From 000ad0090a0b4eb9889f4c45d35d4d7af2dbbe27 Mon Sep 17 00:00:00 2001 From: David Barksdale Date: Mon, 22 Jul 2013 08:26:16 -0500 Subject: Imported Upstream version 0.9.5a --- ChangeLog | 7030 +++++++++++++++ INSTALL | 15 +- Makefile.am | 2 +- Makefile.in | 164 +- README | 90 +- aclocal.m4 | 138 +- compile | 227 +- config.guess | 259 +- config.sub | 213 +- configure | 7231 +++++++++------ configure.ac | 396 +- contrib/Makefile.am | 10 +- contrib/Makefile.in | 148 +- contrib/coverage.sh | 2 +- contrib/gnunet_janitor.py.in | 8 +- contrib/hostlist.cgi | 5 - contrib/hostlist.php | 35 - contrib/pydiffer.py.in | 39 + contrib/report.sh | 62 +- contrib/terminate.py.in | 64 + contrib/testing_hostkeys.ecc | Bin 0 -> 8388608 bytes depcomp | 190 +- doc/Makefile.am | 2 +- doc/Makefile.in | 94 +- doc/README.mysql | 95 - doc/README.postgres | 49 - doc/man/Makefile.am | 9 + doc/man/Makefile.in | 179 +- doc/man/gnunet-arm.1 | 4 +- doc/man/gnunet-ats.1 | 64 + doc/man/gnunet-auto-share.1 | 86 + doc/man/gnunet-config.1 | 43 + doc/man/gnunet-dns2gns.1 | 46 + doc/man/gnunet-download.1 | 2 +- doc/man/gnunet-ecc.1 | 43 + doc/man/gnunet-gns-fcfsd.1 | 38 + doc/man/gnunet-gns-proxy.1 | 41 + doc/man/gnunet-gns.1 | 36 +- doc/man/gnunet-namestore.1 | 3 + doc/man/gnunet-peerinfo.1 | 8 +- doc/man/gnunet-publish.1 | 10 +- doc/man/gnunet-rsa.1 | 3 + doc/man/gnunet-search.1 | 8 +- doc/man/gnunet-transport.1 | 19 +- doc/man/gnunet-uri.1 | 30 + doc/man/gnunet-vpn.1 | 4 +- doc/man/gnunet.conf.5 | 20 + gnunet_config.h | 194 +- gnunet_config.h.in | 166 +- install-sh | 35 +- ltmain.sh | 4016 ++++++--- m4/Makefile.in | 80 +- m4/argz.m4 | 2 +- m4/libtool.m4 | 2238 +++-- m4/ltdl.m4 | 19 +- m4/ltoptions.m4 | 32 +- m4/ltversion.m4 | 12 +- m4/lt~obsolete.m4 | 12 +- missing | 53 +- pkgconfig/Makefile.am | 36 +- pkgconfig/Makefile.in | 194 +- pkgconfig/gnunetats.pc.in | 12 + pkgconfig/gnunetcore.pc.in | 2 +- pkgconfig/gnunetdatacache.pc.in | 2 +- pkgconfig/gnunetdatastore.pc.in | 2 +- pkgconfig/gnunetdhtlog.pc.in | 12 - pkgconfig/gnunetdns.pc.in | 12 + pkgconfig/gnunetdnsparser.pc.in | 12 + pkgconfig/gnunetgns.pc.in | 12 + pkgconfig/gnunetlockmanager.pc.in | 12 + pkgconfig/gnunetmesh.pc.in | 12 + pkgconfig/gnunetmysql.pc.in | 12 + pkgconfig/gnunetnamestore.pc.in | 12 + pkgconfig/gnunetpostgres.pc.in | 12 + pkgconfig/gnunetstream.pc.in | 12 + pkgconfig/gnunettestbed.pc.in | 12 + pkgconfig/gnunettun.pc.in | 12 + pkgconfig/gnunetvpn.pc.in | 12 + po/POTFILES.in | 74 +- po/de.gmo | Bin 6753 -> 6842 bytes po/de.po | 4990 +++++----- po/es.gmo | Bin 6270 -> 6241 bytes po/es.po | 4949 ++++++---- po/gnunet.pot | 3974 ++++---- po/sv.gmo | Bin 3950 -> 4029 bytes po/sv.po | 4639 ++++++---- po/vi.gmo | Bin 13248 -> 11495 bytes po/vi.po | 4795 ++++++---- po/zh_CN.gmo | Bin 4304 -> 3594 bytes po/zh_CN.po | 4473 +++++---- src/Makefile.am | 15 +- src/Makefile.in | 115 +- src/arm/Makefile.am | 32 +- src/arm/Makefile.in | 295 +- src/arm/arm.conf.in | 9 +- src/arm/arm_api.c | 123 +- src/arm/do_start_process.c | 30 +- src/arm/gnunet-arm.c | 321 +- src/arm/gnunet-service-arm.c | 81 +- src/arm/test_arm_api.c | 26 +- src/arm/test_arm_api_data.conf | 10 +- src/arm/test_exponential_backoff.c | 30 +- src/arm/test_gnunet_arm.py.in | 106 + src/arm/test_gnunet_arm.sh | 65 - src/arm/test_gnunet_service_arm.c | 169 + src/arm/test_gnunet_service_manager.c | 185 - src/ats-tool/Makefile.am | 21 + src/ats-tool/Makefile.in | 685 ++ src/ats-tool/gnunet-ats.c | 539 ++ src/ats/Makefile.am | 196 +- src/ats/Makefile.in | 735 +- src/ats/ats.conf.in | 15 +- src/ats/ats.h | 15 + src/ats/ats_api_performance.c | 294 +- src/ats/ats_api_scheduling.c | 371 +- src/ats/gnunet-service-ats.c | 15 +- src/ats/gnunet-service-ats_addresses.c | 1541 ++-- src/ats/gnunet-service-ats_addresses.h | 232 +- src/ats/gnunet-service-ats_addresses_mlp.c | 231 +- src/ats/gnunet-service-ats_addresses_mlp.h | 96 +- src/ats/gnunet-service-ats_addresses_simplistic.c | 1377 +++ src/ats/gnunet-service-ats_addresses_simplistic.h | 151 + src/ats/gnunet-service-ats_performance.c | 393 +- src/ats/gnunet-service-ats_performance.h | 26 +- src/ats/gnunet-service-ats_reservations.c | 4 +- src/ats/gnunet-service-ats_scheduling.c | 97 +- src/ats/gnunet-service-ats_scheduling.h | 18 +- src/ats/perf_ats_mlp.c | 372 - src/ats/test_ats_api.conf | 13 +- src/ats/test_ats_api_common.c | 139 + src/ats/test_ats_api_common.h | 75 + src/ats/test_ats_api_performance.c | 596 ++ src/ats/test_ats_api_reset_backoff.c | 308 - src/ats/test_ats_api_scheduling.c | 253 - src/ats/test_ats_api_scheduling_add_address.c | 199 + src/ats/test_ats_api_scheduling_add_session.c | 237 + src/ats/test_ats_api_scheduling_block_and_reset.c | 364 + src/ats/test_ats_api_scheduling_check_min_bw_alt.c | 417 + src/ats/test_ats_api_scheduling_destroy_address.c | 218 + ...ats_api_scheduling_destroy_inbound_connection.c | 223 + src/ats/test_ats_api_scheduling_destroy_session.c | 235 + src/ats/test_ats_api_scheduling_init.c | 141 + src/ats/test_ats_api_scheduling_min_bw.c | 185 + src/ats/test_ats_api_scheduling_update_address.c | 247 + src/ats/test_ats_mlp.c | 195 - src/ats/test_ats_mlp_averaging.c | 178 - src/ats/test_ats_simplistic.c | 380 + src/ats/test_ats_simplistic_change_preference.c | 418 + src/ats/test_ats_simplistic_pref_aging.c | 448 + src/ats/test_ats_simplistic_switch_networks.c | 451 + src/block/Makefile.am | 23 +- src/block/Makefile.in | 210 +- src/block/block.c | 14 +- src/block/plugin_block_template.c | 25 +- src/block/plugin_block_test.c | 14 +- src/block/test_block.c | 77 - src/chat/Makefile.am | 6 +- src/chat/Makefile.in | 261 +- src/chat/chat.c | 21 +- src/chat/chat.conf.in | 1 - src/chat/chat.h | 20 +- src/chat/gnunet-chat.c | 31 +- src/chat/gnunet-service-chat.c | 69 +- src/chat/test_chat.c | 126 +- src/chat/test_chat_data.conf | 5 +- src/chat/test_chat_peer1.conf | 3 - src/chat/test_chat_peer2.conf | 3 - src/chat/test_chat_peer3.conf | 3 - src/chat/test_chat_private.c | 50 +- src/consensus/Makefile.am | 90 + src/consensus/Makefile.in | 1059 +++ src/consensus/consensus.conf.in | 11 + src/consensus/consensus_api.c | 535 ++ src/consensus/gnunet-consensus-ibf.c | 197 + src/consensus/gnunet-consensus-start-peers.c | 172 + src/consensus/gnunet-consensus.c | 336 + src/consensus/gnunet-service-consensus.c | 1835 ++++ src/consensus/ibf.c | 262 + src/consensus/test_consensus.conf | 26 + src/consensus/test_consensus_api.c | 124 + src/core/Makefile.am | 10 +- src/core/Makefile.in | 261 +- src/core/core.conf.in | 2 - src/core/core.h | 4 +- src/core/core_api.c | 513 +- src/core/gnunet-core.c | 146 +- src/core/gnunet-service-core.c | 86 +- src/core/gnunet-service-core_clients.c | 27 +- src/core/gnunet-service-core_kx.c | 37 +- src/core/gnunet-service-core_kx.h | 3 +- src/core/gnunet-service-core_neighbours.c | 27 +- src/core/gnunet-service-core_sessions.c | 19 +- src/core/test_core_api.c | 46 +- src/core/test_core_api_data.conf | 1 - src/core/test_core_api_peer1.conf | 1 - src/core/test_core_api_peer2.conf | 3 +- src/core/test_core_api_reliability.c | 25 +- src/core/test_core_api_send_to_self.c | 110 +- src/core/test_core_api_send_to_self.conf | 2 - src/core/test_core_api_start_only.c | 40 +- src/core/test_core_defaults.conf | 4 +- ...t_core_quota_asymmetric_recv_limited_peer1.conf | 16 +- ...t_core_quota_asymmetric_recv_limited_peer2.conf | 21 +- ...est_core_quota_asymmetric_send_limit_peer1.conf | 19 +- ...est_core_quota_asymmetric_send_limit_peer2.conf | 23 +- src/core/test_core_quota_compliance.c | 24 +- src/core/test_core_quota_peer1.conf | 17 +- src/core/test_core_quota_peer2.conf | 21 +- src/datacache/Makefile.am | 69 +- src/datacache/Makefile.in | 337 +- src/datacache/datacache.c | 74 +- src/datacache/datacache.conf | 8 - src/datacache/perf_datacache.c | 61 +- src/datacache/perf_datacache_data_heap.conf | 5 + src/datacache/perf_datacache_data_mysql.conf | 13 - src/datacache/plugin_datacache_heap.c | 441 + src/datacache/plugin_datacache_mysql.c | 474 - src/datacache/plugin_datacache_postgres.c | 85 +- src/datacache/plugin_datacache_sqlite.c | 126 +- src/datacache/plugin_datacache_template.c | 16 +- src/datacache/test_datacache.c | 68 +- src/datacache/test_datacache_data_heap.conf | 4 + src/datacache/test_datacache_data_mysql.conf | 13 - src/datacache/test_datacache_quota.c | 40 +- src/datastore/Makefile.am | 83 +- src/datastore/Makefile.in | 458 +- src/datastore/datastore.conf.in | 8 +- src/datastore/datastore.h | 6 +- src/datastore/datastore_api.c | 52 +- src/datastore/gnunet-service-datastore.c | 20 +- src/datastore/perf_datastore_api.c | 113 +- src/datastore/perf_plugin_datastore.c | 87 +- src/datastore/perf_plugin_datastore_data_heap.conf | 7 + .../perf_plugin_datastore_data_mysql.conf | 1 - .../perf_plugin_datastore_data_postgres.conf | 1 - .../perf_plugin_datastore_data_sqlite.conf | 1 - src/datastore/plugin_datastore_heap.c | 868 ++ src/datastore/plugin_datastore_mysql.c | 34 +- src/datastore/plugin_datastore_postgres.c | 32 +- src/datastore/plugin_datastore_sqlite.c | 47 +- src/datastore/plugin_datastore_template.c | 22 +- src/datastore/test_datastore_api.c | 122 +- src/datastore/test_datastore_api_data_heap.conf | 20 + src/datastore/test_datastore_api_data_mysql.conf | 1 - .../test_datastore_api_data_postgres.conf | 1 - src/datastore/test_datastore_api_data_sqlite.conf | 3 - src/datastore/test_datastore_api_management.c | 146 +- src/datastore/test_defaults.conf | 6 + src/datastore/test_plugin_datastore.c | 95 +- src/datastore/test_plugin_datastore_data_heap.conf | 6 + .../test_plugin_datastore_data_mysql.conf | 1 - .../test_plugin_datastore_data_postgres.conf | 1 - .../test_plugin_datastore_data_sqlite.conf | 1 - src/dht/Makefile.am | 126 +- src/dht/Makefile.in | 458 +- src/dht/dht.conf.in | 21 +- src/dht/dht.h | 51 +- src/dht/dht_api.c | 198 +- src/dht/dht_test_lib.c | 214 + src/dht/dht_test_lib.h | 95 + src/dht/gnunet-dht-get.c | 86 +- src/dht/gnunet-dht-monitor.c | 126 +- src/dht/gnunet-dht-put.c | 34 +- src/dht/gnunet-service-dht.c | 11 +- src/dht/gnunet-service-dht_clients.c | 190 +- src/dht/gnunet-service-dht_clients.h | 8 +- src/dht/gnunet-service-dht_datacache.c | 94 +- src/dht/gnunet-service-dht_datacache.h | 4 +- src/dht/gnunet-service-dht_hello.c | 4 +- src/dht/gnunet-service-dht_neighbours.c | 151 +- src/dht/gnunet-service-dht_neighbours.h | 6 +- src/dht/gnunet-service-dht_nse.c | 15 + src/dht/gnunet-service-dht_routing.c | 79 +- src/dht/gnunet-service-dht_routing.h | 4 +- src/dht/multipeer_topo.dat | 31 - src/dht/plugin_block_dht.c | 6 +- src/dht/test_dht_2dtorus.conf | 68 +- src/dht/test_dht_api.c | 207 +- src/dht/test_dht_api_data.conf | 11 +- src/dht/test_dht_api_peer1.conf | 8 +- src/dht/test_dht_line.conf | 68 +- src/dht/test_dht_monitor.c | 651 +- src/dht/test_dht_monitor.conf | 57 + src/dht/test_dht_multipeer.c | 859 -- src/dht/test_dht_multipeer.conf | 59 + src/dht/test_dht_multipeer_data.conf | 129 - src/dht/test_dht_multipeer_topology.dat | 11 + src/dht/test_dht_tools.py | 123 + src/dht/test_dht_tools.py.in | 123 + src/dht/test_dht_tools.sh | 73 - src/dht/test_dht_topo.c | 769 +- src/dht/test_dht_twopeer.c | 494 - src/dht/test_dht_twopeer_data.conf | 76 - src/dht/test_dht_twopeer_get_put.c | 590 -- src/dht/test_dht_twopeer_path_tracking.c | 522 -- src/dht/test_dht_twopeer_put_get.c | 510 -- src/dns/Makefile.am | 28 +- src/dns/Makefile.in | 269 +- src/dns/dns.conf.in | 11 +- src/dns/dnsparser.c | 302 +- src/dns/dnsparser.h | 195 + src/dns/dnsstub.c | 561 ++ src/dns/gnunet-dns-monitor.c | 35 +- src/dns/gnunet-dns-redirector.c | 16 +- src/dns/gnunet-helper-dns.c | 88 +- src/dns/gnunet-service-dns.c | 758 +- src/dns/plugin_block_dns.c | 6 +- src/dns/test_gnunet_dns.sh | 30 +- src/dv/Makefile.am | 21 +- src/dv/Makefile.in | 257 +- src/dv/dv.conf.in | 2 - src/dv/dv_api.c | 28 +- src/dv/gnunet-service-dv.c | 36 +- src/dv/test_transport_api_dv.c | 1247 --- src/dv/test_transport_dv_data.conf | 7 +- src/exit/Makefile.am | 33 +- src/exit/Makefile.in | 238 +- src/exit/exit.conf | 21 +- src/exit/exit.h | 6 +- src/exit/gnunet-daemon-exit.c | 836 +- src/exit/gnunet-helper-exit-windows.c | 1568 ++++ src/exit/gnunet-helper-exit.c | 32 +- src/fragmentation/Makefile.am | 7 +- src/fragmentation/Makefile.in | 142 +- src/fragmentation/fragmentation.c | 89 +- src/fragmentation/test_fragmentation.c | 22 +- src/fs/Makefile.am | 136 +- src/fs/Makefile.in | 632 +- src/fs/fs.conf.in | 46 +- src/fs/fs.h | 28 +- src/fs/fs_api.c | 514 +- src/fs/fs_api.h | 41 +- src/fs/fs_dirmetascan.c | 33 +- src/fs/fs_download.c | 101 +- src/fs/fs_file_information.c | 3 +- src/fs/fs_getopt.c | 11 +- src/fs/fs_namespace.c | 194 +- src/fs/fs_namespace_advertise.c | 12 +- src/fs/fs_publish.c | 99 +- src/fs/fs_publish_ksk.c | 4 +- src/fs/fs_search.c | 184 +- src/fs/fs_sharetree.c | 14 +- src/fs/fs_test_lib.c | 904 +- src/fs/fs_test_lib.h | 111 +- src/fs/fs_test_lib_data.conf | 6 + src/fs/fs_unindex.c | 13 +- src/fs/fs_uri.c | 48 +- src/fs/gnunet-auto-share.c | 795 ++ src/fs/gnunet-daemon-fsprofiler.c | 660 ++ src/fs/gnunet-directory.c | 16 +- src/fs/gnunet-download.c | 93 +- src/fs/gnunet-fs-profiler.c | 203 + src/fs/gnunet-fs.c | 15 +- src/fs/gnunet-helper-fs-publish.c | 64 +- src/fs/gnunet-pseudonym.c | 20 +- src/fs/gnunet-publish.c | 56 +- src/fs/gnunet-search.c | 39 +- src/fs/gnunet-service-fs.c | 75 +- src/fs/gnunet-service-fs.h | 15 +- src/fs/gnunet-service-fs_cp.c | 343 +- src/fs/gnunet-service-fs_cp.h | 17 +- src/fs/gnunet-service-fs_indexing.c | 128 +- src/fs/gnunet-service-fs_indexing.h | 2 +- src/fs/gnunet-service-fs_lc.c | 36 +- src/fs/gnunet-service-fs_pe.c | 249 +- src/fs/gnunet-service-fs_pe.h | 8 +- src/fs/gnunet-service-fs_pr.c | 340 +- src/fs/gnunet-service-fs_pr.h | 55 +- src/fs/gnunet-service-fs_push.c | 11 +- src/fs/gnunet-service-fs_put.c | 7 +- src/fs/gnunet-service-fs_stream.c | 1466 +++ src/fs/gnunet-service-fs_stream.h | 91 + src/fs/gnunet-unindex.c | 21 +- src/fs/perf_gnunet_service_fs_p2p.c | 220 +- src/fs/perf_gnunet_service_fs_p2p.conf | 7 + src/fs/perf_gnunet_service_fs_p2p_respect.c | 473 + src/fs/perf_gnunet_service_fs_p2p_trust.c | 418 - src/fs/plugin_block_fs.c | 24 +- src/fs/test_fs_data.conf | 1 - src/fs/test_fs_defaults.conf | 30 +- src/fs/test_fs_directory.c | 6 +- src/fs/test_fs_download.c | 234 +- src/fs/test_fs_download_data.conf | 7 +- src/fs/test_fs_download_indexed.c | 366 - src/fs/test_fs_download_indexed.conf | 10 + src/fs/test_fs_download_persistence.c | 120 +- src/fs/test_fs_download_stream.conf | 10 + src/fs/test_fs_file_information.c | 12 - src/fs/test_fs_file_information_data.conf | 1 - src/fs/test_fs_getopt.c | 7 +- src/fs/test_fs_list_indexed.c | 115 +- src/fs/test_fs_list_indexed_data.conf | 1 - src/fs/test_fs_namespace.c | 86 +- src/fs/test_fs_namespace_data.conf | 1 - src/fs/test_fs_namespace_list_updateable.c | 89 +- src/fs/test_fs_publish.c | 114 +- src/fs/test_fs_publish_data.conf | 1 - src/fs/test_fs_publish_persistence.c | 98 +- src/fs/test_fs_search.c | 98 +- src/fs/test_fs_search_data.conf | 1 - src/fs/test_fs_search_persistence.c | 113 +- src/fs/test_fs_search_probes.c | 80 +- src/fs/test_fs_start_stop.c | 88 +- src/fs/test_fs_test_lib.c | 110 +- src/fs/test_fs_unindex.c | 121 +- src/fs/test_fs_unindex_data.conf | 1 - src/fs/test_fs_unindex_persistence.c | 122 +- src/fs/test_fs_uri.c | 50 +- src/fs/test_gnunet_fs_idx.py.in | 13 +- src/fs/test_gnunet_fs_idx_data.conf | 1 - src/fs/test_gnunet_fs_ns.py.in | 0 src/fs/test_gnunet_fs_ns_data.conf | 1 - src/fs/test_gnunet_fs_psd.py.in | 18 +- src/fs/test_gnunet_fs_psd_data.conf | 1 - src/fs/test_gnunet_fs_rec.py.in | 11 +- src/fs/test_gnunet_fs_rec_data.conf | 1 - src/fs/test_gnunet_service_fs_migration.c | 137 +- src/fs/test_gnunet_service_fs_migration_data.conf | 3 +- src/fs/test_gnunet_service_fs_p2p.c | 115 +- src/fs/test_gnunet_service_fs_p2p_stream.conf | 16 + src/fs/test_plugin_block_fs.c | 77 + src/gns/Makefile.am | 354 +- src/gns/Makefile.in | 826 +- src/gns/gns-helper-service-w32.conf | 4 + src/gns/gns.conf.in | 61 +- src/gns/gns.h | 72 +- src/gns/gns_api.c | 925 +- src/gns/gns_common.c | 79 + src/gns/gns_common.h | 58 + src/gns/gnunet-dns2gns.c | 708 ++ src/gns/gnunet-gns-fcfsd.c | 248 +- src/gns/gnunet-gns-helper-service-w32.c | 749 ++ src/gns/gnunet-gns-proxy-setup-ca | 31 + src/gns/gnunet-gns-proxy.c | 3105 ++++++- src/gns/gnunet-gns.c | 280 +- src/gns/gnunet-service-gns.c | 1389 +-- src/gns/gnunet-service-gns_interceptor.c | 178 +- src/gns/gnunet-service-gns_interceptor.h | 34 +- src/gns/gnunet-service-gns_resolver.c | 4121 ++++++--- src/gns/gnunet-service-gns_resolver.h | 478 +- src/gns/nss/Makefile.am | 25 +- src/gns/nss/Makefile.in | 194 +- src/gns/nss/install-nss-plugin.sh | 8 + src/gns/nss/nss_gns.c | 16 +- src/gns/nss/nss_gns_query.c | 95 +- src/gns/nss/nss_gns_query.h | 43 +- src/gns/nss/uninstall-nss-plugin.sh | 8 + src/gns/plugin_block_gns.c | 135 +- src/gns/test_gns_cname_lookup.c | 449 + src/gns/test_gns_defaults.conf | 6 +- src/gns/test_gns_dht_default.conf | 15 +- src/gns/test_gns_dht_delegated_lookup.c | 274 +- src/gns/test_gns_dht_three_peers.c | 660 ++ src/gns/test_gns_dht_threepeer.c | 524 -- src/gns/test_gns_max_queries.c | 279 +- src/gns/test_gns_ns_lookup.c | 446 + src/gns/test_gns_pseu_shorten.c | 462 +- src/gns/test_gns_revocation.c | 285 + src/gns/test_gns_simple_delegated_lookup.c | 319 +- src/gns/test_gns_simple_get_authority.c | 233 +- src/gns/test_gns_simple_lookup.c | 331 +- src/gns/test_gns_simple_lookup.conf | 23 +- src/gns/test_gns_simple_mx_lookup.c | 265 +- src/gns/test_gns_simple_shorten.c | 253 +- src/gns/test_gns_simple_srv_lookup.c | 308 + src/gns/test_gns_simple_zkey_lookup.c | 228 +- src/gns/w32nsp-install.c | 81 + src/gns/w32nsp-resolve.c | 369 + src/gns/w32nsp-uninstall.c | 30 + src/gns/w32nsp.c | 705 ++ ...25GVU8TTV0PBNNN8JVCPUEDFV1UHJJU884JD25V0T0.zkey | Bin 0 -> 914 bytes ...1B40QLEMTG5D8G1CN6EN16QUSG5R2DT71GRJN34LSG.zkey | Bin 0 -> 914 bytes src/gns/zonefiles/test_zonekey | Bin 0 -> 914 bytes src/hello/Makefile.am | 5 +- src/hello/Makefile.in | 142 +- src/hello/address.c | 2 +- src/hello/gnunet-hello.c | 4 - src/hello/hello.c | 357 +- src/hello/test_hello.c | 71 +- src/hostlist/Makefile.am | 8 +- src/hostlist/Makefile.in | 263 +- src/hostlist/gnunet-daemon-hostlist.c | 7 +- src/hostlist/hostlist-client.c | 69 +- src/hostlist/hostlist-server.c | 9 +- src/hostlist/hostlist.conf | 3 +- src/hostlist/test_gnunet_daemon_hostlist.c | 16 +- .../test_gnunet_daemon_hostlist_learning.c | 23 +- .../test_gnunet_daemon_hostlist_peer1.conf | 2 - .../test_gnunet_daemon_hostlist_peer2.conf | 1 - .../test_gnunet_daemon_hostlist_reconnect.c | 30 +- src/hostlist/test_hostlist_defaults.conf | 7 +- src/hostlist/test_learning_adv_peer.conf | 1 - src/hostlist/test_learning_learn_peer.conf | 1 - src/hostlist/test_learning_learn_peer2.conf | 1 - src/include/Makefile.am | 19 +- src/include/Makefile.in | 160 +- src/include/block_dns.h | 2 +- src/include/block_fs.h | 4 +- src/include/block_gns.h | 30 +- src/include/block_mesh.h | 64 + src/include/block_regex.h | 120 + src/include/gauger.h | 45 +- src/include/gns_protocol.h | 161 + src/include/gnunet_applications.h | 15 + src/include/gnunet_arm_service.h | 3 + src/include/gnunet_ats_service.h | 136 +- src/include/gnunet_block_lib.h | 43 +- src/include/gnunet_block_plugin.h | 4 +- src/include/gnunet_chat_service.h | 6 +- src/include/gnunet_common.h | 131 +- src/include/gnunet_configuration_lib.h | 47 + src/include/gnunet_constants.h | 33 +- src/include/gnunet_container_lib.h | 192 +- src/include/gnunet_core_service.h | 53 +- src/include/gnunet_crypto_lib.h | 449 +- src/include/gnunet_datacache_lib.h | 24 +- src/include/gnunet_datacache_plugin.h | 16 +- src/include/gnunet_datastore_plugin.h | 13 +- src/include/gnunet_datastore_service.h | 8 +- src/include/gnunet_dht_service.h | 40 +- src/include/gnunet_disk_lib.h | 248 +- src/include/gnunet_dnsparser_lib.h | 196 + src/include/gnunet_dnsstub_lib.h | 124 + src/include/gnunet_fragmentation_lib.h | 19 +- src/include/gnunet_fs_service.h | 102 +- src/include/gnunet_getopt_lib.h | 24 +- src/include/gnunet_gns_service.h | 172 +- src/include/gnunet_hello_lib.h | 45 + src/include/gnunet_helper_lib.h | 28 +- src/include/gnunet_lockmanager_service.h | 7 +- src/include/gnunet_mesh_service.h | 194 +- src/include/gnunet_namestore_plugin.h | 2 + src/include/gnunet_namestore_service.h | 127 +- src/include/gnunet_nat_lib.h | 42 +- src/include/gnunet_network_lib.h | 39 +- src/include/gnunet_os_lib.h | 72 +- src/include/gnunet_peer_lib.h | 18 + src/include/gnunet_protocols.h | 404 +- src/include/gnunet_pseudonym_lib.h | 14 +- src/include/gnunet_regex_lib.h | 234 +- src/include/gnunet_scheduler_lib.h | 2 + src/include/gnunet_server_lib.h | 26 +- src/include/gnunet_stream_lib.h | 118 +- src/include/gnunet_strings_lib.h | 171 +- src/include/gnunet_testbed_service.h | 973 +- src/include/gnunet_testing_lib-new.h | 299 - src/include/gnunet_testing_lib.h | 1315 +-- src/include/gnunet_time_lib.h | 28 +- src/include/gnunet_transport_plugin.h | 22 +- src/include/gnunet_transport_service.h | 115 +- src/include/gnunet_vpn_service.h | 2 +- src/include/platform.h | 19 +- src/include/winproc.h | 1 + src/integration-tests/Makefile.am | 15 +- src/integration-tests/Makefile.in | 202 +- .../confs/c_bootstrap_server.conf | 42 +- .../confs/c_bootstrap_server_w_massif.conf | 348 + src/integration-tests/confs/c_nat_client.conf | 42 +- src/integration-tests/confs/c_no_nat_client.conf | 42 +- src/integration-tests/confs/c_no_nat_client_2.conf | 39 +- .../confs/c_no_nat_client_http.conf | 41 +- .../confs/c_no_nat_client_http_2.conf | 39 +- .../confs/c_no_nat_client_unix.conf | 41 +- .../confs/c_no_nat_client_unix_2.conf | 39 +- .../confs/c_normal_client_tcp.conf | 42 +- .../confs/c_normal_client_tcp_udp.conf | 42 +- .../confs/c_normal_client_tcp_udp_http.conf | 42 +- src/integration-tests/connection_watchdog.c | 27 +- src/integration-tests/gnunet_testing.py.in | 10 +- src/integration-tests/test_connection_stability.c | 126 - .../test_connection_stability.conf | 82 - .../test_integration_bootstrap_and_connect.py.in | 13 +- ...tion_bootstrap_and_connect_and_disconnect.py.in | 13 +- ..._bootstrap_and_connect_and_disconnect_nat.py.in | 13 +- .../test_integration_clique.py.in | 16 +- .../test_integration_clique_nat.py.in | 16 +- .../test_integration_connect_on_restart.py.in | 16 +- .../test_integration_connection_values_tcp.py.in | 10 +- ...est_integration_connection_values_tcp_udp.py.in | 11 +- ...ntegration_connection_values_tcp_udp_http.py.in | 10 +- .../test_integration_disconnect.py.in | 13 +- .../test_integration_restart.py.in | 13 +- src/lockmanager/Makefile.am | 26 +- src/lockmanager/Makefile.in | 283 +- src/lockmanager/gnunet-service-lockmanager.c | 269 +- src/lockmanager/lockmanager.conf.in | 1 - src/lockmanager/lockmanager_api.c | 325 +- src/lockmanager/test_lockmanager_api.c | 171 +- src/lockmanager/test_lockmanager_api.conf | 8 +- .../test_lockmanager_api_acquireretry.c | 224 + src/lockmanager/test_lockmanager_api_lockrelease.c | 168 +- src/lockmanager/test_lockmanager_api_servercrash.c | 190 +- src/mesh/Makefile.am | 251 +- src/mesh/Makefile.in | 788 +- src/mesh/gnunet-mesh.c | 235 + src/mesh/gnunet-service-mesh-new.c | 8483 +++++++++++++++++ src/mesh/gnunet-service-mesh.c | 9530 ++++++++++++++------ src/mesh/mesh.conf.in | 13 +- src/mesh/mesh.h | 247 +- src/mesh/mesh_api.c | 998 +- src/mesh/mesh_common.c | 250 + src/mesh/mesh_protocol.h | 126 +- src/mesh/mesh_test_lib.c | 297 + src/mesh/mesh_test_lib.h | 106 + src/mesh/mesh_tunnel_tree.c | 121 +- src/mesh/mesh_tunnel_tree.h | 47 +- src/mesh/plugin_block_mesh.c | 205 + src/mesh/test_mesh.conf | 20 +- src/mesh/test_mesh_2dtorus.c | 320 +- src/mesh/test_mesh_2dtorus.conf | 62 +- src/mesh/test_mesh_api.c | 104 +- src/mesh/test_mesh_local_1.c | 111 +- src/mesh/test_mesh_local_2.c | 109 +- src/mesh/test_mesh_local_traffic.c | 526 ++ src/mesh/test_mesh_path.conf | 69 - src/mesh/test_mesh_regex.c | 444 + src/mesh/test_mesh_small.c | 987 +- src/mesh/test_mesh_small.conf | 63 +- src/mesh/test_mesh_tree_api.c | 67 +- src/mysql/Makefile.am | 2 +- src/mysql/Makefile.in | 123 +- src/namestore/Makefile.am | 72 +- src/namestore/Makefile.in | 411 +- src/namestore/gnunet-namestore.c | 402 +- src/namestore/gnunet-service-namestore.c | 2662 +++--- src/namestore/namestore.conf.in | 16 +- src/namestore/namestore.h | 78 +- src/namestore/namestore_api.c | 1281 ++- src/namestore/namestore_common.c | 422 +- src/namestore/plugin_namestore_postgres.c | 677 ++ src/namestore/plugin_namestore_sqlite.c | 40 +- src/namestore/test_namestore_api.c | 233 +- src/namestore/test_namestore_api.conf | 16 +- src/namestore/test_namestore_api_create.c | 227 +- src/namestore/test_namestore_api_create_update.c | 359 +- src/namestore/test_namestore_api_lookup.c | 277 +- .../test_namestore_api_lookup_specific_type.c | 231 +- src/namestore/test_namestore_api_put.c | 187 +- src/namestore/test_namestore_api_remove.c | 180 +- ...test_namestore_api_remove_not_existing_record.c | 179 +- src/namestore/test_namestore_api_sign_verify.c | 57 +- src/namestore/test_namestore_api_zone_iteration.c | 231 +- ...st_namestore_api_zone_iteration_specific_zone.c | 185 +- .../test_namestore_api_zone_iteration_stop.c | 187 +- src/namestore/test_namestore_api_zone_to_name.c | 148 +- .../test_namestore_record_serialization.c | 10 +- src/namestore/test_plugin_namestore.c | 26 +- src/namestore/test_plugin_namestore_postgres.conf | 3 + src/nat/Makefile.am | 20 +- src/nat/Makefile.in | 264 +- src/nat/gnunet-nat-server.c | 7 + src/nat/nat.c | 37 +- src/nat/nat_auto.c | 584 ++ src/nat/nat_mini.c | 16 +- src/nat/test_nat_data.conf | 7 +- src/nat/test_nat_mini.c | 11 - src/nat/test_nat_test.c | 2 +- src/nat/test_nat_test_data.conf | 2 - src/nse/Makefile.am | 11 +- src/nse/Makefile.in | 237 +- src/nse/gnunet-nse-profiler.c | 1264 +-- src/nse/gnunet-service-nse.c | 228 +- src/nse/nse.conf.in | 1 - src/nse/nse_api.c | 11 +- src/nse/nse_profiler_test.conf | 9 +- src/nse/test_nse.conf | 13 +- src/nse/test_nse_api.c | 92 +- src/nse/test_nse_multipeer.c | 298 +- src/peerinfo-tool/Makefile.am | 2 +- src/peerinfo-tool/Makefile.in | 131 +- src/peerinfo-tool/gnunet-peerinfo.c | 371 +- src/peerinfo-tool/gnunet-peerinfo_plugins.c | 12 +- src/peerinfo-tool/test_gnunet_peerinfo.py.in | 10 +- src/peerinfo-tool/test_gnunet_peerinfo_data.conf | 7 + src/peerinfo/Makefile.am | 9 +- src/peerinfo/Makefile.in | 244 +- src/peerinfo/gnunet-service-peerinfo.c | 256 +- src/peerinfo/peerinfo.conf.in | 8 +- src/peerinfo/peerinfo.h | 3 +- src/peerinfo/peerinfo_api.c | 62 +- src/peerinfo/perf_peerinfo_api.c | 76 +- src/peerinfo/test_peerinfo_api.c | 80 +- src/peerinfo/test_peerinfo_api_data.conf | 1 - src/postgres/Makefile.in | 118 +- src/pt/Makefile.am | 75 +- src/pt/Makefile.in | 505 +- src/pt/gnunet-daemon-pt.c | 25 +- src/pt/pt.conf | 1 - src/pt/test_gns_vpn.c | 596 ++ src/pt/test_gns_vpn.conf | 58 + src/pt/test_gnunet_vpn.c | 481 + src/pt/test_gnunet_vpn.conf | 49 + src/regex/Makefile.am | 155 +- src/regex/Makefile.in | 501 +- src/regex/gnunet-daemon-regexprofiler.c | 472 + src/regex/gnunet-regex-profiler.c | 1889 ++++ src/regex/gnunet-regex-simulation-profiler.c | 711 ++ src/regex/perf-regex.c | 87 + src/regex/plugin_block_regex.c | 256 + src/regex/regex.c | 3407 ++++--- src/regex/regex_block_lib.c | 210 + src/regex/regex_block_lib.h | 98 + src/regex/regex_dht.c | 790 ++ src/regex/regex_graph.c | 317 + src/regex/regex_internal.h | 484 + src/regex/regex_random.c | 170 + src/regex/regex_simulation_profiler_test.conf | 7 + src/regex/regex_test_lib.c | 291 + src/regex/regex_test_lib.h | 80 + src/regex/test_regex_eval_api.c | 284 +- src/regex/test_regex_graph_api.c | 157 + src/regex/test_regex_iptoregex.c | 103 + src/regex/test_regex_iterate_api.c | 229 +- src/regex/test_regex_proofs.c | 171 + src/statistics/Makefile.am | 23 +- src/statistics/Makefile.in | 265 +- src/statistics/gnunet-service-statistics.c | 15 + src/statistics/gnunet-statistics.c | 179 +- src/statistics/statistics.conf.in | 1 - src/statistics/statistics_api.c | 63 +- src/statistics/test_gnunet_statistics.py.in | 148 + src/statistics/test_gnunet_statistics.sh | 199 - src/statistics/test_statistics_api.c | 59 +- src/statistics/test_statistics_api_data.conf | 5 +- src/statistics/test_statistics_api_loop.c | 47 +- src/statistics/test_statistics_api_watch.c | 38 +- .../test_statistics_api_watch_zero_value.c | 50 +- src/stream/Makefile.am | 58 +- src/stream/Makefile.in | 245 +- src/stream/perf_stream_api.c | 1047 +++ src/stream/stream.h | 190 + src/stream/stream_api.c | 1814 ++-- src/stream/stream_protocol.h | 195 - src/stream/test_stream_2peers.c | 449 +- src/stream/test_stream_2peers_halfclose.c | 488 +- src/stream/test_stream_big.c | 429 + src/stream/test_stream_local.c | 225 +- src/stream/test_stream_local.conf | 37 +- src/stream/test_stream_sequence_wraparound.c | 425 + src/sysmon/Makefile.am | 73 + src/sysmon/Makefile.in | 928 ++ src/sysmon/gnunet-service-sysmon.c | 838 ++ src/sysmon/sysmon-properties.conf | 14 + src/sysmon/sysmon.conf.in | 11 + src/sysmon/test_glibtop.c | 53 + src/sysmon/test_glibtop_network.c | 88 + src/sysmon/test_glibtop_process.c | 122 + src/template/Makefile.am | 6 +- src/template/Makefile.in | 233 +- src/template/gnunet-template.c | 16 +- src/template/template.conf | 1 - src/template/test_template_api.c | 5 +- src/testbed/Makefile.am | 268 +- src/testbed/Makefile.in | 989 +- src/testbed/gnunet-helper-testbed.c | 489 + src/testbed/gnunet-service-testbed.c | 2227 +++++ src/testbed/gnunet-service-testbed.h | 911 ++ src/testbed/gnunet-service-testbed_cache.c | 1048 +++ src/testbed/gnunet-service-testbed_oc.c | 1595 ++++ src/testbed/gnunet-testbed-profiler.c | 283 + src/testbed/gnunet_mpi_test.c | 107 + src/testbed/ll_master.c | 92 + src/testbed/ll_monitor.c | 76 + src/testbed/overlay_topology.txt | 5 + src/testbed/sample.job | 16 + src/testbed/sample_hosts.txt | 15 + src/testbed/test_gnunet_helper_testbed.c | 249 + src/testbed/test_testbed_api.c | 464 + src/testbed/test_testbed_api.conf | 91 + src/testbed/test_testbed_api_2peers_1controller.c | 532 ++ src/testbed/test_testbed_api_3peers_3controllers.c | 946 ++ src/testbed/test_testbed_api_controllerlink.c | 749 ++ src/testbed/test_testbed_api_hosts.c | 130 + src/testbed/test_testbed_api_operations.c | 430 + src/testbed/test_testbed_api_test.c | 241 + src/testbed/test_testbed_api_testbed_run.c | 223 + ...st_testbed_api_testbed_run_topology2dtorus.conf | 79 + ...est_testbed_api_testbed_run_topologyclique.conf | 79 + ...t_testbed_api_testbed_run_topologyfromfile.conf | 80 + .../test_testbed_api_testbed_run_topologyline.conf | 79 + ...est_testbed_api_testbed_run_topologyrandom.conf | 79 + .../test_testbed_api_testbed_run_topologyring.conf | 79 + ..._testbed_api_testbed_run_topologyscalefree.conf | 79 + ...testbed_api_testbed_run_topologysmallworld.conf | 83 + ...bed_api_testbed_run_topologysmallworldring.conf | 83 + src/testbed/test_testbed_api_topology.c | 172 + src/testbed/test_testbed_api_topology_clique.c | 168 + src/testbed/testbed.conf | 0 src/testbed/testbed.conf.in | 18 + src/testbed/testbed.h | 272 +- src/testbed/testbed_api.c | 2702 +++++- src/testbed/testbed_api.h | 590 ++ src/testbed/testbed_api_hosts.c | 566 +- src/testbed/testbed_api_hosts.h | 130 +- src/testbed/testbed_api_operations.c | 386 +- src/testbed/testbed_api_operations.h | 88 +- src/testbed/testbed_api_peers.c | 640 +- src/testbed/testbed_api_peers.h | 245 +- src/testbed/testbed_api_services.c | 245 +- src/testbed/testbed_api_statistics.c | 56 + src/testbed/testbed_api_test.c | 111 +- src/testbed/testbed_api_testbed.c | 1207 ++- src/testbed/testbed_api_topology.c | 1000 +- src/testbed/testbed_api_topology.h | 70 + src/testbed/testbed_helper.h | 89 + src/testing/Makefile.am | 298 +- src/testing/Makefile.in | 850 +- src/testing/gnunet-testing-run-service.c | 211 + src/testing/gnunet-testing.c | 229 +- src/testing/helper.c | 75 - src/testing/test_testing.c | 126 - src/testing/test_testing_2dtorus.c | 372 - src/testing/test_testing_2dtorus.conf | 81 - src/testing/test_testing_connect.c | 197 - src/testing/test_testing_connect_peer1.conf | 37 - src/testing/test_testing_connect_peer2.conf | 37 - src/testing/test_testing_data.conf | 7 - src/testing/test_testing_data_remote.conf | 12 - .../test_testing_data_topology_2d_torus.conf | 7 - .../test_testing_data_topology_blacklist.conf | 13 - src/testing/test_testing_data_topology_churn.conf | 10 - src/testing/test_testing_data_topology_clique.conf | 10 - .../test_testing_data_topology_clique_dfs.conf | 13 - .../test_testing_data_topology_clique_minimum.conf | 10 - .../test_testing_data_topology_clique_random.conf | 16 - .../test_testing_data_topology_erdos_renyi.conf | 7 - .../test_testing_data_topology_internat.conf | 7 - src/testing/test_testing_data_topology_none.conf | 37 - src/testing/test_testing_data_topology_ring.conf | 7 - .../test_testing_data_topology_scale_free.conf | 11 - ...est_testing_data_topology_small_world_ring.conf | 8 - ...st_testing_data_topology_small_world_torus.conf | 7 - .../test_testing_data_topology_stability.conf | 9 - src/testing/test_testing_defaults.conf | 14 +- src/testing/test_testing_group.c | 166 - src/testing/test_testing_group_remote.c | 263 - src/testing/test_testing_new_peerstartup.c | 161 - src/testing/test_testing_new_portreservation.c | 90 - src/testing/test_testing_new_servicestartup.c | 110 - src/testing/test_testing_peergroup.c | 157 - src/testing/test_testing_peergroup_data.conf | 22 - src/testing/test_testing_peerstartup.c | 143 + src/testing/test_testing_portreservation.c | 103 + src/testing/test_testing_reconnect.c | 249 - src/testing/test_testing_servicestartup.c | 74 + src/testing/test_testing_topology.c | 1220 --- src/testing/test_testing_topology_blacklist.c | 595 -- src/testing/test_testing_topology_churn.c | 322 - src/testing/testing.c | 3019 +++---- src/testing/testing_group.c | 7038 --------------- src/testing/testing_new.c | 1000 -- src/testing/testing_peergroup.c | 1017 --- src/topology/Makefile.am | 6 +- src/topology/Makefile.in | 220 +- src/topology/gnunet-daemon-topology.c | 59 +- src/topology/test_gnunet_daemon_topology.c | 170 +- src/topology/test_gnunet_daemon_topology_data.conf | 9 +- src/topology/topology.conf | 2 - src/transport/Makefile.am | 471 +- src/transport/Makefile.in | 1542 +++- src/transport/gnunet-helper-transport-wlan.c | 163 +- src/transport/gnunet-service-transport.c | 196 +- src/transport/gnunet-service-transport.h | 31 + src/transport/gnunet-service-transport_blacklist.c | 29 +- src/transport/gnunet-service-transport_clients.c | 110 +- src/transport/gnunet-service-transport_clients.h | 1 + src/transport/gnunet-service-transport_hello.c | 9 +- .../gnunet-service-transport_manipulation.c | 336 + .../gnunet-service-transport_manipulation.h | 63 + .../gnunet-service-transport_neighbours.c | 537 +- .../gnunet-service-transport_neighbours.h | 21 +- src/transport/gnunet-service-transport_plugins.c | 35 +- src/transport/gnunet-service-transport_plugins.h | 13 + .../gnunet-service-transport_validation.c | 212 +- .../gnunet-service-transport_validation.h | 4 +- .../gnunet-transport-certificate-creation | 148 - .../gnunet-transport-certificate-creation.c | 39 +- src/transport/gnunet-transport-wlan-receiver.c | 116 + src/transport/gnunet-transport-wlan-sender.c | 80 +- src/transport/gnunet-transport.c | 687 +- src/transport/plugin_transport_http.c | 1743 ---- src/transport/plugin_transport_http.h | 553 -- src/transport/plugin_transport_http_client.c | 1755 +++- src/transport/plugin_transport_http_common.c | 408 + src/transport/plugin_transport_http_common.h | 168 + src/transport/plugin_transport_http_server.c | 3019 +++++-- src/transport/plugin_transport_tcp.c | 258 +- src/transport/plugin_transport_template.c | 62 +- src/transport/plugin_transport_udp.c | 1572 ++-- src/transport/plugin_transport_udp.h | 18 +- src/transport/plugin_transport_udp_broadcasting.c | 33 +- src/transport/plugin_transport_unix.c | 309 +- src/transport/plugin_transport_wlan.c | 123 +- src/transport/plugin_transport_wlan.h | 23 + src/transport/template_cfg_peer1.conf | 7 +- src/transport/template_cfg_peer2.conf | 6 +- src/transport/test_http_common.c | 264 + src/transport/test_plugin_hostkey | Bin 0 -> 914 bytes src/transport/test_plugin_hostkey.ecc | Bin 0 -> 2048 bytes src/transport/test_plugin_transport.c | 728 ++ src/transport/test_plugin_transport_data.conf | 42 +- src/transport/test_quota_compliance.c | 55 +- src/transport/test_quota_compliance_data.conf | 1 - ...est_quota_compliance_http_asymmetric_peer1.conf | 6 +- ...est_quota_compliance_http_asymmetric_peer2.conf | 8 +- .../test_quota_compliance_http_peer1.conf | 6 +- .../test_quota_compliance_http_peer2.conf | 8 +- ...st_quota_compliance_https_asymmetric_peer1.conf | 8 +- ...st_quota_compliance_https_asymmetric_peer2.conf | 5 +- .../test_quota_compliance_https_peer1.conf | 8 +- .../test_quota_compliance_https_peer2.conf | 5 +- ...test_quota_compliance_tcp_asymmetric_peer1.conf | 1 - ...test_quota_compliance_tcp_asymmetric_peer2.conf | 1 - src/transport/test_quota_compliance_tcp_peer1.conf | 1 - src/transport/test_quota_compliance_tcp_peer2.conf | 1 - src/transport/test_quota_compliance_udp_peer1.conf | 1 - src/transport/test_quota_compliance_udp_peer2.conf | 1 - ...est_quota_compliance_unix_asymmetric_peer1.conf | 1 - ...est_quota_compliance_unix_asymmetric_peer2.conf | 1 - .../test_quota_compliance_unix_peer1.conf | 1 - .../test_quota_compliance_unix_peer2.conf | 1 - ...est_quota_compliance_wlan_asymmetric_peer1.conf | 29 + ...est_quota_compliance_wlan_asymmetric_peer2.conf | 29 + .../test_quota_compliance_wlan_peer1.conf | 29 + .../test_quota_compliance_wlan_peer2.conf | 29 + src/transport/test_transport_api.c | 13 - .../test_transport_api_bidirectional_connect.c | 7 - ..._transport_api_bidirectional_connect_peer1.conf | 4 +- ..._transport_api_bidirectional_connect_peer2.conf | 3 +- src/transport/test_transport_api_blacklisting.c | 24 - src/transport/test_transport_api_data.conf | 1 - src/transport/test_transport_api_disconnect.c | 22 - .../test_transport_api_disconnect_tcp_peer1.conf | 2 - .../test_transport_api_disconnect_tcp_peer2.conf | 1 - .../test_transport_api_http_nat_peer1.conf | 38 - .../test_transport_api_http_nat_peer2.conf | 31 - src/transport/test_transport_api_http_peer1.conf | 7 +- src/transport/test_transport_api_http_peer2.conf | 8 +- .../test_transport_api_http_reverse_peer1.conf | 39 + .../test_transport_api_http_reverse_peer2.conf | 40 + .../test_transport_api_https_nat_peer1.conf | 36 - .../test_transport_api_https_nat_peer2.conf | 33 - src/transport/test_transport_api_https_peer1.conf | 6 +- src/transport/test_transport_api_https_peer2.conf | 8 +- src/transport/test_transport_api_limited_sockets.c | 77 +- ...st_transport_api_limited_sockets_tcp_peer1.conf | 1 - ...st_transport_api_limited_sockets_tcp_peer2.conf | 1 - .../test_transport_api_manipulation_recv_tcp.c | 493 + ..._transport_api_manipulation_recv_tcp_peer1.conf | 30 + ..._transport_api_manipulation_recv_tcp_peer2.conf | 30 + .../test_transport_api_manipulation_send_tcp.c | 500 + ..._transport_api_manipulation_send_tcp_peer1.conf | 30 + ..._transport_api_manipulation_send_tcp_peer2.conf | 30 + src/transport/test_transport_api_multi_peer1.conf | 3 +- src/transport/test_transport_api_multi_peer2.conf | 3 +- src/transport/test_transport_api_reliability.c | 25 - ...t_transport_api_reliability_http_nat_peer1.conf | 38 - ...t_transport_api_reliability_http_nat_peer2.conf | 35 - .../test_transport_api_reliability_http_peer1.conf | 6 +- .../test_transport_api_reliability_http_peer2.conf | 10 +- ..._transport_api_reliability_https_nat_peer1.conf | 36 - ..._transport_api_reliability_https_nat_peer2.conf | 33 - ...test_transport_api_reliability_https_peer1.conf | 8 +- ...test_transport_api_reliability_https_peer2.conf | 5 +- ...st_transport_api_reliability_tcp_nat_peer1.conf | 1 - ...st_transport_api_reliability_tcp_nat_peer2.conf | 1 - .../test_transport_api_reliability_tcp_peer1.conf | 1 - .../test_transport_api_reliability_tcp_peer2.conf | 2 - .../test_transport_api_reliability_wlan_peer1.conf | 1 - .../test_transport_api_reliability_wlan_peer2.conf | 1 - src/transport/test_transport_api_restart_1peer.c | 15 +- src/transport/test_transport_api_restart_2peers.c | 14 +- .../test_transport_api_tcp_nat_peer1.conf | 2 - .../test_transport_api_tcp_nat_peer2.conf | 2 - src/transport/test_transport_api_tcp_peer1.conf | 2 - src/transport/test_transport_api_tcp_peer2.conf | 1 - src/transport/test_transport_api_timeout.c | 14 - .../test_transport_api_timeout_http_peer1.conf | 7 +- .../test_transport_api_timeout_http_peer2.conf | 9 +- .../test_transport_api_timeout_https_peer1.conf | 9 +- .../test_transport_api_timeout_https_peer2.conf | 6 +- .../test_transport_api_timeout_tcp_peer1.conf | 1 - .../test_transport_api_timeout_tcp_peer2.conf | 1 - .../test_transport_api_timeout_udp_peer1.conf | 1 - .../test_transport_api_timeout_udp_peer2.conf | 1 - .../test_transport_api_timeout_unix_peer1.conf | 1 - .../test_transport_api_timeout_unix_peer2.conf | 1 - .../test_transport_api_udp_nat_peer1.conf | 2 - .../test_transport_api_udp_nat_peer2.conf | 2 - src/transport/test_transport_api_udp_peer1.conf | 1 - src/transport/test_transport_api_udp_peer2.conf | 1 - src/transport/test_transport_api_unix_peer1.conf | 1 - src/transport/test_transport_api_unix_peer2.conf | 1 - src/transport/test_transport_api_unreliability.c | 60 +- .../test_transport_api_unreliability_constant.c | 24 - ...sport_api_unreliability_constant_udp_peer1.conf | 1 - ...sport_api_unreliability_constant_udp_peer2.conf | 1 - ...test_transport_api_unreliability_udp_peer1.conf | 1 - ...test_transport_api_unreliability_udp_peer2.conf | 1 - ...est_transport_api_unreliability_unix_peer1.conf | 1 - ...est_transport_api_unreliability_unix_peer2.conf | 1 - ...est_transport_api_unreliability_wlan_peer1.conf | 1 - ...est_transport_api_unreliability_wlan_peer2.conf | 1 - src/transport/test_transport_api_wlan_peer1.conf | 3 - src/transport/test_transport_api_wlan_peer2.conf | 3 - src/transport/test_transport_defaults.conf | 4 +- src/transport/test_transport_startonly.c | 27 +- src/transport/test_transport_startonly.conf | 1 - src/transport/test_transport_testing.c | 34 +- src/transport/test_transport_testing_restart.c | 151 + src/transport/test_transport_testing_startstop.c | 132 + src/transport/transport-testing.c | 346 +- src/transport/transport-testing.h | 85 +- src/transport/transport.conf.in | 29 +- src/transport/transport.h | 76 + src/transport/transport_api.c | 406 +- src/transport/transport_api_address_lookup.c | 4 +- src/tun/Makefile.am | 3 +- src/tun/Makefile.in | 138 +- src/util/Makefile.am | 66 +- src/util/Makefile.in | 606 +- src/util/bandwidth.c | 7 +- src/util/client.c | 106 +- src/util/common_allocation.c | 58 +- src/util/common_logging.c | 437 +- src/util/configuration.c | 468 +- src/util/connection.c | 32 +- src/util/container_bloomfilter.c | 32 +- src/util/container_heap.c | 2 + src/util/container_meta_data.c | 299 +- src/util/container_multihashmap.c | 529 +- src/util/crypto_crc.c | 3 +- src/util/crypto_ecc.c | 1082 +++ src/util/crypto_hash.c | 72 +- src/util/crypto_ksk.c | 30 +- src/util/crypto_random.c | 51 +- src/util/crypto_rsa.c | 651 +- src/util/disk.c | 340 +- src/util/getopt.c | 110 +- src/util/getopt_helpers.c | 42 +- src/util/gnunet-config.c | 184 + src/util/gnunet-ecc.c | 249 + src/util/gnunet-resolver.c | 15 +- src/util/gnunet-rsa.c | 142 +- src/util/gnunet-service-resolver.c | 15 + src/util/gnunet-uri.c | 184 + src/util/helper.c | 119 +- src/util/network.c | 677 +- src/util/os_installation.c | 423 +- src/util/os_priority.c | 1137 ++- src/util/peer.c | 100 +- src/util/perf_crypto_hash.c | 10 +- src/util/perf_malloc.c | 66 + src/util/program.c | 28 +- src/util/pseudonym.c | 61 +- src/util/resolver.conf.in | 1 - src/util/resolver_api.c | 2 +- src/util/scheduler.c | 18 +- src/util/server.c | 136 +- src/util/service.c | 106 +- src/util/speedup.c | 5 +- src/util/strings.c | 294 +- src/util/test_client.c | 29 +- src/util/test_common_logging_runtime_loglevels.c | 62 +- src/util/test_configuration.c | 3 +- src/util/test_connection.c | 54 +- src/util/test_connection_addressing.c | 28 +- src/util/test_connection_receive_cancel.c | 2 - src/util/test_connection_timeout.c | 34 +- src/util/test_connection_timeout_no_connect.c | 32 +- src/util/test_connection_transmit_cancel.c | 32 +- src/util/test_container_bloomfilter.c | 8 +- src/util/test_container_multihashmap.c | 6 +- src/util/test_crypto_ecc.c | 241 + src/util/test_crypto_hash.c | 20 +- src/util/test_crypto_ksk.c | 23 +- src/util/test_crypto_rsa.c | 105 +- src/util/test_disk.c | 2 +- src/util/test_getopt.c | 13 +- src/util/test_os_network.c | 32 +- src/util/test_os_priority.c | 1 - src/util/test_os_start_process.c | 61 +- src/util/test_peer.c | 9 +- src/util/test_plugin.c | 21 +- src/util/test_pseudonym.c | 28 +- src/util/test_resolver_api.c | 76 +- src/util/test_resolver_api_data.conf | 1 - src/util/test_scheduler.c | 13 +- src/util/test_scheduler_delay.c | 19 +- src/util/test_server.c | 2 - src/util/test_server_disconnect.c | 1 - src/util/test_server_mst_interrupt.c | 37 +- src/util/test_server_with_client.c | 28 +- src/util/test_server_with_client_unix.c | 30 +- src/util/test_service.c | 32 +- src/util/test_strings.c | 59 +- src/util/test_time.c | 16 +- src/util/time.c | 24 +- src/util/util.conf | 3 + src/util/w32cat.c | 108 + src/util/win.c | 1329 +++ src/util/win.cc | 1266 --- src/vpn/Makefile.am | 77 +- src/vpn/Makefile.in | 485 +- src/vpn/gnunet-helper-vpn-windows.c | 1557 ++++ src/vpn/gnunet-service-vpn.c | 124 +- src/vpn/gnunet-vpn.c | 24 +- src/vpn/test_gnunet_vpn.c | 599 -- src/vpn/test_gnunet_vpn.conf | 43 - src/vpn/vpn.conf.in | 3 +- src/vpn/vpn.h | 4 +- src/vpn/vpn_api.c | 4 +- 1112 files changed, 184610 insertions(+), 87399 deletions(-) delete mode 100644 contrib/hostlist.cgi delete mode 100644 contrib/hostlist.php create mode 100644 contrib/pydiffer.py.in create mode 100644 contrib/terminate.py.in create mode 100644 contrib/testing_hostkeys.ecc delete mode 100644 doc/README.mysql delete mode 100644 doc/README.postgres create mode 100644 doc/man/gnunet-ats.1 create mode 100644 doc/man/gnunet-auto-share.1 create mode 100644 doc/man/gnunet-config.1 create mode 100644 doc/man/gnunet-dns2gns.1 create mode 100644 doc/man/gnunet-ecc.1 create mode 100644 doc/man/gnunet-gns-fcfsd.1 create mode 100644 doc/man/gnunet-gns-proxy.1 create mode 100644 doc/man/gnunet-uri.1 create mode 100644 doc/man/gnunet.conf.5 mode change 100755 => 100644 ltmain.sh create mode 100644 pkgconfig/gnunetats.pc.in delete mode 100644 pkgconfig/gnunetdhtlog.pc.in create mode 100644 pkgconfig/gnunetdns.pc.in create mode 100644 pkgconfig/gnunetdnsparser.pc.in create mode 100644 pkgconfig/gnunetgns.pc.in create mode 100644 pkgconfig/gnunetlockmanager.pc.in create mode 100644 pkgconfig/gnunetmesh.pc.in create mode 100644 pkgconfig/gnunetmysql.pc.in create mode 100644 pkgconfig/gnunetnamestore.pc.in create mode 100644 pkgconfig/gnunetpostgres.pc.in create mode 100644 pkgconfig/gnunetstream.pc.in create mode 100644 pkgconfig/gnunettestbed.pc.in create mode 100644 pkgconfig/gnunettun.pc.in create mode 100644 pkgconfig/gnunetvpn.pc.in create mode 100644 src/arm/test_gnunet_arm.py.in delete mode 100755 src/arm/test_gnunet_arm.sh create mode 100644 src/arm/test_gnunet_service_arm.c delete mode 100644 src/arm/test_gnunet_service_manager.c create mode 100644 src/ats-tool/Makefile.am create mode 100644 src/ats-tool/Makefile.in create mode 100644 src/ats-tool/gnunet-ats.c create mode 100644 src/ats/gnunet-service-ats_addresses_simplistic.c create mode 100644 src/ats/gnunet-service-ats_addresses_simplistic.h delete mode 100644 src/ats/perf_ats_mlp.c create mode 100644 src/ats/test_ats_api_common.c create mode 100644 src/ats/test_ats_api_common.h create mode 100644 src/ats/test_ats_api_performance.c delete mode 100644 src/ats/test_ats_api_reset_backoff.c delete mode 100644 src/ats/test_ats_api_scheduling.c create mode 100644 src/ats/test_ats_api_scheduling_add_address.c create mode 100644 src/ats/test_ats_api_scheduling_add_session.c create mode 100644 src/ats/test_ats_api_scheduling_block_and_reset.c create mode 100644 src/ats/test_ats_api_scheduling_check_min_bw_alt.c create mode 100644 src/ats/test_ats_api_scheduling_destroy_address.c create mode 100644 src/ats/test_ats_api_scheduling_destroy_inbound_connection.c create mode 100644 src/ats/test_ats_api_scheduling_destroy_session.c create mode 100644 src/ats/test_ats_api_scheduling_init.c create mode 100644 src/ats/test_ats_api_scheduling_min_bw.c create mode 100644 src/ats/test_ats_api_scheduling_update_address.c delete mode 100644 src/ats/test_ats_mlp.c delete mode 100644 src/ats/test_ats_mlp_averaging.c create mode 100644 src/ats/test_ats_simplistic.c create mode 100644 src/ats/test_ats_simplistic_change_preference.c create mode 100644 src/ats/test_ats_simplistic_pref_aging.c create mode 100644 src/ats/test_ats_simplistic_switch_networks.c delete mode 100644 src/block/test_block.c create mode 100644 src/consensus/Makefile.am create mode 100644 src/consensus/Makefile.in create mode 100644 src/consensus/consensus.conf.in create mode 100644 src/consensus/consensus_api.c create mode 100644 src/consensus/gnunet-consensus-ibf.c create mode 100644 src/consensus/gnunet-consensus-start-peers.c create mode 100644 src/consensus/gnunet-consensus.c create mode 100644 src/consensus/gnunet-service-consensus.c create mode 100644 src/consensus/ibf.c create mode 100644 src/consensus/test_consensus.conf create mode 100644 src/consensus/test_consensus_api.c create mode 100644 src/datacache/perf_datacache_data_heap.conf delete mode 100644 src/datacache/perf_datacache_data_mysql.conf create mode 100644 src/datacache/plugin_datacache_heap.c delete mode 100644 src/datacache/plugin_datacache_mysql.c create mode 100644 src/datacache/test_datacache_data_heap.conf delete mode 100644 src/datacache/test_datacache_data_mysql.conf create mode 100644 src/datastore/perf_plugin_datastore_data_heap.conf create mode 100644 src/datastore/plugin_datastore_heap.c create mode 100644 src/datastore/test_datastore_api_data_heap.conf create mode 100644 src/datastore/test_plugin_datastore_data_heap.conf create mode 100644 src/dht/dht_test_lib.c create mode 100644 src/dht/dht_test_lib.h delete mode 100644 src/dht/multipeer_topo.dat create mode 100644 src/dht/test_dht_monitor.conf delete mode 100644 src/dht/test_dht_multipeer.c create mode 100644 src/dht/test_dht_multipeer.conf delete mode 100644 src/dht/test_dht_multipeer_data.conf create mode 100644 src/dht/test_dht_multipeer_topology.dat create mode 100755 src/dht/test_dht_tools.py create mode 100644 src/dht/test_dht_tools.py.in delete mode 100755 src/dht/test_dht_tools.sh delete mode 100644 src/dht/test_dht_twopeer.c delete mode 100644 src/dht/test_dht_twopeer_data.conf delete mode 100644 src/dht/test_dht_twopeer_get_put.c delete mode 100644 src/dht/test_dht_twopeer_path_tracking.c delete mode 100644 src/dht/test_dht_twopeer_put_get.c create mode 100644 src/dns/dnsparser.h create mode 100644 src/dns/dnsstub.c delete mode 100644 src/dv/test_transport_api_dv.c create mode 100644 src/exit/gnunet-helper-exit-windows.c create mode 100644 src/fs/gnunet-auto-share.c create mode 100644 src/fs/gnunet-daemon-fsprofiler.c create mode 100644 src/fs/gnunet-fs-profiler.c create mode 100644 src/fs/gnunet-service-fs_stream.c create mode 100644 src/fs/gnunet-service-fs_stream.h create mode 100644 src/fs/perf_gnunet_service_fs_p2p.conf create mode 100644 src/fs/perf_gnunet_service_fs_p2p_respect.c delete mode 100644 src/fs/perf_gnunet_service_fs_p2p_trust.c delete mode 100644 src/fs/test_fs_download_indexed.c create mode 100644 src/fs/test_fs_download_indexed.conf create mode 100644 src/fs/test_fs_download_stream.conf mode change 100644 => 100755 src/fs/test_gnunet_fs_idx.py.in mode change 100644 => 100755 src/fs/test_gnunet_fs_ns.py.in mode change 100644 => 100755 src/fs/test_gnunet_fs_psd.py.in mode change 100644 => 100755 src/fs/test_gnunet_fs_rec.py.in create mode 100644 src/fs/test_gnunet_service_fs_p2p_stream.conf create mode 100644 src/fs/test_plugin_block_fs.c create mode 100644 src/gns/gns-helper-service-w32.conf create mode 100644 src/gns/gns_common.c create mode 100644 src/gns/gns_common.h create mode 100644 src/gns/gnunet-dns2gns.c create mode 100644 src/gns/gnunet-gns-helper-service-w32.c create mode 100644 src/gns/gnunet-gns-proxy-setup-ca create mode 100755 src/gns/nss/install-nss-plugin.sh create mode 100755 src/gns/nss/uninstall-nss-plugin.sh create mode 100644 src/gns/test_gns_cname_lookup.c create mode 100644 src/gns/test_gns_dht_three_peers.c delete mode 100644 src/gns/test_gns_dht_threepeer.c create mode 100644 src/gns/test_gns_ns_lookup.c create mode 100644 src/gns/test_gns_revocation.c create mode 100644 src/gns/test_gns_simple_srv_lookup.c create mode 100644 src/gns/w32nsp-install.c create mode 100644 src/gns/w32nsp-resolve.c create mode 100644 src/gns/w32nsp-uninstall.c create mode 100644 src/gns/w32nsp.c create mode 100644 src/gns/zonefiles/188JSUMKEF25GVU8TTV0PBNNN8JVCPUEDFV1UHJJU884JD25V0T0.zkey create mode 100644 src/gns/zonefiles/OEFL7A4VEF1B40QLEMTG5D8G1CN6EN16QUSG5R2DT71GRJN34LSG.zkey create mode 100644 src/gns/zonefiles/test_zonekey create mode 100644 src/include/block_mesh.h create mode 100644 src/include/block_regex.h create mode 100644 src/include/gns_protocol.h create mode 100644 src/include/gnunet_dnsstub_lib.h delete mode 100644 src/include/gnunet_testing_lib-new.h create mode 100644 src/integration-tests/confs/c_bootstrap_server_w_massif.conf delete mode 100644 src/integration-tests/test_connection_stability.c delete mode 100644 src/integration-tests/test_connection_stability.conf create mode 100644 src/lockmanager/test_lockmanager_api_acquireretry.c create mode 100644 src/mesh/gnunet-mesh.c create mode 100644 src/mesh/gnunet-service-mesh-new.c create mode 100644 src/mesh/mesh_common.c create mode 100644 src/mesh/mesh_test_lib.c create mode 100644 src/mesh/mesh_test_lib.h create mode 100644 src/mesh/plugin_block_mesh.c create mode 100644 src/mesh/test_mesh_local_traffic.c delete mode 100644 src/mesh/test_mesh_path.conf create mode 100644 src/mesh/test_mesh_regex.c create mode 100644 src/namestore/plugin_namestore_postgres.c create mode 100644 src/namestore/test_plugin_namestore_postgres.conf create mode 100644 src/nat/nat_auto.c mode change 100644 => 100755 src/peerinfo-tool/test_gnunet_peerinfo.py.in mode change 100644 => 100755 src/peerinfo/perf_peerinfo_api.c create mode 100644 src/pt/test_gns_vpn.c create mode 100644 src/pt/test_gns_vpn.conf create mode 100644 src/pt/test_gnunet_vpn.c create mode 100644 src/pt/test_gnunet_vpn.conf create mode 100644 src/regex/gnunet-daemon-regexprofiler.c create mode 100644 src/regex/gnunet-regex-profiler.c create mode 100644 src/regex/gnunet-regex-simulation-profiler.c create mode 100644 src/regex/perf-regex.c create mode 100644 src/regex/plugin_block_regex.c create mode 100644 src/regex/regex_block_lib.c create mode 100644 src/regex/regex_block_lib.h create mode 100644 src/regex/regex_dht.c create mode 100644 src/regex/regex_graph.c create mode 100644 src/regex/regex_internal.h create mode 100644 src/regex/regex_random.c create mode 100644 src/regex/regex_simulation_profiler_test.conf create mode 100644 src/regex/regex_test_lib.c create mode 100644 src/regex/regex_test_lib.h create mode 100644 src/regex/test_regex_graph_api.c create mode 100644 src/regex/test_regex_iptoregex.c create mode 100644 src/regex/test_regex_proofs.c create mode 100644 src/statistics/test_gnunet_statistics.py.in delete mode 100755 src/statistics/test_gnunet_statistics.sh create mode 100644 src/stream/perf_stream_api.c create mode 100644 src/stream/stream.h delete mode 100644 src/stream/stream_protocol.h create mode 100644 src/stream/test_stream_big.c create mode 100644 src/stream/test_stream_sequence_wraparound.c create mode 100644 src/sysmon/Makefile.am create mode 100644 src/sysmon/Makefile.in create mode 100644 src/sysmon/gnunet-service-sysmon.c create mode 100644 src/sysmon/sysmon-properties.conf create mode 100644 src/sysmon/sysmon.conf.in create mode 100644 src/sysmon/test_glibtop.c create mode 100644 src/sysmon/test_glibtop_network.c create mode 100644 src/sysmon/test_glibtop_process.c create mode 100644 src/testbed/gnunet-helper-testbed.c create mode 100644 src/testbed/gnunet-service-testbed.c create mode 100644 src/testbed/gnunet-service-testbed.h create mode 100644 src/testbed/gnunet-service-testbed_cache.c create mode 100644 src/testbed/gnunet-service-testbed_oc.c create mode 100644 src/testbed/gnunet-testbed-profiler.c create mode 100644 src/testbed/gnunet_mpi_test.c create mode 100644 src/testbed/ll_master.c create mode 100644 src/testbed/ll_monitor.c create mode 100644 src/testbed/overlay_topology.txt create mode 100755 src/testbed/sample.job create mode 100644 src/testbed/sample_hosts.txt create mode 100644 src/testbed/test_gnunet_helper_testbed.c create mode 100644 src/testbed/test_testbed_api.c create mode 100644 src/testbed/test_testbed_api.conf create mode 100644 src/testbed/test_testbed_api_2peers_1controller.c create mode 100644 src/testbed/test_testbed_api_3peers_3controllers.c create mode 100644 src/testbed/test_testbed_api_controllerlink.c create mode 100644 src/testbed/test_testbed_api_hosts.c create mode 100644 src/testbed/test_testbed_api_operations.c create mode 100644 src/testbed/test_testbed_api_test.c create mode 100644 src/testbed/test_testbed_api_testbed_run.c create mode 100644 src/testbed/test_testbed_api_testbed_run_topology2dtorus.conf create mode 100644 src/testbed/test_testbed_api_testbed_run_topologyclique.conf create mode 100644 src/testbed/test_testbed_api_testbed_run_topologyfromfile.conf create mode 100644 src/testbed/test_testbed_api_testbed_run_topologyline.conf create mode 100644 src/testbed/test_testbed_api_testbed_run_topologyrandom.conf create mode 100644 src/testbed/test_testbed_api_testbed_run_topologyring.conf create mode 100644 src/testbed/test_testbed_api_testbed_run_topologyscalefree.conf create mode 100644 src/testbed/test_testbed_api_testbed_run_topologysmallworld.conf create mode 100644 src/testbed/test_testbed_api_testbed_run_topologysmallworldring.conf create mode 100644 src/testbed/test_testbed_api_topology.c create mode 100644 src/testbed/test_testbed_api_topology_clique.c delete mode 100644 src/testbed/testbed.conf create mode 100644 src/testbed/testbed.conf.in create mode 100644 src/testbed/testbed_api.h create mode 100644 src/testbed/testbed_api_statistics.c create mode 100644 src/testbed/testbed_api_topology.h create mode 100644 src/testbed/testbed_helper.h create mode 100644 src/testing/gnunet-testing-run-service.c delete mode 100644 src/testing/helper.c delete mode 100644 src/testing/test_testing.c delete mode 100644 src/testing/test_testing_2dtorus.c delete mode 100644 src/testing/test_testing_2dtorus.conf delete mode 100644 src/testing/test_testing_connect.c delete mode 100644 src/testing/test_testing_connect_peer1.conf delete mode 100644 src/testing/test_testing_connect_peer2.conf delete mode 100644 src/testing/test_testing_data.conf delete mode 100644 src/testing/test_testing_data_remote.conf delete mode 100644 src/testing/test_testing_data_topology_2d_torus.conf delete mode 100644 src/testing/test_testing_data_topology_blacklist.conf delete mode 100644 src/testing/test_testing_data_topology_churn.conf delete mode 100644 src/testing/test_testing_data_topology_clique.conf delete mode 100644 src/testing/test_testing_data_topology_clique_dfs.conf delete mode 100644 src/testing/test_testing_data_topology_clique_minimum.conf delete mode 100644 src/testing/test_testing_data_topology_clique_random.conf delete mode 100644 src/testing/test_testing_data_topology_erdos_renyi.conf delete mode 100644 src/testing/test_testing_data_topology_internat.conf delete mode 100644 src/testing/test_testing_data_topology_none.conf delete mode 100644 src/testing/test_testing_data_topology_ring.conf delete mode 100644 src/testing/test_testing_data_topology_scale_free.conf delete mode 100644 src/testing/test_testing_data_topology_small_world_ring.conf delete mode 100644 src/testing/test_testing_data_topology_small_world_torus.conf delete mode 100644 src/testing/test_testing_data_topology_stability.conf delete mode 100644 src/testing/test_testing_group.c delete mode 100644 src/testing/test_testing_group_remote.c delete mode 100644 src/testing/test_testing_new_peerstartup.c delete mode 100644 src/testing/test_testing_new_portreservation.c delete mode 100644 src/testing/test_testing_new_servicestartup.c delete mode 100644 src/testing/test_testing_peergroup.c delete mode 100644 src/testing/test_testing_peergroup_data.conf create mode 100644 src/testing/test_testing_peerstartup.c create mode 100644 src/testing/test_testing_portreservation.c delete mode 100644 src/testing/test_testing_reconnect.c create mode 100644 src/testing/test_testing_servicestartup.c delete mode 100644 src/testing/test_testing_topology.c delete mode 100644 src/testing/test_testing_topology_blacklist.c delete mode 100644 src/testing/test_testing_topology_churn.c delete mode 100644 src/testing/testing_group.c delete mode 100644 src/testing/testing_new.c delete mode 100644 src/testing/testing_peergroup.c create mode 100644 src/transport/gnunet-service-transport_manipulation.c create mode 100644 src/transport/gnunet-service-transport_manipulation.h delete mode 100755 src/transport/gnunet-transport-certificate-creation create mode 100644 src/transport/gnunet-transport-wlan-receiver.c delete mode 100644 src/transport/plugin_transport_http.c delete mode 100644 src/transport/plugin_transport_http.h create mode 100644 src/transport/plugin_transport_http_common.c create mode 100644 src/transport/plugin_transport_http_common.h create mode 100644 src/transport/test_http_common.c create mode 100644 src/transport/test_plugin_hostkey create mode 100644 src/transport/test_plugin_hostkey.ecc create mode 100644 src/transport/test_plugin_transport.c create mode 100644 src/transport/test_quota_compliance_wlan_asymmetric_peer1.conf create mode 100644 src/transport/test_quota_compliance_wlan_asymmetric_peer2.conf create mode 100644 src/transport/test_quota_compliance_wlan_peer1.conf create mode 100644 src/transport/test_quota_compliance_wlan_peer2.conf delete mode 100644 src/transport/test_transport_api_http_nat_peer1.conf delete mode 100644 src/transport/test_transport_api_http_nat_peer2.conf create mode 100644 src/transport/test_transport_api_http_reverse_peer1.conf create mode 100644 src/transport/test_transport_api_http_reverse_peer2.conf delete mode 100644 src/transport/test_transport_api_https_nat_peer1.conf delete mode 100644 src/transport/test_transport_api_https_nat_peer2.conf create mode 100644 src/transport/test_transport_api_manipulation_recv_tcp.c create mode 100644 src/transport/test_transport_api_manipulation_recv_tcp_peer1.conf create mode 100644 src/transport/test_transport_api_manipulation_recv_tcp_peer2.conf create mode 100644 src/transport/test_transport_api_manipulation_send_tcp.c create mode 100644 src/transport/test_transport_api_manipulation_send_tcp_peer1.conf create mode 100644 src/transport/test_transport_api_manipulation_send_tcp_peer2.conf delete mode 100644 src/transport/test_transport_api_reliability_http_nat_peer1.conf delete mode 100644 src/transport/test_transport_api_reliability_http_nat_peer2.conf delete mode 100644 src/transport/test_transport_api_reliability_https_nat_peer1.conf delete mode 100644 src/transport/test_transport_api_reliability_https_nat_peer2.conf create mode 100644 src/transport/test_transport_testing_restart.c create mode 100644 src/transport/test_transport_testing_startstop.c create mode 100644 src/util/crypto_ecc.c create mode 100644 src/util/gnunet-config.c create mode 100644 src/util/gnunet-ecc.c create mode 100644 src/util/gnunet-uri.c create mode 100644 src/util/perf_malloc.c create mode 100644 src/util/test_crypto_ecc.c create mode 100644 src/util/w32cat.c create mode 100644 src/util/win.c delete mode 100644 src/util/win.cc create mode 100644 src/vpn/gnunet-helper-vpn-windows.c delete mode 100644 src/vpn/test_gnunet_vpn.c delete mode 100644 src/vpn/test_gnunet_vpn.conf diff --git a/ChangeLog b/ChangeLog index d1ebc0e..233d630 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,7033 @@ +2013-02-05 16:06 wachs + + * [r26026] src/transport/gnunet-service-transport_manipulation.c, + src/transport/test_transport_api_manipulation_recv_tcp.c, + src/transport/test_transport_api_manipulation_send_tcp.c: + documentation + +2013-02-05 16:03 wachs + + * [r26025] src/transport/Makefile.am: extradist + -This line, and those below, will be ignored-- + + M src/transport/Makefile.am + +2013-02-05 16:02 wachs + + * [r26024] src/include/gnunet_transport_service.h, + src/transport/transport_api.c: docu + +2013-02-05 15:53 wachs + + * [r26023] + src/transport/test_transport_api_manipulation_recv_tcp.c: new + test + +2013-02-05 15:50 wachs + + * [r26022] src/transport/gnunet-service-transport_manipulation.c, + src/transport/test_transport_api_manipulation_send_tcp.c: fixes + +2013-02-05 15:35 wachs + + * [r26021] src/transport/Makefile.am, + src/transport/gnunet-service-transport_manipulation.c, + src/transport/gnunet-service-transport_manipulation.h, + src/transport/test_transport_api_manipulation.c, + src/transport/test_transport_api_manipulation_recv_tcp_peer1.conf, + src/transport/test_transport_api_manipulation_recv_tcp_peer2.conf, + src/transport/test_transport_api_manipulation_send_tcp.c, + src/transport/test_transport_api_manipulation_send_tcp_peer1.conf, + src/transport/test_transport_api_manipulation_send_tcp_peer2.conf, + src/transport/test_transport_api_manipulation_tcp_peer1.conf, + src/transport/test_transport_api_manipulation_tcp_peer2.conf: + traffic manipulation: receive delay + +2013-02-05 14:39 wachs + + * [r26020] src/transport/test_transport_api_manipulation.c: delay + sending implemented + +2013-02-05 14:24 harsha + + * [r26019] src/gns/test_gns_dht_three_peers.c, + src/include/gnunet_testbed_service.h, + src/regex/gnunet-regex-profiler.c, + src/testbed/test_testbed_api_topology.c, + src/testbed/test_testbed_api_topology_clique.c, + src/testbed/testbed_api_testbed.c, + src/testbed/testbed_api_topology.c: add completion callback for + overlay topology configure functions + +2013-02-05 12:47 wachs + + * [r26016] src/include/gnunet_transport_service.h, + src/transport/Makefile.am, src/transport/transport_api.c: last + commit for metric + +2013-02-05 12:46 wachs + + * [r26015] src/include/gnunet_protocols.h, + src/transport/test_transport_api_manipulation_tcp_peer1.conf, + src/transport/test_transport_api_manipulation_tcp_peer2.conf: + more + +2013-02-05 12:45 wachs + + * [r26014] src/transport/gnunet-service-transport.c, + src/transport/gnunet-service-transport.h, + src/transport/transport.h: more metric + +2013-02-05 12:44 wachs + + * [r26013] src/transport/gnunet-service-transport_clients.c, + src/transport/test_transport_api_manipulation.c: transport metric + manipulation + +2013-02-04 16:54 wachs + + * [r26007] src/transport/plugin_transport_tcp.c: limit connection + for tcp + +2013-02-04 15:40 wachs + + * [r26003] src/transport/gnunet-service-transport.c, + src/transport/gnunet-service-transport_neighbours.c, + src/transport/gnunet-service-transport_neighbours.h, + src/transport/gnunet-service-transport_validation.c, + src/transport/gnunet-service-transport_validation.h, + src/transport/transport.h: throttling validations + +2013-02-04 15:34 wachs + + * [r26002] configure.ac: check for getrlimit + +2013-02-04 10:52 wachs + + * [r26001] src/transport/gnunet-transport.c: implemented 0002773 + +2013-02-04 09:53 wachs + + * [r25997] src/ats/gnunet-service-ats_addresses.c: fix for 0002723 + +2013-02-04 09:34 wachs + + * [r25996] src/transport/gnunet-service-transport.c, + src/transport/plugin_transport_tcp.c: check code for 0002774 + +2013-02-02 17:26 LRN + + * [r25988] src/util/container_meta_data.c: Discard large metadata + items first + +2013-02-02 17:26 LRN + + * [r25987] src/util/container_meta_data.c: Fix a memory leak in MD + serializer + +2013-02-02 17:25 LRN + + * [r25986] src/util/container_meta_data.c: Fix a buffer overflow + +2013-02-02 17:25 LRN + + * [r25985] src/fs/gnunet-helper-fs-publish.c: Don't send more than + 64k from fs helper + +2013-02-01 12:49 harsha + + * [r25974] src/transport/transport_api.c: + GNUNET_TRANSPORT_get_hello() to call its callback asynchronously + +2013-01-31 14:15 cfuchs + + * [r25967] src/exit/gnunet-helper-exit-windows.c: re-enumated argv + to conform with helper-exit syntax + + added stub for ipv4 nat. Note that there is a problem ahead! + +2013-01-31 13:12 cfuchs + + * [r25966] src/exit/gnunet-helper-exit-windows.c, + src/vpn/gnunet-helper-vpn-windows.c: added support for partial + write to stdin/stdout. + + there seems to be no point in adding support for partial read + from the + TAP, as there is no delimiter and we get data on a per-frame + level. + +2013-01-31 12:32 cfuchs + + * [r25964] src/exit/gnunet-helper-exit-windows.c, + src/vpn/gnunet-helper-vpn-windows.c: added support for partial + reads from stdin + +2013-01-31 10:41 cfuchs + + * [r25959] src/exit/gnunet-helper-exit-windows.c, + src/vpn/gnunet-helper-vpn-windows.c: helper-vpn and helper-exit + now are 64bit capabled. + + added check if we are running on a win32/wow64/win64 host system. + +2013-01-31 09:45 grothoff + + * [r25956] src/vpn/vpn.conf.in: porting to W32 requires a port, + yepee + +2013-01-31 09:11 cfuchs + + * [r25954] src/exit/gnunet-helper-exit-windows.c, + src/vpn/gnunet-helper-vpn-windows.c: some final + code-beautification (coding style 4tw!) + + removed a few obsolete variables + +2013-01-31 08:52 cfuchs + + * [r25953] src/exit/Makefile.am, + src/exit/gnunet-helper-exit-windows.c: added + gnunet-helper-exit-windows, which currently is just a copy of + gnunet-helper-vpn-windows + +2013-01-30 17:45 cfuchs + + * [r25952] src/vpn/gnunet-helper-vpn-windows.c: added nice debug + output for gnunet-herlper-vpn-windows. + +2013-01-30 15:54 grothoff + + * [r25947] src/fs/perf_gnunet_service_fs_p2p.c, + src/fs/perf_gnunet_service_fs_p2p.conf, + src/include/gnunet_network_lib.h, + src/testbed/gnunet-service-testbed_hc.c: API extension, make + blocking socket API visible + +2013-01-30 15:06 harsha + + * [r25945] src/testbed/gnunet-service-testbed_hc.c: towards caching + CORE handles + +2013-01-30 13:38 harsha + + * [r25944] src/core/core_api.c, src/include/gnunet_core_service.h: + function to synchronously check if a peer is connected at CORE + level + +2013-01-30 10:06 harsha + + * [r25938] src/testbed/gnunet-service-testbed.h, + src/testbed/gnunet-service-testbed_hc.c, + src/testbed/gnunet-service-testbed_oc.c: cache transport handles + with peer connect notifications + +2013-01-30 09:22 wachs + + * [r25937] src/include/gnunet_transport_service.h, + src/transport/transport_api.c: forgot + +2013-01-29 15:10 harsha + + * [r25933] src/testbed/gnunet-service-testbed_hc.c, + src/testbed/gnunet-service-testbed_oc.c: caching transport + handles + +2013-01-26 14:27 harsha + + * [r25921] src/testbed/gnunet-service-testbed_oc.c: bound remote + overlay connect operation execution to limited number of open + file descriptors + +2013-01-26 09:50 grothoff + + * [r25919] src/arm/gnunet-arm.c, src/arm/test_arm_api.c, + src/arm/test_exponential_backoff.c, + src/arm/test_gnunet_service_arm.c: LRN: Here's a patch. See if it + doesn't break anything for you. + + Arm service is started with -c only when the process + that + runs arm service has "[arm]/CONFIG" defined in the configuration + used + to run arm service (usually - process' own configuration). + + Since default [arm] config has no CONFIG defined anymore (thanks + to + your r25908), we need to add this code to put the config file + that was + passed to gnunet-arm tool via -c as "[arm]/CONFIG" for arm + service to + receive it. + + Otherwise arm service is run without config and reads default + config + (~/.gnunet/gnunet.conf) instead, which is clearly not what we + need. + +2013-01-25 22:27 harsha + + * [r25918] po/POTFILES.in: fix 2746 + +2013-01-25 20:38 harsha + + * [r25917] src/testbed/gnunet-service-testbed.c, + src/testbed/gnunet-service-testbed.h, + src/testbed/testbed.conf.in: read MAX_OPEN_FDS from configuration + +2013-01-25 16:42 harsha + + * [r25913] src/testbed/gnunet-service-testbed_oc.c: bound overlay + connect operation execution to limited number of open file + descriptors + +2013-01-25 16:02 grothoff + + * [r25907] src/arm/arm_api.c: start gnunet-service-arm nicely if + configuration file does not exist + +2013-01-25 15:22 grothoff + + * [r25904] src/exit/Makefile.am, src/exit/exit.conf, + src/exit/gnunet-daemon-exit.c: add DNS exit for mesh to + gnunet-daemon-exit + +2013-01-25 15:22 grothoff + + * [r25903] src/dns/Makefile.am, src/dns/dns.conf.in, + src/dns/gnunet-service-dns.c: remove DNS exit for mesh from + gnunet-service-dns + +2013-01-25 10:55 harsha + + * [r25892] src/testbed/Makefile.am, + src/testbed/gnunet-service-testbed.c, + src/testbed/gnunet-service-testbed.h, + src/testbed/gnunet-service-testbed_hc.c: separate hello cache as + module + +2013-01-24 17:01 harsha + + * [r25889] src/testbed/test_testbed_api_operations.c: test harder + +2013-01-24 15:46 bartpolot + + * [r25886] src/mesh/Makefile.am, + src/mesh/gnunet-daemon-regexprofiler.c, + src/mesh/gnunet-regex-profiler.c, src/mesh/gnunet-service-mesh.c, + src/regex, src/regex/Makefile.am, + src/regex/gnunet-daemon-regexprofiler.c, + src/regex/gnunet-regex-profiler.c: Moved regex profiler and + profiler daemon from mesh to regex, adaped to regex dht lib + +2013-01-24 13:54 cfuchs + + * [r25885] src/vpn/gnunet-helper-vpn-windows.c: re-fixed incorrect + from last commit... :-D forgot to save. + +2013-01-24 13:51 cfuchs + + * [r25884] src/vpn/gnunet-helper-vpn-windows.c: added debug logics + to print to and read from STDIN, instead of from + named pipes + + moved declaration of hdr outside of the ifs + + fixed an incorrect comparison introduced in last commit + +2013-01-24 13:07 cfuchs + + * [r25883] src/vpn/gnunet-helper-vpn-windows.c: helper now always + uses BOOL(winbool) instead of boolean to stay + consistent + + attept_write now properly resets the read facility to + IOSTATE_RESUME, in + case read was stalled because write was busy + +2013-01-24 12:49 cfuchs + + * [r25882] src/vpn/gnunet-helper-vpn-windows.c: added + IOSTATE_RESUME and related code to state machines + +2013-01-24 12:24 harsha + + * [r25881] src/testbed/testbed_api_operations.c, + src/testbed/testbed_api_operations.h: operations now can + explicitly register how many resources they require + +2013-01-24 11:46 dold + + * [r25879] src/consensus/gnunet-consensus.c: fix + +2013-01-24 08:51 cfuchs + + * [r25871] src/vpn/gnunet-helper-vpn-windows.c: added gnunet-header + stripping and adding functionality + + woops logics bug discovered: when read goes into waiting, the + output + facility will + not transfer the input buffer and forget about it silently... + +2013-01-24 08:23 cfuchs + + * [r25870] src/vpn/gnunet-helper-vpn-windows.c: added ip-address + remove functions + + newly set IP addresses now should expire upon reboot (buggy on + some + windows, but at least it solves the IP-persistence issues in win7 + and + above) + + cloned read functions to properly apply or strip the gnunet + message + header + + removed the status BOOL from the overlapped struct and made it + local + + some fixes here and there + + added a lot of comments + + style adjustments + + TODO: + * actually strip the gnunet message header or apply it again + * test with the main vpn binary + +2013-01-24 02:55 dold + + * [r25866] src/consensus/consensus_api.c, + src/consensus/consensus_protocol.h, + src/consensus/gnunet-consensus.c, + src/consensus/gnunet-service-consensus.c, src/consensus/ibf.c, + src/consensus/test_consensus.conf: implemented value exchange, + various fixes + +2013-01-23 13:15 harsha + + * [r25862] contrib/testbed_infiniband.conf: profiler now depends on + config file to give topology option + +2013-01-23 13:14 harsha + + * [r25861] src/testbed/gnunet-testbed-profiler.c, + src/testbed/testbed_api_testbed.c: fix 2688: profiler now uses + GNUNET_TESTBED_run () + +2013-01-23 10:46 harsha + + * [r25860] src/testbed/testbed_api_testbed.c: use all IP addresses + of master controller as trusted ip + +2013-01-23 10:10 wachs + + * [r25859] src/ats/test_ats_simplistic_pref_aging.c: test + +2013-01-22 16:44 wachs + + * [r25857] src/ats/test_ats_simplistic_pref_aging.c: changes + +2013-01-22 16:01 wachs + + * [r25856] src/ats/gnunet-service-ats_addresses_simplistic.c: wrong + type causing invalid reads + +2013-01-22 11:04 wachs + + * [r25854] contrib/pydmesg: print dmesg messages with human + readable timestamps + useful to check when segfaults etc happened + +2013-01-21 16:58 wachs + + * [r25853] src/ats/gnunet-service-ats_addresses_simplistic.c: + changes to aging + +2013-01-21 16:29 wachs + + * [r25850] src/ats/gnunet-service-ats_addresses_simplistic.c: fixes + +2013-01-21 16:26 LRN + + * [r25848] po/POTFILES.in: mesh_block_lib.c is gone + +2013-01-21 16:15 wachs + + * [r25847] src/ats/test_ats_simplistic_pref_aging.c: improving test + +2013-01-21 13:24 grothoff + + * [r25837] contrib/gnunet-chk.py: 3 + +2013-01-18 16:52 wachs + + * [r25835] src/ats/gnunet-service-ats_addresses_simplistic.c: + preference aging + improved quota recalculation due to pref + change + +2013-01-18 15:48 wachs + + * [r25833] src/ats/Makefile.am, + src/ats/gnunet-service-ats_addresses_simplistic.c, + src/ats/test_ats_simplistic_pref_aging.c: changes + +2013-01-18 14:07 wachs + + * [r25831] src/ats-tool/gnunet-ats.c: print network type + +2013-01-18 13:49 wachs + + * [r25830] src/transport/plugin_transport_http_client.c, + src/transport/plugin_transport_http_common.c: changes + +2013-01-18 12:23 wachs + + * [r25829] src/transport/plugin_transport_http_common.c, + src/transport/test_http_common.c: changes + +2013-01-18 12:01 wachs + + * [r25828] src/transport/plugin_transport_http_common.c: mem leak + +2013-01-18 11:16 wachs + + * [r25827] src/transport/test_http_common.c: change + +2013-01-18 11:07 wachs + + * [r25826] src/transport/plugin_transport_http_common.c, + src/transport/plugin_transport_http_common.h, + src/transport/test_http_common.c: address parsing + +2013-01-18 04:51 LRN + + * [r25823] src/regex/Makefile.am: Fix regex dependencies + +2013-01-18 04:43 LRN + + * [r25822] src/transport/gnunet-transport.c: Fix FPRINTF invocation + +2013-01-18 04:43 LRN + + * [r25821] src/core/gnunet-service-core_kx.c: Replace EPV with a + warning + +2013-01-18 04:43 LRN + + * [r25820] src/transport/gnunet-service-transport_validation.c: + Re-enable signature check warning + +2013-01-17 17:09 bartpolot + + * [r25819] src/include/block_mesh.h, src/include/block_regex.h, + src/include/gnunet_block_lib.h, src/include/gnunet_regex_lib.h, + src/mesh/Makefile.am, src/mesh/gnunet-service-mesh-new.c, + src/mesh/gnunet-service-mesh.c, src/mesh/mesh_block_lib.c, + src/mesh/mesh_block_lib.h, src/mesh/plugin_block_mesh.c, + src/regex/Makefile.am, src/regex/plugin_block_regex.c, + src/regex/regex.c, src/regex/regex_block_lib.c, + src/regex/regex_block_lib.h, src/regex/regex_dht.c: Move regex + DHT integration from mesh to regex + +2013-01-17 16:31 wachs + + * [r25818] src/transport/test_http_common.c: test + +2013-01-17 16:21 wachs + + * [r25817] src/transport/Makefile.am, + src/transport/gnunet-service-transport_clients.c, + src/transport/plugin_transport_http_common.c, + src/transport/plugin_transport_http_common.h: address parsing + +2013-01-17 14:23 cfuchs + + * [r25816] src/vpn/gnunet-helper-vpn-windows.c: * a little bit of + bugfixing + * added functionality to remove ip addresses from our interfaces + * some formatting work + * added rety-loop for the interface-name resolver (retry up to 30 + seconds) + * set new ipv4/v6 addresses to be forgotten on bootup + (store=active) + * adjusted some debug output (added a few \n here and there) + +2013-01-17 13:33 wachs + + * [r25814] src/transport/gnunet-transport.c: end when no addresses + returned + +2013-01-17 13:03 wachs + + * [r25813] src/transport/gnunet-transport.c: improved timeout + handling for address listing + +2013-01-17 12:25 wachs + + * [r25812] src/transport/gnunet-transport.c: timeout for address + listing + +2013-01-17 10:28 grothoff + + * [r25809] src/vpn/gnunet-helper-vpn-windows.c: minor style stuff + +2013-01-16 17:21 cfuchs + + * [r25805] src/vpn/gnunet-helper-vpn-windows.c: more debugging + work. + + Registry is extremely slow at refreshing. inserted a makeshift + sleep(5) + to avoid retrieving outdated interface-information. + + added proper return-codes to set_address4/6 + + fixed incorrect string-length handling for the HWID tags + + updatedriverforplugandplaydevicesa now updates only the driver + for our + current device, no longer the other siblings too (for >10 + devices, + this could easily have taken > 60 seconds! ). + + removed inet_pton, as we require API version XPSP2 anyway. + +2013-01-15 20:22 cfuchs + + * [r25802] src/vpn/Makefile.am, + src/vpn/gnunet-helper-vpn-windows.c: added calls for updating the + driver in a for device. seems like this is + mandatory when adding a new device node. unfortunately this is + pretty + slow... + + added new required include+library to link against: newdev.h/dll + +2013-01-15 19:15 cfuchs + + * [r25801] src/vpn/gnunet-helper-vpn-windows.c: more bug fixing + +2013-01-15 18:50 cfuchs + + * [r25800] src/vpn/gnunet-helper-vpn-windows.c: a bit of bugfixing + +2013-01-15 14:45 cfuchs + + * [r25799] src/vpn/gnunet-helper-vpn-windows.c: final logics for + run implemented + added teardown functionality. + + now: testing... + +2013-01-15 14:42 wachs + + * [r25798] src/ats/gnunet-service-ats_addresses_simplistic.c: fix + for failing fs tests + +2013-01-15 14:11 wachs + + * [r25797] src/sysmon/gnunet-service-sysmon.c, + src/sysmon/sysmon.conf.in: changes + +2013-01-15 13:32 wachs + + * [r25794] src/sysmon/gnunet-service-sysmon.c, + src/sysmon/sysmon.conf.in: time stamp + +2013-01-15 13:23 wachs + + * [r25793] src/sysmon/gnunet-service-sysmon.c: IPv6 support + +2013-01-15 12:55 wachs + + * [r25792] src/sysmon/gnunet-service-sysmon.c, + src/sysmon/sysmon.conf.in, src/sysmon/test_glibtop_network.c: + changes + +2013-01-15 11:14 wachs + + * [r25791] src/sysmon/Makefile.am, + src/sysmon/gnunet-service-sysmon.c, + src/sysmon/sysmon-properties.conf, src/sysmon/sysmon.conf.in: + changes + +2013-01-15 10:17 wachs + + * [r25790] src/sysmon/gnunet-service-sysmon.c: fix + +2013-01-15 10:14 wachs + + * [r25789] src/sysmon/gnunet-service-sysmon.c: fix + +2013-01-15 10:13 wachs + + * [r25788] src/sysmon/Makefile.am: install withouth libgtop + +2013-01-15 09:34 wachs + + * [r25787] src/ats/gnunet-service-ats_addresses_simplistic.c: + fixing 0002735: + precision error when calculating quotas + +2013-01-15 09:09 wachs + + * [r25786] src/ats/gnunet-service-ats_addresses_simplistic.c: get + more information + +2013-01-14 16:44 wachs + + * [r25785] src/sysmon/gnunet-service-sysmon.c, + src/sysmon/sysmon.conf.in: gtop integration + +2013-01-14 16:22 wachs + + * [r25784] src/sysmon/gnunet-service-sysmon.c: changes + +2013-01-14 15:53 wachs + + * [r25782] src/sysmon/gnunet-service-sysmon.c, + src/sysmon/sysmon.conf.in: changes + +2013-01-14 15:39 harsha + + * [r25781] contrib/testbed_infiniband.conf: - kill irrelavant stuff + +2013-01-14 15:09 wachs + + * [r25779] src/sysmon/gnunet-service-sysmon.c: changes + +2013-01-14 12:02 wachs + + * [r25771] src/include/gnunet_ats_service.h: handle + +2013-01-14 11:14 wachs + + * [r25770] src/transport/gnunet-service-transport_neighbours.c: + fixing mantis 0002732 + +2013-01-14 11:11 wachs + + * [r25769] src/ats/ats_api_scheduling.c: adding suggest handle to + allow transport to check if we have pending address request + +2013-01-14 11:00 wachs + + * [r25768] src/ats/test_ats_simplistic_change_preference.c: no + pending request + +2013-01-14 10:49 wachs + + * [r25767] src/ats/test_ats_simplistic.c: no suggest to cancel + +2013-01-14 10:01 wachs + + * [r25766] src/ats/gnunet-service-ats_addresses_simplistic.c: fix + for quota check + +2013-01-11 16:32 wachs + + * [r25762] src/ats/gnunet-service-ats_addresses_simplistic.c, + src/ats/test_ats_simplistic_change_preference.c: changes + +2013-01-11 15:32 wachs + + * [r25761] src/ats/gnunet-service-ats_addresses_simplistic.c: fix + for broken tests + +2013-01-11 15:31 wachs + + * [r25760] src/ats/test_ats_api_scheduling_check_min_bw_alt.c: fix + test + +2013-01-11 14:32 wachs + + * [r25759] src/ats/gnunet-service-ats_addresses_simplistic.c: + changes + +2013-01-11 13:38 wachs + + * [r25758] src/ats/gnunet-service-ats_addresses_simplistic.c: + changes + +2013-01-11 13:37 wachs + + * [r25757] src/ats/test_ats_simplistic_change_preference.c: change + to test to let updates settle + +2013-01-11 12:39 wachs + + * [r25754] src/ats/gnunet-service-ats_addresses_simplistic.c: + global calculation + +2013-01-11 10:37 wachs + + * [r25753] src/ats/gnunet-service-ats_addresses_simplistic.c: docu + +2013-01-11 09:51 wachs + + * [r25752] src/ats/gnunet-service-ats_addresses.c: commit for + mantis: 0002729 + quota load: support "unlimited", fancy strings and integer values + (set by gnunet setup) + +2013-01-10 12:36 cfuchs + + * [r25743] src/vpn/gnunet-helper-vpn-windows.c: consolidated read + and write functions, as we can read from a named pipe + the same way as we can read from our TAP. + + added high-level description of attempt_read + +2013-01-10 11:54 cfuchs + + * [r25741] src/vpn/gnunet-helper-vpn-windows.c: as discussed, + vpn-helper-windows will only function if stdin/stdout are + handed down as pipes. + + helper will reopen stdin and stdout in overlapped mode. + ReOpenFile + requires WinXPSP2 or Win2003SP1. + +2013-01-10 09:39 cfuchs + + * [r25737] src/vpn/gnunet-helper-vpn-windows.c: In Windows, pipes, + files and the console have to be accessed + differently(in contrast to *nix). overlapping does not exist for + console + handles, and different functions are required to read/write/poll + stdin/out. + + - THus, we can now detect the type of handle we got as + stdin/stdout from our calling process. + + - Did a bit of refactoring. + + next: add logics to use the proper access mode depending on our + handletype. + +2013-01-09 23:53 harsha + + * [r25736] src/testbed/testbed_api.c: allow customizing remote + shell command and the program started by it + +2013-01-09 09:34 wachs + + * [r25727] src/ats/gnunet-service-ats_addresses_simplistic.c: + enable preference calculation to finish it and debug + +2013-01-09 08:48 wachs + + * [r25726] src/transport/gnunet-service-transport_validation.c: + debug code for mantis 0002726 + +2013-01-08 14:08 cfuchs + + * [r25713] src/vpn/gnunet-helper-vpn-windows.c: fixed a wrong + conditional + + more research on the conin/stdin+overlapping issue. + +2013-01-07 16:09 wachs + + * [r25708] src/gns/test_gns_dht_three_peers.c: 10 sec was too + optimistic for mamasparc + +2013-01-07 15:52 wachs + + * [r25707] src/gns/test_gns_dht_three_peers.c: fixing test by + debugging (but still fails) + +2013-01-06 00:13 harsha + + * [r25702] src/testbed/gnunet-service-testbed.c, + src/testbed/test_testbed_api.conf, + src/testbed/test_testbed_api_testbed_run_topology2dtorus.conf, + src/testbed/test_testbed_api_testbed_run_topologyclique.conf, + src/testbed/test_testbed_api_testbed_run_topologyfromfile.conf, + src/testbed/test_testbed_api_testbed_run_topologyline.conf, + src/testbed/test_testbed_api_testbed_run_topologyrandom.conf, + src/testbed/test_testbed_api_testbed_run_topologyring.conf, + src/testbed/test_testbed_api_testbed_run_topologyscalefree.conf, + src/testbed/test_testbed_api_testbed_run_topologysmallworld.conf, + src/testbed/test_testbed_api_testbed_run_topologysmallworldring.conf, + src/testbed/testbed.conf.in: cache HELLO's of peers + +2013-01-05 16:48 harsha + + * [r25700] src/testbed/gnunet-service-testbed.c: aggressively + persuade transport to connect + +2013-01-04 12:18 grothoff + + * [r25691] src/peerinfo/gnunet-service-peerinfo.c: fix + +2013-01-03 22:40 grothoff + + * [r25686] src/peerinfo/gnunet-service-peerinfo.c, + src/peerinfo/peerinfo.conf.in: adding NO_IO option to peerinfo to + disable disc accesses for experiments + +2013-01-03 16:11 cfuchs + + * [r25683] src/vpn/gnunet-helper-vpn-windows.c: There are now four + states for the OI facilities: + * ready (to do work), + * queued (waiting for async-io to return), + * waiting (a read-facilities wait for its output partner to get + process) + * failed (if a socket error occured) + + added attempt_tap_read machine. + reworked run() for overlapped IO + +2013-01-03 14:58 harsha + + * [r25682] src/testbed/testbed_api_testbed.c: fix #2720 + +2013-01-03 10:40 cfuchs + + * [r25677] src/vpn/gnunet-helper-vpn-windows.c: added initial stuff + for overlapped IO and event handling + +2013-01-03 00:43 dold + + * [r25675] src/consensus/Makefile.am, src/consensus/consensus.h, + src/consensus/consensus_api.c, + src/consensus/gnunet-consensus-start-peers.c, + src/consensus/gnunet-consensus.c, + src/consensus/gnunet-service-consensus.c, + src/consensus/test_consensus_api.c, + src/include/gnunet_applications.h, + src/include/gnunet_consensus_service.h, + src/include/gnunet_protocols.h: implemented the modified + consensus api, started implementing p2p protocol for consensus + +2013-01-02 16:03 harsha + + * [r25674] src/testbed/testbed_api.c, src/testbed/testbed_api.h: + weigh all readings equally + +2013-01-02 15:36 harsha + + * [r25673] src/testbed/testbed_api.c: linear increase and decrease + when SD is within 1 and 2 SD respectively + +2013-01-01 22:44 harsha + + * [r25670] src/testbed/standard_deviation.c, + src/testbed/test_testbed_api.conf, src/testbed/testbed_api.c, + src/testbed/testbed_api.h, src/testbed/testbed_api_peers.c, + src/testbed/testbed_api_peers.h: adaptive parallelism for overlay + connect operations based on SD calculations + +2013-01-01 11:49 cfuchs + + * [r25668] src/vpn/gnunet-helper-vpn-windows.c: * re-added mainloop + for run + * started work on our select-equivalent for windows. + +2012-12-31 15:52 cfuchs + + * [r25667] src/include/tap-windows.h, + src/vpn/gnunet-helper-vpn-windows.c: * added tap version checking + logics. Many tap32 versions are broken, + Only version 9.8 and later support IPv6, 9.8 is broken with IPv4. + Thus, + we are using the same minium version as openvpn 2.3: tap32-9.9 + + * created our TAP/TUN handle-object (equivalent to the *nix + init_tun() + function), this still requires some more logics to be + complete. + + * added logics to set the tun up (+a fixed sleep, to wait for it + to + come up) + + * we now also store the device's GUID, as we need it for creating + the + handle. + + * added the exports of tap32: src/include/tap_windows.h , for the + sake + of upgradability. This file contains version-specific defines for + the + driver. + + * happy new year! + +2012-12-29 20:20 cfuchs + + * [r25665] src/vpn/gnunet-helper-vpn-windows.c: reworked vpn-helper + to now use regular(!) char, instead of wchar, + according to recommendations found in the C/C++-specs(wchar != + unicode support, but may break compiler compatibility). + +2012-12-24 12:08 LRN + + * [r25643] src/consensus/Makefile.am: Dependencies in consensus + makefiles + +2012-12-24 09:48 LRN + + * [r25642] src/sysmon/sysmon.conf.in: Resolve port conflict between + ats and sysmon + +2012-12-22 08:50 LRN + + * [r25640] src/hostlist/hostlist.conf: Fix default hostlists + +2012-12-21 16:48 grothoff + + * [r25635] po/de.po, po/es.po, po/sv.po, po/vi.po, po/zh_CN.po: + releasing GNUnet 0.9.5 + +2012-12-21 16:29 harsha + + * [r25634] src/lockmanager/gnunet-service-lockmanager.c: remove + disconnecting client from waitling lists of other locks + +2012-12-21 10:06 dold + + * [r25613] src/consensus/gnunet-consensus-ibf.c, + src/consensus/ibf.c, src/consensus/ibf.h: collision detection for + IBF, timing for test tool + +2012-12-20 14:50 wachs + + * [r25583] src/ats/gnunet-service-ats_addresses_simplistic.c, + src/ats/test_ats_simplistic_change_preference.c: preference value + calculation + +2012-12-20 14:01 bartpolot + + * [r25581] configure.ac, po/POTFILES.in, src/Makefile.am, + src/testing_old: Remove testing_old + +2012-12-20 13:57 LRN + + * [r25580] src/fs/fs_uri.c: Fix percentization of non-ASCII strings + +2012-12-20 00:39 dold + + * [r25571] src/consensus/Makefile.am, + src/consensus/gnunet-consensus-ibf.c, src/consensus/ibf.c, + src/consensus/ibf.h: implemented the invertible bloom filter + +2012-12-19 09:36 wachs + + * [r25538] src/ats/test_ats_simplistic_change_preference.c: fixing + test + +2012-12-17 16:03 wachs + + * [r25520] src/ats/ats_api_peer_change_preference.c: unused code + +2012-12-17 15:08 wachs + + * [r25517] src/ats/Makefile.am, + src/ats/gnunet-service-ats_addresses.c, + src/ats/gnunet-service-ats_addresses_simplistic.c: changes + +2012-12-17 14:30 wachs + + * [r25516] src/ats/test_ats_api.conf: no valgrind + +2012-12-17 14:30 wachs + + * [r25515] src/ats/gnunet-service-ats_addresses.c, + src/ats/gnunet-service-ats_addresses.h, + src/ats/gnunet-service-ats_addresses_mlp.c, + src/ats/gnunet-service-ats_addresses_mlp.h, + src/ats/gnunet-service-ats_addresses_simplistic.c, + src/ats/gnunet-service-ats_addresses_simplistic.h, + src/ats/gnunet-service-ats_performance.c, + src/ats/test_ats_api.conf: adding client reference + +2012-12-17 12:48 wachs + + * [r25511] configure.ac: libgtop check + +2012-12-17 12:45 wachs + + * [r25509] src/sysmon/Makefile.am: new check + +2012-12-17 12:15 wachs + + * [r25506] src/sysmon/Makefile.am: glib check + +2012-12-17 12:14 wachs + + * [r25505] configure.ac: check for glib + +2012-12-15 14:24 grothoff + + * [r25493] src/fs/gnunet-service-fs_pe.c: LRN: fixing #2701 + +2012-12-14 10:56 wachs + + * [r25480] src/dns/dnsparser.c: doxygen + +2012-12-14 10:54 wachs + + * [r25479] src/hello/hello.c: doxyen + +2012-12-14 10:54 wachs + + * [r25478] src/sysmon/gnunet-service-sysmon.c: doxygen + +2012-12-14 10:51 wachs + + * [r25477] src/fs/Makefile.am: fixes for make dist + +2012-12-14 10:43 wachs + + * [r25476] doc/man/gnunet-ats.1: updated man page + +2012-12-14 10:02 wachs + + * [r25475] src/include/gnunet_ats_service.h: docu + +2012-12-14 10:01 wachs + + * [r25474] src/ats/ats.conf.in, + src/ats/gnunet-service-ats_addresses.c, + src/include/gnunet_ats_service.h: improved quota loading + +2012-12-14 09:28 wachs + + * [r25473] src/ats-tool/gnunet-ats.c: new switch -q to print + configured quotas + +2012-12-13 19:31 grothoff + + * [r25465] src/regex/regex.c, src/regex/regex_internal.h: reduce + reallocing to improve performance + +2012-12-13 16:13 wachs + + * [r25459] src/ats/gnunet-service-ats_addresses_simplistic.c: + statistics for solver + +2012-12-13 13:46 wachs + + * [r25449] src/ats/Makefile.am, + src/ats/gnunet-service-ats_addresses_simplistic.c, + src/ats/test_ats_api_scheduling_switch_network.c, + src/ats/test_ats_simplistic_switch_networks.c: simplistic solver + supports moving addresses between networks, test renamed + +2012-12-13 13:01 wachs + + * [r25445] src/ats/test_ats_api_scheduling_switch_network.c: test: + check network type + +2012-12-13 12:41 wachs + + * [r25444] src/ats/test_ats_api_scheduling_switch_network.c: + changes + +2012-12-12 21:45 grothoff + + * [r25434] src/nat/Makefile.am, src/nat/nat_auto.c: nat auto code + from gnunet-gtk now compiles as part of libgnunetnat + +2012-12-12 21:44 grothoff + + * [r25433] src/include/gnunet_configuration_lib.h, + src/util/configuration.c: adding function to compute + configuration differences in memory + +2012-12-12 21:22 cfuchs + + * [r25432] src/vpn/gnunet-helper-vpn-windows.c: Added basic + functionality for setting IPv4/V6 addresses in win32 using + netsh. + Added wrapper for launching programs in a windows shell. + Added define for _tpopen + +2012-12-12 16:51 bartpolot + + * [r25429] src/testbed/gnunet-testbed-profiler.c, + src/testbed/testbed_api.c: Run testbed-helper in a sh interactive + session to make sure the env is set up properly + +2012-12-12 16:15 wachs + + * [r25427] src/ats/Makefile.am, + src/ats/gnunet-service-ats_addresses_simplistic.c, + src/ats/test_ats_api_scheduling_switch_network.c: changes and + test + +2012-12-12 15:32 wachs + + * [r25424] src/ats/Makefile.am, + src/ats/gnunet-service-ats_addresses.c, + src/ats/gnunet-service-ats_addresses.h, + src/ats/gnunet-service-ats_addresses_mlp.c, + src/ats/gnunet-service-ats_addresses_mlp.h, + src/ats/gnunet-service-ats_addresses_simplistic.c, + src/ats/gnunet-service-ats_addresses_simplistic.h: updating + addresses support changing networks + +2012-12-12 13:48 wachs + + * [r25423] src/transport/plugin_transport_tcp.c: fix: tcp did not + return network type + +2012-12-12 13:28 wachs + + * [r25422] src/ats/gnunet-service-ats.c, + src/ats/gnunet-service-ats_addresses.c, + src/ats/gnunet-service-ats_addresses.h, + src/ats/gnunet-service-ats_addresses_mlp.c, + src/ats/gnunet-service-ats_addresses_mlp.h, + src/ats/gnunet-service-ats_addresses_simplistic.c, + src/ats/gnunet-service-ats_addresses_simplistic.h, + src/ats/gnunet-service-ats_performance.c, + src/ats/gnunet-service-ats_performance.h, + src/ats/gnunet-service-ats_scheduling.c, src/sysmon/Makefile.am, + src/sysmon/gnunet-daemon-sysmon.c, + src/sysmon/gnunet-service-sysmon.c, src/sysmon/sysmon.conf.in: + changes + +2012-12-12 11:25 bartpolot + + * [r25420] src/mesh/gnunet-service-mesh.c: mesh now accepts REGEXes + longer than 64KiB + +2012-12-12 11:11 wachs + + * [r25419] src/ats/test_ats_api.conf, + src/ats/test_ats_api_scheduling_block_and_reset.c: add additional + stage due to issues on powerbot: + initial address suggestion can take quite long during service + startup + +2012-12-12 10:48 cfuchs + + * [r25417] contrib/openvpn-tap32, contrib/openvpn-tap32/INSTALL, + contrib/openvpn-tap32/tap32-signed-i386-2.1.zip, + contrib/openvpn-tap32/tap32-source-2.1.zip: added a copy of the + current sources(openvpn-2.1) and a signed copy of the compiled + drivers of tap32, which is used by vpn-helper-windows to emulate + tun/tap on win32. + +2012-12-12 10:34 wachs + + * [r25416] src/transport/plugin_transport_unix.c: msg + +2012-12-12 10:32 wachs + + * [r25415] src/ats-tool/gnunet-ats.c: fix coverity 10389 + +2012-12-12 10:13 wachs + + * [r25414] + src/core/test_core_quota_asymmetric_recv_limited_peer1.conf, + src/core/test_core_quota_asymmetric_recv_limited_peer2.conf, + src/core/test_core_quota_asymmetric_send_limit_peer1.conf, + src/core/test_core_quota_asymmetric_send_limit_peer2.conf, + src/core/test_core_quota_peer1.conf, + src/core/test_core_quota_peer2.conf: fixing confs: core tests + should pass + +2012-12-12 09:54 wachs + + * [r25413] src/ats/gnunet-service-ats_addresses_simplistic.c: fix + coverity 10390 + +2012-12-12 09:37 wachs + + * [r25407] src/ats/test_ats_api_performance.c: fix break + +2012-12-12 09:27 wachs + + * [r25406] src/ats/ats_api_scheduling.c, + src/include/gnunet_ats_service.h: adding function + +2012-12-12 09:20 wachs + + * [r25405] src/ats/ats_api_scheduling.c: msgs + +2012-12-12 08:57 wachs + + * [r25404] src/transport/test_quota_compliance.c: FIX: add quotas + for all networks, transport tests should pass + +2012-12-11 22:35 cfuchs + + * [r25401] src/vpn/gnunet-helper-vpn-windows.c: grml, friendlyName + is not friendly, because it does not help us for + finding anything. Switched over to backup plan: + * lookup the devices's name directly in registry via the + PNPInterfaceID. Registry fun, yey! + * added a few fixes here and there + +2012-12-11 15:46 wachs + + * [r25398] src/ats/Makefile.am, + src/ats/gnunet-service-ats_addresses.c, + src/ats/gnunet-service-ats_addresses.h, + src/ats/gnunet-service-ats_addresses_mlp.c, + src/ats/gnunet-service-ats_addresses_mlp.h, + src/ats/gnunet-service-ats_addresses_simplistic.c, + src/ats/gnunet-service-ats_addresses_simplistic.h, + src/ats/test_ats_api_common.c, src/ats/test_ats_api_common.h, + src/ats/test_ats_api_scheduling_add_address.c, + src/ats/test_ats_api_scheduling_add_session.c, + src/ats/test_ats_api_scheduling_block_and_reset.c, + src/ats/test_ats_api_scheduling_destroy_address.c, + src/ats/test_ats_api_scheduling_destroy_inbound_connection.c, + src/ats/test_ats_api_scheduling_destroy_session.c, + src/ats/test_ats_api_scheduling_update_address.c, + src/ats/test_ats_simplistic.c: changes + +2012-12-11 14:32 wachs + + * [r25396] src/ats/gnunet-service-ats.c, + src/ats/gnunet-service-ats_addresses.c, + src/ats/gnunet-service-ats_addresses.h, + src/ats/gnunet-service-ats_addresses_simplistic.c, + src/ats/gnunet-service-ats_scheduling.c, + src/ats/gnunet-service-ats_scheduling.h: changes + +2012-12-11 13:56 wachs + + * [r25394] src/ats/gnunet-service-ats_addresses_simplistic.c: + changes + +2012-12-11 13:48 harsha + + * [r25393] src/fs/gnunet-fs-profiler.c, + src/include/gnunet_testbed_service.h, + src/testbed/test_testbed_api_testbed_run.c, + src/testbed/testbed_api_test.c, + src/testbed/testbed_api_testbed.c: fix 2689 + +2012-12-11 13:46 wachs + + * [r25392] src/ats/gnunet-service-ats_addresses.c, + src/ats/gnunet-service-ats_addresses_simplistic.c, + src/ats/test_ats_api_scheduling_destroy_address.c: + +2012-12-11 12:27 harsha + + * [r25390] src/consensus/gnunet-consensus-start-peers.c, + src/dht/dht_test_lib.c, src/fs/perf_gnunet_service_fs_p2p.c, + src/fs/perf_gnunet_service_fs_p2p_respect.c, + src/fs/test_fs_test_lib.c, + src/fs/test_gnunet_service_fs_migration.c, + src/fs/test_gnunet_service_fs_p2p.c, + src/gns/test_gns_dht_three_peers.c, + src/include/gnunet_testbed_service.h, + src/nse/test_nse_multipeer.c, src/stream/perf_stream_api.c, + src/stream/test_stream_2peers.c, + src/stream/test_stream_2peers_halfclose.c, + src/testbed/test_testbed_api_test.c, + src/testbed/test_testbed_api_topology.c, + src/testbed/test_testbed_api_topology_clique.c, + src/testbed/testbed_api_test.c, + src/topology/test_gnunet_daemon_topology.c: + GNUNET_TESTBED_test_run to return status + +2012-12-11 10:51 harsha + + * [r25386] src/include/gnunet_stream_lib.h, + src/stream/stream_api.c: allow calling GNUNET_STREAM_read() from + DataProcessor callback + +2012-12-11 10:50 wachs + + * [r25385] src/ats/test_ats_api_scheduling_add_session.c: new test + +2012-12-11 10:50 wachs + + * [r25384] src/ats/Makefile.am, + src/ats/gnunet-service-ats_addresses.c, + src/ats/gnunet-service-ats_addresses_simplistic.c, + src/ats/test_ats_api_scheduling_add_address.c: changes + +2012-12-11 10:08 wachs + + * [r25382] src/ats/gnunet-service-ats_addresses.c, + src/ats/gnunet-service-ats_addresses_simplistic.c, + src/ats/test_ats_api_scheduling_add_address.c: changes + +2012-12-11 09:30 wachs + + * [r25381] src/ats/gnunet-service-ats_addresses.c, + src/ats/gnunet-service-ats_addresses.h, + src/ats/gnunet-service-ats_addresses_mlp.c, + src/ats/gnunet-service-ats_addresses_simplistic.c, + src/ats/perf_ats_mlp.c, src/ats/test_ats_mlp.c, + src/ats/test_ats_mlp_averaging.c: rename + +2012-12-11 09:28 wachs + + * [r25380] src/ats/gnunet-service-ats_addresses_simplistic.c: + changes + +2012-12-10 20:42 cfuchs + + * [r25378] src/vpn/gnunet-helper-vpn-windows.c: added functionality + to fetch the virtual interface's FriendlyName from + the registry. This information is needed for netsh later on. + +2012-12-10 16:22 wachs + + * [r25374] src/ats/test_ats_api_common.h, + src/ats/test_ats_api_scheduling_add_address.c, + src/ats/test_ats_api_scheduling_block_and_reset.c, + src/ats/test_ats_api_scheduling_destroy_address.c, + src/ats/test_ats_api_scheduling_destroy_session.c, + src/ats/test_ats_api_scheduling_update_address.c, + src/ats/test_ats_simplistic.c: changes + +2012-12-10 15:38 wachs + + * [r25372] src/ats/Makefile.am, + src/ats/gnunet-service-ats_addresses_simplistic.c, + src/ats/test_ats_simplistic.c: test and change + +2012-12-10 14:48 wachs + + * [r25367] src/ats/gnunet-service-ats_performance.c: remove + hattrick check + +2012-12-10 14:42 wachs + + * [r25365] src/ats-tool/gnunet-ats.c: coverity + +2012-12-10 14:38 wachs + + * [r25364] src/ats/test_ats_api_performance.c: coverity + +2012-12-10 14:38 wachs + + * [r25363] src/ats/gnunet-service-ats_addresses_simplistic.c: clean + up + +2012-12-10 14:34 grothoff + + * [r25361] src/fs/gnunet-service-fs_stream.c: do not queue more + than one write at a time to stream, -- hopefully fixing #2672 + +2012-12-10 14:25 wachs + + * [r25360] src/ats/gnunet-service-ats_addresses.c, + src/ats/gnunet-service-ats_addresses.h, + src/ats/gnunet-service-ats_addresses_mlp.c, + src/ats/gnunet-service-ats_addresses_mlp.h, + src/ats/gnunet-service-ats_addresses_simplistic.c, + src/ats/gnunet-service-ats_addresses_simplistic.h: more changes + +2012-12-10 14:11 harsha + + * [r25357] src/fs/gnunet-service-fs_stream.c, + src/include/gnunet_stream_lib.h, src/stream/stream_api.c: fix + 2672 + +2012-12-10 13:53 wachs + + * [r25356] src/ats/gnunet-service-ats_addresses_simplistic.c: mgmt + +2012-12-10 13:01 wachs + + * [r25353] src/ats/test_ats_api.conf: fix + +2012-12-10 13:01 wachs + + * [r25352] src/ats/gnunet-service-ats_performance.c, + src/ats/test_ats_api.conf: fix + +2012-12-10 12:35 wachs + + * [r25347] src/ats/gnunet-service-ats_addresses.c, + src/ats/test_ats_api.conf: fix + +2012-12-10 12:27 LRN + + * [r25346] src/util/configuration.c: Unnecessary argument + +2012-12-10 12:22 wachs + + * [r25345] src/util/plugin.c: one more time + +2012-12-10 12:20 wachs + + * [r25344] src/util/configuration.c, src/util/plugin.c: mem leak in + line 193configuration.c + +2012-12-10 12:13 wachs + + * [r25343] src/util/plugin.c: mistake + +2012-12-10 12:12 wachs + + * [r25342] src/util/configuration.c, src/util/plugin.c: mem leak + +2012-12-10 12:04 LRN + + * [r25340] src/util/configuration.c: Fix configuration parsing + + * Don't leak strndup'ed lines. + * Trim leading whitespace, not just trailing + * Do whitespace trimming _before_ discarding commented lines (now + # or % + does not need to be the first character in the line). + . + +2012-12-09 23:22 cfuchs + + * [r25336] src/vpn/gnunet-helper-vpn-windows.c: added unique + additional hwid entry to allow us to find our individual + virtual interface again. Needed, because netsh requires us to + resolve + the devices name as string, which can not be derived off the + deviceinfoset directly. + we are now using the handed over devicename + our PID + + the result looks something like this: gnunet-vpn13381 + +2012-12-09 15:38 grothoff + + * [r25333] src/include/gnunet_disk_lib.h, src/util/crypto_rsa.c, + src/util/disk.c: adding GNUNET_DISK_file_backup function; fixing + #2646 + +2012-12-08 21:38 grothoff + + * [r25329] src/util/os_installation.c: look in + /opt/jdk1.6.0_22/bin:/usr/lib/jvm/java-6-sun//bin:.:/home/grothoff/bin:/usr/local/bin:/usr/bin:/bin:/usr/local/games:/usr/games + for gnunet-arm before trying /proc/exe + +2012-12-08 20:19 grothoff + + * [r25328] src/util/configuration.c: fixing #2680 -- config file + lines can now have any length + +2012-12-07 16:05 wachs + + * [r25315] src/ats/gnunet-service-ats_addresses_simplistic.c: + changes + +2012-12-07 15:39 wachs + + * [r25312] src/ats/gnunet-service-ats_addresses.c, + src/ats/gnunet-service-ats_addresses.h, + src/ats/gnunet-service-ats_addresses_mlp.c, + src/ats/gnunet-service-ats_addresses_mlp.h, + src/ats/gnunet-service-ats_addresses_simplistic.c, + src/ats/gnunet-service-ats_addresses_simplistic.h: mod + +2012-12-07 15:32 wachs + + * [r25311] src/ats/gnunet-service-ats_addresses.c, + src/ats/gnunet-service-ats_addresses.h, + src/ats/gnunet-service-ats_addresses_simplistic.c, + src/ats/gnunet-service-ats_addresses_simplistic.h: mod + +2012-12-07 15:13 wachs + + * [r25310] src/ats/gnunet-service-ats_addresses.c: change + +2012-12-07 14:15 cfuchs + + * [r25309] src/vpn/gnunet-helper-vpn-windows.c: solved fixme's, + linked device handling functions to main program flow, + added some fixes here and there. added more comments to the code. + +2012-12-07 11:12 wachs + + * [r25306] src/ats/gnunet-service-ats_addresses.c, + src/ats/gnunet-service-ats_addresses_simplistic.c: increase + blocking on suggest in addresses, checking in solver + +2012-12-06 15:21 wachs + + * [r25300] src/ats/Makefile.am, src/ats/test_ats_api_scheduling.c: + remove old code + +2012-12-06 15:18 wachs + + * [r25299] src/ats/Makefile.am: changes + +2012-12-06 15:16 wachs + + * [r25298] src/ats/Makefile.am, + src/ats/test_ats_api_reset_backoff.c, + src/ats/test_ats_api_scheduling_block_and_reset.c: tests + +2012-12-06 14:00 wachs + + * [r25297] src/ats/gnunet-service-ats_addresses.c, + src/ats/gnunet-service-ats_addresses.h, + src/ats/gnunet-service-ats_addresses_mlp.c, + src/ats/test_ats_api_scheduling_update_address.c: changes + +2012-12-06 13:16 wachs + + * [r25293] src/ats/test_ats_api_scheduling_add_address.c, + src/ats/test_ats_api_scheduling_update_address.c: ats info + +2012-12-06 12:32 wachs + + * [r25291] src/ats/test_ats_api_scheduling_add_address.c, + src/ats/test_ats_api_scheduling_destroy_address.c, + src/ats/test_ats_api_scheduling_destroy_session.c, + src/ats/test_ats_api_scheduling_update_address.c: improvements + +2012-12-06 12:20 wachs + + * [r25290] src/ats/Makefile.am, + src/ats/test_ats_api_scheduling_destroy_address.c, + src/ats/test_ats_api_scheduling_destroy_session.c, + src/ats/test_ats_api_scheduling_update_address.c, + src/ats/test_ats_api_update_address.c: changes + +2012-12-06 12:17 wachs + + * [r25289] src/ats/test_ats_api_scheduling_add_address.c: changes + +2012-12-06 10:37 dold + + * [r25287] src/include/gnunet_protocols.h: added consensus message + types + +2012-12-06 10:02 wachs + + * [r25285] src/ats/gnunet-service-ats_addresses.c, + src/ats/test_ats_api_common.h, + src/ats/test_ats_api_scheduling_destroy_session.c: changes + +2012-12-06 09:42 wachs + + * [r25284] src/ats/test_ats_api_scheduling_add_address.c, + src/ats/test_ats_api_scheduling_destroy_address.c: changes + +2012-12-06 09:22 wachs + + * [r25283] src/ats/test_ats_api_scheduling_destroy_address.c: fix + +2012-12-06 09:09 wachs + + * [r25281] src/ats/ats_api_scheduling.c, + src/ats/gnunet-service-ats_addresses.c, + src/ats/test_ats_api_scheduling_add_address.c: fix + +2012-12-06 08:41 wachs + + * [r25280] src/ats/test_ats_api_scheduling_init.c: minor + +2012-12-06 01:34 LRN + + * [r25279] src/ats/gnunet-service-ats_addresses.c, + src/ats/gnunet-service-ats_addresses_simplistic.c: Don't crash + when address suggestor fails + +2012-12-05 22:34 LRN + + * [r25278] src/ats/gnunet-service-ats_addresses.c, + src/ats/gnunet-service-ats_addresses_mlp.h: Should be compilable + without libglpk again + +2012-12-05 21:41 dold + + * [r25275] src/consensus/Makefile.am, src/consensus/consensus.h, + src/consensus/consensus_api.c, + src/consensus/gnunet-consensus-start-peers.c, + src/consensus/gnunet-consensus.c, + src/consensus/gnunet-service-consensus.c, src/consensus/ibf.c, + src/consensus/ibf.h, src/consensus/test_consensus.conf: consensus + api, consensus service (local), peer driver and ibf sketch + +2012-12-05 16:39 wachs + + * [r25266] src/ats/test_ats_api_scheduling_add_address.c, + src/ats/test_ats_api_scheduling_destroy_address.c: changes + +2012-12-05 16:33 wachs + + * [r25265] src/ats/test_ats_api_scheduling_destroy_session.c: + changes + +2012-12-05 16:23 wachs + + * [r25264] src/ats/Makefile.am, + src/ats/test_ats_api_scheduling_destroy_session.c: changes + +2012-12-05 16:18 wachs + + * [r25263] src/ats/Makefile.am, + src/ats/gnunet-service-ats_addresses.c, + src/ats/test_ats_api_scheduling_destroy_address.c: fix and new + test + +2012-12-05 16:04 wachs + + * [r25262] src/ats/test_ats_api_common.h: test rewrite + +2012-12-05 15:57 wachs + + * [r25261] src/ats/Makefile.am, + src/ats/gnunet-service-ats_addresses.c, + src/ats/test_ats_api_scheduling_add_address.c, + src/ats/test_ats_api_scheduling_init.c: test rewrite + +2012-12-05 15:38 wachs + + * [r25260] src/ats/ats_api_performance.c: callback check + +2012-12-05 14:56 wachs + + * [r25259] src/ats/gnunet-service-ats_addresses.c: changes + +2012-12-05 14:42 wachs + + * [r25258] src/ats/gnunet-service-ats_addresses.c: remove unusued + code + +2012-12-05 14:41 wachs + + * [r25257] src/ats/gnunet-service-ats_addresses.c, + src/ats/gnunet-service-ats_addresses.h, + src/ats/gnunet-service-ats_addresses_simplistic.c, + src/ats/gnunet-service-ats_addresses_simplistic.h: remove unusued + code + +2012-12-05 14:31 wachs + + * [r25256] src/ats/gnunet-service-ats_addresses.h: some docu + +2012-12-05 14:18 wachs + + * [r25255] src/ats/gnunet-service-ats_addresses_mlp.c, + src/ats/gnunet-service-ats_addresses_mlp.h, + src/ats/perf_ats_mlp.c, src/ats/test_ats_mlp.c, + src/ats/test_ats_mlp_averaging.c: fix tests + +2012-12-05 14:06 wachs + + * [r25254] src/ats/gnunet-service-ats_addresses.c, + src/ats/gnunet-service-ats_addresses.h, + src/ats/gnunet-service-ats_addresses_mlp.c, + src/ats/gnunet-service-ats_addresses_mlp.h, + src/ats/gnunet-service-ats_addresses_simplistic.c, + src/ats/gnunet-service-ats_addresses_simplistic.h, + src/ats/perf_ats_mlp.c, src/ats/test_ats_mlp.c, + src/ats/test_ats_mlp_averaging.c: commit required ... things can + be broken + +2012-12-05 10:44 wachs + + * [r25250] src/ats/gnunet-service-ats_addresses.c: fix for tests + +2012-12-05 10:14 cfuchs + + * [r25249] src/vpn/gnunet-helper-vpn-windows.c: added teardown + functionality for deconstructing the interface created by + the win32 vpn-helper. + +2012-12-04 16:04 wachs + + * [r25243] src/ats/gnunet-service-ats_addresses.c, + src/ats/gnunet-service-ats_addresses.h, + src/ats/gnunet-service-ats_addresses_mlp.c, + src/ats/gnunet-service-ats_scheduling.c: changes + +2012-12-04 15:26 wachs + + * [r25237] src/ats/gnunet-service-ats_addresses_mlp.c, + src/ats/gnunet-service-ats_addresses_mlp.h: doxygen + +2012-12-04 15:14 wachs + + * [r25235] src/ats/gnunet-service-ats_addresses.c: changes + +2012-12-04 15:09 wachs + + * [r25233] src/ats/gnunet-service-ats_addresses.c, + src/ats/gnunet-service-ats_addresses_simplistic.c, + src/ats/gnunet-service-ats_addresses_simplistic.h: docu + +2012-12-04 14:57 wachs + + * [r25232] src/ats/gnunet-service-ats_addresses.c: changes + +2012-12-04 14:38 wachs + + * [r25229] src/ats/gnunet-service-ats_addresses.c, + src/ats/gnunet-service-ats_addresses.h, + src/ats/gnunet-service-ats_addresses_mlp.c, + src/ats/gnunet-service-ats_addresses_mlp.h, + src/ats/gnunet-service-ats_addresses_simplistic.c, + src/ats/gnunet-service-ats_addresses_simplistic.h: changes + +2012-12-04 14:02 wachs + + * [r25228] src/ats/gnunet-service-ats_addresses.c: mem leak + +2012-12-04 13:45 wachs + + * [r25226] src/ats/gnunet-service-ats.c, + src/ats/gnunet-service-ats_addresses.c, + src/ats/gnunet-service-ats_addresses.h: restructure + +2012-12-04 13:16 wachs + + * [r25223] src/ats/ats.conf.in, + src/ats/gnunet-service-ats_addresses.c, + src/ats/gnunet-service-ats_addresses.h, + src/ats/gnunet-service-ats_addresses_mlp.c, + src/ats/gnunet-service-ats_addresses_mlp.h, + src/ats/gnunet-service-ats_addresses_simplistic.c, + src/ats/gnunet-service-ats_addresses_simplistic.h, + src/ats/perf_ats_mlp.c, src/ats/test_ats_mlp.c, + src/ats/test_ats_mlp_averaging.c: changes + +2012-12-03 22:58 cfuchs + + * [r25209] src/vpn/gnunet-helper-vpn-windows.c: Added logics to + install virtual networks interfaces for gnunet-vpn in + win32 based on the info that can be found in the MSDN. + + Current revision: + http://msdn.microsoft.com/en-us/library/windows/hardware/ff549791%28v=vs.85%29.aspx + +2012-12-03 16:46 harsha + + * [r25199] src/include/gnunet_testbed_service.h, + src/testbed/gnunet-testbed-profiler.c, + src/testbed/test_testbed_api_3peers_3controllers.c, + src/testbed/test_testbed_api_controllerlink.c, + src/testbed/testbed_api_hosts.c, + src/testbed/testbed_api_testbed.c: host compatibility check in + GNUNET_TESTBED_run() and fixes + +2012-12-03 15:09 wachs + + * [r25191] src/ats/gnunet-service-ats_addresses_simplistic.c, + src/ats/gnunet-service-ats_addresses_simplistic.h: doxygen + +2012-12-03 15:05 wachs + + * [r25190] src/ats/gnunet-service-ats_addresses.c, + src/ats/gnunet-service-ats_addresses_simplistic.c, + src/ats/gnunet-service-ats_addresses_simplistic.h: changes + +2012-12-03 14:57 wachs + + * [r25189] src/ats/gnunet-service-ats_addresses.c, + src/ats/gnunet-service-ats_addresses_simplistic.c, + src/ats/gnunet-service-ats_addresses_simplistic.h: changes + +2012-12-03 14:50 harsha + + * [r25188] src/testbed/gnunet-testbed-profiler.c: display and + update number of hosts checked + +2012-12-03 14:50 wachs + + * [r25187] src/ats/Makefile.am, src/ats/ats.conf.in, + src/ats/gnunet-service-ats_addresses.c, + src/ats/gnunet-service-ats_addresses_simplistic.c, + src/ats/gnunet-service-ats_addresses_simplistic.h, + src/ats/test_ats_api.conf: changes + +2012-12-03 13:58 harsha + + * [r25185] src/consensus, src/include/gnunet_testbed_service.h, + src/sysmon, src/testbed/gnunet-testbed-profiler.c, + src/testbed/test_testbed_api_3peers_3controllers.c, + src/testbed/test_testbed_api_controllerlink.c, + src/testbed/testbed_api_hosts.c, + src/testbed/testbed_api_testbed.c: making + GNUNET_TESTBED_is_host_compatible() asynchronous + +2012-12-02 12:02 harsha + + * [r25176] src/testbed/testbed_api_testbed.c: hosts file support in + GNUNET_TESTBED_run() - fixes 2667 + +2012-11-30 16:56 harsha + + * [r25173] configure.ac: configure option for using IBM LoadLeveler + for scheduling testbed slaves on SuperMUC + +2012-11-29 09:36 wachs + + * [r25160] src/sysmon/Makefile.am, src/sysmon/test_glibtop.c: + installation test + +2012-11-29 09:07 wachs + + * [r25158] src/sysmon/gnunet-daemon-sysmon.c: type issues + +2012-11-28 16:45 dold + + * [r25157] src/consensus/gnunet-service-consensus.c: fixed copying + of wrong memory address + +2012-11-28 16:36 wachs + + * [r25156] configure.ac: possbility a) I did not commit or b) some + removed my commit?! Please complain about it + +2012-11-28 16:33 dold + + * [r25155] src/include/gnunet_protocols.h: deleted duplicate + message id definition + +2012-11-28 16:32 dold + + * [r25154] po/de.po, po/es.po, po/sv.po, po/vi.po, po/zh_CN.po, + src/consensus/Makefile.am, src/consensus/consensus_api.c, + src/consensus/gnunet-service-consensus.c, + src/consensus/gnunet-service-consensus.cc, + src/consensus/test_consensus.conf, + src/consensus/test_consensus_api.c, + src/include/gnunet_consensus_service.h, + src/include/gnunet_protocols.h: dummy consensus service + +2012-11-28 16:14 wachs + + * [r25153] src/sysmon/Makefile.am, src/sysmon/test_glibtop.c, + src/sysmon/test_glibtop_network.c, + src/sysmon/test_glibtop_process.c: network test + +2012-11-28 15:10 wachs + + * [r25152] src/include/gnunet_protocols.h: compile error + +2012-11-28 14:33 wachs + + * [r25150] src/sysmon/test_glibtop.c: changes + +2012-11-28 14:21 wachs + + * [r25149] src/sysmon/test_glibtop.c: test + +2012-11-28 13:50 wachs + + * [r25148] src/sysmon/Makefile.am, + src/sysmon/gnunet-daemon-sysmon.c: add a test for glibtop + +2012-11-26 17:12 dold + + * [r25143] src/consensus/consensus_api.c, + src/include/gnunet_consensus_service.h: fixed doxygen + +2012-11-26 13:33 harsha + + * [r25139] src/stream/stream_api.c: exponential delay for data + retransmissions + +2012-11-26 13:00 harsha + + * [r25137] src/stream/stream_api.c: seperate timeouts for MESH + retries + +2012-11-26 10:48 wachs + + * [r25135] src/sysmon/gnunet-daemon-sysmon.c: changes + +2012-11-26 10:26 wachs + + * [r25134] src/sysmon/gnunet-daemon-sysmon.c: changes + +2012-11-26 10:11 cfuchs + + * [r25133] src/vpn/Makefile.am: added libraries for setupapi & + dependencies + +2012-11-24 23:54 grothoff + + * [r25125] src/stream/stream_api.c: removing invalid assertions + that shutdown must preceed closing + +2012-11-24 23:45 grothoff + + * [r25123] src/fs/gnunet-service-fs.c, + src/fs/gnunet-service-fs_pr.c, src/fs/gnunet-service-fs_pr.h, + src/fs/gnunet-service-fs_put.c: actually using stream for + dblock/iblock transfer if possible + +2012-11-24 22:49 grothoff + + * [r25119] src/fs/test_fs_download_indexed.conf, + src/fs/test_fs_download_stream.conf: combining test_fs_download.c + and test_fs_download_index.c into one file, adding additional + test test_fs_download_stream + +2012-11-24 22:49 grothoff + + * [r25118] src/fs/Makefile.am, src/fs/test_fs_download.c, + src/fs/test_fs_download_data.conf, + src/fs/test_fs_download_indexed.c: combining test_fs_download.c + and test_fs_download_index.c into one file, adding additional + test test_fs_download_stream + +2012-11-24 22:43 grothoff + + * [r25117] src/include/gauger.h: adding missing parens around macro + arguments in gauger macros + +2012-11-24 08:08 LRN + + * [r25115] src/transport/plugin_transport_udp.c: Be more specific + about UDP read failures + +2012-11-23 17:07 wachs + + * [r25114] src/sysmon, src/sysmon/Makefile.am, + src/sysmon/gnunet-daemon-sysmon.c, src/sysmon/sysmon.conf.in: + changes + +2012-11-23 12:23 harsha + + * [r25113] src/testbed, src/testbed/Makefile.am, + src/testbed/test_testbed_api_testbed_run_topologyscalefree.conf: + test case for scale free routing + +2012-11-22 19:57 grothoff + + * [r25111] src/fs/gnunet-service-fs_pr.c, + src/fs/gnunet-service-fs_stream.c, + src/fs/gnunet-service-fs_stream.h: towards using stream for + non-anonymous file-sharing + +2012-11-22 18:27 grothoff + + * [r25110] src/fs/gnunet-service-fs.c, src/fs/gnunet-service-fs.h, + src/fs/gnunet-service-fs_pr.c, src/fs/gnunet-service-fs_stream.c, + src/include/gnunet_protocols.h: mostly finishing server-side for + FS-over-stream + +2012-11-22 17:03 harsha + + * [r25107] src/testbed, src/testbed/Makefile.am, + src/testbed/overlay_topology.txt, + src/testbed/test_testbed_api_3peers_3controllers.c, + src/testbed/test_testbed_api_testbed_run_topologyfromfile.conf, + src/testbed/testbed_api_testbed.c, + src/testbed/testbed_api_topology.c: topology loading from file + +2012-11-22 15:49 grothoff + + * [r25106] src/Makefile.am, src/fs/Makefile.am, + src/fs/gnunet-service-fs.c, src/fs/gnunet-service-fs_stream.c, + src/fs/gnunet-service-fs_stream.h, + src/include/gnunet_applications.h, + src/include/gnunet_stream_lib.h, src/stream/stream_api.c: + starting to use stream in fs + +2012-11-22 15:29 wachs + + * [r25104] src/ats/gnunet-service-ats_performance.c: fix + uninitialized mem + +2012-11-22 15:15 wachs + + * [r25102] src/ats/gnunet-service-ats_performance.c: bug fixing: + cannot drop messages + +2012-11-22 14:05 wachs + + * [r25099] src/ats/test_ats_api_performance.c: test done + +2012-11-22 13:49 wachs + + * [r25098] src/ats/Makefile.am, src/ats/test_ats_api_performance.c: + stage 3 + +2012-11-21 20:56 dold + + * [r25091] po/POTFILES.in, po/de.po, po/es.po, po/sv.po, po/vi.po, + po/zh_CN.po, src/consensus/Makefile.am, + src/consensus/consensus.h, src/consensus/consensus_api.c, + src/consensus/gnunet-service-consensus.cc, + src/consensus/test_consensus.conf, + src/consensus/test_consensus_api.c, + src/include/gnunet_consensus_service.h, + src/include/gnunet_protocols.h: started implementing consensus + api and service + +2012-11-21 10:51 wachs + + * [r25083] src/ats/ats_api_performance.c, + src/ats/gnunet-service-ats_performance.c, + src/ats/gnunet-service-ats_performance.h, + src/include/gnunet_ats_service.h: dogygen + +2012-11-20 15:00 wachs + + * [r25070] src/ats-tool/gnunet-ats.c, + src/ats/ats_api_performance.c: changes, almost done + +2012-11-20 12:29 harsha + + * [r25067] src/include/gnunet_testbed_service.h, + src/mesh/gnunet-regex-profiler.c, + src/testbed/gnunet-testbed-profiler.c, + src/testbed/test_testbed_api_topology.c, + src/testbed/test_testbed_api_topology_clique.c, + src/testbed/testbed_api_testbed.c, + src/testbed/testbed_api_topology.c: extended overlay configure + topology to return max connections + +2012-11-20 11:24 harsha + + * [r25063] src/testbed/testbed_api_topology.c: scale free topology + +2012-11-19 18:14 LRN + + * [r25059] configure.ac, src/util/program.c, src/util/service.c, + src/util/test_getopt.c: Hardcode svn revision in compiled + binaries + +2012-11-19 16:30 wachs + + * [r25058] src/ats-tool/gnunet-ats.c, src/ats/ats.h, + src/ats/ats_api_performance.c, src/ats/gnunet-service-ats.c, + src/ats/gnunet-service-ats_performance.c, + src/ats/gnunet-service-ats_performance.h, + src/include/gnunet_protocols.h: changes ... more TBD + +2012-11-19 13:59 harsha + + * [r25050] src/include/gnunet_stream_lib.h, + src/stream/stream_api.c: cleanup write handle upon shutdown + +2012-11-19 09:56 wachs + + * [r25045] contrib/ssh-keys: omar ssh key + +2012-11-18 20:56 tg + + * [r25044] src/include/gnunet_hello_lib.h: hello lib header fix + +2012-11-18 19:54 harsha + + * [r25042] src/stream/Makefile.am, src/stream/stream_api.c, + src/stream/test_stream_local.conf: use statistics + +2012-11-18 18:09 tg + + * [r25040] src/hello/hello.c, src/include/gnunet_crypto_lib.h, + src/include/gnunet_hello_lib.h, + src/peerinfo-tool/gnunet-peerinfo.c, src/util/crypto_rsa.c: moved + hello uri functions to hello lib + +2012-11-18 18:09 tg + + * [r25039] src/dht/gnunet-service-dht.c, + src/dht/gnunet-service-dht_neighbours.c, + src/transport/gnunet-service-transport.c, + src/transport/gnunet-service-transport_hello.c: configurable + hello expiration + +2012-11-18 18:09 tg + + * [r25038] src/util/server.c: util/server: removed unused var + +2012-11-17 22:21 bartpolot + + * [r25034] src/include/gnunet_mesh_service.h, + src/include/gnunet_protocols.h, src/mesh/Makefile.am, + src/mesh/gnunet-service-mesh.c, src/mesh/mesh.h, + src/mesh/mesh_api.c: Added mesh CLI with basic tunnel listing + +2012-11-17 12:24 harsha + + * [r25032] src/testing/testing.c: fix memleak + +2012-11-17 08:57 LRN + + * [r25031] src/statistics/gnunet-statistics.c: Use full, 3-argument + fprintf invocation + +2012-11-16 17:53 harsha + + * [r25029] src/testbed, src/testbed/Makefile.am, + src/testbed/test_testbed_api_testbed_run_topologysmallworld.conf, + src/testbed/testbed_api_testbed.c, + src/testbed/testbed_api_topology.c: small world topology + +2012-11-16 16:43 harsha + + * [r25017] src/include/gnunet_testbed_service.h, + src/testbed/testbed_api_topology.c: 2D Torus topology + +2012-11-16 16:36 wachs + + * [r25014] src/transport/gnunet-service-transport_neighbours.c: + logging + +2012-11-16 16:35 wachs + + * [r25011] src/ats/gnunet-service-ats_addresses.c, + src/transport/gnunet-service-transport_neighbours.c: transmit all + ats properties + +2012-11-16 14:36 harsha + + * [r25002] src/testbed/test_testbed_api.conf, + src/testbed/testbed.conf.in, src/testbed/testbed_api.c, + src/testbed/testbed_api.h, src/testbed/testbed_api_peers.c: + adaptive parallel overlay connects + +2012-11-16 14:11 wachs + + * [r25001] src/ats-tool/gnunet-ats.c, + src/include/gnunet_ats_service.h: print ats properties + +2012-11-16 13:14 szengel + + * [r24998] contrib/regex_profiler_infiniband.conf: Saner default + values for the infiniband regex profiler conf + +2012-11-16 13:08 szengel + + * [r24997] src/regex/gnunet-regex-simulation-profiler.c, + src/regex/regex.c, src/regex/regex_internal.h, + src/regex/regex_random.c, + src/regex/regex_simulation_profiler_test.conf, + src/regex/test_regex_eval_api.c, + src/regex/test_regex_graph_api.c, + src/regex/test_regex_iterate_api.c: Cleaup, indentation, comments + etc. + +2012-11-16 13:06 wachs + + * [r24995] src/ats-tool/gnunet-ats.c: print ats information + +2012-11-16 11:20 harsha + + * [r24993] src/testbed/test_testbed_api_operations.c, + src/testbed/testbed_api_operations.c, + src/testbed/testbed_api_operations.h: dynamically adjustable + operation queues + +2012-11-15 14:50 wachs + + * [r24985] src/namestore/gnunet-service-namestore.c, + src/namestore/namestore.h, src/namestore/namestore_common.c, + src/namestore/test_namestore_api.conf, + src/namestore/test_namestore_api_create.c, + src/namestore/test_namestore_api_create_update.c, + src/namestore/test_namestore_api_lookup.c, + src/namestore/test_namestore_api_lookup_specific_type.c, + src/namestore/test_namestore_api_put.c, + src/namestore/test_namestore_api_remove.c, + src/namestore/test_namestore_api_remove_not_existing_record.c, + src/namestore/test_namestore_api_sign_verify.c: implementing + mantis 0002193 + +2012-11-15 13:59 wachs + + * [r24984] src/testing/testing.c: prefix support for testing + +2012-11-15 13:38 grothoff + + * [r24982] src/include/gnunet_consensus_service.h: polishing + consensus API + +2012-11-15 10:44 dold + + * [r24978] src/consensus/Makefile.am, + src/consensus/gnunet-consensus.c, + src/consensus/gnunet-service-consensus.cc, + src/include/gnunet_consensus_service.h: added declarations for + the consensus api + +2012-11-15 10:24 dold + + * [r24977] src/mesh/mesh.conf.in: changed @UNIXONLY@ to @JAVAPORT@ + +2012-11-15 09:58 wachs + + * [r24974] src/transport/plugin_transport_udp.c: fix + +2012-11-14 17:06 harsha + + * [r24970] src/include/gnunet_testing_lib-new.h, + src/testbed/gnunet-service-testbed.c, src/testing/testing.c: kill + all peers first and wait for them later + +2012-11-14 15:55 wachs + + * [r24966] src/transport/plugin_transport_unix.c: fix mantis + 0002653 + +2012-11-14 15:53 grothoff + + * [r24965] src/dht/dht_api.c, src/dht/gnunet-service-dht_clients.c, + src/dht/gnunet-service-dht_neighbours.c: fixing crash of mesh + service -- reproduced by regex profiler w 100 peers -- on + shutdown due to failure to initialize dht_handle field + +2012-11-14 15:15 wachs + + * [r24962] src/transport/plugin_transport_unix.c: use api correctly + +2012-11-14 14:21 wachs + + * [r24957] src/transport/test_transport_api_unreliability.c: + hunting bugs + +2012-11-14 14:09 wachs + + * [r24955] src/transport/plugin_transport_unix.c, + src/transport/test_transport_api_unreliability.c: improve unix + timeout behaviour + +2012-11-14 13:41 szengel + + * [r24953] src/mesh/gnunet-regex-profiler.c: Removed waiting time + before linking + +2012-11-14 13:03 grothoff + + * [r24950] src/dht/gnunet-service-dht_clients.c: use exp backoff + macro, start with retry frequency of 1s, instead of the insane + 1ms + +2012-11-14 10:50 bartpolot + + * [r24945] src/dht/gnunet-service-dht_clients.c, + src/dht/gnunet-service-dht_datacache.c, + src/dht/gnunet-service-dht_routing.c, + src/include/gnunet_block_lib.h, src/mesh/plugin_block_mesh.c: + Added GNUNET_BLOCK_EVALUATION_RESULT_IRRELEVANT + +2012-11-14 09:19 szengel + + * [r24943] src/mesh/gnunet-daemon-regexprofiler.c: doxygen + +2012-11-14 09:16 szengel + + * [r24942] src/mesh/gnunet-daemon-regexprofiler.c: union of regexes + in profiler + +2012-11-13 20:05 grothoff + + * [r24938] src/datacache/Makefile.am, src/datacache/datacache.c, + src/datacache/perf_datacache.c, + src/datacache/perf_datacache_data_heap.conf, + src/datacache/perf_datacache_data_mysql.conf, + src/datacache/plugin_datacache_heap.c, + src/datacache/plugin_datacache_mysql.c, + src/datacache/plugin_datacache_postgres.c, + src/datacache/plugin_datacache_sqlite.c, + src/datacache/plugin_datacache_template.c, + src/datacache/test_datacache.c, + src/datacache/test_datacache_data_heap.conf, + src/datacache/test_datacache_data_mysql.conf, + src/datacache/test_datacache_quota.c, + src/dht/gnunet-service-dht_datacache.c, + src/include/gnunet_datacache_lib.h, + src/include/gnunet_datacache_plugin.h: changing datacache API to + separate put-paths from data (so that plugins can test for + duplicates), removing support for MySQL + +2012-11-13 17:02 szengel + + * [r24933] src/regex/regex.c, src/regex/regex_internal.h: + optimizations + +2012-11-13 13:55 grothoff + + * [r24931] src/datacache/datacache.c: fixing #2641, datastore size + way off + +2012-11-13 13:25 grothoff + + * [r24928] src/datastore/plugin_datastore_sqlite.c: fixing + bloomfilter reconstruction after quota change, iterator for + sqlite failed to return keys due to off-by-one error + +2012-11-12 18:14 harsha + + * [r24920] src/include/gnunet_testbed_service.h: Options for 2D + Torus + +2012-11-12 18:13 harsha + + * [r24919] src/testbed, src/testbed/Makefile.am, + src/testbed/test_testbed_api_testbed_run_topologyrandom.conf, + src/testbed/test_testbed_api_testbed_run_topologysmallworldring.conf, + src/testbed/testbed_api_testbed.c, + src/testbed/testbed_api_topology.c: implementing small world ring + topology + +2012-11-12 16:55 harsha + + * [r24918] src/testbed, src/testbed/Makefile.am, + src/testbed/test_testbed_api_testbed_run_topologyring.conf, + src/testbed/testbed_api_testbed.c: test case for ring topology + +2012-11-12 16:21 harsha + + * [r24917] src/testbed/testbed_api_topology.c: implemented line + topology + +2012-11-12 14:42 grothoff + + * [r24913] src/datacache/datacache.c: add option to disable Bloom + filter entirely (only for benchmarking) + +2012-11-12 11:00 grothoff + + * [r24908] src/datacache/datacache.c, + src/datacache/plugin_datacache_sqlite.c: support running purely + in-memory + +2012-11-12 08:45 wachs + + * [r24906] src/include/gnunet_transport_service.h, + src/transport/transport_api.c: doxygen + +2012-11-11 15:04 szengel + + * [r24901] src/mesh/gnunet-daemon-regexprofiler.c, + src/mesh/gnunet-service-mesh.c: doxygen + +2012-11-11 14:23 szengel + + * [r24900] contrib/regex_profiler_infiniband.conf, + src/mesh/gnunet-daemon-regexprofiler.c, + src/mesh/gnunet-regex-profiler.c, src/mesh/gnunet-service-mesh.c: + Better mesh/regex profiler performance. + +2012-11-10 22:16 grothoff + + * [r24893] doc/man/gnunet-peerinfo.1: "man gnunet-peerinfo" doesn't + have the -g or -p options which are listed in "gnunet-peerinfo + --help". One spelling mistake is also fixed in the attached + "diff" (see: additional information). This was against r24891. - + #2649. + +2012-11-10 21:36 grothoff + + * [r24892] src/fs/gnunet-service-fs_pr.c: use new DHT API to block + known results when searching in the DHT + +2012-11-10 20:21 LRN + + * [r24890] src/gns/w32nsp.c: Update w32nsp to use 'gads' instead of + 'gnunet' + +2012-11-10 13:41 grothoff + + * [r24883] src/util/os_installation.c: trying to fix #2645 -- + support lib64/gnunet/libexec/ installations + +2012-11-10 10:29 LRN + + * [r24882] src/include/gauger.h: Fix W32 gauger C bindings - quote + arguments + +2012-11-10 05:51 LRN + + * [r24881] src/include/gauger.h: Update gauger C binding for W32 + +2012-11-09 15:56 wachs + + * [r24873] src/transport/gnunet-service-transport_clients.c, + src/transport/gnunet-service-transport_neighbours.c, + src/transport/gnunet-transport.c: implement mantis 0002419 + +2012-11-09 15:04 harsha + + * [r24870] src/testbed/test_testbed_api_2peers_1controller.c: save + tests from crashing + +2012-11-09 15:01 wachs + + * [r24868] src/include/gnunet_transport_service.h: docu + +2012-11-09 13:52 wachs + + * [r24863] src/transport/gnunet-transport.c: API change + +2012-11-09 13:33 wachs + + * [r24862] src/core/test_core_api.c, + src/core/test_core_api_reliability.c, + src/core/test_core_quota_compliance.c, + src/dht/gnunet-service-dht_neighbours.c, + src/include/gnunet_transport_service.h, + src/testbed/gnunet-service-testbed.c, src/testing_old/testing.c, + src/topology/gnunet-daemon-topology.c, + src/transport/gnunet-transport.c, + src/transport/test_transport_api_restart_1peer.c, + src/transport/test_transport_api_restart_2peers.c, + src/transport/transport-testing.c, src/transport/transport_api.c: + changes to transport api + +2012-11-09 12:34 harsha + + * [r24861] src/testbed/gnunet-service-testbed.c: adopting to new + transport API + +2012-11-08 19:25 bartpolot + + * [r24849] src/mesh/gnunet-service-mesh.c, + src/mesh/mesh_block_lib.c, src/mesh/mesh_block_lib.h, + src/mesh/mesh_common.c, src/mesh/plugin_block_mesh.c: MESH uses + DHT xquery to limit the results returned during a regex string + search + +2012-11-08 16:50 LRN + + * [r24848] src/transport/gnunet-transport.c: Use full, 3-argument + invocation of FRPINTF (again) + +2012-11-08 15:12 grothoff + + * [r24847] src/statistics/statistics_api.c: add option to disable + use of stats entirely + +2012-11-08 15:04 wachs + + * [r24846] src/transport/gnunet-transport.c: fixed -b semantics: + receive from all peers + +2012-11-08 14:09 wachs + + * [r24841] src/transport/gnunet-transport.c: changes + +2012-11-08 11:01 wachs + + * [r24834] src/transport/gnunet-transport.c: not working yet + +2012-11-07 18:26 harsha + + * [r24826] src/include/gnunet_disk_lib.h, src/util/disk.c: making + readable check optional + +2012-11-07 17:26 szengel + + * [r24825] src/mesh/Makefile.am, + src/mesh/gnunet-daemon-regexprofiler.c, + src/mesh/gnunet-service-regexprofiler.c: regexprofiler service to + daemon + +2012-11-07 16:56 harsha + + * [r24823] src/chat/chat.c, src/fs/fs_api.c, + src/fs/gnunet-auto-share.c, src/include/gnunet_disk_lib.h, + src/mesh/gnunet-regex-profiler.c, + src/regex/gnunet-regex-simulation-profiler.c, src/util/disk.c, + src/util/test_disk.c: Parameterized directory listing permission + check + +2012-11-07 11:24 LRN + + * [r24818] src/ats-tool/gnunet-ats.c: Use full, 3-argument FPRINTF + invocation + +2012-11-07 09:54 wachs + + * [r24817] src/transport/gnunet-service-transport_clients.c: fix + mem leak mantis 0002635 + +2012-11-06 23:46 harsha + + * [r24816] src/stream/perf_stream_api.c: reduce number of packets + +2012-11-06 23:25 harsha + + * [r24815] src/arm/gnunet-arm.c: print help for timeout argument + +2012-11-06 22:32 harsha + + * [r24813] src/util/disk.c: check for existing directories in + reverse order + +2012-11-06 18:16 szengel + + * [r24811] contrib/regex_profiler_infiniband.conf, + src/mesh/gnunet-regex-profiler.c, + src/mesh/gnunet-service-regexprofiler.c: Added regex prefix to + config for regex profiler. + +2012-11-05 21:37 harsha + + * [r24801] src/gns/nss/Makefile.am: nss uninstall script to extra + dist + +2012-11-05 21:35 harsha + + * [r24800] src/testbed/Makefile.am: including sample_hosts.txt to + EXTRA_DIST + +2012-11-05 21:21 grothoff + + * [r24799] po/de.po, po/es.po, po/sv.po, po/vi.po, po/zh_CN.po, + src/transport/Makefile.am: ready for 0.9.4 release + +2012-11-05 21:01 szengel + + * [r24792] src/mesh/gnunet-regex-profiler.c, + src/mesh/gnunet-service-regexprofiler.c: regex profiler fixes + +2012-11-05 20:46 harsha + + * [r24788] src/stream/perf_stream_api.c: dead code + +2012-11-05 20:41 harsha + + * [r24787] src/stream/perf_stream_api.c: changing to fixed number + of packets instead of fixed size test data + +2012-11-05 20:05 wachs + + * [r24782] src/transport/plugin_transport_http_common.c: last cb + NULL + +2012-11-05 19:21 harsha + + * [r24779] src/testing/testing.c: coverity fixes + +2012-11-05 19:11 harsha + + * [r24777] src/testbed/testbed_api_testbed.c: coverity fix + +2012-11-05 19:05 harsha + + * [r24776] src/stream/stream_api.c: coverity fixes + +2012-11-05 18:53 wachs + + * [r24774] src/transport/plugin_transport_http_server.c: fix + +2012-11-05 17:03 bartpolot + + * [r24764] src/mesh/gnunet-service-mesh.c: dont cancel mesh pending + traffic on tunnel destroy + +2012-11-05 17:03 harsha + + * [r24763] src/testbed/test_testbed_api.conf, + src/testbed/test_testbed_api_testbed_run_topologyclique.conf, + src/testbed/test_testbed_api_testbed_run_topologyline.conf, + src/testbed/test_testbed_api_testbed_run_topologyrandom.conf: + reverted test configurations to include ATS + +2012-11-05 16:54 harsha + + * [r24762] + src/testbed/test_testbed_api_testbed_run_topologyclique.conf, + src/testbed/test_testbed_api_testbed_run_topologyline.conf, + src/testbed/test_testbed_api_testbed_run_topologyrandom.conf: + merging configs + +2012-11-05 16:49 harsha + + * [r24761] src/testbed/test_testbed_api.conf, + src/testbed/test_testbed_api_testbed_run_topologyclique.conf, + src/testbed/test_testbed_api_testbed_run_topologyline.conf, + src/testbed/test_testbed_api_testbed_run_topologyrandom.conf: + merging configs + +2012-11-05 16:31 wachs + + * [r24760] src/ats/gnunet-service-ats_addresses.c: not a hard + error, print a warning + +2012-11-05 16:08 harsha + + * [r24759] src/testbed/test_testbed_api.conf: do not start + gns-helper-service even on windows + +2012-11-05 16:02 harsha + + * [r24758] src/testbed/Makefile.am: added testing configuration + files + +2012-11-05 16:01 szengel + + * [r24757] src/include/gnunet_regex_lib.h, + src/mesh/gnunet-regex-profiler.c, + src/mesh/gnunet-service-regexprofiler.c, + src/mesh/regexprofiler.conf: regex profiler fixes + +2012-11-05 15:59 harsha + + * [r24756] src/testbed/testbed_api.c: maintain argv for helpers + +2012-11-05 15:58 wachs + + * [r24755] src/transport/plugin_transport_http_client.c: docu + +2012-11-05 15:54 harsha + + * [r24754] src/util/helper.c: fix + +2012-11-05 15:50 wachs + + * [r24753] src/transport/plugin_transport_http_client.c, + src/transport/test_transport_api_unreliability.c: doxygen error + +2012-11-05 15:22 wachs + + * [r24752] src/dht/Makefile.am: make dist not working + +2012-11-05 14:52 wachs + + * [r24749] src/ats/ats_api_performance.c: infocb can be NULL + +2012-11-05 14:33 szengel + + * [r24744] contrib/regex_profiler_infiniband.conf, + src/mesh/Makefile.am, src/mesh/regex_profiler_test.conf: Moving + regex profiler config to contrib + +2012-11-05 14:30 szengel + + * [r24743] src/mesh/regex_profiler_test.conf: Commiting changes to + regex_profiler_test.conf before moving it to contrib + +2012-11-05 13:56 wachs + + * [r24738] src/transport/test_transport_api_unreliability.c: + hunting + +2012-11-05 13:52 wachs + + * [r24736] src/transport/test_transport_api_unreliability.c: bug + hunting + +2012-11-05 13:29 szengel + + * [r24731] src/mesh/Makefile.am, + src/mesh/gnunet-service-regexprofiler.c, + src/mesh/regexprofiler.conf: Adding new regexprofiler service + that is used in conjunction with the + gnunet-regex-profiler to announce regexes from a policy file + +2012-11-05 12:56 harsha + + * [r24723] src/stream/perf_stream_api.c: fix to keep testing + running + +2012-11-05 12:17 wachs + + * [r24718] src/gns/gnunet-service-gns_resolver.c: fix memory leak + +2012-11-05 09:39 wachs + + * [r24705] src/transport/plugin_transport_http_server.c: coverity + bugs 10360 && 10361 + +2012-11-05 09:06 wachs + + * [r24699] contrib/Makefile.am: make check fails in root dir + +2012-11-04 23:57 LRN + + * [r24697] src/hello/test_hello.c: Typo + +2012-11-04 21:49 szengel + + * [r24695] src/mesh/gnunet-regex-profiler.c: fix + +2012-11-04 18:35 szengel + + * [r24692] src/mesh/gnunet-regex-profiler.c: regex profiler fixes + +2012-11-04 17:48 szengel + + * [r24691] src/mesh/gnunet-regex-profiler.c: regex profiler cleanup + +2012-11-03 22:47 LRN + + * [r24687] src/dht/Makefile.am: link testbed after dhttest (depends + on testbed) + +2012-11-03 19:10 LRN + + * [r24685] src/dht/Makefile.am: twopeer test depends on dhttest + library + +2012-11-02 19:35 szengel + + * [r24684] src/mesh/gnunet-regex-profiler.c: regex profiler fixes + +2012-11-02 18:22 LRN + + * [r24683] src/dht/Makefile.am: twopeer test depends on testbed + +2012-11-02 16:41 szengel + + * [r24682] src/exit/Makefile.am, src/exit/gnunet-daemon-exit.c, + src/include/gnunet_applications.h, src/vpn/Makefile.am, + src/vpn/gnunet-service-vpn.c: Using regex for exit/vpn + +2012-11-02 16:01 harsha + + * [r24681] src: ignore gtags files + +2012-11-02 15:54 harsha + + * [r24680] src/testing/testing.c: reverting back to fix failing + testbed tests due to late startup of peers + +2012-11-02 15:52 harsha + + * [r24679] src/testbed/gnunet-service-testbed.c: fix memleak + +2012-11-02 15:14 harsha + + * [r24678] src/testbed/test_testbed_api_3peers_3controllers.c: fix + crashing test + +2012-11-02 09:28 harsha + + * [r24672] src/testbed/test_testbed_api_testbed_run.c: fix test on + W32 + +2012-11-01 23:03 LRN + + * [r24671] src/testbed/test_testbed_api_testbed_run.c, + src/testing_old/test_testing_large_topology.c: Use strrchr() + instead of legacy rindex() + +2012-11-01 22:03 harsha + + * [r24669] src/testing/test_testing_peerstartup.c, + src/testing/test_testing_portreservation.c: fix + +2012-11-01 22:02 harsha + + * [r24668] src/testing/test_testing_peerstartup.c, + src/testing/test_testing_portreservation.c: fix crashing checks + +2012-11-01 21:30 harsha + + * [r24667] src/testbed/testbed_api_testbed.c: fix + +2012-11-01 21:12 harsha + + * [r24666] src/testbed, src/testbed/Makefile.am, + src/testbed/test_testbed_api.conf, + src/testbed/test_testbed_api_testbed_run.c, + src/testbed/test_testbed_api_testbed_run_topologyclique.conf, + src/testbed/test_testbed_api_testbed_run_topologyline.conf, + src/testbed/test_testbed_api_testbed_run_topologyrandom.conf, + src/testbed/testbed_api_testbed.c: topology option support for + GNUNET_TESTBED_run() via configuration + +2012-11-01 16:45 LRN + + * [r24663] src/util/network.c: W32: Remove unnecessary 0 and -1 + checks + +2012-11-01 16:43 LRN + + * [r24662] src/util/network.c: W32: optimize + GNUNET_NETWORK_fdset_add + +2012-11-01 16:43 LRN + + * [r24661] src/util/configuration.c: More configuration debugging + +2012-11-01 16:42 LRN + + * [r24660] src/util/configuration.c: Debug for dollar-expansion + +2012-11-01 16:01 harsha + + * [r24656] src/testing/testing.c: fix + +2012-11-01 11:55 harsha + + * [r24655] src/testing/testing.c: fixing testing failures on pi + +2012-11-01 11:44 harsha + + * [r24654] src/testbed/gnunet-service-testbed.c, + src/testbed/test_testbed_api.conf: fix for port-conflicts while + starting multiple controllers on same host + +2012-10-31 21:13 harsha + + * [r24641] src/testing/testing.c: check all available addresses + +2012-10-31 20:36 harsha + + * [r24640] src/testbed/test_testbed_api_3peers_3controllers.c, + src/testbed/test_testbed_api_controllerlink.c: fixes failing + tests + +2012-10-31 15:36 harsha + + * [r24639] src/include/gnunet_protocols.h, + src/testbed/gnunet-service-testbed.c, src/testbed/testbed.h, + src/testbed/testbed_api.c: dead code + +2012-10-31 15:10 wachs + + * [r24637] src/transport/plugin_transport_http_server.c: fix + +2012-10-31 14:24 wachs + + * [r24636] src/transport/plugin_transport_http_server.c: error + +2012-10-31 13:52 wachs + + * [r24635] src/ats-test: unused code + +2012-10-31 12:21 harsha + + * [r24632] src/testbed/gnunet-helper-testbed.c: fix crashes when + aborting testing drivers + +2012-10-31 10:22 wachs + + * [r24630] src/ats-tool/gnunet-ats.c: docu + +2012-10-31 10:13 harsha + + * [r24629] src/include/gnunet_stream_lib.h, + src/stream/stream_api.c: fixes + +2012-10-31 10:12 wachs + + * [r24628] doc/man/Makefile.am, doc/man/gnunet-ats.1: man + +2012-10-31 09:15 harsha + + * [r24627] src/include/gnunet_testbed_service.h, + src/mesh/gnunet-regex-profiler.c, + src/testbed/gnunet-testbed-profiler.c, + src/testbed/test_testbed_api_3peers_3controllers.c, + src/testbed/test_testbed_api_controllerlink.c, + src/testbed/testbed.conf.in, src/testbed/testbed_api.c, + src/testbed/testbed_api.h, src/testbed/testbed_api_hosts.c: + locate helpers in libexec + +2012-10-30 23:03 harsha + + * [r24626] src/util/helper.c: for starting up non gnunet helpers + (SSH for example) + +2012-10-30 22:26 szengel + + * [r24625] src/mesh/gnunet-regex-profiler.c, + src/mesh/gnunet-service-mesh.c, + src/mesh/regex_profiler_test.conf: mesh regex profiler + +2012-10-30 22:12 LRN + + * [r24624] src/datacache/plugin_datacache_sqlite.c, + src/datastore/plugin_datastore_sqlite.c, src/fs/fs_getopt.c, + src/namestore/plugin_namestore_sqlite.c: Fix ENABLE_NLS usage + + ENABLE_NLS is for gettext only, it's not an indicator of + nl_langinfo + availability. + Use unistring instead of nl_langinfo, since unistring is always + there. + GNUnet supports UTF-8 now (or should support), so most + conversions are + unnecessary anyway. + +2012-10-30 22:11 LRN + + * [r24623] src/util/strings.c, src/util/test_strings.c: Restore + warnings, fix test compilation + +2012-10-30 21:23 LRN + + * [r24622] src/util/strings.c: Just use unistring + +2012-10-30 21:22 LRN + + * [r24621] src/util/strings.c: Missing include + +2012-10-30 21:08 LRN + + * [r24619] src/util/os_installation.c: W32: Fix + get_path_from_module_filename() + +2012-10-30 21:08 LRN + + * [r24618] src/util/strings.c: Allow using libunistring for string + conversion + +2012-10-29 16:41 szengel + + * [r24597] src/mesh/gnunet-regex-profiler.c: sequential mesh + service connects and regex announcing in regex profiler + +2012-10-29 16:14 grothoff + + * [r24593] src/arm/Makefile.am, src/arm/do_start_process.c, + src/ats-tool, src/ats/Makefile.am, src/chat/Makefile.am, + src/chat/test_chat.c, src/chat/test_chat_private.c, + src/core/Makefile.am, src/core/test_core_api.c, + src/core/test_core_api_reliability.c, + src/core/test_core_api_start_only.c, + src/core/test_core_quota_compliance.c, src/datastore/Makefile.am, + src/dht/Makefile.am, src/dns/Makefile.am, src/dv/Makefile.am, + src/exit/Makefile.am, src/fs/Makefile.am, src/gns/Makefile.am, + src/hostlist/Makefile.am, + src/hostlist/test_gnunet_daemon_hostlist.c, + src/hostlist/test_gnunet_daemon_hostlist_learning.c, + src/hostlist/test_gnunet_daemon_hostlist_reconnect.c, + src/include/gnunet_os_lib.h, src/lockmanager/Makefile.am, + src/mesh/Makefile.am, src/namestore/Makefile.am, + src/nat/Makefile.am, src/nse/Makefile.am, + src/peerinfo/Makefile.am, src/pt/Makefile.am, src/regex, + src/statistics/Makefile.am, src/statistics/test_statistics_api.c, + src/statistics/test_statistics_api_loop.c, + src/statistics/test_statistics_api_watch.c, + src/statistics/test_statistics_api_watch_zero_value.c, + src/template/Makefile.am, src/testbed/Makefile.am, + src/testing/testing.c, src/topology/Makefile.am, + src/transport/Makefile.am, src/util, src/util/Makefile.am, + src/util/helper.c, src/util/os_installation.c, + src/util/test_resolver_api.c, src/vpn/Makefile.am: installing all + service, daemon and helper binaries to lib/gnunet/libexec/; + updating code to run binaries from new location, which is no + longer in PATH + +2012-10-29 15:43 harsha + + * [r24592] src/testing/testing.c: starting testing processes with a + low priority to not overwhelm testing hosts + +2012-10-28 22:35 szengel + + * [r24583] src/mesh/gnunet-regex-profiler.c: batch regex announcing + in profiler + +2012-10-26 18:23 szengel + + * [r24571] src/mesh/mesh_api.c: passing mesage header instead of + message + +2012-10-26 16:10 szengel + + * [r24570] src/regex/gnunet-regex-simulation-profiler.c: using + prepared statements for regex simulation profiler + +2012-10-26 15:59 szengel + + * [r24569] src/mesh/gnunet-regex-profiler.c: added max path + compression parameter to regex profiler + +2012-10-26 15:10 wachs + + * [r24566] src/statistics/gnunet-statistics.c: gnunet-statistics + can retrieve stats from remote hosts without config + +2012-10-26 15:08 wachs + + * [r24565] src/util/strings.c: memory leak: is const + +2012-10-26 12:58 harsha + + * [r24562] src/fs/fs_test_lib.c, + src/gns/test_gns_dht_three_peers.c, + src/include/gnunet_testbed_service.h, + src/mesh/gnunet-regex-profiler.c, + src/testbed/gnunet-service-testbed.c, + src/testbed/gnunet-testbed-profiler.c, + src/testbed/testbed_api_testbed.c, + src/testbed/testbed_api_topology.c: removed + GNUNET_TESTBED_operation_cancel + +2012-10-26 12:22 wachs + + * [r24561] src/transport/plugin_transport_unix.c: simplify retry + mechanism + +2012-10-26 11:38 wachs + + * [r24560] src/transport/plugin_transport_unix.c: change + +2012-10-26 08:28 wachs + + * [r24559] src/transport/gnunet-service-transport_neighbours.c, + src/transport/plugin_transport_udp.c: more changes + +2012-10-26 08:17 wachs + + * [r24558] src/transport/gnunet-service-transport_neighbours.c: bug + hunting + +2012-10-26 08:07 wachs + + * [r24557] src/ats/gnunet-service-ats_performance.c: fix unused + variable + +2012-10-26 07:02 wachs + + * [r24556] src/transport/plugin_transport_wlan.c: use calculated + delays /w wlan + +2012-10-25 19:37 LRN + + * [r24554] src/ats/gnunet-service-ats_addresses.c: Fix naming, HEAD + fails to compile here + +2012-10-25 19:37 LRN + + * [r24553] src/util/network.c: bratao: W32: Optimize ..._select() + implementation + + Begin with a quick sequential check of sockets and pipes, and + bail out if something is selected already, or if timeout is zero, + avoiding overhead of setting up all the stuff necessary to sleep + until + either a socket or a pipe wakes us up. + +2012-10-25 15:13 wachs + + * [r24552] src/transport/plugin_transport_wlan.c: workaround + +2012-10-25 15:04 wachs + + * [r24551] src/ats/gnunet-service-ats_addresses.c, + src/ats/gnunet-service-ats_performance.c: doxygen + +2012-10-25 14:59 wachs + + * [r24549] src/ats-tool/gnunet-ats.c: doxygen + +2012-10-25 14:46 wachs + + * [r24545] src/ats-tool/gnunet-ats.c: monitor mode + +2012-10-25 14:21 wachs + + * [r24544] src/ats/gnunet-service-ats_addresses.h: some docu + +2012-10-25 14:21 wachs + + * [r24543] src/ats/gnunet-ats.c: move to ats-tool + +2012-10-25 14:15 wachs + + * [r24541] configure.ac, src/Makefile.am: add ats-tool to + buildsystem + +2012-10-25 14:14 wachs + + * [r24540] src/ats-tool, src/ats-tool/Makefile.am, + src/ats-tool/gnunet-ats.c: move ats-tool due to transport + dependency + +2012-10-25 13:56 wachs + + * [r24539] src/ats/Makefile.am, src/ats/gnunet-ats.c: gnunet-ats /w + address printing support + +2012-10-25 12:52 wachs + + * [r24537] src/ats/gnunet-service-ats_addresses.c: report only + active addresses used + +2012-10-25 12:33 wachs + + * [r24536] src/ats/gnunet-ats.c, + src/ats/gnunet-service-ats_addresses.c, + src/ats/gnunet-service-ats_performance.c, + src/ats/gnunet-service-ats_performance.h: gnunet-ats working and + bug 0002593 + +2012-10-25 11:57 szengel + + * [r24535] src/mesh/gnunet-regex-profiler.c, + src/mesh/regex_profiler_test.conf: regex profiler fixes + +2012-10-25 11:25 wachs + + * [r24533] src/ats/gnunet-service-ats_addresses.c, + src/ats/gnunet-service-ats_addresses.h, + src/ats/gnunet-service-ats_performance.c: changes + +2012-10-24 21:32 szengel + + * [r24523] configure.ac, src/mysql/Makefile.am: libmysqlclient + linking for /usr/lib64 (fedora 17) + +2012-10-24 20:34 harsha + + * [r24522] src/testbed/gnunet-service-testbed.c, + src/testbed/test_testbed_api_operations.c, + src/testbed/testbed_api.c, src/testbed/testbed_api_operations.c, + src/testbed/testbed_api_operations.h, + src/testbed/testbed_api_peers.c, + src/testbed/testbed_api_services.c, + src/testbed/testbed_api_topology.c, src/testbed/x64_misc.supp: + multiple operation queues for an operation + +2012-10-24 16:08 harsha + + * [r24521] src/testbed/gnunet-service-testbed.c: removed + exponential backoff while offering HELLO + +2012-10-24 16:01 harsha + + * [r24518] src/testbed/testbed_api.c, + src/testbed/testbed_api_topology.c: fixes + +2012-10-24 13:24 wachs + + * [r24512] src/transport/plugin_transport_udp.c: fix + +2012-10-24 13:22 wachs + + * [r24511] src/ats/gnunet-ats.c: basics + +2012-10-24 12:56 wachs + + * [r24509] src/transport/plugin_transport_udp.c: fix + +2012-10-24 12:29 wachs + + * [r24502] src/transport/plugin_transport_udp.c: coverity + +2012-10-24 08:56 LRN + + * [r24499] src/transport/test_plugin_transport.c: Create directory + for hostkey + +2012-10-23 17:41 szengel + + * [r24492] src/mesh/Makefile.am: fix + +2012-10-23 17:07 szengel + + * [r24489] src/mesh/Makefile.am, src/mesh/gnunet-regex-profiler.c: + added libgnunetstatistics to regex profiler dependencies + +2012-10-23 15:39 szengel + + * [r24488] src/mesh/gnunet-regex-profiler.c, + src/mesh/regex_profiler_test.conf: regex profiler saving + statistics + +2012-10-23 15:11 wachs + + * [r24487] src/transport/plugin_transport_udp.c: timeout stats + +2012-10-23 15:02 wachs + + * [r24486] src/transport/template_cfg_peer1.conf, + src/transport/template_cfg_peer2.conf: conf + +2012-10-23 14:46 szengel + + * [r24483] src/mesh/gnunet-regex-profiler.c: formatting + +2012-10-23 14:42 szengel + + * [r24482] src/mesh/gnunet-regex-profiler.c: Added statistics + service connection to regex profiler + +2012-10-23 12:37 harsha + + * [r24472] src/testbed/gnunet-testbed-profiler.c: exit during + errors too + +2012-10-23 12:31 harsha + + * [r24471] src/testbed/gnunet-service-testbed.c: fix for crashing + service while shutting down when peer create fails + +2012-10-23 10:42 harsha + + * [r24470] src/testbed/gnunet-testbed-profiler.c: trying to fix + win32 build + +2012-10-23 09:13 szengel + + * [r24469] src/mesh/gnunet-regex-profiler.c, + src/mesh/regex_profiler_test.conf: regex profiler fixes + +2012-10-22 23:07 harsha + + * [r24468] src/testbed/gnunet-testbed-profiler.c: fix + +2012-10-22 22:55 harsha + + * [r24467] src/include/gnunet_testbed_service.h: doc + +2012-10-22 22:54 harsha + + * [r24466] src/testing/testing.c: fix + +2012-10-22 22:29 harsha + + * [r24465] src/testbed/testbed_api_peers.c: fix + +2012-10-22 21:30 harsha + + * [r24464] src/testbed/gnunet-testbed-profiler.c: fixes + +2012-10-22 21:26 harsha + + * [r24463] src/testbed/gnunet-testbed-profiler.c: profiler topology + option + +2012-10-22 20:52 harsha + + * [r24462] src/testbed, src/testbed/Makefile.am, + src/testbed/test_testbed_api_topology_clique.c, + src/testbed/testbed_api_topology.c: clique topology + +2012-10-22 15:09 harsha + + * [r24459] src/testbed/gnunet-testbed-profiler.c: allow single host + deployments + +2012-10-22 14:25 harsha + + * [r24458] src/testbed/gnunet-testbed-profiler.c: fix + +2012-10-22 13:58 harsha + + * [r24456] src/testbed/testbed_api.c: fix + +2012-10-22 13:52 szengel + + * [r24455] src/mesh/gnunet-regex-profiler.c, + src/mesh/regex_profiler_test.conf: regex profiler: measuring the + time it takes to match all strings + +2012-10-22 13:46 wachs + + * [r24454] src/fragmentation/fragmentation.c: fix + +2012-10-22 12:34 harsha + + * [r24450] src/testbed/gnunet-testbed-profiler.c: less verbose + +2012-10-22 11:57 harsha + + * [r24449] contrib/testbed_cleanup.sh, + contrib/testbed_infiniband.conf: remove username part + +2012-10-22 11:56 wachs + + * [r24448] src/transport/plugin_transport_http_client.c: doxygen + errors + +2012-10-22 11:51 harsha + + * [r24447] src/testbed/gnunet-testbed-profiler.c: disable auto + retry + +2012-10-22 11:44 harsha + + * [r24446] src/include/gnunet_testbed_service.h, + src/testbed/gnunet-testbed-profiler.c, + src/testbed/test_testbed_api_topology.c, + src/testbed/testbed_api_topology.c: option for disabling auto + retry + +2012-10-21 17:36 harsha + + * [r24442] src/testbed/gnunet-service-testbed.c: simplify + +2012-10-21 17:25 harsha + + * [r24441] src/testbed/gnunet-service-testbed.c: tracking forwarded + operations + +2012-10-21 15:24 szengel + + * [r24440] src/mesh/gnunet-regex-profiler.c: regex profiler: + loading a set of search strings from a file + +2012-10-21 08:55 harsha + + * [r24439] src/testbed/gnunet-service-testbed.c: tracking forwarded + operations as part of link controllers operation + +2012-10-20 10:39 szengel + + * [r24437] src/mesh/gnunet-regex-profiler.c, + src/mesh/regex_profiler_test.conf: Updated regex profiler config + with mesh and dht default arm services + +2012-10-20 09:31 harsha + + * [r24436] src/testbed/testbed_api.c, src/testbed/testbed_api.h, + src/testbed/testbed_api_topology.c: removed duplicate definition + +2012-10-19 17:50 szengel + + * [r24434] src/mesh/gnunet-regex-profiler.c: Aborting profiler + after a timeout + +2012-10-19 16:38 szengel + + * [r24433] src/mesh/gnunet-regex-profiler.c: regex profiler fix + +2012-10-19 14:32 harsha + + * [r24429] src/testbed/gnunet-testbed-profiler.c: doxygen + +2012-10-19 14:24 szengel + + * [r24428] src/regex/regex.c: coverity + +2012-10-19 14:19 harsha + + * [r24427] src/testbed/gnunet-service-testbed.c: fix + +2012-10-19 13:56 harsha + + * [r24425] src/testbed/test_testbed_api_topology.c: reverted to + version 24399 + +2012-10-19 13:47 harsha + + * [r24424] src/testbed/gnunet-service-testbed.c, + src/testbed/test_testbed_api_topology.c, + src/testbed/testbed_api_topology.c: counting references in + overlay connect context + +2012-10-19 12:37 harsha + + * [r24422] src/testbed/gnunet-service-testbed.c: cleanup rocc + +2012-10-19 12:15 harsha + + * [r24421] src/testbed/gnunet-service-testbed.c: removed redundancy + +2012-10-19 12:01 harsha + + * [r24420] src/testbed/gnunet-service-testbed.c: remove remote + peers upon destroy + +2012-10-19 11:42 wachs + + * [r24419] src/transport/plugin_transport_udp.c: coverity + +2012-10-19 10:17 szengel + + * [r24416] src/mesh/gnunet-regex-profiler.c: mesh connections in + regex profiler + +2012-10-19 10:15 szengel + + * [r24415] src/mesh/gnunet-regex-profiler.c, + src/mesh/regex_profiler_test.conf: mesh connections in regex + profiler + +2012-10-19 08:39 harsha + + * [r24413] contrib/testbed_infiniband_results, + contrib/testbed_infiniband_results/30000_connections_90000_peers_30_poc.txt, + contrib/testbed_infiniband_results/6000_connections_10000_peers_100_poc.txt, + contrib/testbed_infiniband_results/6000_connections_10000_peers_20_poc.txt, + contrib/testbed_infiniband_results/6000_connections_10000_peers_30_poc.txt, + contrib/testbed_infiniband_results/6000_connections_20000_peers.txt, + contrib/testbed_infiniband_results/6000_connections_40000_peers.txt, + contrib/testbed_infiniband_results/6000_connections_60000_peers.txt, + contrib/testbed_infiniband_results/6000_connections_60000_peers_5_poc.txt, + contrib/testbed_infiniband_results/6000_connections_80000_peers_20_poc.txt, + contrib/testbed_infiniband_results/6000_connections_80000_peers_5_poc.txt: + testbed results + +2012-10-18 23:02 harsha + + * [r24409] src/testbed/gnunet-testbed-profiler.c: parameterized how + many failures to tolerate + +2012-10-18 18:01 szengel + + * [r24407] src/mesh/test_mesh_regex.c: doxygen + +2012-10-18 18:00 szengel + + * [r24406] src/mesh/gnunet-regex-profiler.c, + src/mesh/regex_profiler_test.conf: regex profiler + +2012-10-18 16:38 szengel + + * [r24405] src/include/gnunet_testbed_service.h, + src/testbed/testbed_api_hosts.c: Exposing + GNUNET_TESTBED_host_get_hostname + +2012-10-18 15:53 harsha + + * [r24404] src/testbed/gnunet-testbed-profiler.c: print statistics + +2012-10-18 15:12 wachs + + * [r24401] src/transport/gnunet-service-transport_validation.c, + src/transport/plugin_transport_udp.c: preliminary workaround for + 0002549 + +2012-10-18 14:52 harsha + + * [r24400] src/testbed/testbed_api.c: use controller's host when + slave host is NULL + +2012-10-18 12:51 wachs + + * [r24398] src/transport/plugin_transport_udp.c: new statistics + +2012-10-17 20:17 szengel + + * [r24383] src/regex/regex.c, src/regex/test_regex_iterate_api.c: + fix + +2012-10-17 18:16 harsha + + * [r24377] src/testbed/gnunet-testbed-profiler.c: peer destroy + state + +2012-10-17 18:11 harsha + + * [r24376] contrib/infiniband_cluster.hosts, + contrib/testbed_infiniband.conf: more cluster nodes + +2012-10-17 18:08 harsha + + * [r24375] src/testbed/gnunet-service-testbed.c: stop peer before + destroying it + +2012-10-17 17:39 szengel + + * [r24373] src/mesh/Makefile.am, src/mesh/gnunet-regex-profiler.c, + src/mesh/regex_profiler_test.conf, src/regex/Makefile.am, + src/regex/gnunet-regex-profiler.c, + src/regex/regex_profiler_test.conf: Moved regex profiler to mesh, + because of dependencies. + +2012-10-17 16:39 wachs + + * [r24371] src/transport/plugin_transport_udp.c: stat + +2012-10-17 16:33 szengel + + * [r24370] src/regex/gnunet-regex-profiler.c: doxygen, indentation + +2012-10-17 16:22 harsha + + * [r24368] src/testbed/testbed.conf.in, src/testbed/testbed_api.c, + src/testbed/testbed_api.h, src/testbed/testbed_api_peers.c: new + operation queue for limiting overlay connects + +2012-10-17 15:52 wachs + + * [r24366] src/transport/plugin_transport_udp.c: new statistic + values and fixes + +2012-10-17 15:26 harsha + + * [r24364] src/testbed/gnunet-service-testbed.c, + src/testbed/gnunet-testbed-profiler.c: fixs for crash while + adding slaves with id greater than 9 + +2012-10-17 15:16 wachs + + * [r24362] src/transport/plugin_transport_udp.c: minors + +2012-10-17 14:40 szengel + + * [r24359] src/regex/Makefile.am, + src/regex/gnunet-regex-profiler.c: doxygen + +2012-10-17 14:20 wachs + + * [r24357] src/transport/plugin_transport_udp.c: clean up and fixes + +2012-10-17 13:53 harsha + + * [r24356] src/testbed/gnunet-service-testbed.c: fixed memory leak + +2012-10-17 13:29 harsha + + * [r24354] src/testbed/gnunet-service-testbed.c, + src/testbed/gnunet-service-testbed.c.new, + src/testbed/test_testbed_api_3peers_3controllers.c: a decent way + to auto link controllers during overlay connects + +2012-10-17 13:10 wachs + + * [r24353] src/transport/plugin_transport_udp.c: improve code while + debugging + +2012-10-17 09:33 wachs + + * [r24350] src/transport/Makefile.am, + src/transport/test_plugin_hostkey, + src/transport/test_plugin_transport.c: use precomputed hostkey + for slow computers + +2012-10-17 09:22 wachs + + * [r24349] src/transport/test_plugin_transport.c: fix + +2012-10-17 09:05 wachs + + * [r24348] src/transport/test_plugin_transport.c: crash in test due + to pending callbacks + +2012-10-17 07:39 wachs + + * [r24346] src/dv/dv_api.c: overhead for dv + +2012-10-16 15:44 harsha + + * [r24345] src/testbed/gnunet-service-testbed.c.new, + src/testbed/testbed_api_hosts.c: checkpoint save + +2012-10-16 14:59 wachs + + * [r24344] src/transport/gnunet-service-transport_clients.c, + src/transport/gnunet-service-transport_neighbours.c, + src/transport/plugin_transport_udp.c, + src/transport/plugin_transport_unix.c, + src/transport/plugin_transport_wlan.c: doxygen + +2012-10-16 14:43 wachs + + * [r24343] src/transport/plugin_transport_udp.c, + src/transport/transport_api.c: changes + +2012-10-16 14:30 wachs + + * [r24342] src/transport/plugin_transport_udp.c, + src/transport/transport_api.c: stats + delay + +2012-10-16 13:25 wachs + + * [r24341] src/transport/gnunet-service-transport_clients.c, + src/transport/plugin_transport_udp.c, src/transport/transport.h, + src/transport/transport_api.c: changes + +2012-10-16 12:19 wachs + + * [r24340] src/transport/gnunet-service-transport_neighbours.c: + debugging + +2012-10-16 12:11 wachs + + * [r24339] src/include/gnunet_transport_plugin.h: header + +2012-10-16 11:43 wachs + + * [r24338] src/transport/gnunet-service-transport_neighbours.c: rm + error msg + +2012-10-16 11:42 wachs + + * [r24337] src/transport/gnunet-service-transport_neighbours.c, + src/transport/plugin_transport_unix.c: fix for overhead + measurement in unix,also fixes assertion in neighbours 1152 + +2012-10-16 11:20 wachs + + * [r24336] src/transport/gnunet-service-transport_clients.c, + src/transport/gnunet-service-transport_neighbours.c, + src/transport/gnunet-service-transport_neighbours.h, + src/transport/plugin_transport_http_client.c, + src/transport/plugin_transport_http_server.c, + src/transport/plugin_transport_tcp.c, + src/transport/plugin_transport_udp.c, + src/transport/plugin_transport_unix.c, + src/transport/plugin_transport_wlan.c: overhead reporting + +2012-10-16 08:20 wachs + + * [r24335] src/transport/plugin_transport_udp.c, + src/transport/plugin_transport_udp.h: changes + +2012-10-16 08:08 wachs + + * [r24334] src/transport/plugin_transport_udp.c: documentation and + preparation + +2012-10-15 21:30 harsha + + * [r24331] src/testbed/gnunet-service-testbed.c: host registration + queues in slave handles + +2012-10-15 20:24 harsha + + * [r24329] src/testbed/gnunet-service-testbed.c: peer to use slave + handle + +2012-10-15 19:48 harsha + + * [r24328] src/testbed/test_testbed_api_topology.c: reducing peers + to avoid timeouts + +2012-10-15 17:22 szengel + + * [r24325] src/regex/gnunet-regex-profiler.c, + src/regex/test_regex_big.c, src/regex/test_regex_big.conf: + replacing test_regex_big with gnunet-regex-profiler + +2012-10-15 17:06 szengel + + * [r24324] src/include/gnunet_regex_lib.h: fix + +2012-10-15 17:06 szengel + + * [r24323] src/regex/Makefile.am, + src/regex/gnunet-regex-profiler.c, src/regex/regex.c, + src/regex/regex_internal.h, src/regex/regex_profiler_test.conf, + src/regex/test_regex_graph_api.c, + src/regex/test_regex_iptoregex.c, + src/regex/test_regex_iterate_api.c: renamed test_regex_big / + fixes + +2012-10-15 16:17 harsha + + * [r24322] src/testbed/gnunet-service-testbed.c, + src/testbed/gnunet-testbed-profiler.c, src/testbed/testbed.h, + src/testbed/testbed_api.c, src/testbed/testbed_api_topology.c: + logging and fixes + +2012-10-15 10:51 harsha + + * [r24321] src/testbed/gnunet-service-testbed.c: timeouts during + forwarded overlay connects + +2012-10-14 16:48 harsha + + * [r24314] src/testbed/gnunet-testbed-profiler.c: output status for + connects + +2012-10-14 13:56 harsha + + * [r24312] src/testbed/gnunet-testbed-profiler.c, + src/testbed/testbed_api_peers.c, + src/testbed/testbed_api_topology.c: peer linking + +2012-10-14 13:23 harsha + + * [r24310] src/testbed/test_testbed_api_topology.c, + src/testbed/testbed_api_topology.c: Random graph topology + +2012-10-14 12:50 harsha + + * [r24308] src/testbed/gnunet-testbed-profiler.c: corrected + profiling time measurement for peer create + +2012-10-14 12:36 harsha + + * [r24307] src/testbed/gnunet-testbed-profiler.c: peer start + +2012-10-14 12:21 harsha + + * [r24306] src/include/gnunet_testbed_service.h, + src/nse/gnunet-nse-profiler.c, src/regex/test_regex_big.c, + src/testbed/gnunet-testbed-profiler.c, + src/testbed/test_testbed_api.c, + src/testbed/test_testbed_api_2peers_1controller.c, + src/testbed/test_testbed_api_3peers_3controllers.c, + src/testbed/test_testbed_api_controllerlink.c, + src/testbed/testbed_api_peers.c, + src/testbed/testbed_api_testbed.c: operation closure in peer + start + +2012-10-14 10:57 harsha + + * [r24305] src/testbed/gnunet-testbed-profiler.c, + src/testbed/testbed_api.c, src/testbed/testbed_api.h: doxygen + +2012-10-14 10:49 harsha + + * [r24304] src/testbed/gnunet-testbed-profiler.c: towards peer + create + +2012-10-14 09:30 harsha + + * [r24303] src/testbed/gnunet-service-testbed.c, + src/testbed/gnunet-testbed-profiler.c: fixes + +2012-10-14 09:19 harsha + + * [r24302] src/testbed/gnunet-testbed-profiler.c: removed peer + destroy. May leak memory, but anyway we need that till the end + +2012-10-14 09:18 harsha + + * [r24301] src/testbed/gnunet-testbed-profiler.c: fix + +2012-10-14 08:45 harsha + + * [r24300] src/testbed/gnunet-testbed-profiler.c: peer create + +2012-10-12 16:14 harsha + + * [r24297] src/testbed/gnunet-service-testbed.c, + src/testbed/gnunet-testbed-profiler.c: fixes + +2012-10-12 15:44 harsha + + * [r24296] src/testbed/gnunet-testbed-profiler.c: slave startup + +2012-10-12 14:58 harsha + + * [r24293] src/testbed/gnunet-service-testbed.c, + src/testbed/gnunet-testbed-profiler.c, src/testbed/testbed_api.c: + fixes + +2012-10-12 14:01 harsha + + * [r24292] contrib/infiniband_cluster.hosts: correct ips + +2012-10-12 13:40 harsha + + * [r24291] src/testbed/gnunet-testbed-profiler.c, + src/testbed/testbed_api.c: host registrations in profiler + +2012-10-12 13:39 harsha + + * [r24290] contrib/infiniband_cluster.hosts: added infiniband hosts + +2012-10-12 12:13 harsha + + * [r24289] src/testbed/gnunet-service-testbed.c, + src/testbed/test_testbed_api_3peers_3controllers.c: send self + config during overlay connect + +2012-10-12 10:31 harsha + + * [r24288] src/testbed/testbed_api_hosts.c: no auto allocation + during scanf + +2012-10-12 10:17 harsha + + * [r24287] src/testbed/gnunet-testbed-profiler.c: fix w32 build + +2012-10-12 10:11 harsha + + * [r24286] src/testbed/testbed_api_testbed.c: tolerate stopped + peers while shutting down testbed_run + +2012-10-12 09:21 harsha + + * [r24285] src/testbed/test_testbed_api_hosts.c, + src/testbed/testbed_api_hosts.c: fixing scanf failures + +2012-10-12 09:02 harsha + + * [r24284] src/include/gnunet_testbed_service.h, + src/testbed/gnunet-testbed-profiler.c, + src/testbed/test_testbed_api_hosts.c, + src/testbed/testbed_api_hosts.c: host file support for testbed + profiler + +2012-10-12 07:47 harsha + + * [r24283] src/testbed/testbed_api_hosts.c: fixes + +2012-10-11 21:23 harsha + + * [r24280] src/include/gnunet_testbed_service.h, + src/testbed/sample_hosts.txt, + src/testbed/test_testbed_api_hosts.c, + src/testbed/testbed_api_hosts.c: fixes for invalid reads + +2012-10-11 20:45 harsha + + * [r24279] src/testbed/sample_hosts.txt, + src/testbed/test_testbed_api_hosts.c, + src/testbed/testbed_api_hosts.c: host loading from file + +2012-10-11 18:54 harsha + + * [r24278] src/testing/testing.c: using header-defined + hostkeyfilesize + +2012-10-11 15:43 harsha + + * [r24270] src/testbed, src/testbed/Makefile.am, + src/testbed/gnunet-testbed-profiler.c: testbed profiler + +2012-10-11 14:45 harsha + + * [r24269] src/testbed/testbed_api.c: disabling hostkey checking + for localhost + +2012-10-11 13:34 harsha + + * [r24264] src/testbed/gnunet-service-testbed.c, + src/testbed/test_testbed_api_3peers_3controllers.c, + src/testbed/testbed_api.c, src/testbed/testbed_api.h: working + overlay connect with implicit suboperations + +2012-10-11 11:03 harsha + + * [r24262] src/testbed/gnunet-service-testbed.c: overlay connect + suboperations + +2012-10-10 19:33 harsha + + * [r24258] src/testbed/gnunet-service-testbed.c, + src/testbed/testbed_api.c, src/testbed/testbed_api.h: controller + linking with host ids + +2012-10-10 15:37 harsha + + * [r24253] src/testbed/gnunet-service-testbed.c, + src/testbed/testbed_api.c, src/testbed/testbed_api.h: checkpoint + save + +2012-10-10 10:59 harsha + + * [r24252] src/testbed/testbed_api.c, src/testbed/testbed_api.h, + src/testbed/testbed_api_peers.c, + src/testbed/testbed_api_services.c: operation id generation from + controller host id and internal counter + +2012-10-10 09:38 harsha + + * [r24250] src/testbed/testbed_api.c, + src/testbed/testbed_api_peers.c, src/testbed/testbed_api_peers.h: + towards handling suboperations during overlay connect + +2012-10-09 17:44 harsha + + * [r24236] src/include/gnunet_protocols.h: fixing compile + +2012-10-09 14:03 harsha + + * [r24234] src/testbed/gnunet-service-testbed.c, + src/testbed/gnunet-service-testbed.c.new, src/testbed/testbed.h, + src/testbed/testbed_api.c, src/testbed/testbed_api.c.new: towards + on-demand configuration retrival for remote controllers during + overlay connect operations + +2012-10-08 22:41 LRN + + * [r24231] src/util/network.c: Implement non-inheritable sockets + for W32 + +2012-10-08 17:18 szengel + + * [r24227] src/regex/test_regex_big.c: mesh service connect + skeleton + +2012-10-08 14:50 harsha + + * [r24226] src/testbed/gnunet-service-testbed.c, + src/testbed/test_testbed_api_3peers_3controllers.c, + src/testbed/test_testbed_api_controllerlink.c: added get peer + config forwarding + +2012-10-08 13:28 harsha + + * [r24224] src/testbed/gnunet-service-testbed.c: forwarding overlay + request connect + +2012-10-07 13:41 szengel + + * [r24214] src/regex/regex_graph.c: fix + +2012-10-06 14:14 harsha + + * [r24206] src/testbed/test_testbed_api_topology.c: fail nicely + +2012-10-06 14:02 harsha + + * [r24204] src/testbed/gnunet-service-testbed.c: exponential delay + in offering HELLOs + +2012-10-05 16:41 szengel + + * [r24198] src/regex/test_regex_big.c, + src/regex/test_regex_big.conf: simple overlay connection working + +2012-10-05 14:45 harsha + + * [r24197] src/regex/test_regex_big.c, + src/regex/test_regex_big.conf: working test on inifiniband + cluster + +2012-10-05 14:12 harsha + + * [r24196] src/include/gnunet_testing_lib-new.h, + src/testbed/gnunet-helper-testbed.c, + src/testbed/gnunet-service-testbed.c, + src/testbed/test_gnunet_helper_testbed.c, + src/testbed/testbed_api.c, src/testbed/testbed_api.h, + src/testbed/testbed_helper.h, src/testing/gnunet-testing.c, + src/testing/test_testing_peerstartup.c, + src/testing/test_testing_portreservation.c, + src/testing/testing.c, src/transport/transport-testing.c: testing + now includes valid hostname rewriting + +2012-10-05 11:54 harsha + + * [r24192] src/util/gnunet-rsa.c: generate keys to use 2048 bit rsa + +2012-10-05 10:08 szengel + + * [r24189] src/regex/test_regex_big.c, + src/regex/test_regex_big.conf: regex testbed testcase + +2012-10-04 14:02 harsha + + * [r24184] src/include/gnunet_testbed_service.h, + src/testbed/test_testbed_api_3peers_3controllers.c, + src/testbed/test_testbed_api_controllerlink.c, + src/testbed/testbed_api.c: added operation closure to + GNUNET_TESTBED_controller_link() + +2012-10-04 13:54 harsha + + * [r24183] src/stream/stream_api.c: removed fixme + +2012-10-04 12:55 wachs + + * [r24181] src/transport/gnunet-service-transport_neighbours.c: + undo + +2012-10-04 12:52 wachs + + * [r24180] src/transport/gnunet-service-transport_clients.c, + src/transport/gnunet-service-transport_clients.h: not required + +2012-10-04 12:47 wachs + + * [r24179] src/transport/gnunet-service-transport_clients.c, + src/transport/gnunet-service-transport_clients.h, + src/transport/gnunet-service-transport_neighbours.c, + src/transport/plugin_transport_http_server.c: fix type issue + +2012-10-04 12:28 harsha + + * [r24178] src/testbed/gnunet-service-testbed.c, + src/testbed/test_testbed_api_3peers_3controllers.c, + src/testbed/test_testbed_api_3peers_3controllers.c.new, + src/testbed/testbed_api.c: test case for overlay connect via + lateral links + +2012-10-04 09:11 harsha + + * [r24171] src/include/gnunet_stream_lib.h, + src/stream/stream_api.c: doc + +2012-10-04 08:53 harsha + + * [r24170] src/stream/stream_api.c: removed session id + +2012-10-04 08:49 harsha + + * [r24169] src/stream/stream_api.c: moved read_io task and its + corresponding timeout task to read handle + +2012-10-02 14:54 harsha + + * [r24162] src/testbed/gnunet-service-testbed.c, + src/testbed/test_testbed_api_controllerlink.c, + src/testbed/testbed_api.c: test case for lateral connections + between controllers + +2012-10-02 12:16 harsha + + * [r24161] src/stream/perf_stream_api.c, src/stream/stream_api.c: + fixing #2574 + +2012-10-02 09:33 harsha + + * [r24160] src/testbed/gnunet-service-testbed.c: allow lateral + connections from other controllers + +2012-10-02 08:54 harsha + + * [r24159] src/testbed/gnunet-service-testbed.c: slave get config + service implementation + +2012-10-02 08:05 harsha + + * [r24158] src/include/gnunet_testbed_service.h, + src/testbed/gnunet-service-testbed.c, src/testbed/testbed_api.c: + clean handling of slave + +2012-10-01 15:04 harsha + + * [r24157] src/testbed/testbed_api.c, src/testbed/testbed_api.h, + src/testbed/testbed_api_services.c: rename to extract_config_() + +2012-10-01 14:59 harsha + + * [r24156] src/include/gnunet_protocols.h, + src/include/gnunet_testbed_service.h, src/testbed/testbed.h, + src/testbed/testbed_api.c, src/testbed/testbed_api.h, + src/testbed/testbed_api_services.c: slave get config client part + +2012-10-01 11:50 harsha + + * [r24155] src/testbed/test_testbed_api_2peers_1controller.c: + remove duplicate specifier + +2012-10-01 10:15 harsha + + * [r24154] src/gns/gnunet-gns-proxy.c: fixes #2573 + +2012-09-30 21:32 harsha + + * [r24153] src/testbed/test_testbed_api_3peers_3controllers.c.new: + checkpoint save + +2012-09-30 21:32 harsha + + * [r24152] src/include/gnunet_testbed_service.h, + src/testbed/testbed_api.c: get slave config + +2012-09-30 21:29 harsha + + * [r24150] src/include/gnunet_stream_lib.h: doc + +2012-09-30 21:12 harsha + + * [r24149] src/stream/stream_api.c: fixing #2571 + +2012-09-30 16:25 LRN + + * [r24147] src/lockmanager/gnunet-service-lockmanager.c: Fix + 0-terminator test in lockmanager + +2012-09-30 15:20 harsha + + * [r24146] src/testbed, src/testbed/test_testbed_api.conf: + disabling VPN to remove verbose warnings for VPN + +2012-09-30 15:11 harsha + + * [r24145] src/stream/perf_stream_api.c, + src/stream/test_stream_2peers.c, + src/stream/test_stream_2peers_halfclose.c, + src/stream/test_stream_big.c, src/stream/test_stream_local.c, + src/stream/test_stream_sequence_wraparound.c: more fixes for + #2570 + +2012-09-30 14:26 harsha + + * [r24144] src/lockmanager/test_lockmanager_api.c, + src/lockmanager/test_lockmanager_api_acquireretry.c, + src/lockmanager/test_lockmanager_api_lockrelease.c, + src/lockmanager/test_lockmanager_api_servercrash.c: removed + duplicate specifiers + +2012-09-30 14:23 harsha + + * [r24143] src/testbed/test_gnunet_helper_testbed.c, + src/testbed/test_testbed_api.c, + src/testbed/test_testbed_api_2peers_1controller.c, + src/testbed/test_testbed_api_controllerlink.c, + src/testbed/test_testbed_api_test.c, + src/testbed/test_testbed_api_testbed_run.c, + src/testbed/test_testbed_api_topology.c: removing duplicate + specifiers + +2012-09-30 14:02 harsha + + * [r24142] src/stream/test_stream_2peers_halfclose.c, + src/stream/test_stream_big.c, src/stream/test_stream_local.c, + src/stream/test_stream_sequence_wraparound.c: fixes for #2570 + +2012-09-30 12:34 harsha + + * [r24141] src/stream/test_stream_2peers.c: clean exit while + aborting + +2012-09-30 12:04 LRN + + * [r24140] src/testbed/test_testbed_api_3peers_3controllers.c: Try + to fix W32 builds + +2012-09-30 08:25 harsha + + * [r24138] src/testbed/Makefile.am, + src/testbed/test_testbed_api_2peers_2controllers.c, + src/testbed/test_testbed_api_3peers_3controllers.c: rename + +2012-09-30 02:05 LRN + + * [r24137] src/testing_old/testing.c: Short timeout for starting + local services + +2012-09-29 20:49 harsha + + * [r24132] src/testbed/test_testbed_api_2peers_2controllers.c: + removed getaddrinfo + +2012-09-29 19:36 LRN + + * [r24131] src/gns/gnunet-service-gns.c: Missing declarations + +2012-09-29 18:34 harsha + + * [r24129] src/testbed/test_testbed_api_2peers_2controllers.c: + towards starting 3 controllers on a single machine + +2012-09-29 06:44 harsha + + * [r24125] src/testbed/gnunet-service-testbed.c: fixes #2568 + +2012-09-29 01:29 LRN + + * [r24124] src/transport/transport-testing.c: Fix a typo + +2012-09-28 12:36 bartpolot + + * [r24098] src/include/gnunet_getopt_lib.h, src/util/getopt.c, + src/util/getopt_helpers.c, src/util/service.c, + src/util/test_getopt.c: Passing -v or -h options to a command no + longer returns error code + +2012-09-28 10:10 harsha + + * [r24089] src/testbed: svn ignore + +2012-09-28 10:06 harsha + + * [r24086] src/testbed/Makefile.am, + src/testbed/test_testbed_api_topology.c, + src/testbed/testbed_api.c, src/testbed/testbed_api_topology.c: + topology test case + +2012-09-28 09:48 wachs + + * [r24080] src/transport/plugin_transport_http_client_old.c, + src/transport/plugin_transport_http_server_old.c: rm old code + +2012-09-28 09:36 harsha + + * [r24076] src/testbed/testbed_api_topology.c: implemented generic + topology overlay connections + +2012-09-27 22:55 LRN + + * [r24065] src/util/Makefile.am, src/util/win.c, src/util/win.cc: + W32-specific platform stuff is now pure C + +2012-09-27 19:40 grothoff + + * [r24063] contrib/pogen.sh, po/POTFILES.in, po/es.po, po/sv.po, + po/vi.po, po/zh_CN.po, src/util/helper.c: improving PO set + +2012-09-27 19:01 grothoff + + * [r24060] contrib/pogen.sh, src/arm/arm_api.c, + src/arm/gnunet-arm.c, src/arm/gnunet-service-arm.c, + src/chat/chat.c, src/datastore/plugin_datastore_sqlite.c, + src/dv/test_transport_api_dv.c, src/fs/fs_namespace.c, + src/fs/gnunet-service-fs_indexing.c, + src/fs/gnunet-service-fs_pr.c, src/fs/gnunet-service-fs_push.c, + src/gns/gnunet-gns-fcfsd.c, src/include/gnunet_common.h, + src/namestore/gnunet-namestore.c, + src/namestore/plugin_namestore_sqlite.c, + src/topology/gnunet-daemon-topology.c, + src/transport/gnunet-service-transport_blacklist.c, + src/transport/plugin_transport_tcp.c, + src/transport/plugin_transport_wlan.c, src/util/common_logging.c, + src/util/gnunet-config.c: reducing error messages about missing + configuration options by introducing new helper functions to + print them uniformly + +2012-09-27 14:19 szengel + + * [r24059] src/regex/test_regex_eval_api.c: fix + +2012-09-27 14:11 szengel + + * [r24058] src/regex/test_regex_eval_api.c, + src/regex/test_regex_graph_api.c, + src/regex/test_regex_iptoregex.c, + src/regex/test_regex_iterate_api.c, + src/regex/test_regex_proofs.c: tests + +2012-09-27 13:18 szengel + + * [r24054] src/include/gnunet_regex_lib.h, src/regex/Makefile.am, + src/regex/regex.c, src/regex/test_regex_iptoregex.c: iptoregex + test + +2012-09-27 09:19 wachs + + * [r24034] src/transport/plugin_transport_udp.c: new statistics + value to measure payload + +2012-09-26 21:22 szengel + + * [r24025] src/regex/regex.c: ip/prefix to regex + +2012-09-26 20:16 grothoff + + * [r24024] configure.ac, src/util/crypto_random.c: releaxing + libgcrypt version check, fixing Debian #684997 + +2012-09-26 14:46 szengel + + * [r24019] src/regex/regex.c, src/regex/test_regex_iterate_api.c: + fixes + +2012-09-26 13:55 wachs + + * [r24018] src/transport/plugin_transport_unix.c: UNIX stats + +2012-09-26 13:51 wachs + + * [r24017] src/transport/plugin_transport_wlan.c: WLAN stats + +2012-09-26 13:39 harsha + + * [r24016] src/testbed/testbed.conf.in, src/testbed/testbed_api.c, + src/testbed/testbed_api.h, src/testbed/testbed_api_topology.c: + towards generic topology creation + +2012-09-26 13:29 harsha + + * [r24014] src/include/gnunet_testbed_service.h: doc + +2012-09-26 08:55 wachs + + * [r24006] src/transport/plugin_transport_http_client.c: changing + type + +2012-09-25 18:10 grothoff + + * [r24003] doc/man/gnunet-rsa.1, src/util/gnunet-rsa.c: turn + gnunet-rsa into key generation tool + +2012-09-25 15:32 harsha + + * [r24002] src/testbed/gnunet-service-testbed.c: fixes + +2012-09-25 13:12 harsha + + * [r23991] src/testbed/gnunet-service-testbed.c: overlay connect + using lateral connections + +2012-09-25 12:09 harsha + + * [r23990] src/testbed/gnunet-service-testbed.c, + src/testbed/testbed.h, src/testbed/testbed_api_peers.c: added + peer2_host field in overlay connect message + +2012-09-25 11:44 harsha + + * [r23989] src/testbed/gnunet-service-testbed.c: overlay connect + forwarding when peer1 is not local + +2012-09-24 19:11 szengel + + * [r23982] src/regex/regex.c, src/regex/test_regex_iterate_api.c: + regex: iteration improvements/fixes + +2012-09-24 12:49 wachs + + * [r23979] src/gns/gns_api.c, src/gns/gnunet-gns.c, + src/transport/transport-testing.c: coverity bugs + +2012-09-24 12:39 wachs + + * [r23978] src/gns/gnunet-service-gns_resolver.c, + src/util/os_priority.c, src/util/test_os_start_process.c: + coverity bugs + +2012-09-24 12:25 wachs + + * [r23977] src/gns/gns_api.c, + src/gns/gnunet-service-gns_resolver.h: dozygen + +2012-09-24 10:07 wachs + + * [r23974] src/transport/plugin_transport_http_client.c: hunting + bugs + +2012-09-24 10:05 wachs + + * [r23973] src/transport/plugin_transport_http_client.c: hunting + bugs + +2012-09-24 09:53 wachs + + * [r23972] src/transport/plugin_transport_http_client.c: changes + +2012-09-24 08:31 LRN + + * [r23968] src/gns/Makefile.am: Add ldflags to gnunetgns_common + +2012-09-24 07:34 LRN + + * [r23967] configure.ac: Use native srcdir for #includes + +2012-09-24 05:18 LRN + + * [r23966] po/POTFILES.in: Remove non-existing files from POTFILES + +2012-09-23 16:56 szengel + + * [r23960] src/regex/regex_internal.h, + src/regex/test_regex_iterate_api.c: refactoring + +2012-09-23 16:24 szengel + + * [r23959] src/regex/regex.c, src/regex/regex_internal.h: DFA path + compression + +2012-09-23 13:08 szengel + + * [r23958] src/regex/test_regex_eval_api.c: fixed leak + +2012-09-23 07:39 harsha + + * [r23957] src/include/gnunet_testbed_service.h: doc + +2012-09-23 07:38 harsha + + * [r23956] src/stream/perf_stream_api.c: measuring uplink and + downlink + +2012-09-22 22:10 harsha + + * [r23955] src/stream/stream_api.c: fixing stream data + retransmissions + +2012-09-22 09:01 LRN + + * [r23941] src/gns/Makefile.am: Fix gns dependencies + +2012-09-21 12:15 wachs + + * [r23932] src/transport/gnunet-service-transport_clients.c, + src/transport/gnunet-service-transport_plugins.c, + src/transport/gnunet-service-transport_plugins.h: prefix based + plugin lookup for transport + +2012-09-21 12:15 wachs + + * [r23931] src/peerinfo-tool/gnunet-peerinfo_plugins.c: prefix + based plugin lookup for peerinfo tool + +2012-09-21 12:10 szengel + + * [r23930] src/pt/test_gnunet_vpn.c: Added warning to check the + firewall when tests fail (which happend to me). The + long diff is due to running pre-commit script prior to check-in. + +2012-09-20 21:46 szengel + + * [r23927] src/regex/regex.c: optimizations + +2012-09-20 13:48 grothoff + + * [r23923] src/exit/gnunet-helper-exit.c: give sysctl /dev/null + instead of no stdin/stdout + +2012-09-20 13:26 wachs + + * [r23919] src/transport/template_cfg_peer1.conf, + src/transport/template_cfg_peer2.conf: no valgrind + +2012-09-20 10:57 grothoff + + * [r23909] src/gns/gnocksy: tot tot + +2012-09-19 12:51 wachs + + * [r23901] src/transport/plugin_transport_http_server.c, + src/transport/transport.conf.in: move https cert location to + servicehome + +2012-09-19 09:27 wachs + + * [r23897] src/transport/plugin_transport_http_server.c: strip + external hostname prefix && improve url parsing output + +2012-09-18 15:46 harsha + + * [r23893] src/stream/perf_stream_api.c: 1 hop performance testing + +2012-09-18 15:34 harsha + + * [r23891] src/testbed/testbed_api.c: fixing valgrind unconditional + jump error + +2012-09-18 14:09 harsha + + * [r23890] src/stream/perf_stream_api.c: case to show lowered + throughtput if payload size if 64000 + +2012-09-18 14:08 harsha + + * [r23889] src/stream/stream_api.c: sequence difference calculation + fixes while processing DATA_ACKs + +2012-09-18 12:38 harsha + + * [r23881] src/testing/testing.c: appropriate logging string + +2012-09-18 12:38 harsha + + * [r23880] src/testbed/test_testbed_api_2peers_2controllers.c, + src/testbed/test_testbed_api_controllerlink.c, + src/testbed/test_testbed_api_testbed_run.c: fixes + +2012-09-17 14:32 szengel + + * [r23863] src/regex/regex.c, src/regex/test_regex_eval_api.c, + src/regex/test_regex_graph_api.c: coverity + +2012-09-17 13:20 grothoff + + * [r23854] src/datastore/datastore.conf.in: fixing Debian #684317 + +2012-09-17 13:18 grothoff + + * [r23853] src/transport/plugin_transport_udp.c, + src/transport/plugin_transport_udp.h: fixing udp busyloop + reported by LRN on #gnunet on 8-27 + +2012-09-17 10:45 grothoff + + * [r23845] src/core/gnunet-service-core.c, + src/core/gnunet-service-core_kx.c, + src/core/gnunet-service-core_kx.h, src/fs/fs_uri.c, + src/include/gnunet_crypto_lib.h, src/include/gnunet_server_lib.h, + src/mesh/gnunet-service-mesh.c, src/nse/gnunet-service-nse.c, + src/peerinfo-tool/gnunet-peerinfo.c, + src/transport/gnunet-service-transport.c, + src/transport/test_plugin_transport.c, src/util/crypto_random.c, + src/util/crypto_rsa.c, src/util/gnunet-rsa.c, src/util/server.c: + fixing #1551/#2503 + +2012-09-17 10:09 harsha + + * [r23844] src/testbed/Makefile.am: + test_testbed_api_2peers_2controllers to default tests + +2012-09-17 10:09 harsha + + * [r23843] src/testbed/test_testbed_api_2peers_2controllers.c: + checks for working local SSH + +2012-09-17 10:06 harsha + + * [r23842] src/testbed/gnunet-service-testbed.c: doxygen fixes + +2012-09-17 10:02 harsha + + * [r23840] src/testbed/gnunet-service-testbed.c, + src/testbed/test_testbed_api_2peers_2controllers.c: fixes and + working testcase for 2peers_2controllers + +2012-09-17 09:06 wachs + + * [r23838] src/util/helper.c: fix for "bad address " issue with + wlan helper + +2012-09-16 13:50 harsha + + * [r23836] src/testbed, src/testbed/Makefile.am, + src/testbed/test_testbed_api_2peers_2controllers.c, + src/testbed/testbed_api_peers.c: new test case (not working) + +2012-09-16 12:33 harsha + + * [r23835] src/testbed, src/testbed/Makefile.am, + src/testbed/test_testbed_api_2peers.c, + src/testbed/test_testbed_api_2peers_1controller.c: rename + +2012-09-16 11:51 harsha + + * [r23834] src/testbed/gnunet-service-testbed.c: extended rocc + +2012-09-16 03:42 LRN + + * [r23832] src/dht/gnunet-dht-monitor.c: Remove duplicate cleanups + +2012-09-15 18:53 grothoff + + * [r23830] src/nse/Makefile.am, src/nse/test_nse_multipeer.c: + making nse multipeer test use testbed + +2012-09-15 18:28 grothoff + + * [r23829] src/dht/gnunet-dht-monitor.c, src/dht/gnunet-dht-put.c: + fixing #2544 + +2012-09-14 20:42 harsha + + * [r23828] src/testbed/gnunet-service-testbed.c, + src/testbed/testbed_api.c, src/testbed/testbed_api_hosts.c, + src/testbed/testbed_api_services.c: coverity fixes + +2012-09-14 20:07 harsha + + * [r23827] src/testbed/gnunet-service-testbed.c: handler for + overlay request connect + +2012-09-14 17:06 schanzen + + * [r23826] src/gns/gnunet-gns.c: leak + +2012-09-14 14:53 harsha + + * [r23812] src/testbed/gnunet-service-testbed.c: 1/2 part - + inter-host overlay connect + +2012-09-14 14:05 harsha + + * [r23807] src/testbed/gnunet-service-testbed.c, + src/testbed/testbed.h: unstable checkpoint save + +2012-09-14 13:18 wachs + + * [r23804] src/transport/plugin_transport_http_client.c: client + side PUT disconnect + +2012-09-14 12:48 harsha + + * [r23803] src/include/gnunet_protocols.h: messages for + inter-controller overlay connect + +2012-09-14 12:46 harsha + + * [r23802] src/testbed/gnunet-service-testbed.c: stop peers before + destroying + +2012-09-14 12:23 grothoff + + * [r23799] src/dht/gnunet-dht-monitor.c: fix + +2012-09-14 12:14 harsha + + * [r23798] src/testbed/gnunet-service-testbed.c, + src/testbed/misc.supp: add to routing if delegated host is + subordinate + +2012-09-14 11:51 harsha + + * [r23797] src/testbed/gnunet-service-testbed.c: more checks on + while working on overlay connect request + +2012-09-14 11:31 harsha + + * [r23790] src/testbed/gnunet-service-testbed.c: removed OCC state + +2012-09-14 10:43 harsha + + * [r23788] src/testbed/testbed.h: added new message for inter-host + overlay connects + +2012-09-14 10:33 harsha + + * [r23787] src/testbed/gnunet-service-testbed.c: disambiguating + local overlay connect + +2012-09-14 09:02 wachs + + * [r23781] src/dht/gnunet-dht-get.c, src/dht/gnunet-dht-put.c: + demux everywhere option for CLI + +2012-09-14 07:57 grothoff + + * [r23773] src/dht/gnunet-dht-get.c: code cleanup + +2012-09-13 09:25 szengel + + * [r23762] src/regex/regex.c, src/regex/regex_internal.h: comments + +2012-09-12 20:25 harsha + + * [r23761] contrib/ssh-keys, src/stream/perf_stream_api.c: added + work ssh key + +2012-09-12 16:46 harsha + + * [r23760] src/testbed/gnunet-service-testbed.c, + src/testbed/test_testbed_api.c, + src/testbed/test_testbed_api_2peers.c, + src/testbed/test_testbed_api_controllerlink.c, + src/testbed/test_testbed_api_hosts.c, + src/testbed/test_testbed_api_operations.c, src/testbed/testbed.h, + src/testbed/testbed_helper.h: file end comment + +2012-09-12 16:16 harsha + + * [r23759] src/testbed/test_testbed_api_2peers.c: tests to show + overlay_connect on already connected peers doesn't fail + +2012-09-12 13:43 harsha + + * [r23758] src/testbed/gnunet-service-testbed.c: removed dead code + +2012-09-12 10:51 grothoff + + * [r23757] src/include/gnunet_testbed_service.h, + src/nse/gnunet-nse-profiler.c: triple star fun done + +2012-09-12 10:44 grothoff + + * [r23756] src/include/gnunet_testbed_service.h, + src/nse/gnunet-nse-profiler.c, src/stream/stream_protocol.h, + src/testbed/testbed_api_hosts.c: triple star fun + +2012-09-12 10:37 harsha + + * [r23755] src/stream/perf_stream_api.c, src/stream/stream_api.c: + fixes + +2012-09-12 10:18 harsha + + * [r23754] src/stream/perf_stream_api.c: fix + +2012-09-12 10:09 harsha + + * [r23753] src/stream/perf_stream_api.c: reasonable buffer for + performance measurements + +2012-09-12 10:04 harsha + + * [r23752] src/stream/perf_stream_api.c, + src/stream/test_stream_big.c: stream performance - implemented 1 + hop throughput calculation + +2012-09-11 20:44 harsha + + * [r23751] src/stream/perf_stream_api.c: more scaffolding + +2012-09-11 20:01 harsha + + * [r23750] src/stream/perf_stream_api.c: scaffolding + +2012-09-11 14:12 harsha + + * [r23749] src/stream, src/stream/Makefile.am, + src/stream/perf_stream_api.c: stub for stream performance tests + +2012-09-11 12:55 harsha + + * [r23748] src/stream/stream_api.c: stream speedup fixes + +2012-09-11 10:36 harsha + + * [r23747] src/stream/test_stream_big.c, + src/stream/test_stream_sequence_wraparound.c: reduced payload + size + +2012-09-11 10:24 harsha + + * [r23746] src/include/gnunet_stream_lib.h, src/stream/mesh.supp, + src/stream/stream_api.c: rename MAX_PACKET_SIZE option to + MAX_PAYLOAD_SIZE + +2012-09-11 09:37 harsha + + * [r23745] src/include/gnunet_stream_lib.h, + src/stream/stream_api.c, src/stream/test_stream_big.c, + src/stream/test_stream_sequence_wraparound.c: stream option to + set packet size + +2012-09-10 22:17 grothoff + + * [r23744] src/fs/fs_api.c, src/fs/fs_api.h, src/fs/fs_namespace.c, + src/fs/fs_publish.c, src/fs/fs_search.c, src/fs/fs_uri.c, + src/include/gnunet_fs_service.h: eliminating use of 'namespace' + as a fieldname / variable name to be C++ compatible + +2012-09-10 20:33 harsha + + * [r23743] src/include/gnunet_testbed_service.h, + src/testbed/testbed_api.c, src/testbed/testbed_api_peers.c: + cleanup when operations fail + +2012-09-10 19:19 grothoff + + * [r23742] src/namestore/namestore.conf.in: fixing Debian #686238 + +2012-09-10 19:01 grothoff + + * [r23741] src/nse/Makefile.am, src/nse/gnunet-nse-profiler.c: nse + profiler _compiles_ against new testbed API + +2012-09-10 18:58 grothoff + + * [r23740] src/include/gnunet_testbed_service.h, + src/testbed/Makefile.am, src/testbed/testbed_api_statistics.c: + adding another testbed API function: convenience function to get + all stats from all peers + +2012-09-10 14:08 szengel + + * [r23738] src/regex/regex.c, src/regex/test_regex_graph_api.c: + removing temp file in graph test + +2012-09-09 18:37 grothoff + + * [r23731] src/dv/Makefile.am: commenting out dead test + +2012-09-09 18:36 grothoff + + * [r23730] doc/man/gnunet-search.1, src/fs/gnunet-search.c, + src/include/gnunet_getopt_lib.h, src/util/getopt_helpers.c: new + getopt helper function to parse relative time command line + argument + +2012-09-09 14:20 harsha + + * [r23725] src/testbed/gnunet-service-testbed.c, + src/testbed/testbed_api.c, src/testbed/testbed_api.h, + src/testbed/testbed_api_services.c: error reporting in + service_connect + +2012-09-09 13:52 harsha + + * [r23724] src/include/gnunet_protocols.h, + src/testbed/gnunet-service-testbed.c, src/testbed/testbed.h, + src/testbed/testbed_api.c, src/testbed/testbed_api_services.c: + renamed GNUNET_MESSAGE_TYPE_TESTBED_OPERATIONEVENT to + GNUNET_MESSAGE_TYPE_TESTBED_OPERATIONFAILEVENT + +2012-09-09 13:46 harsha + + * [r23723] src/testbed/testbed_api.c, + src/testbed/testbed_api_peers.c, src/testbed/testbed_api_peers.h: + implemented continuations to testbed peer start/stop API + +2012-09-09 13:41 grothoff + + * [r23722] src/testbed/testbed_api_peers.h: doxygen fix + +2012-09-09 13:39 grothoff + + * [r23721] src/topology/Makefile.am, + src/topology/test_gnunet_daemon_topology.c: migrating topology + test to new testbed API + +2012-09-09 13:28 grothoff + + * [r23720] src/fs/Makefile.am, src/fs/fs_test_lib.c, + src/fs/fs_test_lib.h, src/fs/perf_gnunet_service_fs_p2p.c, + src/fs/perf_gnunet_service_fs_p2p_respect.c, + src/fs/test_fs_test_lib.c, + src/fs/test_gnunet_service_fs_migration.c, + src/fs/test_gnunet_service_fs_p2p.c: make fs tests build against + new testbed library -- they do not pass yet + +2012-09-08 19:19 grothoff + + * [r23716] configure.ac: clarify - kernel + +2012-09-08 13:50 harsha + + * [r23711] src/stream/Makefile.am, + src/stream/test_stream_2peers_halfclose.c: + test_stream_2peers_halfclose to testbed + +2012-09-07 16:53 harsha + + * [r23700] src/stream, src/stream/Makefile.am, + src/stream/test_stream_2peers.c, + src/stream/test_stream_2peers_new.c: migrate stream 2peers test + to testbed + +2012-09-07 16:38 szengel + + * [r23699] src/regex/Makefile.am, src/regex/regex.c, + src/regex/regex_graph.c, src/regex/test_regex_eval_api.c, + src/regex/test_regex_graph_api.c, + src/regex/test_regex_iterate_api.c: coverage + +2012-09-07 12:04 wachs + + * [r23697] + src/integration-tests/confs/c_bootstrap_server_w_massif.conf, + src/integration-tests/gnunet_testing.py.in, + src/integration-tests/test_mem_consumption.py: changes + +2012-09-07 11:17 bartpolot + + * [r23695] src/mesh/gnunet-service-mesh.c, + src/mesh/mesh_protocol.h: Added explicit keepalive to mesh + +2012-09-07 10:03 wachs + + * [r23692] src/transport/plugin_transport_http_server.c: + +2012-09-07 09:07 wachs + + * [r23687] src/transport/test_transport_api_multi_peer1.conf, + src/transport/test_transport_api_multi_peer2.conf: error message + on windows + +2012-09-06 16:24 schanzen + + * [r23681] src/dns/dnsstub.c, src/include/gns_protocol.h: doxy + +2012-09-06 15:51 grothoff + + * [r23676] src/dns/dnsstub.c, src/dns/gnunet-service-dns.c: fix use + uninit + +2012-09-05 13:36 harsha + + * [r23660] src/stream/mesh.supp: suppressions for mesh + +2012-09-05 13:32 harsha + + * [r23659] src/stream/test_stream_2peers_new.c: fix + +2012-09-05 13:20 wachs + + * [r23658] src/gns/Makefile.am, src/gns/test_gns_dht_three_peers.c: + fix + +2012-09-05 11:47 wachs + + * [r23657] src/gns/Makefile.am: does not compile due to api changes + ... + +2012-09-05 11:44 harsha + + * [r23656] src/include/gnunet_testbed_service.h, + src/testbed/test_testbed_api.c, + src/testbed/testbed_api_services.c: service connect callback + instead of operation completion callback + +2012-09-05 10:50 harsha + + * [r23655] src/include/gnunet_testbed_service-new.h, + src/include/gnunet_testbed_service.h, + src/testbed/test_testbed_api.c, + src/testbed/test_testbed_api_2peers.c, + src/testbed/test_testbed_api_controllerlink.c, + src/testbed/test_testbed_api_test.c, src/testbed/testbed_api.c, + src/testbed/testbed_api_peers.c, src/testbed/testbed_api_peers.h, + src/testbed/testbed_api_services.c: changed testbed API to + include convenience callbacks + +2012-09-05 09:00 wachs + + * [r23651] src/gns/test_gns_dht_three_peers.c: test working, but + fails + +2012-09-05 08:33 wachs + + * [r23650] src/gns/test_gns_dht_three_peers.c: more + +2012-09-05 08:28 wachs + + * [r23649] src/gns/test_gns_dht_default.conf, + src/gns/test_gns_dht_three_peers.c: do not autostart: I have to + copy zonefile + +2012-09-05 07:46 wachs + + * [r23646] src/gns/Makefile.am, src/gns/test_gns_dht_three_peers.c: + use precomputed zonekeys + +2012-09-05 07:16 wachs + + * [r23645] src/Makefile.am: install testbed + +2012-09-05 06:51 wachs + + * [r23644] src/gns/Makefile.am: fix + +2012-09-04 18:00 harsha + + * [r23640] src/include/gnunet_testbed_service-new.h, + src/include/gnunet_testbed_service.h.new: new testbed interface + +2012-09-04 14:46 harsha + + * [r23631] src/include/gnunet_testbed_service.h.new: save + +2012-09-04 14:09 harsha + + * [r23628] src/stream/Makefile.am: new stream/testbed testcase into + defaults + +2012-09-04 14:09 harsha + + * [r23627] src/testbed/test_testbed_api.conf: enable offline checks + +2012-09-04 13:59 grothoff + + * [r23626] contrib/gnunet.doxy: updating doxygen options + +2012-09-04 13:50 harsha + + * [r23625] src/testbed/test_testbed_api_2peers.c: sane timeout + +2012-09-04 12:45 grothoff + + * [r23617] src/gns/gnunet-service-gns_resolver.c: check return + value from sendto + +2012-09-04 12:43 grothoff + + * [r23616] src/util/disk.c: mark fcntl return value as + intentionally unchecked + +2012-09-04 12:24 harsha + + * [r23613] src/stream, src/stream/Makefile.am, + src/stream/stream_api.c, src/stream/stream_protocol.h, + src/stream/test_stream_2peers_new.c: new stream testcase using + testbed + +2012-09-04 11:14 wachs + + * [r23607] src/gns/test_gns_proxy.c: shutdown + +2012-09-04 10:28 harsha + + * [r23604] src/testbed/gnunet-service-testbed.c: sane logging and + code + +2012-09-04 10:01 wachs + + * [r23603] src/transport/plugin_transport_http_client.c: fix unload + +2012-09-04 08:48 wachs + + * [r23601] src/gns/test_gns_simple_lookup.conf: no valgrind + +2012-09-04 08:47 wachs + + * [r23600] src/gns/gnunet-service-gns_resolver.c, + src/gns/test_gns_simple_lookup.conf: unaligned memory access + +2012-09-04 06:52 wachs + + * [r23598] src/gns/test_gns_max_queries.c, + src/gns/test_gns_ns_lookup.c, src/gns/test_gns_simple_shorten.c, + src/gns/test_gns_simple_srv_lookup.c: minor fixes + +2012-09-03 15:25 wachs + + * [r23596] src/gns/Makefile.am, src/gns/test_gns_revocation.c: next + +2012-09-03 15:04 wachs + + * [r23593] src/gns/Makefile.am, src/gns/test_gns_max_queries.c: + next one + +2012-09-03 13:25 grothoff + + * [r23573] src/gns/gnunet-dns2gns.c, + src/gns/gnunet-service-gns_resolver.c: better log message, fixing + stale task + +2012-09-03 13:07 harsha + + * [r23571] src/include/gnunet_testbed_service.h: fix + +2012-09-03 13:00 grothoff + + * [r23570] src/util/service.c: always allow root + +2012-09-03 12:42 wachs + + * [r23568] src/integration-tests/Makefile.am: fix + +2012-09-03 12:03 wachs + + * [r23566] src/gns/Makefile.am, + src/gns/test_gns_simple_get_authority.c, + src/gns/test_gns_simple_shorten.c: test + +2012-09-03 11:44 wachs + + * [r23564] src/gns/test_gns_simple_shorten.c: fix + +2012-09-03 11:26 wachs + + * [r23563] src/gns/Makefile.am, src/gns/test_gns_simple_shorten.c: + test porting + +2012-09-03 10:45 harsha + + * [r23562] src/testbed/test_testbed_api_test.c, + src/testbed/testbed_api_test.c, + src/testbed/testbed_api_testbed.c: controller callback added in + GNUNET_TESTBED_test_run + +2012-09-03 10:12 harsha + + * [r23561] src/testbed/testbed.h: doc + +2012-09-02 16:33 grothoff + + * [r23557] src/dht/dht.conf.in: typo + +2012-09-02 14:06 grothoff + + * [r23556] src/fs/fs_search.c: commenting code + +2012-09-02 12:51 grothoff + + * [r23555] src/dht/dht.conf.in, + src/dht/gnunet-service-dht_neighbours.c: adding DHT option to + disable calls to try connect + +2012-09-02 11:17 harsha + + * [r23554] src/include/gnunet_testbed_service.h, + src/testbed/testbed_api_test.c, + src/testbed/testbed_api_testbed.c: input checks + +2012-09-02 10:25 harsha + + * [r23553] contrib/ssh-keys: removed testbed testing key + +2012-09-01 16:08 harsha + + * [r23550] src/testbed/test_testbed_api_testbed_run.c, + src/testbed/testbed_api_testbed.c: repect event mask before + calling event callback + +2012-09-01 15:44 harsha + + * [r23549] src/testbed/Makefile.am: added new testcase to default + checks + +2012-09-01 15:42 harsha + + * [r23548] src/testbed, src/testbed/Makefile.am, + src/testbed/test_testbed_api_test.c, + src/testbed/test_testbed_api_testbed_run.c, + src/testbed/testbed_api_test.c, + src/testbed/testbed_api_testbed.c: tests for testbed_test_run and + some fixes + +2012-08-31 16:24 harsha + + * [r23546] src/testbed/testbed_api_test.c: implemented + GNUNET_TESTBED_test_run + +2012-08-31 16:23 harsha + + * [r23545] src/testbed/testbed_api_testbed.c: restructuring and + checks + +2012-08-31 13:32 wachs + + * [r23544] + src/transport/test_transport_api_http_reverse_peer2.conf: a + config file + +2012-08-31 13:25 wachs + + * [r23543] src/transport/Makefile.am: changes + +2012-08-31 13:24 wachs + + * [r23542] src/transport/transport.conf.in: external host + +2012-08-31 12:24 wachs + + * [r23541] src/transport/transport.conf.in: config for new http/s + plugins + +2012-08-31 12:05 harsha + + * [r23540] src/testbed/test_testbed_api_testbed_run.c, + src/testbed/testbed_api_testbed.c: check if peer has already been + stopped before attempting to stop it again + +2012-08-31 11:45 wachs + + * [r23537] src/transport/plugin_transport_http_server.c: doxygen + fix + +2012-08-31 11:41 wachs + + * [r23536] src/transport/plugin_transport_http_server.c: cleanup + +2012-08-31 11:07 harsha + + * [r23535] src/lockmanager/gnunet-service-lockmanager.c, + src/lockmanager/lockmanager_api.c, + src/lockmanager/test_lockmanager_api.c, + src/lockmanager/test_lockmanager_api_acquireretry.c, + src/lockmanager/test_lockmanager_api_lockrelease.c, + src/lockmanager/test_lockmanager_api_servercrash.c: indentation + standard + +2012-08-31 11:03 wachs + + * [r23534] src/transport/Makefile.am: makefile + +2012-08-31 10:57 harsha + + * [r23533] src/testbed, src/testbed/Makefile.am, + src/testbed/gnunet-helper-testbed.c, + src/testbed/gnunet-testbed-helper.c, + src/testbed/test_gnunet_helper_testbed.c, + src/testbed/test_gnunet_testbed_helper.c, + src/testbed/testbed_api.c, src/testbed/testbed_helper.h: renamed + gnunet-testbed-helper to gnunet-helper-testbed + +2012-08-31 10:56 wachs + + * [r23532] src/transport/plugin_transport_http_client.c: cleanup + for http_client + +2012-08-31 10:36 harsha + + * [r23531] src/testbed/gnunet-service-testbed.c, + src/testbed/gnunet-testbed-helper.c, + src/testbed/test_gnunet_testbed_helper.c, + src/testbed/test_testbed_api.c, + src/testbed/test_testbed_api_2peers.c, + src/testbed/test_testbed_api_controllerlink.c, + src/testbed/test_testbed_api_hosts.c, + src/testbed/test_testbed_api_operations.c, + src/testbed/test_testbed_api_testbed_run.c, + src/testbed/testbed.h, src/testbed/testbed_api.c, + src/testbed/testbed_api.h, src/testbed/testbed_api_hosts.c, + src/testbed/testbed_api_hosts.h, + src/testbed/testbed_api_operations.c, + src/testbed/testbed_api_operations.h, + src/testbed/testbed_api_peers.c, src/testbed/testbed_api_peers.h, + src/testbed/testbed_api_services.c, + src/testbed/testbed_api_test.c, + src/testbed/testbed_api_testbed.c, + src/testbed/testbed_api_topology.c, src/testbed/testbed_helper.h: + adhering to indentation standard + +2012-08-31 10:06 harsha + + * [r23530] src/testbed/Makefile.am: added testbed_run test to + default checks + +2012-08-31 10:05 harsha + + * [r23529] src/testbed/test_testbed_api_testbed_run.c, + src/testbed/testbed_api_testbed.c: stop peers before destroying + them + +2012-08-31 07:52 harsha + + * [r23528] src/include/gnunet_testbed_service.h, + src/testbed/gnunet-service-testbed.c, + src/testbed/test_testbed_api_testbed_run.c, + src/testbed/testbed_api_testbed.c, src/testbed/x64_misc.supp: + Removed RunHandle return from GNUNET_TESTBED_run + +2012-08-30 19:54 harsha + + * [r23527] src/testbed/testbed_api.c: api handler for operation + fail event + +2012-08-30 19:53 harsha + + * [r23526] src/testbed/testbed_api_peers.c: peer_create starts with + 0 + +2012-08-30 19:52 harsha + + * [r23525] src/testbed/gnunet-service-testbed.c: peer_list handling + fixes + +2012-08-30 18:41 grothoff + + * [r23522] src/fs/fs_uri.c: fixing #2530 + +2012-08-29 22:46 harsha + + * [r23512] src/testbed/gnunet-service-testbed.c: fixes + +2012-08-29 22:23 harsha + + * [r23511] src/testbed, src/testbed/test_testbed_api_testbed_run.c: + added the forgotten test case + +2012-08-29 22:10 harsha + + * [r23510] src/testbed/Makefile.am, + src/testbed/gnunet-service-testbed.c, + src/testbed/testbed_api_testbed.c: GNUNET_TESTBED_run and test + cases + +2012-08-29 16:39 harsha + + * [r23508] src/include/gnunet_testbed_service.h: GNUNET_TESTBED_run + to return a handle which can be used for clean shutdown + +2012-08-29 14:56 harsha + + * [r23501] src/testbed/testbed_api.c, + src/testbed/testbed_api_testbed.c: checkpoint save for + testbed_run + +2012-08-29 13:18 wachs + + * [r23498] src/transport/plugin_transport_http_client.c, + src/transport/plugin_transport_http_server.c, + src/transport/test_plugin_transport.c: changes + +2012-08-29 13:09 grothoff + + * [r23497] configure.ac, src/dns/gnunet-service-dns.c, + src/exit/gnunet-daemon-exit.c, src/fs/fs_dirmetascan.c, + src/include/gnunet_helper_lib.h, + src/testbed/test_gnunet_testbed_helper.c, + src/testbed/testbed_api.c, src/transport/plugin_transport_wlan.c, + src/transport/test_plugin_transport.c, + src/util/common_allocation.c, src/util/helper.c, + src/vpn/gnunet-service-vpn.c: only use control pipe with helpers + IF the helper actually supports it + +2012-08-29 12:35 grothoff + + * [r23494] src/include/gnunet_testing_lib-new.h, + src/testing/testing.c: extend API to enalbe exclusive port ranges + to be specified for testing-system objects + +2012-08-29 09:14 wachs + + * [r23490] src/transport/plugin_transport_http_client.c, + src/transport/test_plugin_transport.c: changes + +2012-08-29 08:14 wachs + + * [r23488] src/transport/plugin_transport_http_client.c, + src/transport/test_plugin_transport.c: changes + +2012-08-29 07:41 wachs + + * [r23487] src/transport/test_plugin_transport_udp.c: not used + +2012-08-29 07:20 wachs + + * [r23486] src/transport/plugin_transport_http_client.c: coverity + 10259 + +2012-08-29 07:18 wachs + + * [r23485] src/transport/plugin_transport_http_common.c: coverity + 10260 + +2012-08-29 07:16 wachs + + * [r23484] src/transport/test_plugin_transport.c: coverity 10270 + +2012-08-29 00:39 LRN + + * [r23482] src/transport/test_transport_api_http_peer1.conf, + src/transport/test_transport_api_http_peer2.conf, + src/transport/test_transport_api_http_reverse_peer1.conf: No + valgrind in HEAD, please + +2012-08-28 15:11 wachs + + * [r23480] src/ats/ats_api_scheduling.c, + src/include/gnunet_transport_plugin.h: changes + +2012-08-28 15:11 wachs + + * [r23479] src/transport/Makefile.am, + src/transport/plugin_transport_http_common.c, + src/transport/plugin_transport_http_common.h, + src/transport/plugin_transport_http_server.c, + src/transport/test_transport_api_http_nat_peer1.conf, + src/transport/test_transport_api_http_nat_peer2.conf, + src/transport/test_transport_api_http_peer1.conf, + src/transport/test_transport_api_http_reverse_peer1.conf, + src/transport/test_transport_api_http_reverse_proxy.conf, + src/transport/test_transport_api_https_nat_peer1.conf, + src/transport/test_transport_api_https_nat_peer2.conf, + src/transport/test_transport_api_reliability_http_nat_peer1.conf, + src/transport/test_transport_api_reliability_http_nat_peer2.conf, + src/transport/test_transport_api_reliability_https_nat_peer1.conf, + src/transport/test_transport_api_reliability_https_nat_peer2.conf: + confs + coverity + +2012-08-28 14:51 wachs + + * [r23478] src/transport/plugin_transport_http_server.c: changes + +2012-08-28 14:51 wachs + + * [r23477] src/transport/plugin_transport_http_common.c: changes + +2012-08-28 14:51 wachs + + * [r23476] src/transport/plugin_transport_http_common.h: changes + +2012-08-28 14:51 wachs + + * [r23475] src/transport/plugin_transport_http_client.c: changes + +2012-08-28 13:41 LRN + + * [r23473] src/transport/Makefile.am: Fix https client ldflags + +2012-08-28 11:43 wachs + + * [r23472] src/transport/Makefile.am, + src/transport/plugin_transport_http_client.c, + src/transport/plugin_transport_http_server.c, + src/transport/test_quota_compliance_https_asymmetric_peer1.conf, + src/transport/test_quota_compliance_https_asymmetric_peer2.conf, + src/transport/test_quota_compliance_https_peer1.conf, + src/transport/test_quota_compliance_https_peer2.conf, + src/transport/test_transport_api_https_peer1.conf, + src/transport/test_transport_api_https_peer2.conf, + src/transport/test_transport_api_reliability_https_peer1.conf, + src/transport/test_transport_api_reliability_https_peer2.conf, + src/transport/test_transport_api_timeout_https_peer1.conf, + src/transport/test_transport_api_timeout_https_peer2.conf: tests + +2012-08-28 10:54 wachs + + * [r23471] + src/transport/test_quota_compliance_http_asymmetric_peer1.conf, + src/transport/test_quota_compliance_http_asymmetric_peer2.conf: + asymmetric + +2012-08-28 10:51 wachs + + * [r23470] src/transport/Makefile.am, + src/transport/test_quota_compliance_http_peer1.conf, + src/transport/test_quota_compliance_http_peer2.conf: qutoa + +2012-08-28 10:19 LRN + + * [r23469] configure.ac: Make poisoning configurable. Enable it on + debug builds by default + +2012-08-28 09:55 wachs + + * [r23467] src/transport/Makefile.am, + src/transport/plugin_transport_http_common.h, + src/transport/test_transport_api_http_peer2.conf, + src/transport/test_transport_api_reliability_http_peer1.conf, + src/transport/test_transport_api_reliability_http_peer2.conf, + src/transport/test_transport_api_timeout_http_peer1.conf, + src/transport/test_transport_api_timeout_http_peer2.conf: test + conf updates + +2012-08-28 08:45 LRN + + * [r23465] src/transport/Makefile.am: fix http client ldflags + +2012-08-27 21:31 harsha + + * [r23459] src/include/gnunet_testbed_service.h: more doc + +2012-08-27 18:52 grothoff + + * [r23453] Makefile.am, contrib/Makefile.am, contrib/hostlist.cgi, + contrib/hostlist.php, contrib/report.sh, contrib/submit, + doc/Makefile.am: updating report.sh, removing obsolete hostlist + scripts + +2012-08-27 17:36 harsha + + * [r23448] src/testbed/Makefile.am, src/testbed/test_testbed_api.c, + src/testbed/testbed_api_services.c: peer service connect and its + test case + +2012-08-27 15:47 LRN + + * [r23446] src/fs/perf_gnunet_service_fs_p2p.conf: Fix fs test + config + +2012-08-27 15:42 wachs + + * [r23445] src/transport/plugin_transport_http_client.c: timeout + +2012-08-27 15:33 wachs + + * [r23444] src/transport/plugin_transport_http_client.c: fix + +2012-08-27 15:02 wachs + + * [r23442] src/transport/plugin_transport_http_client.c, + src/transport/plugin_transport_http_common.h, + src/transport/plugin_transport_http_server.c: changes + +2012-08-27 14:23 wachs + + * [r23439] src/transport/plugin_transport_http_client.c: more code + +2012-08-27 13:40 wachs + + * [r23437] src/transport/plugin_transport_http_server.c: change + +2012-08-27 13:03 wachs + + * [r23436] src/transport/plugin_transport_http_client.c: more + +2012-08-27 13:03 wachs + + * [r23435] src/transport/plugin_transport_http_server.c: + +2012-08-27 12:08 wachs + + * [r23434] src/transport/plugin_transport_http_client.c: code + +2012-08-27 11:51 wachs + + * [r23433] src/transport/plugin_transport_http_client.c, + src/transport/test_transport_api_http_peer1.conf, + src/transport/test_transport_api_http_peer2.conf, + src/transport/test_transport_api_http_reverse_proxy.conf: changes + +2012-08-27 11:44 wachs + + * [r23432] src/transport/transport-testing.c: docu + +2012-08-27 11:40 wachs + + * [r23431] src/transport/test_plugin_transport.c: fix + +2012-08-27 11:33 wachs + + * [r23430] src/transport/Makefile.am: test + +2012-08-27 11:32 wachs + + * [r23429] src/transport/plugin_transport_http_client.c: changes + +2012-08-27 09:58 szengel + + * [r23428] src/regex/regex.c, src/regex/regex_internal.h: Fixes + +2012-08-27 09:24 wachs + + * [r23427] src/transport/test_plugin_transport.c: fix for wlan + +2012-08-27 09:10 harsha + + * [r23425] src/testbed/testbed_api.c, src/testbed/testbed_api.h, + src/testbed/testbed_api_services.c: service connect checkpoint + save + +2012-08-26 10:45 harsha + + * [r23423] src/testbed/gnunet-service-testbed.c, + src/testbed/testbed_api_peers.c: doxygen fixes + +2012-08-25 14:19 LRN + + * [r23421] src/include/gnunet_transport_plugin.h, + src/transport/plugin_transport_http.c: changes to address + notification strike back + +2012-08-25 11:50 harsha + + * [r23420] src/testbed/testbed_api.c, src/testbed/testbed_api.h, + src/testbed/testbed_api_peers.c, src/testbed/testbed_api_peers.h, + src/testbed/testbed_api_services.c: towards implementing + service_connect + +2012-08-25 10:29 harsha + + * [r23419] src/testbed/testbed.conf.in, src/testbed/testbed_api.c, + src/testbed/testbed_api.h, src/testbed/testbed_api_peers.c: + operation queue renaming + +2012-08-24 17:52 harsha + + * [r23415] src/testbed/gnunet-service-testbed.c, + src/testbed/test_testbed_api_controllerlink.c, + src/testbed/testbed_api.c: peer start/stop forwarding with tests + +2012-08-24 15:46 harsha + + * [r23412] src/testbed/gnunet-service-testbed.c, + src/testbed/test_testbed_api_controllerlink.c: peer destroy + forwarding with tests + +2012-08-24 15:18 wachs + + * [r23410] src/transport/gnunet-service-transport.c, + src/transport/plugin_transport_http_client.c, + src/transport/plugin_transport_http_server.c, + src/transport/plugin_transport_tcp.c, + src/transport/plugin_transport_udp.c, + src/transport/plugin_transport_unix.c, + src/transport/plugin_transport_wlan.c: changes to address + notification + +2012-08-24 15:11 wachs + + * [r23409] src/transport/plugin_transport_template.c: update + +2012-08-24 14:51 wachs + + * [r23408] src/transport/plugin_transport_http_client.c, + src/transport/plugin_transport_http_common.h, + src/transport/plugin_transport_http_server.c, + src/transport/test_transport_api_http_reverse_proxy.conf: changes + +2012-08-24 13:51 harsha + + * [r23407] src/testbed/gnunet-service-testbed.c, + src/testbed/test_testbed_api_controllerlink.c: peer create + fowarding with tests + +2012-08-24 13:24 wachs + + * [r23405] src/transport/plugin_transport_http_server.c: more + +2012-08-24 13:02 wachs + + * [r23402] src/transport/plugin_transport_http_server.c: code + +2012-08-24 12:20 LRN + + * [r23401] src/mesh/gnunet-service-mesh.c: More + dont-access-t-when-it-is-NULL fixes + +2012-08-24 10:39 LRN + + * [r23400] src/mesh/gnunet-service-mesh.c: Don't access t when t is + NULL + +2012-08-24 08:12 wachs + + * [r23399] src/transport/plugin_transport_http_server.c: mod + +2012-08-23 18:02 LRN + + * [r23390] src/dns/Makefile.am: Roll back r23388, fix it + differently + +2012-08-23 17:52 LRN + + * [r23389] src/transport/Makefile.am: Don't run unix test on W32 + +2012-08-23 17:49 LRN + + * [r23388] src/dns/Makefile.am: Fix dns service dependencies + +2012-08-23 14:54 wachs + + * [r23385] src/transport/plugin_transport_http_server.c: more code + +2012-08-23 12:28 wachs + + * [r23380] src/transport/Makefile.am, + src/transport/test_plugin_transport_data.conf: more test + +2012-08-23 12:24 wachs + + * [r23379] src/transport/plugin_transport_http_common.c: improved + security checks + +2012-08-23 12:23 wachs + + * [r23378] src/transport/test_plugin_transport.c: mem leak + +2012-08-23 12:12 wachs + + * [r23377] src/transport/plugin_transport_http_server.c: fix + +2012-08-23 11:59 wachs + + * [r23376] src/transport/test_plugin_transport.c: fix + +2012-08-23 11:48 wachs + + * [r23375] src/transport/Makefile.am, + src/transport/plugin_transport_udp_broadcasting.c, + src/transport/test_plugin_transport.c: plugin test + +2012-08-23 10:01 wachs + + * [r23373] src/transport/test_plugin_transport.c: + +2012-08-23 07:29 wachs + + * [r23372] src/transport/test_plugin_transport.c: changes to plugin + test + +2012-08-23 07:04 wachs + + * [r23371] src/transport/plugin_transport_template.c: update + template with latest api changes + +2012-08-22 15:26 wachs + + * [r23364] src/transport/plugin_transport_http_client.c: changes + +2012-08-22 15:23 wachs + + * [r23363] src/transport/plugin_transport_http_common.h, + src/transport/plugin_transport_http_server.c, + src/transport/test_transport_api_http_reverse_proxy.conf: latest + changes + +2012-08-22 14:49 wachs + + * [r23362] src/transport/plugin_transport_http_common.c, + src/transport/plugin_transport_http_common.h, + src/transport/plugin_transport_http_server.c, + src/transport/test_transport_api_http_reverse_proxy.conf: changes + +2012-08-22 13:41 wachs + + * [r23360] src/transport/Makefile.am, + src/transport/plugin_transport_http_client.c, + src/transport/plugin_transport_http_common.c, + src/transport/plugin_transport_http_common.h, + src/transport/plugin_transport_http_server.c, + src/transport/test_transport_api_http_reverse_proxy.conf: changes + +2012-08-22 12:49 harsha + + * [r23359] contrib/ssh-keys: added testbed testing ssh key + +2012-08-22 12:19 wachs + + * [r23358] src/transport/Makefile.am: changes + +2012-08-22 12:14 wachs + + * [r23357] src/transport/plugin_transport_http_server.c: fix for + https + +2012-08-22 12:03 harsha + + * [r23356] src/testbed/testbed_api.c: added ssh batch mode param + +2012-08-22 10:56 wachs + + * [r23355] src/transport/plugin_transport_http_server.c, + src/transport/test_transport_api_http_reverse_proxy.conf: more + +2012-08-22 10:06 wachs + + * [r23354] src/transport/plugin_transport_http_client.c, + src/transport/plugin_transport_http_server.c, + src/transport/test_transport_api_http_reverse_proxy.conf: changes + +2012-08-22 08:13 wachs + + * [r23353] configure.ac, src/transport/Makefile.am: libcurl check + +2012-08-22 06:34 wachs + + * [r23352] contrib/ssh-keys: key + +2012-08-21 13:46 harsha + + * [r23345] src/testbed/Makefile.am, + src/testbed/test_testbed_api_controllerlink.c, + src/testbed/testbed_api.c: added checks for passwordless ssh + login during tests + +2012-08-21 12:12 harsha + + * [r23340] src/testbed/Makefile.am, + src/testbed/test_testbed_api_controllerlink.c: removed controller + link testcase from default tests + +2012-08-21 11:59 harsha + + * [r23339] src/testbed/gnunet-service-testbed.c, + src/testbed/testbed_api.c: modified link controller forwarding to + use forwarded operations + +2012-08-21 11:15 wachs + + * [r23338] src/transport/plugin_transport_http.c, + src/transport/plugin_transport_http.h, + src/transport/test_transport_api_http_reverse_proxy.conf: mod + +2012-08-21 11:05 wachs + + * [r23337] src/transport/plugin_transport_http_server.c: improved + url parsing + +2012-08-21 08:50 wachs + + * [r23336] src/transport/Makefile.am: change + +2012-08-21 08:49 wachs + + * [r23335] + src/transport/test_transport_api_http_reverse_proxy.conf: new + conf + +2012-08-21 08:16 harsha + + * [r23334] src/testbed/Makefile.am: added controller link testcase + to default tests + +2012-08-21 06:01 grothoff + + * [r23331] po/de.po, po/es.po, po/sv.po, po/vi.po, po/zh_CN.po, + src/dns/Makefile.am, src/dns/dnsstub.c, + src/dns/gnunet-service-dns.c, src/include/Makefile.am, + src/include/gnunet_dnsstub_lib.h: refactoring dns service to take + stub code into separate library for use in gns2dns proxy + +2012-08-17 17:33 szengel + + * [r23290] src/regex/regex.c, src/regex/test_regex_eval_api.c: + Fixed eval test case and stack smashing protection + +2012-08-17 14:54 harsha + + * [r23288] src/include/gnunet_testbed_service.h, + src/testbed/gnunet-service-testbed.c, + src/testbed/test_testbed_api_controllerlink.c, + src/testbed/testbed.h, src/testbed/testbed_api.c, + src/testbed/testbed_api.h, src/testbed/testbed_api_peers.c: + controller link as operation + +2012-08-17 12:32 harsha + + * [r23286] src/testbed/gnunet-service-testbed.c, + src/testbed/gnunet-testbed-helper.c, + src/testbed/test_testbed_api_controllerlink.c, + src/testbed/testbed_api.c, src/testbed/testbed_api_hosts.c: fixes + +2012-08-17 10:03 szengel + + * [r23280] src/regex/regex.c, src/regex/regex_graph.c, + src/regex/regex_internal.h: Added multi-striding capabilities to + regex. + +2012-08-14 14:25 harsha + + * [r23229] src/testbed/gnunet-service-testbed.c, + src/testbed/test_testbed_api_controllerlink.c: fixes + +2012-08-14 13:38 harsha + + * [r23225] src/testbed/gnunet-service-testbed.c, + src/testbed/test_testbed_api_controllerlink.c, + src/testbed/testbed_api_hosts.c: fixes and removed slave2 from + controller link test + +2012-08-14 13:24 harsha + + * [r23224] src/testbed, src/testbed/Makefile.am, + src/testbed/gnunet-service-testbed.c, + src/testbed/test_testbed_api_2peers.c, + src/testbed/test_testbed_api_controllerlink.c, + src/testbed/testbed_api.c: fixes + +2012-08-13 16:17 szengel + + * [r23212] src/regex/regex.c, src/regex/regex_graph.c, + src/regex/regex_internal.h: using strings as labels + +2012-08-11 15:13 harsha + + * [r23203] src/testbed/gnunet-service-testbed.c: implemented peer + create operation forwarding + +2012-08-11 13:04 harsha + + * [r23201] src/testbed/testbed_api.c, src/testbed/testbed_api.h: + forward operation msg cancel + +2012-08-11 12:46 harsha + + * [r23200] src/testbed/gnunet-service-testbed.c, + src/testbed/testbed.h, src/testbed/testbed_api.c, + src/testbed/testbed_api.h: api forward operation message + +2012-08-11 10:38 harsha + + * [r23199] src/testbed/gnunet-service-testbed.c: Local and remote + peers + +2012-08-10 20:03 harsha + + * [r23198] src/testbed/gnunet-service-testbed.c, + src/testbed/testbed_api.h: towards peer create forwarding + +2012-08-10 15:33 harsha + + * [r23195] src/testbed/gnunet-service-testbed.c, + src/testbed/testbed.h, src/testbed/testbed_api.c: controller + hostname in init + +2012-08-10 09:56 harsha + + * [r23193] src/testbed/gnunet-service-testbed.c: overlay connect + operation failure reporting + +2012-08-10 07:34 harsha + + * [r23192] src/testbed/gnunet-service-testbed.c: cleaner peer + destory + +2012-08-09 09:31 wachs + + * [r23171] src/namestore/namestore_common.c: bug + +2012-08-08 13:12 wachs + + * [r23164] src/integration-tests/connection_watchdog.c: coverity + +2012-08-08 10:31 wachs + + * [r23162] src/transport/transport_api.c: callback for offer_hello + +2012-08-08 10:05 wachs + + * [r23161] src/transport/gnunet-service-transport_validation.c: + remove msg + +2012-08-07 20:33 harsha + + * [r23158] src/testbed/Makefile.am, + src/testbed/gnunet-service-testbed.c, src/testbed/testbed_api.c: + fixed memory leak with HELLO + +2012-08-07 15:02 harsha + + * [r23149] src/testbed/Makefile.am, + src/testbed/gnunet-service-testbed.c, + src/testbed/test_testbed_api.conf, + src/testbed/test_testbed_api_2peers.c, src/testbed/testbed_api.c: + working version of peer connect + +2012-08-07 12:23 harsha + + * [r23146] src/testbed/Makefile.am, + src/testbed/gnunet-service-testbed.c, + src/testbed/test_testbed_api_2peers.c, + src/testbed/testbed_api_operations.c: hacking overlay connect + +2012-08-04 07:45 LRN + + * [r23093] src/gns/gnunet-gns-proxy.c: Fix a typo + +2012-08-03 22:34 harsha + + * [r23076] src/testbed/gnunet-service-testbed.c, + src/testbed/test_testbed_api_2peers.c, src/testbed/testbed.h, + src/testbed/testbed_api.c, src/testbed/testbed_api_peers.c, + src/testbed/testbed_api_peers.h: refined overlay connect and + extended test case + +2012-08-03 18:32 grothoff + + * [r23073] src/gns/gnunet-gns-proxy.c: better style + +2012-08-01 15:03 harsha + + * [r23032] src/testbed/gnunet-service-testbed.c, + src/testbed/testbed_api_peers.c: improved overlay connect + handling + +2012-08-01 11:48 harsha + + * [r23029] src/testbed/testbed_api.c, src/testbed/testbed_api.h, + src/testbed/testbed_api_peers.c: state information for + OperationContext + +2012-08-01 11:12 harsha + + * [r23027] src/testbed/testbed_api.c, src/testbed/testbed_api.h, + src/testbed/testbed_api_peers.c: peer info with new operations + handling + +2012-07-31 18:48 harsha + + * [r23022] src/testbed/testbed_api.c, + src/testbed/testbed_api_operations.c, + src/testbed/testbed_api_peers.c: peer start/stop with new + operations handling + +2012-07-31 15:29 harsha + + * [r23020] src/testbed/testbed_api.c, + src/testbed/testbed_api_peers.c, src/testbed/testbed_api_peers.h: + peer destroy with new operations handling + +2012-07-31 14:53 harsha + + * [r23019] src/include/gnunet_testbed_service.h: doc + +2012-07-31 14:52 harsha + + * [r23018] src/testbed/testbed.conf.in, src/testbed/testbed_api.c, + src/testbed/testbed_api.h, src/testbed/testbed_api_operations.c, + src/testbed/testbed_api_peers.c, src/testbed/testbed_api_peers.h: + peer create with new operations handling + +2012-07-31 07:38 wachs + + * [r23009] src/gns/nss/Makefile.am: fix + +2012-07-30 10:59 LRN + + * [r22969] src/dns/Makefile.am, src/dns/install-dns-helper.sh, + src/exit/Makefile.am, src/exit/install-exit-helper.sh, + src/gns/nss/Makefile.am, src/gns/nss/install-nss-plugin.sh, + src/nat/Makefile.am, src/nat/install-nat-helper.sh, + src/transport/Makefile.am, src/transport/install-wlan-helper.sh, + src/vpn/Makefile.am, src/vpn/install-vpn-helper.sh: Do not run + install commands from makefiles directly + +2012-07-30 07:26 grothoff + + * [r22960] src/include/gnunet_common.h: fix for gcc alginment issue + on sparc reported to Debian as #670578 + +2012-07-29 21:32 harsha + + * [r22958] src/testbed/test_testbed_api_operations.c, + src/testbed/testbed_api_operations.c, + src/testbed/testbed_api_operations.h: removed redundant cls(data) + +2012-07-29 20:40 harsha + + * [r22955] src/stream/stream_api.c: fixes + +2012-07-29 11:24 harsha + + * [r22953] src/testbed, src/testbed/Makefile.am, + src/testbed/test_testbed_api.c, + src/testbed/test_testbed_api_operations.c, + src/testbed/testbed_api_operations.c, + src/testbed/testbed_api_operations.h: testbed operations + +2012-07-28 23:05 harsha + + * [r22952] src/testbed/testbed_api_operations.c, + src/testbed/testbed_api_operations.h: testbed operations + +2012-07-27 15:06 harsha + + * [r22950] src/testbed/gnunet-service-testbed.c, + src/testbed/testbed_api_hosts.c: fixes + +2012-07-27 14:37 harsha + + * [r22947] src/testbed/gnunet-service-testbed.c: extensive message + checking + +2012-07-27 13:54 harsha + + * [r22945] src/testbed/gnunet-service-testbed.c: fixed LCF + forwarding + +2012-07-27 12:41 harsha + + * [r22942] src/testbed/testbed_api_hosts.c: fixed incorrect realloc + size + +2012-07-27 12:02 harsha + + * [r22941] src/testbed/gnunet-service-testbed.c: removed slave + context + +2012-07-27 10:25 LRN + + * [r22938] src/util/helper.c: Use pipe control for helper processes + + This fixes testbed service leak in testbed tests. + Either this, or NOT using helper API for testbed helper. + +2012-07-27 10:25 LRN + + * [r22937] src/gns/gnunet-gns-helper-service-w32.c, + src/gns/w32nsp-install.c, src/gns/w32nsp-resolve.c, + src/gns/w32nsp-uninstall.c, src/gns/w32nsp.c: Fix w32nsp headers + +2012-07-27 10:09 harsha + + * [r22936] src/testbed/gnunet-testbed-helper.c: helper shutdown on + stdin close + +2012-07-26 06:50 wachs + + * [r22919] src/ats/ats_api_scheduling.c: transport fix + +2012-07-25 15:31 bartpolot + + * [r22916] src/dns/gnunet-service-dns.c, + src/exit/gnunet-daemon-exit.c, src/include/gnunet_mesh_service.h, + src/mesh/mesh_api.c, src/pt/gnunet-daemon-pt.c, + src/stream/stream_api.c, src/vpn/gnunet-service-vpn.c: Eliminate + mesh priority option + +2012-07-25 14:22 bartpolot + + * [r22910] src/dns/gnunet-service-dns.c, + src/exit/gnunet-daemon-exit.c, src/include/gnunet_mesh_service.h, + src/include/gnunet_protocols.h, src/mesh/mesh.h, + src/mesh/mesh_api.c, src/pt/gnunet-daemon-pt.c, + src/stream/stream_api.c, src/vpn/gnunet-service-vpn.c: Eliminated + mesh API buffering + +2012-07-25 12:27 wachs + + * [r22907] src/transport/gnunet-service-transport_validation.c: + comment + +2012-07-24 13:46 harsha + + * [r22870] src/testbed/test_testbed_api.c, + src/testbed/testbed_api.c, src/testbed/testbed_api.h, + src/testbed/testbed_api_operations.c, + src/testbed/testbed_api_operations.h, + src/testbed/testbed_api_peers.c, src/testbed/testbed_api_peers.h: + fixed mem leaks with operations + +2012-07-24 12:39 harsha + + * [r22868] src/testbed/test_testbed_api.c, + src/testbed/testbed_api.c, src/testbed/testbed_api_peers.c, + src/testbed/testbed_api_peers.h: testcases for peer get + information + +2012-07-24 11:40 harsha + + * [r22867] src/testbed/gnunet-service-testbed.c: hack for unix + domain sockets + +2012-07-24 11:31 harsha + + * [r22866] src/testbed/testbed_api.c: message checks at client + receive side + +2012-07-23 14:35 szengel + + * [r22847] src/regex/regex.c: Fixed coverty issues + +2012-07-23 11:40 wachs + + * [r22836] src/ats/gnunet-service-ats_addresses_mlp.c: coverity + 10104/3/2 + +2012-07-22 18:33 harsha + + * [r22823] src/include/gnunet_testbed_service.h: removed redundant + info request + +2012-07-22 13:47 LRN + + * [r22820] src/dht/Makefile.am, src/dht/test_dht_tools.py.in, + src/fs/test_gnunet_fs_rec.py.in: pythonize test_dht_tools + +2012-07-22 13:47 LRN + + * [r22819] contrib/Makefile.am, contrib/pydiffer.py.in, + src/fs/test_gnunet_fs_rec.py.in: Use Python batteries in fs_rec + test + +2012-07-22 13:47 LRN + + * [r22818] src/ats-test/test_transport_ats_1addr.conf, + src/ats-test/test_transport_ats_2addr.conf, + src/ats-test/test_transport_ats_4addr.conf, + src/dht/test_dht_2dtorus.conf, src/dht/test_dht_api_data.conf, + src/dht/test_dht_line.conf, src/dht/test_dht_multipeer_data.conf, + src/dht/test_dht_twopeer_data.conf, + src/dv/test_transport_dv_data.conf, src/fs/test_fs_defaults.conf, + src/gns/test_gns_defaults.conf, src/gns/test_gns_proxy.conf, + src/integration-tests/test_connection_stability.conf, + src/mesh/test_mesh_2dtorus.conf, src/mesh/test_mesh_small.conf, + src/nse/test_nse.conf, src/stream/test_stream_local.conf, + src/testing/test_testing_defaults.conf, + src/testing_old/test_testing_2dtorus.conf, + src/testing_old/test_testing_defaults.conf, + src/testing_old/testing_group.c, + src/topology/test_gnunet_daemon_topology_data.conf: Fix hostkey + loading for old testing framework + +2012-07-22 13:47 LRN + + * [r22817] src/transport/transport-testing.c: + DOS-pathsep-compatible filename extraction + +2012-07-22 13:46 LRN + + * [r22816] src/gns/Makefile.am: Fix dns2gns dependencies + +2012-07-22 13:46 LRN + + * [r22815] src/fs/test_gnunet_fs_idx.py.in, + src/fs/test_gnunet_fs_psd.py.in: Use test tgz instead of COPYING + for FS tests + +2012-07-20 20:17 grothoff + + * [r22810] src/gns/Makefile.am, src/gns/gnunet-dns2gns.c: ns2gns + +2012-07-20 15:03 harsha + + * [r22800] src/testbed/gnunet-service-testbed.c: fix NULL memory + access + +2012-07-20 14:57 harsha + + * [r22799] src/testbed/gnunet-service-testbed.c: fix mem leak + +2012-07-20 14:49 harsha + + * [r22798] src/testbed/gnunet-service-testbed.c, + src/testbed/test_testbed_api.c, src/testbed/testbed_api.c, + src/testbed/testbed_api_peers.c: peer start and stop + +2012-07-20 14:48 harsha + + * [r22797] src/testing/testing.c: decide btw ipv4 or ipv6 + +2012-07-20 12:02 harsha + + * [r22788] src/include/gnunet_testbed_service.h, src/testbed, + src/testbed/gnunet-service-testbed.c, + src/testbed/test_testbed_api.c, + src/testbed/test_testbed_api_2peers.c, src/testbed/testbed.h, + src/testbed/testbed_api.c, src/testbed/testbed_api.h, + src/testbed/testbed_api_peers.c, src/testbed/testbed_api_peers.h: + peer create callback + +2012-07-19 12:50 wachs + + * [r22774] src/ats/gnunet-service-ats_addresses.c: memory leak + +2012-07-18 21:55 harsha + + * [r22769] src/testbed/gnunet-service-testbed.c, + src/testbed/testbed_api.h, src/testbed/testbed_api_peers.c: + peer_stop and service handle for peerstop message: TODO: handler + for peer stop success + +2012-07-18 19:38 LRN + + * [r22767] src/util/os_priority.c: Fix arm-lsocks protocol + violation on W32 + +2012-07-18 17:46 LRN + + * [r22766] src/mesh/Makefile.am: Really try to fix compilation on + Windows + +2012-07-18 15:42 harsha + + * [r22761] src/testbed/gnunet-service-testbed.c: peer create + handling at service + +2012-07-18 15:25 harsha + + * [r22755] src/testbed/test_testbed_api_2peers.c, + src/testbed/testbed_api.c, src/testbed/testbed_api.h, + src/testbed/testbed_api_peers.c: testbed api peer start + +2012-07-18 13:25 harsha + + * [r22749] src/testbed/Makefile.am, + src/testbed/gnunet-testbed-helper.c, + src/testbed/test_testbed_api_2peers.c, src/testbed/testbed_api.c, + src/testbed/testbed_api.h, src/testbed/testbed_api_hosts.c, + src/testbed/testbed_api_hosts.h, src/testbed/testbed_api_peers.c: + API internal function call changes + +2012-07-18 13:03 harsha + + * [r22748] src/include/gnunet_testbed_service.h, + src/testbed/Makefile.am, src/testbed/test_testbed_api.c, + src/testbed/testbed_api.c, src/testbed/valgrind-zlib.supp: fix; + modified testcase for test_testbed_api; valigrind suppression for + zlib + +2012-07-18 11:58 harsha + + * [r22743] src/testbed/testbed_api.c: fix + +2012-07-18 11:56 harsha + + * [r22742] src/testbed/test_gnunet_testbed_helper.c, + src/testbed/testbed_api.c: implemented controller_start success + callback + +2012-07-18 11:33 harsha + + * [r22741] src/testbed/Makefile.am: libz linking + +2012-07-18 08:45 harsha + + * [r22739] src/mesh/Makefile.am: mesh compile + +2012-07-18 08:35 harsha + + * [r22738] src/testbed/Makefile.am, + src/testbed/gnunet-testbed-helper.c, + src/testbed/test_gnunet_testbed_helper.c: fixed + test_gnunet_testbed_helper + +2012-07-18 07:43 harsha + + * [r22737] src/testbed/Makefile.am: fix compile + +2012-07-17 22:25 harsha + + * [r22736] src/include/gnunet_protocols.h, + src/include/gnunet_testbed_service.h, src/testbed/Makefile.am, + src/testbed/gnunet-service-testbed.c, + src/testbed/gnunet-testbed-helper.c, + src/testbed/test_testbed_api_hosts.c, src/testbed/testbed_api.c, + src/testbed/testbed_api_hosts.c, src/testbed/testbed_api_hosts.h, + src/testbed/testbed_helper.h: helper reply with modified config + +2012-07-17 19:09 harsha + + * [r22726] src/include/gnunet_helper_lib.h, + src/testbed/test_testbed_api_hosts.c, src/testbed/testbed_api.c, + src/testbed/testbed_api_hosts.c, src/util/helper.c: helper + exception callback lesser parameters + +2012-07-17 14:59 harsha + + * [r22720] src/include/gnunet_testbed_service.h, + src/testbed/Makefile.am, src/testbed/gnunet-service-testbed.c, + src/testbed/test_testbed_api.c, + src/testbed/test_testbed_api_hosts.c, src/testbed/testbed_api.c, + src/testbed/testbed_api_hosts.c, src/testbed/testbed_api_hosts.h: + helper integration to GNUNET_TESTBED_host_run_() + todo: add controller start callback + with the configuration with which the controller is started + +2012-07-17 12:54 bartpolot + + * [r22715] src/mesh/Makefile.am, src/mesh/gnunet-service-mesh.c, + src/mesh/gnunet-service-mesh_new.c: Added REGEX announce and + discovery to MESH + +2012-07-17 12:12 harsha + + * [r22713] src/testbed/test_gnunet_testbed_helper.c, + src/testbed/testbed_api_hosts.c, src/testbed/testbed_api_hosts.h: + separated helper init message + +2012-07-16 18:58 harsha + + * [r22707] src/dns/gnunet-service-dns.c, + src/exit/gnunet-daemon-exit.c, src/fs/fs_dirmetascan.c, + src/include/gnunet_helper_lib.h, + src/testbed/test_gnunet_testbed_helper.c, + src/transport/plugin_transport_wlan.c, src/util/helper.c, + src/vpn/gnunet-service-vpn.c: extended HELPER api to notify when + child crashes + +2012-07-15 15:07 harsha + + * [r22686] src/include/gnunet_testing_lib-new.h, + src/testing/testing.c: doc + +2012-07-15 14:30 harsha + + * [r22684] src/testbed/gnunet-testbed-helper.c, + src/testbed/test_gnunet_testbed_helper.c: config localization and + service startup + +2012-07-15 14:29 harsha + + * [r22683] src/util: svn ignore + +2012-07-14 23:26 harsha + + * [r22672] src/testbed/gnunet-testbed-helper.c, + src/testbed/testbed_helper.h: init message handling + +2012-07-14 22:54 harsha + + * [r22668] src/include/gnunet_disk_lib.h: doc + +2012-07-14 18:39 harsha + + * [r22660] src/testbed/gnunet-testbed-helper.c, + src/testbed/test_gnunet_testbed_helper.c: relaxed time for + shutdown + +2012-07-14 09:44 harsha + + * [r22649] src/include/gnunet_protocols.h: testbed helper init + message + +2012-07-14 01:15 harsha + + * [r22648] src/testbed, src/testbed/Makefile.am, + src/testbed/test_gnunet_testbed_helper.c: testbed helper testcase + +2012-07-13 16:37 harsha + + * [r22640] src/testbed, src/testbed/Makefile.am, + src/testbed/gnunet-testbed-helper.c, + src/testbed/testbed_helper.h: testbed helper + +2012-07-13 16:24 LRN + + * [r22639] src/transport/Makefile.am: Fix transport makefile + +2012-07-13 16:24 LRN + + * [r22638] src/util/os_priority.c: W32: correct handling of crazy + W32 process quirks + +2012-07-13 16:24 LRN + + * [r22637] src/util/network.c: Handle peek errors more + appropriately in w32 select + +2012-07-13 16:24 LRN + + * [r22636] src/util/network.c: Safer handling of corner-cases in + w32 select + +2012-07-13 00:39 LRN + + * [r22625] src/util/disk.c: Demote WARNING to INFO, preserve errno + +2012-07-12 21:08 LRN + + * [r22624] contrib/terminate.py.in: Missing file + +2012-07-12 21:06 LRN + + * [r22623] contrib/Makefile.am, contrib/gnunet_janitor.py.in, + src/include/winproc.h, src/util/os_priority.c, src/util/win.cc: + W32: safer process termination + +2012-07-12 11:50 harsha + + * [r22616] src/testbed/gnunet-service-testbed.c, + src/testbed/testbed_api.c, src/testbed/testbed_api_hosts.c, + src/testbed/testbed_api_hosts.h: implemented controller error + callback + +2012-07-11 20:19 LRN + + * [r22611] src/util/w32cat.c: A small fix for W32cat + +2012-07-11 15:36 szengel + + * [r22610] src/regex/regex.c: bugfix + +2012-07-11 15:06 harsha + + * [r22607] src/include/gnunet_testbed_service.h, + src/testbed/Makefile.am, src/testbed/gnunet-service-testbed.c, + src/testbed/test_testbed_api.c, + src/testbed/test_testbed_api_hosts.c, src/testbed/testbed_api.c: + fixes for controller_start() API changes + +2012-07-11 08:05 LRN + + * [r22598] src/gns/gns.conf.in: Make gns port non-unix-only + +2012-07-10 14:33 wachs + + * [r22594] src/transport/plugin_transport_http_server.c: improved + server disconnect + +2012-07-09 18:48 harsha + + * [r22577] src/testbed/gnunet-service-testbed.c: more fixes + +2012-07-09 15:18 szengel + + * [r22575] src/regex/regex.c: regex: fixed iterating over the + initial states. + +2012-07-09 15:18 szengel + + * [r22574] src/regex/test_regex_iterate_api.c: regex: fixed + iterating over the initial states + +2012-07-08 20:28 harsha + + * [r22546] src/testbed/testbed_api.c, src/testbed/testbed_api.h, + src/testbed/testbed_api_peers.c, src/testbed/testbed_api_peers.h: + operation and peer_destroy + +2012-07-07 16:12 harsha + + * [r22540] src/include/gnunet_testing_lib-new.h, + src/testing/testing.c: testing doc + +2012-07-06 22:49 harsha + + * [r22535] src/testbed/testbed_api_peers.c: testbed peer_create () + +2012-07-06 22:36 harsha + + * [r22534] src/testbed/testbed.h, src/testbed/testbed_api.c, + src/testbed/testbed_api.h: function exports from testbed_api + +2012-07-06 15:29 wachs + + * [r22532] src/transport/transport_api.c: undo + +2012-07-06 15:24 wachs + + * [r22530] src/transport/Makefile.am, + src/transport/gnunet-service-transport_neighbours.c, + src/transport/test_quota_compliance.c, + src/transport/test_quota_compliance_wlan_asymmetric_peer1.conf, + src/transport/test_quota_compliance_wlan_asymmetric_peer2.conf, + src/transport/test_quota_compliance_wlan_peer1.conf, + src/transport/test_quota_compliance_wlan_peer2.conf, + src/transport/transport_api.c: quota tests for wlan + +2012-07-06 15:13 harsha + + * [r22529] src/testbed, src/testbed/Makefile.am, + src/testbed/gnunet-service-testbed.c, + src/testbed/test_testbed_api.c, + src/testbed/test_testbed_api.conf, src/testbed/testbed_api.c: + testbed api test case and fixes + +2012-07-06 14:30 szengel + + * [r22527] src/regex/regex.c, src/regex/regex_graph.c: regex: + iterating over the initial states + +2012-07-06 08:49 wachs + + * [r22516] src/transport/gnunet-transport.c: fixing assertion: + cancel transmit ready on disconnect + +2012-07-05 22:29 harsha + + * [r22509] src/testbed/testbed_api_hosts.c: fixes + +2012-07-05 21:14 harsha + + * [r22508] src/testbed/gnunet-service-testbed.c: routing controller + link messages + +2012-07-05 19:59 harsha + + * [r22507] src/testbed/gnunet-service-testbed.c: direct links to + slave controllers + +2012-07-05 14:29 szengel + + * [r22500] src/include/gnunet_regex_lib.h, src/regex/regex_graph.c: + regex: added verbose flag to graph api. + +2012-07-05 09:46 szengel + + * [r22492] src/regex/regex.c, src/regex/regex_graph.c: regex: fixed + static analyzer warnings + +2012-07-05 07:57 grothoff + + * [r22488] src/namestore/namestore_common.c: LRN: More logging for + namespace comparison: + Changes GNUNET_NAMESTORE_records_cmp from a simple if statement + to a + chain of if statements, each of which will log the reason + comparison + failed before returning FALSE, making it obvious why comparison + failed. + +2012-07-04 15:46 szengel + + * [r22482] src/include/gnunet_regex_lib.h, src/regex/regex.c, + src/regex/test_regex_iterate_api.c: regex: actually checking the + proof, fixes + +2012-07-04 13:54 szengel + + * [r22478] src/regex/Makefile.am, src/regex/regex.c, + src/regex/regex_graph.c, src/regex/regex_internal.h, + src/regex/test_regex_eval_api.c, src/regex/test_regex_proofs.c: + Summary: regex cleanup and bugfixes + Author: szengel + +2012-07-02 21:42 harsha + + * [r22447] src/transport/transport.conf.in: ignoring ACCEPT_FROM + for transport plugins while testing + +2012-07-02 21:39 harsha + + * [r22446] src/testing/test_testing_defaults.conf, + src/testing/test_testing_portreservation.c, + src/testing/testing.c: added TESTING_IGNORE_KEYS + +2012-07-02 14:56 wachs + + * [r22441] src/transport/Makefile.am, + src/transport/test_transport_testing.c, + src/transport/test_transport_testing_restart.c, + src/transport/test_transport_testing_startstop.c, + src/transport/transport-testing.c, + src/transport/transport-testing.h: porting transport testing to + new testing lib (mantis 2453) + +2012-07-02 14:34 wachs + + * [r22440] src/testing/testing.c: workaround for mantis 2476 + +2012-07-02 13:23 szengel + + * [r22435] src/regex/regex.c: fixed leaks + +2012-07-02 12:25 szengel + + * [r22430] src/regex/regex.c: removed unnecessary debug statements + +2012-07-02 12:22 szengel + + * [r22429] src/regex/regex.c, src/regex/test_regex_eval_api.c, + src/regex/test_regex_iterate_api.c, + src/regex/test_regex_proofs.c: regex bugfixes + +2012-07-02 07:52 wachs + + * [r22422] src/transport/gnunet-service-transport_neighbours.c: fix + for mantis 2445 & 2471 + +2012-07-01 22:08 harsha + + * [r22420] src/testbed/gnunet-service-testbed.c: routing + +2012-07-01 15:37 harsha + + * [r22413] src/testbed/gnunet-service-testbed.c, + src/testbed/testbed.h, src/testbed/testbed_api.c: link controller + handler + +2012-06-29 16:43 wachs + + * [r22394] src/transport/gnunet-service-transport_neighbours.c: fix + for mantis 2445 + +2012-06-29 15:12 harsha + + * [r22390] src/testbed/testbed.h, src/testbed/testbed_api.c: + testbed api: controller link message + +2012-06-29 13:30 wachs + + * [r22381] src/transport/plugin_transport_udp.c, + src/transport/transport.conf.in: improved error messages when no + network connectivity and fancy interval time + +2012-06-29 12:25 wachs + + * [r22378] src/transport/plugin_transport_udp_broadcasting.c, + src/transport/transport.conf.in: do not print error msg when we + have no network connectivity + +2012-06-28 12:41 szengel + + * [r22363] src/regex/regex.c: cleanup, fixes + +2012-06-27 16:13 szengel + + * [r22353] src/include/gnunet_regex_lib.h, src/regex/Makefile.am, + src/regex/regex.c, src/regex/regex_internal.h, + src/regex/regex_random.c, src/regex/test_regex_eval_api.c, + src/regex/test_regex_proofs.c: new and improved tests + +2012-06-27 15:34 dold + + * [r22352] src/peerinfo/peerinfo.conf.in, + src/testing/gnunet-testing-run-service.c: added JAVAPORT to + peerinfo config, fix in gnunet-testing-run-service.c + +2012-06-27 12:24 harsha + + * [r22345] src/include/gnunet_configuration_lib.h, + src/util/configuration.c: configuration serialization + +2012-06-26 19:07 harsha + + * [r22313] src/include/gnunet_protocols.h, + src/include/gnunet_testbed_service.h, + src/testbed/gnunet-service-testbed.c, src/testbed/testbed.h, + src/testbed/testbed_api.c, src/testbed/testbed_api_hosts.c, + src/testbed/testbed_api_hosts.h: testbed host registration + +2012-06-26 14:45 wachs + + * [r22301] src/transport/gnunet-service-transport_neighbours.c: fix + for 0002463 + +2012-06-26 13:52 szengel + + * [r22298] src/include/gnunet_regex_lib.h, src/regex/regex.c, + src/regex/test_regex_eval_api.c, src/regex/test_regex_proofs.c: + doxygen fixes + +2012-06-26 13:01 wachs + + * [r22293] src/transport/gnunet-service-transport_neighbours.c: fix + for mantis 0002462 + +2012-06-25 22:36 grothoff + + * [r22283] src/include/gnunet_namestore_service.h, + src/namestore/gnunet-namestore.c, + src/namestore/gnunet-service-namestore.c, + src/namestore/namestore.conf.in, src/namestore/namestore_api.c, + src/namestore/plugin_namestore_postgres.c, + src/namestore/test_namestore_api.c, + src/namestore/test_namestore_api.conf, + src/namestore/test_namestore_api_create.c, + src/namestore/test_namestore_api_create_update.c, + src/namestore/test_namestore_api_lookup.c, + src/namestore/test_namestore_api_lookup_specific_type.c, + src/namestore/test_namestore_api_put.c, + src/namestore/test_namestore_api_remove.c, + src/namestore/test_namestore_api_remove_not_existing_record.c, + src/namestore/test_namestore_api_zone_iteration.c, + src/namestore/test_namestore_api_zone_iteration_specific_zone.c, + src/namestore/test_namestore_api_zone_iteration_stop.c, + src/namestore/test_namestore_api_zone_to_name.c, + src/namestore/test_plugin_namestore.c, + src/namestore/test_plugin_namestore_postgres.conf: trying to fix + #2458, largely works + +2012-06-25 16:16 szengel + + * [r22275] src/regex/regex.c, src/regex/test_regex_iterate_api.c: + regex bugfixes and optimizations + +2012-06-25 11:15 szengel + + * [r22269] src/regex/Makefile.am, src/regex/regex.c, + src/regex/test_regex_proofs.c: new test for regex + +2012-06-25 10:36 szengel + + * [r22268] src/regex/regex.c: regex optimizations + +2012-06-25 08:33 szengel + + * [r22266] src/regex/regex.c, src/regex/test_regex_eval_api.c, + src/regex/test_regex_iterate_api.c: regex simplification wip + +2012-06-22 00:37 schanzen + + * [r22197] src/gns/Makefile.am, + src/gns/gnunet-service-gns_resolver.c, + src/gns/test_gns_simple_srv_lookup.c, + src/include/gnunet_dnsparser_lib.h, + src/include/gnunet_gns_service.h: Added proper SRV handling and + test + +2012-06-21 19:03 szengel + + * [r22193] src/regex/test_regex_eval_api.c: Updated testcase to use + fewer random regexes. + +2012-06-20 19:24 harsha + + * [r22173] src/lockmanager/Makefile.am, + src/lockmanager/gnunet-service-lockmanager.c, + src/lockmanager/lockmanager_api.c, + src/lockmanager/test_lockmanager_api.c, + src/lockmanager/test_lockmanager_api_acquireretry.c, + src/lockmanager/test_lockmanager_api_lockrelease.c, + src/lockmanager/test_lockmanager_api_servercrash.c: lockmanager + testcase new testing library + +2012-06-20 10:53 wachs + + * [r22139] src/namestore/namestore_api.c: clean up and + documentation for namestor API + +2012-06-19 21:44 grothoff + + * [r22121] src/include/gnunet_strings_lib.h, src/util/strings.c: + adding API for parsing absolute time + +2012-06-19 12:40 harsha + + * [r22108] src/testbed, src/testbed/Makefile.am, + src/testbed/test_testbed_api.conf, + src/testbed/test_testbed_api_hosts.c, + src/testbed/testbed_api_hosts.c: testbed_api_hosts test cases + +2012-06-19 09:39 wachs + + * [r22104] src/ats/gnunet-service-ats_addresses.c: fix a major bug: + delete session for unknown address (addr==NULL, length==0) + +2012-06-19 08:04 wachs + + * [r22099] src/ats/Makefile.am, + src/ats/test_ats_api_scheduling_destroy_session.c: new test + deleting a session using the plugin_env_session_end way + (addr=NULL,addr_length=0) + session + this fails atm and is a bug + +2012-06-18 15:00 grothoff + + * [r22081] doc/man/Makefile.am, doc/man/gnunet-auto-share.1, + doc/man/gnunet-publish.1, src/fs/fs.conf.in, + src/include/gnunet_scheduler_lib.h: adding man page for + gnunet-auto-share, updating man page for gnunet-publish + +2012-06-16 21:47 schanzen + + * [r22053] src/gns/gnunet-service-gns_resolver.c: properly handle + CNAME as specified in rfc1034#section-3.6.2 + +2012-06-16 16:53 grothoff + + * [r22043] src/include/gnunet_hello_lib.h, + src/include/gnunet_peer_lib.h: fix compilation with c++ + +2012-06-16 09:44 schanzen + + * [r22036] src/gns/Makefile.am, + src/gns/gnunet-service-gns_resolver.c, + src/gns/gnunet-service-gns_resolver.h, + src/include/gnunet_gns_service.h: Add VPN resolution + +2012-06-15 15:28 harsha + + * [r22027] src/stream/Makefile.am: added test_stream_big to make + check tests + +2012-06-15 15:25 harsha + + * [r22025] src/stream/stream_api.c, src/stream/test_stream_big.c: + remvod verbose debugging in stream api; fixed warning in + stream_big test case + +2012-06-15 15:19 harsha + + * [r22024] src/stream/stream_api.c, src/stream/test_stream_big.c: + stream misc fixing + +2012-06-14 09:52 wachs + + * [r21994] src/ats/ats_api_scheduling.c: fixing deletion of unknown + addresses + +2012-06-14 08:51 wachs + + * [r21987] src/util/test_common_logging_runtime_loglevels.c: fix + for segfault + +2012-06-14 08:09 harsha + + * [r21985] src/testbed/Makefile.am, + src/testbed/gnunet-service-testbed.c: handling add host + +2012-06-13 12:41 dold + + * [r21964] src/testing/gnunet-testing-run-service.c: changed how + gnunet-testing-run-service communicates over stdin/stdout + +2012-06-13 11:42 szengel + + * [r21952] src/regex/regex.c, src/regex/test_regex_iterate_api.c: + more regex simplifications. fixes. + +2012-06-12 23:01 dold + + * [r21937] src/testing/gnunet-testing-run-service.c: fix + +2012-06-12 22:37 dold + + * [r21936] src/testing/gnunet-testing-run-service.c: fixed + indentation + +2012-06-12 22:30 dold + + * [r21935] src/testing/gnunet-testing-run-service.c: fix + +2012-06-12 22:26 dold + + * [r21934] src/include/gnunet_testing_lib-new.h, + src/testing/Makefile.am, + src/testing/gnunet-testing-run-service.c, src/testing/testing.c: + added a command line tool for running and controlling services + for testing + +2012-06-12 21:12 harsha + + * [r21932] src/testbed, src/testbed/testbed_api_hosts.c: fixed + static to non static + +2012-06-12 20:23 harsha + + * [r21930] configure.ac, src/testbed, src/testbed/Makefile.am, + src/testbed/gnunet-service-testbed.c, src/testbed/testbed.conf, + src/testbed/testbed.conf.in, src/testbed/testbed.h: testbed + service build system + +2012-06-12 12:58 bartpolot + + * [r21914] src/mesh/gnunet-service-mesh.c: Removed core queue + requirements from mesh (backporting mesh_new) + +2012-06-12 12:43 wachs + + * [r21912] src/core/gnunet-core.c: exclude notification about + myself + +2012-06-12 11:24 wachs + + * [r21910] src/transport/gnunet-transport.c: clean up + +2012-06-12 11:24 wachs + + * [r21909] src/core/gnunet-core.c: core monitor mode + +2012-06-12 11:17 schanzen + + * [r21908] src/gns/Makefile.am, src/gns/gnunet-gns-proxy-setup-ca: + autoimport CA + +2012-06-12 10:21 grothoff + + * [r21903] src/namestore/plugin_namestore_postgres.c: completed + postgres plugin for namestore service + +2012-06-12 10:04 schanzen + + * [r21902] src/gns/createProxyCa.sh, src/gns/gns.conf.in, + src/gns/gnunet-gns-proxy.c: Script for CA generation. Making it + easy with config option + +2012-06-12 09:02 wachs + + * [r21900] src/transport/gnunet-transport.c: monitor mode + implemented correctly + +2012-06-11 15:10 szengel + + * [r21892] src/regex/regex.c, src/regex/test_regex_eval_api.c, + src/regex/test_regex_iterate_api.c: simplified regex/proof + generation + +2012-06-11 14:59 schanzen + + * [r21890] src/gns/gns.conf.in, src/gns/gns.h, src/gns/gns_api.c, + src/gns/gnunet-gns-proxy.c, src/gns/gnunet-gns.c, + src/gns/gnunet-service-gns.c, src/gns/test_gns_pseu_shorten.c, + src/include/gnunet_gns_service.h: new API for shorten key + +2012-06-11 09:54 grothoff + + * [r21873] README, configure.ac, src/gns/Makefile.am: adding check + for gnutls + +2012-06-10 22:47 grothoff + + * [r21867] src/arm/gnunet-arm.c, src/ats/perf_ats_mlp.c, + src/chat/gnunet-chat.c, src/core/gnunet-core.c, + src/dht/gnunet-dht-get.c, src/dht/gnunet-dht-monitor.c, + src/dht/gnunet-dht-put.c, src/dns/gnunet-dns-monitor.c, + src/dns/gnunet-dns-redirector.c, src/exit/gnunet-daemon-exit.c, + src/fs/gnunet-directory.c, src/fs/gnunet-download.c, + src/fs/gnunet-fs.c, src/fs/gnunet-helper-fs-publish.c, + src/fs/gnunet-pseudonym.c, src/fs/gnunet-publish.c, + src/fs/gnunet-search.c, src/fs/gnunet-unindex.c, + src/gns/gnunet-gns-fcfsd.c, src/gns/gnunet-gns-lookup.c, + src/gns/gnunet-gns-proxy.c, src/gns/gnunet-gns.c, + src/hostlist/gnunet-daemon-hostlist.c, + src/include/gnunet_strings_lib.h, + src/integration-tests/connection_watchdog.c, + src/namestore/gnunet-namestore.c, src/nat/gnunet-nat-server.c, + src/nse/gnunet-nse-profiler.c, + src/peerinfo-tool/gnunet-peerinfo.c, src/pt/gnunet-daemon-pt.c, + src/statistics/gnunet-statistics.c, + src/template/gnunet-template.c, src/testing_old/gnunet-testing.c, + src/topology/gnunet-daemon-topology.c, + src/transport/gnunet-transport.c, src/util/gnunet-resolver.c, + src/util/gnunet-rsa.c, src/util/program.c, src/util/strings.c, + src/vpn/gnunet-vpn.c: LRN: new utf8 argv converter for W32, + converting strings on command-line to UTF-8 for all command-line + tools. + +2012-06-10 22:44 grothoff + + * [r21866] src/testing_old/testing_group.c: LRN: + Fix-test_group-interval.patch: + Just a wild guess - you wanted to find ids either inside the + interval + or outside of it. + Although maybe you should have used <= and >= in one of the + conditions + then? + CG: only mrwiggles knows the truth. Anyway, old testing will be + gone soon enough.... + +2012-06-10 22:42 grothoff + + * [r21865] src/util/crypto_random.c: LRN: fix RAND_MAX on W32: + MinGW stdlib.h defines it to 0x7FFF, but our implementation is + better. + +2012-06-07 07:05 grothoff + + * [r21794] src/util/network.c: LRN: new select wrapper for W32 + which avoids busy-waiting + +2012-06-06 21:12 grothoff + + * [r21790] README: bumping required curl version to 7.21.3 + +2012-06-06 15:00 szengel + + * [r21788] src/regex/regex.c: removed unnecessary brackets + +2012-06-06 14:35 szengel + + * [r21787] src/include/gnunet_regex_lib.h, src/regex/regex.c, + src/regex/test_regex_eval_api.c: Test for computed regex. + +2012-06-06 13:05 szengel + + * [r21782] src/regex/regex.c: even better proofs + +2012-06-06 12:10 grothoff + + * [r21780] src/testing/testing_new.c: fix arm termination on W32 by + enabling signalling pipe to be used + +2012-06-06 10:54 szengel + + * [r21774] src/regex/regex.c, src/regex/test_regex_iterate_api.c: + Better proofs + +2012-06-04 13:59 szengel + + * [r21760] src/regex/regex.c: assigning proofs + +2012-06-04 13:30 szengel + + * [r21759] src/regex/regex.c, src/regex/test_regex_iterate_api.c: + Towards new proof algorithm + +2012-06-04 09:31 grothoff + + * [r21752] src/include/platform.h: #2404, patch 03: include net/if + on GNU + +2012-06-04 09:31 grothoff + + * [r21751] src/util/disk.c: #2404, patch 02: include sys/vfs on GNU + +2012-06-04 09:30 grothoff + + * [r21750] configure.ac: #2404, patch 01: configure support for GNU + Hurd + 2012-06-02 14:39 grothoff * [r21729] configure.ac, src/include/plibc.h, src/util/server.c, diff --git a/INSTALL b/INSTALL index 7d1c323..6e90e07 100644 --- a/INSTALL +++ b/INSTALL @@ -1,8 +1,8 @@ Installation Instructions ************************* -Copyright (C) 1994, 1995, 1996, 1999, 2000, 2001, 2002, 2004, 2005, -2006, 2007, 2008, 2009 Free Software Foundation, Inc. +Copyright (C) 1994-1996, 1999-2002, 2004-2012 Free Software Foundation, +Inc. Copying and distribution of this file, with or without modification, are permitted in any medium without royalty provided the copyright @@ -226,6 +226,11 @@ order to use an ANSI C compiler: and if that doesn't work, install pre-built binaries of GCC for HP-UX. + HP-UX `make' updates targets which have the same time stamps as +their prerequisites, which makes it generally unusable when shipped +generated files such as `configure' are involved. Use GNU `make' +instead. + On OSF/1 a.k.a. Tru64, some versions of the default C compiler cannot parse its `' header file. The option `-nodtk' can be used as a workaround. If GNU CC is not installed, it is therefore recommended @@ -304,9 +309,10 @@ causes the specified `gcc' to be used as the C compiler (unless it is overridden in the site shell script). Unfortunately, this technique does not work for `CONFIG_SHELL' due to -an Autoconf bug. Until the bug is fixed you can use this workaround: +an Autoconf limitation. Until the limitation is lifted, you can use +this workaround: - CONFIG_SHELL=/bin/bash /bin/bash ./configure CONFIG_SHELL=/bin/bash + CONFIG_SHELL=/bin/bash ./configure CONFIG_SHELL=/bin/bash `configure' Invocation ====================== @@ -362,4 +368,3 @@ operates. `configure' also accepts some other, not widely useful, options. Run `configure --help' for more details. - diff --git a/Makefile.am b/Makefile.am index 1c804cb..39a37a9 100644 --- a/Makefile.am +++ b/Makefile.am @@ -11,7 +11,7 @@ gnunetincludedir = $(includedir)/gnunet gnunetinclude_HEADERS = gnunet_config.h docdir = $(datadir)/doc/gnunet/ -doc_DATA = COPYING +doc_DATA = COPYING README ACLOCAL_AMFLAGS = -I m4 diff --git a/Makefile.in b/Makefile.in index 015c1d7..adc5c1f 100644 --- a/Makefile.in +++ b/Makefile.in @@ -1,9 +1,9 @@ -# Makefile.in generated by automake 1.11.1 from Makefile.am. +# Makefile.in generated by automake 1.11.6 from Makefile.am. # @configure_input@ # Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, -# 2003, 2004, 2005, 2006, 2007, 2008, 2009 Free Software Foundation, -# Inc. +# 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Free Software +# Foundation, Inc. # This Makefile.in is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. @@ -17,6 +17,23 @@ VPATH = @srcdir@ +am__make_dryrun = \ + { \ + am__dry=no; \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + echo 'am--echo: ; @echo "AM" OK' | $(MAKE) -f - 2>/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } pkgdatadir = $(datadir)/@PACKAGE@ pkgincludedir = $(includedir)/@PACKAGE@ pkglibdir = $(libdir)/@PACKAGE@ @@ -45,14 +62,15 @@ DIST_COMMON = README $(am__configure_deps) $(gnunetinclude_HEADERS) \ ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 am__aclocal_m4_deps = $(top_srcdir)/m4/absolute-header.m4 \ $(top_srcdir)/m4/align.m4 $(top_srcdir)/m4/argz.m4 \ - $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/iconv.m4 \ - $(top_srcdir)/m4/lib-ld.m4 $(top_srcdir)/m4/lib-link.m4 \ - $(top_srcdir)/m4/lib-prefix.m4 $(top_srcdir)/m4/libcurl.m4 \ - $(top_srcdir)/m4/libgcrypt.m4 $(top_srcdir)/m4/libtool.m4 \ - $(top_srcdir)/m4/libunistring.m4 $(top_srcdir)/m4/ltdl.m4 \ - $(top_srcdir)/m4/ltoptions.m4 $(top_srcdir)/m4/ltsugar.m4 \ - $(top_srcdir)/m4/ltversion.m4 $(top_srcdir)/m4/lt~obsolete.m4 \ - $(top_srcdir)/m4/nls.m4 $(top_srcdir)/m4/po.m4 \ + $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/glib-2.0.m4 \ + $(top_srcdir)/m4/iconv.m4 $(top_srcdir)/m4/lib-ld.m4 \ + $(top_srcdir)/m4/lib-link.m4 $(top_srcdir)/m4/lib-prefix.m4 \ + $(top_srcdir)/m4/libcurl.m4 $(top_srcdir)/m4/libgcrypt.m4 \ + $(top_srcdir)/m4/libtool.m4 $(top_srcdir)/m4/libunistring.m4 \ + $(top_srcdir)/m4/ltdl.m4 $(top_srcdir)/m4/ltoptions.m4 \ + $(top_srcdir)/m4/ltsugar.m4 $(top_srcdir)/m4/ltversion.m4 \ + $(top_srcdir)/m4/lt~obsolete.m4 $(top_srcdir)/m4/nls.m4 \ + $(top_srcdir)/m4/pkg.m4 $(top_srcdir)/m4/po.m4 \ $(top_srcdir)/m4/progtest.m4 $(top_srcdir)/acinclude.m4 \ $(top_srcdir)/configure.ac am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ @@ -63,11 +81,11 @@ mkinstalldirs = $(install_sh) -d CONFIG_HEADER = gnunet_config.h CONFIG_CLEAN_FILES = CONFIG_CLEAN_VPATH_FILES = -AM_V_GEN = $(am__v_GEN_$(V)) -am__v_GEN_ = $(am__v_GEN_$(AM_DEFAULT_VERBOSITY)) +AM_V_GEN = $(am__v_GEN_@AM_V@) +am__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@) am__v_GEN_0 = @echo " GEN " $@; -AM_V_at = $(am__v_at_$(V)) -am__v_at_ = $(am__v_at_$(AM_DEFAULT_VERBOSITY)) +AM_V_at = $(am__v_at_@AM_V@) +am__v_at_ = $(am__v_at_@AM_DEFAULT_V@) am__v_at_0 = @ SOURCES = DIST_SOURCES = @@ -78,6 +96,11 @@ RECURSIVE_TARGETS = all-recursive check-recursive dvi-recursive \ install-pdf-recursive install-ps-recursive install-recursive \ installcheck-recursive installdirs-recursive pdf-recursive \ ps-recursive uninstall-recursive +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac am__vpath_adj_setup = srcdirstrip=`echo "$(srcdir)" | sed 's|.|.|g'`; am__vpath_adj = case $$p in \ $(srcdir)/*) f=`echo "$$p" | sed "s|^$$srcdirstrip/||"`;; \ @@ -99,6 +122,12 @@ am__nobase_list = $(am__nobase_strip_setup); \ am__base_list = \ sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \ sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g' +am__uninstall_files_from_dir = { \ + test -z "$$files" \ + || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \ + || { echo " ( cd '$$dir' && rm -f" $$files ")"; \ + $(am__cd) "$$dir" && rm -f $$files; }; \ + } am__installdirs = "$(DESTDIR)$(docdir)" \ "$(DESTDIR)$(gnunetincludedir)" DATA = $(doc_DATA) @@ -115,9 +144,11 @@ DISTFILES = $(DIST_COMMON) $(DIST_SOURCES) $(TEXINFOS) $(EXTRA_DIST) distdir = $(PACKAGE)-$(VERSION) top_distdir = $(distdir) am__remove_distdir = \ - { test ! -d "$(distdir)" \ - || { find "$(distdir)" -type d ! -perm -200 -exec chmod u+w {} ';' \ - && rm -fr "$(distdir)"; }; } + if test -d "$(distdir)"; then \ + find "$(distdir)" -type d ! -perm -200 -exec chmod u+w {} ';' \ + && rm -rf "$(distdir)" \ + || { sleep 5 && rm -rf "$(distdir)"; }; \ + else :; fi am__relativize = \ dir0=`pwd`; \ sed_first='s,^\([^/]*\)/.*$$,\1,'; \ @@ -146,6 +177,8 @@ am__relativize = \ DIST_ARCHIVES = $(distdir).tar.gz GZIP_ENV = --best distuninstallcheck_listfiles = find . -type f -print +am__distuninstallcheck_listfiles = $(distuninstallcheck_listfiles) \ + | sed 's|^\./|$(prefix)/|' | grep -v '$(infodir)/dir$$' distcleancheck_listfiles = find . -type f -print ACLOCAL = @ACLOCAL@ AMTAR = @AMTAR@ @@ -182,6 +215,10 @@ EXEEXT = @EXEEXT@ EXT_LIBS = @EXT_LIBS@ EXT_LIB_PATH = @EXT_LIB_PATH@ FGREP = @FGREP@ +GLIB_CFLAGS = @GLIB_CFLAGS@ +GLIB_GENMARSHAL = @GLIB_GENMARSHAL@ +GLIB_LIBS = @GLIB_LIBS@ +GLIB_MKENUMS = @GLIB_MKENUMS@ GMSGFMT = @GMSGFMT@ GMSGFMT_015 = @GMSGFMT_015@ GNUNETDNS_GROUP = @GNUNETDNS_GROUP@ @@ -192,6 +229,7 @@ GN_LIBINTL = @GN_LIBINTL@ GN_LIB_LDFLAGS = @GN_LIB_LDFLAGS@ GN_PLUGIN_LDFLAGS = @GN_PLUGIN_LDFLAGS@ GN_USER_HOME_DIR = @GN_USER_HOME_DIR@ +GOBJECT_QUERY = @GOBJECT_QUERY@ GREP = @GREP@ HAVE_LIBUNISTRING = @HAVE_LIBUNISTRING@ INCLTDL = @INCLTDL@ @@ -214,6 +252,8 @@ LIBCURL_CPPFLAGS = @LIBCURL_CPPFLAGS@ LIBGCRYPT_CFLAGS = @LIBGCRYPT_CFLAGS@ LIBGCRYPT_CONFIG = @LIBGCRYPT_CONFIG@ LIBGCRYPT_LIBS = @LIBGCRYPT_LIBS@ +LIBGTOP_CFLAGS = @LIBGTOP_CFLAGS@ +LIBGTOP_LIBS = @LIBGTOP_LIBS@ LIBICONV = @LIBICONV@ LIBINTL = @LIBINTL@ LIBLTDL = @LIBLTDL@ @@ -235,6 +275,7 @@ LT_CONFIG_H = @LT_CONFIG_H@ LT_DLLOADERS = @LT_DLLOADERS@ LT_DLPREOPEN = @LT_DLPREOPEN@ MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ MKDIR_P = @MKDIR_P@ MONKEYPREFIX = @MONKEYPREFIX@ MSGFMT = @MSGFMT@ @@ -244,6 +285,7 @@ MYSQL_CPPFLAGS = @MYSQL_CPPFLAGS@ MYSQL_LDFLAGS = @MYSQL_LDFLAGS@ NM = @NM@ NMEDIT = @NMEDIT@ +NSS_DIR = @NSS_DIR@ OBJC = @OBJC@ OBJCDEPMODE = @OBJCDEPMODE@ OBJCFLAGS = @OBJCFLAGS@ @@ -259,6 +301,7 @@ PACKAGE_TARNAME = @PACKAGE_TARNAME@ PACKAGE_URL = @PACKAGE_URL@ PACKAGE_VERSION = @PACKAGE_VERSION@ PATH_SEPARATOR = @PATH_SEPARATOR@ +PKG_CONFIG = @PKG_CONFIG@ POSTGRES_CPPFLAGS = @POSTGRES_CPPFLAGS@ POSTGRES_LDFLAGS = @POSTGRES_LDFLAGS@ POSUB = @POSUB@ @@ -290,6 +333,7 @@ abs_builddir = @abs_builddir@ abs_srcdir = @abs_srcdir@ abs_top_builddir = @abs_top_builddir@ abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ ac_ct_CC = @ac_ct_CC@ ac_ct_CXX = @ac_ct_CXX@ ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ @@ -312,6 +356,7 @@ datarootdir = @datarootdir@ docdir = $(datadir)/doc/gnunet/ dvidir = @dvidir@ exec_prefix = @exec_prefix@ +gitcommand = @gitcommand@ host = @host@ host_alias = @host_alias@ host_cpu = @host_cpu@ @@ -325,7 +370,6 @@ libdir = @libdir@ libexecdir = @libexecdir@ localedir = @localedir@ localstatedir = @localstatedir@ -lt_ECHO = @lt_ECHO@ ltdl_LIBOBJS = @ltdl_LIBOBJS@ ltdl_LTLIBOBJS = @ltdl_LTLIBOBJS@ mandir = @mandir@ @@ -343,6 +387,7 @@ sbindir = @sbindir@ sharedstatedir = @sharedstatedir@ srcdir = @srcdir@ subdirs = @subdirs@ +svnversioncommand = @svnversioncommand@ sys_symbol_underscore = @sys_symbol_underscore@ sysconfdir = @sysconfdir@ target = @target@ @@ -363,13 +408,13 @@ EXTRA_DIST = \ gnunetincludedir = $(includedir)/gnunet gnunetinclude_HEADERS = gnunet_config.h -doc_DATA = COPYING +doc_DATA = COPYING README ACLOCAL_AMFLAGS = -I m4 all: gnunet_config.h $(MAKE) $(AM_MAKEFLAGS) all-recursive .SUFFIXES: -am--refresh: +am--refresh: Makefile @: $(srcdir)/Makefile.in: $(srcdir)/Makefile.am $(am__configure_deps) @for dep in $?; do \ @@ -405,10 +450,8 @@ $(ACLOCAL_M4): $(am__aclocal_m4_deps) $(am__aclocal_m4_deps): gnunet_config.h: stamp-h1 - @if test ! -f $@; then \ - rm -f stamp-h1; \ - $(MAKE) $(AM_MAKEFLAGS) stamp-h1; \ - else :; fi + @if test ! -f $@; then rm -f stamp-h1; else :; fi + @if test ! -f $@; then $(MAKE) $(AM_MAKEFLAGS) stamp-h1; else :; fi stamp-h1: $(srcdir)/gnunet_config.h.in $(top_builddir)/config.status @rm -f stamp-h1 @@ -431,8 +474,11 @@ distclean-libtool: -rm -f libtool config.lt install-docDATA: $(doc_DATA) @$(NORMAL_INSTALL) - test -z "$(docdir)" || $(MKDIR_P) "$(DESTDIR)$(docdir)" @list='$(doc_DATA)'; test -n "$(docdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(docdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(docdir)" || exit 1; \ + fi; \ for p in $$list; do \ if test -f "$$p"; then d=; else d="$(srcdir)/"; fi; \ echo "$$d$$p"; \ @@ -446,13 +492,14 @@ uninstall-docDATA: @$(NORMAL_UNINSTALL) @list='$(doc_DATA)'; test -n "$(docdir)" || list=; \ files=`for p in $$list; do echo $$p; done | sed -e 's|^.*/||'`; \ - test -n "$$files" || exit 0; \ - echo " ( cd '$(DESTDIR)$(docdir)' && rm -f" $$files ")"; \ - cd "$(DESTDIR)$(docdir)" && rm -f $$files + dir='$(DESTDIR)$(docdir)'; $(am__uninstall_files_from_dir) install-gnunetincludeHEADERS: $(gnunetinclude_HEADERS) @$(NORMAL_INSTALL) - test -z "$(gnunetincludedir)" || $(MKDIR_P) "$(DESTDIR)$(gnunetincludedir)" @list='$(gnunetinclude_HEADERS)'; test -n "$(gnunetincludedir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(gnunetincludedir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(gnunetincludedir)" || exit 1; \ + fi; \ for p in $$list; do \ if test -f "$$p"; then d=; else d="$(srcdir)/"; fi; \ echo "$$d$$p"; \ @@ -466,9 +513,7 @@ uninstall-gnunetincludeHEADERS: @$(NORMAL_UNINSTALL) @list='$(gnunetinclude_HEADERS)'; test -n "$(gnunetincludedir)" || list=; \ files=`for p in $$list; do echo $$p; done | sed -e 's|^.*/||'`; \ - test -n "$$files" || exit 0; \ - echo " ( cd '$(DESTDIR)$(gnunetincludedir)' && rm -f" $$files ")"; \ - cd "$(DESTDIR)$(gnunetincludedir)" && rm -f $$files + dir='$(DESTDIR)$(gnunetincludedir)'; $(am__uninstall_files_from_dir) # This directory's subdirectories are mostly independent; you can cd # into them and run `make' without going through this Makefile. @@ -639,13 +684,10 @@ distdir: $(DISTFILES) done @list='$(DIST_SUBDIRS)'; for subdir in $$list; do \ if test "$$subdir" = .; then :; else \ - test -d "$(distdir)/$$subdir" \ - || $(MKDIR_P) "$(distdir)/$$subdir" \ - || exit 1; \ - fi; \ - done - @list='$(DIST_SUBDIRS)'; for subdir in $$list; do \ - if test "$$subdir" = .; then :; else \ + $(am__make_dryrun) \ + || test -d "$(distdir)/$$subdir" \ + || $(MKDIR_P) "$(distdir)/$$subdir" \ + || exit 1; \ dir1=$$subdir; dir2="$(distdir)/$$subdir"; \ $(am__relativize); \ new_distdir=$$reldir; \ @@ -677,7 +719,11 @@ dist-gzip: distdir $(am__remove_distdir) dist-bzip2: distdir - tardir=$(distdir) && $(am__tar) | bzip2 -9 -c >$(distdir).tar.bz2 + tardir=$(distdir) && $(am__tar) | BZIP2=$${BZIP2--9} bzip2 -c >$(distdir).tar.bz2 + $(am__remove_distdir) + +dist-lzip: distdir + tardir=$(distdir) && $(am__tar) | lzip -c $${LZIP_OPT--9} >$(distdir).tar.lz $(am__remove_distdir) dist-lzma: distdir @@ -685,7 +731,7 @@ dist-lzma: distdir $(am__remove_distdir) dist-xz: distdir - tardir=$(distdir) && $(am__tar) | xz -c >$(distdir).tar.xz + tardir=$(distdir) && $(am__tar) | XZ_OPT=$${XZ_OPT--e} xz -c >$(distdir).tar.xz $(am__remove_distdir) dist-tarZ: distdir @@ -716,6 +762,8 @@ distcheck: dist bzip2 -dc $(distdir).tar.bz2 | $(am__untar) ;;\ *.tar.lzma*) \ lzma -dc $(distdir).tar.lzma | $(am__untar) ;;\ + *.tar.lz*) \ + lzip -dc $(distdir).tar.lz | $(am__untar) ;;\ *.tar.xz*) \ xz -dc $(distdir).tar.xz | $(am__untar) ;;\ *.tar.Z*) \ @@ -725,7 +773,7 @@ distcheck: dist *.zip*) \ unzip $(distdir).zip ;;\ esac - chmod -R a-w $(distdir); chmod a+w $(distdir) + chmod -R a-w $(distdir); chmod u+w $(distdir) mkdir $(distdir)/_build mkdir $(distdir)/_inst chmod a-w $(distdir) @@ -735,6 +783,7 @@ distcheck: dist && am__cwd=`pwd` \ && $(am__cd) $(distdir)/_build \ && ../configure --srcdir=.. --prefix="$$dc_install_base" \ + $(AM_DISTCHECK_CONFIGURE_FLAGS) \ $(DISTCHECK_CONFIGURE_FLAGS) \ && $(MAKE) $(AM_MAKEFLAGS) \ && $(MAKE) $(AM_MAKEFLAGS) dvi \ @@ -763,8 +812,16 @@ distcheck: dist list='$(DIST_ARCHIVES)'; for i in $$list; do echo $$i; done) | \ sed -e 1h -e 1s/./=/g -e 1p -e 1x -e '$$p' -e '$$x' distuninstallcheck: - @$(am__cd) '$(distuninstallcheck_dir)' \ - && test `$(distuninstallcheck_listfiles) | wc -l` -le 1 \ + @test -n '$(distuninstallcheck_dir)' || { \ + echo 'ERROR: trying to run $@ with an empty' \ + '$$(distuninstallcheck_dir)' >&2; \ + exit 1; \ + }; \ + $(am__cd) '$(distuninstallcheck_dir)' || { \ + echo 'ERROR: cannot chdir into $(distuninstallcheck_dir)' >&2; \ + exit 1; \ + }; \ + test `$(am__distuninstallcheck_listfiles) | wc -l` -eq 0 \ || { echo "ERROR: files left after uninstall:" ; \ if test -n "$(DESTDIR)"; then \ echo " (check DESTDIR support)"; \ @@ -798,10 +855,15 @@ install-am: all-am installcheck: installcheck-recursive install-strip: - $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ - install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ - `test -z '$(STRIP)' || \ - echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi mostlyclean-generic: clean-generic: @@ -889,8 +951,8 @@ uninstall-am: uninstall-docDATA uninstall-gnunetincludeHEADERS .PHONY: $(RECURSIVE_CLEAN_TARGETS) $(RECURSIVE_TARGETS) CTAGS GTAGS \ all all-am am--refresh check check-am clean clean-generic \ clean-libtool ctags ctags-recursive dist dist-all dist-bzip2 \ - dist-gzip dist-lzma dist-shar dist-tarZ dist-xz dist-zip \ - distcheck distclean distclean-generic distclean-hdr \ + dist-gzip dist-lzip dist-lzma dist-shar dist-tarZ dist-xz \ + dist-zip distcheck distclean distclean-generic distclean-hdr \ distclean-libtool distclean-tags distcleancheck distdir \ distuninstallcheck dvi dvi-am html html-am info info-am \ install install-am install-data install-data-am \ diff --git a/README b/README index 7a3d4cf..6d66977 100644 --- a/README +++ b/README @@ -31,8 +31,9 @@ These are the direct dependencies for running GNUnet: - libextractor >= 0.6.1 - libmicrohttpd >= 0.9.18 - libgcrypt >= 1.2 -- libcurl >= 7.21.0 +- libcurl >= 7.21.3 - libunistring >= 0.9.2 +- gnutls >= 2.12.0 - libltdl >= 2.2 (part of GNU libtool) - sqlite >= 3.0 (default database) - mysql >= 5.1 (alternative to sqLite) @@ -70,15 +71,20 @@ http://www.gnu.org/software/libmicrohttpd/). Then you can start the actual GNUnet compilation and installation process with: $ export GNUNET_PREFIX=/usr/local # or other directory of your choice -$ addgroup gnunetdns -$ adduser gnunet gnunet -$ ./configure --prefix=$GNUNET_PREFIX --with-extractor=$LE_PREFIX +# addgroup gnunetdns +# adduser gnunet gnunet +# ./configure --prefix=$GNUNET_PREFIX --with-extractor=$LE_PREFIX $ make # make install -# sudo -u gnunet mkdir ~/.gnunet/ -# sudo -u gnunet touch ~/.gnunet/gnunet.conf # sudo -u gnunet gnunet-arm -s +Note that running the 'configure' and 'make install' steps as +root (or with sudo) is required as some parts of the installation +require the creation of SUID binaries. The installation will +work if you do not run these steps as root, but some components +may not be installed in the perfect place or with the right +permissions and thus won't work. + This will create the users and groups needed for running GNUnet securely and then compile and install GNUnet to $GNUNET_PREFIX/bin/, $GNUNET_PREFIX/lib/ and $GNUNET_PREFIX/share/ and start the system @@ -88,9 +94,13 @@ end-user applications as another user. If you create a system user "gnunet", it is recommended that you edit the configuration file slightly so that data can be stored in the -system user home directory at "/var/lib/gnunet"; you may also want to +system user home directory at "/var/lib/gnunet". Depending on what +the $HOME-directory of your "gnunet" user is, you might need to set +the SERVICEHOME option in section "[PATHS]" to "/var/lib/gnunet" to +do this. Depending on your personal preferences, you may also want to use "/etc/gnunet.conf" for the location of the configuration file in -this case. +this case (instead of ~gnunet/.gnunet/gnunet.conf"). In this case, +you need to start GNUnet using "gnunet-arm -s -c /etc/gnunet.conf". You can avoid running 'make install' as root if you run configure with the "--with-sudo=yes" option and have extensive sudo rights @@ -124,13 +134,23 @@ $ aclocal -I /usr/local/share/aclocal Configuration ============= -Note that additional, per-user configuration files -(~/.gnunet/gnunet.conf) need to be created by each user (for example, -by running gnunet-setup). Note that gnunet-setup is a separate -download and requires recent versions of GTK+ and Glade; you can also -edit the configuration file by hand, but this is not recommended. For -more general information about the GNU build process read the INSTALL -file. +Note that additional, per-user configuration files can be created by +each user. However, this is usually not necessary as there are few +per-user options that normal users would want to modify. The defaults +that are shipped with the installation are usually just fine. + +The gnunet-setup tool is particularly useful to generate the master +configuration for the peer. gnunet-setup can be used to configure and +test (!) the network settings, choose which applications should be run +and configure databases. Other options you might want to control +include system limitations (such as disk space consumption, bandwidth, +etc.). The resulting configuration files are human-readable and can +theoretically be created or edited by hand. + +gnunet-setup is a separate download and requires somewhat recent +versions of GTK+ and Glade. You can also create the configuration file +by hand, but this is not recommended. For more general information +about the GNU build process read the INSTALL file. GNUnet uses two types of configuration files, one that specifies the system-wide defaults (typically located in @@ -140,20 +160,13 @@ configuration file should be located in "~/.gnunet/gnunet.conf" or its location can be specified by giving the "-c" option to the respective GNUnet application. -The defaults that are shipped with the installation are usually ok, -you may want to adjust the limitations (space consumption, bandwidth, -etc.) though. The configuration files are human-readable. Note that -you MUST create "~/.gnunet/gnunet.conf" explicitly before starting -GNUnet. You can either run gnunet-setup (available as part of the -gnunet-gtk source package) or simply create an empty file. - Usage ===== First, you must obtain an initial list of GNUnet hosts. Knowing a single peer is sufficient since after that GNUnet propagates -information about other peers. Note that the default "gnunet.conf" +information about other peers. Note that the default configuration contains URLs from where GNUnet downloads an initial hostlist whenever it is started. If you want to create an alternative URL for others to use, the file can be generated on any machine running @@ -169,16 +182,24 @@ HTTPPORT to the public. If the solution with the hostlist URL is not feasible for your situation, you can also add hosts manually. Simply copy the hostkeys to "$SERVICEHOME/data/hosts/" (where $SERVICEHOME is the directory -specified in the gnunet.conf configuration file). +specified in the gnunet.conf configuration file). You can also use +"gnunet-peerinfo -g" to GET a URI for a peer and "gnunet-peerinfo -p +URI" to add a URI from another peer. Finally, GNUnet peers that use +UDP or WLAN will discover each other automatically (if they are in the +vicinity of each other) using broadcasts (IPv4/WLAN) or multicasts +(IPv6). -Now start the local node using "gnunet-arm -s". GNUnet should run 24/7 if -you want to maximize your anonymity. +The local node is started using "gnunet-arm -s". GNUnet should run +24/7 if you want to maximize your anonymity, as this makes partitioning +attacks harder. -You should then be able to access GNUnet using the shell: +Once your peer is running, you should then be able to access GNUnet +using the shell: $ gnunet-search KEYWORD -This will display a list of results to the console. Then use +This will display a list of results to the console. You can abort +the command using "CTRL-C". Then use $ gnunet-download -o FILENAME GNUNET_URI @@ -227,7 +248,7 @@ information about the failing testcase to the Mantis bugtracking system at https://gnunet.org/bugs/. -Running http on port 80 and https on port 443 +Running HTTP on port 80 and HTTPS on port 443 ============================================= In order to hide GNUnet's HTTP/HTTPS traffic perfectly, you might @@ -251,6 +272,17 @@ to map them to a priviledged port (from the point of view of the network). However, we are not aware of this providing any advantages at this point. +If you are already running an HTTP or HTTPS server on port 80 (or 443), +you may be able to configure it as a "ReverseProxy". Here, you tell +GNUnet that the externally visible URI is some sub-page on your website, +and GNUnet can then tunnel its traffic via your existing HTTP server. +This is particularly powerful if your existing server uses HTTPS, as +it makes it harder for an adversary to distinguish normal traffic to +your server from GNUnet traffic. Finally, even if you just use HTTP, +you might benefit (!) from ISP's traffic shaping as opposed to being +throttled by ISPs that dislike P2P. Details for configuring the +reverse proxy are documented on our website. + Stay tuned ========== diff --git a/aclocal.m4 b/aclocal.m4 index f7689c9..f02e007 100644 --- a/aclocal.m4 +++ b/aclocal.m4 @@ -1,7 +1,8 @@ -# generated automatically by aclocal 1.11.1 -*- Autoconf -*- +# generated automatically by aclocal 1.11.6 -*- Autoconf -*- # Copyright (C) 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004, -# 2005, 2006, 2007, 2008, 2009 Free Software Foundation, Inc. +# 2005, 2006, 2007, 2008, 2009, 2010, 2011 Free Software Foundation, +# Inc. # This file is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. @@ -13,18 +14,21 @@ m4_ifndef([AC_AUTOCONF_VERSION], [m4_copy([m4_PACKAGE_VERSION], [AC_AUTOCONF_VERSION])])dnl -m4_if(m4_defn([AC_AUTOCONF_VERSION]), [2.67],, -[m4_warning([this file was generated for autoconf 2.67. +m4_if(m4_defn([AC_AUTOCONF_VERSION]), [2.69],, +[m4_warning([this file was generated for autoconf 2.69. You have another version of autoconf. It may work, but is not guaranteed to. If you have problems, you may need to regenerate the build system entirely. To do so, use the procedure documented by the package, typically `autoreconf'.])]) -# Copyright (C) 2002, 2003, 2005, 2006, 2007, 2008 Free Software Foundation, Inc. +# Copyright (C) 2002, 2003, 2005, 2006, 2007, 2008, 2011 Free Software +# Foundation, Inc. # # This file is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. +# serial 1 + # AM_AUTOMAKE_VERSION(VERSION) # ---------------------------- # Automake X.Y traces this macro to ensure aclocal.m4 has been @@ -34,7 +38,7 @@ AC_DEFUN([AM_AUTOMAKE_VERSION], [am__api_version='1.11' dnl Some users find AM_AUTOMAKE_VERSION and mistake it for a way to dnl require some minimum version. Point them to the right macro. -m4_if([$1], [1.11.1], [], +m4_if([$1], [1.11.6], [], [AC_FATAL([Do not call $0, use AM_INIT_AUTOMAKE([$1]).])])dnl ]) @@ -50,19 +54,21 @@ m4_define([_AM_AUTOCONF_VERSION], []) # Call AM_AUTOMAKE_VERSION and AM_AUTOMAKE_VERSION so they can be traced. # This function is AC_REQUIREd by AM_INIT_AUTOMAKE. AC_DEFUN([AM_SET_CURRENT_AUTOMAKE_VERSION], -[AM_AUTOMAKE_VERSION([1.11.1])dnl +[AM_AUTOMAKE_VERSION([1.11.6])dnl m4_ifndef([AC_AUTOCONF_VERSION], [m4_copy([m4_PACKAGE_VERSION], [AC_AUTOCONF_VERSION])])dnl _AM_AUTOCONF_VERSION(m4_defn([AC_AUTOCONF_VERSION]))]) # AM_AUX_DIR_EXPAND -*- Autoconf -*- -# Copyright (C) 2001, 2003, 2005 Free Software Foundation, Inc. +# Copyright (C) 2001, 2003, 2005, 2011 Free Software Foundation, Inc. # # This file is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. +# serial 1 + # For projects using AC_CONFIG_AUX_DIR([foo]), Autoconf sets # $ac_aux_dir to `$srcdir/foo'. In other projects, it is set to # `$srcdir', `$srcdir/..', or `$srcdir/../..'. @@ -144,14 +150,14 @@ AC_CONFIG_COMMANDS_PRE( Usually this means the macro was only invoked conditionally.]]) fi])]) -# Copyright (C) 1999, 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2009 -# Free Software Foundation, Inc. +# Copyright (C) 1999, 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2009, +# 2010, 2011 Free Software Foundation, Inc. # # This file is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. -# serial 10 +# serial 12 # There are a few dirty hacks below to avoid letting `AC_PROG_CC' be # written in clear, in which case automake, when reading aclocal.m4, @@ -191,6 +197,7 @@ AC_CACHE_CHECK([dependency style of $depcc], # instance it was reported that on HP-UX the gcc test will end up # making a dummy file named `D' -- because `-MD' means `put the output # in D'. + rm -rf conftest.dir mkdir conftest.dir # Copy depcomp to subdir because otherwise we won't find it if we're # using a relative directory. @@ -255,7 +262,7 @@ AC_CACHE_CHECK([dependency style of $depcc], break fi ;; - msvisualcpp | msvcmsys) + msvc7 | msvc7msys | msvisualcpp | msvcmsys) # This compiler won't grok `-c -o', but also, the minuso test has # not run yet. These depmodes are late enough in the game, and # so weak that their functioning should not be impacted. @@ -320,10 +327,13 @@ AC_DEFUN([AM_DEP_TRACK], if test "x$enable_dependency_tracking" != xno; then am_depcomp="$ac_aux_dir/depcomp" AMDEPBACKSLASH='\' + am__nodep='_no' fi AM_CONDITIONAL([AMDEP], [test "x$enable_dependency_tracking" != xno]) AC_SUBST([AMDEPBACKSLASH])dnl _AM_SUBST_NOTMAKE([AMDEPBACKSLASH])dnl +AC_SUBST([am__nodep])dnl +_AM_SUBST_NOTMAKE([am__nodep])dnl ]) # Generate code to set up dependency tracking. -*- Autoconf -*- @@ -545,12 +555,15 @@ for _am_header in $config_headers :; do done echo "timestamp for $_am_arg" >`AS_DIRNAME(["$_am_arg"])`/stamp-h[]$_am_stamp_count]) -# Copyright (C) 2001, 2003, 2005, 2008 Free Software Foundation, Inc. +# Copyright (C) 2001, 2003, 2005, 2008, 2011 Free Software Foundation, +# Inc. # # This file is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. +# serial 1 + # AM_PROG_INSTALL_SH # ------------------ # Define $install_sh. @@ -717,12 +730,15 @@ else fi ]) -# Copyright (C) 2003, 2004, 2005, 2006 Free Software Foundation, Inc. +# Copyright (C) 2003, 2004, 2005, 2006, 2011 Free Software Foundation, +# Inc. # # This file is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. +# serial 1 + # AM_PROG_MKDIR_P # --------------- # Check for `mkdir -p'. @@ -745,13 +761,14 @@ esac # Helper functions for option handling. -*- Autoconf -*- -# Copyright (C) 2001, 2002, 2003, 2005, 2008 Free Software Foundation, Inc. +# Copyright (C) 2001, 2002, 2003, 2005, 2008, 2010 Free Software +# Foundation, Inc. # # This file is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. -# serial 4 +# serial 5 # _AM_MANGLE_OPTION(NAME) # ----------------------- @@ -759,13 +776,13 @@ AC_DEFUN([_AM_MANGLE_OPTION], [[_AM_OPTION_]m4_bpatsubst($1, [[^a-zA-Z0-9_]], [_])]) # _AM_SET_OPTION(NAME) -# ------------------------------ +# -------------------- # Set option NAME. Presently that only means defining a flag for this option. AC_DEFUN([_AM_SET_OPTION], [m4_define(_AM_MANGLE_OPTION([$1]), 1)]) # _AM_SET_OPTIONS(OPTIONS) -# ---------------------------------- +# ------------------------ # OPTIONS is a space-separated list of Automake options. AC_DEFUN([_AM_SET_OPTIONS], [m4_foreach_w([_AM_Option], [$1], [_AM_SET_OPTION(_AM_Option)])]) @@ -776,13 +793,15 @@ AC_DEFUN([_AM_SET_OPTIONS], AC_DEFUN([_AM_IF_OPTION], [m4_ifset(_AM_MANGLE_OPTION([$1]), [$2], [$3])]) -# Copyright (C) 1999, 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009 -# Free Software Foundation, Inc. +# Copyright (C) 1999, 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009, +# 2011 Free Software Foundation, Inc. # # This file is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. +# serial 2 + # AM_PATH_PYTHON([MINIMUM-VERSION], [ACTION-IF-FOUND], [ACTION-IF-NOT-FOUND]) # --------------------------------------------------------------------------- # Adds support for distributing Python modules and packages. To @@ -810,8 +829,10 @@ AC_DEFUN([AM_PATH_PYTHON], dnl Find a Python interpreter. Python versions prior to 2.0 are not dnl supported. (2.0 was released on October 16, 2000). m4_define_default([_AM_PYTHON_INTERPRETER_LIST], - [python python2 python3 python3.0 python2.5 python2.4 python2.3 python2.2 dnl -python2.1 python2.0]) +[python python2 python3 python3.2 python3.1 python3.0 python2.7 dnl + python2.6 python2.5 python2.4 python2.3 python2.2 python2.1 python2.0]) + + AC_ARG_VAR([PYTHON], [the Python interpreter]) m4_if([$1],[],[ dnl No version check is needed. @@ -883,9 +904,7 @@ python2.1 python2.0]) dnl site-packages directory, not the python standard library dnl directory like in previous automake betas. This behavior dnl is more consistent with lispdir.m4 for example. - dnl Query distutils for this directory. distutils does not exist in - dnl Python 1.5, so we fall back to the hardcoded directory if it - dnl doesn't work. + dnl Query distutils for this directory. AC_CACHE_CHECK([for $am_display_PYTHON script directory], [am_cv_python_pythondir], [if test "x$prefix" = xNONE @@ -894,8 +913,7 @@ python2.1 python2.0]) else am_py_prefix=$prefix fi - am_cv_python_pythondir=`$PYTHON -c "import sys; from distutils import sysconfig; sys.stdout.write(sysconfig.get_python_lib(0,0,prefix='$am_py_prefix'))" 2>/dev/null || - echo "$PYTHON_PREFIX/lib/python$PYTHON_VERSION/site-packages"` + am_cv_python_pythondir=`$PYTHON -c "import sys; from distutils import sysconfig; sys.stdout.write(sysconfig.get_python_lib(0,0,prefix='$am_py_prefix'))" 2>/dev/null` case $am_cv_python_pythondir in $am_py_prefix*) am__strip_prefix=`echo "$am_py_prefix" | sed 's|.|.|g'` @@ -921,9 +939,7 @@ python2.1 python2.0]) dnl pyexecdir -- directory for installing python extension modules dnl (shared libraries) - dnl Query distutils for this directory. distutils does not exist in - dnl Python 1.5, so we fall back to the hardcoded directory if it - dnl doesn't work. + dnl Query distutils for this directory. AC_CACHE_CHECK([for $am_display_PYTHON extension module directory], [am_cv_python_pyexecdir], [if test "x$exec_prefix" = xNONE @@ -932,8 +948,7 @@ python2.1 python2.0]) else am_py_exec_prefix=$exec_prefix fi - am_cv_python_pyexecdir=`$PYTHON -c "import sys; from distutils import sysconfig; sys.stdout.write(sysconfig.get_python_lib(1,0,prefix='$am_py_exec_prefix'))" 2>/dev/null || - echo "$PYTHON_EXEC_PREFIX/lib/python$PYTHON_VERSION/site-packages"` + am_cv_python_pyexecdir=`$PYTHON -c "import sys; from distutils import sysconfig; sys.stdout.write(sysconfig.get_python_lib(1,0,prefix='$am_py_exec_prefix'))" 2>/dev/null` case $am_cv_python_pyexecdir in $am_py_exec_prefix*) am__strip_prefix=`echo "$am_py_exec_prefix" | sed 's|.|.|g'` @@ -981,12 +996,14 @@ for i in list(range(0, 4)): minverhex = (minverhex << 8) + minver[[i]] sys.exit(sys.hexversion < minverhex)" AS_IF([AM_RUN_LOG([$1 -c "$prog"])], [$3], [$4])]) -# Copyright (C) 2001, 2003, 2005 Free Software Foundation, Inc. +# Copyright (C) 2001, 2003, 2005, 2011 Free Software Foundation, Inc. # # This file is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. +# serial 1 + # AM_RUN_LOG(COMMAND) # ------------------- # Run COMMAND, save the exit status in ac_status, and log it. @@ -1063,13 +1080,13 @@ Check your system clock]) fi AC_MSG_RESULT(yes)]) -# Copyright (C) 2009 Free Software Foundation, Inc. +# Copyright (C) 2009, 2011 Free Software Foundation, Inc. # # This file is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. -# serial 1 +# serial 2 # AM_SILENT_RULES([DEFAULT]) # -------------------------- @@ -1084,18 +1101,50 @@ yes) AM_DEFAULT_VERBOSITY=0;; no) AM_DEFAULT_VERBOSITY=1;; *) AM_DEFAULT_VERBOSITY=m4_if([$1], [yes], [0], [1]);; esac +dnl +dnl A few `make' implementations (e.g., NonStop OS and NextStep) +dnl do not support nested variable expansions. +dnl See automake bug#9928 and bug#10237. +am_make=${MAKE-make} +AC_CACHE_CHECK([whether $am_make supports nested variables], + [am_cv_make_support_nested_variables], + [if AS_ECHO([['TRUE=$(BAR$(V)) +BAR0=false +BAR1=true +V=1 +am__doit: + @$(TRUE) +.PHONY: am__doit']]) | $am_make -f - >/dev/null 2>&1; then + am_cv_make_support_nested_variables=yes +else + am_cv_make_support_nested_variables=no +fi]) +if test $am_cv_make_support_nested_variables = yes; then + dnl Using `$V' instead of `$(V)' breaks IRIX make. + AM_V='$(V)' + AM_DEFAULT_V='$(AM_DEFAULT_VERBOSITY)' +else + AM_V=$AM_DEFAULT_VERBOSITY + AM_DEFAULT_V=$AM_DEFAULT_VERBOSITY +fi +AC_SUBST([AM_V])dnl +AM_SUBST_NOTMAKE([AM_V])dnl +AC_SUBST([AM_DEFAULT_V])dnl +AM_SUBST_NOTMAKE([AM_DEFAULT_V])dnl AC_SUBST([AM_DEFAULT_VERBOSITY])dnl AM_BACKSLASH='\' AC_SUBST([AM_BACKSLASH])dnl _AM_SUBST_NOTMAKE([AM_BACKSLASH])dnl ]) -# Copyright (C) 2001, 2003, 2005 Free Software Foundation, Inc. +# Copyright (C) 2001, 2003, 2005, 2011 Free Software Foundation, Inc. # # This file is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. +# serial 1 + # AM_PROG_INSTALL_STRIP # --------------------- # One issue with vendor `install' (even GNU) is that you can't @@ -1118,13 +1167,13 @@ fi INSTALL_STRIP_PROGRAM="\$(install_sh) -c -s" AC_SUBST([INSTALL_STRIP_PROGRAM])]) -# Copyright (C) 2006, 2008 Free Software Foundation, Inc. +# Copyright (C) 2006, 2008, 2010 Free Software Foundation, Inc. # # This file is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. -# serial 2 +# serial 3 # _AM_SUBST_NOTMAKE(VARIABLE) # --------------------------- @@ -1133,13 +1182,13 @@ AC_SUBST([INSTALL_STRIP_PROGRAM])]) AC_DEFUN([_AM_SUBST_NOTMAKE]) # AM_SUBST_NOTMAKE(VARIABLE) -# --------------------------- +# -------------------------- # Public sister of _AM_SUBST_NOTMAKE. AC_DEFUN([AM_SUBST_NOTMAKE], [_AM_SUBST_NOTMAKE($@)]) # Check how to create a tarball. -*- Autoconf -*- -# Copyright (C) 2004, 2005 Free Software Foundation, Inc. +# Copyright (C) 2004, 2005, 2012 Free Software Foundation, Inc. # # This file is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, @@ -1161,10 +1210,11 @@ AC_DEFUN([AM_SUBST_NOTMAKE], [_AM_SUBST_NOTMAKE($@)]) # a tarball read from stdin. # $(am__untar) < result.tar AC_DEFUN([_AM_PROG_TAR], -[# Always define AMTAR for backward compatibility. -AM_MISSING_PROG([AMTAR], [tar]) +[# Always define AMTAR for backward compatibility. Yes, it's still used +# in the wild :-( We should find a proper way to deprecate it ... +AC_SUBST([AMTAR], ['$${TAR-tar}']) m4_if([$1], [v7], - [am__tar='${AMTAR} chof - "$$tardir"'; am__untar='${AMTAR} xf -'], + [am__tar='$${TAR-tar} chof - "$$tardir"' am__untar='$${TAR-tar} xf -'], [m4_case([$1], [ustar],, [pax],, [m4_fatal([Unknown tar format])]) AC_MSG_CHECKING([how to create a $1 tar archive]) @@ -1237,6 +1287,7 @@ m4_include([m4/absolute-header.m4]) m4_include([m4/align.m4]) m4_include([m4/argz.m4]) m4_include([m4/gettext.m4]) +m4_include([m4/glib-2.0.m4]) m4_include([m4/iconv.m4]) m4_include([m4/lib-ld.m4]) m4_include([m4/lib-link.m4]) @@ -1251,6 +1302,7 @@ m4_include([m4/ltsugar.m4]) m4_include([m4/ltversion.m4]) m4_include([m4/lt~obsolete.m4]) m4_include([m4/nls.m4]) +m4_include([m4/pkg.m4]) m4_include([m4/po.m4]) m4_include([m4/progtest.m4]) m4_include([acinclude.m4]) diff --git a/compile b/compile index c0096a7..7b4a9a7 100755 --- a/compile +++ b/compile @@ -1,10 +1,9 @@ #! /bin/sh -# Wrapper for compilers which do not understand `-c -o'. +# Wrapper for compilers which do not understand '-c -o'. -scriptversion=2009-10-06.20; # UTC +scriptversion=2012-03-05.13; # UTC -# Copyright (C) 1999, 2000, 2003, 2004, 2005, 2009 Free Software -# Foundation, Inc. +# Copyright (C) 1999-2012 Free Software Foundation, Inc. # Written by Tom Tromey . # # This program is free software; you can redistribute it and/or modify @@ -29,21 +28,219 @@ scriptversion=2009-10-06.20; # UTC # bugs to or send patches to # . +nl=' +' + +# We need space, tab and new line, in precisely that order. Quoting is +# there to prevent tools from complaining about whitespace usage. +IFS=" "" $nl" + +file_conv= + +# func_file_conv build_file lazy +# Convert a $build file to $host form and store it in $file +# Currently only supports Windows hosts. If the determined conversion +# type is listed in (the comma separated) LAZY, no conversion will +# take place. +func_file_conv () +{ + file=$1 + case $file in + / | /[!/]*) # absolute file, and not a UNC file + if test -z "$file_conv"; then + # lazily determine how to convert abs files + case `uname -s` in + MINGW*) + file_conv=mingw + ;; + CYGWIN*) + file_conv=cygwin + ;; + *) + file_conv=wine + ;; + esac + fi + case $file_conv/,$2, in + *,$file_conv,*) + ;; + mingw/*) + file=`cmd //C echo "$file " | sed -e 's/"\(.*\) " *$/\1/'` + ;; + cygwin/*) + file=`cygpath -m "$file" || echo "$file"` + ;; + wine/*) + file=`winepath -w "$file" || echo "$file"` + ;; + esac + ;; + esac +} + +# func_cl_dashL linkdir +# Make cl look for libraries in LINKDIR +func_cl_dashL () +{ + func_file_conv "$1" + if test -z "$lib_path"; then + lib_path=$file + else + lib_path="$lib_path;$file" + fi + linker_opts="$linker_opts -LIBPATH:$file" +} + +# func_cl_dashl library +# Do a library search-path lookup for cl +func_cl_dashl () +{ + lib=$1 + found=no + save_IFS=$IFS + IFS=';' + for dir in $lib_path $LIB + do + IFS=$save_IFS + if $shared && test -f "$dir/$lib.dll.lib"; then + found=yes + lib=$dir/$lib.dll.lib + break + fi + if test -f "$dir/$lib.lib"; then + found=yes + lib=$dir/$lib.lib + break + fi + done + IFS=$save_IFS + + if test "$found" != yes; then + lib=$lib.lib + fi +} + +# func_cl_wrapper cl arg... +# Adjust compile command to suit cl +func_cl_wrapper () +{ + # Assume a capable shell + lib_path= + shared=: + linker_opts= + for arg + do + if test -n "$eat"; then + eat= + else + case $1 in + -o) + # configure might choose to run compile as 'compile cc -o foo foo.c'. + eat=1 + case $2 in + *.o | *.[oO][bB][jJ]) + func_file_conv "$2" + set x "$@" -Fo"$file" + shift + ;; + *) + func_file_conv "$2" + set x "$@" -Fe"$file" + shift + ;; + esac + ;; + -I) + eat=1 + func_file_conv "$2" mingw + set x "$@" -I"$file" + shift + ;; + -I*) + func_file_conv "${1#-I}" mingw + set x "$@" -I"$file" + shift + ;; + -l) + eat=1 + func_cl_dashl "$2" + set x "$@" "$lib" + shift + ;; + -l*) + func_cl_dashl "${1#-l}" + set x "$@" "$lib" + shift + ;; + -L) + eat=1 + func_cl_dashL "$2" + ;; + -L*) + func_cl_dashL "${1#-L}" + ;; + -static) + shared=false + ;; + -Wl,*) + arg=${1#-Wl,} + save_ifs="$IFS"; IFS=',' + for flag in $arg; do + IFS="$save_ifs" + linker_opts="$linker_opts $flag" + done + IFS="$save_ifs" + ;; + -Xlinker) + eat=1 + linker_opts="$linker_opts $2" + ;; + -*) + set x "$@" "$1" + shift + ;; + *.cc | *.CC | *.cxx | *.CXX | *.[cC]++) + func_file_conv "$1" + set x "$@" -Tp"$file" + shift + ;; + *.c | *.cpp | *.CPP | *.lib | *.LIB | *.Lib | *.OBJ | *.obj | *.[oO]) + func_file_conv "$1" mingw + set x "$@" "$file" + shift + ;; + *) + set x "$@" "$1" + shift + ;; + esac + fi + shift + done + if test -n "$linker_opts"; then + linker_opts="-link$linker_opts" + fi + exec "$@" $linker_opts + exit 1 +} + +eat= + case $1 in '') - echo "$0: No command. Try \`$0 --help' for more information." 1>&2 + echo "$0: No command. Try '$0 --help' for more information." 1>&2 exit 1; ;; -h | --h*) cat <<\EOF Usage: compile [--help] [--version] PROGRAM [ARGS] -Wrapper for compilers which do not understand `-c -o'. -Remove `-o dest.o' from ARGS, run PROGRAM with the remaining +Wrapper for compilers which do not understand '-c -o'. +Remove '-o dest.o' from ARGS, run PROGRAM with the remaining arguments, and rename the output as expected. If you are trying to build a whole package this is not the -right script to run: please start by reading the file `INSTALL'. +right script to run: please start by reading the file 'INSTALL'. Report bugs to . EOF @@ -53,11 +250,13 @@ EOF echo "compile $scriptversion" exit $? ;; + cl | *[/\\]cl | cl.exe | *[/\\]cl.exe ) + func_cl_wrapper "$@" # Doesn't return... + ;; esac ofile= cfile= -eat= for arg do @@ -66,8 +265,8 @@ do else case $1 in -o) - # configure might choose to run compile as `compile cc -o foo foo.c'. - # So we strip `-o arg' only if arg is an object. + # configure might choose to run compile as 'compile cc -o foo foo.c'. + # So we strip '-o arg' only if arg is an object. eat=1 case $2 in *.o | *.obj) @@ -94,10 +293,10 @@ do done if test -z "$ofile" || test -z "$cfile"; then - # If no `-o' option was seen then we might have been invoked from a + # If no '-o' option was seen then we might have been invoked from a # pattern rule where we don't need one. That is ok -- this is a # normal compilation that the losing compiler can handle. If no - # `.c' file was seen then we are probably linking. That is also + # '.c' file was seen then we are probably linking. That is also # ok. exec "$@" fi @@ -106,7 +305,7 @@ fi cofile=`echo "$cfile" | sed 's|^.*[\\/]||; s|^[a-zA-Z]:||; s/\.c$/.o/'` # Create the lock directory. -# Note: use `[/\\:.-]' here to ensure that we don't use the same name +# Note: use '[/\\:.-]' here to ensure that we don't use the same name # that we are using for the .o file. Also, base the name on the expected # object file name, since that is what matters with a parallel build. lockdir=`echo "$cofile" | sed -e 's|[/\\:.-]|_|g'`.d diff --git a/config.guess b/config.guess index dc84c68..d622a44 100755 --- a/config.guess +++ b/config.guess @@ -1,10 +1,10 @@ #! /bin/sh # Attempt to guess a canonical system name. # Copyright (C) 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999, -# 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009 -# Free Software Foundation, Inc. +# 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, +# 2011, 2012 Free Software Foundation, Inc. -timestamp='2009-11-20' +timestamp='2012-02-10' # This file is free software; you can redistribute it and/or modify it # under the terms of the GNU General Public License as published by @@ -17,9 +17,7 @@ timestamp='2009-11-20' # General Public License for more details. # # You should have received a copy of the GNU General Public License -# along with this program; if not, write to the Free Software -# Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston, MA -# 02110-1301, USA. +# along with this program; if not, see . # # As a special exception to the GNU General Public License, if you # distribute this file as part of a program that contains a @@ -56,8 +54,9 @@ version="\ GNU config.guess ($timestamp) Originally written by Per Bothner. -Copyright (C) 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, -2002, 2003, 2004, 2005, 2006, 2007, 2008 Free Software Foundation, Inc. +Copyright (C) 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999, 2000, +2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011, 2012 +Free Software Foundation, Inc. This is free software; see the source for copying conditions. There is NO warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE." @@ -144,7 +143,7 @@ UNAME_VERSION=`(uname -v) 2>/dev/null` || UNAME_VERSION=unknown case "${UNAME_MACHINE}:${UNAME_SYSTEM}:${UNAME_RELEASE}:${UNAME_VERSION}" in *:NetBSD:*:*) # NetBSD (nbsd) targets should (where applicable) match one or - # more of the tupples: *-*-netbsdelf*, *-*-netbsdaout*, + # more of the tuples: *-*-netbsdelf*, *-*-netbsdaout*, # *-*-netbsdecoff* and *-*-netbsd*. For targets that recently # switched to ELF, *-*-netbsd* would select the old # object file format. This provides both forward @@ -180,7 +179,7 @@ case "${UNAME_MACHINE}:${UNAME_SYSTEM}:${UNAME_RELEASE}:${UNAME_VERSION}" in fi ;; *) - os=netbsd + os=netbsd ;; esac # The OS release @@ -223,7 +222,7 @@ case "${UNAME_MACHINE}:${UNAME_SYSTEM}:${UNAME_RELEASE}:${UNAME_VERSION}" in UNAME_RELEASE=`/usr/sbin/sizer -v | awk '{print $3}'` ;; *5.*) - UNAME_RELEASE=`/usr/sbin/sizer -v | awk '{print $4}'` + UNAME_RELEASE=`/usr/sbin/sizer -v | awk '{print $4}'` ;; esac # According to Compaq, /usr/sbin/psrinfo has been available on @@ -269,7 +268,10 @@ case "${UNAME_MACHINE}:${UNAME_SYSTEM}:${UNAME_RELEASE}:${UNAME_VERSION}" in # A Xn.n version is an unreleased experimental baselevel. # 1.2 uses "1.2" for uname -r. echo ${UNAME_MACHINE}-dec-osf`echo ${UNAME_RELEASE} | sed -e 's/^[PVTX]//' | tr 'ABCDEFGHIJKLMNOPQRSTUVWXYZ' 'abcdefghijklmnopqrstuvwxyz'` - exit ;; + # Reset EXIT trap before exiting to avoid spurious non-zero exit code. + exitcode=$? + trap '' 0 + exit $exitcode ;; Alpha\ *:Windows_NT*:*) # How do we know it's Interix rather than the generic POSIX subsystem? # Should we change UNAME_MACHINE based on the output of uname instead @@ -295,7 +297,7 @@ case "${UNAME_MACHINE}:${UNAME_SYSTEM}:${UNAME_RELEASE}:${UNAME_VERSION}" in echo s390-ibm-zvmoe exit ;; *:OS400:*:*) - echo powerpc-ibm-os400 + echo powerpc-ibm-os400 exit ;; arm:RISC*:1.[012]*:*|arm:riscix:1.[012]*:*) echo arm-acorn-riscix${UNAME_RELEASE} @@ -394,23 +396,23 @@ case "${UNAME_MACHINE}:${UNAME_SYSTEM}:${UNAME_RELEASE}:${UNAME_VERSION}" in # MiNT. But MiNT is downward compatible to TOS, so this should # be no problem. atarist[e]:*MiNT:*:* | atarist[e]:*mint:*:* | atarist[e]:*TOS:*:*) - echo m68k-atari-mint${UNAME_RELEASE} + echo m68k-atari-mint${UNAME_RELEASE} exit ;; atari*:*MiNT:*:* | atari*:*mint:*:* | atarist[e]:*TOS:*:*) echo m68k-atari-mint${UNAME_RELEASE} - exit ;; + exit ;; *falcon*:*MiNT:*:* | *falcon*:*mint:*:* | *falcon*:*TOS:*:*) - echo m68k-atari-mint${UNAME_RELEASE} + echo m68k-atari-mint${UNAME_RELEASE} exit ;; milan*:*MiNT:*:* | milan*:*mint:*:* | *milan*:*TOS:*:*) - echo m68k-milan-mint${UNAME_RELEASE} - exit ;; + echo m68k-milan-mint${UNAME_RELEASE} + exit ;; hades*:*MiNT:*:* | hades*:*mint:*:* | *hades*:*TOS:*:*) - echo m68k-hades-mint${UNAME_RELEASE} - exit ;; + echo m68k-hades-mint${UNAME_RELEASE} + exit ;; *:*MiNT:*:* | *:*mint:*:* | *:*TOS:*:*) - echo m68k-unknown-mint${UNAME_RELEASE} - exit ;; + echo m68k-unknown-mint${UNAME_RELEASE} + exit ;; m68k:machten:*:*) echo m68k-apple-machten${UNAME_RELEASE} exit ;; @@ -480,8 +482,8 @@ EOF echo m88k-motorola-sysv3 exit ;; AViiON:dgux:*:*) - # DG/UX returns AViiON for all architectures - UNAME_PROCESSOR=`/usr/bin/uname -p` + # DG/UX returns AViiON for all architectures + UNAME_PROCESSOR=`/usr/bin/uname -p` if [ $UNAME_PROCESSOR = mc88100 ] || [ $UNAME_PROCESSOR = mc88110 ] then if [ ${TARGET_BINARY_INTERFACE}x = m88kdguxelfx ] || \ @@ -494,7 +496,7 @@ EOF else echo i586-dg-dgux${UNAME_RELEASE} fi - exit ;; + exit ;; M88*:DolphinOS:*:*) # DolphinOS (SVR3) echo m88k-dolphin-sysv3 exit ;; @@ -551,7 +553,7 @@ EOF echo rs6000-ibm-aix3.2 fi exit ;; - *:AIX:*:[456]) + *:AIX:*:[4567]) IBM_CPU_ID=`/usr/sbin/lsdev -C -c processor -S available | sed 1q | awk '{ print $1 }'` if /usr/sbin/lsattr -El ${IBM_CPU_ID} | grep ' POWER' >/dev/null 2>&1; then IBM_ARCH=rs6000 @@ -594,52 +596,52 @@ EOF 9000/[678][0-9][0-9]) if [ -x /usr/bin/getconf ]; then sc_cpu_version=`/usr/bin/getconf SC_CPU_VERSION 2>/dev/null` - sc_kernel_bits=`/usr/bin/getconf SC_KERNEL_BITS 2>/dev/null` - case "${sc_cpu_version}" in - 523) HP_ARCH="hppa1.0" ;; # CPU_PA_RISC1_0 - 528) HP_ARCH="hppa1.1" ;; # CPU_PA_RISC1_1 - 532) # CPU_PA_RISC2_0 - case "${sc_kernel_bits}" in - 32) HP_ARCH="hppa2.0n" ;; - 64) HP_ARCH="hppa2.0w" ;; + sc_kernel_bits=`/usr/bin/getconf SC_KERNEL_BITS 2>/dev/null` + case "${sc_cpu_version}" in + 523) HP_ARCH="hppa1.0" ;; # CPU_PA_RISC1_0 + 528) HP_ARCH="hppa1.1" ;; # CPU_PA_RISC1_1 + 532) # CPU_PA_RISC2_0 + case "${sc_kernel_bits}" in + 32) HP_ARCH="hppa2.0n" ;; + 64) HP_ARCH="hppa2.0w" ;; '') HP_ARCH="hppa2.0" ;; # HP-UX 10.20 - esac ;; - esac + esac ;; + esac fi if [ "${HP_ARCH}" = "" ]; then eval $set_cc_for_build - sed 's/^ //' << EOF >$dummy.c + sed 's/^ //' << EOF >$dummy.c - #define _HPUX_SOURCE - #include - #include + #define _HPUX_SOURCE + #include + #include - int main () - { - #if defined(_SC_KERNEL_BITS) - long bits = sysconf(_SC_KERNEL_BITS); - #endif - long cpu = sysconf (_SC_CPU_VERSION); + int main () + { + #if defined(_SC_KERNEL_BITS) + long bits = sysconf(_SC_KERNEL_BITS); + #endif + long cpu = sysconf (_SC_CPU_VERSION); - switch (cpu) - { - case CPU_PA_RISC1_0: puts ("hppa1.0"); break; - case CPU_PA_RISC1_1: puts ("hppa1.1"); break; - case CPU_PA_RISC2_0: - #if defined(_SC_KERNEL_BITS) - switch (bits) - { - case 64: puts ("hppa2.0w"); break; - case 32: puts ("hppa2.0n"); break; - default: puts ("hppa2.0"); break; - } break; - #else /* !defined(_SC_KERNEL_BITS) */ - puts ("hppa2.0"); break; - #endif - default: puts ("hppa1.0"); break; - } - exit (0); - } + switch (cpu) + { + case CPU_PA_RISC1_0: puts ("hppa1.0"); break; + case CPU_PA_RISC1_1: puts ("hppa1.1"); break; + case CPU_PA_RISC2_0: + #if defined(_SC_KERNEL_BITS) + switch (bits) + { + case 64: puts ("hppa2.0w"); break; + case 32: puts ("hppa2.0n"); break; + default: puts ("hppa2.0"); break; + } break; + #else /* !defined(_SC_KERNEL_BITS) */ + puts ("hppa2.0"); break; + #endif + default: puts ("hppa1.0"); break; + } + exit (0); + } EOF (CCOPTS= $CC_FOR_BUILD -o $dummy $dummy.c 2>/dev/null) && HP_ARCH=`$dummy` test -z "$HP_ARCH" && HP_ARCH=hppa @@ -730,22 +732,22 @@ EOF exit ;; C1*:ConvexOS:*:* | convex:ConvexOS:C1*:*) echo c1-convex-bsd - exit ;; + exit ;; C2*:ConvexOS:*:* | convex:ConvexOS:C2*:*) if getsysinfo -f scalar_acc then echo c32-convex-bsd else echo c2-convex-bsd fi - exit ;; + exit ;; C34*:ConvexOS:*:* | convex:ConvexOS:C34*:*) echo c34-convex-bsd - exit ;; + exit ;; C38*:ConvexOS:*:* | convex:ConvexOS:C38*:*) echo c38-convex-bsd - exit ;; + exit ;; C4*:ConvexOS:*:* | convex:ConvexOS:C4*:*) echo c4-convex-bsd - exit ;; + exit ;; CRAY*Y-MP:*:*:*) echo ymp-cray-unicos${UNAME_RELEASE} | sed -e 's/\.[^.]*$/.X/' exit ;; @@ -769,14 +771,14 @@ EOF exit ;; F30[01]:UNIX_System_V:*:* | F700:UNIX_System_V:*:*) FUJITSU_PROC=`uname -m | tr 'ABCDEFGHIJKLMNOPQRSTUVWXYZ' 'abcdefghijklmnopqrstuvwxyz'` - FUJITSU_SYS=`uname -p | tr 'ABCDEFGHIJKLMNOPQRSTUVWXYZ' 'abcdefghijklmnopqrstuvwxyz' | sed -e 's/\///'` - FUJITSU_REL=`echo ${UNAME_RELEASE} | sed -e 's/ /_/'` - echo "${FUJITSU_PROC}-fujitsu-${FUJITSU_SYS}${FUJITSU_REL}" - exit ;; + FUJITSU_SYS=`uname -p | tr 'ABCDEFGHIJKLMNOPQRSTUVWXYZ' 'abcdefghijklmnopqrstuvwxyz' | sed -e 's/\///'` + FUJITSU_REL=`echo ${UNAME_RELEASE} | sed -e 's/ /_/'` + echo "${FUJITSU_PROC}-fujitsu-${FUJITSU_SYS}${FUJITSU_REL}" + exit ;; 5000:UNIX_System_V:4.*:*) - FUJITSU_SYS=`uname -p | tr 'ABCDEFGHIJKLMNOPQRSTUVWXYZ' 'abcdefghijklmnopqrstuvwxyz' | sed -e 's/\///'` - FUJITSU_REL=`echo ${UNAME_RELEASE} | tr 'ABCDEFGHIJKLMNOPQRSTUVWXYZ' 'abcdefghijklmnopqrstuvwxyz' | sed -e 's/ /_/'` - echo "sparc-fujitsu-${FUJITSU_SYS}${FUJITSU_REL}" + FUJITSU_SYS=`uname -p | tr 'ABCDEFGHIJKLMNOPQRSTUVWXYZ' 'abcdefghijklmnopqrstuvwxyz' | sed -e 's/\///'` + FUJITSU_REL=`echo ${UNAME_RELEASE} | tr 'ABCDEFGHIJKLMNOPQRSTUVWXYZ' 'abcdefghijklmnopqrstuvwxyz' | sed -e 's/ /_/'` + echo "sparc-fujitsu-${FUJITSU_SYS}${FUJITSU_REL}" exit ;; i*86:BSD/386:*:* | i*86:BSD/OS:*:* | *:Ascend\ Embedded/OS:*:*) echo ${UNAME_MACHINE}-pc-bsdi${UNAME_RELEASE} @@ -788,13 +790,12 @@ EOF echo ${UNAME_MACHINE}-unknown-bsdi${UNAME_RELEASE} exit ;; *:FreeBSD:*:*) - case ${UNAME_MACHINE} in - pc98) - echo i386-unknown-freebsd`echo ${UNAME_RELEASE}|sed -e 's/[-(].*//'` ;; + UNAME_PROCESSOR=`/usr/bin/uname -p` + case ${UNAME_PROCESSOR} in amd64) echo x86_64-unknown-freebsd`echo ${UNAME_RELEASE}|sed -e 's/[-(].*//'` ;; *) - echo ${UNAME_MACHINE}-unknown-freebsd`echo ${UNAME_RELEASE}|sed -e 's/[-(].*//'` ;; + echo ${UNAME_PROCESSOR}-unknown-freebsd`echo ${UNAME_RELEASE}|sed -e 's/[-(].*//'` ;; esac exit ;; i*:CYGWIN*:*) @@ -803,15 +804,18 @@ EOF *:MINGW*:*) echo ${UNAME_MACHINE}-pc-mingw32 exit ;; + i*:MSYS*:*) + echo ${UNAME_MACHINE}-pc-msys + exit ;; i*:windows32*:*) - # uname -m includes "-pc" on this system. - echo ${UNAME_MACHINE}-mingw32 + # uname -m includes "-pc" on this system. + echo ${UNAME_MACHINE}-mingw32 exit ;; i*:PW*:*) echo ${UNAME_MACHINE}-pc-pw32 exit ;; *:Interix*:*) - case ${UNAME_MACHINE} in + case ${UNAME_MACHINE} in x86) echo i586-pc-interix${UNAME_RELEASE} exit ;; @@ -857,6 +861,13 @@ EOF i*86:Minix:*:*) echo ${UNAME_MACHINE}-pc-minix exit ;; + aarch64:Linux:*:*) + echo ${UNAME_MACHINE}-unknown-linux-gnu + exit ;; + aarch64_be:Linux:*:*) + UNAME_MACHINE=aarch64_be + echo ${UNAME_MACHINE}-unknown-linux-gnu + exit ;; alpha:Linux:*:*) case `sed -n '/^cpu model/s/^.*: \(.*\)/\1/p' < /proc/cpuinfo` in EV5) UNAME_MACHINE=alphaev5 ;; @@ -866,7 +877,7 @@ EOF EV6) UNAME_MACHINE=alphaev6 ;; EV67) UNAME_MACHINE=alphaev67 ;; EV68*) UNAME_MACHINE=alphaev68 ;; - esac + esac objdump --private-headers /bin/sh | grep -q ld.so.1 if test "$?" = 0 ; then LIBC="libc1" ; else LIBC="" ; fi echo ${UNAME_MACHINE}-unknown-linux-gnu${LIBC} @@ -878,20 +889,29 @@ EOF then echo ${UNAME_MACHINE}-unknown-linux-gnu else - echo ${UNAME_MACHINE}-unknown-linux-gnueabi + if echo __ARM_PCS_VFP | $CC_FOR_BUILD -E - 2>/dev/null \ + | grep -q __ARM_PCS_VFP + then + echo ${UNAME_MACHINE}-unknown-linux-gnueabi + else + echo ${UNAME_MACHINE}-unknown-linux-gnueabihf + fi fi exit ;; avr32*:Linux:*:*) echo ${UNAME_MACHINE}-unknown-linux-gnu exit ;; cris:Linux:*:*) - echo cris-axis-linux-gnu + echo ${UNAME_MACHINE}-axis-linux-gnu exit ;; crisv32:Linux:*:*) - echo crisv32-axis-linux-gnu + echo ${UNAME_MACHINE}-axis-linux-gnu exit ;; frv:Linux:*:*) - echo frv-unknown-linux-gnu + echo ${UNAME_MACHINE}-unknown-linux-gnu + exit ;; + hexagon:Linux:*:*) + echo ${UNAME_MACHINE}-unknown-linux-gnu exit ;; i*86:Linux:*:*) LIBC=gnu @@ -933,7 +953,7 @@ EOF test x"${CPU}" != x && { echo "${CPU}-unknown-linux-gnu"; exit; } ;; or32:Linux:*:*) - echo or32-unknown-linux-gnu + echo ${UNAME_MACHINE}-unknown-linux-gnu exit ;; padre:Linux:*:*) echo sparc-unknown-linux-gnu @@ -959,7 +979,7 @@ EOF echo ${UNAME_MACHINE}-ibm-linux exit ;; sh64*:Linux:*:*) - echo ${UNAME_MACHINE}-unknown-linux-gnu + echo ${UNAME_MACHINE}-unknown-linux-gnu exit ;; sh*:Linux:*:*) echo ${UNAME_MACHINE}-unknown-linux-gnu @@ -967,14 +987,17 @@ EOF sparc:Linux:*:* | sparc64:Linux:*:*) echo ${UNAME_MACHINE}-unknown-linux-gnu exit ;; + tile*:Linux:*:*) + echo ${UNAME_MACHINE}-unknown-linux-gnu + exit ;; vax:Linux:*:*) echo ${UNAME_MACHINE}-dec-linux-gnu exit ;; x86_64:Linux:*:*) - echo x86_64-unknown-linux-gnu + echo ${UNAME_MACHINE}-unknown-linux-gnu exit ;; xtensa*:Linux:*:*) - echo ${UNAME_MACHINE}-unknown-linux-gnu + echo ${UNAME_MACHINE}-unknown-linux-gnu exit ;; i*86:DYNIX/ptx:4*:*) # ptx 4.0 does uname -s correctly, with DYNIX/ptx in there. @@ -983,11 +1006,11 @@ EOF echo i386-sequent-sysv4 exit ;; i*86:UNIX_SV:4.2MP:2.*) - # Unixware is an offshoot of SVR4, but it has its own version - # number series starting with 2... - # I am not positive that other SVR4 systems won't match this, + # Unixware is an offshoot of SVR4, but it has its own version + # number series starting with 2... + # I am not positive that other SVR4 systems won't match this, # I just have to hope. -- rms. - # Use sysv4.2uw... so that sysv4* matches it. + # Use sysv4.2uw... so that sysv4* matches it. echo ${UNAME_MACHINE}-pc-sysv4.2uw${UNAME_VERSION} exit ;; i*86:OS/2:*:*) @@ -1019,7 +1042,7 @@ EOF fi exit ;; i*86:*:5:[678]*) - # UnixWare 7.x, OpenUNIX and OpenServer 6. + # UnixWare 7.x, OpenUNIX and OpenServer 6. case `/bin/uname -X | grep "^Machine"` in *486*) UNAME_MACHINE=i486 ;; *Pentium) UNAME_MACHINE=i586 ;; @@ -1047,13 +1070,13 @@ EOF exit ;; pc:*:*:*) # Left here for compatibility: - # uname -m prints for DJGPP always 'pc', but it prints nothing about - # the processor, so we play safe by assuming i586. + # uname -m prints for DJGPP always 'pc', but it prints nothing about + # the processor, so we play safe by assuming i586. # Note: whatever this is, it MUST be the same as what config.sub # prints for the "djgpp" host, or else GDB configury will decide that # this is a cross-build. echo i586-pc-msdosdjgpp - exit ;; + exit ;; Intel:Mach:3*:*) echo i386-pc-mach3 exit ;; @@ -1088,8 +1111,8 @@ EOF /bin/uname -p 2>/dev/null | /bin/grep entium >/dev/null \ && { echo i586-ncr-sysv4.3${OS_REL}; exit; } ;; 3[34]??:*:4.0:* | 3[34]??,*:*:4.0:*) - /bin/uname -p 2>/dev/null | grep 86 >/dev/null \ - && { echo i486-ncr-sysv4; exit; } ;; + /bin/uname -p 2>/dev/null | grep 86 >/dev/null \ + && { echo i486-ncr-sysv4; exit; } ;; NCR*:*:4.2:* | MPRAS*:*:4.2:*) OS_REL='.3' test -r /etc/.relid \ @@ -1132,10 +1155,10 @@ EOF echo ns32k-sni-sysv fi exit ;; - PENTIUM:*:4.0*:*) # Unisys `ClearPath HMP IX 4000' SVR4/MP effort - # says - echo i586-unisys-sysv4 - exit ;; + PENTIUM:*:4.0*:*) # Unisys `ClearPath HMP IX 4000' SVR4/MP effort + # says + echo i586-unisys-sysv4 + exit ;; *:UNIX_System_V:4*:FTX*) # From Gerald Hewes . # How about differentiating between stratus architectures? -djm @@ -1161,11 +1184,11 @@ EOF exit ;; R[34]000:*System_V*:*:* | R4000:UNIX_SYSV:*:* | R*000:UNIX_SV:*:*) if [ -d /usr/nec ]; then - echo mips-nec-sysv${UNAME_RELEASE} + echo mips-nec-sysv${UNAME_RELEASE} else - echo mips-unknown-sysv${UNAME_RELEASE} + echo mips-unknown-sysv${UNAME_RELEASE} fi - exit ;; + exit ;; BeBox:BeOS:*:*) # BeOS running on hardware made by Be, PPC only. echo powerpc-be-beos exit ;; @@ -1230,6 +1253,9 @@ EOF *:QNX:*:4*) echo i386-pc-qnx exit ;; + NEO-?:NONSTOP_KERNEL:*:*) + echo neo-tandem-nsk${UNAME_RELEASE} + exit ;; NSE-?:NONSTOP_KERNEL:*:*) echo nse-tandem-nsk${UNAME_RELEASE} exit ;; @@ -1275,13 +1301,13 @@ EOF echo pdp10-unknown-its exit ;; SEI:*:*:SEIUX) - echo mips-sei-seiux${UNAME_RELEASE} + echo mips-sei-seiux${UNAME_RELEASE} exit ;; *:DragonFly:*:*) echo ${UNAME_MACHINE}-unknown-dragonfly`echo ${UNAME_RELEASE}|sed -e 's/[-(].*//'` exit ;; *:*VMS:*:*) - UNAME_MACHINE=`(uname -p) 2>/dev/null` + UNAME_MACHINE=`(uname -p) 2>/dev/null` case "${UNAME_MACHINE}" in A*) echo alpha-dec-vms ; exit ;; I*) echo ia64-dec-vms ; exit ;; @@ -1299,6 +1325,9 @@ EOF i*86:AROS:*:*) echo ${UNAME_MACHINE}-pc-aros exit ;; + x86_64:VMkernel:*:*) + echo ${UNAME_MACHINE}-unknown-esx + exit ;; esac #echo '(No uname command or uname output not recognized.)' 1>&2 @@ -1321,11 +1350,11 @@ main () #include printf ("m68k-sony-newsos%s\n", #ifdef NEWSOS4 - "4" + "4" #else - "" + "" #endif - ); exit (0); + ); exit (0); #endif #endif diff --git a/config.sub b/config.sub index 2a55a50..6205f84 100755 --- a/config.sub +++ b/config.sub @@ -1,10 +1,10 @@ #! /bin/sh # Configuration validation subroutine script. # Copyright (C) 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999, -# 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009 -# Free Software Foundation, Inc. +# 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, +# 2011, 2012 Free Software Foundation, Inc. -timestamp='2009-11-20' +timestamp='2012-04-18' # This file is (in principle) common to ALL GNU software. # The presence of a machine in this file suggests that SOME GNU software @@ -21,9 +21,7 @@ timestamp='2009-11-20' # GNU General Public License for more details. # # You should have received a copy of the GNU General Public License -# along with this program; if not, write to the Free Software -# Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston, MA -# 02110-1301, USA. +# along with this program; if not, see . # # As a special exception to the GNU General Public License, if you # distribute this file as part of a program that contains a @@ -75,8 +73,9 @@ Report bugs and patches to ." version="\ GNU config.sub ($timestamp) -Copyright (C) 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, -2002, 2003, 2004, 2005, 2006, 2007, 2008 Free Software Foundation, Inc. +Copyright (C) 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999, 2000, +2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011, 2012 +Free Software Foundation, Inc. This is free software; see the source for copying conditions. There is NO warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE." @@ -123,13 +122,18 @@ esac # Here we must recognize all the valid KERNEL-OS combinations. maybe_os=`echo $1 | sed 's/^\(.*\)-\([^-]*-[^-]*\)$/\2/'` case $maybe_os in - nto-qnx* | linux-gnu* | linux-dietlibc | linux-newlib* | linux-uclibc* | \ - uclinux-uclibc* | uclinux-gnu* | kfreebsd*-gnu* | knetbsd*-gnu* | netbsd*-gnu* | \ + nto-qnx* | linux-gnu* | linux-android* | linux-dietlibc | linux-newlib* | \ + linux-uclibc* | uclinux-uclibc* | uclinux-gnu* | kfreebsd*-gnu* | \ + knetbsd*-gnu* | netbsd*-gnu* | \ kopensolaris*-gnu* | \ storm-chaos* | os2-emx* | rtmk-nova*) os=-$maybe_os basic_machine=`echo $1 | sed 's/^\(.*\)-\([^-]*-[^-]*\)$/\1/'` ;; + android-linux) + os=-linux-android + basic_machine=`echo $1 | sed 's/^\(.*\)-\([^-]*-[^-]*\)$/\1/'`-unknown + ;; *) basic_machine=`echo $1 | sed 's/-[^-]*$//'` if [ $basic_machine != $1 ] @@ -156,8 +160,8 @@ case $os in os= basic_machine=$1 ;; - -bluegene*) - os=-cnk + -bluegene*) + os=-cnk ;; -sim | -cisco | -oki | -wec | -winbond) os= @@ -173,10 +177,10 @@ case $os in os=-chorusos basic_machine=$1 ;; - -chorusrdb) - os=-chorusrdb + -chorusrdb) + os=-chorusrdb basic_machine=$1 - ;; + ;; -hiux*) os=-hiuxwe2 ;; @@ -221,6 +225,12 @@ case $os in -isc*) basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'` ;; + -lynx*178) + os=-lynxos178 + ;; + -lynx*5) + os=-lynxos5 + ;; -lynx*) os=-lynxos ;; @@ -245,17 +255,22 @@ case $basic_machine in # Some are omitted here because they have special meanings below. 1750a | 580 \ | a29k \ + | aarch64 | aarch64_be \ | alpha | alphaev[4-8] | alphaev56 | alphaev6[78] | alphapca5[67] \ | alpha64 | alpha64ev[4-8] | alpha64ev56 | alpha64ev6[78] | alpha64pca5[67] \ | am33_2.0 \ | arc | arm | arm[bl]e | arme[lb] | armv[2345] | armv[345][lb] | avr | avr32 \ + | be32 | be64 \ | bfin \ | c4x | clipper \ | d10v | d30v | dlx | dsp16xx \ + | epiphany \ | fido | fr30 | frv \ | h8300 | h8500 | hppa | hppa1.[01] | hppa2.0 | hppa2.0[nw] | hppa64 \ + | hexagon \ | i370 | i860 | i960 | ia64 \ | ip2k | iq2000 \ + | le32 | le64 \ | lm32 \ | m32c | m32r | m32rle | m68000 | m68k | m88k \ | maxq | mb | microblaze | mcore | mep | metag \ @@ -281,29 +296,39 @@ case $basic_machine in | moxie \ | mt \ | msp430 \ + | nds32 | nds32le | nds32be \ | nios | nios2 \ | ns16k | ns32k \ + | open8 \ | or32 \ | pdp10 | pdp11 | pj | pjl \ - | powerpc | powerpc64 | powerpc64le | powerpcle | ppcbe \ + | powerpc | powerpc64 | powerpc64le | powerpcle \ | pyramid \ - | rx \ + | rl78 | rx \ | score \ | sh | sh[1234] | sh[24]a | sh[24]aeb | sh[23]e | sh[34]eb | sheb | shbe | shle | sh[1234]le | sh3ele \ | sh64 | sh64le \ | sparc | sparc64 | sparc64b | sparc64v | sparc86x | sparclet | sparclite \ | sparcv8 | sparcv9 | sparcv9b | sparcv9v \ - | spu | strongarm \ - | tahoe | thumb | tic4x | tic80 | tron \ + | spu \ + | tahoe | tic4x | tic54x | tic55x | tic6x | tic80 | tron \ | ubicom32 \ - | v850 | v850e \ + | v850 | v850e | v850e1 | v850e2 | v850es | v850e2v3 \ | we32k \ - | x86 | xc16x | xscale | xscalee[bl] | xstormy16 | xtensa \ + | x86 | xc16x | xstormy16 | xtensa \ | z8k | z80) basic_machine=$basic_machine-unknown ;; - m6811 | m68hc11 | m6812 | m68hc12 | picochip) - # Motorola 68HC11/12. + c54x) + basic_machine=tic54x-unknown + ;; + c55x) + basic_machine=tic55x-unknown + ;; + c6x) + basic_machine=tic6x-unknown + ;; + m6811 | m68hc11 | m6812 | m68hc12 | m68hcs12x | picochip) basic_machine=$basic_machine-unknown os=-none ;; @@ -313,6 +338,21 @@ case $basic_machine in basic_machine=mt-unknown ;; + strongarm | thumb | xscale) + basic_machine=arm-unknown + ;; + xgate) + basic_machine=$basic_machine-unknown + os=-none + ;; + xscaleeb) + basic_machine=armeb-unknown + ;; + + xscaleel) + basic_machine=armel-unknown + ;; + # We use `pc' rather than `unknown' # because (1) that's what they normally are, and # (2) the word "unknown" tends to confuse beginning users. @@ -327,21 +367,25 @@ case $basic_machine in # Recognize the basic CPU types with company name. 580-* \ | a29k-* \ + | aarch64-* | aarch64_be-* \ | alpha-* | alphaev[4-8]-* | alphaev56-* | alphaev6[78]-* \ | alpha64-* | alpha64ev[4-8]-* | alpha64ev56-* | alpha64ev6[78]-* \ | alphapca5[67]-* | alpha64pca5[67]-* | arc-* \ | arm-* | armbe-* | armle-* | armeb-* | armv*-* \ | avr-* | avr32-* \ + | be32-* | be64-* \ | bfin-* | bs2000-* \ - | c[123]* | c30-* | [cjt]90-* | c4x-* | c54x-* | c55x-* | c6x-* \ + | c[123]* | c30-* | [cjt]90-* | c4x-* \ | clipper-* | craynv-* | cydra-* \ | d10v-* | d30v-* | dlx-* \ | elxsi-* \ | f30[01]-* | f700-* | fido-* | fr30-* | frv-* | fx80-* \ | h8300-* | h8500-* \ | hppa-* | hppa1.[01]-* | hppa2.0-* | hppa2.0[nw]-* | hppa64-* \ + | hexagon-* \ | i*86-* | i860-* | i960-* | ia64-* \ | ip2k-* | iq2000-* \ + | le32-* | le64-* \ | lm32-* \ | m32c-* | m32r-* | m32rle-* \ | m68000-* | m680[012346]0-* | m68360-* | m683?2-* | m68k-* \ @@ -367,25 +411,29 @@ case $basic_machine in | mmix-* \ | mt-* \ | msp430-* \ + | nds32-* | nds32le-* | nds32be-* \ | nios-* | nios2-* \ | none-* | np1-* | ns16k-* | ns32k-* \ + | open8-* \ | orion-* \ | pdp10-* | pdp11-* | pj-* | pjl-* | pn-* | power-* \ - | powerpc-* | powerpc64-* | powerpc64le-* | powerpcle-* | ppcbe-* \ + | powerpc-* | powerpc64-* | powerpc64le-* | powerpcle-* \ | pyramid-* \ - | romp-* | rs6000-* | rx-* \ + | rl78-* | romp-* | rs6000-* | rx-* \ | sh-* | sh[1234]-* | sh[24]a-* | sh[24]aeb-* | sh[23]e-* | sh[34]eb-* | sheb-* | shbe-* \ | shle-* | sh[1234]le-* | sh3ele-* | sh64-* | sh64le-* \ | sparc-* | sparc64-* | sparc64b-* | sparc64v-* | sparc86x-* | sparclet-* \ | sparclite-* \ - | sparcv8-* | sparcv9-* | sparcv9b-* | sparcv9v-* | strongarm-* | sv1-* | sx?-* \ - | tahoe-* | thumb-* \ - | tic30-* | tic4x-* | tic54x-* | tic55x-* | tic6x-* | tic80-* | tile-* \ + | sparcv8-* | sparcv9-* | sparcv9b-* | sparcv9v-* | sv1-* | sx?-* \ + | tahoe-* \ + | tic30-* | tic4x-* | tic54x-* | tic55x-* | tic6x-* | tic80-* \ + | tile*-* \ | tron-* \ | ubicom32-* \ - | v850-* | v850e-* | vax-* \ + | v850-* | v850e-* | v850e1-* | v850es-* | v850e2-* | v850e2v3-* \ + | vax-* \ | we32k-* \ - | x86-* | x86_64-* | xc16x-* | xps100-* | xscale-* | xscalee[bl]-* \ + | x86-* | x86_64-* | xc16x-* | xps100-* \ | xstormy16-* | xtensa*-* \ | ymp-* \ | z8k-* | z80-*) @@ -410,7 +458,7 @@ case $basic_machine in basic_machine=a29k-amd os=-udi ;; - abacus) + abacus) basic_machine=abacus-unknown ;; adobe68k) @@ -480,11 +528,20 @@ case $basic_machine in basic_machine=powerpc-ibm os=-cnk ;; + c54x-*) + basic_machine=tic54x-`echo $basic_machine | sed 's/^[^-]*-//'` + ;; + c55x-*) + basic_machine=tic55x-`echo $basic_machine | sed 's/^[^-]*-//'` + ;; + c6x-*) + basic_machine=tic6x-`echo $basic_machine | sed 's/^[^-]*-//'` + ;; c90) basic_machine=c90-cray os=-unicos ;; - cegcc) + cegcc) basic_machine=arm-unknown os=-cegcc ;; @@ -516,7 +573,7 @@ case $basic_machine in basic_machine=craynv-cray os=-unicosmp ;; - cr16) + cr16 | cr16-*) basic_machine=cr16-unknown os=-elf ;; @@ -674,7 +731,6 @@ case $basic_machine in i370-ibm* | ibm*) basic_machine=i370-ibm ;; -# I'm not sure what "Sysv32" means. Should this be sysv3.2? i*86v32) basic_machine=`echo $1 | sed -e 's/86.*/86-pc/'` os=-sysv32 @@ -732,7 +788,7 @@ case $basic_machine in basic_machine=ns32k-utek os=-sysv ;; - microblaze) + microblaze) basic_machine=microblaze-xilinx ;; mingw32) @@ -771,10 +827,18 @@ case $basic_machine in ms1-*) basic_machine=`echo $basic_machine | sed -e 's/ms1-/mt-/'` ;; + msys) + basic_machine=i386-pc + os=-msys + ;; mvs) basic_machine=i370-ibm os=-mvs ;; + nacl) + basic_machine=le32-unknown + os=-nacl + ;; ncr3000) basic_machine=i486-ncr os=-sysv4 @@ -839,6 +903,12 @@ case $basic_machine in np1) basic_machine=np1-gould ;; + neo-tandem) + basic_machine=neo-tandem + ;; + nse-tandem) + basic_machine=nse-tandem + ;; nsr-tandem) basic_machine=nsr-tandem ;; @@ -921,9 +991,10 @@ case $basic_machine in ;; power) basic_machine=power-ibm ;; - ppc) basic_machine=powerpc-unknown + ppc | ppcbe) basic_machine=powerpc-unknown ;; - ppc-*) basic_machine=powerpc-`echo $basic_machine | sed 's/^[^-]*-//'` + ppc-* | ppcbe-*) + basic_machine=powerpc-`echo $basic_machine | sed 's/^[^-]*-//'` ;; ppcle | powerpclittle | ppc-le | powerpc-little) basic_machine=powerpcle-unknown @@ -1017,6 +1088,9 @@ case $basic_machine in basic_machine=i860-stratus os=-sysv4 ;; + strongarm-* | thumb-*) + basic_machine=arm-`echo $basic_machine | sed 's/^[^-]*-//'` + ;; sun2) basic_machine=m68000-sun ;; @@ -1073,20 +1147,8 @@ case $basic_machine in basic_machine=t90-cray os=-unicos ;; - tic54x | c54x*) - basic_machine=tic54x-unknown - os=-coff - ;; - tic55x | c55x*) - basic_machine=tic55x-unknown - os=-coff - ;; - tic6x | c6x*) - basic_machine=tic6x-unknown - os=-coff - ;; tile*) - basic_machine=tile-unknown + basic_machine=$basic_machine-unknown os=-linux-gnu ;; tx39) @@ -1156,6 +1218,9 @@ case $basic_machine in xps | xps100) basic_machine=xps100-honeywell ;; + xscale-* | xscalee[bl]-*) + basic_machine=`echo $basic_machine | sed 's/^xscale/arm/'` + ;; ymp) basic_machine=ymp-cray os=-unicos @@ -1253,11 +1318,11 @@ esac if [ x"$os" != x"" ] then case $os in - # First match some system type aliases - # that might get confused with valid system types. + # First match some system type aliases + # that might get confused with valid system types. # -solaris* is a basic system type, with this one exception. - -auroraux) - os=-auroraux + -auroraux) + os=-auroraux ;; -solaris1 | -solaris1.*) os=`echo $os | sed -e 's|solaris1|sunos4|'` @@ -1293,8 +1358,9 @@ case $os in | -ptx* | -coff* | -ecoff* | -winnt* | -domain* | -vsta* \ | -udi* | -eabi* | -lites* | -ieee* | -go32* | -aux* \ | -chorusos* | -chorusrdb* | -cegcc* \ - | -cygwin* | -pe* | -psos* | -moss* | -proelf* | -rtems* \ - | -mingw32* | -linux-gnu* | -linux-newlib* | -linux-uclibc* \ + | -cygwin* | -msys* | -pe* | -psos* | -moss* | -proelf* | -rtems* \ + | -mingw32* | -linux-gnu* | -linux-android* \ + | -linux-newlib* | -linux-uclibc* \ | -uxpv* | -beos* | -mpeix* | -udk* \ | -interix* | -uwin* | -mks* | -rhapsody* | -darwin* | -opened* \ | -openstep* | -oskit* | -conix* | -pw32* | -nonstopux* \ @@ -1341,7 +1407,7 @@ case $os in -opened*) os=-openedition ;; - -os400*) + -os400*) os=-os400 ;; -wince*) @@ -1390,7 +1456,7 @@ case $os in -sinix*) os=-sysv4 ;; - -tpf*) + -tpf*) os=-tpf ;; -triton*) @@ -1435,6 +1501,8 @@ case $os in -dicos*) os=-dicos ;; + -nacl*) + ;; -none) ;; *) @@ -1457,10 +1525,10 @@ else # system, and we'll never get to this point. case $basic_machine in - score-*) + score-*) os=-elf ;; - spu-*) + spu-*) os=-elf ;; *-acorn) @@ -1472,8 +1540,20 @@ case $basic_machine in arm*-semi) os=-aout ;; - c4x-* | tic4x-*) - os=-coff + c4x-* | tic4x-*) + os=-coff + ;; + hexagon-*) + os=-elf + ;; + tic54x-*) + os=-coff + ;; + tic55x-*) + os=-coff + ;; + tic6x-*) + os=-coff ;; # This must come before the *-dec entry. pdp10-*) @@ -1493,14 +1573,11 @@ case $basic_machine in ;; m68000-sun) os=-sunos3 - # This also exists in the configure program, but was not the - # default. - # os=-sunos4 ;; m68*-cisco) os=-aout ;; - mep-*) + mep-*) os=-elf ;; mips*-cisco) @@ -1527,7 +1604,7 @@ case $basic_machine in *-ibm) os=-aix ;; - *-knuth) + *-knuth) os=-mmixware ;; *-wec) diff --git a/configure b/configure index b625925..4d21cc4 100755 --- a/configure +++ b/configure @@ -1,13 +1,11 @@ #! /bin/sh # Guess values for system-dependent variables and create Makefiles. -# Generated by GNU Autoconf 2.67 for gnunet 0.9.3. +# Generated by GNU Autoconf 2.69 for gnunet 0.9.5a. # # Report bugs to . # # -# Copyright (C) 1992, 1993, 1994, 1995, 1996, 1998, 1999, 2000, 2001, -# 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010 Free Software -# Foundation, Inc. +# Copyright (C) 1992-1996, 1998-2012 Free Software Foundation, Inc. # # # This configure script is free software; the Free Software Foundation @@ -91,6 +89,7 @@ fi IFS=" "" $as_nl" # Find who we are. Look in the path if we contain no directory separator. +as_myself= case $0 in #(( *[\\/]* ) as_myself=$0 ;; *) as_save_IFS=$IFS; IFS=$PATH_SEPARATOR @@ -135,6 +134,31 @@ export LANGUAGE # CDPATH. (unset CDPATH) >/dev/null 2>&1 && unset CDPATH +# Use a proper internal environment variable to ensure we don't fall + # into an infinite loop, continuously re-executing ourselves. + if test x"${_as_can_reexec}" != xno && test "x$CONFIG_SHELL" != x; then + _as_can_reexec=no; export _as_can_reexec; + # We cannot yet assume a decent shell, so we have to provide a +# neutralization value for shells without unset; and this also +# works around shells that cannot unset nonexistent variables. +# Preserve -v and -x to the replacement shell. +BASH_ENV=/dev/null +ENV=/dev/null +(unset BASH_ENV) >/dev/null 2>&1 && unset BASH_ENV ENV +case $- in # (((( + *v*x* | *x*v* ) as_opts=-vx ;; + *v* ) as_opts=-v ;; + *x* ) as_opts=-x ;; + * ) as_opts= ;; +esac +exec $CONFIG_SHELL $as_opts "$as_myself" ${1+"$@"} +# Admittedly, this is quite paranoid, since all the known shells bail +# out after a failed `exec'. +$as_echo "$0: could not re-execute with $CONFIG_SHELL" >&2 +as_fn_exit 255 + fi + # We don't want this to propagate to other subprocesses. + { _as_can_reexec=; unset _as_can_reexec;} if test "x$CONFIG_SHELL" = x; then as_bourne_compatible="if test -n \"\${ZSH_VERSION+set}\" && (emulate sh) >/dev/null 2>&1; then : emulate sh @@ -168,11 +192,20 @@ if ( set x; as_fn_ret_success y && test x = \"\$1\" ); then : else exitcode=1; echo positional parameters were not saved. fi -test x\$exitcode = x0 || exit 1" +test x\$exitcode = x0 || exit 1 +test -x / || exit 1" as_suggested=" as_lineno_1=";as_suggested=$as_suggested$LINENO;as_suggested=$as_suggested" as_lineno_1a=\$LINENO as_lineno_2=";as_suggested=$as_suggested$LINENO;as_suggested=$as_suggested" as_lineno_2a=\$LINENO eval 'test \"x\$as_lineno_1'\$as_run'\" != \"x\$as_lineno_2'\$as_run'\" && test \"x\`expr \$as_lineno_1'\$as_run' + 1\`\" = \"x\$as_lineno_2'\$as_run'\"' || exit 1 + + test -n \"\${ZSH_VERSION+set}\${BASH_VERSION+set}\" || ( + ECHO='\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\' + ECHO=\$ECHO\$ECHO\$ECHO\$ECHO\$ECHO + ECHO=\$ECHO\$ECHO\$ECHO\$ECHO\$ECHO\$ECHO + PATH=/empty FPATH=/empty; export PATH FPATH + test \"X\`printf %s \$ECHO\`\" = \"X\$ECHO\" \\ + || test \"X\`print -r -- \$ECHO\`\" = \"X\$ECHO\" ) || exit 1 test \$(( 1 + 1 )) = 2 || exit 1" if (eval "$as_required") 2>/dev/null; then : as_have_required=yes @@ -213,14 +246,25 @@ IFS=$as_save_IFS if test "x$CONFIG_SHELL" != x; then : - # We cannot yet assume a decent shell, so we have to provide a - # neutralization value for shells without unset; and this also - # works around shells that cannot unset nonexistent variables. - BASH_ENV=/dev/null - ENV=/dev/null - (unset BASH_ENV) >/dev/null 2>&1 && unset BASH_ENV ENV - export CONFIG_SHELL - exec "$CONFIG_SHELL" "$as_myself" ${1+"$@"} + export CONFIG_SHELL + # We cannot yet assume a decent shell, so we have to provide a +# neutralization value for shells without unset; and this also +# works around shells that cannot unset nonexistent variables. +# Preserve -v and -x to the replacement shell. +BASH_ENV=/dev/null +ENV=/dev/null +(unset BASH_ENV) >/dev/null 2>&1 && unset BASH_ENV ENV +case $- in # (((( + *v*x* | *x*v* ) as_opts=-vx ;; + *v* ) as_opts=-v ;; + *x* ) as_opts=-x ;; + * ) as_opts= ;; +esac +exec $CONFIG_SHELL $as_opts "$as_myself" ${1+"$@"} +# Admittedly, this is quite paranoid, since all the known shells bail +# out after a failed `exec'. +$as_echo "$0: could not re-execute with $CONFIG_SHELL" >&2 +exit 255 fi if test x$as_have_required = xno; then : @@ -323,6 +367,14 @@ $as_echo X"$as_dir" | } # as_fn_mkdir_p + +# as_fn_executable_p FILE +# ----------------------- +# Test if FILE is an executable regular file. +as_fn_executable_p () +{ + test -f "$1" && test -x "$1" +} # as_fn_executable_p # as_fn_append VAR VALUE # ---------------------- # Append the text in VALUE to the end of the definition contained in VAR. Take @@ -444,6 +496,10 @@ as_cr_alnum=$as_cr_Letters$as_cr_digits chmod +x "$as_me.lineno" || { $as_echo "$as_me: error: cannot create $as_me.lineno; rerun with a POSIX shell" >&2; as_fn_exit 1; } + # If we had to re-execute with $CONFIG_SHELL, we're ensured to have + # already done that, so ensure we don't try to do so again and fall + # in an infinite loop. This has already happened in practice. + _as_can_reexec=no; export _as_can_reexec # Don't try to exec as it changes $[0], causing all sort of problems # (the dirname of $[0] is not the place where we might find the # original and so on. Autoconf is especially sensitive to this). @@ -478,16 +534,16 @@ if (echo >conf$$.file) 2>/dev/null; then # ... but there are two gotchas: # 1) On MSYS, both `ln -s file dir' and `ln file dir' fail. # 2) DJGPP < 2.04 has no symlinks; `ln -s' creates a wrapper executable. - # In both cases, we have to default to `cp -p'. + # In both cases, we have to default to `cp -pR'. ln -s conf$$.file conf$$.dir 2>/dev/null && test ! -f conf$$.exe || - as_ln_s='cp -p' + as_ln_s='cp -pR' elif ln conf$$.file conf$$ 2>/dev/null; then as_ln_s=ln else - as_ln_s='cp -p' + as_ln_s='cp -pR' fi else - as_ln_s='cp -p' + as_ln_s='cp -pR' fi rm -f conf$$ conf$$.exe conf$$.dir/conf$$.file conf$$.file rmdir conf$$.dir 2>/dev/null @@ -499,28 +555,8 @@ else as_mkdir_p=false fi -if test -x / >/dev/null 2>&1; then - as_test_x='test -x' -else - if ls -dL / >/dev/null 2>&1; then - as_ls_L_option=L - else - as_ls_L_option= - fi - as_test_x=' - eval sh -c '\'' - if test -d "$1"; then - test -d "$1/."; - else - case $1 in #( - -*)set "./$1";; - esac; - case `ls -ld'$as_ls_L_option' "$1" 2>/dev/null` in #(( - ???[sx]*):;;*)false;;esac;fi - '\'' sh - ' -fi -as_executable_p=$as_test_x +as_test_x='test -x' +as_executable_p=as_fn_executable_p # Sed expression to map a string onto a valid CPP name. as_tr_cpp="eval sed 'y%*$as_cr_letters%P$as_cr_LETTERS%;s%[^_$as_cr_alnum]%_%g'" @@ -528,160 +564,13 @@ as_tr_cpp="eval sed 'y%*$as_cr_letters%P$as_cr_LETTERS%;s%[^_$as_cr_alnum]%_%g'" # Sed expression to map a string onto a valid variable name. as_tr_sh="eval sed 'y%*+%pp%;s%[^_$as_cr_alnum]%_%g'" - - -# Check that we are running under the correct shell. SHELL=${CONFIG_SHELL-/bin/sh} -case X$lt_ECHO in -X*--fallback-echo) - # Remove one level of quotation (which was required for Make). - ECHO=`echo "$lt_ECHO" | sed 's,\\\\\$\\$0,'$0','` - ;; -esac - -ECHO=${lt_ECHO-echo} -if test "X$1" = X--no-reexec; then - # Discard the --no-reexec flag, and continue. - shift -elif test "X$1" = X--fallback-echo; then - # Avoid inline document here, it may be left over - : -elif test "X`{ $ECHO '\t'; } 2>/dev/null`" = 'X\t' ; then - # Yippee, $ECHO works! - : -else - # Restart under the correct shell. - exec $SHELL "$0" --no-reexec ${1+"$@"} -fi - -if test "X$1" = X--fallback-echo; then - # used as fallback echo - shift - cat <<_LT_EOF -$* -_LT_EOF - exit 0 -fi - -# The HP-UX ksh and POSIX shell print the target directory to stdout -# if CDPATH is set. -(unset CDPATH) >/dev/null 2>&1 && unset CDPATH - -if test -z "$lt_ECHO"; then - if test "X${echo_test_string+set}" != Xset; then - # find a string as large as possible, as long as the shell can cope with it - for cmd in 'sed 50q "$0"' 'sed 20q "$0"' 'sed 10q "$0"' 'sed 2q "$0"' 'echo test'; do - # expected sizes: less than 2Kb, 1Kb, 512 bytes, 16 bytes, ... - if { echo_test_string=`eval $cmd`; } 2>/dev/null && - { test "X$echo_test_string" = "X$echo_test_string"; } 2>/dev/null - then - break - fi - done - fi - - if test "X`{ $ECHO '\t'; } 2>/dev/null`" = 'X\t' && - echo_testing_string=`{ $ECHO "$echo_test_string"; } 2>/dev/null` && - test "X$echo_testing_string" = "X$echo_test_string"; then - : - else - # The Solaris, AIX, and Digital Unix default echo programs unquote - # backslashes. This makes it impossible to quote backslashes using - # echo "$something" | sed 's/\\/\\\\/g' - # - # So, first we look for a working echo in the user's PATH. - - lt_save_ifs="$IFS"; IFS=$PATH_SEPARATOR - for dir in $PATH /usr/ucb; do - IFS="$lt_save_ifs" - if (test -f $dir/echo || test -f $dir/echo$ac_exeext) && - test "X`($dir/echo '\t') 2>/dev/null`" = 'X\t' && - echo_testing_string=`($dir/echo "$echo_test_string") 2>/dev/null` && - test "X$echo_testing_string" = "X$echo_test_string"; then - ECHO="$dir/echo" - break - fi - done - IFS="$lt_save_ifs" - - if test "X$ECHO" = Xecho; then - # We didn't find a better echo, so look for alternatives. - if test "X`{ print -r '\t'; } 2>/dev/null`" = 'X\t' && - echo_testing_string=`{ print -r "$echo_test_string"; } 2>/dev/null` && - test "X$echo_testing_string" = "X$echo_test_string"; then - # This shell has a builtin print -r that does the trick. - ECHO='print -r' - elif { test -f /bin/ksh || test -f /bin/ksh$ac_exeext; } && - test "X$CONFIG_SHELL" != X/bin/ksh; then - # If we have ksh, try running configure again with it. - ORIGINAL_CONFIG_SHELL=${CONFIG_SHELL-/bin/sh} - export ORIGINAL_CONFIG_SHELL - CONFIG_SHELL=/bin/ksh - export CONFIG_SHELL - exec $CONFIG_SHELL "$0" --no-reexec ${1+"$@"} - else - # Try using printf. - ECHO='printf %s\n' - if test "X`{ $ECHO '\t'; } 2>/dev/null`" = 'X\t' && - echo_testing_string=`{ $ECHO "$echo_test_string"; } 2>/dev/null` && - test "X$echo_testing_string" = "X$echo_test_string"; then - # Cool, printf works - : - elif echo_testing_string=`($ORIGINAL_CONFIG_SHELL "$0" --fallback-echo '\t') 2>/dev/null` && - test "X$echo_testing_string" = 'X\t' && - echo_testing_string=`($ORIGINAL_CONFIG_SHELL "$0" --fallback-echo "$echo_test_string") 2>/dev/null` && - test "X$echo_testing_string" = "X$echo_test_string"; then - CONFIG_SHELL=$ORIGINAL_CONFIG_SHELL - export CONFIG_SHELL - SHELL="$CONFIG_SHELL" - export SHELL - ECHO="$CONFIG_SHELL $0 --fallback-echo" - elif echo_testing_string=`($CONFIG_SHELL "$0" --fallback-echo '\t') 2>/dev/null` && - test "X$echo_testing_string" = 'X\t' && - echo_testing_string=`($CONFIG_SHELL "$0" --fallback-echo "$echo_test_string") 2>/dev/null` && - test "X$echo_testing_string" = "X$echo_test_string"; then - ECHO="$CONFIG_SHELL $0 --fallback-echo" - else - # maybe with a smaller string... - prev=: - - for cmd in 'echo test' 'sed 2q "$0"' 'sed 10q "$0"' 'sed 20q "$0"' 'sed 50q "$0"'; do - if { test "X$echo_test_string" = "X`eval $cmd`"; } 2>/dev/null - then - break - fi - prev="$cmd" - done - - if test "$prev" != 'sed 50q "$0"'; then - echo_test_string=`eval $prev` - export echo_test_string - exec ${ORIGINAL_CONFIG_SHELL-${CONFIG_SHELL-/bin/sh}} "$0" ${1+"$@"} - else - # Oops. We lost completely, so just stick with echo. - ECHO=echo - fi - fi - fi - fi - fi -fi - -# Copy echo and quote the copy suitably for passing to libtool from -# the Makefile, instead of quoting the original, which is used later. -lt_ECHO=$ECHO -if test "X$lt_ECHO" = "X$CONFIG_SHELL $0 --fallback-echo"; then - lt_ECHO="$CONFIG_SHELL \\\$\$0 --fallback-echo" -fi - - - - lt_ltdl_dir='libltdl' lt_dlopen_dir="$lt_ltdl_dir" + test -n "$DJDIR" || exec 7<&0 &1 @@ -705,8 +594,8 @@ MAKEFLAGS= # Identity of this package. PACKAGE_NAME='gnunet' PACKAGE_TARNAME='gnunet' -PACKAGE_VERSION='0.9.3' -PACKAGE_STRING='gnunet 0.9.3' +PACKAGE_VERSION='0.9.5a' +PACKAGE_STRING='gnunet 0.9.5a' PACKAGE_BUGREPORT='bug-gnunet@gnu.org' PACKAGE_URL='' @@ -753,6 +642,8 @@ ltdl_LIBOBJS am__EXEEXT_FALSE am__EXEEXT_TRUE LTLIBOBJS +gitcommand +svnversioncommand USE_COVERAGE_FALSE USE_COVERAGE_TRUE HAVE_EXPERIMENTAL_FALSE @@ -767,7 +658,14 @@ ENABLE_MONKEY_FALSE ENABLE_MONKEY_TRUE ENABLE_TEST_RUN_FALSE ENABLE_TEST_RUN_TRUE +WITH_LL_FALSE +WITH_LL_TRUE +HAVE_GNUTLS_FALSE +HAVE_GNUTLS_TRUE GNUNETDNS_GROUP +INSTALL_NSS_FALSE +INSTALL_NSS_TRUE +NSS_DIR HAVE_SUDO_FALSE HAVE_SUDO_TRUE SUDO_BINARY @@ -798,8 +696,6 @@ MSGFMT_015 GMSGFMT MSGFMT USE_NLS -HAVE_PYTHON_PEXPECT_FALSE -HAVE_PYTHON_PEXPECT_TRUE HAVE_PYTHON_FALSE HAVE_PYTHON_TRUE pkgpyexecdir @@ -836,8 +732,22 @@ LTLIBICONV LIBICONV HAVE_GLIBCNSS_FALSE HAVE_GLIBCNSS_TRUE +HAVE_LIBGTOP_FALSE +HAVE_LIBGTOP_TRUE +LIBGTOP_LIBS +LIBGTOP_CFLAGS +HAVE_GLIB2_FALSE +HAVE_GLIB2_TRUE +GLIB_MKENUMS +GOBJECT_QUERY +GLIB_GENMARSHAL +GLIB_LIBS +GLIB_CFLAGS +PKG_CONFIG HAVE_LIBGLPK_FALSE HAVE_LIBGLPK_TRUE +HAVE_LIBCURL_FALSE +HAVE_LIBCURL_TRUE LIBCURL LIBCURL_CPPFLAGS _libcurl_config @@ -845,6 +755,8 @@ LIBGCRYPT_LIBS LIBGCRYPT_CFLAGS LIBGCRYPT_CONFIG build_target +GNU_FALSE +GNU_TRUE LINUX_FALSE LINUX_TRUE OPENBSD_FALSE @@ -891,8 +803,9 @@ OTOOL LIPO NMEDIT DSYMUTIL -lt_ECHO +MANIFEST_TOOL RANLIB +ac_ct_AR AR NM ac_ct_DUMPBIN @@ -923,6 +836,7 @@ CPP am__fastdepCC_FALSE am__fastdepCC_TRUE CCDEPMODE +am__nodep AMDEPBACKSLASH AMDEP_FALSE AMDEP_TRUE @@ -938,6 +852,8 @@ CFLAGS CC AM_BACKSLASH AM_DEFAULT_VERBOSITY +AM_DEFAULT_V +AM_V am__untar am__tar AMTAR @@ -1021,6 +937,7 @@ enable_shared with_pic enable_fast_install with_gnu_ld +with_sysroot enable_libtool_lock with_included_ltdl with_ltdl_include @@ -1032,7 +949,10 @@ with_libgcrypt_prefix enable_gcc_hardening enable_linker_hardening enable_logging +enable_poisoning with_libcurl +with_libidn +enable_glibtest with_extractor enable_rpath with_libiconv_prefix @@ -1049,13 +969,17 @@ with_daemon_home_dir with_daemon_config_dir enable_framework with_sudo +with_nssdir with_gnunetdns +with_gnutls +with_ll enable_testruns enable_monkey enable_expensivetests enable_javaports enable_benchmarks enable_experimental +enable_heapstats enable_windows_workarounds enable_coverage ' @@ -1074,7 +998,8 @@ CCC OBJC OBJCFLAGS CXXCPP -XMKMF' +XMKMF +PYTHON' ac_subdirs_all='libltdl' # Initialize some variables set by options. @@ -1479,7 +1404,7 @@ Try \`$0 --help' for more information" $as_echo "$as_me: WARNING: you should use --build, --host, --target" >&2 expr "x$ac_option" : ".*[^-._$as_cr_alnum]" >/dev/null && $as_echo "$as_me: WARNING: invalid host type: $ac_option" >&2 - : ${build_alias=$ac_option} ${host_alias=$ac_option} ${target_alias=$ac_option} + : "${build_alias=$ac_option} ${host_alias=$ac_option} ${target_alias=$ac_option}" ;; esac @@ -1530,8 +1455,6 @@ target=$target_alias if test "x$host_alias" != x; then if test "x$build_alias" = x; then cross_compiling=maybe - $as_echo "$as_me: WARNING: if you wanted to set the --build type, don't use --host. - If a cross compiler is detected then cross compile mode will be used" >&2 elif test "x$build_alias" != "x$host_alias"; then cross_compiling=yes fi @@ -1617,7 +1540,7 @@ if test "$ac_init_help" = "long"; then # Omit some internal or obsolete options to make the list less imposing. # This message is too long to be a string in the A/UX 3.1 sh. cat <<_ACEOF -\`configure' configures gnunet 0.9.3 to adapt to many kinds of systems. +\`configure' configures gnunet 0.9.5a to adapt to many kinds of systems. Usage: $0 [OPTION]... [VAR=VALUE]... @@ -1692,7 +1615,7 @@ fi if test -n "$ac_init_help"; then case $ac_init_help in - short | recursive ) echo "Configuration of gnunet 0.9.3:";; + short | recursive ) echo "Configuration of gnunet 0.9.5a:";; esac cat <<\_ACEOF @@ -1717,6 +1640,9 @@ Optional Features: --enable-logging[=value] Enable logging calls. Possible values: yes,no,verbose,veryverbose ('yes' is the default) + --enable-poisoning enable poisoning of freed memory (good for + debugging) + --disable-glibtest do not try to compile and run a test GLIB program --disable-rpath do not hardcode runtime library paths --disable-mysql-version-check do not check MySQL version --disable-nls do not use Native Language Support @@ -1728,6 +1654,7 @@ Optional Features: (default is NO) --enable-benchmarks enable running benchmarks during make check --enable-experimental enable compiling experimental code + --enable-heapstats enable expensive heap statistics --enable-windows_workarounds enable workarounds used on Windows (only useful for test cases) @@ -1736,9 +1663,11 @@ Optional Features: Optional Packages: --with-PACKAGE[=ARG] use PACKAGE [ARG=yes] --without-PACKAGE do not use PACKAGE (same as --with-PACKAGE=no) - --with-pic try to use only PIC/non-PIC objects [default=use + --with-pic[=PKGS] try to use only PIC/non-PIC objects [default=use both] --with-gnu-ld assume the C compiler uses GNU ld [default=no] + --with-sysroot=DIR Search for dependent libraries within DIR + (or the compiler's sysroot if not specified). --with-included-ltdl use the GNU ltdl sources included here --with-ltdl-include=DIR use the ltdl headers installed in DIR --with-ltdl-lib=DIR use the libltdl.la installed in DIR @@ -1747,6 +1676,7 @@ Optional Packages: prefix where LIBGCRYPT is installed (optional) --with-libcurl=PREFIX look for the curl library in PREFIX/lib and headers in PREFIX/include + --with-libidn=DIR Support IDN (needs GNU Libidn) --with-extractor=PFX base of libextractor installation --with-gnu-ld assume the C compiler uses GNU ld default=no --with-libiconv-prefix[=DIR] search for libiconv in DIR/include and DIR/lib @@ -1766,7 +1696,11 @@ Optional Packages: --with-daemon-config-dir=DIR default daemon config directory (/etc) --with-sudo=PATH path to sudo binary (or just yes) + --with-nssdir=PATH where to install NSS plugins --with-gnunetdns=GRPNAME name for gnunetdns group + --with-gnutls=PFX base of gnutls installation + --with-ll=PFX use IBM LoadLeveler (installed at PFX) for running + testbed on SuperMUC. Default is no Some influential environment variables: CC C compiler command @@ -1783,6 +1717,7 @@ Some influential environment variables: OBJCFLAGS Objective C compiler flags CXXCPP C++ preprocessor XMKMF Path to xmkmf, Makefile generator for X Window System + PYTHON the Python interpreter Use these variables to override the choices made by `configure' or to help it to find libraries and programs with nonstandard names/locations. @@ -1850,10 +1785,10 @@ fi test -n "$ac_init_help" && exit $ac_status if $ac_init_version; then cat <<\_ACEOF -gnunet configure 0.9.3 -generated by GNU Autoconf 2.67 +gnunet configure 0.9.5a +generated by GNU Autoconf 2.69 -Copyright (C) 2010 Free Software Foundation, Inc. +Copyright (C) 2012 Free Software Foundation, Inc. This configure script is free software; the Free Software Foundation gives unlimited permission to copy, distribute and modify it. _ACEOF @@ -1897,7 +1832,7 @@ sed 's/^/| /' conftest.$ac_ext >&5 ac_retval=1 fi - eval $as_lineno_stack; test "x$as_lineno_stack" = x && { as_lineno=; unset as_lineno;} + eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno as_fn_set_status $ac_retval } # ac_fn_c_try_compile @@ -1934,7 +1869,7 @@ sed 's/^/| /' conftest.$ac_ext >&5 ac_retval=1 fi - eval $as_lineno_stack; test "x$as_lineno_stack" = x && { as_lineno=; unset as_lineno;} + eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno as_fn_set_status $ac_retval } # ac_fn_c_try_cpp @@ -1972,7 +1907,7 @@ sed 's/^/| /' conftest.$ac_ext >&5 ac_retval=1 fi - eval $as_lineno_stack; test "x$as_lineno_stack" = x && { as_lineno=; unset as_lineno;} + eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno as_fn_set_status $ac_retval } # ac_fn_cxx_try_compile @@ -2010,7 +1945,7 @@ sed 's/^/| /' conftest.$ac_ext >&5 ac_retval=1 fi - eval $as_lineno_stack; test "x$as_lineno_stack" = x && { as_lineno=; unset as_lineno;} + eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno as_fn_set_status $ac_retval } # ac_fn_objc_try_compile @@ -2042,7 +1977,7 @@ $as_echo "$ac_try_echo"; } >&5 test ! -s conftest.err } && test -s conftest$ac_exeext && { test "$cross_compiling" = yes || - $as_test_x conftest$ac_exeext + test -x conftest$ac_exeext }; then : ac_retval=0 else @@ -2056,7 +1991,7 @@ fi # interfere with the next link command; also delete a directory that is # left behind by Apple's compiler. We do this before executing the actions. rm -rf conftest.dSYM conftest_ipa8_conftest.oo - eval $as_lineno_stack; test "x$as_lineno_stack" = x && { as_lineno=; unset as_lineno;} + eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno as_fn_set_status $ac_retval } # ac_fn_c_try_link @@ -2070,7 +2005,7 @@ ac_fn_c_check_header_compile () as_lineno=${as_lineno-"$1"} as_lineno_stack=as_lineno_stack=$as_lineno_stack { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $2" >&5 $as_echo_n "checking for $2... " >&6; } -if eval "test \"\${$3+set}\"" = set; then : +if eval \${$3+:} false; then : $as_echo_n "(cached) " >&6 else cat confdefs.h - <<_ACEOF >conftest.$ac_ext @@ -2088,7 +2023,7 @@ fi eval ac_res=\$$3 { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_res" >&5 $as_echo "$ac_res" >&6; } - eval $as_lineno_stack; test "x$as_lineno_stack" = x && { as_lineno=; unset as_lineno;} + eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno } # ac_fn_c_check_header_compile @@ -2129,7 +2064,7 @@ sed 's/^/| /' conftest.$ac_ext >&5 ac_retval=$ac_status fi rm -rf conftest.dSYM conftest_ipa8_conftest.oo - eval $as_lineno_stack; test "x$as_lineno_stack" = x && { as_lineno=; unset as_lineno;} + eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno as_fn_set_status $ac_retval } # ac_fn_c_try_run @@ -2142,7 +2077,7 @@ ac_fn_c_check_func () as_lineno=${as_lineno-"$1"} as_lineno_stack=as_lineno_stack=$as_lineno_stack { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $2" >&5 $as_echo_n "checking for $2... " >&6; } -if eval "test \"\${$3+set}\"" = set; then : +if eval \${$3+:} false; then : $as_echo_n "(cached) " >&6 else cat confdefs.h - <<_ACEOF >conftest.$ac_ext @@ -2197,7 +2132,7 @@ fi eval ac_res=\$$3 { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_res" >&5 $as_echo "$ac_res" >&6; } - eval $as_lineno_stack; test "x$as_lineno_stack" = x && { as_lineno=; unset as_lineno;} + eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno } # ac_fn_c_check_func @@ -2233,7 +2168,7 @@ sed 's/^/| /' conftest.$ac_ext >&5 ac_retval=1 fi - eval $as_lineno_stack; test "x$as_lineno_stack" = x && { as_lineno=; unset as_lineno;} + eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno as_fn_set_status $ac_retval } # ac_fn_cxx_try_cpp @@ -2265,7 +2200,7 @@ $as_echo "$ac_try_echo"; } >&5 test ! -s conftest.err } && test -s conftest$ac_exeext && { test "$cross_compiling" = yes || - $as_test_x conftest$ac_exeext + test -x conftest$ac_exeext }; then : ac_retval=0 else @@ -2279,7 +2214,7 @@ fi # interfere with the next link command; also delete a directory that is # left behind by Apple's compiler. We do this before executing the actions. rm -rf conftest.dSYM conftest_ipa8_conftest.oo - eval $as_lineno_stack; test "x$as_lineno_stack" = x && { as_lineno=; unset as_lineno;} + eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno as_fn_set_status $ac_retval } # ac_fn_cxx_try_link @@ -2295,7 +2230,7 @@ ac_fn_c_check_decl () as_decl_use=`echo $2|sed -e 's/(/((/' -e 's/)/) 0&/' -e 's/,/) 0& (/g'` { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether $as_decl_name is declared" >&5 $as_echo_n "checking whether $as_decl_name is declared... " >&6; } -if eval "test \"\${$3+set}\"" = set; then : +if eval \${$3+:} false; then : $as_echo_n "(cached) " >&6 else cat confdefs.h - <<_ACEOF >conftest.$ac_ext @@ -2326,7 +2261,7 @@ fi eval ac_res=\$$3 { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_res" >&5 $as_echo "$ac_res" >&6; } - eval $as_lineno_stack; test "x$as_lineno_stack" = x && { as_lineno=; unset as_lineno;} + eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno } # ac_fn_c_check_decl @@ -2339,7 +2274,7 @@ ac_fn_c_check_type () as_lineno=${as_lineno-"$1"} as_lineno_stack=as_lineno_stack=$as_lineno_stack { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $2" >&5 $as_echo_n "checking for $2... " >&6; } -if eval "test \"\${$3+set}\"" = set; then : +if eval \${$3+:} false; then : $as_echo_n "(cached) " >&6 else eval "$3=no" @@ -2380,7 +2315,7 @@ fi eval ac_res=\$$3 { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_res" >&5 $as_echo "$ac_res" >&6; } - eval $as_lineno_stack; test "x$as_lineno_stack" = x && { as_lineno=; unset as_lineno;} + eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno } # ac_fn_c_check_type @@ -2392,10 +2327,10 @@ $as_echo "$ac_res" >&6; } ac_fn_c_check_header_mongrel () { as_lineno=${as_lineno-"$1"} as_lineno_stack=as_lineno_stack=$as_lineno_stack - if eval "test \"\${$3+set}\"" = set; then : + if eval \${$3+:} false; then : { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $2" >&5 $as_echo_n "checking for $2... " >&6; } -if eval "test \"\${$3+set}\"" = set; then : +if eval \${$3+:} false; then : $as_echo_n "(cached) " >&6 fi eval ac_res=\$$3 @@ -2462,7 +2397,7 @@ $as_echo "$as_me: WARNING: $2: proceeding with the compiler's result" >&2;} esac { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $2" >&5 $as_echo_n "checking for $2... " >&6; } -if eval "test \"\${$3+set}\"" = set; then : +if eval \${$3+:} false; then : $as_echo_n "(cached) " >&6 else eval "$3=\$ac_header_compiler" @@ -2471,7 +2406,7 @@ eval ac_res=\$$3 { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_res" >&5 $as_echo "$ac_res" >&6; } fi - eval $as_lineno_stack; test "x$as_lineno_stack" = x && { as_lineno=; unset as_lineno;} + eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno } # ac_fn_c_check_header_mongrel @@ -2484,7 +2419,7 @@ ac_fn_c_check_member () as_lineno=${as_lineno-"$1"} as_lineno_stack=as_lineno_stack=$as_lineno_stack { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $2.$3" >&5 $as_echo_n "checking for $2.$3... " >&6; } -if eval "test \"\${$4+set}\"" = set; then : +if eval \${$4+:} false; then : $as_echo_n "(cached) " >&6 else cat confdefs.h - <<_ACEOF >conftest.$ac_ext @@ -2528,7 +2463,7 @@ fi eval ac_res=\$$4 { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_res" >&5 $as_echo "$ac_res" >&6; } - eval $as_lineno_stack; test "x$as_lineno_stack" = x && { as_lineno=; unset as_lineno;} + eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno } # ac_fn_c_check_member @@ -2549,7 +2484,8 @@ int main () { static int test_array [1 - 2 * !(($2) >= 0)]; -test_array [0] = 0 +test_array [0] = 0; +return test_array [0]; ; return 0; @@ -2565,7 +2501,8 @@ int main () { static int test_array [1 - 2 * !(($2) <= $ac_mid)]; -test_array [0] = 0 +test_array [0] = 0; +return test_array [0]; ; return 0; @@ -2591,7 +2528,8 @@ int main () { static int test_array [1 - 2 * !(($2) < 0)]; -test_array [0] = 0 +test_array [0] = 0; +return test_array [0]; ; return 0; @@ -2607,7 +2545,8 @@ int main () { static int test_array [1 - 2 * !(($2) >= $ac_mid)]; -test_array [0] = 0 +test_array [0] = 0; +return test_array [0]; ; return 0; @@ -2641,7 +2580,8 @@ int main () { static int test_array [1 - 2 * !(($2) <= $ac_mid)]; -test_array [0] = 0 +test_array [0] = 0; +return test_array [0]; ; return 0; @@ -2705,7 +2645,7 @@ rm -f core *.core core.conftest.* gmon.out bb.out conftest$ac_exeext \ rm -f conftest.val fi - eval $as_lineno_stack; test "x$as_lineno_stack" = x && { as_lineno=; unset as_lineno;} + eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno as_fn_set_status $ac_retval } # ac_fn_c_compute_int @@ -2713,8 +2653,8 @@ cat >config.log <<_ACEOF This file contains any messages produced by compilers while running configure, to aid debugging if configure makes a mistake. -It was created by gnunet $as_me 0.9.3, which was -generated by GNU Autoconf 2.67. Invocation command line was +It was created by gnunet $as_me 0.9.5a, which was +generated by GNU Autoconf 2.69. Invocation command line was $ $0 $@ @@ -2972,7 +2912,7 @@ $as_echo "$as_me: loading site script $ac_site_file" >&6;} || { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 $as_echo "$as_me: error: in \`$ac_pwd':" >&2;} as_fn_error $? "failed to load site script $ac_site_file -See \`config.log' for more details" "$LINENO" 5 ; } +See \`config.log' for more details" "$LINENO" 5; } fi done @@ -3098,7 +3038,7 @@ $SHELL "$ac_aux_dir/config.sub" sun4 >/dev/null 2>&1 || { $as_echo "$as_me:${as_lineno-$LINENO}: checking build system type" >&5 $as_echo_n "checking build system type... " >&6; } -if test "${ac_cv_build+set}" = set; then : +if ${ac_cv_build+:} false; then : $as_echo_n "(cached) " >&6 else ac_build_alias=$build_alias @@ -3114,7 +3054,7 @@ fi $as_echo "$ac_cv_build" >&6; } case $ac_cv_build in *-*-*) ;; -*) as_fn_error $? "invalid value of canonical build" "$LINENO" 5 ;; +*) as_fn_error $? "invalid value of canonical build" "$LINENO" 5;; esac build=$ac_cv_build ac_save_IFS=$IFS; IFS='-' @@ -3132,7 +3072,7 @@ case $build_os in *\ *) build_os=`echo "$build_os" | sed 's/ /-/g'`;; esac { $as_echo "$as_me:${as_lineno-$LINENO}: checking host system type" >&5 $as_echo_n "checking host system type... " >&6; } -if test "${ac_cv_host+set}" = set; then : +if ${ac_cv_host+:} false; then : $as_echo_n "(cached) " >&6 else if test "x$host_alias" = x; then @@ -3147,7 +3087,7 @@ fi $as_echo "$ac_cv_host" >&6; } case $ac_cv_host in *-*-*) ;; -*) as_fn_error $? "invalid value of canonical host" "$LINENO" 5 ;; +*) as_fn_error $? "invalid value of canonical host" "$LINENO" 5;; esac host=$ac_cv_host ac_save_IFS=$IFS; IFS='-' @@ -3165,7 +3105,7 @@ case $host_os in *\ *) host_os=`echo "$host_os" | sed 's/ /-/g'`;; esac { $as_echo "$as_me:${as_lineno-$LINENO}: checking target system type" >&5 $as_echo_n "checking target system type... " >&6; } -if test "${ac_cv_target+set}" = set; then : +if ${ac_cv_target+:} false; then : $as_echo_n "(cached) " >&6 else if test "x$target_alias" = x; then @@ -3180,7 +3120,7 @@ fi $as_echo "$ac_cv_target" >&6; } case $ac_cv_target in *-*-*) ;; -*) as_fn_error $? "invalid value of canonical target" "$LINENO" 5 ;; +*) as_fn_error $? "invalid value of canonical target" "$LINENO" 5;; esac target=$ac_cv_target ac_save_IFS=$IFS; IFS='-' @@ -3224,7 +3164,7 @@ am__api_version='1.11' { $as_echo "$as_me:${as_lineno-$LINENO}: checking for a BSD-compatible install" >&5 $as_echo_n "checking for a BSD-compatible install... " >&6; } if test -z "$INSTALL"; then -if test "${ac_cv_path_install+set}" = set; then : +if ${ac_cv_path_install+:} false; then : $as_echo_n "(cached) " >&6 else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR @@ -3244,7 +3184,7 @@ case $as_dir/ in #(( # by default. for ac_prog in ginstall scoinst install; do for ac_exec_ext in '' $ac_executable_extensions; do - if { test -f "$as_dir/$ac_prog$ac_exec_ext" && $as_test_x "$as_dir/$ac_prog$ac_exec_ext"; }; then + if as_fn_executable_p "$as_dir/$ac_prog$ac_exec_ext"; then if test $ac_prog = install && grep dspmsg "$as_dir/$ac_prog$ac_exec_ext" >/dev/null 2>&1; then # AIX install. It has an incompatible calling convention. @@ -3311,11 +3251,11 @@ am_lf=' ' case `pwd` in *[\\\"\#\$\&\'\`$am_lf]*) - as_fn_error $? "unsafe absolute working directory name" "$LINENO" 5 ;; + as_fn_error $? "unsafe absolute working directory name" "$LINENO" 5;; esac case $srcdir in *[\\\"\#\$\&\'\`$am_lf\ \ ]*) - as_fn_error $? "unsafe srcdir value: \`$srcdir'" "$LINENO" 5 ;; + as_fn_error $? "unsafe srcdir value: \`$srcdir'" "$LINENO" 5;; esac # Do `set' in a subshell so we don't clobber the current shell's @@ -3401,7 +3341,7 @@ if test "$cross_compiling" != no; then set dummy ${ac_tool_prefix}strip; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } -if test "${ac_cv_prog_STRIP+set}" = set; then : +if ${ac_cv_prog_STRIP+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$STRIP"; then @@ -3413,7 +3353,7 @@ do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do - if { test -f "$as_dir/$ac_word$ac_exec_ext" && $as_test_x "$as_dir/$ac_word$ac_exec_ext"; }; then + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_STRIP="${ac_tool_prefix}strip" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 @@ -3441,7 +3381,7 @@ if test -z "$ac_cv_prog_STRIP"; then set dummy strip; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } -if test "${ac_cv_prog_ac_ct_STRIP+set}" = set; then : +if ${ac_cv_prog_ac_ct_STRIP+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$ac_ct_STRIP"; then @@ -3453,7 +3393,7 @@ do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do - if { test -f "$as_dir/$ac_word$ac_exec_ext" && $as_test_x "$as_dir/$ac_word$ac_exec_ext"; }; then + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_ac_ct_STRIP="strip" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 @@ -3494,7 +3434,7 @@ INSTALL_STRIP_PROGRAM="\$(install_sh) -c -s" { $as_echo "$as_me:${as_lineno-$LINENO}: checking for a thread-safe mkdir -p" >&5 $as_echo_n "checking for a thread-safe mkdir -p... " >&6; } if test -z "$MKDIR_P"; then - if test "${ac_cv_path_mkdir+set}" = set; then : + if ${ac_cv_path_mkdir+:} false; then : $as_echo_n "(cached) " >&6 else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR @@ -3504,7 +3444,7 @@ do test -z "$as_dir" && as_dir=. for ac_prog in mkdir gmkdir; do for ac_exec_ext in '' $ac_executable_extensions; do - { test -f "$as_dir/$ac_prog$ac_exec_ext" && $as_test_x "$as_dir/$ac_prog$ac_exec_ext"; } || continue + as_fn_executable_p "$as_dir/$ac_prog$ac_exec_ext" || continue case `"$as_dir/$ac_prog$ac_exec_ext" --version 2>&1` in #( 'mkdir (GNU coreutils) '* | \ 'mkdir (coreutils) '* | \ @@ -3545,7 +3485,7 @@ do set dummy $ac_prog; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } -if test "${ac_cv_prog_AWK+set}" = set; then : +if ${ac_cv_prog_AWK+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$AWK"; then @@ -3557,7 +3497,7 @@ do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do - if { test -f "$as_dir/$ac_word$ac_exec_ext" && $as_test_x "$as_dir/$ac_word$ac_exec_ext"; }; then + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_AWK="$ac_prog" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 @@ -3585,7 +3525,7 @@ done $as_echo_n "checking whether ${MAKE-make} sets \$(MAKE)... " >&6; } set x ${MAKE-make} ac_make=`$as_echo "$2" | sed 's/+/p/g; s/[^a-zA-Z0-9_]/_/g'` -if eval "test \"\${ac_cv_prog_make_${ac_make}_set+set}\"" = set; then : +if eval \${ac_cv_prog_make_${ac_make}_set+:} false; then : $as_echo_n "(cached) " >&6 else cat >conftest.make <<\_ACEOF @@ -3643,7 +3583,7 @@ fi # Define the identity of the package. PACKAGE=gnunet - VERSION=0.9.3 + VERSION=0.9.5a cat >>confdefs.h <<_ACEOF @@ -3673,11 +3613,11 @@ MAKEINFO=${MAKEINFO-"${am_missing_run}makeinfo"} # We need awk for the "check" target. The system "awk" is bad on # some platforms. -# Always define AMTAR for backward compatibility. - -AMTAR=${AMTAR-"${am_missing_run}tar"} +# Always define AMTAR for backward compatibility. Yes, it's still used +# in the wild :-( We should find a proper way to deprecate it ... +AMTAR='$${TAR-tar}' -am__tar='${AMTAR} chof - "$$tardir"'; am__untar='${AMTAR} xf -' +am__tar='$${TAR-tar} chof - "$$tardir"' am__untar='$${TAR-tar} xf -' @@ -3693,6 +3633,33 @@ yes) AM_DEFAULT_VERBOSITY=0;; no) AM_DEFAULT_VERBOSITY=1;; *) AM_DEFAULT_VERBOSITY=0;; esac +am_make=${MAKE-make} +{ $as_echo "$as_me:${as_lineno-$LINENO}: checking whether $am_make supports nested variables" >&5 +$as_echo_n "checking whether $am_make supports nested variables... " >&6; } +if ${am_cv_make_support_nested_variables+:} false; then : + $as_echo_n "(cached) " >&6 +else + if $as_echo 'TRUE=$(BAR$(V)) +BAR0=false +BAR1=true +V=1 +am__doit: + @$(TRUE) +.PHONY: am__doit' | $am_make -f - >/dev/null 2>&1; then + am_cv_make_support_nested_variables=yes +else + am_cv_make_support_nested_variables=no +fi +fi +{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $am_cv_make_support_nested_variables" >&5 +$as_echo "$am_cv_make_support_nested_variables" >&6; } +if test $am_cv_make_support_nested_variables = yes; then + AM_V='$(V)' + AM_DEFAULT_V='$(AM_DEFAULT_VERBOSITY)' +else + AM_V=$AM_DEFAULT_VERBOSITY + AM_DEFAULT_V=$AM_DEFAULT_VERBOSITY +fi AM_BACKSLASH='\' ac_config_headers="$ac_config_headers gnunet_config.h" @@ -3705,7 +3672,7 @@ do set dummy $ac_prog; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } -if test "${ac_cv_prog_AWK+set}" = set; then : +if ${ac_cv_prog_AWK+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$AWK"; then @@ -3717,7 +3684,7 @@ do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do - if { test -f "$as_dir/$ac_word$ac_exec_ext" && $as_test_x "$as_dir/$ac_word$ac_exec_ext"; }; then + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_AWK="$ac_prog" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 @@ -3751,7 +3718,7 @@ if test -n "$ac_tool_prefix"; then set dummy ${ac_tool_prefix}gcc; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } -if test "${ac_cv_prog_CC+set}" = set; then : +if ${ac_cv_prog_CC+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$CC"; then @@ -3763,7 +3730,7 @@ do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do - if { test -f "$as_dir/$ac_word$ac_exec_ext" && $as_test_x "$as_dir/$ac_word$ac_exec_ext"; }; then + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_CC="${ac_tool_prefix}gcc" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 @@ -3791,7 +3758,7 @@ if test -z "$ac_cv_prog_CC"; then set dummy gcc; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } -if test "${ac_cv_prog_ac_ct_CC+set}" = set; then : +if ${ac_cv_prog_ac_ct_CC+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$ac_ct_CC"; then @@ -3803,7 +3770,7 @@ do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do - if { test -f "$as_dir/$ac_word$ac_exec_ext" && $as_test_x "$as_dir/$ac_word$ac_exec_ext"; }; then + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_ac_ct_CC="gcc" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 @@ -3844,7 +3811,7 @@ if test -z "$CC"; then set dummy ${ac_tool_prefix}cc; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } -if test "${ac_cv_prog_CC+set}" = set; then : +if ${ac_cv_prog_CC+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$CC"; then @@ -3856,7 +3823,7 @@ do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do - if { test -f "$as_dir/$ac_word$ac_exec_ext" && $as_test_x "$as_dir/$ac_word$ac_exec_ext"; }; then + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_CC="${ac_tool_prefix}cc" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 @@ -3884,7 +3851,7 @@ if test -z "$CC"; then set dummy cc; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } -if test "${ac_cv_prog_CC+set}" = set; then : +if ${ac_cv_prog_CC+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$CC"; then @@ -3897,7 +3864,7 @@ do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do - if { test -f "$as_dir/$ac_word$ac_exec_ext" && $as_test_x "$as_dir/$ac_word$ac_exec_ext"; }; then + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then if test "$as_dir/$ac_word$ac_exec_ext" = "/usr/ucb/cc"; then ac_prog_rejected=yes continue @@ -3943,7 +3910,7 @@ if test -z "$CC"; then set dummy $ac_tool_prefix$ac_prog; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } -if test "${ac_cv_prog_CC+set}" = set; then : +if ${ac_cv_prog_CC+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$CC"; then @@ -3955,7 +3922,7 @@ do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do - if { test -f "$as_dir/$ac_word$ac_exec_ext" && $as_test_x "$as_dir/$ac_word$ac_exec_ext"; }; then + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_CC="$ac_tool_prefix$ac_prog" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 @@ -3987,7 +3954,7 @@ do set dummy $ac_prog; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } -if test "${ac_cv_prog_ac_ct_CC+set}" = set; then : +if ${ac_cv_prog_ac_ct_CC+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$ac_ct_CC"; then @@ -3999,7 +3966,7 @@ do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do - if { test -f "$as_dir/$ac_word$ac_exec_ext" && $as_test_x "$as_dir/$ac_word$ac_exec_ext"; }; then + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_ac_ct_CC="$ac_prog" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 @@ -4042,7 +4009,7 @@ fi test -z "$CC" && { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 $as_echo "$as_me: error: in \`$ac_pwd':" >&2;} as_fn_error $? "no acceptable C compiler found in \$PATH -See \`config.log' for more details" "$LINENO" 5 ; } +See \`config.log' for more details" "$LINENO" 5; } # Provide some information about the compiler. $as_echo "$as_me:${as_lineno-$LINENO}: checking for C compiler version" >&5 @@ -4157,7 +4124,7 @@ sed 's/^/| /' conftest.$ac_ext >&5 { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 $as_echo "$as_me: error: in \`$ac_pwd':" >&2;} as_fn_error 77 "C compiler cannot create executables -See \`config.log' for more details" "$LINENO" 5 ; } +See \`config.log' for more details" "$LINENO" 5; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: yes" >&5 $as_echo "yes" >&6; } @@ -4200,7 +4167,7 @@ else { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 $as_echo "$as_me: error: in \`$ac_pwd':" >&2;} as_fn_error $? "cannot compute suffix of executables: cannot compile and link -See \`config.log' for more details" "$LINENO" 5 ; } +See \`config.log' for more details" "$LINENO" 5; } fi rm -f conftest conftest$ac_cv_exeext { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_exeext" >&5 @@ -4259,7 +4226,7 @@ $as_echo "$ac_try_echo"; } >&5 $as_echo "$as_me: error: in \`$ac_pwd':" >&2;} as_fn_error $? "cannot run C compiled programs. If you meant to cross compile, use \`--host'. -See \`config.log' for more details" "$LINENO" 5 ; } +See \`config.log' for more details" "$LINENO" 5; } fi fi fi @@ -4270,7 +4237,7 @@ rm -f conftest.$ac_ext conftest$ac_cv_exeext conftest.out ac_clean_files=$ac_clean_files_save { $as_echo "$as_me:${as_lineno-$LINENO}: checking for suffix of object files" >&5 $as_echo_n "checking for suffix of object files... " >&6; } -if test "${ac_cv_objext+set}" = set; then : +if ${ac_cv_objext+:} false; then : $as_echo_n "(cached) " >&6 else cat confdefs.h - <<_ACEOF >conftest.$ac_ext @@ -4311,7 +4278,7 @@ sed 's/^/| /' conftest.$ac_ext >&5 { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 $as_echo "$as_me: error: in \`$ac_pwd':" >&2;} as_fn_error $? "cannot compute suffix of object files: cannot compile -See \`config.log' for more details" "$LINENO" 5 ; } +See \`config.log' for more details" "$LINENO" 5; } fi rm -f conftest.$ac_cv_objext conftest.$ac_ext fi @@ -4321,7 +4288,7 @@ OBJEXT=$ac_cv_objext ac_objext=$OBJEXT { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether we are using the GNU C compiler" >&5 $as_echo_n "checking whether we are using the GNU C compiler... " >&6; } -if test "${ac_cv_c_compiler_gnu+set}" = set; then : +if ${ac_cv_c_compiler_gnu+:} false; then : $as_echo_n "(cached) " >&6 else cat confdefs.h - <<_ACEOF >conftest.$ac_ext @@ -4358,7 +4325,7 @@ ac_test_CFLAGS=${CFLAGS+set} ac_save_CFLAGS=$CFLAGS { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether $CC accepts -g" >&5 $as_echo_n "checking whether $CC accepts -g... " >&6; } -if test "${ac_cv_prog_cc_g+set}" = set; then : +if ${ac_cv_prog_cc_g+:} false; then : $as_echo_n "(cached) " >&6 else ac_save_c_werror_flag=$ac_c_werror_flag @@ -4436,7 +4403,7 @@ else fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $CC option to accept ISO C89" >&5 $as_echo_n "checking for $CC option to accept ISO C89... " >&6; } -if test "${ac_cv_prog_cc_c89+set}" = set; then : +if ${ac_cv_prog_cc_c89+:} false; then : $as_echo_n "(cached) " >&6 else ac_cv_prog_cc_c89=no @@ -4445,8 +4412,7 @@ cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include #include -#include -#include +struct stat; /* Most of the following tests are stolen from RCS 5.7's src/conf.sh. */ struct buf { int x; }; FILE * (*rcsopen) (struct buf *, struct stat *, int); @@ -4582,6 +4548,7 @@ fi if test "x$enable_dependency_tracking" != xno; then am_depcomp="$ac_aux_dir/depcomp" AMDEPBACKSLASH='\' + am__nodep='_no' fi if test "x$enable_dependency_tracking" != xno; then AMDEP_TRUE= @@ -4597,7 +4564,7 @@ depcc="$CC" am_compiler_list= { $as_echo "$as_me:${as_lineno-$LINENO}: checking dependency style of $depcc" >&5 $as_echo_n "checking dependency style of $depcc... " >&6; } -if test "${am_cv_CC_dependencies_compiler_type+set}" = set; then : +if ${am_cv_CC_dependencies_compiler_type+:} false; then : $as_echo_n "(cached) " >&6 else if test -z "$AMDEP_TRUE" && test -f "$am_depcomp"; then @@ -4606,6 +4573,7 @@ else # instance it was reported that on HP-UX the gcc test will end up # making a dummy file named `D' -- because `-MD' means `put the output # in D'. + rm -rf conftest.dir mkdir conftest.dir # Copy depcomp to subdir because otherwise we won't find it if we're # using a relative directory. @@ -4665,7 +4633,7 @@ else break fi ;; - msvisualcpp | msvcmsys) + msvc7 | msvc7msys | msvisualcpp | msvcmsys) # This compiler won't grok `-c -o', but also, the minuso test has # not run yet. These depmodes are late enough in the game, and # so weak that their functioning should not be impacted. @@ -4732,7 +4700,7 @@ if test -n "$CPP" && test -d "$CPP"; then CPP= fi if test -z "$CPP"; then - if test "${ac_cv_prog_CPP+set}" = set; then : + if ${ac_cv_prog_CPP+:} false; then : $as_echo_n "(cached) " >&6 else # Double quotes because CPP needs to be expanded @@ -4848,7 +4816,7 @@ else { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 $as_echo "$as_me: error: in \`$ac_pwd':" >&2;} as_fn_error $? "C preprocessor \"$CPP\" fails sanity check -See \`config.log' for more details" "$LINENO" 5 ; } +See \`config.log' for more details" "$LINENO" 5; } fi ac_ext=c @@ -4873,7 +4841,7 @@ if test -z "$CXX"; then set dummy $ac_tool_prefix$ac_prog; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } -if test "${ac_cv_prog_CXX+set}" = set; then : +if ${ac_cv_prog_CXX+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$CXX"; then @@ -4885,7 +4853,7 @@ do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do - if { test -f "$as_dir/$ac_word$ac_exec_ext" && $as_test_x "$as_dir/$ac_word$ac_exec_ext"; }; then + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_CXX="$ac_tool_prefix$ac_prog" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 @@ -4917,7 +4885,7 @@ do set dummy $ac_prog; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } -if test "${ac_cv_prog_ac_ct_CXX+set}" = set; then : +if ${ac_cv_prog_ac_ct_CXX+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$ac_ct_CXX"; then @@ -4929,7 +4897,7 @@ do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do - if { test -f "$as_dir/$ac_word$ac_exec_ext" && $as_test_x "$as_dir/$ac_word$ac_exec_ext"; }; then + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_ac_ct_CXX="$ac_prog" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 @@ -4995,7 +4963,7 @@ done { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether we are using the GNU C++ compiler" >&5 $as_echo_n "checking whether we are using the GNU C++ compiler... " >&6; } -if test "${ac_cv_cxx_compiler_gnu+set}" = set; then : +if ${ac_cv_cxx_compiler_gnu+:} false; then : $as_echo_n "(cached) " >&6 else cat confdefs.h - <<_ACEOF >conftest.$ac_ext @@ -5032,7 +5000,7 @@ ac_test_CXXFLAGS=${CXXFLAGS+set} ac_save_CXXFLAGS=$CXXFLAGS { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether $CXX accepts -g" >&5 $as_echo_n "checking whether $CXX accepts -g... " >&6; } -if test "${ac_cv_prog_cxx_g+set}" = set; then : +if ${ac_cv_prog_cxx_g+:} false; then : $as_echo_n "(cached) " >&6 else ac_save_cxx_werror_flag=$ac_cxx_werror_flag @@ -5118,7 +5086,7 @@ depcc="$CXX" am_compiler_list= { $as_echo "$as_me:${as_lineno-$LINENO}: checking dependency style of $depcc" >&5 $as_echo_n "checking dependency style of $depcc... " >&6; } -if test "${am_cv_CXX_dependencies_compiler_type+set}" = set; then : +if ${am_cv_CXX_dependencies_compiler_type+:} false; then : $as_echo_n "(cached) " >&6 else if test -z "$AMDEP_TRUE" && test -f "$am_depcomp"; then @@ -5127,6 +5095,7 @@ else # instance it was reported that on HP-UX the gcc test will end up # making a dummy file named `D' -- because `-MD' means `put the output # in D'. + rm -rf conftest.dir mkdir conftest.dir # Copy depcomp to subdir because otherwise we won't find it if we're # using a relative directory. @@ -5186,7 +5155,7 @@ else break fi ;; - msvisualcpp | msvcmsys) + msvc7 | msvc7msys | msvisualcpp | msvcmsys) # This compiler won't grok `-c -o', but also, the minuso test has # not run yet. These depmodes are late enough in the game, and # so weak that their functioning should not be impacted. @@ -5253,7 +5222,7 @@ if test -n "$ac_tool_prefix"; then set dummy $ac_tool_prefix$ac_prog; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } -if test "${ac_cv_prog_OBJC+set}" = set; then : +if ${ac_cv_prog_OBJC+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$OBJC"; then @@ -5265,7 +5234,7 @@ do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do - if { test -f "$as_dir/$ac_word$ac_exec_ext" && $as_test_x "$as_dir/$ac_word$ac_exec_ext"; }; then + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_OBJC="$ac_tool_prefix$ac_prog" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 @@ -5297,7 +5266,7 @@ do set dummy $ac_prog; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } -if test "${ac_cv_prog_ac_ct_OBJC+set}" = set; then : +if ${ac_cv_prog_ac_ct_OBJC+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$ac_ct_OBJC"; then @@ -5309,7 +5278,7 @@ do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do - if { test -f "$as_dir/$ac_word$ac_exec_ext" && $as_test_x "$as_dir/$ac_word$ac_exec_ext"; }; then + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_ac_ct_OBJC="$ac_prog" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 @@ -5373,7 +5342,7 @@ done { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether we are using the GNU Objective C compiler" >&5 $as_echo_n "checking whether we are using the GNU Objective C compiler... " >&6; } -if test "${ac_cv_objc_compiler_gnu+set}" = set; then : +if ${ac_cv_objc_compiler_gnu+:} false; then : $as_echo_n "(cached) " >&6 else cat confdefs.h - <<_ACEOF >conftest.$ac_ext @@ -5410,7 +5379,7 @@ ac_test_OBJCFLAGS=${OBJCFLAGS+set} ac_save_OBJCFLAGS=$OBJCFLAGS { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether $OBJC accepts -g" >&5 $as_echo_n "checking whether $OBJC accepts -g... " >&6; } -if test "${ac_cv_prog_objc_g+set}" = set; then : +if ${ac_cv_prog_objc_g+:} false; then : $as_echo_n "(cached) " >&6 else ac_save_objc_werror_flag=$ac_objc_werror_flag @@ -5496,7 +5465,7 @@ depcc="$OBJC" am_compiler_list='gcc3 gcc' { $as_echo "$as_me:${as_lineno-$LINENO}: checking dependency style of $depcc" >&5 $as_echo_n "checking dependency style of $depcc... " >&6; } -if test "${am_cv_OBJC_dependencies_compiler_type+set}" = set; then : +if ${am_cv_OBJC_dependencies_compiler_type+:} false; then : $as_echo_n "(cached) " >&6 else if test -z "$AMDEP_TRUE" && test -f "$am_depcomp"; then @@ -5505,6 +5474,7 @@ else # instance it was reported that on HP-UX the gcc test will end up # making a dummy file named `D' -- because `-MD' means `put the output # in D'. + rm -rf conftest.dir mkdir conftest.dir # Copy depcomp to subdir because otherwise we won't find it if we're # using a relative directory. @@ -5562,7 +5532,7 @@ else break fi ;; - msvisualcpp | msvcmsys) + msvc7 | msvc7msys | msvisualcpp | msvcmsys) # This compiler won't grok `-c -o', but also, the minuso test has # not run yet. These depmodes are late enough in the game, and # so weak that their functioning should not be impacted. @@ -5633,7 +5603,7 @@ fi $as_echo_n "checking whether ${MAKE-make} sets \$(MAKE)... " >&6; } set x ${MAKE-make} ac_make=`$as_echo "$2" | sed 's/+/p/g; s/[^a-zA-Z0-9_]/_/g'` -if eval "test \"\${ac_cv_prog_make_${ac_make}_set+set}\"" = set; then : +if eval \${ac_cv_prog_make_${ac_make}_set+:} false; then : $as_echo_n "(cached) " >&6 else cat >conftest.make <<\_ACEOF @@ -5669,7 +5639,7 @@ $as_echo_n "checking whether cc understands -c and -o together... " >&6; } fi set dummy $CC; ac_cc=`$as_echo "$2" | sed 's/[^a-zA-Z0-9_]/_/g;s/^[0-9]/_/'` -if eval "test \"\${ac_cv_prog_cc_${ac_cc}_c_o+set}\"" = set; then : +if eval \${ac_cv_prog_cc_${ac_cc}_c_o+:} false; then : $as_echo_n "(cached) " >&6 else cat confdefs.h - <<_ACEOF >conftest.$ac_ext @@ -5794,8 +5764,8 @@ esac -macro_version='2.2.6b' -macro_revision='1.3017' +macro_version='2.4.2' +macro_revision='1.3337' @@ -5811,9 +5781,78 @@ macro_revision='1.3017' ltmain="$ac_aux_dir/ltmain.sh" +# Backslashify metacharacters that are still active within +# double-quoted strings. +sed_quote_subst='s/\(["`$\\]\)/\\\1/g' + +# Same as above, but do not quote variable references. +double_quote_subst='s/\(["`\\]\)/\\\1/g' + +# Sed substitution to delay expansion of an escaped shell variable in a +# double_quote_subst'ed string. +delay_variable_subst='s/\\\\\\\\\\\$/\\\\\\$/g' + +# Sed substitution to delay expansion of an escaped single quote. +delay_single_quote_subst='s/'\''/'\'\\\\\\\'\''/g' + +# Sed substitution to avoid accidental globbing in evaled expressions +no_glob_subst='s/\*/\\\*/g' + +ECHO='\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\' +ECHO=$ECHO$ECHO$ECHO$ECHO$ECHO +ECHO=$ECHO$ECHO$ECHO$ECHO$ECHO$ECHO + +{ $as_echo "$as_me:${as_lineno-$LINENO}: checking how to print strings" >&5 +$as_echo_n "checking how to print strings... " >&6; } +# Test print first, because it will be a builtin if present. +if test "X`( print -r -- -n ) 2>/dev/null`" = X-n && \ + test "X`print -r -- $ECHO 2>/dev/null`" = "X$ECHO"; then + ECHO='print -r --' +elif test "X`printf %s $ECHO 2>/dev/null`" = "X$ECHO"; then + ECHO='printf %s\n' +else + # Use this function as a fallback that always works. + func_fallback_echo () + { + eval 'cat <<_LTECHO_EOF +$1 +_LTECHO_EOF' + } + ECHO='func_fallback_echo' +fi + +# func_echo_all arg... +# Invoke $ECHO with all args, space-separated. +func_echo_all () +{ + $ECHO "" +} + +case "$ECHO" in + printf*) { $as_echo "$as_me:${as_lineno-$LINENO}: result: printf" >&5 +$as_echo "printf" >&6; } ;; + print*) { $as_echo "$as_me:${as_lineno-$LINENO}: result: print -r" >&5 +$as_echo "print -r" >&6; } ;; + *) { $as_echo "$as_me:${as_lineno-$LINENO}: result: cat" >&5 +$as_echo "cat" >&6; } ;; +esac + + + + + + + + + + + + + + { $as_echo "$as_me:${as_lineno-$LINENO}: checking for a sed that does not truncate output" >&5 $as_echo_n "checking for a sed that does not truncate output... " >&6; } -if test "${ac_cv_path_SED+set}" = set; then : +if ${ac_cv_path_SED+:} false; then : $as_echo_n "(cached) " >&6 else ac_script=s/aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa/bbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbb/ @@ -5833,7 +5872,7 @@ do for ac_prog in sed gsed; do for ac_exec_ext in '' $ac_executable_extensions; do ac_path_SED="$as_dir/$ac_prog$ac_exec_ext" - { test -f "$ac_path_SED" && $as_test_x "$ac_path_SED"; } || continue + as_fn_executable_p "$ac_path_SED" || continue # Check for GNU ac_path_SED and select it if it is found. # Check for GNU $ac_path_SED case `"$ac_path_SED" --version 2>&1` in @@ -5895,7 +5934,7 @@ Xsed="$SED -e 1s/^X//" { $as_echo "$as_me:${as_lineno-$LINENO}: checking for grep that handles long lines and -e" >&5 $as_echo_n "checking for grep that handles long lines and -e... " >&6; } -if test "${ac_cv_path_GREP+set}" = set; then : +if ${ac_cv_path_GREP+:} false; then : $as_echo_n "(cached) " >&6 else if test -z "$GREP"; then @@ -5909,7 +5948,7 @@ do for ac_prog in grep ggrep; do for ac_exec_ext in '' $ac_executable_extensions; do ac_path_GREP="$as_dir/$ac_prog$ac_exec_ext" - { test -f "$ac_path_GREP" && $as_test_x "$ac_path_GREP"; } || continue + as_fn_executable_p "$ac_path_GREP" || continue # Check for GNU ac_path_GREP and select it if it is found. # Check for GNU $ac_path_GREP case `"$ac_path_GREP" --version 2>&1` in @@ -5958,7 +5997,7 @@ $as_echo "$ac_cv_path_GREP" >&6; } { $as_echo "$as_me:${as_lineno-$LINENO}: checking for egrep" >&5 $as_echo_n "checking for egrep... " >&6; } -if test "${ac_cv_path_EGREP+set}" = set; then : +if ${ac_cv_path_EGREP+:} false; then : $as_echo_n "(cached) " >&6 else if echo a | $GREP -E '(a|b)' >/dev/null 2>&1 @@ -5975,7 +6014,7 @@ do for ac_prog in egrep; do for ac_exec_ext in '' $ac_executable_extensions; do ac_path_EGREP="$as_dir/$ac_prog$ac_exec_ext" - { test -f "$ac_path_EGREP" && $as_test_x "$ac_path_EGREP"; } || continue + as_fn_executable_p "$ac_path_EGREP" || continue # Check for GNU ac_path_EGREP and select it if it is found. # Check for GNU $ac_path_EGREP case `"$ac_path_EGREP" --version 2>&1` in @@ -6025,7 +6064,7 @@ $as_echo "$ac_cv_path_EGREP" >&6; } { $as_echo "$as_me:${as_lineno-$LINENO}: checking for fgrep" >&5 $as_echo_n "checking for fgrep... " >&6; } -if test "${ac_cv_path_FGREP+set}" = set; then : +if ${ac_cv_path_FGREP+:} false; then : $as_echo_n "(cached) " >&6 else if echo 'ab*c' | $GREP -F 'ab*c' >/dev/null 2>&1 @@ -6042,7 +6081,7 @@ do for ac_prog in fgrep; do for ac_exec_ext in '' $ac_executable_extensions; do ac_path_FGREP="$as_dir/$ac_prog$ac_exec_ext" - { test -f "$ac_path_FGREP" && $as_test_x "$ac_path_FGREP"; } || continue + as_fn_executable_p "$ac_path_FGREP" || continue # Check for GNU ac_path_FGREP and select it if it is found. # Check for GNU $ac_path_FGREP case `"$ac_path_FGREP" --version 2>&1` in @@ -6156,7 +6195,7 @@ else { $as_echo "$as_me:${as_lineno-$LINENO}: checking for non-GNU ld" >&5 $as_echo_n "checking for non-GNU ld... " >&6; } fi -if test "${lt_cv_path_LD+set}" = set; then : +if ${lt_cv_path_LD+:} false; then : $as_echo_n "(cached) " >&6 else if test -z "$LD"; then @@ -6196,7 +6235,7 @@ fi test -z "$LD" && as_fn_error $? "no acceptable ld found in \$PATH" "$LINENO" 5 { $as_echo "$as_me:${as_lineno-$LINENO}: checking if the linker ($LD) is GNU ld" >&5 $as_echo_n "checking if the linker ($LD) is GNU ld... " >&6; } -if test "${lt_cv_prog_gnu_ld+set}" = set; then : +if ${lt_cv_prog_gnu_ld+:} false; then : $as_echo_n "(cached) " >&6 else # I'd rather use --version here, but apparently some GNU lds only accept -v. @@ -6223,7 +6262,7 @@ with_gnu_ld=$lt_cv_prog_gnu_ld { $as_echo "$as_me:${as_lineno-$LINENO}: checking for BSD- or MS-compatible name lister (nm)" >&5 $as_echo_n "checking for BSD- or MS-compatible name lister (nm)... " >&6; } -if test "${lt_cv_path_NM+set}" = set; then : +if ${lt_cv_path_NM+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$NM"; then @@ -6276,14 +6315,17 @@ if test "$lt_cv_path_NM" != "no"; then NM="$lt_cv_path_NM" else # Didn't find any BSD compatible name lister, look for dumpbin. - if test -n "$ac_tool_prefix"; then - for ac_prog in "dumpbin -symbols" "link -dump -symbols" + if test -n "$DUMPBIN"; then : + # Let the user override the test. + else + if test -n "$ac_tool_prefix"; then + for ac_prog in dumpbin "link -dump" do # Extract the first word of "$ac_tool_prefix$ac_prog", so it can be a program name with args. set dummy $ac_tool_prefix$ac_prog; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } -if test "${ac_cv_prog_DUMPBIN+set}" = set; then : +if ${ac_cv_prog_DUMPBIN+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$DUMPBIN"; then @@ -6295,7 +6337,7 @@ do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do - if { test -f "$as_dir/$ac_word$ac_exec_ext" && $as_test_x "$as_dir/$ac_word$ac_exec_ext"; }; then + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_DUMPBIN="$ac_tool_prefix$ac_prog" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 @@ -6321,13 +6363,13 @@ fi fi if test -z "$DUMPBIN"; then ac_ct_DUMPBIN=$DUMPBIN - for ac_prog in "dumpbin -symbols" "link -dump -symbols" + for ac_prog in dumpbin "link -dump" do # Extract the first word of "$ac_prog", so it can be a program name with args. set dummy $ac_prog; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } -if test "${ac_cv_prog_ac_ct_DUMPBIN+set}" = set; then : +if ${ac_cv_prog_ac_ct_DUMPBIN+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$ac_ct_DUMPBIN"; then @@ -6339,7 +6381,7 @@ do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do - if { test -f "$as_dir/$ac_word$ac_exec_ext" && $as_test_x "$as_dir/$ac_word$ac_exec_ext"; }; then + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_ac_ct_DUMPBIN="$ac_prog" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 @@ -6376,6 +6418,15 @@ esac fi fi + case `$DUMPBIN -symbols /dev/null 2>&1 | sed '1q'` in + *COFF*) + DUMPBIN="$DUMPBIN -symbols" + ;; + *) + DUMPBIN=: + ;; + esac + fi if test "$DUMPBIN" != ":"; then NM="$DUMPBIN" @@ -6390,18 +6441,18 @@ test -z "$NM" && NM=nm { $as_echo "$as_me:${as_lineno-$LINENO}: checking the name lister ($NM) interface" >&5 $as_echo_n "checking the name lister ($NM) interface... " >&6; } -if test "${lt_cv_nm_interface+set}" = set; then : +if ${lt_cv_nm_interface+:} false; then : $as_echo_n "(cached) " >&6 else lt_cv_nm_interface="BSD nm" echo "int some_variable = 0;" > conftest.$ac_ext - (eval echo "\"\$as_me:6398: $ac_compile\"" >&5) + (eval echo "\"\$as_me:$LINENO: $ac_compile\"" >&5) (eval "$ac_compile" 2>conftest.err) cat conftest.err >&5 - (eval echo "\"\$as_me:6401: $NM \\\"conftest.$ac_objext\\\"\"" >&5) + (eval echo "\"\$as_me:$LINENO: $NM \\\"conftest.$ac_objext\\\"\"" >&5) (eval "$NM \"conftest.$ac_objext\"" 2>conftest.err > conftest.out) cat conftest.err >&5 - (eval echo "\"\$as_me:6404: output\"" >&5) + (eval echo "\"\$as_me:$LINENO: output\"" >&5) cat conftest.out >&5 if $GREP 'External.*some_variable' conftest.out > /dev/null; then lt_cv_nm_interface="MS dumpbin" @@ -6414,7 +6465,7 @@ $as_echo "$lt_cv_nm_interface" >&6; } # find the maximum length of command line arguments { $as_echo "$as_me:${as_lineno-$LINENO}: checking the maximum length of command line arguments" >&5 $as_echo_n "checking the maximum length of command line arguments... " >&6; } -if test "${lt_cv_sys_max_cmd_len+set}" = set; then : +if ${lt_cv_sys_max_cmd_len+:} false; then : $as_echo_n "(cached) " >&6 else i=0 @@ -6447,6 +6498,11 @@ else lt_cv_sys_max_cmd_len=8192; ;; + mint*) + # On MiNT this can take a long time and run out of memory. + lt_cv_sys_max_cmd_len=8192; + ;; + amigaos*) # On AmigaOS with pdksh, this test takes hours, literally. # So we just punt and use a minimum line length of 8192. @@ -6472,6 +6528,11 @@ else lt_cv_sys_max_cmd_len=196608 ;; + os2*) + # The test takes a long time on OS/2. + lt_cv_sys_max_cmd_len=8192 + ;; + osf*) # Dr. Hans Ekkehard Plesser reports seeing a kernel panic running configure # due to this test when exec_disable_arg_limit is 1 on Tru64. It is not @@ -6511,8 +6572,8 @@ else # If test is not a shell built-in, we'll probably end up computing a # maximum length that is only half of the actual maximum length, but # we can't tell. - while { test "X"`$SHELL $0 --fallback-echo "X$teststring$teststring" 2>/dev/null` \ - = "XX$teststring$teststring"; } >/dev/null 2>&1 && + while { test "X"`env echo "$teststring$teststring" 2>/dev/null` \ + = "X$teststring$teststring"; } >/dev/null 2>&1 && test $i != 17 # 1/2 MB should be enough do i=`expr $i + 1` @@ -6554,8 +6615,8 @@ $as_echo_n "checking whether the shell understands some XSI constructs... " >&6; # Try some XSI features xsi_shell=no ( _lt_dummy="a/b/c" - test "${_lt_dummy##*/},${_lt_dummy%/*},"${_lt_dummy%"$_lt_dummy"}, \ - = c,a/b,, \ + test "${_lt_dummy##*/},${_lt_dummy%/*},${_lt_dummy#??}"${_lt_dummy%"$_lt_dummy"}, \ + = c,a/b,b/c, \ && eval 'test $(( 1 + 1 )) -eq 2 \ && test "${#_lt_dummy}" -eq 5' ) >/dev/null 2>&1 \ && xsi_shell=yes @@ -6604,9 +6665,83 @@ esac +{ $as_echo "$as_me:${as_lineno-$LINENO}: checking how to convert $build file names to $host format" >&5 +$as_echo_n "checking how to convert $build file names to $host format... " >&6; } +if ${lt_cv_to_host_file_cmd+:} false; then : + $as_echo_n "(cached) " >&6 +else + case $host in + *-*-mingw* ) + case $build in + *-*-mingw* ) # actually msys + lt_cv_to_host_file_cmd=func_convert_file_msys_to_w32 + ;; + *-*-cygwin* ) + lt_cv_to_host_file_cmd=func_convert_file_cygwin_to_w32 + ;; + * ) # otherwise, assume *nix + lt_cv_to_host_file_cmd=func_convert_file_nix_to_w32 + ;; + esac + ;; + *-*-cygwin* ) + case $build in + *-*-mingw* ) # actually msys + lt_cv_to_host_file_cmd=func_convert_file_msys_to_cygwin + ;; + *-*-cygwin* ) + lt_cv_to_host_file_cmd=func_convert_file_noop + ;; + * ) # otherwise, assume *nix + lt_cv_to_host_file_cmd=func_convert_file_nix_to_cygwin + ;; + esac + ;; + * ) # unhandled hosts (and "normal" native builds) + lt_cv_to_host_file_cmd=func_convert_file_noop + ;; +esac + +fi + +to_host_file_cmd=$lt_cv_to_host_file_cmd +{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $lt_cv_to_host_file_cmd" >&5 +$as_echo "$lt_cv_to_host_file_cmd" >&6; } + + + + + +{ $as_echo "$as_me:${as_lineno-$LINENO}: checking how to convert $build file names to toolchain format" >&5 +$as_echo_n "checking how to convert $build file names to toolchain format... " >&6; } +if ${lt_cv_to_tool_file_cmd+:} false; then : + $as_echo_n "(cached) " >&6 +else + #assume ordinary cross tools, or native build. +lt_cv_to_tool_file_cmd=func_convert_file_noop +case $host in + *-*-mingw* ) + case $build in + *-*-mingw* ) # actually msys + lt_cv_to_tool_file_cmd=func_convert_file_msys_to_w32 + ;; + esac + ;; +esac + +fi + +to_tool_file_cmd=$lt_cv_to_tool_file_cmd +{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $lt_cv_to_tool_file_cmd" >&5 +$as_echo "$lt_cv_to_tool_file_cmd" >&6; } + + + + + { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $LD option to reload object files" >&5 $as_echo_n "checking for $LD option to reload object files... " >&6; } -if test "${lt_cv_ld_reload_flag+set}" = set; then : +if ${lt_cv_ld_reload_flag+:} false; then : $as_echo_n "(cached) " >&6 else lt_cv_ld_reload_flag='-r' @@ -6620,6 +6755,11 @@ case $reload_flag in esac reload_cmds='$LD$reload_flag -o $output$reload_objs' case $host_os in + cygwin* | mingw* | pw32* | cegcc*) + if test "$GCC" != yes; then + reload_cmds=false + fi + ;; darwin*) if test "$GCC" = yes; then reload_cmds='$LTCC $LTCFLAGS -nostdlib ${wl}-r -o $output$reload_objs' @@ -6642,7 +6782,7 @@ if test -n "$ac_tool_prefix"; then set dummy ${ac_tool_prefix}objdump; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } -if test "${ac_cv_prog_OBJDUMP+set}" = set; then : +if ${ac_cv_prog_OBJDUMP+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$OBJDUMP"; then @@ -6654,7 +6794,7 @@ do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do - if { test -f "$as_dir/$ac_word$ac_exec_ext" && $as_test_x "$as_dir/$ac_word$ac_exec_ext"; }; then + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_OBJDUMP="${ac_tool_prefix}objdump" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 @@ -6682,7 +6822,7 @@ if test -z "$ac_cv_prog_OBJDUMP"; then set dummy objdump; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } -if test "${ac_cv_prog_ac_ct_OBJDUMP+set}" = set; then : +if ${ac_cv_prog_ac_ct_OBJDUMP+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$ac_ct_OBJDUMP"; then @@ -6694,7 +6834,7 @@ do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do - if { test -f "$as_dir/$ac_word$ac_exec_ext" && $as_test_x "$as_dir/$ac_word$ac_exec_ext"; }; then + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_ac_ct_OBJDUMP="objdump" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 @@ -6738,7 +6878,7 @@ test -z "$OBJDUMP" && OBJDUMP=objdump { $as_echo "$as_me:${as_lineno-$LINENO}: checking how to recognize dependent libraries" >&5 $as_echo_n "checking how to recognize dependent libraries... " >&6; } -if test "${lt_cv_deplibs_check_method+set}" = set; then : +if ${lt_cv_deplibs_check_method+:} false; then : $as_echo_n "(cached) " >&6 else lt_cv_file_magic_cmd='$MAGIC_CMD' @@ -6780,16 +6920,18 @@ mingw* | pw32*) # Base MSYS/MinGW do not provide the 'file' command needed by # func_win32_libid shell function, so use a weaker test based on 'objdump', # unless we find 'file', for example because we are cross-compiling. - if ( file / ) >/dev/null 2>&1; then + # func_win32_libid assumes BSD nm, so disallow it if using MS dumpbin. + if ( test "$lt_cv_nm_interface" = "BSD nm" && file / ) >/dev/null 2>&1; then lt_cv_deplibs_check_method='file_magic ^x86 archive import|^x86 DLL' lt_cv_file_magic_cmd='func_win32_libid' else - lt_cv_deplibs_check_method='file_magic file format pei*-i386(.*architecture: i386)?' + # Keep this pattern in sync with the one in func_win32_libid. + lt_cv_deplibs_check_method='file_magic file format (pei*-i386(.*architecture: i386)?|pe-arm-wince|pe-x86-64)' lt_cv_file_magic_cmd='$OBJDUMP -f' fi ;; -cegcc) +cegcc*) # use the weaker test based on 'objdump'. See mingw*. lt_cv_deplibs_check_method='file_magic file format pe-arm-.*little(.*architecture: arm)?' lt_cv_file_magic_cmd='$OBJDUMP -f' @@ -6815,7 +6957,7 @@ freebsd* | dragonfly*) fi ;; -gnu*) +haiku*) lt_cv_deplibs_check_method=pass_all ;; @@ -6827,11 +6969,11 @@ hpux10.20* | hpux11*) lt_cv_file_magic_test_file=/usr/lib/hpux32/libc.so ;; hppa*64*) - lt_cv_deplibs_check_method='file_magic (s[0-9][0-9][0-9]|ELF-[0-9][0-9]) shared object file - PA-RISC [0-9].[0-9]' + lt_cv_deplibs_check_method='file_magic (s[0-9][0-9][0-9]|ELF[ -][0-9][0-9])(-bit)?( [LM]SB)? shared object( file)?[, -]* PA-RISC [0-9]\.[0-9]' lt_cv_file_magic_test_file=/usr/lib/pa20_64/libc.sl ;; *) - lt_cv_deplibs_check_method='file_magic (s[0-9][0-9][0-9]|PA-RISC[0-9].[0-9]) shared library' + lt_cv_deplibs_check_method='file_magic (s[0-9][0-9][0-9]|PA-RISC[0-9]\.[0-9]) shared library' lt_cv_file_magic_test_file=/usr/lib/libc.sl ;; esac @@ -6852,8 +6994,8 @@ irix5* | irix6* | nonstopux*) lt_cv_deplibs_check_method=pass_all ;; -# This must be Linux ELF. -linux* | k*bsd*-gnu | kopensolaris*-gnu) +# This must be glibc/ELF. +linux* | k*bsd*-gnu | kopensolaris*-gnu | gnu*) lt_cv_deplibs_check_method=pass_all ;; @@ -6934,6 +7076,21 @@ esac fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $lt_cv_deplibs_check_method" >&5 $as_echo "$lt_cv_deplibs_check_method" >&6; } + +file_magic_glob= +want_nocaseglob=no +if test "$build" = "$host"; then + case $host_os in + mingw* | pw32*) + if ( shopt | grep nocaseglob ) >/dev/null 2>&1; then + want_nocaseglob=yes + else + file_magic_glob=`echo aAbBcCdDeEfFgGhHiIjJkKlLmMnNoOpPqQrRsStTuUvVwWxXyYzZ | $SED -e "s/\(..\)/s\/[\1]\/[\1]\/g;/g"` + fi + ;; + esac +fi + file_magic_cmd=$lt_cv_file_magic_cmd deplibs_check_method=$lt_cv_deplibs_check_method test -z "$deplibs_check_method" && deplibs_check_method=unknown @@ -6947,18 +7104,28 @@ test -z "$deplibs_check_method" && deplibs_check_method=unknown + + + + + + + + + + if test -n "$ac_tool_prefix"; then - # Extract the first word of "${ac_tool_prefix}ar", so it can be a program name with args. -set dummy ${ac_tool_prefix}ar; ac_word=$2 + # Extract the first word of "${ac_tool_prefix}dlltool", so it can be a program name with args. +set dummy ${ac_tool_prefix}dlltool; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } -if test "${ac_cv_prog_AR+set}" = set; then : +if ${ac_cv_prog_DLLTOOL+:} false; then : $as_echo_n "(cached) " >&6 else - if test -n "$AR"; then - ac_cv_prog_AR="$AR" # Let the user override the test. + if test -n "$DLLTOOL"; then + ac_cv_prog_DLLTOOL="$DLLTOOL" # Let the user override the test. else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH @@ -6966,8 +7133,8 @@ do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do - if { test -f "$as_dir/$ac_word$ac_exec_ext" && $as_test_x "$as_dir/$ac_word$ac_exec_ext"; }; then - ac_cv_prog_AR="${ac_tool_prefix}ar" + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then + ac_cv_prog_DLLTOOL="${ac_tool_prefix}dlltool" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi @@ -6977,10 +7144,10 @@ IFS=$as_save_IFS fi fi -AR=$ac_cv_prog_AR -if test -n "$AR"; then - { $as_echo "$as_me:${as_lineno-$LINENO}: result: $AR" >&5 -$as_echo "$AR" >&6; } +DLLTOOL=$ac_cv_prog_DLLTOOL +if test -n "$DLLTOOL"; then + { $as_echo "$as_me:${as_lineno-$LINENO}: result: $DLLTOOL" >&5 +$as_echo "$DLLTOOL" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } @@ -6988,17 +7155,17 @@ fi fi -if test -z "$ac_cv_prog_AR"; then - ac_ct_AR=$AR - # Extract the first word of "ar", so it can be a program name with args. -set dummy ar; ac_word=$2 +if test -z "$ac_cv_prog_DLLTOOL"; then + ac_ct_DLLTOOL=$DLLTOOL + # Extract the first word of "dlltool", so it can be a program name with args. +set dummy dlltool; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } -if test "${ac_cv_prog_ac_ct_AR+set}" = set; then : +if ${ac_cv_prog_ac_ct_DLLTOOL+:} false; then : $as_echo_n "(cached) " >&6 else - if test -n "$ac_ct_AR"; then - ac_cv_prog_ac_ct_AR="$ac_ct_AR" # Let the user override the test. + if test -n "$ac_ct_DLLTOOL"; then + ac_cv_prog_ac_ct_DLLTOOL="$ac_ct_DLLTOOL" # Let the user override the test. else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH @@ -7006,8 +7173,8 @@ do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do - if { test -f "$as_dir/$ac_word$ac_exec_ext" && $as_test_x "$as_dir/$ac_word$ac_exec_ext"; }; then - ac_cv_prog_ac_ct_AR="ar" + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then + ac_cv_prog_ac_ct_DLLTOOL="dlltool" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi @@ -7017,17 +7184,17 @@ IFS=$as_save_IFS fi fi -ac_ct_AR=$ac_cv_prog_ac_ct_AR -if test -n "$ac_ct_AR"; then - { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_ct_AR" >&5 -$as_echo "$ac_ct_AR" >&6; } +ac_ct_DLLTOOL=$ac_cv_prog_ac_ct_DLLTOOL +if test -n "$ac_ct_DLLTOOL"; then + { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_ct_DLLTOOL" >&5 +$as_echo "$ac_ct_DLLTOOL" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi - if test "x$ac_ct_AR" = x; then - AR="false" + if test "x$ac_ct_DLLTOOL" = x; then + DLLTOOL="false" else case $cross_compiling:$ac_tool_warned in yes:) @@ -7035,14 +7202,13 @@ yes:) $as_echo "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;} ac_tool_warned=yes ;; esac - AR=$ac_ct_AR + DLLTOOL=$ac_ct_DLLTOOL fi else - AR="$ac_cv_prog_AR" + DLLTOOL="$ac_cv_prog_DLLTOOL" fi -test -z "$AR" && AR=ar -test -z "$AR_FLAGS" && AR_FLAGS=cru +test -z "$DLLTOOL" && DLLTOOL=dlltool @@ -7050,16 +7216,222 @@ test -z "$AR_FLAGS" && AR_FLAGS=cru +{ $as_echo "$as_me:${as_lineno-$LINENO}: checking how to associate runtime and link libraries" >&5 +$as_echo_n "checking how to associate runtime and link libraries... " >&6; } +if ${lt_cv_sharedlib_from_linklib_cmd+:} false; then : + $as_echo_n "(cached) " >&6 +else + lt_cv_sharedlib_from_linklib_cmd='unknown' +case $host_os in +cygwin* | mingw* | pw32* | cegcc*) + # two different shell functions defined in ltmain.sh + # decide which to use based on capabilities of $DLLTOOL + case `$DLLTOOL --help 2>&1` in + *--identify-strict*) + lt_cv_sharedlib_from_linklib_cmd=func_cygming_dll_for_implib + ;; + *) + lt_cv_sharedlib_from_linklib_cmd=func_cygming_dll_for_implib_fallback + ;; + esac + ;; +*) + # fallback: assume linklib IS sharedlib + lt_cv_sharedlib_from_linklib_cmd="$ECHO" + ;; +esac +fi +{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $lt_cv_sharedlib_from_linklib_cmd" >&5 +$as_echo "$lt_cv_sharedlib_from_linklib_cmd" >&6; } +sharedlib_from_linklib_cmd=$lt_cv_sharedlib_from_linklib_cmd +test -z "$sharedlib_from_linklib_cmd" && sharedlib_from_linklib_cmd=$ECHO -if test -n "$ac_tool_prefix"; then - # Extract the first word of "${ac_tool_prefix}strip", so it can be a program name with args. -set dummy ${ac_tool_prefix}strip; ac_word=$2 -{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 -$as_echo_n "checking for $ac_word... " >&6; } -if test "${ac_cv_prog_STRIP+set}" = set; then : + + + + + + +if test -n "$ac_tool_prefix"; then + for ac_prog in ar + do + # Extract the first word of "$ac_tool_prefix$ac_prog", so it can be a program name with args. +set dummy $ac_tool_prefix$ac_prog; ac_word=$2 +{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +$as_echo_n "checking for $ac_word... " >&6; } +if ${ac_cv_prog_AR+:} false; then : + $as_echo_n "(cached) " >&6 +else + if test -n "$AR"; then + ac_cv_prog_AR="$AR" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + test -z "$as_dir" && as_dir=. + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then + ac_cv_prog_AR="$ac_tool_prefix$ac_prog" + $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + +fi +fi +AR=$ac_cv_prog_AR +if test -n "$AR"; then + { $as_echo "$as_me:${as_lineno-$LINENO}: result: $AR" >&5 +$as_echo "$AR" >&6; } +else + { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 +$as_echo "no" >&6; } +fi + + + test -n "$AR" && break + done +fi +if test -z "$AR"; then + ac_ct_AR=$AR + for ac_prog in ar +do + # Extract the first word of "$ac_prog", so it can be a program name with args. +set dummy $ac_prog; ac_word=$2 +{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +$as_echo_n "checking for $ac_word... " >&6; } +if ${ac_cv_prog_ac_ct_AR+:} false; then : + $as_echo_n "(cached) " >&6 +else + if test -n "$ac_ct_AR"; then + ac_cv_prog_ac_ct_AR="$ac_ct_AR" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + test -z "$as_dir" && as_dir=. + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then + ac_cv_prog_ac_ct_AR="$ac_prog" + $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + +fi +fi +ac_ct_AR=$ac_cv_prog_ac_ct_AR +if test -n "$ac_ct_AR"; then + { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_ct_AR" >&5 +$as_echo "$ac_ct_AR" >&6; } +else + { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 +$as_echo "no" >&6; } +fi + + + test -n "$ac_ct_AR" && break +done + + if test "x$ac_ct_AR" = x; then + AR="false" + else + case $cross_compiling:$ac_tool_warned in +yes:) +{ $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet" >&5 +$as_echo "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;} +ac_tool_warned=yes ;; +esac + AR=$ac_ct_AR + fi +fi + +: ${AR=ar} +: ${AR_FLAGS=cru} + + + + + + + + + + + +{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for archiver @FILE support" >&5 +$as_echo_n "checking for archiver @FILE support... " >&6; } +if ${lt_cv_ar_at_file+:} false; then : + $as_echo_n "(cached) " >&6 +else + lt_cv_ar_at_file=no + cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ + +int +main () +{ + + ; + return 0; +} +_ACEOF +if ac_fn_c_try_compile "$LINENO"; then : + echo conftest.$ac_objext > conftest.lst + lt_ar_try='$AR $AR_FLAGS libconftest.a @conftest.lst >&5' + { { eval echo "\"\$as_me\":${as_lineno-$LINENO}: \"$lt_ar_try\""; } >&5 + (eval $lt_ar_try) 2>&5 + ac_status=$? + $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 + test $ac_status = 0; } + if test "$ac_status" -eq 0; then + # Ensure the archiver fails upon bogus file names. + rm -f conftest.$ac_objext libconftest.a + { { eval echo "\"\$as_me\":${as_lineno-$LINENO}: \"$lt_ar_try\""; } >&5 + (eval $lt_ar_try) 2>&5 + ac_status=$? + $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 + test $ac_status = 0; } + if test "$ac_status" -ne 0; then + lt_cv_ar_at_file=@ + fi + fi + rm -f conftest.* libconftest.a + +fi +rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext + +fi +{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $lt_cv_ar_at_file" >&5 +$as_echo "$lt_cv_ar_at_file" >&6; } + +if test "x$lt_cv_ar_at_file" = xno; then + archiver_list_spec= +else + archiver_list_spec=$lt_cv_ar_at_file +fi + + + + + + + +if test -n "$ac_tool_prefix"; then + # Extract the first word of "${ac_tool_prefix}strip", so it can be a program name with args. +set dummy ${ac_tool_prefix}strip; ac_word=$2 +{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +$as_echo_n "checking for $ac_word... " >&6; } +if ${ac_cv_prog_STRIP+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$STRIP"; then @@ -7071,7 +7443,7 @@ do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do - if { test -f "$as_dir/$ac_word$ac_exec_ext" && $as_test_x "$as_dir/$ac_word$ac_exec_ext"; }; then + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_STRIP="${ac_tool_prefix}strip" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 @@ -7099,7 +7471,7 @@ if test -z "$ac_cv_prog_STRIP"; then set dummy strip; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } -if test "${ac_cv_prog_ac_ct_STRIP+set}" = set; then : +if ${ac_cv_prog_ac_ct_STRIP+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$ac_ct_STRIP"; then @@ -7111,7 +7483,7 @@ do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do - if { test -f "$as_dir/$ac_word$ac_exec_ext" && $as_test_x "$as_dir/$ac_word$ac_exec_ext"; }; then + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_ac_ct_STRIP="strip" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 @@ -7158,7 +7530,7 @@ if test -n "$ac_tool_prefix"; then set dummy ${ac_tool_prefix}ranlib; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } -if test "${ac_cv_prog_RANLIB+set}" = set; then : +if ${ac_cv_prog_RANLIB+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$RANLIB"; then @@ -7170,7 +7542,7 @@ do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do - if { test -f "$as_dir/$ac_word$ac_exec_ext" && $as_test_x "$as_dir/$ac_word$ac_exec_ext"; }; then + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_RANLIB="${ac_tool_prefix}ranlib" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 @@ -7198,7 +7570,7 @@ if test -z "$ac_cv_prog_RANLIB"; then set dummy ranlib; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } -if test "${ac_cv_prog_ac_ct_RANLIB+set}" = set; then : +if ${ac_cv_prog_ac_ct_RANLIB+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$ac_ct_RANLIB"; then @@ -7210,7 +7582,7 @@ do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do - if { test -f "$as_dir/$ac_word$ac_exec_ext" && $as_test_x "$as_dir/$ac_word$ac_exec_ext"; }; then + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_ac_ct_RANLIB="ranlib" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 @@ -7260,15 +7632,27 @@ old_postuninstall_cmds= if test -n "$RANLIB"; then case $host_os in openbsd*) - old_postinstall_cmds="$old_postinstall_cmds~\$RANLIB -t \$oldlib" + old_postinstall_cmds="$old_postinstall_cmds~\$RANLIB -t \$tool_oldlib" ;; *) - old_postinstall_cmds="$old_postinstall_cmds~\$RANLIB \$oldlib" + old_postinstall_cmds="$old_postinstall_cmds~\$RANLIB \$tool_oldlib" ;; esac - old_archive_cmds="$old_archive_cmds~\$RANLIB \$oldlib" + old_archive_cmds="$old_archive_cmds~\$RANLIB \$tool_oldlib" fi +case $host_os in + darwin*) + lock_old_archive_extraction=yes ;; + *) + lock_old_archive_extraction=no ;; +esac + + + + + + @@ -7315,7 +7699,7 @@ compiler=$CC # Check for command to grab the raw symbol name followed by C symbol from nm. { $as_echo "$as_me:${as_lineno-$LINENO}: checking command to parse $NM output from $compiler object" >&5 $as_echo_n "checking command to parse $NM output from $compiler object... " >&6; } -if test "${lt_cv_sys_global_symbol_pipe+set}" = set; then : +if ${lt_cv_sys_global_symbol_pipe+:} false; then : $as_echo_n "(cached) " >&6 else @@ -7376,8 +7760,8 @@ esac lt_cv_sys_global_symbol_to_cdecl="sed -n -e 's/^T .* \(.*\)$/extern int \1();/p' -e 's/^$symcode* .* \(.*\)$/extern char \1;/p'" # Transform an extracted symbol line into symbol name and symbol address -lt_cv_sys_global_symbol_to_c_name_address="sed -n -e 's/^: \([^ ]*\) $/ {\\\"\1\\\", (void *) 0},/p' -e 's/^$symcode* \([^ ]*\) \([^ ]*\)$/ {\"\2\", (void *) \&\2},/p'" -lt_cv_sys_global_symbol_to_c_name_address_lib_prefix="sed -n -e 's/^: \([^ ]*\) $/ {\\\"\1\\\", (void *) 0},/p' -e 's/^$symcode* \([^ ]*\) \(lib[^ ]*\)$/ {\"\2\", (void *) \&\2},/p' -e 's/^$symcode* \([^ ]*\) \([^ ]*\)$/ {\"lib\2\", (void *) \&\2},/p'" +lt_cv_sys_global_symbol_to_c_name_address="sed -n -e 's/^: \([^ ]*\)[ ]*$/ {\\\"\1\\\", (void *) 0},/p' -e 's/^$symcode* \([^ ]*\) \([^ ]*\)$/ {\"\2\", (void *) \&\2},/p'" +lt_cv_sys_global_symbol_to_c_name_address_lib_prefix="sed -n -e 's/^: \([^ ]*\)[ ]*$/ {\\\"\1\\\", (void *) 0},/p' -e 's/^$symcode* \([^ ]*\) \(lib[^ ]*\)$/ {\"\2\", (void *) \&\2},/p' -e 's/^$symcode* \([^ ]*\) \([^ ]*\)$/ {\"lib\2\", (void *) \&\2},/p'" # Handle CRLF in mingw tool chain opt_cr= @@ -7401,6 +7785,7 @@ for ac_symprfx in "" "_"; do # which start with @ or ?. lt_cv_sys_global_symbol_pipe="$AWK '"\ " {last_section=section; section=\$ 3};"\ +" /^COFF SYMBOL TABLE/{for(i in hide) delete hide[i]};"\ " /Section length .*#relocs.*(pick any)/{hide[last_section]=1};"\ " \$ 0!~/External *\|/{next};"\ " / 0+ UNDEF /{next}; / UNDEF \([^|]\)*()/{next};"\ @@ -7413,6 +7798,7 @@ for ac_symprfx in "" "_"; do else lt_cv_sys_global_symbol_pipe="sed -n -e 's/^.*[ ]\($symcode$symcode*\)[ ][ ]*$ac_symprfx$sympat$opt_cr$/$symxfrm/p'" fi + lt_cv_sys_global_symbol_pipe="$lt_cv_sys_global_symbol_pipe | sed '/ __gnu_lto/d'" # Check to see that the pipe works correctly. pipe_works=no @@ -7438,8 +7824,8 @@ _LT_EOF test $ac_status = 0; }; then # Now try to grab the symbols. nlist=conftest.nm - if { { eval echo "\"\$as_me\":${as_lineno-$LINENO}: \"$NM conftest.$ac_objext \| $lt_cv_sys_global_symbol_pipe \> $nlist\""; } >&5 - (eval $NM conftest.$ac_objext \| $lt_cv_sys_global_symbol_pipe \> $nlist) 2>&5 + if { { eval echo "\"\$as_me\":${as_lineno-$LINENO}: \"$NM conftest.$ac_objext \| "$lt_cv_sys_global_symbol_pipe" \> $nlist\""; } >&5 + (eval $NM conftest.$ac_objext \| "$lt_cv_sys_global_symbol_pipe" \> $nlist) 2>&5 ac_status=$? $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; } && test -s "$nlist"; then @@ -7454,6 +7840,18 @@ _LT_EOF if $GREP ' nm_test_var$' "$nlist" >/dev/null; then if $GREP ' nm_test_func$' "$nlist" >/dev/null; then cat <<_LT_EOF > conftest.$ac_ext +/* Keep this code in sync between libtool.m4, ltmain, lt_system.h, and tests. */ +#if defined(_WIN32) || defined(__CYGWIN__) || defined(_WIN32_WCE) +/* DATA imports from DLLs on WIN32 con't be const, because runtime + relocations are performed -- see ld's documentation on pseudo-relocs. */ +# define LT_DLSYM_CONST +#elif defined(__osf__) +/* This system does not cope well with relocations in const data. */ +# define LT_DLSYM_CONST +#else +# define LT_DLSYM_CONST const +#endif + #ifdef __cplusplus extern "C" { #endif @@ -7465,7 +7863,7 @@ _LT_EOF cat <<_LT_EOF >> conftest.$ac_ext /* The mapping between symbol names and symbols. */ -const struct { +LT_DLSYM_CONST struct { const char *name; void *address; } @@ -7491,8 +7889,8 @@ static const void *lt_preloaded_setup() { _LT_EOF # Now try linking the two files. mv conftest.$ac_objext conftstm.$ac_objext - lt_save_LIBS="$LIBS" - lt_save_CFLAGS="$CFLAGS" + lt_globsym_save_LIBS=$LIBS + lt_globsym_save_CFLAGS=$CFLAGS LIBS="conftstm.$ac_objext" CFLAGS="$CFLAGS$lt_prog_compiler_no_builtin_flag" if { { eval echo "\"\$as_me\":${as_lineno-$LINENO}: \"$ac_link\""; } >&5 @@ -7502,8 +7900,8 @@ _LT_EOF test $ac_status = 0; } && test -s conftest${ac_exeext}; then pipe_works=yes fi - LIBS="$lt_save_LIBS" - CFLAGS="$lt_save_CFLAGS" + LIBS=$lt_globsym_save_LIBS + CFLAGS=$lt_globsym_save_CFLAGS else echo "cannot find nm_test_func in $nlist" >&5 fi @@ -7540,6 +7938,26 @@ else $as_echo "ok" >&6; } fi +# Response file support. +if test "$lt_cv_nm_interface" = "MS dumpbin"; then + nm_file_list_spec='@' +elif $NM --help 2>/dev/null | grep '[@]FILE' >/dev/null; then + nm_file_list_spec='@' +fi + + + + + + + + + + + + + + @@ -7553,10 +7971,38 @@ fi +{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for sysroot" >&5 +$as_echo_n "checking for sysroot... " >&6; } +# Check whether --with-sysroot was given. +if test "${with_sysroot+set}" = set; then : + withval=$with_sysroot; +else + with_sysroot=no +fi +lt_sysroot= +case ${with_sysroot} in #( + yes) + if test "$GCC" = yes; then + lt_sysroot=`$CC --print-sysroot 2>/dev/null` + fi + ;; #( + /*) + lt_sysroot=`echo "$with_sysroot" | sed -e "$sed_quote_subst"` + ;; #( + no|'') + ;; #( + *) + { $as_echo "$as_me:${as_lineno-$LINENO}: result: ${with_sysroot}" >&5 +$as_echo "${with_sysroot}" >&6; } + as_fn_error $? "The sysroot must be an absolute path." "$LINENO" 5 + ;; +esac + { $as_echo "$as_me:${as_lineno-$LINENO}: result: ${lt_sysroot:-no}" >&5 +$as_echo "${lt_sysroot:-no}" >&6; } @@ -7593,7 +8039,7 @@ ia64-*-hpux*) ;; *-*-irix6*) # Find out which ABI we are using. - echo '#line 7596 "configure"' > conftest.$ac_ext + echo '#line '$LINENO' "configure"' > conftest.$ac_ext if { { eval echo "\"\$as_me\":${as_lineno-$LINENO}: \"$ac_compile\""; } >&5 (eval $ac_compile) 2>&5 ac_status=$? @@ -7687,7 +8133,7 @@ s390*-*linux*|s390*-*tpf*|sparc*-*linux*) CFLAGS="$CFLAGS -belf" { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether the C compiler needs -belf" >&5 $as_echo_n "checking whether the C compiler needs -belf... " >&6; } -if test "${lt_cv_cc_needs_belf+set}" = set; then : +if ${lt_cv_cc_needs_belf+:} false; then : $as_echo_n "(cached) " >&6 else ac_ext=c @@ -7728,7 +8174,7 @@ $as_echo "$lt_cv_cc_needs_belf" >&6; } CFLAGS="$SAVE_CFLAGS" fi ;; -sparc*-*solaris*) +*-*solaris*) # Find out which ABI we are using. echo 'int i;' > conftest.$ac_ext if { { eval echo "\"\$as_me\":${as_lineno-$LINENO}: \"$ac_compile\""; } >&5 @@ -7739,7 +8185,20 @@ sparc*-*solaris*) case `/usr/bin/file conftest.o` in *64-bit*) case $lt_cv_prog_gnu_ld in - yes*) LD="${LD-ld} -m elf64_sparc" ;; + yes*) + case $host in + i?86-*-solaris*) + LD="${LD-ld} -m elf_x86_64" + ;; + sparc*-*-solaris*) + LD="${LD-ld} -m elf64_sparc" + ;; + esac + # GNU ld 2.21 introduced _sol2 emulations. Use them if available. + if ${LD-ld} -V | grep _sol2 >/dev/null 2>&1; then + LD="${LD-ld}_sol2" + fi + ;; *) if ${LD-ld} -64 -r -o conftest2.o conftest.o >/dev/null 2>&1; then LD="${LD-ld} -64" @@ -7755,19 +8214,16 @@ esac need_locks="$enable_libtool_lock" - - case $host_os in - rhapsody* | darwin*) - if test -n "$ac_tool_prefix"; then - # Extract the first word of "${ac_tool_prefix}dsymutil", so it can be a program name with args. -set dummy ${ac_tool_prefix}dsymutil; ac_word=$2 +if test -n "$ac_tool_prefix"; then + # Extract the first word of "${ac_tool_prefix}mt", so it can be a program name with args. +set dummy ${ac_tool_prefix}mt; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } -if test "${ac_cv_prog_DSYMUTIL+set}" = set; then : +if ${ac_cv_prog_MANIFEST_TOOL+:} false; then : $as_echo_n "(cached) " >&6 else - if test -n "$DSYMUTIL"; then - ac_cv_prog_DSYMUTIL="$DSYMUTIL" # Let the user override the test. + if test -n "$MANIFEST_TOOL"; then + ac_cv_prog_MANIFEST_TOOL="$MANIFEST_TOOL" # Let the user override the test. else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH @@ -7775,8 +8231,8 @@ do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do - if { test -f "$as_dir/$ac_word$ac_exec_ext" && $as_test_x "$as_dir/$ac_word$ac_exec_ext"; }; then - ac_cv_prog_DSYMUTIL="${ac_tool_prefix}dsymutil" + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then + ac_cv_prog_MANIFEST_TOOL="${ac_tool_prefix}mt" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi @@ -7786,10 +8242,10 @@ IFS=$as_save_IFS fi fi -DSYMUTIL=$ac_cv_prog_DSYMUTIL -if test -n "$DSYMUTIL"; then - { $as_echo "$as_me:${as_lineno-$LINENO}: result: $DSYMUTIL" >&5 -$as_echo "$DSYMUTIL" >&6; } +MANIFEST_TOOL=$ac_cv_prog_MANIFEST_TOOL +if test -n "$MANIFEST_TOOL"; then + { $as_echo "$as_me:${as_lineno-$LINENO}: result: $MANIFEST_TOOL" >&5 +$as_echo "$MANIFEST_TOOL" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } @@ -7797,17 +8253,17 @@ fi fi -if test -z "$ac_cv_prog_DSYMUTIL"; then - ac_ct_DSYMUTIL=$DSYMUTIL - # Extract the first word of "dsymutil", so it can be a program name with args. -set dummy dsymutil; ac_word=$2 +if test -z "$ac_cv_prog_MANIFEST_TOOL"; then + ac_ct_MANIFEST_TOOL=$MANIFEST_TOOL + # Extract the first word of "mt", so it can be a program name with args. +set dummy mt; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } -if test "${ac_cv_prog_ac_ct_DSYMUTIL+set}" = set; then : +if ${ac_cv_prog_ac_ct_MANIFEST_TOOL+:} false; then : $as_echo_n "(cached) " >&6 else - if test -n "$ac_ct_DSYMUTIL"; then - ac_cv_prog_ac_ct_DSYMUTIL="$ac_ct_DSYMUTIL" # Let the user override the test. + if test -n "$ac_ct_MANIFEST_TOOL"; then + ac_cv_prog_ac_ct_MANIFEST_TOOL="$ac_ct_MANIFEST_TOOL" # Let the user override the test. else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH @@ -7815,8 +8271,8 @@ do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do - if { test -f "$as_dir/$ac_word$ac_exec_ext" && $as_test_x "$as_dir/$ac_word$ac_exec_ext"; }; then - ac_cv_prog_ac_ct_DSYMUTIL="dsymutil" + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then + ac_cv_prog_ac_ct_MANIFEST_TOOL="mt" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi @@ -7826,17 +8282,17 @@ IFS=$as_save_IFS fi fi -ac_ct_DSYMUTIL=$ac_cv_prog_ac_ct_DSYMUTIL -if test -n "$ac_ct_DSYMUTIL"; then - { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_ct_DSYMUTIL" >&5 -$as_echo "$ac_ct_DSYMUTIL" >&6; } +ac_ct_MANIFEST_TOOL=$ac_cv_prog_ac_ct_MANIFEST_TOOL +if test -n "$ac_ct_MANIFEST_TOOL"; then + { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_ct_MANIFEST_TOOL" >&5 +$as_echo "$ac_ct_MANIFEST_TOOL" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi - if test "x$ac_ct_DSYMUTIL" = x; then - DSYMUTIL=":" + if test "x$ac_ct_MANIFEST_TOOL" = x; then + MANIFEST_TOOL=":" else case $cross_compiling:$ac_tool_warned in yes:) @@ -7844,22 +8300,50 @@ yes:) $as_echo "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;} ac_tool_warned=yes ;; esac - DSYMUTIL=$ac_ct_DSYMUTIL + MANIFEST_TOOL=$ac_ct_MANIFEST_TOOL fi else - DSYMUTIL="$ac_cv_prog_DSYMUTIL" + MANIFEST_TOOL="$ac_cv_prog_MANIFEST_TOOL" +fi + +test -z "$MANIFEST_TOOL" && MANIFEST_TOOL=mt +{ $as_echo "$as_me:${as_lineno-$LINENO}: checking if $MANIFEST_TOOL is a manifest tool" >&5 +$as_echo_n "checking if $MANIFEST_TOOL is a manifest tool... " >&6; } +if ${lt_cv_path_mainfest_tool+:} false; then : + $as_echo_n "(cached) " >&6 +else + lt_cv_path_mainfest_tool=no + echo "$as_me:$LINENO: $MANIFEST_TOOL '-?'" >&5 + $MANIFEST_TOOL '-?' 2>conftest.err > conftest.out + cat conftest.err >&5 + if $GREP 'Manifest Tool' conftest.out > /dev/null; then + lt_cv_path_mainfest_tool=yes + fi + rm -f conftest* +fi +{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $lt_cv_path_mainfest_tool" >&5 +$as_echo "$lt_cv_path_mainfest_tool" >&6; } +if test "x$lt_cv_path_mainfest_tool" != xyes; then + MANIFEST_TOOL=: fi + + + + + + case $host_os in + rhapsody* | darwin*) if test -n "$ac_tool_prefix"; then - # Extract the first word of "${ac_tool_prefix}nmedit", so it can be a program name with args. -set dummy ${ac_tool_prefix}nmedit; ac_word=$2 + # Extract the first word of "${ac_tool_prefix}dsymutil", so it can be a program name with args. +set dummy ${ac_tool_prefix}dsymutil; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } -if test "${ac_cv_prog_NMEDIT+set}" = set; then : +if ${ac_cv_prog_DSYMUTIL+:} false; then : $as_echo_n "(cached) " >&6 else - if test -n "$NMEDIT"; then - ac_cv_prog_NMEDIT="$NMEDIT" # Let the user override the test. + if test -n "$DSYMUTIL"; then + ac_cv_prog_DSYMUTIL="$DSYMUTIL" # Let the user override the test. else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH @@ -7867,8 +8351,8 @@ do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do - if { test -f "$as_dir/$ac_word$ac_exec_ext" && $as_test_x "$as_dir/$ac_word$ac_exec_ext"; }; then - ac_cv_prog_NMEDIT="${ac_tool_prefix}nmedit" + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then + ac_cv_prog_DSYMUTIL="${ac_tool_prefix}dsymutil" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi @@ -7878,10 +8362,10 @@ IFS=$as_save_IFS fi fi -NMEDIT=$ac_cv_prog_NMEDIT -if test -n "$NMEDIT"; then - { $as_echo "$as_me:${as_lineno-$LINENO}: result: $NMEDIT" >&5 -$as_echo "$NMEDIT" >&6; } +DSYMUTIL=$ac_cv_prog_DSYMUTIL +if test -n "$DSYMUTIL"; then + { $as_echo "$as_me:${as_lineno-$LINENO}: result: $DSYMUTIL" >&5 +$as_echo "$DSYMUTIL" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } @@ -7889,25 +8373,117 @@ fi fi -if test -z "$ac_cv_prog_NMEDIT"; then - ac_ct_NMEDIT=$NMEDIT - # Extract the first word of "nmedit", so it can be a program name with args. -set dummy nmedit; ac_word=$2 +if test -z "$ac_cv_prog_DSYMUTIL"; then + ac_ct_DSYMUTIL=$DSYMUTIL + # Extract the first word of "dsymutil", so it can be a program name with args. +set dummy dsymutil; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } -if test "${ac_cv_prog_ac_ct_NMEDIT+set}" = set; then : +if ${ac_cv_prog_ac_ct_DSYMUTIL+:} false; then : $as_echo_n "(cached) " >&6 else - if test -n "$ac_ct_NMEDIT"; then - ac_cv_prog_ac_ct_NMEDIT="$ac_ct_NMEDIT" # Let the user override the test. -else + if test -n "$ac_ct_DSYMUTIL"; then + ac_cv_prog_ac_ct_DSYMUTIL="$ac_ct_DSYMUTIL" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + test -z "$as_dir" && as_dir=. + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then + ac_cv_prog_ac_ct_DSYMUTIL="dsymutil" + $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + +fi +fi +ac_ct_DSYMUTIL=$ac_cv_prog_ac_ct_DSYMUTIL +if test -n "$ac_ct_DSYMUTIL"; then + { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_ct_DSYMUTIL" >&5 +$as_echo "$ac_ct_DSYMUTIL" >&6; } +else + { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 +$as_echo "no" >&6; } +fi + + if test "x$ac_ct_DSYMUTIL" = x; then + DSYMUTIL=":" + else + case $cross_compiling:$ac_tool_warned in +yes:) +{ $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet" >&5 +$as_echo "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;} +ac_tool_warned=yes ;; +esac + DSYMUTIL=$ac_ct_DSYMUTIL + fi +else + DSYMUTIL="$ac_cv_prog_DSYMUTIL" +fi + + if test -n "$ac_tool_prefix"; then + # Extract the first word of "${ac_tool_prefix}nmedit", so it can be a program name with args. +set dummy ${ac_tool_prefix}nmedit; ac_word=$2 +{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +$as_echo_n "checking for $ac_word... " >&6; } +if ${ac_cv_prog_NMEDIT+:} false; then : + $as_echo_n "(cached) " >&6 +else + if test -n "$NMEDIT"; then + ac_cv_prog_NMEDIT="$NMEDIT" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + test -z "$as_dir" && as_dir=. + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then + ac_cv_prog_NMEDIT="${ac_tool_prefix}nmedit" + $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + +fi +fi +NMEDIT=$ac_cv_prog_NMEDIT +if test -n "$NMEDIT"; then + { $as_echo "$as_me:${as_lineno-$LINENO}: result: $NMEDIT" >&5 +$as_echo "$NMEDIT" >&6; } +else + { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 +$as_echo "no" >&6; } +fi + + +fi +if test -z "$ac_cv_prog_NMEDIT"; then + ac_ct_NMEDIT=$NMEDIT + # Extract the first word of "nmedit", so it can be a program name with args. +set dummy nmedit; ac_word=$2 +{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +$as_echo_n "checking for $ac_word... " >&6; } +if ${ac_cv_prog_ac_ct_NMEDIT+:} false; then : + $as_echo_n "(cached) " >&6 +else + if test -n "$ac_ct_NMEDIT"; then + ac_cv_prog_ac_ct_NMEDIT="$ac_ct_NMEDIT" # Let the user override the test. +else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do - if { test -f "$as_dir/$ac_word$ac_exec_ext" && $as_test_x "$as_dir/$ac_word$ac_exec_ext"; }; then + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_ac_ct_NMEDIT="nmedit" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 @@ -7947,7 +8523,7 @@ fi set dummy ${ac_tool_prefix}lipo; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } -if test "${ac_cv_prog_LIPO+set}" = set; then : +if ${ac_cv_prog_LIPO+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$LIPO"; then @@ -7959,7 +8535,7 @@ do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do - if { test -f "$as_dir/$ac_word$ac_exec_ext" && $as_test_x "$as_dir/$ac_word$ac_exec_ext"; }; then + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_LIPO="${ac_tool_prefix}lipo" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 @@ -7987,7 +8563,7 @@ if test -z "$ac_cv_prog_LIPO"; then set dummy lipo; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } -if test "${ac_cv_prog_ac_ct_LIPO+set}" = set; then : +if ${ac_cv_prog_ac_ct_LIPO+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$ac_ct_LIPO"; then @@ -7999,7 +8575,7 @@ do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do - if { test -f "$as_dir/$ac_word$ac_exec_ext" && $as_test_x "$as_dir/$ac_word$ac_exec_ext"; }; then + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_ac_ct_LIPO="lipo" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 @@ -8039,7 +8615,7 @@ fi set dummy ${ac_tool_prefix}otool; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } -if test "${ac_cv_prog_OTOOL+set}" = set; then : +if ${ac_cv_prog_OTOOL+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$OTOOL"; then @@ -8051,7 +8627,7 @@ do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do - if { test -f "$as_dir/$ac_word$ac_exec_ext" && $as_test_x "$as_dir/$ac_word$ac_exec_ext"; }; then + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_OTOOL="${ac_tool_prefix}otool" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 @@ -8079,7 +8655,7 @@ if test -z "$ac_cv_prog_OTOOL"; then set dummy otool; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } -if test "${ac_cv_prog_ac_ct_OTOOL+set}" = set; then : +if ${ac_cv_prog_ac_ct_OTOOL+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$ac_ct_OTOOL"; then @@ -8091,7 +8667,7 @@ do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do - if { test -f "$as_dir/$ac_word$ac_exec_ext" && $as_test_x "$as_dir/$ac_word$ac_exec_ext"; }; then + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_ac_ct_OTOOL="otool" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 @@ -8131,7 +8707,7 @@ fi set dummy ${ac_tool_prefix}otool64; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } -if test "${ac_cv_prog_OTOOL64+set}" = set; then : +if ${ac_cv_prog_OTOOL64+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$OTOOL64"; then @@ -8143,7 +8719,7 @@ do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do - if { test -f "$as_dir/$ac_word$ac_exec_ext" && $as_test_x "$as_dir/$ac_word$ac_exec_ext"; }; then + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_OTOOL64="${ac_tool_prefix}otool64" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 @@ -8171,7 +8747,7 @@ if test -z "$ac_cv_prog_OTOOL64"; then set dummy otool64; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } -if test "${ac_cv_prog_ac_ct_OTOOL64+set}" = set; then : +if ${ac_cv_prog_ac_ct_OTOOL64+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$ac_ct_OTOOL64"; then @@ -8183,7 +8759,7 @@ do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do - if { test -f "$as_dir/$ac_word$ac_exec_ext" && $as_test_x "$as_dir/$ac_word$ac_exec_ext"; }; then + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_ac_ct_OTOOL64="otool64" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 @@ -8246,7 +8822,7 @@ fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking for -single_module linker flag" >&5 $as_echo_n "checking for -single_module linker flag... " >&6; } -if test "${lt_cv_apple_cc_single_mod+set}" = set; then : +if ${lt_cv_apple_cc_single_mod+:} false; then : $as_echo_n "(cached) " >&6 else lt_cv_apple_cc_single_mod=no @@ -8262,7 +8838,13 @@ else $LTCC $LTCFLAGS $LDFLAGS -o libconftest.dylib \ -dynamiclib -Wl,-single_module conftest.c 2>conftest.err _lt_result=$? - if test -f libconftest.dylib && test ! -s conftest.err && test $_lt_result = 0; then + # If there is a non-empty error log, and "single_module" + # appears in it, assume the flag caused a linker warning + if test -s conftest.err && $GREP single_module conftest.err; then + cat conftest.err >&5 + # Otherwise, if the output was created with a 0 exit code from + # the compiler, it worked. + elif test -f libconftest.dylib && test $_lt_result -eq 0; then lt_cv_apple_cc_single_mod=yes else cat conftest.err >&5 @@ -8273,9 +8855,10 @@ else fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $lt_cv_apple_cc_single_mod" >&5 $as_echo "$lt_cv_apple_cc_single_mod" >&6; } + { $as_echo "$as_me:${as_lineno-$LINENO}: checking for -exported_symbols_list linker flag" >&5 $as_echo_n "checking for -exported_symbols_list linker flag... " >&6; } -if test "${lt_cv_ld_exported_symbols_list+set}" = set; then : +if ${lt_cv_ld_exported_symbols_list+:} false; then : $as_echo_n "(cached) " >&6 else lt_cv_ld_exported_symbols_list=no @@ -8305,6 +8888,41 @@ rm -f core conftest.err conftest.$ac_objext \ fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $lt_cv_ld_exported_symbols_list" >&5 $as_echo "$lt_cv_ld_exported_symbols_list" >&6; } + + { $as_echo "$as_me:${as_lineno-$LINENO}: checking for -force_load linker flag" >&5 +$as_echo_n "checking for -force_load linker flag... " >&6; } +if ${lt_cv_ld_force_load+:} false; then : + $as_echo_n "(cached) " >&6 +else + lt_cv_ld_force_load=no + cat > conftest.c << _LT_EOF +int forced_loaded() { return 2;} +_LT_EOF + echo "$LTCC $LTCFLAGS -c -o conftest.o conftest.c" >&5 + $LTCC $LTCFLAGS -c -o conftest.o conftest.c 2>&5 + echo "$AR cru libconftest.a conftest.o" >&5 + $AR cru libconftest.a conftest.o 2>&5 + echo "$RANLIB libconftest.a" >&5 + $RANLIB libconftest.a 2>&5 + cat > conftest.c << _LT_EOF +int main() { return 0;} +_LT_EOF + echo "$LTCC $LTCFLAGS $LDFLAGS -o conftest conftest.c -Wl,-force_load,./libconftest.a" >&5 + $LTCC $LTCFLAGS $LDFLAGS -o conftest conftest.c -Wl,-force_load,./libconftest.a 2>conftest.err + _lt_result=$? + if test -s conftest.err && $GREP force_load conftest.err; then + cat conftest.err >&5 + elif test -f conftest && test $_lt_result -eq 0 && $GREP forced_load conftest >/dev/null 2>&1 ; then + lt_cv_ld_force_load=yes + else + cat conftest.err >&5 + fi + rm -f conftest.err libconftest.a conftest conftest.c + rm -rf conftest.dSYM + +fi +{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $lt_cv_ld_force_load" >&5 +$as_echo "$lt_cv_ld_force_load" >&6; } case $host_os in rhapsody* | darwin1.[012]) _lt_dar_allow_undefined='${wl}-undefined ${wl}suppress' ;; @@ -8332,7 +8950,7 @@ $as_echo "$lt_cv_ld_exported_symbols_list" >&6; } else _lt_dar_export_syms='~$NMEDIT -s $output_objdir/${libname}-symbols.expsym ${lib}' fi - if test "$DSYMUTIL" != ":"; then + if test "$DSYMUTIL" != ":" && test "$lt_cv_ld_force_load" = "no"; then _lt_dsymutil='~$DSYMUTIL $lib || :' else _lt_dsymutil= @@ -8343,7 +8961,7 @@ $as_echo "$lt_cv_ld_exported_symbols_list" >&6; } { $as_echo "$as_me:${as_lineno-$LINENO}: checking for ANSI C header files" >&5 $as_echo_n "checking for ANSI C header files... " >&6; } -if test "${ac_cv_header_stdc+set}" = set; then : +if ${ac_cv_header_stdc+:} false; then : $as_echo_n "(cached) " >&6 else cat confdefs.h - <<_ACEOF >conftest.$ac_ext @@ -8474,7 +9092,7 @@ for ac_header in dlfcn.h do : ac_fn_c_check_header_compile "$LINENO" "dlfcn.h" "ac_cv_header_dlfcn_h" "$ac_includes_default " -if test "x$ac_cv_header_dlfcn_h" = x""yes; then : +if test "x$ac_cv_header_dlfcn_h" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_DLFCN_H 1 _ACEOF @@ -8485,27 +9103,64 @@ done -ac_ext=cpp -ac_cpp='$CXXCPP $CPPFLAGS' -ac_compile='$CXX -c $CXXFLAGS $CPPFLAGS conftest.$ac_ext >&5' -ac_link='$CXX -o conftest$ac_exeext $CXXFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5' -ac_compiler_gnu=$ac_cv_cxx_compiler_gnu -if test -z "$CXX"; then - if test -n "$CCC"; then - CXX=$CCC - else - if test -n "$ac_tool_prefix"; then - for ac_prog in g++ c++ gpp aCC CC cxx cc++ cl.exe FCC KCC RCC xlC_r xlC - do - # Extract the first word of "$ac_tool_prefix$ac_prog", so it can be a program name with args. -set dummy $ac_tool_prefix$ac_prog; ac_word=$2 + +func_stripname_cnf () +{ + case ${2} in + .*) func_stripname_result=`$ECHO "${3}" | $SED "s%^${1}%%; s%\\\\${2}\$%%"`;; + *) func_stripname_result=`$ECHO "${3}" | $SED "s%^${1}%%; s%${2}\$%%"`;; + esac +} # func_stripname_cnf + + + + + +# Set options +# Check whether --enable-static was given. +if test "${enable_static+set}" = set; then : + enableval=$enable_static; p=${PACKAGE-default} + case $enableval in + yes) enable_static=yes ;; + no) enable_static=no ;; + *) + enable_static=no + # Look at the argument we got. We use all the common list separators. + lt_save_ifs="$IFS"; IFS="${IFS}$PATH_SEPARATOR," + for pkg in $enableval; do + IFS="$lt_save_ifs" + if test "X$pkg" = "X$p"; then + enable_static=yes + fi + done + IFS="$lt_save_ifs" + ;; + esac +else + enable_static=no +fi + + + + + + + +enable_dlopen=yes +enable_win32_dll=yes + +case $host in +*-*-cygwin* | *-*-mingw* | *-*-pw32* | *-*-cegcc*) + if test -n "$ac_tool_prefix"; then + # Extract the first word of "${ac_tool_prefix}as", so it can be a program name with args. +set dummy ${ac_tool_prefix}as; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } -if test "${ac_cv_prog_CXX+set}" = set; then : +if ${ac_cv_prog_AS+:} false; then : $as_echo_n "(cached) " >&6 else - if test -n "$CXX"; then - ac_cv_prog_CXX="$CXX" # Let the user override the test. + if test -n "$AS"; then + ac_cv_prog_AS="$AS" # Let the user override the test. else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH @@ -8513,8 +9168,8 @@ do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do - if { test -f "$as_dir/$ac_word$ac_exec_ext" && $as_test_x "$as_dir/$ac_word$ac_exec_ext"; }; then - ac_cv_prog_CXX="$ac_tool_prefix$ac_prog" + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then + ac_cv_prog_AS="${ac_tool_prefix}as" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi @@ -8524,32 +9179,28 @@ IFS=$as_save_IFS fi fi -CXX=$ac_cv_prog_CXX -if test -n "$CXX"; then - { $as_echo "$as_me:${as_lineno-$LINENO}: result: $CXX" >&5 -$as_echo "$CXX" >&6; } +AS=$ac_cv_prog_AS +if test -n "$AS"; then + { $as_echo "$as_me:${as_lineno-$LINENO}: result: $AS" >&5 +$as_echo "$AS" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi - test -n "$CXX" && break - done fi -if test -z "$CXX"; then - ac_ct_CXX=$CXX - for ac_prog in g++ c++ gpp aCC CC cxx cc++ cl.exe FCC KCC RCC xlC_r xlC -do - # Extract the first word of "$ac_prog", so it can be a program name with args. -set dummy $ac_prog; ac_word=$2 +if test -z "$ac_cv_prog_AS"; then + ac_ct_AS=$AS + # Extract the first word of "as", so it can be a program name with args. +set dummy as; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } -if test "${ac_cv_prog_ac_ct_CXX+set}" = set; then : +if ${ac_cv_prog_ac_ct_AS+:} false; then : $as_echo_n "(cached) " >&6 else - if test -n "$ac_ct_CXX"; then - ac_cv_prog_ac_ct_CXX="$ac_ct_CXX" # Let the user override the test. + if test -n "$ac_ct_AS"; then + ac_cv_prog_ac_ct_AS="$ac_ct_AS" # Let the user override the test. else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH @@ -8557,8 +9208,8 @@ do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do - if { test -f "$as_dir/$ac_word$ac_exec_ext" && $as_test_x "$as_dir/$ac_word$ac_exec_ext"; }; then - ac_cv_prog_ac_ct_CXX="$ac_prog" + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then + ac_cv_prog_ac_ct_AS="as" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi @@ -8568,21 +9219,17 @@ IFS=$as_save_IFS fi fi -ac_ct_CXX=$ac_cv_prog_ac_ct_CXX -if test -n "$ac_ct_CXX"; then - { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_ct_CXX" >&5 -$as_echo "$ac_ct_CXX" >&6; } +ac_ct_AS=$ac_cv_prog_ac_ct_AS +if test -n "$ac_ct_AS"; then + { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_ct_AS" >&5 +$as_echo "$ac_ct_AS" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi - - test -n "$ac_ct_CXX" && break -done - - if test "x$ac_ct_CXX" = x; then - CXX="g++" + if test "x$ac_ct_AS" = x; then + AS="false" else case $cross_compiling:$ac_tool_warned in yes:) @@ -8590,561 +9237,18 @@ yes:) $as_echo "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;} ac_tool_warned=yes ;; esac - CXX=$ac_ct_CXX - fi -fi - + AS=$ac_ct_AS fi +else + AS="$ac_cv_prog_AS" fi -# Provide some information about the compiler. -$as_echo "$as_me:${as_lineno-$LINENO}: checking for C++ compiler version" >&5 -set X $ac_compile -ac_compiler=$2 -for ac_option in --version -v -V -qversion; do - { { ac_try="$ac_compiler $ac_option >&5" -case "(($ac_try" in - *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;; - *) ac_try_echo=$ac_try;; -esac -eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\"" -$as_echo "$ac_try_echo"; } >&5 - (eval "$ac_compiler $ac_option >&5") 2>conftest.err - ac_status=$? - if test -s conftest.err; then - sed '10a\ -... rest of stderr output deleted ... - 10q' conftest.err >conftest.er1 - cat conftest.er1 >&5 - fi - rm -f conftest.er1 conftest.err - $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 - test $ac_status = 0; } -done -{ $as_echo "$as_me:${as_lineno-$LINENO}: checking whether we are using the GNU C++ compiler" >&5 -$as_echo_n "checking whether we are using the GNU C++ compiler... " >&6; } -if test "${ac_cv_cxx_compiler_gnu+set}" = set; then : - $as_echo_n "(cached) " >&6 -else - cat confdefs.h - <<_ACEOF >conftest.$ac_ext -/* end confdefs.h. */ - -int -main () -{ -#ifndef __GNUC__ - choke me -#endif - - ; - return 0; -} -_ACEOF -if ac_fn_cxx_try_compile "$LINENO"; then : - ac_compiler_gnu=yes -else - ac_compiler_gnu=no -fi -rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext -ac_cv_cxx_compiler_gnu=$ac_compiler_gnu - -fi -{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_cxx_compiler_gnu" >&5 -$as_echo "$ac_cv_cxx_compiler_gnu" >&6; } -if test $ac_compiler_gnu = yes; then - GXX=yes -else - GXX= -fi -ac_test_CXXFLAGS=${CXXFLAGS+set} -ac_save_CXXFLAGS=$CXXFLAGS -{ $as_echo "$as_me:${as_lineno-$LINENO}: checking whether $CXX accepts -g" >&5 -$as_echo_n "checking whether $CXX accepts -g... " >&6; } -if test "${ac_cv_prog_cxx_g+set}" = set; then : - $as_echo_n "(cached) " >&6 -else - ac_save_cxx_werror_flag=$ac_cxx_werror_flag - ac_cxx_werror_flag=yes - ac_cv_prog_cxx_g=no - CXXFLAGS="-g" - cat confdefs.h - <<_ACEOF >conftest.$ac_ext -/* end confdefs.h. */ - -int -main () -{ - - ; - return 0; -} -_ACEOF -if ac_fn_cxx_try_compile "$LINENO"; then : - ac_cv_prog_cxx_g=yes -else - CXXFLAGS="" - cat confdefs.h - <<_ACEOF >conftest.$ac_ext -/* end confdefs.h. */ - -int -main () -{ - - ; - return 0; -} -_ACEOF -if ac_fn_cxx_try_compile "$LINENO"; then : - -else - ac_cxx_werror_flag=$ac_save_cxx_werror_flag - CXXFLAGS="-g" - cat confdefs.h - <<_ACEOF >conftest.$ac_ext -/* end confdefs.h. */ - -int -main () -{ - - ; - return 0; -} -_ACEOF -if ac_fn_cxx_try_compile "$LINENO"; then : - ac_cv_prog_cxx_g=yes -fi -rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext -fi -rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext -fi -rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext - ac_cxx_werror_flag=$ac_save_cxx_werror_flag -fi -{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_prog_cxx_g" >&5 -$as_echo "$ac_cv_prog_cxx_g" >&6; } -if test "$ac_test_CXXFLAGS" = set; then - CXXFLAGS=$ac_save_CXXFLAGS -elif test $ac_cv_prog_cxx_g = yes; then - if test "$GXX" = yes; then - CXXFLAGS="-g -O2" - else - CXXFLAGS="-g" - fi -else - if test "$GXX" = yes; then - CXXFLAGS="-O2" - else - CXXFLAGS= - fi -fi -ac_ext=c -ac_cpp='$CPP $CPPFLAGS' -ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5' -ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5' -ac_compiler_gnu=$ac_cv_c_compiler_gnu - -depcc="$CXX" am_compiler_list= - -{ $as_echo "$as_me:${as_lineno-$LINENO}: checking dependency style of $depcc" >&5 -$as_echo_n "checking dependency style of $depcc... " >&6; } -if test "${am_cv_CXX_dependencies_compiler_type+set}" = set; then : - $as_echo_n "(cached) " >&6 -else - if test -z "$AMDEP_TRUE" && test -f "$am_depcomp"; then - # We make a subdir and do the tests there. Otherwise we can end up - # making bogus files that we don't know about and never remove. For - # instance it was reported that on HP-UX the gcc test will end up - # making a dummy file named `D' -- because `-MD' means `put the output - # in D'. - mkdir conftest.dir - # Copy depcomp to subdir because otherwise we won't find it if we're - # using a relative directory. - cp "$am_depcomp" conftest.dir - cd conftest.dir - # We will build objects and dependencies in a subdirectory because - # it helps to detect inapplicable dependency modes. For instance - # both Tru64's cc and ICC support -MD to output dependencies as a - # side effect of compilation, but ICC will put the dependencies in - # the current directory while Tru64 will put them in the object - # directory. - mkdir sub - - am_cv_CXX_dependencies_compiler_type=none - if test "$am_compiler_list" = ""; then - am_compiler_list=`sed -n 's/^#*\([a-zA-Z0-9]*\))$/\1/p' < ./depcomp` - fi - am__universal=false - case " $depcc " in #( - *\ -arch\ *\ -arch\ *) am__universal=true ;; - esac - - for depmode in $am_compiler_list; do - # Setup a source with many dependencies, because some compilers - # like to wrap large dependency lists on column 80 (with \), and - # we should not choose a depcomp mode which is confused by this. - # - # We need to recreate these files for each test, as the compiler may - # overwrite some of them when testing with obscure command lines. - # This happens at least with the AIX C compiler. - : > sub/conftest.c - for i in 1 2 3 4 5 6; do - echo '#include "conftst'$i'.h"' >> sub/conftest.c - # Using `: > sub/conftst$i.h' creates only sub/conftst1.h with - # Solaris 8's {/usr,}/bin/sh. - touch sub/conftst$i.h - done - echo "${am__include} ${am__quote}sub/conftest.Po${am__quote}" > confmf - - # We check with `-c' and `-o' for the sake of the "dashmstdout" - # mode. It turns out that the SunPro C++ compiler does not properly - # handle `-M -o', and we need to detect this. Also, some Intel - # versions had trouble with output in subdirs - am__obj=sub/conftest.${OBJEXT-o} - am__minus_obj="-o $am__obj" - case $depmode in - gcc) - # This depmode causes a compiler race in universal mode. - test "$am__universal" = false || continue - ;; - nosideeffect) - # after this tag, mechanisms are not by side-effect, so they'll - # only be used when explicitly requested - if test "x$enable_dependency_tracking" = xyes; then - continue - else - break - fi - ;; - msvisualcpp | msvcmsys) - # This compiler won't grok `-c -o', but also, the minuso test has - # not run yet. These depmodes are late enough in the game, and - # so weak that their functioning should not be impacted. - am__obj=conftest.${OBJEXT-o} - am__minus_obj= - ;; - none) break ;; - esac - if depmode=$depmode \ - source=sub/conftest.c object=$am__obj \ - depfile=sub/conftest.Po tmpdepfile=sub/conftest.TPo \ - $SHELL ./depcomp $depcc -c $am__minus_obj sub/conftest.c \ - >/dev/null 2>conftest.err && - grep sub/conftst1.h sub/conftest.Po > /dev/null 2>&1 && - grep sub/conftst6.h sub/conftest.Po > /dev/null 2>&1 && - grep $am__obj sub/conftest.Po > /dev/null 2>&1 && - ${MAKE-make} -s -f confmf > /dev/null 2>&1; then - # icc doesn't choke on unknown options, it will just issue warnings - # or remarks (even with -Werror). So we grep stderr for any message - # that says an option was ignored or not supported. - # When given -MP, icc 7.0 and 7.1 complain thusly: - # icc: Command line warning: ignoring option '-M'; no argument required - # The diagnosis changed in icc 8.0: - # icc: Command line remark: option '-MP' not supported - if (grep 'ignoring option' conftest.err || - grep 'not supported' conftest.err) >/dev/null 2>&1; then :; else - am_cv_CXX_dependencies_compiler_type=$depmode - break - fi - fi - done - - cd .. - rm -rf conftest.dir -else - am_cv_CXX_dependencies_compiler_type=none -fi - -fi -{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $am_cv_CXX_dependencies_compiler_type" >&5 -$as_echo "$am_cv_CXX_dependencies_compiler_type" >&6; } -CXXDEPMODE=depmode=$am_cv_CXX_dependencies_compiler_type - - if - test "x$enable_dependency_tracking" != xno \ - && test "$am_cv_CXX_dependencies_compiler_type" = gcc3; then - am__fastdepCXX_TRUE= - am__fastdepCXX_FALSE='#' -else - am__fastdepCXX_TRUE='#' - am__fastdepCXX_FALSE= -fi - - -if test -n "$CXX" && ( test "X$CXX" != "Xno" && - ( (test "X$CXX" = "Xg++" && `g++ -v >/dev/null 2>&1` ) || - (test "X$CXX" != "Xg++"))) ; then - ac_ext=cpp -ac_cpp='$CXXCPP $CPPFLAGS' -ac_compile='$CXX -c $CXXFLAGS $CPPFLAGS conftest.$ac_ext >&5' -ac_link='$CXX -o conftest$ac_exeext $CXXFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5' -ac_compiler_gnu=$ac_cv_cxx_compiler_gnu -{ $as_echo "$as_me:${as_lineno-$LINENO}: checking how to run the C++ preprocessor" >&5 -$as_echo_n "checking how to run the C++ preprocessor... " >&6; } -if test -z "$CXXCPP"; then - if test "${ac_cv_prog_CXXCPP+set}" = set; then : - $as_echo_n "(cached) " >&6 -else - # Double quotes because CXXCPP needs to be expanded - for CXXCPP in "$CXX -E" "/lib/cpp" - do - ac_preproc_ok=false -for ac_cxx_preproc_warn_flag in '' yes -do - # Use a header file that comes with gcc, so configuring glibc - # with a fresh cross-compiler works. - # Prefer to if __STDC__ is defined, since - # exists even on freestanding compilers. - # On the NeXT, cc -E runs the code through the compiler's parser, - # not just through cpp. "Syntax error" is here to catch this case. - cat confdefs.h - <<_ACEOF >conftest.$ac_ext -/* end confdefs.h. */ -#ifdef __STDC__ -# include -#else -# include -#endif - Syntax error -_ACEOF -if ac_fn_cxx_try_cpp "$LINENO"; then : - -else - # Broken: fails on valid input. -continue -fi -rm -f conftest.err conftest.i conftest.$ac_ext - - # OK, works on sane cases. Now check whether nonexistent headers - # can be detected and how. - cat confdefs.h - <<_ACEOF >conftest.$ac_ext -/* end confdefs.h. */ -#include -_ACEOF -if ac_fn_cxx_try_cpp "$LINENO"; then : - # Broken: success on invalid input. -continue -else - # Passes both tests. -ac_preproc_ok=: -break -fi -rm -f conftest.err conftest.i conftest.$ac_ext - -done -# Because of `break', _AC_PREPROC_IFELSE's cleaning code was skipped. -rm -f conftest.i conftest.err conftest.$ac_ext -if $ac_preproc_ok; then : - break -fi - - done - ac_cv_prog_CXXCPP=$CXXCPP - -fi - CXXCPP=$ac_cv_prog_CXXCPP -else - ac_cv_prog_CXXCPP=$CXXCPP -fi -{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $CXXCPP" >&5 -$as_echo "$CXXCPP" >&6; } -ac_preproc_ok=false -for ac_cxx_preproc_warn_flag in '' yes -do - # Use a header file that comes with gcc, so configuring glibc - # with a fresh cross-compiler works. - # Prefer to if __STDC__ is defined, since - # exists even on freestanding compilers. - # On the NeXT, cc -E runs the code through the compiler's parser, - # not just through cpp. "Syntax error" is here to catch this case. - cat confdefs.h - <<_ACEOF >conftest.$ac_ext -/* end confdefs.h. */ -#ifdef __STDC__ -# include -#else -# include -#endif - Syntax error -_ACEOF -if ac_fn_cxx_try_cpp "$LINENO"; then : - -else - # Broken: fails on valid input. -continue -fi -rm -f conftest.err conftest.i conftest.$ac_ext - - # OK, works on sane cases. Now check whether nonexistent headers - # can be detected and how. - cat confdefs.h - <<_ACEOF >conftest.$ac_ext -/* end confdefs.h. */ -#include -_ACEOF -if ac_fn_cxx_try_cpp "$LINENO"; then : - # Broken: success on invalid input. -continue -else - # Passes both tests. -ac_preproc_ok=: -break -fi -rm -f conftest.err conftest.i conftest.$ac_ext - -done -# Because of `break', _AC_PREPROC_IFELSE's cleaning code was skipped. -rm -f conftest.i conftest.err conftest.$ac_ext -if $ac_preproc_ok; then : - -else - { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 -$as_echo "$as_me: error: in \`$ac_pwd':" >&2;} -_lt_caught_CXX_error=yes; } -fi - -ac_ext=c -ac_cpp='$CPP $CPPFLAGS' -ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5' -ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5' -ac_compiler_gnu=$ac_cv_c_compiler_gnu - -else - _lt_caught_CXX_error=yes -fi - - - - - -# Set options -# Check whether --enable-static was given. -if test "${enable_static+set}" = set; then : - enableval=$enable_static; p=${PACKAGE-default} - case $enableval in - yes) enable_static=yes ;; - no) enable_static=no ;; - *) - enable_static=no - # Look at the argument we got. We use all the common list separators. - lt_save_ifs="$IFS"; IFS="${IFS}$PATH_SEPARATOR," - for pkg in $enableval; do - IFS="$lt_save_ifs" - if test "X$pkg" = "X$p"; then - enable_static=yes - fi - done - IFS="$lt_save_ifs" - ;; - esac -else - enable_static=no -fi - - - - - - - -enable_dlopen=yes -enable_win32_dll=yes - -case $host in -*-*-cygwin* | *-*-mingw* | *-*-pw32* | *-cegcc*) - if test -n "$ac_tool_prefix"; then - # Extract the first word of "${ac_tool_prefix}as", so it can be a program name with args. -set dummy ${ac_tool_prefix}as; ac_word=$2 -{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 -$as_echo_n "checking for $ac_word... " >&6; } -if test "${ac_cv_prog_AS+set}" = set; then : - $as_echo_n "(cached) " >&6 -else - if test -n "$AS"; then - ac_cv_prog_AS="$AS" # Let the user override the test. -else -as_save_IFS=$IFS; IFS=$PATH_SEPARATOR -for as_dir in $PATH -do - IFS=$as_save_IFS - test -z "$as_dir" && as_dir=. - for ac_exec_ext in '' $ac_executable_extensions; do - if { test -f "$as_dir/$ac_word$ac_exec_ext" && $as_test_x "$as_dir/$ac_word$ac_exec_ext"; }; then - ac_cv_prog_AS="${ac_tool_prefix}as" - $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 - break 2 - fi -done - done -IFS=$as_save_IFS - -fi -fi -AS=$ac_cv_prog_AS -if test -n "$AS"; then - { $as_echo "$as_me:${as_lineno-$LINENO}: result: $AS" >&5 -$as_echo "$AS" >&6; } -else - { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 -$as_echo "no" >&6; } -fi - - -fi -if test -z "$ac_cv_prog_AS"; then - ac_ct_AS=$AS - # Extract the first word of "as", so it can be a program name with args. -set dummy as; ac_word=$2 -{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 -$as_echo_n "checking for $ac_word... " >&6; } -if test "${ac_cv_prog_ac_ct_AS+set}" = set; then : - $as_echo_n "(cached) " >&6 -else - if test -n "$ac_ct_AS"; then - ac_cv_prog_ac_ct_AS="$ac_ct_AS" # Let the user override the test. -else -as_save_IFS=$IFS; IFS=$PATH_SEPARATOR -for as_dir in $PATH -do - IFS=$as_save_IFS - test -z "$as_dir" && as_dir=. - for ac_exec_ext in '' $ac_executable_extensions; do - if { test -f "$as_dir/$ac_word$ac_exec_ext" && $as_test_x "$as_dir/$ac_word$ac_exec_ext"; }; then - ac_cv_prog_ac_ct_AS="as" - $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 - break 2 - fi -done - done -IFS=$as_save_IFS - -fi -fi -ac_ct_AS=$ac_cv_prog_ac_ct_AS -if test -n "$ac_ct_AS"; then - { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_ct_AS" >&5 -$as_echo "$ac_ct_AS" >&6; } -else - { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 -$as_echo "no" >&6; } -fi - - if test "x$ac_ct_AS" = x; then - AS="false" - else - case $cross_compiling:$ac_tool_warned in -yes:) -{ $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet" >&5 -$as_echo "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;} -ac_tool_warned=yes ;; -esac - AS=$ac_ct_AS - fi -else - AS="$ac_cv_prog_AS" -fi - - if test -n "$ac_tool_prefix"; then - # Extract the first word of "${ac_tool_prefix}dlltool", so it can be a program name with args. -set dummy ${ac_tool_prefix}dlltool; ac_word=$2 -{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 -$as_echo_n "checking for $ac_word... " >&6; } -if test "${ac_cv_prog_DLLTOOL+set}" = set; then : + if test -n "$ac_tool_prefix"; then + # Extract the first word of "${ac_tool_prefix}dlltool", so it can be a program name with args. +set dummy ${ac_tool_prefix}dlltool; ac_word=$2 +{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +$as_echo_n "checking for $ac_word... " >&6; } +if ${ac_cv_prog_DLLTOOL+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$DLLTOOL"; then @@ -9156,7 +9260,7 @@ do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do - if { test -f "$as_dir/$ac_word$ac_exec_ext" && $as_test_x "$as_dir/$ac_word$ac_exec_ext"; }; then + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_DLLTOOL="${ac_tool_prefix}dlltool" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 @@ -9184,7 +9288,7 @@ if test -z "$ac_cv_prog_DLLTOOL"; then set dummy dlltool; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } -if test "${ac_cv_prog_ac_ct_DLLTOOL+set}" = set; then : +if ${ac_cv_prog_ac_ct_DLLTOOL+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$ac_ct_DLLTOOL"; then @@ -9196,7 +9300,7 @@ do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do - if { test -f "$as_dir/$ac_word$ac_exec_ext" && $as_test_x "$as_dir/$ac_word$ac_exec_ext"; }; then + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_ac_ct_DLLTOOL="dlltool" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 @@ -9236,7 +9340,7 @@ fi set dummy ${ac_tool_prefix}objdump; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } -if test "${ac_cv_prog_OBJDUMP+set}" = set; then : +if ${ac_cv_prog_OBJDUMP+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$OBJDUMP"; then @@ -9248,7 +9352,7 @@ do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do - if { test -f "$as_dir/$ac_word$ac_exec_ext" && $as_test_x "$as_dir/$ac_word$ac_exec_ext"; }; then + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_OBJDUMP="${ac_tool_prefix}objdump" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 @@ -9276,7 +9380,7 @@ if test -z "$ac_cv_prog_OBJDUMP"; then set dummy objdump; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } -if test "${ac_cv_prog_ac_ct_OBJDUMP+set}" = set; then : +if ${ac_cv_prog_ac_ct_OBJDUMP+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$ac_ct_OBJDUMP"; then @@ -9288,7 +9392,7 @@ do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do - if { test -f "$as_dir/$ac_word$ac_exec_ext" && $as_test_x "$as_dir/$ac_word$ac_exec_ext"; }; then + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_ac_ct_OBJDUMP="objdump" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 @@ -9383,7 +9487,22 @@ fi # Check whether --with-pic was given. if test "${with_pic+set}" = set; then : - withval=$with_pic; pic_mode="$withval" + withval=$with_pic; lt_p=${PACKAGE-default} + case $withval in + yes|no) pic_mode=$withval ;; + *) + pic_mode=default + # Look at the argument we got. We use all the common list separators. + lt_save_ifs="$IFS"; IFS="${IFS}$PATH_SEPARATOR," + for lt_pkg in $withval; do + IFS="$lt_save_ifs" + if test "X$lt_pkg" = "X$lt_p"; then + pic_mode=yes + fi + done + IFS="$lt_save_ifs" + ;; + esac else pic_mode=default fi @@ -9454,6 +9573,11 @@ LIBTOOL='$(SHELL) $(top_builddir)/libtool' + + + + + @@ -9481,7 +9605,7 @@ fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking for objdir" >&5 $as_echo_n "checking for objdir... " >&6; } -if test "${lt_cv_objdir+set}" = set; then : +if ${lt_cv_objdir+:} false; then : $as_echo_n "(cached) " >&6 else rm -f .libs 2>/dev/null @@ -9509,19 +9633,6 @@ _ACEOF - - - - - - - - - - - - - case $host_os in aix3*) # AIX sometimes has problems with the GCC collect2 program. For some @@ -9534,23 +9645,6 @@ aix3*) ;; esac -# Sed substitution that helps us do robust quoting. It backslashifies -# metacharacters that are still active within double-quoted strings. -sed_quote_subst='s/\(["`$\\]\)/\\\1/g' - -# Same as above, but do not quote variable references. -double_quote_subst='s/\(["`\\]\)/\\\1/g' - -# Sed substitution to delay expansion of an escaped shell variable in a -# double_quote_subst'ed string. -delay_variable_subst='s/\\\\\\\\\\\$/\\\\\\$/g' - -# Sed substitution to delay expansion of an escaped single quote. -delay_single_quote_subst='s/'\''/'\'\\\\\\\'\''/g' - -# Sed substitution to avoid accidental globbing in evaled expressions -no_glob_subst='s/\*/\\\*/g' - # Global variables: ofile=libtool can_build_shared=yes @@ -9579,7 +9673,7 @@ for cc_temp in $compiler""; do *) break;; esac done -cc_basename=`$ECHO "X$cc_temp" | $Xsed -e 's%.*/%%' -e "s%^$host_alias-%%"` +cc_basename=`$ECHO "$cc_temp" | $SED "s%.*/%%; s%^$host_alias-%%"` # Only perform the check for file, if the check method requires it @@ -9589,7 +9683,7 @@ file_magic*) if test "$file_magic_cmd" = '$MAGIC_CMD'; then { $as_echo "$as_me:${as_lineno-$LINENO}: checking for ${ac_tool_prefix}file" >&5 $as_echo_n "checking for ${ac_tool_prefix}file... " >&6; } -if test "${lt_cv_path_MAGIC_CMD+set}" = set; then : +if ${lt_cv_path_MAGIC_CMD+:} false; then : $as_echo_n "(cached) " >&6 else case $MAGIC_CMD in @@ -9655,7 +9749,7 @@ if test -z "$lt_cv_path_MAGIC_CMD"; then if test -n "$ac_tool_prefix"; then { $as_echo "$as_me:${as_lineno-$LINENO}: checking for file" >&5 $as_echo_n "checking for file... " >&6; } -if test "${lt_cv_path_MAGIC_CMD+set}" = set; then : +if ${lt_cv_path_MAGIC_CMD+:} false; then : $as_echo_n "(cached) " >&6 else case $MAGIC_CMD in @@ -9788,11 +9882,16 @@ if test -n "$compiler"; then lt_prog_compiler_no_builtin_flag= if test "$GCC" = yes; then - lt_prog_compiler_no_builtin_flag=' -fno-builtin' + case $cc_basename in + nvcc*) + lt_prog_compiler_no_builtin_flag=' -Xcompiler -fno-builtin' ;; + *) + lt_prog_compiler_no_builtin_flag=' -fno-builtin' ;; + esac { $as_echo "$as_me:${as_lineno-$LINENO}: checking if $compiler supports -fno-rtti -fno-exceptions" >&5 $as_echo_n "checking if $compiler supports -fno-rtti -fno-exceptions... " >&6; } -if test "${lt_cv_prog_compiler_rtti_exceptions+set}" = set; then : +if ${lt_cv_prog_compiler_rtti_exceptions+:} false; then : $as_echo_n "(cached) " >&6 else lt_cv_prog_compiler_rtti_exceptions=no @@ -9808,15 +9907,15 @@ else -e 's:.*FLAGS}\{0,1\} :&$lt_compiler_flag :; t' \ -e 's: [^ ]*conftest\.: $lt_compiler_flag&:; t' \ -e 's:$: $lt_compiler_flag:'` - (eval echo "\"\$as_me:9811: $lt_compile\"" >&5) + (eval echo "\"\$as_me:$LINENO: $lt_compile\"" >&5) (eval "$lt_compile" 2>conftest.err) ac_status=$? cat conftest.err >&5 - echo "$as_me:9815: \$? = $ac_status" >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 if (exit $ac_status) && test -s "$ac_outfile"; then # The compiler can only warn and ignore the option if not recognized # So say no if there are warnings other than the usual output. - $ECHO "X$_lt_compiler_boilerplate" | $Xsed -e '/^$/d' >conftest.exp + $ECHO "$_lt_compiler_boilerplate" | $SED '/^$/d' >conftest.exp $SED '/^$/d; /^ *+/d' conftest.err >conftest.er2 if test ! -s conftest.er2 || diff conftest.exp conftest.er2 >/dev/null; then lt_cv_prog_compiler_rtti_exceptions=yes @@ -9845,8 +9944,6 @@ fi lt_prog_compiler_pic= lt_prog_compiler_static= -{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $compiler option to produce PIC" >&5 -$as_echo_n "checking for $compiler option to produce PIC... " >&6; } if test "$GCC" = yes; then lt_prog_compiler_wl='-Wl,' @@ -9894,6 +9991,12 @@ $as_echo_n "checking for $compiler option to produce PIC... " >&6; } lt_prog_compiler_pic='-fno-common' ;; + haiku*) + # PIC is the default for Haiku. + # The "-static" flag exists, but is broken. + lt_prog_compiler_static= + ;; + hpux*) # PIC is the default for 64-bit PA HP-UX, but not for 32-bit # PA HP-UX. On IA64 HP-UX, PIC is the default but the pic flag @@ -9936,6 +10039,15 @@ $as_echo_n "checking for $compiler option to produce PIC... " >&6; } lt_prog_compiler_pic='-fPIC' ;; esac + + case $cc_basename in + nvcc*) # Cuda Compiler Driver 2.2 + lt_prog_compiler_wl='-Xlinker ' + if test -n "$lt_prog_compiler_pic"; then + lt_prog_compiler_pic="-Xcompiler $lt_prog_compiler_pic" + fi + ;; + esac else # PORTME Check for flag to pass linker flags through the system compiler. case $host_os in @@ -9977,7 +10089,7 @@ $as_echo_n "checking for $compiler option to produce PIC... " >&6; } lt_prog_compiler_static='-non_shared' ;; - linux* | k*bsd*-gnu | kopensolaris*-gnu) + linux* | k*bsd*-gnu | kopensolaris*-gnu | gnu*) case $cc_basename in # old Intel for x86_64 which still supported -KPIC. ecc*) @@ -9998,7 +10110,13 @@ $as_echo_n "checking for $compiler option to produce PIC... " >&6; } lt_prog_compiler_pic='--shared' lt_prog_compiler_static='--static' ;; - pgcc* | pgf77* | pgf90* | pgf95*) + nagfor*) + # NAG Fortran compiler + lt_prog_compiler_wl='-Wl,-Wl,,' + lt_prog_compiler_pic='-PIC' + lt_prog_compiler_static='-Bstatic' + ;; + pgcc* | pgf77* | pgf90* | pgf95* | pgfortran*) # Portland Group compilers (*not* the Pentium gcc compiler, # which looks to be a dead project) lt_prog_compiler_wl='-Wl,' @@ -10010,25 +10128,40 @@ $as_echo_n "checking for $compiler option to produce PIC... " >&6; } # All Alpha code is PIC. lt_prog_compiler_static='-non_shared' ;; - xl*) - # IBM XL C 8.0/Fortran 10.1 on PPC + xl* | bgxl* | bgf* | mpixl*) + # IBM XL C 8.0/Fortran 10.1, 11.1 on PPC and BlueGene lt_prog_compiler_wl='-Wl,' lt_prog_compiler_pic='-qpic' lt_prog_compiler_static='-qstaticlink' ;; *) case `$CC -V 2>&1 | sed 5q` in + *Sun\ Ceres\ Fortran* | *Sun*Fortran*\ [1-7].* | *Sun*Fortran*\ 8.[0-3]*) + # Sun Fortran 8.3 passes all unrecognized flags to the linker + lt_prog_compiler_pic='-KPIC' + lt_prog_compiler_static='-Bstatic' + lt_prog_compiler_wl='' + ;; + *Sun\ F* | *Sun*Fortran*) + lt_prog_compiler_pic='-KPIC' + lt_prog_compiler_static='-Bstatic' + lt_prog_compiler_wl='-Qoption ld ' + ;; *Sun\ C*) # Sun C 5.9 lt_prog_compiler_pic='-KPIC' lt_prog_compiler_static='-Bstatic' lt_prog_compiler_wl='-Wl,' ;; - *Sun\ F*) - # Sun Fortran 8.3 passes all unrecognized flags to the linker - lt_prog_compiler_pic='-KPIC' + *Intel*\ [CF]*Compiler*) + lt_prog_compiler_wl='-Wl,' + lt_prog_compiler_pic='-fPIC' + lt_prog_compiler_static='-static' + ;; + *Portland\ Group*) + lt_prog_compiler_wl='-Wl,' + lt_prog_compiler_pic='-fpic' lt_prog_compiler_static='-Bstatic' - lt_prog_compiler_wl='' ;; esac ;; @@ -10060,7 +10193,7 @@ $as_echo_n "checking for $compiler option to produce PIC... " >&6; } lt_prog_compiler_pic='-KPIC' lt_prog_compiler_static='-Bstatic' case $cc_basename in - f77* | f90* | f95*) + f77* | f90* | f95* | sunf77* | sunf90* | sunf95*) lt_prog_compiler_wl='-Qoption ld ';; *) lt_prog_compiler_wl='-Wl,';; @@ -10117,13 +10250,17 @@ case $host_os in lt_prog_compiler_pic="$lt_prog_compiler_pic -DPIC" ;; esac -{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $lt_prog_compiler_pic" >&5 -$as_echo "$lt_prog_compiler_pic" >&6; } - - - - +{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $compiler option to produce PIC" >&5 +$as_echo_n "checking for $compiler option to produce PIC... " >&6; } +if ${lt_cv_prog_compiler_pic+:} false; then : + $as_echo_n "(cached) " >&6 +else + lt_cv_prog_compiler_pic=$lt_prog_compiler_pic +fi +{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $lt_cv_prog_compiler_pic" >&5 +$as_echo "$lt_cv_prog_compiler_pic" >&6; } +lt_prog_compiler_pic=$lt_cv_prog_compiler_pic # # Check to make sure the PIC flag actually works. @@ -10131,7 +10268,7 @@ $as_echo "$lt_prog_compiler_pic" >&6; } if test -n "$lt_prog_compiler_pic"; then { $as_echo "$as_me:${as_lineno-$LINENO}: checking if $compiler PIC flag $lt_prog_compiler_pic works" >&5 $as_echo_n "checking if $compiler PIC flag $lt_prog_compiler_pic works... " >&6; } -if test "${lt_cv_prog_compiler_pic_works+set}" = set; then : +if ${lt_cv_prog_compiler_pic_works+:} false; then : $as_echo_n "(cached) " >&6 else lt_cv_prog_compiler_pic_works=no @@ -10147,15 +10284,15 @@ else -e 's:.*FLAGS}\{0,1\} :&$lt_compiler_flag :; t' \ -e 's: [^ ]*conftest\.: $lt_compiler_flag&:; t' \ -e 's:$: $lt_compiler_flag:'` - (eval echo "\"\$as_me:10150: $lt_compile\"" >&5) + (eval echo "\"\$as_me:$LINENO: $lt_compile\"" >&5) (eval "$lt_compile" 2>conftest.err) ac_status=$? cat conftest.err >&5 - echo "$as_me:10154: \$? = $ac_status" >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 if (exit $ac_status) && test -s "$ac_outfile"; then # The compiler can only warn and ignore the option if not recognized # So say no if there are warnings other than the usual output. - $ECHO "X$_lt_compiler_boilerplate" | $Xsed -e '/^$/d' >conftest.exp + $ECHO "$_lt_compiler_boilerplate" | $SED '/^$/d' >conftest.exp $SED '/^$/d; /^ *+/d' conftest.err >conftest.er2 if test ! -s conftest.er2 || diff conftest.exp conftest.er2 >/dev/null; then lt_cv_prog_compiler_pic_works=yes @@ -10184,13 +10321,18 @@ fi + + + + + # # Check to make sure the static flag actually works. # wl=$lt_prog_compiler_wl eval lt_tmp_static_flag=\"$lt_prog_compiler_static\" { $as_echo "$as_me:${as_lineno-$LINENO}: checking if $compiler static flag $lt_tmp_static_flag works" >&5 $as_echo_n "checking if $compiler static flag $lt_tmp_static_flag works... " >&6; } -if test "${lt_cv_prog_compiler_static_works+set}" = set; then : +if ${lt_cv_prog_compiler_static_works+:} false; then : $as_echo_n "(cached) " >&6 else lt_cv_prog_compiler_static_works=no @@ -10203,7 +10345,7 @@ else if test -s conftest.err; then # Append any errors to the config.log. cat conftest.err 1>&5 - $ECHO "X$_lt_linker_boilerplate" | $Xsed -e '/^$/d' > conftest.exp + $ECHO "$_lt_linker_boilerplate" | $SED '/^$/d' > conftest.exp $SED '/^$/d; /^ *+/d' conftest.err >conftest.er2 if diff conftest.exp conftest.er2 >/dev/null; then lt_cv_prog_compiler_static_works=yes @@ -10233,7 +10375,7 @@ fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking if $compiler supports -c -o file.$ac_objext" >&5 $as_echo_n "checking if $compiler supports -c -o file.$ac_objext... " >&6; } -if test "${lt_cv_prog_compiler_c_o+set}" = set; then : +if ${lt_cv_prog_compiler_c_o+:} false; then : $as_echo_n "(cached) " >&6 else lt_cv_prog_compiler_c_o=no @@ -10252,16 +10394,16 @@ else -e 's:.*FLAGS}\{0,1\} :&$lt_compiler_flag :; t' \ -e 's: [^ ]*conftest\.: $lt_compiler_flag&:; t' \ -e 's:$: $lt_compiler_flag:'` - (eval echo "\"\$as_me:10255: $lt_compile\"" >&5) + (eval echo "\"\$as_me:$LINENO: $lt_compile\"" >&5) (eval "$lt_compile" 2>out/conftest.err) ac_status=$? cat out/conftest.err >&5 - echo "$as_me:10259: \$? = $ac_status" >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 if (exit $ac_status) && test -s out/conftest2.$ac_objext then # The compiler can only warn and ignore the option if not recognized # So say no if there are warnings - $ECHO "X$_lt_compiler_boilerplate" | $Xsed -e '/^$/d' > out/conftest.exp + $ECHO "$_lt_compiler_boilerplate" | $SED '/^$/d' > out/conftest.exp $SED '/^$/d; /^ *+/d' out/conftest.err >out/conftest.er2 if test ! -s out/conftest.er2 || diff out/conftest.exp out/conftest.er2 >/dev/null; then lt_cv_prog_compiler_c_o=yes @@ -10288,7 +10430,7 @@ $as_echo "$lt_cv_prog_compiler_c_o" >&6; } { $as_echo "$as_me:${as_lineno-$LINENO}: checking if $compiler supports -c -o file.$ac_objext" >&5 $as_echo_n "checking if $compiler supports -c -o file.$ac_objext... " >&6; } -if test "${lt_cv_prog_compiler_c_o+set}" = set; then : +if ${lt_cv_prog_compiler_c_o+:} false; then : $as_echo_n "(cached) " >&6 else lt_cv_prog_compiler_c_o=no @@ -10307,16 +10449,16 @@ else -e 's:.*FLAGS}\{0,1\} :&$lt_compiler_flag :; t' \ -e 's: [^ ]*conftest\.: $lt_compiler_flag&:; t' \ -e 's:$: $lt_compiler_flag:'` - (eval echo "\"\$as_me:10310: $lt_compile\"" >&5) + (eval echo "\"\$as_me:$LINENO: $lt_compile\"" >&5) (eval "$lt_compile" 2>out/conftest.err) ac_status=$? cat out/conftest.err >&5 - echo "$as_me:10314: \$? = $ac_status" >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 if (exit $ac_status) && test -s out/conftest2.$ac_objext then # The compiler can only warn and ignore the option if not recognized # So say no if there are warnings - $ECHO "X$_lt_compiler_boilerplate" | $Xsed -e '/^$/d' > out/conftest.exp + $ECHO "$_lt_compiler_boilerplate" | $SED '/^$/d' > out/conftest.exp $SED '/^$/d; /^ *+/d' out/conftest.err >out/conftest.er2 if test ! -s out/conftest.er2 || diff out/conftest.exp out/conftest.er2 >/dev/null; then lt_cv_prog_compiler_c_o=yes @@ -10382,7 +10524,6 @@ $as_echo_n "checking whether the $compiler linker ($LD) supports shared librarie hardcode_direct=no hardcode_direct_absolute=no hardcode_libdir_flag_spec= - hardcode_libdir_flag_spec_ld= hardcode_libdir_separator= hardcode_minus_L=no hardcode_shlibpath_var=unsupported @@ -10426,13 +10567,39 @@ $as_echo_n "checking whether the $compiler linker ($LD) supports shared librarie openbsd*) with_gnu_ld=no ;; - linux* | k*bsd*-gnu) + linux* | k*bsd*-gnu | gnu*) link_all_deplibs=no ;; esac ld_shlibs=yes + + # On some targets, GNU ld is compatible enough with the native linker + # that we're better off using the native interface for both. + lt_use_gnu_ld_interface=no if test "$with_gnu_ld" = yes; then + case $host_os in + aix*) + # The AIX port of GNU ld has always aspired to compatibility + # with the native linker. However, as the warning in the GNU ld + # block says, versions before 2.19.5* couldn't really create working + # shared libraries, regardless of the interface used. + case `$LD -v 2>&1` in + *\ \(GNU\ Binutils\)\ 2.19.5*) ;; + *\ \(GNU\ Binutils\)\ 2.[2-9]*) ;; + *\ \(GNU\ Binutils\)\ [3-9]*) ;; + *) + lt_use_gnu_ld_interface=yes + ;; + esac + ;; + *) + lt_use_gnu_ld_interface=yes + ;; + esac + fi + + if test "$lt_use_gnu_ld_interface" = yes; then # If archive_cmds runs LD, not CC, wlarc should be empty wlarc='${wl}' @@ -10466,11 +10633,12 @@ $as_echo_n "checking whether the $compiler linker ($LD) supports shared librarie ld_shlibs=no cat <<_LT_EOF 1>&2 -*** Warning: the GNU linker, at least up to release 2.9.1, is reported +*** Warning: the GNU linker, at least up to release 2.19, is reported *** to be unable to reliably create shared libraries on AIX. *** Therefore, libtool is disabling shared libraries support. If you -*** really care for shared libraries, you may want to modify your PATH -*** so that a non-GNU linker is found, and then restart. +*** really care for shared libraries, you may want to install binutils +*** 2.20 or above, or modify your PATH so that a non-GNU linker is found. +*** You will then need to restart the configuration process. _LT_EOF fi @@ -10506,10 +10674,12 @@ _LT_EOF # _LT_TAGVAR(hardcode_libdir_flag_spec, ) is actually meaningless, # as there is no search path for DLLs. hardcode_libdir_flag_spec='-L$libdir' + export_dynamic_flag_spec='${wl}--export-all-symbols' allow_undefined_flag=unsupported always_export_symbols=no enable_shared_with_static_runtimes=yes - export_symbols_cmds='$NM $libobjs $convenience | $global_symbol_pipe | $SED -e '\''/^[BCDGRS][ ]/s/.*[ ]\([^ ]*\)/\1 DATA/'\'' | $SED -e '\''/^[AITW][ ]/s/.*[ ]//'\'' | sort | uniq > $export_symbols' + export_symbols_cmds='$NM $libobjs $convenience | $global_symbol_pipe | $SED -e '\''/^[BCDGRS][ ]/s/.*[ ]\([^ ]*\)/\1 DATA/;s/^.*[ ]__nm__\([^ ]*\)[ ][^ ]*/\1 DATA/;/^I[ ]/d;/^[AITW][ ]/s/.* //'\'' | sort | uniq > $export_symbols' + exclude_expsyms='[_]+GLOBAL_OFFSET_TABLE_|[_]+GLOBAL__[FID]_.*|[_]+head_[A-Za-z0-9_]+_dll|[A-Za-z0-9_]+_dll_iname' if $LD --help 2>&1 | $GREP 'auto-import' > /dev/null; then archive_cmds='$CC -shared $libobjs $deplibs $compiler_flags -o $output_objdir/$soname ${wl}--enable-auto-image-base -Xlinker --out-implib -Xlinker $lib' @@ -10527,6 +10697,11 @@ _LT_EOF fi ;; + haiku*) + archive_cmds='$CC -shared $libobjs $deplibs $compiler_flags ${wl}-soname $wl$soname -o $lib' + link_all_deplibs=yes + ;; + interix[3-9]*) hardcode_direct=no hardcode_shlibpath_var=no @@ -10552,15 +10727,16 @@ _LT_EOF if $LD --help 2>&1 | $EGREP ': supported targets:.* elf' > /dev/null \ && test "$tmp_diet" = no then - tmp_addflag= + tmp_addflag=' $pic_flag' tmp_sharedflag='-shared' case $cc_basename,$host_cpu in pgcc*) # Portland Group C compiler - whole_archive_flag_spec='${wl}--whole-archive`for conv in $convenience\"\"; do test -n \"$conv\" && new_convenience=\"$new_convenience,$conv\"; done; $ECHO \"$new_convenience\"` ${wl}--no-whole-archive' + whole_archive_flag_spec='${wl}--whole-archive`for conv in $convenience\"\"; do test -n \"$conv\" && new_convenience=\"$new_convenience,$conv\"; done; func_echo_all \"$new_convenience\"` ${wl}--no-whole-archive' tmp_addflag=' $pic_flag' ;; - pgf77* | pgf90* | pgf95*) # Portland Group f77 and f90 compilers - whole_archive_flag_spec='${wl}--whole-archive`for conv in $convenience\"\"; do test -n \"$conv\" && new_convenience=\"$new_convenience,$conv\"; done; $ECHO \"$new_convenience\"` ${wl}--no-whole-archive' + pgf77* | pgf90* | pgf95* | pgfortran*) + # Portland Group f77 and f90 compilers + whole_archive_flag_spec='${wl}--whole-archive`for conv in $convenience\"\"; do test -n \"$conv\" && new_convenience=\"$new_convenience,$conv\"; done; func_echo_all \"$new_convenience\"` ${wl}--no-whole-archive' tmp_addflag=' $pic_flag -Mnomain' ;; ecc*,ia64* | icc*,ia64*) # Intel C compiler on ia64 tmp_addflag=' -i_dynamic' ;; @@ -10571,13 +10747,17 @@ _LT_EOF lf95*) # Lahey Fortran 8.1 whole_archive_flag_spec= tmp_sharedflag='--shared' ;; - xl[cC]*) # IBM XL C 8.0 on PPC (deal with xlf below) + xl[cC]* | bgxl[cC]* | mpixl[cC]*) # IBM XL C 8.0 on PPC (deal with xlf below) tmp_sharedflag='-qmkshrobj' tmp_addflag= ;; + nvcc*) # Cuda Compiler Driver 2.2 + whole_archive_flag_spec='${wl}--whole-archive`for conv in $convenience\"\"; do test -n \"$conv\" && new_convenience=\"$new_convenience,$conv\"; done; func_echo_all \"$new_convenience\"` ${wl}--no-whole-archive' + compiler_needs_object=yes + ;; esac case `$CC -V 2>&1 | sed 5q` in *Sun\ C*) # Sun C 5.9 - whole_archive_flag_spec='${wl}--whole-archive`new_convenience=; for conv in $convenience\"\"; do test -z \"$conv\" || new_convenience=\"$new_convenience,$conv\"; done; $ECHO \"$new_convenience\"` ${wl}--no-whole-archive' + whole_archive_flag_spec='${wl}--whole-archive`new_convenience=; for conv in $convenience\"\"; do test -z \"$conv\" || new_convenience=\"$new_convenience,$conv\"; done; func_echo_all \"$new_convenience\"` ${wl}--no-whole-archive' compiler_needs_object=yes tmp_sharedflag='-G' ;; *Sun\ F*) # Sun Fortran 8.3 @@ -10593,17 +10773,16 @@ _LT_EOF fi case $cc_basename in - xlf*) + xlf* | bgf* | bgxlf* | mpixlf*) # IBM XL Fortran 10.1 on PPC cannot create shared libs itself whole_archive_flag_spec='--whole-archive$convenience --no-whole-archive' - hardcode_libdir_flag_spec= - hardcode_libdir_flag_spec_ld='-rpath $libdir' - archive_cmds='$LD -shared $libobjs $deplibs $compiler_flags -soname $soname -o $lib' + hardcode_libdir_flag_spec='${wl}-rpath ${wl}$libdir' + archive_cmds='$LD -shared $libobjs $deplibs $linker_flags -soname $soname -o $lib' if test "x$supports_anon_versioning" = xyes; then archive_expsym_cmds='echo "{ global:" > $output_objdir/$libname.ver~ cat $export_symbols | sed -e "s/\(.*\)/\1;/" >> $output_objdir/$libname.ver~ echo "local: *; };" >> $output_objdir/$libname.ver~ - $LD -shared $libobjs $deplibs $compiler_flags -soname $soname -version-script $output_objdir/$libname.ver -o $lib' + $LD -shared $libobjs $deplibs $linker_flags -soname $soname -version-script $output_objdir/$libname.ver -o $lib' fi ;; esac @@ -10617,8 +10796,8 @@ _LT_EOF archive_cmds='$LD -Bshareable $libobjs $deplibs $linker_flags -o $lib' wlarc= else - archive_cmds='$CC -shared $libobjs $deplibs $compiler_flags ${wl}-soname $wl$soname -o $lib' - archive_expsym_cmds='$CC -shared $libobjs $deplibs $compiler_flags ${wl}-soname $wl$soname ${wl}-retain-symbols-file $wl$export_symbols -o $lib' + archive_cmds='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags ${wl}-soname $wl$soname -o $lib' + archive_expsym_cmds='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags ${wl}-soname $wl$soname ${wl}-retain-symbols-file $wl$export_symbols -o $lib' fi ;; @@ -10636,8 +10815,8 @@ _LT_EOF _LT_EOF elif $LD --help 2>&1 | $GREP ': supported targets:.* elf' > /dev/null; then - archive_cmds='$CC -shared $libobjs $deplibs $compiler_flags ${wl}-soname $wl$soname -o $lib' - archive_expsym_cmds='$CC -shared $libobjs $deplibs $compiler_flags ${wl}-soname $wl$soname ${wl}-retain-symbols-file $wl$export_symbols -o $lib' + archive_cmds='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags ${wl}-soname $wl$soname -o $lib' + archive_expsym_cmds='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags ${wl}-soname $wl$soname ${wl}-retain-symbols-file $wl$export_symbols -o $lib' else ld_shlibs=no fi @@ -10683,8 +10862,8 @@ _LT_EOF *) if $LD --help 2>&1 | $GREP ': supported targets:.* elf' > /dev/null; then - archive_cmds='$CC -shared $libobjs $deplibs $compiler_flags ${wl}-soname $wl$soname -o $lib' - archive_expsym_cmds='$CC -shared $libobjs $deplibs $compiler_flags ${wl}-soname $wl$soname ${wl}-retain-symbols-file $wl$export_symbols -o $lib' + archive_cmds='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags ${wl}-soname $wl$soname -o $lib' + archive_expsym_cmds='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags ${wl}-soname $wl$soname ${wl}-retain-symbols-file $wl$export_symbols -o $lib' else ld_shlibs=no fi @@ -10724,8 +10903,10 @@ _LT_EOF else # If we're using GNU nm, then we don't want the "-C" option. # -C means demangle to AIX nm, but means don't demangle with GNU nm + # Also, AIX nm treats weak defined symbols like other global + # defined symbols, whereas GNU nm marks them as "W". if $NM -V 2>&1 | $GREP 'GNU' > /dev/null; then - export_symbols_cmds='$NM -Bpg $libobjs $convenience | awk '\''{ if (((\$ 2 == "T") || (\$ 2 == "D") || (\$ 2 == "B")) && (substr(\$ 3,1,1) != ".")) { print \$ 3 } }'\'' | sort -u > $export_symbols' + export_symbols_cmds='$NM -Bpg $libobjs $convenience | awk '\''{ if (((\$ 2 == "T") || (\$ 2 == "D") || (\$ 2 == "B") || (\$ 2 == "W")) && (substr(\$ 3,1,1) != ".")) { print \$ 3 } }'\'' | sort -u > $export_symbols' else export_symbols_cmds='$NM -BCpg $libobjs $convenience | awk '\''{ if (((\$ 2 == "T") || (\$ 2 == "D") || (\$ 2 == "B")) && (substr(\$ 3,1,1) != ".")) { print \$ 3 } }'\'' | sort -u > $export_symbols' fi @@ -10813,7 +10994,13 @@ _LT_EOF allow_undefined_flag='-berok' # Determine the default libpath from the value encoded in an # empty executable. - cat confdefs.h - <<_ACEOF >conftest.$ac_ext + if test "${lt_cv_aix_libpath+set}" = set; then + aix_libpath=$lt_cv_aix_libpath +else + if ${lt_cv_aix_libpath_+:} false; then : + $as_echo_n "(cached) " >&6 +else + cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ int @@ -10826,25 +11013,32 @@ main () _ACEOF if ac_fn_c_try_link "$LINENO"; then : -lt_aix_libpath_sed=' - /Import File Strings/,/^$/ { - /^0/ { - s/^0 *\(.*\)$/\1/ - p - } - }' -aix_libpath=`dump -H conftest$ac_exeext 2>/dev/null | $SED -n -e "$lt_aix_libpath_sed"` -# Check for a 64-bit object if we didn't find anything. -if test -z "$aix_libpath"; then - aix_libpath=`dump -HX64 conftest$ac_exeext 2>/dev/null | $SED -n -e "$lt_aix_libpath_sed"` -fi + lt_aix_libpath_sed=' + /Import File Strings/,/^$/ { + /^0/ { + s/^0 *\([^ ]*\) *$/\1/ + p + } + }' + lt_cv_aix_libpath_=`dump -H conftest$ac_exeext 2>/dev/null | $SED -n -e "$lt_aix_libpath_sed"` + # Check for a 64-bit object if we didn't find anything. + if test -z "$lt_cv_aix_libpath_"; then + lt_cv_aix_libpath_=`dump -HX64 conftest$ac_exeext 2>/dev/null | $SED -n -e "$lt_aix_libpath_sed"` + fi fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext -if test -z "$aix_libpath"; then aix_libpath="/usr/lib:/lib"; fi + if test -z "$lt_cv_aix_libpath_"; then + lt_cv_aix_libpath_="/usr/lib:/lib" + fi + +fi + + aix_libpath=$lt_cv_aix_libpath_ +fi hardcode_libdir_flag_spec='${wl}-blibpath:$libdir:'"$aix_libpath" - archive_expsym_cmds='$CC -o $output_objdir/$soname $libobjs $deplibs '"\${wl}$no_entry_flag"' $compiler_flags `if test "x${allow_undefined_flag}" != "x"; then $ECHO "X${wl}${allow_undefined_flag}" | $Xsed; else :; fi` '"\${wl}$exp_sym_flag:\$export_symbols $shared_flag" + archive_expsym_cmds='$CC -o $output_objdir/$soname $libobjs $deplibs '"\${wl}$no_entry_flag"' $compiler_flags `if test "x${allow_undefined_flag}" != "x"; then func_echo_all "${wl}${allow_undefined_flag}"; else :; fi` '"\${wl}$exp_sym_flag:\$export_symbols $shared_flag" else if test "$host_cpu" = ia64; then hardcode_libdir_flag_spec='${wl}-R $libdir:/usr/lib:/lib' @@ -10853,7 +11047,13 @@ if test -z "$aix_libpath"; then aix_libpath="/usr/lib:/lib"; fi else # Determine the default libpath from the value encoded in an # empty executable. - cat confdefs.h - <<_ACEOF >conftest.$ac_ext + if test "${lt_cv_aix_libpath+set}" = set; then + aix_libpath=$lt_cv_aix_libpath +else + if ${lt_cv_aix_libpath_+:} false; then : + $as_echo_n "(cached) " >&6 +else + cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ int @@ -10866,30 +11066,42 @@ main () _ACEOF if ac_fn_c_try_link "$LINENO"; then : -lt_aix_libpath_sed=' - /Import File Strings/,/^$/ { - /^0/ { - s/^0 *\(.*\)$/\1/ - p - } - }' -aix_libpath=`dump -H conftest$ac_exeext 2>/dev/null | $SED -n -e "$lt_aix_libpath_sed"` -# Check for a 64-bit object if we didn't find anything. -if test -z "$aix_libpath"; then - aix_libpath=`dump -HX64 conftest$ac_exeext 2>/dev/null | $SED -n -e "$lt_aix_libpath_sed"` -fi + lt_aix_libpath_sed=' + /Import File Strings/,/^$/ { + /^0/ { + s/^0 *\([^ ]*\) *$/\1/ + p + } + }' + lt_cv_aix_libpath_=`dump -H conftest$ac_exeext 2>/dev/null | $SED -n -e "$lt_aix_libpath_sed"` + # Check for a 64-bit object if we didn't find anything. + if test -z "$lt_cv_aix_libpath_"; then + lt_cv_aix_libpath_=`dump -HX64 conftest$ac_exeext 2>/dev/null | $SED -n -e "$lt_aix_libpath_sed"` + fi fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext -if test -z "$aix_libpath"; then aix_libpath="/usr/lib:/lib"; fi + if test -z "$lt_cv_aix_libpath_"; then + lt_cv_aix_libpath_="/usr/lib:/lib" + fi + +fi + + aix_libpath=$lt_cv_aix_libpath_ +fi hardcode_libdir_flag_spec='${wl}-blibpath:$libdir:'"$aix_libpath" # Warning - without using the other run time loading flags, # -berok will link without error, but may produce a broken library. no_undefined_flag=' ${wl}-bernotok' allow_undefined_flag=' ${wl}-berok' - # Exported symbols can be pulled into shared objects from archives - whole_archive_flag_spec='$convenience' + if test "$with_gnu_ld" = yes; then + # We only use this code for GNU lds that support --whole-archive. + whole_archive_flag_spec='${wl}--whole-archive$convenience ${wl}--no-whole-archive' + else + # Exported symbols can be pulled into shared objects from archives + whole_archive_flag_spec='$convenience' + fi archive_cmds_need_lc=yes # This is similar to how AIX traditionally builds its shared libraries. archive_expsym_cmds="\$CC $shared_flag"' -o $output_objdir/$soname $libobjs $deplibs ${wl}-bnoentry $compiler_flags ${wl}-bE:$export_symbols${allow_undefined_flag}~$AR $AR_FLAGS $output_objdir/$libname$release.a $output_objdir/$soname' @@ -10921,20 +11133,64 @@ if test -z "$aix_libpath"; then aix_libpath="/usr/lib:/lib"; fi # Microsoft Visual C++. # hardcode_libdir_flag_spec is actually meaningless, as there is # no search path for DLLs. - hardcode_libdir_flag_spec=' ' - allow_undefined_flag=unsupported - # Tell ltmain to make .lib files, not .a files. - libext=lib - # Tell ltmain to make .dll files, not .so files. - shrext_cmds=".dll" - # FIXME: Setting linknames here is a bad hack. - archive_cmds='$CC -o $lib $libobjs $compiler_flags `$ECHO "X$deplibs" | $Xsed -e '\''s/ -lc$//'\''` -link -dll~linknames=' - # The linker will automatically build a .lib file if we build a DLL. - old_archive_from_new_cmds='true' - # FIXME: Should let the user specify the lib program. - old_archive_cmds='lib -OUT:$oldlib$oldobjs$old_deplibs' - fix_srcfile_path='`cygpath -w "$srcfile"`' - enable_shared_with_static_runtimes=yes + case $cc_basename in + cl*) + # Native MSVC + hardcode_libdir_flag_spec=' ' + allow_undefined_flag=unsupported + always_export_symbols=yes + file_list_spec='@' + # Tell ltmain to make .lib files, not .a files. + libext=lib + # Tell ltmain to make .dll files, not .so files. + shrext_cmds=".dll" + # FIXME: Setting linknames here is a bad hack. + archive_cmds='$CC -o $output_objdir/$soname $libobjs $compiler_flags $deplibs -Wl,-dll~linknames=' + archive_expsym_cmds='if test "x`$SED 1q $export_symbols`" = xEXPORTS; then + sed -n -e 's/\\\\\\\(.*\\\\\\\)/-link\\\ -EXPORT:\\\\\\\1/' -e '1\\\!p' < $export_symbols > $output_objdir/$soname.exp; + else + sed -e 's/\\\\\\\(.*\\\\\\\)/-link\\\ -EXPORT:\\\\\\\1/' < $export_symbols > $output_objdir/$soname.exp; + fi~ + $CC -o $tool_output_objdir$soname $libobjs $compiler_flags $deplibs "@$tool_output_objdir$soname.exp" -Wl,-DLL,-IMPLIB:"$tool_output_objdir$libname.dll.lib"~ + linknames=' + # The linker will not automatically build a static lib if we build a DLL. + # _LT_TAGVAR(old_archive_from_new_cmds, )='true' + enable_shared_with_static_runtimes=yes + exclude_expsyms='_NULL_IMPORT_DESCRIPTOR|_IMPORT_DESCRIPTOR_.*' + export_symbols_cmds='$NM $libobjs $convenience | $global_symbol_pipe | $SED -e '\''/^[BCDGRS][ ]/s/.*[ ]\([^ ]*\)/\1,DATA/'\'' | $SED -e '\''/^[AITW][ ]/s/.*[ ]//'\'' | sort | uniq > $export_symbols' + # Don't use ranlib + old_postinstall_cmds='chmod 644 $oldlib' + postlink_cmds='lt_outputfile="@OUTPUT@"~ + lt_tool_outputfile="@TOOL_OUTPUT@"~ + case $lt_outputfile in + *.exe|*.EXE) ;; + *) + lt_outputfile="$lt_outputfile.exe" + lt_tool_outputfile="$lt_tool_outputfile.exe" + ;; + esac~ + if test "$MANIFEST_TOOL" != ":" && test -f "$lt_outputfile.manifest"; then + $MANIFEST_TOOL -manifest "$lt_tool_outputfile.manifest" -outputresource:"$lt_tool_outputfile" || exit 1; + $RM "$lt_outputfile.manifest"; + fi' + ;; + *) + # Assume MSVC wrapper + hardcode_libdir_flag_spec=' ' + allow_undefined_flag=unsupported + # Tell ltmain to make .lib files, not .a files. + libext=lib + # Tell ltmain to make .dll files, not .so files. + shrext_cmds=".dll" + # FIXME: Setting linknames here is a bad hack. + archive_cmds='$CC -o $lib $libobjs $compiler_flags `func_echo_all "$deplibs" | $SED '\''s/ -lc$//'\''` -link -dll~linknames=' + # The linker will automatically build a .lib file if we build a DLL. + old_archive_from_new_cmds='true' + # FIXME: Should let the user specify the lib program. + old_archive_cmds='lib -OUT:$oldlib$oldobjs$old_deplibs' + enable_shared_with_static_runtimes=yes + ;; + esac ;; darwin* | rhapsody*) @@ -10944,7 +11200,12 @@ if test -z "$aix_libpath"; then aix_libpath="/usr/lib:/lib"; fi hardcode_direct=no hardcode_automatic=yes hardcode_shlibpath_var=unsupported - whole_archive_flag_spec='' + if test "$lt_cv_ld_force_load" = "yes"; then + whole_archive_flag_spec='`for conv in $convenience\"\"; do test -n \"$conv\" && new_convenience=\"$new_convenience ${wl}-force_load,$conv\"; done; func_echo_all \"$new_convenience\"`' + + else + whole_archive_flag_spec='' + fi link_all_deplibs=yes allow_undefined_flag="$_lt_dar_allow_undefined" case $cc_basename in @@ -10952,7 +11213,7 @@ if test -z "$aix_libpath"; then aix_libpath="/usr/lib:/lib"; fi *) _lt_dar_can_shared=$GCC ;; esac if test "$_lt_dar_can_shared" = "yes"; then - output_verbose_link_cmd=echo + output_verbose_link_cmd=func_echo_all archive_cmds="\$CC -dynamiclib \$allow_undefined_flag -o \$lib \$libobjs \$deplibs \$compiler_flags -install_name \$rpath/\$soname \$verstring $_lt_dar_single_mod${_lt_dsymutil}" module_cmds="\$CC \$allow_undefined_flag -o \$lib -bundle \$libobjs \$deplibs \$compiler_flags${_lt_dsymutil}" archive_expsym_cmds="sed 's,^,_,' < \$export_symbols > \$output_objdir/\${libname}-symbols.expsym~\$CC -dynamiclib \$allow_undefined_flag -o \$lib \$libobjs \$deplibs \$compiler_flags -install_name \$rpath/\$soname \$verstring ${_lt_dar_single_mod}${_lt_dar_export_syms}${_lt_dsymutil}" @@ -10970,10 +11231,6 @@ if test -z "$aix_libpath"; then aix_libpath="/usr/lib:/lib"; fi hardcode_shlibpath_var=no ;; - freebsd1*) - ld_shlibs=no - ;; - # FreeBSD 2.2.[012] allows us to include c++rt0.o to get C++ constructor # support. Future versions do this automatically, but an explicit c++rt0.o # does not break anything, and helps significantly (at the cost of a little @@ -10986,7 +11243,7 @@ if test -z "$aix_libpath"; then aix_libpath="/usr/lib:/lib"; fi ;; # Unfortunately, older versions of FreeBSD 2 do not have this feature. - freebsd2*) + freebsd2.*) archive_cmds='$LD -Bshareable -o $lib $libobjs $deplibs $linker_flags' hardcode_direct=yes hardcode_minus_L=yes @@ -10995,7 +11252,7 @@ if test -z "$aix_libpath"; then aix_libpath="/usr/lib:/lib"; fi # FreeBSD 3 and greater uses gcc -shared to do shared libraries. freebsd* | dragonfly*) - archive_cmds='$CC -shared -o $lib $libobjs $deplibs $compiler_flags' + archive_cmds='$CC -shared $pic_flag -o $lib $libobjs $deplibs $compiler_flags' hardcode_libdir_flag_spec='-R$libdir' hardcode_direct=yes hardcode_shlibpath_var=no @@ -11003,7 +11260,7 @@ if test -z "$aix_libpath"; then aix_libpath="/usr/lib:/lib"; fi hpux9*) if test "$GCC" = yes; then - archive_cmds='$RM $output_objdir/$soname~$CC -shared -fPIC ${wl}+b ${wl}$install_libdir -o $output_objdir/$soname $libobjs $deplibs $compiler_flags~test $output_objdir/$soname = $lib || mv $output_objdir/$soname $lib' + archive_cmds='$RM $output_objdir/$soname~$CC -shared $pic_flag ${wl}+b ${wl}$install_libdir -o $output_objdir/$soname $libobjs $deplibs $compiler_flags~test $output_objdir/$soname = $lib || mv $output_objdir/$soname $lib' else archive_cmds='$RM $output_objdir/$soname~$LD -b +b $install_libdir -o $output_objdir/$soname $libobjs $deplibs $linker_flags~test $output_objdir/$soname = $lib || mv $output_objdir/$soname $lib' fi @@ -11018,14 +11275,13 @@ if test -z "$aix_libpath"; then aix_libpath="/usr/lib:/lib"; fi ;; hpux10*) - if test "$GCC" = yes -a "$with_gnu_ld" = no; then - archive_cmds='$CC -shared -fPIC ${wl}+h ${wl}$soname ${wl}+b ${wl}$install_libdir -o $lib $libobjs $deplibs $compiler_flags' + if test "$GCC" = yes && test "$with_gnu_ld" = no; then + archive_cmds='$CC -shared $pic_flag ${wl}+h ${wl}$soname ${wl}+b ${wl}$install_libdir -o $lib $libobjs $deplibs $compiler_flags' else archive_cmds='$LD -b +h $soname +b $install_libdir -o $lib $libobjs $deplibs $linker_flags' fi if test "$with_gnu_ld" = no; then hardcode_libdir_flag_spec='${wl}+b ${wl}$libdir' - hardcode_libdir_flag_spec_ld='+b $libdir' hardcode_libdir_separator=: hardcode_direct=yes hardcode_direct_absolute=yes @@ -11037,16 +11293,16 @@ if test -z "$aix_libpath"; then aix_libpath="/usr/lib:/lib"; fi ;; hpux11*) - if test "$GCC" = yes -a "$with_gnu_ld" = no; then + if test "$GCC" = yes && test "$with_gnu_ld" = no; then case $host_cpu in hppa*64*) archive_cmds='$CC -shared ${wl}+h ${wl}$soname -o $lib $libobjs $deplibs $compiler_flags' ;; ia64*) - archive_cmds='$CC -shared -fPIC ${wl}+h ${wl}$soname ${wl}+nodefaultrpath -o $lib $libobjs $deplibs $compiler_flags' + archive_cmds='$CC -shared $pic_flag ${wl}+h ${wl}$soname ${wl}+nodefaultrpath -o $lib $libobjs $deplibs $compiler_flags' ;; *) - archive_cmds='$CC -shared -fPIC ${wl}+h ${wl}$soname ${wl}+b ${wl}$install_libdir -o $lib $libobjs $deplibs $compiler_flags' + archive_cmds='$CC -shared $pic_flag ${wl}+h ${wl}$soname ${wl}+b ${wl}$install_libdir -o $lib $libobjs $deplibs $compiler_flags' ;; esac else @@ -11058,7 +11314,46 @@ if test -z "$aix_libpath"; then aix_libpath="/usr/lib:/lib"; fi archive_cmds='$CC -b ${wl}+h ${wl}$soname ${wl}+nodefaultrpath -o $lib $libobjs $deplibs $compiler_flags' ;; *) - archive_cmds='$CC -b ${wl}+h ${wl}$soname ${wl}+b ${wl}$install_libdir -o $lib $libobjs $deplibs $compiler_flags' + + # Older versions of the 11.00 compiler do not understand -b yet + # (HP92453-01 A.11.01.20 doesn't, HP92453-01 B.11.X.35175-35176.GP does) + { $as_echo "$as_me:${as_lineno-$LINENO}: checking if $CC understands -b" >&5 +$as_echo_n "checking if $CC understands -b... " >&6; } +if ${lt_cv_prog_compiler__b+:} false; then : + $as_echo_n "(cached) " >&6 +else + lt_cv_prog_compiler__b=no + save_LDFLAGS="$LDFLAGS" + LDFLAGS="$LDFLAGS -b" + echo "$lt_simple_link_test_code" > conftest.$ac_ext + if (eval $ac_link 2>conftest.err) && test -s conftest$ac_exeext; then + # The linker can only warn and ignore the option if not recognized + # So say no if there are warnings + if test -s conftest.err; then + # Append any errors to the config.log. + cat conftest.err 1>&5 + $ECHO "$_lt_linker_boilerplate" | $SED '/^$/d' > conftest.exp + $SED '/^$/d; /^ *+/d' conftest.err >conftest.er2 + if diff conftest.exp conftest.er2 >/dev/null; then + lt_cv_prog_compiler__b=yes + fi + else + lt_cv_prog_compiler__b=yes + fi + fi + $RM -r conftest* + LDFLAGS="$save_LDFLAGS" + +fi +{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $lt_cv_prog_compiler__b" >&5 +$as_echo "$lt_cv_prog_compiler__b" >&6; } + +if test x"$lt_cv_prog_compiler__b" = xyes; then + archive_cmds='$CC -b ${wl}+h ${wl}$soname ${wl}+b ${wl}$install_libdir -o $lib $libobjs $deplibs $compiler_flags' +else + archive_cmds='$LD -b +h $soname +b $install_libdir -o $lib $libobjs $deplibs $linker_flags' +fi + ;; esac fi @@ -11086,26 +11381,39 @@ if test -z "$aix_libpath"; then aix_libpath="/usr/lib:/lib"; fi irix5* | irix6* | nonstopux*) if test "$GCC" = yes; then - archive_cmds='$CC -shared $libobjs $deplibs $compiler_flags ${wl}-soname ${wl}$soname `test -n "$verstring" && $ECHO "X${wl}-set_version ${wl}$verstring" | $Xsed` ${wl}-update_registry ${wl}${output_objdir}/so_locations -o $lib' + archive_cmds='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags ${wl}-soname ${wl}$soname `test -n "$verstring" && func_echo_all "${wl}-set_version ${wl}$verstring"` ${wl}-update_registry ${wl}${output_objdir}/so_locations -o $lib' # Try to use the -exported_symbol ld option, if it does not # work, assume that -exports_file does not work either and # implicitly export all symbols. - save_LDFLAGS="$LDFLAGS" - LDFLAGS="$LDFLAGS -shared ${wl}-exported_symbol ${wl}foo ${wl}-update_registry ${wl}/dev/null" - cat confdefs.h - <<_ACEOF >conftest.$ac_ext + # This should be the same for all languages, so no per-tag cache variable. + { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether the $host_os linker accepts -exported_symbol" >&5 +$as_echo_n "checking whether the $host_os linker accepts -exported_symbol... " >&6; } +if ${lt_cv_irix_exported_symbol+:} false; then : + $as_echo_n "(cached) " >&6 +else + save_LDFLAGS="$LDFLAGS" + LDFLAGS="$LDFLAGS -shared ${wl}-exported_symbol ${wl}foo ${wl}-update_registry ${wl}/dev/null" + cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ -int foo(void) {} +int foo (void) { return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : - archive_expsym_cmds='$CC -shared $libobjs $deplibs $compiler_flags ${wl}-soname ${wl}$soname `test -n "$verstring" && $ECHO "X${wl}-set_version ${wl}$verstring" | $Xsed` ${wl}-update_registry ${wl}${output_objdir}/so_locations ${wl}-exports_file ${wl}$export_symbols -o $lib' - + lt_cv_irix_exported_symbol=yes +else + lt_cv_irix_exported_symbol=no fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext - LDFLAGS="$save_LDFLAGS" + LDFLAGS="$save_LDFLAGS" +fi +{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $lt_cv_irix_exported_symbol" >&5 +$as_echo "$lt_cv_irix_exported_symbol" >&6; } + if test "$lt_cv_irix_exported_symbol" = yes; then + archive_expsym_cmds='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags ${wl}-soname ${wl}$soname `test -n "$verstring" && func_echo_all "${wl}-set_version ${wl}$verstring"` ${wl}-update_registry ${wl}${output_objdir}/so_locations ${wl}-exports_file ${wl}$export_symbols -o $lib' + fi else - archive_cmds='$CC -shared $libobjs $deplibs $compiler_flags -soname $soname `test -n "$verstring" && $ECHO "X-set_version $verstring" | $Xsed` -update_registry ${output_objdir}/so_locations -o $lib' - archive_expsym_cmds='$CC -shared $libobjs $deplibs $compiler_flags -soname $soname `test -n "$verstring" && $ECHO "X-set_version $verstring" | $Xsed` -update_registry ${output_objdir}/so_locations -exports_file $export_symbols -o $lib' + archive_cmds='$CC -shared $libobjs $deplibs $compiler_flags -soname $soname `test -n "$verstring" && func_echo_all "-set_version $verstring"` -update_registry ${output_objdir}/so_locations -o $lib' + archive_expsym_cmds='$CC -shared $libobjs $deplibs $compiler_flags -soname $soname `test -n "$verstring" && func_echo_all "-set_version $verstring"` -update_registry ${output_objdir}/so_locations -exports_file $export_symbols -o $lib' fi archive_cmds_need_lc='no' hardcode_libdir_flag_spec='${wl}-rpath ${wl}$libdir' @@ -11167,17 +11475,17 @@ rm -f core conftest.err conftest.$ac_objext \ hardcode_libdir_flag_spec='-L$libdir' hardcode_minus_L=yes allow_undefined_flag=unsupported - archive_cmds='$ECHO "LIBRARY $libname INITINSTANCE" > $output_objdir/$libname.def~$ECHO "DESCRIPTION \"$libname\"" >> $output_objdir/$libname.def~$ECHO DATA >> $output_objdir/$libname.def~$ECHO " SINGLE NONSHARED" >> $output_objdir/$libname.def~$ECHO EXPORTS >> $output_objdir/$libname.def~emxexp $libobjs >> $output_objdir/$libname.def~$CC -Zdll -Zcrtdll -o $lib $libobjs $deplibs $compiler_flags $output_objdir/$libname.def' + archive_cmds='$ECHO "LIBRARY $libname INITINSTANCE" > $output_objdir/$libname.def~$ECHO "DESCRIPTION \"$libname\"" >> $output_objdir/$libname.def~echo DATA >> $output_objdir/$libname.def~echo " SINGLE NONSHARED" >> $output_objdir/$libname.def~echo EXPORTS >> $output_objdir/$libname.def~emxexp $libobjs >> $output_objdir/$libname.def~$CC -Zdll -Zcrtdll -o $lib $libobjs $deplibs $compiler_flags $output_objdir/$libname.def' old_archive_from_new_cmds='emximp -o $output_objdir/$libname.a $output_objdir/$libname.def' ;; osf3*) if test "$GCC" = yes; then allow_undefined_flag=' ${wl}-expect_unresolved ${wl}\*' - archive_cmds='$CC -shared${allow_undefined_flag} $libobjs $deplibs $compiler_flags ${wl}-soname ${wl}$soname `test -n "$verstring" && $ECHO "X${wl}-set_version ${wl}$verstring" | $Xsed` ${wl}-update_registry ${wl}${output_objdir}/so_locations -o $lib' + archive_cmds='$CC -shared${allow_undefined_flag} $libobjs $deplibs $compiler_flags ${wl}-soname ${wl}$soname `test -n "$verstring" && func_echo_all "${wl}-set_version ${wl}$verstring"` ${wl}-update_registry ${wl}${output_objdir}/so_locations -o $lib' else allow_undefined_flag=' -expect_unresolved \*' - archive_cmds='$CC -shared${allow_undefined_flag} $libobjs $deplibs $compiler_flags -soname $soname `test -n "$verstring" && $ECHO "X-set_version $verstring" | $Xsed` -update_registry ${output_objdir}/so_locations -o $lib' + archive_cmds='$CC -shared${allow_undefined_flag} $libobjs $deplibs $compiler_flags -soname $soname `test -n "$verstring" && func_echo_all "-set_version $verstring"` -update_registry ${output_objdir}/so_locations -o $lib' fi archive_cmds_need_lc='no' hardcode_libdir_flag_spec='${wl}-rpath ${wl}$libdir' @@ -11187,13 +11495,13 @@ rm -f core conftest.err conftest.$ac_objext \ osf4* | osf5*) # as osf3* with the addition of -msym flag if test "$GCC" = yes; then allow_undefined_flag=' ${wl}-expect_unresolved ${wl}\*' - archive_cmds='$CC -shared${allow_undefined_flag} $libobjs $deplibs $compiler_flags ${wl}-msym ${wl}-soname ${wl}$soname `test -n "$verstring" && $ECHO "X${wl}-set_version ${wl}$verstring" | $Xsed` ${wl}-update_registry ${wl}${output_objdir}/so_locations -o $lib' + archive_cmds='$CC -shared${allow_undefined_flag} $pic_flag $libobjs $deplibs $compiler_flags ${wl}-msym ${wl}-soname ${wl}$soname `test -n "$verstring" && func_echo_all "${wl}-set_version ${wl}$verstring"` ${wl}-update_registry ${wl}${output_objdir}/so_locations -o $lib' hardcode_libdir_flag_spec='${wl}-rpath ${wl}$libdir' else allow_undefined_flag=' -expect_unresolved \*' - archive_cmds='$CC -shared${allow_undefined_flag} $libobjs $deplibs $compiler_flags -msym -soname $soname `test -n "$verstring" && $ECHO "X-set_version $verstring" | $Xsed` -update_registry ${output_objdir}/so_locations -o $lib' + archive_cmds='$CC -shared${allow_undefined_flag} $libobjs $deplibs $compiler_flags -msym -soname $soname `test -n "$verstring" && func_echo_all "-set_version $verstring"` -update_registry ${output_objdir}/so_locations -o $lib' archive_expsym_cmds='for i in `cat $export_symbols`; do printf "%s %s\\n" -exported_symbol "\$i" >> $lib.exp; done; printf "%s\\n" "-hidden">> $lib.exp~ - $CC -shared${allow_undefined_flag} ${wl}-input ${wl}$lib.exp $compiler_flags $libobjs $deplibs -soname $soname `test -n "$verstring" && $ECHO "X-set_version $verstring" | $Xsed` -update_registry ${output_objdir}/so_locations -o $lib~$RM $lib.exp' + $CC -shared${allow_undefined_flag} ${wl}-input ${wl}$lib.exp $compiler_flags $libobjs $deplibs -soname $soname `test -n "$verstring" && $ECHO "-set_version $verstring"` -update_registry ${output_objdir}/so_locations -o $lib~$RM $lib.exp' # Both c and cxx compiler support -rpath directly hardcode_libdir_flag_spec='-rpath $libdir' @@ -11206,9 +11514,9 @@ rm -f core conftest.err conftest.$ac_objext \ no_undefined_flag=' -z defs' if test "$GCC" = yes; then wlarc='${wl}' - archive_cmds='$CC -shared ${wl}-z ${wl}text ${wl}-h ${wl}$soname -o $lib $libobjs $deplibs $compiler_flags' + archive_cmds='$CC -shared $pic_flag ${wl}-z ${wl}text ${wl}-h ${wl}$soname -o $lib $libobjs $deplibs $compiler_flags' archive_expsym_cmds='echo "{ global:" > $lib.exp~cat $export_symbols | $SED -e "s/\(.*\)/\1;/" >> $lib.exp~echo "local: *; };" >> $lib.exp~ - $CC -shared ${wl}-z ${wl}text ${wl}-M ${wl}$lib.exp ${wl}-h ${wl}$soname -o $lib $libobjs $deplibs $compiler_flags~$RM $lib.exp' + $CC -shared $pic_flag ${wl}-z ${wl}text ${wl}-M ${wl}$lib.exp ${wl}-h ${wl}$soname -o $lib $libobjs $deplibs $compiler_flags~$RM $lib.exp' else case `$CC -V 2>&1` in *"Compilers 5.0"*) @@ -11396,44 +11704,50 @@ x|xyes) # to ld, don't add -lc before -lgcc. { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether -lc should be explicitly linked in" >&5 $as_echo_n "checking whether -lc should be explicitly linked in... " >&6; } - $RM conftest* - echo "$lt_simple_compile_test_code" > conftest.$ac_ext +if ${lt_cv_archive_cmds_need_lc+:} false; then : + $as_echo_n "(cached) " >&6 +else + $RM conftest* + echo "$lt_simple_compile_test_code" > conftest.$ac_ext - if { { eval echo "\"\$as_me\":${as_lineno-$LINENO}: \"$ac_compile\""; } >&5 + if { { eval echo "\"\$as_me\":${as_lineno-$LINENO}: \"$ac_compile\""; } >&5 (eval $ac_compile) 2>&5 ac_status=$? $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; } 2>conftest.err; then - soname=conftest - lib=conftest - libobjs=conftest.$ac_objext - deplibs= - wl=$lt_prog_compiler_wl - pic_flag=$lt_prog_compiler_pic - compiler_flags=-v - linker_flags=-v - verstring= - output_objdir=. - libname=conftest - lt_save_allow_undefined_flag=$allow_undefined_flag - allow_undefined_flag= - if { { eval echo "\"\$as_me\":${as_lineno-$LINENO}: \"$archive_cmds 2\>\&1 \| $GREP \" -lc \" \>/dev/null 2\>\&1\""; } >&5 + soname=conftest + lib=conftest + libobjs=conftest.$ac_objext + deplibs= + wl=$lt_prog_compiler_wl + pic_flag=$lt_prog_compiler_pic + compiler_flags=-v + linker_flags=-v + verstring= + output_objdir=. + libname=conftest + lt_save_allow_undefined_flag=$allow_undefined_flag + allow_undefined_flag= + if { { eval echo "\"\$as_me\":${as_lineno-$LINENO}: \"$archive_cmds 2\>\&1 \| $GREP \" -lc \" \>/dev/null 2\>\&1\""; } >&5 (eval $archive_cmds 2\>\&1 \| $GREP \" -lc \" \>/dev/null 2\>\&1) 2>&5 ac_status=$? $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; } - then - archive_cmds_need_lc=no - else - archive_cmds_need_lc=yes - fi - allow_undefined_flag=$lt_save_allow_undefined_flag - else - cat conftest.err 1>&5 - fi - $RM conftest* - { $as_echo "$as_me:${as_lineno-$LINENO}: result: $archive_cmds_need_lc" >&5 -$as_echo "$archive_cmds_need_lc" >&6; } + then + lt_cv_archive_cmds_need_lc=no + else + lt_cv_archive_cmds_need_lc=yes + fi + allow_undefined_flag=$lt_save_allow_undefined_flag + else + cat conftest.err 1>&5 + fi + $RM conftest* + +fi +{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $lt_cv_archive_cmds_need_lc" >&5 +$as_echo "$lt_cv_archive_cmds_need_lc" >&6; } + archive_cmds_need_lc=$lt_cv_archive_cmds_need_lc ;; esac fi @@ -11585,11 +11899,6 @@ esac - - - - - @@ -11604,16 +11913,23 @@ if test "$GCC" = yes; then darwin*) lt_awk_arg="/^libraries:/,/LR/" ;; *) lt_awk_arg="/^libraries:/" ;; esac - lt_search_path_spec=`$CC -print-search-dirs | awk $lt_awk_arg | $SED -e "s/^libraries://" -e "s,=/,/,g"` - if $ECHO "$lt_search_path_spec" | $GREP ';' >/dev/null ; then + case $host_os in + mingw* | cegcc*) lt_sed_strip_eq="s,=\([A-Za-z]:\),\1,g" ;; + *) lt_sed_strip_eq="s,=/,/,g" ;; + esac + lt_search_path_spec=`$CC -print-search-dirs | awk $lt_awk_arg | $SED -e "s/^libraries://" -e $lt_sed_strip_eq` + case $lt_search_path_spec in + *\;*) # if the path contains ";" then we assume it to be the separator # otherwise default to the standard path separator (i.e. ":") - it is # assumed that no part of a normal pathname contains ";" but that should # okay in the real world where ";" in dirpaths is itself problematic. - lt_search_path_spec=`$ECHO "$lt_search_path_spec" | $SED -e 's/;/ /g'` - else - lt_search_path_spec=`$ECHO "$lt_search_path_spec" | $SED -e "s/$PATH_SEPARATOR/ /g"` - fi + lt_search_path_spec=`$ECHO "$lt_search_path_spec" | $SED 's/;/ /g'` + ;; + *) + lt_search_path_spec=`$ECHO "$lt_search_path_spec" | $SED "s/$PATH_SEPARATOR/ /g"` + ;; + esac # Ok, now we have the path, separated by spaces, we can step through it # and add multilib dir if necessary. lt_tmp_lt_search_path_spec= @@ -11626,7 +11942,7 @@ if test "$GCC" = yes; then lt_tmp_lt_search_path_spec="$lt_tmp_lt_search_path_spec $lt_sys_path" fi done - lt_search_path_spec=`$ECHO $lt_tmp_lt_search_path_spec | awk ' + lt_search_path_spec=`$ECHO "$lt_tmp_lt_search_path_spec" | awk ' BEGIN {RS=" "; FS="/|\n";} { lt_foo=""; lt_count=0; @@ -11646,7 +11962,13 @@ BEGIN {RS=" "; FS="/|\n";} { if (lt_foo != "") { lt_freq[lt_foo]++; } if (lt_freq[lt_foo] == 1) { print lt_foo; } }'` - sys_lib_search_path_spec=`$ECHO $lt_search_path_spec` + # AWK program above erroneously prepends '/' to C:/dos/paths + # for these hosts. + case $host_os in + mingw* | cegcc*) lt_search_path_spec=`$ECHO "$lt_search_path_spec" |\ + $SED 's,/\([A-Za-z]:\),\1,g'` ;; + esac + sys_lib_search_path_spec=`$ECHO "$lt_search_path_spec" | $lt_NL2SP` else sys_lib_search_path_spec="/lib /usr/lib /usr/local/lib" fi @@ -11672,7 +11994,7 @@ need_version=unknown case $host_os in aix3*) - version_type=linux + version_type=linux # correct to gnu/linux during the next big refactor library_names_spec='${libname}${release}${shared_ext}$versuffix $libname.a' shlibpath_var=LIBPATH @@ -11681,7 +12003,7 @@ aix3*) ;; aix[4-9]*) - version_type=linux + version_type=linux # correct to gnu/linux during the next big refactor need_lib_prefix=no need_version=no hardcode_into_libs=yes @@ -11734,7 +12056,7 @@ amigaos*) m68k) library_names_spec='$libname.ixlibrary $libname.a' # Create ${libname}_ixlibrary.a entries in /sys/libs. - finish_eval='for lib in `ls $libdir/*.ixlibrary 2>/dev/null`; do libname=`$ECHO "X$lib" | $Xsed -e '\''s%^.*/\([^/]*\)\.ixlibrary$%\1%'\''`; test $RM /sys/libs/${libname}_ixlibrary.a; $show "cd /sys/libs && $LN_S $lib ${libname}_ixlibrary.a"; cd /sys/libs && $LN_S $lib ${libname}_ixlibrary.a || exit 1; done' + finish_eval='for lib in `ls $libdir/*.ixlibrary 2>/dev/null`; do libname=`func_echo_all "$lib" | $SED '\''s%^.*/\([^/]*\)\.ixlibrary$%\1%'\''`; test $RM /sys/libs/${libname}_ixlibrary.a; $show "cd /sys/libs && $LN_S $lib ${libname}_ixlibrary.a"; cd /sys/libs && $LN_S $lib ${libname}_ixlibrary.a || exit 1; done' ;; esac ;; @@ -11746,7 +12068,7 @@ beos*) ;; bsdi[45]*) - version_type=linux + version_type=linux # correct to gnu/linux during the next big refactor need_version=no library_names_spec='${libname}${release}${shared_ext}$versuffix ${libname}${release}${shared_ext}$major $libname${shared_ext}' soname_spec='${libname}${release}${shared_ext}$major' @@ -11765,8 +12087,9 @@ cygwin* | mingw* | pw32* | cegcc*) need_version=no need_lib_prefix=no - case $GCC,$host_os in - yes,cygwin* | yes,mingw* | yes,pw32* | yes,cegcc*) + case $GCC,$cc_basename in + yes,*) + # gcc library_names_spec='$libname.dll.a' # DLL is installed to $(libdir)/../bin by postinstall_cmds postinstall_cmds='base_file=`basename \${file}`~ @@ -11787,36 +12110,83 @@ cygwin* | mingw* | pw32* | cegcc*) cygwin*) # Cygwin DLLs use 'cyg' prefix rather than 'lib' soname_spec='`echo ${libname} | sed -e 's/^lib/cyg/'``echo ${release} | $SED -e 's/[.]/-/g'`${versuffix}${shared_ext}' - sys_lib_search_path_spec="/usr/lib /lib/w32api /lib /usr/local/lib" + + sys_lib_search_path_spec="$sys_lib_search_path_spec /usr/lib/w32api" ;; mingw* | cegcc*) # MinGW DLLs use traditional 'lib' prefix soname_spec='${libname}`echo ${release} | $SED -e 's/[.]/-/g'`${versuffix}${shared_ext}' - sys_lib_search_path_spec=`$CC -print-search-dirs | $GREP "^libraries:" | $SED -e "s/^libraries://" -e "s,=/,/,g"` - if $ECHO "$sys_lib_search_path_spec" | $GREP ';[c-zC-Z]:/' >/dev/null; then - # It is most probably a Windows format PATH printed by - # mingw gcc, but we are running on Cygwin. Gcc prints its search - # path with ; separators, and with drive letters. We can handle the - # drive letters (cygwin fileutils understands them), so leave them, - # especially as we might pass files found there to a mingw objdump, - # which wouldn't understand a cygwinified path. Ahh. - sys_lib_search_path_spec=`$ECHO "$sys_lib_search_path_spec" | $SED -e 's/;/ /g'` - else - sys_lib_search_path_spec=`$ECHO "$sys_lib_search_path_spec" | $SED -e "s/$PATH_SEPARATOR/ /g"` - fi ;; pw32*) # pw32 DLLs use 'pw' prefix rather than 'lib' library_names_spec='`echo ${libname} | sed -e 's/^lib/pw/'``echo ${release} | $SED -e 's/[.]/-/g'`${versuffix}${shared_ext}' ;; esac + dynamic_linker='Win32 ld.exe' + ;; + + *,cl*) + # Native MSVC + libname_spec='$name' + soname_spec='${libname}`echo ${release} | $SED -e 's/[.]/-/g'`${versuffix}${shared_ext}' + library_names_spec='${libname}.dll.lib' + + case $build_os in + mingw*) + sys_lib_search_path_spec= + lt_save_ifs=$IFS + IFS=';' + for lt_path in $LIB + do + IFS=$lt_save_ifs + # Let DOS variable expansion print the short 8.3 style file name. + lt_path=`cd "$lt_path" 2>/dev/null && cmd //C "for %i in (".") do @echo %~si"` + sys_lib_search_path_spec="$sys_lib_search_path_spec $lt_path" + done + IFS=$lt_save_ifs + # Convert to MSYS style. + sys_lib_search_path_spec=`$ECHO "$sys_lib_search_path_spec" | sed -e 's|\\\\|/|g' -e 's| \\([a-zA-Z]\\):| /\\1|g' -e 's|^ ||'` + ;; + cygwin*) + # Convert to unix form, then to dos form, then back to unix form + # but this time dos style (no spaces!) so that the unix form looks + # like /cygdrive/c/PROGRA~1:/cygdr... + sys_lib_search_path_spec=`cygpath --path --unix "$LIB"` + sys_lib_search_path_spec=`cygpath --path --dos "$sys_lib_search_path_spec" 2>/dev/null` + sys_lib_search_path_spec=`cygpath --path --unix "$sys_lib_search_path_spec" | $SED -e "s/$PATH_SEPARATOR/ /g"` + ;; + *) + sys_lib_search_path_spec="$LIB" + if $ECHO "$sys_lib_search_path_spec" | $GREP ';[c-zC-Z]:/' >/dev/null; then + # It is most probably a Windows format PATH. + sys_lib_search_path_spec=`$ECHO "$sys_lib_search_path_spec" | $SED -e 's/;/ /g'` + else + sys_lib_search_path_spec=`$ECHO "$sys_lib_search_path_spec" | $SED -e "s/$PATH_SEPARATOR/ /g"` + fi + # FIXME: find the short name or the path components, as spaces are + # common. (e.g. "Program Files" -> "PROGRA~1") + ;; + esac + + # DLL is installed to $(libdir)/../bin by postinstall_cmds + postinstall_cmds='base_file=`basename \${file}`~ + dlpath=`$SHELL 2>&1 -c '\''. $dir/'\''\${base_file}'\''i; echo \$dlname'\''`~ + dldir=$destdir/`dirname \$dlpath`~ + test -d \$dldir || mkdir -p \$dldir~ + $install_prog $dir/$dlname \$dldir/$dlname' + postuninstall_cmds='dldll=`$SHELL 2>&1 -c '\''. $file; echo \$dlname'\''`~ + dlpath=$dir/\$dldll~ + $RM \$dlpath' + shlibpath_overrides_runpath=yes + dynamic_linker='Win32 link.exe' ;; *) + # Assume MSVC wrapper library_names_spec='${libname}`echo ${release} | $SED -e 's/[.]/-/g'`${versuffix}${shared_ext} $libname.lib' + dynamic_linker='Win32 ld.exe' ;; esac - dynamic_linker='Win32 ld.exe' # FIXME: first we should search . and the directory the executable is in shlibpath_var=PATH ;; @@ -11837,7 +12207,7 @@ darwin* | rhapsody*) ;; dgux*) - version_type=linux + version_type=linux # correct to gnu/linux during the next big refactor need_lib_prefix=no need_version=no library_names_spec='${libname}${release}${shared_ext}$versuffix ${libname}${release}${shared_ext}$major $libname$shared_ext' @@ -11845,10 +12215,6 @@ dgux*) shlibpath_var=LD_LIBRARY_PATH ;; -freebsd1*) - dynamic_linker=no - ;; - freebsd* | dragonfly*) # DragonFly does not have aout. When/if they implement a new # versioning mechanism, adjust this. @@ -11856,7 +12222,7 @@ freebsd* | dragonfly*) objformat=`/usr/bin/objformat` else case $host_os in - freebsd[123]*) objformat=aout ;; + freebsd[23].*) objformat=aout ;; *) objformat=elf ;; esac fi @@ -11874,7 +12240,7 @@ freebsd* | dragonfly*) esac shlibpath_var=LD_LIBRARY_PATH case $host_os in - freebsd2*) + freebsd2.*) shlibpath_overrides_runpath=yes ;; freebsd3.[01]* | freebsdelf3.[01]*) @@ -11893,13 +12259,16 @@ freebsd* | dragonfly*) esac ;; -gnu*) - version_type=linux +haiku*) + version_type=linux # correct to gnu/linux during the next big refactor need_lib_prefix=no need_version=no + dynamic_linker="$host_os runtime_loader" library_names_spec='${libname}${release}${shared_ext}$versuffix ${libname}${release}${shared_ext}${major} ${libname}${shared_ext}' soname_spec='${libname}${release}${shared_ext}$major' - shlibpath_var=LD_LIBRARY_PATH + shlibpath_var=LIBRARY_PATH + shlibpath_overrides_runpath=yes + sys_lib_dlsearch_path_spec='/boot/home/config/lib /boot/common/lib /boot/system/lib' hardcode_into_libs=yes ;; @@ -11945,12 +12314,14 @@ hpux9* | hpux10* | hpux11*) soname_spec='${libname}${release}${shared_ext}$major' ;; esac - # HP-UX runs *really* slowly unless shared libraries are mode 555. + # HP-UX runs *really* slowly unless shared libraries are mode 555, ... postinstall_cmds='chmod 555 $lib' + # or fails outright, so override atomically: + install_override_mode=555 ;; interix[3-9]*) - version_type=linux + version_type=linux # correct to gnu/linux during the next big refactor need_lib_prefix=no need_version=no library_names_spec='${libname}${release}${shared_ext}$versuffix ${libname}${release}${shared_ext}$major ${libname}${shared_ext}' @@ -11966,7 +12337,7 @@ irix5* | irix6* | nonstopux*) nonstopux*) version_type=nonstopux ;; *) if test "$lt_cv_prog_gnu_ld" = yes; then - version_type=linux + version_type=linux # correct to gnu/linux during the next big refactor else version_type=irix fi ;; @@ -12003,9 +12374,9 @@ linux*oldld* | linux*aout* | linux*coff*) dynamic_linker=no ;; -# This must be Linux ELF. -linux* | k*bsd*-gnu | kopensolaris*-gnu) - version_type=linux +# This must be glibc/ELF. +linux* | k*bsd*-gnu | kopensolaris*-gnu | gnu*) + version_type=linux # correct to gnu/linux during the next big refactor need_lib_prefix=no need_version=no library_names_spec='${libname}${release}${shared_ext}$versuffix ${libname}${release}${shared_ext}$major $libname${shared_ext}' @@ -12013,12 +12384,17 @@ linux* | k*bsd*-gnu | kopensolaris*-gnu) finish_cmds='PATH="\$PATH:/sbin" ldconfig -n $libdir' shlibpath_var=LD_LIBRARY_PATH shlibpath_overrides_runpath=no + # Some binutils ld are patched to set DT_RUNPATH - save_LDFLAGS=$LDFLAGS - save_libdir=$libdir - eval "libdir=/foo; wl=\"$lt_prog_compiler_wl\"; \ - LDFLAGS=\"\$LDFLAGS $hardcode_libdir_flag_spec\"" - cat confdefs.h - <<_ACEOF >conftest.$ac_ext + if ${lt_cv_shlibpath_overrides_runpath+:} false; then : + $as_echo_n "(cached) " >&6 +else + lt_cv_shlibpath_overrides_runpath=no + save_LDFLAGS=$LDFLAGS + save_libdir=$libdir + eval "libdir=/foo; wl=\"$lt_prog_compiler_wl\"; \ + LDFLAGS=\"\$LDFLAGS $hardcode_libdir_flag_spec\"" + cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ int @@ -12031,13 +12407,17 @@ main () _ACEOF if ac_fn_c_try_link "$LINENO"; then : if ($OBJDUMP -p conftest$ac_exeext) 2>/dev/null | grep "RUNPATH.*$libdir" >/dev/null; then : - shlibpath_overrides_runpath=yes + lt_cv_shlibpath_overrides_runpath=yes fi fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext - LDFLAGS=$save_LDFLAGS - libdir=$save_libdir + LDFLAGS=$save_LDFLAGS + libdir=$save_libdir + +fi + + shlibpath_overrides_runpath=$lt_cv_shlibpath_overrides_runpath # This implies no fast_install, which is unacceptable. # Some rework will be needed to allow for fast_install @@ -12046,7 +12426,7 @@ rm -f core conftest.err conftest.$ac_objext \ # Append ld.so.conf contents to the search path if test -f /etc/ld.so.conf; then - lt_ld_extra=`awk '/^include / { system(sprintf("cd /etc; cat %s 2>/dev/null", \$2)); skip = 1; } { if (!skip) print \$0; skip = 0; }' < /etc/ld.so.conf | $SED -e 's/#.*//;/^[ ]*hwcap[ ]/d;s/[:, ]/ /g;s/=[^=]*$//;s/=[^= ]* / /g;/^$/d' | tr '\n' ' '` + lt_ld_extra=`awk '/^include / { system(sprintf("cd /etc; cat %s 2>/dev/null", \$2)); skip = 1; } { if (!skip) print \$0; skip = 0; }' < /etc/ld.so.conf | $SED -e 's/#.*//;/^[ ]*hwcap[ ]/d;s/[:, ]/ /g;s/=[^=]*$//;s/=[^= ]* / /g;s/"//g;/^$/d' | tr '\n' ' '` sys_lib_dlsearch_path_spec="/lib /usr/lib $lt_ld_extra" fi @@ -12090,7 +12470,7 @@ netbsd*) ;; newsos6) - version_type=linux + version_type=linux # correct to gnu/linux during the next big refactor library_names_spec='${libname}${release}${shared_ext}$versuffix ${libname}${release}${shared_ext}$major $libname${shared_ext}' shlibpath_var=LD_LIBRARY_PATH shlibpath_overrides_runpath=yes @@ -12159,7 +12539,7 @@ rdos*) ;; solaris*) - version_type=linux + version_type=linux # correct to gnu/linux during the next big refactor need_lib_prefix=no need_version=no library_names_spec='${libname}${release}${shared_ext}$versuffix ${libname}${release}${shared_ext}$major $libname${shared_ext}' @@ -12184,7 +12564,7 @@ sunos4*) ;; sysv4 | sysv4.3*) - version_type=linux + version_type=linux # correct to gnu/linux during the next big refactor library_names_spec='${libname}${release}${shared_ext}$versuffix ${libname}${release}${shared_ext}$major $libname${shared_ext}' soname_spec='${libname}${release}${shared_ext}$major' shlibpath_var=LD_LIBRARY_PATH @@ -12208,7 +12588,7 @@ sysv4 | sysv4.3*) sysv4*MP*) if test -d /usr/nec ;then - version_type=linux + version_type=linux # correct to gnu/linux during the next big refactor library_names_spec='$libname${shared_ext}.$versuffix $libname${shared_ext}.$major $libname${shared_ext}' soname_spec='$libname${shared_ext}.$major' shlibpath_var=LD_LIBRARY_PATH @@ -12239,7 +12619,7 @@ sysv5* | sco3.2v5* | sco5v6* | unixware* | OpenUNIX* | sysv4*uw2*) tpf*) # TPF is a cross-target only. Preferred cross-host = GNU/Linux. - version_type=linux + version_type=linux # correct to gnu/linux during the next big refactor need_lib_prefix=no need_version=no library_names_spec='${libname}${release}${shared_ext}$versuffix ${libname}${release}${shared_ext}$major $libname${shared_ext}' @@ -12249,7 +12629,7 @@ tpf*) ;; uts4*) - version_type=linux + version_type=linux # correct to gnu/linux during the next big refactor library_names_spec='${libname}${release}${shared_ext}$versuffix ${libname}${release}${shared_ext}$major $libname${shared_ext}' soname_spec='${libname}${release}${shared_ext}$major' shlibpath_var=LD_LIBRARY_PATH @@ -12355,6 +12735,11 @@ fi + + + + + @@ -12433,7 +12818,7 @@ else # if libdl is installed we need to link against it { $as_echo "$as_me:${as_lineno-$LINENO}: checking for dlopen in -ldl" >&5 $as_echo_n "checking for dlopen in -ldl... " >&6; } -if test "${ac_cv_lib_dl_dlopen+set}" = set; then : +if ${ac_cv_lib_dl_dlopen+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS @@ -12467,7 +12852,7 @@ LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_dl_dlopen" >&5 $as_echo "$ac_cv_lib_dl_dlopen" >&6; } -if test "x$ac_cv_lib_dl_dlopen" = x""yes; then : +if test "x$ac_cv_lib_dl_dlopen" = xyes; then : lt_cv_dlopen="dlopen" lt_cv_dlopen_libs="-ldl" else @@ -12481,12 +12866,12 @@ fi *) ac_fn_c_check_func "$LINENO" "shl_load" "ac_cv_func_shl_load" -if test "x$ac_cv_func_shl_load" = x""yes; then : +if test "x$ac_cv_func_shl_load" = xyes; then : lt_cv_dlopen="shl_load" else { $as_echo "$as_me:${as_lineno-$LINENO}: checking for shl_load in -ldld" >&5 $as_echo_n "checking for shl_load in -ldld... " >&6; } -if test "${ac_cv_lib_dld_shl_load+set}" = set; then : +if ${ac_cv_lib_dld_shl_load+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS @@ -12520,16 +12905,16 @@ LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_dld_shl_load" >&5 $as_echo "$ac_cv_lib_dld_shl_load" >&6; } -if test "x$ac_cv_lib_dld_shl_load" = x""yes; then : +if test "x$ac_cv_lib_dld_shl_load" = xyes; then : lt_cv_dlopen="shl_load" lt_cv_dlopen_libs="-ldld" else ac_fn_c_check_func "$LINENO" "dlopen" "ac_cv_func_dlopen" -if test "x$ac_cv_func_dlopen" = x""yes; then : +if test "x$ac_cv_func_dlopen" = xyes; then : lt_cv_dlopen="dlopen" else { $as_echo "$as_me:${as_lineno-$LINENO}: checking for dlopen in -ldl" >&5 $as_echo_n "checking for dlopen in -ldl... " >&6; } -if test "${ac_cv_lib_dl_dlopen+set}" = set; then : +if ${ac_cv_lib_dl_dlopen+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS @@ -12563,12 +12948,12 @@ LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_dl_dlopen" >&5 $as_echo "$ac_cv_lib_dl_dlopen" >&6; } -if test "x$ac_cv_lib_dl_dlopen" = x""yes; then : +if test "x$ac_cv_lib_dl_dlopen" = xyes; then : lt_cv_dlopen="dlopen" lt_cv_dlopen_libs="-ldl" else { $as_echo "$as_me:${as_lineno-$LINENO}: checking for dlopen in -lsvld" >&5 $as_echo_n "checking for dlopen in -lsvld... " >&6; } -if test "${ac_cv_lib_svld_dlopen+set}" = set; then : +if ${ac_cv_lib_svld_dlopen+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS @@ -12602,12 +12987,12 @@ LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_svld_dlopen" >&5 $as_echo "$ac_cv_lib_svld_dlopen" >&6; } -if test "x$ac_cv_lib_svld_dlopen" = x""yes; then : +if test "x$ac_cv_lib_svld_dlopen" = xyes; then : lt_cv_dlopen="dlopen" lt_cv_dlopen_libs="-lsvld" else { $as_echo "$as_me:${as_lineno-$LINENO}: checking for dld_link in -ldld" >&5 $as_echo_n "checking for dld_link in -ldld... " >&6; } -if test "${ac_cv_lib_dld_dld_link+set}" = set; then : +if ${ac_cv_lib_dld_dld_link+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS @@ -12641,7 +13026,7 @@ LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_dld_dld_link" >&5 $as_echo "$ac_cv_lib_dld_dld_link" >&6; } -if test "x$ac_cv_lib_dld_dld_link" = x""yes; then : +if test "x$ac_cv_lib_dld_dld_link" = xyes; then : lt_cv_dlopen="dld_link" lt_cv_dlopen_libs="-ldld" fi @@ -12682,7 +13067,7 @@ fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether a program can dlopen itself" >&5 $as_echo_n "checking whether a program can dlopen itself... " >&6; } -if test "${lt_cv_dlopen_self+set}" = set; then : +if ${lt_cv_dlopen_self+:} false; then : $as_echo_n "(cached) " >&6 else if test "$cross_compiling" = yes; then : @@ -12691,7 +13076,7 @@ else lt_dlunknown=0; lt_dlno_uscore=1; lt_dlneed_uscore=2 lt_status=$lt_dlunknown cat > conftest.$ac_ext <<_LT_EOF -#line 12694 "configure" +#line $LINENO "configure" #include "confdefs.h" #if HAVE_DLFCN_H @@ -12732,7 +13117,13 @@ else # endif #endif -void fnord() { int i=42;} +/* When -fvisbility=hidden is used, assume the code has been annotated + correspondingly for the symbols needed. */ +#if defined(__GNUC__) && (((__GNUC__ == 3) && (__GNUC_MINOR__ >= 3)) || (__GNUC__ > 3)) +int fnord () __attribute__((visibility("default"))); +#endif + +int fnord () { return 42; } int main () { void *self = dlopen (0, LT_DLGLOBAL|LT_DLLAZY_OR_NOW); @@ -12741,7 +13132,11 @@ int main () if (self) { if (dlsym (self,"fnord")) status = $lt_dlno_uscore; - else if (dlsym( self,"_fnord")) status = $lt_dlneed_uscore; + else + { + if (dlsym( self,"_fnord")) status = $lt_dlneed_uscore; + else puts (dlerror ()); + } /* dlclose (self); */ } else @@ -12778,7 +13173,7 @@ $as_echo "$lt_cv_dlopen_self" >&6; } wl=$lt_prog_compiler_wl eval LDFLAGS=\"\$LDFLAGS $lt_prog_compiler_static\" { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether a statically linked program can dlopen itself" >&5 $as_echo_n "checking whether a statically linked program can dlopen itself... " >&6; } -if test "${lt_cv_dlopen_self_static+set}" = set; then : +if ${lt_cv_dlopen_self_static+:} false; then : $as_echo_n "(cached) " >&6 else if test "$cross_compiling" = yes; then : @@ -12787,7 +13182,7 @@ else lt_dlunknown=0; lt_dlno_uscore=1; lt_dlneed_uscore=2 lt_status=$lt_dlunknown cat > conftest.$ac_ext <<_LT_EOF -#line 12790 "configure" +#line $LINENO "configure" #include "confdefs.h" #if HAVE_DLFCN_H @@ -12828,7 +13223,13 @@ else # endif #endif -void fnord() { int i=42;} +/* When -fvisbility=hidden is used, assume the code has been annotated + correspondingly for the symbols needed. */ +#if defined(__GNUC__) && (((__GNUC__ == 3) && (__GNUC_MINOR__ >= 3)) || (__GNUC__ > 3)) +int fnord () __attribute__((visibility("default"))); +#endif + +int fnord () { return 42; } int main () { void *self = dlopen (0, LT_DLGLOBAL|LT_DLLAZY_OR_NOW); @@ -12837,7 +13238,11 @@ int main () if (self) { if (dlsym (self,"fnord")) status = $lt_dlno_uscore; - else if (dlsym( self,"_fnord")) status = $lt_dlneed_uscore; + else + { + if (dlsym( self,"_fnord")) status = $lt_dlneed_uscore; + else puts (dlerror ()); + } /* dlclose (self); */ } else @@ -12994,6 +13399,145 @@ ac_compiler_gnu=$ac_cv_c_compiler_gnu CC="$lt_save_CC" + if test -n "$CXX" && ( test "X$CXX" != "Xno" && + ( (test "X$CXX" = "Xg++" && `g++ -v >/dev/null 2>&1` ) || + (test "X$CXX" != "Xg++"))) ; then + ac_ext=cpp +ac_cpp='$CXXCPP $CPPFLAGS' +ac_compile='$CXX -c $CXXFLAGS $CPPFLAGS conftest.$ac_ext >&5' +ac_link='$CXX -o conftest$ac_exeext $CXXFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5' +ac_compiler_gnu=$ac_cv_cxx_compiler_gnu +{ $as_echo "$as_me:${as_lineno-$LINENO}: checking how to run the C++ preprocessor" >&5 +$as_echo_n "checking how to run the C++ preprocessor... " >&6; } +if test -z "$CXXCPP"; then + if ${ac_cv_prog_CXXCPP+:} false; then : + $as_echo_n "(cached) " >&6 +else + # Double quotes because CXXCPP needs to be expanded + for CXXCPP in "$CXX -E" "/lib/cpp" + do + ac_preproc_ok=false +for ac_cxx_preproc_warn_flag in '' yes +do + # Use a header file that comes with gcc, so configuring glibc + # with a fresh cross-compiler works. + # Prefer to if __STDC__ is defined, since + # exists even on freestanding compilers. + # On the NeXT, cc -E runs the code through the compiler's parser, + # not just through cpp. "Syntax error" is here to catch this case. + cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ +#ifdef __STDC__ +# include +#else +# include +#endif + Syntax error +_ACEOF +if ac_fn_cxx_try_cpp "$LINENO"; then : + +else + # Broken: fails on valid input. +continue +fi +rm -f conftest.err conftest.i conftest.$ac_ext + + # OK, works on sane cases. Now check whether nonexistent headers + # can be detected and how. + cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ +#include +_ACEOF +if ac_fn_cxx_try_cpp "$LINENO"; then : + # Broken: success on invalid input. +continue +else + # Passes both tests. +ac_preproc_ok=: +break +fi +rm -f conftest.err conftest.i conftest.$ac_ext + +done +# Because of `break', _AC_PREPROC_IFELSE's cleaning code was skipped. +rm -f conftest.i conftest.err conftest.$ac_ext +if $ac_preproc_ok; then : + break +fi + + done + ac_cv_prog_CXXCPP=$CXXCPP + +fi + CXXCPP=$ac_cv_prog_CXXCPP +else + ac_cv_prog_CXXCPP=$CXXCPP +fi +{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $CXXCPP" >&5 +$as_echo "$CXXCPP" >&6; } +ac_preproc_ok=false +for ac_cxx_preproc_warn_flag in '' yes +do + # Use a header file that comes with gcc, so configuring glibc + # with a fresh cross-compiler works. + # Prefer to if __STDC__ is defined, since + # exists even on freestanding compilers. + # On the NeXT, cc -E runs the code through the compiler's parser, + # not just through cpp. "Syntax error" is here to catch this case. + cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ +#ifdef __STDC__ +# include +#else +# include +#endif + Syntax error +_ACEOF +if ac_fn_cxx_try_cpp "$LINENO"; then : + +else + # Broken: fails on valid input. +continue +fi +rm -f conftest.err conftest.i conftest.$ac_ext + + # OK, works on sane cases. Now check whether nonexistent headers + # can be detected and how. + cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ +#include +_ACEOF +if ac_fn_cxx_try_cpp "$LINENO"; then : + # Broken: success on invalid input. +continue +else + # Passes both tests. +ac_preproc_ok=: +break +fi +rm -f conftest.err conftest.i conftest.$ac_ext + +done +# Because of `break', _AC_PREPROC_IFELSE's cleaning code was skipped. +rm -f conftest.i conftest.err conftest.$ac_ext +if $ac_preproc_ok; then : + +else + { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 +$as_echo "$as_me: error: in \`$ac_pwd':" >&2;} +as_fn_error $? "C++ preprocessor \"$CXXCPP\" fails sanity check +See \`config.log' for more details" "$LINENO" 5; } +fi + +ac_ext=c +ac_cpp='$CPP $CPPFLAGS' +ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5' +ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5' +ac_compiler_gnu=$ac_cv_c_compiler_gnu + +else + _lt_caught_CXX_error=yes +fi ac_ext=cpp ac_cpp='$CXXCPP $CPPFLAGS' @@ -13010,7 +13554,6 @@ export_dynamic_flag_spec_CXX= hardcode_direct_CXX=no hardcode_direct_absolute_CXX=no hardcode_libdir_flag_spec_CXX= -hardcode_libdir_flag_spec_ld_CXX= hardcode_libdir_separator_CXX= hardcode_minus_L_CXX=no hardcode_shlibpath_var_CXX=unsupported @@ -13020,6 +13563,8 @@ module_cmds_CXX= module_expsym_cmds_CXX= link_all_deplibs_CXX=unknown old_archive_cmds_CXX=$old_archive_cmds +reload_flag_CXX=$reload_flag +reload_cmds_CXX=$reload_cmds no_undefined_flag_CXX= whole_archive_flag_spec_CXX= enable_shared_with_static_runtimes_CXX=no @@ -13075,6 +13620,7 @@ $RM -r conftest* # Allow CC to be a program name with arguments. lt_save_CC=$CC + lt_save_CFLAGS=$CFLAGS lt_save_LD=$LD lt_save_GCC=$GCC GCC=$GXX @@ -13092,6 +13638,7 @@ $RM -r conftest* fi test -z "${LDCXX+set}" || LD=$LDCXX CC=${CXX-"c++"} + CFLAGS=$CXXFLAGS compiler=$CC compiler_CXX=$CC for cc_temp in $compiler""; do @@ -13102,7 +13649,7 @@ $RM -r conftest* *) break;; esac done -cc_basename=`$ECHO "X$cc_temp" | $Xsed -e 's%.*/%%' -e "s%^$host_alias-%%"` +cc_basename=`$ECHO "$cc_temp" | $SED "s%.*/%%; s%^$host_alias-%%"` if test -n "$compiler"; then @@ -13165,7 +13712,7 @@ else { $as_echo "$as_me:${as_lineno-$LINENO}: checking for non-GNU ld" >&5 $as_echo_n "checking for non-GNU ld... " >&6; } fi -if test "${lt_cv_path_LD+set}" = set; then : +if ${lt_cv_path_LD+:} false; then : $as_echo_n "(cached) " >&6 else if test -z "$LD"; then @@ -13205,7 +13752,7 @@ fi test -z "$LD" && as_fn_error $? "no acceptable ld found in \$PATH" "$LINENO" 5 { $as_echo "$as_me:${as_lineno-$LINENO}: checking if the linker ($LD) is GNU ld" >&5 $as_echo_n "checking if the linker ($LD) is GNU ld... " >&6; } -if test "${lt_cv_prog_gnu_ld+set}" = set; then : +if ${lt_cv_prog_gnu_ld+:} false; then : $as_echo_n "(cached) " >&6 else # I'd rather use --version here, but apparently some GNU lds only accept -v. @@ -13231,8 +13778,8 @@ with_gnu_ld=$lt_cv_prog_gnu_ld # Check if GNU C++ uses GNU ld as the underlying linker, since the # archiving commands below assume that GNU ld is being used. if test "$with_gnu_ld" = yes; then - archive_cmds_CXX='$CC -shared -nostdlib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags ${wl}-soname $wl$soname -o $lib' - archive_expsym_cmds_CXX='$CC -shared -nostdlib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags ${wl}-soname $wl$soname ${wl}-retain-symbols-file $wl$export_symbols -o $lib' + archive_cmds_CXX='$CC $pic_flag -shared -nostdlib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags ${wl}-soname $wl$soname -o $lib' + archive_expsym_cmds_CXX='$CC $pic_flag -shared -nostdlib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags ${wl}-soname $wl$soname ${wl}-retain-symbols-file $wl$export_symbols -o $lib' hardcode_libdir_flag_spec_CXX='${wl}-rpath ${wl}$libdir' export_dynamic_flag_spec_CXX='${wl}--export-dynamic' @@ -13264,7 +13811,7 @@ with_gnu_ld=$lt_cv_prog_gnu_ld # Commands to make compiler produce verbose output that lists # what "hidden" libraries, object files and flags are used when # linking a shared library. - output_verbose_link_cmd='$CC -shared $CFLAGS -v conftest.$objext 2>&1 | $GREP "\-L"' + output_verbose_link_cmd='$CC -shared $CFLAGS -v conftest.$objext 2>&1 | $GREP -v "^Configured with:" | $GREP "\-L"' else GXX=no @@ -13374,7 +13921,13 @@ $as_echo_n "checking whether the $compiler linker ($LD) supports shared librarie allow_undefined_flag_CXX='-berok' # Determine the default libpath from the value encoded in an empty # executable. - cat confdefs.h - <<_ACEOF >conftest.$ac_ext + if test "${lt_cv_aix_libpath+set}" = set; then + aix_libpath=$lt_cv_aix_libpath +else + if ${lt_cv_aix_libpath__CXX+:} false; then : + $as_echo_n "(cached) " >&6 +else + cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ int @@ -13387,26 +13940,33 @@ main () _ACEOF if ac_fn_cxx_try_link "$LINENO"; then : -lt_aix_libpath_sed=' - /Import File Strings/,/^$/ { - /^0/ { - s/^0 *\(.*\)$/\1/ - p - } - }' -aix_libpath=`dump -H conftest$ac_exeext 2>/dev/null | $SED -n -e "$lt_aix_libpath_sed"` -# Check for a 64-bit object if we didn't find anything. -if test -z "$aix_libpath"; then - aix_libpath=`dump -HX64 conftest$ac_exeext 2>/dev/null | $SED -n -e "$lt_aix_libpath_sed"` -fi + lt_aix_libpath_sed=' + /Import File Strings/,/^$/ { + /^0/ { + s/^0 *\([^ ]*\) *$/\1/ + p + } + }' + lt_cv_aix_libpath__CXX=`dump -H conftest$ac_exeext 2>/dev/null | $SED -n -e "$lt_aix_libpath_sed"` + # Check for a 64-bit object if we didn't find anything. + if test -z "$lt_cv_aix_libpath__CXX"; then + lt_cv_aix_libpath__CXX=`dump -HX64 conftest$ac_exeext 2>/dev/null | $SED -n -e "$lt_aix_libpath_sed"` + fi fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext -if test -z "$aix_libpath"; then aix_libpath="/usr/lib:/lib"; fi + if test -z "$lt_cv_aix_libpath__CXX"; then + lt_cv_aix_libpath__CXX="/usr/lib:/lib" + fi + +fi + + aix_libpath=$lt_cv_aix_libpath__CXX +fi hardcode_libdir_flag_spec_CXX='${wl}-blibpath:$libdir:'"$aix_libpath" - archive_expsym_cmds_CXX='$CC -o $output_objdir/$soname $libobjs $deplibs '"\${wl}$no_entry_flag"' $compiler_flags `if test "x${allow_undefined_flag}" != "x"; then $ECHO "X${wl}${allow_undefined_flag}" | $Xsed; else :; fi` '"\${wl}$exp_sym_flag:\$export_symbols $shared_flag" + archive_expsym_cmds_CXX='$CC -o $output_objdir/$soname $libobjs $deplibs '"\${wl}$no_entry_flag"' $compiler_flags `if test "x${allow_undefined_flag}" != "x"; then func_echo_all "${wl}${allow_undefined_flag}"; else :; fi` '"\${wl}$exp_sym_flag:\$export_symbols $shared_flag" else if test "$host_cpu" = ia64; then hardcode_libdir_flag_spec_CXX='${wl}-R $libdir:/usr/lib:/lib' @@ -13415,7 +13975,13 @@ if test -z "$aix_libpath"; then aix_libpath="/usr/lib:/lib"; fi else # Determine the default libpath from the value encoded in an # empty executable. - cat confdefs.h - <<_ACEOF >conftest.$ac_ext + if test "${lt_cv_aix_libpath+set}" = set; then + aix_libpath=$lt_cv_aix_libpath +else + if ${lt_cv_aix_libpath__CXX+:} false; then : + $as_echo_n "(cached) " >&6 +else + cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ int @@ -13428,30 +13994,42 @@ main () _ACEOF if ac_fn_cxx_try_link "$LINENO"; then : -lt_aix_libpath_sed=' - /Import File Strings/,/^$/ { - /^0/ { - s/^0 *\(.*\)$/\1/ - p - } - }' -aix_libpath=`dump -H conftest$ac_exeext 2>/dev/null | $SED -n -e "$lt_aix_libpath_sed"` -# Check for a 64-bit object if we didn't find anything. -if test -z "$aix_libpath"; then - aix_libpath=`dump -HX64 conftest$ac_exeext 2>/dev/null | $SED -n -e "$lt_aix_libpath_sed"` -fi + lt_aix_libpath_sed=' + /Import File Strings/,/^$/ { + /^0/ { + s/^0 *\([^ ]*\) *$/\1/ + p + } + }' + lt_cv_aix_libpath__CXX=`dump -H conftest$ac_exeext 2>/dev/null | $SED -n -e "$lt_aix_libpath_sed"` + # Check for a 64-bit object if we didn't find anything. + if test -z "$lt_cv_aix_libpath__CXX"; then + lt_cv_aix_libpath__CXX=`dump -HX64 conftest$ac_exeext 2>/dev/null | $SED -n -e "$lt_aix_libpath_sed"` + fi fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext -if test -z "$aix_libpath"; then aix_libpath="/usr/lib:/lib"; fi + if test -z "$lt_cv_aix_libpath__CXX"; then + lt_cv_aix_libpath__CXX="/usr/lib:/lib" + fi + +fi + + aix_libpath=$lt_cv_aix_libpath__CXX +fi hardcode_libdir_flag_spec_CXX='${wl}-blibpath:$libdir:'"$aix_libpath" # Warning - without using the other run time loading flags, # -berok will link without error, but may produce a broken library. no_undefined_flag_CXX=' ${wl}-bernotok' allow_undefined_flag_CXX=' ${wl}-berok' - # Exported symbols can be pulled into shared objects from archives - whole_archive_flag_spec_CXX='$convenience' + if test "$with_gnu_ld" = yes; then + # We only use this code for GNU lds that support --whole-archive. + whole_archive_flag_spec_CXX='${wl}--whole-archive$convenience ${wl}--no-whole-archive' + else + # Exported symbols can be pulled into shared objects from archives + whole_archive_flag_spec_CXX='$convenience' + fi archive_cmds_need_lc_CXX=yes # This is similar to how AIX traditionally builds its shared # libraries. @@ -13481,28 +14059,75 @@ if test -z "$aix_libpath"; then aix_libpath="/usr/lib:/lib"; fi ;; cygwin* | mingw* | pw32* | cegcc*) - # _LT_TAGVAR(hardcode_libdir_flag_spec, CXX) is actually meaningless, - # as there is no search path for DLLs. - hardcode_libdir_flag_spec_CXX='-L$libdir' - allow_undefined_flag_CXX=unsupported - always_export_symbols_CXX=no - enable_shared_with_static_runtimes_CXX=yes - - if $LD --help 2>&1 | $GREP 'auto-import' > /dev/null; then - archive_cmds_CXX='$CC -shared -nostdlib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags -o $output_objdir/$soname ${wl}--enable-auto-image-base -Xlinker --out-implib -Xlinker $lib' - # If the export-symbols file already is a .def file (1st line - # is EXPORTS), use it as is; otherwise, prepend... - archive_expsym_cmds_CXX='if test "x`$SED 1q $export_symbols`" = xEXPORTS; then - cp $export_symbols $output_objdir/$soname.def; - else - echo EXPORTS > $output_objdir/$soname.def; - cat $export_symbols >> $output_objdir/$soname.def; - fi~ - $CC -shared -nostdlib $output_objdir/$soname.def $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags -o $output_objdir/$soname ${wl}--enable-auto-image-base -Xlinker --out-implib -Xlinker $lib' - else - ld_shlibs_CXX=no - fi - ;; + case $GXX,$cc_basename in + ,cl* | no,cl*) + # Native MSVC + # hardcode_libdir_flag_spec is actually meaningless, as there is + # no search path for DLLs. + hardcode_libdir_flag_spec_CXX=' ' + allow_undefined_flag_CXX=unsupported + always_export_symbols_CXX=yes + file_list_spec_CXX='@' + # Tell ltmain to make .lib files, not .a files. + libext=lib + # Tell ltmain to make .dll files, not .so files. + shrext_cmds=".dll" + # FIXME: Setting linknames here is a bad hack. + archive_cmds_CXX='$CC -o $output_objdir/$soname $libobjs $compiler_flags $deplibs -Wl,-dll~linknames=' + archive_expsym_cmds_CXX='if test "x`$SED 1q $export_symbols`" = xEXPORTS; then + $SED -n -e 's/\\\\\\\(.*\\\\\\\)/-link\\\ -EXPORT:\\\\\\\1/' -e '1\\\!p' < $export_symbols > $output_objdir/$soname.exp; + else + $SED -e 's/\\\\\\\(.*\\\\\\\)/-link\\\ -EXPORT:\\\\\\\1/' < $export_symbols > $output_objdir/$soname.exp; + fi~ + $CC -o $tool_output_objdir$soname $libobjs $compiler_flags $deplibs "@$tool_output_objdir$soname.exp" -Wl,-DLL,-IMPLIB:"$tool_output_objdir$libname.dll.lib"~ + linknames=' + # The linker will not automatically build a static lib if we build a DLL. + # _LT_TAGVAR(old_archive_from_new_cmds, CXX)='true' + enable_shared_with_static_runtimes_CXX=yes + # Don't use ranlib + old_postinstall_cmds_CXX='chmod 644 $oldlib' + postlink_cmds_CXX='lt_outputfile="@OUTPUT@"~ + lt_tool_outputfile="@TOOL_OUTPUT@"~ + case $lt_outputfile in + *.exe|*.EXE) ;; + *) + lt_outputfile="$lt_outputfile.exe" + lt_tool_outputfile="$lt_tool_outputfile.exe" + ;; + esac~ + func_to_tool_file "$lt_outputfile"~ + if test "$MANIFEST_TOOL" != ":" && test -f "$lt_outputfile.manifest"; then + $MANIFEST_TOOL -manifest "$lt_tool_outputfile.manifest" -outputresource:"$lt_tool_outputfile" || exit 1; + $RM "$lt_outputfile.manifest"; + fi' + ;; + *) + # g++ + # _LT_TAGVAR(hardcode_libdir_flag_spec, CXX) is actually meaningless, + # as there is no search path for DLLs. + hardcode_libdir_flag_spec_CXX='-L$libdir' + export_dynamic_flag_spec_CXX='${wl}--export-all-symbols' + allow_undefined_flag_CXX=unsupported + always_export_symbols_CXX=no + enable_shared_with_static_runtimes_CXX=yes + + if $LD --help 2>&1 | $GREP 'auto-import' > /dev/null; then + archive_cmds_CXX='$CC -shared -nostdlib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags -o $output_objdir/$soname ${wl}--enable-auto-image-base -Xlinker --out-implib -Xlinker $lib' + # If the export-symbols file already is a .def file (1st line + # is EXPORTS), use it as is; otherwise, prepend... + archive_expsym_cmds_CXX='if test "x`$SED 1q $export_symbols`" = xEXPORTS; then + cp $export_symbols $output_objdir/$soname.def; + else + echo EXPORTS > $output_objdir/$soname.def; + cat $export_symbols >> $output_objdir/$soname.def; + fi~ + $CC -shared -nostdlib $output_objdir/$soname.def $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags -o $output_objdir/$soname ${wl}--enable-auto-image-base -Xlinker --out-implib -Xlinker $lib' + else + ld_shlibs_CXX=no + fi + ;; + esac + ;; darwin* | rhapsody*) @@ -13510,7 +14135,12 @@ if test -z "$aix_libpath"; then aix_libpath="/usr/lib:/lib"; fi hardcode_direct_CXX=no hardcode_automatic_CXX=yes hardcode_shlibpath_var_CXX=unsupported - whole_archive_flag_spec_CXX='' + if test "$lt_cv_ld_force_load" = "yes"; then + whole_archive_flag_spec_CXX='`for conv in $convenience\"\"; do test -n \"$conv\" && new_convenience=\"$new_convenience ${wl}-force_load,$conv\"; done; func_echo_all \"$new_convenience\"`' + + else + whole_archive_flag_spec_CXX='' + fi link_all_deplibs_CXX=yes allow_undefined_flag_CXX="$_lt_dar_allow_undefined" case $cc_basename in @@ -13518,7 +14148,7 @@ if test -z "$aix_libpath"; then aix_libpath="/usr/lib:/lib"; fi *) _lt_dar_can_shared=$GCC ;; esac if test "$_lt_dar_can_shared" = "yes"; then - output_verbose_link_cmd=echo + output_verbose_link_cmd=func_echo_all archive_cmds_CXX="\$CC -dynamiclib \$allow_undefined_flag -o \$lib \$libobjs \$deplibs \$compiler_flags -install_name \$rpath/\$soname \$verstring $_lt_dar_single_mod${_lt_dsymutil}" module_cmds_CXX="\$CC \$allow_undefined_flag -o \$lib -bundle \$libobjs \$deplibs \$compiler_flags${_lt_dsymutil}" archive_expsym_cmds_CXX="sed 's,^,_,' < \$export_symbols > \$output_objdir/\${libname}-symbols.expsym~\$CC -dynamiclib \$allow_undefined_flag -o \$lib \$libobjs \$deplibs \$compiler_flags -install_name \$rpath/\$soname \$verstring ${_lt_dar_single_mod}${_lt_dar_export_syms}${_lt_dsymutil}" @@ -13552,7 +14182,7 @@ if test -z "$aix_libpath"; then aix_libpath="/usr/lib:/lib"; fi esac ;; - freebsd[12]*) + freebsd2.*) # C++ shared libraries reported to be fairly broken before # switch to ELF ld_shlibs_CXX=no @@ -13568,7 +14198,9 @@ if test -z "$aix_libpath"; then aix_libpath="/usr/lib:/lib"; fi ld_shlibs_CXX=yes ;; - gnu*) + haiku*) + archive_cmds_CXX='$CC -shared $libobjs $deplibs $compiler_flags ${wl}-soname $wl$soname -o $lib' + link_all_deplibs_CXX=yes ;; hpux9*) @@ -13595,11 +14227,11 @@ if test -z "$aix_libpath"; then aix_libpath="/usr/lib:/lib"; fi # explicitly linking system object files so we need to strip them # from the output so that they don't get included in the library # dependencies. - output_verbose_link_cmd='templist=`($CC -b $CFLAGS -v conftest.$objext 2>&1) | $EGREP "\-L"`; list=""; for z in $templist; do case $z in conftest.$objext) list="$list $z";; *.$objext);; *) list="$list $z";;esac; done; $ECHO "X$list" | $Xsed' + output_verbose_link_cmd='templist=`($CC -b $CFLAGS -v conftest.$objext 2>&1) | $EGREP "\-L"`; list=""; for z in $templist; do case $z in conftest.$objext) list="$list $z";; *.$objext);; *) list="$list $z";;esac; done; func_echo_all "$list"' ;; *) if test "$GXX" = yes; then - archive_cmds_CXX='$RM $output_objdir/$soname~$CC -shared -nostdlib -fPIC ${wl}+b ${wl}$install_libdir -o $output_objdir/$soname $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags~test $output_objdir/$soname = $lib || mv $output_objdir/$soname $lib' + archive_cmds_CXX='$RM $output_objdir/$soname~$CC -shared -nostdlib $pic_flag ${wl}+b ${wl}$install_libdir -o $output_objdir/$soname $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags~test $output_objdir/$soname = $lib || mv $output_objdir/$soname $lib' else # FIXME: insert proper C++ library support ld_shlibs_CXX=no @@ -13660,7 +14292,7 @@ if test -z "$aix_libpath"; then aix_libpath="/usr/lib:/lib"; fi # explicitly linking system object files so we need to strip them # from the output so that they don't get included in the library # dependencies. - output_verbose_link_cmd='templist=`($CC -b $CFLAGS -v conftest.$objext 2>&1) | $GREP "\-L"`; list=""; for z in $templist; do case $z in conftest.$objext) list="$list $z";; *.$objext);; *) list="$list $z";;esac; done; $ECHO "X$list" | $Xsed' + output_verbose_link_cmd='templist=`($CC -b $CFLAGS -v conftest.$objext 2>&1) | $GREP "\-L"`; list=""; for z in $templist; do case $z in conftest.$objext) list="$list $z";; *.$objext);; *) list="$list $z";;esac; done; func_echo_all "$list"' ;; *) if test "$GXX" = yes; then @@ -13670,10 +14302,10 @@ if test -z "$aix_libpath"; then aix_libpath="/usr/lib:/lib"; fi archive_cmds_CXX='$CC -shared -nostdlib -fPIC ${wl}+h ${wl}$soname -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags' ;; ia64*) - archive_cmds_CXX='$CC -shared -nostdlib -fPIC ${wl}+h ${wl}$soname ${wl}+nodefaultrpath -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags' + archive_cmds_CXX='$CC -shared -nostdlib $pic_flag ${wl}+h ${wl}$soname ${wl}+nodefaultrpath -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags' ;; *) - archive_cmds_CXX='$CC -shared -nostdlib -fPIC ${wl}+h ${wl}$soname ${wl}+b ${wl}$install_libdir -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags' + archive_cmds_CXX='$CC -shared -nostdlib $pic_flag ${wl}+h ${wl}$soname ${wl}+b ${wl}$install_libdir -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags' ;; esac fi @@ -13703,7 +14335,7 @@ if test -z "$aix_libpath"; then aix_libpath="/usr/lib:/lib"; fi case $cc_basename in CC*) # SGI C++ - archive_cmds_CXX='$CC -shared -all -multigot $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags -soname $soname `test -n "$verstring" && $ECHO "X-set_version $verstring" | $Xsed` -update_registry ${output_objdir}/so_locations -o $lib' + archive_cmds_CXX='$CC -shared -all -multigot $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags -soname $soname `test -n "$verstring" && func_echo_all "-set_version $verstring"` -update_registry ${output_objdir}/so_locations -o $lib' # Archives containing C++ object files must be created using # "CC -ar", where "CC" is the IRIX C++ compiler. This is @@ -13714,9 +14346,9 @@ if test -z "$aix_libpath"; then aix_libpath="/usr/lib:/lib"; fi *) if test "$GXX" = yes; then if test "$with_gnu_ld" = no; then - archive_cmds_CXX='$CC -shared -nostdlib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags ${wl}-soname ${wl}$soname `test -n "$verstring" && $ECHO "X${wl}-set_version ${wl}$verstring" | $Xsed` ${wl}-update_registry ${wl}${output_objdir}/so_locations -o $lib' + archive_cmds_CXX='$CC -shared $pic_flag -nostdlib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags ${wl}-soname ${wl}$soname `test -n "$verstring" && func_echo_all "${wl}-set_version ${wl}$verstring"` ${wl}-update_registry ${wl}${output_objdir}/so_locations -o $lib' else - archive_cmds_CXX='$CC -shared -nostdlib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags ${wl}-soname ${wl}$soname `test -n "$verstring" && $ECHO "X${wl}-set_version ${wl}$verstring" | $Xsed` -o $lib' + archive_cmds_CXX='$CC -shared $pic_flag -nostdlib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags ${wl}-soname ${wl}$soname `test -n "$verstring" && func_echo_all "${wl}-set_version ${wl}$verstring"` -o $lib' fi fi link_all_deplibs_CXX=yes @@ -13727,7 +14359,7 @@ if test -z "$aix_libpath"; then aix_libpath="/usr/lib:/lib"; fi inherit_rpath_CXX=yes ;; - linux* | k*bsd*-gnu | kopensolaris*-gnu) + linux* | k*bsd*-gnu | kopensolaris*-gnu | gnu*) case $cc_basename in KCC*) # Kuck and Associates, Inc. (KAI) C++ Compiler @@ -13745,7 +14377,7 @@ if test -z "$aix_libpath"; then aix_libpath="/usr/lib:/lib"; fi # explicitly linking system object files so we need to strip them # from the output so that they don't get included in the library # dependencies. - output_verbose_link_cmd='templist=`$CC $CFLAGS -v conftest.$objext -o libconftest$shared_ext 2>&1 | $GREP "ld"`; rm -f libconftest$shared_ext; list=""; for z in $templist; do case $z in conftest.$objext) list="$list $z";; *.$objext);; *) list="$list $z";;esac; done; $ECHO "X$list" | $Xsed' + output_verbose_link_cmd='templist=`$CC $CFLAGS -v conftest.$objext -o libconftest$shared_ext 2>&1 | $GREP "ld"`; rm -f libconftest$shared_ext; list=""; for z in $templist; do case $z in conftest.$objext) list="$list $z";; *.$objext);; *) list="$list $z";;esac; done; func_echo_all "$list"' hardcode_libdir_flag_spec_CXX='${wl}-rpath,$libdir' export_dynamic_flag_spec_CXX='${wl}--export-dynamic' @@ -13782,26 +14414,26 @@ if test -z "$aix_libpath"; then aix_libpath="/usr/lib:/lib"; fi pgCC* | pgcpp*) # Portland Group C++ compiler case `$CC -V` in - *pgCC\ [1-5]* | *pgcpp\ [1-5]*) + *pgCC\ [1-5].* | *pgcpp\ [1-5].*) prelink_cmds_CXX='tpldir=Template.dir~ rm -rf $tpldir~ $CC --prelink_objects --instantiation_dir $tpldir $objs $libobjs $compile_deplibs~ - compile_command="$compile_command `find $tpldir -name \*.o | $NL2SP`"' + compile_command="$compile_command `find $tpldir -name \*.o | sort | $NL2SP`"' old_archive_cmds_CXX='tpldir=Template.dir~ rm -rf $tpldir~ $CC --prelink_objects --instantiation_dir $tpldir $oldobjs$old_deplibs~ - $AR $AR_FLAGS $oldlib$oldobjs$old_deplibs `find $tpldir -name \*.o | $NL2SP`~ + $AR $AR_FLAGS $oldlib$oldobjs$old_deplibs `find $tpldir -name \*.o | sort | $NL2SP`~ $RANLIB $oldlib' archive_cmds_CXX='tpldir=Template.dir~ rm -rf $tpldir~ $CC --prelink_objects --instantiation_dir $tpldir $predep_objects $libobjs $deplibs $convenience $postdep_objects~ - $CC -shared $pic_flag $predep_objects $libobjs $deplibs `find $tpldir -name \*.o | $NL2SP` $postdep_objects $compiler_flags ${wl}-soname ${wl}$soname -o $lib' + $CC -shared $pic_flag $predep_objects $libobjs $deplibs `find $tpldir -name \*.o | sort | $NL2SP` $postdep_objects $compiler_flags ${wl}-soname ${wl}$soname -o $lib' archive_expsym_cmds_CXX='tpldir=Template.dir~ rm -rf $tpldir~ $CC --prelink_objects --instantiation_dir $tpldir $predep_objects $libobjs $deplibs $convenience $postdep_objects~ - $CC -shared $pic_flag $predep_objects $libobjs $deplibs `find $tpldir -name \*.o | $NL2SP` $postdep_objects $compiler_flags ${wl}-soname ${wl}$soname ${wl}-retain-symbols-file ${wl}$export_symbols -o $lib' + $CC -shared $pic_flag $predep_objects $libobjs $deplibs `find $tpldir -name \*.o | sort | $NL2SP` $postdep_objects $compiler_flags ${wl}-soname ${wl}$soname ${wl}-retain-symbols-file ${wl}$export_symbols -o $lib' ;; - *) # Version 6 will use weak symbols + *) # Version 6 and above use weak symbols archive_cmds_CXX='$CC -shared $pic_flag $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags ${wl}-soname ${wl}$soname -o $lib' archive_expsym_cmds_CXX='$CC -shared $pic_flag $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags ${wl}-soname ${wl}$soname ${wl}-retain-symbols-file ${wl}$export_symbols -o $lib' ;; @@ -13809,7 +14441,7 @@ if test -z "$aix_libpath"; then aix_libpath="/usr/lib:/lib"; fi hardcode_libdir_flag_spec_CXX='${wl}--rpath ${wl}$libdir' export_dynamic_flag_spec_CXX='${wl}--export-dynamic' - whole_archive_flag_spec_CXX='${wl}--whole-archive`for conv in $convenience\"\"; do test -n \"$conv\" && new_convenience=\"$new_convenience,$conv\"; done; $ECHO \"$new_convenience\"` ${wl}--no-whole-archive' + whole_archive_flag_spec_CXX='${wl}--whole-archive`for conv in $convenience\"\"; do test -n \"$conv\" && new_convenience=\"$new_convenience,$conv\"; done; func_echo_all \"$new_convenience\"` ${wl}--no-whole-archive' ;; cxx*) # Compaq C++ @@ -13828,9 +14460,9 @@ if test -z "$aix_libpath"; then aix_libpath="/usr/lib:/lib"; fi # explicitly linking system object files so we need to strip them # from the output so that they don't get included in the library # dependencies. - output_verbose_link_cmd='templist=`$CC -shared $CFLAGS -v conftest.$objext 2>&1 | $GREP "ld"`; templist=`$ECHO "X$templist" | $Xsed -e "s/\(^.*ld.*\)\( .*ld .*$\)/\1/"`; list=""; for z in $templist; do case $z in conftest.$objext) list="$list $z";; *.$objext);; *) list="$list $z";;esac; done; $ECHO "X$list" | $Xsed' + output_verbose_link_cmd='templist=`$CC -shared $CFLAGS -v conftest.$objext 2>&1 | $GREP "ld"`; templist=`func_echo_all "$templist" | $SED "s/\(^.*ld.*\)\( .*ld .*$\)/\1/"`; list=""; for z in $templist; do case $z in conftest.$objext) list="$list $z";; *.$objext);; *) list="$list $z";;esac; done; func_echo_all "X$list" | $Xsed' ;; - xl*) + xl* | mpixl* | bgxl*) # IBM XL 8.0 on PPC, with GNU ld hardcode_libdir_flag_spec_CXX='${wl}-rpath ${wl}$libdir' export_dynamic_flag_spec_CXX='${wl}--export-dynamic' @@ -13850,13 +14482,13 @@ if test -z "$aix_libpath"; then aix_libpath="/usr/lib:/lib"; fi archive_cmds_CXX='$CC -G${allow_undefined_flag} -h$soname -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags' archive_expsym_cmds_CXX='$CC -G${allow_undefined_flag} -h$soname -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags ${wl}-retain-symbols-file ${wl}$export_symbols' hardcode_libdir_flag_spec_CXX='-R$libdir' - whole_archive_flag_spec_CXX='${wl}--whole-archive`new_convenience=; for conv in $convenience\"\"; do test -z \"$conv\" || new_convenience=\"$new_convenience,$conv\"; done; $ECHO \"$new_convenience\"` ${wl}--no-whole-archive' + whole_archive_flag_spec_CXX='${wl}--whole-archive`new_convenience=; for conv in $convenience\"\"; do test -z \"$conv\" || new_convenience=\"$new_convenience,$conv\"; done; func_echo_all \"$new_convenience\"` ${wl}--no-whole-archive' compiler_needs_object_CXX=yes # Not sure whether something based on # $CC $CFLAGS -v conftest.$objext -o libconftest$shared_ext 2>&1 # would be better. - output_verbose_link_cmd='echo' + output_verbose_link_cmd='func_echo_all' # Archives containing C++ object files must be created using # "CC -xar", where "CC" is the Sun C++ compiler. This is @@ -13925,7 +14557,7 @@ if test -z "$aix_libpath"; then aix_libpath="/usr/lib:/lib"; fi export_dynamic_flag_spec_CXX='${wl}-E' whole_archive_flag_spec_CXX="$wlarc"'--whole-archive$convenience '"$wlarc"'--no-whole-archive' fi - output_verbose_link_cmd=echo + output_verbose_link_cmd=func_echo_all else ld_shlibs_CXX=no fi @@ -13960,15 +14592,15 @@ if test -z "$aix_libpath"; then aix_libpath="/usr/lib:/lib"; fi case $host in osf3*) allow_undefined_flag_CXX=' ${wl}-expect_unresolved ${wl}\*' - archive_cmds_CXX='$CC -shared${allow_undefined_flag} $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags ${wl}-soname $soname `test -n "$verstring" && $ECHO "X${wl}-set_version $verstring" | $Xsed` -update_registry ${output_objdir}/so_locations -o $lib' + archive_cmds_CXX='$CC -shared${allow_undefined_flag} $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags ${wl}-soname $soname `test -n "$verstring" && func_echo_all "${wl}-set_version $verstring"` -update_registry ${output_objdir}/so_locations -o $lib' hardcode_libdir_flag_spec_CXX='${wl}-rpath ${wl}$libdir' ;; *) allow_undefined_flag_CXX=' -expect_unresolved \*' - archive_cmds_CXX='$CC -shared${allow_undefined_flag} $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags -msym -soname $soname `test -n "$verstring" && $ECHO "X-set_version $verstring" | $Xsed` -update_registry ${output_objdir}/so_locations -o $lib' + archive_cmds_CXX='$CC -shared${allow_undefined_flag} $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags -msym -soname $soname `test -n "$verstring" && func_echo_all "-set_version $verstring"` -update_registry ${output_objdir}/so_locations -o $lib' archive_expsym_cmds_CXX='for i in `cat $export_symbols`; do printf "%s %s\\n" -exported_symbol "\$i" >> $lib.exp; done~ echo "-hidden">> $lib.exp~ - $CC -shared$allow_undefined_flag $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags -msym -soname $soname ${wl}-input ${wl}$lib.exp `test -n "$verstring" && $ECHO "X-set_version $verstring" | $Xsed` -update_registry ${output_objdir}/so_locations -o $lib~ + $CC -shared$allow_undefined_flag $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags -msym -soname $soname ${wl}-input ${wl}$lib.exp `test -n "$verstring" && $ECHO "-set_version $verstring"` -update_registry ${output_objdir}/so_locations -o $lib~ $RM $lib.exp' hardcode_libdir_flag_spec_CXX='-rpath $libdir' ;; @@ -13984,17 +14616,17 @@ if test -z "$aix_libpath"; then aix_libpath="/usr/lib:/lib"; fi # explicitly linking system object files so we need to strip them # from the output so that they don't get included in the library # dependencies. - output_verbose_link_cmd='templist=`$CC -shared $CFLAGS -v conftest.$objext 2>&1 | $GREP "ld" | $GREP -v "ld:"`; templist=`$ECHO "X$templist" | $Xsed -e "s/\(^.*ld.*\)\( .*ld.*$\)/\1/"`; list=""; for z in $templist; do case $z in conftest.$objext) list="$list $z";; *.$objext);; *) list="$list $z";;esac; done; $ECHO "X$list" | $Xsed' + output_verbose_link_cmd='templist=`$CC -shared $CFLAGS -v conftest.$objext 2>&1 | $GREP "ld" | $GREP -v "ld:"`; templist=`func_echo_all "$templist" | $SED "s/\(^.*ld.*\)\( .*ld.*$\)/\1/"`; list=""; for z in $templist; do case $z in conftest.$objext) list="$list $z";; *.$objext);; *) list="$list $z";;esac; done; func_echo_all "$list"' ;; *) if test "$GXX" = yes && test "$with_gnu_ld" = no; then allow_undefined_flag_CXX=' ${wl}-expect_unresolved ${wl}\*' case $host in osf3*) - archive_cmds_CXX='$CC -shared -nostdlib ${allow_undefined_flag} $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags ${wl}-soname ${wl}$soname `test -n "$verstring" && $ECHO "X${wl}-set_version ${wl}$verstring" | $Xsed` ${wl}-update_registry ${wl}${output_objdir}/so_locations -o $lib' + archive_cmds_CXX='$CC -shared -nostdlib ${allow_undefined_flag} $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags ${wl}-soname ${wl}$soname `test -n "$verstring" && func_echo_all "${wl}-set_version ${wl}$verstring"` ${wl}-update_registry ${wl}${output_objdir}/so_locations -o $lib' ;; *) - archive_cmds_CXX='$CC -shared -nostdlib ${allow_undefined_flag} $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags ${wl}-msym ${wl}-soname ${wl}$soname `test -n "$verstring" && $ECHO "${wl}-set_version ${wl}$verstring" | $Xsed` ${wl}-update_registry ${wl}${output_objdir}/so_locations -o $lib' + archive_cmds_CXX='$CC -shared $pic_flag -nostdlib ${allow_undefined_flag} $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags ${wl}-msym ${wl}-soname ${wl}$soname `test -n "$verstring" && func_echo_all "${wl}-set_version ${wl}$verstring"` ${wl}-update_registry ${wl}${output_objdir}/so_locations -o $lib' ;; esac @@ -14004,7 +14636,7 @@ if test -z "$aix_libpath"; then aix_libpath="/usr/lib:/lib"; fi # Commands to make compiler produce verbose output that lists # what "hidden" libraries, object files and flags are used when # linking a shared library. - output_verbose_link_cmd='$CC -shared $CFLAGS -v conftest.$objext 2>&1 | $GREP "\-L"' + output_verbose_link_cmd='$CC -shared $CFLAGS -v conftest.$objext 2>&1 | $GREP -v "^Configured with:" | $GREP "\-L"' else # FIXME: insert proper C++ library support @@ -14040,7 +14672,7 @@ if test -z "$aix_libpath"; then aix_libpath="/usr/lib:/lib"; fi solaris*) case $cc_basename in - CC*) + CC* | sunCC*) # Sun C++ 4.2, 5.x and Centerline C++ archive_cmds_need_lc_CXX=yes no_undefined_flag_CXX=' -zdefs' @@ -14061,7 +14693,7 @@ if test -z "$aix_libpath"; then aix_libpath="/usr/lib:/lib"; fi esac link_all_deplibs_CXX=yes - output_verbose_link_cmd='echo' + output_verbose_link_cmd='func_echo_all' # Archives containing C++ object files must be created using # "CC -xar", where "CC" is the Sun C++ compiler. This is @@ -14081,14 +14713,14 @@ if test -z "$aix_libpath"; then aix_libpath="/usr/lib:/lib"; fi if test "$GXX" = yes && test "$with_gnu_ld" = no; then no_undefined_flag_CXX=' ${wl}-z ${wl}defs' if $CC --version | $GREP -v '^2\.7' > /dev/null; then - archive_cmds_CXX='$CC -shared -nostdlib $LDFLAGS $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags ${wl}-h $wl$soname -o $lib' + archive_cmds_CXX='$CC -shared $pic_flag -nostdlib $LDFLAGS $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags ${wl}-h $wl$soname -o $lib' archive_expsym_cmds_CXX='echo "{ global:" > $lib.exp~cat $export_symbols | $SED -e "s/\(.*\)/\1;/" >> $lib.exp~echo "local: *; };" >> $lib.exp~ - $CC -shared -nostdlib ${wl}-M $wl$lib.exp -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags~$RM $lib.exp' + $CC -shared $pic_flag -nostdlib ${wl}-M $wl$lib.exp -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags~$RM $lib.exp' # Commands to make compiler produce verbose output that lists # what "hidden" libraries, object files and flags are used when # linking a shared library. - output_verbose_link_cmd='$CC -shared $CFLAGS -v conftest.$objext 2>&1 | $GREP "\-L"' + output_verbose_link_cmd='$CC -shared $CFLAGS -v conftest.$objext 2>&1 | $GREP -v "^Configured with:" | $GREP "\-L"' else # g++ 2.7 appears to require `-G' NOT `-shared' on this # platform. @@ -14099,7 +14731,7 @@ if test -z "$aix_libpath"; then aix_libpath="/usr/lib:/lib"; fi # Commands to make compiler produce verbose output that lists # what "hidden" libraries, object files and flags are used when # linking a shared library. - output_verbose_link_cmd='$CC -G $CFLAGS -v conftest.$objext 2>&1 | $GREP "\-L"' + output_verbose_link_cmd='$CC -G $CFLAGS -v conftest.$objext 2>&1 | $GREP -v "^Configured with:" | $GREP "\-L"' fi hardcode_libdir_flag_spec_CXX='${wl}-R $wl$libdir' @@ -14153,6 +14785,10 @@ if test -z "$aix_libpath"; then aix_libpath="/usr/lib:/lib"; fi CC*) archive_cmds_CXX='$CC -G ${wl}-h,$soname -o $lib $libobjs $deplibs $compiler_flags' archive_expsym_cmds_CXX='$CC -G ${wl}-Bexport:$export_symbols ${wl}-h,$soname -o $lib $libobjs $deplibs $compiler_flags' + old_archive_cmds_CXX='$CC -Tprelink_objects $oldobjs~ + '"$old_archive_cmds_CXX" + reload_cmds_CXX='$CC -Tprelink_objects $reload_objs~ + '"$reload_cmds_CXX" ;; *) archive_cmds_CXX='$CC -shared ${wl}-h,$soname -o $lib $libobjs $deplibs $compiler_flags' @@ -14214,6 +14850,14 @@ private: }; _LT_EOF + +_lt_libdeps_save_CFLAGS=$CFLAGS +case "$CC $CFLAGS " in #( +*\ -flto*\ *) CFLAGS="$CFLAGS -fno-lto" ;; +*\ -fwhopr*\ *) CFLAGS="$CFLAGS -fno-whopr" ;; +*\ -fuse-linker-plugin*\ *) CFLAGS="$CFLAGS -fno-use-linker-plugin" ;; +esac + if { { eval echo "\"\$as_me\":${as_lineno-$LINENO}: \"$ac_compile\""; } >&5 (eval $ac_compile) 2>&5 ac_status=$? @@ -14227,7 +14871,7 @@ if { { eval echo "\"\$as_me\":${as_lineno-$LINENO}: \"$ac_compile\""; } >&5 pre_test_object_deps_done=no for p in `eval "$output_verbose_link_cmd"`; do - case $p in + case ${prev}${p} in -L* | -R* | -l*) # Some compilers place space between "-{L,R}" and the path. @@ -14236,13 +14880,22 @@ if { { eval echo "\"\$as_me\":${as_lineno-$LINENO}: \"$ac_compile\""; } >&5 test $p = "-R"; then prev=$p continue - else - prev= fi + # Expand the sysroot to ease extracting the directories later. + if test -z "$prev"; then + case $p in + -L*) func_stripname_cnf '-L' '' "$p"; prev=-L; p=$func_stripname_result ;; + -R*) func_stripname_cnf '-R' '' "$p"; prev=-R; p=$func_stripname_result ;; + -l*) func_stripname_cnf '-l' '' "$p"; prev=-l; p=$func_stripname_result ;; + esac + fi + case $p in + =*) func_stripname_cnf '=' '' "$p"; p=$lt_sysroot$func_stripname_result ;; + esac if test "$pre_test_object_deps_done" = no; then - case $p in - -L* | -R*) + case ${prev} in + -L | -R) # Internal compiler library paths should come after those # provided the user. The postdeps already come after the # user supplied libs so there is no need to process them. @@ -14262,8 +14915,10 @@ if { { eval echo "\"\$as_me\":${as_lineno-$LINENO}: \"$ac_compile\""; } >&5 postdeps_CXX="${postdeps_CXX} ${prev}${p}" fi fi + prev= ;; + *.lto.$objext) ;; # Ignore GCC LTO objects *.$objext) # This assumes that the test object file only shows up # once in the compiler output. @@ -14299,6 +14954,7 @@ else fi $RM -f confest.$objext +CFLAGS=$_lt_libdeps_save_CFLAGS # PORTME: override above test on systems where it is broken case $host_os in @@ -14334,7 +14990,7 @@ linux*) solaris*) case $cc_basename in - CC*) + CC* | sunCC*) # The more standards-conforming stlport4 library is # incompatible with the Cstd library. Avoid specifying # it if it's in CXXFLAGS. Ignore libCrun as @@ -14399,8 +15055,6 @@ fi lt_prog_compiler_pic_CXX= lt_prog_compiler_static_CXX= -{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $compiler option to produce PIC" >&5 -$as_echo_n "checking for $compiler option to produce PIC... " >&6; } # C++ specific cases for pic, static, wl, etc. if test "$GXX" = yes; then @@ -14450,6 +15104,11 @@ $as_echo_n "checking for $compiler option to produce PIC... " >&6; } # DJGPP does not support shared libraries at all lt_prog_compiler_pic_CXX= ;; + haiku*) + # PIC is the default for Haiku. + # The "-static" flag exists, but is broken. + lt_prog_compiler_static_CXX= + ;; interix[3-9]*) # Interix 3.x gcc -fpic/-fPIC options generate broken code. # Instead, we relocate shared libraries at runtime. @@ -14499,6 +15158,11 @@ $as_echo_n "checking for $compiler option to produce PIC... " >&6; } ;; esac ;; + mingw* | cygwin* | os2* | pw32* | cegcc*) + # This hack is so that the source file can tell whether it is being + # built for inclusion in a dll (and should export symbols for example). + lt_prog_compiler_pic_CXX='-DDLL_EXPORT' + ;; dgux*) case $cc_basename in ec++*) @@ -14555,7 +15219,7 @@ $as_echo_n "checking for $compiler option to produce PIC... " >&6; } ;; esac ;; - linux* | k*bsd*-gnu | kopensolaris*-gnu) + linux* | k*bsd*-gnu | kopensolaris*-gnu | gnu*) case $cc_basename in KCC*) # KAI C++ Compiler @@ -14588,8 +15252,8 @@ $as_echo_n "checking for $compiler option to produce PIC... " >&6; } lt_prog_compiler_pic_CXX= lt_prog_compiler_static_CXX='-non_shared' ;; - xlc* | xlC*) - # IBM XL 8.0 on PPC + xlc* | xlC* | bgxl[cC]* | mpixl[cC]*) + # IBM XL 8.0, 9.0 on PPC and BlueGene lt_prog_compiler_wl_CXX='-Wl,' lt_prog_compiler_pic_CXX='-qpic' lt_prog_compiler_static_CXX='-qstaticlink' @@ -14651,7 +15315,7 @@ $as_echo_n "checking for $compiler option to produce PIC... " >&6; } ;; solaris*) case $cc_basename in - CC*) + CC* | sunCC*) # Sun C++ 4.2, 5.x and Centerline C++ lt_prog_compiler_pic_CXX='-KPIC' lt_prog_compiler_static_CXX='-Bstatic' @@ -14716,10 +15380,17 @@ case $host_os in lt_prog_compiler_pic_CXX="$lt_prog_compiler_pic_CXX -DPIC" ;; esac -{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $lt_prog_compiler_pic_CXX" >&5 -$as_echo "$lt_prog_compiler_pic_CXX" >&6; } - +{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $compiler option to produce PIC" >&5 +$as_echo_n "checking for $compiler option to produce PIC... " >&6; } +if ${lt_cv_prog_compiler_pic_CXX+:} false; then : + $as_echo_n "(cached) " >&6 +else + lt_cv_prog_compiler_pic_CXX=$lt_prog_compiler_pic_CXX +fi +{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $lt_cv_prog_compiler_pic_CXX" >&5 +$as_echo "$lt_cv_prog_compiler_pic_CXX" >&6; } +lt_prog_compiler_pic_CXX=$lt_cv_prog_compiler_pic_CXX # # Check to make sure the PIC flag actually works. @@ -14727,7 +15398,7 @@ $as_echo "$lt_prog_compiler_pic_CXX" >&6; } if test -n "$lt_prog_compiler_pic_CXX"; then { $as_echo "$as_me:${as_lineno-$LINENO}: checking if $compiler PIC flag $lt_prog_compiler_pic_CXX works" >&5 $as_echo_n "checking if $compiler PIC flag $lt_prog_compiler_pic_CXX works... " >&6; } -if test "${lt_cv_prog_compiler_pic_works_CXX+set}" = set; then : +if ${lt_cv_prog_compiler_pic_works_CXX+:} false; then : $as_echo_n "(cached) " >&6 else lt_cv_prog_compiler_pic_works_CXX=no @@ -14743,15 +15414,15 @@ else -e 's:.*FLAGS}\{0,1\} :&$lt_compiler_flag :; t' \ -e 's: [^ ]*conftest\.: $lt_compiler_flag&:; t' \ -e 's:$: $lt_compiler_flag:'` - (eval echo "\"\$as_me:14746: $lt_compile\"" >&5) + (eval echo "\"\$as_me:$LINENO: $lt_compile\"" >&5) (eval "$lt_compile" 2>conftest.err) ac_status=$? cat conftest.err >&5 - echo "$as_me:14750: \$? = $ac_status" >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 if (exit $ac_status) && test -s "$ac_outfile"; then # The compiler can only warn and ignore the option if not recognized # So say no if there are warnings other than the usual output. - $ECHO "X$_lt_compiler_boilerplate" | $Xsed -e '/^$/d' >conftest.exp + $ECHO "$_lt_compiler_boilerplate" | $SED '/^$/d' >conftest.exp $SED '/^$/d; /^ *+/d' conftest.err >conftest.er2 if test ! -s conftest.er2 || diff conftest.exp conftest.er2 >/dev/null; then lt_cv_prog_compiler_pic_works_CXX=yes @@ -14777,13 +15448,15 @@ fi + + # # Check to make sure the static flag actually works. # wl=$lt_prog_compiler_wl_CXX eval lt_tmp_static_flag=\"$lt_prog_compiler_static_CXX\" { $as_echo "$as_me:${as_lineno-$LINENO}: checking if $compiler static flag $lt_tmp_static_flag works" >&5 $as_echo_n "checking if $compiler static flag $lt_tmp_static_flag works... " >&6; } -if test "${lt_cv_prog_compiler_static_works_CXX+set}" = set; then : +if ${lt_cv_prog_compiler_static_works_CXX+:} false; then : $as_echo_n "(cached) " >&6 else lt_cv_prog_compiler_static_works_CXX=no @@ -14796,7 +15469,7 @@ else if test -s conftest.err; then # Append any errors to the config.log. cat conftest.err 1>&5 - $ECHO "X$_lt_linker_boilerplate" | $Xsed -e '/^$/d' > conftest.exp + $ECHO "$_lt_linker_boilerplate" | $SED '/^$/d' > conftest.exp $SED '/^$/d; /^ *+/d' conftest.err >conftest.er2 if diff conftest.exp conftest.er2 >/dev/null; then lt_cv_prog_compiler_static_works_CXX=yes @@ -14823,7 +15496,7 @@ fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking if $compiler supports -c -o file.$ac_objext" >&5 $as_echo_n "checking if $compiler supports -c -o file.$ac_objext... " >&6; } -if test "${lt_cv_prog_compiler_c_o_CXX+set}" = set; then : +if ${lt_cv_prog_compiler_c_o_CXX+:} false; then : $as_echo_n "(cached) " >&6 else lt_cv_prog_compiler_c_o_CXX=no @@ -14842,16 +15515,16 @@ else -e 's:.*FLAGS}\{0,1\} :&$lt_compiler_flag :; t' \ -e 's: [^ ]*conftest\.: $lt_compiler_flag&:; t' \ -e 's:$: $lt_compiler_flag:'` - (eval echo "\"\$as_me:14845: $lt_compile\"" >&5) + (eval echo "\"\$as_me:$LINENO: $lt_compile\"" >&5) (eval "$lt_compile" 2>out/conftest.err) ac_status=$? cat out/conftest.err >&5 - echo "$as_me:14849: \$? = $ac_status" >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 if (exit $ac_status) && test -s out/conftest2.$ac_objext then # The compiler can only warn and ignore the option if not recognized # So say no if there are warnings - $ECHO "X$_lt_compiler_boilerplate" | $Xsed -e '/^$/d' > out/conftest.exp + $ECHO "$_lt_compiler_boilerplate" | $SED '/^$/d' > out/conftest.exp $SED '/^$/d; /^ *+/d' out/conftest.err >out/conftest.er2 if test ! -s out/conftest.er2 || diff out/conftest.exp out/conftest.er2 >/dev/null; then lt_cv_prog_compiler_c_o_CXX=yes @@ -14875,7 +15548,7 @@ $as_echo "$lt_cv_prog_compiler_c_o_CXX" >&6; } { $as_echo "$as_me:${as_lineno-$LINENO}: checking if $compiler supports -c -o file.$ac_objext" >&5 $as_echo_n "checking if $compiler supports -c -o file.$ac_objext... " >&6; } -if test "${lt_cv_prog_compiler_c_o_CXX+set}" = set; then : +if ${lt_cv_prog_compiler_c_o_CXX+:} false; then : $as_echo_n "(cached) " >&6 else lt_cv_prog_compiler_c_o_CXX=no @@ -14894,16 +15567,16 @@ else -e 's:.*FLAGS}\{0,1\} :&$lt_compiler_flag :; t' \ -e 's: [^ ]*conftest\.: $lt_compiler_flag&:; t' \ -e 's:$: $lt_compiler_flag:'` - (eval echo "\"\$as_me:14897: $lt_compile\"" >&5) + (eval echo "\"\$as_me:$LINENO: $lt_compile\"" >&5) (eval "$lt_compile" 2>out/conftest.err) ac_status=$? cat out/conftest.err >&5 - echo "$as_me:14901: \$? = $ac_status" >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 if (exit $ac_status) && test -s out/conftest2.$ac_objext then # The compiler can only warn and ignore the option if not recognized # So say no if there are warnings - $ECHO "X$_lt_compiler_boilerplate" | $Xsed -e '/^$/d' > out/conftest.exp + $ECHO "$_lt_compiler_boilerplate" | $SED '/^$/d' > out/conftest.exp $SED '/^$/d; /^ *+/d' out/conftest.err >out/conftest.er2 if test ! -s out/conftest.er2 || diff out/conftest.exp out/conftest.er2 >/dev/null; then lt_cv_prog_compiler_c_o_CXX=yes @@ -14954,30 +15627,40 @@ fi $as_echo_n "checking whether the $compiler linker ($LD) supports shared libraries... " >&6; } export_symbols_cmds_CXX='$NM $libobjs $convenience | $global_symbol_pipe | $SED '\''s/.* //'\'' | sort | uniq > $export_symbols' + exclude_expsyms_CXX='_GLOBAL_OFFSET_TABLE_|_GLOBAL__F[ID]_.*' case $host_os in aix[4-9]*) # If we're using GNU nm, then we don't want the "-C" option. # -C means demangle to AIX nm, but means don't demangle with GNU nm + # Also, AIX nm treats weak defined symbols like other global defined + # symbols, whereas GNU nm marks them as "W". if $NM -V 2>&1 | $GREP 'GNU' > /dev/null; then - export_symbols_cmds_CXX='$NM -Bpg $libobjs $convenience | awk '\''{ if (((\$ 2 == "T") || (\$ 2 == "D") || (\$ 2 == "B")) && (substr(\$ 3,1,1) != ".")) { print \$ 3 } }'\'' | sort -u > $export_symbols' + export_symbols_cmds_CXX='$NM -Bpg $libobjs $convenience | awk '\''{ if (((\$ 2 == "T") || (\$ 2 == "D") || (\$ 2 == "B") || (\$ 2 == "W")) && (substr(\$ 3,1,1) != ".")) { print \$ 3 } }'\'' | sort -u > $export_symbols' else export_symbols_cmds_CXX='$NM -BCpg $libobjs $convenience | awk '\''{ if (((\$ 2 == "T") || (\$ 2 == "D") || (\$ 2 == "B")) && (substr(\$ 3,1,1) != ".")) { print \$ 3 } }'\'' | sort -u > $export_symbols' fi ;; pw32*) export_symbols_cmds_CXX="$ltdll_cmds" - ;; + ;; cygwin* | mingw* | cegcc*) - export_symbols_cmds_CXX='$NM $libobjs $convenience | $global_symbol_pipe | $SED -e '\''/^[BCDGRS][ ]/s/.*[ ]\([^ ]*\)/\1 DATA/;/^.*[ ]__nm__/s/^.*[ ]__nm__\([^ ]*\)[ ][^ ]*/\1 DATA/;/^I[ ]/d;/^[AITW][ ]/s/.* //'\'' | sort | uniq > $export_symbols' - ;; - linux* | k*bsd*-gnu) + case $cc_basename in + cl*) + exclude_expsyms_CXX='_NULL_IMPORT_DESCRIPTOR|_IMPORT_DESCRIPTOR_.*' + ;; + *) + export_symbols_cmds_CXX='$NM $libobjs $convenience | $global_symbol_pipe | $SED -e '\''/^[BCDGRS][ ]/s/.*[ ]\([^ ]*\)/\1 DATA/;s/^.*[ ]__nm__\([^ ]*\)[ ][^ ]*/\1 DATA/;/^I[ ]/d;/^[AITW][ ]/s/.* //'\'' | sort | uniq > $export_symbols' + exclude_expsyms_CXX='[_]+GLOBAL_OFFSET_TABLE_|[_]+GLOBAL__[FID]_.*|[_]+head_[A-Za-z0-9_]+_dll|[A-Za-z0-9_]+_dll_iname' + ;; + esac + ;; + linux* | k*bsd*-gnu | gnu*) link_all_deplibs_CXX=no - ;; + ;; *) export_symbols_cmds_CXX='$NM $libobjs $convenience | $global_symbol_pipe | $SED '\''s/.* //'\'' | sort | uniq > $export_symbols' - ;; + ;; esac - exclude_expsyms_CXX='_GLOBAL_OFFSET_TABLE_|_GLOBAL__F[ID]_.*' { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ld_shlibs_CXX" >&5 $as_echo "$ld_shlibs_CXX" >&6; } @@ -15009,44 +15692,50 @@ x|xyes) # to ld, don't add -lc before -lgcc. { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether -lc should be explicitly linked in" >&5 $as_echo_n "checking whether -lc should be explicitly linked in... " >&6; } - $RM conftest* - echo "$lt_simple_compile_test_code" > conftest.$ac_ext +if ${lt_cv_archive_cmds_need_lc_CXX+:} false; then : + $as_echo_n "(cached) " >&6 +else + $RM conftest* + echo "$lt_simple_compile_test_code" > conftest.$ac_ext - if { { eval echo "\"\$as_me\":${as_lineno-$LINENO}: \"$ac_compile\""; } >&5 + if { { eval echo "\"\$as_me\":${as_lineno-$LINENO}: \"$ac_compile\""; } >&5 (eval $ac_compile) 2>&5 ac_status=$? $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; } 2>conftest.err; then - soname=conftest - lib=conftest - libobjs=conftest.$ac_objext - deplibs= - wl=$lt_prog_compiler_wl_CXX - pic_flag=$lt_prog_compiler_pic_CXX - compiler_flags=-v - linker_flags=-v - verstring= - output_objdir=. - libname=conftest - lt_save_allow_undefined_flag=$allow_undefined_flag_CXX - allow_undefined_flag_CXX= - if { { eval echo "\"\$as_me\":${as_lineno-$LINENO}: \"$archive_cmds_CXX 2\>\&1 \| $GREP \" -lc \" \>/dev/null 2\>\&1\""; } >&5 + soname=conftest + lib=conftest + libobjs=conftest.$ac_objext + deplibs= + wl=$lt_prog_compiler_wl_CXX + pic_flag=$lt_prog_compiler_pic_CXX + compiler_flags=-v + linker_flags=-v + verstring= + output_objdir=. + libname=conftest + lt_save_allow_undefined_flag=$allow_undefined_flag_CXX + allow_undefined_flag_CXX= + if { { eval echo "\"\$as_me\":${as_lineno-$LINENO}: \"$archive_cmds_CXX 2\>\&1 \| $GREP \" -lc \" \>/dev/null 2\>\&1\""; } >&5 (eval $archive_cmds_CXX 2\>\&1 \| $GREP \" -lc \" \>/dev/null 2\>\&1) 2>&5 ac_status=$? $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; } - then - archive_cmds_need_lc_CXX=no - else - archive_cmds_need_lc_CXX=yes - fi - allow_undefined_flag_CXX=$lt_save_allow_undefined_flag - else - cat conftest.err 1>&5 - fi - $RM conftest* - { $as_echo "$as_me:${as_lineno-$LINENO}: result: $archive_cmds_need_lc_CXX" >&5 -$as_echo "$archive_cmds_need_lc_CXX" >&6; } + then + lt_cv_archive_cmds_need_lc_CXX=no + else + lt_cv_archive_cmds_need_lc_CXX=yes + fi + allow_undefined_flag_CXX=$lt_save_allow_undefined_flag + else + cat conftest.err 1>&5 + fi + $RM conftest* + +fi +{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $lt_cv_archive_cmds_need_lc_CXX" >&5 +$as_echo "$lt_cv_archive_cmds_need_lc_CXX" >&6; } + archive_cmds_need_lc_CXX=$lt_cv_archive_cmds_need_lc_CXX ;; esac fi @@ -15111,8 +15800,6 @@ esac - - @@ -15141,7 +15828,7 @@ need_version=unknown case $host_os in aix3*) - version_type=linux + version_type=linux # correct to gnu/linux during the next big refactor library_names_spec='${libname}${release}${shared_ext}$versuffix $libname.a' shlibpath_var=LIBPATH @@ -15150,7 +15837,7 @@ aix3*) ;; aix[4-9]*) - version_type=linux + version_type=linux # correct to gnu/linux during the next big refactor need_lib_prefix=no need_version=no hardcode_into_libs=yes @@ -15203,7 +15890,7 @@ amigaos*) m68k) library_names_spec='$libname.ixlibrary $libname.a' # Create ${libname}_ixlibrary.a entries in /sys/libs. - finish_eval='for lib in `ls $libdir/*.ixlibrary 2>/dev/null`; do libname=`$ECHO "X$lib" | $Xsed -e '\''s%^.*/\([^/]*\)\.ixlibrary$%\1%'\''`; test $RM /sys/libs/${libname}_ixlibrary.a; $show "cd /sys/libs && $LN_S $lib ${libname}_ixlibrary.a"; cd /sys/libs && $LN_S $lib ${libname}_ixlibrary.a || exit 1; done' + finish_eval='for lib in `ls $libdir/*.ixlibrary 2>/dev/null`; do libname=`func_echo_all "$lib" | $SED '\''s%^.*/\([^/]*\)\.ixlibrary$%\1%'\''`; test $RM /sys/libs/${libname}_ixlibrary.a; $show "cd /sys/libs && $LN_S $lib ${libname}_ixlibrary.a"; cd /sys/libs && $LN_S $lib ${libname}_ixlibrary.a || exit 1; done' ;; esac ;; @@ -15215,7 +15902,7 @@ beos*) ;; bsdi[45]*) - version_type=linux + version_type=linux # correct to gnu/linux during the next big refactor need_version=no library_names_spec='${libname}${release}${shared_ext}$versuffix ${libname}${release}${shared_ext}$major $libname${shared_ext}' soname_spec='${libname}${release}${shared_ext}$major' @@ -15234,8 +15921,9 @@ cygwin* | mingw* | pw32* | cegcc*) need_version=no need_lib_prefix=no - case $GCC,$host_os in - yes,cygwin* | yes,mingw* | yes,pw32* | yes,cegcc*) + case $GCC,$cc_basename in + yes,*) + # gcc library_names_spec='$libname.dll.a' # DLL is installed to $(libdir)/../bin by postinstall_cmds postinstall_cmds='base_file=`basename \${file}`~ @@ -15256,36 +15944,82 @@ cygwin* | mingw* | pw32* | cegcc*) cygwin*) # Cygwin DLLs use 'cyg' prefix rather than 'lib' soname_spec='`echo ${libname} | sed -e 's/^lib/cyg/'``echo ${release} | $SED -e 's/[.]/-/g'`${versuffix}${shared_ext}' - sys_lib_search_path_spec="/usr/lib /lib/w32api /lib /usr/local/lib" + ;; mingw* | cegcc*) # MinGW DLLs use traditional 'lib' prefix soname_spec='${libname}`echo ${release} | $SED -e 's/[.]/-/g'`${versuffix}${shared_ext}' - sys_lib_search_path_spec=`$CC -print-search-dirs | $GREP "^libraries:" | $SED -e "s/^libraries://" -e "s,=/,/,g"` - if $ECHO "$sys_lib_search_path_spec" | $GREP ';[c-zC-Z]:/' >/dev/null; then - # It is most probably a Windows format PATH printed by - # mingw gcc, but we are running on Cygwin. Gcc prints its search - # path with ; separators, and with drive letters. We can handle the - # drive letters (cygwin fileutils understands them), so leave them, - # especially as we might pass files found there to a mingw objdump, - # which wouldn't understand a cygwinified path. Ahh. - sys_lib_search_path_spec=`$ECHO "$sys_lib_search_path_spec" | $SED -e 's/;/ /g'` - else - sys_lib_search_path_spec=`$ECHO "$sys_lib_search_path_spec" | $SED -e "s/$PATH_SEPARATOR/ /g"` - fi ;; pw32*) # pw32 DLLs use 'pw' prefix rather than 'lib' library_names_spec='`echo ${libname} | sed -e 's/^lib/pw/'``echo ${release} | $SED -e 's/[.]/-/g'`${versuffix}${shared_ext}' ;; esac + dynamic_linker='Win32 ld.exe' + ;; + + *,cl*) + # Native MSVC + libname_spec='$name' + soname_spec='${libname}`echo ${release} | $SED -e 's/[.]/-/g'`${versuffix}${shared_ext}' + library_names_spec='${libname}.dll.lib' + + case $build_os in + mingw*) + sys_lib_search_path_spec= + lt_save_ifs=$IFS + IFS=';' + for lt_path in $LIB + do + IFS=$lt_save_ifs + # Let DOS variable expansion print the short 8.3 style file name. + lt_path=`cd "$lt_path" 2>/dev/null && cmd //C "for %i in (".") do @echo %~si"` + sys_lib_search_path_spec="$sys_lib_search_path_spec $lt_path" + done + IFS=$lt_save_ifs + # Convert to MSYS style. + sys_lib_search_path_spec=`$ECHO "$sys_lib_search_path_spec" | sed -e 's|\\\\|/|g' -e 's| \\([a-zA-Z]\\):| /\\1|g' -e 's|^ ||'` + ;; + cygwin*) + # Convert to unix form, then to dos form, then back to unix form + # but this time dos style (no spaces!) so that the unix form looks + # like /cygdrive/c/PROGRA~1:/cygdr... + sys_lib_search_path_spec=`cygpath --path --unix "$LIB"` + sys_lib_search_path_spec=`cygpath --path --dos "$sys_lib_search_path_spec" 2>/dev/null` + sys_lib_search_path_spec=`cygpath --path --unix "$sys_lib_search_path_spec" | $SED -e "s/$PATH_SEPARATOR/ /g"` + ;; + *) + sys_lib_search_path_spec="$LIB" + if $ECHO "$sys_lib_search_path_spec" | $GREP ';[c-zC-Z]:/' >/dev/null; then + # It is most probably a Windows format PATH. + sys_lib_search_path_spec=`$ECHO "$sys_lib_search_path_spec" | $SED -e 's/;/ /g'` + else + sys_lib_search_path_spec=`$ECHO "$sys_lib_search_path_spec" | $SED -e "s/$PATH_SEPARATOR/ /g"` + fi + # FIXME: find the short name or the path components, as spaces are + # common. (e.g. "Program Files" -> "PROGRA~1") + ;; + esac + + # DLL is installed to $(libdir)/../bin by postinstall_cmds + postinstall_cmds='base_file=`basename \${file}`~ + dlpath=`$SHELL 2>&1 -c '\''. $dir/'\''\${base_file}'\''i; echo \$dlname'\''`~ + dldir=$destdir/`dirname \$dlpath`~ + test -d \$dldir || mkdir -p \$dldir~ + $install_prog $dir/$dlname \$dldir/$dlname' + postuninstall_cmds='dldll=`$SHELL 2>&1 -c '\''. $file; echo \$dlname'\''`~ + dlpath=$dir/\$dldll~ + $RM \$dlpath' + shlibpath_overrides_runpath=yes + dynamic_linker='Win32 link.exe' ;; *) + # Assume MSVC wrapper library_names_spec='${libname}`echo ${release} | $SED -e 's/[.]/-/g'`${versuffix}${shared_ext} $libname.lib' + dynamic_linker='Win32 ld.exe' ;; esac - dynamic_linker='Win32 ld.exe' # FIXME: first we should search . and the directory the executable is in shlibpath_var=PATH ;; @@ -15305,7 +16039,7 @@ darwin* | rhapsody*) ;; dgux*) - version_type=linux + version_type=linux # correct to gnu/linux during the next big refactor need_lib_prefix=no need_version=no library_names_spec='${libname}${release}${shared_ext}$versuffix ${libname}${release}${shared_ext}$major $libname$shared_ext' @@ -15313,10 +16047,6 @@ dgux*) shlibpath_var=LD_LIBRARY_PATH ;; -freebsd1*) - dynamic_linker=no - ;; - freebsd* | dragonfly*) # DragonFly does not have aout. When/if they implement a new # versioning mechanism, adjust this. @@ -15324,7 +16054,7 @@ freebsd* | dragonfly*) objformat=`/usr/bin/objformat` else case $host_os in - freebsd[123]*) objformat=aout ;; + freebsd[23].*) objformat=aout ;; *) objformat=elf ;; esac fi @@ -15342,7 +16072,7 @@ freebsd* | dragonfly*) esac shlibpath_var=LD_LIBRARY_PATH case $host_os in - freebsd2*) + freebsd2.*) shlibpath_overrides_runpath=yes ;; freebsd3.[01]* | freebsdelf3.[01]*) @@ -15361,13 +16091,16 @@ freebsd* | dragonfly*) esac ;; -gnu*) - version_type=linux +haiku*) + version_type=linux # correct to gnu/linux during the next big refactor need_lib_prefix=no need_version=no + dynamic_linker="$host_os runtime_loader" library_names_spec='${libname}${release}${shared_ext}$versuffix ${libname}${release}${shared_ext}${major} ${libname}${shared_ext}' soname_spec='${libname}${release}${shared_ext}$major' - shlibpath_var=LD_LIBRARY_PATH + shlibpath_var=LIBRARY_PATH + shlibpath_overrides_runpath=yes + sys_lib_dlsearch_path_spec='/boot/home/config/lib /boot/common/lib /boot/system/lib' hardcode_into_libs=yes ;; @@ -15413,12 +16146,14 @@ hpux9* | hpux10* | hpux11*) soname_spec='${libname}${release}${shared_ext}$major' ;; esac - # HP-UX runs *really* slowly unless shared libraries are mode 555. + # HP-UX runs *really* slowly unless shared libraries are mode 555, ... postinstall_cmds='chmod 555 $lib' + # or fails outright, so override atomically: + install_override_mode=555 ;; interix[3-9]*) - version_type=linux + version_type=linux # correct to gnu/linux during the next big refactor need_lib_prefix=no need_version=no library_names_spec='${libname}${release}${shared_ext}$versuffix ${libname}${release}${shared_ext}$major ${libname}${shared_ext}' @@ -15434,7 +16169,7 @@ irix5* | irix6* | nonstopux*) nonstopux*) version_type=nonstopux ;; *) if test "$lt_cv_prog_gnu_ld" = yes; then - version_type=linux + version_type=linux # correct to gnu/linux during the next big refactor else version_type=irix fi ;; @@ -15471,9 +16206,9 @@ linux*oldld* | linux*aout* | linux*coff*) dynamic_linker=no ;; -# This must be Linux ELF. -linux* | k*bsd*-gnu | kopensolaris*-gnu) - version_type=linux +# This must be glibc/ELF. +linux* | k*bsd*-gnu | kopensolaris*-gnu | gnu*) + version_type=linux # correct to gnu/linux during the next big refactor need_lib_prefix=no need_version=no library_names_spec='${libname}${release}${shared_ext}$versuffix ${libname}${release}${shared_ext}$major $libname${shared_ext}' @@ -15481,12 +16216,17 @@ linux* | k*bsd*-gnu | kopensolaris*-gnu) finish_cmds='PATH="\$PATH:/sbin" ldconfig -n $libdir' shlibpath_var=LD_LIBRARY_PATH shlibpath_overrides_runpath=no + # Some binutils ld are patched to set DT_RUNPATH - save_LDFLAGS=$LDFLAGS - save_libdir=$libdir - eval "libdir=/foo; wl=\"$lt_prog_compiler_wl_CXX\"; \ - LDFLAGS=\"\$LDFLAGS $hardcode_libdir_flag_spec_CXX\"" - cat confdefs.h - <<_ACEOF >conftest.$ac_ext + if ${lt_cv_shlibpath_overrides_runpath+:} false; then : + $as_echo_n "(cached) " >&6 +else + lt_cv_shlibpath_overrides_runpath=no + save_LDFLAGS=$LDFLAGS + save_libdir=$libdir + eval "libdir=/foo; wl=\"$lt_prog_compiler_wl_CXX\"; \ + LDFLAGS=\"\$LDFLAGS $hardcode_libdir_flag_spec_CXX\"" + cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ int @@ -15499,13 +16239,17 @@ main () _ACEOF if ac_fn_cxx_try_link "$LINENO"; then : if ($OBJDUMP -p conftest$ac_exeext) 2>/dev/null | grep "RUNPATH.*$libdir" >/dev/null; then : - shlibpath_overrides_runpath=yes + lt_cv_shlibpath_overrides_runpath=yes fi fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext - LDFLAGS=$save_LDFLAGS - libdir=$save_libdir + LDFLAGS=$save_LDFLAGS + libdir=$save_libdir + +fi + + shlibpath_overrides_runpath=$lt_cv_shlibpath_overrides_runpath # This implies no fast_install, which is unacceptable. # Some rework will be needed to allow for fast_install @@ -15514,7 +16258,7 @@ rm -f core conftest.err conftest.$ac_objext \ # Append ld.so.conf contents to the search path if test -f /etc/ld.so.conf; then - lt_ld_extra=`awk '/^include / { system(sprintf("cd /etc; cat %s 2>/dev/null", \$2)); skip = 1; } { if (!skip) print \$0; skip = 0; }' < /etc/ld.so.conf | $SED -e 's/#.*//;/^[ ]*hwcap[ ]/d;s/[:, ]/ /g;s/=[^=]*$//;s/=[^= ]* / /g;/^$/d' | tr '\n' ' '` + lt_ld_extra=`awk '/^include / { system(sprintf("cd /etc; cat %s 2>/dev/null", \$2)); skip = 1; } { if (!skip) print \$0; skip = 0; }' < /etc/ld.so.conf | $SED -e 's/#.*//;/^[ ]*hwcap[ ]/d;s/[:, ]/ /g;s/=[^=]*$//;s/=[^= ]* / /g;s/"//g;/^$/d' | tr '\n' ' '` sys_lib_dlsearch_path_spec="/lib /usr/lib $lt_ld_extra" fi @@ -15558,7 +16302,7 @@ netbsd*) ;; newsos6) - version_type=linux + version_type=linux # correct to gnu/linux during the next big refactor library_names_spec='${libname}${release}${shared_ext}$versuffix ${libname}${release}${shared_ext}$major $libname${shared_ext}' shlibpath_var=LD_LIBRARY_PATH shlibpath_overrides_runpath=yes @@ -15627,7 +16371,7 @@ rdos*) ;; solaris*) - version_type=linux + version_type=linux # correct to gnu/linux during the next big refactor need_lib_prefix=no need_version=no library_names_spec='${libname}${release}${shared_ext}$versuffix ${libname}${release}${shared_ext}$major $libname${shared_ext}' @@ -15652,7 +16396,7 @@ sunos4*) ;; sysv4 | sysv4.3*) - version_type=linux + version_type=linux # correct to gnu/linux during the next big refactor library_names_spec='${libname}${release}${shared_ext}$versuffix ${libname}${release}${shared_ext}$major $libname${shared_ext}' soname_spec='${libname}${release}${shared_ext}$major' shlibpath_var=LD_LIBRARY_PATH @@ -15676,7 +16420,7 @@ sysv4 | sysv4.3*) sysv4*MP*) if test -d /usr/nec ;then - version_type=linux + version_type=linux # correct to gnu/linux during the next big refactor library_names_spec='$libname${shared_ext}.$versuffix $libname${shared_ext}.$major $libname${shared_ext}' soname_spec='$libname${shared_ext}.$major' shlibpath_var=LD_LIBRARY_PATH @@ -15707,7 +16451,7 @@ sysv5* | sco3.2v5* | sco5v6* | unixware* | OpenUNIX* | sysv4*uw2*) tpf*) # TPF is a cross-target only. Preferred cross-host = GNU/Linux. - version_type=linux + version_type=linux # correct to gnu/linux during the next big refactor need_lib_prefix=no need_version=no library_names_spec='${libname}${release}${shared_ext}$versuffix ${libname}${release}${shared_ext}$major $libname${shared_ext}' @@ -15717,7 +16461,7 @@ tpf*) ;; uts4*) - version_type=linux + version_type=linux # correct to gnu/linux during the next big refactor library_names_spec='${libname}${release}${shared_ext}$versuffix ${libname}${release}${shared_ext}$major $libname${shared_ext}' soname_spec='${libname}${release}${shared_ext}$major' shlibpath_var=LD_LIBRARY_PATH @@ -15775,6 +16519,8 @@ fi + + @@ -15825,6 +16571,7 @@ fi fi # test -n "$compiler" CC=$lt_save_CC + CFLAGS=$lt_save_CFLAGS LDCXX=$LD LD=$lt_save_LD GCC=$lt_save_GCC @@ -15853,6 +16600,8 @@ ac_compiler_gnu=$ac_cv_c_compiler_gnu + + ac_config_commands="$ac_config_commands libtool" @@ -15863,12 +16612,14 @@ ac_compiler_gnu=$ac_cv_c_compiler_gnu { $as_echo "$as_me:${as_lineno-$LINENO}: checking which extension is used for runtime loadable modules" >&5 $as_echo_n "checking which extension is used for runtime loadable modules... " >&6; } -if test "${libltdl_cv_shlibext+set}" = set; then : +if ${libltdl_cv_shlibext+:} false; then : $as_echo_n "(cached) " >&6 else module=yes eval libltdl_cv_shlibext=$shrext_cmds +module=no +eval libltdl_cv_shrext=$shrext_cmds fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $libltdl_cv_shlibext" >&5 @@ -15879,11 +16630,18 @@ cat >>confdefs.h <<_ACEOF #define LT_MODULE_EXT "$libltdl_cv_shlibext" _ACEOF +fi +if test "$libltdl_cv_shrext" != "$libltdl_cv_shlibext"; then + +cat >>confdefs.h <<_ACEOF +#define LT_SHARED_EXT "$libltdl_cv_shrext" +_ACEOF + fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking which variable specifies run-time module search path" >&5 $as_echo_n "checking which variable specifies run-time module search path... " >&6; } -if test "${lt_cv_module_path_var+set}" = set; then : +if ${lt_cv_module_path_var+:} false; then : $as_echo_n "(cached) " >&6 else lt_cv_module_path_var="$shlibpath_var" @@ -15900,7 +16658,7 @@ fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking for the default library search path" >&5 $as_echo_n "checking for the default library search path... " >&6; } -if test "${lt_cv_sys_dlsearch_path+set}" = set; then : +if ${lt_cv_sys_dlsearch_path+:} false; then : $as_echo_n "(cached) " >&6 else lt_cv_sys_dlsearch_path="$sys_lib_dlsearch_path_spec" @@ -15937,7 +16695,7 @@ ac_compiler_gnu=$ac_cv_c_compiler_gnu LIBADD_DLOPEN= { $as_echo "$as_me:${as_lineno-$LINENO}: checking for library containing dlopen" >&5 $as_echo_n "checking for library containing dlopen... " >&6; } -if test "${ac_cv_search_dlopen+set}" = set; then : +if ${ac_cv_search_dlopen+:} false; then : $as_echo_n "(cached) " >&6 else ac_func_search_save_LIBS=$LIBS @@ -15971,11 +16729,11 @@ for ac_lib in '' dl; do fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext - if test "${ac_cv_search_dlopen+set}" = set; then : + if ${ac_cv_search_dlopen+:} false; then : break fi done -if test "${ac_cv_search_dlopen+set}" = set; then : +if ${ac_cv_search_dlopen+:} false; then : else ac_cv_search_dlopen=no @@ -16020,7 +16778,7 @@ $as_echo "#define HAVE_LIBDL 1" >>confdefs.h else { $as_echo "$as_me:${as_lineno-$LINENO}: checking for dlopen in -lsvld" >&5 $as_echo_n "checking for dlopen in -lsvld... " >&6; } -if test "${ac_cv_lib_svld_dlopen+set}" = set; then : +if ${ac_cv_lib_svld_dlopen+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS @@ -16054,7 +16812,7 @@ LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_svld_dlopen" >&5 $as_echo "$ac_cv_lib_svld_dlopen" >&6; } -if test "x$ac_cv_lib_svld_dlopen" = x""yes; then : +if test "x$ac_cv_lib_svld_dlopen" = xyes; then : $as_echo "#define HAVE_LIBDL 1" >>confdefs.h @@ -16074,7 +16832,7 @@ then for ac_func in dlerror do : ac_fn_c_check_func "$LINENO" "dlerror" "ac_cv_func_dlerror" -if test "x$ac_cv_func_dlerror" = x""yes; then : +if test "x$ac_cv_func_dlerror" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_DLERROR 1 _ACEOF @@ -16088,7 +16846,7 @@ fi LIBADD_SHL_LOAD= ac_fn_c_check_func "$LINENO" "shl_load" "ac_cv_func_shl_load" -if test "x$ac_cv_func_shl_load" = x""yes; then : +if test "x$ac_cv_func_shl_load" = xyes; then : $as_echo "#define HAVE_SHL_LOAD 1" >>confdefs.h @@ -16096,7 +16854,7 @@ $as_echo "#define HAVE_SHL_LOAD 1" >>confdefs.h else { $as_echo "$as_me:${as_lineno-$LINENO}: checking for shl_load in -ldld" >&5 $as_echo_n "checking for shl_load in -ldld... " >&6; } -if test "${ac_cv_lib_dld_shl_load+set}" = set; then : +if ${ac_cv_lib_dld_shl_load+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS @@ -16130,7 +16888,7 @@ LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_dld_shl_load" >&5 $as_echo "$ac_cv_lib_dld_shl_load" >&6; } -if test "x$ac_cv_lib_dld_shl_load" = x""yes; then : +if test "x$ac_cv_lib_dld_shl_load" = xyes; then : $as_echo "#define HAVE_SHL_LOAD 1" >>confdefs.h @@ -16146,7 +16904,7 @@ case $host_os in darwin[1567].*) # We only want this for pre-Mac OS X 10.4. ac_fn_c_check_func "$LINENO" "_dyld_func_lookup" "ac_cv_func__dyld_func_lookup" -if test "x$ac_cv_func__dyld_func_lookup" = x""yes; then : +if test "x$ac_cv_func__dyld_func_lookup" = xyes; then : $as_echo "#define HAVE_DYLD 1" >>confdefs.h @@ -16160,7 +16918,7 @@ beos*) cygwin* | mingw* | os2* | pw32*) ac_fn_c_check_decl "$LINENO" "cygwin_conv_path" "ac_cv_have_decl_cygwin_conv_path" "#include " -if test "x$ac_cv_have_decl_cygwin_conv_path" = x""yes; then : +if test "x$ac_cv_have_decl_cygwin_conv_path" = xyes; then : ac_have_decl=1 else ac_have_decl=0 @@ -16176,7 +16934,7 @@ esac { $as_echo "$as_me:${as_lineno-$LINENO}: checking for dld_link in -ldld" >&5 $as_echo_n "checking for dld_link in -ldld... " >&6; } -if test "${ac_cv_lib_dld_dld_link+set}" = set; then : +if ${ac_cv_lib_dld_dld_link+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS @@ -16210,7 +16968,7 @@ LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_dld_dld_link" >&5 $as_echo "$ac_cv_lib_dld_dld_link" >&6; } -if test "x$ac_cv_lib_dld_dld_link" = x""yes; then : +if test "x$ac_cv_lib_dld_dld_link" = xyes; then : $as_echo "#define HAVE_DLD 1" >>confdefs.h @@ -16244,7 +17002,7 @@ ac_compiler_gnu=$ac_cv_c_compiler_gnu { $as_echo "$as_me:${as_lineno-$LINENO}: checking for _ prefix in compiled symbols" >&5 $as_echo_n "checking for _ prefix in compiled symbols... " >&6; } -if test "${lt_cv_sys_symbol_underscore+set}" = set; then : +if ${lt_cv_sys_symbol_underscore+:} false; then : $as_echo_n "(cached) " >&6 else lt_cv_sys_symbol_underscore=no @@ -16294,7 +17052,7 @@ if test x"$lt_cv_sys_symbol_underscore" = xyes; then test x"$libltdl_cv_lib_dl_dlopen" = xyes ; then { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether we have to add an underscore for dlsym" >&5 $as_echo_n "checking whether we have to add an underscore for dlsym... " >&6; } -if test "${libltdl_cv_need_uscore+set}" = set; then : +if ${libltdl_cv_need_uscore+:} false; then : $as_echo_n "(cached) " >&6 else libltdl_cv_need_uscore=unknown @@ -16306,7 +17064,7 @@ else lt_dlunknown=0; lt_dlno_uscore=1; lt_dlneed_uscore=2 lt_status=$lt_dlunknown cat > conftest.$ac_ext <<_LT_EOF -#line 16309 "configure" +#line $LINENO "configure" #include "confdefs.h" #if HAVE_DLFCN_H @@ -16347,7 +17105,13 @@ else # endif #endif -void fnord() { int i=42;} +/* When -fvisbility=hidden is used, assume the code has been annotated + correspondingly for the symbols needed. */ +#if defined(__GNUC__) && (((__GNUC__ == 3) && (__GNUC_MINOR__ >= 3)) || (__GNUC__ > 3)) +int fnord () __attribute__((visibility("default"))); +#endif + +int fnord () { return 42; } int main () { void *self = dlopen (0, LT_DLGLOBAL|LT_DLLAZY_OR_NOW); @@ -16356,7 +17120,11 @@ int main () if (self) { if (dlsym (self,"fnord")) status = $lt_dlno_uscore; - else if (dlsym( self,"_fnord")) status = $lt_dlneed_uscore; + else + { + if (dlsym( self,"_fnord")) status = $lt_dlneed_uscore; + else puts (dlerror ()); + } /* dlclose (self); */ } else @@ -16400,7 +17168,7 @@ fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether deplibs are loaded by dlopen" >&5 $as_echo_n "checking whether deplibs are loaded by dlopen... " >&6; } -if test "${lt_cv_sys_dlopen_deplibs+set}" = set; then : +if ${lt_cv_sys_dlopen_deplibs+:} false; then : $as_echo_n "(cached) " >&6 else # PORTME does your system automatically load deplibs for dlopen? @@ -16506,7 +17274,7 @@ for ac_header in argz.h do : ac_fn_c_check_header_compile "$LINENO" "argz.h" "ac_cv_header_argz_h" "$ac_includes_default " -if test "x$ac_cv_header_argz_h" = x""yes; then : +if test "x$ac_cv_header_argz_h" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_ARGZ_H 1 _ACEOF @@ -16520,7 +17288,7 @@ ac_fn_c_check_type "$LINENO" "error_t" "ac_cv_type_error_t" "#if defined(HAVE_AR # include #endif " -if test "x$ac_cv_type_error_t" = x""yes; then : +if test "x$ac_cv_type_error_t" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_ERROR_T 1 @@ -16560,7 +17328,7 @@ done if test -z "$ARGZ_H"; then : { $as_echo "$as_me:${as_lineno-$LINENO}: checking if argz actually works" >&5 $as_echo_n "checking if argz actually works... " >&6; } -if test "${lt_cv_sys_argz_works+set}" = set; then : +if ${lt_cv_sys_argz_works+:} false; then : $as_echo_n "(cached) " >&6 else case $host_os in #( @@ -16591,7 +17359,7 @@ else fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $lt_cv_sys_argz_works" >&5 $as_echo "$lt_cv_sys_argz_works" >&6; } - if test $lt_cv_sys_argz_works = yes; then : + if test "$lt_cv_sys_argz_works" = yes; then : $as_echo "#define HAVE_WORKING_ARGZ 1" >>confdefs.h @@ -16608,7 +17376,7 @@ fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether libtool supports -dlopen/-dlpreopen" >&5 $as_echo_n "checking whether libtool supports -dlopen/-dlpreopen... " >&6; } -if test "${libltdl_cv_preloaded_symbols+set}" = set; then : +if ${libltdl_cv_preloaded_symbols+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$lt_cv_sys_global_symbol_pipe"; then @@ -16653,14 +17421,14 @@ if test "x$with_included_ltdl" != xyes; then ac_fn_c_check_header_compile "$LINENO" "ltdl.h" "ac_cv_header_ltdl_h" "$ac_includes_default " -if test "x$ac_cv_header_ltdl_h" = x""yes; then : +if test "x$ac_cv_header_ltdl_h" = xyes; then : ac_fn_c_check_decl "$LINENO" "lt_dlinterface_register" "ac_cv_have_decl_lt_dlinterface_register" "$ac_includes_default #include " -if test "x$ac_cv_have_decl_lt_dlinterface_register" = x""yes; then : +if test "x$ac_cv_have_decl_lt_dlinterface_register" = xyes; then : { $as_echo "$as_me:${as_lineno-$LINENO}: checking for lt_dladvise_preload in -lltdl" >&5 $as_echo_n "checking for lt_dladvise_preload in -lltdl... " >&6; } -if test "${ac_cv_lib_ltdl_lt_dladvise_preload+set}" = set; then : +if ${ac_cv_lib_ltdl_lt_dladvise_preload+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS @@ -16694,7 +17462,7 @@ LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_ltdl_lt_dladvise_preload" >&5 $as_echo "$ac_cv_lib_ltdl_lt_dladvise_preload" >&6; } -if test "x$ac_cv_lib_ltdl_lt_dladvise_preload" = x""yes; then : +if test "x$ac_cv_lib_ltdl_lt_dladvise_preload" = xyes; then : with_included_ltdl=no else with_included_ltdl=yes @@ -16718,7 +17486,6 @@ fi - # Check whether --with-ltdl_include was given. if test "${with_ltdl_include+set}" = set; then : withval=$with_ltdl_include; @@ -16753,7 +17520,7 @@ fi case ,$with_included_ltdl,$with_ltdl_include,$with_ltdl_lib, in ,yes,no,no,) case $enable_ltdl_convenience in - no) as_fn_error $? "this package needs a convenience libltdl" "$LINENO" 5 ;; + no) as_fn_error $? "this package needs a convenience libltdl" "$LINENO" 5 ;; "") enable_ltdl_convenience=yes ac_configure_args="$ac_configure_args --enable-ltdl-convenience" ;; esac @@ -16837,7 +17604,6 @@ fi - # In order that ltdl.c can compile, find out the first AC_CONFIG_HEADERS # the user used. This is so that ltdl.h can pick up the parent projects # config.h file, The first file in AC_CONFIG_HEADERS must contain the @@ -16902,8 +17668,16 @@ cat >>confdefs.h <<_ACEOF _ACEOF +name= +eval "lt_libprefix=\"$libname_spec\"" + +cat >>confdefs.h <<_ACEOF +#define LT_LIBPREFIX "$lt_libprefix" +_ACEOF + + name=ltdl -LTDLOPEN=`eval "\\$ECHO \"$libname_spec\""` +eval "LTDLOPEN=\"$libname_spec\"" @@ -16929,7 +17703,7 @@ if test "$enable_largefile" != no; then { $as_echo "$as_me:${as_lineno-$LINENO}: checking for special C compiler options needed for large files" >&5 $as_echo_n "checking for special C compiler options needed for large files... " >&6; } -if test "${ac_cv_sys_largefile_CC+set}" = set; then : +if ${ac_cv_sys_largefile_CC+:} false; then : $as_echo_n "(cached) " >&6 else ac_cv_sys_largefile_CC=no @@ -16980,7 +17754,7 @@ $as_echo "$ac_cv_sys_largefile_CC" >&6; } { $as_echo "$as_me:${as_lineno-$LINENO}: checking for _FILE_OFFSET_BITS value needed for large files" >&5 $as_echo_n "checking for _FILE_OFFSET_BITS value needed for large files... " >&6; } -if test "${ac_cv_sys_file_offset_bits+set}" = set; then : +if ${ac_cv_sys_file_offset_bits+:} false; then : $as_echo_n "(cached) " >&6 else while :; do @@ -17049,7 +17823,7 @@ rm -rf conftest* if test $ac_cv_sys_file_offset_bits = unknown; then { $as_echo "$as_me:${as_lineno-$LINENO}: checking for _LARGE_FILES value needed for large files" >&5 $as_echo_n "checking for _LARGE_FILES value needed for large files... " >&6; } -if test "${ac_cv_sys_large_files+set}" = set; then : +if ${ac_cv_sys_large_files+:} false; then : $as_echo_n "(cached) " >&6 else while :; do @@ -17116,11 +17890,13 @@ _ACEOF esac rm -rf conftest* fi + + fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking for _LARGEFILE_SOURCE value needed for large files" >&5 $as_echo_n "checking for _LARGEFILE_SOURCE value needed for large files... " >&6; } -if test "${ac_cv_sys_largefile_source+set}" = set; then : +if ${ac_cv_sys_largefile_source+:} false; then : $as_echo_n "(cached) " >&6 else while :; do @@ -17203,7 +17979,10 @@ fi # Use Linux interface name unless the OS has a different preference DEFAULT_INTERFACE="\"eth0\"" -funcstocheck="socket select inet_ntoa getnameinfo gethostname gethostbyname gethostbyaddr getaddrinfo" +funcstocheck="getnameinfo gethostname gethostbyname gethostbyaddr getaddrinfo" + +# Srcdir in a form that native compiler understands (i.e. DOS path on W32) +native_srcdir=$srcdir # Check system type case "$host_os" in @@ -17248,8 +18027,8 @@ if test "x$with_x" = xno; then have_x=disabled else case $x_includes,$x_libraries in #( - *\'*) as_fn_error $? "cannot use X directory names containing '" "$LINENO" 5 ;; #( - *,NONE | NONE,*) if test "${ac_cv_have_x+set}" = set; then : + *\'*) as_fn_error $? "cannot use X directory names containing '" "$LINENO" 5;; #( + *,NONE | NONE,*) if ${ac_cv_have_x+:} false; then : $as_echo_n "(cached) " >&6 else # One or both of the vars are not set, and there is no cached value. @@ -17526,7 +18305,7 @@ if ac_fn_c_try_link "$LINENO"; then : else { $as_echo "$as_me:${as_lineno-$LINENO}: checking for dnet_ntoa in -ldnet" >&5 $as_echo_n "checking for dnet_ntoa in -ldnet... " >&6; } -if test "${ac_cv_lib_dnet_dnet_ntoa+set}" = set; then : +if ${ac_cv_lib_dnet_dnet_ntoa+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS @@ -17560,14 +18339,14 @@ LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_dnet_dnet_ntoa" >&5 $as_echo "$ac_cv_lib_dnet_dnet_ntoa" >&6; } -if test "x$ac_cv_lib_dnet_dnet_ntoa" = x""yes; then : +if test "x$ac_cv_lib_dnet_dnet_ntoa" = xyes; then : X_EXTRA_LIBS="$X_EXTRA_LIBS -ldnet" fi if test $ac_cv_lib_dnet_dnet_ntoa = no; then { $as_echo "$as_me:${as_lineno-$LINENO}: checking for dnet_ntoa in -ldnet_stub" >&5 $as_echo_n "checking for dnet_ntoa in -ldnet_stub... " >&6; } -if test "${ac_cv_lib_dnet_stub_dnet_ntoa+set}" = set; then : +if ${ac_cv_lib_dnet_stub_dnet_ntoa+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS @@ -17601,7 +18380,7 @@ LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_dnet_stub_dnet_ntoa" >&5 $as_echo "$ac_cv_lib_dnet_stub_dnet_ntoa" >&6; } -if test "x$ac_cv_lib_dnet_stub_dnet_ntoa" = x""yes; then : +if test "x$ac_cv_lib_dnet_stub_dnet_ntoa" = xyes; then : X_EXTRA_LIBS="$X_EXTRA_LIBS -ldnet_stub" fi @@ -17620,14 +18399,14 @@ rm -f core conftest.err conftest.$ac_objext \ # The functions gethostbyname, getservbyname, and inet_addr are # in -lbsd on LynxOS 3.0.1/i386, according to Lars Hecking. ac_fn_c_check_func "$LINENO" "gethostbyname" "ac_cv_func_gethostbyname" -if test "x$ac_cv_func_gethostbyname" = x""yes; then : +if test "x$ac_cv_func_gethostbyname" = xyes; then : fi if test $ac_cv_func_gethostbyname = no; then { $as_echo "$as_me:${as_lineno-$LINENO}: checking for gethostbyname in -lnsl" >&5 $as_echo_n "checking for gethostbyname in -lnsl... " >&6; } -if test "${ac_cv_lib_nsl_gethostbyname+set}" = set; then : +if ${ac_cv_lib_nsl_gethostbyname+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS @@ -17661,14 +18440,14 @@ LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_nsl_gethostbyname" >&5 $as_echo "$ac_cv_lib_nsl_gethostbyname" >&6; } -if test "x$ac_cv_lib_nsl_gethostbyname" = x""yes; then : +if test "x$ac_cv_lib_nsl_gethostbyname" = xyes; then : X_EXTRA_LIBS="$X_EXTRA_LIBS -lnsl" fi if test $ac_cv_lib_nsl_gethostbyname = no; then { $as_echo "$as_me:${as_lineno-$LINENO}: checking for gethostbyname in -lbsd" >&5 $as_echo_n "checking for gethostbyname in -lbsd... " >&6; } -if test "${ac_cv_lib_bsd_gethostbyname+set}" = set; then : +if ${ac_cv_lib_bsd_gethostbyname+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS @@ -17702,7 +18481,7 @@ LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_bsd_gethostbyname" >&5 $as_echo "$ac_cv_lib_bsd_gethostbyname" >&6; } -if test "x$ac_cv_lib_bsd_gethostbyname" = x""yes; then : +if test "x$ac_cv_lib_bsd_gethostbyname" = xyes; then : X_EXTRA_LIBS="$X_EXTRA_LIBS -lbsd" fi @@ -17717,14 +18496,14 @@ fi # must be given before -lnsl if both are needed. We assume that # if connect needs -lnsl, so does gethostbyname. ac_fn_c_check_func "$LINENO" "connect" "ac_cv_func_connect" -if test "x$ac_cv_func_connect" = x""yes; then : +if test "x$ac_cv_func_connect" = xyes; then : fi if test $ac_cv_func_connect = no; then { $as_echo "$as_me:${as_lineno-$LINENO}: checking for connect in -lsocket" >&5 $as_echo_n "checking for connect in -lsocket... " >&6; } -if test "${ac_cv_lib_socket_connect+set}" = set; then : +if ${ac_cv_lib_socket_connect+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS @@ -17758,7 +18537,7 @@ LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_socket_connect" >&5 $as_echo "$ac_cv_lib_socket_connect" >&6; } -if test "x$ac_cv_lib_socket_connect" = x""yes; then : +if test "x$ac_cv_lib_socket_connect" = xyes; then : X_EXTRA_LIBS="-lsocket $X_EXTRA_LIBS" fi @@ -17766,14 +18545,14 @@ fi # Guillermo Gomez says -lposix is necessary on A/UX. ac_fn_c_check_func "$LINENO" "remove" "ac_cv_func_remove" -if test "x$ac_cv_func_remove" = x""yes; then : +if test "x$ac_cv_func_remove" = xyes; then : fi if test $ac_cv_func_remove = no; then { $as_echo "$as_me:${as_lineno-$LINENO}: checking for remove in -lposix" >&5 $as_echo_n "checking for remove in -lposix... " >&6; } -if test "${ac_cv_lib_posix_remove+set}" = set; then : +if ${ac_cv_lib_posix_remove+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS @@ -17807,7 +18586,7 @@ LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_posix_remove" >&5 $as_echo "$ac_cv_lib_posix_remove" >&6; } -if test "x$ac_cv_lib_posix_remove" = x""yes; then : +if test "x$ac_cv_lib_posix_remove" = xyes; then : X_EXTRA_LIBS="$X_EXTRA_LIBS -lposix" fi @@ -17815,14 +18594,14 @@ fi # BSDI BSD/OS 2.1 needs -lipc for XOpenDisplay. ac_fn_c_check_func "$LINENO" "shmat" "ac_cv_func_shmat" -if test "x$ac_cv_func_shmat" = x""yes; then : +if test "x$ac_cv_func_shmat" = xyes; then : fi if test $ac_cv_func_shmat = no; then { $as_echo "$as_me:${as_lineno-$LINENO}: checking for shmat in -lipc" >&5 $as_echo_n "checking for shmat in -lipc... " >&6; } -if test "${ac_cv_lib_ipc_shmat+set}" = set; then : +if ${ac_cv_lib_ipc_shmat+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS @@ -17856,7 +18635,7 @@ LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_ipc_shmat" >&5 $as_echo "$ac_cv_lib_ipc_shmat" >&6; } -if test "x$ac_cv_lib_ipc_shmat" = x""yes; then : +if test "x$ac_cv_lib_ipc_shmat" = xyes; then : X_EXTRA_LIBS="$X_EXTRA_LIBS -lipc" fi @@ -17874,7 +18653,7 @@ fi # John Interrante, Karl Berry { $as_echo "$as_me:${as_lineno-$LINENO}: checking for IceConnectionNumber in -lICE" >&5 $as_echo_n "checking for IceConnectionNumber in -lICE... " >&6; } -if test "${ac_cv_lib_ICE_IceConnectionNumber+set}" = set; then : +if ${ac_cv_lib_ICE_IceConnectionNumber+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS @@ -17908,7 +18687,7 @@ LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_ICE_IceConnectionNumber" >&5 $as_echo "$ac_cv_lib_ICE_IceConnectionNumber" >&6; } -if test "x$ac_cv_lib_ICE_IceConnectionNumber" = x""yes; then : +if test "x$ac_cv_lib_ICE_IceConnectionNumber" = xyes; then : X_PRE_LIBS="$X_PRE_LIBS -lSM -lICE" fi @@ -17917,7 +18696,7 @@ fi fi ;; -freebsd*) +*freebsd*) cat >>confdefs.h <<_ACEOF #define SOMEBSD 1 @@ -17934,7 +18713,7 @@ _ACEOF DLLDIR=lib UNIXONLY="#" ;; -openbsd*) +*openbsd*) cat >>confdefs.h <<_ACEOF #define SOMEBSD 1 @@ -17951,7 +18730,7 @@ _ACEOF DLLDIR=lib UNIXONLY="#" ;; -netbsd*) +*netbsd*) cat >>confdefs.h <<_ACEOF #define SOMEBSD 1 @@ -17979,7 +18758,7 @@ _ACEOF { $as_echo "$as_me:${as_lineno-$LINENO}: checking for res_init in -lresolv" >&5 $as_echo_n "checking for res_init in -lresolv... " >&6; } -if test "${ac_cv_lib_resolv_res_init+set}" = set; then : +if ${ac_cv_lib_resolv_res_init+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS @@ -18013,7 +18792,7 @@ LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_resolv_res_init" >&5 $as_echo "$ac_cv_lib_resolv_res_init" >&6; } -if test "x$ac_cv_lib_resolv_res_init" = x""yes; then : +if test "x$ac_cv_lib_resolv_res_init" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_LIBRESOLV 1 _ACEOF @@ -18024,7 +18803,7 @@ fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking for nanosleep in -lrt" >&5 $as_echo_n "checking for nanosleep in -lrt... " >&6; } -if test "${ac_cv_lib_rt_nanosleep+set}" = set; then : +if ${ac_cv_lib_rt_nanosleep+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS @@ -18058,7 +18837,7 @@ LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_rt_nanosleep" >&5 $as_echo "$ac_cv_lib_rt_nanosleep" >&6; } -if test "x$ac_cv_lib_rt_nanosleep" = x""yes; then : +if test "x$ac_cv_lib_rt_nanosleep" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_LIBRT 1 _ACEOF @@ -18097,7 +18876,7 @@ _ACEOF { $as_echo "$as_me:${as_lineno-$LINENO}: checking for gettext in -lintl" >&5 $as_echo_n "checking for gettext in -lintl... " >&6; } -if test "${ac_cv_lib_intl_gettext+set}" = set; then : +if ${ac_cv_lib_intl_gettext+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS @@ -18131,7 +18910,7 @@ LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_intl_gettext" >&5 $as_echo "$ac_cv_lib_intl_gettext" >&6; } -if test "x$ac_cv_lib_intl_gettext" = x""yes; then : +if test "x$ac_cv_lib_intl_gettext" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_LIBINTL 1 _ACEOF @@ -18161,7 +18940,7 @@ if test -z "$CXX"; then set dummy $ac_tool_prefix$ac_prog; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } -if test "${ac_cv_prog_CXX+set}" = set; then : +if ${ac_cv_prog_CXX+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$CXX"; then @@ -18173,7 +18952,7 @@ do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do - if { test -f "$as_dir/$ac_word$ac_exec_ext" && $as_test_x "$as_dir/$ac_word$ac_exec_ext"; }; then + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_CXX="$ac_tool_prefix$ac_prog" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 @@ -18205,7 +18984,7 @@ do set dummy $ac_prog; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } -if test "${ac_cv_prog_ac_ct_CXX+set}" = set; then : +if ${ac_cv_prog_ac_ct_CXX+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$ac_ct_CXX"; then @@ -18217,7 +18996,7 @@ do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do - if { test -f "$as_dir/$ac_word$ac_exec_ext" && $as_test_x "$as_dir/$ac_word$ac_exec_ext"; }; then + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_ac_ct_CXX="$ac_prog" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 @@ -18283,7 +19062,7 @@ done { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether we are using the GNU C++ compiler" >&5 $as_echo_n "checking whether we are using the GNU C++ compiler... " >&6; } -if test "${ac_cv_cxx_compiler_gnu+set}" = set; then : +if ${ac_cv_cxx_compiler_gnu+:} false; then : $as_echo_n "(cached) " >&6 else cat confdefs.h - <<_ACEOF >conftest.$ac_ext @@ -18320,7 +19099,7 @@ ac_test_CXXFLAGS=${CXXFLAGS+set} ac_save_CXXFLAGS=$CXXFLAGS { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether $CXX accepts -g" >&5 $as_echo_n "checking whether $CXX accepts -g... " >&6; } -if test "${ac_cv_prog_cxx_g+set}" = set; then : +if ${ac_cv_prog_cxx_g+:} false; then : $as_echo_n "(cached) " >&6 else ac_save_cxx_werror_flag=$ac_cxx_werror_flag @@ -18406,7 +19185,7 @@ depcc="$CXX" am_compiler_list= { $as_echo "$as_me:${as_lineno-$LINENO}: checking dependency style of $depcc" >&5 $as_echo_n "checking dependency style of $depcc... " >&6; } -if test "${am_cv_CXX_dependencies_compiler_type+set}" = set; then : +if ${am_cv_CXX_dependencies_compiler_type+:} false; then : $as_echo_n "(cached) " >&6 else if test -z "$AMDEP_TRUE" && test -f "$am_depcomp"; then @@ -18415,6 +19194,7 @@ else # instance it was reported that on HP-UX the gcc test will end up # making a dummy file named `D' -- because `-MD' means `put the output # in D'. + rm -rf conftest.dir mkdir conftest.dir # Copy depcomp to subdir because otherwise we won't find it if we're # using a relative directory. @@ -18474,7 +19254,7 @@ else break fi ;; - msvisualcpp | msvcmsys) + msvc7 | msvc7msys | msvisualcpp | msvcmsys) # This compiler won't grok `-c -o', but also, the minuso test has # not run yet. These depmodes are late enough in the game, and # so weak that their functioning should not be impacted. @@ -18549,7 +19329,7 @@ _ACEOF { $as_echo "$as_me:${as_lineno-$LINENO}: checking for gettext in -lintl" >&5 $as_echo_n "checking for gettext in -lintl... " >&6; } -if test "${ac_cv_lib_intl_gettext+set}" = set; then : +if ${ac_cv_lib_intl_gettext+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS @@ -18583,7 +19363,7 @@ LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_intl_gettext" >&5 $as_echo "$ac_cv_lib_intl_gettext" >&6; } -if test "x$ac_cv_lib_intl_gettext" = x""yes; then : +if test "x$ac_cv_lib_intl_gettext" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_LIBINTL 1 _ACEOF @@ -18613,7 +19393,7 @@ if test -z "$CXX"; then set dummy $ac_tool_prefix$ac_prog; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } -if test "${ac_cv_prog_CXX+set}" = set; then : +if ${ac_cv_prog_CXX+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$CXX"; then @@ -18625,7 +19405,7 @@ do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do - if { test -f "$as_dir/$ac_word$ac_exec_ext" && $as_test_x "$as_dir/$ac_word$ac_exec_ext"; }; then + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_CXX="$ac_tool_prefix$ac_prog" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 @@ -18657,7 +19437,7 @@ do set dummy $ac_prog; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } -if test "${ac_cv_prog_ac_ct_CXX+set}" = set; then : +if ${ac_cv_prog_ac_ct_CXX+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$ac_ct_CXX"; then @@ -18669,7 +19449,7 @@ do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do - if { test -f "$as_dir/$ac_word$ac_exec_ext" && $as_test_x "$as_dir/$ac_word$ac_exec_ext"; }; then + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_ac_ct_CXX="$ac_prog" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 @@ -18735,7 +19515,7 @@ done { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether we are using the GNU C++ compiler" >&5 $as_echo_n "checking whether we are using the GNU C++ compiler... " >&6; } -if test "${ac_cv_cxx_compiler_gnu+set}" = set; then : +if ${ac_cv_cxx_compiler_gnu+:} false; then : $as_echo_n "(cached) " >&6 else cat confdefs.h - <<_ACEOF >conftest.$ac_ext @@ -18772,7 +19552,7 @@ ac_test_CXXFLAGS=${CXXFLAGS+set} ac_save_CXXFLAGS=$CXXFLAGS { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether $CXX accepts -g" >&5 $as_echo_n "checking whether $CXX accepts -g... " >&6; } -if test "${ac_cv_prog_cxx_g+set}" = set; then : +if ${ac_cv_prog_cxx_g+:} false; then : $as_echo_n "(cached) " >&6 else ac_save_cxx_werror_flag=$ac_cxx_werror_flag @@ -18858,7 +19638,7 @@ depcc="$CXX" am_compiler_list= { $as_echo "$as_me:${as_lineno-$LINENO}: checking dependency style of $depcc" >&5 $as_echo_n "checking dependency style of $depcc... " >&6; } -if test "${am_cv_CXX_dependencies_compiler_type+set}" = set; then : +if ${am_cv_CXX_dependencies_compiler_type+:} false; then : $as_echo_n "(cached) " >&6 else if test -z "$AMDEP_TRUE" && test -f "$am_depcomp"; then @@ -18867,6 +19647,7 @@ else # instance it was reported that on HP-UX the gcc test will end up # making a dummy file named `D' -- because `-MD' means `put the output # in D'. + rm -rf conftest.dir mkdir conftest.dir # Copy depcomp to subdir because otherwise we won't find it if we're # using a relative directory. @@ -18926,7 +19707,7 @@ else break fi ;; - msvisualcpp | msvcmsys) + msvc7 | msvc7msys | msvisualcpp | msvcmsys) # This compiler won't grok `-c -o', but also, the minuso test has # not run yet. These depmodes are late enough in the game, and # so weak that their functioning should not be impacted. @@ -18985,6 +19766,16 @@ fi DLLDIR=bin UNIXONLY="" funcstocheck="" + native_srcdir=$(cd $srcdir; pwd -W) + ;; +gnu*) + +cat >>confdefs.h <<_ACEOF +#define GNU 1 +_ACEOF + + build_target="gnu" + UNIXONLY="#" ;; *) { $as_echo "$as_me:${as_lineno-$LINENO}: result: Unrecognised OS $host_os" >&5 @@ -19067,6 +19858,14 @@ else LINUX_FALSE= fi + if test "$build_target" = "gnu"; then + GNU_TRUE= + GNU_FALSE='#' +else + GNU_TRUE='#' + GNU_FALSE= +fi + { $as_echo "$as_me:${as_lineno-$LINENO}: result: $build_target" >&5 $as_echo "$build_target" >&6; } @@ -19081,7 +19880,7 @@ fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether unaligned 64-bit access works" >&5 $as_echo_n "checking whether unaligned 64-bit access works... " >&6; } -if test "${ac_cv_unaligned_64_access+set}" = set; then : +if ${ac_cv_unaligned_64_access+:} false; then : $as_echo_n "(cached) " >&6 else @@ -19131,7 +19930,7 @@ _ACEOF # some other checks for standard libs { $as_echo "$as_me:${as_lineno-$LINENO}: checking for library containing gethostbyname" >&5 $as_echo_n "checking for library containing gethostbyname... " >&6; } -if test "${ac_cv_search_gethostbyname+set}" = set; then : +if ${ac_cv_search_gethostbyname+:} false; then : $as_echo_n "(cached) " >&6 else ac_func_search_save_LIBS=$LIBS @@ -19165,11 +19964,11 @@ for ac_lib in '' nsl ws2_32; do fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext - if test "${ac_cv_search_gethostbyname+set}" = set; then : + if ${ac_cv_search_gethostbyname+:} false; then : break fi done -if test "${ac_cv_search_gethostbyname+set}" = set; then : +if ${ac_cv_search_gethostbyname+:} false; then : else ac_cv_search_gethostbyname=no @@ -19187,7 +19986,7 @@ fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking for socket in -lsocket" >&5 $as_echo_n "checking for socket in -lsocket... " >&6; } -if test "${ac_cv_lib_socket_socket+set}" = set; then : +if ${ac_cv_lib_socket_socket+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS @@ -19221,7 +20020,7 @@ LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_socket_socket" >&5 $as_echo "$ac_cv_lib_socket_socket" >&6; } -if test "x$ac_cv_lib_socket_socket" = x""yes; then : +if test "x$ac_cv_lib_socket_socket" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_LIBSOCKET 1 _ACEOF @@ -19232,7 +20031,7 @@ fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking for log in -lm" >&5 $as_echo_n "checking for log in -lm... " >&6; } -if test "${ac_cv_lib_m_log+set}" = set; then : +if ${ac_cv_lib_m_log+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS @@ -19266,7 +20065,7 @@ LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_m_log" >&5 $as_echo "$ac_cv_lib_m_log" >&6; } -if test "x$ac_cv_lib_m_log" = x""yes; then : +if test "x$ac_cv_lib_m_log" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_LIBM 1 _ACEOF @@ -19277,7 +20076,7 @@ fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking for getloadavg in -lc" >&5 $as_echo_n "checking for getloadavg in -lc... " >&6; } -if test "${ac_cv_lib_c_getloadavg+set}" = set; then : +if ${ac_cv_lib_c_getloadavg+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS @@ -19311,7 +20110,7 @@ LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_c_getloadavg" >&5 $as_echo "$ac_cv_lib_c_getloadavg" >&6; } -if test "x$ac_cv_lib_c_getloadavg" = x""yes; then : +if test "x$ac_cv_lib_c_getloadavg" = xyes; then : $as_echo "#define HAVE_GETLOADAVG 1" >>confdefs.h @@ -19327,7 +20126,7 @@ SAVE_LIBS=$LIBS gnurx=0 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for regexec in -lgnurx" >&5 $as_echo_n "checking for regexec in -lgnurx... " >&6; } -if test "${ac_cv_lib_gnurx_regexec+set}" = set; then : +if ${ac_cv_lib_gnurx_regexec+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS @@ -19361,7 +20160,7 @@ LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_gnurx_regexec" >&5 $as_echo "$ac_cv_lib_gnurx_regexec" >&6; } -if test "x$ac_cv_lib_gnurx_regexec" = x""yes; then : +if test "x$ac_cv_lib_gnurx_regexec" = xyes; then : gnurx=1 fi @@ -19372,6 +20171,10 @@ fi # libgcrypt gcrypt=0 +NEED_LIBGCRYPT_API=1 +NEED_LIBGCRYPT_VERSION=1.4.2 + + # Check whether --with-libgcrypt-prefix was given. if test "${with_libgcrypt_prefix+set}" = set; then : @@ -19390,7 +20193,7 @@ fi set dummy libgcrypt-config; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } -if test "${ac_cv_path_LIBGCRYPT_CONFIG+set}" = set; then : +if ${ac_cv_path_LIBGCRYPT_CONFIG+:} false; then : $as_echo_n "(cached) " >&6 else case $LIBGCRYPT_CONFIG in @@ -19404,7 +20207,7 @@ do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do - if { test -f "$as_dir/$ac_word$ac_exec_ext" && $as_test_x "$as_dir/$ac_word$ac_exec_ext"; }; then + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_path_LIBGCRYPT_CONFIG="$as_dir/$ac_word$ac_exec_ext" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 @@ -19427,7 +20230,7 @@ $as_echo "no" >&6; } fi - tmp=1.2.0 + tmp="$NEED_LIBGCRYPT_API:$NEED_LIBGCRYPT_VERSION" if echo "$tmp" | grep ':' >/dev/null 2>/dev/null ; then req_libgcrypt_api=`echo "$tmp" | sed 's/\(.*\):\(.*\)/\1/'` min_libgcrypt_version=`echo "$tmp" | sed 's/\(.*\):\(.*\)/\2/'` @@ -19509,7 +20312,7 @@ $as_echo "does not match (want=$req_libgcrypt_api got=$tmp)" >&6; } ac_fn_c_check_decl "$LINENO" "gcry_mpi_lshift" "ac_cv_have_decl_gcry_mpi_lshift" "#include " -if test "x$ac_cv_have_decl_gcry_mpi_lshift" = x""yes; then : +if test "x$ac_cv_have_decl_gcry_mpi_lshift" = xyes; then : ac_have_decl=1 else ac_have_decl=0 @@ -19522,9 +20325,21 @@ _ACEOF if test $gcrypt = 0 then - as_fn_error $? "GNUnet needs libgcrypt" "$LINENO" 5 + as_fn_error $? " +*** +*** You need libgcrypt to build this program. +** This library is for example available at +*** ftp://ftp.gnupg.org/gcrypt/libgcrypt/ +*** (at least version $NEED_LIBGCRYPT_VERSION (API $NEED_LIBGCRYPT_API) +*** is required.) +***" "$LINENO" 5 fi +cat >>confdefs.h <<_ACEOF +#define NEED_LIBGCRYPT_VERSION "$NEED_LIBGCRYPT_VERSION" +_ACEOF + + # Adam shostack suggests the following for Windows: # -D_FORTIFY_SOURCE=2 -fstack-protector-all # Check whether --enable-gcc-hardening was given. @@ -19574,6 +20389,35 @@ cat >>confdefs.h <<_ACEOF _ACEOF +# should memory poisoning be enabled? +{ $as_echo "$as_me:${as_lineno-$LINENO}: checking whether to poison freed memory" >&5 +$as_echo_n "checking whether to poison freed memory... " >&6; } +# Check whether --enable-poisoning was given. +if test "${enable_poisoning+set}" = set; then : + enableval=$enable_poisoning; enable_poisoning=${enableval} +else + + if test "x$extra_logging" != "xGNUNET_NO"; then + enable_poisoning="defaults to yes (extra logging is enabled)" + else + enable_poisoning=no + fi + +fi + +{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $enable_poisoning" >&5 +$as_echo "$enable_poisoning" >&6; } +if test ! "x$enable_poisoning" = "xno"; then + enable_poisoning=1 +else + enable_poisoning=0 +fi + +cat >>confdefs.h <<_ACEOF +#define ENABLE_POISONING $enable_poisoning +_ACEOF + + if test $build = $target then { $as_echo "$as_me:${as_lineno-$LINENO}: checking for working HMAC" >&5 @@ -19590,7 +20434,7 @@ if test "$cross_compiling" = yes; then : { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 $as_echo "$as_me: error: in \`$ac_pwd':" >&2;} as_fn_error $? "cannot run test program while cross compiling -See \`config.log' for more details" "$LINENO" 5 ; } +See \`config.log' for more details" "$LINENO" 5; } else cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ @@ -19656,21 +20500,21 @@ else { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 $as_echo "$as_me: error: in \`$ac_pwd':" >&2;} as_fn_error $? "HMAC test vector does not match. This is a known problem with libgcrypt 1.2.2 on Windows and fixed in 1.4.6. -See \`config.log' for more details" "$LINENO" 5 ; } +See \`config.log' for more details" "$LINENO" 5; } fi if test $RESULT = 2 then { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 $as_echo "$as_me: error: in \`$ac_pwd':" >&2;} as_fn_error $? "HMAC test failed -See \`config.log' for more details" "$LINENO" 5 ; } +See \`config.log' for more details" "$LINENO" 5; } fi if test $RESULT = 1 then { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 $as_echo "$as_me: error: in \`$ac_pwd':" >&2;} as_fn_error $? "libgcrypt header version does not match library version -See \`config.log' for more details" "$LINENO" 5 ; } +See \`config.log' for more details" "$LINENO" 5; } fi fi @@ -19728,7 +20572,7 @@ do set dummy $ac_prog; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } -if test "${ac_cv_prog_AWK+set}" = set; then : +if ${ac_cv_prog_AWK+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$AWK"; then @@ -19740,7 +20584,7 @@ do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do - if { test -f "$as_dir/$ac_word$ac_exec_ext" && $as_test_x "$as_dir/$ac_word$ac_exec_ext"; }; then + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_AWK="$ac_prog" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 @@ -19776,7 +20620,7 @@ done set dummy curl-config; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } -if test "${ac_cv_path__libcurl_config+set}" = set; then : +if ${ac_cv_path__libcurl_config+:} false; then : $as_echo_n "(cached) " >&6 else case $_libcurl_config in @@ -19790,7 +20634,7 @@ do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do - if { test -f "$as_dir/$ac_word$ac_exec_ext" && $as_test_x "$as_dir/$ac_word$ac_exec_ext"; }; then + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_path__libcurl_config="$as_dir/$ac_word$ac_exec_ext" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 @@ -19817,7 +20661,7 @@ fi set dummy curl-config; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } -if test "${ac_cv_path__libcurl_config+set}" = set; then : +if ${ac_cv_path__libcurl_config+:} false; then : $as_echo_n "(cached) " >&6 else case $_libcurl_config in @@ -19831,7 +20675,7 @@ do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do - if { test -f "$as_dir/$ac_word$ac_exec_ext" && $as_test_x "$as_dir/$ac_word$ac_exec_ext"; }; then + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_path__libcurl_config="$as_dir/$ac_word$ac_exec_ext" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 @@ -19858,7 +20702,7 @@ fi if test x$_libcurl_config != "x" ; then { $as_echo "$as_me:${as_lineno-$LINENO}: checking for the version of libcurl" >&5 $as_echo_n "checking for the version of libcurl... " >&6; } -if test "${libcurl_cv_lib_curl_version+set}" = set; then : +if ${libcurl_cv_lib_curl_version+:} false; then : $as_echo_n "(cached) " >&6 else libcurl_cv_lib_curl_version=`$_libcurl_config --version | $AWK '{print $2}'` @@ -19867,12 +20711,12 @@ fi $as_echo "$libcurl_cv_lib_curl_version" >&6; } _libcurl_version=`echo $libcurl_cv_lib_curl_version | $_libcurl_version_parse` - _libcurl_wanted=`echo 7.20.1 | $_libcurl_version_parse` + _libcurl_wanted=`echo 7.21.3 | $_libcurl_version_parse` if test $_libcurl_wanted -gt 0 ; then - { $as_echo "$as_me:${as_lineno-$LINENO}: checking for libcurl >= version 7.20.1" >&5 -$as_echo_n "checking for libcurl >= version 7.20.1... " >&6; } -if test "${libcurl_cv_lib_version_ok+set}" = set; then : + { $as_echo "$as_me:${as_lineno-$LINENO}: checking for libcurl >= version 7.21.3" >&5 +$as_echo_n "checking for libcurl >= version 7.21.3... " >&6; } +if ${libcurl_cv_lib_version_ok+:} false; then : $as_echo_n "(cached) " >&6 else @@ -19926,7 +20770,7 @@ $as_echo "$libcurl_cv_lib_version_ok" >&6; } { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether libcurl is usable" >&5 $as_echo_n "checking whether libcurl is usable... " >&6; } -if test "${libcurl_cv_lib_curl_usable+set}" = set; then : +if ${libcurl_cv_lib_curl_usable+:} false; then : $as_echo_n "(cached) " >&6 else @@ -19985,7 +20829,7 @@ $as_echo "$libcurl_cv_lib_curl_usable" >&6; } LIBS="$LIBS $LIBCURL" ac_fn_c_check_func "$LINENO" "curl_free" "ac_cv_func_curl_free" -if test "x$ac_cv_func_curl_free" = x""yes; then : +if test "x$ac_cv_func_curl_free" = xyes; then : else @@ -20036,39 +20880,145 @@ _ACEOF fi fi - for _libcurl_protocol in $_libcurl_protocols ; do - cat >>confdefs.h <<_ACEOF -#define `$as_echo "libcurl_protocol_$_libcurl_protocol" | $as_tr_cpp` 1 + for _libcurl_protocol in $_libcurl_protocols ; do + cat >>confdefs.h <<_ACEOF +#define `$as_echo "libcurl_protocol_$_libcurl_protocol" | $as_tr_cpp` 1 +_ACEOF + + eval `$as_echo "libcurl_protocol_$_libcurl_protocol" | $as_tr_sh`=yes + done + else + unset LIBCURL + unset LIBCURL_CPPFLAGS + fi + fi + + unset _libcurl_try_link + unset _libcurl_version_parse + unset _libcurl_config + unset _libcurl_feature + unset _libcurl_features + unset _libcurl_protocol + unset _libcurl_protocols + unset _libcurl_version + unset _libcurl_ldflags + fi + + if test x$_libcurl_with = xno || test x$libcurl_cv_lib_curl_usable != xyes ; then + # This is the IF-NO path + curl=0 + else + # This is the IF-YES path + curl=1 + fi + + unset _libcurl_with + +if test "$curl" = 1 +then + if true; then + HAVE_LIBCURL_TRUE= + HAVE_LIBCURL_FALSE='#' +else + HAVE_LIBCURL_TRUE='#' + HAVE_LIBCURL_FALSE= +fi + + +$as_echo "#define HAVE_LIBCURL 1" >>confdefs.h + +else + if false; then + HAVE_LIBCURL_TRUE= + HAVE_LIBCURL_FALSE='#' +else + HAVE_LIBCURL_TRUE='#' + HAVE_LIBCURL_FALSE= +fi + +fi + + +# libidn +{ $as_echo "$as_me:${as_lineno-$LINENO}: checking if Libidn can be used" >&5 +$as_echo_n "checking if Libidn can be used... " >&6; } + +# Check whether --with-libidn was given. +if test "${with_libidn+set}" = set; then : + withval=$with_libidn; libidn=$withval +else + libidn=yes +fi + +if test "$libidn" != "no"; then + if test "$libidn" != "yes"; then + LDFLAGS="${LDFLAGS} -L$libidn/lib" + CPPFLAGS="${CPPFLAGS} -I$libidn/include" + fi + ac_fn_c_check_header_mongrel "$LINENO" "idna.h" "ac_cv_header_idna_h" "$ac_includes_default" +if test "x$ac_cv_header_idna_h" = xyes; then : + { $as_echo "$as_me:${as_lineno-$LINENO}: checking for stringprep_check_version in -lidn" >&5 +$as_echo_n "checking for stringprep_check_version in -lidn... " >&6; } +if ${ac_cv_lib_idn_stringprep_check_version+:} false; then : + $as_echo_n "(cached) " >&6 +else + ac_check_lib_save_LIBS=$LIBS +LIBS="-lidn $LIBS" +cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ + +/* Override any GCC internal prototype to avoid an error. + Use char because int might match the return type of a GCC + builtin and then its argument prototype would still apply. */ +#ifdef __cplusplus +extern "C" +#endif +char stringprep_check_version (); +int +main () +{ +return stringprep_check_version (); + ; + return 0; +} _ACEOF +if ac_fn_c_try_link "$LINENO"; then : + ac_cv_lib_idn_stringprep_check_version=yes +else + ac_cv_lib_idn_stringprep_check_version=no +fi +rm -f core conftest.err conftest.$ac_objext \ + conftest$ac_exeext conftest.$ac_ext +LIBS=$ac_check_lib_save_LIBS +fi +{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_idn_stringprep_check_version" >&5 +$as_echo "$ac_cv_lib_idn_stringprep_check_version" >&6; } +if test "x$ac_cv_lib_idn_stringprep_check_version" = xyes; then : + libidn=yes LIBS="${LIBS} -lidn" +else + libidn=no +fi - eval `$as_echo "libcurl_protocol_$_libcurl_protocol" | $as_tr_sh`=yes - done - else - unset LIBCURL - unset LIBCURL_CPPFLAGS - fi - fi +else + libidn=no +fi - unset _libcurl_try_link - unset _libcurl_version_parse - unset _libcurl_config - unset _libcurl_feature - unset _libcurl_features - unset _libcurl_protocol - unset _libcurl_protocols - unset _libcurl_version - unset _libcurl_ldflags - fi - if test x$_libcurl_with = xno || test x$libcurl_cv_lib_curl_usable != xyes ; then - # This is the IF-NO path - as_fn_error $? "GNUnet requires libcurl >= 7.20.1" "$LINENO" 5 +fi +if test "$libidn" != "no" ; then + +$as_echo "#define LIBIDN 1" >>confdefs.h + else - # This is the IF-YES path - : - fi + { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 +$as_echo "$as_me: error: in \`$ac_pwd':" >&2;} +as_fn_error $? "Libidn not found +See \`config.log' for more details" "$LINENO" 5; } +fi +{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $libidn" >&5 +$as_echo "$libidn" >&6; } + - unset _libcurl_with # restore LIBS LIBS=$SAVE_LIBS @@ -20077,7 +21027,7 @@ LIBS=$SAVE_LIBS for ac_header in glpk.h do : ac_fn_c_check_header_mongrel "$LINENO" "glpk.h" "ac_cv_header_glpk_h" "$ac_includes_default" -if test "x$ac_cv_header_glpk_h" = x""yes; then : +if test "x$ac_cv_header_glpk_h" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_GLPK_H 1 _ACEOF @@ -20090,7 +21040,7 @@ done { $as_echo "$as_me:${as_lineno-$LINENO}: checking for glp_create_prob in -lglpk" >&5 $as_echo_n "checking for glp_create_prob in -lglpk... " >&6; } -if test "${ac_cv_lib_glpk_glp_create_prob+set}" = set; then : +if ${ac_cv_lib_glpk_glp_create_prob+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS @@ -20124,7 +21074,7 @@ LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_glpk_glp_create_prob" >&5 $as_echo "$ac_cv_lib_glpk_glp_create_prob" >&6; } -if test "x$ac_cv_lib_glpk_glp_create_prob" = x""yes; then : +if test "x$ac_cv_lib_glpk_glp_create_prob" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_LIBGLPK 1 _ACEOF @@ -20132,55 +21082,487 @@ _ACEOF LIBS="-lglpk $LIBS" else - gplk=false + gplk=false +fi + +# GLPK must support atm MLP presolving, version >= 4.32 +ac_fn_c_check_member "$LINENO" "glp_iocp" "presolve" "ac_cv_member_glp_iocp_presolve" "#include +" +if test "x$ac_cv_member_glp_iocp_presolve" = xyes; then : + +cat >>confdefs.h <<_ACEOF +#define HAVE_GLP_IOCP_PRESOLVE 1 +_ACEOF + + +else + gplk=false +fi + +if test x$gplk = xfalse +then + if false; then + HAVE_LIBGLPK_TRUE= + HAVE_LIBGLPK_FALSE='#' +else + HAVE_LIBGLPK_TRUE='#' + HAVE_LIBGLPK_FALSE= +fi + + { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: GNUnet requires GLPK >= 4.32" >&5 +$as_echo "$as_me: WARNING: GNUnet requires GLPK >= 4.32" >&2;} +else + if true; then + HAVE_LIBGLPK_TRUE= + HAVE_LIBGLPK_FALSE='#' +else + HAVE_LIBGLPK_TRUE='#' + HAVE_LIBGLPK_FALSE= +fi + + +$as_echo "#define HAVE_LIBGLPK 1" >>confdefs.h + +fi + +# test for glib +# Minimum required version for glibtop is 2.6.0 +# Check whether --enable-glibtest was given. +if test "${enable_glibtest+set}" = set; then : + enableval=$enable_glibtest; +else + enable_glibtest=yes +fi + + + pkg_config_args=glib-2.0 + for module in . + do + case "$module" in + gmodule) + pkg_config_args="$pkg_config_args gmodule-2.0" + ;; + gobject) + pkg_config_args="$pkg_config_args gobject-2.0" + ;; + gthread) + pkg_config_args="$pkg_config_args gthread-2.0" + ;; + esac + done + + # Extract the first word of "pkg-config", so it can be a program name with args. +set dummy pkg-config; ac_word=$2 +{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +$as_echo_n "checking for $ac_word... " >&6; } +if ${ac_cv_path_PKG_CONFIG+:} false; then : + $as_echo_n "(cached) " >&6 +else + case $PKG_CONFIG in + [\\/]* | ?:[\\/]*) + ac_cv_path_PKG_CONFIG="$PKG_CONFIG" # Let the user override the test with a path. + ;; + *) + as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + test -z "$as_dir" && as_dir=. + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then + ac_cv_path_PKG_CONFIG="$as_dir/$ac_word$ac_exec_ext" + $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + + test -z "$ac_cv_path_PKG_CONFIG" && ac_cv_path_PKG_CONFIG="no" + ;; +esac +fi +PKG_CONFIG=$ac_cv_path_PKG_CONFIG +if test -n "$PKG_CONFIG"; then + { $as_echo "$as_me:${as_lineno-$LINENO}: result: $PKG_CONFIG" >&5 +$as_echo "$PKG_CONFIG" >&6; } +else + { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 +$as_echo "no" >&6; } +fi + + + + no_glib="" + + if test x$PKG_CONFIG != xno ; then + if $PKG_CONFIG --atleast-pkgconfig-version 0.7 ; then + : + else + echo *** pkg-config too old; version 0.7 or better required. + no_glib=yes + PKG_CONFIG=no + fi + else + no_glib=yes + fi + + min_glib_version=2.6.0 + { $as_echo "$as_me:${as_lineno-$LINENO}: checking for GLIB - version >= $min_glib_version" >&5 +$as_echo_n "checking for GLIB - version >= $min_glib_version... " >&6; } + + if test x$PKG_CONFIG != xno ; then + ## don't try to run the test against uninstalled libtool libs + if $PKG_CONFIG --uninstalled $pkg_config_args; then + echo "Will use uninstalled version of GLib found in PKG_CONFIG_PATH" + enable_glibtest=no + fi + + if $PKG_CONFIG --atleast-version $min_glib_version $pkg_config_args; then + : + else + no_glib=yes + fi + fi + + if test x"$no_glib" = x ; then + GLIB_GENMARSHAL=`$PKG_CONFIG --variable=glib_genmarshal glib-2.0` + GOBJECT_QUERY=`$PKG_CONFIG --variable=gobject_query glib-2.0` + GLIB_MKENUMS=`$PKG_CONFIG --variable=glib_mkenums glib-2.0` + + GLIB_CFLAGS=`$PKG_CONFIG --cflags $pkg_config_args` + GLIB_LIBS=`$PKG_CONFIG --libs $pkg_config_args` + glib_config_major_version=`$PKG_CONFIG --modversion glib-2.0 | \ + sed 's/\([0-9]*\).\([0-9]*\).\([0-9]*\)/\1/'` + glib_config_minor_version=`$PKG_CONFIG --modversion glib-2.0 | \ + sed 's/\([0-9]*\).\([0-9]*\).\([0-9]*\)/\2/'` + glib_config_micro_version=`$PKG_CONFIG --modversion glib-2.0 | \ + sed 's/\([0-9]*\).\([0-9]*\).\([0-9]*\)/\3/'` + if test "x$enable_glibtest" = "xyes" ; then + ac_save_CFLAGS="$CFLAGS" + ac_save_LIBS="$LIBS" + CFLAGS="$CFLAGS $GLIB_CFLAGS" + LIBS="$GLIB_LIBS $LIBS" + rm -f conf.glibtest + if test "$cross_compiling" = yes; then : + echo $ac_n "cross compiling; assumed OK... $ac_c" +else + cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ + +#include +#include +#include + +int +main () +{ + int major, minor, micro; + char *tmp_version; + + system ("touch conf.glibtest"); + + /* HP/UX 9 (%@#!) writes to sscanf strings */ + tmp_version = g_strdup("$min_glib_version"); + if (sscanf(tmp_version, "%d.%d.%d", &major, &minor, µ) != 3) { + printf("%s, bad version string\n", "$min_glib_version"); + exit(1); + } + + if ((glib_major_version != $glib_config_major_version) || + (glib_minor_version != $glib_config_minor_version) || + (glib_micro_version != $glib_config_micro_version)) + { + printf("\n*** 'pkg-config --modversion glib-2.0' returned %d.%d.%d, but GLIB (%d.%d.%d)\n", + $glib_config_major_version, $glib_config_minor_version, $glib_config_micro_version, + glib_major_version, glib_minor_version, glib_micro_version); + printf ("*** was found! If pkg-config was correct, then it is best\n"); + printf ("*** to remove the old version of GLib. You may also be able to fix the error\n"); + printf("*** by modifying your LD_LIBRARY_PATH enviroment variable, or by editing\n"); + printf("*** /etc/ld.so.conf. Make sure you have run ldconfig if that is\n"); + printf("*** required on your system.\n"); + printf("*** If pkg-config was wrong, set the environment variable PKG_CONFIG_PATH\n"); + printf("*** to point to the correct configuration files\n"); + } + else if ((glib_major_version != GLIB_MAJOR_VERSION) || + (glib_minor_version != GLIB_MINOR_VERSION) || + (glib_micro_version != GLIB_MICRO_VERSION)) + { + printf("*** GLIB header files (version %d.%d.%d) do not match\n", + GLIB_MAJOR_VERSION, GLIB_MINOR_VERSION, GLIB_MICRO_VERSION); + printf("*** library (version %d.%d.%d)\n", + glib_major_version, glib_minor_version, glib_micro_version); + } + else + { + if ((glib_major_version > major) || + ((glib_major_version == major) && (glib_minor_version > minor)) || + ((glib_major_version == major) && (glib_minor_version == minor) && (glib_micro_version >= micro))) + { + return 0; + } + else + { + printf("\n*** An old version of GLIB (%d.%d.%d) was found.\n", + glib_major_version, glib_minor_version, glib_micro_version); + printf("*** You need a version of GLIB newer than %d.%d.%d. The latest version of\n", + major, minor, micro); + printf("*** GLIB is always available from ftp://ftp.gtk.org.\n"); + printf("***\n"); + printf("*** If you have already installed a sufficiently new version, this error\n"); + printf("*** probably means that the wrong copy of the pkg-config shell script is\n"); + printf("*** being found. The easiest way to fix this is to remove the old version\n"); + printf("*** of GLIB, but you can also set the PKG_CONFIG environment to point to the\n"); + printf("*** correct copy of pkg-config. (In this case, you will have to\n"); + printf("*** modify your LD_LIBRARY_PATH enviroment variable, or edit /etc/ld.so.conf\n"); + printf("*** so that the correct libraries are found at run-time))\n"); + } + } + return 1; +} + +_ACEOF +if ac_fn_c_try_run "$LINENO"; then : + +else + no_glib=yes +fi +rm -f core *.core core.conftest.* gmon.out bb.out conftest$ac_exeext \ + conftest.$ac_objext conftest.beam conftest.$ac_ext +fi + + CFLAGS="$ac_save_CFLAGS" + LIBS="$ac_save_LIBS" + fi + fi + if test "x$no_glib" = x ; then + { $as_echo "$as_me:${as_lineno-$LINENO}: result: yes (version $glib_config_major_version.$glib_config_minor_version.$glib_config_micro_version)" >&5 +$as_echo "yes (version $glib_config_major_version.$glib_config_minor_version.$glib_config_micro_version)" >&6; } + glib2=true + else + { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 +$as_echo "no" >&6; } + if test "$PKG_CONFIG" = "no" ; then + echo "*** A new enough version of pkg-config was not found." + echo "*** See http://www.freedesktop.org/software/pkgconfig/" + else + if test -f conf.glibtest ; then + : + else + echo "*** Could not run GLIB test program, checking why..." + ac_save_CFLAGS="$CFLAGS" + ac_save_LIBS="$LIBS" + CFLAGS="$CFLAGS $GLIB_CFLAGS" + LIBS="$LIBS $GLIB_LIBS" + cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ + +#include +#include + +int +main () +{ + return ((glib_major_version) || (glib_minor_version) || (glib_micro_version)); + ; + return 0; +} +_ACEOF +if ac_fn_c_try_link "$LINENO"; then : + echo "*** The test program compiled, but did not run. This usually means" + echo "*** that the run-time linker is not finding GLIB or finding the wrong" + echo "*** version of GLIB. If it is not finding GLIB, you'll need to set your" + echo "*** LD_LIBRARY_PATH environment variable, or edit /etc/ld.so.conf to point" + echo "*** to the installed location Also, make sure you have run ldconfig if that" + echo "*** is required on your system" + echo "***" + echo "*** If you have an old version installed, it is best to remove it, although" + echo "*** you may also be able to get things to work by modifying LD_LIBRARY_PATH" +else + echo "*** The test program failed to compile or link. See the file config.log for the" + echo "*** exact error that occured. This usually means GLIB is incorrectly installed." +fi +rm -f core conftest.err conftest.$ac_objext \ + conftest$ac_exeext conftest.$ac_ext + CFLAGS="$ac_save_CFLAGS" + LIBS="$ac_save_LIBS" + fi + fi + GLIB_CFLAGS="" + GLIB_LIBS="" + GLIB_GENMARSHAL="" + GOBJECT_QUERY="" + GLIB_MKENUMS="" + glib2=false + fi + + + + + + rm -f conf.glibtest + +if test x$glib2 = xfalse +then + if false; then + HAVE_GLIB2_TRUE= + HAVE_GLIB2_FALSE='#' +else + HAVE_GLIB2_TRUE='#' + HAVE_GLIB2_FALSE= +fi + + { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: GNUnet requires GLIB >= 2.6.0" >&5 +$as_echo "$as_me: WARNING: GNUnet requires GLIB >= 2.6.0" >&2;} +else + if true; then + HAVE_GLIB2_TRUE= + HAVE_GLIB2_FALSE='#' +else + HAVE_GLIB2_TRUE='#' + HAVE_GLIB2_FALSE= +fi + + +$as_echo "#define HAVE_GLIB2 1" >>confdefs.h + + LIBS="$LIBS $GLIB_LIBS" + CFLAGS="$CFLAGS $GLIB_CFLAGS" +fi + +#libgtop + + succeeded=no + + if test -z "$PKG_CONFIG"; then + # Extract the first word of "pkg-config", so it can be a program name with args. +set dummy pkg-config; ac_word=$2 +{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +$as_echo_n "checking for $ac_word... " >&6; } +if ${ac_cv_path_PKG_CONFIG+:} false; then : + $as_echo_n "(cached) " >&6 +else + case $PKG_CONFIG in + [\\/]* | ?:[\\/]*) + ac_cv_path_PKG_CONFIG="$PKG_CONFIG" # Let the user override the test with a path. + ;; + *) + as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + test -z "$as_dir" && as_dir=. + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then + ac_cv_path_PKG_CONFIG="$as_dir/$ac_word$ac_exec_ext" + $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + + test -z "$ac_cv_path_PKG_CONFIG" && ac_cv_path_PKG_CONFIG="no" + ;; +esac +fi +PKG_CONFIG=$ac_cv_path_PKG_CONFIG +if test -n "$PKG_CONFIG"; then + { $as_echo "$as_me:${as_lineno-$LINENO}: result: $PKG_CONFIG" >&5 +$as_echo "$PKG_CONFIG" >&6; } +else + { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 +$as_echo "no" >&6; } fi -# GLPK must support atm MLP presolving, version >= 4.32 -ac_fn_c_check_member "$LINENO" "glp_iocp" "presolve" "ac_cv_member_glp_iocp_presolve" "#include -" -if test "x$ac_cv_member_glp_iocp_presolve" = x""yes; then : -cat >>confdefs.h <<_ACEOF -#define HAVE_GLP_IOCP_PRESOLVE 1 -_ACEOF + fi + if test "$PKG_CONFIG" = "no" ; then + echo "*** The pkg-config script could not be found. Make sure it is" + echo "*** in your path, or set the PKG_CONFIG environment variable" + echo "*** to the full path to pkg-config." + echo "*** Or see http://www.freedesktop.org/software/pkgconfig to get pkg-config." + else + PKG_CONFIG_MIN_VERSION=0.9.0 + if $PKG_CONFIG --atleast-pkgconfig-version $PKG_CONFIG_MIN_VERSION; then + { $as_echo "$as_me:${as_lineno-$LINENO}: checking for libgtop-2.0" >&5 +$as_echo_n "checking for libgtop-2.0... " >&6; } -else - gplk=false -fi + if $PKG_CONFIG --exists "libgtop-2.0" ; then + { $as_echo "$as_me:${as_lineno-$LINENO}: result: yes" >&5 +$as_echo "yes" >&6; } + succeeded=yes + + { $as_echo "$as_me:${as_lineno-$LINENO}: checking LIBGTOP_CFLAGS" >&5 +$as_echo_n "checking LIBGTOP_CFLAGS... " >&6; } + LIBGTOP_CFLAGS=`$PKG_CONFIG --cflags "libgtop-2.0"` + { $as_echo "$as_me:${as_lineno-$LINENO}: result: $LIBGTOP_CFLAGS" >&5 +$as_echo "$LIBGTOP_CFLAGS" >&6; } + + { $as_echo "$as_me:${as_lineno-$LINENO}: checking LIBGTOP_LIBS" >&5 +$as_echo_n "checking LIBGTOP_LIBS... " >&6; } + LIBGTOP_LIBS=`$PKG_CONFIG --libs "libgtop-2.0"` + { $as_echo "$as_me:${as_lineno-$LINENO}: result: $LIBGTOP_LIBS" >&5 +$as_echo "$LIBGTOP_LIBS" >&6; } + else + LIBGTOP_CFLAGS="" + LIBGTOP_LIBS="" + ## If we have a custom action on failure, don't print errors, but + ## do set a variable so people can do so. + LIBGTOP_PKG_ERRORS=`$PKG_CONFIG --errors-to-stdout --print-errors "libgtop-2.0"` -if test x$gplk = xfalse + fi + + + + else + echo "*** Your version of pkg-config is too old. You need version $PKG_CONFIG_MIN_VERSION or newer." + echo "*** See http://www.freedesktop.org/software/pkgconfig" + fi + fi + + if test $succeeded = yes; then + gtop=true + else + gtop=false + fi + +if test x$gtop = xfalse then if false; then - HAVE_LIBGLPK_TRUE= - HAVE_LIBGLPK_FALSE='#' + HAVE_LIBGTOP_TRUE= + HAVE_LIBGTOP_FALSE='#' else - HAVE_LIBGLPK_TRUE='#' - HAVE_LIBGLPK_FALSE= + HAVE_LIBGTOP_TRUE='#' + HAVE_LIBGTOP_FALSE= fi - { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: GNUnet requires GLPK >= 4.32" >&5 -$as_echo "$as_me: WARNING: GNUnet requires GLPK >= 4.32" >&2;} + { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: GNUnet requires libgtop" >&5 +$as_echo "$as_me: WARNING: GNUnet requires libgtop" >&2;} else if true; then - HAVE_LIBGLPK_TRUE= - HAVE_LIBGLPK_FALSE='#' + HAVE_LIBGTOP_TRUE= + HAVE_LIBGTOP_FALSE='#' else - HAVE_LIBGLPK_TRUE='#' - HAVE_LIBGLPK_FALSE= + HAVE_LIBGTOP_TRUE='#' + HAVE_LIBGTOP_FALSE= fi -$as_echo "#define HAVE_LIBGLPK 1" >>confdefs.h +$as_echo "#define HAVE_LIBGTOP 1" >>confdefs.h + LIBS="$LIBS $LIBGTOP_LIBS" + CFLAGS="$CFLAGS $LIBGTOP_CFLAGS" fi + for ac_header in nss.h do : ac_fn_c_check_header_mongrel "$LINENO" "nss.h" "ac_cv_header_nss_h" "$ac_includes_default" -if test "x$ac_cv_header_nss_h" = x""yes; then : +if test "x$ac_cv_header_nss_h" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_NSS_H 1 _ACEOF @@ -20219,7 +21601,7 @@ fi # test for kvm and kstat (for CPU stats under BSD/Solaris) { $as_echo "$as_me:${as_lineno-$LINENO}: checking for kvm_open in -lkvm" >&5 $as_echo_n "checking for kvm_open in -lkvm... " >&6; } -if test "${ac_cv_lib_kvm_kvm_open+set}" = set; then : +if ${ac_cv_lib_kvm_kvm_open+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS @@ -20253,7 +21635,7 @@ LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_kvm_kvm_open" >&5 $as_echo "$ac_cv_lib_kvm_kvm_open" >&6; } -if test "x$ac_cv_lib_kvm_kvm_open" = x""yes; then : +if test "x$ac_cv_lib_kvm_kvm_open" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_LIBKVM 1 _ACEOF @@ -20264,7 +21646,7 @@ fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking for kstat_open in -lkstat" >&5 $as_echo_n "checking for kstat_open in -lkstat... " >&6; } -if test "${ac_cv_lib_kstat_kstat_open+set}" = set; then : +if ${ac_cv_lib_kstat_kstat_open+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS @@ -20298,7 +21680,7 @@ LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_kstat_kstat_open" >&5 $as_echo "$ac_cv_lib_kstat_kstat_open" >&6; } -if test "x$ac_cv_lib_kstat_kstat_open" = x""yes; then : +if test "x$ac_cv_lib_kstat_kstat_open" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_LIBKSTAT 1 _ACEOF @@ -20324,13 +21706,13 @@ $as_echo "$with_extractor" >&6; } for ac_header in extractor.h do : ac_fn_c_check_header_mongrel "$LINENO" "extractor.h" "ac_cv_header_extractor_h" "$ac_includes_default" -if test "x$ac_cv_header_extractor_h" = x""yes; then : +if test "x$ac_cv_header_extractor_h" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_EXTRACTOR_H 1 _ACEOF { $as_echo "$as_me:${as_lineno-$LINENO}: checking for EXTRACTOR_plugin_add_defaults in -lextractor" >&5 $as_echo_n "checking for EXTRACTOR_plugin_add_defaults in -lextractor... " >&6; } -if test "${ac_cv_lib_extractor_EXTRACTOR_plugin_add_defaults+set}" = set; then : +if ${ac_cv_lib_extractor_EXTRACTOR_plugin_add_defaults+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS @@ -20364,7 +21746,7 @@ LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_extractor_EXTRACTOR_plugin_add_defaults" >&5 $as_echo "$ac_cv_lib_extractor_EXTRACTOR_plugin_add_defaults" >&6; } -if test "x$ac_cv_lib_extractor_EXTRACTOR_plugin_add_defaults" = x""yes; then : +if test "x$ac_cv_lib_extractor_EXTRACTOR_plugin_add_defaults" = xyes; then : extractor=1 fi @@ -20379,13 +21761,13 @@ done for ac_header in extractor.h do : ac_fn_c_check_header_mongrel "$LINENO" "extractor.h" "ac_cv_header_extractor_h" "$ac_includes_default" -if test "x$ac_cv_header_extractor_h" = x""yes; then : +if test "x$ac_cv_header_extractor_h" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_EXTRACTOR_H 1 _ACEOF { $as_echo "$as_me:${as_lineno-$LINENO}: checking for EXTRACTOR_plugin_add_defaults in -lextractor" >&5 $as_echo_n "checking for EXTRACTOR_plugin_add_defaults in -lextractor... " >&6; } -if test "${ac_cv_lib_extractor_EXTRACTOR_plugin_add_defaults+set}" = set; then : +if ${ac_cv_lib_extractor_EXTRACTOR_plugin_add_defaults+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS @@ -20419,7 +21801,7 @@ LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_extractor_EXTRACTOR_plugin_add_defaults" >&5 $as_echo "$ac_cv_lib_extractor_EXTRACTOR_plugin_add_defaults" >&6; } -if test "x$ac_cv_lib_extractor_EXTRACTOR_plugin_add_defaults" = x""yes; then : +if test "x$ac_cv_lib_extractor_EXTRACTOR_plugin_add_defaults" = xyes; then : EXT_LIB_PATH="-L$with_extractor/lib $EXT_LIB_PATH" extractor=1 fi @@ -20437,13 +21819,13 @@ $as_echo "--with-extractor not specified" >&6; } for ac_header in extractor.h do : ac_fn_c_check_header_mongrel "$LINENO" "extractor.h" "ac_cv_header_extractor_h" "$ac_includes_default" -if test "x$ac_cv_header_extractor_h" = x""yes; then : +if test "x$ac_cv_header_extractor_h" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_EXTRACTOR_H 1 _ACEOF { $as_echo "$as_me:${as_lineno-$LINENO}: checking for EXTRACTOR_plugin_add_defaults in -lextractor" >&5 $as_echo_n "checking for EXTRACTOR_plugin_add_defaults in -lextractor... " >&6; } -if test "${ac_cv_lib_extractor_EXTRACTOR_plugin_add_defaults+set}" = set; then : +if ${ac_cv_lib_extractor_EXTRACTOR_plugin_add_defaults+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS @@ -20477,7 +21859,7 @@ LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_extractor_EXTRACTOR_plugin_add_defaults" >&5 $as_echo "$ac_cv_lib_extractor_EXTRACTOR_plugin_add_defaults" >&6; } -if test "x$ac_cv_lib_extractor_EXTRACTOR_plugin_add_defaults" = x""yes; then : +if test "x$ac_cv_lib_extractor_EXTRACTOR_plugin_add_defaults" = xyes; then : extractor=1 fi @@ -20571,7 +21953,7 @@ else { $as_echo "$as_me:${as_lineno-$LINENO}: checking for non-GNU ld" >&5 $as_echo_n "checking for non-GNU ld... " >&6; } fi -if test "${acl_cv_path_LD+set}" = set; then : +if ${acl_cv_path_LD+:} false; then : $as_echo_n "(cached) " >&6 else if test -z "$LD"; then @@ -20608,7 +21990,7 @@ fi test -z "$LD" && as_fn_error $? "no acceptable ld found in \$PATH" "$LINENO" 5 { $as_echo "$as_me:${as_lineno-$LINENO}: checking if the linker ($LD) is GNU ld" >&5 $as_echo_n "checking if the linker ($LD) is GNU ld... " >&6; } -if test "${acl_cv_prog_gnu_ld+set}" = set; then : +if ${acl_cv_prog_gnu_ld+:} false; then : $as_echo_n "(cached) " >&6 else # I'd rather use --version here, but apparently some GNU ld's only accept -v. @@ -20628,7 +22010,7 @@ with_gnu_ld=$acl_cv_prog_gnu_ld { $as_echo "$as_me:${as_lineno-$LINENO}: checking for shared library run path origin" >&5 $as_echo_n "checking for shared library run path origin... " >&6; } -if test "${acl_cv_rpath+set}" = set; then : +if ${acl_cv_rpath+:} false; then : $as_echo_n "(cached) " >&6 else @@ -21105,7 +22487,7 @@ fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking for iconv" >&5 $as_echo_n "checking for iconv... " >&6; } -if test "${am_cv_func_iconv+set}" = set; then : +if ${am_cv_func_iconv+:} false; then : $as_echo_n "(cached) " >&6 else @@ -21180,7 +22562,7 @@ $as_echo "$LIBICONV" >&6; } if test "$am_cv_func_iconv" = yes; then { $as_echo "$as_me:${as_lineno-$LINENO}: checking for iconv declaration" >&5 $as_echo_n "checking for iconv declaration... " >&6; } - if test "${am_cv_proto_iconv+set}" = set; then : + if ${am_cv_proto_iconv+:} false; then : $as_echo_n "(cached) " >&6 else @@ -21663,7 +23045,7 @@ fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking for libunistring" >&5 $as_echo_n "checking for libunistring... " >&6; } -if test "${ac_cv_libunistring+set}" = set; then : +if ${ac_cv_libunistring+:} false; then : $as_echo_n "(cached) " >&6 else @@ -22144,7 +23526,7 @@ fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking for libunistring" >&5 $as_echo_n "checking for libunistring... " >&6; } -if test "${ac_cv_libunistring+set}" = set; then : +if ${ac_cv_libunistring+:} false; then : $as_echo_n "(cached) " >&6 else @@ -22628,7 +24010,7 @@ fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking for libunistring" >&5 $as_echo_n "checking for libunistring... " >&6; } -if test "${ac_cv_libunistring+set}" = set; then : +if ${ac_cv_libunistring+:} false; then : $as_echo_n "(cached) " >&6 else @@ -22682,7 +24064,7 @@ $as_echo "$LIBUNISTRING" >&6; } if test $HAVE_LIBUNISTRING = yes; then { $as_echo "$as_me:${as_lineno-$LINENO}: checking for libunistring version" >&5 $as_echo_n "checking for libunistring version... " >&6; } -if test "${gl_cv_libunistring_version+set}" = set; then : +if ${gl_cv_libunistring_version+:} false; then : $as_echo_n "(cached) " >&6 else if ac_fn_c_compute_int "$LINENO" "_LIBUNISTRING_VERSION" "gl_libunistring_hexversion" "#include "; then : @@ -22786,7 +24168,7 @@ for ac_hdr in dirent.h sys/ndir.h sys/dir.h ndir.h; do as_ac_Header=`$as_echo "ac_cv_header_dirent_$ac_hdr" | $as_tr_sh` { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_hdr that defines DIR" >&5 $as_echo_n "checking for $ac_hdr that defines DIR... " >&6; } -if eval "test \"\${$as_ac_Header+set}\"" = set; then : +if eval \${$as_ac_Header+:} false; then : $as_echo_n "(cached) " >&6 else cat confdefs.h - <<_ACEOF >conftest.$ac_ext @@ -22826,7 +24208,7 @@ done if test $ac_header_dirent = dirent.h; then { $as_echo "$as_me:${as_lineno-$LINENO}: checking for library containing opendir" >&5 $as_echo_n "checking for library containing opendir... " >&6; } -if test "${ac_cv_search_opendir+set}" = set; then : +if ${ac_cv_search_opendir+:} false; then : $as_echo_n "(cached) " >&6 else ac_func_search_save_LIBS=$LIBS @@ -22860,11 +24242,11 @@ for ac_lib in '' dir; do fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext - if test "${ac_cv_search_opendir+set}" = set; then : + if ${ac_cv_search_opendir+:} false; then : break fi done -if test "${ac_cv_search_opendir+set}" = set; then : +if ${ac_cv_search_opendir+:} false; then : else ac_cv_search_opendir=no @@ -22883,7 +24265,7 @@ fi else { $as_echo "$as_me:${as_lineno-$LINENO}: checking for library containing opendir" >&5 $as_echo_n "checking for library containing opendir... " >&6; } -if test "${ac_cv_search_opendir+set}" = set; then : +if ${ac_cv_search_opendir+:} false; then : $as_echo_n "(cached) " >&6 else ac_func_search_save_LIBS=$LIBS @@ -22917,11 +24299,11 @@ for ac_lib in '' x; do fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext - if test "${ac_cv_search_opendir+set}" = set; then : + if ${ac_cv_search_opendir+:} false; then : break fi done -if test "${ac_cv_search_opendir+set}" = set; then : +if ${ac_cv_search_opendir+:} false; then : else ac_cv_search_opendir=no @@ -22941,7 +24323,7 @@ fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking for ANSI C header files" >&5 $as_echo_n "checking for ANSI C header files... " >&6; } -if test "${ac_cv_header_stdc+set}" = set; then : +if ${ac_cv_header_stdc+:} false; then : $as_echo_n "(cached) " >&6 else cat confdefs.h - <<_ACEOF >conftest.$ac_ext @@ -23070,7 +24452,7 @@ done # Checks for headers that are only required on some systems or opional (and where we do NOT abort if they are not there) -for ac_header in langinfo.h sys/param.h sys/mount.h sys/statvfs.h sys/select.h sockLib.h sys/mman.h sys/msg.h sys/vfs.h arpa/inet.h fcntl.h libintl.h netdb.h netinet/in.h netinet/in_systm.h sys/ioctl.h sys/socket.h sys/time.h unistd.h kstat.h sys/sysinfo.h kvm.h sys/file.h sys/resource.h ifaddrs.h mach/mach.h stddef.h sys/timeb.h terminos.h argz.h ucred.h endian.h sys/endian.h +for ac_header in malloc.h malloc/malloc.h langinfo.h sys/param.h sys/mount.h sys/statvfs.h sys/select.h sockLib.h sys/mman.h sys/msg.h sys/vfs.h arpa/inet.h fcntl.h libintl.h netdb.h netinet/in.h netinet/in_systm.h sys/ioctl.h sys/socket.h sys/time.h unistd.h kstat.h sys/sysinfo.h kvm.h sys/file.h sys/resource.h ifaddrs.h mach/mach.h stddef.h sys/timeb.h terminos.h argz.h ucred.h endian.h sys/endian.h execinfo.h do : as_ac_Header=`$as_echo "ac_cv_header_$ac_header" | $as_tr_sh` ac_fn_c_check_header_mongrel "$LINENO" "$ac_header" "$as_ac_Header" "$ac_includes_default" @@ -23103,7 +24485,7 @@ $as_echo "\"$with_sqlite\"" >&6; } for ac_header in sqlite3.h do : ac_fn_c_check_header_mongrel "$LINENO" "sqlite3.h" "ac_cv_header_sqlite3_h" "$ac_includes_default" -if test "x$ac_cv_header_sqlite3_h" = x""yes; then : +if test "x$ac_cv_header_sqlite3_h" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_SQLITE3_H 1 _ACEOF @@ -23119,7 +24501,7 @@ done for ac_header in sqlite3.h do : ac_fn_c_check_header_mongrel "$LINENO" "sqlite3.h" "ac_cv_header_sqlite3_h" "$ac_includes_default" -if test "x$ac_cv_header_sqlite3_h" = x""yes; then : +if test "x$ac_cv_header_sqlite3_h" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_SQLITE3_H 1 _ACEOF @@ -23142,7 +24524,7 @@ $as_echo "--with-sqlite not specified" >&6; } for ac_header in sqlite3.h do : ac_fn_c_check_header_mongrel "$LINENO" "sqlite3.h" "ac_cv_header_sqlite3_h" "$ac_includes_default" -if test "x$ac_cv_header_sqlite3_h" = x""yes; then : +if test "x$ac_cv_header_sqlite3_h" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_SQLITE3_H 1 _ACEOF @@ -23180,7 +24562,7 @@ $as_echo "\"$with_postgres\"" >&6; } for ac_header in postgresql/libpq-fe.h do : ac_fn_c_check_header_mongrel "$LINENO" "postgresql/libpq-fe.h" "ac_cv_header_postgresql_libpq_fe_h" "$ac_includes_default" -if test "x$ac_cv_header_postgresql_libpq_fe_h" = x""yes; then : +if test "x$ac_cv_header_postgresql_libpq_fe_h" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_POSTGRESQL_LIBPQ_FE_H 1 _ACEOF @@ -23196,7 +24578,7 @@ done for ac_header in postgresql/libpq-fe.h do : ac_fn_c_check_header_mongrel "$LINENO" "postgresql/libpq-fe.h" "ac_cv_header_postgresql_libpq_fe_h" "$ac_includes_default" -if test "x$ac_cv_header_postgresql_libpq_fe_h" = x""yes; then : +if test "x$ac_cv_header_postgresql_libpq_fe_h" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_POSTGRESQL_LIBPQ_FE_H 1 _ACEOF @@ -23219,7 +24601,7 @@ $as_echo "--with-postgres not specified" >&6; } for ac_header in postgresql/libpq-fe.h do : ac_fn_c_check_header_mongrel "$LINENO" "postgresql/libpq-fe.h" "ac_cv_header_postgresql_libpq_fe_h" "$ac_includes_default" -if test "x$ac_cv_header_postgresql_libpq_fe_h" = x""yes; then : +if test "x$ac_cv_header_postgresql_libpq_fe_h" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_POSTGRESQL_LIBPQ_FE_H 1 _ACEOF @@ -23245,7 +24627,7 @@ fi zlib=1 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for compress in -lz" >&5 $as_echo_n "checking for compress in -lz... " >&6; } -if test "${ac_cv_lib_z_compress+set}" = set; then : +if ${ac_cv_lib_z_compress+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS @@ -23279,7 +24661,7 @@ LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_z_compress" >&5 $as_echo "$ac_cv_lib_z_compress" >&6; } -if test "x$ac_cv_lib_z_compress" = x""yes; then : +if test "x$ac_cv_lib_z_compress" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_LIBZ 1 _ACEOF @@ -23306,7 +24688,7 @@ fi # mysql & windows ac_fn_c_check_type "$LINENO" "sigset_t" "ac_cv_type_sigset_t" "#include " -if test "x$ac_cv_type_sigset_t" = x""yes; then : +if test "x$ac_cv_type_sigset_t" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_SIGSET_T 1 @@ -23316,7 +24698,7 @@ _ACEOF fi ac_fn_c_check_type "$LINENO" "off_t" "ac_cv_type_off_t" "#include " -if test "x$ac_cv_type_off_t" = x""yes; then : +if test "x$ac_cv_type_off_t" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_OFF_T 1 @@ -23327,7 +24709,7 @@ fi ac_fn_c_check_type "$LINENO" "size_t" "ac_cv_type_size_t" "#include " -if test "x$ac_cv_type_size_t" = x""yes; then : +if test "x$ac_cv_type_size_t" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_SIZE_T 1 @@ -23365,13 +24747,13 @@ $as_echo "\"$with_mysql\"" >&6; } do : ac_fn_c_check_header_compile "$LINENO" "mysql/mysql.h" "ac_cv_header_mysql_mysql_h" "$CYGWIN_MYSQL_MAGIC " -if test "x$ac_cv_header_mysql_mysql_h" = x""yes; then : +if test "x$ac_cv_header_mysql_mysql_h" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_MYSQL_MYSQL_H 1 _ACEOF { $as_echo "$as_me:${as_lineno-$LINENO}: checking for mysql_init in -lmysqlclient" >&5 $as_echo_n "checking for mysql_init in -lmysqlclient... " >&6; } -if test "${ac_cv_lib_mysqlclient_mysql_init+set}" = set; then : +if ${ac_cv_lib_mysqlclient_mysql_init+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS @@ -23405,7 +24787,7 @@ LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_mysqlclient_mysql_init" >&5 $as_echo "$ac_cv_lib_mysqlclient_mysql_init" >&6; } -if test "x$ac_cv_lib_mysqlclient_mysql_init" = x""yes; then : +if test "x$ac_cv_lib_mysqlclient_mysql_init" = xyes; then : MYSQL_LDFLAGS="-L$with_mysql/lib -L$with_mysql/lib/mysql" MYSQL_CPPFLAGS="-I$with_mysql/include" @@ -23421,10 +24803,17 @@ done else { $as_echo "$as_me:${as_lineno-$LINENO}: result: --with-mysql not specified" >&5 $as_echo "--with-mysql not specified" >&6; } - LDFLAGS="-L/usr/lib/mysql $LDFLAGS $ZLIBS" + if test -d "/usr/lib64/mysql"; then + MYSQL_LIBDIR="/usr/lib64/mysql" + elif test -d "/usr/lib/mysql"; then + MYSQL_LIBDIR="/usr/lib/mysql" + else + MYSQL_LIBDIR="/usr/lib" + fi + LDFLAGS="-L$MYSQL_LIBDIR $LDFLAGS $ZLIBS" { $as_echo "$as_me:${as_lineno-$LINENO}: checking for mysql_init in -lmysqlclient" >&5 $as_echo_n "checking for mysql_init in -lmysqlclient... " >&6; } -if test "${ac_cv_lib_mysqlclient_mysql_init+set}" = set; then : +if ${ac_cv_lib_mysqlclient_mysql_init+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS @@ -23458,16 +24847,16 @@ LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_mysqlclient_mysql_init" >&5 $as_echo "$ac_cv_lib_mysqlclient_mysql_init" >&6; } -if test "x$ac_cv_lib_mysqlclient_mysql_init" = x""yes; then : +if test "x$ac_cv_lib_mysqlclient_mysql_init" = xyes; then : for ac_header in mysql/mysql.h do : ac_fn_c_check_header_compile "$LINENO" "mysql/mysql.h" "ac_cv_header_mysql_mysql_h" "$CYGWIN_MYSQL_MAGIC " -if test "x$ac_cv_header_mysql_mysql_h" = x""yes; then : +if test "x$ac_cv_header_mysql_mysql_h" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_MYSQL_MYSQL_H 1 _ACEOF - MYSQL_LDFLAGS="-L/usr/lib/mysql" + MYSQL_LDFLAGS="-L$MYSQL_LIBDIR" mysql=true @@ -23500,7 +24889,7 @@ $as_echo_n "checking mysql version... " >&6; } { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 $as_echo "$as_me: error: in \`$ac_pwd':" >&2;} as_fn_error $? "cannot run test program while cross compiling -See \`config.log' for more details" "$LINENO" 5 ; } +See \`config.log' for more details" "$LINENO" 5; } else cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ @@ -23579,19 +24968,19 @@ $as_echo "$with_microhttpd" >&6; } yes) for ac_header in microhttpd.h do : - ac_fn_c_check_header_compile "$LINENO" "microhttpd.h" "ac_cv_header_microhttpd_h" "#include \"$srcdir/src/include/platform.h\" + ac_fn_c_check_header_compile "$LINENO" "microhttpd.h" "ac_cv_header_microhttpd_h" "#include \"$native_srcdir/src/include/platform.h\" " -if test "x$ac_cv_header_microhttpd_h" = x""yes; then : +if test "x$ac_cv_header_microhttpd_h" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_MICROHTTPD_H 1 _ACEOF - ac_fn_c_check_decl "$LINENO" "MHD_OPTION_PER_IP_CONNECTION_LIMIT" "ac_cv_have_decl_MHD_OPTION_PER_IP_CONNECTION_LIMIT" "#include \"$srcdir/src/include/platform.h\" + ac_fn_c_check_decl "$LINENO" "MHD_OPTION_PER_IP_CONNECTION_LIMIT" "ac_cv_have_decl_MHD_OPTION_PER_IP_CONNECTION_LIMIT" "#include \"$native_srcdir/src/include/platform.h\" #include " -if test "x$ac_cv_have_decl_MHD_OPTION_PER_IP_CONNECTION_LIMIT" = x""yes; then : +if test "x$ac_cv_have_decl_MHD_OPTION_PER_IP_CONNECTION_LIMIT" = xyes; then : { $as_echo "$as_me:${as_lineno-$LINENO}: checking for MHD_start_daemon in -lmicrohttpd" >&5 $as_echo_n "checking for MHD_start_daemon in -lmicrohttpd... " >&6; } -if test "${ac_cv_lib_microhttpd_MHD_start_daemon+set}" = set; then : +if ${ac_cv_lib_microhttpd_MHD_start_daemon+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS @@ -23625,7 +25014,7 @@ LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_microhttpd_MHD_start_daemon" >&5 $as_echo "$ac_cv_lib_microhttpd_MHD_start_daemon" >&6; } -if test "x$ac_cv_lib_microhttpd_MHD_start_daemon" = x""yes; then : +if test "x$ac_cv_lib_microhttpd_MHD_start_daemon" = xyes; then : { $as_echo "$as_me:${as_lineno-$LINENO}: checking for libmicrohttpd >= 0.9.18" >&5 $as_echo_n "checking for libmicrohttpd >= 0.9.18... " >&6; } if test "$cross_compiling" = yes; then : @@ -23634,7 +25023,7 @@ else cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ - #include "$srcdir/src/include/platform.h" + #include "$native_srcdir/src/include/platform.h" #include int main () { return MHD_VERSION >= 0x0091200 ? 0 : 1; } @@ -23666,19 +25055,19 @@ done CPPFLAGS="-I$with_microhttpd/include $CPPFLAGS" for ac_header in microhttpd.h do : - ac_fn_c_check_header_compile "$LINENO" "microhttpd.h" "ac_cv_header_microhttpd_h" "#include \"$srcdir/src/include/platform.h\" + ac_fn_c_check_header_compile "$LINENO" "microhttpd.h" "ac_cv_header_microhttpd_h" "#include \"$native_srcdir/src/include/platform.h\" " -if test "x$ac_cv_header_microhttpd_h" = x""yes; then : +if test "x$ac_cv_header_microhttpd_h" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_MICROHTTPD_H 1 _ACEOF - ac_fn_c_check_decl "$LINENO" "MHD_OPTION_PER_IP_CONNECTION_LIMIT" "ac_cv_have_decl_MHD_OPTION_PER_IP_CONNECTION_LIMIT" "#include \"$srcdir/src/include/platform.h\" + ac_fn_c_check_decl "$LINENO" "MHD_OPTION_PER_IP_CONNECTION_LIMIT" "ac_cv_have_decl_MHD_OPTION_PER_IP_CONNECTION_LIMIT" "#include \"$native_srcdir/src/include/platform.h\" #include " -if test "x$ac_cv_have_decl_MHD_OPTION_PER_IP_CONNECTION_LIMIT" = x""yes; then : +if test "x$ac_cv_have_decl_MHD_OPTION_PER_IP_CONNECTION_LIMIT" = xyes; then : { $as_echo "$as_me:${as_lineno-$LINENO}: checking for MHD_start_daemon in -lmicrohttpd" >&5 $as_echo_n "checking for MHD_start_daemon in -lmicrohttpd... " >&6; } -if test "${ac_cv_lib_microhttpd_MHD_start_daemon+set}" = set; then : +if ${ac_cv_lib_microhttpd_MHD_start_daemon+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS @@ -23712,7 +25101,7 @@ LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_microhttpd_MHD_start_daemon" >&5 $as_echo "$ac_cv_lib_microhttpd_MHD_start_daemon" >&6; } -if test "x$ac_cv_lib_microhttpd_MHD_start_daemon" = x""yes; then : +if test "x$ac_cv_lib_microhttpd_MHD_start_daemon" = xyes; then : EXT_LIB_PATH="-L$with_microhttpd/lib $EXT_LIB_PATH" { $as_echo "$as_me:${as_lineno-$LINENO}: checking for libmicrohttpd >= 0.9.18" >&5 $as_echo_n "checking for libmicrohttpd >= 0.9.18... " >&6; } @@ -23722,7 +25111,7 @@ else cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ - #include "$srcdir/src/include/platform.h" + #include "$native_srcdir/src/include/platform.h" #include int main () { return MHD_VERSION >= 0x0091200 ? 0 : 1; } @@ -23756,19 +25145,19 @@ else $as_echo "--with-microhttpd not specified" >&6; } for ac_header in microhttpd.h do : - ac_fn_c_check_header_compile "$LINENO" "microhttpd.h" "ac_cv_header_microhttpd_h" "#include \"$srcdir/src/include/platform.h\" + ac_fn_c_check_header_compile "$LINENO" "microhttpd.h" "ac_cv_header_microhttpd_h" "#include \"$native_srcdir/src/include/platform.h\" " -if test "x$ac_cv_header_microhttpd_h" = x""yes; then : +if test "x$ac_cv_header_microhttpd_h" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_MICROHTTPD_H 1 _ACEOF - ac_fn_c_check_decl "$LINENO" "MHD_OPTION_PER_IP_CONNECTION_LIMIT" "ac_cv_have_decl_MHD_OPTION_PER_IP_CONNECTION_LIMIT" "#include \"$srcdir/src/include/platform.h\" + ac_fn_c_check_decl "$LINENO" "MHD_OPTION_PER_IP_CONNECTION_LIMIT" "ac_cv_have_decl_MHD_OPTION_PER_IP_CONNECTION_LIMIT" "#include \"$native_srcdir/src/include/platform.h\" #include " -if test "x$ac_cv_have_decl_MHD_OPTION_PER_IP_CONNECTION_LIMIT" = x""yes; then : +if test "x$ac_cv_have_decl_MHD_OPTION_PER_IP_CONNECTION_LIMIT" = xyes; then : { $as_echo "$as_me:${as_lineno-$LINENO}: checking for MHD_start_daemon in -lmicrohttpd" >&5 $as_echo_n "checking for MHD_start_daemon in -lmicrohttpd... " >&6; } -if test "${ac_cv_lib_microhttpd_MHD_start_daemon+set}" = set; then : +if ${ac_cv_lib_microhttpd_MHD_start_daemon+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS @@ -23802,7 +25191,7 @@ LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_microhttpd_MHD_start_daemon" >&5 $as_echo "$ac_cv_lib_microhttpd_MHD_start_daemon" >&6; } -if test "x$ac_cv_lib_microhttpd_MHD_start_daemon" = x""yes; then : +if test "x$ac_cv_lib_microhttpd_MHD_start_daemon" = xyes; then : { $as_echo "$as_me:${as_lineno-$LINENO}: checking for libmicrohttpd >= 0.9.18" >&5 $as_echo_n "checking for libmicrohttpd >= 0.9.18... " >&6; } if test "$cross_compiling" = yes; then : @@ -23811,7 +25200,7 @@ else cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ - #include "$srcdir/src/include/platform.h" + #include "$native_srcdir/src/include/platform.h" #include int main () { return MHD_VERSION >= 0x0091200 ? 0 : 1; } @@ -23862,6 +25251,8 @@ LIBS=$SAVE_LIBS + + if test -n "$PYTHON"; then # If the user set $PYTHON, use it and don't search something else. { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether $PYTHON version >= 2.6" >&5 @@ -23891,11 +25282,11 @@ fi # VERSION. { $as_echo "$as_me:${as_lineno-$LINENO}: checking for a Python interpreter with version >= 2.6" >&5 $as_echo_n "checking for a Python interpreter with version >= 2.6... " >&6; } -if test "${am_cv_pathless_PYTHON+set}" = set; then : +if ${am_cv_pathless_PYTHON+:} false; then : $as_echo_n "(cached) " >&6 else - for am_cv_pathless_PYTHON in python python2 python3 python3.0 python2.5 python2.4 python2.3 python2.2 python2.1 python2.0 none; do + for am_cv_pathless_PYTHON in python python2 python3 python3.2 python3.1 python3.0 python2.7 python2.6 python2.5 python2.4 python2.3 python2.2 python2.1 python2.0 none; do test "$am_cv_pathless_PYTHON" = none && break prog="import sys # split strings by '.' and convert to numeric. Append some zeros @@ -23925,7 +25316,7 @@ $as_echo "$am_cv_pathless_PYTHON" >&6; } set dummy $am_cv_pathless_PYTHON; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } -if test "${ac_cv_path_PYTHON+set}" = set; then : +if ${ac_cv_path_PYTHON+:} false; then : $as_echo_n "(cached) " >&6 else case $PYTHON in @@ -23939,7 +25330,7 @@ do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do - if { test -f "$as_dir/$ac_word$ac_exec_ext" && $as_test_x "$as_dir/$ac_word$ac_exec_ext"; }; then + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_path_PYTHON="$as_dir/$ac_word$ac_exec_ext" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 @@ -23973,7 +25364,7 @@ fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $am_display_PYTHON version" >&5 $as_echo_n "checking for $am_display_PYTHON version... " >&6; } -if test "${am_cv_python_version+set}" = set; then : +if ${am_cv_python_version+:} false; then : $as_echo_n "(cached) " >&6 else am_cv_python_version=`$PYTHON -c "import sys; sys.stdout.write(sys.version[:3])"` @@ -23992,7 +25383,7 @@ $as_echo "$am_cv_python_version" >&6; } { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $am_display_PYTHON platform" >&5 $as_echo_n "checking for $am_display_PYTHON platform... " >&6; } -if test "${am_cv_python_platform+set}" = set; then : +if ${am_cv_python_platform+:} false; then : $as_echo_n "(cached) " >&6 else am_cv_python_platform=`$PYTHON -c "import sys; sys.stdout.write(sys.platform)"` @@ -24004,9 +25395,9 @@ $as_echo "$am_cv_python_platform" >&6; } - { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $am_display_PYTHON script directory" >&5 + { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $am_display_PYTHON script directory" >&5 $as_echo_n "checking for $am_display_PYTHON script directory... " >&6; } -if test "${am_cv_python_pythondir+set}" = set; then : +if ${am_cv_python_pythondir+:} false; then : $as_echo_n "(cached) " >&6 else if test "x$prefix" = xNONE @@ -24015,8 +25406,7 @@ else else am_py_prefix=$prefix fi - am_cv_python_pythondir=`$PYTHON -c "import sys; from distutils import sysconfig; sys.stdout.write(sysconfig.get_python_lib(0,0,prefix='$am_py_prefix'))" 2>/dev/null || - echo "$PYTHON_PREFIX/lib/python$PYTHON_VERSION/site-packages"` + am_cv_python_pythondir=`$PYTHON -c "import sys; from distutils import sysconfig; sys.stdout.write(sysconfig.get_python_lib(0,0,prefix='$am_py_prefix'))" 2>/dev/null` case $am_cv_python_pythondir in $am_py_prefix*) am__strip_prefix=`echo "$am_py_prefix" | sed 's|.|.|g'` @@ -24042,9 +25432,9 @@ $as_echo "$am_cv_python_pythondir" >&6; } pkgpythondir=\${pythondir}/$PACKAGE - { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $am_display_PYTHON extension module directory" >&5 + { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $am_display_PYTHON extension module directory" >&5 $as_echo_n "checking for $am_display_PYTHON extension module directory... " >&6; } -if test "${am_cv_python_pyexecdir+set}" = set; then : +if ${am_cv_python_pyexecdir+:} false; then : $as_echo_n "(cached) " >&6 else if test "x$exec_prefix" = xNONE @@ -24053,8 +25443,7 @@ else else am_py_exec_prefix=$exec_prefix fi - am_cv_python_pyexecdir=`$PYTHON -c "import sys; from distutils import sysconfig; sys.stdout.write(sysconfig.get_python_lib(1,0,prefix='$am_py_exec_prefix'))" 2>/dev/null || - echo "$PYTHON_EXEC_PREFIX/lib/python$PYTHON_VERSION/site-packages"` + am_cv_python_pyexecdir=`$PYTHON -c "import sys; from distutils import sysconfig; sys.stdout.write(sysconfig.get_python_lib(1,0,prefix='$am_py_exec_prefix'))" 2>/dev/null` case $am_cv_python_pyexecdir in $am_py_exec_prefix*) am__strip_prefix=`echo "$am_py_exec_prefix" | sed 's|.|.|g'` @@ -24093,40 +25482,6 @@ else fi -if test "$PYTHON" != : -then - { $as_echo "$as_me:${as_lineno-$LINENO}: checking for pexpect" >&5 -$as_echo_n "checking for pexpect... " >&6; } - $PYTHON -c "import pexpect" > /dev/null 2> /dev/null - PYEX=$? - if test $PYEX -eq 0; then - HAVE_PYTHON_PEXPECT_TRUE= - HAVE_PYTHON_PEXPECT_FALSE='#' -else - HAVE_PYTHON_PEXPECT_TRUE='#' - HAVE_PYTHON_PEXPECT_FALSE= -fi - - if test $PYEX -eq 0 - then - { $as_echo "$as_me:${as_lineno-$LINENO}: result: yes" >&5 -$as_echo "yes" >&6; } - else - { $as_echo "$as_me:${as_lineno-$LINENO}: result: not found" >&5 -$as_echo "not found" >&6; } - fi -else - if 0; then - HAVE_PYTHON_PEXPECT_TRUE= - HAVE_PYTHON_PEXPECT_FALSE='#' -else - HAVE_PYTHON_PEXPECT_TRUE='#' - HAVE_PYTHON_PEXPECT_FALSE= -fi - -fi - - # check for gettext { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether NLS is requested" >&5 @@ -24178,7 +25533,7 @@ rm -f conf$$.file set dummy msgfmt; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } -if test "${ac_cv_path_MSGFMT+set}" = set; then : +if ${ac_cv_path_MSGFMT+:} false; then : $as_echo_n "(cached) " >&6 else case "$MSGFMT" in @@ -24219,7 +25574,7 @@ fi set dummy gmsgfmt; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } -if test "${ac_cv_path_GMSGFMT+set}" = set; then : +if ${ac_cv_path_GMSGFMT+:} false; then : $as_echo_n "(cached) " >&6 else case $GMSGFMT in @@ -24233,7 +25588,7 @@ do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do - if { test -f "$as_dir/$ac_word$ac_exec_ext" && $as_test_x "$as_dir/$ac_word$ac_exec_ext"; }; then + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_path_GMSGFMT="$as_dir/$ac_word$ac_exec_ext" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 @@ -24301,7 +25656,7 @@ rm -f conf$$.file set dummy xgettext; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } -if test "${ac_cv_path_XGETTEXT+set}" = set; then : +if ${ac_cv_path_XGETTEXT+:} false; then : $as_echo_n "(cached) " >&6 else case "$XGETTEXT" in @@ -24379,7 +25734,7 @@ rm -f conf$$.file set dummy msgmerge; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } -if test "${ac_cv_path_MSGMERGE+set}" = set; then : +if ${ac_cv_path_MSGMERGE+:} false; then : $as_echo_n "(cached) " >&6 else case "$MSGMERGE" in @@ -24447,7 +25802,7 @@ fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking for CFPreferencesCopyAppValue" >&5 $as_echo_n "checking for CFPreferencesCopyAppValue... " >&6; } -if test "${gt_cv_func_CFPreferencesCopyAppValue+set}" = set; then : +if ${gt_cv_func_CFPreferencesCopyAppValue+:} false; then : $as_echo_n "(cached) " >&6 else gt_save_LIBS="$LIBS" @@ -24481,7 +25836,7 @@ $as_echo "#define HAVE_CFPREFERENCESCOPYAPPVALUE 1" >>confdefs.h fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking for CFLocaleCopyCurrent" >&5 $as_echo_n "checking for CFLocaleCopyCurrent... " >&6; } -if test "${gt_cv_func_CFLocaleCopyCurrent+set}" = set; then : +if ${gt_cv_func_CFLocaleCopyCurrent+:} false; then : $as_echo_n "(cached) " >&6 else gt_save_LIBS="$LIBS" @@ -24557,7 +25912,7 @@ typedef int array [2 * (__GNU_GETTEXT_SUPPORTED_REVISION(0) >= 1) - 1]; { $as_echo "$as_me:${as_lineno-$LINENO}: checking for GNU gettext in libc" >&5 $as_echo_n "checking for GNU gettext in libc... " >&6; } -if eval "test \"\${$gt_func_gnugettext_libc+set}\"" = set; then : +if eval \${$gt_func_gnugettext_libc+:} false; then : $as_echo_n "(cached) " >&6 else cat confdefs.h - <<_ACEOF >conftest.$ac_ext @@ -24620,7 +25975,7 @@ $as_echo "$ac_res" >&6; } { $as_echo "$as_me:${as_lineno-$LINENO}: checking for iconv" >&5 $as_echo_n "checking for iconv... " >&6; } -if test "${am_cv_func_iconv+set}" = set; then : +if ${am_cv_func_iconv+:} false; then : $as_echo_n "(cached) " >&6 else @@ -25088,7 +26443,7 @@ fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking for GNU gettext in libintl" >&5 $as_echo_n "checking for GNU gettext in libintl... " >&6; } -if eval "test \"\${$gt_func_gnugettext_libintl+set}\"" = set; then : +if eval \${$gt_func_gnugettext_libintl+:} false; then : $as_echo_n "(cached) " >&6 else gt_save_CPPFLAGS="$CPPFLAGS" @@ -25298,7 +26653,7 @@ $as_echo "#define HAVE_DCGETTEXT 1" >>confdefs.h { $as_echo "$as_me:${as_lineno-$LINENO}: checking for iconv" >&5 $as_echo_n "checking for iconv... " >&6; } -if test "${am_cv_func_iconv+set}" = set; then : +if ${am_cv_func_iconv+:} false; then : $as_echo_n "(cached) " >&6 else @@ -25373,7 +26728,7 @@ $as_echo "$LIBICONV" >&6; } if test "$am_cv_func_iconv" = yes; then { $as_echo "$as_me:${as_lineno-$LINENO}: checking for iconv declaration" >&5 $as_echo_n "checking for iconv declaration... " >&6; } - if test "${am_cv_proto_iconv+set}" = set; then : + if ${am_cv_proto_iconv+:} false; then : $as_echo_n "(cached) " >&6 else @@ -25424,7 +26779,7 @@ _ACEOF # Checks for standard typedefs, structures, and compiler characteristics. ac_fn_c_check_type "$LINENO" "pid_t" "ac_cv_type_pid_t" "$ac_includes_default" -if test "x$ac_cv_type_pid_t" = x""yes; then : +if test "x$ac_cv_type_pid_t" = xyes; then : else @@ -25435,7 +26790,7 @@ _ACEOF fi ac_fn_c_check_type "$LINENO" "size_t" "ac_cv_type_size_t" "$ac_includes_default" -if test "x$ac_cv_type_size_t" = x""yes; then : +if test "x$ac_cv_type_size_t" = xyes; then : else @@ -25446,7 +26801,7 @@ _ACEOF fi ac_fn_c_check_type "$LINENO" "mode_t" "ac_cv_type_mode_t" "$ac_includes_default" -if test "x$ac_cv_type_mode_t" = x""yes; then : +if test "x$ac_cv_type_mode_t" = xyes; then : else @@ -25458,7 +26813,7 @@ fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether time.h and sys/time.h may both be included" >&5 $as_echo_n "checking whether time.h and sys/time.h may both be included... " >&6; } -if test "${ac_cv_header_time+set}" = set; then : +if ${ac_cv_header_time+:} false; then : $as_echo_n "(cached) " >&6 else cat confdefs.h - <<_ACEOF >conftest.$ac_ext @@ -25493,7 +26848,7 @@ fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether stat file-mode macros are broken" >&5 $as_echo_n "checking whether stat file-mode macros are broken... " >&6; } -if test "${ac_cv_header_stat_broken+set}" = set; then : +if ${ac_cv_header_stat_broken+:} false; then : $as_echo_n "(cached) " >&6 else cat confdefs.h - <<_ACEOF >conftest.$ac_ext @@ -25535,84 +26890,66 @@ fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking for stdbool.h that conforms to C99" >&5 $as_echo_n "checking for stdbool.h that conforms to C99... " >&6; } -if test "${ac_cv_header_stdbool_h+set}" = set; then : +if ${ac_cv_header_stdbool_h+:} false; then : $as_echo_n "(cached) " >&6 else cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ -#include -#ifndef bool - "error: bool is not defined" -#endif -#ifndef false - "error: false is not defined" -#endif -#if false - "error: false is not 0" -#endif -#ifndef true - "error: true is not defined" -#endif -#if true != 1 - "error: true is not 1" -#endif -#ifndef __bool_true_false_are_defined - "error: __bool_true_false_are_defined is not defined" -#endif - - struct s { _Bool s: 1; _Bool t; } s; - - char a[true == 1 ? 1 : -1]; - char b[false == 0 ? 1 : -1]; - char c[__bool_true_false_are_defined == 1 ? 1 : -1]; - char d[(bool) 0.5 == true ? 1 : -1]; - bool e = &s; - char f[(_Bool) 0.0 == false ? 1 : -1]; - char g[true]; - char h[sizeof (_Bool)]; - char i[sizeof s.t]; - enum { j = false, k = true, l = false * true, m = true * 256 }; - /* The following fails for - HP aC++/ANSI C B3910B A.05.55 [Dec 04 2003]. */ - _Bool n[m]; - char o[sizeof n == m * sizeof n[0] ? 1 : -1]; - char p[-1 - (_Bool) 0 < 0 && -1 - (bool) 0 < 0 ? 1 : -1]; -# if defined __xlc__ || defined __GNUC__ - /* Catch a bug in IBM AIX xlc compiler version 6.0.0.0 - reported by James Lemley on 2005-10-05; see - http://lists.gnu.org/archive/html/bug-coreutils/2005-10/msg00086.html - This test is not quite right, since xlc is allowed to - reject this program, as the initializer for xlcbug is - not one of the forms that C requires support for. - However, doing the test right would require a runtime - test, and that would make cross-compilation harder. - Let us hope that IBM fixes the xlc bug, and also adds - support for this kind of constant expression. In the - meantime, this test will reject xlc, which is OK, since - our stdbool.h substitute should suffice. We also test - this with GCC, where it should work, to detect more - quickly whether someone messes up the test in the - future. */ - char digs[] = "0123456789"; - int xlcbug = 1 / (&(digs + 5)[-2 + (bool) 1] == &digs[4] ? 1 : -1); -# endif - /* Catch a bug in an HP-UX C compiler. See - http://gcc.gnu.org/ml/gcc-patches/2003-12/msg02303.html - http://lists.gnu.org/archive/html/bug-coreutils/2005-11/msg00161.html - */ - _Bool q = true; - _Bool *pq = &q; + #include + #ifndef bool + "error: bool is not defined" + #endif + #ifndef false + "error: false is not defined" + #endif + #if false + "error: false is not 0" + #endif + #ifndef true + "error: true is not defined" + #endif + #if true != 1 + "error: true is not 1" + #endif + #ifndef __bool_true_false_are_defined + "error: __bool_true_false_are_defined is not defined" + #endif + + struct s { _Bool s: 1; _Bool t; } s; + + char a[true == 1 ? 1 : -1]; + char b[false == 0 ? 1 : -1]; + char c[__bool_true_false_are_defined == 1 ? 1 : -1]; + char d[(bool) 0.5 == true ? 1 : -1]; + /* See body of main program for 'e'. */ + char f[(_Bool) 0.0 == false ? 1 : -1]; + char g[true]; + char h[sizeof (_Bool)]; + char i[sizeof s.t]; + enum { j = false, k = true, l = false * true, m = true * 256 }; + /* The following fails for + HP aC++/ANSI C B3910B A.05.55 [Dec 04 2003]. */ + _Bool n[m]; + char o[sizeof n == m * sizeof n[0] ? 1 : -1]; + char p[-1 - (_Bool) 0 < 0 && -1 - (bool) 0 < 0 ? 1 : -1]; + /* Catch a bug in an HP-UX C compiler. See + http://gcc.gnu.org/ml/gcc-patches/2003-12/msg02303.html + http://lists.gnu.org/archive/html/bug-coreutils/2005-11/msg00161.html + */ + _Bool q = true; + _Bool *pq = &q; int main () { - *pq |= q; - *pq |= ! q; - /* Refer to every declared value, to avoid compiler optimizations. */ - return (!a + !b + !c + !d + !e + !f + !g + !h + !i + !!j + !k + !!l - + !m + !n + !o + !p + !q + !pq); + bool e = &s; + *pq |= q; + *pq |= ! q; + /* Refer to every declared value, to avoid compiler optimizations. */ + return (!a + !b + !c + !d + !e + !f + !g + !h + !i + !!j + !k + !!l + + !m + !n + !o + !p + !q + !pq); ; return 0; @@ -25627,8 +26964,8 @@ rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_header_stdbool_h" >&5 $as_echo "$ac_cv_header_stdbool_h" >&6; } -ac_fn_c_check_type "$LINENO" "_Bool" "ac_cv_type__Bool" "$ac_includes_default" -if test "x$ac_cv_type__Bool" = x""yes; then : + ac_fn_c_check_type "$LINENO" "_Bool" "ac_cv_type__Bool" "$ac_includes_default" +if test "x$ac_cv_type__Bool" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE__BOOL 1 @@ -25637,6 +26974,7 @@ _ACEOF fi + if test $ac_cv_header_stdbool_h = yes; then $as_echo "#define HAVE_STDBOOL_H 1" >>confdefs.h @@ -25645,7 +26983,7 @@ fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether struct tm is in sys/time.h or time.h" >&5 $as_echo_n "checking whether struct tm is in sys/time.h or time.h... " >&6; } -if test "${ac_cv_struct_tm+set}" = set; then : +if ${ac_cv_struct_tm+:} false; then : $as_echo_n "(cached) " >&6 else cat confdefs.h - <<_ACEOF >conftest.$ac_ext @@ -25685,7 +27023,7 @@ ac_fn_c_check_member "$LINENO" "struct sockaddr_in" "sin_len" "ac_cv_member_stru #include " -if test "x$ac_cv_member_struct_sockaddr_in_sin_len" = x""yes; then : +if test "x$ac_cv_member_struct_sockaddr_in_sin_len" = xyes; then : $as_echo "#define HAVE_SOCKADDR_IN_SIN_LEN 1" >>confdefs.h @@ -25698,7 +27036,7 @@ fi # Checks for library functions. { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether closedir returns void" >&5 $as_echo_n "checking whether closedir returns void... " >&6; } -if test "${ac_cv_func_closedir_void+set}" = set; then : +if ${ac_cv_func_closedir_void+:} false; then : $as_echo_n "(cached) " >&6 else if test "$cross_compiling" = yes; then : @@ -25741,7 +27079,7 @@ fi for ac_header in vfork.h do : ac_fn_c_check_header_mongrel "$LINENO" "vfork.h" "ac_cv_header_vfork_h" "$ac_includes_default" -if test "x$ac_cv_header_vfork_h" = x""yes; then : +if test "x$ac_cv_header_vfork_h" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_VFORK_H 1 _ACEOF @@ -25765,7 +27103,7 @@ done if test "x$ac_cv_func_fork" = xyes; then { $as_echo "$as_me:${as_lineno-$LINENO}: checking for working fork" >&5 $as_echo_n "checking for working fork... " >&6; } -if test "${ac_cv_func_fork_works+set}" = set; then : +if ${ac_cv_func_fork_works+:} false; then : $as_echo_n "(cached) " >&6 else if test "$cross_compiling" = yes; then : @@ -25818,7 +27156,7 @@ ac_cv_func_vfork_works=$ac_cv_func_vfork if test "x$ac_cv_func_vfork" = xyes; then { $as_echo "$as_me:${as_lineno-$LINENO}: checking for working vfork" >&5 $as_echo_n "checking for working vfork... " >&6; } -if test "${ac_cv_func_vfork_works+set}" = set; then : +if ${ac_cv_func_vfork_works+:} false; then : $as_echo_n "(cached) " >&6 else if test "$cross_compiling" = yes; then : @@ -25954,7 +27292,7 @@ fi if test $ac_cv_c_compiler_gnu = yes; then { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether $CC needs -traditional" >&5 $as_echo_n "checking whether $CC needs -traditional... " >&6; } -if test "${ac_cv_prog_gcc_traditional+set}" = set; then : +if ${ac_cv_prog_gcc_traditional+:} false; then : $as_echo_n "(cached) " >&6 else ac_pattern="Autoconf.*'x'" @@ -25995,7 +27333,7 @@ fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking for working memcmp" >&5 $as_echo_n "checking for working memcmp... " >&6; } -if test "${ac_cv_func_memcmp_working+set}" = set; then : +if ${ac_cv_func_memcmp_working+:} false; then : $as_echo_n "(cached) " >&6 else if test "$cross_compiling" = yes; then : @@ -26070,7 +27408,7 @@ done { $as_echo "$as_me:${as_lineno-$LINENO}: checking types of arguments for select" >&5 $as_echo_n "checking types of arguments for select... " >&6; } -if test "${ac_cv_func_select_args+set}" = set; then : +if ${ac_cv_func_select_args+:} false; then : $as_echo_n "(cached) " >&6 else for ac_arg234 in 'fd_set *' 'int *' 'void *'; do @@ -26104,7 +27442,7 @@ rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext done done # Provide a safe default value. -: ${ac_cv_func_select_args='int,int *,struct timeval *'} +: "${ac_cv_func_select_args=int,int *,struct timeval *}" fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_func_select_args" >&5 @@ -26132,7 +27470,7 @@ rm -f conftest* { $as_echo "$as_me:${as_lineno-$LINENO}: checking for uid_t in sys/types.h" >&5 $as_echo_n "checking for uid_t in sys/types.h... " >&6; } -if test "${ac_cv_type_uid_t+set}" = set; then : +if ${ac_cv_type_uid_t+:} false; then : $as_echo_n "(cached) " >&6 else cat confdefs.h - <<_ACEOF >conftest.$ac_ext @@ -26163,7 +27501,7 @@ fi for ac_header in unistd.h do : ac_fn_c_check_header_mongrel "$LINENO" "unistd.h" "ac_cv_header_unistd_h" "$ac_includes_default" -if test "x$ac_cv_header_unistd_h" = x""yes; then : +if test "x$ac_cv_header_unistd_h" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_UNISTD_H 1 _ACEOF @@ -26174,7 +27512,7 @@ done { $as_echo "$as_me:${as_lineno-$LINENO}: checking for working chown" >&5 $as_echo_n "checking for working chown... " >&6; } -if test "${ac_cv_func_chown_works+set}" = set; then : +if ${ac_cv_func_chown_works+:} false; then : $as_echo_n "(cached) " >&6 else if test "$cross_compiling" = yes; then : @@ -26228,7 +27566,7 @@ fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking return type of signal handlers" >&5 $as_echo_n "checking return type of signal handlers... " >&6; } -if test "${ac_cv_type_signal+set}" = set; then : +if ${ac_cv_type_signal+:} false; then : $as_echo_n "(cached) " >&6 else cat confdefs.h - <<_ACEOF >conftest.$ac_ext @@ -26261,7 +27599,7 @@ _ACEOF { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether lstat correctly handles trailing slash" >&5 $as_echo_n "checking whether lstat correctly handles trailing slash... " >&6; } -if test "${ac_cv_func_lstat_dereferences_slashed_symlink+set}" = set; then : +if ${ac_cv_func_lstat_dereferences_slashed_symlink+:} false; then : $as_echo_n "(cached) " >&6 else rm -f conftest.sym conftest.file @@ -26323,7 +27661,7 @@ fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether stat accepts an empty string" >&5 $as_echo_n "checking whether stat accepts an empty string... " >&6; } -if test "${ac_cv_func_stat_empty_string_bug+set}" = set; then : +if ${ac_cv_func_stat_empty_string_bug+:} false; then : $as_echo_n "(cached) " >&6 else if test "$cross_compiling" = yes; then : @@ -26370,7 +27708,7 @@ fi for ac_func in strftime do : ac_fn_c_check_func "$LINENO" "strftime" "ac_cv_func_strftime" -if test "x$ac_cv_func_strftime" = x""yes; then : +if test "x$ac_cv_func_strftime" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_STRFTIME 1 _ACEOF @@ -26379,7 +27717,7 @@ else # strftime is in -lintl on SCO UNIX. { $as_echo "$as_me:${as_lineno-$LINENO}: checking for strftime in -lintl" >&5 $as_echo_n "checking for strftime in -lintl... " >&6; } -if test "${ac_cv_lib_intl_strftime+set}" = set; then : +if ${ac_cv_lib_intl_strftime+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS @@ -26413,7 +27751,7 @@ LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_intl_strftime" >&5 $as_echo "$ac_cv_lib_intl_strftime" >&6; } -if test "x$ac_cv_lib_intl_strftime" = x""yes; then : +if test "x$ac_cv_lib_intl_strftime" = xyes; then : $as_echo "#define HAVE_STRFTIME 1" >>confdefs.h LIBS="-lintl $LIBS" @@ -26425,13 +27763,13 @@ done for ac_func in vprintf do : ac_fn_c_check_func "$LINENO" "vprintf" "ac_cv_func_vprintf" -if test "x$ac_cv_func_vprintf" = x""yes; then : +if test "x$ac_cv_func_vprintf" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_VPRINTF 1 _ACEOF ac_fn_c_check_func "$LINENO" "_doprnt" "ac_cv_func__doprnt" -if test "x$ac_cv_func__doprnt" = x""yes; then : +if test "x$ac_cv_func__doprnt" = xyes; then : $as_echo "#define HAVE_DOPRNT 1" >>confdefs.h @@ -26443,7 +27781,7 @@ done { $as_echo "$as_me:${as_lineno-$LINENO}: checking for sys/wait.h that is POSIX.1 compatible" >&5 $as_echo_n "checking for sys/wait.h that is POSIX.1 compatible... " >&6; } -if test "${ac_cv_header_sys_wait_h+set}" = set; then : +if ${ac_cv_header_sys_wait_h+:} false; then : $as_echo_n "(cached) " >&6 else cat confdefs.h - <<_ACEOF >conftest.$ac_ext @@ -26483,7 +27821,7 @@ $as_echo "#define HAVE_SYS_WAIT_H 1" >>confdefs.h fi ac_fn_c_check_type "$LINENO" "off_t" "ac_cv_type_off_t" "$ac_includes_default" -if test "x$ac_cv_type_off_t" = x""yes; then : +if test "x$ac_cv_type_off_t" = xyes; then : else @@ -26495,7 +27833,7 @@ fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking for uid_t in sys/types.h" >&5 $as_echo_n "checking for uid_t in sys/types.h... " >&6; } -if test "${ac_cv_type_uid_t+set}" = set; then : +if ${ac_cv_type_uid_t+:} false; then : $as_echo_n "(cached) " >&6 else cat confdefs.h - <<_ACEOF >conftest.$ac_ext @@ -26523,7 +27861,7 @@ $as_echo "#define gid_t int" >>confdefs.h fi -for ac_func in floor memmove rmdir strncasecmp strrchr strtol atoll dup2 fdatasync ftruncate gettimeofday memset mkdir mkfifo strcasecmp strchr strdup strerror strstr clock_gettime getrusage rand uname setlocale getcwd mktime gmtime_r gmtime strlcpy strlcat ftruncate stat64 sbrk mmap mremap setrlimit sysconf initgroups getifaddrs freeifaddrs localtime_r nl_langinfo putenv realpath strndup gethostbyname2 gethostbyname getpeerucred getpeereid setresuid $funcstocheck +for ac_func in atoll stat64 strnlen mremap getrlimit setrlimit sysconf initgroups strndup gethostbyname2 getpeerucred getpeereid setresuid $funcstocheck getifaddrs freeifaddrs getresgid mallinfo malloc_size malloc_usable_size getrusage do : as_ac_var=`$as_echo "ac_cv_func_$ac_func" | $as_tr_sh` ac_fn_c_check_func "$LINENO" "$ac_func" "$as_ac_var" @@ -26633,68 +27971,463 @@ GN_PLUGIN_LDFLAGS="-export-dynamic -avoid-version -module -no-undefined" -# test for sudo -{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for sudo" >&5 -$as_echo_n "checking for sudo... " >&6; } +# test for sudo +{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for sudo" >&5 +$as_echo_n "checking for sudo... " >&6; } + +# Check whether --with-sudo was given. +if test "${with_sudo+set}" = set; then : + withval=$with_sudo; { $as_echo "$as_me:${as_lineno-$LINENO}: result: \"$with_sudo\"" >&5 +$as_echo "\"$with_sudo\"" >&6; } + case $with_sudo in + no) + SUDO_BINARY= + ;; + yes) + SUDO_BINARY=sudo + ;; + *) + SUDO_BINARY=$with_sudo + ;; + esac + +else + { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 +$as_echo "no" >&6; } +fi + + + if test "x$SUDO_BINARY" != "x" -o -w /; then + HAVE_SUDO_TRUE= + HAVE_SUDO_FALSE='#' +else + HAVE_SUDO_TRUE='#' + HAVE_SUDO_FALSE= +fi + + + +# test for nssdir +{ $as_echo "$as_me:${as_lineno-$LINENO}: checking with nssdir" >&5 +$as_echo_n "checking with nssdir... " >&6; } + +# Check whether --with-nssdir was given. +if test "${with_nssdir+set}" = set; then : + withval=$with_nssdir; { $as_echo "$as_me:${as_lineno-$LINENO}: result: \"$with_nssdir\"" >&5 +$as_echo "\"$with_nssdir\"" >&6; } + case $with_nssdir in + no) + NSS_DIR= + install_nss=0 + ;; + yes) + NSS_DIR="/lib" + install_nss=1 + ;; + *) + NSS_DIR=$with_nssdir + install_nss=1 + ;; + esac + +else + + if test "x$SUDO_BINARY" != "x" -o -w / + then + NSS_DIR="/lib" + install_nss=1 + { $as_echo "$as_me:${as_lineno-$LINENO}: result: yes, to /lib" >&5 +$as_echo "yes, to /lib" >&6; } + else + NSS_DIR= + install_nss=0 + { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 +$as_echo "no" >&6; } + fi + +fi + + + if test "x$install_nss" != "x0"; then + INSTALL_NSS_TRUE= + INSTALL_NSS_FALSE='#' +else + INSTALL_NSS_TRUE='#' + INSTALL_NSS_FALSE= +fi + + +# test for gnunetdns group name +GNUNETDNS_GROUP=gnunetdns +{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for gnunetdns group name" >&5 +$as_echo_n "checking for gnunetdns group name... " >&6; } + +# Check whether --with-gnunetdns was given. +if test "${with_gnunetdns+set}" = set; then : + withval=$with_gnunetdns; { $as_echo "$as_me:${as_lineno-$LINENO}: result: \"$with_gnunetdns\"" >&5 +$as_echo "\"$with_gnunetdns\"" >&6; } + case $with_gnunetdns in + no) + GNUNETDNS_GROUP=gnunet + ;; + yes) + GNUNETDNS_GROUP=gnunetdns + ;; + *) + GNUNETDNS_GROUP=$with_gnunetdns + ;; + esac + +else + { $as_echo "$as_me:${as_lineno-$LINENO}: result: gnunetdns" >&5 +$as_echo "gnunetdns" >&6; } +fi + + + + + +# gnutls +gnutls=0 +{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for gnutls" >&5 +$as_echo_n "checking for gnutls... " >&6; } + +# Check whether --with-gnutls was given. +if test "${with_gnutls+set}" = set; then : + withval=$with_gnutls; { $as_echo "$as_me:${as_lineno-$LINENO}: result: $with_gnutls" >&5 +$as_echo "$with_gnutls" >&6; } + case $with_gnutls in + no) + ;; + yes) + for ac_header in gnutls/abstract.h +do : + ac_fn_c_check_header_mongrel "$LINENO" "gnutls/abstract.h" "ac_cv_header_gnutls_abstract_h" "$ac_includes_default" +if test "x$ac_cv_header_gnutls_abstract_h" = xyes; then : + cat >>confdefs.h <<_ACEOF +#define HAVE_GNUTLS_ABSTRACT_H 1 +_ACEOF + { $as_echo "$as_me:${as_lineno-$LINENO}: checking for gnutls_priority_set in -lgnutls" >&5 +$as_echo_n "checking for gnutls_priority_set in -lgnutls... " >&6; } +if ${ac_cv_lib_gnutls_gnutls_priority_set+:} false; then : + $as_echo_n "(cached) " >&6 +else + ac_check_lib_save_LIBS=$LIBS +LIBS="-lgnutls $LIBS" +cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ + +/* Override any GCC internal prototype to avoid an error. + Use char because int might match the return type of a GCC + builtin and then its argument prototype would still apply. */ +#ifdef __cplusplus +extern "C" +#endif +char gnutls_priority_set (); +int +main () +{ +return gnutls_priority_set (); + ; + return 0; +} +_ACEOF +if ac_fn_c_try_link "$LINENO"; then : + ac_cv_lib_gnutls_gnutls_priority_set=yes +else + ac_cv_lib_gnutls_gnutls_priority_set=no +fi +rm -f core conftest.err conftest.$ac_objext \ + conftest$ac_exeext conftest.$ac_ext +LIBS=$ac_check_lib_save_LIBS +fi +{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_gnutls_gnutls_priority_set" >&5 +$as_echo "$ac_cv_lib_gnutls_gnutls_priority_set" >&6; } +if test "x$ac_cv_lib_gnutls_gnutls_priority_set" = xyes; then : + gnutls=true +fi + +fi + +done + + ;; + *) + LDFLAGS="-L$with_gnutls/lib $LDFLAGS" + CPPFLAGS="-I$with_gnutls/include $CPPFLAGS" + for ac_header in gnutls/abstract.h +do : + ac_fn_c_check_header_mongrel "$LINENO" "gnutls/abstract.h" "ac_cv_header_gnutls_abstract_h" "$ac_includes_default" +if test "x$ac_cv_header_gnutls_abstract_h" = xyes; then : + cat >>confdefs.h <<_ACEOF +#define HAVE_GNUTLS_ABSTRACT_H 1 +_ACEOF + { $as_echo "$as_me:${as_lineno-$LINENO}: checking for gnutls_priority_set in -lgnutls" >&5 +$as_echo_n "checking for gnutls_priority_set in -lgnutls... " >&6; } +if ${ac_cv_lib_gnutls_gnutls_priority_set+:} false; then : + $as_echo_n "(cached) " >&6 +else + ac_check_lib_save_LIBS=$LIBS +LIBS="-lgnutls $LIBS" +cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ + +/* Override any GCC internal prototype to avoid an error. + Use char because int might match the return type of a GCC + builtin and then its argument prototype would still apply. */ +#ifdef __cplusplus +extern "C" +#endif +char gnutls_priority_set (); +int +main () +{ +return gnutls_priority_set (); + ; + return 0; +} +_ACEOF +if ac_fn_c_try_link "$LINENO"; then : + ac_cv_lib_gnutls_gnutls_priority_set=yes +else + ac_cv_lib_gnutls_gnutls_priority_set=no +fi +rm -f core conftest.err conftest.$ac_objext \ + conftest$ac_exeext conftest.$ac_ext +LIBS=$ac_check_lib_save_LIBS +fi +{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_gnutls_gnutls_priority_set" >&5 +$as_echo "$ac_cv_lib_gnutls_gnutls_priority_set" >&6; } +if test "x$ac_cv_lib_gnutls_gnutls_priority_set" = xyes; then : + EXT_LIB_PATH="-L$with_gnutls/lib $EXT_LIB_PATH" + gnutls=true +fi + +fi + +done + + ;; + esac + +else + { $as_echo "$as_me:${as_lineno-$LINENO}: result: --with-gnutls not specified" >&5 +$as_echo "--with-gnutls not specified" >&6; } + for ac_header in gnutls/abstract.h +do : + ac_fn_c_check_header_mongrel "$LINENO" "gnutls/abstract.h" "ac_cv_header_gnutls_abstract_h" "$ac_includes_default" +if test "x$ac_cv_header_gnutls_abstract_h" = xyes; then : + cat >>confdefs.h <<_ACEOF +#define HAVE_GNUTLS_ABSTRACT_H 1 +_ACEOF + { $as_echo "$as_me:${as_lineno-$LINENO}: checking for gnutls_priority_set in -lgnutls" >&5 +$as_echo_n "checking for gnutls_priority_set in -lgnutls... " >&6; } +if ${ac_cv_lib_gnutls_gnutls_priority_set+:} false; then : + $as_echo_n "(cached) " >&6 +else + ac_check_lib_save_LIBS=$LIBS +LIBS="-lgnutls $LIBS" +cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ + +/* Override any GCC internal prototype to avoid an error. + Use char because int might match the return type of a GCC + builtin and then its argument prototype would still apply. */ +#ifdef __cplusplus +extern "C" +#endif +char gnutls_priority_set (); +int +main () +{ +return gnutls_priority_set (); + ; + return 0; +} +_ACEOF +if ac_fn_c_try_link "$LINENO"; then : + ac_cv_lib_gnutls_gnutls_priority_set=yes +else + ac_cv_lib_gnutls_gnutls_priority_set=no +fi +rm -f core conftest.err conftest.$ac_objext \ + conftest$ac_exeext conftest.$ac_ext +LIBS=$ac_check_lib_save_LIBS +fi +{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_gnutls_gnutls_priority_set" >&5 +$as_echo "$ac_cv_lib_gnutls_gnutls_priority_set" >&6; } +if test "x$ac_cv_lib_gnutls_gnutls_priority_set" = xyes; then : + gnutls=true +fi + +fi + +done + +fi + + if test x$gnutls = xtrue; then + HAVE_GNUTLS_TRUE= + HAVE_GNUTLS_FALSE='#' +else + HAVE_GNUTLS_TRUE='#' + HAVE_GNUTLS_FALSE= +fi + + +cat >>confdefs.h <<_ACEOF +#define HAVE_GNUTLS $gnutls +_ACEOF + + + +# Test if we are building for superMUC +llapi=0 +{ $as_echo "$as_me:${as_lineno-$LINENO}: checking if testbed should use IBM LoadLeveler to run on SuperMUC" >&5 +$as_echo_n "checking if testbed should use IBM LoadLeveler to run on SuperMUC... " >&6; } + +# Check whether --with-ll was given. +if test "${with_ll+set}" = set; then : + withval=$with_ll; { $as_echo "$as_me:${as_lineno-$LINENO}: result: $with_ll" >&5 +$as_echo "$with_ll" >&6; } + case $with_ll in + no) + ;; + yes) + for ac_header in llapi.h +do : + ac_fn_c_check_header_mongrel "$LINENO" "llapi.h" "ac_cv_header_llapi_h" "$ac_includes_default" +if test "x$ac_cv_header_llapi_h" = xyes; then : + cat >>confdefs.h <<_ACEOF +#define HAVE_LLAPI_H 1 +_ACEOF + { $as_echo "$as_me:${as_lineno-$LINENO}: checking for llsubmit in -lllapi" >&5 +$as_echo_n "checking for llsubmit in -lllapi... " >&6; } +if ${ac_cv_lib_llapi_llsubmit+:} false; then : + $as_echo_n "(cached) " >&6 +else + ac_check_lib_save_LIBS=$LIBS +LIBS="-lllapi $LIBS" +cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ + +/* Override any GCC internal prototype to avoid an error. + Use char because int might match the return type of a GCC + builtin and then its argument prototype would still apply. */ +#ifdef __cplusplus +extern "C" +#endif +char llsubmit (); +int +main () +{ +return llsubmit (); + ; + return 0; +} +_ACEOF +if ac_fn_c_try_link "$LINENO"; then : + ac_cv_lib_llapi_llsubmit=yes +else + ac_cv_lib_llapi_llsubmit=no +fi +rm -f core conftest.err conftest.$ac_objext \ + conftest$ac_exeext conftest.$ac_ext +LIBS=$ac_check_lib_save_LIBS +fi +{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_llapi_llsubmit" >&5 +$as_echo "$ac_cv_lib_llapi_llsubmit" >&6; } +if test "x$ac_cv_lib_llapi_llsubmit" = xyes; then : + llapi=true +else + as_fn_error $? "libllapi not found but --with-llapi given" "$LINENO" 5 +fi + +else + as_fn_error $? "llapi.h not found but --with-llapi given" "$LINENO" 5 +fi + +done -# Check whether --with-sudo was given. -if test "${with_sudo+set}" = set; then : - withval=$with_sudo; { $as_echo "$as_me:${as_lineno-$LINENO}: result: \"$with_sudo\"" >&5 -$as_echo "\"$with_sudo\"" >&6; } - case $with_sudo in - no) - SUDO_BINARY= - ;; - yes) - SUDO_BINARY=sudo - ;; - *) - SUDO_BINARY=$with_sudo - ;; - esac + ;; + *) + LDFLAGS="-L$with_ll/lib $LDFLAGS" + CPPFLAGS="-I$with_ll/include $CPPFLAGS" + for ac_header in llapi.h +do : + ac_fn_c_check_header_mongrel "$LINENO" "llapi.h" "ac_cv_header_llapi_h" "$ac_includes_default" +if test "x$ac_cv_header_llapi_h" = xyes; then : + cat >>confdefs.h <<_ACEOF +#define HAVE_LLAPI_H 1 +_ACEOF + { $as_echo "$as_me:${as_lineno-$LINENO}: checking for llsubmit in -lllapi" >&5 +$as_echo_n "checking for llsubmit in -lllapi... " >&6; } +if ${ac_cv_lib_llapi_llsubmit+:} false; then : + $as_echo_n "(cached) " >&6 +else + ac_check_lib_save_LIBS=$LIBS +LIBS="-lllapi $LIBS" +cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ +/* Override any GCC internal prototype to avoid an error. + Use char because int might match the return type of a GCC + builtin and then its argument prototype would still apply. */ +#ifdef __cplusplus +extern "C" +#endif +char llsubmit (); +int +main () +{ +return llsubmit (); + ; + return 0; +} +_ACEOF +if ac_fn_c_try_link "$LINENO"; then : + ac_cv_lib_llapi_llsubmit=yes else - { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 -$as_echo "no" >&6; } + ac_cv_lib_llapi_llsubmit=no +fi +rm -f core conftest.err conftest.$ac_objext \ + conftest$ac_exeext conftest.$ac_ext +LIBS=$ac_check_lib_save_LIBS +fi +{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_llapi_llsubmit" >&5 +$as_echo "$ac_cv_lib_llapi_llsubmit" >&6; } +if test "x$ac_cv_lib_llapi_llsubmit" = xyes; then : + llapi=true +else + as_fn_error $? "libllapi not found but --with-llapi given" "$LINENO" 5 fi - - if test "x$SUDO_BINARY" != "x" -o -w /; then - HAVE_SUDO_TRUE= - HAVE_SUDO_FALSE='#' else - HAVE_SUDO_TRUE='#' - HAVE_SUDO_FALSE= + as_fn_error $? "llapi.h not found but --with-llapi given" "$LINENO" 5 fi +done -# test for gnunetdns group name -GNUNETDNS_GROUP=gnunetdns -{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for gnunetdns group name" >&5 -$as_echo_n "checking for gnunetdns group name... " >&6; } + ;; + esac -# Check whether --with-gnunetdns was given. -if test "${with_gnunetdns+set}" = set; then : - withval=$with_gnunetdns; { $as_echo "$as_me:${as_lineno-$LINENO}: result: \"$with_gnunetdns\"" >&5 -$as_echo "\"$with_gnunetdns\"" >&6; } - case $with_gnunetdns in - no) - GNUNETDNS_GROUP=gnunet - ;; - yes) - GNUNETDNS_GROUP=gnunetdns - ;; - *) - GNUNETDNS_GROUP=$with_gnunetdns - ;; - esac +else + { $as_echo "$as_me:${as_lineno-$LINENO}: result: --with-ll not specified" >&5 +$as_echo "--with-ll not specified" >&6; } +fi + if test "x$llapi" = "xtrue"; then + WITH_LL_TRUE= + WITH_LL_FALSE='#' else - { $as_echo "$as_me:${as_lineno-$LINENO}: result: gnunetdns" >&5 -$as_echo "gnunetdns" >&6; } + WITH_LL_TRUE='#' + WITH_LL_FALSE= fi +cat >>confdefs.h <<_ACEOF +#define WITH_LL $llapi +_ACEOF # should 'make check' run tests? @@ -26831,6 +28564,24 @@ else fi +# should memory statistics be kept (very expensive CPU-wise!) +{ $as_echo "$as_me:${as_lineno-$LINENO}: checking whether to create expensive statistics on memory use" >&5 +$as_echo_n "checking whether to create expensive statistics on memory use... " >&6; } +# Check whether --enable-heapstats was given. +if test "${enable_heapstats+set}" = set; then : + enableval=$enable_heapstats; enable_heapstats=1 +else + enable_heapstats=0 +fi + +{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $enable_heapstats" >&5 +$as_echo "$enable_heapstats" >&6; } + +cat >>confdefs.h <<_ACEOF +#define ENABLE_HEAP_STATISTICS $enable_heapstats +_ACEOF + + # should code be enabled that works around missing OS functionality on Windows? # used for test cases if test $build_target = "mingw" @@ -27111,53 +28862,168 @@ rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext else - { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether to enable windows workarounds" >&5 -$as_echo_n "checking whether to enable windows workarounds... " >&6; } - # Check whether --enable-windows_workarounds was given. -if test "${enable_windows_workarounds+set}" = set; then : - enableval=$enable_windows_workarounds; enable_workarounds=${enableval} -else - enable_workarounds=no + { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether to enable windows workarounds" >&5 +$as_echo_n "checking whether to enable windows workarounds... " >&6; } + # Check whether --enable-windows_workarounds was given. +if test "${enable_windows_workarounds+set}" = set; then : + enableval=$enable_windows_workarounds; enable_workarounds=${enableval} +else + enable_workarounds=no +fi + + { $as_echo "$as_me:${as_lineno-$LINENO}: result: $enable_workarounds" >&5 +$as_echo "$enable_workarounds" >&6; } + if test x$enable_windows_workarounds = "xyes" + then + workarounds=1 + else + workarounds=0 + fi +fi + +cat >>confdefs.h <<_ACEOF +#define ENABLE_WINDOWS_WORKAROUNDS $workarounds +_ACEOF + + +# gcov compilation +{ $as_echo "$as_me:${as_lineno-$LINENO}: checking whether to compile with support for code coverage analysis" >&5 +$as_echo_n "checking whether to compile with support for code coverage analysis... " >&6; } +# Check whether --enable-coverage was given. +if test "${enable_coverage+set}" = set; then : + enableval=$enable_coverage; use_gcov=${enableval} +else + use_gcov=no +fi + +{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $use_gcov" >&5 +$as_echo "$use_gcov" >&6; } + if test "x$use_gcov" = "xyes"; then + USE_COVERAGE_TRUE= + USE_COVERAGE_FALSE='#' +else + USE_COVERAGE_TRUE='#' + USE_COVERAGE_FALSE= +fi + + + +# version info +# Extract the first word of "svnversion", so it can be a program name with args. +set dummy svnversion; ac_word=$2 +{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +$as_echo_n "checking for $ac_word... " >&6; } +if ${ac_cv_path_svnversioncommand+:} false; then : + $as_echo_n "(cached) " >&6 +else + case $svnversioncommand in + [\\/]* | ?:[\\/]*) + ac_cv_path_svnversioncommand="$svnversioncommand" # Let the user override the test with a path. + ;; + *) + as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + test -z "$as_dir" && as_dir=. + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then + ac_cv_path_svnversioncommand="$as_dir/$ac_word$ac_exec_ext" + $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + + ;; +esac +fi +svnversioncommand=$ac_cv_path_svnversioncommand +if test -n "$svnversioncommand"; then + { $as_echo "$as_me:${as_lineno-$LINENO}: result: $svnversioncommand" >&5 +$as_echo "$svnversioncommand" >&6; } +else + { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 +$as_echo "no" >&6; } +fi + + +# Extract the first word of "git", so it can be a program name with args. +set dummy git; ac_word=$2 +{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +$as_echo_n "checking for $ac_word... " >&6; } +if ${ac_cv_path_gitcommand+:} false; then : + $as_echo_n "(cached) " >&6 +else + case $gitcommand in + [\\/]* | ?:[\\/]*) + ac_cv_path_gitcommand="$gitcommand" # Let the user override the test with a path. + ;; + *) + as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + test -z "$as_dir" && as_dir=. + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then + ac_cv_path_gitcommand="$as_dir/$ac_word$ac_exec_ext" + $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + + ;; +esac +fi +gitcommand=$ac_cv_path_gitcommand +if test -n "$gitcommand"; then + { $as_echo "$as_me:${as_lineno-$LINENO}: result: $gitcommand" >&5 +$as_echo "$gitcommand" >&6; } +else + { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 +$as_echo "no" >&6; } fi - { $as_echo "$as_me:${as_lineno-$LINENO}: result: $enable_workarounds" >&5 -$as_echo "$enable_workarounds" >&6; } - if test x$enable_windows_workarounds = "xyes" + +if test "X$svnversioncommand" = "X" || test `$svnversioncommand -n '.'` = "exported" +then + if test "X$gitcommand" = "X" then - workarounds=1 + +cat >>confdefs.h <<_ACEOF +#define VCS_VERSION "release" +_ACEOF + else - workarounds=0 - fi -fi + gitver=$(git log -1 | grep "git-svn-id" | sed -e 's/.*@\([0-9]\+\) .*/\1/') + if "X$gitver" = "X" + then cat >>confdefs.h <<_ACEOF -#define ENABLE_WINDOWS_WORKAROUNDS $workarounds +#define VCS_VERSION "release" _ACEOF + else -# gcov compilation -{ $as_echo "$as_me:${as_lineno-$LINENO}: checking whether to compile with support for code coverage analysis" >&5 -$as_echo_n "checking whether to compile with support for code coverage analysis... " >&6; } -# Check whether --enable-coverage was given. -if test "${enable_coverage+set}" = set; then : - enableval=$enable_coverage; use_gcov=${enableval} -else - use_gcov=no -fi +cat >>confdefs.h <<_ACEOF +#define VCS_VERSION "svn-$gitver" +_ACEOF -{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $use_gcov" >&5 -$as_echo "$use_gcov" >&6; } - if test "x$use_gcov" = "xyes"; then - USE_COVERAGE_TRUE= - USE_COVERAGE_FALSE='#' + fi + fi else - USE_COVERAGE_TRUE='#' - USE_COVERAGE_FALSE= -fi +cat >>confdefs.h <<_ACEOF +#define VCS_VERSION "svn-`svnversion -n`" +_ACEOF +fi -ac_config_files="$ac_config_files Makefile contrib/Makefile doc/Makefile doc/man/Makefile m4/Makefile po/Makefile.in src/Makefile src/arm/Makefile src/arm/arm.conf src/ats/Makefile src/ats/ats.conf src/block/Makefile src/chat/Makefile src/chat/chat.conf src/core/Makefile src/core/core.conf src/datacache/Makefile src/datastore/Makefile src/datastore/datastore.conf src/dht/Makefile src/dht/dht.conf src/dns/Makefile src/dns/dns.conf src/dv/Makefile src/dv/dv.conf src/exit/Makefile src/fragmentation/Makefile src/fs/Makefile src/fs/fs.conf src/gns/Makefile src/gns/gns.conf src/gns/nss/Makefile src/hello/Makefile src/include/Makefile src/include/gnunet_directories.h src/hostlist/Makefile src/lockmanager/Makefile src/lockmanager/lockmanager.conf src/mesh/Makefile src/mesh/mesh.conf src/mysql/Makefile src/namestore/Makefile src/namestore/namestore.conf src/nat/Makefile src/nse/Makefile src/nse/nse.conf src/peerinfo/Makefile src/peerinfo/peerinfo.conf src/peerinfo-tool/Makefile src/postgres/Makefile src/pt/Makefile src/regex/Makefile src/statistics/Makefile src/statistics/statistics.conf src/stream/Makefile src/template/Makefile src/testbed/Makefile src/testing/Makefile src/topology/Makefile src/transport/Makefile src/transport/transport.conf src/tun/Makefile src/util/Makefile src/util/resolver.conf src/vpn/Makefile src/vpn/vpn.conf src/integration-tests/Makefile pkgconfig/Makefile pkgconfig/gnunetarm.pc pkgconfig/gnunetblock.pc pkgconfig/gnunetcore.pc pkgconfig/gnunetdatacache.pc pkgconfig/gnunetdatastore.pc pkgconfig/gnunetdht.pc pkgconfig/gnunetdhtlog.pc pkgconfig/gnunetdv.pc pkgconfig/gnunetfragmentation.pc pkgconfig/gnunetfs.pc pkgconfig/gnunethello.pc pkgconfig/gnunetnat.pc pkgconfig/gnunetnse.pc pkgconfig/gnunetpeerinfo.pc pkgconfig/gnunetregex.pc pkgconfig/gnunetstatistics.pc pkgconfig/gnunettesting.pc pkgconfig/gnunettransport.pc pkgconfig/gnunetutil.pc" +ac_config_files="$ac_config_files Makefile contrib/Makefile doc/Makefile doc/man/Makefile m4/Makefile po/Makefile.in src/Makefile src/arm/Makefile src/arm/arm.conf src/ats/Makefile src/ats/ats.conf src/ats-tool/Makefile src/block/Makefile src/chat/Makefile src/chat/chat.conf src/core/Makefile src/core/core.conf src/consensus/Makefile src/consensus/consensus.conf src/datacache/Makefile src/datastore/Makefile src/datastore/datastore.conf src/dht/Makefile src/dht/dht.conf src/dns/Makefile src/dns/dns.conf src/dv/Makefile src/dv/dv.conf src/exit/Makefile src/fragmentation/Makefile src/fs/Makefile src/fs/fs.conf src/gns/Makefile src/gns/gns.conf src/gns/nss/Makefile src/hello/Makefile src/include/Makefile src/include/gnunet_directories.h src/hostlist/Makefile src/lockmanager/Makefile src/lockmanager/lockmanager.conf src/mesh/Makefile src/mesh/mesh.conf src/mysql/Makefile src/namestore/Makefile src/namestore/namestore.conf src/nat/Makefile src/nse/Makefile src/nse/nse.conf src/peerinfo/Makefile src/peerinfo/peerinfo.conf src/peerinfo-tool/Makefile src/postgres/Makefile src/pt/Makefile src/regex/Makefile src/statistics/Makefile src/statistics/statistics.conf src/stream/Makefile src/sysmon/Makefile src/sysmon/sysmon.conf src/template/Makefile src/testbed/Makefile src/testbed/testbed.conf src/testing/Makefile src/topology/Makefile src/transport/Makefile src/transport/transport.conf src/tun/Makefile src/util/Makefile src/util/resolver.conf src/vpn/Makefile src/vpn/vpn.conf src/integration-tests/Makefile pkgconfig/Makefile pkgconfig/gnunetats.pc pkgconfig/gnunetarm.pc pkgconfig/gnunetblock.pc pkgconfig/gnunetcore.pc pkgconfig/gnunetdatacache.pc pkgconfig/gnunetdatastore.pc pkgconfig/gnunetdht.pc pkgconfig/gnunetdns.pc pkgconfig/gnunetdnsparser.pc pkgconfig/gnunetdv.pc pkgconfig/gnunetfragmentation.pc pkgconfig/gnunetfs.pc pkgconfig/gnunetgns.pc pkgconfig/gnunethello.pc pkgconfig/gnunetlockmanager.pc pkgconfig/gnunetmesh.pc pkgconfig/gnunetmysql.pc pkgconfig/gnunetnamestore.pc pkgconfig/gnunetnat.pc pkgconfig/gnunetnse.pc pkgconfig/gnunetpeerinfo.pc pkgconfig/gnunetpostgres.pc pkgconfig/gnunetregex.pc pkgconfig/gnunetstatistics.pc pkgconfig/gnunetstream.pc pkgconfig/gnunettestbed.pc pkgconfig/gnunettesting.pc pkgconfig/gnunettransport.pc pkgconfig/gnunettun.pc pkgconfig/gnunetutil.pc pkgconfig/gnunetvpn.pc" cat >confcache <<\_ACEOF # This file is a shell script that caches the results of configure @@ -27223,10 +29089,21 @@ $as_echo "$as_me: WARNING: cache variable $ac_var contains a newline" >&2;} ;; :end' >>confcache if diff "$cache_file" confcache >/dev/null 2>&1; then :; else if test -w "$cache_file"; then - test "x$cache_file" != "x/dev/null" && + if test "x$cache_file" != "x/dev/null"; then { $as_echo "$as_me:${as_lineno-$LINENO}: updating cache $cache_file" >&5 $as_echo "$as_me: updating cache $cache_file" >&6;} - cat confcache >$cache_file + if test ! -f "$cache_file" || test -h "$cache_file"; then + cat confcache >"$cache_file" + else + case $cache_file in #( + */* | ?:*) + mv -f confcache "$cache_file"$$ && + mv -f "$cache_file"$$ "$cache_file" ;; #( + *) + mv -f confcache "$cache_file" ;; + esac + fi + fi else { $as_echo "$as_me:${as_lineno-$LINENO}: not updating unwritable cache $cache_file" >&5 $as_echo "$as_me: not updating unwritable cache $cache_file" >&6;} @@ -27281,10 +29158,6 @@ if test -z "${am__fastdepOBJC_TRUE}" && test -z "${am__fastdepOBJC_FALSE}"; then as_fn_error $? "conditional \"am__fastdepOBJC\" was never defined. Usually this means the macro was only invoked conditionally." "$LINENO" 5 fi -if test -z "${am__fastdepCXX_TRUE}" && test -z "${am__fastdepCXX_FALSE}"; then - as_fn_error $? "conditional \"am__fastdepCXX\" was never defined. -Usually this means the macro was only invoked conditionally." "$LINENO" 5 -fi if test -z "${INSTALL_LTDL_TRUE}" && test -z "${INSTALL_LTDL_FALSE}"; then as_fn_error $? "conditional \"INSTALL_LTDL\" was never defined. Usually this means the macro was only invoked conditionally." "$LINENO" 5 @@ -27346,10 +29219,22 @@ if test -z "${LINUX_TRUE}" && test -z "${LINUX_FALSE}"; then as_fn_error $? "conditional \"LINUX\" was never defined. Usually this means the macro was only invoked conditionally." "$LINENO" 5 fi +if test -z "${GNU_TRUE}" && test -z "${GNU_FALSE}"; then + as_fn_error $? "conditional \"GNU\" was never defined. +Usually this means the macro was only invoked conditionally." "$LINENO" 5 +fi if test -z "${am__fastdepOBJC_TRUE}" && test -z "${am__fastdepOBJC_FALSE}"; then as_fn_error $? "conditional \"am__fastdepOBJC\" was never defined. Usually this means the macro was only invoked conditionally." "$LINENO" 5 fi +if test -z "${HAVE_LIBCURL_TRUE}" && test -z "${HAVE_LIBCURL_FALSE}"; then + as_fn_error $? "conditional \"HAVE_LIBCURL\" was never defined. +Usually this means the macro was only invoked conditionally." "$LINENO" 5 +fi +if test -z "${HAVE_LIBCURL_TRUE}" && test -z "${HAVE_LIBCURL_FALSE}"; then + as_fn_error $? "conditional \"HAVE_LIBCURL\" was never defined. +Usually this means the macro was only invoked conditionally." "$LINENO" 5 +fi if test -z "${HAVE_LIBGLPK_TRUE}" && test -z "${HAVE_LIBGLPK_FALSE}"; then as_fn_error $? "conditional \"HAVE_LIBGLPK\" was never defined. Usually this means the macro was only invoked conditionally." "$LINENO" 5 @@ -27358,6 +29243,22 @@ if test -z "${HAVE_LIBGLPK_TRUE}" && test -z "${HAVE_LIBGLPK_FALSE}"; then as_fn_error $? "conditional \"HAVE_LIBGLPK\" was never defined. Usually this means the macro was only invoked conditionally." "$LINENO" 5 fi +if test -z "${HAVE_GLIB2_TRUE}" && test -z "${HAVE_GLIB2_FALSE}"; then + as_fn_error $? "conditional \"HAVE_GLIB2\" was never defined. +Usually this means the macro was only invoked conditionally." "$LINENO" 5 +fi +if test -z "${HAVE_GLIB2_TRUE}" && test -z "${HAVE_GLIB2_FALSE}"; then + as_fn_error $? "conditional \"HAVE_GLIB2\" was never defined. +Usually this means the macro was only invoked conditionally." "$LINENO" 5 +fi +if test -z "${HAVE_LIBGTOP_TRUE}" && test -z "${HAVE_LIBGTOP_FALSE}"; then + as_fn_error $? "conditional \"HAVE_LIBGTOP\" was never defined. +Usually this means the macro was only invoked conditionally." "$LINENO" 5 +fi +if test -z "${HAVE_LIBGTOP_TRUE}" && test -z "${HAVE_LIBGTOP_FALSE}"; then + as_fn_error $? "conditional \"HAVE_LIBGTOP\" was never defined. +Usually this means the macro was only invoked conditionally." "$LINENO" 5 +fi if test -z "${HAVE_GLIBCNSS_TRUE}" && test -z "${HAVE_GLIBCNSS_FALSE}"; then as_fn_error $? "conditional \"HAVE_GLIBCNSS\" was never defined. Usually this means the macro was only invoked conditionally." "$LINENO" 5 @@ -27394,14 +29295,6 @@ if test -z "${HAVE_PYTHON_TRUE}" && test -z "${HAVE_PYTHON_FALSE}"; then as_fn_error $? "conditional \"HAVE_PYTHON\" was never defined. Usually this means the macro was only invoked conditionally." "$LINENO" 5 fi -if test -z "${HAVE_PYTHON_PEXPECT_TRUE}" && test -z "${HAVE_PYTHON_PEXPECT_FALSE}"; then - as_fn_error $? "conditional \"HAVE_PYTHON_PEXPECT\" was never defined. -Usually this means the macro was only invoked conditionally." "$LINENO" 5 -fi -if test -z "${HAVE_PYTHON_PEXPECT_TRUE}" && test -z "${HAVE_PYTHON_PEXPECT_FALSE}"; then - as_fn_error $? "conditional \"HAVE_PYTHON_PEXPECT\" was never defined. -Usually this means the macro was only invoked conditionally." "$LINENO" 5 -fi if test -z "${WANT_FRAMEWORK_TRUE}" && test -z "${WANT_FRAMEWORK_FALSE}"; then as_fn_error $? "conditional \"WANT_FRAMEWORK\" was never defined. Usually this means the macro was only invoked conditionally." "$LINENO" 5 @@ -27410,6 +29303,18 @@ if test -z "${HAVE_SUDO_TRUE}" && test -z "${HAVE_SUDO_FALSE}"; then as_fn_error $? "conditional \"HAVE_SUDO\" was never defined. Usually this means the macro was only invoked conditionally." "$LINENO" 5 fi +if test -z "${INSTALL_NSS_TRUE}" && test -z "${INSTALL_NSS_FALSE}"; then + as_fn_error $? "conditional \"INSTALL_NSS\" was never defined. +Usually this means the macro was only invoked conditionally." "$LINENO" 5 +fi +if test -z "${HAVE_GNUTLS_TRUE}" && test -z "${HAVE_GNUTLS_FALSE}"; then + as_fn_error $? "conditional \"HAVE_GNUTLS\" was never defined. +Usually this means the macro was only invoked conditionally." "$LINENO" 5 +fi +if test -z "${WITH_LL_TRUE}" && test -z "${WITH_LL_FALSE}"; then + as_fn_error $? "conditional \"WITH_LL\" was never defined. +Usually this means the macro was only invoked conditionally." "$LINENO" 5 +fi if test -z "${ENABLE_TEST_RUN_TRUE}" && test -z "${ENABLE_TEST_RUN_FALSE}"; then as_fn_error $? "conditional \"ENABLE_TEST_RUN\" was never defined. Usually this means the macro was only invoked conditionally." "$LINENO" 5 @@ -27435,7 +29340,7 @@ if test -z "${USE_COVERAGE_TRUE}" && test -z "${USE_COVERAGE_FALSE}"; then Usually this means the macro was only invoked conditionally." "$LINENO" 5 fi -: ${CONFIG_STATUS=./config.status} +: "${CONFIG_STATUS=./config.status}" ac_write_fail=0 ac_clean_files_save=$ac_clean_files ac_clean_files="$ac_clean_files $CONFIG_STATUS" @@ -27536,6 +29441,7 @@ fi IFS=" "" $as_nl" # Find who we are. Look in the path if we contain no directory separator. +as_myself= case $0 in #(( *[\\/]* ) as_myself=$0 ;; *) as_save_IFS=$IFS; IFS=$PATH_SEPARATOR @@ -27731,16 +29637,16 @@ if (echo >conf$$.file) 2>/dev/null; then # ... but there are two gotchas: # 1) On MSYS, both `ln -s file dir' and `ln file dir' fail. # 2) DJGPP < 2.04 has no symlinks; `ln -s' creates a wrapper executable. - # In both cases, we have to default to `cp -p'. + # In both cases, we have to default to `cp -pR'. ln -s conf$$.file conf$$.dir 2>/dev/null && test ! -f conf$$.exe || - as_ln_s='cp -p' + as_ln_s='cp -pR' elif ln conf$$.file conf$$ 2>/dev/null; then as_ln_s=ln else - as_ln_s='cp -p' + as_ln_s='cp -pR' fi else - as_ln_s='cp -p' + as_ln_s='cp -pR' fi rm -f conf$$ conf$$.exe conf$$.dir/conf$$.file conf$$.file rmdir conf$$.dir 2>/dev/null @@ -27800,28 +29706,16 @@ else as_mkdir_p=false fi -if test -x / >/dev/null 2>&1; then - as_test_x='test -x' -else - if ls -dL / >/dev/null 2>&1; then - as_ls_L_option=L - else - as_ls_L_option= - fi - as_test_x=' - eval sh -c '\'' - if test -d "$1"; then - test -d "$1/."; - else - case $1 in #( - -*)set "./$1";; - esac; - case `ls -ld'$as_ls_L_option' "$1" 2>/dev/null` in #(( - ???[sx]*):;;*)false;;esac;fi - '\'' sh - ' -fi -as_executable_p=$as_test_x + +# as_fn_executable_p FILE +# ----------------------- +# Test if FILE is an executable regular file. +as_fn_executable_p () +{ + test -f "$1" && test -x "$1" +} # as_fn_executable_p +as_test_x='test -x' +as_executable_p=as_fn_executable_p # Sed expression to map a string onto a valid CPP name. as_tr_cpp="eval sed 'y%*$as_cr_letters%P$as_cr_LETTERS%;s%[^_$as_cr_alnum]%_%g'" @@ -27842,8 +29736,8 @@ cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1 # report actual input values of CONFIG_FILES etc. instead of their # values after options handling. ac_log=" -This file was extended by gnunet $as_me 0.9.3, which was -generated by GNU Autoconf 2.67. Invocation command line was +This file was extended by gnunet $as_me 0.9.5a, which was +generated by GNU Autoconf 2.69. Invocation command line was CONFIG_FILES = $CONFIG_FILES CONFIG_HEADERS = $CONFIG_HEADERS @@ -27908,11 +29802,11 @@ _ACEOF cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1 ac_cs_config="`$as_echo "$ac_configure_args" | sed 's/^ //; s/[\\""\`\$]/\\\\&/g'`" ac_cs_version="\\ -gnunet config.status 0.9.3 -configured by $0, generated by GNU Autoconf 2.67, +gnunet config.status 0.9.5a +configured by $0, generated by GNU Autoconf 2.69, with options \\"\$ac_cs_config\\" -Copyright (C) 2010 Free Software Foundation, Inc. +Copyright (C) 2012 Free Software Foundation, Inc. This config.status script is free software; the Free Software Foundation gives unlimited permission to copy, distribute and modify it." @@ -28003,7 +29897,7 @@ fi _ACEOF cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1 if \$ac_cs_recheck; then - set X '$SHELL' '$0' $ac_configure_args \$ac_configure_extra_args --no-create --no-recursion + set X $SHELL '$0' $ac_configure_args \$ac_configure_extra_args --no-create --no-recursion shift \$as_echo "running CONFIG_SHELL=$SHELL \$*" >&6 CONFIG_SHELL='$SHELL' @@ -28037,186 +29931,212 @@ AMDEP_TRUE="$AMDEP_TRUE" ac_aux_dir="$ac_aux_dir" sed_quote_subst='$sed_quote_subst' double_quote_subst='$double_quote_subst' delay_variable_subst='$delay_variable_subst' -macro_version='`$ECHO "X$macro_version" | $Xsed -e "$delay_single_quote_subst"`' -macro_revision='`$ECHO "X$macro_revision" | $Xsed -e "$delay_single_quote_subst"`' -enable_static='`$ECHO "X$enable_static" | $Xsed -e "$delay_single_quote_subst"`' -AS='`$ECHO "X$AS" | $Xsed -e "$delay_single_quote_subst"`' -DLLTOOL='`$ECHO "X$DLLTOOL" | $Xsed -e "$delay_single_quote_subst"`' -OBJDUMP='`$ECHO "X$OBJDUMP" | $Xsed -e "$delay_single_quote_subst"`' -enable_shared='`$ECHO "X$enable_shared" | $Xsed -e "$delay_single_quote_subst"`' -pic_mode='`$ECHO "X$pic_mode" | $Xsed -e "$delay_single_quote_subst"`' -enable_fast_install='`$ECHO "X$enable_fast_install" | $Xsed -e "$delay_single_quote_subst"`' -host_alias='`$ECHO "X$host_alias" | $Xsed -e "$delay_single_quote_subst"`' -host='`$ECHO "X$host" | $Xsed -e "$delay_single_quote_subst"`' -host_os='`$ECHO "X$host_os" | $Xsed -e "$delay_single_quote_subst"`' -build_alias='`$ECHO "X$build_alias" | $Xsed -e "$delay_single_quote_subst"`' -build='`$ECHO "X$build" | $Xsed -e "$delay_single_quote_subst"`' -build_os='`$ECHO "X$build_os" | $Xsed -e "$delay_single_quote_subst"`' -SED='`$ECHO "X$SED" | $Xsed -e "$delay_single_quote_subst"`' -Xsed='`$ECHO "X$Xsed" | $Xsed -e "$delay_single_quote_subst"`' -GREP='`$ECHO "X$GREP" | $Xsed -e "$delay_single_quote_subst"`' -EGREP='`$ECHO "X$EGREP" | $Xsed -e "$delay_single_quote_subst"`' -FGREP='`$ECHO "X$FGREP" | $Xsed -e "$delay_single_quote_subst"`' -LD='`$ECHO "X$LD" | $Xsed -e "$delay_single_quote_subst"`' -NM='`$ECHO "X$NM" | $Xsed -e "$delay_single_quote_subst"`' -LN_S='`$ECHO "X$LN_S" | $Xsed -e "$delay_single_quote_subst"`' -max_cmd_len='`$ECHO "X$max_cmd_len" | $Xsed -e "$delay_single_quote_subst"`' -ac_objext='`$ECHO "X$ac_objext" | $Xsed -e "$delay_single_quote_subst"`' -exeext='`$ECHO "X$exeext" | $Xsed -e "$delay_single_quote_subst"`' -lt_unset='`$ECHO "X$lt_unset" | $Xsed -e "$delay_single_quote_subst"`' -lt_SP2NL='`$ECHO "X$lt_SP2NL" | $Xsed -e "$delay_single_quote_subst"`' -lt_NL2SP='`$ECHO "X$lt_NL2SP" | $Xsed -e "$delay_single_quote_subst"`' -reload_flag='`$ECHO "X$reload_flag" | $Xsed -e "$delay_single_quote_subst"`' -reload_cmds='`$ECHO "X$reload_cmds" | $Xsed -e "$delay_single_quote_subst"`' -deplibs_check_method='`$ECHO "X$deplibs_check_method" | $Xsed -e "$delay_single_quote_subst"`' -file_magic_cmd='`$ECHO "X$file_magic_cmd" | $Xsed -e "$delay_single_quote_subst"`' -AR='`$ECHO "X$AR" | $Xsed -e "$delay_single_quote_subst"`' -AR_FLAGS='`$ECHO "X$AR_FLAGS" | $Xsed -e "$delay_single_quote_subst"`' -STRIP='`$ECHO "X$STRIP" | $Xsed -e "$delay_single_quote_subst"`' -RANLIB='`$ECHO "X$RANLIB" | $Xsed -e "$delay_single_quote_subst"`' -old_postinstall_cmds='`$ECHO "X$old_postinstall_cmds" | $Xsed -e "$delay_single_quote_subst"`' -old_postuninstall_cmds='`$ECHO "X$old_postuninstall_cmds" | $Xsed -e "$delay_single_quote_subst"`' -old_archive_cmds='`$ECHO "X$old_archive_cmds" | $Xsed -e "$delay_single_quote_subst"`' -CC='`$ECHO "X$CC" | $Xsed -e "$delay_single_quote_subst"`' -CFLAGS='`$ECHO "X$CFLAGS" | $Xsed -e "$delay_single_quote_subst"`' -compiler='`$ECHO "X$compiler" | $Xsed -e "$delay_single_quote_subst"`' -GCC='`$ECHO "X$GCC" | $Xsed -e "$delay_single_quote_subst"`' -lt_cv_sys_global_symbol_pipe='`$ECHO "X$lt_cv_sys_global_symbol_pipe" | $Xsed -e "$delay_single_quote_subst"`' -lt_cv_sys_global_symbol_to_cdecl='`$ECHO "X$lt_cv_sys_global_symbol_to_cdecl" | $Xsed -e "$delay_single_quote_subst"`' -lt_cv_sys_global_symbol_to_c_name_address='`$ECHO "X$lt_cv_sys_global_symbol_to_c_name_address" | $Xsed -e "$delay_single_quote_subst"`' -lt_cv_sys_global_symbol_to_c_name_address_lib_prefix='`$ECHO "X$lt_cv_sys_global_symbol_to_c_name_address_lib_prefix" | $Xsed -e "$delay_single_quote_subst"`' -objdir='`$ECHO "X$objdir" | $Xsed -e "$delay_single_quote_subst"`' -SHELL='`$ECHO "X$SHELL" | $Xsed -e "$delay_single_quote_subst"`' -ECHO='`$ECHO "X$ECHO" | $Xsed -e "$delay_single_quote_subst"`' -MAGIC_CMD='`$ECHO "X$MAGIC_CMD" | $Xsed -e "$delay_single_quote_subst"`' -lt_prog_compiler_no_builtin_flag='`$ECHO "X$lt_prog_compiler_no_builtin_flag" | $Xsed -e "$delay_single_quote_subst"`' -lt_prog_compiler_wl='`$ECHO "X$lt_prog_compiler_wl" | $Xsed -e "$delay_single_quote_subst"`' -lt_prog_compiler_pic='`$ECHO "X$lt_prog_compiler_pic" | $Xsed -e "$delay_single_quote_subst"`' -lt_prog_compiler_static='`$ECHO "X$lt_prog_compiler_static" | $Xsed -e "$delay_single_quote_subst"`' -lt_cv_prog_compiler_c_o='`$ECHO "X$lt_cv_prog_compiler_c_o" | $Xsed -e "$delay_single_quote_subst"`' -need_locks='`$ECHO "X$need_locks" | $Xsed -e "$delay_single_quote_subst"`' -DSYMUTIL='`$ECHO "X$DSYMUTIL" | $Xsed -e "$delay_single_quote_subst"`' -NMEDIT='`$ECHO "X$NMEDIT" | $Xsed -e "$delay_single_quote_subst"`' -LIPO='`$ECHO "X$LIPO" | $Xsed -e "$delay_single_quote_subst"`' -OTOOL='`$ECHO "X$OTOOL" | $Xsed -e "$delay_single_quote_subst"`' -OTOOL64='`$ECHO "X$OTOOL64" | $Xsed -e "$delay_single_quote_subst"`' -libext='`$ECHO "X$libext" | $Xsed -e "$delay_single_quote_subst"`' -shrext_cmds='`$ECHO "X$shrext_cmds" | $Xsed -e "$delay_single_quote_subst"`' -extract_expsyms_cmds='`$ECHO "X$extract_expsyms_cmds" | $Xsed -e "$delay_single_quote_subst"`' -archive_cmds_need_lc='`$ECHO "X$archive_cmds_need_lc" | $Xsed -e "$delay_single_quote_subst"`' -enable_shared_with_static_runtimes='`$ECHO "X$enable_shared_with_static_runtimes" | $Xsed -e "$delay_single_quote_subst"`' -export_dynamic_flag_spec='`$ECHO "X$export_dynamic_flag_spec" | $Xsed -e "$delay_single_quote_subst"`' -whole_archive_flag_spec='`$ECHO "X$whole_archive_flag_spec" | $Xsed -e "$delay_single_quote_subst"`' -compiler_needs_object='`$ECHO "X$compiler_needs_object" | $Xsed -e "$delay_single_quote_subst"`' -old_archive_from_new_cmds='`$ECHO "X$old_archive_from_new_cmds" | $Xsed -e "$delay_single_quote_subst"`' -old_archive_from_expsyms_cmds='`$ECHO "X$old_archive_from_expsyms_cmds" | $Xsed -e "$delay_single_quote_subst"`' -archive_cmds='`$ECHO "X$archive_cmds" | $Xsed -e "$delay_single_quote_subst"`' -archive_expsym_cmds='`$ECHO "X$archive_expsym_cmds" | $Xsed -e "$delay_single_quote_subst"`' -module_cmds='`$ECHO "X$module_cmds" | $Xsed -e "$delay_single_quote_subst"`' -module_expsym_cmds='`$ECHO "X$module_expsym_cmds" | $Xsed -e "$delay_single_quote_subst"`' -with_gnu_ld='`$ECHO "X$with_gnu_ld" | $Xsed -e "$delay_single_quote_subst"`' -allow_undefined_flag='`$ECHO "X$allow_undefined_flag" | $Xsed -e "$delay_single_quote_subst"`' -no_undefined_flag='`$ECHO "X$no_undefined_flag" | $Xsed -e "$delay_single_quote_subst"`' -hardcode_libdir_flag_spec='`$ECHO "X$hardcode_libdir_flag_spec" | $Xsed -e "$delay_single_quote_subst"`' -hardcode_libdir_flag_spec_ld='`$ECHO "X$hardcode_libdir_flag_spec_ld" | $Xsed -e "$delay_single_quote_subst"`' -hardcode_libdir_separator='`$ECHO "X$hardcode_libdir_separator" | $Xsed -e "$delay_single_quote_subst"`' -hardcode_direct='`$ECHO "X$hardcode_direct" | $Xsed -e "$delay_single_quote_subst"`' -hardcode_direct_absolute='`$ECHO "X$hardcode_direct_absolute" | $Xsed -e "$delay_single_quote_subst"`' -hardcode_minus_L='`$ECHO "X$hardcode_minus_L" | $Xsed -e "$delay_single_quote_subst"`' -hardcode_shlibpath_var='`$ECHO "X$hardcode_shlibpath_var" | $Xsed -e "$delay_single_quote_subst"`' -hardcode_automatic='`$ECHO "X$hardcode_automatic" | $Xsed -e "$delay_single_quote_subst"`' -inherit_rpath='`$ECHO "X$inherit_rpath" | $Xsed -e "$delay_single_quote_subst"`' -link_all_deplibs='`$ECHO "X$link_all_deplibs" | $Xsed -e "$delay_single_quote_subst"`' -fix_srcfile_path='`$ECHO "X$fix_srcfile_path" | $Xsed -e "$delay_single_quote_subst"`' -always_export_symbols='`$ECHO "X$always_export_symbols" | $Xsed -e "$delay_single_quote_subst"`' -export_symbols_cmds='`$ECHO "X$export_symbols_cmds" | $Xsed -e "$delay_single_quote_subst"`' -exclude_expsyms='`$ECHO "X$exclude_expsyms" | $Xsed -e "$delay_single_quote_subst"`' -include_expsyms='`$ECHO "X$include_expsyms" | $Xsed -e "$delay_single_quote_subst"`' -prelink_cmds='`$ECHO "X$prelink_cmds" | $Xsed -e "$delay_single_quote_subst"`' -file_list_spec='`$ECHO "X$file_list_spec" | $Xsed -e "$delay_single_quote_subst"`' -variables_saved_for_relink='`$ECHO "X$variables_saved_for_relink" | $Xsed -e "$delay_single_quote_subst"`' -need_lib_prefix='`$ECHO "X$need_lib_prefix" | $Xsed -e "$delay_single_quote_subst"`' -need_version='`$ECHO "X$need_version" | $Xsed -e "$delay_single_quote_subst"`' -version_type='`$ECHO "X$version_type" | $Xsed -e "$delay_single_quote_subst"`' -runpath_var='`$ECHO "X$runpath_var" | $Xsed -e "$delay_single_quote_subst"`' -shlibpath_var='`$ECHO "X$shlibpath_var" | $Xsed -e "$delay_single_quote_subst"`' -shlibpath_overrides_runpath='`$ECHO "X$shlibpath_overrides_runpath" | $Xsed -e "$delay_single_quote_subst"`' -libname_spec='`$ECHO "X$libname_spec" | $Xsed -e "$delay_single_quote_subst"`' -library_names_spec='`$ECHO "X$library_names_spec" | $Xsed -e "$delay_single_quote_subst"`' -soname_spec='`$ECHO "X$soname_spec" | $Xsed -e "$delay_single_quote_subst"`' -postinstall_cmds='`$ECHO "X$postinstall_cmds" | $Xsed -e "$delay_single_quote_subst"`' -postuninstall_cmds='`$ECHO "X$postuninstall_cmds" | $Xsed -e "$delay_single_quote_subst"`' -finish_cmds='`$ECHO "X$finish_cmds" | $Xsed -e "$delay_single_quote_subst"`' -finish_eval='`$ECHO "X$finish_eval" | $Xsed -e "$delay_single_quote_subst"`' -hardcode_into_libs='`$ECHO "X$hardcode_into_libs" | $Xsed -e "$delay_single_quote_subst"`' -sys_lib_search_path_spec='`$ECHO "X$sys_lib_search_path_spec" | $Xsed -e "$delay_single_quote_subst"`' -sys_lib_dlsearch_path_spec='`$ECHO "X$sys_lib_dlsearch_path_spec" | $Xsed -e "$delay_single_quote_subst"`' -hardcode_action='`$ECHO "X$hardcode_action" | $Xsed -e "$delay_single_quote_subst"`' -enable_dlopen='`$ECHO "X$enable_dlopen" | $Xsed -e "$delay_single_quote_subst"`' -enable_dlopen_self='`$ECHO "X$enable_dlopen_self" | $Xsed -e "$delay_single_quote_subst"`' -enable_dlopen_self_static='`$ECHO "X$enable_dlopen_self_static" | $Xsed -e "$delay_single_quote_subst"`' -old_striplib='`$ECHO "X$old_striplib" | $Xsed -e "$delay_single_quote_subst"`' -striplib='`$ECHO "X$striplib" | $Xsed -e "$delay_single_quote_subst"`' -compiler_lib_search_dirs='`$ECHO "X$compiler_lib_search_dirs" | $Xsed -e "$delay_single_quote_subst"`' -predep_objects='`$ECHO "X$predep_objects" | $Xsed -e "$delay_single_quote_subst"`' -postdep_objects='`$ECHO "X$postdep_objects" | $Xsed -e "$delay_single_quote_subst"`' -predeps='`$ECHO "X$predeps" | $Xsed -e "$delay_single_quote_subst"`' -postdeps='`$ECHO "X$postdeps" | $Xsed -e "$delay_single_quote_subst"`' -compiler_lib_search_path='`$ECHO "X$compiler_lib_search_path" | $Xsed -e "$delay_single_quote_subst"`' -LD_CXX='`$ECHO "X$LD_CXX" | $Xsed -e "$delay_single_quote_subst"`' -old_archive_cmds_CXX='`$ECHO "X$old_archive_cmds_CXX" | $Xsed -e "$delay_single_quote_subst"`' -compiler_CXX='`$ECHO "X$compiler_CXX" | $Xsed -e "$delay_single_quote_subst"`' -GCC_CXX='`$ECHO "X$GCC_CXX" | $Xsed -e "$delay_single_quote_subst"`' -lt_prog_compiler_no_builtin_flag_CXX='`$ECHO "X$lt_prog_compiler_no_builtin_flag_CXX" | $Xsed -e "$delay_single_quote_subst"`' -lt_prog_compiler_wl_CXX='`$ECHO "X$lt_prog_compiler_wl_CXX" | $Xsed -e "$delay_single_quote_subst"`' -lt_prog_compiler_pic_CXX='`$ECHO "X$lt_prog_compiler_pic_CXX" | $Xsed -e "$delay_single_quote_subst"`' -lt_prog_compiler_static_CXX='`$ECHO "X$lt_prog_compiler_static_CXX" | $Xsed -e "$delay_single_quote_subst"`' -lt_cv_prog_compiler_c_o_CXX='`$ECHO "X$lt_cv_prog_compiler_c_o_CXX" | $Xsed -e "$delay_single_quote_subst"`' -archive_cmds_need_lc_CXX='`$ECHO "X$archive_cmds_need_lc_CXX" | $Xsed -e "$delay_single_quote_subst"`' -enable_shared_with_static_runtimes_CXX='`$ECHO "X$enable_shared_with_static_runtimes_CXX" | $Xsed -e "$delay_single_quote_subst"`' -export_dynamic_flag_spec_CXX='`$ECHO "X$export_dynamic_flag_spec_CXX" | $Xsed -e "$delay_single_quote_subst"`' -whole_archive_flag_spec_CXX='`$ECHO "X$whole_archive_flag_spec_CXX" | $Xsed -e "$delay_single_quote_subst"`' -compiler_needs_object_CXX='`$ECHO "X$compiler_needs_object_CXX" | $Xsed -e "$delay_single_quote_subst"`' -old_archive_from_new_cmds_CXX='`$ECHO "X$old_archive_from_new_cmds_CXX" | $Xsed -e "$delay_single_quote_subst"`' -old_archive_from_expsyms_cmds_CXX='`$ECHO "X$old_archive_from_expsyms_cmds_CXX" | $Xsed -e "$delay_single_quote_subst"`' -archive_cmds_CXX='`$ECHO "X$archive_cmds_CXX" | $Xsed -e "$delay_single_quote_subst"`' -archive_expsym_cmds_CXX='`$ECHO "X$archive_expsym_cmds_CXX" | $Xsed -e "$delay_single_quote_subst"`' -module_cmds_CXX='`$ECHO "X$module_cmds_CXX" | $Xsed -e "$delay_single_quote_subst"`' -module_expsym_cmds_CXX='`$ECHO "X$module_expsym_cmds_CXX" | $Xsed -e "$delay_single_quote_subst"`' -with_gnu_ld_CXX='`$ECHO "X$with_gnu_ld_CXX" | $Xsed -e "$delay_single_quote_subst"`' -allow_undefined_flag_CXX='`$ECHO "X$allow_undefined_flag_CXX" | $Xsed -e "$delay_single_quote_subst"`' -no_undefined_flag_CXX='`$ECHO "X$no_undefined_flag_CXX" | $Xsed -e "$delay_single_quote_subst"`' -hardcode_libdir_flag_spec_CXX='`$ECHO "X$hardcode_libdir_flag_spec_CXX" | $Xsed -e "$delay_single_quote_subst"`' -hardcode_libdir_flag_spec_ld_CXX='`$ECHO "X$hardcode_libdir_flag_spec_ld_CXX" | $Xsed -e "$delay_single_quote_subst"`' -hardcode_libdir_separator_CXX='`$ECHO "X$hardcode_libdir_separator_CXX" | $Xsed -e "$delay_single_quote_subst"`' -hardcode_direct_CXX='`$ECHO "X$hardcode_direct_CXX" | $Xsed -e "$delay_single_quote_subst"`' -hardcode_direct_absolute_CXX='`$ECHO "X$hardcode_direct_absolute_CXX" | $Xsed -e "$delay_single_quote_subst"`' -hardcode_minus_L_CXX='`$ECHO "X$hardcode_minus_L_CXX" | $Xsed -e "$delay_single_quote_subst"`' -hardcode_shlibpath_var_CXX='`$ECHO "X$hardcode_shlibpath_var_CXX" | $Xsed -e "$delay_single_quote_subst"`' -hardcode_automatic_CXX='`$ECHO "X$hardcode_automatic_CXX" | $Xsed -e "$delay_single_quote_subst"`' -inherit_rpath_CXX='`$ECHO "X$inherit_rpath_CXX" | $Xsed -e "$delay_single_quote_subst"`' -link_all_deplibs_CXX='`$ECHO "X$link_all_deplibs_CXX" | $Xsed -e "$delay_single_quote_subst"`' -fix_srcfile_path_CXX='`$ECHO "X$fix_srcfile_path_CXX" | $Xsed -e "$delay_single_quote_subst"`' -always_export_symbols_CXX='`$ECHO "X$always_export_symbols_CXX" | $Xsed -e "$delay_single_quote_subst"`' -export_symbols_cmds_CXX='`$ECHO "X$export_symbols_cmds_CXX" | $Xsed -e "$delay_single_quote_subst"`' -exclude_expsyms_CXX='`$ECHO "X$exclude_expsyms_CXX" | $Xsed -e "$delay_single_quote_subst"`' -include_expsyms_CXX='`$ECHO "X$include_expsyms_CXX" | $Xsed -e "$delay_single_quote_subst"`' -prelink_cmds_CXX='`$ECHO "X$prelink_cmds_CXX" | $Xsed -e "$delay_single_quote_subst"`' -file_list_spec_CXX='`$ECHO "X$file_list_spec_CXX" | $Xsed -e "$delay_single_quote_subst"`' -hardcode_action_CXX='`$ECHO "X$hardcode_action_CXX" | $Xsed -e "$delay_single_quote_subst"`' -compiler_lib_search_dirs_CXX='`$ECHO "X$compiler_lib_search_dirs_CXX" | $Xsed -e "$delay_single_quote_subst"`' -predep_objects_CXX='`$ECHO "X$predep_objects_CXX" | $Xsed -e "$delay_single_quote_subst"`' -postdep_objects_CXX='`$ECHO "X$postdep_objects_CXX" | $Xsed -e "$delay_single_quote_subst"`' -predeps_CXX='`$ECHO "X$predeps_CXX" | $Xsed -e "$delay_single_quote_subst"`' -postdeps_CXX='`$ECHO "X$postdeps_CXX" | $Xsed -e "$delay_single_quote_subst"`' -compiler_lib_search_path_CXX='`$ECHO "X$compiler_lib_search_path_CXX" | $Xsed -e "$delay_single_quote_subst"`' +macro_version='`$ECHO "$macro_version" | $SED "$delay_single_quote_subst"`' +macro_revision='`$ECHO "$macro_revision" | $SED "$delay_single_quote_subst"`' +enable_static='`$ECHO "$enable_static" | $SED "$delay_single_quote_subst"`' +AS='`$ECHO "$AS" | $SED "$delay_single_quote_subst"`' +DLLTOOL='`$ECHO "$DLLTOOL" | $SED "$delay_single_quote_subst"`' +OBJDUMP='`$ECHO "$OBJDUMP" | $SED "$delay_single_quote_subst"`' +enable_shared='`$ECHO "$enable_shared" | $SED "$delay_single_quote_subst"`' +pic_mode='`$ECHO "$pic_mode" | $SED "$delay_single_quote_subst"`' +enable_fast_install='`$ECHO "$enable_fast_install" | $SED "$delay_single_quote_subst"`' +SHELL='`$ECHO "$SHELL" | $SED "$delay_single_quote_subst"`' +ECHO='`$ECHO "$ECHO" | $SED "$delay_single_quote_subst"`' +PATH_SEPARATOR='`$ECHO "$PATH_SEPARATOR" | $SED "$delay_single_quote_subst"`' +host_alias='`$ECHO "$host_alias" | $SED "$delay_single_quote_subst"`' +host='`$ECHO "$host" | $SED "$delay_single_quote_subst"`' +host_os='`$ECHO "$host_os" | $SED "$delay_single_quote_subst"`' +build_alias='`$ECHO "$build_alias" | $SED "$delay_single_quote_subst"`' +build='`$ECHO "$build" | $SED "$delay_single_quote_subst"`' +build_os='`$ECHO "$build_os" | $SED "$delay_single_quote_subst"`' +SED='`$ECHO "$SED" | $SED "$delay_single_quote_subst"`' +Xsed='`$ECHO "$Xsed" | $SED "$delay_single_quote_subst"`' +GREP='`$ECHO "$GREP" | $SED "$delay_single_quote_subst"`' +EGREP='`$ECHO "$EGREP" | $SED "$delay_single_quote_subst"`' +FGREP='`$ECHO "$FGREP" | $SED "$delay_single_quote_subst"`' +LD='`$ECHO "$LD" | $SED "$delay_single_quote_subst"`' +NM='`$ECHO "$NM" | $SED "$delay_single_quote_subst"`' +LN_S='`$ECHO "$LN_S" | $SED "$delay_single_quote_subst"`' +max_cmd_len='`$ECHO "$max_cmd_len" | $SED "$delay_single_quote_subst"`' +ac_objext='`$ECHO "$ac_objext" | $SED "$delay_single_quote_subst"`' +exeext='`$ECHO "$exeext" | $SED "$delay_single_quote_subst"`' +lt_unset='`$ECHO "$lt_unset" | $SED "$delay_single_quote_subst"`' +lt_SP2NL='`$ECHO "$lt_SP2NL" | $SED "$delay_single_quote_subst"`' +lt_NL2SP='`$ECHO "$lt_NL2SP" | $SED "$delay_single_quote_subst"`' +lt_cv_to_host_file_cmd='`$ECHO "$lt_cv_to_host_file_cmd" | $SED "$delay_single_quote_subst"`' +lt_cv_to_tool_file_cmd='`$ECHO "$lt_cv_to_tool_file_cmd" | $SED "$delay_single_quote_subst"`' +reload_flag='`$ECHO "$reload_flag" | $SED "$delay_single_quote_subst"`' +reload_cmds='`$ECHO "$reload_cmds" | $SED "$delay_single_quote_subst"`' +deplibs_check_method='`$ECHO "$deplibs_check_method" | $SED "$delay_single_quote_subst"`' +file_magic_cmd='`$ECHO "$file_magic_cmd" | $SED "$delay_single_quote_subst"`' +file_magic_glob='`$ECHO "$file_magic_glob" | $SED "$delay_single_quote_subst"`' +want_nocaseglob='`$ECHO "$want_nocaseglob" | $SED "$delay_single_quote_subst"`' +sharedlib_from_linklib_cmd='`$ECHO "$sharedlib_from_linklib_cmd" | $SED "$delay_single_quote_subst"`' +AR='`$ECHO "$AR" | $SED "$delay_single_quote_subst"`' +AR_FLAGS='`$ECHO "$AR_FLAGS" | $SED "$delay_single_quote_subst"`' +archiver_list_spec='`$ECHO "$archiver_list_spec" | $SED "$delay_single_quote_subst"`' +STRIP='`$ECHO "$STRIP" | $SED "$delay_single_quote_subst"`' +RANLIB='`$ECHO "$RANLIB" | $SED "$delay_single_quote_subst"`' +old_postinstall_cmds='`$ECHO "$old_postinstall_cmds" | $SED "$delay_single_quote_subst"`' +old_postuninstall_cmds='`$ECHO "$old_postuninstall_cmds" | $SED "$delay_single_quote_subst"`' +old_archive_cmds='`$ECHO "$old_archive_cmds" | $SED "$delay_single_quote_subst"`' +lock_old_archive_extraction='`$ECHO "$lock_old_archive_extraction" | $SED "$delay_single_quote_subst"`' +CC='`$ECHO "$CC" | $SED "$delay_single_quote_subst"`' +CFLAGS='`$ECHO "$CFLAGS" | $SED "$delay_single_quote_subst"`' +compiler='`$ECHO "$compiler" | $SED "$delay_single_quote_subst"`' +GCC='`$ECHO "$GCC" | $SED "$delay_single_quote_subst"`' +lt_cv_sys_global_symbol_pipe='`$ECHO "$lt_cv_sys_global_symbol_pipe" | $SED "$delay_single_quote_subst"`' +lt_cv_sys_global_symbol_to_cdecl='`$ECHO "$lt_cv_sys_global_symbol_to_cdecl" | $SED "$delay_single_quote_subst"`' +lt_cv_sys_global_symbol_to_c_name_address='`$ECHO "$lt_cv_sys_global_symbol_to_c_name_address" | $SED "$delay_single_quote_subst"`' +lt_cv_sys_global_symbol_to_c_name_address_lib_prefix='`$ECHO "$lt_cv_sys_global_symbol_to_c_name_address_lib_prefix" | $SED "$delay_single_quote_subst"`' +nm_file_list_spec='`$ECHO "$nm_file_list_spec" | $SED "$delay_single_quote_subst"`' +lt_sysroot='`$ECHO "$lt_sysroot" | $SED "$delay_single_quote_subst"`' +objdir='`$ECHO "$objdir" | $SED "$delay_single_quote_subst"`' +MAGIC_CMD='`$ECHO "$MAGIC_CMD" | $SED "$delay_single_quote_subst"`' +lt_prog_compiler_no_builtin_flag='`$ECHO "$lt_prog_compiler_no_builtin_flag" | $SED "$delay_single_quote_subst"`' +lt_prog_compiler_pic='`$ECHO "$lt_prog_compiler_pic" | $SED "$delay_single_quote_subst"`' +lt_prog_compiler_wl='`$ECHO "$lt_prog_compiler_wl" | $SED "$delay_single_quote_subst"`' +lt_prog_compiler_static='`$ECHO "$lt_prog_compiler_static" | $SED "$delay_single_quote_subst"`' +lt_cv_prog_compiler_c_o='`$ECHO "$lt_cv_prog_compiler_c_o" | $SED "$delay_single_quote_subst"`' +need_locks='`$ECHO "$need_locks" | $SED "$delay_single_quote_subst"`' +MANIFEST_TOOL='`$ECHO "$MANIFEST_TOOL" | $SED "$delay_single_quote_subst"`' +DSYMUTIL='`$ECHO "$DSYMUTIL" | $SED "$delay_single_quote_subst"`' +NMEDIT='`$ECHO "$NMEDIT" | $SED "$delay_single_quote_subst"`' +LIPO='`$ECHO "$LIPO" | $SED "$delay_single_quote_subst"`' +OTOOL='`$ECHO "$OTOOL" | $SED "$delay_single_quote_subst"`' +OTOOL64='`$ECHO "$OTOOL64" | $SED "$delay_single_quote_subst"`' +libext='`$ECHO "$libext" | $SED "$delay_single_quote_subst"`' +shrext_cmds='`$ECHO "$shrext_cmds" | $SED "$delay_single_quote_subst"`' +extract_expsyms_cmds='`$ECHO "$extract_expsyms_cmds" | $SED "$delay_single_quote_subst"`' +archive_cmds_need_lc='`$ECHO "$archive_cmds_need_lc" | $SED "$delay_single_quote_subst"`' +enable_shared_with_static_runtimes='`$ECHO "$enable_shared_with_static_runtimes" | $SED "$delay_single_quote_subst"`' +export_dynamic_flag_spec='`$ECHO "$export_dynamic_flag_spec" | $SED "$delay_single_quote_subst"`' +whole_archive_flag_spec='`$ECHO "$whole_archive_flag_spec" | $SED "$delay_single_quote_subst"`' +compiler_needs_object='`$ECHO "$compiler_needs_object" | $SED "$delay_single_quote_subst"`' +old_archive_from_new_cmds='`$ECHO "$old_archive_from_new_cmds" | $SED "$delay_single_quote_subst"`' +old_archive_from_expsyms_cmds='`$ECHO "$old_archive_from_expsyms_cmds" | $SED "$delay_single_quote_subst"`' +archive_cmds='`$ECHO "$archive_cmds" | $SED "$delay_single_quote_subst"`' +archive_expsym_cmds='`$ECHO "$archive_expsym_cmds" | $SED "$delay_single_quote_subst"`' +module_cmds='`$ECHO "$module_cmds" | $SED "$delay_single_quote_subst"`' +module_expsym_cmds='`$ECHO "$module_expsym_cmds" | $SED "$delay_single_quote_subst"`' +with_gnu_ld='`$ECHO "$with_gnu_ld" | $SED "$delay_single_quote_subst"`' +allow_undefined_flag='`$ECHO "$allow_undefined_flag" | $SED "$delay_single_quote_subst"`' +no_undefined_flag='`$ECHO "$no_undefined_flag" | $SED "$delay_single_quote_subst"`' +hardcode_libdir_flag_spec='`$ECHO "$hardcode_libdir_flag_spec" | $SED "$delay_single_quote_subst"`' +hardcode_libdir_separator='`$ECHO "$hardcode_libdir_separator" | $SED "$delay_single_quote_subst"`' +hardcode_direct='`$ECHO "$hardcode_direct" | $SED "$delay_single_quote_subst"`' +hardcode_direct_absolute='`$ECHO "$hardcode_direct_absolute" | $SED "$delay_single_quote_subst"`' +hardcode_minus_L='`$ECHO "$hardcode_minus_L" | $SED "$delay_single_quote_subst"`' +hardcode_shlibpath_var='`$ECHO "$hardcode_shlibpath_var" | $SED "$delay_single_quote_subst"`' +hardcode_automatic='`$ECHO "$hardcode_automatic" | $SED "$delay_single_quote_subst"`' +inherit_rpath='`$ECHO "$inherit_rpath" | $SED "$delay_single_quote_subst"`' +link_all_deplibs='`$ECHO "$link_all_deplibs" | $SED "$delay_single_quote_subst"`' +always_export_symbols='`$ECHO "$always_export_symbols" | $SED "$delay_single_quote_subst"`' +export_symbols_cmds='`$ECHO "$export_symbols_cmds" | $SED "$delay_single_quote_subst"`' +exclude_expsyms='`$ECHO "$exclude_expsyms" | $SED "$delay_single_quote_subst"`' +include_expsyms='`$ECHO "$include_expsyms" | $SED "$delay_single_quote_subst"`' +prelink_cmds='`$ECHO "$prelink_cmds" | $SED "$delay_single_quote_subst"`' +postlink_cmds='`$ECHO "$postlink_cmds" | $SED "$delay_single_quote_subst"`' +file_list_spec='`$ECHO "$file_list_spec" | $SED "$delay_single_quote_subst"`' +variables_saved_for_relink='`$ECHO "$variables_saved_for_relink" | $SED "$delay_single_quote_subst"`' +need_lib_prefix='`$ECHO "$need_lib_prefix" | $SED "$delay_single_quote_subst"`' +need_version='`$ECHO "$need_version" | $SED "$delay_single_quote_subst"`' +version_type='`$ECHO "$version_type" | $SED "$delay_single_quote_subst"`' +runpath_var='`$ECHO "$runpath_var" | $SED "$delay_single_quote_subst"`' +shlibpath_var='`$ECHO "$shlibpath_var" | $SED "$delay_single_quote_subst"`' +shlibpath_overrides_runpath='`$ECHO "$shlibpath_overrides_runpath" | $SED "$delay_single_quote_subst"`' +libname_spec='`$ECHO "$libname_spec" | $SED "$delay_single_quote_subst"`' +library_names_spec='`$ECHO "$library_names_spec" | $SED "$delay_single_quote_subst"`' +soname_spec='`$ECHO "$soname_spec" | $SED "$delay_single_quote_subst"`' +install_override_mode='`$ECHO "$install_override_mode" | $SED "$delay_single_quote_subst"`' +postinstall_cmds='`$ECHO "$postinstall_cmds" | $SED "$delay_single_quote_subst"`' +postuninstall_cmds='`$ECHO "$postuninstall_cmds" | $SED "$delay_single_quote_subst"`' +finish_cmds='`$ECHO "$finish_cmds" | $SED "$delay_single_quote_subst"`' +finish_eval='`$ECHO "$finish_eval" | $SED "$delay_single_quote_subst"`' +hardcode_into_libs='`$ECHO "$hardcode_into_libs" | $SED "$delay_single_quote_subst"`' +sys_lib_search_path_spec='`$ECHO "$sys_lib_search_path_spec" | $SED "$delay_single_quote_subst"`' +sys_lib_dlsearch_path_spec='`$ECHO "$sys_lib_dlsearch_path_spec" | $SED "$delay_single_quote_subst"`' +hardcode_action='`$ECHO "$hardcode_action" | $SED "$delay_single_quote_subst"`' +enable_dlopen='`$ECHO "$enable_dlopen" | $SED "$delay_single_quote_subst"`' +enable_dlopen_self='`$ECHO "$enable_dlopen_self" | $SED "$delay_single_quote_subst"`' +enable_dlopen_self_static='`$ECHO "$enable_dlopen_self_static" | $SED "$delay_single_quote_subst"`' +old_striplib='`$ECHO "$old_striplib" | $SED "$delay_single_quote_subst"`' +striplib='`$ECHO "$striplib" | $SED "$delay_single_quote_subst"`' +compiler_lib_search_dirs='`$ECHO "$compiler_lib_search_dirs" | $SED "$delay_single_quote_subst"`' +predep_objects='`$ECHO "$predep_objects" | $SED "$delay_single_quote_subst"`' +postdep_objects='`$ECHO "$postdep_objects" | $SED "$delay_single_quote_subst"`' +predeps='`$ECHO "$predeps" | $SED "$delay_single_quote_subst"`' +postdeps='`$ECHO "$postdeps" | $SED "$delay_single_quote_subst"`' +compiler_lib_search_path='`$ECHO "$compiler_lib_search_path" | $SED "$delay_single_quote_subst"`' +LD_CXX='`$ECHO "$LD_CXX" | $SED "$delay_single_quote_subst"`' +reload_flag_CXX='`$ECHO "$reload_flag_CXX" | $SED "$delay_single_quote_subst"`' +reload_cmds_CXX='`$ECHO "$reload_cmds_CXX" | $SED "$delay_single_quote_subst"`' +old_archive_cmds_CXX='`$ECHO "$old_archive_cmds_CXX" | $SED "$delay_single_quote_subst"`' +compiler_CXX='`$ECHO "$compiler_CXX" | $SED "$delay_single_quote_subst"`' +GCC_CXX='`$ECHO "$GCC_CXX" | $SED "$delay_single_quote_subst"`' +lt_prog_compiler_no_builtin_flag_CXX='`$ECHO "$lt_prog_compiler_no_builtin_flag_CXX" | $SED "$delay_single_quote_subst"`' +lt_prog_compiler_pic_CXX='`$ECHO "$lt_prog_compiler_pic_CXX" | $SED "$delay_single_quote_subst"`' +lt_prog_compiler_wl_CXX='`$ECHO "$lt_prog_compiler_wl_CXX" | $SED "$delay_single_quote_subst"`' +lt_prog_compiler_static_CXX='`$ECHO "$lt_prog_compiler_static_CXX" | $SED "$delay_single_quote_subst"`' +lt_cv_prog_compiler_c_o_CXX='`$ECHO "$lt_cv_prog_compiler_c_o_CXX" | $SED "$delay_single_quote_subst"`' +archive_cmds_need_lc_CXX='`$ECHO "$archive_cmds_need_lc_CXX" | $SED "$delay_single_quote_subst"`' +enable_shared_with_static_runtimes_CXX='`$ECHO "$enable_shared_with_static_runtimes_CXX" | $SED "$delay_single_quote_subst"`' +export_dynamic_flag_spec_CXX='`$ECHO "$export_dynamic_flag_spec_CXX" | $SED "$delay_single_quote_subst"`' +whole_archive_flag_spec_CXX='`$ECHO "$whole_archive_flag_spec_CXX" | $SED "$delay_single_quote_subst"`' +compiler_needs_object_CXX='`$ECHO "$compiler_needs_object_CXX" | $SED "$delay_single_quote_subst"`' +old_archive_from_new_cmds_CXX='`$ECHO "$old_archive_from_new_cmds_CXX" | $SED "$delay_single_quote_subst"`' +old_archive_from_expsyms_cmds_CXX='`$ECHO "$old_archive_from_expsyms_cmds_CXX" | $SED "$delay_single_quote_subst"`' +archive_cmds_CXX='`$ECHO "$archive_cmds_CXX" | $SED "$delay_single_quote_subst"`' +archive_expsym_cmds_CXX='`$ECHO "$archive_expsym_cmds_CXX" | $SED "$delay_single_quote_subst"`' +module_cmds_CXX='`$ECHO "$module_cmds_CXX" | $SED "$delay_single_quote_subst"`' +module_expsym_cmds_CXX='`$ECHO "$module_expsym_cmds_CXX" | $SED "$delay_single_quote_subst"`' +with_gnu_ld_CXX='`$ECHO "$with_gnu_ld_CXX" | $SED "$delay_single_quote_subst"`' +allow_undefined_flag_CXX='`$ECHO "$allow_undefined_flag_CXX" | $SED "$delay_single_quote_subst"`' +no_undefined_flag_CXX='`$ECHO "$no_undefined_flag_CXX" | $SED "$delay_single_quote_subst"`' +hardcode_libdir_flag_spec_CXX='`$ECHO "$hardcode_libdir_flag_spec_CXX" | $SED "$delay_single_quote_subst"`' +hardcode_libdir_separator_CXX='`$ECHO "$hardcode_libdir_separator_CXX" | $SED "$delay_single_quote_subst"`' +hardcode_direct_CXX='`$ECHO "$hardcode_direct_CXX" | $SED "$delay_single_quote_subst"`' +hardcode_direct_absolute_CXX='`$ECHO "$hardcode_direct_absolute_CXX" | $SED "$delay_single_quote_subst"`' +hardcode_minus_L_CXX='`$ECHO "$hardcode_minus_L_CXX" | $SED "$delay_single_quote_subst"`' +hardcode_shlibpath_var_CXX='`$ECHO "$hardcode_shlibpath_var_CXX" | $SED "$delay_single_quote_subst"`' +hardcode_automatic_CXX='`$ECHO "$hardcode_automatic_CXX" | $SED "$delay_single_quote_subst"`' +inherit_rpath_CXX='`$ECHO "$inherit_rpath_CXX" | $SED "$delay_single_quote_subst"`' +link_all_deplibs_CXX='`$ECHO "$link_all_deplibs_CXX" | $SED "$delay_single_quote_subst"`' +always_export_symbols_CXX='`$ECHO "$always_export_symbols_CXX" | $SED "$delay_single_quote_subst"`' +export_symbols_cmds_CXX='`$ECHO "$export_symbols_cmds_CXX" | $SED "$delay_single_quote_subst"`' +exclude_expsyms_CXX='`$ECHO "$exclude_expsyms_CXX" | $SED "$delay_single_quote_subst"`' +include_expsyms_CXX='`$ECHO "$include_expsyms_CXX" | $SED "$delay_single_quote_subst"`' +prelink_cmds_CXX='`$ECHO "$prelink_cmds_CXX" | $SED "$delay_single_quote_subst"`' +postlink_cmds_CXX='`$ECHO "$postlink_cmds_CXX" | $SED "$delay_single_quote_subst"`' +file_list_spec_CXX='`$ECHO "$file_list_spec_CXX" | $SED "$delay_single_quote_subst"`' +hardcode_action_CXX='`$ECHO "$hardcode_action_CXX" | $SED "$delay_single_quote_subst"`' +compiler_lib_search_dirs_CXX='`$ECHO "$compiler_lib_search_dirs_CXX" | $SED "$delay_single_quote_subst"`' +predep_objects_CXX='`$ECHO "$predep_objects_CXX" | $SED "$delay_single_quote_subst"`' +postdep_objects_CXX='`$ECHO "$postdep_objects_CXX" | $SED "$delay_single_quote_subst"`' +predeps_CXX='`$ECHO "$predeps_CXX" | $SED "$delay_single_quote_subst"`' +postdeps_CXX='`$ECHO "$postdeps_CXX" | $SED "$delay_single_quote_subst"`' +compiler_lib_search_path_CXX='`$ECHO "$compiler_lib_search_path_CXX" | $SED "$delay_single_quote_subst"`' LTCC='$LTCC' LTCFLAGS='$LTCFLAGS' compiler='$compiler_DEFAULT' +# A function that is used when there is no print builtin or printf. +func_fallback_echo () +{ + eval 'cat <<_LTECHO_EOF +\$1 +_LTECHO_EOF' +} + # Quote evaled strings. -for var in SED \ +for var in AS \ +DLLTOOL \ +OBJDUMP \ +SHELL \ +ECHO \ +PATH_SEPARATOR \ +SED \ GREP \ EGREP \ FGREP \ @@ -28228,8 +30148,12 @@ lt_NL2SP \ reload_flag \ deplibs_check_method \ file_magic_cmd \ +file_magic_glob \ +want_nocaseglob \ +sharedlib_from_linklib_cmd \ AR \ AR_FLAGS \ +archiver_list_spec \ STRIP \ RANLIB \ CC \ @@ -28239,14 +30163,14 @@ lt_cv_sys_global_symbol_pipe \ lt_cv_sys_global_symbol_to_cdecl \ lt_cv_sys_global_symbol_to_c_name_address \ lt_cv_sys_global_symbol_to_c_name_address_lib_prefix \ -SHELL \ -ECHO \ +nm_file_list_spec \ lt_prog_compiler_no_builtin_flag \ -lt_prog_compiler_wl \ lt_prog_compiler_pic \ +lt_prog_compiler_wl \ lt_prog_compiler_static \ lt_cv_prog_compiler_c_o \ need_locks \ +MANIFEST_TOOL \ DSYMUTIL \ NMEDIT \ LIPO \ @@ -28260,9 +30184,7 @@ with_gnu_ld \ allow_undefined_flag \ no_undefined_flag \ hardcode_libdir_flag_spec \ -hardcode_libdir_flag_spec_ld \ hardcode_libdir_separator \ -fix_srcfile_path \ exclude_expsyms \ include_expsyms \ file_list_spec \ @@ -28270,6 +30192,7 @@ variables_saved_for_relink \ libname_spec \ library_names_spec \ soname_spec \ +install_override_mode \ finish_eval \ old_striplib \ striplib \ @@ -28280,10 +30203,11 @@ predeps \ postdeps \ compiler_lib_search_path \ LD_CXX \ +reload_flag_CXX \ compiler_CXX \ lt_prog_compiler_no_builtin_flag_CXX \ -lt_prog_compiler_wl_CXX \ lt_prog_compiler_pic_CXX \ +lt_prog_compiler_wl_CXX \ lt_prog_compiler_static_CXX \ lt_cv_prog_compiler_c_o_CXX \ export_dynamic_flag_spec_CXX \ @@ -28293,9 +30217,7 @@ with_gnu_ld_CXX \ allow_undefined_flag_CXX \ no_undefined_flag_CXX \ hardcode_libdir_flag_spec_CXX \ -hardcode_libdir_flag_spec_ld_CXX \ hardcode_libdir_separator_CXX \ -fix_srcfile_path_CXX \ exclude_expsyms_CXX \ include_expsyms_CXX \ file_list_spec_CXX \ @@ -28305,9 +30227,9 @@ postdep_objects_CXX \ predeps_CXX \ postdeps_CXX \ compiler_lib_search_path_CXX; do - case \`eval \\\\\$ECHO "X\\\\\$\$var"\` in + case \`eval \\\\\$ECHO \\\\""\\\\\$\$var"\\\\"\` in *[\\\\\\\`\\"\\\$]*) - eval "lt_\$var=\\\\\\"\\\`\\\$ECHO \\"X\\\$\$var\\" | \\\$Xsed -e \\"\\\$sed_quote_subst\\"\\\`\\\\\\"" + eval "lt_\$var=\\\\\\"\\\`\\\$ECHO \\"\\\$\$var\\" | \\\$SED \\"\\\$sed_quote_subst\\"\\\`\\\\\\"" ;; *) eval "lt_\$var=\\\\\\"\\\$\$var\\\\\\"" @@ -28329,11 +30251,13 @@ module_cmds \ module_expsym_cmds \ export_symbols_cmds \ prelink_cmds \ +postlink_cmds \ postinstall_cmds \ postuninstall_cmds \ finish_cmds \ sys_lib_search_path_spec \ sys_lib_dlsearch_path_spec \ +reload_cmds_CXX \ old_archive_cmds_CXX \ old_archive_from_new_cmds_CXX \ old_archive_from_expsyms_cmds_CXX \ @@ -28342,10 +30266,11 @@ archive_expsym_cmds_CXX \ module_cmds_CXX \ module_expsym_cmds_CXX \ export_symbols_cmds_CXX \ -prelink_cmds_CXX; do - case \`eval \\\\\$ECHO "X\\\\\$\$var"\` in +prelink_cmds_CXX \ +postlink_cmds_CXX; do + case \`eval \\\\\$ECHO \\\\""\\\\\$\$var"\\\\"\` in *[\\\\\\\`\\"\\\$]*) - eval "lt_\$var=\\\\\\"\\\`\\\$ECHO \\"X\\\$\$var\\" | \\\$Xsed -e \\"\\\$double_quote_subst\\" -e \\"\\\$sed_quote_subst\\" -e \\"\\\$delay_variable_subst\\"\\\`\\\\\\"" + eval "lt_\$var=\\\\\\"\\\`\\\$ECHO \\"\\\$\$var\\" | \\\$SED -e \\"\\\$double_quote_subst\\" -e \\"\\\$sed_quote_subst\\" -e \\"\\\$delay_variable_subst\\"\\\`\\\\\\"" ;; *) eval "lt_\$var=\\\\\\"\\\$\$var\\\\\\"" @@ -28353,12 +30278,6 @@ prelink_cmds_CXX; do esac done -# Fix-up fallback echo if it was mangled by the above quoting rules. -case \$lt_ECHO in -*'\\\$0 --fallback-echo"') lt_ECHO=\`\$ECHO "X\$lt_ECHO" | \$Xsed -e 's/\\\\\\\\\\\\\\\$0 --fallback-echo"\$/\$0 --fallback-echo"/'\` - ;; -esac - ac_aux_dir='$ac_aux_dir' xsi_shell='$xsi_shell' lt_shell_append='$lt_shell_append' @@ -28411,11 +30330,14 @@ do "src/arm/arm.conf") CONFIG_FILES="$CONFIG_FILES src/arm/arm.conf" ;; "src/ats/Makefile") CONFIG_FILES="$CONFIG_FILES src/ats/Makefile" ;; "src/ats/ats.conf") CONFIG_FILES="$CONFIG_FILES src/ats/ats.conf" ;; + "src/ats-tool/Makefile") CONFIG_FILES="$CONFIG_FILES src/ats-tool/Makefile" ;; "src/block/Makefile") CONFIG_FILES="$CONFIG_FILES src/block/Makefile" ;; "src/chat/Makefile") CONFIG_FILES="$CONFIG_FILES src/chat/Makefile" ;; "src/chat/chat.conf") CONFIG_FILES="$CONFIG_FILES src/chat/chat.conf" ;; "src/core/Makefile") CONFIG_FILES="$CONFIG_FILES src/core/Makefile" ;; "src/core/core.conf") CONFIG_FILES="$CONFIG_FILES src/core/core.conf" ;; + "src/consensus/Makefile") CONFIG_FILES="$CONFIG_FILES src/consensus/Makefile" ;; + "src/consensus/consensus.conf") CONFIG_FILES="$CONFIG_FILES src/consensus/consensus.conf" ;; "src/datacache/Makefile") CONFIG_FILES="$CONFIG_FILES src/datacache/Makefile" ;; "src/datastore/Makefile") CONFIG_FILES="$CONFIG_FILES src/datastore/Makefile" ;; "src/datastore/datastore.conf") CONFIG_FILES="$CONFIG_FILES src/datastore/datastore.conf" ;; @@ -28455,8 +30377,11 @@ do "src/statistics/Makefile") CONFIG_FILES="$CONFIG_FILES src/statistics/Makefile" ;; "src/statistics/statistics.conf") CONFIG_FILES="$CONFIG_FILES src/statistics/statistics.conf" ;; "src/stream/Makefile") CONFIG_FILES="$CONFIG_FILES src/stream/Makefile" ;; + "src/sysmon/Makefile") CONFIG_FILES="$CONFIG_FILES src/sysmon/Makefile" ;; + "src/sysmon/sysmon.conf") CONFIG_FILES="$CONFIG_FILES src/sysmon/sysmon.conf" ;; "src/template/Makefile") CONFIG_FILES="$CONFIG_FILES src/template/Makefile" ;; "src/testbed/Makefile") CONFIG_FILES="$CONFIG_FILES src/testbed/Makefile" ;; + "src/testbed/testbed.conf") CONFIG_FILES="$CONFIG_FILES src/testbed/testbed.conf" ;; "src/testing/Makefile") CONFIG_FILES="$CONFIG_FILES src/testing/Makefile" ;; "src/topology/Makefile") CONFIG_FILES="$CONFIG_FILES src/topology/Makefile" ;; "src/transport/Makefile") CONFIG_FILES="$CONFIG_FILES src/transport/Makefile" ;; @@ -28468,27 +30393,39 @@ do "src/vpn/vpn.conf") CONFIG_FILES="$CONFIG_FILES src/vpn/vpn.conf" ;; "src/integration-tests/Makefile") CONFIG_FILES="$CONFIG_FILES src/integration-tests/Makefile" ;; "pkgconfig/Makefile") CONFIG_FILES="$CONFIG_FILES pkgconfig/Makefile" ;; + "pkgconfig/gnunetats.pc") CONFIG_FILES="$CONFIG_FILES pkgconfig/gnunetats.pc" ;; "pkgconfig/gnunetarm.pc") CONFIG_FILES="$CONFIG_FILES pkgconfig/gnunetarm.pc" ;; "pkgconfig/gnunetblock.pc") CONFIG_FILES="$CONFIG_FILES pkgconfig/gnunetblock.pc" ;; "pkgconfig/gnunetcore.pc") CONFIG_FILES="$CONFIG_FILES pkgconfig/gnunetcore.pc" ;; "pkgconfig/gnunetdatacache.pc") CONFIG_FILES="$CONFIG_FILES pkgconfig/gnunetdatacache.pc" ;; "pkgconfig/gnunetdatastore.pc") CONFIG_FILES="$CONFIG_FILES pkgconfig/gnunetdatastore.pc" ;; "pkgconfig/gnunetdht.pc") CONFIG_FILES="$CONFIG_FILES pkgconfig/gnunetdht.pc" ;; - "pkgconfig/gnunetdhtlog.pc") CONFIG_FILES="$CONFIG_FILES pkgconfig/gnunetdhtlog.pc" ;; + "pkgconfig/gnunetdns.pc") CONFIG_FILES="$CONFIG_FILES pkgconfig/gnunetdns.pc" ;; + "pkgconfig/gnunetdnsparser.pc") CONFIG_FILES="$CONFIG_FILES pkgconfig/gnunetdnsparser.pc" ;; "pkgconfig/gnunetdv.pc") CONFIG_FILES="$CONFIG_FILES pkgconfig/gnunetdv.pc" ;; "pkgconfig/gnunetfragmentation.pc") CONFIG_FILES="$CONFIG_FILES pkgconfig/gnunetfragmentation.pc" ;; "pkgconfig/gnunetfs.pc") CONFIG_FILES="$CONFIG_FILES pkgconfig/gnunetfs.pc" ;; + "pkgconfig/gnunetgns.pc") CONFIG_FILES="$CONFIG_FILES pkgconfig/gnunetgns.pc" ;; "pkgconfig/gnunethello.pc") CONFIG_FILES="$CONFIG_FILES pkgconfig/gnunethello.pc" ;; + "pkgconfig/gnunetlockmanager.pc") CONFIG_FILES="$CONFIG_FILES pkgconfig/gnunetlockmanager.pc" ;; + "pkgconfig/gnunetmesh.pc") CONFIG_FILES="$CONFIG_FILES pkgconfig/gnunetmesh.pc" ;; + "pkgconfig/gnunetmysql.pc") CONFIG_FILES="$CONFIG_FILES pkgconfig/gnunetmysql.pc" ;; + "pkgconfig/gnunetnamestore.pc") CONFIG_FILES="$CONFIG_FILES pkgconfig/gnunetnamestore.pc" ;; "pkgconfig/gnunetnat.pc") CONFIG_FILES="$CONFIG_FILES pkgconfig/gnunetnat.pc" ;; "pkgconfig/gnunetnse.pc") CONFIG_FILES="$CONFIG_FILES pkgconfig/gnunetnse.pc" ;; "pkgconfig/gnunetpeerinfo.pc") CONFIG_FILES="$CONFIG_FILES pkgconfig/gnunetpeerinfo.pc" ;; + "pkgconfig/gnunetpostgres.pc") CONFIG_FILES="$CONFIG_FILES pkgconfig/gnunetpostgres.pc" ;; "pkgconfig/gnunetregex.pc") CONFIG_FILES="$CONFIG_FILES pkgconfig/gnunetregex.pc" ;; "pkgconfig/gnunetstatistics.pc") CONFIG_FILES="$CONFIG_FILES pkgconfig/gnunetstatistics.pc" ;; + "pkgconfig/gnunetstream.pc") CONFIG_FILES="$CONFIG_FILES pkgconfig/gnunetstream.pc" ;; + "pkgconfig/gnunettestbed.pc") CONFIG_FILES="$CONFIG_FILES pkgconfig/gnunettestbed.pc" ;; "pkgconfig/gnunettesting.pc") CONFIG_FILES="$CONFIG_FILES pkgconfig/gnunettesting.pc" ;; "pkgconfig/gnunettransport.pc") CONFIG_FILES="$CONFIG_FILES pkgconfig/gnunettransport.pc" ;; + "pkgconfig/gnunettun.pc") CONFIG_FILES="$CONFIG_FILES pkgconfig/gnunettun.pc" ;; "pkgconfig/gnunetutil.pc") CONFIG_FILES="$CONFIG_FILES pkgconfig/gnunetutil.pc" ;; + "pkgconfig/gnunetvpn.pc") CONFIG_FILES="$CONFIG_FILES pkgconfig/gnunetvpn.pc" ;; - *) as_fn_error $? "invalid argument: \`$ac_config_target'" "$LINENO" 5 ;; + *) as_fn_error $? "invalid argument: \`$ac_config_target'" "$LINENO" 5;; esac done @@ -28511,9 +30448,10 @@ fi # after its creation but before its name has been assigned to `$tmp'. $debug || { - tmp= + tmp= ac_tmp= trap 'exit_status=$? - { test -z "$tmp" || test ! -d "$tmp" || rm -fr "$tmp"; } && exit $exit_status + : "${ac_tmp:=$tmp}" + { test ! -d "$ac_tmp" || rm -fr "$ac_tmp"; } && exit $exit_status ' 0 trap 'as_fn_exit 1' 1 2 13 15 } @@ -28521,12 +30459,13 @@ $debug || { tmp=`(umask 077 && mktemp -d "./confXXXXXX") 2>/dev/null` && - test -n "$tmp" && test -d "$tmp" + test -d "$tmp" } || { tmp=./conf$$-$RANDOM (umask 077 && mkdir "$tmp") } || as_fn_error $? "cannot create a temporary directory in ." "$LINENO" 5 +ac_tmp=$tmp # Set up the scripts for CONFIG_FILES section. # No need to generate them if there are no CONFIG_FILES. @@ -28548,7 +30487,7 @@ else ac_cs_awk_cr=$ac_cr fi -echo 'BEGIN {' >"$tmp/subs1.awk" && +echo 'BEGIN {' >"$ac_tmp/subs1.awk" && _ACEOF @@ -28576,7 +30515,7 @@ done rm -f conf$$subs.sh cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1 -cat >>"\$tmp/subs1.awk" <<\\_ACAWK && +cat >>"\$ac_tmp/subs1.awk" <<\\_ACAWK && _ACEOF sed -n ' h @@ -28624,7 +30563,7 @@ t delim rm -f conf$$subs.awk cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1 _ACAWK -cat >>"\$tmp/subs1.awk" <<_ACAWK && +cat >>"\$ac_tmp/subs1.awk" <<_ACAWK && for (key in S) S_is_set[key] = 1 FS = "" @@ -28656,7 +30595,7 @@ if sed "s/$ac_cr//" < /dev/null > /dev/null 2>&1; then sed "s/$ac_cr\$//; s/$ac_cr/$ac_cs_awk_cr/g" else cat -fi < "$tmp/subs1.awk" > "$tmp/subs.awk" \ +fi < "$ac_tmp/subs1.awk" > "$ac_tmp/subs.awk" \ || as_fn_error $? "could not setup config files machinery" "$LINENO" 5 _ACEOF @@ -28690,7 +30629,7 @@ fi # test -n "$CONFIG_FILES" # No need to generate them if there are no CONFIG_HEADERS. # This happens for instance with `./config.status Makefile'. if test -n "$CONFIG_HEADERS"; then -cat >"$tmp/defines.awk" <<\_ACAWK || +cat >"$ac_tmp/defines.awk" <<\_ACAWK || BEGIN { _ACEOF @@ -28702,8 +30641,8 @@ _ACEOF # handling of long lines. ac_delim='%!_!# ' for ac_last_try in false false :; do - ac_t=`sed -n "/$ac_delim/p" confdefs.h` - if test -z "$ac_t"; then + ac_tt=`sed -n "/$ac_delim/p" confdefs.h` + if test -z "$ac_tt"; then break elif $ac_last_try; then as_fn_error $? "could not make $CONFIG_HEADERS" "$LINENO" 5 @@ -28804,7 +30743,7 @@ do esac case $ac_mode$ac_tag in :[FHL]*:*);; - :L* | :C*:*) as_fn_error $? "invalid tag \`$ac_tag'" "$LINENO" 5 ;; + :L* | :C*:*) as_fn_error $? "invalid tag \`$ac_tag'" "$LINENO" 5;; :[FH]-) ac_tag=-:-;; :[FH]*) ac_tag=$ac_tag:$ac_tag.in;; esac @@ -28823,7 +30762,7 @@ do for ac_f do case $ac_f in - -) ac_f="$tmp/stdin";; + -) ac_f="$ac_tmp/stdin";; *) # Look for the file first in the build tree, then in the source tree # (if the path is not absolute). The absolute path cannot be DOS-style, # because $ac_f cannot contain `:'. @@ -28832,7 +30771,7 @@ do [\\/$]*) false;; *) test -f "$srcdir/$ac_f" && ac_f="$srcdir/$ac_f";; esac || - as_fn_error 1 "cannot find input file: \`$ac_f'" "$LINENO" 5 ;; + as_fn_error 1 "cannot find input file: \`$ac_f'" "$LINENO" 5;; esac case $ac_f in *\'*) ac_f=`$as_echo "$ac_f" | sed "s/'/'\\\\\\\\''/g"`;; esac as_fn_append ac_file_inputs " '$ac_f'" @@ -28858,8 +30797,8 @@ $as_echo "$as_me: creating $ac_file" >&6;} esac case $ac_tag in - *:-:* | *:-) cat >"$tmp/stdin" \ - || as_fn_error $? "could not create $ac_file" "$LINENO" 5 ;; + *:-:* | *:-) cat >"$ac_tmp/stdin" \ + || as_fn_error $? "could not create $ac_file" "$LINENO" 5 ;; esac ;; esac @@ -28995,21 +30934,22 @@ s&@INSTALL@&$ac_INSTALL&;t t s&@MKDIR_P@&$ac_MKDIR_P&;t t $ac_datarootdir_hack " -eval sed \"\$ac_sed_extra\" "$ac_file_inputs" | $AWK -f "$tmp/subs.awk" >$tmp/out \ - || as_fn_error $? "could not create $ac_file" "$LINENO" 5 +eval sed \"\$ac_sed_extra\" "$ac_file_inputs" | $AWK -f "$ac_tmp/subs.awk" \ + >$ac_tmp/out || as_fn_error $? "could not create $ac_file" "$LINENO" 5 test -z "$ac_datarootdir_hack$ac_datarootdir_seen" && - { ac_out=`sed -n '/\${datarootdir}/p' "$tmp/out"`; test -n "$ac_out"; } && - { ac_out=`sed -n '/^[ ]*datarootdir[ ]*:*=/p' "$tmp/out"`; test -z "$ac_out"; } && + { ac_out=`sed -n '/\${datarootdir}/p' "$ac_tmp/out"`; test -n "$ac_out"; } && + { ac_out=`sed -n '/^[ ]*datarootdir[ ]*:*=/p' \ + "$ac_tmp/out"`; test -z "$ac_out"; } && { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: $ac_file contains a reference to the variable \`datarootdir' which seems to be undefined. Please make sure it is defined" >&5 $as_echo "$as_me: WARNING: $ac_file contains a reference to the variable \`datarootdir' which seems to be undefined. Please make sure it is defined" >&2;} - rm -f "$tmp/stdin" + rm -f "$ac_tmp/stdin" case $ac_file in - -) cat "$tmp/out" && rm -f "$tmp/out";; - *) rm -f "$ac_file" && mv "$tmp/out" "$ac_file";; + -) cat "$ac_tmp/out" && rm -f "$ac_tmp/out";; + *) rm -f "$ac_file" && mv "$ac_tmp/out" "$ac_file";; esac \ || as_fn_error $? "could not create $ac_file" "$LINENO" 5 ;; @@ -29020,20 +30960,20 @@ which seems to be undefined. Please make sure it is defined" >&2;} if test x"$ac_file" != x-; then { $as_echo "/* $configure_input */" \ - && eval '$AWK -f "$tmp/defines.awk"' "$ac_file_inputs" - } >"$tmp/config.h" \ + && eval '$AWK -f "$ac_tmp/defines.awk"' "$ac_file_inputs" + } >"$ac_tmp/config.h" \ || as_fn_error $? "could not create $ac_file" "$LINENO" 5 - if diff "$ac_file" "$tmp/config.h" >/dev/null 2>&1; then + if diff "$ac_file" "$ac_tmp/config.h" >/dev/null 2>&1; then { $as_echo "$as_me:${as_lineno-$LINENO}: $ac_file is unchanged" >&5 $as_echo "$as_me: $ac_file is unchanged" >&6;} else rm -f "$ac_file" - mv "$tmp/config.h" "$ac_file" \ + mv "$ac_tmp/config.h" "$ac_file" \ || as_fn_error $? "could not create $ac_file" "$LINENO" 5 fi else $as_echo "/* $configure_input */" \ - && eval '$AWK -f "$tmp/defines.awk"' "$ac_file_inputs" \ + && eval '$AWK -f "$ac_tmp/defines.awk"' "$ac_file_inputs" \ || as_fn_error $? "could not create -" "$LINENO" 5 fi # Compute "$ac_file"'s index in $config_headers. @@ -29195,7 +31135,8 @@ $as_echo X"$file" | # NOTE: Changes made to this file will be lost: look at ltmain.sh. # # Copyright (C) 1996, 1997, 1998, 1999, 2000, 2001, 2003, 2004, 2005, -# 2006, 2007, 2008 Free Software Foundation, Inc. +# 2006, 2007, 2008, 2009, 2010, 2011 Free Software +# Foundation, Inc. # Written by Gordon Matzigkeit, 1996 # # This file is part of GNU Libtool. @@ -29235,13 +31176,13 @@ macro_revision=$macro_revision build_old_libs=$enable_static # Assembler program. -AS=$AS +AS=$lt_AS # DLL creation program. -DLLTOOL=$DLLTOOL +DLLTOOL=$lt_DLLTOOL # Object dumper program. -OBJDUMP=$OBJDUMP +OBJDUMP=$lt_OBJDUMP # Whether or not to build shared libraries. build_libtool_libs=$enable_shared @@ -29252,6 +31193,15 @@ pic_mode=$pic_mode # Whether or not to optimize for fast installation. fast_install=$enable_fast_install +# Shell to use when invoking shell scripts. +SHELL=$lt_SHELL + +# An echo program that protects backslashes. +ECHO=$lt_ECHO + +# The PATH separator for the build system. +PATH_SEPARATOR=$lt_PATH_SEPARATOR + # The host system. host_alias=$host_alias host=$host @@ -29301,20 +31251,36 @@ SP2NL=$lt_lt_SP2NL # turn newlines into spaces. NL2SP=$lt_lt_NL2SP -# How to create reloadable object files. -reload_flag=$lt_reload_flag -reload_cmds=$lt_reload_cmds +# convert \$build file names to \$host format. +to_host_file_cmd=$lt_cv_to_host_file_cmd + +# convert \$build files to toolchain format. +to_tool_file_cmd=$lt_cv_to_tool_file_cmd # Method to check whether dependent libraries are shared objects. deplibs_check_method=$lt_deplibs_check_method -# Command to use when deplibs_check_method == "file_magic". +# Command to use when deplibs_check_method = "file_magic". file_magic_cmd=$lt_file_magic_cmd +# How to find potential files when deplibs_check_method = "file_magic". +file_magic_glob=$lt_file_magic_glob + +# Find potential files using nocaseglob when deplibs_check_method = "file_magic". +want_nocaseglob=$lt_want_nocaseglob + +# Command to associate shared and link libraries. +sharedlib_from_linklib_cmd=$lt_sharedlib_from_linklib_cmd + # The archiver. AR=$lt_AR + +# Flags to create an archive. AR_FLAGS=$lt_AR_FLAGS +# How to feed a file listing to the archiver. +archiver_list_spec=$lt_archiver_list_spec + # A symbol stripping program. STRIP=$lt_STRIP @@ -29323,6 +31289,9 @@ RANLIB=$lt_RANLIB old_postinstall_cmds=$lt_old_postinstall_cmds old_postuninstall_cmds=$lt_old_postuninstall_cmds +# Whether to use a lock for old archive extraction. +lock_old_archive_extraction=$lock_old_archive_extraction + # A C compiler. LTCC=$lt_CC @@ -29341,14 +31310,14 @@ global_symbol_to_c_name_address=$lt_lt_cv_sys_global_symbol_to_c_name_address # Transform the output of nm in a C name address pair when lib prefix is needed. global_symbol_to_c_name_address_lib_prefix=$lt_lt_cv_sys_global_symbol_to_c_name_address_lib_prefix -# The name of the directory that contains temporary libtool files. -objdir=$objdir +# Specify filename containing input files for \$NM. +nm_file_list_spec=$lt_nm_file_list_spec -# Shell to use when invoking shell scripts. -SHELL=$lt_SHELL +# The root where to search for dependent libraries,and in which our libraries should be installed. +lt_sysroot=$lt_sysroot -# An echo program that does not interpret backslashes. -ECHO=$lt_ECHO +# The name of the directory that contains temporary libtool files. +objdir=$objdir # Used to examine libraries when file_magic_cmd begins with "file". MAGIC_CMD=$MAGIC_CMD @@ -29356,6 +31325,9 @@ MAGIC_CMD=$MAGIC_CMD # Must we lock files when doing compilation? need_locks=$lt_need_locks +# Manifest tool. +MANIFEST_TOOL=$lt_MANIFEST_TOOL + # Tool to manipulate archived DWARF debug symbol files on Mac OS X. DSYMUTIL=$lt_DSYMUTIL @@ -29412,6 +31384,9 @@ library_names_spec=$lt_library_names_spec # The coded name of the library, if different from the real name. soname_spec=$lt_soname_spec +# Permission mode override for installation of shared libraries. +install_override_mode=$lt_install_override_mode + # Command to use after installation of a shared archive. postinstall_cmds=$lt_postinstall_cmds @@ -29451,6 +31426,10 @@ striplib=$lt_striplib # The linker used to build libraries. LD=$lt_LD +# How to create reloadable object files. +reload_flag=$lt_reload_flag +reload_cmds=$lt_reload_cmds + # Commands used to build an old-style archive. old_archive_cmds=$lt_old_archive_cmds @@ -29463,12 +31442,12 @@ with_gcc=$GCC # Compiler flag to turn off builtin functions. no_builtin_flag=$lt_lt_prog_compiler_no_builtin_flag -# How to pass a linker flag through the compiler. -wl=$lt_lt_prog_compiler_wl - # Additional compiler flags for building library objects. pic_flag=$lt_lt_prog_compiler_pic +# How to pass a linker flag through the compiler. +wl=$lt_lt_prog_compiler_wl + # Compiler flag to prevent dynamic linking. link_static_flag=$lt_lt_prog_compiler_static @@ -29518,10 +31497,6 @@ no_undefined_flag=$lt_no_undefined_flag # This must work even if \$libdir does not exist hardcode_libdir_flag_spec=$lt_hardcode_libdir_flag_spec -# If ld is used when linking, flag to hardcode \$libdir into a binary -# during linking. This must work even if \$libdir does not exist. -hardcode_libdir_flag_spec_ld=$lt_hardcode_libdir_flag_spec_ld - # Whether we need a single "-rpath" flag with a separated argument. hardcode_libdir_separator=$lt_hardcode_libdir_separator @@ -29555,9 +31530,6 @@ inherit_rpath=$inherit_rpath # Whether libtool must link a program against all its dependency libraries. link_all_deplibs=$link_all_deplibs -# Fix the shell variable \$srcfile for the compiler. -fix_srcfile_path=$lt_fix_srcfile_path - # Set to "yes" if exported symbols are required. always_export_symbols=$always_export_symbols @@ -29573,6 +31545,9 @@ include_expsyms=$lt_include_expsyms # Commands necessary for linking programs (against libraries) with templates. prelink_cmds=$lt_prelink_cmds +# Commands necessary for finishing linking programs. +postlink_cmds=$lt_postlink_cmds + # Specify filename containing input files. file_list_spec=$lt_file_list_spec @@ -29619,212 +31594,169 @@ ltmain="$ac_aux_dir/ltmain.sh" # if finds mixed CR/LF and LF-only lines. Since sed operates in # text mode, it properly converts lines to CR/LF. This bash problem # is reportedly fixed, but why not run on old versions too? - sed '/^# Generated shell functions inserted here/q' "$ltmain" >> "$cfgfile" \ - || (rm -f "$cfgfile"; exit 1) - - case $xsi_shell in - yes) - cat << \_LT_EOF >> "$cfgfile" - -# func_dirname file append nondir_replacement -# Compute the dirname of FILE. If nonempty, add APPEND to the result, -# otherwise set result to NONDIR_REPLACEMENT. -func_dirname () -{ - case ${1} in - */*) func_dirname_result="${1%/*}${2}" ;; - * ) func_dirname_result="${3}" ;; - esac -} - -# func_basename file -func_basename () -{ - func_basename_result="${1##*/}" -} - -# func_dirname_and_basename file append nondir_replacement -# perform func_basename and func_dirname in a single function -# call: -# dirname: Compute the dirname of FILE. If nonempty, -# add APPEND to the result, otherwise set result -# to NONDIR_REPLACEMENT. -# value returned in "$func_dirname_result" -# basename: Compute filename of FILE. -# value retuned in "$func_basename_result" -# Implementation must be kept synchronized with func_dirname -# and func_basename. For efficiency, we do not delegate to -# those functions but instead duplicate the functionality here. -func_dirname_and_basename () -{ - case ${1} in - */*) func_dirname_result="${1%/*}${2}" ;; - * ) func_dirname_result="${3}" ;; - esac - func_basename_result="${1##*/}" -} - -# func_stripname prefix suffix name -# strip PREFIX and SUFFIX off of NAME. -# PREFIX and SUFFIX must not contain globbing or regex special -# characters, hashes, percent signs, but SUFFIX may contain a leading -# dot (in which case that matches only a dot). -func_stripname () -{ - # pdksh 5.2.14 does not do ${X%$Y} correctly if both X and Y are - # positional parameters, so assign one to ordinary parameter first. - func_stripname_result=${3} - func_stripname_result=${func_stripname_result#"${1}"} - func_stripname_result=${func_stripname_result%"${2}"} -} - -# func_opt_split -func_opt_split () -{ - func_opt_split_opt=${1%%=*} - func_opt_split_arg=${1#*=} -} - -# func_lo2o object -func_lo2o () -{ - case ${1} in - *.lo) func_lo2o_result=${1%.lo}.${objext} ;; - *) func_lo2o_result=${1} ;; - esac -} - -# func_xform libobj-or-source -func_xform () -{ - func_xform_result=${1%.*}.lo -} - -# func_arith arithmetic-term... -func_arith () -{ - func_arith_result=$(( $* )) -} - -# func_len string -# STRING may not start with a hyphen. -func_len () -{ - func_len_result=${#1} -} - -_LT_EOF - ;; - *) # Bourne compatible functions. - cat << \_LT_EOF >> "$cfgfile" - -# func_dirname file append nondir_replacement -# Compute the dirname of FILE. If nonempty, add APPEND to the result, -# otherwise set result to NONDIR_REPLACEMENT. -func_dirname () -{ - # Extract subdirectory from the argument. - func_dirname_result=`$ECHO "X${1}" | $Xsed -e "$dirname"` - if test "X$func_dirname_result" = "X${1}"; then - func_dirname_result="${3}" - else - func_dirname_result="$func_dirname_result${2}" - fi -} - -# func_basename file -func_basename () -{ - func_basename_result=`$ECHO "X${1}" | $Xsed -e "$basename"` -} - - -# func_stripname prefix suffix name -# strip PREFIX and SUFFIX off of NAME. -# PREFIX and SUFFIX must not contain globbing or regex special -# characters, hashes, percent signs, but SUFFIX may contain a leading -# dot (in which case that matches only a dot). -# func_strip_suffix prefix name -func_stripname () -{ - case ${2} in - .*) func_stripname_result=`$ECHO "X${3}" \ - | $Xsed -e "s%^${1}%%" -e "s%\\\\${2}\$%%"`;; - *) func_stripname_result=`$ECHO "X${3}" \ - | $Xsed -e "s%^${1}%%" -e "s%${2}\$%%"`;; - esac -} - -# sed scripts: -my_sed_long_opt='1s/^\(-[^=]*\)=.*/\1/;q' -my_sed_long_arg='1s/^-[^=]*=//' - -# func_opt_split -func_opt_split () -{ - func_opt_split_opt=`$ECHO "X${1}" | $Xsed -e "$my_sed_long_opt"` - func_opt_split_arg=`$ECHO "X${1}" | $Xsed -e "$my_sed_long_arg"` -} - -# func_lo2o object -func_lo2o () -{ - func_lo2o_result=`$ECHO "X${1}" | $Xsed -e "$lo2o"` -} - -# func_xform libobj-or-source -func_xform () -{ - func_xform_result=`$ECHO "X${1}" | $Xsed -e 's/\.[^.]*$/.lo/'` -} - -# func_arith arithmetic-term... -func_arith () -{ - func_arith_result=`expr "$@"` -} - -# func_len string -# STRING may not start with a hyphen. -func_len () -{ - func_len_result=`expr "$1" : ".*" 2>/dev/null || echo $max_cmd_len` -} - -_LT_EOF -esac - -case $lt_shell_append in - yes) - cat << \_LT_EOF >> "$cfgfile" - -# func_append var value -# Append VALUE to the end of shell variable VAR. -func_append () -{ - eval "$1+=\$2" -} -_LT_EOF - ;; - *) - cat << \_LT_EOF >> "$cfgfile" - -# func_append var value -# Append VALUE to the end of shell variable VAR. -func_append () -{ - eval "$1=\$$1\$2" -} - -_LT_EOF - ;; - esac - - - sed -n '/^# Generated shell functions inserted here/,$p' "$ltmain" >> "$cfgfile" \ - || (rm -f "$cfgfile"; exit 1) - - mv -f "$cfgfile" "$ofile" || + sed '$q' "$ltmain" >> "$cfgfile" \ + || (rm -f "$cfgfile"; exit 1) + + if test x"$xsi_shell" = xyes; then + sed -e '/^func_dirname ()$/,/^} # func_dirname /c\ +func_dirname ()\ +{\ +\ case ${1} in\ +\ */*) func_dirname_result="${1%/*}${2}" ;;\ +\ * ) func_dirname_result="${3}" ;;\ +\ esac\ +} # Extended-shell func_dirname implementation' "$cfgfile" > $cfgfile.tmp \ + && mv -f "$cfgfile.tmp" "$cfgfile" \ + || (rm -f "$cfgfile" && cp "$cfgfile.tmp" "$cfgfile" && rm -f "$cfgfile.tmp") +test 0 -eq $? || _lt_function_replace_fail=: + + + sed -e '/^func_basename ()$/,/^} # func_basename /c\ +func_basename ()\ +{\ +\ func_basename_result="${1##*/}"\ +} # Extended-shell func_basename implementation' "$cfgfile" > $cfgfile.tmp \ + && mv -f "$cfgfile.tmp" "$cfgfile" \ + || (rm -f "$cfgfile" && cp "$cfgfile.tmp" "$cfgfile" && rm -f "$cfgfile.tmp") +test 0 -eq $? || _lt_function_replace_fail=: + + + sed -e '/^func_dirname_and_basename ()$/,/^} # func_dirname_and_basename /c\ +func_dirname_and_basename ()\ +{\ +\ case ${1} in\ +\ */*) func_dirname_result="${1%/*}${2}" ;;\ +\ * ) func_dirname_result="${3}" ;;\ +\ esac\ +\ func_basename_result="${1##*/}"\ +} # Extended-shell func_dirname_and_basename implementation' "$cfgfile" > $cfgfile.tmp \ + && mv -f "$cfgfile.tmp" "$cfgfile" \ + || (rm -f "$cfgfile" && cp "$cfgfile.tmp" "$cfgfile" && rm -f "$cfgfile.tmp") +test 0 -eq $? || _lt_function_replace_fail=: + + + sed -e '/^func_stripname ()$/,/^} # func_stripname /c\ +func_stripname ()\ +{\ +\ # pdksh 5.2.14 does not do ${X%$Y} correctly if both X and Y are\ +\ # positional parameters, so assign one to ordinary parameter first.\ +\ func_stripname_result=${3}\ +\ func_stripname_result=${func_stripname_result#"${1}"}\ +\ func_stripname_result=${func_stripname_result%"${2}"}\ +} # Extended-shell func_stripname implementation' "$cfgfile" > $cfgfile.tmp \ + && mv -f "$cfgfile.tmp" "$cfgfile" \ + || (rm -f "$cfgfile" && cp "$cfgfile.tmp" "$cfgfile" && rm -f "$cfgfile.tmp") +test 0 -eq $? || _lt_function_replace_fail=: + + + sed -e '/^func_split_long_opt ()$/,/^} # func_split_long_opt /c\ +func_split_long_opt ()\ +{\ +\ func_split_long_opt_name=${1%%=*}\ +\ func_split_long_opt_arg=${1#*=}\ +} # Extended-shell func_split_long_opt implementation' "$cfgfile" > $cfgfile.tmp \ + && mv -f "$cfgfile.tmp" "$cfgfile" \ + || (rm -f "$cfgfile" && cp "$cfgfile.tmp" "$cfgfile" && rm -f "$cfgfile.tmp") +test 0 -eq $? || _lt_function_replace_fail=: + + + sed -e '/^func_split_short_opt ()$/,/^} # func_split_short_opt /c\ +func_split_short_opt ()\ +{\ +\ func_split_short_opt_arg=${1#??}\ +\ func_split_short_opt_name=${1%"$func_split_short_opt_arg"}\ +} # Extended-shell func_split_short_opt implementation' "$cfgfile" > $cfgfile.tmp \ + && mv -f "$cfgfile.tmp" "$cfgfile" \ + || (rm -f "$cfgfile" && cp "$cfgfile.tmp" "$cfgfile" && rm -f "$cfgfile.tmp") +test 0 -eq $? || _lt_function_replace_fail=: + + + sed -e '/^func_lo2o ()$/,/^} # func_lo2o /c\ +func_lo2o ()\ +{\ +\ case ${1} in\ +\ *.lo) func_lo2o_result=${1%.lo}.${objext} ;;\ +\ *) func_lo2o_result=${1} ;;\ +\ esac\ +} # Extended-shell func_lo2o implementation' "$cfgfile" > $cfgfile.tmp \ + && mv -f "$cfgfile.tmp" "$cfgfile" \ + || (rm -f "$cfgfile" && cp "$cfgfile.tmp" "$cfgfile" && rm -f "$cfgfile.tmp") +test 0 -eq $? || _lt_function_replace_fail=: + + + sed -e '/^func_xform ()$/,/^} # func_xform /c\ +func_xform ()\ +{\ + func_xform_result=${1%.*}.lo\ +} # Extended-shell func_xform implementation' "$cfgfile" > $cfgfile.tmp \ + && mv -f "$cfgfile.tmp" "$cfgfile" \ + || (rm -f "$cfgfile" && cp "$cfgfile.tmp" "$cfgfile" && rm -f "$cfgfile.tmp") +test 0 -eq $? || _lt_function_replace_fail=: + + + sed -e '/^func_arith ()$/,/^} # func_arith /c\ +func_arith ()\ +{\ + func_arith_result=$(( $* ))\ +} # Extended-shell func_arith implementation' "$cfgfile" > $cfgfile.tmp \ + && mv -f "$cfgfile.tmp" "$cfgfile" \ + || (rm -f "$cfgfile" && cp "$cfgfile.tmp" "$cfgfile" && rm -f "$cfgfile.tmp") +test 0 -eq $? || _lt_function_replace_fail=: + + + sed -e '/^func_len ()$/,/^} # func_len /c\ +func_len ()\ +{\ + func_len_result=${#1}\ +} # Extended-shell func_len implementation' "$cfgfile" > $cfgfile.tmp \ + && mv -f "$cfgfile.tmp" "$cfgfile" \ + || (rm -f "$cfgfile" && cp "$cfgfile.tmp" "$cfgfile" && rm -f "$cfgfile.tmp") +test 0 -eq $? || _lt_function_replace_fail=: + +fi + +if test x"$lt_shell_append" = xyes; then + sed -e '/^func_append ()$/,/^} # func_append /c\ +func_append ()\ +{\ + eval "${1}+=\\${2}"\ +} # Extended-shell func_append implementation' "$cfgfile" > $cfgfile.tmp \ + && mv -f "$cfgfile.tmp" "$cfgfile" \ + || (rm -f "$cfgfile" && cp "$cfgfile.tmp" "$cfgfile" && rm -f "$cfgfile.tmp") +test 0 -eq $? || _lt_function_replace_fail=: + + + sed -e '/^func_append_quoted ()$/,/^} # func_append_quoted /c\ +func_append_quoted ()\ +{\ +\ func_quote_for_eval "${2}"\ +\ eval "${1}+=\\\\ \\$func_quote_for_eval_result"\ +} # Extended-shell func_append_quoted implementation' "$cfgfile" > $cfgfile.tmp \ + && mv -f "$cfgfile.tmp" "$cfgfile" \ + || (rm -f "$cfgfile" && cp "$cfgfile.tmp" "$cfgfile" && rm -f "$cfgfile.tmp") +test 0 -eq $? || _lt_function_replace_fail=: + + + # Save a `func_append' function call where possible by direct use of '+=' + sed -e 's%func_append \([a-zA-Z_]\{1,\}\) "%\1+="%g' $cfgfile > $cfgfile.tmp \ + && mv -f "$cfgfile.tmp" "$cfgfile" \ + || (rm -f "$cfgfile" && cp "$cfgfile.tmp" "$cfgfile" && rm -f "$cfgfile.tmp") + test 0 -eq $? || _lt_function_replace_fail=: +else + # Save a `func_append' function call even when '+=' is not available + sed -e 's%func_append \([a-zA-Z_]\{1,\}\) "%\1="$\1%g' $cfgfile > $cfgfile.tmp \ + && mv -f "$cfgfile.tmp" "$cfgfile" \ + || (rm -f "$cfgfile" && cp "$cfgfile.tmp" "$cfgfile" && rm -f "$cfgfile.tmp") + test 0 -eq $? || _lt_function_replace_fail=: +fi + +if test x"$_lt_function_replace_fail" = x":"; then + { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: Unable to substitute extended shell functions in $ofile" >&5 +$as_echo "$as_me: WARNING: Unable to substitute extended shell functions in $ofile" >&2;} +fi + + + mv -f "$cfgfile" "$ofile" || (rm -f "$ofile" && cp "$cfgfile" "$ofile" && rm -f "$cfgfile") chmod +x "$ofile" @@ -29836,6 +31768,10 @@ _LT_EOF # The linker used to build libraries. LD=$lt_LD_CXX +# How to create reloadable object files. +reload_flag=$lt_reload_flag_CXX +reload_cmds=$lt_reload_cmds_CXX + # Commands used to build an old-style archive. old_archive_cmds=$lt_old_archive_cmds_CXX @@ -29848,12 +31784,12 @@ with_gcc=$GCC_CXX # Compiler flag to turn off builtin functions. no_builtin_flag=$lt_lt_prog_compiler_no_builtin_flag_CXX -# How to pass a linker flag through the compiler. -wl=$lt_lt_prog_compiler_wl_CXX - # Additional compiler flags for building library objects. pic_flag=$lt_lt_prog_compiler_pic_CXX +# How to pass a linker flag through the compiler. +wl=$lt_lt_prog_compiler_wl_CXX + # Compiler flag to prevent dynamic linking. link_static_flag=$lt_lt_prog_compiler_static_CXX @@ -29903,10 +31839,6 @@ no_undefined_flag=$lt_no_undefined_flag_CXX # This must work even if \$libdir does not exist hardcode_libdir_flag_spec=$lt_hardcode_libdir_flag_spec_CXX -# If ld is used when linking, flag to hardcode \$libdir into a binary -# during linking. This must work even if \$libdir does not exist. -hardcode_libdir_flag_spec_ld=$lt_hardcode_libdir_flag_spec_ld_CXX - # Whether we need a single "-rpath" flag with a separated argument. hardcode_libdir_separator=$lt_hardcode_libdir_separator_CXX @@ -29940,9 +31872,6 @@ inherit_rpath=$inherit_rpath_CXX # Whether libtool must link a program against all its dependency libraries. link_all_deplibs=$link_all_deplibs_CXX -# Fix the shell variable \$srcfile for the compiler. -fix_srcfile_path=$lt_fix_srcfile_path_CXX - # Set to "yes" if exported symbols are required. always_export_symbols=$always_export_symbols_CXX @@ -29958,6 +31887,9 @@ include_expsyms=$lt_include_expsyms_CXX # Commands necessary for linking programs (against libraries) with templates. prelink_cmds=$lt_prelink_cmds_CXX +# Commands necessary for finishing linking programs. +postlink_cmds=$lt_postlink_cmds_CXX + # Specify filename containing input files. file_list_spec=$lt_file_list_spec_CXX @@ -30295,6 +32227,20 @@ then $as_echo "$as_me: NOTICE: sqlite not found. sqLite support will not be compiled." >&6;} fi +# libcurl +if test "x$curl" = "x0" +then + { $as_echo "$as_me:${as_lineno-$LINENO}: NOTICE: libcurl not found. http client support will not be compiled." >&5 +$as_echo "$as_me: NOTICE: libcurl not found. http client support will not be compiled." >&6;} +fi + +#gnutls +if test x$gnutls != xtrue +then + { $as_echo "$as_me:${as_lineno-$LINENO}: NOTICE: gnutls not found, gnunet-gns-proxy will not be built" >&5 +$as_echo "$as_me: NOTICE: gnutls not found, gnunet-gns-proxy will not be built" >&6;} +fi + # java ports if test "x$enable_java_ports" = "xyes" then @@ -30323,57 +32269,76 @@ then $as_echo "$as_me: NOTICE: --with-sudo not specified and not running as 'root', will not install GNS NSS library" >&6;} fi + { $as_echo "$as_me:${as_lineno-$LINENO}: ******************************************** -You can compile GNUnet with - make -now. After that, run (if necessary as 'root') - make install -to install everything. You may want to create a new user account -to run the GNUnet service: - adduser gnunet -You also need to create an configuration file that should -specify the path where GNUnet should store data. For example, -you could store in \"/etc/gnunet.conf\" the following lines: - -[PATHS] -SERVICEHOME = /var/lib/gnunet -DEFAULTCONFIG = /etc/gnunet.conf - -Now, in order to start your peer, run as the 'gnunet' user - gnunet-arm -s +Please make sure NOW that you have created a user and group 'gnunet' +and additionally a group 'gnunetdns': + addgroup gnunetdns + adduser gnunet -Each GNUnet user should also create an (at least initially) empty -configuration file: - mkdir $HOME/.gnunet/ - touch $HOME/.gnunet/gnunet.conf +Make sure that '/var/lib/gnunet' is owned (and writable) by user +'gnunet'. Then, you can compile GNUnet with + make -Optionally, download and compile: -- gnunet-gtk to get a GUI for file-sharing and configuration. -********************************************" >&5 -$as_echo "$as_me: ******************************************** -You can compile GNUnet with - make -now. After that, run (if necessary as 'root') +After that, run (if necessary as 'root') make install -to install everything. You may want to create a new user account -to run the GNUnet service: - adduser gnunet -You also need to create an configuration file that should -specify the path where GNUnet should store data. For example, -you could store in \"/etc/gnunet.conf\" the following lines: - -[PATHS] -SERVICEHOME = /var/lib/gnunet -DEFAULTCONFIG = /etc/gnunet.conf - -Now, in order to start your peer, run as the 'gnunet' user +to install everything. + +Each GNUnet user should be added to the 'gnunet' group (may +require fresh login to come into effect): + adduser $USERNAME gnunet +(run the above command as root once for each of your users, replacing +\"$USERNAME\" with the respective login names). If you have a global IP +address, no further configuration is required. + +Optionally, download and compile gnunet-gtk to get a GUI for +file-sharing and configuration. This is particularly recommended +if your network setup is non-trivial, as gnunet-setup can be +used to test in the GUI if your network configuration is working. +gnunet-setup should be run as the \"gnunet\" user under X. As it +does very little with the network, running it as \"root\" is likely +also harmless. You can also run it as a normal user, but then +you have to copy ~/.gnunet/gnunet.conf\" over to the \"gnunet\" user's +home directory in the end. + +Once you have configured your peer, run (as the 'gnunet' user) gnunet-arm -s +to start the peer. You can then run the various GNUnet-tools as +your \"normal\" user (who should only be in the group 'gnunet'). +********************************************" >&5 +$as_echo "$as_me: ******************************************** +Please make sure NOW that you have created a user and group 'gnunet' +and additionally a group 'gnunetdns': + addgroup gnunetdns + adduser gnunet -Each GNUnet user should also create an (at least initially) empty -configuration file: - mkdir $HOME/.gnunet/ - touch $HOME/.gnunet/gnunet.conf +Make sure that '/var/lib/gnunet' is owned (and writable) by user +'gnunet'. Then, you can compile GNUnet with + make -Optionally, download and compile: -- gnunet-gtk to get a GUI for file-sharing and configuration. +After that, run (if necessary as 'root') + make install +to install everything. + +Each GNUnet user should be added to the 'gnunet' group (may +require fresh login to come into effect): + adduser $USERNAME gnunet +(run the above command as root once for each of your users, replacing +\"$USERNAME\" with the respective login names). If you have a global IP +address, no further configuration is required. + +Optionally, download and compile gnunet-gtk to get a GUI for +file-sharing and configuration. This is particularly recommended +if your network setup is non-trivial, as gnunet-setup can be +used to test in the GUI if your network configuration is working. +gnunet-setup should be run as the \"gnunet\" user under X. As it +does very little with the network, running it as \"root\" is likely +also harmless. You can also run it as a normal user, but then +you have to copy ~/.gnunet/gnunet.conf\" over to the \"gnunet\" user's +home directory in the end. + +Once you have configured your peer, run (as the 'gnunet' user) + gnunet-arm -s +to start the peer. You can then run the various GNUnet-tools as +your \"normal\" user (who should only be in the group 'gnunet'). ********************************************" >&6;} diff --git a/configure.ac b/configure.ac index 2a8d612..42884d0 100644 --- a/configure.ac +++ b/configure.ac @@ -1,5 +1,5 @@ # This file is part of GNUnet. -# (C) 2001--2012 Christian Grothoff (and other contributing authors) +# (C) 2001--2013 Christian Grothoff (and other contributing authors) # # GNUnet is free software; you can redistribute it and/or modify # it under the terms of the GNU General Public License as published @@ -22,13 +22,13 @@ # AC_PREREQ(2.61) # Checks for programs. -AC_INIT([gnunet], [0.9.3],[bug-gnunet@gnu.org]) +AC_INIT([gnunet], [0.9.5a],[bug-gnunet@gnu.org]) AC_CANONICAL_TARGET AC_CANONICAL_HOST AC_CANONICAL_SYSTEM -AM_INIT_AUTOMAKE([gnunet], [0.9.3]) +AM_INIT_AUTOMAKE([gnunet], [0.9.5a]) m4_ifdef([AM_SILENT_RULES], [AM_SILENT_RULES([yes])]) AC_CONFIG_HEADERS([gnunet_config.h]) AH_TOP([#define _GNU_SOURCE 1]) @@ -68,7 +68,10 @@ fi # Use Linux interface name unless the OS has a different preference DEFAULT_INTERFACE="\"eth0\"" -funcstocheck="socket select inet_ntoa getnameinfo gethostname gethostbyname gethostbyaddr getaddrinfo" +funcstocheck="getnameinfo gethostname gethostbyname gethostbyaddr getaddrinfo" + +# Srcdir in a form that native compiler understands (i.e. DOS path on W32) +native_srcdir=$srcdir # Check system type case "$host_os" in @@ -84,14 +87,14 @@ case "$host_os" in UNIXONLY="#" ;; linux*) - AC_DEFINE_UNQUOTED(LINUX,1,[This is a Linux system]) + AC_DEFINE_UNQUOTED(LINUX,1,[This is a Linux kernel]) build_target="linux" LIBPREFIX= DLLDIR=lib UNIXONLY="#" AC_PATH_XTRA ;; -freebsd*) +*freebsd*) AC_DEFINE_UNQUOTED(SOMEBSD,1,[This is a BSD system]) AC_DEFINE_UNQUOTED(FREEBSD,1,[This is a FreeBSD system]) CFLAGS="-D_THREAD_SAFE $CFLAGS" @@ -100,7 +103,7 @@ freebsd*) DLLDIR=lib UNIXONLY="#" ;; -openbsd*) +*openbsd*) AC_DEFINE_UNQUOTED(SOMEBSD,1,[This is a BSD system]) AC_DEFINE_UNQUOTED(OPENBSD,1,[This is an OpenBSD system]) LIBS=`echo $LIBS | sed -e "s/-ldl//"` @@ -109,7 +112,7 @@ openbsd*) DLLDIR=lib UNIXONLY="#" ;; -netbsd*) +*netbsd*) AC_DEFINE_UNQUOTED(SOMEBSD,1,[This is a BSD system]) AC_DEFINE_UNQUOTED(NETBSD,1,[This is a NetBSD system]) LIBPREFIX= @@ -127,7 +130,7 @@ netbsd*) UNIXONLY="#" ;; *arm-linux*) - AC_DEFINE_UNQUOTED(LINUX,1,[This is a Linux system]) + AC_DEFINE_UNQUOTED(LINUX,1,[This is a Linux kernel]) CFLAGS="-D_REENTRANT -fPIC -pipe $CFLAGS" build_target="linux" LIBPREFIX= @@ -161,6 +164,12 @@ netbsd*) DLLDIR=bin UNIXONLY="" funcstocheck="" + native_srcdir=$(cd $srcdir; pwd -W) + ;; +gnu*) + AC_DEFINE_UNQUOTED(GNU,1,[This is a GNU system]) + build_target="gnu" + UNIXONLY="#" ;; *) AC_MSG_RESULT(Unrecognised OS $host_os) @@ -184,6 +193,7 @@ AM_CONDITIONAL(SOLARIS, test "$build_target" = "solaris") AM_CONDITIONAL(XFREEBSD, test "$build_target" = "freebsd") AM_CONDITIONAL(OPENBSD, test "$build_target" = "openbsd") AM_CONDITIONAL(LINUX, test "$build_target" = "linux") +AM_CONDITIONAL(GNU, test "$build_target" = "gnu") AC_MSG_RESULT([$build_target]) AC_SUBST(build_target) @@ -211,13 +221,25 @@ fi # libgcrypt gcrypt=0 -AM_PATH_LIBGCRYPT(1.2.0, gcrypt=1) +NEED_LIBGCRYPT_API=1 +NEED_LIBGCRYPT_VERSION=1.4.2 + + +AM_PATH_LIBGCRYPT("$NEED_LIBGCRYPT_API:$NEED_LIBGCRYPT_VERSION", gcrypt=1) AC_CHECK_DECLS([gcry_mpi_lshift], [], [], [[#include ]]) if test $gcrypt = 0 then - AC_MSG_ERROR([GNUnet needs libgcrypt]) + AC_MSG_ERROR([[ +*** +*** You need libgcrypt to build this program. +** This library is for example available at +*** ftp://ftp.gnupg.org/gcrypt/libgcrypt/ +*** (at least version $NEED_LIBGCRYPT_VERSION (API $NEED_LIBGCRYPT_API) +*** is required.) +***]]) fi +AC_DEFINE_UNQUOTED([NEED_LIBGCRYPT_VERSION], "$NEED_LIBGCRYPT_VERSION", [required libgcrypt version]) # Adam shostack suggests the following for Windows: # -D_FORTIFY_SOURCE=2 -fstack-protector-all @@ -250,6 +272,26 @@ AC_ARG_ENABLE([logging], ], []) AC_DEFINE_UNQUOTED([GNUNET_EXTRA_LOGGING],[$extra_logging],[1 if extra logging is enabled, 2 for very verbose extra logging, 0 otherwise]) +# should memory poisoning be enabled? +AC_MSG_CHECKING(whether to poison freed memory) +AC_ARG_ENABLE([poisoning], + [AS_HELP_STRING([--enable-poisoning], [enable poisoning of freed memory (good for debugging)])], + [enable_poisoning=${enableval}], + [ + if test "x$extra_logging" != "xGNUNET_NO"; then + enable_poisoning="defaults to yes (extra logging is enabled)" + else + enable_poisoning=no + fi + ]) +AC_MSG_RESULT($enable_poisoning) +if test ! "x$enable_poisoning" = "xno"; then + enable_poisoning=1 +else + enable_poisoning=0 +fi +AC_DEFINE_UNQUOTED([ENABLE_POISONING],[$enable_poisoning],[1 if freed memory should be poisoned, 0 otherwise]) + if test $build = $target then AC_MSG_CHECKING([for working HMAC]) @@ -320,7 +362,40 @@ AC_LANG_POP(C) fi # $build = $target # libcurl -LIBCURL_CHECK_CONFIG(,7.20.1,,AC_MSG_ERROR([GNUnet requires libcurl >= 7.20.1])) +LIBCURL_CHECK_CONFIG(,7.21.3,curl=1,curl=0) +if test "$curl" = 1 +then + AM_CONDITIONAL(HAVE_LIBCURL, true) + AC_DEFINE([HAVE_LIBCURL],[1],[Have libcurl]) +else + AM_CONDITIONAL(HAVE_LIBCURL, false) +fi + + +# libidn +AC_MSG_CHECKING([if Libidn can be used]) +AC_ARG_WITH(libidn, AC_HELP_STRING([--with-libidn=[DIR]], + [Support IDN (needs GNU Libidn)]), +libidn=$withval, libidn=yes) +if test "$libidn" != "no"; then + if test "$libidn" != "yes"; then + LDFLAGS="${LDFLAGS} -L$libidn/lib" + CPPFLAGS="${CPPFLAGS} -I$libidn/include" + fi + AC_CHECK_HEADER(idna.h, + AC_CHECK_LIB(idn, stringprep_check_version, + [libidn=yes LIBS="${LIBS} -lidn"], libidn=no), + libidn=no) +fi +if test "$libidn" != "no" ; then + AC_DEFINE(LIBIDN, 1, [Define to 1 if you want IDN support.]) + else + AC_MSG_FAILURE([Libidn not found]) +fi +AC_MSG_RESULT($libidn) + + + # restore LIBS LIBS=$SAVE_LIBS @@ -338,6 +413,34 @@ else AC_DEFINE([HAVE_LIBGLPK],[1],[Have GLPK]) fi +# test for glib +# Minimum required version for glibtop is 2.6.0 +AM_PATH_GLIB_2_0(2.6.0, [glib2=true] , [glib2=false] ,) +if test x$glib2 = xfalse +then + AM_CONDITIONAL(HAVE_GLIB2, false) + AC_MSG_WARN([GNUnet requires GLIB >= 2.6.0]) +else + AM_CONDITIONAL(HAVE_GLIB2, true) + AC_DEFINE([HAVE_GLIB2],[1],[Have glib2]) + LIBS="$LIBS $GLIB_LIBS" + CFLAGS="$CFLAGS $GLIB_CFLAGS" +fi + +#libgtop +PKG_CHECK_MODULES(LIBGTOP,libgtop-2.0, [gtop=true] , [gtop=false] ) +if test x$gtop = xfalse +then + AM_CONDITIONAL(HAVE_LIBGTOP, false) + AC_MSG_WARN([GNUnet requires libgtop]) +else + AM_CONDITIONAL(HAVE_LIBGTOP, true) + AC_DEFINE([HAVE_LIBGTOP],[1],[Have libgtop]) + LIBS="$LIBS $LIBGTOP_LIBS" + CFLAGS="$CFLAGS $LIBGTOP_CFLAGS" +fi + + AC_CHECK_HEADERS([nss.h],[nss=true],[nss=false]) @@ -411,7 +514,7 @@ AC_HEADER_STDC AC_CHECK_HEADERS([fcntl.h math.h errno.h ctype.h limits.h stdio.h stdlib.h string.h unistd.h stdarg.h signal.h locale.h sys/stat.h sys/types.h],,AC_MSG_ERROR([Compiling GNUnet requires standard UNIX headers files])) # Checks for headers that are only required on some systems or opional (and where we do NOT abort if they are not there) -AC_CHECK_HEADERS([langinfo.h sys/param.h sys/mount.h sys/statvfs.h sys/select.h sockLib.h sys/mman.h sys/msg.h sys/vfs.h arpa/inet.h fcntl.h libintl.h netdb.h netinet/in.h netinet/in_systm.h sys/ioctl.h sys/socket.h sys/time.h unistd.h kstat.h sys/sysinfo.h kvm.h sys/file.h sys/resource.h ifaddrs.h mach/mach.h stddef.h sys/timeb.h terminos.h argz.h ucred.h endian.h sys/endian.h]) +AC_CHECK_HEADERS([malloc.h malloc/malloc.h langinfo.h sys/param.h sys/mount.h sys/statvfs.h sys/select.h sockLib.h sys/mman.h sys/msg.h sys/vfs.h arpa/inet.h fcntl.h libintl.h netdb.h netinet/in.h netinet/in_systm.h sys/ioctl.h sys/socket.h sys/time.h unistd.h kstat.h sys/sysinfo.h kvm.h sys/file.h sys/resource.h ifaddrs.h mach/mach.h stddef.h sys/timeb.h terminos.h argz.h ucred.h endian.h sys/endian.h execinfo.h]) SAVE_LDFLAGS=$LDFLAGS SAVE_CPPFLAGS=$CPPFLAGS @@ -523,10 +626,17 @@ AC_ARG_WITH(mysql, fi ], [AC_MSG_RESULT([--with-mysql not specified]) - LDFLAGS="-L/usr/lib/mysql $LDFLAGS $ZLIBS" + if test -d "/usr/lib64/mysql"; then + MYSQL_LIBDIR="/usr/lib64/mysql" + elif test -d "/usr/lib/mysql"; then + MYSQL_LIBDIR="/usr/lib/mysql" + else + MYSQL_LIBDIR="/usr/lib" + fi + LDFLAGS="-L$MYSQL_LIBDIR $LDFLAGS $ZLIBS" AC_CHECK_LIB(mysqlclient, mysql_init, [AC_CHECK_HEADERS(mysql/mysql.h, - MYSQL_LDFLAGS="-L/usr/lib/mysql" + MYSQL_LDFLAGS="-L$MYSQL_LIBDIR" mysql=true , [], [$CYGWIN_MYSQL_MAGIC])]) @@ -584,15 +694,15 @@ AC_ARG_WITH(microhttpd, AC_CHECK_LIB([microhttpd], [MHD_start_daemon], [AC_MSG_CHECKING([for libmicrohttpd >= 0.9.18]) AC_RUN_IFELSE([ - #include "$srcdir/src/include/platform.h" + #include "$native_srcdir/src/include/platform.h" #include int main () { return MHD_VERSION >= 0x0091200 ? 0 : 1; } ], [ AC_MSG_RESULT(ok) lmhd=1],[AC_MSG_RESULT(failed)],lmhd=1)]), - [],[#include "$srcdir/src/include/platform.h" + [],[#include "$native_srcdir/src/include/platform.h" #include ]),, - [#include "$srcdir/src/include/platform.h"]) + [#include "$native_srcdir/src/include/platform.h"]) ;; *) LDFLAGS="-L$with_microhttpd/lib $LDFLAGS" @@ -603,15 +713,15 @@ AC_ARG_WITH(microhttpd, EXT_LIB_PATH="-L$with_microhttpd/lib $EXT_LIB_PATH" [AC_MSG_CHECKING([for libmicrohttpd >= 0.9.18]) AC_RUN_IFELSE([ - #include "$srcdir/src/include/platform.h" + #include "$native_srcdir/src/include/platform.h" #include int main () { return MHD_VERSION >= 0x0091200 ? 0 : 1; } ], [ AC_MSG_RESULT(ok) lmhd=1],[AC_MSG_RESULT(failed)],lmhd=1)]), - [],[#include "$srcdir/src/include/platform.h" + [],[#include "$native_srcdir/src/include/platform.h" #include ]),, - [#include "$srcdir/src/include/platform.h"]) + [#include "$native_srcdir/src/include/platform.h"]) ;; esac ], @@ -621,15 +731,15 @@ AC_ARG_WITH(microhttpd, AC_CHECK_LIB([microhttpd], [MHD_start_daemon], [AC_MSG_CHECKING([for libmicrohttpd >= 0.9.18]) AC_RUN_IFELSE([ - #include "$srcdir/src/include/platform.h" + #include "$native_srcdir/src/include/platform.h" #include int main () { return MHD_VERSION >= 0x0091200 ? 0 : 1; } ], [ AC_MSG_RESULT(ok) lmhd=1],[AC_MSG_RESULT(failed)],lmhd=1)]), - [],[#include "$srcdir/src/include/platform.h" + [],[#include "$native_srcdir/src/include/platform.h" #include ]),, - [#include "$srcdir/src/include/platform.h"])]) + [#include "$native_srcdir/src/include/platform.h"])]) AM_CONDITIONAL(HAVE_MHD, test x$lmhd = x1) AC_DEFINE_UNQUOTED([HAVE_MHD], $lmhd, [We have libmicrohttpd]) @@ -641,23 +751,6 @@ LIBS=$SAVE_LIBS AM_PATH_PYTHON([2.6],, [:]) AM_CONDITIONAL([HAVE_PYTHON], [test "$PYTHON" != :]) -if test "$PYTHON" != : -then - AC_MSG_CHECKING([for pexpect]) - $PYTHON -c "import pexpect" > /dev/null 2> /dev/null - PYEX=$? - AM_CONDITIONAL(HAVE_PYTHON_PEXPECT, test $PYEX -eq 0) - if test $PYEX -eq 0 - then - AC_MSG_RESULT([yes]) - else - AC_MSG_RESULT([not found]) - fi -else - AM_CONDITIONAL(HAVE_PYTHON_PEXPECT, 0) -fi - - # check for gettext AM_GNU_GETTEXT([external]) AM_GNU_GETTEXT_VERSION([0.16.1]) @@ -701,7 +794,7 @@ AC_FUNC_VPRINTF AC_HEADER_SYS_WAIT AC_TYPE_OFF_T AC_TYPE_UID_T -AC_CHECK_FUNCS([floor memmove rmdir strncasecmp strrchr strtol atoll dup2 fdatasync ftruncate gettimeofday memset mkdir mkfifo strcasecmp strchr strdup strerror strstr clock_gettime getrusage rand uname setlocale getcwd mktime gmtime_r gmtime strlcpy strlcat ftruncate stat64 sbrk mmap mremap setrlimit sysconf initgroups getifaddrs freeifaddrs localtime_r nl_langinfo putenv realpath strndup gethostbyname2 gethostbyname getpeerucred getpeereid setresuid $funcstocheck]) +AC_CHECK_FUNCS([atoll stat64 strnlen mremap getrlimit setrlimit sysconf initgroups strndup gethostbyname2 getpeerucred getpeereid setresuid $funcstocheck getifaddrs freeifaddrs getresgid mallinfo malloc_size malloc_usable_size getrusage]) # restore LIBS LIBS=$SAVE_LIBS @@ -780,6 +873,42 @@ AC_ARG_WITH(sudo, AC_SUBST(SUDO_BINARY) AM_CONDITIONAL([HAVE_SUDO], [test "x$SUDO_BINARY" != "x" -o -w /]) + +# test for nssdir +AC_MSG_CHECKING(with nssdir) +AC_ARG_WITH(nssdir, + [ --with-nssdir=PATH where to install NSS plugins], + [AC_MSG_RESULT("$with_nssdir") + case $with_nssdir in + no) + NSS_DIR= + install_nss=0 + ;; + yes) + NSS_DIR="/lib" + install_nss=1 + ;; + *) + NSS_DIR=$with_nssdir + install_nss=1 + ;; + esac + ], + [ + if test "x$SUDO_BINARY" != "x" -o -w / + then + NSS_DIR="/lib" + install_nss=1 + AC_MSG_RESULT([yes, to /lib]) + else + NSS_DIR= + install_nss=0 + AC_MSG_RESULT([no]) + fi + ]) +AC_SUBST(NSS_DIR) +AM_CONDITIONAL([INSTALL_NSS], [test "x$install_nss" != "x0"]) + # test for gnunetdns group name GNUNETDNS_GROUP=gnunetdns AC_MSG_CHECKING(for gnunetdns group name) @@ -802,6 +931,71 @@ AC_ARG_WITH(gnunetdns, AC_SUBST(GNUNETDNS_GROUP) + +# gnutls +gnutls=0 +AC_MSG_CHECKING(for gnutls) +AC_ARG_WITH(gnutls, + [ --with-gnutls=PFX base of gnutls installation], + [AC_MSG_RESULT([$with_gnutls]) + case $with_gnutls in + no) + ;; + yes) + AC_CHECK_HEADERS([gnutls/abstract.h], + AC_CHECK_LIB([gnutls], [gnutls_priority_set], + gnutls=true)) + ;; + *) + LDFLAGS="-L$with_gnutls/lib $LDFLAGS" + CPPFLAGS="-I$with_gnutls/include $CPPFLAGS" + AC_CHECK_HEADERS([gnutls/abstract.h], + AC_CHECK_LIB([gnutls], [gnutls_priority_set], + EXT_LIB_PATH="-L$with_gnutls/lib $EXT_LIB_PATH" + gnutls=true)) + ;; + esac + ], + [AC_MSG_RESULT([--with-gnutls not specified]) + AC_CHECK_HEADERS([gnutls/abstract.h], + AC_CHECK_LIB([gnutls], [gnutls_priority_set], + gnutls=true))]) +AM_CONDITIONAL(HAVE_GNUTLS, test x$gnutls = xtrue) +AC_DEFINE_UNQUOTED([HAVE_GNUTLS], $gnutls, [We have gnutls]) + + +# Test if we are building for superMUC +llapi=0 +AC_MSG_CHECKING(if testbed should use IBM LoadLeveler to run on SuperMUC) +AC_ARG_WITH([ll], + [AS_HELP_STRING([--with-ll=PFX], + [use IBM LoadLeveler (installed at PFX) for running testbed on SuperMUC]. Default is no)], + [AC_MSG_RESULT([$with_ll]) + case $with_ll in + no) + ;; + yes) + AC_CHECK_HEADERS([llapi.h], + AC_CHECK_LIB([llapi], [llsubmit], + llapi=true, + AC_MSG_ERROR(libllapi not found but --with-llapi given)), + AC_MSG_ERROR(llapi.h not found but --with-llapi given)) + ;; + *) + LDFLAGS="-L$with_ll/lib $LDFLAGS" + CPPFLAGS="-I$with_ll/include $CPPFLAGS" + AC_CHECK_HEADERS([llapi.h], + AC_CHECK_LIB([llapi], [llsubmit], + llapi=true, + AC_MSG_ERROR(libllapi not found but --with-llapi given)), + AC_MSG_ERROR(llapi.h not found but --with-llapi given)) + ;; + esac + ], + [AC_MSG_RESULT(--with-ll not specified)]) +AM_CONDITIONAL([WITH_LL], [test "x$llapi" = "xtrue"]) +AC_DEFINE_UNQUOTED(WITH_LL, $llapi, [Do we have to use IBM LoadLeveler]) + # should 'make check' run tests? AC_MSG_CHECKING(whether to run tests) AC_ARG_ENABLE([testruns], @@ -871,6 +1065,15 @@ AC_ARG_ENABLE([experimental], AC_MSG_RESULT($enable_experimental) AM_CONDITIONAL([HAVE_EXPERIMENTAL], [test "x$enable_experimental" = "xyes"]) +# should memory statistics be kept (very expensive CPU-wise!) +AC_MSG_CHECKING(whether to create expensive statistics on memory use) +AC_ARG_ENABLE([heapstats], + [AS_HELP_STRING([--enable-heapstats], [enable expensive heap statistics])], + [enable_heapstats=1], + [enable_heapstats=0]) +AC_MSG_RESULT($enable_heapstats) +AC_DEFINE_UNQUOTED([ENABLE_HEAP_STATISTICS],$enable_heapstats,[enable expensive heap statistics]) + # should code be enabled that works around missing OS functionality on Windows? # used for test cases if test $build_target = "mingw" @@ -993,6 +1196,27 @@ AC_MSG_RESULT($use_gcov) AM_CONDITIONAL([USE_COVERAGE], [test "x$use_gcov" = "xyes"]) +# version info +AC_PATH_PROG(svnversioncommand, svnversion) +AC_PATH_PROG(gitcommand, git) +if test "X$svnversioncommand" = "X" || test `$svnversioncommand -n '.'` = "exported" +then + if test "X$gitcommand" = "X" + then + AC_DEFINE_UNQUOTED(VCS_VERSION, ["release"], [repository svn version]) + else + gitver=$(git log -1 | grep "git-svn-id" | sed -e 's/.*@\([[0-9]]\+\) .*/\1/') + if "X$gitver" = "X" + then + AC_DEFINE_UNQUOTED(VCS_VERSION, ["release"], [repository svn version]) + else + AC_DEFINE_UNQUOTED(VCS_VERSION, ["svn-$gitver"], [repository svn version]) + fi + fi +else + AC_DEFINE_UNQUOTED(VCS_VERSION, ["svn-`svnversion -n`"], [repository svn version]) +fi + AC_CONFIG_FILES([ Makefile contrib/Makefile @@ -1005,11 +1229,14 @@ src/arm/Makefile src/arm/arm.conf src/ats/Makefile src/ats/ats.conf +src/ats-tool/Makefile src/block/Makefile src/chat/Makefile src/chat/chat.conf src/core/Makefile src/core/core.conf +src/consensus/Makefile +src/consensus/consensus.conf src/datacache/Makefile src/datastore/Makefile src/datastore/datastore.conf @@ -1049,8 +1276,11 @@ src/regex/Makefile src/statistics/Makefile src/statistics/statistics.conf src/stream/Makefile +src/sysmon/Makefile +src/sysmon/sysmon.conf src/template/Makefile src/testbed/Makefile +src/testbed/testbed.conf src/testing/Makefile src/topology/Makefile src/transport/Makefile @@ -1062,25 +1292,37 @@ src/vpn/Makefile src/vpn/vpn.conf src/integration-tests/Makefile pkgconfig/Makefile +pkgconfig/gnunetats.pc pkgconfig/gnunetarm.pc pkgconfig/gnunetblock.pc pkgconfig/gnunetcore.pc pkgconfig/gnunetdatacache.pc pkgconfig/gnunetdatastore.pc pkgconfig/gnunetdht.pc -pkgconfig/gnunetdhtlog.pc +pkgconfig/gnunetdns.pc +pkgconfig/gnunetdnsparser.pc pkgconfig/gnunetdv.pc pkgconfig/gnunetfragmentation.pc pkgconfig/gnunetfs.pc +pkgconfig/gnunetgns.pc pkgconfig/gnunethello.pc +pkgconfig/gnunetlockmanager.pc +pkgconfig/gnunetmesh.pc +pkgconfig/gnunetmysql.pc +pkgconfig/gnunetnamestore.pc pkgconfig/gnunetnat.pc pkgconfig/gnunetnse.pc pkgconfig/gnunetpeerinfo.pc +pkgconfig/gnunetpostgres.pc pkgconfig/gnunetregex.pc pkgconfig/gnunetstatistics.pc +pkgconfig/gnunetstream.pc +pkgconfig/gnunettestbed.pc pkgconfig/gnunettesting.pc pkgconfig/gnunettransport.pc +pkgconfig/gnunettun.pc pkgconfig/gnunetutil.pc +pkgconfig/gnunetvpn.pc ]) AC_OUTPUT @@ -1098,6 +1340,18 @@ then AC_MSG_NOTICE([NOTICE: sqlite not found. sqLite support will not be compiled.]) fi +# libcurl +if test "x$curl" = "x0" +then + AC_MSG_NOTICE([NOTICE: libcurl not found. http client support will not be compiled.]) +fi + +#gnutls +if test x$gnutls != xtrue +then + AC_MSG_NOTICE([NOTICE: gnutls not found, gnunet-gns-proxy will not be built]) +fi + # java ports if test "x$enable_java_ports" = "xyes" then @@ -1121,30 +1375,40 @@ then AC_MSG_NOTICE([NOTICE: --with-sudo not specified and not running as 'root', will not install GNS NSS library]) fi + AC_MSG_NOTICE([******************************************** -You can compile GNUnet with - make -now. After that, run (if necessary as 'root') - make install -to install everything. You may want to create a new user account -to run the GNUnet service: - adduser gnunet -You also need to create an configuration file that should -specify the path where GNUnet should store data. For example, -you could store in "/etc/gnunet.conf" the following lines: - -[[PATHS]] -SERVICEHOME = /var/lib/gnunet -DEFAULTCONFIG = /etc/gnunet.conf - -Now, in order to start your peer, run as the 'gnunet' user - gnunet-arm -s +Please make sure NOW that you have created a user and group 'gnunet' +and additionally a group 'gnunetdns': + addgroup gnunetdns + adduser gnunet + +Make sure that '/var/lib/gnunet' is owned (and writable) by user +'gnunet'. Then, you can compile GNUnet with + make -Each GNUnet user should also create an (at least initially) empty -configuration file: - mkdir $HOME/.gnunet/ - touch $HOME/.gnunet/gnunet.conf +After that, run (if necessary as 'root') + make install +to install everything. + +Each GNUnet user should be added to the 'gnunet' group (may +require fresh login to come into effect): + adduser $USERNAME gnunet +(run the above command as root once for each of your users, replacing +"$USERNAME" with the respective login names). If you have a global IP +address, no further configuration is required. -Optionally, download and compile: -- gnunet-gtk to get a GUI for file-sharing and configuration. +Optionally, download and compile gnunet-gtk to get a GUI for +file-sharing and configuration. This is particularly recommended +if your network setup is non-trivial, as gnunet-setup can be +used to test in the GUI if your network configuration is working. +gnunet-setup should be run as the "gnunet" user under X. As it +does very little with the network, running it as "root" is likely +also harmless. You can also run it as a normal user, but then +you have to copy ~/.gnunet/gnunet.conf" over to the "gnunet" user's +home directory in the end. + +Once you have configured your peer, run (as the 'gnunet' user) + gnunet-arm -s +to start the peer. You can then run the various GNUnet-tools as +your "normal" user (who should only be in the group 'gnunet'). ********************************************]) diff --git a/contrib/Makefile.am b/contrib/Makefile.am index 0d65393..e287696 100644 --- a/contrib/Makefile.am +++ b/contrib/Makefile.am @@ -13,6 +13,8 @@ timeout_watchdog_SOURCES = \ endif noinst_SCRIPTS = \ + terminate.py \ + pydiffer.py \ gnunet_pyexpect.py \ gnunet_janitor.py @@ -21,15 +23,16 @@ bin_SCRIPTS = \ dist_pkgdata_DATA = \ gnunet-logo-color.png \ - testing_hostkeys.dat + testing_hostkeys.dat \ + testing_hostkeys.ecc EXTRA_DIST = \ coverage.sh \ - hostlist.cgi \ - hostlist.php \ report.sh \ + terminate.py.in \ gnunet_pyexpect.py.in \ gnunet_janitor.py.in \ + pydiffer.py.in \ gnunet-gns-import.sh do_subst = $(SED) -e 's,[@]PYTHON[@],$(PYTHON),g' @@ -56,6 +59,7 @@ test_gnunet_prefix_SOURCES = \ test_gnunet_prefix_LDADD = \ $(GCLIBADD) $(WINLIB) \ $(LTLIBICONV) \ + $(GN_LIBINTL) \ -lltdl -lunistring $(XLIB) pkghellodir= $(pkgdatadir)/hellos diff --git a/contrib/Makefile.in b/contrib/Makefile.in index 80134e5..3869ee8 100644 --- a/contrib/Makefile.in +++ b/contrib/Makefile.in @@ -1,9 +1,9 @@ -# Makefile.in generated by automake 1.11.1 from Makefile.am. +# Makefile.in generated by automake 1.11.6 from Makefile.am. # @configure_input@ # Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, -# 2003, 2004, 2005, 2006, 2007, 2008, 2009 Free Software Foundation, -# Inc. +# 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Free Software +# Foundation, Inc. # This Makefile.in is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. @@ -18,6 +18,23 @@ VPATH = @srcdir@ +am__make_dryrun = \ + { \ + am__dry=no; \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + echo 'am--echo: ; @echo "AM" OK' | $(MAKE) -f - 2>/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } pkgdatadir = $(datadir)/@PACKAGE@ pkgincludedir = $(includedir)/@PACKAGE@ pkglibdir = $(libdir)/@PACKAGE@ @@ -45,14 +62,15 @@ DIST_COMMON = $(dist_pkgdata_DATA) $(srcdir)/Makefile.am \ ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 am__aclocal_m4_deps = $(top_srcdir)/m4/absolute-header.m4 \ $(top_srcdir)/m4/align.m4 $(top_srcdir)/m4/argz.m4 \ - $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/iconv.m4 \ - $(top_srcdir)/m4/lib-ld.m4 $(top_srcdir)/m4/lib-link.m4 \ - $(top_srcdir)/m4/lib-prefix.m4 $(top_srcdir)/m4/libcurl.m4 \ - $(top_srcdir)/m4/libgcrypt.m4 $(top_srcdir)/m4/libtool.m4 \ - $(top_srcdir)/m4/libunistring.m4 $(top_srcdir)/m4/ltdl.m4 \ - $(top_srcdir)/m4/ltoptions.m4 $(top_srcdir)/m4/ltsugar.m4 \ - $(top_srcdir)/m4/ltversion.m4 $(top_srcdir)/m4/lt~obsolete.m4 \ - $(top_srcdir)/m4/nls.m4 $(top_srcdir)/m4/po.m4 \ + $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/glib-2.0.m4 \ + $(top_srcdir)/m4/iconv.m4 $(top_srcdir)/m4/lib-ld.m4 \ + $(top_srcdir)/m4/lib-link.m4 $(top_srcdir)/m4/lib-prefix.m4 \ + $(top_srcdir)/m4/libcurl.m4 $(top_srcdir)/m4/libgcrypt.m4 \ + $(top_srcdir)/m4/libtool.m4 $(top_srcdir)/m4/libunistring.m4 \ + $(top_srcdir)/m4/ltdl.m4 $(top_srcdir)/m4/ltoptions.m4 \ + $(top_srcdir)/m4/ltsugar.m4 $(top_srcdir)/m4/ltversion.m4 \ + $(top_srcdir)/m4/lt~obsolete.m4 $(top_srcdir)/m4/nls.m4 \ + $(top_srcdir)/m4/pkg.m4 $(top_srcdir)/m4/po.m4 \ $(top_srcdir)/m4/progtest.m4 $(top_srcdir)/acinclude.m4 \ $(top_srcdir)/configure.ac am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ @@ -65,9 +83,10 @@ PROGRAMS = $(noinst_PROGRAMS) am_test_gnunet_prefix_OBJECTS = test_gnunet_prefix.$(OBJEXT) test_gnunet_prefix_OBJECTS = $(am_test_gnunet_prefix_OBJECTS) am__DEPENDENCIES_1 = -test_gnunet_prefix_DEPENDENCIES = $(am__DEPENDENCIES_1) -AM_V_lt = $(am__v_lt_$(V)) -am__v_lt_ = $(am__v_lt_$(AM_DEFAULT_VERBOSITY)) +test_gnunet_prefix_DEPENDENCIES = $(am__DEPENDENCIES_1) \ + $(am__DEPENDENCIES_1) +AM_V_lt = $(am__v_lt_@AM_V@) +am__v_lt_ = $(am__v_lt_@AM_DEFAULT_V@) am__v_lt_0 = --silent am__timeout_watchdog_SOURCES_DIST = timeout_watchdog.c \ timeout_watchdog_w32.c @@ -97,6 +116,12 @@ am__nobase_list = $(am__nobase_strip_setup); \ am__base_list = \ sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \ sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g' +am__uninstall_files_from_dir = { \ + test -z "$$files" \ + || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \ + || { echo " ( cd '$$dir' && rm -f" $$files ")"; \ + $(am__cd) "$$dir" && rm -f $$files; }; \ + } am__installdirs = "$(DESTDIR)$(bindir)" "$(DESTDIR)$(pkgdatadir)" SCRIPTS = $(bin_SCRIPTS) $(noinst_SCRIPTS) DEFAULT_INCLUDES = -I.@am__isrc@ -I$(top_builddir) @@ -109,25 +134,30 @@ LTCOMPILE = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) \ $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) \ $(AM_CFLAGS) $(CFLAGS) -AM_V_CC = $(am__v_CC_$(V)) -am__v_CC_ = $(am__v_CC_$(AM_DEFAULT_VERBOSITY)) +AM_V_CC = $(am__v_CC_@AM_V@) +am__v_CC_ = $(am__v_CC_@AM_DEFAULT_V@) am__v_CC_0 = @echo " CC " $@; -AM_V_at = $(am__v_at_$(V)) -am__v_at_ = $(am__v_at_$(AM_DEFAULT_VERBOSITY)) +AM_V_at = $(am__v_at_@AM_V@) +am__v_at_ = $(am__v_at_@AM_DEFAULT_V@) am__v_at_0 = @ CCLD = $(CC) LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ $(AM_LDFLAGS) $(LDFLAGS) -o $@ -AM_V_CCLD = $(am__v_CCLD_$(V)) -am__v_CCLD_ = $(am__v_CCLD_$(AM_DEFAULT_VERBOSITY)) +AM_V_CCLD = $(am__v_CCLD_@AM_V@) +am__v_CCLD_ = $(am__v_CCLD_@AM_DEFAULT_V@) am__v_CCLD_0 = @echo " CCLD " $@; -AM_V_GEN = $(am__v_GEN_$(V)) -am__v_GEN_ = $(am__v_GEN_$(AM_DEFAULT_VERBOSITY)) +AM_V_GEN = $(am__v_GEN_@AM_V@) +am__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@) am__v_GEN_0 = @echo " GEN " $@; SOURCES = $(test_gnunet_prefix_SOURCES) $(timeout_watchdog_SOURCES) DIST_SOURCES = $(test_gnunet_prefix_SOURCES) \ $(am__timeout_watchdog_SOURCES_DIST) +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac DATA = $(dist_pkgdata_DATA) ETAGS = etags CTAGS = ctags @@ -167,6 +197,10 @@ EXEEXT = @EXEEXT@ EXT_LIBS = @EXT_LIBS@ EXT_LIB_PATH = @EXT_LIB_PATH@ FGREP = @FGREP@ +GLIB_CFLAGS = @GLIB_CFLAGS@ +GLIB_GENMARSHAL = @GLIB_GENMARSHAL@ +GLIB_LIBS = @GLIB_LIBS@ +GLIB_MKENUMS = @GLIB_MKENUMS@ GMSGFMT = @GMSGFMT@ GMSGFMT_015 = @GMSGFMT_015@ GNUNETDNS_GROUP = @GNUNETDNS_GROUP@ @@ -177,6 +211,7 @@ GN_LIBINTL = @GN_LIBINTL@ GN_LIB_LDFLAGS = @GN_LIB_LDFLAGS@ GN_PLUGIN_LDFLAGS = @GN_PLUGIN_LDFLAGS@ GN_USER_HOME_DIR = @GN_USER_HOME_DIR@ +GOBJECT_QUERY = @GOBJECT_QUERY@ GREP = @GREP@ HAVE_LIBUNISTRING = @HAVE_LIBUNISTRING@ INCLTDL = @INCLTDL@ @@ -199,6 +234,8 @@ LIBCURL_CPPFLAGS = @LIBCURL_CPPFLAGS@ LIBGCRYPT_CFLAGS = @LIBGCRYPT_CFLAGS@ LIBGCRYPT_CONFIG = @LIBGCRYPT_CONFIG@ LIBGCRYPT_LIBS = @LIBGCRYPT_LIBS@ +LIBGTOP_CFLAGS = @LIBGTOP_CFLAGS@ +LIBGTOP_LIBS = @LIBGTOP_LIBS@ LIBICONV = @LIBICONV@ LIBINTL = @LIBINTL@ LIBLTDL = @LIBLTDL@ @@ -220,6 +257,7 @@ LT_CONFIG_H = @LT_CONFIG_H@ LT_DLLOADERS = @LT_DLLOADERS@ LT_DLPREOPEN = @LT_DLPREOPEN@ MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ MKDIR_P = @MKDIR_P@ MONKEYPREFIX = @MONKEYPREFIX@ MSGFMT = @MSGFMT@ @@ -229,6 +267,7 @@ MYSQL_CPPFLAGS = @MYSQL_CPPFLAGS@ MYSQL_LDFLAGS = @MYSQL_LDFLAGS@ NM = @NM@ NMEDIT = @NMEDIT@ +NSS_DIR = @NSS_DIR@ OBJC = @OBJC@ OBJCDEPMODE = @OBJCDEPMODE@ OBJCFLAGS = @OBJCFLAGS@ @@ -244,6 +283,7 @@ PACKAGE_TARNAME = @PACKAGE_TARNAME@ PACKAGE_URL = @PACKAGE_URL@ PACKAGE_VERSION = @PACKAGE_VERSION@ PATH_SEPARATOR = @PATH_SEPARATOR@ +PKG_CONFIG = @PKG_CONFIG@ POSTGRES_CPPFLAGS = @POSTGRES_CPPFLAGS@ POSTGRES_LDFLAGS = @POSTGRES_LDFLAGS@ POSUB = @POSUB@ @@ -275,6 +315,7 @@ abs_builddir = @abs_builddir@ abs_srcdir = @abs_srcdir@ abs_top_builddir = @abs_top_builddir@ abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ ac_ct_CC = @ac_ct_CC@ ac_ct_CXX = @ac_ct_CXX@ ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ @@ -297,6 +338,7 @@ datarootdir = @datarootdir@ docdir = @docdir@ dvidir = @dvidir@ exec_prefix = @exec_prefix@ +gitcommand = @gitcommand@ host = @host@ host_alias = @host_alias@ host_cpu = @host_cpu@ @@ -310,7 +352,6 @@ libdir = @libdir@ libexecdir = @libexecdir@ localedir = @localedir@ localstatedir = @localstatedir@ -lt_ECHO = @lt_ECHO@ ltdl_LIBOBJS = @ltdl_LIBOBJS@ ltdl_LTLIBOBJS = @ltdl_LTLIBOBJS@ mandir = @mandir@ @@ -328,6 +369,7 @@ sbindir = @sbindir@ sharedstatedir = @sharedstatedir@ srcdir = @srcdir@ subdirs = @subdirs@ +svnversioncommand = @svnversioncommand@ sys_symbol_underscore = @sys_symbol_underscore@ sysconfdir = @sysconfdir@ target = @target@ @@ -346,6 +388,8 @@ INCLUDES = -I$(top_srcdir)/src/include -I$(top_builddir)/src/include @MINGW_TRUE@ timeout_watchdog_w32.c noinst_SCRIPTS = \ + terminate.py \ + pydiffer.py \ gnunet_pyexpect.py \ gnunet_janitor.py @@ -354,15 +398,16 @@ bin_SCRIPTS = \ dist_pkgdata_DATA = \ gnunet-logo-color.png \ - testing_hostkeys.dat + testing_hostkeys.dat \ + testing_hostkeys.ecc EXTRA_DIST = \ coverage.sh \ - hostlist.cgi \ - hostlist.php \ report.sh \ + terminate.py.in \ gnunet_pyexpect.py.in \ gnunet_janitor.py.in \ + pydiffer.py.in \ gnunet-gns-import.sh do_subst = $(SED) -e 's,[@]PYTHON[@],$(PYTHON),g' @@ -372,6 +417,7 @@ test_gnunet_prefix_SOURCES = \ test_gnunet_prefix_LDADD = \ $(GCLIBADD) $(WINLIB) \ $(LTLIBICONV) \ + $(GN_LIBINTL) \ -lltdl -lunistring $(XLIB) pkghellodir = $(pkgdatadir)/hellos @@ -427,16 +473,19 @@ clean-noinstPROGRAMS: list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ echo " rm -f" $$list; \ rm -f $$list -test_gnunet_prefix$(EXEEXT): $(test_gnunet_prefix_OBJECTS) $(test_gnunet_prefix_DEPENDENCIES) +test_gnunet_prefix$(EXEEXT): $(test_gnunet_prefix_OBJECTS) $(test_gnunet_prefix_DEPENDENCIES) $(EXTRA_test_gnunet_prefix_DEPENDENCIES) @rm -f test_gnunet_prefix$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_gnunet_prefix_OBJECTS) $(test_gnunet_prefix_LDADD) $(LIBS) -timeout_watchdog$(EXEEXT): $(timeout_watchdog_OBJECTS) $(timeout_watchdog_DEPENDENCIES) +timeout_watchdog$(EXEEXT): $(timeout_watchdog_OBJECTS) $(timeout_watchdog_DEPENDENCIES) $(EXTRA_timeout_watchdog_DEPENDENCIES) @rm -f timeout_watchdog$(EXEEXT) $(AM_V_CCLD)$(LINK) $(timeout_watchdog_OBJECTS) $(timeout_watchdog_LDADD) $(LIBS) install-binSCRIPTS: $(bin_SCRIPTS) @$(NORMAL_INSTALL) - test -z "$(bindir)" || $(MKDIR_P) "$(DESTDIR)$(bindir)" @list='$(bin_SCRIPTS)'; test -n "$(bindir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(bindir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(bindir)" || exit 1; \ + fi; \ for p in $$list; do \ if test -f "$$p"; then d=; else d="$(srcdir)/"; fi; \ if test -f "$$d$$p"; then echo "$$d$$p"; echo "$$p"; else :; fi; \ @@ -464,9 +513,7 @@ uninstall-binSCRIPTS: @list='$(bin_SCRIPTS)'; test -n "$(bindir)" || exit 0; \ files=`for p in $$list; do echo "$$p"; done | \ sed -e 's,.*/,,;$(transform)'`; \ - test -n "$$list" || exit 0; \ - echo " ( cd '$(DESTDIR)$(bindir)' && rm -f" $$files ")"; \ - cd "$(DESTDIR)$(bindir)" && rm -f $$files + dir='$(DESTDIR)$(bindir)'; $(am__uninstall_files_from_dir) mostlyclean-compile: -rm -f *.$(OBJEXT) @@ -481,26 +528,23 @@ distclean-compile: .c.o: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c $< .c.obj: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'` @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c `$(CYGPATH_W) '$<'` +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c `$(CYGPATH_W) '$<'` .c.lo: @am__fastdepCC_TRUE@ $(AM_V_CC)$(LTCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LTCOMPILE) -c -o $@ $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LTCOMPILE) -c -o $@ $< mostlyclean-libtool: -rm -f *.lo @@ -509,8 +553,11 @@ clean-libtool: -rm -rf .libs _libs install-dist_pkgdataDATA: $(dist_pkgdata_DATA) @$(NORMAL_INSTALL) - test -z "$(pkgdatadir)" || $(MKDIR_P) "$(DESTDIR)$(pkgdatadir)" @list='$(dist_pkgdata_DATA)'; test -n "$(pkgdatadir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(pkgdatadir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(pkgdatadir)" || exit 1; \ + fi; \ for p in $$list; do \ if test -f "$$p"; then d=; else d="$(srcdir)/"; fi; \ echo "$$d$$p"; \ @@ -524,9 +571,7 @@ uninstall-dist_pkgdataDATA: @$(NORMAL_UNINSTALL) @list='$(dist_pkgdata_DATA)'; test -n "$(pkgdatadir)" || list=; \ files=`for p in $$list; do echo $$p; done | sed -e 's|^.*/||'`; \ - test -n "$$files" || exit 0; \ - echo " ( cd '$(DESTDIR)$(pkgdatadir)' && rm -f" $$files ")"; \ - cd "$(DESTDIR)$(pkgdatadir)" && rm -f $$files + dir='$(DESTDIR)$(pkgdatadir)'; $(am__uninstall_files_from_dir) ID: $(HEADERS) $(SOURCES) $(LISP) $(TAGS_FILES) list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ @@ -631,10 +676,15 @@ install-am: all-am installcheck: installcheck-am install-strip: - $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ - install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ - `test -z '$(STRIP)' || \ - echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi mostlyclean-generic: clean-generic: diff --git a/contrib/coverage.sh b/contrib/coverage.sh index b53a382..dd6a6ab 100755 --- a/contrib/coverage.sh +++ b/contrib/coverage.sh @@ -2,7 +2,7 @@ # make sure configure was run with coverage enabled... lcov --directory . --zerocounters make check -rm `find * -name "test_*.gc??"` +rm `find * -name "test_*.gc??"` `find * -name "perf_*.gc??"` for n in `find * -name "*.gc??" | grep libs` do cd `dirname $n` diff --git a/contrib/gnunet_janitor.py.in b/contrib/gnunet_janitor.py.in index 056ab9b..69186fd 100644 --- a/contrib/gnunet_janitor.py.in +++ b/contrib/gnunet_janitor.py.in @@ -30,13 +30,11 @@ import sys import shutil import time import signal +import terminate if os.name == 'nt': from win32com.client import GetObject WMI = GetObject('winmgmts:') - killsignal = signal.SIGTERM # any valid value will result in TerminateProcess() -else: - killsignal = signal.SIGKILL def get_process_list (): result = [] @@ -63,7 +61,7 @@ def main (): if re.match (r'gnunet-service-arm', p[1]): print ("killing arm process {0:5} {1}".format (p[0], p[1])) try: - os.kill (int (p[0]), killsignal) + terminate.safe_terminate_process_by_pid (int (p[0]), 1) except OSError as e: print ("failed: {0}".format (e)) pass @@ -71,7 +69,7 @@ def main (): if not re.match (r'gnunet-service-arm', p[1]): print ("killing non-arm process {0:5} {1}".format (p[0], p[1])) try: - os.kill (int (p[0]), killsignal) + terminate.safe_terminate_process_by_pid (int (p[0]), 1) except OSError as e: print ("failed: {0}".format (e)) pass diff --git a/contrib/hostlist.cgi b/contrib/hostlist.cgi deleted file mode 100644 index f04246e..0000000 --- a/contrib/hostlist.cgi +++ /dev/null @@ -1,5 +0,0 @@ -#!/bin/sh -# This is a CGI script to generate the host list on-demand. -# by Michael Wensley, with minor improvements by Christian Grothoff -echo -ne "Content-Type: application/octet-stream\r\n\r\n" -cat /var/lib/gnunet/data/hosts/*.{2,3,4,5,6,8,12,17,23,25} diff --git a/contrib/hostlist.php b/contrib/hostlist.php deleted file mode 100644 index 1585615..0000000 --- a/contrib/hostlist.php +++ /dev/null @@ -1,35 +0,0 @@ -= 4.3.0 -// Author: "Krasko Oleksandr" <0m3r.mail@gmail.com> -// Minor improvements by Christian Grothoff -header("Content-Type: application/octet-stream\r\n\r\n"); -$extmas = array(); -$pv=$_GET['p']; -if (isset($pv)) - { - for ($ii=0;$ii<64;$ii++) - if (0 != ($pv & (1 << $ii))) - $extmas[] = $ii; - } -else - { - $extmas = array('2','3','4','5','6','8','12','17','23','25'); - } -$path = '/var/lib/gnunet/data/hosts/'; // adjust as necessary -$dir = opendir($path); -if (! $dir) - die("Cannot open directory $path.\n"); -$mas = array(); -while ($fname = readdir($dir)) { - $fn = $path . '/' . $fname; - if (is_file($fn)) { - $dpo = strpos($fname, '.') + 1; - $len = strlen($fname); - if (in_array(substr($fname, $dpo - $len), $extmas)) - $mas[] = $fn; - } -} -shuffle($mas); // randomize order -foreach ($mas as $val) - echo file_get_contents($val); -?> diff --git a/contrib/pydiffer.py.in b/contrib/pydiffer.py.in new file mode 100644 index 0000000..23d546b --- /dev/null +++ b/contrib/pydiffer.py.in @@ -0,0 +1,39 @@ +#!@PYTHON@ +import os +import sys +import difflib +import filecmp + +def getdiff (old, new): + diff = [] + with open (old) as a: + with open (new) as b: + for l in difflib.unified_diff (a.read ().splitlines (), b.read ().splitlines ()): + diff.append (l) + return diff + +def dc_getdiff (dc, old, new): + diff = [] + for f in dc.left_only: + diff.append ("Only in {}: {}".format (old, f)) + for f in dc.right_only: + diff.append ("Only in {}: {}".format (new, f)) + for f in dc.diff_files: + r = getdiff (os.path.join (old, f), os.path.join (new, f)) + diff.extend (r) + for dn, dc in dc.subdirs.items (): + r = dc_getdiff (dc, os.path.join (old, dn), os.path.join (new, dn)) + diff.extend (r) + return diff + +def dcdiff (old, new): + dc = filecmp.dircmp (old, new) + diff = dc_getdiff (dc, old, new) + return diff + +def main (): + for l in dcdiff (sys.argv[1], sys.argv[2]): + print (l) + +if __name__ == '__main__': + main () diff --git a/contrib/report.sh b/contrib/report.sh index 37a1c41..6e1d399 100755 --- a/contrib/report.sh +++ b/contrib/report.sh @@ -156,6 +156,26 @@ else fi fi +TEST=`$WHICH dpkg 2> /dev/null` +if test -n "$TEST"; then + LINES=`dpkg -s libunistring-dev | grep Version | wc -l` + if test "$LINES" = "1" + then + VERSION=`dpkg -s libunistring-dev | grep Version | awk '{print $2}'` + echo "libunistring : libunistring3-dev-$VERSION.deb" + else + echo "libunistring : dpkg: libunistring3-dev not installed" + fi +else + TEST=`$WHICH rpm 2> /dev/null` + if test -n "$TEST"; then + rpm -q unistring | sed -e "s/unistring-//" 2> /dev/null | \ + awk '{print "libunistring : "$1.rpm}' + else + echo "libunistring : Test not available" + fi +fi + TEST=`$WHICH gettext 2> /dev/null` if test -n "$TEST"; then gettext --version | head -n1 2> /dev/null | \ @@ -173,15 +193,7 @@ else echo "libcurl : Not found" fi - -TEST=`which qmake 2> /dev/null` -if test -x "$TEST"; then - qmake --version | tail -n 1 | awk '{print "Qt : "$4}' -else - echo "Qt : Not found" -fi - -echo -n "MHD : " +echo -n "libmicrohttpd : " TMPFILE=`mktemp /tmp/mhd-version-testXXXXXX` cat - >$TMPFILE.c < @@ -197,4 +209,36 @@ gcc -o $TMPFILE $TMPFILE.c 2> /dev/null && $TMPFILE || echo "Not found" rm -f $TMPFILE $TMPFILE.bin +echo -n "GNU GLPK : " +TMPFILE=`mktemp /tmp/glpk-version-testXXXXXX` +cat - >$TMPFILE.c < +#include +int main() +{ + fprintf (stdout, "%u.%u\n", GLP_MAJOR_VERSION, GLP_MINOR_VERSION); + return 0; +} +EOF + +gcc -o $TMPFILE $TMPFILE.c 2> /dev/null && $TMPFILE || echo "Not found" +rm -f $TMPFILE $TMPFILE.bin + + +echo -n "GNUtls : " +TMPFILE=`mktemp /tmp/gnutls-version-testXXXXXX` +cat - >$TMPFILE.c < +#include +int main() +{ + fprintf (stdout, "%s\n", GNUTLS_VERSION); + return 0; +} +EOF + +gcc -o $TMPFILE $TMPFILE.c 2> /dev/null && $TMPFILE || echo "Not found" +rm -f $TMPFILE $TMPFILE.bin + + echo "--------------------------------------------------------------" diff --git a/contrib/terminate.py.in b/contrib/terminate.py.in new file mode 100644 index 0000000..14c79c1 --- /dev/null +++ b/contrib/terminate.py.in @@ -0,0 +1,64 @@ +#!@PYTHON@ +# This file is part of GNUnet. +# (C) 2011 Christian Grothoff (and other contributing authors) +# +# GNUnet is free software; you can redistribute it and/or modify +# it under the terms of the GNU General Public License as published +# by the Free Software Foundation; either version 2, or (at your +# option) any later version. +# +# GNUnet is distributed in the hope that it will be useful, but +# WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +# General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with GNUnet; see the file COPYING. If not, write to the +# Free Software Foundation, Inc., 59 Temple Place - Suite 330, +# Boston, MA 02111-1307, USA. +# +# Utility module that implements safe process termination for W32. +# For other platforms it's equivalent to Popen.kill () +# Requires pywin32 on W32. + +import sys +import os +import subprocess +if os.name == 'nt': + import win32api + import win32process + +class dummyobj (object): + pass + +def safe_terminate_process_by_pid (pid, code): + if os.name == 'nt': + p = dummyobj () + p._handle = win32api.OpenProcess (2 | 1024 | 8 | 32 | 16, 0, pid) + result = safe_terminate_process (p, code) + win32api.CloseHandle (p._handle) + return result + else: + return os.kill (int (pid), SIGKILL) + +def safe_terminate_process (proc, code): + if os.name == 'nt': + cp = win32api.GetCurrentProcess () + result = False + dupproc = win32api.DuplicateHandle (cp, proc._handle, cp, 2 | 1024 | 8 | 32 | 16, 0, 0) + try: + exitcode = win32process.GetExitCodeProcess (dupproc) + if exitcode == 0x103: + kernel32 = win32api.GetModuleHandle ("kernel32") + exitprocess = win32api.GetProcAddress (kernel32, "ExitProcess") + th, tid = win32process.CreateRemoteThread (dupproc, None, 0, exitprocess, code, 0) + win32api.CloseHandle (th) + result = True + else: + result = True + # except failed to get exit code? failed to get module handle? + finally: + win32api.CloseHandle (dupproc) + return result + else: + return proc.kill () diff --git a/contrib/testing_hostkeys.ecc b/contrib/testing_hostkeys.ecc new file mode 100644 index 0000000..ec28939 Binary files /dev/null and b/contrib/testing_hostkeys.ecc differ diff --git a/depcomp b/depcomp index df8eea7..25a39e6 100755 --- a/depcomp +++ b/depcomp @@ -1,10 +1,10 @@ #! /bin/sh # depcomp - compile a program generating dependencies as side-effects -scriptversion=2009-04-28.21; # UTC +scriptversion=2012-03-27.16; # UTC -# Copyright (C) 1999, 2000, 2003, 2004, 2005, 2006, 2007, 2009 Free -# Software Foundation, Inc. +# Copyright (C) 1999, 2000, 2003, 2004, 2005, 2006, 2007, 2009, 2010, +# 2011, 2012 Free Software Foundation, Inc. # This program is free software; you can redistribute it and/or modify # it under the terms of the GNU General Public License as published by @@ -28,7 +28,7 @@ scriptversion=2009-04-28.21; # UTC case $1 in '') - echo "$0: No command. Try \`$0 --help' for more information." 1>&2 + echo "$0: No command. Try '$0 --help' for more information." 1>&2 exit 1; ;; -h | --h*) @@ -40,11 +40,11 @@ as side-effects. Environment variables: depmode Dependency tracking mode. - source Source file read by `PROGRAMS ARGS'. - object Object file output by `PROGRAMS ARGS'. + source Source file read by 'PROGRAMS ARGS'. + object Object file output by 'PROGRAMS ARGS'. DEPDIR directory where to store dependencies. depfile Dependency file to output. - tmpdepfile Temporary file to use when outputing dependencies. + tmpdepfile Temporary file to use when outputting dependencies. libtool Whether libtool is used (yes/no). Report bugs to . @@ -57,6 +57,12 @@ EOF ;; esac +# A tabulation character. +tab=' ' +# A newline character. +nl=' +' + if test -z "$depmode" || test -z "$source" || test -z "$object"; then echo "depcomp: Variables source, object and depmode must be set" 1>&2 exit 1 @@ -90,10 +96,24 @@ if test "$depmode" = msvcmsys; then # This is just like msvisualcpp but w/o cygpath translation. # Just convert the backslash-escaped backslashes to single forward # slashes to satisfy depend.m4 - cygpath_u="sed s,\\\\\\\\,/,g" + cygpath_u='sed s,\\\\,/,g' depmode=msvisualcpp fi +if test "$depmode" = msvc7msys; then + # This is just like msvc7 but w/o cygpath translation. + # Just convert the backslash-escaped backslashes to single forward + # slashes to satisfy depend.m4 + cygpath_u='sed s,\\\\,/,g' + depmode=msvc7 +fi + +if test "$depmode" = xlc; then + # IBM C/C++ Compilers xlc/xlC can output gcc-like dependency informations. + gccflag=-qmakedep=gcc,-MF + depmode=gcc +fi + case "$depmode" in gcc3) ## gcc 3 implements dependency tracking that does exactly what @@ -148,20 +168,21 @@ gcc) ## The second -e expression handles DOS-style file names with drive letters. sed -e 's/^[^:]*: / /' \ -e 's/^['$alpha']:\/[^:]*: / /' < "$tmpdepfile" >> "$depfile" -## This next piece of magic avoids the `deleted header file' problem. +## This next piece of magic avoids the "deleted header file" problem. ## The problem is that when a header file which appears in a .P file ## is deleted, the dependency causes make to die (because there is ## typically no way to rebuild the header). We avoid this by adding ## dummy dependencies for each header file. Too bad gcc doesn't do ## this for us directly. - tr ' ' ' -' < "$tmpdepfile" | -## Some versions of gcc put a space before the `:'. On the theory + tr ' ' "$nl" < "$tmpdepfile" | +## Some versions of gcc put a space before the ':'. On the theory ## that the space means something, we add a space to the output as -## well. +## well. hp depmode also adds that space, but also prefixes the VPATH +## to the object. Take care to not repeat it in the output. ## Some versions of the HPUX 10.20 sed can't process this invocation ## correctly. Breaking it into two sed invocations is a workaround. - sed -e 's/^\\$//' -e '/^$/d' -e '/:$/d' | sed -e 's/$/ :/' >> "$depfile" + sed -e 's/^\\$//' -e '/^$/d' -e "s|.*$object$||" -e '/:$/d' \ + | sed -e 's/$/ :/' >> "$depfile" rm -f "$tmpdepfile" ;; @@ -193,18 +214,15 @@ sgi) # clever and replace this with sed code, as IRIX sed won't handle # lines with more than a fixed number of characters (4096 in # IRIX 6.2 sed, 8192 in IRIX 6.5). We also remove comment lines; - # the IRIX cc adds comments like `#:fec' to the end of the + # the IRIX cc adds comments like '#:fec' to the end of the # dependency line. - tr ' ' ' -' < "$tmpdepfile" \ + tr ' ' "$nl" < "$tmpdepfile" \ | sed -e 's/^.*\.o://' -e 's/#.*$//' -e '/^$/ d' | \ - tr ' -' ' ' >> "$depfile" + tr "$nl" ' ' >> "$depfile" echo >> "$depfile" # The second pass generates a dummy entry for each header file. - tr ' ' ' -' < "$tmpdepfile" \ + tr ' ' "$nl" < "$tmpdepfile" \ | sed -e 's/^.*\.o://' -e 's/#.*$//' -e '/^$/ d' -e 's/$/:/' \ >> "$depfile" else @@ -216,10 +234,17 @@ sgi) rm -f "$tmpdepfile" ;; +xlc) + # This case exists only to let depend.m4 do its work. It works by + # looking at the text of this script. This case will never be run, + # since it is checked for above. + exit 1 + ;; + aix) # The C for AIX Compiler uses -M and outputs the dependencies # in a .u file. In older versions, this file always lives in the - # current directory. Also, the AIX compiler puts `$object:' at the + # current directory. Also, the AIX compiler puts '$object:' at the # start of each line; $object doesn't have directory information. # Version 6 uses the directory in both cases. dir=`echo "$object" | sed -e 's|/[^/]*$|/|'` @@ -249,12 +274,11 @@ aix) test -f "$tmpdepfile" && break done if test -f "$tmpdepfile"; then - # Each line is of the form `foo.o: dependent.h'. + # Each line is of the form 'foo.o: dependent.h'. # Do two passes, one to just change these to - # `$object: dependent.h' and one to simply `dependent.h:'. + # '$object: dependent.h' and one to simply 'dependent.h:'. sed -e "s,^.*\.[a-z]*:,$object:," < "$tmpdepfile" > "$depfile" - # That's a tab and a space in the []. - sed -e 's,^.*\.[a-z]*:[ ]*,,' -e 's,$,:,' < "$tmpdepfile" >> "$depfile" + sed -e 's,^.*\.[a-z]*:['"$tab"' ]*,,' -e 's,$,:,' < "$tmpdepfile" >> "$depfile" else # The sourcefile does not contain any dependencies, so just # store a dummy comment line, to avoid errors with the Makefile @@ -265,23 +289,26 @@ aix) ;; icc) - # Intel's C compiler understands `-MD -MF file'. However on - # icc -MD -MF foo.d -c -o sub/foo.o sub/foo.c + # Intel's C compiler anf tcc (Tiny C Compiler) understand '-MD -MF file'. + # However on + # $CC -MD -MF foo.d -c -o sub/foo.o sub/foo.c # ICC 7.0 will fill foo.d with something like # foo.o: sub/foo.c # foo.o: sub/foo.h - # which is wrong. We want: + # which is wrong. We want # sub/foo.o: sub/foo.c # sub/foo.o: sub/foo.h # sub/foo.c: # sub/foo.h: # ICC 7.1 will output # foo.o: sub/foo.c sub/foo.h - # and will wrap long lines using \ : + # and will wrap long lines using '\': # foo.o: sub/foo.c ... \ # sub/foo.h ... \ # ... - + # tcc 0.9.26 (FIXME still under development at the moment of writing) + # will emit a similar output, but also prepend the continuation lines + # with horizontal tabulation characters. "$@" -MD -MF "$tmpdepfile" stat=$? if test $stat -eq 0; then : @@ -290,15 +317,21 @@ icc) exit $stat fi rm -f "$depfile" - # Each line is of the form `foo.o: dependent.h', - # or `foo.o: dep1.h dep2.h \', or ` dep3.h dep4.h \'. + # Each line is of the form 'foo.o: dependent.h', + # or 'foo.o: dep1.h dep2.h \', or ' dep3.h dep4.h \'. # Do two passes, one to just change these to - # `$object: dependent.h' and one to simply `dependent.h:'. - sed "s,^[^:]*:,$object :," < "$tmpdepfile" > "$depfile" - # Some versions of the HPUX 10.20 sed can't process this invocation - # correctly. Breaking it into two sed invocations is a workaround. - sed 's,^[^:]*: \(.*\)$,\1,;s/^\\$//;/^$/d;/:$/d' < "$tmpdepfile" | - sed -e 's/$/ :/' >> "$depfile" + # '$object: dependent.h' and one to simply 'dependent.h:'. + sed -e "s/^[ $tab][ $tab]*/ /" -e "s,^[^:]*:,$object :," \ + < "$tmpdepfile" > "$depfile" + sed ' + s/[ '"$tab"'][ '"$tab"']*/ /g + s/^ *// + s/ *\\*$// + s/^[^:]*: *// + /^$/d + /:$/d + s/$/ :/ + ' < "$tmpdepfile" >> "$depfile" rm -f "$tmpdepfile" ;; @@ -334,7 +367,7 @@ hp2) done if test -f "$tmpdepfile"; then sed -e "s,^.*\.[a-z]*:,$object:," "$tmpdepfile" > "$depfile" - # Add `dependent.h:' lines. + # Add 'dependent.h:' lines. sed -ne '2,${ s/^ *// s/ \\*$// @@ -349,9 +382,9 @@ hp2) tru64) # The Tru64 compiler uses -MD to generate dependencies as a side - # effect. `cc -MD -o foo.o ...' puts the dependencies into `foo.o.d'. + # effect. 'cc -MD -o foo.o ...' puts the dependencies into 'foo.o.d'. # At least on Alpha/Redhat 6.1, Compaq CCC V6.2-504 seems to put - # dependencies in `foo.d' instead, so we check for that too. + # dependencies in 'foo.d' instead, so we check for that too. # Subdirectories are respected. dir=`echo "$object" | sed -e 's|/[^/]*$|/|'` test "x$dir" = "x$object" && dir= @@ -397,14 +430,59 @@ tru64) done if test -f "$tmpdepfile"; then sed -e "s,^.*\.[a-z]*:,$object:," < "$tmpdepfile" > "$depfile" - # That's a tab and a space in the []. - sed -e 's,^.*\.[a-z]*:[ ]*,,' -e 's,$,:,' < "$tmpdepfile" >> "$depfile" + sed -e 's,^.*\.[a-z]*:['"$tab"' ]*,,' -e 's,$,:,' < "$tmpdepfile" >> "$depfile" else echo "#dummy" > "$depfile" fi rm -f "$tmpdepfile" ;; +msvc7) + if test "$libtool" = yes; then + showIncludes=-Wc,-showIncludes + else + showIncludes=-showIncludes + fi + "$@" $showIncludes > "$tmpdepfile" + stat=$? + grep -v '^Note: including file: ' "$tmpdepfile" + if test "$stat" = 0; then : + else + rm -f "$tmpdepfile" + exit $stat + fi + rm -f "$depfile" + echo "$object : \\" > "$depfile" + # The first sed program below extracts the file names and escapes + # backslashes for cygpath. The second sed program outputs the file + # name when reading, but also accumulates all include files in the + # hold buffer in order to output them again at the end. This only + # works with sed implementations that can handle large buffers. + sed < "$tmpdepfile" -n ' +/^Note: including file: *\(.*\)/ { + s//\1/ + s/\\/\\\\/g + p +}' | $cygpath_u | sort -u | sed -n ' +s/ /\\ /g +s/\(.*\)/'"$tab"'\1 \\/p +s/.\(.*\) \\/\1:/ +H +$ { + s/.*/'"$tab"'/ + G + p +}' >> "$depfile" + rm -f "$tmpdepfile" + ;; + +msvc7msys) + # This case exists only to let depend.m4 do its work. It works by + # looking at the text of this script. This case will never be run, + # since it is checked for above. + exit 1 + ;; + #nosideeffect) # This comment above is used by automake to tell side-effect # dependency tracking mechanisms from slower ones. @@ -422,7 +500,7 @@ dashmstdout) shift fi - # Remove `-o $object'. + # Remove '-o $object'. IFS=" " for arg do @@ -442,15 +520,14 @@ dashmstdout) done test -z "$dashmflag" && dashmflag=-M - # Require at least two characters before searching for `:' + # Require at least two characters before searching for ':' # in the target name. This is to cope with DOS-style filenames: - # a dependency such as `c:/foo/bar' could be seen as target `c' otherwise. + # a dependency such as 'c:/foo/bar' could be seen as target 'c' otherwise. "$@" $dashmflag | - sed 's:^[ ]*[^: ][^:][^:]*\:[ ]*:'"$object"'\: :' > "$tmpdepfile" + sed 's:^['"$tab"' ]*[^:'"$tab"' ][^:][^:]*\:['"$tab"' ]*:'"$object"'\: :' > "$tmpdepfile" rm -f "$depfile" cat < "$tmpdepfile" > "$depfile" - tr ' ' ' -' < "$tmpdepfile" | \ + tr ' ' "$nl" < "$tmpdepfile" | \ ## Some versions of the HPUX 10.20 sed can't process this invocation ## correctly. Breaking it into two sed invocations is a workaround. sed -e 's/^\\$//' -e '/^$/d' -e '/:$/d' | sed -e 's/$/ :/' >> "$depfile" @@ -503,9 +580,10 @@ makedepend) touch "$tmpdepfile" ${MAKEDEPEND-makedepend} -o"$obj_suffix" -f"$tmpdepfile" "$@" rm -f "$depfile" - cat < "$tmpdepfile" > "$depfile" - sed '1,2d' "$tmpdepfile" | tr ' ' ' -' | \ + # makedepend may prepend the VPATH from the source file name to the object. + # No need to regex-escape $object, excess matching of '.' is harmless. + sed "s|^.*\($object *:\)|\1|" "$tmpdepfile" > "$depfile" + sed '1,2d' "$tmpdepfile" | tr ' ' "$nl" | \ ## Some versions of the HPUX 10.20 sed can't process this invocation ## correctly. Breaking it into two sed invocations is a workaround. sed -e 's/^\\$//' -e '/^$/d' -e '/:$/d' | sed -e 's/$/ :/' >> "$depfile" @@ -525,7 +603,7 @@ cpp) shift fi - # Remove `-o $object'. + # Remove '-o $object'. IFS=" " for arg do @@ -594,8 +672,8 @@ msvisualcpp) sed -n '/^#line [0-9][0-9]* "\([^"]*\)"/ s::\1:p' | $cygpath_u | sort -u > "$tmpdepfile" rm -f "$depfile" echo "$object : \\" > "$depfile" - sed < "$tmpdepfile" -n -e 's% %\\ %g' -e '/^\(.*\)$/ s:: \1 \\:p' >> "$depfile" - echo " " >> "$depfile" + sed < "$tmpdepfile" -n -e 's% %\\ %g' -e '/^\(.*\)$/ s::'"$tab"'\1 \\:p' >> "$depfile" + echo "$tab" >> "$depfile" sed < "$tmpdepfile" -n -e 's% %\\ %g' -e '/^\(.*\)$/ s::\1\::p' >> "$depfile" rm -f "$tmpdepfile" ;; diff --git a/doc/Makefile.am b/doc/Makefile.am index 738d970..6f92cc1 100644 --- a/doc/Makefile.am +++ b/doc/Makefile.am @@ -1,3 +1,3 @@ SUBDIRS = man -EXTRA_DIST = README.mysql README.postgres +docdir = $(datadir)/doc/gnunet/ diff --git a/doc/Makefile.in b/doc/Makefile.in index f1b7b45..9db5f9c 100644 --- a/doc/Makefile.in +++ b/doc/Makefile.in @@ -1,9 +1,9 @@ -# Makefile.in generated by automake 1.11.1 from Makefile.am. +# Makefile.in generated by automake 1.11.6 from Makefile.am. # @configure_input@ # Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, -# 2003, 2004, 2005, 2006, 2007, 2008, 2009 Free Software Foundation, -# Inc. +# 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Free Software +# Foundation, Inc. # This Makefile.in is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. @@ -15,6 +15,23 @@ @SET_MAKE@ VPATH = @srcdir@ +am__make_dryrun = \ + { \ + am__dry=no; \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + echo 'am--echo: ; @echo "AM" OK' | $(MAKE) -f - 2>/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } pkgdatadir = $(datadir)/@PACKAGE@ pkgincludedir = $(includedir)/@PACKAGE@ pkglibdir = $(libdir)/@PACKAGE@ @@ -39,14 +56,15 @@ DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 am__aclocal_m4_deps = $(top_srcdir)/m4/absolute-header.m4 \ $(top_srcdir)/m4/align.m4 $(top_srcdir)/m4/argz.m4 \ - $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/iconv.m4 \ - $(top_srcdir)/m4/lib-ld.m4 $(top_srcdir)/m4/lib-link.m4 \ - $(top_srcdir)/m4/lib-prefix.m4 $(top_srcdir)/m4/libcurl.m4 \ - $(top_srcdir)/m4/libgcrypt.m4 $(top_srcdir)/m4/libtool.m4 \ - $(top_srcdir)/m4/libunistring.m4 $(top_srcdir)/m4/ltdl.m4 \ - $(top_srcdir)/m4/ltoptions.m4 $(top_srcdir)/m4/ltsugar.m4 \ - $(top_srcdir)/m4/ltversion.m4 $(top_srcdir)/m4/lt~obsolete.m4 \ - $(top_srcdir)/m4/nls.m4 $(top_srcdir)/m4/po.m4 \ + $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/glib-2.0.m4 \ + $(top_srcdir)/m4/iconv.m4 $(top_srcdir)/m4/lib-ld.m4 \ + $(top_srcdir)/m4/lib-link.m4 $(top_srcdir)/m4/lib-prefix.m4 \ + $(top_srcdir)/m4/libcurl.m4 $(top_srcdir)/m4/libgcrypt.m4 \ + $(top_srcdir)/m4/libtool.m4 $(top_srcdir)/m4/libunistring.m4 \ + $(top_srcdir)/m4/ltdl.m4 $(top_srcdir)/m4/ltoptions.m4 \ + $(top_srcdir)/m4/ltsugar.m4 $(top_srcdir)/m4/ltversion.m4 \ + $(top_srcdir)/m4/lt~obsolete.m4 $(top_srcdir)/m4/nls.m4 \ + $(top_srcdir)/m4/pkg.m4 $(top_srcdir)/m4/po.m4 \ $(top_srcdir)/m4/progtest.m4 $(top_srcdir)/acinclude.m4 \ $(top_srcdir)/configure.ac am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ @@ -55,11 +73,11 @@ mkinstalldirs = $(install_sh) -d CONFIG_HEADER = $(top_builddir)/gnunet_config.h CONFIG_CLEAN_FILES = CONFIG_CLEAN_VPATH_FILES = -AM_V_GEN = $(am__v_GEN_$(V)) -am__v_GEN_ = $(am__v_GEN_$(AM_DEFAULT_VERBOSITY)) +AM_V_GEN = $(am__v_GEN_@AM_V@) +am__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@) am__v_GEN_0 = @echo " GEN " $@; -AM_V_at = $(am__v_at_$(V)) -am__v_at_ = $(am__v_at_$(AM_DEFAULT_VERBOSITY)) +AM_V_at = $(am__v_at_@AM_V@) +am__v_at_ = $(am__v_at_@AM_DEFAULT_V@) am__v_at_0 = @ SOURCES = DIST_SOURCES = @@ -70,6 +88,11 @@ RECURSIVE_TARGETS = all-recursive check-recursive dvi-recursive \ install-pdf-recursive install-ps-recursive install-recursive \ installcheck-recursive installdirs-recursive pdf-recursive \ ps-recursive uninstall-recursive +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac RECURSIVE_CLEAN_TARGETS = mostlyclean-recursive clean-recursive \ distclean-recursive maintainer-clean-recursive AM_RECURSIVE_TARGETS = $(RECURSIVE_TARGETS:-recursive=) \ @@ -139,6 +162,10 @@ EXEEXT = @EXEEXT@ EXT_LIBS = @EXT_LIBS@ EXT_LIB_PATH = @EXT_LIB_PATH@ FGREP = @FGREP@ +GLIB_CFLAGS = @GLIB_CFLAGS@ +GLIB_GENMARSHAL = @GLIB_GENMARSHAL@ +GLIB_LIBS = @GLIB_LIBS@ +GLIB_MKENUMS = @GLIB_MKENUMS@ GMSGFMT = @GMSGFMT@ GMSGFMT_015 = @GMSGFMT_015@ GNUNETDNS_GROUP = @GNUNETDNS_GROUP@ @@ -149,6 +176,7 @@ GN_LIBINTL = @GN_LIBINTL@ GN_LIB_LDFLAGS = @GN_LIB_LDFLAGS@ GN_PLUGIN_LDFLAGS = @GN_PLUGIN_LDFLAGS@ GN_USER_HOME_DIR = @GN_USER_HOME_DIR@ +GOBJECT_QUERY = @GOBJECT_QUERY@ GREP = @GREP@ HAVE_LIBUNISTRING = @HAVE_LIBUNISTRING@ INCLTDL = @INCLTDL@ @@ -171,6 +199,8 @@ LIBCURL_CPPFLAGS = @LIBCURL_CPPFLAGS@ LIBGCRYPT_CFLAGS = @LIBGCRYPT_CFLAGS@ LIBGCRYPT_CONFIG = @LIBGCRYPT_CONFIG@ LIBGCRYPT_LIBS = @LIBGCRYPT_LIBS@ +LIBGTOP_CFLAGS = @LIBGTOP_CFLAGS@ +LIBGTOP_LIBS = @LIBGTOP_LIBS@ LIBICONV = @LIBICONV@ LIBINTL = @LIBINTL@ LIBLTDL = @LIBLTDL@ @@ -192,6 +222,7 @@ LT_CONFIG_H = @LT_CONFIG_H@ LT_DLLOADERS = @LT_DLLOADERS@ LT_DLPREOPEN = @LT_DLPREOPEN@ MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ MKDIR_P = @MKDIR_P@ MONKEYPREFIX = @MONKEYPREFIX@ MSGFMT = @MSGFMT@ @@ -201,6 +232,7 @@ MYSQL_CPPFLAGS = @MYSQL_CPPFLAGS@ MYSQL_LDFLAGS = @MYSQL_LDFLAGS@ NM = @NM@ NMEDIT = @NMEDIT@ +NSS_DIR = @NSS_DIR@ OBJC = @OBJC@ OBJCDEPMODE = @OBJCDEPMODE@ OBJCFLAGS = @OBJCFLAGS@ @@ -216,6 +248,7 @@ PACKAGE_TARNAME = @PACKAGE_TARNAME@ PACKAGE_URL = @PACKAGE_URL@ PACKAGE_VERSION = @PACKAGE_VERSION@ PATH_SEPARATOR = @PATH_SEPARATOR@ +PKG_CONFIG = @PKG_CONFIG@ POSTGRES_CPPFLAGS = @POSTGRES_CPPFLAGS@ POSTGRES_LDFLAGS = @POSTGRES_LDFLAGS@ POSUB = @POSUB@ @@ -247,6 +280,7 @@ abs_builddir = @abs_builddir@ abs_srcdir = @abs_srcdir@ abs_top_builddir = @abs_top_builddir@ abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ ac_ct_CC = @ac_ct_CC@ ac_ct_CXX = @ac_ct_CXX@ ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ @@ -266,9 +300,10 @@ build_vendor = @build_vendor@ builddir = @builddir@ datadir = @datadir@ datarootdir = @datarootdir@ -docdir = @docdir@ +docdir = $(datadir)/doc/gnunet/ dvidir = @dvidir@ exec_prefix = @exec_prefix@ +gitcommand = @gitcommand@ host = @host@ host_alias = @host_alias@ host_cpu = @host_cpu@ @@ -282,7 +317,6 @@ libdir = @libdir@ libexecdir = @libexecdir@ localedir = @localedir@ localstatedir = @localstatedir@ -lt_ECHO = @lt_ECHO@ ltdl_LIBOBJS = @ltdl_LIBOBJS@ ltdl_LTLIBOBJS = @ltdl_LTLIBOBJS@ mandir = @mandir@ @@ -300,6 +334,7 @@ sbindir = @sbindir@ sharedstatedir = @sharedstatedir@ srcdir = @srcdir@ subdirs = @subdirs@ +svnversioncommand = @svnversioncommand@ sys_symbol_underscore = @sys_symbol_underscore@ sysconfdir = @sysconfdir@ target = @target@ @@ -311,7 +346,6 @@ top_build_prefix = @top_build_prefix@ top_builddir = @top_builddir@ top_srcdir = @top_srcdir@ SUBDIRS = man -EXTRA_DIST = README.mysql README.postgres all: all-recursive .SUFFIXES: @@ -519,13 +553,10 @@ distdir: $(DISTFILES) done @list='$(DIST_SUBDIRS)'; for subdir in $$list; do \ if test "$$subdir" = .; then :; else \ - test -d "$(distdir)/$$subdir" \ - || $(MKDIR_P) "$(distdir)/$$subdir" \ - || exit 1; \ - fi; \ - done - @list='$(DIST_SUBDIRS)'; for subdir in $$list; do \ - if test "$$subdir" = .; then :; else \ + $(am__make_dryrun) \ + || test -d "$(distdir)/$$subdir" \ + || $(MKDIR_P) "$(distdir)/$$subdir" \ + || exit 1; \ dir1=$$subdir; dir2="$(distdir)/$$subdir"; \ $(am__relativize); \ new_distdir=$$reldir; \ @@ -560,10 +591,15 @@ install-am: all-am installcheck: installcheck-recursive install-strip: - $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ - install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ - `test -z '$(STRIP)' || \ - echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi mostlyclean-generic: clean-generic: diff --git a/doc/README.mysql b/doc/README.mysql deleted file mode 100644 index 84aeb24..0000000 --- a/doc/README.mysql +++ /dev/null @@ -1,95 +0,0 @@ -How to setup the MySQL database for GNUnet. - -NOTE: This db module does NOT work with mysql before 4.1 since we need -prepared statements. We are generally testing the code against MySQL -5.0 at this point. - -HIGHLIGHTS - -Pros - + On up-to-date hardware where mysql can be used comfortably, this - module will have better performance than the other db choices - (according to our tests). - + Its often possible to recover the mysql database from internal - inconsistencies. The other db choices do not support repair - (gnunet-check cannot fix problems internal to the dbmgr!). - For example, we have seen several cases where power failure - has ruined a gdbm database beyond repair. - + much faster (for one of the key benchmarks -- content migration - -- we have measure mysql taking 2s for an operation where - sqlite takes 150s). -Cons - - Memory usage (Comment: "I have 1G and it never caused me trouble") - - Manual setup - -MANUAL SETUP INSTRUCTIONS - - 1) in /etc/gnunet.conf, set - DATABASE = mysql - - 2) Then access mysql as root, - $ mysql -u root -p - and do the following. [You should replace $USER with the username - that will be running the gnunetd process]. - - CREATE DATABASE gnunet; - GRANT select,insert,update,delete,create,alter,drop,create temporary tables - ON gnunet.* TO $USER@localhost; - SET PASSWORD FOR $USER@localhost=PASSWORD('$the_password_you_like'); - FLUSH PRIVILEGES; - - 3) In the $HOME directory of $USER, create a ".my.cnf" file - with the following lines - - [client] - user=$USER - password=$the_password_you_like - - Thats it. Note that .my.cnf file is a security risk unless its on - a safe partition etc. The $HOME/.my.cnf can of course be a symbolic - link. Even greater security risk can be achieved by setting no - password for $USER. Luckily $USER has only priviledges to mess - up GNUnet's tables, nothing else (unless you give him more, - of course). - - 4) Still, perhaps you should briefly try if the DB connection - works. First, login as $USER. Then use, - - $ mysql -u $USER - mysql> use gnunet; - - If you get the message "Database changed" it probably works. - - [If you get "ERROR 2002: Can't connect to local MySQL server - through socket '/tmp/mysql.sock' (2)" it may be resolvable by - "ln -s /var/run/mysqld/mysqld.sock /tmp/mysql.sock" - so there may be some additional trouble depending on your mysql setup.] - - 5) If you want to run the testcases, you must create a second - database "gnunetcheck" with the same username and password. - This database will then be used for testing ("make check"). - - -REPAIRING TABLES - -- Its probably healthy to check your tables for inconsistencies - every now and then, especially after system crashes. -- If you get odd SEGVs on gnunetd startup, it might be that the mysql - databases have been corrupted. -- The tables can be verified/fixed in two ways; - 1) by shutting down mysqld (mandatory!) and running - # myisamchk -r *.MYI - in /var/lib/mysql/gnunet/ (or wherever the tables are stored). - Another repair command is "mysqlcheck". The usable command - may depend on your mysql build/version. Or, - 2) by executing - mysql> REPAIR TABLE gn090; - - -PROBLEMS? - -If you have problems related to the mysql module, your best friend is -probably the mysql manual. The first thing to check is that mysql is -basically operational, that you can connect to it, create tables, -issue queries etc. - diff --git a/doc/README.postgres b/doc/README.postgres deleted file mode 100644 index 2c96716..0000000 --- a/doc/README.postgres +++ /dev/null @@ -1,49 +0,0 @@ -How to setup the Postgres database for GNUnet. - -NOTE: This db module was developed for Postgres 8.3. I have no -idea what the minimum version that we require is exactly. - -HIGHLIGHTS - -Pros - + Easier to setup than MySQL - + Real database -Cons - - Quite slow - - Still some setup - -MANUAL SETUP INSTRUCTIONS - - 1) in /etc/gnunet.conf, set - DATABASE = postgres - - 2) Then access postgres to create a user; I had to do this to get - access and create a user: - # su - postgres - $ createuser - At this point, use the name of the user running gnunet - for the role, do not set it to superuser, allow the creation - of databases. - - 3) As that user, create a database (or two): - $ createdb gnunet - $ createdb gnunetcheck # this way you can run "make check" - - Thats it. - - 4) Still, perhaps you should briefly try if the DB connection - works. First, login as the user who will run gnunetd. Then use, - - $ psql gnunet # or gnunetcheck - gnunet=> \dt - - If, after you have started gnunetd at least once, you get a - gn090 table here, it probably works. - -PROBLEMS? - -If you have problems related to the postgres module, your best friend -is probably the postgres manual. The first thing to check is that -postgres is basically operational, that you can connect to it, create -tables, issue queries etc. (see step 4 above for details). - diff --git a/doc/man/Makefile.am b/doc/man/Makefile.am index c640460..dc68375 100644 --- a/doc/man/Makefile.am +++ b/doc/man/Makefile.am @@ -1,11 +1,19 @@ man_MANS = \ + gnunet.conf.5 \ gnunet-arm.1 \ + gnunet-ats.1 \ + gnunet-auto-share.1 \ + gnunet-config.1 \ gnunet-core.1 \ gnunet-directory.1 \ + gnunet-dns2gns.1 \ gnunet-download.1 \ gnunet-download-manager.1 \ + gnunet-ecc.1 \ gnunet-fs.1 \ gnunet-gns.1 \ + gnunet-gns-fcfsd.1 \ + gnunet-gns-proxy.1 \ gnunet-namestore.1 \ gnunet-nat-server.1 \ gnunet-peerinfo.1 \ @@ -16,6 +24,7 @@ man_MANS = \ gnunet-statistics.1 \ gnunet-transport.1 \ gnunet-unindex.1 \ + gnunet-uri.1 \ gnunet-vpn.1 EXTRA_DIST = ${man_MANS} diff --git a/doc/man/Makefile.in b/doc/man/Makefile.in index 76f2b02..44981d0 100644 --- a/doc/man/Makefile.in +++ b/doc/man/Makefile.in @@ -1,9 +1,9 @@ -# Makefile.in generated by automake 1.11.1 from Makefile.am. +# Makefile.in generated by automake 1.11.6 from Makefile.am. # @configure_input@ # Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, -# 2003, 2004, 2005, 2006, 2007, 2008, 2009 Free Software Foundation, -# Inc. +# 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Free Software +# Foundation, Inc. # This Makefile.in is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. @@ -15,6 +15,23 @@ @SET_MAKE@ VPATH = @srcdir@ +am__make_dryrun = \ + { \ + am__dry=no; \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + echo 'am--echo: ; @echo "AM" OK' | $(MAKE) -f - 2>/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } pkgdatadir = $(datadir)/@PACKAGE@ pkgincludedir = $(includedir)/@PACKAGE@ pkglibdir = $(libdir)/@PACKAGE@ @@ -39,14 +56,15 @@ DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 am__aclocal_m4_deps = $(top_srcdir)/m4/absolute-header.m4 \ $(top_srcdir)/m4/align.m4 $(top_srcdir)/m4/argz.m4 \ - $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/iconv.m4 \ - $(top_srcdir)/m4/lib-ld.m4 $(top_srcdir)/m4/lib-link.m4 \ - $(top_srcdir)/m4/lib-prefix.m4 $(top_srcdir)/m4/libcurl.m4 \ - $(top_srcdir)/m4/libgcrypt.m4 $(top_srcdir)/m4/libtool.m4 \ - $(top_srcdir)/m4/libunistring.m4 $(top_srcdir)/m4/ltdl.m4 \ - $(top_srcdir)/m4/ltoptions.m4 $(top_srcdir)/m4/ltsugar.m4 \ - $(top_srcdir)/m4/ltversion.m4 $(top_srcdir)/m4/lt~obsolete.m4 \ - $(top_srcdir)/m4/nls.m4 $(top_srcdir)/m4/po.m4 \ + $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/glib-2.0.m4 \ + $(top_srcdir)/m4/iconv.m4 $(top_srcdir)/m4/lib-ld.m4 \ + $(top_srcdir)/m4/lib-link.m4 $(top_srcdir)/m4/lib-prefix.m4 \ + $(top_srcdir)/m4/libcurl.m4 $(top_srcdir)/m4/libgcrypt.m4 \ + $(top_srcdir)/m4/libtool.m4 $(top_srcdir)/m4/libunistring.m4 \ + $(top_srcdir)/m4/ltdl.m4 $(top_srcdir)/m4/ltoptions.m4 \ + $(top_srcdir)/m4/ltsugar.m4 $(top_srcdir)/m4/ltversion.m4 \ + $(top_srcdir)/m4/lt~obsolete.m4 $(top_srcdir)/m4/nls.m4 \ + $(top_srcdir)/m4/pkg.m4 $(top_srcdir)/m4/po.m4 \ $(top_srcdir)/m4/progtest.m4 $(top_srcdir)/acinclude.m4 \ $(top_srcdir)/configure.ac am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ @@ -55,14 +73,19 @@ mkinstalldirs = $(install_sh) -d CONFIG_HEADER = $(top_builddir)/gnunet_config.h CONFIG_CLEAN_FILES = CONFIG_CLEAN_VPATH_FILES = -AM_V_GEN = $(am__v_GEN_$(V)) -am__v_GEN_ = $(am__v_GEN_$(AM_DEFAULT_VERBOSITY)) +AM_V_GEN = $(am__v_GEN_@AM_V@) +am__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@) am__v_GEN_0 = @echo " GEN " $@; -AM_V_at = $(am__v_at_$(V)) -am__v_at_ = $(am__v_at_$(AM_DEFAULT_VERBOSITY)) +AM_V_at = $(am__v_at_@AM_V@) +am__v_at_ = $(am__v_at_@AM_DEFAULT_V@) am__v_at_0 = @ SOURCES = DIST_SOURCES = +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac am__vpath_adj_setup = srcdirstrip=`echo "$(srcdir)" | sed 's|.|.|g'`; am__vpath_adj = case $$p in \ $(srcdir)/*) f=`echo "$$p" | sed "s|^$$srcdirstrip/||"`;; \ @@ -84,8 +107,15 @@ am__nobase_list = $(am__nobase_strip_setup); \ am__base_list = \ sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \ sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g' +am__uninstall_files_from_dir = { \ + test -z "$$files" \ + || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \ + || { echo " ( cd '$$dir' && rm -f" $$files ")"; \ + $(am__cd) "$$dir" && rm -f $$files; }; \ + } man1dir = $(mandir)/man1 -am__installdirs = "$(DESTDIR)$(man1dir)" +am__installdirs = "$(DESTDIR)$(man1dir)" "$(DESTDIR)$(man5dir)" +man5dir = $(mandir)/man5 NROFF = nroff MANS = $(man_MANS) DISTFILES = $(DIST_COMMON) $(DIST_SOURCES) $(TEXINFOS) $(EXTRA_DIST) @@ -124,6 +154,10 @@ EXEEXT = @EXEEXT@ EXT_LIBS = @EXT_LIBS@ EXT_LIB_PATH = @EXT_LIB_PATH@ FGREP = @FGREP@ +GLIB_CFLAGS = @GLIB_CFLAGS@ +GLIB_GENMARSHAL = @GLIB_GENMARSHAL@ +GLIB_LIBS = @GLIB_LIBS@ +GLIB_MKENUMS = @GLIB_MKENUMS@ GMSGFMT = @GMSGFMT@ GMSGFMT_015 = @GMSGFMT_015@ GNUNETDNS_GROUP = @GNUNETDNS_GROUP@ @@ -134,6 +168,7 @@ GN_LIBINTL = @GN_LIBINTL@ GN_LIB_LDFLAGS = @GN_LIB_LDFLAGS@ GN_PLUGIN_LDFLAGS = @GN_PLUGIN_LDFLAGS@ GN_USER_HOME_DIR = @GN_USER_HOME_DIR@ +GOBJECT_QUERY = @GOBJECT_QUERY@ GREP = @GREP@ HAVE_LIBUNISTRING = @HAVE_LIBUNISTRING@ INCLTDL = @INCLTDL@ @@ -156,6 +191,8 @@ LIBCURL_CPPFLAGS = @LIBCURL_CPPFLAGS@ LIBGCRYPT_CFLAGS = @LIBGCRYPT_CFLAGS@ LIBGCRYPT_CONFIG = @LIBGCRYPT_CONFIG@ LIBGCRYPT_LIBS = @LIBGCRYPT_LIBS@ +LIBGTOP_CFLAGS = @LIBGTOP_CFLAGS@ +LIBGTOP_LIBS = @LIBGTOP_LIBS@ LIBICONV = @LIBICONV@ LIBINTL = @LIBINTL@ LIBLTDL = @LIBLTDL@ @@ -177,6 +214,7 @@ LT_CONFIG_H = @LT_CONFIG_H@ LT_DLLOADERS = @LT_DLLOADERS@ LT_DLPREOPEN = @LT_DLPREOPEN@ MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ MKDIR_P = @MKDIR_P@ MONKEYPREFIX = @MONKEYPREFIX@ MSGFMT = @MSGFMT@ @@ -186,6 +224,7 @@ MYSQL_CPPFLAGS = @MYSQL_CPPFLAGS@ MYSQL_LDFLAGS = @MYSQL_LDFLAGS@ NM = @NM@ NMEDIT = @NMEDIT@ +NSS_DIR = @NSS_DIR@ OBJC = @OBJC@ OBJCDEPMODE = @OBJCDEPMODE@ OBJCFLAGS = @OBJCFLAGS@ @@ -201,6 +240,7 @@ PACKAGE_TARNAME = @PACKAGE_TARNAME@ PACKAGE_URL = @PACKAGE_URL@ PACKAGE_VERSION = @PACKAGE_VERSION@ PATH_SEPARATOR = @PATH_SEPARATOR@ +PKG_CONFIG = @PKG_CONFIG@ POSTGRES_CPPFLAGS = @POSTGRES_CPPFLAGS@ POSTGRES_LDFLAGS = @POSTGRES_LDFLAGS@ POSUB = @POSUB@ @@ -232,6 +272,7 @@ abs_builddir = @abs_builddir@ abs_srcdir = @abs_srcdir@ abs_top_builddir = @abs_top_builddir@ abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ ac_ct_CC = @ac_ct_CC@ ac_ct_CXX = @ac_ct_CXX@ ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ @@ -254,6 +295,7 @@ datarootdir = @datarootdir@ docdir = @docdir@ dvidir = @dvidir@ exec_prefix = @exec_prefix@ +gitcommand = @gitcommand@ host = @host@ host_alias = @host_alias@ host_cpu = @host_cpu@ @@ -267,7 +309,6 @@ libdir = @libdir@ libexecdir = @libexecdir@ localedir = @localedir@ localstatedir = @localstatedir@ -lt_ECHO = @lt_ECHO@ ltdl_LIBOBJS = @ltdl_LIBOBJS@ ltdl_LTLIBOBJS = @ltdl_LTLIBOBJS@ mandir = @mandir@ @@ -285,6 +326,7 @@ sbindir = @sbindir@ sharedstatedir = @sharedstatedir@ srcdir = @srcdir@ subdirs = @subdirs@ +svnversioncommand = @svnversioncommand@ sys_symbol_underscore = @sys_symbol_underscore@ sysconfdir = @sysconfdir@ target = @target@ @@ -296,13 +338,21 @@ top_build_prefix = @top_build_prefix@ top_builddir = @top_builddir@ top_srcdir = @top_srcdir@ man_MANS = \ + gnunet.conf.5 \ gnunet-arm.1 \ + gnunet-ats.1 \ + gnunet-auto-share.1 \ + gnunet-config.1 \ gnunet-core.1 \ gnunet-directory.1 \ + gnunet-dns2gns.1 \ gnunet-download.1 \ gnunet-download-manager.1 \ + gnunet-ecc.1 \ gnunet-fs.1 \ gnunet-gns.1 \ + gnunet-gns-fcfsd.1 \ + gnunet-gns-proxy.1 \ gnunet-namestore.1 \ gnunet-nat-server.1 \ gnunet-peerinfo.1 \ @@ -313,6 +363,7 @@ man_MANS = \ gnunet-statistics.1 \ gnunet-transport.1 \ gnunet-unindex.1 \ + gnunet-uri.1 \ gnunet-vpn.1 EXTRA_DIST = ${man_MANS} @@ -357,11 +408,18 @@ clean-libtool: -rm -rf .libs _libs install-man1: $(man_MANS) @$(NORMAL_INSTALL) - test -z "$(man1dir)" || $(MKDIR_P) "$(DESTDIR)$(man1dir)" - @list=''; test -n "$(man1dir)" || exit 0; \ - { for i in $$list; do echo "$$i"; done; \ - l2='$(man_MANS)'; for i in $$l2; do echo "$$i"; done | \ - sed -n '/\.1[a-z]*$$/p'; \ + @list1=''; \ + list2='$(man_MANS)'; \ + test -n "$(man1dir)" \ + && test -n "`echo $$list1$$list2`" \ + || exit 0; \ + echo " $(MKDIR_P) '$(DESTDIR)$(man1dir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(man1dir)" || exit 1; \ + { for i in $$list1; do echo "$$i"; done; \ + if test -n "$$list2"; then \ + for i in $$list2; do echo "$$i"; done \ + | sed -n '/\.1[a-z]*$$/p'; \ + fi; \ } | while read p; do \ if test -f $$p; then d=; else d="$(srcdir)/"; fi; \ echo "$$d$$p"; echo "$$p"; \ @@ -390,9 +448,50 @@ uninstall-man1: sed -n '/\.1[a-z]*$$/p'; \ } | sed -e 's,.*/,,;h;s,.*\.,,;s,^[^1][0-9a-z]*$$,1,;x' \ -e 's,\.[0-9a-z]*$$,,;$(transform);G;s,\n,.,'`; \ - test -z "$$files" || { \ - echo " ( cd '$(DESTDIR)$(man1dir)' && rm -f" $$files ")"; \ - cd "$(DESTDIR)$(man1dir)" && rm -f $$files; } + dir='$(DESTDIR)$(man1dir)'; $(am__uninstall_files_from_dir) +install-man5: $(man_MANS) + @$(NORMAL_INSTALL) + @list1=''; \ + list2='$(man_MANS)'; \ + test -n "$(man5dir)" \ + && test -n "`echo $$list1$$list2`" \ + || exit 0; \ + echo " $(MKDIR_P) '$(DESTDIR)$(man5dir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(man5dir)" || exit 1; \ + { for i in $$list1; do echo "$$i"; done; \ + if test -n "$$list2"; then \ + for i in $$list2; do echo "$$i"; done \ + | sed -n '/\.5[a-z]*$$/p'; \ + fi; \ + } | while read p; do \ + if test -f $$p; then d=; else d="$(srcdir)/"; fi; \ + echo "$$d$$p"; echo "$$p"; \ + done | \ + sed -e 'n;s,.*/,,;p;h;s,.*\.,,;s,^[^5][0-9a-z]*$$,5,;x' \ + -e 's,\.[0-9a-z]*$$,,;$(transform);G;s,\n,.,' | \ + sed 'N;N;s,\n, ,g' | { \ + list=; while read file base inst; do \ + if test "$$base" = "$$inst"; then list="$$list $$file"; else \ + echo " $(INSTALL_DATA) '$$file' '$(DESTDIR)$(man5dir)/$$inst'"; \ + $(INSTALL_DATA) "$$file" "$(DESTDIR)$(man5dir)/$$inst" || exit $$?; \ + fi; \ + done; \ + for i in $$list; do echo "$$i"; done | $(am__base_list) | \ + while read files; do \ + test -z "$$files" || { \ + echo " $(INSTALL_DATA) $$files '$(DESTDIR)$(man5dir)'"; \ + $(INSTALL_DATA) $$files "$(DESTDIR)$(man5dir)" || exit $$?; }; \ + done; } + +uninstall-man5: + @$(NORMAL_UNINSTALL) + @list=''; test -n "$(man5dir)" || exit 0; \ + files=`{ for i in $$list; do echo "$$i"; done; \ + l2='$(man_MANS)'; for i in $$l2; do echo "$$i"; done | \ + sed -n '/\.5[a-z]*$$/p'; \ + } | sed -e 's,.*/,,;h;s,.*\.,,;s,^[^5][0-9a-z]*$$,5,;x' \ + -e 's,\.[0-9a-z]*$$,,;$(transform);G;s,\n,.,'`; \ + dir='$(DESTDIR)$(man5dir)'; $(am__uninstall_files_from_dir) tags: TAGS TAGS: @@ -447,7 +546,7 @@ check-am: all-am check: check-am all-am: Makefile $(MANS) installdirs: - for dir in "$(DESTDIR)$(man1dir)"; do \ + for dir in "$(DESTDIR)$(man1dir)" "$(DESTDIR)$(man5dir)"; do \ test -z "$$dir" || $(MKDIR_P) "$$dir"; \ done install: install-am @@ -460,10 +559,15 @@ install-am: all-am installcheck: installcheck-am install-strip: - $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ - install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ - `test -z '$(STRIP)' || \ - echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi mostlyclean-generic: clean-generic: @@ -511,7 +615,7 @@ install-info: install-info-am install-info-am: -install-man: install-man1 +install-man: install-man1 install-man5 install-pdf: install-pdf-am @@ -541,7 +645,7 @@ ps-am: uninstall-am: uninstall-man -uninstall-man: uninstall-man1 +uninstall-man: uninstall-man1 uninstall-man5 .MAKE: install-am install-strip @@ -551,11 +655,12 @@ uninstall-man: uninstall-man1 install-data install-data-am install-dvi install-dvi-am \ install-exec install-exec-am install-html install-html-am \ install-info install-info-am install-man install-man1 \ - install-pdf install-pdf-am install-ps install-ps-am \ - install-strip installcheck installcheck-am installdirs \ - maintainer-clean maintainer-clean-generic mostlyclean \ - mostlyclean-generic mostlyclean-libtool pdf pdf-am ps ps-am \ - uninstall uninstall-am uninstall-man uninstall-man1 + install-man5 install-pdf install-pdf-am install-ps \ + install-ps-am install-strip installcheck installcheck-am \ + installdirs maintainer-clean maintainer-clean-generic \ + mostlyclean mostlyclean-generic mostlyclean-libtool pdf pdf-am \ + ps ps-am uninstall uninstall-am uninstall-man uninstall-man1 \ + uninstall-man5 # Tell versions [3.59,3.63) of GNU make to not export all variables. diff --git a/doc/man/gnunet-arm.1 b/doc/man/gnunet-arm.1 index 86a748e..1fbfa41 100644 --- a/doc/man/gnunet-arm.1 +++ b/doc/man/gnunet-arm.1 @@ -17,7 +17,7 @@ gnunet\-arm \- control GNUnet services Use the configuration file FILENAME. .B .IP "\-e, \-\-end" -Shutdown all GNUnet services (including ARM itself). Running "gnunet-arm -e" is the usual way to shutdown a GNUnet peer. +Shutdown all GNUnet services (including ARM itself). Running "gnunet-arm \-e" is the usual way to shutdown a GNUnet peer. .B .IP "\-h, \-\-help" Print short help on options. @@ -32,7 +32,7 @@ Starts the specified SERVICE if it is not already running. More specifically, t Stop the specified SERVICE if it is running. While this will kill the service right now, the service may be restarted immediately if other services depend on it (service is then started 'on-demand'). If the service used to be a 'default' service, its default-service status will be revoked. If the service was not a default service, it will just be (temporarily) stopped, but could be re-started on-demand at any time. .B .IP "\-s, \-\-start" -Start all GNUnet default services on this system (and also ARM). Naturally, if a service is demanded by a default service, it will then also be started. Running "gnunet-arm -s" is the usual way to start a GNUnet peer. +Start all GNUnet default services on this system (and also ARM). Naturally, if a service is demanded by a default service, it will then also be started. Running "gnunet-arm \-s" is the usual way to start a GNUnet peer. .B .IP "\-I, \-\-info" List all running services. diff --git a/doc/man/gnunet-ats.1 b/doc/man/gnunet-ats.1 new file mode 100644 index 0000000..c143f7a --- /dev/null +++ b/doc/man/gnunet-ats.1 @@ -0,0 +1,64 @@ +.TH GNUNET\-ATS 1 "Oct 31, 2012" "GNUnet" + +.SH NAME +gnunet\-ats \- display information about transport resource allocation + +.SH SYNOPSIS +.B gnunet\-ats +.RI [ options ] +.br + +.SH DESCRIPTION +\fBgnunet\-ats\fP can be used to display information about the GNUnet's +transport selection mechanism. It shows information about the +addresses and the assigned input and output bandwidth. + +.SH OPTIONS +.B +.IP "\-a, \-\-aa" +List all addresses currently known to ats. +.B +.IP "\-c FILENAME, \-\-config=FILENAME" +Use the configuration file FILENAME. +.B +.IP "\-h, \-\-help" +Print short help on options. +.B +.IP "\-i, \-\-id=PEERID" +Print information for a specific peer identity only +.B +.IP "\-k, \-\-value=VALUE" +Value to set for when changing preference values +.B +.IP "\-L LOGLEVEL, \-\-loglevel=LOGLEVEL" +Use LOGLEVEL for logging. Valid values are DEBUG, INFO, WARNING and ERROR. +.B +.IP "\-m, \-\-monitor" +Monitor changes to the bandwidth assignments continously +.B +.IP "\-n, \-\-numeric" +Do not resolve IP addresses to hostnames +.B +.IP "\-k, \-\-preference=E" +Set preference values, -i, -k and -t required +.B +.IP "\-q, \-\-quotas" +Print quotas for all network types +.B +.IP "\-t, \-\-type=VALUE" +Preference type to change: latency | bandwidth +.B +.IP "\-u, \-\-used" +Print addresses actively used only +.B +.IP "\-V, \-\-verbose" +Print verbose output (include ATS address properties) +.B +.IP "\-v, \-\-version" +Print GNUnet version number. + +.SH BUGS +Report bugs by using Mantis or by sending electronic mail to + +.SH SEE ALSO +gnunet\-transport(1) diff --git a/doc/man/gnunet-auto-share.1 b/doc/man/gnunet-auto-share.1 new file mode 100644 index 0000000..6373da2 --- /dev/null +++ b/doc/man/gnunet-auto-share.1 @@ -0,0 +1,86 @@ +.TH GNUNET\-AUTO\-SHARE "1" "18 Jun 2012" "GNUnet" +.SH NAME +gnunet\-auto\-share \- a command line tool to automatically share an entire directory with other users +.SH SYNOPSIS +.B gnunet\-auto\-share +[\fIOPTIONS\fR] DIRNAME +.SH DESCRIPTION +.PP +In order to share files with other GNUnet users, the files must first be made available to GNUnet. This tool can be used to automatically share all files from a certain directory. The program will periodically scan the directory for changes and publish files that are new or that changed on GNUnet. Which files have already been shared is remembered in a ".auto-share" file in the shared directory. You can run the tool by hand or automatically by adding the respective options to your configuration. gnunet\-auto\-share has many options in common with gnunet\-publish, but can only be used to index files. +.PP +You can use automatic meta\-data extraction (based on libextractor). +.PP + +\fB\-c \fIFILENAME\fR, \fB\-\-config=FILENAME\fR +Use alternate config file (if this option is not specified, the default is ~/.gnunet/gnunet.conf). + +.TP +\fB\-D\fR, \fB\-\-disable\-extractor\fR +Disable use of GNU libextractor for finding additional keywords and metadata. + +.TP +\fB\-h\fR, \fB\-\-help\fR +Print a brief help page with all the options. + +.TP +\fB\-L \fILOGLEVEL\fR, \fB\-\-loglevel=\fILOGLEVEL\fR +Change the loglevel. Possible values for LOGLEVEL are +ERROR, WARNING, INFO and DEBUG. + +.TP +\fB\-p \fIPRIORITY\fR, \fB\-\-prio=\fIPRIORITY\fR +Executive summary: You probably don't need it. + +Set the priority of the published content (default: 365). If the local database is full, GNUnet will discard the content with the lowest ranking. Note that ranks change over time depending on popularity. The default should be high enough to preserve the locally published content in favor of content that migrates from other peers. + +.TP +\fB\-r \fILEVEL\fR, \fB\-\-replication=\fILEVEL\fR +Set the desired replication level. If CONTENT_PUSHING is set to YES, GNUnet will push each block (for the file) LEVEL times to other peers before doing normal "random" replication of all content. This option can be used to push some content out into the network harder. Note that pushing content LEVEL times into the network does not guarantee that there will actually be LEVEL replicas. + +.TP +\fB\-v\fR, \fB\-\-version\fR +Print the version number. + +.TP +\fB\-V\fR, \fB\-\-verbose\fR +Be verbose. Using this option causes gnunet\-publish to print progress information and at the end the file identification that can be used to download the file from GNUnet. + + +.SH SETTING ANONYMITY LEVEL + +The \fB\-a\fR option can be used to specify additional anonymity constraints. If set to 0, GNUnet will publish the file non-anonymously and in fact sign the advertisement for the file using your peer's private key. This will allow other users to download the file as fast as possible, including using non-anonymous methods (DHT, direct transfer). If you set it to 1 (default), you use the standard anonymous routing algorithm (which does not explicitly leak your identity). However, a powerful adversary may still be able to perform traffic analysis (statistics) to over time infer data about your identity. You can gain better privacy by specifying a higher level of anonymity, which increases the amount of cover traffic your own traffic will get, at the expense of performance. Note that regardless of the anonymity level you choose, peers that cache content in the network always use anonymity level 1. + +The definition of the ANONYMITY LEVEL is the following. 0 means no anonymity is required. Otherwise a value of 'v' means that 1 out of v bytes of "anonymous" traffic can be from the local user, leaving 'v-1' bytes of cover traffic per byte on the wire. Thus, if GNUnet routes n bytes of messages from foreign peers (using anonymous routing), it may originate n/(v-1) bytes of data in the same time\-period. The time\-period is twice the average delay that GNUnet defers forwarded queries. + +The default is 1 and this should be fine for most users. Also notice that if you choose very large values, you may end up having no throughput at all, especially if many of your fellow GNUnet\-peers all do the same. + + +.SH EXAMPLES +.PP + +\fBBasic example\fR + +Share a directory "$HOME/gnunet\-share/": + + # gnunet\-auto\-share $HOME/gnunet\-share/ & + + +\fBBasic configuration\fR + +Share a directory "$HOME/gnunet\-share/": + + [ARM] + DEFAULTSERVICES = gnunet-auto-share # other default services here + + [gnunet-auto-share] + OPTIONS = $HOME/gnunet\-share + + +.SH FILES +.TP +~/.gnunet/gnunet.conf +GNUnet configuration file +.SH "REPORTING BUGS" +Report bugs to or by sending electronic mail to +.SH "SEE ALSO" +\fBgnunet\-fs\-gtk\fP(1), \fBgnunet\-publish\fP(1), \fBgnunet\-search\fP(1), \fBgnunet\-download\fP(1), \fBgnunet.conf\fP(5), \fBextract\fP(1) diff --git a/doc/man/gnunet-config.1 b/doc/man/gnunet-config.1 new file mode 100644 index 0000000..3a7fa62 --- /dev/null +++ b/doc/man/gnunet-config.1 @@ -0,0 +1,43 @@ +.TH GNUNET\-CONFIG 1 "Jul 15, 2012" "GNUnet" + +.SH NAME +gnunet\-config \- manipulate GNUnet configuration files + +.SH SYNOPSIS +.B gnunet\-config +.RI [ options ] +.br + +.SH DESCRIPTION +\fBgnunet\-config\fP can be used to read or modify GNUnet configuration files. + +.SH OPTIONS +.B +.IP "\-f, \-\-filename" +When accessing a specific option using \-s and \-o, perform expansions as if the value represents a filename. +.B +.IP "\-s SECTION, \-\-section=SECTION" +Which configuration section should be accessed or edited. Required option. +.B +.IP "\-o OPTION, \-\-option=OPTION" +Which configuration option should be accessed or edited. Required to set a value. If not given, all values of a given section will be printed in the format "OPTION = VALUE". +.B +.IP "\-V VALUE, \-\-value VALUE" +Configuration value to store in the given section under the given option. Must only be given together with \-s and \-o options. +.B +.IP "\-c FILENAME, \-\-config=FILENAME" +Use the configuration file FILENAME. +.B +.IP "\-h, \-\-help" +Print short help on options. +.B +.IP "\-L LOGLEVEL, \-\-loglevel=LOGLEVEL" +Use LOGLEVEL for logging. Valid values are DEBUG, INFO, WARNING and ERROR. +.B +.IP "\-v, \-\-version" +Print GNUnet version number. + + +.SH BUGS +Report bugs by using Mantis or by sending electronic mail to + diff --git a/doc/man/gnunet-dns2gns.1 b/doc/man/gnunet-dns2gns.1 new file mode 100644 index 0000000..f60f40e --- /dev/null +++ b/doc/man/gnunet-dns2gns.1 @@ -0,0 +1,46 @@ +.TH GNUNET\-DNS2GNS 1 "Oct 25, 2012" "GNUnet" + +.SH NAME +gnunet\-dns2gns \- run a DNS-to-GNS proxy + +.SH SYNOPSIS +.B gnunet\-dns2gns +.RI [ options ] +.br + +.SH DESCRIPTION +Most users will not want to run an DNS to GADS proxy/gateway and thus will not need this program. + +\fBgnunet\-dns2gns\fP runs a DNS resolver which delegates requests to the ".gads" and ".zkey" zones to GADS. All other requests are forwarded to DNS. This DNS proxy is useful for enabling non-personalized GADS\-resolution to an entire network or to offer GADS\-resolution to DNS users. + +A DNS\-to\-GNS proxy using gnunet\-dns2gns is available at ".zkey.eu" + +.SH OPTIONS +.B +.IP "\-c FILENAME, \-\-config=FILENAME" +Use the configuration file FILENAME. +.B +.IP "\-d IP, \-\-dns=IP" +IP address of a recursive DNS resolver that should be used for non-GADS hostnames. +.B +.IP "\-f NAME, \-\-fcfs=NAME" +Authoritative FCFS suffix to use. This is the name under which the local zone's names will be made available. Default is "fcfs.zkey.eu". +.B +.IP "\-h, \-\-help" +Print short help on options. +.B +.IP "\-L LOGLEVEL, \-\-loglevel=LOGLEVEL" +Use LOGLEVEL for logging. Valid values are DEBUG, INFO, WARNING and ERROR. +.B +.IP "\-s SUFFIX, \-\-suffix=SUFFIX" +Authoritative DNS suffix to use. This is the name under which the GADS ".zkey" zone is mapped into the DNS namespace. Default is "zkey.eu". +.B +.IP "\-v, \-\-version" +Print GNUnet version number. + + +.SH BUGS +Report bugs by using Mantis or by sending electronic mail to + +.SH SEE ALSO +gnunet\-gns\-fcfs(1), gnunet\-gns(1) diff --git a/doc/man/gnunet-download.1 b/doc/man/gnunet-download.1 index 9754cb0..a2d1aad 100644 --- a/doc/man/gnunet-download.1 +++ b/doc/man/gnunet-download.1 @@ -47,7 +47,7 @@ set the maximum number of parallel requests that is allowed. If multiple files .TP \fB\-R\fR, \fB\-\-recursive\fR -download directories recursively (and in parallel); note that the URI must belong to a GNUnet directory and that the filename given must end with a '/' \-\- otherwise, only the file corresponding to the URI will be downloaded. Note that in addition to using '-R', you must also specify a filename ending in '.gnd' so that the code realizes that the top-level file is a directory (since we have no meta data). +download directories recursively (and in parallel); note that the URI must belong to a GNUnet directory and that the filename given must end with a '/' \-\- otherwise, only the file corresponding to the URI will be downloaded. Note that in addition to using '\-R', you must also specify a filename ending in '.gnd' so that the code realizes that the top-level file is a directory (since we have no meta data). .TP \fB\-v\fR, \fB\-\-version\fR diff --git a/doc/man/gnunet-ecc.1 b/doc/man/gnunet-ecc.1 new file mode 100644 index 0000000..943f85e --- /dev/null +++ b/doc/man/gnunet-ecc.1 @@ -0,0 +1,43 @@ +.TH GNUNET\-ECC 1 "Mar 15, 2012" "GNUnet" + +.SH NAME +gnunet\-ecc \- manipulate GNUnet ECC key files + +.SH SYNOPSIS +.B gnunet\-ecc +.RI [ options ] FILENAME +.br + +.SH DESCRIPTION +\fBgnunet\-ecc\fP can be used to create an ECC private key and to print the corresponding public key. You must specify a filename containing an ECC private key in GNUnet format as an argument. If the file does not exist, gnunet\-ecc will create a key. This may then take a while. If the option \-p is given, the corresponding public key will be printed to the console. + +.SH OPTIONS +.B +.IP "\-g COUNT, \-\-generate-keys=COUNT" +Create COUNT public-private key pairs and write them to FILENAME. Used for creating a file for testing. +.B +.IP "\-p, \-\-print-public-key" +Print the corresponding public key to stdout. +.B +.IP "\-P, \-\-print-peer-identity" +Print the corresponding peer identity (hash of the public key) to stdout. This hash is used for the name of peers. +.B +.IP "\-s, \-\-print-short-identity" +Print the corresponding short hash (256-bit hash of the public key) to stdout. This hash is used for names in the zkey zone. +.B +.IP "\-c FILENAME, \-\-config=FILENAME" +Use the configuration file FILENAME. +.B +.IP "\-h, \-\-help" +Print short help on options. +.B +.IP "\-L LOGLEVEL, \-\-loglevel=LOGLEVEL" +Use LOGLEVEL for logging. Valid values are DEBUG, INFO, WARNING and ERROR. +.B +.IP "\-v, \-\-version" +Print GNUnet version number. + + +.SH BUGS +Report bugs by using Mantis or by sending electronic mail to + diff --git a/doc/man/gnunet-gns-fcfsd.1 b/doc/man/gnunet-gns-fcfsd.1 new file mode 100644 index 0000000..fbd45e4 --- /dev/null +++ b/doc/man/gnunet-gns-fcfsd.1 @@ -0,0 +1,38 @@ +.TH GNUNET\-GNS-FCFSD 1 "Oct 25, 2012" "GNUnet" + +.SH NAME +gnunet\-gns-fcfsd \- HTTP server for GADS domain registration + +.SH SYNOPSIS +.B gnunet\-gns-fcfsd +.RI [ options ] +.br + +.SH DESCRIPTION +Most users will not want to run an FCFS\-zone and thus will not need this program. + +\fBgnunet\-gns-fcfsd\fP runs a web server where users can register names to be mapped to their GADS zone. Names are made available on a First Come First Served basis (hence fcfs). Registered names do not expire. The HTTP server is run on the port that is specified in the configuration file in section "[fcfsd]" under the name "HTTPPORT". The key of the zone in which the names are registered must be specified under the name "ZONEKEY" in the same section. It is possible to manage gnunet\-gns\-fcfsd using gnunet\-(service\-arm) by starting the daemon using "gnunet\-arm -i fcfsd" or by adding "fcfds" to the "DEFAULTSERVICES" option. + +An FCFS\-zone is run at http://gnunet.org/fcfs/. The respective zone key can be imported into an individual user's zone using "gnunet-gns-import.sh". GADS users are encouraged to register their zone with the gnunet.org FCFS authority. + +.SH OPTIONS +.B +.IP "\-c FILENAME, \-\-config=FILENAME" +Use the configuration file FILENAME. +.B +.IP "\-h, \-\-help" +Print short help on options. +.B +.IP "\-L LOGLEVEL, \-\-loglevel=LOGLEVEL" +Use LOGLEVEL for logging. Valid values are DEBUG, INFO, WARNING and ERROR. +.B +.IP "\-v, \-\-version" +Print GNUnet version number. + + +.SH BUGS +Report bugs by using Mantis or by sending electronic mail to + +.SH SEE ALSO +gnunet\-gns(1), gnunet\-gns\-proxy(1) + diff --git a/doc/man/gnunet-gns-proxy.1 b/doc/man/gnunet-gns-proxy.1 new file mode 100644 index 0000000..9b9f603 --- /dev/null +++ b/doc/man/gnunet-gns-proxy.1 @@ -0,0 +1,41 @@ +.TH GNUNET\-GNS\-PROXY 1 "Oct 25, 2012" "GNUnet" + +.SH NAME +gnunet\-gns\-proxy \- run a client side GNS SOCKS proxy + +.SH SYNOPSIS +.B gnunet\-gns\-proxy +.RI [ options ] +.br + +.SH DESCRIPTION +Most users will want to run this SOCKS proxy. It can be used in combination with browsers that support the SOCKS 4a protocol. + +The proxy will perform SSL authentication of GNS names and rewrite GNS enabled HTML content. To assert the validity of GNS names a local root CA certificate has to be generated that is used by the proxy. Thus "gnunet-gns-proxy-setup-ca" should be executed before the first launch of this proxy or the \-\-authority switch is used to specify an appropriate CA certificate that is already trusted by the browser. + +.SH OPTIONS +.B +.IP "\-c FILENAME, \-\-config=FILENAME" +Use the configuration file FILENAME. +.B +.IP "\-a AUTHORITY, \-\-authority=AUTHORITY" +Path to a PEM CA file that contains the certificate and private key of the CA to use to assert the validity of GNS names. The default port is specified in the configuration file for the gns service under "[gns-proxy]" PROXY_CACERT. +.B +.IP "\-p PORT, \-\-port=PORT" +The port this proxy should listen on. Default is 7777. +.B +.IP "\-h, \-\-help" +Print short help on options. +.B +.IP "\-L LOGLEVEL, \-\-loglevel=LOGLEVEL" +Use LOGLEVEL for logging. Valid values are DEBUG, INFO, WARNING and ERROR. +.B +.IP "\-v, \-\-version" +Print GNUnet version number. + + +.SH BUGS +Report bugs by using Mantis or by sending electronic mail to + +.SH SEE ALSO +gnunet\-gns(1) diff --git a/doc/man/gnunet-gns.1 b/doc/man/gnunet-gns.1 index 4d00c82..ef5a0f9 100644 --- a/doc/man/gnunet-gns.1 +++ b/doc/man/gnunet-gns.1 @@ -1,32 +1,56 @@ -.TH GNUNET\-GNS 1 "Mar 5, 2012" "GNUnet" +.TH GNUNET\-GNS 1 "Aug 8, 2012" "GNUnet" .SH NAME -gnunet\-gns \- manipulate GNUnet GNS zones +gnunet\-gns \- Access to GNUnet Name Service .SH SYNOPSIS .B gnunet\-gns -.RI [ options ] -z ZONEFILE +.RI [ options ] .br .SH DESCRIPTION -\fBgnunet\-gns\fP can be used to create and manipulate a GNS zone. +\fBgnunet\-gns\fP can be used to lookup and process GNUnet Name Service names. .SH OPTIONS .B +.IP "\-a NAME, \-\-authority=NAME" +Get the authority of a particular name. +For example the authority for "www.fcfs.gads" is "fcfs.gads". +.B .IP "\-c FILENAME, \-\-config=FILENAME" Use the configuration file FILENAME. .B +.IP "\-r, \-\-raw" +No unneeded output. +This is a quiet mode where only important information is displayed. +For example a lookup for an IP address will only yield the IP address, no +descriptive text. +.B +.IP "\-s NAME, \-\-shorten NAME" +Shorten GNUnet Name Service Name. +The service will try to shorten the delegation chain of the name if a "closer" +authority chain exists relative to your local root zone. +.B +.IP "\-t RRTYPE, \-\-type=RRTYPE" +Resource Record Type (RRTYPE) to look for. +Supported RRTYPE's are: A, AAAA, CNAME, NS, PKEY, PSEU, TLSA, SRV, SOA, MX, LEHO, VPN, REV, PTR, TXT + +Defaults to "A". +.B .IP "\-h, \-\-help" Print short help on options. .B .IP "\-L LOGLEVEL, \-\-loglevel=LOGLEVEL" Use LOGLEVEL for logging. Valid values are DEBUG, INFO, WARNING and ERROR. .B -.IP "\-s NAME, \-\-shorten=NAME" -GNS domain name to shorten +.IP "\-u NAME, \-\-lookup=NAME" +Name to lookup. +Resolve the specified name using the GNUnet Name System. .B .IP "\-v, \-\-version" Print GNUnet version number. +.B + .SH BUGS Report bugs by using Mantis or by sending electronic mail to diff --git a/doc/man/gnunet-namestore.1 b/doc/man/gnunet-namestore.1 index 4ecdbb0..f05db0a 100644 --- a/doc/man/gnunet-namestore.1 +++ b/doc/man/gnunet-namestore.1 @@ -40,6 +40,9 @@ Name of the record to add/delete/display .IP "\-t TYPE, \-\-type=TYPE" Type of the record to add/delete/display (i.e. "A", "AAAA", "NS", "PKEY", "MX" etc.) .B +.IP "\-u URI, \-\-uri=URI" +Add PKEY record from gnunet://gns/-URI to our zone; the record type is always PKEY, if no expiration is given FOREVER is used +.B .IP "\-v, \-\-version" Print GNUnet version number. .B diff --git a/doc/man/gnunet-peerinfo.1 b/doc/man/gnunet-peerinfo.1 index e2691b1..354fd05 100644 --- a/doc/man/gnunet-peerinfo.1 +++ b/doc/man/gnunet-peerinfo.1 @@ -17,12 +17,18 @@ gnunet\-peerinfo \- Display information about other peers. .IP "\-c FILENAME, \-\-config=FILENAME" Load config file (default: ~/.gnunet/gnunet.conf) .B +.IP "\-g, \-\-get\-hello +Output HELLO uri(s) +.B .IP "\-h, \-\-help" Print help page .B .IP "\-n, \-\-numeric" Disable resolution of IPs to hostnames .B +.IP "\-p, \-\-put\-hello=HELLO +Add given HELLO uri to the database +.B .IP "\-q, \-\-quiet" Do not print anything but the peer identities .B @@ -32,7 +38,7 @@ Print only our own identity (together with "\-q", this is the exact line that ot .IP "\-v, \-\-version" Print the version number .B -.IP "\-L LOGLEVEL, \-\-loglelvel=LOGLEVEL" +.IP "\-L LOGLEVEL, \-\-loglevel=LOGLEVEL" Set the loglevel diff --git a/doc/man/gnunet-publish.1 b/doc/man/gnunet-publish.1 index a189c74..467f45a 100644 --- a/doc/man/gnunet-publish.1 +++ b/doc/man/gnunet-publish.1 @@ -6,14 +6,12 @@ gnunet\-publish \- a command line interface for publishing new content into GNUn [\fIOPTIONS\fR] FILENAME .SH DESCRIPTION .PP -In order to share files with other GNUnet users, the files must first be made available to GNUnet. GNUnet does not automatically share all files from a certain directory. In fact, even files that are downloaded are not automatically shared. +In order to share files with other GNUnet users, the files must first be made available to GNUnet. GNUnet does not automatically share all files from a certain directory (however, you can do this with the gnunet\-auto\-share tool). In fact, even files that are downloaded are not automatically shared. .PP In order to start sharing files, the files must be added either using gnunet\-publish or a graphical interface such as gnunet\-fs\-gtk. The command line tool gnunet\-publish is more useful if many files are supposed to be added. gnunet\-publish can automatically publish batches of files, recursively publish directories, create directories that can be browsed within GNUnet and publish file lists in a namespace. When run on a directory, gnunet\-publish will always recursively publish all of the files in the directory. .PP gnunet\-publish can automatically extract keywords from the files that are shared. Users that want to download files from GNUnet use keywords to search for the appropriate content. You can disable keyword extraction with the \-D option. You can manually add keywords using the \-k option. The keywords are case\-sensitive. .PP -You can use automatic meta\-data extraction (based on libextractor) or the command\-line option \-m to specify meta-data. For the \-m option you need to use the form keyword\-type:value. For example, use "\-m os:Linux" to specify that the operating system is Linux. Common meta\-data types are "author name", "title" , "mimetype", "filename", "language", "subject" and "keywords". A full list can be obtained from the extract tool using the option \-\-list. The meta\-data is used to help users in searching for files on the network. -.PP In addition to searching for files by keyword, GNUnet allows organizing files into directories. With directories, the user only needs to find the directory in order to be able to download any of the files listed in the directory. Directories can contain pointers to other directories. .PP With gnunet\-publish, it is easy to create new directories simultaneously when adding the files. Simply pass the name of a directory instead of a file. @@ -127,7 +125,7 @@ Index a file COPYING with the keywords \fBgpl\fR and \fBtest\fR: Index a file COPYING with description "GNU License", mime-type "text/plain" and keywords \fBgpl\fR and \fBtest\fR: - # gnunet\-publish \-m "description:GNU License" \-k gpl \-k test -m "mimetype:text/plain" COPYING + # gnunet\-publish \-m "description:GNU License" \-k gpl \-k test \-m "mimetype:text/plain" COPYING \fBUsing directories\fR @@ -157,7 +155,7 @@ Recursively publish (\-n) /var/lib/mysql and build a matching directory structur Create a namespace entry 'root' in namespace MPAA-1 and announce that the next update will be called 'next': - # gnunet\-publish \-P MPAA-1 -t root \-N next noise.mp3 + # gnunet\-publish \-P MPAA-1 \-t root \-N next noise.mp3 Update the previous entry, do not allow any future updates: @@ -171,4 +169,4 @@ GNUnet configuration file .SH "REPORTING BUGS" Report bugs to or by sending electronic mail to .SH "SEE ALSO" -\fBgnunet\-fs\-gtk\fP(1), \fBgnunet\-pseudonym\fP(1), \fBgnunet\-search\fP(1), \fBgnunet\-download\fP(1), \fBgnunet.conf\fP(5), \fBextract\fP(1) +\fBgnunet\-auto\-share\fP(1), \fBgnunet\-fs\-gtk\fP(1), \fBgnunet\-pseudonym\fP(1), \fBgnunet\-search\fP(1), \fBgnunet\-download\fP(1), \fBgnunet.conf\fP(5), \fBextract\fP(1) diff --git a/doc/man/gnunet-rsa.1 b/doc/man/gnunet-rsa.1 index 46f24de..c61bc1f 100644 --- a/doc/man/gnunet-rsa.1 +++ b/doc/man/gnunet-rsa.1 @@ -13,6 +13,9 @@ gnunet\-rsa \- manipulate GNUnet RSA key files .SH OPTIONS .B +.IP "\-g COUNT, \-\-generate-keys=COUNT" +Create COUNT public-private key pairs and write them to FILENAME. Used for creating a file for testing. +.B .IP "\-p, \-\-print-public-key" Print the corresponding public key to stdout. .B diff --git a/doc/man/gnunet-search.1 b/doc/man/gnunet-search.1 index ccca75f..05ab275 100644 --- a/doc/man/gnunet-search.1 +++ b/doc/man/gnunet-search.1 @@ -47,8 +47,8 @@ Only search locally, do not forward requests to other peers. automatically terminate the search after receiving VALUE results. .TP -\fB\-t \fIVALUE\fR, \fB\-\-timeout=\fIVALUE\fR -Automatically timeout search after VALUE ms. Otherwise the search runs until gnunet\-search is aborted with CTRL\-C. +\fB\-t \fIDELAY\fR, \fB\-\-timeout=\fIDELAY\fR +Automatically timeout search after DELAY. The value given must be a number followed by a space and a time unit, for example "500 ms". Note that the quotes are required on the shell. Otherwise the search runs until gnunet\-search is aborted with CTRL\-C. .TP \fB\-v\fR, \fB\-\-version\fR @@ -76,12 +76,12 @@ Search results are printed by gnunet\-search like this: .ad l gnunet\-download \-o "COPYING" gnunet://fs/chk/HASH1.HASH2.SIZE - Description: The GNU Public License + Description: The GNU General Public License Mime-type: text/plain .ad b -The first line contains the command to run to download the file. The suggested filename in the example is COPYING. The GNUnet URI consists of the key and query hash of the file and finally the size of the file. After the command to download the file GNUnet will print meta\-data about the file as advertised in the search result, here "The GNU Public License" and the mime\-type (see the options for gnunet\-publish on how to supply meta-data by hand). +The first line contains the command to run to download the file. The suggested filename in the example is COPYING. The GNUnet URI consists of the key and query hash of the file and finally the size of the file. After the command to download the file GNUnet will print meta\-data about the file as advertised in the search result, here "The GNU General Public License" and the mime\-type (see the options for gnunet\-publish on how to supply meta-data by hand). .SH FILES .TP diff --git a/doc/man/gnunet-transport.1 b/doc/man/gnunet-transport.1 index cc1a022..45fd706 100644 --- a/doc/man/gnunet-transport.1 +++ b/doc/man/gnunet-transport.1 @@ -14,11 +14,14 @@ gnunet\-transport is a tool to access various functions of GNUnet's transport su \fB\-b\fR, \fB\-\-benchmark\fR measure how fast we are receiving data (from all connections). On exit, the data rate will be reported. Runs until aborted with CTRL-C. .TP +\fB\-C \fIPEER\fR, \fB\-\-connect=PEER\fR +peer to connect to (used in conjunction with \-p) +.TP \fB\-c \fIFILENAME\fR, \fB\-\-config=FILENAME\fR configuration file to use .TP -\fB\-C \fIPEER\fR, \fB\-\-connect=PEER\fR -peer to connect to (and to use for sending if used in conjunction with \-s) +\fB\-e \fB\-\-events\fR +provide information about all connect and disconnect events (continuously) .TP \fB\-h\fR, \fB\-\-help\fR print help page @@ -26,14 +29,20 @@ print help page \fB\-i\fR, \fB\-\-information\fR print information about our current connections (once) .TP +\fB\-L \fILOGLEVEL\fR, \fB\-\-loglevel=LOGLEVEL\fR +Change the loglevel. Possible values for LOGLEVEL are ERROR, WARNING, INFO and DEBUG. +.TP +\fB\-l \fILOGFILE\fR, \fB\-\-logfile=LOGFILE\fR +configure logging to write logs to LOGFILE +.TP \fB\-m\fR, \fB\-\-monitor\fR print information about our current connections (continuously) .TP -\fB\-L \fILOGLEVEL\fR, \fB\-\-loglevel=LOGLEVEL\fR -Change the loglevel. Possible values for LOGLEVEL are ERROR, WARNING, INFO and DEBUG. +\fB\-p \fIPEER\fR, \fB\-\-peer=PEER\fR +the peer identity .TP \fB\-s\fR, \fB\-\-send\fR -transmit (dummy) traffic as quickly as possible to the peer specified with the \-C option. The rate will still be limited by the quota(s) determined by the peers (ATS subsystem). Will run until CTRL\-C is pressed or until the connection to the other peer is disrupted. +transmit (dummy) traffic as quickly as possible to the peer specified with the \-p option. The rate will still be limited by the quota(s) determined by the peers (ATS subsystem). Will run until CTRL\-C is pressed or until the connection to the other peer is disrupted. .TP \fB\-t\fR, \fB\-\-test\fR test transport configuration. With this flag, the tool will check if each of the configured transport plugins has a working address. Plugins that do not have a listen port configured will be ignored. The test is performed with the help of an external server (by default running on gnunet.org) which tries to contact the local machine. The test can only work if the local GNUnet peer is not yet running. diff --git a/doc/man/gnunet-uri.1 b/doc/man/gnunet-uri.1 new file mode 100644 index 0000000..9eac68a --- /dev/null +++ b/doc/man/gnunet-uri.1 @@ -0,0 +1,30 @@ +.TH GNUNET\-URI 1 "Jun 26, 2012" "GNUnet" + +.SH NAME +gnunet\-uri \- invoke default handler for GNUnet URIs + +.SH SYNOPSIS +.B gnunet\-uri +.RI URI +.br + +.SH DESCRIPTION +\fBgnunet\-uri\fP can be used to invoke the correct tool to handle a GNUnet URI. GNUnet URIs have the format "gnunet://SUBSYSTEM/DETAILS" and thus the specific tool to handle the URI depends on the subsystem. gnunet\-uri will determine the correct tool (by looking for SUBSYSTEM in the configuration section "uri") and invoke it. + +.SH OPTIONS +.B +.IP "\-c FILENAME, \-\-config=FILENAME" +Use the configuration file FILENAME. +.B +.IP "\-h, \-\-help" +Print short help on options. +.B +.IP "\-L LOGLEVEL, \-\-loglevel=LOGLEVEL" +Use LOGLEVEL for logging. Valid values are DEBUG, INFO, WARNING and ERROR. +.B +.IP "\-v, \-\-version" +Print GNUnet version number. + + +.SH BUGS +Report bugs by using Mantis or by sending electronic mail to diff --git a/doc/man/gnunet-vpn.1 b/doc/man/gnunet-vpn.1 index ad5b9db..80b78ce 100644 --- a/doc/man/gnunet-vpn.1 +++ b/doc/man/gnunet-vpn.1 @@ -27,8 +27,8 @@ Display IP address only after the tunnel is fully connected. .IP "\-c FILENAME, \-\-config=FILENAME" Use the configuration file FILENAME. .B -.IP "\-d SEC, \-\-duration SEC" -The mapping should be established for SEC seconds. Default is 5 minutes. +.IP "\-d TIME, \-\-duration TIME" +The mapping should be established for TIME. The value given must be a number followed by a space and a time unit, for example "500 ms". Note that the quotes are required on the shell. Default is 5 minutes. .B .IP "\-h, \-\-help" Print short help on options. diff --git a/doc/man/gnunet.conf.5 b/doc/man/gnunet.conf.5 new file mode 100644 index 0000000..0d2f868 --- /dev/null +++ b/doc/man/gnunet.conf.5 @@ -0,0 +1,20 @@ +.TH GNUNET.CONF "5" "25 Oct 2012" "GNUnet" +.SH NAME +gnunet.conf \- GNUnet configuration file +.SH SYNOPSIS +~/.gnunet/gnunet.conf +.SH DESCRIPTION +.PP +A GNUnet setup typically consists of a a set of service processes run by a user "gnunet" and a set of user-interface processes run by a standard account. The service processes are usually started using "gnunet\-arm \-s". The default location for the configuration file is then "~gnunet/.gnunet/gnunet.conf"; however, as normal users also may need read-access to this configuration, you might want to instead put the service process configuration to "/etc/gnunet.conf". gnunet\-setup can be used to edit this configuration. The configuration for normal users is in "$HOME/.gnunet/gnunet.conf". The file does not have to exist, and there are no options that typically require manual configuration in this file. Note that while it is possible to run both sets of processes as the same user (and use one shared configuration file), this breaks some GNUnet components (GADS/GNS) and is generally not recommended. +.TP +The basic structure of the configuration file is the following. The file is split into sections. Every section begins with "[SECTIONNAME]" and contains a number of options of the form "OPTION=VALUE". Empty lines and lines beginning with a "#" are treated as comments. Almost all options are optional and the tools resort to reasonable defaults if they are not present. +.PP +Default values for all of the options can be found in the files in the "$GNUNET_PREFIX/share/gnunet/config.d/" directory. Note that only some of the options can be configured with gnunet\-setup, as for most options the default choice is all that should ever be needed by normal users. However, developers may find some of the other options of interest. +.SH FILES +.TP +~/.gnunet/gnunet.conf +GNUnet configuration file +.SH "REPORTING BUGS" +Report bugs by using Mantis or by sending electronic mail to +.SH "SEE ALSO" +\fBgnunet\-setup\fP(1), \fBgnunet\-arm\fP(1) diff --git a/gnunet_config.h b/gnunet_config.h index 0cbce52..a69ce0d 100644 --- a/gnunet_config.h +++ b/gnunet_config.h @@ -12,10 +12,16 @@ /* This is an Apple Darwin system */ /* #undef DARWIN */ +/* enable expensive heap statistics */ +#define ENABLE_HEAP_STATISTICS 0 + /* Define to 1 if translation of program messages to the user's native language is requested. */ #define ENABLE_NLS 1 +/* 1 if freed memory should be poisoned, 0 otherwise */ +#define ENABLE_POISONING 0 + /* enable workarounds used on Windows (only useful for test cases) */ #define ENABLE_WINDOWS_WORKAROUNDS 0 @@ -25,6 +31,9 @@ /* This is a FreeBSD system */ /* #undef FREEBSD */ +/* This is a GNU system */ +/* #undef GNU */ + /* Define to cull all logging calls */ /* #undef GNUNET_CULL_LOGGING */ @@ -77,9 +86,6 @@ /* Define to 1 if your system has a working `chown' function. */ #define HAVE_CHOWN 1 -/* Define to 1 if you have the `clock_gettime' function. */ -/* #undef HAVE_CLOCK_GETTIME */ - /* Define to 1 if you have the `closedir' function. */ #define HAVE_CLOSEDIR 1 @@ -120,9 +126,6 @@ /* Define to 1 if you don't have `vprintf' but do have `_doprnt.' */ /* #undef HAVE_DOPRNT */ -/* Define to 1 if you have the `dup2' function. */ -#define HAVE_DUP2 1 - /* Define if you have the _dyld_func_lookup function. */ /* #undef HAVE_DYLD */ @@ -135,20 +138,17 @@ /* Define to 1 if the system has the type `error_t'. */ #define HAVE_ERROR_T 1 +/* Define to 1 if you have the header file. */ +#define HAVE_EXECINFO_H 1 + /* Define to 1 if you have the header file. */ #define HAVE_EXTRACTOR_H 1 /* Define to 1 if you have the header file. */ #define HAVE_FCNTL_H 1 -/* Define to 1 if you have the `fdatasync' function. */ -#define HAVE_FDATASYNC 1 - -/* Define to 1 if you have the `floor' function. */ -/* #undef HAVE_FLOOR */ - /* Define to 1 if you have the `fork' function. */ -/* #undef HAVE_FORK */ +#define HAVE_FORK 1 /* Define to 1 if you have the `freeifaddrs' function. */ #define HAVE_FREEIFADDRS 1 @@ -156,15 +156,9 @@ /* Define to 1 if fseeko (and presumably ftello) exists and is declared. */ #define HAVE_FSEEKO 1 -/* Define to 1 if you have the `ftruncate' function. */ -#define HAVE_FTRUNCATE 1 - /* Define this if getaddrinfo() is available */ #define HAVE_GETADDRINFO 1 -/* Define to 1 if you have the `getcwd' function. */ -#define HAVE_GETCWD 1 - /* Define this if gethostbyaddr() is available */ #define HAVE_GETHOSTBYADDR 1 @@ -192,14 +186,20 @@ /* Define to 1 if you have the `getpeerucred' function. */ /* #undef HAVE_GETPEERUCRED */ +/* Define to 1 if you have the `getresgid' function. */ +#define HAVE_GETRESGID 1 + +/* Define to 1 if you have the `getrlimit' function. */ +#define HAVE_GETRLIMIT 1 + /* Define to 1 if you have the `getrusage' function. */ #define HAVE_GETRUSAGE 1 /* Define if the GNU gettext() function is already present or preinstalled. */ #define HAVE_GETTEXT 1 -/* Define to 1 if you have the `gettimeofday' function. */ -#define HAVE_GETTIMEOFDAY 1 +/* Have glib2 */ +#define HAVE_GLIB2 1 /* Define to 1 if you have the header file. */ #define HAVE_GLPK_H 1 @@ -207,11 +207,11 @@ /* Define to 1 if `presolve' is a member of `glp_iocp'. */ #define HAVE_GLP_IOCP_PRESOLVE 1 -/* Define to 1 if you have the `gmtime' function. */ -#define HAVE_GMTIME 1 +/* We have gnutls */ +#define HAVE_GNUTLS true -/* Define to 1 if you have the `gmtime_r' function. */ -#define HAVE_GMTIME_R 1 +/* Define to 1 if you have the header file. */ +#define HAVE_GNUTLS_ABSTRACT_H 1 /* Define if you have the iconv() function. */ #define HAVE_ICONV 1 @@ -220,7 +220,7 @@ #define HAVE_IFADDRS_H 1 /* Define this if inet_ntoa() is available */ -#define HAVE_INET_NTOA 1 +/* #undef HAVE_INET_NTOA */ /* Define to 1 if you have the `initgroups' function. */ #define HAVE_INITGROUPS 1 @@ -237,7 +237,7 @@ /* Define to 1 if you have the header file. */ #define HAVE_LANGINFO_H 1 -/* Define to 1 if you have a functional curl library. */ +/* Have libcurl */ #define HAVE_LIBCURL 1 /* Define if you have the libdl library or equivalent. */ @@ -249,6 +249,9 @@ /* Have GLPK */ #define HAVE_LIBGLPK 1 +/* Have libgtop */ +/* #undef HAVE_LIBGTOP */ + /* Define to 1 if you have the `intl' library (-lintl). */ /* #undef HAVE_LIBINTL */ @@ -262,7 +265,7 @@ /* #undef HAVE_LIBKVM */ /* Define to 1 if you have the `m' library (-lm). */ -/* #undef HAVE_LIBM */ +#define HAVE_LIBM 1 /* Define to 1 if you have the `resolv' library (-lresolv). */ /* #undef HAVE_LIBRESOLV */ @@ -282,12 +285,12 @@ /* Define to 1 if you have the header file. */ #define HAVE_LIMITS_H 1 +/* Define to 1 if you have the header file. */ +/* #undef HAVE_LLAPI_H */ + /* Define to 1 if you have the header file. */ #define HAVE_LOCALE_H 1 -/* Define to 1 if you have the `localtime_r' function. */ -#define HAVE_LOCALTIME_R 1 - /* Define this if a modern libltdl is already installed */ #define HAVE_LTDL 1 @@ -297,36 +300,33 @@ /* Define to 1 if you have the header file. */ /* #undef HAVE_MACH_O_DYLD_H */ +/* Define to 1 if you have the `mallinfo' function. */ +#define HAVE_MALLINFO 1 + +/* Define to 1 if you have the header file. */ +#define HAVE_MALLOC_H 1 + +/* Define to 1 if you have the header file. */ +/* #undef HAVE_MALLOC_MALLOC_H */ + +/* Define to 1 if you have the `malloc_size' function. */ +/* #undef HAVE_MALLOC_SIZE */ + +/* Define to 1 if you have the `malloc_usable_size' function. */ +#define HAVE_MALLOC_USABLE_SIZE 1 + /* Define to 1 if you have the header file. */ #define HAVE_MATH_H 1 -/* Define to 1 if you have the `memmove' function. */ -/* #undef HAVE_MEMMOVE */ - /* Define to 1 if you have the header file. */ #define HAVE_MEMORY_H 1 -/* Define to 1 if you have the `memset' function. */ -/* #undef HAVE_MEMSET */ - /* We have libmicrohttpd */ #define HAVE_MHD 1 /* Define to 1 if you have the header file. */ #define HAVE_MICROHTTPD_H 1 -/* Define to 1 if you have the `mkdir' function. */ -#define HAVE_MKDIR 1 - -/* Define to 1 if you have the `mkfifo' function. */ -#define HAVE_MKFIFO 1 - -/* Define to 1 if you have the `mktime' function. */ -#define HAVE_MKTIME 1 - -/* Define to 1 if you have the `mmap' function. */ -#define HAVE_MMAP 1 - /* Define to 1 if you have the `mremap' function. */ #define HAVE_MREMAP 1 @@ -345,9 +345,6 @@ /* Define to 1 if you have the header file. */ #define HAVE_NETINET_IN_SYSTM_H 1 -/* Define to 1 if you have the `nl_langinfo' function. */ -#define HAVE_NL_LANGINFO 1 - /* Define to 1 if you have the header file. */ #define HAVE_NSS_H 1 @@ -363,29 +360,11 @@ /* Define if libtool can extract symbol lists from object files. */ #define HAVE_PRELOADED_SYMBOLS 1 -/* Define to 1 if you have the `putenv' function. */ -#define HAVE_PUTENV 1 - -/* Define to 1 if you have the `rand' function. */ -#define HAVE_RAND 1 - /* Define to 1 if you have the `readdir' function. */ #define HAVE_READDIR 1 -/* Define to 1 if you have the `realpath' function. */ -#define HAVE_REALPATH 1 - -/* Define to 1 if you have the `rmdir' function. */ -#define HAVE_RMDIR 1 - -/* Define to 1 if you have the `sbrk' function. */ -#define HAVE_SBRK 1 - /* Define this if select() is available */ -#define HAVE_SELECT 1 - -/* Define to 1 if you have the `setlocale' function. */ -#define HAVE_SETLOCALE 1 +/* #undef HAVE_SELECT */ /* Define to 1 if you have the `setresuid' function. */ #define HAVE_SETRESUID 1 @@ -409,7 +388,7 @@ /* #undef HAVE_SOCKADDR_IN_SIN_LEN */ /* Define this if socket() is available */ -#define HAVE_SOCKET 1 +/* #undef HAVE_SOCKET */ /* Define to 1 if you have the header file. */ /* #undef HAVE_SOCKLIB_H */ @@ -428,7 +407,7 @@ #define HAVE_STDARG_H 1 /* Define to 1 if stdbool.h conforms to C99. */ -/* #undef HAVE_STDBOOL_H */ +#define HAVE_STDBOOL_H 1 /* Define to 1 if you have the header file. */ #define HAVE_STDDEF_H 1 @@ -442,20 +421,8 @@ /* Define to 1 if you have the header file. */ #define HAVE_STDLIB_H 1 -/* Define to 1 if you have the `strcasecmp' function. */ -/* #undef HAVE_STRCASECMP */ - -/* Define to 1 if you have the `strchr' function. */ -/* #undef HAVE_STRCHR */ - -/* Define to 1 if you have the `strdup' function. */ -/* #undef HAVE_STRDUP */ - -/* Define to 1 if you have the `strerror' function. */ -#define HAVE_STRERROR 1 - /* Define to 1 if you have the `strftime' function. */ -/* #undef HAVE_STRFTIME */ +#define HAVE_STRFTIME 1 /* Define to 1 if you have the header file. */ #define HAVE_STRINGS_H 1 @@ -469,20 +436,11 @@ /* Define to 1 if you have the `strlcpy' function. */ /* #undef HAVE_STRLCPY */ -/* Define to 1 if you have the `strncasecmp' function. */ -/* #undef HAVE_STRNCASECMP */ - /* Define to 1 if you have the `strndup' function. */ -/* #undef HAVE_STRNDUP */ - -/* Define to 1 if you have the `strrchr' function. */ -/* #undef HAVE_STRRCHR */ +#define HAVE_STRNDUP 1 -/* Define to 1 if you have the `strstr' function. */ -/* #undef HAVE_STRSTR */ - -/* Define to 1 if you have the `strtol' function. */ -#define HAVE_STRTOL 1 +/* Define to 1 if you have the `strnlen' function. */ +#define HAVE_STRNLEN 1 /* Define to 1 if you have the `sysconf' function. */ #define HAVE_SYSCONF 1 @@ -561,9 +519,6 @@ /* We can access-64 bit values that are only 32-bit aligned */ #define HAVE_UNALIGNED_64_ACCESS 0 -/* Define to 1 if you have the `uname' function. */ -#define HAVE_UNAME 1 - /* Define to 1 if you have the header file. */ #define HAVE_UNISTD_H 1 @@ -574,13 +529,13 @@ /* #undef HAVE_VFORK_H */ /* Define to 1 if you have the `vprintf' function. */ -/* #undef HAVE_VPRINTF */ +#define HAVE_VPRINTF 1 /* This value is set to 1 to indicate that the system argz facility works */ #define HAVE_WORKING_ARGZ 1 /* Define to 1 if `fork' works. */ -/* #undef HAVE_WORKING_FORK */ +#define HAVE_WORKING_FORK 1 /* Define to 1 if `vfork' works. */ #define HAVE_WORKING_VFORK 1 @@ -654,7 +609,10 @@ /* Defined if libcurl supports TFTP */ #define LIBCURL_PROTOCOL_TFTP 1 -/* This is a Linux system */ +/* Define to 1 if you want IDN support. */ +#define LIBIDN 1 + +/* This is a Linux kernel */ #define LINUX 1 /* Define to 1 if `lstat' dereferences a symlink specified with a trailing @@ -665,11 +623,14 @@ /* #undef LTDL_DLOPEN_DEPLIBS */ /* Define to the system default library search path. */ -#define LT_DLSEARCH_PATH "/lib:/usr/lib:/usr/local/lib:/lib/x86_64-linux-gnu:/usr/lib/x86_64-linux-gnu" +#define LT_DLSEARCH_PATH "/lib:/usr/lib:/usr/local/lib:/lib/x86_64-linux-gnu:/usr/lib/x86_64-linux-gnu:/lib32:/usr/lib32" /* The archive extension */ #define LT_LIBEXT "a" +/* The archive prefix */ +#define LT_LIBPREFIX "lib" + /* Define to the extension used for runtime loadable modules, say, ".so". */ #define LT_MODULE_EXT ".so" @@ -681,9 +642,15 @@ */ #define LT_OBJDIR ".libs/" +/* Define to the shared library suffix, say, ".dylib". */ +/* #undef LT_SHARED_EXT */ + /* This is a MinGW system */ /* #undef MINGW */ +/* required libgcrypt version */ +#define NEED_LIBGCRYPT_VERSION "1.4.2" + /* Define if dlsym() requires a leading underscore in symbol names. */ /* #undef NEED_USCORE */ @@ -709,7 +676,7 @@ #define PACKAGE_NAME "gnunet" /* Define to the full name and version of this package. */ -#define PACKAGE_STRING "gnunet 0.9.3" +#define PACKAGE_STRING "gnunet 0.9.5a" /* Define to the one symbol short name of this package. */ #define PACKAGE_TARNAME "gnunet" @@ -718,7 +685,7 @@ #define PACKAGE_URL "" /* Define to the version of this package. */ -#define PACKAGE_VERSION "0.9.3" +#define PACKAGE_VERSION "0.9.5a" /* Define as the return type of signal handlers (`int' or `void'). */ #define RETSIGTYPE void @@ -750,15 +717,26 @@ /* Define to 1 if your declares `struct tm'. */ /* #undef TM_IN_SYS_TIME */ +/* repository svn version */ +#define VCS_VERSION "svn-26026:26032M" + /* Version number of package */ -#define VERSION "0.9.3" +#define VERSION "0.9.5a" /* This is a Windows system */ /* #undef WINDOWS */ +/* Do we have to use IBM LoadLeveler */ +#define WITH_LL 0 + /* Define to 1 if the X Window System is missing or not being used. */ /* #undef X_DISPLAY_MISSING */ +/* Enable large inode numbers on Mac OS X 10.5. */ +#ifndef _DARWIN_USE_64_BIT_INODE +# define _DARWIN_USE_64_BIT_INODE 1 +#endif + /* Number of bits in a file offset, on hosts where this is settable. */ /* #undef _FILE_OFFSET_BITS */ diff --git a/gnunet_config.h.in b/gnunet_config.h.in index 1a99e14..f02296e 100644 --- a/gnunet_config.h.in +++ b/gnunet_config.h.in @@ -11,10 +11,16 @@ /* This is an Apple Darwin system */ #undef DARWIN +/* enable expensive heap statistics */ +#undef ENABLE_HEAP_STATISTICS + /* Define to 1 if translation of program messages to the user's native language is requested. */ #undef ENABLE_NLS +/* 1 if freed memory should be poisoned, 0 otherwise */ +#undef ENABLE_POISONING + /* enable workarounds used on Windows (only useful for test cases) */ #undef ENABLE_WINDOWS_WORKAROUNDS @@ -24,6 +30,9 @@ /* This is a FreeBSD system */ #undef FREEBSD +/* This is a GNU system */ +#undef GNU + /* Define to cull all logging calls */ #undef GNUNET_CULL_LOGGING @@ -76,9 +85,6 @@ /* Define to 1 if your system has a working `chown' function. */ #undef HAVE_CHOWN -/* Define to 1 if you have the `clock_gettime' function. */ -#undef HAVE_CLOCK_GETTIME - /* Define to 1 if you have the `closedir' function. */ #undef HAVE_CLOSEDIR @@ -119,9 +125,6 @@ /* Define to 1 if you don't have `vprintf' but do have `_doprnt.' */ #undef HAVE_DOPRNT -/* Define to 1 if you have the `dup2' function. */ -#undef HAVE_DUP2 - /* Define if you have the _dyld_func_lookup function. */ #undef HAVE_DYLD @@ -134,18 +137,15 @@ /* Define to 1 if the system has the type `error_t'. */ #undef HAVE_ERROR_T +/* Define to 1 if you have the header file. */ +#undef HAVE_EXECINFO_H + /* Define to 1 if you have the header file. */ #undef HAVE_EXTRACTOR_H /* Define to 1 if you have the header file. */ #undef HAVE_FCNTL_H -/* Define to 1 if you have the `fdatasync' function. */ -#undef HAVE_FDATASYNC - -/* Define to 1 if you have the `floor' function. */ -#undef HAVE_FLOOR - /* Define to 1 if you have the `fork' function. */ #undef HAVE_FORK @@ -155,15 +155,9 @@ /* Define to 1 if fseeko (and presumably ftello) exists and is declared. */ #undef HAVE_FSEEKO -/* Define to 1 if you have the `ftruncate' function. */ -#undef HAVE_FTRUNCATE - /* Define this if getaddrinfo() is available */ #undef HAVE_GETADDRINFO -/* Define to 1 if you have the `getcwd' function. */ -#undef HAVE_GETCWD - /* Define this if gethostbyaddr() is available */ #undef HAVE_GETHOSTBYADDR @@ -191,14 +185,20 @@ /* Define to 1 if you have the `getpeerucred' function. */ #undef HAVE_GETPEERUCRED +/* Define to 1 if you have the `getresgid' function. */ +#undef HAVE_GETRESGID + +/* Define to 1 if you have the `getrlimit' function. */ +#undef HAVE_GETRLIMIT + /* Define to 1 if you have the `getrusage' function. */ #undef HAVE_GETRUSAGE /* Define if the GNU gettext() function is already present or preinstalled. */ #undef HAVE_GETTEXT -/* Define to 1 if you have the `gettimeofday' function. */ -#undef HAVE_GETTIMEOFDAY +/* Have glib2 */ +#undef HAVE_GLIB2 /* Define to 1 if you have the header file. */ #undef HAVE_GLPK_H @@ -206,11 +206,11 @@ /* Define to 1 if `presolve' is a member of `glp_iocp'. */ #undef HAVE_GLP_IOCP_PRESOLVE -/* Define to 1 if you have the `gmtime' function. */ -#undef HAVE_GMTIME +/* We have gnutls */ +#undef HAVE_GNUTLS -/* Define to 1 if you have the `gmtime_r' function. */ -#undef HAVE_GMTIME_R +/* Define to 1 if you have the header file. */ +#undef HAVE_GNUTLS_ABSTRACT_H /* Define if you have the iconv() function. */ #undef HAVE_ICONV @@ -236,7 +236,7 @@ /* Define to 1 if you have the header file. */ #undef HAVE_LANGINFO_H -/* Define to 1 if you have a functional curl library. */ +/* Have libcurl */ #undef HAVE_LIBCURL /* Define if you have the libdl library or equivalent. */ @@ -248,6 +248,9 @@ /* Have GLPK */ #undef HAVE_LIBGLPK +/* Have libgtop */ +#undef HAVE_LIBGTOP + /* Define to 1 if you have the `intl' library (-lintl). */ #undef HAVE_LIBINTL @@ -281,12 +284,12 @@ /* Define to 1 if you have the header file. */ #undef HAVE_LIMITS_H +/* Define to 1 if you have the header file. */ +#undef HAVE_LLAPI_H + /* Define to 1 if you have the header file. */ #undef HAVE_LOCALE_H -/* Define to 1 if you have the `localtime_r' function. */ -#undef HAVE_LOCALTIME_R - /* Define this if a modern libltdl is already installed */ #undef HAVE_LTDL @@ -296,36 +299,33 @@ /* Define to 1 if you have the header file. */ #undef HAVE_MACH_O_DYLD_H +/* Define to 1 if you have the `mallinfo' function. */ +#undef HAVE_MALLINFO + +/* Define to 1 if you have the header file. */ +#undef HAVE_MALLOC_H + +/* Define to 1 if you have the header file. */ +#undef HAVE_MALLOC_MALLOC_H + +/* Define to 1 if you have the `malloc_size' function. */ +#undef HAVE_MALLOC_SIZE + +/* Define to 1 if you have the `malloc_usable_size' function. */ +#undef HAVE_MALLOC_USABLE_SIZE + /* Define to 1 if you have the header file. */ #undef HAVE_MATH_H -/* Define to 1 if you have the `memmove' function. */ -#undef HAVE_MEMMOVE - /* Define to 1 if you have the header file. */ #undef HAVE_MEMORY_H -/* Define to 1 if you have the `memset' function. */ -#undef HAVE_MEMSET - /* We have libmicrohttpd */ #undef HAVE_MHD /* Define to 1 if you have the header file. */ #undef HAVE_MICROHTTPD_H -/* Define to 1 if you have the `mkdir' function. */ -#undef HAVE_MKDIR - -/* Define to 1 if you have the `mkfifo' function. */ -#undef HAVE_MKFIFO - -/* Define to 1 if you have the `mktime' function. */ -#undef HAVE_MKTIME - -/* Define to 1 if you have the `mmap' function. */ -#undef HAVE_MMAP - /* Define to 1 if you have the `mremap' function. */ #undef HAVE_MREMAP @@ -344,9 +344,6 @@ /* Define to 1 if you have the header file. */ #undef HAVE_NETINET_IN_SYSTM_H -/* Define to 1 if you have the `nl_langinfo' function. */ -#undef HAVE_NL_LANGINFO - /* Define to 1 if you have the header file. */ #undef HAVE_NSS_H @@ -362,30 +359,12 @@ /* Define if libtool can extract symbol lists from object files. */ #undef HAVE_PRELOADED_SYMBOLS -/* Define to 1 if you have the `putenv' function. */ -#undef HAVE_PUTENV - -/* Define to 1 if you have the `rand' function. */ -#undef HAVE_RAND - /* Define to 1 if you have the `readdir' function. */ #undef HAVE_READDIR -/* Define to 1 if you have the `realpath' function. */ -#undef HAVE_REALPATH - -/* Define to 1 if you have the `rmdir' function. */ -#undef HAVE_RMDIR - -/* Define to 1 if you have the `sbrk' function. */ -#undef HAVE_SBRK - /* Define this if select() is available */ #undef HAVE_SELECT -/* Define to 1 if you have the `setlocale' function. */ -#undef HAVE_SETLOCALE - /* Define to 1 if you have the `setresuid' function. */ #undef HAVE_SETRESUID @@ -441,18 +420,6 @@ /* Define to 1 if you have the header file. */ #undef HAVE_STDLIB_H -/* Define to 1 if you have the `strcasecmp' function. */ -#undef HAVE_STRCASECMP - -/* Define to 1 if you have the `strchr' function. */ -#undef HAVE_STRCHR - -/* Define to 1 if you have the `strdup' function. */ -#undef HAVE_STRDUP - -/* Define to 1 if you have the `strerror' function. */ -#undef HAVE_STRERROR - /* Define to 1 if you have the `strftime' function. */ #undef HAVE_STRFTIME @@ -468,20 +435,11 @@ /* Define to 1 if you have the `strlcpy' function. */ #undef HAVE_STRLCPY -/* Define to 1 if you have the `strncasecmp' function. */ -#undef HAVE_STRNCASECMP - /* Define to 1 if you have the `strndup' function. */ #undef HAVE_STRNDUP -/* Define to 1 if you have the `strrchr' function. */ -#undef HAVE_STRRCHR - -/* Define to 1 if you have the `strstr' function. */ -#undef HAVE_STRSTR - -/* Define to 1 if you have the `strtol' function. */ -#undef HAVE_STRTOL +/* Define to 1 if you have the `strnlen' function. */ +#undef HAVE_STRNLEN /* Define to 1 if you have the `sysconf' function. */ #undef HAVE_SYSCONF @@ -560,9 +518,6 @@ /* We can access-64 bit values that are only 32-bit aligned */ #undef HAVE_UNALIGNED_64_ACCESS -/* Define to 1 if you have the `uname' function. */ -#undef HAVE_UNAME - /* Define to 1 if you have the header file. */ #undef HAVE_UNISTD_H @@ -653,7 +608,10 @@ /* Defined if libcurl supports TFTP */ #undef LIBCURL_PROTOCOL_TFTP -/* This is a Linux system */ +/* Define to 1 if you want IDN support. */ +#undef LIBIDN + +/* This is a Linux kernel */ #undef LINUX /* Define to 1 if `lstat' dereferences a symlink specified with a trailing @@ -669,6 +627,9 @@ /* The archive extension */ #undef LT_LIBEXT +/* The archive prefix */ +#undef LT_LIBPREFIX + /* Define to the extension used for runtime loadable modules, say, ".so". */ #undef LT_MODULE_EXT @@ -680,9 +641,15 @@ */ #undef LT_OBJDIR +/* Define to the shared library suffix, say, ".dylib". */ +#undef LT_SHARED_EXT + /* This is a MinGW system */ #undef MINGW +/* required libgcrypt version */ +#undef NEED_LIBGCRYPT_VERSION + /* Define if dlsym() requires a leading underscore in symbol names. */ #undef NEED_USCORE @@ -749,15 +716,26 @@ /* Define to 1 if your declares `struct tm'. */ #undef TM_IN_SYS_TIME +/* repository svn version */ +#undef VCS_VERSION + /* Version number of package */ #undef VERSION /* This is a Windows system */ #undef WINDOWS +/* Do we have to use IBM LoadLeveler */ +#undef WITH_LL + /* Define to 1 if the X Window System is missing or not being used. */ #undef X_DISPLAY_MISSING +/* Enable large inode numbers on Mac OS X 10.5. */ +#ifndef _DARWIN_USE_64_BIT_INODE +# define _DARWIN_USE_64_BIT_INODE 1 +#endif + /* Number of bits in a file offset, on hosts where this is settable. */ #undef _FILE_OFFSET_BITS diff --git a/install-sh b/install-sh index 6781b98..377bb86 100755 --- a/install-sh +++ b/install-sh @@ -1,7 +1,7 @@ #!/bin/sh # install - install a program, script, or datafile -scriptversion=2009-04-28.21; # UTC +scriptversion=2011-11-20.07; # UTC # This originates from X11R5 (mit/util/scripts/install.sh), which was # later released in X11R6 (xc/config/util/install.sh) with the @@ -35,7 +35,7 @@ scriptversion=2009-04-28.21; # UTC # FSF changes to this file are in the public domain. # # Calling this script install-sh is preferred over install.sh, to prevent -# `make' implicit rules from creating a file called install from it +# 'make' implicit rules from creating a file called install from it # when there is no Makefile. # # This script is compatible with the BSD install script, but was written @@ -156,6 +156,10 @@ while test $# -ne 0; do -s) stripcmd=$stripprog;; -t) dst_arg=$2 + # Protect names problematic for 'test' and other utilities. + case $dst_arg in + -* | [=\(\)!]) dst_arg=./$dst_arg;; + esac shift;; -T) no_target_directory=true;; @@ -186,6 +190,10 @@ if test $# -ne 0 && test -z "$dir_arg$dst_arg"; then fi shift # arg dst_arg=$arg + # Protect names problematic for 'test' and other utilities. + case $dst_arg in + -* | [=\(\)!]) dst_arg=./$dst_arg;; + esac done fi @@ -194,13 +202,17 @@ if test $# -eq 0; then echo "$0: no input file specified." >&2 exit 1 fi - # It's OK to call `install-sh -d' without argument. + # It's OK to call 'install-sh -d' without argument. # This can happen when creating conditional directories. exit 0 fi if test -z "$dir_arg"; then - trap '(exit $?); exit' 1 2 13 15 + do_exit='(exit $ret); exit $ret' + trap "ret=129; $do_exit" 1 + trap "ret=130; $do_exit" 2 + trap "ret=141; $do_exit" 13 + trap "ret=143; $do_exit" 15 # Set umask so as not to create temps with too-generous modes. # However, 'strip' requires both read and write access to temps. @@ -228,9 +240,9 @@ fi for src do - # Protect names starting with `-'. + # Protect names problematic for 'test' and other utilities. case $src in - -*) src=./$src;; + -* | [=\(\)!]) src=./$src;; esac if test -n "$dir_arg"; then @@ -252,12 +264,7 @@ do echo "$0: no destination specified." >&2 exit 1 fi - dst=$dst_arg - # Protect names starting with `-'. - case $dst in - -*) dst=./$dst;; - esac # If destination is a directory, append the input filename; won't work # if double slashes aren't ignored. @@ -347,7 +354,7 @@ do if test -z "$dir_arg" || { # Check for POSIX incompatibilities with -m. # HP-UX 11.23 and IRIX 6.5 mkdir -m -p sets group- or - # other-writeable bit of parent directory when it shouldn't. + # other-writable bit of parent directory when it shouldn't. # FreeBSD 6.1 mkdir -m -p sets mode of existing directory. ls_ld_tmpdir=`ls -ld "$tmpdir"` case $ls_ld_tmpdir in @@ -385,7 +392,7 @@ do case $dstdir in /*) prefix='/';; - -*) prefix='./';; + [-=\(\)!]*) prefix='./';; *) prefix='';; esac @@ -403,7 +410,7 @@ do for d do - test -z "$d" && continue + test X"$d" = X && continue prefix=$prefix$d if test -d "$prefix"; then diff --git a/ltmain.sh b/ltmain.sh old mode 100755 new mode 100644 index d88da2c..33f642a --- a/ltmain.sh +++ b/ltmain.sh @@ -1,9 +1,9 @@ -# Generated from ltmain.m4sh. -# ltmain.sh (GNU libtool) 2.2.6b +# libtool (GNU libtool) 2.4.2 # Written by Gordon Matzigkeit , 1996 -# Copyright (C) 1996, 1997, 1998, 1999, 2000, 2001, 2003, 2004, 2005, 2006, 2007 2008 Free Software Foundation, Inc. +# Copyright (C) 1996, 1997, 1998, 1999, 2000, 2001, 2003, 2004, 2005, 2006, +# 2007, 2008, 2009, 2010, 2011 Free Software Foundation, Inc. # This is free software; see the source for copying conditions. There is NO # warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. @@ -32,50 +32,57 @@ # # Provide generalized library-building support services. # -# --config show all configuration variables -# --debug enable verbose shell tracing -# -n, --dry-run display commands without modifying any files -# --features display basic configuration information and exit -# --mode=MODE use operation mode MODE -# --preserve-dup-deps don't remove duplicate dependency libraries -# --quiet, --silent don't print informational messages -# --tag=TAG use configuration variables from tag TAG -# -v, --verbose print informational messages (default) -# --version print version information -# -h, --help print short or long help message +# --config show all configuration variables +# --debug enable verbose shell tracing +# -n, --dry-run display commands without modifying any files +# --features display basic configuration information and exit +# --mode=MODE use operation mode MODE +# --preserve-dup-deps don't remove duplicate dependency libraries +# --quiet, --silent don't print informational messages +# --no-quiet, --no-silent +# print informational messages (default) +# --no-warn don't display warning messages +# --tag=TAG use configuration variables from tag TAG +# -v, --verbose print more informational messages than default +# --no-verbose don't print the extra informational messages +# --version print version information +# -h, --help, --help-all print short, long, or detailed help message # # MODE must be one of the following: # -# clean remove files from the build directory -# compile compile a source file into a libtool object -# execute automatically set library path, then run a program -# finish complete the installation of libtool libraries -# install install libraries or executables -# link create a library or an executable -# uninstall remove libraries from an installed directory +# clean remove files from the build directory +# compile compile a source file into a libtool object +# execute automatically set library path, then run a program +# finish complete the installation of libtool libraries +# install install libraries or executables +# link create a library or an executable +# uninstall remove libraries from an installed directory # -# MODE-ARGS vary depending on the MODE. +# MODE-ARGS vary depending on the MODE. When passed as first option, +# `--mode=MODE' may be abbreviated as `MODE' or a unique abbreviation of that. # Try `$progname --help --mode=MODE' for a more detailed description of MODE. # # When reporting a bug, please describe a test case to reproduce it and # include the following information: # -# host-triplet: $host -# shell: $SHELL -# compiler: $LTCC -# compiler flags: $LTCFLAGS -# linker: $LD (gnu? $with_gnu_ld) -# $progname: (GNU libtool) 2.2.6b Debian-2.2.6b-2 -# automake: $automake_version -# autoconf: $autoconf_version +# host-triplet: $host +# shell: $SHELL +# compiler: $LTCC +# compiler flags: $LTCFLAGS +# linker: $LD (gnu? $with_gnu_ld) +# $progname: (GNU libtool) 2.4.2 Debian-2.4.2-1.1 +# automake: $automake_version +# autoconf: $autoconf_version # # Report bugs to . +# GNU libtool home page: . +# General help using GNU software: . -PROGRAM=ltmain.sh +PROGRAM=libtool PACKAGE=libtool -VERSION="2.2.6b Debian-2.2.6b-2" +VERSION="2.4.2 Debian-2.4.2-1.1" TIMESTAMP="" -package_revision=1.3017 +package_revision=1.3337 # Be Bourne compatible if test -n "${ZSH_VERSION+set}" && (emulate sh) >/dev/null 2>&1; then @@ -91,10 +98,15 @@ fi BIN_SH=xpg4; export BIN_SH # for Tru64 DUALCASE=1; export DUALCASE # for MKS sh +# A function that is used when there is no print builtin or printf. +func_fallback_echo () +{ + eval 'cat <<_LTECHO_EOF +$1 +_LTECHO_EOF' +} + # NLS nuisances: We save the old values to restore during execute mode. -# Only set LANG and LC_ALL to C if already set. -# These must not be set unconditionally because not all systems understand -# e.g. LANG=C (notably SCO). lt_user_locale= lt_safe_locale= for lt_var in LANG LANGUAGE LC_ALL LC_CTYPE LC_COLLATE LC_MESSAGES @@ -107,24 +119,28 @@ do lt_safe_locale=\"$lt_var=C; \$lt_safe_locale\" fi" done +LC_ALL=C +LANGUAGE=C +export LANGUAGE LC_ALL $lt_unset CDPATH +# Work around backward compatibility issue on IRIX 6.5. On IRIX 6.4+, sh +# is ksh but when the shell is invoked as "sh" and the current value of +# the _XPG environment variable is not equal to 1 (one), the special +# positional parameter $0, within a function call, is the name of the +# function. +progpath="$0" : ${CP="cp -f"} -: ${ECHO="echo"} -: ${EGREP="/bin/grep -E"} -: ${FGREP="/bin/grep -F"} -: ${GREP="/bin/grep"} -: ${LN_S="ln -s"} +test "${ECHO+set}" = set || ECHO=${as_echo-'printf %s\n'} : ${MAKE="make"} : ${MKDIR="mkdir"} : ${MV="mv -f"} : ${RM="rm -f"} -: ${SED="/bin/sed"} : ${SHELL="${CONFIG_SHELL-/bin/sh}"} : ${Xsed="$SED -e 1s/^X//"} @@ -144,6 +160,27 @@ IFS=" $lt_nl" dirname="s,/[^/]*$,," basename="s,^.*/,," +# func_dirname file append nondir_replacement +# Compute the dirname of FILE. If nonempty, add APPEND to the result, +# otherwise set result to NONDIR_REPLACEMENT. +func_dirname () +{ + func_dirname_result=`$ECHO "${1}" | $SED "$dirname"` + if test "X$func_dirname_result" = "X${1}"; then + func_dirname_result="${3}" + else + func_dirname_result="$func_dirname_result${2}" + fi +} # func_dirname may be replaced by extended shell implementation + + +# func_basename file +func_basename () +{ + func_basename_result=`$ECHO "${1}" | $SED "$basename"` +} # func_basename may be replaced by extended shell implementation + + # func_dirname_and_basename file append nondir_replacement # perform func_basename and func_dirname in a single function # call: @@ -158,33 +195,183 @@ basename="s,^.*/,," # those functions but instead duplicate the functionality here. func_dirname_and_basename () { - # Extract subdirectory from the argument. - func_dirname_result=`$ECHO "X${1}" | $Xsed -e "$dirname"` - if test "X$func_dirname_result" = "X${1}"; then - func_dirname_result="${3}" - else - func_dirname_result="$func_dirname_result${2}" - fi - func_basename_result=`$ECHO "X${1}" | $Xsed -e "$basename"` + # Extract subdirectory from the argument. + func_dirname_result=`$ECHO "${1}" | $SED -e "$dirname"` + if test "X$func_dirname_result" = "X${1}"; then + func_dirname_result="${3}" + else + func_dirname_result="$func_dirname_result${2}" + fi + func_basename_result=`$ECHO "${1}" | $SED -e "$basename"` +} # func_dirname_and_basename may be replaced by extended shell implementation + + +# func_stripname prefix suffix name +# strip PREFIX and SUFFIX off of NAME. +# PREFIX and SUFFIX must not contain globbing or regex special +# characters, hashes, percent signs, but SUFFIX may contain a leading +# dot (in which case that matches only a dot). +# func_strip_suffix prefix name +func_stripname () +{ + case ${2} in + .*) func_stripname_result=`$ECHO "${3}" | $SED "s%^${1}%%; s%\\\\${2}\$%%"`;; + *) func_stripname_result=`$ECHO "${3}" | $SED "s%^${1}%%; s%${2}\$%%"`;; + esac +} # func_stripname may be replaced by extended shell implementation + + +# These SED scripts presuppose an absolute path with a trailing slash. +pathcar='s,^/\([^/]*\).*$,\1,' +pathcdr='s,^/[^/]*,,' +removedotparts=':dotsl + s@/\./@/@g + t dotsl + s,/\.$,/,' +collapseslashes='s@/\{1,\}@/@g' +finalslash='s,/*$,/,' + +# func_normal_abspath PATH +# Remove doubled-up and trailing slashes, "." path components, +# and cancel out any ".." path components in PATH after making +# it an absolute path. +# value returned in "$func_normal_abspath_result" +func_normal_abspath () +{ + # Start from root dir and reassemble the path. + func_normal_abspath_result= + func_normal_abspath_tpath=$1 + func_normal_abspath_altnamespace= + case $func_normal_abspath_tpath in + "") + # Empty path, that just means $cwd. + func_stripname '' '/' "`pwd`" + func_normal_abspath_result=$func_stripname_result + return + ;; + # The next three entries are used to spot a run of precisely + # two leading slashes without using negated character classes; + # we take advantage of case's first-match behaviour. + ///*) + # Unusual form of absolute path, do nothing. + ;; + //*) + # Not necessarily an ordinary path; POSIX reserves leading '//' + # and for example Cygwin uses it to access remote file shares + # over CIFS/SMB, so we conserve a leading double slash if found. + func_normal_abspath_altnamespace=/ + ;; + /*) + # Absolute path, do nothing. + ;; + *) + # Relative path, prepend $cwd. + func_normal_abspath_tpath=`pwd`/$func_normal_abspath_tpath + ;; + esac + # Cancel out all the simple stuff to save iterations. We also want + # the path to end with a slash for ease of parsing, so make sure + # there is one (and only one) here. + func_normal_abspath_tpath=`$ECHO "$func_normal_abspath_tpath" | $SED \ + -e "$removedotparts" -e "$collapseslashes" -e "$finalslash"` + while :; do + # Processed it all yet? + if test "$func_normal_abspath_tpath" = / ; then + # If we ascended to the root using ".." the result may be empty now. + if test -z "$func_normal_abspath_result" ; then + func_normal_abspath_result=/ + fi + break + fi + func_normal_abspath_tcomponent=`$ECHO "$func_normal_abspath_tpath" | $SED \ + -e "$pathcar"` + func_normal_abspath_tpath=`$ECHO "$func_normal_abspath_tpath" | $SED \ + -e "$pathcdr"` + # Figure out what to do with it + case $func_normal_abspath_tcomponent in + "") + # Trailing empty path component, ignore it. + ;; + ..) + # Parent dir; strip last assembled component from result. + func_dirname "$func_normal_abspath_result" + func_normal_abspath_result=$func_dirname_result + ;; + *) + # Actual path component, append it. + func_normal_abspath_result=$func_normal_abspath_result/$func_normal_abspath_tcomponent + ;; + esac + done + # Restore leading double-slash if one was found on entry. + func_normal_abspath_result=$func_normal_abspath_altnamespace$func_normal_abspath_result } -# Generated shell functions inserted here. +# func_relative_path SRCDIR DSTDIR +# generates a relative path from SRCDIR to DSTDIR, with a trailing +# slash if non-empty, suitable for immediately appending a filename +# without needing to append a separator. +# value returned in "$func_relative_path_result" +func_relative_path () +{ + func_relative_path_result= + func_normal_abspath "$1" + func_relative_path_tlibdir=$func_normal_abspath_result + func_normal_abspath "$2" + func_relative_path_tbindir=$func_normal_abspath_result + + # Ascend the tree starting from libdir + while :; do + # check if we have found a prefix of bindir + case $func_relative_path_tbindir in + $func_relative_path_tlibdir) + # found an exact match + func_relative_path_tcancelled= + break + ;; + $func_relative_path_tlibdir*) + # found a matching prefix + func_stripname "$func_relative_path_tlibdir" '' "$func_relative_path_tbindir" + func_relative_path_tcancelled=$func_stripname_result + if test -z "$func_relative_path_result"; then + func_relative_path_result=. + fi + break + ;; + *) + func_dirname $func_relative_path_tlibdir + func_relative_path_tlibdir=${func_dirname_result} + if test "x$func_relative_path_tlibdir" = x ; then + # Have to descend all the way to the root! + func_relative_path_result=../$func_relative_path_result + func_relative_path_tcancelled=$func_relative_path_tbindir + break + fi + func_relative_path_result=../$func_relative_path_result + ;; + esac + done -# Work around backward compatibility issue on IRIX 6.5. On IRIX 6.4+, sh -# is ksh but when the shell is invoked as "sh" and the current value of -# the _XPG environment variable is not equal to 1 (one), the special -# positional parameter $0, within a function call, is the name of the -# function. -progpath="$0" + # Now calculate path; take care to avoid doubling-up slashes. + func_stripname '' '/' "$func_relative_path_result" + func_relative_path_result=$func_stripname_result + func_stripname '/' '/' "$func_relative_path_tcancelled" + if test "x$func_stripname_result" != x ; then + func_relative_path_result=${func_relative_path_result}/${func_stripname_result} + fi + + # Normalisation. If bindir is libdir, return empty string, + # else relative path ending with a slash; either way, target + # file name can be directly appended. + if test ! -z "$func_relative_path_result"; then + func_stripname './' '' "$func_relative_path_result/" + func_relative_path_result=$func_stripname_result + fi +} # The name of this program: -# In the unlikely event $progname began with a '-', it would play havoc with -# func_echo (imagine progname=-n), so we prepend ./ in that case: func_dirname_and_basename "$progpath" progname=$func_basename_result -case $progname in - -*) progname=./$progname ;; -esac # Make sure we have an absolute path for reexecution: case $progpath in @@ -196,7 +383,7 @@ case $progpath in ;; *) save_IFS="$IFS" - IFS=: + IFS=${PATH_SEPARATOR-:} for progdir in $PATH; do IFS="$save_IFS" test -x "$progdir/$progname" && break @@ -215,6 +402,15 @@ sed_quote_subst='s/\([`"$\\]\)/\\\1/g' # Same as above, but do not quote variable references. double_quote_subst='s/\(["`\\]\)/\\\1/g' +# Sed substitution that turns a string into a regex matching for the +# string literally. +sed_make_literal_regex='s,[].[^$\\*\/],\\&,g' + +# Sed substitution that converts a w32 file name or path +# which contains forward slashes, into one that contains +# (escaped) backslashes. A very naive implementation. +lt_sed_naive_backslashify='s|\\\\*|\\|g;s|/|\\|g;s|\\|\\\\|g' + # Re-`\' parameter expansions in output of double_quote_subst that were # `\'-ed in input to the same. If an odd number of `\' preceded a '$' # in input to double_quote_subst, that '$' was protected from expansion. @@ -243,7 +439,7 @@ opt_warning=: # name if it has been set yet. func_echo () { - $ECHO "$progname${mode+: }$mode: $*" + $ECHO "$progname: ${opt_mode+$opt_mode: }$*" } # func_verbose arg... @@ -258,18 +454,25 @@ func_verbose () : } +# func_echo_all arg... +# Invoke $ECHO with all args, space-separated. +func_echo_all () +{ + $ECHO "$*" +} + # func_error arg... # Echo program name prefixed message to standard error. func_error () { - $ECHO "$progname${mode+: }$mode: "${1+"$@"} 1>&2 + $ECHO "$progname: ${opt_mode+$opt_mode: }"${1+"$@"} 1>&2 } # func_warning arg... # Echo program name prefixed warning message to standard error. func_warning () { - $opt_warning && $ECHO "$progname${mode+: }$mode: warning: "${1+"$@"} 1>&2 + $opt_warning && $ECHO "$progname: ${opt_mode+$opt_mode: }warning: "${1+"$@"} 1>&2 # bash bug again: : @@ -326,9 +529,9 @@ func_mkdir_p () case $my_directory_path in */*) ;; *) break ;; esac # ...otherwise throw away the child directory and loop - my_directory_path=`$ECHO "X$my_directory_path" | $Xsed -e "$dirname"` + my_directory_path=`$ECHO "$my_directory_path" | $SED -e "$dirname"` done - my_dir_list=`$ECHO "X$my_dir_list" | $Xsed -e 's,:*$,,'` + my_dir_list=`$ECHO "$my_dir_list" | $SED 's,:*$,,'` save_mkdir_p_IFS="$IFS"; IFS=':' for my_dir in $my_dir_list; do @@ -378,7 +581,7 @@ func_mktempdir () func_fatal_error "cannot create temporary directory \`$my_tmpdir'" fi - $ECHO "X$my_tmpdir" | $Xsed + $ECHO "$my_tmpdir" } @@ -392,7 +595,7 @@ func_quote_for_eval () { case $1 in *[\\\`\"\$]*) - func_quote_for_eval_unquoted_result=`$ECHO "X$1" | $Xsed -e "$sed_quote_subst"` ;; + func_quote_for_eval_unquoted_result=`$ECHO "$1" | $SED "$sed_quote_subst"` ;; *) func_quote_for_eval_unquoted_result="$1" ;; esac @@ -419,7 +622,7 @@ func_quote_for_expand () { case $1 in *[\\\`\"]*) - my_arg=`$ECHO "X$1" | $Xsed \ + my_arg=`$ECHO "$1" | $SED \ -e "$double_quote_subst" -e "$sed_double_backslash"` ;; *) my_arg="$1" ;; @@ -488,15 +691,39 @@ func_show_eval_locale () fi } - - +# func_tr_sh +# Turn $1 into a string suitable for a shell variable name. +# Result is stored in $func_tr_sh_result. All characters +# not in the set a-zA-Z0-9_ are replaced with '_'. Further, +# if $1 begins with a digit, a '_' is prepended as well. +func_tr_sh () +{ + case $1 in + [0-9]* | *[!a-zA-Z0-9_]*) + func_tr_sh_result=`$ECHO "$1" | $SED 's/^\([0-9]\)/_\1/; s/[^a-zA-Z0-9_]/_/g'` + ;; + * ) + func_tr_sh_result=$1 + ;; + esac +} # func_version # Echo version message to standard output and exit. func_version () { - $SED -n '/^# '$PROGRAM' (GNU /,/# warranty; / { + $opt_debug + + $SED -n '/(C)/!b go + :more + /\./!{ + N + s/\n# / / + b more + } + :go + /^# '$PROGRAM' (GNU /,/# warranty; / { s/^# // s/^# *$// s/\((C)\)[ 0-9,-]*\( [1-9][0-9]*\)/\1\2/ @@ -509,22 +736,28 @@ func_version () # Echo short help message to standard output and exit. func_usage () { - $SED -n '/^# Usage:/,/# -h/ { + $opt_debug + + $SED -n '/^# Usage:/,/^# *.*--help/ { s/^# // s/^# *$// s/\$progname/'$progname'/ p }' < "$progpath" - $ECHO + echo $ECHO "run \`$progname --help | more' for full usage" exit $? } -# func_help -# Echo long help message to standard output and exit. +# func_help [NOEXIT] +# Echo long help message to standard output and exit, +# unless 'noexit' is passed as argument. func_help () { + $opt_debug + $SED -n '/^# Usage:/,/# Report bugs to/ { + :print s/^# // s/^# *$// s*\$progname*'$progname'* @@ -534,11 +767,18 @@ func_help () s*\$LTCFLAGS*'"$LTCFLAGS"'* s*\$LD*'"$LD"'* s/\$with_gnu_ld/'"$with_gnu_ld"'/ - s/\$automake_version/'"`(automake --version) 2>/dev/null |$SED 1q`"'/ - s/\$autoconf_version/'"`(autoconf --version) 2>/dev/null |$SED 1q`"'/ + s/\$automake_version/'"`(${AUTOMAKE-automake} --version) 2>/dev/null |$SED 1q`"'/ + s/\$autoconf_version/'"`(${AUTOCONF-autoconf} --version) 2>/dev/null |$SED 1q`"'/ p - }' < "$progpath" - exit $? + d + } + /^# .* home page:/b print + /^# General help using/b print + ' < "$progpath" + ret=$? + if test -z "$1"; then + exit $ret + fi } # func_missing_arg argname @@ -546,63 +786,106 @@ func_help () # exit_cmd. func_missing_arg () { - func_error "missing argument for $1" + $opt_debug + + func_error "missing argument for $1." exit_cmd=exit } -exit_cmd=: +# func_split_short_opt shortopt +# Set func_split_short_opt_name and func_split_short_opt_arg shell +# variables after splitting SHORTOPT after the 2nd character. +func_split_short_opt () +{ + my_sed_short_opt='1s/^\(..\).*$/\1/;q' + my_sed_short_rest='1s/^..\(.*\)$/\1/;q' + func_split_short_opt_name=`$ECHO "$1" | $SED "$my_sed_short_opt"` + func_split_short_opt_arg=`$ECHO "$1" | $SED "$my_sed_short_rest"` +} # func_split_short_opt may be replaced by extended shell implementation + + +# func_split_long_opt longopt +# Set func_split_long_opt_name and func_split_long_opt_arg shell +# variables after splitting LONGOPT at the `=' sign. +func_split_long_opt () +{ + my_sed_long_opt='1s/^\(--[^=]*\)=.*/\1/;q' + my_sed_long_arg='1s/^--[^=]*=//' + + func_split_long_opt_name=`$ECHO "$1" | $SED "$my_sed_long_opt"` + func_split_long_opt_arg=`$ECHO "$1" | $SED "$my_sed_long_arg"` +} # func_split_long_opt may be replaced by extended shell implementation + +exit_cmd=: -# Check that we have a working $ECHO. -if test "X$1" = X--no-reexec; then - # Discard the --no-reexec flag, and continue. - shift -elif test "X$1" = X--fallback-echo; then - # Avoid inline document here, it may be left over - : -elif test "X`{ $ECHO '\t'; } 2>/dev/null`" = 'X\t'; then - # Yippee, $ECHO works! - : -else - # Restart under the correct shell, and then maybe $ECHO will work. - exec $SHELL "$progpath" --no-reexec ${1+"$@"} -fi -if test "X$1" = X--fallback-echo; then - # used as fallback echo - shift - cat </dev/null || echo $max_cmd_len` +} # func_len may be replaced by extended shell implementation + + +# func_lo2o object +func_lo2o () +{ + func_lo2o_result=`$ECHO "${1}" | $SED "$lo2o"` +} # func_lo2o may be replaced by extended shell implementation + + +# func_xform libobj-or-source +func_xform () +{ + func_xform_result=`$ECHO "${1}" | $SED 's/\.[^.]*$/.lo/'` +} # func_xform may be replaced by extended shell implementation + + # func_fatal_configuration arg... # Echo program name prefixed message to standard error, followed by # a configuration failure hint, and exit. @@ -636,16 +919,16 @@ func_config () # Display the features supported by this script. func_features () { - $ECHO "host: $host" + echo "host: $host" if test "$build_libtool_libs" = yes; then - $ECHO "enable shared libraries" + echo "enable shared libraries" else - $ECHO "disable shared libraries" + echo "disable shared libraries" fi if test "$build_old_libs" = yes; then - $ECHO "enable static libraries" + echo "enable static libraries" else - $ECHO "disable static libraries" + echo "disable static libraries" fi exit $? @@ -692,117 +975,209 @@ func_enable_tag () esac } -# Parse options once, thoroughly. This comes as soon as possible in -# the script to make things like `libtool --version' happen quickly. +# func_check_version_match +# Ensure that we are using m4 macros, and libtool script from the same +# release of libtool. +func_check_version_match () { + if test "$package_revision" != "$macro_revision"; then + if test "$VERSION" != "$macro_version"; then + if test -z "$macro_version"; then + cat >&2 <<_LT_EOF +$progname: Version mismatch error. This is $PACKAGE $VERSION, but the +$progname: definition of this LT_INIT comes from an older release. +$progname: You should recreate aclocal.m4 with macros from $PACKAGE $VERSION +$progname: and run autoconf again. +_LT_EOF + else + cat >&2 <<_LT_EOF +$progname: Version mismatch error. This is $PACKAGE $VERSION, but the +$progname: definition of this LT_INIT comes from $PACKAGE $macro_version. +$progname: You should recreate aclocal.m4 with macros from $PACKAGE $VERSION +$progname: and run autoconf again. +_LT_EOF + fi + else + cat >&2 <<_LT_EOF +$progname: Version mismatch error. This is $PACKAGE $VERSION, revision $package_revision, +$progname: but the definition of this LT_INIT comes from revision $macro_revision. +$progname: You should recreate aclocal.m4 with macros from revision $package_revision +$progname: of $PACKAGE $VERSION and run autoconf again. +_LT_EOF + fi + + exit $EXIT_MISMATCH + fi +} + + +# Shorthand for --mode=foo, only valid as the first argument +case $1 in +clean|clea|cle|cl) + shift; set dummy --mode clean ${1+"$@"}; shift + ;; +compile|compil|compi|comp|com|co|c) + shift; set dummy --mode compile ${1+"$@"}; shift + ;; +execute|execut|execu|exec|exe|ex|e) + shift; set dummy --mode execute ${1+"$@"}; shift + ;; +finish|finis|fini|fin|fi|f) + shift; set dummy --mode finish ${1+"$@"}; shift + ;; +install|instal|insta|inst|ins|in|i) + shift; set dummy --mode install ${1+"$@"}; shift + ;; +link|lin|li|l) + shift; set dummy --mode link ${1+"$@"}; shift + ;; +uninstall|uninstal|uninsta|uninst|unins|unin|uni|un|u) + shift; set dummy --mode uninstall ${1+"$@"}; shift + ;; +esac + + + +# Option defaults: +opt_debug=: +opt_dry_run=false +opt_config=false +opt_preserve_dup_deps=false +opt_features=false +opt_finish=false +opt_help=false +opt_help_all=false +opt_silent=: +opt_warning=: +opt_verbose=: +opt_silent=false +opt_verbose=false - # Shorthand for --mode=foo, only valid as the first argument - case $1 in - clean|clea|cle|cl) - shift; set dummy --mode clean ${1+"$@"}; shift - ;; - compile|compil|compi|comp|com|co|c) - shift; set dummy --mode compile ${1+"$@"}; shift - ;; - execute|execut|execu|exec|exe|ex|e) - shift; set dummy --mode execute ${1+"$@"}; shift - ;; - finish|finis|fini|fin|fi|f) - shift; set dummy --mode finish ${1+"$@"}; shift - ;; - install|instal|insta|inst|ins|in|i) - shift; set dummy --mode install ${1+"$@"}; shift - ;; - link|lin|li|l) - shift; set dummy --mode link ${1+"$@"}; shift - ;; - uninstall|uninstal|uninsta|uninst|unins|unin|uni|un|u) - shift; set dummy --mode uninstall ${1+"$@"}; shift - ;; - esac - # Parse non-mode specific arguments: - while test "$#" -gt 0; do +# Parse options once, thoroughly. This comes as soon as possible in the +# script to make things like `--version' happen as quickly as we can. +{ + # this just eases exit handling + while test $# -gt 0; do opt="$1" shift - case $opt in - --config) func_config ;; - - --debug) preserve_args="$preserve_args $opt" + --debug|-x) opt_debug='set -x' func_echo "enabling shell trace mode" - opt_debug='set -x' $opt_debug ;; - - -dlopen) test "$#" -eq 0 && func_missing_arg "$opt" && break - execute_dlfiles="$execute_dlfiles $1" - shift + --dry-run|--dryrun|-n) + opt_dry_run=: ;; - - --dry-run | -n) opt_dry_run=: ;; - --features) func_features ;; - --finish) mode="finish" ;; - - --mode) test "$#" -eq 0 && func_missing_arg "$opt" && break - case $1 in - # Valid mode arguments: - clean) ;; - compile) ;; - execute) ;; - finish) ;; - install) ;; - link) ;; - relink) ;; - uninstall) ;; - - # Catch anything else as an error - *) func_error "invalid argument for $opt" - exit_cmd=exit - break - ;; - esac - - mode="$1" + --config) + opt_config=: +func_config + ;; + --dlopen|-dlopen) + optarg="$1" + opt_dlopen="${opt_dlopen+$opt_dlopen +}$optarg" shift ;; - --preserve-dup-deps) - opt_duplicate_deps=: ;; - - --quiet|--silent) preserve_args="$preserve_args $opt" - opt_silent=: + opt_preserve_dup_deps=: ;; - - --verbose| -v) preserve_args="$preserve_args $opt" + --features) + opt_features=: +func_features + ;; + --finish) + opt_finish=: +set dummy --mode finish ${1+"$@"}; shift + ;; + --help) + opt_help=: + ;; + --help-all) + opt_help_all=: +opt_help=': help-all' + ;; + --mode) + test $# = 0 && func_missing_arg $opt && break + optarg="$1" + opt_mode="$optarg" +case $optarg in + # Valid mode arguments: + clean|compile|execute|finish|install|link|relink|uninstall) ;; + + # Catch anything else as an error + *) func_error "invalid argument for $opt" + exit_cmd=exit + break + ;; +esac + shift + ;; + --no-silent|--no-quiet) opt_silent=false +func_append preserve_args " $opt" ;; - - --tag) test "$#" -eq 0 && func_missing_arg "$opt" && break - preserve_args="$preserve_args $opt $1" - func_enable_tag "$1" # tagname is set here + --no-warning|--no-warn) + opt_warning=false +func_append preserve_args " $opt" + ;; + --no-verbose) + opt_verbose=false +func_append preserve_args " $opt" + ;; + --silent|--quiet) + opt_silent=: +func_append preserve_args " $opt" + opt_verbose=false + ;; + --verbose|-v) + opt_verbose=: +func_append preserve_args " $opt" +opt_silent=false + ;; + --tag) + test $# = 0 && func_missing_arg $opt && break + optarg="$1" + opt_tag="$optarg" +func_append preserve_args " $opt $optarg" +func_enable_tag "$optarg" shift ;; + -\?|-h) func_usage ;; + --help) func_help ;; + --version) func_version ;; + # Separate optargs to long options: - -dlopen=*|--mode=*|--tag=*) - func_opt_split "$opt" - set dummy "$func_opt_split_opt" "$func_opt_split_arg" ${1+"$@"} + --*=*) + func_split_long_opt "$opt" + set dummy "$func_split_long_opt_name" "$func_split_long_opt_arg" ${1+"$@"} shift ;; - -\?|-h) func_usage ;; - --help) opt_help=: ;; - --version) func_version ;; - - -*) func_fatal_help "unrecognized option \`$opt'" ;; - - *) nonopt="$opt" - break + # Separate non-argument short options: + -\?*|-h*|-n*|-v*) + func_split_short_opt "$opt" + set dummy "$func_split_short_opt_name" "-$func_split_short_opt_arg" ${1+"$@"} + shift ;; + + --) break ;; + -*) func_fatal_help "unrecognized option \`$opt'" ;; + *) set dummy "$opt" ${1+"$@"}; shift; break ;; esac done + # Validate options: + + # save first non-option argument + if test "$#" -gt 0; then + nonopt="$opt" + shift + fi + + # preserve --debug + test "$opt_debug" = : || func_append preserve_args " --debug" case $host in *cygwin* | *mingw* | *pw32* | *cegcc*) @@ -810,82 +1185,44 @@ func_enable_tag () opt_duplicate_compiler_generated_deps=: ;; *) - opt_duplicate_compiler_generated_deps=$opt_duplicate_deps + opt_duplicate_compiler_generated_deps=$opt_preserve_dup_deps ;; esac - # Having warned about all mis-specified options, bail out if - # anything was wrong. - $exit_cmd $EXIT_FAILURE -} + $opt_help || { + # Sanity checks first: + func_check_version_match -# func_check_version_match -# Ensure that we are using m4 macros, and libtool script from the same -# release of libtool. -func_check_version_match () -{ - if test "$package_revision" != "$macro_revision"; then - if test "$VERSION" != "$macro_version"; then - if test -z "$macro_version"; then - cat >&2 <<_LT_EOF -$progname: Version mismatch error. This is $PACKAGE $VERSION, but the -$progname: definition of this LT_INIT comes from an older release. -$progname: You should recreate aclocal.m4 with macros from $PACKAGE $VERSION -$progname: and run autoconf again. -_LT_EOF - else - cat >&2 <<_LT_EOF -$progname: Version mismatch error. This is $PACKAGE $VERSION, but the -$progname: definition of this LT_INIT comes from $PACKAGE $macro_version. -$progname: You should recreate aclocal.m4 with macros from $PACKAGE $VERSION -$progname: and run autoconf again. -_LT_EOF - fi - else - cat >&2 <<_LT_EOF -$progname: Version mismatch error. This is $PACKAGE $VERSION, revision $package_revision, -$progname: but the definition of this LT_INIT comes from revision $macro_revision. -$progname: You should recreate aclocal.m4 with macros from revision $package_revision -$progname: of $PACKAGE $VERSION and run autoconf again. -_LT_EOF + if test "$build_libtool_libs" != yes && test "$build_old_libs" != yes; then + func_fatal_configuration "not configured to build any kind of library" fi - exit $EXIT_MISMATCH - fi -} - - -## ----------- ## -## Main. ## -## ----------- ## - -$opt_help || { - # Sanity checks first: - func_check_version_match + # Darwin sucks + eval std_shrext=\"$shrext_cmds\" - if test "$build_libtool_libs" != yes && test "$build_old_libs" != yes; then - func_fatal_configuration "not configured to build any kind of library" - fi + # Only execute mode is allowed to have -dlopen flags. + if test -n "$opt_dlopen" && test "$opt_mode" != execute; then + func_error "unrecognized option \`-dlopen'" + $ECHO "$help" 1>&2 + exit $EXIT_FAILURE + fi - test -z "$mode" && func_fatal_error "error: you must specify a MODE." + # Change the help message to a mode-specific one. + generic_help="$help" + help="Try \`$progname --help --mode=$opt_mode' for more information." + } - # Darwin sucks - eval std_shrext=\"$shrext_cmds\" + # Bail if the options were screwed + $exit_cmd $EXIT_FAILURE +} - # Only execute mode is allowed to have -dlopen flags. - if test -n "$execute_dlfiles" && test "$mode" != execute; then - func_error "unrecognized option \`-dlopen'" - $ECHO "$help" 1>&2 - exit $EXIT_FAILURE - fi - # Change the help message to a mode-specific one. - generic_help="$help" - help="Try \`$progname --help --mode=$mode' for more information." -} +## ----------- ## +## Main. ## +## ----------- ## # func_lalib_p file # True iff FILE is a libtool `.la' library or `.lo' object file. @@ -950,12 +1287,9 @@ func_ltwrapper_executable_p () # temporary ltwrapper_script. func_ltwrapper_scriptname () { - func_ltwrapper_scriptname_result="" - if func_ltwrapper_executable_p "$1"; then - func_dirname_and_basename "$1" "" "." - func_stripname '' '.exe' "$func_basename_result" - func_ltwrapper_scriptname_result="$func_dirname_result/$objdir/${func_stripname_result}_ltshwrapper" - fi + func_dirname_and_basename "$1" "" "." + func_stripname '' '.exe' "$func_basename_result" + func_ltwrapper_scriptname_result="$func_dirname_result/$objdir/${func_stripname_result}_ltshwrapper" } # func_ltwrapper_p file @@ -1001,6 +1335,37 @@ func_source () } +# func_resolve_sysroot PATH +# Replace a leading = in PATH with a sysroot. Store the result into +# func_resolve_sysroot_result +func_resolve_sysroot () +{ + func_resolve_sysroot_result=$1 + case $func_resolve_sysroot_result in + =*) + func_stripname '=' '' "$func_resolve_sysroot_result" + func_resolve_sysroot_result=$lt_sysroot$func_stripname_result + ;; + esac +} + +# func_replace_sysroot PATH +# If PATH begins with the sysroot, replace it with = and +# store the result into func_replace_sysroot_result. +func_replace_sysroot () +{ + case "$lt_sysroot:$1" in + ?*:"$lt_sysroot"*) + func_stripname "$lt_sysroot" '' "$1" + func_replace_sysroot_result="=$func_stripname_result" + ;; + *) + # Including no sysroot. + func_replace_sysroot_result=$1 + ;; + esac +} + # func_infer_tag arg # Infer tagged configuration to use if any are available and # if one wasn't chosen via the "--tag" command line option. @@ -1013,13 +1378,15 @@ func_infer_tag () if test -n "$available_tags" && test -z "$tagname"; then CC_quoted= for arg in $CC; do - func_quote_for_eval "$arg" - CC_quoted="$CC_quoted $func_quote_for_eval_result" + func_append_quoted CC_quoted "$arg" done + CC_expanded=`func_echo_all $CC` + CC_quoted_expanded=`func_echo_all $CC_quoted` case $@ in # Blanks in the command may have been stripped by the calling shell, # but not from the CC environment variable when configure was run. - " $CC "* | "$CC "* | " `$ECHO $CC` "* | "`$ECHO $CC` "* | " $CC_quoted"* | "$CC_quoted "* | " `$ECHO $CC_quoted` "* | "`$ECHO $CC_quoted` "*) ;; + " $CC "* | "$CC "* | " $CC_expanded "* | "$CC_expanded "* | \ + " $CC_quoted"* | "$CC_quoted "* | " $CC_quoted_expanded "* | "$CC_quoted_expanded "*) ;; # Blanks at the start of $base_compile will cause this to fail # if we don't check for them as well. *) @@ -1030,11 +1397,13 @@ func_infer_tag () CC_quoted= for arg in $CC; do # Double-quote args containing other shell metacharacters. - func_quote_for_eval "$arg" - CC_quoted="$CC_quoted $func_quote_for_eval_result" + func_append_quoted CC_quoted "$arg" done + CC_expanded=`func_echo_all $CC` + CC_quoted_expanded=`func_echo_all $CC_quoted` case "$@ " in - " $CC "* | "$CC "* | " `$ECHO $CC` "* | "`$ECHO $CC` "* | " $CC_quoted"* | "$CC_quoted "* | " `$ECHO $CC_quoted` "* | "`$ECHO $CC_quoted` "*) + " $CC "* | "$CC "* | " $CC_expanded "* | "$CC_expanded "* | \ + " $CC_quoted"* | "$CC_quoted "* | " $CC_quoted_expanded "* | "$CC_quoted_expanded "*) # The compiler in the base compile command matches # the one in the tagged configuration. # Assume this is the tagged configuration we want. @@ -1097,6 +1466,486 @@ EOF } } + +################################################## +# FILE NAME AND PATH CONVERSION HELPER FUNCTIONS # +################################################## + +# func_convert_core_file_wine_to_w32 ARG +# Helper function used by file name conversion functions when $build is *nix, +# and $host is mingw, cygwin, or some other w32 environment. Relies on a +# correctly configured wine environment available, with the winepath program +# in $build's $PATH. +# +# ARG is the $build file name to be converted to w32 format. +# Result is available in $func_convert_core_file_wine_to_w32_result, and will +# be empty on error (or when ARG is empty) +func_convert_core_file_wine_to_w32 () +{ + $opt_debug + func_convert_core_file_wine_to_w32_result="$1" + if test -n "$1"; then + # Unfortunately, winepath does not exit with a non-zero error code, so we + # are forced to check the contents of stdout. On the other hand, if the + # command is not found, the shell will set an exit code of 127 and print + # *an error message* to stdout. So we must check for both error code of + # zero AND non-empty stdout, which explains the odd construction: + func_convert_core_file_wine_to_w32_tmp=`winepath -w "$1" 2>/dev/null` + if test "$?" -eq 0 && test -n "${func_convert_core_file_wine_to_w32_tmp}"; then + func_convert_core_file_wine_to_w32_result=`$ECHO "$func_convert_core_file_wine_to_w32_tmp" | + $SED -e "$lt_sed_naive_backslashify"` + else + func_convert_core_file_wine_to_w32_result= + fi + fi +} +# end: func_convert_core_file_wine_to_w32 + + +# func_convert_core_path_wine_to_w32 ARG +# Helper function used by path conversion functions when $build is *nix, and +# $host is mingw, cygwin, or some other w32 environment. Relies on a correctly +# configured wine environment available, with the winepath program in $build's +# $PATH. Assumes ARG has no leading or trailing path separator characters. +# +# ARG is path to be converted from $build format to win32. +# Result is available in $func_convert_core_path_wine_to_w32_result. +# Unconvertible file (directory) names in ARG are skipped; if no directory names +# are convertible, then the result may be empty. +func_convert_core_path_wine_to_w32 () +{ + $opt_debug + # unfortunately, winepath doesn't convert paths, only file names + func_convert_core_path_wine_to_w32_result="" + if test -n "$1"; then + oldIFS=$IFS + IFS=: + for func_convert_core_path_wine_to_w32_f in $1; do + IFS=$oldIFS + func_convert_core_file_wine_to_w32 "$func_convert_core_path_wine_to_w32_f" + if test -n "$func_convert_core_file_wine_to_w32_result" ; then + if test -z "$func_convert_core_path_wine_to_w32_result"; then + func_convert_core_path_wine_to_w32_result="$func_convert_core_file_wine_to_w32_result" + else + func_append func_convert_core_path_wine_to_w32_result ";$func_convert_core_file_wine_to_w32_result" + fi + fi + done + IFS=$oldIFS + fi +} +# end: func_convert_core_path_wine_to_w32 + + +# func_cygpath ARGS... +# Wrapper around calling the cygpath program via LT_CYGPATH. This is used when +# when (1) $build is *nix and Cygwin is hosted via a wine environment; or (2) +# $build is MSYS and $host is Cygwin, or (3) $build is Cygwin. In case (1) or +# (2), returns the Cygwin file name or path in func_cygpath_result (input +# file name or path is assumed to be in w32 format, as previously converted +# from $build's *nix or MSYS format). In case (3), returns the w32 file name +# or path in func_cygpath_result (input file name or path is assumed to be in +# Cygwin format). Returns an empty string on error. +# +# ARGS are passed to cygpath, with the last one being the file name or path to +# be converted. +# +# Specify the absolute *nix (or w32) name to cygpath in the LT_CYGPATH +# environment variable; do not put it in $PATH. +func_cygpath () +{ + $opt_debug + if test -n "$LT_CYGPATH" && test -f "$LT_CYGPATH"; then + func_cygpath_result=`$LT_CYGPATH "$@" 2>/dev/null` + if test "$?" -ne 0; then + # on failure, ensure result is empty + func_cygpath_result= + fi + else + func_cygpath_result= + func_error "LT_CYGPATH is empty or specifies non-existent file: \`$LT_CYGPATH'" + fi +} +#end: func_cygpath + + +# func_convert_core_msys_to_w32 ARG +# Convert file name or path ARG from MSYS format to w32 format. Return +# result in func_convert_core_msys_to_w32_result. +func_convert_core_msys_to_w32 () +{ + $opt_debug + # awkward: cmd appends spaces to result + func_convert_core_msys_to_w32_result=`( cmd //c echo "$1" ) 2>/dev/null | + $SED -e 's/[ ]*$//' -e "$lt_sed_naive_backslashify"` +} +#end: func_convert_core_msys_to_w32 + + +# func_convert_file_check ARG1 ARG2 +# Verify that ARG1 (a file name in $build format) was converted to $host +# format in ARG2. Otherwise, emit an error message, but continue (resetting +# func_to_host_file_result to ARG1). +func_convert_file_check () +{ + $opt_debug + if test -z "$2" && test -n "$1" ; then + func_error "Could not determine host file name corresponding to" + func_error " \`$1'" + func_error "Continuing, but uninstalled executables may not work." + # Fallback: + func_to_host_file_result="$1" + fi +} +# end func_convert_file_check + + +# func_convert_path_check FROM_PATHSEP TO_PATHSEP FROM_PATH TO_PATH +# Verify that FROM_PATH (a path in $build format) was converted to $host +# format in TO_PATH. Otherwise, emit an error message, but continue, resetting +# func_to_host_file_result to a simplistic fallback value (see below). +func_convert_path_check () +{ + $opt_debug + if test -z "$4" && test -n "$3"; then + func_error "Could not determine the host path corresponding to" + func_error " \`$3'" + func_error "Continuing, but uninstalled executables may not work." + # Fallback. This is a deliberately simplistic "conversion" and + # should not be "improved". See libtool.info. + if test "x$1" != "x$2"; then + lt_replace_pathsep_chars="s|$1|$2|g" + func_to_host_path_result=`echo "$3" | + $SED -e "$lt_replace_pathsep_chars"` + else + func_to_host_path_result="$3" + fi + fi +} +# end func_convert_path_check + + +# func_convert_path_front_back_pathsep FRONTPAT BACKPAT REPL ORIG +# Modifies func_to_host_path_result by prepending REPL if ORIG matches FRONTPAT +# and appending REPL if ORIG matches BACKPAT. +func_convert_path_front_back_pathsep () +{ + $opt_debug + case $4 in + $1 ) func_to_host_path_result="$3$func_to_host_path_result" + ;; + esac + case $4 in + $2 ) func_append func_to_host_path_result "$3" + ;; + esac +} +# end func_convert_path_front_back_pathsep + + +################################################## +# $build to $host FILE NAME CONVERSION FUNCTIONS # +################################################## +# invoked via `$to_host_file_cmd ARG' +# +# In each case, ARG is the path to be converted from $build to $host format. +# Result will be available in $func_to_host_file_result. + + +# func_to_host_file ARG +# Converts the file name ARG from $build format to $host format. Return result +# in func_to_host_file_result. +func_to_host_file () +{ + $opt_debug + $to_host_file_cmd "$1" +} +# end func_to_host_file + + +# func_to_tool_file ARG LAZY +# converts the file name ARG from $build format to toolchain format. Return +# result in func_to_tool_file_result. If the conversion in use is listed +# in (the comma separated) LAZY, no conversion takes place. +func_to_tool_file () +{ + $opt_debug + case ,$2, in + *,"$to_tool_file_cmd",*) + func_to_tool_file_result=$1 + ;; + *) + $to_tool_file_cmd "$1" + func_to_tool_file_result=$func_to_host_file_result + ;; + esac +} +# end func_to_tool_file + + +# func_convert_file_noop ARG +# Copy ARG to func_to_host_file_result. +func_convert_file_noop () +{ + func_to_host_file_result="$1" +} +# end func_convert_file_noop + + +# func_convert_file_msys_to_w32 ARG +# Convert file name ARG from (mingw) MSYS to (mingw) w32 format; automatic +# conversion to w32 is not available inside the cwrapper. Returns result in +# func_to_host_file_result. +func_convert_file_msys_to_w32 () +{ + $opt_debug + func_to_host_file_result="$1" + if test -n "$1"; then + func_convert_core_msys_to_w32 "$1" + func_to_host_file_result="$func_convert_core_msys_to_w32_result" + fi + func_convert_file_check "$1" "$func_to_host_file_result" +} +# end func_convert_file_msys_to_w32 + + +# func_convert_file_cygwin_to_w32 ARG +# Convert file name ARG from Cygwin to w32 format. Returns result in +# func_to_host_file_result. +func_convert_file_cygwin_to_w32 () +{ + $opt_debug + func_to_host_file_result="$1" + if test -n "$1"; then + # because $build is cygwin, we call "the" cygpath in $PATH; no need to use + # LT_CYGPATH in this case. + func_to_host_file_result=`cygpath -m "$1"` + fi + func_convert_file_check "$1" "$func_to_host_file_result" +} +# end func_convert_file_cygwin_to_w32 + + +# func_convert_file_nix_to_w32 ARG +# Convert file name ARG from *nix to w32 format. Requires a wine environment +# and a working winepath. Returns result in func_to_host_file_result. +func_convert_file_nix_to_w32 () +{ + $opt_debug + func_to_host_file_result="$1" + if test -n "$1"; then + func_convert_core_file_wine_to_w32 "$1" + func_to_host_file_result="$func_convert_core_file_wine_to_w32_result" + fi + func_convert_file_check "$1" "$func_to_host_file_result" +} +# end func_convert_file_nix_to_w32 + + +# func_convert_file_msys_to_cygwin ARG +# Convert file name ARG from MSYS to Cygwin format. Requires LT_CYGPATH set. +# Returns result in func_to_host_file_result. +func_convert_file_msys_to_cygwin () +{ + $opt_debug + func_to_host_file_result="$1" + if test -n "$1"; then + func_convert_core_msys_to_w32 "$1" + func_cygpath -u "$func_convert_core_msys_to_w32_result" + func_to_host_file_result="$func_cygpath_result" + fi + func_convert_file_check "$1" "$func_to_host_file_result" +} +# end func_convert_file_msys_to_cygwin + + +# func_convert_file_nix_to_cygwin ARG +# Convert file name ARG from *nix to Cygwin format. Requires Cygwin installed +# in a wine environment, working winepath, and LT_CYGPATH set. Returns result +# in func_to_host_file_result. +func_convert_file_nix_to_cygwin () +{ + $opt_debug + func_to_host_file_result="$1" + if test -n "$1"; then + # convert from *nix to w32, then use cygpath to convert from w32 to cygwin. + func_convert_core_file_wine_to_w32 "$1" + func_cygpath -u "$func_convert_core_file_wine_to_w32_result" + func_to_host_file_result="$func_cygpath_result" + fi + func_convert_file_check "$1" "$func_to_host_file_result" +} +# end func_convert_file_nix_to_cygwin + + +############################################# +# $build to $host PATH CONVERSION FUNCTIONS # +############################################# +# invoked via `$to_host_path_cmd ARG' +# +# In each case, ARG is the path to be converted from $build to $host format. +# The result will be available in $func_to_host_path_result. +# +# Path separators are also converted from $build format to $host format. If +# ARG begins or ends with a path separator character, it is preserved (but +# converted to $host format) on output. +# +# All path conversion functions are named using the following convention: +# file name conversion function : func_convert_file_X_to_Y () +# path conversion function : func_convert_path_X_to_Y () +# where, for any given $build/$host combination the 'X_to_Y' value is the +# same. If conversion functions are added for new $build/$host combinations, +# the two new functions must follow this pattern, or func_init_to_host_path_cmd +# will break. + + +# func_init_to_host_path_cmd +# Ensures that function "pointer" variable $to_host_path_cmd is set to the +# appropriate value, based on the value of $to_host_file_cmd. +to_host_path_cmd= +func_init_to_host_path_cmd () +{ + $opt_debug + if test -z "$to_host_path_cmd"; then + func_stripname 'func_convert_file_' '' "$to_host_file_cmd" + to_host_path_cmd="func_convert_path_${func_stripname_result}" + fi +} + + +# func_to_host_path ARG +# Converts the path ARG from $build format to $host format. Return result +# in func_to_host_path_result. +func_to_host_path () +{ + $opt_debug + func_init_to_host_path_cmd + $to_host_path_cmd "$1" +} +# end func_to_host_path + + +# func_convert_path_noop ARG +# Copy ARG to func_to_host_path_result. +func_convert_path_noop () +{ + func_to_host_path_result="$1" +} +# end func_convert_path_noop + + +# func_convert_path_msys_to_w32 ARG +# Convert path ARG from (mingw) MSYS to (mingw) w32 format; automatic +# conversion to w32 is not available inside the cwrapper. Returns result in +# func_to_host_path_result. +func_convert_path_msys_to_w32 () +{ + $opt_debug + func_to_host_path_result="$1" + if test -n "$1"; then + # Remove leading and trailing path separator characters from ARG. MSYS + # behavior is inconsistent here; cygpath turns them into '.;' and ';.'; + # and winepath ignores them completely. + func_stripname : : "$1" + func_to_host_path_tmp1=$func_stripname_result + func_convert_core_msys_to_w32 "$func_to_host_path_tmp1" + func_to_host_path_result="$func_convert_core_msys_to_w32_result" + func_convert_path_check : ";" \ + "$func_to_host_path_tmp1" "$func_to_host_path_result" + func_convert_path_front_back_pathsep ":*" "*:" ";" "$1" + fi +} +# end func_convert_path_msys_to_w32 + + +# func_convert_path_cygwin_to_w32 ARG +# Convert path ARG from Cygwin to w32 format. Returns result in +# func_to_host_file_result. +func_convert_path_cygwin_to_w32 () +{ + $opt_debug + func_to_host_path_result="$1" + if test -n "$1"; then + # See func_convert_path_msys_to_w32: + func_stripname : : "$1" + func_to_host_path_tmp1=$func_stripname_result + func_to_host_path_result=`cygpath -m -p "$func_to_host_path_tmp1"` + func_convert_path_check : ";" \ + "$func_to_host_path_tmp1" "$func_to_host_path_result" + func_convert_path_front_back_pathsep ":*" "*:" ";" "$1" + fi +} +# end func_convert_path_cygwin_to_w32 + + +# func_convert_path_nix_to_w32 ARG +# Convert path ARG from *nix to w32 format. Requires a wine environment and +# a working winepath. Returns result in func_to_host_file_result. +func_convert_path_nix_to_w32 () +{ + $opt_debug + func_to_host_path_result="$1" + if test -n "$1"; then + # See func_convert_path_msys_to_w32: + func_stripname : : "$1" + func_to_host_path_tmp1=$func_stripname_result + func_convert_core_path_wine_to_w32 "$func_to_host_path_tmp1" + func_to_host_path_result="$func_convert_core_path_wine_to_w32_result" + func_convert_path_check : ";" \ + "$func_to_host_path_tmp1" "$func_to_host_path_result" + func_convert_path_front_back_pathsep ":*" "*:" ";" "$1" + fi +} +# end func_convert_path_nix_to_w32 + + +# func_convert_path_msys_to_cygwin ARG +# Convert path ARG from MSYS to Cygwin format. Requires LT_CYGPATH set. +# Returns result in func_to_host_file_result. +func_convert_path_msys_to_cygwin () +{ + $opt_debug + func_to_host_path_result="$1" + if test -n "$1"; then + # See func_convert_path_msys_to_w32: + func_stripname : : "$1" + func_to_host_path_tmp1=$func_stripname_result + func_convert_core_msys_to_w32 "$func_to_host_path_tmp1" + func_cygpath -u -p "$func_convert_core_msys_to_w32_result" + func_to_host_path_result="$func_cygpath_result" + func_convert_path_check : : \ + "$func_to_host_path_tmp1" "$func_to_host_path_result" + func_convert_path_front_back_pathsep ":*" "*:" : "$1" + fi +} +# end func_convert_path_msys_to_cygwin + + +# func_convert_path_nix_to_cygwin ARG +# Convert path ARG from *nix to Cygwin format. Requires Cygwin installed in a +# a wine environment, working winepath, and LT_CYGPATH set. Returns result in +# func_to_host_file_result. +func_convert_path_nix_to_cygwin () +{ + $opt_debug + func_to_host_path_result="$1" + if test -n "$1"; then + # Remove leading and trailing path separator characters from + # ARG. msys behavior is inconsistent here, cygpath turns them + # into '.;' and ';.', and winepath ignores them completely. + func_stripname : : "$1" + func_to_host_path_tmp1=$func_stripname_result + func_convert_core_path_wine_to_w32 "$func_to_host_path_tmp1" + func_cygpath -u -p "$func_convert_core_path_wine_to_w32_result" + func_to_host_path_result="$func_cygpath_result" + func_convert_path_check : : \ + "$func_to_host_path_tmp1" "$func_to_host_path_result" + func_convert_path_front_back_pathsep ":*" "*:" : "$1" + fi +} +# end func_convert_path_nix_to_cygwin + + # func_mode_compile arg... func_mode_compile () { @@ -1137,12 +1986,12 @@ func_mode_compile () ;; -pie | -fpie | -fPIE) - pie_flag="$pie_flag $arg" + func_append pie_flag " $arg" continue ;; -shared | -static | -prefer-pic | -prefer-non-pic) - later="$later $arg" + func_append later " $arg" continue ;; @@ -1163,15 +2012,14 @@ func_mode_compile () save_ifs="$IFS"; IFS=',' for arg in $args; do IFS="$save_ifs" - func_quote_for_eval "$arg" - lastarg="$lastarg $func_quote_for_eval_result" + func_append_quoted lastarg "$arg" done IFS="$save_ifs" func_stripname ' ' '' "$lastarg" lastarg=$func_stripname_result # Add the arguments to base_compile. - base_compile="$base_compile $lastarg" + func_append base_compile " $lastarg" continue ;; @@ -1187,8 +2035,7 @@ func_mode_compile () esac # case $arg_mode # Aesthetically quote the previous argument. - func_quote_for_eval "$lastarg" - base_compile="$base_compile $func_quote_for_eval_result" + func_append_quoted base_compile "$lastarg" done # for arg case $arg_mode in @@ -1213,7 +2060,7 @@ func_mode_compile () *.[cCFSifmso] | \ *.ada | *.adb | *.ads | *.asm | \ *.c++ | *.cc | *.ii | *.class | *.cpp | *.cxx | \ - *.[fF][09]? | *.for | *.java | *.obj | *.sx) + *.[fF][09]? | *.for | *.java | *.go | *.obj | *.sx | *.cu | *.cup) func_xform "$libobj" libobj=$func_xform_result ;; @@ -1288,7 +2135,7 @@ func_mode_compile () # Calculate the filename of the output object if compiler does # not support -o with -c if test "$compiler_c_o" = no; then - output_obj=`$ECHO "X$srcfile" | $Xsed -e 's%^.*/%%' -e 's%\.[^.]*$%%'`.${objext} + output_obj=`$ECHO "$srcfile" | $SED 's%^.*/%%; s%\.[^.]*$%%'`.${objext} lockfile="$output_obj.lock" else output_obj= @@ -1319,17 +2166,16 @@ compiler." $opt_dry_run || $RM $removelist exit $EXIT_FAILURE fi - removelist="$removelist $output_obj" + func_append removelist " $output_obj" $ECHO "$srcfile" > "$lockfile" fi $opt_dry_run || $RM $removelist - removelist="$removelist $lockfile" + func_append removelist " $lockfile" trap '$opt_dry_run || $RM $removelist; exit $EXIT_FAILURE' 1 2 15 - if test -n "$fix_srcfile_path"; then - eval srcfile=\"$fix_srcfile_path\" - fi + func_to_tool_file "$srcfile" func_convert_file_msys_to_w32 + srcfile=$func_to_tool_file_result func_quote_for_eval "$srcfile" qsrcfile=$func_quote_for_eval_result @@ -1349,7 +2195,7 @@ compiler." if test -z "$output_obj"; then # Place PIC objects in $objdir - command="$command -o $lobj" + func_append command " -o $lobj" fi func_show_eval_locale "$command" \ @@ -1396,11 +2242,11 @@ compiler." command="$base_compile $qsrcfile $pic_flag" fi if test "$compiler_c_o" = yes; then - command="$command -o $obj" + func_append command " -o $obj" fi # Suppress compiler output if we already did a PIC compilation. - command="$command$suppress_output" + func_append command "$suppress_output" func_show_eval_locale "$command" \ '$opt_dry_run || $RM $removelist; exit $EXIT_FAILURE' @@ -1445,13 +2291,13 @@ compiler." } $opt_help || { -test "$mode" = compile && func_mode_compile ${1+"$@"} + test "$opt_mode" = compile && func_mode_compile ${1+"$@"} } func_mode_help () { # We need to display help for each of the modes. - case $mode in + case $opt_mode in "") # Generic help is extracted from the usage comments # at the start of this file. @@ -1482,10 +2328,11 @@ This mode accepts the following additional options: -o OUTPUT-FILE set the output file name to OUTPUT-FILE -no-suppress do not suppress compiler output for multiple passes - -prefer-pic try to building PIC objects only - -prefer-non-pic try to building non-PIC objects only + -prefer-pic try to build PIC objects only + -prefer-non-pic try to build non-PIC objects only -shared do not build a \`.o' file suitable for static linking -static only build a \`.o' file suitable for static linking + -Wc,FLAG pass FLAG directly to the compiler COMPILE-COMMAND is a command to be used in creating a \`standard' object file from the given SOURCEFILE. @@ -1538,7 +2385,7 @@ either the \`install' or \`cp' program. The following components of INSTALL-COMMAND are treated specially: - -inst-prefix PREFIX-DIR Use PREFIX-DIR as a staging area for installation + -inst-prefix-dir PREFIX-DIR Use PREFIX-DIR as a staging area for installation The rest of the components are interpreted as arguments to that command (only BSD-compatible install options are recognized)." @@ -1558,6 +2405,8 @@ The following components of LINK-COMMAND are treated specially: -all-static do not do any dynamic linking at all -avoid-version do not add a version suffix if possible + -bindir BINDIR specify path to binaries directory (for systems where + libraries must be found in the PATH setting at runtime) -dlopen FILE \`-dlpreopen' FILE if it cannot be dlopened at runtime -dlpreopen FILE link in FILE and add its symbols to lt_preloaded_symbols -export-dynamic allow symbols from OUTPUT-FILE to be resolved with dlsym(3) @@ -1586,6 +2435,11 @@ The following components of LINK-COMMAND are treated specially: -version-info CURRENT[:REVISION[:AGE]] specify library version info [each variable defaults to 0] -weak LIBNAME declare that the target provides the LIBNAME interface + -Wc,FLAG + -Xcompiler FLAG pass linker-specific FLAG directly to the compiler + -Wl,FLAG + -Xlinker FLAG pass linker-specific FLAG directly to the linker + -XCClinker FLAG pass link-specific FLAG to the compiler driver (CC) All other options (arguments beginning with \`-') are ignored. @@ -1619,18 +2473,44 @@ Otherwise, only FILE itself is deleted using RM." ;; *) - func_fatal_help "invalid operation mode \`$mode'" + func_fatal_help "invalid operation mode \`$opt_mode'" ;; esac - $ECHO + echo $ECHO "Try \`$progname --help' for more information about other modes." - - exit $? } - # Now that we've collected a possible --mode arg, show help if necessary - $opt_help && func_mode_help +# Now that we've collected a possible --mode arg, show help if necessary +if $opt_help; then + if test "$opt_help" = :; then + func_mode_help + else + { + func_help noexit + for opt_mode in compile link execute install finish uninstall clean; do + func_mode_help + done + } | sed -n '1p; 2,$s/^Usage:/ or: /p' + { + func_help noexit + for opt_mode in compile link execute install finish uninstall clean; do + echo + func_mode_help + done + } | + sed '1d + /^When reporting/,/^Report/{ + H + d + } + $x + /information about other modes/d + /more detailed .*MODE/d + s/^Usage:.*--mode=\([^ ]*\) .*/Description of \1 mode:/' + fi + exit $? +fi # func_mode_execute arg... @@ -1643,13 +2523,16 @@ func_mode_execute () func_fatal_help "you must specify a COMMAND" # Handle -dlopen flags immediately. - for file in $execute_dlfiles; do + for file in $opt_dlopen; do test -f "$file" \ || func_fatal_help "\`$file' is not a file" dir= case $file in *.la) + func_resolve_sysroot "$file" + file=$func_resolve_sysroot_result + # Check to see that this really is a libtool archive. func_lalib_unsafe_p "$file" \ || func_fatal_help "\`$lib' is not a valid libtool archive" @@ -1671,7 +2554,7 @@ func_mode_execute () dir="$func_dirname_result" if test -f "$dir/$objdir/$dlname"; then - dir="$dir/$objdir" + func_append dir "/$objdir" else if test ! -f "$dir/$dlname"; then func_fatal_error "cannot find \`$dlname' in \`$dir' or \`$dir/$objdir'" @@ -1712,7 +2595,7 @@ func_mode_execute () for file do case $file in - -*) ;; + -* | *.la | *.lo ) ;; *) # Do a test to see if this is really a libtool program. if func_ltwrapper_script_p "$file"; then @@ -1728,8 +2611,7 @@ func_mode_execute () ;; esac # Quote arguments (to preserve shell metacharacters). - func_quote_for_eval "$file" - args="$args $func_quote_for_eval_result" + func_append_quoted args "$file" done if test "X$opt_dry_run" = Xfalse; then @@ -1754,29 +2636,66 @@ func_mode_execute () # Display what would be done. if test -n "$shlibpath_var"; then eval "\$ECHO \"\$shlibpath_var=\$$shlibpath_var\"" - $ECHO "export $shlibpath_var" + echo "export $shlibpath_var" fi $ECHO "$cmd$args" exit $EXIT_SUCCESS fi } -test "$mode" = execute && func_mode_execute ${1+"$@"} +test "$opt_mode" = execute && func_mode_execute ${1+"$@"} # func_mode_finish arg... func_mode_finish () { $opt_debug - libdirs="$nonopt" + libs= + libdirs= admincmds= - if test -n "$finish_cmds$finish_eval" && test -n "$libdirs"; then - for dir - do - libdirs="$libdirs $dir" - done + for opt in "$nonopt" ${1+"$@"} + do + if test -d "$opt"; then + func_append libdirs " $opt" + + elif test -f "$opt"; then + if func_lalib_unsafe_p "$opt"; then + func_append libs " $opt" + else + func_warning "\`$opt' is not a valid libtool archive" + fi + + else + func_fatal_error "invalid argument \`$opt'" + fi + done + + if test -n "$libs"; then + if test -n "$lt_sysroot"; then + sysroot_regex=`$ECHO "$lt_sysroot" | $SED "$sed_make_literal_regex"` + sysroot_cmd="s/\([ ']\)$sysroot_regex/\1/g;" + else + sysroot_cmd= + fi + + # Remove sysroot references + if $opt_dry_run; then + for lib in $libs; do + echo "removing references to $lt_sysroot and \`=' prefixes from $lib" + done + else + tmpdir=`func_mktempdir` + for lib in $libs; do + sed -e "${sysroot_cmd} s/\([ ']-[LR]\)=/\1/g; s/\([ ']\)=/\1/g" $lib \ + > $tmpdir/tmp-la + mv -f $tmpdir/tmp-la $lib + done + ${RM}r "$tmpdir" + fi + fi + if test -n "$finish_cmds$finish_eval" && test -n "$libdirs"; then for libdir in $libdirs; do if test -n "$finish_cmds"; then # Do each command in the finish commands. @@ -1786,7 +2705,7 @@ func_mode_finish () if test -n "$finish_eval"; then # Do the single finish_eval. eval cmds=\"$finish_eval\" - $opt_dry_run || eval "$cmds" || admincmds="$admincmds + $opt_dry_run || eval "$cmds" || func_append admincmds " $cmds" fi done @@ -1795,53 +2714,55 @@ func_mode_finish () # Exit here if they wanted silent mode. $opt_silent && exit $EXIT_SUCCESS - $ECHO "X----------------------------------------------------------------------" | $Xsed - $ECHO "Libraries have been installed in:" - for libdir in $libdirs; do - $ECHO " $libdir" - done - $ECHO - $ECHO "If you ever happen to want to link against installed libraries" - $ECHO "in a given directory, LIBDIR, you must either use libtool, and" - $ECHO "specify the full pathname of the library, or use the \`-LLIBDIR'" - $ECHO "flag during linking and do at least one of the following:" - if test -n "$shlibpath_var"; then - $ECHO " - add LIBDIR to the \`$shlibpath_var' environment variable" - $ECHO " during execution" - fi - if test -n "$runpath_var"; then - $ECHO " - add LIBDIR to the \`$runpath_var' environment variable" - $ECHO " during linking" - fi - if test -n "$hardcode_libdir_flag_spec"; then - libdir=LIBDIR - eval flag=\"$hardcode_libdir_flag_spec\" + if test -n "$finish_cmds$finish_eval" && test -n "$libdirs"; then + echo "----------------------------------------------------------------------" + echo "Libraries have been installed in:" + for libdir in $libdirs; do + $ECHO " $libdir" + done + echo + echo "If you ever happen to want to link against installed libraries" + echo "in a given directory, LIBDIR, you must either use libtool, and" + echo "specify the full pathname of the library, or use the \`-LLIBDIR'" + echo "flag during linking and do at least one of the following:" + if test -n "$shlibpath_var"; then + echo " - add LIBDIR to the \`$shlibpath_var' environment variable" + echo " during execution" + fi + if test -n "$runpath_var"; then + echo " - add LIBDIR to the \`$runpath_var' environment variable" + echo " during linking" + fi + if test -n "$hardcode_libdir_flag_spec"; then + libdir=LIBDIR + eval flag=\"$hardcode_libdir_flag_spec\" - $ECHO " - use the \`$flag' linker flag" - fi - if test -n "$admincmds"; then - $ECHO " - have your system administrator run these commands:$admincmds" - fi - if test -f /etc/ld.so.conf; then - $ECHO " - have your system administrator add LIBDIR to \`/etc/ld.so.conf'" - fi - $ECHO + $ECHO " - use the \`$flag' linker flag" + fi + if test -n "$admincmds"; then + $ECHO " - have your system administrator run these commands:$admincmds" + fi + if test -f /etc/ld.so.conf; then + echo " - have your system administrator add LIBDIR to \`/etc/ld.so.conf'" + fi + echo - $ECHO "See any operating system documentation about shared libraries for" - case $host in - solaris2.[6789]|solaris2.1[0-9]) - $ECHO "more information, such as the ld(1), crle(1) and ld.so(8) manual" - $ECHO "pages." - ;; - *) - $ECHO "more information, such as the ld(1) and ld.so(8) manual pages." - ;; - esac - $ECHO "X----------------------------------------------------------------------" | $Xsed + echo "See any operating system documentation about shared libraries for" + case $host in + solaris2.[6789]|solaris2.1[0-9]) + echo "more information, such as the ld(1), crle(1) and ld.so(8) manual" + echo "pages." + ;; + *) + echo "more information, such as the ld(1) and ld.so(8) manual pages." + ;; + esac + echo "----------------------------------------------------------------------" + fi exit $EXIT_SUCCESS } -test "$mode" = finish && func_mode_finish ${1+"$@"} +test "$opt_mode" = finish && func_mode_finish ${1+"$@"} # func_mode_install arg... @@ -1852,7 +2773,7 @@ func_mode_install () # install_prog (especially on Windows NT). if test "$nonopt" = "$SHELL" || test "$nonopt" = /bin/sh || # Allow the use of GNU shtool's install command. - $ECHO "X$nonopt" | $GREP shtool >/dev/null; then + case $nonopt in *shtool*) :;; *) false;; esac; then # Aesthetically quote it. func_quote_for_eval "$nonopt" install_prog="$func_quote_for_eval_result " @@ -1866,7 +2787,12 @@ func_mode_install () # The real first argument should be the name of the installation program. # Aesthetically quote it. func_quote_for_eval "$arg" - install_prog="$install_prog$func_quote_for_eval_result" + func_append install_prog "$func_quote_for_eval_result" + install_shared_prog=$install_prog + case " $install_prog " in + *[\\\ /]cp\ *) install_cp=: ;; + *) install_cp=false ;; + esac # We need to accept at least all the BSD install flags. dest= @@ -1876,10 +2802,12 @@ func_mode_install () install_type= isdir=no stripme= + no_mode=: for arg do + arg2= if test -n "$dest"; then - files="$files $dest" + func_append files " $dest" dest=$arg continue fi @@ -1887,10 +2815,9 @@ func_mode_install () case $arg in -d) isdir=yes ;; -f) - case " $install_prog " in - *[\\\ /]cp\ *) ;; - *) prev=$arg ;; - esac + if $install_cp; then :; else + prev=$arg + fi ;; -g | -m | -o) prev=$arg @@ -1904,6 +2831,10 @@ func_mode_install () *) # If the previous option needed an argument, then skip it. if test -n "$prev"; then + if test "x$prev" = x-m && test -n "$install_override_mode"; then + arg2=$install_override_mode + no_mode=false + fi prev= else dest=$arg @@ -1914,7 +2845,11 @@ func_mode_install () # Aesthetically quote the argument. func_quote_for_eval "$arg" - install_prog="$install_prog $func_quote_for_eval_result" + func_append install_prog " $func_quote_for_eval_result" + if test -n "$arg2"; then + func_quote_for_eval "$arg2" + fi + func_append install_shared_prog " $func_quote_for_eval_result" done test -z "$install_prog" && \ @@ -1923,6 +2858,13 @@ func_mode_install () test -n "$prev" && \ func_fatal_help "the \`$prev' option requires an argument" + if test -n "$install_override_mode" && $no_mode; then + if $install_cp; then :; else + func_quote_for_eval "$install_override_mode" + func_append install_shared_prog " -m $func_quote_for_eval_result" + fi + fi + if test -z "$files"; then if test -z "$dest"; then func_fatal_help "no file or destination specified" @@ -1977,10 +2919,13 @@ func_mode_install () case $file in *.$libext) # Do the static libraries later. - staticlibs="$staticlibs $file" + func_append staticlibs " $file" ;; *.la) + func_resolve_sysroot "$file" + file=$func_resolve_sysroot_result + # Check to see that this really is a libtool archive. func_lalib_unsafe_p "$file" \ || func_fatal_help "\`$file' is not a valid libtool archive" @@ -1994,23 +2939,23 @@ func_mode_install () if test "X$destdir" = "X$libdir"; then case "$current_libdirs " in *" $libdir "*) ;; - *) current_libdirs="$current_libdirs $libdir" ;; + *) func_append current_libdirs " $libdir" ;; esac else # Note the libdir as a future libdir. case "$future_libdirs " in *" $libdir "*) ;; - *) future_libdirs="$future_libdirs $libdir" ;; + *) func_append future_libdirs " $libdir" ;; esac fi func_dirname "$file" "/" "" dir="$func_dirname_result" - dir="$dir$objdir" + func_append dir "$objdir" if test -n "$relink_command"; then # Determine the prefix the user has applied to our future dir. - inst_prefix_dir=`$ECHO "X$destdir" | $Xsed -e "s%$libdir\$%%"` + inst_prefix_dir=`$ECHO "$destdir" | $SED -e "s%$libdir\$%%"` # Don't allow the user to place us outside of our expected # location b/c this prevents finding dependent libraries that @@ -2023,9 +2968,9 @@ func_mode_install () if test -n "$inst_prefix_dir"; then # Stick the inst_prefix_dir data into the link command. - relink_command=`$ECHO "X$relink_command" | $Xsed -e "s%@inst_prefix_dir@%-inst-prefix-dir $inst_prefix_dir%"` + relink_command=`$ECHO "$relink_command" | $SED "s%@inst_prefix_dir@%-inst-prefix-dir $inst_prefix_dir%"` else - relink_command=`$ECHO "X$relink_command" | $Xsed -e "s%@inst_prefix_dir@%%"` + relink_command=`$ECHO "$relink_command" | $SED "s%@inst_prefix_dir@%%"` fi func_warning "relinking \`$file'" @@ -2043,7 +2988,7 @@ func_mode_install () test -n "$relink_command" && srcname="$realname"T # Install the shared library and build the symlinks. - func_show_eval "$install_prog $dir/$srcname $destdir/$realname" \ + func_show_eval "$install_shared_prog $dir/$srcname $destdir/$realname" \ 'exit $?' tstripme="$stripme" case $host_os in @@ -2083,7 +3028,7 @@ func_mode_install () func_show_eval "$install_prog $instname $destdir/$name" 'exit $?' # Maybe install the static library, too. - test -n "$old_library" && staticlibs="$staticlibs $dir/$old_library" + test -n "$old_library" && func_append staticlibs " $dir/$old_library" ;; *.lo) @@ -2183,7 +3128,7 @@ func_mode_install () if test -f "$lib"; then func_source "$lib" fi - libfile="$libdir/"`$ECHO "X$lib" | $Xsed -e 's%^.*/%%g'` ### testsuite: skip nested quoting test + libfile="$libdir/"`$ECHO "$lib" | $SED 's%^.*/%%g'` ### testsuite: skip nested quoting test if test -n "$libdir" && test ! -f "$libfile"; then func_warning "\`$lib' has not been installed in \`$libdir'" finalize=no @@ -2202,7 +3147,7 @@ func_mode_install () file="$func_basename_result" outputname="$tmpdir/$file" # Replace the output file specification. - relink_command=`$ECHO "X$relink_command" | $Xsed -e 's%@OUTPUT@%'"$outputname"'%g'` + relink_command=`$ECHO "$relink_command" | $SED 's%@OUTPUT@%'"$outputname"'%g'` $opt_silent || { func_quote_for_expand "$relink_command" @@ -2221,7 +3166,7 @@ func_mode_install () } else # Install the binary that we compiled earlier. - file=`$ECHO "X$file$stripped_ext" | $Xsed -e "s%\([^/]*\)$%$objdir/\1%"` + file=`$ECHO "$file$stripped_ext" | $SED "s%\([^/]*\)$%$objdir/\1%"` fi fi @@ -2257,11 +3202,13 @@ func_mode_install () # Set up the ranlib parameters. oldlib="$destdir/$name" + func_to_tool_file "$oldlib" func_convert_file_msys_to_w32 + tool_oldlib=$func_to_tool_file_result func_show_eval "$install_prog \$file \$oldlib" 'exit $?' if test -n "$stripme" && test -n "$old_striplib"; then - func_show_eval "$old_striplib $oldlib" 'exit $?' + func_show_eval "$old_striplib $tool_oldlib" 'exit $?' fi # Do each command in the postinstall commands. @@ -2280,7 +3227,7 @@ func_mode_install () fi } -test "$mode" = install && func_mode_install ${1+"$@"} +test "$opt_mode" = install && func_mode_install ${1+"$@"} # func_generate_dlsyms outputname originator pic_p @@ -2323,6 +3270,22 @@ func_generate_dlsyms () extern \"C\" { #endif +#if defined(__GNUC__) && (((__GNUC__ == 4) && (__GNUC_MINOR__ >= 4)) || (__GNUC__ > 4)) +#pragma GCC diagnostic ignored \"-Wstrict-prototypes\" +#endif + +/* Keep this code in sync between libtool.m4, ltmain, lt_system.h, and tests. */ +#if defined(_WIN32) || defined(__CYGWIN__) || defined(_WIN32_WCE) +/* DATA imports from DLLs on WIN32 con't be const, because runtime + relocations are performed -- see ld's documentation on pseudo-relocs. */ +# define LT_DLSYM_CONST +#elif defined(__osf__) +/* This system does not cope well with relocations in const data. */ +# define LT_DLSYM_CONST +#else +# define LT_DLSYM_CONST const +#endif + /* External symbol declarations for the compiler. */\ " @@ -2332,10 +3295,11 @@ extern \"C\" { $opt_dry_run || echo ': @PROGRAM@ ' > "$nlist" # Add our own program objects to the symbol list. - progfiles=`$ECHO "X$objs$old_deplibs" | $SP2NL | $Xsed -e "$lo2o" | $NL2SP` + progfiles=`$ECHO "$objs$old_deplibs" | $SP2NL | $SED "$lo2o" | $NL2SP` for progfile in $progfiles; do - func_verbose "extracting global C symbols from \`$progfile'" - $opt_dry_run || eval "$NM $progfile | $global_symbol_pipe >> '$nlist'" + func_to_tool_file "$progfile" func_convert_file_msys_to_w32 + func_verbose "extracting global C symbols from \`$func_to_tool_file_result'" + $opt_dry_run || eval "$NM $func_to_tool_file_result | $global_symbol_pipe >> '$nlist'" done if test -n "$exclude_expsyms"; then @@ -2371,7 +3335,7 @@ extern \"C\" { eval '$GREP -f "$output_objdir/$outputname.exp" < "$nlist" > "$nlist"T' eval '$MV "$nlist"T "$nlist"' case $host in - *cygwin | *mingw* | *cegcc* ) + *cygwin* | *mingw* | *cegcc* ) eval "echo EXPORTS "'> "$output_objdir/$outputname.def"' eval 'cat "$nlist" >> "$output_objdir/$outputname.def"' ;; @@ -2384,10 +3348,52 @@ extern \"C\" { func_verbose "extracting global C symbols from \`$dlprefile'" func_basename "$dlprefile" name="$func_basename_result" - $opt_dry_run || { - eval '$ECHO ": $name " >> "$nlist"' - eval "$NM $dlprefile 2>/dev/null | $global_symbol_pipe >> '$nlist'" - } + case $host in + *cygwin* | *mingw* | *cegcc* ) + # if an import library, we need to obtain dlname + if func_win32_import_lib_p "$dlprefile"; then + func_tr_sh "$dlprefile" + eval "curr_lafile=\$libfile_$func_tr_sh_result" + dlprefile_dlbasename="" + if test -n "$curr_lafile" && func_lalib_p "$curr_lafile"; then + # Use subshell, to avoid clobbering current variable values + dlprefile_dlname=`source "$curr_lafile" && echo "$dlname"` + if test -n "$dlprefile_dlname" ; then + func_basename "$dlprefile_dlname" + dlprefile_dlbasename="$func_basename_result" + else + # no lafile. user explicitly requested -dlpreopen . + $sharedlib_from_linklib_cmd "$dlprefile" + dlprefile_dlbasename=$sharedlib_from_linklib_result + fi + fi + $opt_dry_run || { + if test -n "$dlprefile_dlbasename" ; then + eval '$ECHO ": $dlprefile_dlbasename" >> "$nlist"' + else + func_warning "Could not compute DLL name from $name" + eval '$ECHO ": $name " >> "$nlist"' + fi + func_to_tool_file "$dlprefile" func_convert_file_msys_to_w32 + eval "$NM \"$func_to_tool_file_result\" 2>/dev/null | $global_symbol_pipe | + $SED -e '/I __imp/d' -e 's/I __nm_/D /;s/_nm__//' >> '$nlist'" + } + else # not an import lib + $opt_dry_run || { + eval '$ECHO ": $name " >> "$nlist"' + func_to_tool_file "$dlprefile" func_convert_file_msys_to_w32 + eval "$NM \"$func_to_tool_file_result\" 2>/dev/null | $global_symbol_pipe >> '$nlist'" + } + fi + ;; + *) + $opt_dry_run || { + eval '$ECHO ": $name " >> "$nlist"' + func_to_tool_file "$dlprefile" func_convert_file_msys_to_w32 + eval "$NM \"$func_to_tool_file_result\" 2>/dev/null | $global_symbol_pipe >> '$nlist'" + } + ;; + esac done $opt_dry_run || { @@ -2415,36 +3421,19 @@ extern \"C\" { if test -f "$nlist"S; then eval "$global_symbol_to_cdecl"' < "$nlist"S >> "$output_objdir/$my_dlsyms"' else - $ECHO '/* NONE */' >> "$output_objdir/$my_dlsyms" + echo '/* NONE */' >> "$output_objdir/$my_dlsyms" fi - $ECHO >> "$output_objdir/$my_dlsyms" "\ + echo >> "$output_objdir/$my_dlsyms" "\ /* The mapping between symbol names and symbols. */ typedef struct { const char *name; void *address; } lt_dlsymlist; -" - case $host in - *cygwin* | *mingw* | *cegcc* ) - $ECHO >> "$output_objdir/$my_dlsyms" "\ -/* DATA imports from DLLs on WIN32 con't be const, because - runtime relocations are performed -- see ld's documentation - on pseudo-relocs. */" - lt_dlsym_const= ;; - *osf5*) - echo >> "$output_objdir/$my_dlsyms" "\ -/* This system does not cope well with relocations in const data */" - lt_dlsym_const= ;; - *) - lt_dlsym_const=const ;; - esac - - $ECHO >> "$output_objdir/$my_dlsyms" "\ -extern $lt_dlsym_const lt_dlsymlist +extern LT_DLSYM_CONST lt_dlsymlist lt_${my_prefix}_LTX_preloaded_symbols[]; -$lt_dlsym_const lt_dlsymlist +LT_DLSYM_CONST lt_dlsymlist lt_${my_prefix}_LTX_preloaded_symbols[] = {\ { \"$my_originator\", (void *) 0 }," @@ -2457,7 +3446,7 @@ lt_${my_prefix}_LTX_preloaded_symbols[] = eval "$global_symbol_to_c_name_address_lib_prefix" < "$nlist" >> "$output_objdir/$my_dlsyms" ;; esac - $ECHO >> "$output_objdir/$my_dlsyms" "\ + echo >> "$output_objdir/$my_dlsyms" "\ {0, (void *) 0} }; @@ -2484,7 +3473,7 @@ static const void *lt_preloaded_setup() { # linked before any other PIC object. But we must not use # pic_flag when linking with -static. The problem exists in # FreeBSD 2.2.6 and is fixed in FreeBSD 3.1. - *-*-freebsd2*|*-*-freebsd3.0*|*-*-freebsdelf3.0*) + *-*-freebsd2.*|*-*-freebsd3.0*|*-*-freebsdelf3.0*) pic_flag_for_symtable=" $pic_flag -DFREEBSD_WORKAROUND" ;; *-*-hpux*) pic_flag_for_symtable=" $pic_flag" ;; @@ -2500,7 +3489,7 @@ static const void *lt_preloaded_setup() { for arg in $LTCFLAGS; do case $arg in -pie | -fpie | -fPIE) ;; - *) symtab_cflags="$symtab_cflags $arg" ;; + *) func_append symtab_cflags " $arg" ;; esac done @@ -2515,16 +3504,16 @@ static const void *lt_preloaded_setup() { case $host in *cygwin* | *mingw* | *cegcc* ) if test -f "$output_objdir/$my_outputname.def"; then - compile_command=`$ECHO "X$compile_command" | $Xsed -e "s%@SYMFILE@%$output_objdir/$my_outputname.def $symfileobj%"` - finalize_command=`$ECHO "X$finalize_command" | $Xsed -e "s%@SYMFILE@%$output_objdir/$my_outputname.def $symfileobj%"` + compile_command=`$ECHO "$compile_command" | $SED "s%@SYMFILE@%$output_objdir/$my_outputname.def $symfileobj%"` + finalize_command=`$ECHO "$finalize_command" | $SED "s%@SYMFILE@%$output_objdir/$my_outputname.def $symfileobj%"` else - compile_command=`$ECHO "X$compile_command" | $Xsed -e "s%@SYMFILE@%$symfileobj%"` - finalize_command=`$ECHO "X$finalize_command" | $Xsed -e "s%@SYMFILE@%$symfileobj%"` + compile_command=`$ECHO "$compile_command" | $SED "s%@SYMFILE@%$symfileobj%"` + finalize_command=`$ECHO "$finalize_command" | $SED "s%@SYMFILE@%$symfileobj%"` fi ;; *) - compile_command=`$ECHO "X$compile_command" | $Xsed -e "s%@SYMFILE@%$symfileobj%"` - finalize_command=`$ECHO "X$finalize_command" | $Xsed -e "s%@SYMFILE@%$symfileobj%"` + compile_command=`$ECHO "$compile_command" | $SED "s%@SYMFILE@%$symfileobj%"` + finalize_command=`$ECHO "$finalize_command" | $SED "s%@SYMFILE@%$symfileobj%"` ;; esac ;; @@ -2538,8 +3527,8 @@ static const void *lt_preloaded_setup() { # really was required. # Nullify the symbol file. - compile_command=`$ECHO "X$compile_command" | $Xsed -e "s% @SYMFILE@%%"` - finalize_command=`$ECHO "X$finalize_command" | $Xsed -e "s% @SYMFILE@%%"` + compile_command=`$ECHO "$compile_command" | $SED "s% @SYMFILE@%%"` + finalize_command=`$ECHO "$finalize_command" | $SED "s% @SYMFILE@%%"` fi } @@ -2549,6 +3538,7 @@ static const void *lt_preloaded_setup() { # Need a lot of goo to handle *both* DLLs and import libs # Has to be a shell function in order to 'eat' the argument # that is supplied when $file_magic_command is called. +# Despite the name, also deal with 64 bit binaries. func_win32_libid () { $opt_debug @@ -2559,9 +3549,11 @@ func_win32_libid () win32_libid_type="x86 archive import" ;; *ar\ archive*) # could be an import, or static + # Keep the egrep pattern in sync with the one in _LT_CHECK_MAGIC_METHOD. if eval $OBJDUMP -f $1 | $SED -e '10q' 2>/dev/null | - $EGREP 'file format pe-i386(.*architecture: i386)?' >/dev/null ; then - win32_nmres=`eval $NM -f posix -A $1 | + $EGREP 'file format (pei*-i386(.*architecture: i386)?|pe-arm-wince|pe-x86-64)' >/dev/null; then + func_to_tool_file "$1" func_convert_file_msys_to_w32 + win32_nmres=`eval $NM -f posix -A \"$func_to_tool_file_result\" | $SED -n -e ' 1,100{ / I /{ @@ -2590,6 +3582,131 @@ func_win32_libid () $ECHO "$win32_libid_type" } +# func_cygming_dll_for_implib ARG +# +# Platform-specific function to extract the +# name of the DLL associated with the specified +# import library ARG. +# Invoked by eval'ing the libtool variable +# $sharedlib_from_linklib_cmd +# Result is available in the variable +# $sharedlib_from_linklib_result +func_cygming_dll_for_implib () +{ + $opt_debug + sharedlib_from_linklib_result=`$DLLTOOL --identify-strict --identify "$1"` +} + +# func_cygming_dll_for_implib_fallback_core SECTION_NAME LIBNAMEs +# +# The is the core of a fallback implementation of a +# platform-specific function to extract the name of the +# DLL associated with the specified import library LIBNAME. +# +# SECTION_NAME is either .idata$6 or .idata$7, depending +# on the platform and compiler that created the implib. +# +# Echos the name of the DLL associated with the +# specified import library. +func_cygming_dll_for_implib_fallback_core () +{ + $opt_debug + match_literal=`$ECHO "$1" | $SED "$sed_make_literal_regex"` + $OBJDUMP -s --section "$1" "$2" 2>/dev/null | + $SED '/^Contents of section '"$match_literal"':/{ + # Place marker at beginning of archive member dllname section + s/.*/====MARK====/ + p + d + } + # These lines can sometimes be longer than 43 characters, but + # are always uninteresting + /:[ ]*file format pe[i]\{,1\}-/d + /^In archive [^:]*:/d + # Ensure marker is printed + /^====MARK====/p + # Remove all lines with less than 43 characters + /^.\{43\}/!d + # From remaining lines, remove first 43 characters + s/^.\{43\}//' | + $SED -n ' + # Join marker and all lines until next marker into a single line + /^====MARK====/ b para + H + $ b para + b + :para + x + s/\n//g + # Remove the marker + s/^====MARK====// + # Remove trailing dots and whitespace + s/[\. \t]*$// + # Print + /./p' | + # we now have a list, one entry per line, of the stringified + # contents of the appropriate section of all members of the + # archive which possess that section. Heuristic: eliminate + # all those which have a first or second character that is + # a '.' (that is, objdump's representation of an unprintable + # character.) This should work for all archives with less than + # 0x302f exports -- but will fail for DLLs whose name actually + # begins with a literal '.' or a single character followed by + # a '.'. + # + # Of those that remain, print the first one. + $SED -e '/^\./d;/^.\./d;q' +} + +# func_cygming_gnu_implib_p ARG +# This predicate returns with zero status (TRUE) if +# ARG is a GNU/binutils-style import library. Returns +# with nonzero status (FALSE) otherwise. +func_cygming_gnu_implib_p () +{ + $opt_debug + func_to_tool_file "$1" func_convert_file_msys_to_w32 + func_cygming_gnu_implib_tmp=`$NM "$func_to_tool_file_result" | eval "$global_symbol_pipe" | $EGREP ' (_head_[A-Za-z0-9_]+_[ad]l*|[A-Za-z0-9_]+_[ad]l*_iname)$'` + test -n "$func_cygming_gnu_implib_tmp" +} + +# func_cygming_ms_implib_p ARG +# This predicate returns with zero status (TRUE) if +# ARG is an MS-style import library. Returns +# with nonzero status (FALSE) otherwise. +func_cygming_ms_implib_p () +{ + $opt_debug + func_to_tool_file "$1" func_convert_file_msys_to_w32 + func_cygming_ms_implib_tmp=`$NM "$func_to_tool_file_result" | eval "$global_symbol_pipe" | $GREP '_NULL_IMPORT_DESCRIPTOR'` + test -n "$func_cygming_ms_implib_tmp" +} + +# func_cygming_dll_for_implib_fallback ARG +# Platform-specific function to extract the +# name of the DLL associated with the specified +# import library ARG. +# +# This fallback implementation is for use when $DLLTOOL +# does not support the --identify-strict option. +# Invoked by eval'ing the libtool variable +# $sharedlib_from_linklib_cmd +# Result is available in the variable +# $sharedlib_from_linklib_result +func_cygming_dll_for_implib_fallback () +{ + $opt_debug + if func_cygming_gnu_implib_p "$1" ; then + # binutils import library + sharedlib_from_linklib_result=`func_cygming_dll_for_implib_fallback_core '.idata$7' "$1"` + elif func_cygming_ms_implib_p "$1" ; then + # ms-generated import library + sharedlib_from_linklib_result=`func_cygming_dll_for_implib_fallback_core '.idata$6' "$1"` + else + # unknown + sharedlib_from_linklib_result="" + fi +} # func_extract_an_archive dir oldlib @@ -2598,7 +3715,18 @@ func_extract_an_archive () $opt_debug f_ex_an_ar_dir="$1"; shift f_ex_an_ar_oldlib="$1" - func_show_eval "(cd \$f_ex_an_ar_dir && $AR x \"\$f_ex_an_ar_oldlib\")" 'exit $?' + if test "$lock_old_archive_extraction" = yes; then + lockfile=$f_ex_an_ar_oldlib.lock + until $opt_dry_run || ln "$progpath" "$lockfile" 2>/dev/null; do + func_echo "Waiting for $lockfile to be removed" + sleep 2 + done + fi + func_show_eval "(cd \$f_ex_an_ar_dir && $AR x \"\$f_ex_an_ar_oldlib\")" \ + 'stat=$?; rm -f "$lockfile"; exit $stat' + if test "$lock_old_archive_extraction" = yes; then + $opt_dry_run || rm -f "$lockfile" + fi if ($AR t "$f_ex_an_ar_oldlib" | sort | sort -uc >/dev/null 2>&1); then : else @@ -2669,7 +3797,7 @@ func_extract_archives () darwin_file= darwin_files= for darwin_file in $darwin_filelist; do - darwin_files=`find unfat-$$ -name $darwin_file -print | $NL2SP` + darwin_files=`find unfat-$$ -name $darwin_file -print | sort | $NL2SP` $LIPO -create -output "$darwin_file" $darwin_files done # $darwin_filelist $RM -rf unfat-$$ @@ -2684,25 +3812,30 @@ func_extract_archives () func_extract_an_archive "$my_xdir" "$my_xabs" ;; esac - my_oldobjs="$my_oldobjs "`find $my_xdir -name \*.$objext -print -o -name \*.lo -print | $NL2SP` + my_oldobjs="$my_oldobjs "`find $my_xdir -name \*.$objext -print -o -name \*.lo -print | sort | $NL2SP` done func_extract_archives_result="$my_oldobjs" } - -# func_emit_wrapper_part1 [arg=no] +# func_emit_wrapper [arg=no] +# +# Emit a libtool wrapper script on stdout. +# Don't directly open a file because we may want to +# incorporate the script contents within a cygwin/mingw +# wrapper executable. Must ONLY be called from within +# func_mode_link because it depends on a number of variables +# set therein. # -# Emit the first part of a libtool wrapper script on stdout. -# For more information, see the description associated with -# func_emit_wrapper(), below. -func_emit_wrapper_part1 () +# ARG is the value that the WRAPPER_SCRIPT_BELONGS_IN_OBJDIR +# variable will take. If 'yes', then the emitted script +# will assume that the directory in which it is stored is +# the $objdir directory. This is a cygwin/mingw-specific +# behavior. +func_emit_wrapper () { - func_emit_wrapper_part1_arg1=no - if test -n "$1" ; then - func_emit_wrapper_part1_arg1=$1 - fi + func_emit_wrapper_arg1=${1-no} $ECHO "\ #! $SHELL @@ -2718,7 +3851,6 @@ func_emit_wrapper_part1 () # Sed substitution that helps us do robust quoting. It backslashifies # metacharacters that are still active within double-quoted strings. -Xsed='${SED} -e 1s/^X//' sed_quote_subst='$sed_quote_subst' # Be Bourne compatible @@ -2749,31 +3881,135 @@ if test \"\$libtool_install_magic\" = \"$magic\"; then else # When we are sourced in execute mode, \$file and \$ECHO are already set. if test \"\$libtool_execute_magic\" != \"$magic\"; then - ECHO=\"$qecho\" - file=\"\$0\" - # Make sure echo works. - if test \"X\$1\" = X--no-reexec; then - # Discard the --no-reexec flag, and continue. - shift - elif test \"X\`{ \$ECHO '\t'; } 2>/dev/null\`\" = 'X\t'; then - # Yippee, \$ECHO works! - : - else - # Restart under the correct shell, and then maybe \$ECHO will work. - exec $SHELL \"\$0\" --no-reexec \${1+\"\$@\"} - fi - fi\ + file=\"\$0\"" + + qECHO=`$ECHO "$ECHO" | $SED "$sed_quote_subst"` + $ECHO "\ + +# A function that is used when there is no print builtin or printf. +func_fallback_echo () +{ + eval 'cat <<_LTECHO_EOF +\$1 +_LTECHO_EOF' +} + ECHO=\"$qECHO\" + fi + +# Very basic option parsing. These options are (a) specific to +# the libtool wrapper, (b) are identical between the wrapper +# /script/ and the wrapper /executable/ which is used only on +# windows platforms, and (c) all begin with the string "--lt-" +# (application programs are unlikely to have options which match +# this pattern). +# +# There are only two supported options: --lt-debug and +# --lt-dump-script. There is, deliberately, no --lt-help. +# +# The first argument to this parsing function should be the +# script's $0 value, followed by "$@". +lt_option_debug= +func_parse_lt_options () +{ + lt_script_arg0=\$0 + shift + for lt_opt + do + case \"\$lt_opt\" in + --lt-debug) lt_option_debug=1 ;; + --lt-dump-script) + lt_dump_D=\`\$ECHO \"X\$lt_script_arg0\" | $SED -e 's/^X//' -e 's%/[^/]*$%%'\` + test \"X\$lt_dump_D\" = \"X\$lt_script_arg0\" && lt_dump_D=. + lt_dump_F=\`\$ECHO \"X\$lt_script_arg0\" | $SED -e 's/^X//' -e 's%^.*/%%'\` + cat \"\$lt_dump_D/\$lt_dump_F\" + exit 0 + ;; + --lt-*) + \$ECHO \"Unrecognized --lt- option: '\$lt_opt'\" 1>&2 + exit 1 + ;; + esac + done + + # Print the debug banner immediately: + if test -n \"\$lt_option_debug\"; then + echo \"${outputname}:${output}:\${LINENO}: libtool wrapper (GNU $PACKAGE$TIMESTAMP) $VERSION\" 1>&2 + fi +} + +# Used when --lt-debug. Prints its arguments to stdout +# (redirection is the responsibility of the caller) +func_lt_dump_args () +{ + lt_dump_args_N=1; + for lt_arg + do + \$ECHO \"${outputname}:${output}:\${LINENO}: newargv[\$lt_dump_args_N]: \$lt_arg\" + lt_dump_args_N=\`expr \$lt_dump_args_N + 1\` + done +} + +# Core function for launching the target application +func_exec_program_core () +{ " - $ECHO "\ + case $host in + # Backslashes separate directories on plain windows + *-*-mingw | *-*-os2* | *-cegcc*) + $ECHO "\ + if test -n \"\$lt_option_debug\"; then + \$ECHO \"${outputname}:${output}:\${LINENO}: newargv[0]: \$progdir\\\\\$program\" 1>&2 + func_lt_dump_args \${1+\"\$@\"} 1>&2 + fi + exec \"\$progdir\\\\\$program\" \${1+\"\$@\"} +" + ;; + + *) + $ECHO "\ + if test -n \"\$lt_option_debug\"; then + \$ECHO \"${outputname}:${output}:\${LINENO}: newargv[0]: \$progdir/\$program\" 1>&2 + func_lt_dump_args \${1+\"\$@\"} 1>&2 + fi + exec \"\$progdir/\$program\" \${1+\"\$@\"} +" + ;; + esac + $ECHO "\ + \$ECHO \"\$0: cannot exec \$program \$*\" 1>&2 + exit 1 +} + +# A function to encapsulate launching the target application +# Strips options in the --lt-* namespace from \$@ and +# launches target application with the remaining arguments. +func_exec_program () +{ + case \" \$* \" in + *\\ --lt-*) + for lt_wr_arg + do + case \$lt_wr_arg in + --lt-*) ;; + *) set x \"\$@\" \"\$lt_wr_arg\"; shift;; + esac + shift + done ;; + esac + func_exec_program_core \${1+\"\$@\"} +} + + # Parse options + func_parse_lt_options \"\$0\" \${1+\"\$@\"} # Find the directory that this script lives in. - thisdir=\`\$ECHO \"X\$file\" | \$Xsed -e 's%/[^/]*$%%'\` + thisdir=\`\$ECHO \"\$file\" | $SED 's%/[^/]*$%%'\` test \"x\$thisdir\" = \"x\$file\" && thisdir=. # Follow symbolic links until we get to the real thisdir. - file=\`ls -ld \"\$file\" | ${SED} -n 's/.*-> //p'\` + file=\`ls -ld \"\$file\" | $SED -n 's/.*-> //p'\` while test -n \"\$file\"; do - destdir=\`\$ECHO \"X\$file\" | \$Xsed -e 's%/[^/]*\$%%'\` + destdir=\`\$ECHO \"\$file\" | $SED 's%/[^/]*\$%%'\` # If there was a directory component, then change thisdir. if test \"x\$destdir\" != \"x\$file\"; then @@ -2783,30 +4019,13 @@ else esac fi - file=\`\$ECHO \"X\$file\" | \$Xsed -e 's%^.*/%%'\` - file=\`ls -ld \"\$thisdir/\$file\" | ${SED} -n 's/.*-> //p'\` + file=\`\$ECHO \"\$file\" | $SED 's%^.*/%%'\` + file=\`ls -ld \"\$thisdir/\$file\" | $SED -n 's/.*-> //p'\` done -" -} -# end: func_emit_wrapper_part1 - -# func_emit_wrapper_part2 [arg=no] -# -# Emit the second part of a libtool wrapper script on stdout. -# For more information, see the description associated with -# func_emit_wrapper(), below. -func_emit_wrapper_part2 () -{ - func_emit_wrapper_part2_arg1=no - if test -n "$1" ; then - func_emit_wrapper_part2_arg1=$1 - fi - - $ECHO "\ # Usually 'no', except on cygwin/mingw when embedded into # the cwrapper. - WRAPPER_SCRIPT_BELONGS_IN_OBJDIR=$func_emit_wrapper_part2_arg1 + WRAPPER_SCRIPT_BELONGS_IN_OBJDIR=$func_emit_wrapper_arg1 if test \"\$WRAPPER_SCRIPT_BELONGS_IN_OBJDIR\" = \"yes\"; then # special case for '.' if test \"\$thisdir\" = \".\"; then @@ -2814,7 +4033,7 @@ func_emit_wrapper_part2 () fi # remove .libs from thisdir case \"\$thisdir\" in - *[\\\\/]$objdir ) thisdir=\`\$ECHO \"X\$thisdir\" | \$Xsed -e 's%[\\\\/][^\\\\/]*$%%'\` ;; + *[\\\\/]$objdir ) thisdir=\`\$ECHO \"\$thisdir\" | $SED 's%[\\\\/][^\\\\/]*$%%'\` ;; $objdir ) thisdir=. ;; esac fi @@ -2869,6 +4088,18 @@ func_emit_wrapper_part2 () if test -f \"\$progdir/\$program\"; then" + # fixup the dll searchpath if we need to. + # + # Fix the DLL searchpath if we need to. Do this before prepending + # to shlibpath, because on Windows, both are PATH and uninstalled + # libraries must come first. + if test -n "$dllsearchpath"; then + $ECHO "\ + # Add the dll search path components to the executable PATH + PATH=$dllsearchpath:\$PATH +" + fi + # Export our shlibpath_var if we have one. if test "$shlibpath_overrides_runpath" = yes && test -n "$shlibpath_var" && test -n "$temp_rpath"; then $ECHO "\ @@ -2877,253 +4108,28 @@ func_emit_wrapper_part2 () # Some systems cannot cope with colon-terminated $shlibpath_var # The second colon is a workaround for a bug in BeOS R4 sed - $shlibpath_var=\`\$ECHO \"X\$$shlibpath_var\" | \$Xsed -e 's/::*\$//'\` + $shlibpath_var=\`\$ECHO \"\$$shlibpath_var\" | $SED 's/::*\$//'\` export $shlibpath_var " fi - # fixup the dll searchpath if we need to. - if test -n "$dllsearchpath"; then - $ECHO "\ - # Add the dll search path components to the executable PATH - PATH=$dllsearchpath:\$PATH -" - fi - $ECHO "\ if test \"\$libtool_execute_magic\" != \"$magic\"; then # Run the actual program with our arguments. -" - case $host in - # Backslashes separate directories on plain windows - *-*-mingw | *-*-os2* | *-cegcc*) - $ECHO "\ - exec \"\$progdir\\\\\$program\" \${1+\"\$@\"} -" - ;; - - *) - $ECHO "\ - exec \"\$progdir/\$program\" \${1+\"\$@\"} -" - ;; - esac - $ECHO "\ - \$ECHO \"\$0: cannot exec \$program \$*\" 1>&2 - exit 1 + func_exec_program \${1+\"\$@\"} fi else # The program doesn't exist. \$ECHO \"\$0: error: \\\`\$progdir/\$program' does not exist\" 1>&2 \$ECHO \"This script is just a wrapper for \$program.\" 1>&2 - $ECHO \"See the $PACKAGE documentation for more information.\" 1>&2 + \$ECHO \"See the $PACKAGE documentation for more information.\" 1>&2 exit 1 fi fi\ " } -# end: func_emit_wrapper_part2 - - -# func_emit_wrapper [arg=no] -# -# Emit a libtool wrapper script on stdout. -# Don't directly open a file because we may want to -# incorporate the script contents within a cygwin/mingw -# wrapper executable. Must ONLY be called from within -# func_mode_link because it depends on a number of variables -# set therein. -# -# ARG is the value that the WRAPPER_SCRIPT_BELONGS_IN_OBJDIR -# variable will take. If 'yes', then the emitted script -# will assume that the directory in which it is stored is -# the $objdir directory. This is a cygwin/mingw-specific -# behavior. -func_emit_wrapper () -{ - func_emit_wrapper_arg1=no - if test -n "$1" ; then - func_emit_wrapper_arg1=$1 - fi - - # split this up so that func_emit_cwrapperexe_src - # can call each part independently. - func_emit_wrapper_part1 "${func_emit_wrapper_arg1}" - func_emit_wrapper_part2 "${func_emit_wrapper_arg1}" -} - - -# func_to_host_path arg -# -# Convert paths to host format when used with build tools. -# Intended for use with "native" mingw (where libtool itself -# is running under the msys shell), or in the following cross- -# build environments: -# $build $host -# mingw (msys) mingw [e.g. native] -# cygwin mingw -# *nix + wine mingw -# where wine is equipped with the `winepath' executable. -# In the native mingw case, the (msys) shell automatically -# converts paths for any non-msys applications it launches, -# but that facility isn't available from inside the cwrapper. -# Similar accommodations are necessary for $host mingw and -# $build cygwin. Calling this function does no harm for other -# $host/$build combinations not listed above. -# -# ARG is the path (on $build) that should be converted to -# the proper representation for $host. The result is stored -# in $func_to_host_path_result. -func_to_host_path () -{ - func_to_host_path_result="$1" - if test -n "$1" ; then - case $host in - *mingw* ) - lt_sed_naive_backslashify='s|\\\\*|\\|g;s|/|\\|g;s|\\|\\\\|g' - case $build in - *mingw* ) # actually, msys - # awkward: cmd appends spaces to result - lt_sed_strip_trailing_spaces="s/[ ]*\$//" - func_to_host_path_tmp1=`( cmd //c echo "$1" |\ - $SED -e "$lt_sed_strip_trailing_spaces" ) 2>/dev/null || echo ""` - func_to_host_path_result=`echo "$func_to_host_path_tmp1" |\ - $SED -e "$lt_sed_naive_backslashify"` - ;; - *cygwin* ) - func_to_host_path_tmp1=`cygpath -w "$1"` - func_to_host_path_result=`echo "$func_to_host_path_tmp1" |\ - $SED -e "$lt_sed_naive_backslashify"` - ;; - * ) - # Unfortunately, winepath does not exit with a non-zero - # error code, so we are forced to check the contents of - # stdout. On the other hand, if the command is not - # found, the shell will set an exit code of 127 and print - # *an error message* to stdout. So we must check for both - # error code of zero AND non-empty stdout, which explains - # the odd construction: - func_to_host_path_tmp1=`winepath -w "$1" 2>/dev/null` - if test "$?" -eq 0 && test -n "${func_to_host_path_tmp1}"; then - func_to_host_path_result=`echo "$func_to_host_path_tmp1" |\ - $SED -e "$lt_sed_naive_backslashify"` - else - # Allow warning below. - func_to_host_path_result="" - fi - ;; - esac - if test -z "$func_to_host_path_result" ; then - func_error "Could not determine host path corresponding to" - func_error " '$1'" - func_error "Continuing, but uninstalled executables may not work." - # Fallback: - func_to_host_path_result="$1" - fi - ;; - esac - fi -} -# end: func_to_host_path -# func_to_host_pathlist arg -# -# Convert pathlists to host format when used with build tools. -# See func_to_host_path(), above. This function supports the -# following $build/$host combinations (but does no harm for -# combinations not listed here): -# $build $host -# mingw (msys) mingw [e.g. native] -# cygwin mingw -# *nix + wine mingw -# -# Path separators are also converted from $build format to -# $host format. If ARG begins or ends with a path separator -# character, it is preserved (but converted to $host format) -# on output. -# -# ARG is a pathlist (on $build) that should be converted to -# the proper representation on $host. The result is stored -# in $func_to_host_pathlist_result. -func_to_host_pathlist () -{ - func_to_host_pathlist_result="$1" - if test -n "$1" ; then - case $host in - *mingw* ) - lt_sed_naive_backslashify='s|\\\\*|\\|g;s|/|\\|g;s|\\|\\\\|g' - # Remove leading and trailing path separator characters from - # ARG. msys behavior is inconsistent here, cygpath turns them - # into '.;' and ';.', and winepath ignores them completely. - func_to_host_pathlist_tmp2="$1" - # Once set for this call, this variable should not be - # reassigned. It is used in tha fallback case. - func_to_host_pathlist_tmp1=`echo "$func_to_host_pathlist_tmp2" |\ - $SED -e 's|^:*||' -e 's|:*$||'` - case $build in - *mingw* ) # Actually, msys. - # Awkward: cmd appends spaces to result. - lt_sed_strip_trailing_spaces="s/[ ]*\$//" - func_to_host_pathlist_tmp2=`( cmd //c echo "$func_to_host_pathlist_tmp1" |\ - $SED -e "$lt_sed_strip_trailing_spaces" ) 2>/dev/null || echo ""` - func_to_host_pathlist_result=`echo "$func_to_host_pathlist_tmp2" |\ - $SED -e "$lt_sed_naive_backslashify"` - ;; - *cygwin* ) - func_to_host_pathlist_tmp2=`cygpath -w -p "$func_to_host_pathlist_tmp1"` - func_to_host_pathlist_result=`echo "$func_to_host_pathlist_tmp2" |\ - $SED -e "$lt_sed_naive_backslashify"` - ;; - * ) - # unfortunately, winepath doesn't convert pathlists - func_to_host_pathlist_result="" - func_to_host_pathlist_oldIFS=$IFS - IFS=: - for func_to_host_pathlist_f in $func_to_host_pathlist_tmp1 ; do - IFS=$func_to_host_pathlist_oldIFS - if test -n "$func_to_host_pathlist_f" ; then - func_to_host_path "$func_to_host_pathlist_f" - if test -n "$func_to_host_path_result" ; then - if test -z "$func_to_host_pathlist_result" ; then - func_to_host_pathlist_result="$func_to_host_path_result" - else - func_to_host_pathlist_result="$func_to_host_pathlist_result;$func_to_host_path_result" - fi - fi - fi - IFS=: - done - IFS=$func_to_host_pathlist_oldIFS - ;; - esac - if test -z "$func_to_host_pathlist_result" ; then - func_error "Could not determine the host path(s) corresponding to" - func_error " '$1'" - func_error "Continuing, but uninstalled executables may not work." - # Fallback. This may break if $1 contains DOS-style drive - # specifications. The fix is not to complicate the expression - # below, but for the user to provide a working wine installation - # with winepath so that path translation in the cross-to-mingw - # case works properly. - lt_replace_pathsep_nix_to_dos="s|:|;|g" - func_to_host_pathlist_result=`echo "$func_to_host_pathlist_tmp1" |\ - $SED -e "$lt_replace_pathsep_nix_to_dos"` - fi - # Now, add the leading and trailing path separators back - case "$1" in - :* ) func_to_host_pathlist_result=";$func_to_host_pathlist_result" - ;; - esac - case "$1" in - *: ) func_to_host_pathlist_result="$func_to_host_pathlist_result;" - ;; - esac - ;; - esac - fi -} -# end: func_to_host_pathlist # func_emit_cwrapperexe_src # emit the source code for a wrapper executable on stdout @@ -3141,31 +4147,23 @@ func_emit_cwrapperexe_src () This wrapper executable should never be moved out of the build directory. If it is, it will not operate correctly. - - Currently, it simply execs the wrapper *script* "$SHELL $output", - but could eventually absorb all of the scripts functionality and - exec $objdir/$outputname directly. */ EOF cat <<"EOF" +#ifdef _MSC_VER +# define _CRT_SECURE_NO_DEPRECATE 1 +#endif #include #include #ifdef _MSC_VER # include # include # include -# define setmode _setmode #else # include # include # ifdef __CYGWIN__ # include -# define HAVE_SETENV -# ifdef __STRICT_ANSI__ -char *realpath (const char *, char *); -int putenv (char *); -int setenv (const char *, const char *, int); -# endif # endif #endif #include @@ -3177,6 +4175,44 @@ int setenv (const char *, const char *, int); #include #include +/* declarations of non-ANSI functions */ +#if defined(__MINGW32__) +# ifdef __STRICT_ANSI__ +int _putenv (const char *); +# endif +#elif defined(__CYGWIN__) +# ifdef __STRICT_ANSI__ +char *realpath (const char *, char *); +int putenv (char *); +int setenv (const char *, const char *, int); +# endif +/* #elif defined (other platforms) ... */ +#endif + +/* portability defines, excluding path handling macros */ +#if defined(_MSC_VER) +# define setmode _setmode +# define stat _stat +# define chmod _chmod +# define getcwd _getcwd +# define putenv _putenv +# define S_IXUSR _S_IEXEC +# ifndef _INTPTR_T_DEFINED +# define _INTPTR_T_DEFINED +# define intptr_t int +# endif +#elif defined(__MINGW32__) +# define setmode _setmode +# define stat _stat +# define chmod _chmod +# define getcwd _getcwd +# define putenv _putenv +#elif defined(__CYGWIN__) +# define HAVE_SETENV +# define FOPEN_WB "wb" +/* #elif defined (other platforms) ... */ +#endif + #if defined(PATH_MAX) # define LT_PATHMAX PATH_MAX #elif defined(MAXPATHLEN) @@ -3192,14 +4228,7 @@ int setenv (const char *, const char *, int); # define S_IXGRP 0 #endif -#ifdef _MSC_VER -# define S_IXUSR _S_IEXEC -# define stat _stat -# ifndef _INTPTR_T_DEFINED -# define intptr_t int -# endif -#endif - +/* path handling portability macros */ #ifndef DIR_SEPARATOR # define DIR_SEPARATOR '/' # define PATH_SEPARATOR ':' @@ -3230,10 +4259,6 @@ int setenv (const char *, const char *, int); # define IS_PATH_SEPARATOR(ch) ((ch) == PATH_SEPARATOR_2) #endif /* PATH_SEPARATOR_2 */ -#ifdef __CYGWIN__ -# define FOPEN_WB "wb" -#endif - #ifndef FOPEN_WB # define FOPEN_WB "w" #endif @@ -3246,22 +4271,13 @@ int setenv (const char *, const char *, int); if (stale) { free ((void *) stale); stale = 0; } \ } while (0) -#undef LTWRAPPER_DEBUGPRINTF -#if defined DEBUGWRAPPER -# define LTWRAPPER_DEBUGPRINTF(args) ltwrapper_debugprintf args -static void -ltwrapper_debugprintf (const char *fmt, ...) -{ - va_list args; - va_start (args, fmt); - (void) vfprintf (stderr, fmt, args); - va_end (args); -} +#if defined(LT_DEBUGWRAPPER) +static int lt_debug = 1; #else -# define LTWRAPPER_DEBUGPRINTF(args) +static int lt_debug = 0; #endif -const char *program_name = NULL; +const char *program_name = "libtool-wrapper"; /* in case xstrdup fails */ void *xmalloc (size_t num); char *xstrdup (const char *string); @@ -3271,41 +4287,27 @@ char *chase_symlinks (const char *pathspec); int make_executable (const char *path); int check_executable (const char *path); char *strendzap (char *str, const char *pat); -void lt_fatal (const char *message, ...); +void lt_debugprintf (const char *file, int line, const char *fmt, ...); +void lt_fatal (const char *file, int line, const char *message, ...); +static const char *nonnull (const char *s); +static const char *nonempty (const char *s); void lt_setenv (const char *name, const char *value); char *lt_extend_str (const char *orig_value, const char *add, int to_end); -void lt_opt_process_env_set (const char *arg); -void lt_opt_process_env_prepend (const char *arg); -void lt_opt_process_env_append (const char *arg); -int lt_split_name_value (const char *arg, char** name, char** value); void lt_update_exe_path (const char *name, const char *value); void lt_update_lib_path (const char *name, const char *value); - -static const char *script_text_part1 = -EOF - - func_emit_wrapper_part1 yes | - $SED -e 's/\([\\"]\)/\\\1/g' \ - -e 's/^/ "/' -e 's/$/\\n"/' - echo ";" - cat <"))); + lt_debugprintf (__FILE__, __LINE__, "(main) lt_argv_zero: %s\n", + nonnull (lt_argv_zero)); for (i = 0; i < newargc; i++) { - LTWRAPPER_DEBUGPRINTF (("(main) newargz[%d] : %s\n", i, (newargz[i] ? newargz[i] : ""))); + lt_debugprintf (__FILE__, __LINE__, "(main) newargz[%d]: %s\n", + i, nonnull (newargz[i])); } EOF @@ -3560,11 +4523,14 @@ EOF mingw*) cat <<"EOF" /* execv doesn't actually work on mingw as expected on unix */ + newargz = prepare_spawn (newargz); rval = _spawnv (_P_WAIT, lt_argv_zero, (const char * const *) newargz); if (rval == -1) { /* failed to start process */ - LTWRAPPER_DEBUGPRINTF (("(main) failed to launch target \"%s\": errno = %d\n", lt_argv_zero, errno)); + lt_debugprintf (__FILE__, __LINE__, + "(main) failed to launch target \"%s\": %s\n", + lt_argv_zero, nonnull (strerror (errno))); return 127; } return rval; @@ -3586,7 +4552,7 @@ xmalloc (size_t num) { void *p = (void *) malloc (num); if (!p) - lt_fatal ("Memory exhausted"); + lt_fatal (__FILE__, __LINE__, "memory exhausted"); return p; } @@ -3620,8 +4586,8 @@ check_executable (const char *path) { struct stat st; - LTWRAPPER_DEBUGPRINTF (("(check_executable) : %s\n", - path ? (*path ? path : "EMPTY!") : "NULL!")); + lt_debugprintf (__FILE__, __LINE__, "(check_executable): %s\n", + nonempty (path)); if ((!path) || (!*path)) return 0; @@ -3638,8 +4604,8 @@ make_executable (const char *path) int rval = 0; struct stat st; - LTWRAPPER_DEBUGPRINTF (("(make_executable) : %s\n", - path ? (*path ? path : "EMPTY!") : "NULL!")); + lt_debugprintf (__FILE__, __LINE__, "(make_executable): %s\n", + nonempty (path)); if ((!path) || (!*path)) return 0; @@ -3665,8 +4631,8 @@ find_executable (const char *wrapper) int tmp_len; char *concat_name; - LTWRAPPER_DEBUGPRINTF (("(find_executable) : %s\n", - wrapper ? (*wrapper ? wrapper : "EMPTY!") : "NULL!")); + lt_debugprintf (__FILE__, __LINE__, "(find_executable): %s\n", + nonempty (wrapper)); if ((wrapper == NULL) || (*wrapper == '\0')) return NULL; @@ -3719,7 +4685,8 @@ find_executable (const char *wrapper) { /* empty path: current directory */ if (getcwd (tmp, LT_PATHMAX) == NULL) - lt_fatal ("getcwd failed"); + lt_fatal (__FILE__, __LINE__, "getcwd failed: %s", + nonnull (strerror (errno))); tmp_len = strlen (tmp); concat_name = XMALLOC (char, tmp_len + 1 + strlen (wrapper) + 1); @@ -3744,7 +4711,8 @@ find_executable (const char *wrapper) } /* Relative path | not found in path: prepend cwd */ if (getcwd (tmp, LT_PATHMAX) == NULL) - lt_fatal ("getcwd failed"); + lt_fatal (__FILE__, __LINE__, "getcwd failed: %s", + nonnull (strerror (errno))); tmp_len = strlen (tmp); concat_name = XMALLOC (char, tmp_len + 1 + strlen (wrapper) + 1); memcpy (concat_name, tmp, tmp_len); @@ -3770,8 +4738,9 @@ chase_symlinks (const char *pathspec) int has_symlinks = 0; while (strlen (tmp_pathspec) && !has_symlinks) { - LTWRAPPER_DEBUGPRINTF (("checking path component for symlinks: %s\n", - tmp_pathspec)); + lt_debugprintf (__FILE__, __LINE__, + "checking path component for symlinks: %s\n", + tmp_pathspec); if (lstat (tmp_pathspec, &s) == 0) { if (S_ISLNK (s.st_mode) != 0) @@ -3793,8 +4762,9 @@ chase_symlinks (const char *pathspec) } else { - char *errstr = strerror (errno); - lt_fatal ("Error accessing file %s (%s)", tmp_pathspec, errstr); + lt_fatal (__FILE__, __LINE__, + "error accessing file \"%s\": %s", + tmp_pathspec, nonnull (strerror (errno))); } } XFREE (tmp_pathspec); @@ -3807,7 +4777,8 @@ chase_symlinks (const char *pathspec) tmp_pathspec = realpath (pathspec, buf); if (tmp_pathspec == 0) { - lt_fatal ("Could not follow symlinks for %s", pathspec); + lt_fatal (__FILE__, __LINE__, + "could not follow symlinks for %s", pathspec); } return xstrdup (tmp_pathspec); #endif @@ -3833,11 +4804,25 @@ strendzap (char *str, const char *pat) return str; } +void +lt_debugprintf (const char *file, int line, const char *fmt, ...) +{ + va_list args; + if (lt_debug) + { + (void) fprintf (stderr, "%s:%s:%d: ", program_name, file, line); + va_start (args, fmt); + (void) vfprintf (stderr, fmt, args); + va_end (args); + } +} + static void -lt_error_core (int exit_status, const char *mode, +lt_error_core (int exit_status, const char *file, + int line, const char *mode, const char *message, va_list ap) { - fprintf (stderr, "%s: %s: ", program_name, mode); + fprintf (stderr, "%s:%s:%d: %s: ", program_name, file, line, mode); vfprintf (stderr, message, ap); fprintf (stderr, ".\n"); @@ -3846,20 +4831,32 @@ lt_error_core (int exit_status, const char *mode, } void -lt_fatal (const char *message, ...) +lt_fatal (const char *file, int line, const char *message, ...) { va_list ap; va_start (ap, message); - lt_error_core (EXIT_FAILURE, "FATAL", message, ap); + lt_error_core (EXIT_FAILURE, file, line, "FATAL", message, ap); va_end (ap); } +static const char * +nonnull (const char *s) +{ + return s ? s : "(null)"; +} + +static const char * +nonempty (const char *s) +{ + return (s && !*s) ? "(empty)" : nonnull (s); +} + void lt_setenv (const char *name, const char *value) { - LTWRAPPER_DEBUGPRINTF (("(lt_setenv) setting '%s' to '%s'\n", - (name ? name : ""), - (value ? value : ""))); + lt_debugprintf (__FILE__, __LINE__, + "(lt_setenv) setting '%s' to '%s'\n", + nonnull (name), nonnull (value)); { #ifdef HAVE_SETENV /* always make a copy, for consistency with !HAVE_SETENV */ @@ -3904,95 +4901,12 @@ lt_extend_str (const char *orig_value, const char *add, int to_end) return new_value; } -int -lt_split_name_value (const char *arg, char** name, char** value) -{ - const char *p; - int len; - if (!arg || !*arg) - return 1; - - p = strchr (arg, (int)'='); - - if (!p) - return 1; - - *value = xstrdup (++p); - - len = strlen (arg) - strlen (*value); - *name = XMALLOC (char, len); - strncpy (*name, arg, len-1); - (*name)[len - 1] = '\0'; - - return 0; -} - -void -lt_opt_process_env_set (const char *arg) -{ - char *name = NULL; - char *value = NULL; - - if (lt_split_name_value (arg, &name, &value) != 0) - { - XFREE (name); - XFREE (value); - lt_fatal ("bad argument for %s: '%s'", env_set_opt, arg); - } - - lt_setenv (name, value); - XFREE (name); - XFREE (value); -} - -void -lt_opt_process_env_prepend (const char *arg) -{ - char *name = NULL; - char *value = NULL; - char *new_value = NULL; - - if (lt_split_name_value (arg, &name, &value) != 0) - { - XFREE (name); - XFREE (value); - lt_fatal ("bad argument for %s: '%s'", env_prepend_opt, arg); - } - - new_value = lt_extend_str (getenv (name), value, 0); - lt_setenv (name, new_value); - XFREE (new_value); - XFREE (name); - XFREE (value); -} - -void -lt_opt_process_env_append (const char *arg) -{ - char *name = NULL; - char *value = NULL; - char *new_value = NULL; - - if (lt_split_name_value (arg, &name, &value) != 0) - { - XFREE (name); - XFREE (value); - lt_fatal ("bad argument for %s: '%s'", env_append_opt, arg); - } - - new_value = lt_extend_str (getenv (name), value, 1); - lt_setenv (name, new_value); - XFREE (new_value); - XFREE (name); - XFREE (value); -} - void lt_update_exe_path (const char *name, const char *value) { - LTWRAPPER_DEBUGPRINTF (("(lt_update_exe_path) modifying '%s' by prepending '%s'\n", - (name ? name : ""), - (value ? value : ""))); + lt_debugprintf (__FILE__, __LINE__, + "(lt_update_exe_path) modifying '%s' by prepending '%s'\n", + nonnull (name), nonnull (value)); if (name && *name && value && *value) { @@ -4011,9 +4925,9 @@ lt_update_exe_path (const char *name, const char *value) void lt_update_lib_path (const char *name, const char *value) { - LTWRAPPER_DEBUGPRINTF (("(lt_update_lib_path) modifying '%s' by prepending '%s'\n", - (name ? name : ""), - (value ? value : ""))); + lt_debugprintf (__FILE__, __LINE__, + "(lt_update_lib_path) modifying '%s' by prepending '%s'\n", + nonnull (name), nonnull (value)); if (name && *name && value && *value) { @@ -4023,11 +4937,158 @@ lt_update_lib_path (const char *name, const char *value) } } +EOF + case $host_os in + mingw*) + cat <<"EOF" + +/* Prepares an argument vector before calling spawn(). + Note that spawn() does not by itself call the command interpreter + (getenv ("COMSPEC") != NULL ? getenv ("COMSPEC") : + ({ OSVERSIONINFO v; v.dwOSVersionInfoSize = sizeof(OSVERSIONINFO); + GetVersionEx(&v); + v.dwPlatformId == VER_PLATFORM_WIN32_NT; + }) ? "cmd.exe" : "command.com"). + Instead it simply concatenates the arguments, separated by ' ', and calls + CreateProcess(). We must quote the arguments since Win32 CreateProcess() + interprets characters like ' ', '\t', '\\', '"' (but not '<' and '>') in a + special way: + - Space and tab are interpreted as delimiters. They are not treated as + delimiters if they are surrounded by double quotes: "...". + - Unescaped double quotes are removed from the input. Their only effect is + that within double quotes, space and tab are treated like normal + characters. + - Backslashes not followed by double quotes are not special. + - But 2*n+1 backslashes followed by a double quote become + n backslashes followed by a double quote (n >= 0): + \" -> " + \\\" -> \" + \\\\\" -> \\" + */ +#define SHELL_SPECIAL_CHARS "\"\\ \001\002\003\004\005\006\007\010\011\012\013\014\015\016\017\020\021\022\023\024\025\026\027\030\031\032\033\034\035\036\037" +#define SHELL_SPACE_CHARS " \001\002\003\004\005\006\007\010\011\012\013\014\015\016\017\020\021\022\023\024\025\026\027\030\031\032\033\034\035\036\037" +char ** +prepare_spawn (char **argv) +{ + size_t argc; + char **new_argv; + size_t i; + + /* Count number of arguments. */ + for (argc = 0; argv[argc] != NULL; argc++) + ; + + /* Allocate new argument vector. */ + new_argv = XMALLOC (char *, argc + 1); + + /* Put quoted arguments into the new argument vector. */ + for (i = 0; i < argc; i++) + { + const char *string = argv[i]; + + if (string[0] == '\0') + new_argv[i] = xstrdup ("\"\""); + else if (strpbrk (string, SHELL_SPECIAL_CHARS) != NULL) + { + int quote_around = (strpbrk (string, SHELL_SPACE_CHARS) != NULL); + size_t length; + unsigned int backslashes; + const char *s; + char *quoted_string; + char *p; + + length = 0; + backslashes = 0; + if (quote_around) + length++; + for (s = string; *s != '\0'; s++) + { + char c = *s; + if (c == '"') + length += backslashes + 1; + length++; + if (c == '\\') + backslashes++; + else + backslashes = 0; + } + if (quote_around) + length += backslashes + 1; + + quoted_string = XMALLOC (char, length + 1); + + p = quoted_string; + backslashes = 0; + if (quote_around) + *p++ = '"'; + for (s = string; *s != '\0'; s++) + { + char c = *s; + if (c == '"') + { + unsigned int j; + for (j = backslashes + 1; j > 0; j--) + *p++ = '\\'; + } + *p++ = c; + if (c == '\\') + backslashes++; + else + backslashes = 0; + } + if (quote_around) + { + unsigned int j; + for (j = backslashes; j > 0; j--) + *p++ = '\\'; + *p++ = '"'; + } + *p = '\0'; + + new_argv[i] = quoted_string; + } + else + new_argv[i] = (char *) string; + } + new_argv[argc] = NULL; + + return new_argv; +} +EOF + ;; + esac + cat <<"EOF" +void lt_dump_script (FILE* f) +{ +EOF + func_emit_wrapper yes | + $SED -n -e ' +s/^\(.\{79\}\)\(..*\)/\1\ +\2/ +h +s/\([\\"]\)/\\\1/g +s/$/\\n/ +s/\([^\n]*\).*/ fputs ("\1", f);/p +g +D' + cat <<"EOF" +} EOF } # end: func_emit_cwrapperexe_src +# func_win32_import_lib_p ARG +# True if ARG is an import lib, as indicated by $file_magic_cmd +func_win32_import_lib_p () +{ + $opt_debug + case `eval $file_magic_cmd \"\$1\" 2>/dev/null | $SED -e 10q` in + *import*) : ;; + *) false ;; + esac +} + # func_mode_link arg... func_mode_link () { @@ -4072,6 +5133,7 @@ func_mode_link () new_inherited_linker_flags= avoid_version=no + bindir= dlfiles= dlprefiles= dlself=no @@ -4164,6 +5226,11 @@ func_mode_link () esac case $prev in + bindir) + bindir="$arg" + prev= + continue + ;; dlfiles|dlprefiles) if test "$preload" = no; then # Add the symbol object into the linking commands. @@ -4195,9 +5262,9 @@ func_mode_link () ;; *) if test "$prev" = dlfiles; then - dlfiles="$dlfiles $arg" + func_append dlfiles " $arg" else - dlprefiles="$dlprefiles $arg" + func_append dlprefiles " $arg" fi prev= continue @@ -4221,7 +5288,7 @@ func_mode_link () *-*-darwin*) case "$deplibs " in *" $qarg.ltframework "*) ;; - *) deplibs="$deplibs $qarg.ltframework" # this is fixed later + *) func_append deplibs " $qarg.ltframework" # this is fixed later ;; esac ;; @@ -4240,7 +5307,7 @@ func_mode_link () moreargs= for fil in `cat "$save_arg"` do -# moreargs="$moreargs $fil" +# func_append moreargs " $fil" arg=$fil # A libtool-controlled object. @@ -4269,7 +5336,7 @@ func_mode_link () if test "$prev" = dlfiles; then if test "$build_libtool_libs" = yes && test "$dlopen_support" = yes; then - dlfiles="$dlfiles $pic_object" + func_append dlfiles " $pic_object" prev= continue else @@ -4281,7 +5348,7 @@ func_mode_link () # CHECK ME: I think I busted this. -Ossama if test "$prev" = dlprefiles; then # Preload the old-style object. - dlprefiles="$dlprefiles $pic_object" + func_append dlprefiles " $pic_object" prev= fi @@ -4351,12 +5418,12 @@ func_mode_link () if test "$prev" = rpath; then case "$rpath " in *" $arg "*) ;; - *) rpath="$rpath $arg" ;; + *) func_append rpath " $arg" ;; esac else case "$xrpath " in *" $arg "*) ;; - *) xrpath="$xrpath $arg" ;; + *) func_append xrpath " $arg" ;; esac fi prev= @@ -4368,28 +5435,28 @@ func_mode_link () continue ;; weak) - weak_libs="$weak_libs $arg" + func_append weak_libs " $arg" prev= continue ;; xcclinker) - linker_flags="$linker_flags $qarg" - compiler_flags="$compiler_flags $qarg" + func_append linker_flags " $qarg" + func_append compiler_flags " $qarg" prev= func_append compile_command " $qarg" func_append finalize_command " $qarg" continue ;; xcompiler) - compiler_flags="$compiler_flags $qarg" + func_append compiler_flags " $qarg" prev= func_append compile_command " $qarg" func_append finalize_command " $qarg" continue ;; xlinker) - linker_flags="$linker_flags $qarg" - compiler_flags="$compiler_flags $wl$qarg" + func_append linker_flags " $qarg" + func_append compiler_flags " $wl$qarg" prev= func_append compile_command " $wl$qarg" func_append finalize_command " $wl$qarg" @@ -4425,6 +5492,11 @@ func_mode_link () continue ;; + -bindir) + prev=bindir + continue + ;; + -dlopen) prev=dlfiles continue @@ -4475,15 +5547,16 @@ func_mode_link () ;; -L*) - func_stripname '-L' '' "$arg" - dir=$func_stripname_result - if test -z "$dir"; then + func_stripname "-L" '' "$arg" + if test -z "$func_stripname_result"; then if test "$#" -gt 0; then func_fatal_error "require no space between \`-L' and \`$1'" else func_fatal_error "need path for \`-L' option" fi fi + func_resolve_sysroot "$func_stripname_result" + dir=$func_resolve_sysroot_result # We need an absolute path. case $dir in [\\/]* | [A-Za-z]:[\\/]*) ;; @@ -4495,24 +5568,30 @@ func_mode_link () ;; esac case "$deplibs " in - *" -L$dir "*) ;; + *" -L$dir "* | *" $arg "*) + # Will only happen for absolute or sysroot arguments + ;; *) - deplibs="$deplibs -L$dir" - lib_search_path="$lib_search_path $dir" + # Preserve sysroot, but never include relative directories + case $dir in + [\\/]* | [A-Za-z]:[\\/]* | =*) func_append deplibs " $arg" ;; + *) func_append deplibs " -L$dir" ;; + esac + func_append lib_search_path " $dir" ;; esac case $host in *-*-cygwin* | *-*-mingw* | *-*-pw32* | *-*-os2* | *-cegcc*) - testbindir=`$ECHO "X$dir" | $Xsed -e 's*/lib$*/bin*'` + testbindir=`$ECHO "$dir" | $SED 's*/lib$*/bin*'` case :$dllsearchpath: in *":$dir:"*) ;; ::) dllsearchpath=$dir;; - *) dllsearchpath="$dllsearchpath:$dir";; + *) func_append dllsearchpath ":$dir";; esac case :$dllsearchpath: in *":$testbindir:"*) ;; ::) dllsearchpath=$testbindir;; - *) dllsearchpath="$dllsearchpath:$testbindir";; + *) func_append dllsearchpath ":$testbindir";; esac ;; esac @@ -4522,7 +5601,7 @@ func_mode_link () -l*) if test "X$arg" = "X-lc" || test "X$arg" = "X-lm"; then case $host in - *-*-cygwin* | *-*-mingw* | *-*-pw32* | *-*-beos* | *-cegcc*) + *-*-cygwin* | *-*-mingw* | *-*-pw32* | *-*-beos* | *-cegcc* | *-*-haiku*) # These systems don't actually have a C or math library (as such) continue ;; @@ -4536,7 +5615,7 @@ func_mode_link () ;; *-*-rhapsody* | *-*-darwin1.[012]) # Rhapsody C and math libraries are in the System framework - deplibs="$deplibs System.ltframework" + func_append deplibs " System.ltframework" continue ;; *-*-sco3.2v5* | *-*-sco5v6*) @@ -4556,7 +5635,7 @@ func_mode_link () ;; esac fi - deplibs="$deplibs $arg" + func_append deplibs " $arg" continue ;; @@ -4568,21 +5647,22 @@ func_mode_link () # Tru64 UNIX uses -model [arg] to determine the layout of C++ # classes, name mangling, and exception handling. # Darwin uses the -arch flag to determine output architecture. - -model|-arch|-isysroot) - compiler_flags="$compiler_flags $arg" + -model|-arch|-isysroot|--sysroot) + func_append compiler_flags " $arg" func_append compile_command " $arg" func_append finalize_command " $arg" prev=xcompiler continue ;; - -mt|-mthreads|-kthread|-Kthread|-pthread|-pthreads|--thread-safe|-threads) - compiler_flags="$compiler_flags $arg" + -mt|-mthreads|-kthread|-Kthread|-pthread|-pthreads|--thread-safe \ + |-threads|-fopenmp|-openmp|-mp|-xopenmp|-omp|-qsmp=*) + func_append compiler_flags " $arg" func_append compile_command " $arg" func_append finalize_command " $arg" case "$new_inherited_linker_flags " in *" $arg "*) ;; - * ) new_inherited_linker_flags="$new_inherited_linker_flags $arg" ;; + * ) func_append new_inherited_linker_flags " $arg" ;; esac continue ;; @@ -4649,13 +5729,17 @@ func_mode_link () # We need an absolute path. case $dir in [\\/]* | [A-Za-z]:[\\/]*) ;; + =*) + func_stripname '=' '' "$dir" + dir=$lt_sysroot$func_stripname_result + ;; *) func_fatal_error "only absolute run-paths are allowed" ;; esac case "$xrpath " in *" $dir "*) ;; - *) xrpath="$xrpath $dir" ;; + *) func_append xrpath " $dir" ;; esac continue ;; @@ -4708,8 +5792,8 @@ func_mode_link () for flag in $args; do IFS="$save_ifs" func_quote_for_eval "$flag" - arg="$arg $wl$func_quote_for_eval_result" - compiler_flags="$compiler_flags $func_quote_for_eval_result" + func_append arg " $func_quote_for_eval_result" + func_append compiler_flags " $func_quote_for_eval_result" done IFS="$save_ifs" func_stripname ' ' '' "$arg" @@ -4724,9 +5808,9 @@ func_mode_link () for flag in $args; do IFS="$save_ifs" func_quote_for_eval "$flag" - arg="$arg $wl$func_quote_for_eval_result" - compiler_flags="$compiler_flags $wl$func_quote_for_eval_result" - linker_flags="$linker_flags $func_quote_for_eval_result" + func_append arg " $wl$func_quote_for_eval_result" + func_append compiler_flags " $wl$func_quote_for_eval_result" + func_append linker_flags " $func_quote_for_eval_result" done IFS="$save_ifs" func_stripname ' ' '' "$arg" @@ -4754,23 +5838,27 @@ func_mode_link () arg="$func_quote_for_eval_result" ;; - # -64, -mips[0-9] enable 64-bit mode on the SGI compiler - # -r[0-9][0-9]* specifies the processor on the SGI compiler - # -xarch=*, -xtarget=* enable 64-bit mode on the Sun compiler - # +DA*, +DD* enable 64-bit mode on the HP compiler - # -q* pass through compiler args for the IBM compiler - # -m*, -t[45]*, -txscale* pass through architecture-specific - # compiler args for GCC - # -F/path gives path to uninstalled frameworks, gcc on darwin - # -p, -pg, --coverage, -fprofile-* pass through profiling flag for GCC - # @file GCC response files + # Flags to be passed through unchanged, with rationale: + # -64, -mips[0-9] enable 64-bit mode for the SGI compiler + # -r[0-9][0-9]* specify processor for the SGI compiler + # -xarch=*, -xtarget=* enable 64-bit mode for the Sun compiler + # +DA*, +DD* enable 64-bit mode for the HP compiler + # -q* compiler args for the IBM compiler + # -m*, -t[45]*, -txscale* architecture-specific flags for GCC + # -F/path path to uninstalled frameworks, gcc on darwin + # -p, -pg, --coverage, -fprofile-* profiling flags for GCC + # @file GCC response files + # -tp=* Portland pgcc target processor selection + # --sysroot=* for sysroot support + # -O*, -flto*, -fwhopr*, -fuse-linker-plugin GCC link-time optimization -64|-mips[0-9]|-r[0-9][0-9]*|-xarch=*|-xtarget=*|+DA*|+DD*|-q*|-m*| \ - -t[45]*|-txscale*|-p|-pg|--coverage|-fprofile-*|-F*|@*) + -t[45]*|-txscale*|-p|-pg|--coverage|-fprofile-*|-F*|@*|-tp=*|--sysroot=*| \ + -O*|-flto*|-fwhopr*|-fuse-linker-plugin) func_quote_for_eval "$arg" arg="$func_quote_for_eval_result" func_append compile_command " $arg" func_append finalize_command " $arg" - compiler_flags="$compiler_flags $arg" + func_append compiler_flags " $arg" continue ;; @@ -4782,7 +5870,7 @@ func_mode_link () *.$objext) # A standard object. - objs="$objs $arg" + func_append objs " $arg" ;; *.lo) @@ -4813,7 +5901,7 @@ func_mode_link () if test "$prev" = dlfiles; then if test "$build_libtool_libs" = yes && test "$dlopen_support" = yes; then - dlfiles="$dlfiles $pic_object" + func_append dlfiles " $pic_object" prev= continue else @@ -4825,7 +5913,7 @@ func_mode_link () # CHECK ME: I think I busted this. -Ossama if test "$prev" = dlprefiles; then # Preload the old-style object. - dlprefiles="$dlprefiles $pic_object" + func_append dlprefiles " $pic_object" prev= fi @@ -4870,24 +5958,25 @@ func_mode_link () *.$libext) # An archive. - deplibs="$deplibs $arg" - old_deplibs="$old_deplibs $arg" + func_append deplibs " $arg" + func_append old_deplibs " $arg" continue ;; *.la) # A libtool-controlled library. + func_resolve_sysroot "$arg" if test "$prev" = dlfiles; then # This library was specified with -dlopen. - dlfiles="$dlfiles $arg" + func_append dlfiles " $func_resolve_sysroot_result" prev= elif test "$prev" = dlprefiles; then # The library was specified with -dlpreopen. - dlprefiles="$dlprefiles $arg" + func_append dlprefiles " $func_resolve_sysroot_result" prev= else - deplibs="$deplibs $arg" + func_append deplibs " $func_resolve_sysroot_result" fi continue ;; @@ -4925,7 +6014,7 @@ func_mode_link () if test -n "$shlibpath_var"; then # get the directories listed in $shlibpath_var - eval shlib_search_path=\`\$ECHO \"X\${$shlibpath_var}\" \| \$Xsed -e \'s/:/ /g\'\` + eval shlib_search_path=\`\$ECHO \"\${$shlibpath_var}\" \| \$SED \'s/:/ /g\'\` else shlib_search_path= fi @@ -4934,6 +6023,8 @@ func_mode_link () func_dirname "$output" "/" "" output_objdir="$func_dirname_result$objdir" + func_to_tool_file "$output_objdir/" + tool_output_objdir=$func_to_tool_file_result # Create the object directory. func_mkdir_p "$output_objdir" @@ -4954,12 +6045,12 @@ func_mode_link () # Find all interdependent deplibs by searching for libraries # that are linked more than once (e.g. -la -lb -la) for deplib in $deplibs; do - if $opt_duplicate_deps ; then + if $opt_preserve_dup_deps ; then case "$libs " in - *" $deplib "*) specialdeplibs="$specialdeplibs $deplib" ;; + *" $deplib "*) func_append specialdeplibs " $deplib" ;; esac fi - libs="$libs $deplib" + func_append libs " $deplib" done if test "$linkmode" = lib; then @@ -4972,9 +6063,9 @@ func_mode_link () if $opt_duplicate_compiler_generated_deps; then for pre_post_dep in $predeps $postdeps; do case "$pre_post_deps " in - *" $pre_post_dep "*) specialdeplibs="$specialdeplibs $pre_post_deps" ;; + *" $pre_post_dep "*) func_append specialdeplibs " $pre_post_deps" ;; esac - pre_post_deps="$pre_post_deps $pre_post_dep" + func_append pre_post_deps " $pre_post_dep" done fi pre_post_deps= @@ -5044,17 +6135,19 @@ func_mode_link () for lib in $dlprefiles; do # Ignore non-libtool-libs dependency_libs= + func_resolve_sysroot "$lib" case $lib in - *.la) func_source "$lib" ;; + *.la) func_source "$func_resolve_sysroot_result" ;; esac # Collect preopened libtool deplibs, except any this library # has declared as weak libs for deplib in $dependency_libs; do - deplib_base=`$ECHO "X$deplib" | $Xsed -e "$basename"` + func_basename "$deplib" + deplib_base=$func_basename_result case " $weak_libs " in *" $deplib_base "*) ;; - *) deplibs="$deplibs $deplib" ;; + *) func_append deplibs " $deplib" ;; esac done done @@ -5070,16 +6163,17 @@ func_mode_link () lib= found=no case $deplib in - -mt|-mthreads|-kthread|-Kthread|-pthread|-pthreads|--thread-safe|-threads) + -mt|-mthreads|-kthread|-Kthread|-pthread|-pthreads|--thread-safe \ + |-threads|-fopenmp|-openmp|-mp|-xopenmp|-omp|-qsmp=*) if test "$linkmode,$pass" = "prog,link"; then compile_deplibs="$deplib $compile_deplibs" finalize_deplibs="$deplib $finalize_deplibs" else - compiler_flags="$compiler_flags $deplib" + func_append compiler_flags " $deplib" if test "$linkmode" = lib ; then case "$new_inherited_linker_flags " in *" $deplib "*) ;; - * ) new_inherited_linker_flags="$new_inherited_linker_flags $deplib" ;; + * ) func_append new_inherited_linker_flags " $deplib" ;; esac fi fi @@ -5164,7 +6258,7 @@ func_mode_link () if test "$linkmode" = lib ; then case "$new_inherited_linker_flags " in *" $deplib "*) ;; - * ) new_inherited_linker_flags="$new_inherited_linker_flags $deplib" ;; + * ) func_append new_inherited_linker_flags " $deplib" ;; esac fi fi @@ -5177,7 +6271,8 @@ func_mode_link () test "$pass" = conv && continue newdependency_libs="$deplib $newdependency_libs" func_stripname '-L' '' "$deplib" - newlib_search_path="$newlib_search_path $func_stripname_result" + func_resolve_sysroot "$func_stripname_result" + func_append newlib_search_path " $func_resolve_sysroot_result" ;; prog) if test "$pass" = conv; then @@ -5191,7 +6286,8 @@ func_mode_link () finalize_deplibs="$deplib $finalize_deplibs" fi func_stripname '-L' '' "$deplib" - newlib_search_path="$newlib_search_path $func_stripname_result" + func_resolve_sysroot "$func_stripname_result" + func_append newlib_search_path " $func_resolve_sysroot_result" ;; *) func_warning "\`-L' is ignored for archives/objects" @@ -5202,17 +6298,21 @@ func_mode_link () -R*) if test "$pass" = link; then func_stripname '-R' '' "$deplib" - dir=$func_stripname_result + func_resolve_sysroot "$func_stripname_result" + dir=$func_resolve_sysroot_result # Make sure the xrpath contains only unique directories. case "$xrpath " in *" $dir "*) ;; - *) xrpath="$xrpath $dir" ;; + *) func_append xrpath " $dir" ;; esac fi deplibs="$deplib $deplibs" continue ;; - *.la) lib="$deplib" ;; + *.la) + func_resolve_sysroot "$deplib" + lib=$func_resolve_sysroot_result + ;; *.$libext) if test "$pass" = conv; then deplibs="$deplib $deplibs" @@ -5230,7 +6330,7 @@ func_mode_link () match_pattern*) set dummy $deplibs_check_method; shift match_pattern_regex=`expr "$deplibs_check_method" : "$1 \(.*\)"` - if eval "\$ECHO \"X$deplib\"" 2>/dev/null | $Xsed -e 10q \ + if eval "\$ECHO \"$deplib\"" 2>/dev/null | $SED 10q \ | $EGREP "$match_pattern_regex" > /dev/null; then valid_a_lib=yes fi @@ -5240,15 +6340,15 @@ func_mode_link () ;; esac if test "$valid_a_lib" != yes; then - $ECHO + echo $ECHO "*** Warning: Trying to link with static lib archive $deplib." - $ECHO "*** I have the capability to make that library automatically link in when" - $ECHO "*** you link to this library. But I can only do this if you have a" - $ECHO "*** shared version of the library, which you do not appear to have" - $ECHO "*** because the file extensions .$libext of this argument makes me believe" - $ECHO "*** that it is just a static archive that I should not use here." + echo "*** I have the capability to make that library automatically link in when" + echo "*** you link to this library. But I can only do this if you have a" + echo "*** shared version of the library, which you do not appear to have" + echo "*** because the file extensions .$libext of this argument makes me believe" + echo "*** that it is just a static archive that I should not use here." else - $ECHO + echo $ECHO "*** Warning: Linking the shared library $output against the" $ECHO "*** static library $deplib is not portable!" deplibs="$deplib $deplibs" @@ -5275,11 +6375,11 @@ func_mode_link () if test "$pass" = dlpreopen || test "$dlopen_support" != yes || test "$build_libtool_libs" = no; then # If there is no dlopen support or we're linking statically, # we need to preload. - newdlprefiles="$newdlprefiles $deplib" + func_append newdlprefiles " $deplib" compile_deplibs="$deplib $compile_deplibs" finalize_deplibs="$deplib $finalize_deplibs" else - newdlfiles="$newdlfiles $deplib" + func_append newdlfiles " $deplib" fi fi continue @@ -5321,20 +6421,20 @@ func_mode_link () # Convert "-framework foo" to "foo.ltframework" if test -n "$inherited_linker_flags"; then - tmp_inherited_linker_flags=`$ECHO "X$inherited_linker_flags" | $Xsed -e 's/-framework \([^ $]*\)/\1.ltframework/g'` + tmp_inherited_linker_flags=`$ECHO "$inherited_linker_flags" | $SED 's/-framework \([^ $]*\)/\1.ltframework/g'` for tmp_inherited_linker_flag in $tmp_inherited_linker_flags; do case " $new_inherited_linker_flags " in *" $tmp_inherited_linker_flag "*) ;; - *) new_inherited_linker_flags="$new_inherited_linker_flags $tmp_inherited_linker_flag";; + *) func_append new_inherited_linker_flags " $tmp_inherited_linker_flag";; esac done fi - dependency_libs=`$ECHO "X $dependency_libs" | $Xsed -e 's% \([^ $]*\).ltframework% -framework \1%g'` + dependency_libs=`$ECHO " $dependency_libs" | $SED 's% \([^ $]*\).ltframework% -framework \1%g'` if test "$linkmode,$pass" = "lib,link" || test "$linkmode,$pass" = "prog,scan" || { test "$linkmode" != prog && test "$linkmode" != lib; }; then - test -n "$dlopen" && dlfiles="$dlfiles $dlopen" - test -n "$dlpreopen" && dlprefiles="$dlprefiles $dlpreopen" + test -n "$dlopen" && func_append dlfiles " $dlopen" + test -n "$dlpreopen" && func_append dlprefiles " $dlpreopen" fi if test "$pass" = conv; then @@ -5345,17 +6445,17 @@ func_mode_link () func_fatal_error "cannot find name of link library for \`$lib'" fi # It is a libtool convenience library, so add in its objects. - convenience="$convenience $ladir/$objdir/$old_library" - old_convenience="$old_convenience $ladir/$objdir/$old_library" + func_append convenience " $ladir/$objdir/$old_library" + func_append old_convenience " $ladir/$objdir/$old_library" tmp_libs= for deplib in $dependency_libs; do deplibs="$deplib $deplibs" - if $opt_duplicate_deps ; then + if $opt_preserve_dup_deps ; then case "$tmp_libs " in - *" $deplib "*) specialdeplibs="$specialdeplibs $deplib" ;; + *" $deplib "*) func_append specialdeplibs " $deplib" ;; esac fi - tmp_libs="$tmp_libs $deplib" + func_append tmp_libs " $deplib" done elif test "$linkmode" != prog && test "$linkmode" != lib; then func_fatal_error "\`$lib' is not a convenience library" @@ -5366,9 +6466,15 @@ func_mode_link () # Get the name of the library we link against. linklib= - for l in $old_library $library_names; do - linklib="$l" - done + if test -n "$old_library" && + { test "$prefer_static_libs" = yes || + test "$prefer_static_libs,$installed" = "built,no"; }; then + linklib=$old_library + else + for l in $old_library $library_names; do + linklib="$l" + done + fi if test -z "$linklib"; then func_fatal_error "cannot find name of link library for \`$lib'" fi @@ -5385,9 +6491,9 @@ func_mode_link () # statically, we need to preload. We also need to preload any # dependent libraries so libltdl's deplib preloader doesn't # bomb out in the load deplibs phase. - dlprefiles="$dlprefiles $lib $dependency_libs" + func_append dlprefiles " $lib $dependency_libs" else - newdlfiles="$newdlfiles $lib" + func_append newdlfiles " $lib" fi continue fi # $pass = dlopen @@ -5409,14 +6515,14 @@ func_mode_link () # Find the relevant object directory and library name. if test "X$installed" = Xyes; then - if test ! -f "$libdir/$linklib" && test -f "$abs_ladir/$linklib"; then + if test ! -f "$lt_sysroot$libdir/$linklib" && test -f "$abs_ladir/$linklib"; then func_warning "library \`$lib' was moved." dir="$ladir" absdir="$abs_ladir" libdir="$abs_ladir" else - dir="$libdir" - absdir="$libdir" + dir="$lt_sysroot$libdir" + absdir="$lt_sysroot$libdir" fi test "X$hardcode_automatic" = Xyes && avoidtemprpath=yes else @@ -5424,12 +6530,12 @@ func_mode_link () dir="$ladir" absdir="$abs_ladir" # Remove this search path later - notinst_path="$notinst_path $abs_ladir" + func_append notinst_path " $abs_ladir" else dir="$ladir/$objdir" absdir="$abs_ladir/$objdir" # Remove this search path later - notinst_path="$notinst_path $abs_ladir" + func_append notinst_path " $abs_ladir" fi fi # $installed = yes func_stripname 'lib' '.la' "$laname" @@ -5440,20 +6546,46 @@ func_mode_link () if test -z "$libdir" && test "$linkmode" = prog; then func_fatal_error "only libraries may -dlpreopen a convenience library: \`$lib'" fi - # Prefer using a static library (so that no silly _DYNAMIC symbols - # are required to link). - if test -n "$old_library"; then - newdlprefiles="$newdlprefiles $dir/$old_library" - # Keep a list of preopened convenience libraries to check - # that they are being used correctly in the link pass. - test -z "$libdir" && \ - dlpreconveniencelibs="$dlpreconveniencelibs $dir/$old_library" - # Otherwise, use the dlname, so that lt_dlopen finds it. - elif test -n "$dlname"; then - newdlprefiles="$newdlprefiles $dir/$dlname" - else - newdlprefiles="$newdlprefiles $dir/$linklib" - fi + case "$host" in + # special handling for platforms with PE-DLLs. + *cygwin* | *mingw* | *cegcc* ) + # Linker will automatically link against shared library if both + # static and shared are present. Therefore, ensure we extract + # symbols from the import library if a shared library is present + # (otherwise, the dlopen module name will be incorrect). We do + # this by putting the import library name into $newdlprefiles. + # We recover the dlopen module name by 'saving' the la file + # name in a special purpose variable, and (later) extracting the + # dlname from the la file. + if test -n "$dlname"; then + func_tr_sh "$dir/$linklib" + eval "libfile_$func_tr_sh_result=\$abs_ladir/\$laname" + func_append newdlprefiles " $dir/$linklib" + else + func_append newdlprefiles " $dir/$old_library" + # Keep a list of preopened convenience libraries to check + # that they are being used correctly in the link pass. + test -z "$libdir" && \ + func_append dlpreconveniencelibs " $dir/$old_library" + fi + ;; + * ) + # Prefer using a static library (so that no silly _DYNAMIC symbols + # are required to link). + if test -n "$old_library"; then + func_append newdlprefiles " $dir/$old_library" + # Keep a list of preopened convenience libraries to check + # that they are being used correctly in the link pass. + test -z "$libdir" && \ + func_append dlpreconveniencelibs " $dir/$old_library" + # Otherwise, use the dlname, so that lt_dlopen finds it. + elif test -n "$dlname"; then + func_append newdlprefiles " $dir/$dlname" + else + func_append newdlprefiles " $dir/$linklib" + fi + ;; + esac fi # $pass = dlpreopen if test -z "$libdir"; then @@ -5471,7 +6603,7 @@ func_mode_link () if test "$linkmode" = prog && test "$pass" != link; then - newlib_search_path="$newlib_search_path $ladir" + func_append newlib_search_path " $ladir" deplibs="$lib $deplibs" linkalldeplibs=no @@ -5484,7 +6616,8 @@ func_mode_link () for deplib in $dependency_libs; do case $deplib in -L*) func_stripname '-L' '' "$deplib" - newlib_search_path="$newlib_search_path $func_stripname_result" + func_resolve_sysroot "$func_stripname_result" + func_append newlib_search_path " $func_resolve_sysroot_result" ;; esac # Need to link against all dependency_libs? @@ -5495,12 +6628,12 @@ func_mode_link () # or/and link against static libraries newdependency_libs="$deplib $newdependency_libs" fi - if $opt_duplicate_deps ; then + if $opt_preserve_dup_deps ; then case "$tmp_libs " in - *" $deplib "*) specialdeplibs="$specialdeplibs $deplib" ;; + *" $deplib "*) func_append specialdeplibs " $deplib" ;; esac fi - tmp_libs="$tmp_libs $deplib" + func_append tmp_libs " $deplib" done # for deplib continue fi # $linkmode = prog... @@ -5515,7 +6648,7 @@ func_mode_link () # Make sure the rpath contains only unique directories. case "$temp_rpath:" in *"$absdir:"*) ;; - *) temp_rpath="$temp_rpath$absdir:" ;; + *) func_append temp_rpath "$absdir:" ;; esac fi @@ -5527,7 +6660,7 @@ func_mode_link () *) case "$compile_rpath " in *" $absdir "*) ;; - *) compile_rpath="$compile_rpath $absdir" + *) func_append compile_rpath " $absdir" ;; esac ;; esac @@ -5536,7 +6669,7 @@ func_mode_link () *) case "$finalize_rpath " in *" $libdir "*) ;; - *) finalize_rpath="$finalize_rpath $libdir" + *) func_append finalize_rpath " $libdir" ;; esac ;; esac @@ -5561,12 +6694,12 @@ func_mode_link () case $host in *cygwin* | *mingw* | *cegcc*) # No point in relinking DLLs because paths are not encoded - notinst_deplibs="$notinst_deplibs $lib" + func_append notinst_deplibs " $lib" need_relink=no ;; *) if test "$installed" = no; then - notinst_deplibs="$notinst_deplibs $lib" + func_append notinst_deplibs " $lib" need_relink=yes fi ;; @@ -5583,7 +6716,7 @@ func_mode_link () fi done if test -z "$dlopenmodule" && test "$shouldnotlink" = yes && test "$pass" = link; then - $ECHO + echo if test "$linkmode" = prog; then $ECHO "*** Warning: Linking the executable $output against the loadable module" else @@ -5601,7 +6734,7 @@ func_mode_link () *) case "$compile_rpath " in *" $absdir "*) ;; - *) compile_rpath="$compile_rpath $absdir" + *) func_append compile_rpath " $absdir" ;; esac ;; esac @@ -5610,7 +6743,7 @@ func_mode_link () *) case "$finalize_rpath " in *" $libdir "*) ;; - *) finalize_rpath="$finalize_rpath $libdir" + *) func_append finalize_rpath " $libdir" ;; esac ;; esac @@ -5664,7 +6797,7 @@ func_mode_link () linklib=$newlib fi # test -n "$old_archive_from_expsyms_cmds" - if test "$linkmode" = prog || test "$mode" != relink; then + if test "$linkmode" = prog || test "$opt_mode" != relink; then add_shlibpath= add_dir= add= @@ -5686,9 +6819,9 @@ func_mode_link () if test "X$dlopenmodule" != "X$lib"; then $ECHO "*** Warning: lib $linklib is a module, not a shared library" if test -z "$old_library" ; then - $ECHO - $ECHO "*** And there doesn't seem to be a static archive available" - $ECHO "*** The link will probably fail, sorry" + echo + echo "*** And there doesn't seem to be a static archive available" + echo "*** The link will probably fail, sorry" else add="$dir/$old_library" fi @@ -5715,12 +6848,12 @@ func_mode_link () test "$hardcode_direct_absolute" = no; then add="$dir/$linklib" elif test "$hardcode_minus_L" = yes; then - add_dir="-L$dir" + add_dir="-L$absdir" # Try looking first in the location we're being installed to. if test -n "$inst_prefix_dir"; then case $libdir in [\\/]*) - add_dir="$add_dir -L$inst_prefix_dir$libdir" + func_append add_dir " -L$inst_prefix_dir$libdir" ;; esac fi @@ -5742,7 +6875,7 @@ func_mode_link () if test -n "$add_shlibpath"; then case :$compile_shlibpath: in *":$add_shlibpath:"*) ;; - *) compile_shlibpath="$compile_shlibpath$add_shlibpath:" ;; + *) func_append compile_shlibpath "$add_shlibpath:" ;; esac fi if test "$linkmode" = prog; then @@ -5756,13 +6889,13 @@ func_mode_link () test "$hardcode_shlibpath_var" = yes; then case :$finalize_shlibpath: in *":$libdir:"*) ;; - *) finalize_shlibpath="$finalize_shlibpath$libdir:" ;; + *) func_append finalize_shlibpath "$libdir:" ;; esac fi fi fi - if test "$linkmode" = prog || test "$mode" = relink; then + if test "$linkmode" = prog || test "$opt_mode" = relink; then add_shlibpath= add_dir= add= @@ -5776,7 +6909,7 @@ func_mode_link () elif test "$hardcode_shlibpath_var" = yes; then case :$finalize_shlibpath: in *":$libdir:"*) ;; - *) finalize_shlibpath="$finalize_shlibpath$libdir:" ;; + *) func_append finalize_shlibpath "$libdir:" ;; esac add="-l$name" elif test "$hardcode_automatic" = yes; then @@ -5793,7 +6926,7 @@ func_mode_link () if test -n "$inst_prefix_dir"; then case $libdir in [\\/]*) - add_dir="$add_dir -L$inst_prefix_dir$libdir" + func_append add_dir " -L$inst_prefix_dir$libdir" ;; esac fi @@ -5828,21 +6961,21 @@ func_mode_link () # Just print a warning and add the library to dependency_libs so # that the program can be linked against the static library. - $ECHO + echo $ECHO "*** Warning: This system can not link to static lib archive $lib." - $ECHO "*** I have the capability to make that library automatically link in when" - $ECHO "*** you link to this library. But I can only do this if you have a" - $ECHO "*** shared version of the library, which you do not appear to have." + echo "*** I have the capability to make that library automatically link in when" + echo "*** you link to this library. But I can only do this if you have a" + echo "*** shared version of the library, which you do not appear to have." if test "$module" = yes; then - $ECHO "*** But as you try to build a module library, libtool will still create " - $ECHO "*** a static module, that should work as long as the dlopening application" - $ECHO "*** is linked with the -dlopen flag to resolve symbols at runtime." + echo "*** But as you try to build a module library, libtool will still create " + echo "*** a static module, that should work as long as the dlopening application" + echo "*** is linked with the -dlopen flag to resolve symbols at runtime." if test -z "$global_symbol_pipe"; then - $ECHO - $ECHO "*** However, this would only work if libtool was able to extract symbol" - $ECHO "*** lists from a program, using \`nm' or equivalent, but libtool could" - $ECHO "*** not find such a program. So, this module is probably useless." - $ECHO "*** \`nm' from GNU binutils and a full rebuild may help." + echo + echo "*** However, this would only work if libtool was able to extract symbol" + echo "*** lists from a program, using \`nm' or equivalent, but libtool could" + echo "*** not find such a program. So, this module is probably useless." + echo "*** \`nm' from GNU binutils and a full rebuild may help." fi if test "$build_old_libs" = no; then build_libtool_libs=module @@ -5870,27 +7003,33 @@ func_mode_link () temp_xrpath=$func_stripname_result case " $xrpath " in *" $temp_xrpath "*) ;; - *) xrpath="$xrpath $temp_xrpath";; + *) func_append xrpath " $temp_xrpath";; esac;; - *) temp_deplibs="$temp_deplibs $libdir";; + *) func_append temp_deplibs " $libdir";; esac done dependency_libs="$temp_deplibs" fi - newlib_search_path="$newlib_search_path $absdir" + func_append newlib_search_path " $absdir" # Link against this library test "$link_static" = no && newdependency_libs="$abs_ladir/$laname $newdependency_libs" # ... and its dependency_libs tmp_libs= for deplib in $dependency_libs; do newdependency_libs="$deplib $newdependency_libs" - if $opt_duplicate_deps ; then + case $deplib in + -L*) func_stripname '-L' '' "$deplib" + func_resolve_sysroot "$func_stripname_result";; + *) func_resolve_sysroot "$deplib" ;; + esac + if $opt_preserve_dup_deps ; then case "$tmp_libs " in - *" $deplib "*) specialdeplibs="$specialdeplibs $deplib" ;; + *" $func_resolve_sysroot_result "*) + func_append specialdeplibs " $func_resolve_sysroot_result" ;; esac fi - tmp_libs="$tmp_libs $deplib" + func_append tmp_libs " $func_resolve_sysroot_result" done if test "$link_all_deplibs" != no; then @@ -5900,8 +7039,10 @@ func_mode_link () case $deplib in -L*) path="$deplib" ;; *.la) + func_resolve_sysroot "$deplib" + deplib=$func_resolve_sysroot_result func_dirname "$deplib" "" "." - dir="$func_dirname_result" + dir=$func_dirname_result # We need an absolute path. case $dir in [\\/]* | [A-Za-z]:[\\/]*) absdir="$dir" ;; @@ -5928,8 +7069,8 @@ func_mode_link () if test -z "$darwin_install_name"; then darwin_install_name=`${OTOOL64} -L $depdepl | awk '{if (NR == 2) {print $1;exit}}'` fi - compiler_flags="$compiler_flags ${wl}-dylib_file ${wl}${darwin_install_name}:${depdepl}" - linker_flags="$linker_flags -dylib_file ${darwin_install_name}:${depdepl}" + func_append compiler_flags " ${wl}-dylib_file ${wl}${darwin_install_name}:${depdepl}" + func_append linker_flags " -dylib_file ${darwin_install_name}:${depdepl}" path= fi fi @@ -5962,7 +7103,7 @@ func_mode_link () compile_deplibs="$new_inherited_linker_flags $compile_deplibs" finalize_deplibs="$new_inherited_linker_flags $finalize_deplibs" else - compiler_flags="$compiler_flags "`$ECHO "X $new_inherited_linker_flags" | $Xsed -e 's% \([^ $]*\).ltframework% -framework \1%g'` + compiler_flags="$compiler_flags "`$ECHO " $new_inherited_linker_flags" | $SED 's% \([^ $]*\).ltframework% -framework \1%g'` fi fi dependency_libs="$newdependency_libs" @@ -5979,7 +7120,7 @@ func_mode_link () for dir in $newlib_search_path; do case "$lib_search_path " in *" $dir "*) ;; - *) lib_search_path="$lib_search_path $dir" ;; + *) func_append lib_search_path " $dir" ;; esac done newlib_search_path= @@ -6037,10 +7178,10 @@ func_mode_link () -L*) case " $tmp_libs " in *" $deplib "*) ;; - *) tmp_libs="$tmp_libs $deplib" ;; + *) func_append tmp_libs " $deplib" ;; esac ;; - *) tmp_libs="$tmp_libs $deplib" ;; + *) func_append tmp_libs " $deplib" ;; esac done eval $var=\"$tmp_libs\" @@ -6056,7 +7197,7 @@ func_mode_link () ;; esac if test -n "$i" ; then - tmp_libs="$tmp_libs $i" + func_append tmp_libs " $i" fi done dependency_libs=$tmp_libs @@ -6097,7 +7238,7 @@ func_mode_link () # Now set the variables for building old libraries. build_libtool_libs=no oldlibs="$output" - objs="$objs$old_deplibs" + func_append objs "$old_deplibs" ;; lib) @@ -6130,10 +7271,10 @@ func_mode_link () if test "$deplibs_check_method" != pass_all; then func_fatal_error "cannot build libtool library \`$output' from non-libtool objects on this host:$objs" else - $ECHO + echo $ECHO "*** Warning: Linking the shared library $output against the non-libtool" $ECHO "*** objects $objs is not portable!" - libobjs="$libobjs $objs" + func_append libobjs " $objs" fi fi @@ -6192,13 +7333,14 @@ func_mode_link () # which has an extra 1 added just for fun # case $version_type in + # correct linux to gnu/linux during the next big refactor darwin|linux|osf|windows|none) func_arith $number_major + $number_minor current=$func_arith_result age="$number_minor" revision="$number_revision" ;; - freebsd-aout|freebsd-elf|sunos) + freebsd-aout|freebsd-elf|qnx|sunos) current="$number_major" revision="$number_minor" age="0" @@ -6311,7 +7453,7 @@ func_mode_link () versuffix="$major.$revision" ;; - linux) + linux) # correct to gnu/linux during the next big refactor func_arith $current - $age major=.$func_arith_result versuffix="$major.$age.$revision" @@ -6334,7 +7476,7 @@ func_mode_link () done # Make executables depend on our current version. - verstring="$verstring:${current}.0" + func_append verstring ":${current}.0" ;; qnx) @@ -6402,10 +7544,10 @@ func_mode_link () fi func_generate_dlsyms "$libname" "$libname" "yes" - libobjs="$libobjs $symfileobj" + func_append libobjs " $symfileobj" test "X$libobjs" = "X " && libobjs= - if test "$mode" != relink; then + if test "$opt_mode" != relink; then # Remove our outputs, but don't remove object files since they # may have been created when compiling PIC objects. removelist= @@ -6421,7 +7563,7 @@ func_mode_link () continue fi fi - removelist="$removelist $p" + func_append removelist " $p" ;; *) ;; esac @@ -6432,27 +7574,28 @@ func_mode_link () # Now set the variables for building old libraries. if test "$build_old_libs" = yes && test "$build_libtool_libs" != convenience ; then - oldlibs="$oldlibs $output_objdir/$libname.$libext" + func_append oldlibs " $output_objdir/$libname.$libext" # Transform .lo files to .o files. - oldobjs="$objs "`$ECHO "X$libobjs" | $SP2NL | $Xsed -e '/\.'${libext}'$/d' -e "$lo2o" | $NL2SP` + oldobjs="$objs "`$ECHO "$libobjs" | $SP2NL | $SED "/\.${libext}$/d; $lo2o" | $NL2SP` fi # Eliminate all temporary directories. #for path in $notinst_path; do - # lib_search_path=`$ECHO "X$lib_search_path " | $Xsed -e "s% $path % %g"` - # deplibs=`$ECHO "X$deplibs " | $Xsed -e "s% -L$path % %g"` - # dependency_libs=`$ECHO "X$dependency_libs " | $Xsed -e "s% -L$path % %g"` + # lib_search_path=`$ECHO "$lib_search_path " | $SED "s% $path % %g"` + # deplibs=`$ECHO "$deplibs " | $SED "s% -L$path % %g"` + # dependency_libs=`$ECHO "$dependency_libs " | $SED "s% -L$path % %g"` #done if test -n "$xrpath"; then # If the user specified any rpath flags, then add them. temp_xrpath= for libdir in $xrpath; do - temp_xrpath="$temp_xrpath -R$libdir" + func_replace_sysroot "$libdir" + func_append temp_xrpath " -R$func_replace_sysroot_result" case "$finalize_rpath " in *" $libdir "*) ;; - *) finalize_rpath="$finalize_rpath $libdir" ;; + *) func_append finalize_rpath " $libdir" ;; esac done if test "$hardcode_into_libs" != yes || test "$build_old_libs" = yes; then @@ -6466,7 +7609,7 @@ func_mode_link () for lib in $old_dlfiles; do case " $dlprefiles $dlfiles " in *" $lib "*) ;; - *) dlfiles="$dlfiles $lib" ;; + *) func_append dlfiles " $lib" ;; esac done @@ -6476,19 +7619,19 @@ func_mode_link () for lib in $old_dlprefiles; do case "$dlprefiles " in *" $lib "*) ;; - *) dlprefiles="$dlprefiles $lib" ;; + *) func_append dlprefiles " $lib" ;; esac done if test "$build_libtool_libs" = yes; then if test -n "$rpath"; then case $host in - *-*-cygwin* | *-*-mingw* | *-*-pw32* | *-*-os2* | *-*-beos* | *-cegcc*) + *-*-cygwin* | *-*-mingw* | *-*-pw32* | *-*-os2* | *-*-beos* | *-cegcc* | *-*-haiku*) # these systems don't actually have a c library (as such)! ;; *-*-rhapsody* | *-*-darwin1.[012]) # Rhapsody C library is in the System framework - deplibs="$deplibs System.ltframework" + func_append deplibs " System.ltframework" ;; *-*-netbsd*) # Don't link with libc until the a.out ld.so is fixed. @@ -6505,7 +7648,7 @@ func_mode_link () *) # Add libc to deplibs on all other systems if necessary. if test "$build_libtool_need_lc" = "yes"; then - deplibs="$deplibs -lc" + func_append deplibs " -lc" fi ;; esac @@ -6554,7 +7697,7 @@ EOF if test "X$allow_libtool_libs_with_static_runtimes" = "Xyes" ; then case " $predeps $postdeps " in *" $i "*) - newdeplibs="$newdeplibs $i" + func_append newdeplibs " $i" i="" ;; esac @@ -6565,21 +7708,21 @@ EOF set dummy $deplib_matches; shift deplib_match=$1 if test `expr "$ldd_output" : ".*$deplib_match"` -ne 0 ; then - newdeplibs="$newdeplibs $i" + func_append newdeplibs " $i" else droppeddeps=yes - $ECHO + echo $ECHO "*** Warning: dynamic linker does not accept needed library $i." - $ECHO "*** I have the capability to make that library automatically link in when" - $ECHO "*** you link to this library. But I can only do this if you have a" - $ECHO "*** shared version of the library, which I believe you do not have" - $ECHO "*** because a test_compile did reveal that the linker did not use it for" - $ECHO "*** its dynamic dependency list that programs get resolved with at runtime." + echo "*** I have the capability to make that library automatically link in when" + echo "*** you link to this library. But I can only do this if you have a" + echo "*** shared version of the library, which I believe you do not have" + echo "*** because a test_compile did reveal that the linker did not use it for" + echo "*** its dynamic dependency list that programs get resolved with at runtime." fi fi ;; *) - newdeplibs="$newdeplibs $i" + func_append newdeplibs " $i" ;; esac done @@ -6597,7 +7740,7 @@ EOF if test "X$allow_libtool_libs_with_static_runtimes" = "Xyes" ; then case " $predeps $postdeps " in *" $i "*) - newdeplibs="$newdeplibs $i" + func_append newdeplibs " $i" i="" ;; esac @@ -6608,29 +7751,29 @@ EOF set dummy $deplib_matches; shift deplib_match=$1 if test `expr "$ldd_output" : ".*$deplib_match"` -ne 0 ; then - newdeplibs="$newdeplibs $i" + func_append newdeplibs " $i" else droppeddeps=yes - $ECHO + echo $ECHO "*** Warning: dynamic linker does not accept needed library $i." - $ECHO "*** I have the capability to make that library automatically link in when" - $ECHO "*** you link to this library. But I can only do this if you have a" - $ECHO "*** shared version of the library, which you do not appear to have" - $ECHO "*** because a test_compile did reveal that the linker did not use this one" - $ECHO "*** as a dynamic dependency that programs can get resolved with at runtime." + echo "*** I have the capability to make that library automatically link in when" + echo "*** you link to this library. But I can only do this if you have a" + echo "*** shared version of the library, which you do not appear to have" + echo "*** because a test_compile did reveal that the linker did not use this one" + echo "*** as a dynamic dependency that programs can get resolved with at runtime." fi fi else droppeddeps=yes - $ECHO + echo $ECHO "*** Warning! Library $i is needed by this library but I was not able to" - $ECHO "*** make it link in! You will probably need to install it or some" - $ECHO "*** library that it depends on before this library will be fully" - $ECHO "*** functional. Installing it before continuing would be even better." + echo "*** make it link in! You will probably need to install it or some" + echo "*** library that it depends on before this library will be fully" + echo "*** functional. Installing it before continuing would be even better." fi ;; *) - newdeplibs="$newdeplibs $i" + func_append newdeplibs " $i" ;; esac done @@ -6647,15 +7790,27 @@ EOF if test "X$allow_libtool_libs_with_static_runtimes" = "Xyes" ; then case " $predeps $postdeps " in *" $a_deplib "*) - newdeplibs="$newdeplibs $a_deplib" + func_append newdeplibs " $a_deplib" a_deplib="" ;; esac fi if test -n "$a_deplib" ; then libname=`eval "\\$ECHO \"$libname_spec\""` + if test -n "$file_magic_glob"; then + libnameglob=`func_echo_all "$libname" | $SED -e $file_magic_glob` + else + libnameglob=$libname + fi + test "$want_nocaseglob" = yes && nocaseglob=`shopt -p nocaseglob` for i in $lib_search_path $sys_lib_search_path $shlib_search_path; do - potential_libs=`ls $i/$libname[.-]* 2>/dev/null` + if test "$want_nocaseglob" = yes; then + shopt -s nocaseglob + potential_libs=`ls $i/$libnameglob[.-]* 2>/dev/null` + $nocaseglob + else + potential_libs=`ls $i/$libnameglob[.-]* 2>/dev/null` + fi for potent_lib in $potential_libs; do # Follow soft links. if ls -lLd "$potent_lib" 2>/dev/null | @@ -6672,13 +7827,13 @@ EOF potliblink=`ls -ld $potlib | ${SED} 's/.* -> //'` case $potliblink in [\\/]* | [A-Za-z]:[\\/]*) potlib="$potliblink";; - *) potlib=`$ECHO "X$potlib" | $Xsed -e 's,[^/]*$,,'`"$potliblink";; + *) potlib=`$ECHO "$potlib" | $SED 's,[^/]*$,,'`"$potliblink";; esac done if eval $file_magic_cmd \"\$potlib\" 2>/dev/null | $SED -e 10q | $EGREP "$file_magic_regex" > /dev/null; then - newdeplibs="$newdeplibs $a_deplib" + func_append newdeplibs " $a_deplib" a_deplib="" break 2 fi @@ -6687,12 +7842,12 @@ EOF fi if test -n "$a_deplib" ; then droppeddeps=yes - $ECHO + echo $ECHO "*** Warning: linker path does not have real file for library $a_deplib." - $ECHO "*** I have the capability to make that library automatically link in when" - $ECHO "*** you link to this library. But I can only do this if you have a" - $ECHO "*** shared version of the library, which you do not appear to have" - $ECHO "*** because I did check the linker path looking for a file starting" + echo "*** I have the capability to make that library automatically link in when" + echo "*** you link to this library. But I can only do this if you have a" + echo "*** shared version of the library, which you do not appear to have" + echo "*** because I did check the linker path looking for a file starting" if test -z "$potlib" ; then $ECHO "*** with $libname but no candidates were found. (...for file magic test)" else @@ -6703,7 +7858,7 @@ EOF ;; *) # Add a -L argument. - newdeplibs="$newdeplibs $a_deplib" + func_append newdeplibs " $a_deplib" ;; esac done # Gone through all deplibs. @@ -6719,7 +7874,7 @@ EOF if test "X$allow_libtool_libs_with_static_runtimes" = "Xyes" ; then case " $predeps $postdeps " in *" $a_deplib "*) - newdeplibs="$newdeplibs $a_deplib" + func_append newdeplibs " $a_deplib" a_deplib="" ;; esac @@ -6730,9 +7885,9 @@ EOF potential_libs=`ls $i/$libname[.-]* 2>/dev/null` for potent_lib in $potential_libs; do potlib="$potent_lib" # see symlink-check above in file_magic test - if eval "\$ECHO \"X$potent_lib\"" 2>/dev/null | $Xsed -e 10q | \ + if eval "\$ECHO \"$potent_lib\"" 2>/dev/null | $SED 10q | \ $EGREP "$match_pattern_regex" > /dev/null; then - newdeplibs="$newdeplibs $a_deplib" + func_append newdeplibs " $a_deplib" a_deplib="" break 2 fi @@ -6741,12 +7896,12 @@ EOF fi if test -n "$a_deplib" ; then droppeddeps=yes - $ECHO + echo $ECHO "*** Warning: linker path does not have real file for library $a_deplib." - $ECHO "*** I have the capability to make that library automatically link in when" - $ECHO "*** you link to this library. But I can only do this if you have a" - $ECHO "*** shared version of the library, which you do not appear to have" - $ECHO "*** because I did check the linker path looking for a file starting" + echo "*** I have the capability to make that library automatically link in when" + echo "*** you link to this library. But I can only do this if you have a" + echo "*** shared version of the library, which you do not appear to have" + echo "*** because I did check the linker path looking for a file starting" if test -z "$potlib" ; then $ECHO "*** with $libname but no candidates were found. (...for regex pattern test)" else @@ -6757,32 +7912,32 @@ EOF ;; *) # Add a -L argument. - newdeplibs="$newdeplibs $a_deplib" + func_append newdeplibs " $a_deplib" ;; esac done # Gone through all deplibs. ;; none | unknown | *) newdeplibs="" - tmp_deplibs=`$ECHO "X $deplibs" | $Xsed \ - -e 's/ -lc$//' -e 's/ -[LR][^ ]*//g'` + tmp_deplibs=`$ECHO " $deplibs" | $SED 's/ -lc$//; s/ -[LR][^ ]*//g'` if test "X$allow_libtool_libs_with_static_runtimes" = "Xyes" ; then for i in $predeps $postdeps ; do # can't use Xsed below, because $i might contain '/' - tmp_deplibs=`$ECHO "X $tmp_deplibs" | $Xsed -e "s,$i,,"` + tmp_deplibs=`$ECHO " $tmp_deplibs" | $SED "s,$i,,"` done fi - if $ECHO "X $tmp_deplibs" | $Xsed -e 's/[ ]//g' | - $GREP . >/dev/null; then - $ECHO + case $tmp_deplibs in + *[!\ \ ]*) + echo if test "X$deplibs_check_method" = "Xnone"; then - $ECHO "*** Warning: inter-library dependencies are not supported in this platform." + echo "*** Warning: inter-library dependencies are not supported in this platform." else - $ECHO "*** Warning: inter-library dependencies are not known to be supported." + echo "*** Warning: inter-library dependencies are not known to be supported." fi - $ECHO "*** All declared inter-library dependencies are being dropped." + echo "*** All declared inter-library dependencies are being dropped." droppeddeps=yes - fi + ;; + esac ;; esac versuffix=$versuffix_save @@ -6794,23 +7949,23 @@ EOF case $host in *-*-rhapsody* | *-*-darwin1.[012]) # On Rhapsody replace the C library with the System framework - newdeplibs=`$ECHO "X $newdeplibs" | $Xsed -e 's/ -lc / System.ltframework /'` + newdeplibs=`$ECHO " $newdeplibs" | $SED 's/ -lc / System.ltframework /'` ;; esac if test "$droppeddeps" = yes; then if test "$module" = yes; then - $ECHO - $ECHO "*** Warning: libtool could not satisfy all declared inter-library" + echo + echo "*** Warning: libtool could not satisfy all declared inter-library" $ECHO "*** dependencies of module $libname. Therefore, libtool will create" - $ECHO "*** a static module, that should work as long as the dlopening" - $ECHO "*** application is linked with the -dlopen flag." + echo "*** a static module, that should work as long as the dlopening" + echo "*** application is linked with the -dlopen flag." if test -z "$global_symbol_pipe"; then - $ECHO - $ECHO "*** However, this would only work if libtool was able to extract symbol" - $ECHO "*** lists from a program, using \`nm' or equivalent, but libtool could" - $ECHO "*** not find such a program. So, this module is probably useless." - $ECHO "*** \`nm' from GNU binutils and a full rebuild may help." + echo + echo "*** However, this would only work if libtool was able to extract symbol" + echo "*** lists from a program, using \`nm' or equivalent, but libtool could" + echo "*** not find such a program. So, this module is probably useless." + echo "*** \`nm' from GNU binutils and a full rebuild may help." fi if test "$build_old_libs" = no; then oldlibs="$output_objdir/$libname.$libext" @@ -6820,16 +7975,16 @@ EOF build_libtool_libs=no fi else - $ECHO "*** The inter-library dependencies that have been dropped here will be" - $ECHO "*** automatically added whenever a program is linked with this library" - $ECHO "*** or is declared to -dlopen it." + echo "*** The inter-library dependencies that have been dropped here will be" + echo "*** automatically added whenever a program is linked with this library" + echo "*** or is declared to -dlopen it." if test "$allow_undefined" = no; then - $ECHO - $ECHO "*** Since this library must not contain undefined symbols," - $ECHO "*** because either the platform does not support them or" - $ECHO "*** it was explicitly requested with -no-undefined," - $ECHO "*** libtool will only create a static version of it." + echo + echo "*** Since this library must not contain undefined symbols," + echo "*** because either the platform does not support them or" + echo "*** it was explicitly requested with -no-undefined," + echo "*** libtool will only create a static version of it." if test "$build_old_libs" = no; then oldlibs="$output_objdir/$libname.$libext" build_libtool_libs=module @@ -6846,9 +8001,9 @@ EOF # Time to change all our "foo.ltframework" stuff back to "-framework foo" case $host in *-*-darwin*) - newdeplibs=`$ECHO "X $newdeplibs" | $Xsed -e 's% \([^ $]*\).ltframework% -framework \1%g'` - new_inherited_linker_flags=`$ECHO "X $new_inherited_linker_flags" | $Xsed -e 's% \([^ $]*\).ltframework% -framework \1%g'` - deplibs=`$ECHO "X $deplibs" | $Xsed -e 's% \([^ $]*\).ltframework% -framework \1%g'` + newdeplibs=`$ECHO " $newdeplibs" | $SED 's% \([^ $]*\).ltframework% -framework \1%g'` + new_inherited_linker_flags=`$ECHO " $new_inherited_linker_flags" | $SED 's% \([^ $]*\).ltframework% -framework \1%g'` + deplibs=`$ECHO " $deplibs" | $SED 's% \([^ $]*\).ltframework% -framework \1%g'` ;; esac @@ -6861,7 +8016,7 @@ EOF *) case " $deplibs " in *" -L$path/$objdir "*) - new_libs="$new_libs -L$path/$objdir" ;; + func_append new_libs " -L$path/$objdir" ;; esac ;; esac @@ -6871,10 +8026,10 @@ EOF -L*) case " $new_libs " in *" $deplib "*) ;; - *) new_libs="$new_libs $deplib" ;; + *) func_append new_libs " $deplib" ;; esac ;; - *) new_libs="$new_libs $deplib" ;; + *) func_append new_libs " $deplib" ;; esac done deplibs="$new_libs" @@ -6886,15 +8041,22 @@ EOF # Test again, we may have decided not to build it any more if test "$build_libtool_libs" = yes; then + # Remove ${wl} instances when linking with ld. + # FIXME: should test the right _cmds variable. + case $archive_cmds in + *\$LD\ *) wl= ;; + esac if test "$hardcode_into_libs" = yes; then # Hardcode the library paths hardcode_libdirs= dep_rpath= rpath="$finalize_rpath" - test "$mode" != relink && rpath="$compile_rpath$rpath" + test "$opt_mode" != relink && rpath="$compile_rpath$rpath" for libdir in $rpath; do if test -n "$hardcode_libdir_flag_spec"; then if test -n "$hardcode_libdir_separator"; then + func_replace_sysroot "$libdir" + libdir=$func_replace_sysroot_result if test -z "$hardcode_libdirs"; then hardcode_libdirs="$libdir" else @@ -6903,18 +8065,18 @@ EOF *"$hardcode_libdir_separator$libdir$hardcode_libdir_separator"*) ;; *) - hardcode_libdirs="$hardcode_libdirs$hardcode_libdir_separator$libdir" + func_append hardcode_libdirs "$hardcode_libdir_separator$libdir" ;; esac fi else eval flag=\"$hardcode_libdir_flag_spec\" - dep_rpath="$dep_rpath $flag" + func_append dep_rpath " $flag" fi elif test -n "$runpath_var"; then case "$perm_rpath " in *" $libdir "*) ;; - *) perm_rpath="$perm_rpath $libdir" ;; + *) func_append perm_rpath " $libdir" ;; esac fi done @@ -6922,17 +8084,13 @@ EOF if test -n "$hardcode_libdir_separator" && test -n "$hardcode_libdirs"; then libdir="$hardcode_libdirs" - if test -n "$hardcode_libdir_flag_spec_ld"; then - eval dep_rpath=\"$hardcode_libdir_flag_spec_ld\" - else - eval dep_rpath=\"$hardcode_libdir_flag_spec\" - fi + eval "dep_rpath=\"$hardcode_libdir_flag_spec\"" fi if test -n "$runpath_var" && test -n "$perm_rpath"; then # We should set the runpath_var. rpath= for dir in $perm_rpath; do - rpath="$rpath$dir:" + func_append rpath "$dir:" done eval "$runpath_var='$rpath\$$runpath_var'; export $runpath_var" fi @@ -6940,7 +8098,7 @@ EOF fi shlibpath="$finalize_shlibpath" - test "$mode" != relink && shlibpath="$compile_shlibpath$shlibpath" + test "$opt_mode" != relink && shlibpath="$compile_shlibpath$shlibpath" if test -n "$shlibpath"; then eval "$shlibpath_var='$shlibpath\$$shlibpath_var'; export $shlibpath_var" fi @@ -6966,18 +8124,18 @@ EOF linknames= for link do - linknames="$linknames $link" + func_append linknames " $link" done # Use standard objects if they are pic - test -z "$pic_flag" && libobjs=`$ECHO "X$libobjs" | $SP2NL | $Xsed -e "$lo2o" | $NL2SP` + test -z "$pic_flag" && libobjs=`$ECHO "$libobjs" | $SP2NL | $SED "$lo2o" | $NL2SP` test "X$libobjs" = "X " && libobjs= delfiles= if test -n "$export_symbols" && test -n "$include_expsyms"; then $opt_dry_run || cp "$export_symbols" "$output_objdir/$libname.uexp" export_symbols="$output_objdir/$libname.uexp" - delfiles="$delfiles $export_symbols" + func_append delfiles " $export_symbols" fi orig_export_symbols= @@ -7008,13 +8166,45 @@ EOF $opt_dry_run || $RM $export_symbols cmds=$export_symbols_cmds save_ifs="$IFS"; IFS='~' - for cmd in $cmds; do + for cmd1 in $cmds; do IFS="$save_ifs" - eval cmd=\"$cmd\" - func_len " $cmd" - len=$func_len_result - if test "$len" -lt "$max_cmd_len" || test "$max_cmd_len" -le -1; then + # Take the normal branch if the nm_file_list_spec branch + # doesn't work or if tool conversion is not needed. + case $nm_file_list_spec~$to_tool_file_cmd in + *~func_convert_file_noop | *~func_convert_file_msys_to_w32 | ~*) + try_normal_branch=yes + eval cmd=\"$cmd1\" + func_len " $cmd" + len=$func_len_result + ;; + *) + try_normal_branch=no + ;; + esac + if test "$try_normal_branch" = yes \ + && { test "$len" -lt "$max_cmd_len" \ + || test "$max_cmd_len" -le -1; } + then + func_show_eval "$cmd" 'exit $?' + skipped_export=false + elif test -n "$nm_file_list_spec"; then + func_basename "$output" + output_la=$func_basename_result + save_libobjs=$libobjs + save_output=$output + output=${output_objdir}/${output_la}.nm + func_to_tool_file "$output" + libobjs=$nm_file_list_spec$func_to_tool_file_result + func_append delfiles " $output" + func_verbose "creating $NM input file list: $output" + for obj in $save_libobjs; do + func_to_tool_file "$obj" + $ECHO "$func_to_tool_file_result" + done > "$output" + eval cmd=\"$cmd1\" func_show_eval "$cmd" 'exit $?' + output=$save_output + libobjs=$save_libobjs skipped_export=false else # The command line is too long to execute in one step. @@ -7036,7 +8226,7 @@ EOF if test -n "$export_symbols" && test -n "$include_expsyms"; then tmp_export_symbols="$export_symbols" test -n "$orig_export_symbols" && tmp_export_symbols="$orig_export_symbols" - $opt_dry_run || eval '$ECHO "X$include_expsyms" | $Xsed | $SP2NL >> "$tmp_export_symbols"' + $opt_dry_run || eval '$ECHO "$include_expsyms" | $SP2NL >> "$tmp_export_symbols"' fi if test "X$skipped_export" != "X:" && test -n "$orig_export_symbols"; then @@ -7048,7 +8238,7 @@ EOF # global variables. join(1) would be nice here, but unfortunately # isn't a blessed tool. $opt_dry_run || $SED -e '/[ ,]DATA/!d;s,\(.*\)\([ \,].*\),s|^\1$|\1\2|,' < $export_symbols > $output_objdir/$libname.filter - delfiles="$delfiles $export_symbols $output_objdir/$libname.filter" + func_append delfiles " $export_symbols $output_objdir/$libname.filter" export_symbols=$output_objdir/$libname.def $opt_dry_run || $SED -f $output_objdir/$libname.filter < $orig_export_symbols > $export_symbols fi @@ -7058,7 +8248,7 @@ EOF case " $convenience " in *" $test_deplib "*) ;; *) - tmp_deplibs="$tmp_deplibs $test_deplib" + func_append tmp_deplibs " $test_deplib" ;; esac done @@ -7078,21 +8268,21 @@ EOF test "X$libobjs" = "X " && libobjs= else gentop="$output_objdir/${outputname}x" - generated="$generated $gentop" + func_append generated " $gentop" func_extract_archives $gentop $convenience - libobjs="$libobjs $func_extract_archives_result" + func_append libobjs " $func_extract_archives_result" test "X$libobjs" = "X " && libobjs= fi fi if test "$thread_safe" = yes && test -n "$thread_safe_flag_spec"; then eval flag=\"$thread_safe_flag_spec\" - linker_flags="$linker_flags $flag" + func_append linker_flags " $flag" fi # Make a backup of the uninstalled library when relinking - if test "$mode" = relink; then + if test "$opt_mode" = relink; then $opt_dry_run || eval '(cd $output_objdir && $RM ${realname}U && $MV $realname ${realname}U)' || exit $? fi @@ -7137,7 +8327,8 @@ EOF save_libobjs=$libobjs fi save_output=$output - output_la=`$ECHO "X$output" | $Xsed -e "$basename"` + func_basename "$output" + output_la=$func_basename_result # Clear the reloadable object creation command queue and # initialize k to one. @@ -7150,13 +8341,16 @@ EOF if test -n "$save_libobjs" && test "X$skipped_export" != "X:" && test "$with_gnu_ld" = yes; then output=${output_objdir}/${output_la}.lnkscript func_verbose "creating GNU ld script: $output" - $ECHO 'INPUT (' > $output + echo 'INPUT (' > $output for obj in $save_libobjs do - $ECHO "$obj" >> $output + func_to_tool_file "$obj" + $ECHO "$func_to_tool_file_result" >> $output done - $ECHO ')' >> $output - delfiles="$delfiles $output" + echo ')' >> $output + func_append delfiles " $output" + func_to_tool_file "$output" + output=$func_to_tool_file_result elif test -n "$save_libobjs" && test "X$skipped_export" != "X:" && test "X$file_list_spec" != X; then output=${output_objdir}/${output_la}.lnk func_verbose "creating linker input file list: $output" @@ -7170,10 +8364,12 @@ EOF fi for obj do - $ECHO "$obj" >> $output + func_to_tool_file "$obj" + $ECHO "$func_to_tool_file_result" >> $output done - delfiles="$delfiles $output" - output=$firstobj\"$file_list_spec$output\" + func_append delfiles " $output" + func_to_tool_file "$output" + output=$firstobj\"$file_list_spec$func_to_tool_file_result\" else if test -n "$save_libobjs"; then func_verbose "creating reloadable object files..." @@ -7197,17 +8393,19 @@ EOF # command to the queue. if test "$k" -eq 1 ; then # The first file doesn't have a previous command to add. - eval concat_cmds=\"$reload_cmds $objlist $last_robj\" + reload_objs=$objlist + eval concat_cmds=\"$reload_cmds\" else # All subsequent reloadable object files will link in # the last one created. - eval concat_cmds=\"\$concat_cmds~$reload_cmds $objlist $last_robj~\$RM $last_robj\" + reload_objs="$objlist $last_robj" + eval concat_cmds=\"\$concat_cmds~$reload_cmds~\$RM $last_robj\" fi last_robj=$output_objdir/$output_la-${k}.$objext func_arith $k + 1 k=$func_arith_result output=$output_objdir/$output_la-${k}.$objext - objlist=$obj + objlist=" $obj" func_len " $last_robj" func_arith $len0 + $func_len_result len=$func_arith_result @@ -7217,11 +8415,12 @@ EOF # reloadable object file. All subsequent reloadable object # files will link in the last one created. test -z "$concat_cmds" || concat_cmds=$concat_cmds~ - eval concat_cmds=\"\${concat_cmds}$reload_cmds $objlist $last_robj\" + reload_objs="$objlist $last_robj" + eval concat_cmds=\"\${concat_cmds}$reload_cmds\" if test -n "$last_robj"; then eval concat_cmds=\"\${concat_cmds}~\$RM $last_robj\" fi - delfiles="$delfiles $output" + func_append delfiles " $output" else output= @@ -7255,7 +8454,7 @@ EOF lt_exit=$? # Restore the uninstalled library and exit - if test "$mode" = relink; then + if test "$opt_mode" = relink; then ( cd "$output_objdir" && \ $RM "${realname}T" && \ $MV "${realname}U" "$realname" ) @@ -7276,7 +8475,7 @@ EOF if test -n "$export_symbols" && test -n "$include_expsyms"; then tmp_export_symbols="$export_symbols" test -n "$orig_export_symbols" && tmp_export_symbols="$orig_export_symbols" - $opt_dry_run || eval '$ECHO "X$include_expsyms" | $Xsed | $SP2NL >> "$tmp_export_symbols"' + $opt_dry_run || eval '$ECHO "$include_expsyms" | $SP2NL >> "$tmp_export_symbols"' fi if test -n "$orig_export_symbols"; then @@ -7288,7 +8487,7 @@ EOF # global variables. join(1) would be nice here, but unfortunately # isn't a blessed tool. $opt_dry_run || $SED -e '/[ ,]DATA/!d;s,\(.*\)\([ \,].*\),s|^\1$|\1\2|,' < $export_symbols > $output_objdir/$libname.filter - delfiles="$delfiles $export_symbols $output_objdir/$libname.filter" + func_append delfiles " $export_symbols $output_objdir/$libname.filter" export_symbols=$output_objdir/$libname.def $opt_dry_run || $SED -f $output_objdir/$libname.filter < $orig_export_symbols > $export_symbols fi @@ -7329,10 +8528,10 @@ EOF # Add any objects from preloaded convenience libraries if test -n "$dlprefiles"; then gentop="$output_objdir/${outputname}x" - generated="$generated $gentop" + func_append generated " $gentop" func_extract_archives $gentop $dlprefiles - libobjs="$libobjs $func_extract_archives_result" + func_append libobjs " $func_extract_archives_result" test "X$libobjs" = "X " && libobjs= fi @@ -7348,7 +8547,7 @@ EOF lt_exit=$? # Restore the uninstalled library and exit - if test "$mode" = relink; then + if test "$opt_mode" = relink; then ( cd "$output_objdir" && \ $RM "${realname}T" && \ $MV "${realname}U" "$realname" ) @@ -7360,7 +8559,7 @@ EOF IFS="$save_ifs" # Restore the uninstalled library and exit - if test "$mode" = relink; then + if test "$opt_mode" = relink; then $opt_dry_run || eval '(cd $output_objdir && $RM ${realname}T && $MV $realname ${realname}T && $MV ${realname}U $realname)' || exit $? if test -n "$convenience"; then @@ -7441,18 +8640,21 @@ EOF if test -n "$convenience"; then if test -n "$whole_archive_flag_spec"; then eval tmp_whole_archive_flags=\"$whole_archive_flag_spec\" - reload_conv_objs=$reload_objs\ `$ECHO "X$tmp_whole_archive_flags" | $Xsed -e 's|,| |g'` + reload_conv_objs=$reload_objs\ `$ECHO "$tmp_whole_archive_flags" | $SED 's|,| |g'` else gentop="$output_objdir/${obj}x" - generated="$generated $gentop" + func_append generated " $gentop" func_extract_archives $gentop $convenience reload_conv_objs="$reload_objs $func_extract_archives_result" fi fi + # If we're not building shared, we need to use non_pic_objs + test "$build_libtool_libs" != yes && libobjs="$non_pic_objects" + # Create the old-style object. - reload_objs="$objs$old_deplibs "`$ECHO "X$libobjs" | $SP2NL | $Xsed -e '/\.'${libext}$'/d' -e '/\.lib$/d' -e "$lo2o" | $NL2SP`" $reload_conv_objs" ### testsuite: skip nested quoting test + reload_objs="$objs$old_deplibs "`$ECHO "$libobjs" | $SP2NL | $SED "/\.${libext}$/d; /\.lib$/d; $lo2o" | $NL2SP`" $reload_conv_objs" ### testsuite: skip nested quoting test output="$obj" func_execute_cmds "$reload_cmds" 'exit $?' @@ -7512,8 +8714,8 @@ EOF case $host in *-*-rhapsody* | *-*-darwin1.[012]) # On Rhapsody replace the C library is the System framework - compile_deplibs=`$ECHO "X $compile_deplibs" | $Xsed -e 's/ -lc / System.ltframework /'` - finalize_deplibs=`$ECHO "X $finalize_deplibs" | $Xsed -e 's/ -lc / System.ltframework /'` + compile_deplibs=`$ECHO " $compile_deplibs" | $SED 's/ -lc / System.ltframework /'` + finalize_deplibs=`$ECHO " $finalize_deplibs" | $SED 's/ -lc / System.ltframework /'` ;; esac @@ -7524,14 +8726,14 @@ EOF if test "$tagname" = CXX ; then case ${MACOSX_DEPLOYMENT_TARGET-10.0} in 10.[0123]) - compile_command="$compile_command ${wl}-bind_at_load" - finalize_command="$finalize_command ${wl}-bind_at_load" + func_append compile_command " ${wl}-bind_at_load" + func_append finalize_command " ${wl}-bind_at_load" ;; esac fi # Time to change all our "foo.ltframework" stuff back to "-framework foo" - compile_deplibs=`$ECHO "X $compile_deplibs" | $Xsed -e 's% \([^ $]*\).ltframework% -framework \1%g'` - finalize_deplibs=`$ECHO "X $finalize_deplibs" | $Xsed -e 's% \([^ $]*\).ltframework% -framework \1%g'` + compile_deplibs=`$ECHO " $compile_deplibs" | $SED 's% \([^ $]*\).ltframework% -framework \1%g'` + finalize_deplibs=`$ECHO " $finalize_deplibs" | $SED 's% \([^ $]*\).ltframework% -framework \1%g'` ;; esac @@ -7545,7 +8747,7 @@ EOF *) case " $compile_deplibs " in *" -L$path/$objdir "*) - new_libs="$new_libs -L$path/$objdir" ;; + func_append new_libs " -L$path/$objdir" ;; esac ;; esac @@ -7555,17 +8757,17 @@ EOF -L*) case " $new_libs " in *" $deplib "*) ;; - *) new_libs="$new_libs $deplib" ;; + *) func_append new_libs " $deplib" ;; esac ;; - *) new_libs="$new_libs $deplib" ;; + *) func_append new_libs " $deplib" ;; esac done compile_deplibs="$new_libs" - compile_command="$compile_command $compile_deplibs" - finalize_command="$finalize_command $finalize_deplibs" + func_append compile_command " $compile_deplibs" + func_append finalize_command " $finalize_deplibs" if test -n "$rpath$xrpath"; then # If the user specified any rpath flags, then add them. @@ -7573,7 +8775,7 @@ EOF # This is the magic to use -rpath. case "$finalize_rpath " in *" $libdir "*) ;; - *) finalize_rpath="$finalize_rpath $libdir" ;; + *) func_append finalize_rpath " $libdir" ;; esac done fi @@ -7592,18 +8794,18 @@ EOF *"$hardcode_libdir_separator$libdir$hardcode_libdir_separator"*) ;; *) - hardcode_libdirs="$hardcode_libdirs$hardcode_libdir_separator$libdir" + func_append hardcode_libdirs "$hardcode_libdir_separator$libdir" ;; esac fi else eval flag=\"$hardcode_libdir_flag_spec\" - rpath="$rpath $flag" + func_append rpath " $flag" fi elif test -n "$runpath_var"; then case "$perm_rpath " in *" $libdir "*) ;; - *) perm_rpath="$perm_rpath $libdir" ;; + *) func_append perm_rpath " $libdir" ;; esac fi case $host in @@ -7612,12 +8814,12 @@ EOF case :$dllsearchpath: in *":$libdir:"*) ;; ::) dllsearchpath=$libdir;; - *) dllsearchpath="$dllsearchpath:$libdir";; + *) func_append dllsearchpath ":$libdir";; esac case :$dllsearchpath: in *":$testbindir:"*) ;; ::) dllsearchpath=$testbindir;; - *) dllsearchpath="$dllsearchpath:$testbindir";; + *) func_append dllsearchpath ":$testbindir";; esac ;; esac @@ -7643,18 +8845,18 @@ EOF *"$hardcode_libdir_separator$libdir$hardcode_libdir_separator"*) ;; *) - hardcode_libdirs="$hardcode_libdirs$hardcode_libdir_separator$libdir" + func_append hardcode_libdirs "$hardcode_libdir_separator$libdir" ;; esac fi else eval flag=\"$hardcode_libdir_flag_spec\" - rpath="$rpath $flag" + func_append rpath " $flag" fi elif test -n "$runpath_var"; then case "$finalize_perm_rpath " in *" $libdir "*) ;; - *) finalize_perm_rpath="$finalize_perm_rpath $libdir" ;; + *) func_append finalize_perm_rpath " $libdir" ;; esac fi done @@ -7668,8 +8870,8 @@ EOF if test -n "$libobjs" && test "$build_old_libs" = yes; then # Transform all the library objects into standard objects. - compile_command=`$ECHO "X$compile_command" | $SP2NL | $Xsed -e "$lo2o" | $NL2SP` - finalize_command=`$ECHO "X$finalize_command" | $SP2NL | $Xsed -e "$lo2o" | $NL2SP` + compile_command=`$ECHO "$compile_command" | $SP2NL | $SED "$lo2o" | $NL2SP` + finalize_command=`$ECHO "$finalize_command" | $SP2NL | $SED "$lo2o" | $NL2SP` fi func_generate_dlsyms "$outputname" "@PROGRAM@" "no" @@ -7681,15 +8883,15 @@ EOF wrappers_required=yes case $host in + *cegcc* | *mingw32ce*) + # Disable wrappers for cegcc and mingw32ce hosts, we are cross compiling anyway. + wrappers_required=no + ;; *cygwin* | *mingw* ) if test "$build_libtool_libs" != yes; then wrappers_required=no fi ;; - *cegcc) - # Disable wrappers for cegcc, we are cross compiling anyway. - wrappers_required=no - ;; *) if test "$need_relink" = no || test "$build_libtool_libs" != yes; then wrappers_required=no @@ -7698,13 +8900,19 @@ EOF esac if test "$wrappers_required" = no; then # Replace the output file specification. - compile_command=`$ECHO "X$compile_command" | $Xsed -e 's%@OUTPUT@%'"$output"'%g'` + compile_command=`$ECHO "$compile_command" | $SED 's%@OUTPUT@%'"$output"'%g'` link_command="$compile_command$compile_rpath" # We have no uninstalled library dependencies, so finalize right now. exit_status=0 func_show_eval "$link_command" 'exit_status=$?' + if test -n "$postlink_cmds"; then + func_to_tool_file "$output" + postlink_cmds=`func_echo_all "$postlink_cmds" | $SED -e 's%@OUTPUT@%'"$output"'%g' -e 's%@TOOL_OUTPUT@%'"$func_to_tool_file_result"'%g'` + func_execute_cmds "$postlink_cmds" 'exit $?' + fi + # Delete the generated files. if test -f "$output_objdir/${outputname}S.${objext}"; then func_show_eval '$RM "$output_objdir/${outputname}S.${objext}"' @@ -7727,7 +8935,7 @@ EOF # We should set the runpath_var. rpath= for dir in $perm_rpath; do - rpath="$rpath$dir:" + func_append rpath "$dir:" done compile_var="$runpath_var=\"$rpath\$$runpath_var\" " fi @@ -7735,7 +8943,7 @@ EOF # We should set the runpath_var. rpath= for dir in $finalize_perm_rpath; do - rpath="$rpath$dir:" + func_append rpath "$dir:" done finalize_var="$runpath_var=\"$rpath\$$runpath_var\" " fi @@ -7745,11 +8953,18 @@ EOF # We don't need to create a wrapper script. link_command="$compile_var$compile_command$compile_rpath" # Replace the output file specification. - link_command=`$ECHO "X$link_command" | $Xsed -e 's%@OUTPUT@%'"$output"'%g'` + link_command=`$ECHO "$link_command" | $SED 's%@OUTPUT@%'"$output"'%g'` # Delete the old output file. $opt_dry_run || $RM $output # Link the executable and exit func_show_eval "$link_command" 'exit $?' + + if test -n "$postlink_cmds"; then + func_to_tool_file "$output" + postlink_cmds=`func_echo_all "$postlink_cmds" | $SED -e 's%@OUTPUT@%'"$output"'%g' -e 's%@TOOL_OUTPUT@%'"$func_to_tool_file_result"'%g'` + func_execute_cmds "$postlink_cmds" 'exit $?' + fi + exit $EXIT_SUCCESS fi @@ -7764,7 +8979,7 @@ EOF if test "$fast_install" != no; then link_command="$finalize_var$compile_command$finalize_rpath" if test "$fast_install" = yes; then - relink_command=`$ECHO "X$compile_var$compile_command$compile_rpath" | $Xsed -e 's%@OUTPUT@%\$progdir/\$file%g'` + relink_command=`$ECHO "$compile_var$compile_command$compile_rpath" | $SED 's%@OUTPUT@%\$progdir/\$file%g'` else # fast_install is set to needless relink_command= @@ -7776,13 +8991,19 @@ EOF fi # Replace the output file specification. - link_command=`$ECHO "X$link_command" | $Xsed -e 's%@OUTPUT@%'"$output_objdir/$outputname"'%g'` + link_command=`$ECHO "$link_command" | $SED 's%@OUTPUT@%'"$output_objdir/$outputname"'%g'` # Delete the old output files. $opt_dry_run || $RM $output $output_objdir/$outputname $output_objdir/lt-$outputname func_show_eval "$link_command" 'exit $?' + if test -n "$postlink_cmds"; then + func_to_tool_file "$output_objdir/$outputname" + postlink_cmds=`func_echo_all "$postlink_cmds" | $SED -e 's%@OUTPUT@%'"$output_objdir/$outputname"'%g' -e 's%@TOOL_OUTPUT@%'"$func_to_tool_file_result"'%g'` + func_execute_cmds "$postlink_cmds" 'exit $?' + fi + # Now create the wrapper script. func_verbose "creating $output" @@ -7800,18 +9021,7 @@ EOF fi done relink_command="(cd `pwd`; $relink_command)" - relink_command=`$ECHO "X$relink_command" | $Xsed -e "$sed_quote_subst"` - fi - - # Quote $ECHO for shipping. - if test "X$ECHO" = "X$SHELL $progpath --fallback-echo"; then - case $progpath in - [\\/]* | [A-Za-z]:[\\/]*) qecho="$SHELL $progpath --fallback-echo";; - *) qecho="$SHELL `pwd`/$progpath --fallback-echo";; - esac - qecho=`$ECHO "X$qecho" | $Xsed -e "$sed_quote_subst"` - else - qecho=`$ECHO "X$ECHO" | $Xsed -e "$sed_quote_subst"` + relink_command=`$ECHO "$relink_command" | $SED "$sed_quote_subst"` fi # Only actually do things if not in dry run mode. @@ -7891,7 +9101,7 @@ EOF else oldobjs="$old_deplibs $non_pic_objects" if test "$preload" = yes && test -f "$symfileobj"; then - oldobjs="$oldobjs $symfileobj" + func_append oldobjs " $symfileobj" fi fi addlibs="$old_convenience" @@ -7899,10 +9109,10 @@ EOF if test -n "$addlibs"; then gentop="$output_objdir/${outputname}x" - generated="$generated $gentop" + func_append generated " $gentop" func_extract_archives $gentop $addlibs - oldobjs="$oldobjs $func_extract_archives_result" + func_append oldobjs " $func_extract_archives_result" fi # Do each command in the archive commands. @@ -7913,10 +9123,10 @@ EOF # Add any objects from preloaded convenience libraries if test -n "$dlprefiles"; then gentop="$output_objdir/${outputname}x" - generated="$generated $gentop" + func_append generated " $gentop" func_extract_archives $gentop $dlprefiles - oldobjs="$oldobjs $func_extract_archives_result" + func_append oldobjs " $func_extract_archives_result" fi # POSIX demands no paths to be encoded in archives. We have @@ -7932,9 +9142,9 @@ EOF done | sort | sort -uc >/dev/null 2>&1); then : else - $ECHO "copying selected object files to avoid basename conflicts..." + echo "copying selected object files to avoid basename conflicts..." gentop="$output_objdir/${outputname}x" - generated="$generated $gentop" + func_append generated " $gentop" func_mkdir_p "$gentop" save_oldobjs=$oldobjs oldobjs= @@ -7958,18 +9168,30 @@ EOF esac done func_show_eval "ln $obj $gentop/$newobj || cp $obj $gentop/$newobj" - oldobjs="$oldobjs $gentop/$newobj" + func_append oldobjs " $gentop/$newobj" ;; - *) oldobjs="$oldobjs $obj" ;; + *) func_append oldobjs " $obj" ;; esac done fi + func_to_tool_file "$oldlib" func_convert_file_msys_to_w32 + tool_oldlib=$func_to_tool_file_result eval cmds=\"$old_archive_cmds\" func_len " $cmds" len=$func_len_result if test "$len" -lt "$max_cmd_len" || test "$max_cmd_len" -le -1; then cmds=$old_archive_cmds + elif test -n "$archiver_list_spec"; then + func_verbose "using command file archive linking..." + for obj in $oldobjs + do + func_to_tool_file "$obj" + $ECHO "$func_to_tool_file_result" + done > $output_objdir/$libname.libcmd + func_to_tool_file "$output_objdir/$libname.libcmd" + oldobjs=" $archiver_list_spec$func_to_tool_file_result" + cmds=$old_archive_cmds else # the command line is too long to link in one step, link in parts func_verbose "using piecewise archive linking..." @@ -8043,7 +9265,7 @@ EOF done # Quote the link command for shipping. relink_command="(cd `pwd`; $SHELL $progpath $preserve_args --mode=relink $libtool_args @inst_prefix_dir@)" - relink_command=`$ECHO "X$relink_command" | $Xsed -e "$sed_quote_subst"` + relink_command=`$ECHO "$relink_command" | $SED "$sed_quote_subst"` if test "$hardcode_automatic" = yes ; then relink_command= fi @@ -8063,12 +9285,23 @@ EOF *.la) func_basename "$deplib" name="$func_basename_result" - eval libdir=`${SED} -n -e 's/^libdir=\(.*\)$/\1/p' $deplib` + func_resolve_sysroot "$deplib" + eval libdir=`${SED} -n -e 's/^libdir=\(.*\)$/\1/p' $func_resolve_sysroot_result` test -z "$libdir" && \ func_fatal_error "\`$deplib' is not a valid libtool archive" - newdependency_libs="$newdependency_libs $libdir/$name" + func_append newdependency_libs " ${lt_sysroot:+=}$libdir/$name" + ;; + -L*) + func_stripname -L '' "$deplib" + func_replace_sysroot "$func_stripname_result" + func_append newdependency_libs " -L$func_replace_sysroot_result" ;; - *) newdependency_libs="$newdependency_libs $deplib" ;; + -R*) + func_stripname -R '' "$deplib" + func_replace_sysroot "$func_stripname_result" + func_append newdependency_libs " -R$func_replace_sysroot_result" + ;; + *) func_append newdependency_libs " $deplib" ;; esac done dependency_libs="$newdependency_libs" @@ -8082,9 +9315,9 @@ EOF eval libdir=`${SED} -n -e 's/^libdir=\(.*\)$/\1/p' $lib` test -z "$libdir" && \ func_fatal_error "\`$lib' is not a valid libtool archive" - newdlfiles="$newdlfiles $libdir/$name" + func_append newdlfiles " ${lt_sysroot:+=}$libdir/$name" ;; - *) newdlfiles="$newdlfiles $lib" ;; + *) func_append newdlfiles " $lib" ;; esac done dlfiles="$newdlfiles" @@ -8101,7 +9334,7 @@ EOF eval libdir=`${SED} -n -e 's/^libdir=\(.*\)$/\1/p' $lib` test -z "$libdir" && \ func_fatal_error "\`$lib' is not a valid libtool archive" - newdlprefiles="$newdlprefiles $libdir/$name" + func_append newdlprefiles " ${lt_sysroot:+=}$libdir/$name" ;; esac done @@ -8113,7 +9346,7 @@ EOF [\\/]* | [A-Za-z]:[\\/]*) abs="$lib" ;; *) abs=`pwd`"/$lib" ;; esac - newdlfiles="$newdlfiles $abs" + func_append newdlfiles " $abs" done dlfiles="$newdlfiles" newdlprefiles= @@ -8122,15 +9355,33 @@ EOF [\\/]* | [A-Za-z]:[\\/]*) abs="$lib" ;; *) abs=`pwd`"/$lib" ;; esac - newdlprefiles="$newdlprefiles $abs" + func_append newdlprefiles " $abs" done dlprefiles="$newdlprefiles" fi $RM $output # place dlname in correct position for cygwin + # In fact, it would be nice if we could use this code for all target + # systems that can't hard-code library paths into their executables + # and that have no shared library path variable independent of PATH, + # but it turns out we can't easily determine that from inspecting + # libtool variables, so we have to hard-code the OSs to which it + # applies here; at the moment, that means platforms that use the PE + # object format with DLL files. See the long comment at the top of + # tests/bindir.at for full details. tdlname=$dlname case $host,$output,$installed,$module,$dlname in - *cygwin*,*lai,yes,no,*.dll | *mingw*,*lai,yes,no,*.dll | *cegcc*,*lai,yes,no,*.dll) tdlname=../bin/$dlname ;; + *cygwin*,*lai,yes,no,*.dll | *mingw*,*lai,yes,no,*.dll | *cegcc*,*lai,yes,no,*.dll) + # If a -bindir argument was supplied, place the dll there. + if test "x$bindir" != x ; + then + func_relative_path "$install_libdir" "$bindir" + tdlname=$func_relative_path_result$dlname + else + # Otherwise fall back on heuristic. + tdlname=../bin/$dlname + fi + ;; esac $ECHO > $output "\ # $outputname - a libtool library file @@ -8189,7 +9440,7 @@ relink_command=\"$relink_command\"" exit $EXIT_SUCCESS } -{ test "$mode" = link || test "$mode" = relink; } && +{ test "$opt_mode" = link || test "$opt_mode" = relink; } && func_mode_link ${1+"$@"} @@ -8209,9 +9460,9 @@ func_mode_uninstall () for arg do case $arg in - -f) RM="$RM $arg"; rmforce=yes ;; - -*) RM="$RM $arg" ;; - *) files="$files $arg" ;; + -f) func_append RM " $arg"; rmforce=yes ;; + -*) func_append RM " $arg" ;; + *) func_append files " $arg" ;; esac done @@ -8220,24 +9471,23 @@ func_mode_uninstall () rmdirs= - origobjdir="$objdir" for file in $files; do func_dirname "$file" "" "." dir="$func_dirname_result" if test "X$dir" = X.; then - objdir="$origobjdir" + odir="$objdir" else - objdir="$dir/$origobjdir" + odir="$dir/$objdir" fi func_basename "$file" name="$func_basename_result" - test "$mode" = uninstall && objdir="$dir" + test "$opt_mode" = uninstall && odir="$dir" - # Remember objdir for removal later, being careful to avoid duplicates - if test "$mode" = clean; then + # Remember odir for removal later, being careful to avoid duplicates + if test "$opt_mode" = clean; then case " $rmdirs " in - *" $objdir "*) ;; - *) rmdirs="$rmdirs $objdir" ;; + *" $odir "*) ;; + *) func_append rmdirs " $odir" ;; esac fi @@ -8263,18 +9513,17 @@ func_mode_uninstall () # Delete the libtool libraries and symlinks. for n in $library_names; do - rmfiles="$rmfiles $objdir/$n" + func_append rmfiles " $odir/$n" done - test -n "$old_library" && rmfiles="$rmfiles $objdir/$old_library" + test -n "$old_library" && func_append rmfiles " $odir/$old_library" - case "$mode" in + case "$opt_mode" in clean) - case " $library_names " in - # " " in the beginning catches empty $dlname + case " $library_names " in *" $dlname "*) ;; - *) rmfiles="$rmfiles $objdir/$dlname" ;; + *) test -n "$dlname" && func_append rmfiles " $odir/$dlname" ;; esac - test -n "$libdir" && rmfiles="$rmfiles $objdir/$name $objdir/${name}i" + test -n "$libdir" && func_append rmfiles " $odir/$name $odir/${name}i" ;; uninstall) if test -n "$library_names"; then @@ -8302,19 +9551,19 @@ func_mode_uninstall () # Add PIC object to the list of files to remove. if test -n "$pic_object" && test "$pic_object" != none; then - rmfiles="$rmfiles $dir/$pic_object" + func_append rmfiles " $dir/$pic_object" fi # Add non-PIC object to the list of files to remove. if test -n "$non_pic_object" && test "$non_pic_object" != none; then - rmfiles="$rmfiles $dir/$non_pic_object" + func_append rmfiles " $dir/$non_pic_object" fi fi ;; *) - if test "$mode" = clean ; then + if test "$opt_mode" = clean ; then noexename=$name case $file in *.exe) @@ -8324,7 +9573,7 @@ func_mode_uninstall () noexename=$func_stripname_result # $file with .exe has already been added to rmfiles, # add $file without .exe - rmfiles="$rmfiles $file" + func_append rmfiles " $file" ;; esac # Do a test to see if this is a libtool program. @@ -8333,7 +9582,7 @@ func_mode_uninstall () func_ltwrapper_scriptname "$file" relink_command= func_source $func_ltwrapper_scriptname_result - rmfiles="$rmfiles $func_ltwrapper_scriptname_result" + func_append rmfiles " $func_ltwrapper_scriptname_result" else relink_command= func_source $dir/$noexename @@ -8341,12 +9590,12 @@ func_mode_uninstall () # note $name still contains .exe if it was in $file originally # as does the version of $file that was added into $rmfiles - rmfiles="$rmfiles $objdir/$name $objdir/${name}S.${objext}" + func_append rmfiles " $odir/$name $odir/${name}S.${objext}" if test "$fast_install" = yes && test -n "$relink_command"; then - rmfiles="$rmfiles $objdir/lt-$name" + func_append rmfiles " $odir/lt-$name" fi if test "X$noexename" != "X$name" ; then - rmfiles="$rmfiles $objdir/lt-${noexename}.c" + func_append rmfiles " $odir/lt-${noexename}.c" fi fi fi @@ -8354,7 +9603,6 @@ func_mode_uninstall () esac func_show_eval "$RM $rmfiles" 'exit_status=1' done - objdir="$origobjdir" # Try to remove the ${objdir}s in the directories where we deleted files for dir in $rmdirs; do @@ -8366,16 +9614,16 @@ func_mode_uninstall () exit $exit_status } -{ test "$mode" = uninstall || test "$mode" = clean; } && +{ test "$opt_mode" = uninstall || test "$opt_mode" = clean; } && func_mode_uninstall ${1+"$@"} -test -z "$mode" && { +test -z "$opt_mode" && { help="$generic_help" func_fatal_help "you must specify a MODE" } test -z "$exec_cmd" && \ - func_fatal_help "invalid operation mode \`$mode'" + func_fatal_help "invalid operation mode \`$opt_mode'" if test -n "$exec_cmd"; then eval exec "$exec_cmd" diff --git a/m4/Makefile.in b/m4/Makefile.in index cda2c71..3427ea5 100644 --- a/m4/Makefile.in +++ b/m4/Makefile.in @@ -1,9 +1,9 @@ -# Makefile.in generated by automake 1.11.1 from Makefile.am. +# Makefile.in generated by automake 1.11.6 from Makefile.am. # @configure_input@ # Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, -# 2003, 2004, 2005, 2006, 2007, 2008, 2009 Free Software Foundation, -# Inc. +# 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Free Software +# Foundation, Inc. # This Makefile.in is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. @@ -15,6 +15,23 @@ @SET_MAKE@ VPATH = @srcdir@ +am__make_dryrun = \ + { \ + am__dry=no; \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + echo 'am--echo: ; @echo "AM" OK' | $(MAKE) -f - 2>/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } pkgdatadir = $(datadir)/@PACKAGE@ pkgincludedir = $(includedir)/@PACKAGE@ pkglibdir = $(libdir)/@PACKAGE@ @@ -39,14 +56,15 @@ DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in ChangeLog ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 am__aclocal_m4_deps = $(top_srcdir)/m4/absolute-header.m4 \ $(top_srcdir)/m4/align.m4 $(top_srcdir)/m4/argz.m4 \ - $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/iconv.m4 \ - $(top_srcdir)/m4/lib-ld.m4 $(top_srcdir)/m4/lib-link.m4 \ - $(top_srcdir)/m4/lib-prefix.m4 $(top_srcdir)/m4/libcurl.m4 \ - $(top_srcdir)/m4/libgcrypt.m4 $(top_srcdir)/m4/libtool.m4 \ - $(top_srcdir)/m4/libunistring.m4 $(top_srcdir)/m4/ltdl.m4 \ - $(top_srcdir)/m4/ltoptions.m4 $(top_srcdir)/m4/ltsugar.m4 \ - $(top_srcdir)/m4/ltversion.m4 $(top_srcdir)/m4/lt~obsolete.m4 \ - $(top_srcdir)/m4/nls.m4 $(top_srcdir)/m4/po.m4 \ + $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/glib-2.0.m4 \ + $(top_srcdir)/m4/iconv.m4 $(top_srcdir)/m4/lib-ld.m4 \ + $(top_srcdir)/m4/lib-link.m4 $(top_srcdir)/m4/lib-prefix.m4 \ + $(top_srcdir)/m4/libcurl.m4 $(top_srcdir)/m4/libgcrypt.m4 \ + $(top_srcdir)/m4/libtool.m4 $(top_srcdir)/m4/libunistring.m4 \ + $(top_srcdir)/m4/ltdl.m4 $(top_srcdir)/m4/ltoptions.m4 \ + $(top_srcdir)/m4/ltsugar.m4 $(top_srcdir)/m4/ltversion.m4 \ + $(top_srcdir)/m4/lt~obsolete.m4 $(top_srcdir)/m4/nls.m4 \ + $(top_srcdir)/m4/pkg.m4 $(top_srcdir)/m4/po.m4 \ $(top_srcdir)/m4/progtest.m4 $(top_srcdir)/acinclude.m4 \ $(top_srcdir)/configure.ac am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ @@ -55,14 +73,19 @@ mkinstalldirs = $(install_sh) -d CONFIG_HEADER = $(top_builddir)/gnunet_config.h CONFIG_CLEAN_FILES = CONFIG_CLEAN_VPATH_FILES = -AM_V_GEN = $(am__v_GEN_$(V)) -am__v_GEN_ = $(am__v_GEN_$(AM_DEFAULT_VERBOSITY)) +AM_V_GEN = $(am__v_GEN_@AM_V@) +am__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@) am__v_GEN_0 = @echo " GEN " $@; -AM_V_at = $(am__v_at_$(V)) -am__v_at_ = $(am__v_at_$(AM_DEFAULT_VERBOSITY)) +AM_V_at = $(am__v_at_@AM_V@) +am__v_at_ = $(am__v_at_@AM_DEFAULT_V@) am__v_at_0 = @ SOURCES = DIST_SOURCES = +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac DISTFILES = $(DIST_COMMON) $(DIST_SOURCES) $(TEXINFOS) $(EXTRA_DIST) ACLOCAL = @ACLOCAL@ AMTAR = @AMTAR@ @@ -99,6 +122,10 @@ EXEEXT = @EXEEXT@ EXT_LIBS = @EXT_LIBS@ EXT_LIB_PATH = @EXT_LIB_PATH@ FGREP = @FGREP@ +GLIB_CFLAGS = @GLIB_CFLAGS@ +GLIB_GENMARSHAL = @GLIB_GENMARSHAL@ +GLIB_LIBS = @GLIB_LIBS@ +GLIB_MKENUMS = @GLIB_MKENUMS@ GMSGFMT = @GMSGFMT@ GMSGFMT_015 = @GMSGFMT_015@ GNUNETDNS_GROUP = @GNUNETDNS_GROUP@ @@ -109,6 +136,7 @@ GN_LIBINTL = @GN_LIBINTL@ GN_LIB_LDFLAGS = @GN_LIB_LDFLAGS@ GN_PLUGIN_LDFLAGS = @GN_PLUGIN_LDFLAGS@ GN_USER_HOME_DIR = @GN_USER_HOME_DIR@ +GOBJECT_QUERY = @GOBJECT_QUERY@ GREP = @GREP@ HAVE_LIBUNISTRING = @HAVE_LIBUNISTRING@ INCLTDL = @INCLTDL@ @@ -131,6 +159,8 @@ LIBCURL_CPPFLAGS = @LIBCURL_CPPFLAGS@ LIBGCRYPT_CFLAGS = @LIBGCRYPT_CFLAGS@ LIBGCRYPT_CONFIG = @LIBGCRYPT_CONFIG@ LIBGCRYPT_LIBS = @LIBGCRYPT_LIBS@ +LIBGTOP_CFLAGS = @LIBGTOP_CFLAGS@ +LIBGTOP_LIBS = @LIBGTOP_LIBS@ LIBICONV = @LIBICONV@ LIBINTL = @LIBINTL@ LIBLTDL = @LIBLTDL@ @@ -152,6 +182,7 @@ LT_CONFIG_H = @LT_CONFIG_H@ LT_DLLOADERS = @LT_DLLOADERS@ LT_DLPREOPEN = @LT_DLPREOPEN@ MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ MKDIR_P = @MKDIR_P@ MONKEYPREFIX = @MONKEYPREFIX@ MSGFMT = @MSGFMT@ @@ -161,6 +192,7 @@ MYSQL_CPPFLAGS = @MYSQL_CPPFLAGS@ MYSQL_LDFLAGS = @MYSQL_LDFLAGS@ NM = @NM@ NMEDIT = @NMEDIT@ +NSS_DIR = @NSS_DIR@ OBJC = @OBJC@ OBJCDEPMODE = @OBJCDEPMODE@ OBJCFLAGS = @OBJCFLAGS@ @@ -176,6 +208,7 @@ PACKAGE_TARNAME = @PACKAGE_TARNAME@ PACKAGE_URL = @PACKAGE_URL@ PACKAGE_VERSION = @PACKAGE_VERSION@ PATH_SEPARATOR = @PATH_SEPARATOR@ +PKG_CONFIG = @PKG_CONFIG@ POSTGRES_CPPFLAGS = @POSTGRES_CPPFLAGS@ POSTGRES_LDFLAGS = @POSTGRES_LDFLAGS@ POSUB = @POSUB@ @@ -207,6 +240,7 @@ abs_builddir = @abs_builddir@ abs_srcdir = @abs_srcdir@ abs_top_builddir = @abs_top_builddir@ abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ ac_ct_CC = @ac_ct_CC@ ac_ct_CXX = @ac_ct_CXX@ ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ @@ -229,6 +263,7 @@ datarootdir = @datarootdir@ docdir = @docdir@ dvidir = @dvidir@ exec_prefix = @exec_prefix@ +gitcommand = @gitcommand@ host = @host@ host_alias = @host_alias@ host_cpu = @host_cpu@ @@ -242,7 +277,6 @@ libdir = @libdir@ libexecdir = @libexecdir@ localedir = @localedir@ localstatedir = @localstatedir@ -lt_ECHO = @lt_ECHO@ ltdl_LIBOBJS = @ltdl_LIBOBJS@ ltdl_LTLIBOBJS = @ltdl_LTLIBOBJS@ mandir = @mandir@ @@ -260,6 +294,7 @@ sbindir = @sbindir@ sharedstatedir = @sharedstatedir@ srcdir = @srcdir@ subdirs = @subdirs@ +svnversioncommand = @svnversioncommand@ sys_symbol_underscore = @sys_symbol_underscore@ sysconfdir = @sysconfdir@ target = @target@ @@ -400,10 +435,15 @@ install-am: all-am installcheck: installcheck-am install-strip: - $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ - install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ - `test -z '$(STRIP)' || \ - echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi mostlyclean-generic: clean-generic: diff --git a/m4/argz.m4 b/m4/argz.m4 index 37c1b11..d1f4ec5 100644 --- a/m4/argz.m4 +++ b/m4/argz.m4 @@ -66,7 +66,7 @@ AS_IF([test -z "$ARGZ_H"], ;; #( *) lt_cv_sys_argz_works=yes ;; esac]]) - AS_IF([test $lt_cv_sys_argz_works = yes], + AS_IF([test "$lt_cv_sys_argz_works" = yes], [AC_DEFINE([HAVE_WORKING_ARGZ], 1, [This value is set to 1 to indicate that the system argz facility works])], [ARGZ_H=argz.h diff --git a/m4/libtool.m4 b/m4/libtool.m4 index a3fee53..534d1cc 100644 --- a/m4/libtool.m4 +++ b/m4/libtool.m4 @@ -1,7 +1,8 @@ # libtool.m4 - Configure libtool for the host system. -*-Autoconf-*- # # Copyright (C) 1996, 1997, 1998, 1999, 2000, 2001, 2003, 2004, 2005, -# 2006, 2007, 2008 Free Software Foundation, Inc. +# 2006, 2007, 2008, 2009, 2010, 2011 Free Software +# Foundation, Inc. # Written by Gordon Matzigkeit, 1996 # # This file is free software; the Free Software Foundation gives @@ -10,7 +11,8 @@ m4_define([_LT_COPYING], [dnl # Copyright (C) 1996, 1997, 1998, 1999, 2000, 2001, 2003, 2004, 2005, -# 2006, 2007, 2008 Free Software Foundation, Inc. +# 2006, 2007, 2008, 2009, 2010, 2011 Free Software +# Foundation, Inc. # Written by Gordon Matzigkeit, 1996 # # This file is part of GNU Libtool. @@ -37,7 +39,7 @@ m4_define([_LT_COPYING], [dnl # 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. ]) -# serial 56 LT_INIT +# serial 57 LT_INIT # LT_PREREQ(VERSION) @@ -66,6 +68,7 @@ esac # ------------------ AC_DEFUN([LT_INIT], [AC_PREREQ([2.58])dnl We use AC_INCLUDES_DEFAULT +AC_REQUIRE([AC_CONFIG_AUX_DIR_DEFAULT])dnl AC_BEFORE([$0], [LT_LANG])dnl AC_BEFORE([$0], [LT_OUTPUT])dnl AC_BEFORE([$0], [LTDL_INIT])dnl @@ -82,6 +85,8 @@ AC_REQUIRE([LTVERSION_VERSION])dnl AC_REQUIRE([LTOBSOLETE_VERSION])dnl m4_require([_LT_PROG_LTMAIN])dnl +_LT_SHELL_INIT([SHELL=${CONFIG_SHELL-/bin/sh}]) + dnl Parse OPTIONS _LT_SET_OPTIONS([$0], [$1]) @@ -118,7 +123,7 @@ m4_defun([_LT_CC_BASENAME], *) break;; esac done -cc_basename=`$ECHO "X$cc_temp" | $Xsed -e 's%.*/%%' -e "s%^$host_alias-%%"` +cc_basename=`$ECHO "$cc_temp" | $SED "s%.*/%%; s%^$host_alias-%%"` ]) @@ -138,6 +143,11 @@ m4_defun([_LT_FILEUTILS_DEFAULTS], m4_defun([_LT_SETUP], [AC_REQUIRE([AC_CANONICAL_HOST])dnl AC_REQUIRE([AC_CANONICAL_BUILD])dnl +AC_REQUIRE([_LT_PREPARE_SED_QUOTE_VARS])dnl +AC_REQUIRE([_LT_PROG_ECHO_BACKSLASH])dnl + +_LT_DECL([], [PATH_SEPARATOR], [1], [The PATH separator for the build system])dnl +dnl _LT_DECL([], [host_alias], [0], [The host system])dnl _LT_DECL([], [host], [0])dnl _LT_DECL([], [host_os], [0])dnl @@ -160,10 +170,13 @@ _LT_DECL([], [exeext], [0], [Executable file suffix (normally "")])dnl dnl m4_require([_LT_FILEUTILS_DEFAULTS])dnl m4_require([_LT_CHECK_SHELL_FEATURES])dnl +m4_require([_LT_PATH_CONVERSION_FUNCTIONS])dnl m4_require([_LT_CMD_RELOAD])dnl m4_require([_LT_CHECK_MAGIC_METHOD])dnl +m4_require([_LT_CHECK_SHAREDLIB_FROM_LINKLIB])dnl m4_require([_LT_CMD_OLD_ARCHIVE])dnl m4_require([_LT_CMD_GLOBAL_SYMBOLS])dnl +m4_require([_LT_WITH_SYSROOT])dnl _LT_CONFIG_LIBTOOL_INIT([ # See if we are running on zsh, and set the options which allow our @@ -179,7 +192,6 @@ fi _LT_CHECK_OBJDIR m4_require([_LT_TAG_COMPILER])dnl -_LT_PROG_ECHO_BACKSLASH case $host_os in aix3*) @@ -193,23 +205,6 @@ aix3*) ;; esac -# Sed substitution that helps us do robust quoting. It backslashifies -# metacharacters that are still active within double-quoted strings. -sed_quote_subst='s/\([["`$\\]]\)/\\\1/g' - -# Same as above, but do not quote variable references. -double_quote_subst='s/\([["`\\]]\)/\\\1/g' - -# Sed substitution to delay expansion of an escaped shell variable in a -# double_quote_subst'ed string. -delay_variable_subst='s/\\\\\\\\\\\$/\\\\\\$/g' - -# Sed substitution to delay expansion of an escaped single quote. -delay_single_quote_subst='s/'\''/'\'\\\\\\\'\''/g' - -# Sed substitution to avoid accidental globbing in evaled expressions -no_glob_subst='s/\*/\\\*/g' - # Global variables: ofile=libtool can_build_shared=yes @@ -250,6 +245,28 @@ _LT_CONFIG_COMMANDS ])# _LT_SETUP +# _LT_PREPARE_SED_QUOTE_VARS +# -------------------------- +# Define a few sed substitution that help us do robust quoting. +m4_defun([_LT_PREPARE_SED_QUOTE_VARS], +[# Backslashify metacharacters that are still active within +# double-quoted strings. +sed_quote_subst='s/\([["`$\\]]\)/\\\1/g' + +# Same as above, but do not quote variable references. +double_quote_subst='s/\([["`\\]]\)/\\\1/g' + +# Sed substitution to delay expansion of an escaped shell variable in a +# double_quote_subst'ed string. +delay_variable_subst='s/\\\\\\\\\\\$/\\\\\\$/g' + +# Sed substitution to delay expansion of an escaped single quote. +delay_single_quote_subst='s/'\''/'\'\\\\\\\'\''/g' + +# Sed substitution to avoid accidental globbing in evaled expressions +no_glob_subst='s/\*/\\\*/g' +]) + # _LT_PROG_LTMAIN # --------------- # Note that this code is called both from `configure', and `config.status' @@ -408,7 +425,7 @@ m4_define([_lt_decl_all_varnames], # declaration there will have the same value as in `configure'. VARNAME # must have a single quote delimited value for this to work. m4_define([_LT_CONFIG_STATUS_DECLARE], -[$1='`$ECHO "X$][$1" | $Xsed -e "$delay_single_quote_subst"`']) +[$1='`$ECHO "$][$1" | $SED "$delay_single_quote_subst"`']) # _LT_CONFIG_STATUS_DECLARATIONS @@ -418,7 +435,7 @@ m4_define([_LT_CONFIG_STATUS_DECLARE], # embedded single quotes properly. In configure, this macro expands # each variable declared with _LT_DECL (and _LT_TAGDECL) into: # -# ='`$ECHO "X$" | $Xsed -e "$delay_single_quote_subst"`' +# ='`$ECHO "$" | $SED "$delay_single_quote_subst"`' m4_defun([_LT_CONFIG_STATUS_DECLARATIONS], [m4_foreach([_lt_var], m4_quote(lt_decl_all_varnames), [m4_n([_LT_CONFIG_STATUS_DECLARE(_lt_var)])])]) @@ -517,12 +534,20 @@ LTCC='$LTCC' LTCFLAGS='$LTCFLAGS' compiler='$compiler_DEFAULT' +# A function that is used when there is no print builtin or printf. +func_fallback_echo () +{ + eval 'cat <<_LTECHO_EOF +\$[]1 +_LTECHO_EOF' +} + # Quote evaled strings. for var in lt_decl_all_varnames([[ \ ]], lt_decl_quote_varnames); do - case \`eval \\\\\$ECHO "X\\\\\$\$var"\` in + case \`eval \\\\\$ECHO \\\\""\\\\\$\$var"\\\\"\` in *[[\\\\\\\`\\"\\\$]]*) - eval "lt_\$var=\\\\\\"\\\`\\\$ECHO \\"X\\\$\$var\\" | \\\$Xsed -e \\"\\\$sed_quote_subst\\"\\\`\\\\\\"" + eval "lt_\$var=\\\\\\"\\\`\\\$ECHO \\"\\\$\$var\\" | \\\$SED \\"\\\$sed_quote_subst\\"\\\`\\\\\\"" ;; *) eval "lt_\$var=\\\\\\"\\\$\$var\\\\\\"" @@ -533,9 +558,9 @@ done # Double-quote double-evaled strings. for var in lt_decl_all_varnames([[ \ ]], lt_decl_dquote_varnames); do - case \`eval \\\\\$ECHO "X\\\\\$\$var"\` in + case \`eval \\\\\$ECHO \\\\""\\\\\$\$var"\\\\"\` in *[[\\\\\\\`\\"\\\$]]*) - eval "lt_\$var=\\\\\\"\\\`\\\$ECHO \\"X\\\$\$var\\" | \\\$Xsed -e \\"\\\$double_quote_subst\\" -e \\"\\\$sed_quote_subst\\" -e \\"\\\$delay_variable_subst\\"\\\`\\\\\\"" + eval "lt_\$var=\\\\\\"\\\`\\\$ECHO \\"\\\$\$var\\" | \\\$SED -e \\"\\\$double_quote_subst\\" -e \\"\\\$sed_quote_subst\\" -e \\"\\\$delay_variable_subst\\"\\\`\\\\\\"" ;; *) eval "lt_\$var=\\\\\\"\\\$\$var\\\\\\"" @@ -543,16 +568,38 @@ for var in lt_decl_all_varnames([[ \ esac done -# Fix-up fallback echo if it was mangled by the above quoting rules. -case \$lt_ECHO in -*'\\\[$]0 --fallback-echo"')dnl " - lt_ECHO=\`\$ECHO "X\$lt_ECHO" | \$Xsed -e 's/\\\\\\\\\\\\\\\[$]0 --fallback-echo"\[$]/\[$]0 --fallback-echo"/'\` - ;; -esac - _LT_OUTPUT_LIBTOOL_INIT ]) +# _LT_GENERATED_FILE_INIT(FILE, [COMMENT]) +# ------------------------------------ +# Generate a child script FILE with all initialization necessary to +# reuse the environment learned by the parent script, and make the +# file executable. If COMMENT is supplied, it is inserted after the +# `#!' sequence but before initialization text begins. After this +# macro, additional text can be appended to FILE to form the body of +# the child script. The macro ends with non-zero status if the +# file could not be fully written (such as if the disk is full). +m4_ifdef([AS_INIT_GENERATED], +[m4_defun([_LT_GENERATED_FILE_INIT],[AS_INIT_GENERATED($@)])], +[m4_defun([_LT_GENERATED_FILE_INIT], +[m4_require([AS_PREPARE])]dnl +[m4_pushdef([AS_MESSAGE_LOG_FD])]dnl +[lt_write_fail=0 +cat >$1 <<_ASEOF || lt_write_fail=1 +#! $SHELL +# Generated by $as_me. +$2 +SHELL=\${CONFIG_SHELL-$SHELL} +export SHELL +_ASEOF +cat >>$1 <<\_ASEOF || lt_write_fail=1 +AS_SHELL_SANITIZE +_AS_PREPARE +exec AS_MESSAGE_FD>&1 +_ASEOF +test $lt_write_fail = 0 && chmod +x $1[]dnl +m4_popdef([AS_MESSAGE_LOG_FD])])])# _LT_GENERATED_FILE_INIT # LT_OUTPUT # --------- @@ -562,20 +609,11 @@ _LT_OUTPUT_LIBTOOL_INIT AC_DEFUN([LT_OUTPUT], [: ${CONFIG_LT=./config.lt} AC_MSG_NOTICE([creating $CONFIG_LT]) -cat >"$CONFIG_LT" <<_LTEOF -#! $SHELL -# Generated by $as_me. -# Run this file to recreate a libtool stub with the current configuration. - -lt_cl_silent=false -SHELL=\${CONFIG_SHELL-$SHELL} -_LTEOF +_LT_GENERATED_FILE_INIT(["$CONFIG_LT"], +[# Run this file to recreate a libtool stub with the current configuration.]) cat >>"$CONFIG_LT" <<\_LTEOF -AS_SHELL_SANITIZE -_AS_PREPARE - -exec AS_MESSAGE_FD>&1 +lt_cl_silent=false exec AS_MESSAGE_LOG_FD>>config.log { echo @@ -601,7 +639,7 @@ m4_ifset([AC_PACKAGE_NAME], [AC_PACKAGE_NAME ])config.lt[]dnl m4_ifset([AC_PACKAGE_VERSION], [ AC_PACKAGE_VERSION]) configured by $[0], generated by m4_PACKAGE_STRING. -Copyright (C) 2008 Free Software Foundation, Inc. +Copyright (C) 2011 Free Software Foundation, Inc. This config.lt script is free software; the Free Software Foundation gives unlimited permision to copy, distribute and modify it." @@ -646,15 +684,13 @@ chmod +x "$CONFIG_LT" # appending to config.log, which fails on DOS, as config.log is still kept # open by configure. Here we exec the FD to /dev/null, effectively closing # config.log, so it can be properly (re)opened and appended to by config.lt. -if test "$no_create" != yes; then - lt_cl_success=: - test "$silent" = yes && - lt_config_lt_args="$lt_config_lt_args --quiet" - exec AS_MESSAGE_LOG_FD>/dev/null - $SHELL "$CONFIG_LT" $lt_config_lt_args || lt_cl_success=false - exec AS_MESSAGE_LOG_FD>>config.log - $lt_cl_success || AS_EXIT(1) -fi +lt_cl_success=: +test "$silent" = yes && + lt_config_lt_args="$lt_config_lt_args --quiet" +exec AS_MESSAGE_LOG_FD>/dev/null +$SHELL "$CONFIG_LT" $lt_config_lt_args || lt_cl_success=false +exec AS_MESSAGE_LOG_FD>>config.log +$lt_cl_success || AS_EXIT(1) ])# LT_OUTPUT @@ -717,15 +753,12 @@ _LT_EOF # if finds mixed CR/LF and LF-only lines. Since sed operates in # text mode, it properly converts lines to CR/LF. This bash problem # is reportedly fixed, but why not run on old versions too? - sed '/^# Generated shell functions inserted here/q' "$ltmain" >> "$cfgfile" \ - || (rm -f "$cfgfile"; exit 1) - - _LT_PROG_XSI_SHELLFNS + sed '$q' "$ltmain" >> "$cfgfile" \ + || (rm -f "$cfgfile"; exit 1) - sed -n '/^# Generated shell functions inserted here/,$p' "$ltmain" >> "$cfgfile" \ - || (rm -f "$cfgfile"; exit 1) + _LT_PROG_REPLACE_SHELLFNS - mv -f "$cfgfile" "$ofile" || + mv -f "$cfgfile" "$ofile" || (rm -f "$ofile" && cp "$cfgfile" "$ofile" && rm -f "$cfgfile") chmod +x "$ofile" ], @@ -770,6 +803,7 @@ AC_DEFUN([LT_LANG], m4_case([$1], [C], [_LT_LANG(C)], [C++], [_LT_LANG(CXX)], + [Go], [_LT_LANG(GO)], [Java], [_LT_LANG(GCJ)], [Fortran 77], [_LT_LANG(F77)], [Fortran], [_LT_LANG(FC)], @@ -791,6 +825,31 @@ m4_defun([_LT_LANG], ])# _LT_LANG +m4_ifndef([AC_PROG_GO], [ +############################################################ +# NOTE: This macro has been submitted for inclusion into # +# GNU Autoconf as AC_PROG_GO. When it is available in # +# a released version of Autoconf we should remove this # +# macro and use it instead. # +############################################################ +m4_defun([AC_PROG_GO], +[AC_LANG_PUSH(Go)dnl +AC_ARG_VAR([GOC], [Go compiler command])dnl +AC_ARG_VAR([GOFLAGS], [Go compiler flags])dnl +_AC_ARG_VAR_LDFLAGS()dnl +AC_CHECK_TOOL(GOC, gccgo) +if test -z "$GOC"; then + if test -n "$ac_tool_prefix"; then + AC_CHECK_PROG(GOC, [${ac_tool_prefix}gccgo], [${ac_tool_prefix}gccgo]) + fi +fi +if test -z "$GOC"; then + AC_CHECK_PROG(GOC, gccgo, gccgo, false) +fi +])#m4_defun +])#m4_ifndef + + # _LT_LANG_DEFAULT_CONFIG # ----------------------- m4_defun([_LT_LANG_DEFAULT_CONFIG], @@ -821,6 +880,10 @@ AC_PROVIDE_IFELSE([AC_PROG_GCJ], m4_ifdef([LT_PROG_GCJ], [m4_define([LT_PROG_GCJ], defn([LT_PROG_GCJ])[LT_LANG(GCJ)])])])])]) +AC_PROVIDE_IFELSE([AC_PROG_GO], + [LT_LANG(GO)], + [m4_define([AC_PROG_GO], defn([AC_PROG_GO])[LT_LANG(GO)])]) + AC_PROVIDE_IFELSE([LT_PROG_RC], [LT_LANG(RC)], [m4_define([LT_PROG_RC], defn([LT_PROG_RC])[LT_LANG(RC)])]) @@ -831,11 +894,13 @@ AU_DEFUN([AC_LIBTOOL_CXX], [LT_LANG(C++)]) AU_DEFUN([AC_LIBTOOL_F77], [LT_LANG(Fortran 77)]) AU_DEFUN([AC_LIBTOOL_FC], [LT_LANG(Fortran)]) AU_DEFUN([AC_LIBTOOL_GCJ], [LT_LANG(Java)]) +AU_DEFUN([AC_LIBTOOL_RC], [LT_LANG(Windows Resource)]) dnl aclocal-1.4 backwards compatibility: dnl AC_DEFUN([AC_LIBTOOL_CXX], []) dnl AC_DEFUN([AC_LIBTOOL_F77], []) dnl AC_DEFUN([AC_LIBTOOL_FC], []) dnl AC_DEFUN([AC_LIBTOOL_GCJ], []) +dnl AC_DEFUN([AC_LIBTOOL_RC], []) # _LT_TAG_COMPILER @@ -921,7 +986,13 @@ m4_defun_once([_LT_REQUIRED_DARWIN_CHECKS],[ $LTCC $LTCFLAGS $LDFLAGS -o libconftest.dylib \ -dynamiclib -Wl,-single_module conftest.c 2>conftest.err _lt_result=$? - if test -f libconftest.dylib && test ! -s conftest.err && test $_lt_result = 0; then + # If there is a non-empty error log, and "single_module" + # appears in it, assume the flag caused a linker warning + if test -s conftest.err && $GREP single_module conftest.err; then + cat conftest.err >&AS_MESSAGE_LOG_FD + # Otherwise, if the output was created with a 0 exit code from + # the compiler, it worked. + elif test -f libconftest.dylib && test $_lt_result -eq 0; then lt_cv_apple_cc_single_mod=yes else cat conftest.err >&AS_MESSAGE_LOG_FD @@ -929,6 +1000,7 @@ m4_defun_once([_LT_REQUIRED_DARWIN_CHECKS],[ rm -rf libconftest.dylib* rm -f conftest.* fi]) + AC_CACHE_CHECK([for -exported_symbols_list linker flag], [lt_cv_ld_exported_symbols_list], [lt_cv_ld_exported_symbols_list=no @@ -940,6 +1012,34 @@ m4_defun_once([_LT_REQUIRED_DARWIN_CHECKS],[ [lt_cv_ld_exported_symbols_list=no]) LDFLAGS="$save_LDFLAGS" ]) + + AC_CACHE_CHECK([for -force_load linker flag],[lt_cv_ld_force_load], + [lt_cv_ld_force_load=no + cat > conftest.c << _LT_EOF +int forced_loaded() { return 2;} +_LT_EOF + echo "$LTCC $LTCFLAGS -c -o conftest.o conftest.c" >&AS_MESSAGE_LOG_FD + $LTCC $LTCFLAGS -c -o conftest.o conftest.c 2>&AS_MESSAGE_LOG_FD + echo "$AR cru libconftest.a conftest.o" >&AS_MESSAGE_LOG_FD + $AR cru libconftest.a conftest.o 2>&AS_MESSAGE_LOG_FD + echo "$RANLIB libconftest.a" >&AS_MESSAGE_LOG_FD + $RANLIB libconftest.a 2>&AS_MESSAGE_LOG_FD + cat > conftest.c << _LT_EOF +int main() { return 0;} +_LT_EOF + echo "$LTCC $LTCFLAGS $LDFLAGS -o conftest conftest.c -Wl,-force_load,./libconftest.a" >&AS_MESSAGE_LOG_FD + $LTCC $LTCFLAGS $LDFLAGS -o conftest conftest.c -Wl,-force_load,./libconftest.a 2>conftest.err + _lt_result=$? + if test -s conftest.err && $GREP force_load conftest.err; then + cat conftest.err >&AS_MESSAGE_LOG_FD + elif test -f conftest && test $_lt_result -eq 0 && $GREP forced_load conftest >/dev/null 2>&1 ; then + lt_cv_ld_force_load=yes + else + cat conftest.err >&AS_MESSAGE_LOG_FD + fi + rm -f conftest.err libconftest.a conftest conftest.c + rm -rf conftest.dSYM + ]) case $host_os in rhapsody* | darwin1.[[012]]) _lt_dar_allow_undefined='${wl}-undefined ${wl}suppress' ;; @@ -967,7 +1067,7 @@ m4_defun_once([_LT_REQUIRED_DARWIN_CHECKS],[ else _lt_dar_export_syms='~$NMEDIT -s $output_objdir/${libname}-symbols.expsym ${lib}' fi - if test "$DSYMUTIL" != ":"; then + if test "$DSYMUTIL" != ":" && test "$lt_cv_ld_force_load" = "no"; then _lt_dsymutil='~$DSYMUTIL $lib || :' else _lt_dsymutil= @@ -977,8 +1077,8 @@ m4_defun_once([_LT_REQUIRED_DARWIN_CHECKS],[ ]) -# _LT_DARWIN_LINKER_FEATURES -# -------------------------- +# _LT_DARWIN_LINKER_FEATURES([TAG]) +# --------------------------------- # Checks for linker and compiler features on darwin m4_defun([_LT_DARWIN_LINKER_FEATURES], [ @@ -987,7 +1087,13 @@ m4_defun([_LT_DARWIN_LINKER_FEATURES], _LT_TAGVAR(hardcode_direct, $1)=no _LT_TAGVAR(hardcode_automatic, $1)=yes _LT_TAGVAR(hardcode_shlibpath_var, $1)=unsupported - _LT_TAGVAR(whole_archive_flag_spec, $1)='' + if test "$lt_cv_ld_force_load" = "yes"; then + _LT_TAGVAR(whole_archive_flag_spec, $1)='`for conv in $convenience\"\"; do test -n \"$conv\" && new_convenience=\"$new_convenience ${wl}-force_load,$conv\"; done; func_echo_all \"$new_convenience\"`' + m4_case([$1], [F77], [_LT_TAGVAR(compiler_needs_object, $1)=yes], + [FC], [_LT_TAGVAR(compiler_needs_object, $1)=yes]) + else + _LT_TAGVAR(whole_archive_flag_spec, $1)='' + fi _LT_TAGVAR(link_all_deplibs, $1)=yes _LT_TAGVAR(allow_undefined_flag, $1)="$_lt_dar_allow_undefined" case $cc_basename in @@ -995,7 +1101,7 @@ m4_defun([_LT_DARWIN_LINKER_FEATURES], *) _lt_dar_can_shared=$GCC ;; esac if test "$_lt_dar_can_shared" = "yes"; then - output_verbose_link_cmd=echo + output_verbose_link_cmd=func_echo_all _LT_TAGVAR(archive_cmds, $1)="\$CC -dynamiclib \$allow_undefined_flag -o \$lib \$libobjs \$deplibs \$compiler_flags -install_name \$rpath/\$soname \$verstring $_lt_dar_single_mod${_lt_dsymutil}" _LT_TAGVAR(module_cmds, $1)="\$CC \$allow_undefined_flag -o \$lib -bundle \$libobjs \$deplibs \$compiler_flags${_lt_dsymutil}" _LT_TAGVAR(archive_expsym_cmds, $1)="sed 's,^,_,' < \$export_symbols > \$output_objdir/\${libname}-symbols.expsym~\$CC -dynamiclib \$allow_undefined_flag -o \$lib \$libobjs \$deplibs \$compiler_flags -install_name \$rpath/\$soname \$verstring ${_lt_dar_single_mod}${_lt_dar_export_syms}${_lt_dsymutil}" @@ -1011,203 +1117,142 @@ m4_defun([_LT_DARWIN_LINKER_FEATURES], fi ]) -# _LT_SYS_MODULE_PATH_AIX -# ----------------------- +# _LT_SYS_MODULE_PATH_AIX([TAGNAME]) +# ---------------------------------- # Links a minimal program and checks the executable # for the system default hardcoded library path. In most cases, # this is /usr/lib:/lib, but when the MPI compilers are used # the location of the communication and MPI libs are included too. # If we don't find anything, use the default library path according # to the aix ld manual. +# Store the results from the different compilers for each TAGNAME. +# Allow to override them for all tags through lt_cv_aix_libpath. m4_defun([_LT_SYS_MODULE_PATH_AIX], [m4_require([_LT_DECL_SED])dnl -AC_LINK_IFELSE(AC_LANG_PROGRAM,[ -lt_aix_libpath_sed=' - /Import File Strings/,/^$/ { - /^0/ { - s/^0 *\(.*\)$/\1/ - p - } - }' -aix_libpath=`dump -H conftest$ac_exeext 2>/dev/null | $SED -n -e "$lt_aix_libpath_sed"` -# Check for a 64-bit object if we didn't find anything. -if test -z "$aix_libpath"; then - aix_libpath=`dump -HX64 conftest$ac_exeext 2>/dev/null | $SED -n -e "$lt_aix_libpath_sed"` -fi],[]) -if test -z "$aix_libpath"; then aix_libpath="/usr/lib:/lib"; fi +if test "${lt_cv_aix_libpath+set}" = set; then + aix_libpath=$lt_cv_aix_libpath +else + AC_CACHE_VAL([_LT_TAGVAR([lt_cv_aix_libpath_], [$1])], + [AC_LINK_IFELSE([AC_LANG_PROGRAM],[ + lt_aix_libpath_sed='[ + /Import File Strings/,/^$/ { + /^0/ { + s/^0 *\([^ ]*\) *$/\1/ + p + } + }]' + _LT_TAGVAR([lt_cv_aix_libpath_], [$1])=`dump -H conftest$ac_exeext 2>/dev/null | $SED -n -e "$lt_aix_libpath_sed"` + # Check for a 64-bit object if we didn't find anything. + if test -z "$_LT_TAGVAR([lt_cv_aix_libpath_], [$1])"; then + _LT_TAGVAR([lt_cv_aix_libpath_], [$1])=`dump -HX64 conftest$ac_exeext 2>/dev/null | $SED -n -e "$lt_aix_libpath_sed"` + fi],[]) + if test -z "$_LT_TAGVAR([lt_cv_aix_libpath_], [$1])"; then + _LT_TAGVAR([lt_cv_aix_libpath_], [$1])="/usr/lib:/lib" + fi + ]) + aix_libpath=$_LT_TAGVAR([lt_cv_aix_libpath_], [$1]) +fi ])# _LT_SYS_MODULE_PATH_AIX # _LT_SHELL_INIT(ARG) # ------------------- m4_define([_LT_SHELL_INIT], -[ifdef([AC_DIVERSION_NOTICE], - [AC_DIVERT_PUSH(AC_DIVERSION_NOTICE)], - [AC_DIVERT_PUSH(NOTICE)]) -$1 -AC_DIVERT_POP -])# _LT_SHELL_INIT +[m4_divert_text([M4SH-INIT], [$1 +])])# _LT_SHELL_INIT + # _LT_PROG_ECHO_BACKSLASH # ----------------------- -# Add some code to the start of the generated configure script which -# will find an echo command which doesn't interpret backslashes. +# Find how we can fake an echo command that does not interpret backslash. +# In particular, with Autoconf 2.60 or later we add some code to the start +# of the generated configure script which will find a shell with a builtin +# printf (which we can use as an echo command). m4_defun([_LT_PROG_ECHO_BACKSLASH], -[_LT_SHELL_INIT([ -# Check that we are running under the correct shell. -SHELL=${CONFIG_SHELL-/bin/sh} - -case X$lt_ECHO in -X*--fallback-echo) - # Remove one level of quotation (which was required for Make). - ECHO=`echo "$lt_ECHO" | sed 's,\\\\\[$]\\[$]0,'[$]0','` - ;; -esac - -ECHO=${lt_ECHO-echo} -if test "X[$]1" = X--no-reexec; then - # Discard the --no-reexec flag, and continue. - shift -elif test "X[$]1" = X--fallback-echo; then - # Avoid inline document here, it may be left over - : -elif test "X`{ $ECHO '\t'; } 2>/dev/null`" = 'X\t' ; then - # Yippee, $ECHO works! - : +[ECHO='\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\' +ECHO=$ECHO$ECHO$ECHO$ECHO$ECHO +ECHO=$ECHO$ECHO$ECHO$ECHO$ECHO$ECHO + +AC_MSG_CHECKING([how to print strings]) +# Test print first, because it will be a builtin if present. +if test "X`( print -r -- -n ) 2>/dev/null`" = X-n && \ + test "X`print -r -- $ECHO 2>/dev/null`" = "X$ECHO"; then + ECHO='print -r --' +elif test "X`printf %s $ECHO 2>/dev/null`" = "X$ECHO"; then + ECHO='printf %s\n' else - # Restart under the correct shell. - exec $SHELL "[$]0" --no-reexec ${1+"[$]@"} -fi - -if test "X[$]1" = X--fallback-echo; then - # used as fallback echo - shift - cat <<_LT_EOF -[$]* -_LT_EOF - exit 0 + # Use this function as a fallback that always works. + func_fallback_echo () + { + eval 'cat <<_LTECHO_EOF +$[]1 +_LTECHO_EOF' + } + ECHO='func_fallback_echo' fi -# The HP-UX ksh and POSIX shell print the target directory to stdout -# if CDPATH is set. -(unset CDPATH) >/dev/null 2>&1 && unset CDPATH - -if test -z "$lt_ECHO"; then - if test "X${echo_test_string+set}" != Xset; then - # find a string as large as possible, as long as the shell can cope with it - for cmd in 'sed 50q "[$]0"' 'sed 20q "[$]0"' 'sed 10q "[$]0"' 'sed 2q "[$]0"' 'echo test'; do - # expected sizes: less than 2Kb, 1Kb, 512 bytes, 16 bytes, ... - if { echo_test_string=`eval $cmd`; } 2>/dev/null && - { test "X$echo_test_string" = "X$echo_test_string"; } 2>/dev/null - then - break - fi - done - fi - - if test "X`{ $ECHO '\t'; } 2>/dev/null`" = 'X\t' && - echo_testing_string=`{ $ECHO "$echo_test_string"; } 2>/dev/null` && - test "X$echo_testing_string" = "X$echo_test_string"; then - : - else - # The Solaris, AIX, and Digital Unix default echo programs unquote - # backslashes. This makes it impossible to quote backslashes using - # echo "$something" | sed 's/\\/\\\\/g' - # - # So, first we look for a working echo in the user's PATH. - - lt_save_ifs="$IFS"; IFS=$PATH_SEPARATOR - for dir in $PATH /usr/ucb; do - IFS="$lt_save_ifs" - if (test -f $dir/echo || test -f $dir/echo$ac_exeext) && - test "X`($dir/echo '\t') 2>/dev/null`" = 'X\t' && - echo_testing_string=`($dir/echo "$echo_test_string") 2>/dev/null` && - test "X$echo_testing_string" = "X$echo_test_string"; then - ECHO="$dir/echo" - break - fi - done - IFS="$lt_save_ifs" - - if test "X$ECHO" = Xecho; then - # We didn't find a better echo, so look for alternatives. - if test "X`{ print -r '\t'; } 2>/dev/null`" = 'X\t' && - echo_testing_string=`{ print -r "$echo_test_string"; } 2>/dev/null` && - test "X$echo_testing_string" = "X$echo_test_string"; then - # This shell has a builtin print -r that does the trick. - ECHO='print -r' - elif { test -f /bin/ksh || test -f /bin/ksh$ac_exeext; } && - test "X$CONFIG_SHELL" != X/bin/ksh; then - # If we have ksh, try running configure again with it. - ORIGINAL_CONFIG_SHELL=${CONFIG_SHELL-/bin/sh} - export ORIGINAL_CONFIG_SHELL - CONFIG_SHELL=/bin/ksh - export CONFIG_SHELL - exec $CONFIG_SHELL "[$]0" --no-reexec ${1+"[$]@"} - else - # Try using printf. - ECHO='printf %s\n' - if test "X`{ $ECHO '\t'; } 2>/dev/null`" = 'X\t' && - echo_testing_string=`{ $ECHO "$echo_test_string"; } 2>/dev/null` && - test "X$echo_testing_string" = "X$echo_test_string"; then - # Cool, printf works - : - elif echo_testing_string=`($ORIGINAL_CONFIG_SHELL "[$]0" --fallback-echo '\t') 2>/dev/null` && - test "X$echo_testing_string" = 'X\t' && - echo_testing_string=`($ORIGINAL_CONFIG_SHELL "[$]0" --fallback-echo "$echo_test_string") 2>/dev/null` && - test "X$echo_testing_string" = "X$echo_test_string"; then - CONFIG_SHELL=$ORIGINAL_CONFIG_SHELL - export CONFIG_SHELL - SHELL="$CONFIG_SHELL" - export SHELL - ECHO="$CONFIG_SHELL [$]0 --fallback-echo" - elif echo_testing_string=`($CONFIG_SHELL "[$]0" --fallback-echo '\t') 2>/dev/null` && - test "X$echo_testing_string" = 'X\t' && - echo_testing_string=`($CONFIG_SHELL "[$]0" --fallback-echo "$echo_test_string") 2>/dev/null` && - test "X$echo_testing_string" = "X$echo_test_string"; then - ECHO="$CONFIG_SHELL [$]0 --fallback-echo" - else - # maybe with a smaller string... - prev=: - - for cmd in 'echo test' 'sed 2q "[$]0"' 'sed 10q "[$]0"' 'sed 20q "[$]0"' 'sed 50q "[$]0"'; do - if { test "X$echo_test_string" = "X`eval $cmd`"; } 2>/dev/null - then - break - fi - prev="$cmd" - done +# func_echo_all arg... +# Invoke $ECHO with all args, space-separated. +func_echo_all () +{ + $ECHO "$*" +} - if test "$prev" != 'sed 50q "[$]0"'; then - echo_test_string=`eval $prev` - export echo_test_string - exec ${ORIGINAL_CONFIG_SHELL-${CONFIG_SHELL-/bin/sh}} "[$]0" ${1+"[$]@"} - else - # Oops. We lost completely, so just stick with echo. - ECHO=echo - fi - fi - fi - fi - fi -fi +case "$ECHO" in + printf*) AC_MSG_RESULT([printf]) ;; + print*) AC_MSG_RESULT([print -r]) ;; + *) AC_MSG_RESULT([cat]) ;; +esac -# Copy echo and quote the copy suitably for passing to libtool from -# the Makefile, instead of quoting the original, which is used later. -lt_ECHO=$ECHO -if test "X$lt_ECHO" = "X$CONFIG_SHELL [$]0 --fallback-echo"; then - lt_ECHO="$CONFIG_SHELL \\\$\[$]0 --fallback-echo" -fi +m4_ifdef([_AS_DETECT_SUGGESTED], +[_AS_DETECT_SUGGESTED([ + test -n "${ZSH_VERSION+set}${BASH_VERSION+set}" || ( + ECHO='\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\' + ECHO=$ECHO$ECHO$ECHO$ECHO$ECHO + ECHO=$ECHO$ECHO$ECHO$ECHO$ECHO$ECHO + PATH=/empty FPATH=/empty; export PATH FPATH + test "X`printf %s $ECHO`" = "X$ECHO" \ + || test "X`print -r -- $ECHO`" = "X$ECHO" )])]) -AC_SUBST(lt_ECHO) -]) _LT_DECL([], [SHELL], [1], [Shell to use when invoking shell scripts]) -_LT_DECL([], [ECHO], [1], - [An echo program that does not interpret backslashes]) +_LT_DECL([], [ECHO], [1], [An echo program that protects backslashes]) ])# _LT_PROG_ECHO_BACKSLASH +# _LT_WITH_SYSROOT +# ---------------- +AC_DEFUN([_LT_WITH_SYSROOT], +[AC_MSG_CHECKING([for sysroot]) +AC_ARG_WITH([sysroot], +[ --with-sysroot[=DIR] Search for dependent libraries within DIR + (or the compiler's sysroot if not specified).], +[], [with_sysroot=no]) + +dnl lt_sysroot will always be passed unquoted. We quote it here +dnl in case the user passed a directory name. +lt_sysroot= +case ${with_sysroot} in #( + yes) + if test "$GCC" = yes; then + lt_sysroot=`$CC --print-sysroot 2>/dev/null` + fi + ;; #( + /*) + lt_sysroot=`echo "$with_sysroot" | sed -e "$sed_quote_subst"` + ;; #( + no|'') + ;; #( + *) + AC_MSG_RESULT([${with_sysroot}]) + AC_MSG_ERROR([The sysroot must be an absolute path.]) + ;; +esac + + AC_MSG_RESULT([${lt_sysroot:-no}]) +_LT_DECL([], [lt_sysroot], [0], [The root where to search for ]dnl +[dependent libraries, and in which our libraries should be installed.])]) + # _LT_ENABLE_LOCK # --------------- m4_defun([_LT_ENABLE_LOCK], @@ -1236,7 +1281,7 @@ ia64-*-hpux*) ;; *-*-irix6*) # Find out which ABI we are using. - echo '[#]line __oline__ "configure"' > conftest.$ac_ext + echo '[#]line '$LINENO' "configure"' > conftest.$ac_ext if AC_TRY_EVAL(ac_compile); then if test "$lt_cv_prog_gnu_ld" = yes; then case `/usr/bin/file conftest.$ac_objext` in @@ -1329,14 +1374,27 @@ s390*-*linux*|s390*-*tpf*|sparc*-*linux*) CFLAGS="$SAVE_CFLAGS" fi ;; -sparc*-*solaris*) +*-*solaris*) # Find out which ABI we are using. echo 'int i;' > conftest.$ac_ext if AC_TRY_EVAL(ac_compile); then case `/usr/bin/file conftest.o` in *64-bit*) case $lt_cv_prog_gnu_ld in - yes*) LD="${LD-ld} -m elf64_sparc" ;; + yes*) + case $host in + i?86-*-solaris*) + LD="${LD-ld} -m elf_x86_64" + ;; + sparc*-*-solaris*) + LD="${LD-ld} -m elf64_sparc" + ;; + esac + # GNU ld 2.21 introduced _sol2 emulations. Use them if available. + if ${LD-ld} -V | grep _sol2 >/dev/null 2>&1; then + LD="${LD-ld}_sol2" + fi + ;; *) if ${LD-ld} -64 -r -o conftest2.o conftest.o >/dev/null 2>&1; then LD="${LD-ld} -64" @@ -1354,14 +1412,47 @@ need_locks="$enable_libtool_lock" ])# _LT_ENABLE_LOCK +# _LT_PROG_AR +# ----------- +m4_defun([_LT_PROG_AR], +[AC_CHECK_TOOLS(AR, [ar], false) +: ${AR=ar} +: ${AR_FLAGS=cru} +_LT_DECL([], [AR], [1], [The archiver]) +_LT_DECL([], [AR_FLAGS], [1], [Flags to create an archive]) + +AC_CACHE_CHECK([for archiver @FILE support], [lt_cv_ar_at_file], + [lt_cv_ar_at_file=no + AC_COMPILE_IFELSE([AC_LANG_PROGRAM], + [echo conftest.$ac_objext > conftest.lst + lt_ar_try='$AR $AR_FLAGS libconftest.a @conftest.lst >&AS_MESSAGE_LOG_FD' + AC_TRY_EVAL([lt_ar_try]) + if test "$ac_status" -eq 0; then + # Ensure the archiver fails upon bogus file names. + rm -f conftest.$ac_objext libconftest.a + AC_TRY_EVAL([lt_ar_try]) + if test "$ac_status" -ne 0; then + lt_cv_ar_at_file=@ + fi + fi + rm -f conftest.* libconftest.a + ]) + ]) + +if test "x$lt_cv_ar_at_file" = xno; then + archiver_list_spec= +else + archiver_list_spec=$lt_cv_ar_at_file +fi +_LT_DECL([], [archiver_list_spec], [1], + [How to feed a file listing to the archiver]) +])# _LT_PROG_AR + + # _LT_CMD_OLD_ARCHIVE # ------------------- m4_defun([_LT_CMD_OLD_ARCHIVE], -[AC_CHECK_TOOL(AR, ar, false) -test -z "$AR" && AR=ar -test -z "$AR_FLAGS" && AR_FLAGS=cru -_LT_DECL([], [AR], [1], [The archiver]) -_LT_DECL([], [AR_FLAGS], [1]) +[_LT_PROG_AR AC_CHECK_TOOL(STRIP, strip, :) test -z "$STRIP" && STRIP=: @@ -1380,18 +1471,27 @@ old_postuninstall_cmds= if test -n "$RANLIB"; then case $host_os in openbsd*) - old_postinstall_cmds="$old_postinstall_cmds~\$RANLIB -t \$oldlib" + old_postinstall_cmds="$old_postinstall_cmds~\$RANLIB -t \$tool_oldlib" ;; *) - old_postinstall_cmds="$old_postinstall_cmds~\$RANLIB \$oldlib" + old_postinstall_cmds="$old_postinstall_cmds~\$RANLIB \$tool_oldlib" ;; esac - old_archive_cmds="$old_archive_cmds~\$RANLIB \$oldlib" + old_archive_cmds="$old_archive_cmds~\$RANLIB \$tool_oldlib" fi + +case $host_os in + darwin*) + lock_old_archive_extraction=yes ;; + *) + lock_old_archive_extraction=no ;; +esac _LT_DECL([], [old_postinstall_cmds], [2]) _LT_DECL([], [old_postuninstall_cmds], [2]) _LT_TAGDECL([], [old_archive_cmds], [2], [Commands used to build an old-style archive]) +_LT_DECL([], [lock_old_archive_extraction], [0], + [Whether to use a lock for old archive extraction]) ])# _LT_CMD_OLD_ARCHIVE @@ -1416,15 +1516,15 @@ AC_CACHE_CHECK([$1], [$2], -e 's:.*FLAGS}\{0,1\} :&$lt_compiler_flag :; t' \ -e 's: [[^ ]]*conftest\.: $lt_compiler_flag&:; t' \ -e 's:$: $lt_compiler_flag:'` - (eval echo "\"\$as_me:__oline__: $lt_compile\"" >&AS_MESSAGE_LOG_FD) + (eval echo "\"\$as_me:$LINENO: $lt_compile\"" >&AS_MESSAGE_LOG_FD) (eval "$lt_compile" 2>conftest.err) ac_status=$? cat conftest.err >&AS_MESSAGE_LOG_FD - echo "$as_me:__oline__: \$? = $ac_status" >&AS_MESSAGE_LOG_FD + echo "$as_me:$LINENO: \$? = $ac_status" >&AS_MESSAGE_LOG_FD if (exit $ac_status) && test -s "$ac_outfile"; then # The compiler can only warn and ignore the option if not recognized # So say no if there are warnings other than the usual output. - $ECHO "X$_lt_compiler_boilerplate" | $Xsed -e '/^$/d' >conftest.exp + $ECHO "$_lt_compiler_boilerplate" | $SED '/^$/d' >conftest.exp $SED '/^$/d; /^ *+/d' conftest.err >conftest.er2 if test ! -s conftest.er2 || diff conftest.exp conftest.er2 >/dev/null; then $2=yes @@ -1464,7 +1564,7 @@ AC_CACHE_CHECK([$1], [$2], if test -s conftest.err; then # Append any errors to the config.log. cat conftest.err 1>&AS_MESSAGE_LOG_FD - $ECHO "X$_lt_linker_boilerplate" | $Xsed -e '/^$/d' > conftest.exp + $ECHO "$_lt_linker_boilerplate" | $SED '/^$/d' > conftest.exp $SED '/^$/d; /^ *+/d' conftest.err >conftest.er2 if diff conftest.exp conftest.er2 >/dev/null; then $2=yes @@ -1527,6 +1627,11 @@ AC_CACHE_VAL([lt_cv_sys_max_cmd_len], [dnl lt_cv_sys_max_cmd_len=8192; ;; + mint*) + # On MiNT this can take a long time and run out of memory. + lt_cv_sys_max_cmd_len=8192; + ;; + amigaos*) # On AmigaOS with pdksh, this test takes hours, literally. # So we just punt and use a minimum line length of 8192. @@ -1552,6 +1657,11 @@ AC_CACHE_VAL([lt_cv_sys_max_cmd_len], [dnl lt_cv_sys_max_cmd_len=196608 ;; + os2*) + # The test takes a long time on OS/2. + lt_cv_sys_max_cmd_len=8192 + ;; + osf*) # Dr. Hans Ekkehard Plesser reports seeing a kernel panic running configure # due to this test when exec_disable_arg_limit is 1 on Tru64. It is not @@ -1591,8 +1701,8 @@ AC_CACHE_VAL([lt_cv_sys_max_cmd_len], [dnl # If test is not a shell built-in, we'll probably end up computing a # maximum length that is only half of the actual maximum length, but # we can't tell. - while { test "X"`$SHELL [$]0 --fallback-echo "X$teststring$teststring" 2>/dev/null` \ - = "XX$teststring$teststring"; } >/dev/null 2>&1 && + while { test "X"`env echo "$teststring$teststring" 2>/dev/null` \ + = "X$teststring$teststring"; } >/dev/null 2>&1 && test $i != 17 # 1/2 MB should be enough do i=`expr $i + 1` @@ -1643,7 +1753,7 @@ else lt_dlunknown=0; lt_dlno_uscore=1; lt_dlneed_uscore=2 lt_status=$lt_dlunknown cat > conftest.$ac_ext <<_LT_EOF -[#line __oline__ "configure" +[#line $LINENO "configure" #include "confdefs.h" #if HAVE_DLFCN_H @@ -1684,7 +1794,13 @@ else # endif #endif -void fnord() { int i=42;} +/* When -fvisbility=hidden is used, assume the code has been annotated + correspondingly for the symbols needed. */ +#if defined(__GNUC__) && (((__GNUC__ == 3) && (__GNUC_MINOR__ >= 3)) || (__GNUC__ > 3)) +int fnord () __attribute__((visibility("default"))); +#endif + +int fnord () { return 42; } int main () { void *self = dlopen (0, LT_DLGLOBAL|LT_DLLAZY_OR_NOW); @@ -1693,7 +1809,11 @@ int main () if (self) { if (dlsym (self,"fnord")) status = $lt_dlno_uscore; - else if (dlsym( self,"_fnord")) status = $lt_dlneed_uscore; + else + { + if (dlsym( self,"_fnord")) status = $lt_dlneed_uscore; + else puts (dlerror ()); + } /* dlclose (self); */ } else @@ -1869,16 +1989,16 @@ AC_CACHE_CHECK([if $compiler supports -c -o file.$ac_objext], -e 's:.*FLAGS}\{0,1\} :&$lt_compiler_flag :; t' \ -e 's: [[^ ]]*conftest\.: $lt_compiler_flag&:; t' \ -e 's:$: $lt_compiler_flag:'` - (eval echo "\"\$as_me:__oline__: $lt_compile\"" >&AS_MESSAGE_LOG_FD) + (eval echo "\"\$as_me:$LINENO: $lt_compile\"" >&AS_MESSAGE_LOG_FD) (eval "$lt_compile" 2>out/conftest.err) ac_status=$? cat out/conftest.err >&AS_MESSAGE_LOG_FD - echo "$as_me:__oline__: \$? = $ac_status" >&AS_MESSAGE_LOG_FD + echo "$as_me:$LINENO: \$? = $ac_status" >&AS_MESSAGE_LOG_FD if (exit $ac_status) && test -s out/conftest2.$ac_objext then # The compiler can only warn and ignore the option if not recognized # So say no if there are warnings - $ECHO "X$_lt_compiler_boilerplate" | $Xsed -e '/^$/d' > out/conftest.exp + $ECHO "$_lt_compiler_boilerplate" | $SED '/^$/d' > out/conftest.exp $SED '/^$/d; /^ *+/d' out/conftest.err >out/conftest.er2 if test ! -s out/conftest.er2 || diff out/conftest.exp out/conftest.er2 >/dev/null; then _LT_TAGVAR(lt_cv_prog_compiler_c_o, $1)=yes @@ -2037,6 +2157,7 @@ m4_require([_LT_DECL_EGREP])dnl m4_require([_LT_FILEUTILS_DEFAULTS])dnl m4_require([_LT_DECL_OBJDUMP])dnl m4_require([_LT_DECL_SED])dnl +m4_require([_LT_CHECK_SHELL_FEATURES])dnl AC_MSG_CHECKING([dynamic linker characteristics]) m4_if([$1], [], [ @@ -2045,16 +2166,23 @@ if test "$GCC" = yes; then darwin*) lt_awk_arg="/^libraries:/,/LR/" ;; *) lt_awk_arg="/^libraries:/" ;; esac - lt_search_path_spec=`$CC -print-search-dirs | awk $lt_awk_arg | $SED -e "s/^libraries://" -e "s,=/,/,g"` - if $ECHO "$lt_search_path_spec" | $GREP ';' >/dev/null ; then + case $host_os in + mingw* | cegcc*) lt_sed_strip_eq="s,=\([[A-Za-z]]:\),\1,g" ;; + *) lt_sed_strip_eq="s,=/,/,g" ;; + esac + lt_search_path_spec=`$CC -print-search-dirs | awk $lt_awk_arg | $SED -e "s/^libraries://" -e $lt_sed_strip_eq` + case $lt_search_path_spec in + *\;*) # if the path contains ";" then we assume it to be the separator # otherwise default to the standard path separator (i.e. ":") - it is # assumed that no part of a normal pathname contains ";" but that should # okay in the real world where ";" in dirpaths is itself problematic. - lt_search_path_spec=`$ECHO "$lt_search_path_spec" | $SED -e 's/;/ /g'` - else - lt_search_path_spec=`$ECHO "$lt_search_path_spec" | $SED -e "s/$PATH_SEPARATOR/ /g"` - fi + lt_search_path_spec=`$ECHO "$lt_search_path_spec" | $SED 's/;/ /g'` + ;; + *) + lt_search_path_spec=`$ECHO "$lt_search_path_spec" | $SED "s/$PATH_SEPARATOR/ /g"` + ;; + esac # Ok, now we have the path, separated by spaces, we can step through it # and add multilib dir if necessary. lt_tmp_lt_search_path_spec= @@ -2067,7 +2195,7 @@ if test "$GCC" = yes; then lt_tmp_lt_search_path_spec="$lt_tmp_lt_search_path_spec $lt_sys_path" fi done - lt_search_path_spec=`$ECHO $lt_tmp_lt_search_path_spec | awk ' + lt_search_path_spec=`$ECHO "$lt_tmp_lt_search_path_spec" | awk ' BEGIN {RS=" "; FS="/|\n";} { lt_foo=""; lt_count=0; @@ -2087,7 +2215,13 @@ BEGIN {RS=" "; FS="/|\n";} { if (lt_foo != "") { lt_freq[[lt_foo]]++; } if (lt_freq[[lt_foo]] == 1) { print lt_foo; } }'` - sys_lib_search_path_spec=`$ECHO $lt_search_path_spec` + # AWK program above erroneously prepends '/' to C:/dos/paths + # for these hosts. + case $host_os in + mingw* | cegcc*) lt_search_path_spec=`$ECHO "$lt_search_path_spec" |\ + $SED 's,/\([[A-Za-z]]:\),\1,g'` ;; + esac + sys_lib_search_path_spec=`$ECHO "$lt_search_path_spec" | $lt_NL2SP` else sys_lib_search_path_spec="/lib /usr/lib /usr/local/lib" fi]) @@ -2113,7 +2247,7 @@ need_version=unknown case $host_os in aix3*) - version_type=linux + version_type=linux # correct to gnu/linux during the next big refactor library_names_spec='${libname}${release}${shared_ext}$versuffix $libname.a' shlibpath_var=LIBPATH @@ -2122,7 +2256,7 @@ aix3*) ;; aix[[4-9]]*) - version_type=linux + version_type=linux # correct to gnu/linux during the next big refactor need_lib_prefix=no need_version=no hardcode_into_libs=yes @@ -2175,7 +2309,7 @@ amigaos*) m68k) library_names_spec='$libname.ixlibrary $libname.a' # Create ${libname}_ixlibrary.a entries in /sys/libs. - finish_eval='for lib in `ls $libdir/*.ixlibrary 2>/dev/null`; do libname=`$ECHO "X$lib" | $Xsed -e '\''s%^.*/\([[^/]]*\)\.ixlibrary$%\1%'\''`; test $RM /sys/libs/${libname}_ixlibrary.a; $show "cd /sys/libs && $LN_S $lib ${libname}_ixlibrary.a"; cd /sys/libs && $LN_S $lib ${libname}_ixlibrary.a || exit 1; done' + finish_eval='for lib in `ls $libdir/*.ixlibrary 2>/dev/null`; do libname=`func_echo_all "$lib" | $SED '\''s%^.*/\([[^/]]*\)\.ixlibrary$%\1%'\''`; test $RM /sys/libs/${libname}_ixlibrary.a; $show "cd /sys/libs && $LN_S $lib ${libname}_ixlibrary.a"; cd /sys/libs && $LN_S $lib ${libname}_ixlibrary.a || exit 1; done' ;; esac ;; @@ -2187,7 +2321,7 @@ beos*) ;; bsdi[[45]]*) - version_type=linux + version_type=linux # correct to gnu/linux during the next big refactor need_version=no library_names_spec='${libname}${release}${shared_ext}$versuffix ${libname}${release}${shared_ext}$major $libname${shared_ext}' soname_spec='${libname}${release}${shared_ext}$major' @@ -2206,8 +2340,9 @@ cygwin* | mingw* | pw32* | cegcc*) need_version=no need_lib_prefix=no - case $GCC,$host_os in - yes,cygwin* | yes,mingw* | yes,pw32* | yes,cegcc*) + case $GCC,$cc_basename in + yes,*) + # gcc library_names_spec='$libname.dll.a' # DLL is installed to $(libdir)/../bin by postinstall_cmds postinstall_cmds='base_file=`basename \${file}`~ @@ -2228,36 +2363,83 @@ cygwin* | mingw* | pw32* | cegcc*) cygwin*) # Cygwin DLLs use 'cyg' prefix rather than 'lib' soname_spec='`echo ${libname} | sed -e 's/^lib/cyg/'``echo ${release} | $SED -e 's/[[.]]/-/g'`${versuffix}${shared_ext}' - sys_lib_search_path_spec="/usr/lib /lib/w32api /lib /usr/local/lib" +m4_if([$1], [],[ + sys_lib_search_path_spec="$sys_lib_search_path_spec /usr/lib/w32api"]) ;; mingw* | cegcc*) # MinGW DLLs use traditional 'lib' prefix soname_spec='${libname}`echo ${release} | $SED -e 's/[[.]]/-/g'`${versuffix}${shared_ext}' - sys_lib_search_path_spec=`$CC -print-search-dirs | $GREP "^libraries:" | $SED -e "s/^libraries://" -e "s,=/,/,g"` - if $ECHO "$sys_lib_search_path_spec" | [$GREP ';[c-zC-Z]:/' >/dev/null]; then - # It is most probably a Windows format PATH printed by - # mingw gcc, but we are running on Cygwin. Gcc prints its search - # path with ; separators, and with drive letters. We can handle the - # drive letters (cygwin fileutils understands them), so leave them, - # especially as we might pass files found there to a mingw objdump, - # which wouldn't understand a cygwinified path. Ahh. - sys_lib_search_path_spec=`$ECHO "$sys_lib_search_path_spec" | $SED -e 's/;/ /g'` - else - sys_lib_search_path_spec=`$ECHO "$sys_lib_search_path_spec" | $SED -e "s/$PATH_SEPARATOR/ /g"` - fi ;; pw32*) # pw32 DLLs use 'pw' prefix rather than 'lib' library_names_spec='`echo ${libname} | sed -e 's/^lib/pw/'``echo ${release} | $SED -e 's/[[.]]/-/g'`${versuffix}${shared_ext}' ;; esac + dynamic_linker='Win32 ld.exe' + ;; + + *,cl*) + # Native MSVC + libname_spec='$name' + soname_spec='${libname}`echo ${release} | $SED -e 's/[[.]]/-/g'`${versuffix}${shared_ext}' + library_names_spec='${libname}.dll.lib' + + case $build_os in + mingw*) + sys_lib_search_path_spec= + lt_save_ifs=$IFS + IFS=';' + for lt_path in $LIB + do + IFS=$lt_save_ifs + # Let DOS variable expansion print the short 8.3 style file name. + lt_path=`cd "$lt_path" 2>/dev/null && cmd //C "for %i in (".") do @echo %~si"` + sys_lib_search_path_spec="$sys_lib_search_path_spec $lt_path" + done + IFS=$lt_save_ifs + # Convert to MSYS style. + sys_lib_search_path_spec=`$ECHO "$sys_lib_search_path_spec" | sed -e 's|\\\\|/|g' -e 's| \\([[a-zA-Z]]\\):| /\\1|g' -e 's|^ ||'` + ;; + cygwin*) + # Convert to unix form, then to dos form, then back to unix form + # but this time dos style (no spaces!) so that the unix form looks + # like /cygdrive/c/PROGRA~1:/cygdr... + sys_lib_search_path_spec=`cygpath --path --unix "$LIB"` + sys_lib_search_path_spec=`cygpath --path --dos "$sys_lib_search_path_spec" 2>/dev/null` + sys_lib_search_path_spec=`cygpath --path --unix "$sys_lib_search_path_spec" | $SED -e "s/$PATH_SEPARATOR/ /g"` + ;; + *) + sys_lib_search_path_spec="$LIB" + if $ECHO "$sys_lib_search_path_spec" | [$GREP ';[c-zC-Z]:/' >/dev/null]; then + # It is most probably a Windows format PATH. + sys_lib_search_path_spec=`$ECHO "$sys_lib_search_path_spec" | $SED -e 's/;/ /g'` + else + sys_lib_search_path_spec=`$ECHO "$sys_lib_search_path_spec" | $SED -e "s/$PATH_SEPARATOR/ /g"` + fi + # FIXME: find the short name or the path components, as spaces are + # common. (e.g. "Program Files" -> "PROGRA~1") + ;; + esac + + # DLL is installed to $(libdir)/../bin by postinstall_cmds + postinstall_cmds='base_file=`basename \${file}`~ + dlpath=`$SHELL 2>&1 -c '\''. $dir/'\''\${base_file}'\''i; echo \$dlname'\''`~ + dldir=$destdir/`dirname \$dlpath`~ + test -d \$dldir || mkdir -p \$dldir~ + $install_prog $dir/$dlname \$dldir/$dlname' + postuninstall_cmds='dldll=`$SHELL 2>&1 -c '\''. $file; echo \$dlname'\''`~ + dlpath=$dir/\$dldll~ + $RM \$dlpath' + shlibpath_overrides_runpath=yes + dynamic_linker='Win32 link.exe' ;; *) + # Assume MSVC wrapper library_names_spec='${libname}`echo ${release} | $SED -e 's/[[.]]/-/g'`${versuffix}${shared_ext} $libname.lib' + dynamic_linker='Win32 ld.exe' ;; esac - dynamic_linker='Win32 ld.exe' # FIXME: first we should search . and the directory the executable is in shlibpath_var=PATH ;; @@ -2278,7 +2460,7 @@ m4_if([$1], [],[ ;; dgux*) - version_type=linux + version_type=linux # correct to gnu/linux during the next big refactor need_lib_prefix=no need_version=no library_names_spec='${libname}${release}${shared_ext}$versuffix ${libname}${release}${shared_ext}$major $libname$shared_ext' @@ -2286,10 +2468,6 @@ dgux*) shlibpath_var=LD_LIBRARY_PATH ;; -freebsd1*) - dynamic_linker=no - ;; - freebsd* | dragonfly*) # DragonFly does not have aout. When/if they implement a new # versioning mechanism, adjust this. @@ -2297,7 +2475,7 @@ freebsd* | dragonfly*) objformat=`/usr/bin/objformat` else case $host_os in - freebsd[[123]]*) objformat=aout ;; + freebsd[[23]].*) objformat=aout ;; *) objformat=elf ;; esac fi @@ -2315,7 +2493,7 @@ freebsd* | dragonfly*) esac shlibpath_var=LD_LIBRARY_PATH case $host_os in - freebsd2*) + freebsd2.*) shlibpath_overrides_runpath=yes ;; freebsd3.[[01]]* | freebsdelf3.[[01]]*) @@ -2334,13 +2512,16 @@ freebsd* | dragonfly*) esac ;; -gnu*) - version_type=linux +haiku*) + version_type=linux # correct to gnu/linux during the next big refactor need_lib_prefix=no need_version=no + dynamic_linker="$host_os runtime_loader" library_names_spec='${libname}${release}${shared_ext}$versuffix ${libname}${release}${shared_ext}${major} ${libname}${shared_ext}' soname_spec='${libname}${release}${shared_ext}$major' - shlibpath_var=LD_LIBRARY_PATH + shlibpath_var=LIBRARY_PATH + shlibpath_overrides_runpath=yes + sys_lib_dlsearch_path_spec='/boot/home/config/lib /boot/common/lib /boot/system/lib' hardcode_into_libs=yes ;; @@ -2386,12 +2567,14 @@ hpux9* | hpux10* | hpux11*) soname_spec='${libname}${release}${shared_ext}$major' ;; esac - # HP-UX runs *really* slowly unless shared libraries are mode 555. + # HP-UX runs *really* slowly unless shared libraries are mode 555, ... postinstall_cmds='chmod 555 $lib' + # or fails outright, so override atomically: + install_override_mode=555 ;; interix[[3-9]]*) - version_type=linux + version_type=linux # correct to gnu/linux during the next big refactor need_lib_prefix=no need_version=no library_names_spec='${libname}${release}${shared_ext}$versuffix ${libname}${release}${shared_ext}$major ${libname}${shared_ext}' @@ -2407,7 +2590,7 @@ irix5* | irix6* | nonstopux*) nonstopux*) version_type=nonstopux ;; *) if test "$lt_cv_prog_gnu_ld" = yes; then - version_type=linux + version_type=linux # correct to gnu/linux during the next big refactor else version_type=irix fi ;; @@ -2444,9 +2627,9 @@ linux*oldld* | linux*aout* | linux*coff*) dynamic_linker=no ;; -# This must be Linux ELF. -linux* | k*bsd*-gnu | kopensolaris*-gnu) - version_type=linux +# This must be glibc/ELF. +linux* | k*bsd*-gnu | kopensolaris*-gnu | gnu*) + version_type=linux # correct to gnu/linux during the next big refactor need_lib_prefix=no need_version=no library_names_spec='${libname}${release}${shared_ext}$versuffix ${libname}${release}${shared_ext}$major $libname${shared_ext}' @@ -2454,16 +2637,21 @@ linux* | k*bsd*-gnu | kopensolaris*-gnu) finish_cmds='PATH="\$PATH:/sbin" ldconfig -n $libdir' shlibpath_var=LD_LIBRARY_PATH shlibpath_overrides_runpath=no + # Some binutils ld are patched to set DT_RUNPATH - save_LDFLAGS=$LDFLAGS - save_libdir=$libdir - eval "libdir=/foo; wl=\"$_LT_TAGVAR(lt_prog_compiler_wl, $1)\"; \ - LDFLAGS=\"\$LDFLAGS $_LT_TAGVAR(hardcode_libdir_flag_spec, $1)\"" - AC_LINK_IFELSE([AC_LANG_PROGRAM([],[])], - [AS_IF([ ($OBJDUMP -p conftest$ac_exeext) 2>/dev/null | grep "RUNPATH.*$libdir" >/dev/null], - [shlibpath_overrides_runpath=yes])]) - LDFLAGS=$save_LDFLAGS - libdir=$save_libdir + AC_CACHE_VAL([lt_cv_shlibpath_overrides_runpath], + [lt_cv_shlibpath_overrides_runpath=no + save_LDFLAGS=$LDFLAGS + save_libdir=$libdir + eval "libdir=/foo; wl=\"$_LT_TAGVAR(lt_prog_compiler_wl, $1)\"; \ + LDFLAGS=\"\$LDFLAGS $_LT_TAGVAR(hardcode_libdir_flag_spec, $1)\"" + AC_LINK_IFELSE([AC_LANG_PROGRAM([],[])], + [AS_IF([ ($OBJDUMP -p conftest$ac_exeext) 2>/dev/null | grep "RUNPATH.*$libdir" >/dev/null], + [lt_cv_shlibpath_overrides_runpath=yes])]) + LDFLAGS=$save_LDFLAGS + libdir=$save_libdir + ]) + shlibpath_overrides_runpath=$lt_cv_shlibpath_overrides_runpath # This implies no fast_install, which is unacceptable. # Some rework will be needed to allow for fast_install @@ -2472,7 +2660,7 @@ linux* | k*bsd*-gnu | kopensolaris*-gnu) # Append ld.so.conf contents to the search path if test -f /etc/ld.so.conf; then - lt_ld_extra=`awk '/^include / { system(sprintf("cd /etc; cat %s 2>/dev/null", \[$]2)); skip = 1; } { if (!skip) print \[$]0; skip = 0; }' < /etc/ld.so.conf | $SED -e 's/#.*//;/^[ ]*hwcap[ ]/d;s/[:, ]/ /g;s/=[^=]*$//;s/=[^= ]* / /g;/^$/d' | tr '\n' ' '` + lt_ld_extra=`awk '/^include / { system(sprintf("cd /etc; cat %s 2>/dev/null", \[$]2)); skip = 1; } { if (!skip) print \[$]0; skip = 0; }' < /etc/ld.so.conf | $SED -e 's/#.*//;/^[ ]*hwcap[ ]/d;s/[:, ]/ /g;s/=[^=]*$//;s/=[^= ]* / /g;s/"//g;/^$/d' | tr '\n' ' '` sys_lib_dlsearch_path_spec="/lib /usr/lib $lt_ld_extra" fi @@ -2516,7 +2704,7 @@ netbsd*) ;; newsos6) - version_type=linux + version_type=linux # correct to gnu/linux during the next big refactor library_names_spec='${libname}${release}${shared_ext}$versuffix ${libname}${release}${shared_ext}$major $libname${shared_ext}' shlibpath_var=LD_LIBRARY_PATH shlibpath_overrides_runpath=yes @@ -2585,7 +2773,7 @@ rdos*) ;; solaris*) - version_type=linux + version_type=linux # correct to gnu/linux during the next big refactor need_lib_prefix=no need_version=no library_names_spec='${libname}${release}${shared_ext}$versuffix ${libname}${release}${shared_ext}$major $libname${shared_ext}' @@ -2610,7 +2798,7 @@ sunos4*) ;; sysv4 | sysv4.3*) - version_type=linux + version_type=linux # correct to gnu/linux during the next big refactor library_names_spec='${libname}${release}${shared_ext}$versuffix ${libname}${release}${shared_ext}$major $libname${shared_ext}' soname_spec='${libname}${release}${shared_ext}$major' shlibpath_var=LD_LIBRARY_PATH @@ -2634,7 +2822,7 @@ sysv4 | sysv4.3*) sysv4*MP*) if test -d /usr/nec ;then - version_type=linux + version_type=linux # correct to gnu/linux during the next big refactor library_names_spec='$libname${shared_ext}.$versuffix $libname${shared_ext}.$major $libname${shared_ext}' soname_spec='$libname${shared_ext}.$major' shlibpath_var=LD_LIBRARY_PATH @@ -2665,7 +2853,7 @@ sysv5* | sco3.2v5* | sco5v6* | unixware* | OpenUNIX* | sysv4*uw2*) tpf*) # TPF is a cross-target only. Preferred cross-host = GNU/Linux. - version_type=linux + version_type=linux # correct to gnu/linux during the next big refactor need_lib_prefix=no need_version=no library_names_spec='${libname}${release}${shared_ext}$versuffix ${libname}${release}${shared_ext}$major $libname${shared_ext}' @@ -2675,7 +2863,7 @@ tpf*) ;; uts4*) - version_type=linux + version_type=linux # correct to gnu/linux during the next big refactor library_names_spec='${libname}${release}${shared_ext}$versuffix ${libname}${release}${shared_ext}$major $libname${shared_ext}' soname_spec='${libname}${release}${shared_ext}$major' shlibpath_var=LD_LIBRARY_PATH @@ -2717,6 +2905,8 @@ _LT_DECL([], [library_names_spec], [1], The last name is the one that the linker finds with -lNAME]]) _LT_DECL([], [soname_spec], [1], [[The coded name of the library, if different from the real name]]) +_LT_DECL([], [install_override_mode], [1], + [Permission mode override for installation of shared libraries]) _LT_DECL([], [postinstall_cmds], [2], [Command to use after installation of a shared archive]) _LT_DECL([], [postuninstall_cmds], [2], @@ -2829,6 +3019,7 @@ AC_REQUIRE([AC_CANONICAL_HOST])dnl AC_REQUIRE([AC_CANONICAL_BUILD])dnl m4_require([_LT_DECL_SED])dnl m4_require([_LT_DECL_EGREP])dnl +m4_require([_LT_PROG_ECHO_BACKSLASH])dnl AC_ARG_WITH([gnu-ld], [AS_HELP_STRING([--with-gnu-ld], @@ -2950,6 +3141,11 @@ case $reload_flag in esac reload_cmds='$LD$reload_flag -o $output$reload_objs' case $host_os in + cygwin* | mingw* | pw32* | cegcc*) + if test "$GCC" != yes; then + reload_cmds=false + fi + ;; darwin*) if test "$GCC" = yes; then reload_cmds='$LTCC $LTCFLAGS -nostdlib ${wl}-r -o $output$reload_objs' @@ -2958,8 +3154,8 @@ case $host_os in fi ;; esac -_LT_DECL([], [reload_flag], [1], [How to create reloadable object files])dnl -_LT_DECL([], [reload_cmds], [2])dnl +_LT_TAGDECL([], [reload_flag], [1], [How to create reloadable object files])dnl +_LT_TAGDECL([], [reload_cmds], [2])dnl ])# _LT_CMD_RELOAD @@ -3011,16 +3207,18 @@ mingw* | pw32*) # Base MSYS/MinGW do not provide the 'file' command needed by # func_win32_libid shell function, so use a weaker test based on 'objdump', # unless we find 'file', for example because we are cross-compiling. - if ( file / ) >/dev/null 2>&1; then + # func_win32_libid assumes BSD nm, so disallow it if using MS dumpbin. + if ( test "$lt_cv_nm_interface" = "BSD nm" && file / ) >/dev/null 2>&1; then lt_cv_deplibs_check_method='file_magic ^x86 archive import|^x86 DLL' lt_cv_file_magic_cmd='func_win32_libid' else - lt_cv_deplibs_check_method='file_magic file format pei*-i386(.*architecture: i386)?' + # Keep this pattern in sync with the one in func_win32_libid. + lt_cv_deplibs_check_method='file_magic file format (pei*-i386(.*architecture: i386)?|pe-arm-wince|pe-x86-64)' lt_cv_file_magic_cmd='$OBJDUMP -f' fi ;; -cegcc) +cegcc*) # use the weaker test based on 'objdump'. See mingw*. lt_cv_deplibs_check_method='file_magic file format pe-arm-.*little(.*architecture: arm)?' lt_cv_file_magic_cmd='$OBJDUMP -f' @@ -3046,7 +3244,7 @@ freebsd* | dragonfly*) fi ;; -gnu*) +haiku*) lt_cv_deplibs_check_method=pass_all ;; @@ -3058,11 +3256,11 @@ hpux10.20* | hpux11*) lt_cv_file_magic_test_file=/usr/lib/hpux32/libc.so ;; hppa*64*) - [lt_cv_deplibs_check_method='file_magic (s[0-9][0-9][0-9]|ELF-[0-9][0-9]) shared object file - PA-RISC [0-9].[0-9]'] + [lt_cv_deplibs_check_method='file_magic (s[0-9][0-9][0-9]|ELF[ -][0-9][0-9])(-bit)?( [LM]SB)? shared object( file)?[, -]* PA-RISC [0-9]\.[0-9]'] lt_cv_file_magic_test_file=/usr/lib/pa20_64/libc.sl ;; *) - lt_cv_deplibs_check_method='file_magic (s[[0-9]][[0-9]][[0-9]]|PA-RISC[[0-9]].[[0-9]]) shared library' + lt_cv_deplibs_check_method='file_magic (s[[0-9]][[0-9]][[0-9]]|PA-RISC[[0-9]]\.[[0-9]]) shared library' lt_cv_file_magic_test_file=/usr/lib/libc.sl ;; esac @@ -3083,8 +3281,8 @@ irix5* | irix6* | nonstopux*) lt_cv_deplibs_check_method=pass_all ;; -# This must be Linux ELF. -linux* | k*bsd*-gnu | kopensolaris*-gnu) +# This must be glibc/ELF. +linux* | k*bsd*-gnu | kopensolaris*-gnu | gnu*) lt_cv_deplibs_check_method=pass_all ;; @@ -3162,6 +3360,21 @@ tpf*) ;; esac ]) + +file_magic_glob= +want_nocaseglob=no +if test "$build" = "$host"; then + case $host_os in + mingw* | pw32*) + if ( shopt | grep nocaseglob ) >/dev/null 2>&1; then + want_nocaseglob=yes + else + file_magic_glob=`echo aAbBcCdDeEfFgGhHiIjJkKlLmMnNoOpPqQrRsStTuUvVwWxXyYzZ | $SED -e "s/\(..\)/s\/[[\1]]\/[[\1]]\/g;/g"` + fi + ;; + esac +fi + file_magic_cmd=$lt_cv_file_magic_cmd deplibs_check_method=$lt_cv_deplibs_check_method test -z "$deplibs_check_method" && deplibs_check_method=unknown @@ -3169,7 +3382,11 @@ test -z "$deplibs_check_method" && deplibs_check_method=unknown _LT_DECL([], [deplibs_check_method], [1], [Method to check whether dependent libraries are shared objects]) _LT_DECL([], [file_magic_cmd], [1], - [Command to use when deplibs_check_method == "file_magic"]) + [Command to use when deplibs_check_method = "file_magic"]) +_LT_DECL([], [file_magic_glob], [1], + [How to find potential files when deplibs_check_method = "file_magic"]) +_LT_DECL([], [want_nocaseglob], [1], + [Find potential files using nocaseglob when deplibs_check_method = "file_magic"]) ])# _LT_CHECK_MAGIC_METHOD @@ -3226,7 +3443,19 @@ if test "$lt_cv_path_NM" != "no"; then NM="$lt_cv_path_NM" else # Didn't find any BSD compatible name lister, look for dumpbin. - AC_CHECK_TOOLS(DUMPBIN, ["dumpbin -symbols" "link -dump -symbols"], :) + if test -n "$DUMPBIN"; then : + # Let the user override the test. + else + AC_CHECK_TOOLS(DUMPBIN, [dumpbin "link -dump"], :) + case `$DUMPBIN -symbols /dev/null 2>&1 | sed '1q'` in + *COFF*) + DUMPBIN="$DUMPBIN -symbols" + ;; + *) + DUMPBIN=: + ;; + esac + fi AC_SUBST([DUMPBIN]) if test "$DUMPBIN" != ":"; then NM="$DUMPBIN" @@ -3239,13 +3468,13 @@ _LT_DECL([], [NM], [1], [A BSD- or MS-compatible name lister])dnl AC_CACHE_CHECK([the name lister ($NM) interface], [lt_cv_nm_interface], [lt_cv_nm_interface="BSD nm" echo "int some_variable = 0;" > conftest.$ac_ext - (eval echo "\"\$as_me:__oline__: $ac_compile\"" >&AS_MESSAGE_LOG_FD) + (eval echo "\"\$as_me:$LINENO: $ac_compile\"" >&AS_MESSAGE_LOG_FD) (eval "$ac_compile" 2>conftest.err) cat conftest.err >&AS_MESSAGE_LOG_FD - (eval echo "\"\$as_me:__oline__: $NM \\\"conftest.$ac_objext\\\"\"" >&AS_MESSAGE_LOG_FD) + (eval echo "\"\$as_me:$LINENO: $NM \\\"conftest.$ac_objext\\\"\"" >&AS_MESSAGE_LOG_FD) (eval "$NM \"conftest.$ac_objext\"" 2>conftest.err > conftest.out) cat conftest.err >&AS_MESSAGE_LOG_FD - (eval echo "\"\$as_me:__oline__: output\"" >&AS_MESSAGE_LOG_FD) + (eval echo "\"\$as_me:$LINENO: output\"" >&AS_MESSAGE_LOG_FD) cat conftest.out >&AS_MESSAGE_LOG_FD if $GREP 'External.*some_variable' conftest.out > /dev/null; then lt_cv_nm_interface="MS dumpbin" @@ -3260,15 +3489,76 @@ dnl aclocal-1.4 backwards compatibility: dnl AC_DEFUN([AM_PROG_NM], []) dnl AC_DEFUN([AC_PROG_NM], []) +# _LT_CHECK_SHAREDLIB_FROM_LINKLIB +# -------------------------------- +# how to determine the name of the shared library +# associated with a specific link library. +# -- PORTME fill in with the dynamic library characteristics +m4_defun([_LT_CHECK_SHAREDLIB_FROM_LINKLIB], +[m4_require([_LT_DECL_EGREP]) +m4_require([_LT_DECL_OBJDUMP]) +m4_require([_LT_DECL_DLLTOOL]) +AC_CACHE_CHECK([how to associate runtime and link libraries], +lt_cv_sharedlib_from_linklib_cmd, +[lt_cv_sharedlib_from_linklib_cmd='unknown' -# LT_LIB_M -# -------- +case $host_os in +cygwin* | mingw* | pw32* | cegcc*) + # two different shell functions defined in ltmain.sh + # decide which to use based on capabilities of $DLLTOOL + case `$DLLTOOL --help 2>&1` in + *--identify-strict*) + lt_cv_sharedlib_from_linklib_cmd=func_cygming_dll_for_implib + ;; + *) + lt_cv_sharedlib_from_linklib_cmd=func_cygming_dll_for_implib_fallback + ;; + esac + ;; +*) + # fallback: assume linklib IS sharedlib + lt_cv_sharedlib_from_linklib_cmd="$ECHO" + ;; +esac +]) +sharedlib_from_linklib_cmd=$lt_cv_sharedlib_from_linklib_cmd +test -z "$sharedlib_from_linklib_cmd" && sharedlib_from_linklib_cmd=$ECHO + +_LT_DECL([], [sharedlib_from_linklib_cmd], [1], + [Command to associate shared and link libraries]) +])# _LT_CHECK_SHAREDLIB_FROM_LINKLIB + + +# _LT_PATH_MANIFEST_TOOL +# ---------------------- +# locate the manifest tool +m4_defun([_LT_PATH_MANIFEST_TOOL], +[AC_CHECK_TOOL(MANIFEST_TOOL, mt, :) +test -z "$MANIFEST_TOOL" && MANIFEST_TOOL=mt +AC_CACHE_CHECK([if $MANIFEST_TOOL is a manifest tool], [lt_cv_path_mainfest_tool], + [lt_cv_path_mainfest_tool=no + echo "$as_me:$LINENO: $MANIFEST_TOOL '-?'" >&AS_MESSAGE_LOG_FD + $MANIFEST_TOOL '-?' 2>conftest.err > conftest.out + cat conftest.err >&AS_MESSAGE_LOG_FD + if $GREP 'Manifest Tool' conftest.out > /dev/null; then + lt_cv_path_mainfest_tool=yes + fi + rm -f conftest*]) +if test "x$lt_cv_path_mainfest_tool" != xyes; then + MANIFEST_TOOL=: +fi +_LT_DECL([], [MANIFEST_TOOL], [1], [Manifest tool])dnl +])# _LT_PATH_MANIFEST_TOOL + + +# LT_LIB_M +# -------- # check for math library AC_DEFUN([LT_LIB_M], [AC_REQUIRE([AC_CANONICAL_HOST])dnl LIBM= case $host in -*-*-beos* | *-*-cygwin* | *-*-pw32* | *-*-darwin*) +*-*-beos* | *-*-cegcc* | *-*-cygwin* | *-*-haiku* | *-*-pw32* | *-*-darwin*) # These system don't have libm, or don't need it ;; *-ncr-sysv4.3*) @@ -3296,7 +3586,12 @@ m4_defun([_LT_COMPILER_NO_RTTI], _LT_TAGVAR(lt_prog_compiler_no_builtin_flag, $1)= if test "$GCC" = yes; then - _LT_TAGVAR(lt_prog_compiler_no_builtin_flag, $1)=' -fno-builtin' + case $cc_basename in + nvcc*) + _LT_TAGVAR(lt_prog_compiler_no_builtin_flag, $1)=' -Xcompiler -fno-builtin' ;; + *) + _LT_TAGVAR(lt_prog_compiler_no_builtin_flag, $1)=' -fno-builtin' ;; + esac _LT_COMPILER_OPTION([if $compiler supports -fno-rtti -fno-exceptions], lt_cv_prog_compiler_rtti_exceptions, @@ -3313,6 +3608,7 @@ _LT_TAGDECL([no_builtin_flag], [lt_prog_compiler_no_builtin_flag], [1], m4_defun([_LT_CMD_GLOBAL_SYMBOLS], [AC_REQUIRE([AC_CANONICAL_HOST])dnl AC_REQUIRE([AC_PROG_CC])dnl +AC_REQUIRE([AC_PROG_AWK])dnl AC_REQUIRE([LT_PATH_NM])dnl AC_REQUIRE([LT_PATH_LD])dnl m4_require([_LT_DECL_SED])dnl @@ -3380,8 +3676,8 @@ esac lt_cv_sys_global_symbol_to_cdecl="sed -n -e 's/^T .* \(.*\)$/extern int \1();/p' -e 's/^$symcode* .* \(.*\)$/extern char \1;/p'" # Transform an extracted symbol line into symbol name and symbol address -lt_cv_sys_global_symbol_to_c_name_address="sed -n -e 's/^: \([[^ ]]*\) $/ {\\\"\1\\\", (void *) 0},/p' -e 's/^$symcode* \([[^ ]]*\) \([[^ ]]*\)$/ {\"\2\", (void *) \&\2},/p'" -lt_cv_sys_global_symbol_to_c_name_address_lib_prefix="sed -n -e 's/^: \([[^ ]]*\) $/ {\\\"\1\\\", (void *) 0},/p' -e 's/^$symcode* \([[^ ]]*\) \(lib[[^ ]]*\)$/ {\"\2\", (void *) \&\2},/p' -e 's/^$symcode* \([[^ ]]*\) \([[^ ]]*\)$/ {\"lib\2\", (void *) \&\2},/p'" +lt_cv_sys_global_symbol_to_c_name_address="sed -n -e 's/^: \([[^ ]]*\)[[ ]]*$/ {\\\"\1\\\", (void *) 0},/p' -e 's/^$symcode* \([[^ ]]*\) \([[^ ]]*\)$/ {\"\2\", (void *) \&\2},/p'" +lt_cv_sys_global_symbol_to_c_name_address_lib_prefix="sed -n -e 's/^: \([[^ ]]*\)[[ ]]*$/ {\\\"\1\\\", (void *) 0},/p' -e 's/^$symcode* \([[^ ]]*\) \(lib[[^ ]]*\)$/ {\"\2\", (void *) \&\2},/p' -e 's/^$symcode* \([[^ ]]*\) \([[^ ]]*\)$/ {\"lib\2\", (void *) \&\2},/p'" # Handle CRLF in mingw tool chain opt_cr= @@ -3405,6 +3701,7 @@ for ac_symprfx in "" "_"; do # which start with @ or ?. lt_cv_sys_global_symbol_pipe="$AWK ['"\ " {last_section=section; section=\$ 3};"\ +" /^COFF SYMBOL TABLE/{for(i in hide) delete hide[i]};"\ " /Section length .*#relocs.*(pick any)/{hide[last_section]=1};"\ " \$ 0!~/External *\|/{next};"\ " / 0+ UNDEF /{next}; / UNDEF \([^|]\)*()/{next};"\ @@ -3417,6 +3714,7 @@ for ac_symprfx in "" "_"; do else lt_cv_sys_global_symbol_pipe="sed -n -e 's/^.*[[ ]]\($symcode$symcode*\)[[ ]][[ ]]*$ac_symprfx$sympat$opt_cr$/$symxfrm/p'" fi + lt_cv_sys_global_symbol_pipe="$lt_cv_sys_global_symbol_pipe | sed '/ __gnu_lto/d'" # Check to see that the pipe works correctly. pipe_works=no @@ -3438,7 +3736,7 @@ _LT_EOF if AC_TRY_EVAL(ac_compile); then # Now try to grab the symbols. nlist=conftest.nm - if AC_TRY_EVAL(NM conftest.$ac_objext \| $lt_cv_sys_global_symbol_pipe \> $nlist) && test -s "$nlist"; then + if AC_TRY_EVAL(NM conftest.$ac_objext \| "$lt_cv_sys_global_symbol_pipe" \> $nlist) && test -s "$nlist"; then # Try sorting and uniquifying the output. if sort "$nlist" | uniq > "$nlist"T; then mv -f "$nlist"T "$nlist" @@ -3450,6 +3748,18 @@ _LT_EOF if $GREP ' nm_test_var$' "$nlist" >/dev/null; then if $GREP ' nm_test_func$' "$nlist" >/dev/null; then cat <<_LT_EOF > conftest.$ac_ext +/* Keep this code in sync between libtool.m4, ltmain, lt_system.h, and tests. */ +#if defined(_WIN32) || defined(__CYGWIN__) || defined(_WIN32_WCE) +/* DATA imports from DLLs on WIN32 con't be const, because runtime + relocations are performed -- see ld's documentation on pseudo-relocs. */ +# define LT@&t@_DLSYM_CONST +#elif defined(__osf__) +/* This system does not cope well with relocations in const data. */ +# define LT@&t@_DLSYM_CONST +#else +# define LT@&t@_DLSYM_CONST const +#endif + #ifdef __cplusplus extern "C" { #endif @@ -3461,7 +3771,7 @@ _LT_EOF cat <<_LT_EOF >> conftest.$ac_ext /* The mapping between symbol names and symbols. */ -const struct { +LT@&t@_DLSYM_CONST struct { const char *name; void *address; } @@ -3487,15 +3797,15 @@ static const void *lt_preloaded_setup() { _LT_EOF # Now try linking the two files. mv conftest.$ac_objext conftstm.$ac_objext - lt_save_LIBS="$LIBS" - lt_save_CFLAGS="$CFLAGS" + lt_globsym_save_LIBS=$LIBS + lt_globsym_save_CFLAGS=$CFLAGS LIBS="conftstm.$ac_objext" CFLAGS="$CFLAGS$_LT_TAGVAR(lt_prog_compiler_no_builtin_flag, $1)" if AC_TRY_EVAL(ac_link) && test -s conftest${ac_exeext}; then pipe_works=yes fi - LIBS="$lt_save_LIBS" - CFLAGS="$lt_save_CFLAGS" + LIBS=$lt_globsym_save_LIBS + CFLAGS=$lt_globsym_save_CFLAGS else echo "cannot find nm_test_func in $nlist" >&AS_MESSAGE_LOG_FD fi @@ -3528,6 +3838,13 @@ else AC_MSG_RESULT(ok) fi +# Response file support. +if test "$lt_cv_nm_interface" = "MS dumpbin"; then + nm_file_list_spec='@' +elif $NM --help 2>/dev/null | grep '[[@]]FILE' >/dev/null; then + nm_file_list_spec='@' +fi + _LT_DECL([global_symbol_pipe], [lt_cv_sys_global_symbol_pipe], [1], [Take the output of nm and produce a listing of raw symbols and C names]) _LT_DECL([global_symbol_to_cdecl], [lt_cv_sys_global_symbol_to_cdecl], [1], @@ -3538,6 +3855,8 @@ _LT_DECL([global_symbol_to_c_name_address], _LT_DECL([global_symbol_to_c_name_address_lib_prefix], [lt_cv_sys_global_symbol_to_c_name_address_lib_prefix], [1], [Transform the output of nm in a C name address pair when lib prefix is needed]) +_LT_DECL([], [nm_file_list_spec], [1], + [Specify filename containing input files for $NM]) ]) # _LT_CMD_GLOBAL_SYMBOLS @@ -3549,7 +3868,6 @@ _LT_TAGVAR(lt_prog_compiler_wl, $1)= _LT_TAGVAR(lt_prog_compiler_pic, $1)= _LT_TAGVAR(lt_prog_compiler_static, $1)= -AC_MSG_CHECKING([for $compiler option to produce PIC]) m4_if([$1], [CXX], [ # C++ specific cases for pic, static, wl, etc. if test "$GXX" = yes; then @@ -3600,6 +3918,11 @@ m4_if([$1], [CXX], [ # DJGPP does not support shared libraries at all _LT_TAGVAR(lt_prog_compiler_pic, $1)= ;; + haiku*) + # PIC is the default for Haiku. + # The "-static" flag exists, but is broken. + _LT_TAGVAR(lt_prog_compiler_static, $1)= + ;; interix[[3-9]]*) # Interix 3.x gcc -fpic/-fPIC options generate broken code. # Instead, we relocate shared libraries at runtime. @@ -3649,6 +3972,12 @@ m4_if([$1], [CXX], [ ;; esac ;; + mingw* | cygwin* | os2* | pw32* | cegcc*) + # This hack is so that the source file can tell whether it is being + # built for inclusion in a dll (and should export symbols for example). + m4_if([$1], [GCJ], [], + [_LT_TAGVAR(lt_prog_compiler_pic, $1)='-DDLL_EXPORT']) + ;; dgux*) case $cc_basename in ec++*) @@ -3705,7 +4034,7 @@ m4_if([$1], [CXX], [ ;; esac ;; - linux* | k*bsd*-gnu | kopensolaris*-gnu) + linux* | k*bsd*-gnu | kopensolaris*-gnu | gnu*) case $cc_basename in KCC*) # KAI C++ Compiler @@ -3738,8 +4067,8 @@ m4_if([$1], [CXX], [ _LT_TAGVAR(lt_prog_compiler_pic, $1)= _LT_TAGVAR(lt_prog_compiler_static, $1)='-non_shared' ;; - xlc* | xlC*) - # IBM XL 8.0 on PPC + xlc* | xlC* | bgxl[[cC]]* | mpixl[[cC]]*) + # IBM XL 8.0, 9.0 on PPC and BlueGene _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' _LT_TAGVAR(lt_prog_compiler_pic, $1)='-qpic' _LT_TAGVAR(lt_prog_compiler_static, $1)='-qstaticlink' @@ -3801,7 +4130,7 @@ m4_if([$1], [CXX], [ ;; solaris*) case $cc_basename in - CC*) + CC* | sunCC*) # Sun C++ 4.2, 5.x and Centerline C++ _LT_TAGVAR(lt_prog_compiler_pic, $1)='-KPIC' _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic' @@ -3905,6 +4234,12 @@ m4_if([$1], [CXX], [ _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fno-common' ;; + haiku*) + # PIC is the default for Haiku. + # The "-static" flag exists, but is broken. + _LT_TAGVAR(lt_prog_compiler_static, $1)= + ;; + hpux*) # PIC is the default for 64-bit PA HP-UX, but not for 32-bit # PA HP-UX. On IA64 HP-UX, PIC is the default but the pic flag @@ -3947,6 +4282,15 @@ m4_if([$1], [CXX], [ _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fPIC' ;; esac + + case $cc_basename in + nvcc*) # Cuda Compiler Driver 2.2 + _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Xlinker ' + if test -n "$_LT_TAGVAR(lt_prog_compiler_pic, $1)"; then + _LT_TAGVAR(lt_prog_compiler_pic, $1)="-Xcompiler $_LT_TAGVAR(lt_prog_compiler_pic, $1)" + fi + ;; + esac else # PORTME Check for flag to pass linker flags through the system compiler. case $host_os in @@ -3989,7 +4333,7 @@ m4_if([$1], [CXX], [ _LT_TAGVAR(lt_prog_compiler_static, $1)='-non_shared' ;; - linux* | k*bsd*-gnu | kopensolaris*-gnu) + linux* | k*bsd*-gnu | kopensolaris*-gnu | gnu*) case $cc_basename in # old Intel for x86_64 which still supported -KPIC. ecc*) @@ -4010,7 +4354,13 @@ m4_if([$1], [CXX], [ _LT_TAGVAR(lt_prog_compiler_pic, $1)='--shared' _LT_TAGVAR(lt_prog_compiler_static, $1)='--static' ;; - pgcc* | pgf77* | pgf90* | pgf95*) + nagfor*) + # NAG Fortran compiler + _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,-Wl,,' + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-PIC' + _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic' + ;; + pgcc* | pgf77* | pgf90* | pgf95* | pgfortran*) # Portland Group compilers (*not* the Pentium gcc compiler, # which looks to be a dead project) _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' @@ -4022,25 +4372,40 @@ m4_if([$1], [CXX], [ # All Alpha code is PIC. _LT_TAGVAR(lt_prog_compiler_static, $1)='-non_shared' ;; - xl*) - # IBM XL C 8.0/Fortran 10.1 on PPC + xl* | bgxl* | bgf* | mpixl*) + # IBM XL C 8.0/Fortran 10.1, 11.1 on PPC and BlueGene _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' _LT_TAGVAR(lt_prog_compiler_pic, $1)='-qpic' _LT_TAGVAR(lt_prog_compiler_static, $1)='-qstaticlink' ;; *) case `$CC -V 2>&1 | sed 5q` in + *Sun\ Ceres\ Fortran* | *Sun*Fortran*\ [[1-7]].* | *Sun*Fortran*\ 8.[[0-3]]*) + # Sun Fortran 8.3 passes all unrecognized flags to the linker + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-KPIC' + _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic' + _LT_TAGVAR(lt_prog_compiler_wl, $1)='' + ;; + *Sun\ F* | *Sun*Fortran*) + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-KPIC' + _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic' + _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Qoption ld ' + ;; *Sun\ C*) # Sun C 5.9 _LT_TAGVAR(lt_prog_compiler_pic, $1)='-KPIC' _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic' _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' ;; - *Sun\ F*) - # Sun Fortran 8.3 passes all unrecognized flags to the linker - _LT_TAGVAR(lt_prog_compiler_pic, $1)='-KPIC' + *Intel*\ [[CF]]*Compiler*) + _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fPIC' + _LT_TAGVAR(lt_prog_compiler_static, $1)='-static' + ;; + *Portland\ Group*) + _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fpic' _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic' - _LT_TAGVAR(lt_prog_compiler_wl, $1)='' ;; esac ;; @@ -4072,7 +4437,7 @@ m4_if([$1], [CXX], [ _LT_TAGVAR(lt_prog_compiler_pic, $1)='-KPIC' _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic' case $cc_basename in - f77* | f90* | f95*) + f77* | f90* | f95* | sunf77* | sunf90* | sunf95*) _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Qoption ld ';; *) _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,';; @@ -4129,9 +4494,11 @@ case $host_os in _LT_TAGVAR(lt_prog_compiler_pic, $1)="$_LT_TAGVAR(lt_prog_compiler_pic, $1)@&t@m4_if([$1],[],[ -DPIC],[m4_if([$1],[CXX],[ -DPIC],[])])" ;; esac -AC_MSG_RESULT([$_LT_TAGVAR(lt_prog_compiler_pic, $1)]) -_LT_TAGDECL([wl], [lt_prog_compiler_wl], [1], - [How to pass a linker flag through the compiler]) + +AC_CACHE_CHECK([for $compiler option to produce PIC], + [_LT_TAGVAR(lt_cv_prog_compiler_pic, $1)], + [_LT_TAGVAR(lt_cv_prog_compiler_pic, $1)=$_LT_TAGVAR(lt_prog_compiler_pic, $1)]) +_LT_TAGVAR(lt_prog_compiler_pic, $1)=$_LT_TAGVAR(lt_cv_prog_compiler_pic, $1) # # Check to make sure the PIC flag actually works. @@ -4150,6 +4517,8 @@ fi _LT_TAGDECL([pic_flag], [lt_prog_compiler_pic], [1], [Additional compiler flags for building library objects]) +_LT_TAGDECL([wl], [lt_prog_compiler_wl], [1], + [How to pass a linker flag through the compiler]) # # Check to make sure the static flag actually works. # @@ -4170,6 +4539,7 @@ _LT_TAGDECL([link_static_flag], [lt_prog_compiler_static], [1], m4_defun([_LT_LINKER_SHLIBS], [AC_REQUIRE([LT_PATH_LD])dnl AC_REQUIRE([LT_PATH_NM])dnl +m4_require([_LT_PATH_MANIFEST_TOOL])dnl m4_require([_LT_FILEUTILS_DEFAULTS])dnl m4_require([_LT_DECL_EGREP])dnl m4_require([_LT_DECL_SED])dnl @@ -4178,30 +4548,40 @@ m4_require([_LT_TAG_COMPILER])dnl AC_MSG_CHECKING([whether the $compiler linker ($LD) supports shared libraries]) m4_if([$1], [CXX], [ _LT_TAGVAR(export_symbols_cmds, $1)='$NM $libobjs $convenience | $global_symbol_pipe | $SED '\''s/.* //'\'' | sort | uniq > $export_symbols' + _LT_TAGVAR(exclude_expsyms, $1)=['_GLOBAL_OFFSET_TABLE_|_GLOBAL__F[ID]_.*'] case $host_os in aix[[4-9]]*) # If we're using GNU nm, then we don't want the "-C" option. # -C means demangle to AIX nm, but means don't demangle with GNU nm + # Also, AIX nm treats weak defined symbols like other global defined + # symbols, whereas GNU nm marks them as "W". if $NM -V 2>&1 | $GREP 'GNU' > /dev/null; then - _LT_TAGVAR(export_symbols_cmds, $1)='$NM -Bpg $libobjs $convenience | awk '\''{ if (((\$ 2 == "T") || (\$ 2 == "D") || (\$ 2 == "B")) && ([substr](\$ 3,1,1) != ".")) { print \$ 3 } }'\'' | sort -u > $export_symbols' + _LT_TAGVAR(export_symbols_cmds, $1)='$NM -Bpg $libobjs $convenience | awk '\''{ if (((\$ 2 == "T") || (\$ 2 == "D") || (\$ 2 == "B") || (\$ 2 == "W")) && ([substr](\$ 3,1,1) != ".")) { print \$ 3 } }'\'' | sort -u > $export_symbols' else _LT_TAGVAR(export_symbols_cmds, $1)='$NM -BCpg $libobjs $convenience | awk '\''{ if (((\$ 2 == "T") || (\$ 2 == "D") || (\$ 2 == "B")) && ([substr](\$ 3,1,1) != ".")) { print \$ 3 } }'\'' | sort -u > $export_symbols' fi ;; pw32*) _LT_TAGVAR(export_symbols_cmds, $1)="$ltdll_cmds" - ;; + ;; cygwin* | mingw* | cegcc*) - _LT_TAGVAR(export_symbols_cmds, $1)='$NM $libobjs $convenience | $global_symbol_pipe | $SED -e '\''/^[[BCDGRS]][[ ]]/s/.*[[ ]]\([[^ ]]*\)/\1 DATA/;/^.*[[ ]]__nm__/s/^.*[[ ]]__nm__\([[^ ]]*\)[[ ]][[^ ]]*/\1 DATA/;/^I[[ ]]/d;/^[[AITW]][[ ]]/s/.* //'\'' | sort | uniq > $export_symbols' - ;; - linux* | k*bsd*-gnu) + case $cc_basename in + cl*) + _LT_TAGVAR(exclude_expsyms, $1)='_NULL_IMPORT_DESCRIPTOR|_IMPORT_DESCRIPTOR_.*' + ;; + *) + _LT_TAGVAR(export_symbols_cmds, $1)='$NM $libobjs $convenience | $global_symbol_pipe | $SED -e '\''/^[[BCDGRS]][[ ]]/s/.*[[ ]]\([[^ ]]*\)/\1 DATA/;s/^.*[[ ]]__nm__\([[^ ]]*\)[[ ]][[^ ]]*/\1 DATA/;/^I[[ ]]/d;/^[[AITW]][[ ]]/s/.* //'\'' | sort | uniq > $export_symbols' + _LT_TAGVAR(exclude_expsyms, $1)=['[_]+GLOBAL_OFFSET_TABLE_|[_]+GLOBAL__[FID]_.*|[_]+head_[A-Za-z0-9_]+_dll|[A-Za-z0-9_]+_dll_iname'] + ;; + esac + ;; + linux* | k*bsd*-gnu | gnu*) _LT_TAGVAR(link_all_deplibs, $1)=no - ;; + ;; *) _LT_TAGVAR(export_symbols_cmds, $1)='$NM $libobjs $convenience | $global_symbol_pipe | $SED '\''s/.* //'\'' | sort | uniq > $export_symbols' - ;; + ;; esac - _LT_TAGVAR(exclude_expsyms, $1)=['_GLOBAL_OFFSET_TABLE_|_GLOBAL__F[ID]_.*'] ], [ runpath_var= _LT_TAGVAR(allow_undefined_flag, $1)= @@ -4216,7 +4596,6 @@ m4_if([$1], [CXX], [ _LT_TAGVAR(hardcode_direct, $1)=no _LT_TAGVAR(hardcode_direct_absolute, $1)=no _LT_TAGVAR(hardcode_libdir_flag_spec, $1)= - _LT_TAGVAR(hardcode_libdir_flag_spec_ld, $1)= _LT_TAGVAR(hardcode_libdir_separator, $1)= _LT_TAGVAR(hardcode_minus_L, $1)=no _LT_TAGVAR(hardcode_shlibpath_var, $1)=unsupported @@ -4261,13 +4640,39 @@ dnl Note also adjust exclude_expsyms for C++ above. openbsd*) with_gnu_ld=no ;; - linux* | k*bsd*-gnu) + linux* | k*bsd*-gnu | gnu*) _LT_TAGVAR(link_all_deplibs, $1)=no ;; esac _LT_TAGVAR(ld_shlibs, $1)=yes + + # On some targets, GNU ld is compatible enough with the native linker + # that we're better off using the native interface for both. + lt_use_gnu_ld_interface=no if test "$with_gnu_ld" = yes; then + case $host_os in + aix*) + # The AIX port of GNU ld has always aspired to compatibility + # with the native linker. However, as the warning in the GNU ld + # block says, versions before 2.19.5* couldn't really create working + # shared libraries, regardless of the interface used. + case `$LD -v 2>&1` in + *\ \(GNU\ Binutils\)\ 2.19.5*) ;; + *\ \(GNU\ Binutils\)\ 2.[[2-9]]*) ;; + *\ \(GNU\ Binutils\)\ [[3-9]]*) ;; + *) + lt_use_gnu_ld_interface=yes + ;; + esac + ;; + *) + lt_use_gnu_ld_interface=yes + ;; + esac + fi + + if test "$lt_use_gnu_ld_interface" = yes; then # If archive_cmds runs LD, not CC, wlarc should be empty wlarc='${wl}' @@ -4301,11 +4706,12 @@ dnl Note also adjust exclude_expsyms for C++ above. _LT_TAGVAR(ld_shlibs, $1)=no cat <<_LT_EOF 1>&2 -*** Warning: the GNU linker, at least up to release 2.9.1, is reported +*** Warning: the GNU linker, at least up to release 2.19, is reported *** to be unable to reliably create shared libraries on AIX. *** Therefore, libtool is disabling shared libraries support. If you -*** really care for shared libraries, you may want to modify your PATH -*** so that a non-GNU linker is found, and then restart. +*** really care for shared libraries, you may want to install binutils +*** 2.20 or above, or modify your PATH so that a non-GNU linker is found. +*** You will then need to restart the configuration process. _LT_EOF fi @@ -4341,10 +4747,12 @@ _LT_EOF # _LT_TAGVAR(hardcode_libdir_flag_spec, $1) is actually meaningless, # as there is no search path for DLLs. _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-L$libdir' + _LT_TAGVAR(export_dynamic_flag_spec, $1)='${wl}--export-all-symbols' _LT_TAGVAR(allow_undefined_flag, $1)=unsupported _LT_TAGVAR(always_export_symbols, $1)=no _LT_TAGVAR(enable_shared_with_static_runtimes, $1)=yes - _LT_TAGVAR(export_symbols_cmds, $1)='$NM $libobjs $convenience | $global_symbol_pipe | $SED -e '\''/^[[BCDGRS]][[ ]]/s/.*[[ ]]\([[^ ]]*\)/\1 DATA/'\'' | $SED -e '\''/^[[AITW]][[ ]]/s/.*[[ ]]//'\'' | sort | uniq > $export_symbols' + _LT_TAGVAR(export_symbols_cmds, $1)='$NM $libobjs $convenience | $global_symbol_pipe | $SED -e '\''/^[[BCDGRS]][[ ]]/s/.*[[ ]]\([[^ ]]*\)/\1 DATA/;s/^.*[[ ]]__nm__\([[^ ]]*\)[[ ]][[^ ]]*/\1 DATA/;/^I[[ ]]/d;/^[[AITW]][[ ]]/s/.* //'\'' | sort | uniq > $export_symbols' + _LT_TAGVAR(exclude_expsyms, $1)=['[_]+GLOBAL_OFFSET_TABLE_|[_]+GLOBAL__[FID]_.*|[_]+head_[A-Za-z0-9_]+_dll|[A-Za-z0-9_]+_dll_iname'] if $LD --help 2>&1 | $GREP 'auto-import' > /dev/null; then _LT_TAGVAR(archive_cmds, $1)='$CC -shared $libobjs $deplibs $compiler_flags -o $output_objdir/$soname ${wl}--enable-auto-image-base -Xlinker --out-implib -Xlinker $lib' @@ -4362,6 +4770,11 @@ _LT_EOF fi ;; + haiku*) + _LT_TAGVAR(archive_cmds, $1)='$CC -shared $libobjs $deplibs $compiler_flags ${wl}-soname $wl$soname -o $lib' + _LT_TAGVAR(link_all_deplibs, $1)=yes + ;; + interix[[3-9]]*) _LT_TAGVAR(hardcode_direct, $1)=no _LT_TAGVAR(hardcode_shlibpath_var, $1)=no @@ -4387,15 +4800,16 @@ _LT_EOF if $LD --help 2>&1 | $EGREP ': supported targets:.* elf' > /dev/null \ && test "$tmp_diet" = no then - tmp_addflag= + tmp_addflag=' $pic_flag' tmp_sharedflag='-shared' case $cc_basename,$host_cpu in pgcc*) # Portland Group C compiler - _LT_TAGVAR(whole_archive_flag_spec, $1)='${wl}--whole-archive`for conv in $convenience\"\"; do test -n \"$conv\" && new_convenience=\"$new_convenience,$conv\"; done; $ECHO \"$new_convenience\"` ${wl}--no-whole-archive' + _LT_TAGVAR(whole_archive_flag_spec, $1)='${wl}--whole-archive`for conv in $convenience\"\"; do test -n \"$conv\" && new_convenience=\"$new_convenience,$conv\"; done; func_echo_all \"$new_convenience\"` ${wl}--no-whole-archive' tmp_addflag=' $pic_flag' ;; - pgf77* | pgf90* | pgf95*) # Portland Group f77 and f90 compilers - _LT_TAGVAR(whole_archive_flag_spec, $1)='${wl}--whole-archive`for conv in $convenience\"\"; do test -n \"$conv\" && new_convenience=\"$new_convenience,$conv\"; done; $ECHO \"$new_convenience\"` ${wl}--no-whole-archive' + pgf77* | pgf90* | pgf95* | pgfortran*) + # Portland Group f77 and f90 compilers + _LT_TAGVAR(whole_archive_flag_spec, $1)='${wl}--whole-archive`for conv in $convenience\"\"; do test -n \"$conv\" && new_convenience=\"$new_convenience,$conv\"; done; func_echo_all \"$new_convenience\"` ${wl}--no-whole-archive' tmp_addflag=' $pic_flag -Mnomain' ;; ecc*,ia64* | icc*,ia64*) # Intel C compiler on ia64 tmp_addflag=' -i_dynamic' ;; @@ -4406,13 +4820,17 @@ _LT_EOF lf95*) # Lahey Fortran 8.1 _LT_TAGVAR(whole_archive_flag_spec, $1)= tmp_sharedflag='--shared' ;; - xl[[cC]]*) # IBM XL C 8.0 on PPC (deal with xlf below) + xl[[cC]]* | bgxl[[cC]]* | mpixl[[cC]]*) # IBM XL C 8.0 on PPC (deal with xlf below) tmp_sharedflag='-qmkshrobj' tmp_addflag= ;; + nvcc*) # Cuda Compiler Driver 2.2 + _LT_TAGVAR(whole_archive_flag_spec, $1)='${wl}--whole-archive`for conv in $convenience\"\"; do test -n \"$conv\" && new_convenience=\"$new_convenience,$conv\"; done; func_echo_all \"$new_convenience\"` ${wl}--no-whole-archive' + _LT_TAGVAR(compiler_needs_object, $1)=yes + ;; esac case `$CC -V 2>&1 | sed 5q` in *Sun\ C*) # Sun C 5.9 - _LT_TAGVAR(whole_archive_flag_spec, $1)='${wl}--whole-archive`new_convenience=; for conv in $convenience\"\"; do test -z \"$conv\" || new_convenience=\"$new_convenience,$conv\"; done; $ECHO \"$new_convenience\"` ${wl}--no-whole-archive' + _LT_TAGVAR(whole_archive_flag_spec, $1)='${wl}--whole-archive`new_convenience=; for conv in $convenience\"\"; do test -z \"$conv\" || new_convenience=\"$new_convenience,$conv\"; done; func_echo_all \"$new_convenience\"` ${wl}--no-whole-archive' _LT_TAGVAR(compiler_needs_object, $1)=yes tmp_sharedflag='-G' ;; *Sun\ F*) # Sun Fortran 8.3 @@ -4428,17 +4846,16 @@ _LT_EOF fi case $cc_basename in - xlf*) + xlf* | bgf* | bgxlf* | mpixlf*) # IBM XL Fortran 10.1 on PPC cannot create shared libs itself _LT_TAGVAR(whole_archive_flag_spec, $1)='--whole-archive$convenience --no-whole-archive' - _LT_TAGVAR(hardcode_libdir_flag_spec, $1)= - _LT_TAGVAR(hardcode_libdir_flag_spec_ld, $1)='-rpath $libdir' - _LT_TAGVAR(archive_cmds, $1)='$LD -shared $libobjs $deplibs $compiler_flags -soname $soname -o $lib' + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='${wl}-rpath ${wl}$libdir' + _LT_TAGVAR(archive_cmds, $1)='$LD -shared $libobjs $deplibs $linker_flags -soname $soname -o $lib' if test "x$supports_anon_versioning" = xyes; then _LT_TAGVAR(archive_expsym_cmds, $1)='echo "{ global:" > $output_objdir/$libname.ver~ cat $export_symbols | sed -e "s/\(.*\)/\1;/" >> $output_objdir/$libname.ver~ echo "local: *; };" >> $output_objdir/$libname.ver~ - $LD -shared $libobjs $deplibs $compiler_flags -soname $soname -version-script $output_objdir/$libname.ver -o $lib' + $LD -shared $libobjs $deplibs $linker_flags -soname $soname -version-script $output_objdir/$libname.ver -o $lib' fi ;; esac @@ -4452,8 +4869,8 @@ _LT_EOF _LT_TAGVAR(archive_cmds, $1)='$LD -Bshareable $libobjs $deplibs $linker_flags -o $lib' wlarc= else - _LT_TAGVAR(archive_cmds, $1)='$CC -shared $libobjs $deplibs $compiler_flags ${wl}-soname $wl$soname -o $lib' - _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared $libobjs $deplibs $compiler_flags ${wl}-soname $wl$soname ${wl}-retain-symbols-file $wl$export_symbols -o $lib' + _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags ${wl}-soname $wl$soname -o $lib' + _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags ${wl}-soname $wl$soname ${wl}-retain-symbols-file $wl$export_symbols -o $lib' fi ;; @@ -4471,8 +4888,8 @@ _LT_EOF _LT_EOF elif $LD --help 2>&1 | $GREP ': supported targets:.* elf' > /dev/null; then - _LT_TAGVAR(archive_cmds, $1)='$CC -shared $libobjs $deplibs $compiler_flags ${wl}-soname $wl$soname -o $lib' - _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared $libobjs $deplibs $compiler_flags ${wl}-soname $wl$soname ${wl}-retain-symbols-file $wl$export_symbols -o $lib' + _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags ${wl}-soname $wl$soname -o $lib' + _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags ${wl}-soname $wl$soname ${wl}-retain-symbols-file $wl$export_symbols -o $lib' else _LT_TAGVAR(ld_shlibs, $1)=no fi @@ -4518,8 +4935,8 @@ _LT_EOF *) if $LD --help 2>&1 | $GREP ': supported targets:.* elf' > /dev/null; then - _LT_TAGVAR(archive_cmds, $1)='$CC -shared $libobjs $deplibs $compiler_flags ${wl}-soname $wl$soname -o $lib' - _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared $libobjs $deplibs $compiler_flags ${wl}-soname $wl$soname ${wl}-retain-symbols-file $wl$export_symbols -o $lib' + _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags ${wl}-soname $wl$soname -o $lib' + _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags ${wl}-soname $wl$soname ${wl}-retain-symbols-file $wl$export_symbols -o $lib' else _LT_TAGVAR(ld_shlibs, $1)=no fi @@ -4559,8 +4976,10 @@ _LT_EOF else # If we're using GNU nm, then we don't want the "-C" option. # -C means demangle to AIX nm, but means don't demangle with GNU nm + # Also, AIX nm treats weak defined symbols like other global + # defined symbols, whereas GNU nm marks them as "W". if $NM -V 2>&1 | $GREP 'GNU' > /dev/null; then - _LT_TAGVAR(export_symbols_cmds, $1)='$NM -Bpg $libobjs $convenience | awk '\''{ if (((\$ 2 == "T") || (\$ 2 == "D") || (\$ 2 == "B")) && ([substr](\$ 3,1,1) != ".")) { print \$ 3 } }'\'' | sort -u > $export_symbols' + _LT_TAGVAR(export_symbols_cmds, $1)='$NM -Bpg $libobjs $convenience | awk '\''{ if (((\$ 2 == "T") || (\$ 2 == "D") || (\$ 2 == "B") || (\$ 2 == "W")) && ([substr](\$ 3,1,1) != ".")) { print \$ 3 } }'\'' | sort -u > $export_symbols' else _LT_TAGVAR(export_symbols_cmds, $1)='$NM -BCpg $libobjs $convenience | awk '\''{ if (((\$ 2 == "T") || (\$ 2 == "D") || (\$ 2 == "B")) && ([substr](\$ 3,1,1) != ".")) { print \$ 3 } }'\'' | sort -u > $export_symbols' fi @@ -4648,9 +5067,9 @@ _LT_EOF _LT_TAGVAR(allow_undefined_flag, $1)='-berok' # Determine the default libpath from the value encoded in an # empty executable. - _LT_SYS_MODULE_PATH_AIX + _LT_SYS_MODULE_PATH_AIX([$1]) _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='${wl}-blibpath:$libdir:'"$aix_libpath" - _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -o $output_objdir/$soname $libobjs $deplibs '"\${wl}$no_entry_flag"' $compiler_flags `if test "x${allow_undefined_flag}" != "x"; then $ECHO "X${wl}${allow_undefined_flag}" | $Xsed; else :; fi` '"\${wl}$exp_sym_flag:\$export_symbols $shared_flag" + _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -o $output_objdir/$soname $libobjs $deplibs '"\${wl}$no_entry_flag"' $compiler_flags `if test "x${allow_undefined_flag}" != "x"; then func_echo_all "${wl}${allow_undefined_flag}"; else :; fi` '"\${wl}$exp_sym_flag:\$export_symbols $shared_flag" else if test "$host_cpu" = ia64; then _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='${wl}-R $libdir:/usr/lib:/lib' @@ -4659,14 +5078,19 @@ _LT_EOF else # Determine the default libpath from the value encoded in an # empty executable. - _LT_SYS_MODULE_PATH_AIX + _LT_SYS_MODULE_PATH_AIX([$1]) _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='${wl}-blibpath:$libdir:'"$aix_libpath" # Warning - without using the other run time loading flags, # -berok will link without error, but may produce a broken library. _LT_TAGVAR(no_undefined_flag, $1)=' ${wl}-bernotok' _LT_TAGVAR(allow_undefined_flag, $1)=' ${wl}-berok' - # Exported symbols can be pulled into shared objects from archives - _LT_TAGVAR(whole_archive_flag_spec, $1)='$convenience' + if test "$with_gnu_ld" = yes; then + # We only use this code for GNU lds that support --whole-archive. + _LT_TAGVAR(whole_archive_flag_spec, $1)='${wl}--whole-archive$convenience ${wl}--no-whole-archive' + else + # Exported symbols can be pulled into shared objects from archives + _LT_TAGVAR(whole_archive_flag_spec, $1)='$convenience' + fi _LT_TAGVAR(archive_cmds_need_lc, $1)=yes # This is similar to how AIX traditionally builds its shared libraries. _LT_TAGVAR(archive_expsym_cmds, $1)="\$CC $shared_flag"' -o $output_objdir/$soname $libobjs $deplibs ${wl}-bnoentry $compiler_flags ${wl}-bE:$export_symbols${allow_undefined_flag}~$AR $AR_FLAGS $output_objdir/$libname$release.a $output_objdir/$soname' @@ -4698,20 +5122,64 @@ _LT_EOF # Microsoft Visual C++. # hardcode_libdir_flag_spec is actually meaningless, as there is # no search path for DLLs. - _LT_TAGVAR(hardcode_libdir_flag_spec, $1)=' ' - _LT_TAGVAR(allow_undefined_flag, $1)=unsupported - # Tell ltmain to make .lib files, not .a files. - libext=lib - # Tell ltmain to make .dll files, not .so files. - shrext_cmds=".dll" - # FIXME: Setting linknames here is a bad hack. - _LT_TAGVAR(archive_cmds, $1)='$CC -o $lib $libobjs $compiler_flags `$ECHO "X$deplibs" | $Xsed -e '\''s/ -lc$//'\''` -link -dll~linknames=' - # The linker will automatically build a .lib file if we build a DLL. - _LT_TAGVAR(old_archive_from_new_cmds, $1)='true' - # FIXME: Should let the user specify the lib program. - _LT_TAGVAR(old_archive_cmds, $1)='lib -OUT:$oldlib$oldobjs$old_deplibs' - _LT_TAGVAR(fix_srcfile_path, $1)='`cygpath -w "$srcfile"`' - _LT_TAGVAR(enable_shared_with_static_runtimes, $1)=yes + case $cc_basename in + cl*) + # Native MSVC + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)=' ' + _LT_TAGVAR(allow_undefined_flag, $1)=unsupported + _LT_TAGVAR(always_export_symbols, $1)=yes + _LT_TAGVAR(file_list_spec, $1)='@' + # Tell ltmain to make .lib files, not .a files. + libext=lib + # Tell ltmain to make .dll files, not .so files. + shrext_cmds=".dll" + # FIXME: Setting linknames here is a bad hack. + _LT_TAGVAR(archive_cmds, $1)='$CC -o $output_objdir/$soname $libobjs $compiler_flags $deplibs -Wl,-dll~linknames=' + _LT_TAGVAR(archive_expsym_cmds, $1)='if test "x`$SED 1q $export_symbols`" = xEXPORTS; then + sed -n -e 's/\\\\\\\(.*\\\\\\\)/-link\\\ -EXPORT:\\\\\\\1/' -e '1\\\!p' < $export_symbols > $output_objdir/$soname.exp; + else + sed -e 's/\\\\\\\(.*\\\\\\\)/-link\\\ -EXPORT:\\\\\\\1/' < $export_symbols > $output_objdir/$soname.exp; + fi~ + $CC -o $tool_output_objdir$soname $libobjs $compiler_flags $deplibs "@$tool_output_objdir$soname.exp" -Wl,-DLL,-IMPLIB:"$tool_output_objdir$libname.dll.lib"~ + linknames=' + # The linker will not automatically build a static lib if we build a DLL. + # _LT_TAGVAR(old_archive_from_new_cmds, $1)='true' + _LT_TAGVAR(enable_shared_with_static_runtimes, $1)=yes + _LT_TAGVAR(exclude_expsyms, $1)='_NULL_IMPORT_DESCRIPTOR|_IMPORT_DESCRIPTOR_.*' + _LT_TAGVAR(export_symbols_cmds, $1)='$NM $libobjs $convenience | $global_symbol_pipe | $SED -e '\''/^[[BCDGRS]][[ ]]/s/.*[[ ]]\([[^ ]]*\)/\1,DATA/'\'' | $SED -e '\''/^[[AITW]][[ ]]/s/.*[[ ]]//'\'' | sort | uniq > $export_symbols' + # Don't use ranlib + _LT_TAGVAR(old_postinstall_cmds, $1)='chmod 644 $oldlib' + _LT_TAGVAR(postlink_cmds, $1)='lt_outputfile="@OUTPUT@"~ + lt_tool_outputfile="@TOOL_OUTPUT@"~ + case $lt_outputfile in + *.exe|*.EXE) ;; + *) + lt_outputfile="$lt_outputfile.exe" + lt_tool_outputfile="$lt_tool_outputfile.exe" + ;; + esac~ + if test "$MANIFEST_TOOL" != ":" && test -f "$lt_outputfile.manifest"; then + $MANIFEST_TOOL -manifest "$lt_tool_outputfile.manifest" -outputresource:"$lt_tool_outputfile" || exit 1; + $RM "$lt_outputfile.manifest"; + fi' + ;; + *) + # Assume MSVC wrapper + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)=' ' + _LT_TAGVAR(allow_undefined_flag, $1)=unsupported + # Tell ltmain to make .lib files, not .a files. + libext=lib + # Tell ltmain to make .dll files, not .so files. + shrext_cmds=".dll" + # FIXME: Setting linknames here is a bad hack. + _LT_TAGVAR(archive_cmds, $1)='$CC -o $lib $libobjs $compiler_flags `func_echo_all "$deplibs" | $SED '\''s/ -lc$//'\''` -link -dll~linknames=' + # The linker will automatically build a .lib file if we build a DLL. + _LT_TAGVAR(old_archive_from_new_cmds, $1)='true' + # FIXME: Should let the user specify the lib program. + _LT_TAGVAR(old_archive_cmds, $1)='lib -OUT:$oldlib$oldobjs$old_deplibs' + _LT_TAGVAR(enable_shared_with_static_runtimes, $1)=yes + ;; + esac ;; darwin* | rhapsody*) @@ -4724,10 +5192,6 @@ _LT_EOF _LT_TAGVAR(hardcode_shlibpath_var, $1)=no ;; - freebsd1*) - _LT_TAGVAR(ld_shlibs, $1)=no - ;; - # FreeBSD 2.2.[012] allows us to include c++rt0.o to get C++ constructor # support. Future versions do this automatically, but an explicit c++rt0.o # does not break anything, and helps significantly (at the cost of a little @@ -4740,7 +5204,7 @@ _LT_EOF ;; # Unfortunately, older versions of FreeBSD 2 do not have this feature. - freebsd2*) + freebsd2.*) _LT_TAGVAR(archive_cmds, $1)='$LD -Bshareable -o $lib $libobjs $deplibs $linker_flags' _LT_TAGVAR(hardcode_direct, $1)=yes _LT_TAGVAR(hardcode_minus_L, $1)=yes @@ -4749,7 +5213,7 @@ _LT_EOF # FreeBSD 3 and greater uses gcc -shared to do shared libraries. freebsd* | dragonfly*) - _LT_TAGVAR(archive_cmds, $1)='$CC -shared -o $lib $libobjs $deplibs $compiler_flags' + _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag -o $lib $libobjs $deplibs $compiler_flags' _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-R$libdir' _LT_TAGVAR(hardcode_direct, $1)=yes _LT_TAGVAR(hardcode_shlibpath_var, $1)=no @@ -4757,7 +5221,7 @@ _LT_EOF hpux9*) if test "$GCC" = yes; then - _LT_TAGVAR(archive_cmds, $1)='$RM $output_objdir/$soname~$CC -shared -fPIC ${wl}+b ${wl}$install_libdir -o $output_objdir/$soname $libobjs $deplibs $compiler_flags~test $output_objdir/$soname = $lib || mv $output_objdir/$soname $lib' + _LT_TAGVAR(archive_cmds, $1)='$RM $output_objdir/$soname~$CC -shared $pic_flag ${wl}+b ${wl}$install_libdir -o $output_objdir/$soname $libobjs $deplibs $compiler_flags~test $output_objdir/$soname = $lib || mv $output_objdir/$soname $lib' else _LT_TAGVAR(archive_cmds, $1)='$RM $output_objdir/$soname~$LD -b +b $install_libdir -o $output_objdir/$soname $libobjs $deplibs $linker_flags~test $output_objdir/$soname = $lib || mv $output_objdir/$soname $lib' fi @@ -4772,14 +5236,13 @@ _LT_EOF ;; hpux10*) - if test "$GCC" = yes -a "$with_gnu_ld" = no; then - _LT_TAGVAR(archive_cmds, $1)='$CC -shared -fPIC ${wl}+h ${wl}$soname ${wl}+b ${wl}$install_libdir -o $lib $libobjs $deplibs $compiler_flags' + if test "$GCC" = yes && test "$with_gnu_ld" = no; then + _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag ${wl}+h ${wl}$soname ${wl}+b ${wl}$install_libdir -o $lib $libobjs $deplibs $compiler_flags' else _LT_TAGVAR(archive_cmds, $1)='$LD -b +h $soname +b $install_libdir -o $lib $libobjs $deplibs $linker_flags' fi if test "$with_gnu_ld" = no; then _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='${wl}+b ${wl}$libdir' - _LT_TAGVAR(hardcode_libdir_flag_spec_ld, $1)='+b $libdir' _LT_TAGVAR(hardcode_libdir_separator, $1)=: _LT_TAGVAR(hardcode_direct, $1)=yes _LT_TAGVAR(hardcode_direct_absolute, $1)=yes @@ -4791,16 +5254,16 @@ _LT_EOF ;; hpux11*) - if test "$GCC" = yes -a "$with_gnu_ld" = no; then + if test "$GCC" = yes && test "$with_gnu_ld" = no; then case $host_cpu in hppa*64*) _LT_TAGVAR(archive_cmds, $1)='$CC -shared ${wl}+h ${wl}$soname -o $lib $libobjs $deplibs $compiler_flags' ;; ia64*) - _LT_TAGVAR(archive_cmds, $1)='$CC -shared -fPIC ${wl}+h ${wl}$soname ${wl}+nodefaultrpath -o $lib $libobjs $deplibs $compiler_flags' + _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag ${wl}+h ${wl}$soname ${wl}+nodefaultrpath -o $lib $libobjs $deplibs $compiler_flags' ;; *) - _LT_TAGVAR(archive_cmds, $1)='$CC -shared -fPIC ${wl}+h ${wl}$soname ${wl}+b ${wl}$install_libdir -o $lib $libobjs $deplibs $compiler_flags' + _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag ${wl}+h ${wl}$soname ${wl}+b ${wl}$install_libdir -o $lib $libobjs $deplibs $compiler_flags' ;; esac else @@ -4812,7 +5275,14 @@ _LT_EOF _LT_TAGVAR(archive_cmds, $1)='$CC -b ${wl}+h ${wl}$soname ${wl}+nodefaultrpath -o $lib $libobjs $deplibs $compiler_flags' ;; *) - _LT_TAGVAR(archive_cmds, $1)='$CC -b ${wl}+h ${wl}$soname ${wl}+b ${wl}$install_libdir -o $lib $libobjs $deplibs $compiler_flags' + m4_if($1, [], [ + # Older versions of the 11.00 compiler do not understand -b yet + # (HP92453-01 A.11.01.20 doesn't, HP92453-01 B.11.X.35175-35176.GP does) + _LT_LINKER_OPTION([if $CC understands -b], + _LT_TAGVAR(lt_cv_prog_compiler__b, $1), [-b], + [_LT_TAGVAR(archive_cmds, $1)='$CC -b ${wl}+h ${wl}$soname ${wl}+b ${wl}$install_libdir -o $lib $libobjs $deplibs $compiler_flags'], + [_LT_TAGVAR(archive_cmds, $1)='$LD -b +h $soname +b $install_libdir -o $lib $libobjs $deplibs $linker_flags'])], + [_LT_TAGVAR(archive_cmds, $1)='$CC -b ${wl}+h ${wl}$soname ${wl}+b ${wl}$install_libdir -o $lib $libobjs $deplibs $compiler_flags']) ;; esac fi @@ -4840,19 +5310,34 @@ _LT_EOF irix5* | irix6* | nonstopux*) if test "$GCC" = yes; then - _LT_TAGVAR(archive_cmds, $1)='$CC -shared $libobjs $deplibs $compiler_flags ${wl}-soname ${wl}$soname `test -n "$verstring" && $ECHO "X${wl}-set_version ${wl}$verstring" | $Xsed` ${wl}-update_registry ${wl}${output_objdir}/so_locations -o $lib' + _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags ${wl}-soname ${wl}$soname `test -n "$verstring" && func_echo_all "${wl}-set_version ${wl}$verstring"` ${wl}-update_registry ${wl}${output_objdir}/so_locations -o $lib' # Try to use the -exported_symbol ld option, if it does not # work, assume that -exports_file does not work either and # implicitly export all symbols. - save_LDFLAGS="$LDFLAGS" - LDFLAGS="$LDFLAGS -shared ${wl}-exported_symbol ${wl}foo ${wl}-update_registry ${wl}/dev/null" - AC_LINK_IFELSE(int foo(void) {}, - _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared $libobjs $deplibs $compiler_flags ${wl}-soname ${wl}$soname `test -n "$verstring" && $ECHO "X${wl}-set_version ${wl}$verstring" | $Xsed` ${wl}-update_registry ${wl}${output_objdir}/so_locations ${wl}-exports_file ${wl}$export_symbols -o $lib' - ) - LDFLAGS="$save_LDFLAGS" + # This should be the same for all languages, so no per-tag cache variable. + AC_CACHE_CHECK([whether the $host_os linker accepts -exported_symbol], + [lt_cv_irix_exported_symbol], + [save_LDFLAGS="$LDFLAGS" + LDFLAGS="$LDFLAGS -shared ${wl}-exported_symbol ${wl}foo ${wl}-update_registry ${wl}/dev/null" + AC_LINK_IFELSE( + [AC_LANG_SOURCE( + [AC_LANG_CASE([C], [[int foo (void) { return 0; }]], + [C++], [[int foo (void) { return 0; }]], + [Fortran 77], [[ + subroutine foo + end]], + [Fortran], [[ + subroutine foo + end]])])], + [lt_cv_irix_exported_symbol=yes], + [lt_cv_irix_exported_symbol=no]) + LDFLAGS="$save_LDFLAGS"]) + if test "$lt_cv_irix_exported_symbol" = yes; then + _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags ${wl}-soname ${wl}$soname `test -n "$verstring" && func_echo_all "${wl}-set_version ${wl}$verstring"` ${wl}-update_registry ${wl}${output_objdir}/so_locations ${wl}-exports_file ${wl}$export_symbols -o $lib' + fi else - _LT_TAGVAR(archive_cmds, $1)='$CC -shared $libobjs $deplibs $compiler_flags -soname $soname `test -n "$verstring" && $ECHO "X-set_version $verstring" | $Xsed` -update_registry ${output_objdir}/so_locations -o $lib' - _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared $libobjs $deplibs $compiler_flags -soname $soname `test -n "$verstring" && $ECHO "X-set_version $verstring" | $Xsed` -update_registry ${output_objdir}/so_locations -exports_file $export_symbols -o $lib' + _LT_TAGVAR(archive_cmds, $1)='$CC -shared $libobjs $deplibs $compiler_flags -soname $soname `test -n "$verstring" && func_echo_all "-set_version $verstring"` -update_registry ${output_objdir}/so_locations -o $lib' + _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared $libobjs $deplibs $compiler_flags -soname $soname `test -n "$verstring" && func_echo_all "-set_version $verstring"` -update_registry ${output_objdir}/so_locations -exports_file $export_symbols -o $lib' fi _LT_TAGVAR(archive_cmds_need_lc, $1)='no' _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='${wl}-rpath ${wl}$libdir' @@ -4914,17 +5399,17 @@ _LT_EOF _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-L$libdir' _LT_TAGVAR(hardcode_minus_L, $1)=yes _LT_TAGVAR(allow_undefined_flag, $1)=unsupported - _LT_TAGVAR(archive_cmds, $1)='$ECHO "LIBRARY $libname INITINSTANCE" > $output_objdir/$libname.def~$ECHO "DESCRIPTION \"$libname\"" >> $output_objdir/$libname.def~$ECHO DATA >> $output_objdir/$libname.def~$ECHO " SINGLE NONSHARED" >> $output_objdir/$libname.def~$ECHO EXPORTS >> $output_objdir/$libname.def~emxexp $libobjs >> $output_objdir/$libname.def~$CC -Zdll -Zcrtdll -o $lib $libobjs $deplibs $compiler_flags $output_objdir/$libname.def' + _LT_TAGVAR(archive_cmds, $1)='$ECHO "LIBRARY $libname INITINSTANCE" > $output_objdir/$libname.def~$ECHO "DESCRIPTION \"$libname\"" >> $output_objdir/$libname.def~echo DATA >> $output_objdir/$libname.def~echo " SINGLE NONSHARED" >> $output_objdir/$libname.def~echo EXPORTS >> $output_objdir/$libname.def~emxexp $libobjs >> $output_objdir/$libname.def~$CC -Zdll -Zcrtdll -o $lib $libobjs $deplibs $compiler_flags $output_objdir/$libname.def' _LT_TAGVAR(old_archive_from_new_cmds, $1)='emximp -o $output_objdir/$libname.a $output_objdir/$libname.def' ;; osf3*) if test "$GCC" = yes; then _LT_TAGVAR(allow_undefined_flag, $1)=' ${wl}-expect_unresolved ${wl}\*' - _LT_TAGVAR(archive_cmds, $1)='$CC -shared${allow_undefined_flag} $libobjs $deplibs $compiler_flags ${wl}-soname ${wl}$soname `test -n "$verstring" && $ECHO "X${wl}-set_version ${wl}$verstring" | $Xsed` ${wl}-update_registry ${wl}${output_objdir}/so_locations -o $lib' + _LT_TAGVAR(archive_cmds, $1)='$CC -shared${allow_undefined_flag} $libobjs $deplibs $compiler_flags ${wl}-soname ${wl}$soname `test -n "$verstring" && func_echo_all "${wl}-set_version ${wl}$verstring"` ${wl}-update_registry ${wl}${output_objdir}/so_locations -o $lib' else _LT_TAGVAR(allow_undefined_flag, $1)=' -expect_unresolved \*' - _LT_TAGVAR(archive_cmds, $1)='$CC -shared${allow_undefined_flag} $libobjs $deplibs $compiler_flags -soname $soname `test -n "$verstring" && $ECHO "X-set_version $verstring" | $Xsed` -update_registry ${output_objdir}/so_locations -o $lib' + _LT_TAGVAR(archive_cmds, $1)='$CC -shared${allow_undefined_flag} $libobjs $deplibs $compiler_flags -soname $soname `test -n "$verstring" && func_echo_all "-set_version $verstring"` -update_registry ${output_objdir}/so_locations -o $lib' fi _LT_TAGVAR(archive_cmds_need_lc, $1)='no' _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='${wl}-rpath ${wl}$libdir' @@ -4934,13 +5419,13 @@ _LT_EOF osf4* | osf5*) # as osf3* with the addition of -msym flag if test "$GCC" = yes; then _LT_TAGVAR(allow_undefined_flag, $1)=' ${wl}-expect_unresolved ${wl}\*' - _LT_TAGVAR(archive_cmds, $1)='$CC -shared${allow_undefined_flag} $libobjs $deplibs $compiler_flags ${wl}-msym ${wl}-soname ${wl}$soname `test -n "$verstring" && $ECHO "X${wl}-set_version ${wl}$verstring" | $Xsed` ${wl}-update_registry ${wl}${output_objdir}/so_locations -o $lib' + _LT_TAGVAR(archive_cmds, $1)='$CC -shared${allow_undefined_flag} $pic_flag $libobjs $deplibs $compiler_flags ${wl}-msym ${wl}-soname ${wl}$soname `test -n "$verstring" && func_echo_all "${wl}-set_version ${wl}$verstring"` ${wl}-update_registry ${wl}${output_objdir}/so_locations -o $lib' _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='${wl}-rpath ${wl}$libdir' else _LT_TAGVAR(allow_undefined_flag, $1)=' -expect_unresolved \*' - _LT_TAGVAR(archive_cmds, $1)='$CC -shared${allow_undefined_flag} $libobjs $deplibs $compiler_flags -msym -soname $soname `test -n "$verstring" && $ECHO "X-set_version $verstring" | $Xsed` -update_registry ${output_objdir}/so_locations -o $lib' + _LT_TAGVAR(archive_cmds, $1)='$CC -shared${allow_undefined_flag} $libobjs $deplibs $compiler_flags -msym -soname $soname `test -n "$verstring" && func_echo_all "-set_version $verstring"` -update_registry ${output_objdir}/so_locations -o $lib' _LT_TAGVAR(archive_expsym_cmds, $1)='for i in `cat $export_symbols`; do printf "%s %s\\n" -exported_symbol "\$i" >> $lib.exp; done; printf "%s\\n" "-hidden">> $lib.exp~ - $CC -shared${allow_undefined_flag} ${wl}-input ${wl}$lib.exp $compiler_flags $libobjs $deplibs -soname $soname `test -n "$verstring" && $ECHO "X-set_version $verstring" | $Xsed` -update_registry ${output_objdir}/so_locations -o $lib~$RM $lib.exp' + $CC -shared${allow_undefined_flag} ${wl}-input ${wl}$lib.exp $compiler_flags $libobjs $deplibs -soname $soname `test -n "$verstring" && $ECHO "-set_version $verstring"` -update_registry ${output_objdir}/so_locations -o $lib~$RM $lib.exp' # Both c and cxx compiler support -rpath directly _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-rpath $libdir' @@ -4953,9 +5438,9 @@ _LT_EOF _LT_TAGVAR(no_undefined_flag, $1)=' -z defs' if test "$GCC" = yes; then wlarc='${wl}' - _LT_TAGVAR(archive_cmds, $1)='$CC -shared ${wl}-z ${wl}text ${wl}-h ${wl}$soname -o $lib $libobjs $deplibs $compiler_flags' + _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag ${wl}-z ${wl}text ${wl}-h ${wl}$soname -o $lib $libobjs $deplibs $compiler_flags' _LT_TAGVAR(archive_expsym_cmds, $1)='echo "{ global:" > $lib.exp~cat $export_symbols | $SED -e "s/\(.*\)/\1;/" >> $lib.exp~echo "local: *; };" >> $lib.exp~ - $CC -shared ${wl}-z ${wl}text ${wl}-M ${wl}$lib.exp ${wl}-h ${wl}$soname -o $lib $libobjs $deplibs $compiler_flags~$RM $lib.exp' + $CC -shared $pic_flag ${wl}-z ${wl}text ${wl}-M ${wl}$lib.exp ${wl}-h ${wl}$soname -o $lib $libobjs $deplibs $compiler_flags~$RM $lib.exp' else case `$CC -V 2>&1` in *"Compilers 5.0"*) @@ -5131,36 +5616,38 @@ x|xyes) # Test whether the compiler implicitly links with -lc since on some # systems, -lgcc has to come before -lc. If gcc already passes -lc # to ld, don't add -lc before -lgcc. - AC_MSG_CHECKING([whether -lc should be explicitly linked in]) - $RM conftest* - echo "$lt_simple_compile_test_code" > conftest.$ac_ext - - if AC_TRY_EVAL(ac_compile) 2>conftest.err; then - soname=conftest - lib=conftest - libobjs=conftest.$ac_objext - deplibs= - wl=$_LT_TAGVAR(lt_prog_compiler_wl, $1) - pic_flag=$_LT_TAGVAR(lt_prog_compiler_pic, $1) - compiler_flags=-v - linker_flags=-v - verstring= - output_objdir=. - libname=conftest - lt_save_allow_undefined_flag=$_LT_TAGVAR(allow_undefined_flag, $1) - _LT_TAGVAR(allow_undefined_flag, $1)= - if AC_TRY_EVAL(_LT_TAGVAR(archive_cmds, $1) 2\>\&1 \| $GREP \" -lc \" \>/dev/null 2\>\&1) - then - _LT_TAGVAR(archive_cmds_need_lc, $1)=no - else - _LT_TAGVAR(archive_cmds_need_lc, $1)=yes - fi - _LT_TAGVAR(allow_undefined_flag, $1)=$lt_save_allow_undefined_flag - else - cat conftest.err 1>&5 - fi - $RM conftest* - AC_MSG_RESULT([$_LT_TAGVAR(archive_cmds_need_lc, $1)]) + AC_CACHE_CHECK([whether -lc should be explicitly linked in], + [lt_cv_]_LT_TAGVAR(archive_cmds_need_lc, $1), + [$RM conftest* + echo "$lt_simple_compile_test_code" > conftest.$ac_ext + + if AC_TRY_EVAL(ac_compile) 2>conftest.err; then + soname=conftest + lib=conftest + libobjs=conftest.$ac_objext + deplibs= + wl=$_LT_TAGVAR(lt_prog_compiler_wl, $1) + pic_flag=$_LT_TAGVAR(lt_prog_compiler_pic, $1) + compiler_flags=-v + linker_flags=-v + verstring= + output_objdir=. + libname=conftest + lt_save_allow_undefined_flag=$_LT_TAGVAR(allow_undefined_flag, $1) + _LT_TAGVAR(allow_undefined_flag, $1)= + if AC_TRY_EVAL(_LT_TAGVAR(archive_cmds, $1) 2\>\&1 \| $GREP \" -lc \" \>/dev/null 2\>\&1) + then + lt_cv_[]_LT_TAGVAR(archive_cmds_need_lc, $1)=no + else + lt_cv_[]_LT_TAGVAR(archive_cmds_need_lc, $1)=yes + fi + _LT_TAGVAR(allow_undefined_flag, $1)=$lt_save_allow_undefined_flag + else + cat conftest.err 1>&5 + fi + $RM conftest* + ]) + _LT_TAGVAR(archive_cmds_need_lc, $1)=$lt_cv_[]_LT_TAGVAR(archive_cmds_need_lc, $1) ;; esac fi @@ -5197,9 +5684,6 @@ _LT_TAGDECL([], [no_undefined_flag], [1], _LT_TAGDECL([], [hardcode_libdir_flag_spec], [1], [Flag to hardcode $libdir into a binary during linking. This must work even if $libdir does not exist]) -_LT_TAGDECL([], [hardcode_libdir_flag_spec_ld], [1], - [[If ld is used when linking, flag to hardcode $libdir into a binary - during linking. This must work even if $libdir does not exist]]) _LT_TAGDECL([], [hardcode_libdir_separator], [1], [Whether we need a single "-rpath" flag with a separated argument]) _LT_TAGDECL([], [hardcode_direct], [0], @@ -5225,8 +5709,6 @@ _LT_TAGDECL([], [inherit_rpath], [0], to runtime path list]) _LT_TAGDECL([], [link_all_deplibs], [0], [Whether libtool must link a program against all its dependency libraries]) -_LT_TAGDECL([], [fix_srcfile_path], [1], - [Fix the shell variable $srcfile for the compiler]) _LT_TAGDECL([], [always_export_symbols], [0], [Set to "yes" if exported symbols are required]) _LT_TAGDECL([], [export_symbols_cmds], [2], @@ -5237,6 +5719,8 @@ _LT_TAGDECL([], [include_expsyms], [1], [Symbols that must always be exported]) _LT_TAGDECL([], [prelink_cmds], [2], [Commands necessary for linking programs (against libraries) with templates]) +_LT_TAGDECL([], [postlink_cmds], [2], + [Commands necessary for finishing linking programs]) _LT_TAGDECL([], [file_list_spec], [1], [Specify filename containing input files]) dnl FIXME: Not yet implemented @@ -5330,37 +5814,22 @@ CC="$lt_save_CC" ])# _LT_LANG_C_CONFIG -# _LT_PROG_CXX -# ------------ -# Since AC_PROG_CXX is broken, in that it returns g++ if there is no c++ -# compiler, we have our own version here. -m4_defun([_LT_PROG_CXX], -[ -pushdef([AC_MSG_ERROR], [_lt_caught_CXX_error=yes]) -AC_PROG_CXX -if test -n "$CXX" && ( test "X$CXX" != "Xno" && - ( (test "X$CXX" = "Xg++" && `g++ -v >/dev/null 2>&1` ) || - (test "X$CXX" != "Xg++"))) ; then - AC_PROG_CXXCPP -else - _lt_caught_CXX_error=yes -fi -popdef([AC_MSG_ERROR]) -])# _LT_PROG_CXX - -dnl aclocal-1.4 backwards compatibility: -dnl AC_DEFUN([_LT_PROG_CXX], []) - - # _LT_LANG_CXX_CONFIG([TAG]) # -------------------------- # Ensure that the configuration variables for a C++ compiler are suitably # defined. These variables are subsequently used by _LT_CONFIG to write # the compiler configuration to `libtool'. m4_defun([_LT_LANG_CXX_CONFIG], -[AC_REQUIRE([_LT_PROG_CXX])dnl -m4_require([_LT_FILEUTILS_DEFAULTS])dnl +[m4_require([_LT_FILEUTILS_DEFAULTS])dnl m4_require([_LT_DECL_EGREP])dnl +m4_require([_LT_PATH_MANIFEST_TOOL])dnl +if test -n "$CXX" && ( test "X$CXX" != "Xno" && + ( (test "X$CXX" = "Xg++" && `g++ -v >/dev/null 2>&1` ) || + (test "X$CXX" != "Xg++"))) ; then + AC_PROG_CXXCPP +else + _lt_caught_CXX_error=yes +fi AC_LANG_PUSH(C++) _LT_TAGVAR(archive_cmds_need_lc, $1)=no @@ -5372,7 +5841,6 @@ _LT_TAGVAR(export_dynamic_flag_spec, $1)= _LT_TAGVAR(hardcode_direct, $1)=no _LT_TAGVAR(hardcode_direct_absolute, $1)=no _LT_TAGVAR(hardcode_libdir_flag_spec, $1)= -_LT_TAGVAR(hardcode_libdir_flag_spec_ld, $1)= _LT_TAGVAR(hardcode_libdir_separator, $1)= _LT_TAGVAR(hardcode_minus_L, $1)=no _LT_TAGVAR(hardcode_shlibpath_var, $1)=unsupported @@ -5382,6 +5850,8 @@ _LT_TAGVAR(module_cmds, $1)= _LT_TAGVAR(module_expsym_cmds, $1)= _LT_TAGVAR(link_all_deplibs, $1)=unknown _LT_TAGVAR(old_archive_cmds, $1)=$old_archive_cmds +_LT_TAGVAR(reload_flag, $1)=$reload_flag +_LT_TAGVAR(reload_cmds, $1)=$reload_cmds _LT_TAGVAR(no_undefined_flag, $1)= _LT_TAGVAR(whole_archive_flag_spec, $1)= _LT_TAGVAR(enable_shared_with_static_runtimes, $1)=no @@ -5413,6 +5883,7 @@ if test "$_lt_caught_CXX_error" != yes; then # Allow CC to be a program name with arguments. lt_save_CC=$CC + lt_save_CFLAGS=$CFLAGS lt_save_LD=$LD lt_save_GCC=$GCC GCC=$GXX @@ -5430,6 +5901,7 @@ if test "$_lt_caught_CXX_error" != yes; then fi test -z "${LDCXX+set}" || LD=$LDCXX CC=${CXX-"c++"} + CFLAGS=$CXXFLAGS compiler=$CC _LT_TAGVAR(compiler, $1)=$CC _LT_CC_BASENAME([$compiler]) @@ -5451,8 +5923,8 @@ if test "$_lt_caught_CXX_error" != yes; then # Check if GNU C++ uses GNU ld as the underlying linker, since the # archiving commands below assume that GNU ld is being used. if test "$with_gnu_ld" = yes; then - _LT_TAGVAR(archive_cmds, $1)='$CC -shared -nostdlib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags ${wl}-soname $wl$soname -o $lib' - _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared -nostdlib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags ${wl}-soname $wl$soname ${wl}-retain-symbols-file $wl$export_symbols -o $lib' + _LT_TAGVAR(archive_cmds, $1)='$CC $pic_flag -shared -nostdlib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags ${wl}-soname $wl$soname -o $lib' + _LT_TAGVAR(archive_expsym_cmds, $1)='$CC $pic_flag -shared -nostdlib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags ${wl}-soname $wl$soname ${wl}-retain-symbols-file $wl$export_symbols -o $lib' _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='${wl}-rpath ${wl}$libdir' _LT_TAGVAR(export_dynamic_flag_spec, $1)='${wl}--export-dynamic' @@ -5484,7 +5956,7 @@ if test "$_lt_caught_CXX_error" != yes; then # Commands to make compiler produce verbose output that lists # what "hidden" libraries, object files and flags are used when # linking a shared library. - output_verbose_link_cmd='$CC -shared $CFLAGS -v conftest.$objext 2>&1 | $GREP "\-L"' + output_verbose_link_cmd='$CC -shared $CFLAGS -v conftest.$objext 2>&1 | $GREP -v "^Configured with:" | $GREP "\-L"' else GXX=no @@ -5593,10 +6065,10 @@ if test "$_lt_caught_CXX_error" != yes; then _LT_TAGVAR(allow_undefined_flag, $1)='-berok' # Determine the default libpath from the value encoded in an empty # executable. - _LT_SYS_MODULE_PATH_AIX + _LT_SYS_MODULE_PATH_AIX([$1]) _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='${wl}-blibpath:$libdir:'"$aix_libpath" - _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -o $output_objdir/$soname $libobjs $deplibs '"\${wl}$no_entry_flag"' $compiler_flags `if test "x${allow_undefined_flag}" != "x"; then $ECHO "X${wl}${allow_undefined_flag}" | $Xsed; else :; fi` '"\${wl}$exp_sym_flag:\$export_symbols $shared_flag" + _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -o $output_objdir/$soname $libobjs $deplibs '"\${wl}$no_entry_flag"' $compiler_flags `if test "x${allow_undefined_flag}" != "x"; then func_echo_all "${wl}${allow_undefined_flag}"; else :; fi` '"\${wl}$exp_sym_flag:\$export_symbols $shared_flag" else if test "$host_cpu" = ia64; then _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='${wl}-R $libdir:/usr/lib:/lib' @@ -5605,14 +6077,19 @@ if test "$_lt_caught_CXX_error" != yes; then else # Determine the default libpath from the value encoded in an # empty executable. - _LT_SYS_MODULE_PATH_AIX + _LT_SYS_MODULE_PATH_AIX([$1]) _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='${wl}-blibpath:$libdir:'"$aix_libpath" # Warning - without using the other run time loading flags, # -berok will link without error, but may produce a broken library. _LT_TAGVAR(no_undefined_flag, $1)=' ${wl}-bernotok' _LT_TAGVAR(allow_undefined_flag, $1)=' ${wl}-berok' - # Exported symbols can be pulled into shared objects from archives - _LT_TAGVAR(whole_archive_flag_spec, $1)='$convenience' + if test "$with_gnu_ld" = yes; then + # We only use this code for GNU lds that support --whole-archive. + _LT_TAGVAR(whole_archive_flag_spec, $1)='${wl}--whole-archive$convenience ${wl}--no-whole-archive' + else + # Exported symbols can be pulled into shared objects from archives + _LT_TAGVAR(whole_archive_flag_spec, $1)='$convenience' + fi _LT_TAGVAR(archive_cmds_need_lc, $1)=yes # This is similar to how AIX traditionally builds its shared # libraries. @@ -5642,28 +6119,75 @@ if test "$_lt_caught_CXX_error" != yes; then ;; cygwin* | mingw* | pw32* | cegcc*) - # _LT_TAGVAR(hardcode_libdir_flag_spec, $1) is actually meaningless, - # as there is no search path for DLLs. - _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-L$libdir' - _LT_TAGVAR(allow_undefined_flag, $1)=unsupported - _LT_TAGVAR(always_export_symbols, $1)=no - _LT_TAGVAR(enable_shared_with_static_runtimes, $1)=yes - - if $LD --help 2>&1 | $GREP 'auto-import' > /dev/null; then - _LT_TAGVAR(archive_cmds, $1)='$CC -shared -nostdlib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags -o $output_objdir/$soname ${wl}--enable-auto-image-base -Xlinker --out-implib -Xlinker $lib' - # If the export-symbols file already is a .def file (1st line - # is EXPORTS), use it as is; otherwise, prepend... - _LT_TAGVAR(archive_expsym_cmds, $1)='if test "x`$SED 1q $export_symbols`" = xEXPORTS; then - cp $export_symbols $output_objdir/$soname.def; - else - echo EXPORTS > $output_objdir/$soname.def; - cat $export_symbols >> $output_objdir/$soname.def; - fi~ - $CC -shared -nostdlib $output_objdir/$soname.def $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags -o $output_objdir/$soname ${wl}--enable-auto-image-base -Xlinker --out-implib -Xlinker $lib' - else - _LT_TAGVAR(ld_shlibs, $1)=no - fi - ;; + case $GXX,$cc_basename in + ,cl* | no,cl*) + # Native MSVC + # hardcode_libdir_flag_spec is actually meaningless, as there is + # no search path for DLLs. + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)=' ' + _LT_TAGVAR(allow_undefined_flag, $1)=unsupported + _LT_TAGVAR(always_export_symbols, $1)=yes + _LT_TAGVAR(file_list_spec, $1)='@' + # Tell ltmain to make .lib files, not .a files. + libext=lib + # Tell ltmain to make .dll files, not .so files. + shrext_cmds=".dll" + # FIXME: Setting linknames here is a bad hack. + _LT_TAGVAR(archive_cmds, $1)='$CC -o $output_objdir/$soname $libobjs $compiler_flags $deplibs -Wl,-dll~linknames=' + _LT_TAGVAR(archive_expsym_cmds, $1)='if test "x`$SED 1q $export_symbols`" = xEXPORTS; then + $SED -n -e 's/\\\\\\\(.*\\\\\\\)/-link\\\ -EXPORT:\\\\\\\1/' -e '1\\\!p' < $export_symbols > $output_objdir/$soname.exp; + else + $SED -e 's/\\\\\\\(.*\\\\\\\)/-link\\\ -EXPORT:\\\\\\\1/' < $export_symbols > $output_objdir/$soname.exp; + fi~ + $CC -o $tool_output_objdir$soname $libobjs $compiler_flags $deplibs "@$tool_output_objdir$soname.exp" -Wl,-DLL,-IMPLIB:"$tool_output_objdir$libname.dll.lib"~ + linknames=' + # The linker will not automatically build a static lib if we build a DLL. + # _LT_TAGVAR(old_archive_from_new_cmds, $1)='true' + _LT_TAGVAR(enable_shared_with_static_runtimes, $1)=yes + # Don't use ranlib + _LT_TAGVAR(old_postinstall_cmds, $1)='chmod 644 $oldlib' + _LT_TAGVAR(postlink_cmds, $1)='lt_outputfile="@OUTPUT@"~ + lt_tool_outputfile="@TOOL_OUTPUT@"~ + case $lt_outputfile in + *.exe|*.EXE) ;; + *) + lt_outputfile="$lt_outputfile.exe" + lt_tool_outputfile="$lt_tool_outputfile.exe" + ;; + esac~ + func_to_tool_file "$lt_outputfile"~ + if test "$MANIFEST_TOOL" != ":" && test -f "$lt_outputfile.manifest"; then + $MANIFEST_TOOL -manifest "$lt_tool_outputfile.manifest" -outputresource:"$lt_tool_outputfile" || exit 1; + $RM "$lt_outputfile.manifest"; + fi' + ;; + *) + # g++ + # _LT_TAGVAR(hardcode_libdir_flag_spec, $1) is actually meaningless, + # as there is no search path for DLLs. + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-L$libdir' + _LT_TAGVAR(export_dynamic_flag_spec, $1)='${wl}--export-all-symbols' + _LT_TAGVAR(allow_undefined_flag, $1)=unsupported + _LT_TAGVAR(always_export_symbols, $1)=no + _LT_TAGVAR(enable_shared_with_static_runtimes, $1)=yes + + if $LD --help 2>&1 | $GREP 'auto-import' > /dev/null; then + _LT_TAGVAR(archive_cmds, $1)='$CC -shared -nostdlib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags -o $output_objdir/$soname ${wl}--enable-auto-image-base -Xlinker --out-implib -Xlinker $lib' + # If the export-symbols file already is a .def file (1st line + # is EXPORTS), use it as is; otherwise, prepend... + _LT_TAGVAR(archive_expsym_cmds, $1)='if test "x`$SED 1q $export_symbols`" = xEXPORTS; then + cp $export_symbols $output_objdir/$soname.def; + else + echo EXPORTS > $output_objdir/$soname.def; + cat $export_symbols >> $output_objdir/$soname.def; + fi~ + $CC -shared -nostdlib $output_objdir/$soname.def $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags -o $output_objdir/$soname ${wl}--enable-auto-image-base -Xlinker --out-implib -Xlinker $lib' + else + _LT_TAGVAR(ld_shlibs, $1)=no + fi + ;; + esac + ;; darwin* | rhapsody*) _LT_DARWIN_LINKER_FEATURES($1) ;; @@ -5686,7 +6210,7 @@ if test "$_lt_caught_CXX_error" != yes; then esac ;; - freebsd[[12]]*) + freebsd2.*) # C++ shared libraries reported to be fairly broken before # switch to ELF _LT_TAGVAR(ld_shlibs, $1)=no @@ -5702,7 +6226,9 @@ if test "$_lt_caught_CXX_error" != yes; then _LT_TAGVAR(ld_shlibs, $1)=yes ;; - gnu*) + haiku*) + _LT_TAGVAR(archive_cmds, $1)='$CC -shared $libobjs $deplibs $compiler_flags ${wl}-soname $wl$soname -o $lib' + _LT_TAGVAR(link_all_deplibs, $1)=yes ;; hpux9*) @@ -5729,11 +6255,11 @@ if test "$_lt_caught_CXX_error" != yes; then # explicitly linking system object files so we need to strip them # from the output so that they don't get included in the library # dependencies. - output_verbose_link_cmd='templist=`($CC -b $CFLAGS -v conftest.$objext 2>&1) | $EGREP "\-L"`; list=""; for z in $templist; do case $z in conftest.$objext) list="$list $z";; *.$objext);; *) list="$list $z";;esac; done; $ECHO "X$list" | $Xsed' + output_verbose_link_cmd='templist=`($CC -b $CFLAGS -v conftest.$objext 2>&1) | $EGREP "\-L"`; list=""; for z in $templist; do case $z in conftest.$objext) list="$list $z";; *.$objext);; *) list="$list $z";;esac; done; func_echo_all "$list"' ;; *) if test "$GXX" = yes; then - _LT_TAGVAR(archive_cmds, $1)='$RM $output_objdir/$soname~$CC -shared -nostdlib -fPIC ${wl}+b ${wl}$install_libdir -o $output_objdir/$soname $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags~test $output_objdir/$soname = $lib || mv $output_objdir/$soname $lib' + _LT_TAGVAR(archive_cmds, $1)='$RM $output_objdir/$soname~$CC -shared -nostdlib $pic_flag ${wl}+b ${wl}$install_libdir -o $output_objdir/$soname $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags~test $output_objdir/$soname = $lib || mv $output_objdir/$soname $lib' else # FIXME: insert proper C++ library support _LT_TAGVAR(ld_shlibs, $1)=no @@ -5794,7 +6320,7 @@ if test "$_lt_caught_CXX_error" != yes; then # explicitly linking system object files so we need to strip them # from the output so that they don't get included in the library # dependencies. - output_verbose_link_cmd='templist=`($CC -b $CFLAGS -v conftest.$objext 2>&1) | $GREP "\-L"`; list=""; for z in $templist; do case $z in conftest.$objext) list="$list $z";; *.$objext);; *) list="$list $z";;esac; done; $ECHO "X$list" | $Xsed' + output_verbose_link_cmd='templist=`($CC -b $CFLAGS -v conftest.$objext 2>&1) | $GREP "\-L"`; list=""; for z in $templist; do case $z in conftest.$objext) list="$list $z";; *.$objext);; *) list="$list $z";;esac; done; func_echo_all "$list"' ;; *) if test "$GXX" = yes; then @@ -5804,10 +6330,10 @@ if test "$_lt_caught_CXX_error" != yes; then _LT_TAGVAR(archive_cmds, $1)='$CC -shared -nostdlib -fPIC ${wl}+h ${wl}$soname -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags' ;; ia64*) - _LT_TAGVAR(archive_cmds, $1)='$CC -shared -nostdlib -fPIC ${wl}+h ${wl}$soname ${wl}+nodefaultrpath -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags' + _LT_TAGVAR(archive_cmds, $1)='$CC -shared -nostdlib $pic_flag ${wl}+h ${wl}$soname ${wl}+nodefaultrpath -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags' ;; *) - _LT_TAGVAR(archive_cmds, $1)='$CC -shared -nostdlib -fPIC ${wl}+h ${wl}$soname ${wl}+b ${wl}$install_libdir -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags' + _LT_TAGVAR(archive_cmds, $1)='$CC -shared -nostdlib $pic_flag ${wl}+h ${wl}$soname ${wl}+b ${wl}$install_libdir -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags' ;; esac fi @@ -5837,7 +6363,7 @@ if test "$_lt_caught_CXX_error" != yes; then case $cc_basename in CC*) # SGI C++ - _LT_TAGVAR(archive_cmds, $1)='$CC -shared -all -multigot $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags -soname $soname `test -n "$verstring" && $ECHO "X-set_version $verstring" | $Xsed` -update_registry ${output_objdir}/so_locations -o $lib' + _LT_TAGVAR(archive_cmds, $1)='$CC -shared -all -multigot $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags -soname $soname `test -n "$verstring" && func_echo_all "-set_version $verstring"` -update_registry ${output_objdir}/so_locations -o $lib' # Archives containing C++ object files must be created using # "CC -ar", where "CC" is the IRIX C++ compiler. This is @@ -5848,9 +6374,9 @@ if test "$_lt_caught_CXX_error" != yes; then *) if test "$GXX" = yes; then if test "$with_gnu_ld" = no; then - _LT_TAGVAR(archive_cmds, $1)='$CC -shared -nostdlib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags ${wl}-soname ${wl}$soname `test -n "$verstring" && $ECHO "X${wl}-set_version ${wl}$verstring" | $Xsed` ${wl}-update_registry ${wl}${output_objdir}/so_locations -o $lib' + _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag -nostdlib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags ${wl}-soname ${wl}$soname `test -n "$verstring" && func_echo_all "${wl}-set_version ${wl}$verstring"` ${wl}-update_registry ${wl}${output_objdir}/so_locations -o $lib' else - _LT_TAGVAR(archive_cmds, $1)='$CC -shared -nostdlib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags ${wl}-soname ${wl}$soname `test -n "$verstring" && $ECHO "X${wl}-set_version ${wl}$verstring" | $Xsed` -o $lib' + _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag -nostdlib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags ${wl}-soname ${wl}$soname `test -n "$verstring" && func_echo_all "${wl}-set_version ${wl}$verstring"` -o $lib' fi fi _LT_TAGVAR(link_all_deplibs, $1)=yes @@ -5861,7 +6387,7 @@ if test "$_lt_caught_CXX_error" != yes; then _LT_TAGVAR(inherit_rpath, $1)=yes ;; - linux* | k*bsd*-gnu | kopensolaris*-gnu) + linux* | k*bsd*-gnu | kopensolaris*-gnu | gnu*) case $cc_basename in KCC*) # Kuck and Associates, Inc. (KAI) C++ Compiler @@ -5879,7 +6405,7 @@ if test "$_lt_caught_CXX_error" != yes; then # explicitly linking system object files so we need to strip them # from the output so that they don't get included in the library # dependencies. - output_verbose_link_cmd='templist=`$CC $CFLAGS -v conftest.$objext -o libconftest$shared_ext 2>&1 | $GREP "ld"`; rm -f libconftest$shared_ext; list=""; for z in $templist; do case $z in conftest.$objext) list="$list $z";; *.$objext);; *) list="$list $z";;esac; done; $ECHO "X$list" | $Xsed' + output_verbose_link_cmd='templist=`$CC $CFLAGS -v conftest.$objext -o libconftest$shared_ext 2>&1 | $GREP "ld"`; rm -f libconftest$shared_ext; list=""; for z in $templist; do case $z in conftest.$objext) list="$list $z";; *.$objext);; *) list="$list $z";;esac; done; func_echo_all "$list"' _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='${wl}-rpath,$libdir' _LT_TAGVAR(export_dynamic_flag_spec, $1)='${wl}--export-dynamic' @@ -5916,26 +6442,26 @@ if test "$_lt_caught_CXX_error" != yes; then pgCC* | pgcpp*) # Portland Group C++ compiler case `$CC -V` in - *pgCC\ [[1-5]]* | *pgcpp\ [[1-5]]*) + *pgCC\ [[1-5]].* | *pgcpp\ [[1-5]].*) _LT_TAGVAR(prelink_cmds, $1)='tpldir=Template.dir~ rm -rf $tpldir~ $CC --prelink_objects --instantiation_dir $tpldir $objs $libobjs $compile_deplibs~ - compile_command="$compile_command `find $tpldir -name \*.o | $NL2SP`"' + compile_command="$compile_command `find $tpldir -name \*.o | sort | $NL2SP`"' _LT_TAGVAR(old_archive_cmds, $1)='tpldir=Template.dir~ rm -rf $tpldir~ $CC --prelink_objects --instantiation_dir $tpldir $oldobjs$old_deplibs~ - $AR $AR_FLAGS $oldlib$oldobjs$old_deplibs `find $tpldir -name \*.o | $NL2SP`~ + $AR $AR_FLAGS $oldlib$oldobjs$old_deplibs `find $tpldir -name \*.o | sort | $NL2SP`~ $RANLIB $oldlib' _LT_TAGVAR(archive_cmds, $1)='tpldir=Template.dir~ rm -rf $tpldir~ $CC --prelink_objects --instantiation_dir $tpldir $predep_objects $libobjs $deplibs $convenience $postdep_objects~ - $CC -shared $pic_flag $predep_objects $libobjs $deplibs `find $tpldir -name \*.o | $NL2SP` $postdep_objects $compiler_flags ${wl}-soname ${wl}$soname -o $lib' + $CC -shared $pic_flag $predep_objects $libobjs $deplibs `find $tpldir -name \*.o | sort | $NL2SP` $postdep_objects $compiler_flags ${wl}-soname ${wl}$soname -o $lib' _LT_TAGVAR(archive_expsym_cmds, $1)='tpldir=Template.dir~ rm -rf $tpldir~ $CC --prelink_objects --instantiation_dir $tpldir $predep_objects $libobjs $deplibs $convenience $postdep_objects~ - $CC -shared $pic_flag $predep_objects $libobjs $deplibs `find $tpldir -name \*.o | $NL2SP` $postdep_objects $compiler_flags ${wl}-soname ${wl}$soname ${wl}-retain-symbols-file ${wl}$export_symbols -o $lib' + $CC -shared $pic_flag $predep_objects $libobjs $deplibs `find $tpldir -name \*.o | sort | $NL2SP` $postdep_objects $compiler_flags ${wl}-soname ${wl}$soname ${wl}-retain-symbols-file ${wl}$export_symbols -o $lib' ;; - *) # Version 6 will use weak symbols + *) # Version 6 and above use weak symbols _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags ${wl}-soname ${wl}$soname -o $lib' _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared $pic_flag $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags ${wl}-soname ${wl}$soname ${wl}-retain-symbols-file ${wl}$export_symbols -o $lib' ;; @@ -5943,7 +6469,7 @@ if test "$_lt_caught_CXX_error" != yes; then _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='${wl}--rpath ${wl}$libdir' _LT_TAGVAR(export_dynamic_flag_spec, $1)='${wl}--export-dynamic' - _LT_TAGVAR(whole_archive_flag_spec, $1)='${wl}--whole-archive`for conv in $convenience\"\"; do test -n \"$conv\" && new_convenience=\"$new_convenience,$conv\"; done; $ECHO \"$new_convenience\"` ${wl}--no-whole-archive' + _LT_TAGVAR(whole_archive_flag_spec, $1)='${wl}--whole-archive`for conv in $convenience\"\"; do test -n \"$conv\" && new_convenience=\"$new_convenience,$conv\"; done; func_echo_all \"$new_convenience\"` ${wl}--no-whole-archive' ;; cxx*) # Compaq C++ @@ -5962,9 +6488,9 @@ if test "$_lt_caught_CXX_error" != yes; then # explicitly linking system object files so we need to strip them # from the output so that they don't get included in the library # dependencies. - output_verbose_link_cmd='templist=`$CC -shared $CFLAGS -v conftest.$objext 2>&1 | $GREP "ld"`; templist=`$ECHO "X$templist" | $Xsed -e "s/\(^.*ld.*\)\( .*ld .*$\)/\1/"`; list=""; for z in $templist; do case $z in conftest.$objext) list="$list $z";; *.$objext);; *) list="$list $z";;esac; done; $ECHO "X$list" | $Xsed' + output_verbose_link_cmd='templist=`$CC -shared $CFLAGS -v conftest.$objext 2>&1 | $GREP "ld"`; templist=`func_echo_all "$templist" | $SED "s/\(^.*ld.*\)\( .*ld .*$\)/\1/"`; list=""; for z in $templist; do case $z in conftest.$objext) list="$list $z";; *.$objext);; *) list="$list $z";;esac; done; func_echo_all "X$list" | $Xsed' ;; - xl*) + xl* | mpixl* | bgxl*) # IBM XL 8.0 on PPC, with GNU ld _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='${wl}-rpath ${wl}$libdir' _LT_TAGVAR(export_dynamic_flag_spec, $1)='${wl}--export-dynamic' @@ -5984,13 +6510,13 @@ if test "$_lt_caught_CXX_error" != yes; then _LT_TAGVAR(archive_cmds, $1)='$CC -G${allow_undefined_flag} -h$soname -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags' _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -G${allow_undefined_flag} -h$soname -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags ${wl}-retain-symbols-file ${wl}$export_symbols' _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-R$libdir' - _LT_TAGVAR(whole_archive_flag_spec, $1)='${wl}--whole-archive`new_convenience=; for conv in $convenience\"\"; do test -z \"$conv\" || new_convenience=\"$new_convenience,$conv\"; done; $ECHO \"$new_convenience\"` ${wl}--no-whole-archive' + _LT_TAGVAR(whole_archive_flag_spec, $1)='${wl}--whole-archive`new_convenience=; for conv in $convenience\"\"; do test -z \"$conv\" || new_convenience=\"$new_convenience,$conv\"; done; func_echo_all \"$new_convenience\"` ${wl}--no-whole-archive' _LT_TAGVAR(compiler_needs_object, $1)=yes # Not sure whether something based on # $CC $CFLAGS -v conftest.$objext -o libconftest$shared_ext 2>&1 # would be better. - output_verbose_link_cmd='echo' + output_verbose_link_cmd='func_echo_all' # Archives containing C++ object files must be created using # "CC -xar", where "CC" is the Sun C++ compiler. This is @@ -6059,7 +6585,7 @@ if test "$_lt_caught_CXX_error" != yes; then _LT_TAGVAR(export_dynamic_flag_spec, $1)='${wl}-E' _LT_TAGVAR(whole_archive_flag_spec, $1)="$wlarc"'--whole-archive$convenience '"$wlarc"'--no-whole-archive' fi - output_verbose_link_cmd=echo + output_verbose_link_cmd=func_echo_all else _LT_TAGVAR(ld_shlibs, $1)=no fi @@ -6094,15 +6620,15 @@ if test "$_lt_caught_CXX_error" != yes; then case $host in osf3*) _LT_TAGVAR(allow_undefined_flag, $1)=' ${wl}-expect_unresolved ${wl}\*' - _LT_TAGVAR(archive_cmds, $1)='$CC -shared${allow_undefined_flag} $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags ${wl}-soname $soname `test -n "$verstring" && $ECHO "X${wl}-set_version $verstring" | $Xsed` -update_registry ${output_objdir}/so_locations -o $lib' + _LT_TAGVAR(archive_cmds, $1)='$CC -shared${allow_undefined_flag} $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags ${wl}-soname $soname `test -n "$verstring" && func_echo_all "${wl}-set_version $verstring"` -update_registry ${output_objdir}/so_locations -o $lib' _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='${wl}-rpath ${wl}$libdir' ;; *) _LT_TAGVAR(allow_undefined_flag, $1)=' -expect_unresolved \*' - _LT_TAGVAR(archive_cmds, $1)='$CC -shared${allow_undefined_flag} $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags -msym -soname $soname `test -n "$verstring" && $ECHO "X-set_version $verstring" | $Xsed` -update_registry ${output_objdir}/so_locations -o $lib' + _LT_TAGVAR(archive_cmds, $1)='$CC -shared${allow_undefined_flag} $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags -msym -soname $soname `test -n "$verstring" && func_echo_all "-set_version $verstring"` -update_registry ${output_objdir}/so_locations -o $lib' _LT_TAGVAR(archive_expsym_cmds, $1)='for i in `cat $export_symbols`; do printf "%s %s\\n" -exported_symbol "\$i" >> $lib.exp; done~ echo "-hidden">> $lib.exp~ - $CC -shared$allow_undefined_flag $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags -msym -soname $soname ${wl}-input ${wl}$lib.exp `test -n "$verstring" && $ECHO "X-set_version $verstring" | $Xsed` -update_registry ${output_objdir}/so_locations -o $lib~ + $CC -shared$allow_undefined_flag $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags -msym -soname $soname ${wl}-input ${wl}$lib.exp `test -n "$verstring" && $ECHO "-set_version $verstring"` -update_registry ${output_objdir}/so_locations -o $lib~ $RM $lib.exp' _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-rpath $libdir' ;; @@ -6118,17 +6644,17 @@ if test "$_lt_caught_CXX_error" != yes; then # explicitly linking system object files so we need to strip them # from the output so that they don't get included in the library # dependencies. - output_verbose_link_cmd='templist=`$CC -shared $CFLAGS -v conftest.$objext 2>&1 | $GREP "ld" | $GREP -v "ld:"`; templist=`$ECHO "X$templist" | $Xsed -e "s/\(^.*ld.*\)\( .*ld.*$\)/\1/"`; list=""; for z in $templist; do case $z in conftest.$objext) list="$list $z";; *.$objext);; *) list="$list $z";;esac; done; $ECHO "X$list" | $Xsed' + output_verbose_link_cmd='templist=`$CC -shared $CFLAGS -v conftest.$objext 2>&1 | $GREP "ld" | $GREP -v "ld:"`; templist=`func_echo_all "$templist" | $SED "s/\(^.*ld.*\)\( .*ld.*$\)/\1/"`; list=""; for z in $templist; do case $z in conftest.$objext) list="$list $z";; *.$objext);; *) list="$list $z";;esac; done; func_echo_all "$list"' ;; *) if test "$GXX" = yes && test "$with_gnu_ld" = no; then _LT_TAGVAR(allow_undefined_flag, $1)=' ${wl}-expect_unresolved ${wl}\*' case $host in osf3*) - _LT_TAGVAR(archive_cmds, $1)='$CC -shared -nostdlib ${allow_undefined_flag} $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags ${wl}-soname ${wl}$soname `test -n "$verstring" && $ECHO "X${wl}-set_version ${wl}$verstring" | $Xsed` ${wl}-update_registry ${wl}${output_objdir}/so_locations -o $lib' + _LT_TAGVAR(archive_cmds, $1)='$CC -shared -nostdlib ${allow_undefined_flag} $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags ${wl}-soname ${wl}$soname `test -n "$verstring" && func_echo_all "${wl}-set_version ${wl}$verstring"` ${wl}-update_registry ${wl}${output_objdir}/so_locations -o $lib' ;; *) - _LT_TAGVAR(archive_cmds, $1)='$CC -shared -nostdlib ${allow_undefined_flag} $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags ${wl}-msym ${wl}-soname ${wl}$soname `test -n "$verstring" && $ECHO "${wl}-set_version ${wl}$verstring" | $Xsed` ${wl}-update_registry ${wl}${output_objdir}/so_locations -o $lib' + _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag -nostdlib ${allow_undefined_flag} $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags ${wl}-msym ${wl}-soname ${wl}$soname `test -n "$verstring" && func_echo_all "${wl}-set_version ${wl}$verstring"` ${wl}-update_registry ${wl}${output_objdir}/so_locations -o $lib' ;; esac @@ -6138,7 +6664,7 @@ if test "$_lt_caught_CXX_error" != yes; then # Commands to make compiler produce verbose output that lists # what "hidden" libraries, object files and flags are used when # linking a shared library. - output_verbose_link_cmd='$CC -shared $CFLAGS -v conftest.$objext 2>&1 | $GREP "\-L"' + output_verbose_link_cmd='$CC -shared $CFLAGS -v conftest.$objext 2>&1 | $GREP -v "^Configured with:" | $GREP "\-L"' else # FIXME: insert proper C++ library support @@ -6174,7 +6700,7 @@ if test "$_lt_caught_CXX_error" != yes; then solaris*) case $cc_basename in - CC*) + CC* | sunCC*) # Sun C++ 4.2, 5.x and Centerline C++ _LT_TAGVAR(archive_cmds_need_lc,$1)=yes _LT_TAGVAR(no_undefined_flag, $1)=' -zdefs' @@ -6195,7 +6721,7 @@ if test "$_lt_caught_CXX_error" != yes; then esac _LT_TAGVAR(link_all_deplibs, $1)=yes - output_verbose_link_cmd='echo' + output_verbose_link_cmd='func_echo_all' # Archives containing C++ object files must be created using # "CC -xar", where "CC" is the Sun C++ compiler. This is @@ -6215,14 +6741,14 @@ if test "$_lt_caught_CXX_error" != yes; then if test "$GXX" = yes && test "$with_gnu_ld" = no; then _LT_TAGVAR(no_undefined_flag, $1)=' ${wl}-z ${wl}defs' if $CC --version | $GREP -v '^2\.7' > /dev/null; then - _LT_TAGVAR(archive_cmds, $1)='$CC -shared -nostdlib $LDFLAGS $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags ${wl}-h $wl$soname -o $lib' + _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag -nostdlib $LDFLAGS $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags ${wl}-h $wl$soname -o $lib' _LT_TAGVAR(archive_expsym_cmds, $1)='echo "{ global:" > $lib.exp~cat $export_symbols | $SED -e "s/\(.*\)/\1;/" >> $lib.exp~echo "local: *; };" >> $lib.exp~ - $CC -shared -nostdlib ${wl}-M $wl$lib.exp -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags~$RM $lib.exp' + $CC -shared $pic_flag -nostdlib ${wl}-M $wl$lib.exp -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags~$RM $lib.exp' # Commands to make compiler produce verbose output that lists # what "hidden" libraries, object files and flags are used when # linking a shared library. - output_verbose_link_cmd='$CC -shared $CFLAGS -v conftest.$objext 2>&1 | $GREP "\-L"' + output_verbose_link_cmd='$CC -shared $CFLAGS -v conftest.$objext 2>&1 | $GREP -v "^Configured with:" | $GREP "\-L"' else # g++ 2.7 appears to require `-G' NOT `-shared' on this # platform. @@ -6233,7 +6759,7 @@ if test "$_lt_caught_CXX_error" != yes; then # Commands to make compiler produce verbose output that lists # what "hidden" libraries, object files and flags are used when # linking a shared library. - output_verbose_link_cmd='$CC -G $CFLAGS -v conftest.$objext 2>&1 | $GREP "\-L"' + output_verbose_link_cmd='$CC -G $CFLAGS -v conftest.$objext 2>&1 | $GREP -v "^Configured with:" | $GREP "\-L"' fi _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='${wl}-R $wl$libdir' @@ -6287,6 +6813,10 @@ if test "$_lt_caught_CXX_error" != yes; then CC*) _LT_TAGVAR(archive_cmds, $1)='$CC -G ${wl}-h,$soname -o $lib $libobjs $deplibs $compiler_flags' _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -G ${wl}-Bexport:$export_symbols ${wl}-h,$soname -o $lib $libobjs $deplibs $compiler_flags' + _LT_TAGVAR(old_archive_cmds, $1)='$CC -Tprelink_objects $oldobjs~ + '"$_LT_TAGVAR(old_archive_cmds, $1)" + _LT_TAGVAR(reload_cmds, $1)='$CC -Tprelink_objects $reload_objs~ + '"$_LT_TAGVAR(reload_cmds, $1)" ;; *) _LT_TAGVAR(archive_cmds, $1)='$CC -shared ${wl}-h,$soname -o $lib $libobjs $deplibs $compiler_flags' @@ -6342,6 +6872,7 @@ if test "$_lt_caught_CXX_error" != yes; then fi # test -n "$compiler" CC=$lt_save_CC + CFLAGS=$lt_save_CFLAGS LDCXX=$LD LD=$lt_save_LD GCC=$lt_save_GCC @@ -6356,6 +6887,29 @@ AC_LANG_POP ])# _LT_LANG_CXX_CONFIG +# _LT_FUNC_STRIPNAME_CNF +# ---------------------- +# func_stripname_cnf prefix suffix name +# strip PREFIX and SUFFIX off of NAME. +# PREFIX and SUFFIX must not contain globbing or regex special +# characters, hashes, percent signs, but SUFFIX may contain a leading +# dot (in which case that matches only a dot). +# +# This function is identical to the (non-XSI) version of func_stripname, +# except this one can be used by m4 code that may be executed by configure, +# rather than the libtool script. +m4_defun([_LT_FUNC_STRIPNAME_CNF],[dnl +AC_REQUIRE([_LT_DECL_SED]) +AC_REQUIRE([_LT_PROG_ECHO_BACKSLASH]) +func_stripname_cnf () +{ + case ${2} in + .*) func_stripname_result=`$ECHO "${3}" | $SED "s%^${1}%%; s%\\\\${2}\$%%"`;; + *) func_stripname_result=`$ECHO "${3}" | $SED "s%^${1}%%; s%${2}\$%%"`;; + esac +} # func_stripname_cnf +])# _LT_FUNC_STRIPNAME_CNF + # _LT_SYS_HIDDEN_LIBDEPS([TAGNAME]) # --------------------------------- # Figure out "hidden" library dependencies from verbose @@ -6364,6 +6918,7 @@ AC_LANG_POP # objects, libraries and library flags. m4_defun([_LT_SYS_HIDDEN_LIBDEPS], [m4_require([_LT_FILEUTILS_DEFAULTS])dnl +AC_REQUIRE([_LT_FUNC_STRIPNAME_CNF])dnl # Dependencies to place before and after the object being linked: _LT_TAGVAR(predep_objects, $1)= _LT_TAGVAR(postdep_objects, $1)= @@ -6413,7 +6968,20 @@ public class foo { } }; _LT_EOF +], [$1], [GO], [cat > conftest.$ac_ext <<_LT_EOF +package foo +func foo() { +} +_LT_EOF ]) + +_lt_libdeps_save_CFLAGS=$CFLAGS +case "$CC $CFLAGS " in #( +*\ -flto*\ *) CFLAGS="$CFLAGS -fno-lto" ;; +*\ -fwhopr*\ *) CFLAGS="$CFLAGS -fno-whopr" ;; +*\ -fuse-linker-plugin*\ *) CFLAGS="$CFLAGS -fno-use-linker-plugin" ;; +esac + dnl Parse the compiler output and extract the necessary dnl objects, libraries and library flags. if AC_TRY_EVAL(ac_compile); then @@ -6425,7 +6993,7 @@ if AC_TRY_EVAL(ac_compile); then pre_test_object_deps_done=no for p in `eval "$output_verbose_link_cmd"`; do - case $p in + case ${prev}${p} in -L* | -R* | -l*) # Some compilers place space between "-{L,R}" and the path. @@ -6434,13 +7002,22 @@ if AC_TRY_EVAL(ac_compile); then test $p = "-R"; then prev=$p continue - else - prev= fi + # Expand the sysroot to ease extracting the directories later. + if test -z "$prev"; then + case $p in + -L*) func_stripname_cnf '-L' '' "$p"; prev=-L; p=$func_stripname_result ;; + -R*) func_stripname_cnf '-R' '' "$p"; prev=-R; p=$func_stripname_result ;; + -l*) func_stripname_cnf '-l' '' "$p"; prev=-l; p=$func_stripname_result ;; + esac + fi + case $p in + =*) func_stripname_cnf '=' '' "$p"; p=$lt_sysroot$func_stripname_result ;; + esac if test "$pre_test_object_deps_done" = no; then - case $p in - -L* | -R*) + case ${prev} in + -L | -R) # Internal compiler library paths should come after those # provided the user. The postdeps already come after the # user supplied libs so there is no need to process them. @@ -6460,8 +7037,10 @@ if AC_TRY_EVAL(ac_compile); then _LT_TAGVAR(postdeps, $1)="${_LT_TAGVAR(postdeps, $1)} ${prev}${p}" fi fi + prev= ;; + *.lto.$objext) ;; # Ignore GCC LTO objects *.$objext) # This assumes that the test object file only shows up # once in the compiler output. @@ -6497,6 +7076,7 @@ else fi $RM -f confest.$objext +CFLAGS=$_lt_libdeps_save_CFLAGS # PORTME: override above test on systems where it is broken m4_if([$1], [CXX], @@ -6533,7 +7113,7 @@ linux*) solaris*) case $cc_basename in - CC*) + CC* | sunCC*) # The more standards-conforming stlport4 library is # incompatible with the Cstd library. Avoid specifying # it if it's in CXXFLAGS. Ignore libCrun as @@ -6577,32 +7157,16 @@ _LT_TAGDECL([], [compiler_lib_search_path], [1], ])# _LT_SYS_HIDDEN_LIBDEPS -# _LT_PROG_F77 -# ------------ -# Since AC_PROG_F77 is broken, in that it returns the empty string -# if there is no fortran compiler, we have our own version here. -m4_defun([_LT_PROG_F77], -[ -pushdef([AC_MSG_ERROR], [_lt_disable_F77=yes]) -AC_PROG_F77 -if test -z "$F77" || test "X$F77" = "Xno"; then - _lt_disable_F77=yes -fi -popdef([AC_MSG_ERROR]) -])# _LT_PROG_F77 - -dnl aclocal-1.4 backwards compatibility: -dnl AC_DEFUN([_LT_PROG_F77], []) - - # _LT_LANG_F77_CONFIG([TAG]) # -------------------------- # Ensure that the configuration variables for a Fortran 77 compiler are # suitably defined. These variables are subsequently used by _LT_CONFIG # to write the compiler configuration to `libtool'. m4_defun([_LT_LANG_F77_CONFIG], -[AC_REQUIRE([_LT_PROG_F77])dnl -AC_LANG_PUSH(Fortran 77) +[AC_LANG_PUSH(Fortran 77) +if test -z "$F77" || test "X$F77" = "Xno"; then + _lt_disable_F77=yes +fi _LT_TAGVAR(archive_cmds_need_lc, $1)=no _LT_TAGVAR(allow_undefined_flag, $1)= @@ -6612,7 +7176,6 @@ _LT_TAGVAR(export_dynamic_flag_spec, $1)= _LT_TAGVAR(hardcode_direct, $1)=no _LT_TAGVAR(hardcode_direct_absolute, $1)=no _LT_TAGVAR(hardcode_libdir_flag_spec, $1)= -_LT_TAGVAR(hardcode_libdir_flag_spec_ld, $1)= _LT_TAGVAR(hardcode_libdir_separator, $1)= _LT_TAGVAR(hardcode_minus_L, $1)=no _LT_TAGVAR(hardcode_automatic, $1)=no @@ -6621,6 +7184,8 @@ _LT_TAGVAR(module_cmds, $1)= _LT_TAGVAR(module_expsym_cmds, $1)= _LT_TAGVAR(link_all_deplibs, $1)=unknown _LT_TAGVAR(old_archive_cmds, $1)=$old_archive_cmds +_LT_TAGVAR(reload_flag, $1)=$reload_flag +_LT_TAGVAR(reload_cmds, $1)=$reload_cmds _LT_TAGVAR(no_undefined_flag, $1)= _LT_TAGVAR(whole_archive_flag_spec, $1)= _LT_TAGVAR(enable_shared_with_static_runtimes, $1)=no @@ -6660,7 +7225,9 @@ if test "$_lt_disable_F77" != yes; then # Allow CC to be a program name with arguments. lt_save_CC="$CC" lt_save_GCC=$GCC + lt_save_CFLAGS=$CFLAGS CC=${F77-"f77"} + CFLAGS=$FFLAGS compiler=$CC _LT_TAGVAR(compiler, $1)=$CC _LT_CC_BASENAME([$compiler]) @@ -6714,38 +7281,24 @@ if test "$_lt_disable_F77" != yes; then GCC=$lt_save_GCC CC="$lt_save_CC" + CFLAGS="$lt_save_CFLAGS" fi # test "$_lt_disable_F77" != yes AC_LANG_POP ])# _LT_LANG_F77_CONFIG -# _LT_PROG_FC -# ----------- -# Since AC_PROG_FC is broken, in that it returns the empty string -# if there is no fortran compiler, we have our own version here. -m4_defun([_LT_PROG_FC], -[ -pushdef([AC_MSG_ERROR], [_lt_disable_FC=yes]) -AC_PROG_FC -if test -z "$FC" || test "X$FC" = "Xno"; then - _lt_disable_FC=yes -fi -popdef([AC_MSG_ERROR]) -])# _LT_PROG_FC - -dnl aclocal-1.4 backwards compatibility: -dnl AC_DEFUN([_LT_PROG_FC], []) - - # _LT_LANG_FC_CONFIG([TAG]) # ------------------------- # Ensure that the configuration variables for a Fortran compiler are # suitably defined. These variables are subsequently used by _LT_CONFIG # to write the compiler configuration to `libtool'. m4_defun([_LT_LANG_FC_CONFIG], -[AC_REQUIRE([_LT_PROG_FC])dnl -AC_LANG_PUSH(Fortran) +[AC_LANG_PUSH(Fortran) + +if test -z "$FC" || test "X$FC" = "Xno"; then + _lt_disable_FC=yes +fi _LT_TAGVAR(archive_cmds_need_lc, $1)=no _LT_TAGVAR(allow_undefined_flag, $1)= @@ -6755,7 +7308,6 @@ _LT_TAGVAR(export_dynamic_flag_spec, $1)= _LT_TAGVAR(hardcode_direct, $1)=no _LT_TAGVAR(hardcode_direct_absolute, $1)=no _LT_TAGVAR(hardcode_libdir_flag_spec, $1)= -_LT_TAGVAR(hardcode_libdir_flag_spec_ld, $1)= _LT_TAGVAR(hardcode_libdir_separator, $1)= _LT_TAGVAR(hardcode_minus_L, $1)=no _LT_TAGVAR(hardcode_automatic, $1)=no @@ -6764,6 +7316,8 @@ _LT_TAGVAR(module_cmds, $1)= _LT_TAGVAR(module_expsym_cmds, $1)= _LT_TAGVAR(link_all_deplibs, $1)=unknown _LT_TAGVAR(old_archive_cmds, $1)=$old_archive_cmds +_LT_TAGVAR(reload_flag, $1)=$reload_flag +_LT_TAGVAR(reload_cmds, $1)=$reload_cmds _LT_TAGVAR(no_undefined_flag, $1)= _LT_TAGVAR(whole_archive_flag_spec, $1)= _LT_TAGVAR(enable_shared_with_static_runtimes, $1)=no @@ -6803,7 +7357,9 @@ if test "$_lt_disable_FC" != yes; then # Allow CC to be a program name with arguments. lt_save_CC="$CC" lt_save_GCC=$GCC + lt_save_CFLAGS=$CFLAGS CC=${FC-"f95"} + CFLAGS=$FCFLAGS compiler=$CC GCC=$ac_cv_fc_compiler_gnu @@ -6859,7 +7415,8 @@ if test "$_lt_disable_FC" != yes; then fi # test -n "$compiler" GCC=$lt_save_GCC - CC="$lt_save_CC" + CC=$lt_save_CC + CFLAGS=$lt_save_CFLAGS fi # test "$_lt_disable_FC" != yes AC_LANG_POP @@ -6896,10 +7453,12 @@ _LT_COMPILER_BOILERPLATE _LT_LINKER_BOILERPLATE # Allow CC to be a program name with arguments. -lt_save_CC="$CC" +lt_save_CC=$CC +lt_save_CFLAGS=$CFLAGS lt_save_GCC=$GCC GCC=yes CC=${GCJ-"gcj"} +CFLAGS=$GCJFLAGS compiler=$CC _LT_TAGVAR(compiler, $1)=$CC _LT_TAGVAR(LD, $1)="$LD" @@ -6909,6 +7468,8 @@ _LT_CC_BASENAME([$compiler]) _LT_TAGVAR(archive_cmds_need_lc, $1)=no _LT_TAGVAR(old_archive_cmds, $1)=$old_archive_cmds +_LT_TAGVAR(reload_flag, $1)=$reload_flag +_LT_TAGVAR(reload_cmds, $1)=$reload_cmds ## CAVEAT EMPTOR: ## There is no encapsulation within the following macros, do not change @@ -6928,10 +7489,82 @@ fi AC_LANG_RESTORE GCC=$lt_save_GCC -CC="$lt_save_CC" +CC=$lt_save_CC +CFLAGS=$lt_save_CFLAGS ])# _LT_LANG_GCJ_CONFIG +# _LT_LANG_GO_CONFIG([TAG]) +# -------------------------- +# Ensure that the configuration variables for the GNU Go compiler +# are suitably defined. These variables are subsequently used by _LT_CONFIG +# to write the compiler configuration to `libtool'. +m4_defun([_LT_LANG_GO_CONFIG], +[AC_REQUIRE([LT_PROG_GO])dnl +AC_LANG_SAVE + +# Source file extension for Go test sources. +ac_ext=go + +# Object file extension for compiled Go test sources. +objext=o +_LT_TAGVAR(objext, $1)=$objext + +# Code to be used in simple compile tests +lt_simple_compile_test_code="package main; func main() { }" + +# Code to be used in simple link tests +lt_simple_link_test_code='package main; func main() { }' + +# ltmain only uses $CC for tagged configurations so make sure $CC is set. +_LT_TAG_COMPILER + +# save warnings/boilerplate of simple test code +_LT_COMPILER_BOILERPLATE +_LT_LINKER_BOILERPLATE + +# Allow CC to be a program name with arguments. +lt_save_CC=$CC +lt_save_CFLAGS=$CFLAGS +lt_save_GCC=$GCC +GCC=yes +CC=${GOC-"gccgo"} +CFLAGS=$GOFLAGS +compiler=$CC +_LT_TAGVAR(compiler, $1)=$CC +_LT_TAGVAR(LD, $1)="$LD" +_LT_CC_BASENAME([$compiler]) + +# Go did not exist at the time GCC didn't implicitly link libc in. +_LT_TAGVAR(archive_cmds_need_lc, $1)=no + +_LT_TAGVAR(old_archive_cmds, $1)=$old_archive_cmds +_LT_TAGVAR(reload_flag, $1)=$reload_flag +_LT_TAGVAR(reload_cmds, $1)=$reload_cmds + +## CAVEAT EMPTOR: +## There is no encapsulation within the following macros, do not change +## the running order or otherwise move them around unless you know exactly +## what you are doing... +if test -n "$compiler"; then + _LT_COMPILER_NO_RTTI($1) + _LT_COMPILER_PIC($1) + _LT_COMPILER_C_O($1) + _LT_COMPILER_FILE_LOCKS($1) + _LT_LINKER_SHLIBS($1) + _LT_LINKER_HARDCODE_LIBPATH($1) + + _LT_CONFIG($1) +fi + +AC_LANG_RESTORE + +GCC=$lt_save_GCC +CC=$lt_save_CC +CFLAGS=$lt_save_CFLAGS +])# _LT_LANG_GO_CONFIG + + # _LT_LANG_RC_CONFIG([TAG]) # ------------------------- # Ensure that the configuration variables for the Windows resource compiler @@ -6963,9 +7596,11 @@ _LT_LINKER_BOILERPLATE # Allow CC to be a program name with arguments. lt_save_CC="$CC" +lt_save_CFLAGS=$CFLAGS lt_save_GCC=$GCC GCC= CC=${RC-"windres"} +CFLAGS= compiler=$CC _LT_TAGVAR(compiler, $1)=$CC _LT_CC_BASENAME([$compiler]) @@ -6978,7 +7613,8 @@ fi GCC=$lt_save_GCC AC_LANG_RESTORE -CC="$lt_save_CC" +CC=$lt_save_CC +CFLAGS=$lt_save_CFLAGS ])# _LT_LANG_RC_CONFIG @@ -6998,6 +7634,13 @@ dnl aclocal-1.4 backwards compatibility: dnl AC_DEFUN([LT_AC_PROG_GCJ], []) +# LT_PROG_GO +# ---------- +AC_DEFUN([LT_PROG_GO], +[AC_CHECK_TOOL(GOC, gccgo,) +]) + + # LT_PROG_RC # ---------- AC_DEFUN([LT_PROG_RC], @@ -7037,6 +7680,15 @@ _LT_DECL([], [OBJDUMP], [1], [An object symbol dumper]) AC_SUBST([OBJDUMP]) ]) +# _LT_DECL_DLLTOOL +# ---------------- +# Ensure DLLTOOL variable is set. +m4_defun([_LT_DECL_DLLTOOL], +[AC_CHECK_TOOL(DLLTOOL, dlltool, false) +test -z "$DLLTOOL" && DLLTOOL=dlltool +_LT_DECL([], [DLLTOOL], [1], [DLL creation program]) +AC_SUBST([DLLTOOL]) +]) # _LT_DECL_SED # ------------ @@ -7130,8 +7782,8 @@ m4_defun([_LT_CHECK_SHELL_FEATURES], # Try some XSI features xsi_shell=no ( _lt_dummy="a/b/c" - test "${_lt_dummy##*/},${_lt_dummy%/*},"${_lt_dummy%"$_lt_dummy"}, \ - = c,a/b,, \ + test "${_lt_dummy##*/},${_lt_dummy%/*},${_lt_dummy#??}"${_lt_dummy%"$_lt_dummy"}, \ + = c,a/b,b/c, \ && eval 'test $(( 1 + 1 )) -eq 2 \ && test "${#_lt_dummy}" -eq 5' ) >/dev/null 2>&1 \ && xsi_shell=yes @@ -7170,208 +7822,162 @@ _LT_DECL([NL2SP], [lt_NL2SP], [1], [turn newlines into spaces])dnl ])# _LT_CHECK_SHELL_FEATURES -# _LT_PROG_XSI_SHELLFNS -# --------------------- -# Bourne and XSI compatible variants of some useful shell functions. -m4_defun([_LT_PROG_XSI_SHELLFNS], -[case $xsi_shell in - yes) - cat << \_LT_EOF >> "$cfgfile" - -# func_dirname file append nondir_replacement -# Compute the dirname of FILE. If nonempty, add APPEND to the result, -# otherwise set result to NONDIR_REPLACEMENT. -func_dirname () -{ - case ${1} in - */*) func_dirname_result="${1%/*}${2}" ;; - * ) func_dirname_result="${3}" ;; - esac -} - -# func_basename file -func_basename () -{ - func_basename_result="${1##*/}" -} - -# func_dirname_and_basename file append nondir_replacement -# perform func_basename and func_dirname in a single function -# call: -# dirname: Compute the dirname of FILE. If nonempty, -# add APPEND to the result, otherwise set result -# to NONDIR_REPLACEMENT. -# value returned in "$func_dirname_result" -# basename: Compute filename of FILE. -# value retuned in "$func_basename_result" -# Implementation must be kept synchronized with func_dirname -# and func_basename. For efficiency, we do not delegate to -# those functions but instead duplicate the functionality here. -func_dirname_and_basename () -{ - case ${1} in - */*) func_dirname_result="${1%/*}${2}" ;; - * ) func_dirname_result="${3}" ;; - esac - func_basename_result="${1##*/}" -} - -# func_stripname prefix suffix name -# strip PREFIX and SUFFIX off of NAME. -# PREFIX and SUFFIX must not contain globbing or regex special -# characters, hashes, percent signs, but SUFFIX may contain a leading -# dot (in which case that matches only a dot). -func_stripname () -{ - # pdksh 5.2.14 does not do ${X%$Y} correctly if both X and Y are - # positional parameters, so assign one to ordinary parameter first. - func_stripname_result=${3} - func_stripname_result=${func_stripname_result#"${1}"} - func_stripname_result=${func_stripname_result%"${2}"} -} - -# func_opt_split -func_opt_split () -{ - func_opt_split_opt=${1%%=*} - func_opt_split_arg=${1#*=} -} - -# func_lo2o object -func_lo2o () -{ - case ${1} in - *.lo) func_lo2o_result=${1%.lo}.${objext} ;; - *) func_lo2o_result=${1} ;; - esac -} - -# func_xform libobj-or-source -func_xform () -{ - func_xform_result=${1%.*}.lo -} - -# func_arith arithmetic-term... -func_arith () -{ - func_arith_result=$(( $[*] )) -} - -# func_len string -# STRING may not start with a hyphen. -func_len () -{ - func_len_result=${#1} -} +# _LT_PROG_FUNCTION_REPLACE (FUNCNAME, REPLACEMENT-BODY) +# ------------------------------------------------------ +# In `$cfgfile', look for function FUNCNAME delimited by `^FUNCNAME ()$' and +# '^} FUNCNAME ', and replace its body with REPLACEMENT-BODY. +m4_defun([_LT_PROG_FUNCTION_REPLACE], +[dnl { +sed -e '/^$1 ()$/,/^} # $1 /c\ +$1 ()\ +{\ +m4_bpatsubsts([$2], [$], [\\], [^\([ ]\)], [\\\1]) +} # Extended-shell $1 implementation' "$cfgfile" > $cfgfile.tmp \ + && mv -f "$cfgfile.tmp" "$cfgfile" \ + || (rm -f "$cfgfile" && cp "$cfgfile.tmp" "$cfgfile" && rm -f "$cfgfile.tmp") +test 0 -eq $? || _lt_function_replace_fail=: +]) -_LT_EOF - ;; - *) # Bourne compatible functions. - cat << \_LT_EOF >> "$cfgfile" -# func_dirname file append nondir_replacement -# Compute the dirname of FILE. If nonempty, add APPEND to the result, -# otherwise set result to NONDIR_REPLACEMENT. -func_dirname () -{ - # Extract subdirectory from the argument. - func_dirname_result=`$ECHO "X${1}" | $Xsed -e "$dirname"` - if test "X$func_dirname_result" = "X${1}"; then - func_dirname_result="${3}" - else - func_dirname_result="$func_dirname_result${2}" - fi -} +# _LT_PROG_REPLACE_SHELLFNS +# ------------------------- +# Replace existing portable implementations of several shell functions with +# equivalent extended shell implementations where those features are available.. +m4_defun([_LT_PROG_REPLACE_SHELLFNS], +[if test x"$xsi_shell" = xyes; then + _LT_PROG_FUNCTION_REPLACE([func_dirname], [dnl + case ${1} in + */*) func_dirname_result="${1%/*}${2}" ;; + * ) func_dirname_result="${3}" ;; + esac]) + + _LT_PROG_FUNCTION_REPLACE([func_basename], [dnl + func_basename_result="${1##*/}"]) + + _LT_PROG_FUNCTION_REPLACE([func_dirname_and_basename], [dnl + case ${1} in + */*) func_dirname_result="${1%/*}${2}" ;; + * ) func_dirname_result="${3}" ;; + esac + func_basename_result="${1##*/}"]) -# func_basename file -func_basename () -{ - func_basename_result=`$ECHO "X${1}" | $Xsed -e "$basename"` -} + _LT_PROG_FUNCTION_REPLACE([func_stripname], [dnl + # pdksh 5.2.14 does not do ${X%$Y} correctly if both X and Y are + # positional parameters, so assign one to ordinary parameter first. + func_stripname_result=${3} + func_stripname_result=${func_stripname_result#"${1}"} + func_stripname_result=${func_stripname_result%"${2}"}]) -dnl func_dirname_and_basename -dnl A portable version of this function is already defined in general.m4sh -dnl so there is no need for it here. + _LT_PROG_FUNCTION_REPLACE([func_split_long_opt], [dnl + func_split_long_opt_name=${1%%=*} + func_split_long_opt_arg=${1#*=}]) -# func_stripname prefix suffix name -# strip PREFIX and SUFFIX off of NAME. -# PREFIX and SUFFIX must not contain globbing or regex special -# characters, hashes, percent signs, but SUFFIX may contain a leading -# dot (in which case that matches only a dot). -# func_strip_suffix prefix name -func_stripname () -{ - case ${2} in - .*) func_stripname_result=`$ECHO "X${3}" \ - | $Xsed -e "s%^${1}%%" -e "s%\\\\${2}\$%%"`;; - *) func_stripname_result=`$ECHO "X${3}" \ - | $Xsed -e "s%^${1}%%" -e "s%${2}\$%%"`;; - esac -} + _LT_PROG_FUNCTION_REPLACE([func_split_short_opt], [dnl + func_split_short_opt_arg=${1#??} + func_split_short_opt_name=${1%"$func_split_short_opt_arg"}]) -# sed scripts: -my_sed_long_opt='1s/^\(-[[^=]]*\)=.*/\1/;q' -my_sed_long_arg='1s/^-[[^=]]*=//' + _LT_PROG_FUNCTION_REPLACE([func_lo2o], [dnl + case ${1} in + *.lo) func_lo2o_result=${1%.lo}.${objext} ;; + *) func_lo2o_result=${1} ;; + esac]) -# func_opt_split -func_opt_split () -{ - func_opt_split_opt=`$ECHO "X${1}" | $Xsed -e "$my_sed_long_opt"` - func_opt_split_arg=`$ECHO "X${1}" | $Xsed -e "$my_sed_long_arg"` -} + _LT_PROG_FUNCTION_REPLACE([func_xform], [ func_xform_result=${1%.*}.lo]) -# func_lo2o object -func_lo2o () -{ - func_lo2o_result=`$ECHO "X${1}" | $Xsed -e "$lo2o"` -} + _LT_PROG_FUNCTION_REPLACE([func_arith], [ func_arith_result=$(( $[*] ))]) -# func_xform libobj-or-source -func_xform () -{ - func_xform_result=`$ECHO "X${1}" | $Xsed -e 's/\.[[^.]]*$/.lo/'` -} + _LT_PROG_FUNCTION_REPLACE([func_len], [ func_len_result=${#1}]) +fi -# func_arith arithmetic-term... -func_arith () -{ - func_arith_result=`expr "$[@]"` -} +if test x"$lt_shell_append" = xyes; then + _LT_PROG_FUNCTION_REPLACE([func_append], [ eval "${1}+=\\${2}"]) -# func_len string -# STRING may not start with a hyphen. -func_len () -{ - func_len_result=`expr "$[1]" : ".*" 2>/dev/null || echo $max_cmd_len` -} + _LT_PROG_FUNCTION_REPLACE([func_append_quoted], [dnl + func_quote_for_eval "${2}" +dnl m4 expansion turns \\\\ into \\, and then the shell eval turns that into \ + eval "${1}+=\\\\ \\$func_quote_for_eval_result"]) -_LT_EOF -esac + # Save a `func_append' function call where possible by direct use of '+=' + sed -e 's%func_append \([[a-zA-Z_]]\{1,\}\) "%\1+="%g' $cfgfile > $cfgfile.tmp \ + && mv -f "$cfgfile.tmp" "$cfgfile" \ + || (rm -f "$cfgfile" && cp "$cfgfile.tmp" "$cfgfile" && rm -f "$cfgfile.tmp") + test 0 -eq $? || _lt_function_replace_fail=: +else + # Save a `func_append' function call even when '+=' is not available + sed -e 's%func_append \([[a-zA-Z_]]\{1,\}\) "%\1="$\1%g' $cfgfile > $cfgfile.tmp \ + && mv -f "$cfgfile.tmp" "$cfgfile" \ + || (rm -f "$cfgfile" && cp "$cfgfile.tmp" "$cfgfile" && rm -f "$cfgfile.tmp") + test 0 -eq $? || _lt_function_replace_fail=: +fi -case $lt_shell_append in - yes) - cat << \_LT_EOF >> "$cfgfile" +if test x"$_lt_function_replace_fail" = x":"; then + AC_MSG_WARN([Unable to substitute extended shell functions in $ofile]) +fi +]) -# func_append var value -# Append VALUE to the end of shell variable VAR. -func_append () -{ - eval "$[1]+=\$[2]" -} -_LT_EOF +# _LT_PATH_CONVERSION_FUNCTIONS +# ----------------------------- +# Determine which file name conversion functions should be used by +# func_to_host_file (and, implicitly, by func_to_host_path). These are needed +# for certain cross-compile configurations and native mingw. +m4_defun([_LT_PATH_CONVERSION_FUNCTIONS], +[AC_REQUIRE([AC_CANONICAL_HOST])dnl +AC_REQUIRE([AC_CANONICAL_BUILD])dnl +AC_MSG_CHECKING([how to convert $build file names to $host format]) +AC_CACHE_VAL(lt_cv_to_host_file_cmd, +[case $host in + *-*-mingw* ) + case $build in + *-*-mingw* ) # actually msys + lt_cv_to_host_file_cmd=func_convert_file_msys_to_w32 + ;; + *-*-cygwin* ) + lt_cv_to_host_file_cmd=func_convert_file_cygwin_to_w32 + ;; + * ) # otherwise, assume *nix + lt_cv_to_host_file_cmd=func_convert_file_nix_to_w32 + ;; + esac ;; - *) - cat << \_LT_EOF >> "$cfgfile" - -# func_append var value -# Append VALUE to the end of shell variable VAR. -func_append () -{ - eval "$[1]=\$$[1]\$[2]" -} - -_LT_EOF + *-*-cygwin* ) + case $build in + *-*-mingw* ) # actually msys + lt_cv_to_host_file_cmd=func_convert_file_msys_to_cygwin + ;; + *-*-cygwin* ) + lt_cv_to_host_file_cmd=func_convert_file_noop + ;; + * ) # otherwise, assume *nix + lt_cv_to_host_file_cmd=func_convert_file_nix_to_cygwin + ;; + esac ;; - esac + * ) # unhandled hosts (and "normal" native builds) + lt_cv_to_host_file_cmd=func_convert_file_noop + ;; +esac +]) +to_host_file_cmd=$lt_cv_to_host_file_cmd +AC_MSG_RESULT([$lt_cv_to_host_file_cmd]) +_LT_DECL([to_host_file_cmd], [lt_cv_to_host_file_cmd], + [0], [convert $build file names to $host format])dnl + +AC_MSG_CHECKING([how to convert $build file names to toolchain format]) +AC_CACHE_VAL(lt_cv_to_tool_file_cmd, +[#assume ordinary cross tools, or native build. +lt_cv_to_tool_file_cmd=func_convert_file_noop +case $host in + *-*-mingw* ) + case $build in + *-*-mingw* ) # actually msys + lt_cv_to_tool_file_cmd=func_convert_file_msys_to_w32 + ;; + esac + ;; +esac ]) +to_tool_file_cmd=$lt_cv_to_tool_file_cmd +AC_MSG_RESULT([$lt_cv_to_tool_file_cmd]) +_LT_DECL([to_tool_file_cmd], [lt_cv_to_tool_file_cmd], + [0], [convert $build files to toolchain format])dnl +])# _LT_PATH_CONVERSION_FUNCTIONS diff --git a/m4/ltdl.m4 b/m4/ltdl.m4 index aeae738..1ef84a5 100644 --- a/m4/ltdl.m4 +++ b/m4/ltdl.m4 @@ -1,13 +1,13 @@ # ltdl.m4 - Configure ltdl for the target system. -*-Autoconf-*- # -# Copyright (C) 1999-2006, 2007, 2008 Free Software Foundation, Inc. +# Copyright (C) 1999-2006, 2007, 2008, 2011 Free Software Foundation, Inc. # Written by Thomas Tanner, 1999 # # This file is free software; the Free Software Foundation gives # unlimited permission to copy and/or distribute it, with or without # modifications, as long as this notice is preserved. -# serial 17 LTDL_INIT +# serial 18 LTDL_INIT # LT_CONFIG_LTDL_DIR(DIRECTORY, [LTDL-MODE]) # ------------------------------------------ @@ -407,10 +407,16 @@ AC_CHECK_HEADERS([unistd.h dl.h sys/dl.h dld.h mach-o/dyld.h dirent.h], AC_CHECK_FUNCS([closedir opendir readdir], [], [AC_LIBOBJ([lt__dirent])]) AC_CHECK_FUNCS([strlcat strlcpy], [], [AC_LIBOBJ([lt__strl])]) +m4_pattern_allow([LT_LIBEXT])dnl AC_DEFINE_UNQUOTED([LT_LIBEXT],["$libext"],[The archive extension]) +name= +eval "lt_libprefix=\"$libname_spec\"" +m4_pattern_allow([LT_LIBPREFIX])dnl +AC_DEFINE_UNQUOTED([LT_LIBPREFIX],["$lt_libprefix"],[The archive prefix]) + name=ltdl -LTDLOPEN=`eval "\\$ECHO \"$libname_spec\""` +eval "LTDLOPEN=\"$libname_spec\"" AC_SUBST([LTDLOPEN]) ])# _LTDL_SETUP @@ -547,12 +553,19 @@ AC_CACHE_CHECK([which extension is used for runtime loadable modules], [ module=yes eval libltdl_cv_shlibext=$shrext_cmds +module=no +eval libltdl_cv_shrext=$shrext_cmds ]) if test -n "$libltdl_cv_shlibext"; then m4_pattern_allow([LT_MODULE_EXT])dnl AC_DEFINE_UNQUOTED([LT_MODULE_EXT], ["$libltdl_cv_shlibext"], [Define to the extension used for runtime loadable modules, say, ".so".]) fi +if test "$libltdl_cv_shrext" != "$libltdl_cv_shlibext"; then + m4_pattern_allow([LT_SHARED_EXT])dnl + AC_DEFINE_UNQUOTED([LT_SHARED_EXT], ["$libltdl_cv_shrext"], + [Define to the shared library suffix, say, ".dylib".]) +fi ])# LT_SYS_MODULE_EXT # Old name: diff --git a/m4/ltoptions.m4 b/m4/ltoptions.m4 index 34151a3..5d9acd8 100644 --- a/m4/ltoptions.m4 +++ b/m4/ltoptions.m4 @@ -1,13 +1,14 @@ # Helper functions for option handling. -*- Autoconf -*- # -# Copyright (C) 2004, 2005, 2007, 2008 Free Software Foundation, Inc. +# Copyright (C) 2004, 2005, 2007, 2008, 2009 Free Software Foundation, +# Inc. # Written by Gary V. Vaughan, 2004 # # This file is free software; the Free Software Foundation gives # unlimited permission to copy and/or distribute it, with or without # modifications, as long as this notice is preserved. -# serial 6 ltoptions.m4 +# serial 7 ltoptions.m4 # This is to help aclocal find these macros, as it can't see m4_define. AC_DEFUN([LTOPTIONS_VERSION], [m4_if([1])]) @@ -125,7 +126,7 @@ LT_OPTION_DEFINE([LT_INIT], [win32-dll], [enable_win32_dll=yes case $host in -*-*-cygwin* | *-*-mingw* | *-*-pw32* | *-cegcc*) +*-*-cygwin* | *-*-mingw* | *-*-pw32* | *-*-cegcc*) AC_CHECK_TOOL(AS, as, false) AC_CHECK_TOOL(DLLTOOL, dlltool, false) AC_CHECK_TOOL(OBJDUMP, objdump, false) @@ -133,13 +134,13 @@ case $host in esac test -z "$AS" && AS=as -_LT_DECL([], [AS], [0], [Assembler program])dnl +_LT_DECL([], [AS], [1], [Assembler program])dnl test -z "$DLLTOOL" && DLLTOOL=dlltool -_LT_DECL([], [DLLTOOL], [0], [DLL creation program])dnl +_LT_DECL([], [DLLTOOL], [1], [DLL creation program])dnl test -z "$OBJDUMP" && OBJDUMP=objdump -_LT_DECL([], [OBJDUMP], [0], [Object dumper program])dnl +_LT_DECL([], [OBJDUMP], [1], [Object dumper program])dnl ])# win32-dll AU_DEFUN([AC_LIBTOOL_WIN32_DLL], @@ -325,9 +326,24 @@ dnl AC_DEFUN([AM_DISABLE_FAST_INSTALL], []) # MODE is either `yes' or `no'. If omitted, it defaults to `both'. m4_define([_LT_WITH_PIC], [AC_ARG_WITH([pic], - [AS_HELP_STRING([--with-pic], + [AS_HELP_STRING([--with-pic@<:@=PKGS@:>@], [try to use only PIC/non-PIC objects @<:@default=use both@:>@])], - [pic_mode="$withval"], + [lt_p=${PACKAGE-default} + case $withval in + yes|no) pic_mode=$withval ;; + *) + pic_mode=default + # Look at the argument we got. We use all the common list separators. + lt_save_ifs="$IFS"; IFS="${IFS}$PATH_SEPARATOR," + for lt_pkg in $withval; do + IFS="$lt_save_ifs" + if test "X$lt_pkg" = "X$lt_p"; then + pic_mode=yes + fi + done + IFS="$lt_save_ifs" + ;; + esac], [pic_mode=default]) test -z "$pic_mode" && pic_mode=m4_default([$1], [default]) diff --git a/m4/ltversion.m4 b/m4/ltversion.m4 index f3c5309..07a8602 100644 --- a/m4/ltversion.m4 +++ b/m4/ltversion.m4 @@ -7,17 +7,17 @@ # unlimited permission to copy and/or distribute it, with or without # modifications, as long as this notice is preserved. -# Generated from ltversion.in. +# @configure_input@ -# serial 3017 ltversion.m4 +# serial 3337 ltversion.m4 # This file is part of GNU Libtool -m4_define([LT_PACKAGE_VERSION], [2.2.6b]) -m4_define([LT_PACKAGE_REVISION], [1.3017]) +m4_define([LT_PACKAGE_VERSION], [2.4.2]) +m4_define([LT_PACKAGE_REVISION], [1.3337]) AC_DEFUN([LTVERSION_VERSION], -[macro_version='2.2.6b' -macro_revision='1.3017' +[macro_version='2.4.2' +macro_revision='1.3337' _LT_DECL(, macro_version, 0, [Which release of libtool.m4 was used?]) _LT_DECL(, macro_revision, 0) ]) diff --git a/m4/lt~obsolete.m4 b/m4/lt~obsolete.m4 index 637bb20..c573da9 100644 --- a/m4/lt~obsolete.m4 +++ b/m4/lt~obsolete.m4 @@ -1,13 +1,13 @@ # lt~obsolete.m4 -- aclocal satisfying obsolete definitions. -*-Autoconf-*- # -# Copyright (C) 2004, 2005, 2007 Free Software Foundation, Inc. +# Copyright (C) 2004, 2005, 2007, 2009 Free Software Foundation, Inc. # Written by Scott James Remnant, 2004. # # This file is free software; the Free Software Foundation gives # unlimited permission to copy and/or distribute it, with or without # modifications, as long as this notice is preserved. -# serial 4 lt~obsolete.m4 +# serial 5 lt~obsolete.m4 # These exist entirely to fool aclocal when bootstrapping libtool. # @@ -77,7 +77,6 @@ m4_ifndef([AC_DISABLE_FAST_INSTALL], [AC_DEFUN([AC_DISABLE_FAST_INSTALL])]) m4_ifndef([_LT_AC_LANG_CXX], [AC_DEFUN([_LT_AC_LANG_CXX])]) m4_ifndef([_LT_AC_LANG_F77], [AC_DEFUN([_LT_AC_LANG_F77])]) m4_ifndef([_LT_AC_LANG_GCJ], [AC_DEFUN([_LT_AC_LANG_GCJ])]) -m4_ifndef([AC_LIBTOOL_RC], [AC_DEFUN([AC_LIBTOOL_RC])]) m4_ifndef([AC_LIBTOOL_LANG_C_CONFIG], [AC_DEFUN([AC_LIBTOOL_LANG_C_CONFIG])]) m4_ifndef([_LT_AC_LANG_C_CONFIG], [AC_DEFUN([_LT_AC_LANG_C_CONFIG])]) m4_ifndef([AC_LIBTOOL_LANG_CXX_CONFIG], [AC_DEFUN([AC_LIBTOOL_LANG_CXX_CONFIG])]) @@ -90,3 +89,10 @@ m4_ifndef([AC_LIBTOOL_LANG_RC_CONFIG], [AC_DEFUN([AC_LIBTOOL_LANG_RC_CONFIG])]) m4_ifndef([_LT_AC_LANG_RC_CONFIG], [AC_DEFUN([_LT_AC_LANG_RC_CONFIG])]) m4_ifndef([AC_LIBTOOL_CONFIG], [AC_DEFUN([AC_LIBTOOL_CONFIG])]) m4_ifndef([_LT_AC_FILE_LTDLL_C], [AC_DEFUN([_LT_AC_FILE_LTDLL_C])]) +m4_ifndef([_LT_REQUIRED_DARWIN_CHECKS], [AC_DEFUN([_LT_REQUIRED_DARWIN_CHECKS])]) +m4_ifndef([_LT_AC_PROG_CXXCPP], [AC_DEFUN([_LT_AC_PROG_CXXCPP])]) +m4_ifndef([_LT_PREPARE_SED_QUOTE_VARS], [AC_DEFUN([_LT_PREPARE_SED_QUOTE_VARS])]) +m4_ifndef([_LT_PROG_ECHO_BACKSLASH], [AC_DEFUN([_LT_PROG_ECHO_BACKSLASH])]) +m4_ifndef([_LT_PROG_F77], [AC_DEFUN([_LT_PROG_F77])]) +m4_ifndef([_LT_PROG_FC], [AC_DEFUN([_LT_PROG_FC])]) +m4_ifndef([_LT_PROG_CXX], [AC_DEFUN([_LT_PROG_CXX])]) diff --git a/missing b/missing index 28055d2..86a8fc3 100755 --- a/missing +++ b/missing @@ -1,10 +1,10 @@ #! /bin/sh # Common stub for a few missing GNU programs while installing. -scriptversion=2009-04-28.21; # UTC +scriptversion=2012-01-06.13; # UTC # Copyright (C) 1996, 1997, 1999, 2000, 2002, 2003, 2004, 2005, 2006, -# 2008, 2009 Free Software Foundation, Inc. +# 2008, 2009, 2010, 2011, 2012 Free Software Foundation, Inc. # Originally by Fran,cois Pinard , 1996. # This program is free software; you can redistribute it and/or modify @@ -84,7 +84,6 @@ Supported PROGRAM values: help2man touch the output file lex create \`lex.yy.c', if possible, from existing .c makeinfo touch the output file - tar try tar, gnutar, gtar, then tar without non-portable flags yacc create \`y.tab.[ch]', if possible, from existing .[ch] Version suffixes to PROGRAM as well as the prefixes \`gnu-', \`gnu', and @@ -122,15 +121,6 @@ case $1 in # Not GNU programs, they don't have --version. ;; - tar*) - if test -n "$run"; then - echo 1>&2 "ERROR: \`tar' requires --run" - exit 1 - elif test "x$2" = "x--version" || test "x$2" = "x--help"; then - exit 1 - fi - ;; - *) if test -z "$run" && ($1 --version) > /dev/null 2>&1; then # We have it, but it failed. @@ -226,7 +216,7 @@ WARNING: \`$1' $msg. You should only need it if \`Bison' from any GNU archive site." rm -f y.tab.c y.tab.h if test $# -ne 1; then - eval LASTARG="\${$#}" + eval LASTARG=\${$#} case $LASTARG in *.y) SRCFILE=`echo "$LASTARG" | sed 's/y$/c/'` @@ -256,7 +246,7 @@ WARNING: \`$1' is $msg. You should only need it if \`Flex' from any GNU archive site." rm -f lex.yy.c if test $# -ne 1; then - eval LASTARG="\${$#}" + eval LASTARG=\${$#} case $LASTARG in *.l) SRCFILE=`echo "$LASTARG" | sed 's/l$/c/'` @@ -318,41 +308,6 @@ WARNING: \`$1' is $msg. You should only need it if touch $file ;; - tar*) - shift - - # We have already tried tar in the generic part. - # Look for gnutar/gtar before invocation to avoid ugly error - # messages. - if (gnutar --version > /dev/null 2>&1); then - gnutar "$@" && exit 0 - fi - if (gtar --version > /dev/null 2>&1); then - gtar "$@" && exit 0 - fi - firstarg="$1" - if shift; then - case $firstarg in - *o*) - firstarg=`echo "$firstarg" | sed s/o//` - tar "$firstarg" "$@" && exit 0 - ;; - esac - case $firstarg in - *h*) - firstarg=`echo "$firstarg" | sed s/h//` - tar "$firstarg" "$@" && exit 0 - ;; - esac - fi - - echo 1>&2 "\ -WARNING: I can't seem to be able to run \`tar' with the given arguments. - You may want to install GNU tar or Free paxutils, or check the - command line arguments." - exit 1 - ;; - *) echo 1>&2 "\ WARNING: \`$1' is needed, and is $msg. diff --git a/pkgconfig/Makefile.am b/pkgconfig/Makefile.am index 5173f03..ca0c393 100644 --- a/pkgconfig/Makefile.am +++ b/pkgconfig/Makefile.am @@ -1,22 +1,35 @@ pcfiles = \ + gnunetats.pc \ gnunetarm.pc \ gnunetblock.pc \ gnunetcore.pc \ gnunetdatacache.pc \ gnunetdatastore.pc \ gnunetdht.pc \ - gnunetdhtlog.pc \ + gnunetdns.pc \ + gnunetdnsparser.pc \ gnunetdv.pc \ gnunetfragmentation.pc \ gnunetfs.pc \ + gnunetgns.pc \ gnunethello.pc \ - gnunetnse.pc \ + gnunetlockmanager.pc \ + gnunetmesh.pc \ + gnunetmysql.pc \ + gnunetnamestore.pc \ gnunetnat.pc \ + gnunetnse.pc \ gnunetpeerinfo.pc \ + gnunetpostgres.pc \ + gnunetregex.pc \ gnunetstatistics.pc \ + gnunetstream.pc \ + gnunettestbed.pc \ gnunettesting.pc \ gnunettransport.pc \ - gnunetutil.pc + gnunettun.pc \ + gnunetutil.pc \ + gnunetvpn.pc all-local: $(pcfiles) @@ -32,23 +45,36 @@ pkgconfig_DATA = $(pcfiles) EXTRA_DIST = \ gnunetarm.pc.in \ + gnunetats.pc.in \ gnunetblock.pc.in \ gnunetcore.pc.in \ gnunetdatacache.pc.in \ gnunetdatastore.pc.in \ gnunetdht.pc.in \ - gnunetdhtlog.pc.in \ + gnunetdns.pc.in \ + gnunetdnsparser.pc.in \ gnunetdv.pc.in \ gnunetfragmentation.pc.in \ gnunetfs.pc.in \ + gnunetgns.pc.in \ gnunethello.pc.in \ + gnunetlockmanager.pc.in \ + gnunetmesh.pc.in \ + gnunetmysql.pc.in \ + gnunetnamestore.pc.in \ gnunetnat.pc.in \ gnunetnse.pc.in \ gnunetpeerinfo.pc.in \ + gnunetpostgres.pc.in \ + gnunetregex.pc.in \ gnunetstatistics.pc.in \ + gnunetstream.pc.in \ + gnunettestbed.pc.in \ gnunettesting.pc.in \ gnunettransport.pc.in \ - gnunetutil.pc.in + gnunettun.pc.in \ + gnunetutil.pc.in \ + gnunetvpn.pc.in CLEANFILES = $(pcfiles) INCLUDES = -I$(top_srcdir)/src/include diff --git a/pkgconfig/Makefile.in b/pkgconfig/Makefile.in index 7177ec3..0755fd6 100644 --- a/pkgconfig/Makefile.in +++ b/pkgconfig/Makefile.in @@ -1,9 +1,9 @@ -# Makefile.in generated by automake 1.11.1 from Makefile.am. +# Makefile.in generated by automake 1.11.6 from Makefile.am. # @configure_input@ # Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, -# 2003, 2004, 2005, 2006, 2007, 2008, 2009 Free Software Foundation, -# Inc. +# 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Free Software +# Foundation, Inc. # This Makefile.in is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. @@ -16,6 +16,23 @@ @SET_MAKE@ VPATH = @srcdir@ +am__make_dryrun = \ + { \ + am__dry=no; \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + echo 'am--echo: ; @echo "AM" OK' | $(MAKE) -f - 2>/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } pkgdatadir = $(datadir)/@PACKAGE@ pkgincludedir = $(includedir)/@PACKAGE@ pkglibdir = $(libdir)/@PACKAGE@ @@ -37,48 +54,63 @@ host_triplet = @host@ target_triplet = @target@ subdir = pkgconfig DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in \ - $(srcdir)/gnunetarm.pc.in $(srcdir)/gnunetblock.pc.in \ - $(srcdir)/gnunetcore.pc.in $(srcdir)/gnunetdatacache.pc.in \ + $(srcdir)/gnunetarm.pc.in $(srcdir)/gnunetats.pc.in \ + $(srcdir)/gnunetblock.pc.in $(srcdir)/gnunetcore.pc.in \ + $(srcdir)/gnunetdatacache.pc.in \ $(srcdir)/gnunetdatastore.pc.in $(srcdir)/gnunetdht.pc.in \ - $(srcdir)/gnunetdhtlog.pc.in $(srcdir)/gnunetdv.pc.in \ - $(srcdir)/gnunetfragmentation.pc.in $(srcdir)/gnunetfs.pc.in \ - $(srcdir)/gnunethello.pc.in $(srcdir)/gnunetnat.pc.in \ + $(srcdir)/gnunetdns.pc.in $(srcdir)/gnunetdnsparser.pc.in \ + $(srcdir)/gnunetdv.pc.in $(srcdir)/gnunetfragmentation.pc.in \ + $(srcdir)/gnunetfs.pc.in $(srcdir)/gnunetgns.pc.in \ + $(srcdir)/gnunethello.pc.in $(srcdir)/gnunetlockmanager.pc.in \ + $(srcdir)/gnunetmesh.pc.in $(srcdir)/gnunetmysql.pc.in \ + $(srcdir)/gnunetnamestore.pc.in $(srcdir)/gnunetnat.pc.in \ $(srcdir)/gnunetnse.pc.in $(srcdir)/gnunetpeerinfo.pc.in \ - $(srcdir)/gnunetregex.pc.in $(srcdir)/gnunetstatistics.pc.in \ - $(srcdir)/gnunettesting.pc.in $(srcdir)/gnunettransport.pc.in \ - $(srcdir)/gnunetutil.pc.in + $(srcdir)/gnunetpostgres.pc.in $(srcdir)/gnunetregex.pc.in \ + $(srcdir)/gnunetstatistics.pc.in $(srcdir)/gnunetstream.pc.in \ + $(srcdir)/gnunettestbed.pc.in $(srcdir)/gnunettesting.pc.in \ + $(srcdir)/gnunettransport.pc.in $(srcdir)/gnunettun.pc.in \ + $(srcdir)/gnunetutil.pc.in $(srcdir)/gnunetvpn.pc.in ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 am__aclocal_m4_deps = $(top_srcdir)/m4/absolute-header.m4 \ $(top_srcdir)/m4/align.m4 $(top_srcdir)/m4/argz.m4 \ - $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/iconv.m4 \ - $(top_srcdir)/m4/lib-ld.m4 $(top_srcdir)/m4/lib-link.m4 \ - $(top_srcdir)/m4/lib-prefix.m4 $(top_srcdir)/m4/libcurl.m4 \ - $(top_srcdir)/m4/libgcrypt.m4 $(top_srcdir)/m4/libtool.m4 \ - $(top_srcdir)/m4/libunistring.m4 $(top_srcdir)/m4/ltdl.m4 \ - $(top_srcdir)/m4/ltoptions.m4 $(top_srcdir)/m4/ltsugar.m4 \ - $(top_srcdir)/m4/ltversion.m4 $(top_srcdir)/m4/lt~obsolete.m4 \ - $(top_srcdir)/m4/nls.m4 $(top_srcdir)/m4/po.m4 \ + $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/glib-2.0.m4 \ + $(top_srcdir)/m4/iconv.m4 $(top_srcdir)/m4/lib-ld.m4 \ + $(top_srcdir)/m4/lib-link.m4 $(top_srcdir)/m4/lib-prefix.m4 \ + $(top_srcdir)/m4/libcurl.m4 $(top_srcdir)/m4/libgcrypt.m4 \ + $(top_srcdir)/m4/libtool.m4 $(top_srcdir)/m4/libunistring.m4 \ + $(top_srcdir)/m4/ltdl.m4 $(top_srcdir)/m4/ltoptions.m4 \ + $(top_srcdir)/m4/ltsugar.m4 $(top_srcdir)/m4/ltversion.m4 \ + $(top_srcdir)/m4/lt~obsolete.m4 $(top_srcdir)/m4/nls.m4 \ + $(top_srcdir)/m4/pkg.m4 $(top_srcdir)/m4/po.m4 \ $(top_srcdir)/m4/progtest.m4 $(top_srcdir)/acinclude.m4 \ $(top_srcdir)/configure.ac am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ $(ACLOCAL_M4) mkinstalldirs = $(install_sh) -d CONFIG_HEADER = $(top_builddir)/gnunet_config.h -CONFIG_CLEAN_FILES = gnunetarm.pc gnunetblock.pc gnunetcore.pc \ - gnunetdatacache.pc gnunetdatastore.pc gnunetdht.pc \ - gnunetdhtlog.pc gnunetdv.pc gnunetfragmentation.pc gnunetfs.pc \ - gnunethello.pc gnunetnat.pc gnunetnse.pc gnunetpeerinfo.pc \ - gnunetregex.pc gnunetstatistics.pc gnunettesting.pc \ - gnunettransport.pc gnunetutil.pc +CONFIG_CLEAN_FILES = gnunetats.pc gnunetarm.pc gnunetblock.pc \ + gnunetcore.pc gnunetdatacache.pc gnunetdatastore.pc \ + gnunetdht.pc gnunetdns.pc gnunetdnsparser.pc gnunetdv.pc \ + gnunetfragmentation.pc gnunetfs.pc gnunetgns.pc gnunethello.pc \ + gnunetlockmanager.pc gnunetmesh.pc gnunetmysql.pc \ + gnunetnamestore.pc gnunetnat.pc gnunetnse.pc gnunetpeerinfo.pc \ + gnunetpostgres.pc gnunetregex.pc gnunetstatistics.pc \ + gnunetstream.pc gnunettestbed.pc gnunettesting.pc \ + gnunettransport.pc gnunettun.pc gnunetutil.pc gnunetvpn.pc CONFIG_CLEAN_VPATH_FILES = -AM_V_GEN = $(am__v_GEN_$(V)) -am__v_GEN_ = $(am__v_GEN_$(AM_DEFAULT_VERBOSITY)) +AM_V_GEN = $(am__v_GEN_@AM_V@) +am__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@) am__v_GEN_0 = @echo " GEN " $@; -AM_V_at = $(am__v_at_$(V)) -am__v_at_ = $(am__v_at_$(AM_DEFAULT_VERBOSITY)) +AM_V_at = $(am__v_at_@AM_V@) +am__v_at_ = $(am__v_at_@AM_DEFAULT_V@) am__v_at_0 = @ SOURCES = DIST_SOURCES = +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac am__vpath_adj_setup = srcdirstrip=`echo "$(srcdir)" | sed 's|.|.|g'`; am__vpath_adj = case $$p in \ $(srcdir)/*) f=`echo "$$p" | sed "s|^$$srcdirstrip/||"`;; \ @@ -100,6 +132,12 @@ am__nobase_list = $(am__nobase_strip_setup); \ am__base_list = \ sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \ sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g' +am__uninstall_files_from_dir = { \ + test -z "$$files" \ + || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \ + || { echo " ( cd '$$dir' && rm -f" $$files ")"; \ + $(am__cd) "$$dir" && rm -f $$files; }; \ + } am__installdirs = "$(DESTDIR)$(pkgconfigdir)" DATA = $(pkgconfig_DATA) DISTFILES = $(DIST_COMMON) $(DIST_SOURCES) $(TEXINFOS) $(EXTRA_DIST) @@ -138,6 +176,10 @@ EXEEXT = @EXEEXT@ EXT_LIBS = @EXT_LIBS@ EXT_LIB_PATH = @EXT_LIB_PATH@ FGREP = @FGREP@ +GLIB_CFLAGS = @GLIB_CFLAGS@ +GLIB_GENMARSHAL = @GLIB_GENMARSHAL@ +GLIB_LIBS = @GLIB_LIBS@ +GLIB_MKENUMS = @GLIB_MKENUMS@ GMSGFMT = @GMSGFMT@ GMSGFMT_015 = @GMSGFMT_015@ GNUNETDNS_GROUP = @GNUNETDNS_GROUP@ @@ -148,6 +190,7 @@ GN_LIBINTL = @GN_LIBINTL@ GN_LIB_LDFLAGS = @GN_LIB_LDFLAGS@ GN_PLUGIN_LDFLAGS = @GN_PLUGIN_LDFLAGS@ GN_USER_HOME_DIR = @GN_USER_HOME_DIR@ +GOBJECT_QUERY = @GOBJECT_QUERY@ GREP = @GREP@ HAVE_LIBUNISTRING = @HAVE_LIBUNISTRING@ INCLTDL = @INCLTDL@ @@ -170,6 +213,8 @@ LIBCURL_CPPFLAGS = @LIBCURL_CPPFLAGS@ LIBGCRYPT_CFLAGS = @LIBGCRYPT_CFLAGS@ LIBGCRYPT_CONFIG = @LIBGCRYPT_CONFIG@ LIBGCRYPT_LIBS = @LIBGCRYPT_LIBS@ +LIBGTOP_CFLAGS = @LIBGTOP_CFLAGS@ +LIBGTOP_LIBS = @LIBGTOP_LIBS@ LIBICONV = @LIBICONV@ LIBINTL = @LIBINTL@ LIBLTDL = @LIBLTDL@ @@ -191,6 +236,7 @@ LT_CONFIG_H = @LT_CONFIG_H@ LT_DLLOADERS = @LT_DLLOADERS@ LT_DLPREOPEN = @LT_DLPREOPEN@ MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ MKDIR_P = @MKDIR_P@ MONKEYPREFIX = @MONKEYPREFIX@ MSGFMT = @MSGFMT@ @@ -200,6 +246,7 @@ MYSQL_CPPFLAGS = @MYSQL_CPPFLAGS@ MYSQL_LDFLAGS = @MYSQL_LDFLAGS@ NM = @NM@ NMEDIT = @NMEDIT@ +NSS_DIR = @NSS_DIR@ OBJC = @OBJC@ OBJCDEPMODE = @OBJCDEPMODE@ OBJCFLAGS = @OBJCFLAGS@ @@ -215,6 +262,7 @@ PACKAGE_TARNAME = @PACKAGE_TARNAME@ PACKAGE_URL = @PACKAGE_URL@ PACKAGE_VERSION = @PACKAGE_VERSION@ PATH_SEPARATOR = @PATH_SEPARATOR@ +PKG_CONFIG = @PKG_CONFIG@ POSTGRES_CPPFLAGS = @POSTGRES_CPPFLAGS@ POSTGRES_LDFLAGS = @POSTGRES_LDFLAGS@ POSUB = @POSUB@ @@ -246,6 +294,7 @@ abs_builddir = @abs_builddir@ abs_srcdir = @abs_srcdir@ abs_top_builddir = @abs_top_builddir@ abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ ac_ct_CC = @ac_ct_CC@ ac_ct_CXX = @ac_ct_CXX@ ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ @@ -268,6 +317,7 @@ datarootdir = @datarootdir@ docdir = @docdir@ dvidir = @dvidir@ exec_prefix = @exec_prefix@ +gitcommand = @gitcommand@ host = @host@ host_alias = @host_alias@ host_cpu = @host_cpu@ @@ -281,7 +331,6 @@ libdir = @libdir@ libexecdir = @libexecdir@ localedir = @localedir@ localstatedir = @localstatedir@ -lt_ECHO = @lt_ECHO@ ltdl_LIBOBJS = @ltdl_LIBOBJS@ ltdl_LTLIBOBJS = @ltdl_LTLIBOBJS@ mandir = @mandir@ @@ -299,6 +348,7 @@ sbindir = @sbindir@ sharedstatedir = @sharedstatedir@ srcdir = @srcdir@ subdirs = @subdirs@ +svnversioncommand = @svnversioncommand@ sys_symbol_underscore = @sys_symbol_underscore@ sysconfdir = @sysconfdir@ target = @target@ @@ -310,24 +360,37 @@ top_build_prefix = @top_build_prefix@ top_builddir = @top_builddir@ top_srcdir = @top_srcdir@ pcfiles = \ + gnunetats.pc \ gnunetarm.pc \ gnunetblock.pc \ gnunetcore.pc \ gnunetdatacache.pc \ gnunetdatastore.pc \ gnunetdht.pc \ - gnunetdhtlog.pc \ + gnunetdns.pc \ + gnunetdnsparser.pc \ gnunetdv.pc \ gnunetfragmentation.pc \ gnunetfs.pc \ + gnunetgns.pc \ gnunethello.pc \ - gnunetnse.pc \ + gnunetlockmanager.pc \ + gnunetmesh.pc \ + gnunetmysql.pc \ + gnunetnamestore.pc \ gnunetnat.pc \ + gnunetnse.pc \ gnunetpeerinfo.pc \ + gnunetpostgres.pc \ + gnunetregex.pc \ gnunetstatistics.pc \ + gnunetstream.pc \ + gnunettestbed.pc \ gnunettesting.pc \ gnunettransport.pc \ - gnunetutil.pc + gnunettun.pc \ + gnunetutil.pc \ + gnunetvpn.pc cp_verbose = $(cp_verbose_$(V)) cp_verbose_ = $(cp_verbose_$(AM_DEFAULT_VERBOSITY)) @@ -336,23 +399,36 @@ pkgconfigdir = $(libdir)/pkgconfig pkgconfig_DATA = $(pcfiles) EXTRA_DIST = \ gnunetarm.pc.in \ + gnunetats.pc.in \ gnunetblock.pc.in \ gnunetcore.pc.in \ gnunetdatacache.pc.in \ gnunetdatastore.pc.in \ gnunetdht.pc.in \ - gnunetdhtlog.pc.in \ + gnunetdns.pc.in \ + gnunetdnsparser.pc.in \ gnunetdv.pc.in \ gnunetfragmentation.pc.in \ gnunetfs.pc.in \ + gnunetgns.pc.in \ gnunethello.pc.in \ + gnunetlockmanager.pc.in \ + gnunetmesh.pc.in \ + gnunetmysql.pc.in \ + gnunetnamestore.pc.in \ gnunetnat.pc.in \ gnunetnse.pc.in \ gnunetpeerinfo.pc.in \ + gnunetpostgres.pc.in \ + gnunetregex.pc.in \ gnunetstatistics.pc.in \ + gnunetstream.pc.in \ + gnunettestbed.pc.in \ gnunettesting.pc.in \ gnunettransport.pc.in \ - gnunetutil.pc.in + gnunettun.pc.in \ + gnunetutil.pc.in \ + gnunetvpn.pc.in CLEANFILES = $(pcfiles) INCLUDES = -I$(top_srcdir)/src/include @@ -389,6 +465,8 @@ $(top_srcdir)/configure: $(am__configure_deps) $(ACLOCAL_M4): $(am__aclocal_m4_deps) cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh $(am__aclocal_m4_deps): +gnunetats.pc: $(top_builddir)/config.status $(srcdir)/gnunetats.pc.in + cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ gnunetarm.pc: $(top_builddir)/config.status $(srcdir)/gnunetarm.pc.in cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ gnunetblock.pc: $(top_builddir)/config.status $(srcdir)/gnunetblock.pc.in @@ -401,7 +479,9 @@ gnunetdatastore.pc: $(top_builddir)/config.status $(srcdir)/gnunetdatastore.pc.i cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ gnunetdht.pc: $(top_builddir)/config.status $(srcdir)/gnunetdht.pc.in cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ -gnunetdhtlog.pc: $(top_builddir)/config.status $(srcdir)/gnunetdhtlog.pc.in +gnunetdns.pc: $(top_builddir)/config.status $(srcdir)/gnunetdns.pc.in + cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ +gnunetdnsparser.pc: $(top_builddir)/config.status $(srcdir)/gnunetdnsparser.pc.in cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ gnunetdv.pc: $(top_builddir)/config.status $(srcdir)/gnunetdv.pc.in cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ @@ -409,24 +489,44 @@ gnunetfragmentation.pc: $(top_builddir)/config.status $(srcdir)/gnunetfragmentat cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ gnunetfs.pc: $(top_builddir)/config.status $(srcdir)/gnunetfs.pc.in cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ +gnunetgns.pc: $(top_builddir)/config.status $(srcdir)/gnunetgns.pc.in + cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ gnunethello.pc: $(top_builddir)/config.status $(srcdir)/gnunethello.pc.in cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ +gnunetlockmanager.pc: $(top_builddir)/config.status $(srcdir)/gnunetlockmanager.pc.in + cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ +gnunetmesh.pc: $(top_builddir)/config.status $(srcdir)/gnunetmesh.pc.in + cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ +gnunetmysql.pc: $(top_builddir)/config.status $(srcdir)/gnunetmysql.pc.in + cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ +gnunetnamestore.pc: $(top_builddir)/config.status $(srcdir)/gnunetnamestore.pc.in + cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ gnunetnat.pc: $(top_builddir)/config.status $(srcdir)/gnunetnat.pc.in cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ gnunetnse.pc: $(top_builddir)/config.status $(srcdir)/gnunetnse.pc.in cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ gnunetpeerinfo.pc: $(top_builddir)/config.status $(srcdir)/gnunetpeerinfo.pc.in cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ +gnunetpostgres.pc: $(top_builddir)/config.status $(srcdir)/gnunetpostgres.pc.in + cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ gnunetregex.pc: $(top_builddir)/config.status $(srcdir)/gnunetregex.pc.in cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ gnunetstatistics.pc: $(top_builddir)/config.status $(srcdir)/gnunetstatistics.pc.in cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ +gnunetstream.pc: $(top_builddir)/config.status $(srcdir)/gnunetstream.pc.in + cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ +gnunettestbed.pc: $(top_builddir)/config.status $(srcdir)/gnunettestbed.pc.in + cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ gnunettesting.pc: $(top_builddir)/config.status $(srcdir)/gnunettesting.pc.in cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ gnunettransport.pc: $(top_builddir)/config.status $(srcdir)/gnunettransport.pc.in cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ +gnunettun.pc: $(top_builddir)/config.status $(srcdir)/gnunettun.pc.in + cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ gnunetutil.pc: $(top_builddir)/config.status $(srcdir)/gnunetutil.pc.in cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ +gnunetvpn.pc: $(top_builddir)/config.status $(srcdir)/gnunetvpn.pc.in + cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ mostlyclean-libtool: -rm -f *.lo @@ -435,8 +535,11 @@ clean-libtool: -rm -rf .libs _libs install-pkgconfigDATA: $(pkgconfig_DATA) @$(NORMAL_INSTALL) - test -z "$(pkgconfigdir)" || $(MKDIR_P) "$(DESTDIR)$(pkgconfigdir)" @list='$(pkgconfig_DATA)'; test -n "$(pkgconfigdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(pkgconfigdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(pkgconfigdir)" || exit 1; \ + fi; \ for p in $$list; do \ if test -f "$$p"; then d=; else d="$(srcdir)/"; fi; \ echo "$$d$$p"; \ @@ -450,9 +553,7 @@ uninstall-pkgconfigDATA: @$(NORMAL_UNINSTALL) @list='$(pkgconfig_DATA)'; test -n "$(pkgconfigdir)" || list=; \ files=`for p in $$list; do echo $$p; done | sed -e 's|^.*/||'`; \ - test -n "$$files" || exit 0; \ - echo " ( cd '$(DESTDIR)$(pkgconfigdir)' && rm -f" $$files ")"; \ - cd "$(DESTDIR)$(pkgconfigdir)" && rm -f $$files + dir='$(DESTDIR)$(pkgconfigdir)'; $(am__uninstall_files_from_dir) tags: TAGS TAGS: @@ -507,10 +608,15 @@ install-am: all-am installcheck: installcheck-am install-strip: - $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ - install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ - `test -z '$(STRIP)' || \ - echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi mostlyclean-generic: clean-generic: diff --git a/pkgconfig/gnunetats.pc.in b/pkgconfig/gnunetats.pc.in new file mode 100644 index 0000000..c95469f --- /dev/null +++ b/pkgconfig/gnunetats.pc.in @@ -0,0 +1,12 @@ +prefix=@prefix@ +exec_prefix=@exec_prefix@ +libdir=@libdir@ +includedir=@includedir@ + +Name: GNUnet ATS +Description: Provides API for allocating bandwidth, expressing preferences for certain peers and accessing allocation information +URL: http://gnunet.org +Version: @VERSION@ +Requires: +Libs: -L${libdir} -lgnunetats +Cflags: -I${includedir} diff --git a/pkgconfig/gnunetcore.pc.in b/pkgconfig/gnunetcore.pc.in index 66a469a..e1d52ed 100644 --- a/pkgconfig/gnunetcore.pc.in +++ b/pkgconfig/gnunetcore.pc.in @@ -4,7 +4,7 @@ libdir=@libdir@ includedir=@includedir@ Name: GNUnet core -Description: Provides API to access core service +Description: Provides API for (encrypted) P2P communication URL: http://gnunet.org Version: @VERSION@ Requires: diff --git a/pkgconfig/gnunetdatacache.pc.in b/pkgconfig/gnunetdatacache.pc.in index e69875e..1e85136 100644 --- a/pkgconfig/gnunetdatacache.pc.in +++ b/pkgconfig/gnunetdatacache.pc.in @@ -4,7 +4,7 @@ libdir=@libdir@ includedir=@includedir@ Name: GNUnet datacache -Description: Provides datacache API implementation +Description: Provides datacache API for temporary storage to disk URL: http://gnunet.org Version: @VERSION@ Requires: diff --git a/pkgconfig/gnunetdatastore.pc.in b/pkgconfig/gnunetdatastore.pc.in index 9a0ddf8..249426a 100644 --- a/pkgconfig/gnunetdatastore.pc.in +++ b/pkgconfig/gnunetdatastore.pc.in @@ -4,7 +4,7 @@ libdir=@libdir@ includedir=@includedir@ Name: GNUnet datastore -Description: Management API for the datastore for files stored on a GNUnet node +Description: Management API for the datastore for persistant storage to disk URL: http://gnunet.org Version: @VERSION@ Requires: diff --git a/pkgconfig/gnunetdhtlog.pc.in b/pkgconfig/gnunetdhtlog.pc.in deleted file mode 100644 index 29fcef0..0000000 --- a/pkgconfig/gnunetdhtlog.pc.in +++ /dev/null @@ -1,12 +0,0 @@ -prefix=@prefix@ -exec_prefix=@exec_prefix@ -libdir=@libdir@ -includedir=@includedir@ - -Name: GNUnet dhtlog -Description: Library for logging DHT operations via plugins -URL: http://gnunet.org -Version: @VERSION@ -Requires: -Libs: -L${libdir} -lgnunetdhtlog -Cflags: -I${includedir} diff --git a/pkgconfig/gnunetdns.pc.in b/pkgconfig/gnunetdns.pc.in new file mode 100644 index 0000000..9f215f3 --- /dev/null +++ b/pkgconfig/gnunetdns.pc.in @@ -0,0 +1,12 @@ +prefix=@prefix@ +exec_prefix=@exec_prefix@ +libdir=@libdir@ +includedir=@includedir@ + +Name: GNUnet DNS +Description: Provides API to access GNUnet's DNS service (to intercept and manipulate DNS queries) +URL: http://gnunet.org +Version: @VERSION@ +Requires: +Libs: -L${libdir} -lgnunetdns +Cflags: -I${includedir} diff --git a/pkgconfig/gnunetdnsparser.pc.in b/pkgconfig/gnunetdnsparser.pc.in new file mode 100644 index 0000000..ffb5fca --- /dev/null +++ b/pkgconfig/gnunetdnsparser.pc.in @@ -0,0 +1,12 @@ +prefix=@prefix@ +exec_prefix=@exec_prefix@ +libdir=@libdir@ +includedir=@includedir@ + +Name: GNUnet DNS parser +Description: Provides API for parsing and serializing DNS packets +URL: http://gnunet.org +Version: @VERSION@ +Requires: +Libs: -L${libdir} -lgnunetdnsparser +Cflags: -I${includedir} diff --git a/pkgconfig/gnunetgns.pc.in b/pkgconfig/gnunetgns.pc.in new file mode 100644 index 0000000..fa0f8ea --- /dev/null +++ b/pkgconfig/gnunetgns.pc.in @@ -0,0 +1,12 @@ +prefix=@prefix@ +exec_prefix=@exec_prefix@ +libdir=@libdir@ +includedir=@includedir@ + +Name: GNUnet GNS +Description: Provides API to access the GNUnet Naming System +URL: http://gnunet.org +Version: @VERSION@ +Requires: +Libs: -L${libdir} -lgnunetgns +Cflags: -I${includedir} diff --git a/pkgconfig/gnunetlockmanager.pc.in b/pkgconfig/gnunetlockmanager.pc.in new file mode 100644 index 0000000..d2c4f7b --- /dev/null +++ b/pkgconfig/gnunetlockmanager.pc.in @@ -0,0 +1,12 @@ +prefix=@prefix@ +exec_prefix=@exec_prefix@ +libdir=@libdir@ +includedir=@includedir@ + +Name: GNUnet Lockmanager +Description: Provides API for mutual exclusion between GNUnet services +URL: http://gnunet.org +Version: @VERSION@ +Requires: +Libs: -L${libdir} -lgnunetlockmanager +Cflags: -I${includedir} diff --git a/pkgconfig/gnunetmesh.pc.in b/pkgconfig/gnunetmesh.pc.in new file mode 100644 index 0000000..e6ed8de --- /dev/null +++ b/pkgconfig/gnunetmesh.pc.in @@ -0,0 +1,12 @@ +prefix=@prefix@ +exec_prefix=@exec_prefix@ +libdir=@libdir@ +includedir=@includedir@ + +Name: GNUnet Mesh +Description: API for multicast and multi-hop routing between GNUnet peers +URL: http://gnunet.org +Version: @VERSION@ +Requires: +Libs: -L${libdir} -lgnunetmesh +Cflags: -I${includedir} diff --git a/pkgconfig/gnunetmysql.pc.in b/pkgconfig/gnunetmysql.pc.in new file mode 100644 index 0000000..a3d547f --- /dev/null +++ b/pkgconfig/gnunetmysql.pc.in @@ -0,0 +1,12 @@ +prefix=@prefix@ +exec_prefix=@exec_prefix@ +libdir=@libdir@ +includedir=@includedir@ + +Name: GNUnet MySQL +Description: Provides API for common interactions with libmysqlclient +URL: http://gnunet.org +Version: @VERSION@ +Requires: +Libs: -L${libdir} -lgnunetmysql +Cflags: -I${includedir} diff --git a/pkgconfig/gnunetnamestore.pc.in b/pkgconfig/gnunetnamestore.pc.in new file mode 100644 index 0000000..964c6eb --- /dev/null +++ b/pkgconfig/gnunetnamestore.pc.in @@ -0,0 +1,12 @@ +prefix=@prefix@ +exec_prefix=@exec_prefix@ +libdir=@libdir@ +includedir=@includedir@ + +Name: GNUnet Namestore +Description: Provides API for storing GNS records to a database +URL: http://gnunet.org +Version: @VERSION@ +Requires: +Libs: -L${libdir} -lgnunetnamestore +Cflags: -I${includedir} diff --git a/pkgconfig/gnunetpostgres.pc.in b/pkgconfig/gnunetpostgres.pc.in new file mode 100644 index 0000000..5d82315 --- /dev/null +++ b/pkgconfig/gnunetpostgres.pc.in @@ -0,0 +1,12 @@ +prefix=@prefix@ +exec_prefix=@exec_prefix@ +libdir=@libdir@ +includedir=@includedir@ + +Name: GNUnet Postgres +Description: API with common functions for interacting with libpq +URL: http://gnunet.org +Version: @VERSION@ +Requires: +Libs: -L${libdir} -lgnunetpostgres +Cflags: -I${includedir} diff --git a/pkgconfig/gnunetstream.pc.in b/pkgconfig/gnunetstream.pc.in new file mode 100644 index 0000000..47c4dde --- /dev/null +++ b/pkgconfig/gnunetstream.pc.in @@ -0,0 +1,12 @@ +prefix=@prefix@ +exec_prefix=@exec_prefix@ +libdir=@libdir@ +includedir=@includedir@ + +Name: GNUnet Stream +Description: Provides API for reliable, in-order communcation between two peers +URL: http://gnunet.org +Version: @VERSION@ +Requires: +Libs: -L${libdir} -lgnunetstream +Cflags: -I${includedir} diff --git a/pkgconfig/gnunettestbed.pc.in b/pkgconfig/gnunettestbed.pc.in new file mode 100644 index 0000000..cf4fffb --- /dev/null +++ b/pkgconfig/gnunettestbed.pc.in @@ -0,0 +1,12 @@ +prefix=@prefix@ +exec_prefix=@exec_prefix@ +libdir=@libdir@ +includedir=@includedir@ + +Name: GNUnet Testbed +Description: Provides API for deploying and managing testbeds +URL: http://gnunet.org +Version: @VERSION@ +Requires: +Libs: -L${libdir} -lgnunettestbed +Cflags: -I${includedir} diff --git a/pkgconfig/gnunettun.pc.in b/pkgconfig/gnunettun.pc.in new file mode 100644 index 0000000..2a3bd52 --- /dev/null +++ b/pkgconfig/gnunettun.pc.in @@ -0,0 +1,12 @@ +prefix=@prefix@ +exec_prefix=@exec_prefix@ +libdir=@libdir@ +includedir=@includedir@ + +Name: GNUnet TUN +Description: Provides API for parsing IP packets for Linux TUN interface interaction +URL: http://gnunet.org +Version: @VERSION@ +Requires: +Libs: -L${libdir} -lgnunettun +Cflags: -I${includedir} diff --git a/pkgconfig/gnunetvpn.pc.in b/pkgconfig/gnunetvpn.pc.in new file mode 100644 index 0000000..db8d6f9 --- /dev/null +++ b/pkgconfig/gnunetvpn.pc.in @@ -0,0 +1,12 @@ +prefix=@prefix@ +exec_prefix=@exec_prefix@ +libdir=@libdir@ +includedir=@includedir@ + +Name: GNUnet VPN +Description: Provides API for accessing the GNUnet VPN +URL: http://gnunet.org +Version: @VERSION@ +Requires: +Libs: -L${libdir} -lgnunetvpn +Cflags: -I${includedir} diff --git a/po/POTFILES.in b/po/POTFILES.in index 198daf9..8e2c75f 100644 --- a/po/POTFILES.in +++ b/po/POTFILES.in @@ -7,16 +7,21 @@ src/ats/ats_api_performance.c src/ats/ats_api_scheduling.c src/ats/gnunet-service-ats_addresses.c src/ats/gnunet-service-ats_addresses_mlp.c +src/ats/gnunet-service-ats_addresses_simplistic.c src/ats/gnunet-service-ats.c src/ats/gnunet-service-ats_performance.c src/ats/gnunet-service-ats_reservations.c src/ats/gnunet-service-ats_scheduling.c +src/ats-tool/gnunet-ats.c src/block/block.c src/block/plugin_block_template.c src/block/plugin_block_test.c -src/chat/chat.c -src/chat/gnunet-chat.c -src/chat/gnunet-service-chat.c +src/consensus/consensus_api.c +src/consensus/gnunet-consensus.c +src/consensus/gnunet-consensus-ibf.c +src/consensus/gnunet-consensus-start-peers.c +src/consensus/gnunet-service-consensus.c +src/consensus/ibf.c src/core/core_api.c src/core/core_api_is_connected.c src/core/core_api_iterate_peers.c @@ -28,17 +33,19 @@ src/core/gnunet-service-core_neighbours.c src/core/gnunet-service-core_sessions.c src/core/gnunet-service-core_typemap.c src/datacache/datacache.c -src/datacache/plugin_datacache_mysql.c +src/datacache/plugin_datacache_heap.c src/datacache/plugin_datacache_postgres.c src/datacache/plugin_datacache_sqlite.c src/datacache/plugin_datacache_template.c src/datastore/datastore_api.c src/datastore/gnunet-service-datastore.c +src/datastore/plugin_datastore_heap.c src/datastore/plugin_datastore_mysql.c src/datastore/plugin_datastore_postgres.c src/datastore/plugin_datastore_sqlite.c src/datastore/plugin_datastore_template.c src/dht/dht_api.c +src/dht/dht_test_lib.c src/dht/gnunet-dht-get.c src/dht/gnunet-dht-monitor.c src/dht/gnunet-dht-put.c @@ -52,6 +59,7 @@ src/dht/gnunet-service-dht_routing.c src/dht/plugin_block_dht.c src/dns/dns_api.c src/dns/dnsparser.c +src/dns/dnsstub.c src/dns/gnunet-dns-monitor.c src/dns/gnunet-dns-redirector.c src/dns/gnunet-helper-dns.c @@ -62,6 +70,7 @@ src/dv/gnunet-service-dv.c src/dv/plugin_transport_dv.c src/exit/gnunet-daemon-exit.c src/exit/gnunet-helper-exit.c +src/exit/gnunet-helper-exit-windows.c src/fragmentation/defragmentation.c src/fragmentation/fragmentation.c src/fs/fs_api.c @@ -82,9 +91,12 @@ src/fs/fs_test_lib.c src/fs/fs_tree.c src/fs/fs_unindex.c src/fs/fs_uri.c +src/fs/gnunet-auto-share.c +src/fs/gnunet-daemon-fsprofiler.c src/fs/gnunet-directory.c src/fs/gnunet-download.c src/fs/gnunet-fs.c +src/fs/gnunet-fs-profiler.c src/fs/gnunet-helper-fs-publish.c src/fs/gnunet-pseudonym.c src/fs/gnunet-publish.c @@ -97,11 +109,15 @@ src/fs/gnunet-service-fs_pe.c src/fs/gnunet-service-fs_pr.c src/fs/gnunet-service-fs_push.c src/fs/gnunet-service-fs_put.c +src/fs/gnunet-service-fs_stream.c src/fs/gnunet-unindex.c src/fs/plugin_block_fs.c src/gns/gns_api.c +src/gns/gns_common.c +src/gns/gnunet-dns2gns.c src/gns/gnunet-gns.c src/gns/gnunet-gns-fcfsd.c +src/gns/gnunet-gns-helper-service-w32.c src/gns/gnunet-gns-proxy.c src/gns/gnunet-service-gns.c src/gns/gnunet-service-gns_interceptor.c @@ -109,6 +125,10 @@ src/gns/gnunet-service-gns_resolver.c src/gns/nss/nss_gns.c src/gns/nss/nss_gns_query.c src/gns/plugin_block_gns.c +src/gns/w32nsp.c +src/gns/w32nsp-install.c +src/gns/w32nsp-resolve.c +src/gns/w32nsp-uninstall.c src/hello/address.c src/hello/gnunet-hello.c src/hello/hello.c @@ -118,20 +138,27 @@ src/hostlist/hostlist-server.c src/integration-tests/connection_watchdog.c src/lockmanager/gnunet-service-lockmanager.c src/lockmanager/lockmanager_api.c +src/mesh/gnunet-mesh.c src/mesh/gnunet-service-mesh.c +src/mesh/gnunet-service-mesh-new.c src/mesh/mesh_api.c +src/mesh/mesh_common.c +src/mesh/mesh_test_lib.c src/mesh/mesh_tunnel_tree.c +src/mesh/plugin_block_mesh.c src/mysql/mysql.c src/namestore/gnunet-namestore.c src/namestore/gnunet-service-namestore.c src/namestore/namestore_api.c src/namestore/namestore_common.c +src/namestore/plugin_namestore_postgres.c src/namestore/plugin_namestore_sqlite.c src/nat/gnunet-helper-nat-client.c src/nat/gnunet-helper-nat-client-windows.c src/nat/gnunet-helper-nat-server.c src/nat/gnunet-helper-nat-server-windows.c src/nat/gnunet-nat-server.c +src/nat/nat_auto.c src/nat/nat.c src/nat/nat_mini.c src/nat/nat_test.c @@ -145,27 +172,45 @@ src/peerinfo-tool/gnunet-peerinfo.c src/peerinfo-tool/gnunet-peerinfo_plugins.c src/postgres/postgres.c src/pt/gnunet-daemon-pt.c +src/regex/gnunet-daemon-regexprofiler.c +src/regex/gnunet-regex-profiler.c +src/regex/gnunet-regex-simulation-profiler.c +src/regex/perf-regex.c +src/regex/plugin_block_regex.c +src/regex/regex_block_lib.c src/regex/regex.c +src/regex/regex_dht.c +src/regex/regex_graph.c +src/regex/regex_random.c +src/regex/regex_test_lib.c src/statistics/gnunet-service-statistics.c src/statistics/gnunet-statistics.c src/statistics/statistics_api.c src/stream/stream_api.c +src/sysmon/gnunet-service-sysmon.c src/template/gnunet-service-template.c src/template/gnunet-template.c +src/testbed/gnunet-helper-testbed.c +src/testbed/gnunet_mpi_test.c +src/testbed/gnunet-service-testbed.c +src/testbed/gnunet-service-testbed_cache.c +src/testbed/gnunet-service-testbed_oc.c +src/testbed/gnunet-testbed-profiler.c +src/testbed/ll_master.c +src/testbed/ll_monitor.c +src/testbed/standard_deviation.c src/testbed/testbed_api.c src/testbed/testbed_api_hosts.c src/testbed/testbed_api_operations.c src/testbed/testbed_api_peers.c src/testbed/testbed_api_services.c +src/testbed/testbed_api_statistics.c src/testbed/testbed_api_testbed.c src/testbed/testbed_api_test.c src/testbed/testbed_api_topology.c src/testing/gnunet-testing.c -src/testing/helper.c +src/testing/gnunet-testing-run-service.c src/testing/testing.c -src/testing/testing_group.c -src/testing/testing_new.c -src/testing/testing_peergroup.c src/topology/gnunet-daemon-topology.c src/transport/gnunet-helper-transport-wlan.c src/transport/gnunet-helper-transport-wlan-dummy.c @@ -173,15 +218,19 @@ src/transport/gnunet-service-transport_blacklist.c src/transport/gnunet-service-transport.c src/transport/gnunet-service-transport_clients.c src/transport/gnunet-service-transport_hello.c +src/transport/gnunet-service-transport_manipulation.c src/transport/gnunet-service-transport_neighbours.c src/transport/gnunet-service-transport_plugins.c src/transport/gnunet-service-transport_validation.c src/transport/gnunet-transport.c src/transport/gnunet-transport-certificate-creation.c +src/transport/gnunet-transport-wlan-receiver.c src/transport/gnunet-transport-wlan-sender.c src/transport/plugin_transport_http.c src/transport/plugin_transport_http_client.c +src/transport/plugin_transport_http_common.c src/transport/plugin_transport_http_server.c +src/transport/plugin_transport_smtp.c src/transport/plugin_transport_tcp.c src/transport/plugin_transport_template.c src/transport/plugin_transport_udp_broadcasting.c @@ -209,6 +258,7 @@ src/util/container_multihashmap.c src/util/container_slist.c src/util/crypto_aes.c src/util/crypto_crc.c +src/util/crypto_ecc.c src/util/crypto_hash.c src/util/crypto_hkdf.c src/util/crypto_kdf.c @@ -218,10 +268,13 @@ src/util/crypto_rsa.c src/util/disk.c src/util/getopt.c src/util/getopt_helpers.c +src/util/gnunet-config.c src/util/gnunet-config-diff.c +src/util/gnunet-ecc.c src/util/gnunet-resolver.c src/util/gnunet-rsa.c src/util/gnunet-service-resolver.c +src/util/gnunet-uri.c src/util/helper.c src/util/load.c src/util/network.c @@ -243,8 +296,11 @@ src/util/signal.c src/util/speedup.c src/util/strings.c src/util/time.c +src/util/w32cat.c +src/util/win.c src/util/winproc.c src/vpn/gnunet-helper-vpn.c +src/vpn/gnunet-helper-vpn-windows.c src/vpn/gnunet-service-vpn.c src/vpn/gnunet-vpn.c src/vpn/vpn_api.c @@ -252,3 +308,5 @@ src/dht/dht.h src/include/gnunet_common.h src/include/gnunet_postgres_lib.h src/include/gnunet_time_lib.h +src/testbed/testbed_api.h +src/testbed/testbed_api_operations.h diff --git a/po/de.gmo b/po/de.gmo index 729be3a..dc340e0 100644 Binary files a/po/de.gmo and b/po/de.gmo differ diff --git a/po/de.po b/po/de.po index 7f15916..7464a85 100644 --- a/po/de.po +++ b/po/de.po @@ -7,7 +7,7 @@ msgid "" msgstr "" "Project-Id-Version: GNUnet 0.7.0b\n" "Report-Msgid-Bugs-To: gnunet-developers@mail.gnu.org\n" -"POT-Creation-Date: 2012-06-05 15:47+0200\n" +"POT-Creation-Date: 2013-02-05 19:22+0100\n" "PO-Revision-Date: 2006-03-17 21:37+0100\n" "Last-Translator: Nils Durner \n" "Language-Team: German \n" @@ -17,274 +17,218 @@ msgstr "" "Content-Transfer-Encoding: 8bit\n" "Plural-Forms: nplurals=2; plural=(n != 1);\n" -#: src/arm/arm_api.c:165 +#: src/arm/arm_api.c:162 #, fuzzy msgid "Failed to transmit shutdown request to client.\n" msgstr "Fehler beim Senden einer `%s' Anfrage an den SMTP Server.\n" -#: src/arm/arm_api.c:349 -#, fuzzy, c-format -msgid "Configuration failes to specify option `%s' in section `%s'!\n" -msgstr "" -"Die Konfigurationsdatei muss in der Sektion `%s' unter `%s' ein Verzeichnis " -"angeben, in dem FS Daten gespeichert werden.\n" - -#: src/arm/arm_api.c:363 -#, fuzzy, c-format -msgid "Configuration fails to specify option `%s' in section `%s'!\n" -msgstr "" -"Die Konfigurationsdatei muss in der Sektion `%s' unter `%s' ein Verzeichnis " -"angeben, in dem FS Daten gespeichert werden.\n" - -#: src/arm/arm_api.c:432 -#, fuzzy, c-format -msgid "Error receiving response to `%s' request from ARM for service `%s'\n" -msgstr "Beschädigte Antwort auf `%s' von Knoten `%s' empfangen.\n" - -#: src/arm/arm_api.c:485 -#, c-format -msgid "Requesting start of service `%s'.\n" -msgstr "" - -#: src/arm/arm_api.c:486 -#, c-format -msgid "Requesting termination of service `%s'.\n" -msgstr "" - -#: src/arm/arm_api.c:507 -#, c-format -msgid "Error while trying to transmit request to start `%s' to ARM\n" -msgstr "" - -#: src/arm/arm_api.c:508 -#, c-format -msgid "Error while trying to transmit request to stop `%s' to ARM\n" -msgstr "" - -#: src/arm/arm_api.c:540 -#, fuzzy, c-format -msgid "Asked to start service `%s' within %llu ms\n" -msgstr "`%s': Nachricht wurde nicht innerhalb %llu ms empfangen.\n" - -#: src/arm/arm_api.c:612 -#, fuzzy, c-format -msgid "Stopping service `%s' within %llu ms\n" -msgstr "Keine Antwort innerhalb %llums erhalten.\n" - -#: src/arm/gnunet-arm.c:159 +#: src/arm/gnunet-arm.c:166 #, fuzzy, c-format msgid "Service `%s' is unknown to ARM.\n" msgstr "Namespace `%s' hat das Rating %d.\n" -#: src/arm/gnunet-arm.c:164 +#: src/arm/gnunet-arm.c:171 #, fuzzy, c-format msgid "Service `%s' has been stopped.\n" msgstr "Dienst gelöscht.\n" -#: src/arm/gnunet-arm.c:167 +#: src/arm/gnunet-arm.c:174 #, fuzzy, c-format msgid "Service `%s' was already running.\n" msgstr "Diese Suche läuft bereits!\n" -#: src/arm/gnunet-arm.c:172 +#: src/arm/gnunet-arm.c:179 #, fuzzy, c-format msgid "Service `%s' has been started.\n" msgstr "Dienst gelöscht.\n" -#: src/arm/gnunet-arm.c:175 +#: src/arm/gnunet-arm.c:182 #, fuzzy, c-format msgid "Service `%s' was already being stopped.\n" msgstr "Dienst gelöscht.\n" -#: src/arm/gnunet-arm.c:179 +#: src/arm/gnunet-arm.c:186 #, fuzzy, c-format msgid "Service `%s' was already not running.\n" msgstr "Diese Suche läuft bereits!\n" -#: src/arm/gnunet-arm.c:183 +#: src/arm/gnunet-arm.c:190 #, fuzzy msgid "Request ignored as ARM is shutting down.\n" msgstr "`%s' fährt herunter.\n" -#: src/arm/gnunet-arm.c:187 +#: src/arm/gnunet-arm.c:194 #, fuzzy msgid "Error communicating with ARM service.\n" msgstr "Informationen über andere GNUnet Knoten ausgeben." -#: src/arm/gnunet-arm.c:191 +#: src/arm/gnunet-arm.c:198 #, fuzzy msgid "Timeout communicating with ARM service.\n" msgstr "Informationen über andere GNUnet Knoten ausgeben." -#: src/arm/gnunet-arm.c:195 +#: src/arm/gnunet-arm.c:202 #, fuzzy msgid "Operation failed.\n" msgstr "Absicherung fehlgeschlagen bei %s:%d.\n" -#: src/arm/gnunet-arm.c:199 +#: src/arm/gnunet-arm.c:206 msgid "Unknown response code from ARM.\n" msgstr "" -#: src/arm/gnunet-arm.c:222 +#: src/arm/gnunet-arm.c:229 #, fuzzy msgid "Error communicating with ARM. ARM not running?\n" msgstr "Informationen über andere GNUnet Knoten ausgeben." -#: src/arm/gnunet-arm.c:225 +#: src/arm/gnunet-arm.c:232 #, fuzzy msgid "Running services:\n" msgstr "Collection `%s' begonnen.\n" -#: src/arm/gnunet-arm.c:249 -#, fuzzy, c-format -msgid "Fatal configuration error: `%s' option in section `%s' missing.\n" -msgstr "" -"Es muss eine Liste von Freunden in der Konfigurationsdatei unter `%s' in der " -"Sektion `%s' angegeben werden.\n" - -#: src/arm/gnunet-arm.c:257 src/arm/gnunet-arm.c:357 src/arm/gnunet-arm.c:373 -msgid "Fatal error initializing ARM API.\n" -msgstr "" - -#: src/arm/gnunet-arm.c:280 +#: src/arm/gnunet-arm.c:253 #, fuzzy, c-format msgid "Failed to remove configuration file %s\n" msgstr "Fehler beim Speichern der Konfigurationsdatei `%s':" -#: src/arm/gnunet-arm.c:286 +#: src/arm/gnunet-arm.c:259 #, fuzzy, c-format msgid "Failed to remove servicehome directory %s\n" msgstr "Dateiformat fehlerhaft (kein GNUnet Verzeichnis?)\n" -#: src/arm/gnunet-arm.c:407 +#: src/arm/gnunet-arm.c:322 src/arm/gnunet-arm.c:407 src/arm/gnunet-arm.c:424 +msgid "Fatal error initializing ARM API.\n" +msgstr "" + +#: src/arm/gnunet-arm.c:453 msgid "stop all GNUnet services" msgstr "" -#: src/arm/gnunet-arm.c:409 +#: src/arm/gnunet-arm.c:455 msgid "start a particular service" msgstr "" -#: src/arm/gnunet-arm.c:411 +#: src/arm/gnunet-arm.c:457 msgid "stop a particular service" msgstr "" -#: src/arm/gnunet-arm.c:413 +#: src/arm/gnunet-arm.c:459 msgid "start all GNUnet default services" msgstr "" -#: src/arm/gnunet-arm.c:416 +#: src/arm/gnunet-arm.c:462 msgid "stop and start all GNUnet default services" msgstr "" -#: src/arm/gnunet-arm.c:419 +#: src/arm/gnunet-arm.c:465 msgid "delete config file and directory on exit" msgstr "" -#: src/arm/gnunet-arm.c:421 +#: src/arm/gnunet-arm.c:467 msgid "don't print status messages" msgstr "" -#: src/arm/gnunet-arm.c:424 +#: src/arm/gnunet-arm.c:470 #, fuzzy -msgid "timeout for completing current operation" +msgid "timeout in MSECS milliseconds for completing current operation" msgstr "Zeit, die gewartet wird, bis der Durchlauf fertiggestellt wird (in ms)" -#: src/arm/gnunet-arm.c:426 -msgid "List currently running services" +#: src/arm/gnunet-arm.c:472 +#, fuzzy +msgid "list currently running services" +msgstr "Collection `%s' begonnen.\n" + +#: src/arm/gnunet-arm.c:474 +msgid "don't let gnunet-service-arm inherit standard output" +msgstr "" + +#: src/arm/gnunet-arm.c:476 +msgid "don't let gnunet-service-arm inherit standard error" msgstr "" -#: src/arm/gnunet-arm.c:437 +#: src/arm/gnunet-arm.c:487 msgid "Control services and the Automated Restart Manager (ARM)" msgstr "" -#: src/arm/gnunet-service-arm.c:332 +#: src/arm/gnunet-service-arm.c:345 #, fuzzy, c-format msgid "Failed to start service `%s'\n" msgstr "Der Transportdienst auf Port %d konnte nicht gestartet werden.\n" -#: src/arm/gnunet-service-arm.c:335 +#: src/arm/gnunet-service-arm.c:348 #, fuzzy, c-format msgid "Starting service `%s'\n" msgstr "Collection `%s' begonnen.\n" -#: src/arm/gnunet-service-arm.c:361 +#: src/arm/gnunet-service-arm.c:374 #, fuzzy msgid "Could not send status result to client\n" msgstr "Anfrage konnte nicht an gnunetd gesendet werden.\n" -#: src/arm/gnunet-service-arm.c:393 +#: src/arm/gnunet-service-arm.c:406 #, fuzzy msgid "Could not send list result to client\n" msgstr "Anfrage konnte nicht an gnunetd gesendet werden.\n" -#: src/arm/gnunet-service-arm.c:523 +#: src/arm/gnunet-service-arm.c:537 #, fuzzy, c-format msgid "Unable to create socket for service `%s': %s\n" msgstr "Fehler beim Anlegen des Benutzerkontos:" -#: src/arm/gnunet-service-arm.c:545 +#: src/arm/gnunet-service-arm.c:559 #, c-format msgid "Unable to bind listening socket for service `%s' to address `%s': %s\n" msgstr "" -#: src/arm/gnunet-service-arm.c:559 +#: src/arm/gnunet-service-arm.c:573 #, c-format msgid "ARM now monitors connections to service `%s' at `%s'\n" msgstr "" -#: src/arm/gnunet-service-arm.c:667 +#: src/arm/gnunet-service-arm.c:681 #, fuzzy, c-format msgid "Preparing to stop `%s'\n" msgstr "Collection `%s' begonnen.\n" -#: src/arm/gnunet-service-arm.c:878 +#: src/arm/gnunet-service-arm.c:892 #, fuzzy, c-format msgid "Restarting service `%s'.\n" msgstr "Collection `%s' begonnen.\n" -#: src/arm/gnunet-service-arm.c:970 +#: src/arm/gnunet-service-arm.c:985 msgid "exit" msgstr "" -#: src/arm/gnunet-service-arm.c:975 +#: src/arm/gnunet-service-arm.c:990 msgid "signal" msgstr "" -#: src/arm/gnunet-service-arm.c:980 +#: src/arm/gnunet-service-arm.c:995 #, fuzzy msgid "unknown" msgstr "Unbekannter Fehler" -#: src/arm/gnunet-service-arm.c:986 +#: src/arm/gnunet-service-arm.c:1001 #, fuzzy, c-format -msgid "Service `%s' took %llu ms to terminate\n" +msgid "Service `%s' took %s to terminate\n" msgstr "Dienst gelöscht.\n" -#: src/arm/gnunet-service-arm.c:1021 +#: src/arm/gnunet-service-arm.c:1036 #, c-format msgid "Service `%s' terminated with status %s/%d, will restart in %llu ms\n" msgstr "" -#: src/arm/gnunet-service-arm.c:1127 -#, fuzzy, c-format -msgid "Configuration file `%s' for service `%s' not valid: %s\n" -msgstr "Konfigurationsdatei `%s' wurde erzeugt.\n" - -#: src/arm/gnunet-service-arm.c:1129 -msgid "option missing" -msgstr "" - -#: src/arm/gnunet-service-arm.c:1213 +#: src/arm/gnunet-service-arm.c:1228 #, fuzzy, c-format msgid "Starting default services `%s'\n" msgstr "Collection `%s' begonnen.\n" -#: src/arm/gnunet-service-arm.c:1224 +#: src/arm/gnunet-service-arm.c:1239 #, c-format msgid "Default service `%s' not configured correctly!\n" msgstr "" -#: src/arm/gnunet-service-arm.c:1238 +#: src/arm/gnunet-service-arm.c:1253 msgid "" "No default services configured, GNUnet will not really start right now.\n" msgstr "" @@ -293,301 +237,265 @@ msgstr "" msgid "Initiating shutdown as requested by client.\n" msgstr "" -#: src/block/block.c:105 -#, fuzzy, c-format -msgid "Loading block plugin `%s'\n" -msgstr "Teste Transport(e) %s\n" - -#: src/chat/chat.c:175 -#, fuzzy -msgid "Could not transmit confirmation receipt\n" -msgstr "Auf die Namespace Informationen konnte nicht zugegriffen werden.\n" - -#: src/chat/chat.c:283 -msgid "The current user must be the the first one joined\n" -msgstr "" - -#: src/chat/chat.c:412 -#, fuzzy, c-format -msgid "Unknown message type: '%u'\n" -msgstr "Unbekannte Operation `%s'\n" - -#: src/chat/chat.c:472 -#, fuzzy, c-format -msgid "Configuration option `%s' in section `%s' missing\n" -msgstr "Konfigurationsdatei `%s' wurde erzeugt.\n" - -#: src/chat/chat.c:480 +#: src/ats/ats_api_performance.c:465 #, fuzzy, c-format -msgid "Failed to access chat home directory `%s'\n" -msgstr "Dateiformat fehlerhaft (kein GNUnet Verzeichnis?)\n" +msgid "Received %s message\n" +msgstr "ungültige `%s' Nachricht empfangen\n" -#: src/chat/chat.c:498 +#: src/ats/ats_api_performance.c:508 #, fuzzy, c-format -msgid "Failed to create/open key in file `%s'\n" -msgstr "Datei wurde als `%s' gespeichert.\n" - -#: src/chat/chat.c:559 -#, fuzzy -msgid "Could not serialize metadata\n" -msgstr "Konnte libgnunetutil nicht initialisieren!\n" - -#: src/chat/chat.c:674 -#, fuzzy -msgid "Failed to connect to the chat service\n" -msgstr "Es konnte keine Verbindung mit gnunetd hergestellt werden.\n" - -#: src/chat/chat.c:680 -msgid "Undefined mandatory parameter: joinCallback\n" -msgstr "" +msgid "Received last message for %s \n" +msgstr "GAP hat ungültige Inhalte von `%s' empfangen.\n" -#: src/chat/chat.c:686 -msgid "Undefined mandatory parameter: messageCallback\n" +#: src/ats/gnunet-service-ats_addresses.c:993 +#: src/ats/gnunet-service-ats_addresses.c:1027 +#, c-format +msgid "" +"Could not load quota for network `%s': `%s', assigning default bandwidth " +"%llu\n" msgstr "" -#: src/chat/chat.c:692 -msgid "Undefined mandatory parameter: memberCallback\n" +#: src/ats/gnunet-service-ats_addresses.c:999 +#, c-format +msgid "Outbound quota configure for network `%s' is %llu\n" msgstr "" -#: src/chat/gnunet-chat.c:93 -msgid "Joined\n" +#: src/ats/gnunet-service-ats_addresses.c:1006 +#, c-format +msgid "" +"No outbound quota configured for network `%s', assigning default bandwidth " +"%llu\n" msgstr "" -#: src/chat/gnunet-chat.c:125 src/chat/gnunet-chat.c:133 -#: src/chat/gnunet-chat.c:213 src/chat/gnunet-chat.c:253 -#: src/chat/gnunet-chat.c:329 src/chat/gnunet-chat.c:371 -#: src/chat/gnunet-chat.c:400 src/chat/gnunet-chat.c:700 -msgid "anonymous" +#: src/ats/gnunet-service-ats_addresses.c:1033 +#, c-format +msgid "Inbound quota configured for network `%s' is %llu\n" msgstr "" -#: src/chat/gnunet-chat.c:144 -#, fuzzy, c-format -msgid "(%s) `%s' said: %s\n" -msgstr "`%s' %s schlug fehl: %s\n" - -#: src/chat/gnunet-chat.c:147 src/chat/gnunet-chat.c:150 -#, fuzzy, c-format -msgid "(%s) `%s' said to you: %s\n" -msgstr "`%s' %s schlug fehl: %s\n" - -#: src/chat/gnunet-chat.c:153 -#, fuzzy, c-format -msgid "(%s) `%s' said for sure: %s\n" -msgstr "`%s' fehlgeschlagen für Laufwerk %s: %u\n" - -#: src/chat/gnunet-chat.c:156 -#, fuzzy, c-format -msgid "(%s) `%s' said to you for sure: %s\n" -msgstr "`%s' schlug bei %s:%d mit dem Fehler %s fehl\n" - -#: src/chat/gnunet-chat.c:159 -#, fuzzy, c-format -msgid "(%s) `%s' was confirmed that you received: %s\n" -msgstr "`%s' schlug bei %s:%d mit dem Fehler %s fehl\n" - -#: src/chat/gnunet-chat.c:162 -#, fuzzy, c-format -msgid "(%s) `%s' was confirmed that you and only you received: %s\n" -msgstr "`%s' schlug bei %s:%d mit dem Fehler %s fehl\n" - -#: src/chat/gnunet-chat.c:165 -#, fuzzy, c-format -msgid "(%s) `%s' was confirmed that you received from him or her: %s\n" -msgstr "`%s' schlug bei %s:%d mit dem Fehler %s fehl\n" - -#: src/chat/gnunet-chat.c:170 -#, fuzzy, c-format -msgid "" -"(%s) `%s' was confirmed that you and only you received from him or her: %s\n" -msgstr "`%s' schlug bei %s:%d mit dem Fehler %s fehl\n" - -#: src/chat/gnunet-chat.c:173 -#, fuzzy, c-format -msgid "(%s) `%s' said off the record: %s\n" -msgstr "`%s' schlug bei %s:%d mit dem Fehler %s fehl\n" - -#: src/chat/gnunet-chat.c:176 +#: src/ats/gnunet-service-ats_addresses.c:1040 #, c-format -msgid "(%s) <%s> said using an unknown message type: %s\n" +msgid "" +"No outbound quota configure for network `%s', assigning default bandwidth " +"%llu\n" msgstr "" -#: src/chat/gnunet-chat.c:217 +#: src/ats-tool/gnunet-ats.c:141 #, c-format -msgid "'%s' acknowledged message #%d\n" +msgid "%u address resolutions had a timeout\n" msgstr "" -#: src/chat/gnunet-chat.c:260 +#: src/ats-tool/gnunet-ats.c:143 #, c-format -msgid "`%s' entered the room\n" +msgid "ATS returned results for %u addresses\n" msgstr "" -#: src/chat/gnunet-chat.c:260 -#, fuzzy, c-format -msgid "`%s' left the room\n" -msgstr "Fehler beim Binden an UDP Port %d.\n" - -#: src/chat/gnunet-chat.c:321 src/chat/gnunet-chat.c:363 -#, fuzzy -msgid "Could not change username\n" -msgstr "Namespace `%s' konnte nicht erstellt werden (existiert bereits?).\n" - -#: src/chat/gnunet-chat.c:334 src/chat/gnunet-chat.c:702 -#, fuzzy, c-format -msgid "Joining room `%s' as user `%s'...\n" -msgstr "Ungültige Antwort auf `%s' von Knoten `%s' empfangen.\n" - -#: src/chat/gnunet-chat.c:373 +#: src/ats-tool/gnunet-ats.c:199 #, fuzzy, c-format -msgid "Changed username to `%s'\n" -msgstr "Benutzer/Gruppe kann nicht zu `%s' gewechselt werden: %s\n" +msgid "" +"Peer `%s' plugin `%s', address `%s', `%s' bw out: %u Bytes/s, bw in %u Bytes/" +"s, %s\n" +msgstr "Knoten `%s' mit Vertrauen %8u und Adresse `%s'\n" -#: src/chat/gnunet-chat.c:388 +#: src/ats-tool/gnunet-ats.c:326 #, c-format -msgid "Users in room `%s': " +msgid "Quota for network `%11s' (in/out): %10s / %10s\n" msgstr "" -#: src/chat/gnunet-chat.c:434 -msgid "Syntax: /msg USERNAME MESSAGE" -msgstr "" +#: src/ats-tool/gnunet-ats.c:345 src/namestore/gnunet-namestore.c:610 +#: src/transport/gnunet-transport.c:813 +#, fuzzy, c-format +msgid "Service `%s' is not running\n" +msgstr "`%s' ist keine Datei.\n" -#: src/chat/gnunet-chat.c:443 -#, c-format -msgid "Unknown user `%s'. Make sure you specify its numeric suffix, if any.\n" -msgstr "" +#: src/ats-tool/gnunet-ats.c:355 src/transport/gnunet-transport.c:819 +#, fuzzy, c-format +msgid "Failed to parse peer identity `%s'\n" +msgstr "Fehler beim Lesen der Freunde-Liste von `%s'\n" -#: src/chat/gnunet-chat.c:460 +#: src/ats-tool/gnunet-ats.c:363 #, c-format -msgid "User `%s' is currently not in the room!\n" +msgid "Please select one operation : %s or %s or %s or %s or %s\n" msgstr "" -#: src/chat/gnunet-chat.c:513 +#: src/ats-tool/gnunet-ats.c:379 src/ats-tool/gnunet-ats.c:398 +#: src/ats-tool/gnunet-ats.c:415 src/ats-tool/gnunet-ats.c:440 #, fuzzy, c-format -msgid "Unknown command `%s'\n" -msgstr "Unbekannte Operation `%s'\n" - -#: src/chat/gnunet-chat.c:524 -msgid "" -"Use `/join #roomname' to join a chat room. Joining a room will cause you to " -"leave the current room" -msgstr "" +msgid "Cannot connect to ATS service, exiting...\n" +msgstr "`%s' Dienst konnte nicht initialisiert werden.\n" -#: src/chat/gnunet-chat.c:528 -msgid "" -"Use `/nick nickname' to change your nickname. This will cause you to leave " -"the current room and immediately rejoin it with the new name." -msgstr "" +#: src/ats-tool/gnunet-ats.c:388 src/ats-tool/gnunet-ats.c:405 +#, fuzzy, c-format +msgid "Cannot issue request to ATS service, exiting...\n" +msgstr "`%s' Dienst konnte nicht initialisiert werden.\n" -#: src/chat/gnunet-chat.c:532 -msgid "" -"Use `/msg nickname message' to send a private message to the specified user" +#: src/ats-tool/gnunet-ats.c:433 +msgid "Type required\n" msgstr "" -#: src/chat/gnunet-chat.c:535 -msgid "The `/notice' command is an alias for `/msg'" +#: src/ats-tool/gnunet-ats.c:490 +msgid "get list of active addresses currently used" msgstr "" -#: src/chat/gnunet-chat.c:537 -msgid "The `/query' command is an alias for `/msg'" +#: src/ats-tool/gnunet-ats.c:493 +msgid "get list of all active addresses" msgstr "" -#: src/chat/gnunet-chat.c:539 -msgid "Use `/sig message' to send a signed public message" -msgstr "" +#: src/ats-tool/gnunet-ats.c:496 +#, fuzzy +msgid "do not resolve IP addresses to hostnames" +msgstr "Fehler beim Lesen der Freunde-Liste von `%s'\n" -#: src/chat/gnunet-chat.c:542 -msgid "Use `/ack message' to require signed acknowledgment of the message" +#: src/ats-tool/gnunet-ats.c:499 +msgid "monitor mode" msgstr "" -#: src/chat/gnunet-chat.c:545 -msgid "Use `/anonymous message' to send a public anonymous message" -msgstr "" +#: src/ats-tool/gnunet-ats.c:502 +#, fuzzy +msgid "set preference for the given peer" +msgstr "Informationen über andere GNUnet Knoten ausgeben." -#: src/chat/gnunet-chat.c:547 -msgid "The `/anon' command is an alias for `/anonymous'" +#: src/ats-tool/gnunet-ats.c:505 +msgid "print all configured quotas" msgstr "" -#: src/chat/gnunet-chat.c:549 -msgid "Use `/quit' to terminate gnunet-chat" +#: src/ats-tool/gnunet-ats.c:508 +msgid "peer id" msgstr "" -#: src/chat/gnunet-chat.c:551 -msgid "The `/leave' command is an alias for `/quit'" +#: src/ats-tool/gnunet-ats.c:511 +msgid "preference type to set: latency | bandwidth" msgstr "" -#: src/chat/gnunet-chat.c:554 -msgid "Use `/names' to list all of the current members in the chat room" +#: src/ats-tool/gnunet-ats.c:514 +msgid "preference value" msgstr "" -#: src/chat/gnunet-chat.c:556 -msgid "Use `/help command' to get help for a specific command" +#: src/ats-tool/gnunet-ats.c:517 +msgid "verbose output (include ATS address properties)" msgstr "" -#: src/chat/gnunet-chat.c:672 +#: src/ats-tool/gnunet-ats.c:526 #, fuzzy -msgid "You must specify a nickname\n" -msgstr "Sie müssen einen Empfänger angeben!\n" +msgid "Print information about ATS state" +msgstr "Informationen über andere GNUnet Knoten ausgeben." -#: src/chat/gnunet-chat.c:688 +#: src/block/block.c:105 #, fuzzy, c-format -msgid "Failed to join room `%s'\n" -msgstr "Fehler beim Binden an UDP Port %d.\n" +msgid "Loading block plugin `%s'\n" +msgstr "Teste Transport(e) %s\n" -#: src/chat/gnunet-chat.c:727 -msgid "set the nickname to use (required)" -msgstr "" +#: src/consensus/gnunet-consensus.c:317 +#, fuzzy +msgid "number of peers in consensus" +msgstr "Anzahl an Durchläufen" -#: src/chat/gnunet-chat.c:730 -msgid "set the chat room to join" +#: src/consensus/gnunet-consensus.c:320 +msgid "how many peers receive one value?" msgstr "" -#: src/chat/gnunet-chat.c:742 -msgid "Join a chat on GNUnet." -msgstr "" +#: src/consensus/gnunet-consensus.c:323 +#, fuzzy +msgid "number of values" +msgstr "Anzahl an Durchläufen" -#: src/chat/gnunet-service-chat.c:267 +#: src/consensus/gnunet-consensus.c:326 #, fuzzy -msgid "Failed to queue a message notification\n" -msgstr "Fehler beim Speichern der Konfiguration!" +msgid "consensus timeout" +msgstr "# Sitzungsschlüssel akzeptiert" -#: src/chat/gnunet-service-chat.c:546 +#: src/consensus/gnunet-consensus-ibf.c:176 #, fuzzy -msgid "Failed to queue a join notification\n" -msgstr "Fehler beim Abfragen der Netzwerkverkehrsbedingungen von gnunetd.\n" +msgid "number of element in set A-B" +msgstr "Anzahl an Durchläufen" -#: src/chat/gnunet-service-chat.c:729 +#: src/consensus/gnunet-consensus-ibf.c:179 #, fuzzy -msgid "Failed to queue a confirmation receipt\n" -msgstr "Fehler beim Speichern der Konfiguration!" +msgid "number of element in set B-A" +msgstr "Anzahl an Durchläufen" + +#: src/consensus/gnunet-consensus-ibf.c:182 +msgid "number of common elements in A and B" +msgstr "" -#: src/chat/gnunet-service-chat.c:907 +#: src/consensus/gnunet-consensus-ibf.c:185 +msgid "hash num" +msgstr "" + +#: src/consensus/gnunet-consensus-ibf.c:188 +msgid "ibf size" +msgstr "" + +#: src/consensus/gnunet-consensus-start-peers.c:158 +msgid "start peers with the given template configuration" +msgstr "" + +#: src/consensus/gnunet-consensus-start-peers.c:161 #, fuzzy -msgid "Failed to queue a leave notification\n" -msgstr "Fehler beim Speichern der Konfiguration!" +msgid "number of peers to start" +msgstr "Anzahl an Durchläufen" -#: src/core/core_api.c:786 +#: src/core/core_api.c:755 msgid "Client was disconnected from core service, trying to reconnect.\n" msgstr "" -#: src/core/gnunet-core.c:54 src/peerinfo-tool/gnunet-peerinfo.c:286 +#: src/core/gnunet-core.c:86 src/peerinfo-tool/gnunet-peerinfo.c:214 #, fuzzy, c-format msgid "Peer `%s'\n" msgstr "Ich bin Peer `%s'.\n" -#: src/core/gnunet-core.c:72 src/peerinfo-tool/gnunet-peerinfo.c:817 +#: src/core/gnunet-core.c:119 src/core/gnunet-core.c:147 +#: src/transport/gnunet-transport.c:612 src/transport/gnunet-transport.c:636 +#, c-format +msgid "%24s: %-17s %4s (%u connections in total)\n" +msgstr "" + +#: src/core/gnunet-core.c:121 src/transport/gnunet-transport.c:614 +#, fuzzy +msgid "Connected to" +msgstr "`%s' hat sich mit `%s' verbunden.\n" + +#: src/core/gnunet-core.c:149 src/transport/gnunet-transport.c:638 +#, fuzzy +msgid "Disconnected from" +msgstr "`%s' hat sich mit `%s' verbunden.\n" + +#: src/core/gnunet-core.c:174 src/mesh/gnunet-mesh.c:176 +#: src/peerinfo-tool/gnunet-peerinfo.c:541 #, fuzzy, c-format msgid "Invalid command line argument `%s'\n" msgstr "Ungültige Kommandozeilen Parameter:\n" -#: src/core/gnunet-core.c:95 +#: src/core/gnunet-core.c:211 src/transport/gnunet-transport.c:1005 +#, fuzzy +msgid "provide information about all current connections (continuously)" +msgstr "Informationen über andere GNUnet Knoten ausgeben." + +#: src/core/gnunet-core.c:222 #, fuzzy msgid "Print information about connected peers." msgstr "Informationen über andere GNUnet Knoten ausgeben." -#: src/core/gnunet-service-core.c:97 +#: src/core/gnunet-service-core.c:109 +#, fuzzy, c-format +msgid "Failed to read hostkey: %s\n" +msgstr "Fehler beim Starten der Collection.\n" + +#: src/core/gnunet-service-core.c:123 #, c-format msgid "Core service of `%4s' ready.\n" msgstr "" +#: src/core/gnunet-service-core.c:149 +#, fuzzy +msgid "Core service is lacking HOSTKEY configuration setting. Exiting.\n" +msgstr "GNUnet Konfiguration" + +#: src/core/gnunet-service-core.c:163 +#: src/transport/gnunet-service-transport.c:737 +#, fuzzy +msgid "Transport service is unable to access hostkey. Exiting.\n" +msgstr "Auf die Namespace Informationen konnte nicht zugegriffen werden.\n" + #: src/core/gnunet-service-core_clients.c:370 #, fuzzy msgid "# send requests dropped (disconnected)" @@ -598,7 +506,7 @@ msgstr "# gap Anfragen verworfen: Kollision in RT" msgid "# messages discarded (session disconnected)" msgstr "# defragmentierter Nachrichten" -#: src/core/gnunet-service-core_clients.c:818 +#: src/core/gnunet-service-core_clients.c:518 #, fuzzy, c-format msgid "# bytes of messages of type %u received" msgstr "# Bytes Rauschen empfangen" @@ -644,7 +552,7 @@ msgid "# SET_KEY messages decrypted" msgstr "# defragmentierter Nachrichten" #: src/core/gnunet-service-core_kx.c:977 -#: src/transport/gnunet-service-transport_validation.c:810 +#: src/transport/gnunet-service-transport_validation.c:865 #, fuzzy msgid "# PING messages received" msgstr "# PING Nachrichten erstellt" @@ -672,7 +580,7 @@ msgid "# keepalive messages sent" msgstr "# Klartext PING Nachrichten gesendet" #: src/core/gnunet-service-core_kx.c:1236 -#: src/transport/gnunet-service-transport_validation.c:1031 +#: src/transport/gnunet-service-transport_validation.c:1161 #, fuzzy msgid "# PONG messages received" msgstr "# verschlüsselter PONG Nachrichten empfangen" @@ -692,58 +600,49 @@ msgstr "# Knotenankündigungen empfangen" msgid "# rekey operations confirmed via PONG" msgstr "# Knotenankündigungen empfangen" -#: src/core/gnunet-service-core_kx.c:1381 -#: src/core/gnunet-service-core_kx.c:1398 +#: src/core/gnunet-service-core_kx.c:1383 +#: src/core/gnunet-service-core_kx.c:1400 #, fuzzy msgid "# SET_KEY and PING messages created" msgstr "# PING Nachrichten erstellt" -#: src/core/gnunet-service-core_kx.c:1402 +#: src/core/gnunet-service-core_kx.c:1404 msgid "# REKEY operations performed" msgstr "" -#: src/core/gnunet-service-core_kx.c:1537 +#: src/core/gnunet-service-core_kx.c:1539 msgid "# failed to decrypt message (no session key)" msgstr "" -#: src/core/gnunet-service-core_kx.c:1577 -#: src/core/gnunet-service-core_kx.c:1602 +#: src/core/gnunet-service-core_kx.c:1579 +#: src/core/gnunet-service-core_kx.c:1604 #, fuzzy msgid "# bytes dropped (duplicates)" msgstr "# Bytes verworfen von UDP (outgoing)" -#: src/core/gnunet-service-core_kx.c:1589 +#: src/core/gnunet-service-core_kx.c:1591 #, fuzzy msgid "# bytes dropped (out of sequence)" msgstr "# Bytes verworfen von UDP (outgoing)" -#: src/core/gnunet-service-core_kx.c:1626 +#: src/core/gnunet-service-core_kx.c:1628 #, fuzzy, c-format -msgid "Message received far too old (%llu ms). Content ignored.\n" +msgid "Message received far too old (%s). Content ignored.\n" msgstr "Empfangene Client-Nachricht ist ungültig.\n" -#: src/core/gnunet-service-core_kx.c:1630 +#: src/core/gnunet-service-core_kx.c:1632 #, fuzzy msgid "# bytes dropped (ancient message)" msgstr "# Bytes verworfen von UDP (outgoing)" -#: src/core/gnunet-service-core_kx.c:1638 +#: src/core/gnunet-service-core_kx.c:1640 #, fuzzy msgid "# bytes of payload decrypted" msgstr "# Bytes entschlüsselt" -#: src/core/gnunet-service-core_kx.c:1700 -#, fuzzy -msgid "Core service is lacking HOSTKEY configuration setting. Exiting.\n" -msgstr "GNUnet Konfiguration" - -#: src/core/gnunet-service-core_kx.c:1708 -msgid "Core service could not access hostkey. Exiting.\n" -msgstr "" - -#: src/core/gnunet-service-core_kx.c:1718 src/hostlist/hostlist-server.c:551 -#: src/peerinfo-tool/gnunet-peerinfo.c:823 -#: src/transport/gnunet-service-transport.c:611 +#: src/core/gnunet-service-core_kx.c:1703 src/hostlist/hostlist-server.c:552 +#: src/peerinfo-tool/gnunet-peerinfo.c:547 +#: src/transport/gnunet-service-transport.c:644 #, fuzzy msgid "Could not access PEERINFO service. Exiting.\n" msgstr "Auf die Namespace Informationen konnte nicht zugegriffen werden.\n" @@ -762,23 +661,23 @@ msgstr "" msgid "# encrypted bytes given to transport" msgstr "" -#: src/core/gnunet-service-core_neighbours.c:418 +#: src/core/gnunet-service-core_neighbours.c:421 #, fuzzy, c-format msgid "Unsupported message of type %u (%u bytes) received from peer `%s'\n" msgstr "Ungültige Nachricht des Typs %u empfangen. Nachricht wird verworfen.\n" #: src/core/gnunet-service-core_sessions.c:206 #: src/core/gnunet-service-core_sessions.c:269 -#: src/dht/gnunet-service-dht_neighbours.c:625 -#: src/dht/gnunet-service-dht_neighbours.c:683 -#: src/fs/gnunet-service-fs_cp.c:615 src/fs/gnunet-service-fs_cp.c:1532 -#: src/topology/gnunet-daemon-topology.c:709 -#: src/topology/gnunet-daemon-topology.c:810 -#: src/transport/gnunet-service-transport_neighbours.c:874 -#: src/transport/gnunet-service-transport_neighbours.c:1080 -#: src/transport/gnunet-service-transport_neighbours.c:1089 -#: src/transport/gnunet-service-transport_neighbours.c:2568 -#: src/transport/gnunet-service-transport_neighbours.c:2814 +#: src/dht/gnunet-service-dht_neighbours.c:645 +#: src/dht/gnunet-service-dht_neighbours.c:703 +#: src/fs/gnunet-service-fs_cp.c:630 src/fs/gnunet-service-fs_cp.c:1544 +#: src/topology/gnunet-daemon-topology.c:704 +#: src/topology/gnunet-daemon-topology.c:805 +#: src/transport/gnunet-service-transport_neighbours.c:1052 +#: src/transport/gnunet-service-transport_neighbours.c:1276 +#: src/transport/gnunet-service-transport_neighbours.c:1285 +#: src/transport/gnunet-service-transport_neighbours.c:2826 +#: src/transport/gnunet-service-transport_neighbours.c:3089 #, fuzzy msgid "# peers connected" msgstr "# verbundener Knoten" @@ -802,40 +701,52 @@ msgstr "# verschlüsselter PING Nachrichten empfangen" msgid "# updates to my type map" msgstr "" -#: src/datacache/datacache.c:115 src/datacache/datacache.c:250 +#: src/datacache/datacache.c:115 src/datacache/datacache.c:266 #: src/datastore/gnunet-service-datastore.c:834 #, fuzzy msgid "# bytes stored" msgstr "# bytes in der Datenbank" -#: src/datacache/datacache.c:141 src/datacache/datacache.c:148 +#: src/datacache/datacache.c:117 src/datacache/datacache.c:268 +#, fuzzy +msgid "# items stored" +msgstr "# bytes in der Datenbank" + +#: src/datacache/datacache.c:143 src/datacache/datacache.c:150 #: src/datastore/gnunet-service-datastore.c:1483 #: src/datastore/gnunet-service-datastore.c:1494 #, fuzzy, c-format msgid "No `%s' specified for `%s' in configuration!\n" msgstr "In der Konfigurationsdatei wurden keine Anwendungen definiert!\n" -#: src/datacache/datacache.c:180 +#: src/datacache/datacache.c:184 #, c-format msgid "Loading `%s' datacache plugin\n" msgstr "" -#: src/datacache/datacache.c:188 +#: src/datacache/datacache.c:192 #, fuzzy, c-format msgid "Failed to load datacache plugin for `%s'\n" msgstr "Fehler beim Aktualisieren der Daten des Moduls `%s'\n" -#: src/datacache/datacache.c:276 +#: src/datacache/datacache.c:295 #, fuzzy msgid "# requests received" msgstr "# Client Trace-Anfragen empfangen" -#: src/datacache/datacache.c:284 +#: src/datacache/datacache.c:304 msgid "# requests filtered by bloom filter" msgstr "" -#: src/datacache/plugin_datacache_mysql.c:97 -#: src/datacache/plugin_datacache_mysql.c:104 +#: src/datacache/plugin_datacache_heap.c:406 +#, fuzzy +msgid "Heap datacache running\n" +msgstr "sqlite Datenspeicher" + +#: src/datacache/plugin_datacache_postgres.c:392 +msgid "Postgres datacache running\n" +msgstr "" + #: src/datacache/plugin_datacache_sqlite.c:69 #: src/datacache/plugin_datacache_sqlite.c:72 #: src/datastore/plugin_datastore_mysql.c:803 @@ -843,59 +754,52 @@ msgstr "" #: src/datastore/plugin_datastore_sqlite.c:57 src/mysql/mysql.c:41 #: src/mysql/mysql.c:48 src/mysql/mysql.c:522 src/mysql/mysql.c:531 #: src/mysql/mysql.c:591 src/mysql/mysql.c:607 -#: src/namestore/plugin_namestore_sqlite.c:51 src/util/crypto_ksk.c:49 -#: src/util/crypto_rsa.c:67 src/include/gnunet_common.h:525 -#: src/include/gnunet_common.h:532 +#: src/namestore/plugin_namestore_postgres.c:52 +#: src/namestore/plugin_namestore_sqlite.c:51 src/util/crypto_ecc.c:46 +#: src/util/crypto_ksk.c:49 src/util/crypto_rsa.c:59 +#: src/include/gnunet_common.h:607 src/include/gnunet_common.h:614 #, c-format msgid "`%s' failed at %s:%d with error: %s\n" msgstr "`%s' schlug bei %s:%d mit dem Fehler %s fehl\n" -#: src/datacache/plugin_datacache_mysql.c:450 -msgid "MySQL datacache running\n" -msgstr "" - -#: src/datacache/plugin_datacache_postgres.c:367 -msgid "Postgres datacache running\n" -msgstr "" - -#: src/datacache/plugin_datacache_sqlite.c:410 +#: src/datacache/plugin_datacache_sqlite.c:450 msgid "Sqlite datacache running\n" msgstr "" -#: src/datacache/plugin_datacache_sqlite.c:443 -#: src/datastore/plugin_datastore_sqlite.c:408 -#: src/namestore/plugin_namestore_sqlite.c:370 +#: src/datacache/plugin_datacache_sqlite.c:484 +#: src/datastore/plugin_datastore_sqlite.c:401 +#: src/namestore/plugin_namestore_sqlite.c:362 msgid "Tried to close sqlite without finalizing all prepared statements.\n" msgstr "" -#: src/datacache/plugin_datacache_sqlite.c:450 +#: src/datacache/plugin_datacache_sqlite.c:491 #, fuzzy, c-format msgid "Failed to close statement %p: %d\n" msgstr "Fehler beim Lesen der Freunde-Liste von `%s'\n" -#: src/datacache/plugin_datacache_template.c:121 +#: src/datacache/plugin_datacache_template.c:125 msgid "Template datacache running\n" msgstr "" -#: src/datastore/datastore_api.c:305 +#: src/datastore/datastore_api.c:310 #, fuzzy msgid "Failed to transmit request to drop database.\n" msgstr "Fehler beim Senden einer `%s' Anfrage an den SMTP Server.\n" -#: src/datastore/datastore_api.c:388 +#: src/datastore/datastore_api.c:393 msgid "# queue entry timeouts" msgstr "" -#: src/datastore/datastore_api.c:432 +#: src/datastore/datastore_api.c:437 msgid "# queue overflows" msgstr "" -#: src/datastore/datastore_api.c:459 +#: src/datastore/datastore_api.c:465 #, fuzzy msgid "# queue entries created" msgstr "# dht Anfragen weitergeleitet" -#: src/datastore/datastore_api.c:477 +#: src/datastore/datastore_api.c:483 #, fuzzy msgid "# Requests dropped from datastore queue" msgstr "# gap Anfragen verworfen: Kollision in RT" @@ -904,73 +808,69 @@ msgstr "# gap Anfragen verworfen: Kollision in RT" msgid "# datastore connections (re)created" msgstr "" -#: src/datastore/datastore_api.c:548 -msgid "# reconnected to DATASTORE" -msgstr "" - -#: src/datastore/datastore_api.c:612 +#: src/datastore/datastore_api.c:608 #, fuzzy msgid "# transmission request failures" msgstr "# Klartext PONG Nachrichten empfangen" -#: src/datastore/datastore_api.c:633 +#: src/datastore/datastore_api.c:630 #, fuzzy msgid "# bytes sent to datastore" msgstr "# bytes in der Datenbank" -#: src/datastore/datastore_api.c:764 +#: src/datastore/datastore_api.c:762 #, fuzzy msgid "Failed to receive status response from database." msgstr "" "\n" "Fehler beim Empfangen der Antwort von gnunetd.\n" -#: src/datastore/datastore_api.c:778 +#: src/datastore/datastore_api.c:776 msgid "Error reading response from datastore service" msgstr "" -#: src/datastore/datastore_api.c:790 src/datastore/datastore_api.c:796 +#: src/datastore/datastore_api.c:788 src/datastore/datastore_api.c:794 #, fuzzy msgid "Invalid error message received from datastore service" msgstr "Ungültige `%s' Nachricht von Knoten `%s' empfangen.\n" -#: src/datastore/datastore_api.c:800 +#: src/datastore/datastore_api.c:798 #, fuzzy msgid "# status messages received" msgstr "# verschlüsselter PING Nachrichten empfangen" -#: src/datastore/datastore_api.c:869 +#: src/datastore/datastore_api.c:867 #, fuzzy msgid "# PUT requests executed" msgstr "# dht Anfragen weitergeleitet" -#: src/datastore/datastore_api.c:936 +#: src/datastore/datastore_api.c:934 #, fuzzy msgid "# RESERVE requests executed" msgstr "# dht Anfragen weitergeleitet" -#: src/datastore/datastore_api.c:997 +#: src/datastore/datastore_api.c:995 msgid "# RELEASE RESERVE requests executed" msgstr "" -#: src/datastore/datastore_api.c:1054 +#: src/datastore/datastore_api.c:1052 #, fuzzy msgid "# UPDATE requests executed" msgstr "# dht Anfragen weitergeleitet" -#: src/datastore/datastore_api.c:1118 +#: src/datastore/datastore_api.c:1116 #, fuzzy msgid "# REMOVE requests executed" msgstr "# dht Anfragen weitergeleitet" -#: src/datastore/datastore_api.c:1163 +#: src/datastore/datastore_api.c:1161 #, fuzzy msgid "Failed to receive response from database.\n" msgstr "" "\n" "Fehler beim Empfangen der Antwort von gnunetd.\n" -#: src/datastore/datastore_api.c:1221 +#: src/datastore/datastore_api.c:1220 #, fuzzy msgid "# Results received" msgstr "# Bytes empfangen über TCP" @@ -983,7 +883,7 @@ msgstr "" msgid "# GET ZERO ANONYMITY requests executed" msgstr "" -#: src/datastore/datastore_api.c:1409 +#: src/datastore/datastore_api.c:1410 #, fuzzy msgid "# GET requests executed" msgstr "# dht Anfragen weitergeleitet" @@ -998,10 +898,12 @@ msgid "# bytes purged (low-priority)" msgstr "" #: src/datastore/gnunet-service-datastore.c:480 +#: src/gns/gnunet-gns-helper-service-w32.c:159 msgid "Transmission to client failed!\n" msgstr "" #: src/datastore/gnunet-service-datastore.c:511 +#: src/gns/gnunet-gns-helper-service-w32.c:189 msgid "Shutdown in progress, aborting transmission.\n" msgstr "" @@ -1143,6 +1045,11 @@ msgstr "" msgid "Bloomfilter construction complete.\n" msgstr "" +#: src/datastore/plugin_datastore_heap.c:820 +#, fuzzy +msgid "Heap database running\n" +msgstr "sqlite Datenspeicher" + #: src/datastore/plugin_datastore_mysql.c:780 #, fuzzy, c-format msgid "Failed to prepare statement `%s'\n" @@ -1165,6 +1072,7 @@ msgstr "" "Fehler beim Empfangen der Antwort von gnunetd.\n" #: src/datastore/plugin_datastore_postgres.c:860 +#: src/namestore/plugin_namestore_postgres.c:652 msgid "Postgres database running\n" msgstr "" @@ -1173,223 +1081,240 @@ msgstr "" msgid "`%s' failed at %s:%u with error: %s" msgstr "`%s' schlug bei %s:%d mit dem Fehler %s fehl\n" -#: src/datastore/plugin_datastore_sqlite.c:233 -#: src/namestore/plugin_namestore_sqlite.c:204 -#, fuzzy, c-format -msgid "Option `%s' in section `%s' missing in configuration!\n" -msgstr "In der Konfigurationsdatei wurden keine Anwendungen definiert!\n" - -#: src/datastore/plugin_datastore_sqlite.c:260 -#: src/namestore/plugin_namestore_sqlite.c:229 +#: src/datastore/plugin_datastore_sqlite.c:253 +#: src/namestore/plugin_namestore_sqlite.c:223 #, c-format msgid "Unable to initialize SQLite: %s.\n" msgstr "SQLite Datenbank konnte nicht initialisiert werden: %s.\n" -#: src/datastore/plugin_datastore_sqlite.c:655 +#: src/datastore/plugin_datastore_sqlite.c:648 #, fuzzy msgid "Invalid data in database. Trying to fix (by deletion).\n" msgstr "Ungültige Daten in %s. Korrektur wird versucht (durch Löschung).\n" -#: src/datastore/plugin_datastore_sqlite.c:1139 +#: src/datastore/plugin_datastore_sqlite.c:1134 msgid "sqlite version to old to determine size, assuming zero\n" msgstr "" -#: src/datastore/plugin_datastore_sqlite.c:1158 +#: src/datastore/plugin_datastore_sqlite.c:1153 #, c-format msgid "" "Using sqlite page utilization to estimate payload (%llu pages of size %llu " "bytes)\n" msgstr "" -#: src/datastore/plugin_datastore_sqlite.c:1198 -#: src/namestore/plugin_namestore_sqlite.c:829 +#: src/datastore/plugin_datastore_sqlite.c:1193 +#: src/namestore/plugin_namestore_sqlite.c:827 #, fuzzy msgid "Sqlite database running\n" msgstr "sqlite Datenspeicher" -#: src/datastore/plugin_datastore_template.c:241 +#: src/datastore/plugin_datastore_template.c:257 msgid "Template database running\n" msgstr "" -#: src/dht/dht_api.c:348 +#: src/dht/dht_api.c:375 #, fuzzy msgid "Failed to connect to the DHT service!\n" msgstr "Es konnte keine Verbindung mit gnunetd hergestellt werden.\n" -#: src/dht/gnunet-dht-get.c:201 src/dht/gnunet-dht-monitor.c:293 -#: src/dht/gnunet-dht-put.c:192 +#: src/dht/gnunet-dht-get.c:132 +#, c-format +msgid "" +"Result %d, type %d:\n" +"%.*s\n" +msgstr "" + +#: src/dht/gnunet-dht-get.c:156 +msgid "Must provide key for DHT GET!\n" +msgstr "" + +#: src/dht/gnunet-dht-get.c:162 src/dht/gnunet-dht-monitor.c:225 +#, fuzzy +msgid "Failed to connect to DHT service!\n" +msgstr "Es konnte keine Verbindung mit gnunetd hergestellt werden.\n" + +#: src/dht/gnunet-dht-get.c:170 +msgid "Issueing DHT GET with key" +msgstr "" + +#: src/dht/gnunet-dht-get.c:186 src/dht/gnunet-dht-monitor.c:262 +#: src/dht/gnunet-dht-put.c:198 msgid "the query key" msgstr "" -#: src/dht/gnunet-dht-get.c:204 +#: src/dht/gnunet-dht-get.c:189 msgid "how many parallel requests (replicas) to create" msgstr "" -#: src/dht/gnunet-dht-get.c:207 src/dht/gnunet-dht-monitor.c:296 +#: src/dht/gnunet-dht-get.c:192 src/dht/gnunet-dht-monitor.c:265 msgid "the type of data to look for" msgstr "" -#: src/dht/gnunet-dht-get.c:210 src/dht/gnunet-dht-put.c:201 +#: src/dht/gnunet-dht-get.c:195 src/dht/gnunet-dht-put.c:210 msgid "how long to execute this query before giving up?" msgstr "" -#: src/dht/gnunet-dht-get.c:213 src/dht/gnunet-dht-monitor.c:302 -#: src/dht/gnunet-dht-put.c:204 src/fs/gnunet-download.c:271 -#: src/fs/gnunet-publish.c:731 src/fs/gnunet-search.c:297 -#: src/fs/gnunet-unindex.c:169 src/nse/gnunet-nse-profiler.c:910 +#: src/dht/gnunet-dht-get.c:198 src/dht/gnunet-dht-put.c:201 +msgid "use DHT's demultiplex everywhere option" +msgstr "" + +#: src/dht/gnunet-dht-get.c:201 src/dht/gnunet-dht-monitor.c:271 +#: src/dht/gnunet-dht-put.c:213 src/fs/gnunet-auto-share.c:753 +#: src/fs/gnunet-download.c:328 src/fs/gnunet-publish.c:736 +#: src/fs/gnunet-search.c:294 src/fs/gnunet-unindex.c:168 +#: src/nse/gnunet-nse-profiler.c:1033 msgid "be verbose (print progress information)" msgstr "" -#: src/dht/gnunet-dht-get.c:232 +#: src/dht/gnunet-dht-get.c:222 msgid "Issue a GET request to the GNUnet DHT, prints results." msgstr "" -#: src/dht/gnunet-dht-monitor.c:299 -msgid "how long to execute? 0 = forever" +#: src/dht/gnunet-dht-monitor.c:268 +msgid "how long should the monitor command run" msgstr "" -#: src/dht/gnunet-dht-monitor.c:321 +#: src/dht/gnunet-dht-monitor.c:293 msgid "Prints all packets that go through the DHT." msgstr "" -#: src/dht/gnunet-dht-put.c:108 +#: src/dht/gnunet-dht-put.c:118 #, fuzzy -msgid "PUT request sent!\n" +msgid "PUT request sent with key" msgstr "# gap Anfragen insgesamt empfangen" -#: src/dht/gnunet-dht-put.c:111 +#: src/dht/gnunet-dht-put.c:121 msgid "Timeout sending PUT request!\n" msgstr "" -#: src/dht/gnunet-dht-put.c:114 +#: src/dht/gnunet-dht-put.c:124 #, fuzzy msgid "PUT request not confirmed!\n" msgstr "# gap Anfragen insgesamt empfangen" -#: src/dht/gnunet-dht-put.c:144 +#: src/dht/gnunet-dht-put.c:153 msgid "Must provide KEY and DATA for DHT put!\n" msgstr "" -#: src/dht/gnunet-dht-put.c:152 +#: src/dht/gnunet-dht-put.c:160 #, fuzzy, c-format msgid "Could not connect to %s service!\n" msgstr "Verbindung zu gnunetd konnte nicht hergestellt werden.\n" -#: src/dht/gnunet-dht-put.c:157 -#, fuzzy, c-format -msgid "Connected to %s service!\n" -msgstr "`%s' hat sich mit `%s' verbunden.\n" - -#: src/dht/gnunet-dht-put.c:172 +#: src/dht/gnunet-dht-put.c:176 #, c-format msgid "Issuing put request for `%s' with data `%s'!\n" msgstr "" -#: src/dht/gnunet-dht-put.c:186 +#: src/dht/gnunet-dht-put.c:192 msgid "the data to insert under the key" msgstr "" -#: src/dht/gnunet-dht-put.c:189 +#: src/dht/gnunet-dht-put.c:195 msgid "how long to store this entry in the dht (in seconds)" msgstr "" -#: src/dht/gnunet-dht-put.c:195 +#: src/dht/gnunet-dht-put.c:204 msgid "how many replicas to create" msgstr "" -#: src/dht/gnunet-dht-put.c:198 +#: src/dht/gnunet-dht-put.c:207 msgid "the type to insert data as" msgstr "" -#: src/dht/gnunet-dht-put.c:223 +#: src/dht/gnunet-dht-put.c:235 msgid "Issue a PUT request to the GNUnet DHT insert DATA under KEY." msgstr "" -#: src/dht/gnunet-service-dht.c:163 src/testing/testing.c:544 -#: src/testing/testing.c:1968 src/testing/testing.c:1998 +#: src/dht/gnunet-service-dht.c:172 #, fuzzy msgid "Failed to connect to transport service!\n" msgstr "Der Transportdienst auf Port %d konnte nicht gestartet werden.\n" -#: src/dht/gnunet-service-dht_clients.c:407 +#: src/dht/gnunet-service-dht_clients.c:413 #, fuzzy msgid "# GET requests from clients injected" msgstr "# Client Trace-Anfragen empfangen" -#: src/dht/gnunet-service-dht_clients.c:500 +#: src/dht/gnunet-service-dht_clients.c:503 #, fuzzy msgid "# PUT requests received from clients" msgstr "Empfangene Client-Nachricht ist ungültig.\n" -#: src/dht/gnunet-service-dht_clients.c:584 +#: src/dht/gnunet-service-dht_clients.c:585 #, fuzzy msgid "# GET requests received from clients" msgstr "Empfangene Client-Nachricht ist ungültig.\n" -#: src/dht/gnunet-service-dht_clients.c:682 +#: src/dht/gnunet-service-dht_clients.c:791 #, fuzzy msgid "# GET STOP requests received from clients" msgstr "Empfangene Client-Nachricht ist ungültig.\n" -#: src/dht/gnunet-service-dht_clients.c:919 +#: src/dht/gnunet-service-dht_clients.c:1035 msgid "# Key match, type mismatches in REPLY to CLIENT" msgstr "" -#: src/dht/gnunet-service-dht_clients.c:932 +#: src/dht/gnunet-service-dht_clients.c:1048 msgid "# Duplicate REPLIES to CLIENT request dropped" msgstr "" -#: src/dht/gnunet-service-dht_clients.c:967 +#: src/dht/gnunet-service-dht_clients.c:1085 #, fuzzy, c-format msgid "Unsupported block type (%u) in request!\n" msgstr "Ungültige Nachricht des Typs %u empfangen. Nachricht wird verworfen.\n" -#: src/dht/gnunet-service-dht_clients.c:989 +#: src/dht/gnunet-service-dht_clients.c:1108 #, fuzzy msgid "# RESULTS queued for clients" msgstr "Empfangene Client-Nachricht ist ungültig.\n" -#: src/dht/gnunet-service-dht_clients.c:1038 -#: src/dht/gnunet-service-dht_clients.c:1081 +#: src/dht/gnunet-service-dht_clients.c:1157 +#: src/dht/gnunet-service-dht_clients.c:1199 msgid "# REPLIES ignored for CLIENTS (no match)" msgstr "" -#: src/dht/gnunet-service-dht_clients.c:1048 +#: src/dht/gnunet-service-dht_clients.c:1167 #, fuzzy msgid "Could not pass reply to client, message too big!\n" msgstr "'join' Nachricht konnte nicht an gnunetd gesendet werden.\n" -#: src/dht/gnunet-service-dht_datacache.c:93 +#: src/dht/gnunet-service-dht_datacache.c:64 #, fuzzy, c-format msgid "%s request received, but have no datacache!\n" msgstr "# Bytes empfangen über TCP" -#: src/dht/gnunet-service-dht_datacache.c:103 +#: src/dht/gnunet-service-dht_datacache.c:74 msgid "# ITEMS stored in datacache" msgstr "" -#: src/dht/gnunet-service-dht_datacache.c:207 +#: src/dht/gnunet-service-dht_datacache.c:159 msgid "# Good RESULTS found in datacache" msgstr "" -#: src/dht/gnunet-service-dht_datacache.c:218 +#: src/dht/gnunet-service-dht_datacache.c:170 msgid "# Duplicate RESULTS found in datacache" msgstr "" -#: src/dht/gnunet-service-dht_datacache.c:224 +#: src/dht/gnunet-service-dht_datacache.c:176 msgid "# Invalid RESULTS found in datacache" msgstr "" -#: src/dht/gnunet-service-dht_datacache.c:236 +#: src/dht/gnunet-service-dht_datacache.c:182 +msgid "# Irrelevant RESULTS found in datacache" +msgstr "" + +#: src/dht/gnunet-service-dht_datacache.c:194 msgid "# Unsupported RESULTS found in datacache" msgstr "" -#: src/dht/gnunet-service-dht_datacache.c:239 +#: src/dht/gnunet-service-dht_datacache.c:197 #, c-format msgid "Unsupported block type (%u) in local response!\n" msgstr "" -#: src/dht/gnunet-service-dht_datacache.c:269 +#: src/dht/gnunet-service-dht_datacache.c:227 #, fuzzy msgid "# GET requests given to datacache" msgstr "# Client Trace-Anfragen empfangen" @@ -1399,95 +1324,102 @@ msgstr "# Client Trace-Anfragen empfangen" msgid "# HELLOs obtained from peerinfo" msgstr "Empfangene Client-Nachricht ist ungültig.\n" -#: src/dht/gnunet-service-dht_neighbours.c:481 +#: src/dht/gnunet-service-dht_neighbours.c:501 msgid "# Preference updates given to core" msgstr "" -#: src/dht/gnunet-service-dht_neighbours.c:571 +#: src/dht/gnunet-service-dht_neighbours.c:591 #, fuzzy msgid "# FIND PEER messages initiated" msgstr "# PING Nachrichten erstellt" -#: src/dht/gnunet-service-dht_neighbours.c:717 +#: src/dht/gnunet-service-dht_neighbours.c:737 #, fuzzy msgid "# Queued messages discarded (peer disconnected)" msgstr "# defragmentierter Nachrichten" -#: src/dht/gnunet-service-dht_neighbours.c:772 +#: src/dht/gnunet-service-dht_neighbours.c:792 #, fuzzy msgid "# Bytes transmitted to other peers" msgstr "# Bytes des Typs %d übertragen" -#: src/dht/gnunet-service-dht_neighbours.c:810 +#: src/dht/gnunet-service-dht_neighbours.c:830 #, fuzzy -msgid "# Bytes of bandwdith requested from core" +msgid "# Bytes of bandwidth requested from core" msgstr "# Client Trace-Anfragen empfangen" -#: src/dht/gnunet-service-dht_neighbours.c:1032 -#: src/dht/gnunet-service-dht_neighbours.c:1060 +#: src/dht/gnunet-service-dht_neighbours.c:1052 +#: src/dht/gnunet-service-dht_neighbours.c:1080 msgid "# Peers excluded from routing due to Bloomfilter" msgstr "" -#: src/dht/gnunet-service-dht_neighbours.c:1041 -#: src/dht/gnunet-service-dht_neighbours.c:1075 +#: src/dht/gnunet-service-dht_neighbours.c:1061 +#: src/dht/gnunet-service-dht_neighbours.c:1095 #, fuzzy msgid "# Peer selection failed" msgstr " Verbindung fehlgeschlagen\n" -#: src/dht/gnunet-service-dht_neighbours.c:1207 +#: src/dht/gnunet-service-dht_neighbours.c:1229 #, fuzzy msgid "# PUT requests routed" msgstr "# dht Anfragen weitergeleitet" -#: src/dht/gnunet-service-dht_neighbours.c:1236 +#: src/dht/gnunet-service-dht_neighbours.c:1258 #, fuzzy msgid "# PUT messages queued for transmission" msgstr "# PING Nachrichten erstellt" -#: src/dht/gnunet-service-dht_neighbours.c:1315 +#: src/dht/gnunet-service-dht_neighbours.c:1265 +#: src/dht/gnunet-service-dht_neighbours.c:1378 +#: src/dht/gnunet-service-dht_neighbours.c:1478 +#, fuzzy +msgid "# P2P messages dropped due to full queue" +msgstr "# gap Anfragen verworfen: Kollision in RT" + +#: src/dht/gnunet-service-dht_neighbours.c:1343 #, fuzzy msgid "# GET requests routed" msgstr "# dht Anfragen weitergeleitet" -#: src/dht/gnunet-service-dht_neighbours.c:1342 +#: src/dht/gnunet-service-dht_neighbours.c:1370 #, fuzzy msgid "# GET messages queued for transmission" msgstr "# PING Nachrichten erstellt" -#: src/dht/gnunet-service-dht_neighbours.c:1443 +#: src/dht/gnunet-service-dht_neighbours.c:1485 #, fuzzy msgid "# RESULT messages queued for transmission" msgstr "# PING Nachrichten erstellt" -#: src/dht/gnunet-service-dht_neighbours.c:1531 +#: src/dht/gnunet-service-dht_neighbours.c:1573 #, fuzzy msgid "# P2P PUT requests received" msgstr "# Client Trace-Anfragen empfangen" -#: src/dht/gnunet-service-dht_neighbours.c:1647 +#: src/dht/gnunet-service-dht_neighbours.c:1702 msgid "# FIND PEER requests ignored due to Bloomfilter" msgstr "" -#: src/dht/gnunet-service-dht_neighbours.c:1655 +#: src/dht/gnunet-service-dht_neighbours.c:1710 msgid "# FIND PEER requests ignored due to lack of HELLO" msgstr "" -#: src/dht/gnunet-service-dht_neighbours.c:1746 +#: src/dht/gnunet-service-dht_neighbours.c:1801 #, fuzzy msgid "# P2P GET requests received" msgstr "# Client Trace-Anfragen empfangen" -#: src/dht/gnunet-service-dht_neighbours.c:1788 +#: src/dht/gnunet-service-dht_neighbours.c:1843 #, fuzzy msgid "# P2P FIND PEER requests processed" msgstr "# Client Trace-Anfragen empfangen" -#: src/dht/gnunet-service-dht_neighbours.c:1802 +#: src/dht/gnunet-service-dht_neighbours.c:1857 #, fuzzy msgid "# P2P GET requests ONLY routed" msgstr "# dht Anfragen weitergeleitet" -#: src/dht/gnunet-service-dht_neighbours.c:1876 +#: src/dht/gnunet-service-dht_neighbours.c:1944 #, fuzzy msgid "# P2P RESULTS received" msgstr "# Bytes empfangen über TCP" @@ -1509,18 +1441,27 @@ msgstr "" msgid "# Invalid REPLIES matched against routing table" msgstr "" -#: src/dht/gnunet-service-dht_routing.c:238 +#: src/dht/gnunet-service-dht_routing.c:232 +msgid "# Irrelevant REPLIES matched against routing table" +msgstr "" + +#: src/dht/gnunet-service-dht_routing.c:244 msgid "# Unsupported REPLIES matched against routing table" msgstr "" -#: src/dht/gnunet-service-dht_routing.c:311 +#: src/dht/gnunet-service-dht_routing.c:317 msgid "# Entries removed from routing table" msgstr "" -#: src/dht/gnunet-service-dht_routing.c:352 +#: src/dht/gnunet-service-dht_routing.c:400 msgid "# Entries added to routing table" msgstr "" +#: src/dht/gnunet-service-dht_routing.c:418 +#, fuzzy +msgid "# DHT requests combined" +msgstr "# Client Trace-Anfragen empfangen" + #: src/dht/plugin_block_dht.c:136 #, fuzzy, c-format msgid "Block not of type %u\n" @@ -1535,15 +1476,51 @@ msgstr "" msgid "Block of type %u is malformed\n" msgstr "" -#: src/dns/gnunet-dns-monitor.c:337 -msgid "only monitor DNS queries" +#: src/dns/dnsparser.c:152 +#, fuzzy, c-format +msgid "Failed to convert DNS IDNA name `%s' to UTF-8: %s\n" +msgstr "Datei wurde als `%s' gespeichert.\n" + +#: src/dns/dnsparser.c:626 +#, fuzzy, c-format +msgid "Failed to convert UTF-8 name `%s' to DNS IDNA format: %s\n" +msgstr "Datei wurde als `%s' gespeichert.\n" + +#: src/dns/dnsstub.c:175 +#, fuzzy, c-format +msgid "Could not bind to any port: %s\n" +msgstr "IP des Hosts `%s' konnte nicht ermittelt werden: %s\n" + +#: src/dns/dnsstub.c:295 src/dns/dnsstub.c:383 +#: src/gns/gnunet-service-gns_resolver.c:1621 +#, fuzzy, c-format +msgid "Failed to send DNS request to %s\n" +msgstr "HTTP Anfrage konnte nicht an Host `%s' gesendet werden: %s\n" + +#: src/dns/dnsstub.c:299 +#, fuzzy, c-format +msgid "Sent DNS request to %s\n" +msgstr "# Client Trace-Anfragen empfangen" + +#: src/dns/dnsstub.c:368 +#, c-format +msgid "Configured DNS exit `%s' is not working / valid.\n" +msgstr "" + +#: src/dns/dnsstub.c:440 +#, c-format +msgid "Received DNS response that is too small (%u bytes)" +msgstr "" + +#: src/dns/gnunet-dns-monitor.c:355 +msgid "only monitor DNS queries" msgstr "" -#: src/dns/gnunet-dns-monitor.c:340 +#: src/dns/gnunet-dns-monitor.c:358 msgid "only monitor DNS replies" msgstr "" -#: src/dns/gnunet-dns-monitor.c:348 +#: src/dns/gnunet-dns-monitor.c:369 msgid "Monitor DNS queries." msgstr "" @@ -1555,77 +1532,59 @@ msgstr "" msgid "set AAAA records" msgstr "" -#: src/dns/gnunet-dns-redirector.c:247 +#: src/dns/gnunet-dns-redirector.c:251 msgid "Change DNS replies to point elsewhere." msgstr "" -#: src/dns/gnunet-service-dns.c:485 -#, fuzzy, c-format -msgid "Could not bind to any port: %s\n" -msgstr "IP des Hosts `%s' konnte nicht ermittelt werden: %s\n" - -#: src/dns/gnunet-service-dns.c:639 +#: src/dns/gnunet-service-dns.c:456 msgid "# DNS requests answered via TUN interface" msgstr "" -#: src/dns/gnunet-service-dns.c:822 +#: src/dns/gnunet-service-dns.c:603 msgid "# DNS exit failed (failed to open socket)" msgstr "" -#: src/dns/gnunet-service-dns.c:1005 -#, c-format -msgid "Received DNS response that is too small (%u bytes)" -msgstr "" - -#: src/dns/gnunet-service-dns.c:1050 +#: src/dns/gnunet-service-dns.c:714 msgid "# External DNS response discarded (no matching request)" msgstr "" -#: src/dns/gnunet-service-dns.c:1168 +#: src/dns/gnunet-service-dns.c:792 msgid "# Client response discarded (no matching request)" msgstr "" -#: src/dns/gnunet-service-dns.c:1281 +#: src/dns/gnunet-service-dns.c:907 msgid "Received malformed IPv4-UDP packet on TUN interface.\n" msgstr "" -#: src/dns/gnunet-service-dns.c:1297 +#: src/dns/gnunet-service-dns.c:923 msgid "Received malformed IPv6-UDP packet on TUN interface.\n" msgstr "" -#: src/dns/gnunet-service-dns.c:1306 +#: src/dns/gnunet-service-dns.c:932 #, c-format msgid "Got non-IP packet with %u bytes and protocol %u from TUN\n" msgstr "" -#: src/dns/gnunet-service-dns.c:1315 +#: src/dns/gnunet-service-dns.c:942 msgid "# Non-DNS UDP packet received via TUN interface" msgstr "" -#: src/dns/gnunet-service-dns.c:1380 +#: src/dns/gnunet-service-dns.c:1009 #, fuzzy msgid "# DNS requests received via TUN interface" msgstr "Empfangene Client-Nachricht ist ungültig.\n" -#: src/dns/gnunet-service-dns.c:1465 -#, c-format -msgid "Configured DNS exit `%s' is not working / valid.\n" -msgstr "" - -#: src/dns/gnunet-service-dns.c:1497 src/exit/gnunet-daemon-exit.c:2674 -msgid "# Inbound MESH tunnels created" -msgstr "" - -#: src/dns/gnunet-service-dns.c:1561 src/exit/gnunet-daemon-exit.c:3032 +#: src/dns/gnunet-service-dns.c:1049 src/exit/gnunet-daemon-exit.c:3351 #, c-format msgid "`%s' must be installed SUID, refusing to run\n" msgstr "" -#: src/dns/gnunet-service-dns.c:1581 -msgid "Configured to provide DNS exit, but no valid DNS server configured!\n" -msgstr "" +#: src/dns/gnunet-service-dns.c:1069 src/exit/gnunet-daemon-exit.c:3407 +#, fuzzy +msgid "need a valid IPv4 or IPv6 address\n" +msgstr "Ungültiger Parameter: `%s'\n" -#: src/dv/dv_api.c:179 +#: src/dv/dv_api.c:189 #, fuzzy msgid "Failed to connect to the dv service!\n" msgstr "Es konnte keine Verbindung mit gnunetd hergestellt werden.\n" @@ -1635,205 +1594,209 @@ msgstr "Es konnte keine Verbindung mit gnunetd hergestellt werden.\n" msgid "%s Received message from %s of type %d, distance %u!\n" msgstr "Beschädigte Nachricht von Knoten `%s' in %s:%d empfangen.\n" -#: src/exit/gnunet-daemon-exit.c:508 +#: src/exit/gnunet-daemon-exit.c:741 #, c-format msgid "Got duplicate service records for `%s:%u'\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:563 +#: src/exit/gnunet-daemon-exit.c:794 #, fuzzy msgid "# Bytes transmitted via mesh tunnels" msgstr "# Bytes des Typs %d übertragen" -#: src/exit/gnunet-daemon-exit.c:679 src/exit/gnunet-daemon-exit.c:2069 -#: src/exit/gnunet-daemon-exit.c:2319 src/vpn/gnunet-service-vpn.c:1394 -#: src/vpn/gnunet-service-vpn.c:1795 src/vpn/gnunet-service-vpn.c:1958 +#: src/exit/gnunet-daemon-exit.c:911 src/exit/gnunet-daemon-exit.c:2343 +#: src/exit/gnunet-daemon-exit.c:2603 src/vpn/gnunet-service-vpn.c:1411 +#: src/vpn/gnunet-service-vpn.c:1812 src/vpn/gnunet-service-vpn.c:1975 msgid "# ICMPv4 packets dropped (type not allowed)" msgstr "" -#: src/exit/gnunet-daemon-exit.c:716 src/exit/gnunet-daemon-exit.c:2128 -#: src/exit/gnunet-daemon-exit.c:2378 src/vpn/gnunet-service-vpn.c:1450 -#: src/vpn/gnunet-service-vpn.c:1854 src/vpn/gnunet-service-vpn.c:1991 +#: src/exit/gnunet-daemon-exit.c:948 src/exit/gnunet-daemon-exit.c:2402 +#: src/exit/gnunet-daemon-exit.c:2662 src/vpn/gnunet-service-vpn.c:1467 +#: src/vpn/gnunet-service-vpn.c:1871 src/vpn/gnunet-service-vpn.c:2008 msgid "# ICMPv6 packets dropped (type not allowed)" msgstr "" -#: src/exit/gnunet-daemon-exit.c:756 +#: src/exit/gnunet-daemon-exit.c:988 msgid "# ICMP packets dropped (not allowed)" msgstr "" -#: src/exit/gnunet-daemon-exit.c:763 +#: src/exit/gnunet-daemon-exit.c:995 msgid "ICMP Packet dropped, have no matching connection information\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:840 +#: src/exit/gnunet-daemon-exit.c:1072 msgid "UDP Packet dropped, have no matching connection information\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:915 +#: src/exit/gnunet-daemon-exit.c:1147 msgid "TCP Packet dropped, have no matching connection information\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:968 +#: src/exit/gnunet-daemon-exit.c:1200 #, fuzzy msgid "# Packets received from TUN" msgstr "# Bytes empfangen über HTTP" -#: src/exit/gnunet-daemon-exit.c:982 +#: src/exit/gnunet-daemon-exit.c:1214 #, fuzzy msgid "# Bytes received from TUN" msgstr "# Bytes empfangen über HTTP" -#: src/exit/gnunet-daemon-exit.c:1008 +#: src/exit/gnunet-daemon-exit.c:1240 msgid "IPv4 packet options received. Ignored.\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:1035 +#: src/exit/gnunet-daemon-exit.c:1267 #, c-format msgid "IPv4 packet with unsupported next header %u received. Ignored.\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:1081 +#: src/exit/gnunet-daemon-exit.c:1313 #, c-format msgid "IPv6 packet with unsupported next header %d received. Ignored.\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:1089 +#: src/exit/gnunet-daemon-exit.c:1321 #, c-format msgid "Packet from unknown protocol %u received. Ignored.\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:1471 +#: src/exit/gnunet-daemon-exit.c:1703 #, fuzzy msgid "# TCP packets sent via TUN" msgstr "# Bytes gesendet über UDP" -#: src/exit/gnunet-daemon-exit.c:1571 +#: src/exit/gnunet-daemon-exit.c:1814 #, fuzzy msgid "# TCP service creation requests received via mesh" msgstr "# Client Trace-Anfragen empfangen" -#: src/exit/gnunet-daemon-exit.c:1574 src/exit/gnunet-daemon-exit.c:1653 -#: src/exit/gnunet-daemon-exit.c:1763 src/exit/gnunet-daemon-exit.c:1993 -#: src/exit/gnunet-daemon-exit.c:2235 src/exit/gnunet-daemon-exit.c:2516 -#: src/exit/gnunet-daemon-exit.c:2616 +#: src/exit/gnunet-daemon-exit.c:1817 src/exit/gnunet-daemon-exit.c:1906 +#: src/exit/gnunet-daemon-exit.c:2026 src/exit/gnunet-daemon-exit.c:2267 +#: src/exit/gnunet-daemon-exit.c:2519 src/exit/gnunet-daemon-exit.c:2811 +#: src/exit/gnunet-daemon-exit.c:2921 #, fuzzy msgid "# Bytes received from MESH" msgstr "# Bytes empfangen über HTTP" -#: src/exit/gnunet-daemon-exit.c:1607 src/exit/gnunet-daemon-exit.c:2638 +#: src/exit/gnunet-daemon-exit.c:1850 src/exit/gnunet-daemon-exit.c:2943 #, c-format msgid "No service found for %s on port %d!\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:1611 +#: src/exit/gnunet-daemon-exit.c:1854 #, fuzzy msgid "# TCP requests dropped (no such service)" msgstr "# gap Anfragen verworfen: Kollision in RT" -#: src/exit/gnunet-daemon-exit.c:1656 +#: src/exit/gnunet-daemon-exit.c:1909 #, fuzzy msgid "# TCP IP-exit creation requests received via mesh" msgstr "# Client Trace-Anfragen empfangen" -#: src/exit/gnunet-daemon-exit.c:1766 +#: src/exit/gnunet-daemon-exit.c:2029 #, fuzzy msgid "# TCP data requests received via mesh" msgstr "# Client Trace-Anfragen empfangen" -#: src/exit/gnunet-daemon-exit.c:1780 +#: src/exit/gnunet-daemon-exit.c:2043 #, fuzzy msgid "# TCP DATA requests dropped (no session)" msgstr "# gap Anfragen verworfen: Kollision in RT" -#: src/exit/gnunet-daemon-exit.c:1830 +#: src/exit/gnunet-daemon-exit.c:2093 #, fuzzy msgid "# ICMP packets sent via TUN" msgstr "# Bytes gesendet über UDP" -#: src/exit/gnunet-daemon-exit.c:1996 +#: src/exit/gnunet-daemon-exit.c:2270 #, fuzzy msgid "# ICMP IP-exit requests received via mesh" msgstr "# Client Trace-Anfragen empfangen" -#: src/exit/gnunet-daemon-exit.c:2238 +#: src/exit/gnunet-daemon-exit.c:2522 #, fuzzy msgid "# ICMP service requests received via mesh" msgstr "Empfangene Client-Nachricht ist ungültig.\n" -#: src/exit/gnunet-daemon-exit.c:2304 src/vpn/gnunet-service-vpn.c:1384 -#: src/vpn/gnunet-service-vpn.c:1952 +#: src/exit/gnunet-daemon-exit.c:2588 src/vpn/gnunet-service-vpn.c:1401 +#: src/vpn/gnunet-service-vpn.c:1969 msgid "# ICMPv4 packets dropped (impossible PT to v6)" msgstr "" -#: src/exit/gnunet-daemon-exit.c:2363 src/vpn/gnunet-service-vpn.c:1420 -#: src/vpn/gnunet-service-vpn.c:1432 src/vpn/gnunet-service-vpn.c:1842 +#: src/exit/gnunet-daemon-exit.c:2647 src/vpn/gnunet-service-vpn.c:1437 +#: src/vpn/gnunet-service-vpn.c:1449 src/vpn/gnunet-service-vpn.c:1859 msgid "# ICMPv6 packets dropped (impossible PT to v4)" msgstr "" -#: src/exit/gnunet-daemon-exit.c:2413 +#: src/exit/gnunet-daemon-exit.c:2697 #, fuzzy msgid "# UDP packets sent via TUN" msgstr "# Bytes gesendet über UDP" -#: src/exit/gnunet-daemon-exit.c:2519 +#: src/exit/gnunet-daemon-exit.c:2814 #, fuzzy msgid "# UDP IP-exit requests received via mesh" msgstr "# Client Trace-Anfragen empfangen" -#: src/exit/gnunet-daemon-exit.c:2619 +#: src/exit/gnunet-daemon-exit.c:2924 #, fuzzy msgid "# UDP service requests received via mesh" msgstr "# Client Trace-Anfragen empfangen" -#: src/exit/gnunet-daemon-exit.c:2642 +#: src/exit/gnunet-daemon-exit.c:2947 #, fuzzy msgid "# UDP requests dropped (no such service)" msgstr "# gap Anfragen verworfen: Kollision in RT" -#: src/exit/gnunet-daemon-exit.c:2882 +#: src/exit/gnunet-daemon-exit.c:2980 +msgid "# Inbound MESH tunnels created" +msgstr "" + +#: src/exit/gnunet-daemon-exit.c:3209 #, c-format msgid "No addresses found for hostname `%s' of service `%s'!\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:2896 src/exit/gnunet-daemon-exit.c:2908 +#: src/exit/gnunet-daemon-exit.c:3223 src/exit/gnunet-daemon-exit.c:3235 #, c-format msgid "Service `%s' configured for IPv4, but IPv4 is disabled!\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:2919 +#: src/exit/gnunet-daemon-exit.c:3246 #, c-format msgid "No IP addresses found for hostname `%s' of service `%s'!\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:3048 +#: src/exit/gnunet-daemon-exit.c:3364 msgid "" "This system does not support IPv4, will disable IPv4 functions despite them " "being enabled in the configuration\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:3056 +#: src/exit/gnunet-daemon-exit.c:3372 msgid "" "This system does not support IPv6, will disable IPv6 functions despite them " "being enabled in the configuration\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:3063 +#: src/exit/gnunet-daemon-exit.c:3379 msgid "" "Cannot enable IPv4 exit but disable IPv4 on TUN interface, will use " "ENABLE_IPv4=YES\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:3069 +#: src/exit/gnunet-daemon-exit.c:3385 msgid "" "Cannot enable IPv6 exit but disable IPv6 on TUN interface, will use " "ENABLE_IPv6=YES\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:3075 src/pt/gnunet-daemon-pt.c:884 +#: src/exit/gnunet-daemon-exit.c:3391 src/pt/gnunet-daemon-pt.c:884 msgid "No useful service enabled. Exiting.\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:3236 +#: src/exit/gnunet-daemon-exit.c:3620 msgid "Daemon to run to provide an IP exit node for the VPN" msgstr "" @@ -1855,113 +1818,113 @@ msgstr "# Bytes empfangen über TCP" msgid "# messages defragmented" msgstr "# defragmentierter Nachrichten" -#: src/fragmentation/fragmentation.c:203 +#: src/fragmentation/fragmentation.c:208 #, fuzzy msgid "# fragments transmitted" msgstr "# Selbstbekanntmachungen übertragen" -#: src/fragmentation/fragmentation.c:206 +#: src/fragmentation/fragmentation.c:211 #, fuzzy msgid "# fragments retransmitted" msgstr "# Selbstbekanntmachungen übertragen" -#: src/fragmentation/fragmentation.c:232 +#: src/fragmentation/fragmentation.c:237 #, fuzzy msgid "# fragments wrap arounds" msgstr "# Selbstbekanntmachungen übertragen" -#: src/fragmentation/fragmentation.c:273 +#: src/fragmentation/fragmentation.c:281 msgid "# messages fragmented" msgstr "# fragmentierter Nachrichten" -#: src/fragmentation/fragmentation.c:276 +#: src/fragmentation/fragmentation.c:284 msgid "# total size of fragmented messages" msgstr "" -#: src/fragmentation/fragmentation.c:363 +#: src/fragmentation/fragmentation.c:405 #, fuzzy msgid "# fragment acknowledgements received" msgstr "# Knotenankündigungen empfangen" -#: src/fragmentation/fragmentation.c:369 +#: src/fragmentation/fragmentation.c:411 msgid "# bits removed from fragmentation ACKs" msgstr "" -#: src/fragmentation/fragmentation.c:393 +#: src/fragmentation/fragmentation.c:435 #, fuzzy msgid "# fragmentation transmissions completed" msgstr "# Klartext PONG Nachrichten empfangen" -#: src/fs/fs_api.c:339 +#: src/fs/fs_api.c:465 #, fuzzy, c-format msgid "Could not open file `%s': %s" msgstr "Datei wurde als `%s' gespeichert.\n" -#: src/fs/fs_api.c:348 +#: src/fs/fs_api.c:474 #, fuzzy, c-format msgid "Could not read file `%s': %s" msgstr "Datei wurde als `%s' gespeichert.\n" -#: src/fs/fs_api.c:354 +#: src/fs/fs_api.c:480 #, c-format msgid "Short read reading from file `%s'!" msgstr "" -#: src/fs/fs_api.c:938 +#: src/fs/fs_api.c:1061 #, fuzzy, c-format msgid "Failed to resume publishing information `%s': %s\n" msgstr "Datei wurde als `%s' gespeichert.\n" -#: src/fs/fs_api.c:1395 +#: src/fs/fs_api.c:1520 #, c-format msgid "Failed to recover namespace `%s', cannot resume publishing operation.\n" msgstr "" -#: src/fs/fs_api.c:1437 +#: src/fs/fs_api.c:1562 #, c-format msgid "Failure while resuming publishing operation `%s': %s\n" msgstr "" -#: src/fs/fs_api.c:1453 +#: src/fs/fs_api.c:1578 #, fuzzy, c-format msgid "Failed to resume publishing operation `%s': %s\n" msgstr "Datei wurde als `%s' gespeichert.\n" -#: src/fs/fs_api.c:2106 +#: src/fs/fs_api.c:2229 #, c-format msgid "Failure while resuming unindexing operation `%s': %s\n" msgstr "" -#: src/fs/fs_api.c:2116 +#: src/fs/fs_api.c:2239 #, fuzzy, c-format msgid "Failed to resume unindexing operation `%s': %s\n" msgstr "Datei wurde als `%s' gespeichert.\n" -#: src/fs/fs_api.c:2241 src/fs/fs_api.c:2480 +#: src/fs/fs_api.c:2364 src/fs/fs_api.c:2604 #, fuzzy, c-format msgid "Failed to resume sub-download `%s': %s\n" msgstr "Datei wurde als `%s' gespeichert.\n" -#: src/fs/fs_api.c:2258 +#: src/fs/fs_api.c:2381 #, fuzzy, c-format msgid "Failed to resume sub-search `%s': %s\n" msgstr "Datei wurde als `%s' gespeichert.\n" -#: src/fs/fs_api.c:2270 src/fs/fs_api.c:2289 src/fs/fs_api.c:2773 +#: src/fs/fs_api.c:2394 src/fs/fs_api.c:2413 src/fs/fs_api.c:2897 #, c-format msgid "Failure while resuming search operation `%s': %s\n" msgstr "" -#: src/fs/fs_api.c:2471 +#: src/fs/fs_api.c:2595 #, c-format msgid "Failed to resume sub-download `%s': could not open file `%s'\n" msgstr "" -#: src/fs/fs_api.c:2717 +#: src/fs/fs_api.c:2841 msgid "Could not resume running search, will resume as paused search\n" msgstr "" -#: src/fs/fs_api.c:2811 +#: src/fs/fs_api.c:2935 #, c-format msgid "Failure while resuming download operation `%s': %s\n" msgstr "" @@ -1971,64 +1934,64 @@ msgstr "" msgid "MAGIC mismatch. This is not a GNUnet directory.\n" msgstr "Dateiformat fehlerhaft (kein GNUnet Verzeichnis?)\n" -#: src/fs/fs_download.c:311 +#: src/fs/fs_download.c:321 #, fuzzy msgid "" "Recursive downloads of directories larger than 4 GB are not supported on 32-" "bit systems\n" msgstr "Rekursiver Download des Verzeichnisses `%s' bei %llu von %llu Bytes.\n" -#: src/fs/fs_download.c:331 +#: src/fs/fs_download.c:341 msgid "Directory too large for system address space\n" msgstr "" -#: src/fs/fs_download.c:497 src/fs/fs_download.c:509 +#: src/fs/fs_download.c:507 src/fs/fs_download.c:519 #, fuzzy, c-format msgid "Failed to open file `%s' for writing" msgstr "Datei wurde als `%s' gespeichert.\n" -#: src/fs/fs_download.c:878 +#: src/fs/fs_download.c:888 #, fuzzy, c-format msgid "Failed to create directory for recursive download of `%s'\n" msgstr "Fehler beim Aktualisieren der Daten des Moduls `%s'\n" -#: src/fs/fs_download.c:960 +#: src/fs/fs_download.c:970 #, c-format msgid "" "Internal error or bogus download URI (expected %u bytes at depth %u and " "offset %llu/%llu, got %u bytes)" msgstr "" -#: src/fs/fs_download.c:986 +#: src/fs/fs_download.c:996 msgid "internal error decrypting content" msgstr "" -#: src/fs/fs_download.c:1009 +#: src/fs/fs_download.c:1019 #, fuzzy, c-format msgid "Download failed: could not open file `%s': %s" msgstr "Datei wurde als `%s' gespeichert.\n" -#: src/fs/fs_download.c:1019 +#: src/fs/fs_download.c:1029 #, fuzzy, c-format msgid "Failed to seek to offset %llu in file `%s': %s" msgstr "Datei wurde als `%s' gespeichert.\n" -#: src/fs/fs_download.c:1028 +#: src/fs/fs_download.c:1038 #, fuzzy, c-format msgid "Failed to write block of %u bytes at offset %llu in file `%s': %s" msgstr "Datei wurde als `%s' gespeichert.\n" -#: src/fs/fs_download.c:1125 +#: src/fs/fs_download.c:1136 #, fuzzy msgid "internal error decoding tree" msgstr "=\tFehler beim Lesen des Verzeichnisses.\n" -#: src/fs/fs_download.c:1888 +#: src/fs/fs_download.c:1927 #, fuzzy msgid "Invalid URI" msgstr "Ungültiger Parameter: `%s'\n" -#: src/fs/fs_getopt.c:191 +#: src/fs/fs_getopt.c:192 #, c-format msgid "" "Unknown metadata type in metadata option `%s'. Using metadata type " @@ -2070,41 +2033,38 @@ msgstr "SQLite Datenbank konnte nicht initialisiert werden.\n" msgid "Failed to connect to datastore service" msgstr "Es konnte keine Verbindung mit gnunetd hergestellt werden.\n" -#: src/fs/fs_namespace.c:57 src/fs/fs_namespace.c:83 -#, fuzzy, c-format -msgid "Configuration fails to specify `%s' in section `%s'\n" -msgstr "" -"Die Konfigurationsdatei muss in der Sektion `%s' unter `%s' ein Verzeichnis " -"angeben, in dem FS Daten gespeichert werden.\n" - -#: src/fs/fs_namespace.c:112 +#: src/fs/fs_namespace.c:110 #, fuzzy, c-format msgid "Failed to open `%s' for writing: %s\n" msgstr "Datei wurde als `%s' gespeichert.\n" -#: src/fs/fs_namespace.c:134 src/fs/fs_namespace.c:222 +#: src/fs/fs_namespace.c:132 src/fs/fs_namespace.c:220 #, fuzzy, c-format msgid "Failed to write `%s': %s\n" msgstr "Es konnte keine Verbindung mit gnunetd hergestellt werden.\n" -#: src/fs/fs_namespace.c:256 +#: src/fs/fs_namespace.c:252 #, fuzzy, c-format msgid "Failed to create or read private key for namespace `%s'\n" msgstr "Fehler beim Aktualisieren der Daten des Moduls `%s'\n" -#: src/fs/fs_namespace.c:371 +#: src/fs/fs_namespace.c:367 #, fuzzy, c-format msgid "Failed to read namespace private key file `%s', deleting it!\n" msgstr "" "Der Eintrag konnte dem Namespace `%s' nicht hinzugefügt werden (existiert " "er?)\n" -#: src/fs/fs_namespace.c:588 src/fs/fs_publish_ksk.c:295 +#: src/fs/fs_namespace.c:558 +msgid "Identifiers or URI too long to create SBlock" +msgstr "" + +#: src/fs/fs_namespace.c:593 src/fs/fs_publish_ksk.c:295 #, fuzzy msgid "Internal error." msgstr "Unbekannter Fehler.\n" -#: src/fs/fs_namespace.c:631 +#: src/fs/fs_namespace.c:636 #, fuzzy msgid "Failed to connect to datastore." msgstr "Es konnte keine Verbindung mit gnunetd hergestellt werden." @@ -2116,62 +2076,62 @@ msgstr "" "\n" "Fehler beim Uploaden der Datei: %s\n" -#: src/fs/fs_publish.c:621 src/fs/fs_publish.c:638 src/fs/fs_publish.c:677 -#: src/fs/fs_publish.c:697 src/fs/fs_publish.c:722 src/fs/fs_publish.c:862 +#: src/fs/fs_publish.c:622 src/fs/fs_publish.c:639 src/fs/fs_publish.c:678 +#: src/fs/fs_publish.c:698 src/fs/fs_publish.c:723 src/fs/fs_publish.c:863 #, fuzzy, c-format msgid "Can not index file `%s': %s. Will try to insert instead.\n" msgstr "Indizieren der Datei `%s' schlug fehl. Versuch Datei einzufügen...\n" -#: src/fs/fs_publish.c:623 +#: src/fs/fs_publish.c:624 msgid "timeout on index-start request to `fs' service" msgstr "" -#: src/fs/fs_publish.c:635 +#: src/fs/fs_publish.c:636 #, fuzzy msgid "unknown error" msgstr "Unbekannter Fehler" -#: src/fs/fs_publish.c:678 +#: src/fs/fs_publish.c:679 msgid "failed to compute hash" msgstr "" -#: src/fs/fs_publish.c:698 +#: src/fs/fs_publish.c:699 msgid "filename too long" msgstr "" -#: src/fs/fs_publish.c:723 +#: src/fs/fs_publish.c:724 #, fuzzy msgid "could not connect to `fs' service" msgstr "Verbindung zu gnunetd konnte nicht hergestellt werden.\n" -#: src/fs/fs_publish.c:746 +#: src/fs/fs_publish.c:747 #, fuzzy, c-format msgid "Failed to get file identifiers for `%s'\n" msgstr "Fehler beim Lesen der Freunde-Liste von `%s'\n" -#: src/fs/fs_publish.c:811 +#: src/fs/fs_publish.c:812 #, fuzzy, c-format msgid "Recursive upload failed at `%s': %s" msgstr "`%s' schlug fehl bei %s:%d mit dem Fehler: `%s'.\n" -#: src/fs/fs_publish.c:817 +#: src/fs/fs_publish.c:818 #, fuzzy, c-format msgid "Recursive upload failed: %s" msgstr "" "\n" "Fehler beim Uploaden der Datei: %s\n" -#: src/fs/fs_publish.c:863 +#: src/fs/fs_publish.c:864 #, fuzzy msgid "needs to be an actual file" msgstr "`%s' ist keine normale Datei.\n" -#: src/fs/fs_publish.c:1071 +#: src/fs/fs_publish.c:1090 #, c-format msgid "Insufficient space for publishing: %s" msgstr "" -#: src/fs/fs_publish.c:1142 +#: src/fs/fs_publish.c:1161 #, c-format msgid "Reserving space for %u entries and %llu bytes for publication\n" msgstr "" @@ -2181,16 +2141,11 @@ msgstr "" msgid "Could not connect to datastore." msgstr "Verbindung zu gnunetd konnte nicht hergestellt werden.\n" -#: src/fs/fs_search.c:829 +#: src/fs/fs_search.c:892 #, c-format msgid "Got result with unknown block type `%d', ignoring" msgstr "" -#: src/fs/fs_test_lib.c:269 -#, fuzzy, c-format -msgid "Failed to start daemon: %s\n" -msgstr "Fehler beim Starten der Collection.\n" - #: src/fs/fs_unindex.c:58 msgid "Failed to find given position in file" msgstr "" @@ -2218,97 +2173,97 @@ msgstr "Ungültige Antwort auf `%s'.\n" msgid "Failed to connect to FS service for unindexing." msgstr "Es konnte keine Verbindung mit gnunetd hergestellt werden." -#: src/fs/fs_unindex.c:344 +#: src/fs/fs_unindex.c:349 src/fs/fs_unindex.c:361 #, fuzzy msgid "Failed to get KSKs from directory scan." msgstr "Dateiformat fehlerhaft (kein GNUnet Verzeichnis?)\n" -#: src/fs/fs_unindex.c:356 +#: src/fs/fs_unindex.c:357 #, fuzzy, c-format msgid "Internal error scanning `%s'.\n" msgstr "=\tFehler beim Lesen des Verzeichnisses.\n" -#: src/fs/fs_unindex.c:411 +#: src/fs/fs_unindex.c:416 #, fuzzy, c-format msgid "Failed to remove KBlock: %s\n" msgstr "Datei wurde als `%s' gespeichert.\n" -#: src/fs/fs_unindex.c:501 +#: src/fs/fs_unindex.c:506 #, fuzzy, c-format msgid "Failed to parse URI `%s' from KBlock!\n" msgstr "Datei `%s' hat URI: %s\n" -#: src/fs/fs_unindex.c:553 src/fs/fs_unindex.c:618 +#: src/fs/fs_unindex.c:558 src/fs/fs_unindex.c:623 #, fuzzy msgid "Failed to connect to `datastore' service." msgstr "`%s' Dienst konnte nicht initialisiert werden.\n" -#: src/fs/fs_unindex.c:631 +#: src/fs/fs_unindex.c:636 #, fuzzy msgid "Failed to open file for unindexing." msgstr "Es konnte keine Verbindung mit gnunetd hergestellt werden." -#: src/fs/fs_unindex.c:665 +#: src/fs/fs_unindex.c:670 #, fuzzy msgid "Failed to compute hash of file." msgstr "Es konnte keine Verbindung mit gnunetd hergestellt werden." -#: src/fs/fs_uri.c:220 -#, c-format +#: src/fs/fs_uri.c:221 +#, no-c-format msgid "`%' must be followed by HEX number" msgstr "" -#: src/fs/fs_uri.c:279 +#: src/fs/fs_uri.c:280 #, fuzzy msgid "Malformed KSK URI (must not begin or end with `+')" msgstr "Ungültige URL `%s' (muss mit `%s' beginnen)\n" -#: src/fs/fs_uri.c:297 +#: src/fs/fs_uri.c:298 msgid "`++' not allowed in KSK URI" msgstr "" -#: src/fs/fs_uri.c:304 +#: src/fs/fs_uri.c:305 msgid "Quotes not balanced in KSK URI" msgstr "" -#: src/fs/fs_uri.c:372 src/fs/fs_uri.c:379 +#: src/fs/fs_uri.c:373 src/fs/fs_uri.c:380 msgid "Malformed SKS URI" msgstr "" -#: src/fs/fs_uri.c:423 src/fs/fs_uri.c:438 +#: src/fs/fs_uri.c:424 src/fs/fs_uri.c:439 msgid "Malformed CHK URI" msgstr "" -#: src/fs/fs_uri.c:568 src/fs/fs_uri.c:583 src/fs/fs_uri.c:593 -#: src/fs/fs_uri.c:621 +#: src/fs/fs_uri.c:569 src/fs/fs_uri.c:584 src/fs/fs_uri.c:594 +#: src/fs/fs_uri.c:622 msgid "SKS URI malformed" msgstr "" -#: src/fs/fs_uri.c:603 +#: src/fs/fs_uri.c:604 msgid "SKS URI malformed (could not decode public key)" msgstr "" -#: src/fs/fs_uri.c:609 +#: src/fs/fs_uri.c:610 msgid "SKS URI malformed (could not find signature)" msgstr "" -#: src/fs/fs_uri.c:615 +#: src/fs/fs_uri.c:616 msgid "SKS URI malformed (could not decode signature)" msgstr "" -#: src/fs/fs_uri.c:628 +#: src/fs/fs_uri.c:629 msgid "SKS URI malformed (could not parse expiration time)" msgstr "" -#: src/fs/fs_uri.c:640 +#: src/fs/fs_uri.c:641 msgid "SKS URI malformed (signature failed validation)" msgstr "" -#: src/fs/fs_uri.c:678 +#: src/fs/fs_uri.c:679 msgid "Unrecognized URI type" msgstr "" -#: src/fs/fs_uri.c:903 +#: src/fs/fs_uri.c:904 #, fuzzy msgid "Lacking key configuration settings.\n" msgstr "GNUnet Konfiguration" @@ -2326,6 +2281,70 @@ msgstr "Keine Schlüsselwörter angegeben!\n" msgid "Number of double-quotes not balanced!\n" msgstr "" +#: src/fs/gnunet-auto-share.c:236 +#, fuzzy, c-format +msgid "Failed to load state: %s\n" +msgstr "Fehler beim Starten der Collection.\n" + +#: src/fs/gnunet-auto-share.c:289 src/fs/gnunet-auto-share.c:299 +#: src/fs/gnunet-auto-share.c:309 +#, fuzzy, c-format +msgid "Failed to save state to file %s\n" +msgstr "Fehler beim Lesen der Freunde-Liste von `%s'\n" + +#: src/fs/gnunet-auto-share.c:401 +#, c-format +msgid "Publication of `%s' done\n" +msgstr "" + +#: src/fs/gnunet-auto-share.c:488 +#, fuzzy, c-format +msgid "Publishing `%s'\n" +msgstr "" +"\n" +"Fehler beim Uploaden der Datei: %s\n" + +#: src/fs/gnunet-auto-share.c:497 +#, fuzzy, c-format +msgid "Failed to run `%s'\n" +msgstr "Fehler beim Starten der Collection.\n" + +#: src/fs/gnunet-auto-share.c:686 +#, fuzzy, c-format +msgid "" +"You must specify one and only one directory name for automatic publication.\n" +msgstr "Sie dürfen nur eine Datei zum Deindizieren angeben.\n" + +#: src/fs/gnunet-auto-share.c:737 src/fs/gnunet-pseudonym.c:279 +#: src/fs/gnunet-publish.c:683 +msgid "set the desired LEVEL of sender-anonymity" +msgstr "Gewünschten Grad an Sender-Anonymität festlegen" + +#: src/fs/gnunet-auto-share.c:741 src/fs/gnunet-publish.c:687 +msgid "disable adding the creation time to the metadata of the uploaded file" +msgstr "" + +#: src/fs/gnunet-auto-share.c:744 src/fs/gnunet-publish.c:690 +msgid "do not use libextractor to add keywords or metadata" +msgstr "" + +#: src/fs/gnunet-auto-share.c:747 src/fs/gnunet-publish.c:714 +msgid "specify the priority of the content" +msgstr "Die Priorität des Inhalts angeben" + +#: src/fs/gnunet-auto-share.c:750 src/fs/gnunet-pseudonym.c:304 +#: src/fs/gnunet-publish.c:721 +msgid "set the desired replication LEVEL" +msgstr "" + +#: src/fs/gnunet-auto-share.c:770 +msgid "Automatically publish files from a directory on GNUnet" +msgstr "" + +#: src/fs/gnunet-daemon-fsprofiler.c:656 +msgid "Daemon to use file-sharing to measure its performance." +msgstr "" + #: src/fs/gnunet-directory.c:49 #, c-format msgid "\t\n" @@ -2356,97 +2375,97 @@ msgstr "Fehler beim Lesen der Freunde-Liste von `%s'\n" msgid "`%s' is not a GNUnet directory\n" msgstr "Dateiformat fehlerhaft (kein GNUnet Verzeichnis?)\n" -#: src/fs/gnunet-directory.c:179 +#: src/fs/gnunet-directory.c:183 #, fuzzy msgid "Display contents of a GNUnet directory" msgstr "Dateiformat fehlerhaft (kein GNUnet Verzeichnis?)\n" -#: src/fs/gnunet-download.c:101 +#: src/fs/gnunet-download.c:137 #, fuzzy, c-format msgid "Starting download `%s'.\n" msgstr "Collection `%s' begonnen.\n" -#: src/fs/gnunet-download.c:110 +#: src/fs/gnunet-download.c:147 #, fuzzy msgid "" msgstr "Unbekannter Fehler" -#: src/fs/gnunet-download.c:119 +#: src/fs/gnunet-download.c:157 #, c-format msgid "" "Downloading `%s' at %llu/%llu (%s remaining, %s/s). Block took %s to " "download\n" msgstr "" -#: src/fs/gnunet-download.c:129 +#: src/fs/gnunet-download.c:179 #, fuzzy, c-format msgid "Error downloading: %s.\n" msgstr "Fehler beim Download: %s\n" -#: src/fs/gnunet-download.c:137 +#: src/fs/gnunet-download.c:194 #, fuzzy, c-format msgid "Downloading `%s' done (%s/s).\n" msgstr "Upload abgewiesen!" -#: src/fs/gnunet-download.c:152 src/fs/gnunet-publish.c:190 -#: src/fs/gnunet-search.c:190 src/fs/gnunet-unindex.c:109 +#: src/fs/gnunet-download.c:209 src/fs/gnunet-publish.c:195 +#: src/fs/gnunet-search.c:193 src/fs/gnunet-unindex.c:108 #, c-format msgid "Unexpected status: %d\n" msgstr "" -#: src/fs/gnunet-download.c:177 +#: src/fs/gnunet-download.c:234 #, fuzzy msgid "You need to specify a URI argument.\n" msgstr "Sie müssen einen Empfänger angeben!\n" -#: src/fs/gnunet-download.c:183 src/fs/gnunet-publish.c:624 +#: src/fs/gnunet-download.c:240 src/fs/gnunet-publish.c:629 #, fuzzy, c-format msgid "Failed to parse URI: %s\n" msgstr "Datei `%s' hat URI: %s\n" -#: src/fs/gnunet-download.c:190 +#: src/fs/gnunet-download.c:247 msgid "Only CHK or LOC URIs supported.\n" msgstr "" -#: src/fs/gnunet-download.c:197 +#: src/fs/gnunet-download.c:254 msgid "Target filename must be specified.\n" msgstr "" -#: src/fs/gnunet-download.c:211 src/fs/gnunet-publish.c:602 -#: src/fs/gnunet-search.c:241 src/fs/gnunet-unindex.c:141 +#: src/fs/gnunet-download.c:268 src/fs/gnunet-publish.c:607 +#: src/fs/gnunet-search.c:243 src/fs/gnunet-unindex.c:140 #, fuzzy, c-format msgid "Could not initialize `%s' subsystem.\n" msgstr "`%s' Dienst konnte nicht initialisiert werden.\n" -#: src/fs/gnunet-download.c:248 src/fs/gnunet-search.c:285 +#: src/fs/gnunet-download.c:305 src/fs/gnunet-search.c:282 msgid "set the desired LEVEL of receiver-anonymity" msgstr "Den Grad LEVEL der gewünschten Empfänger-Anonymität setzen" -#: src/fs/gnunet-download.c:251 +#: src/fs/gnunet-download.c:308 msgid "delete incomplete downloads (when aborted with CTRL-C)" msgstr "" -#: src/fs/gnunet-download.c:254 src/fs/gnunet-search.c:288 +#: src/fs/gnunet-download.c:311 src/fs/gnunet-search.c:285 msgid "only search the local peer (no P2P network search)" msgstr "" -#: src/fs/gnunet-download.c:257 +#: src/fs/gnunet-download.c:314 msgid "write the file to FILENAME" msgstr "Schreibe die Datei in DATEINAME" -#: src/fs/gnunet-download.c:261 +#: src/fs/gnunet-download.c:318 msgid "set the maximum number of parallel downloads that is allowed" msgstr "" -#: src/fs/gnunet-download.c:265 +#: src/fs/gnunet-download.c:322 msgid "set the maximum number of parallel requests for blocks that is allowed" msgstr "" -#: src/fs/gnunet-download.c:268 +#: src/fs/gnunet-download.c:325 msgid "download a GNUnet directory recursively" msgstr "Das GNUnet Verzeichnis rekursiv herunterladen" -#: src/fs/gnunet-download.c:278 +#: src/fs/gnunet-download.c:339 msgid "" "Download files from GNUnet using a GNUnet CHK or LOC URI (gnunet://fs/" "chk/...)" @@ -2456,12 +2475,28 @@ msgstr "" msgid "print a list of all indexed files" msgstr "" -#: src/fs/gnunet-fs.c:124 +#: src/fs/gnunet-fs.c:127 #, fuzzy msgid "Special file-sharing operations" msgstr "Alle Optionen anzeigen" -#: src/fs/gnunet-pseudonym.c:160 src/statistics/gnunet-statistics.c:167 +#: src/fs/gnunet-fs-profiler.c:182 +msgid "run the experiment with COUNT peers" +msgstr "" + +#: src/fs/gnunet-fs-profiler.c:185 +msgid "specifies name of a file with the HOSTS the testbed should use" +msgstr "" + +#: src/fs/gnunet-fs-profiler.c:188 +msgid "automatically terminate experiment after DELAY" +msgstr "" + +#: src/fs/gnunet-fs-profiler.c:197 +msgid "run a testbed to measure file-sharing performance" +msgstr "" + +#: src/fs/gnunet-pseudonym.c:160 src/statistics/gnunet-statistics.c:283 #, fuzzy, c-format msgid "Invalid argument `%s'\n" msgstr "Ungültiger Parameter: `%s'\n" @@ -2472,10 +2507,6 @@ msgstr "Ungültiger Parameter: `%s'\n" msgid "Option `%s' ignored\n" msgstr "%s: Option `%s' ist mehrdeutig\n" -#: src/fs/gnunet-pseudonym.c:279 src/fs/gnunet-publish.c:678 -msgid "set the desired LEVEL of sender-anonymity" -msgstr "Gewünschten Grad an Sender-Anonymität festlegen" - #: src/fs/gnunet-pseudonym.c:282 msgid "create or advertise namespace NAME" msgstr "" @@ -2493,7 +2524,7 @@ msgstr "" "Ein zusätzliches Schlüsselwort für alle Dateien und Verzeichnisse hinzufügen " "(diese Option kann mehrmals angegeben werden)" -#: src/fs/gnunet-pseudonym.c:292 src/fs/gnunet-publish.c:697 +#: src/fs/gnunet-pseudonym.c:292 src/fs/gnunet-publish.c:702 msgid "set the meta-data for the given TYPE to the given VALUE" msgstr "" "Die Meta-Daten des angegebenen Typs TYPE auf den angegebenen Wert VALUE " @@ -2512,10 +2543,6 @@ msgstr "" msgid "do not print names of remote namespaces" msgstr "" -#: src/fs/gnunet-pseudonym.c:304 src/fs/gnunet-publish.c:716 -msgid "set the desired replication LEVEL" -msgstr "" - #: src/fs/gnunet-pseudonym.c:307 #, fuzzy msgid "specify ID of the root of the namespace" @@ -2526,145 +2553,132 @@ msgstr "das Rating eines Namespaces setzen" msgid "change rating of namespace ID by VALUE" msgstr "das Rating eines Namespaces setzen" -#: src/fs/gnunet-pseudonym.c:318 +#: src/fs/gnunet-pseudonym.c:322 msgid "Manage GNUnet pseudonyms." msgstr "" -#: src/fs/gnunet-publish.c:147 +#: src/fs/gnunet-publish.c:152 #, c-format msgid "Publishing `%s' at %llu/%llu (%s remaining)\n" msgstr "" -#: src/fs/gnunet-publish.c:155 +#: src/fs/gnunet-publish.c:159 #, fuzzy, c-format msgid "Error publishing: %s.\n" msgstr "Fehler beim Download: %s\n" -#: src/fs/gnunet-publish.c:165 +#: src/fs/gnunet-publish.c:169 #, c-format msgid "Publishing `%s' done.\n" msgstr "" -#: src/fs/gnunet-publish.c:169 +#: src/fs/gnunet-publish.c:173 #, fuzzy, c-format msgid "URI is `%s'.\n" msgstr "Ich bin Peer `%s'.\n" -#: src/fs/gnunet-publish.c:187 +#: src/fs/gnunet-publish.c:192 #, fuzzy msgid "Cleanup after abort complete.\n" msgstr "`%s' Startvorgang abgeschlossen.\n" -#: src/fs/gnunet-publish.c:305 +#: src/fs/gnunet-publish.c:310 #, fuzzy, c-format msgid "Meta data for file `%s' (%s)\n" msgstr "Daten des Moduls `%s' werden aktualisiert\n" -#: src/fs/gnunet-publish.c:307 +#: src/fs/gnunet-publish.c:312 #, fuzzy, c-format msgid "Keywords for file `%s' (%s)\n" msgstr "Schlüsselwörter für Datei `%s':\n" -#: src/fs/gnunet-publish.c:358 +#: src/fs/gnunet-publish.c:363 src/fs/gnunet-publish.c:617 #, fuzzy, c-format -msgid "Failed to create namespace `%s'\n" +msgid "Failed to create namespace `%s' (illegal filename?)\n" msgstr "Namespace `%s' konnte nicht erstellt werden (existiert bereits?).\n" -#: src/fs/gnunet-publish.c:433 +#: src/fs/gnunet-publish.c:438 #, fuzzy msgid "Could not publish\n" msgstr "`%s' konnte nicht aufgelöst werden: %s\n" -#: src/fs/gnunet-publish.c:460 +#: src/fs/gnunet-publish.c:465 #, fuzzy msgid "Could not start publishing.\n" msgstr "Anwendung `%s' konnte nicht initialisiert werden.\n" -#: src/fs/gnunet-publish.c:491 +#: src/fs/gnunet-publish.c:496 #, fuzzy, c-format msgid "Scanning directory `%s'.\n" msgstr "Fehler beim Lesen der Freunde-Liste von `%s'\n" -#: src/fs/gnunet-publish.c:493 +#: src/fs/gnunet-publish.c:498 #, fuzzy, c-format msgid "Scanning file `%s'.\n" msgstr "Collection `%s' begonnen.\n" -#: src/fs/gnunet-publish.c:498 +#: src/fs/gnunet-publish.c:503 #, c-format msgid "There was trouble processing file `%s', skipping it.\n" msgstr "" -#: src/fs/gnunet-publish.c:503 +#: src/fs/gnunet-publish.c:508 #, fuzzy msgid "Preprocessing complete.\n" msgstr "GNUnet wurde erfolgreich heruntergefahren.\n" -#: src/fs/gnunet-publish.c:507 +#: src/fs/gnunet-publish.c:512 #, fuzzy, c-format msgid "Extracting meta data from file `%s' complete.\n" msgstr "Daten des Moduls `%s' werden aktualisiert\n" -#: src/fs/gnunet-publish.c:511 +#: src/fs/gnunet-publish.c:516 msgid "Meta data extraction has finished.\n" msgstr "" -#: src/fs/gnunet-publish.c:518 +#: src/fs/gnunet-publish.c:523 #, fuzzy msgid "Internal error scanning directory.\n" msgstr "=\tFehler beim Lesen des Verzeichnisses.\n" -#: src/fs/gnunet-publish.c:552 +#: src/fs/gnunet-publish.c:557 #, c-format msgid "Cannot extract metadata from a URI!\n" msgstr "" -#: src/fs/gnunet-publish.c:559 +#: src/fs/gnunet-publish.c:564 #, c-format msgid "You must specify one and only one filename for insertion.\n" msgstr "Sie dürfen nur eine Datei zum Deindizieren angeben.\n" -#: src/fs/gnunet-publish.c:565 +#: src/fs/gnunet-publish.c:570 #, fuzzy, c-format msgid "You must NOT specify an URI and a filename.\n" msgstr "Sie müssen einen Empfänger angeben!\n" -#: src/fs/gnunet-publish.c:573 src/vpn/gnunet-vpn.c:214 +#: src/fs/gnunet-publish.c:578 src/vpn/gnunet-vpn.c:213 #, fuzzy, c-format msgid "Option `%s' is required when using option `%s'.\n" msgstr "Option `%s' macht keinen Sinn ohne die Option `%s'.\n" -#: src/fs/gnunet-publish.c:583 src/fs/gnunet-publish.c:590 -#: src/transport/gnunet-transport.c:560 +#: src/fs/gnunet-publish.c:588 src/fs/gnunet-publish.c:595 +#: src/transport/gnunet-transport.c:843 src/transport/gnunet-transport.c:873 #, c-format msgid "Option `%s' makes no sense without option `%s'.\n" msgstr "Option `%s' macht keinen Sinn ohne die Option `%s'.\n" -#: src/fs/gnunet-publish.c:612 -#, fuzzy, c-format -msgid "Could not create namespace `%s'\n" -msgstr "Namespace `%s' konnte nicht erstellt werden (existiert bereits?).\n" - -#: src/fs/gnunet-publish.c:645 +#: src/fs/gnunet-publish.c:650 #, fuzzy, c-format msgid "Failed to access `%s': %s\n" msgstr "Datei wurde als `%s' gespeichert.\n" -#: src/fs/gnunet-publish.c:657 +#: src/fs/gnunet-publish.c:662 msgid "" "Failed to start meta directory scanner. Is gnunet-helper-publish-fs " "installed?\n" msgstr "" -#: src/fs/gnunet-publish.c:682 -msgid "disable adding the creation time to the metadata of the uploaded file" -msgstr "" - -#: src/fs/gnunet-publish.c:685 -msgid "do not use libextractor to add keywords or metadata" -msgstr "" - -#: src/fs/gnunet-publish.c:689 +#: src/fs/gnunet-publish.c:694 msgid "" "print list of extracted keywords that would be used, but do not perform " "upload" @@ -2672,7 +2686,7 @@ msgstr "" "Liste der extrahierten Schlüsselworte, die verwendet werden würden, " "ausgeben, aber keinen Upload durchführen" -#: src/fs/gnunet-publish.c:693 +#: src/fs/gnunet-publish.c:698 msgid "" "add an additional keyword for the top-level file or directory (this option " "can be specified multiple times)" @@ -2680,7 +2694,7 @@ msgstr "" "Ein zusätzliches Schlüsselwort für die Datei oder das Verzeichnis auf der " "obersten Ebene hinzufügen (diese Option kann mehrmals angegeben werden)" -#: src/fs/gnunet-publish.c:700 +#: src/fs/gnunet-publish.c:705 msgid "" "do not index, perform full insertion (stores entire file in encrypted form " "in GNUnet database)" @@ -2688,7 +2702,7 @@ msgstr "" "Nicht indizieren, sondern komplett einfügen (speichert die gesamte Datei in " "verschlüsselter Form in der GNUnet Datenbank)" -#: src/fs/gnunet-publish.c:705 +#: src/fs/gnunet-publish.c:710 msgid "" "specify ID of an updated version to be published in the future (for " "namespace insertions only)" @@ -2696,239 +2710,228 @@ msgstr "" "ID einer aktualisierten Version angeben, die in der Zukunft veröffentlich " "werden soll. (nur für das Einfügen in Namespaces)" -#: src/fs/gnunet-publish.c:709 -msgid "specify the priority of the content" -msgstr "Die Priorität des Inhalts angeben" - -#: src/fs/gnunet-publish.c:713 +#: src/fs/gnunet-publish.c:718 msgid "publish the files under the pseudonym NAME (place file into namespace)" msgstr "" "Die Datei unter dem Pseudonym NAME veröffentlichen (platziert die Datei in " "einem Namespace)" -#: src/fs/gnunet-publish.c:719 +#: src/fs/gnunet-publish.c:724 msgid "" "only simulate the process but do not do any actual publishing (useful to " "compute URIs)" msgstr "" -#: src/fs/gnunet-publish.c:723 +#: src/fs/gnunet-publish.c:728 msgid "" "set the ID of this version of the publication (for namespace insertions only)" msgstr "" "die ID dieser Version der Veröffentlichung setzen (nur für das Einfügen in " "Namespaces)" -#: src/fs/gnunet-publish.c:727 +#: src/fs/gnunet-publish.c:732 msgid "" "URI to be published (can be used instead of passing a file to add keywords " "to the file with the respective URI)" msgstr "" -#: src/fs/gnunet-publish.c:742 +#: src/fs/gnunet-publish.c:748 msgid "Publish a file or directory on GNUnet" msgstr "" -#: src/fs/gnunet-search.c:111 +#: src/fs/gnunet-search.c:114 #, c-format msgid "Failed to write directory with search results to `%s'\n" msgstr "" -#: src/fs/gnunet-search.c:181 +#: src/fs/gnunet-search.c:184 #, fuzzy, c-format msgid "Error searching: %s.\n" msgstr "Fehler beim Verlassen der DHT.\n" -#: src/fs/gnunet-search.c:231 +#: src/fs/gnunet-search.c:233 #, fuzzy msgid "Could not create keyword URI from arguments.\n" msgstr "Namespace `%s' konnte nicht erstellt werden (existiert bereits?).\n" -#: src/fs/gnunet-search.c:255 +#: src/fs/gnunet-search.c:257 #, fuzzy msgid "Could not start searching.\n" msgstr "Namespace `%s' konnte nicht erstellt werden (existiert bereits?).\n" -#: src/fs/gnunet-search.c:291 +#: src/fs/gnunet-search.c:288 msgid "write search results to file starting with PREFIX" msgstr "" -#: src/fs/gnunet-search.c:294 -msgid "automatically terminate search after VALUE ms" +#: src/fs/gnunet-search.c:291 +msgid "automatically terminate search after DELAY" msgstr "" -#: src/fs/gnunet-search.c:301 +#: src/fs/gnunet-search.c:298 msgid "automatically terminate search after VALUE results are found" msgstr "" -#: src/fs/gnunet-search.c:308 +#: src/fs/gnunet-search.c:309 msgid "Search GNUnet for files that were published on GNUnet" msgstr "" -#: src/fs/gnunet-service-fs.c:240 +#: src/fs/gnunet-service-fs.c:248 msgid "# running average P2P latency (ms)" msgstr "" -#: src/fs/gnunet-service-fs.c:300 src/fs/gnunet-service-fs.c:489 +#: src/fs/gnunet-service-fs.c:309 src/fs/gnunet-service-fs.c:523 #, fuzzy msgid "# Loopback routes suppressed" msgstr "# gap Routing erfolgreich (insgesamt)" -#: src/fs/gnunet-service-fs.c:581 src/hostlist/gnunet-daemon-hostlist.c:297 -#: src/topology/gnunet-daemon-topology.c:1330 -#: src/topology/gnunet-daemon-topology.c:1337 +#: src/fs/gnunet-service-fs.c:628 src/hostlist/gnunet-daemon-hostlist.c:297 +#: src/topology/gnunet-daemon-topology.c:1322 +#: src/topology/gnunet-daemon-topology.c:1329 #, fuzzy, c-format msgid "Failed to connect to `%s' service.\n" msgstr "`%s' Dienst konnte nicht initialisiert werden.\n" -#: src/fs/gnunet-service-fs_cp.c:696 +#: src/fs/gnunet-service-fs_cp.c:711 #, fuzzy msgid "# migration stop messages received" msgstr "# verschlüsselter PING Nachrichten empfangen" -#: src/fs/gnunet-service-fs_cp.c:700 +#: src/fs/gnunet-service-fs_cp.c:715 #, c-format -msgid "Migration of content to peer `%s' blocked for %llu ms\n" +msgid "Migration of content to peer `%s' blocked for %s\n" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:735 +#: src/fs/gnunet-service-fs_cp.c:751 #, fuzzy msgid "# replies transmitted to other peers" msgstr "# Bytes des Typs %d übertragen" -#: src/fs/gnunet-service-fs_cp.c:741 +#: src/fs/gnunet-service-fs_cp.c:757 msgid "# replies dropped" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:766 src/fs/gnunet-service-fs_cp.c:1324 +#: src/fs/gnunet-service-fs_cp.c:782 src/fs/gnunet-service-fs_cp.c:1345 msgid "# P2P searches active" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:858 +#: src/fs/gnunet-service-fs_cp.c:875 msgid "# artificial delays introduced (ms)" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:911 +#: src/fs/gnunet-service-fs_cp.c:928 #, fuzzy msgid "# replies dropped due to type mismatch" msgstr "# gap Anfragen verworfen: Kollision in RT" -#: src/fs/gnunet-service-fs_cp.c:919 +#: src/fs/gnunet-service-fs_cp.c:936 #, fuzzy msgid "# replies received for other peers" msgstr "# Bytes des Typs %d empfangen" -#: src/fs/gnunet-service-fs_cp.c:933 +#: src/fs/gnunet-service-fs_cp.c:950 msgid "# replies dropped due to insufficient cover traffic" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:971 +#: src/fs/gnunet-service-fs_cp.c:988 msgid "# P2P searches destroyed due to ultimate reply" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:1038 +#: src/fs/gnunet-service-fs_cp.c:1056 #, fuzzy msgid "# requests done for free (low load)" msgstr "# gap Anfragen verworfen: Kollision in RT" -#: src/fs/gnunet-service-fs_cp.c:1062 +#: src/fs/gnunet-service-fs_cp.c:1081 msgid "# request dropped, priority insufficient" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:1072 +#: src/fs/gnunet-service-fs_cp.c:1091 #, fuzzy msgid "# requests done for a price (normal load)" msgstr "# gap Anfragen verworfen: Kollision in RT" -#: src/fs/gnunet-service-fs_cp.c:1151 +#: src/fs/gnunet-service-fs_cp.c:1170 msgid "# GET requests received (from other peers)" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:1185 +#: src/fs/gnunet-service-fs_cp.c:1204 #, fuzzy msgid "# requests dropped due to initiator not being connected" msgstr "# gap Anfragen verworfen: Kollision in RT" -#: src/fs/gnunet-service-fs_cp.c:1207 +#: src/fs/gnunet-service-fs_cp.c:1227 #, fuzzy msgid "# requests dropped due to missing reverse route" msgstr "# gap Anfragen verworfen: Kollision in RT" -#: src/fs/gnunet-service-fs_cp.c:1267 +#: src/fs/gnunet-service-fs_cp.c:1288 #, fuzzy msgid "# requests dropped due TTL underflow" msgstr "# gap Anfragen verworfen: Kollision in RT" -#: src/fs/gnunet-service-fs_cp.c:1293 +#: src/fs/gnunet-service-fs_cp.c:1314 #, fuzzy msgid "# requests dropped due to higher-TTL request" msgstr "# gap Anfragen verworfen: Kollision in RT" -#: src/fs/gnunet-service-fs_cp.c:1322 +#: src/fs/gnunet-service-fs_cp.c:1343 #, fuzzy msgid "# P2P query messages received and processed" msgstr "# verschlüsselter PING Nachrichten empfangen" -#: src/fs/gnunet-service-fs_cp.c:1687 +#: src/fs/gnunet-service-fs_cp.c:1713 #, fuzzy msgid "# migration stop messages sent" msgstr "# verschlüsselter PING Nachrichten empfangen" -#: src/fs/gnunet-service-fs_indexing.c:113 -#: src/fs/gnunet-service-fs_indexing.c:163 -#, fuzzy, c-format -msgid "Configuration option `%s' in section `%s' missing.\n" -msgstr "Konfigurationsdatei `%s' wurde erzeugt.\n" - -#: src/fs/gnunet-service-fs_indexing.c:121 -#: src/fs/gnunet-service-fs_indexing.c:177 +#: src/fs/gnunet-service-fs_indexing.c:130 +#: src/fs/gnunet-service-fs_indexing.c:181 #, fuzzy, c-format msgid "Could not open `%s'.\n" msgstr "Datei wurde als `%s' gespeichert.\n" -#: src/fs/gnunet-service-fs_indexing.c:137 +#: src/fs/gnunet-service-fs_indexing.c:142 #, fuzzy, c-format msgid "Error writing `%s'.\n" msgstr "Fehler beim Anlegen des Benutzers" -#: src/fs/gnunet-service-fs_indexing.c:228 +#: src/fs/gnunet-service-fs_indexing.c:237 #, c-format msgid "" "Index request received for file `%s' is already indexed as `%s'. Permitting " "anyway.\n" msgstr "" -#: src/fs/gnunet-service-fs_indexing.c:266 +#: src/fs/gnunet-service-fs_indexing.c:275 #, c-format msgid "Hash mismatch trying to index file `%s' which has hash `%s'\n" msgstr "" -#: src/fs/gnunet-service-fs_indexing.c:481 +#: src/fs/gnunet-service-fs_indexing.c:477 #, fuzzy, c-format msgid "Failed to delete bogus block: %s\n" msgstr "Datei wurde als `%s' gespeichert.\n" -#: src/fs/gnunet-service-fs_indexing.c:539 +#: src/fs/gnunet-service-fs_indexing.c:542 msgid "# index blocks removed: original file inaccessible" msgstr "" -#: src/fs/gnunet-service-fs_indexing.c:554 +#: src/fs/gnunet-service-fs_indexing.c:557 #, fuzzy, c-format msgid "Could not access indexed file `%s' (%s) at offset %llu: %s\n" msgstr "`%s' konnte nicht aufgelöst werden: %s\n" -#: src/fs/gnunet-service-fs_indexing.c:556 +#: src/fs/gnunet-service-fs_indexing.c:559 #, fuzzy msgid "not indexed" msgstr "Deindizierung schlug fehl." -#: src/fs/gnunet-service-fs_indexing.c:571 +#: src/fs/gnunet-service-fs_indexing.c:574 #, fuzzy, c-format msgid "Indexed file `%s' changed at offset %llu\n" msgstr "Indizierung der Daten schlug an Position %i fehl.\n" -#: src/fs/gnunet-service-fs_lc.c:202 src/fs/gnunet-service-fs_lc.c:362 -#: src/fs/gnunet-service-fs_lc.c:488 +#: src/fs/gnunet-service-fs_lc.c:202 src/fs/gnunet-service-fs_lc.c:369 #, fuzzy msgid "# client searches active" msgstr "# gap Anfragen insgesamt empfangen" @@ -2938,330 +2941,483 @@ msgstr "# gap Anfragen insgesamt empfangen" msgid "# replies received for local clients" msgstr "# gap Anfragen insgesamt empfangen" -#: src/fs/gnunet-service-fs_lc.c:321 +#: src/fs/gnunet-service-fs_lc.c:328 #, fuzzy msgid "# client searches received" msgstr "# gap Anfragen insgesamt empfangen" -#: src/fs/gnunet-service-fs_lc.c:356 +#: src/fs/gnunet-service-fs_lc.c:363 msgid "# client searches updated (merged content seen list)" msgstr "" -#: src/fs/gnunet-service-fs_pe.c:265 +#: src/fs/gnunet-service-fs_pe.c:269 msgid "# average retransmission delay (ms)" msgstr "" -#: src/fs/gnunet-service-fs_pe.c:391 +#: src/fs/gnunet-service-fs_pe.c:400 #, fuzzy msgid "# transmission failed (core has no bandwidth)" msgstr "Kein Transport des Typs %d bekannt.\n" -#: src/fs/gnunet-service-fs_pe.c:420 +#: src/fs/gnunet-service-fs_pe.c:433 #, fuzzy msgid "# query messages sent to other peers" msgstr "# Bytes ausgehender Nachrichten verworfen" -#: src/fs/gnunet-service-fs_pe.c:469 +#: src/fs/gnunet-service-fs_pe.c:482 msgid "# delay heap timeout" msgstr "" -#: src/fs/gnunet-service-fs_pe.c:476 +#: src/fs/gnunet-service-fs_pe.c:490 #, fuzzy msgid "# query plans executed" msgstr "# dht Anfragen weitergeleitet" -#: src/fs/gnunet-service-fs_pe.c:538 +#: src/fs/gnunet-service-fs_pe.c:550 #, fuzzy msgid "# requests merged" msgstr "# Client Trace-Anfragen empfangen" -#: src/fs/gnunet-service-fs_pe.c:544 +#: src/fs/gnunet-service-fs_pe.c:558 #, fuzzy msgid "# requests refreshed" msgstr "# Client Trace-Anfragen empfangen" -#: src/fs/gnunet-service-fs_pe.c:597 src/fs/gnunet-service-fs_pe.c:681 -#: src/fs/gnunet-service-fs_pe.c:748 +#: src/fs/gnunet-service-fs_pe.c:612 src/fs/gnunet-service-fs_pe.c:696 +#: src/fs/gnunet-service-fs_pe.c:767 msgid "# query plan entries" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:285 +#: src/fs/gnunet-service-fs_pr.c:312 #, fuzzy msgid "# Pending requests created" msgstr "# Client Trace-Anfragen empfangen" -#: src/fs/gnunet-service-fs_pr.c:367 src/fs/gnunet-service-fs_pr.c:616 +#: src/fs/gnunet-service-fs_pr.c:404 src/fs/gnunet-service-fs_pr.c:667 #, fuzzy msgid "# Pending requests active" msgstr "# Client Trace-Anfragen empfangen" -#: src/fs/gnunet-service-fs_pr.c:779 +#: src/fs/gnunet-service-fs_pr.c:835 #, fuzzy msgid "# replies received and matched" msgstr "# Bytes empfangen über TCP" -#: src/fs/gnunet-service-fs_pr.c:808 +#: src/fs/gnunet-service-fs_pr.c:868 msgid "# duplicate replies discarded (bloomfilter)" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:822 +#: src/fs/gnunet-service-fs_pr.c:877 +msgid "# irrelevant replies discarded" +msgstr "" + +#: src/fs/gnunet-service-fs_pr.c:891 #, c-format msgid "Unsupported block type %u\n" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:835 +#: src/fs/gnunet-service-fs_pr.c:904 msgid "# results found locally" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:953 +#: src/fs/gnunet-service-fs_pr.c:1025 msgid "# Datastore `PUT' failures" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:980 +#: src/fs/gnunet-service-fs_pr.c:1052 #, fuzzy msgid "# storage requests dropped due to high load" msgstr "# gap Anfragen verworfen: Kollision in RT" -#: src/fs/gnunet-service-fs_pr.c:1015 +#: src/fs/gnunet-service-fs_pr.c:1087 #, fuzzy msgid "# Replies received from DHT" msgstr "# Bytes empfangen über HTTP" -#: src/fs/gnunet-service-fs_pr.c:1106 +#: src/fs/gnunet-service-fs_pr.c:1221 +#, fuzzy +msgid "# Replies received from STREAM" +msgstr "# Bytes empfangen über HTTP" + +#: src/fs/gnunet-service-fs_pr.c:1273 #, c-format -msgid "Datastore lookup already took %llu ms!\n" +msgid "Datastore lookup already took %s!\n" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1127 +#: src/fs/gnunet-service-fs_pr.c:1293 #, c-format -msgid "On-demand lookup already took %llu ms!\n" +msgid "On-demand lookup already took %s!\n" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1174 +#: src/fs/gnunet-service-fs_pr.c:1340 msgid "# Datastore lookups concluded (no results)" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1188 +#: src/fs/gnunet-service-fs_pr.c:1355 msgid "# Datastore lookups concluded (seen all)" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1197 +#: src/fs/gnunet-service-fs_pr.c:1364 msgid "# Datastore lookups aborted (more than MAX_RESULTS)" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1211 +#: src/fs/gnunet-service-fs_pr.c:1379 msgid "# requested DBLOCK or IBLOCK not found" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1224 +#: src/fs/gnunet-service-fs_pr.c:1393 msgid "# on-demand blocks matched requests" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1237 +#: src/fs/gnunet-service-fs_pr.c:1406 msgid "# on-demand lookups performed successfully" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1242 +#: src/fs/gnunet-service-fs_pr.c:1411 msgid "# on-demand lookups failed" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1269 src/fs/gnunet-service-fs_pr.c:1309 -#: src/fs/gnunet-service-fs_pr.c:1447 +#: src/fs/gnunet-service-fs_pr.c:1438 src/fs/gnunet-service-fs_pr.c:1478 +#: src/fs/gnunet-service-fs_pr.c:1619 msgid "# Datastore lookups concluded (error queueing)" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1327 +#: src/fs/gnunet-service-fs_pr.c:1496 msgid "# Datastore lookups concluded (found last result)" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1338 +#: src/fs/gnunet-service-fs_pr.c:1507 msgid "# Datastore lookups concluded (load too high)" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1424 +#: src/fs/gnunet-service-fs_pr.c:1595 msgid "# Datastore lookups initiated" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1508 +#: src/fs/gnunet-service-fs_pr.c:1680 #, fuzzy msgid "# GAP PUT messages received" msgstr "# verschlüsselter PONG Nachrichten empfangen" -#: src/fs/gnunet-service-fs_pr.c:1601 src/fs/gnunet-service-fs_pr.c:1610 -#, fuzzy, c-format -msgid "Configuration fails to specify `%s', assuming default value." -msgstr "Konfigurationsdatei `%s' wurde erzeugt.\n" - #: src/fs/gnunet-service-fs_push.c:629 -#, c-format -msgid "" -"Invalid value specified for option `%s' in section `%s', content pushing " -"disabled\n" +msgid "time required, content pushing disabled" +msgstr "" + +#: src/fs/gnunet-service-fs_stream.c:777 +#, fuzzy +msgid "# replies received via stream" +msgstr "# Bytes empfangen über TCP" + +#: src/fs/gnunet-service-fs_stream.c:791 +#, fuzzy +msgid "# replies received via stream dropped" +msgstr "# Bytes empfangen über TCP" + +#: src/fs/gnunet-service-fs_stream.c:930 +#: src/fs/gnunet-service-fs_stream.c:1384 +#, fuzzy +msgid "# stream connections active" +msgstr "# verbundener Knoten" + +#: src/fs/gnunet-service-fs_stream.c:1166 +msgid "# Blocks transferred via stream" msgstr "" +#: src/fs/gnunet-service-fs_stream.c:1326 +#, fuzzy +msgid "# queries received via stream" +msgstr "# Bytes empfangen über TCP" + +#: src/fs/gnunet-service-fs_stream.c:1376 +#, fuzzy +msgid "# stream client connections rejected" +msgstr "GNUnet Konfiguration" + #: src/fs/gnunet-unindex.c:89 #, c-format msgid "Unindexing at %llu/%llu (%s remaining)\n" msgstr "" -#: src/fs/gnunet-unindex.c:96 +#: src/fs/gnunet-unindex.c:95 #, fuzzy, c-format msgid "Error unindexing: %s.\n" msgstr "" "\n" "Fehler beim Deindizieren der Datei: %s\n" -#: src/fs/gnunet-unindex.c:101 +#: src/fs/gnunet-unindex.c:100 #, fuzzy msgid "Unindexing done.\n" msgstr "Dateien deindizieren." -#: src/fs/gnunet-unindex.c:131 +#: src/fs/gnunet-unindex.c:130 #, fuzzy, c-format msgid "You must specify one and only one filename for unindexing.\n" msgstr "Sie dürfen nur eine Datei zum Deindizieren angeben.\n" -#: src/fs/gnunet-unindex.c:148 +#: src/fs/gnunet-unindex.c:147 #, fuzzy msgid "Could not start unindex operation.\n" msgstr "Auf die Namespace Informationen konnte nicht zugegriffen werden.\n" -#: src/fs/gnunet-unindex.c:176 +#: src/fs/gnunet-unindex.c:179 msgid "Unindex a file that was previously indexed with gnunet-publish." msgstr "" -#: src/fs/plugin_block_fs.c:131 -msgid "Reply mismatched in terms of namespace. Discarded.\n" -msgstr "" +#: src/gns/gns_api.c:598 +#, fuzzy +msgid "Failed to serialize lookup reply from GNS service!\n" +msgstr "Fehler beim Empfangen der Antwort von gnunetd auf die `%s' Nachricht\n" -#: src/gns/gnunet-gns.c:191 +#: src/gns/gnunet-dns2gns.c:192 #, fuzzy +msgid "Failed to pack DNS response into UDP packet!\n" +msgstr "Fehler beim Senden einer `%s' Anfrage an den SMTP Server.\n" + +#: src/gns/gnunet-dns2gns.c:367 +#, fuzzy, c-format +msgid "Cannot parse DNS request from %s\n" +msgstr "Fehler beim Senden einer `%s' Anfrage an den SMTP Server.\n" + +#: src/gns/gnunet-dns2gns.c:383 +#, fuzzy, c-format +msgid "Received malformed DNS request from %s\n" +msgstr "GAP hat ungültige Inhalte von `%s' empfangen.\n" + +#: src/gns/gnunet-dns2gns.c:391 +#, fuzzy, c-format +msgid "Received unsupported DNS request from %s\n" +msgstr "GAP hat ungültige Inhalte von `%s' empfangen.\n" + +#: src/gns/gnunet-dns2gns.c:679 +msgid "IP of recursive DNS resolver to use (required)" +msgstr "" + +#: src/gns/gnunet-dns2gns.c:682 +msgid "Authoritative DNS suffix to use (optional); default: zkey.eu" +msgstr "" + +#: src/gns/gnunet-dns2gns.c:685 +msgid "Authoritative FCFS suffix to use (optional); default: fcfs.zkey.eu" +msgstr "" + +#: src/gns/gnunet-dns2gns.c:688 +msgid "UDP port to listen on for inbound DNS requests; default: 53" +msgstr "" + +#: src/gns/gnunet-dns2gns.c:701 +msgid "GNUnet DNS-to-GNS proxy (a DNS server)" +msgstr "" + +#: src/gns/gnunet-gns.c:221 +#, fuzzy, c-format msgid "Failed to connect to GNS\n" msgstr "Es konnte keine Verbindung mit gnunetd hergestellt werden.\n" -#: src/gns/gnunet-gns.c:232 -msgid "try to shorten a given GNS name" +#: src/gns/gnunet-gns.c:335 +#, c-format +msgid "Please specify lookup, shorten or authority operation!\n" msgstr "" -#: src/gns/gnunet-gns.c:235 -msgid "Lookup a record using GNS (NOT IMPLEMENTED)" +#: src/gns/gnunet-gns.c:356 +#, fuzzy +msgid "try to shorten a given name" +msgstr "Es konnte keine Verbindung mit gnunetd hergestellt werden.\n" + +#: src/gns/gnunet-gns.c:359 +msgid "Lookup a record for the given name" msgstr "" -#: src/gns/gnunet-gns.c:238 +#: src/gns/gnunet-gns.c:362 msgid "Get the authority of a particular name" msgstr "" -#: src/gns/gnunet-gns.c:241 +#: src/gns/gnunet-gns.c:365 #, fuzzy -msgid "Specify the type of the record lookup" +msgid "Specify the type of the record to lookup" msgstr "Die Priorität des Inhalts angeben" -#: src/gns/gnunet-gns.c:244 +#: src/gns/gnunet-gns.c:368 msgid "No unneeded output" msgstr "" -#: src/gns/gnunet-gns.c:255 +#: src/gns/gnunet-gns.c:381 msgid "GNUnet GNS access tool" msgstr "" -#: src/gns/gnunet-gns-fcfsd.c:280 +#: src/gns/gnunet-gns-fcfsd.c:451 #, fuzzy, c-format msgid "Unsupported form value `%s'\n" msgstr "Kommando `%s' wird nicht unterstützt. Vorgang wird abgebrochen.\n" -#: src/gns/gnunet-gns-fcfsd.c:333 +#: src/gns/gnunet-gns-fcfsd.c:480 #, fuzzy, c-format msgid "Failed to create record for domain `%s': %s\n" msgstr "Konfigurationsdatei `%s' konnte nicht geparst werden.\n" -#: src/gns/gnunet-gns-fcfsd.c:377 +#: src/gns/gnunet-gns-fcfsd.c:524 #, c-format msgid "Found existing name `%s' for the given key\n" msgstr "" -#: src/gns/gnunet-gns-fcfsd.c:439 +#: src/gns/gnunet-gns-fcfsd.c:586 #, c-format msgid "Found %u existing records for domain `%s'\n" msgstr "" -#: src/gns/gnunet-gns-fcfsd.c:498 +#: src/gns/gnunet-gns-fcfsd.c:648 #, fuzzy, c-format msgid "Failed to create page for `%s'\n" msgstr "Namespace `%s' konnte nicht erstellt werden (existiert bereits?).\n" -#: src/gns/gnunet-gns-fcfsd.c:514 +#: src/gns/gnunet-gns-fcfsd.c:664 #, fuzzy, c-format msgid "Failed to setup post processor for `%s'\n" msgstr "Fehler beim Aktualisieren der Daten des Moduls `%s'\n" -#: src/gns/gnunet-gns-fcfsd.c:725 src/gns/gnunet-gns-fcfsd.c:737 -#, fuzzy, c-format -msgid "Option `%s' not specified in configuration section `%s'\n" +#: src/gns/gnunet-gns-fcfsd.c:700 +msgid "Domain name must not contain `.'\n" +msgstr "" + +#: src/gns/gnunet-gns-fcfsd.c:708 +msgid "Domain name must not contain `+'\n" msgstr "" -"Option `%s' ist in der Konfigurationsdatei in der Sektion `%s' nicht " -"gesetzt, sie wird auf %dm gesetzt.\n" -#: src/gns/gnunet-gns-fcfsd.c:747 src/namestore/gnunet-namestore.c:299 +#: src/gns/gnunet-gns-fcfsd.c:912 src/namestore/gnunet-namestore.c:364 #, fuzzy msgid "Failed to read or create private zone key\n" msgstr "Fehler beim Aktualisieren der Daten des Moduls `%s'\n" -#: src/gns/gnunet-gns-fcfsd.c:757 src/namestore/gnunet-namestore.c:310 +#: src/gns/gnunet-gns-fcfsd.c:922 src/namestore/gnunet-namestore.c:375 #, fuzzy msgid "Failed to connect to namestore\n" msgstr "Es konnte keine Verbindung mit gnunetd hergestellt werden." -#: src/gns/gnunet-gns-fcfsd.c:773 src/gns/gnunet-gns-proxy.c:525 +#: src/gns/gnunet-gns-fcfsd.c:938 src/gns/gnunet-gns-proxy.c:2857 #, fuzzy msgid "Failed to start HTTP server\n" msgstr "Fehler beim Starten der Collection.\n" -#: src/gns/gnunet-gns-fcfsd.c:804 +#: src/gns/gnunet-gns-fcfsd.c:972 msgid "GNUnet GNS first come first serve registration service" msgstr "" -#: src/gns/gnunet-gns-proxy.c:800 -msgid "listen on specified port" +#: src/gns/gnunet-gns-proxy.c:2494 +#, fuzzy, c-format +msgid "Unable to import private key from file `%s'\n" +msgstr "Fehler beim Anlegen des Benutzerkontos:" + +#: src/gns/gnunet-gns-proxy.c:2522 +#, fuzzy, c-format +msgid "Unable to import certificate %s\n" +msgstr "Fehler beim Speichern der Konfigurationsdatei `%s':" + +#: src/gns/gnunet-gns-proxy.c:3510 +msgid "listen on specified port (default: 7777)" +msgstr "" + +#: src/gns/gnunet-gns-proxy.c:3513 +msgid "pem file to use as CA" msgstr "" -#: src/gns/gnunet-gns-proxy.c:811 +#: src/gns/gnunet-gns-proxy.c:3525 msgid "GNUnet GNS proxy" msgstr "" -#: src/hello/gnunet-hello.c:122 +#: src/gns/gnunet-service-gns.c:486 +#, c-format +msgid "Records for name `%s' in zone %s too large to fit into DHT" +msgstr "" + +#: src/gns/gnunet-service-gns.c:1216 +#, fuzzy +msgid "Failed to connect to the namestore!\n" +msgstr "Es konnte keine Verbindung mit gnunetd hergestellt werden." + +#: src/gns/gnunet-service-gns.c:1277 +#, fuzzy +msgid "Could not connect to DHT!\n" +msgstr "Verbindung zu gnunetd konnte nicht hergestellt werden.\n" + +#: src/gns/gnunet-service-gns.c:1288 +#, fuzzy +msgid "Unable to initialize resolver!\n" +msgstr "SQLite Datenbank konnte nicht initialisiert werden: %s.\n" + +#: src/gns/gnunet-service-gns_resolver.c:3439 +#, c-format +msgid "Not a GADS TLD: `%s'\n" +msgstr "" + +#: src/hello/gnunet-hello.c:118 msgid "Call with name of HELLO file to modify.\n" msgstr "" -#: src/hello/gnunet-hello.c:128 +#: src/hello/gnunet-hello.c:124 #, fuzzy, c-format msgid "Error accessing file `%s': %s\n" msgstr "Fehler beim Anlegen des Benutzers" -#: src/hello/gnunet-hello.c:136 +#: src/hello/gnunet-hello.c:132 #, c-format msgid "File `%s' is too big to be a HELLO\n" msgstr "" -#: src/hello/gnunet-hello.c:143 +#: src/hello/gnunet-hello.c:139 #, c-format msgid "File `%s' is too small to be a HELLO\n" msgstr "" -#: src/hello/gnunet-hello.c:153 src/hello/gnunet-hello.c:181 +#: src/hello/gnunet-hello.c:149 src/hello/gnunet-hello.c:177 #, fuzzy, c-format msgid "Error opening file `%s': %s\n" msgstr "Fehler beim Anlegen des Benutzers" -#: src/hello/gnunet-hello.c:169 +#: src/hello/gnunet-hello.c:165 #, fuzzy, c-format msgid "Did not find well-formed HELLO in file `%s'\n" msgstr "Fehler beim Lesen der Freunde-Liste von `%s'\n" -#: src/hello/gnunet-hello.c:193 +#: src/hello/gnunet-hello.c:189 #, fuzzy, c-format msgid "Error writing HELLO to file `%s': %s\n" msgstr "Fehler beim Anlegen des Benutzers" +#: src/hello/hello.c:904 +#, fuzzy +msgid "Failed to parse HELLO message: missing expiration time\n" +msgstr "Fehler beim Speichern der Konfiguration!" + +#: src/hello/hello.c:913 +#, fuzzy +msgid "Failed to parse HELLO message: invalid expiration time\n" +msgstr "Fehler beim Speichern der Konfiguration!" + +#: src/hello/hello.c:923 +#, fuzzy +msgid "Failed to parse HELLO message: malformed\n" +msgstr "Fehler beim Lesen der Freunde-Liste von `%s'\n" + +#: src/hello/hello.c:933 +#, fuzzy +msgid "Failed to parse HELLO message: missing transport plugin\n" +msgstr "Anwendung `%s' konnte nicht initialisiert werden.\n" + +#: src/hello/hello.c:950 +#, c-format +msgid "Plugin `%s' not found\n" +msgstr "" + +#: src/hello/hello.c:959 +#, c-format +msgid "Plugin `%s' does not support URIs yet\n" +msgstr "" + +#: src/hello/hello.c:978 +#, fuzzy, c-format +msgid "Failed to parse `%s' as an address for plugin `%s'\n" +msgstr "Fehler beim Binden an UDP Port %d.\n" + #: src/hostlist/gnunet-daemon-hostlist.c:264 msgid "" "None of the functions for the hostlist daemon were enabled. I have no " @@ -3286,7 +3442,7 @@ msgstr "" msgid "provide a hostlist server" msgstr "" -#: src/hostlist/gnunet-daemon-hostlist.c:341 +#: src/hostlist/gnunet-daemon-hostlist.c:344 msgid "GNUnet hostlist server and client" msgstr "" @@ -3309,178 +3465,142 @@ msgstr "Ungültige `%s' Nachricht von Knoten `%s' empfangen.\n" msgid "# valid HELLOs downloaded from hostlist servers" msgstr "# Hellos per HTTP heruntergeladen" -#: src/hostlist/hostlist-client.c:375 src/hostlist/hostlist-client.c:396 -#, c-format -msgid "No `%s' specified in `%s' configuration, will not bootstrap.\n" -msgstr "" - -#: src/hostlist/hostlist-client.c:473 src/hostlist/hostlist-client.c:683 -#: src/hostlist/hostlist-client.c:689 src/hostlist/hostlist-client.c:741 -#: src/hostlist/hostlist-client.c:750 src/hostlist/hostlist-client.c:871 -#: src/hostlist/hostlist-client.c:961 src/hostlist/hostlist-client.c:966 -#: src/transport/plugin_transport_http_client.c:110 -#: src/transport/plugin_transport_http_client.c:125 +#: src/hostlist/hostlist-client.c:469 src/hostlist/hostlist-client.c:680 +#: src/hostlist/hostlist-client.c:686 src/hostlist/hostlist-client.c:738 +#: src/hostlist/hostlist-client.c:747 src/hostlist/hostlist-client.c:868 +#: src/hostlist/hostlist-client.c:958 src/hostlist/hostlist-client.c:963 +#: src/transport/plugin_transport_http_client.c:1052 +#: src/transport/plugin_transport_http_client.c:1067 #, c-format msgid "%s failed at %s:%d: `%s'\n" msgstr "`%s' schlug fehl bei %s:%d mit dem Fehler: `%s'.\n" -#: src/hostlist/hostlist-client.c:593 src/hostlist/hostlist-client.c:1331 +#: src/hostlist/hostlist-client.c:589 src/hostlist/hostlist-client.c:1325 msgid "# advertised hostlist URIs" msgstr "" -#: src/hostlist/hostlist-client.c:623 +#: src/hostlist/hostlist-client.c:619 #, c-format msgid "# advertised URI `%s' downloaded" msgstr "" -#: src/hostlist/hostlist-client.c:664 +#: src/hostlist/hostlist-client.c:661 #, c-format msgid "" "Advertised hostlist with URI `%s' could not be downloaded. Advertised URI " "gets dismissed.\n" msgstr "" -#: src/hostlist/hostlist-client.c:802 +#: src/hostlist/hostlist-client.c:799 #, fuzzy, c-format msgid "Timeout trying to download hostlist from `%s'\n" msgstr "Fehler beim Lesen der Freunde-Liste von `%s'\n" -#: src/hostlist/hostlist-client.c:816 +#: src/hostlist/hostlist-client.c:813 #, c-format msgid "Download limit of %u bytes exceeded, stopping download\n" msgstr "" -#: src/hostlist/hostlist-client.c:836 +#: src/hostlist/hostlist-client.c:833 #, fuzzy, c-format msgid "Download of hostlist from `%s' failed: `%s'\n" msgstr "" "Upload von `%s' komplett, derzeitige durchschnittliche Geschwindigkeit " "beträgt %8.3f KB/s.\n" -#: src/hostlist/hostlist-client.c:842 +#: src/hostlist/hostlist-client.c:839 #, fuzzy, c-format msgid "Download of hostlist `%s' completed.\n" msgstr "" "Upload von `%s' komplett, derzeitige durchschnittliche Geschwindigkeit " "beträgt %8.3f KB/s.\n" -#: src/hostlist/hostlist-client.c:850 +#: src/hostlist/hostlist-client.c:847 #, c-format msgid "Adding successfully tested hostlist `%s' datastore.\n" msgstr "" -#: src/hostlist/hostlist-client.c:903 +#: src/hostlist/hostlist-client.c:900 #, c-format msgid "Bootstrapping using hostlist at `%s'.\n" msgstr "" -#: src/hostlist/hostlist-client.c:911 +#: src/hostlist/hostlist-client.c:908 msgid "# hostlist downloads initiated" msgstr "" -#: src/hostlist/hostlist-client.c:1037 src/hostlist/hostlist-client.c:1505 +#: src/hostlist/hostlist-client.c:1035 src/hostlist/hostlist-client.c:1498 msgid "# milliseconds between hostlist downloads" msgstr "" -#: src/hostlist/hostlist-client.c:1046 +#: src/hostlist/hostlist-client.c:1043 #, c-format -msgid "Have %u/%u connections. Will consider downloading hostlist in %llums\n" -msgstr "" - -#: src/hostlist/hostlist-client.c:1084 -msgid "Scheduled saving of hostlists\n" +msgid "Have %u/%u connections. Will consider downloading hostlist in %s\n" msgstr "" -#: src/hostlist/hostlist-client.c:1088 -#, c-format -msgid "Hostlists will be saved to file again in %llums\n" -msgstr "" - -#: src/hostlist/hostlist-client.c:1111 src/hostlist/hostlist-client.c:1127 +#: src/hostlist/hostlist-client.c:1107 src/hostlist/hostlist-client.c:1123 #, fuzzy msgid "# active connections" msgstr "GNUnet Konfiguration" -#: src/hostlist/hostlist-client.c:1242 -#, c-format -msgid "Initial time between hostlist downloads is %llums\n" -msgstr "" - #: src/hostlist/hostlist-client.c:1273 -#, c-format -msgid "" -"No `%s' specified in `%s' configuration, cannot load hostlists from file.\n" -msgstr "" - -#: src/hostlist/hostlist-client.c:1279 #, fuzzy, c-format msgid "Loading saved hostlist entries from file `%s' \n" msgstr "Fehler beim Lesen der Freunde-Liste von `%s'\n" -#: src/hostlist/hostlist-client.c:1283 -#, c-format -msgid "Hostlist file `%s' is not existing\n" -msgstr "" +#: src/hostlist/hostlist-client.c:1277 +#, fuzzy, c-format +msgid "Hostlist file `%s' does not exist\n" +msgstr "Sitzungsschlüssel von Knoten `%s' konnte nicht überprüft werden.\n" -#: src/hostlist/hostlist-client.c:1294 +#: src/hostlist/hostlist-client.c:1288 #, fuzzy, c-format msgid "Could not open file `%s' for reading to load hostlists: %s\n" msgstr "Datei wurde als `%s' gespeichert.\n" -#: src/hostlist/hostlist-client.c:1327 +#: src/hostlist/hostlist-client.c:1321 #, c-format msgid "%u hostlist URIs loaded from file\n" msgstr "" -#: src/hostlist/hostlist-client.c:1329 +#: src/hostlist/hostlist-client.c:1323 msgid "# hostlist URIs read from file" msgstr "" -#: src/hostlist/hostlist-client.c:1362 -#, c-format -msgid "" -"No `%s' specified in `%s' configuration, cannot save hostlists to file.\n" -msgstr "" - -#: src/hostlist/hostlist-client.c:1376 +#: src/hostlist/hostlist-client.c:1368 #, fuzzy, c-format msgid "Could not open file `%s' for writing to save hostlists: %s\n" msgstr "Datei wurde als `%s' gespeichert.\n" -#: src/hostlist/hostlist-client.c:1381 +#: src/hostlist/hostlist-client.c:1373 #, fuzzy, c-format msgid "Writing %u hostlist URIs to `%s'\n" msgstr "Fehler beim Lesen der Freunde-Liste von `%s'\n" -#: src/hostlist/hostlist-client.c:1405 src/hostlist/hostlist-client.c:1422 +#: src/hostlist/hostlist-client.c:1397 src/hostlist/hostlist-client.c:1414 #, c-format msgid "Error writing hostlist URIs to file `%s'\n" msgstr "" -#: src/hostlist/hostlist-client.c:1417 +#: src/hostlist/hostlist-client.c:1409 msgid "# hostlist URIs written to file" msgstr "" -#: src/hostlist/hostlist-client.c:1470 +#: src/hostlist/hostlist-client.c:1463 msgid "Learning is enabled on this peer\n" msgstr "" -#: src/hostlist/hostlist-client.c:1473 -#, c-format -msgid "Hostlists will be saved to file again in %llums\n" -msgstr "" - -#: src/hostlist/hostlist-client.c:1482 +#: src/hostlist/hostlist-client.c:1475 msgid "Learning is not enabled on this peer\n" msgstr "" -#: src/hostlist/hostlist-client.c:1494 +#: src/hostlist/hostlist-client.c:1487 #, c-format msgid "" "Since learning is not enabled on this peer, hostlist file `%s' was removed\n" msgstr "" -#: src/hostlist/hostlist-client.c:1498 +#: src/hostlist/hostlist-client.c:1491 #, fuzzy, c-format msgid "Hostlist file `%s' could not be removed\n" msgstr "Sitzungsschlüssel von Knoten `%s' konnte nicht überprüft werden.\n" @@ -3495,9 +3615,9 @@ msgid "expired addresses encountered" msgstr "" #: src/hostlist/hostlist-server.c:184 src/hostlist/hostlist-server.c:425 -#: src/peerinfo-tool/gnunet-peerinfo.c:403 -#: src/peerinfo-tool/gnunet-peerinfo.c:519 -#: src/topology/gnunet-daemon-topology.c:927 +#: src/peerinfo-tool/gnunet-peerinfo.c:331 +#: src/peerinfo-tool/gnunet-peerinfo.c:386 +#: src/topology/gnunet-daemon-topology.c:922 #, fuzzy, c-format msgid "Error in communication with PEERINFO service: %s\n" msgstr "Informationen über andere GNUnet Knoten ausgeben." @@ -3520,10 +3640,6 @@ msgstr "Fehler beim Senden einer `%s' Anfrage an den SMTP Server.\n" msgid "hostlist requests refused (not HTTP GET)" msgstr "# Client Trace-Anfragen empfangen" -#: src/hostlist/hostlist-server.c:273 -msgid "Sending 100 CONTINUE reply\n" -msgstr "" - #: src/hostlist/hostlist-server.c:279 #, c-format msgid "Refusing `%s' request with %llu bytes of upload data\n" @@ -3561,65 +3677,103 @@ msgstr "# Bekanntmachungen von anderen übertragen" msgid "Advertisement message could not be queued by core\n" msgstr "" -#: src/hostlist/hostlist-server.c:561 +#: src/hostlist/hostlist-server.c:562 #, fuzzy, c-format msgid "Invalid port number %llu. Exiting.\n" msgstr "Ungültige Parameter. Abbruch.\n" -#: src/hostlist/hostlist-server.c:570 +#: src/hostlist/hostlist-server.c:571 #, c-format msgid "Hostlist service starts on %s:%llu\n" msgstr "" -#: src/hostlist/hostlist-server.c:584 +#: src/hostlist/hostlist-server.c:585 #, fuzzy, c-format msgid "Address to obtain hostlist: `%s'\n" msgstr "Fehler beim Lesen der Freunde-Liste von `%s'\n" -#: src/hostlist/hostlist-server.c:624 +#: src/hostlist/hostlist-server.c:625 #, fuzzy, c-format msgid "`%s' is not a valid IP address! Ignoring BINDTOIP.\n" msgstr "`%s' ist nicht verfügbar." -#: src/hostlist/hostlist-server.c:666 +#: src/hostlist/hostlist-server.c:667 #, fuzzy, c-format msgid "Could not start hostlist HTTP server on port %u\n" msgstr "Der Transportdienst auf Port %d konnte nicht gestartet werden.\n" -#: src/integration-tests/connection_watchdog.c:997 +#: src/integration-tests/connection_watchdog.c:1001 #, fuzzy, c-format msgid "Transport plugin: `%s' port %llu\n" msgstr "Der Transportdienst auf Port %d konnte nicht gestartet werden.\n" -#: src/integration-tests/connection_watchdog.c:1030 +#: src/integration-tests/connection_watchdog.c:1034 #, fuzzy, c-format msgid "Found %u transport plugins: `%s'\n" msgstr "Teste Transport(e) %s\n" -#: src/integration-tests/connection_watchdog.c:1089 +#: src/integration-tests/connection_watchdog.c:1093 msgid "Send ping messages to test connectivity (default == NO)" msgstr "" -#: src/integration-tests/connection_watchdog.c:1095 -#: src/template/gnunet-template.c:68 +#: src/integration-tests/connection_watchdog.c:1102 +#: src/template/gnunet-template.c:70 #, fuzzy msgid "help text" msgstr "Hilfetext für -t" -#: src/mesh/gnunet-service-mesh.c:4590 -msgid "Wrong CORE service\n" -msgstr "" +#: src/mesh/gnunet-mesh.c:211 +#, fuzzy +msgid "provide information about all tunnels (continuously) NOT IMPLEMENTED" +msgstr "Informationen über andere GNUnet Knoten ausgeben." -#: src/mesh/gnunet-service-mesh.c:4784 +#: src/mesh/gnunet-mesh.c:214 #, fuzzy -msgid "Mesh service is lacking key configuration settings. Exiting.\n" -msgstr "GNUnet Konfiguration" +msgid "provide information about a particular tunnel" +msgstr "Informationen über andere GNUnet Knoten ausgeben." -#: src/mesh/gnunet-service-mesh.c:4793 +#: src/mesh/gnunet-mesh.c:224 #, fuzzy -msgid "Mesh service could not access hostkey. Exiting.\n" +msgid "Print information about mesh tunnels and peers." +msgstr "Informationen über andere GNUnet Knoten ausgeben." + +#: src/mesh/gnunet-service-mesh.c:8015 src/mesh/gnunet-service-mesh-new.c:8015 +msgid "Wrong CORE service\n" +msgstr "" + +#: src/mesh/gnunet-service-mesh.c:8232 src/mesh/gnunet-service-mesh-new.c:8232 +#, fuzzy, c-format +msgid "Mesh service could not access hostkey: %s. Exiting.\n" msgstr "Auf die Namespace Informationen konnte nicht zugegriffen werden.\n" +#: src/mesh/gnunet-service-mesh.c:8314 src/mesh/gnunet-service-mesh.c:8326 +#: src/mesh/gnunet-service-mesh.c:8338 src/mesh/gnunet-service-mesh.c:8352 +#: src/mesh/gnunet-service-mesh.c:8364 src/mesh/gnunet-service-mesh.c:8376 +#: src/mesh/gnunet-service-mesh.c:8388 src/mesh/gnunet-service-mesh-new.c:8321 +#: src/mesh/gnunet-service-mesh-new.c:8333 +#: src/mesh/gnunet-service-mesh-new.c:8345 +#: src/mesh/gnunet-service-mesh-new.c:8359 +#: src/mesh/gnunet-service-mesh-new.c:8371 +#: src/mesh/gnunet-service-mesh-new.c:8383 +#: src/mesh/gnunet-service-mesh-new.c:8395 +#: src/regex/gnunet-daemon-regexprofiler.c:335 +#: src/regex/gnunet-daemon-regexprofiler.c:347 +#: src/regex/gnunet-daemon-regexprofiler.c:360 +#: src/regex/gnunet-daemon-regexprofiler.c:373 +#: src/regex/gnunet-regex-simulation-profiler.c:659 +#, fuzzy, c-format +msgid "%s service is lacking key configuration settings (%s). Exiting.\n" +msgstr "GNUnet Konfiguration" + +#: src/mesh/gnunet-service-mesh.c:8400 src/mesh/gnunet-service-mesh.c:8410 +#: src/mesh/gnunet-service-mesh.c:8421 src/mesh/gnunet-service-mesh-new.c:8407 +#: src/mesh/gnunet-service-mesh-new.c:8417 +#: src/mesh/gnunet-service-mesh-new.c:8428 +#, fuzzy, c-format +msgid "" +"%s service is lacking key configuration settings (%s). Using default (%u).\n" +msgstr "GNUnet Konfiguration" + #: src/mysql/mysql.c:174 #, c-format msgid "Trying to use file `%s' for MySQL configuration.\n" @@ -3630,201 +3784,330 @@ msgstr "Versuche, Datei `%s' für MySQL Konfiguration zu verwenden.\n" msgid "Could not access file `%s': %s\n" msgstr "`%s' konnte nicht aufgelöst werden: %s\n" -#: src/namestore/gnunet-namestore.c:157 +#: src/namestore/gnunet-namestore.c:212 #, fuzzy, c-format msgid "Adding record failed: %s\n" msgstr "" "\n" "Fehler beim Uploaden der Datei: %s\n" -#: src/namestore/gnunet-namestore.c:183 +#: src/namestore/gnunet-namestore.c:243 #, fuzzy, c-format msgid "Deleting record failed: %s\n" msgstr "" "\n" "Fehler beim Uploaden der Datei: %s\n" -#: src/namestore/gnunet-namestore.c:239 +#: src/namestore/gnunet-namestore.c:304 #, c-format msgid "\tCorrupt or unsupported record of type %u\n" msgstr "" -#: src/namestore/gnunet-namestore.c:276 -#, c-format -msgid "Option `%s' not given, but I need a zone key file!\n" +#: src/namestore/gnunet-namestore.c:320 +msgid "for at least" msgstr "" -#: src/namestore/gnunet-namestore.c:281 -#, fuzzy, c-format -msgid "Using default zone file `%s'\n" -msgstr "Collection `%s' begonnen.\n" +#: src/namestore/gnunet-namestore.c:321 +msgid "until" +msgstr "" -#: src/namestore/gnunet-namestore.c:291 +#: src/namestore/gnunet-namestore.c:356 #, c-format msgid "No options given\n" msgstr "" -#: src/namestore/gnunet-namestore.c:321 +#: src/namestore/gnunet-namestore.c:386 #, fuzzy, c-format msgid "Unsupported type `%s'\n" msgstr "Ungültige Nachricht des Typs %u empfangen. Nachricht wird verworfen.\n" -#: src/namestore/gnunet-namestore.c:328 src/namestore/gnunet-namestore.c:350 -#: src/namestore/gnunet-namestore.c:374 src/namestore/gnunet-namestore.c:384 -#: src/namestore/gnunet-namestore.c:409 +#: src/namestore/gnunet-namestore.c:394 src/namestore/gnunet-namestore.c:418 +#: src/namestore/gnunet-namestore.c:465 src/namestore/gnunet-namestore.c:477 +#: src/namestore/gnunet-namestore.c:518 #, fuzzy, c-format msgid "Missing option `%s' for operation `%s'\n" msgstr "Konfigurationsdatei `%s' wurde erzeugt.\n" -#: src/namestore/gnunet-namestore.c:329 src/namestore/gnunet-namestore.c:351 +#: src/namestore/gnunet-namestore.c:395 src/namestore/gnunet-namestore.c:419 msgid "add/del" msgstr "" -#: src/namestore/gnunet-namestore.c:341 +#: src/namestore/gnunet-namestore.c:408 #, fuzzy, c-format msgid "Value `%s' invalid for record type `%s'\n" msgstr "%s: Symbolwert `%s' ist ungültig für %s\n" -#: src/namestore/gnunet-namestore.c:366 +#: src/namestore/gnunet-namestore.c:446 #, fuzzy, c-format msgid "Invalid time format `%s'\n" msgstr "Ungültiger Parameter: `%s'\n" -#: src/namestore/gnunet-namestore.c:375 src/namestore/gnunet-namestore.c:385 +#: src/namestore/gnunet-namestore.c:455 +#, c-format +msgid "" +"Deletion requires either absolute time, or no time at all. Got relative time " +"`%s' instead.\n" +msgstr "" + +#: src/namestore/gnunet-namestore.c:466 src/namestore/gnunet-namestore.c:478 +#: src/namestore/gnunet-namestore.c:497 msgid "add" msgstr "" -#: src/namestore/gnunet-namestore.c:410 +#: src/namestore/gnunet-namestore.c:496 +#, fuzzy, c-format +msgid "No valid expiration time for operation `%s'\n" +msgstr "Konfigurationsdatei `%s' wurde erzeugt.\n" + +#: src/namestore/gnunet-namestore.c:519 msgid "del" msgstr "" -#: src/namestore/gnunet-namestore.c:462 +#: src/namestore/gnunet-namestore.c:569 +#: src/peerinfo-tool/gnunet-peerinfo.c:598 +#, fuzzy, c-format +msgid "Invalid URI `%s'\n" +msgstr "Ungültiger Parameter: `%s'\n" + +#: src/namestore/gnunet-namestore.c:625 +#, fuzzy, c-format +msgid "Using default zone file `%s'\n" +msgstr "Collection `%s' begonnen.\n" + +#: src/namestore/gnunet-namestore.c:677 msgid "add record" msgstr "" -#: src/namestore/gnunet-namestore.c:465 +#: src/namestore/gnunet-namestore.c:680 msgid "delete record" msgstr "" -#: src/namestore/gnunet-namestore.c:468 +#: src/namestore/gnunet-namestore.c:683 msgid "display records" msgstr "" -#: src/namestore/gnunet-namestore.c:471 +#: src/namestore/gnunet-namestore.c:686 msgid "" "expiration time for record to use (for adding only), \"never\" is possible" msgstr "" -#: src/namestore/gnunet-namestore.c:474 +#: src/namestore/gnunet-namestore.c:689 msgid "name of the record to add/delete/display" msgstr "" -#: src/namestore/gnunet-namestore.c:477 +#: src/namestore/gnunet-namestore.c:692 msgid "type of the record to add/delete/display" msgstr "" -#: src/namestore/gnunet-namestore.c:480 +#: src/namestore/gnunet-namestore.c:695 +msgid "URI to import into our zone" +msgstr "" + +#: src/namestore/gnunet-namestore.c:698 msgid "value of the record to add/delete" msgstr "" -#: src/namestore/gnunet-namestore.c:483 +#: src/namestore/gnunet-namestore.c:701 msgid "create or list public record" msgstr "" -#: src/namestore/gnunet-namestore.c:486 +#: src/namestore/gnunet-namestore.c:704 msgid "create or list non-authority record" msgstr "" -#: src/namestore/gnunet-namestore.c:489 +#: src/namestore/gnunet-namestore.c:707 msgid "filename with the zone key" msgstr "" -#: src/namestore/gnunet-namestore.c:500 +#: src/namestore/gnunet-namestore.c:718 #, fuzzy msgid "GNUnet zone manipulation tool" msgstr "GNUnet Konfiguration" -#: src/namestore/gnunet-service-namestore.c:143 -#, c-format -msgid "File zone `%s' but corrupt content already exists, failed to write! \n" -msgstr "" +#: src/namestore/gnunet-service-namestore.c:241 +#: src/namestore/gnunet-service-namestore.c:257 +#, fuzzy, c-format +msgid "Failed to write zone key to file `%s': %s\n" +msgstr "Datei wurde als `%s' gespeichert.\n" -#: src/namestore/gnunet-service-namestore.c:154 -#, c-format -msgid "File zone `%s' containing this key already exists\n" +#: src/namestore/gnunet-service-namestore.c:243 +msgid "file exists but reading key failed" msgstr "" -#: src/namestore/gnunet-service-namestore.c:160 -#, c-format -msgid "" -"File zone `%s' but different zone key already exists, failed to write! \n" +#: src/namestore/gnunet-service-namestore.c:259 +msgid "file exists with different key" msgstr "" -#: src/namestore/gnunet-service-namestore.c:198 +#: src/namestore/gnunet-service-namestore.c:1557 +#, fuzzy +msgid "Failed to find record to remove\n" +msgstr "Verbindung zu gnunetd konnte nicht hergestellt werden.\n" + +#: src/namestore/gnunet-service-namestore.c:2172 #, fuzzy, c-format -msgid "Stored zonekey for zone `%s' in file `%s'\n" -msgstr "Datei wurde als `%s' gespeichert.\n" +msgid "Could not parse zone key file `%s'\n" +msgstr "Konfigurationsdatei `%s' konnte nicht geparst werden.\n" -#: src/namestore/gnunet-service-namestore.c:1909 +#: src/namestore/gnunet-service-namestore.c:2262 #, fuzzy msgid "No directory to load zonefiles specified in configuration\n" msgstr "In der Konfigurationsdatei wurden keine Anwendungen definiert!\n" -#: src/namestore/gnunet-service-namestore.c:1918 +#: src/namestore/gnunet-service-namestore.c:2272 #, c-format msgid "Creating directory `%s' for zone files failed!\n" msgstr "" -#: src/namestore/namestore_api.c:315 src/namestore/namestore_api.c:353 -msgid "Namestore added record successfully" -msgstr "" - -#: src/namestore/namestore_api.c:323 +#: src/namestore/namestore_api.c:345 msgid "Namestore failed to add record" msgstr "" -#: src/namestore/namestore_api.c:361 -msgid "Namestore record already existed" -msgstr "" - -#: src/namestore/namestore_api.c:368 +#: src/namestore/namestore_api.c:371 msgid "Namestore failed to add record\n" msgstr "" -#: src/namestore/namestore_api.c:401 +#: src/namestore/namestore_api.c:415 +#, fuzzy +msgid "Failed to create new signature" +msgstr "Namespace `%s' konnte nicht erstellt werden (existiert bereits?).\n" + +#: src/namestore/namestore_api.c:419 #, fuzzy -msgid "Namestore removed record successfully" -msgstr "Der GNUnet Dienst wurde erfolgreich installiert.\n" +msgid "Failed to put new set of records in database" +msgstr "Fehler beim Senden einer `%s' Anfrage an den SMTP Server.\n" -#: src/namestore/namestore_api.c:408 -msgid "No records for entry" +#: src/namestore/namestore_api.c:423 +#, fuzzy +msgid "Failed to remove records from database" msgstr "" +"\n" +"Fehler beim Empfangen der Antwort von gnunetd.\n" -#: src/namestore/namestore_api.c:415 +#: src/namestore/namestore_api.c:427 #, fuzzy -msgid "Could not find record to remove" -msgstr "Verbindung zu gnunetd konnte nicht hergestellt werden.\n" +msgid "Failed to access database" +msgstr "Datei wurde als `%s' gespeichert.\n" -#: src/namestore/namestore_api.c:422 +#: src/namestore/namestore_api.c:431 #, fuzzy -msgid "Failed to create new signature" -msgstr "Namespace `%s' konnte nicht erstellt werden (existiert bereits?).\n" +msgid "unknown internal error in namestore" +msgstr "=\tFehler beim Lesen des Verzeichnisses.\n" + +#: src/namestore/namestore_api.c:436 +msgid "Protocol error" +msgstr "" + +#: src/namestore/namestore_common.c:530 src/namestore/namestore_common.c:670 +#, fuzzy, c-format +msgid "Unsupported record type %d\n" +msgstr "Ungültige Nachricht des Typs %u empfangen. Nachricht wird verworfen.\n" + +#: src/namestore/namestore_common.c:537 +#, fuzzy, c-format +msgid "Unable to parse IPv4 address `%s'\n" +msgstr "Ungültiger Parameter: `%s'\n" + +#: src/namestore/namestore_common.c:560 +#, fuzzy, c-format +msgid "Unable to parse SOA record `%s'\n" +msgstr "Fehler beim Lesen der Freunde-Liste von `%s'\n" + +#: src/namestore/namestore_common.c:583 +#, fuzzy, c-format +msgid "Unable to parse MX record `%s'\n" +msgstr "Fehler beim Lesen der Freunde-Liste von `%s'\n" -#: src/namestore/namestore_api.c:429 +#: src/namestore/namestore_common.c:601 +#, fuzzy, c-format +msgid "Unable to parse IPv6 address `%s'\n" +msgstr "Ungültiger Parameter: `%s'\n" + +#: src/namestore/namestore_common.c:614 +#, fuzzy, c-format +msgid "Unable to parse PKEY record `%s'\n" +msgstr "Fehler beim Lesen der Freunde-Liste von `%s'\n" + +#: src/namestore/namestore_common.c:635 +#, fuzzy, c-format +msgid "Unable to parse VPN record string `%s'\n" +msgstr "Fehler beim Lesen der Freunde-Liste von `%s'\n" + +#: src/namestore/namestore_common.c:661 +#, fuzzy, c-format +msgid "Unable to parse TLSA record string `%s'\n" +msgstr "Fehler beim Lesen der Freunde-Liste von `%s'\n" + +#: src/namestore/plugin_namestore_postgres.c:95 #, fuzzy -msgid "Failed to put new set of records in database" -msgstr "Fehler beim Senden einer `%s' Anfrage an den SMTP Server.\n" +msgid "Failed to create indices\n" +msgstr "Namespace `%s' konnte nicht erstellt werden (existiert bereits?).\n" #: src/nat/gnunet-nat-server.c:279 #, c-format msgid "Please pass valid port number as the first argument! (got `%s')\n" msgstr "" -#: src/nat/gnunet-nat-server.c:318 +#: src/nat/gnunet-nat-server.c:321 msgid "GNUnet NAT traversal test helper daemon" msgstr "" -#: src/nat/nat.c:799 +#: src/nat/nat_auto.c:169 +msgid "NAT traversal with ICMP Server timed out.\n" +msgstr "" + +#: src/nat/nat_auto.c:199 +msgid "NAT traversal with ICMP Server succeeded.\n" +msgstr "" + +#: src/nat/nat_auto.c:200 +msgid "NAT traversal with ICMP Server failed.\n" +msgstr "" + +#: src/nat/nat_auto.c:219 +#, fuzzy +msgid "Testing connection reversal with ICMP server.\n" +msgstr "Informationen über andere GNUnet Knoten ausgeben." + +#: src/nat/nat_auto.c:265 +#, fuzzy, c-format +msgid "Detected external IP `%s'\n" +msgstr "Ungültiger RPC `%s' empfangen.\n" + +#: src/nat/nat_auto.c:331 +msgid "This system has a global IPv6 address, setting IPv6 to supported.\n" +msgstr "" + +#: src/nat/nat_auto.c:347 +#, fuzzy, c-format +msgid "Detected internal network address `%s'.\n" +msgstr "GNUnet verwendet nun die IP-Adresse %u.%u.%u.%u.\n" + +#: src/nat/nat_auto.c:400 +msgid "upnpc found, enabling its use\n" +msgstr "" + +#: src/nat/nat_auto.c:401 +#, fuzzy +msgid "upnpc not found\n" +msgstr "Kommando `%s' wurde nicht gefunden!\n" + +#: src/nat/nat_auto.c:434 +msgid "gnunet-helper-nat-server found, testing it\n" +msgstr "" + +#: src/nat/nat_auto.c:435 +msgid "No working gnunet-helper-nat-server found\n" +msgstr "" + +#: src/nat/nat_auto.c:469 +msgid "gnunet-helper-nat-client found, enabling it\n" +msgstr "" + +#: src/nat/nat_auto.c:470 +msgid "gnunet-helper-nat-client not found or behind NAT, disabling it\n" +msgstr "" + +#: src/nat/nat.c:795 #, c-format msgid "gnunet-helper-nat-server generated malformed address `%s'\n" msgstr "" @@ -3834,27 +4117,34 @@ msgstr "" msgid "Failed to start %s\n" msgstr "Fehler beim Starten der Collection.\n" -#: src/nat/nat.c:1111 -#, fuzzy, c-format -msgid "Malformed %s `%s' given in configuration!\n" -msgstr "Fehler beim Speichern der Konfiguration!" +#: src/nat/nat.c:1113 +msgid "malformed" +msgstr "" -#: src/nat/nat.c:1177 src/nat/nat.c:1187 +#: src/nat/nat.c:1179 src/nat/nat.c:1191 #, c-format msgid "" "Configuration requires `%s', but binary is not installed properly (SUID bit " "not set). Option disabled.\n" msgstr "" -#: src/nat/nat.c:1321 +#: src/nat/nat.c:1326 msgid "Internal IP address not known, cannot use ICMP NAT traversal method\n" msgstr "" -#: src/nat/nat.c:1332 +#: src/nat/nat.c:1337 #, c-format msgid "Running gnunet-helper-nat-client %s %s %u\n" msgstr "" +#: src/nat/nat_mini.c:170 +msgid "`external-ip' command not found\n" +msgstr "" + +#: src/nat/nat_mini.c:505 +msgid "`upnpc' command not found\n" +msgstr "" + #: src/nat/nat_test.c:341 #, fuzzy msgid "Failed to connect to `gnunet-nat-server'\n" @@ -3865,46 +4155,78 @@ msgstr "Es konnte keine Verbindung mit gnunetd hergestellt werden.\n" msgid "Failed to create listen socket bound to `%s' for NAT test: %s\n" msgstr "" -#: src/nse/gnunet-nse-profiler.c:928 +#: src/nse/gnunet-nse-profiler.c:1009 +#, fuzzy +msgid "limit to the number of connections to NSE services, 0 for none" +msgstr "Es konnte keine Verbindung mit gnunetd hergestellt werden." + +#: src/nse/gnunet-nse-profiler.c:1012 +msgid "name of the file for writing connection information and statistics" +msgstr "" + +#: src/nse/gnunet-nse-profiler.c:1015 +msgid "name of the file with the login information for the testbed" +msgstr "" + +#: src/nse/gnunet-nse-profiler.c:1018 +msgid "IP address of this system as seen by the rest of the testbed" +msgstr "" + +#: src/nse/gnunet-nse-profiler.c:1021 +msgid "delay between queries to statistics during a round" +msgstr "" + +#: src/nse/gnunet-nse-profiler.c:1024 +msgid "prefix of the filenames we use for writing the topology for each round" +msgstr "" + +#: src/nse/gnunet-nse-profiler.c:1027 +msgid "name of the file for writing the main results" +msgstr "" + +#: src/nse/gnunet-nse-profiler.c:1030 +msgid "Number of peers to run in each round, separated by commas" +msgstr "" + +#: src/nse/gnunet-nse-profiler.c:1036 +msgid "delay between rounds" +msgstr "" + +#: src/nse/gnunet-nse-profiler.c:1046 #, fuzzy msgid "Measure quality and performance of the NSE service." msgstr "Auf den Dienst konnte nicht zugegriffen werden" -#: src/nse/gnunet-service-nse.c:925 -#, c-format -msgid "Proof of work invalid: %llu!\n" -msgstr "" +#: src/nse/gnunet-service-nse.c:1389 +#, fuzzy, c-format +msgid "NSE service could not access hostkey: %s\n" +msgstr "Auf die Namespace Informationen konnte nicht zugegriffen werden.\n" -#: src/nse/gnunet-service-nse.c:1381 src/nse/gnunet-service-nse.c:1400 -#: src/nse/gnunet-service-nse.c:1421 +#: src/nse/gnunet-service-nse.c:1403 src/nse/gnunet-service-nse.c:1478 +#: src/nse/gnunet-service-nse.c:1495 msgid "NSE service is lacking key configuration settings. Exiting.\n" msgstr "" -#: src/nse/gnunet-service-nse.c:1388 +#: src/nse/gnunet-service-nse.c:1485 #, fuzzy msgid "Invalid work requirement for NSE service. Exiting.\n" msgstr "Ungültige Parameter. Abbruch.\n" -#: src/nse/gnunet-service-nse.c:1409 -#, fuzzy -msgid "NSE service could not access hostkey. Exiting.\n" -msgstr "Auf die Namespace Informationen konnte nicht zugegriffen werden.\n" - #: src/peerinfo/gnunet-service-peerinfo.c:134 #, fuzzy, c-format msgid "Removing expired address of transport `%s'\n" msgstr "Verfügbare(r) Transport(e): %s\n" -#: src/peerinfo/gnunet-service-peerinfo.c:203 +#: src/peerinfo/gnunet-service-peerinfo.c:230 #, fuzzy, c-format msgid "Failed to parse HELLO in file `%s'\n" msgstr "Fehler beim Lesen der Freunde-Liste von `%s'\n" -#: src/peerinfo/gnunet-service-peerinfo.c:229 +#: src/peerinfo/gnunet-service-peerinfo.c:269 msgid "# peers known" msgstr "" -#: src/peerinfo/gnunet-service-peerinfo.c:254 +#: src/peerinfo/gnunet-service-peerinfo.c:297 #, c-format msgid "" "File `%s' in directory `%s' does not match naming convention. Removed.\n" @@ -3912,38 +4234,38 @@ msgstr "" "Die Datei `%s' im Verzeichnis `%s' entspricht nicht der Namenskonvention. " "Datei wurde entfernt.\n" -#: src/peerinfo/gnunet-service-peerinfo.c:353 +#: src/peerinfo/gnunet-service-peerinfo.c:419 #, fuzzy, c-format msgid "Still no peers found in `%s'!\n" msgstr "Dienst `%s' konnte nicht ordentlich entladen werden!\n" -#: src/peerinfo/gnunet-service-peerinfo.c:710 +#: src/peerinfo/gnunet-service-peerinfo.c:807 #, c-format msgid "Importing HELLOs from `%s'\n" msgstr "" -#: src/peerinfo/peerinfo_api.c:238 +#: src/peerinfo/peerinfo_api.c:239 msgid "aborted due to explicit disconnect request" msgstr "" -#: src/peerinfo/peerinfo_api.c:358 +#: src/peerinfo/peerinfo_api.c:359 #, fuzzy msgid "failed to transmit request (service down?)" msgstr "Fehler beim Senden einer `%s' Anfrage an den SMTP Server.\n" -#: src/peerinfo/peerinfo_api.c:505 +#: src/peerinfo/peerinfo_api.c:509 #, fuzzy msgid "Failed to receive response from `PEERINFO' service." msgstr "Fehler beim Empfangen der Antwort von gnunetd auf die `%s' Nachricht\n" -#: src/peerinfo/peerinfo_api.c:531 src/peerinfo/peerinfo_api.c:550 -#: src/peerinfo/peerinfo_api.c:565 src/peerinfo/peerinfo_api.c:576 -#: src/peerinfo/peerinfo_api.c:587 +#: src/peerinfo/peerinfo_api.c:550 src/peerinfo/peerinfo_api.c:569 +#: src/peerinfo/peerinfo_api.c:584 src/peerinfo/peerinfo_api.c:595 +#: src/peerinfo/peerinfo_api.c:606 #, fuzzy msgid "Received invalid message from `PEERINFO' service." msgstr "Ungültige `%s' Anfrage von `%s' empfangen.\n" -#: src/peerinfo/peerinfo_api.c:663 +#: src/peerinfo/peerinfo_api.c:681 #, fuzzy msgid "Timeout transmitting iteration request to `PEERINFO' service." msgstr "Fehler beim Senden einer `%s' Anfrage an den SMTP Server.\n" @@ -3953,91 +4275,51 @@ msgstr "Fehler beim Senden einer `%s' Anfrage an den SMTP Server.\n" msgid "Could not connect to `%s' service.\n" msgstr "Verbindung zu gnunetd konnte nicht hergestellt werden.\n" -#: src/peerinfo-tool/gnunet-peerinfo.c:581 -#, fuzzy -msgid "Failed to parse HELLO message: missing expiration time\n" -msgstr "Fehler beim Speichern der Konfiguration!" - -#: src/peerinfo-tool/gnunet-peerinfo.c:589 -#, fuzzy -msgid "Failed to parse HELLO message: invalid expiration time\n" -msgstr "Fehler beim Speichern der Konfiguration!" - -#: src/peerinfo-tool/gnunet-peerinfo.c:598 -#, fuzzy -msgid "Failed to parse HELLO message: malformed\n" -msgstr "Fehler beim Lesen der Freunde-Liste von `%s'\n" - -#: src/peerinfo-tool/gnunet-peerinfo.c:608 -#, fuzzy -msgid "Failed to parse HELLO message: missing transport plugin\n" -msgstr "Anwendung `%s' konnte nicht initialisiert werden.\n" - -#: src/peerinfo-tool/gnunet-peerinfo.c:625 -#, c-format -msgid "Plugin `%s' not found\n" -msgstr "" - -#: src/peerinfo-tool/gnunet-peerinfo.c:634 -#, c-format -msgid "Plugin `%s' does not support URIs yet\n" -msgstr "" - -#: src/peerinfo-tool/gnunet-peerinfo.c:653 -#, fuzzy, c-format -msgid "Failed to parse `%s' as an address for plugin `%s'\n" -msgstr "Fehler beim Binden an UDP Port %d.\n" - -#: src/peerinfo-tool/gnunet-peerinfo.c:685 +#: src/peerinfo-tool/gnunet-peerinfo.c:419 #, fuzzy, c-format msgid "Failure adding HELLO: %s\n" msgstr "Fehler bei %s:%d.\n" -#: src/peerinfo-tool/gnunet-peerinfo.c:833 +#: src/peerinfo-tool/gnunet-peerinfo.c:557 #, fuzzy, c-format msgid "Could not find option `%s:%s' in configuration.\n" msgstr "Knoten `%s' konnte nicht in der Routing Tabelle gefunden werden!\n" -#: src/peerinfo-tool/gnunet-peerinfo.c:840 +#: src/peerinfo-tool/gnunet-peerinfo.c:563 #, fuzzy, c-format msgid "Loading hostkey from `%s' failed.\n" msgstr "Das Parsen des Hello von `%s' schlug fehl.\n" -#: src/peerinfo-tool/gnunet-peerinfo.c:875 -#, fuzzy, c-format -msgid "Invalid URI `%s'\n" -msgstr "Ungültiger Parameter: `%s'\n" - -#: src/peerinfo-tool/gnunet-peerinfo.c:899 +#: src/peerinfo-tool/gnunet-peerinfo.c:622 #, c-format msgid "I am peer `%s'.\n" msgstr "Ich bin Peer `%s'.\n" -#: src/peerinfo-tool/gnunet-peerinfo.c:936 +#: src/peerinfo-tool/gnunet-peerinfo.c:648 msgid "don't resolve host names" msgstr "" -#: src/peerinfo-tool/gnunet-peerinfo.c:939 +#: src/peerinfo-tool/gnunet-peerinfo.c:651 msgid "output only the identity strings" msgstr "" -#: src/peerinfo-tool/gnunet-peerinfo.c:942 +#: src/peerinfo-tool/gnunet-peerinfo.c:654 msgid "output our own identity only" msgstr "" -#: src/peerinfo-tool/gnunet-peerinfo.c:945 +#: src/peerinfo-tool/gnunet-peerinfo.c:657 msgid "list all known peers" msgstr "" -#: src/peerinfo-tool/gnunet-peerinfo.c:948 +#: src/peerinfo-tool/gnunet-peerinfo.c:660 msgid "also output HELLO uri(s)" msgstr "" -#: src/peerinfo-tool/gnunet-peerinfo.c:951 +#: src/peerinfo-tool/gnunet-peerinfo.c:663 msgid "add given HELLO uri to the database" msgstr "" -#: src/peerinfo-tool/gnunet-peerinfo.c:957 +#: src/peerinfo-tool/gnunet-peerinfo.c:674 #, fuzzy msgid "Print information about peers." msgstr "Informationen über andere GNUnet Knoten ausgeben." @@ -4133,479 +4415,561 @@ msgstr "" msgid "Failed to connect to %s service. Exiting.\n" msgstr "`%s' Dienst konnte nicht initialisiert werden.\n" -#: src/pt/gnunet-daemon-pt.c:973 +#: src/pt/gnunet-daemon-pt.c:976 msgid "Daemon to run to perform IP protocol translation to GNUnet" msgstr "" -#: src/statistics/gnunet-service-statistics.c:271 +#: src/regex/gnunet-daemon-regexprofiler.c:293 #, fuzzy, c-format -msgid "Loading %llu bytes of statistics from `%s'\n" -msgstr "Dateien aus dem GNUnet herunterladen." +msgid "Regexprofiler could not access hostkey: %s. Exiting.\n" +msgstr "Auf die Namespace Informationen konnte nicht zugegriffen werden.\n" -#: src/statistics/gnunet-service-statistics.c:330 -#, fuzzy, c-format -msgid "Wrote %llu bytes of statistics to `%s'\n" -msgstr "Dateien aus dem GNUnet herunterladen." +#: src/regex/gnunet-daemon-regexprofiler.c:452 +msgid "Daemon to announce regular expressions for the peer using mesh." +msgstr "" -#: src/statistics/gnunet-statistics.c:122 -#, fuzzy -msgid "Failed to obtain statistics.\n" -msgstr "Statistiken über den Netzwerkverkehr konnten nicht ermittelt werden.\n" +#: src/regex/gnunet-regex-profiler.c:1147 +msgid "An operation has failed while starting peers\n" +msgstr "" -#: src/statistics/gnunet-statistics.c:199 -#, c-format -msgid "No subsystem or name given\n" +#: src/regex/gnunet-regex-profiler.c:1193 +#, fuzzy, c-format +msgid "Creating a peer failed. Error: %s\n" +msgstr "" +"\n" +"Fehler beim Uploaden der Datei: %s\n" + +#: src/regex/gnunet-regex-profiler.c:1320 +msgid "An operation has failed while starting slaves\n" msgstr "" -#: src/statistics/gnunet-statistics.c:207 +#: src/regex/gnunet-regex-profiler.c:1342 #, fuzzy, c-format -msgid "Failed to initialize watch routine\n" -msgstr "SQLite Datenbank konnte nicht initialisiert werden.\n" +msgid "No files found in `%s'\n" +msgstr "Dienst `%s' konnte nicht ordentlich entladen werden!\n" -#: src/statistics/gnunet-statistics.c:227 -msgid "limit output to statistics for the given NAME" +#: src/regex/gnunet-regex-profiler.c:1397 +msgid "An operation has failed while linking\n" msgstr "" -#: src/statistics/gnunet-statistics.c:230 -msgid "make the value being set persistent" +#: src/regex/gnunet-regex-profiler.c:1508 +#: src/testbed/testbed_api_testbed.c:805 +#, c-format +msgid "Host registration failed for a host. Error: %s\n" msgstr "" -#: src/statistics/gnunet-statistics.c:233 -msgid "limit output to the given SUBSYSTEM" +#: src/regex/gnunet-regex-profiler.c:1589 +msgid "Unable to connect to master controller -- Check config\n" msgstr "" -#: src/statistics/gnunet-statistics.c:236 -msgid "just print the statistics value" +#: src/regex/gnunet-regex-profiler.c:1691 +#: src/testbed/testbed_api_testbed.c:970 +#, c-format +msgid "Host %s cannot start testbed\n" msgstr "" -#: src/statistics/gnunet-statistics.c:239 -msgid "watch value continously" +#: src/regex/gnunet-regex-profiler.c:1694 +#: src/testbed/testbed_api_testbed.c:974 +msgid "Testbed cannot be started on localhost\n" msgstr "" -#: src/statistics/gnunet-statistics.c:246 -msgid "Print statistics about GNUnet operations." -msgstr "Statistiken der GNUnet Aktivitäten ausgeben." +#: src/regex/gnunet-regex-profiler.c:1734 +#, c-format +msgid "No hosts-file specified on command line. Exiting.\n" +msgstr "" -#: src/statistics/statistics_api.c:456 -#, fuzzy -msgid "Could not save some persistent statistics\n" +#: src/regex/gnunet-regex-profiler.c:1739 +#: src/regex/gnunet-regex-simulation-profiler.c:622 +#, c-format +msgid "No policy directory specified on command line. Exiting.\n" msgstr "" -"IP(v4) dieses Hosts konnte nicht ermittelt werden. Bitte geben Sie die IP in " -"der Konfigurationsdatei an.\n" -#: src/statistics/statistics_api.c:999 -msgid "" -"Failed to receive acknowledgement from statistics service, some statistics " -"might have been lost!\n" +#: src/regex/gnunet-regex-profiler.c:1745 +#: src/testbed/testbed_api_testbed.c:1065 +#, c-format +msgid "No hosts loaded. Need at least one host\n" msgstr "" -#: src/testing/gnunet-testing.c:157 -#, fuzzy -msgid "Could not read hostkeys file, specify hostkey file with -H!\n" -msgstr "Fehler beim Lesen der Freunde-Liste von `%s'\n" - -#: src/testing/gnunet-testing.c:159 +#: src/regex/gnunet-regex-profiler.c:1748 #, c-format -msgid "Specified hostkey file `%s' not found!\n" +msgid "Checking whether given hosts can start testbed. Please wait\n" msgstr "" -#: src/testing/gnunet-testing.c:273 -#, fuzzy -msgid "create unique configuration files" +#: src/regex/gnunet-regex-profiler.c:1769 +#, fuzzy, c-format +msgid "Exiting\n" msgstr "" -"Einen Wert aus der Konfigurationsdatei auf der Standardausgabe ausgeben" +"\n" +"Abbruch.\n" -#: src/testing/gnunet-testing.c:275 -msgid "create hostkey files from pre-computed hostkey list" +#: src/regex/gnunet-regex-profiler.c:1775 +#, fuzzy, c-format +msgid "No configuration file given. Exiting\n" +msgstr "Konfigurationsdatei FILENAME verwenden" + +#: src/regex/gnunet-regex-profiler.c:1784 +#, fuzzy, c-format +msgid "Configuration option (regex_prefix) missing. Exiting\n" +msgstr "Konfigurationsdatei `%s' wurde erzeugt.\n" + +#: src/regex/gnunet-regex-profiler.c:1802 +#: src/regex/gnunet-regex-simulation-profiler.c:629 +#, c-format +msgid "Specified policies directory does not exist. Exiting.\n" msgstr "" -#: src/testing/gnunet-testing.c:277 -msgid "host key file" +#: src/regex/gnunet-regex-profiler.c:1809 +#, c-format +msgid "No search strings file given. Exiting.\n" msgstr "" -#: src/testing/gnunet-testing.c:279 -#, fuzzy -msgid "number of unique configuration files or hostkeys to create" +#: src/regex/gnunet-regex-profiler.c:1817 +#, c-format +msgid "" +"Error loading search strings. Given file does not contain enough strings. " +"Exiting.\n" msgstr "" -"Einen Wert aus der Konfigurationsdatei auf der Standardausgabe ausgeben" -#: src/testing/gnunet-testing.c:281 +#: src/regex/gnunet-regex-profiler.c:1823 +#, fuzzy, c-format +msgid "Error loading search strings. Exiting.\n" +msgstr "Fehler beim Verlassen der DHT.\n" + +#: src/regex/gnunet-regex-profiler.c:1850 #, fuzzy -msgid "configuration template" -msgstr "GNUnet Konfiguration" +msgid "name of the file for writing statistics" +msgstr "Statistiken über den Netzwerkverkehr konnten nicht ermittelt werden.\n" -#: src/testing/gnunet-testing.c:287 -msgid "Command line tool to access the testing library" +#: src/regex/gnunet-regex-profiler.c:1853 +msgid "create COUNT number of random links between peers" msgstr "" -#: src/testing/helper.c:56 -#, fuzzy -msgid "Peer is lacking HOSTKEY configuration setting.\n" -msgstr "GNUnet Konfiguration" +#: src/regex/gnunet-regex-profiler.c:1856 +msgid "wait TIMEOUT before considering a string match as failed" +msgstr "" -#: src/testing/helper.c:64 -#, fuzzy -msgid "Could not access hostkey.\n" -msgstr "Konfigurationsdatei `%s' konnte nicht geparst werden.\n" +#: src/regex/gnunet-regex-profiler.c:1859 +msgid "wait DELAY before starting string search" +msgstr "" -#: src/testing/testing.c:200 -msgid "`scp' does not seem to terminate (timeout copying config).\n" +#: src/regex/gnunet-regex-profiler.c:1862 +msgid "number of search strings to read from search strings file" msgstr "" -#: src/testing/testing.c:214 src/testing/testing.c:798 -#, fuzzy -msgid "`scp' did not complete cleanly.\n" -msgstr "`%s' ist zu keinem Knoten verbunden.\n" +#: src/regex/gnunet-regex-profiler.c:1865 +#: src/regex/gnunet-regex-simulation-profiler.c:692 +msgid "maximum path compression length" +msgstr "" -#: src/testing/testing.c:237 -#, fuzzy -msgid "Failed to create pipe for `gnunet-peerinfo' process.\n" -msgstr "Fehler beim Starten der Collection.\n" +#: src/regex/gnunet-regex-profiler.c:1868 +msgid "" +"if this option is set, only one peer is responsible for searching all strings" +msgstr "" -#: src/testing/testing.c:238 -#, fuzzy -msgid "Failed to create pipe for `ssh' process.\n" -msgstr "Dateiformat fehlerhaft (kein GNUnet Verzeichnis?)\n" +#: src/regex/gnunet-regex-profiler.c:1881 +msgid "Profiler for regex" +msgstr "" -#: src/testing/testing.c:286 -#, fuzzy, c-format -msgid "Could not start `%s' process to create hostkey.\n" +#: src/regex/gnunet-regex-simulation-profiler.c:689 +msgid "name of the table to write DFAs" msgstr "" -"IP(v4) dieses Hosts konnte nicht ermittelt werden. Bitte geben Sie die IP in " -"der Konfigurationsdatei an.\n" -#: src/testing/testing.c:293 -#, fuzzy -msgid "Failed to start `gnunet-peerinfo' process.\n" -msgstr "Fehler beim Starten der Collection.\n" +#: src/regex/gnunet-regex-simulation-profiler.c:705 +msgid "Profiler for regex library" +msgstr "" -#: src/testing/testing.c:294 src/testing/testing.c:471 -#, fuzzy -msgid "Failed to start `ssh' process.\n" -msgstr "Fehler beim Starten der Collection.\n" +#: src/statistics/gnunet-service-statistics.c:271 +#, fuzzy, c-format +msgid "Loading %llu bytes of statistics from `%s'\n" +msgstr "Dateien aus dem GNUnet herunterladen." -#: src/testing/testing.c:354 +#: src/statistics/gnunet-service-statistics.c:330 #, fuzzy, c-format -msgid "Error reading from gnunet-peerinfo: %s\n" -msgstr "Fehler beim Lesen von Informationen von gnunetd.\n" +msgid "Wrote %llu bytes of statistics to `%s'\n" +msgstr "Dateien aus dem GNUnet herunterladen." -#: src/testing/testing.c:358 +#: src/statistics/gnunet-statistics.c:141 #, fuzzy -msgid "Malformed output from gnunet-peerinfo!\n" -msgstr "Fehler beim Lesen von Informationen von gnunetd.\n" +msgid "Failed to obtain statistics.\n" +msgstr "Statistiken über den Netzwerkverkehr konnten nicht ermittelt werden.\n" -#: src/testing/testing.c:368 -#, fuzzy -msgid "Failed to get hostkey!\n" +#: src/statistics/gnunet-statistics.c:143 +#, fuzzy, c-format +msgid "Failed to obtain statistics from host `%s:%llu'\n" msgstr "Statistiken über den Netzwerkverkehr konnten nicht ermittelt werden.\n" -#: src/testing/testing.c:400 -msgid "`Failed while waiting for topology setup!\n" +#: src/statistics/gnunet-statistics.c:181 +#, fuzzy, c-format +msgid "Trying to connect to remote host, but service `%s' is not running\n" +msgstr "Verbindung zu gnunetd konnte nicht hergestellt werden.\n" + +#: src/statistics/gnunet-statistics.c:190 +#, fuzzy, c-format +msgid "A port is required to connect to host `%s'\n" +msgstr "Es konnte keine Verbindung mit gnunetd hergestellt werden.\n" + +#: src/statistics/gnunet-statistics.c:196 +#, c-format +msgid "A port has to be between 1 and 65535 to connect to host `%s'\n" +msgstr "" + +#: src/statistics/gnunet-statistics.c:210 +msgid "Missing argument: subsystem \n" +msgstr "" + +#: src/statistics/gnunet-statistics.c:216 +msgid "Missing argument: name\n" +msgstr "" + +#: src/statistics/gnunet-statistics.c:247 +#, c-format +msgid "No subsystem or name given\n" msgstr "" -#: src/testing/testing.c:463 +#: src/statistics/gnunet-statistics.c:255 #, fuzzy, c-format -msgid "Could not start `%s' process to start GNUnet.\n" +msgid "Failed to initialize watch routine\n" +msgstr "SQLite Datenbank konnte nicht initialisiert werden.\n" + +#: src/statistics/gnunet-statistics.c:310 +msgid "limit output to statistics for the given NAME" msgstr "" -"IP(v4) dieses Hosts konnte nicht ermittelt werden. Bitte geben Sie die IP in " -"der Konfigurationsdatei an.\n" -#: src/testing/testing.c:470 -#, fuzzy -msgid "Failed to start `gnunet-arm' process.\n" -msgstr "Es konnte keine Verbindung mit gnunetd hergestellt werden.\n" +#: src/statistics/gnunet-statistics.c:313 +msgid "make the value being set persistent" +msgstr "" -#: src/testing/testing.c:493 src/testing/testing.c:600 -msgid "`gnunet-arm' does not seem to terminate.\n" +#: src/statistics/gnunet-statistics.c:316 +msgid "limit output to the given SUBSYSTEM" msgstr "" -#: src/testing/testing.c:494 src/testing/testing.c:601 -#: src/testing/testing.c:621 -msgid "`ssh' does not seem to terminate.\n" +#: src/statistics/gnunet-statistics.c:319 +msgid "just print the statistics value" msgstr "" -#: src/testing/testing.c:570 -msgid "Unable to get HELLO for peer!\n" +#: src/statistics/gnunet-statistics.c:322 +msgid "watch value continuously" msgstr "" -#: src/testing/testing.c:620 -msgid "`gnunet-arm' terminated with non-zero exit status (or timed out)!\n" +#: src/statistics/gnunet-statistics.c:325 +msgid "connect to remote host" msgstr "" -#: src/testing/testing.c:643 src/testing/testing.c:675 -msgid "either `gnunet-arm' or `ssh' does not seem to terminate.\n" +#: src/statistics/gnunet-statistics.c:328 +msgid "port for remote host" msgstr "" -#: src/testing/testing.c:658 src/testing/testing.c:713 +#: src/statistics/gnunet-statistics.c:340 +msgid "Print statistics about GNUnet operations." +msgstr "Statistiken der GNUnet Aktivitäten ausgeben." + +#: src/statistics/statistics_api.c:511 #, fuzzy -msgid "shutdown (either `gnunet-arm' or `ssh') did not complete cleanly.\n" -msgstr "`%s' ist zu keinem Knoten verbunden.\n" +msgid "Could not save some persistent statistics\n" +msgstr "" +"IP(v4) dieses Hosts konnte nicht ermittelt werden. Bitte geben Sie die IP in " +"der Konfigurationsdatei an.\n" + +#: src/statistics/statistics_api.c:1056 +msgid "" +"Failed to receive acknowledgement from statistics service, some statistics " +"might have been lost!\n" +msgstr "" + +#: src/sysmon/gnunet-service-sysmon.c:546 +#, c-format +msgid "Could not parse execution interval for `%s', set to default 60 sec.\n" +msgstr "" + +#: src/testbed/gnunet-testbed-profiler.c:231 +#, c-format +msgid "No hosts-file specified on command line\n" +msgstr "" + +#: src/testbed/gnunet-testbed-profiler.c:261 +msgid "create COUNT number of peers" +msgstr "" + +#: src/testbed/gnunet-testbed-profiler.c:264 +msgid "tolerate COUNT number of continious timeout failures" +msgstr "" -#: src/testing/testing.c:786 -msgid "`scp' does not seem to terminate.\n" +#: src/testbed/gnunet-testbed-profiler.c:276 +msgid "Profiler for testbed" msgstr "" -#: src/testing/testing.c:948 +#: src/testbed/ll_master.c:57 #, fuzzy, c-format -msgid "Starting service %s for peer `%4s'\n" -msgstr "Collection `%s' begonnen.\n" +msgid "Job command file not given. Exiting\n" +msgstr "Konfigurationsdatei FILENAME verwenden" -#: src/testing/testing.c:1207 src/testing/testing_group.c:6154 +#: src/testbed/testbed_api.c:499 #, fuzzy, c-format -msgid "Could not start `%s' process to copy configuration directory.\n" -msgstr "" -"IP(v4) dieses Hosts konnte nicht ermittelt werden. Bitte geben Sie die IP in " -"der Konfigurationsdatei an.\n" +msgid "Adding host %u failed with error: %s\n" +msgstr "`%s' schlug bei %s:%d mit dem Fehler %s fehl\n" -#: src/testing/testing.c:1292 src/testing/testing.c:1359 +#: src/testbed/testbed_api_hosts.c:306 #, fuzzy, c-format -msgid "Terminating peer `%4s'\n" -msgstr "Zugriff verweigert für `%s' bei %s:%d.\n" +msgid "Hosts file %s not found\n" +msgstr "`%s' fehlgeschlagen: Tabelle nicht gefunden!\n" -#: src/testing/testing.c:1448 +#: src/testbed/testbed_api_hosts.c:314 #, fuzzy, c-format -msgid "Setting d->dead on peer `%4s'\n" -msgstr "Collection `%s' begonnen.\n" +msgid "Hosts file %s has no data\n" +msgstr "Sitzungsschlüssel von Knoten `%s' konnte nicht überprüft werden.\n" + +#: src/testbed/testbed_api_hosts.c:321 +#, fuzzy, c-format +msgid "Hosts file %s cannot be read\n" +msgstr "Sitzungsschlüssel von Knoten `%s' konnte nicht überprüft werden.\n" -#: src/testing/testing.c:1601 -msgid "Peer not yet running, can not change configuration at this point." +#: src/testbed/testbed_api_testbed.c:623 +msgid "Linking controllers failed. Exiting" msgstr "" -#: src/testing/testing.c:1609 +#: src/testbed/testbed_api_testbed.c:1009 #, fuzzy -msgid "Failed to write new configuration to disk." -msgstr "Fehler beim Speichern der Konfiguration!" +msgid "Cannot start the master controller" +msgstr "GNUnet testbed Controller starten." -#: src/testing/testing.c:1636 -#, fuzzy, c-format -msgid "Could not start `%s' process to copy configuration file.\n" +#: src/testbed/testbed_api_testbed.c:1089 +msgid "Specified topology must be supported by testbed" msgstr "" -"IP(v4) dieses Hosts konnte nicht ermittelt werden. Bitte geben Sie die IP in " -"der Konfigurationsdatei an.\n" -#: src/testing/testing.c:1639 -#, fuzzy -msgid "Failed to copy new configuration to remote machine." -msgstr "Fehler beim Speichern der Konfiguration!" +#: src/testbed/testbed_api_topology.c:668 +#, fuzzy, c-format +msgid "Topology file %s not found\n" +msgstr "`%s' fehlgeschlagen: Tabelle nicht gefunden!\n" -#: src/testing/testing.c:1794 -#, fuzzy -msgid "Peers failed to connect" -msgstr "Es konnte keine Verbindung mit gnunetd hergestellt werden." +#: src/testbed/testbed_api_topology.c:674 +#, fuzzy, c-format +msgid "Topology file %s has no data\n" +msgstr "Sitzungsschlüssel von Knoten `%s' konnte nicht überprüft werden.\n" -#: src/testing/testing.c:1922 -#, fuzzy -msgid "Failed to connect to core service of first peer!\n" -msgstr "Der Transportdienst auf Port %d konnte nicht gestartet werden.\n" +#: src/testbed/testbed_api_topology.c:681 +#, fuzzy, c-format +msgid "Topology file %s cannot be read\n" +msgstr "Sitzungsschlüssel von Knoten `%s' konnte nicht überprüft werden.\n" + +#: src/testbed/testbed_api_topology.c:704 +#, fuzzy, c-format +msgid "Failed to read peer index from toology file: %s" +msgstr "Konfigurationsdatei `%s' konnte nicht geparst werden.\n" -#: src/testing/testing.c:2145 -msgid "Peers are not fully running yet, can not connect!\n" +#: src/testbed/testbed_api_topology.c:713 +#: src/testbed/testbed_api_topology.c:737 +#, c-format +msgid "Value in given topology file: %s out of range\n" msgstr "" -#: src/testing/testing_group.c:1895 src/testing/testing_group.c:1907 -#: src/testing/testing_group.c:2008 src/testing/testing_group.c:2065 -#: src/testing/testing_group.c:2152 src/testing/testing_group.c:2172 -#: src/testing/testing_group.c:2302 src/testing/testing_peergroup.c:950 +#: src/testbed/testbed_api_topology.c:719 +#: src/testbed/testbed_api_topology.c:743 #, fuzzy, c-format -msgid "Invalid value `%s' for option `%s' in section `%s': expected float\n" -msgstr "" -"Die Konfigurationsdatei muss in der Sektion `%s' unter `%s' ein Verzeichnis " -"angeben, in dem FS Daten gespeichert werden.\n" +msgid "Failed to read peer index from topology file: %s" +msgstr "Konfigurationsdatei `%s' konnte nicht geparst werden.\n" -#: src/testing/testing_group.c:2160 -#, c-format -msgid "" -"Invalid value `%s' for option `%s' in section `%s': got %f, needed value " -"greater than 0\n" +#: src/testbed/testbed_api_topology.c:725 +#: src/testbed/testbed_api_topology.c:749 +msgid "Topology file needs more peers than given ones\n" msgstr "" -#: src/testing/testing_group.c:2877 src/testing/testing_group.c:3063 +#: src/testbed/testbed_api_topology.c:764 #, fuzzy, c-format -msgid "" -"No `%s' specified in peer configuration in section `%s', cannot copy friends " -"file!\n" +msgid "Ignoring to connect peer %u to peer %u\n" +msgstr "Verbindung zu %u.%u.%u.%u:%u fehlgeschlagen: %s\n" + +#: src/testing/gnunet-testing.c:132 +#, fuzzy, c-format +msgid "Could not extract hostkey %u (offset too large?)\n" +msgstr "Fehler beim Lesen der Freunde-Liste von `%s'\n" + +#: src/testing/gnunet-testing.c:203 +#, fuzzy +msgid "create unique configuration files" msgstr "" -"Option `%s' ist in der Konfigurationsdatei in der Sektion `%s' nicht " -"gesetzt, sie wird auf %dm gesetzt.\n" +"Einen Wert aus der Konfigurationsdatei auf der Standardausgabe ausgeben" -#: src/testing/testing_group.c:3957 -msgid "Creating no allowed topology (all peers can connect at core level)\n" +#: src/testing/gnunet-testing.c:205 +msgid "extract hostkey file from pre-computed hostkey list" msgstr "" -#: src/testing/testing_group.c:5226 +#: src/testing/gnunet-testing.c:207 #, fuzzy -msgid "Unknown topology specification, can't connect peers!\n" -msgstr "Syntaxfehler in Topolgieangabe, Bytes werden übersprungen.\n" +msgid "" +"number of unique configuration files to create, or number of the hostkey to " +"extract" +msgstr "" +"Einen Wert aus der Konfigurationsdatei auf der Standardausgabe ausgeben" -#: src/testing/testing_group.c:5944 src/transport/transport-testing.c:636 +#: src/testing/gnunet-testing.c:209 #, fuzzy -msgid "Could not read hostkeys file!\n" -msgstr "Fehler beim Lesen der Freunde-Liste von `%s'\n" +msgid "configuration template" +msgstr "GNUnet Konfiguration" -#: src/testing/testing_group.c:6011 -#, fuzzy, c-format -msgid "Could not create configuration for peer number %u on `%s'!\n" -msgstr "Auf die Namespace Informationen konnte nicht zugegriffen werden.\n" +#: src/testing/gnunet-testing.c:218 +msgid "Command line tool to access the testing library" +msgstr "" + +#: src/testing/gnunet-testing-run-service.c:129 +#, c-format +msgid "Unknown command, use 'q' to quit or 'r' to restart peer\n" +msgstr "" + +#: src/testing/gnunet-testing-run-service.c:186 +#, fuzzy +msgid "name of the template configuration file to use (optional)" +msgstr "" +"Einen Wert aus der Konfigurationsdatei auf der Standardausgabe ausgeben" -#: src/testing/testing_new.c:169 -msgid "tmppath cannot be NULL\n" +#: src/testing/gnunet-testing-run-service.c:189 +msgid "name of the service to run" msgstr "" -#: src/testing/testing_new.c:356 +#: src/testing/testing.c:211 #, c-format msgid "Hostkeys file not found: %s\n" msgstr "" -#: src/testing/testing_new.c:365 -#, fuzzy, c-format -msgid "Could not open hostkeys file: %s\n" -msgstr "Fehler beim Lesen der Freunde-Liste von `%s'\n" - -#: src/testing/testing_new.c:380 +#: src/testing/testing.c:227 #, c-format msgid "Incorrect hostkey file format: %s\n" msgstr "" -#: src/testing/testing_new.c:437 +#: src/testing/testing.c:541 #, fuzzy, c-format msgid "Key number %u does not exist\n" msgstr "Anzahl an Nachrichten, die pro Durchlauf verwendet wird" -#: src/testing/testing_new.c:446 +#: src/testing/testing.c:551 #, fuzzy, c-format msgid "Error while decoding key %u\n" msgstr "Fehler beim Download: %s\n" -#: src/testing/testing_new.c:680 +#: src/testing/testing.c:865 #, fuzzy msgid "Failed to create configuration for peer (not enough free ports?)\n" msgstr "Auf die Namespace Informationen konnte nicht zugegriffen werden.\n" -#: src/testing/testing_new.c:691 +#: src/testing/testing.c:876 #, c-format msgid "" "You attempted to create a testbed with more than %u hosts. Please " "precompute more hostkeys first.\n" msgstr "" -#: src/testing/testing_new.c:704 +#: src/testing/testing.c:890 #, fuzzy, c-format msgid "Failed to initialize hostkey for peer %u\n" msgstr "SQLite Datenbank konnte nicht initialisiert werden.\n" -#: src/testing/testing_new.c:734 +#: src/testing/testing.c:923 #, fuzzy, c-format msgid "Failed to write hostkey file for peer %u: %s\n" msgstr "Dateiformat fehlerhaft (kein GNUnet Verzeichnis?)\n" -#: src/testing/testing_new.c:751 +#: src/testing/testing.c:941 #, fuzzy, c-format msgid "Failed to write configuration file `%s' for peer %u: %s\n" msgstr "Fehler beim Speichern der Konfigurationsdatei `%s':" -#: src/testing/testing_new.c:791 +#: src/testing/testing.c:1014 #, fuzzy, c-format msgid "Failed to start `%s': %s\n" msgstr "Es konnte keine Verbindung mit gnunetd hergestellt werden.\n" -#: src/testing/testing_new.c:959 +#: src/testing/testing.c:1219 #, fuzzy, c-format msgid "Failed to load configuration from %s\n" msgstr "Fehler beim Speichern der Konfigurationsdatei `%s':" -#: src/topology/gnunet-daemon-topology.c:259 +#: src/topology/gnunet-daemon-topology.c:254 msgid "# peers blacklisted" msgstr "" -#: src/topology/gnunet-daemon-topology.c:392 +#: src/topology/gnunet-daemon-topology.c:387 #, fuzzy msgid "# connect requests issued to transport" msgstr "# Client Trace-Anfragen empfangen" -#: src/topology/gnunet-daemon-topology.c:730 -#: src/topology/gnunet-daemon-topology.c:815 +#: src/topology/gnunet-daemon-topology.c:725 +#: src/topology/gnunet-daemon-topology.c:810 #, fuzzy msgid "# friends connected" msgstr "# verbundener Knoten" -#: src/topology/gnunet-daemon-topology.c:996 +#: src/topology/gnunet-daemon-topology.c:991 msgid "Failed to connect to core service, can not manage topology!\n" msgstr "" -#: src/topology/gnunet-daemon-topology.c:1026 -#, c-format -msgid "Option `%s' in section `%s' not specified!\n" -msgstr "" - -#: src/topology/gnunet-daemon-topology.c:1039 +#: src/topology/gnunet-daemon-topology.c:1034 #, fuzzy, c-format msgid "Could not read friends list `%s'\n" msgstr "Fehler beim Lesen der Freunde-Liste von `%s'\n" -#: src/topology/gnunet-daemon-topology.c:1045 +#: src/topology/gnunet-daemon-topology.c:1040 #, c-format msgid "Friends file `%s' is empty.\n" msgstr "" -#: src/topology/gnunet-daemon-topology.c:1054 +#: src/topology/gnunet-daemon-topology.c:1049 #, fuzzy, c-format msgid "Failed to read friends list from `%s': out of memory\n" msgstr "Fehler beim Lesen der Freunde-Liste von `%s'\n" -#: src/topology/gnunet-daemon-topology.c:1062 +#: src/topology/gnunet-daemon-topology.c:1057 #, c-format msgid "Failed to read friends list from `%s'\n" msgstr "Fehler beim Lesen der Freunde-Liste von `%s'\n" -#: src/topology/gnunet-daemon-topology.c:1082 +#: src/topology/gnunet-daemon-topology.c:1077 #, fuzzy, c-format msgid "" "Syntax error in topology specification at offset %llu, skipping bytes.\n" msgstr "Syntaxfehler in Topolgieangabe, Bytes werden übersprungen.\n" -#: src/topology/gnunet-daemon-topology.c:1095 +#: src/topology/gnunet-daemon-topology.c:1090 #, fuzzy, c-format msgid "" "Syntax error in topology specification at offset %llu, skipping bytes `%s'.\n" msgstr "Syntaxfehler in Topologieangabe, überspringe Bytes `%s'.\n" -#: src/topology/gnunet-daemon-topology.c:1105 +#: src/topology/gnunet-daemon-topology.c:1100 #, fuzzy, c-format msgid "Found friend `%s' in configuration\n" msgstr " gconfig\tGTK Konfiguration\n" -#: src/topology/gnunet-daemon-topology.c:1111 +#: src/topology/gnunet-daemon-topology.c:1106 #, c-format msgid "Found myself `%s' in friend list (useless, ignored)\n" msgstr "" -#: src/topology/gnunet-daemon-topology.c:1121 +#: src/topology/gnunet-daemon-topology.c:1116 #, fuzzy msgid "# friends in configuration" msgstr " gconfig\tGTK Konfiguration\n" -#: src/topology/gnunet-daemon-topology.c:1127 +#: src/topology/gnunet-daemon-topology.c:1122 msgid "" "Fewer friends specified than required by minimum friend count. Will only " "connect to friends.\n" msgstr "" -#: src/topology/gnunet-daemon-topology.c:1134 +#: src/topology/gnunet-daemon-topology.c:1129 msgid "" "More friendly connections required than target total number of connections.\n" msgstr "" -#: src/topology/gnunet-daemon-topology.c:1169 +#: src/topology/gnunet-daemon-topology.c:1164 #, fuzzy msgid "# HELLO messages received" msgstr "# verschlüsselter PONG Nachrichten empfangen" -#: src/topology/gnunet-daemon-topology.c:1224 +#: src/topology/gnunet-daemon-topology.c:1219 #, fuzzy msgid "# HELLO messages gossipped" msgstr "# ausgehender Nachrichten verworfen" -#: src/topology/gnunet-daemon-topology.c:1363 +#: src/topology/gnunet-daemon-topology.c:1358 msgid "GNUnet topology control (maintaining P2P mesh and F2F constraints)" msgstr "" @@ -4614,11 +4978,6 @@ msgstr "" msgid "Could not read blacklist file `%s'\n" msgstr "Fehler beim Lesen der Freunde-Liste von `%s'\n" -#: src/transport/gnunet-service-transport_blacklist.c:252 -#, c-format -msgid "Blacklist file `%s' is empty.\n" -msgstr "" - #: src/transport/gnunet-service-transport_blacklist.c:263 #, fuzzy, c-format msgid "Failed to read blacklist from `%s'\n" @@ -4647,172 +5006,178 @@ msgid "Found myself `%s' in blacklist (useless, ignored)\n" msgstr "" #: src/transport/gnunet-service-transport_blacklist.c:514 -#: src/transport/gnunet-service-transport_blacklist.c:747 +#: src/transport/gnunet-service-transport_blacklist.c:752 msgid "# disconnects due to blacklist" msgstr "" -#: src/transport/gnunet-service-transport.c:163 +#: src/transport/gnunet-service-transport.c:183 #, fuzzy msgid "# bytes payload discarded due to not connected peer " msgstr "# Knotenankündigungen empfangen" -#: src/transport/gnunet-service-transport.c:237 +#: src/transport/gnunet-service-transport.c:258 #, fuzzy msgid "# bytes total received" msgstr "# gap Anfragen insgesamt empfangen" -#: src/transport/gnunet-service-transport.c:284 +#: src/transport/gnunet-service-transport.c:305 #, fuzzy msgid "# bytes payload received" msgstr "# Bytes entschlüsselt" -#: src/transport/gnunet-service-transport.c:582 -msgid "Transport service is lacking key configuration settings. Exiting.\n" -msgstr "" +#: src/transport/gnunet-service-transport.c:614 +#, fuzzy, c-format +msgid "Transport service could not access hostkey: %s. Exiting.\n" +msgstr "Auf die Namespace Informationen konnte nicht zugegriffen werden.\n" + +#: src/transport/gnunet-service-transport.c:625 +#, fuzzy +msgid "Could not access STATISTICS service. Exiting.\n" +msgstr "Auf die Namespace Informationen konnte nicht zugegriffen werden.\n" -#: src/transport/gnunet-service-transport.c:591 -msgid "Transport service could not access hostkey. Exiting.\n" +#: src/transport/gnunet-service-transport.c:720 +msgid "Transport service is lacking key configuration settings. Exiting.\n" msgstr "" -#: src/transport/gnunet-service-transport_clients.c:352 +#: src/transport/gnunet-service-transport_clients.c:389 #, c-format msgid "Dropping message of type %u and size %u, have %u/%u messages pending\n" msgstr "" -#: src/transport/gnunet-service-transport_clients.c:357 +#: src/transport/gnunet-service-transport_clients.c:394 #, fuzzy msgid "# messages dropped due to slow client" msgstr "# gap Anfragen verworfen: Kollision in RT" -#: src/transport/gnunet-service-transport_clients.c:503 +#: src/transport/gnunet-service-transport_clients.c:546 #, c-format msgid "Rejecting control connection from peer `%s', which is not me!\n" msgstr "" -#: src/transport/gnunet-service-transport_clients.c:631 +#: src/transport/gnunet-service-transport_clients.c:687 msgid "# bytes payload dropped (other peer was not connected)" msgstr "" -#: src/transport/gnunet-service-transport_clients.c:682 +#: src/transport/gnunet-service-transport_clients.c:738 #, fuzzy msgid "# REQUEST CONNECT messages received" msgstr "# verschlüsselter PONG Nachrichten empfangen" -#: src/transport/gnunet-service-transport_hello.c:172 +#: src/transport/gnunet-service-transport_hello.c:175 msgid "# refreshed my HELLO" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:1032 +#: src/transport/gnunet-service-transport_neighbours.c:1227 #, fuzzy msgid "# DISCONNECT messages sent" msgstr "# verschlüsselter PONG Nachrichten empfangen" -#: src/transport/gnunet-service-transport_neighbours.c:1148 -#: src/transport/gnunet-service-transport_neighbours.c:1482 +#: src/transport/gnunet-service-transport_neighbours.c:1357 +#: src/transport/gnunet-service-transport_neighbours.c:1694 #, fuzzy msgid "# bytes in message queue for other peers" msgstr "# Bytes ausgehender Nachrichten verworfen" -#: src/transport/gnunet-service-transport_neighbours.c:1153 +#: src/transport/gnunet-service-transport_neighbours.c:1362 #, fuzzy msgid "# messages transmitted to other peers" msgstr "# Bytes des Typs %d übertragen" -#: src/transport/gnunet-service-transport_neighbours.c:1158 +#: src/transport/gnunet-service-transport_neighbours.c:1367 #, fuzzy msgid "# transmission failures for messages to other peers" msgstr "# Bytes ausgehender Nachrichten verworfen" -#: src/transport/gnunet-service-transport_neighbours.c:1215 +#: src/transport/gnunet-service-transport_neighbours.c:1424 msgid "# messages timed out while in transport queue" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:1254 +#: src/transport/gnunet-service-transport_neighbours.c:1466 #, fuzzy msgid "# keepalives sent" msgstr "# p2p Trace-Antworten gesendet" -#: src/transport/gnunet-service-transport_neighbours.c:1278 +#: src/transport/gnunet-service-transport_neighbours.c:1490 #, fuzzy msgid "# KEEPALIVE messages discarded (peer unknown)" msgstr "# defragmentierter Nachrichten" -#: src/transport/gnunet-service-transport_neighbours.c:1286 +#: src/transport/gnunet-service-transport_neighbours.c:1498 #, fuzzy msgid "# KEEPALIVE messages discarded (no session)" msgstr "# defragmentierter Nachrichten" -#: src/transport/gnunet-service-transport_neighbours.c:1323 +#: src/transport/gnunet-service-transport_neighbours.c:1535 #, fuzzy msgid "# KEEPALIVE_RESPONSE messages discarded (not connected)" msgstr "# defragmentierter Nachrichten" -#: src/transport/gnunet-service-transport_neighbours.c:1332 +#: src/transport/gnunet-service-transport_neighbours.c:1544 #, fuzzy msgid "# KEEPALIVE_RESPONSE messages discarded (not expected)" msgstr "# defragmentierter Nachrichten" -#: src/transport/gnunet-service-transport_neighbours.c:1388 +#: src/transport/gnunet-service-transport_neighbours.c:1600 #, fuzzy msgid "# messages discarded due to lack of neighbour record" msgstr "# defragmentierter Nachrichten" -#: src/transport/gnunet-service-transport_neighbours.c:1422 +#: src/transport/gnunet-service-transport_neighbours.c:1634 #, fuzzy msgid "# bandwidth quota violations by other peers" msgstr "Verfolgt die Bandbreitennutzung von gnunetd" -#: src/transport/gnunet-service-transport_neighbours.c:1438 +#: src/transport/gnunet-service-transport_neighbours.c:1650 msgid "# ms throttling suggested" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:2544 +#: src/transport/gnunet-service-transport_neighbours.c:2802 #, fuzzy msgid "# unexpected CONNECT_ACK messages (no peer)" msgstr "COUNT Nachrichten versenden" -#: src/transport/gnunet-service-transport_neighbours.c:2559 -#: src/transport/gnunet-service-transport_neighbours.c:2585 +#: src/transport/gnunet-service-transport_neighbours.c:2817 +#: src/transport/gnunet-service-transport_neighbours.c:2851 #, fuzzy msgid "# unexpected CONNECT_ACK messages (not ready)" msgstr "COUNT Nachrichten versenden" -#: src/transport/gnunet-service-transport_neighbours.c:2598 +#: src/transport/gnunet-service-transport_neighbours.c:2864 #, fuzzy msgid "# unexpected CONNECT_ACK messages (waiting on ATS)" msgstr "COUNT Nachrichten versenden" -#: src/transport/gnunet-service-transport_neighbours.c:2627 +#: src/transport/gnunet-service-transport_neighbours.c:2897 #, fuzzy msgid "# unexpected CONNECT_ACK messages (disconnecting)" msgstr "COUNT Nachrichten versenden" -#: src/transport/gnunet-service-transport_neighbours.c:2807 +#: src/transport/gnunet-service-transport_neighbours.c:3082 #, fuzzy msgid "# unexpected SESSION ACK messages" msgstr "# verschlüsselter PONG Nachrichten gesendet" -#: src/transport/gnunet-service-transport_neighbours.c:2856 +#: src/transport/gnunet-service-transport_neighbours.c:3137 msgid "# SET QUOTA messages ignored (no such peer)" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:2870 +#: src/transport/gnunet-service-transport_neighbours.c:3151 msgid "# disconnects due to quota of 0" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:2901 +#: src/transport/gnunet-service-transport_neighbours.c:3182 msgid "# disconnect messages ignored (old format)" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:2912 +#: src/transport/gnunet-service-transport_neighbours.c:3193 msgid "# disconnect messages ignored (timestamp)" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:2943 +#: src/transport/gnunet-service-transport_neighbours.c:3224 msgid "# other peer asked to disconnect from us" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:3020 +#: src/transport/gnunet-service-transport_neighbours.c:3319 #, fuzzy msgid "# disconnected from peer upon explicit request" msgstr "# gap Anfragen verworfen: Kollision in RT" @@ -4821,312 +5186,510 @@ msgstr "# gap Anfragen verworfen: Kollision in RT" msgid "Transport service is lacking NEIGHBOUR_LIMIT option.\n" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:414 +#: src/transport/gnunet-service-transport_validation.c:425 msgid "# address records discarded" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:463 +#: src/transport/gnunet-service-transport_validation.c:487 #, c-format msgid "" "Not transmitting `%s' with `%s', message too big (%u bytes!). This should " "not happen.\n" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:512 +#: src/transport/gnunet-service-transport_validation.c:536 #, fuzzy msgid "# PING without HELLO messages sent" msgstr "# Klartext PING Nachrichten gesendet" -#: src/transport/gnunet-service-transport_validation.c:570 +#: src/transport/gnunet-service-transport_validation.c:618 msgid "# address revalidations started" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:805 +#: src/transport/gnunet-service-transport_validation.c:860 #, fuzzy msgid "# PING message for different peer received" msgstr "# PING Nachrichten erstellt" -#: src/transport/gnunet-service-transport_validation.c:840 +#: src/transport/gnunet-service-transport_validation.c:925 #, c-format -msgid "" -"Not confirming PING with address `%s' since I cannot confirm having this " -"address.\n" +msgid "Received a PING message with validation bug from `%s'\n" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:924 +#: src/transport/gnunet-service-transport_validation.c:1054 msgid "# PONGs unicast via reliable transport" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:933 +#: src/transport/gnunet-service-transport_validation.c:1063 msgid "# PONGs multicast to all available addresses" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:1055 +#: src/transport/gnunet-service-transport_validation.c:1188 msgid "# PONGs dropped, no matching pending validation" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:1080 +#: src/transport/gnunet-service-transport_validation.c:1216 msgid "# PONGs dropped, signature expired" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:1136 +#: src/transport/gnunet-service-transport_validation.c:1270 #, fuzzy, c-format msgid "Adding `%s' without addresses for peer `%s'\n" msgstr "Adresse des Knotens `%s' konnte nicht ermittelt werden.\n" -#: src/transport/gnunet-transport.c:260 -msgid "No transport plugins configured, peer will never communicate\n" -msgstr "" +#: src/transport/gnunet-transport.c:266 +#, fuzzy, c-format +msgid "Transmitted %llu bytes/s (%llu bytes in %s)\n" +msgstr "Fehler beim Lesen der Freunde-Liste von `%s'\n" #: src/transport/gnunet-transport.c:273 -#, c-format -msgid "No port configured for plugin `%s', cannot test it\n" -msgstr "" +#, fuzzy, c-format +msgid "Received %llu bytes/s (%llu bytes in %s)\n" +msgstr "GAP hat ungültige Inhalte von `%s' empfangen.\n" -#: src/transport/gnunet-transport.c:323 -#, c-format -msgid "Received %llu bytes/s (%llu bytes in %llu ms)\n" +#: src/transport/gnunet-transport.c:303 +#, fuzzy, c-format +msgid "Failed to connect to `%s'\n" +msgstr "Es konnte keine Verbindung mit gnunetd hergestellt werden.\n" + +#: src/transport/gnunet-transport.c:316 +#, fuzzy, c-format +msgid "Failed to resolve address for peer `%s'\n" +msgstr "Fehler beim Binden an UDP Port %d.\n" + +#: src/transport/gnunet-transport.c:325 +#, fuzzy +msgid "Failed to list connections, timeout occured\n" +msgstr "Es konnte keine Verbindung mit gnunetd hergestellt werden." + +#: src/transport/gnunet-transport.c:429 +msgid "No transport plugins configured, peer will never communicate\n" msgstr "" -#: src/transport/gnunet-transport.c:330 +#: src/transport/gnunet-transport.c:442 #, c-format -msgid "Transmitted %llu bytes/s (%llu bytes in %llu ms)\n" +msgid "No port configured for plugin `%s', cannot test it\n" msgstr "" -#: src/transport/gnunet-transport.c:363 +#: src/transport/gnunet-transport.c:506 #, fuzzy, c-format msgid "Transmitting %u bytes to %s\n" msgstr "Fehler beim Lesen der Freunde-Liste von `%s'\n" -#: src/transport/gnunet-transport.c:383 +#: src/transport/gnunet-transport.c:531 #, fuzzy, c-format -msgid "Connected to %s\n" -msgstr "`%s' hat sich mit `%s' verbunden.\n" +msgid "Successfully connected to `%s'\n" +msgstr "Zugriff verweigert für `%s' bei %s:%d.\n" + +#: src/transport/gnunet-transport.c:553 +#, c-format +msgid "" +"Successfully connected to `%s', starting to send benchmark data in %u Kb " +"blocks\n" +msgstr "" -#: src/transport/gnunet-transport.c:414 +#: src/transport/gnunet-transport.c:588 #, fuzzy, c-format -msgid "Disconnected from %s\n" +msgid "Disconnected from peer `%s' while benchmarking\n" msgstr "`%s' hat sich mit `%s' verbunden.\n" -#: src/transport/gnunet-transport.c:443 +#: src/transport/gnunet-transport.c:664 #, fuzzy, c-format msgid "Received %u bytes from %s\n" msgstr "GAP hat ungültige Inhalte von `%s' empfangen.\n" -#: src/transport/gnunet-transport.c:466 +#: src/transport/gnunet-transport.c:687 #, fuzzy, c-format msgid "Peer `%s': %s %s\n" msgstr "Ich bin Peer `%s'.\n" -#: src/transport/gnunet-transport.c:473 +#: src/transport/gnunet-transport.c:702 #, c-format msgid "Peer `%s': %s \n" msgstr "" -#: src/transport/gnunet-transport.c:501 +#: src/transport/gnunet-transport.c:766 #, fuzzy, c-format msgid "Peer `%s' disconnected\n" msgstr "# verbundener Knoten" -#: src/transport/gnunet-transport.c:569 -#, fuzzy, c-format -msgid "Failed to parse peer identity `%s'\n" -msgstr "Fehler beim Lesen der Freunde-Liste von `%s'\n" +#: src/transport/gnunet-transport.c:794 +#, fuzzy +msgid "Failed to send connect request to transport service\n" +msgstr "Der Transportdienst auf Port %d konnte nicht gestartet werden.\n" + +#: src/transport/gnunet-transport.c:828 +#, c-format +msgid "" +"Multiple operations given. Please choose only one operation: %s, %s, %s, %s, " +"%s, %s\n" +msgstr "" + +#: src/transport/gnunet-transport.c:834 +#, c-format +msgid "" +"No operation given. Please choose one operation: %s, %s, %s, %s, %s, %s\n" +msgstr "" + +#: src/transport/gnunet-transport.c:854 src/transport/gnunet-transport.c:884 +#: src/transport/gnunet-transport.c:906 src/transport/gnunet-transport.c:945 +#, fuzzy +msgid "Failed to connect to transport service\n" +msgstr "Der Transportdienst auf Port %d konnte nicht gestartet werden.\n" + +#: src/transport/gnunet-transport.c:861 src/transport/gnunet-transport.c:891 +#, fuzzy +msgid "Failed to send request to transport service\n" +msgstr "Der Transportdienst auf Port %d konnte nicht gestartet werden.\n" -#: src/transport/gnunet-transport.c:618 -msgid "measure how fast we are receiving data (until CTRL-C)" +#: src/transport/gnunet-transport.c:911 +msgid "Starting to receive benchmark data\n" msgstr "" -#: src/transport/gnunet-transport.c:621 +#: src/transport/gnunet-transport.c:996 +msgid "measure how fast we are receiving data from all peers (until CTRL-C)" +msgstr "" + +#: src/transport/gnunet-transport.c:999 #, fuzzy -msgid "try to connect to the given peer" +msgid "connect to a peer" msgstr "Es konnte keine Verbindung mit gnunetd hergestellt werden.\n" -#: src/transport/gnunet-transport.c:624 +#: src/transport/gnunet-transport.c:1002 #, fuzzy msgid "provide information about all current connections (once)" msgstr "Informationen über andere GNUnet Knoten ausgeben." -#: src/transport/gnunet-transport.c:627 +#: src/transport/gnunet-transport.c:1008 #, fuzzy -msgid "provide information about all current connections (continuously)" +msgid "" +"provide information about all connects and disconnect events (continuously)" msgstr "Informationen über andere GNUnet Knoten ausgeben." -#: src/transport/gnunet-transport.c:630 +#: src/transport/gnunet-transport.c:1011 #, fuzzy msgid "do not resolve hostnames" msgstr "Fehler beim Lesen der Freunde-Liste von `%s'\n" -#: src/transport/gnunet-transport.c:634 +#: src/transport/gnunet-transport.c:1014 +msgid "peer identity" +msgstr "" + +#: src/transport/gnunet-transport.c:1018 msgid "send data for benchmarking to the other peer (until CTRL-C)" msgstr "" -#: src/transport/gnunet-transport.c:637 +#: src/transport/gnunet-transport.c:1021 msgid "test transport configuration (involves external server)" msgstr "" -#: src/transport/gnunet-transport.c:645 +#: src/transport/gnunet-transport.c:1032 #, fuzzy msgid "Direct access to transport service." msgstr "Der Transportdienst auf Port %d konnte nicht gestartet werden.\n" -#: src/transport/plugin_transport_http.c:1100 +#: src/transport/plugin_transport_http.c:817 +#: src/transport/plugin_transport_http_server.c:2556 msgid "Disabling IPv6 since it is not supported on this system!\n" msgstr "" -#: src/transport/plugin_transport_http.c:1149 +#: src/transport/plugin_transport_http.c:866 +#: src/transport/plugin_transport_http_server.c:2324 #, fuzzy msgid "Require valid port number for service in configuration!\n" msgstr "In der Konfigurationsdatei wurden keine Anwendungen definiert!\n" -#: src/transport/plugin_transport_http.c:1174 src/util/service.c:1036 +#: src/transport/plugin_transport_http.c:898 +#: src/transport/plugin_transport_http_server.c:2356 src/util/service.c:1053 #, fuzzy, c-format msgid "Failed to resolve `%s': %s\n" msgstr "Datei wurde als `%s' gespeichert.\n" -#: src/transport/plugin_transport_http.c:1191 src/util/service.c:1053 +#: src/transport/plugin_transport_http.c:915 +#: src/transport/plugin_transport_http_server.c:2373 src/util/service.c:1070 #, fuzzy, c-format msgid "Failed to find %saddress for `%s'.\n" msgstr "Fehler beim Binden an UDP Port %d.\n" -#: src/transport/plugin_transport_http.c:1296 +#: src/transport/plugin_transport_http.c:1020 +#: src/transport/plugin_transport_http_server.c:2484 #, c-format msgid "Found %u addresses to report to NAT service\n" msgstr "" -#: src/transport/plugin_transport_http.c:1309 -#, c-format -msgid "FREEING %s\n" -msgstr "" - -#: src/transport/plugin_transport_http.c:1386 +#: src/transport/plugin_transport_http.c:1133 +#: src/transport/plugin_transport_http_server.c:2652 #, fuzzy msgid "Neither IPv4 nor IPv6 are enabled! Fix in configuration\n" msgstr "Netzwerkbekanntmachungen wurden per Konfiguration deaktiviert!\n" -#: src/transport/plugin_transport_http.c:1399 +#: src/transport/plugin_transport_http.c:1146 +#: src/transport/plugin_transport_http_server.c:2663 #, fuzzy msgid "Port is required! Fix in configuration\n" msgstr " gconfig\tGTK Konfiguration\n" -#: src/transport/plugin_transport_http.c:1410 +#: src/transport/plugin_transport_http.c:1157 msgid "Port 0, client only mode\n" msgstr "" -#: src/transport/plugin_transport_http.c:1430 +#: src/transport/plugin_transport_http.c:1177 #, c-format msgid "" "Specific IPv4 address `%s' for plugin %s in configuration file is invalid! " "Binding to all addresses!\n" msgstr "" -#: src/transport/plugin_transport_http.c:1460 +#: src/transport/plugin_transport_http.c:1206 #, c-format msgid "" "Specific IPv6 address `%s' for plugin %s in configuration file is invalid! " "Binding to all addresses!\n" msgstr "" -#: src/transport/plugin_transport_http_client.c:624 -#, c-format -msgid "Could not initialize curl multi handle, failed to start %s plugin!\n" -msgstr "" +#: src/transport/plugin_transport_http.c:1223 +#: src/transport/plugin_transport_http_server.c:2745 +#, fuzzy, c-format +msgid "Using external hostname `%s'\n" +msgstr "Collection `%s' begonnen.\n" + +#: src/transport/plugin_transport_http.c:1228 +msgid "No external hostname configured\n" +msgstr "" + +#: src/transport/plugin_transport_http_client.c:1516 +#, c-format +msgid "Could not initialize curl multi handle, failed to start %s plugin!\n" +msgstr "" + +#: src/transport/plugin_transport_http_client.c:1647 +#: src/transport/plugin_transport_http_server.c:2869 +#, fuzzy, c-format +msgid "Shutting down plugin `%s'\n" +msgstr "Teste Transport(e) %s\n" + +#: src/transport/plugin_transport_http_client.c:1672 +#: src/transport/plugin_transport_http_server.c:2928 +#, fuzzy, c-format +msgid "Shutdown for plugin `%s' complete\n" +msgstr "" +"Upload von `%s' komplett, derzeitige durchschnittliche Geschwindigkeit " +"beträgt %8.3f KB/s.\n" -#: src/transport/plugin_transport_http_server.c:178 +#: src/transport/plugin_transport_http_client.c:1700 +#: src/transport/plugin_transport_http_server.c:2775 +#, fuzzy, c-format +msgid "Maximum number of connections is %u\n" +msgstr "Maximale Anzahl an Chat Clients erreicht.\n" + +#: src/transport/plugin_transport_http_server.c:1342 +#, c-format +msgid "" +"Access from connection %p (%u of %u) for `%s' `%s' url `%s' with upload data " +"size %u\n" +msgstr "" + +#: src/transport/plugin_transport_http_server.c:1603 +#, c-format +msgid "Accepting connection (%u of %u) from `%s'\n" +msgstr "" + +#: src/transport/plugin_transport_http_server.c:1611 +#, c-format +msgid "" +"Server reached maximum number connections (%u), rejecting new connection\n" +msgstr "" + +#: src/transport/plugin_transport_http_server.c:1912 msgid "" "Could not create a new TLS certificate, program `gnunet-transport-" "certificate-creation' could not be started!\n" msgstr "" -#: src/transport/plugin_transport_http_server.c:202 +#: src/transport/plugin_transport_http_server.c:1936 msgid "No usable TLS certificate found and creating one failed!\n" msgstr "" -#: src/transport/plugin_transport_tcp.c:591 +#: src/transport/plugin_transport_http_server.c:2631 +#, c-format +msgid "IPv4 support is %s\n" +msgstr "" + +#: src/transport/plugin_transport_http_server.c:2645 +#, c-format +msgid "IPv6 support is %s\n" +msgstr "" + +#: src/transport/plugin_transport_http_server.c:2670 +#, fuzzy, c-format +msgid "Using port %u\n" +msgstr "Teste Transport(e) %s\n" + +#: src/transport/plugin_transport_http_server.c:2685 +#, fuzzy, c-format +msgid "Specific IPv4 address `%s' in configuration file is invalid!\n" +msgstr "" +"Sie müssen für `%s' in der Sektion `%s' der Konfigurationsdatei eine " +"positive Zahl angeben.\n" + +#: src/transport/plugin_transport_http_server.c:2695 +#, fuzzy, c-format +msgid "Binding to IPv4 address %s\n" +msgstr "Ungültiger Parameter: `%s'\n" + +#: src/transport/plugin_transport_http_server.c:2716 +#, fuzzy, c-format +msgid "Specific IPv6 address `%s' in configuration file is invalid!\n" +msgstr "" +"Sie müssen für `%s' in der Sektion `%s' der Konfigurationsdatei eine " +"positive Zahl angeben.\n" + +#: src/transport/plugin_transport_http_server.c:2726 +#, fuzzy, c-format +msgid "Binding to IPv6 address %s\n" +msgstr "Ungültiger Parameter: `%s'\n" + +#: src/transport/plugin_transport_http_server.c:2761 +#, fuzzy, c-format +msgid "Notifying transport only about hostname `%s'\n" +msgstr "Fehler beim Lesen der Freunde-Liste von `%s'\n" + +#: src/transport/plugin_transport_smtp.c:370 +#, fuzzy, c-format +msgid "Received malformed message via %s. Ignored.\n" +msgstr "" +"Es wurde eine ungültige Nachricht per SMTP empfangen (ungültige Größe).\n" + +#: src/transport/plugin_transport_smtp.c:457 +#, fuzzy +msgid "SMTP filter string to invalid, lacks ': '\n" +msgstr "SMTP Filterstring zu lang, wurde auf `%s' abgeschnitten\n" + +#: src/transport/plugin_transport_smtp.c:466 +#, c-format +msgid "SMTP filter string to long, capped to `%s'\n" +msgstr "SMTP Filterstring zu lang, wurde auf `%s' abgeschnitten\n" + +#: src/transport/plugin_transport_smtp.c:561 +#: src/transport/plugin_transport_smtp.c:571 +#: src/transport/plugin_transport_smtp.c:584 +#: src/transport/plugin_transport_smtp.c:603 +#: src/transport/plugin_transport_smtp.c:626 +#: src/transport/plugin_transport_smtp.c:634 +#: src/transport/plugin_transport_smtp.c:647 +#: src/transport/plugin_transport_smtp.c:658 +#, fuzzy, c-format +msgid "SMTP: `%s' failed: %s.\n" +msgstr "`%s' schlug fehl: %s\n" + +#: src/transport/plugin_transport_smtp.c:799 +#, fuzzy +msgid "No email-address specified, can not start SMTP transport.\n" +msgstr "" +"Kein Filter für E-Mail angegeben, es kann keine Bekanntmachung erstellt " +"werden.\n" + +#: src/transport/plugin_transport_smtp.c:811 +#, fuzzy +msgid "# bytes received via SMTP" +msgstr "# Bytes empfangen über TCP" + +#: src/transport/plugin_transport_smtp.c:812 +#, fuzzy +msgid "# bytes sent via SMTP" +msgstr "# Bytes gesendet über TCP" + +#: src/transport/plugin_transport_smtp.c:814 +#, fuzzy +msgid "# bytes dropped by SMTP (outgoing)" +msgstr "# Bytes verworfen von TCP (ausgehend)" + +#: src/transport/plugin_transport_tcp.c:595 #, c-format msgid "Unexpected address length: %u bytes\n" msgstr "" -#: src/transport/plugin_transport_tcp.c:767 -#: src/transport/plugin_transport_tcp.c:856 -#: src/transport/plugin_transport_tcp.c:906 -#: src/transport/plugin_transport_tcp.c:992 -#: src/transport/plugin_transport_tcp.c:1086 -#: src/transport/plugin_transport_tcp.c:1103 +#: src/transport/plugin_transport_tcp.c:771 +#: src/transport/plugin_transport_tcp.c:860 +#: src/transport/plugin_transport_tcp.c:910 +#: src/transport/plugin_transport_tcp.c:996 +#: src/transport/plugin_transport_tcp.c:1139 +#: src/transport/plugin_transport_tcp.c:1156 #, fuzzy msgid "# bytes currently in TCP buffers" msgstr "# Bytes gesendet über TCP" -#: src/transport/plugin_transport_tcp.c:774 -#: src/transport/plugin_transport_tcp.c:963 -#: src/transport/plugin_transport_tcp.c:1761 -#: src/transport/plugin_transport_tcp.c:2390 +#: src/transport/plugin_transport_tcp.c:778 +#: src/transport/plugin_transport_tcp.c:967 +#: src/transport/plugin_transport_tcp.c:1826 +#: src/transport/plugin_transport_tcp.c:2462 #, fuzzy msgid "# TCP sessions active" msgstr "# Sitzungsschlüssel akzeptiert" -#: src/transport/plugin_transport_tcp.c:860 +#: src/transport/plugin_transport_tcp.c:864 #, fuzzy msgid "# bytes discarded by TCP (timeout)" msgstr "# Bytes verworfen von TCP (ausgehend)" -#: src/transport/plugin_transport_tcp.c:909 +#: src/transport/plugin_transport_tcp.c:913 #, fuzzy msgid "# bytes transmitted via TCP" msgstr "# Bytes des Typs %d übertragen" -#: src/transport/plugin_transport_tcp.c:996 +#: src/transport/plugin_transport_tcp.c:1000 #, fuzzy msgid "# bytes discarded by TCP (disconnect)" msgstr "# Bytes verworfen von TCP (ausgehend)" -#: src/transport/plugin_transport_tcp.c:1290 +#: src/transport/plugin_transport_tcp.c:1113 +#, c-format +msgid "Trying to send with invalid session %p\n" +msgstr "" + +#: src/transport/plugin_transport_tcp.c:1349 #, c-format msgid "Address of unexpected length: %u\n" msgstr "" -#: src/transport/plugin_transport_tcp.c:1401 +#: src/transport/plugin_transport_tcp.c:1466 msgid "# transport-service disconnect requests for TCP" msgstr "" -#: src/transport/plugin_transport_tcp.c:1802 +#: src/transport/plugin_transport_tcp.c:1867 #, fuzzy msgid "# TCP WELCOME messages received" msgstr "# verschlüsselter PONG Nachrichten empfangen" -#: src/transport/plugin_transport_tcp.c:1973 +#: src/transport/plugin_transport_tcp.c:2046 msgid "# bytes received via TCP" msgstr "# Bytes empfangen über TCP" -#: src/transport/plugin_transport_tcp.c:2043 +#: src/transport/plugin_transport_tcp.c:2124 msgid "# network-level TCP disconnect events" msgstr "" -#: src/transport/plugin_transport_tcp.c:2279 src/util/service.c:940 +#: src/transport/plugin_transport_tcp.c:2350 src/util/service.c:948 +#: src/util/service.c:954 #, c-format msgid "Require valid port number for service `%s' in configuration!\n" msgstr "" -#: src/transport/plugin_transport_tcp.c:2293 +#: src/transport/plugin_transport_tcp.c:2364 #, fuzzy msgid "Failed to start service.\n" msgstr "Fehler beim Starten der Collection.\n" -#: src/transport/plugin_transport_tcp.c:2355 -#, fuzzy, c-format -msgid "Failed to find option %s in section %s!\n" -msgstr "Fehler beim Binden an UDP Port %d.\n" - -#: src/transport/plugin_transport_tcp.c:2378 +#: src/transport/plugin_transport_tcp.c:2450 #, fuzzy, c-format msgid "TCP transport listening on port %llu\n" msgstr "Der Transportdienst auf Port %d konnte nicht gestartet werden.\n" -#: src/transport/plugin_transport_tcp.c:2382 +#: src/transport/plugin_transport_tcp.c:2454 msgid "TCP transport not listening on any port (client only)\n" msgstr "" -#: src/transport/plugin_transport_tcp.c:2386 +#: src/transport/plugin_transport_tcp.c:2458 #, c-format msgid "TCP transport advertises itself as being on port %llu\n" msgstr "" @@ -5141,129 +5704,132 @@ msgstr "# verschlüsselter PONG Nachrichten empfangen" msgid "# IPv4 broadcast HELLO beacons received via udp" msgstr "# verschlüsselter PONG Nachrichten empfangen" -#: src/transport/plugin_transport_udp_broadcasting.c:367 +#: src/transport/plugin_transport_udp_broadcasting.c:394 #, c-format msgid "Failed to set IPv4 broadcast option for broadcast socket on port %d\n" msgstr "" -#: src/transport/plugin_transport_udp.c:1894 +#: src/transport/plugin_transport_udp.c:2517 +#, c-format +msgid "" +"UDP could not transmit message to `%s': Network seems down, please check " +"your network configuration\n" +msgstr "" + +#: src/transport/plugin_transport_udp.c:2531 #, c-format msgid "" -"UDP could not message to `%s': `%s'. Please check your network configuration " -"and disable IPv6 if your connection does not have a global IPv6 address\n" +"UDP could not transmit message to `%s': Please check your network " +"configuration and disable IPv6 if your connection does not have a global " +"IPv6 address\n" msgstr "" -#: src/transport/plugin_transport_udp.c:2138 +#: src/transport/plugin_transport_udp.c:2772 #, fuzzy msgid "Failed to open UDP sockets\n" msgstr "Fehler beim Binden an UDP6 Port %d.\n" -#: src/transport/plugin_transport_udp.c:2306 +#: src/transport/plugin_transport_udp.c:2848 #, c-format msgid "Given `%s' option is out of range: %llu > %u\n" msgstr "" -#: src/transport/plugin_transport_udp.c:2349 +#: src/transport/plugin_transport_udp.c:2891 #, fuzzy, c-format msgid "Invalid IPv6 address: `%s'\n" msgstr "Ungültiger Parameter: `%s'\n" -#: src/transport/plugin_transport_unix.c:1356 +#: src/transport/plugin_transport_unix.c:1357 #, fuzzy msgid "Failed to open UNIX sockets\n" msgstr "Datei wurde als `%s' gespeichert.\n" -#: src/transport/plugin_transport_wlan.c:561 +#: src/transport/plugin_transport_wlan.c:580 msgid "# WLAN ACKs sent" msgstr "" -#: src/transport/plugin_transport_wlan.c:580 +#: src/transport/plugin_transport_wlan.c:599 #, fuzzy msgid "# WLAN messages defragmented" msgstr "# defragmentierter Nachrichten" -#: src/transport/plugin_transport_wlan.c:626 -#: src/transport/plugin_transport_wlan.c:676 -#: src/transport/plugin_transport_wlan.c:1696 +#: src/transport/plugin_transport_wlan.c:645 +#: src/transport/plugin_transport_wlan.c:695 +#: src/transport/plugin_transport_wlan.c:1758 #, fuzzy msgid "# WLAN sessions allocated" msgstr "# Sitzungsschlüssel akzeptiert" -#: src/transport/plugin_transport_wlan.c:749 +#: src/transport/plugin_transport_wlan.c:770 #, fuzzy msgid "# WLAN message fragments sent" msgstr "# fragmentierter Nachrichten" -#: src/transport/plugin_transport_wlan.c:767 +#: src/transport/plugin_transport_wlan.c:794 msgid "# WLAN messages pending (with fragmentation)" msgstr "" -#: src/transport/plugin_transport_wlan.c:867 -#: src/transport/plugin_transport_wlan.c:948 -#: src/transport/plugin_transport_wlan.c:1698 +#: src/transport/plugin_transport_wlan.c:902 +#: src/transport/plugin_transport_wlan.c:987 +#: src/transport/plugin_transport_wlan.c:1760 #, fuzzy msgid "# WLAN MAC endpoints allocated" msgstr "# Client Trace-Anfragen empfangen" -#: src/transport/plugin_transport_wlan.c:1119 +#: src/transport/plugin_transport_wlan.c:1169 #, fuzzy msgid "# HELLO messages received via WLAN" msgstr "# verschlüsselter PONG Nachrichten empfangen" -#: src/transport/plugin_transport_wlan.c:1140 +#: src/transport/plugin_transport_wlan.c:1190 #, fuzzy msgid "# fragments received via WLAN" msgstr "# verworfener Nachrichten" -#: src/transport/plugin_transport_wlan.c:1150 +#: src/transport/plugin_transport_wlan.c:1200 #, fuzzy msgid "# ACKs received via WLAN" msgstr "# Bytes empfangen über TCP" -#: src/transport/plugin_transport_wlan.c:1207 +#: src/transport/plugin_transport_wlan.c:1257 #, fuzzy msgid "# WLAN DATA messages discarded due to CRC32 error" msgstr "# defragmentierter Nachrichten" -#: src/transport/plugin_transport_wlan.c:1306 +#: src/transport/plugin_transport_wlan.c:1358 #, fuzzy msgid "# DATA messages received via WLAN" msgstr "# verschlüsselter PONG Nachrichten empfangen" -#: src/transport/plugin_transport_wlan.c:1341 +#: src/transport/plugin_transport_wlan.c:1393 #, fuzzy msgid "# WLAN DATA messages processed" msgstr "# verschlüsselter PONG Nachrichten empfangen" -#: src/transport/plugin_transport_wlan.c:1402 +#: src/transport/plugin_transport_wlan.c:1454 #, fuzzy msgid "# HELLO beacons sent via WLAN" msgstr "# Bytes gesendet über UDP" -#: src/transport/plugin_transport_wlan.c:1511 +#: src/transport/plugin_transport_wlan.c:1563 msgid "WLAN address with invalid size encountered\n" msgstr "" -#: src/transport/plugin_transport_wlan.c:1668 -#, fuzzy, c-format -msgid "Invalid configuration option `%s' in section `%s'\n" -msgstr "Konfigurationsdatei `%s' wurde erzeugt.\n" - -#: src/transport/plugin_transport_wlan.c:1677 +#: src/transport/plugin_transport_wlan.c:1739 #, c-format msgid "Helper binary `%s' not SUID, cannot run WLAN transport\n" msgstr "" -#: src/transport/plugin_transport_wlan.c:1687 -#, fuzzy, c-format -msgid "Missing configuration option `%s' in section `%s'\n" -msgstr "Konfigurationsdatei `%s' wurde erzeugt.\n" - -#: src/transport/transport_api.c:570 +#: src/transport/transport_api.c:659 #, fuzzy, c-format msgid "Received unexpected message of type %u in %s:%u\n" msgstr "Es wurde eine unbekannte Testbed Nachricht des Typs %u empfangen.\n" +#: src/transport/transport-testing.c:586 +#, fuzzy +msgid "Failed to initialize testing library!\n" +msgstr "SQLite Datenbank konnte nicht initialisiert werden.\n" + #: src/util/bio.c:136 src/util/bio.c:142 #, fuzzy, c-format msgid "Error reading `%s': %s" @@ -5294,263 +5860,318 @@ msgstr "" msgid "Metadata `%s' failed to deserialize" msgstr "" -#: src/util/client.c:359 +#: src/util/client.c:276 src/util/client.c:753 src/util/service.c:984 +#, c-format +msgid "UNIXPATH `%s' too long, maximum length is %llu\n" +msgstr "" + +#: src/util/client.c:280 src/util/client.c:757 src/util/service.c:988 +#, fuzzy, c-format +msgid "Using `%s' instead\n" +msgstr "%s: Option `%s' ist mehrdeutig\n" + +#: src/util/client.c:371 #, c-format msgid "" "Could not determine valid hostname and port for service `%s' from " "configuration.\n" msgstr "" -#: src/util/client.c:367 +#: src/util/client.c:379 #, c-format msgid "Need a non-empty hostname for service `%s'.\n" msgstr "" -#: src/util/client.c:685 +#: src/util/client.c:698 msgid "Failure to transmit TEST request.\n" msgstr "" -#: src/util/client.c:740 src/util/service.c:970 -#, c-format -msgid "UNIXPATH `%s' too long, maximum length is %llu\n" -msgstr "" - -#: src/util/client.c:882 +#: src/util/client.c:898 #, fuzzy, c-format msgid "Could not connect to service `%s', must not be running.\n" msgstr "Verbindung zu gnunetd konnte nicht hergestellt werden.\n" -#: src/util/client.c:896 +#: src/util/client.c:912 #, fuzzy, c-format msgid "Failure to transmit request to service `%s'\n" msgstr "Fehler beim Senden einer `%s' Anfrage an den SMTP Server.\n" -#: src/util/client.c:1149 +#: src/util/client.c:1177 msgid "Could not submit request, not expecting to receive a response.\n" msgstr "" -#: src/util/common_logging.c:239 src/util/common_logging.c:890 +#: src/util/common_logging.c:258 src/util/common_logging.c:1007 msgid "DEBUG" msgstr "DEBUG" -#: src/util/common_logging.c:241 src/util/common_logging.c:888 +#: src/util/common_logging.c:260 src/util/common_logging.c:1005 msgid "INFO" msgstr "INFO" -#: src/util/common_logging.c:243 src/util/common_logging.c:886 +#: src/util/common_logging.c:262 src/util/common_logging.c:1003 msgid "WARNING" msgstr "WARNUNG" -#: src/util/common_logging.c:245 src/util/common_logging.c:884 +#: src/util/common_logging.c:264 src/util/common_logging.c:1001 msgid "ERROR" msgstr "FEHLER" -#: src/util/common_logging.c:247 src/util/common_logging.c:892 +#: src/util/common_logging.c:266 src/util/common_logging.c:1009 msgid "NONE" msgstr "" -#: src/util/common_logging.c:610 +#: src/util/common_logging.c:395 #, fuzzy, c-format msgid "Failed to create or access directory for log file `%s'\n" msgstr "Konfigurationsdatei `%s' konnte nicht geparst werden.\n" -#: src/util/common_logging.c:725 +#: src/util/common_logging.c:819 #, c-format msgid "Message `%.*s' repeated %u times in the last %s\n" msgstr "" -#: src/util/common_logging.c:893 +#: src/util/common_logging.c:1010 msgid "INVALID" msgstr "" -#: src/util/common_logging.c:992 +#: src/util/common_logging.c:1149 #, fuzzy msgid "unknown address" msgstr "Unbekannter Fehler" -#: src/util/common_logging.c:1030 +#: src/util/common_logging.c:1187 #, fuzzy msgid "invalid address" msgstr "Ungültige Parameter: " -#: src/util/configuration.c:244 +#: src/util/common_logging.c:1205 +#, fuzzy, c-format +msgid "Configuration fails to specify option `%s' in section `%s'!\n" +msgstr "" +"Die Konfigurationsdatei muss in der Sektion `%s' unter `%s' ein Verzeichnis " +"angeben, in dem FS Daten gespeichert werden.\n" + +#: src/util/common_logging.c:1226 +#, fuzzy, c-format +msgid "" +"Configuration specifies invalid value for option `%s' in section `%s': %s\n" +msgstr "" +"Die Konfigurationsdatei muss in der Sektion `%s' unter `%s' ein Verzeichnis " +"angeben, in dem FS Daten gespeichert werden.\n" + +#: src/util/configuration.c:291 #, fuzzy, c-format -msgid "Syntax error in configuration file `%s' at line %u.\n" +msgid "Syntax error while deserializing in line %u\n" msgstr "Syntaxfehler in Konfigurationsdatei `%s' in Zeile %d.\n" -#: src/util/configuration.c:816 +#: src/util/configuration.c:998 #, c-format msgid "" "Configuration value '%s' for '%s' in section '%s' is not in set of legal " "choices\n" msgstr "" -#: src/util/connection.c:420 +#: src/util/connection.c:427 #, fuzzy, c-format msgid "Access denied to `%s'\n" msgstr "Zugriff verweigert für `%s' bei %s:%d.\n" -#: src/util/connection.c:435 +#: src/util/connection.c:442 #, c-format msgid "Accepting connection from `%s': %p\n" msgstr "" -#: src/util/connection.c:550 +#: src/util/connection.c:557 #, fuzzy, c-format msgid "" "Failed to establish TCP connection to `%s:%u', no further addresses to try.\n" msgstr "Fehler beim Aufbauen einer Verbindung mit gnunetd.\n" -#: src/util/connection.c:739 src/util/connection.c:909 +#: src/util/connection.c:755 src/util/connection.c:922 #, fuzzy, c-format msgid "Trying to connect to `%s' (%p)\n" msgstr "Es konnte keine Verbindung mit gnunetd hergestellt werden.\n" -#: src/util/connection.c:748 -#, fuzzy, c-format -msgid "Failed to connect to `%s' (%p)\n" -msgstr "Es konnte keine Verbindung mit gnunetd hergestellt werden.\n" - -#: src/util/connection.c:900 +#: src/util/connection.c:913 #, fuzzy, c-format msgid "Attempt to connect to `%s' failed\n" msgstr "Es konnte keine Verbindung mit gnunetd hergestellt werden.\n" -#: src/util/container_bloomfilter.c:510 +#: src/util/container_bloomfilter.c:518 #, c-format msgid "" "Size of file on disk is incorrect for this Bloom filter (want %llu, have " "%llu)\n" msgstr "" -#: src/util/crypto_random.c:280 -#, c-format -msgid "Starting `%s' process to generate entropy\n" -msgstr "" +#: src/util/crypto_ecc.c:441 +#, fuzzy, c-format +msgid "" +"File `%s' does not contain a valid private key (too long, %llu bytes). " +"Deleting it.\n" +msgstr "Die Datei `%s' enthält kein Pseudonym.\n" -#: src/util/crypto_random.c:309 -#, c-format -msgid "libgcrypt has not the expected version (version %s is required).\n" -msgstr "" -"libgcrypt hat nicht die erwartete Version (Version %s wird vorausgesetzt).\n" +#: src/util/crypto_ecc.c:456 src/util/crypto_rsa.c:660 +#, fuzzy, c-format +msgid "" +"File `%s' does not contain a valid private key (failed decode, %llu bytes). " +"Deleting it.\n" +msgstr "Die Datei `%s' enthält kein Pseudonym.\n" -#: src/util/crypto_rsa.c:661 src/util/crypto_rsa.c:708 +#: src/util/crypto_ecc.c:552 src/util/crypto_ecc.c:596 +#: src/util/crypto_rsa.c:757 src/util/crypto_rsa.c:801 #, fuzzy, c-format -msgid "Could not aquire lock on file `%s': %s...\n" +msgid "Could not acquire lock on file `%s': %s...\n" msgstr "PID konnte nicht in Datei `%s' geschrieben werden: %s.\n" -#: src/util/crypto_rsa.c:666 +#: src/util/crypto_ecc.c:557 src/util/crypto_rsa.c:762 #, fuzzy msgid "Creating a new private key. This may take a while.\n" msgstr "Ein neuer Hostkey wird erzeugt (dies kann eine Weile dauern).\n" -#: src/util/crypto_rsa.c:684 -#, c-format -msgid "I am host `%s'. Stored new private key in `%s'.\n" -msgstr "" - -#: src/util/crypto_rsa.c:712 src/util/crypto_rsa.c:748 -msgid "This may be ok if someone is currently generating a hostkey.\n" +#: src/util/crypto_ecc.c:600 src/util/crypto_rsa.c:805 +#: src/util/crypto_rsa.c:841 +msgid "This may be ok if someone is currently generating a private key.\n" msgstr "" -#: src/util/crypto_rsa.c:743 +#: src/util/crypto_ecc.c:631 src/util/crypto_rsa.c:836 #, c-format msgid "" -"When trying to read hostkey file `%s' I found %u bytes but I need at least " -"%u.\n" +"When trying to read key file `%s' I found %u bytes but I need at least %u.\n" +msgstr "" + +#: src/util/crypto_ecc.c:636 +msgid "This may be ok if someone is currently generating a key.\n" msgstr "" -#: src/util/crypto_rsa.c:763 +#: src/util/crypto_ecc.c:651 src/util/crypto_rsa.c:856 #, fuzzy, c-format msgid "File `%s' does not contain a valid private key. Deleting it.\n" msgstr "Die Datei `%s' enthält kein Pseudonym.\n" -#: src/util/crypto_rsa.c:781 +#: src/util/crypto_ecc.c:773 src/util/crypto_rsa.c:941 +msgid "interrupted by shutdown" +msgstr "" + +#: src/util/crypto_ecc.c:784 +#, fuzzy +msgid "gnunet-ecc failed" +msgstr "gnunet-update ausführen" + +#: src/util/crypto_ecc.c:979 +#, fuzzy, c-format +msgid "ECC signing failed at %s:%d: %s\n" +msgstr "`%s' schlug fehl bei %s:%d mit dem Fehler: `%s'.\n" + +#: src/util/crypto_ecc.c:1047 +#, fuzzy, c-format +msgid "ECC signature verification failed at %s:%d: %s\n" +msgstr "RSA Signaturüberprüfung fehlgeschlagen bei %s:%d: %s\n" + +#: src/util/crypto_random.c:313 +#, c-format +msgid "Starting `%s' process to generate entropy\n" +msgstr "" + +#: src/util/crypto_random.c:342 +#, c-format +msgid "libgcrypt has not the expected version (version %s is required).\n" +msgstr "" +"libgcrypt hat nicht die erwartete Version (Version %s wird vorausgesetzt).\n" + +#: src/util/crypto_rsa.c:644 #, fuzzy, c-format -msgid "I am host `%s'. Read private key from `%s'.\n" -msgstr "Aufruf von `%s' mit Schlüssel `%s'.\n" +msgid "" +"File `%s' does not contain a valid private key (too long, %llu bytes). " +"Renaming it.\n" +msgstr "Die Datei `%s' enthält kein Pseudonym.\n" + +#: src/util/crypto_rsa.c:952 +#, fuzzy +msgid "gnunet-rsa failed" +msgstr "gnunet-update ausführen" -#: src/util/crypto_rsa.c:1032 +#: src/util/crypto_rsa.c:1343 #, c-format msgid "RSA signature verification failed at %s:%d: %s\n" msgstr "RSA Signaturüberprüfung fehlgeschlagen bei %s:%d: %s\n" -#: src/util/disk.c:498 +#: src/util/disk.c:601 #, fuzzy, c-format msgid "`%s' failed for drive `%S': %u\n" msgstr "`%s' fehlgeschlagen für Laufwerk %s: %u\n" -#: src/util/disk.c:1062 +#: src/util/disk.c:1205 #, fuzzy, c-format msgid "Expected `%s' to be a directory!\n" msgstr "`%s' erwartet, dass `%s' ein Verzeichnis ist!\n" -#: src/util/disk.c:1416 src/util/service.c:1650 +#: src/util/disk.c:1559 src/util/service.c:1669 #, fuzzy, c-format msgid "Cannot obtain information about user `%s': %s\n" msgstr "Fehler beim Speichern der Konfigurationsdatei: `%s': %s.\n" -#: src/util/disk.c:1734 +#: src/util/disk.c:1931 #, fuzzy, c-format msgid "No `%s' specified for service `%s' in configuration.\n" msgstr "In der Konfigurationsdatei wurden keine Anwendungen definiert!\n" -#: src/util/getopt.c:669 +#: src/util/getopt.c:570 #, c-format msgid "%s: option `%s' is ambiguous\n" msgstr "%s: Option `%s' ist mehrdeutig\n" -#: src/util/getopt.c:693 +#: src/util/getopt.c:594 #, c-format msgid "%s: option `--%s' does not allow an argument\n" msgstr "%s: Option '--%s' erlaubt keinen Parameter\n" -#: src/util/getopt.c:698 +#: src/util/getopt.c:599 #, c-format msgid "%s: option `%c%s' does not allow an argument\n" msgstr "%s: Option '%c%s' erlaubt keinen Parameter\n" -#: src/util/getopt.c:715 src/util/getopt.c:883 +#: src/util/getopt.c:616 src/util/getopt.c:783 #, c-format msgid "%s: option `%s' requires an argument\n" msgstr "%s: Option `%s' benötigt einen Parameter\n" -#: src/util/getopt.c:744 +#: src/util/getopt.c:645 #, c-format msgid "%s: unrecognized option `--%s'\n" msgstr "%s: unbekannte Option '--%s'\n" -#: src/util/getopt.c:748 +#: src/util/getopt.c:649 #, c-format msgid "%s: unrecognized option `%c%s'\n" msgstr "%s: unbekannte Option '%c%s'\n" -#: src/util/getopt.c:773 +#: src/util/getopt.c:674 #, c-format msgid "%s: illegal option -- %c\n" msgstr "%s: unerlaubte Option -- %c\n" -#: src/util/getopt.c:775 +#: src/util/getopt.c:676 #, c-format msgid "%s: invalid option -- %c\n" msgstr "%s: ungültige Option -- %c\n" -#: src/util/getopt.c:803 src/util/getopt.c:931 +#: src/util/getopt.c:704 src/util/getopt.c:831 #, c-format msgid "%s: option requires an argument -- %c\n" msgstr "%s: Option benötigt einen Parameter -- %c\n" -#: src/util/getopt.c:851 +#: src/util/getopt.c:752 #, c-format msgid "%s: option `-W %s' is ambiguous\n" msgstr "%s: Option '-W %s' ist mehrdeutig\n" -#: src/util/getopt.c:869 +#: src/util/getopt.c:770 #, c-format msgid "%s: option `-W %s' does not allow an argument\n" msgstr "%s: Option '-W %s' erlaubt keinen Parameter\n" -#: src/util/getopt.c:1035 +#: src/util/getopt.c:935 #, fuzzy, c-format msgid "Use %s to get a list of options.\n" msgstr "Verwenden Sie --help, um eine Liste der Optionen zu erhalten.\n" @@ -5563,37 +6184,110 @@ msgstr "" "Parameter, die für lange Optionen zwingend sind, sind auch für kurze " "Optionen zwingend.\n" -#: src/util/getopt_helpers.c:258 src/util/getopt_helpers.c:286 +#: src/util/getopt_helpers.c:258 src/util/getopt_helpers.c:316 #, c-format msgid "You must pass a number to the `%s' option.\n" msgstr "Sie müssen für die Option `%s' zusätzlich eine Zahl angeben.\n" -#: src/util/gnunet-resolver.c:148 -msgid "perform a reverse lookup" +#: src/util/getopt_helpers.c:288 +#, fuzzy, c-format +msgid "You must pass relative time to the `%s' option.\n" +msgstr "Sie müssen eine positive Zahl zu der Option `%s' übergeben.\n" + +#: src/util/gnunet-config.c:90 +#, c-format +msgid "--section argument is required\n" msgstr "" -#: src/util/gnunet-resolver.c:154 -msgid "Use build-in GNUnet stub resolver" +#: src/util/gnunet-config.c:133 +#, c-format +msgid "--option argument required to set value\n" +msgstr "" + +#: src/util/gnunet-config.c:160 +msgid "obtain option of value as a filename (with $-expansion)" +msgstr "" + +#: src/util/gnunet-config.c:163 +msgid "name of the section to access" +msgstr "" + +#: src/util/gnunet-config.c:166 +msgid "name of the option to access" +msgstr "" + +#: src/util/gnunet-config.c:169 +msgid "value to set" +msgstr "" + +#: src/util/gnunet-config.c:178 +#, fuzzy +msgid "Manipulate GNUnet configuration files" +msgstr "" +"Einen Wert aus der Konfigurationsdatei auf der Standardausgabe ausgeben" + +#: src/util/gnunet-ecc.c:107 src/util/gnunet-rsa.c:107 +#, fuzzy, c-format +msgid "Failed to open `%s': %s\n" +msgstr "Datei wurde als `%s' gespeichert.\n" + +#: src/util/gnunet-ecc.c:113 src/util/gnunet-rsa.c:113 +#, c-format +msgid "Generating %u keys, please wait" msgstr "" -#: src/util/gnunet-rsa.c:64 +#: src/util/gnunet-ecc.c:128 src/util/gnunet-rsa.c:137 +#, fuzzy, c-format +msgid "" +"\n" +"Failed to write to `%s': %s\n" +msgstr "Es konnte keine Verbindung mit gnunetd hergestellt werden.\n" + +#: src/util/gnunet-ecc.c:140 src/util/gnunet-rsa.c:149 +#, fuzzy, c-format +msgid "Finished!\n" +msgstr "Fertigstellen" + +#: src/util/gnunet-ecc.c:163 src/util/gnunet-rsa.c:172 #, c-format msgid "No hostkey file specified on command line\n" msgstr "" -#: src/util/gnunet-rsa.c:112 +#: src/util/gnunet-ecc.c:220 src/util/gnunet-rsa.c:229 +msgid "create COUNT public-private key pairs (for testing)" +msgstr "" + +#: src/util/gnunet-ecc.c:223 src/util/gnunet-rsa.c:232 msgid "print the public key in ASCII format" msgstr "" -#: src/util/gnunet-rsa.c:115 +#: src/util/gnunet-ecc.c:226 src/util/gnunet-rsa.c:235 msgid "print the hash of the public key in ASCII format" msgstr "" -#: src/util/gnunet-rsa.c:118 +#: src/util/gnunet-ecc.c:229 src/util/gnunet-rsa.c:238 msgid "print the short hash of the public key in ASCII format" msgstr "" -#: src/util/gnunet-rsa.c:124 +#: src/util/gnunet-ecc.c:232 src/util/gnunet-rsa.c:241 +msgid "" +"use insecure, weak random number generator for key generation (for testing " +"only)" +msgstr "" + +#: src/util/gnunet-ecc.c:243 +msgid "Manipulate GNUnet private ECC key files" +msgstr "" + +#: src/util/gnunet-resolver.c:148 +msgid "perform a reverse lookup" +msgstr "" + +#: src/util/gnunet-resolver.c:159 +msgid "Use build-in GNUnet stub resolver" +msgstr "" + +#: src/util/gnunet-rsa.c:252 msgid "Manipulate GNUnet private RSA key files" msgstr "" @@ -5608,70 +6302,74 @@ msgstr "`%s' konnte nicht aufgelöst werden: %s\n" msgid "Could not find IP of host `%s': %s\n" msgstr "IP des Hosts `%s' konnte nicht ermittelt werden: %s\n" -#: src/util/helper.c:244 +#: src/util/gnunet-uri.c:90 +#, c-format +msgid "No URI specified on command line\n" +msgstr "" + +#: src/util/gnunet-uri.c:95 #, fuzzy, c-format -msgid "Error reading from `%s': %s\n" -msgstr "Fehler beim Anlegen des Benutzers" +msgid "Invalid URI: does not start with `%s'\n" +msgstr "Ungültige Antwort auf `%s'.\n" + +#: src/util/gnunet-uri.c:102 +#, c-format +msgid "Invalid URI: fails to specify subsystem\n" +msgstr "" -#: src/util/helper.c:259 +#: src/util/gnunet-uri.c:112 #, c-format -msgid "Got 0 bytes from helper `%s' (EOF)\n" +msgid "No handler known for subsystem `%s'\n" +msgstr "" + +#: src/util/gnunet-uri.c:174 +msgid "Perform default-actions for GNUnet URIs" msgstr "" -#: src/util/helper.c:269 +#: src/util/helper.c:260 #, fuzzy, c-format -msgid "Got %u bytes from helper `%s'\n" -msgstr "GAP hat ungültige Inhalte von `%s' empfangen.\n" +msgid "Error reading from `%s': %s\n" +msgstr "Fehler beim Anlegen des Benutzers" -#: src/util/helper.c:278 +#: src/util/helper.c:305 #, fuzzy, c-format msgid "Failed to parse inbound message from helper `%s'\n" msgstr "Fehler beim Lesen der Freunde-Liste von `%s'\n" -#: src/util/helper.c:310 -#, fuzzy, c-format -msgid "Starting HELPER process `%s'\n" -msgstr "Collection `%s' begonnen.\n" - -#: src/util/helper.c:440 +#: src/util/helper.c:499 #, fuzzy, c-format msgid "Error writing to `%s': %s\n" msgstr "Fehler beim Anlegen des Benutzers" -#: src/util/network.c:1200 +#: src/util/network.c:127 +#, c-format +msgid "Unable to shorten unix path `%s' while keeping name unique\n" +msgstr "" + +#: src/util/network.c:1331 #, c-format msgid "" "Fatal internal logic error, process hangs in `%s' (abort with CTRL-C)!\n" msgstr "" -#: src/util/os_installation.c:299 +#: src/util/os_installation.c:420 #, c-format msgid "" "Could not determine installation path for %s. Set `%s' environment " "variable.\n" msgstr "" -#: src/util/os_installation.c:486 +#: src/util/os_installation.c:702 #, fuzzy, c-format msgid "Could not find binary `%s' in PATH!\n" msgstr "Knoten `%s' konnte nicht in der Routing Tabelle gefunden werden!\n" -#: src/util/os_installation.c:492 -#, fuzzy, c-format -msgid "access (%s, X_OK) failed: %s\n" -msgstr "`%s' schlug fehl: %s\n" - -#: src/util/os_installation.c:507 -#, fuzzy, c-format -msgid "stat (%s) failed: %s\n" -msgstr "`%s' schlug fehl: %s\n" - -#: src/util/os_priority.c:305 +#: src/util/os_priority.c:302 #, fuzzy, c-format msgid "Failed to open named pipe `%s' for reading: %s\n" msgstr "Datei wurde als `%s' gespeichert.\n" -#: src/util/os_priority.c:306 +#: src/util/os_priority.c:303 #, fuzzy, c-format msgid "Failed to open named pipe `%s' for writing: %s\n" msgstr "Datei wurde als `%s' gespeichert.\n" @@ -5697,12 +6395,17 @@ msgstr "`%s' fehlgeschlagen für die Bibliothek `%s'. Ort: %s:%d. Fehler: %s\n" msgid "Could not determine plugin installation path.\n" msgstr "Öffentliche IP-Adresse konnte nicht ermittelt werden.\n" -#: src/util/pseudonym.c:276 +#: src/util/program.c:254 src/util/service.c:1791 +#, fuzzy, c-format +msgid "Could not access configuration file `%s'\n" +msgstr "Konfigurationsdatei `%s' konnte nicht geparst werden.\n" + +#: src/util/pseudonym.c:282 #, fuzzy, c-format msgid "Failed to parse metadata about pseudonym from file `%s': %s\n" msgstr "Fehler beim Parsen der Gerätedaten von `%s' bei %s:%d.\n" -#: src/util/pseudonym.c:407 src/util/pseudonym.c:433 +#: src/util/pseudonym.c:413 src/util/pseudonym.c:439 #, fuzzy msgid "no-name" msgstr "Name anzeigen" @@ -5735,152 +6438,152 @@ msgstr "Fehler beim Lesen der Freunde-Liste von `%s'\n" msgid "Could not resolve our FQDN : %s\n" msgstr "`%s' konnte nicht aufgelöst werden: %s\n" -#: src/util/scheduler.c:786 +#: src/util/scheduler.c:782 msgid "Looks like we're busy waiting...\n" msgstr "" -#: src/util/scheduler.c:916 +#: src/util/scheduler.c:912 #, c-format msgid "Attempt to cancel dead task %llu!\n" msgstr "" -#: src/util/server.c:483 +#: src/util/server.c:426 #, fuzzy, c-format msgid "`%s' failed for port %d (%s).\n" msgstr "`%s' fehlgeschlagen für Laufwerk %s: %u\n" -#: src/util/server.c:492 +#: src/util/server.c:435 #, fuzzy, c-format msgid "`%s' failed for port %d (%s): address already in use\n" msgstr "`%s' schlug fehl für Port %d: %s. Läuft gnunetd bereits?\n" -#: src/util/server.c:497 +#: src/util/server.c:446 #, fuzzy, c-format -msgid "`%s' failed for `%s': address already in use\n" +msgid "`%s' failed for `%.*s': address already in use\n" msgstr "`%s' schlug fehl für Port %d: %s. Läuft gnunetd bereits?\n" -#: src/util/server.c:827 +#: src/util/server.c:830 #, c-format msgid "" "Processing code for message of type %u did not call " -"GNUNET_SERVER_receive_done after %llums\n" +"`GNUNET_SERVER_receive_done' after %s\n" msgstr "" -#: src/util/service.c:135 src/util/service.c:161 src/util/service.c:204 -#: src/util/service.c:225 src/util/service.c:232 +#: src/util/service.c:142 src/util/service.c:168 src/util/service.c:211 +#: src/util/service.c:232 src/util/service.c:239 #, c-format msgid "Invalid format for IP: `%s'\n" msgstr "Ungültiges Format für IP: `%s'\n" -#: src/util/service.c:188 +#: src/util/service.c:195 #, c-format msgid "Invalid network notation ('/%d' is not legal in IPv4 CIDR)." msgstr "Ungültige Netzwerk Notation ('/%d ist nicht gültig in IPv4 CIDR)." -#: src/util/service.c:281 +#: src/util/service.c:288 #, c-format msgid "Invalid network notation (does not end with ';': `%s')\n" msgstr "Ungültige Netzwerk Notation (endet nicht mit ';': `%s')\n" -#: src/util/service.c:313 +#: src/util/service.c:320 #, fuzzy, c-format msgid "Wrong format `%s' for netmask\n" msgstr "Falsches Format `%s' für Netzmaske: %s\n" -#: src/util/service.c:343 +#: src/util/service.c:350 #, fuzzy, c-format msgid "Wrong format `%s' for network\n" msgstr "Falsches Format `%s' für Netzwerk: %s\n" -#: src/util/service.c:698 +#: src/util/service.c:707 #, c-format msgid "Access denied to UID %d / GID %d\n" msgstr "" -#: src/util/service.c:703 +#: src/util/service.c:712 #, fuzzy, c-format msgid "Unknown address family %d\n" msgstr "Unbekannte Operation `%s'\n" -#: src/util/service.c:710 +#: src/util/service.c:719 #, c-format msgid "Access from `%s' denied to service `%s'\n" msgstr "" -#: src/util/service.c:765 +#: src/util/service.c:774 #, c-format msgid "Could not parse IPv4 network specification `%s' for `%s:%s'\n" msgstr "" -#: src/util/service.c:802 +#: src/util/service.c:811 #, c-format msgid "Could not parse IPv6 network specification `%s' for `%s:%s'\n" msgstr "" -#: src/util/service.c:920 +#: src/util/service.c:929 #, c-format msgid "" "Disabling IPv6 support for service `%s', failed to create IPv6 socket: %s\n" msgstr "" -#: src/util/service.c:990 +#: src/util/service.c:1007 #, c-format msgid "" "Disabling UNIX domain socket support for service `%s', failed to create UNIX " "domain socket: %s\n" msgstr "" -#: src/util/service.c:1007 +#: src/util/service.c:1024 #, c-format msgid "Have neither PORT nor UNIXPATH for service `%s', but one is required\n" msgstr "" -#: src/util/service.c:1241 +#: src/util/service.c:1258 msgid "Could not access a pre-bound socket, will try to bind myself\n" msgstr "" -#: src/util/service.c:1292 src/util/service.c:1310 +#: src/util/service.c:1309 src/util/service.c:1327 #, c-format msgid "Specified value for `%s' of service `%s' is invalid\n" msgstr "" -#: src/util/service.c:1337 +#: src/util/service.c:1354 #, c-format msgid "Could not access pre-bound socket %u, will try to bind myself\n" msgstr "" -#: src/util/service.c:1506 +#: src/util/service.c:1525 #, fuzzy, c-format msgid "Failed to start `%s' at `%s'\n" msgstr "Es konnte keine Verbindung mit gnunetd hergestellt werden.\n" -#: src/util/service.c:1539 +#: src/util/service.c:1558 #, fuzzy, c-format msgid "Service `%s' runs at %s\n" msgstr "Knoten `%s' mit Vertrauen %8u und Adresse `%s'\n" -#: src/util/service.c:1588 +#: src/util/service.c:1607 msgid "Service process failed to initialize\n" msgstr "" -#: src/util/service.c:1592 +#: src/util/service.c:1611 msgid "Service process could not initialize server function\n" msgstr "" -#: src/util/service.c:1596 +#: src/util/service.c:1615 msgid "Service process failed to report status\n" msgstr "" -#: src/util/service.c:1651 +#: src/util/service.c:1670 msgid "No such user" msgstr "" -#: src/util/service.c:1664 +#: src/util/service.c:1683 #, c-format msgid "Cannot change user/group to `%s': %s\n" msgstr "Benutzer/Gruppe kann nicht zu `%s' gewechselt werden: %s\n" -#: src/util/service.c:1729 +#: src/util/service.c:1749 msgid "do daemonize (detach from terminal)" msgstr "" @@ -5889,292 +6592,641 @@ msgstr "" msgid "signal (%d, %p) returned %d.\n" msgstr "Aufruf von `%s' gibt %d zurück.\n" -#: src/util/strings.c:144 +#: src/util/strings.c:146 msgid "b" msgstr "b" -#: src/util/strings.c:334 +#: src/util/strings.c:413 #, c-format msgid "Character sets requested were `%s'->`%s'\n" msgstr "" -#: src/util/strings.c:481 +#: src/util/strings.c:528 msgid "Failed to expand `$HOME': environment variable `HOME' not set" msgstr "" -#: src/util/strings.c:573 +#: src/util/strings.c:625 msgid "ms" msgstr "ms" -#: src/util/strings.c:578 -msgid "eternity" +#: src/util/strings.c:629 +msgid "forever" msgstr "" -#: src/util/strings.c:582 +#: src/util/strings.c:631 +msgid "0 ms" +msgstr "" + +#: src/util/strings.c:637 msgid "s" msgstr "s" -#: src/util/strings.c:586 -msgid "m" -msgstr "m" +#: src/util/strings.c:643 +msgid "m" +msgstr "m" + +#: src/util/strings.c:649 +msgid "h" +msgstr "h" + +#: src/util/strings.c:656 +#, fuzzy +msgid "day" +msgstr " Tage" + +#: src/util/strings.c:658 +#, fuzzy +msgid "days" +msgstr " Tage" + +#: src/util/strings.c:685 +msgid "end of time" +msgstr "" + +#: src/util/strings.c:1073 +msgid "IPv6 address did not start with `['\n" +msgstr "" + +#: src/util/strings.c:1081 +msgid "IPv6 address did contain ':' to separate port number\n" +msgstr "" + +#: src/util/strings.c:1087 +msgid "IPv6 address did contain ']' before ':' to separate port number\n" +msgstr "" + +#: src/util/strings.c:1094 +msgid "IPv6 address did contain a valid port number after the last ':'\n" +msgstr "" + +#: src/util/strings.c:1103 +#, fuzzy, c-format +msgid "Invalid IPv6 address `%s': %s\n" +msgstr "Ungültiger Parameter: `%s'\n" + +#: src/vpn/gnunet-service-vpn.c:512 src/vpn/gnunet-service-vpn.c:1088 +#, fuzzy +msgid "# Active tunnels" +msgstr "GNUnet Konfiguration" + +#: src/vpn/gnunet-service-vpn.c:609 src/vpn/gnunet-service-vpn.c:646 +#, fuzzy +msgid "# peers connected to mesh tunnels" +msgstr "# verbundener Knoten" + +#: src/vpn/gnunet-service-vpn.c:699 +#, fuzzy +msgid "# Bytes given to mesh for transmission" +msgstr "# PING Nachrichten erstellt" + +#: src/vpn/gnunet-service-vpn.c:737 +#, fuzzy +msgid "# Bytes dropped in mesh queue (overflow)" +msgstr "# Bytes verworfen von UDP (outgoing)" + +#: src/vpn/gnunet-service-vpn.c:771 +#, fuzzy +msgid "# Mesh tunnels created" +msgstr "# dht Anfragen weitergeleitet" + +#: src/vpn/gnunet-service-vpn.c:794 +#, fuzzy +msgid "Failed to setup mesh tunnel!\n" +msgstr "Statistiken über den Netzwerkverkehr konnten nicht ermittelt werden.\n" + +#: src/vpn/gnunet-service-vpn.c:990 +#, c-format +msgid "Protocol %u not supported, dropping\n" +msgstr "" + +#: src/vpn/gnunet-service-vpn.c:1308 +msgid "# ICMPv4 packets dropped (not allowed)" +msgstr "" + +#: src/vpn/gnunet-service-vpn.c:1329 +msgid "# ICMPv6 packets dropped (not allowed)" +msgstr "" + +#: src/vpn/gnunet-service-vpn.c:1534 +#, fuzzy +msgid "# Packets received from TUN interface" +msgstr "Empfangene Client-Nachricht ist ungültig.\n" + +#: src/vpn/gnunet-service-vpn.c:1572 src/vpn/gnunet-service-vpn.c:1613 +#, c-format +msgid "Packet received for unmapped destination `%s' (dropping it)\n" +msgstr "" + +#: src/vpn/gnunet-service-vpn.c:1623 +msgid "Received IPv4 packet with options (dropping it)\n" +msgstr "" + +#: src/vpn/gnunet-service-vpn.c:1637 +#, c-format +msgid "Received packet of unknown protocol %d from TUN (dropping it)\n" +msgstr "" + +#: src/vpn/gnunet-service-vpn.c:1721 +#, fuzzy +msgid "# ICMP packets received from mesh" +msgstr "Empfangene Client-Nachricht ist ungültig.\n" + +#: src/vpn/gnunet-service-vpn.c:2062 +#, fuzzy +msgid "# UDP packets received from mesh" +msgstr "Empfangene Client-Nachricht ist ungültig.\n" + +#: src/vpn/gnunet-service-vpn.c:2220 +#, fuzzy +msgid "# TCP packets received from mesh" +msgstr "Empfangene Client-Nachricht ist ungültig.\n" + +#: src/vpn/gnunet-service-vpn.c:2371 +msgid "Failed to find unallocated IPv4 address in VPN's range\n" +msgstr "" + +#: src/vpn/gnunet-service-vpn.c:2426 +#, fuzzy +msgid "Failed to find unallocated IPv6 address in VPN's range\n" +msgstr "Die öffentliche IPv6-Adresse konnte nicht ermittelt werden!\n" + +#: src/vpn/gnunet-service-vpn.c:2465 src/vpn/gnunet-service-vpn.c:2678 +#, fuzzy +msgid "# Active destinations" +msgstr "GNUnet Konfiguration" + +#: src/vpn/gnunet-service-vpn.c:2751 +msgid "Failed to allocate IP address for new destination\n" +msgstr "" + +#: src/vpn/gnunet-service-vpn.c:3138 +msgid "IPv6 support disabled as this system does not support IPv6\n" +msgstr "" + +#: src/vpn/gnunet-service-vpn.c:3170 +msgid "IPv4 support disabled as this system does not support IPv4\n" +msgstr "" + +#: src/vpn/gnunet-vpn.c:151 +#, fuzzy +msgid "Error creating tunnel\n" +msgstr "Hostkey wurde erfolgreich erzeugt.\n" + +#: src/vpn/gnunet-vpn.c:194 src/vpn/gnunet-vpn.c:225 +#, fuzzy, c-format +msgid "Option `%s' makes no sense with option `%s'.\n" +msgstr "Option `%s' macht keinen Sinn ohne die Option `%s'.\n" + +#: src/vpn/gnunet-vpn.c:207 +#, fuzzy, c-format +msgid "Option `%s' or `%s' is required.\n" +msgstr "%s: Option `%s' ist mehrdeutig\n" + +#: src/vpn/gnunet-vpn.c:219 +#, fuzzy, c-format +msgid "Option `%s' or `%s' is required when using option `%s'.\n" +msgstr "Option `%s' macht keinen Sinn ohne die Option `%s'.\n" + +#: src/vpn/gnunet-vpn.c:237 +#, fuzzy, c-format +msgid "`%s' is not a valid peer identifier.\n" +msgstr "`%s' ist nicht verfügbar." + +#: src/vpn/gnunet-vpn.c:259 +#, fuzzy, c-format +msgid "`%s' is not a valid IP address.\n" +msgstr "`%s' ist nicht verfügbar." + +#: src/vpn/gnunet-vpn.c:295 +msgid "request that result should be an IPv4 address" +msgstr "" + +#: src/vpn/gnunet-vpn.c:298 +msgid "request that result should be an IPv6 address" +msgstr "" + +#: src/vpn/gnunet-vpn.c:301 +msgid "print IP address only after mesh tunnel has been created" +msgstr "" + +#: src/vpn/gnunet-vpn.c:304 +msgid "how long should the mapping be valid for new tunnels?" +msgstr "" + +#: src/vpn/gnunet-vpn.c:307 +msgid "destination IP for the tunnel" +msgstr "" + +#: src/vpn/gnunet-vpn.c:310 +msgid "peer offering the service we would like to access" +msgstr "" + +#: src/vpn/gnunet-vpn.c:313 +msgid "name of the service we would like to access" +msgstr "" + +#: src/vpn/gnunet-vpn.c:316 +#, fuzzy +msgid "service is offered via TCP" +msgstr "# Bytes empfangen über TCP" + +#: src/vpn/gnunet-vpn.c:319 +#, fuzzy +msgid "service is offered via UDP" +msgstr "# Bytes empfangen über UDP" + +#: src/vpn/gnunet-vpn.c:331 +msgid "Setup tunnels via VPN." +msgstr "" + +#: src/include/gnunet_common.h:579 src/include/gnunet_common.h:584 +#: src/include/gnunet_common.h:590 +#, fuzzy, c-format +msgid "Assertion failed at %s:%d.\n" +msgstr "Absicherung fehlgeschlagen bei %s:%d.\n" + +#: src/include/gnunet_common.h:600 +#, fuzzy, c-format +msgid "External protocol violation detected at %s:%d.\n" +msgstr "Absicherung fehlgeschlagen bei %s:%d.\n" + +#: src/include/gnunet_common.h:621 src/include/gnunet_common.h:628 +#, fuzzy, c-format +msgid "`%s' failed on file `%s' at %s:%d with error: %s\n" +msgstr "`%s' schlug bei Datei `%s' fehl. Ort: %s:%d. Fehler: %s\n" + +#, fuzzy +#~ msgid "session identifier" +#~ msgstr "# Sitzungen aufgebaut" + +#, fuzzy +#~ msgid "Mesh service could not access hostkey. Exiting.\n" +#~ msgstr "Auf die Namespace Informationen konnte nicht zugegriffen werden.\n" + +#, fuzzy +#~ msgid "" +#~ "provide inthe 'struct GNUNET_TRANSPORT_PeerIterateContextformation about " +#~ "all tunnels (continuously)" +#~ msgstr "Informationen über andere GNUnet Knoten ausgeben." + +#, fuzzy +#~ msgid "Connected to %s\n" +#~ msgstr "`%s' hat sich mit `%s' verbunden.\n" + +#, fuzzy +#~ msgid "Error receiving response to `%s' request from ARM for service `%s'\n" +#~ msgstr "Beschädigte Antwort auf `%s' von Knoten `%s' empfangen.\n" + +#, fuzzy +#~ msgid "Asked to start service `%s' within %llu ms\n" +#~ msgstr "`%s': Nachricht wurde nicht innerhalb %llu ms empfangen.\n" + +#, fuzzy +#~ msgid "Stopping service `%s' within %llu ms\n" +#~ msgstr "Keine Antwort innerhalb %llums erhalten.\n" + +#, fuzzy +#~ msgid "Fatal configuration error: `%s' option in section `%s' missing.\n" +#~ msgstr "" +#~ "Es muss eine Liste von Freunden in der Konfigurationsdatei unter `%s' in " +#~ "der Sektion `%s' angegeben werden.\n" + +#, fuzzy +#~ msgid "Configuration file `%s' for service `%s' not valid: %s\n" +#~ msgstr "Konfigurationsdatei `%s' wurde erzeugt.\n" + +#, fuzzy +#~ msgid "list information for all peers" +#~ msgstr "Informationen über andere GNUnet Knoten ausgeben." + +#, fuzzy +#~ msgid "Could not transmit confirmation receipt\n" +#~ msgstr "Auf die Namespace Informationen konnte nicht zugegriffen werden.\n" + +#, fuzzy +#~ msgid "Unknown message type: '%u'\n" +#~ msgstr "Unbekannte Operation `%s'\n" + +#, fuzzy +#~ msgid "Configuration option `%s' in section `%s' missing\n" +#~ msgstr "Konfigurationsdatei `%s' wurde erzeugt.\n" + +#, fuzzy +#~ msgid "Failed to access chat home directory `%s'\n" +#~ msgstr "Dateiformat fehlerhaft (kein GNUnet Verzeichnis?)\n" + +#, fuzzy +#~ msgid "Failed to create/open key in file `%s'\n" +#~ msgstr "Datei wurde als `%s' gespeichert.\n" + +#, fuzzy +#~ msgid "Could not serialize metadata\n" +#~ msgstr "Konnte libgnunetutil nicht initialisieren!\n" + +#, fuzzy +#~ msgid "Failed to connect to the chat service\n" +#~ msgstr "Es konnte keine Verbindung mit gnunetd hergestellt werden.\n" + +#, fuzzy +#~ msgid "(%s) `%s' said: %s\n" +#~ msgstr "`%s' %s schlug fehl: %s\n" + +#, fuzzy +#~ msgid "(%s) `%s' said to you: %s\n" +#~ msgstr "`%s' %s schlug fehl: %s\n" + +#, fuzzy +#~ msgid "(%s) `%s' said for sure: %s\n" +#~ msgstr "`%s' fehlgeschlagen für Laufwerk %s: %u\n" + +#, fuzzy +#~ msgid "(%s) `%s' said to you for sure: %s\n" +#~ msgstr "`%s' schlug bei %s:%d mit dem Fehler %s fehl\n" + +#, fuzzy +#~ msgid "(%s) `%s' was confirmed that you received: %s\n" +#~ msgstr "`%s' schlug bei %s:%d mit dem Fehler %s fehl\n" + +#, fuzzy +#~ msgid "(%s) `%s' was confirmed that you and only you received: %s\n" +#~ msgstr "`%s' schlug bei %s:%d mit dem Fehler %s fehl\n" + +#, fuzzy +#~ msgid "(%s) `%s' was confirmed that you received from him or her: %s\n" +#~ msgstr "`%s' schlug bei %s:%d mit dem Fehler %s fehl\n" + +#, fuzzy +#~ msgid "" +#~ "(%s) `%s' was confirmed that you and only you received from him or her: " +#~ "%s\n" +#~ msgstr "`%s' schlug bei %s:%d mit dem Fehler %s fehl\n" + +#, fuzzy +#~ msgid "(%s) `%s' said off the record: %s\n" +#~ msgstr "`%s' schlug bei %s:%d mit dem Fehler %s fehl\n" + +#, fuzzy +#~ msgid "`%s' left the room\n" +#~ msgstr "Fehler beim Binden an UDP Port %d.\n" + +#, fuzzy +#~ msgid "Could not change username\n" +#~ msgstr "Namespace `%s' konnte nicht erstellt werden (existiert bereits?).\n" + +#, fuzzy +#~ msgid "Joining room `%s' as user `%s'...\n" +#~ msgstr "Ungültige Antwort auf `%s' von Knoten `%s' empfangen.\n" + +#, fuzzy +#~ msgid "Changed username to `%s'\n" +#~ msgstr "Benutzer/Gruppe kann nicht zu `%s' gewechselt werden: %s\n" -#: src/util/strings.c:590 -msgid "h" -msgstr "h" +#, fuzzy +#~ msgid "Unknown command `%s'\n" +#~ msgstr "Unbekannte Operation `%s'\n" -#: src/util/strings.c:594 -msgid " days" -msgstr " Tage" +#, fuzzy +#~ msgid "You must specify a nickname\n" +#~ msgstr "Sie müssen einen Empfänger angeben!\n" -#: src/util/strings.c:618 -msgid "end of time" -msgstr "" +#, fuzzy +#~ msgid "Failed to join room `%s'\n" +#~ msgstr "Fehler beim Binden an UDP Port %d.\n" -#: src/util/strings.c:1012 -msgid "IPv6 address did not start with `['\n" -msgstr "" +#, fuzzy +#~ msgid "Failed to queue a message notification\n" +#~ msgstr "Fehler beim Speichern der Konfiguration!" -#: src/util/strings.c:1020 -msgid "IPv6 address did contain ':' to separate port number\n" -msgstr "" +#, fuzzy +#~ msgid "Failed to queue a join notification\n" +#~ msgstr "Fehler beim Abfragen der Netzwerkverkehrsbedingungen von gnunetd.\n" -#: src/util/strings.c:1026 -msgid "IPv6 address did contain ']' before ':' to separate port number\n" -msgstr "" +#, fuzzy +#~ msgid "Failed to queue a confirmation receipt\n" +#~ msgstr "Fehler beim Speichern der Konfiguration!" -#: src/util/strings.c:1033 -msgid "IPv6 address did contain a valid port number after the last ':'\n" -msgstr "" +#, fuzzy +#~ msgid "Failed to queue a leave notification\n" +#~ msgstr "Fehler beim Speichern der Konfiguration!" -#: src/util/strings.c:1042 -#, fuzzy, c-format -msgid "Invalid IPv6 address `%s': %s\n" -msgstr "Ungültiger Parameter: `%s'\n" +#, fuzzy +#~ msgid "Option `%s' in section `%s' missing in configuration!\n" +#~ msgstr "In der Konfigurationsdatei wurden keine Anwendungen definiert!\n" -#: src/vpn/gnunet-service-vpn.c:511 src/vpn/gnunet-service-vpn.c:1071 #, fuzzy -msgid "# Active tunnels" -msgstr "GNUnet Konfiguration" +#~ msgid "Connected to %s service!\n" +#~ msgstr "`%s' hat sich mit `%s' verbunden.\n" -#: src/vpn/gnunet-service-vpn.c:608 src/vpn/gnunet-service-vpn.c:645 #, fuzzy -msgid "# peers connected to mesh tunnels" -msgstr "# verbundener Knoten" +#~ msgid "Configuration fails to specify `%s' in section `%s'\n" +#~ msgstr "" +#~ "Die Konfigurationsdatei muss in der Sektion `%s' unter `%s' ein " +#~ "Verzeichnis angeben, in dem FS Daten gespeichert werden.\n" -#: src/vpn/gnunet-service-vpn.c:699 #, fuzzy -msgid "# Bytes given to mesh for transmission" -msgstr "# PING Nachrichten erstellt" +#~ msgid "Failed to start daemon: %s\n" +#~ msgstr "Fehler beim Starten der Collection.\n" -#: src/vpn/gnunet-service-vpn.c:737 #, fuzzy -msgid "# Bytes dropped in mesh queue (overflow)" -msgstr "# Bytes verworfen von UDP (outgoing)" +#~ msgid "Configuration fails to specify `%s', assuming default value." +#~ msgstr "Konfigurationsdatei `%s' wurde erzeugt.\n" -#: src/vpn/gnunet-service-vpn.c:772 #, fuzzy -msgid "# Mesh tunnels created" -msgstr "# dht Anfragen weitergeleitet" +#~ msgid "Key file `%s' for private zone does not exist!\n" +#~ msgstr "Anzahl an Nachrichten, die pro Durchlauf verwendet wird" -#: src/vpn/gnunet-service-vpn.c:795 #, fuzzy -msgid "Failed to setup mesh tunnel!\n" -msgstr "Statistiken über den Netzwerkverkehr konnten nicht ermittelt werden.\n" +#~ msgid "Option `%s' not specified in configuration section `%s'\n" +#~ msgstr "" +#~ "Option `%s' ist in der Konfigurationsdatei in der Sektion `%s' nicht " +#~ "gesetzt, sie wird auf %dm gesetzt.\n" -#: src/vpn/gnunet-service-vpn.c:973 -#, c-format -msgid "Protocol %u not supported, dropping\n" -msgstr "" +#, fuzzy +#~ msgid "Malformed %s `%s' given in configuration!\n" +#~ msgstr "Fehler beim Speichern der Konfiguration!" -#: src/vpn/gnunet-service-vpn.c:1291 -msgid "# ICMPv4 packets dropped (not allowed)" -msgstr "" +#, fuzzy +#~ msgid "Peer is lacking HOSTKEY configuration setting.\n" +#~ msgstr "GNUnet Konfiguration" -#: src/vpn/gnunet-service-vpn.c:1312 -msgid "# ICMPv6 packets dropped (not allowed)" -msgstr "" +#, fuzzy +#~ msgid "Could not access hostkey.\n" +#~ msgstr "Konfigurationsdatei `%s' konnte nicht geparst werden.\n" -#: src/vpn/gnunet-service-vpn.c:1517 #, fuzzy -msgid "# Packets received from TUN interface" -msgstr "Empfangene Client-Nachricht ist ungültig.\n" +#~ msgid "`scp' did not complete cleanly.\n" +#~ msgstr "`%s' ist zu keinem Knoten verbunden.\n" -#: src/vpn/gnunet-service-vpn.c:1555 src/vpn/gnunet-service-vpn.c:1596 -#, c-format -msgid "Packet received for unmapped destination `%s' (dropping it)\n" -msgstr "" +#, fuzzy +#~ msgid "Failed to create pipe for `gnunet-peerinfo' process.\n" +#~ msgstr "Fehler beim Starten der Collection.\n" -#: src/vpn/gnunet-service-vpn.c:1606 -msgid "Received IPv4 packet with options (dropping it)\n" -msgstr "" +#, fuzzy +#~ msgid "Failed to create pipe for `ssh' process.\n" +#~ msgstr "Dateiformat fehlerhaft (kein GNUnet Verzeichnis?)\n" -#: src/vpn/gnunet-service-vpn.c:1620 -#, c-format -msgid "Received packet of unknown protocol %d from TUN (dropping it)\n" -msgstr "" +#, fuzzy +#~ msgid "Could not start `%s' process to create hostkey.\n" +#~ msgstr "" +#~ "IP(v4) dieses Hosts konnte nicht ermittelt werden. Bitte geben Sie die IP " +#~ "in der Konfigurationsdatei an.\n" -#: src/vpn/gnunet-service-vpn.c:1704 #, fuzzy -msgid "# ICMP packets received from mesh" -msgstr "Empfangene Client-Nachricht ist ungültig.\n" +#~ msgid "Failed to start `gnunet-peerinfo' process.\n" +#~ msgstr "Fehler beim Starten der Collection.\n" -#: src/vpn/gnunet-service-vpn.c:2045 #, fuzzy -msgid "# UDP packets received from mesh" -msgstr "Empfangene Client-Nachricht ist ungültig.\n" +#~ msgid "Failed to start `ssh' process.\n" +#~ msgstr "Fehler beim Starten der Collection.\n" -#: src/vpn/gnunet-service-vpn.c:2203 #, fuzzy -msgid "# TCP packets received from mesh" -msgstr "Empfangene Client-Nachricht ist ungültig.\n" +#~ msgid "Error reading from gnunet-peerinfo: %s\n" +#~ msgstr "Fehler beim Lesen von Informationen von gnunetd.\n" -#: src/vpn/gnunet-service-vpn.c:2354 -msgid "Failed to find unallocated IPv4 address in VPN's range\n" -msgstr "" +#, fuzzy +#~ msgid "Malformed output from gnunet-peerinfo!\n" +#~ msgstr "Fehler beim Lesen von Informationen von gnunetd.\n" -#: src/vpn/gnunet-service-vpn.c:2409 #, fuzzy -msgid "Failed to find unallocated IPv6 address in VPN's range\n" -msgstr "Die öffentliche IPv6-Adresse konnte nicht ermittelt werden!\n" +#~ msgid "Failed to get hostkey!\n" +#~ msgstr "" +#~ "Statistiken über den Netzwerkverkehr konnten nicht ermittelt werden.\n" -#: src/vpn/gnunet-service-vpn.c:2448 src/vpn/gnunet-service-vpn.c:2661 #, fuzzy -msgid "# Active destinations" -msgstr "GNUnet Konfiguration" +#~ msgid "Could not start `%s' process to start GNUnet.\n" +#~ msgstr "" +#~ "IP(v4) dieses Hosts konnte nicht ermittelt werden. Bitte geben Sie die IP " +#~ "in der Konfigurationsdatei an.\n" -#: src/vpn/gnunet-service-vpn.c:2734 -msgid "Failed to allocate IP address for new destination\n" -msgstr "" +#, fuzzy +#~ msgid "Failed to start `gnunet-arm' process.\n" +#~ msgstr "Es konnte keine Verbindung mit gnunetd hergestellt werden.\n" -#: src/vpn/gnunet-service-vpn.c:3141 -msgid "IPv6 support disabled as this system does not support IPv6\n" -msgstr "" +#, fuzzy +#~ msgid "shutdown (either `gnunet-arm' or `ssh') did not complete cleanly.\n" +#~ msgstr "`%s' ist zu keinem Knoten verbunden.\n" -#: src/vpn/gnunet-service-vpn.c:3173 -msgid "IPv4 support disabled as this system does not support IPv4\n" -msgstr "" +#, fuzzy +#~ msgid "Starting service %s for peer `%4s'\n" +#~ msgstr "Collection `%s' begonnen.\n" -#: src/vpn/gnunet-vpn.c:151 #, fuzzy -msgid "Error creating tunnel\n" -msgstr "Hostkey wurde erfolgreich erzeugt.\n" +#~ msgid "Could not start `%s' process to copy configuration directory.\n" +#~ msgstr "" +#~ "IP(v4) dieses Hosts konnte nicht ermittelt werden. Bitte geben Sie die IP " +#~ "in der Konfigurationsdatei an.\n" -#: src/vpn/gnunet-vpn.c:195 src/vpn/gnunet-vpn.c:226 -#, fuzzy, c-format -msgid "Option `%s' makes no sense with option `%s'.\n" -msgstr "Option `%s' macht keinen Sinn ohne die Option `%s'.\n" +#, fuzzy +#~ msgid "Terminating peer `%4s'\n" +#~ msgstr "Zugriff verweigert für `%s' bei %s:%d.\n" -#: src/vpn/gnunet-vpn.c:208 -#, fuzzy, c-format -msgid "Option `%s' or `%s' is required.\n" -msgstr "%s: Option `%s' ist mehrdeutig\n" +#, fuzzy +#~ msgid "Setting d->dead on peer `%4s'\n" +#~ msgstr "Collection `%s' begonnen.\n" -#: src/vpn/gnunet-vpn.c:220 -#, fuzzy, c-format -msgid "Option `%s' or `%s' is required when using option `%s'.\n" -msgstr "Option `%s' macht keinen Sinn ohne die Option `%s'.\n" +#, fuzzy +#~ msgid "Failed to write new configuration to disk." +#~ msgstr "Fehler beim Speichern der Konfiguration!" -#: src/vpn/gnunet-vpn.c:238 -#, fuzzy, c-format -msgid "`%s' is not a valid peer identifier.\n" -msgstr "`%s' ist nicht verfügbar." +#, fuzzy +#~ msgid "Could not start `%s' process to copy configuration file.\n" +#~ msgstr "" +#~ "IP(v4) dieses Hosts konnte nicht ermittelt werden. Bitte geben Sie die IP " +#~ "in der Konfigurationsdatei an.\n" -#: src/vpn/gnunet-vpn.c:260 -#, fuzzy, c-format -msgid "`%s' is not a valid IP address.\n" -msgstr "`%s' ist nicht verfügbar." +#, fuzzy +#~ msgid "Failed to copy new configuration to remote machine." +#~ msgstr "Fehler beim Speichern der Konfiguration!" -#: src/vpn/gnunet-vpn.c:296 -msgid "request that result should be an IPv4 address" -msgstr "" +#, fuzzy +#~ msgid "Peers failed to connect" +#~ msgstr "Es konnte keine Verbindung mit gnunetd hergestellt werden." -#: src/vpn/gnunet-vpn.c:299 -msgid "request that result should be an IPv6 address" -msgstr "" +#, fuzzy +#~ msgid "Failed to connect to core service of first peer!\n" +#~ msgstr "Der Transportdienst auf Port %d konnte nicht gestartet werden.\n" -#: src/vpn/gnunet-vpn.c:302 -msgid "print IP address only after mesh tunnel has been created" -msgstr "" +#, fuzzy +#~ msgid "Invalid value `%s' for option `%s' in section `%s': expected float\n" +#~ msgstr "" +#~ "Die Konfigurationsdatei muss in der Sektion `%s' unter `%s' ein " +#~ "Verzeichnis angeben, in dem FS Daten gespeichert werden.\n" -#: src/vpn/gnunet-vpn.c:305 -msgid "how long should the mapping be valid for new tunnels?" -msgstr "" +#, fuzzy +#~ msgid "" +#~ "No `%s' specified in peer configuration in section `%s', cannot copy " +#~ "friends file!\n" +#~ msgstr "" +#~ "Option `%s' ist in der Konfigurationsdatei in der Sektion `%s' nicht " +#~ "gesetzt, sie wird auf %dm gesetzt.\n" -#: src/vpn/gnunet-vpn.c:308 -msgid "destination IP for the tunnel" -msgstr "" +#, fuzzy +#~ msgid "Unknown topology specification, can't connect peers!\n" +#~ msgstr "Syntaxfehler in Topolgieangabe, Bytes werden übersprungen.\n" -#: src/vpn/gnunet-vpn.c:311 -msgid "peer offering the service we would like to access" -msgstr "" +#, fuzzy +#~ msgid "Could not read hostkeys file `%s'!\n" +#~ msgstr "Fehler beim Lesen der Freunde-Liste von `%s'\n" -#: src/vpn/gnunet-vpn.c:314 -msgid "name of the service we would like to access" -msgstr "" +#, fuzzy +#~ msgid "Could not create configuration for peer number %u on `%s'!\n" +#~ msgstr "Auf die Namespace Informationen konnte nicht zugegriffen werden.\n" -#: src/vpn/gnunet-vpn.c:317 #, fuzzy -msgid "service is offered via TCP" -msgstr "# Bytes empfangen über TCP" +#~ msgid "Failed to find option %s in section %s!\n" +#~ msgstr "Fehler beim Binden an UDP Port %d.\n" -#: src/vpn/gnunet-vpn.c:320 #, fuzzy -msgid "service is offered via UDP" -msgstr "# Bytes empfangen über UDP" +#~ msgid "Invalid configuration option `%s' in section `%s'\n" +#~ msgstr "Konfigurationsdatei `%s' wurde erzeugt.\n" -#: src/vpn/gnunet-vpn.c:329 -msgid "Setup tunnels via VPN." -msgstr "" +#, fuzzy +#~ msgid "Missing configuration option `%s' in section `%s'\n" +#~ msgstr "Konfigurationsdatei `%s' wurde erzeugt.\n" -#: src/include/gnunet_common.h:497 src/include/gnunet_common.h:502 -#: src/include/gnunet_common.h:508 -#, fuzzy, c-format -msgid "Assertion failed at %s:%d.\n" -msgstr "Absicherung fehlgeschlagen bei %s:%d.\n" +#, fuzzy +#~ msgid "I am host `%s'. Read private key from `%s'.\n" +#~ msgstr "Aufruf von `%s' mit Schlüssel `%s'.\n" -#: src/include/gnunet_common.h:518 -#, fuzzy, c-format -msgid "External protocol violation detected at %s:%d.\n" -msgstr "Absicherung fehlgeschlagen bei %s:%d.\n" +#, fuzzy +#~ msgid "internal error" +#~ msgstr "Unbekannter Fehler.\n" -#: src/include/gnunet_common.h:539 src/include/gnunet_common.h:546 -#, fuzzy, c-format -msgid "`%s' failed on file `%s' at %s:%d with error: %s\n" -msgstr "`%s' schlug bei Datei `%s' fehl. Ort: %s:%d. Fehler: %s\n" +#, fuzzy +#~ msgid "Got %u bytes from helper `%s'\n" +#~ msgstr "GAP hat ungültige Inhalte von `%s' empfangen.\n" #, fuzzy -#~ msgid "Received malformed message via %s. Ignored.\n" -#~ msgstr "" -#~ "Es wurde eine ungültige Nachricht per SMTP empfangen (ungültige Größe).\n" +#~ msgid "Starting HELPER process `%s'\n" +#~ msgstr "Collection `%s' begonnen.\n" #, fuzzy -#~ msgid "SMTP filter string to invalid, lacks ': '\n" -#~ msgstr "SMTP Filterstring zu lang, wurde auf `%s' abgeschnitten\n" +#~ msgid "Could not create namespace `%s'\n" +#~ msgstr "Namespace `%s' konnte nicht erstellt werden (existiert bereits?).\n" -#~ msgid "SMTP filter string to long, capped to `%s'\n" -#~ msgstr "SMTP Filterstring zu lang, wurde auf `%s' abgeschnitten\n" +#, fuzzy +#~ msgid "Stored zonekey for zone `%s' in file `%s'\n" +#~ msgstr "Datei wurde als `%s' gespeichert.\n" #, fuzzy -#~ msgid "SMTP: `%s' failed: %s.\n" -#~ msgstr "`%s' schlug fehl: %s\n" +#~ msgid "Namestore removed record successfully" +#~ msgstr "Der GNUnet Dienst wurde erfolgreich installiert.\n" #, fuzzy -#~ msgid "No email-address specified, can not start SMTP transport.\n" -#~ msgstr "" -#~ "Kein Filter für E-Mail angegeben, es kann keine Bekanntmachung erstellt " -#~ "werden.\n" +#~ msgid "Could not read hostkeys file, specify hostkey file with -H!\n" +#~ msgstr "Fehler beim Lesen der Freunde-Liste von `%s'\n" #, fuzzy -#~ msgid "# bytes received via SMTP" -#~ msgstr "# Bytes empfangen über TCP" +#~ msgid "Could not open hostkeys file: %s\n" +#~ msgstr "Fehler beim Lesen der Freunde-Liste von `%s'\n" #, fuzzy -#~ msgid "# bytes sent via SMTP" -#~ msgstr "# Bytes gesendet über TCP" +#~ msgid "access (%s, X_OK) failed: %s\n" +#~ msgstr "`%s' schlug fehl: %s\n" #, fuzzy -#~ msgid "# bytes dropped by SMTP (outgoing)" -#~ msgstr "# Bytes verworfen von TCP (ausgehend)" +#~ msgid "stat (%s) failed: %s\n" +#~ msgstr "`%s' schlug fehl: %s\n" #, fuzzy #~ msgid "# Peers connected" @@ -6212,10 +7264,6 @@ msgstr "`%s' schlug bei Datei `%s' fehl. Ort: %s:%d. Fehler: %s\n" #~ msgid "Finished copying all blacklist files!\n" #~ msgstr "Fehler beim Lesen der Freunde-Liste von `%s'\n" -#, fuzzy -#~ msgid "Offering HELLO of peer %s to peer %s\n" -#~ msgstr "Verbindung zu %u.%u.%u.%u:%u fehlgeschlagen: %s\n" - #, fuzzy #~ msgid "Failed during blacklist file copying!\n" #~ msgstr "Fehler beim Lesen der Freunde-Liste von `%s'\n" @@ -6224,10 +7272,6 @@ msgstr "`%s' schlug bei Datei `%s' fehl. Ort: %s:%d. Fehler: %s\n" #~ msgid "# bytes payload received for other peers" #~ msgstr "# Bytes des Typs %d empfangen" -#, fuzzy -#~ msgid "# fast reconnects failed" -#~ msgstr "# verbundener Knoten" - #, fuzzy #~ msgid "# peers disconnected due to timeout" #~ msgstr "# geschlossener Verbindungen (HANGUP gesendet)" @@ -6244,10 +7288,6 @@ msgstr "`%s' schlug bei Datei `%s' fehl. Ort: %s:%d. Fehler: %s\n" #~ msgid "# unexpected CONNECT_ACK messages" #~ msgstr "COUNT Nachrichten versenden" -#, fuzzy -#~ msgid "# wlan session timeouts" -#~ msgstr "# Sitzungsschlüssel akzeptiert" - #, fuzzy #~ msgid "# wlan session created" #~ msgstr "# Sitzungsschlüssel akzeptiert" @@ -6329,9 +7369,6 @@ msgstr "`%s' schlug bei Datei `%s' fehl. Ort: %s:%d. Fehler: %s\n" #~ msgid "be verbose" #~ msgstr "umfangreiche Meldungen ausgeben" -#~ msgid "use configuration file FILENAME" -#~ msgstr "Konfigurationsdatei FILENAME verwenden" - #, fuzzy #~ msgid "Failed to stop service `%s'!\n" #~ msgstr "Fehler beim Binden an UDP Port %d.\n" @@ -6340,10 +7377,6 @@ msgstr "`%s' schlug bei Datei `%s' fehl. Ort: %s:%d. Fehler: %s\n" #~ msgid "Failed to start service `%s'!\n" #~ msgstr "Der Transportdienst auf Port %d konnte nicht gestartet werden.\n" -#, fuzzy -#~ msgid "Service `%s' is not running.\n" -#~ msgstr "`%s' ist keine Datei.\n" - #, fuzzy #~ msgid "Binary implementing service `%s' not known!\n" #~ msgstr "" @@ -6354,18 +7387,10 @@ msgstr "`%s' schlug bei Datei `%s' fehl. Ort: %s:%d. Fehler: %s\n" #~ msgid "Service `%s' stopped\n" #~ msgstr "Dienst gelöscht.\n" -#, fuzzy -#~ msgid "Unable to start service `%s': %s\n" -#~ msgstr "Fehler beim Speichern der Konfigurationsdatei `%s':" - #, fuzzy #~ msgid "Unable to accept connection for service `%s': %s\n" #~ msgstr "Fehler beim Speichern der Konfigurationsdatei `%s':" -#, fuzzy -#~ msgid "Peer `%s' plugin: `%s' address `%s'\n" -#~ msgstr "Knoten `%s' mit Vertrauen %8u und Adresse `%s'\n" - #, fuzzy #~ msgid "Failed to transmit request to DATASTORE.\n" #~ msgstr "Fehler beim Senden einer `%s' Anfrage an den SMTP Server.\n" @@ -6991,18 +8016,10 @@ msgstr "`%s' schlug bei Datei `%s' fehl. Ort: %s:%d. Fehler: %s\n" #~ msgid "Command `%s' failed with error code %u\n" #~ msgstr "`%s' schlug bei %s:%d mit dem Fehler %s fehl\n" -#, fuzzy -#~ msgid "Invalid process priority `%s'\n" -#~ msgstr "Ungültige Antwort auf `%s'.\n" - #, fuzzy #~ msgid "Real-time delay violation (%llu ms) at %s:%u\n" #~ msgstr "Unerwartete sehr große Allokierung (%u Bytes) bei %s:%d!\n" -#, fuzzy -#~ msgid "`%s' failed with error code %d: %s\n" -#~ msgstr "`%s' schlug bei %s:%d mit dem Fehler %s fehl\n" - #, fuzzy #~ msgid "Deadlock due to `%s'.\n" #~ msgstr "Durch `%s' ist ein Deadlock bei %s:%d entstanden\n" @@ -7068,9 +8085,6 @@ msgstr "`%s' schlug bei Datei `%s' fehl. Ort: %s:%d. Fehler: %s\n" #~ msgid "output in gnuplot format" #~ msgstr "Ausgabe im gnuplot Format" -#~ msgid "number of iterations" -#~ msgstr "Anzahl an Durchläufen" - #~ msgid "number of messages to use per iteration" #~ msgstr "Anzahl an Nachrichten, die pro Durchlauf verwendet wird" @@ -7383,9 +8397,6 @@ msgstr "`%s' schlug bei Datei `%s' fehl. Ort: %s:%d. Fehler: %s\n" #~ msgid "# session keys sent" #~ msgstr "# Sitzungsschlüssel gesendet" -#~ msgid "# sessions established" -#~ msgstr "# Sitzungen aufgebaut" - #~ msgid "automate creation of a namespace by starting a collection" #~ msgstr "" #~ "Erstellung eines Namespaces durch das Anfangen einer Collection " @@ -7991,9 +9002,6 @@ msgstr "`%s' schlug bei Datei `%s' fehl. Ort: %s:%d. Fehler: %s\n" #~ msgid "specifies after how many MS to time-out" #~ msgstr "Gibt an, nach wievielen MS die Zeit abgelaufen sein soll" -#~ msgid "Testing transport(s) %s\n" -#~ msgstr "Teste Transport(e) %s\n" - #~ msgid "Available transport(s): %s\n" #~ msgstr "Verfügbare(r) Transport(e): %s\n" @@ -8120,11 +9128,6 @@ msgstr "`%s' schlug bei Datei `%s' fehl. Ort: %s:%d. Fehler: %s\n" #~ msgid "This is equivalent to the -H option. The format is IP:PORT." #~ msgstr "Wert der Option anzeigen" -#, fuzzy -#~ msgid "What is the path to the configuration file for gnunetd?" -#~ msgstr "" -#~ "Einen Wert aus der Konfigurationsdatei auf der Standardausgabe ausgeben" - #, fuzzy #~ msgid "General options" #~ msgstr "Weitere Einstellungen" @@ -8388,9 +9391,6 @@ msgstr "`%s' schlug bei Datei `%s' fehl. Ort: %s:%d. Fehler: %s\n" #~ msgid "Message received from peer is invalid.\n" #~ msgstr "Empfangene Nachricht ist ungültig.\n" -#~ msgid "Maximum number of chat clients reached.\n" -#~ msgstr "Maximale Anzahl an Chat Clients erreicht.\n" - #~ msgid "Now %d of %d chat clients at this node.\n" #~ msgstr "Jetzt sind %d von %d auf diesem Knoten.\n" @@ -8436,9 +9436,6 @@ msgstr "`%s' schlug bei Datei `%s' fehl. Ort: %s:%d. Fehler: %s\n" #~ msgid "Protocol violation on socket. Expected command.\n" #~ msgstr "Protokollverletzung auf Socket. Kommando erwartet.\n" -#~ msgid "Start GNUnet testbed controller." -#~ msgstr "GNUnet testbed Controller starten." - #~ msgid "Malformed entry in the configuration in section %s under %s: %s\n" #~ msgstr "" #~ "Beschädigter Eintrag in der Konfigurationsdatei in Sektion %s unter %s: " @@ -8454,9 +9451,6 @@ msgstr "`%s' schlug bei Datei `%s' fehl. Ort: %s:%d. Fehler: %s\n" #~ msgstr "" #~ "Das TESTBED konnte keine Hello Nachricht für das Protokoll %u erzeugen\n" -#~ msgid "received invalid `%s' message\n" -#~ msgstr "ungültige `%s' Nachricht empfangen\n" - #~ msgid "received invalid `%s' message (empty module name)\n" #~ msgstr "ungültige `%s' Nachricht empfangen (leerer Modulname)\n" @@ -8508,9 +9502,6 @@ msgstr "`%s' schlug bei Datei `%s' fehl. Ort: %s:%d. Fehler: %s\n" #~ msgstr "" #~ "Testbed konnte nicht registriert werden, Host `%s' ist nicht bekannt.\n" -#~ msgid "Failed to send HTTP request to host `%s': %s\n" -#~ msgstr "HTTP Anfrage konnte nicht an Host `%s' gesendet werden: %s\n" - #~ msgid "Failed so send HTTP request `%s' to host `%s': %s\n" #~ msgstr "Fehler beim Senden der HTTP Anfrage `%s' an Host `%s': %s\n" @@ -8723,9 +9714,6 @@ msgstr "`%s' schlug bei Datei `%s' fehl. Ort: %s:%d. Fehler: %s\n" #~ msgid "Other settings" #~ msgstr "Weitere Einstellungen" -#~ msgid "Finish" -#~ msgstr "Fertigstellen" - #~ msgid "" #~ "Define the user and the group owning the GNUnet service here.\n" #~ "\n" @@ -8760,10 +9748,6 @@ msgstr "`%s' schlug bei Datei `%s' fehl. Ort: %s:%d. Fehler: %s\n" #~ msgid "Group:" #~ msgstr "Gruppe:" -#, fuzzy -#~ msgid "gnunet-setup" -#~ msgstr "gnunet-update ausführen" - #, fuzzy #~ msgid "Save configuration" #~ msgstr "GNUnet Konfiguration" @@ -8960,9 +9944,6 @@ msgstr "`%s' schlug bei Datei `%s' fehl. Ort: %s:%d. Fehler: %s\n" #~ msgid "Invalid response to `%s' from `%s'\n" #~ msgstr "Ungültige Antwort auf `%s' von `%s'\n" -#~ msgid "Received invalid RPC `%s'.\n" -#~ msgstr "Ungültiger RPC `%s' empfangen.\n" - #~ msgid "RPC for `%s' received for table that we do not participate in!\n" #~ msgstr "" #~ "RPC für `%s' empfangen für eine Tabelle, an der wir nicht beteiligt " @@ -9094,9 +10075,6 @@ msgstr "`%s' schlug bei Datei `%s' fehl. Ort: %s:%d. Fehler: %s\n" #~ msgid "Joined DHT. Press CTRL-C to leave.\n" #~ msgstr "Der DHT beigetreten. Drücken Sie STRG-C, um sie zu verlassen.\n" -#~ msgid "`%s' failed: table not found!\n" -#~ msgstr "`%s' fehlgeschlagen: Tabelle nicht gefunden!\n" - #~ msgid "sendAck failed. Terminating connection to client.\n" #~ msgstr "sendAck fehlgeschlagen. Beende Verbindung zu Client.\n" @@ -9301,9 +10279,6 @@ msgstr "`%s' schlug bei Datei `%s' fehl. Ort: %s:%d. Fehler: %s\n" #~ msgid "process directories recursively" #~ msgstr "Verzeichnisse rekursiv bearbeiten" -#~ msgid "You must pass a positive number to the `%s' option.\n" -#~ msgstr "Sie müssen eine positive Zahl zu der Option `%s' übergeben.\n" - #~ msgid "Only one file or directory can be specified at a time.\n" #~ msgstr "Nur eine Datei oder Verzeichnis kann auf einmal angegeben werden.\n" @@ -9360,13 +10335,6 @@ msgstr "`%s' schlug bei Datei `%s' fehl. Ort: %s:%d. Fehler: %s\n" #~ msgid "Option `%s' makes no sense without option `%s'." #~ msgstr "Option `%s' macht keinen Sinn ohne die Option `%s'." -#~ msgid "" -#~ "\n" -#~ "Exiting.\n" -#~ msgstr "" -#~ "\n" -#~ "Abbruch.\n" - #~ msgid "Updated data for %d applications.\n" #~ msgstr "Daten für %d Anwendungen wurden aktualisiert.\n" diff --git a/po/es.gmo b/po/es.gmo index 07ff667..814e650 100644 Binary files a/po/es.gmo and b/po/es.gmo differ diff --git a/po/es.po b/po/es.po index 0174aca..df51fe2 100644 --- a/po/es.po +++ b/po/es.po @@ -7,7 +7,7 @@ msgid "" msgstr "" "Project-Id-Version: GNUnet 0.7.0e\n" "Report-Msgid-Bugs-To: gnunet-developers@mail.gnu.org\n" -"POT-Creation-Date: 2012-06-05 15:47+0200\n" +"POT-Creation-Date: 2013-02-05 19:22+0100\n" "PO-Revision-Date: 2006-06-29 12:05+0200\n" "Last-Translator: Miguel Angel Arruga \n" "Language-Team: Spanish\n" @@ -17,270 +17,216 @@ msgstr "" "Content-Transfer-Encoding: 8bit\n" "Plural-Forms: nplurals=2; plural=(n != 1);\n" -#: src/arm/arm_api.c:165 +#: src/arm/arm_api.c:162 msgid "Failed to transmit shutdown request to client.\n" msgstr "" -#: src/arm/arm_api.c:349 -#, fuzzy, c-format -msgid "Configuration failes to specify option `%s' in section `%s'!\n" -msgstr "" -"El fichero de configuración debe especificar el directorio para almacenar " -"los datos FS en la sección '%s' bajo '%s'.\n" - -#: src/arm/arm_api.c:363 -#, fuzzy, c-format -msgid "Configuration fails to specify option `%s' in section `%s'!\n" -msgstr "" -"El fichero de configuración debe especificar el directorio para almacenar " -"los datos FS en la sección '%s' bajo '%s'.\n" - -#: src/arm/arm_api.c:432 -#, fuzzy, c-format -msgid "Error receiving response to `%s' request from ARM for service `%s'\n" -msgstr "Recibida respuesta anómala a'%s' del par '%s'.\n" - -#: src/arm/arm_api.c:485 -#, c-format -msgid "Requesting start of service `%s'.\n" -msgstr "" - -#: src/arm/arm_api.c:486 -#, c-format -msgid "Requesting termination of service `%s'.\n" -msgstr "" - -#: src/arm/arm_api.c:507 -#, c-format -msgid "Error while trying to transmit request to start `%s' to ARM\n" -msgstr "" - -#: src/arm/arm_api.c:508 -#, c-format -msgid "Error while trying to transmit request to stop `%s' to ARM\n" -msgstr "" - -#: src/arm/arm_api.c:540 -#, fuzzy, c-format -msgid "Asked to start service `%s' within %llu ms\n" -msgstr "'%s': No se recibió el mensaje en %llu ms.\n" - -#: src/arm/arm_api.c:612 -#, fuzzy, c-format -msgid "Stopping service `%s' within %llu ms\n" -msgstr "No se ha recibido una respuesta en %llums.\n" - -#: src/arm/gnunet-arm.c:159 +#: src/arm/gnunet-arm.c:166 #, fuzzy, c-format msgid "Service `%s' is unknown to ARM.\n" msgstr "El espacio '%s' ha sido valorado con un %d.\n" -#: src/arm/gnunet-arm.c:164 +#: src/arm/gnunet-arm.c:171 #, fuzzy, c-format msgid "Service `%s' has been stopped.\n" msgstr "Servicio eliminado.\n" -#: src/arm/gnunet-arm.c:167 +#: src/arm/gnunet-arm.c:174 #, fuzzy, c-format msgid "Service `%s' was already running.\n" msgstr "¡Esta búsqueda está aún pendiente!\n" -#: src/arm/gnunet-arm.c:172 +#: src/arm/gnunet-arm.c:179 #, fuzzy, c-format msgid "Service `%s' has been started.\n" msgstr "Servicio eliminado.\n" -#: src/arm/gnunet-arm.c:175 +#: src/arm/gnunet-arm.c:182 #, fuzzy, c-format msgid "Service `%s' was already being stopped.\n" msgstr "Servicio eliminado.\n" -#: src/arm/gnunet-arm.c:179 +#: src/arm/gnunet-arm.c:186 #, fuzzy, c-format msgid "Service `%s' was already not running.\n" msgstr "¡Esta búsqueda está aún pendiente!\n" -#: src/arm/gnunet-arm.c:183 +#: src/arm/gnunet-arm.c:190 #, fuzzy msgid "Request ignored as ARM is shutting down.\n" msgstr "'%s' se esta cerrando.\n" -#: src/arm/gnunet-arm.c:187 +#: src/arm/gnunet-arm.c:194 #, fuzzy msgid "Error communicating with ARM service.\n" msgstr "Imprime información de los pares de GNUnet." -#: src/arm/gnunet-arm.c:191 +#: src/arm/gnunet-arm.c:198 #, fuzzy msgid "Timeout communicating with ARM service.\n" msgstr "Imprime información de los pares de GNUnet." -#: src/arm/gnunet-arm.c:195 +#: src/arm/gnunet-arm.c:202 #, fuzzy msgid "Operation failed.\n" msgstr "La verificación de la firma RSA fallo en %s: %d: %s\n" -#: src/arm/gnunet-arm.c:199 +#: src/arm/gnunet-arm.c:206 msgid "Unknown response code from ARM.\n" msgstr "" -#: src/arm/gnunet-arm.c:222 +#: src/arm/gnunet-arm.c:229 #, fuzzy msgid "Error communicating with ARM. ARM not running?\n" msgstr "Imprime información de los pares de GNUnet." -#: src/arm/gnunet-arm.c:225 +#: src/arm/gnunet-arm.c:232 #, fuzzy msgid "Running services:\n" msgstr "Iniciada colección '%s'.\n" -#: src/arm/gnunet-arm.c:249 -#, c-format -msgid "Fatal configuration error: `%s' option in section `%s' missing.\n" -msgstr "" - -#: src/arm/gnunet-arm.c:257 src/arm/gnunet-arm.c:357 src/arm/gnunet-arm.c:373 -msgid "Fatal error initializing ARM API.\n" -msgstr "" - -#: src/arm/gnunet-arm.c:280 +#: src/arm/gnunet-arm.c:253 #, fuzzy, c-format msgid "Failed to remove configuration file %s\n" msgstr "Imposible guardar el fichero de configuración '%s':" -#: src/arm/gnunet-arm.c:286 +#: src/arm/gnunet-arm.c:259 #, fuzzy, c-format msgid "Failed to remove servicehome directory %s\n" msgstr "Error en el formato del fichero (¿no es un directorio de GNUnet?)\n" -#: src/arm/gnunet-arm.c:407 +#: src/arm/gnunet-arm.c:322 src/arm/gnunet-arm.c:407 src/arm/gnunet-arm.c:424 +msgid "Fatal error initializing ARM API.\n" +msgstr "" + +#: src/arm/gnunet-arm.c:453 msgid "stop all GNUnet services" msgstr "" -#: src/arm/gnunet-arm.c:409 +#: src/arm/gnunet-arm.c:455 msgid "start a particular service" msgstr "" -#: src/arm/gnunet-arm.c:411 +#: src/arm/gnunet-arm.c:457 msgid "stop a particular service" msgstr "" -#: src/arm/gnunet-arm.c:413 +#: src/arm/gnunet-arm.c:459 msgid "start all GNUnet default services" msgstr "" -#: src/arm/gnunet-arm.c:416 +#: src/arm/gnunet-arm.c:462 msgid "stop and start all GNUnet default services" msgstr "" -#: src/arm/gnunet-arm.c:419 +#: src/arm/gnunet-arm.c:465 msgid "delete config file and directory on exit" msgstr "" -#: src/arm/gnunet-arm.c:421 +#: src/arm/gnunet-arm.c:467 msgid "don't print status messages" msgstr "" -#: src/arm/gnunet-arm.c:424 +#: src/arm/gnunet-arm.c:470 #, fuzzy -msgid "timeout for completing current operation" +msgid "timeout in MSECS milliseconds for completing current operation" msgstr "tiempo para esperar hasta completar una iteración (en ms)" -#: src/arm/gnunet-arm.c:426 -msgid "List currently running services" +#: src/arm/gnunet-arm.c:472 +#, fuzzy +msgid "list currently running services" +msgstr "Iniciada colección '%s'.\n" + +#: src/arm/gnunet-arm.c:474 +msgid "don't let gnunet-service-arm inherit standard output" +msgstr "" + +#: src/arm/gnunet-arm.c:476 +msgid "don't let gnunet-service-arm inherit standard error" msgstr "" -#: src/arm/gnunet-arm.c:437 +#: src/arm/gnunet-arm.c:487 msgid "Control services and the Automated Restart Manager (ARM)" msgstr "" -#: src/arm/gnunet-service-arm.c:332 +#: src/arm/gnunet-service-arm.c:345 #, fuzzy, c-format msgid "Failed to start service `%s'\n" msgstr "Falló al comenzar la recolección.\n" -#: src/arm/gnunet-service-arm.c:335 +#: src/arm/gnunet-service-arm.c:348 #, fuzzy, c-format msgid "Starting service `%s'\n" msgstr "Iniciada colección '%s'.\n" -#: src/arm/gnunet-service-arm.c:361 +#: src/arm/gnunet-service-arm.c:374 #, fuzzy msgid "Could not send status result to client\n" msgstr "Imposible mandar el mensaje a gnunetd\n" -#: src/arm/gnunet-service-arm.c:393 +#: src/arm/gnunet-service-arm.c:406 #, fuzzy msgid "Could not send list result to client\n" msgstr "Imposible mandar el mensaje a gnunetd\n" -#: src/arm/gnunet-service-arm.c:523 +#: src/arm/gnunet-service-arm.c:537 #, fuzzy, c-format msgid "Unable to create socket for service `%s': %s\n" msgstr "Imposible crear la cuenta de usuario:" -#: src/arm/gnunet-service-arm.c:545 +#: src/arm/gnunet-service-arm.c:559 #, c-format msgid "Unable to bind listening socket for service `%s' to address `%s': %s\n" msgstr "" -#: src/arm/gnunet-service-arm.c:559 +#: src/arm/gnunet-service-arm.c:573 #, c-format msgid "ARM now monitors connections to service `%s' at `%s'\n" msgstr "" -#: src/arm/gnunet-service-arm.c:667 +#: src/arm/gnunet-service-arm.c:681 #, fuzzy, c-format msgid "Preparing to stop `%s'\n" msgstr "Iniciada colección '%s'.\n" -#: src/arm/gnunet-service-arm.c:878 +#: src/arm/gnunet-service-arm.c:892 #, fuzzy, c-format msgid "Restarting service `%s'.\n" msgstr "Iniciada colección '%s'.\n" -#: src/arm/gnunet-service-arm.c:970 +#: src/arm/gnunet-service-arm.c:985 msgid "exit" msgstr "" -#: src/arm/gnunet-service-arm.c:975 +#: src/arm/gnunet-service-arm.c:990 msgid "signal" msgstr "" -#: src/arm/gnunet-service-arm.c:980 +#: src/arm/gnunet-service-arm.c:995 msgid "unknown" msgstr "desconocido" -#: src/arm/gnunet-service-arm.c:986 +#: src/arm/gnunet-service-arm.c:1001 #, fuzzy, c-format -msgid "Service `%s' took %llu ms to terminate\n" +msgid "Service `%s' took %s to terminate\n" msgstr "Servicio eliminado.\n" -#: src/arm/gnunet-service-arm.c:1021 +#: src/arm/gnunet-service-arm.c:1036 #, c-format msgid "Service `%s' terminated with status %s/%d, will restart in %llu ms\n" msgstr "" -#: src/arm/gnunet-service-arm.c:1127 -#, fuzzy, c-format -msgid "Configuration file `%s' for service `%s' not valid: %s\n" -msgstr "Fichero de configuración '%s' creado.\n" - -#: src/arm/gnunet-service-arm.c:1129 -msgid "option missing" -msgstr "" - -#: src/arm/gnunet-service-arm.c:1213 +#: src/arm/gnunet-service-arm.c:1228 #, fuzzy, c-format msgid "Starting default services `%s'\n" msgstr "Iniciada colección '%s'.\n" -#: src/arm/gnunet-service-arm.c:1224 +#: src/arm/gnunet-service-arm.c:1239 #, c-format msgid "Default service `%s' not configured correctly!\n" msgstr "" -#: src/arm/gnunet-service-arm.c:1238 +#: src/arm/gnunet-service-arm.c:1253 msgid "" "No default services configured, GNUnet will not really start right now.\n" msgstr "" @@ -289,301 +235,265 @@ msgstr "" msgid "Initiating shutdown as requested by client.\n" msgstr "" -#: src/block/block.c:105 -#, fuzzy, c-format -msgid "Loading block plugin `%s'\n" -msgstr "Probando transporte(s) %s\n" - -#: src/chat/chat.c:175 -#, fuzzy -msgid "Could not transmit confirmation receipt\n" -msgstr "Imposible acceder a la información del espacio.\n" - -#: src/chat/chat.c:283 -msgid "The current user must be the the first one joined\n" -msgstr "" - -#: src/chat/chat.c:412 -#, fuzzy, c-format -msgid "Unknown message type: '%u'\n" -msgstr "Operación desconocida '%s'\n" - -#: src/chat/chat.c:472 -#, fuzzy, c-format -msgid "Configuration option `%s' in section `%s' missing\n" -msgstr "Fichero de configuración '%s' creado.\n" - -#: src/chat/chat.c:480 +#: src/ats/ats_api_performance.c:465 #, fuzzy, c-format -msgid "Failed to access chat home directory `%s'\n" -msgstr "Error en el formato del fichero (¿no es un directorio de GNUnet?)\n" +msgid "Received %s message\n" +msgstr "recibido mensaje '%s' no válido\n" -#: src/chat/chat.c:498 +#: src/ats/ats_api_performance.c:508 #, fuzzy, c-format -msgid "Failed to create/open key in file `%s'\n" -msgstr "Fichero almacenado en '%s'.\n" - -#: src/chat/chat.c:559 -#, fuzzy -msgid "Could not serialize metadata\n" -msgstr "¡Imposible inicializar libgnunetutil!\n" - -#: src/chat/chat.c:674 -#, fuzzy -msgid "Failed to connect to the chat service\n" -msgstr "Fallo al conectar a gnunetd.\n" - -#: src/chat/chat.c:680 -msgid "Undefined mandatory parameter: joinCallback\n" -msgstr "" - -#: src/chat/chat.c:686 -msgid "Undefined mandatory parameter: messageCallback\n" -msgstr "" - -#: src/chat/chat.c:692 -msgid "Undefined mandatory parameter: memberCallback\n" -msgstr "" +msgid "Received last message for %s \n" +msgstr "GAP recibido contenido no válido de '%s'\n" -#: src/chat/gnunet-chat.c:93 -msgid "Joined\n" +#: src/ats/gnunet-service-ats_addresses.c:993 +#: src/ats/gnunet-service-ats_addresses.c:1027 +#, c-format +msgid "" +"Could not load quota for network `%s': `%s', assigning default bandwidth " +"%llu\n" msgstr "" -#: src/chat/gnunet-chat.c:125 src/chat/gnunet-chat.c:133 -#: src/chat/gnunet-chat.c:213 src/chat/gnunet-chat.c:253 -#: src/chat/gnunet-chat.c:329 src/chat/gnunet-chat.c:371 -#: src/chat/gnunet-chat.c:400 src/chat/gnunet-chat.c:700 -msgid "anonymous" +#: src/ats/gnunet-service-ats_addresses.c:999 +#, c-format +msgid "Outbound quota configure for network `%s' is %llu\n" msgstr "" -#: src/chat/gnunet-chat.c:144 -#, fuzzy, c-format -msgid "(%s) `%s' said: %s\n" -msgstr "'%s' %s falló: %s\n" - -#: src/chat/gnunet-chat.c:147 src/chat/gnunet-chat.c:150 -#, fuzzy, c-format -msgid "(%s) `%s' said to you: %s\n" -msgstr "'%s' %s falló: %s\n" - -#: src/chat/gnunet-chat.c:153 -#, fuzzy, c-format -msgid "(%s) `%s' said for sure: %s\n" -msgstr "'%s' %s falló: %s\n" - -#: src/chat/gnunet-chat.c:156 -#, fuzzy, c-format -msgid "(%s) `%s' said to you for sure: %s\n" -msgstr "'%s' falló con el código de error %s: %s" - -#: src/chat/gnunet-chat.c:159 -#, fuzzy, c-format -msgid "(%s) `%s' was confirmed that you received: %s\n" -msgstr "'%s' falló con el código de error %d: %s" - -#: src/chat/gnunet-chat.c:162 -#, fuzzy, c-format -msgid "(%s) `%s' was confirmed that you and only you received: %s\n" -msgstr "'%s' falló con el código de error %d: %s" - -#: src/chat/gnunet-chat.c:165 -#, fuzzy, c-format -msgid "(%s) `%s' was confirmed that you received from him or her: %s\n" -msgstr "'%s' falló con el código de error %d: %s" - -#: src/chat/gnunet-chat.c:170 -#, fuzzy, c-format +#: src/ats/gnunet-service-ats_addresses.c:1006 +#, c-format msgid "" -"(%s) `%s' was confirmed that you and only you received from him or her: %s\n" -msgstr "'%s' falló con el código de error %d: %s" - -#: src/chat/gnunet-chat.c:173 -#, fuzzy, c-format -msgid "(%s) `%s' said off the record: %s\n" -msgstr "'%s' falló con el código de error %s: %s" +"No outbound quota configured for network `%s', assigning default bandwidth " +"%llu\n" +msgstr "" -#: src/chat/gnunet-chat.c:176 +#: src/ats/gnunet-service-ats_addresses.c:1033 #, c-format -msgid "(%s) <%s> said using an unknown message type: %s\n" +msgid "Inbound quota configured for network `%s' is %llu\n" msgstr "" -#: src/chat/gnunet-chat.c:217 +#: src/ats/gnunet-service-ats_addresses.c:1040 #, c-format -msgid "'%s' acknowledged message #%d\n" +msgid "" +"No outbound quota configure for network `%s', assigning default bandwidth " +"%llu\n" msgstr "" -#: src/chat/gnunet-chat.c:260 +#: src/ats-tool/gnunet-ats.c:141 #, c-format -msgid "`%s' entered the room\n" +msgid "%u address resolutions had a timeout\n" msgstr "" -#: src/chat/gnunet-chat.c:260 +#: src/ats-tool/gnunet-ats.c:143 #, c-format -msgid "`%s' left the room\n" +msgid "ATS returned results for %u addresses\n" msgstr "" -#: src/chat/gnunet-chat.c:321 src/chat/gnunet-chat.c:363 -#, fuzzy -msgid "Could not change username\n" -msgstr "Imposible crear el espacio '%s' (¿existe?).\n" - -#: src/chat/gnunet-chat.c:334 src/chat/gnunet-chat.c:702 +#: src/ats-tool/gnunet-ats.c:199 #, fuzzy, c-format -msgid "Joining room `%s' as user `%s'...\n" -msgstr "Respuesta inválida a '%s' del par '%s'.\n" +msgid "" +"Peer `%s' plugin `%s', address `%s', `%s' bw out: %u Bytes/s, bw in %u Bytes/" +"s, %s\n" +msgstr "Par '%s' con credibilidad %8u y dirección '%s'\n" -#: src/chat/gnunet-chat.c:373 -#, fuzzy, c-format -msgid "Changed username to `%s'\n" -msgstr "Imposible cambiar el usuario/grupo a '%s': %s\n" +#: src/ats-tool/gnunet-ats.c:326 +#, c-format +msgid "Quota for network `%11s' (in/out): %10s / %10s\n" +msgstr "" -#: src/chat/gnunet-chat.c:388 +#: src/ats-tool/gnunet-ats.c:345 src/namestore/gnunet-namestore.c:610 +#: src/transport/gnunet-transport.c:813 #, fuzzy, c-format -msgid "Users in room `%s': " -msgstr "Fichero almacenado en '%s'.\n" - -#: src/chat/gnunet-chat.c:434 -msgid "Syntax: /msg USERNAME MESSAGE" -msgstr "" +msgid "Service `%s' is not running\n" +msgstr "'%s' no es un fichero.\n" -#: src/chat/gnunet-chat.c:443 -#, c-format -msgid "Unknown user `%s'. Make sure you specify its numeric suffix, if any.\n" -msgstr "" +#: src/ats-tool/gnunet-ats.c:355 src/transport/gnunet-transport.c:819 +#, fuzzy, c-format +msgid "Failed to parse peer identity `%s'\n" +msgstr "Falló al actualizar los datos del módulo '%s'\n" -#: src/chat/gnunet-chat.c:460 +#: src/ats-tool/gnunet-ats.c:363 #, c-format -msgid "User `%s' is currently not in the room!\n" +msgid "Please select one operation : %s or %s or %s or %s or %s\n" msgstr "" -#: src/chat/gnunet-chat.c:513 +#: src/ats-tool/gnunet-ats.c:379 src/ats-tool/gnunet-ats.c:398 +#: src/ats-tool/gnunet-ats.c:415 src/ats-tool/gnunet-ats.c:440 #, fuzzy, c-format -msgid "Unknown command `%s'\n" -msgstr "Operación desconocida '%s'\n" - -#: src/chat/gnunet-chat.c:524 -msgid "" -"Use `/join #roomname' to join a chat room. Joining a room will cause you to " -"leave the current room" -msgstr "" +msgid "Cannot connect to ATS service, exiting...\n" +msgstr "Fallo al conectar a gnunetd.\n" -#: src/chat/gnunet-chat.c:528 -msgid "" -"Use `/nick nickname' to change your nickname. This will cause you to leave " -"the current room and immediately rejoin it with the new name." -msgstr "" +#: src/ats-tool/gnunet-ats.c:388 src/ats-tool/gnunet-ats.c:405 +#, fuzzy, c-format +msgid "Cannot issue request to ATS service, exiting...\n" +msgstr "Fallo al conectar a gnunetd.\n" -#: src/chat/gnunet-chat.c:532 -msgid "" -"Use `/msg nickname message' to send a private message to the specified user" +#: src/ats-tool/gnunet-ats.c:433 +msgid "Type required\n" msgstr "" -#: src/chat/gnunet-chat.c:535 -msgid "The `/notice' command is an alias for `/msg'" +#: src/ats-tool/gnunet-ats.c:490 +msgid "get list of active addresses currently used" msgstr "" -#: src/chat/gnunet-chat.c:537 -msgid "The `/query' command is an alias for `/msg'" +#: src/ats-tool/gnunet-ats.c:493 +msgid "get list of all active addresses" msgstr "" -#: src/chat/gnunet-chat.c:539 -msgid "Use `/sig message' to send a signed public message" -msgstr "" +#: src/ats-tool/gnunet-ats.c:496 +#, fuzzy +msgid "do not resolve IP addresses to hostnames" +msgstr "GNUnet usa ahora la dirección IP %u.%u.%u.%u.\n" -#: src/chat/gnunet-chat.c:542 -msgid "Use `/ack message' to require signed acknowledgment of the message" +#: src/ats-tool/gnunet-ats.c:499 +msgid "monitor mode" msgstr "" -#: src/chat/gnunet-chat.c:545 -msgid "Use `/anonymous message' to send a public anonymous message" -msgstr "" +#: src/ats-tool/gnunet-ats.c:502 +#, fuzzy +msgid "set preference for the given peer" +msgstr "Imprime información de los pares de GNUnet." -#: src/chat/gnunet-chat.c:547 -msgid "The `/anon' command is an alias for `/anonymous'" +#: src/ats-tool/gnunet-ats.c:505 +msgid "print all configured quotas" msgstr "" -#: src/chat/gnunet-chat.c:549 -msgid "Use `/quit' to terminate gnunet-chat" +#: src/ats-tool/gnunet-ats.c:508 +msgid "peer id" msgstr "" -#: src/chat/gnunet-chat.c:551 -msgid "The `/leave' command is an alias for `/quit'" +#: src/ats-tool/gnunet-ats.c:511 +msgid "preference type to set: latency | bandwidth" msgstr "" -#: src/chat/gnunet-chat.c:554 -msgid "Use `/names' to list all of the current members in the chat room" +#: src/ats-tool/gnunet-ats.c:514 +msgid "preference value" msgstr "" -#: src/chat/gnunet-chat.c:556 -msgid "Use `/help command' to get help for a specific command" +#: src/ats-tool/gnunet-ats.c:517 +msgid "verbose output (include ATS address properties)" msgstr "" -#: src/chat/gnunet-chat.c:672 +#: src/ats-tool/gnunet-ats.c:526 #, fuzzy -msgid "You must specify a nickname\n" -msgstr "¡Debes especificar un receptor!\n" +msgid "Print information about ATS state" +msgstr "Imprime información de los pares de GNUnet." -#: src/chat/gnunet-chat.c:688 +#: src/block/block.c:105 #, fuzzy, c-format -msgid "Failed to join room `%s'\n" -msgstr "Fichero almacenado en '%s'.\n" +msgid "Loading block plugin `%s'\n" +msgstr "Probando transporte(s) %s\n" -#: src/chat/gnunet-chat.c:727 -msgid "set the nickname to use (required)" -msgstr "" +#: src/consensus/gnunet-consensus.c:317 +#, fuzzy +msgid "number of peers in consensus" +msgstr "número de repeticiones" -#: src/chat/gnunet-chat.c:730 -msgid "set the chat room to join" +#: src/consensus/gnunet-consensus.c:320 +msgid "how many peers receive one value?" msgstr "" -#: src/chat/gnunet-chat.c:742 -msgid "Join a chat on GNUnet." -msgstr "" +#: src/consensus/gnunet-consensus.c:323 +#, fuzzy +msgid "number of values" +msgstr "número de repeticiones" -#: src/chat/gnunet-service-chat.c:267 +#: src/consensus/gnunet-consensus.c:326 #, fuzzy -msgid "Failed to queue a message notification\n" -msgstr "Imposible guardar la configuración" +msgid "consensus timeout" +msgstr "# claves de la sesión aceptadas" -#: src/chat/gnunet-service-chat.c:546 +#: src/consensus/gnunet-consensus-ibf.c:176 #, fuzzy -msgid "Failed to queue a join notification\n" -msgstr "Imposible guardar la configuración" +msgid "number of element in set A-B" +msgstr "número de repeticiones" -#: src/chat/gnunet-service-chat.c:729 +#: src/consensus/gnunet-consensus-ibf.c:179 #, fuzzy -msgid "Failed to queue a confirmation receipt\n" -msgstr "Imposible guardar la configuración" +msgid "number of element in set B-A" +msgstr "número de repeticiones" + +#: src/consensus/gnunet-consensus-ibf.c:182 +msgid "number of common elements in A and B" +msgstr "" + +#: src/consensus/gnunet-consensus-ibf.c:185 +msgid "hash num" +msgstr "" + +#: src/consensus/gnunet-consensus-ibf.c:188 +msgid "ibf size" +msgstr "" + +#: src/consensus/gnunet-consensus-start-peers.c:158 +msgid "start peers with the given template configuration" +msgstr "" -#: src/chat/gnunet-service-chat.c:907 +#: src/consensus/gnunet-consensus-start-peers.c:161 #, fuzzy -msgid "Failed to queue a leave notification\n" -msgstr "Imposible guardar la configuración" +msgid "number of peers to start" +msgstr "número de repeticiones" -#: src/core/core_api.c:786 +#: src/core/core_api.c:755 msgid "Client was disconnected from core service, trying to reconnect.\n" msgstr "" -#: src/core/gnunet-core.c:54 src/peerinfo-tool/gnunet-peerinfo.c:286 +#: src/core/gnunet-core.c:86 src/peerinfo-tool/gnunet-peerinfo.c:214 #, fuzzy, c-format msgid "Peer `%s'\n" msgstr "Yo soy el par '%s'.\n" -#: src/core/gnunet-core.c:72 src/peerinfo-tool/gnunet-peerinfo.c:817 +#: src/core/gnunet-core.c:119 src/core/gnunet-core.c:147 +#: src/transport/gnunet-transport.c:612 src/transport/gnunet-transport.c:636 +#, c-format +msgid "%24s: %-17s %4s (%u connections in total)\n" +msgstr "" + +#: src/core/gnunet-core.c:121 src/transport/gnunet-transport.c:614 +#, fuzzy +msgid "Connected to" +msgstr "'%s' conectado a '%s'.\n" + +#: src/core/gnunet-core.c:149 src/transport/gnunet-transport.c:638 +#, fuzzy +msgid "Disconnected from" +msgstr "'%s' conectado a '%s'.\n" + +#: src/core/gnunet-core.c:174 src/mesh/gnunet-mesh.c:176 +#: src/peerinfo-tool/gnunet-peerinfo.c:541 #, fuzzy, c-format msgid "Invalid command line argument `%s'\n" msgstr "Argumentos en la linea de comandos inválidos:\n" -#: src/core/gnunet-core.c:95 +#: src/core/gnunet-core.c:211 src/transport/gnunet-transport.c:1005 +#, fuzzy +msgid "provide information about all current connections (continuously)" +msgstr "Imprime información de los pares de GNUnet." + +#: src/core/gnunet-core.c:222 #, fuzzy msgid "Print information about connected peers." msgstr "Imprime información de los pares de GNUnet." -#: src/core/gnunet-service-core.c:97 +#: src/core/gnunet-service-core.c:109 +#, fuzzy, c-format +msgid "Failed to read hostkey: %s\n" +msgstr "Falló al comenzar la recolección.\n" + +#: src/core/gnunet-service-core.c:123 #, c-format msgid "Core service of `%4s' ready.\n" msgstr "" +#: src/core/gnunet-service-core.c:149 +#, fuzzy +msgid "Core service is lacking HOSTKEY configuration setting. Exiting.\n" +msgstr "Configuración de GNUnet" + +#: src/core/gnunet-service-core.c:163 +#: src/transport/gnunet-service-transport.c:737 +#, fuzzy +msgid "Transport service is unable to access hostkey. Exiting.\n" +msgstr "Imposible acceder a la información del espacio.\n" + #: src/core/gnunet-service-core_clients.c:370 #, fuzzy msgid "# send requests dropped (disconnected)" @@ -594,7 +504,7 @@ msgstr "# Anuncios de los pares recibidos" msgid "# messages discarded (session disconnected)" msgstr "# mensajes defragmentados" -#: src/core/gnunet-service-core_clients.c:818 +#: src/core/gnunet-service-core_clients.c:518 #, fuzzy, c-format msgid "# bytes of messages of type %u received" msgstr "# bytes de ruido recibidos" @@ -640,7 +550,7 @@ msgid "# SET_KEY messages decrypted" msgstr "# mensajes defragmentados" #: src/core/gnunet-service-core_kx.c:977 -#: src/transport/gnunet-service-transport_validation.c:810 +#: src/transport/gnunet-service-transport_validation.c:865 #, fuzzy msgid "# PING messages received" msgstr "# mensajes PONG encriptados recibidos" @@ -668,7 +578,7 @@ msgid "# keepalive messages sent" msgstr "# mensajes PONG encriptados recibidos" #: src/core/gnunet-service-core_kx.c:1236 -#: src/transport/gnunet-service-transport_validation.c:1031 +#: src/transport/gnunet-service-transport_validation.c:1161 #, fuzzy msgid "# PONG messages received" msgstr "# mensajes PONG encriptados recibidos" @@ -688,58 +598,49 @@ msgstr "# Anuncios de los pares recibidos" msgid "# rekey operations confirmed via PONG" msgstr "# Anuncios de los pares recibidos" -#: src/core/gnunet-service-core_kx.c:1381 -#: src/core/gnunet-service-core_kx.c:1398 +#: src/core/gnunet-service-core_kx.c:1383 +#: src/core/gnunet-service-core_kx.c:1400 #, fuzzy msgid "# SET_KEY and PING messages created" msgstr "# mensajes de texto mandados por PING" -#: src/core/gnunet-service-core_kx.c:1402 +#: src/core/gnunet-service-core_kx.c:1404 msgid "# REKEY operations performed" msgstr "" -#: src/core/gnunet-service-core_kx.c:1537 +#: src/core/gnunet-service-core_kx.c:1539 msgid "# failed to decrypt message (no session key)" msgstr "" -#: src/core/gnunet-service-core_kx.c:1577 -#: src/core/gnunet-service-core_kx.c:1602 +#: src/core/gnunet-service-core_kx.c:1579 +#: src/core/gnunet-service-core_kx.c:1604 #, fuzzy msgid "# bytes dropped (duplicates)" msgstr "# bytes omitidos por UDP (salientes)" -#: src/core/gnunet-service-core_kx.c:1589 +#: src/core/gnunet-service-core_kx.c:1591 #, fuzzy msgid "# bytes dropped (out of sequence)" msgstr "# bytes omitidos por UDP (salientes)" -#: src/core/gnunet-service-core_kx.c:1626 +#: src/core/gnunet-service-core_kx.c:1628 #, fuzzy, c-format -msgid "Message received far too old (%llu ms). Content ignored.\n" +msgid "Message received far too old (%s). Content ignored.\n" msgstr "El mensaje recibido del cliente es inválido\n" -#: src/core/gnunet-service-core_kx.c:1630 +#: src/core/gnunet-service-core_kx.c:1632 #, fuzzy msgid "# bytes dropped (ancient message)" msgstr "# bytes omitidos por UDP (salientes)" -#: src/core/gnunet-service-core_kx.c:1638 +#: src/core/gnunet-service-core_kx.c:1640 #, fuzzy msgid "# bytes of payload decrypted" msgstr "# bytes desencriptados" -#: src/core/gnunet-service-core_kx.c:1700 -#, fuzzy -msgid "Core service is lacking HOSTKEY configuration setting. Exiting.\n" -msgstr "Configuración de GNUnet" - -#: src/core/gnunet-service-core_kx.c:1708 -msgid "Core service could not access hostkey. Exiting.\n" -msgstr "" - -#: src/core/gnunet-service-core_kx.c:1718 src/hostlist/hostlist-server.c:551 -#: src/peerinfo-tool/gnunet-peerinfo.c:823 -#: src/transport/gnunet-service-transport.c:611 +#: src/core/gnunet-service-core_kx.c:1703 src/hostlist/hostlist-server.c:552 +#: src/peerinfo-tool/gnunet-peerinfo.c:547 +#: src/transport/gnunet-service-transport.c:644 #, fuzzy msgid "Could not access PEERINFO service. Exiting.\n" msgstr "Imposible acceder a la información del espacio.\n" @@ -758,23 +659,23 @@ msgstr "" msgid "# encrypted bytes given to transport" msgstr "" -#: src/core/gnunet-service-core_neighbours.c:418 +#: src/core/gnunet-service-core_neighbours.c:421 #, fuzzy, c-format msgid "Unsupported message of type %u (%u bytes) received from peer `%s'\n" msgstr "Mensaje no válido del tipo %u recibido. Omitiendo.\n" #: src/core/gnunet-service-core_sessions.c:206 #: src/core/gnunet-service-core_sessions.c:269 -#: src/dht/gnunet-service-dht_neighbours.c:625 -#: src/dht/gnunet-service-dht_neighbours.c:683 -#: src/fs/gnunet-service-fs_cp.c:615 src/fs/gnunet-service-fs_cp.c:1532 -#: src/topology/gnunet-daemon-topology.c:709 -#: src/topology/gnunet-daemon-topology.c:810 -#: src/transport/gnunet-service-transport_neighbours.c:874 -#: src/transport/gnunet-service-transport_neighbours.c:1080 -#: src/transport/gnunet-service-transport_neighbours.c:1089 -#: src/transport/gnunet-service-transport_neighbours.c:2568 -#: src/transport/gnunet-service-transport_neighbours.c:2814 +#: src/dht/gnunet-service-dht_neighbours.c:645 +#: src/dht/gnunet-service-dht_neighbours.c:703 +#: src/fs/gnunet-service-fs_cp.c:630 src/fs/gnunet-service-fs_cp.c:1544 +#: src/topology/gnunet-daemon-topology.c:704 +#: src/topology/gnunet-daemon-topology.c:805 +#: src/transport/gnunet-service-transport_neighbours.c:1052 +#: src/transport/gnunet-service-transport_neighbours.c:1276 +#: src/transport/gnunet-service-transport_neighbours.c:1285 +#: src/transport/gnunet-service-transport_neighbours.c:2826 +#: src/transport/gnunet-service-transport_neighbours.c:3089 #, fuzzy msgid "# peers connected" msgstr "# de pares conectados" @@ -797,40 +698,52 @@ msgstr "# mensajes PONG encriptados recibidos" msgid "# updates to my type map" msgstr "" -#: src/datacache/datacache.c:115 src/datacache/datacache.c:250 +#: src/datacache/datacache.c:115 src/datacache/datacache.c:266 #: src/datastore/gnunet-service-datastore.c:834 #, fuzzy msgid "# bytes stored" msgstr "# bytes en la base de datos" -#: src/datacache/datacache.c:141 src/datacache/datacache.c:148 +#: src/datacache/datacache.c:117 src/datacache/datacache.c:268 +#, fuzzy +msgid "# items stored" +msgstr "# bytes en la base de datos" + +#: src/datacache/datacache.c:143 src/datacache/datacache.c:150 #: src/datastore/gnunet-service-datastore.c:1483 #: src/datastore/gnunet-service-datastore.c:1494 #, fuzzy, c-format msgid "No `%s' specified for `%s' in configuration!\n" msgstr "¡Ninguna aplicación definida en la configuración!\n" -#: src/datacache/datacache.c:180 +#: src/datacache/datacache.c:184 #, c-format msgid "Loading `%s' datacache plugin\n" msgstr "" -#: src/datacache/datacache.c:188 +#: src/datacache/datacache.c:192 #, fuzzy, c-format msgid "Failed to load datacache plugin for `%s'\n" msgstr "Falló al actualizar los datos del módulo '%s'\n" -#: src/datacache/datacache.c:276 +#: src/datacache/datacache.c:295 #, fuzzy msgid "# requests received" msgstr "# mensajes PONG encriptados recibidos" -#: src/datacache/datacache.c:284 +#: src/datacache/datacache.c:304 msgid "# requests filtered by bloom filter" msgstr "" -#: src/datacache/plugin_datacache_mysql.c:97 -#: src/datacache/plugin_datacache_mysql.c:104 +#: src/datacache/plugin_datacache_heap.c:406 +#, fuzzy +msgid "Heap datacache running\n" +msgstr "base de datos sqlite" + +#: src/datacache/plugin_datacache_postgres.c:392 +msgid "Postgres datacache running\n" +msgstr "" + #: src/datacache/plugin_datacache_sqlite.c:69 #: src/datacache/plugin_datacache_sqlite.c:72 #: src/datastore/plugin_datastore_mysql.c:803 @@ -838,58 +751,51 @@ msgstr "" #: src/datastore/plugin_datastore_sqlite.c:57 src/mysql/mysql.c:41 #: src/mysql/mysql.c:48 src/mysql/mysql.c:522 src/mysql/mysql.c:531 #: src/mysql/mysql.c:591 src/mysql/mysql.c:607 -#: src/namestore/plugin_namestore_sqlite.c:51 src/util/crypto_ksk.c:49 -#: src/util/crypto_rsa.c:67 src/include/gnunet_common.h:525 -#: src/include/gnunet_common.h:532 +#: src/namestore/plugin_namestore_postgres.c:52 +#: src/namestore/plugin_namestore_sqlite.c:51 src/util/crypto_ecc.c:46 +#: src/util/crypto_ksk.c:49 src/util/crypto_rsa.c:59 +#: src/include/gnunet_common.h:607 src/include/gnunet_common.h:614 #, c-format msgid "`%s' failed at %s:%d with error: %s\n" msgstr "'%s' falló en %s: %d con el error: %s\n" -#: src/datacache/plugin_datacache_mysql.c:450 -msgid "MySQL datacache running\n" -msgstr "" - -#: src/datacache/plugin_datacache_postgres.c:367 -msgid "Postgres datacache running\n" -msgstr "" - -#: src/datacache/plugin_datacache_sqlite.c:410 +#: src/datacache/plugin_datacache_sqlite.c:450 msgid "Sqlite datacache running\n" msgstr "" -#: src/datacache/plugin_datacache_sqlite.c:443 -#: src/datastore/plugin_datastore_sqlite.c:408 -#: src/namestore/plugin_namestore_sqlite.c:370 +#: src/datacache/plugin_datacache_sqlite.c:484 +#: src/datastore/plugin_datastore_sqlite.c:401 +#: src/namestore/plugin_namestore_sqlite.c:362 msgid "Tried to close sqlite without finalizing all prepared statements.\n" msgstr "" -#: src/datacache/plugin_datacache_sqlite.c:450 +#: src/datacache/plugin_datacache_sqlite.c:491 #, fuzzy, c-format msgid "Failed to close statement %p: %d\n" msgstr "Falló al actualizar los datos del módulo '%s'\n" -#: src/datacache/plugin_datacache_template.c:121 +#: src/datacache/plugin_datacache_template.c:125 msgid "Template datacache running\n" msgstr "" -#: src/datastore/datastore_api.c:305 +#: src/datastore/datastore_api.c:310 #, fuzzy msgid "Failed to transmit request to drop database.\n" msgstr "Falló al mandar la petición HTTP al host '%s': %s\n" -#: src/datastore/datastore_api.c:388 +#: src/datastore/datastore_api.c:393 msgid "# queue entry timeouts" msgstr "" -#: src/datastore/datastore_api.c:432 +#: src/datastore/datastore_api.c:437 msgid "# queue overflows" msgstr "" -#: src/datastore/datastore_api.c:459 +#: src/datastore/datastore_api.c:465 msgid "# queue entries created" msgstr "" -#: src/datastore/datastore_api.c:477 +#: src/datastore/datastore_api.c:483 #, fuzzy msgid "# Requests dropped from datastore queue" msgstr "# Anuncios de los pares recibidos" @@ -898,72 +804,68 @@ msgstr "# Anuncios de los pares recibidos" msgid "# datastore connections (re)created" msgstr "" -#: src/datastore/datastore_api.c:548 -msgid "# reconnected to DATASTORE" -msgstr "" - -#: src/datastore/datastore_api.c:612 +#: src/datastore/datastore_api.c:608 #, fuzzy msgid "# transmission request failures" msgstr "# mensajes de texto mandados por PING" -#: src/datastore/datastore_api.c:633 +#: src/datastore/datastore_api.c:630 #, fuzzy msgid "# bytes sent to datastore" msgstr "# bytes en la base de datos" -#: src/datastore/datastore_api.c:764 +#: src/datastore/datastore_api.c:762 #, fuzzy msgid "Failed to receive status response from database." msgstr "" "\n" "Fallo al recibir la respuesta de gnunetd.\n" -#: src/datastore/datastore_api.c:778 +#: src/datastore/datastore_api.c:776 msgid "Error reading response from datastore service" msgstr "" -#: src/datastore/datastore_api.c:790 src/datastore/datastore_api.c:796 +#: src/datastore/datastore_api.c:788 src/datastore/datastore_api.c:794 #, fuzzy msgid "Invalid error message received from datastore service" msgstr "Mensaje '%s' inválido recibido del par '%s'.\n" -#: src/datastore/datastore_api.c:800 +#: src/datastore/datastore_api.c:798 #, fuzzy msgid "# status messages received" msgstr "# mensajes PONG encriptados recibidos" -#: src/datastore/datastore_api.c:869 +#: src/datastore/datastore_api.c:867 #, fuzzy msgid "# PUT requests executed" msgstr "# mensajes PONG encriptados recibidos" -#: src/datastore/datastore_api.c:936 +#: src/datastore/datastore_api.c:934 msgid "# RESERVE requests executed" msgstr "" -#: src/datastore/datastore_api.c:997 +#: src/datastore/datastore_api.c:995 msgid "# RELEASE RESERVE requests executed" msgstr "" -#: src/datastore/datastore_api.c:1054 +#: src/datastore/datastore_api.c:1052 #, fuzzy msgid "# UPDATE requests executed" msgstr "# mensajes PONG encriptados recibidos" -#: src/datastore/datastore_api.c:1118 +#: src/datastore/datastore_api.c:1116 #, fuzzy msgid "# REMOVE requests executed" msgstr "# mensajes PONG encriptados recibidos" -#: src/datastore/datastore_api.c:1163 +#: src/datastore/datastore_api.c:1161 #, fuzzy msgid "Failed to receive response from database.\n" msgstr "" "\n" "Fallo al recibir la respuesta de gnunetd.\n" -#: src/datastore/datastore_api.c:1221 +#: src/datastore/datastore_api.c:1220 #, fuzzy msgid "# Results received" msgstr "# bytes recibidos por TCP" @@ -976,7 +878,7 @@ msgstr "" msgid "# GET ZERO ANONYMITY requests executed" msgstr "" -#: src/datastore/datastore_api.c:1409 +#: src/datastore/datastore_api.c:1410 #, fuzzy msgid "# GET requests executed" msgstr "# mensajes PONG encriptados recibidos" @@ -991,10 +893,12 @@ msgid "# bytes purged (low-priority)" msgstr "" #: src/datastore/gnunet-service-datastore.c:480 +#: src/gns/gnunet-gns-helper-service-w32.c:159 msgid "Transmission to client failed!\n" msgstr "" #: src/datastore/gnunet-service-datastore.c:511 +#: src/gns/gnunet-gns-helper-service-w32.c:189 msgid "Shutdown in progress, aborting transmission.\n" msgstr "" @@ -1136,6 +1040,11 @@ msgstr "" msgid "Bloomfilter construction complete.\n" msgstr "" +#: src/datastore/plugin_datastore_heap.c:820 +#, fuzzy +msgid "Heap database running\n" +msgstr "base de datos sqlite" + #: src/datastore/plugin_datastore_mysql.c:780 #, fuzzy, c-format msgid "Failed to prepare statement `%s'\n" @@ -1158,6 +1067,7 @@ msgstr "" "Fallo al recibir la respuesta de gnunetd.\n" #: src/datastore/plugin_datastore_postgres.c:860 +#: src/namestore/plugin_namestore_postgres.c:652 msgid "Postgres database running\n" msgstr "" @@ -1166,222 +1076,240 @@ msgstr "" msgid "`%s' failed at %s:%u with error: %s" msgstr "'%s' falló en %s: %d con el error: %s\n" -#: src/datastore/plugin_datastore_sqlite.c:233 -#: src/namestore/plugin_namestore_sqlite.c:204 -#, fuzzy, c-format -msgid "Option `%s' in section `%s' missing in configuration!\n" -msgstr "¡Ninguna aplicación definida en la configuración!\n" - -#: src/datastore/plugin_datastore_sqlite.c:260 -#: src/namestore/plugin_namestore_sqlite.c:229 +#: src/datastore/plugin_datastore_sqlite.c:253 +#: src/namestore/plugin_namestore_sqlite.c:223 #, fuzzy, c-format msgid "Unable to initialize SQLite: %s.\n" msgstr "Imposible inicializar SQLite.\n" -#: src/datastore/plugin_datastore_sqlite.c:655 +#: src/datastore/plugin_datastore_sqlite.c:648 #, fuzzy msgid "Invalid data in database. Trying to fix (by deletion).\n" msgstr "Datos no válidos en %s. Intentando fijar (por borrado).\n" -#: src/datastore/plugin_datastore_sqlite.c:1139 +#: src/datastore/plugin_datastore_sqlite.c:1134 msgid "sqlite version to old to determine size, assuming zero\n" msgstr "" -#: src/datastore/plugin_datastore_sqlite.c:1158 +#: src/datastore/plugin_datastore_sqlite.c:1153 #, c-format msgid "" "Using sqlite page utilization to estimate payload (%llu pages of size %llu " "bytes)\n" msgstr "" -#: src/datastore/plugin_datastore_sqlite.c:1198 -#: src/namestore/plugin_namestore_sqlite.c:829 +#: src/datastore/plugin_datastore_sqlite.c:1193 +#: src/namestore/plugin_namestore_sqlite.c:827 #, fuzzy msgid "Sqlite database running\n" msgstr "base de datos sqlite" -#: src/datastore/plugin_datastore_template.c:241 +#: src/datastore/plugin_datastore_template.c:257 msgid "Template database running\n" msgstr "" -#: src/dht/dht_api.c:348 +#: src/dht/dht_api.c:375 #, fuzzy msgid "Failed to connect to the DHT service!\n" msgstr "Fallo al conectar a gnunetd.\n" -#: src/dht/gnunet-dht-get.c:201 src/dht/gnunet-dht-monitor.c:293 -#: src/dht/gnunet-dht-put.c:192 +#: src/dht/gnunet-dht-get.c:132 +#, c-format +msgid "" +"Result %d, type %d:\n" +"%.*s\n" +msgstr "" + +#: src/dht/gnunet-dht-get.c:156 +msgid "Must provide key for DHT GET!\n" +msgstr "" + +#: src/dht/gnunet-dht-get.c:162 src/dht/gnunet-dht-monitor.c:225 +#, fuzzy +msgid "Failed to connect to DHT service!\n" +msgstr "Fallo al conectar a gnunetd.\n" + +#: src/dht/gnunet-dht-get.c:170 +msgid "Issueing DHT GET with key" +msgstr "" + +#: src/dht/gnunet-dht-get.c:186 src/dht/gnunet-dht-monitor.c:262 +#: src/dht/gnunet-dht-put.c:198 msgid "the query key" msgstr "" -#: src/dht/gnunet-dht-get.c:204 +#: src/dht/gnunet-dht-get.c:189 msgid "how many parallel requests (replicas) to create" msgstr "" -#: src/dht/gnunet-dht-get.c:207 src/dht/gnunet-dht-monitor.c:296 +#: src/dht/gnunet-dht-get.c:192 src/dht/gnunet-dht-monitor.c:265 msgid "the type of data to look for" msgstr "" -#: src/dht/gnunet-dht-get.c:210 src/dht/gnunet-dht-put.c:201 +#: src/dht/gnunet-dht-get.c:195 src/dht/gnunet-dht-put.c:210 msgid "how long to execute this query before giving up?" msgstr "" -#: src/dht/gnunet-dht-get.c:213 src/dht/gnunet-dht-monitor.c:302 -#: src/dht/gnunet-dht-put.c:204 src/fs/gnunet-download.c:271 -#: src/fs/gnunet-publish.c:731 src/fs/gnunet-search.c:297 -#: src/fs/gnunet-unindex.c:169 src/nse/gnunet-nse-profiler.c:910 +#: src/dht/gnunet-dht-get.c:198 src/dht/gnunet-dht-put.c:201 +msgid "use DHT's demultiplex everywhere option" +msgstr "" + +#: src/dht/gnunet-dht-get.c:201 src/dht/gnunet-dht-monitor.c:271 +#: src/dht/gnunet-dht-put.c:213 src/fs/gnunet-auto-share.c:753 +#: src/fs/gnunet-download.c:328 src/fs/gnunet-publish.c:736 +#: src/fs/gnunet-search.c:294 src/fs/gnunet-unindex.c:168 +#: src/nse/gnunet-nse-profiler.c:1033 msgid "be verbose (print progress information)" msgstr "" -#: src/dht/gnunet-dht-get.c:232 +#: src/dht/gnunet-dht-get.c:222 msgid "Issue a GET request to the GNUnet DHT, prints results." msgstr "" -#: src/dht/gnunet-dht-monitor.c:299 -msgid "how long to execute? 0 = forever" +#: src/dht/gnunet-dht-monitor.c:268 +msgid "how long should the monitor command run" msgstr "" -#: src/dht/gnunet-dht-monitor.c:321 +#: src/dht/gnunet-dht-monitor.c:293 msgid "Prints all packets that go through the DHT." msgstr "" -#: src/dht/gnunet-dht-put.c:108 -msgid "PUT request sent!\n" -msgstr "" +#: src/dht/gnunet-dht-put.c:118 +#, fuzzy +msgid "PUT request sent with key" +msgstr "# mensajes PONG encriptados recibidos" -#: src/dht/gnunet-dht-put.c:111 +#: src/dht/gnunet-dht-put.c:121 msgid "Timeout sending PUT request!\n" msgstr "" -#: src/dht/gnunet-dht-put.c:114 +#: src/dht/gnunet-dht-put.c:124 #, fuzzy msgid "PUT request not confirmed!\n" msgstr "# mensajes PONG encriptados recibidos" -#: src/dht/gnunet-dht-put.c:144 +#: src/dht/gnunet-dht-put.c:153 msgid "Must provide KEY and DATA for DHT put!\n" msgstr "" -#: src/dht/gnunet-dht-put.c:152 +#: src/dht/gnunet-dht-put.c:160 #, fuzzy, c-format msgid "Could not connect to %s service!\n" msgstr "Imposible conectar con gnunetd.\n" -#: src/dht/gnunet-dht-put.c:157 -#, fuzzy, c-format -msgid "Connected to %s service!\n" -msgstr "'%s' conectado a '%s'.\n" - -#: src/dht/gnunet-dht-put.c:172 +#: src/dht/gnunet-dht-put.c:176 #, c-format msgid "Issuing put request for `%s' with data `%s'!\n" msgstr "" -#: src/dht/gnunet-dht-put.c:186 +#: src/dht/gnunet-dht-put.c:192 msgid "the data to insert under the key" msgstr "" -#: src/dht/gnunet-dht-put.c:189 +#: src/dht/gnunet-dht-put.c:195 msgid "how long to store this entry in the dht (in seconds)" msgstr "" -#: src/dht/gnunet-dht-put.c:195 +#: src/dht/gnunet-dht-put.c:204 msgid "how many replicas to create" msgstr "" -#: src/dht/gnunet-dht-put.c:198 +#: src/dht/gnunet-dht-put.c:207 msgid "the type to insert data as" msgstr "" -#: src/dht/gnunet-dht-put.c:223 +#: src/dht/gnunet-dht-put.c:235 msgid "Issue a PUT request to the GNUnet DHT insert DATA under KEY." msgstr "" -#: src/dht/gnunet-service-dht.c:163 src/testing/testing.c:544 -#: src/testing/testing.c:1968 src/testing/testing.c:1998 +#: src/dht/gnunet-service-dht.c:172 #, fuzzy msgid "Failed to connect to transport service!\n" msgstr "Fallo al conectar a gnunetd.\n" -#: src/dht/gnunet-service-dht_clients.c:407 +#: src/dht/gnunet-service-dht_clients.c:413 #, fuzzy msgid "# GET requests from clients injected" msgstr "# mensajes PONG encriptados recibidos" -#: src/dht/gnunet-service-dht_clients.c:500 +#: src/dht/gnunet-service-dht_clients.c:503 #, fuzzy msgid "# PUT requests received from clients" msgstr "El mensaje recibido del cliente es inválido\n" -#: src/dht/gnunet-service-dht_clients.c:584 +#: src/dht/gnunet-service-dht_clients.c:585 #, fuzzy msgid "# GET requests received from clients" msgstr "El mensaje recibido del cliente es inválido\n" -#: src/dht/gnunet-service-dht_clients.c:682 +#: src/dht/gnunet-service-dht_clients.c:791 #, fuzzy msgid "# GET STOP requests received from clients" msgstr "El mensaje recibido del cliente es inválido\n" -#: src/dht/gnunet-service-dht_clients.c:919 +#: src/dht/gnunet-service-dht_clients.c:1035 msgid "# Key match, type mismatches in REPLY to CLIENT" msgstr "" -#: src/dht/gnunet-service-dht_clients.c:932 +#: src/dht/gnunet-service-dht_clients.c:1048 msgid "# Duplicate REPLIES to CLIENT request dropped" msgstr "" -#: src/dht/gnunet-service-dht_clients.c:967 +#: src/dht/gnunet-service-dht_clients.c:1085 #, fuzzy, c-format msgid "Unsupported block type (%u) in request!\n" msgstr "Mensaje no válido del tipo %u recibido. Omitiendo.\n" -#: src/dht/gnunet-service-dht_clients.c:989 +#: src/dht/gnunet-service-dht_clients.c:1108 #, fuzzy msgid "# RESULTS queued for clients" msgstr "El mensaje recibido del cliente es inválido\n" -#: src/dht/gnunet-service-dht_clients.c:1038 -#: src/dht/gnunet-service-dht_clients.c:1081 +#: src/dht/gnunet-service-dht_clients.c:1157 +#: src/dht/gnunet-service-dht_clients.c:1199 msgid "# REPLIES ignored for CLIENTS (no match)" msgstr "" -#: src/dht/gnunet-service-dht_clients.c:1048 +#: src/dht/gnunet-service-dht_clients.c:1167 #, fuzzy msgid "Could not pass reply to client, message too big!\n" msgstr "Imposible mandar el mensaje a gnunetd\n" -#: src/dht/gnunet-service-dht_datacache.c:93 +#: src/dht/gnunet-service-dht_datacache.c:64 #, fuzzy, c-format msgid "%s request received, but have no datacache!\n" msgstr "# bytes recibidos por TCP" -#: src/dht/gnunet-service-dht_datacache.c:103 +#: src/dht/gnunet-service-dht_datacache.c:74 msgid "# ITEMS stored in datacache" msgstr "" -#: src/dht/gnunet-service-dht_datacache.c:207 +#: src/dht/gnunet-service-dht_datacache.c:159 msgid "# Good RESULTS found in datacache" msgstr "" -#: src/dht/gnunet-service-dht_datacache.c:218 +#: src/dht/gnunet-service-dht_datacache.c:170 msgid "# Duplicate RESULTS found in datacache" msgstr "" -#: src/dht/gnunet-service-dht_datacache.c:224 +#: src/dht/gnunet-service-dht_datacache.c:176 msgid "# Invalid RESULTS found in datacache" msgstr "" -#: src/dht/gnunet-service-dht_datacache.c:236 +#: src/dht/gnunet-service-dht_datacache.c:182 +msgid "# Irrelevant RESULTS found in datacache" +msgstr "" + +#: src/dht/gnunet-service-dht_datacache.c:194 msgid "# Unsupported RESULTS found in datacache" msgstr "" -#: src/dht/gnunet-service-dht_datacache.c:239 +#: src/dht/gnunet-service-dht_datacache.c:197 #, c-format msgid "Unsupported block type (%u) in local response!\n" msgstr "" -#: src/dht/gnunet-service-dht_datacache.c:269 +#: src/dht/gnunet-service-dht_datacache.c:227 #, fuzzy msgid "# GET requests given to datacache" msgstr "# mensajes PONG encriptados recibidos" @@ -1391,94 +1319,101 @@ msgstr "# mensajes PONG encriptados recibidos" msgid "# HELLOs obtained from peerinfo" msgstr "El mensaje recibido del cliente es inválido\n" -#: src/dht/gnunet-service-dht_neighbours.c:481 +#: src/dht/gnunet-service-dht_neighbours.c:501 msgid "# Preference updates given to core" msgstr "" -#: src/dht/gnunet-service-dht_neighbours.c:571 +#: src/dht/gnunet-service-dht_neighbours.c:591 #, fuzzy msgid "# FIND PEER messages initiated" msgstr "# mensajes fragmentados" -#: src/dht/gnunet-service-dht_neighbours.c:717 +#: src/dht/gnunet-service-dht_neighbours.c:737 #, fuzzy msgid "# Queued messages discarded (peer disconnected)" msgstr "# mensajes defragmentados" -#: src/dht/gnunet-service-dht_neighbours.c:772 +#: src/dht/gnunet-service-dht_neighbours.c:792 #, fuzzy msgid "# Bytes transmitted to other peers" msgstr "# bytes recibidos por TCP" -#: src/dht/gnunet-service-dht_neighbours.c:810 +#: src/dht/gnunet-service-dht_neighbours.c:830 #, fuzzy -msgid "# Bytes of bandwdith requested from core" +msgid "# Bytes of bandwidth requested from core" msgstr "# mensajes PONG encriptados recibidos" -#: src/dht/gnunet-service-dht_neighbours.c:1032 -#: src/dht/gnunet-service-dht_neighbours.c:1060 +#: src/dht/gnunet-service-dht_neighbours.c:1052 +#: src/dht/gnunet-service-dht_neighbours.c:1080 msgid "# Peers excluded from routing due to Bloomfilter" msgstr "" -#: src/dht/gnunet-service-dht_neighbours.c:1041 -#: src/dht/gnunet-service-dht_neighbours.c:1075 +#: src/dht/gnunet-service-dht_neighbours.c:1061 +#: src/dht/gnunet-service-dht_neighbours.c:1095 #, fuzzy msgid "# Peer selection failed" msgstr "Conexión fallida\n" -#: src/dht/gnunet-service-dht_neighbours.c:1207 +#: src/dht/gnunet-service-dht_neighbours.c:1229 #, fuzzy msgid "# PUT requests routed" msgstr "# mensajes PONG encriptados recibidos" -#: src/dht/gnunet-service-dht_neighbours.c:1236 +#: src/dht/gnunet-service-dht_neighbours.c:1258 #, fuzzy msgid "# PUT messages queued for transmission" msgstr "# bytes de mensajes salientes omitidos" -#: src/dht/gnunet-service-dht_neighbours.c:1315 +#: src/dht/gnunet-service-dht_neighbours.c:1265 +#: src/dht/gnunet-service-dht_neighbours.c:1378 +#: src/dht/gnunet-service-dht_neighbours.c:1478 +#, fuzzy +msgid "# P2P messages dropped due to full queue" +msgstr "# Anuncios de los pares recibidos" + +#: src/dht/gnunet-service-dht_neighbours.c:1343 #, fuzzy msgid "# GET requests routed" msgstr "# mensajes PONG encriptados recibidos" -#: src/dht/gnunet-service-dht_neighbours.c:1342 +#: src/dht/gnunet-service-dht_neighbours.c:1370 #, fuzzy msgid "# GET messages queued for transmission" msgstr "# bytes de mensajes salientes omitidos" -#: src/dht/gnunet-service-dht_neighbours.c:1443 +#: src/dht/gnunet-service-dht_neighbours.c:1485 msgid "# RESULT messages queued for transmission" msgstr "" -#: src/dht/gnunet-service-dht_neighbours.c:1531 +#: src/dht/gnunet-service-dht_neighbours.c:1573 #, fuzzy msgid "# P2P PUT requests received" msgstr "# mensajes PONG encriptados recibidos" -#: src/dht/gnunet-service-dht_neighbours.c:1647 +#: src/dht/gnunet-service-dht_neighbours.c:1702 msgid "# FIND PEER requests ignored due to Bloomfilter" msgstr "" -#: src/dht/gnunet-service-dht_neighbours.c:1655 +#: src/dht/gnunet-service-dht_neighbours.c:1710 msgid "# FIND PEER requests ignored due to lack of HELLO" msgstr "" -#: src/dht/gnunet-service-dht_neighbours.c:1746 +#: src/dht/gnunet-service-dht_neighbours.c:1801 #, fuzzy msgid "# P2P GET requests received" msgstr "# mensajes PONG encriptados recibidos" -#: src/dht/gnunet-service-dht_neighbours.c:1788 +#: src/dht/gnunet-service-dht_neighbours.c:1843 #, fuzzy msgid "# P2P FIND PEER requests processed" msgstr "# mensajes PONG encriptados recibidos" -#: src/dht/gnunet-service-dht_neighbours.c:1802 +#: src/dht/gnunet-service-dht_neighbours.c:1857 #, fuzzy msgid "# P2P GET requests ONLY routed" msgstr "# mensajes PONG encriptados recibidos" -#: src/dht/gnunet-service-dht_neighbours.c:1876 +#: src/dht/gnunet-service-dht_neighbours.c:1944 #, fuzzy msgid "# P2P RESULTS received" msgstr "# bytes recibidos por TCP" @@ -1500,18 +1435,27 @@ msgstr "" msgid "# Invalid REPLIES matched against routing table" msgstr "" -#: src/dht/gnunet-service-dht_routing.c:238 +#: src/dht/gnunet-service-dht_routing.c:232 +msgid "# Irrelevant REPLIES matched against routing table" +msgstr "" + +#: src/dht/gnunet-service-dht_routing.c:244 msgid "# Unsupported REPLIES matched against routing table" msgstr "" -#: src/dht/gnunet-service-dht_routing.c:311 +#: src/dht/gnunet-service-dht_routing.c:317 msgid "# Entries removed from routing table" msgstr "" -#: src/dht/gnunet-service-dht_routing.c:352 +#: src/dht/gnunet-service-dht_routing.c:400 msgid "# Entries added to routing table" msgstr "" +#: src/dht/gnunet-service-dht_routing.c:418 +#, fuzzy +msgid "# DHT requests combined" +msgstr "# mensajes PONG encriptados recibidos" + #: src/dht/plugin_block_dht.c:136 #, c-format msgid "Block not of type %u\n" @@ -1526,15 +1470,51 @@ msgstr "" msgid "Block of type %u is malformed\n" msgstr "" -#: src/dns/gnunet-dns-monitor.c:337 +#: src/dns/dnsparser.c:152 +#, fuzzy, c-format +msgid "Failed to convert DNS IDNA name `%s' to UTF-8: %s\n" +msgstr "Fichero almacenado en '%s'.\n" + +#: src/dns/dnsparser.c:626 +#, fuzzy, c-format +msgid "Failed to convert UTF-8 name `%s' to DNS IDNA format: %s\n" +msgstr "Fichero almacenado en '%s'.\n" + +#: src/dns/dnsstub.c:175 +#, fuzzy, c-format +msgid "Could not bind to any port: %s\n" +msgstr "Imposible encontrar la IP del host '%s': %s\n" + +#: src/dns/dnsstub.c:295 src/dns/dnsstub.c:383 +#: src/gns/gnunet-service-gns_resolver.c:1621 +#, fuzzy, c-format +msgid "Failed to send DNS request to %s\n" +msgstr "Falló al mandar la petición HTTP al host '%s': %s\n" + +#: src/dns/dnsstub.c:299 +#, fuzzy, c-format +msgid "Sent DNS request to %s\n" +msgstr "Falló al mandar la petición HTTP al host '%s': %s\n" + +#: src/dns/dnsstub.c:368 +#, c-format +msgid "Configured DNS exit `%s' is not working / valid.\n" +msgstr "" + +#: src/dns/dnsstub.c:440 +#, c-format +msgid "Received DNS response that is too small (%u bytes)" +msgstr "" + +#: src/dns/gnunet-dns-monitor.c:355 msgid "only monitor DNS queries" msgstr "" -#: src/dns/gnunet-dns-monitor.c:340 +#: src/dns/gnunet-dns-monitor.c:358 msgid "only monitor DNS replies" msgstr "" -#: src/dns/gnunet-dns-monitor.c:348 +#: src/dns/gnunet-dns-monitor.c:369 msgid "Monitor DNS queries." msgstr "" @@ -1546,77 +1526,59 @@ msgstr "" msgid "set AAAA records" msgstr "" -#: src/dns/gnunet-dns-redirector.c:247 +#: src/dns/gnunet-dns-redirector.c:251 msgid "Change DNS replies to point elsewhere." msgstr "" -#: src/dns/gnunet-service-dns.c:485 -#, fuzzy, c-format -msgid "Could not bind to any port: %s\n" -msgstr "Imposible encontrar la IP del host '%s': %s\n" - -#: src/dns/gnunet-service-dns.c:639 +#: src/dns/gnunet-service-dns.c:456 msgid "# DNS requests answered via TUN interface" msgstr "" -#: src/dns/gnunet-service-dns.c:822 +#: src/dns/gnunet-service-dns.c:603 msgid "# DNS exit failed (failed to open socket)" msgstr "" -#: src/dns/gnunet-service-dns.c:1005 -#, c-format -msgid "Received DNS response that is too small (%u bytes)" -msgstr "" - -#: src/dns/gnunet-service-dns.c:1050 +#: src/dns/gnunet-service-dns.c:714 msgid "# External DNS response discarded (no matching request)" msgstr "" -#: src/dns/gnunet-service-dns.c:1168 +#: src/dns/gnunet-service-dns.c:792 msgid "# Client response discarded (no matching request)" msgstr "" -#: src/dns/gnunet-service-dns.c:1281 +#: src/dns/gnunet-service-dns.c:907 msgid "Received malformed IPv4-UDP packet on TUN interface.\n" msgstr "" -#: src/dns/gnunet-service-dns.c:1297 +#: src/dns/gnunet-service-dns.c:923 msgid "Received malformed IPv6-UDP packet on TUN interface.\n" msgstr "" -#: src/dns/gnunet-service-dns.c:1306 +#: src/dns/gnunet-service-dns.c:932 #, c-format msgid "Got non-IP packet with %u bytes and protocol %u from TUN\n" msgstr "" -#: src/dns/gnunet-service-dns.c:1315 +#: src/dns/gnunet-service-dns.c:942 msgid "# Non-DNS UDP packet received via TUN interface" msgstr "" -#: src/dns/gnunet-service-dns.c:1380 +#: src/dns/gnunet-service-dns.c:1009 #, fuzzy msgid "# DNS requests received via TUN interface" msgstr "El mensaje recibido del cliente es inválido\n" -#: src/dns/gnunet-service-dns.c:1465 -#, c-format -msgid "Configured DNS exit `%s' is not working / valid.\n" -msgstr "" - -#: src/dns/gnunet-service-dns.c:1497 src/exit/gnunet-daemon-exit.c:2674 -msgid "# Inbound MESH tunnels created" -msgstr "" - -#: src/dns/gnunet-service-dns.c:1561 src/exit/gnunet-daemon-exit.c:3032 +#: src/dns/gnunet-service-dns.c:1049 src/exit/gnunet-daemon-exit.c:3351 #, c-format msgid "`%s' must be installed SUID, refusing to run\n" msgstr "" -#: src/dns/gnunet-service-dns.c:1581 -msgid "Configured to provide DNS exit, but no valid DNS server configured!\n" -msgstr "" +#: src/dns/gnunet-service-dns.c:1069 src/exit/gnunet-daemon-exit.c:3407 +#, fuzzy +msgid "need a valid IPv4 or IPv6 address\n" +msgstr "Argumento no válido: '%s'\n" -#: src/dv/dv_api.c:179 +#: src/dv/dv_api.c:189 #, fuzzy msgid "Failed to connect to the dv service!\n" msgstr "Fallo al conectar a gnunetd.\n" @@ -1626,205 +1588,209 @@ msgstr "Fallo al conectar a gnunetd.\n" msgid "%s Received message from %s of type %d, distance %u!\n" msgstr "Recibido mensaje corrupto del par '%s' en %s:%d.\n" -#: src/exit/gnunet-daemon-exit.c:508 +#: src/exit/gnunet-daemon-exit.c:741 #, c-format msgid "Got duplicate service records for `%s:%u'\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:563 +#: src/exit/gnunet-daemon-exit.c:794 #, fuzzy msgid "# Bytes transmitted via mesh tunnels" msgstr "# bytes desencriptados" -#: src/exit/gnunet-daemon-exit.c:679 src/exit/gnunet-daemon-exit.c:2069 -#: src/exit/gnunet-daemon-exit.c:2319 src/vpn/gnunet-service-vpn.c:1394 -#: src/vpn/gnunet-service-vpn.c:1795 src/vpn/gnunet-service-vpn.c:1958 +#: src/exit/gnunet-daemon-exit.c:911 src/exit/gnunet-daemon-exit.c:2343 +#: src/exit/gnunet-daemon-exit.c:2603 src/vpn/gnunet-service-vpn.c:1411 +#: src/vpn/gnunet-service-vpn.c:1812 src/vpn/gnunet-service-vpn.c:1975 msgid "# ICMPv4 packets dropped (type not allowed)" msgstr "" -#: src/exit/gnunet-daemon-exit.c:716 src/exit/gnunet-daemon-exit.c:2128 -#: src/exit/gnunet-daemon-exit.c:2378 src/vpn/gnunet-service-vpn.c:1450 -#: src/vpn/gnunet-service-vpn.c:1854 src/vpn/gnunet-service-vpn.c:1991 +#: src/exit/gnunet-daemon-exit.c:948 src/exit/gnunet-daemon-exit.c:2402 +#: src/exit/gnunet-daemon-exit.c:2662 src/vpn/gnunet-service-vpn.c:1467 +#: src/vpn/gnunet-service-vpn.c:1871 src/vpn/gnunet-service-vpn.c:2008 msgid "# ICMPv6 packets dropped (type not allowed)" msgstr "" -#: src/exit/gnunet-daemon-exit.c:756 +#: src/exit/gnunet-daemon-exit.c:988 msgid "# ICMP packets dropped (not allowed)" msgstr "" -#: src/exit/gnunet-daemon-exit.c:763 +#: src/exit/gnunet-daemon-exit.c:995 msgid "ICMP Packet dropped, have no matching connection information\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:840 +#: src/exit/gnunet-daemon-exit.c:1072 msgid "UDP Packet dropped, have no matching connection information\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:915 +#: src/exit/gnunet-daemon-exit.c:1147 msgid "TCP Packet dropped, have no matching connection information\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:968 +#: src/exit/gnunet-daemon-exit.c:1200 #, fuzzy msgid "# Packets received from TUN" msgstr "# bytes recibidos vía HTTP" -#: src/exit/gnunet-daemon-exit.c:982 +#: src/exit/gnunet-daemon-exit.c:1214 #, fuzzy msgid "# Bytes received from TUN" msgstr "# bytes recibidos vía HTTP" -#: src/exit/gnunet-daemon-exit.c:1008 +#: src/exit/gnunet-daemon-exit.c:1240 msgid "IPv4 packet options received. Ignored.\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:1035 +#: src/exit/gnunet-daemon-exit.c:1267 #, c-format msgid "IPv4 packet with unsupported next header %u received. Ignored.\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:1081 +#: src/exit/gnunet-daemon-exit.c:1313 #, c-format msgid "IPv6 packet with unsupported next header %d received. Ignored.\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:1089 +#: src/exit/gnunet-daemon-exit.c:1321 #, c-format msgid "Packet from unknown protocol %u received. Ignored.\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:1471 +#: src/exit/gnunet-daemon-exit.c:1703 #, fuzzy msgid "# TCP packets sent via TUN" msgstr "# bytes enviados vía UDP" -#: src/exit/gnunet-daemon-exit.c:1571 +#: src/exit/gnunet-daemon-exit.c:1814 #, fuzzy msgid "# TCP service creation requests received via mesh" msgstr "# mensajes PONG encriptados recibidos" -#: src/exit/gnunet-daemon-exit.c:1574 src/exit/gnunet-daemon-exit.c:1653 -#: src/exit/gnunet-daemon-exit.c:1763 src/exit/gnunet-daemon-exit.c:1993 -#: src/exit/gnunet-daemon-exit.c:2235 src/exit/gnunet-daemon-exit.c:2516 -#: src/exit/gnunet-daemon-exit.c:2616 +#: src/exit/gnunet-daemon-exit.c:1817 src/exit/gnunet-daemon-exit.c:1906 +#: src/exit/gnunet-daemon-exit.c:2026 src/exit/gnunet-daemon-exit.c:2267 +#: src/exit/gnunet-daemon-exit.c:2519 src/exit/gnunet-daemon-exit.c:2811 +#: src/exit/gnunet-daemon-exit.c:2921 #, fuzzy msgid "# Bytes received from MESH" msgstr "# bytes recibidos vía HTTP" -#: src/exit/gnunet-daemon-exit.c:1607 src/exit/gnunet-daemon-exit.c:2638 +#: src/exit/gnunet-daemon-exit.c:1850 src/exit/gnunet-daemon-exit.c:2943 #, c-format msgid "No service found for %s on port %d!\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:1611 +#: src/exit/gnunet-daemon-exit.c:1854 #, fuzzy msgid "# TCP requests dropped (no such service)" msgstr "# Anuncios de los pares recibidos" -#: src/exit/gnunet-daemon-exit.c:1656 +#: src/exit/gnunet-daemon-exit.c:1909 #, fuzzy msgid "# TCP IP-exit creation requests received via mesh" msgstr "# mensajes PONG encriptados recibidos" -#: src/exit/gnunet-daemon-exit.c:1766 +#: src/exit/gnunet-daemon-exit.c:2029 #, fuzzy msgid "# TCP data requests received via mesh" msgstr "# mensajes PONG encriptados recibidos" -#: src/exit/gnunet-daemon-exit.c:1780 +#: src/exit/gnunet-daemon-exit.c:2043 #, fuzzy msgid "# TCP DATA requests dropped (no session)" msgstr "# Anuncios de los pares recibidos" -#: src/exit/gnunet-daemon-exit.c:1830 +#: src/exit/gnunet-daemon-exit.c:2093 #, fuzzy msgid "# ICMP packets sent via TUN" msgstr "# bytes enviados vía UDP" -#: src/exit/gnunet-daemon-exit.c:1996 +#: src/exit/gnunet-daemon-exit.c:2270 #, fuzzy msgid "# ICMP IP-exit requests received via mesh" msgstr "# mensajes PONG encriptados recibidos" -#: src/exit/gnunet-daemon-exit.c:2238 +#: src/exit/gnunet-daemon-exit.c:2522 #, fuzzy msgid "# ICMP service requests received via mesh" msgstr "El mensaje recibido del cliente es inválido\n" -#: src/exit/gnunet-daemon-exit.c:2304 src/vpn/gnunet-service-vpn.c:1384 -#: src/vpn/gnunet-service-vpn.c:1952 +#: src/exit/gnunet-daemon-exit.c:2588 src/vpn/gnunet-service-vpn.c:1401 +#: src/vpn/gnunet-service-vpn.c:1969 msgid "# ICMPv4 packets dropped (impossible PT to v6)" msgstr "" -#: src/exit/gnunet-daemon-exit.c:2363 src/vpn/gnunet-service-vpn.c:1420 -#: src/vpn/gnunet-service-vpn.c:1432 src/vpn/gnunet-service-vpn.c:1842 +#: src/exit/gnunet-daemon-exit.c:2647 src/vpn/gnunet-service-vpn.c:1437 +#: src/vpn/gnunet-service-vpn.c:1449 src/vpn/gnunet-service-vpn.c:1859 msgid "# ICMPv6 packets dropped (impossible PT to v4)" msgstr "" -#: src/exit/gnunet-daemon-exit.c:2413 +#: src/exit/gnunet-daemon-exit.c:2697 #, fuzzy msgid "# UDP packets sent via TUN" msgstr "# bytes enviados vía UDP" -#: src/exit/gnunet-daemon-exit.c:2519 +#: src/exit/gnunet-daemon-exit.c:2814 #, fuzzy msgid "# UDP IP-exit requests received via mesh" msgstr "# mensajes PONG encriptados recibidos" -#: src/exit/gnunet-daemon-exit.c:2619 +#: src/exit/gnunet-daemon-exit.c:2924 #, fuzzy msgid "# UDP service requests received via mesh" msgstr "# mensajes PONG encriptados recibidos" -#: src/exit/gnunet-daemon-exit.c:2642 +#: src/exit/gnunet-daemon-exit.c:2947 #, fuzzy msgid "# UDP requests dropped (no such service)" msgstr "# Anuncios de los pares recibidos" -#: src/exit/gnunet-daemon-exit.c:2882 +#: src/exit/gnunet-daemon-exit.c:2980 +msgid "# Inbound MESH tunnels created" +msgstr "" + +#: src/exit/gnunet-daemon-exit.c:3209 #, c-format msgid "No addresses found for hostname `%s' of service `%s'!\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:2896 src/exit/gnunet-daemon-exit.c:2908 +#: src/exit/gnunet-daemon-exit.c:3223 src/exit/gnunet-daemon-exit.c:3235 #, c-format msgid "Service `%s' configured for IPv4, but IPv4 is disabled!\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:2919 +#: src/exit/gnunet-daemon-exit.c:3246 #, c-format msgid "No IP addresses found for hostname `%s' of service `%s'!\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:3048 +#: src/exit/gnunet-daemon-exit.c:3364 msgid "" "This system does not support IPv4, will disable IPv4 functions despite them " "being enabled in the configuration\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:3056 +#: src/exit/gnunet-daemon-exit.c:3372 msgid "" "This system does not support IPv6, will disable IPv6 functions despite them " "being enabled in the configuration\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:3063 +#: src/exit/gnunet-daemon-exit.c:3379 msgid "" "Cannot enable IPv4 exit but disable IPv4 on TUN interface, will use " "ENABLE_IPv4=YES\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:3069 +#: src/exit/gnunet-daemon-exit.c:3385 msgid "" "Cannot enable IPv6 exit but disable IPv6 on TUN interface, will use " "ENABLE_IPv6=YES\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:3075 src/pt/gnunet-daemon-pt.c:884 +#: src/exit/gnunet-daemon-exit.c:3391 src/pt/gnunet-daemon-pt.c:884 msgid "No useful service enabled. Exiting.\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:3236 +#: src/exit/gnunet-daemon-exit.c:3620 msgid "Daemon to run to provide an IP exit node for the VPN" msgstr "" @@ -1846,113 +1812,113 @@ msgstr "# bytes recibidos por TCP" msgid "# messages defragmented" msgstr "# mensajes defragmentados" -#: src/fragmentation/fragmentation.c:203 +#: src/fragmentation/fragmentation.c:208 #, fuzzy msgid "# fragments transmitted" msgstr "# Auto-anuncios transmitidos" -#: src/fragmentation/fragmentation.c:206 +#: src/fragmentation/fragmentation.c:211 #, fuzzy msgid "# fragments retransmitted" msgstr "# Auto-anuncios transmitidos" -#: src/fragmentation/fragmentation.c:232 +#: src/fragmentation/fragmentation.c:237 #, fuzzy msgid "# fragments wrap arounds" msgstr "# Auto-anuncios transmitidos" -#: src/fragmentation/fragmentation.c:273 +#: src/fragmentation/fragmentation.c:281 msgid "# messages fragmented" msgstr "# mensajes fragmentados" -#: src/fragmentation/fragmentation.c:276 +#: src/fragmentation/fragmentation.c:284 msgid "# total size of fragmented messages" msgstr "" -#: src/fragmentation/fragmentation.c:363 +#: src/fragmentation/fragmentation.c:405 #, fuzzy msgid "# fragment acknowledgements received" msgstr "# Anuncios de los pares recibidos" -#: src/fragmentation/fragmentation.c:369 +#: src/fragmentation/fragmentation.c:411 msgid "# bits removed from fragmentation ACKs" msgstr "" -#: src/fragmentation/fragmentation.c:393 +#: src/fragmentation/fragmentation.c:435 #, fuzzy msgid "# fragmentation transmissions completed" msgstr "# mensajes de texto mandados por PING" -#: src/fs/fs_api.c:339 +#: src/fs/fs_api.c:465 #, fuzzy, c-format msgid "Could not open file `%s': %s" msgstr "Fichero almacenado en '%s'.\n" -#: src/fs/fs_api.c:348 +#: src/fs/fs_api.c:474 #, fuzzy, c-format msgid "Could not read file `%s': %s" msgstr "Fichero almacenado en '%s'.\n" -#: src/fs/fs_api.c:354 +#: src/fs/fs_api.c:480 #, c-format msgid "Short read reading from file `%s'!" msgstr "" -#: src/fs/fs_api.c:938 +#: src/fs/fs_api.c:1061 #, fuzzy, c-format msgid "Failed to resume publishing information `%s': %s\n" msgstr "Fichero almacenado en '%s'.\n" -#: src/fs/fs_api.c:1395 +#: src/fs/fs_api.c:1520 #, c-format msgid "Failed to recover namespace `%s', cannot resume publishing operation.\n" msgstr "" -#: src/fs/fs_api.c:1437 +#: src/fs/fs_api.c:1562 #, c-format msgid "Failure while resuming publishing operation `%s': %s\n" msgstr "" -#: src/fs/fs_api.c:1453 +#: src/fs/fs_api.c:1578 #, fuzzy, c-format msgid "Failed to resume publishing operation `%s': %s\n" msgstr "Fichero almacenado en '%s'.\n" -#: src/fs/fs_api.c:2106 +#: src/fs/fs_api.c:2229 #, c-format msgid "Failure while resuming unindexing operation `%s': %s\n" msgstr "" -#: src/fs/fs_api.c:2116 +#: src/fs/fs_api.c:2239 #, fuzzy, c-format msgid "Failed to resume unindexing operation `%s': %s\n" msgstr "Fichero almacenado en '%s'.\n" -#: src/fs/fs_api.c:2241 src/fs/fs_api.c:2480 +#: src/fs/fs_api.c:2364 src/fs/fs_api.c:2604 #, fuzzy, c-format msgid "Failed to resume sub-download `%s': %s\n" msgstr "Fichero almacenado en '%s'.\n" -#: src/fs/fs_api.c:2258 +#: src/fs/fs_api.c:2381 #, fuzzy, c-format msgid "Failed to resume sub-search `%s': %s\n" msgstr "Fichero almacenado en '%s'.\n" -#: src/fs/fs_api.c:2270 src/fs/fs_api.c:2289 src/fs/fs_api.c:2773 +#: src/fs/fs_api.c:2394 src/fs/fs_api.c:2413 src/fs/fs_api.c:2897 #, c-format msgid "Failure while resuming search operation `%s': %s\n" msgstr "" -#: src/fs/fs_api.c:2471 +#: src/fs/fs_api.c:2595 #, c-format msgid "Failed to resume sub-download `%s': could not open file `%s'\n" msgstr "" -#: src/fs/fs_api.c:2717 +#: src/fs/fs_api.c:2841 msgid "Could not resume running search, will resume as paused search\n" msgstr "" -#: src/fs/fs_api.c:2811 +#: src/fs/fs_api.c:2935 #, c-format msgid "Failure while resuming download operation `%s': %s\n" msgstr "" @@ -1962,63 +1928,63 @@ msgstr "" msgid "MAGIC mismatch. This is not a GNUnet directory.\n" msgstr "Error en el formato del fichero (¿no es un directorio de GNUnet?)\n" -#: src/fs/fs_download.c:311 +#: src/fs/fs_download.c:321 msgid "" "Recursive downloads of directories larger than 4 GB are not supported on 32-" "bit systems\n" msgstr "" -#: src/fs/fs_download.c:331 +#: src/fs/fs_download.c:341 msgid "Directory too large for system address space\n" msgstr "" -#: src/fs/fs_download.c:497 src/fs/fs_download.c:509 +#: src/fs/fs_download.c:507 src/fs/fs_download.c:519 #, fuzzy, c-format msgid "Failed to open file `%s' for writing" msgstr "Fichero almacenado en '%s'.\n" -#: src/fs/fs_download.c:878 +#: src/fs/fs_download.c:888 #, fuzzy, c-format msgid "Failed to create directory for recursive download of `%s'\n" msgstr "Falló al actualizar los datos del módulo '%s'\n" -#: src/fs/fs_download.c:960 +#: src/fs/fs_download.c:970 #, c-format msgid "" "Internal error or bogus download URI (expected %u bytes at depth %u and " "offset %llu/%llu, got %u bytes)" msgstr "" -#: src/fs/fs_download.c:986 +#: src/fs/fs_download.c:996 msgid "internal error decrypting content" msgstr "" -#: src/fs/fs_download.c:1009 +#: src/fs/fs_download.c:1019 #, fuzzy, c-format msgid "Download failed: could not open file `%s': %s" msgstr "Fichero almacenado en '%s'.\n" -#: src/fs/fs_download.c:1019 +#: src/fs/fs_download.c:1029 #, fuzzy, c-format msgid "Failed to seek to offset %llu in file `%s': %s" msgstr "Fichero almacenado en '%s'.\n" -#: src/fs/fs_download.c:1028 +#: src/fs/fs_download.c:1038 #, fuzzy, c-format msgid "Failed to write block of %u bytes at offset %llu in file `%s': %s" msgstr "Fichero almacenado en '%s'.\n" -#: src/fs/fs_download.c:1125 +#: src/fs/fs_download.c:1136 #, fuzzy msgid "internal error decoding tree" msgstr "=\tError leyendo el directorio.\n" -#: src/fs/fs_download.c:1888 +#: src/fs/fs_download.c:1927 #, fuzzy msgid "Invalid URI" msgstr "Argumento no válido: '%s'\n" -#: src/fs/fs_getopt.c:191 +#: src/fs/fs_getopt.c:192 #, c-format msgid "" "Unknown metadata type in metadata option `%s'. Using metadata type " @@ -2062,39 +2028,36 @@ msgstr "Imposible inicializar SQLite.\n" msgid "Failed to connect to datastore service" msgstr "Fallo al conectar a gnunetd.\n" -#: src/fs/fs_namespace.c:57 src/fs/fs_namespace.c:83 -#, fuzzy, c-format -msgid "Configuration fails to specify `%s' in section `%s'\n" -msgstr "" -"El fichero de configuración debe especificar el directorio para almacenar " -"los datos FS en la sección '%s' bajo '%s'.\n" - -#: src/fs/fs_namespace.c:112 +#: src/fs/fs_namespace.c:110 #, fuzzy, c-format msgid "Failed to open `%s' for writing: %s\n" msgstr "Fichero almacenado en '%s'.\n" -#: src/fs/fs_namespace.c:134 src/fs/fs_namespace.c:222 +#: src/fs/fs_namespace.c:132 src/fs/fs_namespace.c:220 #, fuzzy, c-format msgid "Failed to write `%s': %s\n" msgstr "Fallo al conectar a gnunetd.\n" -#: src/fs/fs_namespace.c:256 +#: src/fs/fs_namespace.c:252 #, fuzzy, c-format msgid "Failed to create or read private key for namespace `%s'\n" msgstr "Falló al actualizar los datos del módulo '%s'\n" -#: src/fs/fs_namespace.c:371 +#: src/fs/fs_namespace.c:367 #, fuzzy, c-format msgid "Failed to read namespace private key file `%s', deleting it!\n" msgstr "Fallo al añadir la entrada al espacio '%s' (¿existe?)\n" -#: src/fs/fs_namespace.c:588 src/fs/fs_publish_ksk.c:295 +#: src/fs/fs_namespace.c:558 +msgid "Identifiers or URI too long to create SBlock" +msgstr "" + +#: src/fs/fs_namespace.c:593 src/fs/fs_publish_ksk.c:295 #, fuzzy msgid "Internal error." msgstr "Error desconocido.\n" -#: src/fs/fs_namespace.c:631 +#: src/fs/fs_namespace.c:636 #, fuzzy msgid "Failed to connect to datastore." msgstr "Fallo al conectarse a gnunetd" @@ -2106,62 +2069,62 @@ msgstr "" "\n" "Error subiendo el fichero %s\n" -#: src/fs/fs_publish.c:621 src/fs/fs_publish.c:638 src/fs/fs_publish.c:677 -#: src/fs/fs_publish.c:697 src/fs/fs_publish.c:722 src/fs/fs_publish.c:862 +#: src/fs/fs_publish.c:622 src/fs/fs_publish.c:639 src/fs/fs_publish.c:678 +#: src/fs/fs_publish.c:698 src/fs/fs_publish.c:723 src/fs/fs_publish.c:863 #, fuzzy, c-format msgid "Can not index file `%s': %s. Will try to insert instead.\n" msgstr "Indexación del fichero '%s' fallida. Intentando insertar fichero...\n" -#: src/fs/fs_publish.c:623 +#: src/fs/fs_publish.c:624 msgid "timeout on index-start request to `fs' service" msgstr "" -#: src/fs/fs_publish.c:635 +#: src/fs/fs_publish.c:636 #, fuzzy msgid "unknown error" msgstr "Error desconocido" -#: src/fs/fs_publish.c:678 +#: src/fs/fs_publish.c:679 msgid "failed to compute hash" msgstr "" -#: src/fs/fs_publish.c:698 +#: src/fs/fs_publish.c:699 msgid "filename too long" msgstr "" -#: src/fs/fs_publish.c:723 +#: src/fs/fs_publish.c:724 #, fuzzy msgid "could not connect to `fs' service" msgstr "Imposible conectar con gnunetd.\n" -#: src/fs/fs_publish.c:746 +#: src/fs/fs_publish.c:747 #, fuzzy, c-format msgid "Failed to get file identifiers for `%s'\n" msgstr "Falló al actualizar los datos del módulo '%s'\n" -#: src/fs/fs_publish.c:811 +#: src/fs/fs_publish.c:812 #, fuzzy, c-format msgid "Recursive upload failed at `%s': %s" msgstr "'%s' falló en %s: %d con error: '%s'.\n" -#: src/fs/fs_publish.c:817 +#: src/fs/fs_publish.c:818 #, fuzzy, c-format msgid "Recursive upload failed: %s" msgstr "" "\n" "Error subiendo el fichero %s\n" -#: src/fs/fs_publish.c:863 +#: src/fs/fs_publish.c:864 #, fuzzy msgid "needs to be an actual file" msgstr "'%s' no es un fichero regular.\n" -#: src/fs/fs_publish.c:1071 +#: src/fs/fs_publish.c:1090 #, c-format msgid "Insufficient space for publishing: %s" msgstr "" -#: src/fs/fs_publish.c:1142 +#: src/fs/fs_publish.c:1161 #, c-format msgid "Reserving space for %u entries and %llu bytes for publication\n" msgstr "" @@ -2171,16 +2134,11 @@ msgstr "" msgid "Could not connect to datastore." msgstr "Imposible conectar con gnunetd.\n" -#: src/fs/fs_search.c:829 +#: src/fs/fs_search.c:892 #, c-format msgid "Got result with unknown block type `%d', ignoring" msgstr "" -#: src/fs/fs_test_lib.c:269 -#, fuzzy, c-format -msgid "Failed to start daemon: %s\n" -msgstr "Falló al comenzar la recolección.\n" - #: src/fs/fs_unindex.c:58 msgid "Failed to find given position in file" msgstr "" @@ -2208,97 +2166,97 @@ msgstr "Respuesta inválida a '%s'.\n" msgid "Failed to connect to FS service for unindexing." msgstr "Fallo al conectarse a gnunetd" -#: src/fs/fs_unindex.c:344 +#: src/fs/fs_unindex.c:349 src/fs/fs_unindex.c:361 #, fuzzy msgid "Failed to get KSKs from directory scan." msgstr "Error en el formato del fichero (¿no es un directorio de GNUnet?)\n" -#: src/fs/fs_unindex.c:356 +#: src/fs/fs_unindex.c:357 #, fuzzy, c-format msgid "Internal error scanning `%s'.\n" msgstr "=\tError leyendo el directorio.\n" -#: src/fs/fs_unindex.c:411 +#: src/fs/fs_unindex.c:416 #, fuzzy, c-format msgid "Failed to remove KBlock: %s\n" msgstr "Fichero almacenado en '%s'.\n" -#: src/fs/fs_unindex.c:501 +#: src/fs/fs_unindex.c:506 #, fuzzy, c-format msgid "Failed to parse URI `%s' from KBlock!\n" msgstr "El fichero '%s' tiene la URI: '%s'\n" -#: src/fs/fs_unindex.c:553 src/fs/fs_unindex.c:618 +#: src/fs/fs_unindex.c:558 src/fs/fs_unindex.c:623 #, fuzzy msgid "Failed to connect to `datastore' service." msgstr "Falló al inicializar el servicio '%s'.\n" -#: src/fs/fs_unindex.c:631 +#: src/fs/fs_unindex.c:636 #, fuzzy msgid "Failed to open file for unindexing." msgstr "Fallo al conectarse a gnunetd" -#: src/fs/fs_unindex.c:665 +#: src/fs/fs_unindex.c:670 #, fuzzy msgid "Failed to compute hash of file." msgstr "Fallo al conectarse a gnunetd" -#: src/fs/fs_uri.c:220 -#, c-format +#: src/fs/fs_uri.c:221 +#, no-c-format msgid "`%' must be followed by HEX number" msgstr "" -#: src/fs/fs_uri.c:279 +#: src/fs/fs_uri.c:280 #, fuzzy msgid "Malformed KSK URI (must not begin or end with `+')" msgstr "URL invalida '%s' (debe comenzar por '%s')\n" -#: src/fs/fs_uri.c:297 +#: src/fs/fs_uri.c:298 msgid "`++' not allowed in KSK URI" msgstr "" -#: src/fs/fs_uri.c:304 +#: src/fs/fs_uri.c:305 msgid "Quotes not balanced in KSK URI" msgstr "" -#: src/fs/fs_uri.c:372 src/fs/fs_uri.c:379 +#: src/fs/fs_uri.c:373 src/fs/fs_uri.c:380 msgid "Malformed SKS URI" msgstr "" -#: src/fs/fs_uri.c:423 src/fs/fs_uri.c:438 +#: src/fs/fs_uri.c:424 src/fs/fs_uri.c:439 msgid "Malformed CHK URI" msgstr "" -#: src/fs/fs_uri.c:568 src/fs/fs_uri.c:583 src/fs/fs_uri.c:593 -#: src/fs/fs_uri.c:621 +#: src/fs/fs_uri.c:569 src/fs/fs_uri.c:584 src/fs/fs_uri.c:594 +#: src/fs/fs_uri.c:622 msgid "SKS URI malformed" msgstr "" -#: src/fs/fs_uri.c:603 +#: src/fs/fs_uri.c:604 msgid "SKS URI malformed (could not decode public key)" msgstr "" -#: src/fs/fs_uri.c:609 +#: src/fs/fs_uri.c:610 msgid "SKS URI malformed (could not find signature)" msgstr "" -#: src/fs/fs_uri.c:615 +#: src/fs/fs_uri.c:616 msgid "SKS URI malformed (could not decode signature)" msgstr "" -#: src/fs/fs_uri.c:628 +#: src/fs/fs_uri.c:629 msgid "SKS URI malformed (could not parse expiration time)" msgstr "" -#: src/fs/fs_uri.c:640 +#: src/fs/fs_uri.c:641 msgid "SKS URI malformed (signature failed validation)" msgstr "" -#: src/fs/fs_uri.c:678 +#: src/fs/fs_uri.c:679 msgid "Unrecognized URI type" msgstr "" -#: src/fs/fs_uri.c:903 +#: src/fs/fs_uri.c:904 #, fuzzy msgid "Lacking key configuration settings.\n" msgstr "Configuración de GNUnet" @@ -2316,6 +2274,70 @@ msgstr "¡Ninguna clave especificada!\n" msgid "Number of double-quotes not balanced!\n" msgstr "" +#: src/fs/gnunet-auto-share.c:236 +#, fuzzy, c-format +msgid "Failed to load state: %s\n" +msgstr "Falló al comenzar la recolección.\n" + +#: src/fs/gnunet-auto-share.c:289 src/fs/gnunet-auto-share.c:299 +#: src/fs/gnunet-auto-share.c:309 +#, fuzzy, c-format +msgid "Failed to save state to file %s\n" +msgstr "Falló al actualizar los datos del módulo '%s'\n" + +#: src/fs/gnunet-auto-share.c:401 +#, c-format +msgid "Publication of `%s' done\n" +msgstr "" + +#: src/fs/gnunet-auto-share.c:488 +#, fuzzy, c-format +msgid "Publishing `%s'\n" +msgstr "" +"\n" +"Error subiendo el fichero %s\n" + +#: src/fs/gnunet-auto-share.c:497 +#, fuzzy, c-format +msgid "Failed to run `%s'\n" +msgstr "Falló al comenzar la recolección.\n" + +#: src/fs/gnunet-auto-share.c:686 +#, fuzzy, c-format +msgid "" +"You must specify one and only one directory name for automatic publication.\n" +msgstr "Debes especificar uno y solo un fichero para desindexar.\n" + +#: src/fs/gnunet-auto-share.c:737 src/fs/gnunet-pseudonym.c:279 +#: src/fs/gnunet-publish.c:683 +msgid "set the desired LEVEL of sender-anonymity" +msgstr "seleccione el NIVEL deseado de anonimato al enviar" + +#: src/fs/gnunet-auto-share.c:741 src/fs/gnunet-publish.c:687 +msgid "disable adding the creation time to the metadata of the uploaded file" +msgstr "" + +#: src/fs/gnunet-auto-share.c:744 src/fs/gnunet-publish.c:690 +msgid "do not use libextractor to add keywords or metadata" +msgstr "" + +#: src/fs/gnunet-auto-share.c:747 src/fs/gnunet-publish.c:714 +msgid "specify the priority of the content" +msgstr "especifica la prioridad del contenido" + +#: src/fs/gnunet-auto-share.c:750 src/fs/gnunet-pseudonym.c:304 +#: src/fs/gnunet-publish.c:721 +msgid "set the desired replication LEVEL" +msgstr "" + +#: src/fs/gnunet-auto-share.c:770 +msgid "Automatically publish files from a directory on GNUnet" +msgstr "" + +#: src/fs/gnunet-daemon-fsprofiler.c:656 +msgid "Daemon to use file-sharing to measure its performance." +msgstr "" + #: src/fs/gnunet-directory.c:49 #, c-format msgid "\t\n" @@ -2346,97 +2368,97 @@ msgstr "Error en el formato del fichero (¿no es un directorio de GNUnet?)\n" msgid "`%s' is not a GNUnet directory\n" msgstr "Error en el formato del fichero (¿no es un directorio de GNUnet?)\n" -#: src/fs/gnunet-directory.c:179 +#: src/fs/gnunet-directory.c:183 #, fuzzy msgid "Display contents of a GNUnet directory" msgstr "Error en el formato del fichero (¿no es un directorio de GNUnet?)\n" -#: src/fs/gnunet-download.c:101 +#: src/fs/gnunet-download.c:137 #, fuzzy, c-format msgid "Starting download `%s'.\n" msgstr "Iniciada colección '%s'.\n" -#: src/fs/gnunet-download.c:110 +#: src/fs/gnunet-download.c:147 #, fuzzy msgid "" msgstr "Error desconocido" -#: src/fs/gnunet-download.c:119 +#: src/fs/gnunet-download.c:157 #, c-format msgid "" "Downloading `%s' at %llu/%llu (%s remaining, %s/s). Block took %s to " "download\n" msgstr "" -#: src/fs/gnunet-download.c:129 +#: src/fs/gnunet-download.c:179 #, fuzzy, c-format msgid "Error downloading: %s.\n" msgstr "Error descargando: %s\n" -#: src/fs/gnunet-download.c:137 +#: src/fs/gnunet-download.c:194 #, fuzzy, c-format msgid "Downloading `%s' done (%s/s).\n" msgstr "¡Subida rechazada!" -#: src/fs/gnunet-download.c:152 src/fs/gnunet-publish.c:190 -#: src/fs/gnunet-search.c:190 src/fs/gnunet-unindex.c:109 +#: src/fs/gnunet-download.c:209 src/fs/gnunet-publish.c:195 +#: src/fs/gnunet-search.c:193 src/fs/gnunet-unindex.c:108 #, fuzzy, c-format msgid "Unexpected status: %d\n" msgstr "Estado de descarga inesperado." -#: src/fs/gnunet-download.c:177 +#: src/fs/gnunet-download.c:234 #, fuzzy msgid "You need to specify a URI argument.\n" msgstr "¡Debes especificar un receptor!\n" -#: src/fs/gnunet-download.c:183 src/fs/gnunet-publish.c:624 +#: src/fs/gnunet-download.c:240 src/fs/gnunet-publish.c:629 #, fuzzy, c-format msgid "Failed to parse URI: %s\n" msgstr "El fichero '%s' tiene la URI: '%s'\n" -#: src/fs/gnunet-download.c:190 +#: src/fs/gnunet-download.c:247 msgid "Only CHK or LOC URIs supported.\n" msgstr "" -#: src/fs/gnunet-download.c:197 +#: src/fs/gnunet-download.c:254 msgid "Target filename must be specified.\n" msgstr "" -#: src/fs/gnunet-download.c:211 src/fs/gnunet-publish.c:602 -#: src/fs/gnunet-search.c:241 src/fs/gnunet-unindex.c:141 +#: src/fs/gnunet-download.c:268 src/fs/gnunet-publish.c:607 +#: src/fs/gnunet-search.c:243 src/fs/gnunet-unindex.c:140 #, fuzzy, c-format msgid "Could not initialize `%s' subsystem.\n" msgstr "Falló al inicializar el servicio '%s'.\n" -#: src/fs/gnunet-download.c:248 src/fs/gnunet-search.c:285 +#: src/fs/gnunet-download.c:305 src/fs/gnunet-search.c:282 msgid "set the desired LEVEL of receiver-anonymity" msgstr "seleccione el NIVEL deseado de anonimidad-del-receptor" -#: src/fs/gnunet-download.c:251 +#: src/fs/gnunet-download.c:308 msgid "delete incomplete downloads (when aborted with CTRL-C)" msgstr "" -#: src/fs/gnunet-download.c:254 src/fs/gnunet-search.c:288 +#: src/fs/gnunet-download.c:311 src/fs/gnunet-search.c:285 msgid "only search the local peer (no P2P network search)" msgstr "" -#: src/fs/gnunet-download.c:257 +#: src/fs/gnunet-download.c:314 msgid "write the file to FILENAME" msgstr "escribe el fichero al FICHERO" -#: src/fs/gnunet-download.c:261 +#: src/fs/gnunet-download.c:318 msgid "set the maximum number of parallel downloads that is allowed" msgstr "" -#: src/fs/gnunet-download.c:265 +#: src/fs/gnunet-download.c:322 msgid "set the maximum number of parallel requests for blocks that is allowed" msgstr "" -#: src/fs/gnunet-download.c:268 +#: src/fs/gnunet-download.c:325 msgid "download a GNUnet directory recursively" msgstr "descarga un directorio de GNUnet recursivamente" -#: src/fs/gnunet-download.c:278 +#: src/fs/gnunet-download.c:339 msgid "" "Download files from GNUnet using a GNUnet CHK or LOC URI (gnunet://fs/" "chk/...)" @@ -2446,11 +2468,27 @@ msgstr "" msgid "print a list of all indexed files" msgstr "" -#: src/fs/gnunet-fs.c:124 +#: src/fs/gnunet-fs.c:127 msgid "Special file-sharing operations" msgstr "" -#: src/fs/gnunet-pseudonym.c:160 src/statistics/gnunet-statistics.c:167 +#: src/fs/gnunet-fs-profiler.c:182 +msgid "run the experiment with COUNT peers" +msgstr "" + +#: src/fs/gnunet-fs-profiler.c:185 +msgid "specifies name of a file with the HOSTS the testbed should use" +msgstr "" + +#: src/fs/gnunet-fs-profiler.c:188 +msgid "automatically terminate experiment after DELAY" +msgstr "" + +#: src/fs/gnunet-fs-profiler.c:197 +msgid "run a testbed to measure file-sharing performance" +msgstr "" + +#: src/fs/gnunet-pseudonym.c:160 src/statistics/gnunet-statistics.c:283 #, fuzzy, c-format msgid "Invalid argument `%s'\n" msgstr "Argumento no válido: '%s'\n" @@ -2461,10 +2499,6 @@ msgstr "Argumento no válido: '%s'\n" msgid "Option `%s' ignored\n" msgstr "%s: la opción '%s' es ambigua\n" -#: src/fs/gnunet-pseudonym.c:279 src/fs/gnunet-publish.c:678 -msgid "set the desired LEVEL of sender-anonymity" -msgstr "seleccione el NIVEL deseado de anonimato al enviar" - #: src/fs/gnunet-pseudonym.c:282 msgid "create or advertise namespace NAME" msgstr "" @@ -2482,7 +2516,7 @@ msgstr "" "añade una clave adicional para todos los ficheros y directorios (esta opción " "puede ser especificada varias veces)" -#: src/fs/gnunet-pseudonym.c:292 src/fs/gnunet-publish.c:697 +#: src/fs/gnunet-pseudonym.c:292 src/fs/gnunet-publish.c:702 msgid "set the meta-data for the given TYPE to the given VALUE" msgstr "cambia el meta-dato para el TIPO dado al VALOR dado" @@ -2499,10 +2533,6 @@ msgstr "" msgid "do not print names of remote namespaces" msgstr "" -#: src/fs/gnunet-pseudonym.c:304 src/fs/gnunet-publish.c:716 -msgid "set the desired replication LEVEL" -msgstr "" - #: src/fs/gnunet-pseudonym.c:307 #, fuzzy msgid "specify ID of the root of the namespace" @@ -2513,145 +2543,132 @@ msgstr "cambia la valoración de un espacio" msgid "change rating of namespace ID by VALUE" msgstr "cambia la valoración de un espacio" -#: src/fs/gnunet-pseudonym.c:318 +#: src/fs/gnunet-pseudonym.c:322 msgid "Manage GNUnet pseudonyms." msgstr "" -#: src/fs/gnunet-publish.c:147 +#: src/fs/gnunet-publish.c:152 #, c-format msgid "Publishing `%s' at %llu/%llu (%s remaining)\n" msgstr "" -#: src/fs/gnunet-publish.c:155 +#: src/fs/gnunet-publish.c:159 #, fuzzy, c-format msgid "Error publishing: %s.\n" msgstr "Error descargando: %s\n" -#: src/fs/gnunet-publish.c:165 +#: src/fs/gnunet-publish.c:169 #, c-format msgid "Publishing `%s' done.\n" msgstr "" -#: src/fs/gnunet-publish.c:169 +#: src/fs/gnunet-publish.c:173 #, fuzzy, c-format msgid "URI is `%s'.\n" msgstr "Yo soy el par '%s'.\n" -#: src/fs/gnunet-publish.c:187 +#: src/fs/gnunet-publish.c:192 #, fuzzy msgid "Cleanup after abort complete.\n" msgstr "'%s' comienzo completo.\n" -#: src/fs/gnunet-publish.c:305 +#: src/fs/gnunet-publish.c:310 #, fuzzy, c-format msgid "Meta data for file `%s' (%s)\n" msgstr "Actualizando los datos del módulo '%s'\n" -#: src/fs/gnunet-publish.c:307 +#: src/fs/gnunet-publish.c:312 #, fuzzy, c-format msgid "Keywords for file `%s' (%s)\n" msgstr "Claves para los ficheros '%s':\n" -#: src/fs/gnunet-publish.c:358 +#: src/fs/gnunet-publish.c:363 src/fs/gnunet-publish.c:617 #, fuzzy, c-format -msgid "Failed to create namespace `%s'\n" +msgid "Failed to create namespace `%s' (illegal filename?)\n" msgstr "Imposible crear el espacio '%s' (¿existe?).\n" -#: src/fs/gnunet-publish.c:433 +#: src/fs/gnunet-publish.c:438 #, fuzzy msgid "Could not publish\n" msgstr "Imposible ejecutar '%s': %s\n" -#: src/fs/gnunet-publish.c:460 +#: src/fs/gnunet-publish.c:465 #, fuzzy msgid "Could not start publishing.\n" msgstr "Imposible inicializar la aplicación '%s'\n" -#: src/fs/gnunet-publish.c:491 +#: src/fs/gnunet-publish.c:496 #, fuzzy, c-format msgid "Scanning directory `%s'.\n" msgstr "Error en el formato del fichero (¿no es un directorio de GNUnet?)\n" -#: src/fs/gnunet-publish.c:493 +#: src/fs/gnunet-publish.c:498 #, fuzzy, c-format msgid "Scanning file `%s'.\n" msgstr "Iniciada colección '%s'.\n" -#: src/fs/gnunet-publish.c:498 +#: src/fs/gnunet-publish.c:503 #, c-format msgid "There was trouble processing file `%s', skipping it.\n" msgstr "" -#: src/fs/gnunet-publish.c:503 +#: src/fs/gnunet-publish.c:508 #, fuzzy msgid "Preprocessing complete.\n" msgstr "Cierre completado.\n" -#: src/fs/gnunet-publish.c:507 +#: src/fs/gnunet-publish.c:512 #, fuzzy, c-format msgid "Extracting meta data from file `%s' complete.\n" msgstr "Actualizando los datos del módulo '%s'\n" -#: src/fs/gnunet-publish.c:511 +#: src/fs/gnunet-publish.c:516 msgid "Meta data extraction has finished.\n" msgstr "" -#: src/fs/gnunet-publish.c:518 +#: src/fs/gnunet-publish.c:523 #, fuzzy msgid "Internal error scanning directory.\n" msgstr "=\tError leyendo el directorio.\n" -#: src/fs/gnunet-publish.c:552 +#: src/fs/gnunet-publish.c:557 #, c-format msgid "Cannot extract metadata from a URI!\n" msgstr "" -#: src/fs/gnunet-publish.c:559 +#: src/fs/gnunet-publish.c:564 #, fuzzy, c-format msgid "You must specify one and only one filename for insertion.\n" msgstr "Debes especificar uno y solo un fichero para desindexar.\n" -#: src/fs/gnunet-publish.c:565 +#: src/fs/gnunet-publish.c:570 #, fuzzy, c-format msgid "You must NOT specify an URI and a filename.\n" msgstr "¡Debes especificar un receptor!\n" -#: src/fs/gnunet-publish.c:573 src/vpn/gnunet-vpn.c:214 +#: src/fs/gnunet-publish.c:578 src/vpn/gnunet-vpn.c:213 #, fuzzy, c-format msgid "Option `%s' is required when using option `%s'.\n" msgstr "La opción '%s' no tiene sentido sin la opción '%s'.\n" -#: src/fs/gnunet-publish.c:583 src/fs/gnunet-publish.c:590 -#: src/transport/gnunet-transport.c:560 +#: src/fs/gnunet-publish.c:588 src/fs/gnunet-publish.c:595 +#: src/transport/gnunet-transport.c:843 src/transport/gnunet-transport.c:873 #, c-format msgid "Option `%s' makes no sense without option `%s'.\n" msgstr "La opción '%s' no tiene sentido sin la opción '%s'.\n" -#: src/fs/gnunet-publish.c:612 -#, fuzzy, c-format -msgid "Could not create namespace `%s'\n" -msgstr "Imposible crear el espacio '%s' (¿existe?).\n" - -#: src/fs/gnunet-publish.c:645 +#: src/fs/gnunet-publish.c:650 #, fuzzy, c-format msgid "Failed to access `%s': %s\n" msgstr "Fichero almacenado en '%s'.\n" -#: src/fs/gnunet-publish.c:657 +#: src/fs/gnunet-publish.c:662 msgid "" "Failed to start meta directory scanner. Is gnunet-helper-publish-fs " "installed?\n" msgstr "" -#: src/fs/gnunet-publish.c:682 -msgid "disable adding the creation time to the metadata of the uploaded file" -msgstr "" - -#: src/fs/gnunet-publish.c:685 -msgid "do not use libextractor to add keywords or metadata" -msgstr "" - -#: src/fs/gnunet-publish.c:689 +#: src/fs/gnunet-publish.c:694 msgid "" "print list of extracted keywords that would be used, but do not perform " "upload" @@ -2659,7 +2676,7 @@ msgstr "" "imprime la lista de las claves extraidas que podrían ser usadas, pero no " "realiza la subida" -#: src/fs/gnunet-publish.c:693 +#: src/fs/gnunet-publish.c:698 msgid "" "add an additional keyword for the top-level file or directory (this option " "can be specified multiple times)" @@ -2667,7 +2684,7 @@ msgstr "" "añade una clave adicional para el fichero del nivel más alto o el directorio " "(esta opción puede ser especificada varias veces)" -#: src/fs/gnunet-publish.c:700 +#: src/fs/gnunet-publish.c:705 msgid "" "do not index, perform full insertion (stores entire file in encrypted form " "in GNUnet database)" @@ -2675,7 +2692,7 @@ msgstr "" "no indexar, hacer inserciones totales (almacena el fichero entero de forma " "encriptada en la base de datos de GNUnet)" -#: src/fs/gnunet-publish.c:705 +#: src/fs/gnunet-publish.c:710 msgid "" "specify ID of an updated version to be published in the future (for " "namespace insertions only)" @@ -2683,236 +2700,225 @@ msgstr "" "especifica la ID de una versión actualizada para ser publicada en el futuro " "(para inserciones en el espacio únicamente)" -#: src/fs/gnunet-publish.c:709 -msgid "specify the priority of the content" -msgstr "especifica la prioridad del contenido" - -#: src/fs/gnunet-publish.c:713 +#: src/fs/gnunet-publish.c:718 msgid "publish the files under the pseudonym NAME (place file into namespace)" msgstr "" "publica los ficheros bajo el pseudónimo NOMBRE (coloca el fichero en el " "espacio)" -#: src/fs/gnunet-publish.c:719 +#: src/fs/gnunet-publish.c:724 msgid "" "only simulate the process but do not do any actual publishing (useful to " "compute URIs)" msgstr "" -#: src/fs/gnunet-publish.c:723 +#: src/fs/gnunet-publish.c:728 msgid "" "set the ID of this version of the publication (for namespace insertions only)" msgstr "" "cambia la ID de esta versión de la publicación (para inserciones en el " "espacio únicamente)" -#: src/fs/gnunet-publish.c:727 +#: src/fs/gnunet-publish.c:732 msgid "" "URI to be published (can be used instead of passing a file to add keywords " "to the file with the respective URI)" msgstr "" -#: src/fs/gnunet-publish.c:742 +#: src/fs/gnunet-publish.c:748 msgid "Publish a file or directory on GNUnet" msgstr "" -#: src/fs/gnunet-search.c:111 +#: src/fs/gnunet-search.c:114 #, c-format msgid "Failed to write directory with search results to `%s'\n" msgstr "" -#: src/fs/gnunet-search.c:181 +#: src/fs/gnunet-search.c:184 #, fuzzy, c-format msgid "Error searching: %s.\n" msgstr "Error abandonando DHT.\n" -#: src/fs/gnunet-search.c:231 +#: src/fs/gnunet-search.c:233 #, fuzzy msgid "Could not create keyword URI from arguments.\n" msgstr "Imposible crear el espacio '%s' (¿existe?).\n" -#: src/fs/gnunet-search.c:255 +#: src/fs/gnunet-search.c:257 #, fuzzy msgid "Could not start searching.\n" msgstr "Imposible crear el espacio '%s' (¿existe?).\n" -#: src/fs/gnunet-search.c:291 +#: src/fs/gnunet-search.c:288 msgid "write search results to file starting with PREFIX" msgstr "" -#: src/fs/gnunet-search.c:294 -msgid "automatically terminate search after VALUE ms" +#: src/fs/gnunet-search.c:291 +msgid "automatically terminate search after DELAY" msgstr "" -#: src/fs/gnunet-search.c:301 +#: src/fs/gnunet-search.c:298 msgid "automatically terminate search after VALUE results are found" msgstr "" -#: src/fs/gnunet-search.c:308 +#: src/fs/gnunet-search.c:309 msgid "Search GNUnet for files that were published on GNUnet" msgstr "" -#: src/fs/gnunet-service-fs.c:240 +#: src/fs/gnunet-service-fs.c:248 msgid "# running average P2P latency (ms)" msgstr "" -#: src/fs/gnunet-service-fs.c:300 src/fs/gnunet-service-fs.c:489 +#: src/fs/gnunet-service-fs.c:309 src/fs/gnunet-service-fs.c:523 msgid "# Loopback routes suppressed" msgstr "" -#: src/fs/gnunet-service-fs.c:581 src/hostlist/gnunet-daemon-hostlist.c:297 -#: src/topology/gnunet-daemon-topology.c:1330 -#: src/topology/gnunet-daemon-topology.c:1337 +#: src/fs/gnunet-service-fs.c:628 src/hostlist/gnunet-daemon-hostlist.c:297 +#: src/topology/gnunet-daemon-topology.c:1322 +#: src/topology/gnunet-daemon-topology.c:1329 #, fuzzy, c-format msgid "Failed to connect to `%s' service.\n" msgstr "Fallo al conectar a gnunetd.\n" -#: src/fs/gnunet-service-fs_cp.c:696 +#: src/fs/gnunet-service-fs_cp.c:711 #, fuzzy msgid "# migration stop messages received" msgstr "# mensajes PONG encriptados recibidos" -#: src/fs/gnunet-service-fs_cp.c:700 +#: src/fs/gnunet-service-fs_cp.c:715 #, c-format -msgid "Migration of content to peer `%s' blocked for %llu ms\n" +msgid "Migration of content to peer `%s' blocked for %s\n" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:735 +#: src/fs/gnunet-service-fs_cp.c:751 msgid "# replies transmitted to other peers" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:741 +#: src/fs/gnunet-service-fs_cp.c:757 msgid "# replies dropped" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:766 src/fs/gnunet-service-fs_cp.c:1324 +#: src/fs/gnunet-service-fs_cp.c:782 src/fs/gnunet-service-fs_cp.c:1345 msgid "# P2P searches active" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:858 +#: src/fs/gnunet-service-fs_cp.c:875 msgid "# artificial delays introduced (ms)" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:911 +#: src/fs/gnunet-service-fs_cp.c:928 #, fuzzy msgid "# replies dropped due to type mismatch" msgstr "# Anuncios de los pares recibidos" -#: src/fs/gnunet-service-fs_cp.c:919 +#: src/fs/gnunet-service-fs_cp.c:936 msgid "# replies received for other peers" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:933 +#: src/fs/gnunet-service-fs_cp.c:950 msgid "# replies dropped due to insufficient cover traffic" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:971 +#: src/fs/gnunet-service-fs_cp.c:988 msgid "# P2P searches destroyed due to ultimate reply" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:1038 +#: src/fs/gnunet-service-fs_cp.c:1056 #, fuzzy msgid "# requests done for free (low load)" msgstr "# Anuncios de los pares recibidos" -#: src/fs/gnunet-service-fs_cp.c:1062 +#: src/fs/gnunet-service-fs_cp.c:1081 msgid "# request dropped, priority insufficient" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:1072 +#: src/fs/gnunet-service-fs_cp.c:1091 #, fuzzy msgid "# requests done for a price (normal load)" msgstr "# Anuncios de los pares recibidos" -#: src/fs/gnunet-service-fs_cp.c:1151 +#: src/fs/gnunet-service-fs_cp.c:1170 msgid "# GET requests received (from other peers)" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:1185 +#: src/fs/gnunet-service-fs_cp.c:1204 #, fuzzy msgid "# requests dropped due to initiator not being connected" msgstr "# Anuncios de los pares recibidos" -#: src/fs/gnunet-service-fs_cp.c:1207 +#: src/fs/gnunet-service-fs_cp.c:1227 #, fuzzy msgid "# requests dropped due to missing reverse route" msgstr "# Anuncios de los pares recibidos" -#: src/fs/gnunet-service-fs_cp.c:1267 +#: src/fs/gnunet-service-fs_cp.c:1288 #, fuzzy msgid "# requests dropped due TTL underflow" msgstr "# Anuncios de los pares recibidos" -#: src/fs/gnunet-service-fs_cp.c:1293 +#: src/fs/gnunet-service-fs_cp.c:1314 #, fuzzy msgid "# requests dropped due to higher-TTL request" msgstr "# Anuncios de los pares recibidos" -#: src/fs/gnunet-service-fs_cp.c:1322 +#: src/fs/gnunet-service-fs_cp.c:1343 #, fuzzy msgid "# P2P query messages received and processed" msgstr "# mensajes PONG encriptados recibidos" -#: src/fs/gnunet-service-fs_cp.c:1687 +#: src/fs/gnunet-service-fs_cp.c:1713 #, fuzzy msgid "# migration stop messages sent" msgstr "# mensajes PONG encriptados recibidos" -#: src/fs/gnunet-service-fs_indexing.c:113 -#: src/fs/gnunet-service-fs_indexing.c:163 -#, fuzzy, c-format -msgid "Configuration option `%s' in section `%s' missing.\n" -msgstr "Fichero de configuración '%s' creado.\n" - -#: src/fs/gnunet-service-fs_indexing.c:121 -#: src/fs/gnunet-service-fs_indexing.c:177 +#: src/fs/gnunet-service-fs_indexing.c:130 +#: src/fs/gnunet-service-fs_indexing.c:181 #, fuzzy, c-format msgid "Could not open `%s'.\n" msgstr "Fichero almacenado en '%s'.\n" -#: src/fs/gnunet-service-fs_indexing.c:137 +#: src/fs/gnunet-service-fs_indexing.c:142 #, fuzzy, c-format msgid "Error writing `%s'.\n" msgstr "Error creando usuario" -#: src/fs/gnunet-service-fs_indexing.c:228 +#: src/fs/gnunet-service-fs_indexing.c:237 #, c-format msgid "" "Index request received for file `%s' is already indexed as `%s'. Permitting " "anyway.\n" msgstr "" -#: src/fs/gnunet-service-fs_indexing.c:266 +#: src/fs/gnunet-service-fs_indexing.c:275 #, c-format msgid "Hash mismatch trying to index file `%s' which has hash `%s'\n" msgstr "" -#: src/fs/gnunet-service-fs_indexing.c:481 +#: src/fs/gnunet-service-fs_indexing.c:477 #, fuzzy, c-format msgid "Failed to delete bogus block: %s\n" msgstr "Fichero almacenado en '%s'.\n" -#: src/fs/gnunet-service-fs_indexing.c:539 +#: src/fs/gnunet-service-fs_indexing.c:542 msgid "# index blocks removed: original file inaccessible" msgstr "" -#: src/fs/gnunet-service-fs_indexing.c:554 +#: src/fs/gnunet-service-fs_indexing.c:557 #, fuzzy, c-format msgid "Could not access indexed file `%s' (%s) at offset %llu: %s\n" msgstr "Imposible resolver '%s': %s\n" -#: src/fs/gnunet-service-fs_indexing.c:556 +#: src/fs/gnunet-service-fs_indexing.c:559 #, fuzzy msgid "not indexed" msgstr "El desindexado falló" -#: src/fs/gnunet-service-fs_indexing.c:571 +#: src/fs/gnunet-service-fs_indexing.c:574 #, fuzzy, c-format msgid "Indexed file `%s' changed at offset %llu\n" msgstr "La indexación de los datos falló en la posición %i.\n" -#: src/fs/gnunet-service-fs_lc.c:202 src/fs/gnunet-service-fs_lc.c:362 -#: src/fs/gnunet-service-fs_lc.c:488 +#: src/fs/gnunet-service-fs_lc.c:202 src/fs/gnunet-service-fs_lc.c:369 #, fuzzy msgid "# client searches active" msgstr "# mensajes PONG encriptados recibidos" @@ -2922,327 +2928,482 @@ msgstr "# mensajes PONG encriptados recibidos" msgid "# replies received for local clients" msgstr "El mensaje recibido del cliente es inválido\n" -#: src/fs/gnunet-service-fs_lc.c:321 +#: src/fs/gnunet-service-fs_lc.c:328 #, fuzzy msgid "# client searches received" msgstr "# mensajes PONG encriptados recibidos" -#: src/fs/gnunet-service-fs_lc.c:356 +#: src/fs/gnunet-service-fs_lc.c:363 msgid "# client searches updated (merged content seen list)" msgstr "" -#: src/fs/gnunet-service-fs_pe.c:265 +#: src/fs/gnunet-service-fs_pe.c:269 msgid "# average retransmission delay (ms)" msgstr "" -#: src/fs/gnunet-service-fs_pe.c:391 +#: src/fs/gnunet-service-fs_pe.c:400 msgid "# transmission failed (core has no bandwidth)" msgstr "" -#: src/fs/gnunet-service-fs_pe.c:420 +#: src/fs/gnunet-service-fs_pe.c:433 #, fuzzy msgid "# query messages sent to other peers" msgstr "# bytes de mensajes salientes omitidos" -#: src/fs/gnunet-service-fs_pe.c:469 +#: src/fs/gnunet-service-fs_pe.c:482 msgid "# delay heap timeout" msgstr "" -#: src/fs/gnunet-service-fs_pe.c:476 +#: src/fs/gnunet-service-fs_pe.c:490 #, fuzzy msgid "# query plans executed" msgstr "# mensajes PONG encriptados recibidos" -#: src/fs/gnunet-service-fs_pe.c:538 +#: src/fs/gnunet-service-fs_pe.c:550 #, fuzzy msgid "# requests merged" msgstr "# mensajes PONG encriptados recibidos" -#: src/fs/gnunet-service-fs_pe.c:544 +#: src/fs/gnunet-service-fs_pe.c:558 #, fuzzy msgid "# requests refreshed" msgstr "# mensajes PONG encriptados recibidos" -#: src/fs/gnunet-service-fs_pe.c:597 src/fs/gnunet-service-fs_pe.c:681 -#: src/fs/gnunet-service-fs_pe.c:748 +#: src/fs/gnunet-service-fs_pe.c:612 src/fs/gnunet-service-fs_pe.c:696 +#: src/fs/gnunet-service-fs_pe.c:767 msgid "# query plan entries" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:285 +#: src/fs/gnunet-service-fs_pr.c:312 #, fuzzy msgid "# Pending requests created" msgstr "# mensajes PONG encriptados recibidos" -#: src/fs/gnunet-service-fs_pr.c:367 src/fs/gnunet-service-fs_pr.c:616 +#: src/fs/gnunet-service-fs_pr.c:404 src/fs/gnunet-service-fs_pr.c:667 #, fuzzy msgid "# Pending requests active" msgstr "# mensajes PONG encriptados recibidos" -#: src/fs/gnunet-service-fs_pr.c:779 +#: src/fs/gnunet-service-fs_pr.c:835 #, fuzzy msgid "# replies received and matched" msgstr "# bytes recibidos por TCP" -#: src/fs/gnunet-service-fs_pr.c:808 +#: src/fs/gnunet-service-fs_pr.c:868 msgid "# duplicate replies discarded (bloomfilter)" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:822 +#: src/fs/gnunet-service-fs_pr.c:877 +msgid "# irrelevant replies discarded" +msgstr "" + +#: src/fs/gnunet-service-fs_pr.c:891 #, c-format msgid "Unsupported block type %u\n" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:835 +#: src/fs/gnunet-service-fs_pr.c:904 msgid "# results found locally" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:953 +#: src/fs/gnunet-service-fs_pr.c:1025 msgid "# Datastore `PUT' failures" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:980 +#: src/fs/gnunet-service-fs_pr.c:1052 #, fuzzy msgid "# storage requests dropped due to high load" msgstr "# Anuncios de los pares recibidos" -#: src/fs/gnunet-service-fs_pr.c:1015 +#: src/fs/gnunet-service-fs_pr.c:1087 #, fuzzy msgid "# Replies received from DHT" msgstr "# bytes recibidos vía HTTP" -#: src/fs/gnunet-service-fs_pr.c:1106 +#: src/fs/gnunet-service-fs_pr.c:1221 +#, fuzzy +msgid "# Replies received from STREAM" +msgstr "# bytes recibidos vía HTTP" + +#: src/fs/gnunet-service-fs_pr.c:1273 #, c-format -msgid "Datastore lookup already took %llu ms!\n" +msgid "Datastore lookup already took %s!\n" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1127 +#: src/fs/gnunet-service-fs_pr.c:1293 #, c-format -msgid "On-demand lookup already took %llu ms!\n" +msgid "On-demand lookup already took %s!\n" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1174 +#: src/fs/gnunet-service-fs_pr.c:1340 msgid "# Datastore lookups concluded (no results)" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1188 +#: src/fs/gnunet-service-fs_pr.c:1355 msgid "# Datastore lookups concluded (seen all)" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1197 +#: src/fs/gnunet-service-fs_pr.c:1364 msgid "# Datastore lookups aborted (more than MAX_RESULTS)" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1211 +#: src/fs/gnunet-service-fs_pr.c:1379 msgid "# requested DBLOCK or IBLOCK not found" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1224 +#: src/fs/gnunet-service-fs_pr.c:1393 msgid "# on-demand blocks matched requests" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1237 +#: src/fs/gnunet-service-fs_pr.c:1406 msgid "# on-demand lookups performed successfully" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1242 +#: src/fs/gnunet-service-fs_pr.c:1411 msgid "# on-demand lookups failed" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1269 src/fs/gnunet-service-fs_pr.c:1309 -#: src/fs/gnunet-service-fs_pr.c:1447 +#: src/fs/gnunet-service-fs_pr.c:1438 src/fs/gnunet-service-fs_pr.c:1478 +#: src/fs/gnunet-service-fs_pr.c:1619 msgid "# Datastore lookups concluded (error queueing)" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1327 +#: src/fs/gnunet-service-fs_pr.c:1496 msgid "# Datastore lookups concluded (found last result)" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1338 +#: src/fs/gnunet-service-fs_pr.c:1507 msgid "# Datastore lookups concluded (load too high)" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1424 +#: src/fs/gnunet-service-fs_pr.c:1595 msgid "# Datastore lookups initiated" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1508 +#: src/fs/gnunet-service-fs_pr.c:1680 #, fuzzy msgid "# GAP PUT messages received" msgstr "# mensajes PONG encriptados recibidos" -#: src/fs/gnunet-service-fs_pr.c:1601 src/fs/gnunet-service-fs_pr.c:1610 -#, fuzzy, c-format -msgid "Configuration fails to specify `%s', assuming default value." -msgstr "Fichero de configuración '%s' creado.\n" - #: src/fs/gnunet-service-fs_push.c:629 -#, c-format -msgid "" -"Invalid value specified for option `%s' in section `%s', content pushing " -"disabled\n" +msgid "time required, content pushing disabled" +msgstr "" + +#: src/fs/gnunet-service-fs_stream.c:777 +#, fuzzy +msgid "# replies received via stream" +msgstr "# bytes recibidos por TCP" + +#: src/fs/gnunet-service-fs_stream.c:791 +#, fuzzy +msgid "# replies received via stream dropped" +msgstr "# bytes recibidos por TCP" + +#: src/fs/gnunet-service-fs_stream.c:930 +#: src/fs/gnunet-service-fs_stream.c:1384 +#, fuzzy +msgid "# stream connections active" +msgstr "# de pares conectados" + +#: src/fs/gnunet-service-fs_stream.c:1166 +msgid "# Blocks transferred via stream" msgstr "" +#: src/fs/gnunet-service-fs_stream.c:1326 +#, fuzzy +msgid "# queries received via stream" +msgstr "# bytes recibidos por TCP" + +#: src/fs/gnunet-service-fs_stream.c:1376 +#, fuzzy +msgid "# stream client connections rejected" +msgstr "Configuración de GNUnet" + #: src/fs/gnunet-unindex.c:89 #, c-format msgid "Unindexing at %llu/%llu (%s remaining)\n" msgstr "" -#: src/fs/gnunet-unindex.c:96 +#: src/fs/gnunet-unindex.c:95 #, fuzzy, c-format msgid "Error unindexing: %s.\n" msgstr "" "\n" "Error desindexando el fichero: %s\n" -#: src/fs/gnunet-unindex.c:101 +#: src/fs/gnunet-unindex.c:100 #, fuzzy msgid "Unindexing done.\n" msgstr "Desindexar los ficheros." -#: src/fs/gnunet-unindex.c:131 +#: src/fs/gnunet-unindex.c:130 #, fuzzy, c-format msgid "You must specify one and only one filename for unindexing.\n" msgstr "Debes especificar uno y solo un fichero para desindexar.\n" -#: src/fs/gnunet-unindex.c:148 +#: src/fs/gnunet-unindex.c:147 #, fuzzy msgid "Could not start unindex operation.\n" msgstr "Imposible acceder a la información del espacio.\n" -#: src/fs/gnunet-unindex.c:176 +#: src/fs/gnunet-unindex.c:179 msgid "Unindex a file that was previously indexed with gnunet-publish." msgstr "" -#: src/fs/plugin_block_fs.c:131 -msgid "Reply mismatched in terms of namespace. Discarded.\n" -msgstr "" +#: src/gns/gns_api.c:598 +#, fuzzy +msgid "Failed to serialize lookup reply from GNS service!\n" +msgstr "Falló al recibir la respuesta al mensaje '%s' de gnunetd\n" -#: src/gns/gnunet-gns.c:191 +#: src/gns/gnunet-dns2gns.c:192 #, fuzzy +msgid "Failed to pack DNS response into UDP packet!\n" +msgstr "Falló al mandar la petición HTTP al host '%s': %s\n" + +#: src/gns/gnunet-dns2gns.c:367 +#, fuzzy, c-format +msgid "Cannot parse DNS request from %s\n" +msgstr "Falló al mandar la petición HTTP al host '%s': %s\n" + +#: src/gns/gnunet-dns2gns.c:383 +#, fuzzy, c-format +msgid "Received malformed DNS request from %s\n" +msgstr "GAP recibido contenido no válido de '%s'\n" + +#: src/gns/gnunet-dns2gns.c:391 +#, fuzzy, c-format +msgid "Received unsupported DNS request from %s\n" +msgstr "GAP recibido contenido no válido de '%s'\n" + +#: src/gns/gnunet-dns2gns.c:679 +msgid "IP of recursive DNS resolver to use (required)" +msgstr "" + +#: src/gns/gnunet-dns2gns.c:682 +msgid "Authoritative DNS suffix to use (optional); default: zkey.eu" +msgstr "" + +#: src/gns/gnunet-dns2gns.c:685 +msgid "Authoritative FCFS suffix to use (optional); default: fcfs.zkey.eu" +msgstr "" + +#: src/gns/gnunet-dns2gns.c:688 +msgid "UDP port to listen on for inbound DNS requests; default: 53" +msgstr "" + +#: src/gns/gnunet-dns2gns.c:701 +msgid "GNUnet DNS-to-GNS proxy (a DNS server)" +msgstr "" + +#: src/gns/gnunet-gns.c:221 +#, fuzzy, c-format msgid "Failed to connect to GNS\n" msgstr "Fallo al conectar a gnunetd.\n" -#: src/gns/gnunet-gns.c:232 -msgid "try to shorten a given GNS name" +#: src/gns/gnunet-gns.c:335 +#, c-format +msgid "Please specify lookup, shorten or authority operation!\n" msgstr "" -#: src/gns/gnunet-gns.c:235 -msgid "Lookup a record using GNS (NOT IMPLEMENTED)" +#: src/gns/gnunet-gns.c:356 +#, fuzzy +msgid "try to shorten a given name" +msgstr "Fallo al conectar a gnunetd.\n" + +#: src/gns/gnunet-gns.c:359 +msgid "Lookup a record for the given name" msgstr "" -#: src/gns/gnunet-gns.c:238 +#: src/gns/gnunet-gns.c:362 msgid "Get the authority of a particular name" msgstr "" -#: src/gns/gnunet-gns.c:241 +#: src/gns/gnunet-gns.c:365 #, fuzzy -msgid "Specify the type of the record lookup" +msgid "Specify the type of the record to lookup" msgstr "especifica la prioridad del contenido" -#: src/gns/gnunet-gns.c:244 +#: src/gns/gnunet-gns.c:368 msgid "No unneeded output" msgstr "" -#: src/gns/gnunet-gns.c:255 +#: src/gns/gnunet-gns.c:381 msgid "GNUnet GNS access tool" msgstr "" -#: src/gns/gnunet-gns-fcfsd.c:280 +#: src/gns/gnunet-gns-fcfsd.c:451 #, fuzzy, c-format msgid "Unsupported form value `%s'\n" msgstr "Comando inesperado '%s'. Abortando.\n" -#: src/gns/gnunet-gns-fcfsd.c:333 +#: src/gns/gnunet-gns-fcfsd.c:480 #, fuzzy, c-format msgid "Failed to create record for domain `%s': %s\n" msgstr "Imposible pasar el fichero de configuración '%s'.\n" -#: src/gns/gnunet-gns-fcfsd.c:377 +#: src/gns/gnunet-gns-fcfsd.c:524 #, c-format msgid "Found existing name `%s' for the given key\n" msgstr "" -#: src/gns/gnunet-gns-fcfsd.c:439 +#: src/gns/gnunet-gns-fcfsd.c:586 #, c-format msgid "Found %u existing records for domain `%s'\n" msgstr "" -#: src/gns/gnunet-gns-fcfsd.c:498 +#: src/gns/gnunet-gns-fcfsd.c:648 #, fuzzy, c-format msgid "Failed to create page for `%s'\n" msgstr "Imposible crear el espacio '%s' (¿existe?).\n" -#: src/gns/gnunet-gns-fcfsd.c:514 +#: src/gns/gnunet-gns-fcfsd.c:664 #, fuzzy, c-format msgid "Failed to setup post processor for `%s'\n" msgstr "Falló al actualizar los datos del módulo '%s'\n" -#: src/gns/gnunet-gns-fcfsd.c:725 src/gns/gnunet-gns-fcfsd.c:737 -#, fuzzy, c-format -msgid "Option `%s' not specified in configuration section `%s'\n" -msgstr "¡Ninguna aplicación definida en la configuración!\n" +#: src/gns/gnunet-gns-fcfsd.c:700 +msgid "Domain name must not contain `.'\n" +msgstr "" + +#: src/gns/gnunet-gns-fcfsd.c:708 +msgid "Domain name must not contain `+'\n" +msgstr "" -#: src/gns/gnunet-gns-fcfsd.c:747 src/namestore/gnunet-namestore.c:299 +#: src/gns/gnunet-gns-fcfsd.c:912 src/namestore/gnunet-namestore.c:364 #, fuzzy msgid "Failed to read or create private zone key\n" msgstr "Falló al actualizar los datos del módulo '%s'\n" -#: src/gns/gnunet-gns-fcfsd.c:757 src/namestore/gnunet-namestore.c:310 +#: src/gns/gnunet-gns-fcfsd.c:922 src/namestore/gnunet-namestore.c:375 #, fuzzy msgid "Failed to connect to namestore\n" msgstr "Fallo al conectarse a gnunetd" -#: src/gns/gnunet-gns-fcfsd.c:773 src/gns/gnunet-gns-proxy.c:525 +#: src/gns/gnunet-gns-fcfsd.c:938 src/gns/gnunet-gns-proxy.c:2857 #, fuzzy msgid "Failed to start HTTP server\n" msgstr "Falló al comenzar la recolección.\n" -#: src/gns/gnunet-gns-fcfsd.c:804 +#: src/gns/gnunet-gns-fcfsd.c:972 msgid "GNUnet GNS first come first serve registration service" msgstr "" -#: src/gns/gnunet-gns-proxy.c:800 -msgid "listen on specified port" +#: src/gns/gnunet-gns-proxy.c:2494 +#, fuzzy, c-format +msgid "Unable to import private key from file `%s'\n" +msgstr "Imposible crear la cuenta de usuario:" + +#: src/gns/gnunet-gns-proxy.c:2522 +#, fuzzy, c-format +msgid "Unable to import certificate %s\n" +msgstr "Imposible guardar el fichero de configuración '%s':" + +#: src/gns/gnunet-gns-proxy.c:3510 +msgid "listen on specified port (default: 7777)" +msgstr "" + +#: src/gns/gnunet-gns-proxy.c:3513 +msgid "pem file to use as CA" msgstr "" -#: src/gns/gnunet-gns-proxy.c:811 +#: src/gns/gnunet-gns-proxy.c:3525 msgid "GNUnet GNS proxy" msgstr "" -#: src/hello/gnunet-hello.c:122 +#: src/gns/gnunet-service-gns.c:486 +#, c-format +msgid "Records for name `%s' in zone %s too large to fit into DHT" +msgstr "" + +#: src/gns/gnunet-service-gns.c:1216 +#, fuzzy +msgid "Failed to connect to the namestore!\n" +msgstr "Fallo al conectarse a gnunetd" + +#: src/gns/gnunet-service-gns.c:1277 +#, fuzzy +msgid "Could not connect to DHT!\n" +msgstr "Imposible conectar con gnunetd.\n" + +#: src/gns/gnunet-service-gns.c:1288 +#, fuzzy +msgid "Unable to initialize resolver!\n" +msgstr "Imposible inicializar SQLite.\n" + +#: src/gns/gnunet-service-gns_resolver.c:3439 +#, c-format +msgid "Not a GADS TLD: `%s'\n" +msgstr "" + +#: src/hello/gnunet-hello.c:118 msgid "Call with name of HELLO file to modify.\n" msgstr "" -#: src/hello/gnunet-hello.c:128 +#: src/hello/gnunet-hello.c:124 #, fuzzy, c-format msgid "Error accessing file `%s': %s\n" msgstr "Error creando usuario" -#: src/hello/gnunet-hello.c:136 +#: src/hello/gnunet-hello.c:132 #, c-format msgid "File `%s' is too big to be a HELLO\n" msgstr "" -#: src/hello/gnunet-hello.c:143 +#: src/hello/gnunet-hello.c:139 #, c-format msgid "File `%s' is too small to be a HELLO\n" msgstr "" -#: src/hello/gnunet-hello.c:153 src/hello/gnunet-hello.c:181 +#: src/hello/gnunet-hello.c:149 src/hello/gnunet-hello.c:177 #, fuzzy, c-format msgid "Error opening file `%s': %s\n" msgstr "Error creando usuario" -#: src/hello/gnunet-hello.c:169 +#: src/hello/gnunet-hello.c:165 #, fuzzy, c-format msgid "Did not find well-formed HELLO in file `%s'\n" msgstr "Falló al actualizar los datos del módulo '%s'\n" -#: src/hello/gnunet-hello.c:193 +#: src/hello/gnunet-hello.c:189 #, fuzzy, c-format msgid "Error writing HELLO to file `%s': %s\n" msgstr "Error creando usuario" +#: src/hello/hello.c:904 +#, fuzzy +msgid "Failed to parse HELLO message: missing expiration time\n" +msgstr "Imposible guardar la configuración" + +#: src/hello/hello.c:913 +#, fuzzy +msgid "Failed to parse HELLO message: invalid expiration time\n" +msgstr "Imposible guardar la configuración" + +#: src/hello/hello.c:923 +#, fuzzy +msgid "Failed to parse HELLO message: malformed\n" +msgstr "Falló al pasar los datos de la interfaz de '%s' de %s:%d.\n" + +#: src/hello/hello.c:933 +#, fuzzy +msgid "Failed to parse HELLO message: missing transport plugin\n" +msgstr "Imposible inicializar la aplicación '%s'\n" + +#: src/hello/hello.c:950 +#, c-format +msgid "Plugin `%s' not found\n" +msgstr "" + +#: src/hello/hello.c:959 +#, c-format +msgid "Plugin `%s' does not support URIs yet\n" +msgstr "" + +#: src/hello/hello.c:978 +#, fuzzy, c-format +msgid "Failed to parse `%s' as an address for plugin `%s'\n" +msgstr "Fallo al conectar a gnunetd.\n" + #: src/hostlist/gnunet-daemon-hostlist.c:264 msgid "" "None of the functions for the hostlist daemon were enabled. I have no " @@ -3267,7 +3428,7 @@ msgstr "" msgid "provide a hostlist server" msgstr "" -#: src/hostlist/gnunet-daemon-hostlist.c:341 +#: src/hostlist/gnunet-daemon-hostlist.c:344 msgid "GNUnet hostlist server and client" msgstr "" @@ -3290,178 +3451,142 @@ msgstr "Mensaje '%s' inválido recibido del par '%s'.\n" msgid "# valid HELLOs downloaded from hostlist servers" msgstr "# saludos descargados vía HTTP" -#: src/hostlist/hostlist-client.c:375 src/hostlist/hostlist-client.c:396 -#, c-format -msgid "No `%s' specified in `%s' configuration, will not bootstrap.\n" -msgstr "" - -#: src/hostlist/hostlist-client.c:473 src/hostlist/hostlist-client.c:683 -#: src/hostlist/hostlist-client.c:689 src/hostlist/hostlist-client.c:741 -#: src/hostlist/hostlist-client.c:750 src/hostlist/hostlist-client.c:871 -#: src/hostlist/hostlist-client.c:961 src/hostlist/hostlist-client.c:966 -#: src/transport/plugin_transport_http_client.c:110 -#: src/transport/plugin_transport_http_client.c:125 +#: src/hostlist/hostlist-client.c:469 src/hostlist/hostlist-client.c:680 +#: src/hostlist/hostlist-client.c:686 src/hostlist/hostlist-client.c:738 +#: src/hostlist/hostlist-client.c:747 src/hostlist/hostlist-client.c:868 +#: src/hostlist/hostlist-client.c:958 src/hostlist/hostlist-client.c:963 +#: src/transport/plugin_transport_http_client.c:1052 +#: src/transport/plugin_transport_http_client.c:1067 #, fuzzy, c-format msgid "%s failed at %s:%d: `%s'\n" msgstr "'%s' falló en %s: %d con error: '%s'.\n" -#: src/hostlist/hostlist-client.c:593 src/hostlist/hostlist-client.c:1331 +#: src/hostlist/hostlist-client.c:589 src/hostlist/hostlist-client.c:1325 msgid "# advertised hostlist URIs" msgstr "" -#: src/hostlist/hostlist-client.c:623 +#: src/hostlist/hostlist-client.c:619 #, c-format msgid "# advertised URI `%s' downloaded" msgstr "" -#: src/hostlist/hostlist-client.c:664 +#: src/hostlist/hostlist-client.c:661 #, c-format msgid "" "Advertised hostlist with URI `%s' could not be downloaded. Advertised URI " "gets dismissed.\n" msgstr "" -#: src/hostlist/hostlist-client.c:802 +#: src/hostlist/hostlist-client.c:799 #, c-format msgid "Timeout trying to download hostlist from `%s'\n" msgstr "" -#: src/hostlist/hostlist-client.c:816 +#: src/hostlist/hostlist-client.c:813 #, c-format msgid "Download limit of %u bytes exceeded, stopping download\n" msgstr "" -#: src/hostlist/hostlist-client.c:836 +#: src/hostlist/hostlist-client.c:833 #, fuzzy, c-format msgid "Download of hostlist from `%s' failed: `%s'\n" msgstr "" "Subida de '%s' completada, la velocidad media de subida actual es %8.3f " "kbps.\n" -#: src/hostlist/hostlist-client.c:842 +#: src/hostlist/hostlist-client.c:839 #, fuzzy, c-format msgid "Download of hostlist `%s' completed.\n" msgstr "" "Subida de '%s' completada, la velocidad media de subida actual es %8.3f " "kbps.\n" -#: src/hostlist/hostlist-client.c:850 +#: src/hostlist/hostlist-client.c:847 #, c-format msgid "Adding successfully tested hostlist `%s' datastore.\n" msgstr "" -#: src/hostlist/hostlist-client.c:903 +#: src/hostlist/hostlist-client.c:900 #, c-format msgid "Bootstrapping using hostlist at `%s'.\n" msgstr "" -#: src/hostlist/hostlist-client.c:911 +#: src/hostlist/hostlist-client.c:908 msgid "# hostlist downloads initiated" msgstr "" -#: src/hostlist/hostlist-client.c:1037 src/hostlist/hostlist-client.c:1505 +#: src/hostlist/hostlist-client.c:1035 src/hostlist/hostlist-client.c:1498 msgid "# milliseconds between hostlist downloads" msgstr "" -#: src/hostlist/hostlist-client.c:1046 -#, c-format -msgid "Have %u/%u connections. Will consider downloading hostlist in %llums\n" -msgstr "" - -#: src/hostlist/hostlist-client.c:1084 -msgid "Scheduled saving of hostlists\n" -msgstr "" - -#: src/hostlist/hostlist-client.c:1088 +#: src/hostlist/hostlist-client.c:1043 #, c-format -msgid "Hostlists will be saved to file again in %llums\n" +msgid "Have %u/%u connections. Will consider downloading hostlist in %s\n" msgstr "" -#: src/hostlist/hostlist-client.c:1111 src/hostlist/hostlist-client.c:1127 +#: src/hostlist/hostlist-client.c:1107 src/hostlist/hostlist-client.c:1123 #, fuzzy msgid "# active connections" msgstr "Configuración de GNUnet" -#: src/hostlist/hostlist-client.c:1242 -#, c-format -msgid "Initial time between hostlist downloads is %llums\n" -msgstr "" - #: src/hostlist/hostlist-client.c:1273 #, c-format -msgid "" -"No `%s' specified in `%s' configuration, cannot load hostlists from file.\n" -msgstr "" - -#: src/hostlist/hostlist-client.c:1279 -#, c-format msgid "Loading saved hostlist entries from file `%s' \n" msgstr "" -#: src/hostlist/hostlist-client.c:1283 -#, c-format -msgid "Hostlist file `%s' is not existing\n" -msgstr "" +#: src/hostlist/hostlist-client.c:1277 +#, fuzzy, c-format +msgid "Hostlist file `%s' does not exist\n" +msgstr "La clave de sesión del par '%s' no pudo ser verificada.\n" -#: src/hostlist/hostlist-client.c:1294 +#: src/hostlist/hostlist-client.c:1288 #, fuzzy, c-format msgid "Could not open file `%s' for reading to load hostlists: %s\n" msgstr "Fichero almacenado en '%s'.\n" -#: src/hostlist/hostlist-client.c:1327 +#: src/hostlist/hostlist-client.c:1321 #, c-format msgid "%u hostlist URIs loaded from file\n" msgstr "" -#: src/hostlist/hostlist-client.c:1329 +#: src/hostlist/hostlist-client.c:1323 msgid "# hostlist URIs read from file" msgstr "" -#: src/hostlist/hostlist-client.c:1362 -#, c-format -msgid "" -"No `%s' specified in `%s' configuration, cannot save hostlists to file.\n" -msgstr "" - -#: src/hostlist/hostlist-client.c:1376 +#: src/hostlist/hostlist-client.c:1368 #, fuzzy, c-format msgid "Could not open file `%s' for writing to save hostlists: %s\n" msgstr "Fichero almacenado en '%s'.\n" -#: src/hostlist/hostlist-client.c:1381 +#: src/hostlist/hostlist-client.c:1373 #, c-format msgid "Writing %u hostlist URIs to `%s'\n" msgstr "" -#: src/hostlist/hostlist-client.c:1405 src/hostlist/hostlist-client.c:1422 +#: src/hostlist/hostlist-client.c:1397 src/hostlist/hostlist-client.c:1414 #, fuzzy, c-format msgid "Error writing hostlist URIs to file `%s'\n" msgstr "Error creando usuario" -#: src/hostlist/hostlist-client.c:1417 +#: src/hostlist/hostlist-client.c:1409 msgid "# hostlist URIs written to file" msgstr "" -#: src/hostlist/hostlist-client.c:1470 +#: src/hostlist/hostlist-client.c:1463 msgid "Learning is enabled on this peer\n" msgstr "" -#: src/hostlist/hostlist-client.c:1473 -#, c-format -msgid "Hostlists will be saved to file again in %llums\n" -msgstr "" - -#: src/hostlist/hostlist-client.c:1482 +#: src/hostlist/hostlist-client.c:1475 msgid "Learning is not enabled on this peer\n" msgstr "" -#: src/hostlist/hostlist-client.c:1494 +#: src/hostlist/hostlist-client.c:1487 #, c-format msgid "" "Since learning is not enabled on this peer, hostlist file `%s' was removed\n" msgstr "" -#: src/hostlist/hostlist-client.c:1498 +#: src/hostlist/hostlist-client.c:1491 #, fuzzy, c-format msgid "Hostlist file `%s' could not be removed\n" msgstr "La clave de sesión del par '%s' no pudo ser verificada.\n" @@ -3476,9 +3601,9 @@ msgid "expired addresses encountered" msgstr "" #: src/hostlist/hostlist-server.c:184 src/hostlist/hostlist-server.c:425 -#: src/peerinfo-tool/gnunet-peerinfo.c:403 -#: src/peerinfo-tool/gnunet-peerinfo.c:519 -#: src/topology/gnunet-daemon-topology.c:927 +#: src/peerinfo-tool/gnunet-peerinfo.c:331 +#: src/peerinfo-tool/gnunet-peerinfo.c:386 +#: src/topology/gnunet-daemon-topology.c:922 #, fuzzy, c-format msgid "Error in communication with PEERINFO service: %s\n" msgstr "Imprime información de los pares de GNUnet." @@ -3501,10 +3626,6 @@ msgstr "" msgid "hostlist requests refused (not HTTP GET)" msgstr "# mensajes PONG encriptados recibidos" -#: src/hostlist/hostlist-server.c:273 -msgid "Sending 100 CONTINUE reply\n" -msgstr "" - #: src/hostlist/hostlist-server.c:279 #, c-format msgid "Refusing `%s' request with %llu bytes of upload data\n" @@ -3542,66 +3663,103 @@ msgstr "# Anuncios a extraños mandados" msgid "Advertisement message could not be queued by core\n" msgstr "" -#: src/hostlist/hostlist-server.c:561 +#: src/hostlist/hostlist-server.c:562 #, fuzzy, c-format msgid "Invalid port number %llu. Exiting.\n" msgstr "Argumentos no válidos. Saliendo.\n" -#: src/hostlist/hostlist-server.c:570 +#: src/hostlist/hostlist-server.c:571 #, c-format msgid "Hostlist service starts on %s:%llu\n" msgstr "" -#: src/hostlist/hostlist-server.c:584 +#: src/hostlist/hostlist-server.c:585 #, c-format msgid "Address to obtain hostlist: `%s'\n" msgstr "" -#: src/hostlist/hostlist-server.c:624 +#: src/hostlist/hostlist-server.c:625 #, fuzzy, c-format msgid "`%s' is not a valid IP address! Ignoring BINDTOIP.\n" msgstr "'%s' no esta disponible." -#: src/hostlist/hostlist-server.c:666 +#: src/hostlist/hostlist-server.c:667 #, c-format msgid "Could not start hostlist HTTP server on port %u\n" msgstr "" -#: src/integration-tests/connection_watchdog.c:997 +#: src/integration-tests/connection_watchdog.c:1001 #, fuzzy, c-format msgid "Transport plugin: `%s' port %llu\n" msgstr "Probando transporte(s) %s\n" -#: src/integration-tests/connection_watchdog.c:1030 +#: src/integration-tests/connection_watchdog.c:1034 #, fuzzy, c-format msgid "Found %u transport plugins: `%s'\n" msgstr "Probando transporte(s) %s\n" -#: src/integration-tests/connection_watchdog.c:1089 +#: src/integration-tests/connection_watchdog.c:1093 msgid "Send ping messages to test connectivity (default == NO)" msgstr "" -#: src/integration-tests/connection_watchdog.c:1095 -#: src/template/gnunet-template.c:68 +#: src/integration-tests/connection_watchdog.c:1102 +#: src/template/gnunet-template.c:70 #, fuzzy msgid "help text" msgstr "texto de ayuda para -t" -#: src/mesh/gnunet-service-mesh.c:4590 +#: src/mesh/gnunet-mesh.c:211 #, fuzzy -msgid "Wrong CORE service\n" -msgstr "Deteniendo cron\n" +msgid "provide information about all tunnels (continuously) NOT IMPLEMENTED" +msgstr "Imprime información de los pares de GNUnet." -#: src/mesh/gnunet-service-mesh.c:4784 +#: src/mesh/gnunet-mesh.c:214 #, fuzzy -msgid "Mesh service is lacking key configuration settings. Exiting.\n" -msgstr "Configuración de GNUnet" +msgid "provide information about a particular tunnel" +msgstr "Imprime información de los pares de GNUnet." -#: src/mesh/gnunet-service-mesh.c:4793 +#: src/mesh/gnunet-mesh.c:224 #, fuzzy -msgid "Mesh service could not access hostkey. Exiting.\n" +msgid "Print information about mesh tunnels and peers." +msgstr "Imprime información de los pares de GNUnet." + +#: src/mesh/gnunet-service-mesh.c:8015 src/mesh/gnunet-service-mesh-new.c:8015 +msgid "Wrong CORE service\n" +msgstr "" + +#: src/mesh/gnunet-service-mesh.c:8232 src/mesh/gnunet-service-mesh-new.c:8232 +#, fuzzy, c-format +msgid "Mesh service could not access hostkey: %s. Exiting.\n" msgstr "Imposible acceder a la información del espacio.\n" +#: src/mesh/gnunet-service-mesh.c:8314 src/mesh/gnunet-service-mesh.c:8326 +#: src/mesh/gnunet-service-mesh.c:8338 src/mesh/gnunet-service-mesh.c:8352 +#: src/mesh/gnunet-service-mesh.c:8364 src/mesh/gnunet-service-mesh.c:8376 +#: src/mesh/gnunet-service-mesh.c:8388 src/mesh/gnunet-service-mesh-new.c:8321 +#: src/mesh/gnunet-service-mesh-new.c:8333 +#: src/mesh/gnunet-service-mesh-new.c:8345 +#: src/mesh/gnunet-service-mesh-new.c:8359 +#: src/mesh/gnunet-service-mesh-new.c:8371 +#: src/mesh/gnunet-service-mesh-new.c:8383 +#: src/mesh/gnunet-service-mesh-new.c:8395 +#: src/regex/gnunet-daemon-regexprofiler.c:335 +#: src/regex/gnunet-daemon-regexprofiler.c:347 +#: src/regex/gnunet-daemon-regexprofiler.c:360 +#: src/regex/gnunet-daemon-regexprofiler.c:373 +#: src/regex/gnunet-regex-simulation-profiler.c:659 +#, fuzzy, c-format +msgid "%s service is lacking key configuration settings (%s). Exiting.\n" +msgstr "Configuración de GNUnet" + +#: src/mesh/gnunet-service-mesh.c:8400 src/mesh/gnunet-service-mesh.c:8410 +#: src/mesh/gnunet-service-mesh.c:8421 src/mesh/gnunet-service-mesh-new.c:8407 +#: src/mesh/gnunet-service-mesh-new.c:8417 +#: src/mesh/gnunet-service-mesh-new.c:8428 +#, fuzzy, c-format +msgid "" +"%s service is lacking key configuration settings (%s). Using default (%u).\n" +msgstr "Configuración de GNUnet" + #: src/mysql/mysql.c:174 #, c-format msgid "Trying to use file `%s' for MySQL configuration.\n" @@ -3612,201 +3770,330 @@ msgstr "Intentando usar el fichero '%s' para la configuración de MySQL.\n" msgid "Could not access file `%s': %s\n" msgstr "Imposible ejecutar '%s': %s\n" -#: src/namestore/gnunet-namestore.c:157 +#: src/namestore/gnunet-namestore.c:212 #, fuzzy, c-format msgid "Adding record failed: %s\n" msgstr "" "\n" "Error subiendo el fichero %s\n" -#: src/namestore/gnunet-namestore.c:183 +#: src/namestore/gnunet-namestore.c:243 #, fuzzy, c-format msgid "Deleting record failed: %s\n" msgstr "" "\n" "Error subiendo el fichero %s\n" -#: src/namestore/gnunet-namestore.c:239 +#: src/namestore/gnunet-namestore.c:304 #, c-format msgid "\tCorrupt or unsupported record of type %u\n" msgstr "" -#: src/namestore/gnunet-namestore.c:276 -#, c-format -msgid "Option `%s' not given, but I need a zone key file!\n" +#: src/namestore/gnunet-namestore.c:320 +msgid "for at least" msgstr "" -#: src/namestore/gnunet-namestore.c:281 -#, fuzzy, c-format -msgid "Using default zone file `%s'\n" -msgstr "Iniciada colección '%s'.\n" +#: src/namestore/gnunet-namestore.c:321 +msgid "until" +msgstr "" -#: src/namestore/gnunet-namestore.c:291 +#: src/namestore/gnunet-namestore.c:356 #, c-format msgid "No options given\n" msgstr "" -#: src/namestore/gnunet-namestore.c:321 +#: src/namestore/gnunet-namestore.c:386 #, fuzzy, c-format msgid "Unsupported type `%s'\n" msgstr "Mensaje no válido del tipo %u recibido. Omitiendo.\n" -#: src/namestore/gnunet-namestore.c:328 src/namestore/gnunet-namestore.c:350 -#: src/namestore/gnunet-namestore.c:374 src/namestore/gnunet-namestore.c:384 -#: src/namestore/gnunet-namestore.c:409 +#: src/namestore/gnunet-namestore.c:394 src/namestore/gnunet-namestore.c:418 +#: src/namestore/gnunet-namestore.c:465 src/namestore/gnunet-namestore.c:477 +#: src/namestore/gnunet-namestore.c:518 #, fuzzy, c-format msgid "Missing option `%s' for operation `%s'\n" msgstr "Fichero de configuración '%s' creado.\n" -#: src/namestore/gnunet-namestore.c:329 src/namestore/gnunet-namestore.c:351 +#: src/namestore/gnunet-namestore.c:395 src/namestore/gnunet-namestore.c:419 msgid "add/del" msgstr "" -#: src/namestore/gnunet-namestore.c:341 +#: src/namestore/gnunet-namestore.c:408 #, fuzzy, c-format msgid "Value `%s' invalid for record type `%s'\n" msgstr "%s: valor del símbolo '%s' no válido para %s\n" -#: src/namestore/gnunet-namestore.c:366 +#: src/namestore/gnunet-namestore.c:446 #, fuzzy, c-format msgid "Invalid time format `%s'\n" msgstr "Argumento no válido: '%s'\n" -#: src/namestore/gnunet-namestore.c:375 src/namestore/gnunet-namestore.c:385 +#: src/namestore/gnunet-namestore.c:455 +#, c-format +msgid "" +"Deletion requires either absolute time, or no time at all. Got relative time " +"`%s' instead.\n" +msgstr "" + +#: src/namestore/gnunet-namestore.c:466 src/namestore/gnunet-namestore.c:478 +#: src/namestore/gnunet-namestore.c:497 msgid "add" msgstr "" -#: src/namestore/gnunet-namestore.c:410 +#: src/namestore/gnunet-namestore.c:496 +#, fuzzy, c-format +msgid "No valid expiration time for operation `%s'\n" +msgstr "Fichero de configuración '%s' creado.\n" + +#: src/namestore/gnunet-namestore.c:519 msgid "del" msgstr "" -#: src/namestore/gnunet-namestore.c:462 +#: src/namestore/gnunet-namestore.c:569 +#: src/peerinfo-tool/gnunet-peerinfo.c:598 +#, fuzzy, c-format +msgid "Invalid URI `%s'\n" +msgstr "Argumento no válido: '%s'\n" + +#: src/namestore/gnunet-namestore.c:625 +#, fuzzy, c-format +msgid "Using default zone file `%s'\n" +msgstr "Iniciada colección '%s'.\n" + +#: src/namestore/gnunet-namestore.c:677 msgid "add record" msgstr "" -#: src/namestore/gnunet-namestore.c:465 +#: src/namestore/gnunet-namestore.c:680 msgid "delete record" msgstr "" -#: src/namestore/gnunet-namestore.c:468 +#: src/namestore/gnunet-namestore.c:683 msgid "display records" msgstr "" -#: src/namestore/gnunet-namestore.c:471 +#: src/namestore/gnunet-namestore.c:686 msgid "" "expiration time for record to use (for adding only), \"never\" is possible" msgstr "" -#: src/namestore/gnunet-namestore.c:474 +#: src/namestore/gnunet-namestore.c:689 msgid "name of the record to add/delete/display" msgstr "" -#: src/namestore/gnunet-namestore.c:477 +#: src/namestore/gnunet-namestore.c:692 msgid "type of the record to add/delete/display" msgstr "" -#: src/namestore/gnunet-namestore.c:480 +#: src/namestore/gnunet-namestore.c:695 +msgid "URI to import into our zone" +msgstr "" + +#: src/namestore/gnunet-namestore.c:698 msgid "value of the record to add/delete" msgstr "" -#: src/namestore/gnunet-namestore.c:483 +#: src/namestore/gnunet-namestore.c:701 msgid "create or list public record" msgstr "" -#: src/namestore/gnunet-namestore.c:486 +#: src/namestore/gnunet-namestore.c:704 msgid "create or list non-authority record" msgstr "" -#: src/namestore/gnunet-namestore.c:489 +#: src/namestore/gnunet-namestore.c:707 msgid "filename with the zone key" msgstr "" -#: src/namestore/gnunet-namestore.c:500 +#: src/namestore/gnunet-namestore.c:718 #, fuzzy msgid "GNUnet zone manipulation tool" msgstr "Configuración de GNUnet" -#: src/namestore/gnunet-service-namestore.c:143 -#, c-format -msgid "File zone `%s' but corrupt content already exists, failed to write! \n" -msgstr "" +#: src/namestore/gnunet-service-namestore.c:241 +#: src/namestore/gnunet-service-namestore.c:257 +#, fuzzy, c-format +msgid "Failed to write zone key to file `%s': %s\n" +msgstr "Fichero almacenado en '%s'.\n" -#: src/namestore/gnunet-service-namestore.c:154 -#, c-format -msgid "File zone `%s' containing this key already exists\n" +#: src/namestore/gnunet-service-namestore.c:243 +msgid "file exists but reading key failed" msgstr "" -#: src/namestore/gnunet-service-namestore.c:160 -#, c-format -msgid "" -"File zone `%s' but different zone key already exists, failed to write! \n" +#: src/namestore/gnunet-service-namestore.c:259 +msgid "file exists with different key" msgstr "" -#: src/namestore/gnunet-service-namestore.c:198 +#: src/namestore/gnunet-service-namestore.c:1557 +#, fuzzy +msgid "Failed to find record to remove\n" +msgstr "Imposible conectar con gnunetd.\n" + +#: src/namestore/gnunet-service-namestore.c:2172 #, fuzzy, c-format -msgid "Stored zonekey for zone `%s' in file `%s'\n" -msgstr "Fichero almacenado en '%s'.\n" +msgid "Could not parse zone key file `%s'\n" +msgstr "Imposible pasar el fichero de configuración '%s'.\n" -#: src/namestore/gnunet-service-namestore.c:1909 +#: src/namestore/gnunet-service-namestore.c:2262 #, fuzzy msgid "No directory to load zonefiles specified in configuration\n" msgstr "¡Ninguna aplicación definida en la configuración!\n" -#: src/namestore/gnunet-service-namestore.c:1918 +#: src/namestore/gnunet-service-namestore.c:2272 #, c-format msgid "Creating directory `%s' for zone files failed!\n" msgstr "" -#: src/namestore/namestore_api.c:315 src/namestore/namestore_api.c:353 -msgid "Namestore added record successfully" -msgstr "" - -#: src/namestore/namestore_api.c:323 +#: src/namestore/namestore_api.c:345 msgid "Namestore failed to add record" msgstr "" -#: src/namestore/namestore_api.c:361 -msgid "Namestore record already existed" -msgstr "" - -#: src/namestore/namestore_api.c:368 +#: src/namestore/namestore_api.c:371 msgid "Namestore failed to add record\n" msgstr "" -#: src/namestore/namestore_api.c:401 +#: src/namestore/namestore_api.c:415 +#, fuzzy +msgid "Failed to create new signature" +msgstr "Imposible crear el espacio '%s' (¿existe?).\n" + +#: src/namestore/namestore_api.c:419 #, fuzzy -msgid "Namestore removed record successfully" -msgstr "Servicio de GNUnet instalado satisfactoriamente.\n" +msgid "Failed to put new set of records in database" +msgstr "Falló al mandar la petición HTTP al host '%s': %s\n" -#: src/namestore/namestore_api.c:408 -msgid "No records for entry" +#: src/namestore/namestore_api.c:423 +#, fuzzy +msgid "Failed to remove records from database" msgstr "" +"\n" +"Fallo al recibir la respuesta de gnunetd.\n" -#: src/namestore/namestore_api.c:415 +#: src/namestore/namestore_api.c:427 #, fuzzy -msgid "Could not find record to remove" -msgstr "Imposible conectar con gnunetd.\n" +msgid "Failed to access database" +msgstr "Fichero almacenado en '%s'.\n" -#: src/namestore/namestore_api.c:422 +#: src/namestore/namestore_api.c:431 #, fuzzy -msgid "Failed to create new signature" -msgstr "Imposible crear el espacio '%s' (¿existe?).\n" +msgid "unknown internal error in namestore" +msgstr "=\tError leyendo el directorio.\n" + +#: src/namestore/namestore_api.c:436 +msgid "Protocol error" +msgstr "" + +#: src/namestore/namestore_common.c:530 src/namestore/namestore_common.c:670 +#, fuzzy, c-format +msgid "Unsupported record type %d\n" +msgstr "Mensaje no válido del tipo %u recibido. Omitiendo.\n" + +#: src/namestore/namestore_common.c:537 +#, fuzzy, c-format +msgid "Unable to parse IPv4 address `%s'\n" +msgstr "Argumento no válido: '%s'\n" + +#: src/namestore/namestore_common.c:560 +#, fuzzy, c-format +msgid "Unable to parse SOA record `%s'\n" +msgstr "Error en el formato del fichero (¿no es un directorio de GNUnet?)\n" -#: src/namestore/namestore_api.c:429 +#: src/namestore/namestore_common.c:583 +#, fuzzy, c-format +msgid "Unable to parse MX record `%s'\n" +msgstr "Error en el formato del fichero (¿no es un directorio de GNUnet?)\n" + +#: src/namestore/namestore_common.c:601 +#, fuzzy, c-format +msgid "Unable to parse IPv6 address `%s'\n" +msgstr "Argumento no válido: '%s'\n" + +#: src/namestore/namestore_common.c:614 +#, fuzzy, c-format +msgid "Unable to parse PKEY record `%s'\n" +msgstr "Error en el formato del fichero (¿no es un directorio de GNUnet?)\n" + +#: src/namestore/namestore_common.c:635 +#, fuzzy, c-format +msgid "Unable to parse VPN record string `%s'\n" +msgstr "Falló al actualizar los datos del módulo '%s'\n" + +#: src/namestore/namestore_common.c:661 +#, fuzzy, c-format +msgid "Unable to parse TLSA record string `%s'\n" +msgstr "Falló al actualizar los datos del módulo '%s'\n" + +#: src/namestore/plugin_namestore_postgres.c:95 #, fuzzy -msgid "Failed to put new set of records in database" -msgstr "Falló al mandar la petición HTTP al host '%s': %s\n" +msgid "Failed to create indices\n" +msgstr "Imposible crear el espacio '%s' (¿existe?).\n" #: src/nat/gnunet-nat-server.c:279 #, c-format msgid "Please pass valid port number as the first argument! (got `%s')\n" msgstr "" -#: src/nat/gnunet-nat-server.c:318 +#: src/nat/gnunet-nat-server.c:321 msgid "GNUnet NAT traversal test helper daemon" msgstr "" -#: src/nat/nat.c:799 +#: src/nat/nat_auto.c:169 +msgid "NAT traversal with ICMP Server timed out.\n" +msgstr "" + +#: src/nat/nat_auto.c:199 +msgid "NAT traversal with ICMP Server succeeded.\n" +msgstr "" + +#: src/nat/nat_auto.c:200 +msgid "NAT traversal with ICMP Server failed.\n" +msgstr "" + +#: src/nat/nat_auto.c:219 +#, fuzzy +msgid "Testing connection reversal with ICMP server.\n" +msgstr "Imprime información de los pares de GNUnet." + +#: src/nat/nat_auto.c:265 +#, fuzzy, c-format +msgid "Detected external IP `%s'\n" +msgstr "Recibido RPC '%s' inválida.\n" + +#: src/nat/nat_auto.c:331 +msgid "This system has a global IPv6 address, setting IPv6 to supported.\n" +msgstr "" + +#: src/nat/nat_auto.c:347 +#, fuzzy, c-format +msgid "Detected internal network address `%s'.\n" +msgstr "GNUnet usa ahora la dirección IP %u.%u.%u.%u.\n" + +#: src/nat/nat_auto.c:400 +msgid "upnpc found, enabling its use\n" +msgstr "" + +#: src/nat/nat_auto.c:401 +#, fuzzy +msgid "upnpc not found\n" +msgstr "¡Comando '%s' no encontrado!\n" + +#: src/nat/nat_auto.c:434 +msgid "gnunet-helper-nat-server found, testing it\n" +msgstr "" + +#: src/nat/nat_auto.c:435 +msgid "No working gnunet-helper-nat-server found\n" +msgstr "" + +#: src/nat/nat_auto.c:469 +msgid "gnunet-helper-nat-client found, enabling it\n" +msgstr "" + +#: src/nat/nat_auto.c:470 +msgid "gnunet-helper-nat-client not found or behind NAT, disabling it\n" +msgstr "" + +#: src/nat/nat.c:795 #, c-format msgid "gnunet-helper-nat-server generated malformed address `%s'\n" msgstr "" @@ -3816,27 +4103,34 @@ msgstr "" msgid "Failed to start %s\n" msgstr "Falló al comenzar la recolección.\n" -#: src/nat/nat.c:1111 -#, fuzzy, c-format -msgid "Malformed %s `%s' given in configuration!\n" -msgstr "Imposible guardar la configuración" +#: src/nat/nat.c:1113 +msgid "malformed" +msgstr "" -#: src/nat/nat.c:1177 src/nat/nat.c:1187 +#: src/nat/nat.c:1179 src/nat/nat.c:1191 #, c-format msgid "" "Configuration requires `%s', but binary is not installed properly (SUID bit " "not set). Option disabled.\n" msgstr "" -#: src/nat/nat.c:1321 +#: src/nat/nat.c:1326 msgid "Internal IP address not known, cannot use ICMP NAT traversal method\n" msgstr "" -#: src/nat/nat.c:1332 +#: src/nat/nat.c:1337 #, c-format msgid "Running gnunet-helper-nat-client %s %s %u\n" msgstr "" +#: src/nat/nat_mini.c:170 +msgid "`external-ip' command not found\n" +msgstr "" + +#: src/nat/nat_mini.c:505 +msgid "`upnpc' command not found\n" +msgstr "" + #: src/nat/nat_test.c:341 #, fuzzy msgid "Failed to connect to `gnunet-nat-server'\n" @@ -3847,46 +4141,78 @@ msgstr "Fallo al conectar a gnunetd.\n" msgid "Failed to create listen socket bound to `%s' for NAT test: %s\n" msgstr "" -#: src/nse/gnunet-nse-profiler.c:928 +#: src/nse/gnunet-nse-profiler.c:1009 +#, fuzzy +msgid "limit to the number of connections to NSE services, 0 for none" +msgstr "Fallo al conectarse a gnunetd" + +#: src/nse/gnunet-nse-profiler.c:1012 +msgid "name of the file for writing connection information and statistics" +msgstr "" + +#: src/nse/gnunet-nse-profiler.c:1015 +msgid "name of the file with the login information for the testbed" +msgstr "" + +#: src/nse/gnunet-nse-profiler.c:1018 +msgid "IP address of this system as seen by the rest of the testbed" +msgstr "" + +#: src/nse/gnunet-nse-profiler.c:1021 +msgid "delay between queries to statistics during a round" +msgstr "" + +#: src/nse/gnunet-nse-profiler.c:1024 +msgid "prefix of the filenames we use for writing the topology for each round" +msgstr "" + +#: src/nse/gnunet-nse-profiler.c:1027 +msgid "name of the file for writing the main results" +msgstr "" + +#: src/nse/gnunet-nse-profiler.c:1030 +msgid "Number of peers to run in each round, separated by commas" +msgstr "" + +#: src/nse/gnunet-nse-profiler.c:1036 +msgid "delay between rounds" +msgstr "" + +#: src/nse/gnunet-nse-profiler.c:1046 #, fuzzy msgid "Measure quality and performance of the NSE service." msgstr "Imposible acceder al servicio" -#: src/nse/gnunet-service-nse.c:925 -#, c-format -msgid "Proof of work invalid: %llu!\n" -msgstr "" +#: src/nse/gnunet-service-nse.c:1389 +#, fuzzy, c-format +msgid "NSE service could not access hostkey: %s\n" +msgstr "Imposible acceder a la información del espacio.\n" -#: src/nse/gnunet-service-nse.c:1381 src/nse/gnunet-service-nse.c:1400 -#: src/nse/gnunet-service-nse.c:1421 +#: src/nse/gnunet-service-nse.c:1403 src/nse/gnunet-service-nse.c:1478 +#: src/nse/gnunet-service-nse.c:1495 msgid "NSE service is lacking key configuration settings. Exiting.\n" msgstr "" -#: src/nse/gnunet-service-nse.c:1388 +#: src/nse/gnunet-service-nse.c:1485 #, fuzzy msgid "Invalid work requirement for NSE service. Exiting.\n" msgstr "Argumentos no válidos. Saliendo.\n" -#: src/nse/gnunet-service-nse.c:1409 -#, fuzzy -msgid "NSE service could not access hostkey. Exiting.\n" -msgstr "Imposible acceder a la información del espacio.\n" - #: src/peerinfo/gnunet-service-peerinfo.c:134 #, fuzzy, c-format msgid "Removing expired address of transport `%s'\n" msgstr "Transporte(s) disponible(s): %s\n" -#: src/peerinfo/gnunet-service-peerinfo.c:203 +#: src/peerinfo/gnunet-service-peerinfo.c:230 #, fuzzy, c-format msgid "Failed to parse HELLO in file `%s'\n" msgstr "Falló al actualizar los datos del módulo '%s'\n" -#: src/peerinfo/gnunet-service-peerinfo.c:229 +#: src/peerinfo/gnunet-service-peerinfo.c:269 msgid "# peers known" msgstr "" -#: src/peerinfo/gnunet-service-peerinfo.c:254 +#: src/peerinfo/gnunet-service-peerinfo.c:297 #, c-format msgid "" "File `%s' in directory `%s' does not match naming convention. Removed.\n" @@ -3894,38 +4220,38 @@ msgstr "" "El fichero '%s' en el directorio '%s' no sigue la convención de nombres. " "Eliminando.\n" -#: src/peerinfo/gnunet-service-peerinfo.c:353 +#: src/peerinfo/gnunet-service-peerinfo.c:419 #, fuzzy, c-format msgid "Still no peers found in `%s'!\n" msgstr "¡Imposible descargar adecuadamente el servicio '%s'!\n" -#: src/peerinfo/gnunet-service-peerinfo.c:710 +#: src/peerinfo/gnunet-service-peerinfo.c:807 #, c-format msgid "Importing HELLOs from `%s'\n" msgstr "" -#: src/peerinfo/peerinfo_api.c:238 +#: src/peerinfo/peerinfo_api.c:239 msgid "aborted due to explicit disconnect request" msgstr "" -#: src/peerinfo/peerinfo_api.c:358 +#: src/peerinfo/peerinfo_api.c:359 #, fuzzy msgid "failed to transmit request (service down?)" msgstr "Falló al mandar la petición HTTP al host '%s': %s\n" -#: src/peerinfo/peerinfo_api.c:505 +#: src/peerinfo/peerinfo_api.c:509 #, fuzzy msgid "Failed to receive response from `PEERINFO' service." msgstr "Falló al recibir la respuesta al mensaje '%s' de gnunetd\n" -#: src/peerinfo/peerinfo_api.c:531 src/peerinfo/peerinfo_api.c:550 -#: src/peerinfo/peerinfo_api.c:565 src/peerinfo/peerinfo_api.c:576 -#: src/peerinfo/peerinfo_api.c:587 +#: src/peerinfo/peerinfo_api.c:550 src/peerinfo/peerinfo_api.c:569 +#: src/peerinfo/peerinfo_api.c:584 src/peerinfo/peerinfo_api.c:595 +#: src/peerinfo/peerinfo_api.c:606 #, fuzzy msgid "Received invalid message from `PEERINFO' service." msgstr "Recibido mensaje UDP6 inválido de %s:%d, omitiendo.\n" -#: src/peerinfo/peerinfo_api.c:663 +#: src/peerinfo/peerinfo_api.c:681 #, fuzzy msgid "Timeout transmitting iteration request to `PEERINFO' service." msgstr "Falló al inicializar el servicio '%s'.\n" @@ -3935,91 +4261,51 @@ msgstr "Falló al inicializar el servicio '%s'.\n" msgid "Could not connect to `%s' service.\n" msgstr "Imposible conectar con gnunetd.\n" -#: src/peerinfo-tool/gnunet-peerinfo.c:581 -#, fuzzy -msgid "Failed to parse HELLO message: missing expiration time\n" -msgstr "Imposible guardar la configuración" - -#: src/peerinfo-tool/gnunet-peerinfo.c:589 -#, fuzzy -msgid "Failed to parse HELLO message: invalid expiration time\n" -msgstr "Imposible guardar la configuración" - -#: src/peerinfo-tool/gnunet-peerinfo.c:598 -#, fuzzy -msgid "Failed to parse HELLO message: malformed\n" -msgstr "Falló al pasar los datos de la interfaz de '%s' de %s:%d.\n" - -#: src/peerinfo-tool/gnunet-peerinfo.c:608 -#, fuzzy -msgid "Failed to parse HELLO message: missing transport plugin\n" -msgstr "Imposible inicializar la aplicación '%s'\n" - -#: src/peerinfo-tool/gnunet-peerinfo.c:625 -#, c-format -msgid "Plugin `%s' not found\n" -msgstr "" - -#: src/peerinfo-tool/gnunet-peerinfo.c:634 -#, c-format -msgid "Plugin `%s' does not support URIs yet\n" -msgstr "" - -#: src/peerinfo-tool/gnunet-peerinfo.c:653 -#, fuzzy, c-format -msgid "Failed to parse `%s' as an address for plugin `%s'\n" -msgstr "Fallo al conectar a gnunetd.\n" - -#: src/peerinfo-tool/gnunet-peerinfo.c:685 +#: src/peerinfo-tool/gnunet-peerinfo.c:419 #, fuzzy, c-format msgid "Failure adding HELLO: %s\n" msgstr "Fallo en %s:%d.\n" -#: src/peerinfo-tool/gnunet-peerinfo.c:833 +#: src/peerinfo-tool/gnunet-peerinfo.c:557 #, fuzzy, c-format msgid "Could not find option `%s:%s' in configuration.\n" msgstr "¡Imposible encontrar el par '%s' en la tabla de enrutado!\n" -#: src/peerinfo-tool/gnunet-peerinfo.c:840 +#: src/peerinfo-tool/gnunet-peerinfo.c:563 #, fuzzy, c-format msgid "Loading hostkey from `%s' failed.\n" msgstr "Analizando saludo de '%s' se produjo un fallo.\n" -#: src/peerinfo-tool/gnunet-peerinfo.c:875 -#, fuzzy, c-format -msgid "Invalid URI `%s'\n" -msgstr "Argumento no válido: '%s'\n" - -#: src/peerinfo-tool/gnunet-peerinfo.c:899 +#: src/peerinfo-tool/gnunet-peerinfo.c:622 #, c-format msgid "I am peer `%s'.\n" msgstr "Yo soy el par '%s'.\n" -#: src/peerinfo-tool/gnunet-peerinfo.c:936 +#: src/peerinfo-tool/gnunet-peerinfo.c:648 msgid "don't resolve host names" msgstr "" -#: src/peerinfo-tool/gnunet-peerinfo.c:939 +#: src/peerinfo-tool/gnunet-peerinfo.c:651 msgid "output only the identity strings" msgstr "" -#: src/peerinfo-tool/gnunet-peerinfo.c:942 +#: src/peerinfo-tool/gnunet-peerinfo.c:654 msgid "output our own identity only" msgstr "" -#: src/peerinfo-tool/gnunet-peerinfo.c:945 +#: src/peerinfo-tool/gnunet-peerinfo.c:657 msgid "list all known peers" msgstr "" -#: src/peerinfo-tool/gnunet-peerinfo.c:948 +#: src/peerinfo-tool/gnunet-peerinfo.c:660 msgid "also output HELLO uri(s)" msgstr "" -#: src/peerinfo-tool/gnunet-peerinfo.c:951 +#: src/peerinfo-tool/gnunet-peerinfo.c:663 msgid "add given HELLO uri to the database" msgstr "" -#: src/peerinfo-tool/gnunet-peerinfo.c:957 +#: src/peerinfo-tool/gnunet-peerinfo.c:674 #, fuzzy msgid "Print information about peers." msgstr "Imprime información de los pares de GNUnet." @@ -4115,464 +4401,556 @@ msgstr "" msgid "Failed to connect to %s service. Exiting.\n" msgstr "Fallo al conectar a gnunetd.\n" -#: src/pt/gnunet-daemon-pt.c:973 +#: src/pt/gnunet-daemon-pt.c:976 msgid "Daemon to run to perform IP protocol translation to GNUnet" msgstr "" -#: src/statistics/gnunet-service-statistics.c:271 +#: src/regex/gnunet-daemon-regexprofiler.c:293 #, fuzzy, c-format -msgid "Loading %llu bytes of statistics from `%s'\n" -msgstr "Descarga los ficheros de GNUnet" +msgid "Regexprofiler could not access hostkey: %s. Exiting.\n" +msgstr "Imposible acceder a la información del espacio.\n" -#: src/statistics/gnunet-service-statistics.c:330 -#, fuzzy, c-format -msgid "Wrote %llu bytes of statistics to `%s'\n" -msgstr "Descarga los ficheros de GNUnet" +#: src/regex/gnunet-daemon-regexprofiler.c:452 +msgid "Daemon to announce regular expressions for the peer using mesh." +msgstr "" -#: src/statistics/gnunet-statistics.c:122 -#, fuzzy -msgid "Failed to obtain statistics.\n" -msgstr "Fallo en las estadísticas del tráfico.\n" +#: src/regex/gnunet-regex-profiler.c:1147 +msgid "An operation has failed while starting peers\n" +msgstr "" -#: src/statistics/gnunet-statistics.c:199 -#, c-format -msgid "No subsystem or name given\n" +#: src/regex/gnunet-regex-profiler.c:1193 +#, fuzzy, c-format +msgid "Creating a peer failed. Error: %s\n" +msgstr "" +"\n" +"Error subiendo el fichero %s\n" + +#: src/regex/gnunet-regex-profiler.c:1320 +msgid "An operation has failed while starting slaves\n" msgstr "" -#: src/statistics/gnunet-statistics.c:207 +#: src/regex/gnunet-regex-profiler.c:1342 #, fuzzy, c-format -msgid "Failed to initialize watch routine\n" -msgstr "Imposible inicializar SQLite.\n" +msgid "No files found in `%s'\n" +msgstr "¡Imposible descargar adecuadamente el servicio '%s'!\n" -#: src/statistics/gnunet-statistics.c:227 -msgid "limit output to statistics for the given NAME" +#: src/regex/gnunet-regex-profiler.c:1397 +msgid "An operation has failed while linking\n" msgstr "" -#: src/statistics/gnunet-statistics.c:230 -msgid "make the value being set persistent" +#: src/regex/gnunet-regex-profiler.c:1508 +#: src/testbed/testbed_api_testbed.c:805 +#, c-format +msgid "Host registration failed for a host. Error: %s\n" msgstr "" -#: src/statistics/gnunet-statistics.c:233 -msgid "limit output to the given SUBSYSTEM" +#: src/regex/gnunet-regex-profiler.c:1589 +msgid "Unable to connect to master controller -- Check config\n" msgstr "" -#: src/statistics/gnunet-statistics.c:236 -msgid "just print the statistics value" +#: src/regex/gnunet-regex-profiler.c:1691 +#: src/testbed/testbed_api_testbed.c:970 +#, c-format +msgid "Host %s cannot start testbed\n" msgstr "" -#: src/statistics/gnunet-statistics.c:239 -msgid "watch value continously" +#: src/regex/gnunet-regex-profiler.c:1694 +#: src/testbed/testbed_api_testbed.c:974 +msgid "Testbed cannot be started on localhost\n" msgstr "" -#: src/statistics/gnunet-statistics.c:246 -msgid "Print statistics about GNUnet operations." -msgstr "Imprime estadísticas acerca de las operaciones de GNUnet." - -#: src/statistics/statistics_api.c:456 -#, fuzzy -msgid "Could not save some persistent statistics\n" -msgstr "Imposible crear el espacio '%s' (¿existe?).\n" +#: src/regex/gnunet-regex-profiler.c:1734 +#, c-format +msgid "No hosts-file specified on command line. Exiting.\n" +msgstr "" -#: src/statistics/statistics_api.c:999 -msgid "" -"Failed to receive acknowledgement from statistics service, some statistics " -"might have been lost!\n" +#: src/regex/gnunet-regex-profiler.c:1739 +#: src/regex/gnunet-regex-simulation-profiler.c:622 +#, c-format +msgid "No policy directory specified on command line. Exiting.\n" msgstr "" -#: src/testing/gnunet-testing.c:157 -#, fuzzy -msgid "Could not read hostkeys file, specify hostkey file with -H!\n" -msgstr "Imposible inicializar la aplicación '%s'\n" +#: src/regex/gnunet-regex-profiler.c:1745 +#: src/testbed/testbed_api_testbed.c:1065 +#, c-format +msgid "No hosts loaded. Need at least one host\n" +msgstr "" -#: src/testing/gnunet-testing.c:159 +#: src/regex/gnunet-regex-profiler.c:1748 #, c-format -msgid "Specified hostkey file `%s' not found!\n" +msgid "Checking whether given hosts can start testbed. Please wait\n" msgstr "" -#: src/testing/gnunet-testing.c:273 -#, fuzzy -msgid "create unique configuration files" -msgstr "Imposible guardar el fichero de configuración '%s':" +#: src/regex/gnunet-regex-profiler.c:1769 +#, fuzzy, c-format +msgid "Exiting\n" +msgstr "" +"\n" +"Saliendo.\n" + +#: src/regex/gnunet-regex-profiler.c:1775 +#, fuzzy, c-format +msgid "No configuration file given. Exiting\n" +msgstr "usa el fichero de configuración FILENAME" + +#: src/regex/gnunet-regex-profiler.c:1784 +#, fuzzy, c-format +msgid "Configuration option (regex_prefix) missing. Exiting\n" +msgstr "Fichero de configuración '%s' creado.\n" -#: src/testing/gnunet-testing.c:275 -msgid "create hostkey files from pre-computed hostkey list" +#: src/regex/gnunet-regex-profiler.c:1802 +#: src/regex/gnunet-regex-simulation-profiler.c:629 +#, c-format +msgid "Specified policies directory does not exist. Exiting.\n" msgstr "" -#: src/testing/gnunet-testing.c:277 -msgid "host key file" +#: src/regex/gnunet-regex-profiler.c:1809 +#, c-format +msgid "No search strings file given. Exiting.\n" msgstr "" -#: src/testing/gnunet-testing.c:279 -#, fuzzy -msgid "number of unique configuration files or hostkeys to create" -msgstr "Imposible guardar el fichero de configuración '%s':" +#: src/regex/gnunet-regex-profiler.c:1817 +#, c-format +msgid "" +"Error loading search strings. Given file does not contain enough strings. " +"Exiting.\n" +msgstr "" -#: src/testing/gnunet-testing.c:281 +#: src/regex/gnunet-regex-profiler.c:1823 +#, fuzzy, c-format +msgid "Error loading search strings. Exiting.\n" +msgstr "Error abandonando DHT.\n" + +#: src/regex/gnunet-regex-profiler.c:1850 #, fuzzy -msgid "configuration template" -msgstr "Configuración de GNUnet" +msgid "name of the file for writing statistics" +msgstr "Fallo en las estadísticas del tráfico.\n" -#: src/testing/gnunet-testing.c:287 -msgid "Command line tool to access the testing library" +#: src/regex/gnunet-regex-profiler.c:1853 +msgid "create COUNT number of random links between peers" msgstr "" -#: src/testing/helper.c:56 -#, fuzzy -msgid "Peer is lacking HOSTKEY configuration setting.\n" -msgstr "Configuración de GNUnet" +#: src/regex/gnunet-regex-profiler.c:1856 +msgid "wait TIMEOUT before considering a string match as failed" +msgstr "" -#: src/testing/helper.c:64 -#, fuzzy -msgid "Could not access hostkey.\n" -msgstr "Imposible pasar el fichero de configuración '%s'.\n" +#: src/regex/gnunet-regex-profiler.c:1859 +msgid "wait DELAY before starting string search" +msgstr "" -#: src/testing/testing.c:200 -msgid "`scp' does not seem to terminate (timeout copying config).\n" +#: src/regex/gnunet-regex-profiler.c:1862 +msgid "number of search strings to read from search strings file" msgstr "" -#: src/testing/testing.c:214 src/testing/testing.c:798 -#, fuzzy -msgid "`scp' did not complete cleanly.\n" -msgstr "'%s' no esta conectado a ningún par.\n" +#: src/regex/gnunet-regex-profiler.c:1865 +#: src/regex/gnunet-regex-simulation-profiler.c:692 +msgid "maximum path compression length" +msgstr "" -#: src/testing/testing.c:237 -#, fuzzy -msgid "Failed to create pipe for `gnunet-peerinfo' process.\n" -msgstr "Falló al comenzar la recolección.\n" +#: src/regex/gnunet-regex-profiler.c:1868 +msgid "" +"if this option is set, only one peer is responsible for searching all strings" +msgstr "" -#: src/testing/testing.c:238 -#, fuzzy -msgid "Failed to create pipe for `ssh' process.\n" -msgstr "Error en el formato del fichero (¿no es un directorio de GNUnet?)\n" +#: src/regex/gnunet-regex-profiler.c:1881 +msgid "Profiler for regex" +msgstr "" -#: src/testing/testing.c:286 -#, fuzzy, c-format -msgid "Could not start `%s' process to create hostkey.\n" -msgstr "Imposible mandar el mensaje a gnunetd\n" +#: src/regex/gnunet-regex-simulation-profiler.c:689 +msgid "name of the table to write DFAs" +msgstr "" -#: src/testing/testing.c:293 -#, fuzzy -msgid "Failed to start `gnunet-peerinfo' process.\n" -msgstr "Falló al comenzar la recolección.\n" +#: src/regex/gnunet-regex-simulation-profiler.c:705 +msgid "Profiler for regex library" +msgstr "" -#: src/testing/testing.c:294 src/testing/testing.c:471 -#, fuzzy -msgid "Failed to start `ssh' process.\n" -msgstr "Falló al comenzar la recolección.\n" +#: src/statistics/gnunet-service-statistics.c:271 +#, fuzzy, c-format +msgid "Loading %llu bytes of statistics from `%s'\n" +msgstr "Descarga los ficheros de GNUnet" -#: src/testing/testing.c:354 +#: src/statistics/gnunet-service-statistics.c:330 #, fuzzy, c-format -msgid "Error reading from gnunet-peerinfo: %s\n" -msgstr "Se produjo un error leyendo información de gnunetd.\n" +msgid "Wrote %llu bytes of statistics to `%s'\n" +msgstr "Descarga los ficheros de GNUnet" -#: src/testing/testing.c:358 +#: src/statistics/gnunet-statistics.c:141 #, fuzzy -msgid "Malformed output from gnunet-peerinfo!\n" -msgstr "Se produjo un error leyendo información de gnunetd.\n" +msgid "Failed to obtain statistics.\n" +msgstr "Fallo en las estadísticas del tráfico.\n" -#: src/testing/testing.c:368 -#, fuzzy -msgid "Failed to get hostkey!\n" +#: src/statistics/gnunet-statistics.c:143 +#, fuzzy, c-format +msgid "Failed to obtain statistics from host `%s:%llu'\n" msgstr "Fallo en las estadísticas del tráfico.\n" -#: src/testing/testing.c:400 -msgid "`Failed while waiting for topology setup!\n" +#: src/statistics/gnunet-statistics.c:181 +#, fuzzy, c-format +msgid "Trying to connect to remote host, but service `%s' is not running\n" +msgstr "Imposible conectar con gnunetd.\n" + +#: src/statistics/gnunet-statistics.c:190 +#, fuzzy, c-format +msgid "A port is required to connect to host `%s'\n" +msgstr "Fallo al conectar a gnunetd.\n" + +#: src/statistics/gnunet-statistics.c:196 +#, c-format +msgid "A port has to be between 1 and 65535 to connect to host `%s'\n" +msgstr "" + +#: src/statistics/gnunet-statistics.c:210 +msgid "Missing argument: subsystem \n" +msgstr "" + +#: src/statistics/gnunet-statistics.c:216 +msgid "Missing argument: name\n" +msgstr "" + +#: src/statistics/gnunet-statistics.c:247 +#, c-format +msgid "No subsystem or name given\n" msgstr "" -#: src/testing/testing.c:463 +#: src/statistics/gnunet-statistics.c:255 #, fuzzy, c-format -msgid "Could not start `%s' process to start GNUnet.\n" -msgstr "Imposible crear el espacio '%s' (¿existe?).\n" +msgid "Failed to initialize watch routine\n" +msgstr "Imposible inicializar SQLite.\n" -#: src/testing/testing.c:470 -#, fuzzy -msgid "Failed to start `gnunet-arm' process.\n" -msgstr "Fallo al conectar a gnunetd.\n" +#: src/statistics/gnunet-statistics.c:310 +msgid "limit output to statistics for the given NAME" +msgstr "" + +#: src/statistics/gnunet-statistics.c:313 +msgid "make the value being set persistent" +msgstr "" -#: src/testing/testing.c:493 src/testing/testing.c:600 -msgid "`gnunet-arm' does not seem to terminate.\n" +#: src/statistics/gnunet-statistics.c:316 +msgid "limit output to the given SUBSYSTEM" msgstr "" -#: src/testing/testing.c:494 src/testing/testing.c:601 -#: src/testing/testing.c:621 -msgid "`ssh' does not seem to terminate.\n" +#: src/statistics/gnunet-statistics.c:319 +msgid "just print the statistics value" msgstr "" -#: src/testing/testing.c:570 -msgid "Unable to get HELLO for peer!\n" +#: src/statistics/gnunet-statistics.c:322 +msgid "watch value continuously" msgstr "" -#: src/testing/testing.c:620 -msgid "`gnunet-arm' terminated with non-zero exit status (or timed out)!\n" +#: src/statistics/gnunet-statistics.c:325 +msgid "connect to remote host" msgstr "" -#: src/testing/testing.c:643 src/testing/testing.c:675 -msgid "either `gnunet-arm' or `ssh' does not seem to terminate.\n" +#: src/statistics/gnunet-statistics.c:328 +msgid "port for remote host" msgstr "" -#: src/testing/testing.c:658 src/testing/testing.c:713 +#: src/statistics/gnunet-statistics.c:340 +msgid "Print statistics about GNUnet operations." +msgstr "Imprime estadísticas acerca de las operaciones de GNUnet." + +#: src/statistics/statistics_api.c:511 #, fuzzy -msgid "shutdown (either `gnunet-arm' or `ssh') did not complete cleanly.\n" -msgstr "'%s' no esta conectado a ningún par.\n" +msgid "Could not save some persistent statistics\n" +msgstr "Imposible crear el espacio '%s' (¿existe?).\n" + +#: src/statistics/statistics_api.c:1056 +msgid "" +"Failed to receive acknowledgement from statistics service, some statistics " +"might have been lost!\n" +msgstr "" + +#: src/sysmon/gnunet-service-sysmon.c:546 +#, c-format +msgid "Could not parse execution interval for `%s', set to default 60 sec.\n" +msgstr "" + +#: src/testbed/gnunet-testbed-profiler.c:231 +#, c-format +msgid "No hosts-file specified on command line\n" +msgstr "" + +#: src/testbed/gnunet-testbed-profiler.c:261 +msgid "create COUNT number of peers" +msgstr "" + +#: src/testbed/gnunet-testbed-profiler.c:264 +msgid "tolerate COUNT number of continious timeout failures" +msgstr "" -#: src/testing/testing.c:786 -msgid "`scp' does not seem to terminate.\n" +#: src/testbed/gnunet-testbed-profiler.c:276 +msgid "Profiler for testbed" msgstr "" -#: src/testing/testing.c:948 +#: src/testbed/ll_master.c:57 #, fuzzy, c-format -msgid "Starting service %s for peer `%4s'\n" -msgstr "Iniciada colección '%s'.\n" +msgid "Job command file not given. Exiting\n" +msgstr "usa el fichero de configuración FILENAME" -#: src/testing/testing.c:1207 src/testing/testing_group.c:6154 +#: src/testbed/testbed_api.c:499 #, fuzzy, c-format -msgid "Could not start `%s' process to copy configuration directory.\n" -msgstr "Imposible acceder a la información del espacio.\n" +msgid "Adding host %u failed with error: %s\n" +msgstr "'%s' falló con el código de error %d: %s" -#: src/testing/testing.c:1292 src/testing/testing.c:1359 +#: src/testbed/testbed_api_hosts.c:306 #, fuzzy, c-format -msgid "Terminating peer `%4s'\n" -msgstr "Permiso denegado para '%s' en %s:%d.\n" +msgid "Hosts file %s not found\n" +msgstr "'%s' falló: ¡tabla no encontrada!\n" -#: src/testing/testing.c:1448 +#: src/testbed/testbed_api_hosts.c:314 #, fuzzy, c-format -msgid "Setting d->dead on peer `%4s'\n" -msgstr "Iniciada colección '%s'.\n" +msgid "Hosts file %s has no data\n" +msgstr "La clave de sesión del par '%s' no pudo ser verificada.\n" + +#: src/testbed/testbed_api_hosts.c:321 +#, fuzzy, c-format +msgid "Hosts file %s cannot be read\n" +msgstr "La clave de sesión del par '%s' no pudo ser verificada.\n" -#: src/testing/testing.c:1601 -msgid "Peer not yet running, can not change configuration at this point." +#: src/testbed/testbed_api_testbed.c:623 +msgid "Linking controllers failed. Exiting" msgstr "" -#: src/testing/testing.c:1609 +#: src/testbed/testbed_api_testbed.c:1009 #, fuzzy -msgid "Failed to write new configuration to disk." -msgstr "Imposible guardar la configuración" +msgid "Cannot start the master controller" +msgstr "Arranca el cliente de chat de GNUnet" + +#: src/testbed/testbed_api_testbed.c:1089 +msgid "Specified topology must be supported by testbed" +msgstr "" -#: src/testing/testing.c:1636 +#: src/testbed/testbed_api_topology.c:668 #, fuzzy, c-format -msgid "Could not start `%s' process to copy configuration file.\n" -msgstr "¡Imposible encontrar el par '%s' en la tabla de enrutado!\n" +msgid "Topology file %s not found\n" +msgstr "'%s' falló: ¡tabla no encontrada!\n" -#: src/testing/testing.c:1639 -#, fuzzy -msgid "Failed to copy new configuration to remote machine." -msgstr "Imposible guardar la configuración" +#: src/testbed/testbed_api_topology.c:674 +#, fuzzy, c-format +msgid "Topology file %s has no data\n" +msgstr "La clave de sesión del par '%s' no pudo ser verificada.\n" -#: src/testing/testing.c:1794 -#, fuzzy -msgid "Peers failed to connect" -msgstr "Fallo al conectar a gnunetd.\n" +#: src/testbed/testbed_api_topology.c:681 +#, fuzzy, c-format +msgid "Topology file %s cannot be read\n" +msgstr "La clave de sesión del par '%s' no pudo ser verificada.\n" -#: src/testing/testing.c:1922 -#, fuzzy -msgid "Failed to connect to core service of first peer!\n" -msgstr "Fallo al conectar a gnunetd.\n" +#: src/testbed/testbed_api_topology.c:704 +#, fuzzy, c-format +msgid "Failed to read peer index from toology file: %s" +msgstr "Imposible pasar el fichero de configuración '%s'.\n" -#: src/testing/testing.c:2145 -msgid "Peers are not fully running yet, can not connect!\n" +#: src/testbed/testbed_api_topology.c:713 +#: src/testbed/testbed_api_topology.c:737 +#, c-format +msgid "Value in given topology file: %s out of range\n" msgstr "" -#: src/testing/testing_group.c:1895 src/testing/testing_group.c:1907 -#: src/testing/testing_group.c:2008 src/testing/testing_group.c:2065 -#: src/testing/testing_group.c:2152 src/testing/testing_group.c:2172 -#: src/testing/testing_group.c:2302 src/testing/testing_peergroup.c:950 +#: src/testbed/testbed_api_topology.c:719 +#: src/testbed/testbed_api_topology.c:743 #, fuzzy, c-format -msgid "Invalid value `%s' for option `%s' in section `%s': expected float\n" +msgid "Failed to read peer index from topology file: %s" +msgstr "Imposible pasar el fichero de configuración '%s'.\n" + +#: src/testbed/testbed_api_topology.c:725 +#: src/testbed/testbed_api_topology.c:749 +msgid "Topology file needs more peers than given ones\n" msgstr "" -"El fichero de configuración debe especificar el directorio para almacenar " -"los datos FS en la sección '%s' bajo '%s'.\n" -#: src/testing/testing_group.c:2160 -#, c-format -msgid "" -"Invalid value `%s' for option `%s' in section `%s': got %f, needed value " -"greater than 0\n" +#: src/testbed/testbed_api_topology.c:764 +#, fuzzy, c-format +msgid "Ignoring to connect peer %u to peer %u\n" +msgstr "Imposible conectar a %u.%u.%u.%u:%u: %s\n" + +#: src/testing/gnunet-testing.c:132 +#, fuzzy, c-format +msgid "Could not extract hostkey %u (offset too large?)\n" +msgstr "Imposible inicializar la aplicación '%s'\n" + +#: src/testing/gnunet-testing.c:203 +#, fuzzy +msgid "create unique configuration files" +msgstr "Imposible guardar el fichero de configuración '%s':" + +#: src/testing/gnunet-testing.c:205 +msgid "extract hostkey file from pre-computed hostkey list" msgstr "" -#: src/testing/testing_group.c:2877 src/testing/testing_group.c:3063 -#, c-format +#: src/testing/gnunet-testing.c:207 +#, fuzzy msgid "" -"No `%s' specified in peer configuration in section `%s', cannot copy friends " -"file!\n" -msgstr "" +"number of unique configuration files to create, or number of the hostkey to " +"extract" +msgstr "Imposible guardar el fichero de configuración '%s':" + +#: src/testing/gnunet-testing.c:209 +#, fuzzy +msgid "configuration template" +msgstr "Configuración de GNUnet" -#: src/testing/testing_group.c:3957 -msgid "Creating no allowed topology (all peers can connect at core level)\n" +#: src/testing/gnunet-testing.c:218 +msgid "Command line tool to access the testing library" msgstr "" -#: src/testing/testing_group.c:5226 -msgid "Unknown topology specification, can't connect peers!\n" +#: src/testing/gnunet-testing-run-service.c:129 +#, c-format +msgid "Unknown command, use 'q' to quit or 'r' to restart peer\n" msgstr "" -#: src/testing/testing_group.c:5944 src/transport/transport-testing.c:636 +#: src/testing/gnunet-testing-run-service.c:186 #, fuzzy -msgid "Could not read hostkeys file!\n" -msgstr "Imposible inicializar la aplicación '%s'\n" +msgid "name of the template configuration file to use (optional)" +msgstr "Esta es la herramienta de configuración de GNUnet." -#: src/testing/testing_group.c:6011 -#, fuzzy, c-format -msgid "Could not create configuration for peer number %u on `%s'!\n" -msgstr "Imposible acceder a la información del espacio.\n" - -#: src/testing/testing_new.c:169 -msgid "tmppath cannot be NULL\n" +#: src/testing/gnunet-testing-run-service.c:189 +msgid "name of the service to run" msgstr "" -#: src/testing/testing_new.c:356 +#: src/testing/testing.c:211 #, c-format msgid "Hostkeys file not found: %s\n" msgstr "" -#: src/testing/testing_new.c:365 -#, fuzzy, c-format -msgid "Could not open hostkeys file: %s\n" -msgstr "Imposible inicializar la aplicación '%s'\n" - -#: src/testing/testing_new.c:380 +#: src/testing/testing.c:227 #, c-format msgid "Incorrect hostkey file format: %s\n" msgstr "" -#: src/testing/testing_new.c:437 +#: src/testing/testing.c:541 #, fuzzy, c-format msgid "Key number %u does not exist\n" msgstr "número de mensajes a usar por iteración" -#: src/testing/testing_new.c:446 +#: src/testing/testing.c:551 #, fuzzy, c-format msgid "Error while decoding key %u\n" msgstr "Error descargando: %s\n" -#: src/testing/testing_new.c:680 +#: src/testing/testing.c:865 #, fuzzy msgid "Failed to create configuration for peer (not enough free ports?)\n" msgstr "Imposible acceder a la información del espacio.\n" -#: src/testing/testing_new.c:691 +#: src/testing/testing.c:876 #, c-format msgid "" "You attempted to create a testbed with more than %u hosts. Please " "precompute more hostkeys first.\n" msgstr "" -#: src/testing/testing_new.c:704 +#: src/testing/testing.c:890 #, fuzzy, c-format msgid "Failed to initialize hostkey for peer %u\n" msgstr "Imposible inicializar SQLite.\n" -#: src/testing/testing_new.c:734 +#: src/testing/testing.c:923 #, fuzzy, c-format msgid "Failed to write hostkey file for peer %u: %s\n" msgstr "Error en el formato del fichero (¿no es un directorio de GNUnet?)\n" -#: src/testing/testing_new.c:751 +#: src/testing/testing.c:941 #, fuzzy, c-format msgid "Failed to write configuration file `%s' for peer %u: %s\n" msgstr "Imposible guardar el fichero de configuración '%s':" -#: src/testing/testing_new.c:791 +#: src/testing/testing.c:1014 #, fuzzy, c-format msgid "Failed to start `%s': %s\n" msgstr "Fallo al conectar a gnunetd.\n" -#: src/testing/testing_new.c:959 +#: src/testing/testing.c:1219 #, fuzzy, c-format msgid "Failed to load configuration from %s\n" msgstr "Imposible guardar el fichero de configuración '%s':" -#: src/topology/gnunet-daemon-topology.c:259 +#: src/topology/gnunet-daemon-topology.c:254 msgid "# peers blacklisted" msgstr "" -#: src/topology/gnunet-daemon-topology.c:392 +#: src/topology/gnunet-daemon-topology.c:387 #, fuzzy msgid "# connect requests issued to transport" msgstr "# mensajes PONG encriptados recibidos" -#: src/topology/gnunet-daemon-topology.c:730 -#: src/topology/gnunet-daemon-topology.c:815 +#: src/topology/gnunet-daemon-topology.c:725 +#: src/topology/gnunet-daemon-topology.c:810 #, fuzzy msgid "# friends connected" msgstr "# de pares conectados" -#: src/topology/gnunet-daemon-topology.c:996 +#: src/topology/gnunet-daemon-topology.c:991 msgid "Failed to connect to core service, can not manage topology!\n" msgstr "" -#: src/topology/gnunet-daemon-topology.c:1026 -#, c-format -msgid "Option `%s' in section `%s' not specified!\n" -msgstr "" - -#: src/topology/gnunet-daemon-topology.c:1039 +#: src/topology/gnunet-daemon-topology.c:1034 #, fuzzy, c-format msgid "Could not read friends list `%s'\n" msgstr "Imposible inicializar la aplicación '%s'\n" -#: src/topology/gnunet-daemon-topology.c:1045 +#: src/topology/gnunet-daemon-topology.c:1040 #, fuzzy, c-format msgid "Friends file `%s' is empty.\n" msgstr "El formato del fichero '%s' no es válido.\n" -#: src/topology/gnunet-daemon-topology.c:1054 +#: src/topology/gnunet-daemon-topology.c:1049 #, fuzzy, c-format msgid "Failed to read friends list from `%s': out of memory\n" msgstr "Imposible inicializar la aplicación '%s'\n" -#: src/topology/gnunet-daemon-topology.c:1062 +#: src/topology/gnunet-daemon-topology.c:1057 #, c-format msgid "Failed to read friends list from `%s'\n" msgstr "" -#: src/topology/gnunet-daemon-topology.c:1082 +#: src/topology/gnunet-daemon-topology.c:1077 #, c-format msgid "" "Syntax error in topology specification at offset %llu, skipping bytes.\n" msgstr "" -#: src/topology/gnunet-daemon-topology.c:1095 +#: src/topology/gnunet-daemon-topology.c:1090 #, c-format msgid "" "Syntax error in topology specification at offset %llu, skipping bytes `%s'.\n" msgstr "" -#: src/topology/gnunet-daemon-topology.c:1105 +#: src/topology/gnunet-daemon-topology.c:1100 #, fuzzy, c-format msgid "Found friend `%s' in configuration\n" msgstr " gconfig\tConfiguración GTK\n" -#: src/topology/gnunet-daemon-topology.c:1111 +#: src/topology/gnunet-daemon-topology.c:1106 #, c-format msgid "Found myself `%s' in friend list (useless, ignored)\n" msgstr "" -#: src/topology/gnunet-daemon-topology.c:1121 +#: src/topology/gnunet-daemon-topology.c:1116 #, fuzzy msgid "# friends in configuration" msgstr " gconfig\tConfiguración GTK\n" -#: src/topology/gnunet-daemon-topology.c:1127 +#: src/topology/gnunet-daemon-topology.c:1122 msgid "" "Fewer friends specified than required by minimum friend count. Will only " "connect to friends.\n" msgstr "" -#: src/topology/gnunet-daemon-topology.c:1134 +#: src/topology/gnunet-daemon-topology.c:1129 msgid "" "More friendly connections required than target total number of connections.\n" msgstr "" -#: src/topology/gnunet-daemon-topology.c:1169 +#: src/topology/gnunet-daemon-topology.c:1164 #, fuzzy msgid "# HELLO messages received" msgstr "# mensajes PONG encriptados recibidos" -#: src/topology/gnunet-daemon-topology.c:1224 +#: src/topology/gnunet-daemon-topology.c:1219 #, fuzzy msgid "# HELLO messages gossipped" msgstr "# mensajes salientes omitidos" -#: src/topology/gnunet-daemon-topology.c:1363 +#: src/topology/gnunet-daemon-topology.c:1358 msgid "GNUnet topology control (maintaining P2P mesh and F2F constraints)" msgstr "" @@ -4581,11 +4959,6 @@ msgstr "" msgid "Could not read blacklist file `%s'\n" msgstr "Imposible inicializar la aplicación '%s'\n" -#: src/transport/gnunet-service-transport_blacklist.c:252 -#, c-format -msgid "Blacklist file `%s' is empty.\n" -msgstr "" - #: src/transport/gnunet-service-transport_blacklist.c:263 #, fuzzy, c-format msgid "Failed to read blacklist from `%s'\n" @@ -4616,171 +4989,177 @@ msgid "Found myself `%s' in blacklist (useless, ignored)\n" msgstr "" #: src/transport/gnunet-service-transport_blacklist.c:514 -#: src/transport/gnunet-service-transport_blacklist.c:747 +#: src/transport/gnunet-service-transport_blacklist.c:752 msgid "# disconnects due to blacklist" msgstr "" -#: src/transport/gnunet-service-transport.c:163 +#: src/transport/gnunet-service-transport.c:183 #, fuzzy msgid "# bytes payload discarded due to not connected peer " msgstr "# Anuncios de los pares recibidos" -#: src/transport/gnunet-service-transport.c:237 +#: src/transport/gnunet-service-transport.c:258 #, fuzzy msgid "# bytes total received" msgstr "# bytes en la base de datos" -#: src/transport/gnunet-service-transport.c:284 +#: src/transport/gnunet-service-transport.c:305 #, fuzzy msgid "# bytes payload received" msgstr "# bytes desencriptados" -#: src/transport/gnunet-service-transport.c:582 -msgid "Transport service is lacking key configuration settings. Exiting.\n" -msgstr "" +#: src/transport/gnunet-service-transport.c:614 +#, fuzzy, c-format +msgid "Transport service could not access hostkey: %s. Exiting.\n" +msgstr "Imposible acceder a la información del espacio.\n" + +#: src/transport/gnunet-service-transport.c:625 +#, fuzzy +msgid "Could not access STATISTICS service. Exiting.\n" +msgstr "Imposible acceder a la información del espacio.\n" -#: src/transport/gnunet-service-transport.c:591 -msgid "Transport service could not access hostkey. Exiting.\n" +#: src/transport/gnunet-service-transport.c:720 +msgid "Transport service is lacking key configuration settings. Exiting.\n" msgstr "" -#: src/transport/gnunet-service-transport_clients.c:352 +#: src/transport/gnunet-service-transport_clients.c:389 #, c-format msgid "Dropping message of type %u and size %u, have %u/%u messages pending\n" msgstr "" -#: src/transport/gnunet-service-transport_clients.c:357 +#: src/transport/gnunet-service-transport_clients.c:394 #, fuzzy msgid "# messages dropped due to slow client" msgstr "# Anuncios de los pares recibidos" -#: src/transport/gnunet-service-transport_clients.c:503 +#: src/transport/gnunet-service-transport_clients.c:546 #, c-format msgid "Rejecting control connection from peer `%s', which is not me!\n" msgstr "" -#: src/transport/gnunet-service-transport_clients.c:631 +#: src/transport/gnunet-service-transport_clients.c:687 msgid "# bytes payload dropped (other peer was not connected)" msgstr "" -#: src/transport/gnunet-service-transport_clients.c:682 +#: src/transport/gnunet-service-transport_clients.c:738 #, fuzzy msgid "# REQUEST CONNECT messages received" msgstr "# mensajes PONG encriptados recibidos" -#: src/transport/gnunet-service-transport_hello.c:172 +#: src/transport/gnunet-service-transport_hello.c:175 msgid "# refreshed my HELLO" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:1032 +#: src/transport/gnunet-service-transport_neighbours.c:1227 #, fuzzy msgid "# DISCONNECT messages sent" msgstr "# mensajes PONG encriptados recibidos" -#: src/transport/gnunet-service-transport_neighbours.c:1148 -#: src/transport/gnunet-service-transport_neighbours.c:1482 +#: src/transport/gnunet-service-transport_neighbours.c:1357 +#: src/transport/gnunet-service-transport_neighbours.c:1694 #, fuzzy msgid "# bytes in message queue for other peers" msgstr "# bytes de mensajes salientes omitidos" -#: src/transport/gnunet-service-transport_neighbours.c:1153 +#: src/transport/gnunet-service-transport_neighbours.c:1362 #, fuzzy msgid "# messages transmitted to other peers" msgstr "# bytes recibidos por TCP" -#: src/transport/gnunet-service-transport_neighbours.c:1158 +#: src/transport/gnunet-service-transport_neighbours.c:1367 #, fuzzy msgid "# transmission failures for messages to other peers" msgstr "# bytes de mensajes salientes omitidos" -#: src/transport/gnunet-service-transport_neighbours.c:1215 +#: src/transport/gnunet-service-transport_neighbours.c:1424 msgid "# messages timed out while in transport queue" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:1254 +#: src/transport/gnunet-service-transport_neighbours.c:1466 #, fuzzy msgid "# keepalives sent" msgstr "# claves de la sesión mandadas" -#: src/transport/gnunet-service-transport_neighbours.c:1278 +#: src/transport/gnunet-service-transport_neighbours.c:1490 #, fuzzy msgid "# KEEPALIVE messages discarded (peer unknown)" msgstr "# mensajes defragmentados" -#: src/transport/gnunet-service-transport_neighbours.c:1286 +#: src/transport/gnunet-service-transport_neighbours.c:1498 #, fuzzy msgid "# KEEPALIVE messages discarded (no session)" msgstr "# mensajes defragmentados" -#: src/transport/gnunet-service-transport_neighbours.c:1323 +#: src/transport/gnunet-service-transport_neighbours.c:1535 #, fuzzy msgid "# KEEPALIVE_RESPONSE messages discarded (not connected)" msgstr "# mensajes defragmentados" -#: src/transport/gnunet-service-transport_neighbours.c:1332 +#: src/transport/gnunet-service-transport_neighbours.c:1544 #, fuzzy msgid "# KEEPALIVE_RESPONSE messages discarded (not expected)" msgstr "# mensajes defragmentados" -#: src/transport/gnunet-service-transport_neighbours.c:1388 +#: src/transport/gnunet-service-transport_neighbours.c:1600 #, fuzzy msgid "# messages discarded due to lack of neighbour record" msgstr "# mensajes defragmentados" -#: src/transport/gnunet-service-transport_neighbours.c:1422 +#: src/transport/gnunet-service-transport_neighbours.c:1634 msgid "# bandwidth quota violations by other peers" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:1438 +#: src/transport/gnunet-service-transport_neighbours.c:1650 msgid "# ms throttling suggested" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:2544 +#: src/transport/gnunet-service-transport_neighbours.c:2802 #, fuzzy msgid "# unexpected CONNECT_ACK messages (no peer)" msgstr "envia COUNT mensajes" -#: src/transport/gnunet-service-transport_neighbours.c:2559 -#: src/transport/gnunet-service-transport_neighbours.c:2585 +#: src/transport/gnunet-service-transport_neighbours.c:2817 +#: src/transport/gnunet-service-transport_neighbours.c:2851 #, fuzzy msgid "# unexpected CONNECT_ACK messages (not ready)" msgstr "envia COUNT mensajes" -#: src/transport/gnunet-service-transport_neighbours.c:2598 +#: src/transport/gnunet-service-transport_neighbours.c:2864 #, fuzzy msgid "# unexpected CONNECT_ACK messages (waiting on ATS)" msgstr "envia COUNT mensajes" -#: src/transport/gnunet-service-transport_neighbours.c:2627 +#: src/transport/gnunet-service-transport_neighbours.c:2897 #, fuzzy msgid "# unexpected CONNECT_ACK messages (disconnecting)" msgstr "envia COUNT mensajes" -#: src/transport/gnunet-service-transport_neighbours.c:2807 +#: src/transport/gnunet-service-transport_neighbours.c:3082 #, fuzzy msgid "# unexpected SESSION ACK messages" msgstr "# de pares conectados" -#: src/transport/gnunet-service-transport_neighbours.c:2856 +#: src/transport/gnunet-service-transport_neighbours.c:3137 msgid "# SET QUOTA messages ignored (no such peer)" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:2870 +#: src/transport/gnunet-service-transport_neighbours.c:3151 msgid "# disconnects due to quota of 0" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:2901 +#: src/transport/gnunet-service-transport_neighbours.c:3182 msgid "# disconnect messages ignored (old format)" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:2912 +#: src/transport/gnunet-service-transport_neighbours.c:3193 msgid "# disconnect messages ignored (timestamp)" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:2943 +#: src/transport/gnunet-service-transport_neighbours.c:3224 msgid "# other peer asked to disconnect from us" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:3020 +#: src/transport/gnunet-service-transport_neighbours.c:3319 #, fuzzy msgid "# disconnected from peer upon explicit request" msgstr "# Anuncios de los pares recibidos" @@ -4789,311 +5168,504 @@ msgstr "# Anuncios de los pares recibidos" msgid "Transport service is lacking NEIGHBOUR_LIMIT option.\n" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:414 +#: src/transport/gnunet-service-transport_validation.c:425 msgid "# address records discarded" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:463 +#: src/transport/gnunet-service-transport_validation.c:487 #, c-format msgid "" "Not transmitting `%s' with `%s', message too big (%u bytes!). This should " "not happen.\n" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:512 +#: src/transport/gnunet-service-transport_validation.c:536 #, fuzzy msgid "# PING without HELLO messages sent" msgstr "# mensajes de texto mandados por PING" -#: src/transport/gnunet-service-transport_validation.c:570 +#: src/transport/gnunet-service-transport_validation.c:618 msgid "# address revalidations started" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:805 +#: src/transport/gnunet-service-transport_validation.c:860 #, fuzzy msgid "# PING message for different peer received" msgstr "# mensajes PONG encriptados recibidos" -#: src/transport/gnunet-service-transport_validation.c:840 +#: src/transport/gnunet-service-transport_validation.c:925 #, c-format -msgid "" -"Not confirming PING with address `%s' since I cannot confirm having this " -"address.\n" +msgid "Received a PING message with validation bug from `%s'\n" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:924 +#: src/transport/gnunet-service-transport_validation.c:1054 msgid "# PONGs unicast via reliable transport" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:933 +#: src/transport/gnunet-service-transport_validation.c:1063 msgid "# PONGs multicast to all available addresses" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:1055 +#: src/transport/gnunet-service-transport_validation.c:1188 msgid "# PONGs dropped, no matching pending validation" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:1080 +#: src/transport/gnunet-service-transport_validation.c:1216 msgid "# PONGs dropped, signature expired" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:1136 +#: src/transport/gnunet-service-transport_validation.c:1270 #, fuzzy, c-format msgid "Adding `%s' without addresses for peer `%s'\n" msgstr "Imposible obtener la dirección del par '%s'.\n" -#: src/transport/gnunet-transport.c:260 -msgid "No transport plugins configured, peer will never communicate\n" +#: src/transport/gnunet-transport.c:266 +#, c-format +msgid "Transmitted %llu bytes/s (%llu bytes in %s)\n" msgstr "" #: src/transport/gnunet-transport.c:273 -#, c-format -msgid "No port configured for plugin `%s', cannot test it\n" -msgstr "" +#, fuzzy, c-format +msgid "Received %llu bytes/s (%llu bytes in %s)\n" +msgstr "GAP recibido contenido no válido de '%s'\n" -#: src/transport/gnunet-transport.c:323 -#, c-format -msgid "Received %llu bytes/s (%llu bytes in %llu ms)\n" +#: src/transport/gnunet-transport.c:303 +#, fuzzy, c-format +msgid "Failed to connect to `%s'\n" +msgstr "Fallo al conectar a gnunetd.\n" + +#: src/transport/gnunet-transport.c:316 +#, fuzzy, c-format +msgid "Failed to resolve address for peer `%s'\n" +msgstr "Fallo al conectar a gnunetd.\n" + +#: src/transport/gnunet-transport.c:325 +#, fuzzy +msgid "Failed to list connections, timeout occured\n" +msgstr "Fallo al conectarse a gnunetd" + +#: src/transport/gnunet-transport.c:429 +msgid "No transport plugins configured, peer will never communicate\n" msgstr "" -#: src/transport/gnunet-transport.c:330 +#: src/transport/gnunet-transport.c:442 #, c-format -msgid "Transmitted %llu bytes/s (%llu bytes in %llu ms)\n" +msgid "No port configured for plugin `%s', cannot test it\n" msgstr "" -#: src/transport/gnunet-transport.c:363 +#: src/transport/gnunet-transport.c:506 #, c-format msgid "Transmitting %u bytes to %s\n" msgstr "" -#: src/transport/gnunet-transport.c:383 +#: src/transport/gnunet-transport.c:531 #, fuzzy, c-format -msgid "Connected to %s\n" -msgstr "'%s' conectado a '%s'.\n" +msgid "Successfully connected to `%s'\n" +msgstr "Permiso denegado para '%s' en %s:%d.\n" + +#: src/transport/gnunet-transport.c:553 +#, c-format +msgid "" +"Successfully connected to `%s', starting to send benchmark data in %u Kb " +"blocks\n" +msgstr "" -#: src/transport/gnunet-transport.c:414 +#: src/transport/gnunet-transport.c:588 #, fuzzy, c-format -msgid "Disconnected from %s\n" +msgid "Disconnected from peer `%s' while benchmarking\n" msgstr "'%s' conectado a '%s'.\n" -#: src/transport/gnunet-transport.c:443 +#: src/transport/gnunet-transport.c:664 #, fuzzy, c-format msgid "Received %u bytes from %s\n" msgstr "GAP recibido contenido no válido de '%s'\n" -#: src/transport/gnunet-transport.c:466 +#: src/transport/gnunet-transport.c:687 #, fuzzy, c-format msgid "Peer `%s': %s %s\n" msgstr "Yo soy el par '%s'.\n" -#: src/transport/gnunet-transport.c:473 +#: src/transport/gnunet-transport.c:702 #, c-format msgid "Peer `%s': %s \n" msgstr "" -#: src/transport/gnunet-transport.c:501 +#: src/transport/gnunet-transport.c:766 #, fuzzy, c-format msgid "Peer `%s' disconnected\n" msgstr "# de pares conectados" -#: src/transport/gnunet-transport.c:569 -#, fuzzy, c-format -msgid "Failed to parse peer identity `%s'\n" -msgstr "Falló al actualizar los datos del módulo '%s'\n" +#: src/transport/gnunet-transport.c:794 +#, fuzzy +msgid "Failed to send connect request to transport service\n" +msgstr "Fallo al conectar a gnunetd.\n" -#: src/transport/gnunet-transport.c:618 -msgid "measure how fast we are receiving data (until CTRL-C)" +#: src/transport/gnunet-transport.c:828 +#, c-format +msgid "" +"Multiple operations given. Please choose only one operation: %s, %s, %s, %s, " +"%s, %s\n" +msgstr "" + +#: src/transport/gnunet-transport.c:834 +#, c-format +msgid "" +"No operation given. Please choose one operation: %s, %s, %s, %s, %s, %s\n" +msgstr "" + +#: src/transport/gnunet-transport.c:854 src/transport/gnunet-transport.c:884 +#: src/transport/gnunet-transport.c:906 src/transport/gnunet-transport.c:945 +#, fuzzy +msgid "Failed to connect to transport service\n" +msgstr "Fallo al conectar a gnunetd.\n" + +#: src/transport/gnunet-transport.c:861 src/transport/gnunet-transport.c:891 +#, fuzzy +msgid "Failed to send request to transport service\n" +msgstr "Fallo al conectar a gnunetd.\n" + +#: src/transport/gnunet-transport.c:911 +msgid "Starting to receive benchmark data\n" +msgstr "" + +#: src/transport/gnunet-transport.c:996 +msgid "measure how fast we are receiving data from all peers (until CTRL-C)" msgstr "" -#: src/transport/gnunet-transport.c:621 +#: src/transport/gnunet-transport.c:999 #, fuzzy -msgid "try to connect to the given peer" +msgid "connect to a peer" msgstr "Fallo al conectar a gnunetd.\n" -#: src/transport/gnunet-transport.c:624 +#: src/transport/gnunet-transport.c:1002 #, fuzzy msgid "provide information about all current connections (once)" msgstr "Imprime información de los pares de GNUnet." -#: src/transport/gnunet-transport.c:627 +#: src/transport/gnunet-transport.c:1008 #, fuzzy -msgid "provide information about all current connections (continuously)" +msgid "" +"provide information about all connects and disconnect events (continuously)" msgstr "Imprime información de los pares de GNUnet." -#: src/transport/gnunet-transport.c:630 +#: src/transport/gnunet-transport.c:1011 msgid "do not resolve hostnames" msgstr "" -#: src/transport/gnunet-transport.c:634 +#: src/transport/gnunet-transport.c:1014 +msgid "peer identity" +msgstr "" + +#: src/transport/gnunet-transport.c:1018 msgid "send data for benchmarking to the other peer (until CTRL-C)" msgstr "" -#: src/transport/gnunet-transport.c:637 +#: src/transport/gnunet-transport.c:1021 msgid "test transport configuration (involves external server)" msgstr "" -#: src/transport/gnunet-transport.c:645 +#: src/transport/gnunet-transport.c:1032 #, fuzzy msgid "Direct access to transport service." msgstr "Fallo al conectar a gnunetd.\n" -#: src/transport/plugin_transport_http.c:1100 +#: src/transport/plugin_transport_http.c:817 +#: src/transport/plugin_transport_http_server.c:2556 msgid "Disabling IPv6 since it is not supported on this system!\n" msgstr "" -#: src/transport/plugin_transport_http.c:1149 +#: src/transport/plugin_transport_http.c:866 +#: src/transport/plugin_transport_http_server.c:2324 #, fuzzy msgid "Require valid port number for service in configuration!\n" msgstr "¡Ninguna aplicación definida en la configuración!\n" -#: src/transport/plugin_transport_http.c:1174 src/util/service.c:1036 +#: src/transport/plugin_transport_http.c:898 +#: src/transport/plugin_transport_http_server.c:2356 src/util/service.c:1053 #, fuzzy, c-format msgid "Failed to resolve `%s': %s\n" msgstr "Fichero almacenado en '%s'.\n" -#: src/transport/plugin_transport_http.c:1191 src/util/service.c:1053 +#: src/transport/plugin_transport_http.c:915 +#: src/transport/plugin_transport_http_server.c:2373 src/util/service.c:1070 #, fuzzy, c-format msgid "Failed to find %saddress for `%s'.\n" msgstr "Fallo al conectar a gnunetd.\n" -#: src/transport/plugin_transport_http.c:1296 +#: src/transport/plugin_transport_http.c:1020 +#: src/transport/plugin_transport_http_server.c:2484 #, c-format msgid "Found %u addresses to report to NAT service\n" msgstr "" -#: src/transport/plugin_transport_http.c:1309 -#, c-format -msgid "FREEING %s\n" -msgstr "" - -#: src/transport/plugin_transport_http.c:1386 +#: src/transport/plugin_transport_http.c:1133 +#: src/transport/plugin_transport_http_server.c:2652 #, fuzzy msgid "Neither IPv4 nor IPv6 are enabled! Fix in configuration\n" msgstr "¡Advertencias de la red desconectadas por configuración!\n" -#: src/transport/plugin_transport_http.c:1399 +#: src/transport/plugin_transport_http.c:1146 +#: src/transport/plugin_transport_http_server.c:2663 #, fuzzy msgid "Port is required! Fix in configuration\n" msgstr " gconfig\tConfiguración GTK\n" -#: src/transport/plugin_transport_http.c:1410 +#: src/transport/plugin_transport_http.c:1157 msgid "Port 0, client only mode\n" msgstr "" -#: src/transport/plugin_transport_http.c:1430 +#: src/transport/plugin_transport_http.c:1177 #, c-format msgid "" "Specific IPv4 address `%s' for plugin %s in configuration file is invalid! " "Binding to all addresses!\n" msgstr "" -#: src/transport/plugin_transport_http.c:1460 +#: src/transport/plugin_transport_http.c:1206 #, c-format msgid "" "Specific IPv6 address `%s' for plugin %s in configuration file is invalid! " "Binding to all addresses!\n" msgstr "" -#: src/transport/plugin_transport_http_client.c:624 +#: src/transport/plugin_transport_http.c:1223 +#: src/transport/plugin_transport_http_server.c:2745 +#, fuzzy, c-format +msgid "Using external hostname `%s'\n" +msgstr "Iniciada colección '%s'.\n" + +#: src/transport/plugin_transport_http.c:1228 +msgid "No external hostname configured\n" +msgstr "" + +#: src/transport/plugin_transport_http_client.c:1516 #, c-format msgid "Could not initialize curl multi handle, failed to start %s plugin!\n" msgstr "" -#: src/transport/plugin_transport_http_server.c:178 -msgid "" -"Could not create a new TLS certificate, program `gnunet-transport-" -"certificate-creation' could not be started!\n" -msgstr "" +#: src/transport/plugin_transport_http_client.c:1647 +#: src/transport/plugin_transport_http_server.c:2869 +#, fuzzy, c-format +msgid "Shutting down plugin `%s'\n" +msgstr "Probando transporte(s) %s\n" + +#: src/transport/plugin_transport_http_client.c:1672 +#: src/transport/plugin_transport_http_server.c:2928 +#, fuzzy, c-format +msgid "Shutdown for plugin `%s' complete\n" +msgstr "" +"Subida de '%s' completada, la velocidad media de subida actual es %8.3f " +"kbps.\n" + +#: src/transport/plugin_transport_http_client.c:1700 +#: src/transport/plugin_transport_http_server.c:2775 +#, fuzzy, c-format +msgid "Maximum number of connections is %u\n" +msgstr "Número máximo de clientes en el chat alcanzado.\n" + +#: src/transport/plugin_transport_http_server.c:1342 +#, c-format +msgid "" +"Access from connection %p (%u of %u) for `%s' `%s' url `%s' with upload data " +"size %u\n" +msgstr "" + +#: src/transport/plugin_transport_http_server.c:1603 +#, c-format +msgid "Accepting connection (%u of %u) from `%s'\n" +msgstr "" -#: src/transport/plugin_transport_http_server.c:202 +#: src/transport/plugin_transport_http_server.c:1611 +#, c-format +msgid "" +"Server reached maximum number connections (%u), rejecting new connection\n" +msgstr "" + +#: src/transport/plugin_transport_http_server.c:1912 +msgid "" +"Could not create a new TLS certificate, program `gnunet-transport-" +"certificate-creation' could not be started!\n" +msgstr "" + +#: src/transport/plugin_transport_http_server.c:1936 msgid "No usable TLS certificate found and creating one failed!\n" msgstr "" -#: src/transport/plugin_transport_tcp.c:591 +#: src/transport/plugin_transport_http_server.c:2631 +#, c-format +msgid "IPv4 support is %s\n" +msgstr "" + +#: src/transport/plugin_transport_http_server.c:2645 +#, c-format +msgid "IPv6 support is %s\n" +msgstr "" + +#: src/transport/plugin_transport_http_server.c:2670 +#, fuzzy, c-format +msgid "Using port %u\n" +msgstr "Probando transporte(s) %s\n" + +#: src/transport/plugin_transport_http_server.c:2685 +#, fuzzy, c-format +msgid "Specific IPv4 address `%s' in configuration file is invalid!\n" +msgstr "" +"Debes especificar un número positivo para '%s' en la configuración en la " +"sección '%s'.\n" + +#: src/transport/plugin_transport_http_server.c:2695 +#, fuzzy, c-format +msgid "Binding to IPv4 address %s\n" +msgstr "Argumento no válido: '%s'\n" + +#: src/transport/plugin_transport_http_server.c:2716 +#, fuzzy, c-format +msgid "Specific IPv6 address `%s' in configuration file is invalid!\n" +msgstr "" +"Debes especificar un número positivo para '%s' en la configuración en la " +"sección '%s'.\n" + +#: src/transport/plugin_transport_http_server.c:2726 +#, fuzzy, c-format +msgid "Binding to IPv6 address %s\n" +msgstr "Argumento no válido: '%s'\n" + +#: src/transport/plugin_transport_http_server.c:2761 +#, fuzzy, c-format +msgid "Notifying transport only about hostname `%s'\n" +msgstr "Probando transporte(s) %s\n" + +#: src/transport/plugin_transport_smtp.c:370 +#, fuzzy, c-format +msgid "Received malformed message via %s. Ignored.\n" +msgstr "Recibido el mensaje '%s' con un mal formato. Omitiendo.\n" + +#: src/transport/plugin_transport_smtp.c:457 +msgid "SMTP filter string to invalid, lacks ': '\n" +msgstr "" + +#: src/transport/plugin_transport_smtp.c:466 +#, c-format +msgid "SMTP filter string to long, capped to `%s'\n" +msgstr "" + +#: src/transport/plugin_transport_smtp.c:561 +#: src/transport/plugin_transport_smtp.c:571 +#: src/transport/plugin_transport_smtp.c:584 +#: src/transport/plugin_transport_smtp.c:603 +#: src/transport/plugin_transport_smtp.c:626 +#: src/transport/plugin_transport_smtp.c:634 +#: src/transport/plugin_transport_smtp.c:647 +#: src/transport/plugin_transport_smtp.c:658 +#, fuzzy, c-format +msgid "SMTP: `%s' failed: %s.\n" +msgstr "'%s' %s falló: %s\n" + +#: src/transport/plugin_transport_smtp.c:799 +msgid "No email-address specified, can not start SMTP transport.\n" +msgstr "" + +#: src/transport/plugin_transport_smtp.c:811 +#, fuzzy +msgid "# bytes received via SMTP" +msgstr "# bytes recibidos por TCP" + +#: src/transport/plugin_transport_smtp.c:812 +#, fuzzy +msgid "# bytes sent via SMTP" +msgstr "# bytes enviados por TCP" + +#: src/transport/plugin_transport_smtp.c:814 +#, fuzzy +msgid "# bytes dropped by SMTP (outgoing)" +msgstr "# bytes omitidos por TCP (salientes)" + +#: src/transport/plugin_transport_tcp.c:595 #, c-format msgid "Unexpected address length: %u bytes\n" msgstr "" -#: src/transport/plugin_transport_tcp.c:767 -#: src/transport/plugin_transport_tcp.c:856 -#: src/transport/plugin_transport_tcp.c:906 -#: src/transport/plugin_transport_tcp.c:992 -#: src/transport/plugin_transport_tcp.c:1086 -#: src/transport/plugin_transport_tcp.c:1103 +#: src/transport/plugin_transport_tcp.c:771 +#: src/transport/plugin_transport_tcp.c:860 +#: src/transport/plugin_transport_tcp.c:910 +#: src/transport/plugin_transport_tcp.c:996 +#: src/transport/plugin_transport_tcp.c:1139 +#: src/transport/plugin_transport_tcp.c:1156 #, fuzzy msgid "# bytes currently in TCP buffers" msgstr "# bytes enviados por TCP" -#: src/transport/plugin_transport_tcp.c:774 -#: src/transport/plugin_transport_tcp.c:963 -#: src/transport/plugin_transport_tcp.c:1761 -#: src/transport/plugin_transport_tcp.c:2390 +#: src/transport/plugin_transport_tcp.c:778 +#: src/transport/plugin_transport_tcp.c:967 +#: src/transport/plugin_transport_tcp.c:1826 +#: src/transport/plugin_transport_tcp.c:2462 #, fuzzy msgid "# TCP sessions active" msgstr "# claves de la sesión aceptadas" -#: src/transport/plugin_transport_tcp.c:860 +#: src/transport/plugin_transport_tcp.c:864 #, fuzzy msgid "# bytes discarded by TCP (timeout)" msgstr "# bytes omitidos por TCP (salientes)" -#: src/transport/plugin_transport_tcp.c:909 +#: src/transport/plugin_transport_tcp.c:913 #, fuzzy msgid "# bytes transmitted via TCP" msgstr "# bytes desencriptados" -#: src/transport/plugin_transport_tcp.c:996 +#: src/transport/plugin_transport_tcp.c:1000 #, fuzzy msgid "# bytes discarded by TCP (disconnect)" msgstr "# bytes omitidos por TCP (salientes)" -#: src/transport/plugin_transport_tcp.c:1290 +#: src/transport/plugin_transport_tcp.c:1113 +#, c-format +msgid "Trying to send with invalid session %p\n" +msgstr "" + +#: src/transport/plugin_transport_tcp.c:1349 #, c-format msgid "Address of unexpected length: %u\n" msgstr "" -#: src/transport/plugin_transport_tcp.c:1401 +#: src/transport/plugin_transport_tcp.c:1466 msgid "# transport-service disconnect requests for TCP" msgstr "" -#: src/transport/plugin_transport_tcp.c:1802 +#: src/transport/plugin_transport_tcp.c:1867 #, fuzzy msgid "# TCP WELCOME messages received" msgstr "# mensajes PONG encriptados recibidos" -#: src/transport/plugin_transport_tcp.c:1973 +#: src/transport/plugin_transport_tcp.c:2046 msgid "# bytes received via TCP" msgstr "# bytes recibidos por TCP" -#: src/transport/plugin_transport_tcp.c:2043 +#: src/transport/plugin_transport_tcp.c:2124 msgid "# network-level TCP disconnect events" msgstr "" -#: src/transport/plugin_transport_tcp.c:2279 src/util/service.c:940 +#: src/transport/plugin_transport_tcp.c:2350 src/util/service.c:948 +#: src/util/service.c:954 #, c-format msgid "Require valid port number for service `%s' in configuration!\n" msgstr "" -#: src/transport/plugin_transport_tcp.c:2293 +#: src/transport/plugin_transport_tcp.c:2364 #, fuzzy msgid "Failed to start service.\n" msgstr "Falló al comenzar la recolección.\n" -#: src/transport/plugin_transport_tcp.c:2355 -#, fuzzy, c-format -msgid "Failed to find option %s in section %s!\n" -msgstr "Fallo al conectar a gnunetd.\n" - -#: src/transport/plugin_transport_tcp.c:2378 +#: src/transport/plugin_transport_tcp.c:2450 #, c-format msgid "TCP transport listening on port %llu\n" msgstr "" -#: src/transport/plugin_transport_tcp.c:2382 +#: src/transport/plugin_transport_tcp.c:2454 msgid "TCP transport not listening on any port (client only)\n" msgstr "" -#: src/transport/plugin_transport_tcp.c:2386 +#: src/transport/plugin_transport_tcp.c:2458 #, c-format msgid "TCP transport advertises itself as being on port %llu\n" msgstr "" @@ -5108,129 +5680,132 @@ msgstr "# mensajes PONG encriptados recibidos" msgid "# IPv4 broadcast HELLO beacons received via udp" msgstr "# mensajes PONG encriptados recibidos" -#: src/transport/plugin_transport_udp_broadcasting.c:367 +#: src/transport/plugin_transport_udp_broadcasting.c:394 #, c-format msgid "Failed to set IPv4 broadcast option for broadcast socket on port %d\n" msgstr "" -#: src/transport/plugin_transport_udp.c:1894 +#: src/transport/plugin_transport_udp.c:2517 +#, c-format +msgid "" +"UDP could not transmit message to `%s': Network seems down, please check " +"your network configuration\n" +msgstr "" + +#: src/transport/plugin_transport_udp.c:2531 #, c-format msgid "" -"UDP could not message to `%s': `%s'. Please check your network configuration " -"and disable IPv6 if your connection does not have a global IPv6 address\n" +"UDP could not transmit message to `%s': Please check your network " +"configuration and disable IPv6 if your connection does not have a global " +"IPv6 address\n" msgstr "" -#: src/transport/plugin_transport_udp.c:2138 +#: src/transport/plugin_transport_udp.c:2772 #, fuzzy msgid "Failed to open UDP sockets\n" msgstr "Fichero almacenado en '%s'.\n" -#: src/transport/plugin_transport_udp.c:2306 +#: src/transport/plugin_transport_udp.c:2848 #, c-format msgid "Given `%s' option is out of range: %llu > %u\n" msgstr "" -#: src/transport/plugin_transport_udp.c:2349 +#: src/transport/plugin_transport_udp.c:2891 #, fuzzy, c-format msgid "Invalid IPv6 address: `%s'\n" msgstr "Argumento no válido: '%s'\n" -#: src/transport/plugin_transport_unix.c:1356 +#: src/transport/plugin_transport_unix.c:1357 #, fuzzy msgid "Failed to open UNIX sockets\n" msgstr "Fichero almacenado en '%s'.\n" -#: src/transport/plugin_transport_wlan.c:561 +#: src/transport/plugin_transport_wlan.c:580 msgid "# WLAN ACKs sent" msgstr "" -#: src/transport/plugin_transport_wlan.c:580 +#: src/transport/plugin_transport_wlan.c:599 #, fuzzy msgid "# WLAN messages defragmented" msgstr "# mensajes defragmentados" -#: src/transport/plugin_transport_wlan.c:626 -#: src/transport/plugin_transport_wlan.c:676 -#: src/transport/plugin_transport_wlan.c:1696 +#: src/transport/plugin_transport_wlan.c:645 +#: src/transport/plugin_transport_wlan.c:695 +#: src/transport/plugin_transport_wlan.c:1758 #, fuzzy msgid "# WLAN sessions allocated" msgstr "# claves de la sesión aceptadas" -#: src/transport/plugin_transport_wlan.c:749 +#: src/transport/plugin_transport_wlan.c:770 #, fuzzy msgid "# WLAN message fragments sent" msgstr "# mensajes fragmentados" -#: src/transport/plugin_transport_wlan.c:767 +#: src/transport/plugin_transport_wlan.c:794 msgid "# WLAN messages pending (with fragmentation)" msgstr "" -#: src/transport/plugin_transport_wlan.c:867 -#: src/transport/plugin_transport_wlan.c:948 -#: src/transport/plugin_transport_wlan.c:1698 +#: src/transport/plugin_transport_wlan.c:902 +#: src/transport/plugin_transport_wlan.c:987 +#: src/transport/plugin_transport_wlan.c:1760 #, fuzzy msgid "# WLAN MAC endpoints allocated" msgstr "# mensajes PONG encriptados recibidos" -#: src/transport/plugin_transport_wlan.c:1119 +#: src/transport/plugin_transport_wlan.c:1169 #, fuzzy msgid "# HELLO messages received via WLAN" msgstr "# mensajes PONG encriptados recibidos" -#: src/transport/plugin_transport_wlan.c:1140 +#: src/transport/plugin_transport_wlan.c:1190 #, fuzzy msgid "# fragments received via WLAN" msgstr "# fragmentos descartados" -#: src/transport/plugin_transport_wlan.c:1150 +#: src/transport/plugin_transport_wlan.c:1200 #, fuzzy msgid "# ACKs received via WLAN" msgstr "# bytes recibidos por TCP" -#: src/transport/plugin_transport_wlan.c:1207 +#: src/transport/plugin_transport_wlan.c:1257 #, fuzzy msgid "# WLAN DATA messages discarded due to CRC32 error" msgstr "# mensajes defragmentados" -#: src/transport/plugin_transport_wlan.c:1306 +#: src/transport/plugin_transport_wlan.c:1358 #, fuzzy msgid "# DATA messages received via WLAN" msgstr "# mensajes PONG encriptados recibidos" -#: src/transport/plugin_transport_wlan.c:1341 +#: src/transport/plugin_transport_wlan.c:1393 #, fuzzy msgid "# WLAN DATA messages processed" msgstr "# mensajes PONG encriptados recibidos" -#: src/transport/plugin_transport_wlan.c:1402 +#: src/transport/plugin_transport_wlan.c:1454 #, fuzzy msgid "# HELLO beacons sent via WLAN" msgstr "# bytes enviados vía UDP" -#: src/transport/plugin_transport_wlan.c:1511 +#: src/transport/plugin_transport_wlan.c:1563 msgid "WLAN address with invalid size encountered\n" msgstr "" -#: src/transport/plugin_transport_wlan.c:1668 -#, fuzzy, c-format -msgid "Invalid configuration option `%s' in section `%s'\n" -msgstr "Fichero de configuración '%s' creado.\n" - -#: src/transport/plugin_transport_wlan.c:1677 +#: src/transport/plugin_transport_wlan.c:1739 #, c-format msgid "Helper binary `%s' not SUID, cannot run WLAN transport\n" msgstr "" -#: src/transport/plugin_transport_wlan.c:1687 -#, fuzzy, c-format -msgid "Missing configuration option `%s' in section `%s'\n" -msgstr "Fichero de configuración '%s' creado.\n" - -#: src/transport/transport_api.c:570 +#: src/transport/transport_api.c:659 #, fuzzy, c-format msgid "Received unexpected message of type %u in %s:%u\n" msgstr "Recibido mensaje corrupto del par '%s' en %s:%d.\n" +#: src/transport/transport-testing.c:586 +#, fuzzy +msgid "Failed to initialize testing library!\n" +msgstr "Imposible inicializar SQLite.\n" + #: src/util/bio.c:136 src/util/bio.c:142 #, fuzzy, c-format msgid "Error reading `%s': %s" @@ -5261,264 +5836,319 @@ msgstr "" msgid "Metadata `%s' failed to deserialize" msgstr "" -#: src/util/client.c:359 +#: src/util/client.c:276 src/util/client.c:753 src/util/service.c:984 +#, c-format +msgid "UNIXPATH `%s' too long, maximum length is %llu\n" +msgstr "" + +#: src/util/client.c:280 src/util/client.c:757 src/util/service.c:988 +#, fuzzy, c-format +msgid "Using `%s' instead\n" +msgstr "%s: la opción '%s' es ambigua\n" + +#: src/util/client.c:371 #, c-format msgid "" "Could not determine valid hostname and port for service `%s' from " "configuration.\n" msgstr "" -#: src/util/client.c:367 +#: src/util/client.c:379 #, c-format msgid "Need a non-empty hostname for service `%s'.\n" msgstr "" -#: src/util/client.c:685 +#: src/util/client.c:698 msgid "Failure to transmit TEST request.\n" msgstr "" -#: src/util/client.c:740 src/util/service.c:970 -#, c-format -msgid "UNIXPATH `%s' too long, maximum length is %llu\n" -msgstr "" - -#: src/util/client.c:882 +#: src/util/client.c:898 #, fuzzy, c-format msgid "Could not connect to service `%s', must not be running.\n" msgstr "Imposible conectar con gnunetd.\n" -#: src/util/client.c:896 +#: src/util/client.c:912 #, fuzzy, c-format msgid "Failure to transmit request to service `%s'\n" msgstr "Falló al mandar la petición HTTP al host '%s': %s\n" -#: src/util/client.c:1149 +#: src/util/client.c:1177 msgid "Could not submit request, not expecting to receive a response.\n" msgstr "" -#: src/util/common_logging.c:239 src/util/common_logging.c:890 +#: src/util/common_logging.c:258 src/util/common_logging.c:1007 msgid "DEBUG" msgstr "DEPURACIÓN" -#: src/util/common_logging.c:241 src/util/common_logging.c:888 +#: src/util/common_logging.c:260 src/util/common_logging.c:1005 msgid "INFO" msgstr "INFORMACIÓN" -#: src/util/common_logging.c:243 src/util/common_logging.c:886 +#: src/util/common_logging.c:262 src/util/common_logging.c:1003 msgid "WARNING" msgstr "PELIGRO" -#: src/util/common_logging.c:245 src/util/common_logging.c:884 +#: src/util/common_logging.c:264 src/util/common_logging.c:1001 msgid "ERROR" msgstr "ERROR" -#: src/util/common_logging.c:247 src/util/common_logging.c:892 +#: src/util/common_logging.c:266 src/util/common_logging.c:1009 msgid "NONE" msgstr "" -#: src/util/common_logging.c:610 +#: src/util/common_logging.c:395 #, fuzzy, c-format msgid "Failed to create or access directory for log file `%s'\n" msgstr "Imposible pasar el fichero de configuración '%s'.\n" -#: src/util/common_logging.c:725 +#: src/util/common_logging.c:819 #, c-format msgid "Message `%.*s' repeated %u times in the last %s\n" msgstr "" -#: src/util/common_logging.c:893 +#: src/util/common_logging.c:1010 msgid "INVALID" msgstr "" -#: src/util/common_logging.c:992 +#: src/util/common_logging.c:1149 #, fuzzy msgid "unknown address" msgstr "desconocido" -#: src/util/common_logging.c:1030 +#: src/util/common_logging.c:1187 #, fuzzy msgid "invalid address" msgstr "Argumentos inválidos: " -#: src/util/configuration.c:244 +#: src/util/common_logging.c:1205 #, fuzzy, c-format -msgid "Syntax error in configuration file `%s' at line %u.\n" +msgid "Configuration fails to specify option `%s' in section `%s'!\n" +msgstr "" +"El fichero de configuración debe especificar el directorio para almacenar " +"los datos FS en la sección '%s' bajo '%s'.\n" + +#: src/util/common_logging.c:1226 +#, fuzzy, c-format +msgid "" +"Configuration specifies invalid value for option `%s' in section `%s': %s\n" +msgstr "" +"El fichero de configuración debe especificar el directorio para almacenar " +"los datos FS en la sección '%s' bajo '%s'.\n" + +#: src/util/configuration.c:291 +#, fuzzy, c-format +msgid "Syntax error while deserializing in line %u\n" msgstr "" "Error de sintaxis en el fichero de configuración '%s' en la linea %d.\n" -#: src/util/configuration.c:816 +#: src/util/configuration.c:998 #, c-format msgid "" "Configuration value '%s' for '%s' in section '%s' is not in set of legal " "choices\n" msgstr "" -#: src/util/connection.c:420 +#: src/util/connection.c:427 #, fuzzy, c-format msgid "Access denied to `%s'\n" msgstr "Permiso denegado para '%s' en %s:%d.\n" -#: src/util/connection.c:435 +#: src/util/connection.c:442 #, c-format msgid "Accepting connection from `%s': %p\n" msgstr "" -#: src/util/connection.c:550 +#: src/util/connection.c:557 #, fuzzy, c-format msgid "" "Failed to establish TCP connection to `%s:%u', no further addresses to try.\n" msgstr "Se produjo un error estableciendo conexión con gnunetd.\n" -#: src/util/connection.c:739 src/util/connection.c:909 +#: src/util/connection.c:755 src/util/connection.c:922 #, fuzzy, c-format msgid "Trying to connect to `%s' (%p)\n" msgstr "Fallo al conectar a gnunetd.\n" -#: src/util/connection.c:748 -#, fuzzy, c-format -msgid "Failed to connect to `%s' (%p)\n" -msgstr "Fallo al conectar a gnunetd.\n" - -#: src/util/connection.c:900 +#: src/util/connection.c:913 #, fuzzy, c-format msgid "Attempt to connect to `%s' failed\n" msgstr "Fallo al conectar a gnunetd.\n" -#: src/util/container_bloomfilter.c:510 +#: src/util/container_bloomfilter.c:518 #, c-format msgid "" "Size of file on disk is incorrect for this Bloom filter (want %llu, have " "%llu)\n" msgstr "" -#: src/util/crypto_random.c:280 -#, c-format -msgid "Starting `%s' process to generate entropy\n" -msgstr "" +#: src/util/crypto_ecc.c:441 +#, fuzzy, c-format +msgid "" +"File `%s' does not contain a valid private key (too long, %llu bytes). " +"Deleting it.\n" +msgstr "El fichero '%s' no contiene un pseudónimo.\n" -#: src/util/crypto_random.c:309 -#, c-format -msgid "libgcrypt has not the expected version (version %s is required).\n" -msgstr "" -"libgcrypt no está en la versión esperada (se necesita la versión %s).\n" +#: src/util/crypto_ecc.c:456 src/util/crypto_rsa.c:660 +#, fuzzy, c-format +msgid "" +"File `%s' does not contain a valid private key (failed decode, %llu bytes). " +"Deleting it.\n" +msgstr "El fichero '%s' no contiene un pseudónimo.\n" -#: src/util/crypto_rsa.c:661 src/util/crypto_rsa.c:708 +#: src/util/crypto_ecc.c:552 src/util/crypto_ecc.c:596 +#: src/util/crypto_rsa.c:757 src/util/crypto_rsa.c:801 #, fuzzy, c-format -msgid "Could not aquire lock on file `%s': %s...\n" +msgid "Could not acquire lock on file `%s': %s...\n" msgstr "Imposible escribir PID al fichero '%s': %s.\n" -#: src/util/crypto_rsa.c:666 +#: src/util/crypto_ecc.c:557 src/util/crypto_rsa.c:762 #, fuzzy msgid "Creating a new private key. This may take a while.\n" msgstr "Creando nueva clave local (esto puede llevar un tiempo).\n" -#: src/util/crypto_rsa.c:684 -#, c-format -msgid "I am host `%s'. Stored new private key in `%s'.\n" -msgstr "" - -#: src/util/crypto_rsa.c:712 src/util/crypto_rsa.c:748 -msgid "This may be ok if someone is currently generating a hostkey.\n" +#: src/util/crypto_ecc.c:600 src/util/crypto_rsa.c:805 +#: src/util/crypto_rsa.c:841 +msgid "This may be ok if someone is currently generating a private key.\n" msgstr "" -#: src/util/crypto_rsa.c:743 +#: src/util/crypto_ecc.c:631 src/util/crypto_rsa.c:836 #, c-format msgid "" -"When trying to read hostkey file `%s' I found %u bytes but I need at least " -"%u.\n" +"When trying to read key file `%s' I found %u bytes but I need at least %u.\n" +msgstr "" + +#: src/util/crypto_ecc.c:636 +msgid "This may be ok if someone is currently generating a key.\n" msgstr "" -#: src/util/crypto_rsa.c:763 +#: src/util/crypto_ecc.c:651 src/util/crypto_rsa.c:856 #, fuzzy, c-format msgid "File `%s' does not contain a valid private key. Deleting it.\n" msgstr "El fichero '%s' no contiene un pseudónimo.\n" -#: src/util/crypto_rsa.c:781 +#: src/util/crypto_ecc.c:773 src/util/crypto_rsa.c:941 +msgid "interrupted by shutdown" +msgstr "" + +#: src/util/crypto_ecc.c:784 +#, fuzzy +msgid "gnunet-ecc failed" +msgstr "gnunet-setup" + +#: src/util/crypto_ecc.c:979 +#, fuzzy, c-format +msgid "ECC signing failed at %s:%d: %s\n" +msgstr "'%s' falló en %s: %d con error: '%s'.\n" + +#: src/util/crypto_ecc.c:1047 #, fuzzy, c-format -msgid "I am host `%s'. Read private key from `%s'.\n" -msgstr "Llamada a '%s' con la clave '%s'.\n" +msgid "ECC signature verification failed at %s:%d: %s\n" +msgstr "La verificación de la firma RSA fallo en %s: %d: %s\n" + +#: src/util/crypto_random.c:313 +#, c-format +msgid "Starting `%s' process to generate entropy\n" +msgstr "" -#: src/util/crypto_rsa.c:1032 +#: src/util/crypto_random.c:342 +#, c-format +msgid "libgcrypt has not the expected version (version %s is required).\n" +msgstr "" +"libgcrypt no está en la versión esperada (se necesita la versión %s).\n" + +#: src/util/crypto_rsa.c:644 +#, fuzzy, c-format +msgid "" +"File `%s' does not contain a valid private key (too long, %llu bytes). " +"Renaming it.\n" +msgstr "El fichero '%s' no contiene un pseudónimo.\n" + +#: src/util/crypto_rsa.c:952 +#, fuzzy +msgid "gnunet-rsa failed" +msgstr "gnunet-setup" + +#: src/util/crypto_rsa.c:1343 #, c-format msgid "RSA signature verification failed at %s:%d: %s\n" msgstr "La verificación de la firma RSA fallo en %s: %d: %s\n" -#: src/util/disk.c:498 +#: src/util/disk.c:601 #, fuzzy, c-format msgid "`%s' failed for drive `%S': %u\n" msgstr "'%s' falló para la unidad %s: %u\n" -#: src/util/disk.c:1062 +#: src/util/disk.c:1205 #, fuzzy, c-format msgid "Expected `%s' to be a directory!\n" msgstr "¡'%s' se esperaba que '%s' fuera un directorio!\n" -#: src/util/disk.c:1416 src/util/service.c:1650 +#: src/util/disk.c:1559 src/util/service.c:1669 #, fuzzy, c-format msgid "Cannot obtain information about user `%s': %s\n" msgstr "Imposible guardar el fichero de configuración '%s': %s.\n" -#: src/util/disk.c:1734 +#: src/util/disk.c:1931 #, fuzzy, c-format msgid "No `%s' specified for service `%s' in configuration.\n" msgstr "¡Ninguna aplicación definida en la configuración!\n" -#: src/util/getopt.c:669 +#: src/util/getopt.c:570 #, c-format msgid "%s: option `%s' is ambiguous\n" msgstr "%s: la opción '%s' es ambigua\n" -#: src/util/getopt.c:693 +#: src/util/getopt.c:594 #, c-format msgid "%s: option `--%s' does not allow an argument\n" msgstr "%s: la opción '--%s' no permite un argumento\n" -#: src/util/getopt.c:698 +#: src/util/getopt.c:599 #, c-format msgid "%s: option `%c%s' does not allow an argument\n" msgstr "%s: la opción '%c%s' no permite un argumento\n" -#: src/util/getopt.c:715 src/util/getopt.c:883 +#: src/util/getopt.c:616 src/util/getopt.c:783 #, c-format msgid "%s: option `%s' requires an argument\n" msgstr "%s: la opción '%s' requiere un argumento\n" -#: src/util/getopt.c:744 +#: src/util/getopt.c:645 #, c-format msgid "%s: unrecognized option `--%s'\n" msgstr "%s: opción no reconocida '--%s'\n" -#: src/util/getopt.c:748 +#: src/util/getopt.c:649 #, c-format msgid "%s: unrecognized option `%c%s'\n" msgstr "%s: opción no reconocida '%c%s'\n" -#: src/util/getopt.c:773 +#: src/util/getopt.c:674 #, c-format msgid "%s: illegal option -- %c\n" msgstr "%s: opción ilegal -- %c\n" -#: src/util/getopt.c:775 +#: src/util/getopt.c:676 #, c-format msgid "%s: invalid option -- %c\n" msgstr "%s: opción no válida -- %c\n" -#: src/util/getopt.c:803 src/util/getopt.c:931 +#: src/util/getopt.c:704 src/util/getopt.c:831 #, c-format msgid "%s: option requires an argument -- %c\n" msgstr "%s: la opción requiere un argumento --%c\n" -#: src/util/getopt.c:851 +#: src/util/getopt.c:752 #, c-format msgid "%s: option `-W %s' is ambiguous\n" msgstr "%s: la opción '-W %s' es ambigua\n" -#: src/util/getopt.c:869 +#: src/util/getopt.c:770 #, c-format msgid "%s: option `-W %s' does not allow an argument\n" msgstr "%s: la opción '-W %s' no permite un argumento\n" -#: src/util/getopt.c:1035 +#: src/util/getopt.c:935 #, fuzzy, c-format msgid "Use %s to get a list of options.\n" msgstr "Usar --help para obtener una lista de opciones.\n" @@ -5529,37 +6159,110 @@ msgid "" "Arguments mandatory for long options are also mandatory for short options.\n" msgstr "" -#: src/util/getopt_helpers.c:258 src/util/getopt_helpers.c:286 +#: src/util/getopt_helpers.c:258 src/util/getopt_helpers.c:316 #, c-format msgid "You must pass a number to the `%s' option.\n" msgstr "Tienes que introducir un número en la opción '%s'.\n" -#: src/util/gnunet-resolver.c:148 -msgid "perform a reverse lookup" +#: src/util/getopt_helpers.c:288 +#, fuzzy, c-format +msgid "You must pass relative time to the `%s' option.\n" +msgstr "Debes pasar un número positivo a la opción '%s'.\n" + +#: src/util/gnunet-config.c:90 +#, c-format +msgid "--section argument is required\n" msgstr "" -#: src/util/gnunet-resolver.c:154 -msgid "Use build-in GNUnet stub resolver" +#: src/util/gnunet-config.c:133 +#, c-format +msgid "--option argument required to set value\n" +msgstr "" + +#: src/util/gnunet-config.c:160 +msgid "obtain option of value as a filename (with $-expansion)" +msgstr "" + +#: src/util/gnunet-config.c:163 +msgid "name of the section to access" +msgstr "" + +#: src/util/gnunet-config.c:166 +msgid "name of the option to access" +msgstr "" + +#: src/util/gnunet-config.c:169 +msgid "value to set" +msgstr "" + +#: src/util/gnunet-config.c:178 +#, fuzzy +msgid "Manipulate GNUnet configuration files" +msgstr "Imposible guardar el fichero de configuración '%s':" + +#: src/util/gnunet-ecc.c:107 src/util/gnunet-rsa.c:107 +#, fuzzy, c-format +msgid "Failed to open `%s': %s\n" +msgstr "Fichero almacenado en '%s'.\n" + +#: src/util/gnunet-ecc.c:113 src/util/gnunet-rsa.c:113 +#, c-format +msgid "Generating %u keys, please wait" msgstr "" -#: src/util/gnunet-rsa.c:64 +#: src/util/gnunet-ecc.c:128 src/util/gnunet-rsa.c:137 +#, fuzzy, c-format +msgid "" +"\n" +"Failed to write to `%s': %s\n" +msgstr "Fallo al conectar a gnunetd.\n" + +#: src/util/gnunet-ecc.c:140 src/util/gnunet-rsa.c:149 +#, fuzzy, c-format +msgid "Finished!\n" +msgstr "Finalizar" + +#: src/util/gnunet-ecc.c:163 src/util/gnunet-rsa.c:172 #, c-format msgid "No hostkey file specified on command line\n" msgstr "" -#: src/util/gnunet-rsa.c:112 +#: src/util/gnunet-ecc.c:220 src/util/gnunet-rsa.c:229 +msgid "create COUNT public-private key pairs (for testing)" +msgstr "" + +#: src/util/gnunet-ecc.c:223 src/util/gnunet-rsa.c:232 msgid "print the public key in ASCII format" msgstr "" -#: src/util/gnunet-rsa.c:115 +#: src/util/gnunet-ecc.c:226 src/util/gnunet-rsa.c:235 msgid "print the hash of the public key in ASCII format" msgstr "" -#: src/util/gnunet-rsa.c:118 +#: src/util/gnunet-ecc.c:229 src/util/gnunet-rsa.c:238 msgid "print the short hash of the public key in ASCII format" msgstr "" -#: src/util/gnunet-rsa.c:124 +#: src/util/gnunet-ecc.c:232 src/util/gnunet-rsa.c:241 +msgid "" +"use insecure, weak random number generator for key generation (for testing " +"only)" +msgstr "" + +#: src/util/gnunet-ecc.c:243 +#, fuzzy +msgid "Manipulate GNUnet private ECC key files" +msgstr "Imposible guardar el fichero de configuración '%s':" + +#: src/util/gnunet-resolver.c:148 +msgid "perform a reverse lookup" +msgstr "" + +#: src/util/gnunet-resolver.c:159 +msgid "Use build-in GNUnet stub resolver" +msgstr "" + +#: src/util/gnunet-rsa.c:252 msgid "Manipulate GNUnet private RSA key files" msgstr "" @@ -5574,70 +6277,74 @@ msgstr "Imposible resolver '%s': %s\n" msgid "Could not find IP of host `%s': %s\n" msgstr "Imposible encontrar la IP del host '%s': %s\n" -#: src/util/helper.c:244 +#: src/util/gnunet-uri.c:90 +#, c-format +msgid "No URI specified on command line\n" +msgstr "" + +#: src/util/gnunet-uri.c:95 #, fuzzy, c-format -msgid "Error reading from `%s': %s\n" -msgstr "Error creando usuario" +msgid "Invalid URI: does not start with `%s'\n" +msgstr "Respuesta inválida a '%s'.\n" + +#: src/util/gnunet-uri.c:102 +#, c-format +msgid "Invalid URI: fails to specify subsystem\n" +msgstr "" -#: src/util/helper.c:259 +#: src/util/gnunet-uri.c:112 #, c-format -msgid "Got 0 bytes from helper `%s' (EOF)\n" +msgid "No handler known for subsystem `%s'\n" msgstr "" -#: src/util/helper.c:269 +#: src/util/gnunet-uri.c:174 +msgid "Perform default-actions for GNUnet URIs" +msgstr "" + +#: src/util/helper.c:260 #, fuzzy, c-format -msgid "Got %u bytes from helper `%s'\n" -msgstr "GAP recibido contenido no válido de '%s'\n" +msgid "Error reading from `%s': %s\n" +msgstr "Error creando usuario" -#: src/util/helper.c:278 +#: src/util/helper.c:305 #, fuzzy, c-format msgid "Failed to parse inbound message from helper `%s'\n" msgstr "Falló al pasar los datos de la interfaz de '%s' de %s:%d.\n" -#: src/util/helper.c:310 -#, fuzzy, c-format -msgid "Starting HELPER process `%s'\n" -msgstr "Iniciada colección '%s'.\n" - -#: src/util/helper.c:440 +#: src/util/helper.c:499 #, fuzzy, c-format msgid "Error writing to `%s': %s\n" msgstr "Error creando usuario" -#: src/util/network.c:1200 +#: src/util/network.c:127 +#, c-format +msgid "Unable to shorten unix path `%s' while keeping name unique\n" +msgstr "" + +#: src/util/network.c:1331 #, c-format msgid "" "Fatal internal logic error, process hangs in `%s' (abort with CTRL-C)!\n" msgstr "" -#: src/util/os_installation.c:299 +#: src/util/os_installation.c:420 #, c-format msgid "" "Could not determine installation path for %s. Set `%s' environment " "variable.\n" msgstr "" -#: src/util/os_installation.c:486 +#: src/util/os_installation.c:702 #, fuzzy, c-format msgid "Could not find binary `%s' in PATH!\n" msgstr "¡Imposible encontrar el par '%s' en la tabla de enrutado!\n" -#: src/util/os_installation.c:492 -#, fuzzy, c-format -msgid "access (%s, X_OK) failed: %s\n" -msgstr "'%s' %s falló: %s\n" - -#: src/util/os_installation.c:507 -#, fuzzy, c-format -msgid "stat (%s) failed: %s\n" -msgstr "'%s' %s falló: %s\n" - -#: src/util/os_priority.c:305 +#: src/util/os_priority.c:302 #, fuzzy, c-format msgid "Failed to open named pipe `%s' for reading: %s\n" msgstr "Fichero almacenado en '%s'.\n" -#: src/util/os_priority.c:306 +#: src/util/os_priority.c:303 #, fuzzy, c-format msgid "Failed to open named pipe `%s' for writing: %s\n" msgstr "Fichero almacenado en '%s'.\n" @@ -5662,12 +6369,17 @@ msgstr "'%s' falló en la biblioteca '%s' en %s:%d con un error: %s\n" msgid "Could not determine plugin installation path.\n" msgstr "Imposible determinar mi dirección IPv6 pública.\n" -#: src/util/pseudonym.c:276 +#: src/util/program.c:254 src/util/service.c:1791 +#, fuzzy, c-format +msgid "Could not access configuration file `%s'\n" +msgstr "Imposible pasar el fichero de configuración '%s'.\n" + +#: src/util/pseudonym.c:282 #, fuzzy, c-format msgid "Failed to parse metadata about pseudonym from file `%s': %s\n" msgstr "Falló al pasar los datos de la interfaz de '%s' de %s:%d.\n" -#: src/util/pseudonym.c:407 src/util/pseudonym.c:433 +#: src/util/pseudonym.c:413 src/util/pseudonym.c:439 #, fuzzy msgid "no-name" msgstr "Mostrar el nombre" @@ -5700,154 +6412,154 @@ msgstr "" msgid "Could not resolve our FQDN : %s\n" msgstr "Imposible resolver '%s': %s\n" -#: src/util/scheduler.c:786 +#: src/util/scheduler.c:782 msgid "Looks like we're busy waiting...\n" msgstr "" -#: src/util/scheduler.c:916 +#: src/util/scheduler.c:912 #, c-format msgid "Attempt to cancel dead task %llu!\n" msgstr "" -#: src/util/server.c:483 +#: src/util/server.c:426 #, fuzzy, c-format msgid "`%s' failed for port %d (%s).\n" msgstr "'%s' falló para la unidad %s: %u\n" -#: src/util/server.c:492 +#: src/util/server.c:435 #, fuzzy, c-format msgid "`%s' failed for port %d (%s): address already in use\n" msgstr "" "'%s' falló para el puerto %d: %s. ¿Está gnunet ejecutandose actualmente?\n" -#: src/util/server.c:497 +#: src/util/server.c:446 #, fuzzy, c-format -msgid "`%s' failed for `%s': address already in use\n" +msgid "`%s' failed for `%.*s': address already in use\n" msgstr "" "'%s' falló para el puerto %d: %s. ¿Está gnunet ejecutandose actualmente?\n" -#: src/util/server.c:827 +#: src/util/server.c:830 #, c-format msgid "" "Processing code for message of type %u did not call " -"GNUNET_SERVER_receive_done after %llums\n" +"`GNUNET_SERVER_receive_done' after %s\n" msgstr "" -#: src/util/service.c:135 src/util/service.c:161 src/util/service.c:204 -#: src/util/service.c:225 src/util/service.c:232 +#: src/util/service.c:142 src/util/service.c:168 src/util/service.c:211 +#: src/util/service.c:232 src/util/service.c:239 #, c-format msgid "Invalid format for IP: `%s'\n" msgstr "Formato no válido para la IP: '%s'\n" -#: src/util/service.c:188 +#: src/util/service.c:195 #, c-format msgid "Invalid network notation ('/%d' is not legal in IPv4 CIDR)." msgstr "Notación de red no válida ('/%d' no es válido en IPv4 CIDR)." -#: src/util/service.c:281 +#: src/util/service.c:288 #, c-format msgid "Invalid network notation (does not end with ';': `%s')\n" msgstr "Notación de red no válida (no termina con ';': '%s')\n" -#: src/util/service.c:313 +#: src/util/service.c:320 #, fuzzy, c-format msgid "Wrong format `%s' for netmask\n" msgstr "Formato '%s' erróneo para la máscara de red: %s\n" -#: src/util/service.c:343 +#: src/util/service.c:350 #, fuzzy, c-format msgid "Wrong format `%s' for network\n" msgstr "Formato '%s' erróneo para la red: %s\n" -#: src/util/service.c:698 +#: src/util/service.c:707 #, c-format msgid "Access denied to UID %d / GID %d\n" msgstr "" -#: src/util/service.c:703 +#: src/util/service.c:712 #, fuzzy, c-format msgid "Unknown address family %d\n" msgstr "Operación desconocida '%s'\n" -#: src/util/service.c:710 +#: src/util/service.c:719 #, c-format msgid "Access from `%s' denied to service `%s'\n" msgstr "" -#: src/util/service.c:765 +#: src/util/service.c:774 #, c-format msgid "Could not parse IPv4 network specification `%s' for `%s:%s'\n" msgstr "" -#: src/util/service.c:802 +#: src/util/service.c:811 #, c-format msgid "Could not parse IPv6 network specification `%s' for `%s:%s'\n" msgstr "" -#: src/util/service.c:920 +#: src/util/service.c:929 #, c-format msgid "" "Disabling IPv6 support for service `%s', failed to create IPv6 socket: %s\n" msgstr "" -#: src/util/service.c:990 +#: src/util/service.c:1007 #, c-format msgid "" "Disabling UNIX domain socket support for service `%s', failed to create UNIX " "domain socket: %s\n" msgstr "" -#: src/util/service.c:1007 +#: src/util/service.c:1024 #, c-format msgid "Have neither PORT nor UNIXPATH for service `%s', but one is required\n" msgstr "" -#: src/util/service.c:1241 +#: src/util/service.c:1258 msgid "Could not access a pre-bound socket, will try to bind myself\n" msgstr "" -#: src/util/service.c:1292 src/util/service.c:1310 +#: src/util/service.c:1309 src/util/service.c:1327 #, c-format msgid "Specified value for `%s' of service `%s' is invalid\n" msgstr "" -#: src/util/service.c:1337 +#: src/util/service.c:1354 #, c-format msgid "Could not access pre-bound socket %u, will try to bind myself\n" msgstr "" -#: src/util/service.c:1506 +#: src/util/service.c:1525 #, fuzzy, c-format msgid "Failed to start `%s' at `%s'\n" msgstr "Fallo al conectar a gnunetd.\n" -#: src/util/service.c:1539 +#: src/util/service.c:1558 #, fuzzy, c-format msgid "Service `%s' runs at %s\n" msgstr "Par '%s' con credibilidad %8u y dirección '%s'\n" -#: src/util/service.c:1588 +#: src/util/service.c:1607 msgid "Service process failed to initialize\n" msgstr "" -#: src/util/service.c:1592 +#: src/util/service.c:1611 msgid "Service process could not initialize server function\n" msgstr "" -#: src/util/service.c:1596 +#: src/util/service.c:1615 msgid "Service process failed to report status\n" msgstr "" -#: src/util/service.c:1651 +#: src/util/service.c:1670 msgid "No such user" msgstr "" -#: src/util/service.c:1664 +#: src/util/service.c:1683 #, c-format msgid "Cannot change user/group to `%s': %s\n" msgstr "Imposible cambiar el usuario/grupo a '%s': %s\n" -#: src/util/service.c:1729 +#: src/util/service.c:1749 msgid "do daemonize (detach from terminal)" msgstr "" @@ -5856,278 +6568,612 @@ msgstr "" msgid "signal (%d, %p) returned %d.\n" msgstr "La llamada a '%s' devuelve %d.\n" -#: src/util/strings.c:144 +#: src/util/strings.c:146 msgid "b" msgstr "b" -#: src/util/strings.c:334 +#: src/util/strings.c:413 #, c-format msgid "Character sets requested were `%s'->`%s'\n" msgstr "" -#: src/util/strings.c:481 +#: src/util/strings.c:528 msgid "Failed to expand `$HOME': environment variable `HOME' not set" msgstr "" -#: src/util/strings.c:573 +#: src/util/strings.c:625 msgid "ms" msgstr "ms" -#: src/util/strings.c:578 -msgid "eternity" -msgstr "" +#: src/util/strings.c:629 +msgid "forever" +msgstr "" + +#: src/util/strings.c:631 +msgid "0 ms" +msgstr "" + +#: src/util/strings.c:637 +msgid "s" +msgstr "s" + +#: src/util/strings.c:643 +msgid "m" +msgstr "m" + +#: src/util/strings.c:649 +msgid "h" +msgstr "h" + +#: src/util/strings.c:656 +#, fuzzy +msgid "day" +msgstr " días" + +#: src/util/strings.c:658 +#, fuzzy +msgid "days" +msgstr " días" + +#: src/util/strings.c:685 +msgid "end of time" +msgstr "" + +#: src/util/strings.c:1073 +msgid "IPv6 address did not start with `['\n" +msgstr "" + +#: src/util/strings.c:1081 +msgid "IPv6 address did contain ':' to separate port number\n" +msgstr "" + +#: src/util/strings.c:1087 +msgid "IPv6 address did contain ']' before ':' to separate port number\n" +msgstr "" + +#: src/util/strings.c:1094 +msgid "IPv6 address did contain a valid port number after the last ':'\n" +msgstr "" + +#: src/util/strings.c:1103 +#, fuzzy, c-format +msgid "Invalid IPv6 address `%s': %s\n" +msgstr "Argumento no válido: '%s'\n" + +#: src/vpn/gnunet-service-vpn.c:512 src/vpn/gnunet-service-vpn.c:1088 +#, fuzzy +msgid "# Active tunnels" +msgstr "Configuración de GNUnet" + +#: src/vpn/gnunet-service-vpn.c:609 src/vpn/gnunet-service-vpn.c:646 +#, fuzzy +msgid "# peers connected to mesh tunnels" +msgstr "# de pares conectados" + +#: src/vpn/gnunet-service-vpn.c:699 +#, fuzzy +msgid "# Bytes given to mesh for transmission" +msgstr "# bytes de mensajes salientes omitidos" + +#: src/vpn/gnunet-service-vpn.c:737 +#, fuzzy +msgid "# Bytes dropped in mesh queue (overflow)" +msgstr "# bytes omitidos por UDP (salientes)" + +#: src/vpn/gnunet-service-vpn.c:771 +#, fuzzy +msgid "# Mesh tunnels created" +msgstr "# mensajes PONG encriptados recibidos" + +#: src/vpn/gnunet-service-vpn.c:794 +#, fuzzy +msgid "Failed to setup mesh tunnel!\n" +msgstr "Fallo en las estadísticas del tráfico.\n" + +#: src/vpn/gnunet-service-vpn.c:990 +#, c-format +msgid "Protocol %u not supported, dropping\n" +msgstr "" + +#: src/vpn/gnunet-service-vpn.c:1308 +msgid "# ICMPv4 packets dropped (not allowed)" +msgstr "" + +#: src/vpn/gnunet-service-vpn.c:1329 +msgid "# ICMPv6 packets dropped (not allowed)" +msgstr "" + +#: src/vpn/gnunet-service-vpn.c:1534 +#, fuzzy +msgid "# Packets received from TUN interface" +msgstr "El mensaje recibido del cliente es inválido\n" + +#: src/vpn/gnunet-service-vpn.c:1572 src/vpn/gnunet-service-vpn.c:1613 +#, c-format +msgid "Packet received for unmapped destination `%s' (dropping it)\n" +msgstr "" + +#: src/vpn/gnunet-service-vpn.c:1623 +msgid "Received IPv4 packet with options (dropping it)\n" +msgstr "" + +#: src/vpn/gnunet-service-vpn.c:1637 +#, c-format +msgid "Received packet of unknown protocol %d from TUN (dropping it)\n" +msgstr "" + +#: src/vpn/gnunet-service-vpn.c:1721 +#, fuzzy +msgid "# ICMP packets received from mesh" +msgstr "El mensaje recibido del cliente es inválido\n" + +#: src/vpn/gnunet-service-vpn.c:2062 +#, fuzzy +msgid "# UDP packets received from mesh" +msgstr "El mensaje recibido del cliente es inválido\n" + +#: src/vpn/gnunet-service-vpn.c:2220 +#, fuzzy +msgid "# TCP packets received from mesh" +msgstr "El mensaje recibido del cliente es inválido\n" + +#: src/vpn/gnunet-service-vpn.c:2371 +msgid "Failed to find unallocated IPv4 address in VPN's range\n" +msgstr "" + +#: src/vpn/gnunet-service-vpn.c:2426 +#, fuzzy +msgid "Failed to find unallocated IPv6 address in VPN's range\n" +msgstr "¡Falló al obtener mi dirección IPv6 (externa)!\n" + +#: src/vpn/gnunet-service-vpn.c:2465 src/vpn/gnunet-service-vpn.c:2678 +#, fuzzy +msgid "# Active destinations" +msgstr "Configuración de GNUnet" + +#: src/vpn/gnunet-service-vpn.c:2751 +msgid "Failed to allocate IP address for new destination\n" +msgstr "" + +#: src/vpn/gnunet-service-vpn.c:3138 +msgid "IPv6 support disabled as this system does not support IPv6\n" +msgstr "" + +#: src/vpn/gnunet-service-vpn.c:3170 +msgid "IPv4 support disabled as this system does not support IPv4\n" +msgstr "" + +#: src/vpn/gnunet-vpn.c:151 +#, fuzzy +msgid "Error creating tunnel\n" +msgstr "Correcto al crear la clave local.\n" + +#: src/vpn/gnunet-vpn.c:194 src/vpn/gnunet-vpn.c:225 +#, fuzzy, c-format +msgid "Option `%s' makes no sense with option `%s'.\n" +msgstr "La opción '%s' no tiene sentido sin la opción '%s'.\n" + +#: src/vpn/gnunet-vpn.c:207 +#, fuzzy, c-format +msgid "Option `%s' or `%s' is required.\n" +msgstr "%s: la opción '%s' es ambigua\n" + +#: src/vpn/gnunet-vpn.c:219 +#, fuzzy, c-format +msgid "Option `%s' or `%s' is required when using option `%s'.\n" +msgstr "La opción '%s' no tiene sentido sin la opción '%s'.\n" + +#: src/vpn/gnunet-vpn.c:237 +#, fuzzy, c-format +msgid "`%s' is not a valid peer identifier.\n" +msgstr "'%s' no esta disponible." + +#: src/vpn/gnunet-vpn.c:259 +#, fuzzy, c-format +msgid "`%s' is not a valid IP address.\n" +msgstr "'%s' no esta disponible." + +#: src/vpn/gnunet-vpn.c:295 +msgid "request that result should be an IPv4 address" +msgstr "" + +#: src/vpn/gnunet-vpn.c:298 +msgid "request that result should be an IPv6 address" +msgstr "" + +#: src/vpn/gnunet-vpn.c:301 +msgid "print IP address only after mesh tunnel has been created" +msgstr "" + +#: src/vpn/gnunet-vpn.c:304 +msgid "how long should the mapping be valid for new tunnels?" +msgstr "" + +#: src/vpn/gnunet-vpn.c:307 +msgid "destination IP for the tunnel" +msgstr "" + +#: src/vpn/gnunet-vpn.c:310 +msgid "peer offering the service we would like to access" +msgstr "" + +#: src/vpn/gnunet-vpn.c:313 +msgid "name of the service we would like to access" +msgstr "" + +#: src/vpn/gnunet-vpn.c:316 +#, fuzzy +msgid "service is offered via TCP" +msgstr "# bytes recibidos por TCP" + +#: src/vpn/gnunet-vpn.c:319 +#, fuzzy +msgid "service is offered via UDP" +msgstr "# bytes recibidos vía UDP" + +#: src/vpn/gnunet-vpn.c:331 +msgid "Setup tunnels via VPN." +msgstr "" + +#: src/include/gnunet_common.h:579 src/include/gnunet_common.h:584 +#: src/include/gnunet_common.h:590 +#, fuzzy, c-format +msgid "Assertion failed at %s:%d.\n" +msgstr "La verificación de la firma RSA fallo en %s: %d: %s\n" + +#: src/include/gnunet_common.h:600 +#, fuzzy, c-format +msgid "External protocol violation detected at %s:%d.\n" +msgstr "La verificación de la firma RSA fallo en %s: %d: %s\n" + +#: src/include/gnunet_common.h:621 src/include/gnunet_common.h:628 +#, fuzzy, c-format +msgid "`%s' failed on file `%s' at %s:%d with error: %s\n" +msgstr "'%s' falló en el fichero '%s' en %s: %d con el error: %s\n" + +#, fuzzy +#~ msgid "session identifier" +#~ msgstr "# sesiones establecidas" + +#, fuzzy +#~ msgid "Mesh service could not access hostkey. Exiting.\n" +#~ msgstr "Imposible acceder a la información del espacio.\n" + +#, fuzzy +#~ msgid "" +#~ "provide inthe 'struct GNUNET_TRANSPORT_PeerIterateContextformation about " +#~ "all tunnels (continuously)" +#~ msgstr "Imprime información de los pares de GNUnet." + +#, fuzzy +#~ msgid "Connected to %s\n" +#~ msgstr "'%s' conectado a '%s'.\n" + +#, fuzzy +#~ msgid "list information for all peers" +#~ msgstr "Imprime información de los pares de GNUnet." + +#, fuzzy +#~ msgid "Malformed %s `%s' given in configuration!\n" +#~ msgstr "Imposible guardar la configuración" + +#, fuzzy +#~ msgid "I am host `%s'. Read private key from `%s'.\n" +#~ msgstr "Llamada a '%s' con la clave '%s'.\n" + +#, fuzzy +#~ msgid "Got %u bytes from helper `%s'\n" +#~ msgstr "GAP recibido contenido no válido de '%s'\n" + +#, fuzzy +#~ msgid "Starting HELPER process `%s'\n" +#~ msgstr "Iniciada colección '%s'.\n" + +#, fuzzy +#~ msgid "Error receiving response to `%s' request from ARM for service `%s'\n" +#~ msgstr "Recibida respuesta anómala a'%s' del par '%s'.\n" + +#, fuzzy +#~ msgid "Asked to start service `%s' within %llu ms\n" +#~ msgstr "'%s': No se recibió el mensaje en %llu ms.\n" + +#, fuzzy +#~ msgid "Stopping service `%s' within %llu ms\n" +#~ msgstr "No se ha recibido una respuesta en %llums.\n" + +#, fuzzy +#~ msgid "Configuration file `%s' for service `%s' not valid: %s\n" +#~ msgstr "Fichero de configuración '%s' creado.\n" + +#, fuzzy +#~ msgid "Could not transmit confirmation receipt\n" +#~ msgstr "Imposible acceder a la información del espacio.\n" + +#, fuzzy +#~ msgid "Unknown message type: '%u'\n" +#~ msgstr "Operación desconocida '%s'\n" + +#, fuzzy +#~ msgid "Configuration option `%s' in section `%s' missing\n" +#~ msgstr "Fichero de configuración '%s' creado.\n" + +#, fuzzy +#~ msgid "Failed to access chat home directory `%s'\n" +#~ msgstr "Error en el formato del fichero (¿no es un directorio de GNUnet?)\n" + +#, fuzzy +#~ msgid "Failed to create/open key in file `%s'\n" +#~ msgstr "Fichero almacenado en '%s'.\n" + +#, fuzzy +#~ msgid "Could not serialize metadata\n" +#~ msgstr "¡Imposible inicializar libgnunetutil!\n" + +#, fuzzy +#~ msgid "Failed to connect to the chat service\n" +#~ msgstr "Fallo al conectar a gnunetd.\n" + +#, fuzzy +#~ msgid "(%s) `%s' said: %s\n" +#~ msgstr "'%s' %s falló: %s\n" + +#, fuzzy +#~ msgid "(%s) `%s' said to you: %s\n" +#~ msgstr "'%s' %s falló: %s\n" + +#, fuzzy +#~ msgid "(%s) `%s' said for sure: %s\n" +#~ msgstr "'%s' %s falló: %s\n" + +#, fuzzy +#~ msgid "(%s) `%s' said to you for sure: %s\n" +#~ msgstr "'%s' falló con el código de error %s: %s" + +#, fuzzy +#~ msgid "(%s) `%s' was confirmed that you received: %s\n" +#~ msgstr "'%s' falló con el código de error %d: %s" + +#, fuzzy +#~ msgid "(%s) `%s' was confirmed that you and only you received: %s\n" +#~ msgstr "'%s' falló con el código de error %d: %s" + +#, fuzzy +#~ msgid "(%s) `%s' was confirmed that you received from him or her: %s\n" +#~ msgstr "'%s' falló con el código de error %d: %s" + +#, fuzzy +#~ msgid "" +#~ "(%s) `%s' was confirmed that you and only you received from him or her: " +#~ "%s\n" +#~ msgstr "'%s' falló con el código de error %d: %s" -#: src/util/strings.c:582 -msgid "s" -msgstr "s" +#, fuzzy +#~ msgid "(%s) `%s' said off the record: %s\n" +#~ msgstr "'%s' falló con el código de error %s: %s" -#: src/util/strings.c:586 -msgid "m" -msgstr "m" +#, fuzzy +#~ msgid "Could not change username\n" +#~ msgstr "Imposible crear el espacio '%s' (¿existe?).\n" -#: src/util/strings.c:590 -msgid "h" -msgstr "h" +#, fuzzy +#~ msgid "Joining room `%s' as user `%s'...\n" +#~ msgstr "Respuesta inválida a '%s' del par '%s'.\n" -#: src/util/strings.c:594 -msgid " days" -msgstr " días" +#, fuzzy +#~ msgid "Changed username to `%s'\n" +#~ msgstr "Imposible cambiar el usuario/grupo a '%s': %s\n" -#: src/util/strings.c:618 -msgid "end of time" -msgstr "" +#, fuzzy +#~ msgid "Users in room `%s': " +#~ msgstr "Fichero almacenado en '%s'.\n" -#: src/util/strings.c:1012 -msgid "IPv6 address did not start with `['\n" -msgstr "" +#, fuzzy +#~ msgid "Unknown command `%s'\n" +#~ msgstr "Operación desconocida '%s'\n" -#: src/util/strings.c:1020 -msgid "IPv6 address did contain ':' to separate port number\n" -msgstr "" +#, fuzzy +#~ msgid "You must specify a nickname\n" +#~ msgstr "¡Debes especificar un receptor!\n" -#: src/util/strings.c:1026 -msgid "IPv6 address did contain ']' before ':' to separate port number\n" -msgstr "" +#, fuzzy +#~ msgid "Failed to join room `%s'\n" +#~ msgstr "Fichero almacenado en '%s'.\n" -#: src/util/strings.c:1033 -msgid "IPv6 address did contain a valid port number after the last ':'\n" -msgstr "" +#, fuzzy +#~ msgid "Failed to queue a message notification\n" +#~ msgstr "Imposible guardar la configuración" -#: src/util/strings.c:1042 -#, fuzzy, c-format -msgid "Invalid IPv6 address `%s': %s\n" -msgstr "Argumento no válido: '%s'\n" +#, fuzzy +#~ msgid "Failed to queue a join notification\n" +#~ msgstr "Imposible guardar la configuración" -#: src/vpn/gnunet-service-vpn.c:511 src/vpn/gnunet-service-vpn.c:1071 #, fuzzy -msgid "# Active tunnels" -msgstr "Configuración de GNUnet" +#~ msgid "Failed to queue a confirmation receipt\n" +#~ msgstr "Imposible guardar la configuración" -#: src/vpn/gnunet-service-vpn.c:608 src/vpn/gnunet-service-vpn.c:645 #, fuzzy -msgid "# peers connected to mesh tunnels" -msgstr "# de pares conectados" +#~ msgid "Failed to queue a leave notification\n" +#~ msgstr "Imposible guardar la configuración" -#: src/vpn/gnunet-service-vpn.c:699 #, fuzzy -msgid "# Bytes given to mesh for transmission" -msgstr "# bytes de mensajes salientes omitidos" +#~ msgid "Option `%s' in section `%s' missing in configuration!\n" +#~ msgstr "¡Ninguna aplicación definida en la configuración!\n" -#: src/vpn/gnunet-service-vpn.c:737 #, fuzzy -msgid "# Bytes dropped in mesh queue (overflow)" -msgstr "# bytes omitidos por UDP (salientes)" +#~ msgid "Connected to %s service!\n" +#~ msgstr "'%s' conectado a '%s'.\n" -#: src/vpn/gnunet-service-vpn.c:772 #, fuzzy -msgid "# Mesh tunnels created" -msgstr "# mensajes PONG encriptados recibidos" +#~ msgid "Configuration fails to specify `%s' in section `%s'\n" +#~ msgstr "" +#~ "El fichero de configuración debe especificar el directorio para almacenar " +#~ "los datos FS en la sección '%s' bajo '%s'.\n" -#: src/vpn/gnunet-service-vpn.c:795 #, fuzzy -msgid "Failed to setup mesh tunnel!\n" -msgstr "Fallo en las estadísticas del tráfico.\n" +#~ msgid "Failed to start daemon: %s\n" +#~ msgstr "Falló al comenzar la recolección.\n" -#: src/vpn/gnunet-service-vpn.c:973 -#, c-format -msgid "Protocol %u not supported, dropping\n" -msgstr "" +#, fuzzy +#~ msgid "Configuration fails to specify `%s', assuming default value." +#~ msgstr "Fichero de configuración '%s' creado.\n" -#: src/vpn/gnunet-service-vpn.c:1291 -msgid "# ICMPv4 packets dropped (not allowed)" -msgstr "" +#, fuzzy +#~ msgid "Key file `%s' for private zone does not exist!\n" +#~ msgstr "número de mensajes a usar por iteración" -#: src/vpn/gnunet-service-vpn.c:1312 -msgid "# ICMPv6 packets dropped (not allowed)" -msgstr "" +#, fuzzy +#~ msgid "Option `%s' not specified in configuration section `%s'\n" +#~ msgstr "¡Ninguna aplicación definida en la configuración!\n" -#: src/vpn/gnunet-service-vpn.c:1517 #, fuzzy -msgid "# Packets received from TUN interface" -msgstr "El mensaje recibido del cliente es inválido\n" +#~ msgid "Peer is lacking HOSTKEY configuration setting.\n" +#~ msgstr "Configuración de GNUnet" -#: src/vpn/gnunet-service-vpn.c:1555 src/vpn/gnunet-service-vpn.c:1596 -#, c-format -msgid "Packet received for unmapped destination `%s' (dropping it)\n" -msgstr "" +#, fuzzy +#~ msgid "Could not access hostkey.\n" +#~ msgstr "Imposible pasar el fichero de configuración '%s'.\n" -#: src/vpn/gnunet-service-vpn.c:1606 -msgid "Received IPv4 packet with options (dropping it)\n" -msgstr "" +#, fuzzy +#~ msgid "`scp' did not complete cleanly.\n" +#~ msgstr "'%s' no esta conectado a ningún par.\n" -#: src/vpn/gnunet-service-vpn.c:1620 -#, c-format -msgid "Received packet of unknown protocol %d from TUN (dropping it)\n" -msgstr "" +#, fuzzy +#~ msgid "Failed to create pipe for `gnunet-peerinfo' process.\n" +#~ msgstr "Falló al comenzar la recolección.\n" -#: src/vpn/gnunet-service-vpn.c:1704 #, fuzzy -msgid "# ICMP packets received from mesh" -msgstr "El mensaje recibido del cliente es inválido\n" +#~ msgid "Failed to create pipe for `ssh' process.\n" +#~ msgstr "Error en el formato del fichero (¿no es un directorio de GNUnet?)\n" -#: src/vpn/gnunet-service-vpn.c:2045 #, fuzzy -msgid "# UDP packets received from mesh" -msgstr "El mensaje recibido del cliente es inválido\n" +#~ msgid "Could not start `%s' process to create hostkey.\n" +#~ msgstr "Imposible mandar el mensaje a gnunetd\n" -#: src/vpn/gnunet-service-vpn.c:2203 #, fuzzy -msgid "# TCP packets received from mesh" -msgstr "El mensaje recibido del cliente es inválido\n" +#~ msgid "Failed to start `gnunet-peerinfo' process.\n" +#~ msgstr "Falló al comenzar la recolección.\n" -#: src/vpn/gnunet-service-vpn.c:2354 -msgid "Failed to find unallocated IPv4 address in VPN's range\n" -msgstr "" +#, fuzzy +#~ msgid "Failed to start `ssh' process.\n" +#~ msgstr "Falló al comenzar la recolección.\n" -#: src/vpn/gnunet-service-vpn.c:2409 #, fuzzy -msgid "Failed to find unallocated IPv6 address in VPN's range\n" -msgstr "¡Falló al obtener mi dirección IPv6 (externa)!\n" +#~ msgid "Error reading from gnunet-peerinfo: %s\n" +#~ msgstr "Se produjo un error leyendo información de gnunetd.\n" -#: src/vpn/gnunet-service-vpn.c:2448 src/vpn/gnunet-service-vpn.c:2661 #, fuzzy -msgid "# Active destinations" -msgstr "Configuración de GNUnet" +#~ msgid "Malformed output from gnunet-peerinfo!\n" +#~ msgstr "Se produjo un error leyendo información de gnunetd.\n" -#: src/vpn/gnunet-service-vpn.c:2734 -msgid "Failed to allocate IP address for new destination\n" -msgstr "" +#, fuzzy +#~ msgid "Failed to get hostkey!\n" +#~ msgstr "Fallo en las estadísticas del tráfico.\n" -#: src/vpn/gnunet-service-vpn.c:3141 -msgid "IPv6 support disabled as this system does not support IPv6\n" -msgstr "" +#, fuzzy +#~ msgid "Could not start `%s' process to start GNUnet.\n" +#~ msgstr "Imposible crear el espacio '%s' (¿existe?).\n" -#: src/vpn/gnunet-service-vpn.c:3173 -msgid "IPv4 support disabled as this system does not support IPv4\n" -msgstr "" +#, fuzzy +#~ msgid "Failed to start `gnunet-arm' process.\n" +#~ msgstr "Fallo al conectar a gnunetd.\n" -#: src/vpn/gnunet-vpn.c:151 #, fuzzy -msgid "Error creating tunnel\n" -msgstr "Correcto al crear la clave local.\n" +#~ msgid "shutdown (either `gnunet-arm' or `ssh') did not complete cleanly.\n" +#~ msgstr "'%s' no esta conectado a ningún par.\n" -#: src/vpn/gnunet-vpn.c:195 src/vpn/gnunet-vpn.c:226 -#, fuzzy, c-format -msgid "Option `%s' makes no sense with option `%s'.\n" -msgstr "La opción '%s' no tiene sentido sin la opción '%s'.\n" +#, fuzzy +#~ msgid "Starting service %s for peer `%4s'\n" +#~ msgstr "Iniciada colección '%s'.\n" -#: src/vpn/gnunet-vpn.c:208 -#, fuzzy, c-format -msgid "Option `%s' or `%s' is required.\n" -msgstr "%s: la opción '%s' es ambigua\n" +#, fuzzy +#~ msgid "Could not start `%s' process to copy configuration directory.\n" +#~ msgstr "Imposible acceder a la información del espacio.\n" -#: src/vpn/gnunet-vpn.c:220 -#, fuzzy, c-format -msgid "Option `%s' or `%s' is required when using option `%s'.\n" -msgstr "La opción '%s' no tiene sentido sin la opción '%s'.\n" +#, fuzzy +#~ msgid "Terminating peer `%4s'\n" +#~ msgstr "Permiso denegado para '%s' en %s:%d.\n" -#: src/vpn/gnunet-vpn.c:238 -#, fuzzy, c-format -msgid "`%s' is not a valid peer identifier.\n" -msgstr "'%s' no esta disponible." +#, fuzzy +#~ msgid "Setting d->dead on peer `%4s'\n" +#~ msgstr "Iniciada colección '%s'.\n" -#: src/vpn/gnunet-vpn.c:260 -#, fuzzy, c-format -msgid "`%s' is not a valid IP address.\n" -msgstr "'%s' no esta disponible." +#, fuzzy +#~ msgid "Failed to write new configuration to disk." +#~ msgstr "Imposible guardar la configuración" -#: src/vpn/gnunet-vpn.c:296 -msgid "request that result should be an IPv4 address" -msgstr "" +#, fuzzy +#~ msgid "Could not start `%s' process to copy configuration file.\n" +#~ msgstr "¡Imposible encontrar el par '%s' en la tabla de enrutado!\n" -#: src/vpn/gnunet-vpn.c:299 -msgid "request that result should be an IPv6 address" -msgstr "" +#, fuzzy +#~ msgid "Failed to copy new configuration to remote machine." +#~ msgstr "Imposible guardar la configuración" -#: src/vpn/gnunet-vpn.c:302 -msgid "print IP address only after mesh tunnel has been created" -msgstr "" +#, fuzzy +#~ msgid "Peers failed to connect" +#~ msgstr "Fallo al conectar a gnunetd.\n" -#: src/vpn/gnunet-vpn.c:305 -msgid "how long should the mapping be valid for new tunnels?" -msgstr "" +#, fuzzy +#~ msgid "Failed to connect to core service of first peer!\n" +#~ msgstr "Fallo al conectar a gnunetd.\n" -#: src/vpn/gnunet-vpn.c:308 -msgid "destination IP for the tunnel" -msgstr "" +#, fuzzy +#~ msgid "Invalid value `%s' for option `%s' in section `%s': expected float\n" +#~ msgstr "" +#~ "El fichero de configuración debe especificar el directorio para almacenar " +#~ "los datos FS en la sección '%s' bajo '%s'.\n" -#: src/vpn/gnunet-vpn.c:311 -msgid "peer offering the service we would like to access" -msgstr "" +#, fuzzy +#~ msgid "Could not read hostkeys file `%s'!\n" +#~ msgstr "Imposible inicializar la aplicación '%s'\n" -#: src/vpn/gnunet-vpn.c:314 -msgid "name of the service we would like to access" -msgstr "" +#, fuzzy +#~ msgid "Could not create configuration for peer number %u on `%s'!\n" +#~ msgstr "Imposible acceder a la información del espacio.\n" -#: src/vpn/gnunet-vpn.c:317 #, fuzzy -msgid "service is offered via TCP" -msgstr "# bytes recibidos por TCP" +#~ msgid "Failed to find option %s in section %s!\n" +#~ msgstr "Fallo al conectar a gnunetd.\n" -#: src/vpn/gnunet-vpn.c:320 #, fuzzy -msgid "service is offered via UDP" -msgstr "# bytes recibidos vía UDP" +#~ msgid "Invalid configuration option `%s' in section `%s'\n" +#~ msgstr "Fichero de configuración '%s' creado.\n" -#: src/vpn/gnunet-vpn.c:329 -msgid "Setup tunnels via VPN." -msgstr "" +#, fuzzy +#~ msgid "Missing configuration option `%s' in section `%s'\n" +#~ msgstr "Fichero de configuración '%s' creado.\n" -#: src/include/gnunet_common.h:497 src/include/gnunet_common.h:502 -#: src/include/gnunet_common.h:508 -#, fuzzy, c-format -msgid "Assertion failed at %s:%d.\n" -msgstr "La verificación de la firma RSA fallo en %s: %d: %s\n" +#, fuzzy +#~ msgid "internal error" +#~ msgstr "Error desconocido.\n" -#: src/include/gnunet_common.h:518 -#, fuzzy, c-format -msgid "External protocol violation detected at %s:%d.\n" -msgstr "La verificación de la firma RSA fallo en %s: %d: %s\n" +#, fuzzy +#~ msgid "Could not create namespace `%s'\n" +#~ msgstr "Imposible crear el espacio '%s' (¿existe?).\n" -#: src/include/gnunet_common.h:539 src/include/gnunet_common.h:546 -#, fuzzy, c-format -msgid "`%s' failed on file `%s' at %s:%d with error: %s\n" -msgstr "'%s' falló en el fichero '%s' en %s: %d con el error: %s\n" +#, fuzzy +#~ msgid "Stored zonekey for zone `%s' in file `%s'\n" +#~ msgstr "Fichero almacenado en '%s'.\n" #, fuzzy -#~ msgid "Received malformed message via %s. Ignored.\n" -#~ msgstr "Recibido el mensaje '%s' con un mal formato. Omitiendo.\n" +#~ msgid "Namestore removed record successfully" +#~ msgstr "Servicio de GNUnet instalado satisfactoriamente.\n" #, fuzzy -#~ msgid "SMTP: `%s' failed: %s.\n" -#~ msgstr "'%s' %s falló: %s\n" +#~ msgid "Could not read hostkeys file, specify hostkey file with -H!\n" +#~ msgstr "Imposible inicializar la aplicación '%s'\n" #, fuzzy -#~ msgid "# bytes received via SMTP" -#~ msgstr "# bytes recibidos por TCP" +#~ msgid "Could not open hostkeys file: %s\n" +#~ msgstr "Imposible inicializar la aplicación '%s'\n" #, fuzzy -#~ msgid "# bytes sent via SMTP" -#~ msgstr "# bytes enviados por TCP" +#~ msgid "access (%s, X_OK) failed: %s\n" +#~ msgstr "'%s' %s falló: %s\n" #, fuzzy -#~ msgid "# bytes dropped by SMTP (outgoing)" -#~ msgstr "# bytes omitidos por TCP (salientes)" +#~ msgid "stat (%s) failed: %s\n" +#~ msgstr "'%s' %s falló: %s\n" #, fuzzy #~ msgid "# Peers connected" @@ -6165,10 +7211,6 @@ msgstr "'%s' falló en el fichero '%s' en %s: %d con el error: %s\n" #~ msgid "Finished copying all blacklist files!\n" #~ msgstr "Imposible inicializar la aplicación '%s'\n" -#, fuzzy -#~ msgid "Offering HELLO of peer %s to peer %s\n" -#~ msgstr "Imposible conectar a %u.%u.%u.%u:%u: %s\n" - #, fuzzy #~ msgid "Failed during blacklist file copying!\n" #~ msgstr "Falló al pasar los datos de la interfaz de '%s' de %s:%d.\n" @@ -6177,10 +7219,6 @@ msgstr "'%s' falló en el fichero '%s' en %s: %d con el error: %s\n" #~ msgid "# bytes payload received for other peers" #~ msgstr "# bytes recibidos por TCP" -#, fuzzy -#~ msgid "# fast reconnects failed" -#~ msgstr "# de pares conectados" - #, fuzzy #~ msgid "# peers disconnected due to timeout" #~ msgstr "# de pares conectados" @@ -6197,10 +7235,6 @@ msgstr "'%s' falló en el fichero '%s' en %s: %d con el error: %s\n" #~ msgid "# unexpected CONNECT_ACK messages" #~ msgstr "envia COUNT mensajes" -#, fuzzy -#~ msgid "# wlan session timeouts" -#~ msgstr "# claves de la sesión aceptadas" - #, fuzzy #~ msgid "# wlan session created" #~ msgstr "# claves de la sesión aceptadas" @@ -6279,10 +7313,6 @@ msgstr "'%s' falló en el fichero '%s' en %s: %d con el error: %s\n" #~ msgid "print the version number" #~ msgstr "imprime el número de versión" -#, fuzzy -#~ msgid "use configuration file FILENAME" -#~ msgstr "usa el fichero de configuración FILENAME" - #, fuzzy #~ msgid "Failed to stop service `%s'!\n" #~ msgstr "Fichero almacenado en '%s'.\n" @@ -6291,10 +7321,6 @@ msgstr "'%s' falló en el fichero '%s' en %s: %d con el error: %s\n" #~ msgid "Failed to start service `%s'!\n" #~ msgstr "Falló al comenzar la recolección.\n" -#, fuzzy -#~ msgid "Service `%s' is not running.\n" -#~ msgstr "'%s' no es un fichero.\n" - #, fuzzy #~ msgid "Binary implementing service `%s' not known!\n" #~ msgstr "La verificación de la firma falló: el par '%s' no es conocido.\n" @@ -6303,18 +7329,10 @@ msgstr "'%s' falló en el fichero '%s' en %s: %d con el error: %s\n" #~ msgid "Service `%s' stopped\n" #~ msgstr "Servicio eliminado.\n" -#, fuzzy -#~ msgid "Unable to start service `%s': %s\n" -#~ msgstr "Imposible guardar el fichero de configuración '%s':" - #, fuzzy #~ msgid "Unable to accept connection for service `%s': %s\n" #~ msgstr "Imposible guardar el fichero de configuración '%s':" -#, fuzzy -#~ msgid "Peer `%s' plugin: `%s' address `%s'\n" -#~ msgstr "Par '%s' con credibilidad %8u y dirección '%s'\n" - #~ msgid "KiB" #~ msgstr "KiB" @@ -6908,14 +7926,6 @@ msgstr "'%s' falló en el fichero '%s' en %s: %d con el error: %s\n" #~ msgid "Command `%s' failed with error code %u\n" #~ msgstr "'%s' falló con el código de error %s: %s" -#, fuzzy -#~ msgid "Invalid process priority `%s'\n" -#~ msgstr "Respuesta inválida a '%s'.\n" - -#, fuzzy -#~ msgid "`%s' failed with error code %d: %s\n" -#~ msgstr "'%s' falló con el código de error %d: %s" - #~ msgid "Availability test failed for `%s' at %s:%d.\n" #~ msgstr "Test de disponibilidad fallido para '%s' en %s:%d.\n" @@ -6949,9 +7959,6 @@ msgstr "'%s' falló en el fichero '%s' en %s: %d con el error: %s\n" #~ msgid "output in gnuplot format" #~ msgstr "salida en formato de gnuplot" -#~ msgid "number of iterations" -#~ msgstr "número de repeticiones" - #~ msgid "number of messages to use per iteration" #~ msgstr "número de mensajes a usar por iteración" @@ -7206,9 +8213,6 @@ msgstr "'%s' falló en el fichero '%s' en %s: %d con el error: %s\n" #~ msgid "Unknown type in embedded message from `%s': %u (size: %u)\n" #~ msgstr "Tipo desconocido en el mensaje embebido: %u (tamaño: %u)\n" -#~ msgid "# sessions established" -#~ msgstr "# sesiones establecidas" - #~ msgid "automate creation of a namespace by starting a collection" #~ msgstr "creación automática de un espacio al empezar una colección" @@ -7757,9 +8761,6 @@ msgstr "'%s' falló en el fichero '%s' en %s: %d con el error: %s\n" #~ msgid "send messages with SIZE bytes payload" #~ msgstr "manda mensajes con SIZE bytes payload" -#~ msgid "Testing transport(s) %s\n" -#~ msgstr "Probando transporte(s) %s\n" - #~ msgid "Available transport(s): %s\n" #~ msgstr "Transporte(s) disponible(s): %s\n" @@ -7887,10 +8888,6 @@ msgstr "'%s' falló en el fichero '%s' en %s: %d con el error: %s\n" #~ msgid "This is equivalent to the -H option. The format is IP:PORT." #~ msgstr "Muestra el valor de la opción" -#, fuzzy -#~ msgid "What is the path to the configuration file for gnunetd?" -#~ msgstr "Esta es la herramienta de configuración de GNUnet." - #, fuzzy #~ msgid "General options" #~ msgstr "Otras configuraciones" @@ -7921,10 +8918,6 @@ msgstr "'%s' falló en el fichero '%s' en %s: %d con el error: %s\n" #~ "El fichero '%s' en el directorio '%s' no sigue la convención de nombres. " #~ "Eliminando.\n" -#, fuzzy -#~ msgid "You must specify one and only one directory for sharing.\n" -#~ msgstr "Debes especificar uno y solo un fichero para desindexar.\n" - #~ msgid "" #~ "set interval for availability of updates to SECONDS (for namespace " #~ "insertions only)" @@ -8160,9 +9153,6 @@ msgstr "'%s' falló en el fichero '%s' en %s: %d con el error: %s\n" #~ msgid "Other settings" #~ msgstr "Otras configuraciones" -#~ msgid "Finish" -#~ msgstr "Finalizar" - #~ msgid "" #~ "Define the user and the group owning the GNUnet service here.\n" #~ "\n" @@ -8196,9 +9186,6 @@ msgstr "'%s' falló en el fichero '%s' en %s: %d con el error: %s\n" #~ msgid "Group:" #~ msgstr "Grupo:" -#~ msgid "gnunet-setup" -#~ msgstr "gnunet-setup" - #, fuzzy #~ msgid "Save configuration" #~ msgstr "Configuración de GNUnet" @@ -8240,9 +9227,6 @@ msgstr "'%s' falló en el fichero '%s' en %s: %d con el error: %s\n" #~ msgid "Download failed (no reason given)" #~ msgstr "La descarga del ERCS falló (vea los logs)." -#~ msgid "Maximum number of chat clients reached.\n" -#~ msgstr "Número máximo de clientes en el chat alcanzado.\n" - #~ msgid "Now %d of %d chat clients at this node.\n" #~ msgstr "Ahora hay %d de %d clientes de chat en este nodo.\n" @@ -8408,10 +9392,6 @@ msgstr "'%s' falló en el fichero '%s' en %s: %d con el error: %s\n" #~ msgid "Protocol violation on socket. Expected command.\n" #~ msgstr "Violación del protocolo en el socket. Esperando comando.\n" -#, fuzzy -#~ msgid "Start GNUnet testbed controller." -#~ msgstr "Arranca el cliente de chat de GNUnet" - #~ msgid "Malformed entry in the configuration in section %s under %s: %s\n" #~ msgstr "" #~ "Entrada mal formada en la configuración en la sección %s bajo %s: %s\n" @@ -8423,9 +9403,6 @@ msgstr "'%s' falló en el fichero '%s' en %s: %d con el error: %s\n" #~ msgstr "" #~ "TESTBED no puede generar el mensaje de saludo para el protocolo %u\n" -#~ msgid "received invalid `%s' message\n" -#~ msgstr "recibido mensaje '%s' no válido\n" - #~ msgid "received invalid `%s' message (empty module name)\n" #~ msgstr "recibido mensaje '%s' no válido (nombre del módulo vacío)\n" @@ -8607,9 +9584,6 @@ msgstr "'%s' falló en el fichero '%s' en %s: %d con el error: %s\n" #~ msgid "Invalid response to `%s' from `%s'\n" #~ msgstr "Respuesta inválida a '%s' de '%s'\n" -#~ msgid "Received invalid RPC `%s'.\n" -#~ msgstr "Recibido RPC '%s' inválida.\n" - #~ msgid "RPC for `%s' received for table that we do not participate in!\n" #~ msgstr "¡RPC para '%s' recibida de la tabla en la cual no participamos!\n" @@ -8728,9 +9702,6 @@ msgstr "'%s' falló en el fichero '%s' en %s: %d con el error: %s\n" #~ msgid "Joined DHT. Press CTRL-C to leave.\n" #~ msgstr "Unido a DHT. Pulsa CTRL-C para abandonarlo.\n" -#~ msgid "`%s' failed: table not found!\n" -#~ msgstr "'%s' falló: ¡tabla no encontrada!\n" - #~ msgid "sendAck failed. Terminating connection to client.\n" #~ msgstr "sendAck falló. Finalizando conexión con el cliente.\n" @@ -8854,9 +9825,6 @@ msgstr "'%s' falló en el fichero '%s' en %s: %d con el error: %s\n" #~ msgid "process directories recursively" #~ msgstr "procesa los directorios recursivamente" -#~ msgid "You must pass a positive number to the `%s' option.\n" -#~ msgstr "Debes pasar un número positivo a la opción '%s'.\n" - #~ msgid "Only one file or directory can be specified at a time.\n" #~ msgstr "Solo un fichero o un directorio puede ser especificado cada vez.\n" @@ -8900,13 +9868,6 @@ msgstr "'%s' falló en el fichero '%s' en %s: %d con el error: %s\n" #~ msgid "Option `%s' makes no sense without option `%s'." #~ msgstr "La opción '%s' no tiene ningún sentido sin la opción '%s'." -#~ msgid "" -#~ "\n" -#~ "Exiting.\n" -#~ msgstr "" -#~ "\n" -#~ "Saliendo.\n" - #~ msgid "Updated data for %d applications.\n" #~ msgstr "Actualizados los datos para %d aplicaciones.\n" diff --git a/po/gnunet.pot b/po/gnunet.pot index 652e579..327c4af 100644 --- a/po/gnunet.pot +++ b/po/gnunet.pot @@ -8,7 +8,7 @@ msgid "" msgstr "" "Project-Id-Version: PACKAGE VERSION\n" "Report-Msgid-Bugs-To: gnunet-developers@mail.gnu.org\n" -"POT-Creation-Date: 2012-06-05 15:47+0200\n" +"POT-Creation-Date: 2013-02-05 19:22+0100\n" "PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n" "Last-Translator: FULL NAME \n" "Language-Team: LANGUAGE \n" @@ -17,257 +17,206 @@ msgstr "" "Content-Type: text/plain; charset=CHARSET\n" "Content-Transfer-Encoding: 8bit\n" -#: src/arm/arm_api.c:165 +#: src/arm/arm_api.c:162 msgid "Failed to transmit shutdown request to client.\n" msgstr "" -#: src/arm/arm_api.c:349 -#, c-format -msgid "Configuration failes to specify option `%s' in section `%s'!\n" -msgstr "" - -#: src/arm/arm_api.c:363 -#, c-format -msgid "Configuration fails to specify option `%s' in section `%s'!\n" -msgstr "" - -#: src/arm/arm_api.c:432 -#, c-format -msgid "Error receiving response to `%s' request from ARM for service `%s'\n" -msgstr "" - -#: src/arm/arm_api.c:485 -#, c-format -msgid "Requesting start of service `%s'.\n" -msgstr "" - -#: src/arm/arm_api.c:486 -#, c-format -msgid "Requesting termination of service `%s'.\n" -msgstr "" - -#: src/arm/arm_api.c:507 -#, c-format -msgid "Error while trying to transmit request to start `%s' to ARM\n" -msgstr "" - -#: src/arm/arm_api.c:508 -#, c-format -msgid "Error while trying to transmit request to stop `%s' to ARM\n" -msgstr "" - -#: src/arm/arm_api.c:540 -#, c-format -msgid "Asked to start service `%s' within %llu ms\n" -msgstr "" - -#: src/arm/arm_api.c:612 -#, c-format -msgid "Stopping service `%s' within %llu ms\n" -msgstr "" - -#: src/arm/gnunet-arm.c:159 +#: src/arm/gnunet-arm.c:166 #, c-format msgid "Service `%s' is unknown to ARM.\n" msgstr "" -#: src/arm/gnunet-arm.c:164 +#: src/arm/gnunet-arm.c:171 #, c-format msgid "Service `%s' has been stopped.\n" msgstr "" -#: src/arm/gnunet-arm.c:167 +#: src/arm/gnunet-arm.c:174 #, c-format msgid "Service `%s' was already running.\n" msgstr "" -#: src/arm/gnunet-arm.c:172 +#: src/arm/gnunet-arm.c:179 #, c-format msgid "Service `%s' has been started.\n" msgstr "" -#: src/arm/gnunet-arm.c:175 +#: src/arm/gnunet-arm.c:182 #, c-format msgid "Service `%s' was already being stopped.\n" msgstr "" -#: src/arm/gnunet-arm.c:179 +#: src/arm/gnunet-arm.c:186 #, c-format msgid "Service `%s' was already not running.\n" msgstr "" -#: src/arm/gnunet-arm.c:183 +#: src/arm/gnunet-arm.c:190 msgid "Request ignored as ARM is shutting down.\n" msgstr "" -#: src/arm/gnunet-arm.c:187 +#: src/arm/gnunet-arm.c:194 msgid "Error communicating with ARM service.\n" msgstr "" -#: src/arm/gnunet-arm.c:191 +#: src/arm/gnunet-arm.c:198 msgid "Timeout communicating with ARM service.\n" msgstr "" -#: src/arm/gnunet-arm.c:195 +#: src/arm/gnunet-arm.c:202 msgid "Operation failed.\n" msgstr "" -#: src/arm/gnunet-arm.c:199 +#: src/arm/gnunet-arm.c:206 msgid "Unknown response code from ARM.\n" msgstr "" -#: src/arm/gnunet-arm.c:222 +#: src/arm/gnunet-arm.c:229 msgid "Error communicating with ARM. ARM not running?\n" msgstr "" -#: src/arm/gnunet-arm.c:225 +#: src/arm/gnunet-arm.c:232 msgid "Running services:\n" msgstr "" -#: src/arm/gnunet-arm.c:249 -#, c-format -msgid "Fatal configuration error: `%s' option in section `%s' missing.\n" -msgstr "" - -#: src/arm/gnunet-arm.c:257 src/arm/gnunet-arm.c:357 src/arm/gnunet-arm.c:373 -msgid "Fatal error initializing ARM API.\n" -msgstr "" - -#: src/arm/gnunet-arm.c:280 +#: src/arm/gnunet-arm.c:253 #, c-format msgid "Failed to remove configuration file %s\n" msgstr "" -#: src/arm/gnunet-arm.c:286 +#: src/arm/gnunet-arm.c:259 #, c-format msgid "Failed to remove servicehome directory %s\n" msgstr "" -#: src/arm/gnunet-arm.c:407 +#: src/arm/gnunet-arm.c:322 src/arm/gnunet-arm.c:407 src/arm/gnunet-arm.c:424 +msgid "Fatal error initializing ARM API.\n" +msgstr "" + +#: src/arm/gnunet-arm.c:453 msgid "stop all GNUnet services" msgstr "" -#: src/arm/gnunet-arm.c:409 +#: src/arm/gnunet-arm.c:455 msgid "start a particular service" msgstr "" -#: src/arm/gnunet-arm.c:411 +#: src/arm/gnunet-arm.c:457 msgid "stop a particular service" msgstr "" -#: src/arm/gnunet-arm.c:413 +#: src/arm/gnunet-arm.c:459 msgid "start all GNUnet default services" msgstr "" -#: src/arm/gnunet-arm.c:416 +#: src/arm/gnunet-arm.c:462 msgid "stop and start all GNUnet default services" msgstr "" -#: src/arm/gnunet-arm.c:419 +#: src/arm/gnunet-arm.c:465 msgid "delete config file and directory on exit" msgstr "" -#: src/arm/gnunet-arm.c:421 +#: src/arm/gnunet-arm.c:467 msgid "don't print status messages" msgstr "" -#: src/arm/gnunet-arm.c:424 -msgid "timeout for completing current operation" +#: src/arm/gnunet-arm.c:470 +msgid "timeout in MSECS milliseconds for completing current operation" +msgstr "" + +#: src/arm/gnunet-arm.c:472 +msgid "list currently running services" +msgstr "" + +#: src/arm/gnunet-arm.c:474 +msgid "don't let gnunet-service-arm inherit standard output" msgstr "" -#: src/arm/gnunet-arm.c:426 -msgid "List currently running services" +#: src/arm/gnunet-arm.c:476 +msgid "don't let gnunet-service-arm inherit standard error" msgstr "" -#: src/arm/gnunet-arm.c:437 +#: src/arm/gnunet-arm.c:487 msgid "Control services and the Automated Restart Manager (ARM)" msgstr "" -#: src/arm/gnunet-service-arm.c:332 +#: src/arm/gnunet-service-arm.c:345 #, c-format msgid "Failed to start service `%s'\n" msgstr "" -#: src/arm/gnunet-service-arm.c:335 +#: src/arm/gnunet-service-arm.c:348 #, c-format msgid "Starting service `%s'\n" msgstr "" -#: src/arm/gnunet-service-arm.c:361 +#: src/arm/gnunet-service-arm.c:374 msgid "Could not send status result to client\n" msgstr "" -#: src/arm/gnunet-service-arm.c:393 +#: src/arm/gnunet-service-arm.c:406 msgid "Could not send list result to client\n" msgstr "" -#: src/arm/gnunet-service-arm.c:523 +#: src/arm/gnunet-service-arm.c:537 #, c-format msgid "Unable to create socket for service `%s': %s\n" msgstr "" -#: src/arm/gnunet-service-arm.c:545 +#: src/arm/gnunet-service-arm.c:559 #, c-format msgid "Unable to bind listening socket for service `%s' to address `%s': %s\n" msgstr "" -#: src/arm/gnunet-service-arm.c:559 +#: src/arm/gnunet-service-arm.c:573 #, c-format msgid "ARM now monitors connections to service `%s' at `%s'\n" msgstr "" -#: src/arm/gnunet-service-arm.c:667 +#: src/arm/gnunet-service-arm.c:681 #, c-format msgid "Preparing to stop `%s'\n" msgstr "" -#: src/arm/gnunet-service-arm.c:878 +#: src/arm/gnunet-service-arm.c:892 #, c-format msgid "Restarting service `%s'.\n" msgstr "" -#: src/arm/gnunet-service-arm.c:970 +#: src/arm/gnunet-service-arm.c:985 msgid "exit" msgstr "" -#: src/arm/gnunet-service-arm.c:975 +#: src/arm/gnunet-service-arm.c:990 msgid "signal" msgstr "" -#: src/arm/gnunet-service-arm.c:980 +#: src/arm/gnunet-service-arm.c:995 msgid "unknown" msgstr "" -#: src/arm/gnunet-service-arm.c:986 +#: src/arm/gnunet-service-arm.c:1001 #, c-format -msgid "Service `%s' took %llu ms to terminate\n" +msgid "Service `%s' took %s to terminate\n" msgstr "" -#: src/arm/gnunet-service-arm.c:1021 +#: src/arm/gnunet-service-arm.c:1036 #, c-format msgid "Service `%s' terminated with status %s/%d, will restart in %llu ms\n" msgstr "" -#: src/arm/gnunet-service-arm.c:1127 -#, c-format -msgid "Configuration file `%s' for service `%s' not valid: %s\n" -msgstr "" - -#: src/arm/gnunet-service-arm.c:1129 -msgid "option missing" -msgstr "" - -#: src/arm/gnunet-service-arm.c:1213 +#: src/arm/gnunet-service-arm.c:1228 #, c-format msgid "Starting default services `%s'\n" msgstr "" -#: src/arm/gnunet-service-arm.c:1224 +#: src/arm/gnunet-service-arm.c:1239 #, c-format msgid "Default service `%s' not configured correctly!\n" msgstr "" -#: src/arm/gnunet-service-arm.c:1238 +#: src/arm/gnunet-service-arm.c:1253 msgid "" "No default services configured, GNUnet will not really start right now.\n" msgstr "" @@ -276,289 +225,248 @@ msgstr "" msgid "Initiating shutdown as requested by client.\n" msgstr "" -#: src/block/block.c:105 -#, c-format -msgid "Loading block plugin `%s'\n" -msgstr "" - -#: src/chat/chat.c:175 -msgid "Could not transmit confirmation receipt\n" -msgstr "" - -#: src/chat/chat.c:283 -msgid "The current user must be the the first one joined\n" -msgstr "" - -#: src/chat/chat.c:412 +#: src/ats/ats_api_performance.c:465 #, c-format -msgid "Unknown message type: '%u'\n" +msgid "Received %s message\n" msgstr "" -#: src/chat/chat.c:472 +#: src/ats/ats_api_performance.c:508 #, c-format -msgid "Configuration option `%s' in section `%s' missing\n" +msgid "Received last message for %s \n" msgstr "" -#: src/chat/chat.c:480 +#: src/ats/gnunet-service-ats_addresses.c:993 +#: src/ats/gnunet-service-ats_addresses.c:1027 #, c-format -msgid "Failed to access chat home directory `%s'\n" +msgid "" +"Could not load quota for network `%s': `%s', assigning default bandwidth " +"%llu\n" msgstr "" -#: src/chat/chat.c:498 +#: src/ats/gnunet-service-ats_addresses.c:999 #, c-format -msgid "Failed to create/open key in file `%s'\n" -msgstr "" - -#: src/chat/chat.c:559 -msgid "Could not serialize metadata\n" -msgstr "" - -#: src/chat/chat.c:674 -msgid "Failed to connect to the chat service\n" +msgid "Outbound quota configure for network `%s' is %llu\n" msgstr "" -#: src/chat/chat.c:680 -msgid "Undefined mandatory parameter: joinCallback\n" -msgstr "" - -#: src/chat/chat.c:686 -msgid "Undefined mandatory parameter: messageCallback\n" -msgstr "" - -#: src/chat/chat.c:692 -msgid "Undefined mandatory parameter: memberCallback\n" -msgstr "" - -#: src/chat/gnunet-chat.c:93 -msgid "Joined\n" -msgstr "" - -#: src/chat/gnunet-chat.c:125 src/chat/gnunet-chat.c:133 -#: src/chat/gnunet-chat.c:213 src/chat/gnunet-chat.c:253 -#: src/chat/gnunet-chat.c:329 src/chat/gnunet-chat.c:371 -#: src/chat/gnunet-chat.c:400 src/chat/gnunet-chat.c:700 -msgid "anonymous" -msgstr "" - -#: src/chat/gnunet-chat.c:144 +#: src/ats/gnunet-service-ats_addresses.c:1006 #, c-format -msgid "(%s) `%s' said: %s\n" +msgid "" +"No outbound quota configured for network `%s', assigning default bandwidth " +"%llu\n" msgstr "" -#: src/chat/gnunet-chat.c:147 src/chat/gnunet-chat.c:150 +#: src/ats/gnunet-service-ats_addresses.c:1033 #, c-format -msgid "(%s) `%s' said to you: %s\n" +msgid "Inbound quota configured for network `%s' is %llu\n" msgstr "" -#: src/chat/gnunet-chat.c:153 +#: src/ats/gnunet-service-ats_addresses.c:1040 #, c-format -msgid "(%s) `%s' said for sure: %s\n" +msgid "" +"No outbound quota configure for network `%s', assigning default bandwidth " +"%llu\n" msgstr "" -#: src/chat/gnunet-chat.c:156 +#: src/ats-tool/gnunet-ats.c:141 #, c-format -msgid "(%s) `%s' said to you for sure: %s\n" +msgid "%u address resolutions had a timeout\n" msgstr "" -#: src/chat/gnunet-chat.c:159 +#: src/ats-tool/gnunet-ats.c:143 #, c-format -msgid "(%s) `%s' was confirmed that you received: %s\n" +msgid "ATS returned results for %u addresses\n" msgstr "" -#: src/chat/gnunet-chat.c:162 +#: src/ats-tool/gnunet-ats.c:199 #, c-format -msgid "(%s) `%s' was confirmed that you and only you received: %s\n" +msgid "" +"Peer `%s' plugin `%s', address `%s', `%s' bw out: %u Bytes/s, bw in %u Bytes/" +"s, %s\n" msgstr "" -#: src/chat/gnunet-chat.c:165 +#: src/ats-tool/gnunet-ats.c:326 #, c-format -msgid "(%s) `%s' was confirmed that you received from him or her: %s\n" +msgid "Quota for network `%11s' (in/out): %10s / %10s\n" msgstr "" -#: src/chat/gnunet-chat.c:170 +#: src/ats-tool/gnunet-ats.c:345 src/namestore/gnunet-namestore.c:610 +#: src/transport/gnunet-transport.c:813 #, c-format -msgid "" -"(%s) `%s' was confirmed that you and only you received from him or her: %s\n" +msgid "Service `%s' is not running\n" msgstr "" -#: src/chat/gnunet-chat.c:173 +#: src/ats-tool/gnunet-ats.c:355 src/transport/gnunet-transport.c:819 #, c-format -msgid "(%s) `%s' said off the record: %s\n" +msgid "Failed to parse peer identity `%s'\n" msgstr "" -#: src/chat/gnunet-chat.c:176 +#: src/ats-tool/gnunet-ats.c:363 #, c-format -msgid "(%s) <%s> said using an unknown message type: %s\n" +msgid "Please select one operation : %s or %s or %s or %s or %s\n" msgstr "" -#: src/chat/gnunet-chat.c:217 +#: src/ats-tool/gnunet-ats.c:379 src/ats-tool/gnunet-ats.c:398 +#: src/ats-tool/gnunet-ats.c:415 src/ats-tool/gnunet-ats.c:440 #, c-format -msgid "'%s' acknowledged message #%d\n" +msgid "Cannot connect to ATS service, exiting...\n" msgstr "" -#: src/chat/gnunet-chat.c:260 +#: src/ats-tool/gnunet-ats.c:388 src/ats-tool/gnunet-ats.c:405 #, c-format -msgid "`%s' entered the room\n" +msgid "Cannot issue request to ATS service, exiting...\n" msgstr "" -#: src/chat/gnunet-chat.c:260 -#, c-format -msgid "`%s' left the room\n" +#: src/ats-tool/gnunet-ats.c:433 +msgid "Type required\n" msgstr "" -#: src/chat/gnunet-chat.c:321 src/chat/gnunet-chat.c:363 -msgid "Could not change username\n" +#: src/ats-tool/gnunet-ats.c:490 +msgid "get list of active addresses currently used" msgstr "" -#: src/chat/gnunet-chat.c:334 src/chat/gnunet-chat.c:702 -#, c-format -msgid "Joining room `%s' as user `%s'...\n" +#: src/ats-tool/gnunet-ats.c:493 +msgid "get list of all active addresses" msgstr "" -#: src/chat/gnunet-chat.c:373 -#, c-format -msgid "Changed username to `%s'\n" +#: src/ats-tool/gnunet-ats.c:496 +msgid "do not resolve IP addresses to hostnames" msgstr "" -#: src/chat/gnunet-chat.c:388 -#, c-format -msgid "Users in room `%s': " +#: src/ats-tool/gnunet-ats.c:499 +msgid "monitor mode" msgstr "" -#: src/chat/gnunet-chat.c:434 -msgid "Syntax: /msg USERNAME MESSAGE" +#: src/ats-tool/gnunet-ats.c:502 +msgid "set preference for the given peer" msgstr "" -#: src/chat/gnunet-chat.c:443 -#, c-format -msgid "Unknown user `%s'. Make sure you specify its numeric suffix, if any.\n" +#: src/ats-tool/gnunet-ats.c:505 +msgid "print all configured quotas" msgstr "" -#: src/chat/gnunet-chat.c:460 -#, c-format -msgid "User `%s' is currently not in the room!\n" +#: src/ats-tool/gnunet-ats.c:508 +msgid "peer id" msgstr "" -#: src/chat/gnunet-chat.c:513 -#, c-format -msgid "Unknown command `%s'\n" +#: src/ats-tool/gnunet-ats.c:511 +msgid "preference type to set: latency | bandwidth" msgstr "" -#: src/chat/gnunet-chat.c:524 -msgid "" -"Use `/join #roomname' to join a chat room. Joining a room will cause you to " -"leave the current room" +#: src/ats-tool/gnunet-ats.c:514 +msgid "preference value" msgstr "" -#: src/chat/gnunet-chat.c:528 -msgid "" -"Use `/nick nickname' to change your nickname. This will cause you to leave " -"the current room and immediately rejoin it with the new name." +#: src/ats-tool/gnunet-ats.c:517 +msgid "verbose output (include ATS address properties)" msgstr "" -#: src/chat/gnunet-chat.c:532 -msgid "" -"Use `/msg nickname message' to send a private message to the specified user" +#: src/ats-tool/gnunet-ats.c:526 +msgid "Print information about ATS state" msgstr "" -#: src/chat/gnunet-chat.c:535 -msgid "The `/notice' command is an alias for `/msg'" +#: src/block/block.c:105 +#, c-format +msgid "Loading block plugin `%s'\n" msgstr "" -#: src/chat/gnunet-chat.c:537 -msgid "The `/query' command is an alias for `/msg'" +#: src/consensus/gnunet-consensus.c:317 +msgid "number of peers in consensus" msgstr "" -#: src/chat/gnunet-chat.c:539 -msgid "Use `/sig message' to send a signed public message" +#: src/consensus/gnunet-consensus.c:320 +msgid "how many peers receive one value?" msgstr "" -#: src/chat/gnunet-chat.c:542 -msgid "Use `/ack message' to require signed acknowledgment of the message" +#: src/consensus/gnunet-consensus.c:323 +msgid "number of values" msgstr "" -#: src/chat/gnunet-chat.c:545 -msgid "Use `/anonymous message' to send a public anonymous message" +#: src/consensus/gnunet-consensus.c:326 +msgid "consensus timeout" msgstr "" -#: src/chat/gnunet-chat.c:547 -msgid "The `/anon' command is an alias for `/anonymous'" +#: src/consensus/gnunet-consensus-ibf.c:176 +msgid "number of element in set A-B" msgstr "" -#: src/chat/gnunet-chat.c:549 -msgid "Use `/quit' to terminate gnunet-chat" +#: src/consensus/gnunet-consensus-ibf.c:179 +msgid "number of element in set B-A" msgstr "" -#: src/chat/gnunet-chat.c:551 -msgid "The `/leave' command is an alias for `/quit'" +#: src/consensus/gnunet-consensus-ibf.c:182 +msgid "number of common elements in A and B" msgstr "" -#: src/chat/gnunet-chat.c:554 -msgid "Use `/names' to list all of the current members in the chat room" +#: src/consensus/gnunet-consensus-ibf.c:185 +msgid "hash num" msgstr "" -#: src/chat/gnunet-chat.c:556 -msgid "Use `/help command' to get help for a specific command" +#: src/consensus/gnunet-consensus-ibf.c:188 +msgid "ibf size" msgstr "" -#: src/chat/gnunet-chat.c:672 -msgid "You must specify a nickname\n" +#: src/consensus/gnunet-consensus-start-peers.c:158 +msgid "start peers with the given template configuration" msgstr "" -#: src/chat/gnunet-chat.c:688 -#, c-format -msgid "Failed to join room `%s'\n" +#: src/consensus/gnunet-consensus-start-peers.c:161 +msgid "number of peers to start" msgstr "" -#: src/chat/gnunet-chat.c:727 -msgid "set the nickname to use (required)" +#: src/core/core_api.c:755 +msgid "Client was disconnected from core service, trying to reconnect.\n" msgstr "" -#: src/chat/gnunet-chat.c:730 -msgid "set the chat room to join" +#: src/core/gnunet-core.c:86 src/peerinfo-tool/gnunet-peerinfo.c:214 +#, c-format +msgid "Peer `%s'\n" msgstr "" -#: src/chat/gnunet-chat.c:742 -msgid "Join a chat on GNUnet." +#: src/core/gnunet-core.c:119 src/core/gnunet-core.c:147 +#: src/transport/gnunet-transport.c:612 src/transport/gnunet-transport.c:636 +#, c-format +msgid "%24s: %-17s %4s (%u connections in total)\n" msgstr "" -#: src/chat/gnunet-service-chat.c:267 -msgid "Failed to queue a message notification\n" +#: src/core/gnunet-core.c:121 src/transport/gnunet-transport.c:614 +msgid "Connected to" msgstr "" -#: src/chat/gnunet-service-chat.c:546 -msgid "Failed to queue a join notification\n" +#: src/core/gnunet-core.c:149 src/transport/gnunet-transport.c:638 +msgid "Disconnected from" msgstr "" -#: src/chat/gnunet-service-chat.c:729 -msgid "Failed to queue a confirmation receipt\n" +#: src/core/gnunet-core.c:174 src/mesh/gnunet-mesh.c:176 +#: src/peerinfo-tool/gnunet-peerinfo.c:541 +#, c-format +msgid "Invalid command line argument `%s'\n" msgstr "" -#: src/chat/gnunet-service-chat.c:907 -msgid "Failed to queue a leave notification\n" +#: src/core/gnunet-core.c:211 src/transport/gnunet-transport.c:1005 +msgid "provide information about all current connections (continuously)" msgstr "" -#: src/core/core_api.c:786 -msgid "Client was disconnected from core service, trying to reconnect.\n" +#: src/core/gnunet-core.c:222 +msgid "Print information about connected peers." msgstr "" -#: src/core/gnunet-core.c:54 src/peerinfo-tool/gnunet-peerinfo.c:286 +#: src/core/gnunet-service-core.c:109 #, c-format -msgid "Peer `%s'\n" +msgid "Failed to read hostkey: %s\n" msgstr "" -#: src/core/gnunet-core.c:72 src/peerinfo-tool/gnunet-peerinfo.c:817 +#: src/core/gnunet-service-core.c:123 #, c-format -msgid "Invalid command line argument `%s'\n" +msgid "Core service of `%4s' ready.\n" msgstr "" -#: src/core/gnunet-core.c:95 -msgid "Print information about connected peers." +#: src/core/gnunet-service-core.c:149 +msgid "Core service is lacking HOSTKEY configuration setting. Exiting.\n" msgstr "" -#: src/core/gnunet-service-core.c:97 -#, c-format -msgid "Core service of `%4s' ready.\n" +#: src/core/gnunet-service-core.c:163 +#: src/transport/gnunet-service-transport.c:737 +msgid "Transport service is unable to access hostkey. Exiting.\n" msgstr "" #: src/core/gnunet-service-core_clients.c:370 @@ -569,7 +477,7 @@ msgstr "" msgid "# messages discarded (session disconnected)" msgstr "" -#: src/core/gnunet-service-core_clients.c:818 +#: src/core/gnunet-service-core_clients.c:518 #, c-format msgid "# bytes of messages of type %u received" msgstr "" @@ -612,7 +520,7 @@ msgid "# SET_KEY messages decrypted" msgstr "" #: src/core/gnunet-service-core_kx.c:977 -#: src/transport/gnunet-service-transport_validation.c:810 +#: src/transport/gnunet-service-transport_validation.c:865 msgid "# PING messages received" msgstr "" @@ -636,7 +544,7 @@ msgid "# keepalive messages sent" msgstr "" #: src/core/gnunet-service-core_kx.c:1236 -#: src/transport/gnunet-service-transport_validation.c:1031 +#: src/transport/gnunet-service-transport_validation.c:1161 msgid "# PONG messages received" msgstr "" @@ -652,52 +560,44 @@ msgstr "" msgid "# rekey operations confirmed via PONG" msgstr "" -#: src/core/gnunet-service-core_kx.c:1381 -#: src/core/gnunet-service-core_kx.c:1398 +#: src/core/gnunet-service-core_kx.c:1383 +#: src/core/gnunet-service-core_kx.c:1400 msgid "# SET_KEY and PING messages created" msgstr "" -#: src/core/gnunet-service-core_kx.c:1402 +#: src/core/gnunet-service-core_kx.c:1404 msgid "# REKEY operations performed" msgstr "" -#: src/core/gnunet-service-core_kx.c:1537 +#: src/core/gnunet-service-core_kx.c:1539 msgid "# failed to decrypt message (no session key)" msgstr "" -#: src/core/gnunet-service-core_kx.c:1577 -#: src/core/gnunet-service-core_kx.c:1602 +#: src/core/gnunet-service-core_kx.c:1579 +#: src/core/gnunet-service-core_kx.c:1604 msgid "# bytes dropped (duplicates)" msgstr "" -#: src/core/gnunet-service-core_kx.c:1589 +#: src/core/gnunet-service-core_kx.c:1591 msgid "# bytes dropped (out of sequence)" msgstr "" -#: src/core/gnunet-service-core_kx.c:1626 +#: src/core/gnunet-service-core_kx.c:1628 #, c-format -msgid "Message received far too old (%llu ms). Content ignored.\n" +msgid "Message received far too old (%s). Content ignored.\n" msgstr "" -#: src/core/gnunet-service-core_kx.c:1630 +#: src/core/gnunet-service-core_kx.c:1632 msgid "# bytes dropped (ancient message)" msgstr "" -#: src/core/gnunet-service-core_kx.c:1638 +#: src/core/gnunet-service-core_kx.c:1640 msgid "# bytes of payload decrypted" msgstr "" -#: src/core/gnunet-service-core_kx.c:1700 -msgid "Core service is lacking HOSTKEY configuration setting. Exiting.\n" -msgstr "" - -#: src/core/gnunet-service-core_kx.c:1708 -msgid "Core service could not access hostkey. Exiting.\n" -msgstr "" - -#: src/core/gnunet-service-core_kx.c:1718 src/hostlist/hostlist-server.c:551 -#: src/peerinfo-tool/gnunet-peerinfo.c:823 -#: src/transport/gnunet-service-transport.c:611 +#: src/core/gnunet-service-core_kx.c:1703 src/hostlist/hostlist-server.c:552 +#: src/peerinfo-tool/gnunet-peerinfo.c:547 +#: src/transport/gnunet-service-transport.c:644 msgid "Could not access PEERINFO service. Exiting.\n" msgstr "" @@ -714,23 +614,23 @@ msgstr "" msgid "# encrypted bytes given to transport" msgstr "" -#: src/core/gnunet-service-core_neighbours.c:418 +#: src/core/gnunet-service-core_neighbours.c:421 #, c-format msgid "Unsupported message of type %u (%u bytes) received from peer `%s'\n" msgstr "" #: src/core/gnunet-service-core_sessions.c:206 #: src/core/gnunet-service-core_sessions.c:269 -#: src/dht/gnunet-service-dht_neighbours.c:625 -#: src/dht/gnunet-service-dht_neighbours.c:683 -#: src/fs/gnunet-service-fs_cp.c:615 src/fs/gnunet-service-fs_cp.c:1532 -#: src/topology/gnunet-daemon-topology.c:709 -#: src/topology/gnunet-daemon-topology.c:810 -#: src/transport/gnunet-service-transport_neighbours.c:874 -#: src/transport/gnunet-service-transport_neighbours.c:1080 -#: src/transport/gnunet-service-transport_neighbours.c:1089 -#: src/transport/gnunet-service-transport_neighbours.c:2568 -#: src/transport/gnunet-service-transport_neighbours.c:2814 +#: src/dht/gnunet-service-dht_neighbours.c:645 +#: src/dht/gnunet-service-dht_neighbours.c:703 +#: src/fs/gnunet-service-fs_cp.c:630 src/fs/gnunet-service-fs_cp.c:1544 +#: src/topology/gnunet-daemon-topology.c:704 +#: src/topology/gnunet-daemon-topology.c:805 +#: src/transport/gnunet-service-transport_neighbours.c:1052 +#: src/transport/gnunet-service-transport_neighbours.c:1276 +#: src/transport/gnunet-service-transport_neighbours.c:1285 +#: src/transport/gnunet-service-transport_neighbours.c:2826 +#: src/transport/gnunet-service-transport_neighbours.c:3089 msgid "# peers connected" msgstr "" @@ -751,38 +651,48 @@ msgstr "" msgid "# updates to my type map" msgstr "" -#: src/datacache/datacache.c:115 src/datacache/datacache.c:250 +#: src/datacache/datacache.c:115 src/datacache/datacache.c:266 #: src/datastore/gnunet-service-datastore.c:834 msgid "# bytes stored" msgstr "" -#: src/datacache/datacache.c:141 src/datacache/datacache.c:148 +#: src/datacache/datacache.c:117 src/datacache/datacache.c:268 +msgid "# items stored" +msgstr "" + +#: src/datacache/datacache.c:143 src/datacache/datacache.c:150 #: src/datastore/gnunet-service-datastore.c:1483 #: src/datastore/gnunet-service-datastore.c:1494 #, c-format msgid "No `%s' specified for `%s' in configuration!\n" msgstr "" -#: src/datacache/datacache.c:180 +#: src/datacache/datacache.c:184 #, c-format msgid "Loading `%s' datacache plugin\n" msgstr "" -#: src/datacache/datacache.c:188 +#: src/datacache/datacache.c:192 #, c-format msgid "Failed to load datacache plugin for `%s'\n" msgstr "" -#: src/datacache/datacache.c:276 +#: src/datacache/datacache.c:295 msgid "# requests received" msgstr "" -#: src/datacache/datacache.c:284 +#: src/datacache/datacache.c:304 msgid "# requests filtered by bloom filter" msgstr "" -#: src/datacache/plugin_datacache_mysql.c:97 -#: src/datacache/plugin_datacache_mysql.c:104 +#: src/datacache/plugin_datacache_heap.c:406 +msgid "Heap datacache running\n" +msgstr "" + +#: src/datacache/plugin_datacache_postgres.c:392 +msgid "Postgres datacache running\n" +msgstr "" + #: src/datacache/plugin_datacache_sqlite.c:69 #: src/datacache/plugin_datacache_sqlite.c:72 #: src/datastore/plugin_datastore_mysql.c:803 @@ -790,57 +700,50 @@ msgstr "" #: src/datastore/plugin_datastore_sqlite.c:57 src/mysql/mysql.c:41 #: src/mysql/mysql.c:48 src/mysql/mysql.c:522 src/mysql/mysql.c:531 #: src/mysql/mysql.c:591 src/mysql/mysql.c:607 -#: src/namestore/plugin_namestore_sqlite.c:51 src/util/crypto_ksk.c:49 -#: src/util/crypto_rsa.c:67 src/include/gnunet_common.h:525 -#: src/include/gnunet_common.h:532 +#: src/namestore/plugin_namestore_postgres.c:52 +#: src/namestore/plugin_namestore_sqlite.c:51 src/util/crypto_ecc.c:46 +#: src/util/crypto_ksk.c:49 src/util/crypto_rsa.c:59 +#: src/include/gnunet_common.h:607 src/include/gnunet_common.h:614 #, c-format msgid "`%s' failed at %s:%d with error: %s\n" msgstr "" -#: src/datacache/plugin_datacache_mysql.c:450 -msgid "MySQL datacache running\n" -msgstr "" - -#: src/datacache/plugin_datacache_postgres.c:367 -msgid "Postgres datacache running\n" -msgstr "" - -#: src/datacache/plugin_datacache_sqlite.c:410 +#: src/datacache/plugin_datacache_sqlite.c:450 msgid "Sqlite datacache running\n" msgstr "" -#: src/datacache/plugin_datacache_sqlite.c:443 -#: src/datastore/plugin_datastore_sqlite.c:408 -#: src/namestore/plugin_namestore_sqlite.c:370 +#: src/datacache/plugin_datacache_sqlite.c:484 +#: src/datastore/plugin_datastore_sqlite.c:401 +#: src/namestore/plugin_namestore_sqlite.c:362 msgid "Tried to close sqlite without finalizing all prepared statements.\n" msgstr "" -#: src/datacache/plugin_datacache_sqlite.c:450 +#: src/datacache/plugin_datacache_sqlite.c:491 #, c-format msgid "Failed to close statement %p: %d\n" msgstr "" -#: src/datacache/plugin_datacache_template.c:121 +#: src/datacache/plugin_datacache_template.c:125 msgid "Template datacache running\n" msgstr "" -#: src/datastore/datastore_api.c:305 +#: src/datastore/datastore_api.c:310 msgid "Failed to transmit request to drop database.\n" msgstr "" -#: src/datastore/datastore_api.c:388 +#: src/datastore/datastore_api.c:393 msgid "# queue entry timeouts" msgstr "" -#: src/datastore/datastore_api.c:432 +#: src/datastore/datastore_api.c:437 msgid "# queue overflows" msgstr "" -#: src/datastore/datastore_api.c:459 +#: src/datastore/datastore_api.c:465 msgid "# queue entries created" msgstr "" -#: src/datastore/datastore_api.c:477 +#: src/datastore/datastore_api.c:483 msgid "# Requests dropped from datastore queue" msgstr "" @@ -848,59 +751,55 @@ msgstr "" msgid "# datastore connections (re)created" msgstr "" -#: src/datastore/datastore_api.c:548 -msgid "# reconnected to DATASTORE" -msgstr "" - -#: src/datastore/datastore_api.c:612 +#: src/datastore/datastore_api.c:608 msgid "# transmission request failures" msgstr "" -#: src/datastore/datastore_api.c:633 +#: src/datastore/datastore_api.c:630 msgid "# bytes sent to datastore" msgstr "" -#: src/datastore/datastore_api.c:764 +#: src/datastore/datastore_api.c:762 msgid "Failed to receive status response from database." msgstr "" -#: src/datastore/datastore_api.c:778 +#: src/datastore/datastore_api.c:776 msgid "Error reading response from datastore service" msgstr "" -#: src/datastore/datastore_api.c:790 src/datastore/datastore_api.c:796 +#: src/datastore/datastore_api.c:788 src/datastore/datastore_api.c:794 msgid "Invalid error message received from datastore service" msgstr "" -#: src/datastore/datastore_api.c:800 +#: src/datastore/datastore_api.c:798 msgid "# status messages received" msgstr "" -#: src/datastore/datastore_api.c:869 +#: src/datastore/datastore_api.c:867 msgid "# PUT requests executed" msgstr "" -#: src/datastore/datastore_api.c:936 +#: src/datastore/datastore_api.c:934 msgid "# RESERVE requests executed" msgstr "" -#: src/datastore/datastore_api.c:997 +#: src/datastore/datastore_api.c:995 msgid "# RELEASE RESERVE requests executed" msgstr "" -#: src/datastore/datastore_api.c:1054 +#: src/datastore/datastore_api.c:1052 msgid "# UPDATE requests executed" msgstr "" -#: src/datastore/datastore_api.c:1118 +#: src/datastore/datastore_api.c:1116 msgid "# REMOVE requests executed" msgstr "" -#: src/datastore/datastore_api.c:1163 +#: src/datastore/datastore_api.c:1161 msgid "Failed to receive response from database.\n" msgstr "" -#: src/datastore/datastore_api.c:1221 +#: src/datastore/datastore_api.c:1220 msgid "# Results received" msgstr "" @@ -912,7 +811,7 @@ msgstr "" msgid "# GET ZERO ANONYMITY requests executed" msgstr "" -#: src/datastore/datastore_api.c:1409 +#: src/datastore/datastore_api.c:1410 msgid "# GET requests executed" msgstr "" @@ -925,10 +824,12 @@ msgid "# bytes purged (low-priority)" msgstr "" #: src/datastore/gnunet-service-datastore.c:480 +#: src/gns/gnunet-gns-helper-service-w32.c:159 msgid "Transmission to client failed!\n" msgstr "" #: src/datastore/gnunet-service-datastore.c:511 +#: src/gns/gnunet-gns-helper-service-w32.c:189 msgid "Shutdown in progress, aborting transmission.\n" msgstr "" @@ -1063,6 +964,10 @@ msgstr "" msgid "Bloomfilter construction complete.\n" msgstr "" +#: src/datastore/plugin_datastore_heap.c:820 +msgid "Heap database running\n" +msgstr "" + #: src/datastore/plugin_datastore_mysql.c:780 #, c-format msgid "Failed to prepare statement `%s'\n" @@ -1082,6 +987,7 @@ msgid "Failed to drop table from database.\n" msgstr "" #: src/datastore/plugin_datastore_postgres.c:860 +#: src/namestore/plugin_namestore_postgres.c:652 msgid "Postgres database running\n" msgstr "" @@ -1090,211 +996,227 @@ msgstr "" msgid "`%s' failed at %s:%u with error: %s" msgstr "" -#: src/datastore/plugin_datastore_sqlite.c:233 -#: src/namestore/plugin_namestore_sqlite.c:204 -#, c-format -msgid "Option `%s' in section `%s' missing in configuration!\n" -msgstr "" - -#: src/datastore/plugin_datastore_sqlite.c:260 -#: src/namestore/plugin_namestore_sqlite.c:229 +#: src/datastore/plugin_datastore_sqlite.c:253 +#: src/namestore/plugin_namestore_sqlite.c:223 #, c-format msgid "Unable to initialize SQLite: %s.\n" msgstr "" -#: src/datastore/plugin_datastore_sqlite.c:655 +#: src/datastore/plugin_datastore_sqlite.c:648 msgid "Invalid data in database. Trying to fix (by deletion).\n" msgstr "" -#: src/datastore/plugin_datastore_sqlite.c:1139 +#: src/datastore/plugin_datastore_sqlite.c:1134 msgid "sqlite version to old to determine size, assuming zero\n" msgstr "" -#: src/datastore/plugin_datastore_sqlite.c:1158 +#: src/datastore/plugin_datastore_sqlite.c:1153 #, c-format msgid "" "Using sqlite page utilization to estimate payload (%llu pages of size %llu " "bytes)\n" msgstr "" -#: src/datastore/plugin_datastore_sqlite.c:1198 -#: src/namestore/plugin_namestore_sqlite.c:829 +#: src/datastore/plugin_datastore_sqlite.c:1193 +#: src/namestore/plugin_namestore_sqlite.c:827 msgid "Sqlite database running\n" msgstr "" -#: src/datastore/plugin_datastore_template.c:241 +#: src/datastore/plugin_datastore_template.c:257 msgid "Template database running\n" msgstr "" -#: src/dht/dht_api.c:348 +#: src/dht/dht_api.c:375 msgid "Failed to connect to the DHT service!\n" msgstr "" -#: src/dht/gnunet-dht-get.c:201 src/dht/gnunet-dht-monitor.c:293 -#: src/dht/gnunet-dht-put.c:192 +#: src/dht/gnunet-dht-get.c:132 +#, c-format +msgid "" +"Result %d, type %d:\n" +"%.*s\n" +msgstr "" + +#: src/dht/gnunet-dht-get.c:156 +msgid "Must provide key for DHT GET!\n" +msgstr "" + +#: src/dht/gnunet-dht-get.c:162 src/dht/gnunet-dht-monitor.c:225 +msgid "Failed to connect to DHT service!\n" +msgstr "" + +#: src/dht/gnunet-dht-get.c:170 +msgid "Issueing DHT GET with key" +msgstr "" + +#: src/dht/gnunet-dht-get.c:186 src/dht/gnunet-dht-monitor.c:262 +#: src/dht/gnunet-dht-put.c:198 msgid "the query key" msgstr "" -#: src/dht/gnunet-dht-get.c:204 +#: src/dht/gnunet-dht-get.c:189 msgid "how many parallel requests (replicas) to create" msgstr "" -#: src/dht/gnunet-dht-get.c:207 src/dht/gnunet-dht-monitor.c:296 +#: src/dht/gnunet-dht-get.c:192 src/dht/gnunet-dht-monitor.c:265 msgid "the type of data to look for" msgstr "" -#: src/dht/gnunet-dht-get.c:210 src/dht/gnunet-dht-put.c:201 +#: src/dht/gnunet-dht-get.c:195 src/dht/gnunet-dht-put.c:210 msgid "how long to execute this query before giving up?" msgstr "" -#: src/dht/gnunet-dht-get.c:213 src/dht/gnunet-dht-monitor.c:302 -#: src/dht/gnunet-dht-put.c:204 src/fs/gnunet-download.c:271 -#: src/fs/gnunet-publish.c:731 src/fs/gnunet-search.c:297 -#: src/fs/gnunet-unindex.c:169 src/nse/gnunet-nse-profiler.c:910 +#: src/dht/gnunet-dht-get.c:198 src/dht/gnunet-dht-put.c:201 +msgid "use DHT's demultiplex everywhere option" +msgstr "" + +#: src/dht/gnunet-dht-get.c:201 src/dht/gnunet-dht-monitor.c:271 +#: src/dht/gnunet-dht-put.c:213 src/fs/gnunet-auto-share.c:753 +#: src/fs/gnunet-download.c:328 src/fs/gnunet-publish.c:736 +#: src/fs/gnunet-search.c:294 src/fs/gnunet-unindex.c:168 +#: src/nse/gnunet-nse-profiler.c:1033 msgid "be verbose (print progress information)" msgstr "" -#: src/dht/gnunet-dht-get.c:232 +#: src/dht/gnunet-dht-get.c:222 msgid "Issue a GET request to the GNUnet DHT, prints results." msgstr "" -#: src/dht/gnunet-dht-monitor.c:299 -msgid "how long to execute? 0 = forever" +#: src/dht/gnunet-dht-monitor.c:268 +msgid "how long should the monitor command run" msgstr "" -#: src/dht/gnunet-dht-monitor.c:321 +#: src/dht/gnunet-dht-monitor.c:293 msgid "Prints all packets that go through the DHT." msgstr "" -#: src/dht/gnunet-dht-put.c:108 -msgid "PUT request sent!\n" +#: src/dht/gnunet-dht-put.c:118 +msgid "PUT request sent with key" msgstr "" -#: src/dht/gnunet-dht-put.c:111 +#: src/dht/gnunet-dht-put.c:121 msgid "Timeout sending PUT request!\n" msgstr "" -#: src/dht/gnunet-dht-put.c:114 +#: src/dht/gnunet-dht-put.c:124 msgid "PUT request not confirmed!\n" msgstr "" -#: src/dht/gnunet-dht-put.c:144 +#: src/dht/gnunet-dht-put.c:153 msgid "Must provide KEY and DATA for DHT put!\n" msgstr "" -#: src/dht/gnunet-dht-put.c:152 +#: src/dht/gnunet-dht-put.c:160 #, c-format msgid "Could not connect to %s service!\n" msgstr "" -#: src/dht/gnunet-dht-put.c:157 -#, c-format -msgid "Connected to %s service!\n" -msgstr "" - -#: src/dht/gnunet-dht-put.c:172 +#: src/dht/gnunet-dht-put.c:176 #, c-format msgid "Issuing put request for `%s' with data `%s'!\n" msgstr "" -#: src/dht/gnunet-dht-put.c:186 +#: src/dht/gnunet-dht-put.c:192 msgid "the data to insert under the key" msgstr "" -#: src/dht/gnunet-dht-put.c:189 +#: src/dht/gnunet-dht-put.c:195 msgid "how long to store this entry in the dht (in seconds)" msgstr "" -#: src/dht/gnunet-dht-put.c:195 +#: src/dht/gnunet-dht-put.c:204 msgid "how many replicas to create" msgstr "" -#: src/dht/gnunet-dht-put.c:198 +#: src/dht/gnunet-dht-put.c:207 msgid "the type to insert data as" msgstr "" -#: src/dht/gnunet-dht-put.c:223 +#: src/dht/gnunet-dht-put.c:235 msgid "Issue a PUT request to the GNUnet DHT insert DATA under KEY." msgstr "" -#: src/dht/gnunet-service-dht.c:163 src/testing/testing.c:544 -#: src/testing/testing.c:1968 src/testing/testing.c:1998 +#: src/dht/gnunet-service-dht.c:172 msgid "Failed to connect to transport service!\n" msgstr "" -#: src/dht/gnunet-service-dht_clients.c:407 +#: src/dht/gnunet-service-dht_clients.c:413 msgid "# GET requests from clients injected" msgstr "" -#: src/dht/gnunet-service-dht_clients.c:500 +#: src/dht/gnunet-service-dht_clients.c:503 msgid "# PUT requests received from clients" msgstr "" -#: src/dht/gnunet-service-dht_clients.c:584 +#: src/dht/gnunet-service-dht_clients.c:585 msgid "# GET requests received from clients" msgstr "" -#: src/dht/gnunet-service-dht_clients.c:682 +#: src/dht/gnunet-service-dht_clients.c:791 msgid "# GET STOP requests received from clients" msgstr "" -#: src/dht/gnunet-service-dht_clients.c:919 +#: src/dht/gnunet-service-dht_clients.c:1035 msgid "# Key match, type mismatches in REPLY to CLIENT" msgstr "" -#: src/dht/gnunet-service-dht_clients.c:932 +#: src/dht/gnunet-service-dht_clients.c:1048 msgid "# Duplicate REPLIES to CLIENT request dropped" msgstr "" -#: src/dht/gnunet-service-dht_clients.c:967 +#: src/dht/gnunet-service-dht_clients.c:1085 #, c-format msgid "Unsupported block type (%u) in request!\n" msgstr "" -#: src/dht/gnunet-service-dht_clients.c:989 +#: src/dht/gnunet-service-dht_clients.c:1108 msgid "# RESULTS queued for clients" msgstr "" -#: src/dht/gnunet-service-dht_clients.c:1038 -#: src/dht/gnunet-service-dht_clients.c:1081 +#: src/dht/gnunet-service-dht_clients.c:1157 +#: src/dht/gnunet-service-dht_clients.c:1199 msgid "# REPLIES ignored for CLIENTS (no match)" msgstr "" -#: src/dht/gnunet-service-dht_clients.c:1048 +#: src/dht/gnunet-service-dht_clients.c:1167 msgid "Could not pass reply to client, message too big!\n" msgstr "" -#: src/dht/gnunet-service-dht_datacache.c:93 +#: src/dht/gnunet-service-dht_datacache.c:64 #, c-format msgid "%s request received, but have no datacache!\n" msgstr "" -#: src/dht/gnunet-service-dht_datacache.c:103 +#: src/dht/gnunet-service-dht_datacache.c:74 msgid "# ITEMS stored in datacache" msgstr "" -#: src/dht/gnunet-service-dht_datacache.c:207 +#: src/dht/gnunet-service-dht_datacache.c:159 msgid "# Good RESULTS found in datacache" msgstr "" -#: src/dht/gnunet-service-dht_datacache.c:218 +#: src/dht/gnunet-service-dht_datacache.c:170 msgid "# Duplicate RESULTS found in datacache" msgstr "" -#: src/dht/gnunet-service-dht_datacache.c:224 +#: src/dht/gnunet-service-dht_datacache.c:176 msgid "# Invalid RESULTS found in datacache" msgstr "" -#: src/dht/gnunet-service-dht_datacache.c:236 +#: src/dht/gnunet-service-dht_datacache.c:182 +msgid "# Irrelevant RESULTS found in datacache" +msgstr "" + +#: src/dht/gnunet-service-dht_datacache.c:194 msgid "# Unsupported RESULTS found in datacache" msgstr "" -#: src/dht/gnunet-service-dht_datacache.c:239 +#: src/dht/gnunet-service-dht_datacache.c:197 #, c-format msgid "Unsupported block type (%u) in local response!\n" msgstr "" -#: src/dht/gnunet-service-dht_datacache.c:269 +#: src/dht/gnunet-service-dht_datacache.c:227 msgid "# GET requests given to datacache" msgstr "" @@ -1302,81 +1224,87 @@ msgstr "" msgid "# HELLOs obtained from peerinfo" msgstr "" -#: src/dht/gnunet-service-dht_neighbours.c:481 +#: src/dht/gnunet-service-dht_neighbours.c:501 msgid "# Preference updates given to core" msgstr "" -#: src/dht/gnunet-service-dht_neighbours.c:571 +#: src/dht/gnunet-service-dht_neighbours.c:591 msgid "# FIND PEER messages initiated" msgstr "" -#: src/dht/gnunet-service-dht_neighbours.c:717 +#: src/dht/gnunet-service-dht_neighbours.c:737 msgid "# Queued messages discarded (peer disconnected)" msgstr "" -#: src/dht/gnunet-service-dht_neighbours.c:772 +#: src/dht/gnunet-service-dht_neighbours.c:792 msgid "# Bytes transmitted to other peers" msgstr "" -#: src/dht/gnunet-service-dht_neighbours.c:810 -msgid "# Bytes of bandwdith requested from core" +#: src/dht/gnunet-service-dht_neighbours.c:830 +msgid "# Bytes of bandwidth requested from core" msgstr "" -#: src/dht/gnunet-service-dht_neighbours.c:1032 -#: src/dht/gnunet-service-dht_neighbours.c:1060 +#: src/dht/gnunet-service-dht_neighbours.c:1052 +#: src/dht/gnunet-service-dht_neighbours.c:1080 msgid "# Peers excluded from routing due to Bloomfilter" msgstr "" -#: src/dht/gnunet-service-dht_neighbours.c:1041 -#: src/dht/gnunet-service-dht_neighbours.c:1075 +#: src/dht/gnunet-service-dht_neighbours.c:1061 +#: src/dht/gnunet-service-dht_neighbours.c:1095 msgid "# Peer selection failed" msgstr "" -#: src/dht/gnunet-service-dht_neighbours.c:1207 +#: src/dht/gnunet-service-dht_neighbours.c:1229 msgid "# PUT requests routed" msgstr "" -#: src/dht/gnunet-service-dht_neighbours.c:1236 +#: src/dht/gnunet-service-dht_neighbours.c:1258 msgid "# PUT messages queued for transmission" msgstr "" -#: src/dht/gnunet-service-dht_neighbours.c:1315 +#: src/dht/gnunet-service-dht_neighbours.c:1265 +#: src/dht/gnunet-service-dht_neighbours.c:1378 +#: src/dht/gnunet-service-dht_neighbours.c:1478 +msgid "# P2P messages dropped due to full queue" +msgstr "" + +#: src/dht/gnunet-service-dht_neighbours.c:1343 msgid "# GET requests routed" msgstr "" -#: src/dht/gnunet-service-dht_neighbours.c:1342 +#: src/dht/gnunet-service-dht_neighbours.c:1370 msgid "# GET messages queued for transmission" msgstr "" -#: src/dht/gnunet-service-dht_neighbours.c:1443 +#: src/dht/gnunet-service-dht_neighbours.c:1485 msgid "# RESULT messages queued for transmission" msgstr "" -#: src/dht/gnunet-service-dht_neighbours.c:1531 +#: src/dht/gnunet-service-dht_neighbours.c:1573 msgid "# P2P PUT requests received" msgstr "" -#: src/dht/gnunet-service-dht_neighbours.c:1647 +#: src/dht/gnunet-service-dht_neighbours.c:1702 msgid "# FIND PEER requests ignored due to Bloomfilter" msgstr "" -#: src/dht/gnunet-service-dht_neighbours.c:1655 +#: src/dht/gnunet-service-dht_neighbours.c:1710 msgid "# FIND PEER requests ignored due to lack of HELLO" msgstr "" -#: src/dht/gnunet-service-dht_neighbours.c:1746 +#: src/dht/gnunet-service-dht_neighbours.c:1801 msgid "# P2P GET requests received" msgstr "" -#: src/dht/gnunet-service-dht_neighbours.c:1788 +#: src/dht/gnunet-service-dht_neighbours.c:1843 msgid "# P2P FIND PEER requests processed" msgstr "" -#: src/dht/gnunet-service-dht_neighbours.c:1802 +#: src/dht/gnunet-service-dht_neighbours.c:1857 msgid "# P2P GET requests ONLY routed" msgstr "" -#: src/dht/gnunet-service-dht_neighbours.c:1876 +#: src/dht/gnunet-service-dht_neighbours.c:1944 msgid "# P2P RESULTS received" msgstr "" @@ -1396,18 +1324,26 @@ msgstr "" msgid "# Invalid REPLIES matched against routing table" msgstr "" -#: src/dht/gnunet-service-dht_routing.c:238 +#: src/dht/gnunet-service-dht_routing.c:232 +msgid "# Irrelevant REPLIES matched against routing table" +msgstr "" + +#: src/dht/gnunet-service-dht_routing.c:244 msgid "# Unsupported REPLIES matched against routing table" msgstr "" -#: src/dht/gnunet-service-dht_routing.c:311 +#: src/dht/gnunet-service-dht_routing.c:317 msgid "# Entries removed from routing table" msgstr "" -#: src/dht/gnunet-service-dht_routing.c:352 +#: src/dht/gnunet-service-dht_routing.c:400 msgid "# Entries added to routing table" msgstr "" +#: src/dht/gnunet-service-dht_routing.c:418 +msgid "# DHT requests combined" +msgstr "" + #: src/dht/plugin_block_dht.c:136 #, c-format msgid "Block not of type %u\n" @@ -1422,15 +1358,51 @@ msgstr "" msgid "Block of type %u is malformed\n" msgstr "" -#: src/dns/gnunet-dns-monitor.c:337 +#: src/dns/dnsparser.c:152 +#, c-format +msgid "Failed to convert DNS IDNA name `%s' to UTF-8: %s\n" +msgstr "" + +#: src/dns/dnsparser.c:626 +#, c-format +msgid "Failed to convert UTF-8 name `%s' to DNS IDNA format: %s\n" +msgstr "" + +#: src/dns/dnsstub.c:175 +#, c-format +msgid "Could not bind to any port: %s\n" +msgstr "" + +#: src/dns/dnsstub.c:295 src/dns/dnsstub.c:383 +#: src/gns/gnunet-service-gns_resolver.c:1621 +#, c-format +msgid "Failed to send DNS request to %s\n" +msgstr "" + +#: src/dns/dnsstub.c:299 +#, c-format +msgid "Sent DNS request to %s\n" +msgstr "" + +#: src/dns/dnsstub.c:368 +#, c-format +msgid "Configured DNS exit `%s' is not working / valid.\n" +msgstr "" + +#: src/dns/dnsstub.c:440 +#, c-format +msgid "Received DNS response that is too small (%u bytes)" +msgstr "" + +#: src/dns/gnunet-dns-monitor.c:355 msgid "only monitor DNS queries" msgstr "" -#: src/dns/gnunet-dns-monitor.c:340 +#: src/dns/gnunet-dns-monitor.c:358 msgid "only monitor DNS replies" msgstr "" -#: src/dns/gnunet-dns-monitor.c:348 +#: src/dns/gnunet-dns-monitor.c:369 msgid "Monitor DNS queries." msgstr "" @@ -1442,76 +1414,57 @@ msgstr "" msgid "set AAAA records" msgstr "" -#: src/dns/gnunet-dns-redirector.c:247 +#: src/dns/gnunet-dns-redirector.c:251 msgid "Change DNS replies to point elsewhere." msgstr "" -#: src/dns/gnunet-service-dns.c:485 -#, c-format -msgid "Could not bind to any port: %s\n" -msgstr "" - -#: src/dns/gnunet-service-dns.c:639 +#: src/dns/gnunet-service-dns.c:456 msgid "# DNS requests answered via TUN interface" msgstr "" -#: src/dns/gnunet-service-dns.c:822 +#: src/dns/gnunet-service-dns.c:603 msgid "# DNS exit failed (failed to open socket)" msgstr "" -#: src/dns/gnunet-service-dns.c:1005 -#, c-format -msgid "Received DNS response that is too small (%u bytes)" -msgstr "" - -#: src/dns/gnunet-service-dns.c:1050 +#: src/dns/gnunet-service-dns.c:714 msgid "# External DNS response discarded (no matching request)" msgstr "" -#: src/dns/gnunet-service-dns.c:1168 +#: src/dns/gnunet-service-dns.c:792 msgid "# Client response discarded (no matching request)" msgstr "" -#: src/dns/gnunet-service-dns.c:1281 +#: src/dns/gnunet-service-dns.c:907 msgid "Received malformed IPv4-UDP packet on TUN interface.\n" msgstr "" -#: src/dns/gnunet-service-dns.c:1297 +#: src/dns/gnunet-service-dns.c:923 msgid "Received malformed IPv6-UDP packet on TUN interface.\n" msgstr "" -#: src/dns/gnunet-service-dns.c:1306 +#: src/dns/gnunet-service-dns.c:932 #, c-format msgid "Got non-IP packet with %u bytes and protocol %u from TUN\n" msgstr "" -#: src/dns/gnunet-service-dns.c:1315 +#: src/dns/gnunet-service-dns.c:942 msgid "# Non-DNS UDP packet received via TUN interface" msgstr "" -#: src/dns/gnunet-service-dns.c:1380 +#: src/dns/gnunet-service-dns.c:1009 msgid "# DNS requests received via TUN interface" msgstr "" -#: src/dns/gnunet-service-dns.c:1465 -#, c-format -msgid "Configured DNS exit `%s' is not working / valid.\n" -msgstr "" - -#: src/dns/gnunet-service-dns.c:1497 src/exit/gnunet-daemon-exit.c:2674 -msgid "# Inbound MESH tunnels created" -msgstr "" - -#: src/dns/gnunet-service-dns.c:1561 src/exit/gnunet-daemon-exit.c:3032 +#: src/dns/gnunet-service-dns.c:1049 src/exit/gnunet-daemon-exit.c:3351 #, c-format msgid "`%s' must be installed SUID, refusing to run\n" msgstr "" -#: src/dns/gnunet-service-dns.c:1581 -msgid "Configured to provide DNS exit, but no valid DNS server configured!\n" +#: src/dns/gnunet-service-dns.c:1069 src/exit/gnunet-daemon-exit.c:3407 +msgid "need a valid IPv4 or IPv6 address\n" msgstr "" -#: src/dv/dv_api.c:179 +#: src/dv/dv_api.c:189 msgid "Failed to connect to the dv service!\n" msgstr "" @@ -1520,188 +1473,192 @@ msgstr "" msgid "%s Received message from %s of type %d, distance %u!\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:508 +#: src/exit/gnunet-daemon-exit.c:741 #, c-format msgid "Got duplicate service records for `%s:%u'\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:563 +#: src/exit/gnunet-daemon-exit.c:794 msgid "# Bytes transmitted via mesh tunnels" msgstr "" -#: src/exit/gnunet-daemon-exit.c:679 src/exit/gnunet-daemon-exit.c:2069 -#: src/exit/gnunet-daemon-exit.c:2319 src/vpn/gnunet-service-vpn.c:1394 -#: src/vpn/gnunet-service-vpn.c:1795 src/vpn/gnunet-service-vpn.c:1958 +#: src/exit/gnunet-daemon-exit.c:911 src/exit/gnunet-daemon-exit.c:2343 +#: src/exit/gnunet-daemon-exit.c:2603 src/vpn/gnunet-service-vpn.c:1411 +#: src/vpn/gnunet-service-vpn.c:1812 src/vpn/gnunet-service-vpn.c:1975 msgid "# ICMPv4 packets dropped (type not allowed)" msgstr "" -#: src/exit/gnunet-daemon-exit.c:716 src/exit/gnunet-daemon-exit.c:2128 -#: src/exit/gnunet-daemon-exit.c:2378 src/vpn/gnunet-service-vpn.c:1450 -#: src/vpn/gnunet-service-vpn.c:1854 src/vpn/gnunet-service-vpn.c:1991 +#: src/exit/gnunet-daemon-exit.c:948 src/exit/gnunet-daemon-exit.c:2402 +#: src/exit/gnunet-daemon-exit.c:2662 src/vpn/gnunet-service-vpn.c:1467 +#: src/vpn/gnunet-service-vpn.c:1871 src/vpn/gnunet-service-vpn.c:2008 msgid "# ICMPv6 packets dropped (type not allowed)" msgstr "" -#: src/exit/gnunet-daemon-exit.c:756 +#: src/exit/gnunet-daemon-exit.c:988 msgid "# ICMP packets dropped (not allowed)" msgstr "" -#: src/exit/gnunet-daemon-exit.c:763 +#: src/exit/gnunet-daemon-exit.c:995 msgid "ICMP Packet dropped, have no matching connection information\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:840 +#: src/exit/gnunet-daemon-exit.c:1072 msgid "UDP Packet dropped, have no matching connection information\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:915 +#: src/exit/gnunet-daemon-exit.c:1147 msgid "TCP Packet dropped, have no matching connection information\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:968 +#: src/exit/gnunet-daemon-exit.c:1200 msgid "# Packets received from TUN" msgstr "" -#: src/exit/gnunet-daemon-exit.c:982 +#: src/exit/gnunet-daemon-exit.c:1214 msgid "# Bytes received from TUN" msgstr "" -#: src/exit/gnunet-daemon-exit.c:1008 +#: src/exit/gnunet-daemon-exit.c:1240 msgid "IPv4 packet options received. Ignored.\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:1035 +#: src/exit/gnunet-daemon-exit.c:1267 #, c-format msgid "IPv4 packet with unsupported next header %u received. Ignored.\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:1081 +#: src/exit/gnunet-daemon-exit.c:1313 #, c-format msgid "IPv6 packet with unsupported next header %d received. Ignored.\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:1089 +#: src/exit/gnunet-daemon-exit.c:1321 #, c-format msgid "Packet from unknown protocol %u received. Ignored.\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:1471 +#: src/exit/gnunet-daemon-exit.c:1703 msgid "# TCP packets sent via TUN" msgstr "" -#: src/exit/gnunet-daemon-exit.c:1571 +#: src/exit/gnunet-daemon-exit.c:1814 msgid "# TCP service creation requests received via mesh" msgstr "" -#: src/exit/gnunet-daemon-exit.c:1574 src/exit/gnunet-daemon-exit.c:1653 -#: src/exit/gnunet-daemon-exit.c:1763 src/exit/gnunet-daemon-exit.c:1993 -#: src/exit/gnunet-daemon-exit.c:2235 src/exit/gnunet-daemon-exit.c:2516 -#: src/exit/gnunet-daemon-exit.c:2616 +#: src/exit/gnunet-daemon-exit.c:1817 src/exit/gnunet-daemon-exit.c:1906 +#: src/exit/gnunet-daemon-exit.c:2026 src/exit/gnunet-daemon-exit.c:2267 +#: src/exit/gnunet-daemon-exit.c:2519 src/exit/gnunet-daemon-exit.c:2811 +#: src/exit/gnunet-daemon-exit.c:2921 msgid "# Bytes received from MESH" msgstr "" -#: src/exit/gnunet-daemon-exit.c:1607 src/exit/gnunet-daemon-exit.c:2638 +#: src/exit/gnunet-daemon-exit.c:1850 src/exit/gnunet-daemon-exit.c:2943 #, c-format msgid "No service found for %s on port %d!\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:1611 +#: src/exit/gnunet-daemon-exit.c:1854 msgid "# TCP requests dropped (no such service)" msgstr "" -#: src/exit/gnunet-daemon-exit.c:1656 +#: src/exit/gnunet-daemon-exit.c:1909 msgid "# TCP IP-exit creation requests received via mesh" msgstr "" -#: src/exit/gnunet-daemon-exit.c:1766 +#: src/exit/gnunet-daemon-exit.c:2029 msgid "# TCP data requests received via mesh" msgstr "" -#: src/exit/gnunet-daemon-exit.c:1780 +#: src/exit/gnunet-daemon-exit.c:2043 msgid "# TCP DATA requests dropped (no session)" msgstr "" -#: src/exit/gnunet-daemon-exit.c:1830 +#: src/exit/gnunet-daemon-exit.c:2093 msgid "# ICMP packets sent via TUN" msgstr "" -#: src/exit/gnunet-daemon-exit.c:1996 +#: src/exit/gnunet-daemon-exit.c:2270 msgid "# ICMP IP-exit requests received via mesh" msgstr "" -#: src/exit/gnunet-daemon-exit.c:2238 +#: src/exit/gnunet-daemon-exit.c:2522 msgid "# ICMP service requests received via mesh" msgstr "" -#: src/exit/gnunet-daemon-exit.c:2304 src/vpn/gnunet-service-vpn.c:1384 -#: src/vpn/gnunet-service-vpn.c:1952 +#: src/exit/gnunet-daemon-exit.c:2588 src/vpn/gnunet-service-vpn.c:1401 +#: src/vpn/gnunet-service-vpn.c:1969 msgid "# ICMPv4 packets dropped (impossible PT to v6)" msgstr "" -#: src/exit/gnunet-daemon-exit.c:2363 src/vpn/gnunet-service-vpn.c:1420 -#: src/vpn/gnunet-service-vpn.c:1432 src/vpn/gnunet-service-vpn.c:1842 +#: src/exit/gnunet-daemon-exit.c:2647 src/vpn/gnunet-service-vpn.c:1437 +#: src/vpn/gnunet-service-vpn.c:1449 src/vpn/gnunet-service-vpn.c:1859 msgid "# ICMPv6 packets dropped (impossible PT to v4)" msgstr "" -#: src/exit/gnunet-daemon-exit.c:2413 +#: src/exit/gnunet-daemon-exit.c:2697 msgid "# UDP packets sent via TUN" msgstr "" -#: src/exit/gnunet-daemon-exit.c:2519 +#: src/exit/gnunet-daemon-exit.c:2814 msgid "# UDP IP-exit requests received via mesh" msgstr "" -#: src/exit/gnunet-daemon-exit.c:2619 +#: src/exit/gnunet-daemon-exit.c:2924 msgid "# UDP service requests received via mesh" msgstr "" -#: src/exit/gnunet-daemon-exit.c:2642 +#: src/exit/gnunet-daemon-exit.c:2947 msgid "# UDP requests dropped (no such service)" msgstr "" -#: src/exit/gnunet-daemon-exit.c:2882 +#: src/exit/gnunet-daemon-exit.c:2980 +msgid "# Inbound MESH tunnels created" +msgstr "" + +#: src/exit/gnunet-daemon-exit.c:3209 #, c-format msgid "No addresses found for hostname `%s' of service `%s'!\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:2896 src/exit/gnunet-daemon-exit.c:2908 +#: src/exit/gnunet-daemon-exit.c:3223 src/exit/gnunet-daemon-exit.c:3235 #, c-format msgid "Service `%s' configured for IPv4, but IPv4 is disabled!\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:2919 +#: src/exit/gnunet-daemon-exit.c:3246 #, c-format msgid "No IP addresses found for hostname `%s' of service `%s'!\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:3048 +#: src/exit/gnunet-daemon-exit.c:3364 msgid "" "This system does not support IPv4, will disable IPv4 functions despite them " "being enabled in the configuration\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:3056 +#: src/exit/gnunet-daemon-exit.c:3372 msgid "" "This system does not support IPv6, will disable IPv6 functions despite them " "being enabled in the configuration\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:3063 +#: src/exit/gnunet-daemon-exit.c:3379 msgid "" "Cannot enable IPv4 exit but disable IPv4 on TUN interface, will use " "ENABLE_IPv4=YES\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:3069 +#: src/exit/gnunet-daemon-exit.c:3385 msgid "" "Cannot enable IPv6 exit but disable IPv6 on TUN interface, will use " "ENABLE_IPv6=YES\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:3075 src/pt/gnunet-daemon-pt.c:884 +#: src/exit/gnunet-daemon-exit.c:3391 src/pt/gnunet-daemon-pt.c:884 msgid "No useful service enabled. Exiting.\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:3236 +#: src/exit/gnunet-daemon-exit.c:3620 msgid "Daemon to run to provide an IP exit node for the VPN" msgstr "" @@ -1721,108 +1678,108 @@ msgstr "" msgid "# messages defragmented" msgstr "" -#: src/fragmentation/fragmentation.c:203 +#: src/fragmentation/fragmentation.c:208 msgid "# fragments transmitted" msgstr "" -#: src/fragmentation/fragmentation.c:206 +#: src/fragmentation/fragmentation.c:211 msgid "# fragments retransmitted" msgstr "" -#: src/fragmentation/fragmentation.c:232 +#: src/fragmentation/fragmentation.c:237 msgid "# fragments wrap arounds" msgstr "" -#: src/fragmentation/fragmentation.c:273 +#: src/fragmentation/fragmentation.c:281 msgid "# messages fragmented" msgstr "" -#: src/fragmentation/fragmentation.c:276 +#: src/fragmentation/fragmentation.c:284 msgid "# total size of fragmented messages" msgstr "" -#: src/fragmentation/fragmentation.c:363 +#: src/fragmentation/fragmentation.c:405 msgid "# fragment acknowledgements received" msgstr "" -#: src/fragmentation/fragmentation.c:369 +#: src/fragmentation/fragmentation.c:411 msgid "# bits removed from fragmentation ACKs" msgstr "" -#: src/fragmentation/fragmentation.c:393 +#: src/fragmentation/fragmentation.c:435 msgid "# fragmentation transmissions completed" msgstr "" -#: src/fs/fs_api.c:339 +#: src/fs/fs_api.c:465 #, c-format msgid "Could not open file `%s': %s" msgstr "" -#: src/fs/fs_api.c:348 +#: src/fs/fs_api.c:474 #, c-format msgid "Could not read file `%s': %s" msgstr "" -#: src/fs/fs_api.c:354 +#: src/fs/fs_api.c:480 #, c-format msgid "Short read reading from file `%s'!" msgstr "" -#: src/fs/fs_api.c:938 +#: src/fs/fs_api.c:1061 #, c-format msgid "Failed to resume publishing information `%s': %s\n" msgstr "" -#: src/fs/fs_api.c:1395 +#: src/fs/fs_api.c:1520 #, c-format msgid "Failed to recover namespace `%s', cannot resume publishing operation.\n" msgstr "" -#: src/fs/fs_api.c:1437 +#: src/fs/fs_api.c:1562 #, c-format msgid "Failure while resuming publishing operation `%s': %s\n" msgstr "" -#: src/fs/fs_api.c:1453 +#: src/fs/fs_api.c:1578 #, c-format msgid "Failed to resume publishing operation `%s': %s\n" msgstr "" -#: src/fs/fs_api.c:2106 +#: src/fs/fs_api.c:2229 #, c-format msgid "Failure while resuming unindexing operation `%s': %s\n" msgstr "" -#: src/fs/fs_api.c:2116 +#: src/fs/fs_api.c:2239 #, c-format msgid "Failed to resume unindexing operation `%s': %s\n" msgstr "" -#: src/fs/fs_api.c:2241 src/fs/fs_api.c:2480 +#: src/fs/fs_api.c:2364 src/fs/fs_api.c:2604 #, c-format msgid "Failed to resume sub-download `%s': %s\n" msgstr "" -#: src/fs/fs_api.c:2258 +#: src/fs/fs_api.c:2381 #, c-format msgid "Failed to resume sub-search `%s': %s\n" msgstr "" -#: src/fs/fs_api.c:2270 src/fs/fs_api.c:2289 src/fs/fs_api.c:2773 +#: src/fs/fs_api.c:2394 src/fs/fs_api.c:2413 src/fs/fs_api.c:2897 #, c-format msgid "Failure while resuming search operation `%s': %s\n" msgstr "" -#: src/fs/fs_api.c:2471 +#: src/fs/fs_api.c:2595 #, c-format msgid "Failed to resume sub-download `%s': could not open file `%s'\n" msgstr "" -#: src/fs/fs_api.c:2717 +#: src/fs/fs_api.c:2841 msgid "Could not resume running search, will resume as paused search\n" msgstr "" -#: src/fs/fs_api.c:2811 +#: src/fs/fs_api.c:2935 #, c-format msgid "Failure while resuming download operation `%s': %s\n" msgstr "" @@ -1831,61 +1788,61 @@ msgstr "" msgid "MAGIC mismatch. This is not a GNUnet directory.\n" msgstr "" -#: src/fs/fs_download.c:311 +#: src/fs/fs_download.c:321 msgid "" "Recursive downloads of directories larger than 4 GB are not supported on 32-" "bit systems\n" msgstr "" -#: src/fs/fs_download.c:331 +#: src/fs/fs_download.c:341 msgid "Directory too large for system address space\n" msgstr "" -#: src/fs/fs_download.c:497 src/fs/fs_download.c:509 +#: src/fs/fs_download.c:507 src/fs/fs_download.c:519 #, c-format msgid "Failed to open file `%s' for writing" msgstr "" -#: src/fs/fs_download.c:878 +#: src/fs/fs_download.c:888 #, c-format msgid "Failed to create directory for recursive download of `%s'\n" msgstr "" -#: src/fs/fs_download.c:960 +#: src/fs/fs_download.c:970 #, c-format msgid "" "Internal error or bogus download URI (expected %u bytes at depth %u and " "offset %llu/%llu, got %u bytes)" msgstr "" -#: src/fs/fs_download.c:986 +#: src/fs/fs_download.c:996 msgid "internal error decrypting content" msgstr "" -#: src/fs/fs_download.c:1009 +#: src/fs/fs_download.c:1019 #, c-format msgid "Download failed: could not open file `%s': %s" msgstr "" -#: src/fs/fs_download.c:1019 +#: src/fs/fs_download.c:1029 #, c-format msgid "Failed to seek to offset %llu in file `%s': %s" msgstr "" -#: src/fs/fs_download.c:1028 +#: src/fs/fs_download.c:1038 #, c-format msgid "Failed to write block of %u bytes at offset %llu in file `%s': %s" msgstr "" -#: src/fs/fs_download.c:1125 +#: src/fs/fs_download.c:1136 msgid "internal error decoding tree" msgstr "" -#: src/fs/fs_download.c:1888 +#: src/fs/fs_download.c:1927 msgid "Invalid URI" msgstr "" -#: src/fs/fs_getopt.c:191 +#: src/fs/fs_getopt.c:192 #, c-format msgid "" "Unknown metadata type in metadata option `%s'. Using metadata type " @@ -1924,36 +1881,35 @@ msgstr "" msgid "Failed to connect to datastore service" msgstr "" -#: src/fs/fs_namespace.c:57 src/fs/fs_namespace.c:83 -#, c-format -msgid "Configuration fails to specify `%s' in section `%s'\n" -msgstr "" - -#: src/fs/fs_namespace.c:112 +#: src/fs/fs_namespace.c:110 #, c-format msgid "Failed to open `%s' for writing: %s\n" msgstr "" -#: src/fs/fs_namespace.c:134 src/fs/fs_namespace.c:222 +#: src/fs/fs_namespace.c:132 src/fs/fs_namespace.c:220 #, c-format msgid "Failed to write `%s': %s\n" msgstr "" -#: src/fs/fs_namespace.c:256 +#: src/fs/fs_namespace.c:252 #, c-format msgid "Failed to create or read private key for namespace `%s'\n" msgstr "" -#: src/fs/fs_namespace.c:371 +#: src/fs/fs_namespace.c:367 #, c-format msgid "Failed to read namespace private key file `%s', deleting it!\n" msgstr "" -#: src/fs/fs_namespace.c:588 src/fs/fs_publish_ksk.c:295 +#: src/fs/fs_namespace.c:558 +msgid "Identifiers or URI too long to create SBlock" +msgstr "" + +#: src/fs/fs_namespace.c:593 src/fs/fs_publish_ksk.c:295 msgid "Internal error." msgstr "" -#: src/fs/fs_namespace.c:631 +#: src/fs/fs_namespace.c:636 msgid "Failed to connect to datastore." msgstr "" @@ -1962,57 +1918,57 @@ msgstr "" msgid "Publishing failed: %s" msgstr "" -#: src/fs/fs_publish.c:621 src/fs/fs_publish.c:638 src/fs/fs_publish.c:677 -#: src/fs/fs_publish.c:697 src/fs/fs_publish.c:722 src/fs/fs_publish.c:862 +#: src/fs/fs_publish.c:622 src/fs/fs_publish.c:639 src/fs/fs_publish.c:678 +#: src/fs/fs_publish.c:698 src/fs/fs_publish.c:723 src/fs/fs_publish.c:863 #, c-format msgid "Can not index file `%s': %s. Will try to insert instead.\n" msgstr "" -#: src/fs/fs_publish.c:623 +#: src/fs/fs_publish.c:624 msgid "timeout on index-start request to `fs' service" msgstr "" -#: src/fs/fs_publish.c:635 +#: src/fs/fs_publish.c:636 msgid "unknown error" msgstr "" -#: src/fs/fs_publish.c:678 +#: src/fs/fs_publish.c:679 msgid "failed to compute hash" msgstr "" -#: src/fs/fs_publish.c:698 +#: src/fs/fs_publish.c:699 msgid "filename too long" msgstr "" -#: src/fs/fs_publish.c:723 +#: src/fs/fs_publish.c:724 msgid "could not connect to `fs' service" msgstr "" -#: src/fs/fs_publish.c:746 +#: src/fs/fs_publish.c:747 #, c-format msgid "Failed to get file identifiers for `%s'\n" msgstr "" -#: src/fs/fs_publish.c:811 +#: src/fs/fs_publish.c:812 #, c-format msgid "Recursive upload failed at `%s': %s" msgstr "" -#: src/fs/fs_publish.c:817 +#: src/fs/fs_publish.c:818 #, c-format msgid "Recursive upload failed: %s" msgstr "" -#: src/fs/fs_publish.c:863 +#: src/fs/fs_publish.c:864 msgid "needs to be an actual file" msgstr "" -#: src/fs/fs_publish.c:1071 +#: src/fs/fs_publish.c:1090 #, c-format msgid "Insufficient space for publishing: %s" msgstr "" -#: src/fs/fs_publish.c:1142 +#: src/fs/fs_publish.c:1161 #, c-format msgid "Reserving space for %u entries and %llu bytes for publication\n" msgstr "" @@ -2021,16 +1977,11 @@ msgstr "" msgid "Could not connect to datastore." msgstr "" -#: src/fs/fs_search.c:829 +#: src/fs/fs_search.c:892 #, c-format msgid "Got result with unknown block type `%d', ignoring" msgstr "" -#: src/fs/fs_test_lib.c:269 -#, c-format -msgid "Failed to start daemon: %s\n" -msgstr "" - #: src/fs/fs_unindex.c:58 msgid "Failed to find given position in file" msgstr "" @@ -2055,92 +2006,92 @@ msgstr "" msgid "Failed to connect to FS service for unindexing." msgstr "" -#: src/fs/fs_unindex.c:344 +#: src/fs/fs_unindex.c:349 src/fs/fs_unindex.c:361 msgid "Failed to get KSKs from directory scan." msgstr "" -#: src/fs/fs_unindex.c:356 +#: src/fs/fs_unindex.c:357 #, c-format msgid "Internal error scanning `%s'.\n" msgstr "" -#: src/fs/fs_unindex.c:411 +#: src/fs/fs_unindex.c:416 #, c-format msgid "Failed to remove KBlock: %s\n" msgstr "" -#: src/fs/fs_unindex.c:501 +#: src/fs/fs_unindex.c:506 #, c-format msgid "Failed to parse URI `%s' from KBlock!\n" msgstr "" -#: src/fs/fs_unindex.c:553 src/fs/fs_unindex.c:618 +#: src/fs/fs_unindex.c:558 src/fs/fs_unindex.c:623 msgid "Failed to connect to `datastore' service." msgstr "" -#: src/fs/fs_unindex.c:631 +#: src/fs/fs_unindex.c:636 msgid "Failed to open file for unindexing." msgstr "" -#: src/fs/fs_unindex.c:665 +#: src/fs/fs_unindex.c:670 msgid "Failed to compute hash of file." msgstr "" -#: src/fs/fs_uri.c:220 -#, c-format +#: src/fs/fs_uri.c:221 +#, no-c-format msgid "`%' must be followed by HEX number" msgstr "" -#: src/fs/fs_uri.c:279 +#: src/fs/fs_uri.c:280 msgid "Malformed KSK URI (must not begin or end with `+')" msgstr "" -#: src/fs/fs_uri.c:297 +#: src/fs/fs_uri.c:298 msgid "`++' not allowed in KSK URI" msgstr "" -#: src/fs/fs_uri.c:304 +#: src/fs/fs_uri.c:305 msgid "Quotes not balanced in KSK URI" msgstr "" -#: src/fs/fs_uri.c:372 src/fs/fs_uri.c:379 +#: src/fs/fs_uri.c:373 src/fs/fs_uri.c:380 msgid "Malformed SKS URI" msgstr "" -#: src/fs/fs_uri.c:423 src/fs/fs_uri.c:438 +#: src/fs/fs_uri.c:424 src/fs/fs_uri.c:439 msgid "Malformed CHK URI" msgstr "" -#: src/fs/fs_uri.c:568 src/fs/fs_uri.c:583 src/fs/fs_uri.c:593 -#: src/fs/fs_uri.c:621 +#: src/fs/fs_uri.c:569 src/fs/fs_uri.c:584 src/fs/fs_uri.c:594 +#: src/fs/fs_uri.c:622 msgid "SKS URI malformed" msgstr "" -#: src/fs/fs_uri.c:603 +#: src/fs/fs_uri.c:604 msgid "SKS URI malformed (could not decode public key)" msgstr "" -#: src/fs/fs_uri.c:609 +#: src/fs/fs_uri.c:610 msgid "SKS URI malformed (could not find signature)" msgstr "" -#: src/fs/fs_uri.c:615 +#: src/fs/fs_uri.c:616 msgid "SKS URI malformed (could not decode signature)" msgstr "" -#: src/fs/fs_uri.c:628 +#: src/fs/fs_uri.c:629 msgid "SKS URI malformed (could not parse expiration time)" msgstr "" -#: src/fs/fs_uri.c:640 +#: src/fs/fs_uri.c:641 msgid "SKS URI malformed (signature failed validation)" msgstr "" -#: src/fs/fs_uri.c:678 +#: src/fs/fs_uri.c:679 msgid "Unrecognized URI type" msgstr "" -#: src/fs/fs_uri.c:903 +#: src/fs/fs_uri.c:904 msgid "Lacking key configuration settings.\n" msgstr "" @@ -2157,123 +2108,185 @@ msgstr "" msgid "Number of double-quotes not balanced!\n" msgstr "" -#: src/fs/gnunet-directory.c:49 +#: src/fs/gnunet-auto-share.c:236 #, c-format -msgid "\t\n" +msgid "Failed to load state: %s\n" msgstr "" -#: src/fs/gnunet-directory.c:94 +#: src/fs/gnunet-auto-share.c:289 src/fs/gnunet-auto-share.c:299 +#: src/fs/gnunet-auto-share.c:309 #, c-format -msgid "Directory `%s' meta data:\n" +msgid "Failed to save state to file %s\n" msgstr "" -#: src/fs/gnunet-directory.c:97 +#: src/fs/gnunet-auto-share.c:401 #, c-format -msgid "Directory `%s' contents:\n" +msgid "Publication of `%s' done\n" msgstr "" -#: src/fs/gnunet-directory.c:132 -msgid "You must specify a filename to inspect.\n" +#: src/fs/gnunet-auto-share.c:488 +#, c-format +msgid "Publishing `%s'\n" msgstr "" -#: src/fs/gnunet-directory.c:145 +#: src/fs/gnunet-auto-share.c:497 #, c-format -msgid "Failed to read directory `%s'\n" +msgid "Failed to run `%s'\n" msgstr "" -#: src/fs/gnunet-directory.c:154 +#: src/fs/gnunet-auto-share.c:686 #, c-format -msgid "`%s' is not a GNUnet directory\n" +msgid "" +"You must specify one and only one directory name for automatic publication.\n" msgstr "" -#: src/fs/gnunet-directory.c:179 -msgid "Display contents of a GNUnet directory" +#: src/fs/gnunet-auto-share.c:737 src/fs/gnunet-pseudonym.c:279 +#: src/fs/gnunet-publish.c:683 +msgid "set the desired LEVEL of sender-anonymity" msgstr "" -#: src/fs/gnunet-download.c:101 -#, c-format -msgid "Starting download `%s'.\n" +#: src/fs/gnunet-auto-share.c:741 src/fs/gnunet-publish.c:687 +msgid "disable adding the creation time to the metadata of the uploaded file" msgstr "" -#: src/fs/gnunet-download.c:110 -msgid "" +#: src/fs/gnunet-auto-share.c:744 src/fs/gnunet-publish.c:690 +msgid "do not use libextractor to add keywords or metadata" msgstr "" -#: src/fs/gnunet-download.c:119 -#, c-format -msgid "" -"Downloading `%s' at %llu/%llu (%s remaining, %s/s). Block took %s to " -"download\n" +#: src/fs/gnunet-auto-share.c:747 src/fs/gnunet-publish.c:714 +msgid "specify the priority of the content" msgstr "" -#: src/fs/gnunet-download.c:129 -#, c-format -msgid "Error downloading: %s.\n" +#: src/fs/gnunet-auto-share.c:750 src/fs/gnunet-pseudonym.c:304 +#: src/fs/gnunet-publish.c:721 +msgid "set the desired replication LEVEL" msgstr "" -#: src/fs/gnunet-download.c:137 -#, c-format -msgid "Downloading `%s' done (%s/s).\n" +#: src/fs/gnunet-auto-share.c:770 +msgid "Automatically publish files from a directory on GNUnet" msgstr "" -#: src/fs/gnunet-download.c:152 src/fs/gnunet-publish.c:190 -#: src/fs/gnunet-search.c:190 src/fs/gnunet-unindex.c:109 -#, c-format -msgid "Unexpected status: %d\n" +#: src/fs/gnunet-daemon-fsprofiler.c:656 +msgid "Daemon to use file-sharing to measure its performance." msgstr "" -#: src/fs/gnunet-download.c:177 -msgid "You need to specify a URI argument.\n" -msgstr "" +#: src/fs/gnunet-directory.c:49 +#, c-format +msgid "\t\n" +msgstr "" + +#: src/fs/gnunet-directory.c:94 +#, c-format +msgid "Directory `%s' meta data:\n" +msgstr "" + +#: src/fs/gnunet-directory.c:97 +#, c-format +msgid "Directory `%s' contents:\n" +msgstr "" + +#: src/fs/gnunet-directory.c:132 +msgid "You must specify a filename to inspect.\n" +msgstr "" + +#: src/fs/gnunet-directory.c:145 +#, c-format +msgid "Failed to read directory `%s'\n" +msgstr "" + +#: src/fs/gnunet-directory.c:154 +#, c-format +msgid "`%s' is not a GNUnet directory\n" +msgstr "" + +#: src/fs/gnunet-directory.c:183 +msgid "Display contents of a GNUnet directory" +msgstr "" + +#: src/fs/gnunet-download.c:137 +#, c-format +msgid "Starting download `%s'.\n" +msgstr "" + +#: src/fs/gnunet-download.c:147 +msgid "" +msgstr "" + +#: src/fs/gnunet-download.c:157 +#, c-format +msgid "" +"Downloading `%s' at %llu/%llu (%s remaining, %s/s). Block took %s to " +"download\n" +msgstr "" + +#: src/fs/gnunet-download.c:179 +#, c-format +msgid "Error downloading: %s.\n" +msgstr "" + +#: src/fs/gnunet-download.c:194 +#, c-format +msgid "Downloading `%s' done (%s/s).\n" +msgstr "" + +#: src/fs/gnunet-download.c:209 src/fs/gnunet-publish.c:195 +#: src/fs/gnunet-search.c:193 src/fs/gnunet-unindex.c:108 +#, c-format +msgid "Unexpected status: %d\n" +msgstr "" + +#: src/fs/gnunet-download.c:234 +msgid "You need to specify a URI argument.\n" +msgstr "" -#: src/fs/gnunet-download.c:183 src/fs/gnunet-publish.c:624 +#: src/fs/gnunet-download.c:240 src/fs/gnunet-publish.c:629 #, c-format msgid "Failed to parse URI: %s\n" msgstr "" -#: src/fs/gnunet-download.c:190 +#: src/fs/gnunet-download.c:247 msgid "Only CHK or LOC URIs supported.\n" msgstr "" -#: src/fs/gnunet-download.c:197 +#: src/fs/gnunet-download.c:254 msgid "Target filename must be specified.\n" msgstr "" -#: src/fs/gnunet-download.c:211 src/fs/gnunet-publish.c:602 -#: src/fs/gnunet-search.c:241 src/fs/gnunet-unindex.c:141 +#: src/fs/gnunet-download.c:268 src/fs/gnunet-publish.c:607 +#: src/fs/gnunet-search.c:243 src/fs/gnunet-unindex.c:140 #, c-format msgid "Could not initialize `%s' subsystem.\n" msgstr "" -#: src/fs/gnunet-download.c:248 src/fs/gnunet-search.c:285 +#: src/fs/gnunet-download.c:305 src/fs/gnunet-search.c:282 msgid "set the desired LEVEL of receiver-anonymity" msgstr "" -#: src/fs/gnunet-download.c:251 +#: src/fs/gnunet-download.c:308 msgid "delete incomplete downloads (when aborted with CTRL-C)" msgstr "" -#: src/fs/gnunet-download.c:254 src/fs/gnunet-search.c:288 +#: src/fs/gnunet-download.c:311 src/fs/gnunet-search.c:285 msgid "only search the local peer (no P2P network search)" msgstr "" -#: src/fs/gnunet-download.c:257 +#: src/fs/gnunet-download.c:314 msgid "write the file to FILENAME" msgstr "" -#: src/fs/gnunet-download.c:261 +#: src/fs/gnunet-download.c:318 msgid "set the maximum number of parallel downloads that is allowed" msgstr "" -#: src/fs/gnunet-download.c:265 +#: src/fs/gnunet-download.c:322 msgid "set the maximum number of parallel requests for blocks that is allowed" msgstr "" -#: src/fs/gnunet-download.c:268 +#: src/fs/gnunet-download.c:325 msgid "download a GNUnet directory recursively" msgstr "" -#: src/fs/gnunet-download.c:278 +#: src/fs/gnunet-download.c:339 msgid "" "Download files from GNUnet using a GNUnet CHK or LOC URI (gnunet://fs/" "chk/...)" @@ -2283,11 +2296,27 @@ msgstr "" msgid "print a list of all indexed files" msgstr "" -#: src/fs/gnunet-fs.c:124 +#: src/fs/gnunet-fs.c:127 msgid "Special file-sharing operations" msgstr "" -#: src/fs/gnunet-pseudonym.c:160 src/statistics/gnunet-statistics.c:167 +#: src/fs/gnunet-fs-profiler.c:182 +msgid "run the experiment with COUNT peers" +msgstr "" + +#: src/fs/gnunet-fs-profiler.c:185 +msgid "specifies name of a file with the HOSTS the testbed should use" +msgstr "" + +#: src/fs/gnunet-fs-profiler.c:188 +msgid "automatically terminate experiment after DELAY" +msgstr "" + +#: src/fs/gnunet-fs-profiler.c:197 +msgid "run a testbed to measure file-sharing performance" +msgstr "" + +#: src/fs/gnunet-pseudonym.c:160 src/statistics/gnunet-statistics.c:283 #, c-format msgid "Invalid argument `%s'\n" msgstr "" @@ -2298,10 +2327,6 @@ msgstr "" msgid "Option `%s' ignored\n" msgstr "" -#: src/fs/gnunet-pseudonym.c:279 src/fs/gnunet-publish.c:678 -msgid "set the desired LEVEL of sender-anonymity" -msgstr "" - #: src/fs/gnunet-pseudonym.c:282 msgid "create or advertise namespace NAME" msgstr "" @@ -2316,7 +2341,7 @@ msgid "" "multiple times)" msgstr "" -#: src/fs/gnunet-pseudonym.c:292 src/fs/gnunet-publish.c:697 +#: src/fs/gnunet-pseudonym.c:292 src/fs/gnunet-publish.c:702 msgid "set the meta-data for the given TYPE to the given VALUE" msgstr "" @@ -2332,10 +2357,6 @@ msgstr "" msgid "do not print names of remote namespaces" msgstr "" -#: src/fs/gnunet-pseudonym.c:304 src/fs/gnunet-publish.c:716 -msgid "set the desired replication LEVEL" -msgstr "" - #: src/fs/gnunet-pseudonym.c:307 msgid "specify ID of the root of the namespace" msgstr "" @@ -2344,376 +2365,352 @@ msgstr "" msgid "change rating of namespace ID by VALUE" msgstr "" -#: src/fs/gnunet-pseudonym.c:318 +#: src/fs/gnunet-pseudonym.c:322 msgid "Manage GNUnet pseudonyms." msgstr "" -#: src/fs/gnunet-publish.c:147 +#: src/fs/gnunet-publish.c:152 #, c-format msgid "Publishing `%s' at %llu/%llu (%s remaining)\n" msgstr "" -#: src/fs/gnunet-publish.c:155 +#: src/fs/gnunet-publish.c:159 #, c-format msgid "Error publishing: %s.\n" msgstr "" -#: src/fs/gnunet-publish.c:165 +#: src/fs/gnunet-publish.c:169 #, c-format msgid "Publishing `%s' done.\n" msgstr "" -#: src/fs/gnunet-publish.c:169 +#: src/fs/gnunet-publish.c:173 #, c-format msgid "URI is `%s'.\n" msgstr "" -#: src/fs/gnunet-publish.c:187 +#: src/fs/gnunet-publish.c:192 msgid "Cleanup after abort complete.\n" msgstr "" -#: src/fs/gnunet-publish.c:305 +#: src/fs/gnunet-publish.c:310 #, c-format msgid "Meta data for file `%s' (%s)\n" msgstr "" -#: src/fs/gnunet-publish.c:307 +#: src/fs/gnunet-publish.c:312 #, c-format msgid "Keywords for file `%s' (%s)\n" msgstr "" -#: src/fs/gnunet-publish.c:358 +#: src/fs/gnunet-publish.c:363 src/fs/gnunet-publish.c:617 #, c-format -msgid "Failed to create namespace `%s'\n" +msgid "Failed to create namespace `%s' (illegal filename?)\n" msgstr "" -#: src/fs/gnunet-publish.c:433 +#: src/fs/gnunet-publish.c:438 msgid "Could not publish\n" msgstr "" -#: src/fs/gnunet-publish.c:460 +#: src/fs/gnunet-publish.c:465 msgid "Could not start publishing.\n" msgstr "" -#: src/fs/gnunet-publish.c:491 +#: src/fs/gnunet-publish.c:496 #, c-format msgid "Scanning directory `%s'.\n" msgstr "" -#: src/fs/gnunet-publish.c:493 +#: src/fs/gnunet-publish.c:498 #, c-format msgid "Scanning file `%s'.\n" msgstr "" -#: src/fs/gnunet-publish.c:498 +#: src/fs/gnunet-publish.c:503 #, c-format msgid "There was trouble processing file `%s', skipping it.\n" msgstr "" -#: src/fs/gnunet-publish.c:503 +#: src/fs/gnunet-publish.c:508 msgid "Preprocessing complete.\n" msgstr "" -#: src/fs/gnunet-publish.c:507 +#: src/fs/gnunet-publish.c:512 #, c-format msgid "Extracting meta data from file `%s' complete.\n" msgstr "" -#: src/fs/gnunet-publish.c:511 +#: src/fs/gnunet-publish.c:516 msgid "Meta data extraction has finished.\n" msgstr "" -#: src/fs/gnunet-publish.c:518 +#: src/fs/gnunet-publish.c:523 msgid "Internal error scanning directory.\n" msgstr "" -#: src/fs/gnunet-publish.c:552 +#: src/fs/gnunet-publish.c:557 #, c-format msgid "Cannot extract metadata from a URI!\n" msgstr "" -#: src/fs/gnunet-publish.c:559 +#: src/fs/gnunet-publish.c:564 #, c-format msgid "You must specify one and only one filename for insertion.\n" msgstr "" -#: src/fs/gnunet-publish.c:565 +#: src/fs/gnunet-publish.c:570 #, c-format msgid "You must NOT specify an URI and a filename.\n" msgstr "" -#: src/fs/gnunet-publish.c:573 src/vpn/gnunet-vpn.c:214 +#: src/fs/gnunet-publish.c:578 src/vpn/gnunet-vpn.c:213 #, c-format msgid "Option `%s' is required when using option `%s'.\n" msgstr "" -#: src/fs/gnunet-publish.c:583 src/fs/gnunet-publish.c:590 -#: src/transport/gnunet-transport.c:560 +#: src/fs/gnunet-publish.c:588 src/fs/gnunet-publish.c:595 +#: src/transport/gnunet-transport.c:843 src/transport/gnunet-transport.c:873 #, c-format msgid "Option `%s' makes no sense without option `%s'.\n" msgstr "" -#: src/fs/gnunet-publish.c:612 -#, c-format -msgid "Could not create namespace `%s'\n" -msgstr "" - -#: src/fs/gnunet-publish.c:645 +#: src/fs/gnunet-publish.c:650 #, c-format msgid "Failed to access `%s': %s\n" msgstr "" -#: src/fs/gnunet-publish.c:657 +#: src/fs/gnunet-publish.c:662 msgid "" "Failed to start meta directory scanner. Is gnunet-helper-publish-fs " "installed?\n" msgstr "" -#: src/fs/gnunet-publish.c:682 -msgid "disable adding the creation time to the metadata of the uploaded file" -msgstr "" - -#: src/fs/gnunet-publish.c:685 -msgid "do not use libextractor to add keywords or metadata" -msgstr "" - -#: src/fs/gnunet-publish.c:689 +#: src/fs/gnunet-publish.c:694 msgid "" "print list of extracted keywords that would be used, but do not perform " "upload" msgstr "" -#: src/fs/gnunet-publish.c:693 +#: src/fs/gnunet-publish.c:698 msgid "" "add an additional keyword for the top-level file or directory (this option " "can be specified multiple times)" msgstr "" -#: src/fs/gnunet-publish.c:700 +#: src/fs/gnunet-publish.c:705 msgid "" "do not index, perform full insertion (stores entire file in encrypted form " "in GNUnet database)" msgstr "" -#: src/fs/gnunet-publish.c:705 +#: src/fs/gnunet-publish.c:710 msgid "" "specify ID of an updated version to be published in the future (for " "namespace insertions only)" msgstr "" -#: src/fs/gnunet-publish.c:709 -msgid "specify the priority of the content" -msgstr "" - -#: src/fs/gnunet-publish.c:713 +#: src/fs/gnunet-publish.c:718 msgid "publish the files under the pseudonym NAME (place file into namespace)" msgstr "" -#: src/fs/gnunet-publish.c:719 +#: src/fs/gnunet-publish.c:724 msgid "" "only simulate the process but do not do any actual publishing (useful to " "compute URIs)" msgstr "" -#: src/fs/gnunet-publish.c:723 +#: src/fs/gnunet-publish.c:728 msgid "" "set the ID of this version of the publication (for namespace insertions only)" msgstr "" -#: src/fs/gnunet-publish.c:727 +#: src/fs/gnunet-publish.c:732 msgid "" "URI to be published (can be used instead of passing a file to add keywords " "to the file with the respective URI)" msgstr "" -#: src/fs/gnunet-publish.c:742 +#: src/fs/gnunet-publish.c:748 msgid "Publish a file or directory on GNUnet" msgstr "" -#: src/fs/gnunet-search.c:111 +#: src/fs/gnunet-search.c:114 #, c-format msgid "Failed to write directory with search results to `%s'\n" msgstr "" -#: src/fs/gnunet-search.c:181 +#: src/fs/gnunet-search.c:184 #, c-format msgid "Error searching: %s.\n" msgstr "" -#: src/fs/gnunet-search.c:231 +#: src/fs/gnunet-search.c:233 msgid "Could not create keyword URI from arguments.\n" msgstr "" -#: src/fs/gnunet-search.c:255 +#: src/fs/gnunet-search.c:257 msgid "Could not start searching.\n" msgstr "" -#: src/fs/gnunet-search.c:291 +#: src/fs/gnunet-search.c:288 msgid "write search results to file starting with PREFIX" msgstr "" -#: src/fs/gnunet-search.c:294 -msgid "automatically terminate search after VALUE ms" +#: src/fs/gnunet-search.c:291 +msgid "automatically terminate search after DELAY" msgstr "" -#: src/fs/gnunet-search.c:301 +#: src/fs/gnunet-search.c:298 msgid "automatically terminate search after VALUE results are found" msgstr "" -#: src/fs/gnunet-search.c:308 +#: src/fs/gnunet-search.c:309 msgid "Search GNUnet for files that were published on GNUnet" msgstr "" -#: src/fs/gnunet-service-fs.c:240 +#: src/fs/gnunet-service-fs.c:248 msgid "# running average P2P latency (ms)" msgstr "" -#: src/fs/gnunet-service-fs.c:300 src/fs/gnunet-service-fs.c:489 +#: src/fs/gnunet-service-fs.c:309 src/fs/gnunet-service-fs.c:523 msgid "# Loopback routes suppressed" msgstr "" -#: src/fs/gnunet-service-fs.c:581 src/hostlist/gnunet-daemon-hostlist.c:297 -#: src/topology/gnunet-daemon-topology.c:1330 -#: src/topology/gnunet-daemon-topology.c:1337 +#: src/fs/gnunet-service-fs.c:628 src/hostlist/gnunet-daemon-hostlist.c:297 +#: src/topology/gnunet-daemon-topology.c:1322 +#: src/topology/gnunet-daemon-topology.c:1329 #, c-format msgid "Failed to connect to `%s' service.\n" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:696 +#: src/fs/gnunet-service-fs_cp.c:711 msgid "# migration stop messages received" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:700 +#: src/fs/gnunet-service-fs_cp.c:715 #, c-format -msgid "Migration of content to peer `%s' blocked for %llu ms\n" +msgid "Migration of content to peer `%s' blocked for %s\n" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:735 +#: src/fs/gnunet-service-fs_cp.c:751 msgid "# replies transmitted to other peers" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:741 +#: src/fs/gnunet-service-fs_cp.c:757 msgid "# replies dropped" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:766 src/fs/gnunet-service-fs_cp.c:1324 +#: src/fs/gnunet-service-fs_cp.c:782 src/fs/gnunet-service-fs_cp.c:1345 msgid "# P2P searches active" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:858 +#: src/fs/gnunet-service-fs_cp.c:875 msgid "# artificial delays introduced (ms)" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:911 +#: src/fs/gnunet-service-fs_cp.c:928 msgid "# replies dropped due to type mismatch" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:919 +#: src/fs/gnunet-service-fs_cp.c:936 msgid "# replies received for other peers" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:933 +#: src/fs/gnunet-service-fs_cp.c:950 msgid "# replies dropped due to insufficient cover traffic" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:971 +#: src/fs/gnunet-service-fs_cp.c:988 msgid "# P2P searches destroyed due to ultimate reply" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:1038 +#: src/fs/gnunet-service-fs_cp.c:1056 msgid "# requests done for free (low load)" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:1062 +#: src/fs/gnunet-service-fs_cp.c:1081 msgid "# request dropped, priority insufficient" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:1072 +#: src/fs/gnunet-service-fs_cp.c:1091 msgid "# requests done for a price (normal load)" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:1151 +#: src/fs/gnunet-service-fs_cp.c:1170 msgid "# GET requests received (from other peers)" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:1185 +#: src/fs/gnunet-service-fs_cp.c:1204 msgid "# requests dropped due to initiator not being connected" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:1207 +#: src/fs/gnunet-service-fs_cp.c:1227 msgid "# requests dropped due to missing reverse route" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:1267 +#: src/fs/gnunet-service-fs_cp.c:1288 msgid "# requests dropped due TTL underflow" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:1293 +#: src/fs/gnunet-service-fs_cp.c:1314 msgid "# requests dropped due to higher-TTL request" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:1322 +#: src/fs/gnunet-service-fs_cp.c:1343 msgid "# P2P query messages received and processed" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:1687 +#: src/fs/gnunet-service-fs_cp.c:1713 msgid "# migration stop messages sent" msgstr "" -#: src/fs/gnunet-service-fs_indexing.c:113 -#: src/fs/gnunet-service-fs_indexing.c:163 -#, c-format -msgid "Configuration option `%s' in section `%s' missing.\n" -msgstr "" - -#: src/fs/gnunet-service-fs_indexing.c:121 -#: src/fs/gnunet-service-fs_indexing.c:177 +#: src/fs/gnunet-service-fs_indexing.c:130 +#: src/fs/gnunet-service-fs_indexing.c:181 #, c-format msgid "Could not open `%s'.\n" msgstr "" -#: src/fs/gnunet-service-fs_indexing.c:137 +#: src/fs/gnunet-service-fs_indexing.c:142 #, c-format msgid "Error writing `%s'.\n" msgstr "" -#: src/fs/gnunet-service-fs_indexing.c:228 +#: src/fs/gnunet-service-fs_indexing.c:237 #, c-format msgid "" "Index request received for file `%s' is already indexed as `%s'. Permitting " "anyway.\n" msgstr "" -#: src/fs/gnunet-service-fs_indexing.c:266 +#: src/fs/gnunet-service-fs_indexing.c:275 #, c-format msgid "Hash mismatch trying to index file `%s' which has hash `%s'\n" msgstr "" -#: src/fs/gnunet-service-fs_indexing.c:481 +#: src/fs/gnunet-service-fs_indexing.c:477 #, c-format msgid "Failed to delete bogus block: %s\n" msgstr "" -#: src/fs/gnunet-service-fs_indexing.c:539 +#: src/fs/gnunet-service-fs_indexing.c:542 msgid "# index blocks removed: original file inaccessible" msgstr "" -#: src/fs/gnunet-service-fs_indexing.c:554 +#: src/fs/gnunet-service-fs_indexing.c:557 #, c-format msgid "Could not access indexed file `%s' (%s) at offset %llu: %s\n" msgstr "" -#: src/fs/gnunet-service-fs_indexing.c:556 +#: src/fs/gnunet-service-fs_indexing.c:559 msgid "not indexed" msgstr "" -#: src/fs/gnunet-service-fs_indexing.c:571 +#: src/fs/gnunet-service-fs_indexing.c:574 #, c-format msgid "Indexed file `%s' changed at offset %llu\n" msgstr "" -#: src/fs/gnunet-service-fs_lc.c:202 src/fs/gnunet-service-fs_lc.c:362 -#: src/fs/gnunet-service-fs_lc.c:488 +#: src/fs/gnunet-service-fs_lc.c:202 src/fs/gnunet-service-fs_lc.c:369 msgid "# client searches active" msgstr "" @@ -2721,153 +2718,178 @@ msgstr "" msgid "# replies received for local clients" msgstr "" -#: src/fs/gnunet-service-fs_lc.c:321 +#: src/fs/gnunet-service-fs_lc.c:328 msgid "# client searches received" msgstr "" -#: src/fs/gnunet-service-fs_lc.c:356 +#: src/fs/gnunet-service-fs_lc.c:363 msgid "# client searches updated (merged content seen list)" msgstr "" -#: src/fs/gnunet-service-fs_pe.c:265 +#: src/fs/gnunet-service-fs_pe.c:269 msgid "# average retransmission delay (ms)" msgstr "" -#: src/fs/gnunet-service-fs_pe.c:391 +#: src/fs/gnunet-service-fs_pe.c:400 msgid "# transmission failed (core has no bandwidth)" msgstr "" -#: src/fs/gnunet-service-fs_pe.c:420 +#: src/fs/gnunet-service-fs_pe.c:433 msgid "# query messages sent to other peers" msgstr "" -#: src/fs/gnunet-service-fs_pe.c:469 +#: src/fs/gnunet-service-fs_pe.c:482 msgid "# delay heap timeout" msgstr "" -#: src/fs/gnunet-service-fs_pe.c:476 +#: src/fs/gnunet-service-fs_pe.c:490 msgid "# query plans executed" msgstr "" -#: src/fs/gnunet-service-fs_pe.c:538 +#: src/fs/gnunet-service-fs_pe.c:550 msgid "# requests merged" msgstr "" -#: src/fs/gnunet-service-fs_pe.c:544 +#: src/fs/gnunet-service-fs_pe.c:558 msgid "# requests refreshed" msgstr "" -#: src/fs/gnunet-service-fs_pe.c:597 src/fs/gnunet-service-fs_pe.c:681 -#: src/fs/gnunet-service-fs_pe.c:748 +#: src/fs/gnunet-service-fs_pe.c:612 src/fs/gnunet-service-fs_pe.c:696 +#: src/fs/gnunet-service-fs_pe.c:767 msgid "# query plan entries" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:285 +#: src/fs/gnunet-service-fs_pr.c:312 msgid "# Pending requests created" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:367 src/fs/gnunet-service-fs_pr.c:616 +#: src/fs/gnunet-service-fs_pr.c:404 src/fs/gnunet-service-fs_pr.c:667 msgid "# Pending requests active" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:779 +#: src/fs/gnunet-service-fs_pr.c:835 msgid "# replies received and matched" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:808 +#: src/fs/gnunet-service-fs_pr.c:868 msgid "# duplicate replies discarded (bloomfilter)" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:822 +#: src/fs/gnunet-service-fs_pr.c:877 +msgid "# irrelevant replies discarded" +msgstr "" + +#: src/fs/gnunet-service-fs_pr.c:891 #, c-format msgid "Unsupported block type %u\n" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:835 +#: src/fs/gnunet-service-fs_pr.c:904 msgid "# results found locally" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:953 +#: src/fs/gnunet-service-fs_pr.c:1025 msgid "# Datastore `PUT' failures" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:980 +#: src/fs/gnunet-service-fs_pr.c:1052 msgid "# storage requests dropped due to high load" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1015 +#: src/fs/gnunet-service-fs_pr.c:1087 msgid "# Replies received from DHT" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1106 +#: src/fs/gnunet-service-fs_pr.c:1221 +msgid "# Replies received from STREAM" +msgstr "" + +#: src/fs/gnunet-service-fs_pr.c:1273 #, c-format -msgid "Datastore lookup already took %llu ms!\n" +msgid "Datastore lookup already took %s!\n" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1127 +#: src/fs/gnunet-service-fs_pr.c:1293 #, c-format -msgid "On-demand lookup already took %llu ms!\n" +msgid "On-demand lookup already took %s!\n" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1174 +#: src/fs/gnunet-service-fs_pr.c:1340 msgid "# Datastore lookups concluded (no results)" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1188 +#: src/fs/gnunet-service-fs_pr.c:1355 msgid "# Datastore lookups concluded (seen all)" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1197 +#: src/fs/gnunet-service-fs_pr.c:1364 msgid "# Datastore lookups aborted (more than MAX_RESULTS)" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1211 +#: src/fs/gnunet-service-fs_pr.c:1379 msgid "# requested DBLOCK or IBLOCK not found" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1224 +#: src/fs/gnunet-service-fs_pr.c:1393 msgid "# on-demand blocks matched requests" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1237 +#: src/fs/gnunet-service-fs_pr.c:1406 msgid "# on-demand lookups performed successfully" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1242 +#: src/fs/gnunet-service-fs_pr.c:1411 msgid "# on-demand lookups failed" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1269 src/fs/gnunet-service-fs_pr.c:1309 -#: src/fs/gnunet-service-fs_pr.c:1447 +#: src/fs/gnunet-service-fs_pr.c:1438 src/fs/gnunet-service-fs_pr.c:1478 +#: src/fs/gnunet-service-fs_pr.c:1619 msgid "# Datastore lookups concluded (error queueing)" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1327 +#: src/fs/gnunet-service-fs_pr.c:1496 msgid "# Datastore lookups concluded (found last result)" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1338 +#: src/fs/gnunet-service-fs_pr.c:1507 msgid "# Datastore lookups concluded (load too high)" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1424 +#: src/fs/gnunet-service-fs_pr.c:1595 msgid "# Datastore lookups initiated" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1508 +#: src/fs/gnunet-service-fs_pr.c:1680 msgid "# GAP PUT messages received" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1601 src/fs/gnunet-service-fs_pr.c:1610 -#, c-format -msgid "Configuration fails to specify `%s', assuming default value." +#: src/fs/gnunet-service-fs_push.c:629 +msgid "time required, content pushing disabled" msgstr "" -#: src/fs/gnunet-service-fs_push.c:629 -#, c-format -msgid "" -"Invalid value specified for option `%s' in section `%s', content pushing " -"disabled\n" +#: src/fs/gnunet-service-fs_stream.c:777 +msgid "# replies received via stream" +msgstr "" + +#: src/fs/gnunet-service-fs_stream.c:791 +msgid "# replies received via stream dropped" +msgstr "" + +#: src/fs/gnunet-service-fs_stream.c:930 +#: src/fs/gnunet-service-fs_stream.c:1384 +msgid "# stream connections active" +msgstr "" + +#: src/fs/gnunet-service-fs_stream.c:1166 +msgid "# Blocks transferred via stream" +msgstr "" + +#: src/fs/gnunet-service-fs_stream.c:1326 +msgid "# queries received via stream" +msgstr "" + +#: src/fs/gnunet-service-fs_stream.c:1376 +msgid "# stream client connections rejected" msgstr "" #: src/fs/gnunet-unindex.c:89 @@ -2875,153 +2897,268 @@ msgstr "" msgid "Unindexing at %llu/%llu (%s remaining)\n" msgstr "" -#: src/fs/gnunet-unindex.c:96 +#: src/fs/gnunet-unindex.c:95 #, c-format msgid "Error unindexing: %s.\n" msgstr "" -#: src/fs/gnunet-unindex.c:101 +#: src/fs/gnunet-unindex.c:100 msgid "Unindexing done.\n" msgstr "" -#: src/fs/gnunet-unindex.c:131 +#: src/fs/gnunet-unindex.c:130 #, c-format msgid "You must specify one and only one filename for unindexing.\n" msgstr "" -#: src/fs/gnunet-unindex.c:148 +#: src/fs/gnunet-unindex.c:147 msgid "Could not start unindex operation.\n" msgstr "" -#: src/fs/gnunet-unindex.c:176 +#: src/fs/gnunet-unindex.c:179 msgid "Unindex a file that was previously indexed with gnunet-publish." msgstr "" -#: src/fs/plugin_block_fs.c:131 -msgid "Reply mismatched in terms of namespace. Discarded.\n" +#: src/gns/gns_api.c:598 +msgid "Failed to serialize lookup reply from GNS service!\n" +msgstr "" + +#: src/gns/gnunet-dns2gns.c:192 +msgid "Failed to pack DNS response into UDP packet!\n" +msgstr "" + +#: src/gns/gnunet-dns2gns.c:367 +#, c-format +msgid "Cannot parse DNS request from %s\n" +msgstr "" + +#: src/gns/gnunet-dns2gns.c:383 +#, c-format +msgid "Received malformed DNS request from %s\n" +msgstr "" + +#: src/gns/gnunet-dns2gns.c:391 +#, c-format +msgid "Received unsupported DNS request from %s\n" +msgstr "" + +#: src/gns/gnunet-dns2gns.c:679 +msgid "IP of recursive DNS resolver to use (required)" +msgstr "" + +#: src/gns/gnunet-dns2gns.c:682 +msgid "Authoritative DNS suffix to use (optional); default: zkey.eu" +msgstr "" + +#: src/gns/gnunet-dns2gns.c:685 +msgid "Authoritative FCFS suffix to use (optional); default: fcfs.zkey.eu" +msgstr "" + +#: src/gns/gnunet-dns2gns.c:688 +msgid "UDP port to listen on for inbound DNS requests; default: 53" +msgstr "" + +#: src/gns/gnunet-dns2gns.c:701 +msgid "GNUnet DNS-to-GNS proxy (a DNS server)" msgstr "" -#: src/gns/gnunet-gns.c:191 +#: src/gns/gnunet-gns.c:221 +#, c-format msgid "Failed to connect to GNS\n" msgstr "" -#: src/gns/gnunet-gns.c:232 -msgid "try to shorten a given GNS name" +#: src/gns/gnunet-gns.c:335 +#, c-format +msgid "Please specify lookup, shorten or authority operation!\n" +msgstr "" + +#: src/gns/gnunet-gns.c:356 +msgid "try to shorten a given name" msgstr "" -#: src/gns/gnunet-gns.c:235 -msgid "Lookup a record using GNS (NOT IMPLEMENTED)" +#: src/gns/gnunet-gns.c:359 +msgid "Lookup a record for the given name" msgstr "" -#: src/gns/gnunet-gns.c:238 +#: src/gns/gnunet-gns.c:362 msgid "Get the authority of a particular name" msgstr "" -#: src/gns/gnunet-gns.c:241 -msgid "Specify the type of the record lookup" +#: src/gns/gnunet-gns.c:365 +msgid "Specify the type of the record to lookup" msgstr "" -#: src/gns/gnunet-gns.c:244 +#: src/gns/gnunet-gns.c:368 msgid "No unneeded output" msgstr "" -#: src/gns/gnunet-gns.c:255 +#: src/gns/gnunet-gns.c:381 msgid "GNUnet GNS access tool" msgstr "" -#: src/gns/gnunet-gns-fcfsd.c:280 +#: src/gns/gnunet-gns-fcfsd.c:451 #, c-format msgid "Unsupported form value `%s'\n" msgstr "" -#: src/gns/gnunet-gns-fcfsd.c:333 +#: src/gns/gnunet-gns-fcfsd.c:480 #, c-format msgid "Failed to create record for domain `%s': %s\n" msgstr "" -#: src/gns/gnunet-gns-fcfsd.c:377 +#: src/gns/gnunet-gns-fcfsd.c:524 #, c-format msgid "Found existing name `%s' for the given key\n" msgstr "" -#: src/gns/gnunet-gns-fcfsd.c:439 +#: src/gns/gnunet-gns-fcfsd.c:586 #, c-format msgid "Found %u existing records for domain `%s'\n" msgstr "" -#: src/gns/gnunet-gns-fcfsd.c:498 +#: src/gns/gnunet-gns-fcfsd.c:648 #, c-format msgid "Failed to create page for `%s'\n" msgstr "" -#: src/gns/gnunet-gns-fcfsd.c:514 +#: src/gns/gnunet-gns-fcfsd.c:664 #, c-format msgid "Failed to setup post processor for `%s'\n" msgstr "" -#: src/gns/gnunet-gns-fcfsd.c:725 src/gns/gnunet-gns-fcfsd.c:737 -#, c-format -msgid "Option `%s' not specified in configuration section `%s'\n" +#: src/gns/gnunet-gns-fcfsd.c:700 +msgid "Domain name must not contain `.'\n" +msgstr "" + +#: src/gns/gnunet-gns-fcfsd.c:708 +msgid "Domain name must not contain `+'\n" msgstr "" -#: src/gns/gnunet-gns-fcfsd.c:747 src/namestore/gnunet-namestore.c:299 +#: src/gns/gnunet-gns-fcfsd.c:912 src/namestore/gnunet-namestore.c:364 msgid "Failed to read or create private zone key\n" msgstr "" -#: src/gns/gnunet-gns-fcfsd.c:757 src/namestore/gnunet-namestore.c:310 +#: src/gns/gnunet-gns-fcfsd.c:922 src/namestore/gnunet-namestore.c:375 msgid "Failed to connect to namestore\n" msgstr "" -#: src/gns/gnunet-gns-fcfsd.c:773 src/gns/gnunet-gns-proxy.c:525 +#: src/gns/gnunet-gns-fcfsd.c:938 src/gns/gnunet-gns-proxy.c:2857 msgid "Failed to start HTTP server\n" msgstr "" -#: src/gns/gnunet-gns-fcfsd.c:804 +#: src/gns/gnunet-gns-fcfsd.c:972 msgid "GNUnet GNS first come first serve registration service" msgstr "" -#: src/gns/gnunet-gns-proxy.c:800 -msgid "listen on specified port" +#: src/gns/gnunet-gns-proxy.c:2494 +#, c-format +msgid "Unable to import private key from file `%s'\n" +msgstr "" + +#: src/gns/gnunet-gns-proxy.c:2522 +#, c-format +msgid "Unable to import certificate %s\n" +msgstr "" + +#: src/gns/gnunet-gns-proxy.c:3510 +msgid "listen on specified port (default: 7777)" +msgstr "" + +#: src/gns/gnunet-gns-proxy.c:3513 +msgid "pem file to use as CA" msgstr "" -#: src/gns/gnunet-gns-proxy.c:811 +#: src/gns/gnunet-gns-proxy.c:3525 msgid "GNUnet GNS proxy" msgstr "" -#: src/hello/gnunet-hello.c:122 +#: src/gns/gnunet-service-gns.c:486 +#, c-format +msgid "Records for name `%s' in zone %s too large to fit into DHT" +msgstr "" + +#: src/gns/gnunet-service-gns.c:1216 +msgid "Failed to connect to the namestore!\n" +msgstr "" + +#: src/gns/gnunet-service-gns.c:1277 +msgid "Could not connect to DHT!\n" +msgstr "" + +#: src/gns/gnunet-service-gns.c:1288 +msgid "Unable to initialize resolver!\n" +msgstr "" + +#: src/gns/gnunet-service-gns_resolver.c:3439 +#, c-format +msgid "Not a GADS TLD: `%s'\n" +msgstr "" + +#: src/hello/gnunet-hello.c:118 msgid "Call with name of HELLO file to modify.\n" msgstr "" -#: src/hello/gnunet-hello.c:128 +#: src/hello/gnunet-hello.c:124 #, c-format msgid "Error accessing file `%s': %s\n" msgstr "" -#: src/hello/gnunet-hello.c:136 +#: src/hello/gnunet-hello.c:132 #, c-format msgid "File `%s' is too big to be a HELLO\n" msgstr "" -#: src/hello/gnunet-hello.c:143 +#: src/hello/gnunet-hello.c:139 #, c-format msgid "File `%s' is too small to be a HELLO\n" msgstr "" -#: src/hello/gnunet-hello.c:153 src/hello/gnunet-hello.c:181 +#: src/hello/gnunet-hello.c:149 src/hello/gnunet-hello.c:177 #, c-format msgid "Error opening file `%s': %s\n" msgstr "" -#: src/hello/gnunet-hello.c:169 +#: src/hello/gnunet-hello.c:165 #, c-format msgid "Did not find well-formed HELLO in file `%s'\n" msgstr "" -#: src/hello/gnunet-hello.c:193 +#: src/hello/gnunet-hello.c:189 #, c-format msgid "Error writing HELLO to file `%s': %s\n" msgstr "" +#: src/hello/hello.c:904 +msgid "Failed to parse HELLO message: missing expiration time\n" +msgstr "" + +#: src/hello/hello.c:913 +msgid "Failed to parse HELLO message: invalid expiration time\n" +msgstr "" + +#: src/hello/hello.c:923 +msgid "Failed to parse HELLO message: malformed\n" +msgstr "" + +#: src/hello/hello.c:933 +msgid "Failed to parse HELLO message: missing transport plugin\n" +msgstr "" + +#: src/hello/hello.c:950 +#, c-format +msgid "Plugin `%s' not found\n" +msgstr "" + +#: src/hello/hello.c:959 +#, c-format +msgid "Plugin `%s' does not support URIs yet\n" +msgstr "" + +#: src/hello/hello.c:978 +#, c-format +msgid "Failed to parse `%s' as an address for plugin `%s'\n" +msgstr "" + #: src/hostlist/gnunet-daemon-hostlist.c:264 msgid "" "None of the functions for the hostlist daemon were enabled. I have no " @@ -3046,7 +3183,7 @@ msgstr "" msgid "provide a hostlist server" msgstr "" -#: src/hostlist/gnunet-daemon-hostlist.c:341 +#: src/hostlist/gnunet-daemon-hostlist.c:344 msgid "GNUnet hostlist server and client" msgstr "" @@ -3067,173 +3204,137 @@ msgstr "" msgid "# valid HELLOs downloaded from hostlist servers" msgstr "" -#: src/hostlist/hostlist-client.c:375 src/hostlist/hostlist-client.c:396 -#, c-format -msgid "No `%s' specified in `%s' configuration, will not bootstrap.\n" -msgstr "" - -#: src/hostlist/hostlist-client.c:473 src/hostlist/hostlist-client.c:683 -#: src/hostlist/hostlist-client.c:689 src/hostlist/hostlist-client.c:741 -#: src/hostlist/hostlist-client.c:750 src/hostlist/hostlist-client.c:871 -#: src/hostlist/hostlist-client.c:961 src/hostlist/hostlist-client.c:966 -#: src/transport/plugin_transport_http_client.c:110 -#: src/transport/plugin_transport_http_client.c:125 +#: src/hostlist/hostlist-client.c:469 src/hostlist/hostlist-client.c:680 +#: src/hostlist/hostlist-client.c:686 src/hostlist/hostlist-client.c:738 +#: src/hostlist/hostlist-client.c:747 src/hostlist/hostlist-client.c:868 +#: src/hostlist/hostlist-client.c:958 src/hostlist/hostlist-client.c:963 +#: src/transport/plugin_transport_http_client.c:1052 +#: src/transport/plugin_transport_http_client.c:1067 #, c-format msgid "%s failed at %s:%d: `%s'\n" msgstr "" -#: src/hostlist/hostlist-client.c:593 src/hostlist/hostlist-client.c:1331 +#: src/hostlist/hostlist-client.c:589 src/hostlist/hostlist-client.c:1325 msgid "# advertised hostlist URIs" msgstr "" -#: src/hostlist/hostlist-client.c:623 +#: src/hostlist/hostlist-client.c:619 #, c-format msgid "# advertised URI `%s' downloaded" msgstr "" -#: src/hostlist/hostlist-client.c:664 +#: src/hostlist/hostlist-client.c:661 #, c-format msgid "" "Advertised hostlist with URI `%s' could not be downloaded. Advertised URI " "gets dismissed.\n" msgstr "" -#: src/hostlist/hostlist-client.c:802 +#: src/hostlist/hostlist-client.c:799 #, c-format msgid "Timeout trying to download hostlist from `%s'\n" msgstr "" -#: src/hostlist/hostlist-client.c:816 +#: src/hostlist/hostlist-client.c:813 #, c-format msgid "Download limit of %u bytes exceeded, stopping download\n" msgstr "" -#: src/hostlist/hostlist-client.c:836 +#: src/hostlist/hostlist-client.c:833 #, c-format msgid "Download of hostlist from `%s' failed: `%s'\n" msgstr "" -#: src/hostlist/hostlist-client.c:842 +#: src/hostlist/hostlist-client.c:839 #, c-format msgid "Download of hostlist `%s' completed.\n" msgstr "" -#: src/hostlist/hostlist-client.c:850 +#: src/hostlist/hostlist-client.c:847 #, c-format msgid "Adding successfully tested hostlist `%s' datastore.\n" msgstr "" -#: src/hostlist/hostlist-client.c:903 +#: src/hostlist/hostlist-client.c:900 #, c-format msgid "Bootstrapping using hostlist at `%s'.\n" msgstr "" -#: src/hostlist/hostlist-client.c:911 +#: src/hostlist/hostlist-client.c:908 msgid "# hostlist downloads initiated" msgstr "" -#: src/hostlist/hostlist-client.c:1037 src/hostlist/hostlist-client.c:1505 +#: src/hostlist/hostlist-client.c:1035 src/hostlist/hostlist-client.c:1498 msgid "# milliseconds between hostlist downloads" msgstr "" -#: src/hostlist/hostlist-client.c:1046 -#, c-format -msgid "Have %u/%u connections. Will consider downloading hostlist in %llums\n" -msgstr "" - -#: src/hostlist/hostlist-client.c:1084 -msgid "Scheduled saving of hostlists\n" -msgstr "" - -#: src/hostlist/hostlist-client.c:1088 +#: src/hostlist/hostlist-client.c:1043 #, c-format -msgid "Hostlists will be saved to file again in %llums\n" +msgid "Have %u/%u connections. Will consider downloading hostlist in %s\n" msgstr "" -#: src/hostlist/hostlist-client.c:1111 src/hostlist/hostlist-client.c:1127 +#: src/hostlist/hostlist-client.c:1107 src/hostlist/hostlist-client.c:1123 msgid "# active connections" msgstr "" -#: src/hostlist/hostlist-client.c:1242 -#, c-format -msgid "Initial time between hostlist downloads is %llums\n" -msgstr "" - #: src/hostlist/hostlist-client.c:1273 #, c-format -msgid "" -"No `%s' specified in `%s' configuration, cannot load hostlists from file.\n" -msgstr "" - -#: src/hostlist/hostlist-client.c:1279 -#, c-format msgid "Loading saved hostlist entries from file `%s' \n" msgstr "" -#: src/hostlist/hostlist-client.c:1283 +#: src/hostlist/hostlist-client.c:1277 #, c-format -msgid "Hostlist file `%s' is not existing\n" +msgid "Hostlist file `%s' does not exist\n" msgstr "" -#: src/hostlist/hostlist-client.c:1294 +#: src/hostlist/hostlist-client.c:1288 #, c-format msgid "Could not open file `%s' for reading to load hostlists: %s\n" msgstr "" -#: src/hostlist/hostlist-client.c:1327 +#: src/hostlist/hostlist-client.c:1321 #, c-format msgid "%u hostlist URIs loaded from file\n" msgstr "" -#: src/hostlist/hostlist-client.c:1329 +#: src/hostlist/hostlist-client.c:1323 msgid "# hostlist URIs read from file" msgstr "" -#: src/hostlist/hostlist-client.c:1362 -#, c-format -msgid "" -"No `%s' specified in `%s' configuration, cannot save hostlists to file.\n" -msgstr "" - -#: src/hostlist/hostlist-client.c:1376 +#: src/hostlist/hostlist-client.c:1368 #, c-format msgid "Could not open file `%s' for writing to save hostlists: %s\n" msgstr "" -#: src/hostlist/hostlist-client.c:1381 +#: src/hostlist/hostlist-client.c:1373 #, c-format msgid "Writing %u hostlist URIs to `%s'\n" msgstr "" -#: src/hostlist/hostlist-client.c:1405 src/hostlist/hostlist-client.c:1422 +#: src/hostlist/hostlist-client.c:1397 src/hostlist/hostlist-client.c:1414 #, c-format msgid "Error writing hostlist URIs to file `%s'\n" msgstr "" -#: src/hostlist/hostlist-client.c:1417 +#: src/hostlist/hostlist-client.c:1409 msgid "# hostlist URIs written to file" msgstr "" -#: src/hostlist/hostlist-client.c:1470 +#: src/hostlist/hostlist-client.c:1463 msgid "Learning is enabled on this peer\n" msgstr "" -#: src/hostlist/hostlist-client.c:1473 -#, c-format -msgid "Hostlists will be saved to file again in %llums\n" -msgstr "" - -#: src/hostlist/hostlist-client.c:1482 +#: src/hostlist/hostlist-client.c:1475 msgid "Learning is not enabled on this peer\n" msgstr "" -#: src/hostlist/hostlist-client.c:1494 +#: src/hostlist/hostlist-client.c:1487 #, c-format msgid "" "Since learning is not enabled on this peer, hostlist file `%s' was removed\n" msgstr "" -#: src/hostlist/hostlist-client.c:1498 +#: src/hostlist/hostlist-client.c:1491 #, c-format msgid "Hostlist file `%s' could not be removed\n" msgstr "" @@ -3247,9 +3348,9 @@ msgid "expired addresses encountered" msgstr "" #: src/hostlist/hostlist-server.c:184 src/hostlist/hostlist-server.c:425 -#: src/peerinfo-tool/gnunet-peerinfo.c:403 -#: src/peerinfo-tool/gnunet-peerinfo.c:519 -#: src/topology/gnunet-daemon-topology.c:927 +#: src/peerinfo-tool/gnunet-peerinfo.c:331 +#: src/peerinfo-tool/gnunet-peerinfo.c:386 +#: src/topology/gnunet-daemon-topology.c:922 #, c-format msgid "Error in communication with PEERINFO service: %s\n" msgstr "" @@ -3271,10 +3372,6 @@ msgstr "" msgid "hostlist requests refused (not HTTP GET)" msgstr "" -#: src/hostlist/hostlist-server.c:273 -msgid "Sending 100 CONTINUE reply\n" -msgstr "" - #: src/hostlist/hostlist-server.c:279 #, c-format msgid "Refusing `%s' request with %llu bytes of upload data\n" @@ -3308,60 +3405,97 @@ msgstr "" msgid "Advertisement message could not be queued by core\n" msgstr "" -#: src/hostlist/hostlist-server.c:561 +#: src/hostlist/hostlist-server.c:562 #, c-format msgid "Invalid port number %llu. Exiting.\n" msgstr "" -#: src/hostlist/hostlist-server.c:570 +#: src/hostlist/hostlist-server.c:571 #, c-format msgid "Hostlist service starts on %s:%llu\n" msgstr "" -#: src/hostlist/hostlist-server.c:584 +#: src/hostlist/hostlist-server.c:585 #, c-format msgid "Address to obtain hostlist: `%s'\n" msgstr "" -#: src/hostlist/hostlist-server.c:624 +#: src/hostlist/hostlist-server.c:625 #, c-format msgid "`%s' is not a valid IP address! Ignoring BINDTOIP.\n" msgstr "" -#: src/hostlist/hostlist-server.c:666 +#: src/hostlist/hostlist-server.c:667 #, c-format msgid "Could not start hostlist HTTP server on port %u\n" msgstr "" -#: src/integration-tests/connection_watchdog.c:997 +#: src/integration-tests/connection_watchdog.c:1001 #, c-format msgid "Transport plugin: `%s' port %llu\n" msgstr "" -#: src/integration-tests/connection_watchdog.c:1030 +#: src/integration-tests/connection_watchdog.c:1034 #, c-format msgid "Found %u transport plugins: `%s'\n" msgstr "" -#: src/integration-tests/connection_watchdog.c:1089 +#: src/integration-tests/connection_watchdog.c:1093 msgid "Send ping messages to test connectivity (default == NO)" msgstr "" -#: src/integration-tests/connection_watchdog.c:1095 -#: src/template/gnunet-template.c:68 +#: src/integration-tests/connection_watchdog.c:1102 +#: src/template/gnunet-template.c:70 msgid "help text" msgstr "" -#: src/mesh/gnunet-service-mesh.c:4590 +#: src/mesh/gnunet-mesh.c:211 +msgid "provide information about all tunnels (continuously) NOT IMPLEMENTED" +msgstr "" + +#: src/mesh/gnunet-mesh.c:214 +msgid "provide information about a particular tunnel" +msgstr "" + +#: src/mesh/gnunet-mesh.c:224 +msgid "Print information about mesh tunnels and peers." +msgstr "" + +#: src/mesh/gnunet-service-mesh.c:8015 src/mesh/gnunet-service-mesh-new.c:8015 msgid "Wrong CORE service\n" msgstr "" -#: src/mesh/gnunet-service-mesh.c:4784 -msgid "Mesh service is lacking key configuration settings. Exiting.\n" +#: src/mesh/gnunet-service-mesh.c:8232 src/mesh/gnunet-service-mesh-new.c:8232 +#, c-format +msgid "Mesh service could not access hostkey: %s. Exiting.\n" +msgstr "" + +#: src/mesh/gnunet-service-mesh.c:8314 src/mesh/gnunet-service-mesh.c:8326 +#: src/mesh/gnunet-service-mesh.c:8338 src/mesh/gnunet-service-mesh.c:8352 +#: src/mesh/gnunet-service-mesh.c:8364 src/mesh/gnunet-service-mesh.c:8376 +#: src/mesh/gnunet-service-mesh.c:8388 src/mesh/gnunet-service-mesh-new.c:8321 +#: src/mesh/gnunet-service-mesh-new.c:8333 +#: src/mesh/gnunet-service-mesh-new.c:8345 +#: src/mesh/gnunet-service-mesh-new.c:8359 +#: src/mesh/gnunet-service-mesh-new.c:8371 +#: src/mesh/gnunet-service-mesh-new.c:8383 +#: src/mesh/gnunet-service-mesh-new.c:8395 +#: src/regex/gnunet-daemon-regexprofiler.c:335 +#: src/regex/gnunet-daemon-regexprofiler.c:347 +#: src/regex/gnunet-daemon-regexprofiler.c:360 +#: src/regex/gnunet-daemon-regexprofiler.c:373 +#: src/regex/gnunet-regex-simulation-profiler.c:659 +#, c-format +msgid "%s service is lacking key configuration settings (%s). Exiting.\n" msgstr "" -#: src/mesh/gnunet-service-mesh.c:4793 -msgid "Mesh service could not access hostkey. Exiting.\n" +#: src/mesh/gnunet-service-mesh.c:8400 src/mesh/gnunet-service-mesh.c:8410 +#: src/mesh/gnunet-service-mesh.c:8421 src/mesh/gnunet-service-mesh-new.c:8407 +#: src/mesh/gnunet-service-mesh-new.c:8417 +#: src/mesh/gnunet-service-mesh-new.c:8428 +#, c-format +msgid "" +"%s service is lacking key configuration settings (%s). Using default (%u).\n" msgstr "" #: src/mysql/mysql.c:174 @@ -3374,179 +3508,247 @@ msgstr "" msgid "Could not access file `%s': %s\n" msgstr "" -#: src/namestore/gnunet-namestore.c:157 +#: src/namestore/gnunet-namestore.c:212 #, c-format msgid "Adding record failed: %s\n" msgstr "" -#: src/namestore/gnunet-namestore.c:183 +#: src/namestore/gnunet-namestore.c:243 #, c-format msgid "Deleting record failed: %s\n" msgstr "" -#: src/namestore/gnunet-namestore.c:239 +#: src/namestore/gnunet-namestore.c:304 #, c-format msgid "\tCorrupt or unsupported record of type %u\n" msgstr "" -#: src/namestore/gnunet-namestore.c:276 -#, c-format -msgid "Option `%s' not given, but I need a zone key file!\n" +#: src/namestore/gnunet-namestore.c:320 +msgid "for at least" msgstr "" -#: src/namestore/gnunet-namestore.c:281 -#, c-format -msgid "Using default zone file `%s'\n" +#: src/namestore/gnunet-namestore.c:321 +msgid "until" msgstr "" -#: src/namestore/gnunet-namestore.c:291 +#: src/namestore/gnunet-namestore.c:356 #, c-format msgid "No options given\n" msgstr "" -#: src/namestore/gnunet-namestore.c:321 +#: src/namestore/gnunet-namestore.c:386 #, c-format msgid "Unsupported type `%s'\n" msgstr "" -#: src/namestore/gnunet-namestore.c:328 src/namestore/gnunet-namestore.c:350 -#: src/namestore/gnunet-namestore.c:374 src/namestore/gnunet-namestore.c:384 -#: src/namestore/gnunet-namestore.c:409 +#: src/namestore/gnunet-namestore.c:394 src/namestore/gnunet-namestore.c:418 +#: src/namestore/gnunet-namestore.c:465 src/namestore/gnunet-namestore.c:477 +#: src/namestore/gnunet-namestore.c:518 #, c-format msgid "Missing option `%s' for operation `%s'\n" msgstr "" -#: src/namestore/gnunet-namestore.c:329 src/namestore/gnunet-namestore.c:351 +#: src/namestore/gnunet-namestore.c:395 src/namestore/gnunet-namestore.c:419 msgid "add/del" msgstr "" -#: src/namestore/gnunet-namestore.c:341 +#: src/namestore/gnunet-namestore.c:408 #, c-format msgid "Value `%s' invalid for record type `%s'\n" msgstr "" -#: src/namestore/gnunet-namestore.c:366 +#: src/namestore/gnunet-namestore.c:446 #, c-format msgid "Invalid time format `%s'\n" msgstr "" -#: src/namestore/gnunet-namestore.c:375 src/namestore/gnunet-namestore.c:385 +#: src/namestore/gnunet-namestore.c:455 +#, c-format +msgid "" +"Deletion requires either absolute time, or no time at all. Got relative time " +"`%s' instead.\n" +msgstr "" + +#: src/namestore/gnunet-namestore.c:466 src/namestore/gnunet-namestore.c:478 +#: src/namestore/gnunet-namestore.c:497 msgid "add" msgstr "" -#: src/namestore/gnunet-namestore.c:410 +#: src/namestore/gnunet-namestore.c:496 +#, c-format +msgid "No valid expiration time for operation `%s'\n" +msgstr "" + +#: src/namestore/gnunet-namestore.c:519 msgid "del" msgstr "" -#: src/namestore/gnunet-namestore.c:462 +#: src/namestore/gnunet-namestore.c:569 +#: src/peerinfo-tool/gnunet-peerinfo.c:598 +#, c-format +msgid "Invalid URI `%s'\n" +msgstr "" + +#: src/namestore/gnunet-namestore.c:625 +#, c-format +msgid "Using default zone file `%s'\n" +msgstr "" + +#: src/namestore/gnunet-namestore.c:677 msgid "add record" msgstr "" -#: src/namestore/gnunet-namestore.c:465 +#: src/namestore/gnunet-namestore.c:680 msgid "delete record" msgstr "" -#: src/namestore/gnunet-namestore.c:468 +#: src/namestore/gnunet-namestore.c:683 msgid "display records" msgstr "" -#: src/namestore/gnunet-namestore.c:471 +#: src/namestore/gnunet-namestore.c:686 msgid "" "expiration time for record to use (for adding only), \"never\" is possible" msgstr "" -#: src/namestore/gnunet-namestore.c:474 +#: src/namestore/gnunet-namestore.c:689 msgid "name of the record to add/delete/display" msgstr "" -#: src/namestore/gnunet-namestore.c:477 +#: src/namestore/gnunet-namestore.c:692 msgid "type of the record to add/delete/display" msgstr "" -#: src/namestore/gnunet-namestore.c:480 +#: src/namestore/gnunet-namestore.c:695 +msgid "URI to import into our zone" +msgstr "" + +#: src/namestore/gnunet-namestore.c:698 msgid "value of the record to add/delete" msgstr "" -#: src/namestore/gnunet-namestore.c:483 +#: src/namestore/gnunet-namestore.c:701 msgid "create or list public record" msgstr "" -#: src/namestore/gnunet-namestore.c:486 +#: src/namestore/gnunet-namestore.c:704 msgid "create or list non-authority record" msgstr "" -#: src/namestore/gnunet-namestore.c:489 +#: src/namestore/gnunet-namestore.c:707 msgid "filename with the zone key" msgstr "" -#: src/namestore/gnunet-namestore.c:500 +#: src/namestore/gnunet-namestore.c:718 msgid "GNUnet zone manipulation tool" msgstr "" -#: src/namestore/gnunet-service-namestore.c:143 +#: src/namestore/gnunet-service-namestore.c:241 +#: src/namestore/gnunet-service-namestore.c:257 #, c-format -msgid "File zone `%s' but corrupt content already exists, failed to write! \n" +msgid "Failed to write zone key to file `%s': %s\n" msgstr "" -#: src/namestore/gnunet-service-namestore.c:154 -#, c-format -msgid "File zone `%s' containing this key already exists\n" +#: src/namestore/gnunet-service-namestore.c:243 +msgid "file exists but reading key failed" msgstr "" -#: src/namestore/gnunet-service-namestore.c:160 -#, c-format -msgid "" -"File zone `%s' but different zone key already exists, failed to write! \n" +#: src/namestore/gnunet-service-namestore.c:259 +msgid "file exists with different key" +msgstr "" + +#: src/namestore/gnunet-service-namestore.c:1557 +msgid "Failed to find record to remove\n" msgstr "" -#: src/namestore/gnunet-service-namestore.c:198 +#: src/namestore/gnunet-service-namestore.c:2172 #, c-format -msgid "Stored zonekey for zone `%s' in file `%s'\n" +msgid "Could not parse zone key file `%s'\n" msgstr "" -#: src/namestore/gnunet-service-namestore.c:1909 +#: src/namestore/gnunet-service-namestore.c:2262 msgid "No directory to load zonefiles specified in configuration\n" msgstr "" -#: src/namestore/gnunet-service-namestore.c:1918 +#: src/namestore/gnunet-service-namestore.c:2272 #, c-format msgid "Creating directory `%s' for zone files failed!\n" msgstr "" -#: src/namestore/namestore_api.c:315 src/namestore/namestore_api.c:353 -msgid "Namestore added record successfully" +#: src/namestore/namestore_api.c:345 +msgid "Namestore failed to add record" msgstr "" -#: src/namestore/namestore_api.c:323 -msgid "Namestore failed to add record" +#: src/namestore/namestore_api.c:371 +msgid "Namestore failed to add record\n" msgstr "" -#: src/namestore/namestore_api.c:361 -msgid "Namestore record already existed" +#: src/namestore/namestore_api.c:415 +msgid "Failed to create new signature" msgstr "" -#: src/namestore/namestore_api.c:368 -msgid "Namestore failed to add record\n" +#: src/namestore/namestore_api.c:419 +msgid "Failed to put new set of records in database" msgstr "" -#: src/namestore/namestore_api.c:401 -msgid "Namestore removed record successfully" +#: src/namestore/namestore_api.c:423 +msgid "Failed to remove records from database" msgstr "" -#: src/namestore/namestore_api.c:408 -msgid "No records for entry" +#: src/namestore/namestore_api.c:427 +msgid "Failed to access database" msgstr "" -#: src/namestore/namestore_api.c:415 -msgid "Could not find record to remove" +#: src/namestore/namestore_api.c:431 +msgid "unknown internal error in namestore" msgstr "" -#: src/namestore/namestore_api.c:422 -msgid "Failed to create new signature" +#: src/namestore/namestore_api.c:436 +msgid "Protocol error" msgstr "" -#: src/namestore/namestore_api.c:429 -msgid "Failed to put new set of records in database" +#: src/namestore/namestore_common.c:530 src/namestore/namestore_common.c:670 +#, c-format +msgid "Unsupported record type %d\n" +msgstr "" + +#: src/namestore/namestore_common.c:537 +#, c-format +msgid "Unable to parse IPv4 address `%s'\n" +msgstr "" + +#: src/namestore/namestore_common.c:560 +#, c-format +msgid "Unable to parse SOA record `%s'\n" +msgstr "" + +#: src/namestore/namestore_common.c:583 +#, c-format +msgid "Unable to parse MX record `%s'\n" +msgstr "" + +#: src/namestore/namestore_common.c:601 +#, c-format +msgid "Unable to parse IPv6 address `%s'\n" +msgstr "" + +#: src/namestore/namestore_common.c:614 +#, c-format +msgid "Unable to parse PKEY record `%s'\n" +msgstr "" + +#: src/namestore/namestore_common.c:635 +#, c-format +msgid "Unable to parse VPN record string `%s'\n" +msgstr "" + +#: src/namestore/namestore_common.c:661 +#, c-format +msgid "Unable to parse TLSA record string `%s'\n" +msgstr "" + +#: src/namestore/plugin_namestore_postgres.c:95 +msgid "Failed to create indices\n" msgstr "" #: src/nat/gnunet-nat-server.c:279 @@ -3554,11 +3756,65 @@ msgstr "" msgid "Please pass valid port number as the first argument! (got `%s')\n" msgstr "" -#: src/nat/gnunet-nat-server.c:318 +#: src/nat/gnunet-nat-server.c:321 msgid "GNUnet NAT traversal test helper daemon" msgstr "" -#: src/nat/nat.c:799 +#: src/nat/nat_auto.c:169 +msgid "NAT traversal with ICMP Server timed out.\n" +msgstr "" + +#: src/nat/nat_auto.c:199 +msgid "NAT traversal with ICMP Server succeeded.\n" +msgstr "" + +#: src/nat/nat_auto.c:200 +msgid "NAT traversal with ICMP Server failed.\n" +msgstr "" + +#: src/nat/nat_auto.c:219 +msgid "Testing connection reversal with ICMP server.\n" +msgstr "" + +#: src/nat/nat_auto.c:265 +#, c-format +msgid "Detected external IP `%s'\n" +msgstr "" + +#: src/nat/nat_auto.c:331 +msgid "This system has a global IPv6 address, setting IPv6 to supported.\n" +msgstr "" + +#: src/nat/nat_auto.c:347 +#, c-format +msgid "Detected internal network address `%s'.\n" +msgstr "" + +#: src/nat/nat_auto.c:400 +msgid "upnpc found, enabling its use\n" +msgstr "" + +#: src/nat/nat_auto.c:401 +msgid "upnpc not found\n" +msgstr "" + +#: src/nat/nat_auto.c:434 +msgid "gnunet-helper-nat-server found, testing it\n" +msgstr "" + +#: src/nat/nat_auto.c:435 +msgid "No working gnunet-helper-nat-server found\n" +msgstr "" + +#: src/nat/nat_auto.c:469 +msgid "gnunet-helper-nat-client found, enabling it\n" +msgstr "" + +#: src/nat/nat_auto.c:470 +msgid "gnunet-helper-nat-client not found or behind NAT, disabling it\n" +msgstr "" + +#: src/nat/nat.c:795 #, c-format msgid "gnunet-helper-nat-server generated malformed address `%s'\n" msgstr "" @@ -3568,27 +3824,34 @@ msgstr "" msgid "Failed to start %s\n" msgstr "" -#: src/nat/nat.c:1111 -#, c-format -msgid "Malformed %s `%s' given in configuration!\n" +#: src/nat/nat.c:1113 +msgid "malformed" msgstr "" -#: src/nat/nat.c:1177 src/nat/nat.c:1187 +#: src/nat/nat.c:1179 src/nat/nat.c:1191 #, c-format msgid "" "Configuration requires `%s', but binary is not installed properly (SUID bit " "not set). Option disabled.\n" msgstr "" -#: src/nat/nat.c:1321 +#: src/nat/nat.c:1326 msgid "Internal IP address not known, cannot use ICMP NAT traversal method\n" msgstr "" -#: src/nat/nat.c:1332 +#: src/nat/nat.c:1337 #, c-format msgid "Running gnunet-helper-nat-client %s %s %u\n" msgstr "" +#: src/nat/nat_mini.c:170 +msgid "`external-ip' command not found\n" +msgstr "" + +#: src/nat/nat_mini.c:505 +msgid "`upnpc' command not found\n" +msgstr "" + #: src/nat/nat_test.c:341 msgid "Failed to connect to `gnunet-nat-server'\n" msgstr "" @@ -3598,77 +3861,109 @@ msgstr "" msgid "Failed to create listen socket bound to `%s' for NAT test: %s\n" msgstr "" -#: src/nse/gnunet-nse-profiler.c:928 +#: src/nse/gnunet-nse-profiler.c:1009 +msgid "limit to the number of connections to NSE services, 0 for none" +msgstr "" + +#: src/nse/gnunet-nse-profiler.c:1012 +msgid "name of the file for writing connection information and statistics" +msgstr "" + +#: src/nse/gnunet-nse-profiler.c:1015 +msgid "name of the file with the login information for the testbed" +msgstr "" + +#: src/nse/gnunet-nse-profiler.c:1018 +msgid "IP address of this system as seen by the rest of the testbed" +msgstr "" + +#: src/nse/gnunet-nse-profiler.c:1021 +msgid "delay between queries to statistics during a round" +msgstr "" + +#: src/nse/gnunet-nse-profiler.c:1024 +msgid "prefix of the filenames we use for writing the topology for each round" +msgstr "" + +#: src/nse/gnunet-nse-profiler.c:1027 +msgid "name of the file for writing the main results" +msgstr "" + +#: src/nse/gnunet-nse-profiler.c:1030 +msgid "Number of peers to run in each round, separated by commas" +msgstr "" + +#: src/nse/gnunet-nse-profiler.c:1036 +msgid "delay between rounds" +msgstr "" + +#: src/nse/gnunet-nse-profiler.c:1046 msgid "Measure quality and performance of the NSE service." msgstr "" -#: src/nse/gnunet-service-nse.c:925 +#: src/nse/gnunet-service-nse.c:1389 #, c-format -msgid "Proof of work invalid: %llu!\n" +msgid "NSE service could not access hostkey: %s\n" msgstr "" -#: src/nse/gnunet-service-nse.c:1381 src/nse/gnunet-service-nse.c:1400 -#: src/nse/gnunet-service-nse.c:1421 +#: src/nse/gnunet-service-nse.c:1403 src/nse/gnunet-service-nse.c:1478 +#: src/nse/gnunet-service-nse.c:1495 msgid "NSE service is lacking key configuration settings. Exiting.\n" msgstr "" -#: src/nse/gnunet-service-nse.c:1388 +#: src/nse/gnunet-service-nse.c:1485 msgid "Invalid work requirement for NSE service. Exiting.\n" msgstr "" -#: src/nse/gnunet-service-nse.c:1409 -msgid "NSE service could not access hostkey. Exiting.\n" -msgstr "" - #: src/peerinfo/gnunet-service-peerinfo.c:134 #, c-format msgid "Removing expired address of transport `%s'\n" msgstr "" -#: src/peerinfo/gnunet-service-peerinfo.c:203 +#: src/peerinfo/gnunet-service-peerinfo.c:230 #, c-format msgid "Failed to parse HELLO in file `%s'\n" msgstr "" -#: src/peerinfo/gnunet-service-peerinfo.c:229 +#: src/peerinfo/gnunet-service-peerinfo.c:269 msgid "# peers known" msgstr "" -#: src/peerinfo/gnunet-service-peerinfo.c:254 +#: src/peerinfo/gnunet-service-peerinfo.c:297 #, c-format msgid "" "File `%s' in directory `%s' does not match naming convention. Removed.\n" msgstr "" -#: src/peerinfo/gnunet-service-peerinfo.c:353 +#: src/peerinfo/gnunet-service-peerinfo.c:419 #, c-format msgid "Still no peers found in `%s'!\n" msgstr "" -#: src/peerinfo/gnunet-service-peerinfo.c:710 +#: src/peerinfo/gnunet-service-peerinfo.c:807 #, c-format msgid "Importing HELLOs from `%s'\n" msgstr "" -#: src/peerinfo/peerinfo_api.c:238 +#: src/peerinfo/peerinfo_api.c:239 msgid "aborted due to explicit disconnect request" msgstr "" -#: src/peerinfo/peerinfo_api.c:358 +#: src/peerinfo/peerinfo_api.c:359 msgid "failed to transmit request (service down?)" msgstr "" -#: src/peerinfo/peerinfo_api.c:505 +#: src/peerinfo/peerinfo_api.c:509 msgid "Failed to receive response from `PEERINFO' service." msgstr "" -#: src/peerinfo/peerinfo_api.c:531 src/peerinfo/peerinfo_api.c:550 -#: src/peerinfo/peerinfo_api.c:565 src/peerinfo/peerinfo_api.c:576 -#: src/peerinfo/peerinfo_api.c:587 +#: src/peerinfo/peerinfo_api.c:550 src/peerinfo/peerinfo_api.c:569 +#: src/peerinfo/peerinfo_api.c:584 src/peerinfo/peerinfo_api.c:595 +#: src/peerinfo/peerinfo_api.c:606 msgid "Received invalid message from `PEERINFO' service." msgstr "" -#: src/peerinfo/peerinfo_api.c:663 +#: src/peerinfo/peerinfo_api.c:681 msgid "Timeout transmitting iteration request to `PEERINFO' service." msgstr "" @@ -3677,87 +3972,51 @@ msgstr "" msgid "Could not connect to `%s' service.\n" msgstr "" -#: src/peerinfo-tool/gnunet-peerinfo.c:581 -msgid "Failed to parse HELLO message: missing expiration time\n" -msgstr "" - -#: src/peerinfo-tool/gnunet-peerinfo.c:589 -msgid "Failed to parse HELLO message: invalid expiration time\n" -msgstr "" - -#: src/peerinfo-tool/gnunet-peerinfo.c:598 -msgid "Failed to parse HELLO message: malformed\n" -msgstr "" - -#: src/peerinfo-tool/gnunet-peerinfo.c:608 -msgid "Failed to parse HELLO message: missing transport plugin\n" -msgstr "" - -#: src/peerinfo-tool/gnunet-peerinfo.c:625 -#, c-format -msgid "Plugin `%s' not found\n" -msgstr "" - -#: src/peerinfo-tool/gnunet-peerinfo.c:634 -#, c-format -msgid "Plugin `%s' does not support URIs yet\n" -msgstr "" - -#: src/peerinfo-tool/gnunet-peerinfo.c:653 -#, c-format -msgid "Failed to parse `%s' as an address for plugin `%s'\n" -msgstr "" - -#: src/peerinfo-tool/gnunet-peerinfo.c:685 +#: src/peerinfo-tool/gnunet-peerinfo.c:419 #, c-format msgid "Failure adding HELLO: %s\n" msgstr "" -#: src/peerinfo-tool/gnunet-peerinfo.c:833 +#: src/peerinfo-tool/gnunet-peerinfo.c:557 #, c-format msgid "Could not find option `%s:%s' in configuration.\n" msgstr "" -#: src/peerinfo-tool/gnunet-peerinfo.c:840 +#: src/peerinfo-tool/gnunet-peerinfo.c:563 #, c-format msgid "Loading hostkey from `%s' failed.\n" msgstr "" -#: src/peerinfo-tool/gnunet-peerinfo.c:875 -#, c-format -msgid "Invalid URI `%s'\n" -msgstr "" - -#: src/peerinfo-tool/gnunet-peerinfo.c:899 +#: src/peerinfo-tool/gnunet-peerinfo.c:622 #, c-format msgid "I am peer `%s'.\n" msgstr "" -#: src/peerinfo-tool/gnunet-peerinfo.c:936 +#: src/peerinfo-tool/gnunet-peerinfo.c:648 msgid "don't resolve host names" msgstr "" -#: src/peerinfo-tool/gnunet-peerinfo.c:939 +#: src/peerinfo-tool/gnunet-peerinfo.c:651 msgid "output only the identity strings" msgstr "" -#: src/peerinfo-tool/gnunet-peerinfo.c:942 +#: src/peerinfo-tool/gnunet-peerinfo.c:654 msgid "output our own identity only" msgstr "" -#: src/peerinfo-tool/gnunet-peerinfo.c:945 +#: src/peerinfo-tool/gnunet-peerinfo.c:657 msgid "list all known peers" msgstr "" -#: src/peerinfo-tool/gnunet-peerinfo.c:948 +#: src/peerinfo-tool/gnunet-peerinfo.c:660 msgid "also output HELLO uri(s)" msgstr "" -#: src/peerinfo-tool/gnunet-peerinfo.c:951 +#: src/peerinfo-tool/gnunet-peerinfo.c:663 msgid "add given HELLO uri to the database" msgstr "" -#: src/peerinfo-tool/gnunet-peerinfo.c:957 +#: src/peerinfo-tool/gnunet-peerinfo.c:674 msgid "Print information about peers." msgstr "" @@ -3843,434 +4102,538 @@ msgstr "" msgid "Failed to connect to %s service. Exiting.\n" msgstr "" -#: src/pt/gnunet-daemon-pt.c:973 +#: src/pt/gnunet-daemon-pt.c:976 msgid "Daemon to run to perform IP protocol translation to GNUnet" msgstr "" -#: src/statistics/gnunet-service-statistics.c:271 +#: src/regex/gnunet-daemon-regexprofiler.c:293 #, c-format -msgid "Loading %llu bytes of statistics from `%s'\n" +msgid "Regexprofiler could not access hostkey: %s. Exiting.\n" msgstr "" -#: src/statistics/gnunet-service-statistics.c:330 +#: src/regex/gnunet-daemon-regexprofiler.c:452 +msgid "Daemon to announce regular expressions for the peer using mesh." +msgstr "" + +#: src/regex/gnunet-regex-profiler.c:1147 +msgid "An operation has failed while starting peers\n" +msgstr "" + +#: src/regex/gnunet-regex-profiler.c:1193 #, c-format -msgid "Wrote %llu bytes of statistics to `%s'\n" +msgid "Creating a peer failed. Error: %s\n" msgstr "" -#: src/statistics/gnunet-statistics.c:122 -msgid "Failed to obtain statistics.\n" +#: src/regex/gnunet-regex-profiler.c:1320 +msgid "An operation has failed while starting slaves\n" msgstr "" -#: src/statistics/gnunet-statistics.c:199 +#: src/regex/gnunet-regex-profiler.c:1342 #, c-format -msgid "No subsystem or name given\n" +msgid "No files found in `%s'\n" msgstr "" -#: src/statistics/gnunet-statistics.c:207 +#: src/regex/gnunet-regex-profiler.c:1397 +msgid "An operation has failed while linking\n" +msgstr "" + +#: src/regex/gnunet-regex-profiler.c:1508 +#: src/testbed/testbed_api_testbed.c:805 #, c-format -msgid "Failed to initialize watch routine\n" +msgid "Host registration failed for a host. Error: %s\n" msgstr "" -#: src/statistics/gnunet-statistics.c:227 -msgid "limit output to statistics for the given NAME" +#: src/regex/gnunet-regex-profiler.c:1589 +msgid "Unable to connect to master controller -- Check config\n" msgstr "" -#: src/statistics/gnunet-statistics.c:230 -msgid "make the value being set persistent" +#: src/regex/gnunet-regex-profiler.c:1691 +#: src/testbed/testbed_api_testbed.c:970 +#, c-format +msgid "Host %s cannot start testbed\n" msgstr "" -#: src/statistics/gnunet-statistics.c:233 -msgid "limit output to the given SUBSYSTEM" +#: src/regex/gnunet-regex-profiler.c:1694 +#: src/testbed/testbed_api_testbed.c:974 +msgid "Testbed cannot be started on localhost\n" msgstr "" -#: src/statistics/gnunet-statistics.c:236 -msgid "just print the statistics value" +#: src/regex/gnunet-regex-profiler.c:1734 +#, c-format +msgid "No hosts-file specified on command line. Exiting.\n" msgstr "" -#: src/statistics/gnunet-statistics.c:239 -msgid "watch value continously" +#: src/regex/gnunet-regex-profiler.c:1739 +#: src/regex/gnunet-regex-simulation-profiler.c:622 +#, c-format +msgid "No policy directory specified on command line. Exiting.\n" msgstr "" -#: src/statistics/gnunet-statistics.c:246 -msgid "Print statistics about GNUnet operations." +#: src/regex/gnunet-regex-profiler.c:1745 +#: src/testbed/testbed_api_testbed.c:1065 +#, c-format +msgid "No hosts loaded. Need at least one host\n" msgstr "" -#: src/statistics/statistics_api.c:456 -msgid "Could not save some persistent statistics\n" +#: src/regex/gnunet-regex-profiler.c:1748 +#, c-format +msgid "Checking whether given hosts can start testbed. Please wait\n" msgstr "" -#: src/statistics/statistics_api.c:999 -msgid "" -"Failed to receive acknowledgement from statistics service, some statistics " -"might have been lost!\n" +#: src/regex/gnunet-regex-profiler.c:1769 +#, c-format +msgid "Exiting\n" msgstr "" -#: src/testing/gnunet-testing.c:157 -msgid "Could not read hostkeys file, specify hostkey file with -H!\n" +#: src/regex/gnunet-regex-profiler.c:1775 +#, c-format +msgid "No configuration file given. Exiting\n" msgstr "" -#: src/testing/gnunet-testing.c:159 +#: src/regex/gnunet-regex-profiler.c:1784 #, c-format -msgid "Specified hostkey file `%s' not found!\n" +msgid "Configuration option (regex_prefix) missing. Exiting\n" msgstr "" -#: src/testing/gnunet-testing.c:273 -msgid "create unique configuration files" +#: src/regex/gnunet-regex-profiler.c:1802 +#: src/regex/gnunet-regex-simulation-profiler.c:629 +#, c-format +msgid "Specified policies directory does not exist. Exiting.\n" msgstr "" -#: src/testing/gnunet-testing.c:275 -msgid "create hostkey files from pre-computed hostkey list" +#: src/regex/gnunet-regex-profiler.c:1809 +#, c-format +msgid "No search strings file given. Exiting.\n" msgstr "" -#: src/testing/gnunet-testing.c:277 -msgid "host key file" +#: src/regex/gnunet-regex-profiler.c:1817 +#, c-format +msgid "" +"Error loading search strings. Given file does not contain enough strings. " +"Exiting.\n" msgstr "" -#: src/testing/gnunet-testing.c:279 -msgid "number of unique configuration files or hostkeys to create" +#: src/regex/gnunet-regex-profiler.c:1823 +#, c-format +msgid "Error loading search strings. Exiting.\n" msgstr "" -#: src/testing/gnunet-testing.c:281 -msgid "configuration template" +#: src/regex/gnunet-regex-profiler.c:1850 +msgid "name of the file for writing statistics" msgstr "" -#: src/testing/gnunet-testing.c:287 -msgid "Command line tool to access the testing library" +#: src/regex/gnunet-regex-profiler.c:1853 +msgid "create COUNT number of random links between peers" msgstr "" -#: src/testing/helper.c:56 -msgid "Peer is lacking HOSTKEY configuration setting.\n" +#: src/regex/gnunet-regex-profiler.c:1856 +msgid "wait TIMEOUT before considering a string match as failed" msgstr "" -#: src/testing/helper.c:64 -msgid "Could not access hostkey.\n" +#: src/regex/gnunet-regex-profiler.c:1859 +msgid "wait DELAY before starting string search" msgstr "" -#: src/testing/testing.c:200 -msgid "`scp' does not seem to terminate (timeout copying config).\n" +#: src/regex/gnunet-regex-profiler.c:1862 +msgid "number of search strings to read from search strings file" msgstr "" -#: src/testing/testing.c:214 src/testing/testing.c:798 -msgid "`scp' did not complete cleanly.\n" +#: src/regex/gnunet-regex-profiler.c:1865 +#: src/regex/gnunet-regex-simulation-profiler.c:692 +msgid "maximum path compression length" msgstr "" -#: src/testing/testing.c:237 -msgid "Failed to create pipe for `gnunet-peerinfo' process.\n" +#: src/regex/gnunet-regex-profiler.c:1868 +msgid "" +"if this option is set, only one peer is responsible for searching all strings" +msgstr "" + +#: src/regex/gnunet-regex-profiler.c:1881 +msgid "Profiler for regex" +msgstr "" + +#: src/regex/gnunet-regex-simulation-profiler.c:689 +msgid "name of the table to write DFAs" +msgstr "" + +#: src/regex/gnunet-regex-simulation-profiler.c:705 +msgid "Profiler for regex library" +msgstr "" + +#: src/statistics/gnunet-service-statistics.c:271 +#, c-format +msgid "Loading %llu bytes of statistics from `%s'\n" +msgstr "" + +#: src/statistics/gnunet-service-statistics.c:330 +#, c-format +msgid "Wrote %llu bytes of statistics to `%s'\n" msgstr "" -#: src/testing/testing.c:238 -msgid "Failed to create pipe for `ssh' process.\n" +#: src/statistics/gnunet-statistics.c:141 +msgid "Failed to obtain statistics.\n" msgstr "" -#: src/testing/testing.c:286 +#: src/statistics/gnunet-statistics.c:143 #, c-format -msgid "Could not start `%s' process to create hostkey.\n" +msgid "Failed to obtain statistics from host `%s:%llu'\n" msgstr "" -#: src/testing/testing.c:293 -msgid "Failed to start `gnunet-peerinfo' process.\n" +#: src/statistics/gnunet-statistics.c:181 +#, c-format +msgid "Trying to connect to remote host, but service `%s' is not running\n" msgstr "" -#: src/testing/testing.c:294 src/testing/testing.c:471 -msgid "Failed to start `ssh' process.\n" +#: src/statistics/gnunet-statistics.c:190 +#, c-format +msgid "A port is required to connect to host `%s'\n" msgstr "" -#: src/testing/testing.c:354 +#: src/statistics/gnunet-statistics.c:196 #, c-format -msgid "Error reading from gnunet-peerinfo: %s\n" +msgid "A port has to be between 1 and 65535 to connect to host `%s'\n" msgstr "" -#: src/testing/testing.c:358 -msgid "Malformed output from gnunet-peerinfo!\n" +#: src/statistics/gnunet-statistics.c:210 +msgid "Missing argument: subsystem \n" msgstr "" -#: src/testing/testing.c:368 -msgid "Failed to get hostkey!\n" +#: src/statistics/gnunet-statistics.c:216 +msgid "Missing argument: name\n" msgstr "" -#: src/testing/testing.c:400 -msgid "`Failed while waiting for topology setup!\n" +#: src/statistics/gnunet-statistics.c:247 +#, c-format +msgid "No subsystem or name given\n" msgstr "" -#: src/testing/testing.c:463 +#: src/statistics/gnunet-statistics.c:255 #, c-format -msgid "Could not start `%s' process to start GNUnet.\n" +msgid "Failed to initialize watch routine\n" msgstr "" -#: src/testing/testing.c:470 -msgid "Failed to start `gnunet-arm' process.\n" +#: src/statistics/gnunet-statistics.c:310 +msgid "limit output to statistics for the given NAME" msgstr "" -#: src/testing/testing.c:493 src/testing/testing.c:600 -msgid "`gnunet-arm' does not seem to terminate.\n" +#: src/statistics/gnunet-statistics.c:313 +msgid "make the value being set persistent" msgstr "" -#: src/testing/testing.c:494 src/testing/testing.c:601 -#: src/testing/testing.c:621 -msgid "`ssh' does not seem to terminate.\n" +#: src/statistics/gnunet-statistics.c:316 +msgid "limit output to the given SUBSYSTEM" msgstr "" -#: src/testing/testing.c:570 -msgid "Unable to get HELLO for peer!\n" +#: src/statistics/gnunet-statistics.c:319 +msgid "just print the statistics value" msgstr "" -#: src/testing/testing.c:620 -msgid "`gnunet-arm' terminated with non-zero exit status (or timed out)!\n" +#: src/statistics/gnunet-statistics.c:322 +msgid "watch value continuously" msgstr "" -#: src/testing/testing.c:643 src/testing/testing.c:675 -msgid "either `gnunet-arm' or `ssh' does not seem to terminate.\n" +#: src/statistics/gnunet-statistics.c:325 +msgid "connect to remote host" msgstr "" -#: src/testing/testing.c:658 src/testing/testing.c:713 -msgid "shutdown (either `gnunet-arm' or `ssh') did not complete cleanly.\n" +#: src/statistics/gnunet-statistics.c:328 +msgid "port for remote host" msgstr "" -#: src/testing/testing.c:786 -msgid "`scp' does not seem to terminate.\n" +#: src/statistics/gnunet-statistics.c:340 +msgid "Print statistics about GNUnet operations." msgstr "" -#: src/testing/testing.c:948 +#: src/statistics/statistics_api.c:511 +msgid "Could not save some persistent statistics\n" +msgstr "" + +#: src/statistics/statistics_api.c:1056 +msgid "" +"Failed to receive acknowledgement from statistics service, some statistics " +"might have been lost!\n" +msgstr "" + +#: src/sysmon/gnunet-service-sysmon.c:546 #, c-format -msgid "Starting service %s for peer `%4s'\n" +msgid "Could not parse execution interval for `%s', set to default 60 sec.\n" msgstr "" -#: src/testing/testing.c:1207 src/testing/testing_group.c:6154 +#: src/testbed/gnunet-testbed-profiler.c:231 #, c-format -msgid "Could not start `%s' process to copy configuration directory.\n" +msgid "No hosts-file specified on command line\n" +msgstr "" + +#: src/testbed/gnunet-testbed-profiler.c:261 +msgid "create COUNT number of peers" msgstr "" -#: src/testing/testing.c:1292 src/testing/testing.c:1359 +#: src/testbed/gnunet-testbed-profiler.c:264 +msgid "tolerate COUNT number of continious timeout failures" +msgstr "" + +#: src/testbed/gnunet-testbed-profiler.c:276 +msgid "Profiler for testbed" +msgstr "" + +#: src/testbed/ll_master.c:57 #, c-format -msgid "Terminating peer `%4s'\n" +msgid "Job command file not given. Exiting\n" msgstr "" -#: src/testing/testing.c:1448 +#: src/testbed/testbed_api.c:499 #, c-format -msgid "Setting d->dead on peer `%4s'\n" +msgid "Adding host %u failed with error: %s\n" msgstr "" -#: src/testing/testing.c:1601 -msgid "Peer not yet running, can not change configuration at this point." +#: src/testbed/testbed_api_hosts.c:306 +#, c-format +msgid "Hosts file %s not found\n" msgstr "" -#: src/testing/testing.c:1609 -msgid "Failed to write new configuration to disk." +#: src/testbed/testbed_api_hosts.c:314 +#, c-format +msgid "Hosts file %s has no data\n" msgstr "" -#: src/testing/testing.c:1636 +#: src/testbed/testbed_api_hosts.c:321 #, c-format -msgid "Could not start `%s' process to copy configuration file.\n" +msgid "Hosts file %s cannot be read\n" +msgstr "" + +#: src/testbed/testbed_api_testbed.c:623 +msgid "Linking controllers failed. Exiting" msgstr "" -#: src/testing/testing.c:1639 -msgid "Failed to copy new configuration to remote machine." +#: src/testbed/testbed_api_testbed.c:1009 +msgid "Cannot start the master controller" msgstr "" -#: src/testing/testing.c:1794 -msgid "Peers failed to connect" +#: src/testbed/testbed_api_testbed.c:1089 +msgid "Specified topology must be supported by testbed" msgstr "" -#: src/testing/testing.c:1922 -msgid "Failed to connect to core service of first peer!\n" +#: src/testbed/testbed_api_topology.c:668 +#, c-format +msgid "Topology file %s not found\n" msgstr "" -#: src/testing/testing.c:2145 -msgid "Peers are not fully running yet, can not connect!\n" +#: src/testbed/testbed_api_topology.c:674 +#, c-format +msgid "Topology file %s has no data\n" msgstr "" -#: src/testing/testing_group.c:1895 src/testing/testing_group.c:1907 -#: src/testing/testing_group.c:2008 src/testing/testing_group.c:2065 -#: src/testing/testing_group.c:2152 src/testing/testing_group.c:2172 -#: src/testing/testing_group.c:2302 src/testing/testing_peergroup.c:950 +#: src/testbed/testbed_api_topology.c:681 #, c-format -msgid "Invalid value `%s' for option `%s' in section `%s': expected float\n" +msgid "Topology file %s cannot be read\n" msgstr "" -#: src/testing/testing_group.c:2160 +#: src/testbed/testbed_api_topology.c:704 #, c-format -msgid "" -"Invalid value `%s' for option `%s' in section `%s': got %f, needed value " -"greater than 0\n" +msgid "Failed to read peer index from toology file: %s" msgstr "" -#: src/testing/testing_group.c:2877 src/testing/testing_group.c:3063 +#: src/testbed/testbed_api_topology.c:713 +#: src/testbed/testbed_api_topology.c:737 #, c-format -msgid "" -"No `%s' specified in peer configuration in section `%s', cannot copy friends " -"file!\n" +msgid "Value in given topology file: %s out of range\n" msgstr "" -#: src/testing/testing_group.c:3957 -msgid "Creating no allowed topology (all peers can connect at core level)\n" +#: src/testbed/testbed_api_topology.c:719 +#: src/testbed/testbed_api_topology.c:743 +#, c-format +msgid "Failed to read peer index from topology file: %s" msgstr "" -#: src/testing/testing_group.c:5226 -msgid "Unknown topology specification, can't connect peers!\n" +#: src/testbed/testbed_api_topology.c:725 +#: src/testbed/testbed_api_topology.c:749 +msgid "Topology file needs more peers than given ones\n" msgstr "" -#: src/testing/testing_group.c:5944 src/transport/transport-testing.c:636 -msgid "Could not read hostkeys file!\n" +#: src/testbed/testbed_api_topology.c:764 +#, c-format +msgid "Ignoring to connect peer %u to peer %u\n" msgstr "" -#: src/testing/testing_group.c:6011 +#: src/testing/gnunet-testing.c:132 #, c-format -msgid "Could not create configuration for peer number %u on `%s'!\n" +msgid "Could not extract hostkey %u (offset too large?)\n" +msgstr "" + +#: src/testing/gnunet-testing.c:203 +msgid "create unique configuration files" +msgstr "" + +#: src/testing/gnunet-testing.c:205 +msgid "extract hostkey file from pre-computed hostkey list" +msgstr "" + +#: src/testing/gnunet-testing.c:207 +msgid "" +"number of unique configuration files to create, or number of the hostkey to " +"extract" msgstr "" -#: src/testing/testing_new.c:169 -msgid "tmppath cannot be NULL\n" +#: src/testing/gnunet-testing.c:209 +msgid "configuration template" +msgstr "" + +#: src/testing/gnunet-testing.c:218 +msgid "Command line tool to access the testing library" msgstr "" -#: src/testing/testing_new.c:356 +#: src/testing/gnunet-testing-run-service.c:129 #, c-format -msgid "Hostkeys file not found: %s\n" +msgid "Unknown command, use 'q' to quit or 'r' to restart peer\n" +msgstr "" + +#: src/testing/gnunet-testing-run-service.c:186 +msgid "name of the template configuration file to use (optional)" msgstr "" -#: src/testing/testing_new.c:365 +#: src/testing/gnunet-testing-run-service.c:189 +msgid "name of the service to run" +msgstr "" + +#: src/testing/testing.c:211 #, c-format -msgid "Could not open hostkeys file: %s\n" +msgid "Hostkeys file not found: %s\n" msgstr "" -#: src/testing/testing_new.c:380 +#: src/testing/testing.c:227 #, c-format msgid "Incorrect hostkey file format: %s\n" msgstr "" -#: src/testing/testing_new.c:437 +#: src/testing/testing.c:541 #, c-format msgid "Key number %u does not exist\n" msgstr "" -#: src/testing/testing_new.c:446 +#: src/testing/testing.c:551 #, c-format msgid "Error while decoding key %u\n" msgstr "" -#: src/testing/testing_new.c:680 +#: src/testing/testing.c:865 msgid "Failed to create configuration for peer (not enough free ports?)\n" msgstr "" -#: src/testing/testing_new.c:691 +#: src/testing/testing.c:876 #, c-format msgid "" "You attempted to create a testbed with more than %u hosts. Please " "precompute more hostkeys first.\n" msgstr "" -#: src/testing/testing_new.c:704 +#: src/testing/testing.c:890 #, c-format msgid "Failed to initialize hostkey for peer %u\n" msgstr "" -#: src/testing/testing_new.c:734 +#: src/testing/testing.c:923 #, c-format msgid "Failed to write hostkey file for peer %u: %s\n" msgstr "" -#: src/testing/testing_new.c:751 +#: src/testing/testing.c:941 #, c-format msgid "Failed to write configuration file `%s' for peer %u: %s\n" msgstr "" -#: src/testing/testing_new.c:791 +#: src/testing/testing.c:1014 #, c-format msgid "Failed to start `%s': %s\n" msgstr "" -#: src/testing/testing_new.c:959 +#: src/testing/testing.c:1219 #, c-format msgid "Failed to load configuration from %s\n" msgstr "" -#: src/topology/gnunet-daemon-topology.c:259 +#: src/topology/gnunet-daemon-topology.c:254 msgid "# peers blacklisted" msgstr "" -#: src/topology/gnunet-daemon-topology.c:392 +#: src/topology/gnunet-daemon-topology.c:387 msgid "# connect requests issued to transport" msgstr "" -#: src/topology/gnunet-daemon-topology.c:730 -#: src/topology/gnunet-daemon-topology.c:815 +#: src/topology/gnunet-daemon-topology.c:725 +#: src/topology/gnunet-daemon-topology.c:810 msgid "# friends connected" msgstr "" -#: src/topology/gnunet-daemon-topology.c:996 +#: src/topology/gnunet-daemon-topology.c:991 msgid "Failed to connect to core service, can not manage topology!\n" msgstr "" -#: src/topology/gnunet-daemon-topology.c:1026 -#, c-format -msgid "Option `%s' in section `%s' not specified!\n" -msgstr "" - -#: src/topology/gnunet-daemon-topology.c:1039 +#: src/topology/gnunet-daemon-topology.c:1034 #, c-format msgid "Could not read friends list `%s'\n" msgstr "" -#: src/topology/gnunet-daemon-topology.c:1045 +#: src/topology/gnunet-daemon-topology.c:1040 #, c-format msgid "Friends file `%s' is empty.\n" msgstr "" -#: src/topology/gnunet-daemon-topology.c:1054 +#: src/topology/gnunet-daemon-topology.c:1049 #, c-format msgid "Failed to read friends list from `%s': out of memory\n" msgstr "" -#: src/topology/gnunet-daemon-topology.c:1062 +#: src/topology/gnunet-daemon-topology.c:1057 #, c-format msgid "Failed to read friends list from `%s'\n" msgstr "" -#: src/topology/gnunet-daemon-topology.c:1082 +#: src/topology/gnunet-daemon-topology.c:1077 #, c-format msgid "" "Syntax error in topology specification at offset %llu, skipping bytes.\n" msgstr "" -#: src/topology/gnunet-daemon-topology.c:1095 +#: src/topology/gnunet-daemon-topology.c:1090 #, c-format msgid "" "Syntax error in topology specification at offset %llu, skipping bytes `%s'.\n" msgstr "" -#: src/topology/gnunet-daemon-topology.c:1105 +#: src/topology/gnunet-daemon-topology.c:1100 #, c-format msgid "Found friend `%s' in configuration\n" msgstr "" -#: src/topology/gnunet-daemon-topology.c:1111 +#: src/topology/gnunet-daemon-topology.c:1106 #, c-format msgid "Found myself `%s' in friend list (useless, ignored)\n" msgstr "" -#: src/topology/gnunet-daemon-topology.c:1121 +#: src/topology/gnunet-daemon-topology.c:1116 msgid "# friends in configuration" msgstr "" -#: src/topology/gnunet-daemon-topology.c:1127 +#: src/topology/gnunet-daemon-topology.c:1122 msgid "" "Fewer friends specified than required by minimum friend count. Will only " "connect to friends.\n" msgstr "" -#: src/topology/gnunet-daemon-topology.c:1134 +#: src/topology/gnunet-daemon-topology.c:1129 msgid "" "More friendly connections required than target total number of connections.\n" msgstr "" -#: src/topology/gnunet-daemon-topology.c:1169 +#: src/topology/gnunet-daemon-topology.c:1164 msgid "# HELLO messages received" msgstr "" -#: src/topology/gnunet-daemon-topology.c:1224 +#: src/topology/gnunet-daemon-topology.c:1219 msgid "# HELLO messages gossipped" msgstr "" -#: src/topology/gnunet-daemon-topology.c:1363 +#: src/topology/gnunet-daemon-topology.c:1358 msgid "GNUnet topology control (maintaining P2P mesh and F2F constraints)" msgstr "" @@ -4279,11 +4642,6 @@ msgstr "" msgid "Could not read blacklist file `%s'\n" msgstr "" -#: src/transport/gnunet-service-transport_blacklist.c:252 -#, c-format -msgid "Blacklist file `%s' is empty.\n" -msgstr "" - #: src/transport/gnunet-service-transport_blacklist.c:263 #, c-format msgid "Failed to read blacklist from `%s'\n" @@ -4312,151 +4670,156 @@ msgid "Found myself `%s' in blacklist (useless, ignored)\n" msgstr "" #: src/transport/gnunet-service-transport_blacklist.c:514 -#: src/transport/gnunet-service-transport_blacklist.c:747 +#: src/transport/gnunet-service-transport_blacklist.c:752 msgid "# disconnects due to blacklist" msgstr "" -#: src/transport/gnunet-service-transport.c:163 +#: src/transport/gnunet-service-transport.c:183 msgid "# bytes payload discarded due to not connected peer " msgstr "" -#: src/transport/gnunet-service-transport.c:237 +#: src/transport/gnunet-service-transport.c:258 msgid "# bytes total received" msgstr "" -#: src/transport/gnunet-service-transport.c:284 +#: src/transport/gnunet-service-transport.c:305 msgid "# bytes payload received" msgstr "" -#: src/transport/gnunet-service-transport.c:582 -msgid "Transport service is lacking key configuration settings. Exiting.\n" +#: src/transport/gnunet-service-transport.c:614 +#, c-format +msgid "Transport service could not access hostkey: %s. Exiting.\n" msgstr "" -#: src/transport/gnunet-service-transport.c:591 -msgid "Transport service could not access hostkey. Exiting.\n" +#: src/transport/gnunet-service-transport.c:625 +msgid "Could not access STATISTICS service. Exiting.\n" msgstr "" -#: src/transport/gnunet-service-transport_clients.c:352 +#: src/transport/gnunet-service-transport.c:720 +msgid "Transport service is lacking key configuration settings. Exiting.\n" +msgstr "" + +#: src/transport/gnunet-service-transport_clients.c:389 #, c-format msgid "Dropping message of type %u and size %u, have %u/%u messages pending\n" msgstr "" -#: src/transport/gnunet-service-transport_clients.c:357 +#: src/transport/gnunet-service-transport_clients.c:394 msgid "# messages dropped due to slow client" msgstr "" -#: src/transport/gnunet-service-transport_clients.c:503 +#: src/transport/gnunet-service-transport_clients.c:546 #, c-format msgid "Rejecting control connection from peer `%s', which is not me!\n" msgstr "" -#: src/transport/gnunet-service-transport_clients.c:631 +#: src/transport/gnunet-service-transport_clients.c:687 msgid "# bytes payload dropped (other peer was not connected)" msgstr "" -#: src/transport/gnunet-service-transport_clients.c:682 +#: src/transport/gnunet-service-transport_clients.c:738 msgid "# REQUEST CONNECT messages received" msgstr "" -#: src/transport/gnunet-service-transport_hello.c:172 +#: src/transport/gnunet-service-transport_hello.c:175 msgid "# refreshed my HELLO" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:1032 +#: src/transport/gnunet-service-transport_neighbours.c:1227 msgid "# DISCONNECT messages sent" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:1148 -#: src/transport/gnunet-service-transport_neighbours.c:1482 +#: src/transport/gnunet-service-transport_neighbours.c:1357 +#: src/transport/gnunet-service-transport_neighbours.c:1694 msgid "# bytes in message queue for other peers" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:1153 +#: src/transport/gnunet-service-transport_neighbours.c:1362 msgid "# messages transmitted to other peers" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:1158 +#: src/transport/gnunet-service-transport_neighbours.c:1367 msgid "# transmission failures for messages to other peers" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:1215 +#: src/transport/gnunet-service-transport_neighbours.c:1424 msgid "# messages timed out while in transport queue" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:1254 +#: src/transport/gnunet-service-transport_neighbours.c:1466 msgid "# keepalives sent" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:1278 +#: src/transport/gnunet-service-transport_neighbours.c:1490 msgid "# KEEPALIVE messages discarded (peer unknown)" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:1286 +#: src/transport/gnunet-service-transport_neighbours.c:1498 msgid "# KEEPALIVE messages discarded (no session)" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:1323 +#: src/transport/gnunet-service-transport_neighbours.c:1535 msgid "# KEEPALIVE_RESPONSE messages discarded (not connected)" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:1332 +#: src/transport/gnunet-service-transport_neighbours.c:1544 msgid "# KEEPALIVE_RESPONSE messages discarded (not expected)" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:1388 +#: src/transport/gnunet-service-transport_neighbours.c:1600 msgid "# messages discarded due to lack of neighbour record" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:1422 +#: src/transport/gnunet-service-transport_neighbours.c:1634 msgid "# bandwidth quota violations by other peers" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:1438 +#: src/transport/gnunet-service-transport_neighbours.c:1650 msgid "# ms throttling suggested" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:2544 +#: src/transport/gnunet-service-transport_neighbours.c:2802 msgid "# unexpected CONNECT_ACK messages (no peer)" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:2559 -#: src/transport/gnunet-service-transport_neighbours.c:2585 +#: src/transport/gnunet-service-transport_neighbours.c:2817 +#: src/transport/gnunet-service-transport_neighbours.c:2851 msgid "# unexpected CONNECT_ACK messages (not ready)" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:2598 +#: src/transport/gnunet-service-transport_neighbours.c:2864 msgid "# unexpected CONNECT_ACK messages (waiting on ATS)" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:2627 +#: src/transport/gnunet-service-transport_neighbours.c:2897 msgid "# unexpected CONNECT_ACK messages (disconnecting)" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:2807 +#: src/transport/gnunet-service-transport_neighbours.c:3082 msgid "# unexpected SESSION ACK messages" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:2856 +#: src/transport/gnunet-service-transport_neighbours.c:3137 msgid "# SET QUOTA messages ignored (no such peer)" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:2870 +#: src/transport/gnunet-service-transport_neighbours.c:3151 msgid "# disconnects due to quota of 0" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:2901 +#: src/transport/gnunet-service-transport_neighbours.c:3182 msgid "# disconnect messages ignored (old format)" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:2912 +#: src/transport/gnunet-service-transport_neighbours.c:3193 msgid "# disconnect messages ignored (timestamp)" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:2943 +#: src/transport/gnunet-service-transport_neighbours.c:3224 msgid "# other peer asked to disconnect from us" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:3020 +#: src/transport/gnunet-service-transport_neighbours.c:3319 msgid "# disconnected from peer upon explicit request" msgstr "" @@ -4464,295 +4827,475 @@ msgstr "" msgid "Transport service is lacking NEIGHBOUR_LIMIT option.\n" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:414 +#: src/transport/gnunet-service-transport_validation.c:425 msgid "# address records discarded" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:463 +#: src/transport/gnunet-service-transport_validation.c:487 #, c-format msgid "" "Not transmitting `%s' with `%s', message too big (%u bytes!). This should " "not happen.\n" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:512 +#: src/transport/gnunet-service-transport_validation.c:536 msgid "# PING without HELLO messages sent" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:570 +#: src/transport/gnunet-service-transport_validation.c:618 msgid "# address revalidations started" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:805 +#: src/transport/gnunet-service-transport_validation.c:860 msgid "# PING message for different peer received" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:840 +#: src/transport/gnunet-service-transport_validation.c:925 #, c-format -msgid "" -"Not confirming PING with address `%s' since I cannot confirm having this " -"address.\n" +msgid "Received a PING message with validation bug from `%s'\n" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:924 +#: src/transport/gnunet-service-transport_validation.c:1054 msgid "# PONGs unicast via reliable transport" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:933 +#: src/transport/gnunet-service-transport_validation.c:1063 msgid "# PONGs multicast to all available addresses" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:1055 +#: src/transport/gnunet-service-transport_validation.c:1188 msgid "# PONGs dropped, no matching pending validation" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:1080 +#: src/transport/gnunet-service-transport_validation.c:1216 msgid "# PONGs dropped, signature expired" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:1136 +#: src/transport/gnunet-service-transport_validation.c:1270 #, c-format msgid "Adding `%s' without addresses for peer `%s'\n" msgstr "" -#: src/transport/gnunet-transport.c:260 -msgid "No transport plugins configured, peer will never communicate\n" +#: src/transport/gnunet-transport.c:266 +#, c-format +msgid "Transmitted %llu bytes/s (%llu bytes in %s)\n" msgstr "" #: src/transport/gnunet-transport.c:273 #, c-format -msgid "No port configured for plugin `%s', cannot test it\n" +msgid "Received %llu bytes/s (%llu bytes in %s)\n" msgstr "" -#: src/transport/gnunet-transport.c:323 +#: src/transport/gnunet-transport.c:303 #, c-format -msgid "Received %llu bytes/s (%llu bytes in %llu ms)\n" +msgid "Failed to connect to `%s'\n" msgstr "" -#: src/transport/gnunet-transport.c:330 +#: src/transport/gnunet-transport.c:316 #, c-format -msgid "Transmitted %llu bytes/s (%llu bytes in %llu ms)\n" +msgid "Failed to resolve address for peer `%s'\n" msgstr "" -#: src/transport/gnunet-transport.c:363 +#: src/transport/gnunet-transport.c:325 +msgid "Failed to list connections, timeout occured\n" +msgstr "" + +#: src/transport/gnunet-transport.c:429 +msgid "No transport plugins configured, peer will never communicate\n" +msgstr "" + +#: src/transport/gnunet-transport.c:442 +#, c-format +msgid "No port configured for plugin `%s', cannot test it\n" +msgstr "" + +#: src/transport/gnunet-transport.c:506 #, c-format msgid "Transmitting %u bytes to %s\n" msgstr "" -#: src/transport/gnunet-transport.c:383 +#: src/transport/gnunet-transport.c:531 +#, c-format +msgid "Successfully connected to `%s'\n" +msgstr "" + +#: src/transport/gnunet-transport.c:553 #, c-format -msgid "Connected to %s\n" +msgid "" +"Successfully connected to `%s', starting to send benchmark data in %u Kb " +"blocks\n" msgstr "" -#: src/transport/gnunet-transport.c:414 +#: src/transport/gnunet-transport.c:588 #, c-format -msgid "Disconnected from %s\n" +msgid "Disconnected from peer `%s' while benchmarking\n" msgstr "" -#: src/transport/gnunet-transport.c:443 +#: src/transport/gnunet-transport.c:664 #, c-format msgid "Received %u bytes from %s\n" msgstr "" -#: src/transport/gnunet-transport.c:466 +#: src/transport/gnunet-transport.c:687 #, c-format msgid "Peer `%s': %s %s\n" msgstr "" -#: src/transport/gnunet-transport.c:473 +#: src/transport/gnunet-transport.c:702 #, c-format msgid "Peer `%s': %s \n" msgstr "" -#: src/transport/gnunet-transport.c:501 +#: src/transport/gnunet-transport.c:766 #, c-format msgid "Peer `%s' disconnected\n" msgstr "" -#: src/transport/gnunet-transport.c:569 +#: src/transport/gnunet-transport.c:794 +msgid "Failed to send connect request to transport service\n" +msgstr "" + +#: src/transport/gnunet-transport.c:828 #, c-format -msgid "Failed to parse peer identity `%s'\n" +msgid "" +"Multiple operations given. Please choose only one operation: %s, %s, %s, %s, " +"%s, %s\n" msgstr "" -#: src/transport/gnunet-transport.c:618 -msgid "measure how fast we are receiving data (until CTRL-C)" +#: src/transport/gnunet-transport.c:834 +#, c-format +msgid "" +"No operation given. Please choose one operation: %s, %s, %s, %s, %s, %s\n" msgstr "" -#: src/transport/gnunet-transport.c:621 -msgid "try to connect to the given peer" +#: src/transport/gnunet-transport.c:854 src/transport/gnunet-transport.c:884 +#: src/transport/gnunet-transport.c:906 src/transport/gnunet-transport.c:945 +msgid "Failed to connect to transport service\n" msgstr "" -#: src/transport/gnunet-transport.c:624 +#: src/transport/gnunet-transport.c:861 src/transport/gnunet-transport.c:891 +msgid "Failed to send request to transport service\n" +msgstr "" + +#: src/transport/gnunet-transport.c:911 +msgid "Starting to receive benchmark data\n" +msgstr "" + +#: src/transport/gnunet-transport.c:996 +msgid "measure how fast we are receiving data from all peers (until CTRL-C)" +msgstr "" + +#: src/transport/gnunet-transport.c:999 +msgid "connect to a peer" +msgstr "" + +#: src/transport/gnunet-transport.c:1002 msgid "provide information about all current connections (once)" msgstr "" -#: src/transport/gnunet-transport.c:627 -msgid "provide information about all current connections (continuously)" +#: src/transport/gnunet-transport.c:1008 +msgid "" +"provide information about all connects and disconnect events (continuously)" msgstr "" -#: src/transport/gnunet-transport.c:630 +#: src/transport/gnunet-transport.c:1011 msgid "do not resolve hostnames" msgstr "" -#: src/transport/gnunet-transport.c:634 +#: src/transport/gnunet-transport.c:1014 +msgid "peer identity" +msgstr "" + +#: src/transport/gnunet-transport.c:1018 msgid "send data for benchmarking to the other peer (until CTRL-C)" msgstr "" -#: src/transport/gnunet-transport.c:637 +#: src/transport/gnunet-transport.c:1021 msgid "test transport configuration (involves external server)" msgstr "" -#: src/transport/gnunet-transport.c:645 +#: src/transport/gnunet-transport.c:1032 msgid "Direct access to transport service." msgstr "" -#: src/transport/plugin_transport_http.c:1100 +#: src/transport/plugin_transport_http.c:817 +#: src/transport/plugin_transport_http_server.c:2556 msgid "Disabling IPv6 since it is not supported on this system!\n" msgstr "" -#: src/transport/plugin_transport_http.c:1149 +#: src/transport/plugin_transport_http.c:866 +#: src/transport/plugin_transport_http_server.c:2324 msgid "Require valid port number for service in configuration!\n" msgstr "" -#: src/transport/plugin_transport_http.c:1174 src/util/service.c:1036 +#: src/transport/plugin_transport_http.c:898 +#: src/transport/plugin_transport_http_server.c:2356 src/util/service.c:1053 #, c-format msgid "Failed to resolve `%s': %s\n" msgstr "" -#: src/transport/plugin_transport_http.c:1191 src/util/service.c:1053 +#: src/transport/plugin_transport_http.c:915 +#: src/transport/plugin_transport_http_server.c:2373 src/util/service.c:1070 #, c-format msgid "Failed to find %saddress for `%s'.\n" msgstr "" -#: src/transport/plugin_transport_http.c:1296 +#: src/transport/plugin_transport_http.c:1020 +#: src/transport/plugin_transport_http_server.c:2484 #, c-format msgid "Found %u addresses to report to NAT service\n" msgstr "" -#: src/transport/plugin_transport_http.c:1309 -#, c-format -msgid "FREEING %s\n" -msgstr "" - -#: src/transport/plugin_transport_http.c:1386 +#: src/transport/plugin_transport_http.c:1133 +#: src/transport/plugin_transport_http_server.c:2652 msgid "Neither IPv4 nor IPv6 are enabled! Fix in configuration\n" msgstr "" -#: src/transport/plugin_transport_http.c:1399 +#: src/transport/plugin_transport_http.c:1146 +#: src/transport/plugin_transport_http_server.c:2663 msgid "Port is required! Fix in configuration\n" msgstr "" -#: src/transport/plugin_transport_http.c:1410 +#: src/transport/plugin_transport_http.c:1157 msgid "Port 0, client only mode\n" msgstr "" -#: src/transport/plugin_transport_http.c:1430 +#: src/transport/plugin_transport_http.c:1177 #, c-format msgid "" "Specific IPv4 address `%s' for plugin %s in configuration file is invalid! " "Binding to all addresses!\n" msgstr "" -#: src/transport/plugin_transport_http.c:1460 +#: src/transport/plugin_transport_http.c:1206 #, c-format msgid "" "Specific IPv6 address `%s' for plugin %s in configuration file is invalid! " "Binding to all addresses!\n" msgstr "" -#: src/transport/plugin_transport_http_client.c:624 +#: src/transport/plugin_transport_http.c:1223 +#: src/transport/plugin_transport_http_server.c:2745 +#, c-format +msgid "Using external hostname `%s'\n" +msgstr "" + +#: src/transport/plugin_transport_http.c:1228 +msgid "No external hostname configured\n" +msgstr "" + +#: src/transport/plugin_transport_http_client.c:1516 #, c-format msgid "Could not initialize curl multi handle, failed to start %s plugin!\n" msgstr "" -#: src/transport/plugin_transport_http_server.c:178 +#: src/transport/plugin_transport_http_client.c:1647 +#: src/transport/plugin_transport_http_server.c:2869 +#, c-format +msgid "Shutting down plugin `%s'\n" +msgstr "" + +#: src/transport/plugin_transport_http_client.c:1672 +#: src/transport/plugin_transport_http_server.c:2928 +#, c-format +msgid "Shutdown for plugin `%s' complete\n" +msgstr "" + +#: src/transport/plugin_transport_http_client.c:1700 +#: src/transport/plugin_transport_http_server.c:2775 +#, c-format +msgid "Maximum number of connections is %u\n" +msgstr "" + +#: src/transport/plugin_transport_http_server.c:1342 +#, c-format +msgid "" +"Access from connection %p (%u of %u) for `%s' `%s' url `%s' with upload data " +"size %u\n" +msgstr "" + +#: src/transport/plugin_transport_http_server.c:1603 +#, c-format +msgid "Accepting connection (%u of %u) from `%s'\n" +msgstr "" + +#: src/transport/plugin_transport_http_server.c:1611 +#, c-format +msgid "" +"Server reached maximum number connections (%u), rejecting new connection\n" +msgstr "" + +#: src/transport/plugin_transport_http_server.c:1912 msgid "" "Could not create a new TLS certificate, program `gnunet-transport-" "certificate-creation' could not be started!\n" msgstr "" -#: src/transport/plugin_transport_http_server.c:202 +#: src/transport/plugin_transport_http_server.c:1936 msgid "No usable TLS certificate found and creating one failed!\n" msgstr "" -#: src/transport/plugin_transport_tcp.c:591 +#: src/transport/plugin_transport_http_server.c:2631 +#, c-format +msgid "IPv4 support is %s\n" +msgstr "" + +#: src/transport/plugin_transport_http_server.c:2645 +#, c-format +msgid "IPv6 support is %s\n" +msgstr "" + +#: src/transport/plugin_transport_http_server.c:2670 +#, c-format +msgid "Using port %u\n" +msgstr "" + +#: src/transport/plugin_transport_http_server.c:2685 +#, c-format +msgid "Specific IPv4 address `%s' in configuration file is invalid!\n" +msgstr "" + +#: src/transport/plugin_transport_http_server.c:2695 +#, c-format +msgid "Binding to IPv4 address %s\n" +msgstr "" + +#: src/transport/plugin_transport_http_server.c:2716 +#, c-format +msgid "Specific IPv6 address `%s' in configuration file is invalid!\n" +msgstr "" + +#: src/transport/plugin_transport_http_server.c:2726 +#, c-format +msgid "Binding to IPv6 address %s\n" +msgstr "" + +#: src/transport/plugin_transport_http_server.c:2761 +#, c-format +msgid "Notifying transport only about hostname `%s'\n" +msgstr "" + +#: src/transport/plugin_transport_smtp.c:370 +#, c-format +msgid "Received malformed message via %s. Ignored.\n" +msgstr "" + +#: src/transport/plugin_transport_smtp.c:457 +msgid "SMTP filter string to invalid, lacks ': '\n" +msgstr "" + +#: src/transport/plugin_transport_smtp.c:466 +#, c-format +msgid "SMTP filter string to long, capped to `%s'\n" +msgstr "" + +#: src/transport/plugin_transport_smtp.c:561 +#: src/transport/plugin_transport_smtp.c:571 +#: src/transport/plugin_transport_smtp.c:584 +#: src/transport/plugin_transport_smtp.c:603 +#: src/transport/plugin_transport_smtp.c:626 +#: src/transport/plugin_transport_smtp.c:634 +#: src/transport/plugin_transport_smtp.c:647 +#: src/transport/plugin_transport_smtp.c:658 +#, c-format +msgid "SMTP: `%s' failed: %s.\n" +msgstr "" + +#: src/transport/plugin_transport_smtp.c:799 +msgid "No email-address specified, can not start SMTP transport.\n" +msgstr "" + +#: src/transport/plugin_transport_smtp.c:811 +msgid "# bytes received via SMTP" +msgstr "" + +#: src/transport/plugin_transport_smtp.c:812 +msgid "# bytes sent via SMTP" +msgstr "" + +#: src/transport/plugin_transport_smtp.c:814 +msgid "# bytes dropped by SMTP (outgoing)" +msgstr "" + +#: src/transport/plugin_transport_tcp.c:595 #, c-format msgid "Unexpected address length: %u bytes\n" msgstr "" -#: src/transport/plugin_transport_tcp.c:767 -#: src/transport/plugin_transport_tcp.c:856 -#: src/transport/plugin_transport_tcp.c:906 -#: src/transport/plugin_transport_tcp.c:992 -#: src/transport/plugin_transport_tcp.c:1086 -#: src/transport/plugin_transport_tcp.c:1103 +#: src/transport/plugin_transport_tcp.c:771 +#: src/transport/plugin_transport_tcp.c:860 +#: src/transport/plugin_transport_tcp.c:910 +#: src/transport/plugin_transport_tcp.c:996 +#: src/transport/plugin_transport_tcp.c:1139 +#: src/transport/plugin_transport_tcp.c:1156 msgid "# bytes currently in TCP buffers" msgstr "" -#: src/transport/plugin_transport_tcp.c:774 -#: src/transport/plugin_transport_tcp.c:963 -#: src/transport/plugin_transport_tcp.c:1761 -#: src/transport/plugin_transport_tcp.c:2390 +#: src/transport/plugin_transport_tcp.c:778 +#: src/transport/plugin_transport_tcp.c:967 +#: src/transport/plugin_transport_tcp.c:1826 +#: src/transport/plugin_transport_tcp.c:2462 msgid "# TCP sessions active" msgstr "" -#: src/transport/plugin_transport_tcp.c:860 +#: src/transport/plugin_transport_tcp.c:864 msgid "# bytes discarded by TCP (timeout)" msgstr "" -#: src/transport/plugin_transport_tcp.c:909 +#: src/transport/plugin_transport_tcp.c:913 msgid "# bytes transmitted via TCP" msgstr "" -#: src/transport/plugin_transport_tcp.c:996 +#: src/transport/plugin_transport_tcp.c:1000 msgid "# bytes discarded by TCP (disconnect)" msgstr "" -#: src/transport/plugin_transport_tcp.c:1290 +#: src/transport/plugin_transport_tcp.c:1113 +#, c-format +msgid "Trying to send with invalid session %p\n" +msgstr "" + +#: src/transport/plugin_transport_tcp.c:1349 #, c-format msgid "Address of unexpected length: %u\n" msgstr "" -#: src/transport/plugin_transport_tcp.c:1401 +#: src/transport/plugin_transport_tcp.c:1466 msgid "# transport-service disconnect requests for TCP" msgstr "" -#: src/transport/plugin_transport_tcp.c:1802 +#: src/transport/plugin_transport_tcp.c:1867 msgid "# TCP WELCOME messages received" msgstr "" -#: src/transport/plugin_transport_tcp.c:1973 +#: src/transport/plugin_transport_tcp.c:2046 msgid "# bytes received via TCP" msgstr "" -#: src/transport/plugin_transport_tcp.c:2043 +#: src/transport/plugin_transport_tcp.c:2124 msgid "# network-level TCP disconnect events" msgstr "" -#: src/transport/plugin_transport_tcp.c:2279 src/util/service.c:940 +#: src/transport/plugin_transport_tcp.c:2350 src/util/service.c:948 +#: src/util/service.c:954 #, c-format msgid "Require valid port number for service `%s' in configuration!\n" msgstr "" -#: src/transport/plugin_transport_tcp.c:2293 +#: src/transport/plugin_transport_tcp.c:2364 msgid "Failed to start service.\n" msgstr "" -#: src/transport/plugin_transport_tcp.c:2355 -#, c-format -msgid "Failed to find option %s in section %s!\n" -msgstr "" - -#: src/transport/plugin_transport_tcp.c:2378 +#: src/transport/plugin_transport_tcp.c:2450 #, c-format msgid "TCP transport listening on port %llu\n" msgstr "" -#: src/transport/plugin_transport_tcp.c:2382 +#: src/transport/plugin_transport_tcp.c:2454 msgid "TCP transport not listening on any port (client only)\n" msgstr "" -#: src/transport/plugin_transport_tcp.c:2386 +#: src/transport/plugin_transport_tcp.c:2458 #, c-format msgid "TCP transport advertises itself as being on port %llu\n" msgstr "" @@ -4765,114 +5308,116 @@ msgstr "" msgid "# IPv4 broadcast HELLO beacons received via udp" msgstr "" -#: src/transport/plugin_transport_udp_broadcasting.c:367 +#: src/transport/plugin_transport_udp_broadcasting.c:394 #, c-format msgid "Failed to set IPv4 broadcast option for broadcast socket on port %d\n" msgstr "" -#: src/transport/plugin_transport_udp.c:1894 +#: src/transport/plugin_transport_udp.c:2517 +#, c-format +msgid "" +"UDP could not transmit message to `%s': Network seems down, please check " +"your network configuration\n" +msgstr "" + +#: src/transport/plugin_transport_udp.c:2531 #, c-format msgid "" -"UDP could not message to `%s': `%s'. Please check your network configuration " -"and disable IPv6 if your connection does not have a global IPv6 address\n" +"UDP could not transmit message to `%s': Please check your network " +"configuration and disable IPv6 if your connection does not have a global " +"IPv6 address\n" msgstr "" -#: src/transport/plugin_transport_udp.c:2138 +#: src/transport/plugin_transport_udp.c:2772 msgid "Failed to open UDP sockets\n" msgstr "" -#: src/transport/plugin_transport_udp.c:2306 +#: src/transport/plugin_transport_udp.c:2848 #, c-format msgid "Given `%s' option is out of range: %llu > %u\n" msgstr "" -#: src/transport/plugin_transport_udp.c:2349 +#: src/transport/plugin_transport_udp.c:2891 #, c-format msgid "Invalid IPv6 address: `%s'\n" msgstr "" -#: src/transport/plugin_transport_unix.c:1356 +#: src/transport/plugin_transport_unix.c:1357 msgid "Failed to open UNIX sockets\n" msgstr "" -#: src/transport/plugin_transport_wlan.c:561 +#: src/transport/plugin_transport_wlan.c:580 msgid "# WLAN ACKs sent" msgstr "" -#: src/transport/plugin_transport_wlan.c:580 +#: src/transport/plugin_transport_wlan.c:599 msgid "# WLAN messages defragmented" msgstr "" -#: src/transport/plugin_transport_wlan.c:626 -#: src/transport/plugin_transport_wlan.c:676 -#: src/transport/plugin_transport_wlan.c:1696 +#: src/transport/plugin_transport_wlan.c:645 +#: src/transport/plugin_transport_wlan.c:695 +#: src/transport/plugin_transport_wlan.c:1758 msgid "# WLAN sessions allocated" msgstr "" -#: src/transport/plugin_transport_wlan.c:749 +#: src/transport/plugin_transport_wlan.c:770 msgid "# WLAN message fragments sent" msgstr "" -#: src/transport/plugin_transport_wlan.c:767 +#: src/transport/plugin_transport_wlan.c:794 msgid "# WLAN messages pending (with fragmentation)" msgstr "" -#: src/transport/plugin_transport_wlan.c:867 -#: src/transport/plugin_transport_wlan.c:948 -#: src/transport/plugin_transport_wlan.c:1698 +#: src/transport/plugin_transport_wlan.c:902 +#: src/transport/plugin_transport_wlan.c:987 +#: src/transport/plugin_transport_wlan.c:1760 msgid "# WLAN MAC endpoints allocated" msgstr "" -#: src/transport/plugin_transport_wlan.c:1119 +#: src/transport/plugin_transport_wlan.c:1169 msgid "# HELLO messages received via WLAN" msgstr "" -#: src/transport/plugin_transport_wlan.c:1140 +#: src/transport/plugin_transport_wlan.c:1190 msgid "# fragments received via WLAN" msgstr "" -#: src/transport/plugin_transport_wlan.c:1150 +#: src/transport/plugin_transport_wlan.c:1200 msgid "# ACKs received via WLAN" msgstr "" -#: src/transport/plugin_transport_wlan.c:1207 +#: src/transport/plugin_transport_wlan.c:1257 msgid "# WLAN DATA messages discarded due to CRC32 error" msgstr "" -#: src/transport/plugin_transport_wlan.c:1306 +#: src/transport/plugin_transport_wlan.c:1358 msgid "# DATA messages received via WLAN" msgstr "" -#: src/transport/plugin_transport_wlan.c:1341 +#: src/transport/plugin_transport_wlan.c:1393 msgid "# WLAN DATA messages processed" msgstr "" -#: src/transport/plugin_transport_wlan.c:1402 +#: src/transport/plugin_transport_wlan.c:1454 msgid "# HELLO beacons sent via WLAN" msgstr "" -#: src/transport/plugin_transport_wlan.c:1511 +#: src/transport/plugin_transport_wlan.c:1563 msgid "WLAN address with invalid size encountered\n" msgstr "" -#: src/transport/plugin_transport_wlan.c:1668 -#, c-format -msgid "Invalid configuration option `%s' in section `%s'\n" -msgstr "" - -#: src/transport/plugin_transport_wlan.c:1677 +#: src/transport/plugin_transport_wlan.c:1739 #, c-format msgid "Helper binary `%s' not SUID, cannot run WLAN transport\n" msgstr "" -#: src/transport/plugin_transport_wlan.c:1687 +#: src/transport/transport_api.c:659 #, c-format -msgid "Missing configuration option `%s' in section `%s'\n" +msgid "Received unexpected message of type %u in %s:%u\n" msgstr "" -#: src/transport/transport_api.c:570 -#, c-format -msgid "Received unexpected message of type %u in %s:%u\n" +#: src/transport/transport-testing.c:586 +msgid "Failed to initialize testing library!\n" msgstr "" #: src/util/bio.c:136 src/util/bio.c:142 @@ -4904,259 +5449,308 @@ msgstr "" msgid "Metadata `%s' failed to deserialize" msgstr "" -#: src/util/client.c:359 +#: src/util/client.c:276 src/util/client.c:753 src/util/service.c:984 +#, c-format +msgid "UNIXPATH `%s' too long, maximum length is %llu\n" +msgstr "" + +#: src/util/client.c:280 src/util/client.c:757 src/util/service.c:988 +#, c-format +msgid "Using `%s' instead\n" +msgstr "" + +#: src/util/client.c:371 #, c-format msgid "" "Could not determine valid hostname and port for service `%s' from " "configuration.\n" msgstr "" -#: src/util/client.c:367 +#: src/util/client.c:379 #, c-format msgid "Need a non-empty hostname for service `%s'.\n" msgstr "" -#: src/util/client.c:685 +#: src/util/client.c:698 msgid "Failure to transmit TEST request.\n" msgstr "" -#: src/util/client.c:740 src/util/service.c:970 -#, c-format -msgid "UNIXPATH `%s' too long, maximum length is %llu\n" -msgstr "" - -#: src/util/client.c:882 +#: src/util/client.c:898 #, c-format msgid "Could not connect to service `%s', must not be running.\n" msgstr "" -#: src/util/client.c:896 +#: src/util/client.c:912 #, c-format msgid "Failure to transmit request to service `%s'\n" msgstr "" -#: src/util/client.c:1149 +#: src/util/client.c:1177 msgid "Could not submit request, not expecting to receive a response.\n" msgstr "" -#: src/util/common_logging.c:239 src/util/common_logging.c:890 +#: src/util/common_logging.c:258 src/util/common_logging.c:1007 msgid "DEBUG" msgstr "" -#: src/util/common_logging.c:241 src/util/common_logging.c:888 +#: src/util/common_logging.c:260 src/util/common_logging.c:1005 msgid "INFO" msgstr "" -#: src/util/common_logging.c:243 src/util/common_logging.c:886 +#: src/util/common_logging.c:262 src/util/common_logging.c:1003 msgid "WARNING" msgstr "" -#: src/util/common_logging.c:245 src/util/common_logging.c:884 +#: src/util/common_logging.c:264 src/util/common_logging.c:1001 msgid "ERROR" msgstr "" -#: src/util/common_logging.c:247 src/util/common_logging.c:892 +#: src/util/common_logging.c:266 src/util/common_logging.c:1009 msgid "NONE" msgstr "" -#: src/util/common_logging.c:610 +#: src/util/common_logging.c:395 #, c-format msgid "Failed to create or access directory for log file `%s'\n" msgstr "" -#: src/util/common_logging.c:725 +#: src/util/common_logging.c:819 #, c-format msgid "Message `%.*s' repeated %u times in the last %s\n" msgstr "" -#: src/util/common_logging.c:893 +#: src/util/common_logging.c:1010 msgid "INVALID" msgstr "" -#: src/util/common_logging.c:992 +#: src/util/common_logging.c:1149 msgid "unknown address" msgstr "" -#: src/util/common_logging.c:1030 +#: src/util/common_logging.c:1187 msgid "invalid address" msgstr "" -#: src/util/configuration.c:244 +#: src/util/common_logging.c:1205 #, c-format -msgid "Syntax error in configuration file `%s' at line %u.\n" +msgid "Configuration fails to specify option `%s' in section `%s'!\n" msgstr "" -#: src/util/configuration.c:816 +#: src/util/common_logging.c:1226 +#, c-format +msgid "" +"Configuration specifies invalid value for option `%s' in section `%s': %s\n" +msgstr "" + +#: src/util/configuration.c:291 +#, c-format +msgid "Syntax error while deserializing in line %u\n" +msgstr "" + +#: src/util/configuration.c:998 #, c-format msgid "" "Configuration value '%s' for '%s' in section '%s' is not in set of legal " "choices\n" msgstr "" -#: src/util/connection.c:420 +#: src/util/connection.c:427 #, c-format msgid "Access denied to `%s'\n" msgstr "" -#: src/util/connection.c:435 +#: src/util/connection.c:442 #, c-format msgid "Accepting connection from `%s': %p\n" msgstr "" -#: src/util/connection.c:550 +#: src/util/connection.c:557 #, c-format msgid "" "Failed to establish TCP connection to `%s:%u', no further addresses to try.\n" msgstr "" -#: src/util/connection.c:739 src/util/connection.c:909 +#: src/util/connection.c:755 src/util/connection.c:922 #, c-format msgid "Trying to connect to `%s' (%p)\n" msgstr "" -#: src/util/connection.c:748 -#, c-format -msgid "Failed to connect to `%s' (%p)\n" -msgstr "" - -#: src/util/connection.c:900 +#: src/util/connection.c:913 #, c-format msgid "Attempt to connect to `%s' failed\n" msgstr "" -#: src/util/container_bloomfilter.c:510 +#: src/util/container_bloomfilter.c:518 #, c-format msgid "" "Size of file on disk is incorrect for this Bloom filter (want %llu, have " "%llu)\n" msgstr "" -#: src/util/crypto_random.c:280 +#: src/util/crypto_ecc.c:441 #, c-format -msgid "Starting `%s' process to generate entropy\n" +msgid "" +"File `%s' does not contain a valid private key (too long, %llu bytes). " +"Deleting it.\n" msgstr "" -#: src/util/crypto_random.c:309 +#: src/util/crypto_ecc.c:456 src/util/crypto_rsa.c:660 #, c-format -msgid "libgcrypt has not the expected version (version %s is required).\n" +msgid "" +"File `%s' does not contain a valid private key (failed decode, %llu bytes). " +"Deleting it.\n" msgstr "" -#: src/util/crypto_rsa.c:661 src/util/crypto_rsa.c:708 +#: src/util/crypto_ecc.c:552 src/util/crypto_ecc.c:596 +#: src/util/crypto_rsa.c:757 src/util/crypto_rsa.c:801 #, c-format -msgid "Could not aquire lock on file `%s': %s...\n" +msgid "Could not acquire lock on file `%s': %s...\n" msgstr "" -#: src/util/crypto_rsa.c:666 +#: src/util/crypto_ecc.c:557 src/util/crypto_rsa.c:762 msgid "Creating a new private key. This may take a while.\n" msgstr "" -#: src/util/crypto_rsa.c:684 +#: src/util/crypto_ecc.c:600 src/util/crypto_rsa.c:805 +#: src/util/crypto_rsa.c:841 +msgid "This may be ok if someone is currently generating a private key.\n" +msgstr "" + +#: src/util/crypto_ecc.c:631 src/util/crypto_rsa.c:836 #, c-format -msgid "I am host `%s'. Stored new private key in `%s'.\n" +msgid "" +"When trying to read key file `%s' I found %u bytes but I need at least %u.\n" msgstr "" -#: src/util/crypto_rsa.c:712 src/util/crypto_rsa.c:748 -msgid "This may be ok if someone is currently generating a hostkey.\n" +#: src/util/crypto_ecc.c:636 +msgid "This may be ok if someone is currently generating a key.\n" msgstr "" -#: src/util/crypto_rsa.c:743 +#: src/util/crypto_ecc.c:651 src/util/crypto_rsa.c:856 #, c-format -msgid "" -"When trying to read hostkey file `%s' I found %u bytes but I need at least " -"%u.\n" +msgid "File `%s' does not contain a valid private key. Deleting it.\n" msgstr "" -#: src/util/crypto_rsa.c:763 +#: src/util/crypto_ecc.c:773 src/util/crypto_rsa.c:941 +msgid "interrupted by shutdown" +msgstr "" + +#: src/util/crypto_ecc.c:784 +msgid "gnunet-ecc failed" +msgstr "" + +#: src/util/crypto_ecc.c:979 #, c-format -msgid "File `%s' does not contain a valid private key. Deleting it.\n" +msgid "ECC signing failed at %s:%d: %s\n" +msgstr "" + +#: src/util/crypto_ecc.c:1047 +#, c-format +msgid "ECC signature verification failed at %s:%d: %s\n" +msgstr "" + +#: src/util/crypto_random.c:313 +#, c-format +msgid "Starting `%s' process to generate entropy\n" +msgstr "" + +#: src/util/crypto_random.c:342 +#, c-format +msgid "libgcrypt has not the expected version (version %s is required).\n" msgstr "" -#: src/util/crypto_rsa.c:781 +#: src/util/crypto_rsa.c:644 #, c-format -msgid "I am host `%s'. Read private key from `%s'.\n" +msgid "" +"File `%s' does not contain a valid private key (too long, %llu bytes). " +"Renaming it.\n" +msgstr "" + +#: src/util/crypto_rsa.c:952 +msgid "gnunet-rsa failed" msgstr "" -#: src/util/crypto_rsa.c:1032 +#: src/util/crypto_rsa.c:1343 #, c-format msgid "RSA signature verification failed at %s:%d: %s\n" msgstr "" -#: src/util/disk.c:498 +#: src/util/disk.c:601 #, c-format msgid "`%s' failed for drive `%S': %u\n" msgstr "" -#: src/util/disk.c:1062 +#: src/util/disk.c:1205 #, c-format msgid "Expected `%s' to be a directory!\n" msgstr "" -#: src/util/disk.c:1416 src/util/service.c:1650 +#: src/util/disk.c:1559 src/util/service.c:1669 #, c-format msgid "Cannot obtain information about user `%s': %s\n" msgstr "" -#: src/util/disk.c:1734 +#: src/util/disk.c:1931 #, c-format msgid "No `%s' specified for service `%s' in configuration.\n" msgstr "" -#: src/util/getopt.c:669 +#: src/util/getopt.c:570 #, c-format msgid "%s: option `%s' is ambiguous\n" msgstr "" -#: src/util/getopt.c:693 +#: src/util/getopt.c:594 #, c-format msgid "%s: option `--%s' does not allow an argument\n" msgstr "" -#: src/util/getopt.c:698 +#: src/util/getopt.c:599 #, c-format msgid "%s: option `%c%s' does not allow an argument\n" msgstr "" -#: src/util/getopt.c:715 src/util/getopt.c:883 +#: src/util/getopt.c:616 src/util/getopt.c:783 #, c-format msgid "%s: option `%s' requires an argument\n" msgstr "" -#: src/util/getopt.c:744 +#: src/util/getopt.c:645 #, c-format msgid "%s: unrecognized option `--%s'\n" msgstr "" -#: src/util/getopt.c:748 +#: src/util/getopt.c:649 #, c-format msgid "%s: unrecognized option `%c%s'\n" msgstr "" -#: src/util/getopt.c:773 +#: src/util/getopt.c:674 #, c-format msgid "%s: illegal option -- %c\n" msgstr "" -#: src/util/getopt.c:775 +#: src/util/getopt.c:676 #, c-format msgid "%s: invalid option -- %c\n" msgstr "" -#: src/util/getopt.c:803 src/util/getopt.c:931 +#: src/util/getopt.c:704 src/util/getopt.c:831 #, c-format msgid "%s: option requires an argument -- %c\n" msgstr "" -#: src/util/getopt.c:851 +#: src/util/getopt.c:752 #, c-format msgid "%s: option `-W %s' is ambiguous\n" msgstr "" -#: src/util/getopt.c:869 +#: src/util/getopt.c:770 #, c-format msgid "%s: option `-W %s' does not allow an argument\n" msgstr "" -#: src/util/getopt.c:1035 +#: src/util/getopt.c:935 #, c-format msgid "Use %s to get a list of options.\n" msgstr "" @@ -5167,37 +5761,108 @@ msgid "" "Arguments mandatory for long options are also mandatory for short options.\n" msgstr "" -#: src/util/getopt_helpers.c:258 src/util/getopt_helpers.c:286 +#: src/util/getopt_helpers.c:258 src/util/getopt_helpers.c:316 #, c-format msgid "You must pass a number to the `%s' option.\n" msgstr "" -#: src/util/gnunet-resolver.c:148 -msgid "perform a reverse lookup" +#: src/util/getopt_helpers.c:288 +#, c-format +msgid "You must pass relative time to the `%s' option.\n" msgstr "" -#: src/util/gnunet-resolver.c:154 -msgid "Use build-in GNUnet stub resolver" +#: src/util/gnunet-config.c:90 +#, c-format +msgid "--section argument is required\n" msgstr "" -#: src/util/gnunet-rsa.c:64 +#: src/util/gnunet-config.c:133 +#, c-format +msgid "--option argument required to set value\n" +msgstr "" + +#: src/util/gnunet-config.c:160 +msgid "obtain option of value as a filename (with $-expansion)" +msgstr "" + +#: src/util/gnunet-config.c:163 +msgid "name of the section to access" +msgstr "" + +#: src/util/gnunet-config.c:166 +msgid "name of the option to access" +msgstr "" + +#: src/util/gnunet-config.c:169 +msgid "value to set" +msgstr "" + +#: src/util/gnunet-config.c:178 +msgid "Manipulate GNUnet configuration files" +msgstr "" + +#: src/util/gnunet-ecc.c:107 src/util/gnunet-rsa.c:107 +#, c-format +msgid "Failed to open `%s': %s\n" +msgstr "" + +#: src/util/gnunet-ecc.c:113 src/util/gnunet-rsa.c:113 +#, c-format +msgid "Generating %u keys, please wait" +msgstr "" + +#: src/util/gnunet-ecc.c:128 src/util/gnunet-rsa.c:137 +#, c-format +msgid "" +"\n" +"Failed to write to `%s': %s\n" +msgstr "" + +#: src/util/gnunet-ecc.c:140 src/util/gnunet-rsa.c:149 +#, c-format +msgid "Finished!\n" +msgstr "" + +#: src/util/gnunet-ecc.c:163 src/util/gnunet-rsa.c:172 #, c-format msgid "No hostkey file specified on command line\n" msgstr "" -#: src/util/gnunet-rsa.c:112 +#: src/util/gnunet-ecc.c:220 src/util/gnunet-rsa.c:229 +msgid "create COUNT public-private key pairs (for testing)" +msgstr "" + +#: src/util/gnunet-ecc.c:223 src/util/gnunet-rsa.c:232 msgid "print the public key in ASCII format" msgstr "" -#: src/util/gnunet-rsa.c:115 +#: src/util/gnunet-ecc.c:226 src/util/gnunet-rsa.c:235 msgid "print the hash of the public key in ASCII format" msgstr "" -#: src/util/gnunet-rsa.c:118 +#: src/util/gnunet-ecc.c:229 src/util/gnunet-rsa.c:238 msgid "print the short hash of the public key in ASCII format" msgstr "" -#: src/util/gnunet-rsa.c:124 +#: src/util/gnunet-ecc.c:232 src/util/gnunet-rsa.c:241 +msgid "" +"use insecure, weak random number generator for key generation (for testing " +"only)" +msgstr "" + +#: src/util/gnunet-ecc.c:243 +msgid "Manipulate GNUnet private ECC key files" +msgstr "" + +#: src/util/gnunet-resolver.c:148 +msgid "perform a reverse lookup" +msgstr "" + +#: src/util/gnunet-resolver.c:159 +msgid "Use build-in GNUnet stub resolver" +msgstr "" + +#: src/util/gnunet-rsa.c:252 msgid "Manipulate GNUnet private RSA key files" msgstr "" @@ -5212,70 +5877,74 @@ msgstr "" msgid "Could not find IP of host `%s': %s\n" msgstr "" -#: src/util/helper.c:244 +#: src/util/gnunet-uri.c:90 #, c-format -msgid "Error reading from `%s': %s\n" +msgid "No URI specified on command line\n" msgstr "" -#: src/util/helper.c:259 +#: src/util/gnunet-uri.c:95 #, c-format -msgid "Got 0 bytes from helper `%s' (EOF)\n" +msgid "Invalid URI: does not start with `%s'\n" msgstr "" -#: src/util/helper.c:269 +#: src/util/gnunet-uri.c:102 #, c-format -msgid "Got %u bytes from helper `%s'\n" +msgid "Invalid URI: fails to specify subsystem\n" msgstr "" -#: src/util/helper.c:278 +#: src/util/gnunet-uri.c:112 #, c-format -msgid "Failed to parse inbound message from helper `%s'\n" +msgid "No handler known for subsystem `%s'\n" +msgstr "" + +#: src/util/gnunet-uri.c:174 +msgid "Perform default-actions for GNUnet URIs" msgstr "" -#: src/util/helper.c:310 +#: src/util/helper.c:260 #, c-format -msgid "Starting HELPER process `%s'\n" +msgid "Error reading from `%s': %s\n" msgstr "" -#: src/util/helper.c:440 +#: src/util/helper.c:305 +#, c-format +msgid "Failed to parse inbound message from helper `%s'\n" +msgstr "" + +#: src/util/helper.c:499 #, c-format msgid "Error writing to `%s': %s\n" msgstr "" -#: src/util/network.c:1200 +#: src/util/network.c:127 +#, c-format +msgid "Unable to shorten unix path `%s' while keeping name unique\n" +msgstr "" + +#: src/util/network.c:1331 #, c-format msgid "" "Fatal internal logic error, process hangs in `%s' (abort with CTRL-C)!\n" msgstr "" -#: src/util/os_installation.c:299 +#: src/util/os_installation.c:420 #, c-format msgid "" "Could not determine installation path for %s. Set `%s' environment " "variable.\n" msgstr "" -#: src/util/os_installation.c:486 +#: src/util/os_installation.c:702 #, c-format msgid "Could not find binary `%s' in PATH!\n" msgstr "" -#: src/util/os_installation.c:492 -#, c-format -msgid "access (%s, X_OK) failed: %s\n" -msgstr "" - -#: src/util/os_installation.c:507 -#, c-format -msgid "stat (%s) failed: %s\n" -msgstr "" - -#: src/util/os_priority.c:305 +#: src/util/os_priority.c:302 #, c-format msgid "Failed to open named pipe `%s' for reading: %s\n" msgstr "" -#: src/util/os_priority.c:306 +#: src/util/os_priority.c:303 #, c-format msgid "Failed to open named pipe `%s' for writing: %s\n" msgstr "" @@ -5299,12 +5968,17 @@ msgstr "" msgid "Could not determine plugin installation path.\n" msgstr "" -#: src/util/pseudonym.c:276 +#: src/util/program.c:254 src/util/service.c:1791 +#, c-format +msgid "Could not access configuration file `%s'\n" +msgstr "" + +#: src/util/pseudonym.c:282 #, c-format msgid "Failed to parse metadata about pseudonym from file `%s': %s\n" msgstr "" -#: src/util/pseudonym.c:407 src/util/pseudonym.c:433 +#: src/util/pseudonym.c:413 src/util/pseudonym.c:439 msgid "no-name" msgstr "" @@ -5334,152 +6008,152 @@ msgstr "" msgid "Could not resolve our FQDN : %s\n" msgstr "" -#: src/util/scheduler.c:786 +#: src/util/scheduler.c:782 msgid "Looks like we're busy waiting...\n" msgstr "" -#: src/util/scheduler.c:916 +#: src/util/scheduler.c:912 #, c-format msgid "Attempt to cancel dead task %llu!\n" msgstr "" -#: src/util/server.c:483 +#: src/util/server.c:426 #, c-format msgid "`%s' failed for port %d (%s).\n" msgstr "" -#: src/util/server.c:492 +#: src/util/server.c:435 #, c-format msgid "`%s' failed for port %d (%s): address already in use\n" msgstr "" -#: src/util/server.c:497 +#: src/util/server.c:446 #, c-format -msgid "`%s' failed for `%s': address already in use\n" +msgid "`%s' failed for `%.*s': address already in use\n" msgstr "" -#: src/util/server.c:827 +#: src/util/server.c:830 #, c-format msgid "" "Processing code for message of type %u did not call " -"GNUNET_SERVER_receive_done after %llums\n" +"`GNUNET_SERVER_receive_done' after %s\n" msgstr "" -#: src/util/service.c:135 src/util/service.c:161 src/util/service.c:204 -#: src/util/service.c:225 src/util/service.c:232 +#: src/util/service.c:142 src/util/service.c:168 src/util/service.c:211 +#: src/util/service.c:232 src/util/service.c:239 #, c-format msgid "Invalid format for IP: `%s'\n" msgstr "" -#: src/util/service.c:188 +#: src/util/service.c:195 #, c-format msgid "Invalid network notation ('/%d' is not legal in IPv4 CIDR)." msgstr "" -#: src/util/service.c:281 +#: src/util/service.c:288 #, c-format msgid "Invalid network notation (does not end with ';': `%s')\n" msgstr "" -#: src/util/service.c:313 +#: src/util/service.c:320 #, c-format msgid "Wrong format `%s' for netmask\n" msgstr "" -#: src/util/service.c:343 +#: src/util/service.c:350 #, c-format msgid "Wrong format `%s' for network\n" msgstr "" -#: src/util/service.c:698 +#: src/util/service.c:707 #, c-format msgid "Access denied to UID %d / GID %d\n" msgstr "" -#: src/util/service.c:703 +#: src/util/service.c:712 #, c-format msgid "Unknown address family %d\n" msgstr "" -#: src/util/service.c:710 +#: src/util/service.c:719 #, c-format msgid "Access from `%s' denied to service `%s'\n" msgstr "" -#: src/util/service.c:765 +#: src/util/service.c:774 #, c-format msgid "Could not parse IPv4 network specification `%s' for `%s:%s'\n" msgstr "" -#: src/util/service.c:802 +#: src/util/service.c:811 #, c-format msgid "Could not parse IPv6 network specification `%s' for `%s:%s'\n" msgstr "" -#: src/util/service.c:920 +#: src/util/service.c:929 #, c-format msgid "" "Disabling IPv6 support for service `%s', failed to create IPv6 socket: %s\n" msgstr "" -#: src/util/service.c:990 +#: src/util/service.c:1007 #, c-format msgid "" "Disabling UNIX domain socket support for service `%s', failed to create UNIX " "domain socket: %s\n" msgstr "" -#: src/util/service.c:1007 +#: src/util/service.c:1024 #, c-format msgid "Have neither PORT nor UNIXPATH for service `%s', but one is required\n" msgstr "" -#: src/util/service.c:1241 +#: src/util/service.c:1258 msgid "Could not access a pre-bound socket, will try to bind myself\n" msgstr "" -#: src/util/service.c:1292 src/util/service.c:1310 +#: src/util/service.c:1309 src/util/service.c:1327 #, c-format msgid "Specified value for `%s' of service `%s' is invalid\n" msgstr "" -#: src/util/service.c:1337 +#: src/util/service.c:1354 #, c-format msgid "Could not access pre-bound socket %u, will try to bind myself\n" msgstr "" -#: src/util/service.c:1506 +#: src/util/service.c:1525 #, c-format msgid "Failed to start `%s' at `%s'\n" msgstr "" -#: src/util/service.c:1539 +#: src/util/service.c:1558 #, c-format msgid "Service `%s' runs at %s\n" msgstr "" -#: src/util/service.c:1588 +#: src/util/service.c:1607 msgid "Service process failed to initialize\n" msgstr "" -#: src/util/service.c:1592 +#: src/util/service.c:1611 msgid "Service process could not initialize server function\n" msgstr "" -#: src/util/service.c:1596 +#: src/util/service.c:1615 msgid "Service process failed to report status\n" msgstr "" -#: src/util/service.c:1651 +#: src/util/service.c:1670 msgid "No such user" msgstr "" -#: src/util/service.c:1664 +#: src/util/service.c:1683 #, c-format msgid "Cannot change user/group to `%s': %s\n" msgstr "" -#: src/util/service.c:1729 +#: src/util/service.c:1749 msgid "do daemonize (detach from terminal)" msgstr "" @@ -5488,73 +6162,81 @@ msgstr "" msgid "signal (%d, %p) returned %d.\n" msgstr "" -#: src/util/strings.c:144 +#: src/util/strings.c:146 msgid "b" msgstr "" -#: src/util/strings.c:334 +#: src/util/strings.c:413 #, c-format msgid "Character sets requested were `%s'->`%s'\n" msgstr "" -#: src/util/strings.c:481 +#: src/util/strings.c:528 msgid "Failed to expand `$HOME': environment variable `HOME' not set" msgstr "" -#: src/util/strings.c:573 +#: src/util/strings.c:625 msgid "ms" msgstr "" -#: src/util/strings.c:578 -msgid "eternity" +#: src/util/strings.c:629 +msgid "forever" msgstr "" -#: src/util/strings.c:582 +#: src/util/strings.c:631 +msgid "0 ms" +msgstr "" + +#: src/util/strings.c:637 msgid "s" msgstr "" -#: src/util/strings.c:586 +#: src/util/strings.c:643 msgid "m" msgstr "" -#: src/util/strings.c:590 +#: src/util/strings.c:649 msgid "h" msgstr "" -#: src/util/strings.c:594 -msgid " days" +#: src/util/strings.c:656 +msgid "day" +msgstr "" + +#: src/util/strings.c:658 +msgid "days" msgstr "" -#: src/util/strings.c:618 +#: src/util/strings.c:685 msgid "end of time" msgstr "" -#: src/util/strings.c:1012 +#: src/util/strings.c:1073 msgid "IPv6 address did not start with `['\n" msgstr "" -#: src/util/strings.c:1020 +#: src/util/strings.c:1081 msgid "IPv6 address did contain ':' to separate port number\n" msgstr "" -#: src/util/strings.c:1026 +#: src/util/strings.c:1087 msgid "IPv6 address did contain ']' before ':' to separate port number\n" msgstr "" -#: src/util/strings.c:1033 +#: src/util/strings.c:1094 msgid "IPv6 address did contain a valid port number after the last ':'\n" msgstr "" -#: src/util/strings.c:1042 +#: src/util/strings.c:1103 #, c-format msgid "Invalid IPv6 address `%s': %s\n" msgstr "" -#: src/vpn/gnunet-service-vpn.c:511 src/vpn/gnunet-service-vpn.c:1071 +#: src/vpn/gnunet-service-vpn.c:512 src/vpn/gnunet-service-vpn.c:1088 msgid "# Active tunnels" msgstr "" -#: src/vpn/gnunet-service-vpn.c:608 src/vpn/gnunet-service-vpn.c:645 +#: src/vpn/gnunet-service-vpn.c:609 src/vpn/gnunet-service-vpn.c:646 msgid "# peers connected to mesh tunnels" msgstr "" @@ -5566,78 +6248,78 @@ msgstr "" msgid "# Bytes dropped in mesh queue (overflow)" msgstr "" -#: src/vpn/gnunet-service-vpn.c:772 +#: src/vpn/gnunet-service-vpn.c:771 msgid "# Mesh tunnels created" msgstr "" -#: src/vpn/gnunet-service-vpn.c:795 +#: src/vpn/gnunet-service-vpn.c:794 msgid "Failed to setup mesh tunnel!\n" msgstr "" -#: src/vpn/gnunet-service-vpn.c:973 +#: src/vpn/gnunet-service-vpn.c:990 #, c-format msgid "Protocol %u not supported, dropping\n" msgstr "" -#: src/vpn/gnunet-service-vpn.c:1291 +#: src/vpn/gnunet-service-vpn.c:1308 msgid "# ICMPv4 packets dropped (not allowed)" msgstr "" -#: src/vpn/gnunet-service-vpn.c:1312 +#: src/vpn/gnunet-service-vpn.c:1329 msgid "# ICMPv6 packets dropped (not allowed)" msgstr "" -#: src/vpn/gnunet-service-vpn.c:1517 +#: src/vpn/gnunet-service-vpn.c:1534 msgid "# Packets received from TUN interface" msgstr "" -#: src/vpn/gnunet-service-vpn.c:1555 src/vpn/gnunet-service-vpn.c:1596 +#: src/vpn/gnunet-service-vpn.c:1572 src/vpn/gnunet-service-vpn.c:1613 #, c-format msgid "Packet received for unmapped destination `%s' (dropping it)\n" msgstr "" -#: src/vpn/gnunet-service-vpn.c:1606 +#: src/vpn/gnunet-service-vpn.c:1623 msgid "Received IPv4 packet with options (dropping it)\n" msgstr "" -#: src/vpn/gnunet-service-vpn.c:1620 +#: src/vpn/gnunet-service-vpn.c:1637 #, c-format msgid "Received packet of unknown protocol %d from TUN (dropping it)\n" msgstr "" -#: src/vpn/gnunet-service-vpn.c:1704 +#: src/vpn/gnunet-service-vpn.c:1721 msgid "# ICMP packets received from mesh" msgstr "" -#: src/vpn/gnunet-service-vpn.c:2045 +#: src/vpn/gnunet-service-vpn.c:2062 msgid "# UDP packets received from mesh" msgstr "" -#: src/vpn/gnunet-service-vpn.c:2203 +#: src/vpn/gnunet-service-vpn.c:2220 msgid "# TCP packets received from mesh" msgstr "" -#: src/vpn/gnunet-service-vpn.c:2354 +#: src/vpn/gnunet-service-vpn.c:2371 msgid "Failed to find unallocated IPv4 address in VPN's range\n" msgstr "" -#: src/vpn/gnunet-service-vpn.c:2409 +#: src/vpn/gnunet-service-vpn.c:2426 msgid "Failed to find unallocated IPv6 address in VPN's range\n" msgstr "" -#: src/vpn/gnunet-service-vpn.c:2448 src/vpn/gnunet-service-vpn.c:2661 +#: src/vpn/gnunet-service-vpn.c:2465 src/vpn/gnunet-service-vpn.c:2678 msgid "# Active destinations" msgstr "" -#: src/vpn/gnunet-service-vpn.c:2734 +#: src/vpn/gnunet-service-vpn.c:2751 msgid "Failed to allocate IP address for new destination\n" msgstr "" -#: src/vpn/gnunet-service-vpn.c:3141 +#: src/vpn/gnunet-service-vpn.c:3138 msgid "IPv6 support disabled as this system does not support IPv6\n" msgstr "" -#: src/vpn/gnunet-service-vpn.c:3173 +#: src/vpn/gnunet-service-vpn.c:3170 msgid "IPv4 support disabled as this system does not support IPv4\n" msgstr "" @@ -5645,83 +6327,83 @@ msgstr "" msgid "Error creating tunnel\n" msgstr "" -#: src/vpn/gnunet-vpn.c:195 src/vpn/gnunet-vpn.c:226 +#: src/vpn/gnunet-vpn.c:194 src/vpn/gnunet-vpn.c:225 #, c-format msgid "Option `%s' makes no sense with option `%s'.\n" msgstr "" -#: src/vpn/gnunet-vpn.c:208 +#: src/vpn/gnunet-vpn.c:207 #, c-format msgid "Option `%s' or `%s' is required.\n" msgstr "" -#: src/vpn/gnunet-vpn.c:220 +#: src/vpn/gnunet-vpn.c:219 #, c-format msgid "Option `%s' or `%s' is required when using option `%s'.\n" msgstr "" -#: src/vpn/gnunet-vpn.c:238 +#: src/vpn/gnunet-vpn.c:237 #, c-format msgid "`%s' is not a valid peer identifier.\n" msgstr "" -#: src/vpn/gnunet-vpn.c:260 +#: src/vpn/gnunet-vpn.c:259 #, c-format msgid "`%s' is not a valid IP address.\n" msgstr "" -#: src/vpn/gnunet-vpn.c:296 +#: src/vpn/gnunet-vpn.c:295 msgid "request that result should be an IPv4 address" msgstr "" -#: src/vpn/gnunet-vpn.c:299 +#: src/vpn/gnunet-vpn.c:298 msgid "request that result should be an IPv6 address" msgstr "" -#: src/vpn/gnunet-vpn.c:302 +#: src/vpn/gnunet-vpn.c:301 msgid "print IP address only after mesh tunnel has been created" msgstr "" -#: src/vpn/gnunet-vpn.c:305 +#: src/vpn/gnunet-vpn.c:304 msgid "how long should the mapping be valid for new tunnels?" msgstr "" -#: src/vpn/gnunet-vpn.c:308 +#: src/vpn/gnunet-vpn.c:307 msgid "destination IP for the tunnel" msgstr "" -#: src/vpn/gnunet-vpn.c:311 +#: src/vpn/gnunet-vpn.c:310 msgid "peer offering the service we would like to access" msgstr "" -#: src/vpn/gnunet-vpn.c:314 +#: src/vpn/gnunet-vpn.c:313 msgid "name of the service we would like to access" msgstr "" -#: src/vpn/gnunet-vpn.c:317 +#: src/vpn/gnunet-vpn.c:316 msgid "service is offered via TCP" msgstr "" -#: src/vpn/gnunet-vpn.c:320 +#: src/vpn/gnunet-vpn.c:319 msgid "service is offered via UDP" msgstr "" -#: src/vpn/gnunet-vpn.c:329 +#: src/vpn/gnunet-vpn.c:331 msgid "Setup tunnels via VPN." msgstr "" -#: src/include/gnunet_common.h:497 src/include/gnunet_common.h:502 -#: src/include/gnunet_common.h:508 +#: src/include/gnunet_common.h:579 src/include/gnunet_common.h:584 +#: src/include/gnunet_common.h:590 #, c-format msgid "Assertion failed at %s:%d.\n" msgstr "" -#: src/include/gnunet_common.h:518 +#: src/include/gnunet_common.h:600 #, c-format msgid "External protocol violation detected at %s:%d.\n" msgstr "" -#: src/include/gnunet_common.h:539 src/include/gnunet_common.h:546 +#: src/include/gnunet_common.h:621 src/include/gnunet_common.h:628 #, c-format msgid "`%s' failed on file `%s' at %s:%d with error: %s\n" msgstr "" diff --git a/po/sv.gmo b/po/sv.gmo index 5f03fca..8c202fa 100644 Binary files a/po/sv.gmo and b/po/sv.gmo differ diff --git a/po/sv.po b/po/sv.po index e3e5bc3..0a004e4 100644 --- a/po/sv.po +++ b/po/sv.po @@ -7,7 +7,7 @@ msgid "" msgstr "" "Project-Id-Version: GNUnet 0.7.0b\n" "Report-Msgid-Bugs-To: gnunet-developers@mail.gnu.org\n" -"POT-Creation-Date: 2012-06-05 15:47+0200\n" +"POT-Creation-Date: 2013-02-05 19:22+0100\n" "PO-Revision-Date: 2006-01-21 17:16+0100\n" "Last-Translator: Daniel Nylander \n" "Language-Team: Swedish \n" @@ -16,265 +16,215 @@ msgstr "" "Content-Type: text/plain; charset=utf-8\n" "Content-Transfer-Encoding: 8bit\n" -#: src/arm/arm_api.c:165 +#: src/arm/arm_api.c:162 msgid "Failed to transmit shutdown request to client.\n" msgstr "" -#: src/arm/arm_api.c:349 -#, fuzzy, c-format -msgid "Configuration failes to specify option `%s' in section `%s'!\n" -msgstr "Konfigurationsfil \"%s\" hittades inte. Kör \"gnunet-setup -d\"!\n" - -#: src/arm/arm_api.c:363 -#, fuzzy, c-format -msgid "Configuration fails to specify option `%s' in section `%s'!\n" -msgstr "Konfigurationsfil \"%s\" skapad.\n" - -#: src/arm/arm_api.c:432 -#, c-format -msgid "Error receiving response to `%s' request from ARM for service `%s'\n" -msgstr "" - -#: src/arm/arm_api.c:485 -#, c-format -msgid "Requesting start of service `%s'.\n" -msgstr "" - -#: src/arm/arm_api.c:486 -#, c-format -msgid "Requesting termination of service `%s'.\n" -msgstr "" - -#: src/arm/arm_api.c:507 -#, c-format -msgid "Error while trying to transmit request to start `%s' to ARM\n" -msgstr "" - -#: src/arm/arm_api.c:508 -#, c-format -msgid "Error while trying to transmit request to stop `%s' to ARM\n" -msgstr "" - -#: src/arm/arm_api.c:540 -#, fuzzy, c-format -msgid "Asked to start service `%s' within %llu ms\n" -msgstr "\"%s\": Mottog inte meddelande inom %llu ms.\n" - -#: src/arm/arm_api.c:612 -#, fuzzy, c-format -msgid "Stopping service `%s' within %llu ms\n" -msgstr "Inget svar mottaget inom %llums.\n" - -#: src/arm/gnunet-arm.c:159 +#: src/arm/gnunet-arm.c:166 #, fuzzy, c-format msgid "Service `%s' is unknown to ARM.\n" msgstr "\"%s\" är inte en fil.\n" -#: src/arm/gnunet-arm.c:164 +#: src/arm/gnunet-arm.c:171 #, fuzzy, c-format msgid "Service `%s' has been stopped.\n" msgstr "Tjänst borttagen.\n" -#: src/arm/gnunet-arm.c:167 +#: src/arm/gnunet-arm.c:174 #, fuzzy, c-format msgid "Service `%s' was already running.\n" msgstr "\"%s\" är inte en fil.\n" -#: src/arm/gnunet-arm.c:172 +#: src/arm/gnunet-arm.c:179 #, fuzzy, c-format msgid "Service `%s' has been started.\n" msgstr "Tjänst borttagen.\n" -#: src/arm/gnunet-arm.c:175 +#: src/arm/gnunet-arm.c:182 #, fuzzy, c-format msgid "Service `%s' was already being stopped.\n" msgstr "Tjänst borttagen.\n" -#: src/arm/gnunet-arm.c:179 +#: src/arm/gnunet-arm.c:186 #, fuzzy, c-format msgid "Service `%s' was already not running.\n" msgstr "\"%s\" är inte en fil.\n" -#: src/arm/gnunet-arm.c:183 +#: src/arm/gnunet-arm.c:190 msgid "Request ignored as ARM is shutting down.\n" msgstr "" -#: src/arm/gnunet-arm.c:187 +#: src/arm/gnunet-arm.c:194 #, fuzzy msgid "Error communicating with ARM service.\n" msgstr "Skriv ut information om GNUnets motparter." -#: src/arm/gnunet-arm.c:191 +#: src/arm/gnunet-arm.c:198 #, fuzzy msgid "Timeout communicating with ARM service.\n" msgstr "Skriv ut information om GNUnets motparter." -#: src/arm/gnunet-arm.c:195 +#: src/arm/gnunet-arm.c:202 #, fuzzy msgid "Operation failed.\n" msgstr "\"%s\" misslyckades vid %s:%d med fel: \"%s\".\n" -#: src/arm/gnunet-arm.c:199 +#: src/arm/gnunet-arm.c:206 msgid "Unknown response code from ARM.\n" msgstr "" -#: src/arm/gnunet-arm.c:222 +#: src/arm/gnunet-arm.c:229 #, fuzzy msgid "Error communicating with ARM. ARM not running?\n" msgstr "Skriv ut information om GNUnets motparter." -#: src/arm/gnunet-arm.c:225 +#: src/arm/gnunet-arm.c:232 #, fuzzy msgid "Running services:\n" msgstr "Startade samling \"%s\".\n" -#: src/arm/gnunet-arm.c:249 -#, c-format -msgid "Fatal configuration error: `%s' option in section `%s' missing.\n" -msgstr "" - -#: src/arm/gnunet-arm.c:257 src/arm/gnunet-arm.c:357 src/arm/gnunet-arm.c:373 -msgid "Fatal error initializing ARM API.\n" -msgstr "" - -#: src/arm/gnunet-arm.c:280 +#: src/arm/gnunet-arm.c:253 #, fuzzy, c-format msgid "Failed to remove configuration file %s\n" msgstr "Kunde inte spara konfigurationsfil \"%s\":" -#: src/arm/gnunet-arm.c:286 +#: src/arm/gnunet-arm.c:259 #, fuzzy, c-format msgid "Failed to remove servicehome directory %s\n" msgstr "Filformatsfel (inte en GNUnet-katalog?)\n" -#: src/arm/gnunet-arm.c:407 +#: src/arm/gnunet-arm.c:322 src/arm/gnunet-arm.c:407 src/arm/gnunet-arm.c:424 +msgid "Fatal error initializing ARM API.\n" +msgstr "" + +#: src/arm/gnunet-arm.c:453 msgid "stop all GNUnet services" msgstr "" -#: src/arm/gnunet-arm.c:409 +#: src/arm/gnunet-arm.c:455 msgid "start a particular service" msgstr "" -#: src/arm/gnunet-arm.c:411 +#: src/arm/gnunet-arm.c:457 msgid "stop a particular service" msgstr "" -#: src/arm/gnunet-arm.c:413 +#: src/arm/gnunet-arm.c:459 msgid "start all GNUnet default services" msgstr "" -#: src/arm/gnunet-arm.c:416 +#: src/arm/gnunet-arm.c:462 msgid "stop and start all GNUnet default services" msgstr "" -#: src/arm/gnunet-arm.c:419 +#: src/arm/gnunet-arm.c:465 msgid "delete config file and directory on exit" msgstr "" -#: src/arm/gnunet-arm.c:421 +#: src/arm/gnunet-arm.c:467 msgid "don't print status messages" msgstr "" -#: src/arm/gnunet-arm.c:424 -msgid "timeout for completing current operation" +#: src/arm/gnunet-arm.c:470 +msgid "timeout in MSECS milliseconds for completing current operation" +msgstr "" + +#: src/arm/gnunet-arm.c:472 +#, fuzzy +msgid "list currently running services" +msgstr "Startade samling \"%s\".\n" + +#: src/arm/gnunet-arm.c:474 +msgid "don't let gnunet-service-arm inherit standard output" msgstr "" -#: src/arm/gnunet-arm.c:426 -msgid "List currently running services" +#: src/arm/gnunet-arm.c:476 +msgid "don't let gnunet-service-arm inherit standard error" msgstr "" -#: src/arm/gnunet-arm.c:437 +#: src/arm/gnunet-arm.c:487 msgid "Control services and the Automated Restart Manager (ARM)" msgstr "" -#: src/arm/gnunet-service-arm.c:332 +#: src/arm/gnunet-service-arm.c:345 #, fuzzy, c-format msgid "Failed to start service `%s'\n" msgstr "Misslyckades att starta samling.\n" -#: src/arm/gnunet-service-arm.c:335 +#: src/arm/gnunet-service-arm.c:348 #, fuzzy, c-format msgid "Starting service `%s'\n" msgstr "Startade samling \"%s\".\n" -#: src/arm/gnunet-service-arm.c:361 +#: src/arm/gnunet-service-arm.c:374 #, fuzzy msgid "Could not send status result to client\n" msgstr "Kunde inte skicka begäran till gnunetd.\n" -#: src/arm/gnunet-service-arm.c:393 +#: src/arm/gnunet-service-arm.c:406 #, fuzzy msgid "Could not send list result to client\n" msgstr "Kunde inte skicka begäran till gnunetd.\n" -#: src/arm/gnunet-service-arm.c:523 +#: src/arm/gnunet-service-arm.c:537 #, fuzzy, c-format msgid "Unable to create socket for service `%s': %s\n" msgstr "Kunde inte skapa användarkonto:" -#: src/arm/gnunet-service-arm.c:545 +#: src/arm/gnunet-service-arm.c:559 #, c-format msgid "Unable to bind listening socket for service `%s' to address `%s': %s\n" msgstr "" -#: src/arm/gnunet-service-arm.c:559 +#: src/arm/gnunet-service-arm.c:573 #, c-format msgid "ARM now monitors connections to service `%s' at `%s'\n" msgstr "" -#: src/arm/gnunet-service-arm.c:667 +#: src/arm/gnunet-service-arm.c:681 #, fuzzy, c-format msgid "Preparing to stop `%s'\n" msgstr "Startade samling \"%s\".\n" -#: src/arm/gnunet-service-arm.c:878 +#: src/arm/gnunet-service-arm.c:892 #, fuzzy, c-format msgid "Restarting service `%s'.\n" msgstr "Startade samling \"%s\".\n" -#: src/arm/gnunet-service-arm.c:970 +#: src/arm/gnunet-service-arm.c:985 msgid "exit" msgstr "" -#: src/arm/gnunet-service-arm.c:975 +#: src/arm/gnunet-service-arm.c:990 msgid "signal" msgstr "" -#: src/arm/gnunet-service-arm.c:980 +#: src/arm/gnunet-service-arm.c:995 #, fuzzy msgid "unknown" msgstr "Okänt fel" -#: src/arm/gnunet-service-arm.c:986 +#: src/arm/gnunet-service-arm.c:1001 #, fuzzy, c-format -msgid "Service `%s' took %llu ms to terminate\n" +msgid "Service `%s' took %s to terminate\n" msgstr "Tjänst borttagen.\n" -#: src/arm/gnunet-service-arm.c:1021 +#: src/arm/gnunet-service-arm.c:1036 #, c-format msgid "Service `%s' terminated with status %s/%d, will restart in %llu ms\n" msgstr "" -#: src/arm/gnunet-service-arm.c:1127 -#, fuzzy, c-format -msgid "Configuration file `%s' for service `%s' not valid: %s\n" -msgstr "Konfigurationsfil \"%s\" skapad.\n" - -#: src/arm/gnunet-service-arm.c:1129 -msgid "option missing" -msgstr "" - -#: src/arm/gnunet-service-arm.c:1213 +#: src/arm/gnunet-service-arm.c:1228 #, fuzzy, c-format msgid "Starting default services `%s'\n" msgstr "Startade samling \"%s\".\n" -#: src/arm/gnunet-service-arm.c:1224 +#: src/arm/gnunet-service-arm.c:1239 #, c-format msgid "Default service `%s' not configured correctly!\n" msgstr "" -#: src/arm/gnunet-service-arm.c:1238 +#: src/arm/gnunet-service-arm.c:1253 msgid "" "No default services configured, GNUnet will not really start right now.\n" msgstr "" @@ -283,303 +233,265 @@ msgstr "" msgid "Initiating shutdown as requested by client.\n" msgstr "" -#: src/block/block.c:105 -#, fuzzy, c-format -msgid "Loading block plugin `%s'\n" -msgstr "Testar transport(er) %s\n" - -#: src/chat/chat.c:175 -#, fuzzy -msgid "Could not transmit confirmation receipt\n" -msgstr "Kunde inte komma åt namnrymdsinformation.\n" - -#: src/chat/chat.c:283 -msgid "The current user must be the the first one joined\n" -msgstr "" - -#: src/chat/chat.c:412 -#, fuzzy, c-format -msgid "Unknown message type: '%u'\n" -msgstr "Okänd operation \"%s\"\n" - -#: src/chat/chat.c:472 -#, fuzzy, c-format -msgid "Configuration option `%s' in section `%s' missing\n" -msgstr "Konfigurationsfil \"%s\" skapad.\n" - -#: src/chat/chat.c:480 -#, fuzzy, c-format -msgid "Failed to access chat home directory `%s'\n" -msgstr "Filformatsfel (inte en GNUnet-katalog?)\n" - -#: src/chat/chat.c:498 -#, fuzzy, c-format -msgid "Failed to create/open key in file `%s'\n" -msgstr "Misslyckades att leverera \"%s\" meddelande.\n" - -#: src/chat/chat.c:559 -#, fuzzy -msgid "Could not serialize metadata\n" -msgstr "Kunde inte initiera libgnunetutil!\n" - -#: src/chat/chat.c:674 -#, fuzzy -msgid "Failed to connect to the chat service\n" -msgstr "Misslyckades att ansluta till gnunetd.\n" - -#: src/chat/chat.c:680 -msgid "Undefined mandatory parameter: joinCallback\n" -msgstr "" - -#: src/chat/chat.c:686 -msgid "Undefined mandatory parameter: messageCallback\n" -msgstr "" - -#: src/chat/chat.c:692 -msgid "Undefined mandatory parameter: memberCallback\n" -msgstr "" - -#: src/chat/gnunet-chat.c:93 -msgid "Joined\n" -msgstr "" - -#: src/chat/gnunet-chat.c:125 src/chat/gnunet-chat.c:133 -#: src/chat/gnunet-chat.c:213 src/chat/gnunet-chat.c:253 -#: src/chat/gnunet-chat.c:329 src/chat/gnunet-chat.c:371 -#: src/chat/gnunet-chat.c:400 src/chat/gnunet-chat.c:700 -msgid "anonymous" -msgstr "" - -#: src/chat/gnunet-chat.c:144 -#, fuzzy, c-format -msgid "(%s) `%s' said: %s\n" -msgstr "\"%s\" %s misslyckades: %s\n" - -#: src/chat/gnunet-chat.c:147 src/chat/gnunet-chat.c:150 -#, fuzzy, c-format -msgid "(%s) `%s' said to you: %s\n" -msgstr "\"%s\" %s misslyckades: %s\n" - -# drive = hard drive ? -#: src/chat/gnunet-chat.c:153 +#: src/ats/ats_api_performance.c:465 #, fuzzy, c-format -msgid "(%s) `%s' said for sure: %s\n" -msgstr "\"%s\" misslyckades för enhet %s: %u\n" +msgid "Received %s message\n" +msgstr "mottog ogiltigt \"%s\" meddelande\n" -# drive = hard drive ? -#: src/chat/gnunet-chat.c:156 +#: src/ats/ats_api_performance.c:508 #, fuzzy, c-format -msgid "(%s) `%s' said to you for sure: %s\n" -msgstr "\"%s\" misslyckades för enhet %s: %u\n" +msgid "Received last message for %s \n" +msgstr "Mottog ogiltigt \"%s\" meddelande från \"%s\".\n" -#: src/chat/gnunet-chat.c:159 +#: src/ats/gnunet-service-ats_addresses.c:993 +#: src/ats/gnunet-service-ats_addresses.c:1027 #, c-format -msgid "(%s) `%s' was confirmed that you received: %s\n" -msgstr "" - -#: src/chat/gnunet-chat.c:162 -#, c-format -msgid "(%s) `%s' was confirmed that you and only you received: %s\n" +msgid "" +"Could not load quota for network `%s': `%s', assigning default bandwidth " +"%llu\n" msgstr "" -#: src/chat/gnunet-chat.c:165 +#: src/ats/gnunet-service-ats_addresses.c:999 #, c-format -msgid "(%s) `%s' was confirmed that you received from him or her: %s\n" +msgid "Outbound quota configure for network `%s' is %llu\n" msgstr "" -#: src/chat/gnunet-chat.c:170 +#: src/ats/gnunet-service-ats_addresses.c:1006 #, c-format msgid "" -"(%s) `%s' was confirmed that you and only you received from him or her: %s\n" +"No outbound quota configured for network `%s', assigning default bandwidth " +"%llu\n" msgstr "" -#: src/chat/gnunet-chat.c:173 -#, fuzzy, c-format -msgid "(%s) `%s' said off the record: %s\n" -msgstr "\"%s\" misslyckades vid %s:%d med fel: %s\n" - -#: src/chat/gnunet-chat.c:176 +#: src/ats/gnunet-service-ats_addresses.c:1033 #, c-format -msgid "(%s) <%s> said using an unknown message type: %s\n" +msgid "Inbound quota configured for network `%s' is %llu\n" msgstr "" -#: src/chat/gnunet-chat.c:217 +#: src/ats/gnunet-service-ats_addresses.c:1040 #, c-format -msgid "'%s' acknowledged message #%d\n" +msgid "" +"No outbound quota configure for network `%s', assigning default bandwidth " +"%llu\n" msgstr "" -#: src/chat/gnunet-chat.c:260 +#: src/ats-tool/gnunet-ats.c:141 #, c-format -msgid "`%s' entered the room\n" +msgid "%u address resolutions had a timeout\n" msgstr "" -#: src/chat/gnunet-chat.c:260 +#: src/ats-tool/gnunet-ats.c:143 #, c-format -msgid "`%s' left the room\n" +msgid "ATS returned results for %u addresses\n" msgstr "" -#: src/chat/gnunet-chat.c:321 src/chat/gnunet-chat.c:363 -#, fuzzy -msgid "Could not change username\n" -msgstr "Kunde inte skapa namnrymd \"%s\" (existerar?).\n" - -#: src/chat/gnunet-chat.c:334 src/chat/gnunet-chat.c:702 -#, fuzzy, c-format -msgid "Joining room `%s' as user `%s'...\n" -msgstr "Ogiltigt svar till \"%s\" från motpart \"%s\".\n" - -#: src/chat/gnunet-chat.c:373 +#: src/ats-tool/gnunet-ats.c:199 #, fuzzy, c-format -msgid "Changed username to `%s'\n" -msgstr "Kan inte ändra användare/grupp till \"%s\": %s\n" +msgid "" +"Peer `%s' plugin `%s', address `%s', `%s' bw out: %u Bytes/s, bw in %u Bytes/" +"s, %s\n" +msgstr "Motpart \"%s\" med pålitlighet %8u och adress \"%s\"\n" -#: src/chat/gnunet-chat.c:388 +#: src/ats-tool/gnunet-ats.c:326 #, c-format -msgid "Users in room `%s': " +msgid "Quota for network `%11s' (in/out): %10s / %10s\n" msgstr "" -#: src/chat/gnunet-chat.c:434 -msgid "Syntax: /msg USERNAME MESSAGE" -msgstr "" +#: src/ats-tool/gnunet-ats.c:345 src/namestore/gnunet-namestore.c:610 +#: src/transport/gnunet-transport.c:813 +#, fuzzy, c-format +msgid "Service `%s' is not running\n" +msgstr "\"%s\" är inte en fil.\n" -#: src/chat/gnunet-chat.c:443 -#, c-format -msgid "Unknown user `%s'. Make sure you specify its numeric suffix, if any.\n" -msgstr "" +#: src/ats-tool/gnunet-ats.c:355 src/transport/gnunet-transport.c:819 +#, fuzzy, c-format +msgid "Failed to parse peer identity `%s'\n" +msgstr "Misslyckades att läsa kompislista från \"%s\"\n" -#: src/chat/gnunet-chat.c:460 +#: src/ats-tool/gnunet-ats.c:363 #, c-format -msgid "User `%s' is currently not in the room!\n" +msgid "Please select one operation : %s or %s or %s or %s or %s\n" msgstr "" -#: src/chat/gnunet-chat.c:513 +#: src/ats-tool/gnunet-ats.c:379 src/ats-tool/gnunet-ats.c:398 +#: src/ats-tool/gnunet-ats.c:415 src/ats-tool/gnunet-ats.c:440 #, fuzzy, c-format -msgid "Unknown command `%s'\n" -msgstr "Okänd operation \"%s\"\n" - -#: src/chat/gnunet-chat.c:524 -msgid "" -"Use `/join #roomname' to join a chat room. Joining a room will cause you to " -"leave the current room" -msgstr "" +msgid "Cannot connect to ATS service, exiting...\n" +msgstr "Misslyckades att initiera tjänsten \"%s\".\n" -#: src/chat/gnunet-chat.c:528 -msgid "" -"Use `/nick nickname' to change your nickname. This will cause you to leave " -"the current room and immediately rejoin it with the new name." -msgstr "" +#: src/ats-tool/gnunet-ats.c:388 src/ats-tool/gnunet-ats.c:405 +#, fuzzy, c-format +msgid "Cannot issue request to ATS service, exiting...\n" +msgstr "Misslyckades att initiera tjänsten \"%s\".\n" -#: src/chat/gnunet-chat.c:532 -msgid "" -"Use `/msg nickname message' to send a private message to the specified user" +#: src/ats-tool/gnunet-ats.c:433 +msgid "Type required\n" msgstr "" -#: src/chat/gnunet-chat.c:535 -msgid "The `/notice' command is an alias for `/msg'" +#: src/ats-tool/gnunet-ats.c:490 +msgid "get list of active addresses currently used" msgstr "" -#: src/chat/gnunet-chat.c:537 -msgid "The `/query' command is an alias for `/msg'" +#: src/ats-tool/gnunet-ats.c:493 +msgid "get list of all active addresses" msgstr "" -#: src/chat/gnunet-chat.c:539 -msgid "Use `/sig message' to send a signed public message" -msgstr "" +#: src/ats-tool/gnunet-ats.c:496 +#, fuzzy +msgid "do not resolve IP addresses to hostnames" +msgstr "Misslyckades att läsa kompislista från \"%s\"\n" -#: src/chat/gnunet-chat.c:542 -msgid "Use `/ack message' to require signed acknowledgment of the message" +#: src/ats-tool/gnunet-ats.c:499 +msgid "monitor mode" msgstr "" -#: src/chat/gnunet-chat.c:545 -msgid "Use `/anonymous message' to send a public anonymous message" -msgstr "" +#: src/ats-tool/gnunet-ats.c:502 +#, fuzzy +msgid "set preference for the given peer" +msgstr "Skriv ut information om GNUnets motparter." -#: src/chat/gnunet-chat.c:547 -msgid "The `/anon' command is an alias for `/anonymous'" +#: src/ats-tool/gnunet-ats.c:505 +msgid "print all configured quotas" msgstr "" -#: src/chat/gnunet-chat.c:549 -msgid "Use `/quit' to terminate gnunet-chat" +#: src/ats-tool/gnunet-ats.c:508 +msgid "peer id" msgstr "" -#: src/chat/gnunet-chat.c:551 -msgid "The `/leave' command is an alias for `/quit'" +#: src/ats-tool/gnunet-ats.c:511 +msgid "preference type to set: latency | bandwidth" msgstr "" -#: src/chat/gnunet-chat.c:554 -msgid "Use `/names' to list all of the current members in the chat room" +#: src/ats-tool/gnunet-ats.c:514 +msgid "preference value" msgstr "" -#: src/chat/gnunet-chat.c:556 -msgid "Use `/help command' to get help for a specific command" +#: src/ats-tool/gnunet-ats.c:517 +msgid "verbose output (include ATS address properties)" msgstr "" -#: src/chat/gnunet-chat.c:672 +#: src/ats-tool/gnunet-ats.c:526 #, fuzzy -msgid "You must specify a nickname\n" -msgstr "Du måste ange en mottagare!\n" +msgid "Print information about ATS state" +msgstr "Skriv ut information om GNUnets motparter." -#: src/chat/gnunet-chat.c:688 +#: src/block/block.c:105 #, fuzzy, c-format -msgid "Failed to join room `%s'\n" -msgstr "Misslyckades att läsa kompislista från \"%s\"\n" +msgid "Loading block plugin `%s'\n" +msgstr "Testar transport(er) %s\n" -#: src/chat/gnunet-chat.c:727 -msgid "set the nickname to use (required)" -msgstr "" +#: src/consensus/gnunet-consensus.c:317 +#, fuzzy +msgid "number of peers in consensus" +msgstr "antal iterationer" -#: src/chat/gnunet-chat.c:730 -msgid "set the chat room to join" +#: src/consensus/gnunet-consensus.c:320 +msgid "how many peers receive one value?" msgstr "" -#: src/chat/gnunet-chat.c:742 -msgid "Join a chat on GNUnet." -msgstr "" +#: src/consensus/gnunet-consensus.c:323 +#, fuzzy +msgid "number of values" +msgstr "antal iterationer" -#: src/chat/gnunet-service-chat.c:267 +#: src/consensus/gnunet-consensus.c:326 #, fuzzy -msgid "Failed to queue a message notification\n" -msgstr "Kunde inte spara konfiguration!" +msgid "consensus timeout" +msgstr "# sessionsnycklar accepterade" -#: src/chat/gnunet-service-chat.c:546 +#: src/consensus/gnunet-consensus-ibf.c:176 #, fuzzy -msgid "Failed to queue a join notification\n" -msgstr "Kunde inte spara konfiguration!" +msgid "number of element in set A-B" +msgstr "antal iterationer" -#: src/chat/gnunet-service-chat.c:729 +#: src/consensus/gnunet-consensus-ibf.c:179 #, fuzzy -msgid "Failed to queue a confirmation receipt\n" -msgstr "Kunde inte spara konfiguration!" +msgid "number of element in set B-A" +msgstr "antal iterationer" + +#: src/consensus/gnunet-consensus-ibf.c:182 +msgid "number of common elements in A and B" +msgstr "" + +#: src/consensus/gnunet-consensus-ibf.c:185 +msgid "hash num" +msgstr "" + +#: src/consensus/gnunet-consensus-ibf.c:188 +msgid "ibf size" +msgstr "" + +#: src/consensus/gnunet-consensus-start-peers.c:158 +msgid "start peers with the given template configuration" +msgstr "" -#: src/chat/gnunet-service-chat.c:907 +#: src/consensus/gnunet-consensus-start-peers.c:161 #, fuzzy -msgid "Failed to queue a leave notification\n" -msgstr "Kunde inte spara konfiguration!" +msgid "number of peers to start" +msgstr "antal iterationer" -#: src/core/core_api.c:786 +#: src/core/core_api.c:755 msgid "Client was disconnected from core service, trying to reconnect.\n" msgstr "" -#: src/core/gnunet-core.c:54 src/peerinfo-tool/gnunet-peerinfo.c:286 +#: src/core/gnunet-core.c:86 src/peerinfo-tool/gnunet-peerinfo.c:214 #, fuzzy, c-format msgid "Peer `%s'\n" msgstr "Jag är ändpunkt \"%s\".\n" -#: src/core/gnunet-core.c:72 src/peerinfo-tool/gnunet-peerinfo.c:817 +#: src/core/gnunet-core.c:119 src/core/gnunet-core.c:147 +#: src/transport/gnunet-transport.c:612 src/transport/gnunet-transport.c:636 +#, c-format +msgid "%24s: %-17s %4s (%u connections in total)\n" +msgstr "" + +#: src/core/gnunet-core.c:121 src/transport/gnunet-transport.c:614 +#, fuzzy +msgid "Connected to" +msgstr "\"%s\" ansluten till \"%s\".\n" + +#: src/core/gnunet-core.c:149 src/transport/gnunet-transport.c:638 +#, fuzzy +msgid "Disconnected from" +msgstr "\"%s\" ansluten till \"%s\".\n" + +#: src/core/gnunet-core.c:174 src/mesh/gnunet-mesh.c:176 +#: src/peerinfo-tool/gnunet-peerinfo.c:541 #, fuzzy, c-format msgid "Invalid command line argument `%s'\n" msgstr "Ogiltiga kommandoradsargument:\n" -#: src/core/gnunet-core.c:95 +#: src/core/gnunet-core.c:211 src/transport/gnunet-transport.c:1005 +#, fuzzy +msgid "provide information about all current connections (continuously)" +msgstr "Skriv ut information om GNUnets motparter." + +#: src/core/gnunet-core.c:222 #, fuzzy msgid "Print information about connected peers." msgstr "Skriv ut information om GNUnets motparter." -#: src/core/gnunet-service-core.c:97 +#: src/core/gnunet-service-core.c:109 +#, fuzzy, c-format +msgid "Failed to read hostkey: %s\n" +msgstr "Misslyckades att starta samling.\n" + +#: src/core/gnunet-service-core.c:123 #, c-format msgid "Core service of `%4s' ready.\n" msgstr "" +#: src/core/gnunet-service-core.c:149 +#, fuzzy +msgid "Core service is lacking HOSTKEY configuration setting. Exiting.\n" +msgstr "GNUnet-konfiguration" + +#: src/core/gnunet-service-core.c:163 +#: src/transport/gnunet-service-transport.c:737 +#, fuzzy +msgid "Transport service is unable to access hostkey. Exiting.\n" +msgstr "Kunde inte komma åt namnrymdsinformation.\n" + #: src/core/gnunet-service-core_clients.c:370 msgid "# send requests dropped (disconnected)" msgstr "" @@ -589,7 +501,7 @@ msgstr "" msgid "# messages discarded (session disconnected)" msgstr "Nätverksannonsering avstängd i konfigurationen!\n" -#: src/core/gnunet-service-core_clients.c:818 +#: src/core/gnunet-service-core_clients.c:518 #, fuzzy, c-format msgid "# bytes of messages of type %u received" msgstr "# krypterade PONG-meddelanden mottagna" @@ -635,7 +547,7 @@ msgid "# SET_KEY messages decrypted" msgstr "# PING-meddelanden skapade" #: src/core/gnunet-service-core_kx.c:977 -#: src/transport/gnunet-service-transport_validation.c:810 +#: src/transport/gnunet-service-transport_validation.c:865 #, fuzzy msgid "# PING messages received" msgstr "# PING-meddelanden skapade" @@ -663,7 +575,7 @@ msgid "# keepalive messages sent" msgstr "# PING-meddelanden i klartext skickade" #: src/core/gnunet-service-core_kx.c:1236 -#: src/transport/gnunet-service-transport_validation.c:1031 +#: src/transport/gnunet-service-transport_validation.c:1161 #, fuzzy msgid "# PONG messages received" msgstr "# krypterade PONG-meddelanden mottagna" @@ -683,58 +595,49 @@ msgstr "# sessionnycklar vägrade" msgid "# rekey operations confirmed via PONG" msgstr "# sessionnycklar vägrade" -#: src/core/gnunet-service-core_kx.c:1381 -#: src/core/gnunet-service-core_kx.c:1398 +#: src/core/gnunet-service-core_kx.c:1383 +#: src/core/gnunet-service-core_kx.c:1400 #, fuzzy msgid "# SET_KEY and PING messages created" msgstr "# PING-meddelanden skapade" -#: src/core/gnunet-service-core_kx.c:1402 +#: src/core/gnunet-service-core_kx.c:1404 msgid "# REKEY operations performed" msgstr "" -#: src/core/gnunet-service-core_kx.c:1537 +#: src/core/gnunet-service-core_kx.c:1539 msgid "# failed to decrypt message (no session key)" msgstr "" -#: src/core/gnunet-service-core_kx.c:1577 -#: src/core/gnunet-service-core_kx.c:1602 +#: src/core/gnunet-service-core_kx.c:1579 +#: src/core/gnunet-service-core_kx.c:1604 #, fuzzy msgid "# bytes dropped (duplicates)" msgstr "# byte kastade via UDP (utgående)" -#: src/core/gnunet-service-core_kx.c:1589 +#: src/core/gnunet-service-core_kx.c:1591 #, fuzzy msgid "# bytes dropped (out of sequence)" msgstr "# byte kastade via UDP (utgående)" -#: src/core/gnunet-service-core_kx.c:1626 +#: src/core/gnunet-service-core_kx.c:1628 #, fuzzy, c-format -msgid "Message received far too old (%llu ms). Content ignored.\n" +msgid "Message received far too old (%s). Content ignored.\n" msgstr "Meddelande mottaget från klient är ogiltig.\n" -#: src/core/gnunet-service-core_kx.c:1630 +#: src/core/gnunet-service-core_kx.c:1632 #, fuzzy msgid "# bytes dropped (ancient message)" msgstr "# byte kastade via UDP (utgående)" -#: src/core/gnunet-service-core_kx.c:1638 +#: src/core/gnunet-service-core_kx.c:1640 #, fuzzy msgid "# bytes of payload decrypted" msgstr "# byte dekrypterade" -#: src/core/gnunet-service-core_kx.c:1700 -#, fuzzy -msgid "Core service is lacking HOSTKEY configuration setting. Exiting.\n" -msgstr "GNUnet-konfiguration" - -#: src/core/gnunet-service-core_kx.c:1708 -msgid "Core service could not access hostkey. Exiting.\n" -msgstr "" - -#: src/core/gnunet-service-core_kx.c:1718 src/hostlist/hostlist-server.c:551 -#: src/peerinfo-tool/gnunet-peerinfo.c:823 -#: src/transport/gnunet-service-transport.c:611 +#: src/core/gnunet-service-core_kx.c:1703 src/hostlist/hostlist-server.c:552 +#: src/peerinfo-tool/gnunet-peerinfo.c:547 +#: src/transport/gnunet-service-transport.c:644 #, fuzzy msgid "Could not access PEERINFO service. Exiting.\n" msgstr "Kunde inte komma åt namnrymdsinformation.\n" @@ -753,23 +656,23 @@ msgstr "" msgid "# encrypted bytes given to transport" msgstr "" -#: src/core/gnunet-service-core_neighbours.c:418 +#: src/core/gnunet-service-core_neighbours.c:421 #, c-format msgid "Unsupported message of type %u (%u bytes) received from peer `%s'\n" msgstr "" #: src/core/gnunet-service-core_sessions.c:206 #: src/core/gnunet-service-core_sessions.c:269 -#: src/dht/gnunet-service-dht_neighbours.c:625 -#: src/dht/gnunet-service-dht_neighbours.c:683 -#: src/fs/gnunet-service-fs_cp.c:615 src/fs/gnunet-service-fs_cp.c:1532 -#: src/topology/gnunet-daemon-topology.c:709 -#: src/topology/gnunet-daemon-topology.c:810 -#: src/transport/gnunet-service-transport_neighbours.c:874 -#: src/transport/gnunet-service-transport_neighbours.c:1080 -#: src/transport/gnunet-service-transport_neighbours.c:1089 -#: src/transport/gnunet-service-transport_neighbours.c:2568 -#: src/transport/gnunet-service-transport_neighbours.c:2814 +#: src/dht/gnunet-service-dht_neighbours.c:645 +#: src/dht/gnunet-service-dht_neighbours.c:703 +#: src/fs/gnunet-service-fs_cp.c:630 src/fs/gnunet-service-fs_cp.c:1544 +#: src/topology/gnunet-daemon-topology.c:704 +#: src/topology/gnunet-daemon-topology.c:805 +#: src/transport/gnunet-service-transport_neighbours.c:1052 +#: src/transport/gnunet-service-transport_neighbours.c:1276 +#: src/transport/gnunet-service-transport_neighbours.c:1285 +#: src/transport/gnunet-service-transport_neighbours.c:2826 +#: src/transport/gnunet-service-transport_neighbours.c:3089 #, fuzzy msgid "# peers connected" msgstr "# av anslutna parter" @@ -792,40 +695,51 @@ msgstr "# krypterade PONG-meddelanden mottagna" msgid "# updates to my type map" msgstr "" -#: src/datacache/datacache.c:115 src/datacache/datacache.c:250 +#: src/datacache/datacache.c:115 src/datacache/datacache.c:266 #: src/datastore/gnunet-service-datastore.c:834 #, fuzzy msgid "# bytes stored" msgstr "# byte krypterade" -#: src/datacache/datacache.c:141 src/datacache/datacache.c:148 +#: src/datacache/datacache.c:117 src/datacache/datacache.c:268 +#, fuzzy +msgid "# items stored" +msgstr "# byte krypterade" + +#: src/datacache/datacache.c:143 src/datacache/datacache.c:150 #: src/datastore/gnunet-service-datastore.c:1483 #: src/datastore/gnunet-service-datastore.c:1494 #, fuzzy, c-format msgid "No `%s' specified for `%s' in configuration!\n" msgstr "Inga applikationer definierade i konfiguration!\n" -#: src/datacache/datacache.c:180 +#: src/datacache/datacache.c:184 #, c-format msgid "Loading `%s' datacache plugin\n" msgstr "" -#: src/datacache/datacache.c:188 +#: src/datacache/datacache.c:192 #, fuzzy, c-format msgid "Failed to load datacache plugin for `%s'\n" msgstr "Misslyckades att läsa kompislista från \"%s\"\n" -#: src/datacache/datacache.c:276 +#: src/datacache/datacache.c:295 #, fuzzy msgid "# requests received" msgstr "# byte mottogs via TCP" -#: src/datacache/datacache.c:284 +#: src/datacache/datacache.c:304 msgid "# requests filtered by bloom filter" msgstr "" -#: src/datacache/plugin_datacache_mysql.c:97 -#: src/datacache/plugin_datacache_mysql.c:104 +#: src/datacache/plugin_datacache_heap.c:406 +msgid "Heap datacache running\n" +msgstr "" + +#: src/datacache/plugin_datacache_postgres.c:392 +msgid "Postgres datacache running\n" +msgstr "" + #: src/datacache/plugin_datacache_sqlite.c:69 #: src/datacache/plugin_datacache_sqlite.c:72 #: src/datastore/plugin_datastore_mysql.c:803 @@ -833,59 +747,52 @@ msgstr "" #: src/datastore/plugin_datastore_sqlite.c:57 src/mysql/mysql.c:41 #: src/mysql/mysql.c:48 src/mysql/mysql.c:522 src/mysql/mysql.c:531 #: src/mysql/mysql.c:591 src/mysql/mysql.c:607 -#: src/namestore/plugin_namestore_sqlite.c:51 src/util/crypto_ksk.c:49 -#: src/util/crypto_rsa.c:67 src/include/gnunet_common.h:525 -#: src/include/gnunet_common.h:532 +#: src/namestore/plugin_namestore_postgres.c:52 +#: src/namestore/plugin_namestore_sqlite.c:51 src/util/crypto_ecc.c:46 +#: src/util/crypto_ksk.c:49 src/util/crypto_rsa.c:59 +#: src/include/gnunet_common.h:607 src/include/gnunet_common.h:614 #, c-format msgid "`%s' failed at %s:%d with error: %s\n" msgstr "\"%s\" misslyckades vid %s:%d med fel: %s\n" -#: src/datacache/plugin_datacache_mysql.c:450 -msgid "MySQL datacache running\n" -msgstr "" - -#: src/datacache/plugin_datacache_postgres.c:367 -msgid "Postgres datacache running\n" -msgstr "" - -#: src/datacache/plugin_datacache_sqlite.c:410 +#: src/datacache/plugin_datacache_sqlite.c:450 msgid "Sqlite datacache running\n" msgstr "" -#: src/datacache/plugin_datacache_sqlite.c:443 -#: src/datastore/plugin_datastore_sqlite.c:408 -#: src/namestore/plugin_namestore_sqlite.c:370 +#: src/datacache/plugin_datacache_sqlite.c:484 +#: src/datastore/plugin_datastore_sqlite.c:401 +#: src/namestore/plugin_namestore_sqlite.c:362 msgid "Tried to close sqlite without finalizing all prepared statements.\n" msgstr "" -#: src/datacache/plugin_datacache_sqlite.c:450 +#: src/datacache/plugin_datacache_sqlite.c:491 #, fuzzy, c-format msgid "Failed to close statement %p: %d\n" msgstr "Misslyckades att läsa kompislista från \"%s\"\n" -#: src/datacache/plugin_datacache_template.c:121 +#: src/datacache/plugin_datacache_template.c:125 msgid "Template datacache running\n" msgstr "" -#: src/datastore/datastore_api.c:305 +#: src/datastore/datastore_api.c:310 #, fuzzy msgid "Failed to transmit request to drop database.\n" msgstr "Misslyckades att skicka HTTP-begäran till värd \"%s\": %s\n" -#: src/datastore/datastore_api.c:388 +#: src/datastore/datastore_api.c:393 msgid "# queue entry timeouts" msgstr "" -#: src/datastore/datastore_api.c:432 +#: src/datastore/datastore_api.c:437 msgid "# queue overflows" msgstr "" -#: src/datastore/datastore_api.c:459 +#: src/datastore/datastore_api.c:465 #, fuzzy msgid "# queue entries created" msgstr "# PING-meddelanden skapade" -#: src/datastore/datastore_api.c:477 +#: src/datastore/datastore_api.c:483 msgid "# Requests dropped from datastore queue" msgstr "" @@ -894,65 +801,61 @@ msgstr "" msgid "# datastore connections (re)created" msgstr "Nätverksanslutning" -#: src/datastore/datastore_api.c:548 -msgid "# reconnected to DATASTORE" -msgstr "" - -#: src/datastore/datastore_api.c:612 +#: src/datastore/datastore_api.c:608 #, fuzzy msgid "# transmission request failures" msgstr "# klartext PONG-meddelanden mottagna" -#: src/datastore/datastore_api.c:633 +#: src/datastore/datastore_api.c:630 #, fuzzy msgid "# bytes sent to datastore" msgstr "# byte krypterade" -#: src/datastore/datastore_api.c:764 +#: src/datastore/datastore_api.c:762 #, fuzzy msgid "Failed to receive status response from database." msgstr "Misslyckades att ta emot svar till \"%s\" meddelande från gnunetd\n" -#: src/datastore/datastore_api.c:778 +#: src/datastore/datastore_api.c:776 msgid "Error reading response from datastore service" msgstr "" -#: src/datastore/datastore_api.c:790 src/datastore/datastore_api.c:796 +#: src/datastore/datastore_api.c:788 src/datastore/datastore_api.c:794 #, fuzzy msgid "Invalid error message received from datastore service" msgstr "Ogiltigt meddelande mottogs den %s:%d." -#: src/datastore/datastore_api.c:800 +#: src/datastore/datastore_api.c:798 #, fuzzy msgid "# status messages received" msgstr "# krypterade PONG-meddelanden mottagna" -#: src/datastore/datastore_api.c:869 +#: src/datastore/datastore_api.c:867 msgid "# PUT requests executed" msgstr "" -#: src/datastore/datastore_api.c:936 +#: src/datastore/datastore_api.c:934 msgid "# RESERVE requests executed" msgstr "" -#: src/datastore/datastore_api.c:997 +#: src/datastore/datastore_api.c:995 msgid "# RELEASE RESERVE requests executed" msgstr "" -#: src/datastore/datastore_api.c:1054 +#: src/datastore/datastore_api.c:1052 msgid "# UPDATE requests executed" msgstr "" -#: src/datastore/datastore_api.c:1118 +#: src/datastore/datastore_api.c:1116 msgid "# REMOVE requests executed" msgstr "" -#: src/datastore/datastore_api.c:1163 +#: src/datastore/datastore_api.c:1161 #, fuzzy msgid "Failed to receive response from database.\n" msgstr "Misslyckades att ta emot svar till \"%s\" meddelande från gnunetd\n" -#: src/datastore/datastore_api.c:1221 +#: src/datastore/datastore_api.c:1220 #, fuzzy msgid "# Results received" msgstr "# byte mottogs via TCP" @@ -965,7 +868,7 @@ msgstr "" msgid "# GET ZERO ANONYMITY requests executed" msgstr "" -#: src/datastore/datastore_api.c:1409 +#: src/datastore/datastore_api.c:1410 msgid "# GET requests executed" msgstr "" @@ -979,10 +882,12 @@ msgid "# bytes purged (low-priority)" msgstr "" #: src/datastore/gnunet-service-datastore.c:480 +#: src/gns/gnunet-gns-helper-service-w32.c:159 msgid "Transmission to client failed!\n" msgstr "" #: src/datastore/gnunet-service-datastore.c:511 +#: src/gns/gnunet-gns-helper-service-w32.c:189 msgid "Shutdown in progress, aborting transmission.\n" msgstr "" @@ -1122,6 +1027,10 @@ msgstr "" msgid "Bloomfilter construction complete.\n" msgstr "" +#: src/datastore/plugin_datastore_heap.c:820 +msgid "Heap database running\n" +msgstr "" + #: src/datastore/plugin_datastore_mysql.c:780 #, fuzzy, c-format msgid "Failed to prepare statement `%s'\n" @@ -1142,6 +1051,7 @@ msgid "Failed to drop table from database.\n" msgstr "Misslyckades att ta emot svar till \"%s\" meddelande från gnunetd\n" #: src/datastore/plugin_datastore_postgres.c:860 +#: src/namestore/plugin_namestore_postgres.c:652 msgid "Postgres database running\n" msgstr "" @@ -1150,220 +1060,238 @@ msgstr "" msgid "`%s' failed at %s:%u with error: %s" msgstr "\"%s\" misslyckades vid %s:%d med fel: %s\n" -#: src/datastore/plugin_datastore_sqlite.c:233 -#: src/namestore/plugin_namestore_sqlite.c:204 -#, fuzzy, c-format -msgid "Option `%s' in section `%s' missing in configuration!\n" -msgstr "Inga applikationer definierade i konfiguration!\n" - -#: src/datastore/plugin_datastore_sqlite.c:260 -#: src/namestore/plugin_namestore_sqlite.c:229 +#: src/datastore/plugin_datastore_sqlite.c:253 +#: src/namestore/plugin_namestore_sqlite.c:223 #, fuzzy, c-format msgid "Unable to initialize SQLite: %s.\n" msgstr "Kunde inte initiera SQLite.\n" -#: src/datastore/plugin_datastore_sqlite.c:655 +#: src/datastore/plugin_datastore_sqlite.c:648 msgid "Invalid data in database. Trying to fix (by deletion).\n" msgstr "" -#: src/datastore/plugin_datastore_sqlite.c:1139 +#: src/datastore/plugin_datastore_sqlite.c:1134 msgid "sqlite version to old to determine size, assuming zero\n" msgstr "" -#: src/datastore/plugin_datastore_sqlite.c:1158 +#: src/datastore/plugin_datastore_sqlite.c:1153 #, c-format msgid "" "Using sqlite page utilization to estimate payload (%llu pages of size %llu " "bytes)\n" msgstr "" -#: src/datastore/plugin_datastore_sqlite.c:1198 -#: src/namestore/plugin_namestore_sqlite.c:829 +#: src/datastore/plugin_datastore_sqlite.c:1193 +#: src/namestore/plugin_namestore_sqlite.c:827 msgid "Sqlite database running\n" msgstr "" -#: src/datastore/plugin_datastore_template.c:241 +#: src/datastore/plugin_datastore_template.c:257 msgid "Template database running\n" msgstr "" -#: src/dht/dht_api.c:348 +#: src/dht/dht_api.c:375 #, fuzzy msgid "Failed to connect to the DHT service!\n" msgstr "Misslyckades att ansluta till gnunetd.\n" -#: src/dht/gnunet-dht-get.c:201 src/dht/gnunet-dht-monitor.c:293 -#: src/dht/gnunet-dht-put.c:192 +#: src/dht/gnunet-dht-get.c:132 +#, c-format +msgid "" +"Result %d, type %d:\n" +"%.*s\n" +msgstr "" + +#: src/dht/gnunet-dht-get.c:156 +msgid "Must provide key for DHT GET!\n" +msgstr "" + +#: src/dht/gnunet-dht-get.c:162 src/dht/gnunet-dht-monitor.c:225 +#, fuzzy +msgid "Failed to connect to DHT service!\n" +msgstr "Misslyckades att ansluta till gnunetd.\n" + +#: src/dht/gnunet-dht-get.c:170 +msgid "Issueing DHT GET with key" +msgstr "" + +#: src/dht/gnunet-dht-get.c:186 src/dht/gnunet-dht-monitor.c:262 +#: src/dht/gnunet-dht-put.c:198 msgid "the query key" msgstr "" -#: src/dht/gnunet-dht-get.c:204 +#: src/dht/gnunet-dht-get.c:189 msgid "how many parallel requests (replicas) to create" msgstr "" -#: src/dht/gnunet-dht-get.c:207 src/dht/gnunet-dht-monitor.c:296 +#: src/dht/gnunet-dht-get.c:192 src/dht/gnunet-dht-monitor.c:265 msgid "the type of data to look for" msgstr "" -#: src/dht/gnunet-dht-get.c:210 src/dht/gnunet-dht-put.c:201 +#: src/dht/gnunet-dht-get.c:195 src/dht/gnunet-dht-put.c:210 msgid "how long to execute this query before giving up?" msgstr "" -#: src/dht/gnunet-dht-get.c:213 src/dht/gnunet-dht-monitor.c:302 -#: src/dht/gnunet-dht-put.c:204 src/fs/gnunet-download.c:271 -#: src/fs/gnunet-publish.c:731 src/fs/gnunet-search.c:297 -#: src/fs/gnunet-unindex.c:169 src/nse/gnunet-nse-profiler.c:910 +#: src/dht/gnunet-dht-get.c:198 src/dht/gnunet-dht-put.c:201 +msgid "use DHT's demultiplex everywhere option" +msgstr "" + +#: src/dht/gnunet-dht-get.c:201 src/dht/gnunet-dht-monitor.c:271 +#: src/dht/gnunet-dht-put.c:213 src/fs/gnunet-auto-share.c:753 +#: src/fs/gnunet-download.c:328 src/fs/gnunet-publish.c:736 +#: src/fs/gnunet-search.c:294 src/fs/gnunet-unindex.c:168 +#: src/nse/gnunet-nse-profiler.c:1033 msgid "be verbose (print progress information)" msgstr "" -#: src/dht/gnunet-dht-get.c:232 +#: src/dht/gnunet-dht-get.c:222 msgid "Issue a GET request to the GNUnet DHT, prints results." msgstr "" -#: src/dht/gnunet-dht-monitor.c:299 -msgid "how long to execute? 0 = forever" +#: src/dht/gnunet-dht-monitor.c:268 +msgid "how long should the monitor command run" msgstr "" -#: src/dht/gnunet-dht-monitor.c:321 +#: src/dht/gnunet-dht-monitor.c:293 msgid "Prints all packets that go through the DHT." msgstr "" -#: src/dht/gnunet-dht-put.c:108 -msgid "PUT request sent!\n" -msgstr "" +#: src/dht/gnunet-dht-put.c:118 +#, fuzzy +msgid "PUT request sent with key" +msgstr "# byte mottogs via TCP" -#: src/dht/gnunet-dht-put.c:111 +#: src/dht/gnunet-dht-put.c:121 msgid "Timeout sending PUT request!\n" msgstr "" -#: src/dht/gnunet-dht-put.c:114 +#: src/dht/gnunet-dht-put.c:124 #, fuzzy msgid "PUT request not confirmed!\n" msgstr "# byte mottogs via TCP" -#: src/dht/gnunet-dht-put.c:144 +#: src/dht/gnunet-dht-put.c:153 msgid "Must provide KEY and DATA for DHT put!\n" msgstr "" -#: src/dht/gnunet-dht-put.c:152 +#: src/dht/gnunet-dht-put.c:160 #, fuzzy, c-format msgid "Could not connect to %s service!\n" msgstr "Kunde inte ansluta till gnunetd.\n" -#: src/dht/gnunet-dht-put.c:157 -#, fuzzy, c-format -msgid "Connected to %s service!\n" -msgstr "\"%s\" ansluten till \"%s\".\n" - -#: src/dht/gnunet-dht-put.c:172 +#: src/dht/gnunet-dht-put.c:176 #, c-format msgid "Issuing put request for `%s' with data `%s'!\n" msgstr "" -#: src/dht/gnunet-dht-put.c:186 +#: src/dht/gnunet-dht-put.c:192 msgid "the data to insert under the key" msgstr "" -#: src/dht/gnunet-dht-put.c:189 +#: src/dht/gnunet-dht-put.c:195 msgid "how long to store this entry in the dht (in seconds)" msgstr "" -#: src/dht/gnunet-dht-put.c:195 +#: src/dht/gnunet-dht-put.c:204 msgid "how many replicas to create" msgstr "" -#: src/dht/gnunet-dht-put.c:198 +#: src/dht/gnunet-dht-put.c:207 msgid "the type to insert data as" msgstr "" -#: src/dht/gnunet-dht-put.c:223 +#: src/dht/gnunet-dht-put.c:235 msgid "Issue a PUT request to the GNUnet DHT insert DATA under KEY." msgstr "" -#: src/dht/gnunet-service-dht.c:163 src/testing/testing.c:544 -#: src/testing/testing.c:1968 src/testing/testing.c:1998 +#: src/dht/gnunet-service-dht.c:172 #, fuzzy msgid "Failed to connect to transport service!\n" msgstr "Misslyckades att ansluta till gnunetd.\n" -#: src/dht/gnunet-service-dht_clients.c:407 +#: src/dht/gnunet-service-dht_clients.c:413 #, fuzzy msgid "# GET requests from clients injected" msgstr "# byte mottogs via TCP" -#: src/dht/gnunet-service-dht_clients.c:500 +#: src/dht/gnunet-service-dht_clients.c:503 #, fuzzy msgid "# PUT requests received from clients" msgstr "Meddelande mottaget från klient är ogiltig.\n" -#: src/dht/gnunet-service-dht_clients.c:584 +#: src/dht/gnunet-service-dht_clients.c:585 #, fuzzy msgid "# GET requests received from clients" msgstr "Meddelande mottaget från klient är ogiltig.\n" -#: src/dht/gnunet-service-dht_clients.c:682 +#: src/dht/gnunet-service-dht_clients.c:791 #, fuzzy msgid "# GET STOP requests received from clients" msgstr "Meddelande mottaget från klient är ogiltig.\n" -#: src/dht/gnunet-service-dht_clients.c:919 +#: src/dht/gnunet-service-dht_clients.c:1035 msgid "# Key match, type mismatches in REPLY to CLIENT" msgstr "" -#: src/dht/gnunet-service-dht_clients.c:932 +#: src/dht/gnunet-service-dht_clients.c:1048 msgid "# Duplicate REPLIES to CLIENT request dropped" msgstr "" -#: src/dht/gnunet-service-dht_clients.c:967 +#: src/dht/gnunet-service-dht_clients.c:1085 #, c-format msgid "Unsupported block type (%u) in request!\n" msgstr "" -#: src/dht/gnunet-service-dht_clients.c:989 +#: src/dht/gnunet-service-dht_clients.c:1108 #, fuzzy msgid "# RESULTS queued for clients" msgstr "Meddelande mottaget från klient är ogiltig.\n" -#: src/dht/gnunet-service-dht_clients.c:1038 -#: src/dht/gnunet-service-dht_clients.c:1081 +#: src/dht/gnunet-service-dht_clients.c:1157 +#: src/dht/gnunet-service-dht_clients.c:1199 msgid "# REPLIES ignored for CLIENTS (no match)" msgstr "" -#: src/dht/gnunet-service-dht_clients.c:1048 +#: src/dht/gnunet-service-dht_clients.c:1167 #, fuzzy msgid "Could not pass reply to client, message too big!\n" msgstr "Kunde inte skicka meddelande till gnunetd\n" -#: src/dht/gnunet-service-dht_datacache.c:93 +#: src/dht/gnunet-service-dht_datacache.c:64 #, fuzzy, c-format msgid "%s request received, but have no datacache!\n" msgstr "# byte mottagna av typen %d" -#: src/dht/gnunet-service-dht_datacache.c:103 +#: src/dht/gnunet-service-dht_datacache.c:74 msgid "# ITEMS stored in datacache" msgstr "" -#: src/dht/gnunet-service-dht_datacache.c:207 +#: src/dht/gnunet-service-dht_datacache.c:159 msgid "# Good RESULTS found in datacache" msgstr "" -#: src/dht/gnunet-service-dht_datacache.c:218 +#: src/dht/gnunet-service-dht_datacache.c:170 msgid "# Duplicate RESULTS found in datacache" msgstr "" -#: src/dht/gnunet-service-dht_datacache.c:224 +#: src/dht/gnunet-service-dht_datacache.c:176 msgid "# Invalid RESULTS found in datacache" msgstr "" -#: src/dht/gnunet-service-dht_datacache.c:236 +#: src/dht/gnunet-service-dht_datacache.c:182 +msgid "# Irrelevant RESULTS found in datacache" +msgstr "" + +#: src/dht/gnunet-service-dht_datacache.c:194 msgid "# Unsupported RESULTS found in datacache" msgstr "" -#: src/dht/gnunet-service-dht_datacache.c:239 +#: src/dht/gnunet-service-dht_datacache.c:197 #, c-format msgid "Unsupported block type (%u) in local response!\n" msgstr "" -#: src/dht/gnunet-service-dht_datacache.c:269 +#: src/dht/gnunet-service-dht_datacache.c:227 #, fuzzy msgid "# GET requests given to datacache" msgstr "# byte mottogs via TCP" @@ -1373,93 +1301,100 @@ msgstr "# byte mottogs via TCP" msgid "# HELLOs obtained from peerinfo" msgstr "Meddelande mottaget från klient är ogiltig.\n" -#: src/dht/gnunet-service-dht_neighbours.c:481 +#: src/dht/gnunet-service-dht_neighbours.c:501 msgid "# Preference updates given to core" msgstr "" -#: src/dht/gnunet-service-dht_neighbours.c:571 +#: src/dht/gnunet-service-dht_neighbours.c:591 #, fuzzy msgid "# FIND PEER messages initiated" msgstr "# PING-meddelanden skapade" -#: src/dht/gnunet-service-dht_neighbours.c:717 +#: src/dht/gnunet-service-dht_neighbours.c:737 #, fuzzy msgid "# Queued messages discarded (peer disconnected)" msgstr "Nätverksannonsering avstängd i konfigurationen!\n" -#: src/dht/gnunet-service-dht_neighbours.c:772 +#: src/dht/gnunet-service-dht_neighbours.c:792 #, fuzzy msgid "# Bytes transmitted to other peers" msgstr "# byte skickade av typen %d" -#: src/dht/gnunet-service-dht_neighbours.c:810 -msgid "# Bytes of bandwdith requested from core" +#: src/dht/gnunet-service-dht_neighbours.c:830 +msgid "# Bytes of bandwidth requested from core" msgstr "" -#: src/dht/gnunet-service-dht_neighbours.c:1032 -#: src/dht/gnunet-service-dht_neighbours.c:1060 +#: src/dht/gnunet-service-dht_neighbours.c:1052 +#: src/dht/gnunet-service-dht_neighbours.c:1080 msgid "# Peers excluded from routing due to Bloomfilter" msgstr "" -#: src/dht/gnunet-service-dht_neighbours.c:1041 -#: src/dht/gnunet-service-dht_neighbours.c:1075 +#: src/dht/gnunet-service-dht_neighbours.c:1061 +#: src/dht/gnunet-service-dht_neighbours.c:1095 msgid "# Peer selection failed" msgstr "" -#: src/dht/gnunet-service-dht_neighbours.c:1207 +#: src/dht/gnunet-service-dht_neighbours.c:1229 #, fuzzy msgid "# PUT requests routed" msgstr "# byte mottogs via TCP" -#: src/dht/gnunet-service-dht_neighbours.c:1236 +#: src/dht/gnunet-service-dht_neighbours.c:1258 #, fuzzy msgid "# PUT messages queued for transmission" msgstr "# PING-meddelanden skapade" -#: src/dht/gnunet-service-dht_neighbours.c:1315 +#: src/dht/gnunet-service-dht_neighbours.c:1265 +#: src/dht/gnunet-service-dht_neighbours.c:1378 +#: src/dht/gnunet-service-dht_neighbours.c:1478 +#, fuzzy +msgid "# P2P messages dropped due to full queue" +msgstr "Nätverksannonsering avstängd i konfigurationen!\n" + +#: src/dht/gnunet-service-dht_neighbours.c:1343 #, fuzzy msgid "# GET requests routed" msgstr "# byte mottogs via TCP" -#: src/dht/gnunet-service-dht_neighbours.c:1342 +#: src/dht/gnunet-service-dht_neighbours.c:1370 #, fuzzy msgid "# GET messages queued for transmission" msgstr "# PING-meddelanden skapade" -#: src/dht/gnunet-service-dht_neighbours.c:1443 +#: src/dht/gnunet-service-dht_neighbours.c:1485 #, fuzzy msgid "# RESULT messages queued for transmission" msgstr "# PING-meddelanden skapade" -#: src/dht/gnunet-service-dht_neighbours.c:1531 +#: src/dht/gnunet-service-dht_neighbours.c:1573 #, fuzzy msgid "# P2P PUT requests received" msgstr "# byte mottogs via TCP" -#: src/dht/gnunet-service-dht_neighbours.c:1647 +#: src/dht/gnunet-service-dht_neighbours.c:1702 msgid "# FIND PEER requests ignored due to Bloomfilter" msgstr "" -#: src/dht/gnunet-service-dht_neighbours.c:1655 +#: src/dht/gnunet-service-dht_neighbours.c:1710 msgid "# FIND PEER requests ignored due to lack of HELLO" msgstr "" -#: src/dht/gnunet-service-dht_neighbours.c:1746 +#: src/dht/gnunet-service-dht_neighbours.c:1801 #, fuzzy msgid "# P2P GET requests received" msgstr "# byte mottogs via TCP" -#: src/dht/gnunet-service-dht_neighbours.c:1788 +#: src/dht/gnunet-service-dht_neighbours.c:1843 #, fuzzy msgid "# P2P FIND PEER requests processed" msgstr "# byte mottogs via TCP" -#: src/dht/gnunet-service-dht_neighbours.c:1802 +#: src/dht/gnunet-service-dht_neighbours.c:1857 #, fuzzy msgid "# P2P GET requests ONLY routed" msgstr "# byte mottogs via TCP" -#: src/dht/gnunet-service-dht_neighbours.c:1876 +#: src/dht/gnunet-service-dht_neighbours.c:1944 #, fuzzy msgid "# P2P RESULTS received" msgstr "# krypterade PONG-meddelanden mottagna" @@ -1481,18 +1416,27 @@ msgstr "" msgid "# Invalid REPLIES matched against routing table" msgstr "" -#: src/dht/gnunet-service-dht_routing.c:238 +#: src/dht/gnunet-service-dht_routing.c:232 +msgid "# Irrelevant REPLIES matched against routing table" +msgstr "" + +#: src/dht/gnunet-service-dht_routing.c:244 msgid "# Unsupported REPLIES matched against routing table" msgstr "" -#: src/dht/gnunet-service-dht_routing.c:311 +#: src/dht/gnunet-service-dht_routing.c:317 msgid "# Entries removed from routing table" msgstr "" -#: src/dht/gnunet-service-dht_routing.c:352 +#: src/dht/gnunet-service-dht_routing.c:400 msgid "# Entries added to routing table" msgstr "" +#: src/dht/gnunet-service-dht_routing.c:418 +#, fuzzy +msgid "# DHT requests combined" +msgstr "# byte mottogs via TCP" + #: src/dht/plugin_block_dht.c:136 #, fuzzy, c-format msgid "Block not of type %u\n" @@ -1507,16 +1451,52 @@ msgstr "" msgid "Block of type %u is malformed\n" msgstr "" -#: src/dns/gnunet-dns-monitor.c:337 -msgid "only monitor DNS queries" -msgstr "" +#: src/dns/dnsparser.c:152 +#, fuzzy, c-format +msgid "Failed to convert DNS IDNA name `%s' to UTF-8: %s\n" +msgstr "Misslyckades att leverera \"%s\" meddelande.\n" -#: src/dns/gnunet-dns-monitor.c:340 -msgid "only monitor DNS replies" -msgstr "" +#: src/dns/dnsparser.c:626 +#, fuzzy, c-format +msgid "Failed to convert UTF-8 name `%s' to DNS IDNA format: %s\n" +msgstr "Misslyckades att leverera \"%s\" meddelande.\n" -#: src/dns/gnunet-dns-monitor.c:348 -msgid "Monitor DNS queries." +#: src/dns/dnsstub.c:175 +#, fuzzy, c-format +msgid "Could not bind to any port: %s\n" +msgstr "Kunde inte köra \"%s\": %s\n" + +#: src/dns/dnsstub.c:295 src/dns/dnsstub.c:383 +#: src/gns/gnunet-service-gns_resolver.c:1621 +#, fuzzy, c-format +msgid "Failed to send DNS request to %s\n" +msgstr "Misslyckades att skicka HTTP-begäran till värd \"%s\": %s\n" + +#: src/dns/dnsstub.c:299 +#, fuzzy, c-format +msgid "Sent DNS request to %s\n" +msgstr "Misslyckades att skicka HTTP-begäran till värd \"%s\": %s\n" + +#: src/dns/dnsstub.c:368 +#, c-format +msgid "Configured DNS exit `%s' is not working / valid.\n" +msgstr "" + +#: src/dns/dnsstub.c:440 +#, c-format +msgid "Received DNS response that is too small (%u bytes)" +msgstr "" + +#: src/dns/gnunet-dns-monitor.c:355 +msgid "only monitor DNS queries" +msgstr "" + +#: src/dns/gnunet-dns-monitor.c:358 +msgid "only monitor DNS replies" +msgstr "" + +#: src/dns/gnunet-dns-monitor.c:369 +msgid "Monitor DNS queries." msgstr "" #: src/dns/gnunet-dns-redirector.c:236 @@ -1527,77 +1507,59 @@ msgstr "" msgid "set AAAA records" msgstr "" -#: src/dns/gnunet-dns-redirector.c:247 +#: src/dns/gnunet-dns-redirector.c:251 msgid "Change DNS replies to point elsewhere." msgstr "" -#: src/dns/gnunet-service-dns.c:485 -#, fuzzy, c-format -msgid "Could not bind to any port: %s\n" -msgstr "Kunde inte köra \"%s\": %s\n" - -#: src/dns/gnunet-service-dns.c:639 +#: src/dns/gnunet-service-dns.c:456 msgid "# DNS requests answered via TUN interface" msgstr "" -#: src/dns/gnunet-service-dns.c:822 +#: src/dns/gnunet-service-dns.c:603 msgid "# DNS exit failed (failed to open socket)" msgstr "" -#: src/dns/gnunet-service-dns.c:1005 -#, c-format -msgid "Received DNS response that is too small (%u bytes)" -msgstr "" - -#: src/dns/gnunet-service-dns.c:1050 +#: src/dns/gnunet-service-dns.c:714 msgid "# External DNS response discarded (no matching request)" msgstr "" -#: src/dns/gnunet-service-dns.c:1168 +#: src/dns/gnunet-service-dns.c:792 msgid "# Client response discarded (no matching request)" msgstr "" -#: src/dns/gnunet-service-dns.c:1281 +#: src/dns/gnunet-service-dns.c:907 msgid "Received malformed IPv4-UDP packet on TUN interface.\n" msgstr "" -#: src/dns/gnunet-service-dns.c:1297 +#: src/dns/gnunet-service-dns.c:923 msgid "Received malformed IPv6-UDP packet on TUN interface.\n" msgstr "" -#: src/dns/gnunet-service-dns.c:1306 +#: src/dns/gnunet-service-dns.c:932 #, c-format msgid "Got non-IP packet with %u bytes and protocol %u from TUN\n" msgstr "" -#: src/dns/gnunet-service-dns.c:1315 +#: src/dns/gnunet-service-dns.c:942 msgid "# Non-DNS UDP packet received via TUN interface" msgstr "" -#: src/dns/gnunet-service-dns.c:1380 +#: src/dns/gnunet-service-dns.c:1009 #, fuzzy msgid "# DNS requests received via TUN interface" msgstr "Meddelande mottaget från klient är ogiltig.\n" -#: src/dns/gnunet-service-dns.c:1465 -#, c-format -msgid "Configured DNS exit `%s' is not working / valid.\n" -msgstr "" - -#: src/dns/gnunet-service-dns.c:1497 src/exit/gnunet-daemon-exit.c:2674 -msgid "# Inbound MESH tunnels created" -msgstr "" - -#: src/dns/gnunet-service-dns.c:1561 src/exit/gnunet-daemon-exit.c:3032 +#: src/dns/gnunet-service-dns.c:1049 src/exit/gnunet-daemon-exit.c:3351 #, c-format msgid "`%s' must be installed SUID, refusing to run\n" msgstr "" -#: src/dns/gnunet-service-dns.c:1581 -msgid "Configured to provide DNS exit, but no valid DNS server configured!\n" -msgstr "" +#: src/dns/gnunet-service-dns.c:1069 src/exit/gnunet-daemon-exit.c:3407 +#, fuzzy +msgid "need a valid IPv4 or IPv6 address\n" +msgstr "Ogiltigt svar på \"%s\".\n" -#: src/dv/dv_api.c:179 +#: src/dv/dv_api.c:189 #, fuzzy msgid "Failed to connect to the dv service!\n" msgstr "Misslyckades att ansluta till gnunetd.\n" @@ -1607,204 +1569,208 @@ msgstr "Misslyckades att ansluta till gnunetd.\n" msgid "%s Received message from %s of type %d, distance %u!\n" msgstr "Mottog skadat meddelande från motpart \"%s\"i %s:%d.\n" -#: src/exit/gnunet-daemon-exit.c:508 +#: src/exit/gnunet-daemon-exit.c:741 #, c-format msgid "Got duplicate service records for `%s:%u'\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:563 +#: src/exit/gnunet-daemon-exit.c:794 #, fuzzy msgid "# Bytes transmitted via mesh tunnels" msgstr "# byte skickade av typen %d" -#: src/exit/gnunet-daemon-exit.c:679 src/exit/gnunet-daemon-exit.c:2069 -#: src/exit/gnunet-daemon-exit.c:2319 src/vpn/gnunet-service-vpn.c:1394 -#: src/vpn/gnunet-service-vpn.c:1795 src/vpn/gnunet-service-vpn.c:1958 +#: src/exit/gnunet-daemon-exit.c:911 src/exit/gnunet-daemon-exit.c:2343 +#: src/exit/gnunet-daemon-exit.c:2603 src/vpn/gnunet-service-vpn.c:1411 +#: src/vpn/gnunet-service-vpn.c:1812 src/vpn/gnunet-service-vpn.c:1975 msgid "# ICMPv4 packets dropped (type not allowed)" msgstr "" -#: src/exit/gnunet-daemon-exit.c:716 src/exit/gnunet-daemon-exit.c:2128 -#: src/exit/gnunet-daemon-exit.c:2378 src/vpn/gnunet-service-vpn.c:1450 -#: src/vpn/gnunet-service-vpn.c:1854 src/vpn/gnunet-service-vpn.c:1991 +#: src/exit/gnunet-daemon-exit.c:948 src/exit/gnunet-daemon-exit.c:2402 +#: src/exit/gnunet-daemon-exit.c:2662 src/vpn/gnunet-service-vpn.c:1467 +#: src/vpn/gnunet-service-vpn.c:1871 src/vpn/gnunet-service-vpn.c:2008 msgid "# ICMPv6 packets dropped (type not allowed)" msgstr "" -#: src/exit/gnunet-daemon-exit.c:756 +#: src/exit/gnunet-daemon-exit.c:988 msgid "# ICMP packets dropped (not allowed)" msgstr "" -#: src/exit/gnunet-daemon-exit.c:763 +#: src/exit/gnunet-daemon-exit.c:995 msgid "ICMP Packet dropped, have no matching connection information\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:840 +#: src/exit/gnunet-daemon-exit.c:1072 msgid "UDP Packet dropped, have no matching connection information\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:915 +#: src/exit/gnunet-daemon-exit.c:1147 msgid "TCP Packet dropped, have no matching connection information\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:968 +#: src/exit/gnunet-daemon-exit.c:1200 #, fuzzy msgid "# Packets received from TUN" msgstr "# byte mottagna via HTTP" -#: src/exit/gnunet-daemon-exit.c:982 +#: src/exit/gnunet-daemon-exit.c:1214 #, fuzzy msgid "# Bytes received from TUN" msgstr "# byte mottagna via HTTP" -#: src/exit/gnunet-daemon-exit.c:1008 +#: src/exit/gnunet-daemon-exit.c:1240 msgid "IPv4 packet options received. Ignored.\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:1035 +#: src/exit/gnunet-daemon-exit.c:1267 #, c-format msgid "IPv4 packet with unsupported next header %u received. Ignored.\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:1081 +#: src/exit/gnunet-daemon-exit.c:1313 #, c-format msgid "IPv6 packet with unsupported next header %d received. Ignored.\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:1089 +#: src/exit/gnunet-daemon-exit.c:1321 #, c-format msgid "Packet from unknown protocol %u received. Ignored.\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:1471 +#: src/exit/gnunet-daemon-exit.c:1703 #, fuzzy msgid "# TCP packets sent via TUN" msgstr "# byte skickade via UDP" -#: src/exit/gnunet-daemon-exit.c:1571 +#: src/exit/gnunet-daemon-exit.c:1814 msgid "# TCP service creation requests received via mesh" msgstr "" -#: src/exit/gnunet-daemon-exit.c:1574 src/exit/gnunet-daemon-exit.c:1653 -#: src/exit/gnunet-daemon-exit.c:1763 src/exit/gnunet-daemon-exit.c:1993 -#: src/exit/gnunet-daemon-exit.c:2235 src/exit/gnunet-daemon-exit.c:2516 -#: src/exit/gnunet-daemon-exit.c:2616 +#: src/exit/gnunet-daemon-exit.c:1817 src/exit/gnunet-daemon-exit.c:1906 +#: src/exit/gnunet-daemon-exit.c:2026 src/exit/gnunet-daemon-exit.c:2267 +#: src/exit/gnunet-daemon-exit.c:2519 src/exit/gnunet-daemon-exit.c:2811 +#: src/exit/gnunet-daemon-exit.c:2921 #, fuzzy msgid "# Bytes received from MESH" msgstr "# byte mottagna via HTTP" -#: src/exit/gnunet-daemon-exit.c:1607 src/exit/gnunet-daemon-exit.c:2638 +#: src/exit/gnunet-daemon-exit.c:1850 src/exit/gnunet-daemon-exit.c:2943 #, c-format msgid "No service found for %s on port %d!\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:1611 +#: src/exit/gnunet-daemon-exit.c:1854 #, fuzzy msgid "# TCP requests dropped (no such service)" msgstr "# byte mottogs via TCP" -#: src/exit/gnunet-daemon-exit.c:1656 +#: src/exit/gnunet-daemon-exit.c:1909 #, fuzzy msgid "# TCP IP-exit creation requests received via mesh" msgstr "# byte mottogs via TCP" -#: src/exit/gnunet-daemon-exit.c:1766 +#: src/exit/gnunet-daemon-exit.c:2029 #, fuzzy msgid "# TCP data requests received via mesh" msgstr "# byte mottogs via TCP" -#: src/exit/gnunet-daemon-exit.c:1780 +#: src/exit/gnunet-daemon-exit.c:2043 #, fuzzy msgid "# TCP DATA requests dropped (no session)" msgstr "# byte mottogs via TCP" -#: src/exit/gnunet-daemon-exit.c:1830 +#: src/exit/gnunet-daemon-exit.c:2093 #, fuzzy msgid "# ICMP packets sent via TUN" msgstr "# byte skickade via UDP" -#: src/exit/gnunet-daemon-exit.c:1996 +#: src/exit/gnunet-daemon-exit.c:2270 #, fuzzy msgid "# ICMP IP-exit requests received via mesh" msgstr "# byte mottogs via TCP" -#: src/exit/gnunet-daemon-exit.c:2238 +#: src/exit/gnunet-daemon-exit.c:2522 #, fuzzy msgid "# ICMP service requests received via mesh" msgstr "Meddelande mottaget från klient är ogiltig.\n" -#: src/exit/gnunet-daemon-exit.c:2304 src/vpn/gnunet-service-vpn.c:1384 -#: src/vpn/gnunet-service-vpn.c:1952 +#: src/exit/gnunet-daemon-exit.c:2588 src/vpn/gnunet-service-vpn.c:1401 +#: src/vpn/gnunet-service-vpn.c:1969 msgid "# ICMPv4 packets dropped (impossible PT to v6)" msgstr "" -#: src/exit/gnunet-daemon-exit.c:2363 src/vpn/gnunet-service-vpn.c:1420 -#: src/vpn/gnunet-service-vpn.c:1432 src/vpn/gnunet-service-vpn.c:1842 +#: src/exit/gnunet-daemon-exit.c:2647 src/vpn/gnunet-service-vpn.c:1437 +#: src/vpn/gnunet-service-vpn.c:1449 src/vpn/gnunet-service-vpn.c:1859 msgid "# ICMPv6 packets dropped (impossible PT to v4)" msgstr "" -#: src/exit/gnunet-daemon-exit.c:2413 +#: src/exit/gnunet-daemon-exit.c:2697 #, fuzzy msgid "# UDP packets sent via TUN" msgstr "# byte skickade via UDP" -#: src/exit/gnunet-daemon-exit.c:2519 +#: src/exit/gnunet-daemon-exit.c:2814 #, fuzzy msgid "# UDP IP-exit requests received via mesh" msgstr "# byte mottogs via TCP" -#: src/exit/gnunet-daemon-exit.c:2619 +#: src/exit/gnunet-daemon-exit.c:2924 #, fuzzy msgid "# UDP service requests received via mesh" msgstr "# byte mottogs via TCP" -#: src/exit/gnunet-daemon-exit.c:2642 +#: src/exit/gnunet-daemon-exit.c:2947 #, fuzzy msgid "# UDP requests dropped (no such service)" msgstr "# byte mottogs via TCP" -#: src/exit/gnunet-daemon-exit.c:2882 +#: src/exit/gnunet-daemon-exit.c:2980 +msgid "# Inbound MESH tunnels created" +msgstr "" + +#: src/exit/gnunet-daemon-exit.c:3209 #, c-format msgid "No addresses found for hostname `%s' of service `%s'!\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:2896 src/exit/gnunet-daemon-exit.c:2908 +#: src/exit/gnunet-daemon-exit.c:3223 src/exit/gnunet-daemon-exit.c:3235 #, c-format msgid "Service `%s' configured for IPv4, but IPv4 is disabled!\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:2919 +#: src/exit/gnunet-daemon-exit.c:3246 #, c-format msgid "No IP addresses found for hostname `%s' of service `%s'!\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:3048 +#: src/exit/gnunet-daemon-exit.c:3364 msgid "" "This system does not support IPv4, will disable IPv4 functions despite them " "being enabled in the configuration\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:3056 +#: src/exit/gnunet-daemon-exit.c:3372 msgid "" "This system does not support IPv6, will disable IPv6 functions despite them " "being enabled in the configuration\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:3063 +#: src/exit/gnunet-daemon-exit.c:3379 msgid "" "Cannot enable IPv4 exit but disable IPv4 on TUN interface, will use " "ENABLE_IPv4=YES\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:3069 +#: src/exit/gnunet-daemon-exit.c:3385 msgid "" "Cannot enable IPv6 exit but disable IPv6 on TUN interface, will use " "ENABLE_IPv6=YES\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:3075 src/pt/gnunet-daemon-pt.c:884 +#: src/exit/gnunet-daemon-exit.c:3391 src/pt/gnunet-daemon-pt.c:884 msgid "No useful service enabled. Exiting.\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:3236 +#: src/exit/gnunet-daemon-exit.c:3620 msgid "Daemon to run to provide an IP exit node for the VPN" msgstr "" @@ -1826,112 +1792,112 @@ msgstr "# byte mottogs via TCP" msgid "# messages defragmented" msgstr "" -#: src/fragmentation/fragmentation.c:203 +#: src/fragmentation/fragmentation.c:208 #, fuzzy msgid "# fragments transmitted" msgstr "# byte skickade av typen %d" -#: src/fragmentation/fragmentation.c:206 +#: src/fragmentation/fragmentation.c:211 #, fuzzy msgid "# fragments retransmitted" msgstr "# byte skickade av typen %d" -#: src/fragmentation/fragmentation.c:232 +#: src/fragmentation/fragmentation.c:237 #, fuzzy msgid "# fragments wrap arounds" msgstr "# byte skickade av typen %d" -#: src/fragmentation/fragmentation.c:273 +#: src/fragmentation/fragmentation.c:281 msgid "# messages fragmented" msgstr "" -#: src/fragmentation/fragmentation.c:276 +#: src/fragmentation/fragmentation.c:284 msgid "# total size of fragmented messages" msgstr "" -#: src/fragmentation/fragmentation.c:363 +#: src/fragmentation/fragmentation.c:405 msgid "# fragment acknowledgements received" msgstr "" -#: src/fragmentation/fragmentation.c:369 +#: src/fragmentation/fragmentation.c:411 msgid "# bits removed from fragmentation ACKs" msgstr "" -#: src/fragmentation/fragmentation.c:393 +#: src/fragmentation/fragmentation.c:435 #, fuzzy msgid "# fragmentation transmissions completed" msgstr "# klartext PONG-meddelanden mottagna" -#: src/fs/fs_api.c:339 +#: src/fs/fs_api.c:465 #, fuzzy, c-format msgid "Could not open file `%s': %s" msgstr "Kunde inte slå upp \"%s\": %s\n" -#: src/fs/fs_api.c:348 +#: src/fs/fs_api.c:474 #, fuzzy, c-format msgid "Could not read file `%s': %s" msgstr "Kunde inte slå upp \"%s\": %s\n" -#: src/fs/fs_api.c:354 +#: src/fs/fs_api.c:480 #, c-format msgid "Short read reading from file `%s'!" msgstr "" -#: src/fs/fs_api.c:938 +#: src/fs/fs_api.c:1061 #, fuzzy, c-format msgid "Failed to resume publishing information `%s': %s\n" msgstr "Misslyckades att leverera \"%s\" meddelande.\n" -#: src/fs/fs_api.c:1395 +#: src/fs/fs_api.c:1520 #, c-format msgid "Failed to recover namespace `%s', cannot resume publishing operation.\n" msgstr "" -#: src/fs/fs_api.c:1437 +#: src/fs/fs_api.c:1562 #, c-format msgid "Failure while resuming publishing operation `%s': %s\n" msgstr "" -#: src/fs/fs_api.c:1453 +#: src/fs/fs_api.c:1578 #, fuzzy, c-format msgid "Failed to resume publishing operation `%s': %s\n" msgstr "Misslyckades att leverera \"%s\" meddelande.\n" -#: src/fs/fs_api.c:2106 +#: src/fs/fs_api.c:2229 #, c-format msgid "Failure while resuming unindexing operation `%s': %s\n" msgstr "" -#: src/fs/fs_api.c:2116 +#: src/fs/fs_api.c:2239 #, fuzzy, c-format msgid "Failed to resume unindexing operation `%s': %s\n" msgstr "Misslyckades att leverera \"%s\" meddelande.\n" -#: src/fs/fs_api.c:2241 src/fs/fs_api.c:2480 +#: src/fs/fs_api.c:2364 src/fs/fs_api.c:2604 #, fuzzy, c-format msgid "Failed to resume sub-download `%s': %s\n" msgstr "Misslyckades att leverera \"%s\" meddelande.\n" -#: src/fs/fs_api.c:2258 +#: src/fs/fs_api.c:2381 #, fuzzy, c-format msgid "Failed to resume sub-search `%s': %s\n" msgstr "Misslyckades att leverera \"%s\" meddelande.\n" -#: src/fs/fs_api.c:2270 src/fs/fs_api.c:2289 src/fs/fs_api.c:2773 +#: src/fs/fs_api.c:2394 src/fs/fs_api.c:2413 src/fs/fs_api.c:2897 #, c-format msgid "Failure while resuming search operation `%s': %s\n" msgstr "" -#: src/fs/fs_api.c:2471 +#: src/fs/fs_api.c:2595 #, c-format msgid "Failed to resume sub-download `%s': could not open file `%s'\n" msgstr "" -#: src/fs/fs_api.c:2717 +#: src/fs/fs_api.c:2841 msgid "Could not resume running search, will resume as paused search\n" msgstr "" -#: src/fs/fs_api.c:2811 +#: src/fs/fs_api.c:2935 #, c-format msgid "Failure while resuming download operation `%s': %s\n" msgstr "" @@ -1941,63 +1907,63 @@ msgstr "" msgid "MAGIC mismatch. This is not a GNUnet directory.\n" msgstr "Filformatsfel (inte en GNUnet-katalog?)\n" -#: src/fs/fs_download.c:311 +#: src/fs/fs_download.c:321 msgid "" "Recursive downloads of directories larger than 4 GB are not supported on 32-" "bit systems\n" msgstr "" -#: src/fs/fs_download.c:331 +#: src/fs/fs_download.c:341 msgid "Directory too large for system address space\n" msgstr "" -#: src/fs/fs_download.c:497 src/fs/fs_download.c:509 +#: src/fs/fs_download.c:507 src/fs/fs_download.c:519 #, fuzzy, c-format msgid "Failed to open file `%s' for writing" msgstr "Misslyckades att leverera \"%s\" meddelande.\n" -#: src/fs/fs_download.c:878 +#: src/fs/fs_download.c:888 #, fuzzy, c-format msgid "Failed to create directory for recursive download of `%s'\n" msgstr "Misslyckades att läsa kompislista från \"%s\"\n" -#: src/fs/fs_download.c:960 +#: src/fs/fs_download.c:970 #, c-format msgid "" "Internal error or bogus download URI (expected %u bytes at depth %u and " "offset %llu/%llu, got %u bytes)" msgstr "" -#: src/fs/fs_download.c:986 +#: src/fs/fs_download.c:996 msgid "internal error decrypting content" msgstr "" -#: src/fs/fs_download.c:1009 +#: src/fs/fs_download.c:1019 #, fuzzy, c-format msgid "Download failed: could not open file `%s': %s" msgstr "Kunde inte slå upp \"%s\": %s\n" -#: src/fs/fs_download.c:1019 +#: src/fs/fs_download.c:1029 #, fuzzy, c-format msgid "Failed to seek to offset %llu in file `%s': %s" msgstr "Misslyckades att leverera \"%s\" meddelande.\n" -#: src/fs/fs_download.c:1028 +#: src/fs/fs_download.c:1038 #, fuzzy, c-format msgid "Failed to write block of %u bytes at offset %llu in file `%s': %s" msgstr "Misslyckades att leverera \"%s\" meddelande.\n" -#: src/fs/fs_download.c:1125 +#: src/fs/fs_download.c:1136 #, fuzzy msgid "internal error decoding tree" msgstr "=\tFel vid läsning av katalog.\n" -#: src/fs/fs_download.c:1888 +#: src/fs/fs_download.c:1927 #, fuzzy msgid "Invalid URI" msgstr "Ogiltiga argument: " -#: src/fs/fs_getopt.c:191 +#: src/fs/fs_getopt.c:192 #, c-format msgid "" "Unknown metadata type in metadata option `%s'. Using metadata type " @@ -2039,37 +2005,36 @@ msgstr "Misslyckades att leverera \"%s\" meddelande.\n" msgid "Failed to connect to datastore service" msgstr "Misslyckades att ansluta till gnunetd.\n" -#: src/fs/fs_namespace.c:57 src/fs/fs_namespace.c:83 -#, fuzzy, c-format -msgid "Configuration fails to specify `%s' in section `%s'\n" -msgstr "Konfigurationsfil \"%s\" skapad.\n" - -#: src/fs/fs_namespace.c:112 +#: src/fs/fs_namespace.c:110 #, fuzzy, c-format msgid "Failed to open `%s' for writing: %s\n" msgstr "Misslyckades att leverera \"%s\" meddelande.\n" -#: src/fs/fs_namespace.c:134 src/fs/fs_namespace.c:222 +#: src/fs/fs_namespace.c:132 src/fs/fs_namespace.c:220 #, fuzzy, c-format msgid "Failed to write `%s': %s\n" msgstr "Fel vid %s:%d.\n" -#: src/fs/fs_namespace.c:256 +#: src/fs/fs_namespace.c:252 #, fuzzy, c-format msgid "Failed to create or read private key for namespace `%s'\n" msgstr "Misslyckades att läsa kompislista från \"%s\"\n" -#: src/fs/fs_namespace.c:371 +#: src/fs/fs_namespace.c:367 #, c-format msgid "Failed to read namespace private key file `%s', deleting it!\n" msgstr "" -#: src/fs/fs_namespace.c:588 src/fs/fs_publish_ksk.c:295 +#: src/fs/fs_namespace.c:558 +msgid "Identifiers or URI too long to create SBlock" +msgstr "" + +#: src/fs/fs_namespace.c:593 src/fs/fs_publish_ksk.c:295 #, fuzzy msgid "Internal error." msgstr "Okänt fel.\n" -#: src/fs/fs_namespace.c:631 +#: src/fs/fs_namespace.c:636 #, fuzzy msgid "Failed to connect to datastore." msgstr "Misslyckades att ansluta till gnunetd.\n" @@ -2081,61 +2046,61 @@ msgstr "" "\n" "Fel vid uppladdning av fil: %s\n" -#: src/fs/fs_publish.c:621 src/fs/fs_publish.c:638 src/fs/fs_publish.c:677 -#: src/fs/fs_publish.c:697 src/fs/fs_publish.c:722 src/fs/fs_publish.c:862 +#: src/fs/fs_publish.c:622 src/fs/fs_publish.c:639 src/fs/fs_publish.c:678 +#: src/fs/fs_publish.c:698 src/fs/fs_publish.c:723 src/fs/fs_publish.c:863 #, fuzzy, c-format msgid "Can not index file `%s': %s. Will try to insert instead.\n" msgstr "Indexering av fil \"%s\" misslyckades. Försöker att infoga fil...\n" -#: src/fs/fs_publish.c:623 +#: src/fs/fs_publish.c:624 msgid "timeout on index-start request to `fs' service" msgstr "" -#: src/fs/fs_publish.c:635 +#: src/fs/fs_publish.c:636 #, fuzzy msgid "unknown error" msgstr "Okänt fel" -#: src/fs/fs_publish.c:678 +#: src/fs/fs_publish.c:679 msgid "failed to compute hash" msgstr "" -#: src/fs/fs_publish.c:698 +#: src/fs/fs_publish.c:699 msgid "filename too long" msgstr "" -#: src/fs/fs_publish.c:723 +#: src/fs/fs_publish.c:724 #, fuzzy msgid "could not connect to `fs' service" msgstr "Kunde inte ansluta till gnunetd.\n" -#: src/fs/fs_publish.c:746 +#: src/fs/fs_publish.c:747 #, fuzzy, c-format msgid "Failed to get file identifiers for `%s'\n" msgstr "Misslyckades att läsa kompislista från \"%s\"\n" -#: src/fs/fs_publish.c:811 +#: src/fs/fs_publish.c:812 #, fuzzy, c-format msgid "Recursive upload failed at `%s': %s" msgstr "\"%s\" misslyckades vid %s:%d med fel: \"%s\".\n" -#: src/fs/fs_publish.c:817 +#: src/fs/fs_publish.c:818 #, fuzzy, c-format msgid "Recursive upload failed: %s" msgstr "" "\n" "Fel vid uppladdning av fil: %s\n" -#: src/fs/fs_publish.c:863 +#: src/fs/fs_publish.c:864 msgid "needs to be an actual file" msgstr "" -#: src/fs/fs_publish.c:1071 +#: src/fs/fs_publish.c:1090 #, c-format msgid "Insufficient space for publishing: %s" msgstr "" -#: src/fs/fs_publish.c:1142 +#: src/fs/fs_publish.c:1161 #, c-format msgid "Reserving space for %u entries and %llu bytes for publication\n" msgstr "" @@ -2145,16 +2110,11 @@ msgstr "" msgid "Could not connect to datastore." msgstr "Kunde inte ansluta till gnunetd.\n" -#: src/fs/fs_search.c:829 +#: src/fs/fs_search.c:892 #, c-format msgid "Got result with unknown block type `%d', ignoring" msgstr "" -#: src/fs/fs_test_lib.c:269 -#, fuzzy, c-format -msgid "Failed to start daemon: %s\n" -msgstr "Misslyckades att starta samling.\n" - #: src/fs/fs_unindex.c:58 msgid "Failed to find given position in file" msgstr "" @@ -2182,97 +2142,97 @@ msgstr "Ogiltigt svar till \"%s\" från \"%s\"\n" msgid "Failed to connect to FS service for unindexing." msgstr "Misslyckades att ansluta till gnunetd.\n" -#: src/fs/fs_unindex.c:344 +#: src/fs/fs_unindex.c:349 src/fs/fs_unindex.c:361 #, fuzzy msgid "Failed to get KSKs from directory scan." msgstr "Filformatsfel (inte en GNUnet-katalog?)\n" -#: src/fs/fs_unindex.c:356 +#: src/fs/fs_unindex.c:357 #, fuzzy, c-format msgid "Internal error scanning `%s'.\n" msgstr "=\tFel vid läsning av katalog.\n" -#: src/fs/fs_unindex.c:411 +#: src/fs/fs_unindex.c:416 #, fuzzy, c-format msgid "Failed to remove KBlock: %s\n" msgstr "Misslyckades att leverera \"%s\" meddelande.\n" -#: src/fs/fs_unindex.c:501 +#: src/fs/fs_unindex.c:506 #, fuzzy, c-format msgid "Failed to parse URI `%s' from KBlock!\n" msgstr "Fil \"%s\" har URI: %s\n" -#: src/fs/fs_unindex.c:553 src/fs/fs_unindex.c:618 +#: src/fs/fs_unindex.c:558 src/fs/fs_unindex.c:623 #, fuzzy msgid "Failed to connect to `datastore' service." msgstr "Misslyckades att initiera tjänsten \"%s\".\n" -#: src/fs/fs_unindex.c:631 +#: src/fs/fs_unindex.c:636 #, fuzzy msgid "Failed to open file for unindexing." msgstr "Misslyckades att ansluta till gnunetd.\n" -#: src/fs/fs_unindex.c:665 +#: src/fs/fs_unindex.c:670 #, fuzzy msgid "Failed to compute hash of file." msgstr "Misslyckades att ansluta till gnunetd.\n" -#: src/fs/fs_uri.c:220 -#, c-format +#: src/fs/fs_uri.c:221 +#, no-c-format msgid "`%' must be followed by HEX number" msgstr "" -#: src/fs/fs_uri.c:279 +#: src/fs/fs_uri.c:280 #, fuzzy msgid "Malformed KSK URI (must not begin or end with `+')" msgstr "Ogiltig URL \"%s\" (måste börja med \"%s\")\n" -#: src/fs/fs_uri.c:297 +#: src/fs/fs_uri.c:298 msgid "`++' not allowed in KSK URI" msgstr "" -#: src/fs/fs_uri.c:304 +#: src/fs/fs_uri.c:305 msgid "Quotes not balanced in KSK URI" msgstr "" -#: src/fs/fs_uri.c:372 src/fs/fs_uri.c:379 +#: src/fs/fs_uri.c:373 src/fs/fs_uri.c:380 msgid "Malformed SKS URI" msgstr "" -#: src/fs/fs_uri.c:423 src/fs/fs_uri.c:438 +#: src/fs/fs_uri.c:424 src/fs/fs_uri.c:439 msgid "Malformed CHK URI" msgstr "" -#: src/fs/fs_uri.c:568 src/fs/fs_uri.c:583 src/fs/fs_uri.c:593 -#: src/fs/fs_uri.c:621 +#: src/fs/fs_uri.c:569 src/fs/fs_uri.c:584 src/fs/fs_uri.c:594 +#: src/fs/fs_uri.c:622 msgid "SKS URI malformed" msgstr "" -#: src/fs/fs_uri.c:603 +#: src/fs/fs_uri.c:604 msgid "SKS URI malformed (could not decode public key)" msgstr "" -#: src/fs/fs_uri.c:609 +#: src/fs/fs_uri.c:610 msgid "SKS URI malformed (could not find signature)" msgstr "" -#: src/fs/fs_uri.c:615 +#: src/fs/fs_uri.c:616 msgid "SKS URI malformed (could not decode signature)" msgstr "" -#: src/fs/fs_uri.c:628 +#: src/fs/fs_uri.c:629 msgid "SKS URI malformed (could not parse expiration time)" msgstr "" -#: src/fs/fs_uri.c:640 +#: src/fs/fs_uri.c:641 msgid "SKS URI malformed (signature failed validation)" msgstr "" -#: src/fs/fs_uri.c:678 +#: src/fs/fs_uri.c:679 msgid "Unrecognized URI type" msgstr "" -#: src/fs/fs_uri.c:903 +#: src/fs/fs_uri.c:904 #, fuzzy msgid "Lacking key configuration settings.\n" msgstr "GNUnet-konfiguration" @@ -2290,6 +2250,70 @@ msgstr "Inga nyckelord angivna!\n" msgid "Number of double-quotes not balanced!\n" msgstr "" +#: src/fs/gnunet-auto-share.c:236 +#, fuzzy, c-format +msgid "Failed to load state: %s\n" +msgstr "Misslyckades att starta samling.\n" + +#: src/fs/gnunet-auto-share.c:289 src/fs/gnunet-auto-share.c:299 +#: src/fs/gnunet-auto-share.c:309 +#, fuzzy, c-format +msgid "Failed to save state to file %s\n" +msgstr "Misslyckades att läsa kompislista från \"%s\"\n" + +#: src/fs/gnunet-auto-share.c:401 +#, c-format +msgid "Publication of `%s' done\n" +msgstr "" + +#: src/fs/gnunet-auto-share.c:488 +#, fuzzy, c-format +msgid "Publishing `%s'\n" +msgstr "" +"\n" +"Fel vid uppladdning av fil: %s\n" + +#: src/fs/gnunet-auto-share.c:497 +#, fuzzy, c-format +msgid "Failed to run `%s'\n" +msgstr "Misslyckades att starta samling.\n" + +#: src/fs/gnunet-auto-share.c:686 +#, fuzzy, c-format +msgid "" +"You must specify one and only one directory name for automatic publication.\n" +msgstr "Du måste ange en och endast en fil att avindexera.\n" + +#: src/fs/gnunet-auto-share.c:737 src/fs/gnunet-pseudonym.c:279 +#: src/fs/gnunet-publish.c:683 +msgid "set the desired LEVEL of sender-anonymity" +msgstr "" + +#: src/fs/gnunet-auto-share.c:741 src/fs/gnunet-publish.c:687 +msgid "disable adding the creation time to the metadata of the uploaded file" +msgstr "" + +#: src/fs/gnunet-auto-share.c:744 src/fs/gnunet-publish.c:690 +msgid "do not use libextractor to add keywords or metadata" +msgstr "" + +#: src/fs/gnunet-auto-share.c:747 src/fs/gnunet-publish.c:714 +msgid "specify the priority of the content" +msgstr "ange prioritet för innehållet" + +#: src/fs/gnunet-auto-share.c:750 src/fs/gnunet-pseudonym.c:304 +#: src/fs/gnunet-publish.c:721 +msgid "set the desired replication LEVEL" +msgstr "" + +#: src/fs/gnunet-auto-share.c:770 +msgid "Automatically publish files from a directory on GNUnet" +msgstr "" + +#: src/fs/gnunet-daemon-fsprofiler.c:656 +msgid "Daemon to use file-sharing to measure its performance." +msgstr "" + #: src/fs/gnunet-directory.c:49 #, c-format msgid "\t\n" @@ -2320,97 +2344,97 @@ msgstr "Misslyckades att läsa kompislista från \"%s\"\n" msgid "`%s' is not a GNUnet directory\n" msgstr "Filformatsfel (inte en GNUnet-katalog?)\n" -#: src/fs/gnunet-directory.c:179 +#: src/fs/gnunet-directory.c:183 #, fuzzy msgid "Display contents of a GNUnet directory" msgstr "Filformatsfel (inte en GNUnet-katalog?)\n" -#: src/fs/gnunet-download.c:101 +#: src/fs/gnunet-download.c:137 #, fuzzy, c-format msgid "Starting download `%s'.\n" msgstr "Startade samling \"%s\".\n" -#: src/fs/gnunet-download.c:110 +#: src/fs/gnunet-download.c:147 #, fuzzy msgid "" msgstr "Okänt fel" -#: src/fs/gnunet-download.c:119 +#: src/fs/gnunet-download.c:157 #, c-format msgid "" "Downloading `%s' at %llu/%llu (%s remaining, %s/s). Block took %s to " "download\n" msgstr "" -#: src/fs/gnunet-download.c:129 +#: src/fs/gnunet-download.c:179 #, fuzzy, c-format msgid "Error downloading: %s.\n" msgstr "Fel vid nedladdning: %s\n" -#: src/fs/gnunet-download.c:137 +#: src/fs/gnunet-download.c:194 #, fuzzy, c-format msgid "Downloading `%s' done (%s/s).\n" msgstr "Uppladdning vägrades!" -#: src/fs/gnunet-download.c:152 src/fs/gnunet-publish.c:190 -#: src/fs/gnunet-search.c:190 src/fs/gnunet-unindex.c:109 +#: src/fs/gnunet-download.c:209 src/fs/gnunet-publish.c:195 +#: src/fs/gnunet-search.c:193 src/fs/gnunet-unindex.c:108 #, c-format msgid "Unexpected status: %d\n" msgstr "" -#: src/fs/gnunet-download.c:177 +#: src/fs/gnunet-download.c:234 #, fuzzy msgid "You need to specify a URI argument.\n" msgstr "Du måste ange en och endast en fil att avindexera.\n" -#: src/fs/gnunet-download.c:183 src/fs/gnunet-publish.c:624 +#: src/fs/gnunet-download.c:240 src/fs/gnunet-publish.c:629 #, fuzzy, c-format msgid "Failed to parse URI: %s\n" msgstr "Fil \"%s\" har URI: %s\n" -#: src/fs/gnunet-download.c:190 +#: src/fs/gnunet-download.c:247 msgid "Only CHK or LOC URIs supported.\n" msgstr "" -#: src/fs/gnunet-download.c:197 +#: src/fs/gnunet-download.c:254 msgid "Target filename must be specified.\n" msgstr "" -#: src/fs/gnunet-download.c:211 src/fs/gnunet-publish.c:602 -#: src/fs/gnunet-search.c:241 src/fs/gnunet-unindex.c:141 +#: src/fs/gnunet-download.c:268 src/fs/gnunet-publish.c:607 +#: src/fs/gnunet-search.c:243 src/fs/gnunet-unindex.c:140 #, fuzzy, c-format msgid "Could not initialize `%s' subsystem.\n" msgstr "Misslyckades att initiera tjänsten \"%s\".\n" -#: src/fs/gnunet-download.c:248 src/fs/gnunet-search.c:285 +#: src/fs/gnunet-download.c:305 src/fs/gnunet-search.c:282 msgid "set the desired LEVEL of receiver-anonymity" msgstr "" -#: src/fs/gnunet-download.c:251 +#: src/fs/gnunet-download.c:308 msgid "delete incomplete downloads (when aborted with CTRL-C)" msgstr "" -#: src/fs/gnunet-download.c:254 src/fs/gnunet-search.c:288 +#: src/fs/gnunet-download.c:311 src/fs/gnunet-search.c:285 msgid "only search the local peer (no P2P network search)" msgstr "" -#: src/fs/gnunet-download.c:257 +#: src/fs/gnunet-download.c:314 msgid "write the file to FILENAME" msgstr "skriv filen till FILNAMN" -#: src/fs/gnunet-download.c:261 +#: src/fs/gnunet-download.c:318 msgid "set the maximum number of parallel downloads that is allowed" msgstr "" -#: src/fs/gnunet-download.c:265 +#: src/fs/gnunet-download.c:322 msgid "set the maximum number of parallel requests for blocks that is allowed" msgstr "" -#: src/fs/gnunet-download.c:268 +#: src/fs/gnunet-download.c:325 msgid "download a GNUnet directory recursively" msgstr "hämta en GNUnet-katalog rekursivt" -#: src/fs/gnunet-download.c:278 +#: src/fs/gnunet-download.c:339 msgid "" "Download files from GNUnet using a GNUnet CHK or LOC URI (gnunet://fs/" "chk/...)" @@ -2420,12 +2444,28 @@ msgstr "" msgid "print a list of all indexed files" msgstr "" -#: src/fs/gnunet-fs.c:124 +#: src/fs/gnunet-fs.c:127 #, fuzzy msgid "Special file-sharing operations" msgstr "Visa alla alternativ" -#: src/fs/gnunet-pseudonym.c:160 src/statistics/gnunet-statistics.c:167 +#: src/fs/gnunet-fs-profiler.c:182 +msgid "run the experiment with COUNT peers" +msgstr "" + +#: src/fs/gnunet-fs-profiler.c:185 +msgid "specifies name of a file with the HOSTS the testbed should use" +msgstr "" + +#: src/fs/gnunet-fs-profiler.c:188 +msgid "automatically terminate experiment after DELAY" +msgstr "" + +#: src/fs/gnunet-fs-profiler.c:197 +msgid "run a testbed to measure file-sharing performance" +msgstr "" + +#: src/fs/gnunet-pseudonym.c:160 src/statistics/gnunet-statistics.c:283 #, fuzzy, c-format msgid "Invalid argument `%s'\n" msgstr "Ogiltigt argument: \"%s\"\n" @@ -2436,10 +2476,6 @@ msgstr "Ogiltigt argument: \"%s\"\n" msgid "Option `%s' ignored\n" msgstr "%s: flagga \"%s\" är tvetydig\n" -#: src/fs/gnunet-pseudonym.c:279 src/fs/gnunet-publish.c:678 -msgid "set the desired LEVEL of sender-anonymity" -msgstr "" - #: src/fs/gnunet-pseudonym.c:282 msgid "create or advertise namespace NAME" msgstr "" @@ -2454,7 +2490,7 @@ msgid "" "multiple times)" msgstr "" -#: src/fs/gnunet-pseudonym.c:292 src/fs/gnunet-publish.c:697 +#: src/fs/gnunet-pseudonym.c:292 src/fs/gnunet-publish.c:702 msgid "set the meta-data for the given TYPE to the given VALUE" msgstr "" @@ -2470,10 +2506,6 @@ msgstr "" msgid "do not print names of remote namespaces" msgstr "" -#: src/fs/gnunet-pseudonym.c:304 src/fs/gnunet-publish.c:716 -msgid "set the desired replication LEVEL" -msgstr "" - #: src/fs/gnunet-pseudonym.c:307 #, fuzzy msgid "specify ID of the root of the namespace" @@ -2483,390 +2515,366 @@ msgstr "ange prioritet för innehållet" msgid "change rating of namespace ID by VALUE" msgstr "" -#: src/fs/gnunet-pseudonym.c:318 +#: src/fs/gnunet-pseudonym.c:322 msgid "Manage GNUnet pseudonyms." msgstr "" -#: src/fs/gnunet-publish.c:147 +#: src/fs/gnunet-publish.c:152 #, c-format msgid "Publishing `%s' at %llu/%llu (%s remaining)\n" msgstr "" -#: src/fs/gnunet-publish.c:155 +#: src/fs/gnunet-publish.c:159 #, fuzzy, c-format msgid "Error publishing: %s.\n" msgstr "Fel vid nedladdning: %s\n" -#: src/fs/gnunet-publish.c:165 +#: src/fs/gnunet-publish.c:169 #, c-format msgid "Publishing `%s' done.\n" msgstr "" -#: src/fs/gnunet-publish.c:169 +#: src/fs/gnunet-publish.c:173 #, fuzzy, c-format msgid "URI is `%s'.\n" msgstr "Jag är ändpunkt \"%s\".\n" -#: src/fs/gnunet-publish.c:187 +#: src/fs/gnunet-publish.c:192 #, fuzzy msgid "Cleanup after abort complete.\n" msgstr "\"%s\" uppstart klar.\n" -#: src/fs/gnunet-publish.c:305 +#: src/fs/gnunet-publish.c:310 #, fuzzy, c-format msgid "Meta data for file `%s' (%s)\n" msgstr "Uppdaterar data för modul \"%s\"\n" -#: src/fs/gnunet-publish.c:307 +#: src/fs/gnunet-publish.c:312 #, fuzzy, c-format msgid "Keywords for file `%s' (%s)\n" msgstr "Nyckelord för fil \"%s\":\n" -#: src/fs/gnunet-publish.c:358 +#: src/fs/gnunet-publish.c:363 src/fs/gnunet-publish.c:617 #, fuzzy, c-format -msgid "Failed to create namespace `%s'\n" +msgid "Failed to create namespace `%s' (illegal filename?)\n" msgstr "Kunde inte skapa namnrymd \"%s\" (existerar?).\n" -#: src/fs/gnunet-publish.c:433 +#: src/fs/gnunet-publish.c:438 #, fuzzy msgid "Could not publish\n" msgstr "Kunde inte köra \"%s\": %s\n" -#: src/fs/gnunet-publish.c:460 +#: src/fs/gnunet-publish.c:465 #, fuzzy msgid "Could not start publishing.\n" msgstr "Kunde inte slå upp \"%s\": %s\n" -#: src/fs/gnunet-publish.c:491 +#: src/fs/gnunet-publish.c:496 #, fuzzy, c-format msgid "Scanning directory `%s'.\n" msgstr "Misslyckades att läsa kompislista från \"%s\"\n" -#: src/fs/gnunet-publish.c:493 +#: src/fs/gnunet-publish.c:498 #, fuzzy, c-format msgid "Scanning file `%s'.\n" msgstr "Startade samling \"%s\".\n" -#: src/fs/gnunet-publish.c:498 +#: src/fs/gnunet-publish.c:503 #, c-format msgid "There was trouble processing file `%s', skipping it.\n" msgstr "" -#: src/fs/gnunet-publish.c:503 +#: src/fs/gnunet-publish.c:508 #, fuzzy msgid "Preprocessing complete.\n" msgstr "Nedstängning klar.\n" -#: src/fs/gnunet-publish.c:507 +#: src/fs/gnunet-publish.c:512 #, fuzzy, c-format msgid "Extracting meta data from file `%s' complete.\n" msgstr "Uppdaterar data för modul \"%s\"\n" -#: src/fs/gnunet-publish.c:511 +#: src/fs/gnunet-publish.c:516 msgid "Meta data extraction has finished.\n" msgstr "" -#: src/fs/gnunet-publish.c:518 +#: src/fs/gnunet-publish.c:523 #, fuzzy msgid "Internal error scanning directory.\n" msgstr "=\tFel vid läsning av katalog.\n" -#: src/fs/gnunet-publish.c:552 +#: src/fs/gnunet-publish.c:557 #, c-format msgid "Cannot extract metadata from a URI!\n" msgstr "" -#: src/fs/gnunet-publish.c:559 +#: src/fs/gnunet-publish.c:564 #, fuzzy, c-format msgid "You must specify one and only one filename for insertion.\n" msgstr "Du måste ange en och endast en fil att avindexera.\n" -#: src/fs/gnunet-publish.c:565 +#: src/fs/gnunet-publish.c:570 #, fuzzy, c-format msgid "You must NOT specify an URI and a filename.\n" msgstr "Du måste ange en och endast en fil att avindexera.\n" -#: src/fs/gnunet-publish.c:573 src/vpn/gnunet-vpn.c:214 +#: src/fs/gnunet-publish.c:578 src/vpn/gnunet-vpn.c:213 #, fuzzy, c-format msgid "Option `%s' is required when using option `%s'.\n" msgstr "Kommando \"%s\" kräver ett argument (\"%s\").\n" -#: src/fs/gnunet-publish.c:583 src/fs/gnunet-publish.c:590 -#: src/transport/gnunet-transport.c:560 +#: src/fs/gnunet-publish.c:588 src/fs/gnunet-publish.c:595 +#: src/transport/gnunet-transport.c:843 src/transport/gnunet-transport.c:873 #, c-format msgid "Option `%s' makes no sense without option `%s'.\n" msgstr "" -#: src/fs/gnunet-publish.c:612 -#, fuzzy, c-format -msgid "Could not create namespace `%s'\n" -msgstr "Kunde inte skapa namnrymd \"%s\" (existerar?).\n" - -#: src/fs/gnunet-publish.c:645 +#: src/fs/gnunet-publish.c:650 #, fuzzy, c-format msgid "Failed to access `%s': %s\n" msgstr "Misslyckades att leverera \"%s\" meddelande.\n" -#: src/fs/gnunet-publish.c:657 +#: src/fs/gnunet-publish.c:662 msgid "" "Failed to start meta directory scanner. Is gnunet-helper-publish-fs " "installed?\n" msgstr "" -#: src/fs/gnunet-publish.c:682 -msgid "disable adding the creation time to the metadata of the uploaded file" -msgstr "" - -#: src/fs/gnunet-publish.c:685 -msgid "do not use libextractor to add keywords or metadata" -msgstr "" - -#: src/fs/gnunet-publish.c:689 +#: src/fs/gnunet-publish.c:694 msgid "" "print list of extracted keywords that would be used, but do not perform " "upload" msgstr "" -#: src/fs/gnunet-publish.c:693 +#: src/fs/gnunet-publish.c:698 msgid "" "add an additional keyword for the top-level file or directory (this option " "can be specified multiple times)" msgstr "" -#: src/fs/gnunet-publish.c:700 +#: src/fs/gnunet-publish.c:705 msgid "" "do not index, perform full insertion (stores entire file in encrypted form " "in GNUnet database)" msgstr "" -#: src/fs/gnunet-publish.c:705 +#: src/fs/gnunet-publish.c:710 msgid "" "specify ID of an updated version to be published in the future (for " "namespace insertions only)" msgstr "" -#: src/fs/gnunet-publish.c:709 -msgid "specify the priority of the content" -msgstr "ange prioritet för innehållet" - -#: src/fs/gnunet-publish.c:713 +#: src/fs/gnunet-publish.c:718 msgid "publish the files under the pseudonym NAME (place file into namespace)" msgstr "" -#: src/fs/gnunet-publish.c:719 +#: src/fs/gnunet-publish.c:724 msgid "" "only simulate the process but do not do any actual publishing (useful to " "compute URIs)" msgstr "" -#: src/fs/gnunet-publish.c:723 +#: src/fs/gnunet-publish.c:728 msgid "" "set the ID of this version of the publication (for namespace insertions only)" msgstr "" -#: src/fs/gnunet-publish.c:727 +#: src/fs/gnunet-publish.c:732 msgid "" "URI to be published (can be used instead of passing a file to add keywords " "to the file with the respective URI)" msgstr "" -#: src/fs/gnunet-publish.c:742 +#: src/fs/gnunet-publish.c:748 msgid "Publish a file or directory on GNUnet" msgstr "" -#: src/fs/gnunet-search.c:111 +#: src/fs/gnunet-search.c:114 #, c-format msgid "Failed to write directory with search results to `%s'\n" msgstr "" -#: src/fs/gnunet-search.c:181 +#: src/fs/gnunet-search.c:184 #, fuzzy, c-format msgid "Error searching: %s.\n" msgstr "Fel vid lämning av DHT.\n" -#: src/fs/gnunet-search.c:231 +#: src/fs/gnunet-search.c:233 #, fuzzy msgid "Could not create keyword URI from arguments.\n" msgstr "Kunde inte skapa namnrymd \"%s\" (existerar?).\n" -#: src/fs/gnunet-search.c:255 +#: src/fs/gnunet-search.c:257 #, fuzzy msgid "Could not start searching.\n" msgstr "Kunde inte skapa namnrymd \"%s\" (existerar?).\n" -#: src/fs/gnunet-search.c:291 +#: src/fs/gnunet-search.c:288 msgid "write search results to file starting with PREFIX" msgstr "" -#: src/fs/gnunet-search.c:294 -msgid "automatically terminate search after VALUE ms" +#: src/fs/gnunet-search.c:291 +msgid "automatically terminate search after DELAY" msgstr "" -#: src/fs/gnunet-search.c:301 +#: src/fs/gnunet-search.c:298 msgid "automatically terminate search after VALUE results are found" msgstr "" -#: src/fs/gnunet-search.c:308 +#: src/fs/gnunet-search.c:309 msgid "Search GNUnet for files that were published on GNUnet" msgstr "" -#: src/fs/gnunet-service-fs.c:240 +#: src/fs/gnunet-service-fs.c:248 msgid "# running average P2P latency (ms)" msgstr "" -#: src/fs/gnunet-service-fs.c:300 src/fs/gnunet-service-fs.c:489 +#: src/fs/gnunet-service-fs.c:309 src/fs/gnunet-service-fs.c:523 msgid "# Loopback routes suppressed" msgstr "" -#: src/fs/gnunet-service-fs.c:581 src/hostlist/gnunet-daemon-hostlist.c:297 -#: src/topology/gnunet-daemon-topology.c:1330 -#: src/topology/gnunet-daemon-topology.c:1337 +#: src/fs/gnunet-service-fs.c:628 src/hostlist/gnunet-daemon-hostlist.c:297 +#: src/topology/gnunet-daemon-topology.c:1322 +#: src/topology/gnunet-daemon-topology.c:1329 #, fuzzy, c-format msgid "Failed to connect to `%s' service.\n" msgstr "Misslyckades att initiera tjänsten \"%s\".\n" -#: src/fs/gnunet-service-fs_cp.c:696 +#: src/fs/gnunet-service-fs_cp.c:711 #, fuzzy msgid "# migration stop messages received" msgstr "# krypterade PONG-meddelanden mottagna" -#: src/fs/gnunet-service-fs_cp.c:700 +#: src/fs/gnunet-service-fs_cp.c:715 #, c-format -msgid "Migration of content to peer `%s' blocked for %llu ms\n" +msgid "Migration of content to peer `%s' blocked for %s\n" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:735 +#: src/fs/gnunet-service-fs_cp.c:751 #, fuzzy msgid "# replies transmitted to other peers" msgstr "# byte skickade av typen %d" -#: src/fs/gnunet-service-fs_cp.c:741 +#: src/fs/gnunet-service-fs_cp.c:757 msgid "# replies dropped" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:766 src/fs/gnunet-service-fs_cp.c:1324 +#: src/fs/gnunet-service-fs_cp.c:782 src/fs/gnunet-service-fs_cp.c:1345 msgid "# P2P searches active" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:858 +#: src/fs/gnunet-service-fs_cp.c:875 msgid "# artificial delays introduced (ms)" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:911 +#: src/fs/gnunet-service-fs_cp.c:928 #, fuzzy msgid "# replies dropped due to type mismatch" msgstr "# byte mottagna av typen %d" -#: src/fs/gnunet-service-fs_cp.c:919 +#: src/fs/gnunet-service-fs_cp.c:936 #, fuzzy msgid "# replies received for other peers" msgstr "# byte mottagna av typen %d" -#: src/fs/gnunet-service-fs_cp.c:933 +#: src/fs/gnunet-service-fs_cp.c:950 msgid "# replies dropped due to insufficient cover traffic" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:971 +#: src/fs/gnunet-service-fs_cp.c:988 msgid "# P2P searches destroyed due to ultimate reply" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:1038 +#: src/fs/gnunet-service-fs_cp.c:1056 msgid "# requests done for free (low load)" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:1062 +#: src/fs/gnunet-service-fs_cp.c:1081 msgid "# request dropped, priority insufficient" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:1072 +#: src/fs/gnunet-service-fs_cp.c:1091 msgid "# requests done for a price (normal load)" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:1151 +#: src/fs/gnunet-service-fs_cp.c:1170 msgid "# GET requests received (from other peers)" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:1185 +#: src/fs/gnunet-service-fs_cp.c:1204 msgid "# requests dropped due to initiator not being connected" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:1207 +#: src/fs/gnunet-service-fs_cp.c:1227 msgid "# requests dropped due to missing reverse route" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:1267 +#: src/fs/gnunet-service-fs_cp.c:1288 msgid "# requests dropped due TTL underflow" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:1293 +#: src/fs/gnunet-service-fs_cp.c:1314 msgid "# requests dropped due to higher-TTL request" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:1322 +#: src/fs/gnunet-service-fs_cp.c:1343 #, fuzzy msgid "# P2P query messages received and processed" msgstr "# krypterade PONG-meddelanden mottagna" -#: src/fs/gnunet-service-fs_cp.c:1687 +#: src/fs/gnunet-service-fs_cp.c:1713 #, fuzzy msgid "# migration stop messages sent" msgstr "# krypterade PONG-meddelanden mottagna" -#: src/fs/gnunet-service-fs_indexing.c:113 -#: src/fs/gnunet-service-fs_indexing.c:163 -#, fuzzy, c-format -msgid "Configuration option `%s' in section `%s' missing.\n" -msgstr "Konfigurationsfil \"%s\" skapad.\n" - -#: src/fs/gnunet-service-fs_indexing.c:121 -#: src/fs/gnunet-service-fs_indexing.c:177 +#: src/fs/gnunet-service-fs_indexing.c:130 +#: src/fs/gnunet-service-fs_indexing.c:181 #, fuzzy, c-format msgid "Could not open `%s'.\n" msgstr "Kunde inte slå upp \"%s\": %s\n" -#: src/fs/gnunet-service-fs_indexing.c:137 +#: src/fs/gnunet-service-fs_indexing.c:142 #, fuzzy, c-format msgid "Error writing `%s'.\n" msgstr "Fel vid skapandet av användare" -#: src/fs/gnunet-service-fs_indexing.c:228 +#: src/fs/gnunet-service-fs_indexing.c:237 #, c-format msgid "" "Index request received for file `%s' is already indexed as `%s'. Permitting " "anyway.\n" msgstr "" -#: src/fs/gnunet-service-fs_indexing.c:266 +#: src/fs/gnunet-service-fs_indexing.c:275 #, c-format msgid "Hash mismatch trying to index file `%s' which has hash `%s'\n" msgstr "" -#: src/fs/gnunet-service-fs_indexing.c:481 +#: src/fs/gnunet-service-fs_indexing.c:477 #, fuzzy, c-format msgid "Failed to delete bogus block: %s\n" msgstr "Misslyckades att leverera \"%s\" meddelande.\n" -#: src/fs/gnunet-service-fs_indexing.c:539 +#: src/fs/gnunet-service-fs_indexing.c:542 msgid "# index blocks removed: original file inaccessible" msgstr "" -#: src/fs/gnunet-service-fs_indexing.c:554 +#: src/fs/gnunet-service-fs_indexing.c:557 #, fuzzy, c-format msgid "Could not access indexed file `%s' (%s) at offset %llu: %s\n" msgstr "Kunde inte slå upp \"%s\": %s\n" -#: src/fs/gnunet-service-fs_indexing.c:556 +#: src/fs/gnunet-service-fs_indexing.c:559 #, fuzzy msgid "not indexed" msgstr "Avindexering misslyckades." -#: src/fs/gnunet-service-fs_indexing.c:571 +#: src/fs/gnunet-service-fs_indexing.c:574 #, fuzzy, c-format msgid "Indexed file `%s' changed at offset %llu\n" msgstr "Indexering av data misslyckades vid position %i.\n" -#: src/fs/gnunet-service-fs_lc.c:202 src/fs/gnunet-service-fs_lc.c:362 -#: src/fs/gnunet-service-fs_lc.c:488 +#: src/fs/gnunet-service-fs_lc.c:202 src/fs/gnunet-service-fs_lc.c:369 #, fuzzy msgid "# client searches active" msgstr "# klartext PONG-meddelanden mottagna" @@ -2876,326 +2884,481 @@ msgstr "# klartext PONG-meddelanden mottagna" msgid "# replies received for local clients" msgstr "Meddelande mottaget från klient är ogiltig.\n" -#: src/fs/gnunet-service-fs_lc.c:321 +#: src/fs/gnunet-service-fs_lc.c:328 #, fuzzy msgid "# client searches received" msgstr "# klartext PONG-meddelanden mottagna" -#: src/fs/gnunet-service-fs_lc.c:356 +#: src/fs/gnunet-service-fs_lc.c:363 msgid "# client searches updated (merged content seen list)" msgstr "" -#: src/fs/gnunet-service-fs_pe.c:265 +#: src/fs/gnunet-service-fs_pe.c:269 msgid "# average retransmission delay (ms)" msgstr "" -#: src/fs/gnunet-service-fs_pe.c:391 +#: src/fs/gnunet-service-fs_pe.c:400 #, fuzzy msgid "# transmission failed (core has no bandwidth)" msgstr "Ingen transport av typ %d är känd.\n" -#: src/fs/gnunet-service-fs_pe.c:420 +#: src/fs/gnunet-service-fs_pe.c:433 #, fuzzy msgid "# query messages sent to other peers" msgstr "# byte skickade av typen %d" -#: src/fs/gnunet-service-fs_pe.c:469 +#: src/fs/gnunet-service-fs_pe.c:482 msgid "# delay heap timeout" msgstr "" -#: src/fs/gnunet-service-fs_pe.c:476 +#: src/fs/gnunet-service-fs_pe.c:490 msgid "# query plans executed" msgstr "" -#: src/fs/gnunet-service-fs_pe.c:538 +#: src/fs/gnunet-service-fs_pe.c:550 #, fuzzy msgid "# requests merged" msgstr "# byte mottogs via TCP" -#: src/fs/gnunet-service-fs_pe.c:544 +#: src/fs/gnunet-service-fs_pe.c:558 #, fuzzy msgid "# requests refreshed" msgstr "# byte mottogs via TCP" -#: src/fs/gnunet-service-fs_pe.c:597 src/fs/gnunet-service-fs_pe.c:681 -#: src/fs/gnunet-service-fs_pe.c:748 +#: src/fs/gnunet-service-fs_pe.c:612 src/fs/gnunet-service-fs_pe.c:696 +#: src/fs/gnunet-service-fs_pe.c:767 msgid "# query plan entries" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:285 +#: src/fs/gnunet-service-fs_pr.c:312 #, fuzzy msgid "# Pending requests created" msgstr "# byte mottogs via TCP" -#: src/fs/gnunet-service-fs_pr.c:367 src/fs/gnunet-service-fs_pr.c:616 +#: src/fs/gnunet-service-fs_pr.c:404 src/fs/gnunet-service-fs_pr.c:667 msgid "# Pending requests active" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:779 +#: src/fs/gnunet-service-fs_pr.c:835 #, fuzzy msgid "# replies received and matched" msgstr "# byte mottagna av typen %d" -#: src/fs/gnunet-service-fs_pr.c:808 +#: src/fs/gnunet-service-fs_pr.c:868 msgid "# duplicate replies discarded (bloomfilter)" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:822 +#: src/fs/gnunet-service-fs_pr.c:877 +msgid "# irrelevant replies discarded" +msgstr "" + +#: src/fs/gnunet-service-fs_pr.c:891 #, c-format msgid "Unsupported block type %u\n" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:835 +#: src/fs/gnunet-service-fs_pr.c:904 msgid "# results found locally" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:953 +#: src/fs/gnunet-service-fs_pr.c:1025 msgid "# Datastore `PUT' failures" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:980 +#: src/fs/gnunet-service-fs_pr.c:1052 #, fuzzy msgid "# storage requests dropped due to high load" msgstr "Nätverksannonsering avstängd i konfigurationen!\n" -#: src/fs/gnunet-service-fs_pr.c:1015 +#: src/fs/gnunet-service-fs_pr.c:1087 #, fuzzy msgid "# Replies received from DHT" msgstr "# byte mottagna via HTTP" -#: src/fs/gnunet-service-fs_pr.c:1106 +#: src/fs/gnunet-service-fs_pr.c:1221 +#, fuzzy +msgid "# Replies received from STREAM" +msgstr "# byte mottagna via HTTP" + +#: src/fs/gnunet-service-fs_pr.c:1273 #, c-format -msgid "Datastore lookup already took %llu ms!\n" +msgid "Datastore lookup already took %s!\n" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1127 +#: src/fs/gnunet-service-fs_pr.c:1293 #, c-format -msgid "On-demand lookup already took %llu ms!\n" +msgid "On-demand lookup already took %s!\n" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1174 +#: src/fs/gnunet-service-fs_pr.c:1340 msgid "# Datastore lookups concluded (no results)" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1188 +#: src/fs/gnunet-service-fs_pr.c:1355 msgid "# Datastore lookups concluded (seen all)" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1197 +#: src/fs/gnunet-service-fs_pr.c:1364 msgid "# Datastore lookups aborted (more than MAX_RESULTS)" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1211 +#: src/fs/gnunet-service-fs_pr.c:1379 msgid "# requested DBLOCK or IBLOCK not found" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1224 +#: src/fs/gnunet-service-fs_pr.c:1393 msgid "# on-demand blocks matched requests" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1237 +#: src/fs/gnunet-service-fs_pr.c:1406 msgid "# on-demand lookups performed successfully" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1242 +#: src/fs/gnunet-service-fs_pr.c:1411 msgid "# on-demand lookups failed" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1269 src/fs/gnunet-service-fs_pr.c:1309 -#: src/fs/gnunet-service-fs_pr.c:1447 +#: src/fs/gnunet-service-fs_pr.c:1438 src/fs/gnunet-service-fs_pr.c:1478 +#: src/fs/gnunet-service-fs_pr.c:1619 msgid "# Datastore lookups concluded (error queueing)" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1327 +#: src/fs/gnunet-service-fs_pr.c:1496 msgid "# Datastore lookups concluded (found last result)" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1338 +#: src/fs/gnunet-service-fs_pr.c:1507 msgid "# Datastore lookups concluded (load too high)" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1424 +#: src/fs/gnunet-service-fs_pr.c:1595 msgid "# Datastore lookups initiated" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1508 +#: src/fs/gnunet-service-fs_pr.c:1680 #, fuzzy msgid "# GAP PUT messages received" msgstr "# krypterade PONG-meddelanden mottagna" -#: src/fs/gnunet-service-fs_pr.c:1601 src/fs/gnunet-service-fs_pr.c:1610 -#, fuzzy, c-format -msgid "Configuration fails to specify `%s', assuming default value." -msgstr "Konfigurationsfil \"%s\" skapad.\n" - #: src/fs/gnunet-service-fs_push.c:629 -#, c-format -msgid "" -"Invalid value specified for option `%s' in section `%s', content pushing " -"disabled\n" +msgid "time required, content pushing disabled" +msgstr "" + +#: src/fs/gnunet-service-fs_stream.c:777 +#, fuzzy +msgid "# replies received via stream" +msgstr "# byte mottagna av typen %d" + +#: src/fs/gnunet-service-fs_stream.c:791 +#, fuzzy +msgid "# replies received via stream dropped" +msgstr "# byte mottagna av typen %d" + +#: src/fs/gnunet-service-fs_stream.c:930 +#: src/fs/gnunet-service-fs_stream.c:1384 +#, fuzzy +msgid "# stream connections active" +msgstr "Nätverksanslutning" + +#: src/fs/gnunet-service-fs_stream.c:1166 +msgid "# Blocks transferred via stream" msgstr "" +#: src/fs/gnunet-service-fs_stream.c:1326 +#, fuzzy +msgid "# queries received via stream" +msgstr "# byte mottogs via TCP" + +#: src/fs/gnunet-service-fs_stream.c:1376 +#, fuzzy +msgid "# stream client connections rejected" +msgstr "Nätverksanslutning" + #: src/fs/gnunet-unindex.c:89 #, c-format msgid "Unindexing at %llu/%llu (%s remaining)\n" msgstr "" -#: src/fs/gnunet-unindex.c:96 +#: src/fs/gnunet-unindex.c:95 #, fuzzy, c-format msgid "Error unindexing: %s.\n" msgstr "" "\n" "Fel vid avindexering av fil: %s\n" -#: src/fs/gnunet-unindex.c:101 +#: src/fs/gnunet-unindex.c:100 #, fuzzy msgid "Unindexing done.\n" msgstr "Avindexera filer." -#: src/fs/gnunet-unindex.c:131 +#: src/fs/gnunet-unindex.c:130 #, fuzzy, c-format msgid "You must specify one and only one filename for unindexing.\n" msgstr "Du måste ange en och endast en fil att avindexera.\n" -#: src/fs/gnunet-unindex.c:148 +#: src/fs/gnunet-unindex.c:147 #, fuzzy msgid "Could not start unindex operation.\n" msgstr "Kunde inte komma åt namnrymdsinformation.\n" -#: src/fs/gnunet-unindex.c:176 +#: src/fs/gnunet-unindex.c:179 msgid "Unindex a file that was previously indexed with gnunet-publish." msgstr "" -#: src/fs/plugin_block_fs.c:131 -msgid "Reply mismatched in terms of namespace. Discarded.\n" -msgstr "" +#: src/gns/gns_api.c:598 +#, fuzzy +msgid "Failed to serialize lookup reply from GNS service!\n" +msgstr "Misslyckades att ta emot svar till \"%s\" meddelande från gnunetd\n" -#: src/gns/gnunet-gns.c:191 +#: src/gns/gnunet-dns2gns.c:192 #, fuzzy +msgid "Failed to pack DNS response into UDP packet!\n" +msgstr "Misslyckades att skicka HTTP-begäran till värd \"%s\": %s\n" + +#: src/gns/gnunet-dns2gns.c:367 +#, fuzzy, c-format +msgid "Cannot parse DNS request from %s\n" +msgstr "Misslyckades att skicka HTTP-begäran till värd \"%s\": %s\n" + +#: src/gns/gnunet-dns2gns.c:383 +#, fuzzy, c-format +msgid "Received malformed DNS request from %s\n" +msgstr "Mottog ogiltig \"%s\" begäran (storlek %d)\n" + +#: src/gns/gnunet-dns2gns.c:391 +#, fuzzy, c-format +msgid "Received unsupported DNS request from %s\n" +msgstr "Mottog okänd typ av begäran %d vid %s:%d\n" + +#: src/gns/gnunet-dns2gns.c:679 +msgid "IP of recursive DNS resolver to use (required)" +msgstr "" + +#: src/gns/gnunet-dns2gns.c:682 +msgid "Authoritative DNS suffix to use (optional); default: zkey.eu" +msgstr "" + +#: src/gns/gnunet-dns2gns.c:685 +msgid "Authoritative FCFS suffix to use (optional); default: fcfs.zkey.eu" +msgstr "" + +#: src/gns/gnunet-dns2gns.c:688 +msgid "UDP port to listen on for inbound DNS requests; default: 53" +msgstr "" + +#: src/gns/gnunet-dns2gns.c:701 +msgid "GNUnet DNS-to-GNS proxy (a DNS server)" +msgstr "" + +#: src/gns/gnunet-gns.c:221 +#, fuzzy, c-format msgid "Failed to connect to GNS\n" msgstr "Misslyckades att ansluta till gnunetd.\n" -#: src/gns/gnunet-gns.c:232 -msgid "try to shorten a given GNS name" +#: src/gns/gnunet-gns.c:335 +#, c-format +msgid "Please specify lookup, shorten or authority operation!\n" msgstr "" -#: src/gns/gnunet-gns.c:235 -msgid "Lookup a record using GNS (NOT IMPLEMENTED)" +#: src/gns/gnunet-gns.c:356 +#, fuzzy +msgid "try to shorten a given name" +msgstr "Misslyckades att ansluta till gnunetd.\n" + +#: src/gns/gnunet-gns.c:359 +msgid "Lookup a record for the given name" msgstr "" -#: src/gns/gnunet-gns.c:238 +#: src/gns/gnunet-gns.c:362 msgid "Get the authority of a particular name" msgstr "" -#: src/gns/gnunet-gns.c:241 +#: src/gns/gnunet-gns.c:365 #, fuzzy -msgid "Specify the type of the record lookup" +msgid "Specify the type of the record to lookup" msgstr "ange prioritet för innehållet" -#: src/gns/gnunet-gns.c:244 +#: src/gns/gnunet-gns.c:368 msgid "No unneeded output" msgstr "" -#: src/gns/gnunet-gns.c:255 +#: src/gns/gnunet-gns.c:381 msgid "GNUnet GNS access tool" msgstr "" -#: src/gns/gnunet-gns-fcfsd.c:280 +#: src/gns/gnunet-gns-fcfsd.c:451 #, fuzzy, c-format msgid "Unsupported form value `%s'\n" msgstr "Kommando \"%s\" stöds ej. Avbryter.\n" -#: src/gns/gnunet-gns-fcfsd.c:333 +#: src/gns/gnunet-gns-fcfsd.c:480 #, fuzzy, c-format msgid "Failed to create record for domain `%s': %s\n" msgstr "Kunde inte tolka konfigurationsfil \"%s\".\n" -#: src/gns/gnunet-gns-fcfsd.c:377 +#: src/gns/gnunet-gns-fcfsd.c:524 #, c-format msgid "Found existing name `%s' for the given key\n" msgstr "" -#: src/gns/gnunet-gns-fcfsd.c:439 +#: src/gns/gnunet-gns-fcfsd.c:586 #, c-format msgid "Found %u existing records for domain `%s'\n" msgstr "" -#: src/gns/gnunet-gns-fcfsd.c:498 +#: src/gns/gnunet-gns-fcfsd.c:648 #, fuzzy, c-format msgid "Failed to create page for `%s'\n" msgstr "Kunde inte skapa namnrymd \"%s\" (existerar?).\n" -#: src/gns/gnunet-gns-fcfsd.c:514 +#: src/gns/gnunet-gns-fcfsd.c:664 #, fuzzy, c-format msgid "Failed to setup post processor for `%s'\n" msgstr "Misslyckades att läsa kompislista från \"%s\"\n" -#: src/gns/gnunet-gns-fcfsd.c:725 src/gns/gnunet-gns-fcfsd.c:737 -#, fuzzy, c-format -msgid "Option `%s' not specified in configuration section `%s'\n" -msgstr "Inga applikationer definierade i konfiguration!\n" +#: src/gns/gnunet-gns-fcfsd.c:700 +msgid "Domain name must not contain `.'\n" +msgstr "" + +#: src/gns/gnunet-gns-fcfsd.c:708 +msgid "Domain name must not contain `+'\n" +msgstr "" -#: src/gns/gnunet-gns-fcfsd.c:747 src/namestore/gnunet-namestore.c:299 +#: src/gns/gnunet-gns-fcfsd.c:912 src/namestore/gnunet-namestore.c:364 #, fuzzy msgid "Failed to read or create private zone key\n" msgstr "Misslyckades att läsa kompislista från \"%s\"\n" -#: src/gns/gnunet-gns-fcfsd.c:757 src/namestore/gnunet-namestore.c:310 +#: src/gns/gnunet-gns-fcfsd.c:922 src/namestore/gnunet-namestore.c:375 #, fuzzy msgid "Failed to connect to namestore\n" msgstr "Misslyckades att ansluta till gnunetd.\n" -#: src/gns/gnunet-gns-fcfsd.c:773 src/gns/gnunet-gns-proxy.c:525 +#: src/gns/gnunet-gns-fcfsd.c:938 src/gns/gnunet-gns-proxy.c:2857 #, fuzzy msgid "Failed to start HTTP server\n" msgstr "Misslyckades att starta samling.\n" -#: src/gns/gnunet-gns-fcfsd.c:804 +#: src/gns/gnunet-gns-fcfsd.c:972 msgid "GNUnet GNS first come first serve registration service" msgstr "" -#: src/gns/gnunet-gns-proxy.c:800 -msgid "listen on specified port" +#: src/gns/gnunet-gns-proxy.c:2494 +#, fuzzy, c-format +msgid "Unable to import private key from file `%s'\n" +msgstr "Kunde inte skapa användarkonto:" + +#: src/gns/gnunet-gns-proxy.c:2522 +#, fuzzy, c-format +msgid "Unable to import certificate %s\n" +msgstr "Kunde inte spara konfigurationsfil \"%s\":" + +#: src/gns/gnunet-gns-proxy.c:3510 +msgid "listen on specified port (default: 7777)" +msgstr "" + +#: src/gns/gnunet-gns-proxy.c:3513 +msgid "pem file to use as CA" msgstr "" -#: src/gns/gnunet-gns-proxy.c:811 +#: src/gns/gnunet-gns-proxy.c:3525 msgid "GNUnet GNS proxy" msgstr "" -#: src/hello/gnunet-hello.c:122 +#: src/gns/gnunet-service-gns.c:486 +#, c-format +msgid "Records for name `%s' in zone %s too large to fit into DHT" +msgstr "" + +#: src/gns/gnunet-service-gns.c:1216 +#, fuzzy +msgid "Failed to connect to the namestore!\n" +msgstr "Misslyckades att ansluta till gnunetd.\n" + +#: src/gns/gnunet-service-gns.c:1277 +#, fuzzy +msgid "Could not connect to DHT!\n" +msgstr "Kunde inte ansluta till gnunetd.\n" + +#: src/gns/gnunet-service-gns.c:1288 +#, fuzzy +msgid "Unable to initialize resolver!\n" +msgstr "Kunde inte initiera SQLite.\n" + +#: src/gns/gnunet-service-gns_resolver.c:3439 +#, c-format +msgid "Not a GADS TLD: `%s'\n" +msgstr "" + +#: src/hello/gnunet-hello.c:118 msgid "Call with name of HELLO file to modify.\n" msgstr "" -#: src/hello/gnunet-hello.c:128 +#: src/hello/gnunet-hello.c:124 #, fuzzy, c-format msgid "Error accessing file `%s': %s\n" msgstr "Fel vid skapandet av användare" -#: src/hello/gnunet-hello.c:136 +#: src/hello/gnunet-hello.c:132 #, c-format msgid "File `%s' is too big to be a HELLO\n" msgstr "" -#: src/hello/gnunet-hello.c:143 +#: src/hello/gnunet-hello.c:139 #, c-format msgid "File `%s' is too small to be a HELLO\n" msgstr "" -#: src/hello/gnunet-hello.c:153 src/hello/gnunet-hello.c:181 +#: src/hello/gnunet-hello.c:149 src/hello/gnunet-hello.c:177 #, fuzzy, c-format msgid "Error opening file `%s': %s\n" msgstr "Fel vid skapandet av användare" -#: src/hello/gnunet-hello.c:169 +#: src/hello/gnunet-hello.c:165 #, fuzzy, c-format msgid "Did not find well-formed HELLO in file `%s'\n" msgstr "%d filer hittades i katalog.\n" -#: src/hello/gnunet-hello.c:193 +#: src/hello/gnunet-hello.c:189 #, fuzzy, c-format msgid "Error writing HELLO to file `%s': %s\n" msgstr "Fel vid skapandet av användare" +#: src/hello/hello.c:904 +#, fuzzy +msgid "Failed to parse HELLO message: missing expiration time\n" +msgstr "Kunde inte spara konfiguration!" + +#: src/hello/hello.c:913 +#, fuzzy +msgid "Failed to parse HELLO message: invalid expiration time\n" +msgstr "Kunde inte spara konfiguration!" + +#: src/hello/hello.c:923 +#, fuzzy +msgid "Failed to parse HELLO message: malformed\n" +msgstr "Misslyckades att läsa kompislista från \"%s\"\n" + +#: src/hello/hello.c:933 +#, fuzzy +msgid "Failed to parse HELLO message: missing transport plugin\n" +msgstr "Kunde inte slå upp \"%s\": %s\n" + +#: src/hello/hello.c:950 +#, c-format +msgid "Plugin `%s' not found\n" +msgstr "" + +#: src/hello/hello.c:959 +#, c-format +msgid "Plugin `%s' does not support URIs yet\n" +msgstr "" + +#: src/hello/hello.c:978 +#, fuzzy, c-format +msgid "Failed to parse `%s' as an address for plugin `%s'\n" +msgstr "Misslyckades att binda till UDP-port %d.\n" + #: src/hostlist/gnunet-daemon-hostlist.c:264 msgid "" "None of the functions for the hostlist daemon were enabled. I have no " @@ -3220,7 +3383,7 @@ msgstr "" msgid "provide a hostlist server" msgstr "" -#: src/hostlist/gnunet-daemon-hostlist.c:341 +#: src/hostlist/gnunet-daemon-hostlist.c:344 msgid "GNUnet hostlist server and client" msgstr "" @@ -3241,176 +3404,140 @@ msgstr "Ogiltigt meddelande mottogs den %s:%d." msgid "# valid HELLOs downloaded from hostlist servers" msgstr "" -#: src/hostlist/hostlist-client.c:375 src/hostlist/hostlist-client.c:396 -#, c-format -msgid "No `%s' specified in `%s' configuration, will not bootstrap.\n" -msgstr "" - -#: src/hostlist/hostlist-client.c:473 src/hostlist/hostlist-client.c:683 -#: src/hostlist/hostlist-client.c:689 src/hostlist/hostlist-client.c:741 -#: src/hostlist/hostlist-client.c:750 src/hostlist/hostlist-client.c:871 -#: src/hostlist/hostlist-client.c:961 src/hostlist/hostlist-client.c:966 -#: src/transport/plugin_transport_http_client.c:110 -#: src/transport/plugin_transport_http_client.c:125 +#: src/hostlist/hostlist-client.c:469 src/hostlist/hostlist-client.c:680 +#: src/hostlist/hostlist-client.c:686 src/hostlist/hostlist-client.c:738 +#: src/hostlist/hostlist-client.c:747 src/hostlist/hostlist-client.c:868 +#: src/hostlist/hostlist-client.c:958 src/hostlist/hostlist-client.c:963 +#: src/transport/plugin_transport_http_client.c:1052 +#: src/transport/plugin_transport_http_client.c:1067 #, fuzzy, c-format msgid "%s failed at %s:%d: `%s'\n" msgstr "\"%s\" misslyckades vid %s:%d med fel: \"%s\".\n" -#: src/hostlist/hostlist-client.c:593 src/hostlist/hostlist-client.c:1331 +#: src/hostlist/hostlist-client.c:589 src/hostlist/hostlist-client.c:1325 msgid "# advertised hostlist URIs" msgstr "" -#: src/hostlist/hostlist-client.c:623 +#: src/hostlist/hostlist-client.c:619 #, c-format msgid "# advertised URI `%s' downloaded" msgstr "" -#: src/hostlist/hostlist-client.c:664 +#: src/hostlist/hostlist-client.c:661 #, c-format msgid "" "Advertised hostlist with URI `%s' could not be downloaded. Advertised URI " "gets dismissed.\n" msgstr "" -#: src/hostlist/hostlist-client.c:802 +#: src/hostlist/hostlist-client.c:799 #, fuzzy, c-format msgid "Timeout trying to download hostlist from `%s'\n" msgstr "Misslyckades att läsa kompislista från \"%s\"\n" -#: src/hostlist/hostlist-client.c:816 +#: src/hostlist/hostlist-client.c:813 #, c-format msgid "Download limit of %u bytes exceeded, stopping download\n" msgstr "" -#: src/hostlist/hostlist-client.c:836 +#: src/hostlist/hostlist-client.c:833 #, fuzzy, c-format msgid "Download of hostlist from `%s' failed: `%s'\n" msgstr "" "Uppladdning av \"%s\" klar, aktuell genomsnittshastighet är %8.3f kbps.\n" -#: src/hostlist/hostlist-client.c:842 +#: src/hostlist/hostlist-client.c:839 #, fuzzy, c-format msgid "Download of hostlist `%s' completed.\n" msgstr "" "Uppladdning av \"%s\" klar, aktuell genomsnittshastighet är %8.3f kbps.\n" -#: src/hostlist/hostlist-client.c:850 +#: src/hostlist/hostlist-client.c:847 #, c-format msgid "Adding successfully tested hostlist `%s' datastore.\n" msgstr "" -#: src/hostlist/hostlist-client.c:903 +#: src/hostlist/hostlist-client.c:900 #, c-format msgid "Bootstrapping using hostlist at `%s'.\n" msgstr "" -#: src/hostlist/hostlist-client.c:911 +#: src/hostlist/hostlist-client.c:908 msgid "# hostlist downloads initiated" msgstr "" -#: src/hostlist/hostlist-client.c:1037 src/hostlist/hostlist-client.c:1505 +#: src/hostlist/hostlist-client.c:1035 src/hostlist/hostlist-client.c:1498 msgid "# milliseconds between hostlist downloads" msgstr "" -#: src/hostlist/hostlist-client.c:1046 +#: src/hostlist/hostlist-client.c:1043 #, c-format -msgid "Have %u/%u connections. Will consider downloading hostlist in %llums\n" -msgstr "" - -#: src/hostlist/hostlist-client.c:1084 -msgid "Scheduled saving of hostlists\n" +msgid "Have %u/%u connections. Will consider downloading hostlist in %s\n" msgstr "" -#: src/hostlist/hostlist-client.c:1088 -#, c-format -msgid "Hostlists will be saved to file again in %llums\n" -msgstr "" - -#: src/hostlist/hostlist-client.c:1111 src/hostlist/hostlist-client.c:1127 +#: src/hostlist/hostlist-client.c:1107 src/hostlist/hostlist-client.c:1123 #, fuzzy msgid "# active connections" msgstr "Nätverksanslutning" -#: src/hostlist/hostlist-client.c:1242 -#, c-format -msgid "Initial time between hostlist downloads is %llums\n" -msgstr "" - #: src/hostlist/hostlist-client.c:1273 -#, c-format -msgid "" -"No `%s' specified in `%s' configuration, cannot load hostlists from file.\n" -msgstr "" - -#: src/hostlist/hostlist-client.c:1279 #, fuzzy, c-format msgid "Loading saved hostlist entries from file `%s' \n" msgstr "Misslyckades att läsa kompislista från \"%s\"\n" -#: src/hostlist/hostlist-client.c:1283 -#, c-format -msgid "Hostlist file `%s' is not existing\n" -msgstr "" +#: src/hostlist/hostlist-client.c:1277 +#, fuzzy, c-format +msgid "Hostlist file `%s' does not exist\n" +msgstr "antal meddelanden att använda per iteration" -#: src/hostlist/hostlist-client.c:1294 +#: src/hostlist/hostlist-client.c:1288 #, fuzzy, c-format msgid "Could not open file `%s' for reading to load hostlists: %s\n" msgstr "Kunde inte slå upp \"%s\": %s\n" -#: src/hostlist/hostlist-client.c:1327 +#: src/hostlist/hostlist-client.c:1321 #, c-format msgid "%u hostlist URIs loaded from file\n" msgstr "" -#: src/hostlist/hostlist-client.c:1329 +#: src/hostlist/hostlist-client.c:1323 msgid "# hostlist URIs read from file" msgstr "" -#: src/hostlist/hostlist-client.c:1362 -#, c-format -msgid "" -"No `%s' specified in `%s' configuration, cannot save hostlists to file.\n" -msgstr "" - -#: src/hostlist/hostlist-client.c:1376 +#: src/hostlist/hostlist-client.c:1368 #, fuzzy, c-format msgid "Could not open file `%s' for writing to save hostlists: %s\n" msgstr "Kunde inte slå upp \"%s\": %s\n" -#: src/hostlist/hostlist-client.c:1381 +#: src/hostlist/hostlist-client.c:1373 #, fuzzy, c-format msgid "Writing %u hostlist URIs to `%s'\n" msgstr "Misslyckades att läsa kompislista från \"%s\"\n" -#: src/hostlist/hostlist-client.c:1405 src/hostlist/hostlist-client.c:1422 +#: src/hostlist/hostlist-client.c:1397 src/hostlist/hostlist-client.c:1414 #, c-format msgid "Error writing hostlist URIs to file `%s'\n" msgstr "" -#: src/hostlist/hostlist-client.c:1417 +#: src/hostlist/hostlist-client.c:1409 msgid "# hostlist URIs written to file" msgstr "" -#: src/hostlist/hostlist-client.c:1470 +#: src/hostlist/hostlist-client.c:1463 msgid "Learning is enabled on this peer\n" msgstr "" -#: src/hostlist/hostlist-client.c:1473 -#, c-format -msgid "Hostlists will be saved to file again in %llums\n" -msgstr "" - -#: src/hostlist/hostlist-client.c:1482 +#: src/hostlist/hostlist-client.c:1475 msgid "Learning is not enabled on this peer\n" msgstr "" -#: src/hostlist/hostlist-client.c:1494 +#: src/hostlist/hostlist-client.c:1487 #, c-format msgid "" "Since learning is not enabled on this peer, hostlist file `%s' was removed\n" msgstr "" -#: src/hostlist/hostlist-client.c:1498 +#: src/hostlist/hostlist-client.c:1491 #, c-format msgid "Hostlist file `%s' could not be removed\n" msgstr "" @@ -3425,9 +3552,9 @@ msgid "expired addresses encountered" msgstr "" #: src/hostlist/hostlist-server.c:184 src/hostlist/hostlist-server.c:425 -#: src/peerinfo-tool/gnunet-peerinfo.c:403 -#: src/peerinfo-tool/gnunet-peerinfo.c:519 -#: src/topology/gnunet-daemon-topology.c:927 +#: src/peerinfo-tool/gnunet-peerinfo.c:331 +#: src/peerinfo-tool/gnunet-peerinfo.c:386 +#: src/topology/gnunet-daemon-topology.c:922 #, fuzzy, c-format msgid "Error in communication with PEERINFO service: %s\n" msgstr "Skriv ut information om GNUnets motparter." @@ -3449,10 +3576,6 @@ msgstr "" msgid "hostlist requests refused (not HTTP GET)" msgstr "" -#: src/hostlist/hostlist-server.c:273 -msgid "Sending 100 CONTINUE reply\n" -msgstr "" - #: src/hostlist/hostlist-server.c:279 #, c-format msgid "Refusing `%s' request with %llu bytes of upload data\n" @@ -3486,65 +3609,103 @@ msgstr "" msgid "Advertisement message could not be queued by core\n" msgstr "" -#: src/hostlist/hostlist-server.c:561 +#: src/hostlist/hostlist-server.c:562 #, fuzzy, c-format msgid "Invalid port number %llu. Exiting.\n" msgstr "Ogiltiga argument. Avslutar.\n" -#: src/hostlist/hostlist-server.c:570 +#: src/hostlist/hostlist-server.c:571 #, c-format msgid "Hostlist service starts on %s:%llu\n" msgstr "" -#: src/hostlist/hostlist-server.c:584 +#: src/hostlist/hostlist-server.c:585 #, fuzzy, c-format msgid "Address to obtain hostlist: `%s'\n" msgstr "Misslyckades att läsa kompislista från \"%s\"\n" -#: src/hostlist/hostlist-server.c:624 +#: src/hostlist/hostlist-server.c:625 #, fuzzy, c-format msgid "`%s' is not a valid IP address! Ignoring BINDTOIP.\n" msgstr "\"%s\" är inte tillgänglig." -#: src/hostlist/hostlist-server.c:666 +#: src/hostlist/hostlist-server.c:667 #, c-format msgid "Could not start hostlist HTTP server on port %u\n" msgstr "" -#: src/integration-tests/connection_watchdog.c:997 +#: src/integration-tests/connection_watchdog.c:1001 #, fuzzy, c-format msgid "Transport plugin: `%s' port %llu\n" msgstr "Testar transport(er) %s\n" -#: src/integration-tests/connection_watchdog.c:1030 +#: src/integration-tests/connection_watchdog.c:1034 #, fuzzy, c-format msgid "Found %u transport plugins: `%s'\n" msgstr "Testar transport(er) %s\n" -#: src/integration-tests/connection_watchdog.c:1089 +#: src/integration-tests/connection_watchdog.c:1093 msgid "Send ping messages to test connectivity (default == NO)" msgstr "" -#: src/integration-tests/connection_watchdog.c:1095 -#: src/template/gnunet-template.c:68 +#: src/integration-tests/connection_watchdog.c:1102 +#: src/template/gnunet-template.c:70 #, fuzzy msgid "help text" msgstr "hjälptext för -t" -#: src/mesh/gnunet-service-mesh.c:4590 -msgid "Wrong CORE service\n" -msgstr "" +#: src/mesh/gnunet-mesh.c:211 +#, fuzzy +msgid "provide information about all tunnels (continuously) NOT IMPLEMENTED" +msgstr "Skriv ut information om GNUnets motparter." -#: src/mesh/gnunet-service-mesh.c:4784 +#: src/mesh/gnunet-mesh.c:214 #, fuzzy -msgid "Mesh service is lacking key configuration settings. Exiting.\n" -msgstr "GNUnet-konfiguration" +msgid "provide information about a particular tunnel" +msgstr "Skriv ut information om GNUnets motparter." -#: src/mesh/gnunet-service-mesh.c:4793 +#: src/mesh/gnunet-mesh.c:224 #, fuzzy -msgid "Mesh service could not access hostkey. Exiting.\n" +msgid "Print information about mesh tunnels and peers." +msgstr "Skriv ut information om GNUnets motparter." + +#: src/mesh/gnunet-service-mesh.c:8015 src/mesh/gnunet-service-mesh-new.c:8015 +msgid "Wrong CORE service\n" +msgstr "" + +#: src/mesh/gnunet-service-mesh.c:8232 src/mesh/gnunet-service-mesh-new.c:8232 +#, fuzzy, c-format +msgid "Mesh service could not access hostkey: %s. Exiting.\n" msgstr "Kunde inte komma åt namnrymdsinformation.\n" +#: src/mesh/gnunet-service-mesh.c:8314 src/mesh/gnunet-service-mesh.c:8326 +#: src/mesh/gnunet-service-mesh.c:8338 src/mesh/gnunet-service-mesh.c:8352 +#: src/mesh/gnunet-service-mesh.c:8364 src/mesh/gnunet-service-mesh.c:8376 +#: src/mesh/gnunet-service-mesh.c:8388 src/mesh/gnunet-service-mesh-new.c:8321 +#: src/mesh/gnunet-service-mesh-new.c:8333 +#: src/mesh/gnunet-service-mesh-new.c:8345 +#: src/mesh/gnunet-service-mesh-new.c:8359 +#: src/mesh/gnunet-service-mesh-new.c:8371 +#: src/mesh/gnunet-service-mesh-new.c:8383 +#: src/mesh/gnunet-service-mesh-new.c:8395 +#: src/regex/gnunet-daemon-regexprofiler.c:335 +#: src/regex/gnunet-daemon-regexprofiler.c:347 +#: src/regex/gnunet-daemon-regexprofiler.c:360 +#: src/regex/gnunet-daemon-regexprofiler.c:373 +#: src/regex/gnunet-regex-simulation-profiler.c:659 +#, fuzzy, c-format +msgid "%s service is lacking key configuration settings (%s). Exiting.\n" +msgstr "GNUnet-konfiguration" + +#: src/mesh/gnunet-service-mesh.c:8400 src/mesh/gnunet-service-mesh.c:8410 +#: src/mesh/gnunet-service-mesh.c:8421 src/mesh/gnunet-service-mesh-new.c:8407 +#: src/mesh/gnunet-service-mesh-new.c:8417 +#: src/mesh/gnunet-service-mesh-new.c:8428 +#, fuzzy, c-format +msgid "" +"%s service is lacking key configuration settings (%s). Using default (%u).\n" +msgstr "GNUnet-konfiguration" + #: src/mysql/mysql.c:174 #, c-format msgid "Trying to use file `%s' for MySQL configuration.\n" @@ -3555,200 +3716,328 @@ msgstr "Försöker använda fil \"%s\" för MySQL-konfiguration.\n" msgid "Could not access file `%s': %s\n" msgstr "Kunde inte köra \"%s\": %s\n" -#: src/namestore/gnunet-namestore.c:157 +#: src/namestore/gnunet-namestore.c:212 #, fuzzy, c-format msgid "Adding record failed: %s\n" msgstr "" "\n" "Fel vid uppladdning av fil: %s\n" -#: src/namestore/gnunet-namestore.c:183 +#: src/namestore/gnunet-namestore.c:243 #, fuzzy, c-format msgid "Deleting record failed: %s\n" msgstr "" "\n" "Fel vid uppladdning av fil: %s\n" -#: src/namestore/gnunet-namestore.c:239 +#: src/namestore/gnunet-namestore.c:304 #, c-format msgid "\tCorrupt or unsupported record of type %u\n" msgstr "" -#: src/namestore/gnunet-namestore.c:276 -#, c-format -msgid "Option `%s' not given, but I need a zone key file!\n" +#: src/namestore/gnunet-namestore.c:320 +msgid "for at least" msgstr "" -#: src/namestore/gnunet-namestore.c:281 -#, fuzzy, c-format -msgid "Using default zone file `%s'\n" -msgstr "Startade samling \"%s\".\n" +#: src/namestore/gnunet-namestore.c:321 +msgid "until" +msgstr "" -#: src/namestore/gnunet-namestore.c:291 +#: src/namestore/gnunet-namestore.c:356 #, c-format msgid "No options given\n" msgstr "" -#: src/namestore/gnunet-namestore.c:321 +#: src/namestore/gnunet-namestore.c:386 #, fuzzy, c-format msgid "Unsupported type `%s'\n" msgstr "Kommando \"%s\" stöds ej. Avbryter.\n" -#: src/namestore/gnunet-namestore.c:328 src/namestore/gnunet-namestore.c:350 -#: src/namestore/gnunet-namestore.c:374 src/namestore/gnunet-namestore.c:384 -#: src/namestore/gnunet-namestore.c:409 +#: src/namestore/gnunet-namestore.c:394 src/namestore/gnunet-namestore.c:418 +#: src/namestore/gnunet-namestore.c:465 src/namestore/gnunet-namestore.c:477 +#: src/namestore/gnunet-namestore.c:518 #, fuzzy, c-format msgid "Missing option `%s' for operation `%s'\n" msgstr "Konfigurationsfil \"%s\" skapad.\n" -#: src/namestore/gnunet-namestore.c:329 src/namestore/gnunet-namestore.c:351 +#: src/namestore/gnunet-namestore.c:395 src/namestore/gnunet-namestore.c:419 msgid "add/del" msgstr "" -#: src/namestore/gnunet-namestore.c:341 +#: src/namestore/gnunet-namestore.c:408 #, fuzzy, c-format msgid "Value `%s' invalid for record type `%s'\n" msgstr "%s: symbolvärde \"%s\" ogiltigt för %s\n" -#: src/namestore/gnunet-namestore.c:366 +#: src/namestore/gnunet-namestore.c:446 #, fuzzy, c-format msgid "Invalid time format `%s'\n" msgstr "Ogiltigt format för IP: \"%s\"\n" -#: src/namestore/gnunet-namestore.c:375 src/namestore/gnunet-namestore.c:385 +#: src/namestore/gnunet-namestore.c:455 +#, c-format +msgid "" +"Deletion requires either absolute time, or no time at all. Got relative time " +"`%s' instead.\n" +msgstr "" + +#: src/namestore/gnunet-namestore.c:466 src/namestore/gnunet-namestore.c:478 +#: src/namestore/gnunet-namestore.c:497 msgid "add" msgstr "" -#: src/namestore/gnunet-namestore.c:410 +#: src/namestore/gnunet-namestore.c:496 +#, fuzzy, c-format +msgid "No valid expiration time for operation `%s'\n" +msgstr "Konfigurationsfil \"%s\" skapad.\n" + +#: src/namestore/gnunet-namestore.c:519 msgid "del" msgstr "" -#: src/namestore/gnunet-namestore.c:462 +#: src/namestore/gnunet-namestore.c:569 +#: src/peerinfo-tool/gnunet-peerinfo.c:598 +#, fuzzy, c-format +msgid "Invalid URI `%s'\n" +msgstr "Ogiltiga argument: " + +#: src/namestore/gnunet-namestore.c:625 +#, fuzzy, c-format +msgid "Using default zone file `%s'\n" +msgstr "Startade samling \"%s\".\n" + +#: src/namestore/gnunet-namestore.c:677 msgid "add record" msgstr "" -#: src/namestore/gnunet-namestore.c:465 +#: src/namestore/gnunet-namestore.c:680 msgid "delete record" msgstr "" -#: src/namestore/gnunet-namestore.c:468 +#: src/namestore/gnunet-namestore.c:683 msgid "display records" msgstr "" -#: src/namestore/gnunet-namestore.c:471 +#: src/namestore/gnunet-namestore.c:686 msgid "" "expiration time for record to use (for adding only), \"never\" is possible" msgstr "" -#: src/namestore/gnunet-namestore.c:474 +#: src/namestore/gnunet-namestore.c:689 msgid "name of the record to add/delete/display" msgstr "" -#: src/namestore/gnunet-namestore.c:477 +#: src/namestore/gnunet-namestore.c:692 msgid "type of the record to add/delete/display" msgstr "" -#: src/namestore/gnunet-namestore.c:480 +#: src/namestore/gnunet-namestore.c:695 +msgid "URI to import into our zone" +msgstr "" + +#: src/namestore/gnunet-namestore.c:698 msgid "value of the record to add/delete" msgstr "" -#: src/namestore/gnunet-namestore.c:483 +#: src/namestore/gnunet-namestore.c:701 msgid "create or list public record" msgstr "" -#: src/namestore/gnunet-namestore.c:486 +#: src/namestore/gnunet-namestore.c:704 msgid "create or list non-authority record" msgstr "" -#: src/namestore/gnunet-namestore.c:489 +#: src/namestore/gnunet-namestore.c:707 msgid "filename with the zone key" msgstr "" -#: src/namestore/gnunet-namestore.c:500 +#: src/namestore/gnunet-namestore.c:718 #, fuzzy msgid "GNUnet zone manipulation tool" msgstr "GNUnet-konfiguration" -#: src/namestore/gnunet-service-namestore.c:143 -#, c-format -msgid "File zone `%s' but corrupt content already exists, failed to write! \n" -msgstr "" +#: src/namestore/gnunet-service-namestore.c:241 +#: src/namestore/gnunet-service-namestore.c:257 +#, fuzzy, c-format +msgid "Failed to write zone key to file `%s': %s\n" +msgstr "Misslyckades att leverera \"%s\" meddelande.\n" -#: src/namestore/gnunet-service-namestore.c:154 -#, c-format -msgid "File zone `%s' containing this key already exists\n" +#: src/namestore/gnunet-service-namestore.c:243 +msgid "file exists but reading key failed" msgstr "" -#: src/namestore/gnunet-service-namestore.c:160 -#, c-format -msgid "" -"File zone `%s' but different zone key already exists, failed to write! \n" +#: src/namestore/gnunet-service-namestore.c:259 +msgid "file exists with different key" msgstr "" -#: src/namestore/gnunet-service-namestore.c:198 +#: src/namestore/gnunet-service-namestore.c:1557 +#, fuzzy +msgid "Failed to find record to remove\n" +msgstr "Kunde inte ansluta till gnunetd.\n" + +#: src/namestore/gnunet-service-namestore.c:2172 #, fuzzy, c-format -msgid "Stored zonekey for zone `%s' in file `%s'\n" -msgstr "Misslyckades att leverera \"%s\" meddelande.\n" +msgid "Could not parse zone key file `%s'\n" +msgstr "Kunde inte tolka konfigurationsfil \"%s\".\n" -#: src/namestore/gnunet-service-namestore.c:1909 +#: src/namestore/gnunet-service-namestore.c:2262 #, fuzzy msgid "No directory to load zonefiles specified in configuration\n" msgstr "Inga applikationer definierade i konfiguration!\n" -#: src/namestore/gnunet-service-namestore.c:1918 +#: src/namestore/gnunet-service-namestore.c:2272 #, c-format msgid "Creating directory `%s' for zone files failed!\n" msgstr "" -#: src/namestore/namestore_api.c:315 src/namestore/namestore_api.c:353 -msgid "Namestore added record successfully" -msgstr "" - -#: src/namestore/namestore_api.c:323 +#: src/namestore/namestore_api.c:345 msgid "Namestore failed to add record" msgstr "" -#: src/namestore/namestore_api.c:361 -msgid "Namestore record already existed" -msgstr "" - -#: src/namestore/namestore_api.c:368 +#: src/namestore/namestore_api.c:371 msgid "Namestore failed to add record\n" msgstr "" -#: src/namestore/namestore_api.c:401 -msgid "Namestore removed record successfully" -msgstr "" - -#: src/namestore/namestore_api.c:408 -msgid "No records for entry" -msgstr "" - #: src/namestore/namestore_api.c:415 #, fuzzy -msgid "Could not find record to remove" -msgstr "Kunde inte ansluta till gnunetd.\n" - -#: src/namestore/namestore_api.c:422 -#, fuzzy msgid "Failed to create new signature" msgstr "Kunde inte skapa namnrymd \"%s\" (existerar?).\n" -#: src/namestore/namestore_api.c:429 +#: src/namestore/namestore_api.c:419 #, fuzzy msgid "Failed to put new set of records in database" msgstr "Misslyckades att skicka HTTP-begäran till värd \"%s\": %s\n" +#: src/namestore/namestore_api.c:423 +#, fuzzy +msgid "Failed to remove records from database" +msgstr "Misslyckades att ta emot svar till \"%s\" meddelande från gnunetd\n" + +#: src/namestore/namestore_api.c:427 +#, fuzzy +msgid "Failed to access database" +msgstr "Misslyckades att leverera \"%s\" meddelande.\n" + +#: src/namestore/namestore_api.c:431 +#, fuzzy +msgid "unknown internal error in namestore" +msgstr "=\tFel vid läsning av katalog.\n" + +#: src/namestore/namestore_api.c:436 +msgid "Protocol error" +msgstr "" + +#: src/namestore/namestore_common.c:530 src/namestore/namestore_common.c:670 +#, fuzzy, c-format +msgid "Unsupported record type %d\n" +msgstr "Kommando \"%s\" stöds ej. Avbryter.\n" + +#: src/namestore/namestore_common.c:537 +#, fuzzy, c-format +msgid "Unable to parse IPv4 address `%s'\n" +msgstr "Ogiltigt svar på \"%s\".\n" + +#: src/namestore/namestore_common.c:560 +#, fuzzy, c-format +msgid "Unable to parse SOA record `%s'\n" +msgstr "Misslyckades att läsa kompislista från \"%s\"\n" + +#: src/namestore/namestore_common.c:583 +#, fuzzy, c-format +msgid "Unable to parse MX record `%s'\n" +msgstr "Misslyckades att läsa kompislista från \"%s\"\n" + +#: src/namestore/namestore_common.c:601 +#, fuzzy, c-format +msgid "Unable to parse IPv6 address `%s'\n" +msgstr "Ogiltigt svar på \"%s\".\n" + +#: src/namestore/namestore_common.c:614 +#, fuzzy, c-format +msgid "Unable to parse PKEY record `%s'\n" +msgstr "Misslyckades att läsa kompislista från \"%s\"\n" + +#: src/namestore/namestore_common.c:635 +#, fuzzy, c-format +msgid "Unable to parse VPN record string `%s'\n" +msgstr "Misslyckades att läsa kompislista från \"%s\"\n" + +#: src/namestore/namestore_common.c:661 +#, fuzzy, c-format +msgid "Unable to parse TLSA record string `%s'\n" +msgstr "Misslyckades att läsa kompislista från \"%s\"\n" + +#: src/namestore/plugin_namestore_postgres.c:95 +#, fuzzy +msgid "Failed to create indices\n" +msgstr "Kunde inte skapa namnrymd \"%s\" (existerar?).\n" + #: src/nat/gnunet-nat-server.c:279 #, c-format msgid "Please pass valid port number as the first argument! (got `%s')\n" msgstr "" -#: src/nat/gnunet-nat-server.c:318 +#: src/nat/gnunet-nat-server.c:321 msgid "GNUnet NAT traversal test helper daemon" msgstr "" -#: src/nat/nat.c:799 +#: src/nat/nat_auto.c:169 +msgid "NAT traversal with ICMP Server timed out.\n" +msgstr "" + +#: src/nat/nat_auto.c:199 +msgid "NAT traversal with ICMP Server succeeded.\n" +msgstr "" + +#: src/nat/nat_auto.c:200 +msgid "NAT traversal with ICMP Server failed.\n" +msgstr "" + +#: src/nat/nat_auto.c:219 +#, fuzzy +msgid "Testing connection reversal with ICMP server.\n" +msgstr "Skriv ut information om GNUnets motparter." + +#: src/nat/nat_auto.c:265 +#, fuzzy, c-format +msgid "Detected external IP `%s'\n" +msgstr "Mottog ogiltig RPC \"%s\".\n" + +#: src/nat/nat_auto.c:331 +msgid "This system has a global IPv6 address, setting IPv6 to supported.\n" +msgstr "" + +#: src/nat/nat_auto.c:347 +#, c-format +msgid "Detected internal network address `%s'.\n" +msgstr "" + +#: src/nat/nat_auto.c:400 +msgid "upnpc found, enabling its use\n" +msgstr "" + +#: src/nat/nat_auto.c:401 +#, fuzzy +msgid "upnpc not found\n" +msgstr "Kommando \"%s\" hittades inte!\n" + +#: src/nat/nat_auto.c:434 +msgid "gnunet-helper-nat-server found, testing it\n" +msgstr "" + +#: src/nat/nat_auto.c:435 +msgid "No working gnunet-helper-nat-server found\n" +msgstr "" + +#: src/nat/nat_auto.c:469 +msgid "gnunet-helper-nat-client found, enabling it\n" +msgstr "" + +#: src/nat/nat_auto.c:470 +msgid "gnunet-helper-nat-client not found or behind NAT, disabling it\n" +msgstr "" + +#: src/nat/nat.c:795 #, c-format msgid "gnunet-helper-nat-server generated malformed address `%s'\n" msgstr "" @@ -3758,27 +4047,34 @@ msgstr "" msgid "Failed to start %s\n" msgstr "Misslyckades att starta samling.\n" -#: src/nat/nat.c:1111 -#, fuzzy, c-format -msgid "Malformed %s `%s' given in configuration!\n" -msgstr "Kunde inte spara konfiguration!" +#: src/nat/nat.c:1113 +msgid "malformed" +msgstr "" -#: src/nat/nat.c:1177 src/nat/nat.c:1187 +#: src/nat/nat.c:1179 src/nat/nat.c:1191 #, c-format msgid "" "Configuration requires `%s', but binary is not installed properly (SUID bit " "not set). Option disabled.\n" msgstr "" -#: src/nat/nat.c:1321 +#: src/nat/nat.c:1326 msgid "Internal IP address not known, cannot use ICMP NAT traversal method\n" msgstr "" -#: src/nat/nat.c:1332 +#: src/nat/nat.c:1337 #, c-format msgid "Running gnunet-helper-nat-client %s %s %u\n" msgstr "" +#: src/nat/nat_mini.c:170 +msgid "`external-ip' command not found\n" +msgstr "" + +#: src/nat/nat_mini.c:505 +msgid "`upnpc' command not found\n" +msgstr "" + #: src/nat/nat_test.c:341 #, fuzzy msgid "Failed to connect to `gnunet-nat-server'\n" @@ -3789,83 +4085,115 @@ msgstr "Misslyckades att ansluta till gnunetd.\n" msgid "Failed to create listen socket bound to `%s' for NAT test: %s\n" msgstr "" -#: src/nse/gnunet-nse-profiler.c:928 +#: src/nse/gnunet-nse-profiler.c:1009 +#, fuzzy +msgid "limit to the number of connections to NSE services, 0 for none" +msgstr "Misslyckades att ansluta till gnunetd.\n" + +#: src/nse/gnunet-nse-profiler.c:1012 +msgid "name of the file for writing connection information and statistics" +msgstr "" + +#: src/nse/gnunet-nse-profiler.c:1015 +msgid "name of the file with the login information for the testbed" +msgstr "" + +#: src/nse/gnunet-nse-profiler.c:1018 +msgid "IP address of this system as seen by the rest of the testbed" +msgstr "" + +#: src/nse/gnunet-nse-profiler.c:1021 +msgid "delay between queries to statistics during a round" +msgstr "" + +#: src/nse/gnunet-nse-profiler.c:1024 +msgid "prefix of the filenames we use for writing the topology for each round" +msgstr "" + +#: src/nse/gnunet-nse-profiler.c:1027 +msgid "name of the file for writing the main results" +msgstr "" + +#: src/nse/gnunet-nse-profiler.c:1030 +msgid "Number of peers to run in each round, separated by commas" +msgstr "" + +#: src/nse/gnunet-nse-profiler.c:1036 +msgid "delay between rounds" +msgstr "" + +#: src/nse/gnunet-nse-profiler.c:1046 #, fuzzy msgid "Measure quality and performance of the NSE service." msgstr "Kan inte tillgå tjänsten" -#: src/nse/gnunet-service-nse.c:925 -#, c-format -msgid "Proof of work invalid: %llu!\n" -msgstr "" +#: src/nse/gnunet-service-nse.c:1389 +#, fuzzy, c-format +msgid "NSE service could not access hostkey: %s\n" +msgstr "Kunde inte komma åt namnrymdsinformation.\n" -#: src/nse/gnunet-service-nse.c:1381 src/nse/gnunet-service-nse.c:1400 -#: src/nse/gnunet-service-nse.c:1421 +#: src/nse/gnunet-service-nse.c:1403 src/nse/gnunet-service-nse.c:1478 +#: src/nse/gnunet-service-nse.c:1495 msgid "NSE service is lacking key configuration settings. Exiting.\n" msgstr "" -#: src/nse/gnunet-service-nse.c:1388 +#: src/nse/gnunet-service-nse.c:1485 #, fuzzy msgid "Invalid work requirement for NSE service. Exiting.\n" msgstr "Ogiltiga argument. Avslutar.\n" -#: src/nse/gnunet-service-nse.c:1409 -#, fuzzy -msgid "NSE service could not access hostkey. Exiting.\n" -msgstr "Kunde inte komma åt namnrymdsinformation.\n" - #: src/peerinfo/gnunet-service-peerinfo.c:134 #, fuzzy, c-format msgid "Removing expired address of transport `%s'\n" msgstr "Tillgängliga transport(er): %s\n" -#: src/peerinfo/gnunet-service-peerinfo.c:203 +#: src/peerinfo/gnunet-service-peerinfo.c:230 #, fuzzy, c-format msgid "Failed to parse HELLO in file `%s'\n" msgstr "Misslyckades att läsa kompislista från \"%s\"\n" -#: src/peerinfo/gnunet-service-peerinfo.c:229 +#: src/peerinfo/gnunet-service-peerinfo.c:269 msgid "# peers known" msgstr "" -#: src/peerinfo/gnunet-service-peerinfo.c:254 +#: src/peerinfo/gnunet-service-peerinfo.c:297 #, c-format msgid "" "File `%s' in directory `%s' does not match naming convention. Removed.\n" msgstr "" -#: src/peerinfo/gnunet-service-peerinfo.c:353 +#: src/peerinfo/gnunet-service-peerinfo.c:419 #, c-format msgid "Still no peers found in `%s'!\n" msgstr "" -#: src/peerinfo/gnunet-service-peerinfo.c:710 +#: src/peerinfo/gnunet-service-peerinfo.c:807 #, c-format msgid "Importing HELLOs from `%s'\n" msgstr "" -#: src/peerinfo/peerinfo_api.c:238 +#: src/peerinfo/peerinfo_api.c:239 msgid "aborted due to explicit disconnect request" msgstr "" -#: src/peerinfo/peerinfo_api.c:358 +#: src/peerinfo/peerinfo_api.c:359 #, fuzzy msgid "failed to transmit request (service down?)" msgstr "Misslyckades att skicka HTTP-begäran till värd \"%s\": %s\n" -#: src/peerinfo/peerinfo_api.c:505 +#: src/peerinfo/peerinfo_api.c:509 #, fuzzy msgid "Failed to receive response from `PEERINFO' service." msgstr "Misslyckades att ta emot svar till \"%s\" meddelande från gnunetd\n" -#: src/peerinfo/peerinfo_api.c:531 src/peerinfo/peerinfo_api.c:550 -#: src/peerinfo/peerinfo_api.c:565 src/peerinfo/peerinfo_api.c:576 -#: src/peerinfo/peerinfo_api.c:587 +#: src/peerinfo/peerinfo_api.c:550 src/peerinfo/peerinfo_api.c:569 +#: src/peerinfo/peerinfo_api.c:584 src/peerinfo/peerinfo_api.c:595 +#: src/peerinfo/peerinfo_api.c:606 #, fuzzy msgid "Received invalid message from `PEERINFO' service." msgstr "mottog ogiltigt \"%s\" meddelande: %s.\n" -#: src/peerinfo/peerinfo_api.c:663 +#: src/peerinfo/peerinfo_api.c:681 #, fuzzy msgid "Timeout transmitting iteration request to `PEERINFO' service." msgstr "Misslyckades att initiera tjänsten \"%s\".\n" @@ -3875,91 +4203,51 @@ msgstr "Misslyckades att initiera tjänsten \"%s\".\n" msgid "Could not connect to `%s' service.\n" msgstr "Kunde inte ansluta till gnunetd.\n" -#: src/peerinfo-tool/gnunet-peerinfo.c:581 -#, fuzzy -msgid "Failed to parse HELLO message: missing expiration time\n" -msgstr "Kunde inte spara konfiguration!" - -#: src/peerinfo-tool/gnunet-peerinfo.c:589 -#, fuzzy -msgid "Failed to parse HELLO message: invalid expiration time\n" -msgstr "Kunde inte spara konfiguration!" - -#: src/peerinfo-tool/gnunet-peerinfo.c:598 -#, fuzzy -msgid "Failed to parse HELLO message: malformed\n" -msgstr "Misslyckades att läsa kompislista från \"%s\"\n" - -#: src/peerinfo-tool/gnunet-peerinfo.c:608 -#, fuzzy -msgid "Failed to parse HELLO message: missing transport plugin\n" -msgstr "Kunde inte slå upp \"%s\": %s\n" - -#: src/peerinfo-tool/gnunet-peerinfo.c:625 -#, c-format -msgid "Plugin `%s' not found\n" -msgstr "" - -#: src/peerinfo-tool/gnunet-peerinfo.c:634 -#, c-format -msgid "Plugin `%s' does not support URIs yet\n" -msgstr "" - -#: src/peerinfo-tool/gnunet-peerinfo.c:653 -#, fuzzy, c-format -msgid "Failed to parse `%s' as an address for plugin `%s'\n" -msgstr "Misslyckades att binda till UDP-port %d.\n" - -#: src/peerinfo-tool/gnunet-peerinfo.c:685 +#: src/peerinfo-tool/gnunet-peerinfo.c:419 #, c-format msgid "Failure adding HELLO: %s\n" msgstr "" -#: src/peerinfo-tool/gnunet-peerinfo.c:833 +#: src/peerinfo-tool/gnunet-peerinfo.c:557 #, fuzzy, c-format msgid "Could not find option `%s:%s' in configuration.\n" msgstr "Kunde inte hitta motpart \"%s\" i routingtabell!\n" -#: src/peerinfo-tool/gnunet-peerinfo.c:840 +#: src/peerinfo-tool/gnunet-peerinfo.c:563 #, fuzzy, c-format msgid "Loading hostkey from `%s' failed.\n" msgstr "Tolkning av HTTP-svar för URL \"%s\" misslyckades.\n" -#: src/peerinfo-tool/gnunet-peerinfo.c:875 -#, fuzzy, c-format -msgid "Invalid URI `%s'\n" -msgstr "Ogiltiga argument: " - -#: src/peerinfo-tool/gnunet-peerinfo.c:899 +#: src/peerinfo-tool/gnunet-peerinfo.c:622 #, c-format msgid "I am peer `%s'.\n" msgstr "Jag är ändpunkt \"%s\".\n" -#: src/peerinfo-tool/gnunet-peerinfo.c:936 +#: src/peerinfo-tool/gnunet-peerinfo.c:648 msgid "don't resolve host names" msgstr "" -#: src/peerinfo-tool/gnunet-peerinfo.c:939 +#: src/peerinfo-tool/gnunet-peerinfo.c:651 msgid "output only the identity strings" msgstr "" -#: src/peerinfo-tool/gnunet-peerinfo.c:942 +#: src/peerinfo-tool/gnunet-peerinfo.c:654 msgid "output our own identity only" msgstr "" -#: src/peerinfo-tool/gnunet-peerinfo.c:945 +#: src/peerinfo-tool/gnunet-peerinfo.c:657 msgid "list all known peers" msgstr "" -#: src/peerinfo-tool/gnunet-peerinfo.c:948 +#: src/peerinfo-tool/gnunet-peerinfo.c:660 msgid "also output HELLO uri(s)" msgstr "" -#: src/peerinfo-tool/gnunet-peerinfo.c:951 +#: src/peerinfo-tool/gnunet-peerinfo.c:663 msgid "add given HELLO uri to the database" msgstr "" -#: src/peerinfo-tool/gnunet-peerinfo.c:957 +#: src/peerinfo-tool/gnunet-peerinfo.c:674 #, fuzzy msgid "Print information about peers." msgstr "Skriv ut information om GNUnets motparter." @@ -4054,461 +4342,555 @@ msgstr "" msgid "Failed to connect to %s service. Exiting.\n" msgstr "Misslyckades att initiera tjänsten \"%s\".\n" -#: src/pt/gnunet-daemon-pt.c:973 +#: src/pt/gnunet-daemon-pt.c:976 msgid "Daemon to run to perform IP protocol translation to GNUnet" msgstr "" -#: src/statistics/gnunet-service-statistics.c:271 +#: src/regex/gnunet-daemon-regexprofiler.c:293 #, fuzzy, c-format -msgid "Loading %llu bytes of statistics from `%s'\n" -msgstr "Ladda ner filer från GNUnet." +msgid "Regexprofiler could not access hostkey: %s. Exiting.\n" +msgstr "Kunde inte komma åt namnrymdsinformation.\n" -#: src/statistics/gnunet-service-statistics.c:330 -#, fuzzy, c-format -msgid "Wrote %llu bytes of statistics to `%s'\n" -msgstr "Ladda ner filer från GNUnet." +#: src/regex/gnunet-daemon-regexprofiler.c:452 +msgid "Daemon to announce regular expressions for the peer using mesh." +msgstr "" -#: src/statistics/gnunet-statistics.c:122 -#, fuzzy -msgid "Failed to obtain statistics.\n" -msgstr "Misslyckades att binda till UDP-port %d.\n" +#: src/regex/gnunet-regex-profiler.c:1147 +msgid "An operation has failed while starting peers\n" +msgstr "" -#: src/statistics/gnunet-statistics.c:199 -#, c-format -msgid "No subsystem or name given\n" +#: src/regex/gnunet-regex-profiler.c:1193 +#, fuzzy, c-format +msgid "Creating a peer failed. Error: %s\n" +msgstr "" +"\n" +"Fel vid uppladdning av fil: %s\n" + +#: src/regex/gnunet-regex-profiler.c:1320 +msgid "An operation has failed while starting slaves\n" msgstr "" -#: src/statistics/gnunet-statistics.c:207 +#: src/regex/gnunet-regex-profiler.c:1342 #, fuzzy, c-format -msgid "Failed to initialize watch routine\n" -msgstr "Misslyckades att initiera tjänsten \"%s\".\n" +msgid "No files found in `%s'\n" +msgstr "%d filer hittades i katalog.\n" -#: src/statistics/gnunet-statistics.c:227 -msgid "limit output to statistics for the given NAME" +#: src/regex/gnunet-regex-profiler.c:1397 +msgid "An operation has failed while linking\n" msgstr "" -#: src/statistics/gnunet-statistics.c:230 -msgid "make the value being set persistent" +#: src/regex/gnunet-regex-profiler.c:1508 +#: src/testbed/testbed_api_testbed.c:805 +#, c-format +msgid "Host registration failed for a host. Error: %s\n" msgstr "" -#: src/statistics/gnunet-statistics.c:233 -msgid "limit output to the given SUBSYSTEM" +#: src/regex/gnunet-regex-profiler.c:1589 +msgid "Unable to connect to master controller -- Check config\n" msgstr "" -#: src/statistics/gnunet-statistics.c:236 -msgid "just print the statistics value" +#: src/regex/gnunet-regex-profiler.c:1691 +#: src/testbed/testbed_api_testbed.c:970 +#, c-format +msgid "Host %s cannot start testbed\n" msgstr "" -#: src/statistics/gnunet-statistics.c:239 -msgid "watch value continously" +#: src/regex/gnunet-regex-profiler.c:1694 +#: src/testbed/testbed_api_testbed.c:974 +msgid "Testbed cannot be started on localhost\n" msgstr "" -#: src/statistics/gnunet-statistics.c:246 -msgid "Print statistics about GNUnet operations." -msgstr "Skriv ut statistik om GNUnet-operationer." +#: src/regex/gnunet-regex-profiler.c:1734 +#, c-format +msgid "No hosts-file specified on command line. Exiting.\n" +msgstr "" -#: src/statistics/statistics_api.c:456 -#, fuzzy -msgid "Could not save some persistent statistics\n" -msgstr "Kunde inte skapa värdnyckel!\n" +#: src/regex/gnunet-regex-profiler.c:1739 +#: src/regex/gnunet-regex-simulation-profiler.c:622 +#, c-format +msgid "No policy directory specified on command line. Exiting.\n" +msgstr "" -#: src/statistics/statistics_api.c:999 -msgid "" -"Failed to receive acknowledgement from statistics service, some statistics " -"might have been lost!\n" +#: src/regex/gnunet-regex-profiler.c:1745 +#: src/testbed/testbed_api_testbed.c:1065 +#, c-format +msgid "No hosts loaded. Need at least one host\n" msgstr "" -#: src/testing/gnunet-testing.c:157 -#, fuzzy -msgid "Could not read hostkeys file, specify hostkey file with -H!\n" -msgstr "Kunde inte skapa värdnyckel!\n" +#: src/regex/gnunet-regex-profiler.c:1748 +#, c-format +msgid "Checking whether given hosts can start testbed. Please wait\n" +msgstr "" + +#: src/regex/gnunet-regex-profiler.c:1769 +#, fuzzy, c-format +msgid "Exiting\n" +msgstr "" +"\n" +"Avslutar.\n" -#: src/testing/gnunet-testing.c:159 +#: src/regex/gnunet-regex-profiler.c:1775 +#, fuzzy, c-format +msgid "No configuration file given. Exiting\n" +msgstr "använd konfigurationsfil FILNAMN" + +#: src/regex/gnunet-regex-profiler.c:1784 +#, fuzzy, c-format +msgid "Configuration option (regex_prefix) missing. Exiting\n" +msgstr "Konfigurationsfil \"%s\" skapad.\n" + +#: src/regex/gnunet-regex-profiler.c:1802 +#: src/regex/gnunet-regex-simulation-profiler.c:629 +#, c-format +msgid "Specified policies directory does not exist. Exiting.\n" +msgstr "" + +#: src/regex/gnunet-regex-profiler.c:1809 #, c-format -msgid "Specified hostkey file `%s' not found!\n" +msgid "No search strings file given. Exiting.\n" msgstr "" -#: src/testing/gnunet-testing.c:273 +#: src/regex/gnunet-regex-profiler.c:1817 +#, c-format +msgid "" +"Error loading search strings. Given file does not contain enough strings. " +"Exiting.\n" +msgstr "" + +#: src/regex/gnunet-regex-profiler.c:1823 +#, fuzzy, c-format +msgid "Error loading search strings. Exiting.\n" +msgstr "Fel vid lämning av DHT.\n" + +#: src/regex/gnunet-regex-profiler.c:1850 #, fuzzy -msgid "create unique configuration files" -msgstr "skriv ut ett värde från konfigurationsfilen till standard ut" +msgid "name of the file for writing statistics" +msgstr "Visa värde av alternativet" -#: src/testing/gnunet-testing.c:275 -msgid "create hostkey files from pre-computed hostkey list" +#: src/regex/gnunet-regex-profiler.c:1853 +msgid "create COUNT number of random links between peers" msgstr "" -#: src/testing/gnunet-testing.c:277 -msgid "host key file" +#: src/regex/gnunet-regex-profiler.c:1856 +msgid "wait TIMEOUT before considering a string match as failed" msgstr "" -#: src/testing/gnunet-testing.c:279 -#, fuzzy -msgid "number of unique configuration files or hostkeys to create" -msgstr "skriv ut ett värde från konfigurationsfilen till standard ut" +#: src/regex/gnunet-regex-profiler.c:1859 +msgid "wait DELAY before starting string search" +msgstr "" -#: src/testing/gnunet-testing.c:281 -#, fuzzy -msgid "configuration template" -msgstr "Konfigurationsfil \"%s\" skapad.\n" +#: src/regex/gnunet-regex-profiler.c:1862 +msgid "number of search strings to read from search strings file" +msgstr "" -#: src/testing/gnunet-testing.c:287 -msgid "Command line tool to access the testing library" +#: src/regex/gnunet-regex-profiler.c:1865 +#: src/regex/gnunet-regex-simulation-profiler.c:692 +msgid "maximum path compression length" msgstr "" -#: src/testing/helper.c:56 -#, fuzzy -msgid "Peer is lacking HOSTKEY configuration setting.\n" -msgstr "GNUnet-konfiguration" +#: src/regex/gnunet-regex-profiler.c:1868 +msgid "" +"if this option is set, only one peer is responsible for searching all strings" +msgstr "" + +#: src/regex/gnunet-regex-profiler.c:1881 +msgid "Profiler for regex" +msgstr "" -#: src/testing/helper.c:64 +#: src/regex/gnunet-regex-simulation-profiler.c:689 #, fuzzy -msgid "Could not access hostkey.\n" -msgstr "Kunde inte tolka konfigurationsfil \"%s\".\n" +msgid "name of the table to write DFAs" +msgstr "Visa värde av alternativet" -#: src/testing/testing.c:200 -msgid "`scp' does not seem to terminate (timeout copying config).\n" +#: src/regex/gnunet-regex-simulation-profiler.c:705 +msgid "Profiler for regex library" msgstr "" -#: src/testing/testing.c:214 src/testing/testing.c:798 -#, fuzzy -msgid "`scp' did not complete cleanly.\n" -msgstr "\"%s\" är inte ansluten till någon ändpunkt.\n" +#: src/statistics/gnunet-service-statistics.c:271 +#, fuzzy, c-format +msgid "Loading %llu bytes of statistics from `%s'\n" +msgstr "Ladda ner filer från GNUnet." -#: src/testing/testing.c:237 -#, fuzzy -msgid "Failed to create pipe for `gnunet-peerinfo' process.\n" -msgstr "Misslyckades att starta samling.\n" +#: src/statistics/gnunet-service-statistics.c:330 +#, fuzzy, c-format +msgid "Wrote %llu bytes of statistics to `%s'\n" +msgstr "Ladda ner filer från GNUnet." -#: src/testing/testing.c:238 +#: src/statistics/gnunet-statistics.c:141 #, fuzzy -msgid "Failed to create pipe for `ssh' process.\n" -msgstr "Misslyckades att läsa kompislista från \"%s\"\n" +msgid "Failed to obtain statistics.\n" +msgstr "Misslyckades att binda till UDP-port %d.\n" -#: src/testing/testing.c:286 +#: src/statistics/gnunet-statistics.c:143 #, fuzzy, c-format -msgid "Could not start `%s' process to create hostkey.\n" -msgstr "Kunde inte skapa värdnyckel!\n" +msgid "Failed to obtain statistics from host `%s:%llu'\n" +msgstr "Misslyckades att binda till UDP-port %d.\n" -#: src/testing/testing.c:293 -#, fuzzy -msgid "Failed to start `gnunet-peerinfo' process.\n" -msgstr "Misslyckades att starta samling.\n" +#: src/statistics/gnunet-statistics.c:181 +#, fuzzy, c-format +msgid "Trying to connect to remote host, but service `%s' is not running\n" +msgstr "Kunde inte ansluta till gnunetd.\n" -#: src/testing/testing.c:294 src/testing/testing.c:471 -#, fuzzy -msgid "Failed to start `ssh' process.\n" -msgstr "Misslyckades att starta samling.\n" +#: src/statistics/gnunet-statistics.c:190 +#, fuzzy, c-format +msgid "A port is required to connect to host `%s'\n" +msgstr "Kan inte ansluta till %u.%u.%u.%u:%u: %s\n" -#: src/testing/testing.c:354 +#: src/statistics/gnunet-statistics.c:196 #, c-format -msgid "Error reading from gnunet-peerinfo: %s\n" +msgid "A port has to be between 1 and 65535 to connect to host `%s'\n" msgstr "" -#: src/testing/testing.c:358 -#, fuzzy -msgid "Malformed output from gnunet-peerinfo!\n" -msgstr "Misslyckades att starta samling.\n" +#: src/statistics/gnunet-statistics.c:210 +msgid "Missing argument: subsystem \n" +msgstr "" -#: src/testing/testing.c:368 -#, fuzzy -msgid "Failed to get hostkey!\n" -msgstr "Kunde inte skapa värdnyckel!\n" +#: src/statistics/gnunet-statistics.c:216 +msgid "Missing argument: name\n" +msgstr "" -#: src/testing/testing.c:400 -msgid "`Failed while waiting for topology setup!\n" +#: src/statistics/gnunet-statistics.c:247 +#, c-format +msgid "No subsystem or name given\n" msgstr "" -#: src/testing/testing.c:463 +#: src/statistics/gnunet-statistics.c:255 #, fuzzy, c-format -msgid "Could not start `%s' process to start GNUnet.\n" -msgstr "Kunde inte skapa värdnyckel!\n" +msgid "Failed to initialize watch routine\n" +msgstr "Misslyckades att initiera tjänsten \"%s\".\n" -#: src/testing/testing.c:470 -#, fuzzy -msgid "Failed to start `gnunet-arm' process.\n" -msgstr "Misslyckades att ansluta till gnunetd.\n" +#: src/statistics/gnunet-statistics.c:310 +msgid "limit output to statistics for the given NAME" +msgstr "" -#: src/testing/testing.c:493 src/testing/testing.c:600 -msgid "`gnunet-arm' does not seem to terminate.\n" +#: src/statistics/gnunet-statistics.c:313 +msgid "make the value being set persistent" msgstr "" -#: src/testing/testing.c:494 src/testing/testing.c:601 -#: src/testing/testing.c:621 -msgid "`ssh' does not seem to terminate.\n" +#: src/statistics/gnunet-statistics.c:316 +msgid "limit output to the given SUBSYSTEM" msgstr "" -#: src/testing/testing.c:570 -msgid "Unable to get HELLO for peer!\n" +#: src/statistics/gnunet-statistics.c:319 +msgid "just print the statistics value" msgstr "" -#: src/testing/testing.c:620 -msgid "`gnunet-arm' terminated with non-zero exit status (or timed out)!\n" +#: src/statistics/gnunet-statistics.c:322 +msgid "watch value continuously" msgstr "" -#: src/testing/testing.c:643 src/testing/testing.c:675 -msgid "either `gnunet-arm' or `ssh' does not seem to terminate.\n" +#: src/statistics/gnunet-statistics.c:325 +msgid "connect to remote host" msgstr "" -#: src/testing/testing.c:658 src/testing/testing.c:713 +#: src/statistics/gnunet-statistics.c:328 +msgid "port for remote host" +msgstr "" + +#: src/statistics/gnunet-statistics.c:340 +msgid "Print statistics about GNUnet operations." +msgstr "Skriv ut statistik om GNUnet-operationer." + +#: src/statistics/statistics_api.c:511 #, fuzzy -msgid "shutdown (either `gnunet-arm' or `ssh') did not complete cleanly.\n" -msgstr "\"%s\" är inte ansluten till någon ändpunkt.\n" +msgid "Could not save some persistent statistics\n" +msgstr "Kunde inte skapa värdnyckel!\n" -#: src/testing/testing.c:786 -msgid "`scp' does not seem to terminate.\n" +#: src/statistics/statistics_api.c:1056 +msgid "" +"Failed to receive acknowledgement from statistics service, some statistics " +"might have been lost!\n" msgstr "" -#: src/testing/testing.c:948 -#, fuzzy, c-format -msgid "Starting service %s for peer `%4s'\n" -msgstr "Startade samling \"%s\".\n" +#: src/sysmon/gnunet-service-sysmon.c:546 +#, c-format +msgid "Could not parse execution interval for `%s', set to default 60 sec.\n" +msgstr "" -#: src/testing/testing.c:1207 src/testing/testing_group.c:6154 -#, fuzzy, c-format -msgid "Could not start `%s' process to copy configuration directory.\n" -msgstr "Kunde inte skapa värdnyckel!\n" +#: src/testbed/gnunet-testbed-profiler.c:231 +#, c-format +msgid "No hosts-file specified on command line\n" +msgstr "" -#: src/testing/testing.c:1292 src/testing/testing.c:1359 -#, fuzzy, c-format -msgid "Terminating peer `%4s'\n" -msgstr "Åtkomst nekad för \"%s\" vid %s:%d.\n" +#: src/testbed/gnunet-testbed-profiler.c:261 +msgid "create COUNT number of peers" +msgstr "" -#: src/testing/testing.c:1448 -#, fuzzy, c-format -msgid "Setting d->dead on peer `%4s'\n" -msgstr "Startade samling \"%s\".\n" +#: src/testbed/gnunet-testbed-profiler.c:264 +msgid "tolerate COUNT number of continious timeout failures" +msgstr "" -#: src/testing/testing.c:1601 -msgid "Peer not yet running, can not change configuration at this point." +#: src/testbed/gnunet-testbed-profiler.c:276 +msgid "Profiler for testbed" msgstr "" -#: src/testing/testing.c:1609 -#, fuzzy -msgid "Failed to write new configuration to disk." -msgstr "Kunde inte spara konfiguration!" +#: src/testbed/ll_master.c:57 +#, fuzzy, c-format +msgid "Job command file not given. Exiting\n" +msgstr "använd konfigurationsfil FILNAMN" -#: src/testing/testing.c:1636 +#: src/testbed/testbed_api.c:499 #, fuzzy, c-format -msgid "Could not start `%s' process to copy configuration file.\n" -msgstr "Kunde inte skapa värdnyckel!\n" +msgid "Adding host %u failed with error: %s\n" +msgstr "\"%s\" misslyckades vid %s:%d med fel: %s\n" -#: src/testing/testing.c:1639 -#, fuzzy -msgid "Failed to copy new configuration to remote machine." -msgstr "Kunde inte spara konfiguration!" +#: src/testbed/testbed_api_hosts.c:306 +#, fuzzy, c-format +msgid "Hosts file %s not found\n" +msgstr "\"%s\" misslyckades: tabell hittades inte!\n" -#: src/testing/testing.c:1794 -#, fuzzy -msgid "Peers failed to connect" -msgstr "Misslyckades att ansluta till gnunetd.\n" +#: src/testbed/testbed_api_hosts.c:314 +#, c-format +msgid "Hosts file %s has no data\n" +msgstr "" -#: src/testing/testing.c:1922 -#, fuzzy -msgid "Failed to connect to core service of first peer!\n" -msgstr "Misslyckades att starta samling.\n" +#: src/testbed/testbed_api_hosts.c:321 +#, c-format +msgid "Hosts file %s cannot be read\n" +msgstr "" -#: src/testing/testing.c:2145 -msgid "Peers are not fully running yet, can not connect!\n" +#: src/testbed/testbed_api_testbed.c:623 +msgid "Linking controllers failed. Exiting" msgstr "" -#: src/testing/testing_group.c:1895 src/testing/testing_group.c:1907 -#: src/testing/testing_group.c:2008 src/testing/testing_group.c:2065 -#: src/testing/testing_group.c:2152 src/testing/testing_group.c:2172 -#: src/testing/testing_group.c:2302 src/testing/testing_peergroup.c:950 +#: src/testbed/testbed_api_testbed.c:1009 +msgid "Cannot start the master controller" +msgstr "" + +#: src/testbed/testbed_api_testbed.c:1089 +msgid "Specified topology must be supported by testbed" +msgstr "" + +#: src/testbed/testbed_api_topology.c:668 #, fuzzy, c-format -msgid "Invalid value `%s' for option `%s' in section `%s': expected float\n" -msgstr "Konfigurationsfil \"%s\" hittades inte. Kör \"gnunet-setup -d\"!\n" +msgid "Topology file %s not found\n" +msgstr "\"%s\" misslyckades: tabell hittades inte!\n" -#: src/testing/testing_group.c:2160 +#: src/testbed/testbed_api_topology.c:674 #, c-format -msgid "" -"Invalid value `%s' for option `%s' in section `%s': got %f, needed value " -"greater than 0\n" +msgid "Topology file %s has no data\n" msgstr "" -#: src/testing/testing_group.c:2877 src/testing/testing_group.c:3063 +#: src/testbed/testbed_api_topology.c:681 #, c-format -msgid "" -"No `%s' specified in peer configuration in section `%s', cannot copy friends " -"file!\n" +msgid "Topology file %s cannot be read\n" msgstr "" -#: src/testing/testing_group.c:3957 -msgid "Creating no allowed topology (all peers can connect at core level)\n" +#: src/testbed/testbed_api_topology.c:704 +#, fuzzy, c-format +msgid "Failed to read peer index from toology file: %s" +msgstr "Kunde inte tolka konfigurationsfil \"%s\".\n" + +#: src/testbed/testbed_api_topology.c:713 +#: src/testbed/testbed_api_topology.c:737 +#, c-format +msgid "Value in given topology file: %s out of range\n" msgstr "" -#: src/testing/testing_group.c:5226 -msgid "Unknown topology specification, can't connect peers!\n" +#: src/testbed/testbed_api_topology.c:719 +#: src/testbed/testbed_api_topology.c:743 +#, fuzzy, c-format +msgid "Failed to read peer index from topology file: %s" +msgstr "Kunde inte tolka konfigurationsfil \"%s\".\n" + +#: src/testbed/testbed_api_topology.c:725 +#: src/testbed/testbed_api_topology.c:749 +msgid "Topology file needs more peers than given ones\n" msgstr "" -#: src/testing/testing_group.c:5944 src/transport/transport-testing.c:636 -#, fuzzy -msgid "Could not read hostkeys file!\n" -msgstr "Kunde inte skapa värdnyckel!\n" +#: src/testbed/testbed_api_topology.c:764 +#, fuzzy, c-format +msgid "Ignoring to connect peer %u to peer %u\n" +msgstr "Kan inte ansluta till %u.%u.%u.%u:%u: %s\n" -#: src/testing/testing_group.c:6011 +#: src/testing/gnunet-testing.c:132 #, fuzzy, c-format -msgid "Could not create configuration for peer number %u on `%s'!\n" -msgstr "Kunde inte komma åt namnrymdsinformation.\n" +msgid "Could not extract hostkey %u (offset too large?)\n" +msgstr "Kunde inte skapa värdnyckel!\n" + +#: src/testing/gnunet-testing.c:203 +#, fuzzy +msgid "create unique configuration files" +msgstr "skriv ut ett värde från konfigurationsfilen till standard ut" + +#: src/testing/gnunet-testing.c:205 +msgid "extract hostkey file from pre-computed hostkey list" +msgstr "" + +#: src/testing/gnunet-testing.c:207 +#, fuzzy +msgid "" +"number of unique configuration files to create, or number of the hostkey to " +"extract" +msgstr "skriv ut ett värde från konfigurationsfilen till standard ut" -#: src/testing/testing_new.c:169 -msgid "tmppath cannot be NULL\n" +#: src/testing/gnunet-testing.c:209 +#, fuzzy +msgid "configuration template" +msgstr "Konfigurationsfil \"%s\" skapad.\n" + +#: src/testing/gnunet-testing.c:218 +msgid "Command line tool to access the testing library" msgstr "" -#: src/testing/testing_new.c:356 +#: src/testing/gnunet-testing-run-service.c:129 #, c-format -msgid "Hostkeys file not found: %s\n" +msgid "Unknown command, use 'q' to quit or 'r' to restart peer\n" msgstr "" -#: src/testing/testing_new.c:365 -#, fuzzy, c-format -msgid "Could not open hostkeys file: %s\n" -msgstr "Kunde inte skapa värdnyckel!\n" +#: src/testing/gnunet-testing-run-service.c:186 +#, fuzzy +msgid "name of the template configuration file to use (optional)" +msgstr "skriv ut ett värde från konfigurationsfilen till standard ut" + +#: src/testing/gnunet-testing-run-service.c:189 +msgid "name of the service to run" +msgstr "" -#: src/testing/testing_new.c:380 +#: src/testing/testing.c:211 +#, c-format +msgid "Hostkeys file not found: %s\n" +msgstr "" + +#: src/testing/testing.c:227 #, c-format msgid "Incorrect hostkey file format: %s\n" msgstr "" -#: src/testing/testing_new.c:437 +#: src/testing/testing.c:541 #, fuzzy, c-format msgid "Key number %u does not exist\n" msgstr "antal meddelanden att använda per iteration" -#: src/testing/testing_new.c:446 +#: src/testing/testing.c:551 #, fuzzy, c-format msgid "Error while decoding key %u\n" msgstr "Fel vid nedladdning: %s\n" -#: src/testing/testing_new.c:680 +#: src/testing/testing.c:865 #, fuzzy msgid "Failed to create configuration for peer (not enough free ports?)\n" msgstr "Kunde inte komma åt namnrymdsinformation.\n" -#: src/testing/testing_new.c:691 +#: src/testing/testing.c:876 #, c-format msgid "" "You attempted to create a testbed with more than %u hosts. Please " "precompute more hostkeys first.\n" msgstr "" -#: src/testing/testing_new.c:704 +#: src/testing/testing.c:890 #, fuzzy, c-format msgid "Failed to initialize hostkey for peer %u\n" msgstr "Misslyckades att initiera tjänsten \"%s\".\n" -#: src/testing/testing_new.c:734 +#: src/testing/testing.c:923 #, fuzzy, c-format msgid "Failed to write hostkey file for peer %u: %s\n" msgstr "Kunde inte skapa användarkonto:" -#: src/testing/testing_new.c:751 +#: src/testing/testing.c:941 #, fuzzy, c-format msgid "Failed to write configuration file `%s' for peer %u: %s\n" msgstr "Kunde inte spara konfigurationsfil \"%s\":" -#: src/testing/testing_new.c:791 +#: src/testing/testing.c:1014 #, fuzzy, c-format msgid "Failed to start `%s': %s\n" msgstr "Fel vid %s:%d.\n" -#: src/testing/testing_new.c:959 +#: src/testing/testing.c:1219 #, fuzzy, c-format msgid "Failed to load configuration from %s\n" msgstr "Kunde inte spara konfigurationsfil \"%s\":" -#: src/topology/gnunet-daemon-topology.c:259 +#: src/topology/gnunet-daemon-topology.c:254 msgid "# peers blacklisted" msgstr "" -#: src/topology/gnunet-daemon-topology.c:392 +#: src/topology/gnunet-daemon-topology.c:387 #, fuzzy msgid "# connect requests issued to transport" msgstr "# byte mottogs via TCP" -#: src/topology/gnunet-daemon-topology.c:730 -#: src/topology/gnunet-daemon-topology.c:815 +#: src/topology/gnunet-daemon-topology.c:725 +#: src/topology/gnunet-daemon-topology.c:810 #, fuzzy msgid "# friends connected" msgstr "# av anslutna parter" -#: src/topology/gnunet-daemon-topology.c:996 +#: src/topology/gnunet-daemon-topology.c:991 msgid "Failed to connect to core service, can not manage topology!\n" msgstr "" -#: src/topology/gnunet-daemon-topology.c:1026 -#, c-format -msgid "Option `%s' in section `%s' not specified!\n" -msgstr "" - -#: src/topology/gnunet-daemon-topology.c:1039 +#: src/topology/gnunet-daemon-topology.c:1034 #, fuzzy, c-format msgid "Could not read friends list `%s'\n" msgstr "Misslyckades att läsa kompislista från \"%s\"\n" -#: src/topology/gnunet-daemon-topology.c:1045 +#: src/topology/gnunet-daemon-topology.c:1040 #, c-format msgid "Friends file `%s' is empty.\n" msgstr "" -#: src/topology/gnunet-daemon-topology.c:1054 +#: src/topology/gnunet-daemon-topology.c:1049 #, fuzzy, c-format msgid "Failed to read friends list from `%s': out of memory\n" msgstr "Misslyckades att läsa kompislista från \"%s\"\n" -#: src/topology/gnunet-daemon-topology.c:1062 +#: src/topology/gnunet-daemon-topology.c:1057 #, c-format msgid "Failed to read friends list from `%s'\n" msgstr "Misslyckades att läsa kompislista från \"%s\"\n" -#: src/topology/gnunet-daemon-topology.c:1082 +#: src/topology/gnunet-daemon-topology.c:1077 #, c-format msgid "" "Syntax error in topology specification at offset %llu, skipping bytes.\n" msgstr "" -#: src/topology/gnunet-daemon-topology.c:1095 +#: src/topology/gnunet-daemon-topology.c:1090 #, c-format msgid "" "Syntax error in topology specification at offset %llu, skipping bytes `%s'.\n" msgstr "" -#: src/topology/gnunet-daemon-topology.c:1105 +#: src/topology/gnunet-daemon-topology.c:1100 #, fuzzy, c-format msgid "Found friend `%s' in configuration\n" msgstr " gconfig\tGTK-konfiguration\n" -#: src/topology/gnunet-daemon-topology.c:1111 +#: src/topology/gnunet-daemon-topology.c:1106 #, c-format msgid "Found myself `%s' in friend list (useless, ignored)\n" msgstr "" -#: src/topology/gnunet-daemon-topology.c:1121 +#: src/topology/gnunet-daemon-topology.c:1116 #, fuzzy msgid "# friends in configuration" msgstr " gconfig\tGTK-konfiguration\n" -#: src/topology/gnunet-daemon-topology.c:1127 +#: src/topology/gnunet-daemon-topology.c:1122 msgid "" "Fewer friends specified than required by minimum friend count. Will only " "connect to friends.\n" msgstr "" -#: src/topology/gnunet-daemon-topology.c:1134 +#: src/topology/gnunet-daemon-topology.c:1129 msgid "" "More friendly connections required than target total number of connections.\n" msgstr "" -#: src/topology/gnunet-daemon-topology.c:1169 +#: src/topology/gnunet-daemon-topology.c:1164 #, fuzzy msgid "# HELLO messages received" msgstr "# krypterade PONG-meddelanden mottagna" -#: src/topology/gnunet-daemon-topology.c:1224 +#: src/topology/gnunet-daemon-topology.c:1219 msgid "# HELLO messages gossipped" msgstr "" -#: src/topology/gnunet-daemon-topology.c:1363 +#: src/topology/gnunet-daemon-topology.c:1358 msgid "GNUnet topology control (maintaining P2P mesh and F2F constraints)" msgstr "" @@ -4517,11 +4899,6 @@ msgstr "" msgid "Could not read blacklist file `%s'\n" msgstr "Misslyckades att läsa kompislista från \"%s\"\n" -#: src/transport/gnunet-service-transport_blacklist.c:252 -#, c-format -msgid "Blacklist file `%s' is empty.\n" -msgstr "" - #: src/transport/gnunet-service-transport_blacklist.c:263 #, fuzzy, c-format msgid "Failed to read blacklist from `%s'\n" @@ -4550,169 +4927,175 @@ msgid "Found myself `%s' in blacklist (useless, ignored)\n" msgstr "" #: src/transport/gnunet-service-transport_blacklist.c:514 -#: src/transport/gnunet-service-transport_blacklist.c:747 +#: src/transport/gnunet-service-transport_blacklist.c:752 msgid "# disconnects due to blacklist" msgstr "" -#: src/transport/gnunet-service-transport.c:163 +#: src/transport/gnunet-service-transport.c:183 #, fuzzy msgid "# bytes payload discarded due to not connected peer " msgstr "Nätverksannonsering avstängd i konfigurationen!\n" -#: src/transport/gnunet-service-transport.c:237 +#: src/transport/gnunet-service-transport.c:258 #, fuzzy msgid "# bytes total received" msgstr "# byte krypterade" -#: src/transport/gnunet-service-transport.c:284 +#: src/transport/gnunet-service-transport.c:305 #, fuzzy msgid "# bytes payload received" msgstr "# byte dekrypterade" -#: src/transport/gnunet-service-transport.c:582 -msgid "Transport service is lacking key configuration settings. Exiting.\n" -msgstr "" +#: src/transport/gnunet-service-transport.c:614 +#, fuzzy, c-format +msgid "Transport service could not access hostkey: %s. Exiting.\n" +msgstr "Kunde inte komma åt namnrymdsinformation.\n" + +#: src/transport/gnunet-service-transport.c:625 +#, fuzzy +msgid "Could not access STATISTICS service. Exiting.\n" +msgstr "Kunde inte komma åt namnrymdsinformation.\n" -#: src/transport/gnunet-service-transport.c:591 -msgid "Transport service could not access hostkey. Exiting.\n" +#: src/transport/gnunet-service-transport.c:720 +msgid "Transport service is lacking key configuration settings. Exiting.\n" msgstr "" -#: src/transport/gnunet-service-transport_clients.c:352 +#: src/transport/gnunet-service-transport_clients.c:389 #, c-format msgid "Dropping message of type %u and size %u, have %u/%u messages pending\n" msgstr "" -#: src/transport/gnunet-service-transport_clients.c:357 +#: src/transport/gnunet-service-transport_clients.c:394 msgid "# messages dropped due to slow client" msgstr "" -#: src/transport/gnunet-service-transport_clients.c:503 +#: src/transport/gnunet-service-transport_clients.c:546 #, c-format msgid "Rejecting control connection from peer `%s', which is not me!\n" msgstr "" -#: src/transport/gnunet-service-transport_clients.c:631 +#: src/transport/gnunet-service-transport_clients.c:687 msgid "# bytes payload dropped (other peer was not connected)" msgstr "" -#: src/transport/gnunet-service-transport_clients.c:682 +#: src/transport/gnunet-service-transport_clients.c:738 #, fuzzy msgid "# REQUEST CONNECT messages received" msgstr "# krypterade PONG-meddelanden mottagna" -#: src/transport/gnunet-service-transport_hello.c:172 +#: src/transport/gnunet-service-transport_hello.c:175 msgid "# refreshed my HELLO" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:1032 +#: src/transport/gnunet-service-transport_neighbours.c:1227 #, fuzzy msgid "# DISCONNECT messages sent" msgstr "# krypterade PONG-meddelanden mottagna" -#: src/transport/gnunet-service-transport_neighbours.c:1148 -#: src/transport/gnunet-service-transport_neighbours.c:1482 +#: src/transport/gnunet-service-transport_neighbours.c:1357 +#: src/transport/gnunet-service-transport_neighbours.c:1694 msgid "# bytes in message queue for other peers" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:1153 +#: src/transport/gnunet-service-transport_neighbours.c:1362 #, fuzzy msgid "# messages transmitted to other peers" msgstr "# byte skickade av typen %d" -#: src/transport/gnunet-service-transport_neighbours.c:1158 +#: src/transport/gnunet-service-transport_neighbours.c:1367 #, fuzzy msgid "# transmission failures for messages to other peers" msgstr "# byte skickade av typen %d" -#: src/transport/gnunet-service-transport_neighbours.c:1215 +#: src/transport/gnunet-service-transport_neighbours.c:1424 msgid "# messages timed out while in transport queue" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:1254 +#: src/transport/gnunet-service-transport_neighbours.c:1466 #, fuzzy msgid "# keepalives sent" msgstr "# sessionsnycklar skickade" -#: src/transport/gnunet-service-transport_neighbours.c:1278 +#: src/transport/gnunet-service-transport_neighbours.c:1490 #, fuzzy msgid "# KEEPALIVE messages discarded (peer unknown)" msgstr "Nätverksannonsering avstängd i konfigurationen!\n" -#: src/transport/gnunet-service-transport_neighbours.c:1286 +#: src/transport/gnunet-service-transport_neighbours.c:1498 #, fuzzy msgid "# KEEPALIVE messages discarded (no session)" msgstr "Nätverksannonsering avstängd i konfigurationen!\n" -#: src/transport/gnunet-service-transport_neighbours.c:1323 +#: src/transport/gnunet-service-transport_neighbours.c:1535 #, fuzzy msgid "# KEEPALIVE_RESPONSE messages discarded (not connected)" msgstr "Nätverksannonsering avstängd i konfigurationen!\n" -#: src/transport/gnunet-service-transport_neighbours.c:1332 +#: src/transport/gnunet-service-transport_neighbours.c:1544 #, fuzzy msgid "# KEEPALIVE_RESPONSE messages discarded (not expected)" msgstr "Nätverksannonsering avstängd i konfigurationen!\n" -#: src/transport/gnunet-service-transport_neighbours.c:1388 +#: src/transport/gnunet-service-transport_neighbours.c:1600 #, fuzzy msgid "# messages discarded due to lack of neighbour record" msgstr "Nätverksannonsering avstängd i konfigurationen!\n" -#: src/transport/gnunet-service-transport_neighbours.c:1422 +#: src/transport/gnunet-service-transport_neighbours.c:1634 msgid "# bandwidth quota violations by other peers" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:1438 +#: src/transport/gnunet-service-transport_neighbours.c:1650 msgid "# ms throttling suggested" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:2544 +#: src/transport/gnunet-service-transport_neighbours.c:2802 #, fuzzy msgid "# unexpected CONNECT_ACK messages (no peer)" msgstr "skicka ANTAL meddelanden" -#: src/transport/gnunet-service-transport_neighbours.c:2559 -#: src/transport/gnunet-service-transport_neighbours.c:2585 +#: src/transport/gnunet-service-transport_neighbours.c:2817 +#: src/transport/gnunet-service-transport_neighbours.c:2851 #, fuzzy msgid "# unexpected CONNECT_ACK messages (not ready)" msgstr "skicka ANTAL meddelanden" -#: src/transport/gnunet-service-transport_neighbours.c:2598 +#: src/transport/gnunet-service-transport_neighbours.c:2864 #, fuzzy msgid "# unexpected CONNECT_ACK messages (waiting on ATS)" msgstr "skicka ANTAL meddelanden" -#: src/transport/gnunet-service-transport_neighbours.c:2627 +#: src/transport/gnunet-service-transport_neighbours.c:2897 #, fuzzy msgid "# unexpected CONNECT_ACK messages (disconnecting)" msgstr "skicka ANTAL meddelanden" -#: src/transport/gnunet-service-transport_neighbours.c:2807 +#: src/transport/gnunet-service-transport_neighbours.c:3082 #, fuzzy msgid "# unexpected SESSION ACK messages" msgstr "# krypterade PONG-meddelanden skickade" -#: src/transport/gnunet-service-transport_neighbours.c:2856 +#: src/transport/gnunet-service-transport_neighbours.c:3137 msgid "# SET QUOTA messages ignored (no such peer)" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:2870 +#: src/transport/gnunet-service-transport_neighbours.c:3151 msgid "# disconnects due to quota of 0" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:2901 +#: src/transport/gnunet-service-transport_neighbours.c:3182 msgid "# disconnect messages ignored (old format)" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:2912 +#: src/transport/gnunet-service-transport_neighbours.c:3193 msgid "# disconnect messages ignored (timestamp)" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:2943 +#: src/transport/gnunet-service-transport_neighbours.c:3224 msgid "# other peer asked to disconnect from us" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:3020 +#: src/transport/gnunet-service-transport_neighbours.c:3319 #, fuzzy msgid "# disconnected from peer upon explicit request" msgstr "# av anslutna parter" @@ -4721,311 +5104,506 @@ msgstr "# av anslutna parter" msgid "Transport service is lacking NEIGHBOUR_LIMIT option.\n" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:414 +#: src/transport/gnunet-service-transport_validation.c:425 msgid "# address records discarded" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:463 +#: src/transport/gnunet-service-transport_validation.c:487 #, c-format msgid "" "Not transmitting `%s' with `%s', message too big (%u bytes!). This should " "not happen.\n" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:512 +#: src/transport/gnunet-service-transport_validation.c:536 #, fuzzy msgid "# PING without HELLO messages sent" msgstr "# PING-meddelanden i klartext skickade" -#: src/transport/gnunet-service-transport_validation.c:570 +#: src/transport/gnunet-service-transport_validation.c:618 msgid "# address revalidations started" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:805 +#: src/transport/gnunet-service-transport_validation.c:860 #, fuzzy msgid "# PING message for different peer received" msgstr "# PING-meddelanden skapade" -#: src/transport/gnunet-service-transport_validation.c:840 +#: src/transport/gnunet-service-transport_validation.c:925 #, c-format -msgid "" -"Not confirming PING with address `%s' since I cannot confirm having this " -"address.\n" +msgid "Received a PING message with validation bug from `%s'\n" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:924 +#: src/transport/gnunet-service-transport_validation.c:1054 msgid "# PONGs unicast via reliable transport" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:933 +#: src/transport/gnunet-service-transport_validation.c:1063 msgid "# PONGs multicast to all available addresses" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:1055 +#: src/transport/gnunet-service-transport_validation.c:1188 msgid "# PONGs dropped, no matching pending validation" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:1080 +#: src/transport/gnunet-service-transport_validation.c:1216 msgid "# PONGs dropped, signature expired" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:1136 +#: src/transport/gnunet-service-transport_validation.c:1270 #, fuzzy, c-format msgid "Adding `%s' without addresses for peer `%s'\n" msgstr "Motpart \"%s\" med pålitlighet %8u och adress \"%s\"\n" -#: src/transport/gnunet-transport.c:260 -msgid "No transport plugins configured, peer will never communicate\n" -msgstr "" +#: src/transport/gnunet-transport.c:266 +#, fuzzy, c-format +msgid "Transmitted %llu bytes/s (%llu bytes in %s)\n" +msgstr "Misslyckades att läsa kompislista från \"%s\"\n" #: src/transport/gnunet-transport.c:273 #, c-format -msgid "No port configured for plugin `%s', cannot test it\n" +msgid "Received %llu bytes/s (%llu bytes in %s)\n" msgstr "" -#: src/transport/gnunet-transport.c:323 -#, c-format -msgid "Received %llu bytes/s (%llu bytes in %llu ms)\n" +#: src/transport/gnunet-transport.c:303 +#, fuzzy, c-format +msgid "Failed to connect to `%s'\n" +msgstr "Misslyckades att ansluta till gnunetd.\n" + +#: src/transport/gnunet-transport.c:316 +#, fuzzy, c-format +msgid "Failed to resolve address for peer `%s'\n" +msgstr "Misslyckades att binda till UDP-port %d.\n" + +#: src/transport/gnunet-transport.c:325 +#, fuzzy +msgid "Failed to list connections, timeout occured\n" +msgstr "Misslyckades att ansluta till gnunetd.\n" + +#: src/transport/gnunet-transport.c:429 +msgid "No transport plugins configured, peer will never communicate\n" msgstr "" -#: src/transport/gnunet-transport.c:330 +#: src/transport/gnunet-transport.c:442 #, c-format -msgid "Transmitted %llu bytes/s (%llu bytes in %llu ms)\n" +msgid "No port configured for plugin `%s', cannot test it\n" msgstr "" -#: src/transport/gnunet-transport.c:363 +#: src/transport/gnunet-transport.c:506 #, fuzzy, c-format msgid "Transmitting %u bytes to %s\n" msgstr "Misslyckades att läsa kompislista från \"%s\"\n" -#: src/transport/gnunet-transport.c:383 +#: src/transport/gnunet-transport.c:531 #, fuzzy, c-format -msgid "Connected to %s\n" -msgstr "\"%s\" ansluten till \"%s\".\n" +msgid "Successfully connected to `%s'\n" +msgstr "Åtkomst nekad för \"%s\" vid %s:%d.\n" + +#: src/transport/gnunet-transport.c:553 +#, c-format +msgid "" +"Successfully connected to `%s', starting to send benchmark data in %u Kb " +"blocks\n" +msgstr "" -#: src/transport/gnunet-transport.c:414 +#: src/transport/gnunet-transport.c:588 #, fuzzy, c-format -msgid "Disconnected from %s\n" +msgid "Disconnected from peer `%s' while benchmarking\n" msgstr "\"%s\" ansluten till \"%s\".\n" -#: src/transport/gnunet-transport.c:443 +#: src/transport/gnunet-transport.c:664 #, c-format msgid "Received %u bytes from %s\n" msgstr "" -#: src/transport/gnunet-transport.c:466 +#: src/transport/gnunet-transport.c:687 #, fuzzy, c-format msgid "Peer `%s': %s %s\n" msgstr "Jag är ändpunkt \"%s\".\n" -#: src/transport/gnunet-transport.c:473 +#: src/transport/gnunet-transport.c:702 #, c-format msgid "Peer `%s': %s \n" msgstr "" -#: src/transport/gnunet-transport.c:501 +#: src/transport/gnunet-transport.c:766 #, fuzzy, c-format msgid "Peer `%s' disconnected\n" msgstr "# av anslutna parter" -#: src/transport/gnunet-transport.c:569 -#, fuzzy, c-format -msgid "Failed to parse peer identity `%s'\n" -msgstr "Misslyckades att läsa kompislista från \"%s\"\n" +#: src/transport/gnunet-transport.c:794 +#, fuzzy +msgid "Failed to send connect request to transport service\n" +msgstr "Misslyckades att ansluta till gnunetd.\n" + +#: src/transport/gnunet-transport.c:828 +#, c-format +msgid "" +"Multiple operations given. Please choose only one operation: %s, %s, %s, %s, " +"%s, %s\n" +msgstr "" -#: src/transport/gnunet-transport.c:618 -msgid "measure how fast we are receiving data (until CTRL-C)" +#: src/transport/gnunet-transport.c:834 +#, c-format +msgid "" +"No operation given. Please choose one operation: %s, %s, %s, %s, %s, %s\n" msgstr "" -#: src/transport/gnunet-transport.c:621 +#: src/transport/gnunet-transport.c:854 src/transport/gnunet-transport.c:884 +#: src/transport/gnunet-transport.c:906 src/transport/gnunet-transport.c:945 #, fuzzy -msgid "try to connect to the given peer" +msgid "Failed to connect to transport service\n" msgstr "Misslyckades att ansluta till gnunetd.\n" -#: src/transport/gnunet-transport.c:624 +#: src/transport/gnunet-transport.c:861 src/transport/gnunet-transport.c:891 +#, fuzzy +msgid "Failed to send request to transport service\n" +msgstr "Misslyckades att ansluta till gnunetd.\n" + +#: src/transport/gnunet-transport.c:911 +msgid "Starting to receive benchmark data\n" +msgstr "" + +#: src/transport/gnunet-transport.c:996 +msgid "measure how fast we are receiving data from all peers (until CTRL-C)" +msgstr "" + +#: src/transport/gnunet-transport.c:999 +#, fuzzy +msgid "connect to a peer" +msgstr "Misslyckades att ansluta till gnunetd.\n" + +#: src/transport/gnunet-transport.c:1002 #, fuzzy msgid "provide information about all current connections (once)" msgstr "Skriv ut information om GNUnets motparter." -#: src/transport/gnunet-transport.c:627 +#: src/transport/gnunet-transport.c:1008 #, fuzzy -msgid "provide information about all current connections (continuously)" +msgid "" +"provide information about all connects and disconnect events (continuously)" msgstr "Skriv ut information om GNUnets motparter." -#: src/transport/gnunet-transport.c:630 +#: src/transport/gnunet-transport.c:1011 #, fuzzy msgid "do not resolve hostnames" msgstr "Misslyckades att läsa kompislista från \"%s\"\n" -#: src/transport/gnunet-transport.c:634 +#: src/transport/gnunet-transport.c:1014 +msgid "peer identity" +msgstr "" + +#: src/transport/gnunet-transport.c:1018 msgid "send data for benchmarking to the other peer (until CTRL-C)" msgstr "" -#: src/transport/gnunet-transport.c:637 +#: src/transport/gnunet-transport.c:1021 msgid "test transport configuration (involves external server)" msgstr "" -#: src/transport/gnunet-transport.c:645 +#: src/transport/gnunet-transport.c:1032 #, fuzzy msgid "Direct access to transport service." msgstr "Misslyckades att ansluta till gnunetd.\n" -#: src/transport/plugin_transport_http.c:1100 +#: src/transport/plugin_transport_http.c:817 +#: src/transport/plugin_transport_http_server.c:2556 msgid "Disabling IPv6 since it is not supported on this system!\n" msgstr "" -#: src/transport/plugin_transport_http.c:1149 +#: src/transport/plugin_transport_http.c:866 +#: src/transport/plugin_transport_http_server.c:2324 #, fuzzy msgid "Require valid port number for service in configuration!\n" msgstr "Inga applikationer definierade i konfiguration!\n" -#: src/transport/plugin_transport_http.c:1174 src/util/service.c:1036 +#: src/transport/plugin_transport_http.c:898 +#: src/transport/plugin_transport_http_server.c:2356 src/util/service.c:1053 #, fuzzy, c-format msgid "Failed to resolve `%s': %s\n" msgstr "Misslyckades att leverera \"%s\" meddelande.\n" -#: src/transport/plugin_transport_http.c:1191 src/util/service.c:1053 +#: src/transport/plugin_transport_http.c:915 +#: src/transport/plugin_transport_http_server.c:2373 src/util/service.c:1070 #, fuzzy, c-format msgid "Failed to find %saddress for `%s'.\n" msgstr "Misslyckades att binda till UDP-port %d.\n" -#: src/transport/plugin_transport_http.c:1296 +#: src/transport/plugin_transport_http.c:1020 +#: src/transport/plugin_transport_http_server.c:2484 #, c-format msgid "Found %u addresses to report to NAT service\n" msgstr "" -#: src/transport/plugin_transport_http.c:1309 -#, c-format -msgid "FREEING %s\n" -msgstr "" - -#: src/transport/plugin_transport_http.c:1386 +#: src/transport/plugin_transport_http.c:1133 +#: src/transport/plugin_transport_http_server.c:2652 msgid "Neither IPv4 nor IPv6 are enabled! Fix in configuration\n" msgstr "" -#: src/transport/plugin_transport_http.c:1399 +#: src/transport/plugin_transport_http.c:1146 +#: src/transport/plugin_transport_http_server.c:2663 #, fuzzy msgid "Port is required! Fix in configuration\n" msgstr " gconfig\tGTK-konfiguration\n" -#: src/transport/plugin_transport_http.c:1410 +#: src/transport/plugin_transport_http.c:1157 msgid "Port 0, client only mode\n" msgstr "" -#: src/transport/plugin_transport_http.c:1430 +#: src/transport/plugin_transport_http.c:1177 #, c-format msgid "" "Specific IPv4 address `%s' for plugin %s in configuration file is invalid! " "Binding to all addresses!\n" msgstr "" -#: src/transport/plugin_transport_http.c:1460 +#: src/transport/plugin_transport_http.c:1206 #, c-format msgid "" "Specific IPv6 address `%s' for plugin %s in configuration file is invalid! " "Binding to all addresses!\n" msgstr "" -#: src/transport/plugin_transport_http_client.c:624 +#: src/transport/plugin_transport_http.c:1223 +#: src/transport/plugin_transport_http_server.c:2745 +#, fuzzy, c-format +msgid "Using external hostname `%s'\n" +msgstr "Startade samling \"%s\".\n" + +#: src/transport/plugin_transport_http.c:1228 +msgid "No external hostname configured\n" +msgstr "" + +#: src/transport/plugin_transport_http_client.c:1516 #, c-format msgid "Could not initialize curl multi handle, failed to start %s plugin!\n" msgstr "" -#: src/transport/plugin_transport_http_server.c:178 +#: src/transport/plugin_transport_http_client.c:1647 +#: src/transport/plugin_transport_http_server.c:2869 +#, fuzzy, c-format +msgid "Shutting down plugin `%s'\n" +msgstr "Testar transport(er) %s\n" + +#: src/transport/plugin_transport_http_client.c:1672 +#: src/transport/plugin_transport_http_server.c:2928 +#, fuzzy, c-format +msgid "Shutdown for plugin `%s' complete\n" +msgstr "" +"Uppladdning av \"%s\" klar, aktuell genomsnittshastighet är %8.3f kbps.\n" + +#: src/transport/plugin_transport_http_client.c:1700 +#: src/transport/plugin_transport_http_server.c:2775 +#, fuzzy, c-format +msgid "Maximum number of connections is %u\n" +msgstr "Maximalt antal chattklienter uppnått.\n" + +#: src/transport/plugin_transport_http_server.c:1342 +#, c-format +msgid "" +"Access from connection %p (%u of %u) for `%s' `%s' url `%s' with upload data " +"size %u\n" +msgstr "" + +#: src/transport/plugin_transport_http_server.c:1603 +#, c-format +msgid "Accepting connection (%u of %u) from `%s'\n" +msgstr "" + +#: src/transport/plugin_transport_http_server.c:1611 +#, c-format +msgid "" +"Server reached maximum number connections (%u), rejecting new connection\n" +msgstr "" + +#: src/transport/plugin_transport_http_server.c:1912 msgid "" "Could not create a new TLS certificate, program `gnunet-transport-" "certificate-creation' could not be started!\n" msgstr "" -#: src/transport/plugin_transport_http_server.c:202 +#: src/transport/plugin_transport_http_server.c:1936 msgid "No usable TLS certificate found and creating one failed!\n" msgstr "" -#: src/transport/plugin_transport_tcp.c:591 +#: src/transport/plugin_transport_http_server.c:2631 +#, c-format +msgid "IPv4 support is %s\n" +msgstr "" + +#: src/transport/plugin_transport_http_server.c:2645 +#, c-format +msgid "IPv6 support is %s\n" +msgstr "" + +#: src/transport/plugin_transport_http_server.c:2670 +#, fuzzy, c-format +msgid "Using port %u\n" +msgstr "Testar transport(er) %s\n" + +#: src/transport/plugin_transport_http_server.c:2685 +#, fuzzy, c-format +msgid "Specific IPv4 address `%s' in configuration file is invalid!\n" +msgstr "" +"Du måste ange ett positivt nummer för \"%s\" i konfigurationen i sektion \"%s" +"\".\n" + +#: src/transport/plugin_transport_http_server.c:2695 +#, fuzzy, c-format +msgid "Binding to IPv4 address %s\n" +msgstr "Ogiltigt svar på \"%s\".\n" + +#: src/transport/plugin_transport_http_server.c:2716 +#, fuzzy, c-format +msgid "Specific IPv6 address `%s' in configuration file is invalid!\n" +msgstr "" +"Du måste ange ett positivt nummer för \"%s\" i konfigurationen i sektion \"%s" +"\".\n" + +#: src/transport/plugin_transport_http_server.c:2726 +#, fuzzy, c-format +msgid "Binding to IPv6 address %s\n" +msgstr "Ogiltigt svar på \"%s\".\n" + +#: src/transport/plugin_transport_http_server.c:2761 +#, fuzzy, c-format +msgid "Notifying transport only about hostname `%s'\n" +msgstr "Misslyckades att läsa kompislista från \"%s\"\n" + +#: src/transport/plugin_transport_smtp.c:370 +#, fuzzy, c-format +msgid "Received malformed message via %s. Ignored.\n" +msgstr "Mottog ogiltigt \"%s\" meddelande från \"%s\".\n" + +# capped är inte ett bra ord IMHO +#: src/transport/plugin_transport_smtp.c:457 +#, fuzzy +msgid "SMTP filter string to invalid, lacks ': '\n" +msgstr "SMTP-filtersträng för lång, kapad till \"%s\"\n" + +# capped är inte ett bra ord IMHO +#: src/transport/plugin_transport_smtp.c:466 +#, c-format +msgid "SMTP filter string to long, capped to `%s'\n" +msgstr "SMTP-filtersträng för lång, kapad till \"%s\"\n" + +#: src/transport/plugin_transport_smtp.c:561 +#: src/transport/plugin_transport_smtp.c:571 +#: src/transport/plugin_transport_smtp.c:584 +#: src/transport/plugin_transport_smtp.c:603 +#: src/transport/plugin_transport_smtp.c:626 +#: src/transport/plugin_transport_smtp.c:634 +#: src/transport/plugin_transport_smtp.c:647 +#: src/transport/plugin_transport_smtp.c:658 +#, fuzzy, c-format +msgid "SMTP: `%s' failed: %s.\n" +msgstr "\"%s\" %s misslyckades: %s\n" + +#: src/transport/plugin_transport_smtp.c:799 +msgid "No email-address specified, can not start SMTP transport.\n" +msgstr "" + +#: src/transport/plugin_transport_smtp.c:811 +#, fuzzy +msgid "# bytes received via SMTP" +msgstr "# byte mottogs via TCP" + +#: src/transport/plugin_transport_smtp.c:812 +#, fuzzy +msgid "# bytes sent via SMTP" +msgstr "# byte skickades via TCP" + +#: src/transport/plugin_transport_smtp.c:814 +#, fuzzy +msgid "# bytes dropped by SMTP (outgoing)" +msgstr "# byte kastade via TCP (utgående)" + +#: src/transport/plugin_transport_tcp.c:595 #, c-format msgid "Unexpected address length: %u bytes\n" msgstr "" -#: src/transport/plugin_transport_tcp.c:767 -#: src/transport/plugin_transport_tcp.c:856 -#: src/transport/plugin_transport_tcp.c:906 -#: src/transport/plugin_transport_tcp.c:992 -#: src/transport/plugin_transport_tcp.c:1086 -#: src/transport/plugin_transport_tcp.c:1103 +#: src/transport/plugin_transport_tcp.c:771 +#: src/transport/plugin_transport_tcp.c:860 +#: src/transport/plugin_transport_tcp.c:910 +#: src/transport/plugin_transport_tcp.c:996 +#: src/transport/plugin_transport_tcp.c:1139 +#: src/transport/plugin_transport_tcp.c:1156 #, fuzzy msgid "# bytes currently in TCP buffers" msgstr "# byte skickades via TCP" -#: src/transport/plugin_transport_tcp.c:774 -#: src/transport/plugin_transport_tcp.c:963 -#: src/transport/plugin_transport_tcp.c:1761 -#: src/transport/plugin_transport_tcp.c:2390 +#: src/transport/plugin_transport_tcp.c:778 +#: src/transport/plugin_transport_tcp.c:967 +#: src/transport/plugin_transport_tcp.c:1826 +#: src/transport/plugin_transport_tcp.c:2462 #, fuzzy msgid "# TCP sessions active" msgstr "# sessionsnycklar accepterade" -#: src/transport/plugin_transport_tcp.c:860 +#: src/transport/plugin_transport_tcp.c:864 #, fuzzy msgid "# bytes discarded by TCP (timeout)" msgstr "# byte kastade via TCP (utgående)" -#: src/transport/plugin_transport_tcp.c:909 +#: src/transport/plugin_transport_tcp.c:913 #, fuzzy msgid "# bytes transmitted via TCP" msgstr "# byte skickade av typen %d" -#: src/transport/plugin_transport_tcp.c:996 +#: src/transport/plugin_transport_tcp.c:1000 #, fuzzy msgid "# bytes discarded by TCP (disconnect)" msgstr "# byte kastade via TCP (utgående)" -#: src/transport/plugin_transport_tcp.c:1290 +#: src/transport/plugin_transport_tcp.c:1113 +#, c-format +msgid "Trying to send with invalid session %p\n" +msgstr "" + +#: src/transport/plugin_transport_tcp.c:1349 #, c-format msgid "Address of unexpected length: %u\n" msgstr "" -#: src/transport/plugin_transport_tcp.c:1401 +#: src/transport/plugin_transport_tcp.c:1466 msgid "# transport-service disconnect requests for TCP" msgstr "" -#: src/transport/plugin_transport_tcp.c:1802 +#: src/transport/plugin_transport_tcp.c:1867 #, fuzzy msgid "# TCP WELCOME messages received" msgstr "# krypterade PONG-meddelanden mottagna" -#: src/transport/plugin_transport_tcp.c:1973 +#: src/transport/plugin_transport_tcp.c:2046 msgid "# bytes received via TCP" msgstr "# byte mottogs via TCP" -#: src/transport/plugin_transport_tcp.c:2043 +#: src/transport/plugin_transport_tcp.c:2124 msgid "# network-level TCP disconnect events" msgstr "" -#: src/transport/plugin_transport_tcp.c:2279 src/util/service.c:940 +#: src/transport/plugin_transport_tcp.c:2350 src/util/service.c:948 +#: src/util/service.c:954 #, c-format msgid "Require valid port number for service `%s' in configuration!\n" msgstr "" -#: src/transport/plugin_transport_tcp.c:2293 +#: src/transport/plugin_transport_tcp.c:2364 #, fuzzy msgid "Failed to start service.\n" msgstr "Misslyckades att starta samling.\n" -#: src/transport/plugin_transport_tcp.c:2355 -#, fuzzy, c-format -msgid "Failed to find option %s in section %s!\n" -msgstr "Misslyckades att binda till UDP-port %d.\n" - -#: src/transport/plugin_transport_tcp.c:2378 +#: src/transport/plugin_transport_tcp.c:2450 #, c-format msgid "TCP transport listening on port %llu\n" msgstr "" -#: src/transport/plugin_transport_tcp.c:2382 +#: src/transport/plugin_transport_tcp.c:2454 msgid "TCP transport not listening on any port (client only)\n" msgstr "" -#: src/transport/plugin_transport_tcp.c:2386 +#: src/transport/plugin_transport_tcp.c:2458 #, c-format msgid "TCP transport advertises itself as being on port %llu\n" msgstr "" @@ -5040,129 +5618,132 @@ msgstr "# krypterade PONG-meddelanden mottagna" msgid "# IPv4 broadcast HELLO beacons received via udp" msgstr "# krypterade PONG-meddelanden mottagna" -#: src/transport/plugin_transport_udp_broadcasting.c:367 +#: src/transport/plugin_transport_udp_broadcasting.c:394 #, c-format msgid "Failed to set IPv4 broadcast option for broadcast socket on port %d\n" msgstr "" -#: src/transport/plugin_transport_udp.c:1894 +#: src/transport/plugin_transport_udp.c:2517 #, c-format msgid "" -"UDP could not message to `%s': `%s'. Please check your network configuration " -"and disable IPv6 if your connection does not have a global IPv6 address\n" +"UDP could not transmit message to `%s': Network seems down, please check " +"your network configuration\n" msgstr "" -#: src/transport/plugin_transport_udp.c:2138 +#: src/transport/plugin_transport_udp.c:2531 +#, c-format +msgid "" +"UDP could not transmit message to `%s': Please check your network " +"configuration and disable IPv6 if your connection does not have a global " +"IPv6 address\n" +msgstr "" + +#: src/transport/plugin_transport_udp.c:2772 #, fuzzy msgid "Failed to open UDP sockets\n" msgstr "Misslyckades att binda till UDP6-port %d.\n" -#: src/transport/plugin_transport_udp.c:2306 +#: src/transport/plugin_transport_udp.c:2848 #, c-format msgid "Given `%s' option is out of range: %llu > %u\n" msgstr "" -#: src/transport/plugin_transport_udp.c:2349 +#: src/transport/plugin_transport_udp.c:2891 #, fuzzy, c-format msgid "Invalid IPv6 address: `%s'\n" msgstr "Ogiltigt svar på \"%s\".\n" -#: src/transport/plugin_transport_unix.c:1356 +#: src/transport/plugin_transport_unix.c:1357 #, fuzzy msgid "Failed to open UNIX sockets\n" msgstr "Misslyckades att leverera \"%s\" meddelande.\n" -#: src/transport/plugin_transport_wlan.c:561 +#: src/transport/plugin_transport_wlan.c:580 msgid "# WLAN ACKs sent" msgstr "" -#: src/transport/plugin_transport_wlan.c:580 +#: src/transport/plugin_transport_wlan.c:599 #, fuzzy msgid "# WLAN messages defragmented" msgstr "# PING-meddelanden skapade" -#: src/transport/plugin_transport_wlan.c:626 -#: src/transport/plugin_transport_wlan.c:676 -#: src/transport/plugin_transport_wlan.c:1696 +#: src/transport/plugin_transport_wlan.c:645 +#: src/transport/plugin_transport_wlan.c:695 +#: src/transport/plugin_transport_wlan.c:1758 #, fuzzy msgid "# WLAN sessions allocated" msgstr "# sessionsnycklar accepterade" -#: src/transport/plugin_transport_wlan.c:749 +#: src/transport/plugin_transport_wlan.c:770 #, fuzzy msgid "# WLAN message fragments sent" msgstr "# byte mottogs via TCP" -#: src/transport/plugin_transport_wlan.c:767 +#: src/transport/plugin_transport_wlan.c:794 msgid "# WLAN messages pending (with fragmentation)" msgstr "" -#: src/transport/plugin_transport_wlan.c:867 -#: src/transport/plugin_transport_wlan.c:948 -#: src/transport/plugin_transport_wlan.c:1698 +#: src/transport/plugin_transport_wlan.c:902 +#: src/transport/plugin_transport_wlan.c:987 +#: src/transport/plugin_transport_wlan.c:1760 #, fuzzy msgid "# WLAN MAC endpoints allocated" msgstr "# byte mottogs via TCP" -#: src/transport/plugin_transport_wlan.c:1119 +#: src/transport/plugin_transport_wlan.c:1169 #, fuzzy msgid "# HELLO messages received via WLAN" msgstr "# krypterade PONG-meddelanden mottagna" -#: src/transport/plugin_transport_wlan.c:1140 +#: src/transport/plugin_transport_wlan.c:1190 #, fuzzy msgid "# fragments received via WLAN" msgstr "# byte mottogs via TCP" -#: src/transport/plugin_transport_wlan.c:1150 +#: src/transport/plugin_transport_wlan.c:1200 #, fuzzy msgid "# ACKs received via WLAN" msgstr "# byte mottogs via TCP" -#: src/transport/plugin_transport_wlan.c:1207 +#: src/transport/plugin_transport_wlan.c:1257 #, fuzzy msgid "# WLAN DATA messages discarded due to CRC32 error" msgstr "Nätverksannonsering avstängd i konfigurationen!\n" -#: src/transport/plugin_transport_wlan.c:1306 +#: src/transport/plugin_transport_wlan.c:1358 #, fuzzy msgid "# DATA messages received via WLAN" msgstr "# krypterade PONG-meddelanden mottagna" -#: src/transport/plugin_transport_wlan.c:1341 +#: src/transport/plugin_transport_wlan.c:1393 #, fuzzy msgid "# WLAN DATA messages processed" msgstr "# krypterade PONG-meddelanden mottagna" -#: src/transport/plugin_transport_wlan.c:1402 +#: src/transport/plugin_transport_wlan.c:1454 #, fuzzy msgid "# HELLO beacons sent via WLAN" msgstr "# byte skickade via UDP" -#: src/transport/plugin_transport_wlan.c:1511 +#: src/transport/plugin_transport_wlan.c:1563 msgid "WLAN address with invalid size encountered\n" msgstr "" -#: src/transport/plugin_transport_wlan.c:1668 -#, fuzzy, c-format -msgid "Invalid configuration option `%s' in section `%s'\n" -msgstr "Konfigurationsfil \"%s\" skapad.\n" - -#: src/transport/plugin_transport_wlan.c:1677 +#: src/transport/plugin_transport_wlan.c:1739 #, c-format msgid "Helper binary `%s' not SUID, cannot run WLAN transport\n" msgstr "" -#: src/transport/plugin_transport_wlan.c:1687 -#, fuzzy, c-format -msgid "Missing configuration option `%s' in section `%s'\n" -msgstr "Konfigurationsfil \"%s\" skapad.\n" - -#: src/transport/transport_api.c:570 +#: src/transport/transport_api.c:659 #, fuzzy, c-format msgid "Received unexpected message of type %u in %s:%u\n" msgstr "Mottog skadat meddelande från motpart \"%s\"i %s:%d.\n" +#: src/transport/transport-testing.c:586 +#, fuzzy +msgid "Failed to initialize testing library!\n" +msgstr "Misslyckades att initiera tjänsten \"%s\".\n" + #: src/util/bio.c:136 src/util/bio.c:142 #, fuzzy, c-format msgid "Error reading `%s': %s" @@ -5193,261 +5774,312 @@ msgstr "" msgid "Metadata `%s' failed to deserialize" msgstr "" -#: src/util/client.c:359 +#: src/util/client.c:276 src/util/client.c:753 src/util/service.c:984 +#, c-format +msgid "UNIXPATH `%s' too long, maximum length is %llu\n" +msgstr "" + +#: src/util/client.c:280 src/util/client.c:757 src/util/service.c:988 +#, fuzzy, c-format +msgid "Using `%s' instead\n" +msgstr "%s: flagga \"%s\" är tvetydig\n" + +#: src/util/client.c:371 #, c-format msgid "" "Could not determine valid hostname and port for service `%s' from " "configuration.\n" msgstr "" -#: src/util/client.c:367 +#: src/util/client.c:379 #, c-format msgid "Need a non-empty hostname for service `%s'.\n" msgstr "" -#: src/util/client.c:685 +#: src/util/client.c:698 msgid "Failure to transmit TEST request.\n" msgstr "" -#: src/util/client.c:740 src/util/service.c:970 -#, c-format -msgid "UNIXPATH `%s' too long, maximum length is %llu\n" -msgstr "" - -#: src/util/client.c:882 +#: src/util/client.c:898 #, fuzzy, c-format msgid "Could not connect to service `%s', must not be running.\n" msgstr "Kunde inte ansluta till gnunetd.\n" -#: src/util/client.c:896 +#: src/util/client.c:912 #, fuzzy, c-format msgid "Failure to transmit request to service `%s'\n" msgstr "Misslyckades att skicka HTTP-begäran till värd \"%s\": %s\n" -#: src/util/client.c:1149 +#: src/util/client.c:1177 msgid "Could not submit request, not expecting to receive a response.\n" msgstr "" -#: src/util/common_logging.c:239 src/util/common_logging.c:890 +#: src/util/common_logging.c:258 src/util/common_logging.c:1007 msgid "DEBUG" msgstr "FELSÖKNING" -#: src/util/common_logging.c:241 src/util/common_logging.c:888 +#: src/util/common_logging.c:260 src/util/common_logging.c:1005 msgid "INFO" msgstr "INFO" -#: src/util/common_logging.c:243 src/util/common_logging.c:886 +#: src/util/common_logging.c:262 src/util/common_logging.c:1003 msgid "WARNING" msgstr "VARNING" -#: src/util/common_logging.c:245 src/util/common_logging.c:884 +#: src/util/common_logging.c:264 src/util/common_logging.c:1001 msgid "ERROR" msgstr "FEL" -#: src/util/common_logging.c:247 src/util/common_logging.c:892 +#: src/util/common_logging.c:266 src/util/common_logging.c:1009 msgid "NONE" msgstr "" -#: src/util/common_logging.c:610 +#: src/util/common_logging.c:395 #, fuzzy, c-format msgid "Failed to create or access directory for log file `%s'\n" msgstr "Kunde inte tolka konfigurationsfil \"%s\".\n" -#: src/util/common_logging.c:725 +#: src/util/common_logging.c:819 #, c-format msgid "Message `%.*s' repeated %u times in the last %s\n" msgstr "" -#: src/util/common_logging.c:893 +#: src/util/common_logging.c:1010 msgid "INVALID" msgstr "" -#: src/util/common_logging.c:992 +#: src/util/common_logging.c:1149 msgid "unknown address" msgstr "" -#: src/util/common_logging.c:1030 +#: src/util/common_logging.c:1187 msgid "invalid address" msgstr "" -#: src/util/configuration.c:244 +#: src/util/common_logging.c:1205 #, fuzzy, c-format -msgid "Syntax error in configuration file `%s' at line %u.\n" +msgid "Configuration fails to specify option `%s' in section `%s'!\n" +msgstr "Konfigurationsfil \"%s\" skapad.\n" + +#: src/util/common_logging.c:1226 +#, fuzzy, c-format +msgid "" +"Configuration specifies invalid value for option `%s' in section `%s': %s\n" +msgstr "Konfigurationsfil \"%s\" hittades inte. Kör \"gnunet-setup -d\"!\n" + +#: src/util/configuration.c:291 +#, fuzzy, c-format +msgid "Syntax error while deserializing in line %u\n" msgstr "Syntaxfel i konfigurationsfil \"%s\" på rad %d.\n" -#: src/util/configuration.c:816 +#: src/util/configuration.c:998 #, c-format msgid "" "Configuration value '%s' for '%s' in section '%s' is not in set of legal " "choices\n" msgstr "" -#: src/util/connection.c:420 +#: src/util/connection.c:427 #, fuzzy, c-format msgid "Access denied to `%s'\n" msgstr "Åtkomst nekad för \"%s\" vid %s:%d.\n" -#: src/util/connection.c:435 +#: src/util/connection.c:442 #, c-format msgid "Accepting connection from `%s': %p\n" msgstr "" -#: src/util/connection.c:550 +#: src/util/connection.c:557 #, fuzzy, c-format msgid "" "Failed to establish TCP connection to `%s:%u', no further addresses to try.\n" msgstr "Misslyckades att starta samling.\n" -#: src/util/connection.c:739 src/util/connection.c:909 +#: src/util/connection.c:755 src/util/connection.c:922 #, fuzzy, c-format msgid "Trying to connect to `%s' (%p)\n" msgstr "Kan inte ansluta till %u.%u.%u.%u:%u: %s\n" -#: src/util/connection.c:748 -#, fuzzy, c-format -msgid "Failed to connect to `%s' (%p)\n" -msgstr "Kan inte ansluta till %u.%u.%u.%u:%u: %s\n" - -#: src/util/connection.c:900 +#: src/util/connection.c:913 #, fuzzy, c-format msgid "Attempt to connect to `%s' failed\n" msgstr " Anslutning misslyckades\n" -#: src/util/container_bloomfilter.c:510 +#: src/util/container_bloomfilter.c:518 #, c-format msgid "" "Size of file on disk is incorrect for this Bloom filter (want %llu, have " "%llu)\n" msgstr "" -#: src/util/crypto_random.c:280 -#, c-format -msgid "Starting `%s' process to generate entropy\n" -msgstr "" +#: src/util/crypto_ecc.c:441 +#, fuzzy, c-format +msgid "" +"File `%s' does not contain a valid private key (too long, %llu bytes). " +"Deleting it.\n" +msgstr "Filen \"%s\" innehåller ingen pseudonym.\n" -#: src/util/crypto_random.c:309 -#, c-format -msgid "libgcrypt has not the expected version (version %s is required).\n" -msgstr "libgcrypt har inte den förväntande versionen (version %s krävs).\n" +#: src/util/crypto_ecc.c:456 src/util/crypto_rsa.c:660 +#, fuzzy, c-format +msgid "" +"File `%s' does not contain a valid private key (failed decode, %llu bytes). " +"Deleting it.\n" +msgstr "Filen \"%s\" innehåller ingen pseudonym.\n" -#: src/util/crypto_rsa.c:661 src/util/crypto_rsa.c:708 +#: src/util/crypto_ecc.c:552 src/util/crypto_ecc.c:596 +#: src/util/crypto_rsa.c:757 src/util/crypto_rsa.c:801 #, fuzzy, c-format -msgid "Could not aquire lock on file `%s': %s...\n" +msgid "Could not acquire lock on file `%s': %s...\n" msgstr "Kunde inte slå upp \"%s\": %s\n" -#: src/util/crypto_rsa.c:666 +#: src/util/crypto_ecc.c:557 src/util/crypto_rsa.c:762 #, fuzzy msgid "Creating a new private key. This may take a while.\n" msgstr "Skapar ny värdnyckel (det här kan ta en stund).\n" -#: src/util/crypto_rsa.c:684 -#, c-format -msgid "I am host `%s'. Stored new private key in `%s'.\n" -msgstr "" - -#: src/util/crypto_rsa.c:712 src/util/crypto_rsa.c:748 -msgid "This may be ok if someone is currently generating a hostkey.\n" +#: src/util/crypto_ecc.c:600 src/util/crypto_rsa.c:805 +#: src/util/crypto_rsa.c:841 +msgid "This may be ok if someone is currently generating a private key.\n" msgstr "" -#: src/util/crypto_rsa.c:743 +#: src/util/crypto_ecc.c:631 src/util/crypto_rsa.c:836 #, c-format msgid "" -"When trying to read hostkey file `%s' I found %u bytes but I need at least " -"%u.\n" +"When trying to read key file `%s' I found %u bytes but I need at least %u.\n" msgstr "" -#: src/util/crypto_rsa.c:763 +#: src/util/crypto_ecc.c:636 +msgid "This may be ok if someone is currently generating a key.\n" +msgstr "" + +#: src/util/crypto_ecc.c:651 src/util/crypto_rsa.c:856 #, fuzzy, c-format msgid "File `%s' does not contain a valid private key. Deleting it.\n" msgstr "Filen \"%s\" innehåller ingen pseudonym.\n" -#: src/util/crypto_rsa.c:781 +#: src/util/crypto_ecc.c:773 src/util/crypto_rsa.c:941 +msgid "interrupted by shutdown" +msgstr "" + +#: src/util/crypto_ecc.c:784 +#, fuzzy +msgid "gnunet-ecc failed" +msgstr "gnunet-update misslyckades!" + +#: src/util/crypto_ecc.c:979 #, fuzzy, c-format -msgid "I am host `%s'. Read private key from `%s'.\n" -msgstr "Anrop till \"%s\" med nyckel \"%s\".\n" +msgid "ECC signing failed at %s:%d: %s\n" +msgstr "\"%s\" misslyckades vid %s:%d med fel: \"%s\".\n" + +#: src/util/crypto_ecc.c:1047 +#, fuzzy, c-format +msgid "ECC signature verification failed at %s:%d: %s\n" +msgstr "\"%s\" misslyckades vid %s:%d med fel: \"%s\".\n" + +#: src/util/crypto_random.c:313 +#, c-format +msgid "Starting `%s' process to generate entropy\n" +msgstr "" -#: src/util/crypto_rsa.c:1032 +#: src/util/crypto_random.c:342 +#, c-format +msgid "libgcrypt has not the expected version (version %s is required).\n" +msgstr "libgcrypt har inte den förväntande versionen (version %s krävs).\n" + +#: src/util/crypto_rsa.c:644 +#, fuzzy, c-format +msgid "" +"File `%s' does not contain a valid private key (too long, %llu bytes). " +"Renaming it.\n" +msgstr "Filen \"%s\" innehåller ingen pseudonym.\n" + +#: src/util/crypto_rsa.c:952 +#, fuzzy +msgid "gnunet-rsa failed" +msgstr "gnunet-update misslyckades!" + +#: src/util/crypto_rsa.c:1343 #, c-format msgid "RSA signature verification failed at %s:%d: %s\n" msgstr "" # drive = hard drive ? -#: src/util/disk.c:498 +#: src/util/disk.c:601 #, fuzzy, c-format msgid "`%s' failed for drive `%S': %u\n" msgstr "\"%s\" misslyckades för enhet %s: %u\n" -#: src/util/disk.c:1062 +#: src/util/disk.c:1205 #, fuzzy, c-format msgid "Expected `%s' to be a directory!\n" msgstr "\"%s\" förväntade att \"%s\" skulle vara en katalog!\n" -#: src/util/disk.c:1416 src/util/service.c:1650 +#: src/util/disk.c:1559 src/util/service.c:1669 #, fuzzy, c-format msgid "Cannot obtain information about user `%s': %s\n" msgstr "Kan inte öppna konfigurationsfil \"%s\".\n" -#: src/util/disk.c:1734 +#: src/util/disk.c:1931 #, fuzzy, c-format msgid "No `%s' specified for service `%s' in configuration.\n" msgstr "Inga applikationer definierade i konfiguration!\n" -#: src/util/getopt.c:669 +#: src/util/getopt.c:570 #, c-format msgid "%s: option `%s' is ambiguous\n" msgstr "%s: flagga \"%s\" är tvetydig\n" -#: src/util/getopt.c:693 +#: src/util/getopt.c:594 #, c-format msgid "%s: option `--%s' does not allow an argument\n" msgstr "%s: flagga \"--%s\" tillåter inte ett argument\n" -#: src/util/getopt.c:698 +#: src/util/getopt.c:599 #, c-format msgid "%s: option `%c%s' does not allow an argument\n" msgstr "%s: flagga \"%c%s\" tillåter inte ett argument\n" -#: src/util/getopt.c:715 src/util/getopt.c:883 +#: src/util/getopt.c:616 src/util/getopt.c:783 #, c-format msgid "%s: option `%s' requires an argument\n" msgstr "%s: flagga \"%s\" kräver ett argument\n" -#: src/util/getopt.c:744 +#: src/util/getopt.c:645 #, c-format msgid "%s: unrecognized option `--%s'\n" msgstr "%s: okänd flagga \"--%s\"\n" -#: src/util/getopt.c:748 +#: src/util/getopt.c:649 #, c-format msgid "%s: unrecognized option `%c%s'\n" msgstr "%s: okänd flagga \"%c%s\"\n" -#: src/util/getopt.c:773 +#: src/util/getopt.c:674 #, c-format msgid "%s: illegal option -- %c\n" msgstr "%s: otillåten flagga -- %c\n" -#: src/util/getopt.c:775 +#: src/util/getopt.c:676 #, c-format msgid "%s: invalid option -- %c\n" msgstr "%s: ogiltig flagga -- %c\n" -#: src/util/getopt.c:803 src/util/getopt.c:931 +#: src/util/getopt.c:704 src/util/getopt.c:831 #, c-format msgid "%s: option requires an argument -- %c\n" msgstr "%s: flagga kräver ett argument -- %c\n" -#: src/util/getopt.c:851 +#: src/util/getopt.c:752 #, c-format msgid "%s: option `-W %s' is ambiguous\n" msgstr "%s: flagga \"-W %s\" är tvetydig\n" -#: src/util/getopt.c:869 +#: src/util/getopt.c:770 #, c-format msgid "%s: option `-W %s' does not allow an argument\n" msgstr "%s: flagga \"-W %s\" tillåter inte ett argument\n" -#: src/util/getopt.c:1035 +#: src/util/getopt.c:935 #, fuzzy, c-format msgid "Use %s to get a list of options.\n" msgstr "Använd --help för att få en lista på flaggor.\n" @@ -5460,37 +6092,111 @@ msgstr "" "Argument som är obligatoriska för långa flaggor är också obligatoriska för " "korta flaggor.\n" -#: src/util/getopt_helpers.c:258 src/util/getopt_helpers.c:286 +#: src/util/getopt_helpers.c:258 src/util/getopt_helpers.c:316 #, c-format msgid "You must pass a number to the `%s' option.\n" msgstr "Du måste skicka med ett nummer till flaggan \"%s\".\n" -#: src/util/gnunet-resolver.c:148 -msgid "perform a reverse lookup" +#: src/util/getopt_helpers.c:288 +#, fuzzy, c-format +msgid "You must pass relative time to the `%s' option.\n" +msgstr "Du måste skicka med ett nummer till flaggan \"%s\".\n" + +#: src/util/gnunet-config.c:90 +#, c-format +msgid "--section argument is required\n" msgstr "" -#: src/util/gnunet-resolver.c:154 -msgid "Use build-in GNUnet stub resolver" +#: src/util/gnunet-config.c:133 +#, c-format +msgid "--option argument required to set value\n" +msgstr "" + +#: src/util/gnunet-config.c:160 +msgid "obtain option of value as a filename (with $-expansion)" +msgstr "" + +#: src/util/gnunet-config.c:163 +msgid "name of the section to access" +msgstr "" + +#: src/util/gnunet-config.c:166 +#, fuzzy +msgid "name of the option to access" +msgstr "Visa värde av alternativet" + +#: src/util/gnunet-config.c:169 +msgid "value to set" +msgstr "" + +#: src/util/gnunet-config.c:178 +#, fuzzy +msgid "Manipulate GNUnet configuration files" +msgstr "skriv ut ett värde från konfigurationsfilen till standard ut" + +#: src/util/gnunet-ecc.c:107 src/util/gnunet-rsa.c:107 +#, fuzzy, c-format +msgid "Failed to open `%s': %s\n" +msgstr "Misslyckades att leverera \"%s\" meddelande.\n" + +#: src/util/gnunet-ecc.c:113 src/util/gnunet-rsa.c:113 +#, c-format +msgid "Generating %u keys, please wait" msgstr "" -#: src/util/gnunet-rsa.c:64 +#: src/util/gnunet-ecc.c:128 src/util/gnunet-rsa.c:137 +#, fuzzy, c-format +msgid "" +"\n" +"Failed to write to `%s': %s\n" +msgstr "Fel vid %s:%d.\n" + +#: src/util/gnunet-ecc.c:140 src/util/gnunet-rsa.c:149 +#, fuzzy, c-format +msgid "Finished!\n" +msgstr "Slutför" + +#: src/util/gnunet-ecc.c:163 src/util/gnunet-rsa.c:172 #, c-format msgid "No hostkey file specified on command line\n" msgstr "" -#: src/util/gnunet-rsa.c:112 +#: src/util/gnunet-ecc.c:220 src/util/gnunet-rsa.c:229 +msgid "create COUNT public-private key pairs (for testing)" +msgstr "" + +#: src/util/gnunet-ecc.c:223 src/util/gnunet-rsa.c:232 msgid "print the public key in ASCII format" msgstr "" -#: src/util/gnunet-rsa.c:115 +#: src/util/gnunet-ecc.c:226 src/util/gnunet-rsa.c:235 msgid "print the hash of the public key in ASCII format" msgstr "" -#: src/util/gnunet-rsa.c:118 +#: src/util/gnunet-ecc.c:229 src/util/gnunet-rsa.c:238 msgid "print the short hash of the public key in ASCII format" msgstr "" -#: src/util/gnunet-rsa.c:124 +#: src/util/gnunet-ecc.c:232 src/util/gnunet-rsa.c:241 +msgid "" +"use insecure, weak random number generator for key generation (for testing " +"only)" +msgstr "" + +#: src/util/gnunet-ecc.c:243 +#, fuzzy +msgid "Manipulate GNUnet private ECC key files" +msgstr "skriv ut ett värde från konfigurationsfilen till standard ut" + +#: src/util/gnunet-resolver.c:148 +msgid "perform a reverse lookup" +msgstr "" + +#: src/util/gnunet-resolver.c:159 +msgid "Use build-in GNUnet stub resolver" +msgstr "" + +#: src/util/gnunet-rsa.c:252 msgid "Manipulate GNUnet private RSA key files" msgstr "" @@ -5502,73 +6208,77 @@ msgstr "Kunde inte slå upp \"%s\": %s\n" #: src/util/gnunet-service-resolver.c:358 #: src/util/gnunet-service-resolver.c:399 #, c-format -msgid "Could not find IP of host `%s': %s\n" +msgid "Could not find IP of host `%s': %s\n" +msgstr "" + +#: src/util/gnunet-uri.c:90 +#, c-format +msgid "No URI specified on command line\n" msgstr "" -#: src/util/helper.c:244 +#: src/util/gnunet-uri.c:95 #, fuzzy, c-format -msgid "Error reading from `%s': %s\n" -msgstr "Fel vid skapandet av användare" +msgid "Invalid URI: does not start with `%s'\n" +msgstr "Ogiltig nätverksnotation (slutar inte med \";\": \"%s\")\n" -#: src/util/helper.c:259 +#: src/util/gnunet-uri.c:102 #, c-format -msgid "Got 0 bytes from helper `%s' (EOF)\n" +msgid "Invalid URI: fails to specify subsystem\n" msgstr "" -#: src/util/helper.c:269 +#: src/util/gnunet-uri.c:112 #, c-format -msgid "Got %u bytes from helper `%s'\n" +msgid "No handler known for subsystem `%s'\n" +msgstr "" + +#: src/util/gnunet-uri.c:174 +msgid "Perform default-actions for GNUnet URIs" msgstr "" -#: src/util/helper.c:278 +#: src/util/helper.c:260 #, fuzzy, c-format -msgid "Failed to parse inbound message from helper `%s'\n" -msgstr "Misslyckades att läsa kompislista från \"%s\"\n" +msgid "Error reading from `%s': %s\n" +msgstr "Fel vid skapandet av användare" -#: src/util/helper.c:310 +#: src/util/helper.c:305 #, fuzzy, c-format -msgid "Starting HELPER process `%s'\n" -msgstr "Startade samling \"%s\".\n" +msgid "Failed to parse inbound message from helper `%s'\n" +msgstr "Misslyckades att läsa kompislista från \"%s\"\n" -#: src/util/helper.c:440 +#: src/util/helper.c:499 #, fuzzy, c-format msgid "Error writing to `%s': %s\n" msgstr "Fel vid skapandet av användare" -#: src/util/network.c:1200 +#: src/util/network.c:127 +#, c-format +msgid "Unable to shorten unix path `%s' while keeping name unique\n" +msgstr "" + +#: src/util/network.c:1331 #, c-format msgid "" "Fatal internal logic error, process hangs in `%s' (abort with CTRL-C)!\n" msgstr "" -#: src/util/os_installation.c:299 +#: src/util/os_installation.c:420 #, c-format msgid "" "Could not determine installation path for %s. Set `%s' environment " "variable.\n" msgstr "" -#: src/util/os_installation.c:486 +#: src/util/os_installation.c:702 #, fuzzy, c-format msgid "Could not find binary `%s' in PATH!\n" msgstr "Kunde inte hitta motpart \"%s\" i routingtabell!\n" -#: src/util/os_installation.c:492 -#, fuzzy, c-format -msgid "access (%s, X_OK) failed: %s\n" -msgstr "\"%s\" %s misslyckades: %s\n" - -#: src/util/os_installation.c:507 -#, fuzzy, c-format -msgid "stat (%s) failed: %s\n" -msgstr "\"%s\" %s misslyckades: %s\n" - -#: src/util/os_priority.c:305 +#: src/util/os_priority.c:302 #, fuzzy, c-format msgid "Failed to open named pipe `%s' for reading: %s\n" msgstr "Misslyckades att leverera \"%s\" meddelande.\n" -#: src/util/os_priority.c:306 +#: src/util/os_priority.c:303 #, fuzzy, c-format msgid "Failed to open named pipe `%s' for writing: %s\n" msgstr "Misslyckades att leverera \"%s\" meddelande.\n" @@ -5593,12 +6303,17 @@ msgstr "\"%s\" misslyckades vid %s:%d med fel: %s\n" msgid "Could not determine plugin installation path.\n" msgstr "Kunde inte fastställa min publika IPv6-adress.\n" -#: src/util/pseudonym.c:276 +#: src/util/program.c:254 src/util/service.c:1791 +#, fuzzy, c-format +msgid "Could not access configuration file `%s'\n" +msgstr "Kunde inte tolka konfigurationsfil \"%s\".\n" + +#: src/util/pseudonym.c:282 #, fuzzy, c-format msgid "Failed to parse metadata about pseudonym from file `%s': %s\n" msgstr "Misslyckades att läsa kompislista från \"%s\"\n" -#: src/util/pseudonym.c:407 src/util/pseudonym.c:433 +#: src/util/pseudonym.c:413 src/util/pseudonym.c:439 #, fuzzy msgid "no-name" msgstr "Visa namn" @@ -5631,153 +6346,153 @@ msgstr "Misslyckades att läsa kompislista från \"%s\"\n" msgid "Could not resolve our FQDN : %s\n" msgstr "Kunde inte slå upp \"%s\": %s\n" -#: src/util/scheduler.c:786 +#: src/util/scheduler.c:782 msgid "Looks like we're busy waiting...\n" msgstr "" -#: src/util/scheduler.c:916 +#: src/util/scheduler.c:912 #, c-format msgid "Attempt to cancel dead task %llu!\n" msgstr "" # drive = hard drive ? -#: src/util/server.c:483 +#: src/util/server.c:426 #, fuzzy, c-format msgid "`%s' failed for port %d (%s).\n" msgstr "\"%s\" misslyckades för enhet %s: %u\n" -#: src/util/server.c:492 +#: src/util/server.c:435 #, fuzzy, c-format msgid "`%s' failed for port %d (%s): address already in use\n" msgstr "\"%s\" misslyckades för port %d: %s. Körs verkligen gnunetd?\n" -#: src/util/server.c:497 +#: src/util/server.c:446 #, fuzzy, c-format -msgid "`%s' failed for `%s': address already in use\n" +msgid "`%s' failed for `%.*s': address already in use\n" msgstr "\"%s\" misslyckades för port %d: %s. Körs verkligen gnunetd?\n" -#: src/util/server.c:827 +#: src/util/server.c:830 #, c-format msgid "" "Processing code for message of type %u did not call " -"GNUNET_SERVER_receive_done after %llums\n" +"`GNUNET_SERVER_receive_done' after %s\n" msgstr "" -#: src/util/service.c:135 src/util/service.c:161 src/util/service.c:204 -#: src/util/service.c:225 src/util/service.c:232 +#: src/util/service.c:142 src/util/service.c:168 src/util/service.c:211 +#: src/util/service.c:232 src/util/service.c:239 #, c-format msgid "Invalid format for IP: `%s'\n" msgstr "Ogiltigt format för IP: \"%s\"\n" -#: src/util/service.c:188 +#: src/util/service.c:195 #, c-format msgid "Invalid network notation ('/%d' is not legal in IPv4 CIDR)." msgstr "Ogiltig nätverksnotation (\"/%d\" är inte giltig i IPv4 CIDR)." -#: src/util/service.c:281 +#: src/util/service.c:288 #, c-format msgid "Invalid network notation (does not end with ';': `%s')\n" msgstr "Ogiltig nätverksnotation (slutar inte med \";\": \"%s\")\n" -#: src/util/service.c:313 +#: src/util/service.c:320 #, fuzzy, c-format msgid "Wrong format `%s' for netmask\n" msgstr "Fel format \"%s\" för nätmask: %s\n" -#: src/util/service.c:343 +#: src/util/service.c:350 #, fuzzy, c-format msgid "Wrong format `%s' for network\n" msgstr "Fel format \"%s\" för nätverk: %s\n" -#: src/util/service.c:698 +#: src/util/service.c:707 #, c-format msgid "Access denied to UID %d / GID %d\n" msgstr "" -#: src/util/service.c:703 +#: src/util/service.c:712 #, fuzzy, c-format msgid "Unknown address family %d\n" msgstr "Okänd operation \"%s\"\n" -#: src/util/service.c:710 +#: src/util/service.c:719 #, c-format msgid "Access from `%s' denied to service `%s'\n" msgstr "" -#: src/util/service.c:765 +#: src/util/service.c:774 #, c-format msgid "Could not parse IPv4 network specification `%s' for `%s:%s'\n" msgstr "" -#: src/util/service.c:802 +#: src/util/service.c:811 #, c-format msgid "Could not parse IPv6 network specification `%s' for `%s:%s'\n" msgstr "" -#: src/util/service.c:920 +#: src/util/service.c:929 #, c-format msgid "" "Disabling IPv6 support for service `%s', failed to create IPv6 socket: %s\n" msgstr "" -#: src/util/service.c:990 +#: src/util/service.c:1007 #, c-format msgid "" "Disabling UNIX domain socket support for service `%s', failed to create UNIX " "domain socket: %s\n" msgstr "" -#: src/util/service.c:1007 +#: src/util/service.c:1024 #, c-format msgid "Have neither PORT nor UNIXPATH for service `%s', but one is required\n" msgstr "" -#: src/util/service.c:1241 +#: src/util/service.c:1258 msgid "Could not access a pre-bound socket, will try to bind myself\n" msgstr "" -#: src/util/service.c:1292 src/util/service.c:1310 +#: src/util/service.c:1309 src/util/service.c:1327 #, c-format msgid "Specified value for `%s' of service `%s' is invalid\n" msgstr "" -#: src/util/service.c:1337 +#: src/util/service.c:1354 #, c-format msgid "Could not access pre-bound socket %u, will try to bind myself\n" msgstr "" -#: src/util/service.c:1506 +#: src/util/service.c:1525 #, fuzzy, c-format msgid "Failed to start `%s' at `%s'\n" msgstr "Fel vid %s:%d.\n" -#: src/util/service.c:1539 +#: src/util/service.c:1558 #, fuzzy, c-format msgid "Service `%s' runs at %s\n" msgstr "Motpart \"%s\" med pålitlighet %8u och adress \"%s\"\n" -#: src/util/service.c:1588 +#: src/util/service.c:1607 msgid "Service process failed to initialize\n" msgstr "" -#: src/util/service.c:1592 +#: src/util/service.c:1611 msgid "Service process could not initialize server function\n" msgstr "" -#: src/util/service.c:1596 +#: src/util/service.c:1615 msgid "Service process failed to report status\n" msgstr "" -#: src/util/service.c:1651 +#: src/util/service.c:1670 msgid "No such user" msgstr "" -#: src/util/service.c:1664 +#: src/util/service.c:1683 #, c-format msgid "Cannot change user/group to `%s': %s\n" msgstr "Kan inte ändra användare/grupp till \"%s\": %s\n" -#: src/util/service.c:1729 +#: src/util/service.c:1749 msgid "do daemonize (detach from terminal)" msgstr "" @@ -5786,74 +6501,84 @@ msgstr "" msgid "signal (%d, %p) returned %d.\n" msgstr "Anrop till \"%s\" returnerade %d.\n" -#: src/util/strings.c:144 +#: src/util/strings.c:146 msgid "b" msgstr "b" -#: src/util/strings.c:334 +#: src/util/strings.c:413 #, c-format msgid "Character sets requested were `%s'->`%s'\n" msgstr "" -#: src/util/strings.c:481 +#: src/util/strings.c:528 msgid "Failed to expand `$HOME': environment variable `HOME' not set" msgstr "" -#: src/util/strings.c:573 +#: src/util/strings.c:625 msgid "ms" msgstr "ms" -#: src/util/strings.c:578 -msgid "eternity" +#: src/util/strings.c:629 +msgid "forever" msgstr "" -#: src/util/strings.c:582 +#: src/util/strings.c:631 +msgid "0 ms" +msgstr "" + +#: src/util/strings.c:637 msgid "s" msgstr "s" -#: src/util/strings.c:586 +#: src/util/strings.c:643 msgid "m" msgstr "m" -#: src/util/strings.c:590 +#: src/util/strings.c:649 msgid "h" msgstr "h" -#: src/util/strings.c:594 -msgid " days" +#: src/util/strings.c:656 +#, fuzzy +msgid "day" +msgstr " dagar" + +#: src/util/strings.c:658 +#, fuzzy +msgid "days" msgstr " dagar" -#: src/util/strings.c:618 +#: src/util/strings.c:685 msgid "end of time" msgstr "" -#: src/util/strings.c:1012 +#: src/util/strings.c:1073 msgid "IPv6 address did not start with `['\n" msgstr "" -#: src/util/strings.c:1020 +#: src/util/strings.c:1081 msgid "IPv6 address did contain ':' to separate port number\n" msgstr "" -#: src/util/strings.c:1026 +#: src/util/strings.c:1087 msgid "IPv6 address did contain ']' before ':' to separate port number\n" msgstr "" -#: src/util/strings.c:1033 +#: src/util/strings.c:1094 msgid "IPv6 address did contain a valid port number after the last ':'\n" msgstr "" -#: src/util/strings.c:1042 +#: src/util/strings.c:1103 #, fuzzy, c-format msgid "Invalid IPv6 address `%s': %s\n" msgstr "Ogiltigt svar på \"%s\".\n" -#: src/vpn/gnunet-service-vpn.c:511 src/vpn/gnunet-service-vpn.c:1071 +#: src/vpn/gnunet-service-vpn.c:512 src/vpn/gnunet-service-vpn.c:1088 #, fuzzy msgid "# Active tunnels" msgstr "Nätverksanslutning" -#: src/vpn/gnunet-service-vpn.c:608 src/vpn/gnunet-service-vpn.c:645 +#: src/vpn/gnunet-service-vpn.c:609 src/vpn/gnunet-service-vpn.c:646 #, fuzzy msgid "# peers connected to mesh tunnels" msgstr "# av anslutna parter" @@ -5868,85 +6593,85 @@ msgstr "# PING-meddelanden skapade" msgid "# Bytes dropped in mesh queue (overflow)" msgstr "# byte kastade via UDP (utgående)" -#: src/vpn/gnunet-service-vpn.c:772 +#: src/vpn/gnunet-service-vpn.c:771 #, fuzzy msgid "# Mesh tunnels created" msgstr "# PING-meddelanden skapade" -#: src/vpn/gnunet-service-vpn.c:795 +#: src/vpn/gnunet-service-vpn.c:794 #, fuzzy msgid "Failed to setup mesh tunnel!\n" msgstr "Kunde inte skapa värdnyckel!\n" -#: src/vpn/gnunet-service-vpn.c:973 +#: src/vpn/gnunet-service-vpn.c:990 #, c-format msgid "Protocol %u not supported, dropping\n" msgstr "" -#: src/vpn/gnunet-service-vpn.c:1291 +#: src/vpn/gnunet-service-vpn.c:1308 msgid "# ICMPv4 packets dropped (not allowed)" msgstr "" -#: src/vpn/gnunet-service-vpn.c:1312 +#: src/vpn/gnunet-service-vpn.c:1329 msgid "# ICMPv6 packets dropped (not allowed)" msgstr "" -#: src/vpn/gnunet-service-vpn.c:1517 +#: src/vpn/gnunet-service-vpn.c:1534 #, fuzzy msgid "# Packets received from TUN interface" msgstr "Meddelande mottaget från klient är ogiltig.\n" -#: src/vpn/gnunet-service-vpn.c:1555 src/vpn/gnunet-service-vpn.c:1596 +#: src/vpn/gnunet-service-vpn.c:1572 src/vpn/gnunet-service-vpn.c:1613 #, c-format msgid "Packet received for unmapped destination `%s' (dropping it)\n" msgstr "" -#: src/vpn/gnunet-service-vpn.c:1606 +#: src/vpn/gnunet-service-vpn.c:1623 msgid "Received IPv4 packet with options (dropping it)\n" msgstr "" -#: src/vpn/gnunet-service-vpn.c:1620 +#: src/vpn/gnunet-service-vpn.c:1637 #, c-format msgid "Received packet of unknown protocol %d from TUN (dropping it)\n" msgstr "" -#: src/vpn/gnunet-service-vpn.c:1704 +#: src/vpn/gnunet-service-vpn.c:1721 #, fuzzy msgid "# ICMP packets received from mesh" msgstr "Meddelande mottaget från klient är ogiltig.\n" -#: src/vpn/gnunet-service-vpn.c:2045 +#: src/vpn/gnunet-service-vpn.c:2062 #, fuzzy msgid "# UDP packets received from mesh" msgstr "Meddelande mottaget från klient är ogiltig.\n" -#: src/vpn/gnunet-service-vpn.c:2203 +#: src/vpn/gnunet-service-vpn.c:2220 #, fuzzy msgid "# TCP packets received from mesh" msgstr "Meddelande mottaget från klient är ogiltig.\n" -#: src/vpn/gnunet-service-vpn.c:2354 +#: src/vpn/gnunet-service-vpn.c:2371 msgid "Failed to find unallocated IPv4 address in VPN's range\n" msgstr "" -#: src/vpn/gnunet-service-vpn.c:2409 +#: src/vpn/gnunet-service-vpn.c:2426 msgid "Failed to find unallocated IPv6 address in VPN's range\n" msgstr "" -#: src/vpn/gnunet-service-vpn.c:2448 src/vpn/gnunet-service-vpn.c:2661 +#: src/vpn/gnunet-service-vpn.c:2465 src/vpn/gnunet-service-vpn.c:2678 #, fuzzy msgid "# Active destinations" msgstr "Nätverksanslutning" -#: src/vpn/gnunet-service-vpn.c:2734 +#: src/vpn/gnunet-service-vpn.c:2751 msgid "Failed to allocate IP address for new destination\n" msgstr "" -#: src/vpn/gnunet-service-vpn.c:3141 +#: src/vpn/gnunet-service-vpn.c:3138 msgid "IPv6 support disabled as this system does not support IPv6\n" msgstr "" -#: src/vpn/gnunet-service-vpn.c:3173 +#: src/vpn/gnunet-service-vpn.c:3170 msgid "IPv4 support disabled as this system does not support IPv4\n" msgstr "" @@ -5955,117 +6680,388 @@ msgstr "" msgid "Error creating tunnel\n" msgstr "Klar med skapandet av värdnyckel.\n" -#: src/vpn/gnunet-vpn.c:195 src/vpn/gnunet-vpn.c:226 +#: src/vpn/gnunet-vpn.c:194 src/vpn/gnunet-vpn.c:225 #, fuzzy, c-format msgid "Option `%s' makes no sense with option `%s'.\n" msgstr "Kommando \"%s\" kräver ett argument (\"%s\").\n" -#: src/vpn/gnunet-vpn.c:208 +#: src/vpn/gnunet-vpn.c:207 #, fuzzy, c-format msgid "Option `%s' or `%s' is required.\n" msgstr "%s: flagga \"%s\" är tvetydig\n" -#: src/vpn/gnunet-vpn.c:220 +#: src/vpn/gnunet-vpn.c:219 #, fuzzy, c-format msgid "Option `%s' or `%s' is required when using option `%s'.\n" msgstr "Kommando \"%s\" kräver ett argument (\"%s\").\n" -#: src/vpn/gnunet-vpn.c:238 +#: src/vpn/gnunet-vpn.c:237 #, fuzzy, c-format msgid "`%s' is not a valid peer identifier.\n" msgstr "\"%s\" är inte en vanlig fil.\n" -#: src/vpn/gnunet-vpn.c:260 +#: src/vpn/gnunet-vpn.c:259 #, fuzzy, c-format msgid "`%s' is not a valid IP address.\n" msgstr "\"%s\" är inte tillgänglig." -#: src/vpn/gnunet-vpn.c:296 +#: src/vpn/gnunet-vpn.c:295 msgid "request that result should be an IPv4 address" msgstr "" -#: src/vpn/gnunet-vpn.c:299 +#: src/vpn/gnunet-vpn.c:298 msgid "request that result should be an IPv6 address" msgstr "" -#: src/vpn/gnunet-vpn.c:302 +#: src/vpn/gnunet-vpn.c:301 msgid "print IP address only after mesh tunnel has been created" msgstr "" -#: src/vpn/gnunet-vpn.c:305 +#: src/vpn/gnunet-vpn.c:304 msgid "how long should the mapping be valid for new tunnels?" msgstr "" -#: src/vpn/gnunet-vpn.c:308 +#: src/vpn/gnunet-vpn.c:307 msgid "destination IP for the tunnel" msgstr "" -#: src/vpn/gnunet-vpn.c:311 +#: src/vpn/gnunet-vpn.c:310 msgid "peer offering the service we would like to access" msgstr "" -#: src/vpn/gnunet-vpn.c:314 +#: src/vpn/gnunet-vpn.c:313 msgid "name of the service we would like to access" msgstr "" -#: src/vpn/gnunet-vpn.c:317 +#: src/vpn/gnunet-vpn.c:316 #, fuzzy msgid "service is offered via TCP" msgstr "# byte mottogs via TCP" -#: src/vpn/gnunet-vpn.c:320 +#: src/vpn/gnunet-vpn.c:319 #, fuzzy msgid "service is offered via UDP" msgstr "# byte mottagna via UDP" -#: src/vpn/gnunet-vpn.c:329 +#: src/vpn/gnunet-vpn.c:331 msgid "Setup tunnels via VPN." msgstr "" -#: src/include/gnunet_common.h:497 src/include/gnunet_common.h:502 -#: src/include/gnunet_common.h:508 +#: src/include/gnunet_common.h:579 src/include/gnunet_common.h:584 +#: src/include/gnunet_common.h:590 #, fuzzy, c-format msgid "Assertion failed at %s:%d.\n" msgstr "\"%s\" misslyckades vid %s:%d med fel: \"%s\".\n" -#: src/include/gnunet_common.h:518 +#: src/include/gnunet_common.h:600 #, c-format msgid "External protocol violation detected at %s:%d.\n" msgstr "" -#: src/include/gnunet_common.h:539 src/include/gnunet_common.h:546 +#: src/include/gnunet_common.h:621 src/include/gnunet_common.h:628 #, c-format msgid "`%s' failed on file `%s' at %s:%d with error: %s\n" msgstr "\"%s\" misslyckades för fil \"%s\" vid %s:%d med fel: %s\n" #, fuzzy -#~ msgid "Received malformed message via %s. Ignored.\n" -#~ msgstr "Mottog ogiltigt \"%s\" meddelande från \"%s\".\n" +#~ msgid "session identifier" +#~ msgstr "# sessioner etablerade" -# capped är inte ett bra ord IMHO #, fuzzy -#~ msgid "SMTP filter string to invalid, lacks ': '\n" -#~ msgstr "SMTP-filtersträng för lång, kapad till \"%s\"\n" +#~ msgid "Mesh service could not access hostkey. Exiting.\n" +#~ msgstr "Kunde inte komma åt namnrymdsinformation.\n" -# capped är inte ett bra ord IMHO -#~ msgid "SMTP filter string to long, capped to `%s'\n" -#~ msgstr "SMTP-filtersträng för lång, kapad till \"%s\"\n" +#, fuzzy +#~ msgid "" +#~ "provide inthe 'struct GNUNET_TRANSPORT_PeerIterateContextformation about " +#~ "all tunnels (continuously)" +#~ msgstr "Skriv ut information om GNUnets motparter." + +#, fuzzy +#~ msgid "Connected to %s\n" +#~ msgstr "\"%s\" ansluten till \"%s\".\n" + +#, fuzzy +#~ msgid "list information for all peers" +#~ msgstr "Skriv ut information om GNUnets motparter." + +#, fuzzy +#~ msgid "Malformed %s `%s' given in configuration!\n" +#~ msgstr "Kunde inte spara konfiguration!" + +#, fuzzy +#~ msgid "I am host `%s'. Read private key from `%s'.\n" +#~ msgstr "Anrop till \"%s\" med nyckel \"%s\".\n" + +#, fuzzy +#~ msgid "Starting HELPER process `%s'\n" +#~ msgstr "Startade samling \"%s\".\n" + +#, fuzzy +#~ msgid "Asked to start service `%s' within %llu ms\n" +#~ msgstr "\"%s\": Mottog inte meddelande inom %llu ms.\n" + +#, fuzzy +#~ msgid "Stopping service `%s' within %llu ms\n" +#~ msgstr "Inget svar mottaget inom %llums.\n" + +#, fuzzy +#~ msgid "Configuration file `%s' for service `%s' not valid: %s\n" +#~ msgstr "Konfigurationsfil \"%s\" skapad.\n" + +#, fuzzy +#~ msgid "Could not transmit confirmation receipt\n" +#~ msgstr "Kunde inte komma åt namnrymdsinformation.\n" + +#, fuzzy +#~ msgid "Unknown message type: '%u'\n" +#~ msgstr "Okänd operation \"%s\"\n" + +#, fuzzy +#~ msgid "Configuration option `%s' in section `%s' missing\n" +#~ msgstr "Konfigurationsfil \"%s\" skapad.\n" + +#, fuzzy +#~ msgid "Failed to access chat home directory `%s'\n" +#~ msgstr "Filformatsfel (inte en GNUnet-katalog?)\n" + +#, fuzzy +#~ msgid "Failed to create/open key in file `%s'\n" +#~ msgstr "Misslyckades att leverera \"%s\" meddelande.\n" #, fuzzy -#~ msgid "SMTP: `%s' failed: %s.\n" +#~ msgid "Could not serialize metadata\n" +#~ msgstr "Kunde inte initiera libgnunetutil!\n" + +#, fuzzy +#~ msgid "Failed to connect to the chat service\n" +#~ msgstr "Misslyckades att ansluta till gnunetd.\n" + +#, fuzzy +#~ msgid "(%s) `%s' said: %s\n" #~ msgstr "\"%s\" %s misslyckades: %s\n" #, fuzzy -#~ msgid "# bytes received via SMTP" -#~ msgstr "# byte mottogs via TCP" +#~ msgid "(%s) `%s' said to you: %s\n" +#~ msgstr "\"%s\" %s misslyckades: %s\n" + +# drive = hard drive ? +#, fuzzy +#~ msgid "(%s) `%s' said for sure: %s\n" +#~ msgstr "\"%s\" misslyckades för enhet %s: %u\n" +# drive = hard drive ? #, fuzzy -#~ msgid "# bytes sent via SMTP" -#~ msgstr "# byte skickades via TCP" +#~ msgid "(%s) `%s' said to you for sure: %s\n" +#~ msgstr "\"%s\" misslyckades för enhet %s: %u\n" #, fuzzy -#~ msgid "# bytes dropped by SMTP (outgoing)" -#~ msgstr "# byte kastade via TCP (utgående)" +#~ msgid "(%s) `%s' said off the record: %s\n" +#~ msgstr "\"%s\" misslyckades vid %s:%d med fel: %s\n" + +#, fuzzy +#~ msgid "Could not change username\n" +#~ msgstr "Kunde inte skapa namnrymd \"%s\" (existerar?).\n" + +#, fuzzy +#~ msgid "Joining room `%s' as user `%s'...\n" +#~ msgstr "Ogiltigt svar till \"%s\" från motpart \"%s\".\n" + +#, fuzzy +#~ msgid "Changed username to `%s'\n" +#~ msgstr "Kan inte ändra användare/grupp till \"%s\": %s\n" + +#, fuzzy +#~ msgid "Unknown command `%s'\n" +#~ msgstr "Okänd operation \"%s\"\n" + +#, fuzzy +#~ msgid "You must specify a nickname\n" +#~ msgstr "Du måste ange en mottagare!\n" + +#, fuzzy +#~ msgid "Failed to join room `%s'\n" +#~ msgstr "Misslyckades att läsa kompislista från \"%s\"\n" + +#, fuzzy +#~ msgid "Failed to queue a message notification\n" +#~ msgstr "Kunde inte spara konfiguration!" + +#, fuzzy +#~ msgid "Failed to queue a join notification\n" +#~ msgstr "Kunde inte spara konfiguration!" + +#, fuzzy +#~ msgid "Failed to queue a confirmation receipt\n" +#~ msgstr "Kunde inte spara konfiguration!" + +#, fuzzy +#~ msgid "Failed to queue a leave notification\n" +#~ msgstr "Kunde inte spara konfiguration!" + +#, fuzzy +#~ msgid "Option `%s' in section `%s' missing in configuration!\n" +#~ msgstr "Inga applikationer definierade i konfiguration!\n" + +#, fuzzy +#~ msgid "Connected to %s service!\n" +#~ msgstr "\"%s\" ansluten till \"%s\".\n" + +#, fuzzy +#~ msgid "Configuration fails to specify `%s' in section `%s'\n" +#~ msgstr "Konfigurationsfil \"%s\" skapad.\n" + +#, fuzzy +#~ msgid "Failed to start daemon: %s\n" +#~ msgstr "Misslyckades att starta samling.\n" + +#, fuzzy +#~ msgid "Configuration fails to specify `%s', assuming default value." +#~ msgstr "Konfigurationsfil \"%s\" skapad.\n" + +#, fuzzy +#~ msgid "Option `%s' not specified in configuration section `%s'\n" +#~ msgstr "Inga applikationer definierade i konfiguration!\n" + +#, fuzzy +#~ msgid "Peer is lacking HOSTKEY configuration setting.\n" +#~ msgstr "GNUnet-konfiguration" + +#, fuzzy +#~ msgid "Could not access hostkey.\n" +#~ msgstr "Kunde inte tolka konfigurationsfil \"%s\".\n" + +#, fuzzy +#~ msgid "`scp' did not complete cleanly.\n" +#~ msgstr "\"%s\" är inte ansluten till någon ändpunkt.\n" + +#, fuzzy +#~ msgid "Failed to create pipe for `gnunet-peerinfo' process.\n" +#~ msgstr "Misslyckades att starta samling.\n" + +#, fuzzy +#~ msgid "Failed to create pipe for `ssh' process.\n" +#~ msgstr "Misslyckades att läsa kompislista från \"%s\"\n" + +#, fuzzy +#~ msgid "Could not start `%s' process to create hostkey.\n" +#~ msgstr "Kunde inte skapa värdnyckel!\n" + +#, fuzzy +#~ msgid "Failed to start `gnunet-peerinfo' process.\n" +#~ msgstr "Misslyckades att starta samling.\n" + +#, fuzzy +#~ msgid "Failed to start `ssh' process.\n" +#~ msgstr "Misslyckades att starta samling.\n" + +#, fuzzy +#~ msgid "Malformed output from gnunet-peerinfo!\n" +#~ msgstr "Misslyckades att starta samling.\n" + +#, fuzzy +#~ msgid "Failed to get hostkey!\n" +#~ msgstr "Kunde inte skapa värdnyckel!\n" + +#, fuzzy +#~ msgid "Could not start `%s' process to start GNUnet.\n" +#~ msgstr "Kunde inte skapa värdnyckel!\n" + +#, fuzzy +#~ msgid "Failed to start `gnunet-arm' process.\n" +#~ msgstr "Misslyckades att ansluta till gnunetd.\n" + +#, fuzzy +#~ msgid "shutdown (either `gnunet-arm' or `ssh') did not complete cleanly.\n" +#~ msgstr "\"%s\" är inte ansluten till någon ändpunkt.\n" + +#, fuzzy +#~ msgid "Starting service %s for peer `%4s'\n" +#~ msgstr "Startade samling \"%s\".\n" + +#, fuzzy +#~ msgid "Could not start `%s' process to copy configuration directory.\n" +#~ msgstr "Kunde inte skapa värdnyckel!\n" + +#, fuzzy +#~ msgid "Terminating peer `%4s'\n" +#~ msgstr "Åtkomst nekad för \"%s\" vid %s:%d.\n" + +#, fuzzy +#~ msgid "Setting d->dead on peer `%4s'\n" +#~ msgstr "Startade samling \"%s\".\n" + +#, fuzzy +#~ msgid "Failed to write new configuration to disk." +#~ msgstr "Kunde inte spara konfiguration!" + +#, fuzzy +#~ msgid "Could not start `%s' process to copy configuration file.\n" +#~ msgstr "Kunde inte skapa värdnyckel!\n" + +#, fuzzy +#~ msgid "Failed to copy new configuration to remote machine." +#~ msgstr "Kunde inte spara konfiguration!" + +#, fuzzy +#~ msgid "Peers failed to connect" +#~ msgstr "Misslyckades att ansluta till gnunetd.\n" + +#, fuzzy +#~ msgid "Failed to connect to core service of first peer!\n" +#~ msgstr "Misslyckades att starta samling.\n" + +#, fuzzy +#~ msgid "Invalid value `%s' for option `%s' in section `%s': expected float\n" +#~ msgstr "Konfigurationsfil \"%s\" hittades inte. Kör \"gnunet-setup -d\"!\n" + +#, fuzzy +#~ msgid "Could not read hostkeys file `%s'!\n" +#~ msgstr "Kunde inte skapa värdnyckel!\n" + +#, fuzzy +#~ msgid "Could not create configuration for peer number %u on `%s'!\n" +#~ msgstr "Kunde inte komma åt namnrymdsinformation.\n" + +#, fuzzy +#~ msgid "Failed to find option %s in section %s!\n" +#~ msgstr "Misslyckades att binda till UDP-port %d.\n" + +#, fuzzy +#~ msgid "Invalid configuration option `%s' in section `%s'\n" +#~ msgstr "Konfigurationsfil \"%s\" skapad.\n" + +#, fuzzy +#~ msgid "Missing configuration option `%s' in section `%s'\n" +#~ msgstr "Konfigurationsfil \"%s\" skapad.\n" + +#, fuzzy +#~ msgid "internal error" +#~ msgstr "Okänt fel.\n" + +#, fuzzy +#~ msgid "Could not create namespace `%s'\n" +#~ msgstr "Kunde inte skapa namnrymd \"%s\" (existerar?).\n" + +#, fuzzy +#~ msgid "Stored zonekey for zone `%s' in file `%s'\n" +#~ msgstr "Misslyckades att leverera \"%s\" meddelande.\n" + +#, fuzzy +#~ msgid "Could not read hostkeys file, specify hostkey file with -H!\n" +#~ msgstr "Kunde inte skapa värdnyckel!\n" + +#, fuzzy +#~ msgid "Could not open hostkeys file: %s\n" +#~ msgstr "Kunde inte skapa värdnyckel!\n" + +#, fuzzy +#~ msgid "access (%s, X_OK) failed: %s\n" +#~ msgstr "\"%s\" %s misslyckades: %s\n" + +#, fuzzy +#~ msgid "stat (%s) failed: %s\n" +#~ msgstr "\"%s\" %s misslyckades: %s\n" #, fuzzy #~ msgid "# Peers connected" @@ -6127,10 +7123,6 @@ msgstr "\"%s\" misslyckades för fil \"%s\" vid %s:%d med fel: %s\n" #~ msgid "# unexpected CONNECT_ACK messages" #~ msgstr "skicka ANTAL meddelanden" -#, fuzzy -#~ msgid "# wlan session timeouts" -#~ msgstr "# sessionsnycklar accepterade" - #, fuzzy #~ msgid "# wlan session created" #~ msgstr "# sessionsnycklar accepterade" @@ -6209,9 +7201,6 @@ msgstr "\"%s\" misslyckades för fil \"%s\" vid %s:%d med fel: %s\n" #~ msgid "be verbose" #~ msgstr "var informativ" -#~ msgid "use configuration file FILENAME" -#~ msgstr "använd konfigurationsfil FILNAMN" - #, fuzzy #~ msgid "Failed to stop service `%s'!\n" #~ msgstr "Misslyckades att läsa kompislista från \"%s\"\n" @@ -6224,18 +7213,10 @@ msgstr "\"%s\" misslyckades för fil \"%s\" vid %s:%d med fel: %s\n" #~ msgid "Service `%s' stopped\n" #~ msgstr "Tjänst borttagen.\n" -#, fuzzy -#~ msgid "Unable to start service `%s': %s\n" -#~ msgstr "Kunde inte spara konfigurationsfil \"%s\":" - #, fuzzy #~ msgid "Unable to accept connection for service `%s': %s\n" #~ msgstr "Kunde inte spara konfigurationsfil \"%s\":" -#, fuzzy -#~ msgid "Peer `%s' plugin: `%s' address `%s'\n" -#~ msgstr "Motpart \"%s\" med pålitlighet %8u och adress \"%s\"\n" - #, fuzzy #~ msgid "Failed to create IPv4 broadcast socket on port %d\n" #~ msgstr "Misslyckades att läsa kompislista från \"%s\"\n" @@ -6292,10 +7273,6 @@ msgstr "\"%s\" misslyckades för fil \"%s\" vid %s:%d med fel: %s\n" #~ msgid "Failed to load transport plugin for tcp\n" #~ msgstr "Kunde inte slå upp \"%s\": %s\n" -#, fuzzy -#~ msgid "Connection: %X: %s failed at %s:%d: `%s'\n" -#~ msgstr "\"%s\" misslyckades vid %s:%d med fel: \"%s\".\n" - #, fuzzy #~ msgid "Misconfigured address to bind to in configuration!\n" #~ msgstr "Inga applikationer definierade i konfiguration!\n" @@ -6585,10 +7562,6 @@ msgstr "\"%s\" misslyckades för fil \"%s\" vid %s:%d med fel: %s\n" #~ msgid "Real-time delay violation (%llu ms) at %s:%u\n" #~ msgstr "Icke-förväntad mycket stor allokering (%u byte) vid %s:%d!\n" -#, fuzzy -#~ msgid "`%s' failed with error code %d: %s\n" -#~ msgstr "\"%s\" misslyckades vid %s:%d med fel: %s\n" - #, fuzzy #~ msgid "GNUnet error log" #~ msgstr "Spåra GNUnets nätverkstopologi." @@ -6616,9 +7589,6 @@ msgstr "\"%s\" misslyckades för fil \"%s\" vid %s:%d med fel: %s\n" #~ msgid "output in gnuplot format" #~ msgstr "utdata i gnuplot-format" -#~ msgid "number of iterations" -#~ msgstr "antal iterationer" - #~ msgid "number of messages to use per iteration" #~ msgstr "antal meddelanden att använda per iteration" @@ -6750,9 +7720,6 @@ msgstr "\"%s\" misslyckades för fil \"%s\" vid %s:%d med fel: %s\n" #~ "Session key received from peer `%s' has invalid format (discarded).\n" #~ msgstr "Meddelande mottaget från motpart är ogiltig.\n" -#~ msgid "# sessions established" -#~ msgstr "# sessioner etablerade" - #~ msgid "create a new pseudonym under the given NICKNAME" #~ msgstr "skapa en ny pseudonym under angivet SMEKNAMN" @@ -6786,9 +7753,6 @@ msgstr "\"%s\" misslyckades för fil \"%s\" vid %s:%d med fel: %s\n" #~ msgstr "" #~ "Du måste ange ett namn för PID-filen i sektion \"%s\" under \"%s\".\n" -#~ msgid "%d files found in directory.\n" -#~ msgstr "%d filer hittades i katalog.\n" - #~ msgid "Perform directory related operations." #~ msgstr "Genomför katalogrelaterade operationer." @@ -7091,9 +8055,6 @@ msgstr "\"%s\" misslyckades för fil \"%s\" vid %s:%d med fel: %s\n" #~ msgid "specifies after how many MS to time-out" #~ msgstr "anger timeout efter antal MS" -#~ msgid "Testing transport(s) %s\n" -#~ msgstr "Testar transport(er) %s\n" - #~ msgid "Available transport(s): %s\n" #~ msgstr "Tillgängliga transport(er): %s\n" @@ -7162,10 +8123,6 @@ msgstr "\"%s\" misslyckades för fil \"%s\" vid %s:%d med fel: %s\n" #~ msgid "Network interface to monitor" #~ msgstr "Nätverksgränssnitt:" -#, fuzzy -#~ msgid "What is the path to the configuration file for gnunetd?" -#~ msgstr "skriv ut ett värde från konfigurationsfilen till standard ut" - #, fuzzy #~ msgid "General options" #~ msgstr "Visa alla alternativ" @@ -7181,9 +8138,6 @@ msgstr "\"%s\" misslyckades för fil \"%s\" vid %s:%d med fel: %s\n" #~ msgstr "" #~ "Kunde inte slå upp namn för HTTP-proxy \"%s\". Försöker utan proxy.\n" -#~ msgid "Maximum number of chat clients reached.\n" -#~ msgstr "Maximalt antal chattklienter uppnått.\n" - #~ msgid "Now %d of %d chat clients at this node.\n" #~ msgstr "Nu är det %d av %d chattklienter på den här noden.\n" @@ -7199,9 +8153,6 @@ msgstr "\"%s\" misslyckades för fil \"%s\" vid %s:%d med fel: %s\n" #~ msgid "Database failed to delete `%s'.\n" #~ msgstr "Databas misslyckades att ta bort \"%s\".\n" -#~ msgid "`%s' failed: table not found!\n" -#~ msgstr "\"%s\" misslyckades: tabell hittades inte!\n" - #~ msgid "`%s' failed. Terminating connection to client.\n" #~ msgstr "\"%s\" misslyckades. Terminerar anslutning till klient.\n" @@ -7211,9 +8162,6 @@ msgstr "\"%s\" misslyckades för fil \"%s\" vid %s:%d med fel: %s\n" #~ msgid "`%s' called with timeout above 1 hour (bug?)\n" #~ msgstr "\"%s\" anropad med timeout över 1 timma (fel?)\n" -#~ msgid "Received invalid RPC `%s'.\n" -#~ msgstr "Mottog ogiltig RPC \"%s\".\n" - #~ msgid "allow SIZE bytes of memory for the local table" #~ msgstr "tillåt STORLEK byte av minne för lokaltabellen" @@ -7235,15 +8183,9 @@ msgstr "\"%s\" misslyckades för fil \"%s\" vid %s:%d med fel: %s\n" #~ msgid "Failed to send `%s'. Closing connection.\n" #~ msgstr "Misslyckades att skicka \"%s\". Stänger anslutning.\n" -#~ msgid "Received invalid `%s' request (size %d)\n" -#~ msgstr "Mottog ogiltig \"%s\" begäran (storlek %d)\n" - #~ msgid "Received invalid `%s' request (wrong table)\n" #~ msgstr "Mottog ogiltig \"%s\" begäran (fel tabell)\n" -#~ msgid "Received unknown request type %d at %s:%d\n" -#~ msgstr "Mottog okänd typ av begäran %d vid %s:%d\n" - #~ msgid "gnunetd signaled error in response to `%s' message\n" #~ msgstr "gnunetd signalerade fel i svar till \"%s\" meddelande\n" @@ -7333,9 +8275,6 @@ msgstr "\"%s\" misslyckades för fil \"%s\" vid %s:%d med fel: %s\n" #~ msgid "size of `%s' message is wrong. Ignoring.\n" #~ msgstr "storlek på \"%s\" meddelande är fel. Ignorerar.\n" -#~ msgid "received invalid `%s' message\n" -#~ msgstr "mottog ogiltigt \"%s\" meddelande\n" - #~ msgid "'..' is not allowed in file name (%s).\n" #~ msgstr "\"..\" tillåts inte i filnamn (%s).\n" @@ -7378,9 +8317,6 @@ msgstr "\"%s\" misslyckades för fil \"%s\" vid %s:%d med fel: %s\n" #~ msgid "Show _data" #~ msgstr "Visa _data" -#~ msgid "Show value of the option" -#~ msgstr "Visa värde av alternativet" - #~ msgid "Show all _options" #~ msgstr "Visa alla a_lternativ" @@ -7521,9 +8457,6 @@ msgstr "\"%s\" misslyckades för fil \"%s\" vid %s:%d med fel: %s\n" #~ msgid "CPU usage" #~ msgstr "CPU-användning" -#~ msgid "Finish" -#~ msgstr "Slutför" - #~ msgid "Question" #~ msgstr "Fråga" @@ -7533,19 +8466,9 @@ msgstr "\"%s\" misslyckades för fil \"%s\" vid %s:%d med fel: %s\n" #~ msgid "User account:" #~ msgstr "Användarkonto:" -#~ msgid "gnunet-update failed!" -#~ msgstr "gnunet-update misslyckades!" - #~ msgid "You must specify a non-empty set of transports to test!\n" #~ msgstr "Du måste ange en icke-tom uppsättning av transporter att testa!\n" -#~ msgid "" -#~ "\n" -#~ "Exiting.\n" -#~ msgstr "" -#~ "\n" -#~ "Avslutar.\n" - #~ msgid "Updated data for %d applications.\n" #~ msgstr "Uppdaterade data för %d program.\n" diff --git a/po/vi.gmo b/po/vi.gmo index fe4edd8..875fd5c 100644 Binary files a/po/vi.gmo and b/po/vi.gmo differ diff --git a/po/vi.po b/po/vi.po index 6ee9cf4..f6f3ac1 100644 --- a/po/vi.po +++ b/po/vi.po @@ -8,7 +8,7 @@ msgid "" msgstr "" "Project-Id-Version: gnunet 0.8.0a\n" "Report-Msgid-Bugs-To: gnunet-developers@mail.gnu.org\n" -"POT-Creation-Date: 2012-06-05 15:47+0200\n" +"POT-Creation-Date: 2013-02-05 19:22+0100\n" "PO-Revision-Date: 2008-09-10 22:05+0930\n" "Last-Translator: Clytie Siddall \n" "Language-Team: Vietnamese \n" @@ -19,271 +19,219 @@ msgstr "" "Plural-Forms: nplurals=1; plural=0;\n" "X-Generator: LocFactoryEditor 1.7b3\n" -#: src/arm/arm_api.c:165 +#: src/arm/arm_api.c:162 msgid "Failed to transmit shutdown request to client.\n" msgstr "" -#: src/arm/arm_api.c:349 -#, fuzzy, c-format -msgid "Configuration failes to specify option `%s' in section `%s'!\n" -msgstr "" -"Cấu hình không thỏa mãn các ràng buộc của tập tin đặc tả cấu hình « %s ».\n" - -#: src/arm/arm_api.c:363 -#, fuzzy, c-format -msgid "Configuration fails to specify option `%s' in section `%s'!\n" -msgstr "" -"Cấu hình không thỏa mãn các ràng buộc của tập tin đặc tả cấu hình « %s ».\n" - -#: src/arm/arm_api.c:432 -#, c-format -msgid "Error receiving response to `%s' request from ARM for service `%s'\n" -msgstr "" - -#: src/arm/arm_api.c:485 -#, c-format -msgid "Requesting start of service `%s'.\n" -msgstr "" - -#: src/arm/arm_api.c:486 -#, c-format -msgid "Requesting termination of service `%s'.\n" -msgstr "" - -#: src/arm/arm_api.c:507 -#, c-format -msgid "Error while trying to transmit request to start `%s' to ARM\n" -msgstr "" - -#: src/arm/arm_api.c:508 -#, c-format -msgid "Error while trying to transmit request to stop `%s' to ARM\n" -msgstr "" - -#: src/arm/arm_api.c:540 -#, fuzzy, c-format -msgid "Asked to start service `%s' within %llu ms\n" -msgstr "« %s »: Chưa nhận thông báo sau %llu miligiây.\n" - -#: src/arm/arm_api.c:612 -#, c-format -msgid "Stopping service `%s' within %llu ms\n" -msgstr "" - -#: src/arm/gnunet-arm.c:159 +#: src/arm/gnunet-arm.c:166 #, fuzzy, c-format msgid "Service `%s' is unknown to ARM.\n" msgstr "Không gian tên « %s » có đánh giá %d.\n" -#: src/arm/gnunet-arm.c:164 +#: src/arm/gnunet-arm.c:171 #, fuzzy, c-format msgid "Service `%s' has been stopped.\n" msgstr "Dịch vụ đã bị xoá.\n" -#: src/arm/gnunet-arm.c:167 +#: src/arm/gnunet-arm.c:174 #, fuzzy, c-format msgid "Service `%s' was already running.\n" msgstr "Không gian tên « %s » có đánh giá %d.\n" -#: src/arm/gnunet-arm.c:172 +#: src/arm/gnunet-arm.c:179 #, fuzzy, c-format msgid "Service `%s' has been started.\n" msgstr "Dịch vụ đã bị xoá.\n" -#: src/arm/gnunet-arm.c:175 +#: src/arm/gnunet-arm.c:182 #, fuzzy, c-format msgid "Service `%s' was already being stopped.\n" msgstr "Dịch vụ đã bị xoá.\n" -#: src/arm/gnunet-arm.c:179 +#: src/arm/gnunet-arm.c:186 #, fuzzy, c-format msgid "Service `%s' was already not running.\n" msgstr "« %s » không phải là một tập tin.\n" -#: src/arm/gnunet-arm.c:183 +#: src/arm/gnunet-arm.c:190 #, fuzzy msgid "Request ignored as ARM is shutting down.\n" msgstr "« %s » đang tắt.\n" -#: src/arm/gnunet-arm.c:187 +#: src/arm/gnunet-arm.c:194 #, fuzzy msgid "Error communicating with ARM service.\n" msgstr "Cổng để liên lạc với giao diện người dùng GNUnet" -#: src/arm/gnunet-arm.c:191 +#: src/arm/gnunet-arm.c:198 #, fuzzy msgid "Timeout communicating with ARM service.\n" msgstr "Cổng để liên lạc với giao diện người dùng GNUnet" -#: src/arm/gnunet-arm.c:195 +#: src/arm/gnunet-arm.c:202 #, fuzzy msgid "Operation failed.\n" msgstr "Lỗi nội bộ : khẳng định không thành công tại %s:%d.\n" -#: src/arm/gnunet-arm.c:199 +#: src/arm/gnunet-arm.c:206 msgid "Unknown response code from ARM.\n" msgstr "" -#: src/arm/gnunet-arm.c:222 +#: src/arm/gnunet-arm.c:229 #, fuzzy msgid "Error communicating with ARM. ARM not running?\n" msgstr "Cổng để liên lạc với giao diện người dùng GNUnet" -#: src/arm/gnunet-arm.c:225 +#: src/arm/gnunet-arm.c:232 #, fuzzy msgid "Running services:\n" msgstr "Đang nạp và khởi động dùng « %s ».\n" -#: src/arm/gnunet-arm.c:249 -#, c-format -msgid "Fatal configuration error: `%s' option in section `%s' missing.\n" -msgstr "" - -#: src/arm/gnunet-arm.c:257 src/arm/gnunet-arm.c:357 src/arm/gnunet-arm.c:373 -msgid "Fatal error initializing ARM API.\n" -msgstr "" - -#: src/arm/gnunet-arm.c:280 +#: src/arm/gnunet-arm.c:253 #, fuzzy, c-format msgid "Failed to remove configuration file %s\n" msgstr "Không thể lưu tập tin cấu hình « %s »:" -#: src/arm/gnunet-arm.c:286 +#: src/arm/gnunet-arm.c:259 #, fuzzy, c-format msgid "Failed to remove servicehome directory %s\n" msgstr "Lỗi truy cập đến thư mục nhà GNUnet « %s »\n" -#: src/arm/gnunet-arm.c:407 +#: src/arm/gnunet-arm.c:322 src/arm/gnunet-arm.c:407 src/arm/gnunet-arm.c:424 +msgid "Fatal error initializing ARM API.\n" +msgstr "" + +#: src/arm/gnunet-arm.c:453 #, fuzzy msgid "stop all GNUnet services" msgstr "hủy cài đặt dịch vụ GNUnet" -#: src/arm/gnunet-arm.c:409 +#: src/arm/gnunet-arm.c:455 msgid "start a particular service" msgstr "" -#: src/arm/gnunet-arm.c:411 +#: src/arm/gnunet-arm.c:457 msgid "stop a particular service" msgstr "" -#: src/arm/gnunet-arm.c:413 +#: src/arm/gnunet-arm.c:459 #, fuzzy msgid "start all GNUnet default services" msgstr "hủy cài đặt dịch vụ GNUnet" -#: src/arm/gnunet-arm.c:416 +#: src/arm/gnunet-arm.c:462 #, fuzzy msgid "stop and start all GNUnet default services" msgstr "hủy cài đặt dịch vụ GNUnet" -#: src/arm/gnunet-arm.c:419 +#: src/arm/gnunet-arm.c:465 msgid "delete config file and directory on exit" msgstr "" -#: src/arm/gnunet-arm.c:421 +#: src/arm/gnunet-arm.c:467 msgid "don't print status messages" msgstr "" -#: src/arm/gnunet-arm.c:424 +#: src/arm/gnunet-arm.c:470 #, fuzzy -msgid "timeout for completing current operation" +msgid "timeout in MSECS milliseconds for completing current operation" msgstr "thời gian chờ sự hoàn thành của một lần lặp (theo miligiây)" -#: src/arm/gnunet-arm.c:426 -msgid "List currently running services" +#: src/arm/gnunet-arm.c:472 +#, fuzzy +msgid "list currently running services" +msgstr "Đang nạp và khởi động dùng « %s ».\n" + +#: src/arm/gnunet-arm.c:474 +msgid "don't let gnunet-service-arm inherit standard output" +msgstr "" + +#: src/arm/gnunet-arm.c:476 +msgid "don't let gnunet-service-arm inherit standard error" msgstr "" -#: src/arm/gnunet-arm.c:437 +#: src/arm/gnunet-arm.c:487 msgid "Control services and the Automated Restart Manager (ARM)" msgstr "" -#: src/arm/gnunet-service-arm.c:332 +#: src/arm/gnunet-service-arm.c:345 #, fuzzy, c-format msgid "Failed to start service `%s'\n" msgstr "Lỗi bắt đầu thu thập.\n" -#: src/arm/gnunet-service-arm.c:335 +#: src/arm/gnunet-service-arm.c:348 #, fuzzy, c-format msgid "Starting service `%s'\n" msgstr "Đang bắt đầu tài về « %s »\n" -#: src/arm/gnunet-service-arm.c:361 +#: src/arm/gnunet-service-arm.c:374 msgid "Could not send status result to client\n" msgstr "" -#: src/arm/gnunet-service-arm.c:393 +#: src/arm/gnunet-service-arm.c:406 #, fuzzy msgid "Could not send list result to client\n" msgstr "Không thể đọc danh sách bạn bè « %s »\n" -#: src/arm/gnunet-service-arm.c:523 +#: src/arm/gnunet-service-arm.c:537 #, fuzzy, c-format msgid "Unable to create socket for service `%s': %s\n" msgstr "Không thể tạo tài khoản người dùng:" -#: src/arm/gnunet-service-arm.c:545 +#: src/arm/gnunet-service-arm.c:559 #, c-format msgid "Unable to bind listening socket for service `%s' to address `%s': %s\n" msgstr "" -#: src/arm/gnunet-service-arm.c:559 +#: src/arm/gnunet-service-arm.c:573 #, c-format msgid "ARM now monitors connections to service `%s' at `%s'\n" msgstr "" -#: src/arm/gnunet-service-arm.c:667 +#: src/arm/gnunet-service-arm.c:681 #, fuzzy, c-format msgid "Preparing to stop `%s'\n" msgstr "Đang bắt đầu tài lên « %s ».\n" -#: src/arm/gnunet-service-arm.c:878 +#: src/arm/gnunet-service-arm.c:892 #, fuzzy, c-format msgid "Restarting service `%s'.\n" msgstr "Đang nạp và khởi động dùng « %s ».\n" -#: src/arm/gnunet-service-arm.c:970 +#: src/arm/gnunet-service-arm.c:985 msgid "exit" msgstr "" -#: src/arm/gnunet-service-arm.c:975 +#: src/arm/gnunet-service-arm.c:990 msgid "signal" msgstr "" -#: src/arm/gnunet-service-arm.c:980 +#: src/arm/gnunet-service-arm.c:995 #, fuzzy msgid "unknown" msgstr "Lỗi không rõ" -#: src/arm/gnunet-service-arm.c:986 +#: src/arm/gnunet-service-arm.c:1001 #, fuzzy, c-format -msgid "Service `%s' took %llu ms to terminate\n" +msgid "Service `%s' took %s to terminate\n" msgstr "Dịch vụ đã bị xoá.\n" -#: src/arm/gnunet-service-arm.c:1021 +#: src/arm/gnunet-service-arm.c:1036 #, c-format msgid "Service `%s' terminated with status %s/%d, will restart in %llu ms\n" msgstr "" -#: src/arm/gnunet-service-arm.c:1127 -#, fuzzy, c-format -msgid "Configuration file `%s' for service `%s' not valid: %s\n" -msgstr "Tập tin cấu hình « %s » đã được ghi.\n" - -#: src/arm/gnunet-service-arm.c:1129 -msgid "option missing" -msgstr "" - -#: src/arm/gnunet-service-arm.c:1213 +#: src/arm/gnunet-service-arm.c:1228 #, fuzzy, c-format msgid "Starting default services `%s'\n" msgstr "Đang bắt đầu tài về « %s »\n" -#: src/arm/gnunet-service-arm.c:1224 +#: src/arm/gnunet-service-arm.c:1239 #, c-format msgid "Default service `%s' not configured correctly!\n" msgstr "" -#: src/arm/gnunet-service-arm.c:1238 +#: src/arm/gnunet-service-arm.c:1253 msgid "" "No default services configured, GNUnet will not really start right now.\n" msgstr "" @@ -292,312 +240,265 @@ msgstr "" msgid "Initiating shutdown as requested by client.\n" msgstr "" -#: src/block/block.c:105 -#, fuzzy, c-format -msgid "Loading block plugin `%s'\n" -msgstr "Đang nạp các truyền tải « %s »\n" - -#: src/chat/chat.c:175 -#, fuzzy -msgid "Could not transmit confirmation receipt\n" -msgstr "Không thể truy cập đến thông tin về không gian tên.\n" - -#: src/chat/chat.c:283 -msgid "The current user must be the the first one joined\n" -msgstr "" - -#: src/chat/chat.c:412 -#, fuzzy, c-format -msgid "Unknown message type: '%u'\n" -msgstr "\tKhông rõ miền tên « %s »\n" - -#: src/chat/chat.c:472 +#: src/ats/ats_api_performance.c:465 #, fuzzy, c-format -msgid "Configuration option `%s' in section `%s' missing\n" -msgstr "Giá trị cấu hình « %s » cho « %s » trong phần « %s » nên là con số\n" - -#: src/chat/chat.c:480 -#, fuzzy, c-format -msgid "Failed to access chat home directory `%s'\n" -msgstr "Lỗi truy cập đến thư mục nhà GNUnet « %s »\n" +msgid "Received %s message\n" +msgstr "Nhận yêu cầu định tuyến\n" -#: src/chat/chat.c:498 +#: src/ats/ats_api_performance.c:508 #, fuzzy, c-format -msgid "Failed to create/open key in file `%s'\n" -msgstr "Lỗi mở tập tin ghi sự kiện « %s »: %s\n" - -#: src/chat/chat.c:559 -#, fuzzy -msgid "Could not serialize metadata\n" -msgstr "Không thể tạo miền tên.\n" - -#: src/chat/chat.c:674 -#, fuzzy -msgid "Failed to connect to the chat service\n" -msgstr "Lỗi kết nối đến gnunetd.\n" +msgid "Received last message for %s \n" +msgstr "Nhận yêu cầu định tuyến\n" -#: src/chat/chat.c:680 -msgid "Undefined mandatory parameter: joinCallback\n" +#: src/ats/gnunet-service-ats_addresses.c:993 +#: src/ats/gnunet-service-ats_addresses.c:1027 +#, c-format +msgid "" +"Could not load quota for network `%s': `%s', assigning default bandwidth " +"%llu\n" msgstr "" -#: src/chat/chat.c:686 -msgid "Undefined mandatory parameter: messageCallback\n" +#: src/ats/gnunet-service-ats_addresses.c:999 +#, c-format +msgid "Outbound quota configure for network `%s' is %llu\n" msgstr "" -#: src/chat/chat.c:692 -msgid "Undefined mandatory parameter: memberCallback\n" +#: src/ats/gnunet-service-ats_addresses.c:1006 +#, c-format +msgid "" +"No outbound quota configured for network `%s', assigning default bandwidth " +"%llu\n" msgstr "" -#: src/chat/gnunet-chat.c:93 -msgid "Joined\n" +#: src/ats/gnunet-service-ats_addresses.c:1033 +#, c-format +msgid "Inbound quota configured for network `%s' is %llu\n" msgstr "" -#: src/chat/gnunet-chat.c:125 src/chat/gnunet-chat.c:133 -#: src/chat/gnunet-chat.c:213 src/chat/gnunet-chat.c:253 -#: src/chat/gnunet-chat.c:329 src/chat/gnunet-chat.c:371 -#: src/chat/gnunet-chat.c:400 src/chat/gnunet-chat.c:700 -msgid "anonymous" -msgstr "nặc danh" - -#: src/chat/gnunet-chat.c:144 -#, fuzzy, c-format -msgid "(%s) `%s' said: %s\n" -msgstr "« %s » nói: %s\n" - -#: src/chat/gnunet-chat.c:147 src/chat/gnunet-chat.c:150 -#, fuzzy, c-format -msgid "(%s) `%s' said to you: %s\n" -msgstr "« %s » nói cho bạn: %s\n" - -#: src/chat/gnunet-chat.c:153 -#, fuzzy, c-format -msgid "(%s) `%s' said for sure: %s\n" -msgstr "« %s » nói thật: %s\n" - -#: src/chat/gnunet-chat.c:156 -#, fuzzy, c-format -msgid "(%s) `%s' said to you for sure: %s\n" -msgstr "« %s » nói thật cho bạn: %s\n" - -#: src/chat/gnunet-chat.c:159 -#, fuzzy, c-format -msgid "(%s) `%s' was confirmed that you received: %s\n" -msgstr "« %s » xác nhận bạn đã nhận được: %s\n" - -#: src/chat/gnunet-chat.c:162 -#, fuzzy, c-format -msgid "(%s) `%s' was confirmed that you and only you received: %s\n" -msgstr "« %s » xác nhận mà chỉ bạn đã nhận được: %s\n" - -#: src/chat/gnunet-chat.c:165 -#, fuzzy, c-format -msgid "(%s) `%s' was confirmed that you received from him or her: %s\n" -msgstr "« %s » xác nhận mà bạn đã nhận được từ họ : %s\n" - -#: src/chat/gnunet-chat.c:170 -#, fuzzy, c-format +#: src/ats/gnunet-service-ats_addresses.c:1040 +#, c-format msgid "" -"(%s) `%s' was confirmed that you and only you received from him or her: %s\n" -msgstr "« %s » xác nhận mà chỉ bạn đa nhận được từ họ : %s\n" - -#: src/chat/gnunet-chat.c:173 -#, fuzzy, c-format -msgid "(%s) `%s' said off the record: %s\n" -msgstr "« %s » nói không chính thức: %s\n" - -#: src/chat/gnunet-chat.c:176 -#, fuzzy, c-format -msgid "(%s) <%s> said using an unknown message type: %s\n" -msgstr "<%s> đã nói bằng một kiểu tin nhẳn không rõ : %s\n" +"No outbound quota configure for network `%s', assigning default bandwidth " +"%llu\n" +msgstr "" -#: src/chat/gnunet-chat.c:217 +#: src/ats-tool/gnunet-ats.c:141 #, c-format -msgid "'%s' acknowledged message #%d\n" +msgid "%u address resolutions had a timeout\n" msgstr "" -#: src/chat/gnunet-chat.c:260 +#: src/ats-tool/gnunet-ats.c:143 #, c-format -msgid "`%s' entered the room\n" -msgstr "« %s » vào phòng\n" +msgid "ATS returned results for %u addresses\n" +msgstr "" -#: src/chat/gnunet-chat.c:260 -#, c-format -msgid "`%s' left the room\n" -msgstr "« %s » rời phòng\n" +#: src/ats-tool/gnunet-ats.c:199 +#, fuzzy, c-format +msgid "" +"Peer `%s' plugin `%s', address `%s', `%s' bw out: %u Bytes/s, bw in %u Bytes/" +"s, %s\n" +msgstr "Đồng đẳng « %s » có mức tin cậy %8u và địa chỉ « %s »\n" -#: src/chat/gnunet-chat.c:321 src/chat/gnunet-chat.c:363 -#, fuzzy -msgid "Could not change username\n" -msgstr "Không thể tạo miền tên.\n" +#: src/ats-tool/gnunet-ats.c:326 +#, c-format +msgid "Quota for network `%11s' (in/out): %10s / %10s\n" +msgstr "" -#: src/chat/gnunet-chat.c:334 src/chat/gnunet-chat.c:702 +#: src/ats-tool/gnunet-ats.c:345 src/namestore/gnunet-namestore.c:610 +#: src/transport/gnunet-transport.c:813 #, fuzzy, c-format -msgid "Joining room `%s' as user `%s'...\n" -msgstr "Đã vào phòng « %s » là người dùng « %s ».\n" +msgid "Service `%s' is not running\n" +msgstr "« %s » không phải là một tập tin.\n" -#: src/chat/gnunet-chat.c:373 +#: src/ats-tool/gnunet-ats.c:355 src/transport/gnunet-transport.c:819 #, fuzzy, c-format -msgid "Changed username to `%s'\n" -msgstr "Đã thay đổi tên người dùng thành « %s ».\n" - -#: src/chat/gnunet-chat.c:388 -#, c-format -msgid "Users in room `%s': " -msgstr "Người dùng trong phòng « %s »:" - -#: src/chat/gnunet-chat.c:434 -msgid "Syntax: /msg USERNAME MESSAGE" -msgstr "Cú pháp: /msg TÊN_NGƯỜI_DÙNG TIN_NHẲN" +msgid "Failed to parse peer identity `%s'\n" +msgstr "Lỗi đọc danh sách bạn bè từ « %s »\n" -#: src/chat/gnunet-chat.c:443 +#: src/ats-tool/gnunet-ats.c:363 #, c-format -msgid "Unknown user `%s'. Make sure you specify its numeric suffix, if any.\n" +msgid "Please select one operation : %s or %s or %s or %s or %s\n" msgstr "" -#: src/chat/gnunet-chat.c:460 -#, c-format -msgid "User `%s' is currently not in the room!\n" -msgstr "Người dùng « %s » hiện thời không có trong phòng này.\n" +#: src/ats-tool/gnunet-ats.c:379 src/ats-tool/gnunet-ats.c:398 +#: src/ats-tool/gnunet-ats.c:415 src/ats-tool/gnunet-ats.c:440 +#, fuzzy, c-format +msgid "Cannot connect to ATS service, exiting...\n" +msgstr "Lỗi sơ khởi dịch vụ « %s ».\n" -#: src/chat/gnunet-chat.c:513 +#: src/ats-tool/gnunet-ats.c:388 src/ats-tool/gnunet-ats.c:405 #, fuzzy, c-format -msgid "Unknown command `%s'\n" -msgstr "Không rõ câu lệnh « %s ».\n" +msgid "Cannot issue request to ATS service, exiting...\n" +msgstr "Lỗi sơ khởi dịch vụ « %s ».\n" -#: src/chat/gnunet-chat.c:524 -msgid "" -"Use `/join #roomname' to join a chat room. Joining a room will cause you to " -"leave the current room" +#: src/ats-tool/gnunet-ats.c:433 +msgid "Type required\n" msgstr "" -"Gõ chuỗi « /join #tên_phòng » để vào một phòng trò chuyện nào đó (việc này " -"cũng gây ra bạn ra khỏi phòng hiện tại)" -#: src/chat/gnunet-chat.c:528 -msgid "" -"Use `/nick nickname' to change your nickname. This will cause you to leave " -"the current room and immediately rejoin it with the new name." +#: src/ats-tool/gnunet-ats.c:490 +msgid "get list of active addresses currently used" msgstr "" -"Gõ chuỗi « /nick tên_hiệu » để thay đổi tên hiệu của mình (việc này cũng gây " -"ra bạn ra khỏi phòng hiện tại, sau đó vào lại ngay với tên mới)" -#: src/chat/gnunet-chat.c:532 -msgid "" -"Use `/msg nickname message' to send a private message to the specified user" +#: src/ats-tool/gnunet-ats.c:493 +msgid "get list of all active addresses" msgstr "" -"Gõ chuỗi « /msg tên_hiệu tin_nhẳn » để gửi một tin nhẳn riêng cho người dùng " -"có tên đó" -#: src/chat/gnunet-chat.c:535 -msgid "The `/notice' command is an alias for `/msg'" -msgstr "Lệnh « /notice » là một biệt hiệu cho « /msg »" +#: src/ats-tool/gnunet-ats.c:496 +#, fuzzy +msgid "do not resolve IP addresses to hostnames" +msgstr "không quyết định các tên máy" -#: src/chat/gnunet-chat.c:537 -msgid "The `/query' command is an alias for `/msg'" -msgstr "Lệnh « /query » là một biệt hiệu cho « /msg »" +#: src/ats-tool/gnunet-ats.c:499 +msgid "monitor mode" +msgstr "" -#: src/chat/gnunet-chat.c:539 +#: src/ats-tool/gnunet-ats.c:502 #, fuzzy -msgid "Use `/sig message' to send a signed public message" -msgstr "" -"Gõ chuỗi « /msg tên_hiệu tin_nhẳn » để gửi một tin nhẳn riêng cho người dùng " -"có tên đó" +msgid "set preference for the given peer" +msgstr "In ra thông tin về các đồng đẳng GNUnet." -#: src/chat/gnunet-chat.c:542 -msgid "Use `/ack message' to require signed acknowledgment of the message" +#: src/ats-tool/gnunet-ats.c:505 +msgid "print all configured quotas" msgstr "" -#: src/chat/gnunet-chat.c:545 -msgid "Use `/anonymous message' to send a public anonymous message" +#: src/ats-tool/gnunet-ats.c:508 +msgid "peer id" msgstr "" -#: src/chat/gnunet-chat.c:547 -#, fuzzy -msgid "The `/anon' command is an alias for `/anonymous'" -msgstr "Lệnh « /notice » là một biệt hiệu cho « /msg »" - -#: src/chat/gnunet-chat.c:549 -msgid "Use `/quit' to terminate gnunet-chat" -msgstr "Gõ chuỗi « /quit » để thoát khỏi trình gnunet-chat" - -#: src/chat/gnunet-chat.c:551 -msgid "The `/leave' command is an alias for `/quit'" -msgstr "Lệnh « /leave » là một biệt hiệu cho « /quit »" +#: src/ats-tool/gnunet-ats.c:511 +msgid "preference type to set: latency | bandwidth" +msgstr "" -#: src/chat/gnunet-chat.c:554 -msgid "Use `/names' to list all of the current members in the chat room" +#: src/ats-tool/gnunet-ats.c:514 +msgid "preference value" msgstr "" -"Gõ chuỗi « /names » để liệt kê tất cả các thành viên hiện thời trong phòng " -"trò chuyện đó" -#: src/chat/gnunet-chat.c:556 -msgid "Use `/help command' to get help for a specific command" -msgstr "Gõ chuỗi « /help LỆNH » để xem trợ giúp về lệnh đó" +#: src/ats-tool/gnunet-ats.c:517 +msgid "verbose output (include ATS address properties)" +msgstr "" -#: src/chat/gnunet-chat.c:672 -msgid "You must specify a nickname\n" -msgstr "Phải ghi rõ tên hiệu\n" +#: src/ats-tool/gnunet-ats.c:526 +#, fuzzy +msgid "Print information about ATS state" +msgstr "In ra thông tin về các đồng đẳng GNUnet." -#: src/chat/gnunet-chat.c:688 -#, c-format -msgid "Failed to join room `%s'\n" -msgstr "Lỗi vào phòng « %s »\n" +#: src/block/block.c:105 +#, fuzzy, c-format +msgid "Loading block plugin `%s'\n" +msgstr "Đang nạp các truyền tải « %s »\n" -#: src/chat/gnunet-chat.c:727 -msgid "set the nickname to use (required)" -msgstr "đặt tên hiệu cần dùng (cần thiết)" +#: src/consensus/gnunet-consensus.c:317 +#, fuzzy +msgid "number of peers in consensus" +msgstr "số lần lặp lại" -#: src/chat/gnunet-chat.c:730 -msgid "set the chat room to join" -msgstr "đặt phòng trò chuyện cần vào" +#: src/consensus/gnunet-consensus.c:320 +msgid "how many peers receive one value?" +msgstr "" -#: src/chat/gnunet-chat.c:742 -msgid "Join a chat on GNUnet." -msgstr "Vào phòng trò chuyện trên GNUnet." +#: src/consensus/gnunet-consensus.c:323 +#, fuzzy +msgid "number of values" +msgstr "số lần lặp lại" -#: src/chat/gnunet-service-chat.c:267 +#: src/consensus/gnunet-consensus.c:326 #, fuzzy -msgid "Failed to queue a message notification\n" -msgstr "Lỗi lưu cấu hình." +msgid "consensus timeout" +msgstr "# các khoá phiên chạy được chấp nhận" -#: src/chat/gnunet-service-chat.c:546 +#: src/consensus/gnunet-consensus-ibf.c:176 #, fuzzy -msgid "Failed to queue a join notification\n" -msgstr "Lỗi lưu cấu hình." +msgid "number of element in set A-B" +msgstr "số lần lặp lại" -#: src/chat/gnunet-service-chat.c:729 +#: src/consensus/gnunet-consensus-ibf.c:179 #, fuzzy -msgid "Failed to queue a confirmation receipt\n" -msgstr "Lỗi lưu cấu hình." +msgid "number of element in set B-A" +msgstr "số lần lặp lại" + +#: src/consensus/gnunet-consensus-ibf.c:182 +msgid "number of common elements in A and B" +msgstr "" + +#: src/consensus/gnunet-consensus-ibf.c:185 +msgid "hash num" +msgstr "" + +#: src/consensus/gnunet-consensus-ibf.c:188 +msgid "ibf size" +msgstr "" + +#: src/consensus/gnunet-consensus-start-peers.c:158 +msgid "start peers with the given template configuration" +msgstr "" -#: src/chat/gnunet-service-chat.c:907 +#: src/consensus/gnunet-consensus-start-peers.c:161 #, fuzzy -msgid "Failed to queue a leave notification\n" -msgstr "Lỗi lưu cấu hình." +msgid "number of peers to start" +msgstr "số lần lặp lại" -#: src/core/core_api.c:786 +#: src/core/core_api.c:755 msgid "Client was disconnected from core service, trying to reconnect.\n" msgstr "" -#: src/core/gnunet-core.c:54 src/peerinfo-tool/gnunet-peerinfo.c:286 +#: src/core/gnunet-core.c:86 src/peerinfo-tool/gnunet-peerinfo.c:214 #, fuzzy, c-format msgid "Peer `%s'\n" msgstr "Tôi là đồng đẳng « %s ».\n" -#: src/core/gnunet-core.c:72 src/peerinfo-tool/gnunet-peerinfo.c:817 +#: src/core/gnunet-core.c:119 src/core/gnunet-core.c:147 +#: src/transport/gnunet-transport.c:612 src/transport/gnunet-transport.c:636 +#, c-format +msgid "%24s: %-17s %4s (%u connections in total)\n" +msgstr "" + +#: src/core/gnunet-core.c:121 src/transport/gnunet-transport.c:614 +#, fuzzy +msgid "Connected to" +msgstr "« %s » được kết nối tới « %s ».\n" + +#: src/core/gnunet-core.c:149 src/transport/gnunet-transport.c:638 +#, fuzzy +msgid "Disconnected from" +msgstr "« %.*s » được kết nối tới « %.*s ».\n" + +#: src/core/gnunet-core.c:174 src/mesh/gnunet-mesh.c:176 +#: src/peerinfo-tool/gnunet-peerinfo.c:541 #, fuzzy, c-format msgid "Invalid command line argument `%s'\n" msgstr "Đối số không hợp lệ cho « %s ».\n" -#: src/core/gnunet-core.c:95 +#: src/core/gnunet-core.c:211 src/transport/gnunet-transport.c:1005 +#, fuzzy +msgid "provide information about all current connections (continuously)" +msgstr "In ra thông tin về các đồng đẳng GNUnet." + +#: src/core/gnunet-core.c:222 #, fuzzy msgid "Print information about connected peers." msgstr "In ra thông tin về các đồng đẳng GNUnet." -#: src/core/gnunet-service-core.c:97 +#: src/core/gnunet-service-core.c:109 +#, fuzzy, c-format +msgid "Failed to read hostkey: %s\n" +msgstr "Lỗi bắt đầu thu thập.\n" + +#: src/core/gnunet-service-core.c:123 #, c-format msgid "Core service of `%4s' ready.\n" msgstr "" +#: src/core/gnunet-service-core.c:149 +#, fuzzy +msgid "Core service is lacking HOSTKEY configuration setting. Exiting.\n" +msgstr "Lưu cấu hình ngay bây giờ không?" + +#: src/core/gnunet-service-core.c:163 +#: src/transport/gnunet-service-transport.c:737 +#, fuzzy +msgid "Transport service is unable to access hostkey. Exiting.\n" +msgstr "Không thể truy cập đến thông tin về không gian tên.\n" + #: src/core/gnunet-service-core_clients.c:370 #, fuzzy msgid "# send requests dropped (disconnected)" @@ -608,7 +509,7 @@ msgstr "# các yêu cầu lỗ hổng bị bỏ do trọng tải" msgid "# messages discarded (session disconnected)" msgstr "# các thông báo được chắp liền" -#: src/core/gnunet-service-core_clients.c:818 +#: src/core/gnunet-service-core_clients.c:518 #, fuzzy, c-format msgid "# bytes of messages of type %u received" msgstr "# các byte nhiễu được nhận" @@ -654,7 +555,7 @@ msgid "# SET_KEY messages decrypted" msgstr "# các thông báo được chắp liền" #: src/core/gnunet-service-core_kx.c:977 -#: src/transport/gnunet-service-transport_validation.c:810 +#: src/transport/gnunet-service-transport_validation.c:865 #, fuzzy msgid "# PING messages received" msgstr "# các thông báo PING được tạo" @@ -682,7 +583,7 @@ msgid "# keepalive messages sent" msgstr "# các thông báo PING nhập thô được gửi" #: src/core/gnunet-service-core_kx.c:1236 -#: src/transport/gnunet-service-transport_validation.c:1031 +#: src/transport/gnunet-service-transport_validation.c:1161 #, fuzzy msgid "# PONG messages received" msgstr "# các thông báo PONG đã mật mã được nhận" @@ -702,58 +603,49 @@ msgstr "# Các quảng cáo đồng đẳng được xác nhận qua PONG" msgid "# rekey operations confirmed via PONG" msgstr "# Các quảng cáo đồng đẳng được xác nhận qua PONG" -#: src/core/gnunet-service-core_kx.c:1381 -#: src/core/gnunet-service-core_kx.c:1398 +#: src/core/gnunet-service-core_kx.c:1383 +#: src/core/gnunet-service-core_kx.c:1400 #, fuzzy msgid "# SET_KEY and PING messages created" msgstr "# các thông báo PING được tạo" -#: src/core/gnunet-service-core_kx.c:1402 +#: src/core/gnunet-service-core_kx.c:1404 msgid "# REKEY operations performed" msgstr "" -#: src/core/gnunet-service-core_kx.c:1537 +#: src/core/gnunet-service-core_kx.c:1539 msgid "# failed to decrypt message (no session key)" msgstr "" -#: src/core/gnunet-service-core_kx.c:1577 -#: src/core/gnunet-service-core_kx.c:1602 +#: src/core/gnunet-service-core_kx.c:1579 +#: src/core/gnunet-service-core_kx.c:1604 #, fuzzy msgid "# bytes dropped (duplicates)" msgstr "# các byte loại bỏ bởi UDP (đi ra)" -#: src/core/gnunet-service-core_kx.c:1589 +#: src/core/gnunet-service-core_kx.c:1591 #, fuzzy msgid "# bytes dropped (out of sequence)" msgstr "# các byte loại bỏ bởi UDP (đi ra)" -#: src/core/gnunet-service-core_kx.c:1626 +#: src/core/gnunet-service-core_kx.c:1628 #, fuzzy, c-format -msgid "Message received far too old (%llu ms). Content ignored.\n" +msgid "Message received far too old (%s). Content ignored.\n" msgstr "Thông báo nhận được cũ hơn một ngày. Đã loại bỏ.\n" -#: src/core/gnunet-service-core_kx.c:1630 +#: src/core/gnunet-service-core_kx.c:1632 #, fuzzy msgid "# bytes dropped (ancient message)" msgstr "# các byte loại bỏ bởi UDP (đi ra)" -#: src/core/gnunet-service-core_kx.c:1638 +#: src/core/gnunet-service-core_kx.c:1640 #, fuzzy msgid "# bytes of payload decrypted" msgstr "# các byte đã giải mã" -#: src/core/gnunet-service-core_kx.c:1700 -#, fuzzy -msgid "Core service is lacking HOSTKEY configuration setting. Exiting.\n" -msgstr "Lưu cấu hình ngay bây giờ không?" - -#: src/core/gnunet-service-core_kx.c:1708 -msgid "Core service could not access hostkey. Exiting.\n" -msgstr "" - -#: src/core/gnunet-service-core_kx.c:1718 src/hostlist/hostlist-server.c:551 -#: src/peerinfo-tool/gnunet-peerinfo.c:823 -#: src/transport/gnunet-service-transport.c:611 +#: src/core/gnunet-service-core_kx.c:1703 src/hostlist/hostlist-server.c:552 +#: src/peerinfo-tool/gnunet-peerinfo.c:547 +#: src/transport/gnunet-service-transport.c:644 #, fuzzy msgid "Could not access PEERINFO service. Exiting.\n" msgstr "Không thể truy cập đến thông tin về không gian tên.\n" @@ -772,23 +664,23 @@ msgstr "" msgid "# encrypted bytes given to transport" msgstr "" -#: src/core/gnunet-service-core_neighbours.c:418 +#: src/core/gnunet-service-core_neighbours.c:421 #, c-format msgid "Unsupported message of type %u (%u bytes) received from peer `%s'\n" msgstr "" #: src/core/gnunet-service-core_sessions.c:206 #: src/core/gnunet-service-core_sessions.c:269 -#: src/dht/gnunet-service-dht_neighbours.c:625 -#: src/dht/gnunet-service-dht_neighbours.c:683 -#: src/fs/gnunet-service-fs_cp.c:615 src/fs/gnunet-service-fs_cp.c:1532 -#: src/topology/gnunet-daemon-topology.c:709 -#: src/topology/gnunet-daemon-topology.c:810 -#: src/transport/gnunet-service-transport_neighbours.c:874 -#: src/transport/gnunet-service-transport_neighbours.c:1080 -#: src/transport/gnunet-service-transport_neighbours.c:1089 -#: src/transport/gnunet-service-transport_neighbours.c:2568 -#: src/transport/gnunet-service-transport_neighbours.c:2814 +#: src/dht/gnunet-service-dht_neighbours.c:645 +#: src/dht/gnunet-service-dht_neighbours.c:703 +#: src/fs/gnunet-service-fs_cp.c:630 src/fs/gnunet-service-fs_cp.c:1544 +#: src/topology/gnunet-daemon-topology.c:704 +#: src/topology/gnunet-daemon-topology.c:805 +#: src/transport/gnunet-service-transport_neighbours.c:1052 +#: src/transport/gnunet-service-transport_neighbours.c:1276 +#: src/transport/gnunet-service-transport_neighbours.c:1285 +#: src/transport/gnunet-service-transport_neighbours.c:2826 +#: src/transport/gnunet-service-transport_neighbours.c:3089 #, fuzzy msgid "# peers connected" msgstr "# của các đồng đẳng đã kết nối" @@ -812,40 +704,52 @@ msgstr "# các thông báo phát hiện dht được nhận" msgid "# updates to my type map" msgstr "" -#: src/datacache/datacache.c:115 src/datacache/datacache.c:250 +#: src/datacache/datacache.c:115 src/datacache/datacache.c:266 #: src/datastore/gnunet-service-datastore.c:834 #, fuzzy msgid "# bytes stored" msgstr "# các byte trong kho dữ liệu" -#: src/datacache/datacache.c:141 src/datacache/datacache.c:148 +#: src/datacache/datacache.c:117 src/datacache/datacache.c:268 +#, fuzzy +msgid "# items stored" +msgstr "# các byte trong kho dữ liệu" + +#: src/datacache/datacache.c:143 src/datacache/datacache.c:150 #: src/datastore/gnunet-service-datastore.c:1483 #: src/datastore/gnunet-service-datastore.c:1494 #, c-format msgid "No `%s' specified for `%s' in configuration!\n" msgstr "" -#: src/datacache/datacache.c:180 +#: src/datacache/datacache.c:184 #, c-format msgid "Loading `%s' datacache plugin\n" msgstr "" -#: src/datacache/datacache.c:188 +#: src/datacache/datacache.c:192 #, fuzzy, c-format msgid "Failed to load datacache plugin for `%s'\n" msgstr "Lỗi cập nhật dữ liệu cho mô-đun « %s »\n" -#: src/datacache/datacache.c:276 +#: src/datacache/datacache.c:295 #, fuzzy msgid "# requests received" msgstr "# các yêu cầu get (lấy) dht được nhận" -#: src/datacache/datacache.c:284 +#: src/datacache/datacache.c:304 msgid "# requests filtered by bloom filter" msgstr "# các yêu cầu được lọc theo bộ lọc bloom" -#: src/datacache/plugin_datacache_mysql.c:97 -#: src/datacache/plugin_datacache_mysql.c:104 +#: src/datacache/plugin_datacache_heap.c:406 +#, fuzzy +msgid "Heap datacache running\n" +msgstr "kho dữ liệu sqlite" + +#: src/datacache/plugin_datacache_postgres.c:392 +msgid "Postgres datacache running\n" +msgstr "" + #: src/datacache/plugin_datacache_sqlite.c:69 #: src/datacache/plugin_datacache_sqlite.c:72 #: src/datastore/plugin_datastore_mysql.c:803 @@ -853,58 +757,51 @@ msgstr "# các yêu cầu được lọc theo bộ lọc bloom" #: src/datastore/plugin_datastore_sqlite.c:57 src/mysql/mysql.c:41 #: src/mysql/mysql.c:48 src/mysql/mysql.c:522 src/mysql/mysql.c:531 #: src/mysql/mysql.c:591 src/mysql/mysql.c:607 -#: src/namestore/plugin_namestore_sqlite.c:51 src/util/crypto_ksk.c:49 -#: src/util/crypto_rsa.c:67 src/include/gnunet_common.h:525 -#: src/include/gnunet_common.h:532 +#: src/namestore/plugin_namestore_postgres.c:52 +#: src/namestore/plugin_namestore_sqlite.c:51 src/util/crypto_ecc.c:46 +#: src/util/crypto_ksk.c:49 src/util/crypto_rsa.c:59 +#: src/include/gnunet_common.h:607 src/include/gnunet_common.h:614 #, c-format msgid "`%s' failed at %s:%d with error: %s\n" msgstr "« %s » bị lỗi tại %s:%d với lỗi: %s\n" -#: src/datacache/plugin_datacache_mysql.c:450 -msgid "MySQL datacache running\n" -msgstr "" - -#: src/datacache/plugin_datacache_postgres.c:367 -msgid "Postgres datacache running\n" -msgstr "" - -#: src/datacache/plugin_datacache_sqlite.c:410 +#: src/datacache/plugin_datacache_sqlite.c:450 msgid "Sqlite datacache running\n" msgstr "" -#: src/datacache/plugin_datacache_sqlite.c:443 -#: src/datastore/plugin_datastore_sqlite.c:408 -#: src/namestore/plugin_namestore_sqlite.c:370 +#: src/datacache/plugin_datacache_sqlite.c:484 +#: src/datastore/plugin_datastore_sqlite.c:401 +#: src/namestore/plugin_namestore_sqlite.c:362 msgid "Tried to close sqlite without finalizing all prepared statements.\n" msgstr "" -#: src/datacache/plugin_datacache_sqlite.c:450 +#: src/datacache/plugin_datacache_sqlite.c:491 #, fuzzy, c-format msgid "Failed to close statement %p: %d\n" msgstr "Lỗi đọc danh sách bạn bè từ « %s »\n" -#: src/datacache/plugin_datacache_template.c:121 +#: src/datacache/plugin_datacache_template.c:125 msgid "Template datacache running\n" msgstr "" -#: src/datastore/datastore_api.c:305 +#: src/datastore/datastore_api.c:310 msgid "Failed to transmit request to drop database.\n" msgstr "" -#: src/datastore/datastore_api.c:388 +#: src/datastore/datastore_api.c:393 msgid "# queue entry timeouts" msgstr "" -#: src/datastore/datastore_api.c:432 +#: src/datastore/datastore_api.c:437 msgid "# queue overflows" msgstr "" -#: src/datastore/datastore_api.c:459 +#: src/datastore/datastore_api.c:465 #, fuzzy msgid "# queue entries created" msgstr "# các truy vấn lỗ hổng được định tuyến" -#: src/datastore/datastore_api.c:477 +#: src/datastore/datastore_api.c:483 #, fuzzy msgid "# Requests dropped from datastore queue" msgstr "# các yêu cầu lỗ hổng bị bỏ do trọng tải" @@ -914,73 +811,69 @@ msgstr "# các yêu cầu lỗ hổng bị bỏ do trọng tải" msgid "# datastore connections (re)created" msgstr "# các kết nối dht" -#: src/datastore/datastore_api.c:548 -msgid "# reconnected to DATASTORE" -msgstr "" - -#: src/datastore/datastore_api.c:612 +#: src/datastore/datastore_api.c:608 #, fuzzy msgid "# transmission request failures" msgstr "# các sự truyền PONG bị lỗi" -#: src/datastore/datastore_api.c:633 +#: src/datastore/datastore_api.c:630 #, fuzzy msgid "# bytes sent to datastore" msgstr "# các byte trong kho dữ liệu" -#: src/datastore/datastore_api.c:764 +#: src/datastore/datastore_api.c:762 #, fuzzy msgid "Failed to receive status response from database." msgstr "" "\n" "Không nhận được đáp ứng từ gnunetd.\n" -#: src/datastore/datastore_api.c:778 +#: src/datastore/datastore_api.c:776 msgid "Error reading response from datastore service" msgstr "" -#: src/datastore/datastore_api.c:790 src/datastore/datastore_api.c:796 +#: src/datastore/datastore_api.c:788 src/datastore/datastore_api.c:794 #, fuzzy msgid "Invalid error message received from datastore service" msgstr "Nhận được thông báo « %s » sai từ đồng đẳng « %s ».\n" -#: src/datastore/datastore_api.c:800 +#: src/datastore/datastore_api.c:798 #, fuzzy msgid "# status messages received" msgstr "# các thông báo phát hiện dht được nhận" -#: src/datastore/datastore_api.c:869 +#: src/datastore/datastore_api.c:867 #, fuzzy msgid "# PUT requests executed" msgstr "# các yêu cầu dht được định tuyến" -#: src/datastore/datastore_api.c:936 +#: src/datastore/datastore_api.c:934 #, fuzzy msgid "# RESERVE requests executed" msgstr "# các yêu cầu dht được định tuyến" -#: src/datastore/datastore_api.c:997 +#: src/datastore/datastore_api.c:995 msgid "# RELEASE RESERVE requests executed" msgstr "" -#: src/datastore/datastore_api.c:1054 +#: src/datastore/datastore_api.c:1052 #, fuzzy msgid "# UPDATE requests executed" msgstr "# các yêu cầu dht được định tuyến" -#: src/datastore/datastore_api.c:1118 +#: src/datastore/datastore_api.c:1116 #, fuzzy msgid "# REMOVE requests executed" msgstr "# các yêu cầu dht được định tuyến" -#: src/datastore/datastore_api.c:1163 +#: src/datastore/datastore_api.c:1161 #, fuzzy msgid "Failed to receive response from database.\n" msgstr "" "\n" "Không nhận được đáp ứng từ gnunetd.\n" -#: src/datastore/datastore_api.c:1221 +#: src/datastore/datastore_api.c:1220 #, fuzzy msgid "# Results received" msgstr "# các kết quả dht được nhận" @@ -993,7 +886,7 @@ msgstr "" msgid "# GET ZERO ANONYMITY requests executed" msgstr "" -#: src/datastore/datastore_api.c:1409 +#: src/datastore/datastore_api.c:1410 #, fuzzy msgid "# GET requests executed" msgstr "# các yêu cầu dht được định tuyến" @@ -1008,10 +901,12 @@ msgid "# bytes purged (low-priority)" msgstr "" #: src/datastore/gnunet-service-datastore.c:480 +#: src/gns/gnunet-gns-helper-service-w32.c:159 msgid "Transmission to client failed!\n" msgstr "" #: src/datastore/gnunet-service-datastore.c:511 +#: src/gns/gnunet-gns-helper-service-w32.c:189 msgid "Shutdown in progress, aborting transmission.\n" msgstr "" @@ -1153,6 +1048,11 @@ msgstr "" msgid "Bloomfilter construction complete.\n" msgstr "" +#: src/datastore/plugin_datastore_heap.c:820 +#, fuzzy +msgid "Heap database running\n" +msgstr "kho dữ liệu sqlite" + #: src/datastore/plugin_datastore_mysql.c:780 #, fuzzy, c-format msgid "Failed to prepare statement `%s'\n" @@ -1175,6 +1075,7 @@ msgstr "" "Không nhận được đáp ứng từ gnunetd.\n" #: src/datastore/plugin_datastore_postgres.c:860 +#: src/namestore/plugin_namestore_postgres.c:652 msgid "Postgres database running\n" msgstr "" @@ -1183,221 +1084,238 @@ msgstr "" msgid "`%s' failed at %s:%u with error: %s" msgstr "« %s » bị lỗi tại %s:%d với lỗi: %s" -#: src/datastore/plugin_datastore_sqlite.c:233 -#: src/namestore/plugin_namestore_sqlite.c:204 -#, c-format -msgid "Option `%s' in section `%s' missing in configuration!\n" -msgstr "" - -#: src/datastore/plugin_datastore_sqlite.c:260 -#: src/namestore/plugin_namestore_sqlite.c:229 +#: src/datastore/plugin_datastore_sqlite.c:253 +#: src/namestore/plugin_namestore_sqlite.c:223 #, c-format msgid "Unable to initialize SQLite: %s.\n" msgstr "Không thể sơ khởi SQLite: %s.\n" -#: src/datastore/plugin_datastore_sqlite.c:655 +#: src/datastore/plugin_datastore_sqlite.c:648 #, fuzzy msgid "Invalid data in database. Trying to fix (by deletion).\n" msgstr "Dữ liệu sai trong %s. Đang thử sửa chữa (bằng cách xoá).\n" -#: src/datastore/plugin_datastore_sqlite.c:1139 +#: src/datastore/plugin_datastore_sqlite.c:1134 msgid "sqlite version to old to determine size, assuming zero\n" msgstr "" -#: src/datastore/plugin_datastore_sqlite.c:1158 +#: src/datastore/plugin_datastore_sqlite.c:1153 #, c-format msgid "" "Using sqlite page utilization to estimate payload (%llu pages of size %llu " "bytes)\n" msgstr "" -#: src/datastore/plugin_datastore_sqlite.c:1198 -#: src/namestore/plugin_namestore_sqlite.c:829 +#: src/datastore/plugin_datastore_sqlite.c:1193 +#: src/namestore/plugin_namestore_sqlite.c:827 #, fuzzy msgid "Sqlite database running\n" msgstr "kho dữ liệu sqlite" -#: src/datastore/plugin_datastore_template.c:241 +#: src/datastore/plugin_datastore_template.c:257 msgid "Template database running\n" msgstr "" -#: src/dht/dht_api.c:348 +#: src/dht/dht_api.c:375 #, fuzzy msgid "Failed to connect to the DHT service!\n" msgstr "Lỗi kết nối đến gnunetd.\n" -#: src/dht/gnunet-dht-get.c:201 src/dht/gnunet-dht-monitor.c:293 -#: src/dht/gnunet-dht-put.c:192 +#: src/dht/gnunet-dht-get.c:132 +#, c-format +msgid "" +"Result %d, type %d:\n" +"%.*s\n" +msgstr "" + +#: src/dht/gnunet-dht-get.c:156 +msgid "Must provide key for DHT GET!\n" +msgstr "" + +#: src/dht/gnunet-dht-get.c:162 src/dht/gnunet-dht-monitor.c:225 +#, fuzzy +msgid "Failed to connect to DHT service!\n" +msgstr "Lỗi kết nối đến gnunetd.\n" + +#: src/dht/gnunet-dht-get.c:170 +msgid "Issueing DHT GET with key" +msgstr "" + +#: src/dht/gnunet-dht-get.c:186 src/dht/gnunet-dht-monitor.c:262 +#: src/dht/gnunet-dht-put.c:198 msgid "the query key" msgstr "" -#: src/dht/gnunet-dht-get.c:204 +#: src/dht/gnunet-dht-get.c:189 msgid "how many parallel requests (replicas) to create" msgstr "" -#: src/dht/gnunet-dht-get.c:207 src/dht/gnunet-dht-monitor.c:296 +#: src/dht/gnunet-dht-get.c:192 src/dht/gnunet-dht-monitor.c:265 msgid "the type of data to look for" msgstr "" -#: src/dht/gnunet-dht-get.c:210 src/dht/gnunet-dht-put.c:201 +#: src/dht/gnunet-dht-get.c:195 src/dht/gnunet-dht-put.c:210 msgid "how long to execute this query before giving up?" msgstr "" -#: src/dht/gnunet-dht-get.c:213 src/dht/gnunet-dht-monitor.c:302 -#: src/dht/gnunet-dht-put.c:204 src/fs/gnunet-download.c:271 -#: src/fs/gnunet-publish.c:731 src/fs/gnunet-search.c:297 -#: src/fs/gnunet-unindex.c:169 src/nse/gnunet-nse-profiler.c:910 +#: src/dht/gnunet-dht-get.c:198 src/dht/gnunet-dht-put.c:201 +msgid "use DHT's demultiplex everywhere option" +msgstr "" + +#: src/dht/gnunet-dht-get.c:201 src/dht/gnunet-dht-monitor.c:271 +#: src/dht/gnunet-dht-put.c:213 src/fs/gnunet-auto-share.c:753 +#: src/fs/gnunet-download.c:328 src/fs/gnunet-publish.c:736 +#: src/fs/gnunet-search.c:294 src/fs/gnunet-unindex.c:168 +#: src/nse/gnunet-nse-profiler.c:1033 msgid "be verbose (print progress information)" msgstr "" -#: src/dht/gnunet-dht-get.c:232 +#: src/dht/gnunet-dht-get.c:222 msgid "Issue a GET request to the GNUnet DHT, prints results." msgstr "" -#: src/dht/gnunet-dht-monitor.c:299 -msgid "how long to execute? 0 = forever" +#: src/dht/gnunet-dht-monitor.c:268 +msgid "how long should the monitor command run" msgstr "" -#: src/dht/gnunet-dht-monitor.c:321 +#: src/dht/gnunet-dht-monitor.c:293 msgid "Prints all packets that go through the DHT." msgstr "" -#: src/dht/gnunet-dht-put.c:108 +#: src/dht/gnunet-dht-put.c:118 #, fuzzy -msgid "PUT request sent!\n" +msgid "PUT request sent with key" msgstr "# độ tin cậy được tiêu phí" -#: src/dht/gnunet-dht-put.c:111 +#: src/dht/gnunet-dht-put.c:121 msgid "Timeout sending PUT request!\n" msgstr "" -#: src/dht/gnunet-dht-put.c:114 +#: src/dht/gnunet-dht-put.c:124 #, fuzzy msgid "PUT request not confirmed!\n" msgstr "# độ tin cậy được tiêu phí" -#: src/dht/gnunet-dht-put.c:144 +#: src/dht/gnunet-dht-put.c:153 msgid "Must provide KEY and DATA for DHT put!\n" msgstr "" -#: src/dht/gnunet-dht-put.c:152 +#: src/dht/gnunet-dht-put.c:160 #, fuzzy, c-format msgid "Could not connect to %s service!\n" msgstr "Không thể kết nối tới %s:%u: %s\n" -#: src/dht/gnunet-dht-put.c:157 -#, fuzzy, c-format -msgid "Connected to %s service!\n" -msgstr "« %s » được kết nối tới « %s ».\n" - -#: src/dht/gnunet-dht-put.c:172 +#: src/dht/gnunet-dht-put.c:176 #, c-format msgid "Issuing put request for `%s' with data `%s'!\n" msgstr "" -#: src/dht/gnunet-dht-put.c:186 +#: src/dht/gnunet-dht-put.c:192 msgid "the data to insert under the key" msgstr "" -#: src/dht/gnunet-dht-put.c:189 +#: src/dht/gnunet-dht-put.c:195 msgid "how long to store this entry in the dht (in seconds)" msgstr "" -#: src/dht/gnunet-dht-put.c:195 +#: src/dht/gnunet-dht-put.c:204 msgid "how many replicas to create" msgstr "" -#: src/dht/gnunet-dht-put.c:198 +#: src/dht/gnunet-dht-put.c:207 msgid "the type to insert data as" msgstr "" -#: src/dht/gnunet-dht-put.c:223 +#: src/dht/gnunet-dht-put.c:235 msgid "Issue a PUT request to the GNUnet DHT insert DATA under KEY." msgstr "" -#: src/dht/gnunet-service-dht.c:163 src/testing/testing.c:544 -#: src/testing/testing.c:1968 src/testing/testing.c:1998 +#: src/dht/gnunet-service-dht.c:172 #, fuzzy msgid "Failed to connect to transport service!\n" msgstr "Lỗi kết nối đến gnunetd.\n" -#: src/dht/gnunet-service-dht_clients.c:407 +#: src/dht/gnunet-service-dht_clients.c:413 #, fuzzy msgid "# GET requests from clients injected" msgstr "# các yêu cầu get (lấy) dht được nhận" -#: src/dht/gnunet-service-dht_clients.c:500 +#: src/dht/gnunet-service-dht_clients.c:503 #, fuzzy msgid "# PUT requests received from clients" msgstr "# các đáp ứng lỗ hổng được gửi cho trình/máy khách" -#: src/dht/gnunet-service-dht_clients.c:584 +#: src/dht/gnunet-service-dht_clients.c:585 #, fuzzy msgid "# GET requests received from clients" msgstr "# các yêu cầu get (lấy) dht được nhận" -#: src/dht/gnunet-service-dht_clients.c:682 +#: src/dht/gnunet-service-dht_clients.c:791 #, fuzzy msgid "# GET STOP requests received from clients" msgstr "# các yêu cầu get (lấy) dht được nhận" -#: src/dht/gnunet-service-dht_clients.c:919 +#: src/dht/gnunet-service-dht_clients.c:1035 msgid "# Key match, type mismatches in REPLY to CLIENT" msgstr "" -#: src/dht/gnunet-service-dht_clients.c:932 +#: src/dht/gnunet-service-dht_clients.c:1048 msgid "# Duplicate REPLIES to CLIENT request dropped" msgstr "" -#: src/dht/gnunet-service-dht_clients.c:967 +#: src/dht/gnunet-service-dht_clients.c:1085 #, c-format msgid "Unsupported block type (%u) in request!\n" msgstr "" -#: src/dht/gnunet-service-dht_clients.c:989 +#: src/dht/gnunet-service-dht_clients.c:1108 msgid "# RESULTS queued for clients" msgstr "" -#: src/dht/gnunet-service-dht_clients.c:1038 -#: src/dht/gnunet-service-dht_clients.c:1081 +#: src/dht/gnunet-service-dht_clients.c:1157 +#: src/dht/gnunet-service-dht_clients.c:1199 msgid "# REPLIES ignored for CLIENTS (no match)" msgstr "" -#: src/dht/gnunet-service-dht_clients.c:1048 +#: src/dht/gnunet-service-dht_clients.c:1167 msgid "Could not pass reply to client, message too big!\n" msgstr "" -#: src/dht/gnunet-service-dht_datacache.c:93 +#: src/dht/gnunet-service-dht_datacache.c:64 #, fuzzy, c-format msgid "%s request received, but have no datacache!\n" msgstr "# các byte kiểu %d được nhận" -#: src/dht/gnunet-service-dht_datacache.c:103 +#: src/dht/gnunet-service-dht_datacache.c:74 msgid "# ITEMS stored in datacache" msgstr "" -#: src/dht/gnunet-service-dht_datacache.c:207 +#: src/dht/gnunet-service-dht_datacache.c:159 msgid "# Good RESULTS found in datacache" msgstr "" -#: src/dht/gnunet-service-dht_datacache.c:218 +#: src/dht/gnunet-service-dht_datacache.c:170 msgid "# Duplicate RESULTS found in datacache" msgstr "" -#: src/dht/gnunet-service-dht_datacache.c:224 +#: src/dht/gnunet-service-dht_datacache.c:176 msgid "# Invalid RESULTS found in datacache" msgstr "" -#: src/dht/gnunet-service-dht_datacache.c:236 +#: src/dht/gnunet-service-dht_datacache.c:182 +msgid "# Irrelevant RESULTS found in datacache" +msgstr "" + +#: src/dht/gnunet-service-dht_datacache.c:194 msgid "# Unsupported RESULTS found in datacache" msgstr "" -#: src/dht/gnunet-service-dht_datacache.c:239 +#: src/dht/gnunet-service-dht_datacache.c:197 #, c-format msgid "Unsupported block type (%u) in local response!\n" msgstr "" -#: src/dht/gnunet-service-dht_datacache.c:269 +#: src/dht/gnunet-service-dht_datacache.c:227 #, fuzzy msgid "# GET requests given to datacache" msgstr "# các yêu cầu get (lấy) dht được nhận" @@ -1407,96 +1325,103 @@ msgstr "# các yêu cầu get (lấy) dht được nhận" msgid "# HELLOs obtained from peerinfo" msgstr "Nhận được thông báo « %s » sai từ đồng đẳng « %s ».\n" -#: src/dht/gnunet-service-dht_neighbours.c:481 +#: src/dht/gnunet-service-dht_neighbours.c:501 msgid "# Preference updates given to core" msgstr "" -#: src/dht/gnunet-service-dht_neighbours.c:571 +#: src/dht/gnunet-service-dht_neighbours.c:591 #, fuzzy msgid "# FIND PEER messages initiated" msgstr "# các thông báo PING được tạo" -#: src/dht/gnunet-service-dht_neighbours.c:717 +#: src/dht/gnunet-service-dht_neighbours.c:737 #, fuzzy msgid "# Queued messages discarded (peer disconnected)" msgstr "# các thông báo được chắp liền" -#: src/dht/gnunet-service-dht_neighbours.c:772 +#: src/dht/gnunet-service-dht_neighbours.c:792 #, fuzzy msgid "# Bytes transmitted to other peers" msgstr "# các byte kiểu %d được gửi " -#: src/dht/gnunet-service-dht_neighbours.c:810 +#: src/dht/gnunet-service-dht_neighbours.c:830 #, fuzzy -msgid "# Bytes of bandwdith requested from core" +msgid "# Bytes of bandwidth requested from core" msgstr "# các yêu cầu máy/trình khách lỗ hổng được phun vào" -#: src/dht/gnunet-service-dht_neighbours.c:1032 -#: src/dht/gnunet-service-dht_neighbours.c:1060 +#: src/dht/gnunet-service-dht_neighbours.c:1052 +#: src/dht/gnunet-service-dht_neighbours.c:1080 msgid "# Peers excluded from routing due to Bloomfilter" msgstr "" -#: src/dht/gnunet-service-dht_neighbours.c:1041 -#: src/dht/gnunet-service-dht_neighbours.c:1075 +#: src/dht/gnunet-service-dht_neighbours.c:1061 +#: src/dht/gnunet-service-dht_neighbours.c:1095 #, fuzzy msgid "# Peer selection failed" msgstr "# các cuộc gọi HTTP select (lựa chọn)" -#: src/dht/gnunet-service-dht_neighbours.c:1207 +#: src/dht/gnunet-service-dht_neighbours.c:1229 #, fuzzy msgid "# PUT requests routed" msgstr "# các yêu cầu dht được định tuyến" -#: src/dht/gnunet-service-dht_neighbours.c:1236 +#: src/dht/gnunet-service-dht_neighbours.c:1258 #, fuzzy msgid "# PUT messages queued for transmission" msgstr "# các thông báo PING được tạo" -#: src/dht/gnunet-service-dht_neighbours.c:1315 +#: src/dht/gnunet-service-dht_neighbours.c:1265 +#: src/dht/gnunet-service-dht_neighbours.c:1378 +#: src/dht/gnunet-service-dht_neighbours.c:1478 +#, fuzzy +msgid "# P2P messages dropped due to full queue" +msgstr "# các yêu cầu lỗ hổng bị bỏ do trọng tải" + +#: src/dht/gnunet-service-dht_neighbours.c:1343 #, fuzzy msgid "# GET requests routed" msgstr "# các yêu cầu dht được định tuyến" -#: src/dht/gnunet-service-dht_neighbours.c:1342 +#: src/dht/gnunet-service-dht_neighbours.c:1370 #, fuzzy msgid "# GET messages queued for transmission" msgstr "# các thông báo PING được tạo" -#: src/dht/gnunet-service-dht_neighbours.c:1443 +#: src/dht/gnunet-service-dht_neighbours.c:1485 #, fuzzy msgid "# RESULT messages queued for transmission" msgstr "# các thông báo PING được tạo" -#: src/dht/gnunet-service-dht_neighbours.c:1531 +#: src/dht/gnunet-service-dht_neighbours.c:1573 #, fuzzy msgid "# P2P PUT requests received" msgstr "# các yêu cầu get (lấy) dht được nhận" -#: src/dht/gnunet-service-dht_neighbours.c:1647 +#: src/dht/gnunet-service-dht_neighbours.c:1702 #, fuzzy msgid "# FIND PEER requests ignored due to Bloomfilter" msgstr "# các yêu cầu được lọc theo bộ lọc bloom" -#: src/dht/gnunet-service-dht_neighbours.c:1655 +#: src/dht/gnunet-service-dht_neighbours.c:1710 msgid "# FIND PEER requests ignored due to lack of HELLO" msgstr "" -#: src/dht/gnunet-service-dht_neighbours.c:1746 +#: src/dht/gnunet-service-dht_neighbours.c:1801 #, fuzzy msgid "# P2P GET requests received" msgstr "# các yêu cầu get (lấy) dht được nhận" -#: src/dht/gnunet-service-dht_neighbours.c:1788 +#: src/dht/gnunet-service-dht_neighbours.c:1843 #, fuzzy msgid "# P2P FIND PEER requests processed" msgstr "# các yêu cầu get (lấy) dht được nhận" -#: src/dht/gnunet-service-dht_neighbours.c:1802 +#: src/dht/gnunet-service-dht_neighbours.c:1857 #, fuzzy msgid "# P2P GET requests ONLY routed" msgstr "# các yêu cầu dht được định tuyến" -#: src/dht/gnunet-service-dht_neighbours.c:1876 +#: src/dht/gnunet-service-dht_neighbours.c:1944 #, fuzzy msgid "# P2P RESULTS received" msgstr "# Tín hiệu HTTP PUT được nhận" @@ -1518,18 +1443,27 @@ msgstr "" msgid "# Invalid REPLIES matched against routing table" msgstr "" -#: src/dht/gnunet-service-dht_routing.c:238 +#: src/dht/gnunet-service-dht_routing.c:232 +msgid "# Irrelevant REPLIES matched against routing table" +msgstr "" + +#: src/dht/gnunet-service-dht_routing.c:244 msgid "# Unsupported REPLIES matched against routing table" msgstr "" -#: src/dht/gnunet-service-dht_routing.c:311 +#: src/dht/gnunet-service-dht_routing.c:317 msgid "# Entries removed from routing table" msgstr "" -#: src/dht/gnunet-service-dht_routing.c:352 +#: src/dht/gnunet-service-dht_routing.c:400 msgid "# Entries added to routing table" msgstr "" +#: src/dht/gnunet-service-dht_routing.c:418 +#, fuzzy +msgid "# DHT requests combined" +msgstr "# các yêu cầu get (lấy) dht được nhận" + #: src/dht/plugin_block_dht.c:136 #, fuzzy, c-format msgid "Block not of type %u\n" @@ -1544,15 +1478,51 @@ msgstr "" msgid "Block of type %u is malformed\n" msgstr "" -#: src/dns/gnunet-dns-monitor.c:337 -msgid "only monitor DNS queries" -msgstr "" +#: src/dns/dnsparser.c:152 +#, fuzzy, c-format +msgid "Failed to convert DNS IDNA name `%s' to UTF-8: %s\n" +msgstr "Lỗi mở tập tin ghi sự kiện « %s »: %s\n" -#: src/dns/gnunet-dns-monitor.c:340 -msgid "only monitor DNS replies" -msgstr "" +#: src/dns/dnsparser.c:626 +#, fuzzy, c-format +msgid "Failed to convert UTF-8 name `%s' to DNS IDNA format: %s\n" +msgstr "Lỗi mở tập tin ghi sự kiện « %s »: %s\n" -#: src/dns/gnunet-dns-monitor.c:348 +#: src/dns/dnsstub.c:175 +#, fuzzy, c-format +msgid "Could not bind to any port: %s\n" +msgstr "Không tìm thấy địa chỉ IP của máy « %s »: %s\n" + +#: src/dns/dnsstub.c:295 src/dns/dnsstub.c:383 +#: src/gns/gnunet-service-gns_resolver.c:1621 +#, fuzzy, c-format +msgid "Failed to send DNS request to %s\n" +msgstr "Lỗi mở tập tin ghi sự kiện « %s »: %s\n" + +#: src/dns/dnsstub.c:299 +#, fuzzy, c-format +msgid "Sent DNS request to %s\n" +msgstr "Lỗi mở tập tin ghi sự kiện « %s »: %s\n" + +#: src/dns/dnsstub.c:368 +#, c-format +msgid "Configured DNS exit `%s' is not working / valid.\n" +msgstr "" + +#: src/dns/dnsstub.c:440 +#, c-format +msgid "Received DNS response that is too small (%u bytes)" +msgstr "" + +#: src/dns/gnunet-dns-monitor.c:355 +msgid "only monitor DNS queries" +msgstr "" + +#: src/dns/gnunet-dns-monitor.c:358 +msgid "only monitor DNS replies" +msgstr "" + +#: src/dns/gnunet-dns-monitor.c:369 msgid "Monitor DNS queries." msgstr "" @@ -1564,77 +1534,59 @@ msgstr "" msgid "set AAAA records" msgstr "" -#: src/dns/gnunet-dns-redirector.c:247 +#: src/dns/gnunet-dns-redirector.c:251 msgid "Change DNS replies to point elsewhere." msgstr "" -#: src/dns/gnunet-service-dns.c:485 -#, fuzzy, c-format -msgid "Could not bind to any port: %s\n" -msgstr "Không tìm thấy địa chỉ IP của máy « %s »: %s\n" - -#: src/dns/gnunet-service-dns.c:639 +#: src/dns/gnunet-service-dns.c:456 msgid "# DNS requests answered via TUN interface" msgstr "" -#: src/dns/gnunet-service-dns.c:822 +#: src/dns/gnunet-service-dns.c:603 msgid "# DNS exit failed (failed to open socket)" msgstr "" -#: src/dns/gnunet-service-dns.c:1005 -#, c-format -msgid "Received DNS response that is too small (%u bytes)" -msgstr "" - -#: src/dns/gnunet-service-dns.c:1050 +#: src/dns/gnunet-service-dns.c:714 msgid "# External DNS response discarded (no matching request)" msgstr "" -#: src/dns/gnunet-service-dns.c:1168 +#: src/dns/gnunet-service-dns.c:792 msgid "# Client response discarded (no matching request)" msgstr "" -#: src/dns/gnunet-service-dns.c:1281 +#: src/dns/gnunet-service-dns.c:907 msgid "Received malformed IPv4-UDP packet on TUN interface.\n" msgstr "" -#: src/dns/gnunet-service-dns.c:1297 +#: src/dns/gnunet-service-dns.c:923 msgid "Received malformed IPv6-UDP packet on TUN interface.\n" msgstr "" -#: src/dns/gnunet-service-dns.c:1306 +#: src/dns/gnunet-service-dns.c:932 #, c-format msgid "Got non-IP packet with %u bytes and protocol %u from TUN\n" msgstr "" -#: src/dns/gnunet-service-dns.c:1315 +#: src/dns/gnunet-service-dns.c:942 msgid "# Non-DNS UDP packet received via TUN interface" msgstr "" -#: src/dns/gnunet-service-dns.c:1380 +#: src/dns/gnunet-service-dns.c:1009 #, fuzzy msgid "# DNS requests received via TUN interface" msgstr "# các đáp ứng lỗ hổng được gửi cho trình/máy khách" -#: src/dns/gnunet-service-dns.c:1465 -#, c-format -msgid "Configured DNS exit `%s' is not working / valid.\n" -msgstr "" - -#: src/dns/gnunet-service-dns.c:1497 src/exit/gnunet-daemon-exit.c:2674 -msgid "# Inbound MESH tunnels created" -msgstr "" - -#: src/dns/gnunet-service-dns.c:1561 src/exit/gnunet-daemon-exit.c:3032 +#: src/dns/gnunet-service-dns.c:1049 src/exit/gnunet-daemon-exit.c:3351 #, c-format msgid "`%s' must be installed SUID, refusing to run\n" msgstr "" -#: src/dns/gnunet-service-dns.c:1581 -msgid "Configured to provide DNS exit, but no valid DNS server configured!\n" -msgstr "" +#: src/dns/gnunet-service-dns.c:1069 src/exit/gnunet-daemon-exit.c:3407 +#, fuzzy +msgid "need a valid IPv4 or IPv6 address\n" +msgstr "Mức ưu tiên tiến trình không hợp lê « %s ».\n" -#: src/dv/dv_api.c:179 +#: src/dv/dv_api.c:189 #, fuzzy msgid "Failed to connect to the dv service!\n" msgstr "Lỗi kết nối đến gnunetd.\n" @@ -1644,205 +1596,209 @@ msgstr "Lỗi kết nối đến gnunetd.\n" msgid "%s Received message from %s of type %d, distance %u!\n" msgstr "Nhận được thông báo bị hỏng từ đồng đẳng « %s » trong %s:%d.\n" -#: src/exit/gnunet-daemon-exit.c:508 +#: src/exit/gnunet-daemon-exit.c:741 #, c-format msgid "Got duplicate service records for `%s:%u'\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:563 +#: src/exit/gnunet-daemon-exit.c:794 #, fuzzy msgid "# Bytes transmitted via mesh tunnels" msgstr "# các byte được gửi" -#: src/exit/gnunet-daemon-exit.c:679 src/exit/gnunet-daemon-exit.c:2069 -#: src/exit/gnunet-daemon-exit.c:2319 src/vpn/gnunet-service-vpn.c:1394 -#: src/vpn/gnunet-service-vpn.c:1795 src/vpn/gnunet-service-vpn.c:1958 +#: src/exit/gnunet-daemon-exit.c:911 src/exit/gnunet-daemon-exit.c:2343 +#: src/exit/gnunet-daemon-exit.c:2603 src/vpn/gnunet-service-vpn.c:1411 +#: src/vpn/gnunet-service-vpn.c:1812 src/vpn/gnunet-service-vpn.c:1975 msgid "# ICMPv4 packets dropped (type not allowed)" msgstr "" -#: src/exit/gnunet-daemon-exit.c:716 src/exit/gnunet-daemon-exit.c:2128 -#: src/exit/gnunet-daemon-exit.c:2378 src/vpn/gnunet-service-vpn.c:1450 -#: src/vpn/gnunet-service-vpn.c:1854 src/vpn/gnunet-service-vpn.c:1991 +#: src/exit/gnunet-daemon-exit.c:948 src/exit/gnunet-daemon-exit.c:2402 +#: src/exit/gnunet-daemon-exit.c:2662 src/vpn/gnunet-service-vpn.c:1467 +#: src/vpn/gnunet-service-vpn.c:1871 src/vpn/gnunet-service-vpn.c:2008 msgid "# ICMPv6 packets dropped (type not allowed)" msgstr "" -#: src/exit/gnunet-daemon-exit.c:756 +#: src/exit/gnunet-daemon-exit.c:988 msgid "# ICMP packets dropped (not allowed)" msgstr "" -#: src/exit/gnunet-daemon-exit.c:763 +#: src/exit/gnunet-daemon-exit.c:995 msgid "ICMP Packet dropped, have no matching connection information\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:840 +#: src/exit/gnunet-daemon-exit.c:1072 msgid "UDP Packet dropped, have no matching connection information\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:915 +#: src/exit/gnunet-daemon-exit.c:1147 msgid "TCP Packet dropped, have no matching connection information\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:968 +#: src/exit/gnunet-daemon-exit.c:1200 #, fuzzy msgid "# Packets received from TUN" msgstr "# các byte đã nhận qua HTTP" -#: src/exit/gnunet-daemon-exit.c:982 +#: src/exit/gnunet-daemon-exit.c:1214 #, fuzzy msgid "# Bytes received from TUN" msgstr "# các byte đã nhận qua HTTP" -#: src/exit/gnunet-daemon-exit.c:1008 +#: src/exit/gnunet-daemon-exit.c:1240 msgid "IPv4 packet options received. Ignored.\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:1035 +#: src/exit/gnunet-daemon-exit.c:1267 #, c-format msgid "IPv4 packet with unsupported next header %u received. Ignored.\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:1081 +#: src/exit/gnunet-daemon-exit.c:1313 #, c-format msgid "IPv6 packet with unsupported next header %d received. Ignored.\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:1089 +#: src/exit/gnunet-daemon-exit.c:1321 #, c-format msgid "Packet from unknown protocol %u received. Ignored.\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:1471 +#: src/exit/gnunet-daemon-exit.c:1703 #, fuzzy msgid "# TCP packets sent via TUN" msgstr "# các byte đã gửi qua UDP" -#: src/exit/gnunet-daemon-exit.c:1571 +#: src/exit/gnunet-daemon-exit.c:1814 #, fuzzy msgid "# TCP service creation requests received via mesh" msgstr "# các yêu cầu danh sách máy được nhận" -#: src/exit/gnunet-daemon-exit.c:1574 src/exit/gnunet-daemon-exit.c:1653 -#: src/exit/gnunet-daemon-exit.c:1763 src/exit/gnunet-daemon-exit.c:1993 -#: src/exit/gnunet-daemon-exit.c:2235 src/exit/gnunet-daemon-exit.c:2516 -#: src/exit/gnunet-daemon-exit.c:2616 +#: src/exit/gnunet-daemon-exit.c:1817 src/exit/gnunet-daemon-exit.c:1906 +#: src/exit/gnunet-daemon-exit.c:2026 src/exit/gnunet-daemon-exit.c:2267 +#: src/exit/gnunet-daemon-exit.c:2519 src/exit/gnunet-daemon-exit.c:2811 +#: src/exit/gnunet-daemon-exit.c:2921 #, fuzzy msgid "# Bytes received from MESH" msgstr "# các byte đã nhận qua HTTP" -#: src/exit/gnunet-daemon-exit.c:1607 src/exit/gnunet-daemon-exit.c:2638 +#: src/exit/gnunet-daemon-exit.c:1850 src/exit/gnunet-daemon-exit.c:2943 #, c-format msgid "No service found for %s on port %d!\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:1611 +#: src/exit/gnunet-daemon-exit.c:1854 #, fuzzy msgid "# TCP requests dropped (no such service)" msgstr "# các yêu cầu lỗ hổng bị bỏ do trọng tải" -#: src/exit/gnunet-daemon-exit.c:1656 +#: src/exit/gnunet-daemon-exit.c:1909 #, fuzzy msgid "# TCP IP-exit creation requests received via mesh" msgstr "# các yêu cầu danh sách máy được nhận" -#: src/exit/gnunet-daemon-exit.c:1766 +#: src/exit/gnunet-daemon-exit.c:2029 #, fuzzy msgid "# TCP data requests received via mesh" msgstr "# các yêu cầu get (lấy) dht được nhận" -#: src/exit/gnunet-daemon-exit.c:1780 +#: src/exit/gnunet-daemon-exit.c:2043 #, fuzzy msgid "# TCP DATA requests dropped (no session)" msgstr "# các yêu cầu lỗ hổng bị bỏ do trọng tải" -#: src/exit/gnunet-daemon-exit.c:1830 +#: src/exit/gnunet-daemon-exit.c:2093 #, fuzzy msgid "# ICMP packets sent via TUN" msgstr "# các byte đã gửi qua UDP" -#: src/exit/gnunet-daemon-exit.c:1996 +#: src/exit/gnunet-daemon-exit.c:2270 #, fuzzy msgid "# ICMP IP-exit requests received via mesh" msgstr "# các yêu cầu get (lấy) dht được nhận" -#: src/exit/gnunet-daemon-exit.c:2238 +#: src/exit/gnunet-daemon-exit.c:2522 #, fuzzy msgid "# ICMP service requests received via mesh" msgstr "# các đáp ứng lỗ hổng được gửi cho trình/máy khách" -#: src/exit/gnunet-daemon-exit.c:2304 src/vpn/gnunet-service-vpn.c:1384 -#: src/vpn/gnunet-service-vpn.c:1952 +#: src/exit/gnunet-daemon-exit.c:2588 src/vpn/gnunet-service-vpn.c:1401 +#: src/vpn/gnunet-service-vpn.c:1969 msgid "# ICMPv4 packets dropped (impossible PT to v6)" msgstr "" -#: src/exit/gnunet-daemon-exit.c:2363 src/vpn/gnunet-service-vpn.c:1420 -#: src/vpn/gnunet-service-vpn.c:1432 src/vpn/gnunet-service-vpn.c:1842 +#: src/exit/gnunet-daemon-exit.c:2647 src/vpn/gnunet-service-vpn.c:1437 +#: src/vpn/gnunet-service-vpn.c:1449 src/vpn/gnunet-service-vpn.c:1859 msgid "# ICMPv6 packets dropped (impossible PT to v4)" msgstr "" -#: src/exit/gnunet-daemon-exit.c:2413 +#: src/exit/gnunet-daemon-exit.c:2697 #, fuzzy msgid "# UDP packets sent via TUN" msgstr "# các byte đã gửi qua UDP" -#: src/exit/gnunet-daemon-exit.c:2519 +#: src/exit/gnunet-daemon-exit.c:2814 #, fuzzy msgid "# UDP IP-exit requests received via mesh" msgstr "# các yêu cầu get (lấy) dht được nhận" -#: src/exit/gnunet-daemon-exit.c:2619 +#: src/exit/gnunet-daemon-exit.c:2924 #, fuzzy msgid "# UDP service requests received via mesh" msgstr "# các yêu cầu get (lấy) dht được nhận" -#: src/exit/gnunet-daemon-exit.c:2642 +#: src/exit/gnunet-daemon-exit.c:2947 #, fuzzy msgid "# UDP requests dropped (no such service)" msgstr "# các yêu cầu lỗ hổng bị bỏ do trọng tải" -#: src/exit/gnunet-daemon-exit.c:2882 +#: src/exit/gnunet-daemon-exit.c:2980 +msgid "# Inbound MESH tunnels created" +msgstr "" + +#: src/exit/gnunet-daemon-exit.c:3209 #, c-format msgid "No addresses found for hostname `%s' of service `%s'!\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:2896 src/exit/gnunet-daemon-exit.c:2908 +#: src/exit/gnunet-daemon-exit.c:3223 src/exit/gnunet-daemon-exit.c:3235 #, c-format msgid "Service `%s' configured for IPv4, but IPv4 is disabled!\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:2919 +#: src/exit/gnunet-daemon-exit.c:3246 #, c-format msgid "No IP addresses found for hostname `%s' of service `%s'!\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:3048 +#: src/exit/gnunet-daemon-exit.c:3364 msgid "" "This system does not support IPv4, will disable IPv4 functions despite them " "being enabled in the configuration\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:3056 +#: src/exit/gnunet-daemon-exit.c:3372 msgid "" "This system does not support IPv6, will disable IPv6 functions despite them " "being enabled in the configuration\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:3063 +#: src/exit/gnunet-daemon-exit.c:3379 msgid "" "Cannot enable IPv4 exit but disable IPv4 on TUN interface, will use " "ENABLE_IPv4=YES\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:3069 +#: src/exit/gnunet-daemon-exit.c:3385 msgid "" "Cannot enable IPv6 exit but disable IPv6 on TUN interface, will use " "ENABLE_IPv6=YES\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:3075 src/pt/gnunet-daemon-pt.c:884 +#: src/exit/gnunet-daemon-exit.c:3391 src/pt/gnunet-daemon-pt.c:884 msgid "No useful service enabled. Exiting.\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:3236 +#: src/exit/gnunet-daemon-exit.c:3620 msgid "Daemon to run to provide an IP exit node for the VPN" msgstr "" @@ -1864,113 +1820,113 @@ msgstr "# các kết quả dht được nhận" msgid "# messages defragmented" msgstr "# các thông báo được chắp liền" -#: src/fragmentation/fragmentation.c:203 +#: src/fragmentation/fragmentation.c:208 #, fuzzy msgid "# fragments transmitted" msgstr "# Các tự quảng cáo được truyền" -#: src/fragmentation/fragmentation.c:206 +#: src/fragmentation/fragmentation.c:211 #, fuzzy msgid "# fragments retransmitted" msgstr "# Các tự quảng cáo được truyền" -#: src/fragmentation/fragmentation.c:232 +#: src/fragmentation/fragmentation.c:237 #, fuzzy msgid "# fragments wrap arounds" msgstr "# Các tự quảng cáo được truyền" -#: src/fragmentation/fragmentation.c:273 +#: src/fragmentation/fragmentation.c:281 msgid "# messages fragmented" msgstr "# các thông báo bị tế phân" -#: src/fragmentation/fragmentation.c:276 +#: src/fragmentation/fragmentation.c:284 msgid "# total size of fragmented messages" msgstr "" -#: src/fragmentation/fragmentation.c:363 +#: src/fragmentation/fragmentation.c:405 #, fuzzy msgid "# fragment acknowledgements received" msgstr "# Các quảng cáo đồng đẳng được nhận" -#: src/fragmentation/fragmentation.c:369 +#: src/fragmentation/fragmentation.c:411 msgid "# bits removed from fragmentation ACKs" msgstr "" -#: src/fragmentation/fragmentation.c:393 +#: src/fragmentation/fragmentation.c:435 #, fuzzy msgid "# fragmentation transmissions completed" msgstr "# các sự truyền PONG bị lỗi" -#: src/fs/fs_api.c:339 +#: src/fs/fs_api.c:465 #, fuzzy, c-format msgid "Could not open file `%s': %s" msgstr "Lỗi mở tập tin theo dõi « %s »: %s\n" -#: src/fs/fs_api.c:348 +#: src/fs/fs_api.c:474 #, fuzzy, c-format msgid "Could not read file `%s': %s" msgstr "Lỗi mở tập tin theo dõi « %s »: %s\n" -#: src/fs/fs_api.c:354 +#: src/fs/fs_api.c:480 #, c-format msgid "Short read reading from file `%s'!" msgstr "" -#: src/fs/fs_api.c:938 +#: src/fs/fs_api.c:1061 #, fuzzy, c-format msgid "Failed to resume publishing information `%s': %s\n" msgstr "Lỗi mở tập tin ghi sự kiện « %s »: %s\n" -#: src/fs/fs_api.c:1395 +#: src/fs/fs_api.c:1520 #, c-format msgid "Failed to recover namespace `%s', cannot resume publishing operation.\n" msgstr "" -#: src/fs/fs_api.c:1437 +#: src/fs/fs_api.c:1562 #, c-format msgid "Failure while resuming publishing operation `%s': %s\n" msgstr "" -#: src/fs/fs_api.c:1453 +#: src/fs/fs_api.c:1578 #, fuzzy, c-format msgid "Failed to resume publishing operation `%s': %s\n" msgstr "Lỗi mở tập tin ghi sự kiện « %s »: %s\n" -#: src/fs/fs_api.c:2106 +#: src/fs/fs_api.c:2229 #, c-format msgid "Failure while resuming unindexing operation `%s': %s\n" msgstr "" -#: src/fs/fs_api.c:2116 +#: src/fs/fs_api.c:2239 #, fuzzy, c-format msgid "Failed to resume unindexing operation `%s': %s\n" msgstr "Lỗi mở tập tin ghi sự kiện « %s »: %s\n" -#: src/fs/fs_api.c:2241 src/fs/fs_api.c:2480 +#: src/fs/fs_api.c:2364 src/fs/fs_api.c:2604 #, fuzzy, c-format msgid "Failed to resume sub-download `%s': %s\n" msgstr "Lỗi mở tập tin ghi sự kiện « %s »: %s\n" -#: src/fs/fs_api.c:2258 +#: src/fs/fs_api.c:2381 #, fuzzy, c-format msgid "Failed to resume sub-search `%s': %s\n" msgstr "Lỗi mở tập tin ghi sự kiện « %s »: %s\n" -#: src/fs/fs_api.c:2270 src/fs/fs_api.c:2289 src/fs/fs_api.c:2773 +#: src/fs/fs_api.c:2394 src/fs/fs_api.c:2413 src/fs/fs_api.c:2897 #, c-format msgid "Failure while resuming search operation `%s': %s\n" msgstr "" -#: src/fs/fs_api.c:2471 +#: src/fs/fs_api.c:2595 #, c-format msgid "Failed to resume sub-download `%s': could not open file `%s'\n" msgstr "" -#: src/fs/fs_api.c:2717 +#: src/fs/fs_api.c:2841 msgid "Could not resume running search, will resume as paused search\n" msgstr "" -#: src/fs/fs_api.c:2811 +#: src/fs/fs_api.c:2935 #, c-format msgid "Failure while resuming download operation `%s': %s\n" msgstr "" @@ -1980,63 +1936,63 @@ msgstr "" msgid "MAGIC mismatch. This is not a GNUnet directory.\n" msgstr "Lỗi định dạng tập tin (không phải là thư mục GNUnet ?)\n" -#: src/fs/fs_download.c:311 +#: src/fs/fs_download.c:321 msgid "" "Recursive downloads of directories larger than 4 GB are not supported on 32-" "bit systems\n" msgstr "" -#: src/fs/fs_download.c:331 +#: src/fs/fs_download.c:341 msgid "Directory too large for system address space\n" msgstr "" -#: src/fs/fs_download.c:497 src/fs/fs_download.c:509 +#: src/fs/fs_download.c:507 src/fs/fs_download.c:519 #, fuzzy, c-format msgid "Failed to open file `%s' for writing" msgstr "Lỗi mở tập tin ghi sự kiện « %s »: %s\n" -#: src/fs/fs_download.c:878 +#: src/fs/fs_download.c:888 #, fuzzy, c-format msgid "Failed to create directory for recursive download of `%s'\n" msgstr "Lỗi cập nhật dữ liệu cho mô-đun « %s »\n" -#: src/fs/fs_download.c:960 +#: src/fs/fs_download.c:970 #, c-format msgid "" "Internal error or bogus download URI (expected %u bytes at depth %u and " "offset %llu/%llu, got %u bytes)" msgstr "" -#: src/fs/fs_download.c:986 +#: src/fs/fs_download.c:996 msgid "internal error decrypting content" msgstr "" -#: src/fs/fs_download.c:1009 +#: src/fs/fs_download.c:1019 #, fuzzy, c-format msgid "Download failed: could not open file `%s': %s" msgstr "Lỗi mở tập tin theo dõi « %s »: %s\n" -#: src/fs/fs_download.c:1019 +#: src/fs/fs_download.c:1029 #, fuzzy, c-format msgid "Failed to seek to offset %llu in file `%s': %s" msgstr "Lỗi mở tập tin ghi sự kiện « %s »: %s\n" -#: src/fs/fs_download.c:1028 +#: src/fs/fs_download.c:1038 #, fuzzy, c-format msgid "Failed to write block of %u bytes at offset %llu in file `%s': %s" msgstr "Lỗi mở tập tin ghi sự kiện « %s »: %s\n" -#: src/fs/fs_download.c:1125 +#: src/fs/fs_download.c:1136 #, fuzzy msgid "internal error decoding tree" msgstr "=\tLỗi đọc thư mục.\n" -#: src/fs/fs_download.c:1888 +#: src/fs/fs_download.c:1927 #, fuzzy msgid "Invalid URI" msgstr "Dữ liệu nhập không hợp lệ.\n" -#: src/fs/fs_getopt.c:191 +#: src/fs/fs_getopt.c:192 #, c-format msgid "" "Unknown metadata type in metadata option `%s'. Using metadata type " @@ -2080,37 +2036,36 @@ msgstr "Lỗi lấy thông kê về truyền tải.\n" msgid "Failed to connect to datastore service" msgstr "Không kết nối được đến trình nền gnunetd." -#: src/fs/fs_namespace.c:57 src/fs/fs_namespace.c:83 -#, fuzzy, c-format -msgid "Configuration fails to specify `%s' in section `%s'\n" -msgstr "Tập tin cấu hình « %s » đã được ghi.\n" - -#: src/fs/fs_namespace.c:112 +#: src/fs/fs_namespace.c:110 #, fuzzy, c-format msgid "Failed to open `%s' for writing: %s\n" msgstr "Lỗi mở tập tin ghi sự kiện « %s »: %s\n" -#: src/fs/fs_namespace.c:134 src/fs/fs_namespace.c:222 +#: src/fs/fs_namespace.c:132 src/fs/fs_namespace.c:220 #, fuzzy, c-format msgid "Failed to write `%s': %s\n" msgstr "Lỗi chạy %s: %s %d\n" -#: src/fs/fs_namespace.c:256 +#: src/fs/fs_namespace.c:252 #, fuzzy, c-format msgid "Failed to create or read private key for namespace `%s'\n" msgstr "Lỗi cập nhật dữ liệu cho mô-đun « %s »\n" -#: src/fs/fs_namespace.c:371 +#: src/fs/fs_namespace.c:367 #, fuzzy, c-format msgid "Failed to read namespace private key file `%s', deleting it!\n" msgstr "Lỗi thêm mục nhập vào không gian tên « %s » (có chưa ?)\n" -#: src/fs/fs_namespace.c:588 src/fs/fs_publish_ksk.c:295 +#: src/fs/fs_namespace.c:558 +msgid "Identifiers or URI too long to create SBlock" +msgstr "" + +#: src/fs/fs_namespace.c:593 src/fs/fs_publish_ksk.c:295 #, fuzzy msgid "Internal error." msgstr "Lỗi VR." -#: src/fs/fs_namespace.c:631 +#: src/fs/fs_namespace.c:636 #, fuzzy msgid "Failed to connect to datastore." msgstr "Không kết nối được đến trình nền gnunetd." @@ -2120,59 +2075,59 @@ msgstr "Không kết nối được đến trình nền gnunetd." msgid "Publishing failed: %s" msgstr "Gặp lỗi khi tải lên tập tin: %s\n" -#: src/fs/fs_publish.c:621 src/fs/fs_publish.c:638 src/fs/fs_publish.c:677 -#: src/fs/fs_publish.c:697 src/fs/fs_publish.c:722 src/fs/fs_publish.c:862 +#: src/fs/fs_publish.c:622 src/fs/fs_publish.c:639 src/fs/fs_publish.c:678 +#: src/fs/fs_publish.c:698 src/fs/fs_publish.c:723 src/fs/fs_publish.c:863 #, fuzzy, c-format msgid "Can not index file `%s': %s. Will try to insert instead.\n" msgstr "Lỗi đánh chỉ mục tập tin « %s ». Đề nghị: thử chèn tập tin.\n" -#: src/fs/fs_publish.c:623 +#: src/fs/fs_publish.c:624 msgid "timeout on index-start request to `fs' service" msgstr "" -#: src/fs/fs_publish.c:635 +#: src/fs/fs_publish.c:636 #, fuzzy msgid "unknown error" msgstr "Lỗi không rõ" -#: src/fs/fs_publish.c:678 +#: src/fs/fs_publish.c:679 msgid "failed to compute hash" msgstr "" -#: src/fs/fs_publish.c:698 +#: src/fs/fs_publish.c:699 #, fuzzy msgid "filename too long" msgstr "tên tập tin" -#: src/fs/fs_publish.c:723 +#: src/fs/fs_publish.c:724 msgid "could not connect to `fs' service" msgstr "" -#: src/fs/fs_publish.c:746 +#: src/fs/fs_publish.c:747 #, fuzzy, c-format msgid "Failed to get file identifiers for `%s'\n" msgstr "Lỗi đọc danh sách bạn bè từ « %s »\n" -#: src/fs/fs_publish.c:811 +#: src/fs/fs_publish.c:812 #, fuzzy, c-format msgid "Recursive upload failed at `%s': %s" msgstr "%s bị lỗi tại %s:%d: « %s »\n" -#: src/fs/fs_publish.c:817 +#: src/fs/fs_publish.c:818 #, fuzzy, c-format msgid "Recursive upload failed: %s" msgstr "Gặp lỗi khi tải lên tập tin: %s\n" -#: src/fs/fs_publish.c:863 +#: src/fs/fs_publish.c:864 msgid "needs to be an actual file" msgstr "" -#: src/fs/fs_publish.c:1071 +#: src/fs/fs_publish.c:1090 #, fuzzy, c-format msgid "Insufficient space for publishing: %s" msgstr "Không đủ quyền truy cập cho « %s »: %s\n" -#: src/fs/fs_publish.c:1142 +#: src/fs/fs_publish.c:1161 #, c-format msgid "Reserving space for %u entries and %llu bytes for publication\n" msgstr "" @@ -2182,16 +2137,11 @@ msgstr "" msgid "Could not connect to datastore." msgstr "« %s »: Không thể kết nối.\n" -#: src/fs/fs_search.c:829 +#: src/fs/fs_search.c:892 #, c-format msgid "Got result with unknown block type `%d', ignoring" msgstr "" -#: src/fs/fs_test_lib.c:269 -#, fuzzy, c-format -msgid "Failed to start daemon: %s\n" -msgstr "Lỗi bắt đầu thu thập.\n" - #: src/fs/fs_unindex.c:58 msgid "Failed to find given position in file" msgstr "" @@ -2219,96 +2169,96 @@ msgstr "Đối số không hợp lệ cho « %s ».\n" msgid "Failed to connect to FS service for unindexing." msgstr "Không kết nối được đến trình nền gnunetd." -#: src/fs/fs_unindex.c:344 +#: src/fs/fs_unindex.c:349 src/fs/fs_unindex.c:361 #, fuzzy msgid "Failed to get KSKs from directory scan." msgstr "Lỗi truy cập đến thư mục nhà GNUnet « %s »\n" -#: src/fs/fs_unindex.c:356 +#: src/fs/fs_unindex.c:357 #, fuzzy, c-format msgid "Internal error scanning `%s'.\n" msgstr "=\tLỗi đọc thư mục.\n" -#: src/fs/fs_unindex.c:411 +#: src/fs/fs_unindex.c:416 #, fuzzy, c-format msgid "Failed to remove KBlock: %s\n" msgstr "Lỗi mở tập tin ghi sự kiện « %s »: %s\n" -#: src/fs/fs_unindex.c:501 +#: src/fs/fs_unindex.c:506 #, fuzzy, c-format msgid "Failed to parse URI `%s' from KBlock!\n" msgstr "Tập tin « %s » có URI: %s\n" -#: src/fs/fs_unindex.c:553 src/fs/fs_unindex.c:618 +#: src/fs/fs_unindex.c:558 src/fs/fs_unindex.c:623 #, fuzzy msgid "Failed to connect to `datastore' service." msgstr "Lỗi sơ khởi dịch vụ « %s ».\n" -#: src/fs/fs_unindex.c:631 +#: src/fs/fs_unindex.c:636 #, fuzzy msgid "Failed to open file for unindexing." msgstr "Không kết nối được đến trình nền gnunetd." -#: src/fs/fs_unindex.c:665 +#: src/fs/fs_unindex.c:670 #, fuzzy msgid "Failed to compute hash of file." msgstr "Không kết nối được đến trình nền gnunetd." -#: src/fs/fs_uri.c:220 -#, c-format +#: src/fs/fs_uri.c:221 +#, no-c-format msgid "`%' must be followed by HEX number" msgstr "" -#: src/fs/fs_uri.c:279 +#: src/fs/fs_uri.c:280 msgid "Malformed KSK URI (must not begin or end with `+')" msgstr "" -#: src/fs/fs_uri.c:297 +#: src/fs/fs_uri.c:298 msgid "`++' not allowed in KSK URI" msgstr "" -#: src/fs/fs_uri.c:304 +#: src/fs/fs_uri.c:305 msgid "Quotes not balanced in KSK URI" msgstr "" -#: src/fs/fs_uri.c:372 src/fs/fs_uri.c:379 +#: src/fs/fs_uri.c:373 src/fs/fs_uri.c:380 msgid "Malformed SKS URI" msgstr "" -#: src/fs/fs_uri.c:423 src/fs/fs_uri.c:438 +#: src/fs/fs_uri.c:424 src/fs/fs_uri.c:439 msgid "Malformed CHK URI" msgstr "" -#: src/fs/fs_uri.c:568 src/fs/fs_uri.c:583 src/fs/fs_uri.c:593 -#: src/fs/fs_uri.c:621 +#: src/fs/fs_uri.c:569 src/fs/fs_uri.c:584 src/fs/fs_uri.c:594 +#: src/fs/fs_uri.c:622 msgid "SKS URI malformed" msgstr "" -#: src/fs/fs_uri.c:603 +#: src/fs/fs_uri.c:604 msgid "SKS URI malformed (could not decode public key)" msgstr "" -#: src/fs/fs_uri.c:609 +#: src/fs/fs_uri.c:610 msgid "SKS URI malformed (could not find signature)" msgstr "" -#: src/fs/fs_uri.c:615 +#: src/fs/fs_uri.c:616 msgid "SKS URI malformed (could not decode signature)" msgstr "" -#: src/fs/fs_uri.c:628 +#: src/fs/fs_uri.c:629 msgid "SKS URI malformed (could not parse expiration time)" msgstr "" -#: src/fs/fs_uri.c:640 +#: src/fs/fs_uri.c:641 msgid "SKS URI malformed (signature failed validation)" msgstr "" -#: src/fs/fs_uri.c:678 +#: src/fs/fs_uri.c:679 msgid "Unrecognized URI type" msgstr "" -#: src/fs/fs_uri.c:903 +#: src/fs/fs_uri.c:904 #, fuzzy msgid "Lacking key configuration settings.\n" msgstr "Lưu cấu hình ngay bây giờ không?" @@ -2326,6 +2276,69 @@ msgstr "Chưa ghi rõ từ khoá.\n" msgid "Number of double-quotes not balanced!\n" msgstr "Có dấu nháy kép thừa hay thiếu.\n" +#: src/fs/gnunet-auto-share.c:236 +#, fuzzy, c-format +msgid "Failed to load state: %s\n" +msgstr "Lỗi bắt đầu thu thập.\n" + +#: src/fs/gnunet-auto-share.c:289 src/fs/gnunet-auto-share.c:299 +#: src/fs/gnunet-auto-share.c:309 +#, fuzzy, c-format +msgid "Failed to save state to file %s\n" +msgstr "Lỗi đọc danh sách bạn bè từ « %s »\n" + +#: src/fs/gnunet-auto-share.c:401 +#, c-format +msgid "Publication of `%s' done\n" +msgstr "" + +#: src/fs/gnunet-auto-share.c:488 +#, fuzzy, c-format +msgid "Publishing `%s'\n" +msgstr "Gặp lỗi khi tải lên tập tin: %s\n" + +#: src/fs/gnunet-auto-share.c:497 +#, fuzzy, c-format +msgid "Failed to run `%s'\n" +msgstr "Lỗi bắt đầu thu thập.\n" + +#: src/fs/gnunet-auto-share.c:686 +#, fuzzy, c-format +msgid "" +"You must specify one and only one directory name for automatic publication.\n" +msgstr "Phải ghi rõ chỉ một tên tập tin để chèn.\n" + +#: src/fs/gnunet-auto-share.c:737 src/fs/gnunet-pseudonym.c:279 +#: src/fs/gnunet-publish.c:683 +msgid "set the desired LEVEL of sender-anonymity" +msgstr "đặt CẤP mong muốn của tình trạng nặc danh của người gửi" + +#: src/fs/gnunet-auto-share.c:741 src/fs/gnunet-publish.c:687 +msgid "disable adding the creation time to the metadata of the uploaded file" +msgstr "tắt thêm giờ tạo vào siêu dữ liệu của tập tin đã tải lên" + +#: src/fs/gnunet-auto-share.c:744 src/fs/gnunet-publish.c:690 +msgid "do not use libextractor to add keywords or metadata" +msgstr "" + +#: src/fs/gnunet-auto-share.c:747 src/fs/gnunet-publish.c:714 +msgid "specify the priority of the content" +msgstr "xác định mức ưu tiên của nội dung" + +#: src/fs/gnunet-auto-share.c:750 src/fs/gnunet-pseudonym.c:304 +#: src/fs/gnunet-publish.c:721 +msgid "set the desired replication LEVEL" +msgstr "" + +#: src/fs/gnunet-auto-share.c:770 +#, fuzzy +msgid "Automatically publish files from a directory on GNUnet" +msgstr "Tự động chia sẻ một thư mục." + +#: src/fs/gnunet-daemon-fsprofiler.c:656 +msgid "Daemon to use file-sharing to measure its performance." +msgstr "" + #: src/fs/gnunet-directory.c:49 #, c-format msgid "\t\n" @@ -2356,100 +2369,100 @@ msgstr "Lỗi đọc danh sách bạn bè từ « %s »\n" msgid "`%s' is not a GNUnet directory\n" msgstr "Lỗi định dạng tập tin (không phải là thư mục GNUnet ?)\n" -#: src/fs/gnunet-directory.c:179 +#: src/fs/gnunet-directory.c:183 #, fuzzy msgid "Display contents of a GNUnet directory" msgstr "Lỗi định dạng tập tin (không phải là thư mục GNUnet ?)\n" -#: src/fs/gnunet-download.c:101 +#: src/fs/gnunet-download.c:137 #, fuzzy, c-format msgid "Starting download `%s'.\n" msgstr "Đang bắt đầu tài về « %s »\n" -#: src/fs/gnunet-download.c:110 +#: src/fs/gnunet-download.c:147 #, fuzzy msgid "" msgstr "Lỗi không rõ" -#: src/fs/gnunet-download.c:119 +#: src/fs/gnunet-download.c:157 #, c-format msgid "" "Downloading `%s' at %llu/%llu (%s remaining, %s/s). Block took %s to " "download\n" msgstr "" -#: src/fs/gnunet-download.c:129 +#: src/fs/gnunet-download.c:179 #, fuzzy, c-format msgid "Error downloading: %s.\n" msgstr "Gặp lỗi khi tải xuống: %s\n" -#: src/fs/gnunet-download.c:137 +#: src/fs/gnunet-download.c:194 #, fuzzy, c-format msgid "Downloading `%s' done (%s/s).\n" msgstr "Tiến trình tải lên « %s » đã tiếp tục lại.\n" -#: src/fs/gnunet-download.c:152 src/fs/gnunet-publish.c:190 -#: src/fs/gnunet-search.c:190 src/fs/gnunet-unindex.c:109 +#: src/fs/gnunet-download.c:209 src/fs/gnunet-publish.c:195 +#: src/fs/gnunet-search.c:193 src/fs/gnunet-unindex.c:108 #, fuzzy, c-format msgid "Unexpected status: %d\n" msgstr "Gặp sự kiện bất thường: %d\n" -#: src/fs/gnunet-download.c:177 +#: src/fs/gnunet-download.c:234 #, fuzzy msgid "You need to specify a URI argument.\n" msgstr "KHÔNG cho phép ghi rõ cả hai địa chỉ URI và tên tập tin.\n" -#: src/fs/gnunet-download.c:183 src/fs/gnunet-publish.c:624 +#: src/fs/gnunet-download.c:240 src/fs/gnunet-publish.c:629 #, fuzzy, c-format msgid "Failed to parse URI: %s\n" msgstr "Tập tin « %s » có URI: %s\n" -#: src/fs/gnunet-download.c:190 +#: src/fs/gnunet-download.c:247 msgid "Only CHK or LOC URIs supported.\n" msgstr "" -#: src/fs/gnunet-download.c:197 +#: src/fs/gnunet-download.c:254 msgid "Target filename must be specified.\n" msgstr "" -#: src/fs/gnunet-download.c:211 src/fs/gnunet-publish.c:602 -#: src/fs/gnunet-search.c:241 src/fs/gnunet-unindex.c:141 +#: src/fs/gnunet-download.c:268 src/fs/gnunet-publish.c:607 +#: src/fs/gnunet-search.c:243 src/fs/gnunet-unindex.c:140 #, fuzzy, c-format msgid "Could not initialize `%s' subsystem.\n" msgstr "Lỗi sơ khởi dịch vụ « %s ».\n" -#: src/fs/gnunet-download.c:248 src/fs/gnunet-search.c:285 +#: src/fs/gnunet-download.c:305 src/fs/gnunet-search.c:282 #, fuzzy msgid "set the desired LEVEL of receiver-anonymity" msgstr "đặt CẤP mong muốn của tình trạng nặc danh của người gửi" -#: src/fs/gnunet-download.c:251 +#: src/fs/gnunet-download.c:308 msgid "delete incomplete downloads (when aborted with CTRL-C)" msgstr "xoá việc tải về không hoàn thành (khi hủy bở dùng CTRL-C)" -#: src/fs/gnunet-download.c:254 src/fs/gnunet-search.c:288 +#: src/fs/gnunet-download.c:311 src/fs/gnunet-search.c:285 msgid "only search the local peer (no P2P network search)" msgstr "" -#: src/fs/gnunet-download.c:257 +#: src/fs/gnunet-download.c:314 msgid "write the file to FILENAME" msgstr "ghi tập tin vào TÊN_TẬP_TIN" -#: src/fs/gnunet-download.c:261 +#: src/fs/gnunet-download.c:318 #, fuzzy msgid "set the maximum number of parallel downloads that is allowed" msgstr "đặt số tối đa các việc tải xuống đồng thời được phép" -#: src/fs/gnunet-download.c:265 +#: src/fs/gnunet-download.c:322 #, fuzzy msgid "set the maximum number of parallel requests for blocks that is allowed" msgstr "đặt số tối đa các việc tải xuống đồng thời được phép" -#: src/fs/gnunet-download.c:268 +#: src/fs/gnunet-download.c:325 msgid "download a GNUnet directory recursively" msgstr "tải xuống đệ quy một thư mục GNUnet" -#: src/fs/gnunet-download.c:278 +#: src/fs/gnunet-download.c:339 msgid "" "Download files from GNUnet using a GNUnet CHK or LOC URI (gnunet://fs/" "chk/...)" @@ -2459,12 +2472,28 @@ msgstr "" msgid "print a list of all indexed files" msgstr "" -#: src/fs/gnunet-fs.c:124 +#: src/fs/gnunet-fs.c:127 #, fuzzy msgid "Special file-sharing operations" msgstr "Tùy chọn chia sẻ tập tin" -#: src/fs/gnunet-pseudonym.c:160 src/statistics/gnunet-statistics.c:167 +#: src/fs/gnunet-fs-profiler.c:182 +msgid "run the experiment with COUNT peers" +msgstr "" + +#: src/fs/gnunet-fs-profiler.c:185 +msgid "specifies name of a file with the HOSTS the testbed should use" +msgstr "" + +#: src/fs/gnunet-fs-profiler.c:188 +msgid "automatically terminate experiment after DELAY" +msgstr "" + +#: src/fs/gnunet-fs-profiler.c:197 +msgid "run a testbed to measure file-sharing performance" +msgstr "" + +#: src/fs/gnunet-pseudonym.c:160 src/statistics/gnunet-statistics.c:283 #, fuzzy, c-format msgid "Invalid argument `%s'\n" msgstr "Đối số không hợp lệ cho « %s ».\n" @@ -2475,10 +2504,6 @@ msgstr "Đối số không hợp lệ cho « %s ».\n" msgid "Option `%s' ignored\n" msgstr "%s: tùy chọn « %s » là mơ hồ\n" -#: src/fs/gnunet-pseudonym.c:279 src/fs/gnunet-publish.c:678 -msgid "set the desired LEVEL of sender-anonymity" -msgstr "đặt CẤP mong muốn của tình trạng nặc danh của người gửi" - #: src/fs/gnunet-pseudonym.c:282 msgid "create or advertise namespace NAME" msgstr "" @@ -2496,7 +2521,7 @@ msgstr "" "thêm một từ khóa bổ sung cho tất cả tập tin và thư mục (có thể chỉ ra tùy " "chọn này nhiều lần)" -#: src/fs/gnunet-pseudonym.c:292 src/fs/gnunet-publish.c:697 +#: src/fs/gnunet-pseudonym.c:292 src/fs/gnunet-publish.c:702 msgid "set the meta-data for the given TYPE to the given VALUE" msgstr "đặt siêu dữ liệu cho KIỂU đưa ra thành GIÁ_TRỊ chỉ ra" @@ -2513,10 +2538,6 @@ msgstr "" msgid "do not print names of remote namespaces" msgstr "" -#: src/fs/gnunet-pseudonym.c:304 src/fs/gnunet-publish.c:716 -msgid "set the desired replication LEVEL" -msgstr "" - #: src/fs/gnunet-pseudonym.c:307 #, fuzzy msgid "specify ID of the root of the namespace" @@ -2527,144 +2548,131 @@ msgstr "đặt đánh giá của một không gian tên" msgid "change rating of namespace ID by VALUE" msgstr "đặt đánh giá của một không gian tên" -#: src/fs/gnunet-pseudonym.c:318 +#: src/fs/gnunet-pseudonym.c:322 msgid "Manage GNUnet pseudonyms." msgstr "" -#: src/fs/gnunet-publish.c:147 +#: src/fs/gnunet-publish.c:152 #, c-format msgid "Publishing `%s' at %llu/%llu (%s remaining)\n" msgstr "" -#: src/fs/gnunet-publish.c:155 +#: src/fs/gnunet-publish.c:159 #, fuzzy, c-format msgid "Error publishing: %s.\n" msgstr "Gặp lỗi khi tải xuống: %s\n" -#: src/fs/gnunet-publish.c:165 +#: src/fs/gnunet-publish.c:169 #, c-format msgid "Publishing `%s' done.\n" msgstr "" -#: src/fs/gnunet-publish.c:169 +#: src/fs/gnunet-publish.c:173 #, fuzzy, c-format msgid "URI is `%s'.\n" msgstr "Tôi là đồng đẳng « %s ».\n" -#: src/fs/gnunet-publish.c:187 +#: src/fs/gnunet-publish.c:192 #, fuzzy msgid "Cleanup after abort complete.\n" msgstr "Hoàn thành khởi chạy « %s ».\n" -#: src/fs/gnunet-publish.c:305 +#: src/fs/gnunet-publish.c:310 #, fuzzy, c-format msgid "Meta data for file `%s' (%s)\n" msgstr "Đang cập nhật dữ liệu cho mô-đun « %s »\n" -#: src/fs/gnunet-publish.c:307 +#: src/fs/gnunet-publish.c:312 #, fuzzy, c-format msgid "Keywords for file `%s' (%s)\n" msgstr "Từ khoá cho tập tin « %s »:\n" -#: src/fs/gnunet-publish.c:358 +#: src/fs/gnunet-publish.c:363 src/fs/gnunet-publish.c:617 #, fuzzy, c-format -msgid "Failed to create namespace `%s'\n" +msgid "Failed to create namespace `%s' (illegal filename?)\n" msgstr "Không thể tạo miền tên.\n" -#: src/fs/gnunet-publish.c:433 +#: src/fs/gnunet-publish.c:438 #, fuzzy msgid "Could not publish\n" msgstr "Không thể truy cập đến « %s »: %s\n" -#: src/fs/gnunet-publish.c:460 +#: src/fs/gnunet-publish.c:465 #, fuzzy msgid "Could not start publishing.\n" msgstr "Không thể nạp phần bổ sung truyền tải « %s »\n" -#: src/fs/gnunet-publish.c:491 +#: src/fs/gnunet-publish.c:496 #, fuzzy, c-format msgid "Scanning directory `%s'.\n" msgstr "Lỗi đọc danh sách bạn bè từ « %s »\n" -#: src/fs/gnunet-publish.c:493 +#: src/fs/gnunet-publish.c:498 #, fuzzy, c-format msgid "Scanning file `%s'.\n" msgstr "Đang bắt đầu tài về « %s »\n" -#: src/fs/gnunet-publish.c:498 +#: src/fs/gnunet-publish.c:503 #, c-format msgid "There was trouble processing file `%s', skipping it.\n" msgstr "" -#: src/fs/gnunet-publish.c:503 +#: src/fs/gnunet-publish.c:508 msgid "Preprocessing complete.\n" msgstr "" -#: src/fs/gnunet-publish.c:507 +#: src/fs/gnunet-publish.c:512 #, fuzzy, c-format msgid "Extracting meta data from file `%s' complete.\n" msgstr "Đang cập nhật dữ liệu cho mô-đun « %s »\n" -#: src/fs/gnunet-publish.c:511 +#: src/fs/gnunet-publish.c:516 msgid "Meta data extraction has finished.\n" msgstr "" -#: src/fs/gnunet-publish.c:518 +#: src/fs/gnunet-publish.c:523 #, fuzzy msgid "Internal error scanning directory.\n" msgstr "=\tLỗi đọc thư mục.\n" -#: src/fs/gnunet-publish.c:552 +#: src/fs/gnunet-publish.c:557 #, c-format msgid "Cannot extract metadata from a URI!\n" msgstr "Không thể trích siêu dữ liệu ra một địa chỉ URI.\n" -#: src/fs/gnunet-publish.c:559 +#: src/fs/gnunet-publish.c:564 #, c-format msgid "You must specify one and only one filename for insertion.\n" msgstr "Phải ghi rõ chỉ một tên tập tin để chèn.\n" -#: src/fs/gnunet-publish.c:565 +#: src/fs/gnunet-publish.c:570 #, c-format msgid "You must NOT specify an URI and a filename.\n" msgstr "KHÔNG cho phép ghi rõ cả hai địa chỉ URI và tên tập tin.\n" -#: src/fs/gnunet-publish.c:573 src/vpn/gnunet-vpn.c:214 +#: src/fs/gnunet-publish.c:578 src/vpn/gnunet-vpn.c:213 #, c-format msgid "Option `%s' is required when using option `%s'.\n" msgstr "Tùy chọn « %s » cần thiết khi dùng tùy chọn « %s ».\n" -#: src/fs/gnunet-publish.c:583 src/fs/gnunet-publish.c:590 -#: src/transport/gnunet-transport.c:560 +#: src/fs/gnunet-publish.c:588 src/fs/gnunet-publish.c:595 +#: src/transport/gnunet-transport.c:843 src/transport/gnunet-transport.c:873 #, c-format msgid "Option `%s' makes no sense without option `%s'.\n" msgstr "Tùy chọn « %s » không có nghĩa khi không có tùy chọn « %s ».\n" -#: src/fs/gnunet-publish.c:612 -#, fuzzy, c-format -msgid "Could not create namespace `%s'\n" -msgstr "Không thể tạo miền tên.\n" - -#: src/fs/gnunet-publish.c:645 +#: src/fs/gnunet-publish.c:650 #, fuzzy, c-format msgid "Failed to access `%s': %s\n" msgstr "Lỗi mở tập tin ghi sự kiện « %s »: %s\n" -#: src/fs/gnunet-publish.c:657 +#: src/fs/gnunet-publish.c:662 msgid "" "Failed to start meta directory scanner. Is gnunet-helper-publish-fs " "installed?\n" msgstr "" -#: src/fs/gnunet-publish.c:682 -msgid "disable adding the creation time to the metadata of the uploaded file" -msgstr "tắt thêm giờ tạo vào siêu dữ liệu của tập tin đã tải lên" - -#: src/fs/gnunet-publish.c:685 -msgid "do not use libextractor to add keywords or metadata" -msgstr "" - -#: src/fs/gnunet-publish.c:689 +#: src/fs/gnunet-publish.c:694 msgid "" "print list of extracted keywords that would be used, but do not perform " "upload" @@ -2672,7 +2680,7 @@ msgstr "" "in ra danh sách các từ khóa đã giải phóng cần sử dụng, nhưng không thực hiện " "tải lên" -#: src/fs/gnunet-publish.c:693 +#: src/fs/gnunet-publish.c:698 msgid "" "add an additional keyword for the top-level file or directory (this option " "can be specified multiple times)" @@ -2680,7 +2688,7 @@ msgstr "" "thêm một từ khoá bổ sung cho tập tin hoặc thư mục ở cấp đầu (có thể chỉ ra " "tùy chọn này nhiều lần)" -#: src/fs/gnunet-publish.c:700 +#: src/fs/gnunet-publish.c:705 msgid "" "do not index, perform full insertion (stores entire file in encrypted form " "in GNUnet database)" @@ -2688,7 +2696,7 @@ msgstr "" "không đánh chỉ mục, thực hiện việc chèn đầy đủ (chứa toàn bộ tập tin ở dạng " "mã hóa trong cơ sở dữ liệu GNUnet)" -#: src/fs/gnunet-publish.c:705 +#: src/fs/gnunet-publish.c:710 msgid "" "specify ID of an updated version to be published in the future (for " "namespace insertions only)" @@ -2696,16 +2704,12 @@ msgstr "" "chỉ ra mã số của một phiên bản đã cập nhật để công bố trong tương lai (chỉ " "cho sự chèn không gian tên)" -#: src/fs/gnunet-publish.c:709 -msgid "specify the priority of the content" -msgstr "xác định mức ưu tiên của nội dung" - -#: src/fs/gnunet-publish.c:713 +#: src/fs/gnunet-publish.c:718 msgid "publish the files under the pseudonym NAME (place file into namespace)" msgstr "" "công bố các tập tin dưới biệt hiệu TÊN (đặt tập tin vào không gian tên)" -#: src/fs/gnunet-publish.c:719 +#: src/fs/gnunet-publish.c:724 #, fuzzy msgid "" "only simulate the process but do not do any actual publishing (useful to " @@ -2713,13 +2717,13 @@ msgid "" msgstr "" "chỉ mô phỏng tiến trình, không thật công bố (có ích để tính địa chỉ URI)" -#: src/fs/gnunet-publish.c:723 +#: src/fs/gnunet-publish.c:728 msgid "" "set the ID of this version of the publication (for namespace insertions only)" msgstr "" "đặt mã số của phiên bản này của sự công bố (chỉ cho chèn không gian tên)" -#: src/fs/gnunet-publish.c:727 +#: src/fs/gnunet-publish.c:732 msgid "" "URI to be published (can be used instead of passing a file to add keywords " "to the file with the respective URI)" @@ -2727,211 +2731,204 @@ msgstr "" "Địa chỉ URI cần công bố (có thể được dùng thay vào gửi một tập tin để thêm " "từ khoá vào tập tin có địa chỉ URI tương ứng)" -#: src/fs/gnunet-publish.c:742 +#: src/fs/gnunet-publish.c:748 msgid "Publish a file or directory on GNUnet" msgstr "" -#: src/fs/gnunet-search.c:111 +#: src/fs/gnunet-search.c:114 #, c-format msgid "Failed to write directory with search results to `%s'\n" msgstr "" -#: src/fs/gnunet-search.c:181 +#: src/fs/gnunet-search.c:184 #, fuzzy, c-format msgid "Error searching: %s.\n" msgstr "Gặp lỗi khi tải xuống: %s\n" -#: src/fs/gnunet-search.c:231 +#: src/fs/gnunet-search.c:233 #, fuzzy msgid "Could not create keyword URI from arguments.\n" msgstr "Không thể tạo miền tên.\n" -#: src/fs/gnunet-search.c:255 +#: src/fs/gnunet-search.c:257 #, fuzzy msgid "Could not start searching.\n" msgstr "Không thể tạo miền tên.\n" -#: src/fs/gnunet-search.c:291 +#: src/fs/gnunet-search.c:288 msgid "write search results to file starting with PREFIX" msgstr "" -#: src/fs/gnunet-search.c:294 -msgid "automatically terminate search after VALUE ms" +#: src/fs/gnunet-search.c:291 +msgid "automatically terminate search after DELAY" msgstr "" -#: src/fs/gnunet-search.c:301 +#: src/fs/gnunet-search.c:298 msgid "automatically terminate search after VALUE results are found" msgstr "" -#: src/fs/gnunet-search.c:308 +#: src/fs/gnunet-search.c:309 #, fuzzy msgid "Search GNUnet for files that were published on GNUnet" msgstr "Không hiển thị kết quả tìm kiếm cho tập tin được chúng ta tải lên" -#: src/fs/gnunet-service-fs.c:240 +#: src/fs/gnunet-service-fs.c:248 msgid "# running average P2P latency (ms)" msgstr "" -#: src/fs/gnunet-service-fs.c:300 src/fs/gnunet-service-fs.c:489 +#: src/fs/gnunet-service-fs.c:309 src/fs/gnunet-service-fs.c:523 #, fuzzy msgid "# Loopback routes suppressed" msgstr "# tổng số định tuyến lỗ hổng thành công" -#: src/fs/gnunet-service-fs.c:581 src/hostlist/gnunet-daemon-hostlist.c:297 -#: src/topology/gnunet-daemon-topology.c:1330 -#: src/topology/gnunet-daemon-topology.c:1337 +#: src/fs/gnunet-service-fs.c:628 src/hostlist/gnunet-daemon-hostlist.c:297 +#: src/topology/gnunet-daemon-topology.c:1322 +#: src/topology/gnunet-daemon-topology.c:1329 #, fuzzy, c-format msgid "Failed to connect to `%s' service.\n" msgstr "Lỗi sơ khởi dịch vụ « %s ».\n" -#: src/fs/gnunet-service-fs_cp.c:696 +#: src/fs/gnunet-service-fs_cp.c:711 #, fuzzy msgid "# migration stop messages received" msgstr "# các thông báo phát hiện dht được nhận" -#: src/fs/gnunet-service-fs_cp.c:700 +#: src/fs/gnunet-service-fs_cp.c:715 #, c-format -msgid "Migration of content to peer `%s' blocked for %llu ms\n" +msgid "Migration of content to peer `%s' blocked for %s\n" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:735 +#: src/fs/gnunet-service-fs_cp.c:751 #, fuzzy msgid "# replies transmitted to other peers" msgstr "# các byte kiểu %d được gửi " -#: src/fs/gnunet-service-fs_cp.c:741 +#: src/fs/gnunet-service-fs_cp.c:757 #, fuzzy msgid "# replies dropped" msgstr "# các đáp ứng dht được định tuyến" -#: src/fs/gnunet-service-fs_cp.c:766 src/fs/gnunet-service-fs_cp.c:1324 +#: src/fs/gnunet-service-fs_cp.c:782 src/fs/gnunet-service-fs_cp.c:1345 msgid "# P2P searches active" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:858 +#: src/fs/gnunet-service-fs_cp.c:875 msgid "# artificial delays introduced (ms)" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:911 +#: src/fs/gnunet-service-fs_cp.c:928 #, fuzzy msgid "# replies dropped due to type mismatch" msgstr "# các yêu cầu lỗ hổng bị bỏ do trọng tải" -#: src/fs/gnunet-service-fs_cp.c:919 +#: src/fs/gnunet-service-fs_cp.c:936 #, fuzzy msgid "# replies received for other peers" msgstr "# các byte kiểu %d được nhận" -#: src/fs/gnunet-service-fs_cp.c:933 +#: src/fs/gnunet-service-fs_cp.c:950 msgid "# replies dropped due to insufficient cover traffic" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:971 +#: src/fs/gnunet-service-fs_cp.c:988 msgid "# P2P searches destroyed due to ultimate reply" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:1038 +#: src/fs/gnunet-service-fs_cp.c:1056 #, fuzzy msgid "# requests done for free (low load)" msgstr "# các yêu cầu lỗ hổng bị bỏ do trọng tải" -#: src/fs/gnunet-service-fs_cp.c:1062 +#: src/fs/gnunet-service-fs_cp.c:1081 msgid "# request dropped, priority insufficient" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:1072 +#: src/fs/gnunet-service-fs_cp.c:1091 #, fuzzy msgid "# requests done for a price (normal load)" msgstr "# các yêu cầu lỗ hổng bị bỏ do trọng tải" -#: src/fs/gnunet-service-fs_cp.c:1151 +#: src/fs/gnunet-service-fs_cp.c:1170 msgid "# GET requests received (from other peers)" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:1185 +#: src/fs/gnunet-service-fs_cp.c:1204 #, fuzzy msgid "# requests dropped due to initiator not being connected" msgstr "# các yêu cầu lỗ hổng bị bỏ do trọng tải" -#: src/fs/gnunet-service-fs_cp.c:1207 +#: src/fs/gnunet-service-fs_cp.c:1227 #, fuzzy msgid "# requests dropped due to missing reverse route" msgstr "# các yêu cầu lỗ hổng bị bỏ do trọng tải" -#: src/fs/gnunet-service-fs_cp.c:1267 +#: src/fs/gnunet-service-fs_cp.c:1288 #, fuzzy msgid "# requests dropped due TTL underflow" msgstr "# các yêu cầu lỗ hổng bị bỏ do trọng tải" -#: src/fs/gnunet-service-fs_cp.c:1293 +#: src/fs/gnunet-service-fs_cp.c:1314 #, fuzzy msgid "# requests dropped due to higher-TTL request" msgstr "# các yêu cầu lỗ hổng bị bỏ do trọng tải" -#: src/fs/gnunet-service-fs_cp.c:1322 +#: src/fs/gnunet-service-fs_cp.c:1343 #, fuzzy msgid "# P2P query messages received and processed" msgstr "# các thông báo phát hiện dht được nhận" -#: src/fs/gnunet-service-fs_cp.c:1687 +#: src/fs/gnunet-service-fs_cp.c:1713 #, fuzzy msgid "# migration stop messages sent" msgstr "# các thông báo phát hiện dht được nhận" -#: src/fs/gnunet-service-fs_indexing.c:113 -#: src/fs/gnunet-service-fs_indexing.c:163 -#, fuzzy, c-format -msgid "Configuration option `%s' in section `%s' missing.\n" -msgstr "Giá trị cấu hình « %s » cho « %s » trong phần « %s » nên là con số\n" - -#: src/fs/gnunet-service-fs_indexing.c:121 -#: src/fs/gnunet-service-fs_indexing.c:177 +#: src/fs/gnunet-service-fs_indexing.c:130 +#: src/fs/gnunet-service-fs_indexing.c:181 #, fuzzy, c-format msgid "Could not open `%s'.\n" msgstr "Lỗi mở tập tin theo dõi « %s »: %s\n" -#: src/fs/gnunet-service-fs_indexing.c:137 +#: src/fs/gnunet-service-fs_indexing.c:142 #, fuzzy, c-format msgid "Error writing `%s'.\n" msgstr "Gặp lỗi khi tạo người dùng" -#: src/fs/gnunet-service-fs_indexing.c:228 +#: src/fs/gnunet-service-fs_indexing.c:237 #, c-format msgid "" "Index request received for file `%s' is already indexed as `%s'. Permitting " "anyway.\n" msgstr "" -#: src/fs/gnunet-service-fs_indexing.c:266 +#: src/fs/gnunet-service-fs_indexing.c:275 #, c-format msgid "Hash mismatch trying to index file `%s' which has hash `%s'\n" msgstr "" -#: src/fs/gnunet-service-fs_indexing.c:481 +#: src/fs/gnunet-service-fs_indexing.c:477 #, fuzzy, c-format msgid "Failed to delete bogus block: %s\n" msgstr "Lỗi mở tập tin ghi sự kiện « %s »: %s\n" -#: src/fs/gnunet-service-fs_indexing.c:539 +#: src/fs/gnunet-service-fs_indexing.c:542 msgid "# index blocks removed: original file inaccessible" msgstr "" -#: src/fs/gnunet-service-fs_indexing.c:554 +#: src/fs/gnunet-service-fs_indexing.c:557 #, fuzzy, c-format msgid "Could not access indexed file `%s' (%s) at offset %llu: %s\n" msgstr "Không thể giải quyết « %s » (%s): %s\n" -#: src/fs/gnunet-service-fs_indexing.c:556 +#: src/fs/gnunet-service-fs_indexing.c:559 msgid "not indexed" msgstr "" -#: src/fs/gnunet-service-fs_indexing.c:571 +#: src/fs/gnunet-service-fs_indexing.c:574 #, fuzzy, c-format msgid "Indexed file `%s' changed at offset %llu\n" msgstr "Đánh chỉ mục dữ liệu của tập tin « %s » bị lỗi tại vị tri %llu.\n" -#: src/fs/gnunet-service-fs_lc.c:202 src/fs/gnunet-service-fs_lc.c:362 -#: src/fs/gnunet-service-fs_lc.c:488 +#: src/fs/gnunet-service-fs_lc.c:202 src/fs/gnunet-service-fs_lc.c:369 #, fuzzy msgid "# client searches active" msgstr "# các yêu cầu khách lỗ hổng được nhận" @@ -2941,331 +2938,487 @@ msgstr "# các yêu cầu khách lỗ hổng được nhận" msgid "# replies received for local clients" msgstr "# các đáp ứng lỗ hổng được gửi cho trình/máy khách" -#: src/fs/gnunet-service-fs_lc.c:321 +#: src/fs/gnunet-service-fs_lc.c:328 #, fuzzy msgid "# client searches received" msgstr "# các yêu cầu khách lỗ hổng được nhận" -#: src/fs/gnunet-service-fs_lc.c:356 +#: src/fs/gnunet-service-fs_lc.c:363 msgid "# client searches updated (merged content seen list)" msgstr "" -#: src/fs/gnunet-service-fs_pe.c:265 +#: src/fs/gnunet-service-fs_pe.c:269 #, fuzzy msgid "# average retransmission delay (ms)" msgstr "# thời gian trung bình còn kết nối (theo miligiây)" -#: src/fs/gnunet-service-fs_pe.c:391 +#: src/fs/gnunet-service-fs_pe.c:400 #, fuzzy msgid "# transmission failed (core has no bandwidth)" msgstr "Lỗi thử gửi, kiểu truyền tải %d không được hỗ trợ\n" -#: src/fs/gnunet-service-fs_pe.c:420 +#: src/fs/gnunet-service-fs_pe.c:433 #, fuzzy msgid "# query messages sent to other peers" msgstr "# các byte thông báo gửi đi bị loại bỏ" -#: src/fs/gnunet-service-fs_pe.c:469 +#: src/fs/gnunet-service-fs_pe.c:482 msgid "# delay heap timeout" msgstr "" -#: src/fs/gnunet-service-fs_pe.c:476 +#: src/fs/gnunet-service-fs_pe.c:490 #, fuzzy msgid "# query plans executed" msgstr "# các yêu cầu dht được định tuyến" -#: src/fs/gnunet-service-fs_pe.c:538 +#: src/fs/gnunet-service-fs_pe.c:550 #, fuzzy msgid "# requests merged" msgstr "# các yêu cầu get (lấy) dht được nhận" -#: src/fs/gnunet-service-fs_pe.c:544 +#: src/fs/gnunet-service-fs_pe.c:558 #, fuzzy msgid "# requests refreshed" msgstr "# các yêu cầu get (lấy) dht được nhận" -#: src/fs/gnunet-service-fs_pe.c:597 src/fs/gnunet-service-fs_pe.c:681 -#: src/fs/gnunet-service-fs_pe.c:748 +#: src/fs/gnunet-service-fs_pe.c:612 src/fs/gnunet-service-fs_pe.c:696 +#: src/fs/gnunet-service-fs_pe.c:767 msgid "# query plan entries" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:285 +#: src/fs/gnunet-service-fs_pr.c:312 #, fuzzy msgid "# Pending requests created" msgstr "# các yêu cầu get (lấy) dht được nhận" -#: src/fs/gnunet-service-fs_pr.c:367 src/fs/gnunet-service-fs_pr.c:616 +#: src/fs/gnunet-service-fs_pr.c:404 src/fs/gnunet-service-fs_pr.c:667 #, fuzzy msgid "# Pending requests active" msgstr "# các yêu cầu get (lấy) dht được nhận" -#: src/fs/gnunet-service-fs_pr.c:779 +#: src/fs/gnunet-service-fs_pr.c:835 #, fuzzy msgid "# replies received and matched" msgstr "# các byte kiểu %d được nhận" -#: src/fs/gnunet-service-fs_pr.c:808 +#: src/fs/gnunet-service-fs_pr.c:868 msgid "# duplicate replies discarded (bloomfilter)" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:822 +#: src/fs/gnunet-service-fs_pr.c:877 +msgid "# irrelevant replies discarded" +msgstr "" + +#: src/fs/gnunet-service-fs_pr.c:891 #, c-format msgid "Unsupported block type %u\n" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:835 +#: src/fs/gnunet-service-fs_pr.c:904 #, fuzzy msgid "# results found locally" msgstr "# nội dung lỗ hổng được tìm cục bộ" -#: src/fs/gnunet-service-fs_pr.c:953 +#: src/fs/gnunet-service-fs_pr.c:1025 msgid "# Datastore `PUT' failures" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:980 +#: src/fs/gnunet-service-fs_pr.c:1052 #, fuzzy msgid "# storage requests dropped due to high load" msgstr "# các yêu cầu lỗ hổng bị bỏ do trọng tải" -#: src/fs/gnunet-service-fs_pr.c:1015 +#: src/fs/gnunet-service-fs_pr.c:1087 #, fuzzy msgid "# Replies received from DHT" msgstr "# các byte đã nhận qua HTTP" -#: src/fs/gnunet-service-fs_pr.c:1106 +#: src/fs/gnunet-service-fs_pr.c:1221 +#, fuzzy +msgid "# Replies received from STREAM" +msgstr "# các byte đã nhận qua HTTP" + +#: src/fs/gnunet-service-fs_pr.c:1273 #, c-format -msgid "Datastore lookup already took %llu ms!\n" +msgid "Datastore lookup already took %s!\n" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1127 +#: src/fs/gnunet-service-fs_pr.c:1293 #, c-format -msgid "On-demand lookup already took %llu ms!\n" +msgid "On-demand lookup already took %s!\n" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1174 +#: src/fs/gnunet-service-fs_pr.c:1340 msgid "# Datastore lookups concluded (no results)" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1188 +#: src/fs/gnunet-service-fs_pr.c:1355 msgid "# Datastore lookups concluded (seen all)" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1197 +#: src/fs/gnunet-service-fs_pr.c:1364 msgid "# Datastore lookups aborted (more than MAX_RESULTS)" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1211 +#: src/fs/gnunet-service-fs_pr.c:1379 msgid "# requested DBLOCK or IBLOCK not found" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1224 +#: src/fs/gnunet-service-fs_pr.c:1393 msgid "# on-demand blocks matched requests" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1237 +#: src/fs/gnunet-service-fs_pr.c:1406 msgid "# on-demand lookups performed successfully" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1242 +#: src/fs/gnunet-service-fs_pr.c:1411 msgid "# on-demand lookups failed" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1269 src/fs/gnunet-service-fs_pr.c:1309 -#: src/fs/gnunet-service-fs_pr.c:1447 +#: src/fs/gnunet-service-fs_pr.c:1438 src/fs/gnunet-service-fs_pr.c:1478 +#: src/fs/gnunet-service-fs_pr.c:1619 msgid "# Datastore lookups concluded (error queueing)" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1327 +#: src/fs/gnunet-service-fs_pr.c:1496 msgid "# Datastore lookups concluded (found last result)" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1338 +#: src/fs/gnunet-service-fs_pr.c:1507 msgid "# Datastore lookups concluded (load too high)" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1424 +#: src/fs/gnunet-service-fs_pr.c:1595 msgid "# Datastore lookups initiated" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1508 +#: src/fs/gnunet-service-fs_pr.c:1680 #, fuzzy msgid "# GAP PUT messages received" msgstr "# các thông báo PONG đã mật mã được nhận" -#: src/fs/gnunet-service-fs_pr.c:1601 src/fs/gnunet-service-fs_pr.c:1610 -#, fuzzy, c-format -msgid "Configuration fails to specify `%s', assuming default value." -msgstr "Tập tin cấu hình « %s » đã được ghi.\n" - #: src/fs/gnunet-service-fs_push.c:629 -#, c-format -msgid "" -"Invalid value specified for option `%s' in section `%s', content pushing " -"disabled\n" +msgid "time required, content pushing disabled" +msgstr "" + +#: src/fs/gnunet-service-fs_stream.c:777 +#, fuzzy +msgid "# replies received via stream" +msgstr "# các byte kiểu %d được nhận" + +#: src/fs/gnunet-service-fs_stream.c:791 +#, fuzzy +msgid "# replies received via stream dropped" +msgstr "# các byte kiểu %d được nhận" + +#: src/fs/gnunet-service-fs_stream.c:930 +#: src/fs/gnunet-service-fs_stream.c:1384 +#, fuzzy +msgid "# stream connections active" +msgstr "# các kết nối dht" + +#: src/fs/gnunet-service-fs_stream.c:1166 +msgid "# Blocks transferred via stream" msgstr "" +#: src/fs/gnunet-service-fs_stream.c:1326 +#, fuzzy +msgid "# queries received via stream" +msgstr "# các byte đã nhận qua TCP" + +#: src/fs/gnunet-service-fs_stream.c:1376 +#, fuzzy +msgid "# stream client connections rejected" +msgstr "# các kết nối dht" + #: src/fs/gnunet-unindex.c:89 #, fuzzy, c-format msgid "Unindexing at %llu/%llu (%s remaining)\n" msgstr "Lỗi bỏ chỉ mục (không đưa ra lý do)." -#: src/fs/gnunet-unindex.c:96 +#: src/fs/gnunet-unindex.c:95 #, fuzzy, c-format msgid "Error unindexing: %s.\n" msgstr "" "\n" "Gặp lỗi khi bỏ chỉ mục tập tin: %s\n" -#: src/fs/gnunet-unindex.c:101 +#: src/fs/gnunet-unindex.c:100 #, fuzzy msgid "Unindexing done.\n" msgstr "Bỏ chỉ mục tập tin." -#: src/fs/gnunet-unindex.c:131 +#: src/fs/gnunet-unindex.c:130 #, fuzzy, c-format msgid "You must specify one and only one filename for unindexing.\n" msgstr "Phải ghi rõ chỉ một tên tập tin để chèn.\n" -#: src/fs/gnunet-unindex.c:148 +#: src/fs/gnunet-unindex.c:147 #, fuzzy msgid "Could not start unindex operation.\n" msgstr "Không thể truy cập đến thông tin về không gian tên.\n" -#: src/fs/gnunet-unindex.c:176 +#: src/fs/gnunet-unindex.c:179 msgid "Unindex a file that was previously indexed with gnunet-publish." msgstr "" -#: src/fs/plugin_block_fs.c:131 -msgid "Reply mismatched in terms of namespace. Discarded.\n" +#: src/gns/gns_api.c:598 +#, fuzzy +msgid "Failed to serialize lookup reply from GNS service!\n" msgstr "" +"\n" +"Không nhận được đáp ứng từ gnunetd.\n" -#: src/gns/gnunet-gns.c:191 +#: src/gns/gnunet-dns2gns.c:192 #, fuzzy +msgid "Failed to pack DNS response into UDP packet!\n" +msgstr "Lỗi mở tập tin ghi sự kiện « %s »: %s\n" + +#: src/gns/gnunet-dns2gns.c:367 +#, c-format +msgid "Cannot parse DNS request from %s\n" +msgstr "" + +#: src/gns/gnunet-dns2gns.c:383 +#, fuzzy, c-format +msgid "Received malformed DNS request from %s\n" +msgstr "Nhận yêu cầu định tuyến\n" + +#: src/gns/gnunet-dns2gns.c:391 +#, fuzzy, c-format +msgid "Received unsupported DNS request from %s\n" +msgstr "Nhận yêu cầu định tuyến\n" + +#: src/gns/gnunet-dns2gns.c:679 +msgid "IP of recursive DNS resolver to use (required)" +msgstr "" + +#: src/gns/gnunet-dns2gns.c:682 +msgid "Authoritative DNS suffix to use (optional); default: zkey.eu" +msgstr "" + +#: src/gns/gnunet-dns2gns.c:685 +msgid "Authoritative FCFS suffix to use (optional); default: fcfs.zkey.eu" +msgstr "" + +#: src/gns/gnunet-dns2gns.c:688 +msgid "UDP port to listen on for inbound DNS requests; default: 53" +msgstr "" + +#: src/gns/gnunet-dns2gns.c:701 +msgid "GNUnet DNS-to-GNS proxy (a DNS server)" +msgstr "" + +#: src/gns/gnunet-gns.c:221 +#, fuzzy, c-format msgid "Failed to connect to GNS\n" msgstr "Lỗi kết nối đến gnunetd.\n" -#: src/gns/gnunet-gns.c:232 -msgid "try to shorten a given GNS name" +#: src/gns/gnunet-gns.c:335 +#, c-format +msgid "Please specify lookup, shorten or authority operation!\n" msgstr "" -#: src/gns/gnunet-gns.c:235 -msgid "Lookup a record using GNS (NOT IMPLEMENTED)" +#: src/gns/gnunet-gns.c:356 +#, fuzzy +msgid "try to shorten a given name" +msgstr "Lỗi kết nối đến gnunetd.\n" + +#: src/gns/gnunet-gns.c:359 +msgid "Lookup a record for the given name" msgstr "" -#: src/gns/gnunet-gns.c:238 +#: src/gns/gnunet-gns.c:362 msgid "Get the authority of a particular name" msgstr "" -#: src/gns/gnunet-gns.c:241 +#: src/gns/gnunet-gns.c:365 #, fuzzy -msgid "Specify the type of the record lookup" +msgid "Specify the type of the record to lookup" msgstr "xác định mức ưu tiên của nội dung" -#: src/gns/gnunet-gns.c:244 +#: src/gns/gnunet-gns.c:368 msgid "No unneeded output" msgstr "" -#: src/gns/gnunet-gns.c:255 +#: src/gns/gnunet-gns.c:381 msgid "GNUnet GNS access tool" msgstr "" -#: src/gns/gnunet-gns-fcfsd.c:280 +#: src/gns/gnunet-gns-fcfsd.c:451 #, fuzzy, c-format msgid "Unsupported form value `%s'\n" msgstr "Lệnh không được hỗ trợ « %s ». Đang hủy bỏ.\n" -#: src/gns/gnunet-gns-fcfsd.c:333 +#: src/gns/gnunet-gns-fcfsd.c:480 #, fuzzy, c-format msgid "Failed to create record for domain `%s': %s\n" msgstr "Không thể truy cập đến tập tin gnunet-directory « %s »\n" -#: src/gns/gnunet-gns-fcfsd.c:377 +#: src/gns/gnunet-gns-fcfsd.c:524 #, c-format msgid "Found existing name `%s' for the given key\n" msgstr "" -#: src/gns/gnunet-gns-fcfsd.c:439 +#: src/gns/gnunet-gns-fcfsd.c:586 #, c-format msgid "Found %u existing records for domain `%s'\n" msgstr "" -#: src/gns/gnunet-gns-fcfsd.c:498 +#: src/gns/gnunet-gns-fcfsd.c:648 #, fuzzy, c-format msgid "Failed to create page for `%s'\n" msgstr "Không thể tạo miền tên.\n" -#: src/gns/gnunet-gns-fcfsd.c:514 +#: src/gns/gnunet-gns-fcfsd.c:664 #, fuzzy, c-format msgid "Failed to setup post processor for `%s'\n" msgstr "Lỗi cập nhật dữ liệu cho mô-đun « %s »\n" -#: src/gns/gnunet-gns-fcfsd.c:725 src/gns/gnunet-gns-fcfsd.c:737 -#, fuzzy, c-format -msgid "Option `%s' not specified in configuration section `%s'\n" +#: src/gns/gnunet-gns-fcfsd.c:700 +msgid "Domain name must not contain `.'\n" msgstr "" -"Đặc tả mạng dạng sai trong cấu hình phần « %s » cho mục nhập « %s »: %s\n" -#: src/gns/gnunet-gns-fcfsd.c:747 src/namestore/gnunet-namestore.c:299 +#: src/gns/gnunet-gns-fcfsd.c:708 +msgid "Domain name must not contain `+'\n" +msgstr "" + +#: src/gns/gnunet-gns-fcfsd.c:912 src/namestore/gnunet-namestore.c:364 #, fuzzy msgid "Failed to read or create private zone key\n" msgstr "Lỗi cập nhật dữ liệu cho mô-đun « %s »\n" -#: src/gns/gnunet-gns-fcfsd.c:757 src/namestore/gnunet-namestore.c:310 +#: src/gns/gnunet-gns-fcfsd.c:922 src/namestore/gnunet-namestore.c:375 #, fuzzy msgid "Failed to connect to namestore\n" msgstr "Không kết nối được đến trình nền gnunetd." -#: src/gns/gnunet-gns-fcfsd.c:773 src/gns/gnunet-gns-proxy.c:525 +#: src/gns/gnunet-gns-fcfsd.c:938 src/gns/gnunet-gns-proxy.c:2857 #, fuzzy msgid "Failed to start HTTP server\n" msgstr "Lỗi bắt đầu thu thập.\n" -#: src/gns/gnunet-gns-fcfsd.c:804 +#: src/gns/gnunet-gns-fcfsd.c:972 msgid "GNUnet GNS first come first serve registration service" msgstr "" -#: src/gns/gnunet-gns-proxy.c:800 -msgid "listen on specified port" +#: src/gns/gnunet-gns-proxy.c:2494 +#, fuzzy, c-format +msgid "Unable to import private key from file `%s'\n" +msgstr "Không thể tạo tài khoản người dùng:" + +#: src/gns/gnunet-gns-proxy.c:2522 +#, fuzzy, c-format +msgid "Unable to import certificate %s\n" +msgstr "Không thể lưu tập tin cấu hình « %s »:" + +#: src/gns/gnunet-gns-proxy.c:3510 +msgid "listen on specified port (default: 7777)" +msgstr "" + +#: src/gns/gnunet-gns-proxy.c:3513 +msgid "pem file to use as CA" msgstr "" -#: src/gns/gnunet-gns-proxy.c:811 +#: src/gns/gnunet-gns-proxy.c:3525 msgid "GNUnet GNS proxy" msgstr "" -#: src/hello/gnunet-hello.c:122 +#: src/gns/gnunet-service-gns.c:486 +#, c-format +msgid "Records for name `%s' in zone %s too large to fit into DHT" +msgstr "" + +#: src/gns/gnunet-service-gns.c:1216 +#, fuzzy +msgid "Failed to connect to the namestore!\n" +msgstr "Không kết nối được đến trình nền gnunetd." + +#: src/gns/gnunet-service-gns.c:1277 +#, fuzzy +msgid "Could not connect to DHT!\n" +msgstr "Không thể kết nối tới %s:%u: %s\n" + +#: src/gns/gnunet-service-gns.c:1288 +#, fuzzy +msgid "Unable to initialize resolver!\n" +msgstr "Không thể sơ khởi SQLite: %s.\n" + +#: src/gns/gnunet-service-gns_resolver.c:3439 +#, c-format +msgid "Not a GADS TLD: `%s'\n" +msgstr "" + +#: src/hello/gnunet-hello.c:118 msgid "Call with name of HELLO file to modify.\n" msgstr "" -#: src/hello/gnunet-hello.c:128 +#: src/hello/gnunet-hello.c:124 #, fuzzy, c-format msgid "Error accessing file `%s': %s\n" msgstr "Gặp lỗi khi tạo người dùng" -#: src/hello/gnunet-hello.c:136 +#: src/hello/gnunet-hello.c:132 #, c-format msgid "File `%s' is too big to be a HELLO\n" msgstr "" -#: src/hello/gnunet-hello.c:143 +#: src/hello/gnunet-hello.c:139 #, c-format msgid "File `%s' is too small to be a HELLO\n" msgstr "" -#: src/hello/gnunet-hello.c:153 src/hello/gnunet-hello.c:181 +#: src/hello/gnunet-hello.c:149 src/hello/gnunet-hello.c:177 #, fuzzy, c-format msgid "Error opening file `%s': %s\n" msgstr "Gặp lỗi khi tạo người dùng" -#: src/hello/gnunet-hello.c:169 +#: src/hello/gnunet-hello.c:165 #, fuzzy, c-format msgid "Did not find well-formed HELLO in file `%s'\n" msgstr "Không tìm thấy tập tin nào trong thư mục « %s »\n" -#: src/hello/gnunet-hello.c:193 +#: src/hello/gnunet-hello.c:189 #, fuzzy, c-format msgid "Error writing HELLO to file `%s': %s\n" msgstr "Gặp lỗi khi tạo người dùng" +#: src/hello/hello.c:904 +#, fuzzy +msgid "Failed to parse HELLO message: missing expiration time\n" +msgstr "Lỗi lưu cấu hình." + +#: src/hello/hello.c:913 +#, fuzzy +msgid "Failed to parse HELLO message: invalid expiration time\n" +msgstr "Lỗi lưu cấu hình." + +#: src/hello/hello.c:923 +#, fuzzy +msgid "Failed to parse HELLO message: malformed\n" +msgstr "Lỗi đọc danh sách bạn bè từ « %s »\n" + +#: src/hello/hello.c:933 +#, fuzzy +msgid "Failed to parse HELLO message: missing transport plugin\n" +msgstr "Không thể nạp phần bổ sung truyền tải « %s »\n" + +#: src/hello/hello.c:950 +#, c-format +msgid "Plugin `%s' not found\n" +msgstr "" + +#: src/hello/hello.c:959 +#, c-format +msgid "Plugin `%s' does not support URIs yet\n" +msgstr "" + +#: src/hello/hello.c:978 +#, fuzzy, c-format +msgid "Failed to parse `%s' as an address for plugin `%s'\n" +msgstr "Lỗi đóng kết đến cổng %s %d.\n" + #: src/hostlist/gnunet-daemon-hostlist.c:264 msgid "" "None of the functions for the hostlist daemon were enabled. I have no " @@ -3293,7 +3446,7 @@ msgstr "Tắt quảng cáo máy này cho đồng đẳng khác" msgid "provide a hostlist server" msgstr "trình phục vụ danh sách máy HTTP hợp nhất" -#: src/hostlist/gnunet-daemon-hostlist.c:341 +#: src/hostlist/gnunet-daemon-hostlist.c:344 msgid "GNUnet hostlist server and client" msgstr "" @@ -3317,179 +3470,140 @@ msgstr "Nhận được thông báo « %s » sai từ đồng đẳng « %s ».\ msgid "# valid HELLOs downloaded from hostlist servers" msgstr "# các HELLO tải xuống qua HTTP" -#: src/hostlist/hostlist-client.c:375 src/hostlist/hostlist-client.c:396 -#, fuzzy, c-format -msgid "No `%s' specified in `%s' configuration, will not bootstrap.\n" -msgstr "" -"Chưa ghi rõ địa chỉ URL của danh sách các máy nên không nạp và khởi động.\n" - -#: src/hostlist/hostlist-client.c:473 src/hostlist/hostlist-client.c:683 -#: src/hostlist/hostlist-client.c:689 src/hostlist/hostlist-client.c:741 -#: src/hostlist/hostlist-client.c:750 src/hostlist/hostlist-client.c:871 -#: src/hostlist/hostlist-client.c:961 src/hostlist/hostlist-client.c:966 -#: src/transport/plugin_transport_http_client.c:110 -#: src/transport/plugin_transport_http_client.c:125 +#: src/hostlist/hostlist-client.c:469 src/hostlist/hostlist-client.c:680 +#: src/hostlist/hostlist-client.c:686 src/hostlist/hostlist-client.c:738 +#: src/hostlist/hostlist-client.c:747 src/hostlist/hostlist-client.c:868 +#: src/hostlist/hostlist-client.c:958 src/hostlist/hostlist-client.c:963 +#: src/transport/plugin_transport_http_client.c:1052 +#: src/transport/plugin_transport_http_client.c:1067 #, c-format msgid "%s failed at %s:%d: `%s'\n" msgstr "%s bị lỗi tại %s:%d: « %s »\n" -#: src/hostlist/hostlist-client.c:593 src/hostlist/hostlist-client.c:1331 +#: src/hostlist/hostlist-client.c:589 src/hostlist/hostlist-client.c:1325 msgid "# advertised hostlist URIs" msgstr "" -#: src/hostlist/hostlist-client.c:623 +#: src/hostlist/hostlist-client.c:619 #, c-format msgid "# advertised URI `%s' downloaded" msgstr "" -#: src/hostlist/hostlist-client.c:664 +#: src/hostlist/hostlist-client.c:661 #, c-format msgid "" "Advertised hostlist with URI `%s' could not be downloaded. Advertised URI " "gets dismissed.\n" msgstr "" -#: src/hostlist/hostlist-client.c:802 +#: src/hostlist/hostlist-client.c:799 #, fuzzy, c-format msgid "Timeout trying to download hostlist from `%s'\n" msgstr "Đang thử tải danh sách các máy xuống « %s »\n" -#: src/hostlist/hostlist-client.c:816 +#: src/hostlist/hostlist-client.c:813 #, c-format msgid "Download limit of %u bytes exceeded, stopping download\n" msgstr "" -#: src/hostlist/hostlist-client.c:836 +#: src/hostlist/hostlist-client.c:833 #, fuzzy, c-format msgid "Download of hostlist from `%s' failed: `%s'\n" msgstr "Tải lên « %s » hoàn thành, địa chỉ URI là « %s ».\n" -#: src/hostlist/hostlist-client.c:842 +#: src/hostlist/hostlist-client.c:839 #, fuzzy, c-format msgid "Download of hostlist `%s' completed.\n" msgstr "Tải lên « %s » hoàn thành, địa chỉ URI là « %s ».\n" -#: src/hostlist/hostlist-client.c:850 +#: src/hostlist/hostlist-client.c:847 #, c-format msgid "Adding successfully tested hostlist `%s' datastore.\n" msgstr "" -#: src/hostlist/hostlist-client.c:903 +#: src/hostlist/hostlist-client.c:900 #, fuzzy, c-format msgid "Bootstrapping using hostlist at `%s'.\n" msgstr "Đang nạp và khởi động dùng « %s ».\n" -#: src/hostlist/hostlist-client.c:911 +#: src/hostlist/hostlist-client.c:908 msgid "# hostlist downloads initiated" msgstr "" -#: src/hostlist/hostlist-client.c:1037 src/hostlist/hostlist-client.c:1505 +#: src/hostlist/hostlist-client.c:1035 src/hostlist/hostlist-client.c:1498 msgid "# milliseconds between hostlist downloads" msgstr "" -#: src/hostlist/hostlist-client.c:1046 +#: src/hostlist/hostlist-client.c:1043 #, c-format -msgid "Have %u/%u connections. Will consider downloading hostlist in %llums\n" +msgid "Have %u/%u connections. Will consider downloading hostlist in %s\n" msgstr "" -#: src/hostlist/hostlist-client.c:1084 -msgid "Scheduled saving of hostlists\n" -msgstr "" - -#: src/hostlist/hostlist-client.c:1088 -#, c-format -msgid "Hostlists will be saved to file again in %llums\n" -msgstr "" - -#: src/hostlist/hostlist-client.c:1111 src/hostlist/hostlist-client.c:1127 +#: src/hostlist/hostlist-client.c:1107 src/hostlist/hostlist-client.c:1123 #, fuzzy msgid "# active connections" msgstr "# các kết nối dht" -#: src/hostlist/hostlist-client.c:1242 -#, c-format -msgid "Initial time between hostlist downloads is %llums\n" -msgstr "" - #: src/hostlist/hostlist-client.c:1273 #, fuzzy, c-format -msgid "" -"No `%s' specified in `%s' configuration, cannot load hostlists from file.\n" -msgstr "" -"Chưa ghi rõ địa chỉ URL của danh sách các máy nên không nạp và khởi động.\n" - -#: src/hostlist/hostlist-client.c:1279 -#, fuzzy, c-format msgid "Loading saved hostlist entries from file `%s' \n" msgstr "Đang thử tải danh sách các máy xuống « %s »\n" -#: src/hostlist/hostlist-client.c:1283 -#, c-format -msgid "Hostlist file `%s' is not existing\n" -msgstr "" +#: src/hostlist/hostlist-client.c:1277 +#, fuzzy, c-format +msgid "Hostlist file `%s' does not exist\n" +msgstr "Khoá phiên chạy từ đồng đẳng « %s » không thể được thẩm tra.\n" -#: src/hostlist/hostlist-client.c:1294 +#: src/hostlist/hostlist-client.c:1288 #, fuzzy, c-format msgid "Could not open file `%s' for reading to load hostlists: %s\n" msgstr "Lỗi mở tập tin theo dõi « %s »: %s\n" -#: src/hostlist/hostlist-client.c:1327 +#: src/hostlist/hostlist-client.c:1321 #, c-format msgid "%u hostlist URIs loaded from file\n" msgstr "" -#: src/hostlist/hostlist-client.c:1329 +#: src/hostlist/hostlist-client.c:1323 #, fuzzy msgid "# hostlist URIs read from file" msgstr "# các byte danh sách máy được trả về" -#: src/hostlist/hostlist-client.c:1362 -#, fuzzy, c-format -msgid "" -"No `%s' specified in `%s' configuration, cannot save hostlists to file.\n" -msgstr "" -"Chưa ghi rõ địa chỉ URL của danh sách các máy nên không nạp và khởi động.\n" - -#: src/hostlist/hostlist-client.c:1376 +#: src/hostlist/hostlist-client.c:1368 #, fuzzy, c-format msgid "Could not open file `%s' for writing to save hostlists: %s\n" msgstr "Lỗi mở tập tin theo dõi « %s »: %s\n" -#: src/hostlist/hostlist-client.c:1381 +#: src/hostlist/hostlist-client.c:1373 #, fuzzy, c-format msgid "Writing %u hostlist URIs to `%s'\n" msgstr "Đang thử tải danh sách các máy xuống « %s »\n" -#: src/hostlist/hostlist-client.c:1405 src/hostlist/hostlist-client.c:1422 +#: src/hostlist/hostlist-client.c:1397 src/hostlist/hostlist-client.c:1414 #, c-format msgid "Error writing hostlist URIs to file `%s'\n" msgstr "" -#: src/hostlist/hostlist-client.c:1417 +#: src/hostlist/hostlist-client.c:1409 #, fuzzy msgid "# hostlist URIs written to file" msgstr "# các byte danh sách máy được trả về" -#: src/hostlist/hostlist-client.c:1470 +#: src/hostlist/hostlist-client.c:1463 msgid "Learning is enabled on this peer\n" msgstr "" -#: src/hostlist/hostlist-client.c:1473 -#, c-format -msgid "Hostlists will be saved to file again in %llums\n" -msgstr "" - -#: src/hostlist/hostlist-client.c:1482 +#: src/hostlist/hostlist-client.c:1475 msgid "Learning is not enabled on this peer\n" msgstr "" -#: src/hostlist/hostlist-client.c:1494 +#: src/hostlist/hostlist-client.c:1487 #, c-format msgid "" "Since learning is not enabled on this peer, hostlist file `%s' was removed\n" msgstr "" -#: src/hostlist/hostlist-client.c:1498 +#: src/hostlist/hostlist-client.c:1491 #, fuzzy, c-format msgid "Hostlist file `%s' could not be removed\n" msgstr "Khoá phiên chạy từ đồng đẳng « %s » không thể được thẩm tra.\n" @@ -3504,9 +3618,9 @@ msgid "expired addresses encountered" msgstr "" #: src/hostlist/hostlist-server.c:184 src/hostlist/hostlist-server.c:425 -#: src/peerinfo-tool/gnunet-peerinfo.c:403 -#: src/peerinfo-tool/gnunet-peerinfo.c:519 -#: src/topology/gnunet-daemon-topology.c:927 +#: src/peerinfo-tool/gnunet-peerinfo.c:331 +#: src/peerinfo-tool/gnunet-peerinfo.c:386 +#: src/topology/gnunet-daemon-topology.c:922 #, fuzzy, c-format msgid "Error in communication with PEERINFO service: %s\n" msgstr "Cổng để liên lạc với giao diện người dùng GNUnet" @@ -3529,10 +3643,6 @@ msgstr "trình phục vụ danh sách máy HTTP hợp nhất" msgid "hostlist requests refused (not HTTP GET)" msgstr "# các yêu cầu danh sách máy được nhận" -#: src/hostlist/hostlist-server.c:273 -msgid "Sending 100 CONTINUE reply\n" -msgstr "" - #: src/hostlist/hostlist-server.c:279 #, c-format msgid "Refusing `%s' request with %llu bytes of upload data\n" @@ -3571,64 +3681,102 @@ msgstr "# Các quảng cáo ngoại được chuyển tiếp" msgid "Advertisement message could not be queued by core\n" msgstr "" -#: src/hostlist/hostlist-server.c:561 +#: src/hostlist/hostlist-server.c:562 #, c-format msgid "Invalid port number %llu. Exiting.\n" msgstr "" -#: src/hostlist/hostlist-server.c:570 +#: src/hostlist/hostlist-server.c:571 #, c-format msgid "Hostlist service starts on %s:%llu\n" msgstr "" -#: src/hostlist/hostlist-server.c:584 +#: src/hostlist/hostlist-server.c:585 #, fuzzy, c-format msgid "Address to obtain hostlist: `%s'\n" msgstr "Đang thử tải danh sách các máy xuống « %s »\n" -#: src/hostlist/hostlist-server.c:624 +#: src/hostlist/hostlist-server.c:625 #, fuzzy, c-format msgid "`%s' is not a valid IP address! Ignoring BINDTOIP.\n" msgstr "« %s » không sẵn sàng.\n" -#: src/hostlist/hostlist-server.c:666 +#: src/hostlist/hostlist-server.c:667 #, fuzzy, c-format msgid "Could not start hostlist HTTP server on port %u\n" msgstr "Cổng cho trình phục vụ HTTP danh sách máy chủ thống nhất" -#: src/integration-tests/connection_watchdog.c:997 +#: src/integration-tests/connection_watchdog.c:1001 #, fuzzy, c-format msgid "Transport plugin: `%s' port %llu\n" msgstr "Đang nạp các truyền tải « %s »\n" -#: src/integration-tests/connection_watchdog.c:1030 +#: src/integration-tests/connection_watchdog.c:1034 #, fuzzy, c-format msgid "Found %u transport plugins: `%s'\n" msgstr "Đang nạp các truyền tải « %s »\n" -#: src/integration-tests/connection_watchdog.c:1089 +#: src/integration-tests/connection_watchdog.c:1093 msgid "Send ping messages to test connectivity (default == NO)" msgstr "" -#: src/integration-tests/connection_watchdog.c:1095 -#: src/template/gnunet-template.c:68 +#: src/integration-tests/connection_watchdog.c:1102 +#: src/template/gnunet-template.c:70 msgid "help text" msgstr "" -#: src/mesh/gnunet-service-mesh.c:4590 -msgid "Wrong CORE service\n" -msgstr "" +#: src/mesh/gnunet-mesh.c:211 +#, fuzzy +msgid "provide information about all tunnels (continuously) NOT IMPLEMENTED" +msgstr "In ra thông tin về các đồng đẳng GNUnet." -#: src/mesh/gnunet-service-mesh.c:4784 +#: src/mesh/gnunet-mesh.c:214 #, fuzzy -msgid "Mesh service is lacking key configuration settings. Exiting.\n" -msgstr "Lưu cấu hình ngay bây giờ không?" +msgid "provide information about a particular tunnel" +msgstr "In ra thông tin về các đồng đẳng GNUnet." -#: src/mesh/gnunet-service-mesh.c:4793 +#: src/mesh/gnunet-mesh.c:224 #, fuzzy -msgid "Mesh service could not access hostkey. Exiting.\n" +msgid "Print information about mesh tunnels and peers." +msgstr "In ra thông tin về các đồng đẳng GNUnet." + +#: src/mesh/gnunet-service-mesh.c:8015 src/mesh/gnunet-service-mesh-new.c:8015 +msgid "Wrong CORE service\n" +msgstr "" + +#: src/mesh/gnunet-service-mesh.c:8232 src/mesh/gnunet-service-mesh-new.c:8232 +#, fuzzy, c-format +msgid "Mesh service could not access hostkey: %s. Exiting.\n" msgstr "Không thể truy cập đến thông tin về không gian tên.\n" +#: src/mesh/gnunet-service-mesh.c:8314 src/mesh/gnunet-service-mesh.c:8326 +#: src/mesh/gnunet-service-mesh.c:8338 src/mesh/gnunet-service-mesh.c:8352 +#: src/mesh/gnunet-service-mesh.c:8364 src/mesh/gnunet-service-mesh.c:8376 +#: src/mesh/gnunet-service-mesh.c:8388 src/mesh/gnunet-service-mesh-new.c:8321 +#: src/mesh/gnunet-service-mesh-new.c:8333 +#: src/mesh/gnunet-service-mesh-new.c:8345 +#: src/mesh/gnunet-service-mesh-new.c:8359 +#: src/mesh/gnunet-service-mesh-new.c:8371 +#: src/mesh/gnunet-service-mesh-new.c:8383 +#: src/mesh/gnunet-service-mesh-new.c:8395 +#: src/regex/gnunet-daemon-regexprofiler.c:335 +#: src/regex/gnunet-daemon-regexprofiler.c:347 +#: src/regex/gnunet-daemon-regexprofiler.c:360 +#: src/regex/gnunet-daemon-regexprofiler.c:373 +#: src/regex/gnunet-regex-simulation-profiler.c:659 +#, fuzzy, c-format +msgid "%s service is lacking key configuration settings (%s). Exiting.\n" +msgstr "Lưu cấu hình ngay bây giờ không?" + +#: src/mesh/gnunet-service-mesh.c:8400 src/mesh/gnunet-service-mesh.c:8410 +#: src/mesh/gnunet-service-mesh.c:8421 src/mesh/gnunet-service-mesh-new.c:8407 +#: src/mesh/gnunet-service-mesh-new.c:8417 +#: src/mesh/gnunet-service-mesh-new.c:8428 +#, fuzzy, c-format +msgid "" +"%s service is lacking key configuration settings (%s). Using default (%u).\n" +msgstr "Lưu cấu hình ngay bây giờ không?" + #: src/mysql/mysql.c:174 #, c-format msgid "Trying to use file `%s' for MySQL configuration.\n" @@ -3639,199 +3787,328 @@ msgstr "Đang thử dùng tập tin « %s » cho cấu hình MySQL.\n" msgid "Could not access file `%s': %s\n" msgstr "Không thể truy cập đến « %s »: %s\n" -#: src/namestore/gnunet-namestore.c:157 +#: src/namestore/gnunet-namestore.c:212 #, fuzzy, c-format msgid "Adding record failed: %s\n" msgstr "Gặp lỗi khi tải lên tập tin: %s\n" -#: src/namestore/gnunet-namestore.c:183 +#: src/namestore/gnunet-namestore.c:243 #, fuzzy, c-format msgid "Deleting record failed: %s\n" msgstr "Gặp lỗi khi tải lên tập tin: %s\n" -#: src/namestore/gnunet-namestore.c:239 +#: src/namestore/gnunet-namestore.c:304 #, c-format msgid "\tCorrupt or unsupported record of type %u\n" msgstr "" -#: src/namestore/gnunet-namestore.c:276 -#, c-format -msgid "Option `%s' not given, but I need a zone key file!\n" +#: src/namestore/gnunet-namestore.c:320 +msgid "for at least" msgstr "" -#: src/namestore/gnunet-namestore.c:281 -#, fuzzy, c-format -msgid "Using default zone file `%s'\n" -msgstr "Đang bắt đầu tài về « %s »\n" +#: src/namestore/gnunet-namestore.c:321 +msgid "until" +msgstr "" -#: src/namestore/gnunet-namestore.c:291 +#: src/namestore/gnunet-namestore.c:356 #, fuzzy, c-format msgid "No options given\n" msgstr "chưa đưa ra tên" -#: src/namestore/gnunet-namestore.c:321 +#: src/namestore/gnunet-namestore.c:386 #, fuzzy, c-format msgid "Unsupported type `%s'\n" msgstr "Lệnh không được hỗ trợ « %s ». Đang hủy bỏ.\n" -#: src/namestore/gnunet-namestore.c:328 src/namestore/gnunet-namestore.c:350 -#: src/namestore/gnunet-namestore.c:374 src/namestore/gnunet-namestore.c:384 -#: src/namestore/gnunet-namestore.c:409 +#: src/namestore/gnunet-namestore.c:394 src/namestore/gnunet-namestore.c:418 +#: src/namestore/gnunet-namestore.c:465 src/namestore/gnunet-namestore.c:477 +#: src/namestore/gnunet-namestore.c:518 #, fuzzy, c-format msgid "Missing option `%s' for operation `%s'\n" msgstr "Giá trị cấu hình « %s » cho « %s » trong phần « %s » nên là con số\n" -#: src/namestore/gnunet-namestore.c:329 src/namestore/gnunet-namestore.c:351 +#: src/namestore/gnunet-namestore.c:395 src/namestore/gnunet-namestore.c:419 msgid "add/del" msgstr "" -#: src/namestore/gnunet-namestore.c:341 +#: src/namestore/gnunet-namestore.c:408 #, c-format msgid "Value `%s' invalid for record type `%s'\n" msgstr "" -#: src/namestore/gnunet-namestore.c:366 +#: src/namestore/gnunet-namestore.c:446 #, fuzzy, c-format msgid "Invalid time format `%s'\n" msgstr "Địa chỉ IP định dạng sai: %s\n" -#: src/namestore/gnunet-namestore.c:375 src/namestore/gnunet-namestore.c:385 +#: src/namestore/gnunet-namestore.c:455 +#, c-format +msgid "" +"Deletion requires either absolute time, or no time at all. Got relative time " +"`%s' instead.\n" +msgstr "" + +#: src/namestore/gnunet-namestore.c:466 src/namestore/gnunet-namestore.c:478 +#: src/namestore/gnunet-namestore.c:497 msgid "add" msgstr "" -#: src/namestore/gnunet-namestore.c:410 +#: src/namestore/gnunet-namestore.c:496 +#, fuzzy, c-format +msgid "No valid expiration time for operation `%s'\n" +msgstr "Giá trị cấu hình « %s » cho « %s » trong phần « %s » nên là con số\n" + +#: src/namestore/gnunet-namestore.c:519 msgid "del" msgstr "" -#: src/namestore/gnunet-namestore.c:462 +#: src/namestore/gnunet-namestore.c:569 +#: src/peerinfo-tool/gnunet-peerinfo.c:598 +#, fuzzy, c-format +msgid "Invalid URI `%s'\n" +msgstr "Dữ liệu nhập không hợp lệ.\n" + +#: src/namestore/gnunet-namestore.c:625 +#, fuzzy, c-format +msgid "Using default zone file `%s'\n" +msgstr "Đang bắt đầu tài về « %s »\n" + +#: src/namestore/gnunet-namestore.c:677 msgid "add record" msgstr "" -#: src/namestore/gnunet-namestore.c:465 +#: src/namestore/gnunet-namestore.c:680 msgid "delete record" msgstr "" -#: src/namestore/gnunet-namestore.c:468 +#: src/namestore/gnunet-namestore.c:683 msgid "display records" msgstr "" -#: src/namestore/gnunet-namestore.c:471 +#: src/namestore/gnunet-namestore.c:686 msgid "" "expiration time for record to use (for adding only), \"never\" is possible" msgstr "" -#: src/namestore/gnunet-namestore.c:474 +#: src/namestore/gnunet-namestore.c:689 msgid "name of the record to add/delete/display" msgstr "" -#: src/namestore/gnunet-namestore.c:477 +#: src/namestore/gnunet-namestore.c:692 msgid "type of the record to add/delete/display" msgstr "" -#: src/namestore/gnunet-namestore.c:480 +#: src/namestore/gnunet-namestore.c:695 +msgid "URI to import into our zone" +msgstr "" + +#: src/namestore/gnunet-namestore.c:698 msgid "value of the record to add/delete" msgstr "" -#: src/namestore/gnunet-namestore.c:483 +#: src/namestore/gnunet-namestore.c:701 msgid "create or list public record" msgstr "" -#: src/namestore/gnunet-namestore.c:486 +#: src/namestore/gnunet-namestore.c:704 msgid "create or list non-authority record" msgstr "" -#: src/namestore/gnunet-namestore.c:489 +#: src/namestore/gnunet-namestore.c:707 #, fuzzy msgid "filename with the zone key" msgstr "tên tập tin" -#: src/namestore/gnunet-namestore.c:500 +#: src/namestore/gnunet-namestore.c:718 #, fuzzy msgid "GNUnet zone manipulation tool" msgstr "Cấu hình GNUnet" -#: src/namestore/gnunet-service-namestore.c:143 -#, c-format -msgid "File zone `%s' but corrupt content already exists, failed to write! \n" -msgstr "" +#: src/namestore/gnunet-service-namestore.c:241 +#: src/namestore/gnunet-service-namestore.c:257 +#, fuzzy, c-format +msgid "Failed to write zone key to file `%s': %s\n" +msgstr "Lỗi mở tập tin ghi sự kiện « %s »: %s\n" -#: src/namestore/gnunet-service-namestore.c:154 -#, c-format -msgid "File zone `%s' containing this key already exists\n" +#: src/namestore/gnunet-service-namestore.c:243 +msgid "file exists but reading key failed" msgstr "" -#: src/namestore/gnunet-service-namestore.c:160 -#, c-format -msgid "" -"File zone `%s' but different zone key already exists, failed to write! \n" -msgstr "" +#: src/namestore/gnunet-service-namestore.c:259 +#, fuzzy +msgid "file exists with different key" +msgstr "tên tập tin" -#: src/namestore/gnunet-service-namestore.c:198 +#: src/namestore/gnunet-service-namestore.c:1557 +#, fuzzy +msgid "Failed to find record to remove\n" +msgstr "Không thể kết nối tới %s:%u: %s\n" + +#: src/namestore/gnunet-service-namestore.c:2172 #, fuzzy, c-format -msgid "Stored zonekey for zone `%s' in file `%s'\n" -msgstr "Lỗi mở tập tin ghi sự kiện « %s »: %s\n" +msgid "Could not parse zone key file `%s'\n" +msgstr "Không thể truy cập đến tập tin gnunet-directory « %s »\n" -#: src/namestore/gnunet-service-namestore.c:1909 +#: src/namestore/gnunet-service-namestore.c:2262 msgid "No directory to load zonefiles specified in configuration\n" msgstr "" -#: src/namestore/gnunet-service-namestore.c:1918 +#: src/namestore/gnunet-service-namestore.c:2272 #, c-format msgid "Creating directory `%s' for zone files failed!\n" msgstr "" -#: src/namestore/namestore_api.c:315 src/namestore/namestore_api.c:353 -msgid "Namestore added record successfully" -msgstr "" - -#: src/namestore/namestore_api.c:323 +#: src/namestore/namestore_api.c:345 msgid "Namestore failed to add record" msgstr "" -#: src/namestore/namestore_api.c:361 -msgid "Namestore record already existed" -msgstr "" - -#: src/namestore/namestore_api.c:368 +#: src/namestore/namestore_api.c:371 msgid "Namestore failed to add record\n" msgstr "" -#: src/namestore/namestore_api.c:401 -#, fuzzy -msgid "Namestore removed record successfully" -msgstr "Dịch vụ GNUnet đã được cài đặt.\n" - -#: src/namestore/namestore_api.c:408 -msgid "No records for entry" -msgstr "" - #: src/namestore/namestore_api.c:415 #, fuzzy -msgid "Could not find record to remove" -msgstr "Không thể kết nối tới %s:%u: %s\n" - -#: src/namestore/namestore_api.c:422 -#, fuzzy msgid "Failed to create new signature" msgstr "Không thể tạo miền tên.\n" -#: src/namestore/namestore_api.c:429 +#: src/namestore/namestore_api.c:419 #, fuzzy msgid "Failed to put new set of records in database" msgstr "" "\n" "Không nhận được đáp ứng từ gnunetd.\n" +#: src/namestore/namestore_api.c:423 +#, fuzzy +msgid "Failed to remove records from database" +msgstr "" +"\n" +"Không nhận được đáp ứng từ gnunetd.\n" + +#: src/namestore/namestore_api.c:427 +#, fuzzy +msgid "Failed to access database" +msgstr "Lỗi mở tập tin ghi sự kiện « %s »: %s\n" + +#: src/namestore/namestore_api.c:431 +#, fuzzy +msgid "unknown internal error in namestore" +msgstr "=\tLỗi đọc thư mục.\n" + +#: src/namestore/namestore_api.c:436 +msgid "Protocol error" +msgstr "" + +#: src/namestore/namestore_common.c:530 src/namestore/namestore_common.c:670 +#, fuzzy, c-format +msgid "Unsupported record type %d\n" +msgstr "Lệnh không được hỗ trợ « %s ». Đang hủy bỏ.\n" + +#: src/namestore/namestore_common.c:537 +#, fuzzy, c-format +msgid "Unable to parse IPv4 address `%s'\n" +msgstr "Mức ưu tiên tiến trình không hợp lê « %s ».\n" + +#: src/namestore/namestore_common.c:560 +#, fuzzy, c-format +msgid "Unable to parse SOA record `%s'\n" +msgstr "Lỗi đọc danh sách bạn bè từ « %s »\n" + +#: src/namestore/namestore_common.c:583 +#, fuzzy, c-format +msgid "Unable to parse MX record `%s'\n" +msgstr "Lỗi đọc danh sách bạn bè từ « %s »\n" + +#: src/namestore/namestore_common.c:601 +#, fuzzy, c-format +msgid "Unable to parse IPv6 address `%s'\n" +msgstr "Mức ưu tiên tiến trình không hợp lê « %s ».\n" + +#: src/namestore/namestore_common.c:614 +#, fuzzy, c-format +msgid "Unable to parse PKEY record `%s'\n" +msgstr "Lỗi đọc danh sách bạn bè từ « %s »\n" + +#: src/namestore/namestore_common.c:635 +#, fuzzy, c-format +msgid "Unable to parse VPN record string `%s'\n" +msgstr "Lỗi đọc danh sách bạn bè từ « %s »\n" + +#: src/namestore/namestore_common.c:661 +#, fuzzy, c-format +msgid "Unable to parse TLSA record string `%s'\n" +msgstr "Lỗi đọc danh sách bạn bè từ « %s »\n" + +#: src/namestore/plugin_namestore_postgres.c:95 +#, fuzzy +msgid "Failed to create indices\n" +msgstr "Không thể tạo miền tên.\n" + #: src/nat/gnunet-nat-server.c:279 #, c-format msgid "Please pass valid port number as the first argument! (got `%s')\n" msgstr "" -#: src/nat/gnunet-nat-server.c:318 +#: src/nat/gnunet-nat-server.c:321 msgid "GNUnet NAT traversal test helper daemon" msgstr "" -#: src/nat/nat.c:799 +#: src/nat/nat_auto.c:169 +msgid "NAT traversal with ICMP Server timed out.\n" +msgstr "" + +#: src/nat/nat_auto.c:199 +msgid "NAT traversal with ICMP Server succeeded.\n" +msgstr "" + +#: src/nat/nat_auto.c:200 +msgid "NAT traversal with ICMP Server failed.\n" +msgstr "" + +#: src/nat/nat_auto.c:219 +#, fuzzy +msgid "Testing connection reversal with ICMP server.\n" +msgstr "Cổng để liên lạc với giao diện người dùng GNUnet" + +#: src/nat/nat_auto.c:265 +#, c-format +msgid "Detected external IP `%s'\n" +msgstr "" + +#: src/nat/nat_auto.c:331 +msgid "This system has a global IPv6 address, setting IPv6 to supported.\n" +msgstr "" + +#: src/nat/nat_auto.c:347 +#, fuzzy, c-format +msgid "Detected internal network address `%s'.\n" +msgstr "GNUnet bây giờ sử dụng địa chỉ IP %s.\n" + +#: src/nat/nat_auto.c:400 +msgid "upnpc found, enabling its use\n" +msgstr "" + +#: src/nat/nat_auto.c:401 +msgid "upnpc not found\n" +msgstr "" + +#: src/nat/nat_auto.c:434 +msgid "gnunet-helper-nat-server found, testing it\n" +msgstr "" + +#: src/nat/nat_auto.c:435 +msgid "No working gnunet-helper-nat-server found\n" +msgstr "" + +#: src/nat/nat_auto.c:469 +msgid "gnunet-helper-nat-client found, enabling it\n" +msgstr "" + +#: src/nat/nat_auto.c:470 +msgid "gnunet-helper-nat-client not found or behind NAT, disabling it\n" +msgstr "" + +#: src/nat/nat.c:795 #, c-format msgid "gnunet-helper-nat-server generated malformed address `%s'\n" msgstr "" @@ -3841,27 +4118,34 @@ msgstr "" msgid "Failed to start %s\n" msgstr "Lỗi bắt đầu thu thập.\n" -#: src/nat/nat.c:1111 -#, fuzzy, c-format -msgid "Malformed %s `%s' given in configuration!\n" -msgstr "Lỗi lưu cấu hình." +#: src/nat/nat.c:1113 +msgid "malformed" +msgstr "" -#: src/nat/nat.c:1177 src/nat/nat.c:1187 +#: src/nat/nat.c:1179 src/nat/nat.c:1191 #, c-format msgid "" "Configuration requires `%s', but binary is not installed properly (SUID bit " "not set). Option disabled.\n" msgstr "" -#: src/nat/nat.c:1321 +#: src/nat/nat.c:1326 msgid "Internal IP address not known, cannot use ICMP NAT traversal method\n" msgstr "" -#: src/nat/nat.c:1332 +#: src/nat/nat.c:1337 #, c-format msgid "Running gnunet-helper-nat-client %s %s %u\n" msgstr "" +#: src/nat/nat_mini.c:170 +msgid "`external-ip' command not found\n" +msgstr "" + +#: src/nat/nat_mini.c:505 +msgid "`upnpc' command not found\n" +msgstr "" + #: src/nat/nat_test.c:341 #, fuzzy msgid "Failed to connect to `gnunet-nat-server'\n" @@ -3872,45 +4156,77 @@ msgstr "Lỗi kết nối đến gnunetd.\n" msgid "Failed to create listen socket bound to `%s' for NAT test: %s\n" msgstr "" -#: src/nse/gnunet-nse-profiler.c:928 +#: src/nse/gnunet-nse-profiler.c:1009 #, fuzzy -msgid "Measure quality and performance of the NSE service." -msgstr "Không thể truy cập đến dịch vụ" +msgid "limit to the number of connections to NSE services, 0 for none" +msgstr "Không kết nối được đến trình nền gnunetd." -#: src/nse/gnunet-service-nse.c:925 -#, c-format -msgid "Proof of work invalid: %llu!\n" +#: src/nse/gnunet-nse-profiler.c:1012 +msgid "name of the file for writing connection information and statistics" msgstr "" -#: src/nse/gnunet-service-nse.c:1381 src/nse/gnunet-service-nse.c:1400 -#: src/nse/gnunet-service-nse.c:1421 -msgid "NSE service is lacking key configuration settings. Exiting.\n" +#: src/nse/gnunet-nse-profiler.c:1015 +msgid "name of the file with the login information for the testbed" msgstr "" -#: src/nse/gnunet-service-nse.c:1388 -msgid "Invalid work requirement for NSE service. Exiting.\n" +#: src/nse/gnunet-nse-profiler.c:1018 +msgid "IP address of this system as seen by the rest of the testbed" +msgstr "" + +#: src/nse/gnunet-nse-profiler.c:1021 +msgid "delay between queries to statistics during a round" +msgstr "" + +#: src/nse/gnunet-nse-profiler.c:1024 +msgid "prefix of the filenames we use for writing the topology for each round" +msgstr "" + +#: src/nse/gnunet-nse-profiler.c:1027 +msgid "name of the file for writing the main results" +msgstr "" + +#: src/nse/gnunet-nse-profiler.c:1030 +msgid "Number of peers to run in each round, separated by commas" +msgstr "" + +#: src/nse/gnunet-nse-profiler.c:1036 +msgid "delay between rounds" msgstr "" -#: src/nse/gnunet-service-nse.c:1409 +#: src/nse/gnunet-nse-profiler.c:1046 #, fuzzy -msgid "NSE service could not access hostkey. Exiting.\n" +msgid "Measure quality and performance of the NSE service." +msgstr "Không thể truy cập đến dịch vụ" + +#: src/nse/gnunet-service-nse.c:1389 +#, fuzzy, c-format +msgid "NSE service could not access hostkey: %s\n" msgstr "Không thể truy cập đến thông tin về không gian tên.\n" +#: src/nse/gnunet-service-nse.c:1403 src/nse/gnunet-service-nse.c:1478 +#: src/nse/gnunet-service-nse.c:1495 +msgid "NSE service is lacking key configuration settings. Exiting.\n" +msgstr "" + +#: src/nse/gnunet-service-nse.c:1485 +msgid "Invalid work requirement for NSE service. Exiting.\n" +msgstr "" + #: src/peerinfo/gnunet-service-peerinfo.c:134 #, fuzzy, c-format msgid "Removing expired address of transport `%s'\n" msgstr "Đã nạp truyền tải « %s »\n" -#: src/peerinfo/gnunet-service-peerinfo.c:203 +#: src/peerinfo/gnunet-service-peerinfo.c:230 #, fuzzy, c-format msgid "Failed to parse HELLO in file `%s'\n" msgstr "Lỗi đọc danh sách bạn bè từ « %s »\n" -#: src/peerinfo/gnunet-service-peerinfo.c:229 +#: src/peerinfo/gnunet-service-peerinfo.c:269 msgid "# peers known" msgstr "" -#: src/peerinfo/gnunet-service-peerinfo.c:254 +#: src/peerinfo/gnunet-service-peerinfo.c:297 #, c-format msgid "" "File `%s' in directory `%s' does not match naming convention. Removed.\n" @@ -3918,42 +4234,42 @@ msgstr "" "Tập tin « %s » trong thư mục « %s » không tùy theo quy ước đặt tên. Bị gỡ " "bỏ.\n" -#: src/peerinfo/gnunet-service-peerinfo.c:353 +#: src/peerinfo/gnunet-service-peerinfo.c:419 #, c-format msgid "Still no peers found in `%s'!\n" msgstr "Vẫn còn không tìm thấy đồng đẳng trong « %s ».\n" -#: src/peerinfo/gnunet-service-peerinfo.c:710 +#: src/peerinfo/gnunet-service-peerinfo.c:807 #, c-format msgid "Importing HELLOs from `%s'\n" msgstr "" -#: src/peerinfo/peerinfo_api.c:238 +#: src/peerinfo/peerinfo_api.c:239 msgid "aborted due to explicit disconnect request" msgstr "" -#: src/peerinfo/peerinfo_api.c:358 +#: src/peerinfo/peerinfo_api.c:359 #, fuzzy msgid "failed to transmit request (service down?)" msgstr "Lỗi đọc danh sách bạn bè từ « %s »\n" -#: src/peerinfo/peerinfo_api.c:505 +#: src/peerinfo/peerinfo_api.c:509 #, fuzzy msgid "Failed to receive response from `PEERINFO' service." msgstr "" "\n" "Không nhận được đáp ứng từ gnunetd.\n" -#: src/peerinfo/peerinfo_api.c:531 src/peerinfo/peerinfo_api.c:550 -#: src/peerinfo/peerinfo_api.c:565 src/peerinfo/peerinfo_api.c:576 -#: src/peerinfo/peerinfo_api.c:587 +#: src/peerinfo/peerinfo_api.c:550 src/peerinfo/peerinfo_api.c:569 +#: src/peerinfo/peerinfo_api.c:584 src/peerinfo/peerinfo_api.c:595 +#: src/peerinfo/peerinfo_api.c:606 #, fuzzy msgid "Received invalid message from `PEERINFO' service." msgstr "" "\n" "Không nhận được đáp ứng từ gnunetd.\n" -#: src/peerinfo/peerinfo_api.c:663 +#: src/peerinfo/peerinfo_api.c:681 #, fuzzy msgid "Timeout transmitting iteration request to `PEERINFO' service." msgstr "Lỗi sơ khởi dịch vụ « %s ».\n" @@ -3963,92 +4279,52 @@ msgstr "Lỗi sơ khởi dịch vụ « %s ».\n" msgid "Could not connect to `%s' service.\n" msgstr "Không thể kết nối tới %s:%u: %s\n" -#: src/peerinfo-tool/gnunet-peerinfo.c:581 -#, fuzzy -msgid "Failed to parse HELLO message: missing expiration time\n" -msgstr "Lỗi lưu cấu hình." - -#: src/peerinfo-tool/gnunet-peerinfo.c:589 -#, fuzzy -msgid "Failed to parse HELLO message: invalid expiration time\n" -msgstr "Lỗi lưu cấu hình." - -#: src/peerinfo-tool/gnunet-peerinfo.c:598 -#, fuzzy -msgid "Failed to parse HELLO message: malformed\n" -msgstr "Lỗi đọc danh sách bạn bè từ « %s »\n" - -#: src/peerinfo-tool/gnunet-peerinfo.c:608 -#, fuzzy -msgid "Failed to parse HELLO message: missing transport plugin\n" -msgstr "Không thể nạp phần bổ sung truyền tải « %s »\n" - -#: src/peerinfo-tool/gnunet-peerinfo.c:625 -#, c-format -msgid "Plugin `%s' not found\n" -msgstr "" - -#: src/peerinfo-tool/gnunet-peerinfo.c:634 -#, c-format -msgid "Plugin `%s' does not support URIs yet\n" -msgstr "" - -#: src/peerinfo-tool/gnunet-peerinfo.c:653 -#, fuzzy, c-format -msgid "Failed to parse `%s' as an address for plugin `%s'\n" -msgstr "Lỗi đóng kết đến cổng %s %d.\n" - -#: src/peerinfo-tool/gnunet-peerinfo.c:685 +#: src/peerinfo-tool/gnunet-peerinfo.c:419 #, c-format msgid "Failure adding HELLO: %s\n" msgstr "" -#: src/peerinfo-tool/gnunet-peerinfo.c:833 +#: src/peerinfo-tool/gnunet-peerinfo.c:557 #, fuzzy, c-format msgid "Could not find option `%s:%s' in configuration.\n" msgstr "Không tìm thấy phương pháp « %s%s » trong thư viện « %s ».\n" -#: src/peerinfo-tool/gnunet-peerinfo.c:840 +#: src/peerinfo-tool/gnunet-peerinfo.c:563 #, c-format msgid "Loading hostkey from `%s' failed.\n" msgstr "" -#: src/peerinfo-tool/gnunet-peerinfo.c:875 -#, fuzzy, c-format -msgid "Invalid URI `%s'\n" -msgstr "Dữ liệu nhập không hợp lệ.\n" - -#: src/peerinfo-tool/gnunet-peerinfo.c:899 +#: src/peerinfo-tool/gnunet-peerinfo.c:622 #, c-format msgid "I am peer `%s'.\n" msgstr "Tôi là đồng đẳng « %s ».\n" -#: src/peerinfo-tool/gnunet-peerinfo.c:936 +#: src/peerinfo-tool/gnunet-peerinfo.c:648 msgid "don't resolve host names" msgstr "không quyết định các tên máy" -#: src/peerinfo-tool/gnunet-peerinfo.c:939 +#: src/peerinfo-tool/gnunet-peerinfo.c:651 msgid "output only the identity strings" msgstr "chỉ xuất những chuỗi nhận diện" -#: src/peerinfo-tool/gnunet-peerinfo.c:942 +#: src/peerinfo-tool/gnunet-peerinfo.c:654 msgid "output our own identity only" msgstr "chỉ xuất nhận diện mình" -#: src/peerinfo-tool/gnunet-peerinfo.c:945 +#: src/peerinfo-tool/gnunet-peerinfo.c:657 #, fuzzy msgid "list all known peers" msgstr "liệt kê mọi bộ tiếp hợp mạng" -#: src/peerinfo-tool/gnunet-peerinfo.c:948 +#: src/peerinfo-tool/gnunet-peerinfo.c:660 msgid "also output HELLO uri(s)" msgstr "" -#: src/peerinfo-tool/gnunet-peerinfo.c:951 +#: src/peerinfo-tool/gnunet-peerinfo.c:663 msgid "add given HELLO uri to the database" msgstr "" -#: src/peerinfo-tool/gnunet-peerinfo.c:957 +#: src/peerinfo-tool/gnunet-peerinfo.c:674 #, fuzzy msgid "Print information about peers." msgstr "In ra thông tin về các đồng đẳng GNUnet." @@ -4143,470 +4419,557 @@ msgstr "" msgid "Failed to connect to %s service. Exiting.\n" msgstr "Lỗi sơ khởi dịch vụ « %s ».\n" -#: src/pt/gnunet-daemon-pt.c:973 +#: src/pt/gnunet-daemon-pt.c:976 msgid "Daemon to run to perform IP protocol translation to GNUnet" msgstr "" -#: src/statistics/gnunet-service-statistics.c:271 +#: src/regex/gnunet-daemon-regexprofiler.c:293 #, fuzzy, c-format -msgid "Loading %llu bytes of statistics from `%s'\n" -msgstr "Đã tải %llu byte xuống « %s ».\n" +msgid "Regexprofiler could not access hostkey: %s. Exiting.\n" +msgstr "Không thể truy cập đến thông tin về không gian tên.\n" -#: src/statistics/gnunet-service-statistics.c:330 -#, fuzzy, c-format -msgid "Wrote %llu bytes of statistics to `%s'\n" -msgstr "Đã tải %llu byte xuống « %s ».\n" +#: src/regex/gnunet-daemon-regexprofiler.c:452 +msgid "Daemon to announce regular expressions for the peer using mesh." +msgstr "" -#: src/statistics/gnunet-statistics.c:122 -#, fuzzy -msgid "Failed to obtain statistics.\n" -msgstr "Lỗi lấy thông kê về truyền tải.\n" +#: src/regex/gnunet-regex-profiler.c:1147 +msgid "An operation has failed while starting peers\n" +msgstr "" -#: src/statistics/gnunet-statistics.c:199 +#: src/regex/gnunet-regex-profiler.c:1193 #, fuzzy, c-format -msgid "No subsystem or name given\n" -msgstr "chưa đưa ra tên" +msgid "Creating a peer failed. Error: %s\n" +msgstr "Gặp lỗi khi tải lên tập tin: %s\n" -#: src/statistics/gnunet-statistics.c:207 +#: src/regex/gnunet-regex-profiler.c:1320 +msgid "An operation has failed while starting slaves\n" +msgstr "" + +#: src/regex/gnunet-regex-profiler.c:1342 #, fuzzy, c-format -msgid "Failed to initialize watch routine\n" -msgstr "Lỗi sơ khởi dịch vụ « %s ».\n" +msgid "No files found in `%s'\n" +msgstr "Vẫn còn không tìm thấy đồng đẳng trong « %s ».\n" -#: src/statistics/gnunet-statistics.c:227 -msgid "limit output to statistics for the given NAME" +#: src/regex/gnunet-regex-profiler.c:1397 +msgid "An operation has failed while linking\n" msgstr "" -#: src/statistics/gnunet-statistics.c:230 -msgid "make the value being set persistent" +#: src/regex/gnunet-regex-profiler.c:1508 +#: src/testbed/testbed_api_testbed.c:805 +#, c-format +msgid "Host registration failed for a host. Error: %s\n" msgstr "" -#: src/statistics/gnunet-statistics.c:233 -msgid "limit output to the given SUBSYSTEM" +#: src/regex/gnunet-regex-profiler.c:1589 +msgid "Unable to connect to master controller -- Check config\n" msgstr "" -#: src/statistics/gnunet-statistics.c:236 -msgid "just print the statistics value" +#: src/regex/gnunet-regex-profiler.c:1691 +#: src/testbed/testbed_api_testbed.c:970 +#, c-format +msgid "Host %s cannot start testbed\n" msgstr "" -#: src/statistics/gnunet-statistics.c:239 -msgid "watch value continously" +#: src/regex/gnunet-regex-profiler.c:1694 +#: src/testbed/testbed_api_testbed.c:974 +msgid "Testbed cannot be started on localhost\n" msgstr "" -#: src/statistics/gnunet-statistics.c:246 -msgid "Print statistics about GNUnet operations." -msgstr "In ra thống kê về các thao tác GNUnet." - -#: src/statistics/statistics_api.c:456 -#, fuzzy -msgid "Could not save some persistent statistics\n" -msgstr "Không thể tạo miền tên.\n" +#: src/regex/gnunet-regex-profiler.c:1734 +#, c-format +msgid "No hosts-file specified on command line. Exiting.\n" +msgstr "" -#: src/statistics/statistics_api.c:999 -msgid "" -"Failed to receive acknowledgement from statistics service, some statistics " -"might have been lost!\n" +#: src/regex/gnunet-regex-profiler.c:1739 +#: src/regex/gnunet-regex-simulation-profiler.c:622 +#, c-format +msgid "No policy directory specified on command line. Exiting.\n" msgstr "" -#: src/testing/gnunet-testing.c:157 -#, fuzzy -msgid "Could not read hostkeys file, specify hostkey file with -H!\n" -msgstr "Không thể đọc danh sách bạn bè « %s »\n" +#: src/regex/gnunet-regex-profiler.c:1745 +#: src/testbed/testbed_api_testbed.c:1065 +#, c-format +msgid "No hosts loaded. Need at least one host\n" +msgstr "" -#: src/testing/gnunet-testing.c:159 +#: src/regex/gnunet-regex-profiler.c:1748 #, c-format -msgid "Specified hostkey file `%s' not found!\n" +msgid "Checking whether given hosts can start testbed. Please wait\n" msgstr "" -#: src/testing/gnunet-testing.c:273 -#, fuzzy -msgid "create unique configuration files" -msgstr "cập nhật một giá trị trong tập tin cấu hình" +#: src/regex/gnunet-regex-profiler.c:1769 +#, fuzzy, c-format +msgid "Exiting\n" +msgstr "Thoát" + +#: src/regex/gnunet-regex-profiler.c:1775 +#, fuzzy, c-format +msgid "No configuration file given. Exiting\n" +msgstr "dùng tập tin cấu hình TÊN_TẬP_TIN" -#: src/testing/gnunet-testing.c:275 -msgid "create hostkey files from pre-computed hostkey list" +#: src/regex/gnunet-regex-profiler.c:1784 +#, fuzzy, c-format +msgid "Configuration option (regex_prefix) missing. Exiting\n" +msgstr "Giá trị cấu hình « %s » cho « %s » trong phần « %s » nên là con số\n" + +#: src/regex/gnunet-regex-profiler.c:1802 +#: src/regex/gnunet-regex-simulation-profiler.c:629 +#, c-format +msgid "Specified policies directory does not exist. Exiting.\n" msgstr "" -#: src/testing/gnunet-testing.c:277 -msgid "host key file" +#: src/regex/gnunet-regex-profiler.c:1809 +#, c-format +msgid "No search strings file given. Exiting.\n" msgstr "" -#: src/testing/gnunet-testing.c:279 -#, fuzzy -msgid "number of unique configuration files or hostkeys to create" -msgstr "in ra đầu ra tiêu chuẩn một giá trị từ tập tin cấu hình" +#: src/regex/gnunet-regex-profiler.c:1817 +#, c-format +msgid "" +"Error loading search strings. Given file does not contain enough strings. " +"Exiting.\n" +msgstr "" -#: src/testing/gnunet-testing.c:281 +#: src/regex/gnunet-regex-profiler.c:1823 +#, fuzzy, c-format +msgid "Error loading search strings. Exiting.\n" +msgstr "Gặp lỗi khi tải xuống: %s\n" + +#: src/regex/gnunet-regex-profiler.c:1850 #, fuzzy -msgid "configuration template" -msgstr "Cấu hình đã được lưu." +msgid "name of the file for writing statistics" +msgstr "Lỗi lấy thông kê về truyền tải.\n" -#: src/testing/gnunet-testing.c:287 -msgid "Command line tool to access the testing library" +#: src/regex/gnunet-regex-profiler.c:1853 +msgid "create COUNT number of random links between peers" msgstr "" -#: src/testing/helper.c:56 -#, fuzzy -msgid "Peer is lacking HOSTKEY configuration setting.\n" -msgstr "Lưu cấu hình ngay bây giờ không?" +#: src/regex/gnunet-regex-profiler.c:1856 +msgid "wait TIMEOUT before considering a string match as failed" +msgstr "" -#: src/testing/helper.c:64 -#, fuzzy -msgid "Could not access hostkey.\n" -msgstr "Không thể truy cập đến tập tin gnunet-directory « %s »\n" +#: src/regex/gnunet-regex-profiler.c:1859 +msgid "wait DELAY before starting string search" +msgstr "" -#: src/testing/testing.c:200 -msgid "`scp' does not seem to terminate (timeout copying config).\n" +#: src/regex/gnunet-regex-profiler.c:1862 +msgid "number of search strings to read from search strings file" msgstr "" -#: src/testing/testing.c:214 src/testing/testing.c:798 -#, fuzzy -msgid "`scp' did not complete cleanly.\n" -msgstr "« %s » không phải được kết nối tới đồng đẳng nào.\n" +#: src/regex/gnunet-regex-profiler.c:1865 +#: src/regex/gnunet-regex-simulation-profiler.c:692 +msgid "maximum path compression length" +msgstr "" -#: src/testing/testing.c:237 -#, fuzzy -msgid "Failed to create pipe for `gnunet-peerinfo' process.\n" -msgstr "Lỗi bắt đầu thu thập.\n" +#: src/regex/gnunet-regex-profiler.c:1868 +msgid "" +"if this option is set, only one peer is responsible for searching all strings" +msgstr "" -#: src/testing/testing.c:238 -#, fuzzy -msgid "Failed to create pipe for `ssh' process.\n" -msgstr "Lỗi tạo thư mục tạm thời." +#: src/regex/gnunet-regex-profiler.c:1881 +msgid "Profiler for regex" +msgstr "" -#: src/testing/testing.c:286 -#, fuzzy, c-format -msgid "Could not start `%s' process to create hostkey.\n" -msgstr "Lỗi bắt đầu thu thập.\n" +#: src/regex/gnunet-regex-simulation-profiler.c:689 +msgid "name of the table to write DFAs" +msgstr "" -#: src/testing/testing.c:293 -#, fuzzy -msgid "Failed to start `gnunet-peerinfo' process.\n" -msgstr "Lỗi bắt đầu thu thập.\n" +#: src/regex/gnunet-regex-simulation-profiler.c:705 +msgid "Profiler for regex library" +msgstr "" -#: src/testing/testing.c:294 src/testing/testing.c:471 -#, fuzzy -msgid "Failed to start `ssh' process.\n" -msgstr "Lỗi bắt đầu thu thập.\n" +#: src/statistics/gnunet-service-statistics.c:271 +#, fuzzy, c-format +msgid "Loading %llu bytes of statistics from `%s'\n" +msgstr "Đã tải %llu byte xuống « %s ».\n" -#: src/testing/testing.c:354 +#: src/statistics/gnunet-service-statistics.c:330 #, fuzzy, c-format -msgid "Error reading from gnunet-peerinfo: %s\n" -msgstr "Gặp lỗi khi đọc thông tin từ gnunetd.\n" +msgid "Wrote %llu bytes of statistics to `%s'\n" +msgstr "Đã tải %llu byte xuống « %s ».\n" -#: src/testing/testing.c:358 +#: src/statistics/gnunet-statistics.c:141 #, fuzzy -msgid "Malformed output from gnunet-peerinfo!\n" -msgstr "Gặp lỗi khi đọc thông tin từ gnunetd.\n" +msgid "Failed to obtain statistics.\n" +msgstr "Lỗi lấy thông kê về truyền tải.\n" -#: src/testing/testing.c:368 -#, fuzzy -msgid "Failed to get hostkey!\n" +#: src/statistics/gnunet-statistics.c:143 +#, fuzzy, c-format +msgid "Failed to obtain statistics from host `%s:%llu'\n" msgstr "Lỗi lấy thông kê về truyền tải.\n" -#: src/testing/testing.c:400 -msgid "`Failed while waiting for topology setup!\n" +#: src/statistics/gnunet-statistics.c:181 +#, fuzzy, c-format +msgid "Trying to connect to remote host, but service `%s' is not running\n" +msgstr "Lỗi sơ khởi dịch vụ « %s ».\n" + +#: src/statistics/gnunet-statistics.c:190 +#, fuzzy, c-format +msgid "A port is required to connect to host `%s'\n" +msgstr "Không thể kết nối tới %s:%u: %s\n" + +#: src/statistics/gnunet-statistics.c:196 +#, c-format +msgid "A port has to be between 1 and 65535 to connect to host `%s'\n" msgstr "" -#: src/testing/testing.c:463 +#: src/statistics/gnunet-statistics.c:210 +msgid "Missing argument: subsystem \n" +msgstr "" + +#: src/statistics/gnunet-statistics.c:216 +msgid "Missing argument: name\n" +msgstr "" + +#: src/statistics/gnunet-statistics.c:247 #, fuzzy, c-format -msgid "Could not start `%s' process to start GNUnet.\n" -msgstr "Không thể tạo miền tên.\n" +msgid "No subsystem or name given\n" +msgstr "chưa đưa ra tên" -#: src/testing/testing.c:470 -#, fuzzy -msgid "Failed to start `gnunet-arm' process.\n" -msgstr "Lỗi dừng chạy gnunet-auto-share.\n" +#: src/statistics/gnunet-statistics.c:255 +#, fuzzy, c-format +msgid "Failed to initialize watch routine\n" +msgstr "Lỗi sơ khởi dịch vụ « %s ».\n" + +#: src/statistics/gnunet-statistics.c:310 +msgid "limit output to statistics for the given NAME" +msgstr "" + +#: src/statistics/gnunet-statistics.c:313 +msgid "make the value being set persistent" +msgstr "" -#: src/testing/testing.c:493 src/testing/testing.c:600 -msgid "`gnunet-arm' does not seem to terminate.\n" +#: src/statistics/gnunet-statistics.c:316 +msgid "limit output to the given SUBSYSTEM" msgstr "" -#: src/testing/testing.c:494 src/testing/testing.c:601 -#: src/testing/testing.c:621 -msgid "`ssh' does not seem to terminate.\n" +#: src/statistics/gnunet-statistics.c:319 +msgid "just print the statistics value" msgstr "" -#: src/testing/testing.c:570 -msgid "Unable to get HELLO for peer!\n" +#: src/statistics/gnunet-statistics.c:322 +msgid "watch value continuously" msgstr "" -#: src/testing/testing.c:620 -msgid "`gnunet-arm' terminated with non-zero exit status (or timed out)!\n" +#: src/statistics/gnunet-statistics.c:325 +msgid "connect to remote host" msgstr "" -#: src/testing/testing.c:643 src/testing/testing.c:675 -msgid "either `gnunet-arm' or `ssh' does not seem to terminate.\n" +#: src/statistics/gnunet-statistics.c:328 +msgid "port for remote host" msgstr "" -#: src/testing/testing.c:658 src/testing/testing.c:713 +#: src/statistics/gnunet-statistics.c:340 +msgid "Print statistics about GNUnet operations." +msgstr "In ra thống kê về các thao tác GNUnet." + +#: src/statistics/statistics_api.c:511 #, fuzzy -msgid "shutdown (either `gnunet-arm' or `ssh') did not complete cleanly.\n" -msgstr "« %s » không phải được kết nối tới đồng đẳng nào.\n" +msgid "Could not save some persistent statistics\n" +msgstr "Không thể tạo miền tên.\n" + +#: src/statistics/statistics_api.c:1056 +msgid "" +"Failed to receive acknowledgement from statistics service, some statistics " +"might have been lost!\n" +msgstr "" + +#: src/sysmon/gnunet-service-sysmon.c:546 +#, c-format +msgid "Could not parse execution interval for `%s', set to default 60 sec.\n" +msgstr "" + +#: src/testbed/gnunet-testbed-profiler.c:231 +#, c-format +msgid "No hosts-file specified on command line\n" +msgstr "" + +#: src/testbed/gnunet-testbed-profiler.c:261 +msgid "create COUNT number of peers" +msgstr "" -#: src/testing/testing.c:786 -msgid "`scp' does not seem to terminate.\n" +#: src/testbed/gnunet-testbed-profiler.c:264 +msgid "tolerate COUNT number of continious timeout failures" msgstr "" -#: src/testing/testing.c:948 +#: src/testbed/gnunet-testbed-profiler.c:276 +msgid "Profiler for testbed" +msgstr "" + +#: src/testbed/ll_master.c:57 #, fuzzy, c-format -msgid "Starting service %s for peer `%4s'\n" -msgstr "Đang bắt đầu tài về « %s »\n" +msgid "Job command file not given. Exiting\n" +msgstr "dùng tập tin cấu hình TÊN_TẬP_TIN" -#: src/testing/testing.c:1207 src/testing/testing_group.c:6154 +#: src/testbed/testbed_api.c:499 #, fuzzy, c-format -msgid "Could not start `%s' process to copy configuration directory.\n" -msgstr "Không thể truy cập đến thông tin về không gian tên.\n" +msgid "Adding host %u failed with error: %s\n" +msgstr "« %s » thất bại với mã lỗi %d: %s\n" -#: src/testing/testing.c:1292 src/testing/testing.c:1359 +#: src/testbed/testbed_api_hosts.c:306 #, fuzzy, c-format -msgid "Terminating peer `%4s'\n" -msgstr "Không đủ quyền cho « %s ».\n" +msgid "Hosts file %s not found\n" +msgstr "Khoá phiên chạy từ đồng đẳng « %s » không thể được thẩm tra.\n" -#: src/testing/testing.c:1448 +#: src/testbed/testbed_api_hosts.c:314 #, fuzzy, c-format -msgid "Setting d->dead on peer `%4s'\n" -msgstr "Đang bắt đầu tài lên « %s ».\n" +msgid "Hosts file %s has no data\n" +msgstr "Khoá phiên chạy từ đồng đẳng « %s » không thể được thẩm tra.\n" + +#: src/testbed/testbed_api_hosts.c:321 +#, fuzzy, c-format +msgid "Hosts file %s cannot be read\n" +msgstr "Khoá phiên chạy từ đồng đẳng « %s » không thể được thẩm tra.\n" -#: src/testing/testing.c:1601 -msgid "Peer not yet running, can not change configuration at this point." +#: src/testbed/testbed_api_testbed.c:623 +msgid "Linking controllers failed. Exiting" msgstr "" -#: src/testing/testing.c:1609 -#, fuzzy -msgid "Failed to write new configuration to disk." -msgstr "Lỗi lưu cấu hình." +#: src/testbed/testbed_api_testbed.c:1009 +msgid "Cannot start the master controller" +msgstr "" -#: src/testing/testing.c:1636 +#: src/testbed/testbed_api_testbed.c:1089 +msgid "Specified topology must be supported by testbed" +msgstr "" + +#: src/testbed/testbed_api_topology.c:668 #, fuzzy, c-format -msgid "Could not start `%s' process to copy configuration file.\n" -msgstr "Không tìm thấy phương pháp « %s%s » trong thư viện « %s ».\n" +msgid "Topology file %s not found\n" +msgstr "Khoá phiên chạy từ đồng đẳng « %s » không thể được thẩm tra.\n" -#: src/testing/testing.c:1639 -#, fuzzy -msgid "Failed to copy new configuration to remote machine." -msgstr "Lỗi lưu cấu hình." +#: src/testbed/testbed_api_topology.c:674 +#, fuzzy, c-format +msgid "Topology file %s has no data\n" +msgstr "Khoá phiên chạy từ đồng đẳng « %s » không thể được thẩm tra.\n" -#: src/testing/testing.c:1794 -#, fuzzy -msgid "Peers failed to connect" -msgstr "Không kết nối được đến trình nền gnunetd." +#: src/testbed/testbed_api_topology.c:681 +#, fuzzy, c-format +msgid "Topology file %s cannot be read\n" +msgstr "Khoá phiên chạy từ đồng đẳng « %s » không thể được thẩm tra.\n" -#: src/testing/testing.c:1922 -#, fuzzy -msgid "Failed to connect to core service of first peer!\n" -msgstr "Lỗi nạp dịch vụ sqstore. Hãy kiểm tra lại cấu hình.\n" +#: src/testbed/testbed_api_topology.c:704 +#, fuzzy, c-format +msgid "Failed to read peer index from toology file: %s" +msgstr "Không thể truy cập đến tập tin gnunet-directory « %s »\n" -#: src/testing/testing.c:2145 -msgid "Peers are not fully running yet, can not connect!\n" +#: src/testbed/testbed_api_topology.c:713 +#: src/testbed/testbed_api_topology.c:737 +#, c-format +msgid "Value in given topology file: %s out of range\n" msgstr "" -#: src/testing/testing_group.c:1895 src/testing/testing_group.c:1907 -#: src/testing/testing_group.c:2008 src/testing/testing_group.c:2065 -#: src/testing/testing_group.c:2152 src/testing/testing_group.c:2172 -#: src/testing/testing_group.c:2302 src/testing/testing_peergroup.c:950 +#: src/testbed/testbed_api_topology.c:719 +#: src/testbed/testbed_api_topology.c:743 #, fuzzy, c-format -msgid "Invalid value `%s' for option `%s' in section `%s': expected float\n" -msgstr "Giá trị cấu hình « %s » cho « %s » trong phần « %s » nên là con số\n" +msgid "Failed to read peer index from topology file: %s" +msgstr "Không thể truy cập đến tập tin gnunet-directory « %s »\n" -#: src/testing/testing_group.c:2160 +#: src/testbed/testbed_api_topology.c:725 +#: src/testbed/testbed_api_topology.c:749 +msgid "Topology file needs more peers than given ones\n" +msgstr "" + +#: src/testbed/testbed_api_topology.c:764 #, fuzzy, c-format -msgid "" -"Invalid value `%s' for option `%s' in section `%s': got %f, needed value " -"greater than 0\n" -msgstr "Giá trị cấu hình « %s » cho « %s » trong phần « %s » nên là con số\n" +msgid "Ignoring to connect peer %u to peer %u\n" +msgstr "đang kết nối đồng đẳng %s:%d tới đồng đẳng %s:%d\n" -#: src/testing/testing_group.c:2877 src/testing/testing_group.c:3063 +#: src/testing/gnunet-testing.c:132 #, fuzzy, c-format -msgid "" -"No `%s' specified in peer configuration in section `%s', cannot copy friends " -"file!\n" -msgstr "" -"Đặc tả mạng dạng sai trong cấu hình phần « %s » cho mục nhập « %s »: %s\n" +msgid "Could not extract hostkey %u (offset too large?)\n" +msgstr "Không thể đọc danh sách bạn bè « %s »\n" + +#: src/testing/gnunet-testing.c:203 +#, fuzzy +msgid "create unique configuration files" +msgstr "cập nhật một giá trị trong tập tin cấu hình" -#: src/testing/testing_group.c:3957 -msgid "Creating no allowed topology (all peers can connect at core level)\n" +#: src/testing/gnunet-testing.c:205 +msgid "extract hostkey file from pre-computed hostkey list" msgstr "" -#: src/testing/testing_group.c:5226 +#: src/testing/gnunet-testing.c:207 #, fuzzy -msgid "Unknown topology specification, can't connect peers!\n" -msgstr "Lỗi cú pháp trong sự xác định địa hình học, đang bỏ qua các byte.\n" +msgid "" +"number of unique configuration files to create, or number of the hostkey to " +"extract" +msgstr "in ra đầu ra tiêu chuẩn một giá trị từ tập tin cấu hình" -#: src/testing/testing_group.c:5944 src/transport/transport-testing.c:636 +#: src/testing/gnunet-testing.c:209 #, fuzzy -msgid "Could not read hostkeys file!\n" -msgstr "Không thể đọc danh sách bạn bè « %s »\n" +msgid "configuration template" +msgstr "Cấu hình đã được lưu." -#: src/testing/testing_group.c:6011 -#, fuzzy, c-format -msgid "Could not create configuration for peer number %u on `%s'!\n" -msgstr "Không thể truy cập đến thông tin về không gian tên.\n" +#: src/testing/gnunet-testing.c:218 +msgid "Command line tool to access the testing library" +msgstr "" + +#: src/testing/gnunet-testing-run-service.c:129 +#, c-format +msgid "Unknown command, use 'q' to quit or 'r' to restart peer\n" +msgstr "" + +#: src/testing/gnunet-testing-run-service.c:186 +#, fuzzy +msgid "name of the template configuration file to use (optional)" +msgstr "Tập tin cấu hình gnunetd có đường dẫn nào?" -#: src/testing/testing_new.c:169 -msgid "tmppath cannot be NULL\n" +#: src/testing/gnunet-testing-run-service.c:189 +msgid "name of the service to run" msgstr "" -#: src/testing/testing_new.c:356 +#: src/testing/testing.c:211 #, c-format msgid "Hostkeys file not found: %s\n" msgstr "" -#: src/testing/testing_new.c:365 -#, fuzzy, c-format -msgid "Could not open hostkeys file: %s\n" -msgstr "Không thể đọc danh sách bạn bè « %s »\n" - -#: src/testing/testing_new.c:380 +#: src/testing/testing.c:227 #, c-format msgid "Incorrect hostkey file format: %s\n" msgstr "" -#: src/testing/testing_new.c:437 +#: src/testing/testing.c:541 #, fuzzy, c-format msgid "Key number %u does not exist\n" msgstr "đặt số trình nền cần khởi chạy" -#: src/testing/testing_new.c:446 +#: src/testing/testing.c:551 #, fuzzy, c-format msgid "Error while decoding key %u\n" msgstr "Gặp lỗi khi tải xuống: %s\n" -#: src/testing/testing_new.c:680 +#: src/testing/testing.c:865 #, fuzzy msgid "Failed to create configuration for peer (not enough free ports?)\n" msgstr "Không thể truy cập đến thông tin về không gian tên.\n" -#: src/testing/testing_new.c:691 +#: src/testing/testing.c:876 #, c-format msgid "" "You attempted to create a testbed with more than %u hosts. Please " "precompute more hostkeys first.\n" msgstr "" -#: src/testing/testing_new.c:704 +#: src/testing/testing.c:890 #, fuzzy, c-format msgid "Failed to initialize hostkey for peer %u\n" msgstr "Lỗi sơ khởi dịch vụ « %s ».\n" -#: src/testing/testing_new.c:734 +#: src/testing/testing.c:923 #, fuzzy, c-format msgid "Failed to write hostkey file for peer %u: %s\n" msgstr "Lỗi tạo thư mục tạm thời." -#: src/testing/testing_new.c:751 +#: src/testing/testing.c:941 #, fuzzy, c-format msgid "Failed to write configuration file `%s' for peer %u: %s\n" msgstr "Không thể lưu tập tin cấu hình « %s »:" -#: src/testing/testing_new.c:791 +#: src/testing/testing.c:1014 #, fuzzy, c-format msgid "Failed to start `%s': %s\n" msgstr "Lỗi chạy %s: %s %d\n" -#: src/testing/testing_new.c:959 +#: src/testing/testing.c:1219 #, fuzzy, c-format msgid "Failed to load configuration from %s\n" msgstr "Không thể lưu tập tin cấu hình « %s »:" -#: src/topology/gnunet-daemon-topology.c:259 +#: src/topology/gnunet-daemon-topology.c:254 msgid "# peers blacklisted" msgstr "" -#: src/topology/gnunet-daemon-topology.c:392 +#: src/topology/gnunet-daemon-topology.c:387 #, fuzzy msgid "# connect requests issued to transport" msgstr "# các yêu cầu máy/trình khách lỗ hổng được phun vào" -#: src/topology/gnunet-daemon-topology.c:730 -#: src/topology/gnunet-daemon-topology.c:815 +#: src/topology/gnunet-daemon-topology.c:725 +#: src/topology/gnunet-daemon-topology.c:810 #, fuzzy msgid "# friends connected" msgstr "# của các đồng đẳng đã kết nối" -#: src/topology/gnunet-daemon-topology.c:996 +#: src/topology/gnunet-daemon-topology.c:991 msgid "Failed to connect to core service, can not manage topology!\n" msgstr "" -#: src/topology/gnunet-daemon-topology.c:1026 -#, fuzzy, c-format -msgid "Option `%s' in section `%s' not specified!\n" -msgstr "Bị từ chối đặt tùy chọn « %s » trong phần « %s » thành « %s ».\n" - -#: src/topology/gnunet-daemon-topology.c:1039 +#: src/topology/gnunet-daemon-topology.c:1034 #, c-format msgid "Could not read friends list `%s'\n" msgstr "Không thể đọc danh sách bạn bè « %s »\n" -#: src/topology/gnunet-daemon-topology.c:1045 +#: src/topology/gnunet-daemon-topology.c:1040 #, fuzzy, c-format msgid "Friends file `%s' is empty.\n" msgstr "Định dạng của tập tin « %s » là không hợp lệ.\n" -#: src/topology/gnunet-daemon-topology.c:1054 +#: src/topology/gnunet-daemon-topology.c:1049 #, fuzzy, c-format msgid "Failed to read friends list from `%s': out of memory\n" msgstr "Lỗi đọc danh sách bạn bè từ « %s »\n" -#: src/topology/gnunet-daemon-topology.c:1062 +#: src/topology/gnunet-daemon-topology.c:1057 #, c-format msgid "Failed to read friends list from `%s'\n" msgstr "Lỗi đọc danh sách bạn bè từ « %s »\n" -#: src/topology/gnunet-daemon-topology.c:1082 +#: src/topology/gnunet-daemon-topology.c:1077 #, fuzzy, c-format msgid "" "Syntax error in topology specification at offset %llu, skipping bytes.\n" msgstr "Lỗi cú pháp trong sự xác định địa hình học, đang bỏ qua các byte.\n" -#: src/topology/gnunet-daemon-topology.c:1095 +#: src/topology/gnunet-daemon-topology.c:1090 #, fuzzy, c-format msgid "" "Syntax error in topology specification at offset %llu, skipping bytes `%s'.\n" msgstr "" "Lỗi cú pháp trong sự xác định địa hình học, đang bỏ qua các byte « %s ».\n" -#: src/topology/gnunet-daemon-topology.c:1105 +#: src/topology/gnunet-daemon-topology.c:1100 #, fuzzy, c-format msgid "Found friend `%s' in configuration\n" msgstr "" "\n" "Kết thúc cấu hình.\n" -#: src/topology/gnunet-daemon-topology.c:1111 +#: src/topology/gnunet-daemon-topology.c:1106 #, c-format msgid "Found myself `%s' in friend list (useless, ignored)\n" msgstr "" -#: src/topology/gnunet-daemon-topology.c:1121 +#: src/topology/gnunet-daemon-topology.c:1116 #, fuzzy msgid "# friends in configuration" msgstr "" "\n" "Kết thúc cấu hình.\n" -#: src/topology/gnunet-daemon-topology.c:1127 +#: src/topology/gnunet-daemon-topology.c:1122 msgid "" "Fewer friends specified than required by minimum friend count. Will only " "connect to friends.\n" msgstr "" "Xác định quá ít bạn bè (dưới số tối thiểu). Sẽ chỉ kết nối tới bạn bè.\n" -#: src/topology/gnunet-daemon-topology.c:1134 +#: src/topology/gnunet-daemon-topology.c:1129 msgid "" "More friendly connections required than target total number of connections.\n" msgstr "Cần thiết nhiều kết nối bạn bè hơn tổng số kết nối đích.\n" -#: src/topology/gnunet-daemon-topology.c:1169 +#: src/topology/gnunet-daemon-topology.c:1164 #, fuzzy msgid "# HELLO messages received" msgstr "# các thông báo PONG đã mật mã được nhận" -#: src/topology/gnunet-daemon-topology.c:1224 +#: src/topology/gnunet-daemon-topology.c:1219 #, fuzzy msgid "# HELLO messages gossipped" msgstr "# các thông báo gửi đi bị loại bỏ" -#: src/topology/gnunet-daemon-topology.c:1363 +#: src/topology/gnunet-daemon-topology.c:1358 msgid "GNUnet topology control (maintaining P2P mesh and F2F constraints)" msgstr "" @@ -4615,11 +4978,6 @@ msgstr "" msgid "Could not read blacklist file `%s'\n" msgstr "Không thể đọc danh sách bạn bè « %s »\n" -#: src/transport/gnunet-service-transport_blacklist.c:252 -#, c-format -msgid "Blacklist file `%s' is empty.\n" -msgstr "" - #: src/transport/gnunet-service-transport_blacklist.c:263 #, fuzzy, c-format msgid "Failed to read blacklist from `%s'\n" @@ -4649,172 +5007,178 @@ msgid "Found myself `%s' in blacklist (useless, ignored)\n" msgstr "" #: src/transport/gnunet-service-transport_blacklist.c:514 -#: src/transport/gnunet-service-transport_blacklist.c:747 +#: src/transport/gnunet-service-transport_blacklist.c:752 msgid "# disconnects due to blacklist" msgstr "" -#: src/transport/gnunet-service-transport.c:163 +#: src/transport/gnunet-service-transport.c:183 #, fuzzy msgid "# bytes payload discarded due to not connected peer " msgstr "# Các quảng cáo đồng đẳng bị hủy do trọng tải" -#: src/transport/gnunet-service-transport.c:237 +#: src/transport/gnunet-service-transport.c:258 #, fuzzy msgid "# bytes total received" msgstr "# tổng số nội dung lỗ hổng được nhận" -#: src/transport/gnunet-service-transport.c:284 +#: src/transport/gnunet-service-transport.c:305 #, fuzzy msgid "# bytes payload received" msgstr "# các byte đã giải mã" -#: src/transport/gnunet-service-transport.c:582 -msgid "Transport service is lacking key configuration settings. Exiting.\n" -msgstr "" +#: src/transport/gnunet-service-transport.c:614 +#, fuzzy, c-format +msgid "Transport service could not access hostkey: %s. Exiting.\n" +msgstr "Không thể truy cập đến thông tin về không gian tên.\n" -#: src/transport/gnunet-service-transport.c:591 -msgid "Transport service could not access hostkey. Exiting.\n" +#: src/transport/gnunet-service-transport.c:625 +#, fuzzy +msgid "Could not access STATISTICS service. Exiting.\n" +msgstr "Không thể truy cập đến thông tin về không gian tên.\n" + +#: src/transport/gnunet-service-transport.c:720 +msgid "Transport service is lacking key configuration settings. Exiting.\n" msgstr "" -#: src/transport/gnunet-service-transport_clients.c:352 +#: src/transport/gnunet-service-transport_clients.c:389 #, c-format msgid "Dropping message of type %u and size %u, have %u/%u messages pending\n" msgstr "" -#: src/transport/gnunet-service-transport_clients.c:357 +#: src/transport/gnunet-service-transport_clients.c:394 #, fuzzy msgid "# messages dropped due to slow client" msgstr "# các yêu cầu lỗ hổng bị bỏ do trọng tải" -#: src/transport/gnunet-service-transport_clients.c:503 +#: src/transport/gnunet-service-transport_clients.c:546 #, c-format msgid "Rejecting control connection from peer `%s', which is not me!\n" msgstr "" -#: src/transport/gnunet-service-transport_clients.c:631 +#: src/transport/gnunet-service-transport_clients.c:687 msgid "# bytes payload dropped (other peer was not connected)" msgstr "" -#: src/transport/gnunet-service-transport_clients.c:682 +#: src/transport/gnunet-service-transport_clients.c:738 #, fuzzy msgid "# REQUEST CONNECT messages received" msgstr "# các thông báo PONG đã mật mã được nhận" -#: src/transport/gnunet-service-transport_hello.c:172 +#: src/transport/gnunet-service-transport_hello.c:175 msgid "# refreshed my HELLO" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:1032 +#: src/transport/gnunet-service-transport_neighbours.c:1227 #, fuzzy msgid "# DISCONNECT messages sent" msgstr "# các thông báo PONG đã mật mã được nhận" -#: src/transport/gnunet-service-transport_neighbours.c:1148 -#: src/transport/gnunet-service-transport_neighbours.c:1482 +#: src/transport/gnunet-service-transport_neighbours.c:1357 +#: src/transport/gnunet-service-transport_neighbours.c:1694 #, fuzzy msgid "# bytes in message queue for other peers" msgstr "# các byte thông báo gửi đi bị loại bỏ" -#: src/transport/gnunet-service-transport_neighbours.c:1153 +#: src/transport/gnunet-service-transport_neighbours.c:1362 #, fuzzy msgid "# messages transmitted to other peers" msgstr "# các byte kiểu %d được gửi " -#: src/transport/gnunet-service-transport_neighbours.c:1158 +#: src/transport/gnunet-service-transport_neighbours.c:1367 #, fuzzy msgid "# transmission failures for messages to other peers" msgstr "# các byte thông báo gửi đi bị loại bỏ" -#: src/transport/gnunet-service-transport_neighbours.c:1215 +#: src/transport/gnunet-service-transport_neighbours.c:1424 msgid "# messages timed out while in transport queue" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:1254 +#: src/transport/gnunet-service-transport_neighbours.c:1466 #, fuzzy msgid "# keepalives sent" msgstr "# các khoá phiên chạy được gửi" -#: src/transport/gnunet-service-transport_neighbours.c:1278 +#: src/transport/gnunet-service-transport_neighbours.c:1490 #, fuzzy msgid "# KEEPALIVE messages discarded (peer unknown)" msgstr "# các thông báo được chắp liền" -#: src/transport/gnunet-service-transport_neighbours.c:1286 +#: src/transport/gnunet-service-transport_neighbours.c:1498 #, fuzzy msgid "# KEEPALIVE messages discarded (no session)" msgstr "# các thông báo được chắp liền" -#: src/transport/gnunet-service-transport_neighbours.c:1323 +#: src/transport/gnunet-service-transport_neighbours.c:1535 #, fuzzy msgid "# KEEPALIVE_RESPONSE messages discarded (not connected)" msgstr "# các thông báo được chắp liền" -#: src/transport/gnunet-service-transport_neighbours.c:1332 +#: src/transport/gnunet-service-transport_neighbours.c:1544 #, fuzzy msgid "# KEEPALIVE_RESPONSE messages discarded (not expected)" msgstr "# các thông báo được chắp liền" -#: src/transport/gnunet-service-transport_neighbours.c:1388 +#: src/transport/gnunet-service-transport_neighbours.c:1600 #, fuzzy msgid "# messages discarded due to lack of neighbour record" msgstr "# các thông báo được chắp liền" -#: src/transport/gnunet-service-transport_neighbours.c:1422 +#: src/transport/gnunet-service-transport_neighbours.c:1634 #, fuzzy msgid "# bandwidth quota violations by other peers" msgstr "theo dõi gnunetd sử dụng dải thông" -#: src/transport/gnunet-service-transport_neighbours.c:1438 +#: src/transport/gnunet-service-transport_neighbours.c:1650 msgid "# ms throttling suggested" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:2544 +#: src/transport/gnunet-service-transport_neighbours.c:2802 #, fuzzy msgid "# unexpected CONNECT_ACK messages (no peer)" msgstr "gửi ĐẾM thông báo" -#: src/transport/gnunet-service-transport_neighbours.c:2559 -#: src/transport/gnunet-service-transport_neighbours.c:2585 +#: src/transport/gnunet-service-transport_neighbours.c:2817 +#: src/transport/gnunet-service-transport_neighbours.c:2851 #, fuzzy msgid "# unexpected CONNECT_ACK messages (not ready)" msgstr "gửi ĐẾM thông báo" -#: src/transport/gnunet-service-transport_neighbours.c:2598 +#: src/transport/gnunet-service-transport_neighbours.c:2864 #, fuzzy msgid "# unexpected CONNECT_ACK messages (waiting on ATS)" msgstr "gửi ĐẾM thông báo" -#: src/transport/gnunet-service-transport_neighbours.c:2627 +#: src/transport/gnunet-service-transport_neighbours.c:2897 #, fuzzy msgid "# unexpected CONNECT_ACK messages (disconnecting)" msgstr "gửi ĐẾM thông báo" -#: src/transport/gnunet-service-transport_neighbours.c:2807 +#: src/transport/gnunet-service-transport_neighbours.c:3082 #, fuzzy msgid "# unexpected SESSION ACK messages" msgstr "# các thông báo PONG đã mật mã được gửi" -#: src/transport/gnunet-service-transport_neighbours.c:2856 +#: src/transport/gnunet-service-transport_neighbours.c:3137 msgid "# SET QUOTA messages ignored (no such peer)" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:2870 +#: src/transport/gnunet-service-transport_neighbours.c:3151 msgid "# disconnects due to quota of 0" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:2901 +#: src/transport/gnunet-service-transport_neighbours.c:3182 msgid "# disconnect messages ignored (old format)" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:2912 +#: src/transport/gnunet-service-transport_neighbours.c:3193 msgid "# disconnect messages ignored (timestamp)" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:2943 +#: src/transport/gnunet-service-transport_neighbours.c:3224 msgid "# other peer asked to disconnect from us" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:3020 +#: src/transport/gnunet-service-transport_neighbours.c:3319 #, fuzzy msgid "# disconnected from peer upon explicit request" msgstr "# các yêu cầu lỗ hổng bị bỏ do trọng tải" @@ -4823,313 +5187,497 @@ msgstr "# các yêu cầu lỗ hổng bị bỏ do trọng tải" msgid "Transport service is lacking NEIGHBOUR_LIMIT option.\n" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:414 +#: src/transport/gnunet-service-transport_validation.c:425 msgid "# address records discarded" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:463 +#: src/transport/gnunet-service-transport_validation.c:487 #, c-format msgid "" "Not transmitting `%s' with `%s', message too big (%u bytes!). This should " "not happen.\n" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:512 +#: src/transport/gnunet-service-transport_validation.c:536 #, fuzzy msgid "# PING without HELLO messages sent" msgstr "# các thông báo PONG nhập thô được gửi" -#: src/transport/gnunet-service-transport_validation.c:570 +#: src/transport/gnunet-service-transport_validation.c:618 msgid "# address revalidations started" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:805 +#: src/transport/gnunet-service-transport_validation.c:860 #, fuzzy msgid "# PING message for different peer received" msgstr "# các thông báo PING được tạo" -#: src/transport/gnunet-service-transport_validation.c:840 +#: src/transport/gnunet-service-transport_validation.c:925 #, c-format -msgid "" -"Not confirming PING with address `%s' since I cannot confirm having this " -"address.\n" +msgid "Received a PING message with validation bug from `%s'\n" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:924 +#: src/transport/gnunet-service-transport_validation.c:1054 msgid "# PONGs unicast via reliable transport" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:933 +#: src/transport/gnunet-service-transport_validation.c:1063 msgid "# PONGs multicast to all available addresses" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:1055 +#: src/transport/gnunet-service-transport_validation.c:1188 msgid "# PONGs dropped, no matching pending validation" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:1080 +#: src/transport/gnunet-service-transport_validation.c:1216 msgid "# PONGs dropped, signature expired" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:1136 +#: src/transport/gnunet-service-transport_validation.c:1270 #, fuzzy, c-format msgid "Adding `%s' without addresses for peer `%s'\n" msgstr "Không thể lấy địa chỉ của đồng đẳng « %s ».\n" -#: src/transport/gnunet-transport.c:260 -msgid "No transport plugins configured, peer will never communicate\n" -msgstr "" +#: src/transport/gnunet-transport.c:266 +#, fuzzy, c-format +msgid "Transmitted %llu bytes/s (%llu bytes in %s)\n" +msgstr "Đang thử tải danh sách các máy xuống « %s »\n" #: src/transport/gnunet-transport.c:273 -#, c-format -msgid "No port configured for plugin `%s', cannot test it\n" -msgstr "" +#, fuzzy, c-format +msgid "Received %llu bytes/s (%llu bytes in %s)\n" +msgstr "Nhận yêu cầu định tuyến\n" -#: src/transport/gnunet-transport.c:323 -#, c-format -msgid "Received %llu bytes/s (%llu bytes in %llu ms)\n" +#: src/transport/gnunet-transport.c:303 +#, fuzzy, c-format +msgid "Failed to connect to `%s'\n" +msgstr "Lỗi kết nối đến gnunetd.\n" + +#: src/transport/gnunet-transport.c:316 +#, fuzzy, c-format +msgid "Failed to resolve address for peer `%s'\n" +msgstr "Lỗi đóng kết đến cổng %s %d.\n" + +#: src/transport/gnunet-transport.c:325 +#, fuzzy +msgid "Failed to list connections, timeout occured\n" +msgstr "Không kết nối được đến trình nền gnunetd." + +#: src/transport/gnunet-transport.c:429 +msgid "No transport plugins configured, peer will never communicate\n" msgstr "" -#: src/transport/gnunet-transport.c:330 +#: src/transport/gnunet-transport.c:442 #, c-format -msgid "Transmitted %llu bytes/s (%llu bytes in %llu ms)\n" +msgid "No port configured for plugin `%s', cannot test it\n" msgstr "" -#: src/transport/gnunet-transport.c:363 +#: src/transport/gnunet-transport.c:506 #, fuzzy, c-format msgid "Transmitting %u bytes to %s\n" msgstr "Đang thử tải danh sách các máy xuống « %s »\n" -#: src/transport/gnunet-transport.c:383 -#, fuzzy, c-format -msgid "Connected to %s\n" -msgstr "« %s » được kết nối tới « %s ».\n" +#: src/transport/gnunet-transport.c:531 +#, fuzzy, c-format +msgid "Successfully connected to `%s'\n" +msgstr "Không đủ quyền cho « %s ».\n" + +#: src/transport/gnunet-transport.c:553 +#, c-format +msgid "" +"Successfully connected to `%s', starting to send benchmark data in %u Kb " +"blocks\n" +msgstr "" -#: src/transport/gnunet-transport.c:414 +#: src/transport/gnunet-transport.c:588 #, fuzzy, c-format -msgid "Disconnected from %s\n" +msgid "Disconnected from peer `%s' while benchmarking\n" msgstr "« %.*s » được kết nối tới « %.*s ».\n" -#: src/transport/gnunet-transport.c:443 +#: src/transport/gnunet-transport.c:664 #, fuzzy, c-format msgid "Received %u bytes from %s\n" msgstr "Nhận yêu cầu định tuyến\n" -#: src/transport/gnunet-transport.c:466 +#: src/transport/gnunet-transport.c:687 #, fuzzy, c-format msgid "Peer `%s': %s %s\n" msgstr "Tôi là đồng đẳng « %s ».\n" -#: src/transport/gnunet-transport.c:473 +#: src/transport/gnunet-transport.c:702 #, c-format msgid "Peer `%s': %s \n" msgstr "" -#: src/transport/gnunet-transport.c:501 +#: src/transport/gnunet-transport.c:766 #, fuzzy, c-format msgid "Peer `%s' disconnected\n" msgstr "# của các đồng đẳng đã kết nối" -#: src/transport/gnunet-transport.c:569 -#, fuzzy, c-format -msgid "Failed to parse peer identity `%s'\n" -msgstr "Lỗi đọc danh sách bạn bè từ « %s »\n" +#: src/transport/gnunet-transport.c:794 +#, fuzzy +msgid "Failed to send connect request to transport service\n" +msgstr "Lỗi kết nối đến gnunetd.\n" + +#: src/transport/gnunet-transport.c:828 +#, c-format +msgid "" +"Multiple operations given. Please choose only one operation: %s, %s, %s, %s, " +"%s, %s\n" +msgstr "" + +#: src/transport/gnunet-transport.c:834 +#, c-format +msgid "" +"No operation given. Please choose one operation: %s, %s, %s, %s, %s, %s\n" +msgstr "" + +#: src/transport/gnunet-transport.c:854 src/transport/gnunet-transport.c:884 +#: src/transport/gnunet-transport.c:906 src/transport/gnunet-transport.c:945 +#, fuzzy +msgid "Failed to connect to transport service\n" +msgstr "Lỗi kết nối đến gnunetd.\n" + +#: src/transport/gnunet-transport.c:861 src/transport/gnunet-transport.c:891 +#, fuzzy +msgid "Failed to send request to transport service\n" +msgstr "Lỗi kết nối đến gnunetd.\n" -#: src/transport/gnunet-transport.c:618 -msgid "measure how fast we are receiving data (until CTRL-C)" +#: src/transport/gnunet-transport.c:911 +msgid "Starting to receive benchmark data\n" msgstr "" -#: src/transport/gnunet-transport.c:621 +#: src/transport/gnunet-transport.c:996 +msgid "measure how fast we are receiving data from all peers (until CTRL-C)" +msgstr "" + +#: src/transport/gnunet-transport.c:999 #, fuzzy -msgid "try to connect to the given peer" +msgid "connect to a peer" msgstr "Lỗi kết nối đến gnunetd.\n" -#: src/transport/gnunet-transport.c:624 +#: src/transport/gnunet-transport.c:1002 #, fuzzy msgid "provide information about all current connections (once)" msgstr "In ra thông tin về các đồng đẳng GNUnet." -#: src/transport/gnunet-transport.c:627 +#: src/transport/gnunet-transport.c:1008 #, fuzzy -msgid "provide information about all current connections (continuously)" +msgid "" +"provide information about all connects and disconnect events (continuously)" msgstr "In ra thông tin về các đồng đẳng GNUnet." -#: src/transport/gnunet-transport.c:630 +#: src/transport/gnunet-transport.c:1011 #, fuzzy msgid "do not resolve hostnames" msgstr "không quyết định các tên máy" -#: src/transport/gnunet-transport.c:634 +#: src/transport/gnunet-transport.c:1014 +msgid "peer identity" +msgstr "" + +#: src/transport/gnunet-transport.c:1018 msgid "send data for benchmarking to the other peer (until CTRL-C)" msgstr "" -#: src/transport/gnunet-transport.c:637 +#: src/transport/gnunet-transport.c:1021 msgid "test transport configuration (involves external server)" msgstr "" -#: src/transport/gnunet-transport.c:645 +#: src/transport/gnunet-transport.c:1032 #, fuzzy msgid "Direct access to transport service." msgstr "Lỗi kết nối đến gnunetd.\n" -#: src/transport/plugin_transport_http.c:1100 +#: src/transport/plugin_transport_http.c:817 +#: src/transport/plugin_transport_http_server.c:2556 msgid "Disabling IPv6 since it is not supported on this system!\n" msgstr "" -#: src/transport/plugin_transport_http.c:1149 +#: src/transport/plugin_transport_http.c:866 +#: src/transport/plugin_transport_http_server.c:2324 #, fuzzy msgid "Require valid port number for service in configuration!\n" msgstr "Lỗi lưu cấu hình." -#: src/transport/plugin_transport_http.c:1174 src/util/service.c:1036 +#: src/transport/plugin_transport_http.c:898 +#: src/transport/plugin_transport_http_server.c:2356 src/util/service.c:1053 #, fuzzy, c-format msgid "Failed to resolve `%s': %s\n" msgstr "Lỗi mở tập tin ghi sự kiện « %s »: %s\n" -#: src/transport/plugin_transport_http.c:1191 src/util/service.c:1053 +#: src/transport/plugin_transport_http.c:915 +#: src/transport/plugin_transport_http_server.c:2373 src/util/service.c:1070 #, fuzzy, c-format msgid "Failed to find %saddress for `%s'.\n" msgstr "Lỗi đóng kết đến cổng %s %d.\n" -#: src/transport/plugin_transport_http.c:1296 +#: src/transport/plugin_transport_http.c:1020 +#: src/transport/plugin_transport_http_server.c:2484 #, c-format msgid "Found %u addresses to report to NAT service\n" msgstr "" -#: src/transport/plugin_transport_http.c:1309 -#, c-format -msgid "FREEING %s\n" -msgstr "" - -#: src/transport/plugin_transport_http.c:1386 +#: src/transport/plugin_transport_http.c:1133 +#: src/transport/plugin_transport_http_server.c:2652 msgid "Neither IPv4 nor IPv6 are enabled! Fix in configuration\n" msgstr "" -#: src/transport/plugin_transport_http.c:1399 +#: src/transport/plugin_transport_http.c:1146 +#: src/transport/plugin_transport_http_server.c:2663 #, fuzzy msgid "Port is required! Fix in configuration\n" msgstr "" "\n" "Kết thúc cấu hình.\n" -#: src/transport/plugin_transport_http.c:1410 +#: src/transport/plugin_transport_http.c:1157 msgid "Port 0, client only mode\n" msgstr "" -#: src/transport/plugin_transport_http.c:1430 +#: src/transport/plugin_transport_http.c:1177 #, c-format msgid "" "Specific IPv4 address `%s' for plugin %s in configuration file is invalid! " "Binding to all addresses!\n" msgstr "" -#: src/transport/plugin_transport_http.c:1460 +#: src/transport/plugin_transport_http.c:1206 #, c-format msgid "" "Specific IPv6 address `%s' for plugin %s in configuration file is invalid! " "Binding to all addresses!\n" msgstr "" -#: src/transport/plugin_transport_http_client.c:624 +#: src/transport/plugin_transport_http.c:1223 +#: src/transport/plugin_transport_http_server.c:2745 +#, fuzzy, c-format +msgid "Using external hostname `%s'\n" +msgstr "Đang bắt đầu tài về « %s »\n" + +#: src/transport/plugin_transport_http.c:1228 +msgid "No external hostname configured\n" +msgstr "" + +#: src/transport/plugin_transport_http_client.c:1516 #, c-format msgid "Could not initialize curl multi handle, failed to start %s plugin!\n" msgstr "" -#: src/transport/plugin_transport_http_server.c:178 +#: src/transport/plugin_transport_http_client.c:1647 +#: src/transport/plugin_transport_http_server.c:2869 +#, fuzzy, c-format +msgid "Shutting down plugin `%s'\n" +msgstr "Đang nạp các truyền tải « %s »\n" + +#: src/transport/plugin_transport_http_client.c:1672 +#: src/transport/plugin_transport_http_server.c:2928 +#, fuzzy, c-format +msgid "Shutdown for plugin `%s' complete\n" +msgstr "Tải lên « %s » hoàn thành, địa chỉ URI là « %s ».\n" + +#: src/transport/plugin_transport_http_client.c:1700 +#: src/transport/plugin_transport_http_server.c:2775 +#, fuzzy, c-format +msgid "Maximum number of connections is %u\n" +msgstr "tăng sổ tối đa các kết nối TCP/IP" + +#: src/transport/plugin_transport_http_server.c:1342 +#, c-format +msgid "" +"Access from connection %p (%u of %u) for `%s' `%s' url `%s' with upload data " +"size %u\n" +msgstr "" + +#: src/transport/plugin_transport_http_server.c:1603 +#, c-format +msgid "Accepting connection (%u of %u) from `%s'\n" +msgstr "" + +#: src/transport/plugin_transport_http_server.c:1611 +#, c-format +msgid "" +"Server reached maximum number connections (%u), rejecting new connection\n" +msgstr "" + +#: src/transport/plugin_transport_http_server.c:1912 msgid "" "Could not create a new TLS certificate, program `gnunet-transport-" "certificate-creation' could not be started!\n" msgstr "" -#: src/transport/plugin_transport_http_server.c:202 +#: src/transport/plugin_transport_http_server.c:1936 msgid "No usable TLS certificate found and creating one failed!\n" msgstr "" -#: src/transport/plugin_transport_tcp.c:591 +#: src/transport/plugin_transport_http_server.c:2631 +#, c-format +msgid "IPv4 support is %s\n" +msgstr "" + +#: src/transport/plugin_transport_http_server.c:2645 +#, c-format +msgid "IPv6 support is %s\n" +msgstr "" + +#: src/transport/plugin_transport_http_server.c:2670 +#, fuzzy, c-format +msgid "Using port %u\n" +msgstr "Đang thử nghiệm (các) truyền tải %s\n" + +#: src/transport/plugin_transport_http_server.c:2685 +#, fuzzy, c-format +msgid "Specific IPv4 address `%s' in configuration file is invalid!\n" +msgstr "Đang thử dùng tập tin « %s » cho cấu hình MySQL.\n" + +#: src/transport/plugin_transport_http_server.c:2695 +#, fuzzy, c-format +msgid "Binding to IPv4 address %s\n" +msgstr "Mức ưu tiên tiến trình không hợp lê « %s ».\n" + +#: src/transport/plugin_transport_http_server.c:2716 +#, fuzzy, c-format +msgid "Specific IPv6 address `%s' in configuration file is invalid!\n" +msgstr "Đang thử dùng tập tin « %s » cho cấu hình MySQL.\n" + +#: src/transport/plugin_transport_http_server.c:2726 +#, fuzzy, c-format +msgid "Binding to IPv6 address %s\n" +msgstr "Mức ưu tiên tiến trình không hợp lê « %s ».\n" + +#: src/transport/plugin_transport_http_server.c:2761 +#, fuzzy, c-format +msgid "Notifying transport only about hostname `%s'\n" +msgstr "không quyết định các tên máy" + +#: src/transport/plugin_transport_smtp.c:370 +#, c-format +msgid "Received malformed message via %s. Ignored.\n" +msgstr "Nhận được thông báo dạng sai qua %s. Bị bỏ qua.\n" + +#: src/transport/plugin_transport_smtp.c:457 +msgid "SMTP filter string to invalid, lacks ': '\n" +msgstr "Chuỗi lọc vào SMTP không hợp lệ, còn thiếu « : »\n" + +#: src/transport/plugin_transport_smtp.c:466 +#, c-format +msgid "SMTP filter string to long, capped to `%s'\n" +msgstr "Chuỗi lọc vào SMTP quá dài, tối đa « %s »\n" + +#: src/transport/plugin_transport_smtp.c:561 +#: src/transport/plugin_transport_smtp.c:571 +#: src/transport/plugin_transport_smtp.c:584 +#: src/transport/plugin_transport_smtp.c:603 +#: src/transport/plugin_transport_smtp.c:626 +#: src/transport/plugin_transport_smtp.c:634 +#: src/transport/plugin_transport_smtp.c:647 +#: src/transport/plugin_transport_smtp.c:658 +#, c-format +msgid "SMTP: `%s' failed: %s.\n" +msgstr "SMTP: « %s » bị lỗi: %s\n" + +#: src/transport/plugin_transport_smtp.c:799 +msgid "No email-address specified, can not start SMTP transport.\n" +msgstr "Chưa ghi rõ địa chỉ thư điện tử nên không tạo được truyền tải SMTP.\n" + +#: src/transport/plugin_transport_smtp.c:811 +msgid "# bytes received via SMTP" +msgstr "# các byte đã nhận qua SMTP" + +#: src/transport/plugin_transport_smtp.c:812 +msgid "# bytes sent via SMTP" +msgstr "# các byte đã gửi qua SMTP" + +#: src/transport/plugin_transport_smtp.c:814 +msgid "# bytes dropped by SMTP (outgoing)" +msgstr "# các byte loại đi bởi SMTP (đi ra)" + +#: src/transport/plugin_transport_tcp.c:595 #, fuzzy, c-format msgid "Unexpected address length: %u bytes\n" msgstr "Gặp sự kiện bất thường: %d\n" -#: src/transport/plugin_transport_tcp.c:767 -#: src/transport/plugin_transport_tcp.c:856 -#: src/transport/plugin_transport_tcp.c:906 -#: src/transport/plugin_transport_tcp.c:992 -#: src/transport/plugin_transport_tcp.c:1086 -#: src/transport/plugin_transport_tcp.c:1103 +#: src/transport/plugin_transport_tcp.c:771 +#: src/transport/plugin_transport_tcp.c:860 +#: src/transport/plugin_transport_tcp.c:910 +#: src/transport/plugin_transport_tcp.c:996 +#: src/transport/plugin_transport_tcp.c:1139 +#: src/transport/plugin_transport_tcp.c:1156 #, fuzzy msgid "# bytes currently in TCP buffers" msgstr "# các byte đã gừi qua TCP" -#: src/transport/plugin_transport_tcp.c:774 -#: src/transport/plugin_transport_tcp.c:963 -#: src/transport/plugin_transport_tcp.c:1761 -#: src/transport/plugin_transport_tcp.c:2390 +#: src/transport/plugin_transport_tcp.c:778 +#: src/transport/plugin_transport_tcp.c:967 +#: src/transport/plugin_transport_tcp.c:1826 +#: src/transport/plugin_transport_tcp.c:2462 #, fuzzy msgid "# TCP sessions active" msgstr "# các khoá phiên chạy được chấp nhận" -#: src/transport/plugin_transport_tcp.c:860 +#: src/transport/plugin_transport_tcp.c:864 #, fuzzy msgid "# bytes discarded by TCP (timeout)" msgstr "# các byte loại đi bởi TCP (đi ra)" -#: src/transport/plugin_transport_tcp.c:909 +#: src/transport/plugin_transport_tcp.c:913 #, fuzzy msgid "# bytes transmitted via TCP" msgstr "# các byte được gửi" -#: src/transport/plugin_transport_tcp.c:996 +#: src/transport/plugin_transport_tcp.c:1000 #, fuzzy msgid "# bytes discarded by TCP (disconnect)" msgstr "# các byte loại đi bởi TCP (đi ra)" -#: src/transport/plugin_transport_tcp.c:1290 +#: src/transport/plugin_transport_tcp.c:1113 +#, c-format +msgid "Trying to send with invalid session %p\n" +msgstr "" + +#: src/transport/plugin_transport_tcp.c:1349 #, fuzzy, c-format msgid "Address of unexpected length: %u\n" msgstr "Gặp sự kiện bất thường: %d\n" -#: src/transport/plugin_transport_tcp.c:1401 +#: src/transport/plugin_transport_tcp.c:1466 msgid "# transport-service disconnect requests for TCP" msgstr "" -#: src/transport/plugin_transport_tcp.c:1802 +#: src/transport/plugin_transport_tcp.c:1867 #, fuzzy msgid "# TCP WELCOME messages received" msgstr "# các thông báo PONG đã mật mã được nhận" -#: src/transport/plugin_transport_tcp.c:1973 +#: src/transport/plugin_transport_tcp.c:2046 msgid "# bytes received via TCP" msgstr "# các byte đã nhận qua TCP" -#: src/transport/plugin_transport_tcp.c:2043 +#: src/transport/plugin_transport_tcp.c:2124 msgid "# network-level TCP disconnect events" msgstr "" -#: src/transport/plugin_transport_tcp.c:2279 src/util/service.c:940 +#: src/transport/plugin_transport_tcp.c:2350 src/util/service.c:948 +#: src/util/service.c:954 #, c-format msgid "Require valid port number for service `%s' in configuration!\n" msgstr "" -#: src/transport/plugin_transport_tcp.c:2293 +#: src/transport/plugin_transport_tcp.c:2364 #, fuzzy msgid "Failed to start service.\n" msgstr "Lỗi bắt đầu thu thập.\n" -#: src/transport/plugin_transport_tcp.c:2355 -#, fuzzy, c-format -msgid "Failed to find option %s in section %s!\n" -msgstr "Lỗi đóng kết đến cổng %s %d.\n" - -#: src/transport/plugin_transport_tcp.c:2378 +#: src/transport/plugin_transport_tcp.c:2450 #, c-format msgid "TCP transport listening on port %llu\n" msgstr "" -#: src/transport/plugin_transport_tcp.c:2382 +#: src/transport/plugin_transport_tcp.c:2454 msgid "TCP transport not listening on any port (client only)\n" msgstr "" -#: src/transport/plugin_transport_tcp.c:2386 +#: src/transport/plugin_transport_tcp.c:2458 #, c-format msgid "TCP transport advertises itself as being on port %llu\n" msgstr "" @@ -5144,129 +5692,132 @@ msgstr "# các thông báo PONG đã mật mã được nhận" msgid "# IPv4 broadcast HELLO beacons received via udp" msgstr "# các thông báo PONG đã mật mã được nhận" -#: src/transport/plugin_transport_udp_broadcasting.c:367 +#: src/transport/plugin_transport_udp_broadcasting.c:394 #, c-format msgid "Failed to set IPv4 broadcast option for broadcast socket on port %d\n" msgstr "" -#: src/transport/plugin_transport_udp.c:1894 +#: src/transport/plugin_transport_udp.c:2517 +#, c-format +msgid "" +"UDP could not transmit message to `%s': Network seems down, please check " +"your network configuration\n" +msgstr "" + +#: src/transport/plugin_transport_udp.c:2531 #, c-format msgid "" -"UDP could not message to `%s': `%s'. Please check your network configuration " -"and disable IPv6 if your connection does not have a global IPv6 address\n" +"UDP could not transmit message to `%s': Please check your network " +"configuration and disable IPv6 if your connection does not have a global " +"IPv6 address\n" msgstr "" -#: src/transport/plugin_transport_udp.c:2138 +#: src/transport/plugin_transport_udp.c:2772 #, fuzzy msgid "Failed to open UDP sockets\n" msgstr "Lỗi mở tập tin ghi sự kiện « %s »: %s\n" -#: src/transport/plugin_transport_udp.c:2306 +#: src/transport/plugin_transport_udp.c:2848 #, c-format msgid "Given `%s' option is out of range: %llu > %u\n" msgstr "" -#: src/transport/plugin_transport_udp.c:2349 +#: src/transport/plugin_transport_udp.c:2891 #, fuzzy, c-format msgid "Invalid IPv6 address: `%s'\n" msgstr "Mức ưu tiên tiến trình không hợp lê « %s ».\n" -#: src/transport/plugin_transport_unix.c:1356 +#: src/transport/plugin_transport_unix.c:1357 #, fuzzy msgid "Failed to open UNIX sockets\n" msgstr "Lỗi mở tập tin ghi sự kiện « %s »: %s\n" -#: src/transport/plugin_transport_wlan.c:561 +#: src/transport/plugin_transport_wlan.c:580 msgid "# WLAN ACKs sent" msgstr "" -#: src/transport/plugin_transport_wlan.c:580 +#: src/transport/plugin_transport_wlan.c:599 #, fuzzy msgid "# WLAN messages defragmented" msgstr "# các thông báo được chắp liền" -#: src/transport/plugin_transport_wlan.c:626 -#: src/transport/plugin_transport_wlan.c:676 -#: src/transport/plugin_transport_wlan.c:1696 +#: src/transport/plugin_transport_wlan.c:645 +#: src/transport/plugin_transport_wlan.c:695 +#: src/transport/plugin_transport_wlan.c:1758 #, fuzzy msgid "# WLAN sessions allocated" msgstr "# các khoá phiên chạy được chấp nhận" -#: src/transport/plugin_transport_wlan.c:749 +#: src/transport/plugin_transport_wlan.c:770 #, fuzzy msgid "# WLAN message fragments sent" msgstr "# các thông báo bị tế phân" -#: src/transport/plugin_transport_wlan.c:767 +#: src/transport/plugin_transport_wlan.c:794 msgid "# WLAN messages pending (with fragmentation)" msgstr "" -#: src/transport/plugin_transport_wlan.c:867 -#: src/transport/plugin_transport_wlan.c:948 -#: src/transport/plugin_transport_wlan.c:1698 +#: src/transport/plugin_transport_wlan.c:902 +#: src/transport/plugin_transport_wlan.c:987 +#: src/transport/plugin_transport_wlan.c:1760 #, fuzzy msgid "# WLAN MAC endpoints allocated" msgstr "# các yêu cầu get (lấy) dht được nhận" -#: src/transport/plugin_transport_wlan.c:1119 +#: src/transport/plugin_transport_wlan.c:1169 #, fuzzy msgid "# HELLO messages received via WLAN" msgstr "# các thông báo PONG đã mật mã được nhận" -#: src/transport/plugin_transport_wlan.c:1140 +#: src/transport/plugin_transport_wlan.c:1190 #, fuzzy msgid "# fragments received via WLAN" msgstr "# các mảnh bị loại bỏ" -#: src/transport/plugin_transport_wlan.c:1150 +#: src/transport/plugin_transport_wlan.c:1200 #, fuzzy msgid "# ACKs received via WLAN" msgstr "# các byte đã nhận qua TCP" -#: src/transport/plugin_transport_wlan.c:1207 +#: src/transport/plugin_transport_wlan.c:1257 #, fuzzy msgid "# WLAN DATA messages discarded due to CRC32 error" msgstr "# các thông báo được chắp liền" -#: src/transport/plugin_transport_wlan.c:1306 +#: src/transport/plugin_transport_wlan.c:1358 #, fuzzy msgid "# DATA messages received via WLAN" msgstr "# các thông báo PONG đã mật mã được nhận" -#: src/transport/plugin_transport_wlan.c:1341 +#: src/transport/plugin_transport_wlan.c:1393 #, fuzzy msgid "# WLAN DATA messages processed" msgstr "# các thông báo PONG đã mật mã được nhận" -#: src/transport/plugin_transport_wlan.c:1402 +#: src/transport/plugin_transport_wlan.c:1454 #, fuzzy msgid "# HELLO beacons sent via WLAN" msgstr "# các byte đã gửi qua UDP" -#: src/transport/plugin_transport_wlan.c:1511 +#: src/transport/plugin_transport_wlan.c:1563 msgid "WLAN address with invalid size encountered\n" msgstr "" -#: src/transport/plugin_transport_wlan.c:1668 -#, fuzzy, c-format -msgid "Invalid configuration option `%s' in section `%s'\n" -msgstr "Giá trị cấu hình « %s » cho « %s » trong phần « %s » nên là con số\n" - -#: src/transport/plugin_transport_wlan.c:1677 +#: src/transport/plugin_transport_wlan.c:1739 #, c-format msgid "Helper binary `%s' not SUID, cannot run WLAN transport\n" msgstr "" -#: src/transport/plugin_transport_wlan.c:1687 -#, fuzzy, c-format -msgid "Missing configuration option `%s' in section `%s'\n" -msgstr "Giá trị cấu hình « %s » cho « %s » trong phần « %s » nên là con số\n" - -#: src/transport/transport_api.c:570 +#: src/transport/transport_api.c:659 #, fuzzy, c-format msgid "Received unexpected message of type %u in %s:%u\n" msgstr "Nhận được thông báo bị hỏng từ đồng đẳng « %s » trong %s:%d.\n" +#: src/transport/transport-testing.c:586 +#, fuzzy +msgid "Failed to initialize testing library!\n" +msgstr "Lỗi sơ khởi dịch vụ « %s ».\n" + #: src/util/bio.c:136 src/util/bio.c:142 #, fuzzy, c-format msgid "Error reading `%s': %s" @@ -5296,89 +5847,107 @@ msgstr "" msgid "Metadata `%s' failed to deserialize" msgstr "" -#: src/util/client.c:359 +#: src/util/client.c:276 src/util/client.c:753 src/util/service.c:984 +#, c-format +msgid "UNIXPATH `%s' too long, maximum length is %llu\n" +msgstr "" + +#: src/util/client.c:280 src/util/client.c:757 src/util/service.c:988 +#, fuzzy, c-format +msgid "Using `%s' instead\n" +msgstr "%s: tùy chọn « %s » là mơ hồ\n" + +#: src/util/client.c:371 #, c-format msgid "" "Could not determine valid hostname and port for service `%s' from " "configuration.\n" msgstr "" -#: src/util/client.c:367 +#: src/util/client.c:379 #, c-format msgid "Need a non-empty hostname for service `%s'.\n" msgstr "" -#: src/util/client.c:685 +#: src/util/client.c:698 msgid "Failure to transmit TEST request.\n" msgstr "" -#: src/util/client.c:740 src/util/service.c:970 -#, c-format -msgid "UNIXPATH `%s' too long, maximum length is %llu\n" -msgstr "" - -#: src/util/client.c:882 +#: src/util/client.c:898 #, c-format msgid "Could not connect to service `%s', must not be running.\n" msgstr "" -#: src/util/client.c:896 +#: src/util/client.c:912 #, fuzzy, c-format msgid "Failure to transmit request to service `%s'\n" msgstr "Lỗi đọc danh sách bạn bè từ « %s »\n" -#: src/util/client.c:1149 +#: src/util/client.c:1177 msgid "Could not submit request, not expecting to receive a response.\n" msgstr "" -#: src/util/common_logging.c:239 src/util/common_logging.c:890 +#: src/util/common_logging.c:258 src/util/common_logging.c:1007 msgid "DEBUG" msgstr "GỠ LỖI" -#: src/util/common_logging.c:241 src/util/common_logging.c:888 +#: src/util/common_logging.c:260 src/util/common_logging.c:1005 msgid "INFO" msgstr "TIN" -#: src/util/common_logging.c:243 src/util/common_logging.c:886 +#: src/util/common_logging.c:262 src/util/common_logging.c:1003 msgid "WARNING" msgstr "CẢNH BÁO" -#: src/util/common_logging.c:245 src/util/common_logging.c:884 +#: src/util/common_logging.c:264 src/util/common_logging.c:1001 msgid "ERROR" msgstr "LỖI" -#: src/util/common_logging.c:247 src/util/common_logging.c:892 +#: src/util/common_logging.c:266 src/util/common_logging.c:1009 msgid "NONE" msgstr "" -#: src/util/common_logging.c:610 +#: src/util/common_logging.c:395 #, fuzzy, c-format msgid "Failed to create or access directory for log file `%s'\n" msgstr "Không thể truy cập đến tập tin gnunet-directory « %s »\n" -#: src/util/common_logging.c:725 +#: src/util/common_logging.c:819 #, fuzzy, c-format msgid "Message `%.*s' repeated %u times in the last %s\n" msgstr "Thông điệp « %.*s » đã lặp lại %u lần trong %llu giây trước\n" -#: src/util/common_logging.c:893 +#: src/util/common_logging.c:1010 msgid "INVALID" msgstr "" -#: src/util/common_logging.c:992 +#: src/util/common_logging.c:1149 msgid "unknown address" msgstr "" -#: src/util/common_logging.c:1030 +#: src/util/common_logging.c:1187 msgid "invalid address" msgstr "" -#: src/util/configuration.c:244 +#: src/util/common_logging.c:1205 #, fuzzy, c-format -msgid "Syntax error in configuration file `%s' at line %u.\n" +msgid "Configuration fails to specify option `%s' in section `%s'!\n" +msgstr "" +"Cấu hình không thỏa mãn các ràng buộc của tập tin đặc tả cấu hình « %s ».\n" + +#: src/util/common_logging.c:1226 +#, fuzzy, c-format +msgid "" +"Configuration specifies invalid value for option `%s' in section `%s': %s\n" +msgstr "" +"Cấu hình không thỏa mãn các ràng buộc của tập tin đặc tả cấu hình « %s ».\n" + +#: src/util/configuration.c:291 +#, fuzzy, c-format +msgid "Syntax error while deserializing in line %u\n" msgstr "Gặp lỗi cú pháp trong tập tin cấu hình « %s » tại dòng %d.\n" -#: src/util/configuration.c:816 +#: src/util/configuration.c:998 #, c-format msgid "" "Configuration value '%s' for '%s' in section '%s' is not in set of legal " @@ -5387,171 +5956,204 @@ msgstr "" "Giá trị cấu hình « %s » cho « %s » trong phần « %s » không phải nằm trong " "tập hợp các sự chọn được phép\n" -#: src/util/connection.c:420 +#: src/util/connection.c:427 #, fuzzy, c-format msgid "Access denied to `%s'\n" msgstr "Không đủ quyền cho « %s ».\n" -#: src/util/connection.c:435 +#: src/util/connection.c:442 #, c-format msgid "Accepting connection from `%s': %p\n" msgstr "" -#: src/util/connection.c:550 +#: src/util/connection.c:557 #, fuzzy, c-format msgid "" "Failed to establish TCP connection to `%s:%u', no further addresses to try.\n" msgstr "Lỗi thiết lập kết nối với đồng đẳng.\n" -#: src/util/connection.c:739 src/util/connection.c:909 +#: src/util/connection.c:755 src/util/connection.c:922 #, fuzzy, c-format msgid "Trying to connect to `%s' (%p)\n" msgstr "Không thể kết nối tới %s:%u: %s\n" -#: src/util/connection.c:748 -#, fuzzy, c-format -msgid "Failed to connect to `%s' (%p)\n" -msgstr "Không thể kết nối tới %s:%u: %s\n" - -#: src/util/connection.c:900 +#: src/util/connection.c:913 #, fuzzy, c-format msgid "Attempt to connect to `%s' failed\n" msgstr " Lỗi kết nối\n" -#: src/util/container_bloomfilter.c:510 +#: src/util/container_bloomfilter.c:518 #, c-format msgid "" "Size of file on disk is incorrect for this Bloom filter (want %llu, have " "%llu)\n" msgstr "" -#: src/util/crypto_random.c:280 -#, c-format -msgid "Starting `%s' process to generate entropy\n" -msgstr "" +#: src/util/crypto_ecc.c:441 +#, fuzzy, c-format +msgid "" +"File `%s' does not contain a valid private key (too long, %llu bytes). " +"Deleting it.\n" +msgstr "Tập tin « %s » không chứa biệt hiệu nên thử gỡ bỏ.\n" -#: src/util/crypto_random.c:309 -#, c-format -msgid "libgcrypt has not the expected version (version %s is required).\n" -msgstr "libgcrypt không có phiên bản mong đợi (yêu cầu phiên bản %s).\n" +#: src/util/crypto_ecc.c:456 src/util/crypto_rsa.c:660 +#, fuzzy, c-format +msgid "" +"File `%s' does not contain a valid private key (failed decode, %llu bytes). " +"Deleting it.\n" +msgstr "Tập tin « %s » không chứa biệt hiệu nên thử gỡ bỏ.\n" -#: src/util/crypto_rsa.c:661 src/util/crypto_rsa.c:708 +#: src/util/crypto_ecc.c:552 src/util/crypto_ecc.c:596 +#: src/util/crypto_rsa.c:757 src/util/crypto_rsa.c:801 #, fuzzy, c-format -msgid "Could not aquire lock on file `%s': %s...\n" +msgid "Could not acquire lock on file `%s': %s...\n" msgstr "Lỗi mở tập tin theo dõi « %s »: %s\n" -#: src/util/crypto_rsa.c:666 +#: src/util/crypto_ecc.c:557 src/util/crypto_rsa.c:762 #, fuzzy msgid "Creating a new private key. This may take a while.\n" msgstr "Đang tạo khoá máy mới (có thể hơi lâu).\n" -#: src/util/crypto_rsa.c:684 -#, c-format -msgid "I am host `%s'. Stored new private key in `%s'.\n" -msgstr "" - -#: src/util/crypto_rsa.c:712 src/util/crypto_rsa.c:748 -msgid "This may be ok if someone is currently generating a hostkey.\n" +#: src/util/crypto_ecc.c:600 src/util/crypto_rsa.c:805 +#: src/util/crypto_rsa.c:841 +msgid "This may be ok if someone is currently generating a private key.\n" msgstr "" -#: src/util/crypto_rsa.c:743 +#: src/util/crypto_ecc.c:631 src/util/crypto_rsa.c:836 #, c-format msgid "" -"When trying to read hostkey file `%s' I found %u bytes but I need at least " -"%u.\n" +"When trying to read key file `%s' I found %u bytes but I need at least %u.\n" msgstr "" -#: src/util/crypto_rsa.c:763 +#: src/util/crypto_ecc.c:636 +msgid "This may be ok if someone is currently generating a key.\n" +msgstr "" + +#: src/util/crypto_ecc.c:651 src/util/crypto_rsa.c:856 #, fuzzy, c-format msgid "File `%s' does not contain a valid private key. Deleting it.\n" msgstr "Tập tin « %s » không chứa biệt hiệu nên thử gỡ bỏ.\n" -#: src/util/crypto_rsa.c:781 +#: src/util/crypto_ecc.c:773 src/util/crypto_rsa.c:941 +msgid "interrupted by shutdown" +msgstr "" + +#: src/util/crypto_ecc.c:784 +msgid "gnunet-ecc failed" +msgstr "" + +#: src/util/crypto_ecc.c:979 +#, fuzzy, c-format +msgid "ECC signing failed at %s:%d: %s\n" +msgstr "%s bị lỗi tại %s:%d: « %s »\n" + +#: src/util/crypto_ecc.c:1047 +#, fuzzy, c-format +msgid "ECC signature verification failed at %s:%d: %s\n" +msgstr "Lỗi thẩm tra chữ ký RSA tại %s:%d: %s\n" + +#: src/util/crypto_random.c:313 #, c-format -msgid "I am host `%s'. Read private key from `%s'.\n" +msgid "Starting `%s' process to generate entropy\n" +msgstr "" + +#: src/util/crypto_random.c:342 +#, c-format +msgid "libgcrypt has not the expected version (version %s is required).\n" +msgstr "libgcrypt không có phiên bản mong đợi (yêu cầu phiên bản %s).\n" + +#: src/util/crypto_rsa.c:644 +#, fuzzy, c-format +msgid "" +"File `%s' does not contain a valid private key (too long, %llu bytes). " +"Renaming it.\n" +msgstr "Tập tin « %s » không chứa biệt hiệu nên thử gỡ bỏ.\n" + +#: src/util/crypto_rsa.c:952 +msgid "gnunet-rsa failed" msgstr "" -#: src/util/crypto_rsa.c:1032 +#: src/util/crypto_rsa.c:1343 #, c-format msgid "RSA signature verification failed at %s:%d: %s\n" msgstr "Lỗi thẩm tra chữ ký RSA tại %s:%d: %s\n" -#: src/util/disk.c:498 +#: src/util/disk.c:601 #, fuzzy, c-format msgid "`%s' failed for drive `%S': %u\n" msgstr "« %s » thất bại cho ổ đĩa « %s »: %u\n" -#: src/util/disk.c:1062 +#: src/util/disk.c:1205 #, c-format msgid "Expected `%s' to be a directory!\n" msgstr "Mong đợi « %s » là một thư mục.\n" -#: src/util/disk.c:1416 src/util/service.c:1650 +#: src/util/disk.c:1559 src/util/service.c:1669 #, c-format msgid "Cannot obtain information about user `%s': %s\n" msgstr "Không thể lấy thông tin về người dùng « %s »: %s\n" -#: src/util/disk.c:1734 +#: src/util/disk.c:1931 #, c-format msgid "No `%s' specified for service `%s' in configuration.\n" msgstr "" -#: src/util/getopt.c:669 +#: src/util/getopt.c:570 #, c-format msgid "%s: option `%s' is ambiguous\n" msgstr "%s: tùy chọn « %s » là mơ hồ\n" -#: src/util/getopt.c:693 +#: src/util/getopt.c:594 #, c-format msgid "%s: option `--%s' does not allow an argument\n" msgstr "%s: tùy chọn « --%s » không cho phép đối số\n" -#: src/util/getopt.c:698 +#: src/util/getopt.c:599 #, c-format msgid "%s: option `%c%s' does not allow an argument\n" msgstr "%s: tùy chọn « %c%s » không cho phép đối số\n" -#: src/util/getopt.c:715 src/util/getopt.c:883 +#: src/util/getopt.c:616 src/util/getopt.c:783 #, c-format msgid "%s: option `%s' requires an argument\n" msgstr "%s: tùy chọn « %s » cần thiết đối số\n" -#: src/util/getopt.c:744 +#: src/util/getopt.c:645 #, c-format msgid "%s: unrecognized option `--%s'\n" msgstr "%s: không nhận ra tùy chọn « --%s »\n" -#: src/util/getopt.c:748 +#: src/util/getopt.c:649 #, c-format msgid "%s: unrecognized option `%c%s'\n" msgstr "%s: không nhận ra tùy chọn « %c%s »\n" -#: src/util/getopt.c:773 +#: src/util/getopt.c:674 #, c-format msgid "%s: illegal option -- %c\n" msgstr "%s: tùy chọn không được phép -- %c\n" -#: src/util/getopt.c:775 +#: src/util/getopt.c:676 #, c-format msgid "%s: invalid option -- %c\n" msgstr "%s: tùy chọn không hợp lệ -- %c\n" -#: src/util/getopt.c:803 src/util/getopt.c:931 +#: src/util/getopt.c:704 src/util/getopt.c:831 #, c-format msgid "%s: option requires an argument -- %c\n" msgstr "%s: tùy chọn cần thiết đối số -- %c\n" -#: src/util/getopt.c:851 +#: src/util/getopt.c:752 #, c-format msgid "%s: option `-W %s' is ambiguous\n" msgstr "%s: tùy chọn « -W %s » là mơ hồ\n" -#: src/util/getopt.c:869 +#: src/util/getopt.c:770 #, c-format msgid "%s: option `-W %s' does not allow an argument\n" msgstr "%s: tùy chọn « -W %s » không cho phép đối số\n" -#: src/util/getopt.c:1035 +#: src/util/getopt.c:935 #, fuzzy, c-format msgid "Use %s to get a list of options.\n" msgstr "" @@ -5565,37 +6167,110 @@ msgstr "" "Mọi đối số bắt buộc phải sử dụng với tùy chọn dài cũng bắt buộc với tùy chọn " "ngắn.\n" -#: src/util/getopt_helpers.c:258 src/util/getopt_helpers.c:286 +#: src/util/getopt_helpers.c:258 src/util/getopt_helpers.c:316 #, c-format msgid "You must pass a number to the `%s' option.\n" msgstr "Phải gửi một con số cho tùy chọn « %s ».\n" -#: src/util/gnunet-resolver.c:148 -msgid "perform a reverse lookup" +#: src/util/getopt_helpers.c:288 +#, fuzzy, c-format +msgid "You must pass relative time to the `%s' option.\n" +msgstr "Phải gửi một con số cho tùy chọn « %s ».\n" + +#: src/util/gnunet-config.c:90 +#, fuzzy, c-format +msgid "--section argument is required\n" +msgstr "đặt tên hiệu cần dùng (cần thiết)" + +#: src/util/gnunet-config.c:133 +#, c-format +msgid "--option argument required to set value\n" msgstr "" -#: src/util/gnunet-resolver.c:154 -msgid "Use build-in GNUnet stub resolver" +#: src/util/gnunet-config.c:160 +msgid "obtain option of value as a filename (with $-expansion)" +msgstr "" + +#: src/util/gnunet-config.c:163 +msgid "name of the section to access" +msgstr "" + +#: src/util/gnunet-config.c:166 +msgid "name of the option to access" +msgstr "" + +#: src/util/gnunet-config.c:169 +msgid "value to set" +msgstr "" + +#: src/util/gnunet-config.c:178 +#, fuzzy +msgid "Manipulate GNUnet configuration files" +msgstr "cập nhật một giá trị trong tập tin cấu hình" + +#: src/util/gnunet-ecc.c:107 src/util/gnunet-rsa.c:107 +#, fuzzy, c-format +msgid "Failed to open `%s': %s\n" +msgstr "Lỗi mở tập tin ghi sự kiện « %s »: %s\n" + +#: src/util/gnunet-ecc.c:113 src/util/gnunet-rsa.c:113 +#, c-format +msgid "Generating %u keys, please wait" +msgstr "" + +#: src/util/gnunet-ecc.c:128 src/util/gnunet-rsa.c:137 +#, fuzzy, c-format +msgid "" +"\n" +"Failed to write to `%s': %s\n" +msgstr "Lỗi chạy %s: %s %d\n" + +#: src/util/gnunet-ecc.c:140 src/util/gnunet-rsa.c:149 +#, c-format +msgid "Finished!\n" msgstr "" -#: src/util/gnunet-rsa.c:64 +#: src/util/gnunet-ecc.c:163 src/util/gnunet-rsa.c:172 #, c-format msgid "No hostkey file specified on command line\n" msgstr "" -#: src/util/gnunet-rsa.c:112 +#: src/util/gnunet-ecc.c:220 src/util/gnunet-rsa.c:229 +msgid "create COUNT public-private key pairs (for testing)" +msgstr "" + +#: src/util/gnunet-ecc.c:223 src/util/gnunet-rsa.c:232 msgid "print the public key in ASCII format" msgstr "" -#: src/util/gnunet-rsa.c:115 +#: src/util/gnunet-ecc.c:226 src/util/gnunet-rsa.c:235 msgid "print the hash of the public key in ASCII format" msgstr "" -#: src/util/gnunet-rsa.c:118 +#: src/util/gnunet-ecc.c:229 src/util/gnunet-rsa.c:238 msgid "print the short hash of the public key in ASCII format" msgstr "" -#: src/util/gnunet-rsa.c:124 +#: src/util/gnunet-ecc.c:232 src/util/gnunet-rsa.c:241 +msgid "" +"use insecure, weak random number generator for key generation (for testing " +"only)" +msgstr "" + +#: src/util/gnunet-ecc.c:243 +#, fuzzy +msgid "Manipulate GNUnet private ECC key files" +msgstr "cập nhật một giá trị trong tập tin cấu hình" + +#: src/util/gnunet-resolver.c:148 +msgid "perform a reverse lookup" +msgstr "" + +#: src/util/gnunet-resolver.c:159 +msgid "Use build-in GNUnet stub resolver" +msgstr "" + +#: src/util/gnunet-rsa.c:252 msgid "Manipulate GNUnet private RSA key files" msgstr "" @@ -5610,70 +6285,74 @@ msgstr "Không thể giải quyết « %s » (%s): %s\n" msgid "Could not find IP of host `%s': %s\n" msgstr "Không tìm thấy địa chỉ IP của máy « %s »: %s\n" -#: src/util/helper.c:244 +#: src/util/gnunet-uri.c:90 +#, c-format +msgid "No URI specified on command line\n" +msgstr "" + +#: src/util/gnunet-uri.c:95 #, fuzzy, c-format -msgid "Error reading from `%s': %s\n" -msgstr "Gặp lỗi khi tạo người dùng" +msgid "Invalid URI: does not start with `%s'\n" +msgstr "Ký hiệu mạng sai (không kết thúc với « ; »: « %s »)\n" + +#: src/util/gnunet-uri.c:102 +#, c-format +msgid "Invalid URI: fails to specify subsystem\n" +msgstr "" -#: src/util/helper.c:259 +#: src/util/gnunet-uri.c:112 #, c-format -msgid "Got 0 bytes from helper `%s' (EOF)\n" +msgid "No handler known for subsystem `%s'\n" msgstr "" -#: src/util/helper.c:269 +#: src/util/gnunet-uri.c:174 +msgid "Perform default-actions for GNUnet URIs" +msgstr "" + +#: src/util/helper.c:260 #, fuzzy, c-format -msgid "Got %u bytes from helper `%s'\n" -msgstr "Nhận yêu cầu định tuyến\n" +msgid "Error reading from `%s': %s\n" +msgstr "Gặp lỗi khi tạo người dùng" -#: src/util/helper.c:278 +#: src/util/helper.c:305 #, fuzzy, c-format msgid "Failed to parse inbound message from helper `%s'\n" msgstr "Lỗi đọc danh sách bạn bè từ « %s »\n" -#: src/util/helper.c:310 -#, fuzzy, c-format -msgid "Starting HELPER process `%s'\n" -msgstr "Đang bắt đầu tài về « %s »\n" - -#: src/util/helper.c:440 +#: src/util/helper.c:499 #, fuzzy, c-format msgid "Error writing to `%s': %s\n" msgstr "Gặp lỗi khi tạo người dùng" -#: src/util/network.c:1200 +#: src/util/network.c:127 +#, c-format +msgid "Unable to shorten unix path `%s' while keeping name unique\n" +msgstr "" + +#: src/util/network.c:1331 #, c-format msgid "" "Fatal internal logic error, process hangs in `%s' (abort with CTRL-C)!\n" msgstr "" -#: src/util/os_installation.c:299 +#: src/util/os_installation.c:420 #, c-format msgid "" "Could not determine installation path for %s. Set `%s' environment " "variable.\n" msgstr "" -#: src/util/os_installation.c:486 +#: src/util/os_installation.c:702 #, fuzzy, c-format msgid "Could not find binary `%s' in PATH!\n" msgstr "Không thể đọc danh sách bạn bè « %s »\n" -#: src/util/os_installation.c:492 -#, fuzzy, c-format -msgid "access (%s, X_OK) failed: %s\n" -msgstr "SMTP: « %s » bị lỗi: %s\n" - -#: src/util/os_installation.c:507 -#, fuzzy, c-format -msgid "stat (%s) failed: %s\n" -msgstr "SMTP: « %s » bị lỗi: %s\n" - -#: src/util/os_priority.c:305 +#: src/util/os_priority.c:302 #, fuzzy, c-format msgid "Failed to open named pipe `%s' for reading: %s\n" msgstr "Lỗi mở tập tin ghi sự kiện « %s »: %s\n" -#: src/util/os_priority.c:306 +#: src/util/os_priority.c:303 #, fuzzy, c-format msgid "Failed to open named pipe `%s' for writing: %s\n" msgstr "Lỗi mở tập tin ghi sự kiện « %s »: %s\n" @@ -5698,12 +6377,17 @@ msgstr "« %s » thất bại cho thư viện « %s » với lỗi: %s\n" msgid "Could not determine plugin installation path.\n" msgstr "Không thể truy cập đến thông tin về không gian tên.\n" -#: src/util/pseudonym.c:276 +#: src/util/program.c:254 src/util/service.c:1791 +#, fuzzy, c-format +msgid "Could not access configuration file `%s'\n" +msgstr "Không thể truy cập đến tập tin gnunet-directory « %s »\n" + +#: src/util/pseudonym.c:282 #, fuzzy, c-format msgid "Failed to parse metadata about pseudonym from file `%s': %s\n" msgstr "Lỗi phân tích dữ liệu giao diện từ « %s ».\n" -#: src/util/pseudonym.c:407 src/util/pseudonym.c:433 +#: src/util/pseudonym.c:413 src/util/pseudonym.c:439 msgid "no-name" msgstr "không-tên" @@ -5733,152 +6417,152 @@ msgstr "không quyết định các tên máy" msgid "Could not resolve our FQDN : %s\n" msgstr "Không thể giải quyết « %s » (%s): %s\n" -#: src/util/scheduler.c:786 +#: src/util/scheduler.c:782 msgid "Looks like we're busy waiting...\n" msgstr "" -#: src/util/scheduler.c:916 +#: src/util/scheduler.c:912 #, c-format msgid "Attempt to cancel dead task %llu!\n" msgstr "" -#: src/util/server.c:483 +#: src/util/server.c:426 #, fuzzy, c-format msgid "`%s' failed for port %d (%s).\n" msgstr "« %s » thất bại cho ổ đĩa « %s »: %u\n" -#: src/util/server.c:492 +#: src/util/server.c:435 #, fuzzy, c-format msgid "`%s' failed for port %d (%s): address already in use\n" msgstr "« %s » bị lỗi cho cổng %d. Trình gnunetd có chạy chưa?\n" -#: src/util/server.c:497 +#: src/util/server.c:446 #, fuzzy, c-format -msgid "`%s' failed for `%s': address already in use\n" +msgid "`%s' failed for `%.*s': address already in use\n" msgstr "« %s » bị lỗi cho cổng %d. Trình gnunetd có chạy chưa?\n" -#: src/util/server.c:827 +#: src/util/server.c:830 #, c-format msgid "" "Processing code for message of type %u did not call " -"GNUNET_SERVER_receive_done after %llums\n" +"`GNUNET_SERVER_receive_done' after %s\n" msgstr "" -#: src/util/service.c:135 src/util/service.c:161 src/util/service.c:204 -#: src/util/service.c:225 src/util/service.c:232 +#: src/util/service.c:142 src/util/service.c:168 src/util/service.c:211 +#: src/util/service.c:232 src/util/service.c:239 #, c-format msgid "Invalid format for IP: `%s'\n" msgstr "Địa chỉ IP định dạng sai: %s\n" -#: src/util/service.c:188 +#: src/util/service.c:195 #, c-format msgid "Invalid network notation ('/%d' is not legal in IPv4 CIDR)." msgstr "Ký hiệu mạng sai (« /%d » không hợp lệ trong CIDR IPv4)." -#: src/util/service.c:281 +#: src/util/service.c:288 #, c-format msgid "Invalid network notation (does not end with ';': `%s')\n" msgstr "Ký hiệu mạng sai (không kết thúc với « ; »: « %s »)\n" -#: src/util/service.c:313 +#: src/util/service.c:320 #, fuzzy, c-format msgid "Wrong format `%s' for netmask\n" msgstr "Mặt nạ mạng có định dạng sai « %s »: %s\n" -#: src/util/service.c:343 +#: src/util/service.c:350 #, fuzzy, c-format msgid "Wrong format `%s' for network\n" msgstr "Mạng có định dạng sai « %s »: %s\n" -#: src/util/service.c:698 +#: src/util/service.c:707 #, c-format msgid "Access denied to UID %d / GID %d\n" msgstr "" -#: src/util/service.c:703 +#: src/util/service.c:712 #, fuzzy, c-format msgid "Unknown address family %d\n" msgstr "\tKhông rõ miền tên « %s »\n" -#: src/util/service.c:710 +#: src/util/service.c:719 #, c-format msgid "Access from `%s' denied to service `%s'\n" msgstr "" -#: src/util/service.c:765 +#: src/util/service.c:774 #, c-format msgid "Could not parse IPv4 network specification `%s' for `%s:%s'\n" msgstr "" -#: src/util/service.c:802 +#: src/util/service.c:811 #, c-format msgid "Could not parse IPv6 network specification `%s' for `%s:%s'\n" msgstr "" -#: src/util/service.c:920 +#: src/util/service.c:929 #, c-format msgid "" "Disabling IPv6 support for service `%s', failed to create IPv6 socket: %s\n" msgstr "" -#: src/util/service.c:990 +#: src/util/service.c:1007 #, c-format msgid "" "Disabling UNIX domain socket support for service `%s', failed to create UNIX " "domain socket: %s\n" msgstr "" -#: src/util/service.c:1007 +#: src/util/service.c:1024 #, c-format msgid "Have neither PORT nor UNIXPATH for service `%s', but one is required\n" msgstr "" -#: src/util/service.c:1241 +#: src/util/service.c:1258 msgid "Could not access a pre-bound socket, will try to bind myself\n" msgstr "" -#: src/util/service.c:1292 src/util/service.c:1310 +#: src/util/service.c:1309 src/util/service.c:1327 #, c-format msgid "Specified value for `%s' of service `%s' is invalid\n" msgstr "" -#: src/util/service.c:1337 +#: src/util/service.c:1354 #, c-format msgid "Could not access pre-bound socket %u, will try to bind myself\n" msgstr "" -#: src/util/service.c:1506 +#: src/util/service.c:1525 #, fuzzy, c-format msgid "Failed to start `%s' at `%s'\n" msgstr "Lỗi chạy %s: %s %d\n" -#: src/util/service.c:1539 +#: src/util/service.c:1558 #, fuzzy, c-format msgid "Service `%s' runs at %s\n" msgstr "Đồng đẳng « %s » có mức tin cậy %8u\n" -#: src/util/service.c:1588 +#: src/util/service.c:1607 msgid "Service process failed to initialize\n" msgstr "" -#: src/util/service.c:1592 +#: src/util/service.c:1611 msgid "Service process could not initialize server function\n" msgstr "" -#: src/util/service.c:1596 +#: src/util/service.c:1615 msgid "Service process failed to report status\n" msgstr "" -#: src/util/service.c:1651 +#: src/util/service.c:1670 msgid "No such user" msgstr "Không có người dùng như vậy" -#: src/util/service.c:1664 +#: src/util/service.c:1683 #, c-format msgid "Cannot change user/group to `%s': %s\n" msgstr "Không thể thay đổi người dùng/nhóm thành « %s »: %s\n" -#: src/util/service.c:1729 +#: src/util/service.c:1749 msgid "do daemonize (detach from terminal)" msgstr "" @@ -5887,75 +6571,85 @@ msgstr "" msgid "signal (%d, %p) returned %d.\n" msgstr "" -#: src/util/strings.c:144 +#: src/util/strings.c:146 msgid "b" msgstr "b" -#: src/util/strings.c:334 +#: src/util/strings.c:413 #, c-format msgid "Character sets requested were `%s'->`%s'\n" msgstr "" -#: src/util/strings.c:481 +#: src/util/strings.c:528 msgid "Failed to expand `$HOME': environment variable `HOME' not set" msgstr "" "Lỗi mở rộng biến môi trường « $HOME »: chưa đặt biến môi trường « HOME »" -#: src/util/strings.c:573 +#: src/util/strings.c:625 msgid "ms" msgstr "mg" -#: src/util/strings.c:578 -msgid "eternity" +#: src/util/strings.c:629 +msgid "forever" +msgstr "" + +#: src/util/strings.c:631 +msgid "0 ms" msgstr "" -#: src/util/strings.c:582 +#: src/util/strings.c:637 msgid "s" msgstr "g" -#: src/util/strings.c:586 +#: src/util/strings.c:643 msgid "m" msgstr "p" -#: src/util/strings.c:590 +#: src/util/strings.c:649 msgid "h" msgstr "g" -#: src/util/strings.c:594 -msgid " days" +#: src/util/strings.c:656 +#, fuzzy +msgid "day" +msgstr " ngày" + +#: src/util/strings.c:658 +#, fuzzy +msgid "days" msgstr " ngày" -#: src/util/strings.c:618 +#: src/util/strings.c:685 msgid "end of time" msgstr "" -#: src/util/strings.c:1012 +#: src/util/strings.c:1073 msgid "IPv6 address did not start with `['\n" msgstr "" -#: src/util/strings.c:1020 +#: src/util/strings.c:1081 msgid "IPv6 address did contain ':' to separate port number\n" msgstr "" -#: src/util/strings.c:1026 +#: src/util/strings.c:1087 msgid "IPv6 address did contain ']' before ':' to separate port number\n" msgstr "" -#: src/util/strings.c:1033 +#: src/util/strings.c:1094 msgid "IPv6 address did contain a valid port number after the last ':'\n" msgstr "" -#: src/util/strings.c:1042 +#: src/util/strings.c:1103 #, fuzzy, c-format msgid "Invalid IPv6 address `%s': %s\n" msgstr "Mức ưu tiên tiến trình không hợp lê « %s ».\n" -#: src/vpn/gnunet-service-vpn.c:511 src/vpn/gnunet-service-vpn.c:1071 +#: src/vpn/gnunet-service-vpn.c:512 src/vpn/gnunet-service-vpn.c:1088 #, fuzzy msgid "# Active tunnels" msgstr "# các kết nối dht" -#: src/vpn/gnunet-service-vpn.c:608 src/vpn/gnunet-service-vpn.c:645 +#: src/vpn/gnunet-service-vpn.c:609 src/vpn/gnunet-service-vpn.c:646 #, fuzzy msgid "# peers connected to mesh tunnels" msgstr "# của các đồng đẳng đã kết nối" @@ -5970,85 +6664,85 @@ msgstr "# các thông báo PING được tạo" msgid "# Bytes dropped in mesh queue (overflow)" msgstr "# các byte loại bỏ bởi UDP (đi ra)" -#: src/vpn/gnunet-service-vpn.c:772 +#: src/vpn/gnunet-service-vpn.c:771 #, fuzzy msgid "# Mesh tunnels created" msgstr "# các truy vấn lỗ hổng được định tuyến" -#: src/vpn/gnunet-service-vpn.c:795 +#: src/vpn/gnunet-service-vpn.c:794 #, fuzzy msgid "Failed to setup mesh tunnel!\n" msgstr "Lỗi lấy thông kê về truyền tải.\n" -#: src/vpn/gnunet-service-vpn.c:973 +#: src/vpn/gnunet-service-vpn.c:990 #, c-format msgid "Protocol %u not supported, dropping\n" msgstr "" -#: src/vpn/gnunet-service-vpn.c:1291 +#: src/vpn/gnunet-service-vpn.c:1308 msgid "# ICMPv4 packets dropped (not allowed)" msgstr "" -#: src/vpn/gnunet-service-vpn.c:1312 +#: src/vpn/gnunet-service-vpn.c:1329 msgid "# ICMPv6 packets dropped (not allowed)" msgstr "" -#: src/vpn/gnunet-service-vpn.c:1517 +#: src/vpn/gnunet-service-vpn.c:1534 #, fuzzy msgid "# Packets received from TUN interface" msgstr "# các đáp ứng lỗ hổng được gửi cho trình/máy khách" -#: src/vpn/gnunet-service-vpn.c:1555 src/vpn/gnunet-service-vpn.c:1596 +#: src/vpn/gnunet-service-vpn.c:1572 src/vpn/gnunet-service-vpn.c:1613 #, c-format msgid "Packet received for unmapped destination `%s' (dropping it)\n" msgstr "" -#: src/vpn/gnunet-service-vpn.c:1606 +#: src/vpn/gnunet-service-vpn.c:1623 msgid "Received IPv4 packet with options (dropping it)\n" msgstr "" -#: src/vpn/gnunet-service-vpn.c:1620 +#: src/vpn/gnunet-service-vpn.c:1637 #, c-format msgid "Received packet of unknown protocol %d from TUN (dropping it)\n" msgstr "" -#: src/vpn/gnunet-service-vpn.c:1704 +#: src/vpn/gnunet-service-vpn.c:1721 #, fuzzy msgid "# ICMP packets received from mesh" msgstr "# các đáp ứng lỗ hổng được gửi cho trình/máy khách" -#: src/vpn/gnunet-service-vpn.c:2045 +#: src/vpn/gnunet-service-vpn.c:2062 #, fuzzy msgid "# UDP packets received from mesh" msgstr "# các đáp ứng lỗ hổng được gửi cho trình/máy khách" -#: src/vpn/gnunet-service-vpn.c:2203 +#: src/vpn/gnunet-service-vpn.c:2220 #, fuzzy msgid "# TCP packets received from mesh" msgstr "# các đáp ứng lỗ hổng được gửi cho trình/máy khách" -#: src/vpn/gnunet-service-vpn.c:2354 +#: src/vpn/gnunet-service-vpn.c:2371 msgid "Failed to find unallocated IPv4 address in VPN's range\n" msgstr "" -#: src/vpn/gnunet-service-vpn.c:2409 +#: src/vpn/gnunet-service-vpn.c:2426 msgid "Failed to find unallocated IPv6 address in VPN's range\n" msgstr "" -#: src/vpn/gnunet-service-vpn.c:2448 src/vpn/gnunet-service-vpn.c:2661 +#: src/vpn/gnunet-service-vpn.c:2465 src/vpn/gnunet-service-vpn.c:2678 #, fuzzy msgid "# Active destinations" msgstr "# các kết nối dht" -#: src/vpn/gnunet-service-vpn.c:2734 +#: src/vpn/gnunet-service-vpn.c:2751 msgid "Failed to allocate IP address for new destination\n" msgstr "" -#: src/vpn/gnunet-service-vpn.c:3141 +#: src/vpn/gnunet-service-vpn.c:3138 msgid "IPv6 support disabled as this system does not support IPv6\n" msgstr "" -#: src/vpn/gnunet-service-vpn.c:3173 +#: src/vpn/gnunet-service-vpn.c:3170 msgid "IPv4 support disabled as this system does not support IPv4\n" msgstr "" @@ -6057,113 +6751,533 @@ msgstr "" msgid "Error creating tunnel\n" msgstr "Hoàn thành tạo khoá.\n" -#: src/vpn/gnunet-vpn.c:195 src/vpn/gnunet-vpn.c:226 +#: src/vpn/gnunet-vpn.c:194 src/vpn/gnunet-vpn.c:225 #, fuzzy, c-format msgid "Option `%s' makes no sense with option `%s'.\n" msgstr "Tùy chọn « %s » không có nghĩa khi không có tùy chọn « %s ».\n" -#: src/vpn/gnunet-vpn.c:208 +#: src/vpn/gnunet-vpn.c:207 #, fuzzy, c-format msgid "Option `%s' or `%s' is required.\n" msgstr "Bị từ chối đặt tùy chọn « %s » trong phần « %s » thành « %s ».\n" -#: src/vpn/gnunet-vpn.c:220 +#: src/vpn/gnunet-vpn.c:219 #, fuzzy, c-format msgid "Option `%s' or `%s' is required when using option `%s'.\n" msgstr "Tùy chọn « %s » cần thiết khi dùng tùy chọn « %s ».\n" -#: src/vpn/gnunet-vpn.c:238 +#: src/vpn/gnunet-vpn.c:237 #, fuzzy, c-format msgid "`%s' is not a valid peer identifier.\n" msgstr "« %s » không sẵn sàng.\n" -#: src/vpn/gnunet-vpn.c:260 +#: src/vpn/gnunet-vpn.c:259 #, fuzzy, c-format msgid "`%s' is not a valid IP address.\n" msgstr "« %s » không sẵn sàng.\n" -#: src/vpn/gnunet-vpn.c:296 +#: src/vpn/gnunet-vpn.c:295 msgid "request that result should be an IPv4 address" msgstr "" -#: src/vpn/gnunet-vpn.c:299 +#: src/vpn/gnunet-vpn.c:298 msgid "request that result should be an IPv6 address" msgstr "" -#: src/vpn/gnunet-vpn.c:302 +#: src/vpn/gnunet-vpn.c:301 msgid "print IP address only after mesh tunnel has been created" msgstr "" -#: src/vpn/gnunet-vpn.c:305 +#: src/vpn/gnunet-vpn.c:304 msgid "how long should the mapping be valid for new tunnels?" msgstr "" -#: src/vpn/gnunet-vpn.c:308 +#: src/vpn/gnunet-vpn.c:307 msgid "destination IP for the tunnel" msgstr "" -#: src/vpn/gnunet-vpn.c:311 +#: src/vpn/gnunet-vpn.c:310 msgid "peer offering the service we would like to access" msgstr "" -#: src/vpn/gnunet-vpn.c:314 +#: src/vpn/gnunet-vpn.c:313 msgid "name of the service we would like to access" msgstr "" -#: src/vpn/gnunet-vpn.c:317 +#: src/vpn/gnunet-vpn.c:316 #, fuzzy msgid "service is offered via TCP" msgstr "# các byte đã nhận qua TCP" -#: src/vpn/gnunet-vpn.c:320 +#: src/vpn/gnunet-vpn.c:319 #, fuzzy msgid "service is offered via UDP" msgstr "# các byte đã nhận qua UDP" -#: src/vpn/gnunet-vpn.c:329 +#: src/vpn/gnunet-vpn.c:331 msgid "Setup tunnels via VPN." msgstr "" -#: src/include/gnunet_common.h:497 src/include/gnunet_common.h:502 -#: src/include/gnunet_common.h:508 +#: src/include/gnunet_common.h:579 src/include/gnunet_common.h:584 +#: src/include/gnunet_common.h:590 #, fuzzy, c-format msgid "Assertion failed at %s:%d.\n" msgstr "Lỗi nội bộ : khẳng định không thành công tại %s:%d.\n" -#: src/include/gnunet_common.h:518 +#: src/include/gnunet_common.h:600 #, fuzzy, c-format msgid "External protocol violation detected at %s:%d.\n" msgstr "Lỗi nội bộ : khẳng định không thành công tại %s:%d.\n" -#: src/include/gnunet_common.h:539 src/include/gnunet_common.h:546 +#: src/include/gnunet_common.h:621 src/include/gnunet_common.h:628 #, c-format msgid "`%s' failed on file `%s' at %s:%d with error: %s\n" msgstr "« %s » thất bại ở tập tin « %s » tại %s:%d với lỗi: %s\n" -#~ msgid "Received malformed message via %s. Ignored.\n" -#~ msgstr "Nhận được thông báo dạng sai qua %s. Bị bỏ qua.\n" +#, fuzzy +#~ msgid "session identifier" +#~ msgstr "# các phiên chạy được thiết lập" + +#, fuzzy +#~ msgid "Mesh service could not access hostkey. Exiting.\n" +#~ msgstr "Không thể truy cập đến thông tin về không gian tên.\n" -#~ msgid "SMTP filter string to invalid, lacks ': '\n" -#~ msgstr "Chuỗi lọc vào SMTP không hợp lệ, còn thiếu « : »\n" +#, fuzzy +#~ msgid "" +#~ "provide inthe 'struct GNUNET_TRANSPORT_PeerIterateContextformation about " +#~ "all tunnels (continuously)" +#~ msgstr "In ra thông tin về các đồng đẳng GNUnet." -#~ msgid "SMTP filter string to long, capped to `%s'\n" -#~ msgstr "Chuỗi lọc vào SMTP quá dài, tối đa « %s »\n" +#, fuzzy +#~ msgid "Connected to %s\n" +#~ msgstr "« %s » được kết nối tới « %s ».\n" -#~ msgid "SMTP: `%s' failed: %s.\n" -#~ msgstr "SMTP: « %s » bị lỗi: %s\n" +#, fuzzy +#~ msgid "list information for all peers" +#~ msgstr "In ra thông tin về các đồng đẳng GNUnet." + +#, fuzzy +#~ msgid "No `%s' specified in `%s' configuration, will not bootstrap.\n" +#~ msgstr "" +#~ "Chưa ghi rõ địa chỉ URL của danh sách các máy nên không nạp và khởi " +#~ "động.\n" + +#, fuzzy +#~ msgid "" +#~ "No `%s' specified in `%s' configuration, cannot load hostlists from " +#~ "file.\n" +#~ msgstr "" +#~ "Chưa ghi rõ địa chỉ URL của danh sách các máy nên không nạp và khởi " +#~ "động.\n" + +#, fuzzy +#~ msgid "" +#~ "No `%s' specified in `%s' configuration, cannot save hostlists to file.\n" +#~ msgstr "" +#~ "Chưa ghi rõ địa chỉ URL của danh sách các máy nên không nạp và khởi " +#~ "động.\n" + +#, fuzzy +#~ msgid "Malformed %s `%s' given in configuration!\n" +#~ msgstr "Lỗi lưu cấu hình." + +#, fuzzy +#~ msgid "Got %u bytes from helper `%s'\n" +#~ msgstr "Nhận yêu cầu định tuyến\n" + +#, fuzzy +#~ msgid "Starting HELPER process `%s'\n" +#~ msgstr "Đang bắt đầu tài về « %s »\n" + +#, fuzzy +#~ msgid "Asked to start service `%s' within %llu ms\n" +#~ msgstr "« %s »: Chưa nhận thông báo sau %llu miligiây.\n" + +#, fuzzy +#~ msgid "Configuration file `%s' for service `%s' not valid: %s\n" +#~ msgstr "Tập tin cấu hình « %s » đã được ghi.\n" + +#, fuzzy +#~ msgid "Could not transmit confirmation receipt\n" +#~ msgstr "Không thể truy cập đến thông tin về không gian tên.\n" + +#, fuzzy +#~ msgid "Unknown message type: '%u'\n" +#~ msgstr "\tKhông rõ miền tên « %s »\n" + +#, fuzzy +#~ msgid "Configuration option `%s' in section `%s' missing\n" +#~ msgstr "" +#~ "Giá trị cấu hình « %s » cho « %s » trong phần « %s » nên là con số\n" + +#, fuzzy +#~ msgid "Failed to access chat home directory `%s'\n" +#~ msgstr "Lỗi truy cập đến thư mục nhà GNUnet « %s »\n" + +#, fuzzy +#~ msgid "Failed to create/open key in file `%s'\n" +#~ msgstr "Lỗi mở tập tin ghi sự kiện « %s »: %s\n" + +#, fuzzy +#~ msgid "Could not serialize metadata\n" +#~ msgstr "Không thể tạo miền tên.\n" + +#, fuzzy +#~ msgid "Failed to connect to the chat service\n" +#~ msgstr "Lỗi kết nối đến gnunetd.\n" + +#~ msgid "anonymous" +#~ msgstr "nặc danh" + +#, fuzzy +#~ msgid "(%s) `%s' said: %s\n" +#~ msgstr "« %s » nói: %s\n" + +#, fuzzy +#~ msgid "(%s) `%s' said to you: %s\n" +#~ msgstr "« %s » nói cho bạn: %s\n" + +#, fuzzy +#~ msgid "(%s) `%s' said for sure: %s\n" +#~ msgstr "« %s » nói thật: %s\n" + +#, fuzzy +#~ msgid "(%s) `%s' said to you for sure: %s\n" +#~ msgstr "« %s » nói thật cho bạn: %s\n" + +#, fuzzy +#~ msgid "(%s) `%s' was confirmed that you received: %s\n" +#~ msgstr "« %s » xác nhận bạn đã nhận được: %s\n" + +#, fuzzy +#~ msgid "(%s) `%s' was confirmed that you and only you received: %s\n" +#~ msgstr "« %s » xác nhận mà chỉ bạn đã nhận được: %s\n" + +#, fuzzy +#~ msgid "(%s) `%s' was confirmed that you received from him or her: %s\n" +#~ msgstr "« %s » xác nhận mà bạn đã nhận được từ họ : %s\n" + +#, fuzzy +#~ msgid "" +#~ "(%s) `%s' was confirmed that you and only you received from him or her: " +#~ "%s\n" +#~ msgstr "« %s » xác nhận mà chỉ bạn đa nhận được từ họ : %s\n" + +#, fuzzy +#~ msgid "(%s) `%s' said off the record: %s\n" +#~ msgstr "« %s » nói không chính thức: %s\n" + +#, fuzzy +#~ msgid "(%s) <%s> said using an unknown message type: %s\n" +#~ msgstr "<%s> đã nói bằng một kiểu tin nhẳn không rõ : %s\n" + +#~ msgid "`%s' entered the room\n" +#~ msgstr "« %s » vào phòng\n" + +#~ msgid "`%s' left the room\n" +#~ msgstr "« %s » rời phòng\n" + +#, fuzzy +#~ msgid "Could not change username\n" +#~ msgstr "Không thể tạo miền tên.\n" + +#, fuzzy +#~ msgid "Joining room `%s' as user `%s'...\n" +#~ msgstr "Đã vào phòng « %s » là người dùng « %s ».\n" + +#, fuzzy +#~ msgid "Changed username to `%s'\n" +#~ msgstr "Đã thay đổi tên người dùng thành « %s ».\n" + +#~ msgid "Users in room `%s': " +#~ msgstr "Người dùng trong phòng « %s »:" + +#~ msgid "Syntax: /msg USERNAME MESSAGE" +#~ msgstr "Cú pháp: /msg TÊN_NGƯỜI_DÙNG TIN_NHẲN" + +#~ msgid "User `%s' is currently not in the room!\n" +#~ msgstr "Người dùng « %s » hiện thời không có trong phòng này.\n" + +#, fuzzy +#~ msgid "Unknown command `%s'\n" +#~ msgstr "Không rõ câu lệnh « %s ».\n" + +#~ msgid "" +#~ "Use `/join #roomname' to join a chat room. Joining a room will cause you " +#~ "to leave the current room" +#~ msgstr "" +#~ "Gõ chuỗi « /join #tên_phòng » để vào một phòng trò chuyện nào đó (việc " +#~ "này cũng gây ra bạn ra khỏi phòng hiện tại)" + +#~ msgid "" +#~ "Use `/nick nickname' to change your nickname. This will cause you to " +#~ "leave the current room and immediately rejoin it with the new name." +#~ msgstr "" +#~ "Gõ chuỗi « /nick tên_hiệu » để thay đổi tên hiệu của mình (việc này cũng " +#~ "gây ra bạn ra khỏi phòng hiện tại, sau đó vào lại ngay với tên mới)" + +#~ msgid "" +#~ "Use `/msg nickname message' to send a private message to the specified " +#~ "user" +#~ msgstr "" +#~ "Gõ chuỗi « /msg tên_hiệu tin_nhẳn » để gửi một tin nhẳn riêng cho người " +#~ "dùng có tên đó" + +#~ msgid "The `/notice' command is an alias for `/msg'" +#~ msgstr "Lệnh « /notice » là một biệt hiệu cho « /msg »" + +#~ msgid "The `/query' command is an alias for `/msg'" +#~ msgstr "Lệnh « /query » là một biệt hiệu cho « /msg »" + +#, fuzzy +#~ msgid "Use `/sig message' to send a signed public message" +#~ msgstr "" +#~ "Gõ chuỗi « /msg tên_hiệu tin_nhẳn » để gửi một tin nhẳn riêng cho người " +#~ "dùng có tên đó" + +#, fuzzy +#~ msgid "The `/anon' command is an alias for `/anonymous'" +#~ msgstr "Lệnh « /notice » là một biệt hiệu cho « /msg »" + +#~ msgid "Use `/quit' to terminate gnunet-chat" +#~ msgstr "Gõ chuỗi « /quit » để thoát khỏi trình gnunet-chat" + +#~ msgid "The `/leave' command is an alias for `/quit'" +#~ msgstr "Lệnh « /leave » là một biệt hiệu cho « /quit »" + +#~ msgid "Use `/names' to list all of the current members in the chat room" +#~ msgstr "" +#~ "Gõ chuỗi « /names » để liệt kê tất cả các thành viên hiện thời trong " +#~ "phòng trò chuyện đó" + +#~ msgid "Use `/help command' to get help for a specific command" +#~ msgstr "Gõ chuỗi « /help LỆNH » để xem trợ giúp về lệnh đó" + +#~ msgid "You must specify a nickname\n" +#~ msgstr "Phải ghi rõ tên hiệu\n" + +#~ msgid "Failed to join room `%s'\n" +#~ msgstr "Lỗi vào phòng « %s »\n" + +#~ msgid "set the chat room to join" +#~ msgstr "đặt phòng trò chuyện cần vào" + +#~ msgid "Join a chat on GNUnet." +#~ msgstr "Vào phòng trò chuyện trên GNUnet." + +#, fuzzy +#~ msgid "Failed to queue a message notification\n" +#~ msgstr "Lỗi lưu cấu hình." + +#, fuzzy +#~ msgid "Failed to queue a join notification\n" +#~ msgstr "Lỗi lưu cấu hình." + +#, fuzzy +#~ msgid "Failed to queue a confirmation receipt\n" +#~ msgstr "Lỗi lưu cấu hình." + +#, fuzzy +#~ msgid "Failed to queue a leave notification\n" +#~ msgstr "Lỗi lưu cấu hình." + +#, fuzzy +#~ msgid "Connected to %s service!\n" +#~ msgstr "« %s » được kết nối tới « %s ».\n" + +#, fuzzy +#~ msgid "Configuration fails to specify `%s' in section `%s'\n" +#~ msgstr "Tập tin cấu hình « %s » đã được ghi.\n" + +#, fuzzy +#~ msgid "Failed to start daemon: %s\n" +#~ msgstr "Lỗi bắt đầu thu thập.\n" + +#, fuzzy +#~ msgid "Configuration fails to specify `%s', assuming default value." +#~ msgstr "Tập tin cấu hình « %s » đã được ghi.\n" + +#, fuzzy +#~ msgid "Key file `%s' for private zone does not exist!\n" +#~ msgstr "đặt số trình nền cần khởi chạy" + +#, fuzzy +#~ msgid "Option `%s' not specified in configuration section `%s'\n" +#~ msgstr "" +#~ "Đặc tả mạng dạng sai trong cấu hình phần « %s » cho mục nhập « %s »: %s\n" + +#, fuzzy +#~ msgid "Peer is lacking HOSTKEY configuration setting.\n" +#~ msgstr "Lưu cấu hình ngay bây giờ không?" + +#, fuzzy +#~ msgid "Could not access hostkey.\n" +#~ msgstr "Không thể truy cập đến tập tin gnunet-directory « %s »\n" + +#, fuzzy +#~ msgid "`scp' did not complete cleanly.\n" +#~ msgstr "« %s » không phải được kết nối tới đồng đẳng nào.\n" + +#, fuzzy +#~ msgid "Failed to create pipe for `gnunet-peerinfo' process.\n" +#~ msgstr "Lỗi bắt đầu thu thập.\n" + +#, fuzzy +#~ msgid "Failed to create pipe for `ssh' process.\n" +#~ msgstr "Lỗi tạo thư mục tạm thời." + +#, fuzzy +#~ msgid "Could not start `%s' process to create hostkey.\n" +#~ msgstr "Lỗi bắt đầu thu thập.\n" + +#, fuzzy +#~ msgid "Failed to start `gnunet-peerinfo' process.\n" +#~ msgstr "Lỗi bắt đầu thu thập.\n" + +#, fuzzy +#~ msgid "Failed to start `ssh' process.\n" +#~ msgstr "Lỗi bắt đầu thu thập.\n" + +#, fuzzy +#~ msgid "Error reading from gnunet-peerinfo: %s\n" +#~ msgstr "Gặp lỗi khi đọc thông tin từ gnunetd.\n" + +#, fuzzy +#~ msgid "Malformed output from gnunet-peerinfo!\n" +#~ msgstr "Gặp lỗi khi đọc thông tin từ gnunetd.\n" + +#, fuzzy +#~ msgid "Failed to get hostkey!\n" +#~ msgstr "Lỗi lấy thông kê về truyền tải.\n" + +#, fuzzy +#~ msgid "Could not start `%s' process to start GNUnet.\n" +#~ msgstr "Không thể tạo miền tên.\n" + +#, fuzzy +#~ msgid "Failed to start `gnunet-arm' process.\n" +#~ msgstr "Lỗi dừng chạy gnunet-auto-share.\n" + +#, fuzzy +#~ msgid "shutdown (either `gnunet-arm' or `ssh') did not complete cleanly.\n" +#~ msgstr "« %s » không phải được kết nối tới đồng đẳng nào.\n" + +#, fuzzy +#~ msgid "Starting service %s for peer `%4s'\n" +#~ msgstr "Đang bắt đầu tài về « %s »\n" + +#, fuzzy +#~ msgid "Could not start `%s' process to copy configuration directory.\n" +#~ msgstr "Không thể truy cập đến thông tin về không gian tên.\n" + +#, fuzzy +#~ msgid "Terminating peer `%4s'\n" +#~ msgstr "Không đủ quyền cho « %s ».\n" + +#, fuzzy +#~ msgid "Setting d->dead on peer `%4s'\n" +#~ msgstr "Đang bắt đầu tài lên « %s ».\n" + +#, fuzzy +#~ msgid "Failed to write new configuration to disk." +#~ msgstr "Lỗi lưu cấu hình." + +#, fuzzy +#~ msgid "Could not start `%s' process to copy configuration file.\n" +#~ msgstr "Không tìm thấy phương pháp « %s%s » trong thư viện « %s ».\n" + +#, fuzzy +#~ msgid "Failed to copy new configuration to remote machine." +#~ msgstr "Lỗi lưu cấu hình." + +#, fuzzy +#~ msgid "Peers failed to connect" +#~ msgstr "Không kết nối được đến trình nền gnunetd." + +#, fuzzy +#~ msgid "Failed to connect to core service of first peer!\n" +#~ msgstr "Lỗi nạp dịch vụ sqstore. Hãy kiểm tra lại cấu hình.\n" + +#, fuzzy +#~ msgid "Invalid value `%s' for option `%s' in section `%s': expected float\n" +#~ msgstr "" +#~ "Giá trị cấu hình « %s » cho « %s » trong phần « %s » nên là con số\n" -#~ msgid "No email-address specified, can not start SMTP transport.\n" +#, fuzzy +#~ msgid "" +#~ "Invalid value `%s' for option `%s' in section `%s': got %f, needed value " +#~ "greater than 0\n" +#~ msgstr "" +#~ "Giá trị cấu hình « %s » cho « %s » trong phần « %s » nên là con số\n" + +#, fuzzy +#~ msgid "" +#~ "No `%s' specified in peer configuration in section `%s', cannot copy " +#~ "friends file!\n" +#~ msgstr "" +#~ "Đặc tả mạng dạng sai trong cấu hình phần « %s » cho mục nhập « %s »: %s\n" + +#, fuzzy +#~ msgid "Unknown topology specification, can't connect peers!\n" +#~ msgstr "Lỗi cú pháp trong sự xác định địa hình học, đang bỏ qua các byte.\n" + +#, fuzzy +#~ msgid "Could not read hostkeys file `%s'!\n" +#~ msgstr "Không thể đọc danh sách bạn bè « %s »\n" + +#, fuzzy +#~ msgid "Could not create configuration for peer number %u on `%s'!\n" +#~ msgstr "Không thể truy cập đến thông tin về không gian tên.\n" + +#, fuzzy +#~ msgid "Option `%s' in section `%s' not specified!\n" +#~ msgstr "Bị từ chối đặt tùy chọn « %s » trong phần « %s » thành « %s ».\n" + +#, fuzzy +#~ msgid "Failed to find option %s in section %s!\n" +#~ msgstr "Lỗi đóng kết đến cổng %s %d.\n" + +#, fuzzy +#~ msgid "Invalid configuration option `%s' in section `%s'\n" #~ msgstr "" -#~ "Chưa ghi rõ địa chỉ thư điện tử nên không tạo được truyền tải SMTP.\n" +#~ "Giá trị cấu hình « %s » cho « %s » trong phần « %s » nên là con số\n" + +#, fuzzy +#~ msgid "Missing configuration option `%s' in section `%s'\n" +#~ msgstr "" +#~ "Giá trị cấu hình « %s » cho « %s » trong phần « %s » nên là con số\n" + +#, fuzzy +#~ msgid "internal error" +#~ msgstr "Lỗi VR." + +#, fuzzy +#~ msgid "Could not create namespace `%s'\n" +#~ msgstr "Không thể tạo miền tên.\n" + +#, fuzzy +#~ msgid "Stored zonekey for zone `%s' in file `%s'\n" +#~ msgstr "Lỗi mở tập tin ghi sự kiện « %s »: %s\n" + +#, fuzzy +#~ msgid "Namestore removed record successfully" +#~ msgstr "Dịch vụ GNUnet đã được cài đặt.\n" -#~ msgid "# bytes received via SMTP" -#~ msgstr "# các byte đã nhận qua SMTP" +#, fuzzy +#~ msgid "Could not read hostkeys file, specify hostkey file with -H!\n" +#~ msgstr "Không thể đọc danh sách bạn bè « %s »\n" + +#, fuzzy +#~ msgid "Could not open hostkeys file: %s\n" +#~ msgstr "Không thể đọc danh sách bạn bè « %s »\n" -#~ msgid "# bytes sent via SMTP" -#~ msgstr "# các byte đã gửi qua SMTP" +#, fuzzy +#~ msgid "access (%s, X_OK) failed: %s\n" +#~ msgstr "SMTP: « %s » bị lỗi: %s\n" -#~ msgid "# bytes dropped by SMTP (outgoing)" -#~ msgstr "# các byte loại đi bởi SMTP (đi ra)" +#, fuzzy +#~ msgid "stat (%s) failed: %s\n" +#~ msgstr "SMTP: « %s » bị lỗi: %s\n" #, fuzzy #~ msgid "# Peers connected" @@ -6206,10 +7320,6 @@ msgstr "« %s » thất bại ở tập tin « %s » tại %s:%d với lỗi: %s #~ msgid "Finished copying all blacklist files!\n" #~ msgstr "Không thể đọc danh sách bạn bè « %s »\n" -#, fuzzy -#~ msgid "Offering HELLO of peer %s to peer %s\n" -#~ msgstr "đang kết nối đồng đẳng %s:%d tới đồng đẳng %s:%d\n" - #, fuzzy #~ msgid "Failed during blacklist file copying!\n" #~ msgstr "Lỗi đọc danh sách bạn bè từ « %s »\n" @@ -6238,10 +7348,6 @@ msgstr "« %s » thất bại ở tập tin « %s » tại %s:%d với lỗi: %s #~ msgid "# unexpected CONNECT_ACK messages" #~ msgstr "gửi ĐẾM thông báo" -#, fuzzy -#~ msgid "# wlan session timeouts" -#~ msgstr "# các khoá phiên chạy được chấp nhận" - #, fuzzy #~ msgid "# wlan session created" #~ msgstr "# các khoá phiên chạy được chấp nhận" @@ -6289,10 +7395,6 @@ msgstr "« %s » thất bại ở tập tin « %s » tại %s:%d với lỗi: %s #~ msgid "Failed to connect to statistics service!\n" #~ msgstr "Lỗi kết nối đến gnunetd.\n" -#, fuzzy -#~ msgid "Failed to send to `%s': %s\n" -#~ msgstr "Lỗi mở tập tin ghi sự kiện « %s »: %s\n" - #, fuzzy #~ msgid "Could not access file: %s\n" #~ msgstr "Không thể truy cập đến « %s »: %s\n" @@ -6329,9 +7431,6 @@ msgstr "« %s » thất bại ở tập tin « %s » tại %s:%d với lỗi: %s #~ msgid "be verbose" #~ msgstr "xuất chi tiết" -#~ msgid "use configuration file FILENAME" -#~ msgstr "dùng tập tin cấu hình TÊN_TẬP_TIN" - #, fuzzy #~ msgid "Failed to stop service `%s'!\n" #~ msgstr "Lỗi vào phòng « %s »\n" @@ -6348,18 +7447,10 @@ msgstr "« %s » thất bại ở tập tin « %s » tại %s:%d với lỗi: %s #~ msgid "Service `%s' stopped\n" #~ msgstr "Dịch vụ đã bị xoá.\n" -#, fuzzy -#~ msgid "Unable to start service `%s': %s\n" -#~ msgstr "Không thể lưu tập tin cấu hình « %s »:" - #, fuzzy #~ msgid "Unable to accept connection for service `%s': %s\n" #~ msgstr "Không thể lưu tập tin cấu hình « %s »:" -#, fuzzy -#~ msgid "Peer `%s' plugin: `%s' address `%s'\n" -#~ msgstr "Đồng đẳng « %s » có mức tin cậy %8u và địa chỉ « %s »\n" - #~ msgid "KiB" #~ msgstr "KiB" @@ -6713,9 +7804,6 @@ msgstr "« %s » thất bại ở tập tin « %s » tại %s:%d với lỗi: %s #~ msgid "Back" #~ msgstr "Lùi" -#~ msgid "Exit" -#~ msgstr "Thoát" - #~ msgid "Up" #~ msgstr "Lên" @@ -6750,9 +7838,6 @@ msgstr "« %s » thất bại ở tập tin « %s » tại %s:%d với lỗi: %s #~ msgid "install GNUnet as Windows service" #~ msgstr "cài đặt GNUnet như là một dịch vụ Windows" -#~ msgid "increase the maximum number of TCP/IP connections" -#~ msgstr "tăng sổ tối đa các kết nối TCP/IP" - #~ msgid "display a file's hash value" #~ msgstr "hiển thị giá trị tổng kiểm của tập tin" @@ -7075,9 +8160,6 @@ msgstr "« %s » thất bại ở tập tin « %s » tại %s:%d với lỗi: %s #~ msgid "Real-time delay violation (%llu ms) at %s:%u\n" #~ msgstr "Xâm phạm khoảng đợi thời gian thực (%llu miligiây) tại %s:%u\n" -#~ msgid "`%s' failed with error code %d: %s\n" -#~ msgstr "« %s » thất bại với mã lỗi %d: %s\n" - #~ msgid "Deadlock due to `%s'.\n" #~ msgstr "Bế tắc do « %s ».\n" @@ -7143,9 +8225,6 @@ msgstr "« %s » thất bại ở tập tin « %s » tại %s:%d với lỗi: %s #~ msgid "output in gnuplot format" #~ msgstr "kết xuất theo định dạng gnuplot" -#~ msgid "number of iterations" -#~ msgstr "số lần lặp lại" - #~ msgid "number of messages to use per iteration" #~ msgstr "số tin nhắn cần dùng mỗi lần lặp" @@ -7470,9 +8549,6 @@ msgstr "« %s » thất bại ở tập tin « %s » tại %s:%d với lỗi: %s #~ msgstr "" #~ "Gặp kiểu không rõ trong thông báo nhúng từ « %s »: %u (kích cỡ : %u)\n" -#~ msgid "# sessions established" -#~ msgstr "# các phiên chạy được thiết lập" - #~ msgid "automate creation of a namespace by starting a collection" #~ msgstr "tự động tạo một không gian tên bằng cách bắt đầu một thu thập" @@ -7589,9 +8665,6 @@ msgstr "« %s » thất bại ở tập tin « %s » tại %s:%d với lỗi: %s #~ "đừng dùng libextractor để thêm các tham chiếu bổ sung vào mục nhập thư " #~ "mục và/hay tập tin công bố" -#~ msgid "Automatically share a directory." -#~ msgstr "Tự động chia sẻ một thư mục." - #~ msgid "Unknown keyword type `%s' in metadata configuration\n" #~ msgstr "Không rõ kiểu từ khoá « %s » trong cấu hình siêu dữ liệu\n" @@ -8340,9 +9413,6 @@ msgstr "« %s » thất bại ở tập tin « %s » tại %s:%d với lỗi: %s #~ msgid "repeat each test X times" #~ msgstr "lặp lại mỗi hàm thử X lần" -#~ msgid "Testing transport(s) %s\n" -#~ msgstr "Đang thử nghiệm (các) truyền tải %s\n" - #~ msgid "Available transport(s): %s\n" #~ msgstr "Các truyền tải sẵn sàng: %s\n" @@ -9520,9 +10590,6 @@ msgstr "« %s » thất bại ở tập tin « %s » tại %s:%d với lỗi: %s #~ msgid "This is equivalent to the -H option. The format is IP:PORT." #~ msgstr "Đây tương đương với tùy chọn « -H ». Định dạng là « IP:CỔNG »." -#~ msgid "What is the path to the configuration file for gnunetd?" -#~ msgstr "Tập tin cấu hình gnunetd có đường dẫn nào?" - #~ msgid "This option is used when clients need to start gnunetd." #~ msgstr "Tùy chọn này dùng khi ứng dụng khách cần khởi chạy gnunetd." diff --git a/po/zh_CN.gmo b/po/zh_CN.gmo index 6db97d6..4805069 100644 Binary files a/po/zh_CN.gmo and b/po/zh_CN.gmo differ diff --git a/po/zh_CN.po b/po/zh_CN.po index b50a113..682edb2 100644 --- a/po/zh_CN.po +++ b/po/zh_CN.po @@ -7,7 +7,7 @@ msgid "" msgstr "" "Project-Id-Version: gnunet-0.8.1\n" "Report-Msgid-Bugs-To: gnunet-developers@mail.gnu.org\n" -"POT-Creation-Date: 2012-06-05 15:47+0200\n" +"POT-Creation-Date: 2013-02-05 19:22+0100\n" "PO-Revision-Date: 2011-07-09 12:12+0800\n" "Last-Translator: Wylmer Wang \n" "Language-Team: Chinese (simplified) \n" @@ -16,264 +16,213 @@ msgstr "" "Content-Type: text/plain; charset=utf-8\n" "Content-Transfer-Encoding: 8bit\n" -#: src/arm/arm_api.c:165 +#: src/arm/arm_api.c:162 msgid "Failed to transmit shutdown request to client.\n" msgstr "" -#: src/arm/arm_api.c:349 -#, fuzzy, c-format -msgid "Configuration failes to specify option `%s' in section `%s'!\n" -msgstr "配置不满足配置规范文件“%s”的约束!\n" - -#: src/arm/arm_api.c:363 -#, fuzzy, c-format -msgid "Configuration fails to specify option `%s' in section `%s'!\n" -msgstr "配置不满足配置规范文件“%s”的约束!\n" - -#: src/arm/arm_api.c:432 -#, c-format -msgid "Error receiving response to `%s' request from ARM for service `%s'\n" -msgstr "" - -#: src/arm/arm_api.c:485 -#, c-format -msgid "Requesting start of service `%s'.\n" -msgstr "" - -#: src/arm/arm_api.c:486 -#, c-format -msgid "Requesting termination of service `%s'.\n" -msgstr "" - -#: src/arm/arm_api.c:507 -#, c-format -msgid "Error while trying to transmit request to start `%s' to ARM\n" -msgstr "" - -#: src/arm/arm_api.c:508 -#, c-format -msgid "Error while trying to transmit request to stop `%s' to ARM\n" -msgstr "" - -#: src/arm/arm_api.c:540 -#, c-format -msgid "Asked to start service `%s' within %llu ms\n" -msgstr "" - -#: src/arm/arm_api.c:612 -#, c-format -msgid "Stopping service `%s' within %llu ms\n" -msgstr "" - -#: src/arm/gnunet-arm.c:159 +#: src/arm/gnunet-arm.c:166 #, fuzzy, c-format msgid "Service `%s' is unknown to ARM.\n" msgstr "服务已删除。\n" -#: src/arm/gnunet-arm.c:164 +#: src/arm/gnunet-arm.c:171 #, fuzzy, c-format msgid "Service `%s' has been stopped.\n" msgstr "服务已删除。\n" -#: src/arm/gnunet-arm.c:167 +#: src/arm/gnunet-arm.c:174 #, fuzzy, c-format msgid "Service `%s' was already running.\n" msgstr "服务已删除。\n" -#: src/arm/gnunet-arm.c:172 +#: src/arm/gnunet-arm.c:179 #, fuzzy, c-format msgid "Service `%s' has been started.\n" msgstr "服务已删除。\n" -#: src/arm/gnunet-arm.c:175 +#: src/arm/gnunet-arm.c:182 #, fuzzy, c-format msgid "Service `%s' was already being stopped.\n" msgstr "服务已删除。\n" -#: src/arm/gnunet-arm.c:179 +#: src/arm/gnunet-arm.c:186 #, fuzzy, c-format msgid "Service `%s' was already not running.\n" msgstr "服务已删除。\n" -#: src/arm/gnunet-arm.c:183 +#: src/arm/gnunet-arm.c:190 msgid "Request ignored as ARM is shutting down.\n" msgstr "" -#: src/arm/gnunet-arm.c:187 +#: src/arm/gnunet-arm.c:194 msgid "Error communicating with ARM service.\n" msgstr "" -#: src/arm/gnunet-arm.c:191 +#: src/arm/gnunet-arm.c:198 msgid "Timeout communicating with ARM service.\n" msgstr "" -#: src/arm/gnunet-arm.c:195 +#: src/arm/gnunet-arm.c:202 msgid "Operation failed.\n" msgstr "" -#: src/arm/gnunet-arm.c:199 +#: src/arm/gnunet-arm.c:206 msgid "Unknown response code from ARM.\n" msgstr "" -#: src/arm/gnunet-arm.c:222 +#: src/arm/gnunet-arm.c:229 #, fuzzy msgid "Error communicating with ARM. ARM not running?\n" msgstr "连接 %s:%u 出错。守护程序在运行吗?\n" -#: src/arm/gnunet-arm.c:225 +#: src/arm/gnunet-arm.c:232 msgid "Running services:\n" msgstr "" -#: src/arm/gnunet-arm.c:249 -#, c-format -msgid "Fatal configuration error: `%s' option in section `%s' missing.\n" -msgstr "" - -#: src/arm/gnunet-arm.c:257 src/arm/gnunet-arm.c:357 src/arm/gnunet-arm.c:373 -msgid "Fatal error initializing ARM API.\n" -msgstr "" - -#: src/arm/gnunet-arm.c:280 +#: src/arm/gnunet-arm.c:253 #, fuzzy, c-format msgid "Failed to remove configuration file %s\n" msgstr "解析配置文件“%s”失败\n" -#: src/arm/gnunet-arm.c:286 +#: src/arm/gnunet-arm.c:259 #, c-format msgid "Failed to remove servicehome directory %s\n" msgstr "" -#: src/arm/gnunet-arm.c:407 +#: src/arm/gnunet-arm.c:322 src/arm/gnunet-arm.c:407 src/arm/gnunet-arm.c:424 +msgid "Fatal error initializing ARM API.\n" +msgstr "" + +#: src/arm/gnunet-arm.c:453 #, fuzzy msgid "stop all GNUnet services" msgstr "卸载 GNUnet 服务" -#: src/arm/gnunet-arm.c:409 +#: src/arm/gnunet-arm.c:455 msgid "start a particular service" msgstr "" -#: src/arm/gnunet-arm.c:411 +#: src/arm/gnunet-arm.c:457 msgid "stop a particular service" msgstr "" -#: src/arm/gnunet-arm.c:413 +#: src/arm/gnunet-arm.c:459 #, fuzzy msgid "start all GNUnet default services" msgstr "卸载 GNUnet 服务" -#: src/arm/gnunet-arm.c:416 +#: src/arm/gnunet-arm.c:462 #, fuzzy msgid "stop and start all GNUnet default services" msgstr "卸载 GNUnet 服务" -#: src/arm/gnunet-arm.c:419 +#: src/arm/gnunet-arm.c:465 msgid "delete config file and directory on exit" msgstr "" -#: src/arm/gnunet-arm.c:421 +#: src/arm/gnunet-arm.c:467 msgid "don't print status messages" msgstr "" -#: src/arm/gnunet-arm.c:424 +#: src/arm/gnunet-arm.c:470 #, fuzzy -msgid "timeout for completing current operation" +msgid "timeout in MSECS milliseconds for completing current operation" msgstr "等待一次迭代完成的时间(毫秒)" -#: src/arm/gnunet-arm.c:426 -msgid "List currently running services" +#: src/arm/gnunet-arm.c:472 +msgid "list currently running services" +msgstr "" + +#: src/arm/gnunet-arm.c:474 +msgid "don't let gnunet-service-arm inherit standard output" +msgstr "" + +#: src/arm/gnunet-arm.c:476 +msgid "don't let gnunet-service-arm inherit standard error" msgstr "" -#: src/arm/gnunet-arm.c:437 +#: src/arm/gnunet-arm.c:487 msgid "Control services and the Automated Restart Manager (ARM)" msgstr "" -#: src/arm/gnunet-service-arm.c:332 +#: src/arm/gnunet-service-arm.c:345 #, fuzzy, c-format msgid "Failed to start service `%s'\n" msgstr "解析配置文件“%s”失败\n" -#: src/arm/gnunet-service-arm.c:335 +#: src/arm/gnunet-service-arm.c:348 #, c-format msgid "Starting service `%s'\n" msgstr "" -#: src/arm/gnunet-service-arm.c:361 +#: src/arm/gnunet-service-arm.c:374 msgid "Could not send status result to client\n" msgstr "" -#: src/arm/gnunet-service-arm.c:393 +#: src/arm/gnunet-service-arm.c:406 #, fuzzy msgid "Could not send list result to client\n" msgstr "找不到接口“%s”的一个 IP 地址。\n" -#: src/arm/gnunet-service-arm.c:523 +#: src/arm/gnunet-service-arm.c:537 #, fuzzy, c-format msgid "Unable to create socket for service `%s': %s\n" msgstr "无法创建用户账户:" -#: src/arm/gnunet-service-arm.c:545 +#: src/arm/gnunet-service-arm.c:559 #, c-format msgid "Unable to bind listening socket for service `%s' to address `%s': %s\n" msgstr "" -#: src/arm/gnunet-service-arm.c:559 +#: src/arm/gnunet-service-arm.c:573 #, c-format msgid "ARM now monitors connections to service `%s' at `%s'\n" msgstr "" -#: src/arm/gnunet-service-arm.c:667 +#: src/arm/gnunet-service-arm.c:681 #, c-format msgid "Preparing to stop `%s'\n" msgstr "" -#: src/arm/gnunet-service-arm.c:878 +#: src/arm/gnunet-service-arm.c:892 #, c-format msgid "Restarting service `%s'.\n" msgstr "" -#: src/arm/gnunet-service-arm.c:970 +#: src/arm/gnunet-service-arm.c:985 msgid "exit" msgstr "" -#: src/arm/gnunet-service-arm.c:975 +#: src/arm/gnunet-service-arm.c:990 msgid "signal" msgstr "" -#: src/arm/gnunet-service-arm.c:980 +#: src/arm/gnunet-service-arm.c:995 #, fuzzy msgid "unknown" msgstr "未知错误" -#: src/arm/gnunet-service-arm.c:986 +#: src/arm/gnunet-service-arm.c:1001 #, fuzzy, c-format -msgid "Service `%s' took %llu ms to terminate\n" +msgid "Service `%s' took %s to terminate\n" msgstr "服务已删除。\n" -#: src/arm/gnunet-service-arm.c:1021 +#: src/arm/gnunet-service-arm.c:1036 #, c-format msgid "Service `%s' terminated with status %s/%d, will restart in %llu ms\n" msgstr "" -#: src/arm/gnunet-service-arm.c:1127 -#, fuzzy, c-format -msgid "Configuration file `%s' for service `%s' not valid: %s\n" -msgstr "配置文件“%s”已写入。\n" - -#: src/arm/gnunet-service-arm.c:1129 -msgid "option missing" -msgstr "" - -#: src/arm/gnunet-service-arm.c:1213 +#: src/arm/gnunet-service-arm.c:1228 #, fuzzy, c-format msgid "Starting default services `%s'\n" msgstr "卸载 GNUnet 服务" -#: src/arm/gnunet-service-arm.c:1224 +#: src/arm/gnunet-service-arm.c:1239 #, c-format msgid "Default service `%s' not configured correctly!\n" msgstr "" -#: src/arm/gnunet-service-arm.c:1238 +#: src/arm/gnunet-service-arm.c:1253 msgid "" "No default services configured, GNUnet will not really start right now.\n" msgstr "" @@ -282,297 +231,262 @@ msgstr "" msgid "Initiating shutdown as requested by client.\n" msgstr "" -#: src/block/block.c:105 -#, fuzzy, c-format -msgid "Loading block plugin `%s'\n" -msgstr "打开日志文件“%s”失败:%s\n" - -#: src/chat/chat.c:175 -msgid "Could not transmit confirmation receipt\n" -msgstr "" - -#: src/chat/chat.c:283 -msgid "The current user must be the the first one joined\n" -msgstr "" - -#: src/chat/chat.c:412 -#, fuzzy, c-format -msgid "Unknown message type: '%u'\n" -msgstr "未知操作“%s”。\n" - -#: src/chat/chat.c:472 -#, fuzzy, c-format -msgid "Configuration option `%s' in section `%s' missing\n" -msgstr "配置文件“%s”已写入。\n" - -#: src/chat/chat.c:480 -#, fuzzy, c-format -msgid "Failed to access chat home directory `%s'\n" -msgstr "解析配置文件“%s”失败\n" - -#: src/chat/chat.c:498 -#, fuzzy, c-format -msgid "Failed to create/open key in file `%s'\n" -msgstr "打开日志文件“%s”失败:%s\n" - -#: src/chat/chat.c:559 -msgid "Could not serialize metadata\n" -msgstr "" - -#: src/chat/chat.c:674 -#, fuzzy -msgid "Failed to connect to the chat service\n" -msgstr "初始化“%s”服务失败。\n" - -#: src/chat/chat.c:680 -msgid "Undefined mandatory parameter: joinCallback\n" -msgstr "" - -#: src/chat/chat.c:686 -msgid "Undefined mandatory parameter: messageCallback\n" +#: src/ats/ats_api_performance.c:465 +#, c-format +msgid "Received %s message\n" msgstr "" -#: src/chat/chat.c:692 -msgid "Undefined mandatory parameter: memberCallback\n" +#: src/ats/ats_api_performance.c:508 +#, c-format +msgid "Received last message for %s \n" msgstr "" -#: src/chat/gnunet-chat.c:93 -msgid "Joined\n" +#: src/ats/gnunet-service-ats_addresses.c:993 +#: src/ats/gnunet-service-ats_addresses.c:1027 +#, c-format +msgid "" +"Could not load quota for network `%s': `%s', assigning default bandwidth " +"%llu\n" msgstr "" -#: src/chat/gnunet-chat.c:125 src/chat/gnunet-chat.c:133 -#: src/chat/gnunet-chat.c:213 src/chat/gnunet-chat.c:253 -#: src/chat/gnunet-chat.c:329 src/chat/gnunet-chat.c:371 -#: src/chat/gnunet-chat.c:400 src/chat/gnunet-chat.c:700 -msgid "anonymous" -msgstr "匿名" - -#: src/chat/gnunet-chat.c:144 -#, fuzzy, c-format -msgid "(%s) `%s' said: %s\n" -msgstr "“%s”说:%s\n" - -#: src/chat/gnunet-chat.c:147 src/chat/gnunet-chat.c:150 -#, fuzzy, c-format -msgid "(%s) `%s' said to you: %s\n" -msgstr "“%s”对您说:%s\n" - -#: src/chat/gnunet-chat.c:153 -#, fuzzy, c-format -msgid "(%s) `%s' said for sure: %s\n" -msgstr "“%s”对您说:%s\n" - -#: src/chat/gnunet-chat.c:156 -#, fuzzy, c-format -msgid "(%s) `%s' said to you for sure: %s\n" -msgstr "“%s”对您说:%s\n" - -#: src/chat/gnunet-chat.c:159 +#: src/ats/gnunet-service-ats_addresses.c:999 #, c-format -msgid "(%s) `%s' was confirmed that you received: %s\n" +msgid "Outbound quota configure for network `%s' is %llu\n" msgstr "" -#: src/chat/gnunet-chat.c:162 +#: src/ats/gnunet-service-ats_addresses.c:1006 #, c-format -msgid "(%s) `%s' was confirmed that you and only you received: %s\n" +msgid "" +"No outbound quota configured for network `%s', assigning default bandwidth " +"%llu\n" msgstr "" -#: src/chat/gnunet-chat.c:165 +#: src/ats/gnunet-service-ats_addresses.c:1033 #, c-format -msgid "(%s) `%s' was confirmed that you received from him or her: %s\n" +msgid "Inbound quota configured for network `%s' is %llu\n" msgstr "" -#: src/chat/gnunet-chat.c:170 +#: src/ats/gnunet-service-ats_addresses.c:1040 #, c-format msgid "" -"(%s) `%s' was confirmed that you and only you received from him or her: %s\n" +"No outbound quota configure for network `%s', assigning default bandwidth " +"%llu\n" msgstr "" -#: src/chat/gnunet-chat.c:173 -#, fuzzy, c-format -msgid "(%s) `%s' said off the record: %s\n" -msgstr "“%s”对您说:%s\n" - -#: src/chat/gnunet-chat.c:176 +#: src/ats-tool/gnunet-ats.c:141 #, c-format -msgid "(%s) <%s> said using an unknown message type: %s\n" +msgid "%u address resolutions had a timeout\n" msgstr "" -#: src/chat/gnunet-chat.c:217 +#: src/ats-tool/gnunet-ats.c:143 #, c-format -msgid "'%s' acknowledged message #%d\n" +msgid "ATS returned results for %u addresses\n" msgstr "" -#: src/chat/gnunet-chat.c:260 -#, c-format -msgid "`%s' entered the room\n" -msgstr "“%s”进入了房间\n" - -#: src/chat/gnunet-chat.c:260 +#: src/ats-tool/gnunet-ats.c:199 #, c-format -msgid "`%s' left the room\n" -msgstr "“%s”离开了房间\n" - -#: src/chat/gnunet-chat.c:321 src/chat/gnunet-chat.c:363 -#, fuzzy -msgid "Could not change username\n" -msgstr "已将用户名改为“%s”。\n" +msgid "" +"Peer `%s' plugin `%s', address `%s', `%s' bw out: %u Bytes/s, bw in %u Bytes/" +"s, %s\n" +msgstr "" -#: src/chat/gnunet-chat.c:334 src/chat/gnunet-chat.c:702 +#: src/ats-tool/gnunet-ats.c:326 #, c-format -msgid "Joining room `%s' as user `%s'...\n" +msgid "Quota for network `%11s' (in/out): %10s / %10s\n" msgstr "" -#: src/chat/gnunet-chat.c:373 +#: src/ats-tool/gnunet-ats.c:345 src/namestore/gnunet-namestore.c:610 +#: src/transport/gnunet-transport.c:813 #, fuzzy, c-format -msgid "Changed username to `%s'\n" -msgstr "已将用户名改为“%s”。\n" - -#: src/chat/gnunet-chat.c:388 -#, c-format -msgid "Users in room `%s': " -msgstr "房间“%s”中的用户:" +msgid "Service `%s' is not running\n" +msgstr "服务已删除。\n" -#: src/chat/gnunet-chat.c:434 -msgid "Syntax: /msg USERNAME MESSAGE" -msgstr "语法:/msg 用户名 消息" +#: src/ats-tool/gnunet-ats.c:355 src/transport/gnunet-transport.c:819 +#, fuzzy, c-format +msgid "Failed to parse peer identity `%s'\n" +msgstr "解析配置文件“%s”失败\n" -#: src/chat/gnunet-chat.c:443 +#: src/ats-tool/gnunet-ats.c:363 #, c-format -msgid "Unknown user `%s'. Make sure you specify its numeric suffix, if any.\n" +msgid "Please select one operation : %s or %s or %s or %s or %s\n" msgstr "" -#: src/chat/gnunet-chat.c:460 -#, c-format -msgid "User `%s' is currently not in the room!\n" -msgstr "用户“%s”当前不在房间里!\n" +#: src/ats-tool/gnunet-ats.c:379 src/ats-tool/gnunet-ats.c:398 +#: src/ats-tool/gnunet-ats.c:415 src/ats-tool/gnunet-ats.c:440 +#, fuzzy, c-format +msgid "Cannot connect to ATS service, exiting...\n" +msgstr "初始化“%s”服务失败。\n" -#: src/chat/gnunet-chat.c:513 +#: src/ats-tool/gnunet-ats.c:388 src/ats-tool/gnunet-ats.c:405 #, fuzzy, c-format -msgid "Unknown command `%s'\n" -msgstr "未知的命令“%s”。\n" +msgid "Cannot issue request to ATS service, exiting...\n" +msgstr "初始化“%s”服务失败。\n" -#: src/chat/gnunet-chat.c:524 -msgid "" -"Use `/join #roomname' to join a chat room. Joining a room will cause you to " -"leave the current room" +#: src/ats-tool/gnunet-ats.c:433 +msgid "Type required\n" msgstr "" -#: src/chat/gnunet-chat.c:528 -msgid "" -"Use `/nick nickname' to change your nickname. This will cause you to leave " -"the current room and immediately rejoin it with the new name." +#: src/ats-tool/gnunet-ats.c:490 +msgid "get list of active addresses currently used" msgstr "" -#: src/chat/gnunet-chat.c:532 -msgid "" -"Use `/msg nickname message' to send a private message to the specified user" +#: src/ats-tool/gnunet-ats.c:493 +msgid "get list of all active addresses" msgstr "" -#: src/chat/gnunet-chat.c:535 -msgid "The `/notice' command is an alias for `/msg'" -msgstr "" +#: src/ats-tool/gnunet-ats.c:496 +#, fuzzy +msgid "do not resolve IP addresses to hostnames" +msgstr "GNUnet 现在使用 IP 地址 %s。\n" -#: src/chat/gnunet-chat.c:537 -msgid "The `/query' command is an alias for `/msg'" +#: src/ats-tool/gnunet-ats.c:499 +msgid "monitor mode" msgstr "" -#: src/chat/gnunet-chat.c:539 -msgid "Use `/sig message' to send a signed public message" -msgstr "" +#: src/ats-tool/gnunet-ats.c:502 +#, fuzzy +msgid "set preference for the given peer" +msgstr "无法获取有关用户“%s”的信息:%s\n" -#: src/chat/gnunet-chat.c:542 -msgid "Use `/ack message' to require signed acknowledgment of the message" +#: src/ats-tool/gnunet-ats.c:505 +msgid "print all configured quotas" msgstr "" -#: src/chat/gnunet-chat.c:545 -msgid "Use `/anonymous message' to send a public anonymous message" +#: src/ats-tool/gnunet-ats.c:508 +msgid "peer id" msgstr "" -#: src/chat/gnunet-chat.c:547 -msgid "The `/anon' command is an alias for `/anonymous'" +#: src/ats-tool/gnunet-ats.c:511 +msgid "preference type to set: latency | bandwidth" msgstr "" -#: src/chat/gnunet-chat.c:549 -msgid "Use `/quit' to terminate gnunet-chat" +#: src/ats-tool/gnunet-ats.c:514 +msgid "preference value" msgstr "" -#: src/chat/gnunet-chat.c:551 -msgid "The `/leave' command is an alias for `/quit'" +#: src/ats-tool/gnunet-ats.c:517 +msgid "verbose output (include ATS address properties)" msgstr "" -#: src/chat/gnunet-chat.c:554 -msgid "Use `/names' to list all of the current members in the chat room" -msgstr "" +#: src/ats-tool/gnunet-ats.c:526 +#, fuzzy +msgid "Print information about ATS state" +msgstr "无法获取有关用户“%s”的信息:%s\n" -#: src/chat/gnunet-chat.c:556 -msgid "Use `/help command' to get help for a specific command" -msgstr "" +#: src/block/block.c:105 +#, fuzzy, c-format +msgid "Loading block plugin `%s'\n" +msgstr "打开日志文件“%s”失败:%s\n" -#: src/chat/gnunet-chat.c:672 -msgid "You must specify a nickname\n" -msgstr "您必须指定一个昵称\n" +#: src/consensus/gnunet-consensus.c:317 +#, fuzzy +msgid "number of peers in consensus" +msgstr "迭代次数" -#: src/chat/gnunet-chat.c:688 -#, c-format -msgid "Failed to join room `%s'\n" +#: src/consensus/gnunet-consensus.c:320 +msgid "how many peers receive one value?" msgstr "" -#: src/chat/gnunet-chat.c:727 -msgid "set the nickname to use (required)" -msgstr "设置要使用的昵称(必须)" - -#: src/chat/gnunet-chat.c:730 -msgid "set the chat room to join" -msgstr "设置要加入的聊天室" +#: src/consensus/gnunet-consensus.c:323 +#, fuzzy +msgid "number of values" +msgstr "迭代次数" -#: src/chat/gnunet-chat.c:742 -msgid "Join a chat on GNUnet." +#: src/consensus/gnunet-consensus.c:326 +msgid "consensus timeout" msgstr "" -#: src/chat/gnunet-service-chat.c:267 +#: src/consensus/gnunet-consensus-ibf.c:176 #, fuzzy -msgid "Failed to queue a message notification\n" -msgstr "保存配置失败。" +msgid "number of element in set A-B" +msgstr "迭代次数" -#: src/chat/gnunet-service-chat.c:546 +#: src/consensus/gnunet-consensus-ibf.c:179 #, fuzzy -msgid "Failed to queue a join notification\n" -msgstr "保存配置失败。" +msgid "number of element in set B-A" +msgstr "迭代次数" -#: src/chat/gnunet-service-chat.c:729 -#, fuzzy -msgid "Failed to queue a confirmation receipt\n" -msgstr "保存配置失败。" +#: src/consensus/gnunet-consensus-ibf.c:182 +msgid "number of common elements in A and B" +msgstr "" + +#: src/consensus/gnunet-consensus-ibf.c:185 +msgid "hash num" +msgstr "" + +#: src/consensus/gnunet-consensus-ibf.c:188 +msgid "ibf size" +msgstr "" + +#: src/consensus/gnunet-consensus-start-peers.c:158 +msgid "start peers with the given template configuration" +msgstr "" -#: src/chat/gnunet-service-chat.c:907 +#: src/consensus/gnunet-consensus-start-peers.c:161 #, fuzzy -msgid "Failed to queue a leave notification\n" -msgstr "保存配置失败。" +msgid "number of peers to start" +msgstr "迭代次数" -#: src/core/core_api.c:786 +#: src/core/core_api.c:755 msgid "Client was disconnected from core service, trying to reconnect.\n" msgstr "" -#: src/core/gnunet-core.c:54 src/peerinfo-tool/gnunet-peerinfo.c:286 +#: src/core/gnunet-core.c:86 src/peerinfo-tool/gnunet-peerinfo.c:214 #, c-format msgid "Peer `%s'\n" msgstr "" -#: src/core/gnunet-core.c:72 src/peerinfo-tool/gnunet-peerinfo.c:817 +#: src/core/gnunet-core.c:119 src/core/gnunet-core.c:147 +#: src/transport/gnunet-transport.c:612 src/transport/gnunet-transport.c:636 +#, c-format +msgid "%24s: %-17s %4s (%u connections in total)\n" +msgstr "" + +#: src/core/gnunet-core.c:121 src/transport/gnunet-transport.c:614 +#, fuzzy +msgid "Connected to" +msgstr "“%s”已连接到“%s”。\n" + +#: src/core/gnunet-core.c:149 src/transport/gnunet-transport.c:638 +#, fuzzy +msgid "Disconnected from" +msgstr "“%s”已连接到“%s”。\n" + +#: src/core/gnunet-core.c:174 src/mesh/gnunet-mesh.c:176 +#: src/peerinfo-tool/gnunet-peerinfo.c:541 #, fuzzy, c-format msgid "Invalid command line argument `%s'\n" msgstr "“%s”的参数无效。\n" -#: src/core/gnunet-core.c:95 +#: src/core/gnunet-core.c:211 src/transport/gnunet-transport.c:1005 +msgid "provide information about all current connections (continuously)" +msgstr "" + +#: src/core/gnunet-core.c:222 msgid "Print information about connected peers." msgstr "" -#: src/core/gnunet-service-core.c:97 +#: src/core/gnunet-service-core.c:109 +#, fuzzy, c-format +msgid "Failed to read hostkey: %s\n" +msgstr "运行 %s失败:%s %d\n" + +#: src/core/gnunet-service-core.c:123 #, c-format msgid "Core service of `%4s' ready.\n" msgstr "" +#: src/core/gnunet-service-core.c:149 +#, fuzzy +msgid "Core service is lacking HOSTKEY configuration setting. Exiting.\n" +msgstr "立即保存配置?" + +#: src/core/gnunet-service-core.c:163 +#: src/transport/gnunet-service-transport.c:737 +#, fuzzy +msgid "Transport service is unable to access hostkey. Exiting.\n" +msgstr "找不到接口“%s”的一个 IP 地址。\n" + #: src/core/gnunet-service-core_clients.c:370 msgid "# send requests dropped (disconnected)" msgstr "" @@ -581,7 +495,7 @@ msgstr "" msgid "# messages discarded (session disconnected)" msgstr "" -#: src/core/gnunet-service-core_clients.c:818 +#: src/core/gnunet-service-core_clients.c:518 #, c-format msgid "# bytes of messages of type %u received" msgstr "" @@ -624,7 +538,7 @@ msgid "# SET_KEY messages decrypted" msgstr "" #: src/core/gnunet-service-core_kx.c:977 -#: src/transport/gnunet-service-transport_validation.c:810 +#: src/transport/gnunet-service-transport_validation.c:865 msgid "# PING messages received" msgstr "" @@ -648,7 +562,7 @@ msgid "# keepalive messages sent" msgstr "" #: src/core/gnunet-service-core_kx.c:1236 -#: src/transport/gnunet-service-transport_validation.c:1031 +#: src/transport/gnunet-service-transport_validation.c:1161 msgid "# PONG messages received" msgstr "" @@ -664,53 +578,44 @@ msgstr "" msgid "# rekey operations confirmed via PONG" msgstr "" -#: src/core/gnunet-service-core_kx.c:1381 -#: src/core/gnunet-service-core_kx.c:1398 +#: src/core/gnunet-service-core_kx.c:1383 +#: src/core/gnunet-service-core_kx.c:1400 msgid "# SET_KEY and PING messages created" msgstr "" -#: src/core/gnunet-service-core_kx.c:1402 +#: src/core/gnunet-service-core_kx.c:1404 msgid "# REKEY operations performed" msgstr "" -#: src/core/gnunet-service-core_kx.c:1537 +#: src/core/gnunet-service-core_kx.c:1539 msgid "# failed to decrypt message (no session key)" msgstr "" -#: src/core/gnunet-service-core_kx.c:1577 -#: src/core/gnunet-service-core_kx.c:1602 +#: src/core/gnunet-service-core_kx.c:1579 +#: src/core/gnunet-service-core_kx.c:1604 msgid "# bytes dropped (duplicates)" msgstr "" -#: src/core/gnunet-service-core_kx.c:1589 +#: src/core/gnunet-service-core_kx.c:1591 msgid "# bytes dropped (out of sequence)" msgstr "" -#: src/core/gnunet-service-core_kx.c:1626 +#: src/core/gnunet-service-core_kx.c:1628 #, c-format -msgid "Message received far too old (%llu ms). Content ignored.\n" +msgid "Message received far too old (%s). Content ignored.\n" msgstr "" -#: src/core/gnunet-service-core_kx.c:1630 +#: src/core/gnunet-service-core_kx.c:1632 msgid "# bytes dropped (ancient message)" msgstr "" -#: src/core/gnunet-service-core_kx.c:1638 +#: src/core/gnunet-service-core_kx.c:1640 msgid "# bytes of payload decrypted" msgstr "" -#: src/core/gnunet-service-core_kx.c:1700 -#, fuzzy -msgid "Core service is lacking HOSTKEY configuration setting. Exiting.\n" -msgstr "立即保存配置?" - -#: src/core/gnunet-service-core_kx.c:1708 -msgid "Core service could not access hostkey. Exiting.\n" -msgstr "" - -#: src/core/gnunet-service-core_kx.c:1718 src/hostlist/hostlist-server.c:551 -#: src/peerinfo-tool/gnunet-peerinfo.c:823 -#: src/transport/gnunet-service-transport.c:611 +#: src/core/gnunet-service-core_kx.c:1703 src/hostlist/hostlist-server.c:552 +#: src/peerinfo-tool/gnunet-peerinfo.c:547 +#: src/transport/gnunet-service-transport.c:644 msgid "Could not access PEERINFO service. Exiting.\n" msgstr "" @@ -727,23 +632,23 @@ msgstr "" msgid "# encrypted bytes given to transport" msgstr "" -#: src/core/gnunet-service-core_neighbours.c:418 +#: src/core/gnunet-service-core_neighbours.c:421 #, c-format msgid "Unsupported message of type %u (%u bytes) received from peer `%s'\n" msgstr "" #: src/core/gnunet-service-core_sessions.c:206 #: src/core/gnunet-service-core_sessions.c:269 -#: src/dht/gnunet-service-dht_neighbours.c:625 -#: src/dht/gnunet-service-dht_neighbours.c:683 -#: src/fs/gnunet-service-fs_cp.c:615 src/fs/gnunet-service-fs_cp.c:1532 -#: src/topology/gnunet-daemon-topology.c:709 -#: src/topology/gnunet-daemon-topology.c:810 -#: src/transport/gnunet-service-transport_neighbours.c:874 -#: src/transport/gnunet-service-transport_neighbours.c:1080 -#: src/transport/gnunet-service-transport_neighbours.c:1089 -#: src/transport/gnunet-service-transport_neighbours.c:2568 -#: src/transport/gnunet-service-transport_neighbours.c:2814 +#: src/dht/gnunet-service-dht_neighbours.c:645 +#: src/dht/gnunet-service-dht_neighbours.c:703 +#: src/fs/gnunet-service-fs_cp.c:630 src/fs/gnunet-service-fs_cp.c:1544 +#: src/topology/gnunet-daemon-topology.c:704 +#: src/topology/gnunet-daemon-topology.c:805 +#: src/transport/gnunet-service-transport_neighbours.c:1052 +#: src/transport/gnunet-service-transport_neighbours.c:1276 +#: src/transport/gnunet-service-transport_neighbours.c:1285 +#: src/transport/gnunet-service-transport_neighbours.c:2826 +#: src/transport/gnunet-service-transport_neighbours.c:3089 msgid "# peers connected" msgstr "" @@ -764,38 +669,49 @@ msgstr "" msgid "# updates to my type map" msgstr "" -#: src/datacache/datacache.c:115 src/datacache/datacache.c:250 +#: src/datacache/datacache.c:115 src/datacache/datacache.c:266 #: src/datastore/gnunet-service-datastore.c:834 msgid "# bytes stored" msgstr "" -#: src/datacache/datacache.c:141 src/datacache/datacache.c:148 +#: src/datacache/datacache.c:117 src/datacache/datacache.c:268 +msgid "# items stored" +msgstr "" + +#: src/datacache/datacache.c:143 src/datacache/datacache.c:150 #: src/datastore/gnunet-service-datastore.c:1483 #: src/datastore/gnunet-service-datastore.c:1494 #, c-format msgid "No `%s' specified for `%s' in configuration!\n" msgstr "" -#: src/datacache/datacache.c:180 +#: src/datacache/datacache.c:184 #, c-format msgid "Loading `%s' datacache plugin\n" msgstr "" -#: src/datacache/datacache.c:188 +#: src/datacache/datacache.c:192 #, c-format msgid "Failed to load datacache plugin for `%s'\n" msgstr "" -#: src/datacache/datacache.c:276 +#: src/datacache/datacache.c:295 msgid "# requests received" msgstr "" -#: src/datacache/datacache.c:284 +#: src/datacache/datacache.c:304 msgid "# requests filtered by bloom filter" msgstr "" -#: src/datacache/plugin_datacache_mysql.c:97 -#: src/datacache/plugin_datacache_mysql.c:104 +#: src/datacache/plugin_datacache_heap.c:406 +#, fuzzy +msgid "Heap datacache running\n" +msgstr "sqlite 数据仓库" + +#: src/datacache/plugin_datacache_postgres.c:392 +msgid "Postgres datacache running\n" +msgstr "" + #: src/datacache/plugin_datacache_sqlite.c:69 #: src/datacache/plugin_datacache_sqlite.c:72 #: src/datastore/plugin_datastore_mysql.c:803 @@ -803,57 +719,50 @@ msgstr "" #: src/datastore/plugin_datastore_sqlite.c:57 src/mysql/mysql.c:41 #: src/mysql/mysql.c:48 src/mysql/mysql.c:522 src/mysql/mysql.c:531 #: src/mysql/mysql.c:591 src/mysql/mysql.c:607 -#: src/namestore/plugin_namestore_sqlite.c:51 src/util/crypto_ksk.c:49 -#: src/util/crypto_rsa.c:67 src/include/gnunet_common.h:525 -#: src/include/gnunet_common.h:532 +#: src/namestore/plugin_namestore_postgres.c:52 +#: src/namestore/plugin_namestore_sqlite.c:51 src/util/crypto_ecc.c:46 +#: src/util/crypto_ksk.c:49 src/util/crypto_rsa.c:59 +#: src/include/gnunet_common.h:607 src/include/gnunet_common.h:614 #, fuzzy, c-format msgid "`%s' failed at %s:%d with error: %s\n" msgstr "“%s”于 %s:%d 处失败,错误为:%s\n" -#: src/datacache/plugin_datacache_mysql.c:450 -msgid "MySQL datacache running\n" -msgstr "" - -#: src/datacache/plugin_datacache_postgres.c:367 -msgid "Postgres datacache running\n" -msgstr "" - -#: src/datacache/plugin_datacache_sqlite.c:410 +#: src/datacache/plugin_datacache_sqlite.c:450 msgid "Sqlite datacache running\n" msgstr "" -#: src/datacache/plugin_datacache_sqlite.c:443 -#: src/datastore/plugin_datastore_sqlite.c:408 -#: src/namestore/plugin_namestore_sqlite.c:370 +#: src/datacache/plugin_datacache_sqlite.c:484 +#: src/datastore/plugin_datastore_sqlite.c:401 +#: src/namestore/plugin_namestore_sqlite.c:362 msgid "Tried to close sqlite without finalizing all prepared statements.\n" msgstr "" -#: src/datacache/plugin_datacache_sqlite.c:450 +#: src/datacache/plugin_datacache_sqlite.c:491 #, fuzzy, c-format msgid "Failed to close statement %p: %d\n" msgstr "解析配置文件“%s”失败\n" -#: src/datacache/plugin_datacache_template.c:121 +#: src/datacache/plugin_datacache_template.c:125 msgid "Template datacache running\n" msgstr "" -#: src/datastore/datastore_api.c:305 +#: src/datastore/datastore_api.c:310 msgid "Failed to transmit request to drop database.\n" msgstr "" -#: src/datastore/datastore_api.c:388 +#: src/datastore/datastore_api.c:393 msgid "# queue entry timeouts" msgstr "" -#: src/datastore/datastore_api.c:432 +#: src/datastore/datastore_api.c:437 msgid "# queue overflows" msgstr "" -#: src/datastore/datastore_api.c:459 +#: src/datastore/datastore_api.c:465 msgid "# queue entries created" msgstr "" -#: src/datastore/datastore_api.c:477 +#: src/datastore/datastore_api.c:483 msgid "# Requests dropped from datastore queue" msgstr "" @@ -861,59 +770,55 @@ msgstr "" msgid "# datastore connections (re)created" msgstr "" -#: src/datastore/datastore_api.c:548 -msgid "# reconnected to DATASTORE" -msgstr "" - -#: src/datastore/datastore_api.c:612 +#: src/datastore/datastore_api.c:608 msgid "# transmission request failures" msgstr "" -#: src/datastore/datastore_api.c:633 +#: src/datastore/datastore_api.c:630 msgid "# bytes sent to datastore" msgstr "" -#: src/datastore/datastore_api.c:764 +#: src/datastore/datastore_api.c:762 msgid "Failed to receive status response from database." msgstr "" -#: src/datastore/datastore_api.c:778 +#: src/datastore/datastore_api.c:776 msgid "Error reading response from datastore service" msgstr "" -#: src/datastore/datastore_api.c:790 src/datastore/datastore_api.c:796 +#: src/datastore/datastore_api.c:788 src/datastore/datastore_api.c:794 msgid "Invalid error message received from datastore service" msgstr "" -#: src/datastore/datastore_api.c:800 +#: src/datastore/datastore_api.c:798 msgid "# status messages received" msgstr "" -#: src/datastore/datastore_api.c:869 +#: src/datastore/datastore_api.c:867 msgid "# PUT requests executed" msgstr "" -#: src/datastore/datastore_api.c:936 +#: src/datastore/datastore_api.c:934 msgid "# RESERVE requests executed" msgstr "" -#: src/datastore/datastore_api.c:997 +#: src/datastore/datastore_api.c:995 msgid "# RELEASE RESERVE requests executed" msgstr "" -#: src/datastore/datastore_api.c:1054 +#: src/datastore/datastore_api.c:1052 msgid "# UPDATE requests executed" msgstr "" -#: src/datastore/datastore_api.c:1118 +#: src/datastore/datastore_api.c:1116 msgid "# REMOVE requests executed" msgstr "" -#: src/datastore/datastore_api.c:1163 +#: src/datastore/datastore_api.c:1161 msgid "Failed to receive response from database.\n" msgstr "" -#: src/datastore/datastore_api.c:1221 +#: src/datastore/datastore_api.c:1220 msgid "# Results received" msgstr "" @@ -925,7 +830,7 @@ msgstr "" msgid "# GET ZERO ANONYMITY requests executed" msgstr "" -#: src/datastore/datastore_api.c:1409 +#: src/datastore/datastore_api.c:1410 msgid "# GET requests executed" msgstr "" @@ -938,10 +843,12 @@ msgid "# bytes purged (low-priority)" msgstr "" #: src/datastore/gnunet-service-datastore.c:480 +#: src/gns/gnunet-gns-helper-service-w32.c:159 msgid "Transmission to client failed!\n" msgstr "" #: src/datastore/gnunet-service-datastore.c:511 +#: src/gns/gnunet-gns-helper-service-w32.c:189 msgid "Shutdown in progress, aborting transmission.\n" msgstr "" @@ -1077,6 +984,11 @@ msgstr "" msgid "Bloomfilter construction complete.\n" msgstr "" +#: src/datastore/plugin_datastore_heap.c:820 +#, fuzzy +msgid "Heap database running\n" +msgstr "sqlite 数据仓库" + #: src/datastore/plugin_datastore_mysql.c:780 #, fuzzy, c-format msgid "Failed to prepare statement `%s'\n" @@ -1097,6 +1009,7 @@ msgid "Failed to drop table from database.\n" msgstr "发送消息失败。\n" #: src/datastore/plugin_datastore_postgres.c:860 +#: src/namestore/plugin_namestore_postgres.c:652 msgid "Postgres database running\n" msgstr "" @@ -1105,215 +1018,232 @@ msgstr "" msgid "`%s' failed at %s:%u with error: %s" msgstr "“%s”于 %s:%d 处失败,错误为:%s\n" -#: src/datastore/plugin_datastore_sqlite.c:233 -#: src/namestore/plugin_namestore_sqlite.c:204 -#, c-format -msgid "Option `%s' in section `%s' missing in configuration!\n" -msgstr "" - -#: src/datastore/plugin_datastore_sqlite.c:260 -#: src/namestore/plugin_namestore_sqlite.c:229 +#: src/datastore/plugin_datastore_sqlite.c:253 +#: src/namestore/plugin_namestore_sqlite.c:223 #, c-format msgid "Unable to initialize SQLite: %s.\n" msgstr "无法初始化 SQLite:%s。\n" -#: src/datastore/plugin_datastore_sqlite.c:655 +#: src/datastore/plugin_datastore_sqlite.c:648 #, fuzzy msgid "Invalid data in database. Trying to fix (by deletion).\n" msgstr "%s 中有无效数据。请尝试修复(删除之)。\n" -#: src/datastore/plugin_datastore_sqlite.c:1139 +#: src/datastore/plugin_datastore_sqlite.c:1134 msgid "sqlite version to old to determine size, assuming zero\n" msgstr "" -#: src/datastore/plugin_datastore_sqlite.c:1158 +#: src/datastore/plugin_datastore_sqlite.c:1153 #, c-format msgid "" "Using sqlite page utilization to estimate payload (%llu pages of size %llu " "bytes)\n" msgstr "" -#: src/datastore/plugin_datastore_sqlite.c:1198 -#: src/namestore/plugin_namestore_sqlite.c:829 +#: src/datastore/plugin_datastore_sqlite.c:1193 +#: src/namestore/plugin_namestore_sqlite.c:827 #, fuzzy msgid "Sqlite database running\n" msgstr "sqlite 数据仓库" -#: src/datastore/plugin_datastore_template.c:241 +#: src/datastore/plugin_datastore_template.c:257 msgid "Template database running\n" msgstr "" -#: src/dht/dht_api.c:348 +#: src/dht/dht_api.c:375 #, fuzzy msgid "Failed to connect to the DHT service!\n" msgstr "初始化“%s”服务失败。\n" -#: src/dht/gnunet-dht-get.c:201 src/dht/gnunet-dht-monitor.c:293 -#: src/dht/gnunet-dht-put.c:192 +#: src/dht/gnunet-dht-get.c:132 +#, c-format +msgid "" +"Result %d, type %d:\n" +"%.*s\n" +msgstr "" + +#: src/dht/gnunet-dht-get.c:156 +msgid "Must provide key for DHT GET!\n" +msgstr "" + +#: src/dht/gnunet-dht-get.c:162 src/dht/gnunet-dht-monitor.c:225 +#, fuzzy +msgid "Failed to connect to DHT service!\n" +msgstr "初始化“%s”服务失败。\n" + +#: src/dht/gnunet-dht-get.c:170 +msgid "Issueing DHT GET with key" +msgstr "" + +#: src/dht/gnunet-dht-get.c:186 src/dht/gnunet-dht-monitor.c:262 +#: src/dht/gnunet-dht-put.c:198 msgid "the query key" msgstr "" -#: src/dht/gnunet-dht-get.c:204 +#: src/dht/gnunet-dht-get.c:189 msgid "how many parallel requests (replicas) to create" msgstr "" -#: src/dht/gnunet-dht-get.c:207 src/dht/gnunet-dht-monitor.c:296 +#: src/dht/gnunet-dht-get.c:192 src/dht/gnunet-dht-monitor.c:265 msgid "the type of data to look for" msgstr "" -#: src/dht/gnunet-dht-get.c:210 src/dht/gnunet-dht-put.c:201 +#: src/dht/gnunet-dht-get.c:195 src/dht/gnunet-dht-put.c:210 msgid "how long to execute this query before giving up?" msgstr "" -#: src/dht/gnunet-dht-get.c:213 src/dht/gnunet-dht-monitor.c:302 -#: src/dht/gnunet-dht-put.c:204 src/fs/gnunet-download.c:271 -#: src/fs/gnunet-publish.c:731 src/fs/gnunet-search.c:297 -#: src/fs/gnunet-unindex.c:169 src/nse/gnunet-nse-profiler.c:910 +#: src/dht/gnunet-dht-get.c:198 src/dht/gnunet-dht-put.c:201 +msgid "use DHT's demultiplex everywhere option" +msgstr "" + +#: src/dht/gnunet-dht-get.c:201 src/dht/gnunet-dht-monitor.c:271 +#: src/dht/gnunet-dht-put.c:213 src/fs/gnunet-auto-share.c:753 +#: src/fs/gnunet-download.c:328 src/fs/gnunet-publish.c:736 +#: src/fs/gnunet-search.c:294 src/fs/gnunet-unindex.c:168 +#: src/nse/gnunet-nse-profiler.c:1033 msgid "be verbose (print progress information)" msgstr "" -#: src/dht/gnunet-dht-get.c:232 +#: src/dht/gnunet-dht-get.c:222 msgid "Issue a GET request to the GNUnet DHT, prints results." msgstr "" -#: src/dht/gnunet-dht-monitor.c:299 -msgid "how long to execute? 0 = forever" +#: src/dht/gnunet-dht-monitor.c:268 +msgid "how long should the monitor command run" msgstr "" -#: src/dht/gnunet-dht-monitor.c:321 +#: src/dht/gnunet-dht-monitor.c:293 msgid "Prints all packets that go through the DHT." msgstr "" -#: src/dht/gnunet-dht-put.c:108 -msgid "PUT request sent!\n" +#: src/dht/gnunet-dht-put.c:118 +msgid "PUT request sent with key" msgstr "" -#: src/dht/gnunet-dht-put.c:111 +#: src/dht/gnunet-dht-put.c:121 msgid "Timeout sending PUT request!\n" msgstr "" -#: src/dht/gnunet-dht-put.c:114 +#: src/dht/gnunet-dht-put.c:124 msgid "PUT request not confirmed!\n" msgstr "" -#: src/dht/gnunet-dht-put.c:144 +#: src/dht/gnunet-dht-put.c:153 msgid "Must provide KEY and DATA for DHT put!\n" msgstr "" -#: src/dht/gnunet-dht-put.c:152 +#: src/dht/gnunet-dht-put.c:160 #, fuzzy, c-format msgid "Could not connect to %s service!\n" msgstr "无法连接到 %s:%u:%s\n" -#: src/dht/gnunet-dht-put.c:157 -#, fuzzy, c-format -msgid "Connected to %s service!\n" -msgstr "“%s”已连接到“%s”。\n" - -#: src/dht/gnunet-dht-put.c:172 +#: src/dht/gnunet-dht-put.c:176 #, c-format msgid "Issuing put request for `%s' with data `%s'!\n" msgstr "" -#: src/dht/gnunet-dht-put.c:186 +#: src/dht/gnunet-dht-put.c:192 msgid "the data to insert under the key" msgstr "" -#: src/dht/gnunet-dht-put.c:189 +#: src/dht/gnunet-dht-put.c:195 msgid "how long to store this entry in the dht (in seconds)" msgstr "" -#: src/dht/gnunet-dht-put.c:195 +#: src/dht/gnunet-dht-put.c:204 msgid "how many replicas to create" msgstr "" -#: src/dht/gnunet-dht-put.c:198 +#: src/dht/gnunet-dht-put.c:207 msgid "the type to insert data as" msgstr "" -#: src/dht/gnunet-dht-put.c:223 +#: src/dht/gnunet-dht-put.c:235 msgid "Issue a PUT request to the GNUnet DHT insert DATA under KEY." msgstr "" -#: src/dht/gnunet-service-dht.c:163 src/testing/testing.c:544 -#: src/testing/testing.c:1968 src/testing/testing.c:1998 +#: src/dht/gnunet-service-dht.c:172 #, fuzzy msgid "Failed to connect to transport service!\n" msgstr "初始化“%s”服务失败。\n" -#: src/dht/gnunet-service-dht_clients.c:407 +#: src/dht/gnunet-service-dht_clients.c:413 msgid "# GET requests from clients injected" msgstr "" -#: src/dht/gnunet-service-dht_clients.c:500 +#: src/dht/gnunet-service-dht_clients.c:503 msgid "# PUT requests received from clients" msgstr "" -#: src/dht/gnunet-service-dht_clients.c:584 +#: src/dht/gnunet-service-dht_clients.c:585 msgid "# GET requests received from clients" msgstr "" -#: src/dht/gnunet-service-dht_clients.c:682 +#: src/dht/gnunet-service-dht_clients.c:791 msgid "# GET STOP requests received from clients" msgstr "" -#: src/dht/gnunet-service-dht_clients.c:919 +#: src/dht/gnunet-service-dht_clients.c:1035 msgid "# Key match, type mismatches in REPLY to CLIENT" msgstr "" -#: src/dht/gnunet-service-dht_clients.c:932 +#: src/dht/gnunet-service-dht_clients.c:1048 msgid "# Duplicate REPLIES to CLIENT request dropped" msgstr "" -#: src/dht/gnunet-service-dht_clients.c:967 +#: src/dht/gnunet-service-dht_clients.c:1085 #, c-format msgid "Unsupported block type (%u) in request!\n" msgstr "" -#: src/dht/gnunet-service-dht_clients.c:989 +#: src/dht/gnunet-service-dht_clients.c:1108 msgid "# RESULTS queued for clients" msgstr "" -#: src/dht/gnunet-service-dht_clients.c:1038 -#: src/dht/gnunet-service-dht_clients.c:1081 +#: src/dht/gnunet-service-dht_clients.c:1157 +#: src/dht/gnunet-service-dht_clients.c:1199 msgid "# REPLIES ignored for CLIENTS (no match)" msgstr "" -#: src/dht/gnunet-service-dht_clients.c:1048 +#: src/dht/gnunet-service-dht_clients.c:1167 msgid "Could not pass reply to client, message too big!\n" msgstr "" -#: src/dht/gnunet-service-dht_datacache.c:93 +#: src/dht/gnunet-service-dht_datacache.c:64 #, c-format msgid "%s request received, but have no datacache!\n" msgstr "" -#: src/dht/gnunet-service-dht_datacache.c:103 +#: src/dht/gnunet-service-dht_datacache.c:74 msgid "# ITEMS stored in datacache" msgstr "" -#: src/dht/gnunet-service-dht_datacache.c:207 +#: src/dht/gnunet-service-dht_datacache.c:159 msgid "# Good RESULTS found in datacache" msgstr "" -#: src/dht/gnunet-service-dht_datacache.c:218 +#: src/dht/gnunet-service-dht_datacache.c:170 msgid "# Duplicate RESULTS found in datacache" msgstr "" -#: src/dht/gnunet-service-dht_datacache.c:224 +#: src/dht/gnunet-service-dht_datacache.c:176 msgid "# Invalid RESULTS found in datacache" msgstr "" -#: src/dht/gnunet-service-dht_datacache.c:236 +#: src/dht/gnunet-service-dht_datacache.c:182 +msgid "# Irrelevant RESULTS found in datacache" +msgstr "" + +#: src/dht/gnunet-service-dht_datacache.c:194 msgid "# Unsupported RESULTS found in datacache" msgstr "" -#: src/dht/gnunet-service-dht_datacache.c:239 +#: src/dht/gnunet-service-dht_datacache.c:197 #, c-format msgid "Unsupported block type (%u) in local response!\n" msgstr "" -#: src/dht/gnunet-service-dht_datacache.c:269 +#: src/dht/gnunet-service-dht_datacache.c:227 msgid "# GET requests given to datacache" msgstr "" @@ -1321,81 +1251,87 @@ msgstr "" msgid "# HELLOs obtained from peerinfo" msgstr "" -#: src/dht/gnunet-service-dht_neighbours.c:481 +#: src/dht/gnunet-service-dht_neighbours.c:501 msgid "# Preference updates given to core" msgstr "" -#: src/dht/gnunet-service-dht_neighbours.c:571 +#: src/dht/gnunet-service-dht_neighbours.c:591 msgid "# FIND PEER messages initiated" msgstr "" -#: src/dht/gnunet-service-dht_neighbours.c:717 +#: src/dht/gnunet-service-dht_neighbours.c:737 msgid "# Queued messages discarded (peer disconnected)" msgstr "" -#: src/dht/gnunet-service-dht_neighbours.c:772 +#: src/dht/gnunet-service-dht_neighbours.c:792 msgid "# Bytes transmitted to other peers" msgstr "" -#: src/dht/gnunet-service-dht_neighbours.c:810 -msgid "# Bytes of bandwdith requested from core" +#: src/dht/gnunet-service-dht_neighbours.c:830 +msgid "# Bytes of bandwidth requested from core" msgstr "" -#: src/dht/gnunet-service-dht_neighbours.c:1032 -#: src/dht/gnunet-service-dht_neighbours.c:1060 +#: src/dht/gnunet-service-dht_neighbours.c:1052 +#: src/dht/gnunet-service-dht_neighbours.c:1080 msgid "# Peers excluded from routing due to Bloomfilter" msgstr "" -#: src/dht/gnunet-service-dht_neighbours.c:1041 -#: src/dht/gnunet-service-dht_neighbours.c:1075 +#: src/dht/gnunet-service-dht_neighbours.c:1061 +#: src/dht/gnunet-service-dht_neighbours.c:1095 msgid "# Peer selection failed" msgstr "" -#: src/dht/gnunet-service-dht_neighbours.c:1207 +#: src/dht/gnunet-service-dht_neighbours.c:1229 msgid "# PUT requests routed" msgstr "" -#: src/dht/gnunet-service-dht_neighbours.c:1236 +#: src/dht/gnunet-service-dht_neighbours.c:1258 msgid "# PUT messages queued for transmission" msgstr "" -#: src/dht/gnunet-service-dht_neighbours.c:1315 +#: src/dht/gnunet-service-dht_neighbours.c:1265 +#: src/dht/gnunet-service-dht_neighbours.c:1378 +#: src/dht/gnunet-service-dht_neighbours.c:1478 +msgid "# P2P messages dropped due to full queue" +msgstr "" + +#: src/dht/gnunet-service-dht_neighbours.c:1343 msgid "# GET requests routed" msgstr "" -#: src/dht/gnunet-service-dht_neighbours.c:1342 +#: src/dht/gnunet-service-dht_neighbours.c:1370 msgid "# GET messages queued for transmission" msgstr "" -#: src/dht/gnunet-service-dht_neighbours.c:1443 +#: src/dht/gnunet-service-dht_neighbours.c:1485 msgid "# RESULT messages queued for transmission" msgstr "" -#: src/dht/gnunet-service-dht_neighbours.c:1531 +#: src/dht/gnunet-service-dht_neighbours.c:1573 msgid "# P2P PUT requests received" msgstr "" -#: src/dht/gnunet-service-dht_neighbours.c:1647 +#: src/dht/gnunet-service-dht_neighbours.c:1702 msgid "# FIND PEER requests ignored due to Bloomfilter" msgstr "" -#: src/dht/gnunet-service-dht_neighbours.c:1655 +#: src/dht/gnunet-service-dht_neighbours.c:1710 msgid "# FIND PEER requests ignored due to lack of HELLO" msgstr "" -#: src/dht/gnunet-service-dht_neighbours.c:1746 +#: src/dht/gnunet-service-dht_neighbours.c:1801 msgid "# P2P GET requests received" msgstr "" -#: src/dht/gnunet-service-dht_neighbours.c:1788 +#: src/dht/gnunet-service-dht_neighbours.c:1843 msgid "# P2P FIND PEER requests processed" msgstr "" -#: src/dht/gnunet-service-dht_neighbours.c:1802 +#: src/dht/gnunet-service-dht_neighbours.c:1857 msgid "# P2P GET requests ONLY routed" msgstr "" -#: src/dht/gnunet-service-dht_neighbours.c:1876 +#: src/dht/gnunet-service-dht_neighbours.c:1944 msgid "# P2P RESULTS received" msgstr "" @@ -1415,18 +1351,26 @@ msgstr "" msgid "# Invalid REPLIES matched against routing table" msgstr "" -#: src/dht/gnunet-service-dht_routing.c:238 +#: src/dht/gnunet-service-dht_routing.c:232 +msgid "# Irrelevant REPLIES matched against routing table" +msgstr "" + +#: src/dht/gnunet-service-dht_routing.c:244 msgid "# Unsupported REPLIES matched against routing table" msgstr "" -#: src/dht/gnunet-service-dht_routing.c:311 +#: src/dht/gnunet-service-dht_routing.c:317 msgid "# Entries removed from routing table" msgstr "" -#: src/dht/gnunet-service-dht_routing.c:352 +#: src/dht/gnunet-service-dht_routing.c:400 msgid "# Entries added to routing table" msgstr "" +#: src/dht/gnunet-service-dht_routing.c:418 +msgid "# DHT requests combined" +msgstr "" + #: src/dht/plugin_block_dht.c:136 #, c-format msgid "Block not of type %u\n" @@ -1441,15 +1385,51 @@ msgstr "" msgid "Block of type %u is malformed\n" msgstr "" -#: src/dns/gnunet-dns-monitor.c:337 +#: src/dns/dnsparser.c:152 +#, fuzzy, c-format +msgid "Failed to convert DNS IDNA name `%s' to UTF-8: %s\n" +msgstr "打开日志文件“%s”失败:%s\n" + +#: src/dns/dnsparser.c:626 +#, fuzzy, c-format +msgid "Failed to convert UTF-8 name `%s' to DNS IDNA format: %s\n" +msgstr "打开日志文件“%s”失败:%s\n" + +#: src/dns/dnsstub.c:175 +#, fuzzy, c-format +msgid "Could not bind to any port: %s\n" +msgstr "找不到主机“%s”的 IP:%s\n" + +#: src/dns/dnsstub.c:295 src/dns/dnsstub.c:383 +#: src/gns/gnunet-service-gns_resolver.c:1621 +#, fuzzy, c-format +msgid "Failed to send DNS request to %s\n" +msgstr "打开日志文件“%s”失败:%s\n" + +#: src/dns/dnsstub.c:299 +#, fuzzy, c-format +msgid "Sent DNS request to %s\n" +msgstr "打开日志文件“%s”失败:%s\n" + +#: src/dns/dnsstub.c:368 +#, c-format +msgid "Configured DNS exit `%s' is not working / valid.\n" +msgstr "" + +#: src/dns/dnsstub.c:440 +#, c-format +msgid "Received DNS response that is too small (%u bytes)" +msgstr "" + +#: src/dns/gnunet-dns-monitor.c:355 msgid "only monitor DNS queries" msgstr "" -#: src/dns/gnunet-dns-monitor.c:340 +#: src/dns/gnunet-dns-monitor.c:358 msgid "only monitor DNS replies" msgstr "" -#: src/dns/gnunet-dns-monitor.c:348 +#: src/dns/gnunet-dns-monitor.c:369 msgid "Monitor DNS queries." msgstr "" @@ -1461,76 +1441,58 @@ msgstr "" msgid "set AAAA records" msgstr "" -#: src/dns/gnunet-dns-redirector.c:247 +#: src/dns/gnunet-dns-redirector.c:251 msgid "Change DNS replies to point elsewhere." msgstr "" -#: src/dns/gnunet-service-dns.c:485 -#, fuzzy, c-format -msgid "Could not bind to any port: %s\n" -msgstr "找不到主机“%s”的 IP:%s\n" - -#: src/dns/gnunet-service-dns.c:639 +#: src/dns/gnunet-service-dns.c:456 msgid "# DNS requests answered via TUN interface" msgstr "" -#: src/dns/gnunet-service-dns.c:822 +#: src/dns/gnunet-service-dns.c:603 msgid "# DNS exit failed (failed to open socket)" msgstr "" -#: src/dns/gnunet-service-dns.c:1005 -#, c-format -msgid "Received DNS response that is too small (%u bytes)" -msgstr "" - -#: src/dns/gnunet-service-dns.c:1050 +#: src/dns/gnunet-service-dns.c:714 msgid "# External DNS response discarded (no matching request)" msgstr "" -#: src/dns/gnunet-service-dns.c:1168 +#: src/dns/gnunet-service-dns.c:792 msgid "# Client response discarded (no matching request)" msgstr "" -#: src/dns/gnunet-service-dns.c:1281 +#: src/dns/gnunet-service-dns.c:907 msgid "Received malformed IPv4-UDP packet on TUN interface.\n" msgstr "" -#: src/dns/gnunet-service-dns.c:1297 +#: src/dns/gnunet-service-dns.c:923 msgid "Received malformed IPv6-UDP packet on TUN interface.\n" msgstr "" -#: src/dns/gnunet-service-dns.c:1306 +#: src/dns/gnunet-service-dns.c:932 #, c-format msgid "Got non-IP packet with %u bytes and protocol %u from TUN\n" msgstr "" -#: src/dns/gnunet-service-dns.c:1315 +#: src/dns/gnunet-service-dns.c:942 msgid "# Non-DNS UDP packet received via TUN interface" msgstr "" -#: src/dns/gnunet-service-dns.c:1380 +#: src/dns/gnunet-service-dns.c:1009 msgid "# DNS requests received via TUN interface" msgstr "" -#: src/dns/gnunet-service-dns.c:1465 -#, c-format -msgid "Configured DNS exit `%s' is not working / valid.\n" -msgstr "" - -#: src/dns/gnunet-service-dns.c:1497 src/exit/gnunet-daemon-exit.c:2674 -msgid "# Inbound MESH tunnels created" -msgstr "" - -#: src/dns/gnunet-service-dns.c:1561 src/exit/gnunet-daemon-exit.c:3032 +#: src/dns/gnunet-service-dns.c:1049 src/exit/gnunet-daemon-exit.c:3351 #, c-format msgid "`%s' must be installed SUID, refusing to run\n" msgstr "" -#: src/dns/gnunet-service-dns.c:1581 -msgid "Configured to provide DNS exit, but no valid DNS server configured!\n" -msgstr "" +#: src/dns/gnunet-service-dns.c:1069 src/exit/gnunet-daemon-exit.c:3407 +#, fuzzy +msgid "need a valid IPv4 or IPv6 address\n" +msgstr "无效的进程优先级“%s”\n" -#: src/dv/dv_api.c:179 +#: src/dv/dv_api.c:189 #, fuzzy msgid "Failed to connect to the dv service!\n" msgstr "初始化“%s”服务失败。\n" @@ -1540,188 +1502,192 @@ msgstr "初始化“%s”服务失败。\n" msgid "%s Received message from %s of type %d, distance %u!\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:508 +#: src/exit/gnunet-daemon-exit.c:741 #, c-format msgid "Got duplicate service records for `%s:%u'\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:563 +#: src/exit/gnunet-daemon-exit.c:794 msgid "# Bytes transmitted via mesh tunnels" msgstr "" -#: src/exit/gnunet-daemon-exit.c:679 src/exit/gnunet-daemon-exit.c:2069 -#: src/exit/gnunet-daemon-exit.c:2319 src/vpn/gnunet-service-vpn.c:1394 -#: src/vpn/gnunet-service-vpn.c:1795 src/vpn/gnunet-service-vpn.c:1958 +#: src/exit/gnunet-daemon-exit.c:911 src/exit/gnunet-daemon-exit.c:2343 +#: src/exit/gnunet-daemon-exit.c:2603 src/vpn/gnunet-service-vpn.c:1411 +#: src/vpn/gnunet-service-vpn.c:1812 src/vpn/gnunet-service-vpn.c:1975 msgid "# ICMPv4 packets dropped (type not allowed)" msgstr "" -#: src/exit/gnunet-daemon-exit.c:716 src/exit/gnunet-daemon-exit.c:2128 -#: src/exit/gnunet-daemon-exit.c:2378 src/vpn/gnunet-service-vpn.c:1450 -#: src/vpn/gnunet-service-vpn.c:1854 src/vpn/gnunet-service-vpn.c:1991 +#: src/exit/gnunet-daemon-exit.c:948 src/exit/gnunet-daemon-exit.c:2402 +#: src/exit/gnunet-daemon-exit.c:2662 src/vpn/gnunet-service-vpn.c:1467 +#: src/vpn/gnunet-service-vpn.c:1871 src/vpn/gnunet-service-vpn.c:2008 msgid "# ICMPv6 packets dropped (type not allowed)" msgstr "" -#: src/exit/gnunet-daemon-exit.c:756 +#: src/exit/gnunet-daemon-exit.c:988 msgid "# ICMP packets dropped (not allowed)" msgstr "" -#: src/exit/gnunet-daemon-exit.c:763 +#: src/exit/gnunet-daemon-exit.c:995 msgid "ICMP Packet dropped, have no matching connection information\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:840 +#: src/exit/gnunet-daemon-exit.c:1072 msgid "UDP Packet dropped, have no matching connection information\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:915 +#: src/exit/gnunet-daemon-exit.c:1147 msgid "TCP Packet dropped, have no matching connection information\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:968 +#: src/exit/gnunet-daemon-exit.c:1200 msgid "# Packets received from TUN" msgstr "" -#: src/exit/gnunet-daemon-exit.c:982 +#: src/exit/gnunet-daemon-exit.c:1214 msgid "# Bytes received from TUN" msgstr "" -#: src/exit/gnunet-daemon-exit.c:1008 +#: src/exit/gnunet-daemon-exit.c:1240 msgid "IPv4 packet options received. Ignored.\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:1035 +#: src/exit/gnunet-daemon-exit.c:1267 #, c-format msgid "IPv4 packet with unsupported next header %u received. Ignored.\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:1081 +#: src/exit/gnunet-daemon-exit.c:1313 #, c-format msgid "IPv6 packet with unsupported next header %d received. Ignored.\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:1089 +#: src/exit/gnunet-daemon-exit.c:1321 #, c-format msgid "Packet from unknown protocol %u received. Ignored.\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:1471 +#: src/exit/gnunet-daemon-exit.c:1703 msgid "# TCP packets sent via TUN" msgstr "" -#: src/exit/gnunet-daemon-exit.c:1571 +#: src/exit/gnunet-daemon-exit.c:1814 msgid "# TCP service creation requests received via mesh" msgstr "" -#: src/exit/gnunet-daemon-exit.c:1574 src/exit/gnunet-daemon-exit.c:1653 -#: src/exit/gnunet-daemon-exit.c:1763 src/exit/gnunet-daemon-exit.c:1993 -#: src/exit/gnunet-daemon-exit.c:2235 src/exit/gnunet-daemon-exit.c:2516 -#: src/exit/gnunet-daemon-exit.c:2616 +#: src/exit/gnunet-daemon-exit.c:1817 src/exit/gnunet-daemon-exit.c:1906 +#: src/exit/gnunet-daemon-exit.c:2026 src/exit/gnunet-daemon-exit.c:2267 +#: src/exit/gnunet-daemon-exit.c:2519 src/exit/gnunet-daemon-exit.c:2811 +#: src/exit/gnunet-daemon-exit.c:2921 msgid "# Bytes received from MESH" msgstr "" -#: src/exit/gnunet-daemon-exit.c:1607 src/exit/gnunet-daemon-exit.c:2638 +#: src/exit/gnunet-daemon-exit.c:1850 src/exit/gnunet-daemon-exit.c:2943 #, c-format msgid "No service found for %s on port %d!\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:1611 +#: src/exit/gnunet-daemon-exit.c:1854 msgid "# TCP requests dropped (no such service)" msgstr "" -#: src/exit/gnunet-daemon-exit.c:1656 +#: src/exit/gnunet-daemon-exit.c:1909 msgid "# TCP IP-exit creation requests received via mesh" msgstr "" -#: src/exit/gnunet-daemon-exit.c:1766 +#: src/exit/gnunet-daemon-exit.c:2029 msgid "# TCP data requests received via mesh" msgstr "" -#: src/exit/gnunet-daemon-exit.c:1780 +#: src/exit/gnunet-daemon-exit.c:2043 msgid "# TCP DATA requests dropped (no session)" msgstr "" -#: src/exit/gnunet-daemon-exit.c:1830 +#: src/exit/gnunet-daemon-exit.c:2093 msgid "# ICMP packets sent via TUN" msgstr "" -#: src/exit/gnunet-daemon-exit.c:1996 +#: src/exit/gnunet-daemon-exit.c:2270 msgid "# ICMP IP-exit requests received via mesh" msgstr "" -#: src/exit/gnunet-daemon-exit.c:2238 +#: src/exit/gnunet-daemon-exit.c:2522 msgid "# ICMP service requests received via mesh" msgstr "" -#: src/exit/gnunet-daemon-exit.c:2304 src/vpn/gnunet-service-vpn.c:1384 -#: src/vpn/gnunet-service-vpn.c:1952 +#: src/exit/gnunet-daemon-exit.c:2588 src/vpn/gnunet-service-vpn.c:1401 +#: src/vpn/gnunet-service-vpn.c:1969 msgid "# ICMPv4 packets dropped (impossible PT to v6)" msgstr "" -#: src/exit/gnunet-daemon-exit.c:2363 src/vpn/gnunet-service-vpn.c:1420 -#: src/vpn/gnunet-service-vpn.c:1432 src/vpn/gnunet-service-vpn.c:1842 +#: src/exit/gnunet-daemon-exit.c:2647 src/vpn/gnunet-service-vpn.c:1437 +#: src/vpn/gnunet-service-vpn.c:1449 src/vpn/gnunet-service-vpn.c:1859 msgid "# ICMPv6 packets dropped (impossible PT to v4)" msgstr "" -#: src/exit/gnunet-daemon-exit.c:2413 +#: src/exit/gnunet-daemon-exit.c:2697 msgid "# UDP packets sent via TUN" msgstr "" -#: src/exit/gnunet-daemon-exit.c:2519 +#: src/exit/gnunet-daemon-exit.c:2814 msgid "# UDP IP-exit requests received via mesh" msgstr "" -#: src/exit/gnunet-daemon-exit.c:2619 +#: src/exit/gnunet-daemon-exit.c:2924 msgid "# UDP service requests received via mesh" msgstr "" -#: src/exit/gnunet-daemon-exit.c:2642 +#: src/exit/gnunet-daemon-exit.c:2947 msgid "# UDP requests dropped (no such service)" msgstr "" -#: src/exit/gnunet-daemon-exit.c:2882 +#: src/exit/gnunet-daemon-exit.c:2980 +msgid "# Inbound MESH tunnels created" +msgstr "" + +#: src/exit/gnunet-daemon-exit.c:3209 #, c-format msgid "No addresses found for hostname `%s' of service `%s'!\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:2896 src/exit/gnunet-daemon-exit.c:2908 +#: src/exit/gnunet-daemon-exit.c:3223 src/exit/gnunet-daemon-exit.c:3235 #, c-format msgid "Service `%s' configured for IPv4, but IPv4 is disabled!\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:2919 +#: src/exit/gnunet-daemon-exit.c:3246 #, c-format msgid "No IP addresses found for hostname `%s' of service `%s'!\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:3048 +#: src/exit/gnunet-daemon-exit.c:3364 msgid "" "This system does not support IPv4, will disable IPv4 functions despite them " "being enabled in the configuration\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:3056 +#: src/exit/gnunet-daemon-exit.c:3372 msgid "" "This system does not support IPv6, will disable IPv6 functions despite them " "being enabled in the configuration\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:3063 +#: src/exit/gnunet-daemon-exit.c:3379 msgid "" "Cannot enable IPv4 exit but disable IPv4 on TUN interface, will use " "ENABLE_IPv4=YES\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:3069 +#: src/exit/gnunet-daemon-exit.c:3385 msgid "" "Cannot enable IPv6 exit but disable IPv6 on TUN interface, will use " "ENABLE_IPv6=YES\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:3075 src/pt/gnunet-daemon-pt.c:884 +#: src/exit/gnunet-daemon-exit.c:3391 src/pt/gnunet-daemon-pt.c:884 msgid "No useful service enabled. Exiting.\n" msgstr "" -#: src/exit/gnunet-daemon-exit.c:3236 +#: src/exit/gnunet-daemon-exit.c:3620 msgid "Daemon to run to provide an IP exit node for the VPN" msgstr "" @@ -1741,108 +1707,108 @@ msgstr "" msgid "# messages defragmented" msgstr "" -#: src/fragmentation/fragmentation.c:203 +#: src/fragmentation/fragmentation.c:208 msgid "# fragments transmitted" msgstr "" -#: src/fragmentation/fragmentation.c:206 +#: src/fragmentation/fragmentation.c:211 msgid "# fragments retransmitted" msgstr "" -#: src/fragmentation/fragmentation.c:232 +#: src/fragmentation/fragmentation.c:237 msgid "# fragments wrap arounds" msgstr "" -#: src/fragmentation/fragmentation.c:273 +#: src/fragmentation/fragmentation.c:281 msgid "# messages fragmented" msgstr "" -#: src/fragmentation/fragmentation.c:276 +#: src/fragmentation/fragmentation.c:284 msgid "# total size of fragmented messages" msgstr "" -#: src/fragmentation/fragmentation.c:363 +#: src/fragmentation/fragmentation.c:405 msgid "# fragment acknowledgements received" msgstr "" -#: src/fragmentation/fragmentation.c:369 +#: src/fragmentation/fragmentation.c:411 msgid "# bits removed from fragmentation ACKs" msgstr "" -#: src/fragmentation/fragmentation.c:393 +#: src/fragmentation/fragmentation.c:435 msgid "# fragmentation transmissions completed" msgstr "" -#: src/fs/fs_api.c:339 +#: src/fs/fs_api.c:465 #, fuzzy, c-format msgid "Could not open file `%s': %s" msgstr "打开日志文件“%s”失败:%s\n" -#: src/fs/fs_api.c:348 +#: src/fs/fs_api.c:474 #, fuzzy, c-format msgid "Could not read file `%s': %s" msgstr "无法解析“%s”(%s):%s\n" -#: src/fs/fs_api.c:354 +#: src/fs/fs_api.c:480 #, c-format msgid "Short read reading from file `%s'!" msgstr "" -#: src/fs/fs_api.c:938 +#: src/fs/fs_api.c:1061 #, fuzzy, c-format msgid "Failed to resume publishing information `%s': %s\n" msgstr "打开日志文件“%s”失败:%s\n" -#: src/fs/fs_api.c:1395 +#: src/fs/fs_api.c:1520 #, c-format msgid "Failed to recover namespace `%s', cannot resume publishing operation.\n" msgstr "" -#: src/fs/fs_api.c:1437 +#: src/fs/fs_api.c:1562 #, c-format msgid "Failure while resuming publishing operation `%s': %s\n" msgstr "" -#: src/fs/fs_api.c:1453 +#: src/fs/fs_api.c:1578 #, fuzzy, c-format msgid "Failed to resume publishing operation `%s': %s\n" msgstr "解析配置文件“%s”失败\n" -#: src/fs/fs_api.c:2106 +#: src/fs/fs_api.c:2229 #, c-format msgid "Failure while resuming unindexing operation `%s': %s\n" msgstr "" -#: src/fs/fs_api.c:2116 +#: src/fs/fs_api.c:2239 #, fuzzy, c-format msgid "Failed to resume unindexing operation `%s': %s\n" msgstr "解析配置文件“%s”失败\n" -#: src/fs/fs_api.c:2241 src/fs/fs_api.c:2480 +#: src/fs/fs_api.c:2364 src/fs/fs_api.c:2604 #, fuzzy, c-format msgid "Failed to resume sub-download `%s': %s\n" msgstr "打开日志文件“%s”失败:%s\n" -#: src/fs/fs_api.c:2258 +#: src/fs/fs_api.c:2381 #, fuzzy, c-format msgid "Failed to resume sub-search `%s': %s\n" msgstr "打开日志文件“%s”失败:%s\n" -#: src/fs/fs_api.c:2270 src/fs/fs_api.c:2289 src/fs/fs_api.c:2773 +#: src/fs/fs_api.c:2394 src/fs/fs_api.c:2413 src/fs/fs_api.c:2897 #, c-format msgid "Failure while resuming search operation `%s': %s\n" msgstr "" -#: src/fs/fs_api.c:2471 +#: src/fs/fs_api.c:2595 #, fuzzy, c-format msgid "Failed to resume sub-download `%s': could not open file `%s'\n" msgstr "解析配置文件“%s”失败\n" -#: src/fs/fs_api.c:2717 +#: src/fs/fs_api.c:2841 msgid "Could not resume running search, will resume as paused search\n" msgstr "" -#: src/fs/fs_api.c:2811 +#: src/fs/fs_api.c:2935 #, c-format msgid "Failure while resuming download operation `%s': %s\n" msgstr "" @@ -1851,63 +1817,63 @@ msgstr "" msgid "MAGIC mismatch. This is not a GNUnet directory.\n" msgstr "" -#: src/fs/fs_download.c:311 +#: src/fs/fs_download.c:321 msgid "" "Recursive downloads of directories larger than 4 GB are not supported on 32-" "bit systems\n" msgstr "" -#: src/fs/fs_download.c:331 +#: src/fs/fs_download.c:341 msgid "Directory too large for system address space\n" msgstr "" -#: src/fs/fs_download.c:497 src/fs/fs_download.c:509 +#: src/fs/fs_download.c:507 src/fs/fs_download.c:519 #, fuzzy, c-format msgid "Failed to open file `%s' for writing" msgstr "打开日志文件“%s”失败:%s\n" -#: src/fs/fs_download.c:878 +#: src/fs/fs_download.c:888 #, c-format msgid "Failed to create directory for recursive download of `%s'\n" msgstr "" -#: src/fs/fs_download.c:960 +#: src/fs/fs_download.c:970 #, c-format msgid "" "Internal error or bogus download URI (expected %u bytes at depth %u and " "offset %llu/%llu, got %u bytes)" msgstr "" -#: src/fs/fs_download.c:986 +#: src/fs/fs_download.c:996 msgid "internal error decrypting content" msgstr "" -#: src/fs/fs_download.c:1009 +#: src/fs/fs_download.c:1019 #, fuzzy, c-format msgid "Download failed: could not open file `%s': %s" msgstr "打开日志文件“%s”失败:%s\n" -#: src/fs/fs_download.c:1019 +#: src/fs/fs_download.c:1029 #, fuzzy, c-format msgid "Failed to seek to offset %llu in file `%s': %s" msgstr "打开日志文件“%s”失败:%s\n" -#: src/fs/fs_download.c:1028 +#: src/fs/fs_download.c:1038 #, fuzzy, c-format msgid "Failed to write block of %u bytes at offset %llu in file `%s': %s" msgstr "解析配置文件“%s”失败\n" -#: src/fs/fs_download.c:1125 +#: src/fs/fs_download.c:1136 #, fuzzy msgid "internal error decoding tree" msgstr "未知错误。\n" -#: src/fs/fs_download.c:1888 +#: src/fs/fs_download.c:1927 #, fuzzy msgid "Invalid URI" msgstr "无效条目。\n" -#: src/fs/fs_getopt.c:191 +#: src/fs/fs_getopt.c:192 #, c-format msgid "" "Unknown metadata type in metadata option `%s'. Using metadata type " @@ -1949,37 +1915,36 @@ msgstr "发送消息失败。\n" msgid "Failed to connect to datastore service" msgstr "初始化“%s”服务失败。\n" -#: src/fs/fs_namespace.c:57 src/fs/fs_namespace.c:83 -#, fuzzy, c-format -msgid "Configuration fails to specify `%s' in section `%s'\n" -msgstr "配置文件“%s”已写入。\n" - -#: src/fs/fs_namespace.c:112 +#: src/fs/fs_namespace.c:110 #, fuzzy, c-format msgid "Failed to open `%s' for writing: %s\n" msgstr "打开日志文件“%s”失败:%s\n" -#: src/fs/fs_namespace.c:134 src/fs/fs_namespace.c:222 +#: src/fs/fs_namespace.c:132 src/fs/fs_namespace.c:220 #, fuzzy, c-format msgid "Failed to write `%s': %s\n" msgstr "运行 %s失败:%s %d\n" -#: src/fs/fs_namespace.c:256 +#: src/fs/fs_namespace.c:252 #, c-format msgid "Failed to create or read private key for namespace `%s'\n" msgstr "" -#: src/fs/fs_namespace.c:371 +#: src/fs/fs_namespace.c:367 #, c-format msgid "Failed to read namespace private key file `%s', deleting it!\n" msgstr "" -#: src/fs/fs_namespace.c:588 src/fs/fs_publish_ksk.c:295 +#: src/fs/fs_namespace.c:558 +msgid "Identifiers or URI too long to create SBlock" +msgstr "" + +#: src/fs/fs_namespace.c:593 src/fs/fs_publish_ksk.c:295 #, fuzzy msgid "Internal error." msgstr "未知错误。\n" -#: src/fs/fs_namespace.c:631 +#: src/fs/fs_namespace.c:636 msgid "Failed to connect to datastore." msgstr "" @@ -1988,58 +1953,58 @@ msgstr "" msgid "Publishing failed: %s" msgstr "" -#: src/fs/fs_publish.c:621 src/fs/fs_publish.c:638 src/fs/fs_publish.c:677 -#: src/fs/fs_publish.c:697 src/fs/fs_publish.c:722 src/fs/fs_publish.c:862 +#: src/fs/fs_publish.c:622 src/fs/fs_publish.c:639 src/fs/fs_publish.c:678 +#: src/fs/fs_publish.c:698 src/fs/fs_publish.c:723 src/fs/fs_publish.c:863 #, c-format msgid "Can not index file `%s': %s. Will try to insert instead.\n" msgstr "" -#: src/fs/fs_publish.c:623 +#: src/fs/fs_publish.c:624 msgid "timeout on index-start request to `fs' service" msgstr "" -#: src/fs/fs_publish.c:635 +#: src/fs/fs_publish.c:636 #, fuzzy msgid "unknown error" msgstr "未知错误" -#: src/fs/fs_publish.c:678 +#: src/fs/fs_publish.c:679 msgid "failed to compute hash" msgstr "" -#: src/fs/fs_publish.c:698 +#: src/fs/fs_publish.c:699 msgid "filename too long" msgstr "" -#: src/fs/fs_publish.c:723 +#: src/fs/fs_publish.c:724 msgid "could not connect to `fs' service" msgstr "" -#: src/fs/fs_publish.c:746 +#: src/fs/fs_publish.c:747 #, fuzzy, c-format msgid "Failed to get file identifiers for `%s'\n" msgstr "解析配置文件“%s”失败\n" -#: src/fs/fs_publish.c:811 +#: src/fs/fs_publish.c:812 #, c-format msgid "Recursive upload failed at `%s': %s" msgstr "" -#: src/fs/fs_publish.c:817 +#: src/fs/fs_publish.c:818 #, c-format msgid "Recursive upload failed: %s" msgstr "" -#: src/fs/fs_publish.c:863 +#: src/fs/fs_publish.c:864 msgid "needs to be an actual file" msgstr "" -#: src/fs/fs_publish.c:1071 +#: src/fs/fs_publish.c:1090 #, c-format msgid "Insufficient space for publishing: %s" msgstr "" -#: src/fs/fs_publish.c:1142 +#: src/fs/fs_publish.c:1161 #, c-format msgid "Reserving space for %u entries and %llu bytes for publication\n" msgstr "" @@ -2048,16 +2013,11 @@ msgstr "" msgid "Could not connect to datastore." msgstr "" -#: src/fs/fs_search.c:829 +#: src/fs/fs_search.c:892 #, c-format msgid "Got result with unknown block type `%d', ignoring" msgstr "" -#: src/fs/fs_test_lib.c:269 -#, fuzzy, c-format -msgid "Failed to start daemon: %s\n" -msgstr "运行 %s失败:%s %d\n" - #: src/fs/fs_unindex.c:58 msgid "Failed to find given position in file" msgstr "" @@ -2084,95 +2044,95 @@ msgstr "“%s”的参数无效。\n" msgid "Failed to connect to FS service for unindexing." msgstr "" -#: src/fs/fs_unindex.c:344 +#: src/fs/fs_unindex.c:349 src/fs/fs_unindex.c:361 #, fuzzy msgid "Failed to get KSKs from directory scan." msgstr "解析配置文件“%s”失败\n" -#: src/fs/fs_unindex.c:356 +#: src/fs/fs_unindex.c:357 #, fuzzy, c-format msgid "Internal error scanning `%s'.\n" msgstr "未知错误。\n" -#: src/fs/fs_unindex.c:411 +#: src/fs/fs_unindex.c:416 #, fuzzy, c-format msgid "Failed to remove KBlock: %s\n" msgstr "打开日志文件“%s”失败:%s\n" -#: src/fs/fs_unindex.c:501 +#: src/fs/fs_unindex.c:506 #, fuzzy, c-format msgid "Failed to parse URI `%s' from KBlock!\n" msgstr "运行 %s失败:%s %d\n" -#: src/fs/fs_unindex.c:553 src/fs/fs_unindex.c:618 +#: src/fs/fs_unindex.c:558 src/fs/fs_unindex.c:623 #, fuzzy msgid "Failed to connect to `datastore' service." msgstr "初始化“%s”服务失败。\n" -#: src/fs/fs_unindex.c:631 +#: src/fs/fs_unindex.c:636 #, fuzzy msgid "Failed to open file for unindexing." msgstr "打开日志文件“%s”失败:%s\n" -#: src/fs/fs_unindex.c:665 +#: src/fs/fs_unindex.c:670 msgid "Failed to compute hash of file." msgstr "" -#: src/fs/fs_uri.c:220 -#, c-format +#: src/fs/fs_uri.c:221 +#, no-c-format msgid "`%' must be followed by HEX number" msgstr "" -#: src/fs/fs_uri.c:279 +#: src/fs/fs_uri.c:280 msgid "Malformed KSK URI (must not begin or end with `+')" msgstr "" -#: src/fs/fs_uri.c:297 +#: src/fs/fs_uri.c:298 msgid "`++' not allowed in KSK URI" msgstr "" -#: src/fs/fs_uri.c:304 +#: src/fs/fs_uri.c:305 msgid "Quotes not balanced in KSK URI" msgstr "" -#: src/fs/fs_uri.c:372 src/fs/fs_uri.c:379 +#: src/fs/fs_uri.c:373 src/fs/fs_uri.c:380 msgid "Malformed SKS URI" msgstr "" -#: src/fs/fs_uri.c:423 src/fs/fs_uri.c:438 +#: src/fs/fs_uri.c:424 src/fs/fs_uri.c:439 msgid "Malformed CHK URI" msgstr "" -#: src/fs/fs_uri.c:568 src/fs/fs_uri.c:583 src/fs/fs_uri.c:593 -#: src/fs/fs_uri.c:621 +#: src/fs/fs_uri.c:569 src/fs/fs_uri.c:584 src/fs/fs_uri.c:594 +#: src/fs/fs_uri.c:622 msgid "SKS URI malformed" msgstr "" -#: src/fs/fs_uri.c:603 +#: src/fs/fs_uri.c:604 msgid "SKS URI malformed (could not decode public key)" msgstr "" -#: src/fs/fs_uri.c:609 +#: src/fs/fs_uri.c:610 msgid "SKS URI malformed (could not find signature)" msgstr "" -#: src/fs/fs_uri.c:615 +#: src/fs/fs_uri.c:616 msgid "SKS URI malformed (could not decode signature)" msgstr "" -#: src/fs/fs_uri.c:628 +#: src/fs/fs_uri.c:629 msgid "SKS URI malformed (could not parse expiration time)" msgstr "" -#: src/fs/fs_uri.c:640 +#: src/fs/fs_uri.c:641 msgid "SKS URI malformed (signature failed validation)" msgstr "" -#: src/fs/fs_uri.c:678 +#: src/fs/fs_uri.c:679 msgid "Unrecognized URI type" msgstr "" -#: src/fs/fs_uri.c:903 +#: src/fs/fs_uri.c:904 #, fuzzy msgid "Lacking key configuration settings.\n" msgstr "立即保存配置?" @@ -2190,6 +2150,68 @@ msgstr "" msgid "Number of double-quotes not balanced!\n" msgstr "" +#: src/fs/gnunet-auto-share.c:236 +#, fuzzy, c-format +msgid "Failed to load state: %s\n" +msgstr "运行 %s失败:%s %d\n" + +#: src/fs/gnunet-auto-share.c:289 src/fs/gnunet-auto-share.c:299 +#: src/fs/gnunet-auto-share.c:309 +#, fuzzy, c-format +msgid "Failed to save state to file %s\n" +msgstr "解析配置文件“%s”失败\n" + +#: src/fs/gnunet-auto-share.c:401 +#, c-format +msgid "Publication of `%s' done\n" +msgstr "" + +#: src/fs/gnunet-auto-share.c:488 +#, c-format +msgid "Publishing `%s'\n" +msgstr "" + +#: src/fs/gnunet-auto-share.c:497 +#, fuzzy, c-format +msgid "Failed to run `%s'\n" +msgstr "运行 %s失败:%s %d\n" + +#: src/fs/gnunet-auto-share.c:686 +#, c-format +msgid "" +"You must specify one and only one directory name for automatic publication.\n" +msgstr "" + +#: src/fs/gnunet-auto-share.c:737 src/fs/gnunet-pseudonym.c:279 +#: src/fs/gnunet-publish.c:683 +msgid "set the desired LEVEL of sender-anonymity" +msgstr "" + +#: src/fs/gnunet-auto-share.c:741 src/fs/gnunet-publish.c:687 +msgid "disable adding the creation time to the metadata of the uploaded file" +msgstr "" + +#: src/fs/gnunet-auto-share.c:744 src/fs/gnunet-publish.c:690 +msgid "do not use libextractor to add keywords or metadata" +msgstr "" + +#: src/fs/gnunet-auto-share.c:747 src/fs/gnunet-publish.c:714 +msgid "specify the priority of the content" +msgstr "" + +#: src/fs/gnunet-auto-share.c:750 src/fs/gnunet-pseudonym.c:304 +#: src/fs/gnunet-publish.c:721 +msgid "set the desired replication LEVEL" +msgstr "" + +#: src/fs/gnunet-auto-share.c:770 +msgid "Automatically publish files from a directory on GNUnet" +msgstr "" + +#: src/fs/gnunet-daemon-fsprofiler.c:656 +msgid "Daemon to use file-sharing to measure its performance." +msgstr "" + #: src/fs/gnunet-directory.c:49 #, c-format msgid "\t\n" @@ -2220,97 +2242,97 @@ msgstr "解析配置文件“%s”失败\n" msgid "`%s' is not a GNUnet directory\n" msgstr "更改 GNUnet 目录的权限出错" -#: src/fs/gnunet-directory.c:179 +#: src/fs/gnunet-directory.c:183 #, fuzzy msgid "Display contents of a GNUnet directory" msgstr "更改 GNUnet 目录的权限出错" -#: src/fs/gnunet-download.c:101 +#: src/fs/gnunet-download.c:137 #, fuzzy, c-format msgid "Starting download `%s'.\n" msgstr "未知的命令“%s”。\n" -#: src/fs/gnunet-download.c:110 +#: src/fs/gnunet-download.c:147 #, fuzzy msgid "" msgstr "未知错误" -#: src/fs/gnunet-download.c:119 +#: src/fs/gnunet-download.c:157 #, c-format msgid "" "Downloading `%s' at %llu/%llu (%s remaining, %s/s). Block took %s to " "download\n" msgstr "" -#: src/fs/gnunet-download.c:129 +#: src/fs/gnunet-download.c:179 #, c-format msgid "Error downloading: %s.\n" msgstr "" -#: src/fs/gnunet-download.c:137 +#: src/fs/gnunet-download.c:194 #, c-format msgid "Downloading `%s' done (%s/s).\n" msgstr "" -#: src/fs/gnunet-download.c:152 src/fs/gnunet-publish.c:190 -#: src/fs/gnunet-search.c:190 src/fs/gnunet-unindex.c:109 +#: src/fs/gnunet-download.c:209 src/fs/gnunet-publish.c:195 +#: src/fs/gnunet-search.c:193 src/fs/gnunet-unindex.c:108 #, c-format msgid "Unexpected status: %d\n" msgstr "" -#: src/fs/gnunet-download.c:177 +#: src/fs/gnunet-download.c:234 #, fuzzy msgid "You need to specify a URI argument.\n" msgstr "您必须指定一个昵称\n" -#: src/fs/gnunet-download.c:183 src/fs/gnunet-publish.c:624 +#: src/fs/gnunet-download.c:240 src/fs/gnunet-publish.c:629 #, fuzzy, c-format msgid "Failed to parse URI: %s\n" msgstr "运行 %s失败:%s %d\n" -#: src/fs/gnunet-download.c:190 +#: src/fs/gnunet-download.c:247 msgid "Only CHK or LOC URIs supported.\n" msgstr "" -#: src/fs/gnunet-download.c:197 +#: src/fs/gnunet-download.c:254 msgid "Target filename must be specified.\n" msgstr "" -#: src/fs/gnunet-download.c:211 src/fs/gnunet-publish.c:602 -#: src/fs/gnunet-search.c:241 src/fs/gnunet-unindex.c:141 +#: src/fs/gnunet-download.c:268 src/fs/gnunet-publish.c:607 +#: src/fs/gnunet-search.c:243 src/fs/gnunet-unindex.c:140 #, fuzzy, c-format msgid "Could not initialize `%s' subsystem.\n" msgstr "初始化“%s”服务失败。\n" -#: src/fs/gnunet-download.c:248 src/fs/gnunet-search.c:285 +#: src/fs/gnunet-download.c:305 src/fs/gnunet-search.c:282 msgid "set the desired LEVEL of receiver-anonymity" msgstr "" -#: src/fs/gnunet-download.c:251 +#: src/fs/gnunet-download.c:308 msgid "delete incomplete downloads (when aborted with CTRL-C)" msgstr "" -#: src/fs/gnunet-download.c:254 src/fs/gnunet-search.c:288 +#: src/fs/gnunet-download.c:311 src/fs/gnunet-search.c:285 msgid "only search the local peer (no P2P network search)" msgstr "" -#: src/fs/gnunet-download.c:257 +#: src/fs/gnunet-download.c:314 msgid "write the file to FILENAME" msgstr "" -#: src/fs/gnunet-download.c:261 +#: src/fs/gnunet-download.c:318 msgid "set the maximum number of parallel downloads that is allowed" msgstr "" -#: src/fs/gnunet-download.c:265 +#: src/fs/gnunet-download.c:322 msgid "set the maximum number of parallel requests for blocks that is allowed" msgstr "" -#: src/fs/gnunet-download.c:268 +#: src/fs/gnunet-download.c:325 msgid "download a GNUnet directory recursively" msgstr "" -#: src/fs/gnunet-download.c:278 +#: src/fs/gnunet-download.c:339 msgid "" "Download files from GNUnet using a GNUnet CHK or LOC URI (gnunet://fs/" "chk/...)" @@ -2320,11 +2342,27 @@ msgstr "" msgid "print a list of all indexed files" msgstr "" -#: src/fs/gnunet-fs.c:124 +#: src/fs/gnunet-fs.c:127 msgid "Special file-sharing operations" msgstr "" -#: src/fs/gnunet-pseudonym.c:160 src/statistics/gnunet-statistics.c:167 +#: src/fs/gnunet-fs-profiler.c:182 +msgid "run the experiment with COUNT peers" +msgstr "" + +#: src/fs/gnunet-fs-profiler.c:185 +msgid "specifies name of a file with the HOSTS the testbed should use" +msgstr "" + +#: src/fs/gnunet-fs-profiler.c:188 +msgid "automatically terminate experiment after DELAY" +msgstr "" + +#: src/fs/gnunet-fs-profiler.c:197 +msgid "run a testbed to measure file-sharing performance" +msgstr "" + +#: src/fs/gnunet-pseudonym.c:160 src/statistics/gnunet-statistics.c:283 #, fuzzy, c-format msgid "Invalid argument `%s'\n" msgstr "“%s”的参数无效。\n" @@ -2335,10 +2373,6 @@ msgstr "“%s”的参数无效。\n" msgid "Option `%s' ignored\n" msgstr "%s:选项“%s”有歧义\n" -#: src/fs/gnunet-pseudonym.c:279 src/fs/gnunet-publish.c:678 -msgid "set the desired LEVEL of sender-anonymity" -msgstr "" - #: src/fs/gnunet-pseudonym.c:282 msgid "create or advertise namespace NAME" msgstr "" @@ -2353,7 +2387,7 @@ msgid "" "multiple times)" msgstr "" -#: src/fs/gnunet-pseudonym.c:292 src/fs/gnunet-publish.c:697 +#: src/fs/gnunet-pseudonym.c:292 src/fs/gnunet-publish.c:702 msgid "set the meta-data for the given TYPE to the given VALUE" msgstr "" @@ -2369,10 +2403,6 @@ msgstr "" msgid "do not print names of remote namespaces" msgstr "" -#: src/fs/gnunet-pseudonym.c:304 src/fs/gnunet-publish.c:716 -msgid "set the desired replication LEVEL" -msgstr "" - #: src/fs/gnunet-pseudonym.c:307 msgid "specify ID of the root of the namespace" msgstr "" @@ -2381,378 +2411,354 @@ msgstr "" msgid "change rating of namespace ID by VALUE" msgstr "" -#: src/fs/gnunet-pseudonym.c:318 +#: src/fs/gnunet-pseudonym.c:322 msgid "Manage GNUnet pseudonyms." msgstr "" -#: src/fs/gnunet-publish.c:147 +#: src/fs/gnunet-publish.c:152 #, c-format msgid "Publishing `%s' at %llu/%llu (%s remaining)\n" msgstr "" -#: src/fs/gnunet-publish.c:155 +#: src/fs/gnunet-publish.c:159 #, c-format msgid "Error publishing: %s.\n" msgstr "" -#: src/fs/gnunet-publish.c:165 +#: src/fs/gnunet-publish.c:169 #, c-format msgid "Publishing `%s' done.\n" msgstr "" -#: src/fs/gnunet-publish.c:169 +#: src/fs/gnunet-publish.c:173 #, c-format msgid "URI is `%s'.\n" msgstr "" -#: src/fs/gnunet-publish.c:187 +#: src/fs/gnunet-publish.c:192 msgid "Cleanup after abort complete.\n" msgstr "" -#: src/fs/gnunet-publish.c:305 +#: src/fs/gnunet-publish.c:310 #, fuzzy, c-format msgid "Meta data for file `%s' (%s)\n" msgstr "打开日志文件“%s”失败:%s\n" -#: src/fs/gnunet-publish.c:307 +#: src/fs/gnunet-publish.c:312 #, fuzzy, c-format msgid "Keywords for file `%s' (%s)\n" msgstr "无法解析“%s”(%s):%s\n" -#: src/fs/gnunet-publish.c:358 +#: src/fs/gnunet-publish.c:363 src/fs/gnunet-publish.c:617 #, fuzzy, c-format -msgid "Failed to create namespace `%s'\n" +msgid "Failed to create namespace `%s' (illegal filename?)\n" msgstr "发送消息失败。\n" -#: src/fs/gnunet-publish.c:433 +#: src/fs/gnunet-publish.c:438 #, fuzzy msgid "Could not publish\n" msgstr "无法解析“%s”(%s):%s\n" -#: src/fs/gnunet-publish.c:460 +#: src/fs/gnunet-publish.c:465 msgid "Could not start publishing.\n" msgstr "" -#: src/fs/gnunet-publish.c:491 +#: src/fs/gnunet-publish.c:496 #, fuzzy, c-format msgid "Scanning directory `%s'.\n" msgstr "解析配置文件“%s”失败\n" -#: src/fs/gnunet-publish.c:493 +#: src/fs/gnunet-publish.c:498 #, fuzzy, c-format msgid "Scanning file `%s'.\n" msgstr "未知的命令“%s”。\n" -#: src/fs/gnunet-publish.c:498 +#: src/fs/gnunet-publish.c:503 #, c-format msgid "There was trouble processing file `%s', skipping it.\n" msgstr "" -#: src/fs/gnunet-publish.c:503 +#: src/fs/gnunet-publish.c:508 msgid "Preprocessing complete.\n" msgstr "" -#: src/fs/gnunet-publish.c:507 +#: src/fs/gnunet-publish.c:512 #, fuzzy, c-format msgid "Extracting meta data from file `%s' complete.\n" msgstr "打开日志文件“%s”失败:%s\n" -#: src/fs/gnunet-publish.c:511 +#: src/fs/gnunet-publish.c:516 msgid "Meta data extraction has finished.\n" msgstr "" -#: src/fs/gnunet-publish.c:518 +#: src/fs/gnunet-publish.c:523 #, fuzzy msgid "Internal error scanning directory.\n" msgstr "未知错误。\n" -#: src/fs/gnunet-publish.c:552 +#: src/fs/gnunet-publish.c:557 #, c-format msgid "Cannot extract metadata from a URI!\n" msgstr "" -#: src/fs/gnunet-publish.c:559 +#: src/fs/gnunet-publish.c:564 #, c-format msgid "You must specify one and only one filename for insertion.\n" msgstr "" -#: src/fs/gnunet-publish.c:565 +#: src/fs/gnunet-publish.c:570 #, c-format msgid "You must NOT specify an URI and a filename.\n" msgstr "" -#: src/fs/gnunet-publish.c:573 src/vpn/gnunet-vpn.c:214 +#: src/fs/gnunet-publish.c:578 src/vpn/gnunet-vpn.c:213 #, c-format msgid "Option `%s' is required when using option `%s'.\n" msgstr "" -#: src/fs/gnunet-publish.c:583 src/fs/gnunet-publish.c:590 -#: src/transport/gnunet-transport.c:560 +#: src/fs/gnunet-publish.c:588 src/fs/gnunet-publish.c:595 +#: src/transport/gnunet-transport.c:843 src/transport/gnunet-transport.c:873 #, c-format msgid "Option `%s' makes no sense without option `%s'.\n" msgstr "" -#: src/fs/gnunet-publish.c:612 -#, fuzzy, c-format -msgid "Could not create namespace `%s'\n" -msgstr "无法解析“%s”(%s):%s\n" - -#: src/fs/gnunet-publish.c:645 +#: src/fs/gnunet-publish.c:650 #, fuzzy, c-format msgid "Failed to access `%s': %s\n" msgstr "打开日志文件“%s”失败:%s\n" -#: src/fs/gnunet-publish.c:657 +#: src/fs/gnunet-publish.c:662 msgid "" "Failed to start meta directory scanner. Is gnunet-helper-publish-fs " "installed?\n" msgstr "" -#: src/fs/gnunet-publish.c:682 -msgid "disable adding the creation time to the metadata of the uploaded file" -msgstr "" - -#: src/fs/gnunet-publish.c:685 -msgid "do not use libextractor to add keywords or metadata" -msgstr "" - -#: src/fs/gnunet-publish.c:689 +#: src/fs/gnunet-publish.c:694 msgid "" "print list of extracted keywords that would be used, but do not perform " "upload" msgstr "" -#: src/fs/gnunet-publish.c:693 +#: src/fs/gnunet-publish.c:698 msgid "" "add an additional keyword for the top-level file or directory (this option " "can be specified multiple times)" msgstr "" -#: src/fs/gnunet-publish.c:700 +#: src/fs/gnunet-publish.c:705 msgid "" "do not index, perform full insertion (stores entire file in encrypted form " "in GNUnet database)" msgstr "" -#: src/fs/gnunet-publish.c:705 +#: src/fs/gnunet-publish.c:710 msgid "" "specify ID of an updated version to be published in the future (for " "namespace insertions only)" msgstr "" -#: src/fs/gnunet-publish.c:709 -msgid "specify the priority of the content" -msgstr "" - -#: src/fs/gnunet-publish.c:713 +#: src/fs/gnunet-publish.c:718 msgid "publish the files under the pseudonym NAME (place file into namespace)" msgstr "" -#: src/fs/gnunet-publish.c:719 +#: src/fs/gnunet-publish.c:724 msgid "" "only simulate the process but do not do any actual publishing (useful to " "compute URIs)" msgstr "" -#: src/fs/gnunet-publish.c:723 +#: src/fs/gnunet-publish.c:728 msgid "" "set the ID of this version of the publication (for namespace insertions only)" msgstr "" -#: src/fs/gnunet-publish.c:727 +#: src/fs/gnunet-publish.c:732 msgid "" "URI to be published (can be used instead of passing a file to add keywords " "to the file with the respective URI)" msgstr "" -#: src/fs/gnunet-publish.c:742 +#: src/fs/gnunet-publish.c:748 msgid "Publish a file or directory on GNUnet" msgstr "" -#: src/fs/gnunet-search.c:111 +#: src/fs/gnunet-search.c:114 #, c-format msgid "Failed to write directory with search results to `%s'\n" msgstr "" -#: src/fs/gnunet-search.c:181 +#: src/fs/gnunet-search.c:184 #, fuzzy, c-format msgid "Error searching: %s.\n" msgstr "创建用户出错" -#: src/fs/gnunet-search.c:231 +#: src/fs/gnunet-search.c:233 msgid "Could not create keyword URI from arguments.\n" msgstr "" -#: src/fs/gnunet-search.c:255 +#: src/fs/gnunet-search.c:257 msgid "Could not start searching.\n" msgstr "" -#: src/fs/gnunet-search.c:291 +#: src/fs/gnunet-search.c:288 msgid "write search results to file starting with PREFIX" msgstr "" -#: src/fs/gnunet-search.c:294 -msgid "automatically terminate search after VALUE ms" +#: src/fs/gnunet-search.c:291 +msgid "automatically terminate search after DELAY" msgstr "" -#: src/fs/gnunet-search.c:301 +#: src/fs/gnunet-search.c:298 msgid "automatically terminate search after VALUE results are found" msgstr "" -#: src/fs/gnunet-search.c:308 +#: src/fs/gnunet-search.c:309 msgid "Search GNUnet for files that were published on GNUnet" msgstr "" -#: src/fs/gnunet-service-fs.c:240 +#: src/fs/gnunet-service-fs.c:248 msgid "# running average P2P latency (ms)" msgstr "" -#: src/fs/gnunet-service-fs.c:300 src/fs/gnunet-service-fs.c:489 +#: src/fs/gnunet-service-fs.c:309 src/fs/gnunet-service-fs.c:523 msgid "# Loopback routes suppressed" msgstr "" -#: src/fs/gnunet-service-fs.c:581 src/hostlist/gnunet-daemon-hostlist.c:297 -#: src/topology/gnunet-daemon-topology.c:1330 -#: src/topology/gnunet-daemon-topology.c:1337 +#: src/fs/gnunet-service-fs.c:628 src/hostlist/gnunet-daemon-hostlist.c:297 +#: src/topology/gnunet-daemon-topology.c:1322 +#: src/topology/gnunet-daemon-topology.c:1329 #, fuzzy, c-format msgid "Failed to connect to `%s' service.\n" msgstr "初始化“%s”服务失败。\n" -#: src/fs/gnunet-service-fs_cp.c:696 +#: src/fs/gnunet-service-fs_cp.c:711 msgid "# migration stop messages received" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:700 +#: src/fs/gnunet-service-fs_cp.c:715 #, c-format -msgid "Migration of content to peer `%s' blocked for %llu ms\n" +msgid "Migration of content to peer `%s' blocked for %s\n" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:735 +#: src/fs/gnunet-service-fs_cp.c:751 msgid "# replies transmitted to other peers" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:741 +#: src/fs/gnunet-service-fs_cp.c:757 msgid "# replies dropped" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:766 src/fs/gnunet-service-fs_cp.c:1324 +#: src/fs/gnunet-service-fs_cp.c:782 src/fs/gnunet-service-fs_cp.c:1345 msgid "# P2P searches active" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:858 +#: src/fs/gnunet-service-fs_cp.c:875 msgid "# artificial delays introduced (ms)" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:911 +#: src/fs/gnunet-service-fs_cp.c:928 msgid "# replies dropped due to type mismatch" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:919 +#: src/fs/gnunet-service-fs_cp.c:936 msgid "# replies received for other peers" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:933 +#: src/fs/gnunet-service-fs_cp.c:950 msgid "# replies dropped due to insufficient cover traffic" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:971 +#: src/fs/gnunet-service-fs_cp.c:988 msgid "# P2P searches destroyed due to ultimate reply" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:1038 +#: src/fs/gnunet-service-fs_cp.c:1056 msgid "# requests done for free (low load)" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:1062 +#: src/fs/gnunet-service-fs_cp.c:1081 msgid "# request dropped, priority insufficient" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:1072 +#: src/fs/gnunet-service-fs_cp.c:1091 msgid "# requests done for a price (normal load)" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:1151 +#: src/fs/gnunet-service-fs_cp.c:1170 msgid "# GET requests received (from other peers)" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:1185 +#: src/fs/gnunet-service-fs_cp.c:1204 msgid "# requests dropped due to initiator not being connected" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:1207 +#: src/fs/gnunet-service-fs_cp.c:1227 msgid "# requests dropped due to missing reverse route" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:1267 +#: src/fs/gnunet-service-fs_cp.c:1288 msgid "# requests dropped due TTL underflow" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:1293 +#: src/fs/gnunet-service-fs_cp.c:1314 msgid "# requests dropped due to higher-TTL request" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:1322 +#: src/fs/gnunet-service-fs_cp.c:1343 msgid "# P2P query messages received and processed" msgstr "" -#: src/fs/gnunet-service-fs_cp.c:1687 +#: src/fs/gnunet-service-fs_cp.c:1713 msgid "# migration stop messages sent" msgstr "" -#: src/fs/gnunet-service-fs_indexing.c:113 -#: src/fs/gnunet-service-fs_indexing.c:163 -#, fuzzy, c-format -msgid "Configuration option `%s' in section `%s' missing.\n" -msgstr "配置文件“%s”已写入。\n" - -#: src/fs/gnunet-service-fs_indexing.c:121 -#: src/fs/gnunet-service-fs_indexing.c:177 +#: src/fs/gnunet-service-fs_indexing.c:130 +#: src/fs/gnunet-service-fs_indexing.c:181 #, fuzzy, c-format msgid "Could not open `%s'.\n" msgstr "无法解析“%s”(%s):%s\n" -#: src/fs/gnunet-service-fs_indexing.c:137 +#: src/fs/gnunet-service-fs_indexing.c:142 #, fuzzy, c-format msgid "Error writing `%s'.\n" msgstr "创建用户出错" -#: src/fs/gnunet-service-fs_indexing.c:228 +#: src/fs/gnunet-service-fs_indexing.c:237 #, c-format msgid "" "Index request received for file `%s' is already indexed as `%s'. Permitting " "anyway.\n" msgstr "" -#: src/fs/gnunet-service-fs_indexing.c:266 +#: src/fs/gnunet-service-fs_indexing.c:275 #, c-format msgid "Hash mismatch trying to index file `%s' which has hash `%s'\n" msgstr "" -#: src/fs/gnunet-service-fs_indexing.c:481 +#: src/fs/gnunet-service-fs_indexing.c:477 #, fuzzy, c-format msgid "Failed to delete bogus block: %s\n" msgstr "打开日志文件“%s”失败:%s\n" -#: src/fs/gnunet-service-fs_indexing.c:539 +#: src/fs/gnunet-service-fs_indexing.c:542 msgid "# index blocks removed: original file inaccessible" msgstr "" -#: src/fs/gnunet-service-fs_indexing.c:554 +#: src/fs/gnunet-service-fs_indexing.c:557 #, fuzzy, c-format msgid "Could not access indexed file `%s' (%s) at offset %llu: %s\n" msgstr "无法解析“%s”(%s):%s\n" -#: src/fs/gnunet-service-fs_indexing.c:556 +#: src/fs/gnunet-service-fs_indexing.c:559 msgid "not indexed" msgstr "" -#: src/fs/gnunet-service-fs_indexing.c:571 +#: src/fs/gnunet-service-fs_indexing.c:574 #, c-format msgid "Indexed file `%s' changed at offset %llu\n" msgstr "" -#: src/fs/gnunet-service-fs_lc.c:202 src/fs/gnunet-service-fs_lc.c:362 -#: src/fs/gnunet-service-fs_lc.c:488 +#: src/fs/gnunet-service-fs_lc.c:202 src/fs/gnunet-service-fs_lc.c:369 msgid "# client searches active" msgstr "" @@ -2760,153 +2766,181 @@ msgstr "" msgid "# replies received for local clients" msgstr "" -#: src/fs/gnunet-service-fs_lc.c:321 +#: src/fs/gnunet-service-fs_lc.c:328 msgid "# client searches received" msgstr "" -#: src/fs/gnunet-service-fs_lc.c:356 +#: src/fs/gnunet-service-fs_lc.c:363 msgid "# client searches updated (merged content seen list)" msgstr "" -#: src/fs/gnunet-service-fs_pe.c:265 +#: src/fs/gnunet-service-fs_pe.c:269 msgid "# average retransmission delay (ms)" msgstr "" -#: src/fs/gnunet-service-fs_pe.c:391 +#: src/fs/gnunet-service-fs_pe.c:400 msgid "# transmission failed (core has no bandwidth)" msgstr "" -#: src/fs/gnunet-service-fs_pe.c:420 +#: src/fs/gnunet-service-fs_pe.c:433 msgid "# query messages sent to other peers" msgstr "" -#: src/fs/gnunet-service-fs_pe.c:469 +#: src/fs/gnunet-service-fs_pe.c:482 msgid "# delay heap timeout" msgstr "" -#: src/fs/gnunet-service-fs_pe.c:476 +#: src/fs/gnunet-service-fs_pe.c:490 msgid "# query plans executed" msgstr "" -#: src/fs/gnunet-service-fs_pe.c:538 +#: src/fs/gnunet-service-fs_pe.c:550 msgid "# requests merged" msgstr "" -#: src/fs/gnunet-service-fs_pe.c:544 +#: src/fs/gnunet-service-fs_pe.c:558 msgid "# requests refreshed" msgstr "" -#: src/fs/gnunet-service-fs_pe.c:597 src/fs/gnunet-service-fs_pe.c:681 -#: src/fs/gnunet-service-fs_pe.c:748 +#: src/fs/gnunet-service-fs_pe.c:612 src/fs/gnunet-service-fs_pe.c:696 +#: src/fs/gnunet-service-fs_pe.c:767 msgid "# query plan entries" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:285 +#: src/fs/gnunet-service-fs_pr.c:312 msgid "# Pending requests created" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:367 src/fs/gnunet-service-fs_pr.c:616 +#: src/fs/gnunet-service-fs_pr.c:404 src/fs/gnunet-service-fs_pr.c:667 msgid "# Pending requests active" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:779 +#: src/fs/gnunet-service-fs_pr.c:835 msgid "# replies received and matched" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:808 +#: src/fs/gnunet-service-fs_pr.c:868 msgid "# duplicate replies discarded (bloomfilter)" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:822 +#: src/fs/gnunet-service-fs_pr.c:877 +msgid "# irrelevant replies discarded" +msgstr "" + +#: src/fs/gnunet-service-fs_pr.c:891 #, c-format msgid "Unsupported block type %u\n" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:835 +#: src/fs/gnunet-service-fs_pr.c:904 msgid "# results found locally" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:953 +#: src/fs/gnunet-service-fs_pr.c:1025 msgid "# Datastore `PUT' failures" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:980 +#: src/fs/gnunet-service-fs_pr.c:1052 msgid "# storage requests dropped due to high load" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1015 +#: src/fs/gnunet-service-fs_pr.c:1087 msgid "# Replies received from DHT" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1106 +#: src/fs/gnunet-service-fs_pr.c:1221 +msgid "# Replies received from STREAM" +msgstr "" + +#: src/fs/gnunet-service-fs_pr.c:1273 #, c-format -msgid "Datastore lookup already took %llu ms!\n" +msgid "Datastore lookup already took %s!\n" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1127 +#: src/fs/gnunet-service-fs_pr.c:1293 #, c-format -msgid "On-demand lookup already took %llu ms!\n" +msgid "On-demand lookup already took %s!\n" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1174 +#: src/fs/gnunet-service-fs_pr.c:1340 msgid "# Datastore lookups concluded (no results)" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1188 +#: src/fs/gnunet-service-fs_pr.c:1355 msgid "# Datastore lookups concluded (seen all)" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1197 +#: src/fs/gnunet-service-fs_pr.c:1364 msgid "# Datastore lookups aborted (more than MAX_RESULTS)" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1211 +#: src/fs/gnunet-service-fs_pr.c:1379 msgid "# requested DBLOCK or IBLOCK not found" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1224 +#: src/fs/gnunet-service-fs_pr.c:1393 msgid "# on-demand blocks matched requests" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1237 +#: src/fs/gnunet-service-fs_pr.c:1406 msgid "# on-demand lookups performed successfully" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1242 +#: src/fs/gnunet-service-fs_pr.c:1411 msgid "# on-demand lookups failed" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1269 src/fs/gnunet-service-fs_pr.c:1309 -#: src/fs/gnunet-service-fs_pr.c:1447 +#: src/fs/gnunet-service-fs_pr.c:1438 src/fs/gnunet-service-fs_pr.c:1478 +#: src/fs/gnunet-service-fs_pr.c:1619 msgid "# Datastore lookups concluded (error queueing)" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1327 +#: src/fs/gnunet-service-fs_pr.c:1496 msgid "# Datastore lookups concluded (found last result)" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1338 +#: src/fs/gnunet-service-fs_pr.c:1507 msgid "# Datastore lookups concluded (load too high)" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1424 +#: src/fs/gnunet-service-fs_pr.c:1595 msgid "# Datastore lookups initiated" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1508 +#: src/fs/gnunet-service-fs_pr.c:1680 msgid "# GAP PUT messages received" msgstr "" -#: src/fs/gnunet-service-fs_pr.c:1601 src/fs/gnunet-service-fs_pr.c:1610 -#, fuzzy, c-format -msgid "Configuration fails to specify `%s', assuming default value." -msgstr "配置文件“%s”已写入。\n" - #: src/fs/gnunet-service-fs_push.c:629 -#, c-format -msgid "" -"Invalid value specified for option `%s' in section `%s', content pushing " -"disabled\n" +msgid "time required, content pushing disabled" +msgstr "" + +#: src/fs/gnunet-service-fs_stream.c:777 +msgid "# replies received via stream" +msgstr "" + +#: src/fs/gnunet-service-fs_stream.c:791 +msgid "# replies received via stream dropped" +msgstr "" + +#: src/fs/gnunet-service-fs_stream.c:930 +#: src/fs/gnunet-service-fs_stream.c:1384 +#, fuzzy +msgid "# stream connections active" +msgstr "" +"\n" +"按任意键继续\n" + +#: src/fs/gnunet-service-fs_stream.c:1166 +msgid "# Blocks transferred via stream" +msgstr "" + +#: src/fs/gnunet-service-fs_stream.c:1326 +msgid "# queries received via stream" +msgstr "" + +#: src/fs/gnunet-service-fs_stream.c:1376 +msgid "# stream client connections rejected" msgstr "" #: src/fs/gnunet-unindex.c:89 @@ -2914,157 +2948,280 @@ msgstr "" msgid "Unindexing at %llu/%llu (%s remaining)\n" msgstr "" -#: src/fs/gnunet-unindex.c:96 +#: src/fs/gnunet-unindex.c:95 #, c-format msgid "Error unindexing: %s.\n" msgstr "" -#: src/fs/gnunet-unindex.c:101 +#: src/fs/gnunet-unindex.c:100 msgid "Unindexing done.\n" msgstr "" -#: src/fs/gnunet-unindex.c:131 +#: src/fs/gnunet-unindex.c:130 #, c-format msgid "You must specify one and only one filename for unindexing.\n" msgstr "" -#: src/fs/gnunet-unindex.c:148 +#: src/fs/gnunet-unindex.c:147 msgid "Could not start unindex operation.\n" msgstr "" -#: src/fs/gnunet-unindex.c:176 +#: src/fs/gnunet-unindex.c:179 msgid "Unindex a file that was previously indexed with gnunet-publish." msgstr "" -#: src/fs/plugin_block_fs.c:131 -msgid "Reply mismatched in terms of namespace. Discarded.\n" -msgstr "" +#: src/gns/gns_api.c:598 +#, fuzzy +msgid "Failed to serialize lookup reply from GNS service!\n" +msgstr "初始化“%s”服务失败。\n" -#: src/gns/gnunet-gns.c:191 +#: src/gns/gnunet-dns2gns.c:192 #, fuzzy +msgid "Failed to pack DNS response into UDP packet!\n" +msgstr "打开日志文件“%s”失败:%s\n" + +#: src/gns/gnunet-dns2gns.c:367 +#, c-format +msgid "Cannot parse DNS request from %s\n" +msgstr "" + +#: src/gns/gnunet-dns2gns.c:383 +#, c-format +msgid "Received malformed DNS request from %s\n" +msgstr "" + +#: src/gns/gnunet-dns2gns.c:391 +#, c-format +msgid "Received unsupported DNS request from %s\n" +msgstr "" + +#: src/gns/gnunet-dns2gns.c:679 +msgid "IP of recursive DNS resolver to use (required)" +msgstr "" + +#: src/gns/gnunet-dns2gns.c:682 +msgid "Authoritative DNS suffix to use (optional); default: zkey.eu" +msgstr "" + +#: src/gns/gnunet-dns2gns.c:685 +msgid "Authoritative FCFS suffix to use (optional); default: fcfs.zkey.eu" +msgstr "" + +#: src/gns/gnunet-dns2gns.c:688 +msgid "UDP port to listen on for inbound DNS requests; default: 53" +msgstr "" + +#: src/gns/gnunet-dns2gns.c:701 +msgid "GNUnet DNS-to-GNS proxy (a DNS server)" +msgstr "" + +#: src/gns/gnunet-gns.c:221 +#, fuzzy, c-format msgid "Failed to connect to GNS\n" msgstr "初始化“%s”服务失败。\n" -#: src/gns/gnunet-gns.c:232 -msgid "try to shorten a given GNS name" +#: src/gns/gnunet-gns.c:335 +#, c-format +msgid "Please specify lookup, shorten or authority operation!\n" msgstr "" -#: src/gns/gnunet-gns.c:235 -msgid "Lookup a record using GNS (NOT IMPLEMENTED)" +#: src/gns/gnunet-gns.c:356 +#, fuzzy +msgid "try to shorten a given name" +msgstr "初始化“%s”服务失败。\n" + +#: src/gns/gnunet-gns.c:359 +msgid "Lookup a record for the given name" msgstr "" -#: src/gns/gnunet-gns.c:238 +#: src/gns/gnunet-gns.c:362 msgid "Get the authority of a particular name" msgstr "" -#: src/gns/gnunet-gns.c:241 -msgid "Specify the type of the record lookup" +#: src/gns/gnunet-gns.c:365 +msgid "Specify the type of the record to lookup" msgstr "" -#: src/gns/gnunet-gns.c:244 +#: src/gns/gnunet-gns.c:368 msgid "No unneeded output" msgstr "" -#: src/gns/gnunet-gns.c:255 +#: src/gns/gnunet-gns.c:381 msgid "GNUnet GNS access tool" msgstr "" -#: src/gns/gnunet-gns-fcfsd.c:280 +#: src/gns/gnunet-gns-fcfsd.c:451 #, fuzzy, c-format msgid "Unsupported form value `%s'\n" msgstr "未知的命令“%s”。\n" -#: src/gns/gnunet-gns-fcfsd.c:333 +#: src/gns/gnunet-gns-fcfsd.c:480 #, fuzzy, c-format msgid "Failed to create record for domain `%s': %s\n" msgstr "解析配置文件“%s”失败\n" -#: src/gns/gnunet-gns-fcfsd.c:377 +#: src/gns/gnunet-gns-fcfsd.c:524 #, c-format msgid "Found existing name `%s' for the given key\n" msgstr "" -#: src/gns/gnunet-gns-fcfsd.c:439 +#: src/gns/gnunet-gns-fcfsd.c:586 #, c-format msgid "Found %u existing records for domain `%s'\n" msgstr "" -#: src/gns/gnunet-gns-fcfsd.c:498 +#: src/gns/gnunet-gns-fcfsd.c:648 #, fuzzy, c-format msgid "Failed to create page for `%s'\n" msgstr "发送消息失败。\n" -#: src/gns/gnunet-gns-fcfsd.c:514 +#: src/gns/gnunet-gns-fcfsd.c:664 #, fuzzy, c-format msgid "Failed to setup post processor for `%s'\n" msgstr "解析配置文件“%s”失败\n" -#: src/gns/gnunet-gns-fcfsd.c:725 src/gns/gnunet-gns-fcfsd.c:737 -#, fuzzy, c-format -msgid "Option `%s' not specified in configuration section `%s'\n" -msgstr "配置文件“%s”已写入。\n" +#: src/gns/gnunet-gns-fcfsd.c:700 +msgid "Domain name must not contain `.'\n" +msgstr "" + +#: src/gns/gnunet-gns-fcfsd.c:708 +msgid "Domain name must not contain `+'\n" +msgstr "" -#: src/gns/gnunet-gns-fcfsd.c:747 src/namestore/gnunet-namestore.c:299 +#: src/gns/gnunet-gns-fcfsd.c:912 src/namestore/gnunet-namestore.c:364 #, fuzzy msgid "Failed to read or create private zone key\n" msgstr "无法为守护程序创建用户账户。" -#: src/gns/gnunet-gns-fcfsd.c:757 src/namestore/gnunet-namestore.c:310 +#: src/gns/gnunet-gns-fcfsd.c:922 src/namestore/gnunet-namestore.c:375 #, fuzzy msgid "Failed to connect to namestore\n" msgstr "初始化“%s”服务失败。\n" -#: src/gns/gnunet-gns-fcfsd.c:773 src/gns/gnunet-gns-proxy.c:525 +#: src/gns/gnunet-gns-fcfsd.c:938 src/gns/gnunet-gns-proxy.c:2857 #, fuzzy msgid "Failed to start HTTP server\n" msgstr "初始化“%s”服务失败。\n" -#: src/gns/gnunet-gns-fcfsd.c:804 +#: src/gns/gnunet-gns-fcfsd.c:972 msgid "GNUnet GNS first come first serve registration service" msgstr "" -#: src/gns/gnunet-gns-proxy.c:800 -msgid "listen on specified port" +#: src/gns/gnunet-gns-proxy.c:2494 +#, fuzzy, c-format +msgid "Unable to import private key from file `%s'\n" +msgstr "无法创建用户账户:" + +#: src/gns/gnunet-gns-proxy.c:2522 +#, fuzzy, c-format +msgid "Unable to import certificate %s\n" +msgstr "无法保存配置文件“%s”:" + +#: src/gns/gnunet-gns-proxy.c:3510 +msgid "listen on specified port (default: 7777)" +msgstr "" + +#: src/gns/gnunet-gns-proxy.c:3513 +msgid "pem file to use as CA" msgstr "" -#: src/gns/gnunet-gns-proxy.c:811 +#: src/gns/gnunet-gns-proxy.c:3525 msgid "GNUnet GNS proxy" msgstr "" -#: src/hello/gnunet-hello.c:122 +#: src/gns/gnunet-service-gns.c:486 +#, c-format +msgid "Records for name `%s' in zone %s too large to fit into DHT" +msgstr "" + +#: src/gns/gnunet-service-gns.c:1216 +#, fuzzy +msgid "Failed to connect to the namestore!\n" +msgstr "初始化“%s”服务失败。\n" + +#: src/gns/gnunet-service-gns.c:1277 +#, fuzzy +msgid "Could not connect to DHT!\n" +msgstr "无法连接到 %s:%u:%s\n" + +#: src/gns/gnunet-service-gns.c:1288 +#, fuzzy +msgid "Unable to initialize resolver!\n" +msgstr "无法初始化 SQLite:%s。\n" + +#: src/gns/gnunet-service-gns_resolver.c:3439 +#, c-format +msgid "Not a GADS TLD: `%s'\n" +msgstr "" + +#: src/hello/gnunet-hello.c:118 msgid "Call with name of HELLO file to modify.\n" msgstr "" -#: src/hello/gnunet-hello.c:128 +#: src/hello/gnunet-hello.c:124 #, fuzzy, c-format msgid "Error accessing file `%s': %s\n" msgstr "创建用户出错" -#: src/hello/gnunet-hello.c:136 +#: src/hello/gnunet-hello.c:132 #, c-format msgid "File `%s' is too big to be a HELLO\n" msgstr "" -#: src/hello/gnunet-hello.c:143 +#: src/hello/gnunet-hello.c:139 #, c-format msgid "File `%s' is too small to be a HELLO\n" msgstr "" -#: src/hello/gnunet-hello.c:153 src/hello/gnunet-hello.c:181 +#: src/hello/gnunet-hello.c:149 src/hello/gnunet-hello.c:177 #, fuzzy, c-format msgid "Error opening file `%s': %s\n" msgstr "创建用户出错" -#: src/hello/gnunet-hello.c:169 +#: src/hello/gnunet-hello.c:165 #, c-format msgid "Did not find well-formed HELLO in file `%s'\n" msgstr "" -#: src/hello/gnunet-hello.c:193 +#: src/hello/gnunet-hello.c:189 #, fuzzy, c-format msgid "Error writing HELLO to file `%s': %s\n" msgstr "创建用户出错" +#: src/hello/hello.c:904 +#, fuzzy +msgid "Failed to parse HELLO message: missing expiration time\n" +msgstr "保存配置失败。" + +#: src/hello/hello.c:913 +#, fuzzy +msgid "Failed to parse HELLO message: invalid expiration time\n" +msgstr "保存配置失败。" + +#: src/hello/hello.c:923 +#, fuzzy +msgid "Failed to parse HELLO message: malformed\n" +msgstr "打开日志文件“%s”失败:%s\n" + +#: src/hello/hello.c:933 +msgid "Failed to parse HELLO message: missing transport plugin\n" +msgstr "" + +#: src/hello/hello.c:950 +#, c-format +msgid "Plugin `%s' not found\n" +msgstr "" + +#: src/hello/hello.c:959 +#, c-format +msgid "Plugin `%s' does not support URIs yet\n" +msgstr "" + +#: src/hello/hello.c:978 +#, fuzzy, c-format +msgid "Failed to parse `%s' as an address for plugin `%s'\n" +msgstr "找不到接口“%s”的一个 IP 地址。\n" + #: src/hostlist/gnunet-daemon-hostlist.c:264 msgid "" "None of the functions for the hostlist daemon were enabled. I have no " @@ -3089,7 +3246,7 @@ msgstr "" msgid "provide a hostlist server" msgstr "" -#: src/hostlist/gnunet-daemon-hostlist.c:341 +#: src/hostlist/gnunet-daemon-hostlist.c:344 msgid "GNUnet hostlist server and client" msgstr "" @@ -3110,173 +3267,137 @@ msgstr "" msgid "# valid HELLOs downloaded from hostlist servers" msgstr "" -#: src/hostlist/hostlist-client.c:375 src/hostlist/hostlist-client.c:396 -#, c-format -msgid "No `%s' specified in `%s' configuration, will not bootstrap.\n" -msgstr "" - -#: src/hostlist/hostlist-client.c:473 src/hostlist/hostlist-client.c:683 -#: src/hostlist/hostlist-client.c:689 src/hostlist/hostlist-client.c:741 -#: src/hostlist/hostlist-client.c:750 src/hostlist/hostlist-client.c:871 -#: src/hostlist/hostlist-client.c:961 src/hostlist/hostlist-client.c:966 -#: src/transport/plugin_transport_http_client.c:110 -#: src/transport/plugin_transport_http_client.c:125 +#: src/hostlist/hostlist-client.c:469 src/hostlist/hostlist-client.c:680 +#: src/hostlist/hostlist-client.c:686 src/hostlist/hostlist-client.c:738 +#: src/hostlist/hostlist-client.c:747 src/hostlist/hostlist-client.c:868 +#: src/hostlist/hostlist-client.c:958 src/hostlist/hostlist-client.c:963 +#: src/transport/plugin_transport_http_client.c:1052 +#: src/transport/plugin_transport_http_client.c:1067 #, c-format msgid "%s failed at %s:%d: `%s'\n" msgstr "" -#: src/hostlist/hostlist-client.c:593 src/hostlist/hostlist-client.c:1331 +#: src/hostlist/hostlist-client.c:589 src/hostlist/hostlist-client.c:1325 msgid "# advertised hostlist URIs" msgstr "" -#: src/hostlist/hostlist-client.c:623 +#: src/hostlist/hostlist-client.c:619 #, c-format msgid "# advertised URI `%s' downloaded" msgstr "" -#: src/hostlist/hostlist-client.c:664 +#: src/hostlist/hostlist-client.c:661 #, c-format msgid "" "Advertised hostlist with URI `%s' could not be downloaded. Advertised URI " "gets dismissed.\n" msgstr "" -#: src/hostlist/hostlist-client.c:802 +#: src/hostlist/hostlist-client.c:799 #, c-format msgid "Timeout trying to download hostlist from `%s'\n" msgstr "" -#: src/hostlist/hostlist-client.c:816 +#: src/hostlist/hostlist-client.c:813 #, c-format msgid "Download limit of %u bytes exceeded, stopping download\n" msgstr "" -#: src/hostlist/hostlist-client.c:836 +#: src/hostlist/hostlist-client.c:833 #, fuzzy, c-format msgid "Download of hostlist from `%s' failed: `%s'\n" msgstr "打开日志文件“%s”失败:%s\n" -#: src/hostlist/hostlist-client.c:842 +#: src/hostlist/hostlist-client.c:839 #, c-format msgid "Download of hostlist `%s' completed.\n" msgstr "" -#: src/hostlist/hostlist-client.c:850 +#: src/hostlist/hostlist-client.c:847 #, c-format msgid "Adding successfully tested hostlist `%s' datastore.\n" msgstr "" -#: src/hostlist/hostlist-client.c:903 +#: src/hostlist/hostlist-client.c:900 #, c-format msgid "Bootstrapping using hostlist at `%s'.\n" msgstr "" -#: src/hostlist/hostlist-client.c:911 +#: src/hostlist/hostlist-client.c:908 msgid "# hostlist downloads initiated" msgstr "" -#: src/hostlist/hostlist-client.c:1037 src/hostlist/hostlist-client.c:1505 +#: src/hostlist/hostlist-client.c:1035 src/hostlist/hostlist-client.c:1498 msgid "# milliseconds between hostlist downloads" msgstr "" -#: src/hostlist/hostlist-client.c:1046 -#, c-format -msgid "Have %u/%u connections. Will consider downloading hostlist in %llums\n" -msgstr "" - -#: src/hostlist/hostlist-client.c:1084 -msgid "Scheduled saving of hostlists\n" -msgstr "" - -#: src/hostlist/hostlist-client.c:1088 +#: src/hostlist/hostlist-client.c:1043 #, c-format -msgid "Hostlists will be saved to file again in %llums\n" +msgid "Have %u/%u connections. Will consider downloading hostlist in %s\n" msgstr "" -#: src/hostlist/hostlist-client.c:1111 src/hostlist/hostlist-client.c:1127 +#: src/hostlist/hostlist-client.c:1107 src/hostlist/hostlist-client.c:1123 msgid "# active connections" msgstr "" -#: src/hostlist/hostlist-client.c:1242 -#, c-format -msgid "Initial time between hostlist downloads is %llums\n" -msgstr "" - #: src/hostlist/hostlist-client.c:1273 #, c-format -msgid "" -"No `%s' specified in `%s' configuration, cannot load hostlists from file.\n" -msgstr "" - -#: src/hostlist/hostlist-client.c:1279 -#, c-format msgid "Loading saved hostlist entries from file `%s' \n" msgstr "" -#: src/hostlist/hostlist-client.c:1283 +#: src/hostlist/hostlist-client.c:1277 #, c-format -msgid "Hostlist file `%s' is not existing\n" +msgid "Hostlist file `%s' does not exist\n" msgstr "" -#: src/hostlist/hostlist-client.c:1294 +#: src/hostlist/hostlist-client.c:1288 #, fuzzy, c-format msgid "Could not open file `%s' for reading to load hostlists: %s\n" msgstr "无法解析“%s”来确定已方的 IP 地址:%s\n" -#: src/hostlist/hostlist-client.c:1327 +#: src/hostlist/hostlist-client.c:1321 #, c-format msgid "%u hostlist URIs loaded from file\n" msgstr "" -#: src/hostlist/hostlist-client.c:1329 +#: src/hostlist/hostlist-client.c:1323 msgid "# hostlist URIs read from file" msgstr "" -#: src/hostlist/hostlist-client.c:1362 -#, c-format -msgid "" -"No `%s' specified in `%s' configuration, cannot save hostlists to file.\n" -msgstr "" - -#: src/hostlist/hostlist-client.c:1376 +#: src/hostlist/hostlist-client.c:1368 #, fuzzy, c-format msgid "Could not open file `%s' for writing to save hostlists: %s\n" msgstr "无法解析“%s”来确定已方的 IP 地址:%s\n" -#: src/hostlist/hostlist-client.c:1381 +#: src/hostlist/hostlist-client.c:1373 #, c-format msgid "Writing %u hostlist URIs to `%s'\n" msgstr "" -#: src/hostlist/hostlist-client.c:1405 src/hostlist/hostlist-client.c:1422 +#: src/hostlist/hostlist-client.c:1397 src/hostlist/hostlist-client.c:1414 #, c-format msgid "Error writing hostlist URIs to file `%s'\n" msgstr "" -#: src/hostlist/hostlist-client.c:1417 +#: src/hostlist/hostlist-client.c:1409 msgid "# hostlist URIs written to file" msgstr "" -#: src/hostlist/hostlist-client.c:1470 +#: src/hostlist/hostlist-client.c:1463 msgid "Learning is enabled on this peer\n" msgstr "" -#: src/hostlist/hostlist-client.c:1473 -#, c-format -msgid "Hostlists will be saved to file again in %llums\n" -msgstr "" - -#: src/hostlist/hostlist-client.c:1482 +#: src/hostlist/hostlist-client.c:1475 msgid "Learning is not enabled on this peer\n" msgstr "" -#: src/hostlist/hostlist-client.c:1494 +#: src/hostlist/hostlist-client.c:1487 #, c-format msgid "" "Since learning is not enabled on this peer, hostlist file `%s' was removed\n" msgstr "" -#: src/hostlist/hostlist-client.c:1498 +#: src/hostlist/hostlist-client.c:1491 #, c-format msgid "Hostlist file `%s' could not be removed\n" msgstr "" @@ -3290,9 +3411,9 @@ msgid "expired addresses encountered" msgstr "" #: src/hostlist/hostlist-server.c:184 src/hostlist/hostlist-server.c:425 -#: src/peerinfo-tool/gnunet-peerinfo.c:403 -#: src/peerinfo-tool/gnunet-peerinfo.c:519 -#: src/topology/gnunet-daemon-topology.c:927 +#: src/peerinfo-tool/gnunet-peerinfo.c:331 +#: src/peerinfo-tool/gnunet-peerinfo.c:386 +#: src/topology/gnunet-daemon-topology.c:922 #, c-format msgid "Error in communication with PEERINFO service: %s\n" msgstr "" @@ -3314,10 +3435,6 @@ msgstr "" msgid "hostlist requests refused (not HTTP GET)" msgstr "" -#: src/hostlist/hostlist-server.c:273 -msgid "Sending 100 CONTINUE reply\n" -msgstr "" - #: src/hostlist/hostlist-server.c:279 #, c-format msgid "Refusing `%s' request with %llu bytes of upload data\n" @@ -3351,64 +3468,101 @@ msgstr "" msgid "Advertisement message could not be queued by core\n" msgstr "" -#: src/hostlist/hostlist-server.c:561 +#: src/hostlist/hostlist-server.c:562 #, c-format msgid "Invalid port number %llu. Exiting.\n" msgstr "" -#: src/hostlist/hostlist-server.c:570 +#: src/hostlist/hostlist-server.c:571 #, c-format msgid "Hostlist service starts on %s:%llu\n" msgstr "" -#: src/hostlist/hostlist-server.c:584 +#: src/hostlist/hostlist-server.c:585 #, c-format msgid "Address to obtain hostlist: `%s'\n" msgstr "" -#: src/hostlist/hostlist-server.c:624 +#: src/hostlist/hostlist-server.c:625 #, fuzzy, c-format msgid "`%s' is not a valid IP address! Ignoring BINDTOIP.\n" msgstr "“%s”不可用。\n" -#: src/hostlist/hostlist-server.c:666 +#: src/hostlist/hostlist-server.c:667 #, c-format msgid "Could not start hostlist HTTP server on port %u\n" msgstr "" -#: src/integration-tests/connection_watchdog.c:997 +#: src/integration-tests/connection_watchdog.c:1001 #, c-format msgid "Transport plugin: `%s' port %llu\n" msgstr "" -#: src/integration-tests/connection_watchdog.c:1030 +#: src/integration-tests/connection_watchdog.c:1034 #, fuzzy, c-format msgid "Found %u transport plugins: `%s'\n" msgstr "解析配置文件“%s”失败\n" -#: src/integration-tests/connection_watchdog.c:1089 +#: src/integration-tests/connection_watchdog.c:1093 msgid "Send ping messages to test connectivity (default == NO)" msgstr "" -#: src/integration-tests/connection_watchdog.c:1095 -#: src/template/gnunet-template.c:68 +#: src/integration-tests/connection_watchdog.c:1102 +#: src/template/gnunet-template.c:70 msgid "help text" msgstr "" -#: src/mesh/gnunet-service-mesh.c:4590 -msgid "Wrong CORE service\n" +#: src/mesh/gnunet-mesh.c:211 +msgid "provide information about all tunnels (continuously) NOT IMPLEMENTED" msgstr "" -#: src/mesh/gnunet-service-mesh.c:4784 +#: src/mesh/gnunet-mesh.c:214 #, fuzzy -msgid "Mesh service is lacking key configuration settings. Exiting.\n" -msgstr "立即保存配置?" +msgid "provide information about a particular tunnel" +msgstr "无法获取有关用户“%s”的信息:%s\n" -#: src/mesh/gnunet-service-mesh.c:4793 +#: src/mesh/gnunet-mesh.c:224 #, fuzzy -msgid "Mesh service could not access hostkey. Exiting.\n" +msgid "Print information about mesh tunnels and peers." +msgstr "无法获取有关用户“%s”的信息:%s\n" + +#: src/mesh/gnunet-service-mesh.c:8015 src/mesh/gnunet-service-mesh-new.c:8015 +msgid "Wrong CORE service\n" +msgstr "" + +#: src/mesh/gnunet-service-mesh.c:8232 src/mesh/gnunet-service-mesh-new.c:8232 +#, fuzzy, c-format +msgid "Mesh service could not access hostkey: %s. Exiting.\n" msgstr "找不到接口“%s”的一个 IP 地址。\n" +#: src/mesh/gnunet-service-mesh.c:8314 src/mesh/gnunet-service-mesh.c:8326 +#: src/mesh/gnunet-service-mesh.c:8338 src/mesh/gnunet-service-mesh.c:8352 +#: src/mesh/gnunet-service-mesh.c:8364 src/mesh/gnunet-service-mesh.c:8376 +#: src/mesh/gnunet-service-mesh.c:8388 src/mesh/gnunet-service-mesh-new.c:8321 +#: src/mesh/gnunet-service-mesh-new.c:8333 +#: src/mesh/gnunet-service-mesh-new.c:8345 +#: src/mesh/gnunet-service-mesh-new.c:8359 +#: src/mesh/gnunet-service-mesh-new.c:8371 +#: src/mesh/gnunet-service-mesh-new.c:8383 +#: src/mesh/gnunet-service-mesh-new.c:8395 +#: src/regex/gnunet-daemon-regexprofiler.c:335 +#: src/regex/gnunet-daemon-regexprofiler.c:347 +#: src/regex/gnunet-daemon-regexprofiler.c:360 +#: src/regex/gnunet-daemon-regexprofiler.c:373 +#: src/regex/gnunet-regex-simulation-profiler.c:659 +#, fuzzy, c-format +msgid "%s service is lacking key configuration settings (%s). Exiting.\n" +msgstr "立即保存配置?" + +#: src/mesh/gnunet-service-mesh.c:8400 src/mesh/gnunet-service-mesh.c:8410 +#: src/mesh/gnunet-service-mesh.c:8421 src/mesh/gnunet-service-mesh-new.c:8407 +#: src/mesh/gnunet-service-mesh-new.c:8417 +#: src/mesh/gnunet-service-mesh-new.c:8428 +#, fuzzy, c-format +msgid "" +"%s service is lacking key configuration settings (%s). Using default (%u).\n" +msgstr "立即保存配置?" + #: src/mysql/mysql.c:174 #, c-format msgid "Trying to use file `%s' for MySQL configuration.\n" @@ -3419,195 +3573,320 @@ msgstr "" msgid "Could not access file `%s': %s\n" msgstr "无法解析“%s”(%s):%s\n" -#: src/namestore/gnunet-namestore.c:157 +#: src/namestore/gnunet-namestore.c:212 #, c-format msgid "Adding record failed: %s\n" msgstr "" -#: src/namestore/gnunet-namestore.c:183 +#: src/namestore/gnunet-namestore.c:243 #, c-format msgid "Deleting record failed: %s\n" msgstr "" -#: src/namestore/gnunet-namestore.c:239 +#: src/namestore/gnunet-namestore.c:304 #, c-format msgid "\tCorrupt or unsupported record of type %u\n" msgstr "" -#: src/namestore/gnunet-namestore.c:276 -#, c-format -msgid "Option `%s' not given, but I need a zone key file!\n" +#: src/namestore/gnunet-namestore.c:320 +msgid "for at least" msgstr "" -#: src/namestore/gnunet-namestore.c:281 -#, fuzzy, c-format -msgid "Using default zone file `%s'\n" -msgstr "卸载 GNUnet 服务" +#: src/namestore/gnunet-namestore.c:321 +msgid "until" +msgstr "" -#: src/namestore/gnunet-namestore.c:291 +#: src/namestore/gnunet-namestore.c:356 #, c-format msgid "No options given\n" msgstr "" -#: src/namestore/gnunet-namestore.c:321 +#: src/namestore/gnunet-namestore.c:386 #, fuzzy, c-format msgid "Unsupported type `%s'\n" msgstr "未知的命令“%s”。\n" -#: src/namestore/gnunet-namestore.c:328 src/namestore/gnunet-namestore.c:350 -#: src/namestore/gnunet-namestore.c:374 src/namestore/gnunet-namestore.c:384 -#: src/namestore/gnunet-namestore.c:409 +#: src/namestore/gnunet-namestore.c:394 src/namestore/gnunet-namestore.c:418 +#: src/namestore/gnunet-namestore.c:465 src/namestore/gnunet-namestore.c:477 +#: src/namestore/gnunet-namestore.c:518 #, fuzzy, c-format msgid "Missing option `%s' for operation `%s'\n" msgstr "配置文件“%s”已写入。\n" -#: src/namestore/gnunet-namestore.c:329 src/namestore/gnunet-namestore.c:351 +#: src/namestore/gnunet-namestore.c:395 src/namestore/gnunet-namestore.c:419 msgid "add/del" msgstr "" -#: src/namestore/gnunet-namestore.c:341 +#: src/namestore/gnunet-namestore.c:408 #, c-format msgid "Value `%s' invalid for record type `%s'\n" msgstr "" -#: src/namestore/gnunet-namestore.c:366 +#: src/namestore/gnunet-namestore.c:446 #, fuzzy, c-format msgid "Invalid time format `%s'\n" msgstr "IP 格式无效:“%s”\n" -#: src/namestore/gnunet-namestore.c:375 src/namestore/gnunet-namestore.c:385 +#: src/namestore/gnunet-namestore.c:455 +#, c-format +msgid "" +"Deletion requires either absolute time, or no time at all. Got relative time " +"`%s' instead.\n" +msgstr "" + +#: src/namestore/gnunet-namestore.c:466 src/namestore/gnunet-namestore.c:478 +#: src/namestore/gnunet-namestore.c:497 msgid "add" msgstr "" -#: src/namestore/gnunet-namestore.c:410 +#: src/namestore/gnunet-namestore.c:496 +#, fuzzy, c-format +msgid "No valid expiration time for operation `%s'\n" +msgstr "配置文件“%s”已写入。\n" + +#: src/namestore/gnunet-namestore.c:519 msgid "del" msgstr "" -#: src/namestore/gnunet-namestore.c:462 +#: src/namestore/gnunet-namestore.c:569 +#: src/peerinfo-tool/gnunet-peerinfo.c:598 +#, fuzzy, c-format +msgid "Invalid URI `%s'\n" +msgstr "无效条目。\n" + +#: src/namestore/gnunet-namestore.c:625 +#, fuzzy, c-format +msgid "Using default zone file `%s'\n" +msgstr "卸载 GNUnet 服务" + +#: src/namestore/gnunet-namestore.c:677 msgid "add record" msgstr "" -#: src/namestore/gnunet-namestore.c:465 +#: src/namestore/gnunet-namestore.c:680 msgid "delete record" msgstr "" -#: src/namestore/gnunet-namestore.c:468 +#: src/namestore/gnunet-namestore.c:683 msgid "display records" msgstr "" -#: src/namestore/gnunet-namestore.c:471 +#: src/namestore/gnunet-namestore.c:686 msgid "" "expiration time for record to use (for adding only), \"never\" is possible" msgstr "" -#: src/namestore/gnunet-namestore.c:474 +#: src/namestore/gnunet-namestore.c:689 msgid "name of the record to add/delete/display" msgstr "" -#: src/namestore/gnunet-namestore.c:477 +#: src/namestore/gnunet-namestore.c:692 msgid "type of the record to add/delete/display" msgstr "" -#: src/namestore/gnunet-namestore.c:480 +#: src/namestore/gnunet-namestore.c:695 +msgid "URI to import into our zone" +msgstr "" + +#: src/namestore/gnunet-namestore.c:698 msgid "value of the record to add/delete" msgstr "" -#: src/namestore/gnunet-namestore.c:483 +#: src/namestore/gnunet-namestore.c:701 msgid "create or list public record" msgstr "" -#: src/namestore/gnunet-namestore.c:486 +#: src/namestore/gnunet-namestore.c:704 msgid "create or list non-authority record" msgstr "" -#: src/namestore/gnunet-namestore.c:489 +#: src/namestore/gnunet-namestore.c:707 msgid "filename with the zone key" msgstr "" -#: src/namestore/gnunet-namestore.c:500 +#: src/namestore/gnunet-namestore.c:718 #, fuzzy msgid "GNUnet zone manipulation tool" msgstr "GNUnet 配置" -#: src/namestore/gnunet-service-namestore.c:143 -#, c-format -msgid "File zone `%s' but corrupt content already exists, failed to write! \n" -msgstr "" +#: src/namestore/gnunet-service-namestore.c:241 +#: src/namestore/gnunet-service-namestore.c:257 +#, fuzzy, c-format +msgid "Failed to write zone key to file `%s': %s\n" +msgstr "打开日志文件“%s”失败:%s\n" -#: src/namestore/gnunet-service-namestore.c:154 -#, c-format -msgid "File zone `%s' containing this key already exists\n" +#: src/namestore/gnunet-service-namestore.c:243 +msgid "file exists but reading key failed" msgstr "" -#: src/namestore/gnunet-service-namestore.c:160 -#, c-format -msgid "" -"File zone `%s' but different zone key already exists, failed to write! \n" +#: src/namestore/gnunet-service-namestore.c:259 +msgid "file exists with different key" msgstr "" -#: src/namestore/gnunet-service-namestore.c:198 +#: src/namestore/gnunet-service-namestore.c:1557 +#, fuzzy +msgid "Failed to find record to remove\n" +msgstr "无法连接到 %s:%u:%s\n" + +#: src/namestore/gnunet-service-namestore.c:2172 #, fuzzy, c-format -msgid "Stored zonekey for zone `%s' in file `%s'\n" -msgstr "打开日志文件“%s”失败:%s\n" +msgid "Could not parse zone key file `%s'\n" +msgstr "找不到接口“%s”的一个 IP 地址。\n" -#: src/namestore/gnunet-service-namestore.c:1909 +#: src/namestore/gnunet-service-namestore.c:2262 msgid "No directory to load zonefiles specified in configuration\n" msgstr "" -#: src/namestore/gnunet-service-namestore.c:1918 +#: src/namestore/gnunet-service-namestore.c:2272 #, c-format msgid "Creating directory `%s' for zone files failed!\n" msgstr "" -#: src/namestore/namestore_api.c:315 src/namestore/namestore_api.c:353 -msgid "Namestore added record successfully" -msgstr "" - -#: src/namestore/namestore_api.c:323 +#: src/namestore/namestore_api.c:345 msgid "Namestore failed to add record" msgstr "" -#: src/namestore/namestore_api.c:361 -msgid "Namestore record already existed" -msgstr "" - -#: src/namestore/namestore_api.c:368 +#: src/namestore/namestore_api.c:371 msgid "Namestore failed to add record\n" msgstr "" -#: src/namestore/namestore_api.c:401 +#: src/namestore/namestore_api.c:415 #, fuzzy -msgid "Namestore removed record successfully" -msgstr "GNUnet 服务安装成功。\n" +msgid "Failed to create new signature" +msgstr "发送消息失败。\n" -#: src/namestore/namestore_api.c:408 -msgid "No records for entry" +#: src/namestore/namestore_api.c:419 +msgid "Failed to put new set of records in database" msgstr "" -#: src/namestore/namestore_api.c:415 +#: src/namestore/namestore_api.c:423 #, fuzzy -msgid "Could not find record to remove" -msgstr "无法连接到 %s:%u:%s\n" +msgid "Failed to remove records from database" +msgstr "发送消息失败。\n" -#: src/namestore/namestore_api.c:422 +#: src/namestore/namestore_api.c:427 #, fuzzy -msgid "Failed to create new signature" -msgstr "发送消息失败。\n" +msgid "Failed to access database" +msgstr "打开日志文件“%s”失败:%s\n" -#: src/namestore/namestore_api.c:429 -msgid "Failed to put new set of records in database" +#: src/namestore/namestore_api.c:431 +#, fuzzy +msgid "unknown internal error in namestore" +msgstr "未知错误。\n" + +#: src/namestore/namestore_api.c:436 +msgid "Protocol error" msgstr "" +#: src/namestore/namestore_common.c:530 src/namestore/namestore_common.c:670 +#, fuzzy, c-format +msgid "Unsupported record type %d\n" +msgstr "未知的命令“%s”。\n" + +#: src/namestore/namestore_common.c:537 +#, fuzzy, c-format +msgid "Unable to parse IPv4 address `%s'\n" +msgstr "无效的进程优先级“%s”\n" + +#: src/namestore/namestore_common.c:560 +#, fuzzy, c-format +msgid "Unable to parse SOA record `%s'\n" +msgstr "解析配置文件“%s”失败\n" + +#: src/namestore/namestore_common.c:583 +#, fuzzy, c-format +msgid "Unable to parse MX record `%s'\n" +msgstr "解析配置文件“%s”失败\n" + +#: src/namestore/namestore_common.c:601 +#, fuzzy, c-format +msgid "Unable to parse IPv6 address `%s'\n" +msgstr "无效的进程优先级“%s”\n" + +#: src/namestore/namestore_common.c:614 +#, fuzzy, c-format +msgid "Unable to parse PKEY record `%s'\n" +msgstr "解析配置文件“%s”失败\n" + +#: src/namestore/namestore_common.c:635 +#, fuzzy, c-format +msgid "Unable to parse VPN record string `%s'\n" +msgstr "解析配置文件“%s”失败\n" + +#: src/namestore/namestore_common.c:661 +#, fuzzy, c-format +msgid "Unable to parse TLSA record string `%s'\n" +msgstr "解析配置文件“%s”失败\n" + +#: src/namestore/plugin_namestore_postgres.c:95 +#, fuzzy +msgid "Failed to create indices\n" +msgstr "发送消息失败。\n" + #: src/nat/gnunet-nat-server.c:279 #, c-format msgid "Please pass valid port number as the first argument! (got `%s')\n" msgstr "" -#: src/nat/gnunet-nat-server.c:318 +#: src/nat/gnunet-nat-server.c:321 msgid "GNUnet NAT traversal test helper daemon" msgstr "" -#: src/nat/nat.c:799 +#: src/nat/nat_auto.c:169 +msgid "NAT traversal with ICMP Server timed out.\n" +msgstr "" + +#: src/nat/nat_auto.c:199 +msgid "NAT traversal with ICMP Server succeeded.\n" +msgstr "" + +#: src/nat/nat_auto.c:200 +msgid "NAT traversal with ICMP Server failed.\n" +msgstr "" + +#: src/nat/nat_auto.c:219 +msgid "Testing connection reversal with ICMP server.\n" +msgstr "" + +#: src/nat/nat_auto.c:265 +#, c-format +msgid "Detected external IP `%s'\n" +msgstr "" + +#: src/nat/nat_auto.c:331 +msgid "This system has a global IPv6 address, setting IPv6 to supported.\n" +msgstr "" + +#: src/nat/nat_auto.c:347 +#, fuzzy, c-format +msgid "Detected internal network address `%s'.\n" +msgstr "GNUnet 现在使用 IP 地址 %s。\n" + +#: src/nat/nat_auto.c:400 +msgid "upnpc found, enabling its use\n" +msgstr "" + +#: src/nat/nat_auto.c:401 +msgid "upnpc not found\n" +msgstr "" + +#: src/nat/nat_auto.c:434 +msgid "gnunet-helper-nat-server found, testing it\n" +msgstr "" + +#: src/nat/nat_auto.c:435 +msgid "No working gnunet-helper-nat-server found\n" +msgstr "" + +#: src/nat/nat_auto.c:469 +msgid "gnunet-helper-nat-client found, enabling it\n" +msgstr "" + +#: src/nat/nat_auto.c:470 +msgid "gnunet-helper-nat-client not found or behind NAT, disabling it\n" +msgstr "" + +#: src/nat/nat.c:795 #, c-format msgid "gnunet-helper-nat-server generated malformed address `%s'\n" msgstr "" @@ -3617,27 +3896,34 @@ msgstr "" msgid "Failed to start %s\n" msgstr "运行 %s失败:%s %d\n" -#: src/nat/nat.c:1111 -#, fuzzy, c-format -msgid "Malformed %s `%s' given in configuration!\n" -msgstr "保存配置失败。" +#: src/nat/nat.c:1113 +msgid "malformed" +msgstr "" -#: src/nat/nat.c:1177 src/nat/nat.c:1187 +#: src/nat/nat.c:1179 src/nat/nat.c:1191 #, c-format msgid "" "Configuration requires `%s', but binary is not installed properly (SUID bit " "not set). Option disabled.\n" msgstr "" -#: src/nat/nat.c:1321 +#: src/nat/nat.c:1326 msgid "Internal IP address not known, cannot use ICMP NAT traversal method\n" msgstr "" -#: src/nat/nat.c:1332 +#: src/nat/nat.c:1337 #, c-format msgid "Running gnunet-helper-nat-client %s %s %u\n" msgstr "" +#: src/nat/nat_mini.c:170 +msgid "`external-ip' command not found\n" +msgstr "" + +#: src/nat/nat_mini.c:505 +msgid "`upnpc' command not found\n" +msgstr "" + #: src/nat/nat_test.c:341 msgid "Failed to connect to `gnunet-nat-server'\n" msgstr "" @@ -3647,81 +3933,112 @@ msgstr "" msgid "Failed to create listen socket bound to `%s' for NAT test: %s\n" msgstr "" -#: src/nse/gnunet-nse-profiler.c:928 +#: src/nse/gnunet-nse-profiler.c:1009 +msgid "limit to the number of connections to NSE services, 0 for none" +msgstr "" + +#: src/nse/gnunet-nse-profiler.c:1012 +msgid "name of the file for writing connection information and statistics" +msgstr "" + +#: src/nse/gnunet-nse-profiler.c:1015 +msgid "name of the file with the login information for the testbed" +msgstr "" + +#: src/nse/gnunet-nse-profiler.c:1018 +msgid "IP address of this system as seen by the rest of the testbed" +msgstr "" + +#: src/nse/gnunet-nse-profiler.c:1021 +msgid "delay between queries to statistics during a round" +msgstr "" + +#: src/nse/gnunet-nse-profiler.c:1024 +msgid "prefix of the filenames we use for writing the topology for each round" +msgstr "" + +#: src/nse/gnunet-nse-profiler.c:1027 +msgid "name of the file for writing the main results" +msgstr "" + +#: src/nse/gnunet-nse-profiler.c:1030 +msgid "Number of peers to run in each round, separated by commas" +msgstr "" + +#: src/nse/gnunet-nse-profiler.c:1036 +msgid "delay between rounds" +msgstr "" + +#: src/nse/gnunet-nse-profiler.c:1046 #, fuzzy msgid "Measure quality and performance of the NSE service." msgstr "无法访问该服务" -#: src/nse/gnunet-service-nse.c:925 -#, c-format -msgid "Proof of work invalid: %llu!\n" -msgstr "" +#: src/nse/gnunet-service-nse.c:1389 +#, fuzzy, c-format +msgid "NSE service could not access hostkey: %s\n" +msgstr "找不到接口“%s”的一个 IP 地址。\n" -#: src/nse/gnunet-service-nse.c:1381 src/nse/gnunet-service-nse.c:1400 -#: src/nse/gnunet-service-nse.c:1421 +#: src/nse/gnunet-service-nse.c:1403 src/nse/gnunet-service-nse.c:1478 +#: src/nse/gnunet-service-nse.c:1495 msgid "NSE service is lacking key configuration settings. Exiting.\n" msgstr "" -#: src/nse/gnunet-service-nse.c:1388 +#: src/nse/gnunet-service-nse.c:1485 msgid "Invalid work requirement for NSE service. Exiting.\n" msgstr "" -#: src/nse/gnunet-service-nse.c:1409 -#, fuzzy -msgid "NSE service could not access hostkey. Exiting.\n" -msgstr "找不到接口“%s”的一个 IP 地址。\n" - #: src/peerinfo/gnunet-service-peerinfo.c:134 #, c-format msgid "Removing expired address of transport `%s'\n" msgstr "" -#: src/peerinfo/gnunet-service-peerinfo.c:203 +#: src/peerinfo/gnunet-service-peerinfo.c:230 #, fuzzy, c-format msgid "Failed to parse HELLO in file `%s'\n" msgstr "解析配置文件“%s”失败\n" -#: src/peerinfo/gnunet-service-peerinfo.c:229 +#: src/peerinfo/gnunet-service-peerinfo.c:269 msgid "# peers known" msgstr "" -#: src/peerinfo/gnunet-service-peerinfo.c:254 +#: src/peerinfo/gnunet-service-peerinfo.c:297 #, c-format msgid "" "File `%s' in directory `%s' does not match naming convention. Removed.\n" msgstr "" -#: src/peerinfo/gnunet-service-peerinfo.c:353 +#: src/peerinfo/gnunet-service-peerinfo.c:419 #, c-format msgid "Still no peers found in `%s'!\n" msgstr "" -#: src/peerinfo/gnunet-service-peerinfo.c:710 +#: src/peerinfo/gnunet-service-peerinfo.c:807 #, c-format msgid "Importing HELLOs from `%s'\n" msgstr "" -#: src/peerinfo/peerinfo_api.c:238 +#: src/peerinfo/peerinfo_api.c:239 msgid "aborted due to explicit disconnect request" msgstr "" -#: src/peerinfo/peerinfo_api.c:358 +#: src/peerinfo/peerinfo_api.c:359 #, fuzzy msgid "failed to transmit request (service down?)" msgstr "初始化“%s”服务失败。\n" -#: src/peerinfo/peerinfo_api.c:505 +#: src/peerinfo/peerinfo_api.c:509 msgid "Failed to receive response from `PEERINFO' service." msgstr "" -#: src/peerinfo/peerinfo_api.c:531 src/peerinfo/peerinfo_api.c:550 -#: src/peerinfo/peerinfo_api.c:565 src/peerinfo/peerinfo_api.c:576 -#: src/peerinfo/peerinfo_api.c:587 +#: src/peerinfo/peerinfo_api.c:550 src/peerinfo/peerinfo_api.c:569 +#: src/peerinfo/peerinfo_api.c:584 src/peerinfo/peerinfo_api.c:595 +#: src/peerinfo/peerinfo_api.c:606 #, fuzzy msgid "Received invalid message from `PEERINFO' service." msgstr "“%s”的参数无效。\n" -#: src/peerinfo/peerinfo_api.c:663 +#: src/peerinfo/peerinfo_api.c:681 #, fuzzy msgid "Timeout transmitting iteration request to `PEERINFO' service." msgstr "初始化“%s”服务失败。\n" @@ -3731,91 +4048,52 @@ msgstr "初始化“%s”服务失败。\n" msgid "Could not connect to `%s' service.\n" msgstr "无法连接到 %s:%u:%s\n" -#: src/peerinfo-tool/gnunet-peerinfo.c:581 -#, fuzzy -msgid "Failed to parse HELLO message: missing expiration time\n" -msgstr "保存配置失败。" - -#: src/peerinfo-tool/gnunet-peerinfo.c:589 -#, fuzzy -msgid "Failed to parse HELLO message: invalid expiration time\n" -msgstr "保存配置失败。" - -#: src/peerinfo-tool/gnunet-peerinfo.c:598 -#, fuzzy -msgid "Failed to parse HELLO message: malformed\n" -msgstr "打开日志文件“%s”失败:%s\n" - -#: src/peerinfo-tool/gnunet-peerinfo.c:608 -msgid "Failed to parse HELLO message: missing transport plugin\n" -msgstr "" - -#: src/peerinfo-tool/gnunet-peerinfo.c:625 -#, c-format -msgid "Plugin `%s' not found\n" -msgstr "" - -#: src/peerinfo-tool/gnunet-peerinfo.c:634 -#, c-format -msgid "Plugin `%s' does not support URIs yet\n" -msgstr "" - -#: src/peerinfo-tool/gnunet-peerinfo.c:653 -#, fuzzy, c-format -msgid "Failed to parse `%s' as an address for plugin `%s'\n" -msgstr "找不到接口“%s”的一个 IP 地址。\n" - -#: src/peerinfo-tool/gnunet-peerinfo.c:685 +#: src/peerinfo-tool/gnunet-peerinfo.c:419 #, c-format msgid "Failure adding HELLO: %s\n" msgstr "" -#: src/peerinfo-tool/gnunet-peerinfo.c:833 +#: src/peerinfo-tool/gnunet-peerinfo.c:557 #, fuzzy, c-format msgid "Could not find option `%s:%s' in configuration.\n" msgstr "找不到主机“%s”的 IP:%s\n" -#: src/peerinfo-tool/gnunet-peerinfo.c:840 +#: src/peerinfo-tool/gnunet-peerinfo.c:563 #, c-format msgid "Loading hostkey from `%s' failed.\n" msgstr "" -#: src/peerinfo-tool/gnunet-peerinfo.c:875 -#, fuzzy, c-format -msgid "Invalid URI `%s'\n" -msgstr "无效条目。\n" - -#: src/peerinfo-tool/gnunet-peerinfo.c:899 +#: src/peerinfo-tool/gnunet-peerinfo.c:622 #, c-format msgid "I am peer `%s'.\n" msgstr "" -#: src/peerinfo-tool/gnunet-peerinfo.c:936 +#: src/peerinfo-tool/gnunet-peerinfo.c:648 msgid "don't resolve host names" msgstr "" -#: src/peerinfo-tool/gnunet-peerinfo.c:939 +#: src/peerinfo-tool/gnunet-peerinfo.c:651 msgid "output only the identity strings" msgstr "" -#: src/peerinfo-tool/gnunet-peerinfo.c:942 +#: src/peerinfo-tool/gnunet-peerinfo.c:654 msgid "output our own identity only" msgstr "" -#: src/peerinfo-tool/gnunet-peerinfo.c:945 +#: src/peerinfo-tool/gnunet-peerinfo.c:657 #, fuzzy msgid "list all known peers" msgstr "列出所有网络适配器" -#: src/peerinfo-tool/gnunet-peerinfo.c:948 +#: src/peerinfo-tool/gnunet-peerinfo.c:660 msgid "also output HELLO uri(s)" msgstr "" -#: src/peerinfo-tool/gnunet-peerinfo.c:951 +#: src/peerinfo-tool/gnunet-peerinfo.c:663 msgid "add given HELLO uri to the database" msgstr "" -#: src/peerinfo-tool/gnunet-peerinfo.c:957 +#: src/peerinfo-tool/gnunet-peerinfo.c:674 #, fuzzy msgid "Print information about peers." msgstr "无法获取有关用户“%s”的信息:%s\n" @@ -3902,461 +4180,551 @@ msgstr "" msgid "Failed to connect to %s service. Exiting.\n" msgstr "初始化“%s”服务失败。\n" -#: src/pt/gnunet-daemon-pt.c:973 +#: src/pt/gnunet-daemon-pt.c:976 msgid "Daemon to run to perform IP protocol translation to GNUnet" msgstr "" -#: src/statistics/gnunet-service-statistics.c:271 -#, c-format -msgid "Loading %llu bytes of statistics from `%s'\n" +#: src/regex/gnunet-daemon-regexprofiler.c:293 +#, fuzzy, c-format +msgid "Regexprofiler could not access hostkey: %s. Exiting.\n" +msgstr "找不到接口“%s”的一个 IP 地址。\n" + +#: src/regex/gnunet-daemon-regexprofiler.c:452 +msgid "Daemon to announce regular expressions for the peer using mesh." msgstr "" -#: src/statistics/gnunet-service-statistics.c:330 +#: src/regex/gnunet-regex-profiler.c:1147 +msgid "An operation has failed while starting peers\n" +msgstr "" + +#: src/regex/gnunet-regex-profiler.c:1193 +#, fuzzy, c-format +msgid "Creating a peer failed. Error: %s\n" +msgstr "“%s”以错误码 %d 失败:%s\n" + +#: src/regex/gnunet-regex-profiler.c:1320 +msgid "An operation has failed while starting slaves\n" +msgstr "" + +#: src/regex/gnunet-regex-profiler.c:1342 +#, fuzzy, c-format +msgid "No files found in `%s'\n" +msgstr "运行 %s失败:%s %d\n" + +#: src/regex/gnunet-regex-profiler.c:1397 +msgid "An operation has failed while linking\n" +msgstr "" + +#: src/regex/gnunet-regex-profiler.c:1508 +#: src/testbed/testbed_api_testbed.c:805 #, c-format -msgid "Wrote %llu bytes of statistics to `%s'\n" +msgid "Host registration failed for a host. Error: %s\n" msgstr "" -#: src/statistics/gnunet-statistics.c:122 -#, fuzzy -msgid "Failed to obtain statistics.\n" -msgstr "初始化“%s”服务失败。\n" +#: src/regex/gnunet-regex-profiler.c:1589 +msgid "Unable to connect to master controller -- Check config\n" +msgstr "" -#: src/statistics/gnunet-statistics.c:199 +#: src/regex/gnunet-regex-profiler.c:1691 +#: src/testbed/testbed_api_testbed.c:970 #, c-format -msgid "No subsystem or name given\n" +msgid "Host %s cannot start testbed\n" msgstr "" -#: src/statistics/gnunet-statistics.c:207 -#, fuzzy, c-format -msgid "Failed to initialize watch routine\n" -msgstr "初始化“%s”服务失败。\n" +#: src/regex/gnunet-regex-profiler.c:1694 +#: src/testbed/testbed_api_testbed.c:974 +msgid "Testbed cannot be started on localhost\n" +msgstr "" -#: src/statistics/gnunet-statistics.c:227 -msgid "limit output to statistics for the given NAME" +#: src/regex/gnunet-regex-profiler.c:1734 +#, c-format +msgid "No hosts-file specified on command line. Exiting.\n" msgstr "" -#: src/statistics/gnunet-statistics.c:230 -msgid "make the value being set persistent" +#: src/regex/gnunet-regex-profiler.c:1739 +#: src/regex/gnunet-regex-simulation-profiler.c:622 +#, c-format +msgid "No policy directory specified on command line. Exiting.\n" msgstr "" -#: src/statistics/gnunet-statistics.c:233 -msgid "limit output to the given SUBSYSTEM" +#: src/regex/gnunet-regex-profiler.c:1745 +#: src/testbed/testbed_api_testbed.c:1065 +#, c-format +msgid "No hosts loaded. Need at least one host\n" msgstr "" -#: src/statistics/gnunet-statistics.c:236 -msgid "just print the statistics value" +#: src/regex/gnunet-regex-profiler.c:1748 +#, c-format +msgid "Checking whether given hosts can start testbed. Please wait\n" msgstr "" -#: src/statistics/gnunet-statistics.c:239 -msgid "watch value continously" +#: src/regex/gnunet-regex-profiler.c:1769 +#, fuzzy, c-format +msgid "Exiting\n" +msgstr "退出" + +#: src/regex/gnunet-regex-profiler.c:1775 +#, c-format +msgid "No configuration file given. Exiting\n" msgstr "" -#: src/statistics/gnunet-statistics.c:246 -msgid "Print statistics about GNUnet operations." +#: src/regex/gnunet-regex-profiler.c:1784 +#, fuzzy, c-format +msgid "Configuration option (regex_prefix) missing. Exiting\n" +msgstr "配置文件“%s”已写入。\n" + +#: src/regex/gnunet-regex-profiler.c:1802 +#: src/regex/gnunet-regex-simulation-profiler.c:629 +#, c-format +msgid "Specified policies directory does not exist. Exiting.\n" msgstr "" -#: src/statistics/statistics_api.c:456 -#, fuzzy -msgid "Could not save some persistent statistics\n" -msgstr "初始化“%s”服务失败。\n" +#: src/regex/gnunet-regex-profiler.c:1809 +#, c-format +msgid "No search strings file given. Exiting.\n" +msgstr "" -#: src/statistics/statistics_api.c:999 +#: src/regex/gnunet-regex-profiler.c:1817 +#, c-format msgid "" -"Failed to receive acknowledgement from statistics service, some statistics " -"might have been lost!\n" +"Error loading search strings. Given file does not contain enough strings. " +"Exiting.\n" msgstr "" -#: src/testing/gnunet-testing.c:157 +#: src/regex/gnunet-regex-profiler.c:1823 +#, fuzzy, c-format +msgid "Error loading search strings. Exiting.\n" +msgstr "创建用户出错" + +#: src/regex/gnunet-regex-profiler.c:1850 #, fuzzy -msgid "Could not read hostkeys file, specify hostkey file with -H!\n" -msgstr "找不到接口“%s”的一个 IP 地址。\n" +msgid "name of the file for writing statistics" +msgstr "初始化“%s”服务失败。\n" -#: src/testing/gnunet-testing.c:159 -#, c-format -msgid "Specified hostkey file `%s' not found!\n" +#: src/regex/gnunet-regex-profiler.c:1853 +msgid "create COUNT number of random links between peers" msgstr "" -#: src/testing/gnunet-testing.c:273 -#, fuzzy -msgid "create unique configuration files" -msgstr "更改配置文件中的一个值" +#: src/regex/gnunet-regex-profiler.c:1856 +msgid "wait TIMEOUT before considering a string match as failed" +msgstr "" -#: src/testing/gnunet-testing.c:275 -msgid "create hostkey files from pre-computed hostkey list" +#: src/regex/gnunet-regex-profiler.c:1859 +msgid "wait DELAY before starting string search" msgstr "" -#: src/testing/gnunet-testing.c:277 -msgid "host key file" +#: src/regex/gnunet-regex-profiler.c:1862 +msgid "number of search strings to read from search strings file" msgstr "" -#: src/testing/gnunet-testing.c:279 -#, fuzzy -msgid "number of unique configuration files or hostkeys to create" -msgstr "打印配置文件中的一个值到标准输出" +#: src/regex/gnunet-regex-profiler.c:1865 +#: src/regex/gnunet-regex-simulation-profiler.c:692 +msgid "maximum path compression length" +msgstr "" -#: src/testing/gnunet-testing.c:281 -#, fuzzy -msgid "configuration template" -msgstr "配置已保存" +#: src/regex/gnunet-regex-profiler.c:1868 +msgid "" +"if this option is set, only one peer is responsible for searching all strings" +msgstr "" -#: src/testing/gnunet-testing.c:287 -msgid "Command line tool to access the testing library" +#: src/regex/gnunet-regex-profiler.c:1881 +msgid "Profiler for regex" msgstr "" -#: src/testing/helper.c:56 -#, fuzzy -msgid "Peer is lacking HOSTKEY configuration setting.\n" -msgstr "立即保存配置?" +#: src/regex/gnunet-regex-simulation-profiler.c:689 +msgid "name of the table to write DFAs" +msgstr "" -#: src/testing/helper.c:64 -#, fuzzy -msgid "Could not access hostkey.\n" -msgstr "找不到接口“%s”的一个 IP 地址。\n" +#: src/regex/gnunet-regex-simulation-profiler.c:705 +msgid "Profiler for regex library" +msgstr "" -#: src/testing/testing.c:200 -msgid "`scp' does not seem to terminate (timeout copying config).\n" +#: src/statistics/gnunet-service-statistics.c:271 +#, c-format +msgid "Loading %llu bytes of statistics from `%s'\n" msgstr "" -#: src/testing/testing.c:214 src/testing/testing.c:798 -msgid "`scp' did not complete cleanly.\n" +#: src/statistics/gnunet-service-statistics.c:330 +#, c-format +msgid "Wrote %llu bytes of statistics to `%s'\n" msgstr "" -#: src/testing/testing.c:237 +#: src/statistics/gnunet-statistics.c:141 #, fuzzy -msgid "Failed to create pipe for `gnunet-peerinfo' process.\n" +msgid "Failed to obtain statistics.\n" msgstr "初始化“%s”服务失败。\n" -#: src/testing/testing.c:238 -#, fuzzy -msgid "Failed to create pipe for `ssh' process.\n" +#: src/statistics/gnunet-statistics.c:143 +#, fuzzy, c-format +msgid "Failed to obtain statistics from host `%s:%llu'\n" msgstr "初始化“%s”服务失败。\n" -#: src/testing/testing.c:286 +#: src/statistics/gnunet-statistics.c:181 #, fuzzy, c-format -msgid "Could not start `%s' process to create hostkey.\n" +msgid "Trying to connect to remote host, but service `%s' is not running\n" msgstr "初始化“%s”服务失败。\n" -#: src/testing/testing.c:293 -#, fuzzy -msgid "Failed to start `gnunet-peerinfo' process.\n" +#: src/statistics/gnunet-statistics.c:190 +#, fuzzy, c-format +msgid "A port is required to connect to host `%s'\n" +msgstr "无法连接到 %s:%u:%s\n" + +#: src/statistics/gnunet-statistics.c:196 +#, c-format +msgid "A port has to be between 1 and 65535 to connect to host `%s'\n" +msgstr "" + +#: src/statistics/gnunet-statistics.c:210 +msgid "Missing argument: subsystem \n" +msgstr "" + +#: src/statistics/gnunet-statistics.c:216 +msgid "Missing argument: name\n" +msgstr "" + +#: src/statistics/gnunet-statistics.c:247 +#, c-format +msgid "No subsystem or name given\n" +msgstr "" + +#: src/statistics/gnunet-statistics.c:255 +#, fuzzy, c-format +msgid "Failed to initialize watch routine\n" msgstr "初始化“%s”服务失败。\n" -#: src/testing/testing.c:294 src/testing/testing.c:471 +#: src/statistics/gnunet-statistics.c:310 +msgid "limit output to statistics for the given NAME" +msgstr "" + +#: src/statistics/gnunet-statistics.c:313 +msgid "make the value being set persistent" +msgstr "" + +#: src/statistics/gnunet-statistics.c:316 +msgid "limit output to the given SUBSYSTEM" +msgstr "" + +#: src/statistics/gnunet-statistics.c:319 +msgid "just print the statistics value" +msgstr "" + +#: src/statistics/gnunet-statistics.c:322 +msgid "watch value continuously" +msgstr "" + +#: src/statistics/gnunet-statistics.c:325 +msgid "connect to remote host" +msgstr "" + +#: src/statistics/gnunet-statistics.c:328 +msgid "port for remote host" +msgstr "" + +#: src/statistics/gnunet-statistics.c:340 +msgid "Print statistics about GNUnet operations." +msgstr "" + +#: src/statistics/statistics_api.c:511 #, fuzzy -msgid "Failed to start `ssh' process.\n" +msgid "Could not save some persistent statistics\n" msgstr "初始化“%s”服务失败。\n" -#: src/testing/testing.c:354 -#, c-format -msgid "Error reading from gnunet-peerinfo: %s\n" +#: src/statistics/statistics_api.c:1056 +msgid "" +"Failed to receive acknowledgement from statistics service, some statistics " +"might have been lost!\n" +msgstr "" + +#: src/sysmon/gnunet-service-sysmon.c:546 +#, c-format +msgid "Could not parse execution interval for `%s', set to default 60 sec.\n" +msgstr "" + +#: src/testbed/gnunet-testbed-profiler.c:231 +#, c-format +msgid "No hosts-file specified on command line\n" +msgstr "" + +#: src/testbed/gnunet-testbed-profiler.c:261 +msgid "create COUNT number of peers" msgstr "" -#: src/testing/testing.c:358 -msgid "Malformed output from gnunet-peerinfo!\n" +#: src/testbed/gnunet-testbed-profiler.c:264 +msgid "tolerate COUNT number of continious timeout failures" msgstr "" -#: src/testing/testing.c:368 -#, fuzzy -msgid "Failed to get hostkey!\n" -msgstr "发送消息失败。\n" +#: src/testbed/gnunet-testbed-profiler.c:276 +msgid "Profiler for testbed" +msgstr "" -#: src/testing/testing.c:400 -msgid "`Failed while waiting for topology setup!\n" +#: src/testbed/ll_master.c:57 +#, c-format +msgid "Job command file not given. Exiting\n" msgstr "" -#: src/testing/testing.c:463 +#: src/testbed/testbed_api.c:499 #, fuzzy, c-format -msgid "Could not start `%s' process to start GNUnet.\n" -msgstr "初始化“%s”服务失败。\n" +msgid "Adding host %u failed with error: %s\n" +msgstr "“%s”以错误码 %d 失败:%s\n" -#: src/testing/testing.c:470 -#, fuzzy -msgid "Failed to start `gnunet-arm' process.\n" -msgstr "初始化“%s”服务失败。\n" +#: src/testbed/testbed_api_hosts.c:306 +#, c-format +msgid "Hosts file %s not found\n" +msgstr "" -#: src/testing/testing.c:493 src/testing/testing.c:600 -msgid "`gnunet-arm' does not seem to terminate.\n" +#: src/testbed/testbed_api_hosts.c:314 +#, c-format +msgid "Hosts file %s has no data\n" msgstr "" -#: src/testing/testing.c:494 src/testing/testing.c:601 -#: src/testing/testing.c:621 -msgid "`ssh' does not seem to terminate.\n" +#: src/testbed/testbed_api_hosts.c:321 +#, c-format +msgid "Hosts file %s cannot be read\n" msgstr "" -#: src/testing/testing.c:570 -msgid "Unable to get HELLO for peer!\n" +#: src/testbed/testbed_api_testbed.c:623 +msgid "Linking controllers failed. Exiting" msgstr "" -#: src/testing/testing.c:620 -msgid "`gnunet-arm' terminated with non-zero exit status (or timed out)!\n" +#: src/testbed/testbed_api_testbed.c:1009 +msgid "Cannot start the master controller" msgstr "" -#: src/testing/testing.c:643 src/testing/testing.c:675 -msgid "either `gnunet-arm' or `ssh' does not seem to terminate.\n" +#: src/testbed/testbed_api_testbed.c:1089 +msgid "Specified topology must be supported by testbed" msgstr "" -#: src/testing/testing.c:658 src/testing/testing.c:713 -msgid "shutdown (either `gnunet-arm' or `ssh') did not complete cleanly.\n" +#: src/testbed/testbed_api_topology.c:668 +#, c-format +msgid "Topology file %s not found\n" msgstr "" -#: src/testing/testing.c:786 -msgid "`scp' does not seem to terminate.\n" +#: src/testbed/testbed_api_topology.c:674 +#, c-format +msgid "Topology file %s has no data\n" msgstr "" -#: src/testing/testing.c:948 -#, fuzzy, c-format -msgid "Starting service %s for peer `%4s'\n" -msgstr "卸载 GNUnet 服务" +#: src/testbed/testbed_api_topology.c:681 +#, c-format +msgid "Topology file %s cannot be read\n" +msgstr "" -#: src/testing/testing.c:1207 src/testing/testing_group.c:6154 +#: src/testbed/testbed_api_topology.c:704 #, fuzzy, c-format -msgid "Could not start `%s' process to copy configuration directory.\n" -msgstr "找不到主机“%s”的 IP:%s\n" +msgid "Failed to read peer index from toology file: %s" +msgstr "解析配置文件“%s”失败\n" -#: src/testing/testing.c:1292 src/testing/testing.c:1359 -#, fuzzy, c-format -msgid "Terminating peer `%4s'\n" -msgstr "未知的用户“%s”\n" +#: src/testbed/testbed_api_topology.c:713 +#: src/testbed/testbed_api_topology.c:737 +#, c-format +msgid "Value in given topology file: %s out of range\n" +msgstr "" -#: src/testing/testing.c:1448 +#: src/testbed/testbed_api_topology.c:719 +#: src/testbed/testbed_api_topology.c:743 #, fuzzy, c-format -msgid "Setting d->dead on peer `%4s'\n" -msgstr "卸载 GNUnet 服务" +msgid "Failed to read peer index from topology file: %s" +msgstr "解析配置文件“%s”失败\n" -#: src/testing/testing.c:1601 -msgid "Peer not yet running, can not change configuration at this point." +#: src/testbed/testbed_api_topology.c:725 +#: src/testbed/testbed_api_topology.c:749 +msgid "Topology file needs more peers than given ones\n" msgstr "" -#: src/testing/testing.c:1609 -#, fuzzy -msgid "Failed to write new configuration to disk." -msgstr "保存配置失败。" +#: src/testbed/testbed_api_topology.c:764 +#, fuzzy, c-format +msgid "Ignoring to connect peer %u to peer %u\n" +msgstr "无法连接到 %s:%u:%s\n" -#: src/testing/testing.c:1636 +#: src/testing/gnunet-testing.c:132 #, fuzzy, c-format -msgid "Could not start `%s' process to copy configuration file.\n" -msgstr "找不到主机“%s”的 IP:%s\n" +msgid "Could not extract hostkey %u (offset too large?)\n" +msgstr "找不到接口“%s”的一个 IP 地址。\n" -#: src/testing/testing.c:1639 +#: src/testing/gnunet-testing.c:203 #, fuzzy -msgid "Failed to copy new configuration to remote machine." -msgstr "保存配置失败。" +msgid "create unique configuration files" +msgstr "更改配置文件中的一个值" -#: src/testing/testing.c:1794 -#, fuzzy -msgid "Peers failed to connect" +#: src/testing/gnunet-testing.c:205 +msgid "extract hostkey file from pre-computed hostkey list" msgstr "" -"\n" -"按任意键继续\n" -#: src/testing/testing.c:1922 +#: src/testing/gnunet-testing.c:207 #, fuzzy -msgid "Failed to connect to core service of first peer!\n" -msgstr "加载 sqstore 服务失败。检查您的配置!\n" - -#: src/testing/testing.c:2145 -msgid "Peers are not fully running yet, can not connect!\n" -msgstr "" - -#: src/testing/testing_group.c:1895 src/testing/testing_group.c:1907 -#: src/testing/testing_group.c:2008 src/testing/testing_group.c:2065 -#: src/testing/testing_group.c:2152 src/testing/testing_group.c:2172 -#: src/testing/testing_group.c:2302 src/testing/testing_peergroup.c:950 -#, fuzzy, c-format -msgid "Invalid value `%s' for option `%s' in section `%s': expected float\n" -msgstr "配置不满足配置规范文件“%s”的约束!\n" - -#: src/testing/testing_group.c:2160 -#, c-format msgid "" -"Invalid value `%s' for option `%s' in section `%s': got %f, needed value " -"greater than 0\n" -msgstr "" +"number of unique configuration files to create, or number of the hostkey to " +"extract" +msgstr "打印配置文件中的一个值到标准输出" -#: src/testing/testing_group.c:2877 src/testing/testing_group.c:3063 -#, c-format -msgid "" -"No `%s' specified in peer configuration in section `%s', cannot copy friends " -"file!\n" -msgstr "" +#: src/testing/gnunet-testing.c:209 +#, fuzzy +msgid "configuration template" +msgstr "配置已保存" -#: src/testing/testing_group.c:3957 -msgid "Creating no allowed topology (all peers can connect at core level)\n" +#: src/testing/gnunet-testing.c:218 +msgid "Command line tool to access the testing library" msgstr "" -#: src/testing/testing_group.c:5226 -msgid "Unknown topology specification, can't connect peers!\n" +#: src/testing/gnunet-testing-run-service.c:129 +#, c-format +msgid "Unknown command, use 'q' to quit or 'r' to restart peer\n" msgstr "" -#: src/testing/testing_group.c:5944 src/transport/transport-testing.c:636 +#: src/testing/gnunet-testing-run-service.c:186 #, fuzzy -msgid "Could not read hostkeys file!\n" -msgstr "找不到接口“%s”的一个 IP 地址。\n" - -#: src/testing/testing_group.c:6011 -#, fuzzy, c-format -msgid "Could not create configuration for peer number %u on `%s'!\n" -msgstr "解析配置文件“%s”失败\n" +msgid "name of the template configuration file to use (optional)" +msgstr "打印配置文件中的一个值到标准输出" -#: src/testing/testing_new.c:169 -msgid "tmppath cannot be NULL\n" +#: src/testing/gnunet-testing-run-service.c:189 +msgid "name of the service to run" msgstr "" -#: src/testing/testing_new.c:356 +#: src/testing/testing.c:211 #, c-format msgid "Hostkeys file not found: %s\n" msgstr "" -#: src/testing/testing_new.c:365 -#, fuzzy, c-format -msgid "Could not open hostkeys file: %s\n" -msgstr "找不到接口“%s”的一个 IP 地址。\n" - -#: src/testing/testing_new.c:380 +#: src/testing/testing.c:227 #, c-format msgid "Incorrect hostkey file format: %s\n" msgstr "" -#: src/testing/testing_new.c:437 +#: src/testing/testing.c:541 #, c-format msgid "Key number %u does not exist\n" msgstr "" -#: src/testing/testing_new.c:446 +#: src/testing/testing.c:551 #, fuzzy, c-format msgid "Error while decoding key %u\n" msgstr "解析 dscl 输出时出错。\n" -#: src/testing/testing_new.c:680 +#: src/testing/testing.c:865 #, fuzzy msgid "Failed to create configuration for peer (not enough free ports?)\n" msgstr "解析配置文件“%s”失败\n" -#: src/testing/testing_new.c:691 +#: src/testing/testing.c:876 #, c-format msgid "" "You attempted to create a testbed with more than %u hosts. Please " "precompute more hostkeys first.\n" msgstr "" -#: src/testing/testing_new.c:704 +#: src/testing/testing.c:890 #, fuzzy, c-format msgid "Failed to initialize hostkey for peer %u\n" msgstr "初始化“%s”服务失败。\n" -#: src/testing/testing_new.c:734 +#: src/testing/testing.c:923 #, fuzzy, c-format msgid "Failed to write hostkey file for peer %u: %s\n" msgstr "发送消息失败。\n" -#: src/testing/testing_new.c:751 +#: src/testing/testing.c:941 #, fuzzy, c-format msgid "Failed to write configuration file `%s' for peer %u: %s\n" msgstr "解析配置文件“%s”失败\n" -#: src/testing/testing_new.c:791 +#: src/testing/testing.c:1014 #, fuzzy, c-format msgid "Failed to start `%s': %s\n" msgstr "运行 %s失败:%s %d\n" -#: src/testing/testing_new.c:959 +#: src/testing/testing.c:1219 #, fuzzy, c-format msgid "Failed to load configuration from %s\n" msgstr "解析配置文件“%s”失败\n" -#: src/topology/gnunet-daemon-topology.c:259 +#: src/topology/gnunet-daemon-topology.c:254 msgid "# peers blacklisted" msgstr "" -#: src/topology/gnunet-daemon-topology.c:392 +#: src/topology/gnunet-daemon-topology.c:387 msgid "# connect requests issued to transport" msgstr "" -#: src/topology/gnunet-daemon-topology.c:730 -#: src/topology/gnunet-daemon-topology.c:815 +#: src/topology/gnunet-daemon-topology.c:725 +#: src/topology/gnunet-daemon-topology.c:810 msgid "# friends connected" msgstr "" -#: src/topology/gnunet-daemon-topology.c:996 +#: src/topology/gnunet-daemon-topology.c:991 msgid "Failed to connect to core service, can not manage topology!\n" msgstr "" -#: src/topology/gnunet-daemon-topology.c:1026 -#, c-format -msgid "Option `%s' in section `%s' not specified!\n" -msgstr "" - -#: src/topology/gnunet-daemon-topology.c:1039 +#: src/topology/gnunet-daemon-topology.c:1034 #, c-format msgid "Could not read friends list `%s'\n" msgstr "" -#: src/topology/gnunet-daemon-topology.c:1045 +#: src/topology/gnunet-daemon-topology.c:1040 #, c-format msgid "Friends file `%s' is empty.\n" msgstr "" -#: src/topology/gnunet-daemon-topology.c:1054 +#: src/topology/gnunet-daemon-topology.c:1049 #, c-format msgid "Failed to read friends list from `%s': out of memory\n" msgstr "" -#: src/topology/gnunet-daemon-topology.c:1062 +#: src/topology/gnunet-daemon-topology.c:1057 #, c-format msgid "Failed to read friends list from `%s'\n" msgstr "" -#: src/topology/gnunet-daemon-topology.c:1082 +#: src/topology/gnunet-daemon-topology.c:1077 #, c-format msgid "" "Syntax error in topology specification at offset %llu, skipping bytes.\n" msgstr "" -#: src/topology/gnunet-daemon-topology.c:1095 +#: src/topology/gnunet-daemon-topology.c:1090 #, c-format msgid "" "Syntax error in topology specification at offset %llu, skipping bytes `%s'.\n" msgstr "" -#: src/topology/gnunet-daemon-topology.c:1105 +#: src/topology/gnunet-daemon-topology.c:1100 #, fuzzy, c-format msgid "Found friend `%s' in configuration\n" msgstr "" "\n" "结束配置。\n" -#: src/topology/gnunet-daemon-topology.c:1111 +#: src/topology/gnunet-daemon-topology.c:1106 #, c-format msgid "Found myself `%s' in friend list (useless, ignored)\n" msgstr "" -#: src/topology/gnunet-daemon-topology.c:1121 +#: src/topology/gnunet-daemon-topology.c:1116 #, fuzzy msgid "# friends in configuration" msgstr "" "\n" "结束配置。\n" -#: src/topology/gnunet-daemon-topology.c:1127 +#: src/topology/gnunet-daemon-topology.c:1122 msgid "" "Fewer friends specified than required by minimum friend count. Will only " "connect to friends.\n" msgstr "" -#: src/topology/gnunet-daemon-topology.c:1134 +#: src/topology/gnunet-daemon-topology.c:1129 msgid "" "More friendly connections required than target total number of connections.\n" msgstr "" -#: src/topology/gnunet-daemon-topology.c:1169 +#: src/topology/gnunet-daemon-topology.c:1164 msgid "# HELLO messages received" msgstr "" -#: src/topology/gnunet-daemon-topology.c:1224 +#: src/topology/gnunet-daemon-topology.c:1219 msgid "# HELLO messages gossipped" msgstr "" -#: src/topology/gnunet-daemon-topology.c:1363 +#: src/topology/gnunet-daemon-topology.c:1358 msgid "GNUnet topology control (maintaining P2P mesh and F2F constraints)" msgstr "" @@ -4365,11 +4733,6 @@ msgstr "" msgid "Could not read blacklist file `%s'\n" msgstr "无法解析“%s”(%s):%s\n" -#: src/transport/gnunet-service-transport_blacklist.c:252 -#, c-format -msgid "Blacklist file `%s' is empty.\n" -msgstr "" - #: src/transport/gnunet-service-transport_blacklist.c:263 #, fuzzy, c-format msgid "Failed to read blacklist from `%s'\n" @@ -4398,151 +4761,157 @@ msgid "Found myself `%s' in blacklist (useless, ignored)\n" msgstr "" #: src/transport/gnunet-service-transport_blacklist.c:514 -#: src/transport/gnunet-service-transport_blacklist.c:747 +#: src/transport/gnunet-service-transport_blacklist.c:752 msgid "# disconnects due to blacklist" msgstr "" -#: src/transport/gnunet-service-transport.c:163 +#: src/transport/gnunet-service-transport.c:183 msgid "# bytes payload discarded due to not connected peer " msgstr "" -#: src/transport/gnunet-service-transport.c:237 +#: src/transport/gnunet-service-transport.c:258 msgid "# bytes total received" msgstr "" -#: src/transport/gnunet-service-transport.c:284 +#: src/transport/gnunet-service-transport.c:305 msgid "# bytes payload received" msgstr "" -#: src/transport/gnunet-service-transport.c:582 -msgid "Transport service is lacking key configuration settings. Exiting.\n" -msgstr "" +#: src/transport/gnunet-service-transport.c:614 +#, fuzzy, c-format +msgid "Transport service could not access hostkey: %s. Exiting.\n" +msgstr "找不到接口“%s”的一个 IP 地址。\n" + +#: src/transport/gnunet-service-transport.c:625 +#, fuzzy +msgid "Could not access STATISTICS service. Exiting.\n" +msgstr "初始化“%s”服务失败。\n" -#: src/transport/gnunet-service-transport.c:591 -msgid "Transport service could not access hostkey. Exiting.\n" +#: src/transport/gnunet-service-transport.c:720 +msgid "Transport service is lacking key configuration settings. Exiting.\n" msgstr "" -#: src/transport/gnunet-service-transport_clients.c:352 +#: src/transport/gnunet-service-transport_clients.c:389 #, c-format msgid "Dropping message of type %u and size %u, have %u/%u messages pending\n" msgstr "" -#: src/transport/gnunet-service-transport_clients.c:357 +#: src/transport/gnunet-service-transport_clients.c:394 msgid "# messages dropped due to slow client" msgstr "" -#: src/transport/gnunet-service-transport_clients.c:503 +#: src/transport/gnunet-service-transport_clients.c:546 #, c-format msgid "Rejecting control connection from peer `%s', which is not me!\n" msgstr "" -#: src/transport/gnunet-service-transport_clients.c:631 +#: src/transport/gnunet-service-transport_clients.c:687 msgid "# bytes payload dropped (other peer was not connected)" msgstr "" -#: src/transport/gnunet-service-transport_clients.c:682 +#: src/transport/gnunet-service-transport_clients.c:738 msgid "# REQUEST CONNECT messages received" msgstr "" -#: src/transport/gnunet-service-transport_hello.c:172 +#: src/transport/gnunet-service-transport_hello.c:175 msgid "# refreshed my HELLO" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:1032 +#: src/transport/gnunet-service-transport_neighbours.c:1227 msgid "# DISCONNECT messages sent" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:1148 -#: src/transport/gnunet-service-transport_neighbours.c:1482 +#: src/transport/gnunet-service-transport_neighbours.c:1357 +#: src/transport/gnunet-service-transport_neighbours.c:1694 msgid "# bytes in message queue for other peers" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:1153 +#: src/transport/gnunet-service-transport_neighbours.c:1362 msgid "# messages transmitted to other peers" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:1158 +#: src/transport/gnunet-service-transport_neighbours.c:1367 msgid "# transmission failures for messages to other peers" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:1215 +#: src/transport/gnunet-service-transport_neighbours.c:1424 msgid "# messages timed out while in transport queue" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:1254 +#: src/transport/gnunet-service-transport_neighbours.c:1466 msgid "# keepalives sent" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:1278 +#: src/transport/gnunet-service-transport_neighbours.c:1490 msgid "# KEEPALIVE messages discarded (peer unknown)" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:1286 +#: src/transport/gnunet-service-transport_neighbours.c:1498 msgid "# KEEPALIVE messages discarded (no session)" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:1323 +#: src/transport/gnunet-service-transport_neighbours.c:1535 msgid "# KEEPALIVE_RESPONSE messages discarded (not connected)" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:1332 +#: src/transport/gnunet-service-transport_neighbours.c:1544 msgid "# KEEPALIVE_RESPONSE messages discarded (not expected)" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:1388 +#: src/transport/gnunet-service-transport_neighbours.c:1600 msgid "# messages discarded due to lack of neighbour record" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:1422 +#: src/transport/gnunet-service-transport_neighbours.c:1634 msgid "# bandwidth quota violations by other peers" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:1438 +#: src/transport/gnunet-service-transport_neighbours.c:1650 msgid "# ms throttling suggested" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:2544 +#: src/transport/gnunet-service-transport_neighbours.c:2802 msgid "# unexpected CONNECT_ACK messages (no peer)" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:2559 -#: src/transport/gnunet-service-transport_neighbours.c:2585 +#: src/transport/gnunet-service-transport_neighbours.c:2817 +#: src/transport/gnunet-service-transport_neighbours.c:2851 msgid "# unexpected CONNECT_ACK messages (not ready)" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:2598 +#: src/transport/gnunet-service-transport_neighbours.c:2864 msgid "# unexpected CONNECT_ACK messages (waiting on ATS)" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:2627 +#: src/transport/gnunet-service-transport_neighbours.c:2897 msgid "# unexpected CONNECT_ACK messages (disconnecting)" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:2807 +#: src/transport/gnunet-service-transport_neighbours.c:3082 msgid "# unexpected SESSION ACK messages" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:2856 +#: src/transport/gnunet-service-transport_neighbours.c:3137 msgid "# SET QUOTA messages ignored (no such peer)" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:2870 +#: src/transport/gnunet-service-transport_neighbours.c:3151 msgid "# disconnects due to quota of 0" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:2901 +#: src/transport/gnunet-service-transport_neighbours.c:3182 msgid "# disconnect messages ignored (old format)" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:2912 +#: src/transport/gnunet-service-transport_neighbours.c:3193 msgid "# disconnect messages ignored (timestamp)" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:2943 +#: src/transport/gnunet-service-transport_neighbours.c:3224 msgid "# other peer asked to disconnect from us" msgstr "" -#: src/transport/gnunet-service-transport_neighbours.c:3020 +#: src/transport/gnunet-service-transport_neighbours.c:3319 msgid "# disconnected from peer upon explicit request" msgstr "" @@ -4550,304 +4919,488 @@ msgstr "" msgid "Transport service is lacking NEIGHBOUR_LIMIT option.\n" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:414 +#: src/transport/gnunet-service-transport_validation.c:425 msgid "# address records discarded" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:463 +#: src/transport/gnunet-service-transport_validation.c:487 #, c-format msgid "" "Not transmitting `%s' with `%s', message too big (%u bytes!). This should " "not happen.\n" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:512 +#: src/transport/gnunet-service-transport_validation.c:536 msgid "# PING without HELLO messages sent" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:570 +#: src/transport/gnunet-service-transport_validation.c:618 msgid "# address revalidations started" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:805 +#: src/transport/gnunet-service-transport_validation.c:860 msgid "# PING message for different peer received" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:840 +#: src/transport/gnunet-service-transport_validation.c:925 #, c-format -msgid "" -"Not confirming PING with address `%s' since I cannot confirm having this " -"address.\n" +msgid "Received a PING message with validation bug from `%s'\n" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:924 +#: src/transport/gnunet-service-transport_validation.c:1054 msgid "# PONGs unicast via reliable transport" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:933 +#: src/transport/gnunet-service-transport_validation.c:1063 msgid "# PONGs multicast to all available addresses" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:1055 +#: src/transport/gnunet-service-transport_validation.c:1188 msgid "# PONGs dropped, no matching pending validation" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:1080 +#: src/transport/gnunet-service-transport_validation.c:1216 msgid "# PONGs dropped, signature expired" msgstr "" -#: src/transport/gnunet-service-transport_validation.c:1136 +#: src/transport/gnunet-service-transport_validation.c:1270 #, c-format msgid "Adding `%s' without addresses for peer `%s'\n" msgstr "" -#: src/transport/gnunet-transport.c:260 -msgid "No transport plugins configured, peer will never communicate\n" +#: src/transport/gnunet-transport.c:266 +#, c-format +msgid "Transmitted %llu bytes/s (%llu bytes in %s)\n" msgstr "" #: src/transport/gnunet-transport.c:273 #, c-format -msgid "No port configured for plugin `%s', cannot test it\n" +msgid "Received %llu bytes/s (%llu bytes in %s)\n" msgstr "" -#: src/transport/gnunet-transport.c:323 -#, c-format -msgid "Received %llu bytes/s (%llu bytes in %llu ms)\n" +#: src/transport/gnunet-transport.c:303 +#, fuzzy, c-format +msgid "Failed to connect to `%s'\n" +msgstr "初始化“%s”服务失败。\n" + +#: src/transport/gnunet-transport.c:316 +#, fuzzy, c-format +msgid "Failed to resolve address for peer `%s'\n" +msgstr "找不到接口“%s”的一个 IP 地址。\n" + +#: src/transport/gnunet-transport.c:325 +#, fuzzy +msgid "Failed to list connections, timeout occured\n" +msgstr "初始化“%s”服务失败。\n" + +#: src/transport/gnunet-transport.c:429 +msgid "No transport plugins configured, peer will never communicate\n" msgstr "" -#: src/transport/gnunet-transport.c:330 +#: src/transport/gnunet-transport.c:442 #, c-format -msgid "Transmitted %llu bytes/s (%llu bytes in %llu ms)\n" +msgid "No port configured for plugin `%s', cannot test it\n" msgstr "" -#: src/transport/gnunet-transport.c:363 +#: src/transport/gnunet-transport.c:506 #, c-format msgid "Transmitting %u bytes to %s\n" msgstr "" -#: src/transport/gnunet-transport.c:383 +#: src/transport/gnunet-transport.c:531 #, fuzzy, c-format -msgid "Connected to %s\n" +msgid "Successfully connected to `%s'\n" msgstr "“%s”已连接到“%s”。\n" -#: src/transport/gnunet-transport.c:414 +#: src/transport/gnunet-transport.c:553 +#, c-format +msgid "" +"Successfully connected to `%s', starting to send benchmark data in %u Kb " +"blocks\n" +msgstr "" + +#: src/transport/gnunet-transport.c:588 #, fuzzy, c-format -msgid "Disconnected from %s\n" +msgid "Disconnected from peer `%s' while benchmarking\n" msgstr "“%s”已连接到“%s”。\n" -#: src/transport/gnunet-transport.c:443 +#: src/transport/gnunet-transport.c:664 #, c-format msgid "Received %u bytes from %s\n" msgstr "" -#: src/transport/gnunet-transport.c:466 +#: src/transport/gnunet-transport.c:687 #, fuzzy, c-format msgid "Peer `%s': %s %s\n" msgstr "运行 %s失败:%s %d\n" -#: src/transport/gnunet-transport.c:473 +#: src/transport/gnunet-transport.c:702 #, c-format msgid "Peer `%s': %s \n" msgstr "" -#: src/transport/gnunet-transport.c:501 +#: src/transport/gnunet-transport.c:766 #, fuzzy, c-format msgid "Peer `%s' disconnected\n" msgstr "" "\n" "按任意键继续\n" -#: src/transport/gnunet-transport.c:569 -#, fuzzy, c-format -msgid "Failed to parse peer identity `%s'\n" -msgstr "解析配置文件“%s”失败\n" +#: src/transport/gnunet-transport.c:794 +#, fuzzy +msgid "Failed to send connect request to transport service\n" +msgstr "初始化“%s”服务失败。\n" + +#: src/transport/gnunet-transport.c:828 +#, c-format +msgid "" +"Multiple operations given. Please choose only one operation: %s, %s, %s, %s, " +"%s, %s\n" +msgstr "" + +#: src/transport/gnunet-transport.c:834 +#, c-format +msgid "" +"No operation given. Please choose one operation: %s, %s, %s, %s, %s, %s\n" +msgstr "" + +#: src/transport/gnunet-transport.c:854 src/transport/gnunet-transport.c:884 +#: src/transport/gnunet-transport.c:906 src/transport/gnunet-transport.c:945 +#, fuzzy +msgid "Failed to connect to transport service\n" +msgstr "初始化“%s”服务失败。\n" + +#: src/transport/gnunet-transport.c:861 src/transport/gnunet-transport.c:891 +#, fuzzy +msgid "Failed to send request to transport service\n" +msgstr "初始化“%s”服务失败。\n" -#: src/transport/gnunet-transport.c:618 -msgid "measure how fast we are receiving data (until CTRL-C)" +#: src/transport/gnunet-transport.c:911 +msgid "Starting to receive benchmark data\n" msgstr "" -#: src/transport/gnunet-transport.c:621 +#: src/transport/gnunet-transport.c:996 +msgid "measure how fast we are receiving data from all peers (until CTRL-C)" +msgstr "" + +#: src/transport/gnunet-transport.c:999 #, fuzzy -msgid "try to connect to the given peer" +msgid "connect to a peer" msgstr "初始化“%s”服务失败。\n" -#: src/transport/gnunet-transport.c:624 +#: src/transport/gnunet-transport.c:1002 msgid "provide information about all current connections (once)" msgstr "" -#: src/transport/gnunet-transport.c:627 -msgid "provide information about all current connections (continuously)" +#: src/transport/gnunet-transport.c:1008 +msgid "" +"provide information about all connects and disconnect events (continuously)" msgstr "" -#: src/transport/gnunet-transport.c:630 +#: src/transport/gnunet-transport.c:1011 msgid "do not resolve hostnames" msgstr "" -#: src/transport/gnunet-transport.c:634 +#: src/transport/gnunet-transport.c:1014 +msgid "peer identity" +msgstr "" + +#: src/transport/gnunet-transport.c:1018 msgid "send data for benchmarking to the other peer (until CTRL-C)" msgstr "" -#: src/transport/gnunet-transport.c:637 +#: src/transport/gnunet-transport.c:1021 msgid "test transport configuration (involves external server)" msgstr "" -#: src/transport/gnunet-transport.c:645 +#: src/transport/gnunet-transport.c:1032 #, fuzzy msgid "Direct access to transport service." msgstr "初始化“%s”服务失败。\n" -#: src/transport/plugin_transport_http.c:1100 +#: src/transport/plugin_transport_http.c:817 +#: src/transport/plugin_transport_http_server.c:2556 msgid "Disabling IPv6 since it is not supported on this system!\n" msgstr "" -#: src/transport/plugin_transport_http.c:1149 +#: src/transport/plugin_transport_http.c:866 +#: src/transport/plugin_transport_http_server.c:2324 #, fuzzy msgid "Require valid port number for service in configuration!\n" msgstr "保存配置失败。" -#: src/transport/plugin_transport_http.c:1174 src/util/service.c:1036 +#: src/transport/plugin_transport_http.c:898 +#: src/transport/plugin_transport_http_server.c:2356 src/util/service.c:1053 #, fuzzy, c-format msgid "Failed to resolve `%s': %s\n" msgstr "打开日志文件“%s”失败:%s\n" -#: src/transport/plugin_transport_http.c:1191 src/util/service.c:1053 +#: src/transport/plugin_transport_http.c:915 +#: src/transport/plugin_transport_http_server.c:2373 src/util/service.c:1070 #, fuzzy, c-format msgid "Failed to find %saddress for `%s'.\n" msgstr "找不到接口“%s”的一个 IP 地址。\n" -#: src/transport/plugin_transport_http.c:1296 +#: src/transport/plugin_transport_http.c:1020 +#: src/transport/plugin_transport_http_server.c:2484 #, c-format msgid "Found %u addresses to report to NAT service\n" msgstr "" -#: src/transport/plugin_transport_http.c:1309 -#, c-format -msgid "FREEING %s\n" -msgstr "" - -#: src/transport/plugin_transport_http.c:1386 +#: src/transport/plugin_transport_http.c:1133 +#: src/transport/plugin_transport_http_server.c:2652 msgid "Neither IPv4 nor IPv6 are enabled! Fix in configuration\n" msgstr "" -#: src/transport/plugin_transport_http.c:1399 +#: src/transport/plugin_transport_http.c:1146 +#: src/transport/plugin_transport_http_server.c:2663 #, fuzzy msgid "Port is required! Fix in configuration\n" msgstr "" "\n" "结束配置。\n" -#: src/transport/plugin_transport_http.c:1410 +#: src/transport/plugin_transport_http.c:1157 msgid "Port 0, client only mode\n" msgstr "" -#: src/transport/plugin_transport_http.c:1430 +#: src/transport/plugin_transport_http.c:1177 #, c-format msgid "" "Specific IPv4 address `%s' for plugin %s in configuration file is invalid! " "Binding to all addresses!\n" msgstr "" -#: src/transport/plugin_transport_http.c:1460 +#: src/transport/plugin_transport_http.c:1206 #, c-format msgid "" "Specific IPv6 address `%s' for plugin %s in configuration file is invalid! " "Binding to all addresses!\n" msgstr "" -#: src/transport/plugin_transport_http_client.c:624 +#: src/transport/plugin_transport_http.c:1223 +#: src/transport/plugin_transport_http_server.c:2745 +#, fuzzy, c-format +msgid "Using external hostname `%s'\n" +msgstr "卸载 GNUnet 服务" + +#: src/transport/plugin_transport_http.c:1228 +msgid "No external hostname configured\n" +msgstr "" + +#: src/transport/plugin_transport_http_client.c:1516 #, c-format msgid "Could not initialize curl multi handle, failed to start %s plugin!\n" msgstr "" -#: src/transport/plugin_transport_http_server.c:178 +#: src/transport/plugin_transport_http_client.c:1647 +#: src/transport/plugin_transport_http_server.c:2869 +#, fuzzy, c-format +msgid "Shutting down plugin `%s'\n" +msgstr "未知的命令“%s”。\n" + +#: src/transport/plugin_transport_http_client.c:1672 +#: src/transport/plugin_transport_http_server.c:2928 +#, c-format +msgid "Shutdown for plugin `%s' complete\n" +msgstr "" + +#: src/transport/plugin_transport_http_client.c:1700 +#: src/transport/plugin_transport_http_server.c:2775 +#, fuzzy, c-format +msgid "Maximum number of connections is %u\n" +msgstr "增加 TCP/IP 的最大连接数" + +#: src/transport/plugin_transport_http_server.c:1342 +#, c-format +msgid "" +"Access from connection %p (%u of %u) for `%s' `%s' url `%s' with upload data " +"size %u\n" +msgstr "" + +#: src/transport/plugin_transport_http_server.c:1603 +#, c-format +msgid "Accepting connection (%u of %u) from `%s'\n" +msgstr "" + +#: src/transport/plugin_transport_http_server.c:1611 +#, c-format +msgid "" +"Server reached maximum number connections (%u), rejecting new connection\n" +msgstr "" + +#: src/transport/plugin_transport_http_server.c:1912 msgid "" "Could not create a new TLS certificate, program `gnunet-transport-" "certificate-creation' could not be started!\n" msgstr "" -#: src/transport/plugin_transport_http_server.c:202 +#: src/transport/plugin_transport_http_server.c:1936 msgid "No usable TLS certificate found and creating one failed!\n" msgstr "" -#: src/transport/plugin_transport_tcp.c:591 +#: src/transport/plugin_transport_http_server.c:2631 +#, c-format +msgid "IPv4 support is %s\n" +msgstr "" + +#: src/transport/plugin_transport_http_server.c:2645 +#, c-format +msgid "IPv6 support is %s\n" +msgstr "" + +#: src/transport/plugin_transport_http_server.c:2670 +#, c-format +msgid "Using port %u\n" +msgstr "" + +#: src/transport/plugin_transport_http_server.c:2685 +#, c-format +msgid "Specific IPv4 address `%s' in configuration file is invalid!\n" +msgstr "" + +#: src/transport/plugin_transport_http_server.c:2695 +#, fuzzy, c-format +msgid "Binding to IPv4 address %s\n" +msgstr "无效的进程优先级“%s”\n" + +#: src/transport/plugin_transport_http_server.c:2716 +#, c-format +msgid "Specific IPv6 address `%s' in configuration file is invalid!\n" +msgstr "" + +#: src/transport/plugin_transport_http_server.c:2726 +#, fuzzy, c-format +msgid "Binding to IPv6 address %s\n" +msgstr "无效的进程优先级“%s”\n" + +#: src/transport/plugin_transport_http_server.c:2761 +#, c-format +msgid "Notifying transport only about hostname `%s'\n" +msgstr "" + +#: src/transport/plugin_transport_smtp.c:370 +#, c-format +msgid "Received malformed message via %s. Ignored.\n" +msgstr "" + +#: src/transport/plugin_transport_smtp.c:457 +msgid "SMTP filter string to invalid, lacks ': '\n" +msgstr "" + +#: src/transport/plugin_transport_smtp.c:466 +#, c-format +msgid "SMTP filter string to long, capped to `%s'\n" +msgstr "" + +#: src/transport/plugin_transport_smtp.c:561 +#: src/transport/plugin_transport_smtp.c:571 +#: src/transport/plugin_transport_smtp.c:584 +#: src/transport/plugin_transport_smtp.c:603 +#: src/transport/plugin_transport_smtp.c:626 +#: src/transport/plugin_transport_smtp.c:634 +#: src/transport/plugin_transport_smtp.c:647 +#: src/transport/plugin_transport_smtp.c:658 +#, c-format +msgid "SMTP: `%s' failed: %s.\n" +msgstr "" + +#: src/transport/plugin_transport_smtp.c:799 +msgid "No email-address specified, can not start SMTP transport.\n" +msgstr "" + +#: src/transport/plugin_transport_smtp.c:811 +msgid "# bytes received via SMTP" +msgstr "" + +#: src/transport/plugin_transport_smtp.c:812 +msgid "# bytes sent via SMTP" +msgstr "" + +#: src/transport/plugin_transport_smtp.c:814 +msgid "# bytes dropped by SMTP (outgoing)" +msgstr "" + +#: src/transport/plugin_transport_tcp.c:595 #, c-format msgid "Unexpected address length: %u bytes\n" msgstr "" -#: src/transport/plugin_transport_tcp.c:767 -#: src/transport/plugin_transport_tcp.c:856 -#: src/transport/plugin_transport_tcp.c:906 -#: src/transport/plugin_transport_tcp.c:992 -#: src/transport/plugin_transport_tcp.c:1086 -#: src/transport/plugin_transport_tcp.c:1103 +#: src/transport/plugin_transport_tcp.c:771 +#: src/transport/plugin_transport_tcp.c:860 +#: src/transport/plugin_transport_tcp.c:910 +#: src/transport/plugin_transport_tcp.c:996 +#: src/transport/plugin_transport_tcp.c:1139 +#: src/transport/plugin_transport_tcp.c:1156 msgid "# bytes currently in TCP buffers" msgstr "" -#: src/transport/plugin_transport_tcp.c:774 -#: src/transport/plugin_transport_tcp.c:963 -#: src/transport/plugin_transport_tcp.c:1761 -#: src/transport/plugin_transport_tcp.c:2390 +#: src/transport/plugin_transport_tcp.c:778 +#: src/transport/plugin_transport_tcp.c:967 +#: src/transport/plugin_transport_tcp.c:1826 +#: src/transport/plugin_transport_tcp.c:2462 msgid "# TCP sessions active" msgstr "" -#: src/transport/plugin_transport_tcp.c:860 +#: src/transport/plugin_transport_tcp.c:864 msgid "# bytes discarded by TCP (timeout)" msgstr "" -#: src/transport/plugin_transport_tcp.c:909 +#: src/transport/plugin_transport_tcp.c:913 msgid "# bytes transmitted via TCP" msgstr "" -#: src/transport/plugin_transport_tcp.c:996 +#: src/transport/plugin_transport_tcp.c:1000 msgid "# bytes discarded by TCP (disconnect)" msgstr "" -#: src/transport/plugin_transport_tcp.c:1290 +#: src/transport/plugin_transport_tcp.c:1113 +#, c-format +msgid "Trying to send with invalid session %p\n" +msgstr "" + +#: src/transport/plugin_transport_tcp.c:1349 #, c-format msgid "Address of unexpected length: %u\n" msgstr "" -#: src/transport/plugin_transport_tcp.c:1401 +#: src/transport/plugin_transport_tcp.c:1466 msgid "# transport-service disconnect requests for TCP" msgstr "" -#: src/transport/plugin_transport_tcp.c:1802 +#: src/transport/plugin_transport_tcp.c:1867 msgid "# TCP WELCOME messages received" msgstr "" -#: src/transport/plugin_transport_tcp.c:1973 +#: src/transport/plugin_transport_tcp.c:2046 msgid "# bytes received via TCP" msgstr "" -#: src/transport/plugin_transport_tcp.c:2043 +#: src/transport/plugin_transport_tcp.c:2124 msgid "# network-level TCP disconnect events" msgstr "" -#: src/transport/plugin_transport_tcp.c:2279 src/util/service.c:940 +#: src/transport/plugin_transport_tcp.c:2350 src/util/service.c:948 +#: src/util/service.c:954 #, c-format msgid "Require valid port number for service `%s' in configuration!\n" msgstr "" -#: src/transport/plugin_transport_tcp.c:2293 +#: src/transport/plugin_transport_tcp.c:2364 #, fuzzy msgid "Failed to start service.\n" msgstr "初始化“%s”服务失败。\n" -#: src/transport/plugin_transport_tcp.c:2355 -#, c-format -msgid "Failed to find option %s in section %s!\n" -msgstr "" - -#: src/transport/plugin_transport_tcp.c:2378 +#: src/transport/plugin_transport_tcp.c:2450 #, c-format msgid "TCP transport listening on port %llu\n" msgstr "" -#: src/transport/plugin_transport_tcp.c:2382 +#: src/transport/plugin_transport_tcp.c:2454 msgid "TCP transport not listening on any port (client only)\n" msgstr "" -#: src/transport/plugin_transport_tcp.c:2386 +#: src/transport/plugin_transport_tcp.c:2458 #, c-format msgid "TCP transport advertises itself as being on port %llu\n" msgstr "" @@ -4860,118 +5413,121 @@ msgstr "" msgid "# IPv4 broadcast HELLO beacons received via udp" msgstr "" -#: src/transport/plugin_transport_udp_broadcasting.c:367 +#: src/transport/plugin_transport_udp_broadcasting.c:394 #, c-format msgid "Failed to set IPv4 broadcast option for broadcast socket on port %d\n" msgstr "" -#: src/transport/plugin_transport_udp.c:1894 +#: src/transport/plugin_transport_udp.c:2517 +#, c-format +msgid "" +"UDP could not transmit message to `%s': Network seems down, please check " +"your network configuration\n" +msgstr "" + +#: src/transport/plugin_transport_udp.c:2531 #, c-format msgid "" -"UDP could not message to `%s': `%s'. Please check your network configuration " -"and disable IPv6 if your connection does not have a global IPv6 address\n" +"UDP could not transmit message to `%s': Please check your network " +"configuration and disable IPv6 if your connection does not have a global " +"IPv6 address\n" msgstr "" -#: src/transport/plugin_transport_udp.c:2138 +#: src/transport/plugin_transport_udp.c:2772 #, fuzzy msgid "Failed to open UDP sockets\n" msgstr "打开日志文件“%s”失败:%s\n" -#: src/transport/plugin_transport_udp.c:2306 +#: src/transport/plugin_transport_udp.c:2848 #, c-format msgid "Given `%s' option is out of range: %llu > %u\n" msgstr "" -#: src/transport/plugin_transport_udp.c:2349 +#: src/transport/plugin_transport_udp.c:2891 #, fuzzy, c-format msgid "Invalid IPv6 address: `%s'\n" msgstr "无效的进程优先级“%s”\n" -#: src/transport/plugin_transport_unix.c:1356 +#: src/transport/plugin_transport_unix.c:1357 #, fuzzy msgid "Failed to open UNIX sockets\n" msgstr "打开日志文件“%s”失败:%s\n" -#: src/transport/plugin_transport_wlan.c:561 +#: src/transport/plugin_transport_wlan.c:580 msgid "# WLAN ACKs sent" msgstr "" -#: src/transport/plugin_transport_wlan.c:580 +#: src/transport/plugin_transport_wlan.c:599 msgid "# WLAN messages defragmented" msgstr "" -#: src/transport/plugin_transport_wlan.c:626 -#: src/transport/plugin_transport_wlan.c:676 -#: src/transport/plugin_transport_wlan.c:1696 +#: src/transport/plugin_transport_wlan.c:645 +#: src/transport/plugin_transport_wlan.c:695 +#: src/transport/plugin_transport_wlan.c:1758 msgid "# WLAN sessions allocated" msgstr "" -#: src/transport/plugin_transport_wlan.c:749 +#: src/transport/plugin_transport_wlan.c:770 msgid "# WLAN message fragments sent" msgstr "" -#: src/transport/plugin_transport_wlan.c:767 +#: src/transport/plugin_transport_wlan.c:794 msgid "# WLAN messages pending (with fragmentation)" msgstr "" -#: src/transport/plugin_transport_wlan.c:867 -#: src/transport/plugin_transport_wlan.c:948 -#: src/transport/plugin_transport_wlan.c:1698 +#: src/transport/plugin_transport_wlan.c:902 +#: src/transport/plugin_transport_wlan.c:987 +#: src/transport/plugin_transport_wlan.c:1760 msgid "# WLAN MAC endpoints allocated" msgstr "" -#: src/transport/plugin_transport_wlan.c:1119 +#: src/transport/plugin_transport_wlan.c:1169 msgid "# HELLO messages received via WLAN" msgstr "" -#: src/transport/plugin_transport_wlan.c:1140 +#: src/transport/plugin_transport_wlan.c:1190 msgid "# fragments received via WLAN" msgstr "" -#: src/transport/plugin_transport_wlan.c:1150 +#: src/transport/plugin_transport_wlan.c:1200 msgid "# ACKs received via WLAN" msgstr "" -#: src/transport/plugin_transport_wlan.c:1207 +#: src/transport/plugin_transport_wlan.c:1257 msgid "# WLAN DATA messages discarded due to CRC32 error" msgstr "" -#: src/transport/plugin_transport_wlan.c:1306 +#: src/transport/plugin_transport_wlan.c:1358 msgid "# DATA messages received via WLAN" msgstr "" -#: src/transport/plugin_transport_wlan.c:1341 +#: src/transport/plugin_transport_wlan.c:1393 msgid "# WLAN DATA messages processed" msgstr "" -#: src/transport/plugin_transport_wlan.c:1402 +#: src/transport/plugin_transport_wlan.c:1454 msgid "# HELLO beacons sent via WLAN" msgstr "" -#: src/transport/plugin_transport_wlan.c:1511 +#: src/transport/plugin_transport_wlan.c:1563 msgid "WLAN address with invalid size encountered\n" msgstr "" -#: src/transport/plugin_transport_wlan.c:1668 -#, fuzzy, c-format -msgid "Invalid configuration option `%s' in section `%s'\n" -msgstr "配置文件“%s”已写入。\n" - -#: src/transport/plugin_transport_wlan.c:1677 +#: src/transport/plugin_transport_wlan.c:1739 #, c-format msgid "Helper binary `%s' not SUID, cannot run WLAN transport\n" msgstr "" -#: src/transport/plugin_transport_wlan.c:1687 -#, fuzzy, c-format -msgid "Missing configuration option `%s' in section `%s'\n" -msgstr "配置文件“%s”已写入。\n" - -#: src/transport/transport_api.c:570 +#: src/transport/transport_api.c:659 #, c-format msgid "Received unexpected message of type %u in %s:%u\n" msgstr "" +#: src/transport/transport-testing.c:586 +#, fuzzy +msgid "Failed to initialize testing library!\n" +msgstr "初始化“%s”服务失败。\n" + #: src/util/bio.c:136 src/util/bio.c:142 #, fuzzy, c-format msgid "Error reading `%s': %s" @@ -5001,260 +5557,309 @@ msgstr "" msgid "Metadata `%s' failed to deserialize" msgstr "" -#: src/util/client.c:359 +#: src/util/client.c:276 src/util/client.c:753 src/util/service.c:984 +#, c-format +msgid "UNIXPATH `%s' too long, maximum length is %llu\n" +msgstr "" + +#: src/util/client.c:280 src/util/client.c:757 src/util/service.c:988 +#, fuzzy, c-format +msgid "Using `%s' instead\n" +msgstr "%s:选项“%s”有歧义\n" + +#: src/util/client.c:371 #, c-format msgid "" "Could not determine valid hostname and port for service `%s' from " "configuration.\n" msgstr "" -#: src/util/client.c:367 +#: src/util/client.c:379 #, c-format msgid "Need a non-empty hostname for service `%s'.\n" msgstr "" -#: src/util/client.c:685 +#: src/util/client.c:698 msgid "Failure to transmit TEST request.\n" msgstr "" -#: src/util/client.c:740 src/util/service.c:970 -#, c-format -msgid "UNIXPATH `%s' too long, maximum length is %llu\n" -msgstr "" - -#: src/util/client.c:882 +#: src/util/client.c:898 #, c-format msgid "Could not connect to service `%s', must not be running.\n" msgstr "" -#: src/util/client.c:896 +#: src/util/client.c:912 #, c-format msgid "Failure to transmit request to service `%s'\n" msgstr "" -#: src/util/client.c:1149 +#: src/util/client.c:1177 msgid "Could not submit request, not expecting to receive a response.\n" msgstr "" -#: src/util/common_logging.c:239 src/util/common_logging.c:890 +#: src/util/common_logging.c:258 src/util/common_logging.c:1007 msgid "DEBUG" msgstr "调试" -#: src/util/common_logging.c:241 src/util/common_logging.c:888 +#: src/util/common_logging.c:260 src/util/common_logging.c:1005 msgid "INFO" msgstr "信息" -#: src/util/common_logging.c:243 src/util/common_logging.c:886 +#: src/util/common_logging.c:262 src/util/common_logging.c:1003 msgid "WARNING" msgstr "警告" -#: src/util/common_logging.c:245 src/util/common_logging.c:884 +#: src/util/common_logging.c:264 src/util/common_logging.c:1001 msgid "ERROR" msgstr "错误" -#: src/util/common_logging.c:247 src/util/common_logging.c:892 +#: src/util/common_logging.c:266 src/util/common_logging.c:1009 msgid "NONE" msgstr "" -#: src/util/common_logging.c:610 +#: src/util/common_logging.c:395 #, fuzzy, c-format msgid "Failed to create or access directory for log file `%s'\n" msgstr "解析配置文件“%s”失败\n" -#: src/util/common_logging.c:725 +#: src/util/common_logging.c:819 #, fuzzy, c-format msgid "Message `%.*s' repeated %u times in the last %s\n" msgstr "消息“%.*s”重复了 %u 次,在最近 %llu 秒内\n" -#: src/util/common_logging.c:893 +#: src/util/common_logging.c:1010 msgid "INVALID" msgstr "" -#: src/util/common_logging.c:992 +#: src/util/common_logging.c:1149 msgid "unknown address" msgstr "" -#: src/util/common_logging.c:1030 +#: src/util/common_logging.c:1187 msgid "invalid address" msgstr "" -#: src/util/configuration.c:244 +#: src/util/common_logging.c:1205 +#, fuzzy, c-format +msgid "Configuration fails to specify option `%s' in section `%s'!\n" +msgstr "配置不满足配置规范文件“%s”的约束!\n" + +#: src/util/common_logging.c:1226 #, fuzzy, c-format -msgid "Syntax error in configuration file `%s' at line %u.\n" +msgid "" +"Configuration specifies invalid value for option `%s' in section `%s': %s\n" +msgstr "配置不满足配置规范文件“%s”的约束!\n" + +#: src/util/configuration.c:291 +#, fuzzy, c-format +msgid "Syntax error while deserializing in line %u\n" msgstr "配置文件“%s”第 %d 行有语法错误。\n" -#: src/util/configuration.c:816 +#: src/util/configuration.c:998 #, c-format msgid "" "Configuration value '%s' for '%s' in section '%s' is not in set of legal " "choices\n" msgstr "" -#: src/util/connection.c:420 +#: src/util/connection.c:427 #, fuzzy, c-format msgid "Access denied to `%s'\n" msgstr "“%s”已连接到“%s”。\n" -#: src/util/connection.c:435 +#: src/util/connection.c:442 #, c-format msgid "Accepting connection from `%s': %p\n" msgstr "" -#: src/util/connection.c:550 +#: src/util/connection.c:557 #, c-format msgid "" "Failed to establish TCP connection to `%s:%u', no further addresses to try.\n" msgstr "" -#: src/util/connection.c:739 src/util/connection.c:909 +#: src/util/connection.c:755 src/util/connection.c:922 #, fuzzy, c-format msgid "Trying to connect to `%s' (%p)\n" msgstr "无法连接到 %s:%u:%s\n" -#: src/util/connection.c:748 -#, fuzzy, c-format -msgid "Failed to connect to `%s' (%p)\n" -msgstr "无法连接到 %s:%u:%s\n" - -#: src/util/connection.c:900 +#: src/util/connection.c:913 #, c-format msgid "Attempt to connect to `%s' failed\n" msgstr "" -#: src/util/container_bloomfilter.c:510 +#: src/util/container_bloomfilter.c:518 #, c-format msgid "" "Size of file on disk is incorrect for this Bloom filter (want %llu, have " "%llu)\n" msgstr "" -#: src/util/crypto_random.c:280 +#: src/util/crypto_ecc.c:441 #, c-format -msgid "Starting `%s' process to generate entropy\n" +msgid "" +"File `%s' does not contain a valid private key (too long, %llu bytes). " +"Deleting it.\n" msgstr "" -#: src/util/crypto_random.c:309 +#: src/util/crypto_ecc.c:456 src/util/crypto_rsa.c:660 #, c-format -msgid "libgcrypt has not the expected version (version %s is required).\n" -msgstr "libgcrypt 的版本不符合预期(要求版本 %s)。\n" +msgid "" +"File `%s' does not contain a valid private key (failed decode, %llu bytes). " +"Deleting it.\n" +msgstr "" -#: src/util/crypto_rsa.c:661 src/util/crypto_rsa.c:708 +#: src/util/crypto_ecc.c:552 src/util/crypto_ecc.c:596 +#: src/util/crypto_rsa.c:757 src/util/crypto_rsa.c:801 #, fuzzy, c-format -msgid "Could not aquire lock on file `%s': %s...\n" +msgid "Could not acquire lock on file `%s': %s...\n" msgstr "无法解析“%s”(%s):%s\n" -#: src/util/crypto_rsa.c:666 +#: src/util/crypto_ecc.c:557 src/util/crypto_rsa.c:762 #, fuzzy msgid "Creating a new private key. This may take a while.\n" msgstr "正在启动数据仓库转换(可能需要一段时间)。\n" -#: src/util/crypto_rsa.c:684 +#: src/util/crypto_ecc.c:600 src/util/crypto_rsa.c:805 +#: src/util/crypto_rsa.c:841 +msgid "This may be ok if someone is currently generating a private key.\n" +msgstr "" + +#: src/util/crypto_ecc.c:631 src/util/crypto_rsa.c:836 +#, c-format +msgid "" +"When trying to read key file `%s' I found %u bytes but I need at least %u.\n" +msgstr "" + +#: src/util/crypto_ecc.c:636 +msgid "This may be ok if someone is currently generating a key.\n" +msgstr "" + +#: src/util/crypto_ecc.c:651 src/util/crypto_rsa.c:856 #, c-format -msgid "I am host `%s'. Stored new private key in `%s'.\n" +msgid "File `%s' does not contain a valid private key. Deleting it.\n" +msgstr "" + +#: src/util/crypto_ecc.c:773 src/util/crypto_rsa.c:941 +msgid "interrupted by shutdown" msgstr "" -#: src/util/crypto_rsa.c:712 src/util/crypto_rsa.c:748 -msgid "This may be ok if someone is currently generating a hostkey.\n" +#: src/util/crypto_ecc.c:784 +msgid "gnunet-ecc failed" msgstr "" -#: src/util/crypto_rsa.c:743 +#: src/util/crypto_ecc.c:979 +#, fuzzy, c-format +msgid "ECC signing failed at %s:%d: %s\n" +msgstr "对驱动器“%2$s”的“%1$s”操作失败:%3$u\n" + +#: src/util/crypto_ecc.c:1047 #, c-format -msgid "" -"When trying to read hostkey file `%s' I found %u bytes but I need at least " -"%u.\n" +msgid "ECC signature verification failed at %s:%d: %s\n" msgstr "" -#: src/util/crypto_rsa.c:763 +#: src/util/crypto_random.c:313 #, c-format -msgid "File `%s' does not contain a valid private key. Deleting it.\n" +msgid "Starting `%s' process to generate entropy\n" msgstr "" -#: src/util/crypto_rsa.c:781 +#: src/util/crypto_random.c:342 +#, c-format +msgid "libgcrypt has not the expected version (version %s is required).\n" +msgstr "libgcrypt 的版本不符合预期(要求版本 %s)。\n" + +#: src/util/crypto_rsa.c:644 #, c-format -msgid "I am host `%s'. Read private key from `%s'.\n" +msgid "" +"File `%s' does not contain a valid private key (too long, %llu bytes). " +"Renaming it.\n" +msgstr "" + +#: src/util/crypto_rsa.c:952 +msgid "gnunet-rsa failed" msgstr "" -#: src/util/crypto_rsa.c:1032 +#: src/util/crypto_rsa.c:1343 #, c-format msgid "RSA signature verification failed at %s:%d: %s\n" msgstr "" -#: src/util/disk.c:498 +#: src/util/disk.c:601 #, fuzzy, c-format msgid "`%s' failed for drive `%S': %u\n" msgstr "对驱动器“%2$s”的“%1$s”操作失败:%3$u\n" -#: src/util/disk.c:1062 +#: src/util/disk.c:1205 #, c-format msgid "Expected `%s' to be a directory!\n" msgstr "“%s”应为目录!\n" -#: src/util/disk.c:1416 src/util/service.c:1650 +#: src/util/disk.c:1559 src/util/service.c:1669 #, c-format msgid "Cannot obtain information about user `%s': %s\n" msgstr "无法获取有关用户“%s”的信息:%s\n" -#: src/util/disk.c:1734 +#: src/util/disk.c:1931 #, c-format msgid "No `%s' specified for service `%s' in configuration.\n" msgstr "" -#: src/util/getopt.c:669 +#: src/util/getopt.c:570 #, c-format msgid "%s: option `%s' is ambiguous\n" msgstr "%s:选项“%s”有歧义\n" -#: src/util/getopt.c:693 +#: src/util/getopt.c:594 #, c-format msgid "%s: option `--%s' does not allow an argument\n" msgstr "%s:选项“--%s”不允许有参数\n" -#: src/util/getopt.c:698 +#: src/util/getopt.c:599 #, c-format msgid "%s: option `%c%s' does not allow an argument\n" msgstr "%s:选项“%c%s”不允许有参数\n" -#: src/util/getopt.c:715 src/util/getopt.c:883 +#: src/util/getopt.c:616 src/util/getopt.c:783 #, c-format msgid "%s: option `%s' requires an argument\n" msgstr "%s:选项“%s”要求有一个参数\n" -#: src/util/getopt.c:744 +#: src/util/getopt.c:645 #, c-format msgid "%s: unrecognized option `--%s'\n" msgstr "%s:无法识别的选项“--%s”\n" -#: src/util/getopt.c:748 +#: src/util/getopt.c:649 #, c-format msgid "%s: unrecognized option `%c%s'\n" msgstr "%s:无法识别的选项“%c%s”\n" -#: src/util/getopt.c:773 +#: src/util/getopt.c:674 #, c-format msgid "%s: illegal option -- %c\n" msgstr "%s:非法选项 -- %c\n" -#: src/util/getopt.c:775 +#: src/util/getopt.c:676 #, c-format msgid "%s: invalid option -- %c\n" msgstr "%s:无效选项 -- %c\n" -#: src/util/getopt.c:803 src/util/getopt.c:931 +#: src/util/getopt.c:704 src/util/getopt.c:831 #, c-format msgid "%s: option requires an argument -- %c\n" msgstr "%s:选项要求有一个参数 -- %c\n" -#: src/util/getopt.c:851 +#: src/util/getopt.c:752 #, c-format msgid "%s: option `-W %s' is ambiguous\n" msgstr "%s:选项“-W %s”有歧义\n" -#: src/util/getopt.c:869 +#: src/util/getopt.c:770 #, c-format msgid "%s: option `-W %s' does not allow an argument\n" msgstr "%s:选项“-W %s” 不允许有参数\n" -#: src/util/getopt.c:1035 +#: src/util/getopt.c:935 #, fuzzy, c-format msgid "Use %s to get a list of options.\n" msgstr "请使用 --help 获取选项列表。\n" @@ -5265,37 +5870,110 @@ msgid "" "Arguments mandatory for long options are also mandatory for short options.\n" msgstr "长选项的必选参数对短选项也是必选的。\n" -#: src/util/getopt_helpers.c:258 src/util/getopt_helpers.c:286 +#: src/util/getopt_helpers.c:258 src/util/getopt_helpers.c:316 #, c-format msgid "You must pass a number to the `%s' option.\n" msgstr "您必须向“%s”选项传递一个数字。\n" -#: src/util/gnunet-resolver.c:148 -msgid "perform a reverse lookup" +#: src/util/getopt_helpers.c:288 +#, fuzzy, c-format +msgid "You must pass relative time to the `%s' option.\n" +msgstr "您必须向“%s”选项传递一个数字。\n" + +#: src/util/gnunet-config.c:90 +#, fuzzy, c-format +msgid "--section argument is required\n" +msgstr "设置要使用的昵称(必须)" + +#: src/util/gnunet-config.c:133 +#, c-format +msgid "--option argument required to set value\n" msgstr "" -#: src/util/gnunet-resolver.c:154 -msgid "Use build-in GNUnet stub resolver" +#: src/util/gnunet-config.c:160 +msgid "obtain option of value as a filename (with $-expansion)" +msgstr "" + +#: src/util/gnunet-config.c:163 +msgid "name of the section to access" +msgstr "" + +#: src/util/gnunet-config.c:166 +msgid "name of the option to access" +msgstr "" + +#: src/util/gnunet-config.c:169 +msgid "value to set" +msgstr "" + +#: src/util/gnunet-config.c:178 +#, fuzzy +msgid "Manipulate GNUnet configuration files" +msgstr "更改配置文件中的一个值" + +#: src/util/gnunet-ecc.c:107 src/util/gnunet-rsa.c:107 +#, fuzzy, c-format +msgid "Failed to open `%s': %s\n" +msgstr "打开日志文件“%s”失败:%s\n" + +#: src/util/gnunet-ecc.c:113 src/util/gnunet-rsa.c:113 +#, c-format +msgid "Generating %u keys, please wait" +msgstr "" + +#: src/util/gnunet-ecc.c:128 src/util/gnunet-rsa.c:137 +#, fuzzy, c-format +msgid "" +"\n" +"Failed to write to `%s': %s\n" +msgstr "运行 %s失败:%s %d\n" + +#: src/util/gnunet-ecc.c:140 src/util/gnunet-rsa.c:149 +#, c-format +msgid "Finished!\n" msgstr "" -#: src/util/gnunet-rsa.c:64 +#: src/util/gnunet-ecc.c:163 src/util/gnunet-rsa.c:172 #, c-format msgid "No hostkey file specified on command line\n" msgstr "" -#: src/util/gnunet-rsa.c:112 +#: src/util/gnunet-ecc.c:220 src/util/gnunet-rsa.c:229 +msgid "create COUNT public-private key pairs (for testing)" +msgstr "" + +#: src/util/gnunet-ecc.c:223 src/util/gnunet-rsa.c:232 msgid "print the public key in ASCII format" msgstr "" -#: src/util/gnunet-rsa.c:115 +#: src/util/gnunet-ecc.c:226 src/util/gnunet-rsa.c:235 msgid "print the hash of the public key in ASCII format" msgstr "" -#: src/util/gnunet-rsa.c:118 +#: src/util/gnunet-ecc.c:229 src/util/gnunet-rsa.c:238 msgid "print the short hash of the public key in ASCII format" msgstr "" -#: src/util/gnunet-rsa.c:124 +#: src/util/gnunet-ecc.c:232 src/util/gnunet-rsa.c:241 +msgid "" +"use insecure, weak random number generator for key generation (for testing " +"only)" +msgstr "" + +#: src/util/gnunet-ecc.c:243 +#, fuzzy +msgid "Manipulate GNUnet private ECC key files" +msgstr "更改配置文件中的一个值" + +#: src/util/gnunet-resolver.c:148 +msgid "perform a reverse lookup" +msgstr "" + +#: src/util/gnunet-resolver.c:159 +msgid "Use build-in GNUnet stub resolver" +msgstr "" + +#: src/util/gnunet-rsa.c:252 msgid "Manipulate GNUnet private RSA key files" msgstr "" @@ -5310,70 +5988,74 @@ msgstr "无法解析“%s”(%s):%s\n" msgid "Could not find IP of host `%s': %s\n" msgstr "找不到主机“%s”的 IP:%s\n" -#: src/util/helper.c:244 +#: src/util/gnunet-uri.c:90 +#, c-format +msgid "No URI specified on command line\n" +msgstr "" + +#: src/util/gnunet-uri.c:95 #, fuzzy, c-format -msgid "Error reading from `%s': %s\n" -msgstr "创建用户出错" +msgid "Invalid URI: does not start with `%s'\n" +msgstr "无效的网络表示法(没有以“;”结尾:“%s”)\n" -#: src/util/helper.c:259 +#: src/util/gnunet-uri.c:102 #, c-format -msgid "Got 0 bytes from helper `%s' (EOF)\n" +msgid "Invalid URI: fails to specify subsystem\n" msgstr "" -#: src/util/helper.c:269 +#: src/util/gnunet-uri.c:112 #, c-format -msgid "Got %u bytes from helper `%s'\n" +msgid "No handler known for subsystem `%s'\n" +msgstr "" + +#: src/util/gnunet-uri.c:174 +msgid "Perform default-actions for GNUnet URIs" msgstr "" -#: src/util/helper.c:278 +#: src/util/helper.c:260 #, fuzzy, c-format -msgid "Failed to parse inbound message from helper `%s'\n" -msgstr "打开日志文件“%s”失败:%s\n" +msgid "Error reading from `%s': %s\n" +msgstr "创建用户出错" -#: src/util/helper.c:310 +#: src/util/helper.c:305 #, fuzzy, c-format -msgid "Starting HELPER process `%s'\n" -msgstr "卸载 GNUnet 服务" +msgid "Failed to parse inbound message from helper `%s'\n" +msgstr "打开日志文件“%s”失败:%s\n" -#: src/util/helper.c:440 +#: src/util/helper.c:499 #, fuzzy, c-format msgid "Error writing to `%s': %s\n" msgstr "创建用户出错" -#: src/util/network.c:1200 +#: src/util/network.c:127 +#, c-format +msgid "Unable to shorten unix path `%s' while keeping name unique\n" +msgstr "" + +#: src/util/network.c:1331 #, c-format msgid "" "Fatal internal logic error, process hangs in `%s' (abort with CTRL-C)!\n" msgstr "" -#: src/util/os_installation.c:299 +#: src/util/os_installation.c:420 #, fuzzy, c-format msgid "" "Could not determine installation path for %s. Set `%s' environment " "variable.\n" msgstr "无法确定安装路径。请尝试设置“%s”\n" -#: src/util/os_installation.c:486 +#: src/util/os_installation.c:702 #, fuzzy, c-format msgid "Could not find binary `%s' in PATH!\n" msgstr "找不到主机“%s”的 IP:%s\n" -#: src/util/os_installation.c:492 -#, fuzzy, c-format -msgid "access (%s, X_OK) failed: %s\n" -msgstr "“%s”说:%s\n" - -#: src/util/os_installation.c:507 -#, fuzzy, c-format -msgid "stat (%s) failed: %s\n" -msgstr "“%s”说:%s\n" - -#: src/util/os_priority.c:305 +#: src/util/os_priority.c:302 #, fuzzy, c-format msgid "Failed to open named pipe `%s' for reading: %s\n" msgstr "打开日志文件“%s”失败:%s\n" -#: src/util/os_priority.c:306 +#: src/util/os_priority.c:303 #, fuzzy, c-format msgid "Failed to open named pipe `%s' for writing: %s\n" msgstr "打开日志文件“%s”失败:%s\n" @@ -5398,12 +6080,17 @@ msgstr "" msgid "Could not determine plugin installation path.\n" msgstr "无法确定用户界面定义文件。" -#: src/util/pseudonym.c:276 +#: src/util/program.c:254 src/util/service.c:1791 +#, fuzzy, c-format +msgid "Could not access configuration file `%s'\n" +msgstr "找不到接口“%s”的一个 IP 地址。\n" + +#: src/util/pseudonym.c:282 #, fuzzy, c-format msgid "Failed to parse metadata about pseudonym from file `%s': %s\n" msgstr "打开日志文件“%s”失败:%s\n" -#: src/util/pseudonym.c:407 src/util/pseudonym.c:433 +#: src/util/pseudonym.c:413 src/util/pseudonym.c:439 msgid "no-name" msgstr "无名称" @@ -5433,152 +6120,152 @@ msgstr "" msgid "Could not resolve our FQDN : %s\n" msgstr "无法解析“%s”(%s):%s\n" -#: src/util/scheduler.c:786 +#: src/util/scheduler.c:782 msgid "Looks like we're busy waiting...\n" msgstr "" -#: src/util/scheduler.c:916 +#: src/util/scheduler.c:912 #, c-format msgid "Attempt to cancel dead task %llu!\n" msgstr "" -#: src/util/server.c:483 +#: src/util/server.c:426 #, fuzzy, c-format msgid "`%s' failed for port %d (%s).\n" msgstr "对驱动器“%2$s”的“%1$s”操作失败:%3$u\n" -#: src/util/server.c:492 +#: src/util/server.c:435 #, c-format msgid "`%s' failed for port %d (%s): address already in use\n" msgstr "" -#: src/util/server.c:497 +#: src/util/server.c:446 #, fuzzy, c-format -msgid "`%s' failed for `%s': address already in use\n" +msgid "`%s' failed for `%.*s': address already in use\n" msgstr "对驱动器“%2$s”的“%1$s”操作失败:%3$u\n" -#: src/util/server.c:827 +#: src/util/server.c:830 #, c-format msgid "" "Processing code for message of type %u did not call " -"GNUNET_SERVER_receive_done after %llums\n" +"`GNUNET_SERVER_receive_done' after %s\n" msgstr "" -#: src/util/service.c:135 src/util/service.c:161 src/util/service.c:204 -#: src/util/service.c:225 src/util/service.c:232 +#: src/util/service.c:142 src/util/service.c:168 src/util/service.c:211 +#: src/util/service.c:232 src/util/service.c:239 #, c-format msgid "Invalid format for IP: `%s'\n" msgstr "IP 格式无效:“%s”\n" -#: src/util/service.c:188 +#: src/util/service.c:195 #, c-format msgid "Invalid network notation ('/%d' is not legal in IPv4 CIDR)." msgstr "网络表示法无效(“/%d” 在 IPv4 CIDR 中是非法的)。" -#: src/util/service.c:281 +#: src/util/service.c:288 #, c-format msgid "Invalid network notation (does not end with ';': `%s')\n" msgstr "无效的网络表示法(没有以“;”结尾:“%s”)\n" -#: src/util/service.c:313 +#: src/util/service.c:320 #, c-format msgid "Wrong format `%s' for netmask\n" msgstr "网络掩码的格式“%s”错误\n" -#: src/util/service.c:343 +#: src/util/service.c:350 #, c-format msgid "Wrong format `%s' for network\n" msgstr "网络的格式“%s”错误\n" -#: src/util/service.c:698 +#: src/util/service.c:707 #, c-format msgid "Access denied to UID %d / GID %d\n" msgstr "" -#: src/util/service.c:703 +#: src/util/service.c:712 #, c-format msgid "Unknown address family %d\n" msgstr "" -#: src/util/service.c:710 +#: src/util/service.c:719 #, c-format msgid "Access from `%s' denied to service `%s'\n" msgstr "" -#: src/util/service.c:765 +#: src/util/service.c:774 #, c-format msgid "Could not parse IPv4 network specification `%s' for `%s:%s'\n" msgstr "" -#: src/util/service.c:802 +#: src/util/service.c:811 #, c-format msgid "Could not parse IPv6 network specification `%s' for `%s:%s'\n" msgstr "" -#: src/util/service.c:920 +#: src/util/service.c:929 #, c-format msgid "" "Disabling IPv6 support for service `%s', failed to create IPv6 socket: %s\n" msgstr "" -#: src/util/service.c:990 +#: src/util/service.c:1007 #, c-format msgid "" "Disabling UNIX domain socket support for service `%s', failed to create UNIX " "domain socket: %s\n" msgstr "" -#: src/util/service.c:1007 +#: src/util/service.c:1024 #, c-format msgid "Have neither PORT nor UNIXPATH for service `%s', but one is required\n" msgstr "" -#: src/util/service.c:1241 +#: src/util/service.c:1258 msgid "Could not access a pre-bound socket, will try to bind myself\n" msgstr "" -#: src/util/service.c:1292 src/util/service.c:1310 +#: src/util/service.c:1309 src/util/service.c:1327 #, c-format msgid "Specified value for `%s' of service `%s' is invalid\n" msgstr "" -#: src/util/service.c:1337 +#: src/util/service.c:1354 #, c-format msgid "Could not access pre-bound socket %u, will try to bind myself\n" msgstr "" -#: src/util/service.c:1506 +#: src/util/service.c:1525 #, fuzzy, c-format msgid "Failed to start `%s' at `%s'\n" msgstr "运行 %s失败:%s %d\n" -#: src/util/service.c:1539 +#: src/util/service.c:1558 #, c-format msgid "Service `%s' runs at %s\n" msgstr "" -#: src/util/service.c:1588 +#: src/util/service.c:1607 msgid "Service process failed to initialize\n" msgstr "" -#: src/util/service.c:1592 +#: src/util/service.c:1611 msgid "Service process could not initialize server function\n" msgstr "" -#: src/util/service.c:1596 +#: src/util/service.c:1615 msgid "Service process failed to report status\n" msgstr "" -#: src/util/service.c:1651 +#: src/util/service.c:1670 msgid "No such user" msgstr "无此用户" -#: src/util/service.c:1664 +#: src/util/service.c:1683 #, c-format msgid "Cannot change user/group to `%s': %s\n" msgstr "无法更改用户/组为“%s”:%s\n" -#: src/util/service.c:1729 +#: src/util/service.c:1749 msgid "do daemonize (detach from terminal)" msgstr "" @@ -5587,73 +6274,83 @@ msgstr "" msgid "signal (%d, %p) returned %d.\n" msgstr "" -#: src/util/strings.c:144 +#: src/util/strings.c:146 msgid "b" msgstr "b" -#: src/util/strings.c:334 +#: src/util/strings.c:413 #, c-format msgid "Character sets requested were `%s'->`%s'\n" msgstr "" -#: src/util/strings.c:481 +#: src/util/strings.c:528 msgid "Failed to expand `$HOME': environment variable `HOME' not set" msgstr "扩展“$HOME”失败:没有设置环境变量“HOME”" -#: src/util/strings.c:573 +#: src/util/strings.c:625 msgid "ms" msgstr "毫秒" -#: src/util/strings.c:578 -msgid "eternity" +#: src/util/strings.c:629 +msgid "forever" msgstr "" -#: src/util/strings.c:582 +#: src/util/strings.c:631 +msgid "0 ms" +msgstr "" + +#: src/util/strings.c:637 msgid "s" msgstr "秒" -#: src/util/strings.c:586 +#: src/util/strings.c:643 msgid "m" msgstr "分" -#: src/util/strings.c:590 +#: src/util/strings.c:649 msgid "h" msgstr "时" -#: src/util/strings.c:594 -msgid " days" +#: src/util/strings.c:656 +#, fuzzy +msgid "day" +msgstr " 天" + +#: src/util/strings.c:658 +#, fuzzy +msgid "days" msgstr " 天" -#: src/util/strings.c:618 +#: src/util/strings.c:685 msgid "end of time" msgstr "" -#: src/util/strings.c:1012 +#: src/util/strings.c:1073 msgid "IPv6 address did not start with `['\n" msgstr "" -#: src/util/strings.c:1020 +#: src/util/strings.c:1081 msgid "IPv6 address did contain ':' to separate port number\n" msgstr "" -#: src/util/strings.c:1026 +#: src/util/strings.c:1087 msgid "IPv6 address did contain ']' before ':' to separate port number\n" msgstr "" -#: src/util/strings.c:1033 +#: src/util/strings.c:1094 msgid "IPv6 address did contain a valid port number after the last ':'\n" msgstr "" -#: src/util/strings.c:1042 +#: src/util/strings.c:1103 #, fuzzy, c-format msgid "Invalid IPv6 address `%s': %s\n" msgstr "无效的进程优先级“%s”\n" -#: src/vpn/gnunet-service-vpn.c:511 src/vpn/gnunet-service-vpn.c:1071 +#: src/vpn/gnunet-service-vpn.c:512 src/vpn/gnunet-service-vpn.c:1088 msgid "# Active tunnels" msgstr "" -#: src/vpn/gnunet-service-vpn.c:608 src/vpn/gnunet-service-vpn.c:645 +#: src/vpn/gnunet-service-vpn.c:609 src/vpn/gnunet-service-vpn.c:646 #, fuzzy msgid "# peers connected to mesh tunnels" msgstr "" @@ -5668,79 +6365,79 @@ msgstr "" msgid "# Bytes dropped in mesh queue (overflow)" msgstr "" -#: src/vpn/gnunet-service-vpn.c:772 +#: src/vpn/gnunet-service-vpn.c:771 msgid "# Mesh tunnels created" msgstr "" -#: src/vpn/gnunet-service-vpn.c:795 +#: src/vpn/gnunet-service-vpn.c:794 #, fuzzy msgid "Failed to setup mesh tunnel!\n" msgstr "发送消息失败。\n" -#: src/vpn/gnunet-service-vpn.c:973 +#: src/vpn/gnunet-service-vpn.c:990 #, c-format msgid "Protocol %u not supported, dropping\n" msgstr "" -#: src/vpn/gnunet-service-vpn.c:1291 +#: src/vpn/gnunet-service-vpn.c:1308 msgid "# ICMPv4 packets dropped (not allowed)" msgstr "" -#: src/vpn/gnunet-service-vpn.c:1312 +#: src/vpn/gnunet-service-vpn.c:1329 msgid "# ICMPv6 packets dropped (not allowed)" msgstr "" -#: src/vpn/gnunet-service-vpn.c:1517 +#: src/vpn/gnunet-service-vpn.c:1534 msgid "# Packets received from TUN interface" msgstr "" -#: src/vpn/gnunet-service-vpn.c:1555 src/vpn/gnunet-service-vpn.c:1596 +#: src/vpn/gnunet-service-vpn.c:1572 src/vpn/gnunet-service-vpn.c:1613 #, c-format msgid "Packet received for unmapped destination `%s' (dropping it)\n" msgstr "" -#: src/vpn/gnunet-service-vpn.c:1606 +#: src/vpn/gnunet-service-vpn.c:1623 msgid "Received IPv4 packet with options (dropping it)\n" msgstr "" -#: src/vpn/gnunet-service-vpn.c:1620 +#: src/vpn/gnunet-service-vpn.c:1637 #, c-format msgid "Received packet of unknown protocol %d from TUN (dropping it)\n" msgstr "" -#: src/vpn/gnunet-service-vpn.c:1704 +#: src/vpn/gnunet-service-vpn.c:1721 msgid "# ICMP packets received from mesh" msgstr "" -#: src/vpn/gnunet-service-vpn.c:2045 +#: src/vpn/gnunet-service-vpn.c:2062 msgid "# UDP packets received from mesh" msgstr "" -#: src/vpn/gnunet-service-vpn.c:2203 +#: src/vpn/gnunet-service-vpn.c:2220 msgid "# TCP packets received from mesh" msgstr "" -#: src/vpn/gnunet-service-vpn.c:2354 +#: src/vpn/gnunet-service-vpn.c:2371 msgid "Failed to find unallocated IPv4 address in VPN's range\n" msgstr "" -#: src/vpn/gnunet-service-vpn.c:2409 +#: src/vpn/gnunet-service-vpn.c:2426 msgid "Failed to find unallocated IPv6 address in VPN's range\n" msgstr "" -#: src/vpn/gnunet-service-vpn.c:2448 src/vpn/gnunet-service-vpn.c:2661 +#: src/vpn/gnunet-service-vpn.c:2465 src/vpn/gnunet-service-vpn.c:2678 msgid "# Active destinations" msgstr "" -#: src/vpn/gnunet-service-vpn.c:2734 +#: src/vpn/gnunet-service-vpn.c:2751 msgid "Failed to allocate IP address for new destination\n" msgstr "" -#: src/vpn/gnunet-service-vpn.c:3141 +#: src/vpn/gnunet-service-vpn.c:3138 msgid "IPv6 support disabled as this system does not support IPv6\n" msgstr "" -#: src/vpn/gnunet-service-vpn.c:3173 +#: src/vpn/gnunet-service-vpn.c:3170 msgid "IPv4 support disabled as this system does not support IPv4\n" msgstr "" @@ -5749,96 +6446,358 @@ msgstr "" msgid "Error creating tunnel\n" msgstr "创建用户出错" -#: src/vpn/gnunet-vpn.c:195 src/vpn/gnunet-vpn.c:226 +#: src/vpn/gnunet-vpn.c:194 src/vpn/gnunet-vpn.c:225 #, c-format msgid "Option `%s' makes no sense with option `%s'.\n" msgstr "" -#: src/vpn/gnunet-vpn.c:208 +#: src/vpn/gnunet-vpn.c:207 #, fuzzy, c-format msgid "Option `%s' or `%s' is required.\n" msgstr "%s:选项“%s”有歧义\n" -#: src/vpn/gnunet-vpn.c:220 +#: src/vpn/gnunet-vpn.c:219 #, c-format msgid "Option `%s' or `%s' is required when using option `%s'.\n" msgstr "" -#: src/vpn/gnunet-vpn.c:238 +#: src/vpn/gnunet-vpn.c:237 #, fuzzy, c-format msgid "`%s' is not a valid peer identifier.\n" msgstr "“%s”不可用。\n" -#: src/vpn/gnunet-vpn.c:260 +#: src/vpn/gnunet-vpn.c:259 #, fuzzy, c-format msgid "`%s' is not a valid IP address.\n" msgstr "“%s”不可用。\n" -#: src/vpn/gnunet-vpn.c:296 +#: src/vpn/gnunet-vpn.c:295 msgid "request that result should be an IPv4 address" msgstr "" -#: src/vpn/gnunet-vpn.c:299 +#: src/vpn/gnunet-vpn.c:298 msgid "request that result should be an IPv6 address" msgstr "" -#: src/vpn/gnunet-vpn.c:302 +#: src/vpn/gnunet-vpn.c:301 msgid "print IP address only after mesh tunnel has been created" msgstr "" -#: src/vpn/gnunet-vpn.c:305 +#: src/vpn/gnunet-vpn.c:304 msgid "how long should the mapping be valid for new tunnels?" msgstr "" -#: src/vpn/gnunet-vpn.c:308 +#: src/vpn/gnunet-vpn.c:307 msgid "destination IP for the tunnel" msgstr "" -#: src/vpn/gnunet-vpn.c:311 +#: src/vpn/gnunet-vpn.c:310 msgid "peer offering the service we would like to access" msgstr "" -#: src/vpn/gnunet-vpn.c:314 +#: src/vpn/gnunet-vpn.c:313 msgid "name of the service we would like to access" msgstr "" -#: src/vpn/gnunet-vpn.c:317 +#: src/vpn/gnunet-vpn.c:316 msgid "service is offered via TCP" msgstr "" -#: src/vpn/gnunet-vpn.c:320 +#: src/vpn/gnunet-vpn.c:319 msgid "service is offered via UDP" msgstr "" -#: src/vpn/gnunet-vpn.c:329 +#: src/vpn/gnunet-vpn.c:331 msgid "Setup tunnels via VPN." msgstr "" -#: src/include/gnunet_common.h:497 src/include/gnunet_common.h:502 -#: src/include/gnunet_common.h:508 +#: src/include/gnunet_common.h:579 src/include/gnunet_common.h:584 +#: src/include/gnunet_common.h:590 #, c-format msgid "Assertion failed at %s:%d.\n" msgstr "" -#: src/include/gnunet_common.h:518 +#: src/include/gnunet_common.h:600 #, c-format msgid "External protocol violation detected at %s:%d.\n" msgstr "" -#: src/include/gnunet_common.h:539 src/include/gnunet_common.h:546 +#: src/include/gnunet_common.h:621 src/include/gnunet_common.h:628 #, c-format msgid "`%s' failed on file `%s' at %s:%d with error: %s\n" msgstr "" #, fuzzy -#~ msgid "# Peers connected" +#~ msgid "Mesh service could not access hostkey. Exiting.\n" +#~ msgstr "找不到接口“%s”的一个 IP 地址。\n" + +#, fuzzy +#~ msgid "Connected to %s\n" +#~ msgstr "“%s”已连接到“%s”。\n" + +#, fuzzy +#~ msgid "list information for all peers" +#~ msgstr "无法获取有关用户“%s”的信息:%s\n" + +#, fuzzy +#~ msgid "Malformed %s `%s' given in configuration!\n" +#~ msgstr "保存配置失败。" + +#, fuzzy +#~ msgid "Starting HELPER process `%s'\n" +#~ msgstr "卸载 GNUnet 服务" + +#, fuzzy +#~ msgid "Configuration file `%s' for service `%s' not valid: %s\n" +#~ msgstr "配置文件“%s”已写入。\n" + +#, fuzzy +#~ msgid "Unknown message type: '%u'\n" +#~ msgstr "未知操作“%s”。\n" + +#, fuzzy +#~ msgid "Configuration option `%s' in section `%s' missing\n" +#~ msgstr "配置文件“%s”已写入。\n" + +#, fuzzy +#~ msgid "Failed to access chat home directory `%s'\n" +#~ msgstr "解析配置文件“%s”失败\n" + +#, fuzzy +#~ msgid "Failed to create/open key in file `%s'\n" +#~ msgstr "打开日志文件“%s”失败:%s\n" + +#, fuzzy +#~ msgid "Failed to connect to the chat service\n" +#~ msgstr "初始化“%s”服务失败。\n" + +#~ msgid "anonymous" +#~ msgstr "匿名" + +#, fuzzy +#~ msgid "(%s) `%s' said: %s\n" +#~ msgstr "“%s”说:%s\n" + +#, fuzzy +#~ msgid "(%s) `%s' said to you: %s\n" +#~ msgstr "“%s”对您说:%s\n" + +#, fuzzy +#~ msgid "(%s) `%s' said for sure: %s\n" +#~ msgstr "“%s”对您说:%s\n" + +#, fuzzy +#~ msgid "(%s) `%s' said to you for sure: %s\n" +#~ msgstr "“%s”对您说:%s\n" + +#, fuzzy +#~ msgid "(%s) `%s' said off the record: %s\n" +#~ msgstr "“%s”对您说:%s\n" + +#~ msgid "`%s' entered the room\n" +#~ msgstr "“%s”进入了房间\n" + +#~ msgid "`%s' left the room\n" +#~ msgstr "“%s”离开了房间\n" + +#, fuzzy +#~ msgid "Could not change username\n" +#~ msgstr "已将用户名改为“%s”。\n" + +#, fuzzy +#~ msgid "Changed username to `%s'\n" +#~ msgstr "已将用户名改为“%s”。\n" + +#~ msgid "Users in room `%s': " +#~ msgstr "房间“%s”中的用户:" + +#~ msgid "Syntax: /msg USERNAME MESSAGE" +#~ msgstr "语法:/msg 用户名 消息" + +#~ msgid "User `%s' is currently not in the room!\n" +#~ msgstr "用户“%s”当前不在房间里!\n" + +#, fuzzy +#~ msgid "Unknown command `%s'\n" +#~ msgstr "未知的命令“%s”。\n" + +#~ msgid "You must specify a nickname\n" +#~ msgstr "您必须指定一个昵称\n" + +#~ msgid "set the chat room to join" +#~ msgstr "设置要加入的聊天室" + +#, fuzzy +#~ msgid "Failed to queue a message notification\n" +#~ msgstr "保存配置失败。" + +#, fuzzy +#~ msgid "Failed to queue a join notification\n" +#~ msgstr "保存配置失败。" + +#, fuzzy +#~ msgid "Failed to queue a confirmation receipt\n" +#~ msgstr "保存配置失败。" + +#, fuzzy +#~ msgid "Failed to queue a leave notification\n" +#~ msgstr "保存配置失败。" + +#, fuzzy +#~ msgid "Connected to %s service!\n" +#~ msgstr "“%s”已连接到“%s”。\n" + +#, fuzzy +#~ msgid "Configuration fails to specify `%s' in section `%s'\n" +#~ msgstr "配置文件“%s”已写入。\n" + +#, fuzzy +#~ msgid "Failed to start daemon: %s\n" +#~ msgstr "运行 %s失败:%s %d\n" + +#, fuzzy +#~ msgid "Configuration fails to specify `%s', assuming default value." +#~ msgstr "配置文件“%s”已写入。\n" + +#, fuzzy +#~ msgid "Option `%s' not specified in configuration section `%s'\n" +#~ msgstr "配置文件“%s”已写入。\n" + +#, fuzzy +#~ msgid "Peer is lacking HOSTKEY configuration setting.\n" +#~ msgstr "立即保存配置?" + +#, fuzzy +#~ msgid "Could not access hostkey.\n" +#~ msgstr "找不到接口“%s”的一个 IP 地址。\n" + +#, fuzzy +#~ msgid "Failed to create pipe for `gnunet-peerinfo' process.\n" +#~ msgstr "初始化“%s”服务失败。\n" + +#, fuzzy +#~ msgid "Failed to create pipe for `ssh' process.\n" +#~ msgstr "初始化“%s”服务失败。\n" + +#, fuzzy +#~ msgid "Could not start `%s' process to create hostkey.\n" +#~ msgstr "初始化“%s”服务失败。\n" + +#, fuzzy +#~ msgid "Failed to start `gnunet-peerinfo' process.\n" +#~ msgstr "初始化“%s”服务失败。\n" + +#, fuzzy +#~ msgid "Failed to start `ssh' process.\n" +#~ msgstr "初始化“%s”服务失败。\n" + +#, fuzzy +#~ msgid "Failed to get hostkey!\n" +#~ msgstr "发送消息失败。\n" + +#, fuzzy +#~ msgid "Could not start `%s' process to start GNUnet.\n" +#~ msgstr "初始化“%s”服务失败。\n" + +#, fuzzy +#~ msgid "Failed to start `gnunet-arm' process.\n" +#~ msgstr "初始化“%s”服务失败。\n" + +#, fuzzy +#~ msgid "Starting service %s for peer `%4s'\n" +#~ msgstr "卸载 GNUnet 服务" + +#, fuzzy +#~ msgid "Could not start `%s' process to copy configuration directory.\n" +#~ msgstr "找不到主机“%s”的 IP:%s\n" + +#, fuzzy +#~ msgid "Terminating peer `%4s'\n" +#~ msgstr "未知的用户“%s”\n" + +#, fuzzy +#~ msgid "Setting d->dead on peer `%4s'\n" +#~ msgstr "卸载 GNUnet 服务" + +#, fuzzy +#~ msgid "Failed to write new configuration to disk." +#~ msgstr "保存配置失败。" + +#, fuzzy +#~ msgid "Could not start `%s' process to copy configuration file.\n" +#~ msgstr "找不到主机“%s”的 IP:%s\n" + +#, fuzzy +#~ msgid "Failed to copy new configuration to remote machine." +#~ msgstr "保存配置失败。" + +#, fuzzy +#~ msgid "Peers failed to connect" #~ msgstr "" #~ "\n" #~ "按任意键继续\n" #, fuzzy -#~ msgid "%s failed for `%s' at %s:%d: `%s'\n" -#~ msgstr "对驱动器“%2$s”的“%1$s”操作失败:%3$u\n" +#~ msgid "Failed to connect to core service of first peer!\n" +#~ msgstr "加载 sqstore 服务失败。检查您的配置!\n" + +#, fuzzy +#~ msgid "Invalid value `%s' for option `%s' in section `%s': expected float\n" +#~ msgstr "配置不满足配置规范文件“%s”的约束!\n" + +#, fuzzy +#~ msgid "Could not read hostkeys file `%s'!\n" +#~ msgstr "找不到接口“%s”的一个 IP 地址。\n" + +#, fuzzy +#~ msgid "Could not create configuration for peer number %u on `%s'!\n" +#~ msgstr "解析配置文件“%s”失败\n" + +#, fuzzy +#~ msgid "Invalid configuration option `%s' in section `%s'\n" +#~ msgstr "配置文件“%s”已写入。\n" + +#, fuzzy +#~ msgid "Missing configuration option `%s' in section `%s'\n" +#~ msgstr "配置文件“%s”已写入。\n" + +#, fuzzy +#~ msgid "internal error" +#~ msgstr "未知错误。\n" + +#, fuzzy +#~ msgid "Could not create namespace `%s'\n" +#~ msgstr "无法解析“%s”(%s):%s\n" + +#, fuzzy +#~ msgid "Stored zonekey for zone `%s' in file `%s'\n" +#~ msgstr "打开日志文件“%s”失败:%s\n" + +#, fuzzy +#~ msgid "Namestore removed record successfully" +#~ msgstr "GNUnet 服务安装成功。\n" + +#, fuzzy +#~ msgid "Could not read hostkeys file, specify hostkey file with -H!\n" +#~ msgstr "找不到接口“%s”的一个 IP 地址。\n" + +#, fuzzy +#~ msgid "Could not open hostkeys file: %s\n" +#~ msgstr "找不到接口“%s”的一个 IP 地址。\n" + +#, fuzzy +#~ msgid "access (%s, X_OK) failed: %s\n" +#~ msgstr "“%s”说:%s\n" + +#, fuzzy +#~ msgid "stat (%s) failed: %s\n" +#~ msgstr "“%s”说:%s\n" + +#, fuzzy +#~ msgid "# Peers connected" +#~ msgstr "" +#~ "\n" +#~ "按任意键继续\n" #, fuzzy #~ msgid "Unable to initialize Postgres with configuration `%s': %s" @@ -5860,12 +6819,6 @@ msgstr "" #~ msgid "Failed during blacklist file copying!\n" #~ msgstr "解析配置文件“%s”失败\n" -#, fuzzy -#~ msgid "# fast reconnects failed" -#~ msgstr "" -#~ "\n" -#~ "按任意键继续\n" - #~ msgid "Unknown user `%s'\n" #~ msgstr "未知的用户“%s”\n" @@ -5873,10 +6826,6 @@ msgstr "" #~ msgid "Failed to connect to statistics service!\n" #~ msgstr "初始化“%s”服务失败。\n" -#, fuzzy -#~ msgid "Failed to send to `%s': %s\n" -#~ msgstr "打开日志文件“%s”失败:%s\n" - #, fuzzy #~ msgid "Could not access file: %s\n" #~ msgstr "错误:无法访问服务:%s\n" @@ -5897,10 +6846,6 @@ msgstr "" #~ msgid "Service `%s' stopped\n" #~ msgstr "服务已删除。\n" -#, fuzzy -#~ msgid "Unable to start service `%s': %s\n" -#~ msgstr "无法保存配置文件“%s”:" - #, fuzzy #~ msgid "Unable to accept connection for service `%s': %s\n" #~ msgstr "无法保存配置文件“%s”:" @@ -6154,9 +7099,6 @@ msgstr "" #~ msgid "Back" #~ msgstr "后退" -#~ msgid "Exit" -#~ msgstr "退出" - #~ msgid "Up" #~ msgstr "向上" @@ -6191,9 +7133,6 @@ msgstr "" #~ msgid "install GNUnet as Windows service" #~ msgstr "以 Windows 服务方式安装 GNUnet" -#~ msgid "increase the maximum number of TCP/IP connections" -#~ msgstr "增加 TCP/IP 的最大连接数" - #~ msgid "display a file's hash value" #~ msgstr "显示一个文件的散列值" @@ -6462,9 +7401,6 @@ msgstr "" #~ msgid "Real-time delay violation (%llu ms) at %s:%u\n" #~ msgstr "实时延迟冲突(%llu 毫秒),于 %s:%u\n" -#~ msgid "`%s' failed with error code %d: %s\n" -#~ msgstr "“%s”以错误码 %d 失败:%s\n" - #~ msgid "Deadlock due to `%s'.\n" #~ msgstr "“%s”造成了死锁。\n" @@ -6489,9 +7425,6 @@ msgstr "" #~ msgid "output in gnuplot format" #~ msgstr "以 gnuplot 格式输出" -#~ msgid "number of iterations" -#~ msgstr "迭代次数" - #~ msgid "number of messages to use per iteration" #~ msgstr "每次迭代所使用的消息数量" diff --git a/src/Makefile.am b/src/Makefile.am index 37bcbf6..f10630d 100644 --- a/src/Makefile.am +++ b/src/Makefile.am @@ -3,12 +3,15 @@ #endif if HAVE_EXPERIMENTAL - EXP_DIR = chat dv stream regex + EXP_DIR = chat dv consensus sysmon endif if LINUX # All of these currently only work on GNU/Linux - LINUX_DIR = dns gns exit vpn pt + LINUX_DIR = dns exit vpn gns pt +endif +if MINGW + MINGW_DIR = dns gns endif if HAVE_MYSQL @@ -28,6 +31,7 @@ SUBDIRS = \ block \ statistics \ arm \ + testing \ peerinfo \ $(MYSQL_DIR) \ $(POSTGRES_DIR) \ @@ -39,17 +43,20 @@ SUBDIRS = \ nat \ fragmentation \ transport \ + ats-tool \ peerinfo-tool \ core \ - testing \ testbed \ nse \ dht \ hostlist \ topology \ - fs \ + regex \ mesh \ lockmanager \ + stream \ + fs \ $(LINUX_DIR) \ + $(MINGW_DIR) \ integration-tests \ $(EXP_DIR) diff --git a/src/Makefile.in b/src/Makefile.in index f4f21c1..6f0e24a 100644 --- a/src/Makefile.in +++ b/src/Makefile.in @@ -1,9 +1,9 @@ -# Makefile.in generated by automake 1.11.1 from Makefile.am. +# Makefile.in generated by automake 1.11.6 from Makefile.am. # @configure_input@ # Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, -# 2003, 2004, 2005, 2006, 2007, 2008, 2009 Free Software Foundation, -# Inc. +# 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Free Software +# Foundation, Inc. # This Makefile.in is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. @@ -19,6 +19,23 @@ # INTLEMU_SUBDIRS = intlemu #endif VPATH = @srcdir@ +am__make_dryrun = \ + { \ + am__dry=no; \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + echo 'am--echo: ; @echo "AM" OK' | $(MAKE) -f - 2>/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } pkgdatadir = $(datadir)/@PACKAGE@ pkgincludedir = $(includedir)/@PACKAGE@ pkglibdir = $(libdir)/@PACKAGE@ @@ -43,14 +60,15 @@ DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 am__aclocal_m4_deps = $(top_srcdir)/m4/absolute-header.m4 \ $(top_srcdir)/m4/align.m4 $(top_srcdir)/m4/argz.m4 \ - $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/iconv.m4 \ - $(top_srcdir)/m4/lib-ld.m4 $(top_srcdir)/m4/lib-link.m4 \ - $(top_srcdir)/m4/lib-prefix.m4 $(top_srcdir)/m4/libcurl.m4 \ - $(top_srcdir)/m4/libgcrypt.m4 $(top_srcdir)/m4/libtool.m4 \ - $(top_srcdir)/m4/libunistring.m4 $(top_srcdir)/m4/ltdl.m4 \ - $(top_srcdir)/m4/ltoptions.m4 $(top_srcdir)/m4/ltsugar.m4 \ - $(top_srcdir)/m4/ltversion.m4 $(top_srcdir)/m4/lt~obsolete.m4 \ - $(top_srcdir)/m4/nls.m4 $(top_srcdir)/m4/po.m4 \ + $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/glib-2.0.m4 \ + $(top_srcdir)/m4/iconv.m4 $(top_srcdir)/m4/lib-ld.m4 \ + $(top_srcdir)/m4/lib-link.m4 $(top_srcdir)/m4/lib-prefix.m4 \ + $(top_srcdir)/m4/libcurl.m4 $(top_srcdir)/m4/libgcrypt.m4 \ + $(top_srcdir)/m4/libtool.m4 $(top_srcdir)/m4/libunistring.m4 \ + $(top_srcdir)/m4/ltdl.m4 $(top_srcdir)/m4/ltoptions.m4 \ + $(top_srcdir)/m4/ltsugar.m4 $(top_srcdir)/m4/ltversion.m4 \ + $(top_srcdir)/m4/lt~obsolete.m4 $(top_srcdir)/m4/nls.m4 \ + $(top_srcdir)/m4/pkg.m4 $(top_srcdir)/m4/po.m4 \ $(top_srcdir)/m4/progtest.m4 $(top_srcdir)/acinclude.m4 \ $(top_srcdir)/configure.ac am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ @@ -59,11 +77,11 @@ mkinstalldirs = $(install_sh) -d CONFIG_HEADER = $(top_builddir)/gnunet_config.h CONFIG_CLEAN_FILES = CONFIG_CLEAN_VPATH_FILES = -AM_V_GEN = $(am__v_GEN_$(V)) -am__v_GEN_ = $(am__v_GEN_$(AM_DEFAULT_VERBOSITY)) +AM_V_GEN = $(am__v_GEN_@AM_V@) +am__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@) am__v_GEN_0 = @echo " GEN " $@; -AM_V_at = $(am__v_at_$(V)) -am__v_at_ = $(am__v_at_$(AM_DEFAULT_VERBOSITY)) +AM_V_at = $(am__v_at_@AM_V@) +am__v_at_ = $(am__v_at_@AM_DEFAULT_V@) am__v_at_0 = @ SOURCES = DIST_SOURCES = @@ -74,6 +92,11 @@ RECURSIVE_TARGETS = all-recursive check-recursive dvi-recursive \ install-pdf-recursive install-ps-recursive install-recursive \ installcheck-recursive installdirs-recursive pdf-recursive \ ps-recursive uninstall-recursive +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac RECURSIVE_CLEAN_TARGETS = mostlyclean-recursive clean-recursive \ distclean-recursive maintainer-clean-recursive AM_RECURSIVE_TARGETS = $(RECURSIVE_TARGETS:-recursive=) \ @@ -81,11 +104,12 @@ AM_RECURSIVE_TARGETS = $(RECURSIVE_TARGETS:-recursive=) \ distdir ETAGS = etags CTAGS = ctags -DIST_SUBDIRS = include util hello tun block statistics arm peerinfo \ - mysql postgres datacache datastore namestore template ats nat \ - fragmentation transport peerinfo-tool core testing testbed nse \ - dht hostlist topology fs mesh lockmanager dns gns exit vpn pt \ - integration-tests chat dv stream regex +DIST_SUBDIRS = include util hello tun block statistics arm testing \ + peerinfo mysql postgres datacache datastore namestore template \ + ats nat fragmentation transport ats-tool peerinfo-tool core \ + testbed nse dht hostlist topology regex mesh lockmanager \ + stream fs dns exit vpn gns pt integration-tests chat dv \ + consensus sysmon DISTFILES = $(DIST_COMMON) $(DIST_SOURCES) $(TEXINFOS) $(EXTRA_DIST) am__relativize = \ dir0=`pwd`; \ @@ -147,6 +171,10 @@ EXEEXT = @EXEEXT@ EXT_LIBS = @EXT_LIBS@ EXT_LIB_PATH = @EXT_LIB_PATH@ FGREP = @FGREP@ +GLIB_CFLAGS = @GLIB_CFLAGS@ +GLIB_GENMARSHAL = @GLIB_GENMARSHAL@ +GLIB_LIBS = @GLIB_LIBS@ +GLIB_MKENUMS = @GLIB_MKENUMS@ GMSGFMT = @GMSGFMT@ GMSGFMT_015 = @GMSGFMT_015@ GNUNETDNS_GROUP = @GNUNETDNS_GROUP@ @@ -157,6 +185,7 @@ GN_LIBINTL = @GN_LIBINTL@ GN_LIB_LDFLAGS = @GN_LIB_LDFLAGS@ GN_PLUGIN_LDFLAGS = @GN_PLUGIN_LDFLAGS@ GN_USER_HOME_DIR = @GN_USER_HOME_DIR@ +GOBJECT_QUERY = @GOBJECT_QUERY@ GREP = @GREP@ HAVE_LIBUNISTRING = @HAVE_LIBUNISTRING@ INCLTDL = @INCLTDL@ @@ -179,6 +208,8 @@ LIBCURL_CPPFLAGS = @LIBCURL_CPPFLAGS@ LIBGCRYPT_CFLAGS = @LIBGCRYPT_CFLAGS@ LIBGCRYPT_CONFIG = @LIBGCRYPT_CONFIG@ LIBGCRYPT_LIBS = @LIBGCRYPT_LIBS@ +LIBGTOP_CFLAGS = @LIBGTOP_CFLAGS@ +LIBGTOP_LIBS = @LIBGTOP_LIBS@ LIBICONV = @LIBICONV@ LIBINTL = @LIBINTL@ LIBLTDL = @LIBLTDL@ @@ -200,6 +231,7 @@ LT_CONFIG_H = @LT_CONFIG_H@ LT_DLLOADERS = @LT_DLLOADERS@ LT_DLPREOPEN = @LT_DLPREOPEN@ MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ MKDIR_P = @MKDIR_P@ MONKEYPREFIX = @MONKEYPREFIX@ MSGFMT = @MSGFMT@ @@ -209,6 +241,7 @@ MYSQL_CPPFLAGS = @MYSQL_CPPFLAGS@ MYSQL_LDFLAGS = @MYSQL_LDFLAGS@ NM = @NM@ NMEDIT = @NMEDIT@ +NSS_DIR = @NSS_DIR@ OBJC = @OBJC@ OBJCDEPMODE = @OBJCDEPMODE@ OBJCFLAGS = @OBJCFLAGS@ @@ -224,6 +257,7 @@ PACKAGE_TARNAME = @PACKAGE_TARNAME@ PACKAGE_URL = @PACKAGE_URL@ PACKAGE_VERSION = @PACKAGE_VERSION@ PATH_SEPARATOR = @PATH_SEPARATOR@ +PKG_CONFIG = @PKG_CONFIG@ POSTGRES_CPPFLAGS = @POSTGRES_CPPFLAGS@ POSTGRES_LDFLAGS = @POSTGRES_LDFLAGS@ POSUB = @POSUB@ @@ -255,6 +289,7 @@ abs_builddir = @abs_builddir@ abs_srcdir = @abs_srcdir@ abs_top_builddir = @abs_top_builddir@ abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ ac_ct_CC = @ac_ct_CC@ ac_ct_CXX = @ac_ct_CXX@ ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ @@ -277,6 +312,7 @@ datarootdir = @datarootdir@ docdir = @docdir@ dvidir = @dvidir@ exec_prefix = @exec_prefix@ +gitcommand = @gitcommand@ host = @host@ host_alias = @host_alias@ host_cpu = @host_cpu@ @@ -290,7 +326,6 @@ libdir = @libdir@ libexecdir = @libexecdir@ localedir = @localedir@ localstatedir = @localstatedir@ -lt_ECHO = @lt_ECHO@ ltdl_LIBOBJS = @ltdl_LIBOBJS@ ltdl_LTLIBOBJS = @ltdl_LTLIBOBJS@ mandir = @mandir@ @@ -308,6 +343,7 @@ sbindir = @sbindir@ sharedstatedir = @sharedstatedir@ srcdir = @srcdir@ subdirs = @subdirs@ +svnversioncommand = @svnversioncommand@ sys_symbol_underscore = @sys_symbol_underscore@ sysconfdir = @sysconfdir@ target = @target@ @@ -318,10 +354,11 @@ target_vendor = @target_vendor@ top_build_prefix = @top_build_prefix@ top_builddir = @top_builddir@ top_srcdir = @top_srcdir@ -@HAVE_EXPERIMENTAL_TRUE@EXP_DIR = chat dv stream regex +@HAVE_EXPERIMENTAL_TRUE@EXP_DIR = chat dv consensus sysmon # All of these currently only work on GNU/Linux -@LINUX_TRUE@LINUX_DIR = dns gns exit vpn pt +@LINUX_TRUE@LINUX_DIR = dns exit vpn gns pt +@MINGW_TRUE@MINGW_DIR = dns gns @HAVE_MYSQL_TRUE@MYSQL_DIR = mysql @HAVE_POSTGRES_TRUE@POSTGRES_DIR = postgres SUBDIRS = \ @@ -332,6 +369,7 @@ SUBDIRS = \ block \ statistics \ arm \ + testing \ peerinfo \ $(MYSQL_DIR) \ $(POSTGRES_DIR) \ @@ -343,18 +381,21 @@ SUBDIRS = \ nat \ fragmentation \ transport \ + ats-tool \ peerinfo-tool \ core \ - testing \ testbed \ nse \ dht \ hostlist \ topology \ - fs \ + regex \ mesh \ lockmanager \ + stream \ + fs \ $(LINUX_DIR) \ + $(MINGW_DIR) \ integration-tests \ $(EXP_DIR) @@ -565,13 +606,10 @@ distdir: $(DISTFILES) done @list='$(DIST_SUBDIRS)'; for subdir in $$list; do \ if test "$$subdir" = .; then :; else \ - test -d "$(distdir)/$$subdir" \ - || $(MKDIR_P) "$(distdir)/$$subdir" \ - || exit 1; \ - fi; \ - done - @list='$(DIST_SUBDIRS)'; for subdir in $$list; do \ - if test "$$subdir" = .; then :; else \ + $(am__make_dryrun) \ + || test -d "$(distdir)/$$subdir" \ + || $(MKDIR_P) "$(distdir)/$$subdir" \ + || exit 1; \ dir1=$$subdir; dir2="$(distdir)/$$subdir"; \ $(am__relativize); \ new_distdir=$$reldir; \ @@ -606,10 +644,15 @@ install-am: all-am installcheck: installcheck-recursive install-strip: - $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ - install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ - `test -z '$(STRIP)' || \ - echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi mostlyclean-generic: clean-generic: diff --git a/src/arm/Makefile.am b/src/arm/Makefile.am index 7da1e2c..48d9955 100644 --- a/src/arm/Makefile.am +++ b/src/arm/Makefile.am @@ -2,6 +2,8 @@ INCLUDES = -I$(top_srcdir)/src/include pkgcfgdir= $(pkgdatadir)/config.d/ +libexecdir= $(pkglibdir)/libexec/ + pkgcfg_DATA = \ arm.conf @@ -23,11 +25,13 @@ libgnunetarm_la_LIBADD = \ $(GN_LIBINTL) $(XLIB) libgnunetarm_la_LDFLAGS = \ $(GN_LIB_LDFLAGS) $(WINFLAGS) \ - -version-info 1:1:0 + -version-info 1:3:0 bin_PROGRAMS = \ - gnunet-arm \ + gnunet-arm + +libexec_PROGRAMS = \ gnunet-service-arm \ mockup-service @@ -58,10 +62,10 @@ mockup_service_SOURCES = \ check_PROGRAMS = \ test_arm_api \ test_exponential_backoff \ - test_gnunet_service_manager + test_gnunet_service_arm check_SCRIPTS = \ - test_gnunet_arm.sh + test_gnunet_arm.py if ENABLE_TEST_RUN TESTS = $(check_PROGRAMS) $(check_SCRIPTS) @@ -79,13 +83,23 @@ test_exponential_backoff_LDADD = \ $(top_builddir)/src/arm/libgnunetarm.la \ $(top_builddir)/src/util/libgnunetutil.la -test_gnunet_service_manager_SOURCES = \ - test_gnunet_service_manager.c - test_gnunet_service_manager_LDADD = \ +test_gnunet_service_arm_SOURCES = \ + test_gnunet_service_arm.c + test_gnunet_service_arm_LDADD = \ $(top_builddir)/src/arm/libgnunetarm.la \ $(top_builddir)/src/util/libgnunetutil.la +do_subst = $(SED) -e 's,[@]PYTHON[@],$(PYTHON),g' + +%.py: %.py.in Makefile + $(do_subst) < $(srcdir)/$< > $@ + chmod +x $@ + +test_gnunet_arm.py: test_gnunet_arm.py.in Makefile + $(do_subst) < $(srcdir)/test_gnunet_arm.py.in > test_gnunet_arm.py + chmod +x test_gnunet_arm.py + EXTRA_DIST = \ test_arm_api_data.conf \ - do_start_process.c \ - $(check_SCRIPTS) + test_gnunet_arm.py.in \ + do_start_process.c diff --git a/src/arm/Makefile.in b/src/arm/Makefile.in index 122ab3c..07b50d6 100644 --- a/src/arm/Makefile.in +++ b/src/arm/Makefile.in @@ -1,9 +1,9 @@ -# Makefile.in generated by automake 1.11.1 from Makefile.am. +# Makefile.in generated by automake 1.11.6 from Makefile.am. # @configure_input@ # Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, -# 2003, 2004, 2005, 2006, 2007, 2008, 2009 Free Software Foundation, -# Inc. +# 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Free Software +# Foundation, Inc. # This Makefile.in is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. @@ -18,6 +18,23 @@ VPATH = @srcdir@ +am__make_dryrun = \ + { \ + am__dry=no; \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + echo 'am--echo: ; @echo "AM" OK' | $(MAKE) -f - 2>/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } pkgdatadir = $(datadir)/@PACKAGE@ pkgincludedir = $(includedir)/@PACKAGE@ pkglibdir = $(libdir)/@PACKAGE@ @@ -37,25 +54,26 @@ POST_UNINSTALL = : build_triplet = @build@ host_triplet = @host@ target_triplet = @target@ -bin_PROGRAMS = gnunet-arm$(EXEEXT) gnunet-service-arm$(EXEEXT) \ - mockup-service$(EXEEXT) +bin_PROGRAMS = gnunet-arm$(EXEEXT) +libexec_PROGRAMS = gnunet-service-arm$(EXEEXT) mockup-service$(EXEEXT) check_PROGRAMS = test_arm_api$(EXEEXT) \ test_exponential_backoff$(EXEEXT) \ - test_gnunet_service_manager$(EXEEXT) + test_gnunet_service_arm$(EXEEXT) subdir = src/arm DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in \ $(srcdir)/arm.conf.in ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 am__aclocal_m4_deps = $(top_srcdir)/m4/absolute-header.m4 \ $(top_srcdir)/m4/align.m4 $(top_srcdir)/m4/argz.m4 \ - $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/iconv.m4 \ - $(top_srcdir)/m4/lib-ld.m4 $(top_srcdir)/m4/lib-link.m4 \ - $(top_srcdir)/m4/lib-prefix.m4 $(top_srcdir)/m4/libcurl.m4 \ - $(top_srcdir)/m4/libgcrypt.m4 $(top_srcdir)/m4/libtool.m4 \ - $(top_srcdir)/m4/libunistring.m4 $(top_srcdir)/m4/ltdl.m4 \ - $(top_srcdir)/m4/ltoptions.m4 $(top_srcdir)/m4/ltsugar.m4 \ - $(top_srcdir)/m4/ltversion.m4 $(top_srcdir)/m4/lt~obsolete.m4 \ - $(top_srcdir)/m4/nls.m4 $(top_srcdir)/m4/po.m4 \ + $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/glib-2.0.m4 \ + $(top_srcdir)/m4/iconv.m4 $(top_srcdir)/m4/lib-ld.m4 \ + $(top_srcdir)/m4/lib-link.m4 $(top_srcdir)/m4/lib-prefix.m4 \ + $(top_srcdir)/m4/libcurl.m4 $(top_srcdir)/m4/libgcrypt.m4 \ + $(top_srcdir)/m4/libtool.m4 $(top_srcdir)/m4/libunistring.m4 \ + $(top_srcdir)/m4/ltdl.m4 $(top_srcdir)/m4/ltoptions.m4 \ + $(top_srcdir)/m4/ltsugar.m4 $(top_srcdir)/m4/ltversion.m4 \ + $(top_srcdir)/m4/lt~obsolete.m4 $(top_srcdir)/m4/nls.m4 \ + $(top_srcdir)/m4/pkg.m4 $(top_srcdir)/m4/po.m4 \ $(top_srcdir)/m4/progtest.m4 $(top_srcdir)/acinclude.m4 \ $(top_srcdir)/configure.ac am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ @@ -85,8 +103,14 @@ am__nobase_list = $(am__nobase_strip_setup); \ am__base_list = \ sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \ sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g' +am__uninstall_files_from_dir = { \ + test -z "$$files" \ + || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \ + || { echo " ( cd '$$dir' && rm -f" $$files ")"; \ + $(am__cd) "$$dir" && rm -f $$files; }; \ + } am__installdirs = "$(DESTDIR)$(libdir)" "$(DESTDIR)$(bindir)" \ - "$(DESTDIR)$(pkgcfgdir)" + "$(DESTDIR)$(libexecdir)" "$(DESTDIR)$(pkgcfgdir)" LTLIBRARIES = $(lib_LTLIBRARIES) am__DEPENDENCIES_1 = libgnunetarm_la_DEPENDENCIES = \ @@ -94,14 +118,14 @@ libgnunetarm_la_DEPENDENCIES = \ $(am__DEPENDENCIES_1) $(am__DEPENDENCIES_1) am_libgnunetarm_la_OBJECTS = arm_api.lo libgnunetarm_la_OBJECTS = $(am_libgnunetarm_la_OBJECTS) -AM_V_lt = $(am__v_lt_$(V)) -am__v_lt_ = $(am__v_lt_$(AM_DEFAULT_VERBOSITY)) +AM_V_lt = $(am__v_lt_@AM_V@) +am__v_lt_ = $(am__v_lt_@AM_DEFAULT_V@) am__v_lt_0 = --silent libgnunetarm_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ $(AM_CFLAGS) $(CFLAGS) $(libgnunetarm_la_LDFLAGS) $(LDFLAGS) \ -o $@ -PROGRAMS = $(bin_PROGRAMS) +PROGRAMS = $(bin_PROGRAMS) $(libexec_PROGRAMS) am_gnunet_arm_OBJECTS = gnunet-arm.$(OBJEXT) gnunet_arm_OBJECTS = $(am_gnunet_arm_OBJECTS) am_gnunet_service_arm_OBJECTS = gnunet-service-arm.$(OBJEXT) @@ -121,11 +145,11 @@ test_exponential_backoff_OBJECTS = \ test_exponential_backoff_DEPENDENCIES = \ $(top_builddir)/src/arm/libgnunetarm.la \ $(top_builddir)/src/util/libgnunetutil.la -am_test_gnunet_service_manager_OBJECTS = \ - test_gnunet_service_manager.$(OBJEXT) -test_gnunet_service_manager_OBJECTS = \ - $(am_test_gnunet_service_manager_OBJECTS) -test_gnunet_service_manager_DEPENDENCIES = \ +am_test_gnunet_service_arm_OBJECTS = \ + test_gnunet_service_arm.$(OBJEXT) +test_gnunet_service_arm_OBJECTS = \ + $(am_test_gnunet_service_arm_OBJECTS) +test_gnunet_service_arm_DEPENDENCIES = \ $(top_builddir)/src/arm/libgnunetarm.la \ $(top_builddir)/src/util/libgnunetutil.la DEFAULT_INCLUDES = -I.@am__isrc@ -I$(top_builddir) @@ -138,30 +162,35 @@ LTCOMPILE = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) \ $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) \ $(AM_CFLAGS) $(CFLAGS) -AM_V_CC = $(am__v_CC_$(V)) -am__v_CC_ = $(am__v_CC_$(AM_DEFAULT_VERBOSITY)) +AM_V_CC = $(am__v_CC_@AM_V@) +am__v_CC_ = $(am__v_CC_@AM_DEFAULT_V@) am__v_CC_0 = @echo " CC " $@; -AM_V_at = $(am__v_at_$(V)) -am__v_at_ = $(am__v_at_$(AM_DEFAULT_VERBOSITY)) +AM_V_at = $(am__v_at_@AM_V@) +am__v_at_ = $(am__v_at_@AM_DEFAULT_V@) am__v_at_0 = @ CCLD = $(CC) LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ $(AM_LDFLAGS) $(LDFLAGS) -o $@ -AM_V_CCLD = $(am__v_CCLD_$(V)) -am__v_CCLD_ = $(am__v_CCLD_$(AM_DEFAULT_VERBOSITY)) +AM_V_CCLD = $(am__v_CCLD_@AM_V@) +am__v_CCLD_ = $(am__v_CCLD_@AM_DEFAULT_V@) am__v_CCLD_0 = @echo " CCLD " $@; -AM_V_GEN = $(am__v_GEN_$(V)) -am__v_GEN_ = $(am__v_GEN_$(AM_DEFAULT_VERBOSITY)) +AM_V_GEN = $(am__v_GEN_@AM_V@) +am__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@) am__v_GEN_0 = @echo " GEN " $@; SOURCES = $(libgnunetarm_la_SOURCES) $(gnunet_arm_SOURCES) \ $(gnunet_service_arm_SOURCES) $(mockup_service_SOURCES) \ $(test_arm_api_SOURCES) $(test_exponential_backoff_SOURCES) \ - $(test_gnunet_service_manager_SOURCES) + $(test_gnunet_service_arm_SOURCES) DIST_SOURCES = $(libgnunetarm_la_SOURCES) $(gnunet_arm_SOURCES) \ $(gnunet_service_arm_SOURCES) $(mockup_service_SOURCES) \ $(test_arm_api_SOURCES) $(test_exponential_backoff_SOURCES) \ - $(test_gnunet_service_manager_SOURCES) + $(test_gnunet_service_arm_SOURCES) +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac DATA = $(pkgcfg_DATA) ETAGS = etags CTAGS = ctags @@ -203,6 +232,10 @@ EXEEXT = @EXEEXT@ EXT_LIBS = @EXT_LIBS@ EXT_LIB_PATH = @EXT_LIB_PATH@ FGREP = @FGREP@ +GLIB_CFLAGS = @GLIB_CFLAGS@ +GLIB_GENMARSHAL = @GLIB_GENMARSHAL@ +GLIB_LIBS = @GLIB_LIBS@ +GLIB_MKENUMS = @GLIB_MKENUMS@ GMSGFMT = @GMSGFMT@ GMSGFMT_015 = @GMSGFMT_015@ GNUNETDNS_GROUP = @GNUNETDNS_GROUP@ @@ -213,6 +246,7 @@ GN_LIBINTL = @GN_LIBINTL@ GN_LIB_LDFLAGS = @GN_LIB_LDFLAGS@ GN_PLUGIN_LDFLAGS = @GN_PLUGIN_LDFLAGS@ GN_USER_HOME_DIR = @GN_USER_HOME_DIR@ +GOBJECT_QUERY = @GOBJECT_QUERY@ GREP = @GREP@ HAVE_LIBUNISTRING = @HAVE_LIBUNISTRING@ INCLTDL = @INCLTDL@ @@ -235,6 +269,8 @@ LIBCURL_CPPFLAGS = @LIBCURL_CPPFLAGS@ LIBGCRYPT_CFLAGS = @LIBGCRYPT_CFLAGS@ LIBGCRYPT_CONFIG = @LIBGCRYPT_CONFIG@ LIBGCRYPT_LIBS = @LIBGCRYPT_LIBS@ +LIBGTOP_CFLAGS = @LIBGTOP_CFLAGS@ +LIBGTOP_LIBS = @LIBGTOP_LIBS@ LIBICONV = @LIBICONV@ LIBINTL = @LIBINTL@ LIBLTDL = @LIBLTDL@ @@ -256,6 +292,7 @@ LT_CONFIG_H = @LT_CONFIG_H@ LT_DLLOADERS = @LT_DLLOADERS@ LT_DLPREOPEN = @LT_DLPREOPEN@ MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ MKDIR_P = @MKDIR_P@ MONKEYPREFIX = @MONKEYPREFIX@ MSGFMT = @MSGFMT@ @@ -265,6 +302,7 @@ MYSQL_CPPFLAGS = @MYSQL_CPPFLAGS@ MYSQL_LDFLAGS = @MYSQL_LDFLAGS@ NM = @NM@ NMEDIT = @NMEDIT@ +NSS_DIR = @NSS_DIR@ OBJC = @OBJC@ OBJCDEPMODE = @OBJCDEPMODE@ OBJCFLAGS = @OBJCFLAGS@ @@ -280,6 +318,7 @@ PACKAGE_TARNAME = @PACKAGE_TARNAME@ PACKAGE_URL = @PACKAGE_URL@ PACKAGE_VERSION = @PACKAGE_VERSION@ PATH_SEPARATOR = @PATH_SEPARATOR@ +PKG_CONFIG = @PKG_CONFIG@ POSTGRES_CPPFLAGS = @POSTGRES_CPPFLAGS@ POSTGRES_LDFLAGS = @POSTGRES_LDFLAGS@ POSUB = @POSUB@ @@ -311,6 +350,7 @@ abs_builddir = @abs_builddir@ abs_srcdir = @abs_srcdir@ abs_top_builddir = @abs_top_builddir@ abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ ac_ct_CC = @ac_ct_CC@ ac_ct_CXX = @ac_ct_CXX@ ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ @@ -333,6 +373,7 @@ datarootdir = @datarootdir@ docdir = @docdir@ dvidir = @dvidir@ exec_prefix = @exec_prefix@ +gitcommand = @gitcommand@ host = @host@ host_alias = @host_alias@ host_cpu = @host_cpu@ @@ -343,10 +384,9 @@ includedir = @includedir@ infodir = @infodir@ install_sh = @install_sh@ libdir = @libdir@ -libexecdir = @libexecdir@ +libexecdir = $(pkglibdir)/libexec/ localedir = @localedir@ localstatedir = @localstatedir@ -lt_ECHO = @lt_ECHO@ ltdl_LIBOBJS = @ltdl_LIBOBJS@ ltdl_LTLIBOBJS = @ltdl_LTLIBOBJS@ mandir = @mandir@ @@ -364,6 +404,7 @@ sbindir = @sbindir@ sharedstatedir = @sharedstatedir@ srcdir = @srcdir@ subdirs = @subdirs@ +svnversioncommand = @svnversioncommand@ sys_symbol_underscore = @sys_symbol_underscore@ sysconfdir = @sysconfdir@ target = @target@ @@ -392,7 +433,7 @@ libgnunetarm_la_LIBADD = \ libgnunetarm_la_LDFLAGS = \ $(GN_LIB_LDFLAGS) $(WINFLAGS) \ - -version-info 1:1:0 + -version-info 1:3:0 gnunet_arm_SOURCES = \ gnunet-arm.c @@ -422,7 +463,7 @@ mockup_service_LDADD = \ $(top_builddir)/src/util/libgnunetutil.la check_SCRIPTS = \ - test_gnunet_arm.sh + test_gnunet_arm.py @ENABLE_TEST_RUN_TRUE@TESTS = $(check_PROGRAMS) $(check_SCRIPTS) test_arm_api_SOURCES = \ @@ -439,17 +480,18 @@ test_exponential_backoff_LDADD = \ $(top_builddir)/src/arm/libgnunetarm.la \ $(top_builddir)/src/util/libgnunetutil.la -test_gnunet_service_manager_SOURCES = \ - test_gnunet_service_manager.c +test_gnunet_service_arm_SOURCES = \ + test_gnunet_service_arm.c -test_gnunet_service_manager_LDADD = \ +test_gnunet_service_arm_LDADD = \ $(top_builddir)/src/arm/libgnunetarm.la \ $(top_builddir)/src/util/libgnunetutil.la +do_subst = $(SED) -e 's,[@]PYTHON[@],$(PYTHON),g' EXTRA_DIST = \ test_arm_api_data.conf \ - do_start_process.c \ - $(check_SCRIPTS) + test_gnunet_arm.py.in \ + do_start_process.c all: all-am @@ -489,7 +531,6 @@ arm.conf: $(top_builddir)/config.status $(srcdir)/arm.conf.in cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ install-libLTLIBRARIES: $(lib_LTLIBRARIES) @$(NORMAL_INSTALL) - test -z "$(libdir)" || $(MKDIR_P) "$(DESTDIR)$(libdir)" @list='$(lib_LTLIBRARIES)'; test -n "$(libdir)" || list=; \ list2=; for p in $$list; do \ if test -f $$p; then \ @@ -497,6 +538,8 @@ install-libLTLIBRARIES: $(lib_LTLIBRARIES) else :; fi; \ done; \ test -z "$$list2" || { \ + echo " $(MKDIR_P) '$(DESTDIR)$(libdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libdir)" || exit 1; \ echo " $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 '$(DESTDIR)$(libdir)'"; \ $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 "$(DESTDIR)$(libdir)"; \ } @@ -518,12 +561,15 @@ clean-libLTLIBRARIES: echo "rm -f \"$${dir}/so_locations\""; \ rm -f "$${dir}/so_locations"; \ done -libgnunetarm.la: $(libgnunetarm_la_OBJECTS) $(libgnunetarm_la_DEPENDENCIES) +libgnunetarm.la: $(libgnunetarm_la_OBJECTS) $(libgnunetarm_la_DEPENDENCIES) $(EXTRA_libgnunetarm_la_DEPENDENCIES) $(AM_V_CCLD)$(libgnunetarm_la_LINK) -rpath $(libdir) $(libgnunetarm_la_OBJECTS) $(libgnunetarm_la_LIBADD) $(LIBS) install-binPROGRAMS: $(bin_PROGRAMS) @$(NORMAL_INSTALL) - test -z "$(bindir)" || $(MKDIR_P) "$(DESTDIR)$(bindir)" @list='$(bin_PROGRAMS)'; test -n "$(bindir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(bindir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(bindir)" || exit 1; \ + fi; \ for p in $$list; do echo "$$p $$p"; done | \ sed 's/$(EXEEXT)$$//' | \ while read p p1; do if test -f $$p || test -f $$p1; \ @@ -572,24 +618,70 @@ clean-checkPROGRAMS: list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ echo " rm -f" $$list; \ rm -f $$list -gnunet-arm$(EXEEXT): $(gnunet_arm_OBJECTS) $(gnunet_arm_DEPENDENCIES) +install-libexecPROGRAMS: $(libexec_PROGRAMS) + @$(NORMAL_INSTALL) + @list='$(libexec_PROGRAMS)'; test -n "$(libexecdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(libexecdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libexecdir)" || exit 1; \ + fi; \ + for p in $$list; do echo "$$p $$p"; done | \ + sed 's/$(EXEEXT)$$//' | \ + while read p p1; do if test -f $$p || test -f $$p1; \ + then echo "$$p"; echo "$$p"; else :; fi; \ + done | \ + sed -e 'p;s,.*/,,;n;h' -e 's|.*|.|' \ + -e 'p;x;s,.*/,,;s/$(EXEEXT)$$//;$(transform);s/$$/$(EXEEXT)/' | \ + sed 'N;N;N;s,\n, ,g' | \ + $(AWK) 'BEGIN { files["."] = ""; dirs["."] = 1 } \ + { d=$$3; if (dirs[d] != 1) { print "d", d; dirs[d] = 1 } \ + if ($$2 == $$4) files[d] = files[d] " " $$1; \ + else { print "f", $$3 "/" $$4, $$1; } } \ + END { for (d in files) print "f", d, files[d] }' | \ + while read type dir files; do \ + if test "$$dir" = .; then dir=; else dir=/$$dir; fi; \ + test -z "$$files" || { \ + echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files '$(DESTDIR)$(libexecdir)$$dir'"; \ + $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files "$(DESTDIR)$(libexecdir)$$dir" || exit $$?; \ + } \ + ; done + +uninstall-libexecPROGRAMS: + @$(NORMAL_UNINSTALL) + @list='$(libexec_PROGRAMS)'; test -n "$(libexecdir)" || list=; \ + files=`for p in $$list; do echo "$$p"; done | \ + sed -e 'h;s,^.*/,,;s/$(EXEEXT)$$//;$(transform)' \ + -e 's/$$/$(EXEEXT)/' `; \ + test -n "$$list" || exit 0; \ + echo " ( cd '$(DESTDIR)$(libexecdir)' && rm -f" $$files ")"; \ + cd "$(DESTDIR)$(libexecdir)" && rm -f $$files + +clean-libexecPROGRAMS: + @list='$(libexec_PROGRAMS)'; test -n "$$list" || exit 0; \ + echo " rm -f" $$list; \ + rm -f $$list || exit $$?; \ + test -n "$(EXEEXT)" || exit 0; \ + list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ + echo " rm -f" $$list; \ + rm -f $$list +gnunet-arm$(EXEEXT): $(gnunet_arm_OBJECTS) $(gnunet_arm_DEPENDENCIES) $(EXTRA_gnunet_arm_DEPENDENCIES) @rm -f gnunet-arm$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_arm_OBJECTS) $(gnunet_arm_LDADD) $(LIBS) -gnunet-service-arm$(EXEEXT): $(gnunet_service_arm_OBJECTS) $(gnunet_service_arm_DEPENDENCIES) +gnunet-service-arm$(EXEEXT): $(gnunet_service_arm_OBJECTS) $(gnunet_service_arm_DEPENDENCIES) $(EXTRA_gnunet_service_arm_DEPENDENCIES) @rm -f gnunet-service-arm$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_service_arm_OBJECTS) $(gnunet_service_arm_LDADD) $(LIBS) -mockup-service$(EXEEXT): $(mockup_service_OBJECTS) $(mockup_service_DEPENDENCIES) +mockup-service$(EXEEXT): $(mockup_service_OBJECTS) $(mockup_service_DEPENDENCIES) $(EXTRA_mockup_service_DEPENDENCIES) @rm -f mockup-service$(EXEEXT) $(AM_V_CCLD)$(LINK) $(mockup_service_OBJECTS) $(mockup_service_LDADD) $(LIBS) -test_arm_api$(EXEEXT): $(test_arm_api_OBJECTS) $(test_arm_api_DEPENDENCIES) +test_arm_api$(EXEEXT): $(test_arm_api_OBJECTS) $(test_arm_api_DEPENDENCIES) $(EXTRA_test_arm_api_DEPENDENCIES) @rm -f test_arm_api$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_arm_api_OBJECTS) $(test_arm_api_LDADD) $(LIBS) -test_exponential_backoff$(EXEEXT): $(test_exponential_backoff_OBJECTS) $(test_exponential_backoff_DEPENDENCIES) +test_exponential_backoff$(EXEEXT): $(test_exponential_backoff_OBJECTS) $(test_exponential_backoff_DEPENDENCIES) $(EXTRA_test_exponential_backoff_DEPENDENCIES) @rm -f test_exponential_backoff$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_exponential_backoff_OBJECTS) $(test_exponential_backoff_LDADD) $(LIBS) -test_gnunet_service_manager$(EXEEXT): $(test_gnunet_service_manager_OBJECTS) $(test_gnunet_service_manager_DEPENDENCIES) - @rm -f test_gnunet_service_manager$(EXEEXT) - $(AM_V_CCLD)$(LINK) $(test_gnunet_service_manager_OBJECTS) $(test_gnunet_service_manager_LDADD) $(LIBS) +test_gnunet_service_arm$(EXEEXT): $(test_gnunet_service_arm_OBJECTS) $(test_gnunet_service_arm_DEPENDENCIES) $(EXTRA_test_gnunet_service_arm_DEPENDENCIES) + @rm -f test_gnunet_service_arm$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_gnunet_service_arm_OBJECTS) $(test_gnunet_service_arm_LDADD) $(LIBS) mostlyclean-compile: -rm -f *.$(OBJEXT) @@ -603,31 +695,28 @@ distclean-compile: @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/mockup-service.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_arm_api.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_exponential_backoff.Po@am__quote@ -@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_gnunet_service_manager.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_gnunet_service_arm.Po@am__quote@ .c.o: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c $< .c.obj: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'` @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c `$(CYGPATH_W) '$<'` +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c `$(CYGPATH_W) '$<'` .c.lo: @am__fastdepCC_TRUE@ $(AM_V_CC)$(LTCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LTCOMPILE) -c -o $@ $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LTCOMPILE) -c -o $@ $< mostlyclean-libtool: -rm -f *.lo @@ -636,8 +725,11 @@ clean-libtool: -rm -rf .libs _libs install-pkgcfgDATA: $(pkgcfg_DATA) @$(NORMAL_INSTALL) - test -z "$(pkgcfgdir)" || $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" @list='$(pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(pkgcfgdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" || exit 1; \ + fi; \ for p in $$list; do \ if test -f "$$p"; then d=; else d="$(srcdir)/"; fi; \ echo "$$d$$p"; \ @@ -651,9 +743,7 @@ uninstall-pkgcfgDATA: @$(NORMAL_UNINSTALL) @list='$(pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ files=`for p in $$list; do echo $$p; done | sed -e 's|^.*/||'`; \ - test -n "$$files" || exit 0; \ - echo " ( cd '$(DESTDIR)$(pkgcfgdir)' && rm -f" $$files ")"; \ - cd "$(DESTDIR)$(pkgcfgdir)" && rm -f $$files + dir='$(DESTDIR)$(pkgcfgdir)'; $(am__uninstall_files_from_dir) ID: $(HEADERS) $(SOURCES) $(LISP) $(TAGS_FILES) list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ @@ -788,14 +878,15 @@ check-TESTS: $(TESTS) fi; \ dashes=`echo "$$dashes" | sed s/./=/g`; \ if test "$$failed" -eq 0; then \ - echo "$$grn$$dashes"; \ + col="$$grn"; \ else \ - echo "$$red$$dashes"; \ + col="$$red"; \ fi; \ - echo "$$banner"; \ - test -z "$$skipped" || echo "$$skipped"; \ - test -z "$$report" || echo "$$report"; \ - echo "$$dashes$$std"; \ + echo "$${col}$$dashes$${std}"; \ + echo "$${col}$$banner$${std}"; \ + test -z "$$skipped" || echo "$${col}$$skipped$${std}"; \ + test -z "$$report" || echo "$${col}$$report$${std}"; \ + echo "$${col}$$dashes$${std}"; \ test "$$failed" -eq 0; \ else :; fi @@ -837,7 +928,7 @@ all-am: Makefile $(LTLIBRARIES) $(PROGRAMS) $(DATA) install-binPROGRAMS: install-libLTLIBRARIES installdirs: - for dir in "$(DESTDIR)$(libdir)" "$(DESTDIR)$(bindir)" "$(DESTDIR)$(pkgcfgdir)"; do \ + for dir in "$(DESTDIR)$(libdir)" "$(DESTDIR)$(bindir)" "$(DESTDIR)$(libexecdir)" "$(DESTDIR)$(pkgcfgdir)"; do \ test -z "$$dir" || $(MKDIR_P) "$$dir"; \ done install: install-am @@ -850,10 +941,15 @@ install-am: all-am installcheck: installcheck-am install-strip: - $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ - install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ - `test -z '$(STRIP)' || \ - echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi mostlyclean-generic: clean-generic: @@ -868,7 +964,8 @@ maintainer-clean-generic: clean: clean-am clean-am: clean-binPROGRAMS clean-checkPROGRAMS clean-generic \ - clean-libLTLIBRARIES clean-libtool mostlyclean-am + clean-libLTLIBRARIES clean-libexecPROGRAMS clean-libtool \ + mostlyclean-am distclean: distclean-am -rm -rf ./$(DEPDIR) @@ -894,7 +991,8 @@ install-dvi: install-dvi-am install-dvi-am: -install-exec-am: install-binPROGRAMS install-libLTLIBRARIES +install-exec-am: install-binPROGRAMS install-libLTLIBRARIES \ + install-libexecPROGRAMS install-html: install-html-am @@ -935,28 +1033,37 @@ ps: ps-am ps-am: uninstall-am: uninstall-binPROGRAMS uninstall-libLTLIBRARIES \ - uninstall-pkgcfgDATA + uninstall-libexecPROGRAMS uninstall-pkgcfgDATA .MAKE: check-am install-am install-strip .PHONY: CTAGS GTAGS all all-am check check-TESTS check-am clean \ clean-binPROGRAMS clean-checkPROGRAMS clean-generic \ - clean-libLTLIBRARIES clean-libtool ctags distclean \ - distclean-compile distclean-generic distclean-libtool \ - distclean-tags distdir dvi dvi-am html html-am info info-am \ - install install-am install-binPROGRAMS install-data \ - install-data-am install-dvi install-dvi-am install-exec \ - install-exec-am install-html install-html-am install-info \ - install-info-am install-libLTLIBRARIES install-man install-pdf \ - install-pdf-am install-pkgcfgDATA install-ps install-ps-am \ - install-strip installcheck installcheck-am installdirs \ - maintainer-clean maintainer-clean-generic mostlyclean \ - mostlyclean-compile mostlyclean-generic mostlyclean-libtool \ - pdf pdf-am ps ps-am tags uninstall uninstall-am \ - uninstall-binPROGRAMS uninstall-libLTLIBRARIES \ + clean-libLTLIBRARIES clean-libexecPROGRAMS clean-libtool ctags \ + distclean distclean-compile distclean-generic \ + distclean-libtool distclean-tags distdir dvi dvi-am html \ + html-am info info-am install install-am install-binPROGRAMS \ + install-data install-data-am install-dvi install-dvi-am \ + install-exec install-exec-am install-html install-html-am \ + install-info install-info-am install-libLTLIBRARIES \ + install-libexecPROGRAMS install-man install-pdf install-pdf-am \ + install-pkgcfgDATA install-ps install-ps-am install-strip \ + installcheck installcheck-am installdirs maintainer-clean \ + maintainer-clean-generic mostlyclean mostlyclean-compile \ + mostlyclean-generic mostlyclean-libtool pdf pdf-am ps ps-am \ + tags uninstall uninstall-am uninstall-binPROGRAMS \ + uninstall-libLTLIBRARIES uninstall-libexecPROGRAMS \ uninstall-pkgcfgDATA +%.py: %.py.in Makefile + $(do_subst) < $(srcdir)/$< > $@ + chmod +x $@ + +test_gnunet_arm.py: test_gnunet_arm.py.in Makefile + $(do_subst) < $(srcdir)/test_gnunet_arm.py.in > test_gnunet_arm.py + chmod +x test_gnunet_arm.py + # Tell versions [3.59,3.63) of GNU make to not export all variables. # Otherwise a system limit (for SysV at least) may be exceeded. .NOEXPORT: diff --git a/src/arm/arm.conf.in b/src/arm/arm.conf.in index e72e420..e7620b8 100644 --- a/src/arm/arm.conf.in +++ b/src/arm/arm.conf.in @@ -3,7 +3,6 @@ @UNIXONLY@ PORT = 2087 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-arm ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -11,7 +10,13 @@ DEFAULTSERVICES = topology hostlist dht nse mesh fs UNIXPATH = /tmp/gnunet-service-arm.sock UNIX_MATCH_UID = YES UNIX_MATCH_GID = YES -# GLOBAL_POSTFIX = -l $SERVICEHOME/{}-logs + +# In the "-l" option, format characters from 'strftime' are allowed; +# In the GLOBAL_POSTFIX, "{}" stands for the name of the respective +# service. Thus the following option would introduce per-service +# logging with a new log file each day. Note that only the last 3 +# log files are preserved. +# GLOBAL_POSTFIX = -l $SERVICEHOME/{}-%Y-%m-%d.log # GLOBAL_PREFIX = # USERNAME = # MAXBUF = diff --git a/src/arm/arm_api.c b/src/arm/arm_api.c index 1b78d33..fd49a18 100644 --- a/src/arm/arm_api.c +++ b/src/arm/arm_api.c @@ -25,11 +25,8 @@ */ #include "platform.h" #include "gnunet_arm_service.h" -#include "gnunet_client_lib.h" -#include "gnunet_getopt_lib.h" -#include "gnunet_os_lib.h" +#include "gnunet_util_lib.h" #include "gnunet_protocols.h" -#include "gnunet_server_lib.h" #include "arm.h" #define LOG(kind,...) GNUNET_log_from (kind, "arm-api",__VA_ARGS__) @@ -295,6 +292,11 @@ struct RequestContext */ uint16_t type; + /** + * Flags for passing std descriptors to ARM (when starting ARM). + */ + enum GNUNET_OS_InheritStdioFlags std_inheritance; + }; #include "do_start_process.c" @@ -314,6 +316,7 @@ arm_service_report (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { struct RequestContext *pos = cls; struct GNUNET_OS_Process *proc; + char *cbinary; char *binary; char *config; char *loprefix; @@ -342,12 +345,10 @@ arm_service_report (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) lopostfix = GNUNET_strdup (""); if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_string (pos->h->cfg, "arm", "BINARY", - &binary)) + &cbinary)) { - LOG (GNUNET_ERROR_TYPE_WARNING, - _ - ("Configuration failes to specify option `%s' in section `%s'!\n"), - "BINARY", "arm"); + GNUNET_log_config_missing (GNUNET_ERROR_TYPE_WARNING, + "arm", "BINARY"); if (pos->callback != NULL) pos->callback (pos->cls, GNUNET_ARM_PROCESS_UNKNOWN); GNUNET_free (pos); @@ -358,18 +359,9 @@ arm_service_report (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_filename (pos->h->cfg, "arm", "CONFIG", &config)) - { - LOG (GNUNET_ERROR_TYPE_WARNING, - _("Configuration fails to specify option `%s' in section `%s'!\n"), - "CONFIG", "arm"); - if (pos->callback != NULL) - pos->callback (pos->cls, GNUNET_ARM_PROCESS_UNKNOWN); - GNUNET_free (binary); - GNUNET_free (pos); - GNUNET_free (loprefix); - GNUNET_free (lopostfix); - return; - } + config = NULL; + binary = GNUNET_OS_get_libexec_binary_path (cbinary); + GNUNET_free (cbinary); if ((GNUNET_YES == GNUNET_CONFIGURATION_have_value (pos->h->cfg, "TESTING", "WEAKRANDOM")) && (GNUNET_YES == @@ -381,28 +373,39 @@ arm_service_report (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { /* Means we are ONLY running locally */ /* we're clearly running a test, don't daemonize */ - proc = do_start_process (GNUNET_NO, - NULL, loprefix, binary, "-c", config, - /* no daemonization! */ - lopostfix, NULL); + if (NULL == config) + proc = do_start_process (GNUNET_NO, pos->std_inheritance, + NULL, loprefix, binary, + /* no daemonization! */ + lopostfix, NULL); + else + proc = do_start_process (GNUNET_NO, pos->std_inheritance, + NULL, loprefix, binary, "-c", config, + /* no daemonization! */ + lopostfix, NULL); } else { - proc = do_start_process (GNUNET_NO, - NULL, loprefix, binary, "-c", config, - "-d", lopostfix, NULL); + if (NULL == config) + proc = do_start_process (GNUNET_NO, pos->std_inheritance, + NULL, loprefix, binary, + "-d", lopostfix, NULL); + else + proc = do_start_process (GNUNET_NO, pos->std_inheritance, + NULL, loprefix, binary, "-c", config, + "-d", lopostfix, NULL); } GNUNET_free (binary); - GNUNET_free (config); + GNUNET_free_non_null (config); GNUNET_free (loprefix); GNUNET_free (lopostfix); - if (proc == NULL) - { - if (pos->callback != NULL) - pos->callback (pos->cls, GNUNET_ARM_PROCESS_FAILURE); - GNUNET_free (pos); - return; - } + if (NULL == proc) + { + if (pos->callback != NULL) + pos->callback (pos->cls, GNUNET_ARM_PROCESS_FAILURE); + GNUNET_free (pos); + return; + } if (pos->callback != NULL) pos->callback (pos->cls, GNUNET_ARM_PROCESS_STARTING); GNUNET_free (proc); @@ -427,11 +430,7 @@ handle_response (void *cls, const struct GNUNET_MessageHeader *msg) if ((msg == NULL) || (ntohs (msg->size) != sizeof (struct GNUNET_ARM_ResultMessage))) { - LOG (GNUNET_ERROR_TYPE_WARNING, - _ - ("Error receiving response to `%s' request from ARM for service `%s'\n"), - (sc->type == GNUNET_MESSAGE_TYPE_ARM_START) ? "START" : "STOP", - (const char *) &sc[1]); + GNUNET_break (0); GNUNET_CLIENT_disconnect (sc->h->client); sc->h->client = GNUNET_CLIENT_connect ("arm", sc->h->cfg); GNUNET_assert (NULL != sc->h->client); @@ -482,8 +481,8 @@ change_service (struct GNUNET_ARM_Handle *h, const char *service_name, LOG (GNUNET_ERROR_TYPE_DEBUG, (type == GNUNET_MESSAGE_TYPE_ARM_START) ? - _("Requesting start of service `%s'.\n") : - _("Requesting termination of service `%s'.\n"), service_name); + "Requesting start of service `%s'.\n" : + "Requesting termination of service `%s'.\n", service_name); sctx = GNUNET_malloc (sizeof (struct RequestContext) + slen); sctx->h = h; sctx->callback = cb; @@ -501,12 +500,7 @@ change_service (struct GNUNET_ARM_Handle *h, const char *service_name, (sctx->timeout), GNUNET_YES, &handle_response, sctx)) { - LOG (GNUNET_ERROR_TYPE_WARNING, - (type == - GNUNET_MESSAGE_TYPE_ARM_START) - ? _("Error while trying to transmit request to start `%s' to ARM\n") - : _("Error while trying to transmit request to stop `%s' to ARM\n"), - (const char *) &service_name); + GNUNET_break (0); if (cb != NULL) cb (cb_cls, GNUNET_SYSERR); GNUNET_free (sctx); @@ -522,6 +516,7 @@ change_service (struct GNUNET_ARM_Handle *h, const char *service_name, * * @param h handle to ARM * @param service_name name of the service + * @param std_inheritance inheritance of std streams * @param timeout how long to wait before failing for good * @param cb callback to invoke when service is ready * @param cb_cls closure for callback @@ -529,6 +524,7 @@ change_service (struct GNUNET_ARM_Handle *h, const char *service_name, void GNUNET_ARM_start_service (struct GNUNET_ARM_Handle *h, const char *service_name, + enum GNUNET_OS_InheritStdioFlags std_inheritance, struct GNUNET_TIME_Relative timeout, GNUNET_ARM_Callback cb, void *cb_cls) { @@ -537,8 +533,8 @@ GNUNET_ARM_start_service (struct GNUNET_ARM_Handle *h, size_t slen; LOG (GNUNET_ERROR_TYPE_DEBUG, - _("Asked to start service `%s' within %llu ms\n"), service_name, - (unsigned long long) timeout.rel_value); + "Asked to start service `%s' within %s\n", service_name, + GNUNET_STRINGS_relative_time_to_string (timeout, GNUNET_NO)); if (0 == strcasecmp ("arm", service_name)) { slen = strlen ("arm") + 1; @@ -547,12 +543,13 @@ GNUNET_ARM_start_service (struct GNUNET_ARM_Handle *h, sctx->callback = cb; sctx->cls = cb_cls; sctx->timeout = GNUNET_TIME_relative_to_absolute (timeout); + sctx->std_inheritance = std_inheritance; memcpy (&sctx[1], service_name, slen); GNUNET_CLIENT_service_test ("arm", h->cfg, timeout, &arm_service_report, sctx); return; } - if (h->client == NULL) + if (NULL == h->client) { client = GNUNET_CLIENT_connect ("arm", h->cfg); if (client == NULL) @@ -586,7 +583,6 @@ arm_shutdown_callback (void *cls, enum GNUNET_ARM_ProcessStatus reason) if (arm_shutdown_ctx->cb != NULL) arm_shutdown_ctx->cb (arm_shutdown_ctx->cb_cls, reason); - GNUNET_free (arm_shutdown_ctx); } @@ -609,8 +605,10 @@ GNUNET_ARM_stop_service (struct GNUNET_ARM_Handle *h, struct ARM_ShutdownContext *arm_shutdown_ctx; struct GNUNET_CLIENT_Connection *client; - LOG (GNUNET_ERROR_TYPE_INFO, _("Stopping service `%s' within %llu ms\n"), - service_name, (unsigned long long) timeout.rel_value); + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Stopping service `%s' within %s\n", + service_name, + GNUNET_STRINGS_relative_time_to_string (timeout, GNUNET_NO)); if (h->client == NULL) { client = GNUNET_CLIENT_connect ("arm", h->cfg); @@ -682,8 +680,7 @@ handle_list_response (void *cls, const struct GNUNET_MessageHeader *msg) if (NULL == msg) { - LOG (GNUNET_ERROR_TYPE_WARNING, - "Error receiving response to LIST request from ARM\n"); + GNUNET_break (0); GNUNET_CLIENT_disconnect (sc->h->client); sc->h->client = GNUNET_CLIENT_connect ("arm", sc->h->cfg); GNUNET_assert (NULL != sc->h->client); @@ -758,13 +755,10 @@ GNUNET_ARM_list_running_services (struct GNUNET_ARM_Handle *h, client = GNUNET_CLIENT_connect ("arm", h->cfg); if (client == NULL) { - LOG (GNUNET_ERROR_TYPE_DEBUG, - "arm_api, GNUNET_CLIENT_connect returned NULL\n"); + GNUNET_break (0); cb (cb_cls, GNUNET_ARM_PROCESS_COMMUNICATION_ERROR, 0, NULL); return; } - LOG (GNUNET_ERROR_TYPE_DEBUG, - "arm_api, GNUNET_CLIENT_connect returned non-NULL\n"); h->client = client; } @@ -777,8 +771,8 @@ GNUNET_ARM_list_running_services (struct GNUNET_ARM_Handle *h, msg.type = htons (GNUNET_MESSAGE_TYPE_ARM_LIST); LOG (GNUNET_ERROR_TYPE_DEBUG, - "Requesting LIST from ARM service with timeout: %llu ms\n", - (unsigned long long)timeout.rel_value); + "Requesting LIST from ARM service with timeout: %s\n", + GNUNET_STRINGS_relative_time_to_string (timeout, GNUNET_YES)); if (GNUNET_OK != GNUNET_CLIENT_transmit_and_get_response (sctx->h->client, @@ -789,8 +783,7 @@ GNUNET_ARM_list_running_services (struct GNUNET_ARM_Handle *h, &handle_list_response, sctx)) { - LOG (GNUNET_ERROR_TYPE_WARNING, - "Error while trying to transmit request to list services to ARM\n"); + GNUNET_break (0); if (cb != NULL) cb (cb_cls, GNUNET_SYSERR, 0, NULL); GNUNET_free (sctx); diff --git a/src/arm/do_start_process.c b/src/arm/do_start_process.c index 4554f57..b4bb10c 100644 --- a/src/arm/do_start_process.c +++ b/src/arm/do_start_process.c @@ -1,3 +1,23 @@ +/* + This file is part of GNUnet. + (C) 2011, 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + /** * Actually start a process. All of the arguments given to this * function are strings that are used for the "argv" array. However, @@ -8,13 +28,14 @@ * with spaces to the new process. * * @param pipe_control should a pipe be used to send signals to the child? + * @param std_inheritance a set of GNUNET_OS_INHERIT_STD_* flags * @param lsocks array of listen sockets to dup starting at fd3 (systemd-style), or NULL * @param first_arg first argument for argv (may be an empty string) * @param ... more arguments, NULL terminated * @return handle of the started process, NULL on error */ static struct GNUNET_OS_Process * -do_start_process (int pipe_control, +do_start_process (int pipe_control, unsigned int std_inheritance, const SOCKTYPE * lsocks, const char *first_arg, ...) { va_list ap; @@ -26,6 +47,7 @@ do_start_process (int pipe_control, char *cp; const char *last; struct GNUNET_OS_Process *proc; + char *binary_path; argv_size = 1; va_start (ap, first_arg); @@ -97,9 +119,13 @@ do_start_process (int pipe_control, /* *INDENT-ON* */ va_end (ap); argv[argv_size] = NULL; - proc = GNUNET_OS_start_process_v (pipe_control, lsocks, argv[0], argv); + binary_path = argv[0]; + proc = GNUNET_OS_start_process_v (pipe_control, std_inheritance, lsocks, + binary_path, argv); while (argv_size > 0) GNUNET_free (argv[--argv_size]); GNUNET_free (argv); return proc; } + +/* end of do_start_process.c */ diff --git a/src/arm/gnunet-arm.c b/src/arm/gnunet-arm.c index 58aa709..8a98ba0 100644 --- a/src/arm/gnunet-arm.c +++ b/src/arm/gnunet-arm.c @@ -1,6 +1,6 @@ /* This file is part of GNUnet. - (C) 2009 Christian Grothoff (and other contributing authors) + (C) 2009, 2012, 2013 Christian Grothoff (and other contributing authors) GNUnet is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published @@ -25,11 +25,8 @@ */ #include "platform.h" #include "gnunet_arm_service.h" -#include "gnunet_client_lib.h" #include "gnunet_constants.h" -#include "gnunet_getopt_lib.h" -#include "gnunet_program_lib.h" -#include "gnunet_time_lib.h" +#include "gnunet_util_lib.h" /** * Timeout for stopping services. Long to give some services a real chance. @@ -116,7 +113,7 @@ static struct GNUNET_ARM_Handle *h; /** * Our configuration. */ -static const struct GNUNET_CONFIGURATION_Handle *cfg; +static struct GNUNET_CONFIGURATION_Handle *cfg; /** * Processing stage that we are in. Simple counter. @@ -128,6 +125,16 @@ static unsigned int phase; */ static struct GNUNET_TIME_Relative timeout; +/** + * Do we want to give our stdout to gnunet-service-arm? + */ +static unsigned int no_stdout; + +/** + * Do we want to give our stderr to gnunet-service-arm? + */ +static unsigned int no_stderr; + /** * Main continuation-passing-style loop. Runs the various @@ -199,10 +206,10 @@ confirm_cb (void *cls, FPRINTF (stderr, "%s", _("Unknown response code from ARM.\n")); break; } - GNUNET_SCHEDULER_add_continuation (&cps_loop, NULL, - GNUNET_SCHEDULER_REASON_PREREQ_DONE); + GNUNET_SCHEDULER_add_now (&cps_loop, NULL); } + /** * Callback invoked with the list of running services. * Reports to the user and then runs the next phase in the FSM. @@ -227,40 +234,6 @@ list_cb (void *cls, int result, unsigned int count, const char *const*list) FPRINTF (stdout, "%s\n", list[i]); } -/** - * Main function that will be run by the scheduler. - * - * @param cls closure - * @param args remaining command-line arguments - * @param cfgfile name of the configuration file used (for saving, can be NULL!) - * @param c configuration - */ -static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *c) -{ - cfg = c; - config_file = cfgfile; - if (GNUNET_CONFIGURATION_get_value_string - (cfg, "PATHS", "SERVICEHOME", &dir) != GNUNET_OK) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - _ - ("Fatal configuration error: `%s' option in section `%s' missing.\n"), - "SERVICEHOME", "PATHS"); - return; - } - h = GNUNET_ARM_connect (cfg, NULL); - if (h == NULL) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - _("Fatal error initializing ARM API.\n")); - ret = 1; - return; - } - GNUNET_SCHEDULER_add_continuation (&cps_loop, NULL, - GNUNET_SCHEDULER_REASON_PREREQ_DONE); -} /** * Attempts to delete configuration file and SERVICEHOME @@ -288,6 +261,76 @@ delete_files () } } + +/** + * Main continuation-passing-style loop. Runs the various + * jobs that we've been asked to do in order. + * + * @param cls closure, unused + * @param tc context, unused + */ +static void +shutdown_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + GNUNET_ARM_disconnect (h); + h = NULL; + if ((end == GNUNET_YES) && (delete == GNUNET_YES)) + delete_files (); + GNUNET_CONFIGURATION_destroy (cfg); + cfg = NULL; +} + + +/** + * Main function that will be run by the scheduler. + * + * @param cls closure + * @param args remaining command-line arguments + * @param cfgfile name of the configuration file used (for saving, can be NULL!) + * @param c configuration + */ +static void +run (void *cls, char *const *args, const char *cfgfile, + const struct GNUNET_CONFIGURATION_Handle *c) +{ + char *armconfig; + + cfg = GNUNET_CONFIGURATION_dup (c); + config_file = cfgfile; + if (GNUNET_CONFIGURATION_get_value_string + (cfg, "PATHS", "SERVICEHOME", &dir) != GNUNET_OK) + { + GNUNET_log_config_missing (GNUNET_ERROR_TYPE_ERROR, + "PATHS", "SERVICEHOME"); + return; + } + if (NULL != cfgfile) + { + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_filename (cfg, "arm", "CONFIG", + &armconfig)) + { + GNUNET_CONFIGURATION_set_value_string (cfg, "arm", "CONFIG", + cfgfile); + } + else + GNUNET_free (armconfig); + } + if (NULL == (h = GNUNET_ARM_connect (cfg, NULL))) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Fatal error initializing ARM API.\n")); + ret = 1; + GNUNET_CONFIGURATION_destroy (cfg); + cfg = NULL; + return; + } + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, + &shutdown_task, NULL); + GNUNET_SCHEDULER_add_now (&cps_loop, NULL); +} + + /** * Main continuation-passing-style loop. Runs the various * jobs that we've been asked to do in order. @@ -298,96 +341,101 @@ delete_files () static void cps_loop (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { + if (NULL == h) + return; + if (0 != (tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN)) + return; while (1) + { + switch (phase++) { - switch (phase++) + case 0: + if (NULL != term) + { + GNUNET_ARM_stop_service (h, term, + (0 == + timeout.rel_value) ? STOP_TIMEOUT : + timeout, &confirm_cb, term); + return; + } + break; + case 1: + if ((end) || (restart)) + { + GNUNET_ARM_stop_service (h, "arm", + (0 == + timeout.rel_value) ? STOP_TIMEOUT_ARM + : timeout, &confirm_cb, "arm"); + return; + } + break; + case 2: + if (start) + { + GNUNET_ARM_start_service (h, "arm", + (no_stdout ? 0 : GNUNET_OS_INHERIT_STD_OUT) | + (no_stderr ? 0 : GNUNET_OS_INHERIT_STD_ERR), + (0 == + timeout.rel_value) ? START_TIMEOUT : + timeout, &confirm_cb, "arm"); + return; + } + break; + case 3: + if (NULL != init) + { + GNUNET_ARM_start_service (h, init, + (no_stdout ? 0 : GNUNET_OS_INHERIT_STD_OUT) | + (no_stderr ? 0 : GNUNET_OS_INHERIT_STD_ERR), + (0 == + timeout.rel_value) ? START_TIMEOUT : + timeout, &confirm_cb, init); + return; + } + break; + case 4: + if (restart) + { + GNUNET_ARM_disconnect (h); + phase = 0; + end = 0; + start = 1; + restart = 0; + if (NULL == (h = GNUNET_ARM_connect (cfg, NULL))) { - case 0: - if (term != NULL) - { - GNUNET_ARM_stop_service (h, term, - (0 == - timeout.rel_value) ? STOP_TIMEOUT : - timeout, &confirm_cb, term); - return; - } - break; - case 1: - if ((end) || (restart)) - { - GNUNET_ARM_stop_service (h, "arm", - (0 == - timeout.rel_value) ? STOP_TIMEOUT_ARM - : timeout, &confirm_cb, "arm"); - return; - } - break; - case 2: - if (start) - { - GNUNET_ARM_start_service (h, "arm", - (0 == - timeout.rel_value) ? START_TIMEOUT : - timeout, &confirm_cb, "arm"); - return; - } - break; - case 3: - if (init != NULL) - { - GNUNET_ARM_start_service (h, init, - (0 == - timeout.rel_value) ? START_TIMEOUT : - timeout, &confirm_cb, init); - return; - } - break; - case 4: - if (restart) - { - GNUNET_ARM_disconnect (h); - phase = 0; - end = 0; - start = 1; - restart = 0; - h = GNUNET_ARM_connect (cfg, NULL); - if (NULL == h) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - _("Fatal error initializing ARM API.\n")); - ret = 1; - return; - } - GNUNET_SCHEDULER_add_now (&cps_loop, NULL); - return; - } - break; - case 5: - if (list) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Going to list all running services controlled by ARM.\n"); - - if (NULL == h) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - _("Fatal error initializing ARM API.\n")); - return; - } - - GNUNET_ARM_list_running_services (h, - (0 == - timeout.rel_value) ? LIST_TIMEOUT : - timeout, &list_cb, NULL); - return; - } - /* Fall through */ - default: /* last phase */ - GNUNET_ARM_disconnect (h); - if ((end == GNUNET_YES) && (delete == GNUNET_YES)) - delete_files (); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Fatal error initializing ARM API.\n")); + ret = 1; return; } + GNUNET_SCHEDULER_add_now (&cps_loop, NULL); + return; + } + break; + case 5: + if (list) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Going to list all running services controlled by ARM.\n"); + + if (NULL == h) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Fatal error initializing ARM API.\n")); + return; + } + GNUNET_ARM_list_running_services (h, + (0 == + timeout.rel_value) ? LIST_TIMEOUT : + timeout, &list_cb, NULL); + return; + } + /* Fall through */ + default: /* last phase */ + GNUNET_SCHEDULER_shutdown (); + return; } + } } @@ -401,8 +449,6 @@ cps_loop (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) int main (int argc, char *const *argv) { - static unsigned long long temp_timeout_ms; - static const struct GNUNET_GETOPT_CommandLineOption options[] = { {'e', "end", NULL, gettext_noop ("stop all GNUnet services"), GNUNET_NO, &GNUNET_GETOPT_set_one, &end}, @@ -420,16 +466,20 @@ main (int argc, char *const *argv) GNUNET_NO, &GNUNET_GETOPT_set_one, &delete}, {'q', "quiet", NULL, gettext_noop ("don't print status messages"), GNUNET_NO, &GNUNET_GETOPT_set_one, &quiet}, - {'T', "timeout", NULL, - gettext_noop ("timeout for completing current operation"), - GNUNET_YES, &GNUNET_GETOPT_set_ulong, &temp_timeout_ms}, - {'I', "info", NULL, gettext_noop ("List currently running services"), + {'T', "timeout", "MSECS", + gettext_noop ("timeout in MSECS milliseconds for completing current operation"), + GNUNET_YES, &GNUNET_GETOPT_set_relative_time, &timeout}, + {'I', "info", NULL, gettext_noop ("list currently running services"), GNUNET_NO, &GNUNET_GETOPT_set_one, &list}, + {'O', "no-stdout", NULL, gettext_noop ("don't let gnunet-service-arm inherit standard output"), + GNUNET_NO, &GNUNET_GETOPT_set_one, &no_stdout}, + {'E', "no-stderr", NULL, gettext_noop ("don't let gnunet-service-arm inherit standard error"), + GNUNET_NO, &GNUNET_GETOPT_set_one, &no_stderr}, GNUNET_GETOPT_OPTION_END }; - if (temp_timeout_ms > 0) - timeout.rel_value = temp_timeout_ms; + if (GNUNET_OK != GNUNET_STRINGS_get_utf8_args (argc, argv, &argc, &argv)) + return 2; if (GNUNET_OK == GNUNET_PROGRAM_run (argc, argv, "gnunet-arm", @@ -437,9 +487,10 @@ main (int argc, char *const *argv) ("Control services and the Automated Restart Manager (ARM)"), options, &run, NULL)) { + GNUNET_free ((void *) argv); return ret; } - + GNUNET_free ((void*) argv); return 1; } diff --git a/src/arm/gnunet-service-arm.c b/src/arm/gnunet-service-arm.c index ce91043..f16fd52 100644 --- a/src/arm/gnunet-service-arm.c +++ b/src/arm/gnunet-service-arm.c @@ -29,12 +29,6 @@ #include "gnunet_protocols.h" #include "arm.h" -/** - * Threshold after which exponential backoff shouldn't increase (in ms); 30m - */ -#define EXPONENTIAL_BACKOFF_THRESHOLD GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MINUTES, 30) - - /** * List of our services. */ @@ -246,6 +240,7 @@ start_process (struct ServiceList *sl) struct ServiceListeningInfo *sli; SOCKTYPE *lsocks; unsigned int ls; + char *binary; /* calculate listen socket list */ lsocks = NULL; @@ -317,17 +312,35 @@ start_process (struct ServiceList *sl) GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Starting service `%s' using binary `%s' and configuration `%s'\n", sl->name, sl->binary, sl->config); + binary = GNUNET_OS_get_libexec_binary_path (sl->binary); GNUNET_assert (NULL == sl->proc); if (GNUNET_YES == use_debug) - sl->proc = - do_start_process (sl->pipe_control, - lsocks, loprefix, sl->binary, "-c", sl->config, "-L", - "DEBUG", options, NULL); + { + if (NULL == sl->config) + sl->proc = + do_start_process (sl->pipe_control, GNUNET_OS_INHERIT_STD_OUT_AND_ERR, + lsocks, loprefix, binary, "-L", + "DEBUG", options, NULL); + else + sl->proc = + do_start_process (sl->pipe_control, GNUNET_OS_INHERIT_STD_OUT_AND_ERR, + lsocks, loprefix, binary, "-c", sl->config, "-L", + "DEBUG", options, NULL); + } else - sl->proc = - do_start_process (sl->pipe_control, - lsocks, loprefix, sl->binary, "-c", sl->config, - options, NULL); + { + if (NULL == sl->config) + sl->proc = + do_start_process (sl->pipe_control, GNUNET_OS_INHERIT_STD_OUT_AND_ERR, + lsocks, loprefix, binary, + options, NULL); + else + sl->proc = + do_start_process (sl->pipe_control, GNUNET_OS_INHERIT_STD_OUT_AND_ERR, + lsocks, loprefix, binary, "-c", sl->config, + options, NULL); + } + GNUNET_free (binary); if (sl->proc == NULL) GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("Failed to start service `%s'\n"), sl->name); @@ -476,6 +489,7 @@ accept_connection (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) struct ServiceList *sl = sli->sl; sli->accept_task = GNUNET_SCHEDULER_NO_TASK; + GNUNET_assert (GNUNET_NO == in_shutdown); if (0 != (GNUNET_SCHEDULER_REASON_SHUTDOWN & tc->reason)) return; start_process (sl); @@ -903,8 +917,9 @@ delayed_restart_task (void *cls, } if (lowestRestartDelay.rel_value != GNUNET_TIME_UNIT_FOREVER_REL.rel_value) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Will restart process in %llums\n", - (unsigned long long) lowestRestartDelay.rel_value); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Will restart process in %s\n", + GNUNET_STRINGS_relative_time_to_string (lowestRestartDelay, GNUNET_YES)); child_restart_task = GNUNET_SCHEDULER_add_delayed_with_priority (lowestRestartDelay, GNUNET_SCHEDULER_PRIORITY_IDLE, @@ -983,9 +998,9 @@ maint_child_death (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) if (0 != pos->killed_at.abs_value) { GNUNET_log (GNUNET_ERROR_TYPE_INFO, - _("Service `%s' took %llu ms to terminate\n"), + _("Service `%s' took %s to terminate\n"), pos->name, - GNUNET_TIME_absolute_get_duration (pos->killed_at).rel_value); + GNUNET_STRINGS_relative_time_to_string (GNUNET_TIME_absolute_get_duration (pos->killed_at), GNUNET_YES)); } GNUNET_OS_process_destroy (pos->proc); pos->proc = NULL; @@ -1022,10 +1037,7 @@ maint_child_death (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) pos->name, statstr, statcode, pos->backoff.rel_value); /* schedule restart */ pos->restart_at = GNUNET_TIME_relative_to_absolute (pos->backoff); - pos->backoff = - GNUNET_TIME_relative_min (EXPONENTIAL_BACKOFF_THRESHOLD, - GNUNET_TIME_relative_multiply - (pos->backoff, 2)); + pos->backoff = GNUNET_TIME_STD_BACKOFF (pos->backoff); } if (GNUNET_SCHEDULER_NO_TASK != child_restart_task) GNUNET_SCHEDULER_cancel (child_restart_task); @@ -1117,20 +1129,23 @@ setup_service (void *cls, const char *section) return; } config = NULL; - if ((GNUNET_OK != - GNUNET_CONFIGURATION_get_value_filename (cfg, section, "CONFIG", - &config)) || + if (( (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_filename (cfg, section, "CONFIG", + &config)) && + (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_filename (cfg, "PATHS", "DEFAULTCONFIG", + &config)) ) || (0 != STAT (config, &sbuf))) + { + if (NULL != config) { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - _ - ("Configuration file `%s' for service `%s' not valid: %s\n"), - config, section, - (config == NULL) ? _("option missing") : STRERROR (errno)); - GNUNET_free (binary); - GNUNET_free_non_null (config); - return; + GNUNET_log_config_invalid (GNUNET_ERROR_TYPE_WARNING, + section, "CONFIG", + STRERROR (errno)); + GNUNET_free (config); + config = NULL; } + } sl = GNUNET_malloc (sizeof (struct ServiceList)); sl->name = GNUNET_strdup (section); sl->binary = binary; diff --git a/src/arm/test_arm_api.c b/src/arm/test_arm_api.c index 086cfc2..608c75c 100644 --- a/src/arm/test_arm_api.c +++ b/src/arm/test_arm_api.c @@ -30,8 +30,6 @@ #include "gnunet_program_lib.h" #include "gnunet_resolver_service.h" -#define VERBOSE GNUNET_NO - #define START_ARM GNUNET_YES #define START_TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MILLISECONDS, 1500) @@ -111,7 +109,7 @@ arm_notify (void *cls, enum GNUNET_ARM_ProcessStatus success) GNUNET_ARM_stop_service (arm, "arm", TIMEOUT, &arm_stopped, NULL); #endif } - GNUNET_ARM_start_service (arm, "resolver", START_TIMEOUT, &resolver_notify, + GNUNET_ARM_start_service (arm, "resolver", GNUNET_OS_INHERIT_STD_OUT_AND_ERR, START_TIMEOUT, &resolver_notify, NULL); } @@ -120,10 +118,23 @@ static void task (void *cls, char *const *args, const char *cfgfile, const struct GNUNET_CONFIGURATION_Handle *c) { + char *armconfig; cfg = c; + if (NULL != cfgfile) + { + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_filename (cfg, "arm", "CONFIG", + &armconfig)) + { + GNUNET_CONFIGURATION_set_value_string (cfg, "arm", "CONFIG", + cfgfile); + } + else + GNUNET_free (armconfig); + } arm = GNUNET_ARM_connect (cfg, NULL); #if START_ARM - GNUNET_ARM_start_service (arm, "arm", START_TIMEOUT, &arm_notify, NULL); + GNUNET_ARM_start_service (arm, "arm", GNUNET_OS_INHERIT_STD_OUT_AND_ERR, START_TIMEOUT, &arm_notify, NULL); #else arm_notify (NULL, GNUNET_YES); #endif @@ -137,9 +148,6 @@ check () char *const argv[] = { "test-arm-api", "-c", "test_arm_api_data.conf", -#if VERBOSE - "-L", "DEBUG", -#endif NULL }; struct GNUNET_GETOPT_CommandLineOption options[] = { @@ -159,11 +167,7 @@ main (int argc, char *argv[]) GNUNET_log_setup ("test-arm-api", -#if VERBOSE - "DEBUG", -#else "WARNING", -#endif NULL); ret = check (); diff --git a/src/arm/test_arm_api_data.conf b/src/arm/test_arm_api_data.conf index 7d56e65..b1000e9 100644 --- a/src/arm/test_arm_api_data.conf +++ b/src/arm/test_arm_api_data.conf @@ -1,27 +1,22 @@ [PATHS] SERVICEHOME = /tmp/test-gnunetd-arm/ -DEFAULTCONFIG = test_arm_api_data.conf [arm] PORT = 23354 DEFAULTSERVICES = BINARY = gnunet-service-arm OPTIONS = -L ERROR -# DEBUG = YES #PREFIX = valgrind --tool=memcheck --leak-check=yes [resolver] -# DEBUG = YES PORT = 23355 # PREFIX = valgrind [do-nothing] -#DEBUG = YES AUTOSTART = NO PORT = 2223 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = mockup-service ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -44,13 +39,12 @@ AUTOSTART = NO [statistics] AUTOSTART = YES -# DEBUG = NO - [dns] AUTOSTART = NO - +[consensus] +AUTOSTART = NO [nse] AUTOSTART = NO diff --git a/src/arm/test_exponential_backoff.c b/src/arm/test_exponential_backoff.c index 77bd9e2..19ca585 100644 --- a/src/arm/test_exponential_backoff.c +++ b/src/arm/test_exponential_backoff.c @@ -28,8 +28,6 @@ #include "gnunet_program_lib.h" #include "gnunet_protocols.h" -#define VERBOSE GNUNET_NO - #define START_ARM GNUNET_YES #define LOG_BACKOFF GNUNET_NO @@ -115,9 +113,7 @@ service_shutdown_handler (void *cls, const struct GNUNET_MessageHeader *msg) if (msg == NULL) { -#if VERBOSE GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Service shutdown complete.\n"); -#endif if (shutdown_ctx->cont != NULL) shutdown_ctx->cont (shutdown_ctx->cont_cls, GNUNET_NO); @@ -131,10 +127,8 @@ service_shutdown_handler (void *cls, const struct GNUNET_MessageHeader *msg) switch (ntohs (msg->type)) { case GNUNET_MESSAGE_TYPE_ARM_SHUTDOWN: -#if VERBOSE GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received confirmation for service shutdown.\n"); -#endif shutdown_ctx->confirmed = GNUNET_YES; GNUNET_CLIENT_receive (shutdown_ctx->sock, &service_shutdown_handler, shutdown_ctx, @@ -270,7 +264,7 @@ static void arm_notify (void *cls, enum GNUNET_ARM_ProcessStatus status) { GNUNET_assert (status == GNUNET_ARM_PROCESS_STARTING); - GNUNET_ARM_start_service (arm, "do-nothing", TIMEOUT, &do_nothing_notify, + GNUNET_ARM_start_service (arm, "do-nothing", GNUNET_OS_INHERIT_STD_OUT_AND_ERR, TIMEOUT, &do_nothing_notify, NULL); } @@ -361,11 +355,24 @@ static void task (void *cls, char *const *args, const char *cfgfile, const struct GNUNET_CONFIGURATION_Handle *c) { + char *armconfig; cfg = c; + if (NULL != cfgfile) + { + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_filename (cfg, "arm", "CONFIG", + &armconfig)) + { + GNUNET_CONFIGURATION_set_value_string (cfg, "arm", "CONFIG", + cfgfile); + } + else + GNUNET_free (armconfig); + } arm = GNUNET_ARM_connect (cfg, NULL); #if START_ARM - GNUNET_ARM_start_service (arm, "arm", GNUNET_TIME_UNIT_ZERO, &arm_notify, + GNUNET_ARM_start_service (arm, "arm", GNUNET_OS_INHERIT_STD_OUT_AND_ERR, GNUNET_TIME_UNIT_ZERO, &arm_notify, NULL); #else arm_do_nothing (NULL, GNUNET_YES); @@ -379,9 +386,6 @@ check () char *const argv[] = { "test-exponential-backoff", "-c", "test_arm_api_data.conf", -#if VERBOSE - "-L", "DEBUG", -#endif NULL }; struct GNUNET_GETOPT_CommandLineOption options[] = { @@ -431,11 +435,7 @@ main (int argc, char *argv[]) int ret; GNUNET_log_setup ("test-exponential-backoff", -#if VERBOSE - "DEBUG", -#else "WARNING", -#endif NULL); init (); diff --git a/src/arm/test_gnunet_arm.py.in b/src/arm/test_gnunet_arm.py.in new file mode 100644 index 0000000..c7698a3 --- /dev/null +++ b/src/arm/test_gnunet_arm.py.in @@ -0,0 +1,106 @@ +#!@PYTHON@ +from __future__ import print_function +import os +import sys +import shutil +import re +import subprocess +import time + +if os.name == "nt": + tmp = os.getenv ("TEMP") +else: + tmp = "/tmp" + +if os.name == 'nt': + st = 'gnunet-statistics.exe' + arm = 'gnunet-arm.exe' +else: + st = 'gnunet-statistics' + arm = 'gnunet-arm' + +run_arm = [arm, '-c', 'test_arm_api_data.conf', '--no-stdout', '--no-stderr'] +debug = os.getenv ('DEBUG') +if debug: + run_arm += [debug.split (' ')] + +def cleanup (): + shutil.rmtree (os.path.join (tmp, "test-gnunetd-arm"), True) + +def sub_run (args, want_stdo = True, want_stde = False, nofail = False): + if want_stdo: + stdo = subprocess.PIPE + else: + stdo = None + if want_stde: + stde = subprocess.PIPE + else: + stde = None + p = subprocess.Popen (args, stdout = stdo, stderr = stde) + stdo, stde = p.communicate () + if not nofail: + if p.returncode != 0: + sys.exit (p.returncode) + return (p.returncode, stdo, stde) + +def fail (result): + print (result) + r_arm (['-e'], want_stdo = False) + sys.exit (1) + + +def end_arm_failer (command, rc, stdo, stde, normal): + if normal: + if rc != 0: + fail ("FAIL: error running {}\nCommand output was:\n{}\n{}".format (command, stdo, stde)) + else: + if rc == 0: + fail ("FAIL: expected error while running {}\nCommand output was:\n{}\n{}".format (command, stdo, stde)) + +def print_only_failer (command, rc, stdo, stde, normal): + if normal: + if rc != 0: + print ("FAIL: error running {}\nCommand output was:\n{}\n{}".format (command, stdo, stde)) + sys.exit (1) + else: + if rc == 0: + print ("FAIL: expected error while running {}\nCommand output was:\n{}\n{}".format (command, stdo, stde)) + sys.exit (1) + + +def r_something (to_run, extra_args, failer = None, normal = True, **kw): + rc, stdo, stde = sub_run (to_run + extra_args, nofail = True, want_stde = True, **kw) + if failer is not None: + failer (to_run + extra_args, rc, stdo, stde, normal) + return (rc, stdo, stde) + +def r_arm (extra_args, **kw): + return r_something (run_arm, extra_args, **kw) + +cleanup () + +print ("TEST: Bad argument checking...", end='') +r_arm (['-x'], normal = False, failer = print_only_failer) +print ("PASS") + +print ("TEST: Start ARM...", end='') +r_arm (['-s'], failer = print_only_failer) +time.sleep (1) +print ("PASS") + +print ("TEST: Start another service...", end='') +r_arm (['-i', 'resolver'], failer = end_arm_failer) +time.sleep (1) +print ("PASS") + +print ("TEST: Stop a service...", end='') +r_arm (['-k', 'resolver'], failer = end_arm_failer) +time.sleep (1) +print ("PASS") + +print ("TEST: Stop ARM...", end='') +r_arm (['-e'], failer = print_only_failer) +time.sleep (1) +print ("PASS") + +cleanup () diff --git a/src/arm/test_gnunet_arm.sh b/src/arm/test_gnunet_arm.sh deleted file mode 100755 index 4a5b726..0000000 --- a/src/arm/test_gnunet_arm.sh +++ /dev/null @@ -1,65 +0,0 @@ -#!/bin/sh - -exe="./gnunet-arm -c test_arm_api_data.conf" -out=`mktemp /tmp/test-gnunet-arm-logXXXXXXXX` -#DEBUG="-L DEBUG" - - -# ---------------------------------------------------------------------------------- -echo -n "TEST: Bad argument checking... " - -if $exe -x 2> /dev/null; then - echo "FAIL: error running $exe" - exit 1 -fi -echo "PASS" - -# ---------------------------------------------------------------------------------- -echo -n "TEST: Start ARM..." - -if ! $exe $DEBUG -s > $out ; then - echo "FAIL: error running $exe" - echo "Command output was:" - cat $out - exit 1 -fi -echo "PASS" -sleep 1 - -# ---------------------------------------------------------------------------------- -echo -n "TEST: Start another service... " - -if ! $exe $DEBUG -i resolver > $out ; then - echo "FAIL: error running $exe" - echo "Command output was:" - cat $out - kill %% - exit 1 -fi -sleep 1 -echo "PASS" - -# ---------------------------------------------------------------------------------- -echo -n "TEST: Stop a service... " - -if ! $exe $DEBUG -k resolver > $out; then - echo "FAIL: error running $exe" - $exe -e - exit 1 -fi -sleep 1 -echo "PASS" - -# ---------------------------------------------------------------------------------- -echo -n "TEST: Stop ARM... " - -if ! $exe $DEBUG -e > $out; then - echo "FAIL: error running $exe" - exit 1 -fi -sleep 1 -echo "PASS" - -rm -rf /tmp/test-gnunetd-arm/ -rm -f $out - diff --git a/src/arm/test_gnunet_service_arm.c b/src/arm/test_gnunet_service_arm.c new file mode 100644 index 0000000..d367bc6 --- /dev/null +++ b/src/arm/test_gnunet_service_arm.c @@ -0,0 +1,169 @@ +/* + This file is part of GNUnet. + (C) 2009 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ +/** + * @file arm/test_gnunet_service_arm.c + * @brief testcase for gnunet-service-arm.c; tests ARM by making it start the resolver + * @author Safey + * @author Christian Grothoff + */ +#include "platform.h" +#include "gnunet_arm_service.h" +#include "gnunet_resolver_service.h" +#include "gnunet_os_lib.h" +#include "gnunet_program_lib.h" + +/** + * Timeout for starting services, very short because of the strange way start works + * (by checking if running before starting, so really this time is always waited on + * startup (annoying)). + */ +#define START_TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MILLISECONDS, 50) + +#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 10) + +static int ret = 1; + +static struct GNUNET_ARM_Handle *arm; + + +static void +arm_stopped (void *cls, enum GNUNET_ARM_ProcessStatus success) +{ + if (success != GNUNET_ARM_PROCESS_DOWN) + { + GNUNET_break (0); + ret = 4; + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "ARM stopped\n"); + } + GNUNET_ARM_disconnect (arm); + arm = NULL; +} + + +static void +hostNameResolveCB (void *cls, const struct sockaddr *addr, socklen_t addrlen) +{ + if ((ret == 0) || (ret == 4)) + return; + if (NULL == addr) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Name not resolved!\n"); + GNUNET_ARM_stop_service (arm, "arm", TIMEOUT, &arm_stopped, NULL); + ret = 3; + return; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Resolved hostname, now stopping ARM\n"); + ret = 0; + GNUNET_ARM_stop_service (arm, "arm", TIMEOUT, &arm_stopped, NULL); +} + + +static void +arm_notify (void *cls, enum GNUNET_ARM_ProcessStatus success) +{ + if (success != GNUNET_ARM_PROCESS_STARTING) + { + GNUNET_break (0); + ret = 1; + return; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Trying to resolve our own hostname!\n"); + /* connect to the resolver service */ + if (NULL == + GNUNET_RESOLVER_hostname_resolve (AF_UNSPEC, TIMEOUT, + &hostNameResolveCB, NULL)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Unable initiate connection to resolver service\n"); + ret = 2; + GNUNET_ARM_stop_service (arm, "arm", TIMEOUT, &arm_stopped, NULL); + } +} + + +static void +run (void *cls, char *const *args, const char *cfgfile, + const struct GNUNET_CONFIGURATION_Handle *c) +{ + char *armconfig; + + if (NULL != cfgfile) + { + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_filename (c, "arm", "CONFIG", + &armconfig)) + { + GNUNET_CONFIGURATION_set_value_string (c, "arm", "CONFIG", + cfgfile); + } + else + GNUNET_free (armconfig); + } + arm = GNUNET_ARM_connect (c, NULL); + GNUNET_ARM_start_service (arm, "arm", + GNUNET_OS_INHERIT_STD_OUT_AND_ERR, START_TIMEOUT, + &arm_notify, NULL); +} + + +int +main (int argc, char *av[]) +{ + static char *const argv[] = { + "test-gnunet-service-arm", + "-c", "test_arm_api_data.conf", + NULL + }; + static struct GNUNET_GETOPT_CommandLineOption options[] = { + GNUNET_GETOPT_OPTION_END + }; + char hostname[GNUNET_OS_get_hostname_max_length () + 1]; + + if (0 != gethostname (hostname, sizeof (hostname) - 1)) + { + GNUNET_log_strerror (GNUNET_ERROR_TYPE_ERROR | GNUNET_ERROR_TYPE_BULK, + "gethostname"); + FPRINTF (stderr, + "%s", "Failed to determine my own hostname, testcase not run.\n"); + return 0; + } + if (NULL == gethostbyname (hostname)) + { + FPRINTF (stderr, + "Failed to resolve my hostname `%s', testcase not run.\n", + hostname); + return 0; + } + GNUNET_log_setup ("test-gnunet-service-arm", + "WARNING", + NULL); + GNUNET_assert (GNUNET_OK == + GNUNET_PROGRAM_run ((sizeof (argv) / sizeof (char *)) - 1, + argv, "test-gnunet-service-arm", + "nohelp", options, &run, NULL)); + return ret; +} + +/* end of test_gnunet_service_arm.c */ diff --git a/src/arm/test_gnunet_service_manager.c b/src/arm/test_gnunet_service_manager.c deleted file mode 100644 index fe33571..0000000 --- a/src/arm/test_gnunet_service_manager.c +++ /dev/null @@ -1,185 +0,0 @@ -/* - This file is part of GNUnet. - (C) 2009 Christian Grothoff (and other contributing authors) - - GNUnet is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published - by the Free Software Foundation; either version 3, or (at your - option) any later version. - - GNUnet is distributed in the hope that it will be useful, but - WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - General Public License for more details. - - You should have received a copy of the GNU General Public License - along with GNUnet; see the file COPYING. If not, write to the - Free Software Foundation, Inc., 59 Temple Place - Suite 330, - Boston, MA 02111-1307, USA. -*/ -/** - * @file arm/test_gnunet_service_manager.c (A mockup testcase, not functionally complete) - * @brief testcase for gnunet-service-manager.c - */ - -#include "platform.h" -#include "gnunet_arm_service.h" -#include "gnunet_resolver_service.h" -#include "gnunet_os_lib.h" -#include "gnunet_program_lib.h" - -/** - * Timeout for starting services, very short because of the strange way start works - * (by checking if running before starting, so really this time is always waited on - * startup (annoying)). - */ -#define START_TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MILLISECONDS, 50) - -#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 10) - -#define START_ARM GNUNET_YES - -#define VERBOSE GNUNET_NO - -static int ret = 1; - - -static const struct GNUNET_CONFIGURATION_Handle *cfg; - -#if START_ARM -static struct GNUNET_ARM_Handle *arm; -#endif - -static void -arm_stopped (void *cls, enum GNUNET_ARM_ProcessStatus success) -{ - if (success != GNUNET_ARM_PROCESS_DOWN) - { - GNUNET_break (0); - ret = 4; - } - else - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "ARM stopped\n"); - } -#if START_ARM - GNUNET_ARM_disconnect (arm); - arm = NULL; -#endif -} - -static void -hostNameResolveCB (void *cls, const struct sockaddr *addr, socklen_t addrlen) -{ - if ((ret == 0) || (ret == 4)) - return; - if (NULL == addr) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Name not resolved!\n"); -#if START_ARM - GNUNET_ARM_stop_service (arm, "arm", TIMEOUT, &arm_stopped, NULL); -#endif - ret = 3; - return; - } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Resolved hostname, now stopping ARM\n"); - ret = 0; -#if START_ARM - GNUNET_ARM_stop_service (arm, "arm", TIMEOUT, &arm_stopped, NULL); -#endif -} - - -static void -arm_notify (void *cls, enum GNUNET_ARM_ProcessStatus success) -{ - if (success != GNUNET_ARM_PROCESS_STARTING) - { - GNUNET_break (0); - ret = 1; - return; - } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Trying to resolve our own hostname!\n"); - /* connect to the resolver service */ - if (NULL == - GNUNET_RESOLVER_hostname_resolve (AF_UNSPEC, TIMEOUT, - &hostNameResolveCB, NULL)) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "Unable initiate connection to resolver service\n"); - ret = 2; -#if START_ARM - GNUNET_ARM_stop_service (arm, "arm", TIMEOUT, &arm_stopped, NULL); -#endif - } -} - - -static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *c) -{ - cfg = c; -#if START_ARM - arm = GNUNET_ARM_connect (cfg, NULL); - GNUNET_ARM_start_service (arm, "arm", START_TIMEOUT, &arm_notify, NULL); -#else - arm_notify (NULL, GNUNET_YES); -#endif -} - - -static void -check () -{ - char *const argv[] = { - "test-gnunet-service-manager", - "-c", "test_arm_api_data.conf", -#if VERBOSE - "-L", "DEBUG", -#endif - NULL - }; - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - GNUNET_assert (GNUNET_OK == - GNUNET_PROGRAM_run ((sizeof (argv) / sizeof (char *)) - 1, - argv, "test-gnunet-service-manager", - "nohelp", options, &run, NULL)); -} - - -int -main (int argc, char *argv[]) -{ - char hostname[GNUNET_OS_get_hostname_max_length () + 1]; - - if (0 != gethostname (hostname, sizeof (hostname) - 1)) - { - GNUNET_log_strerror (GNUNET_ERROR_TYPE_ERROR | GNUNET_ERROR_TYPE_BULK, - "gethostname"); - FPRINTF (stderr, - "%s", "Failed to determine my own hostname, testcase not run.\n"); - return 0; - } - if (NULL == gethostbyname (hostname)) - { - FPRINTF (stderr, - "Failed to resolve my hostname `%s', testcase not run.\n", - hostname); - return 0; - } - - GNUNET_log_setup ("test-gnunet-service-manager", -#if VERBOSE - "DEBUG", -#else - "WARNING", -#endif - NULL); - check (); - return ret; -} diff --git a/src/ats-tool/Makefile.am b/src/ats-tool/Makefile.am new file mode 100644 index 0000000..c633a20 --- /dev/null +++ b/src/ats-tool/Makefile.am @@ -0,0 +1,21 @@ +INCLUDES = -I$(top_srcdir)/src/include + +if MINGW + WINFLAGS = -Wl,--no-undefined -Wl,--export-all-symbols +endif + +if USE_COVERAGE + AM_CFLAGS = -fprofile-arcs -ftest-coverage +endif + +bin_PROGRAMS = \ + gnunet-ats + +gnunet_ats_SOURCES = \ + gnunet-ats.c +gnunet_ats_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/ats/libgnunetats.la \ + $(top_builddir)/src/transport/libgnunettransport.la \ + $(top_builddir)/src/hello/libgnunethello.la \ + $(GN_LIBINTL) diff --git a/src/ats-tool/Makefile.in b/src/ats-tool/Makefile.in new file mode 100644 index 0000000..0d5a8cb --- /dev/null +++ b/src/ats-tool/Makefile.in @@ -0,0 +1,685 @@ +# Makefile.in generated by automake 1.11.6 from Makefile.am. +# @configure_input@ + +# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, +# 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Free Software +# Foundation, Inc. +# This Makefile.in is free software; the Free Software Foundation +# gives unlimited permission to copy and/or distribute it, +# with or without modifications, as long as this notice is preserved. + +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY, to the extent permitted by law; without +# even the implied warranty of MERCHANTABILITY or FITNESS FOR A +# PARTICULAR PURPOSE. + +@SET_MAKE@ + +VPATH = @srcdir@ +am__make_dryrun = \ + { \ + am__dry=no; \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + echo 'am--echo: ; @echo "AM" OK' | $(MAKE) -f - 2>/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } +pkgdatadir = $(datadir)/@PACKAGE@ +pkgincludedir = $(includedir)/@PACKAGE@ +pkglibdir = $(libdir)/@PACKAGE@ +pkglibexecdir = $(libexecdir)/@PACKAGE@ +am__cd = CDPATH="$${ZSH_VERSION+.}$(PATH_SEPARATOR)" && cd +install_sh_DATA = $(install_sh) -c -m 644 +install_sh_PROGRAM = $(install_sh) -c +install_sh_SCRIPT = $(install_sh) -c +INSTALL_HEADER = $(INSTALL_DATA) +transform = $(program_transform_name) +NORMAL_INSTALL = : +PRE_INSTALL = : +POST_INSTALL = : +NORMAL_UNINSTALL = : +PRE_UNINSTALL = : +POST_UNINSTALL = : +build_triplet = @build@ +host_triplet = @host@ +target_triplet = @target@ +bin_PROGRAMS = gnunet-ats$(EXEEXT) +subdir = src/ats-tool +DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in +ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 +am__aclocal_m4_deps = $(top_srcdir)/m4/absolute-header.m4 \ + $(top_srcdir)/m4/align.m4 $(top_srcdir)/m4/argz.m4 \ + $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/glib-2.0.m4 \ + $(top_srcdir)/m4/iconv.m4 $(top_srcdir)/m4/lib-ld.m4 \ + $(top_srcdir)/m4/lib-link.m4 $(top_srcdir)/m4/lib-prefix.m4 \ + $(top_srcdir)/m4/libcurl.m4 $(top_srcdir)/m4/libgcrypt.m4 \ + $(top_srcdir)/m4/libtool.m4 $(top_srcdir)/m4/libunistring.m4 \ + $(top_srcdir)/m4/ltdl.m4 $(top_srcdir)/m4/ltoptions.m4 \ + $(top_srcdir)/m4/ltsugar.m4 $(top_srcdir)/m4/ltversion.m4 \ + $(top_srcdir)/m4/lt~obsolete.m4 $(top_srcdir)/m4/nls.m4 \ + $(top_srcdir)/m4/pkg.m4 $(top_srcdir)/m4/po.m4 \ + $(top_srcdir)/m4/progtest.m4 $(top_srcdir)/acinclude.m4 \ + $(top_srcdir)/configure.ac +am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ + $(ACLOCAL_M4) +mkinstalldirs = $(install_sh) -d +CONFIG_HEADER = $(top_builddir)/gnunet_config.h +CONFIG_CLEAN_FILES = +CONFIG_CLEAN_VPATH_FILES = +am__installdirs = "$(DESTDIR)$(bindir)" +PROGRAMS = $(bin_PROGRAMS) +am_gnunet_ats_OBJECTS = gnunet-ats.$(OBJEXT) +gnunet_ats_OBJECTS = $(am_gnunet_ats_OBJECTS) +am__DEPENDENCIES_1 = +gnunet_ats_DEPENDENCIES = $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/ats/libgnunetats.la \ + $(top_builddir)/src/transport/libgnunettransport.la \ + $(top_builddir)/src/hello/libgnunethello.la \ + $(am__DEPENDENCIES_1) +AM_V_lt = $(am__v_lt_@AM_V@) +am__v_lt_ = $(am__v_lt_@AM_DEFAULT_V@) +am__v_lt_0 = --silent +DEFAULT_INCLUDES = -I.@am__isrc@ -I$(top_builddir) +depcomp = $(SHELL) $(top_srcdir)/depcomp +am__depfiles_maybe = depfiles +am__mv = mv -f +COMPILE = $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) \ + $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) +LTCOMPILE = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ + $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) \ + $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) \ + $(AM_CFLAGS) $(CFLAGS) +AM_V_CC = $(am__v_CC_@AM_V@) +am__v_CC_ = $(am__v_CC_@AM_DEFAULT_V@) +am__v_CC_0 = @echo " CC " $@; +AM_V_at = $(am__v_at_@AM_V@) +am__v_at_ = $(am__v_at_@AM_DEFAULT_V@) +am__v_at_0 = @ +CCLD = $(CC) +LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ + $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ + $(AM_LDFLAGS) $(LDFLAGS) -o $@ +AM_V_CCLD = $(am__v_CCLD_@AM_V@) +am__v_CCLD_ = $(am__v_CCLD_@AM_DEFAULT_V@) +am__v_CCLD_0 = @echo " CCLD " $@; +AM_V_GEN = $(am__v_GEN_@AM_V@) +am__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@) +am__v_GEN_0 = @echo " GEN " $@; +SOURCES = $(gnunet_ats_SOURCES) +DIST_SOURCES = $(gnunet_ats_SOURCES) +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac +ETAGS = etags +CTAGS = ctags +DISTFILES = $(DIST_COMMON) $(DIST_SOURCES) $(TEXINFOS) $(EXTRA_DIST) +ACLOCAL = @ACLOCAL@ +AMTAR = @AMTAR@ +AM_DEFAULT_VERBOSITY = @AM_DEFAULT_VERBOSITY@ +AR = @AR@ +ARGZ_H = @ARGZ_H@ +AS = @AS@ +AUTOCONF = @AUTOCONF@ +AUTOHEADER = @AUTOHEADER@ +AUTOMAKE = @AUTOMAKE@ +AWK = @AWK@ +CC = @CC@ +CCDEPMODE = @CCDEPMODE@ +CFLAGS = @CFLAGS@ +CPP = @CPP@ +CPPFLAGS = @CPPFLAGS@ +CXX = @CXX@ +CXXCPP = @CXXCPP@ +CXXDEPMODE = @CXXDEPMODE@ +CXXFLAGS = @CXXFLAGS@ +CYGPATH_W = @CYGPATH_W@ +DEFAULT_INTERFACE = @DEFAULT_INTERFACE@ +DEFS = @DEFS@ +DEPDIR = @DEPDIR@ +DLLDIR = @DLLDIR@ +DLLTOOL = @DLLTOOL@ +DSYMUTIL = @DSYMUTIL@ +DUMPBIN = @DUMPBIN@ +ECHO_C = @ECHO_C@ +ECHO_N = @ECHO_N@ +ECHO_T = @ECHO_T@ +EGREP = @EGREP@ +EXEEXT = @EXEEXT@ +EXT_LIBS = @EXT_LIBS@ +EXT_LIB_PATH = @EXT_LIB_PATH@ +FGREP = @FGREP@ +GLIB_CFLAGS = @GLIB_CFLAGS@ +GLIB_GENMARSHAL = @GLIB_GENMARSHAL@ +GLIB_LIBS = @GLIB_LIBS@ +GLIB_MKENUMS = @GLIB_MKENUMS@ +GMSGFMT = @GMSGFMT@ +GMSGFMT_015 = @GMSGFMT_015@ +GNUNETDNS_GROUP = @GNUNETDNS_GROUP@ +GN_DAEMON_CONFIG_DIR = @GN_DAEMON_CONFIG_DIR@ +GN_DAEMON_HOME_DIR = @GN_DAEMON_HOME_DIR@ +GN_INTLINCL = @GN_INTLINCL@ +GN_LIBINTL = @GN_LIBINTL@ +GN_LIB_LDFLAGS = @GN_LIB_LDFLAGS@ +GN_PLUGIN_LDFLAGS = @GN_PLUGIN_LDFLAGS@ +GN_USER_HOME_DIR = @GN_USER_HOME_DIR@ +GOBJECT_QUERY = @GOBJECT_QUERY@ +GREP = @GREP@ +HAVE_LIBUNISTRING = @HAVE_LIBUNISTRING@ +INCLTDL = @INCLTDL@ +INSTALL = @INSTALL@ +INSTALL_DATA = @INSTALL_DATA@ +INSTALL_PROGRAM = @INSTALL_PROGRAM@ +INSTALL_SCRIPT = @INSTALL_SCRIPT@ +INSTALL_STRIP_PROGRAM = @INSTALL_STRIP_PROGRAM@ +INTLLIBS = @INTLLIBS@ +INTL_MACOSX_LIBS = @INTL_MACOSX_LIBS@ +JAVAPORT = @JAVAPORT@ +LD = @LD@ +LDFLAGS = @LDFLAGS@ +LIBADD_DL = @LIBADD_DL@ +LIBADD_DLD_LINK = @LIBADD_DLD_LINK@ +LIBADD_DLOPEN = @LIBADD_DLOPEN@ +LIBADD_SHL_LOAD = @LIBADD_SHL_LOAD@ +LIBCURL = @LIBCURL@ +LIBCURL_CPPFLAGS = @LIBCURL_CPPFLAGS@ +LIBGCRYPT_CFLAGS = @LIBGCRYPT_CFLAGS@ +LIBGCRYPT_CONFIG = @LIBGCRYPT_CONFIG@ +LIBGCRYPT_LIBS = @LIBGCRYPT_LIBS@ +LIBGTOP_CFLAGS = @LIBGTOP_CFLAGS@ +LIBGTOP_LIBS = @LIBGTOP_LIBS@ +LIBICONV = @LIBICONV@ +LIBINTL = @LIBINTL@ +LIBLTDL = @LIBLTDL@ +LIBOBJS = @LIBOBJS@ +LIBPREFIX = @LIBPREFIX@ +LIBS = @LIBS@ +LIBTOOL = @LIBTOOL@ +LIBUNISTRING = @LIBUNISTRING@ +LIPO = @LIPO@ +LN_S = @LN_S@ +LTDLDEPS = @LTDLDEPS@ +LTDLINCL = @LTDLINCL@ +LTDLOPEN = @LTDLOPEN@ +LTLIBICONV = @LTLIBICONV@ +LTLIBINTL = @LTLIBINTL@ +LTLIBOBJS = @LTLIBOBJS@ +LTLIBUNISTRING = @LTLIBUNISTRING@ +LT_CONFIG_H = @LT_CONFIG_H@ +LT_DLLOADERS = @LT_DLLOADERS@ +LT_DLPREOPEN = @LT_DLPREOPEN@ +MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ +MKDIR_P = @MKDIR_P@ +MONKEYPREFIX = @MONKEYPREFIX@ +MSGFMT = @MSGFMT@ +MSGFMT_015 = @MSGFMT_015@ +MSGMERGE = @MSGMERGE@ +MYSQL_CPPFLAGS = @MYSQL_CPPFLAGS@ +MYSQL_LDFLAGS = @MYSQL_LDFLAGS@ +NM = @NM@ +NMEDIT = @NMEDIT@ +NSS_DIR = @NSS_DIR@ +OBJC = @OBJC@ +OBJCDEPMODE = @OBJCDEPMODE@ +OBJCFLAGS = @OBJCFLAGS@ +OBJDUMP = @OBJDUMP@ +OBJEXT = @OBJEXT@ +OTOOL = @OTOOL@ +OTOOL64 = @OTOOL64@ +PACKAGE = @PACKAGE@ +PACKAGE_BUGREPORT = @PACKAGE_BUGREPORT@ +PACKAGE_NAME = @PACKAGE_NAME@ +PACKAGE_STRING = @PACKAGE_STRING@ +PACKAGE_TARNAME = @PACKAGE_TARNAME@ +PACKAGE_URL = @PACKAGE_URL@ +PACKAGE_VERSION = @PACKAGE_VERSION@ +PATH_SEPARATOR = @PATH_SEPARATOR@ +PKG_CONFIG = @PKG_CONFIG@ +POSTGRES_CPPFLAGS = @POSTGRES_CPPFLAGS@ +POSTGRES_LDFLAGS = @POSTGRES_LDFLAGS@ +POSUB = @POSUB@ +PYTHON = @PYTHON@ +PYTHON_EXEC_PREFIX = @PYTHON_EXEC_PREFIX@ +PYTHON_PLATFORM = @PYTHON_PLATFORM@ +PYTHON_PREFIX = @PYTHON_PREFIX@ +PYTHON_VERSION = @PYTHON_VERSION@ +RANLIB = @RANLIB@ +SED = @SED@ +SET_MAKE = @SET_MAKE@ +SHELL = @SHELL@ +SQLITE_CPPFLAGS = @SQLITE_CPPFLAGS@ +SQLITE_LDFLAGS = @SQLITE_LDFLAGS@ +STRIP = @STRIP@ +SUDO_BINARY = @SUDO_BINARY@ +UNIXONLY = @UNIXONLY@ +USE_NLS = @USE_NLS@ +VERSION = @VERSION@ +XGETTEXT = @XGETTEXT@ +XGETTEXT_015 = @XGETTEXT_015@ +XMKMF = @XMKMF@ +X_CFLAGS = @X_CFLAGS@ +X_EXTRA_LIBS = @X_EXTRA_LIBS@ +X_LIBS = @X_LIBS@ +X_PRE_LIBS = @X_PRE_LIBS@ +_libcurl_config = @_libcurl_config@ +abs_builddir = @abs_builddir@ +abs_srcdir = @abs_srcdir@ +abs_top_builddir = @abs_top_builddir@ +abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ +ac_ct_CC = @ac_ct_CC@ +ac_ct_CXX = @ac_ct_CXX@ +ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ +ac_ct_OBJC = @ac_ct_OBJC@ +am__include = @am__include@ +am__leading_dot = @am__leading_dot@ +am__quote = @am__quote@ +am__tar = @am__tar@ +am__untar = @am__untar@ +bindir = @bindir@ +build = @build@ +build_alias = @build_alias@ +build_cpu = @build_cpu@ +build_os = @build_os@ +build_target = @build_target@ +build_vendor = @build_vendor@ +builddir = @builddir@ +datadir = @datadir@ +datarootdir = @datarootdir@ +docdir = @docdir@ +dvidir = @dvidir@ +exec_prefix = @exec_prefix@ +gitcommand = @gitcommand@ +host = @host@ +host_alias = @host_alias@ +host_cpu = @host_cpu@ +host_os = @host_os@ +host_vendor = @host_vendor@ +htmldir = @htmldir@ +includedir = @includedir@ +infodir = @infodir@ +install_sh = @install_sh@ +libdir = @libdir@ +libexecdir = @libexecdir@ +localedir = @localedir@ +localstatedir = @localstatedir@ +ltdl_LIBOBJS = @ltdl_LIBOBJS@ +ltdl_LTLIBOBJS = @ltdl_LTLIBOBJS@ +mandir = @mandir@ +mkdir_p = @mkdir_p@ +oldincludedir = @oldincludedir@ +pdfdir = @pdfdir@ +pkgpyexecdir = @pkgpyexecdir@ +pkgpythondir = @pkgpythondir@ +prefix = @prefix@ +program_transform_name = @program_transform_name@ +psdir = @psdir@ +pyexecdir = @pyexecdir@ +pythondir = @pythondir@ +sbindir = @sbindir@ +sharedstatedir = @sharedstatedir@ +srcdir = @srcdir@ +subdirs = @subdirs@ +svnversioncommand = @svnversioncommand@ +sys_symbol_underscore = @sys_symbol_underscore@ +sysconfdir = @sysconfdir@ +target = @target@ +target_alias = @target_alias@ +target_cpu = @target_cpu@ +target_os = @target_os@ +target_vendor = @target_vendor@ +top_build_prefix = @top_build_prefix@ +top_builddir = @top_builddir@ +top_srcdir = @top_srcdir@ +INCLUDES = -I$(top_srcdir)/src/include +@MINGW_TRUE@WINFLAGS = -Wl,--no-undefined -Wl,--export-all-symbols +@USE_COVERAGE_TRUE@AM_CFLAGS = -fprofile-arcs -ftest-coverage +gnunet_ats_SOURCES = \ + gnunet-ats.c + +gnunet_ats_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/ats/libgnunetats.la \ + $(top_builddir)/src/transport/libgnunettransport.la \ + $(top_builddir)/src/hello/libgnunethello.la \ + $(GN_LIBINTL) + +all: all-am + +.SUFFIXES: +.SUFFIXES: .c .lo .o .obj +$(srcdir)/Makefile.in: $(srcdir)/Makefile.am $(am__configure_deps) + @for dep in $?; do \ + case '$(am__configure_deps)' in \ + *$$dep*) \ + ( cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh ) \ + && { if test -f $@; then exit 0; else break; fi; }; \ + exit 1;; \ + esac; \ + done; \ + echo ' cd $(top_srcdir) && $(AUTOMAKE) --gnu src/ats-tool/Makefile'; \ + $(am__cd) $(top_srcdir) && \ + $(AUTOMAKE) --gnu src/ats-tool/Makefile +.PRECIOUS: Makefile +Makefile: $(srcdir)/Makefile.in $(top_builddir)/config.status + @case '$?' in \ + *config.status*) \ + cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh;; \ + *) \ + echo ' cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ $(am__depfiles_maybe)'; \ + cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ $(am__depfiles_maybe);; \ + esac; + +$(top_builddir)/config.status: $(top_srcdir)/configure $(CONFIG_STATUS_DEPENDENCIES) + cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh + +$(top_srcdir)/configure: $(am__configure_deps) + cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh +$(ACLOCAL_M4): $(am__aclocal_m4_deps) + cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh +$(am__aclocal_m4_deps): +install-binPROGRAMS: $(bin_PROGRAMS) + @$(NORMAL_INSTALL) + @list='$(bin_PROGRAMS)'; test -n "$(bindir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(bindir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(bindir)" || exit 1; \ + fi; \ + for p in $$list; do echo "$$p $$p"; done | \ + sed 's/$(EXEEXT)$$//' | \ + while read p p1; do if test -f $$p || test -f $$p1; \ + then echo "$$p"; echo "$$p"; else :; fi; \ + done | \ + sed -e 'p;s,.*/,,;n;h' -e 's|.*|.|' \ + -e 'p;x;s,.*/,,;s/$(EXEEXT)$$//;$(transform);s/$$/$(EXEEXT)/' | \ + sed 'N;N;N;s,\n, ,g' | \ + $(AWK) 'BEGIN { files["."] = ""; dirs["."] = 1 } \ + { d=$$3; if (dirs[d] != 1) { print "d", d; dirs[d] = 1 } \ + if ($$2 == $$4) files[d] = files[d] " " $$1; \ + else { print "f", $$3 "/" $$4, $$1; } } \ + END { for (d in files) print "f", d, files[d] }' | \ + while read type dir files; do \ + if test "$$dir" = .; then dir=; else dir=/$$dir; fi; \ + test -z "$$files" || { \ + echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files '$(DESTDIR)$(bindir)$$dir'"; \ + $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files "$(DESTDIR)$(bindir)$$dir" || exit $$?; \ + } \ + ; done + +uninstall-binPROGRAMS: + @$(NORMAL_UNINSTALL) + @list='$(bin_PROGRAMS)'; test -n "$(bindir)" || list=; \ + files=`for p in $$list; do echo "$$p"; done | \ + sed -e 'h;s,^.*/,,;s/$(EXEEXT)$$//;$(transform)' \ + -e 's/$$/$(EXEEXT)/' `; \ + test -n "$$list" || exit 0; \ + echo " ( cd '$(DESTDIR)$(bindir)' && rm -f" $$files ")"; \ + cd "$(DESTDIR)$(bindir)" && rm -f $$files + +clean-binPROGRAMS: + @list='$(bin_PROGRAMS)'; test -n "$$list" || exit 0; \ + echo " rm -f" $$list; \ + rm -f $$list || exit $$?; \ + test -n "$(EXEEXT)" || exit 0; \ + list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ + echo " rm -f" $$list; \ + rm -f $$list +gnunet-ats$(EXEEXT): $(gnunet_ats_OBJECTS) $(gnunet_ats_DEPENDENCIES) $(EXTRA_gnunet_ats_DEPENDENCIES) + @rm -f gnunet-ats$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(gnunet_ats_OBJECTS) $(gnunet_ats_LDADD) $(LIBS) + +mostlyclean-compile: + -rm -f *.$(OBJEXT) + +distclean-compile: + -rm -f *.tab.c + +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-ats.Po@am__quote@ + +.c.o: +@am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c $< + +.c.obj: +@am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'` +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c `$(CYGPATH_W) '$<'` + +.c.lo: +@am__fastdepCC_TRUE@ $(AM_V_CC)$(LTCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LTCOMPILE) -c -o $@ $< + +mostlyclean-libtool: + -rm -f *.lo + +clean-libtool: + -rm -rf .libs _libs + +ID: $(HEADERS) $(SOURCES) $(LISP) $(TAGS_FILES) + list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ + unique=`for i in $$list; do \ + if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \ + done | \ + $(AWK) '{ files[$$0] = 1; nonempty = 1; } \ + END { if (nonempty) { for (i in files) print i; }; }'`; \ + mkid -fID $$unique +tags: TAGS + +TAGS: $(HEADERS) $(SOURCES) $(TAGS_DEPENDENCIES) \ + $(TAGS_FILES) $(LISP) + set x; \ + here=`pwd`; \ + list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ + unique=`for i in $$list; do \ + if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \ + done | \ + $(AWK) '{ files[$$0] = 1; nonempty = 1; } \ + END { if (nonempty) { for (i in files) print i; }; }'`; \ + shift; \ + if test -z "$(ETAGS_ARGS)$$*$$unique"; then :; else \ + test -n "$$unique" || unique=$$empty_fix; \ + if test $$# -gt 0; then \ + $(ETAGS) $(ETAGSFLAGS) $(AM_ETAGSFLAGS) $(ETAGS_ARGS) \ + "$$@" $$unique; \ + else \ + $(ETAGS) $(ETAGSFLAGS) $(AM_ETAGSFLAGS) $(ETAGS_ARGS) \ + $$unique; \ + fi; \ + fi +ctags: CTAGS +CTAGS: $(HEADERS) $(SOURCES) $(TAGS_DEPENDENCIES) \ + $(TAGS_FILES) $(LISP) + list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ + unique=`for i in $$list; do \ + if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \ + done | \ + $(AWK) '{ files[$$0] = 1; nonempty = 1; } \ + END { if (nonempty) { for (i in files) print i; }; }'`; \ + test -z "$(CTAGS_ARGS)$$unique" \ + || $(CTAGS) $(CTAGSFLAGS) $(AM_CTAGSFLAGS) $(CTAGS_ARGS) \ + $$unique + +GTAGS: + here=`$(am__cd) $(top_builddir) && pwd` \ + && $(am__cd) $(top_srcdir) \ + && gtags -i $(GTAGS_ARGS) "$$here" + +distclean-tags: + -rm -f TAGS ID GTAGS GRTAGS GSYMS GPATH tags + +distdir: $(DISTFILES) + @srcdirstrip=`echo "$(srcdir)" | sed 's/[].[^$$\\*]/\\\\&/g'`; \ + topsrcdirstrip=`echo "$(top_srcdir)" | sed 's/[].[^$$\\*]/\\\\&/g'`; \ + list='$(DISTFILES)'; \ + dist_files=`for file in $$list; do echo $$file; done | \ + sed -e "s|^$$srcdirstrip/||;t" \ + -e "s|^$$topsrcdirstrip/|$(top_builddir)/|;t"`; \ + case $$dist_files in \ + */*) $(MKDIR_P) `echo "$$dist_files" | \ + sed '/\//!d;s|^|$(distdir)/|;s,/[^/]*$$,,' | \ + sort -u` ;; \ + esac; \ + for file in $$dist_files; do \ + if test -f $$file || test -d $$file; then d=.; else d=$(srcdir); fi; \ + if test -d $$d/$$file; then \ + dir=`echo "/$$file" | sed -e 's,/[^/]*$$,,'`; \ + if test -d "$(distdir)/$$file"; then \ + find "$(distdir)/$$file" -type d ! -perm -700 -exec chmod u+rwx {} \;; \ + fi; \ + if test -d $(srcdir)/$$file && test $$d != $(srcdir); then \ + cp -fpR $(srcdir)/$$file "$(distdir)$$dir" || exit 1; \ + find "$(distdir)/$$file" -type d ! -perm -700 -exec chmod u+rwx {} \;; \ + fi; \ + cp -fpR $$d/$$file "$(distdir)$$dir" || exit 1; \ + else \ + test -f "$(distdir)/$$file" \ + || cp -p $$d/$$file "$(distdir)/$$file" \ + || exit 1; \ + fi; \ + done +check-am: all-am +check: check-am +all-am: Makefile $(PROGRAMS) +installdirs: + for dir in "$(DESTDIR)$(bindir)"; do \ + test -z "$$dir" || $(MKDIR_P) "$$dir"; \ + done +install: install-am +install-exec: install-exec-am +install-data: install-data-am +uninstall: uninstall-am + +install-am: all-am + @$(MAKE) $(AM_MAKEFLAGS) install-exec-am install-data-am + +installcheck: installcheck-am +install-strip: + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi +mostlyclean-generic: + +clean-generic: + +distclean-generic: + -test -z "$(CONFIG_CLEAN_FILES)" || rm -f $(CONFIG_CLEAN_FILES) + -test . = "$(srcdir)" || test -z "$(CONFIG_CLEAN_VPATH_FILES)" || rm -f $(CONFIG_CLEAN_VPATH_FILES) + +maintainer-clean-generic: + @echo "This command is intended for maintainers to use" + @echo "it deletes files that may require special tools to rebuild." +clean: clean-am + +clean-am: clean-binPROGRAMS clean-generic clean-libtool mostlyclean-am + +distclean: distclean-am + -rm -rf ./$(DEPDIR) + -rm -f Makefile +distclean-am: clean-am distclean-compile distclean-generic \ + distclean-tags + +dvi: dvi-am + +dvi-am: + +html: html-am + +html-am: + +info: info-am + +info-am: + +install-data-am: + +install-dvi: install-dvi-am + +install-dvi-am: + +install-exec-am: install-binPROGRAMS + +install-html: install-html-am + +install-html-am: + +install-info: install-info-am + +install-info-am: + +install-man: + +install-pdf: install-pdf-am + +install-pdf-am: + +install-ps: install-ps-am + +install-ps-am: + +installcheck-am: + +maintainer-clean: maintainer-clean-am + -rm -rf ./$(DEPDIR) + -rm -f Makefile +maintainer-clean-am: distclean-am maintainer-clean-generic + +mostlyclean: mostlyclean-am + +mostlyclean-am: mostlyclean-compile mostlyclean-generic \ + mostlyclean-libtool + +pdf: pdf-am + +pdf-am: + +ps: ps-am + +ps-am: + +uninstall-am: uninstall-binPROGRAMS + +.MAKE: install-am install-strip + +.PHONY: CTAGS GTAGS all all-am check check-am clean clean-binPROGRAMS \ + clean-generic clean-libtool ctags distclean distclean-compile \ + distclean-generic distclean-libtool distclean-tags distdir dvi \ + dvi-am html html-am info info-am install install-am \ + install-binPROGRAMS install-data install-data-am install-dvi \ + install-dvi-am install-exec install-exec-am install-html \ + install-html-am install-info install-info-am install-man \ + install-pdf install-pdf-am install-ps install-ps-am \ + install-strip installcheck installcheck-am installdirs \ + maintainer-clean maintainer-clean-generic mostlyclean \ + mostlyclean-compile mostlyclean-generic mostlyclean-libtool \ + pdf pdf-am ps ps-am tags uninstall uninstall-am \ + uninstall-binPROGRAMS + + +# Tell versions [3.59,3.63) of GNU make to not export all variables. +# Otherwise a system limit (for SysV at least) may be exceeded. +.NOEXPORT: diff --git a/src/ats-tool/gnunet-ats.c b/src/ats-tool/gnunet-ats.c new file mode 100644 index 0000000..20ce970 --- /dev/null +++ b/src/ats-tool/gnunet-ats.c @@ -0,0 +1,539 @@ +/* + This file is part of GNUnet. + (C) 2001, 2002, 2004, 2005, 2006, 2007, 2009 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @file ats-tool/gnunet-ats.c + * @brief ATS command line tool + * @author Matthias Wachs + */ +#include "platform.h" +#include "gnunet_util_lib.h" +#include "gnunet_ats_service.h" +#include "gnunet_transport_service.h" + +#define TIMEOUT GNUNET_TIME_relative_multiply(GNUNET_TIME_UNIT_SECONDS, 5) + +#define BIG_M_STRING "unlimited" + +/** + * Final status code. + */ +static int ret; +static int results; +static int resolve_addresses_numeric; +static int receive_done; + +/** + * For which peer should we change preference values? + */ +static char *pid_str; + +static char *type_str; +static unsigned int value; +static int pending; + +/** + * Print verbose ATS information + */ +static int verbose; + +/** + * List only addresses currently used (active) + */ +static int op_list_used; + +/** + * List all addresses + */ +static int op_list_all; + +/** + * List all addresses + */ +static int op_set_pref; + +/** + * Print quotas configured + */ +static int op_print_quotas; + +/** + * Monitor addresses used + */ +static int op_monitor; + + + +static struct GNUNET_ATS_PerformanceHandle *ph; + +struct GNUNET_ATS_AddressListHandle *alh; + +static struct GNUNET_CONFIGURATION_Handle *cfg; + +GNUNET_SCHEDULER_TaskIdentifier end_task; + +struct PendingResolutions +{ + struct PendingResolutions *next; + struct PendingResolutions *prev; + + struct GNUNET_HELLO_Address *address; + struct GNUNET_BANDWIDTH_Value32NBO bandwidth_out; + struct GNUNET_BANDWIDTH_Value32NBO bandwidth_in; + + struct GNUNET_ATS_Information *ats; + uint32_t ats_count; + + struct GNUNET_TRANSPORT_AddressToStringContext * tats_ctx; +}; + +struct PendingResolutions *head; +struct PendingResolutions *tail; + +void end (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct PendingResolutions * pr; + struct PendingResolutions * next; + unsigned int pending; + + if (NULL != alh) + { + GNUNET_ATS_performance_list_addresses_cancel (alh); + alh = NULL; + } + + if (NULL != ph) + { + GNUNET_ATS_performance_done (ph); + ph = NULL; + } + + pending = 0; + next = head; + while (NULL != (pr = next)) + { + next = pr->next; + GNUNET_CONTAINER_DLL_remove (head, tail, pr); + GNUNET_TRANSPORT_address_to_string_cancel (pr->tats_ctx); + GNUNET_free (pr->address); + GNUNET_free (pr); + pending ++; + } + if (0 < pending) + fprintf (stderr, _("%u address resolutions had a timeout\n"), pending); + + fprintf (stderr, _("ATS returned results for %u addresses\n"), results); + ret = 0; +} + + +void transport_addr_to_str_cb (void *cls, const char *address) +{ + struct PendingResolutions * pr = cls; + char *ats_str; + char *ats_tmp; + char *ats_prop_arr[GNUNET_ATS_PropertyCount] = GNUNET_ATS_PropertyStrings; + char *ats_prop_value; + unsigned int c; + uint32_t ats_type; + uint32_t ats_value; + uint32_t network; + if (NULL != address) + { + ats_str = GNUNET_strdup(""); + + + for (c = 0; c < pr->ats_count; c++) + { + ats_tmp = ats_str; + + ats_type = ntohl(pr->ats[c].type); + ats_value = ntohl(pr->ats[c].value); + + if (ats_type > GNUNET_ATS_PropertyCount) + { + GNUNET_break (0); + continue; + } + + switch (ats_type) { + case GNUNET_ATS_NETWORK_TYPE: + if (ats_value > GNUNET_ATS_NetworkTypeCount) + { + GNUNET_break (0); + continue; + } + network = ats_value; + GNUNET_asprintf (&ats_prop_value, "%s", GNUNET_ATS_print_network_type(ats_value)); + break; + default: + GNUNET_asprintf (&ats_prop_value, "%u", ats_value); + break; + } + if ((verbose) && (ats_type < GNUNET_ATS_PropertyCount)) + { + GNUNET_asprintf (&ats_str, "%s%s=%s, ", ats_tmp, ats_prop_arr[ats_type] , ats_prop_value); + GNUNET_free (ats_tmp); + } + GNUNET_free (ats_prop_value); + } + + fprintf (stderr, _("Peer `%s' plugin `%s', address `%s', `%s' bw out: %u Bytes/s, bw in %u Bytes/s, %s\n"), + GNUNET_i2s (&pr->address->peer), pr->address->transport_name, address, + GNUNET_ATS_print_network_type(network), + ntohl (pr->bandwidth_out.value__), ntohl (pr->bandwidth_in.value__),ats_str); + GNUNET_free (ats_str); + } + else + { + /* We're done */ + GNUNET_CONTAINER_DLL_remove (head, tail, pr); + GNUNET_free (pr->address); + GNUNET_free (pr); + pending--; + + if ((GNUNET_YES == receive_done) && (0 == pending)) + { + /* All messages received and no resolutions pending*/ + if (end_task != GNUNET_SCHEDULER_NO_TASK) + GNUNET_SCHEDULER_cancel (end_task); + end_task = GNUNET_SCHEDULER_add_now (end, NULL); + } + } +} + +void ats_perf_cb (void *cls, + const struct + GNUNET_HELLO_Address * + address, + struct + GNUNET_BANDWIDTH_Value32NBO + bandwidth_out, + struct + GNUNET_BANDWIDTH_Value32NBO + bandwidth_in, + const struct + GNUNET_ATS_Information * + ats, uint32_t ats_count) +{ + struct PendingResolutions * pr; + + + if (NULL != address) + { + pr = GNUNET_malloc (sizeof (struct PendingResolutions) + + ats_count * sizeof (struct GNUNET_ATS_Information)); + + pr->ats_count = ats_count; + pr->ats = (struct GNUNET_ATS_Information *) &pr[1]; + if (ats_count > 0) + memcpy (pr->ats, ats, ats_count * sizeof (struct GNUNET_ATS_Information)); + pr->address = GNUNET_HELLO_address_copy (address); + pr->bandwidth_in = bandwidth_in; + pr->bandwidth_out = bandwidth_out; + pr->tats_ctx = GNUNET_TRANSPORT_address_to_string(cfg, address, + resolve_addresses_numeric, GNUNET_TIME_UNIT_FOREVER_REL, transport_addr_to_str_cb, pr); + GNUNET_CONTAINER_DLL_insert (head, tail, pr); + results++; + pending++; + } + else + { + /* All messages received */ + receive_done = GNUNET_YES; + alh = NULL; + if (0 == pending) + { + /* All messages received and no resolutions pending*/ + if (end_task != GNUNET_SCHEDULER_NO_TASK) + GNUNET_SCHEDULER_cancel (end_task); + end_task = GNUNET_SCHEDULER_add_now (end, NULL); + } + } +} + +static unsigned int +print_quotas (const struct GNUNET_CONFIGURATION_Handle *cfg) +{ + char *network_str[GNUNET_ATS_NetworkTypeCount] = GNUNET_ATS_NetworkTypeString; + char * entry_in = NULL; + char * entry_out = NULL; + char * quota_out_str; + char * quota_in_str; + unsigned long long int quota_out; + unsigned long long int quota_in; + int c; + + for (c = 0; (c < GNUNET_ATS_NetworkTypeCount); c++) + { + + GNUNET_asprintf (&entry_out, "%s_QUOTA_OUT", network_str[c]); + GNUNET_asprintf (&entry_in, "%s_QUOTA_IN", network_str[c]); + + /* quota out */ + if (GNUNET_OK == GNUNET_CONFIGURATION_get_value_string(cfg, "ats", entry_out, "a_out_str)) + { + if (0 == strcmp(quota_out_str, BIG_M_STRING) || + (GNUNET_SYSERR == GNUNET_STRINGS_fancy_size_to_bytes (quota_out_str, "a_out))) + quota_out = UINT32_MAX; + + GNUNET_free (quota_out_str); + GNUNET_asprintf ("a_out_str, "%llu", quota_out); + } + else + { + fprintf (stderr, "Outbound quota for network `%11s' not configured!\n", + network_str[c]); + GNUNET_asprintf ("a_out_str, "-"); + } + GNUNET_free (entry_out); + + /* quota in */ + if (GNUNET_OK == GNUNET_CONFIGURATION_get_value_string(cfg, "ats", entry_in, "a_in_str)) + { + if (0 == strcmp(quota_in_str, BIG_M_STRING) || + (GNUNET_SYSERR == GNUNET_STRINGS_fancy_size_to_bytes (quota_in_str, "a_in))) + quota_in = UINT32_MAX; + GNUNET_free (quota_in_str); + GNUNET_asprintf ("a_in_str, "%llu", quota_in); + } + else + { + fprintf (stderr, "Inbound quota for network `%11s' not configured!\n", + network_str[c]); + GNUNET_asprintf ("a_in_str, "-"); + } + GNUNET_free (entry_in); + + fprintf (stderr, _("Quota for network `%11s' (in/out): %10s / %10s\n"), network_str[c], quota_in_str, quota_out_str ); + GNUNET_free (quota_out_str); + GNUNET_free (quota_in_str); + } + return GNUNET_ATS_NetworkTypeCount; +} + + + +void testservice_ats (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct GNUNET_PeerIdentity pid; + struct GNUNET_CONFIGURATION_Handle *cfg = cls; + unsigned int c; + unsigned int type; + + if (0 != (tc->reason & GNUNET_SCHEDULER_REASON_TIMEOUT)) + { + FPRINTF (stderr, _("Service `%s' is not running\n"), "ats"); + return; + } + + results = 0; + + if (NULL != pid_str) + { + if (GNUNET_OK != GNUNET_CRYPTO_hash_from_string (pid_str, &pid.hashPubKey)) + { + FPRINTF (stderr, _("Failed to parse peer identity `%s'\n"), pid_str); + return; + } + } + + c = op_list_all + op_list_used + op_monitor + op_set_pref; + if ((1 < c)) + { + FPRINTF (stderr, _("Please select one operation : %s or %s or %s or %s or %s\n"), + "--used", "--all", "--monitor", "--preference", "--quotas"); + return; + } + if ((0 == c)) + op_list_used = GNUNET_YES; /* set default */ + if (op_print_quotas) + { + ret = print_quotas (cfg); + return; + } + if (op_list_all) + { + ph = GNUNET_ATS_performance_init (cfg, NULL, NULL); + if (NULL == ph) + { + fprintf (stderr, _("Cannot connect to ATS service, exiting...\n")); + return; + } + + alh = GNUNET_ATS_performance_list_addresses (ph, + (NULL == pid_str) ? NULL : &pid, + GNUNET_YES, ats_perf_cb, NULL); + if (NULL == alh) + { + fprintf (stderr, _("Cannot issue request to ATS service, exiting...\n")); + end_task = GNUNET_SCHEDULER_add_now (&end, NULL); + return; + } + end_task = GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, &end, NULL); + } + else if (op_list_used) + { + ph = GNUNET_ATS_performance_init (cfg, NULL, NULL); + if (NULL == ph) + fprintf (stderr, _("Cannot connect to ATS service, exiting...\n")); + + alh = GNUNET_ATS_performance_list_addresses (ph, + (NULL == pid_str) ? NULL : &pid, + GNUNET_NO, ats_perf_cb, NULL); + if (NULL == alh) + { + fprintf (stderr, _("Cannot issue request to ATS service, exiting...\n")); + end_task = GNUNET_SCHEDULER_add_now (&end, NULL); + return; + } + end_task = GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, &end, NULL); + } + else if (op_monitor) + { + ph = GNUNET_ATS_performance_init (cfg, ats_perf_cb, NULL); + if (NULL == ph) + fprintf (stderr, _("Cannot connect to ATS service, exiting...\n")); + end_task = GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, &end, NULL); + + } + else if (op_set_pref) + { + for (c = 0; c/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } pkgdatadir = $(datadir)/@PACKAGE@ pkgincludedir = $(includedir)/@PACKAGE@ pkglibdir = $(libdir)/@PACKAGE@ @@ -37,24 +54,37 @@ POST_UNINSTALL = : build_triplet = @build@ host_triplet = @host@ target_triplet = @target@ -bin_PROGRAMS = gnunet-service-ats$(EXEEXT) -check_PROGRAMS = test_ats_api_scheduling$(EXEEXT) \ - test_ats_api_reset_backoff$(EXEEXT) $(am__EXEEXT_1) \ - $(am__EXEEXT_2) $(am__EXEEXT_3) +libexec_PROGRAMS = gnunet-service-ats$(EXEEXT) +check_PROGRAMS = test_ats_api_scheduling_init$(EXEEXT) \ + test_ats_api_scheduling_add_address$(EXEEXT) \ + test_ats_api_scheduling_add_session$(EXEEXT) \ + test_ats_api_scheduling_min_bw$(EXEEXT) \ + test_ats_api_scheduling_check_min_bw_alt$(EXEEXT) \ + test_ats_api_scheduling_update_address$(EXEEXT) \ + test_ats_api_scheduling_destroy_address$(EXEEXT) \ + test_ats_api_scheduling_destroy_session$(EXEEXT) \ + test_ats_api_scheduling_destroy_inbound_connection$(EXEEXT) \ + test_ats_api_scheduling_block_and_reset$(EXEEXT) \ + test_ats_simplistic$(EXEEXT) \ + test_ats_simplistic_switch_networks$(EXEEXT) \ + test_ats_simplistic_change_preference$(EXEEXT) \ + test_ats_simplistic_pref_aging$(EXEEXT) \ + test_ats_api_performance$(EXEEXT) subdir = src/ats DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in \ $(srcdir)/ats.conf.in ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 am__aclocal_m4_deps = $(top_srcdir)/m4/absolute-header.m4 \ $(top_srcdir)/m4/align.m4 $(top_srcdir)/m4/argz.m4 \ - $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/iconv.m4 \ - $(top_srcdir)/m4/lib-ld.m4 $(top_srcdir)/m4/lib-link.m4 \ - $(top_srcdir)/m4/lib-prefix.m4 $(top_srcdir)/m4/libcurl.m4 \ - $(top_srcdir)/m4/libgcrypt.m4 $(top_srcdir)/m4/libtool.m4 \ - $(top_srcdir)/m4/libunistring.m4 $(top_srcdir)/m4/ltdl.m4 \ - $(top_srcdir)/m4/ltoptions.m4 $(top_srcdir)/m4/ltsugar.m4 \ - $(top_srcdir)/m4/ltversion.m4 $(top_srcdir)/m4/lt~obsolete.m4 \ - $(top_srcdir)/m4/nls.m4 $(top_srcdir)/m4/po.m4 \ + $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/glib-2.0.m4 \ + $(top_srcdir)/m4/iconv.m4 $(top_srcdir)/m4/lib-ld.m4 \ + $(top_srcdir)/m4/lib-link.m4 $(top_srcdir)/m4/lib-prefix.m4 \ + $(top_srcdir)/m4/libcurl.m4 $(top_srcdir)/m4/libgcrypt.m4 \ + $(top_srcdir)/m4/libtool.m4 $(top_srcdir)/m4/libunistring.m4 \ + $(top_srcdir)/m4/ltdl.m4 $(top_srcdir)/m4/ltoptions.m4 \ + $(top_srcdir)/m4/ltsugar.m4 $(top_srcdir)/m4/ltversion.m4 \ + $(top_srcdir)/m4/lt~obsolete.m4 $(top_srcdir)/m4/nls.m4 \ + $(top_srcdir)/m4/pkg.m4 $(top_srcdir)/m4/po.m4 \ $(top_srcdir)/m4/progtest.m4 $(top_srcdir)/acinclude.m4 \ $(top_srcdir)/configure.ac am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ @@ -84,28 +114,35 @@ am__nobase_list = $(am__nobase_strip_setup); \ am__base_list = \ sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \ sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g' -am__installdirs = "$(DESTDIR)$(libdir)" "$(DESTDIR)$(bindir)" \ +am__uninstall_files_from_dir = { \ + test -z "$$files" \ + || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \ + || { echo " ( cd '$$dir' && rm -f" $$files ")"; \ + $(am__cd) "$$dir" && rm -f $$files; }; \ + } +am__installdirs = "$(DESTDIR)$(libdir)" "$(DESTDIR)$(libexecdir)" \ "$(DESTDIR)$(pkgcfgdir)" LTLIBRARIES = $(lib_LTLIBRARIES) +am__DEPENDENCIES_1 = libgnunetats_la_DEPENDENCIES = \ - $(top_builddir)/src/util/libgnunetutil.la + $(top_builddir)/src/util/libgnunetutil.la \ + $(am__DEPENDENCIES_1) am_libgnunetats_la_OBJECTS = ats_api_scheduling.lo \ ats_api_performance.lo libgnunetats_la_OBJECTS = $(am_libgnunetats_la_OBJECTS) -AM_V_lt = $(am__v_lt_$(V)) -am__v_lt_ = $(am__v_lt_$(AM_DEFAULT_VERBOSITY)) +AM_V_lt = $(am__v_lt_@AM_V@) +am__v_lt_ = $(am__v_lt_@AM_DEFAULT_V@) am__v_lt_0 = --silent libgnunetats_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ $(AM_CFLAGS) $(CFLAGS) $(libgnunetats_la_LDFLAGS) $(LDFLAGS) \ -o $@ -@HAVE_LIBGLPK_TRUE@am__EXEEXT_1 = test_ats_mlp$(EXEEXT) -@HAVE_LIBGLPK_TRUE@am__EXEEXT_2 = test_ats_mlp_averaging$(EXEEXT) -@HAVE_LIBGLPK_TRUE@am__EXEEXT_3 = perf_ats_mlp$(EXEEXT) -PROGRAMS = $(bin_PROGRAMS) +PROGRAMS = $(libexec_PROGRAMS) am__gnunet_service_ats_SOURCES_DIST = gnunet-service-ats.c \ gnunet-service-ats.h gnunet-service-ats_addresses.c \ gnunet-service-ats_addresses.h \ + gnunet-service-ats_addresses_simplistic.c \ + gnunet-service-ats_addresses_simplistic.h \ gnunet-service-ats_addresses_mlp.c \ gnunet-service-ats_addresses_mlp.h \ gnunet-service-ats_performance.c \ @@ -117,57 +154,145 @@ am__gnunet_service_ats_SOURCES_DIST = gnunet-service-ats.c \ @HAVE_LIBGLPK_TRUE@am__objects_1 = \ @HAVE_LIBGLPK_TRUE@ gnunet-service-ats_addresses_mlp.$(OBJEXT) am_gnunet_service_ats_OBJECTS = gnunet-service-ats.$(OBJEXT) \ - gnunet-service-ats_addresses.$(OBJEXT) $(am__objects_1) \ - gnunet-service-ats_performance.$(OBJEXT) \ + gnunet-service-ats_addresses.$(OBJEXT) \ + gnunet-service-ats_addresses_simplistic.$(OBJEXT) \ + $(am__objects_1) gnunet-service-ats_performance.$(OBJEXT) \ gnunet-service-ats_scheduling.$(OBJEXT) \ gnunet-service-ats_reservations.$(OBJEXT) gnunet_service_ats_OBJECTS = $(am_gnunet_service_ats_OBJECTS) -am__DEPENDENCIES_1 = -gnunet_service_ats_DEPENDENCIES = \ - $(top_builddir)/src/statistics/libgnunetstatistics.la \ +am_test_ats_api_performance_OBJECTS = \ + test_ats_api_performance.$(OBJEXT) +test_ats_api_performance_OBJECTS = \ + $(am_test_ats_api_performance_OBJECTS) +test_ats_api_performance_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la \ - $(am__DEPENDENCIES_1) $(am__DEPENDENCIES_1) -am__perf_ats_mlp_SOURCES_DIST = gnunet-service-ats_addresses_mlp.c \ - gnunet-service-ats_addresses_mlp.h perf_ats_mlp.c -@HAVE_LIBGLPK_TRUE@am_perf_ats_mlp_OBJECTS = $(am__objects_1) \ -@HAVE_LIBGLPK_TRUE@ perf_ats_mlp.$(OBJEXT) -perf_ats_mlp_OBJECTS = $(am_perf_ats_mlp_OBJECTS) -@HAVE_LIBGLPK_TRUE@perf_ats_mlp_DEPENDENCIES = $(am__DEPENDENCIES_1) \ -@HAVE_LIBGLPK_TRUE@ $(top_builddir)/src/util/libgnunetutil.la \ -@HAVE_LIBGLPK_TRUE@ $(top_builddir)/src/statistics/libgnunetstatistics.la -am_test_ats_api_reset_backoff_OBJECTS = \ - test_ats_api_reset_backoff.$(OBJEXT) -test_ats_api_reset_backoff_OBJECTS = \ - $(am_test_ats_api_reset_backoff_OBJECTS) -test_ats_api_reset_backoff_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/hello/libgnunethello.la \ + $(top_builddir)/src/ats/libgnunetats.la +am_test_ats_api_scheduling_add_address_OBJECTS = \ + test_ats_api_scheduling_add_address.$(OBJEXT) \ + test_ats_api_common.$(OBJEXT) +test_ats_api_scheduling_add_address_OBJECTS = \ + $(am_test_ats_api_scheduling_add_address_OBJECTS) +test_ats_api_scheduling_add_address_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/ats/libgnunetats.la -am_test_ats_api_scheduling_OBJECTS = \ - test_ats_api_scheduling.$(OBJEXT) -test_ats_api_scheduling_OBJECTS = \ - $(am_test_ats_api_scheduling_OBJECTS) -test_ats_api_scheduling_DEPENDENCIES = \ +am_test_ats_api_scheduling_add_session_OBJECTS = \ + test_ats_api_scheduling_add_session.$(OBJEXT) \ + test_ats_api_common.$(OBJEXT) +test_ats_api_scheduling_add_session_OBJECTS = \ + $(am_test_ats_api_scheduling_add_session_OBJECTS) +test_ats_api_scheduling_add_session_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/ats/libgnunetats.la +am_test_ats_api_scheduling_block_and_reset_OBJECTS = \ + test_ats_api_scheduling_block_and_reset.$(OBJEXT) \ + test_ats_api_common.$(OBJEXT) +test_ats_api_scheduling_block_and_reset_OBJECTS = \ + $(am_test_ats_api_scheduling_block_and_reset_OBJECTS) +test_ats_api_scheduling_block_and_reset_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/ats/libgnunetats.la +am_test_ats_api_scheduling_check_min_bw_alt_OBJECTS = \ + test_ats_api_scheduling_check_min_bw_alt.$(OBJEXT) \ + test_ats_api_common.$(OBJEXT) +test_ats_api_scheduling_check_min_bw_alt_OBJECTS = \ + $(am_test_ats_api_scheduling_check_min_bw_alt_OBJECTS) +test_ats_api_scheduling_check_min_bw_alt_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/ats/libgnunetats.la +am_test_ats_api_scheduling_destroy_address_OBJECTS = \ + test_ats_api_scheduling_destroy_address.$(OBJEXT) \ + test_ats_api_common.$(OBJEXT) +test_ats_api_scheduling_destroy_address_OBJECTS = \ + $(am_test_ats_api_scheduling_destroy_address_OBJECTS) +test_ats_api_scheduling_destroy_address_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/ats/libgnunetats.la +am_test_ats_api_scheduling_destroy_inbound_connection_OBJECTS = \ + test_ats_api_scheduling_destroy_inbound_connection.$(OBJEXT) \ + test_ats_api_common.$(OBJEXT) +test_ats_api_scheduling_destroy_inbound_connection_OBJECTS = $(am_test_ats_api_scheduling_destroy_inbound_connection_OBJECTS) +test_ats_api_scheduling_destroy_inbound_connection_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/ats/libgnunetats.la +am_test_ats_api_scheduling_destroy_session_OBJECTS = \ + test_ats_api_scheduling_destroy_session.$(OBJEXT) \ + test_ats_api_common.$(OBJEXT) +test_ats_api_scheduling_destroy_session_OBJECTS = \ + $(am_test_ats_api_scheduling_destroy_session_OBJECTS) +test_ats_api_scheduling_destroy_session_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/ats/libgnunetats.la +am_test_ats_api_scheduling_init_OBJECTS = \ + test_ats_api_scheduling_init.$(OBJEXT) \ + test_ats_api_common.$(OBJEXT) +test_ats_api_scheduling_init_OBJECTS = \ + $(am_test_ats_api_scheduling_init_OBJECTS) +test_ats_api_scheduling_init_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/ats/libgnunetats.la +am_test_ats_api_scheduling_min_bw_OBJECTS = \ + test_ats_api_scheduling_min_bw.$(OBJEXT) \ + test_ats_api_common.$(OBJEXT) +test_ats_api_scheduling_min_bw_OBJECTS = \ + $(am_test_ats_api_scheduling_min_bw_OBJECTS) +test_ats_api_scheduling_min_bw_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/ats/libgnunetats.la +am_test_ats_api_scheduling_update_address_OBJECTS = \ + test_ats_api_scheduling_update_address.$(OBJEXT) \ + test_ats_api_common.$(OBJEXT) +test_ats_api_scheduling_update_address_OBJECTS = \ + $(am_test_ats_api_scheduling_update_address_OBJECTS) +test_ats_api_scheduling_update_address_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/ats/libgnunetats.la +am_test_ats_simplistic_OBJECTS = test_ats_simplistic.$(OBJEXT) \ + test_ats_api_common.$(OBJEXT) +test_ats_simplistic_OBJECTS = $(am_test_ats_simplistic_OBJECTS) +test_ats_simplistic_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/hello/libgnunethello.la \ + $(top_builddir)/src/ats/libgnunetats.la +am_test_ats_simplistic_change_preference_OBJECTS = \ + test_ats_simplistic_change_preference.$(OBJEXT) \ + test_ats_api_common.$(OBJEXT) +test_ats_simplistic_change_preference_OBJECTS = \ + $(am_test_ats_simplistic_change_preference_OBJECTS) +test_ats_simplistic_change_preference_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/ats/libgnunetats.la +am_test_ats_simplistic_pref_aging_OBJECTS = \ + test_ats_simplistic_pref_aging.$(OBJEXT) \ + test_ats_api_common.$(OBJEXT) +test_ats_simplistic_pref_aging_OBJECTS = \ + $(am_test_ats_simplistic_pref_aging_OBJECTS) +test_ats_simplistic_pref_aging_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/ats/libgnunetats.la +am_test_ats_simplistic_switch_networks_OBJECTS = \ + test_ats_simplistic_switch_networks.$(OBJEXT) \ + test_ats_api_common.$(OBJEXT) +test_ats_simplistic_switch_networks_OBJECTS = \ + $(am_test_ats_simplistic_switch_networks_OBJECTS) +test_ats_simplistic_switch_networks_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/ats/libgnunetats.la -am__test_ats_mlp_SOURCES_DIST = gnunet-service-ats_addresses_mlp.c \ - gnunet-service-ats_addresses_mlp.h test_ats_mlp.c -@HAVE_LIBGLPK_TRUE@am_test_ats_mlp_OBJECTS = $(am__objects_1) \ -@HAVE_LIBGLPK_TRUE@ test_ats_mlp.$(OBJEXT) -test_ats_mlp_OBJECTS = $(am_test_ats_mlp_OBJECTS) -@HAVE_LIBGLPK_TRUE@test_ats_mlp_DEPENDENCIES = $(am__DEPENDENCIES_1) \ -@HAVE_LIBGLPK_TRUE@ $(top_builddir)/src/util/libgnunetutil.la \ -@HAVE_LIBGLPK_TRUE@ $(top_builddir)/src/statistics/libgnunetstatistics.la -am__test_ats_mlp_averaging_SOURCES_DIST = \ - gnunet-service-ats_addresses_mlp.c \ - gnunet-service-ats_addresses_mlp.h test_ats_mlp_averaging.c -@HAVE_LIBGLPK_TRUE@am_test_ats_mlp_averaging_OBJECTS = \ -@HAVE_LIBGLPK_TRUE@ $(am__objects_1) \ -@HAVE_LIBGLPK_TRUE@ test_ats_mlp_averaging.$(OBJEXT) -test_ats_mlp_averaging_OBJECTS = $(am_test_ats_mlp_averaging_OBJECTS) -@HAVE_LIBGLPK_TRUE@test_ats_mlp_averaging_DEPENDENCIES = \ -@HAVE_LIBGLPK_TRUE@ $(am__DEPENDENCIES_1) \ -@HAVE_LIBGLPK_TRUE@ $(top_builddir)/src/util/libgnunetutil.la \ -@HAVE_LIBGLPK_TRUE@ $(top_builddir)/src/statistics/libgnunetstatistics.la DEFAULT_INCLUDES = -I.@am__isrc@ -I$(top_builddir) depcomp = $(SHELL) $(top_srcdir)/depcomp am__depfiles_maybe = depfiles @@ -178,33 +303,60 @@ LTCOMPILE = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) \ $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) \ $(AM_CFLAGS) $(CFLAGS) -AM_V_CC = $(am__v_CC_$(V)) -am__v_CC_ = $(am__v_CC_$(AM_DEFAULT_VERBOSITY)) +AM_V_CC = $(am__v_CC_@AM_V@) +am__v_CC_ = $(am__v_CC_@AM_DEFAULT_V@) am__v_CC_0 = @echo " CC " $@; -AM_V_at = $(am__v_at_$(V)) -am__v_at_ = $(am__v_at_$(AM_DEFAULT_VERBOSITY)) +AM_V_at = $(am__v_at_@AM_V@) +am__v_at_ = $(am__v_at_@AM_DEFAULT_V@) am__v_at_0 = @ CCLD = $(CC) LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ $(AM_LDFLAGS) $(LDFLAGS) -o $@ -AM_V_CCLD = $(am__v_CCLD_$(V)) -am__v_CCLD_ = $(am__v_CCLD_$(AM_DEFAULT_VERBOSITY)) +AM_V_CCLD = $(am__v_CCLD_@AM_V@) +am__v_CCLD_ = $(am__v_CCLD_@AM_DEFAULT_V@) am__v_CCLD_0 = @echo " CCLD " $@; -AM_V_GEN = $(am__v_GEN_$(V)) -am__v_GEN_ = $(am__v_GEN_$(AM_DEFAULT_VERBOSITY)) +AM_V_GEN = $(am__v_GEN_@AM_V@) +am__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@) am__v_GEN_0 = @echo " GEN " $@; SOURCES = $(libgnunetats_la_SOURCES) $(gnunet_service_ats_SOURCES) \ - $(perf_ats_mlp_SOURCES) $(test_ats_api_reset_backoff_SOURCES) \ - $(test_ats_api_scheduling_SOURCES) $(test_ats_mlp_SOURCES) \ - $(test_ats_mlp_averaging_SOURCES) + $(test_ats_api_performance_SOURCES) \ + $(test_ats_api_scheduling_add_address_SOURCES) \ + $(test_ats_api_scheduling_add_session_SOURCES) \ + $(test_ats_api_scheduling_block_and_reset_SOURCES) \ + $(test_ats_api_scheduling_check_min_bw_alt_SOURCES) \ + $(test_ats_api_scheduling_destroy_address_SOURCES) \ + $(test_ats_api_scheduling_destroy_inbound_connection_SOURCES) \ + $(test_ats_api_scheduling_destroy_session_SOURCES) \ + $(test_ats_api_scheduling_init_SOURCES) \ + $(test_ats_api_scheduling_min_bw_SOURCES) \ + $(test_ats_api_scheduling_update_address_SOURCES) \ + $(test_ats_simplistic_SOURCES) \ + $(test_ats_simplistic_change_preference_SOURCES) \ + $(test_ats_simplistic_pref_aging_SOURCES) \ + $(test_ats_simplistic_switch_networks_SOURCES) DIST_SOURCES = $(libgnunetats_la_SOURCES) \ $(am__gnunet_service_ats_SOURCES_DIST) \ - $(am__perf_ats_mlp_SOURCES_DIST) \ - $(test_ats_api_reset_backoff_SOURCES) \ - $(test_ats_api_scheduling_SOURCES) \ - $(am__test_ats_mlp_SOURCES_DIST) \ - $(am__test_ats_mlp_averaging_SOURCES_DIST) + $(test_ats_api_performance_SOURCES) \ + $(test_ats_api_scheduling_add_address_SOURCES) \ + $(test_ats_api_scheduling_add_session_SOURCES) \ + $(test_ats_api_scheduling_block_and_reset_SOURCES) \ + $(test_ats_api_scheduling_check_min_bw_alt_SOURCES) \ + $(test_ats_api_scheduling_destroy_address_SOURCES) \ + $(test_ats_api_scheduling_destroy_inbound_connection_SOURCES) \ + $(test_ats_api_scheduling_destroy_session_SOURCES) \ + $(test_ats_api_scheduling_init_SOURCES) \ + $(test_ats_api_scheduling_min_bw_SOURCES) \ + $(test_ats_api_scheduling_update_address_SOURCES) \ + $(test_ats_simplistic_SOURCES) \ + $(test_ats_simplistic_change_preference_SOURCES) \ + $(test_ats_simplistic_pref_aging_SOURCES) \ + $(test_ats_simplistic_switch_networks_SOURCES) +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac DATA = $(pkgcfg_DATA) ETAGS = etags CTAGS = ctags @@ -246,6 +398,10 @@ EXEEXT = @EXEEXT@ EXT_LIBS = @EXT_LIBS@ EXT_LIB_PATH = @EXT_LIB_PATH@ FGREP = @FGREP@ +GLIB_CFLAGS = @GLIB_CFLAGS@ +GLIB_GENMARSHAL = @GLIB_GENMARSHAL@ +GLIB_LIBS = @GLIB_LIBS@ +GLIB_MKENUMS = @GLIB_MKENUMS@ GMSGFMT = @GMSGFMT@ GMSGFMT_015 = @GMSGFMT_015@ GNUNETDNS_GROUP = @GNUNETDNS_GROUP@ @@ -256,6 +412,7 @@ GN_LIBINTL = @GN_LIBINTL@ GN_LIB_LDFLAGS = @GN_LIB_LDFLAGS@ GN_PLUGIN_LDFLAGS = @GN_PLUGIN_LDFLAGS@ GN_USER_HOME_DIR = @GN_USER_HOME_DIR@ +GOBJECT_QUERY = @GOBJECT_QUERY@ GREP = @GREP@ HAVE_LIBUNISTRING = @HAVE_LIBUNISTRING@ INCLTDL = @INCLTDL@ @@ -278,6 +435,8 @@ LIBCURL_CPPFLAGS = @LIBCURL_CPPFLAGS@ LIBGCRYPT_CFLAGS = @LIBGCRYPT_CFLAGS@ LIBGCRYPT_CONFIG = @LIBGCRYPT_CONFIG@ LIBGCRYPT_LIBS = @LIBGCRYPT_LIBS@ +LIBGTOP_CFLAGS = @LIBGTOP_CFLAGS@ +LIBGTOP_LIBS = @LIBGTOP_LIBS@ LIBICONV = @LIBICONV@ LIBINTL = @LIBINTL@ LIBLTDL = @LIBLTDL@ @@ -299,6 +458,7 @@ LT_CONFIG_H = @LT_CONFIG_H@ LT_DLLOADERS = @LT_DLLOADERS@ LT_DLPREOPEN = @LT_DLPREOPEN@ MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ MKDIR_P = @MKDIR_P@ MONKEYPREFIX = @MONKEYPREFIX@ MSGFMT = @MSGFMT@ @@ -308,6 +468,7 @@ MYSQL_CPPFLAGS = @MYSQL_CPPFLAGS@ MYSQL_LDFLAGS = @MYSQL_LDFLAGS@ NM = @NM@ NMEDIT = @NMEDIT@ +NSS_DIR = @NSS_DIR@ OBJC = @OBJC@ OBJCDEPMODE = @OBJCDEPMODE@ OBJCFLAGS = @OBJCFLAGS@ @@ -323,6 +484,7 @@ PACKAGE_TARNAME = @PACKAGE_TARNAME@ PACKAGE_URL = @PACKAGE_URL@ PACKAGE_VERSION = @PACKAGE_VERSION@ PATH_SEPARATOR = @PATH_SEPARATOR@ +PKG_CONFIG = @PKG_CONFIG@ POSTGRES_CPPFLAGS = @POSTGRES_CPPFLAGS@ POSTGRES_LDFLAGS = @POSTGRES_LDFLAGS@ POSUB = @POSUB@ @@ -354,6 +516,7 @@ abs_builddir = @abs_builddir@ abs_srcdir = @abs_srcdir@ abs_top_builddir = @abs_top_builddir@ abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ ac_ct_CC = @ac_ct_CC@ ac_ct_CXX = @ac_ct_CXX@ ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ @@ -376,6 +539,7 @@ datarootdir = @datarootdir@ docdir = @docdir@ dvidir = @dvidir@ exec_prefix = @exec_prefix@ +gitcommand = @gitcommand@ host = @host@ host_alias = @host_alias@ host_cpu = @host_cpu@ @@ -386,10 +550,9 @@ includedir = @includedir@ infodir = @infodir@ install_sh = @install_sh@ libdir = @libdir@ -libexecdir = @libexecdir@ +libexecdir = $(pkglibdir)/libexec/ localedir = @localedir@ localstatedir = @localstatedir@ -lt_ECHO = @lt_ECHO@ ltdl_LIBOBJS = @ltdl_LIBOBJS@ ltdl_LTLIBOBJS = @ltdl_LTLIBOBJS@ mandir = @mandir@ @@ -407,6 +570,7 @@ sbindir = @sbindir@ sharedstatedir = @sharedstatedir@ srcdir = @srcdir@ subdirs = @subdirs@ +svnversioncommand = @svnversioncommand@ sys_symbol_underscore = @sys_symbol_underscore@ sysconfdir = @sysconfdir@ target = @target@ @@ -435,15 +599,17 @@ libgnunetats_la_SOURCES = \ ats_api_performance.c libgnunetats_la_LIBADD = \ - $(top_builddir)/src/util/libgnunetutil.la + $(top_builddir)/src/util/libgnunetutil.la \ + $(LTLIBINTL) libgnunetats_la_LDFLAGS = \ $(GN_LIB_LDFLAGS) \ - -version-info 2:0:2 + -version-info 4:0:0 gnunet_service_ats_SOURCES = \ gnunet-service-ats.c gnunet-service-ats.h\ gnunet-service-ats_addresses.c gnunet-service-ats_addresses.h \ + gnunet-service-ats_addresses_simplistic.c gnunet-service-ats_addresses_simplistic.h \ $(GN_MLP_SRC) \ gnunet-service-ats_performance.c gnunet-service-ats_performance.h \ gnunet-service-ats_scheduling.c gnunet-service-ats_scheduling.h \ @@ -452,70 +618,173 @@ gnunet_service_ats_SOURCES = \ gnunet_service_ats_LDADD = \ $(top_builddir)/src/statistics/libgnunetstatistics.la \ $(top_builddir)/src/util/libgnunetutil.la \ + libgnunetats.la \ $(GN_LIBGLPK) \ $(GN_LIBINTL) +gnunet_service_ats_DEPENDENCIES = \ + libgnunetats.la + +# $(GN_MLP_TEST) \ +# $(GN_MLP_TEST_AVG) \ +# $(GN_MLP_PERF) # test_ats_api_scheduling_get_type # test_ats_api_bandwidth_consumption @ENABLE_TEST_RUN_TRUE@TESTS = $(check_PROGRAMS) -@HAVE_LIBGLPK_TRUE@test_ats_mlp_SOURCES = \ -@HAVE_LIBGLPK_TRUE@ $(GN_MLP_SRC) \ -@HAVE_LIBGLPK_TRUE@ test_ats_mlp.c +test_ats_api_scheduling_init_SOURCES = \ + test_ats_api_scheduling_init.c \ + test_ats_api_common.c test_ats_api_common.h -@HAVE_LIBGLPK_TRUE@test_ats_mlp_LDADD = \ -@HAVE_LIBGLPK_TRUE@ $(GN_LIBGLPK) \ -@HAVE_LIBGLPK_TRUE@ $(top_builddir)/src/util/libgnunetutil.la \ -@HAVE_LIBGLPK_TRUE@ $(top_builddir)/src/statistics/libgnunetstatistics.la +test_ats_api_scheduling_init_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/ats/libgnunetats.la -@HAVE_LIBGLPK_TRUE@test_ats_mlp_averaging_SOURCES = \ -@HAVE_LIBGLPK_TRUE@ $(GN_MLP_SRC) \ -@HAVE_LIBGLPK_TRUE@ test_ats_mlp_averaging.c +test_ats_api_scheduling_add_address_SOURCES = \ + test_ats_api_scheduling_add_address.c \ + test_ats_api_common.c test_ats_api_common.h -@HAVE_LIBGLPK_TRUE@test_ats_mlp_averaging_LDADD = \ -@HAVE_LIBGLPK_TRUE@ $(GN_LIBGLPK) \ -@HAVE_LIBGLPK_TRUE@ $(top_builddir)/src/util/libgnunetutil.la \ -@HAVE_LIBGLPK_TRUE@ $(top_builddir)/src/statistics/libgnunetstatistics.la +test_ats_api_scheduling_add_address_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/ats/libgnunetats.la -@HAVE_LIBGLPK_TRUE@perf_ats_mlp_SOURCES = \ -@HAVE_LIBGLPK_TRUE@ $(GN_MLP_SRC) \ -@HAVE_LIBGLPK_TRUE@ perf_ats_mlp.c +test_ats_api_scheduling_add_session_SOURCES = \ + test_ats_api_scheduling_add_session.c test_ats_api_common.c -@HAVE_LIBGLPK_TRUE@perf_ats_mlp_LDADD = \ -@HAVE_LIBGLPK_TRUE@ $(GN_LIBGLPK) \ -@HAVE_LIBGLPK_TRUE@ $(top_builddir)/src/util/libgnunetutil.la \ -@HAVE_LIBGLPK_TRUE@ $(top_builddir)/src/statistics/libgnunetstatistics.la +test_ats_api_scheduling_add_session_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/ats/libgnunetats.la -test_ats_api_scheduling_SOURCES = \ - test_ats_api_scheduling.c +test_ats_api_scheduling_min_bw_SOURCES = \ + test_ats_api_scheduling_min_bw.c test_ats_api_common.c -test_ats_api_scheduling_LDADD = \ +test_ats_api_scheduling_min_bw_LDADD = \ $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/ats/libgnunetats.la -test_ats_api_reset_backoff_SOURCES = \ - test_ats_api_reset_backoff.c +test_ats_api_scheduling_check_min_bw_alt_SOURCES = \ + test_ats_api_scheduling_check_min_bw_alt.c test_ats_api_common.c + +test_ats_api_scheduling_check_min_bw_alt_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/ats/libgnunetats.la + +test_ats_api_scheduling_update_address_SOURCES = \ + test_ats_api_scheduling_update_address.c test_ats_api_common.c + +test_ats_api_scheduling_update_address_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/ats/libgnunetats.la + +test_ats_api_scheduling_destroy_address_SOURCES = \ + test_ats_api_scheduling_destroy_address.c test_ats_api_common.c + +test_ats_api_scheduling_destroy_address_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/ats/libgnunetats.la + +test_ats_api_scheduling_destroy_session_SOURCES = \ + test_ats_api_scheduling_destroy_session.c test_ats_api_common.c + +test_ats_api_scheduling_destroy_session_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/ats/libgnunetats.la + +test_ats_api_scheduling_destroy_inbound_connection_SOURCES = \ + test_ats_api_scheduling_destroy_inbound_connection.c test_ats_api_common.c + +test_ats_api_scheduling_destroy_inbound_connection_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/ats/libgnunetats.la + +test_ats_api_scheduling_block_and_reset_SOURCES = \ + test_ats_api_scheduling_block_and_reset.c test_ats_api_common.c + +test_ats_api_scheduling_block_and_reset_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/ats/libgnunetats.la + +test_ats_api_performance_SOURCES = \ + test_ats_api_performance.c + +test_ats_api_performance_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/hello/libgnunethello.la \ + $(top_builddir)/src/ats/libgnunetats.la + +test_ats_simplistic_SOURCES = \ + test_ats_simplistic.c test_ats_api_common.c + +test_ats_simplistic_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/hello/libgnunethello.la \ + $(top_builddir)/src/ats/libgnunetats.la + +test_ats_simplistic_switch_networks_SOURCES = \ + test_ats_simplistic_switch_networks.c test_ats_api_common.c -test_ats_api_reset_backoff_LDADD = \ +test_ats_simplistic_switch_networks_LDADD = \ $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/ats/libgnunetats.la + +test_ats_simplistic_change_preference_SOURCES = \ + test_ats_simplistic_change_preference.c test_ats_api_common.c + +test_ats_simplistic_change_preference_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/ats/libgnunetats.la + +test_ats_simplistic_pref_aging_SOURCES = \ + test_ats_simplistic_pref_aging.c test_ats_api_common.c + +test_ats_simplistic_pref_aging_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/ats/libgnunetats.la -#test_ats_api_scheduling_get_type_SOURCES = \ -# test_ats_api_scheduling_get_type.c -#test_ats_api_scheduling_get_type_LDADD = \ +#test_ats_mlp_SOURCES = \ +# $(GN_MLP_SRC) \ +# test_ats_mlp.c +#test_ats_mlp_LDADD = \ +# $(GN_LIBGLPK) \ # $(top_builddir)/src/util/libgnunetutil.la \ -# $(top_builddir)/src/ats/libgnunetats.la +# $(top_builddir)/src/statistics/libgnunetstatistics.la + +#test_ats_mlp_averaging_SOURCES = \ +# $(GN_MLP_SRC) \ +# test_ats_mlp_averaging.c +#test_ats_mlp_averaging_LDADD = \ +# $(GN_LIBGLPK) \ +# $(top_builddir)/src/util/libgnunetutil.la \ +# $(top_builddir)/src/statistics/libgnunetstatistics.la + +#perf_ats_mlp_SOURCES = \ +# $(GN_MLP_SRC) \ +# perf_ats_mlp.c +#perf_ats_mlp_LDADD = \ +# $(GN_LIBGLPK) \ +# $(top_builddir)/src/util/libgnunetutil.la \ +# $(top_builddir)/src/statistics/libgnunetstatistics.la #test_ats_api_bandwidth_consumption_SOURCES = \ # test_ats_api_bandwidth_consumption.c #test_ats_api_bandwidth_consumption_LDADD = \ # $(top_builddir)/src/util/libgnunetutil.la \ -# $(top_builddir)/src/ats/libgnunetats.la - -#test_ats_api_update_address_SOURCES = \ -# test_ats_api_update_address.c -#test_ats_api_update_address_LDADD = \ -# $(top_builddir)/src/util/libgnunetutil.la \ +# $(top_builddir)/src/testing/libgnunettesting.la \ # $(top_builddir)/src/ats/libgnunetats.la EXTRA_DIST = \ ats.h \ @@ -559,7 +828,6 @@ ats.conf: $(top_builddir)/config.status $(srcdir)/ats.conf.in cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ install-libLTLIBRARIES: $(lib_LTLIBRARIES) @$(NORMAL_INSTALL) - test -z "$(libdir)" || $(MKDIR_P) "$(DESTDIR)$(libdir)" @list='$(lib_LTLIBRARIES)'; test -n "$(libdir)" || list=; \ list2=; for p in $$list; do \ if test -f $$p; then \ @@ -567,6 +835,8 @@ install-libLTLIBRARIES: $(lib_LTLIBRARIES) else :; fi; \ done; \ test -z "$$list2" || { \ + echo " $(MKDIR_P) '$(DESTDIR)$(libdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libdir)" || exit 1; \ echo " $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 '$(DESTDIR)$(libdir)'"; \ $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 "$(DESTDIR)$(libdir)"; \ } @@ -588,12 +858,24 @@ clean-libLTLIBRARIES: echo "rm -f \"$${dir}/so_locations\""; \ rm -f "$${dir}/so_locations"; \ done -libgnunetats.la: $(libgnunetats_la_OBJECTS) $(libgnunetats_la_DEPENDENCIES) +libgnunetats.la: $(libgnunetats_la_OBJECTS) $(libgnunetats_la_DEPENDENCIES) $(EXTRA_libgnunetats_la_DEPENDENCIES) $(AM_V_CCLD)$(libgnunetats_la_LINK) -rpath $(libdir) $(libgnunetats_la_OBJECTS) $(libgnunetats_la_LIBADD) $(LIBS) -install-binPROGRAMS: $(bin_PROGRAMS) + +clean-checkPROGRAMS: + @list='$(check_PROGRAMS)'; test -n "$$list" || exit 0; \ + echo " rm -f" $$list; \ + rm -f $$list || exit $$?; \ + test -n "$(EXEEXT)" || exit 0; \ + list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ + echo " rm -f" $$list; \ + rm -f $$list +install-libexecPROGRAMS: $(libexec_PROGRAMS) @$(NORMAL_INSTALL) - test -z "$(bindir)" || $(MKDIR_P) "$(DESTDIR)$(bindir)" - @list='$(bin_PROGRAMS)'; test -n "$(bindir)" || list=; \ + @list='$(libexec_PROGRAMS)'; test -n "$(libexecdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(libexecdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libexecdir)" || exit 1; \ + fi; \ for p in $$list; do echo "$$p $$p"; done | \ sed 's/$(EXEEXT)$$//' | \ while read p p1; do if test -f $$p || test -f $$p1; \ @@ -610,56 +892,77 @@ install-binPROGRAMS: $(bin_PROGRAMS) while read type dir files; do \ if test "$$dir" = .; then dir=; else dir=/$$dir; fi; \ test -z "$$files" || { \ - echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files '$(DESTDIR)$(bindir)$$dir'"; \ - $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files "$(DESTDIR)$(bindir)$$dir" || exit $$?; \ + echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files '$(DESTDIR)$(libexecdir)$$dir'"; \ + $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files "$(DESTDIR)$(libexecdir)$$dir" || exit $$?; \ } \ ; done -uninstall-binPROGRAMS: +uninstall-libexecPROGRAMS: @$(NORMAL_UNINSTALL) - @list='$(bin_PROGRAMS)'; test -n "$(bindir)" || list=; \ + @list='$(libexec_PROGRAMS)'; test -n "$(libexecdir)" || list=; \ files=`for p in $$list; do echo "$$p"; done | \ sed -e 'h;s,^.*/,,;s/$(EXEEXT)$$//;$(transform)' \ -e 's/$$/$(EXEEXT)/' `; \ test -n "$$list" || exit 0; \ - echo " ( cd '$(DESTDIR)$(bindir)' && rm -f" $$files ")"; \ - cd "$(DESTDIR)$(bindir)" && rm -f $$files + echo " ( cd '$(DESTDIR)$(libexecdir)' && rm -f" $$files ")"; \ + cd "$(DESTDIR)$(libexecdir)" && rm -f $$files -clean-binPROGRAMS: - @list='$(bin_PROGRAMS)'; test -n "$$list" || exit 0; \ +clean-libexecPROGRAMS: + @list='$(libexec_PROGRAMS)'; test -n "$$list" || exit 0; \ echo " rm -f" $$list; \ rm -f $$list || exit $$?; \ test -n "$(EXEEXT)" || exit 0; \ list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ echo " rm -f" $$list; \ rm -f $$list - -clean-checkPROGRAMS: - @list='$(check_PROGRAMS)'; test -n "$$list" || exit 0; \ - echo " rm -f" $$list; \ - rm -f $$list || exit $$?; \ - test -n "$(EXEEXT)" || exit 0; \ - list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ - echo " rm -f" $$list; \ - rm -f $$list -gnunet-service-ats$(EXEEXT): $(gnunet_service_ats_OBJECTS) $(gnunet_service_ats_DEPENDENCIES) +gnunet-service-ats$(EXEEXT): $(gnunet_service_ats_OBJECTS) $(gnunet_service_ats_DEPENDENCIES) $(EXTRA_gnunet_service_ats_DEPENDENCIES) @rm -f gnunet-service-ats$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_service_ats_OBJECTS) $(gnunet_service_ats_LDADD) $(LIBS) -perf_ats_mlp$(EXEEXT): $(perf_ats_mlp_OBJECTS) $(perf_ats_mlp_DEPENDENCIES) - @rm -f perf_ats_mlp$(EXEEXT) - $(AM_V_CCLD)$(LINK) $(perf_ats_mlp_OBJECTS) $(perf_ats_mlp_LDADD) $(LIBS) -test_ats_api_reset_backoff$(EXEEXT): $(test_ats_api_reset_backoff_OBJECTS) $(test_ats_api_reset_backoff_DEPENDENCIES) - @rm -f test_ats_api_reset_backoff$(EXEEXT) - $(AM_V_CCLD)$(LINK) $(test_ats_api_reset_backoff_OBJECTS) $(test_ats_api_reset_backoff_LDADD) $(LIBS) -test_ats_api_scheduling$(EXEEXT): $(test_ats_api_scheduling_OBJECTS) $(test_ats_api_scheduling_DEPENDENCIES) - @rm -f test_ats_api_scheduling$(EXEEXT) - $(AM_V_CCLD)$(LINK) $(test_ats_api_scheduling_OBJECTS) $(test_ats_api_scheduling_LDADD) $(LIBS) -test_ats_mlp$(EXEEXT): $(test_ats_mlp_OBJECTS) $(test_ats_mlp_DEPENDENCIES) - @rm -f test_ats_mlp$(EXEEXT) - $(AM_V_CCLD)$(LINK) $(test_ats_mlp_OBJECTS) $(test_ats_mlp_LDADD) $(LIBS) -test_ats_mlp_averaging$(EXEEXT): $(test_ats_mlp_averaging_OBJECTS) $(test_ats_mlp_averaging_DEPENDENCIES) - @rm -f test_ats_mlp_averaging$(EXEEXT) - $(AM_V_CCLD)$(LINK) $(test_ats_mlp_averaging_OBJECTS) $(test_ats_mlp_averaging_LDADD) $(LIBS) +test_ats_api_performance$(EXEEXT): $(test_ats_api_performance_OBJECTS) $(test_ats_api_performance_DEPENDENCIES) $(EXTRA_test_ats_api_performance_DEPENDENCIES) + @rm -f test_ats_api_performance$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_ats_api_performance_OBJECTS) $(test_ats_api_performance_LDADD) $(LIBS) +test_ats_api_scheduling_add_address$(EXEEXT): $(test_ats_api_scheduling_add_address_OBJECTS) $(test_ats_api_scheduling_add_address_DEPENDENCIES) $(EXTRA_test_ats_api_scheduling_add_address_DEPENDENCIES) + @rm -f test_ats_api_scheduling_add_address$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_ats_api_scheduling_add_address_OBJECTS) $(test_ats_api_scheduling_add_address_LDADD) $(LIBS) +test_ats_api_scheduling_add_session$(EXEEXT): $(test_ats_api_scheduling_add_session_OBJECTS) $(test_ats_api_scheduling_add_session_DEPENDENCIES) $(EXTRA_test_ats_api_scheduling_add_session_DEPENDENCIES) + @rm -f test_ats_api_scheduling_add_session$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_ats_api_scheduling_add_session_OBJECTS) $(test_ats_api_scheduling_add_session_LDADD) $(LIBS) +test_ats_api_scheduling_block_and_reset$(EXEEXT): $(test_ats_api_scheduling_block_and_reset_OBJECTS) $(test_ats_api_scheduling_block_and_reset_DEPENDENCIES) $(EXTRA_test_ats_api_scheduling_block_and_reset_DEPENDENCIES) + @rm -f test_ats_api_scheduling_block_and_reset$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_ats_api_scheduling_block_and_reset_OBJECTS) $(test_ats_api_scheduling_block_and_reset_LDADD) $(LIBS) +test_ats_api_scheduling_check_min_bw_alt$(EXEEXT): $(test_ats_api_scheduling_check_min_bw_alt_OBJECTS) $(test_ats_api_scheduling_check_min_bw_alt_DEPENDENCIES) $(EXTRA_test_ats_api_scheduling_check_min_bw_alt_DEPENDENCIES) + @rm -f test_ats_api_scheduling_check_min_bw_alt$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_ats_api_scheduling_check_min_bw_alt_OBJECTS) $(test_ats_api_scheduling_check_min_bw_alt_LDADD) $(LIBS) +test_ats_api_scheduling_destroy_address$(EXEEXT): $(test_ats_api_scheduling_destroy_address_OBJECTS) $(test_ats_api_scheduling_destroy_address_DEPENDENCIES) $(EXTRA_test_ats_api_scheduling_destroy_address_DEPENDENCIES) + @rm -f test_ats_api_scheduling_destroy_address$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_ats_api_scheduling_destroy_address_OBJECTS) $(test_ats_api_scheduling_destroy_address_LDADD) $(LIBS) +test_ats_api_scheduling_destroy_inbound_connection$(EXEEXT): $(test_ats_api_scheduling_destroy_inbound_connection_OBJECTS) $(test_ats_api_scheduling_destroy_inbound_connection_DEPENDENCIES) $(EXTRA_test_ats_api_scheduling_destroy_inbound_connection_DEPENDENCIES) + @rm -f test_ats_api_scheduling_destroy_inbound_connection$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_ats_api_scheduling_destroy_inbound_connection_OBJECTS) $(test_ats_api_scheduling_destroy_inbound_connection_LDADD) $(LIBS) +test_ats_api_scheduling_destroy_session$(EXEEXT): $(test_ats_api_scheduling_destroy_session_OBJECTS) $(test_ats_api_scheduling_destroy_session_DEPENDENCIES) $(EXTRA_test_ats_api_scheduling_destroy_session_DEPENDENCIES) + @rm -f test_ats_api_scheduling_destroy_session$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_ats_api_scheduling_destroy_session_OBJECTS) $(test_ats_api_scheduling_destroy_session_LDADD) $(LIBS) +test_ats_api_scheduling_init$(EXEEXT): $(test_ats_api_scheduling_init_OBJECTS) $(test_ats_api_scheduling_init_DEPENDENCIES) $(EXTRA_test_ats_api_scheduling_init_DEPENDENCIES) + @rm -f test_ats_api_scheduling_init$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_ats_api_scheduling_init_OBJECTS) $(test_ats_api_scheduling_init_LDADD) $(LIBS) +test_ats_api_scheduling_min_bw$(EXEEXT): $(test_ats_api_scheduling_min_bw_OBJECTS) $(test_ats_api_scheduling_min_bw_DEPENDENCIES) $(EXTRA_test_ats_api_scheduling_min_bw_DEPENDENCIES) + @rm -f test_ats_api_scheduling_min_bw$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_ats_api_scheduling_min_bw_OBJECTS) $(test_ats_api_scheduling_min_bw_LDADD) $(LIBS) +test_ats_api_scheduling_update_address$(EXEEXT): $(test_ats_api_scheduling_update_address_OBJECTS) $(test_ats_api_scheduling_update_address_DEPENDENCIES) $(EXTRA_test_ats_api_scheduling_update_address_DEPENDENCIES) + @rm -f test_ats_api_scheduling_update_address$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_ats_api_scheduling_update_address_OBJECTS) $(test_ats_api_scheduling_update_address_LDADD) $(LIBS) +test_ats_simplistic$(EXEEXT): $(test_ats_simplistic_OBJECTS) $(test_ats_simplistic_DEPENDENCIES) $(EXTRA_test_ats_simplistic_DEPENDENCIES) + @rm -f test_ats_simplistic$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_ats_simplistic_OBJECTS) $(test_ats_simplistic_LDADD) $(LIBS) +test_ats_simplistic_change_preference$(EXEEXT): $(test_ats_simplistic_change_preference_OBJECTS) $(test_ats_simplistic_change_preference_DEPENDENCIES) $(EXTRA_test_ats_simplistic_change_preference_DEPENDENCIES) + @rm -f test_ats_simplistic_change_preference$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_ats_simplistic_change_preference_OBJECTS) $(test_ats_simplistic_change_preference_LDADD) $(LIBS) +test_ats_simplistic_pref_aging$(EXEEXT): $(test_ats_simplistic_pref_aging_OBJECTS) $(test_ats_simplistic_pref_aging_DEPENDENCIES) $(EXTRA_test_ats_simplistic_pref_aging_DEPENDENCIES) + @rm -f test_ats_simplistic_pref_aging$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_ats_simplistic_pref_aging_OBJECTS) $(test_ats_simplistic_pref_aging_LDADD) $(LIBS) +test_ats_simplistic_switch_networks$(EXEEXT): $(test_ats_simplistic_switch_networks_OBJECTS) $(test_ats_simplistic_switch_networks_DEPENDENCIES) $(EXTRA_test_ats_simplistic_switch_networks_DEPENDENCIES) + @rm -f test_ats_simplistic_switch_networks$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_ats_simplistic_switch_networks_OBJECTS) $(test_ats_simplistic_switch_networks_LDADD) $(LIBS) mostlyclean-compile: -rm -f *.$(OBJEXT) @@ -672,38 +975,47 @@ distclean-compile: @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-service-ats.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-service-ats_addresses.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-service-ats_addresses_mlp.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-service-ats_addresses_simplistic.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-service-ats_performance.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-service-ats_reservations.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-service-ats_scheduling.Po@am__quote@ -@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/perf_ats_mlp.Po@am__quote@ -@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_ats_api_reset_backoff.Po@am__quote@ -@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_ats_api_scheduling.Po@am__quote@ -@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_ats_mlp.Po@am__quote@ -@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_ats_mlp_averaging.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_ats_api_common.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_ats_api_performance.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_ats_api_scheduling_add_address.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_ats_api_scheduling_add_session.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_ats_api_scheduling_block_and_reset.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_ats_api_scheduling_check_min_bw_alt.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_ats_api_scheduling_destroy_address.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_ats_api_scheduling_destroy_inbound_connection.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_ats_api_scheduling_destroy_session.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_ats_api_scheduling_init.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_ats_api_scheduling_min_bw.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_ats_api_scheduling_update_address.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_ats_simplistic.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_ats_simplistic_change_preference.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_ats_simplistic_pref_aging.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_ats_simplistic_switch_networks.Po@am__quote@ .c.o: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c $< .c.obj: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'` @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c `$(CYGPATH_W) '$<'` +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c `$(CYGPATH_W) '$<'` .c.lo: @am__fastdepCC_TRUE@ $(AM_V_CC)$(LTCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LTCOMPILE) -c -o $@ $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LTCOMPILE) -c -o $@ $< mostlyclean-libtool: -rm -f *.lo @@ -712,8 +1024,11 @@ clean-libtool: -rm -rf .libs _libs install-pkgcfgDATA: $(pkgcfg_DATA) @$(NORMAL_INSTALL) - test -z "$(pkgcfgdir)" || $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" @list='$(pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(pkgcfgdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" || exit 1; \ + fi; \ for p in $$list; do \ if test -f "$$p"; then d=; else d="$(srcdir)/"; fi; \ echo "$$d$$p"; \ @@ -727,9 +1042,7 @@ uninstall-pkgcfgDATA: @$(NORMAL_UNINSTALL) @list='$(pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ files=`for p in $$list; do echo $$p; done | sed -e 's|^.*/||'`; \ - test -n "$$files" || exit 0; \ - echo " ( cd '$(DESTDIR)$(pkgcfgdir)' && rm -f" $$files ")"; \ - cd "$(DESTDIR)$(pkgcfgdir)" && rm -f $$files + dir='$(DESTDIR)$(pkgcfgdir)'; $(am__uninstall_files_from_dir) ID: $(HEADERS) $(SOURCES) $(LISP) $(TAGS_FILES) list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ @@ -864,14 +1177,15 @@ check-TESTS: $(TESTS) fi; \ dashes=`echo "$$dashes" | sed s/./=/g`; \ if test "$$failed" -eq 0; then \ - echo "$$grn$$dashes"; \ + col="$$grn"; \ else \ - echo "$$red$$dashes"; \ + col="$$red"; \ fi; \ - echo "$$banner"; \ - test -z "$$skipped" || echo "$$skipped"; \ - test -z "$$report" || echo "$$report"; \ - echo "$$dashes$$std"; \ + echo "$${col}$$dashes$${std}"; \ + echo "$${col}$$banner$${std}"; \ + test -z "$$skipped" || echo "$${col}$$skipped$${std}"; \ + test -z "$$report" || echo "$${col}$$report$${std}"; \ + echo "$${col}$$dashes$${std}"; \ test "$$failed" -eq 0; \ else :; fi @@ -910,10 +1224,8 @@ check-am: all-am $(MAKE) $(AM_MAKEFLAGS) check-TESTS check: check-am all-am: Makefile $(LTLIBRARIES) $(PROGRAMS) $(DATA) -install-binPROGRAMS: install-libLTLIBRARIES - installdirs: - for dir in "$(DESTDIR)$(libdir)" "$(DESTDIR)$(bindir)" "$(DESTDIR)$(pkgcfgdir)"; do \ + for dir in "$(DESTDIR)$(libdir)" "$(DESTDIR)$(libexecdir)" "$(DESTDIR)$(pkgcfgdir)"; do \ test -z "$$dir" || $(MKDIR_P) "$$dir"; \ done install: install-am @@ -926,10 +1238,15 @@ install-am: all-am installcheck: installcheck-am install-strip: - $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ - install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ - `test -z '$(STRIP)' || \ - echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi mostlyclean-generic: clean-generic: @@ -943,8 +1260,8 @@ maintainer-clean-generic: @echo "it deletes files that may require special tools to rebuild." clean: clean-am -clean-am: clean-binPROGRAMS clean-checkPROGRAMS clean-generic \ - clean-libLTLIBRARIES clean-libtool mostlyclean-am +clean-am: clean-checkPROGRAMS clean-generic clean-libLTLIBRARIES \ + clean-libexecPROGRAMS clean-libtool mostlyclean-am distclean: distclean-am -rm -rf ./$(DEPDIR) @@ -970,7 +1287,7 @@ install-dvi: install-dvi-am install-dvi-am: -install-exec-am: install-binPROGRAMS install-libLTLIBRARIES +install-exec-am: install-libLTLIBRARIES install-libexecPROGRAMS install-html: install-html-am @@ -1010,27 +1327,27 @@ ps: ps-am ps-am: -uninstall-am: uninstall-binPROGRAMS uninstall-libLTLIBRARIES \ +uninstall-am: uninstall-libLTLIBRARIES uninstall-libexecPROGRAMS \ uninstall-pkgcfgDATA .MAKE: check-am install-am install-strip .PHONY: CTAGS GTAGS all all-am check check-TESTS check-am clean \ - clean-binPROGRAMS clean-checkPROGRAMS clean-generic \ - clean-libLTLIBRARIES clean-libtool ctags distclean \ + clean-checkPROGRAMS clean-generic clean-libLTLIBRARIES \ + clean-libexecPROGRAMS clean-libtool ctags distclean \ distclean-compile distclean-generic distclean-libtool \ distclean-tags distdir dvi dvi-am html html-am info info-am \ - install install-am install-binPROGRAMS install-data \ - install-data-am install-dvi install-dvi-am install-exec \ - install-exec-am install-html install-html-am install-info \ - install-info-am install-libLTLIBRARIES install-man install-pdf \ - install-pdf-am install-pkgcfgDATA install-ps install-ps-am \ - install-strip installcheck installcheck-am installdirs \ - maintainer-clean maintainer-clean-generic mostlyclean \ - mostlyclean-compile mostlyclean-generic mostlyclean-libtool \ - pdf pdf-am ps ps-am tags uninstall uninstall-am \ - uninstall-binPROGRAMS uninstall-libLTLIBRARIES \ - uninstall-pkgcfgDATA + install install-am install-data install-data-am install-dvi \ + install-dvi-am install-exec install-exec-am install-html \ + install-html-am install-info install-info-am \ + install-libLTLIBRARIES install-libexecPROGRAMS install-man \ + install-pdf install-pdf-am install-pkgcfgDATA install-ps \ + install-ps-am install-strip installcheck installcheck-am \ + installdirs maintainer-clean maintainer-clean-generic \ + mostlyclean mostlyclean-compile mostlyclean-generic \ + mostlyclean-libtool pdf pdf-am ps ps-am tags uninstall \ + uninstall-am uninstall-libLTLIBRARIES \ + uninstall-libexecPROGRAMS uninstall-pkgcfgDATA # Tell versions [3.59,3.63) of GNU make to not export all variables. diff --git a/src/ats/ats.conf.in b/src/ats/ats.conf.in index f81016e..bdc064e 100644 --- a/src/ats/ats.conf.in +++ b/src/ats/ats.conf.in @@ -3,7 +3,6 @@ AUTOSTART = YES @UNIXONLY@ PORT = 2098 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-ats ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -11,9 +10,12 @@ UNIXPATH = /tmp/gnunet-service-ats.sock UNIX_MATCH_UID = YES UNIX_MATCH_GID = YES -# Enable MLP mode (default: NO) -MLP = NO +# Designated assigment mode: simplistic / MLP +MODE = simplistic + # Network specific inbound/outbound quotas +UNSPECIFIED_QUOTA_IN = 64 KiB +UNSPECIFIED_QUOTA_OUT = 64 KiB # LOOPBACK LOOPBACK_QUOTA_IN = unlimited LOOPBACK_QUOTA_OUT = unlimited @@ -28,6 +30,13 @@ WLAN_QUOTA_IN = 1 MiB WLAN_QUOTA_OUT = 1 MiB # ATS options + +# MLP specific settings +# MAX_DURATION = 3 s +# MAX_ITERATIONS = 1024 + + + DUMP_MLP = NO DUMP_SOLUTION = NO DUMP_OVERWRITE = NO diff --git a/src/ats/ats.h b/src/ats/ats.h index f4c3d9f..70b8826 100644 --- a/src/ats/ats.h +++ b/src/ats/ats.h @@ -170,6 +170,10 @@ struct PeerInformationMessage uint32_t ats_count GNUNET_PACKED; + uint32_t address_active GNUNET_PACKED; + + uint32_t id GNUNET_PACKED; + struct GNUNET_PeerIdentity peer; uint16_t address_length GNUNET_PACKED; @@ -188,6 +192,17 @@ struct PeerInformationMessage }; +struct AddressListRequestMessage +{ + struct GNUNET_MessageHeader header; + + uint32_t id GNUNET_PACKED; + + int32_t all GNUNET_PACKED; + + struct GNUNET_PeerIdentity peer; +}; + struct ReservationRequestMessage { diff --git a/src/ats/ats_api_performance.c b/src/ats/ats_api_performance.c index c98e1c2..25b4926 100644 --- a/src/ats/ats_api_performance.c +++ b/src/ats/ats_api_performance.c @@ -105,6 +105,58 @@ struct GNUNET_ATS_ReservationContext }; +/** + * Linked list of pending reservations. + */ +struct GNUNET_ATS_AddressListHandle +{ + + /** + * Kept in a DLL. + */ + struct GNUNET_ATS_AddressListHandle *next; + + /** + * Kept in a DLL. + */ + struct GNUNET_ATS_AddressListHandle *prev; + + /** + * Performance handle + */ + struct GNUNET_ATS_PerformanceHandle *ph; + + /** + * Callback + */ + GNUNET_ATS_PeerInformationCallback cb; + + /** + * Callback closure + */ + void *cb_cls; + + /** + * Target peer. + */ + struct GNUNET_PeerIdentity peer; + + /** + * Return all or specific peer only + */ + int all_peers; + + /** + * Return all or used address only + */ + int all_addresses; + + /** + * Request multiplexing + */ + uint32_t id; +}; + /** * ATS Handle to obtain and/or modify performance information. */ @@ -151,6 +203,16 @@ struct GNUNET_ATS_PerformanceHandle */ struct GNUNET_ATS_ReservationContext *reservation_tail; + /** + * Head of linked list of pending address list requests. + */ + struct GNUNET_ATS_AddressListHandle *addresslist_head; + + /** + * Tail of linked list of pending address list requests. + */ + struct GNUNET_ATS_AddressListHandle *addresslist_tail; + /** * Current request for transmission to ATS. */ @@ -161,6 +223,10 @@ struct GNUNET_ATS_PerformanceHandle */ GNUNET_SCHEDULER_TaskIdentifier task; + /** + * Request multiplexing + */ + uint32_t id; }; @@ -276,16 +342,12 @@ process_pi_message (struct GNUNET_ATS_PerformanceHandle *ph, uint16_t plugin_name_length; uint32_t ats_count; - if (ph->infocb == NULL) - { - GNUNET_break (0); - return GNUNET_SYSERR; - } if (ntohs (msg->size) < sizeof (struct PeerInformationMessage)) { GNUNET_break (0); return GNUNET_SYSERR; } + pi = (const struct PeerInformationMessage *) msg; ats_count = ntohl (pi->ats_count); plugin_address_length = ntohs (pi->address_length); @@ -303,6 +365,11 @@ process_pi_message (struct GNUNET_ATS_PerformanceHandle *ph, GNUNET_break (0); return GNUNET_SYSERR; } + if (ph->infocb == NULL) + { + return GNUNET_OK; + } + address.peer = pi->peer; address.address = plugin_address; address.address_length = plugin_address_length; @@ -363,6 +430,110 @@ process_rr_message (struct GNUNET_ATS_PerformanceHandle *ph, } +/** + * We received a reservation result message. Validate and process it. + * + * @param ph our context with the callback + * @param msg the message + * @return GNUNET_OK if the message was well-formed + */ +static int +process_ar_message (struct GNUNET_ATS_PerformanceHandle *ph, + const struct GNUNET_MessageHeader *msg) +{ + const struct PeerInformationMessage *pi; + struct GNUNET_ATS_AddressListHandle *alh; + struct GNUNET_ATS_AddressListHandle *next; + const struct GNUNET_ATS_Information *atsi; + const char *plugin_address; + const char *plugin_name; + struct GNUNET_HELLO_Address address; + struct GNUNET_PeerIdentity allzeros; + struct GNUNET_BANDWIDTH_Value32NBO bandwidth_zero; + uint16_t plugin_address_length; + uint16_t plugin_name_length; + uint32_t ats_count; + uint32_t active; + uint32_t id; + + if (ntohs (msg->size) < sizeof (struct PeerInformationMessage)) + { + GNUNET_break (0); + return GNUNET_SYSERR; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + _("Received %s message\n"), "ATS_ADDRESSLIST_RESPONSE"); + + pi = (const struct PeerInformationMessage *) msg; + id = ntohl (pi->id); + ats_count = ntohl (pi->ats_count); + active = ntohl (pi->address_active); + plugin_address_length = ntohs (pi->address_length); + plugin_name_length = ntohs (pi->plugin_name_length); + atsi = (const struct GNUNET_ATS_Information *) &pi[1]; + plugin_address = (const char *) &atsi[ats_count]; + plugin_name = &plugin_address[plugin_address_length]; + if ((plugin_address_length + plugin_name_length + + ats_count * sizeof (struct GNUNET_ATS_Information) + + sizeof (struct PeerInformationMessage) != ntohs (msg->size)) || + (ats_count > + GNUNET_SERVER_MAX_MESSAGE_SIZE / sizeof (struct GNUNET_ATS_Information)) + || (plugin_name[plugin_name_length - 1] != '\0')) + { + GNUNET_break (0); + return GNUNET_SYSERR; + } + + next = ph->addresslist_head; + while (NULL != (alh = next)) + { + next = alh->next; + if (alh->id == id) + break; + } + if (NULL == alh) + { + /* was canceled */ + return GNUNET_SYSERR; + } + + memset (&allzeros, '\0', sizeof (allzeros)); + if ((0 == memcmp (&allzeros, &pi->peer, sizeof (allzeros))) && + (0 == plugin_name_length) && + (0 == plugin_address_length) && + (0 == ats_count)) + { + /* Done */ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + _("Received last message for %s \n"), "ATS_ADDRESSLIST_RESPONSE"); + bandwidth_zero.value__ = htonl (0); + if (NULL != alh->cb) + alh->cb (ph->infocb_cls, + NULL, + bandwidth_zero, bandwidth_zero, + NULL, 0); + GNUNET_CONTAINER_DLL_remove (ph->addresslist_head, ph->addresslist_tail, alh); + GNUNET_free (alh); + return GNUNET_OK; + } + + address.peer = pi->peer; + address.address = plugin_address; + address.address_length = plugin_address_length; + address.transport_name = plugin_name; + + if ((GNUNET_YES == alh->all_addresses) || (GNUNET_YES == active)) + { + if (NULL != alh->cb) + alh->cb (ph->infocb_cls, + &address, + pi->bandwidth_out, pi->bandwidth_in, + atsi, ats_count); + } + return GNUNET_OK; +} + + /** * Type of a function to call when we receive a message * from the service. @@ -387,6 +558,10 @@ process_ats_message (void *cls, const struct GNUNET_MessageHeader *msg) if (GNUNET_OK != process_rr_message (ph, msg)) goto reconnect; break; + case GNUNET_MESSAGE_TYPE_ATS_ADDRESSLIST_RESPONSE: + if (GNUNET_OK != process_ar_message (ph, msg)) + goto reconnect; + break; default: GNUNET_break (0); goto reconnect; @@ -395,6 +570,11 @@ process_ats_message (void *cls, const struct GNUNET_MessageHeader *msg) GNUNET_TIME_UNIT_FOREVER_REL); return; reconnect: + if (NULL != ph->th) + { + GNUNET_CLIENT_notify_transmit_ready_cancel (ph->th); + ph->th = NULL; + } GNUNET_CLIENT_disconnect (ph->client); ph->client = NULL; ph->task = @@ -458,6 +638,7 @@ GNUNET_ATS_performance_init (const struct GNUNET_CONFIGURATION_Handle *cfg, ph->cfg = cfg; ph->infocb = infocb; ph->infocb_cls = infocb_cls; + ph->id = 0; reconnect (ph); return ph; } @@ -473,12 +654,19 @@ GNUNET_ATS_performance_done (struct GNUNET_ATS_PerformanceHandle *ph) { struct PendingMessage *p; struct GNUNET_ATS_ReservationContext *rc; + struct GNUNET_ATS_AddressListHandle *alh; while (NULL != (p = ph->pending_head)) { GNUNET_CONTAINER_DLL_remove (ph->pending_head, ph->pending_tail, p); GNUNET_free (p); } + while (NULL != (alh = ph->addresslist_head)) + { + GNUNET_CONTAINER_DLL_remove (ph->addresslist_head, ph->addresslist_tail, + alh); + GNUNET_free (alh); + } while (NULL != (rc = ph->reservation_head)) { GNUNET_CONTAINER_DLL_remove (ph->reservation_head, ph->reservation_tail, @@ -560,6 +748,102 @@ GNUNET_ATS_reserve_bandwidth_cancel (struct GNUNET_ATS_ReservationContext *rc) rc->rcb = NULL; } +/** + * Get information about addresses known to the ATS subsystem. + * + * @param handle the performance handle to use + * @param peer peer idm can be NULL for all peers + * @param all GNUNET_YES to get information about all addresses or GNUNET_NO to + * get only address currently used + * @param infocb callback to call with the addresses, + * will callback with address == NULL when done + * @param infocb_cls closure for infocb + * @return ats performance context + */ +struct GNUNET_ATS_AddressListHandle* +GNUNET_ATS_performance_list_addresses (struct GNUNET_ATS_PerformanceHandle *handle, + const struct GNUNET_PeerIdentity *peer, + int all, + GNUNET_ATS_PeerInformationCallback infocb, + void *infocb_cls) +{ + struct GNUNET_ATS_AddressListHandle *alh; + struct PendingMessage *p; + struct AddressListRequestMessage *m; + + GNUNET_assert (NULL != handle); + if (NULL == infocb) + return NULL; + + alh = GNUNET_malloc (sizeof (struct GNUNET_ATS_AddressListHandle)); + alh->id = handle->id; + handle->id ++; + alh->cb = infocb; + alh->cb_cls = infocb_cls; + alh->ph = handle; + alh->all_addresses = all; + if (NULL == peer) + alh->all_peers = GNUNET_YES; + else + { + alh->all_peers = GNUNET_NO; + alh->peer = (*peer); + } + + GNUNET_CONTAINER_DLL_insert (handle->addresslist_head, handle->addresslist_tail, alh); + + p = GNUNET_malloc (sizeof (struct PendingMessage) + + sizeof (struct AddressListRequestMessage)); + p->size = sizeof (struct AddressListRequestMessage); + m = (struct AddressListRequestMessage *) &p[1]; + m->header.type = htons (GNUNET_MESSAGE_TYPE_ATS_ADDRESSLIST_REQUEST); + m->header.size = htons (sizeof (struct AddressListRequestMessage)); + m->all = htonl (all); + m->id = htonl (alh->id); + if (NULL != peer) + m->peer = *peer; + else + { + memset (&m->peer, '\0', sizeof (struct GNUNET_PeerIdentity)); + } + GNUNET_CONTAINER_DLL_insert_tail (handle->pending_head, handle->pending_tail, p); + + do_transmit (handle); + + return alh; +} + + +/** + * Cancel a pending address listing operation + * + * @param handle the GNUNET_ATS_AddressListHandle handle to cancel + */ +void +GNUNET_ATS_performance_list_addresses_cancel (struct GNUNET_ATS_AddressListHandle *handle) +{ + GNUNET_assert (NULL != handle); + + GNUNET_CONTAINER_DLL_remove (handle->ph->addresslist_head, handle->ph->addresslist_tail, handle); + GNUNET_free (handle); +} + + +/** + * Convert a GNUNET_ATS_PreferenceType to a string + * + * @param type the preference type + * @return a string or NULL if invalid + */ +const char * +GNUNET_ATS_print_preference_type (uint32_t type) +{ + char *prefs[GNUNET_ATS_PreferenceCount] = GNUNET_ATS_PreferenceTypeString; + if (type < GNUNET_ATS_PreferenceCount) + return prefs[type]; + return NULL; +} + /** * Change preferences for the given peer. Preference changes are forgotten if peers diff --git a/src/ats/ats_api_scheduling.c b/src/ats/ats_api_scheduling.c index 5a4e883..dce267e 100644 --- a/src/ats/ats_api_scheduling.c +++ b/src/ats/ats_api_scheduling.c @@ -30,6 +30,8 @@ #define INTERFACE_PROCESSING_INTERVALL GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 1) +#define NOT_FOUND 0 + /** * Message in linked list we should send to the ATS service. The * actual binary message follows this struct. @@ -92,6 +94,15 @@ struct ATS_Network socklen_t length; }; +/** + * Handle for address suggestions + */ +struct GNUNET_ATS_SuggestHandle +{ + struct GNUNET_ATS_SuggestHandle *prev; + struct GNUNET_ATS_SuggestHandle *next; + struct GNUNET_PeerIdentity id; +}; /** @@ -115,6 +126,16 @@ struct GNUNET_ATS_SchedulingHandle */ void *suggest_cb_cls; + /** + * DLL for suggestions head + */ + struct GNUNET_ATS_SuggestHandle *sug_head; + + /** + * DLL for suggestions tail + */ + struct GNUNET_ATS_SuggestHandle *sug_tail; + /** * Connection to ATS service. */ @@ -344,13 +365,28 @@ find_session (struct GNUNET_ATS_SchedulingHandle *sh, uint32_t session_id, sh->reconnect = GNUNET_YES; return NULL; } + /* This check exploits the fact that first field of a session object + * is peer identity. + */ + if (0 != + memcmp (peer, sh->session_array[session_id].session, + sizeof (struct GNUNET_PeerIdentity))) + { + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, "ats-scheduling-api", + "Session %p belongs to peer `%s'\n", + sh->session_array[session_id].session, GNUNET_i2s_full ((struct GNUNET_PeerIdentity *) &sh->session_array[session_id].peer)); +/* + GNUNET_break (0); + sh->reconnect = GNUNET_YES; + return NULL; +*/ + } return sh->session_array[session_id].session; } /** - * Get the ID for the given session object. If we do not have an ID for - * the given session object, allocate one. + * Get an available session ID for the given session object. * * @param sh our handle * @param session session object @@ -358,29 +394,21 @@ find_session (struct GNUNET_ATS_SchedulingHandle *sh, uint32_t session_id, * @return the session id */ static uint32_t -get_session_id (struct GNUNET_ATS_SchedulingHandle *sh, struct Session *session, +find_empty_session_slot (struct GNUNET_ATS_SchedulingHandle *sh, struct Session *session, const struct GNUNET_PeerIdentity *peer) { unsigned int i; unsigned int f; - GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, "ats-scheduling-api", "Get session ID for session %p from peer %s in %p\n", session, GNUNET_i2s (peer), sh); if (NULL == session) - return 0; + return NOT_FOUND; f = 0; for (i = 1; i < sh->session_array_size; i++) { - if (session == sh->session_array[i].session) - { - GNUNET_assert (0 == - memcmp (peer, &sh->session_array[i].peer, - sizeof (struct GNUNET_PeerIdentity))); - return i; - } if ((f == 0) && (sh->session_array[i].slot_used == GNUNET_NO)) f = i; } @@ -403,6 +431,48 @@ get_session_id (struct GNUNET_ATS_SchedulingHandle *sh, struct Session *session, } +/** + * Get the ID for the given session object. + * + * @param sh our handle + * @param session session object + * @param peer peer the session belongs to + * @return the session id or NOT_FOUND for error + */ +static uint32_t +find_session_id (struct GNUNET_ATS_SchedulingHandle *sh, struct Session *session, + const struct GNUNET_PeerIdentity *peer) +{ + unsigned int i; + char * p2; + + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, "ats-scheduling-api", + "Get session ID for session %p from peer %s in %p\n", session, + GNUNET_i2s (peer), sh); + + if (NULL == session) + return NOT_FOUND; + for (i = 1; i < sh->session_array_size; i++) + { + if (session == sh->session_array[i].session) + { + if (0 != memcmp (peer, &sh->session_array[i].peer, + sizeof (struct GNUNET_PeerIdentity))) + { + p2 = strdup (GNUNET_i2s (&sh->session_array[i].peer)); + GNUNET_log_from (GNUNET_ERROR_TYPE_ERROR, "ats-scheduling-api", + "Session %p did not match: old session was for peer `%s' new session is for `%s'\n", + session, GNUNET_i2s (peer), p2); + GNUNET_free (p2); + return NOT_FOUND; + } + return i; + } + } + return NOT_FOUND; +} + + /** * Remove the session of the given session ID from the session * table (it is no longer valid). @@ -424,12 +494,19 @@ remove_session (struct GNUNET_ATS_SchedulingHandle *sh, uint32_t session_id, if (0 == session_id) return; + GNUNET_assert (session_id < sh->session_array_size); GNUNET_assert (GNUNET_YES == sh->session_array[session_id].slot_used); - GNUNET_assert (0 == - memcmp (peer, &sh->session_array[session_id].peer, - sizeof (struct GNUNET_PeerIdentity))); + GNUNET_assert (0 == memcmp (peer, + &sh->session_array[session_id].peer, + sizeof (struct GNUNET_PeerIdentity))); + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, "ats-scheduling-api", + "Session %p for peer `%s' removed from slot %u \n", + sh->session_array[session_id].session, + GNUNET_i2s (peer), + session_id); sh->session_array[session_id].session = NULL; + } @@ -750,6 +827,21 @@ get_addresses (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) sh); } +/** + * Convert a GNUNET_ATS_NetworkType to a string + * + * @param net the network type + * @return a string or NULL if invalid + */ +const char * +GNUNET_ATS_print_network_type (uint32_t net) +{ + char *networks[GNUNET_ATS_NetworkTypeCount] = GNUNET_ATS_NetworkTypeString; + if (net < GNUNET_ATS_NetworkTypeCount) + return networks[net]; + return NULL; +} + /** * Returns where the address is located: LAN or WAN or ... @@ -763,9 +855,10 @@ struct GNUNET_ATS_Information GNUNET_ATS_address_get_type (struct GNUNET_ATS_SchedulingHandle * sh, const struct sockaddr * addr, socklen_t addrlen) { GNUNET_assert (sh != NULL); - struct GNUNET_ATS_Information ats; struct ATS_Network * cur = sh->net_head; + int type = GNUNET_ATS_NET_UNSPECIFIED; + struct GNUNET_ATS_Information ats; if (addr->sa_family == AF_UNIX) { @@ -804,15 +897,7 @@ GNUNET_ATS_address_get_type (struct GNUNET_ATS_SchedulingHandle * sh, const stru struct sockaddr_in * mask4 = (struct sockaddr_in *) cur->netmask; if (((a4->sin_addr.s_addr & mask4->sin_addr.s_addr)) == net4->sin_addr.s_addr) - { - char * net = GNUNET_strdup (GNUNET_a2s ((const struct sockaddr *) net4, addrlen)); - GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, "ats-scheduling-api", - "`%s' is in network `%s'\n", - GNUNET_a2s ((const struct sockaddr *)a4, addrlen), - net); - GNUNET_free (net); type = GNUNET_ATS_NET_LAN; - } } if (addr->sa_family == AF_INET6) { @@ -830,14 +915,7 @@ GNUNET_ATS_address_get_type (struct GNUNET_ATS_SchedulingHandle * sh, const stru res = GNUNET_NO; if (res == GNUNET_YES) - { - char * net = GNUNET_strdup (GNUNET_a2s ((const struct sockaddr *) net6, addrlen)); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "`%s' is in network `%s'\n", - GNUNET_a2s ((const struct sockaddr *) a6, addrlen), - net); - GNUNET_free (net); type = GNUNET_ATS_NET_LAN; - } } cur = cur->next; } @@ -847,7 +925,12 @@ GNUNET_ATS_address_get_type (struct GNUNET_ATS_SchedulingHandle * sh, const stru type = GNUNET_ATS_NET_WAN; ats.type = htonl (GNUNET_ATS_NETWORK_TYPE); ats.value = htonl (type); - return (const struct GNUNET_ATS_Information) ats; + + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, "ats-scheduling-api", + "`%s' is in network `%s'\n", + GNUNET_a2s ((const struct sockaddr *) addr, addrlen), + GNUNET_ATS_print_network_type(type)); + return ats; } @@ -889,7 +972,8 @@ void GNUNET_ATS_scheduling_done (struct GNUNET_ATS_SchedulingHandle *sh) { struct PendingMessage *p; - + struct GNUNET_ATS_SuggestHandle *cur; + struct GNUNET_ATS_SuggestHandle *next; while (NULL != (p = sh->pending_head)) { GNUNET_CONTAINER_DLL_remove (sh->pending_head, sh->pending_tail, p); @@ -906,6 +990,14 @@ GNUNET_ATS_scheduling_done (struct GNUNET_ATS_SchedulingHandle *sh) sh->task = GNUNET_SCHEDULER_NO_TASK; } + next = sh->sug_head; + while (NULL != (cur = next)) + { + next = cur->next; + GNUNET_CONTAINER_DLL_remove (sh->sug_head, sh->sug_tail, cur); + GNUNET_free (cur); + } + delete_networks (sh); if (sh->interface_task != GNUNET_SCHEDULER_NO_TASK) { @@ -950,13 +1042,15 @@ GNUNET_ATS_reset_backoff (struct GNUNET_ATS_SchedulingHandle *sh, * * @param sh handle * @param peer identity of the peer we need an address for + * @return suggest handle */ -void +struct GNUNET_ATS_SuggestHandle * GNUNET_ATS_suggest_address (struct GNUNET_ATS_SchedulingHandle *sh, const struct GNUNET_PeerIdentity *peer) { struct PendingMessage *p; struct RequestAddressMessage *m; + struct GNUNET_ATS_SuggestHandle *s; // FIXME: ATS needs to remember this in case of // a disconnect! @@ -971,6 +1065,10 @@ GNUNET_ATS_suggest_address (struct GNUNET_ATS_SchedulingHandle *sh, m->peer = *peer; GNUNET_CONTAINER_DLL_insert_tail (sh->pending_head, sh->pending_tail, p); do_transmit (sh); + s = GNUNET_malloc (sizeof (struct GNUNET_ATS_SuggestHandle)); + s->id = (*peer); + GNUNET_CONTAINER_DLL_insert_tail (sh->sug_head, sh->sug_tail, s); + return s; } @@ -986,6 +1084,21 @@ GNUNET_ATS_suggest_address_cancel (struct GNUNET_ATS_SchedulingHandle *sh, { struct PendingMessage *p; struct RequestAddressMessage *m; + struct GNUNET_ATS_SuggestHandle *s; + + for (s = sh->sug_head; NULL != s; s = s->next) + if (0 == memcmp(peer, &s->id, sizeof (s->id))) + break; + if (NULL == s) + { + GNUNET_break (0); + return; + } + else + { + GNUNET_CONTAINER_DLL_remove (sh->sug_head, sh->sug_tail, s); + GNUNET_free (s); + } p = GNUNET_malloc (sizeof (struct PendingMessage) + sizeof (struct RequestAddressMessage)); @@ -1001,6 +1114,101 @@ GNUNET_ATS_suggest_address_cancel (struct GNUNET_ATS_SchedulingHandle *sh, } +/** + * We have a new address ATS should know. Addresses have to be added with this + * function before they can be: updated, set in use and destroyed + * + * @param sh handle + * @param address the address + * @param session session handle, can be NULL + * @param ats performance data for the address + * @param ats_count number of performance records in 'ats' + * @return GNUNET_OK on success, GNUNET_SYSERR on error + */ +int +GNUNET_ATS_address_add (struct GNUNET_ATS_SchedulingHandle *sh, + const struct GNUNET_HELLO_Address *address, + struct Session *session, + const struct GNUNET_ATS_Information *ats, + uint32_t ats_count) +{ + + struct PendingMessage *p; + struct AddressUpdateMessage *m; + struct GNUNET_ATS_Information *am; + char *pm; + size_t namelen; + size_t msize; + uint32_t s = 0; + + if (address == NULL) + { + GNUNET_break (0); + return GNUNET_SYSERR; + } + + namelen = + (address->transport_name == + NULL) ? 0 : strlen (address->transport_name) + 1; + msize = + sizeof (struct AddressUpdateMessage) + address->address_length + + ats_count * sizeof (struct GNUNET_ATS_Information) + namelen; + if ((msize >= GNUNET_SERVER_MAX_MESSAGE_SIZE) || + (address->address_length >= GNUNET_SERVER_MAX_MESSAGE_SIZE) || + (namelen >= GNUNET_SERVER_MAX_MESSAGE_SIZE) || + (ats_count >= + GNUNET_SERVER_MAX_MESSAGE_SIZE / sizeof (struct GNUNET_ATS_Information))) + { + GNUNET_break (0); + return GNUNET_SYSERR; + } + + if (NULL != session) + { + s = find_session_id (sh, session, &address->peer); + if (NOT_FOUND != s) + { + /* Already existing, nothing todo */ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Adding duplicate address for peer `%s', plugin `%s', session %p id %u\n", + GNUNET_i2s (&address->peer), + address->transport_name, session, s); + return GNUNET_SYSERR; + } + s = find_empty_session_slot (sh, session, &address->peer); + GNUNET_break (NOT_FOUND != s); + } + + p = GNUNET_malloc (sizeof (struct PendingMessage) + msize); + p->size = msize; + p->is_init = GNUNET_NO; + m = (struct AddressUpdateMessage *) &p[1]; + m->header.type = htons (GNUNET_MESSAGE_TYPE_ATS_ADDRESS_ADD); + m->header.size = htons (msize); + m->ats_count = htonl (ats_count); + m->peer = address->peer; + m->address_length = htons (address->address_length); + m->plugin_name_length = htons (namelen); + m->session_id = htonl (s); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Adding address for peer `%s', plugin `%s', session %p id %u\n", + GNUNET_i2s (&address->peer), + address->transport_name, session, s); + + am = (struct GNUNET_ATS_Information *) &m[1]; + memcpy (am, ats, ats_count * sizeof (struct GNUNET_ATS_Information)); + pm = (char *) &am[ats_count]; + memcpy (pm, address->address, address->address_length); + if (NULL != address->transport_name) + memcpy (&pm[address->address_length], address->transport_name, namelen); + GNUNET_CONTAINER_DLL_insert_tail (sh->pending_head, sh->pending_tail, p); + do_transmit (sh); + return GNUNET_OK; + +} + + /** * We have updated performance statistics for a given address. Note * that this function can be called for addresses that are currently @@ -1011,7 +1219,7 @@ GNUNET_ATS_suggest_address_cancel (struct GNUNET_ATS_SchedulingHandle *sh, * * @param sh handle * @param address the address - * @param session session handle (if available) + * @param session session handle, can be NULL * @param ats performance data for the address * @param ats_count number of performance records in 'ats' */ @@ -1028,17 +1236,13 @@ GNUNET_ATS_address_update (struct GNUNET_ATS_SchedulingHandle *sh, char *pm; size_t namelen; size_t msize; + uint32_t s = 0; if (address == NULL) { GNUNET_break (0); return; } - if ((address == NULL) && (session == NULL)) - { - GNUNET_break (0); - return; - } namelen = (address->transport_name == @@ -1056,6 +1260,21 @@ GNUNET_ATS_address_update (struct GNUNET_ATS_SchedulingHandle *sh, return; } + if (NULL != session) + { + s = find_session_id (sh, session, &address->peer); + if (NOT_FOUND == s) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Update for unknown address for peer `%s', plugin `%s', session %p id %u\n", + GNUNET_i2s (&address->peer), + address->transport_name, session, s); + + GNUNET_break (0); + return; + } + } + p = GNUNET_malloc (sizeof (struct PendingMessage) + msize); p->size = msize; p->is_init = GNUNET_NO; @@ -1066,7 +1285,14 @@ GNUNET_ATS_address_update (struct GNUNET_ATS_SchedulingHandle *sh, m->peer = address->peer; m->address_length = htons (address->address_length); m->plugin_name_length = htons (namelen); - m->session_id = htonl (get_session_id (sh, session, &address->peer)); + + m->session_id = htonl (s); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Updating address for peer `%s', plugin `%s', session %p id %u\n", + GNUNET_i2s (&address->peer), + address->transport_name, session, s); + am = (struct GNUNET_ATS_Information *) &m[1]; memcpy (am, ats, ats_count * sizeof (struct GNUNET_ATS_Information)); pm = (char *) &am[ats_count]; @@ -1074,6 +1300,7 @@ GNUNET_ATS_address_update (struct GNUNET_ATS_SchedulingHandle *sh, memcpy (&pm[address->address_length], address->transport_name, namelen); GNUNET_CONTAINER_DLL_insert_tail (sh->pending_head, sh->pending_tail, p); do_transmit (sh); + return; } @@ -1082,7 +1309,7 @@ GNUNET_ATS_address_update (struct GNUNET_ATS_SchedulingHandle *sh, * * @param sh handle * @param address the address - * @param session session handle + * @param session session handle, can be NULL * @param in_use GNUNET_YES if this address is now used, GNUNET_NO * if address is not used any more */ @@ -1096,6 +1323,7 @@ GNUNET_ATS_address_in_use (struct GNUNET_ATS_SchedulingHandle *sh, char *pm; size_t namelen; size_t msize; + uint32_t s = 0; GNUNET_assert (NULL != address); namelen = @@ -1110,6 +1338,26 @@ GNUNET_ATS_address_in_use (struct GNUNET_ATS_SchedulingHandle *sh, return; } + if (session != NULL) + { + s = find_session_id (sh, session, &address->peer); + if ((s == NOT_FOUND) && (GNUNET_NO == in_use)) + { + /* trying to set unknown address to NO */ + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Trying to set unknown address to unused for peer `%s', plugin `%s', session %p\n", + GNUNET_i2s (&address->peer), address->transport_name, session); + GNUNET_break (0); + return; + } + if ((s == NOT_FOUND) && (GNUNET_YES == in_use)) + { + /* trying to set new address to YES */ + s = find_empty_session_slot (sh, session, &address->peer); + GNUNET_assert (NOT_FOUND != s); + } + } + p = GNUNET_malloc (sizeof (struct PendingMessage) + msize); p->size = msize; p->is_init = GNUNET_NO; @@ -1120,12 +1368,19 @@ GNUNET_ATS_address_in_use (struct GNUNET_ATS_SchedulingHandle *sh, m->in_use = htons (in_use); m->address_length = htons (address->address_length); m->plugin_name_length = htons (namelen); - m->session_id = htonl (get_session_id (sh, session, &address->peer)); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Setting address used to %s for peer `%s', plugin `%s', session %p\n", + (GNUNET_YES == in_use) ? "YES" : "NO", + GNUNET_i2s (&address->peer), address->transport_name, session); + + m->session_id = htonl (s); pm = (char *) &m[1]; memcpy (pm, address->address, address->address_length); memcpy (&pm[address->address_length], address->transport_name, namelen); GNUNET_CONTAINER_DLL_insert_tail (sh->pending_head, sh->pending_tail, p); do_transmit (sh); + return; } @@ -1134,7 +1389,7 @@ GNUNET_ATS_address_in_use (struct GNUNET_ATS_SchedulingHandle *sh, * * @param sh handle * @param address the address - * @param session session handle that is no longer valid + * @param session session handle that is no longer valid, can be NULL */ void GNUNET_ATS_address_destroyed (struct GNUNET_ATS_SchedulingHandle *sh, @@ -1146,7 +1401,13 @@ GNUNET_ATS_address_destroyed (struct GNUNET_ATS_SchedulingHandle *sh, char *pm; size_t namelen; size_t msize; - uint32_t session_id; + uint32_t s = 0; + + if (address == NULL) + { + GNUNET_break (0); + return; + } GNUNET_assert (address->transport_name != NULL); namelen = strlen (address->transport_name) + 1; @@ -1162,6 +1423,16 @@ GNUNET_ATS_address_destroyed (struct GNUNET_ATS_SchedulingHandle *sh, return; } + s = find_session_id (sh, session, &address->peer); + if ((NULL != session) && (NOT_FOUND == s)) + { + /* trying to delete unknown address */ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Trying to delete unknown address for peer `%s', plugin `%s', session %p\n", + GNUNET_i2s (&address->peer), address->transport_name, session); + return; + } + p = GNUNET_malloc (sizeof (struct PendingMessage) + msize); p->size = msize; p->is_init = GNUNET_NO; @@ -1172,14 +1443,18 @@ GNUNET_ATS_address_destroyed (struct GNUNET_ATS_SchedulingHandle *sh, m->peer = address->peer; m->address_length = htons (address->address_length); m->plugin_name_length = htons (namelen); - session_id = get_session_id (sh, session, &address->peer); - m->session_id = htonl (session_id); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Deleting address for peer `%s', plugin `%s', session %p\n", + GNUNET_i2s (&address->peer), address->transport_name, session); + + m->session_id = htonl (s); pm = (char *) &m[1]; memcpy (pm, address->address, address->address_length); memcpy (&pm[address->address_length], address->transport_name, namelen); GNUNET_CONTAINER_DLL_insert_tail (sh->pending_head, sh->pending_tail, p); do_transmit (sh); - remove_session (sh, session_id, &address->peer); + remove_session (sh, s, &address->peer); } /* end of ats_api_scheduling.c */ diff --git a/src/ats/gnunet-service-ats.c b/src/ats/gnunet-service-ats.c index aef72f1..3218769 100644 --- a/src/ats/gnunet-service-ats.c +++ b/src/ats/gnunet-service-ats.c @@ -41,6 +41,7 @@ struct GNUNET_STATISTICS_Handle *GSA_stats; static struct GNUNET_SERVER_Handle *GSA_server; +struct GAS_Addresses_Handle *GSA_addresses; /** * We have received a 'ClientStartMessage' from a client. Find out which @@ -109,7 +110,7 @@ client_disconnect_handler (void *cls, struct GNUNET_SERVER_Client *client) static void cleanup_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { - GAS_addresses_done (); + GAS_addresses_done (GSA_addresses); GAS_scheduling_done (); GAS_performance_done (); GAS_reservations_done (); @@ -142,6 +143,11 @@ run (void *cls, struct GNUNET_SERVER_Handle *server, {&GAS_handle_request_address_cancel, NULL, GNUNET_MESSAGE_TYPE_ATS_REQUEST_ADDRESS_CANCEL, sizeof (struct RequestAddressMessage)}, + {&GAS_handle_request_address_list, NULL, + GNUNET_MESSAGE_TYPE_ATS_ADDRESSLIST_REQUEST, + sizeof (struct AddressListRequestMessage)}, + {&GAS_handle_address_add, NULL, + GNUNET_MESSAGE_TYPE_ATS_ADDRESS_ADD, 0}, {&GAS_handle_address_update, NULL, GNUNET_MESSAGE_TYPE_ATS_ADDRESS_UPDATE, 0}, {&GAS_handle_address_in_use, NULL, @@ -161,9 +167,10 @@ run (void *cls, struct GNUNET_SERVER_Handle *server, GSA_server = server; GSA_stats = GNUNET_STATISTICS_create ("ats", cfg); GAS_reservations_init (); - GAS_performance_init (server); - GAS_scheduling_init (server); - GAS_addresses_init (cfg, GSA_stats); + GSA_addresses = GAS_addresses_init (cfg, GSA_stats); + GAS_performance_init (server, GSA_addresses); + GAS_scheduling_init (server, GSA_addresses); + GNUNET_SERVER_disconnect_notify (server, &client_disconnect_handler, NULL); GNUNET_SERVER_add_handlers (server, handlers); GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, &cleanup_task, diff --git a/src/ats/gnunet-service-ats_addresses.c b/src/ats/gnunet-service-ats_addresses.c index 9bf5ca6..e890aaa 100644 --- a/src/ats/gnunet-service-ats_addresses.c +++ b/src/ats/gnunet-service-ats_addresses.c @@ -34,104 +34,244 @@ #if HAVE_LIBGLPK #include "gnunet-service-ats_addresses_mlp.h" #endif +#include "gnunet-service-ats_addresses_simplistic.h" -#define VERBOSE GNUNET_NO +/** + * ATS address management + * + * Adding addresses: + * + * - If you add a new address without a session, a new address will be added + * - If you add this address again now with a session a, the existing address + * will be updated with this session + * - If you add this address again now with a session b, a new address object + * with this session will be added + + * Destroying addresses: + * + * - If you destroy an address without a session, the address itself and all + * address instances with an session will be removed + * - If you destroy an address with a session, the session for this address + * will be removed + * + * Conclusion + * Addresses without a session will be updated with a new session and if the + * the session is destroyed the session is removed and address itself still + * exists for suggestion + * + */ -#define ATS_BLOCKING_DELTA GNUNET_TIME_relative_multiply(GNUNET_TIME_UNIT_MILLISECONDS, 100) +/** + * Available ressource assignment modes + */ enum ATS_Mode { /* + * Simplistic mode: + * * Assign each peer an equal amount of bandwidth (bw) * * bw_per_peer = bw_total / #active addresses */ - SIMPLE, + MODE_SIMPLISTIC, /* - * Use MLP solver to assign bandwidth + * MLP mode: + * + * Solve ressource assignment as an optimization problem + * Uses an mixed integer programming solver */ - MLP + MODE_MLP }; -static struct GNUNET_CONTAINER_MultiHashMap *addresses; +/** + * Pending Address suggestion requests + */ +struct GAS_Addresses_Suggestion_Requests +{ + /** + * Next in DLL + */ + struct GAS_Addresses_Suggestion_Requests *next; -#if HAVE_LIBGLPK -static struct GAS_MLP_Handle *mlp; -#endif + /** + * Previous in DLL + */ + struct GAS_Addresses_Suggestion_Requests *prev; -static unsigned long long wan_quota_in; + /** + * Peer ID + */ + struct GNUNET_PeerIdentity id; +}; -static unsigned long long wan_quota_out; +/** + * Handle for ATS address component + */ +struct GAS_Addresses_Handle +{ + /** + * + */ + struct GNUNET_STATISTICS_Handle *stat; -static unsigned int active_addr_count; + /** + * A multihashmap to store all addresses + */ + struct GNUNET_CONTAINER_MultiHashMap *addresses; -static int ats_mode; + /** + * Configure WAN quota in + */ + unsigned long long wan_quota_in; -static int running; + /** + * Configure WAN quota out + */ + unsigned long long wan_quota_out; + /** + * Is ATS addresses running + */ + int running; -static void -send_bw_notification (struct ATS_Address *aa) -{ - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "New bandwidth for peer %s is %u/%u\n", - GNUNET_i2s (&aa->peer), ntohl (aa->assigned_bw_in.value__), - ntohl (aa->assigned_bw_out.value__)); - GAS_scheduling_transmit_address_suggestion (&aa->peer, aa->plugin, aa->addr, - aa->addr_len, aa->session_id, - aa->ats, aa->ats_count, - aa->assigned_bw_out, - aa->assigned_bw_in); - GAS_reservations_set_bandwidth (&aa->peer, aa->assigned_bw_in); - GAS_performance_notify_clients (&aa->peer, aa->plugin, aa->addr, aa->addr_len, - aa->ats, aa->ats_count, aa->assigned_bw_out, - aa->assigned_bw_in); -} + /** + * Configured ATS solver + */ + int ats_mode; -/** - * Update a bandwidth assignment for a peer. This trivial method currently - * simply assigns the same share to all active connections. - * - * @param cls unused - * @param key unused - * @param value the 'struct ATS_Address' - * @return GNUNET_OK (continue to iterate) - */ -static int -update_bw_simple_it (void *cls, const GNUNET_HashCode * key, void *value) -{ - struct ATS_Address *aa = value; + /** + * Solver handle + */ + void *solver; + + /** + * Address suggestion requests DLL head + */ + struct GAS_Addresses_Suggestion_Requests *r_head; - if (GNUNET_YES != aa->active) - return GNUNET_OK; - GNUNET_assert (active_addr_count > 0); + /** + * Address suggestion requests DLL tail + */ + struct GAS_Addresses_Suggestion_Requests *r_tail; + /* Solver functions */ - /* Simple method */ - aa->assigned_bw_in.value__ = htonl (wan_quota_in / active_addr_count); - aa->assigned_bw_out.value__ = htonl (wan_quota_out / active_addr_count); + /** + * Initialize solver + */ + GAS_solver_init s_init; - send_bw_notification (aa); + /** + * Add an address to the solver + */ + GAS_solver_address_add s_add; - return GNUNET_OK; -} + /** + * Update address in solver + */ + GAS_solver_address_update s_update; + /** + * Get address from solver + */ + GAS_solver_get_preferred_address s_get; -/** - * Some (significant) input changed, recalculate bandwidth assignment - * for all peers. - */ -static void -recalculate_assigned_bw () + /** + * Delete address in solver + */ + GAS_solver_address_delete s_del; + + /** + * Change preference for quality in solver + */ + GAS_solver_address_change_preference s_pref; + + /** + * Shutdown solver + */ + GAS_solver_done s_done; +}; + + +static unsigned int +assemble_ats_information (const struct ATS_Address *aa, struct GNUNET_ATS_Information **dest) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Recalculating bandwidth for all active connections\n"); - GNUNET_STATISTICS_update (GSA_stats, "# bandwidth recalculations performed", - 1, GNUNET_NO); - GNUNET_STATISTICS_set (GSA_stats, "# active addresses", active_addr_count, - GNUNET_NO); + unsigned int ats_count = GNUNET_ATS_PropertyCount - 1; + struct GNUNET_ATS_Information *ats = GNUNET_malloc (ats_count * sizeof (struct GNUNET_ATS_Information)); + (*dest) = ats; + + ats[0].type = ntohl(GNUNET_ATS_UTILIZATION_UP); + ats[0].value = aa->atsp_utilization_out.value__; + ats[1].type = ntohl(GNUNET_ATS_UTILIZATION_DOWN); + ats[1].value = aa->atsp_utilization_in.value__; + ats[2].type = ntohl(GNUNET_ATS_NETWORK_TYPE); + ats[2].value = ntohl(aa->atsp_network_type); + ats[3].type = ntohl(GNUNET_ATS_QUALITY_NET_DELAY); + ats[3].value = ntohl(aa->atsp_latency.rel_value); + ats[4].type = ntohl(GNUNET_ATS_QUALITY_NET_DISTANCE); + ats[4].value = ntohl(aa->atsp_distance); + ats[5].type = ntohl(GNUNET_ATS_COST_WAN); + ats[5].value = ntohl (aa->atsp_cost_wan); + ats[6].type = ntohl(GNUNET_ATS_COST_LAN); + ats[6].value = ntohl (aa->atsp_cost_lan); + ats[7].type = ntohl(GNUNET_ATS_COST_WLAN); + ats[7].value = ntohl (aa->atsp_cost_wlan); + return ats_count; +} - GNUNET_CONTAINER_multihashmap_iterate (addresses, &update_bw_simple_it, NULL); +static unsigned int +disassemble_ats_information (const struct GNUNET_ATS_Information *src, + uint32_t ats_count, + struct ATS_Address *dest) +{ + int i; + int res = 0; + for (i = 0; i < ats_count; i++) + switch (ntohl (src[i].type)) + { + case GNUNET_ATS_UTILIZATION_UP: + dest->atsp_utilization_out.value__ = src[i].value; + res ++; + break; + case GNUNET_ATS_UTILIZATION_DOWN: + dest->atsp_utilization_in.value__ = src[i].value; + res ++; + break; + case GNUNET_ATS_QUALITY_NET_DELAY: + dest->atsp_latency.rel_value = ntohl (src[i].value); + res ++; + break; + case GNUNET_ATS_QUALITY_NET_DISTANCE: + dest->atsp_distance = ntohl (src[i].value); + res ++; + break; + case GNUNET_ATS_COST_WAN: + dest->atsp_cost_wan = ntohl (src[i].value); + res ++; + break; + case GNUNET_ATS_COST_LAN: + dest->atsp_cost_lan = ntohl (src[i].value); + res ++; + break; + case GNUNET_ATS_COST_WLAN: + dest->atsp_cost_wlan = ntohl (src[i].value); + res ++; + break; + case GNUNET_ATS_NETWORK_TYPE: + dest->atsp_network_type = ntohl (src[i].value); + res ++; + break; + case GNUNET_ATS_ARRAY_TERMINATOR: + break; + default: + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + "Received unsupported ATS type %u\n", ntohl (src[i].type)); + GNUNET_break (0); + break; + } + return res; } /** @@ -141,7 +281,6 @@ recalculate_assigned_bw () static void free_address (struct ATS_Address *addr) { - GNUNET_free_non_null (addr->ats); GNUNET_free (addr->plugin); GNUNET_free (addr); } @@ -170,6 +309,11 @@ create_address (const struct GNUNET_PeerIdentity *peer, memcpy (&aa[1], plugin_addr, plugin_addr_len); aa->plugin = GNUNET_strdup (plugin_name); aa->session_id = session_id; + aa->active = GNUNET_NO; + aa->used = GNUNET_NO; + aa->solver_information = NULL; + aa->assigned_bw_in = GNUNET_BANDWIDTH_value_init(0); + aa->assigned_bw_out = GNUNET_BANDWIDTH_value_init(0); return aa; } @@ -177,31 +321,20 @@ create_address (const struct GNUNET_PeerIdentity *peer, /** * Destroy the given address. * + * @param handle the address handle * @param addr address to destroy * @return GNUNET_YES if bandwidth allocations should be recalcualted */ static int -destroy_address (struct ATS_Address *addr) +destroy_address (struct GAS_Addresses_Handle *handle, struct ATS_Address *addr) { int ret; ret = GNUNET_NO; GNUNET_assert (GNUNET_YES == - GNUNET_CONTAINER_multihashmap_remove (addresses, + GNUNET_CONTAINER_multihashmap_remove (handle->addresses, &addr->peer.hashPubKey, addr)); - -#if HAVE_LIBGLPK - if (ats_mode == MLP) - GAS_mlp_address_delete (mlp, addresses, addr); -#endif - - if (GNUNET_YES == addr->active) - { - active_addr_count--; - addr->active = GNUNET_NO; - ret = GNUNET_YES; - } free_address (addr); return ret; } @@ -219,39 +352,68 @@ struct CompareAddressContext static int -compare_address_it (void *cls, const GNUNET_HashCode * key, void *value) +compare_address_it (void *cls, const struct GNUNET_HashCode * key, void *value) { struct CompareAddressContext *cac = cls; struct ATS_Address *aa = value; -/* - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "Comparing to: %s %s %u session %u\n", - GNUNET_i2s (&aa->peer), aa->plugin, aa->addr_len, aa->session_id); -*/ - /* find an exact matching address: aa->addr == cac->search->addr && aa->session == cac->search->session */ + /* Find an matching exact address: + * + * Compare by: + * aa->addr_len == cac->search->addr_len + * aa->plugin == cac->search->plugin + * aa->addr == cac->search->addr + * aa->session == cac->search->session + * + * return as exact address + */ if ((aa->addr_len == cac->search->addr_len) && (0 == strcmp (aa->plugin, cac->search->plugin))) { if ((0 == memcmp (aa->addr, cac->search->addr, aa->addr_len)) && (aa->session_id == cac->search->session_id)) - { cac->exact_address = aa; - } } - /* find an matching address: aa->addr == cac->search->addr && aa->session == 0 */ - /* this address can be used to be updated */ + /* Find an matching base address: + * + * Properties: + * + * aa->session_id == 0 + * + * Compare by: + * aa->addr_len == cac->search->addr_len + * aa->plugin == cac->search->plugin + * aa->addr == cac->search->addr + * + * return as base address + */ if ((aa->addr_len == cac->search->addr_len) && (0 == strcmp (aa->plugin, cac->search->plugin))) { if ((0 == memcmp (aa->addr, cac->search->addr, aa->addr_len)) && (aa->session_id == 0)) - { cac->base_address = aa; - } + } + + /* Find an matching exact address based on session: + * + * Properties: + * + * cac->search->addr_len == 0 + * + * Compare by: + * aa->plugin == cac->search->plugin + * aa->session_id == cac->search->session_id + * + * return as exact address + */ + if (0 == cac->search->addr_len) + { + if ((0 == strcmp (aa->plugin, cac->search->plugin)) && (aa->session_id == cac->search->session_id)) + cac->exact_address = aa; } if (cac->exact_address == NULL) - return GNUNET_YES; + return GNUNET_YES; /* Continue iteration to find exact address */ else - return GNUNET_NO; + return GNUNET_NO; /* Stop iteration since we have an exact address */ } @@ -260,177 +422,204 @@ compare_address_it (void *cls, const GNUNET_HashCode * key, void *value) * Compares by peer identity and network address OR by session ID * (one of the two must match). * + * @param handle the address handle * @param peer peer to lookup addresses for * @param addr existing address record * @return existing address record, NULL for none */ struct ATS_Address * -find_address (const struct GNUNET_PeerIdentity *peer, - const struct ATS_Address *addr) +find_equivalent_address (struct GAS_Addresses_Handle *handle, + const struct GNUNET_PeerIdentity *peer, + const struct ATS_Address *addr) { struct CompareAddressContext cac; cac.exact_address = NULL; cac.base_address = NULL; cac.search = addr; - GNUNET_CONTAINER_multihashmap_get_multiple (addresses, &peer->hashPubKey, + GNUNET_CONTAINER_multihashmap_get_multiple (handle->addresses, &peer->hashPubKey, &compare_address_it, &cac); -/* - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "exact address: %s base address: %s\n", - (cac.exact_address != NULL) ? "YES" : "NO", - (cac.base_address != NULL) ? "YES" : "NO"); -*/ if (cac.exact_address == NULL) return cac.base_address; return cac.exact_address; } -static int -compare_address_session_it (void *cls, const GNUNET_HashCode * key, void *value) +static struct ATS_Address * +lookup_address (struct GAS_Addresses_Handle *handle, + const struct GNUNET_PeerIdentity *peer, + const char *plugin_name, + const void *plugin_addr, + size_t plugin_addr_len, + uint32_t session_id, + const struct GNUNET_ATS_Information *atsi, + uint32_t atsi_count) { - struct CompareAddressContext *cac = cls; - struct ATS_Address *aa = value; + struct ATS_Address *aa; + struct ATS_Address *ea; - if ((aa->addr_len == cac->search->addr_len) && (0 == strcmp (aa->plugin, cac->search->plugin))) + aa = create_address (peer, + plugin_name, + plugin_addr, plugin_addr_len, + session_id); + + /* Get existing address or address with session == 0 */ + ea = find_equivalent_address (handle, peer, aa); + free_address (aa); + if (ea == NULL) { - if ((0 == memcmp (aa->addr, cac->search->addr, aa->addr_len)) && (aa->session_id == cac->search->session_id)) - { - cac->exact_address = aa; - return GNUNET_NO; - } + return NULL; } - return GNUNET_YES; + else if (ea->session_id != session_id) + { + return NULL; + } + return ea; } -/** - * Find an existing equivalent address record. - * Compares by peer identity and network address AND by session ID - * (one of the two must match). - * - * @param peer peer to lookup addresses for - * @param addr existing address record - * @return existing address record, NULL for none - */ -struct ATS_Address * -find_exact_address (const struct GNUNET_PeerIdentity *peer, - const struct ATS_Address *addr) +void +GAS_addresses_add (struct GAS_Addresses_Handle *handle, + const struct GNUNET_PeerIdentity *peer, + const char *plugin_name, const void *plugin_addr, + size_t plugin_addr_len, uint32_t session_id, + const struct GNUNET_ATS_Information *atsi, + uint32_t atsi_count) { - struct CompareAddressContext cac; + struct ATS_Address *aa; + struct ATS_Address *ea; + unsigned int ats_res; - cac.exact_address = NULL; - cac.search = addr; - GNUNET_CONTAINER_multihashmap_get_multiple (addresses, &peer->hashPubKey, - &compare_address_session_it, &cac); - return cac.exact_address; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Received `%s' for peer `%s'\n", + "ADDRESS ADD", + GNUNET_i2s (peer)); + + if (GNUNET_NO == handle->running) + return; + + GNUNET_assert (NULL != handle->addresses); + + aa = create_address (peer, plugin_name, plugin_addr, plugin_addr_len, + session_id); + if (atsi_count != (ats_res = disassemble_ats_information(atsi, atsi_count, aa))) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "While adding address: had %u ATS elements to add, could only add %u\n", + atsi_count, ats_res); + } + + /* Get existing address or address with session == 0 */ + ea = find_equivalent_address (handle, peer, aa); + if (ea == NULL) + { + /* We have a new address */ + GNUNET_assert (GNUNET_OK == + GNUNET_CONTAINER_multihashmap_put (handle->addresses, + &peer->hashPubKey, aa, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE)); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Added new address for peer `%s' session id %u, %p\n", + GNUNET_i2s (peer), session_id, aa); + /* Tell solver about new address */ + handle->s_add (handle->solver, handle->addresses, aa); + return; + } + GNUNET_free (aa->plugin); + GNUNET_free (aa); + + if (ea->session_id != 0) + { + /* This address with the same session is already existing + * Should not happen */ + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Added already existing address for peer `%s' `%s' %p with new session %u\n", + GNUNET_i2s (peer), plugin_name, session_id); + GNUNET_break (0); + return; + } + + /* We have an address without an session, update this address */ + + /* Notify solver about update with atsi information and session */ + handle->s_update (handle->solver, handle->addresses, ea, session_id, ea->used, atsi, atsi_count); + + /* Do the update */ + ea->session_id = session_id; + if (atsi_count != (ats_res = disassemble_ats_information(atsi, atsi_count, ea))) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "While updating address: had %u ATS elements to add, could only add %u\n", + atsi_count, ats_res); + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Updated existing address for peer `%s' %p with new session %u\n", + GNUNET_i2s (peer), ea, session_id); } void -GAS_addresses_update (const struct GNUNET_PeerIdentity *peer, +GAS_addresses_update (struct GAS_Addresses_Handle *handle, + const struct GNUNET_PeerIdentity *peer, const char *plugin_name, const void *plugin_addr, size_t plugin_addr_len, uint32_t session_id, const struct GNUNET_ATS_Information *atsi, uint32_t atsi_count) { struct ATS_Address *aa; - struct ATS_Address *old; - uint32_t i; + uint32_t ats_res; - if (GNUNET_NO == running) + if (GNUNET_NO == handle->running) return; - GNUNET_assert (NULL != addresses); + GNUNET_assert (NULL != handle->addresses); - aa = create_address (peer, - plugin_name, - plugin_addr, plugin_addr_len, - session_id); + /* Get existing address */ + aa = lookup_address (handle, peer, plugin_name, plugin_addr, plugin_addr_len, + session_id, atsi, atsi_count); + if (aa == NULL) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Tried to update unknown address for peer `%s' `%s' session id %u\n", + GNUNET_i2s (peer), plugin_name, session_id); + GNUNET_break (0); + return; + } - aa->mlp_information = NULL; - aa->ats = GNUNET_malloc (atsi_count * sizeof (struct GNUNET_ATS_Information)); - aa->ats_count = atsi_count; - memcpy (aa->ats, atsi, atsi_count * sizeof (struct GNUNET_ATS_Information)); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Received `%s' for peer `%s' address \n", + "ADDRESS UPDATE", + GNUNET_i2s (peer), aa); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Updating address for peer `%s' %u\n", - GNUNET_i2s (peer), - session_id); + /* Tell solver about update */ + handle->s_update (handle->solver, handle->addresses, aa, session_id, aa->used, atsi, atsi_count); - /* Get existing address or address with session == 0 */ - old = find_address (peer, aa); - if (old == NULL) - { - GNUNET_assert (GNUNET_OK == - GNUNET_CONTAINER_multihashmap_put (addresses, - &peer->hashPubKey, aa, - GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE)); -#if DEBUG_ATS - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Added new address for peer `%s' %X\n", - GNUNET_i2s (peer), aa); -#endif - old = aa; - } - else + /* Update address */ + if (atsi_count != (ats_res = disassemble_ats_information (atsi, atsi_count, aa))) { -#if DEBUG_ATS GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Updated existing address for peer `%s' %p old session %u new session %u\n", - GNUNET_i2s (peer), old, - old->session_id, session_id); -#endif - GNUNET_free_non_null (old->ats); - old->session_id = session_id; - old->ats = NULL; - old->ats_count = 0; - old->ats = aa->ats; - old->ats_count = aa->ats_count; - GNUNET_free (aa->plugin); - GNUNET_free (aa); - } - for (i = 0; i < atsi_count; i++) - switch (ntohl (atsi[i].type)) - { - case GNUNET_ATS_UTILIZATION_UP: - old->atsp_utilization_out.value__ = atsi[i].value; - break; - case GNUNET_ATS_UTILIZATION_DOWN: - old->atsp_utilization_in.value__ = atsi[i].value; - break; - case GNUNET_ATS_QUALITY_NET_DELAY: - old->atsp_latency.rel_value = ntohl (atsi[i].value); - break; - case GNUNET_ATS_QUALITY_NET_DISTANCE: - old->atsp_distance = ntohl (atsi[i].value); - break; - case GNUNET_ATS_COST_WAN: - old->atsp_cost_wan = ntohl (atsi[i].value); - break; - case GNUNET_ATS_COST_LAN: - old->atsp_cost_lan = ntohl (atsi[i].value); - break; - case GNUNET_ATS_COST_WLAN: - old->atsp_cost_wlan = ntohl (atsi[i].value); - break; - case GNUNET_ATS_NETWORK_TYPE: - old->atsp_network_type = ntohl (atsi[i].value); - break; - - default: - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Received unsupported ATS type %u\n", ntohl (atsi[i].type)); - GNUNET_break (0); - break; - } -#if HAVE_LIBGLPK - if (ats_mode == MLP) - GAS_mlp_address_update (mlp, addresses, old); -#endif + "While adding address: had %u ATS elements to add, could only add %u\n", + atsi_count, ats_res); + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Updated %u ATS elements for address %p\n", + ats_res, aa); } +struct DestroyContext +{ + struct ATS_Address *aa; + + struct GAS_Addresses_Handle *handle; + + /** + * GNUNET_NO : full address + * GNUNET_YES : just session + */ + int result; +}; + + /** * Delete an address * @@ -444,453 +633,576 @@ GAS_addresses_update (const struct GNUNET_PeerIdentity *peer, * @return GNUNET_OK (continue to iterate) */ static int -destroy_by_session_id (void *cls, const GNUNET_HashCode * key, void *value) +destroy_by_session_id (void *cls, const struct GNUNET_HashCode * key, void *value) { - const struct ATS_Address *info = cls; + struct DestroyContext *dc = cls; + struct GAS_Addresses_Handle *handle = dc->handle; + const struct ATS_Address *des = dc->aa; struct ATS_Address *aa = value; - GNUNET_assert (0 == - memcmp (&aa->peer, &info->peer, - sizeof (struct GNUNET_PeerIdentity))); - /* session == 0, remove full address */ - if ((info->session_id == 0) && (0 == strcmp (info->plugin, aa->plugin)) && - (aa->addr_len == info->addr_len) && - (0 == memcmp (info->addr, aa->addr, aa->addr_len))) - { + GNUNET_assert (0 == memcmp (&aa->peer, &des->peer, + sizeof (struct GNUNET_PeerIdentity))); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Deleting address for peer `%s': `%s' %u\n", - GNUNET_i2s (&aa->peer), aa->plugin, aa->session_id); - - if (GNUNET_YES == destroy_address (aa)) - recalculate_assigned_bw (); - return GNUNET_OK; - } - /* session != 0, just remove session */ - if (aa->session_id != info->session_id) - return GNUNET_OK; /* irrelevant */ - if (aa->session_id != 0) - GNUNET_break (0 == strcmp (info->plugin, aa->plugin)); - /* session died */ -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Deleting session for peer `%s': `%s' %u\n", - GNUNET_i2s (&aa->peer), aa->plugin, aa->session_id); -#endif - aa->session_id = 0; - if (GNUNET_YES == aa->active) + if (des->session_id == 0) { - aa->active = GNUNET_NO; - active_addr_count--; - recalculate_assigned_bw (); - } + /* Session == 0, remove full address */ + if ((0 == strcmp (des->plugin, aa->plugin)) && + (aa->addr_len == des->addr_len) && + (0 == memcmp (des->addr, aa->addr, aa->addr_len))) + { - /* session == 0 and addrlen == 0 : destroy address */ - if (aa->addr_len == 0) - { -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Deleting session and address for peer `%s': `%s' %u\n", - GNUNET_i2s (&aa->peer), aa->plugin, aa->session_id); -#endif - (void) destroy_address (aa); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Deleting full address for peer `%s' session %u %p\n", + GNUNET_i2s (&aa->peer), aa->session_id, aa); + + /* Notify solver about deletion */ + handle->s_del (handle->solver, handle->addresses, aa, GNUNET_NO); + destroy_address (handle, aa); + dc->result = GNUNET_NO; + return GNUNET_OK; /* Continue iteration */ + } } else { - /* session was set to 0, update address */ -#if HAVE_LIBGLPK - if (ats_mode == MLP) - GAS_mlp_address_update (mlp, addresses, aa); -#endif - } + /* Session != 0, just remove session */ + if (aa->session_id != des->session_id) + return GNUNET_OK; /* irrelevant */ + + if ((aa->session_id != 0) && + (0 != strcmp (des->plugin, aa->plugin))) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Different plugins during removal: `%s' vs `%s' \n", + des->plugin, aa->plugin); + GNUNET_break (0); + return GNUNET_OK; + } + if (aa->addr_len == 0) + { + /* Inbound connection died, delete full address */ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Deleting inbound address for peer `%s': `%s' session %u\n", + GNUNET_i2s (&aa->peer), aa->plugin, aa->session_id); + + /* Notify solver about deletion */ + handle->s_del (handle->solver, handle->addresses, aa, GNUNET_NO); + destroy_address (handle, aa); + dc->result = GNUNET_NO; + return GNUNET_OK; /* Continue iteration */ + } + else + { + /* Session died */ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Deleting session for peer `%s': `%s' %u\n", + GNUNET_i2s (&aa->peer), aa->plugin, aa->session_id); + /* Notify solver to delete session */ + handle->s_del (handle->solver, handle->addresses, aa, GNUNET_YES); + aa->session_id = 0; + return GNUNET_OK; + } + } return GNUNET_OK; } void -GAS_addresses_destroy (const struct GNUNET_PeerIdentity *peer, +GAS_addresses_destroy (struct GAS_Addresses_Handle *handle, + const struct GNUNET_PeerIdentity *peer, const char *plugin_name, const void *plugin_addr, size_t plugin_addr_len, uint32_t session_id) { - struct ATS_Address *aa; + struct ATS_Address *ea; + struct DestroyContext dc; - if (GNUNET_NO == running) + if (GNUNET_NO == handle->running) return; - GNUNET_break (0 < strlen (plugin_name)); - aa = create_address (peer, plugin_name, plugin_addr, plugin_addr_len, session_id); - - GNUNET_CONTAINER_multihashmap_get_multiple (addresses, &peer->hashPubKey, - &destroy_by_session_id, aa); - - free_address (aa); -} - - -/** - * Find a "good" address to use for a peer. If we already have an existing - * address, we stick to it. Otherwise, we pick by lowest distance and then - * by lowest latency. - * - * @param cls the 'struct ATS_Address**' where we store the result - * @param key unused - * @param value another 'struct ATS_Address*' to consider using - * @return GNUNET_OK (continue to iterate) - */ -static int -find_address_it (void *cls, const GNUNET_HashCode * key, void *value) -{ - struct ATS_Address **ap = cls; - struct ATS_Address *aa = (struct ATS_Address *) value; - struct ATS_Address *ab = *ap; - struct GNUNET_TIME_Absolute now; - - now = GNUNET_TIME_absolute_get(); - - if (aa->blocked_until.abs_value == GNUNET_TIME_absolute_max (now, aa->blocked_until).abs_value) - { - /* This address is blocked for suggestion */ - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Address %p blocked for suggestion for %llu ms \n", - aa, - GNUNET_TIME_absolute_get_difference(now, aa->blocked_until).rel_value); - return GNUNET_OK; - } - - aa->block_interval = GNUNET_TIME_relative_add (aa->block_interval, ATS_BLOCKING_DELTA); - aa->blocked_until = GNUNET_TIME_absolute_add (now, aa->block_interval); + /* Get existing address */ + ea = lookup_address (handle, peer, plugin_name, plugin_addr, plugin_addr_len, + session_id, NULL, 0); GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Address %p ready for suggestion, block interval now %llu \n", aa, aa->block_interval); + "Received `%s' for peer `%s' address %p session %u\n", + "ADDRESS DESTROY", + GNUNET_i2s (peer), ea, session_id); - /* FIXME this is a hack */ - - - if (NULL != ab) + if (ea == NULL) { - if ((0 == strcmp (ab->plugin, "tcp")) && - (0 == strcmp (aa->plugin, "tcp"))) - { - if ((0 != ab->addr_len) && - (0 == aa->addr_len)) - { - /* saved address was an outbound address, but we have an inbound address */ - *ap = aa; - return GNUNET_OK; - } - if (0 == ab->addr_len) - { - /* saved address was an inbound address, so do not overwrite */ - return GNUNET_OK; - } - } + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Tried to destroy unknown address for peer `%s' `%s' session id %u\n", + GNUNET_i2s (peer), plugin_name, session_id); + return; } - /* FIXME end of hack */ - if (NULL == ab) - { - *ap = aa; - return GNUNET_OK; - } - if ((ntohl (ab->assigned_bw_in.value__) == 0) && - (ntohl (aa->assigned_bw_in.value__) > 0)) - { - /* stick to existing connection */ - *ap = aa; - return GNUNET_OK; - } - if (ab->atsp_distance > aa->atsp_distance) - { - /* user shorter distance */ - *ap = aa; - return GNUNET_OK; - } - if (ab->atsp_latency.rel_value > aa->atsp_latency.rel_value) - { - /* user lower latency */ - *ap = aa; - return GNUNET_OK; - } - /* don't care */ - return GNUNET_OK; + GNUNET_break (0 < strlen (plugin_name)); + dc.handle = handle; + dc.aa = create_address (peer, plugin_name, plugin_addr, plugin_addr_len, session_id); + + GNUNET_CONTAINER_multihashmap_get_multiple (handle->addresses, &peer->hashPubKey, + &destroy_by_session_id, &dc); + free_address (dc.aa); } int -GAS_addresses_in_use (const struct GNUNET_PeerIdentity *peer, +GAS_addresses_in_use (struct GAS_Addresses_Handle *handle, + const struct GNUNET_PeerIdentity *peer, const char *plugin_name, const void *plugin_addr, size_t plugin_addr_len, uint32_t session_id, int in_use) { -#if DEBUG_ATS - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Received `%s' message for peer `%s': %i\n", "ADDRESS_IN_USE", - GNUNET_i2s (peer), in_use); -#endif + struct ATS_Address *ea; - struct ATS_Address *aa; - struct ATS_Address *old; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Received `%s' for peer `%s'\n", + "ADDRESS IN USE", + GNUNET_i2s (peer)); - if (GNUNET_NO == running) + if (GNUNET_NO == handle->running) return GNUNET_SYSERR; - aa = create_address (peer, plugin_name, plugin_addr, plugin_addr_len, session_id); - old = find_exact_address (peer, aa); - free_address (aa); - - if (NULL == old) + ea = lookup_address (handle, peer, plugin_name, + plugin_addr, plugin_addr_len, + session_id, NULL, 0); + if (NULL == ea) { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Trying to set unknown address `%s', %s %u %s \n", + GNUNET_i2s (peer), + plugin_name, session_id, + (GNUNET_NO == in_use) ? "NO" : "YES"); GNUNET_break (0); return GNUNET_SYSERR; } - if (old->used == in_use) + if (ea->used == in_use) { GNUNET_break (0); GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Address in use called multiple times for peer `%s': %s -> %s \n", GNUNET_i2s (peer), - (GNUNET_NO == old->used) ? "NO" : "YES", + (GNUNET_NO == ea->used) ? "NO" : "YES", (GNUNET_NO == in_use) ? "NO" : "YES"); return GNUNET_SYSERR; } - old->used = in_use; -#if HAVE_LIBGLPK - if (ats_mode == MLP) - GAS_mlp_address_update (mlp, addresses, old); -#endif + + /* Tell solver about update */ + handle->s_update (handle->solver, handle->addresses, ea, session_id, in_use, NULL, 0); + ea->used = in_use; + return GNUNET_OK; } -void request_address_mlp (const struct GNUNET_PeerIdentity *peer) +/** + * Cancel address suggestions for a peer + * + * @param handle the address handle + * @param peer the respective peer + */ +void +GAS_addresses_request_address_cancel (struct GAS_Addresses_Handle *handle, + const struct GNUNET_PeerIdentity *peer) { - struct ATS_Address *aa; - aa = NULL; - -#if HAVE_GLPK - /* Get preferred address from MLP */ - struct ATS_PreferedAddress * paddr = NULL; - paddr = GAS_mlp_get_preferred_address (mlp, addresses, peer); - aa = paddr->address; - aa->assigned_bw_out = GNUNET_BANDWIDTH_value_init(paddr->bandwidth_out); - /* FIXME use bw in value */ - paddr->bandwidth_in = paddr->bandwidth_out; - aa->assigned_bw_in = GNUNET_BANDWIDTH_value_init (paddr->bandwidth_in); - GNUNET_free (paddr); -#endif + struct GAS_Addresses_Suggestion_Requests *cur = handle->r_head; - if (aa == NULL) + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Received request: `%s' for peer %s\n", "request_address_cancel", GNUNET_i2s (peer)); + + while (NULL != cur) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG | GNUNET_ERROR_TYPE_BULK, - "Cannot suggest address for peer `%s'\n", GNUNET_i2s (peer)); - return; + if (0 == memcmp (peer, &cur->id, sizeof (cur->id))) + break; /* found */ + cur = cur->next; } - if (aa->active == GNUNET_NO) - { - aa->active = GNUNET_YES; - active_addr_count++; - send_bw_notification (aa); - } - else + if (NULL == cur) { - /* just to be sure... */ - GAS_scheduling_transmit_address_suggestion (peer, aa->plugin, aa->addr, - aa->addr_len, aa->session_id, - aa->ats, aa->ats_count, - aa->assigned_bw_out, - aa->assigned_bw_in); + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + "No address requests pending for peer `%s', cannot remove!\n", GNUNET_i2s (peer)); + return; } - + GAS_addresses_handle_backoff_reset (handle, peer); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Removed request pending for peer `%s\n", GNUNET_i2s (peer)); + GNUNET_CONTAINER_DLL_remove (handle->r_head, handle->r_tail, cur); + GNUNET_free (cur); } -void request_address_simple (const struct GNUNET_PeerIdentity *peer) + +/** + * Add an address suggestions for a peer + * + * @param handle the address handle + * @param peer the respective peer + */ +void +GAS_addresses_request_address (struct GAS_Addresses_Handle *handle, + const struct GNUNET_PeerIdentity *peer) { + struct GAS_Addresses_Suggestion_Requests *cur = handle->r_head; struct ATS_Address *aa; - aa = NULL; + struct GNUNET_ATS_Information *ats; + unsigned int ats_count; - /* Get address with: stick to current address, lower distance, lower latency */ - GNUNET_CONTAINER_multihashmap_get_multiple (addresses, &peer->hashPubKey, - &find_address_it, &aa); - if (aa == NULL) + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Received `%s' for peer `%s'\n", + "REQUEST ADDRESS", + GNUNET_i2s (peer)); + + if (GNUNET_NO == handle->running) + return; + while (NULL != cur) + { + if (0 == memcmp (peer, &cur->id, sizeof (cur->id))) + break; /* already suggesting */ + cur = cur->next; + } + if (NULL == cur) + { + cur = GNUNET_malloc (sizeof (struct GAS_Addresses_Suggestion_Requests)); + cur->id = (*peer); + GNUNET_CONTAINER_DLL_insert (handle->r_head, handle->r_tail, cur); + } + + /* Get prefered address from solver */ + aa = (struct ATS_Address *) handle->s_get (handle->solver, handle->addresses, peer); + if (NULL == aa) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG | GNUNET_ERROR_TYPE_BULK, + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Cannot suggest address for peer `%s'\n", GNUNET_i2s (peer)); return; } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG | GNUNET_ERROR_TYPE_BULK, + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Suggesting address %p for peer `%s'\n", aa, GNUNET_i2s (peer)); - if (aa->active == GNUNET_NO) - { - aa->active = GNUNET_YES; - active_addr_count++; - if (ats_mode == SIMPLE) - { - recalculate_assigned_bw (); - } - } - else - { - /* just to be sure... */ - GAS_scheduling_transmit_address_suggestion (peer, aa->plugin, aa->addr, - aa->addr_len, aa->session_id, - aa->ats, aa->ats_count, - aa->assigned_bw_out, - aa->assigned_bw_in); - } -} + ats_count = assemble_ats_information (aa, &ats); + GAS_scheduling_transmit_address_suggestion (peer, + aa->plugin, + aa->addr, aa->addr_len, + aa->session_id, + ats, ats_count, + aa->assigned_bw_out, + aa->assigned_bw_in); + aa->block_interval = GNUNET_TIME_relative_add (aa->block_interval, ATS_BLOCKING_DELTA); + aa->blocked_until = GNUNET_TIME_absolute_add (GNUNET_TIME_absolute_get(), aa->block_interval); -void -GAS_addresses_request_address (const struct GNUNET_PeerIdentity *peer) -{ - if (GNUNET_NO == running) - return; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Address %p ready for suggestion, block interval now %llu \n", + aa, aa->block_interval); - if (ats_mode == SIMPLE) - { - request_address_simple (peer); - } - if (ats_mode == MLP) - { - request_address_mlp(peer); - } + GNUNET_free (ats); } static int -reset_address_it (void *cls, const GNUNET_HashCode * key, void *value) +reset_address_it (void *cls, const struct GNUNET_HashCode * key, void *value) { struct ATS_Address *aa = value; GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Resetting interval for peer `%s' address %p from %llu to 0\n", GNUNET_i2s (&aa->peer), aa, aa->block_interval); + "Resetting interval for peer `%s' address %p from %llu to 0\n", + GNUNET_i2s (&aa->peer), aa, aa->block_interval); aa->blocked_until = GNUNET_TIME_UNIT_ZERO_ABS; aa->block_interval = GNUNET_TIME_UNIT_ZERO; return GNUNET_OK; } + void -GAS_addresses_handle_backoff_reset (const struct GNUNET_PeerIdentity *peer) +GAS_addresses_handle_backoff_reset (struct GAS_Addresses_Handle *handle, + const struct GNUNET_PeerIdentity *peer) { - GNUNET_break (GNUNET_SYSERR != GNUNET_CONTAINER_multihashmap_get_multiple (addresses, + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Received `%s' for peer `%s'\n", + "RESET BACKOFF", + GNUNET_i2s (peer)); + + GNUNET_break (GNUNET_SYSERR != GNUNET_CONTAINER_multihashmap_get_multiple (handle->addresses, &peer->hashPubKey, &reset_address_it, NULL)); } - -// FIXME: this function should likely end up in the LP-subsystem and -// not with 'addresses' in the future... void -GAS_addresses_change_preference (const struct GNUNET_PeerIdentity *peer, +GAS_addresses_change_preference (struct GAS_Addresses_Handle *handle, + void *client, + const struct GNUNET_PeerIdentity *peer, enum GNUNET_ATS_PreferenceKind kind, float score) { - if (GNUNET_NO == running) + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Received `%s' for peer `%s' for client %p\n", + "CHANGE PREFERENCE", + GNUNET_i2s (peer), client); + + if (GNUNET_NO == handle->running) return; -#if HAVE_LIBGLPK - if (ats_mode == MLP) - GAS_mlp_address_change_preference (mlp, peer, kind, score); -#endif -} + if (GNUNET_NO == GNUNET_CONTAINER_multihashmap_contains (handle->addresses, + &peer->hashPubKey)) + { + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + "Received `%s' for unknown peer `%s' from client %p\n", + "CHANGE PREFERENCE", + GNUNET_i2s (peer), client); + return; + } + /* Tell solver about update */ + handle->s_pref (handle->solver, client, peer, kind, score); +} -/** - * Initialize address subsystem. - * - * @param cfg configuration to use - * @param stats the statistics handle to use - */ -void -GAS_addresses_init (const struct GNUNET_CONFIGURATION_Handle *cfg, - const struct GNUNET_STATISTICS_Handle *stats) +static unsigned int +load_quotas (const struct GNUNET_CONFIGURATION_Handle *cfg, unsigned long long *out_dest, unsigned long long *in_dest, int dest_length) { - int mode; + char *network_str[GNUNET_ATS_NetworkTypeCount] = GNUNET_ATS_NetworkTypeString; + char * entry_in = NULL; + char * entry_out = NULL; + char * quota_out_str; + char * quota_in_str; + int c; + int res; + + for (c = 0; (c < GNUNET_ATS_NetworkTypeCount) && (c < dest_length); c++) + { + in_dest[c] = 0; + out_dest[c] = 0; + GNUNET_asprintf (&entry_out, "%s_QUOTA_OUT", network_str[c]); + GNUNET_asprintf (&entry_in, "%s_QUOTA_IN", network_str[c]); - char *quota_wan_in_str; - char *quota_wan_out_str; + /* quota out */ + if (GNUNET_OK == GNUNET_CONFIGURATION_get_value_string(cfg, "ats", entry_out, "a_out_str)) + { + res = GNUNET_NO; + if (0 == strcmp(quota_out_str, BIG_M_STRING)) + { + out_dest[c] = GNUNET_ATS_MaxBandwidth; + res = GNUNET_YES; + } + if ((GNUNET_NO == res) && (GNUNET_OK == GNUNET_STRINGS_fancy_size_to_bytes (quota_out_str, &out_dest[c]))) + res = GNUNET_YES; + if ((GNUNET_NO == res) && (GNUNET_OK == GNUNET_CONFIGURATION_get_value_number (cfg, "ats", entry_out, &out_dest[c]))) + res = GNUNET_YES; - running = GNUNET_NO; + if (GNUNET_NO == res) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("Could not load quota for network `%s': `%s', assigning default bandwidth %llu\n"), + network_str[c], quota_out_str, GNUNET_ATS_DefaultBandwidth); + out_dest[c] = GNUNET_ATS_DefaultBandwidth; + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_INFO, _("Outbound quota configure for network `%s' is %llu\n"), + network_str[c], out_dest[c]); + } + GNUNET_free (quota_out_str); + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, _("No outbound quota configured for network `%s', assigning default bandwidth %llu\n"), + network_str[c], GNUNET_ATS_DefaultBandwidth); + out_dest[c] = GNUNET_ATS_DefaultBandwidth; + } - addresses = GNUNET_CONTAINER_multihashmap_create (128); - GNUNET_assert (NULL != addresses); + /* quota in */ + if (GNUNET_OK == GNUNET_CONFIGURATION_get_value_string(cfg, "ats", entry_in, "a_in_str)) + { + res = GNUNET_NO; + if (0 == strcmp(quota_in_str, BIG_M_STRING)) + { + in_dest[c] = GNUNET_ATS_MaxBandwidth; + res = GNUNET_YES; + } + if ((GNUNET_NO == res) && (GNUNET_OK == GNUNET_STRINGS_fancy_size_to_bytes (quota_in_str, &in_dest[c]))) + res = GNUNET_YES; + if ((GNUNET_NO == res) && (GNUNET_OK == GNUNET_CONFIGURATION_get_value_number (cfg, "ats", entry_in, &in_dest[c]))) + res = GNUNET_YES; - if (GNUNET_OK == GNUNET_CONFIGURATION_get_value_string(cfg, "ats", "WAN_QUOTA_IN", "a_wan_in_str)) - { - if (0 == strcmp(quota_wan_in_str, "unlimited") || - (GNUNET_SYSERR == GNUNET_STRINGS_fancy_size_to_bytes (quota_wan_in_str, &wan_quota_in))) - wan_quota_in = (UINT32_MAX) /10; + if (GNUNET_NO == res) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("Could not load quota for network `%s': `%s', assigning default bandwidth %llu\n"), + network_str[c], quota_in_str, GNUNET_ATS_DefaultBandwidth); + in_dest[c] = GNUNET_ATS_DefaultBandwidth; + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_INFO, _("Inbound quota configured for network `%s' is %llu\n"), + network_str[c], in_dest[c]); + } + GNUNET_free (quota_in_str); + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, _("No outbound quota configure for network `%s', assigning default bandwidth %llu\n"), + network_str[c], GNUNET_ATS_DefaultBandwidth); + out_dest[c] = GNUNET_ATS_DefaultBandwidth; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Loaded quota for network `%s' (in/out): %llu %llu\n", network_str[c], in_dest[c], out_dest[c]); + GNUNET_free (entry_out); + GNUNET_free (entry_in); + } + return GNUNET_ATS_NetworkTypeCount; +} + + +static void +bandwidth_changed_cb (void *cls, struct ATS_Address *address) +{ + struct GAS_Addresses_Handle *handle = cls; + struct GAS_Addresses_Suggestion_Requests *cur; + + GNUNET_assert (handle != NULL); + GNUNET_assert (address != NULL); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Bandwidth assignment changed for peer %s \n", GNUNET_i2s(&address->peer)); + struct GNUNET_ATS_Information *ats; + unsigned int ats_count; - GNUNET_free (quota_wan_in_str); - quota_wan_in_str = NULL; + cur = handle->r_head; + while (NULL != cur) + { + if (0 == memcmp (&address->peer, &cur->id, sizeof (cur->id))) + break; /* we have an address request pending*/ + cur = cur->next; } - else + if (NULL == cur) { - wan_quota_in = (UINT32_MAX) /10; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Nobody is interested in peer `%s' :(\n",GNUNET_i2s (&address->peer)); + return; } - if (GNUNET_OK == GNUNET_CONFIGURATION_get_value_string(cfg, "ats", "WAN_QUOTA_OUT", "a_wan_out_str)) - { - if (0 == strcmp(quota_wan_out_str, "unlimited") || - (GNUNET_SYSERR == GNUNET_STRINGS_fancy_size_to_bytes (quota_wan_out_str, &wan_quota_out))) - wan_quota_out = (UINT32_MAX) /10; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Sending bandwidth update for peer `%s'\n",GNUNET_i2s (&address->peer)); + + ats_count = assemble_ats_information (address, &ats); + GAS_scheduling_transmit_address_suggestion (&address->peer, + address->plugin, + address->addr, address->addr_len, + address->session_id, + ats, ats_count, + address->assigned_bw_out, + address->assigned_bw_in); + GNUNET_free (ats); +} - GNUNET_free (quota_wan_out_str); - quota_wan_out_str = NULL; - } - else + +/** + * Initialize address subsystem. + * + * @param cfg configuration to use + * @param stats the statistics handle to use + */ +struct GAS_Addresses_Handle * +GAS_addresses_init (const struct GNUNET_CONFIGURATION_Handle *cfg, + const struct GNUNET_STATISTICS_Handle *stats) +{ + struct GAS_Addresses_Handle *ah; + int quotas[GNUNET_ATS_NetworkTypeCount] = GNUNET_ATS_NetworkType; + unsigned long long quotas_in[GNUNET_ATS_NetworkTypeCount]; + unsigned long long quotas_out[GNUNET_ATS_NetworkTypeCount]; + int quota_count; + char *mode_str; + int c; + + ah = GNUNET_malloc (sizeof (struct GAS_Addresses_Handle)); + ah->running = GNUNET_NO; + + ah->stat = (struct GNUNET_STATISTICS_Handle *) stats; + /* Initialize the addresses database */ + ah->addresses = GNUNET_CONTAINER_multihashmap_create (128, GNUNET_NO); + GNUNET_assert (NULL != ah->addresses); + + /* Figure out configured solution method */ + if (GNUNET_SYSERR == GNUNET_CONFIGURATION_get_value_string (cfg, "ats", "MODE", &mode_str)) { - wan_quota_out = (UINT32_MAX) /10; + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "No ressource assignment method configured, using simplistic approch\n"); + ah->ats_mode = MODE_SIMPLISTIC; } - - mode = GNUNET_CONFIGURATION_get_value_yesno (cfg, "ats", "MLP"); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "MLP mode %u", mode); - switch (mode) + else { - /* MLP = YES */ - case GNUNET_YES: -#if HAVE_LIBGLPK - ats_mode = MLP; - /* Init the MLP solver with default values */ - mlp = GAS_mlp_init (cfg, stats, MLP_MAX_EXEC_DURATION, MLP_MAX_ITERATIONS); - if (NULL == mlp) + for (c = 0; c < strlen (mode_str); c++) + mode_str[c] = toupper (mode_str[c]); + if (0 == strcmp (mode_str, "SIMPLISTIC")) { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "MLP mode was configured, but libglpk is not installed, switching to simple mode\n"); - GNUNET_STATISTICS_update (GSA_stats, "MLP mode enabled", 0, GNUNET_NO); - break; + ah->ats_mode = MODE_SIMPLISTIC; + } + else if (0 == strcmp (mode_str, "MLP")) + { + ah->ats_mode = MODE_MLP; +#if !HAVE_LIBGLPK + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Assignment method `%s' configured, but GLPK is not availabe, please install \n", mode_str); + ah->ats_mode = MODE_SIMPLISTIC; +#endif } else { - GNUNET_STATISTICS_update (GSA_stats, "MLP enabled", 1, GNUNET_NO); - break; + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Invalid ressource assignment method `%s' configured, using simplistic approch\n", mode_str); + ah->ats_mode = MODE_SIMPLISTIC; } + GNUNET_free (mode_str); + } + /* Start configured solution method */ + switch (ah->ats_mode) + { + case MODE_MLP: + /* Init the MLP solver with default values */ +#if HAVE_LIBGLPK + ah->ats_mode = MODE_MLP; + ah->s_init = &GAS_mlp_init; + ah->s_add = &GAS_mlp_address_add; + ah->s_update = &GAS_mlp_address_update; + ah->s_get = &GAS_mlp_get_preferred_address; + ah->s_pref = &GAS_mlp_address_change_preference; + ah->s_del = &GAS_mlp_address_delete; + ah->s_done = &GAS_mlp_done; #else - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "MLP mode was configured, but libglpk is not installed, switching to simple mode"); - GNUNET_STATISTICS_update (GSA_stats, "MLP enabled", 0, GNUNET_NO); - ats_mode = SIMPLE; - break; + GNUNET_free (ah); + return NULL; #endif - /* MLP = NO */ - case GNUNET_NO: - GNUNET_STATISTICS_update (GSA_stats, "MLP enabled", 0, GNUNET_NO); - ats_mode = SIMPLE; break; - /* No configuration value */ - case GNUNET_SYSERR: - GNUNET_STATISTICS_update (GSA_stats, "MLP enabled", 0, GNUNET_NO); - ats_mode = SIMPLE; + case MODE_SIMPLISTIC: + /* Init the simplistic solver with default values */ + ah->ats_mode = MODE_SIMPLISTIC; + ah->s_init = &GAS_simplistic_init; + ah->s_add = &GAS_simplistic_address_add; + ah->s_update = &GAS_simplistic_address_update; + ah->s_get = &GAS_simplistic_get_preferred_address; + ah->s_pref = &GAS_simplistic_address_change_preference; + ah->s_del = &GAS_simplistic_address_delete; + ah->s_done = &GAS_simplistic_done; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "ATS started in %s mode\n", "SIMPLISTIC"); break; default: + return NULL; break; } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "ATS started with %s mode\n", (SIMPLE == ats_mode) ? "SIMPLE" : "MLP"); - running = GNUNET_YES; + + GNUNET_assert (NULL != ah->s_init); + GNUNET_assert (NULL != ah->s_add); + GNUNET_assert (NULL != ah->s_update); + GNUNET_assert (NULL != ah->s_get); + GNUNET_assert (NULL != ah->s_pref); + GNUNET_assert (NULL != ah->s_del); + GNUNET_assert (NULL != ah->s_done); + + quota_count = load_quotas(cfg, quotas_in, quotas_out, GNUNET_ATS_NetworkTypeCount); + + ah->solver = ah->s_init (cfg, stats, quotas, quotas_in, quotas_out, quota_count, &bandwidth_changed_cb, ah); + if (NULL == ah->solver) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Failed to initialize solver!\n"); + GNUNET_free (ah); + return NULL; + } + + /* up and running */ + ah->running = GNUNET_YES; + return ah; } @@ -903,24 +1215,28 @@ GAS_addresses_init (const struct GNUNET_CONFIGURATION_Handle *cfg, * @return GNUNET_OK (continue to iterate) */ static int -free_address_it (void *cls, const GNUNET_HashCode * key, void *value) +free_address_it (void *cls, const struct GNUNET_HashCode * key, void *value) { + struct GAS_Addresses_Handle *handle = cls; struct ATS_Address *aa = value; - - destroy_address (aa); + handle->s_del (handle->solver, handle->addresses, aa, GNUNET_NO); + destroy_address (handle, aa); return GNUNET_OK; } void -GAS_addresses_destroy_all () +GAS_addresses_destroy_all (struct GAS_Addresses_Handle *handle) { - if (GNUNET_NO == running) + if (GNUNET_NO == handle->running) return; - if (addresses != NULL) - GNUNET_CONTAINER_multihashmap_iterate (addresses, &free_address_it, NULL); - GNUNET_assert (active_addr_count == 0); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Received `%s'\n", + "DESTROY ALL"); + + if (handle->addresses != NULL) + GNUNET_CONTAINER_multihashmap_iterate (handle->addresses, &free_address_it, handle); } @@ -928,18 +1244,147 @@ GAS_addresses_destroy_all () * Shutdown address subsystem. */ void -GAS_addresses_done () +GAS_addresses_done (struct GAS_Addresses_Handle *handle) { - GAS_addresses_destroy_all (); - running = GNUNET_NO; - GNUNET_CONTAINER_multihashmap_destroy (addresses); - addresses = NULL; -#if HAVE_LIBGLPK - if (ats_mode == MLP) + struct GAS_Addresses_Suggestion_Requests *cur; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Shutting down addresses\n"); + GNUNET_assert (NULL != handle); + GAS_addresses_destroy_all (handle); + handle->running = GNUNET_NO; + GNUNET_CONTAINER_multihashmap_destroy (handle->addresses); + handle->addresses = NULL; + while (NULL != (cur = handle->r_head)) { - GAS_mlp_done (mlp); + GNUNET_CONTAINER_DLL_remove (handle->r_head, handle->r_tail, cur); + GNUNET_free (cur); } -#endif + handle->s_done (handle->solver); + GNUNET_free (handle); + /* Stop configured solution method */ + +} + +struct PeerIteratorContext +{ + GNUNET_ATS_Peer_Iterator it; + void *it_cls; + struct GNUNET_CONTAINER_MultiHashMap *peers_returned; +}; + +static int +peer_it (void *cls, + const struct GNUNET_HashCode * key, + void *value) +{ + struct PeerIteratorContext *ip_ctx = cls; + struct GNUNET_PeerIdentity tmp; + + if (GNUNET_NO == GNUNET_CONTAINER_multihashmap_contains(ip_ctx->peers_returned, key)) + { + GNUNET_CONTAINER_multihashmap_put(ip_ctx->peers_returned, key, NULL, GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_FAST); + tmp.hashPubKey = (*key); + ip_ctx->it (ip_ctx->it_cls, &tmp); + } + + return GNUNET_OK; +} + +/** + * Return all peers currently known to ATS + * + * @param handle the address handle + * @param p_it the iterator to call for every peer, callbach with id == NULL + * when done + * @param p_it_cls the closure for the iterator + */ +void +GAS_addresses_iterate_peers (struct GAS_Addresses_Handle *handle, GNUNET_ATS_Peer_Iterator p_it, void *p_it_cls) +{ + struct PeerIteratorContext ip_ctx; + unsigned int size; + + if (NULL == p_it) + return; + GNUNET_assert (NULL != handle->addresses); + + size = GNUNET_CONTAINER_multihashmap_size(handle->addresses); + if (0 != size) + { + ip_ctx.it = p_it; + ip_ctx.it_cls = p_it_cls; + ip_ctx.peers_returned = GNUNET_CONTAINER_multihashmap_create (size, GNUNET_NO); + GNUNET_CONTAINER_multihashmap_iterate (handle->addresses, &peer_it, &ip_ctx); + GNUNET_CONTAINER_multihashmap_destroy (ip_ctx.peers_returned); + } + p_it (p_it_cls, NULL); +} + +struct PeerInfoIteratorContext +{ + GNUNET_ATS_PeerInfo_Iterator it; + void *it_cls; +}; + + +static int +peerinfo_it (void *cls, + const struct GNUNET_HashCode * key, + void *value) +{ + struct PeerInfoIteratorContext *pi_ctx = cls; + struct ATS_Address *addr = (struct ATS_Address *) value; + struct GNUNET_ATS_Information *ats; + uint32_t ats_count; + + if (NULL != pi_ctx->it) + { + ats_count = assemble_ats_information (addr, &ats); + + pi_ctx->it (pi_ctx->it_cls, + &addr->peer, + addr->plugin, + addr->addr, addr->addr_len, + addr->active, + ats, ats_count, + addr->assigned_bw_out, + addr->assigned_bw_in); + GNUNET_free (ats); + } + return GNUNET_YES; +} + + +/** + * Return all peers currently known to ATS + * + * @param handle the address handle + * @param peer the respective peer + * @param pi_it the iterator to call for every peer + * @param pi_it_cls the closure for the iterator + */ +void +GAS_addresses_get_peer_info (struct GAS_Addresses_Handle *handle, + const struct GNUNET_PeerIdentity *peer, + GNUNET_ATS_PeerInfo_Iterator pi_it, + void *pi_it_cls) +{ + struct PeerInfoIteratorContext pi_ctx; + struct GNUNET_BANDWIDTH_Value32NBO zero_bw; + GNUNET_assert (NULL != peer); + GNUNET_assert (NULL != handle->addresses); + if (NULL == pi_it) + return; /* does not make sense without callback */ + + zero_bw = GNUNET_BANDWIDTH_value_init (0); + pi_ctx.it = pi_it; + pi_ctx.it_cls = pi_it_cls; + + GNUNET_CONTAINER_multihashmap_get_multiple (handle->addresses, &peer->hashPubKey, &peerinfo_it, &pi_ctx); + + if (NULL != pi_it) + pi_it (pi_it_cls, NULL, NULL, NULL, 0, GNUNET_NO, NULL, 0, zero_bw, zero_bw); } diff --git a/src/ats/gnunet-service-ats_addresses.h b/src/ats/gnunet-service-ats_addresses.h index fe07563..b774cff 100644 --- a/src/ats/gnunet-service-ats_addresses.h +++ b/src/ats/gnunet-service-ats_addresses.h @@ -32,46 +32,88 @@ #include "gnunet_statistics_service.h" #include "ats.h" +#define ATS_BLOCKING_DELTA GNUNET_TIME_relative_multiply(GNUNET_TIME_UNIT_MILLISECONDS, 100) + +struct GAS_Addresses_Handle; + +/** + * Address with additional information + */ struct ATS_Address { + /** + * Next element in DLL + */ struct ATS_Address *next; + /** + * Previous element in DLL + */ struct ATS_Address *prev; + /** + * Peer ID + */ struct GNUNET_PeerIdentity peer; - size_t addr_len; - + /** + * Session ID, 0 if no session is given + */ uint32_t session_id; - uint32_t ats_count; - + /** + * Address + */ const void *addr; - char *plugin; + /** + * Address length + */ + size_t addr_len; - void *mlp_information; + /** + * Plugin name + */ + char *plugin; - struct GNUNET_ATS_Information *ats; + /** + * Solver specific information for this address + */ + void *solver_information; + /* CHECK USAGE */ struct GNUNET_TIME_Relative atsp_latency; + /* CHECK USAGE */ struct GNUNET_BANDWIDTH_Value32NBO atsp_utilization_in; + /* CHECK USAGE */ struct GNUNET_BANDWIDTH_Value32NBO atsp_utilization_out; + + /* CHECK USAGE */ uint32_t atsp_distance; + /* CHECK USAGE */ uint32_t atsp_cost_wan; + /* CHECK USAGE */ uint32_t atsp_cost_lan; + /* CHECK USAGE */ uint32_t atsp_cost_wlan; + /* CHECK USAGE */ uint32_t atsp_network_type; + /** + * Inbound bandwidth assigned by solver in NBO + */ struct GNUNET_BANDWIDTH_Value32NBO assigned_bw_in; + /** + * Outbound bandwidth assigned by solver in NBO + */ struct GNUNET_BANDWIDTH_Value32NBO assigned_bw_out; /** @@ -95,36 +137,128 @@ struct ATS_Address int used; }; + +/** + * Callback to call from solver when bandwidth for address has changed + * + * @param address the with changed bandwidth assigned + */ + +typedef void + (*GAS_bandwidth_changed_cb) (void *cls, struct ATS_Address *address); + +/** + * Init the simplistic problem solving component + * + * Quotas: + * network[i] contains the network type as type GNUNET_ATS_NetworkType[i] + * out_quota[i] contains outbound quota for network type i + * in_quota[i] contains inbound quota for network type i + * + * Example + * network = {GNUNET_ATS_NET_UNSPECIFIED, GNUNET_ATS_NET_LOOPBACK, GNUNET_ATS_NET_LAN, GNUNET_ATS_NET_WAN, GNUNET_ATS_NET_WLAN} + * network[2] == GNUNET_ATS_NET_LAN + * out_quota[2] == 65353 + * in_quota[2] == 65353 + * + * @param cfg configuration handle + * @param stats the GNUNET_STATISTICS handle + * @param network array of GNUNET_ATS_NetworkType with length dest_length + * @param out_quota array of outbound quotas + * @param in_quota array of outbound quota + * @param bw_changed_cb callback to call when assigned changes + * @return handle for the solver on success, NULL on fail + */ +typedef void * + (*GAS_solver_init) (const struct GNUNET_CONFIGURATION_Handle *cfg, + const struct GNUNET_STATISTICS_Handle *stats, + int *network, + unsigned long long *out_quota, + unsigned long long *in_quota, + int dest_length, + GAS_bandwidth_changed_cb bw_changed_cb, + void *bw_changed_cb_cls); + + +typedef void +(*GAS_solver_address_change_preference) (void *solver, + void *client, + const struct GNUNET_PeerIdentity *peer, + enum GNUNET_ATS_PreferenceKind kind, + float score); + +/** + * Add a single address to the solver + * + * @param solver the solver Handle + * @param addresses the address hashmap containing all addresses + * @param address the address to add + */ +typedef void +(*GAS_solver_address_add) (void *solver, + struct GNUNET_CONTAINER_MultiHashMap * addresses, + struct ATS_Address *address); + + + +typedef void + (*GAS_solver_address_delete) (void *solver, + struct GNUNET_CONTAINER_MultiHashMap *addresses, + struct ATS_Address *address, + int session_only); + +typedef void +(*GAS_solver_address_update) (void *solver, + struct GNUNET_CONTAINER_MultiHashMap *addresses, + struct ATS_Address *address, + uint32_t session, + int in_use, + const struct GNUNET_ATS_Information *atsi, + uint32_t atsi_count); + + +typedef const struct ATS_Address * +(*GAS_solver_get_preferred_address) (void *solver, + struct GNUNET_CONTAINER_MultiHashMap *addresses, + const struct GNUNET_PeerIdentity *peer); + + +typedef void + (*GAS_solver_done) (void *solver); + + /** * Initialize address subsystem. * * @param cfg configuration to use * @param stats the statistics handle to use */ -void +struct GAS_Addresses_Handle * GAS_addresses_init (const struct GNUNET_CONFIGURATION_Handle *cfg, const struct GNUNET_STATISTICS_Handle *stats); - /** * Shutdown address subsystem. */ void -GAS_addresses_done (void); +GAS_addresses_done (struct GAS_Addresses_Handle *handle); void -GAS_addresses_handle_backoff_reset (const struct GNUNET_PeerIdentity *peer); +GAS_addresses_handle_backoff_reset (struct GAS_Addresses_Handle *handle, + const struct GNUNET_PeerIdentity *peer); /** * This address is now used or not used anymore */ int -GAS_addresses_in_use (const struct GNUNET_PeerIdentity *peer, +GAS_addresses_in_use (struct GAS_Addresses_Handle *handle, + const struct GNUNET_PeerIdentity *peer, const char *plugin_name, const void *plugin_addr, size_t plugin_addr_len, uint32_t session_id, int in_use); void -GAS_addresses_update (const struct GNUNET_PeerIdentity *peer, +GAS_addresses_update (struct GAS_Addresses_Handle *handle, + const struct GNUNET_PeerIdentity *peer, const char *plugin_name, const void *plugin_addr, size_t plugin_addr_len, uint32_t session_id, const struct GNUNET_ATS_Information *atsi, @@ -132,32 +266,82 @@ GAS_addresses_update (const struct GNUNET_PeerIdentity *peer, void -GAS_addresses_destroy (const struct GNUNET_PeerIdentity *peer, +GAS_addresses_destroy (struct GAS_Addresses_Handle *handle, + const struct GNUNET_PeerIdentity *peer, const char *plugin_name, const void *plugin_addr, size_t plugin_addr_len, uint32_t session_id); void -GAS_addresses_destroy_all (void); +GAS_addresses_destroy_all (struct GAS_Addresses_Handle *handle); -// FIXME: this function should likely end up in the LP-subsystem and -// not with 'addresses' in the future... -// Note: this call should trigger an address suggestion -// (GAS_scheduling_transmit_address_suggestion) +/** + * Cancel address suggestions for a peer + * + * @param peer the respective peer + */ void -GAS_addresses_request_address (const struct GNUNET_PeerIdentity *peer); +GAS_addresses_request_address_cancel (struct GAS_Addresses_Handle *handle, + const struct GNUNET_PeerIdentity *peer); +void +GAS_addresses_request_address (struct GAS_Addresses_Handle *handle, + const struct GNUNET_PeerIdentity *peer); -// FIXME: this function should likely end up in the LP-subsystem and -// not with 'addresses' in the future... void -GAS_addresses_change_preference (const struct GNUNET_PeerIdentity *peer, +GAS_addresses_change_preference (struct GAS_Addresses_Handle *handle, + void *client, + const struct GNUNET_PeerIdentity *peer, enum GNUNET_ATS_PreferenceKind kind, float score); +void +GAS_addresses_add (struct GAS_Addresses_Handle *handle, + const struct GNUNET_PeerIdentity *peer, + const char *plugin_name, const void *plugin_addr, + size_t plugin_addr_len, uint32_t session_id, + const struct GNUNET_ATS_Information *atsi, + uint32_t atsi_count); + + +typedef void (*GNUNET_ATS_Peer_Iterator) (void *p_it_cls, + const struct GNUNET_PeerIdentity *id); -/* FIXME: add performance request API */ +/** + * Return all peers currently known to ATS + * + * @param p_it the iterator to call for every peer + * @param p_it_cls the closure for the iterator + */ +void +GAS_addresses_iterate_peers (struct GAS_Addresses_Handle *handle, + GNUNET_ATS_Peer_Iterator p_it, + void *p_it_cls); + +typedef void (*GNUNET_ATS_PeerInfo_Iterator) (void *p_it_cls, + const struct GNUNET_PeerIdentity *id, + const char *plugin_name, + const void *plugin_addr, size_t plugin_addr_len, + const int address_active, + const struct GNUNET_ATS_Information *atsi, + uint32_t atsi_count, + struct GNUNET_BANDWIDTH_Value32NBO + bandwidth_out, + struct GNUNET_BANDWIDTH_Value32NBO bandwidth_in); + +/** + * Return information all peers currently known to ATS + * + * @param peer the respective peer + * @param pi_it the iterator to call for every peer + * @param pi_it_cls the closure for the iterator + */ +void +GAS_addresses_get_peer_info (struct GAS_Addresses_Handle *handle, + const struct GNUNET_PeerIdentity *peer, + GNUNET_ATS_PeerInfo_Iterator pi_it, + void *pi_it_cls); #endif diff --git a/src/ats/gnunet-service-ats_addresses_mlp.c b/src/ats/gnunet-service-ats_addresses_mlp.c index 8bfa010..98a77ae 100644 --- a/src/ats/gnunet-service-ats_addresses_mlp.c +++ b/src/ats/gnunet-service-ats_addresses_mlp.c @@ -31,6 +31,8 @@ #include "gnunet_statistics_service.h" #include "glpk.h" +#define LOG(kind,...) GNUNET_log_from (kind, "ats-mlp",__VA_ARGS__) + #define WRITE_MLP GNUNET_NO #define DEBUG_ATS GNUNET_NO #define VERBOSE_GLPK GNUNET_NO @@ -48,68 +50,46 @@ mlp_solve_to_string (int retcode) switch (retcode) { case 0: return "ok"; - break; case GLP_EBADB: return "invalid basis"; - break; case GLP_ESING: return "singular matrix"; - break; case GLP_ECOND: return "ill-conditioned matrix"; - break; case GLP_EBOUND: return "invalid bounds"; - break; case GLP_EFAIL: return "solver failed"; - break; case GLP_EOBJLL: return "objective lower limit reached"; - break; case GLP_EOBJUL: return "objective upper limit reached"; - break; case GLP_EITLIM: return "iteration limit exceeded"; - break; case GLP_ETMLIM: return "time limit exceeded"; - break; case GLP_ENOPFS: return "no primal feasible solution"; - break; case GLP_EROOT: return "root LP optimum not provided"; - break; case GLP_ESTOP: return "search terminated by application"; - break; case GLP_EMIPGAP: return "relative mip gap tolerance reached"; - break; case GLP_ENOFEAS: return "no dual feasible solution"; - break; case GLP_ENOCVG: return "no convergence"; - break; case GLP_EINSTAB: return "numerical instability"; - break; case GLP_EDATA: return "invalid data"; - break; case GLP_ERANGE: return "result out of range"; - break; default: GNUNET_break (0); return "unknown error"; - break; } - GNUNET_break (0); - return "unknown error"; } @@ -124,29 +104,20 @@ mlp_status_to_string (int retcode) switch (retcode) { case GLP_UNDEF: return "solution is undefined"; - break; case GLP_FEAS: return "solution is feasible"; - break; case GLP_INFEAS: return "solution is infeasible"; - break; case GLP_NOFEAS: return "no feasible solution exists"; - break; case GLP_OPT: return "solution is optimal"; - break; case GLP_UNBND: return "solution is unbounded"; - break; default: GNUNET_break (0); return "unknown error"; - break; } - GNUNET_break (0); - return "unknown error"; } /** @@ -162,37 +133,26 @@ mlp_ats_to_string (int ats_index) switch (ats_index) { case GNUNET_ATS_ARRAY_TERMINATOR: return "GNUNET_ATS_ARRAY_TERMINATOR"; - break; case GNUNET_ATS_UTILIZATION_UP: return "GNUNET_ATS_UTILIZATION_UP"; - break; case GNUNET_ATS_UTILIZATION_DOWN: return "GNUNET_ATS_UTILIZATION_DOWN"; - break; case GNUNET_ATS_COST_LAN: return "GNUNET_ATS_COST_LAN"; - break; case GNUNET_ATS_COST_WAN: return "GNUNET_ATS_COST_LAN"; - break; case GNUNET_ATS_COST_WLAN: return "GNUNET_ATS_COST_WLAN"; - break; case GNUNET_ATS_NETWORK_TYPE: return "GNUNET_ATS_NETWORK_TYPE"; - break; case GNUNET_ATS_QUALITY_NET_DELAY: return "GNUNET_ATS_QUALITY_NET_DELAY"; - break; case GNUNET_ATS_QUALITY_NET_DISTANCE: return "GNUNET_ATS_QUALITY_NET_DISTANCE"; - break; default: + GNUNET_break (0); return "unknown"; - break; } - GNUNET_break (0); - return "unknown error"; } /** @@ -278,7 +238,7 @@ mlp_delete_problem (struct GAS_MLP_Handle *mlp) * @return GNUNET_OK to continue */ static int -create_constraint_it (void *cls, const GNUNET_HashCode * key, void *value) +create_constraint_it (void *cls, const struct GNUNET_HashCode * key, void *value) { struct GAS_MLP_Handle *mlp = cls; struct ATS_Address *address = value; @@ -286,8 +246,8 @@ create_constraint_it (void *cls, const GNUNET_HashCode * key, void *value) unsigned int row_index; char *name; - GNUNET_assert (address->mlp_information != NULL); - mlpi = (struct MLP_information *) address->mlp_information; + GNUNET_assert (address->solver_information != NULL); + mlpi = (struct MLP_information *) address->solver_information; /* c 1) bandwidth capping * b_t + (-M) * n_t <= 0 @@ -379,6 +339,7 @@ create_constraint_it (void *cls, const GNUNET_HashCode * key, void *value) return GNUNET_OK; } +#if 0 /** * Find the required ATS information for an address * @@ -387,7 +348,6 @@ create_constraint_it (void *cls, const GNUNET_HashCode * key, void *value) * * @return the index on success, otherwise GNUNET_SYSERR */ - static int mlp_lookup_ats (struct ATS_Address *addr, int ats_index) { @@ -407,6 +367,7 @@ mlp_lookup_ats (struct ATS_Address *addr, int ats_index) else return GNUNET_SYSERR; } +#endif /** * Adds the problem constraints for all addresses @@ -599,7 +560,7 @@ mlp_add_constraints_all_addresses (struct GAS_MLP_Handle *mlp, struct GNUNET_CON /* For all addresses of this peer */ while (addr != NULL) { - mlpi = (struct MLP_information *) addr->mlp_information; + mlpi = (struct MLP_information *) addr->solver_information; /* coefficient for c 2) */ ia[mlp->ci] = peer->r_c2; @@ -650,7 +611,7 @@ mlp_add_constraints_all_addresses (struct GAS_MLP_Handle *mlp, struct GNUNET_CON for (tp = mlp->peer_head; tp != NULL; tp = tp->next) for (ta = tp->head; ta != NULL; ta = ta->next) { - mlpi = ta->mlp_information; + mlpi = ta->solver_information; value = mlpi->q_averaged[c]; mlpi->r_q[c] = mlp->r_q[c]; @@ -674,7 +635,7 @@ mlp_add_constraints_all_addresses (struct GAS_MLP_Handle *mlp, struct GNUNET_CON * @return GNUNET_OK to continue */ static int -create_columns_it (void *cls, const GNUNET_HashCode * key, void *value) +create_columns_it (void *cls, const struct GNUNET_HashCode * key, void *value) { struct GAS_MLP_Handle *mlp = cls; struct ATS_Address *address = value; @@ -682,8 +643,8 @@ create_columns_it (void *cls, const GNUNET_HashCode * key, void *value) unsigned int col; char *name; - GNUNET_assert (address->mlp_information != NULL); - mlpi = address->mlp_information; + GNUNET_assert (address->solver_information != NULL); + mlpi = address->solver_information; /* Add bandwidth column */ col = glp_add_cols (mlp->prob, 2); @@ -866,7 +827,7 @@ lp_solv: end = GNUNET_TIME_absolute_get (); duration = GNUNET_TIME_absolute_get_difference (start, end); mlp->lp_solved++; - mlp->lp_total_duration =+ duration.rel_value; + mlp->lp_total_duration += duration.rel_value; s_ctx->lp_duration = duration; GNUNET_STATISTICS_update (mlp->stats,"# LP problem solved", 1, GNUNET_NO); @@ -943,7 +904,7 @@ mlp_solve_mlp_problem (struct GAS_MLP_Handle *mlp, struct GAS_MLP_SolutionContex end = GNUNET_TIME_absolute_get (); duration = GNUNET_TIME_absolute_get_difference (start, end); mlp->mlp_solved++; - mlp->mlp_total_duration =+ duration.rel_value; + mlp->mlp_total_duration += duration.rel_value; s_ctx->mlp_duration = duration; GNUNET_STATISTICS_update (mlp->stats,"# MLP problem solved", 1, GNUNET_NO); @@ -972,7 +933,7 @@ mlp_solve_mlp_problem (struct GAS_MLP_Handle *mlp, struct GAS_MLP_SolutionContex return GNUNET_OK; } -int GAS_mlp_solve_problem (struct GAS_MLP_Handle *mlp, struct GAS_MLP_SolutionContext *ctx); +int GAS_mlp_solve_problem (void *solver, struct GAS_MLP_SolutionContext *ctx); static void @@ -996,13 +957,14 @@ mlp_scheduler (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) /** * Solves the MLP problem * - * @param mlp the MLP Handle + * @param solver the MLP Handle * @param ctx solution context * @return GNUNET_OK if could be solved, GNUNET_SYSERR on failure */ int -GAS_mlp_solve_problem (struct GAS_MLP_Handle *mlp, struct GAS_MLP_SolutionContext *ctx) +GAS_mlp_solve_problem (void *solver, struct GAS_MLP_SolutionContext *ctx) { + struct GAS_MLP_Handle *mlp = solver; int res; /* Check if solving is already running */ if (GNUNET_YES == mlp->semaphore) @@ -1080,7 +1042,7 @@ GAS_mlp_solve_problem (struct GAS_MLP_Handle *mlp, struct GAS_MLP_SolutionContex double b = 0.0; double n = 0.0; - mlpi = a->mlp_information; + mlpi = a->solver_information; b = glp_mip_col_val(mlp->prob, mlpi->c_b); mlpi->b = b; @@ -1111,15 +1073,23 @@ GAS_mlp_solve_problem (struct GAS_MLP_Handle *mlp, struct GAS_MLP_SolutionContex * * @param cfg the GNUNET_CONFIGURATION_Handle handle * @param stats the GNUNET_STATISTICS handle - * @param max_duration maximum numbers of iterations for the LP/MLP Solver - * @param max_iterations maximum time limit for the LP/MLP Solver - * @return struct GAS_MLP_Handle * on success, NULL on fail + * @param network array of GNUNET_ATS_NetworkType with length dest_length + * @param out_dest array of outbound quotas + * @param in_dest array of outbound quota + * @param dest_length array length for quota arrays + * @param bw_changed_cb callback for changed bandwidth amounts + * @param bw_changed_cb_cls cls for callback + * @return struct GAS_MLP_Handle on success, NULL on fail */ -struct GAS_MLP_Handle * +void * GAS_mlp_init (const struct GNUNET_CONFIGURATION_Handle *cfg, const struct GNUNET_STATISTICS_Handle *stats, - struct GNUNET_TIME_Relative max_duration, - unsigned int max_iterations) + int *network, + unsigned long long *out_dest, + unsigned long long *in_dest, + int dest_length, + GAS_bandwidth_changed_cb bw_changed_cb, + void *bw_changed_cb_cls) { struct GAS_MLP_Handle * mlp = GNUNET_malloc (sizeof (struct GAS_MLP_Handle)); @@ -1134,6 +1104,9 @@ GAS_mlp_init (const struct GNUNET_CONFIGURATION_Handle *cfg, char * quota_out_str; char * quota_in_str; + struct GNUNET_TIME_Relative max_duration; + long long unsigned int max_iterations; + /* Init GLPK environment */ int res = glp_init_env(); switch (res) { @@ -1167,6 +1140,18 @@ GAS_mlp_init (const struct GNUNET_CONFIGURATION_Handle *cfg, mlp->BIG_M = (double) BIG_M_VALUE; + /* Get timeout for iterations */ + if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_time(cfg, "ats", "MAX_DURATION", &max_duration)) + { + max_duration = MLP_MAX_EXEC_DURATION; + } + + /* Get maximum number of iterations */ + if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_size(cfg, "ats", "MAX_ITERATIONS", &max_iterations)) + { + max_iterations = MLP_MAX_ITERATIONS; + } + /* Get diversity coefficient from configuration */ if (GNUNET_OK == GNUNET_CONFIGURATION_get_value_size (cfg, "ats", "COEFFICIENT_D", @@ -1388,29 +1373,33 @@ update_quality (struct GAS_MLP_Handle *mlp, struct ATS_Address * address) GNUNET_i2s (&address->peer)); GNUNET_assert (NULL != address); - GNUNET_assert (NULL != address->mlp_information); - GNUNET_assert (NULL != address->ats); + GNUNET_assert (NULL != address->solver_information); +// GNUNET_assert (NULL != address->ats); - struct MLP_information *mlpi = address->mlp_information; - struct GNUNET_ATS_Information *ats = address->ats; + struct MLP_information *mlpi = address->solver_information; + //struct GNUNET_ATS_Information *ats = address->ats; GNUNET_assert (mlpi != NULL); int c; for (c = 0; c < GNUNET_ATS_QualityPropertiesCount; c++) { - int index = mlp_lookup_ats(address, mlp->q[c]); + + /* FIXME int index = mlp_lookup_ats(address, mlp->q[c]); */ + int index = GNUNET_SYSERR; if (index == GNUNET_SYSERR) continue; - + /* FIXME GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Updating address for peer `%s' value `%s': %f\n", GNUNET_i2s (&address->peer), mlp_ats_to_string(mlp->q[c]), (double) ats[index].value); - int i = mlpi->q_avg_i[c]; + int i = mlpi->q_avg_i[c];*/ double * qp = mlpi->q[c]; + /* FIXME qp[i] = (double) ats[index].value; + */ int t; for (t = 0; t < MLP_AVERAGING_QUEUE_LENGTH; t++) @@ -1538,6 +1527,20 @@ update_quality (struct GAS_MLP_Handle *mlp, struct ATS_Address * address) } } + +/** + * Add a single address to the solve + * + * @param solver the solver Handle + * @param addresses the address hashmap containing all addresses + * @param address the address to add + */ +void +GAS_mlp_address_add (void *solver, struct GNUNET_CONTAINER_MultiHashMap * addresses, struct ATS_Address *address) +{ + +} + /** * Updates a single address in the MLP problem * @@ -1547,14 +1550,24 @@ update_quality (struct GAS_MLP_Handle *mlp, struct ATS_Address * address) * Otherwise the addresses' values can be updated and the existing base can * be reused * - * @param mlp the MLP Handle - * @param addresses the address hashmap - * the address has to be already removed from the hashmap - * @param address the address to update + * @param solver the solver Handle + * @param addresses the address hashmap containing all addresses + * @param address the update address + * @param session the new session (if changed otherwise current) + * @param in_use the new address in use state (if changed otherwise current) + * @param atsi the latest ATS information + * @param atsi_count the atsi count */ void -GAS_mlp_address_update (struct GAS_MLP_Handle *mlp, struct GNUNET_CONTAINER_MultiHashMap * addresses, struct ATS_Address *address) +GAS_mlp_address_update (void *solver, + struct GNUNET_CONTAINER_MultiHashMap *addresses, + struct ATS_Address *address, + uint32_t session, + int in_use, + const struct GNUNET_ATS_Information *atsi, + uint32_t atsi_count) { + struct GAS_MLP_Handle *mlp = solver; int new; struct MLP_information *mlpi; struct GAS_MLP_SolutionContext ctx; @@ -1562,7 +1575,7 @@ GAS_mlp_address_update (struct GAS_MLP_Handle *mlp, struct GNUNET_CONTAINER_Mult GNUNET_STATISTICS_update (mlp->stats, "# MLP address updates", 1, GNUNET_NO); /* We add a new address */ - if (address->mlp_information == NULL) + if (address->solver_information == NULL) new = GNUNET_YES; else new = GNUNET_NO; @@ -1583,7 +1596,7 @@ GAS_mlp_address_update (struct GAS_MLP_Handle *mlp, struct GNUNET_CONTAINER_Mult mlpi->q_averaged[c] = 0.0; } - address->mlp_information = mlpi; + address->solver_information = mlpi; mlp->addr_in_problem ++; GNUNET_STATISTICS_update (mlp->stats, "# addresses in MLP", 1, GNUNET_NO); @@ -1650,22 +1663,27 @@ GAS_mlp_address_update (struct GAS_MLP_Handle *mlp, struct GNUNET_CONTAINER_Mult * * The MLP problem has to be recreated and the problem has to be resolved * - * @param mlp the MLP Handle + * @param solver the MLP Handle * @param addresses the address hashmap * the address has to be already removed from the hashmap * @param address the address to delete + * @param session_only delete only session not whole address */ void -GAS_mlp_address_delete (struct GAS_MLP_Handle *mlp, struct GNUNET_CONTAINER_MultiHashMap * addresses, struct ATS_Address *address) +GAS_mlp_address_delete (void *solver, + struct GNUNET_CONTAINER_MultiHashMap * addresses, + struct ATS_Address *address, + int session_only) { + struct GAS_MLP_Handle *mlp = solver; GNUNET_STATISTICS_update (mlp->stats,"# LP address deletions", 1, GNUNET_NO); struct GAS_MLP_SolutionContext ctx; /* Free resources */ - if (address->mlp_information != NULL) + if (address->solver_information != NULL) { - GNUNET_free (address->mlp_information); - address->mlp_information = NULL; + GNUNET_free (address->solver_information); + address->solver_information = NULL; mlp->addr_in_problem --; GNUNET_STATISTICS_update (mlp->stats, "# addresses in MLP", -1, GNUNET_NO); @@ -1706,22 +1724,22 @@ GAS_mlp_address_delete (struct GAS_MLP_Handle *mlp, struct GNUNET_CONTAINER_Mult } static int -mlp_get_preferred_address_it (void *cls, const GNUNET_HashCode * key, void *value) +mlp_get_preferred_address_it (void *cls, const struct GNUNET_HashCode * key, void *value) { - struct ATS_PreferedAddress *aa = (struct ATS_PreferedAddress *) cls; + struct ATS_Address *aa = (struct ATS_Address *) cls; struct ATS_Address *addr = value; - struct MLP_information *mlpi = addr->mlp_information; + struct MLP_information *mlpi = addr->solver_information; if (mlpi == NULL) return GNUNET_YES; if (mlpi->n == GNUNET_YES) { - aa->address = addr; + aa = addr; if (mlpi->b > (double) UINT32_MAX) - aa->bandwidth_out = UINT32_MAX; + aa->assigned_bw_out.value__ = htonl (UINT32_MAX); else - aa->bandwidth_out = (uint32_t) mlpi->b; - aa->bandwidth_in = 0; + aa->assigned_bw_out.value__ = htonl((uint32_t) mlpi->b); + aa->assigned_bw_in.value__ = htonl(0); return GNUNET_NO; } return GNUNET_YES; @@ -1731,20 +1749,17 @@ mlp_get_preferred_address_it (void *cls, const GNUNET_HashCode * key, void *valu /** * Get the preferred address for a specific peer * - * @param mlp the MLP Handle + * @param solver the MLP Handle * @param addresses address hashmap * @param peer the peer * @return suggested address */ -struct ATS_PreferedAddress * -GAS_mlp_get_preferred_address (struct GAS_MLP_Handle *mlp, +const struct ATS_Address * +GAS_mlp_get_preferred_address (void *solver, struct GNUNET_CONTAINER_MultiHashMap * addresses, const struct GNUNET_PeerIdentity *peer) { - struct ATS_PreferedAddress * aa = GNUNET_malloc (sizeof (struct ATS_PreferedAddress)); - aa->address = NULL; - aa->bandwidth_in = 0; - aa->bandwidth_out = 0; + struct ATS_Address * aa = NULL; GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Getting preferred address for `%s'\n", GNUNET_i2s (peer)); GNUNET_CONTAINER_multihashmap_get_multiple (addresses, &peer->hashPubKey, mlp_get_preferred_address_it, aa); return aa; @@ -1754,31 +1769,37 @@ GAS_mlp_get_preferred_address (struct GAS_MLP_Handle *mlp, /** * Changes the preferences for a peer in the MLP problem * - * @param mlp the MLP Handle + * @param solver the MLP Handle + * @param client client * @param peer the peer * @param kind the kind to change the preference * @param score the score */ void -GAS_mlp_address_change_preference (struct GAS_MLP_Handle *mlp, +GAS_mlp_address_change_preference (void *solver, + void *client, const struct GNUNET_PeerIdentity *peer, enum GNUNET_ATS_PreferenceKind kind, float score) { + struct GAS_MLP_Handle *mlp = solver; GNUNET_STATISTICS_update (mlp->stats,"# LP address preference changes", 1, GNUNET_NO); - struct ATS_Peer *p = mlp_find_peer (mlp, peer); - p = p; + //struct ATS_Peer *p = mlp_find_peer (mlp, peer); + //FIXME to finish implementation /* Here we have to do the matching */ + } /** * Shutdown the MLP problem solving component - * @param mlp the MLP handle + * + * @param solver the solver handle */ void -GAS_mlp_done (struct GAS_MLP_Handle *mlp) +GAS_mlp_done (void *solver) { + struct GAS_MLP_Handle *mlp = solver; struct ATS_Peer * peer; struct ATS_Address *addr; @@ -1799,8 +1820,8 @@ GAS_mlp_done (struct GAS_MLP_Handle *mlp) for (addr = peer->head; NULL != addr; addr = peer->head) { GNUNET_CONTAINER_DLL_remove(peer->head, peer->tail, addr); - GNUNET_free (addr->mlp_information); - addr->mlp_information = NULL; + GNUNET_free (addr->solver_information); + addr->solver_information = NULL; } GNUNET_free (peer); peer = mlp->peer_head; diff --git a/src/ats/gnunet-service-ats_addresses_mlp.h b/src/ats/gnunet-service-ats_addresses_mlp.h index d37eea7..a49f585 100644 --- a/src/ats/gnunet-service-ats_addresses_mlp.h +++ b/src/ats/gnunet-service-ats_addresses_mlp.h @@ -20,7 +20,7 @@ /** * @file ats/gnunet-service-ats_addresses_mlp.h - * @brief ats mlp problem solver + * @brief ats MLP problem solver * @author Matthias Wachs * @author Christian Grothoff */ @@ -34,8 +34,6 @@ #ifndef GNUNET_SERVICE_ATS_ADDRESSES_MLP_H #define GNUNET_SERVICE_ATS_ADDRESSES_MLP_H -#define DEBUG_MLP GNUNET_EXTRA_LOGGING - #define BIG_M_VALUE (UINT32_MAX) /10 #define BIG_M_STRING "unlimited" @@ -66,13 +64,6 @@ struct ATS_Peer struct ATS_Address *tail; }; -struct ATS_PreferedAddress -{ - uint32_t bandwidth_out; - uint32_t bandwidth_in; - struct ATS_Address *address; -}; - struct GAS_MLP_SolutionContext { int lp_result; @@ -105,12 +96,20 @@ struct GAS_MLP_Handle /** * GLPK LP control parameter */ +#if HAVE_LIBGLPK glp_smcp control_param_lp; +#else + void *control_param_lp; +#endif /** * GLPK LP control parameter */ +#if HAVE_LIBGLPK glp_iocp control_param_mlp; +#else + void *control_param_mlp; +#endif /** * Solves the task in an regular interval @@ -317,26 +316,34 @@ struct MLP_information * * @param cfg configuration handle * @param stats the GNUNET_STATISTICS handle - * @param max_duration maximum numbers of iterations for the LP/MLP Solver - * @param max_iterations maximum time limit for the LP/MLP Solver - * @return struct GAS_MLP_Handle * on success, NULL on fail + * @param network array of GNUNET_ATS_NetworkType with length dest_length + * @param out_dest array of outbound quotas + * @param in_dest array of outbound quota + * @param dest_length array length for quota arrays + * @param bw_changed_cb callback for changed bandwidth amounts + * @param bw_changed_cb_cls cls for callback + * @return struct GAS_MLP_Handle on success, NULL on fail */ -struct GAS_MLP_Handle * +void * GAS_mlp_init (const struct GNUNET_CONFIGURATION_Handle *cfg, const struct GNUNET_STATISTICS_Handle *stats, - struct GNUNET_TIME_Relative max_duration, - unsigned int max_iterations); + int *network, + unsigned long long *out_dest, + unsigned long long *in_dest, + int dest_length, + GAS_bandwidth_changed_cb bw_changed_cb, + void *bw_changed_cb_cls); + /** - * Solves the MLP problem on demand + * Add a single address to the solve * - * @param mlp the MLP Handle - * @param ctx solution context - * @return GNUNET_OK if could be solved, GNUNET_SYSERR on failure + * @param solver the solver Handle + * @param addresses the address hashmap containing all addresses + * @param address the address to add */ -int -GAS_mlp_solve_problem (struct GAS_MLP_Handle *mlp, struct GAS_MLP_SolutionContext *ctx); - +void +GAS_mlp_address_add (void *solver, struct GNUNET_CONTAINER_MultiHashMap * addresses, struct ATS_Address *address); /** * Updates a single address in the MLP problem @@ -347,13 +354,22 @@ GAS_mlp_solve_problem (struct GAS_MLP_Handle *mlp, struct GAS_MLP_SolutionContex * Otherwise the addresses' values can be updated and the existing base can * be reused * - * @param mlp the MLP Handle - * @param addresses the address hashmap - * the address has to be already added from the hashmap - * @param address the address to update + * @param solver the solver Handle + * @param addresses the address hashmap containing all addresses + * @param address the update address + * @param session the new session (if changed otherwise current) + * @param in_use the new address in use state (if changed otherwise current) + * @param atsi the latest ATS information + * @param atsi_count the atsi count */ void -GAS_mlp_address_update (struct GAS_MLP_Handle *mlp, struct GNUNET_CONTAINER_MultiHashMap * addresses, struct ATS_Address *address); +GAS_mlp_address_update (void *solver, + struct GNUNET_CONTAINER_MultiHashMap *addresses, + struct ATS_Address *address, + uint32_t session, + int in_use, + const struct GNUNET_ATS_Information *atsi, + uint32_t atsi_count); /** @@ -361,25 +377,31 @@ GAS_mlp_address_update (struct GAS_MLP_Handle *mlp, struct GNUNET_CONTAINER_Mult * * The MLP problem has to be recreated and the problem has to be resolved * - * @param mlp the MLP Handle + * @param solver the MLP Handle * @param addresses the address hashmap * the address has to be already removed from the hashmap * @param address the address to delete + * @param session_only delete only session not whole address */ void -GAS_mlp_address_delete (struct GAS_MLP_Handle *mlp, struct GNUNET_CONTAINER_MultiHashMap * addresses, struct ATS_Address *address); +GAS_mlp_address_delete (void *solver, + struct GNUNET_CONTAINER_MultiHashMap *addresses, + struct ATS_Address *address, + int session_only); /** * Changes the preferences for a peer in the MLP problem * - * @param mlp the MLP Handle + * @param solver the MLP Handle + * @param client client * @param peer the peer * @param kind the kind to change the preference * @param score the score */ void -GAS_mlp_address_change_preference (struct GAS_MLP_Handle *mlp, +GAS_mlp_address_change_preference (void *solver, + void *client, const struct GNUNET_PeerIdentity *peer, enum GNUNET_ATS_PreferenceKind kind, float score); @@ -388,21 +410,23 @@ GAS_mlp_address_change_preference (struct GAS_MLP_Handle *mlp, /** * Get the preferred address for a specific peer * - * @param mlp the MLP Handle + * @param solver the MLP Handle * @param addresses address hashmap * @param peer the peer * @return suggested address */ -struct ATS_PreferedAddress * -GAS_mlp_get_preferred_address (struct GAS_MLP_Handle *mlp, +const struct ATS_Address * +GAS_mlp_get_preferred_address (void *solver, struct GNUNET_CONTAINER_MultiHashMap * addresses, const struct GNUNET_PeerIdentity *peer); /** * Shutdown the MLP problem solving component + * + * @param solver the solver handle */ void -GAS_mlp_done (); +GAS_mlp_done (void *solver); #endif /* end of gnunet-service-ats_addresses_mlp.h */ diff --git a/src/ats/gnunet-service-ats_addresses_simplistic.c b/src/ats/gnunet-service-ats_addresses_simplistic.c new file mode 100644 index 0000000..74a4b43 --- /dev/null +++ b/src/ats/gnunet-service-ats_addresses_simplistic.c @@ -0,0 +1,1377 @@ +/* + This file is part of GNUnet. + (C) 2011 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @file ats/gnunet-service-ats_addresses_simplistic.h + * @brief ats simplistic ressource assignment + * @author Matthias Wachs + * @author Christian Grothoff + */ +#include "platform.h" +#include "gnunet_util_lib.h" +#include "gnunet-service-ats_addresses.h" +#include "gnunet_statistics_service.h" + +#define LOG(kind,...) GNUNET_log_from (kind, "ats-simplistic",__VA_ARGS__) + +/** + * ATS simplistic solver + * + * Assigns in and outbound bandwidth equally for all addresses in specific + * network type (WAN, LAN) based on configured in and outbound quota for this + * network. + * + * For each peer only a single is selected and marked as "active" in the address + * struct. + * + * E.g.: + * + * You have the networks WAN and LAN and quotas + * WAN_TOTAL_IN, WAN_TOTAL_OUT + * LAN_TOTAL_IN, LAN_TOTAL_OUT + * + * If you have x addresses in the network segment LAN, the quotas are + * QUOTA_PER_ADDRESS = LAN_TOTAL_OUT / x + * + * Quotas are automatically recalculated and reported back when addresses are + * - requested + * + */ + +#define PREF_AGING_INTERVAL GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 10) +#define PREF_AGING_FACTOR 0.95 + +#define DEFAULT_PREFERENCE 1.0 +#define MIN_UPDATE_INTERVAL GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 10) + +/** + * A handle for the simplistic solver + */ +struct GAS_SIMPLISTIC_Handle +{ + /** + * Statistics handle + */ + + struct GNUNET_STATISTICS_Handle *stats; + + /** + * Total number of addresses for solver + */ + unsigned int total_addresses; + + /** + * Number of active addresses for solver + */ + unsigned int active_addresses; + + /** + * Networks array + */ + struct Network *network_entries; + + /** + * Number of networks + */ + unsigned int networks; + + /** + * Callback + */ + GAS_bandwidth_changed_cb bw_changed; + + /** + * Callback cls + */ + void *bw_changed_cls; + + struct GNUNET_CONTAINER_MultiHashMap *prefs; + + struct PreferenceClient *pc_head; + struct PreferenceClient *pc_tail; +}; + +struct Network +{ + /** + * ATS network type + */ + unsigned int type; + + /** + * Network description + */ + char *desc; + + /** + * Total inbound quota + * + */ + unsigned long long total_quota_in; + + /** + * Total outbound quota + * + */ + unsigned long long total_quota_out; + + /** + * Number of active addresses for this network + */ + unsigned int active_addresses; + + /** + * Number of total addresses for this network + */ + unsigned int total_addresses; + + /** + * String for statistics total addresses + */ + char *stat_total; + + /** + * String for statistics active addresses + */ + char *stat_active; + + struct AddressWrapper *head; + struct AddressWrapper *tail; +}; + +struct AddressWrapper +{ + struct AddressWrapper *next; + struct AddressWrapper *prev; + + struct ATS_Address *addr; +}; + + +struct PreferenceClient +{ + struct PreferenceClient *prev; + struct PreferenceClient *next; + void *client; + + double f_total[GNUNET_ATS_PreferenceCount]; + + struct PreferencePeer *p_head; + struct PreferencePeer *p_tail; +}; + + +struct PreferencePeer +{ + struct PreferencePeer *next; + struct PreferencePeer *prev; + struct PreferenceClient *client; + struct GAS_SIMPLISTIC_Handle *s; + struct GNUNET_PeerIdentity id; + + double f[GNUNET_ATS_PreferenceCount]; + double f_rel[GNUNET_ATS_PreferenceCount]; + double f_rel_total; + + GNUNET_SCHEDULER_TaskIdentifier aging_task; +}; + +/** + * Get the prefered address for a specific peer + * + * @param solver the solver handle + * @param addresses the address hashmap containing all addresses + * @param peer the identity of the peer + */ +const struct ATS_Address * +GAS_simplistic_get_preferred_address (void *solver, + struct GNUNET_CONTAINER_MultiHashMap * addresses, + const struct GNUNET_PeerIdentity *peer); + +/** + * Init the simplistic problem solving component + * + * Quotas: + * network[i] contains the network type as type GNUNET_ATS_NetworkType[i] + * out_quota[i] contains outbound quota for network type i + * in_quota[i] contains inbound quota for network type i + * + * Example + * network = {GNUNET_ATS_NET_UNSPECIFIED, GNUNET_ATS_NET_LOOPBACK, GNUNET_ATS_NET_LAN, GNUNET_ATS_NET_WAN, GNUNET_ATS_NET_WLAN} + * network[2] == GNUNET_ATS_NET_LAN + * out_quota[2] == 65353 + * in_quota[2] == 65353 + * + * @param cfg configuration handle + * @param stats the GNUNET_STATISTICS handle + * @param network array of GNUNET_ATS_NetworkType with length dest_length + * @param out_quota array of outbound quotas + * @param in_quota array of outbound quota + * @param dest_length array length for quota arrays + * @param bw_changed_cb callback for changed bandwidth amounts + * @param bw_changed_cb_cls cls for callback + * @return handle for the solver on success, NULL on fail + */ +void * +GAS_simplistic_init (const struct GNUNET_CONFIGURATION_Handle *cfg, + const struct GNUNET_STATISTICS_Handle *stats, + int *network, + unsigned long long *out_quota, + unsigned long long *in_quota, + int dest_length, + GAS_bandwidth_changed_cb bw_changed_cb, + void *bw_changed_cb_cls) +{ + int c; + struct GAS_SIMPLISTIC_Handle *s = GNUNET_malloc (sizeof (struct GAS_SIMPLISTIC_Handle)); + struct Network * cur; + char * net_str[GNUNET_ATS_NetworkTypeCount] = GNUNET_ATS_NetworkTypeString; + + + s->stats = (struct GNUNET_STATISTICS_Handle *) stats; + s->bw_changed = bw_changed_cb; + s->bw_changed_cls = bw_changed_cb_cls; + s->networks = dest_length; + s->network_entries = GNUNET_malloc (dest_length * sizeof (struct Network)); + s->active_addresses = 0; + s->total_addresses = 0; + s->prefs = GNUNET_CONTAINER_multihashmap_create (10, GNUNET_NO); + + for (c = 0; c < dest_length; c++) + { + cur = &s->network_entries[c]; + cur->total_addresses = 0; + cur->active_addresses = 0; + cur->type = network[c]; + cur->total_quota_in = in_quota[c]; + cur->total_quota_out = out_quota[c]; + cur->desc = net_str[c]; + GNUNET_asprintf (&cur->stat_total, "# ATS addresses %s total", cur->desc); + GNUNET_asprintf (&cur->stat_active, "# ATS active addresses %s total", cur->desc); + } + return s; +} + +static int +free_pref (void *cls, + const struct GNUNET_HashCode * key, + void *value) +{ + float *v = value; + GNUNET_free (v); + return GNUNET_OK; +} + +/** + * Shutdown the simplistic problem solving component + * + * @param solver the respective handle to shutdown + */ +void +GAS_simplistic_done (void *solver) +{ + struct GAS_SIMPLISTIC_Handle *s = solver; + struct PreferenceClient *pc; + struct PreferenceClient *next_pc; + struct PreferencePeer *p; + struct PreferencePeer *next_p; + struct AddressWrapper *cur; + struct AddressWrapper *next; + int c; + GNUNET_assert (s != NULL); + + for (c = 0; c < s->networks; c++) + { + if (s->network_entries[c].total_addresses > 0) + { + LOG (GNUNET_ERROR_TYPE_ERROR, + "Had %u addresses for network `%s' not deleted during shutdown\n", + s->network_entries[c].total_addresses, + s->network_entries[c].desc); + GNUNET_break (0); + } + + if (s->network_entries[c].active_addresses > 0) + { + LOG (GNUNET_ERROR_TYPE_ERROR, + "Had %u active addresses for network `%s' not deleted during shutdown\n", + s->network_entries[c].active_addresses, + s->network_entries[c].desc); + GNUNET_break (0); + } + + next = s->network_entries[c].head; + while (NULL != (cur = next)) + { + next = cur->next; + GNUNET_CONTAINER_DLL_remove (s->network_entries[c].head, + s->network_entries[c].tail, + cur); + GNUNET_free (cur); + } + GNUNET_free (s->network_entries[c].stat_total); + GNUNET_free (s->network_entries[c].stat_active); + } + if (s->total_addresses > 0) + { + LOG (GNUNET_ERROR_TYPE_ERROR, + "Had %u addresses not deleted during shutdown\n", + s->total_addresses); + GNUNET_break (0); + } + if (s->active_addresses > 0) + { + LOG (GNUNET_ERROR_TYPE_ERROR, + "Had %u active addresses not deleted during shutdown\n", + s->active_addresses); + GNUNET_break (0); + } + GNUNET_free (s->network_entries); + + next_pc = s->pc_head; + while (NULL != (pc = next_pc)) + { + next_pc = pc->next; + GNUNET_CONTAINER_DLL_remove (s->pc_head, s->pc_tail, pc); + next_p = pc->p_head; + while (NULL != (p = next_p)) + { + next_p = p->next; + if (GNUNET_SCHEDULER_NO_TASK != p->aging_task) + { + GNUNET_SCHEDULER_cancel(p->aging_task); + p->aging_task = GNUNET_SCHEDULER_NO_TASK; + } + GNUNET_CONTAINER_DLL_remove (pc->p_head, pc->p_tail, p); + GNUNET_free (p); + } + GNUNET_free (pc); + } + + GNUNET_CONTAINER_multihashmap_iterate (s->prefs, &free_pref, NULL); + GNUNET_CONTAINER_multihashmap_destroy (s->prefs); + GNUNET_free (s); +} + + +/** + * Test if bandwidth is available in this network + * + * @param s the solver handle + * @param net the network type to update + * @return GNUNET_YES or GNUNET_NO + */ + +static int +bw_available_in_network (struct Network *net) +{ + unsigned int na = net->active_addresses + 1; + uint32_t min_bw = ntohl (GNUNET_CONSTANTS_DEFAULT_BW_IN_OUT.value__); + if (((net->total_quota_in / na) > min_bw) && + ((net->total_quota_out / na) > min_bw)) + { + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Enough bandwidth available for %u active addresses in network `%s'\n", + na, + net->desc); + + return GNUNET_YES; + } + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Not enough bandwidth available for %u active addresses in network `%s'\n", + na, + net->desc); + return GNUNET_NO; +} + + +/** + * Update the quotas for a network type + * + * @param s the solver handle + * @param net the network type to update + * @param address_except address excluded from notifcation, since we suggest + * this address + */ +static void +update_quota_per_network (struct GAS_SIMPLISTIC_Handle *s, + struct Network *net, + struct ATS_Address *address_except) +{ + unsigned long long remaining_quota_in = 0; + unsigned long long quota_out_used = 0; + + unsigned long long remaining_quota_out = 0; + unsigned long long quota_in_used = 0; + uint32_t min_bw = ntohl (GNUNET_CONSTANTS_DEFAULT_BW_IN_OUT.value__); + double total_prefs; /* Important: has to be double not float due to precision */ + double cur_pref; /* Important: has to be double not float due to precision */ + double *t = NULL; /* Important: has to be double not float due to precision */ + + unsigned long long assigned_quota_in = 0; + unsigned long long assigned_quota_out = 0; + struct AddressWrapper *cur; + + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Recalculate quota for network type `%s' for %u addresses (in/out): %llu/%llu \n", + net->desc, net->active_addresses, net->total_quota_in, net->total_quota_in); + + if (net->active_addresses == 0) + return; /* no addresses to update */ + + /* Idea TODO + * + * Assign every peer in network minimum Bandwidth + * Distribute bandwidth left according to preference + */ + + if ((net->active_addresses * min_bw) > net->total_quota_in) + { + GNUNET_break (0); + return; + } + if ((net->active_addresses * min_bw) > net->total_quota_out) + { + GNUNET_break (0); + return; + } + + remaining_quota_in = net->total_quota_in - (net->active_addresses * min_bw); + remaining_quota_out = net->total_quota_out - (net->active_addresses * min_bw); + LOG (GNUNET_ERROR_TYPE_DEBUG, "Remaining bandwidth : (in/out): %llu/%llu \n", + remaining_quota_in, remaining_quota_out); + total_prefs = 0.0; + for (cur = net->head; NULL != cur; cur = cur->next) + { + if (GNUNET_YES == cur->addr->active) + { + t = GNUNET_CONTAINER_multihashmap_get (s->prefs, &cur->addr->peer.hashPubKey); + if (NULL == t) + total_prefs += DEFAULT_PREFERENCE; + else + { + total_prefs += (*t); + } + } + } + for (cur = net->head; NULL != cur; cur = cur->next) + { + if (GNUNET_YES == cur->addr->active) + { + cur_pref = 0.0; + t = GNUNET_CONTAINER_multihashmap_get (s->prefs, &cur->addr->peer.hashPubKey); + if (NULL == t) + cur_pref = DEFAULT_PREFERENCE; + else + cur_pref = (*t); + assigned_quota_in = min_bw + ((cur_pref / total_prefs) * remaining_quota_in); + assigned_quota_out = min_bw + ((cur_pref / total_prefs) * remaining_quota_out); + + LOG (GNUNET_ERROR_TYPE_DEBUG, + "New quota for peer `%s' with preference (cur/total) %.3f/%.3f (in/out): %llu / %llu\n", + GNUNET_i2s (&cur->addr->peer), + cur_pref, total_prefs, + assigned_quota_in, assigned_quota_out); + } + else + { + assigned_quota_in = 0; + assigned_quota_out = 0; + } + + quota_in_used += assigned_quota_in; + quota_out_used += assigned_quota_out; + /* Prevent overflow due to rounding errors */ + if (assigned_quota_in > UINT32_MAX) + assigned_quota_in = UINT32_MAX; + if (assigned_quota_out > UINT32_MAX) + assigned_quota_out = UINT32_MAX; + + /* Compare to current bandwidth assigned */ + if ((assigned_quota_in != ntohl(cur->addr->assigned_bw_in.value__)) || + (assigned_quota_out != ntohl(cur->addr->assigned_bw_out.value__))) + { + cur->addr->assigned_bw_in.value__ = htonl (assigned_quota_in); + cur->addr->assigned_bw_out.value__ = htonl (assigned_quota_out); + /* Notify on change */ + if ((GNUNET_YES == cur->addr->active) && (cur->addr != address_except)) + s->bw_changed (s->bw_changed_cls, cur->addr); + } + + } + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Total bandwidth assigned is (in/out): %llu /%llu\n", + quota_in_used, + quota_out_used); + if (quota_out_used > net->total_quota_out + 1) /* +1 is required due to rounding errors */ + { + LOG (GNUNET_ERROR_TYPE_ERROR, + "Total outbound bandwidth assigned is larger than allowed (used/allowed) for %u active addresses: %llu / %llu\n", + net->active_addresses, + quota_out_used, + net->total_quota_out); + } + if (quota_in_used > net->total_quota_in + 1) /* +1 is required due to rounding errors */ + { + LOG (GNUNET_ERROR_TYPE_ERROR, + "Total inbound bandwidth assigned is larger than allowed (used/allowed) for %u active addresses: %llu / %llu\n", + net->active_addresses, + quota_in_used, + net->total_quota_in); + } +} + +static void +update_all_networks (struct GAS_SIMPLISTIC_Handle *s) +{ + int i; + for (i = 0; i < s->networks; i++) + update_quota_per_network (s, &s->network_entries[i], NULL); + +} + +static void +addresse_increment (struct GAS_SIMPLISTIC_Handle *s, + struct Network *net, + int total, + int active) +{ + if (GNUNET_YES == total) + { + s->total_addresses ++; + net->total_addresses ++; + GNUNET_STATISTICS_update (s->stats, "# ATS addresses total", 1, GNUNET_NO); + GNUNET_STATISTICS_update (s->stats, net->stat_total, 1, GNUNET_NO); + } + if (GNUNET_YES == active) + { + net->active_addresses ++; + s->active_addresses ++; + GNUNET_STATISTICS_update (s->stats, "# ATS active addresses total", 1, GNUNET_NO); + GNUNET_STATISTICS_update (s->stats, net->stat_active, 1, GNUNET_NO); + } + +} + +static int +addresse_decrement (struct GAS_SIMPLISTIC_Handle *s, + struct Network *net, + int total, + int active) +{ + int res = GNUNET_OK; + if (GNUNET_YES == total) + { + if (s->total_addresses < 1) + { + GNUNET_break (0); + res = GNUNET_SYSERR; + } + else + { + s->total_addresses --; + GNUNET_STATISTICS_update (s->stats, "# ATS addresses total", -1, GNUNET_NO); + } + if (net->total_addresses < 1) + { + GNUNET_break (0); + res = GNUNET_SYSERR; + } + else + { + net->total_addresses --; + GNUNET_STATISTICS_update (s->stats, net->stat_total, -1, GNUNET_NO); + } + } + + if (GNUNET_YES == active) + { + if (net->active_addresses < 1) + { + GNUNET_break (0); + res = GNUNET_SYSERR; + } + else + { + net->active_addresses --; + GNUNET_STATISTICS_update (s->stats, net->stat_active, -1, GNUNET_NO); + } + if (s->active_addresses < 1) + { + GNUNET_break (0); + res = GNUNET_SYSERR; + } + else + { + s->active_addresses --; + GNUNET_STATISTICS_update (s->stats, "# ATS addresses total", -1, GNUNET_NO); + } + } + return res; +} + + +/** + * Add a single address to the solve + * + * @param solver the solver Handle + * @param addresses the address hashmap containing all addresses + * @param address the address to add + */ +void +GAS_simplistic_address_add (void *solver, struct GNUNET_CONTAINER_MultiHashMap * addresses, struct ATS_Address *address) +{ + struct GAS_SIMPLISTIC_Handle *s = solver; + struct Network *net = NULL; + struct AddressWrapper *aw = NULL; + + GNUNET_assert (NULL != s); + int c; + for (c = 0; c < s->networks; c++) + { + net = &s->network_entries[c]; + if (address->atsp_network_type == net->type) + break; + } + if (NULL == net) + { + GNUNET_break (0); + return; + } + + aw = GNUNET_malloc (sizeof (struct AddressWrapper)); + aw->addr = address; + GNUNET_CONTAINER_DLL_insert (net->head, net->tail, aw); + addresse_increment (s, net, GNUNET_YES, GNUNET_NO); + aw->addr->solver_information = net; + + + LOG (GNUNET_ERROR_TYPE_DEBUG, "After adding address now total %u and active %u addresses in network `%s'\n", + net->total_addresses, + net->active_addresses, + net->desc); +} + +/** + * Remove an address from the solver + * + * @param solver the solver handle + * @param addresses the address hashmap containing all addresses + * @param address the address to remove + * @param session_only delete only session not whole address + */ +void +GAS_simplistic_address_delete (void *solver, + struct GNUNET_CONTAINER_MultiHashMap * addresses, + struct ATS_Address *address, int session_only) +{ + struct GAS_SIMPLISTIC_Handle *s = solver; + struct Network *net; + struct AddressWrapper *aw; + + /* Remove an adress completely, we have to: + * - Remove from specific network + * - Decrease number of total addresses + * - If active: + * - decrease number of active addreses + * - update quotas + */ + + net = (struct Network *) address->solver_information; + + if (GNUNET_NO == session_only) + { + LOG (GNUNET_ERROR_TYPE_DEBUG, "Deleting %s address %p for peer `%s' from network `%s' (total: %u/ active: %u)\n", + (GNUNET_NO == address->active) ? "inactive" : "active", + address, GNUNET_i2s (&address->peer), + net->desc, net->total_addresses, net->active_addresses); + + /* Remove address */ + addresse_decrement (s, net, GNUNET_YES, GNUNET_NO); + for (aw = net->head; NULL != aw; aw = aw->next) + { + if (aw->addr == address) + break; + } + if (NULL == aw ) + { + GNUNET_break (0); + return; + } + GNUNET_CONTAINER_DLL_remove (net->head, net->tail, aw); + GNUNET_free (aw); + } + else + { + /* Remove session only: remove if active and update */ + LOG (GNUNET_ERROR_TYPE_DEBUG, "Deleting %s session %p for peer `%s' from network `%s' (total: %u/ active: %u)\n", + (GNUNET_NO == address->active) ? "inactive" : "active", + address, GNUNET_i2s (&address->peer), + net->desc, net->total_addresses, net->active_addresses); + } + + if (GNUNET_YES == address->active) + { + /* Address was active, remove from network and update quotas*/ + address->active = GNUNET_NO; + if (GNUNET_SYSERR == addresse_decrement (s, net, GNUNET_NO, GNUNET_YES)) + GNUNET_break (0); + update_quota_per_network (s, net, NULL); + } + LOG (GNUNET_ERROR_TYPE_DEBUG, "After deleting address now total %u and active %u addresses in network `%s'\n", + net->total_addresses, + net->active_addresses, + net->desc); + +} + +static struct Network * +find_network (struct GAS_SIMPLISTIC_Handle *s, uint32_t type) +{ + int c; + for (c = 0 ; c < s->networks; c++) + { + if (s->network_entries[c].type == type) + return &s->network_entries[c]; + } + return NULL; +} + +/** + * Updates a single address in the solve + * + * @param solver the solver Handle + * @param addresses the address hashmap containing all addresses + * @param address the update address + * @param session the new session (if changed otherwise current) + * @param in_use the new address in use state (if changed otherwise current) + * @param atsi the latest ATS information + * @param atsi_count the atsi count + */ +void +GAS_simplistic_address_update (void *solver, + struct GNUNET_CONTAINER_MultiHashMap *addresses, + struct ATS_Address *address, + uint32_t session, + int in_use, + const struct GNUNET_ATS_Information *atsi, + uint32_t atsi_count) +{ + struct ATS_Address *new; + struct GAS_SIMPLISTIC_Handle *s = (struct GAS_SIMPLISTIC_Handle *) solver; + int i; + uint32_t value; + uint32_t type; + int save_active = GNUNET_NO; + struct Network *new_net = NULL; + for (i = 0; i < atsi_count; i++) + { + type = ntohl (atsi[i].type); + value = ntohl (atsi[i].value); + switch (type) + { + case GNUNET_ATS_UTILIZATION_UP: + //if (address->atsp_utilization_out.value__ != atsi[i].value) + + break; + case GNUNET_ATS_UTILIZATION_DOWN: + //if (address->atsp_utilization_in.value__ != atsi[i].value) + + break; + case GNUNET_ATS_QUALITY_NET_DELAY: + //if (address->atsp_latency.rel_value != value) + + break; + case GNUNET_ATS_QUALITY_NET_DISTANCE: + //if (address->atsp_distance != value) + + break; + case GNUNET_ATS_COST_WAN: + //if (address->atsp_cost_wan != value) + + break; + case GNUNET_ATS_COST_LAN: + //if (address->atsp_cost_lan != value) + + break; + case GNUNET_ATS_COST_WLAN: + //if (address->atsp_cost_wlan != value) + + break; + case GNUNET_ATS_NETWORK_TYPE: + if (address->atsp_network_type != value) + { + + LOG (GNUNET_ERROR_TYPE_DEBUG, "Network type changed, moving %s address from `%s' to `%s'\n", + (GNUNET_YES == address->active) ? "active" : "inactive", + GNUNET_ATS_print_network_type(address->atsp_network_type), + GNUNET_ATS_print_network_type(value)); + + save_active = address->active; + /* remove from old network */ + GAS_simplistic_address_delete (solver, addresses, address, GNUNET_NO); + + /* set new network type */ + address->atsp_network_type = value; + new_net = find_network (solver, value); + address->solver_information = new_net; + if (address->solver_information == NULL) + { + GNUNET_break (0); + address->atsp_network_type = GNUNET_ATS_NET_UNSPECIFIED; + return; + } + + /* Add to new network and update*/ + GAS_simplistic_address_add (solver, addresses, address); + if (GNUNET_YES == save_active) + { + /* check if bandwidth available in new network */ + if (GNUNET_YES == (bw_available_in_network (new_net))) + { + /* Suggest updated address */ + address->active = GNUNET_YES; + addresse_increment (s, new_net, GNUNET_NO, GNUNET_YES); + update_quota_per_network (solver, new_net, NULL); + } + else + { + LOG (GNUNET_ERROR_TYPE_DEBUG, "Not enough bandwidth in new network, suggesting alternative address ..\n"); + + /* Set old address to zero bw */ + address->assigned_bw_in = GNUNET_BANDWIDTH_value_init (0); + address->assigned_bw_out = GNUNET_BANDWIDTH_value_init (0); + s->bw_changed (s->bw_changed_cls, address); + + /* Find new address to suggest since no bandwidth in network*/ + new = (struct ATS_Address *) GAS_simplistic_get_preferred_address (s, addresses, &address->peer); + if (NULL != new) + { + /* Have an alternative address to suggest */ + s->bw_changed (s->bw_changed_cls, new); + } + + } + } + } + break; + case GNUNET_ATS_ARRAY_TERMINATOR: + break; + default: + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Received unsupported ATS type %u\n", type); + GNUNET_break (0); + break; + + } + + } + if (address->session_id != session) + { + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Session changed from %u to %u\n", address->session_id, session); + address->session_id = session; + } + if (address->used != in_use) + { + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Usage changed from %u to %u\n", address->used, in_use); + address->used = in_use; + } + +} + + + +/** + * Find a "good" address to use for a peer. If we already have an existing + * address, we stick to it. Otherwise, we pick by lowest distance and then + * by lowest latency. + * + * @param cls the 'struct ATS_Address**' where we store the result + * @param key unused + * @param value another 'struct ATS_Address*' to consider using + * @return GNUNET_OK (continue to iterate) + */ +static int +find_address_it (void *cls, const struct GNUNET_HashCode * key, void *value) +{ + struct ATS_Address **previous_p = cls; + struct ATS_Address *current = (struct ATS_Address *) value; + struct ATS_Address *previous = *previous_p; + struct GNUNET_TIME_Absolute now; + struct Network *net = (struct Network *) current->solver_information; + + now = GNUNET_TIME_absolute_get(); + + if (current->blocked_until.abs_value == GNUNET_TIME_absolute_max (now, current->blocked_until).abs_value) + { + /* This address is blocked for suggestion */ + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Address %p blocked for suggestion for %llu ms \n", + current, + GNUNET_TIME_absolute_get_difference(now, current->blocked_until).rel_value); + return GNUNET_OK; + } + + if (GNUNET_NO == bw_available_in_network (net)) + return GNUNET_OK; /* There's no bandwidth available in this network */ + + if (NULL != previous) + { + if ((0 == strcmp (previous->plugin, "tcp")) && + (0 == strcmp (current->plugin, "tcp"))) + { + if ((0 != previous->addr_len) && + (0 == current->addr_len)) + { + /* saved address was an outbound address, but we have an inbound address */ + *previous_p = current; + return GNUNET_OK; + } + if (0 == previous->addr_len) + { + /* saved address was an inbound address, so do not overwrite */ + return GNUNET_OK; + } + } + } + + if (NULL == previous) + { + *previous_p = current; + return GNUNET_OK; + } + if ((ntohl (previous->assigned_bw_in.value__) == 0) && + (ntohl (current->assigned_bw_in.value__) > 0)) + { + /* stick to existing connection */ + *previous_p = current; + return GNUNET_OK; + } + if (previous->atsp_distance > current->atsp_distance) + { + /* user shorter distance */ + *previous_p = current; + return GNUNET_OK; + } + if (previous->atsp_latency.rel_value > current->atsp_latency.rel_value) + { + /* user lower latency */ + *previous_p = current; + return GNUNET_OK; + } + /* don't care */ + return GNUNET_OK; +} + +static int +find_active_address_it (void *cls, const struct GNUNET_HashCode * key, void *value) +{ + struct ATS_Address * dest = (struct ATS_Address *) (*(struct ATS_Address **)cls); + struct ATS_Address * aa = (struct ATS_Address *) value; + + if (GNUNET_YES == aa->active) + { + if (dest != NULL) + { + /* should never happen */ + LOG (GNUNET_ERROR_TYPE_ERROR, "Multiple active addresses for peer `%s'\n", GNUNET_i2s (&aa->peer)); + GNUNET_break (0); + return GNUNET_NO; + } + dest = aa; + } + return GNUNET_OK; +} + +static struct ATS_Address * +find_active_address (void *solver, + struct GNUNET_CONTAINER_MultiHashMap * addresses, + const struct GNUNET_PeerIdentity *peer) +{ + struct ATS_Address * dest = NULL; + + GNUNET_CONTAINER_multihashmap_get_multiple(addresses, + &peer->hashPubKey, + &find_active_address_it, &dest); + return dest; +} + +/** + * Get the prefered address for a specific peer + * + * @param solver the solver handle + * @param addresses the address hashmap containing all addresses + * @param peer the identity of the peer + */ +const struct ATS_Address * +GAS_simplistic_get_preferred_address (void *solver, + struct GNUNET_CONTAINER_MultiHashMap * addresses, + const struct GNUNET_PeerIdentity *peer) +{ + struct GAS_SIMPLISTIC_Handle *s = solver; + struct Network *net_prev; + struct Network *net_cur; + struct ATS_Address *cur; + struct ATS_Address *prev; + + GNUNET_assert (s != NULL); + cur = NULL; + /* Get address with: stick to current address, lower distance, lower latency */ + GNUNET_CONTAINER_multihashmap_get_multiple (addresses, &peer->hashPubKey, + &find_address_it, &cur); + if (NULL == cur) + { + LOG (GNUNET_ERROR_TYPE_DEBUG, "Cannot suggest address for peer `%s'\n", GNUNET_i2s (peer)); + return NULL; + } + + LOG (GNUNET_ERROR_TYPE_DEBUG, "Suggesting %s address %p for peer `%s'\n", + (GNUNET_NO == cur->active) ? "inactive" : "active", + cur, GNUNET_i2s (peer)); + net_cur = (struct Network *) cur->solver_information; + if (GNUNET_YES == cur->active) + { + /* This address was selected previously, so no need to update quotas */ + return cur; + } + + /* This address was not active, so we have to: + * + * - mark previous active address as not active + * - update quota for previous address network + * - update quota for this address network + */ + + prev = find_active_address (s, addresses, peer); + if (NULL != prev) + { + net_prev = (struct Network *) prev->solver_information; + prev->active = GNUNET_NO; /* No active any longer */ + prev->assigned_bw_in = GNUNET_BANDWIDTH_value_init (0); /* no bw assigned */ + prev->assigned_bw_out = GNUNET_BANDWIDTH_value_init (0); /* no bw assigned */ + s->bw_changed (s->bw_changed_cls, prev); /* notify about bw change, REQUIRED? */ + if (GNUNET_SYSERR == addresse_decrement (s, net_prev, GNUNET_NO, GNUNET_YES)) + GNUNET_break (0); + update_quota_per_network (s, net_prev, NULL); + } + + if (GNUNET_NO == (bw_available_in_network (cur->solver_information))) + { + GNUNET_break (0); /* This should never happen*/ + return NULL; + } + + cur->active = GNUNET_YES; + addresse_increment(s, net_cur, GNUNET_NO, GNUNET_YES); + update_quota_per_network (s, net_cur, cur); + + return cur; +} + +static void +recalculate_preferences (struct PreferencePeer *p) +{ + struct GAS_SIMPLISTIC_Handle *s = p->s; + struct PreferencePeer *p_cur; + struct PreferenceClient *c_cur = p->client; + double p_rel_global; + double *dest; + int kind; + int rkind; + int clients; + + /** + * Idea: + * + * We have: + * Set of clients c + * Set of peers p_i in P + * Set of preference kinds k + * A preference value f_k_p_i with an unknown range + * + * We get: + * A client specific relative preference f_p_i_rel [1..2] for all peers + * + * For every client c + * { + * For every preference kind k: + * { + * We remember for the preference f_p_i for each peer p_i. + * We have a default preference value f_p_i = 0 + * We have a sum of all preferences f_t = sum (f_p_i) + * So we can calculate a relative preference value fr_p_i: + * + * f_k_p_i_rel = (f_t + f_p_i) / f_t + * f_k_p_i_rel = [1..2], default 1.0 + * } + * f_p_i_rel = sum (f_k_p_i_rel) / #k + * } + * + **/ + + /* For this client: for all preferences, except TERMINATOR */ + for (kind = GNUNET_ATS_PREFERENCE_END + 1 ; kind < GNUNET_ATS_PreferenceCount; kind ++) + { + /* Recalcalculate total preference for this quality kind over all peers*/ + c_cur->f_total[kind] = 0; + for (p_cur = c_cur->p_head; NULL != p_cur; p_cur = p_cur->next) + c_cur->f_total[kind] += p_cur->f[kind]; + + LOG (GNUNET_ERROR_TYPE_DEBUG, "Client %p has total preference for %s of %.3f\n", + c_cur->client, + GNUNET_ATS_print_preference_type (kind), + c_cur->f_total[kind]); + + /* Recalcalculate relative preference for all peers */ + for (p_cur = c_cur->p_head; NULL != p_cur; p_cur = p_cur->next) + { + /* Calculate relative preference for specific kind */ + if (0.0 == c_cur->f_total[kind]) + { + /* No one has preference, so set default preference */ + p_cur->f_rel[kind] = DEFAULT_PREFERENCE; + } + else + { + p_cur->f_rel[kind] = (c_cur->f_total[kind] + p_cur->f[kind]) / c_cur->f_total[kind]; + } + LOG (GNUNET_ERROR_TYPE_DEBUG, "Client %p: peer `%s' has relative preference for %s of %.3f\n", + c_cur->client, + GNUNET_i2s (&p_cur->id), + GNUNET_ATS_print_preference_type (kind), + p_cur->f_rel[kind]); + + /* Calculate peer relative preference */ + /* Start with kind = 1 to exclude terminator */ + p_cur->f_rel_total = 0; + for (rkind = GNUNET_ATS_PREFERENCE_END + 1; rkind < GNUNET_ATS_PreferenceCount; rkind ++) + { + p_cur->f_rel_total += p_cur->f_rel[rkind]; + } + p_cur->f_rel_total /= (GNUNET_ATS_PreferenceCount - 1.0); /* -1 due to terminator */ + LOG (GNUNET_ERROR_TYPE_DEBUG, "Client %p: peer `%s' has total relative preference of %.3f\n", + c_cur->client, + GNUNET_i2s (&p_cur->id), + p_cur->f_rel_total); + } + } + + /* Calculcate global total relative peer preference over all clients */ + p_rel_global = 0.0; + clients = 0; + for (c_cur = s->pc_head; NULL != c_cur; c_cur = c_cur->next) + { + for (p_cur = c_cur->p_head; NULL != p_cur; p_cur = p_cur->next) + if (0 == memcmp (&p_cur->id, &p->id, sizeof (p_cur->id))) + break; + if (NULL != p_cur) + { + clients++; + p_rel_global += p_cur->f_rel_total; + } + } + p_rel_global /= clients; + LOG (GNUNET_ERROR_TYPE_DEBUG, "Global preference value for peer `%s': %.3f\n", + GNUNET_i2s (&p->id), p_rel_global); + + /* Update global map */ + if (NULL != (dest = GNUNET_CONTAINER_multihashmap_get(s->prefs, &p->id.hashPubKey))) + (*dest) = p_rel_global; + else + { + dest = GNUNET_malloc (sizeof (double)); + (*dest) = p_rel_global; + GNUNET_CONTAINER_multihashmap_put(s->prefs, + &p->id.hashPubKey, + dest, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY); + } +} + +static void +update_preference (struct PreferencePeer *p, + enum GNUNET_ATS_PreferenceKind kind, + float score_f) +{ + double score = score_f; + + /* Update preference value according to type */ + switch (kind) { + case GNUNET_ATS_PREFERENCE_BANDWIDTH: + case GNUNET_ATS_PREFERENCE_LATENCY: + p->f[kind] = (p->f[kind] + score) / 2; + break; + case GNUNET_ATS_PREFERENCE_END: + break; + default: + break; + } + recalculate_preferences(p); + update_all_networks (p->s); +} + + +static void +preference_aging (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + int i; + double *t = NULL; + double backup; + struct PreferencePeer *p = cls; + GNUNET_assert (NULL != p); + + + p->aging_task = GNUNET_SCHEDULER_NO_TASK; + + LOG (GNUNET_ERROR_TYPE_DEBUG, "Aging preferences for peer `%s'\n", + GNUNET_i2s (&p->id)); + + /* Issue for aging : + * + * Not for every peer preference values are set by default, so reducing the + * absolute preference value does not help for aging because it does not have + * influence on the relative values. + * + * So we have to reduce the relative value to have an immediate impact on + * quota calculation. In addition we cannot call recalculate_preferences here + * but instead reduce the absolute value to have an aging impact on future + * calls to change_preference where recalculate_preferences is called + * + */ + /* Aging absolute values: */ + for (i = 0; i < GNUNET_ATS_PreferenceCount; i++) + { + if (p->f[i] > 1.0) + { + backup = p->f[i]; + p->f[i] *= PREF_AGING_FACTOR; + LOG (GNUNET_ERROR_TYPE_DEBUG, "Aged preference for peer `%s' from %.3f to %.3f\n", + GNUNET_i2s (&p->id), backup, p->f[i]); + } + } + /* Updating relative value */ + t = GNUNET_CONTAINER_multihashmap_get (p->s->prefs, &p->id.hashPubKey); + if (NULL == t) + { + GNUNET_break (0); + } + else + { + if ((*t) > 1.0) + (*t) = (*t) * PREF_AGING_FACTOR; + else + (*t) = 1.0; + update_all_networks (p->s); + } + p->aging_task = GNUNET_SCHEDULER_add_delayed (PREF_AGING_INTERVAL, + &preference_aging, p); +} + + +/** + * Changes the preferences for a peer in the problem + * + * @param solver the solver handle + * @param client the client with this preference + * @param peer the peer to change the preference for + * @param kind the kind to change the preference + * @param score the score + */ +void +GAS_simplistic_address_change_preference (void *solver, + void *client, + const struct GNUNET_PeerIdentity *peer, + enum GNUNET_ATS_PreferenceKind kind, + float score_f) +{ + static struct GNUNET_TIME_Absolute next_update; + struct GAS_SIMPLISTIC_Handle *s = solver; + struct PreferenceClient *c_cur; + struct PreferencePeer *p_cur; + int i; + + GNUNET_assert (NULL != solver); + GNUNET_assert (NULL != client); + GNUNET_assert (NULL != peer); + + LOG (GNUNET_ERROR_TYPE_DEBUG, "Client %p changes preference for peer `%s' %s %f\n", + client, + GNUNET_i2s (peer), + GNUNET_ATS_print_preference_type (kind), + score_f); + + if (kind >= GNUNET_ATS_PreferenceCount) + { + GNUNET_break (0); + return; + } + + /* Find preference client */ + for (c_cur = s->pc_head; NULL != c_cur; c_cur = c_cur->next) + { + if (client == c_cur->client) + break; + } + /* Not found: create new preference client */ + if (NULL == c_cur) + { + c_cur = GNUNET_malloc (sizeof (struct PreferenceClient)); + c_cur->client = client; + GNUNET_CONTAINER_DLL_insert (s->pc_head, s->pc_tail, c_cur); + } + + /* Find entry for peer */ + for (p_cur = c_cur->p_head; NULL != p_cur; p_cur = p_cur->next) + if (0 == memcmp (&p_cur->id, peer, sizeof (p_cur->id))) + break; + + /* Not found: create new peer entry */ + if (NULL == p_cur) + { + p_cur = GNUNET_malloc (sizeof (struct PreferencePeer)); + p_cur->s = s; + p_cur->client = c_cur; + p_cur->id = (*peer); + for (i = 0; i < GNUNET_ATS_PreferenceCount; i++) + { + /* Default value per peer absolut preference for a quality: + * No value set, so absolute preference 0 */ + p_cur->f[i] = 0.0; + /* Default value per peer relative preference for a quality: 1.0 */ + p_cur->f_rel[i] = DEFAULT_PREFERENCE; + } + p_cur->aging_task = GNUNET_SCHEDULER_add_delayed (PREF_AGING_INTERVAL, &preference_aging, p_cur); + GNUNET_CONTAINER_DLL_insert (c_cur->p_head, c_cur->p_tail, p_cur); + } + + update_preference (p_cur, kind, score_f); + + /* FIXME: We should update quotas if UPDATE_INTERVAL is reached */ + if (GNUNET_TIME_absolute_get().abs_value > next_update.abs_value) + { + /* update quotas*/ + next_update = GNUNET_TIME_absolute_add (GNUNET_TIME_absolute_get(), + MIN_UPDATE_INTERVAL); + } +} + +/* end of gnunet-service-ats_addresses_simplistic.c */ diff --git a/src/ats/gnunet-service-ats_addresses_simplistic.h b/src/ats/gnunet-service-ats_addresses_simplistic.h new file mode 100644 index 0000000..eab221c --- /dev/null +++ b/src/ats/gnunet-service-ats_addresses_simplistic.h @@ -0,0 +1,151 @@ +/* + This file is part of GNUnet. + (C) 2011 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @file ats/gnunet-service-ats_addresses_simplistic.h + * @brief ats simplistic ressource assignment + * @author Matthias Wachs + * @author Christian Grothoff + */ +#include "platform.h" +#include "gnunet_statistics_service.h" +#include "gnunet-service-ats_addresses.h" + +#define BIG_M_STRING "unlimited" + +/** + * Init the simplistic problem solving component + * + * Quotas: + * network[i] contains the network type as type GNUNET_ATS_NetworkType[i] + * out_quota[i] contains outbound quota for network type i + * in_quota[i] contains inbound quota for network type i + * + * Example + * network = {GNUNET_ATS_NET_UNSPECIFIED, GNUNET_ATS_NET_LOOPBACK, GNUNET_ATS_NET_LAN, GNUNET_ATS_NET_WAN, GNUNET_ATS_NET_WLAN} + * network[2] == GNUNET_ATS_NET_LAN + * out_quota[2] == 65353 + * in_quota[2] == 65353 + * + * @param cfg configuration handle + * @param stats the GNUNET_STATISTICS handle + * @param network array of GNUNET_ATS_NetworkType with length dest_length + * @param out_quota array of outbound quotas + * @param in_quota array of outbound quota + * @param dest_length array length for quota arrays + * @param bw_changed_cb callback for changed bandwidth amounts + * @param bw_changed_cb_cls cls for callback + * @return handle for the solver on success, NULL on fail + */ +void * +GAS_simplistic_init (const struct GNUNET_CONFIGURATION_Handle *cfg, + const struct GNUNET_STATISTICS_Handle *stats, + int *network, + unsigned long long *out_quota, + unsigned long long *in_quota, + int dest_length, + GAS_bandwidth_changed_cb bw_changed_cb, + void *bw_changed_cb_cls); + +/** + * Shutdown the simplistic problem solving component + * + * @param solver the respective handle to shutdown + */ +void +GAS_simplistic_done (void * solver); + +/** + * Add a single address to the solve + * + * @param solver the solver Handle + * @param addresses the address hashmap containing all addresses + * @param address the address to add + */ +void +GAS_simplistic_address_add (void *solver, struct GNUNET_CONTAINER_MultiHashMap * addresses, struct ATS_Address *address); + + +/** + * Updates a single address in the solve + * + * @param solver the solver Handle + * @param addresses the address hashmap containing all addresses + * @param address the update address + * @param session the new session (if changed otherwise current) + * @param in_use the new address in use state (if changed otherwise current) + * @param atsi the latest ATS information + * @param atsi_count the atsi count + */ +void +GAS_simplistic_address_update (void *solver, + struct GNUNET_CONTAINER_MultiHashMap *addresses, + struct ATS_Address *address, + uint32_t session, + int in_use, + const struct GNUNET_ATS_Information *atsi, + uint32_t atsi_count); + + +/** + * Remove an address from the solver + * + * @param solver the solver handle + * @param addresses the address hashmap containing all addresses + * @param address the address to remove + * @param session_only delete only session not whole address + */ +void +GAS_simplistic_address_delete (void *solver, + struct GNUNET_CONTAINER_MultiHashMap * addresses, + struct ATS_Address *address, int session_only); + + +/** + * Get the prefered address for a specific peer + * + * @param solver the solver handle + * @param addresses the address hashmap containing all addresses + * @param peer the identity of the peer + */ +const struct ATS_Address * +GAS_simplistic_get_preferred_address (void *solver, + struct GNUNET_CONTAINER_MultiHashMap * addresses, + const struct GNUNET_PeerIdentity *peer); + + +/** + * Changes the preferences for a peer in the problem + * + * @param solver the solver handle + * @param client the client with this preference + * @param peer the peer to change the preference for + * @param kind the kind to change the preference + * @param score the score + */ +void +GAS_simplistic_address_change_preference (void *solver, + void *client, + const struct GNUNET_PeerIdentity *peer, + enum GNUNET_ATS_PreferenceKind kind, + float score); + + +/* end of gnunet-service-ats_addresses_simplistic.h */ diff --git a/src/ats/gnunet-service-ats_performance.c b/src/ats/gnunet-service-ats_performance.c index 7ab8e9a..35f0223 100644 --- a/src/ats/gnunet-service-ats_performance.c +++ b/src/ats/gnunet-service-ats_performance.c @@ -60,6 +60,28 @@ struct PerformanceClient }; +/** + * We keep clients that are interested in performance in a linked list. + */ +struct AddressIteration +{ + /** + * Actual handle to the client. + */ + struct PerformanceClient *pc; + + int all; + + uint32_t id; + + unsigned int msg_type; +}; + +/** + * Address handle + */ +static struct GAS_Addresses_Handle *GSA_addresses; + /** * Head of linked list of all clients to this service. */ @@ -93,29 +115,6 @@ find_client (struct GNUNET_SERVER_Client *client) return NULL; } - -/** - * Register a new performance client. - * - * @param client handle of the new client - * @param flag flag specifying the type of the client - */ -void -GAS_performance_add_client (struct GNUNET_SERVER_Client *client, - enum StartFlag flag) -{ - struct PerformanceClient *pc; - - GNUNET_break (NULL == find_client (client)); - pc = GNUNET_malloc (sizeof (struct PerformanceClient)); - pc->client = client; - pc->flag = flag; - GNUNET_SERVER_notification_context_add (nc, client); - GNUNET_SERVER_client_keep (client); - GNUNET_CONTAINER_DLL_insert (pc_head, pc_tail, pc); -} - - /** * Unregister a client (which may have been a performance client, * but this is not assured). @@ -126,7 +125,6 @@ void GAS_performance_remove_client (struct GNUNET_SERVER_Client *client) { struct PerformanceClient *pc; - pc = find_client (client); if (NULL == pc) return; @@ -135,31 +133,34 @@ GAS_performance_remove_client (struct GNUNET_SERVER_Client *client) GNUNET_free (pc); } - /** * Transmit the given performance information to all performance * clients. * + * @param pc performance client to send to * @param peer peer for which this is an address suggestion * @param plugin_name 0-termintated string specifying the transport plugin * @param plugin_addr binary address for the plugin to use * @param plugin_addr_len number of bytes in plugin_addr + * @param active is this address active * @param atsi performance data for the address * @param atsi_count number of performance records in 'ats' * @param bandwidth_out assigned outbound bandwidth * @param bandwidth_in assigned inbound bandwidth */ void -GAS_performance_notify_clients (const struct GNUNET_PeerIdentity *peer, - const char *plugin_name, - const void *plugin_addr, size_t plugin_addr_len, - const struct GNUNET_ATS_Information *atsi, - uint32_t atsi_count, - struct GNUNET_BANDWIDTH_Value32NBO - bandwidth_out, - struct GNUNET_BANDWIDTH_Value32NBO bandwidth_in) +GAS_performance_notify_client (struct PerformanceClient *pc, + const struct GNUNET_PeerIdentity *peer, + const char *plugin_name, + const void *plugin_addr, size_t plugin_addr_len, + const int active, + const struct GNUNET_ATS_Information *atsi, + uint32_t atsi_count, + struct GNUNET_BANDWIDTH_Value32NBO + bandwidth_out, + struct GNUNET_BANDWIDTH_Value32NBO bandwidth_in) { - struct PerformanceClient *pc; + struct PeerInformationMessage *msg; size_t plugin_name_length = strlen (plugin_name) + 1; size_t msize = @@ -170,6 +171,10 @@ GAS_performance_notify_clients (const struct GNUNET_PeerIdentity *peer, struct GNUNET_ATS_Information *atsp; char *addrp; + GNUNET_assert (NULL != pc); + if (NULL == find_client (pc->client)) + return; /* Client disconnected */ + GNUNET_assert (msize < GNUNET_SERVER_MAX_MESSAGE_SIZE); GNUNET_assert (atsi_count < GNUNET_SERVER_MAX_MESSAGE_SIZE / @@ -177,9 +182,11 @@ GAS_performance_notify_clients (const struct GNUNET_PeerIdentity *peer, msg = (struct PeerInformationMessage *) buf; msg->header.size = htons (msize); msg->header.type = htons (GNUNET_MESSAGE_TYPE_ATS_PEER_INFORMATION); + msg->id = htonl (0); msg->ats_count = htonl (atsi_count); msg->peer = *peer; msg->address_length = htons (plugin_addr_len); + msg->address_active = ntohl (active); msg->plugin_name_length = htons (plugin_name_length); msg->bandwidth_out = bandwidth_out; msg->bandwidth_in = bandwidth_in; @@ -188,18 +195,314 @@ GAS_performance_notify_clients (const struct GNUNET_PeerIdentity *peer, addrp = (char *) &atsp[atsi_count]; memcpy (addrp, plugin_addr, plugin_addr_len); strcpy (&addrp[plugin_addr_len], plugin_name); + GNUNET_SERVER_notification_context_unicast (nc, pc->client, &msg->header, + GNUNET_YES); +} + + +/** + * Transmit the given performance information to all performance + * clients. + * + * @param peer peer for which this is an address suggestion + * @param plugin_name 0-termintated string specifying the transport plugin + * @param plugin_addr binary address for the plugin to use + * @param plugin_addr_len number of bytes in plugin_addr + * @param active is this address active + * @param atsi performance data for the address + * @param atsi_count number of performance records in 'ats' + * @param bandwidth_out assigned outbound bandwidth + * @param bandwidth_in assigned inbound bandwidth + */ +void +GAS_performance_notify_all_clients (const struct GNUNET_PeerIdentity *peer, + const char *plugin_name, + const void *plugin_addr, size_t plugin_addr_len, + const int active, + const struct GNUNET_ATS_Information *atsi, + uint32_t atsi_count, + struct GNUNET_BANDWIDTH_Value32NBO + bandwidth_out, + struct GNUNET_BANDWIDTH_Value32NBO bandwidth_in) +{ + struct PerformanceClient *pc; + for (pc = pc_head; pc != NULL; pc = pc->next) if (pc->flag == START_FLAG_PERFORMANCE_WITH_PIC) { - GNUNET_SERVER_notification_context_unicast (nc, pc->client, &msg->header, - GNUNET_YES); - GNUNET_STATISTICS_update (GSA_stats, - "# performance updates given to clients", 1, - GNUNET_NO); + GAS_performance_notify_client (pc, + peer, + plugin_name, plugin_addr, plugin_addr_len, + active, + atsi, atsi_count, + bandwidth_out, bandwidth_in); } + GNUNET_STATISTICS_update (GSA_stats, + "# performance updates given to clients", 1, + GNUNET_NO); } +static void +peerinfo_it (void *cls, + const struct GNUNET_PeerIdentity *id, + const char *plugin_name, + const void *plugin_addr, size_t plugin_addr_len, + const int active, + const struct GNUNET_ATS_Information *atsi, + uint32_t atsi_count, + struct GNUNET_BANDWIDTH_Value32NBO + bandwidth_out, + struct GNUNET_BANDWIDTH_Value32NBO bandwidth_in) +{ + struct PerformanceClient *pc = cls; + GNUNET_assert (NULL != pc); + if (NULL == id) + return; + + if (GNUNET_NO == active) + return; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Callback for peer `%s' plugin `%s' BW out %llu, BW in %llu \n", + GNUNET_i2s (id), + plugin_name, + ntohl (bandwidth_out.value__), + ntohl (bandwidth_in.value__)); + GAS_performance_notify_client(pc, + id, + plugin_name, plugin_addr, plugin_addr_len, + active, + atsi, atsi_count, + bandwidth_out, bandwidth_in); +} + + +/** + * Iterator for GAS_performance_add_client + * + * @param cls the client requesting information + * @param id result + */ +static void +peer_it (void *cls, + const struct GNUNET_PeerIdentity *id) +{ + struct PerformanceClient *pc = cls; + if (NULL != id) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Callback for peer `%s'\n", GNUNET_i2s (id)); + GAS_addresses_get_peer_info (GSA_addresses, id, &peerinfo_it, pc); + } +} + +/** + * Register a new performance client. + * + * @param client handle of the new client + * @param flag flag specifying the type of the client + */ +void +GAS_performance_add_client (struct GNUNET_SERVER_Client *client, + enum StartFlag flag) +{ + struct PerformanceClient *pc; + GNUNET_break (NULL == find_client (client)); + + pc = GNUNET_malloc (sizeof (struct PerformanceClient)); + pc->client = client; + pc->flag = flag; + GNUNET_SERVER_notification_context_add (nc, client); + GNUNET_SERVER_client_keep (client); + GNUNET_CONTAINER_DLL_insert (pc_head, pc_tail, pc); + + /* Send information about clients */ + GAS_addresses_iterate_peers (GSA_addresses, &peer_it, pc); +} + +static void transmit_req_addr (struct AddressIteration *ai, + const struct GNUNET_PeerIdentity *id, + const char *plugin_name, + const void *plugin_addr, size_t plugin_addr_len, + const int active, + const struct GNUNET_ATS_Information *atsi, + uint32_t atsi_count, + struct GNUNET_BANDWIDTH_Value32NBO + bandwidth_out, + struct GNUNET_BANDWIDTH_Value32NBO bandwidth_in) + +{ + + struct GNUNET_ATS_Information *atsp; + struct PeerInformationMessage *msg; + char *addrp; + size_t plugin_name_length; + size_t msize; + + if (NULL != plugin_name) + plugin_name_length = strlen (plugin_name) + 1; + else + plugin_name_length = 0; + msize = sizeof (struct PeerInformationMessage) + + atsi_count * sizeof (struct GNUNET_ATS_Information) + + plugin_addr_len + plugin_name_length; + char buf[msize] GNUNET_ALIGN; + + GNUNET_assert (msize < GNUNET_SERVER_MAX_MESSAGE_SIZE); + GNUNET_assert (atsi_count < + GNUNET_SERVER_MAX_MESSAGE_SIZE / + sizeof (struct GNUNET_ATS_Information)); + msg = (struct PeerInformationMessage *) buf; + msg->header.size = htons (msize); + msg->header.type = htons (GNUNET_MESSAGE_TYPE_ATS_ADDRESSLIST_RESPONSE); + msg->ats_count = htonl (atsi_count); + msg->id = htonl (ai->id); + if (NULL != id) + msg->peer = *id; + else + memset (&msg->peer, '\0', sizeof (struct GNUNET_PeerIdentity)); + msg->address_length = htons (plugin_addr_len); + msg->address_active = ntohl (active); + msg->plugin_name_length = htons (plugin_name_length); + msg->bandwidth_out = bandwidth_out; + msg->bandwidth_in = bandwidth_in; + atsp = (struct GNUNET_ATS_Information *) &msg[1]; + memcpy (atsp, atsi, sizeof (struct GNUNET_ATS_Information) * atsi_count); + addrp = (char *) &atsp[atsi_count]; + if (NULL != plugin_addr) + memcpy (addrp, plugin_addr, plugin_addr_len); + if (NULL != plugin_name) + strcpy (&addrp[plugin_addr_len], plugin_name); + GNUNET_SERVER_notification_context_unicast (nc, ai->pc->client, &msg->header, + GNUNET_NO); +} + +static void +req_addr_peerinfo_it (void *cls, + const struct GNUNET_PeerIdentity *id, + const char *plugin_name, + const void *plugin_addr, size_t plugin_addr_len, + const int active, + const struct GNUNET_ATS_Information *atsi, + uint32_t atsi_count, + struct GNUNET_BANDWIDTH_Value32NBO + bandwidth_out, + struct GNUNET_BANDWIDTH_Value32NBO bandwidth_in) +{ + struct AddressIteration *ai = cls; + + GNUNET_assert (NULL != ai); + GNUNET_assert (NULL != ai->pc); + if (NULL == find_client (ai->pc->client)) + return; /* Client disconnected */ + + if ((NULL == id) && (NULL == plugin_name) && (NULL == plugin_addr)) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Address iteration done\n"); + return; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Callback for %s peer `%s' plugin `%s' BW out %u, BW in %u \n", + (active == GNUNET_YES) ? "ACTIVE" : "INACTIVE", + GNUNET_i2s (id), + plugin_name, + (unsigned int) ntohl (bandwidth_out.value__), + (unsigned int) ntohl (bandwidth_in.value__)); + + /* Transmit result */ + if ((GNUNET_YES == ai->all) || (GNUNET_YES == active)) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Sending result for %s peer `%s' plugin `%s' BW out %u, BW in %u \n", + (active == GNUNET_YES) ? "ACTIVE" : "INACTIVE", + GNUNET_i2s (id), + plugin_name, + (unsigned int) ntohl (bandwidth_out.value__), + (unsigned int) ntohl (bandwidth_in.value__)); + transmit_req_addr (cls, + id, + plugin_name, + plugin_addr, plugin_addr_len, + active, + atsi, + atsi_count, + bandwidth_out, bandwidth_in); + } +} + + +/** + * Iterator for GAS_handle_request_address_list + * + * @param cls the client requesting information + * @param id result + */ +static void +req_addr_peer_it (void *cls, + const struct GNUNET_PeerIdentity *id) +{ + struct AddressIteration *ai = cls; + if (NULL != id) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Callback for peer `%s'\n", GNUNET_i2s (id)); + GAS_addresses_get_peer_info (GSA_addresses, id, &req_addr_peerinfo_it, ai); + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Peer iteration done\n"); + } +} + +/** + * Handle 'address list request' messages from clients. + * + * @param cls unused, NULL + * @param client client that sent the request + * @param message the request message + */ +void +GAS_handle_request_address_list (void *cls, struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) +{ + struct PerformanceClient *pc; + struct AddressIteration ai; + struct AddressListRequestMessage * alrm = (struct AddressListRequestMessage *) message; + struct GNUNET_PeerIdentity allzeros; + struct GNUNET_BANDWIDTH_Value32NBO bandwidth_zero; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received `%s' message\n", + "ADDRESSLIST_REQUEST"); + + if (NULL == (pc = find_client(client))) + { + GNUNET_break (0); + return; + } + + ai.all = ntohl (alrm->all); + ai.id = ntohl (alrm->id); + ai.pc = pc; + + memset (&allzeros, '\0', sizeof (struct GNUNET_PeerIdentity)); + bandwidth_zero.value__ = htonl (0); + if (0 == memcmp (&alrm->peer, &allzeros, sizeof (struct GNUNET_PeerIdentity))) + { + /* Return addresses for all peers */ + GAS_addresses_iterate_peers (GSA_addresses, &req_addr_peer_it, &ai); + transmit_req_addr (&ai, NULL, NULL, NULL, 0, GNUNET_NO, NULL, 0, bandwidth_zero, bandwidth_zero); + } + else + { + /* Return addresses for a specific peer */ + GAS_addresses_get_peer_info (GSA_addresses, &alrm->peer, &req_addr_peerinfo_it, &ai); + transmit_req_addr (&ai, NULL, NULL, NULL, 0, GNUNET_NO, NULL, 0, bandwidth_zero, bandwidth_zero); + } + GNUNET_SERVER_receive_done (client, GNUNET_OK); +} + + + /** * Handle 'reservation request' messages from clients. * @@ -251,7 +554,8 @@ GAS_handle_reservation_request (void *cls, struct GNUNET_SERVER_Client *client, * @param message the request message */ void -GAS_handle_preference_change (void *cls, struct GNUNET_SERVER_Client *client, +GAS_handle_preference_change (void *cls, + struct GNUNET_SERVER_Client *client, const struct GNUNET_MessageHeader *message) { const struct ChangePreferenceMessage *msg; @@ -283,7 +587,9 @@ GAS_handle_preference_change (void *cls, struct GNUNET_SERVER_Client *client, 1, GNUNET_NO); pi = (const struct PreferenceInformation *) &msg[1]; for (i = 0; i < nump; i++) - GAS_addresses_change_preference (&msg->peer, + GAS_addresses_change_preference (GSA_addresses, + client, + &msg->peer, (enum GNUNET_ATS_PreferenceKind) ntohl (pi[i].preference_kind), pi[i].preference_value); @@ -295,10 +601,13 @@ GAS_handle_preference_change (void *cls, struct GNUNET_SERVER_Client *client, * Initialize performance subsystem. * * @param server handle to our server + * @param addresses the address handle to use */ void -GAS_performance_init (struct GNUNET_SERVER_Handle *server) +GAS_performance_init (struct GNUNET_SERVER_Handle *server, + struct GAS_Addresses_Handle *addresses) { + GSA_addresses = addresses; nc = GNUNET_SERVER_notification_context_create (server, 128); } diff --git a/src/ats/gnunet-service-ats_performance.h b/src/ats/gnunet-service-ats_performance.h index 75d555a..6d527ae 100644 --- a/src/ats/gnunet-service-ats_performance.h +++ b/src/ats/gnunet-service-ats_performance.h @@ -60,15 +60,17 @@ GAS_performance_remove_client (struct GNUNET_SERVER_Client *client); * @param plugin_name 0-termintated string specifying the transport plugin * @param plugin_addr binary address for the plugin to use * @param plugin_addr_len number of bytes in plugin_addr + * @param active is this address active * @param atsi performance data for the address * @param atsi_count number of performance records in 'ats' * @param bandwidth_out assigned outbound bandwidth * @param bandwidth_in assigned inbound bandwidth */ void -GAS_performance_notify_clients (const struct GNUNET_PeerIdentity *peer, +GAS_performance_notify_all_clients (const struct GNUNET_PeerIdentity *peer, const char *plugin_name, const void *plugin_addr, size_t plugin_addr_len, + const int active, const struct GNUNET_ATS_Information *atsi, uint32_t atsi_count, struct GNUNET_BANDWIDTH_Value32NBO @@ -77,6 +79,18 @@ GAS_performance_notify_clients (const struct GNUNET_PeerIdentity *peer, bandwidth_in); +/** + * Handle 'address list request' messages from clients. + * + * @param cls unused, NULL + * @param client client that sent the request + * @param message the request message + */ +void +GAS_handle_request_address_list (void *cls, + struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message); + /** * Handle 'reservation request' messages from clients. * @@ -85,7 +99,8 @@ GAS_performance_notify_clients (const struct GNUNET_PeerIdentity *peer, * @param message the request message */ void -GAS_handle_reservation_request (void *cls, struct GNUNET_SERVER_Client *client, +GAS_handle_reservation_request (void *cls, + struct GNUNET_SERVER_Client *client, const struct GNUNET_MessageHeader *message); @@ -97,7 +112,8 @@ GAS_handle_reservation_request (void *cls, struct GNUNET_SERVER_Client *client, * @param message the request message */ void -GAS_handle_preference_change (void *cls, struct GNUNET_SERVER_Client *client, +GAS_handle_preference_change (void *cls, + struct GNUNET_SERVER_Client *client, const struct GNUNET_MessageHeader *message); @@ -105,9 +121,11 @@ GAS_handle_preference_change (void *cls, struct GNUNET_SERVER_Client *client, * Initialize performance subsystem. * * @param server handle to our server + * @param addresses the address handle to use */ void -GAS_performance_init (struct GNUNET_SERVER_Handle *server); +GAS_performance_init (struct GNUNET_SERVER_Handle *server, + struct GAS_Addresses_Handle *GSA_addresses); /** diff --git a/src/ats/gnunet-service-ats_reservations.c b/src/ats/gnunet-service-ats_reservations.c index d1212dd..3354c4e 100644 --- a/src/ats/gnunet-service-ats_reservations.c +++ b/src/ats/gnunet-service-ats_reservations.c @@ -122,7 +122,7 @@ GAS_reservations_set_bandwidth (const struct GNUNET_PeerIdentity *peer, void GAS_reservations_init () { - trackers = GNUNET_CONTAINER_multihashmap_create (128); + trackers = GNUNET_CONTAINER_multihashmap_create (128, GNUNET_NO); } @@ -135,7 +135,7 @@ GAS_reservations_init () * @return GNUNET_OK (continue to iterate) */ static int -free_tracker (void *cls, const GNUNET_HashCode * key, void *value) +free_tracker (void *cls, const struct GNUNET_HashCode * key, void *value) { struct GNUNET_BANDWIDTH_Tracker *tracker = value; diff --git a/src/ats/gnunet-service-ats_scheduling.c b/src/ats/gnunet-service-ats_scheduling.c index 0b66ac5..4a20f90 100644 --- a/src/ats/gnunet-service-ats_scheduling.c +++ b/src/ats/gnunet-service-ats_scheduling.c @@ -42,6 +42,11 @@ static struct GNUNET_SERVER_NotificationContext *nc; static struct GNUNET_SERVER_Client *my_client; +/** + * Handle to address subsystem + */ +static struct GAS_Addresses_Handle *address_handle; + /** * Register a new scheduling client. * @@ -74,7 +79,7 @@ GAS_scheduling_remove_client (struct GNUNET_SERVER_Client *client) { if (my_client != client) return; - GAS_addresses_destroy_all (); + GAS_addresses_destroy_all (address_handle); my_client = NULL; } @@ -166,10 +171,8 @@ GAS_handle_request_address (void *cls, struct GNUNET_SERVER_Client *client, GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received `%s' message\n", "REQUEST_ADDRESS"); - GNUNET_STATISTICS_update (GSA_stats, "# address requests received", 1, - GNUNET_NO); GNUNET_break (0 == ntohl (msg->reserved)); - GAS_addresses_request_address (&msg->peer); + GAS_addresses_request_address (address_handle, &msg->peer); GNUNET_SERVER_receive_done (client, GNUNET_OK); } @@ -193,7 +196,7 @@ GAS_handle_request_address_cancel (void *cls, "REQUEST_ADDRESS_CANCEL"); GNUNET_break (0 == ntohl (msg->reserved)); - /* TODO */ + GAS_addresses_request_address_cancel (address_handle, &msg->peer); GNUNET_SERVER_receive_done (client, GNUNET_OK); } @@ -215,10 +218,66 @@ GAS_handle_reset_backoff (void *cls, GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received `%s' message\n", "RESET_BACKOFF"); - GNUNET_STATISTICS_update (GSA_stats, "# backoff reset requests received", 1, - GNUNET_NO); GNUNET_break (0 == ntohl (msg->reserved)); - GAS_addresses_handle_backoff_reset (&msg->peer); + GAS_addresses_handle_backoff_reset (address_handle, &msg->peer); + GNUNET_SERVER_receive_done (client, GNUNET_OK); +} + +/** + * Handle 'address add' messages from clients. + * + * @param cls unused, NULL + * @param client client that sent the request + * @param message the request message + */ +void +GAS_handle_address_add (void *cls, struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) +{ + const struct AddressUpdateMessage *m; + const struct GNUNET_ATS_Information *atsi; + const char *address; + const char *plugin_name; + uint16_t address_length; + uint16_t plugin_name_length; + uint32_t ats_count; + uint16_t size; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received `%s' message\n", + "ADDRESS_ADD"); + size = ntohs (message->size); + if (size < sizeof (struct AddressUpdateMessage)) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + m = (const struct AddressUpdateMessage *) message; + ats_count = ntohl (m->ats_count); + address_length = ntohs (m->address_length); + plugin_name_length = ntohs (m->plugin_name_length); + atsi = (const struct GNUNET_ATS_Information *) &m[1]; + address = (const char *) &atsi[ats_count]; + if (plugin_name_length != 0) + plugin_name = &address[address_length]; + else + plugin_name = ""; + + if ((address_length + plugin_name_length + + ats_count * sizeof (struct GNUNET_ATS_Information) + + sizeof (struct AddressUpdateMessage) != ntohs (message->size)) || + (ats_count > + GNUNET_SERVER_MAX_MESSAGE_SIZE / sizeof (struct GNUNET_ATS_Information)) || + ((plugin_name_length > 0) && (plugin_name[plugin_name_length - 1] != '\0'))) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + GNUNET_STATISTICS_update (GSA_stats, "# address updates received", 1, + GNUNET_NO); + GAS_addresses_add (address_handle, &m->peer, plugin_name, address, address_length, + ntohl (m->session_id), atsi, ats_count); GNUNET_SERVER_receive_done (client, GNUNET_OK); } @@ -276,7 +335,7 @@ GAS_handle_address_update (void *cls, struct GNUNET_SERVER_Client *client, } GNUNET_STATISTICS_update (GSA_stats, "# address updates received", 1, GNUNET_NO); - GAS_addresses_update (&m->peer, plugin_name, address, address_length, + GAS_addresses_update (address_handle, &m->peer, plugin_name, address, address_length, ntohl (m->session_id), atsi, ats_count); GNUNET_SERVER_receive_done (client, GNUNET_OK); } @@ -332,12 +391,13 @@ GAS_handle_address_in_use (void *cls, struct GNUNET_SERVER_Client *client, } in_use = ntohs (m->in_use); - res = GAS_addresses_in_use (&m->peer, - plugin_name, - address, - address_length, - ntohl (m->session_id), - in_use); + res = GAS_addresses_in_use (address_handle, + &m->peer, + plugin_name, + address, + address_length, + ntohl (m->session_id), + in_use); if (res == GNUNET_OK) GNUNET_SERVER_receive_done (client, GNUNET_OK); @@ -402,7 +462,8 @@ GAS_handle_address_destroyed (void *cls, struct GNUNET_SERVER_Client *client, return; } GNUNET_STATISTICS_update (GSA_stats, "# addresses destroyed", 1, GNUNET_NO); - GAS_addresses_destroy (&m->peer, plugin_name, address, address_length, + GAS_addresses_destroy (address_handle, &m->peer, plugin_name, + address, address_length, ntohl (m->session_id)); if (0 != ntohl (m->session_id)) { @@ -421,10 +482,12 @@ GAS_handle_address_destroyed (void *cls, struct GNUNET_SERVER_Client *client, * Initialize scheduling subsystem. * * @param server handle to our server + * @param ah the address handle to use */ void -GAS_scheduling_init (struct GNUNET_SERVER_Handle *server) +GAS_scheduling_init (struct GNUNET_SERVER_Handle *server, struct GAS_Addresses_Handle *ah) { + address_handle = ah; nc = GNUNET_SERVER_notification_context_create (server, 128); } diff --git a/src/ats/gnunet-service-ats_scheduling.h b/src/ats/gnunet-service-ats_scheduling.h index 08a7f1b..d7b5e9c 100644 --- a/src/ats/gnunet-service-ats_scheduling.h +++ b/src/ats/gnunet-service-ats_scheduling.h @@ -115,6 +115,18 @@ GAS_handle_request_address_cancel (void *cls, struct GNUNET_SERVER_Client *client, const struct GNUNET_MessageHeader *message); + +/** + * Handle 'address add' messages from clients. + * + * @param cls unused, NULL + * @param client client that sent the request + * @param message the request message + */ +void +GAS_handle_address_add (void *cls, struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message); + /** * Handle 'address update' messages from clients. * @@ -147,7 +159,8 @@ GAS_handle_address_in_use (void *cls, struct GNUNET_SERVER_Client *client, * @param message the request message */ void -GAS_handle_address_destroyed (void *cls, struct GNUNET_SERVER_Client *client, +GAS_handle_address_destroyed (void *cls, + struct GNUNET_SERVER_Client *client, const struct GNUNET_MessageHeader *message); @@ -155,9 +168,10 @@ GAS_handle_address_destroyed (void *cls, struct GNUNET_SERVER_Client *client, * Initialize scheduling subsystem. * * @param server handle to our server + * @param ah the address handle to use */ void -GAS_scheduling_init (struct GNUNET_SERVER_Handle *server); +GAS_scheduling_init (struct GNUNET_SERVER_Handle *server, struct GAS_Addresses_Handle *ah); /** diff --git a/src/ats/perf_ats_mlp.c b/src/ats/perf_ats_mlp.c deleted file mode 100644 index b9ee5e4..0000000 --- a/src/ats/perf_ats_mlp.c +++ /dev/null @@ -1,372 +0,0 @@ -/* - This file is part of GNUnet. - (C) 2010,2011 Christian Grothoff (and other contributing authors) - - GNUnet is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published - by the Free Software Foundation; either version 3, or (at your - option) any later version. - - GNUnet is distributed in the hope that it will be useful, but - WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - General Public License for more details. - - You should have received a copy of the GNU General Public License - along with GNUnet; see the file COPYING. If not, write to the - Free Software Foundation, Inc., 59 Temple Place - Suite 330, - Boston, MA 02111-1307, USA. -*/ -/** - * @file ats/perf_ats_mlp - * @brief performance test for the MLP solver - * @author Christian Grothoff - * @author Matthias Wachs - - */ -#include "platform.h" -#include "gnunet_util_lib.h" -#include "gnunet_statistics_service.h" -#include "gnunet-service-ats_addresses_mlp.h" - -#define MLP_MAX_EXEC_DURATION GNUNET_TIME_relative_multiply(GNUNET_TIME_UNIT_SECONDS, 3) -#define MLP_MAX_ITERATIONS INT_MAX - -#define DEF_PEERS 10 -#define DEF_ADDRESSES_PER_PEER 5 -#define DEF_ATS_VALUES 2 -#define DEF_ATS_MAX_DELAY 30 -#define DEF_ATS_MAX_DISTANCE 3 - -static unsigned int peers; -static unsigned int addresses; -static unsigned int numeric; -static unsigned int update_percentage; - -static int start; -static int end; - -struct ATS_Peer *p; -struct ATS_Address *a; - -static int ret; - -static struct GNUNET_CONTAINER_MultiHashMap * amap; - -static struct GAS_MLP_Handle *mlp; - - - - -GNUNET_SCHEDULER_TaskIdentifier shutdown_task; - -struct PeerContext -{ - struct GNUNET_PeerIdentity id; - - struct Address *addr; -}; - -struct Address -{ - char *plugin; - size_t plugin_len; - - void *addr; - size_t addr_len; - - struct GNUNET_ATS_Information *ats; - int ats_count; - - void *session; -}; - -void -do_shutdown (void *cls, - const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - unsigned int ca; - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Shutdown\n"); - - if (NULL != mlp) - { - GAS_mlp_done (mlp); - mlp = NULL; - } - - if (NULL != a) - { - for (ca=0; ca < (peers * addresses); ca++) - { - GNUNET_free (a[ca].plugin); - GNUNET_free (a[ca].ats); - } - } - - if (NULL != amap) - GNUNET_CONTAINER_multihashmap_destroy(amap); - GNUNET_free_non_null (a); - GNUNET_free_non_null (p); - -} - -static void -update_addresses (struct ATS_Address * a, unsigned int addrs, unsigned int percentage) -{ - if (percentage == 0) - return; - - unsigned int ua = (addrs) * ((float) percentage / 100); - GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Updating %u of %u addresses per peer\n", ua, addrs); - - unsigned int updated[addrs]; - unsigned int u_types[DEF_ATS_VALUES]; - unsigned int updates = 0; - unsigned int u_type = 0; - unsigned int u_val = 0; - unsigned int cur = 0; - - u_types[0] = 0; - u_types[1] = 0; - - for (cur = 0; cur < addrs; cur ++) - { - updated[cur] = 0; - } - cur = 0; - - while (updates < ua) - { - cur = GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK, addrs); - if (0 == updated[cur]) - { - u_type = GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK, DEF_ATS_VALUES); - switch (u_type) { - case 0: - do - { - u_val = GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK, DEF_ATS_MAX_DELAY); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Updating DELAY from %u to %u\n",a[cur].ats[u_type].value, u_val); - } - while (a[cur].ats[u_type].value == u_val); - break; - case 1: - do - { - u_val = GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK, DEF_ATS_MAX_DISTANCE); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Updating DISTANCE from %u to %u\n",a[cur].ats[u_type].value, u_val); - } - while (a[cur].ats[u_type].value == u_val); - break; - default: - GNUNET_break (0); - break; - } - u_types[u_type]++; - - a[cur].ats[u_type].value = u_val; - updated[cur] = 1; - GAS_mlp_address_update(mlp, amap, &a[cur]); - updates++; - } - } - GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Updated %u delay and %u distance values\n", u_types[0], u_types[1]); - -} - - -static void -check (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) -{ - unsigned int c = 0; - unsigned int c2 = 0; - unsigned int ca = 0; - int update = GNUNET_NO; - int range = GNUNET_NO; - int res; - -#if !HAVE_LIBGLPK - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "GLPK not installed!"); - ret = 1; - return; -#endif - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Setting up %u peers with %u addresses per peer\n", peers, addresses); - - mlp = GAS_mlp_init (cfg, NULL, MLP_MAX_EXEC_DURATION, MLP_MAX_ITERATIONS); - if (NULL == mlp) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Failed to init MLP\n"); - ret = 1; - if (GNUNET_SCHEDULER_NO_TASK != shutdown_task) - GNUNET_SCHEDULER_cancel(shutdown_task); - shutdown_task = GNUNET_SCHEDULER_add_now (&do_shutdown, NULL); - } - - if (peers == 0) - peers = DEF_PEERS; - if (addresses == 0) - addresses = DEF_ADDRESSES_PER_PEER; - - p = GNUNET_malloc (peers * sizeof (struct ATS_Peer)); - a = GNUNET_malloc (peers * addresses * sizeof (struct ATS_Address)); - - amap = GNUNET_CONTAINER_multihashmap_create(addresses * peers); - - mlp->auto_solve = GNUNET_NO; - if (start == 0) - start = 0; - if (end == 0) - end = -1; - if ((start != -1) && (end != -1)) - { - GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Solving problem starting from %u to %u\n", start , end); - range = GNUNET_YES; - } - else - GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Solving problem for %u peers\n", peers); - - if ((update_percentage >= 0) && (update_percentage <= 100)) - { - update = GNUNET_YES; - GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Benchmarking with existing presolution and %u%% updated addresses\n", update_percentage); - } - else if ((update_percentage > 100) && (update_percentage != UINT_MAX)) - { - GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Invalid percentage: %u\n", update_percentage); - ret = 1; - return; - } - - for (c=0; c < peers; c++) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Setting up peer %u\n", c); - GNUNET_CRYPTO_hash_create_random(GNUNET_CRYPTO_QUALITY_NONCE, &p[c].id.hashPubKey); - - for (c2=0; c2 < addresses; c2++) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Setting up address %u for peer %u\n", c2, c); - /* Setting required information */ - a[ca].mlp_information = NULL; - a[ca].prev = NULL; - a[ca].next = NULL; - - /* Setting address */ - a[ca].peer = p[c].id; - a[ca].plugin = GNUNET_strdup("test"); - a[ca].atsp_network_type = GNUNET_ATS_NET_LOOPBACK; - - a[ca].ats = GNUNET_malloc (DEF_ATS_VALUES * sizeof (struct GNUNET_ATS_Information)); - a[ca].ats[0].type = GNUNET_ATS_QUALITY_NET_DELAY; - a[ca].ats[0].value = GNUNET_CRYPTO_random_u32(GNUNET_CRYPTO_QUALITY_WEAK, DEF_ATS_MAX_DELAY); - a[ca].ats[1].type = GNUNET_ATS_QUALITY_NET_DISTANCE; - a[ca].ats[1].value = GNUNET_CRYPTO_random_u32(GNUNET_CRYPTO_QUALITY_WEAK, DEF_ATS_MAX_DISTANCE); - a[ca].ats_count = 2; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Setting up address %u\n", ca); - GNUNET_CONTAINER_multihashmap_put (amap, &a[ca].peer.hashPubKey, &a[ca], GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE); - GAS_mlp_address_update(mlp, amap, &a[ca]); - ca++; - } - - GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Problem contains %u peers and %u adresses\n", mlp->c_p, mlp->addr_in_problem); - - if (((GNUNET_YES == range) && (((start >= 0) && ((c+1) >= start)) && (c <= end))) || ((c+1) == peers)) - { - GNUNET_assert ((c+1) == mlp->c_p); - GNUNET_assert ((c+1) * addresses == mlp->addr_in_problem); - - /* Solving the problem */ - struct GAS_MLP_SolutionContext ctx; - - res = GAS_mlp_solve_problem(mlp, &ctx); - - if (GNUNET_NO == update) - { - if (GNUNET_OK == res) - { - GNUNET_assert (GNUNET_OK == ctx.lp_result); - GNUNET_assert (GNUNET_OK == ctx.mlp_result); - if (GNUNET_YES == numeric) - printf ("%u;%u;%llu;%llu\n",mlp->c_p, mlp->addr_in_problem, (unsigned long long) ctx.lp_duration.rel_value, (unsigned long long) ctx.mlp_duration.rel_value); - else - GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Problem solved for %u peers with %u address successfully (LP: %llu ms / MLP: %llu ms)\n", - mlp->c_p, mlp->addr_in_problem, ctx.lp_duration.rel_value, ctx.mlp_duration.rel_value); - } - else - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Solving problem with %u peers and %u addresses failed\n", c, c2); - } - else - { - struct GAS_MLP_SolutionContext uctx; - /* Update addresses */ - update_addresses (a, (c+1) * c2, update_percentage); - - /* Solve again */ - res = GAS_mlp_solve_problem(mlp, &uctx); - - if (GNUNET_OK == res) - { - GNUNET_assert (GNUNET_OK == uctx.lp_result); - GNUNET_assert (GNUNET_OK == uctx.mlp_result); - if (GNUNET_YES == numeric) - printf ("%u;%u;%llu;%llu;%llu;%llu\n",mlp->c_p, mlp->addr_in_problem, - (unsigned long long) ctx.lp_duration.rel_value, (unsigned long long) ctx.mlp_duration.rel_value, - (unsigned long long) uctx.lp_duration.rel_value, (unsigned long long) uctx.mlp_duration.rel_value); - else - GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Updated problem solved for %u peers with %u address successfully (Initial: LP/MLP: %llu/%llu ms, Update: %llu/%llu ms)\n", - mlp->c_p, mlp->addr_in_problem, - (unsigned long long) ctx.lp_duration.rel_value, (unsigned long long) ctx.mlp_duration.rel_value, - (unsigned long long) uctx.lp_duration.rel_value, (unsigned long long) uctx.mlp_duration.rel_value); - } - else - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Solving updated problem with %u peers and %u addresses failed\n", c, c2); - } - } - } - - if (GNUNET_SCHEDULER_NO_TASK != shutdown_task) - GNUNET_SCHEDULER_cancel(shutdown_task); - shutdown_task = GNUNET_SCHEDULER_add_now (&do_shutdown, NULL); - -} - - -int -main (int argc, char *argv[]) -{ - /* Init invalid */ - update_percentage = UINT_MAX; - static struct GNUNET_GETOPT_CommandLineOption options[] = { - {'a', "addresses", NULL, - gettext_noop ("addresses per peer"), 1, - &GNUNET_GETOPT_set_uint, &addresses}, - {'p', "peers", NULL, - gettext_noop ("peers"), 1, - &GNUNET_GETOPT_set_uint, &peers}, - {'n', "numeric", NULL, - gettext_noop ("numeric output only"), 0, - &GNUNET_GETOPT_set_one, &numeric}, - {'e', "end", NULL, - gettext_noop ("end solving problem"), 1, - &GNUNET_GETOPT_set_uint, &end}, - {'s', "start", NULL, - gettext_noop ("start solving problem"), 1, - &GNUNET_GETOPT_set_uint, &start}, - {'u', "update", NULL, - gettext_noop ("benchmark with existing solution (address updates)"), 1, - &GNUNET_GETOPT_set_uint, &update_percentage}, - GNUNET_GETOPT_OPTION_END - }; - - - GNUNET_PROGRAM_run (argc, argv, - "perf_ats_mlp", "nohelp", options, - &check, NULL); - - - return ret; -} - -/* end of file perf_ats_mlp.c */ diff --git a/src/ats/test_ats_api.conf b/src/ats/test_ats_api.conf index efd7fc9..9e00a15 100644 --- a/src/ats/test_ats_api.conf +++ b/src/ats/test_ats_api.conf @@ -7,13 +7,11 @@ DEFAULTSERVICES = ats UNIXPATH = /tmp/test-ats-scheduling-arm.sock [ats] -#DEBUG = YES -#PREFIX = valgrind --leak-check=full +#PREFIX = valgrind --leak-check=full --track-origins=yes --num-callers=25 AUTOSTART = YES PORT = 12002 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-ats ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -22,8 +20,11 @@ UNIX_MATCH_UID = YES UNIX_MATCH_GID = YES # Enable MLP mode (default: NO) -MLP = NO +MODE = SIMPLISTIC # Network specific inbound/outbound quotas +# UNSPECIFIED +UNSPECIFIED_QUOTA_IN = 64 KiB +UNSPECIFIED_QUOTA_OUT = 64 KiB # LOOPBACK LOOPBACK_QUOTA_IN = unlimited LOOPBACK_QUOTA_OUT = unlimited @@ -34,8 +35,8 @@ LAN_QUOTA_OUT = unlimited WAN_QUOTA_IN = 64 KiB WAN_QUOTA_OUT = 64 KiB # WLAN -WLAN_QUOTA_IN = 1 MiB -WLAN_QUOTA_OUT = 1 MiB +WLAN_QUOTA_IN = 512 +WLAN_QUOTA_OUT = 512 # ATS extended options DUMP_MLP = NO diff --git a/src/ats/test_ats_api_common.c b/src/ats/test_ats_api_common.c new file mode 100644 index 0000000..f1002f8 --- /dev/null +++ b/src/ats/test_ats_api_common.c @@ -0,0 +1,139 @@ +/* + This file is part of GNUnet. + (C) 2010,2011 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ +/** + * @file ats/test_ats_api_common.c + * @brief shared functions for ats test + * @author Christian Grothoff + * @author Matthias Wachs + */ + +#include "test_ats_api_common.h" + +#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 30) + +#define PEERID0 "2AK99KD8RM9UA9LC3QKA0IQ5UBFC0FBB50EBGCFQT8448DGGACNAC4CJQDD1CPFS494O41U88DJD1FLIG8VA5CQR9IN4L96GP104MVO" +#define PEERID1 "5ED7I0AR3MSTAL7FQN04S22E0EQ3CR9RLASCDLVMM1BNFPUPTCT46DLKNJ4DACASJ6U0DR5J8S3R2UJL49682JS7MOVRAB8P8A4PJH0" + +void +create_test_address (struct Test_Address *dest, char * plugin, void *session, void *addr, size_t addrlen) +{ + + dest->plugin = GNUNET_strdup (plugin); + dest->session = session; + if (addrlen > 0) + { + dest->addr = GNUNET_malloc (addrlen); + memcpy (dest->addr, addr, addrlen); + } + else + dest->addr = NULL; + dest->addr_len = addrlen; +} + +void +free_test_address (struct Test_Address *dest) +{ + GNUNET_free (dest->plugin); + if (NULL != dest->addr) + GNUNET_free (dest->addr); +} + +int +compare_addresses (const struct GNUNET_HELLO_Address *address1, void *session1, + const struct GNUNET_HELLO_Address *address2, void *session2) +{ + if (0 != memcmp (&address1->peer, &address2->peer, sizeof (struct GNUNET_PeerIdentity))) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Suggestion with invalid peer id'\n"); + return GNUNET_SYSERR; + } + if (0 != strcmp (address1->transport_name, address2->transport_name)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Suggestion with invalid plugin'\n"); + return GNUNET_SYSERR; + } + if (address1->address_length != address2->address_length) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Suggestion with invalid address length'\n"); + return GNUNET_SYSERR; + + } + else if (0 != memcmp (address1->address, address2->address, address2->address_length)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Suggestion with invalid address'\n"); + return GNUNET_SYSERR; + } + if (session1 != session2) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Suggestion with invalid session1 %p vs session2 %p'\n", + session1, session2); + return GNUNET_SYSERR; + + } + return GNUNET_OK; +} + + +int +compare_ats (const struct GNUNET_ATS_Information *ats_is, uint32_t ats_count_is, + const struct GNUNET_ATS_Information *ats_should, uint32_t ats_count_should) +{ + unsigned int c_o; + unsigned int c_i; + char *prop[] = GNUNET_ATS_PropertyStrings; + uint32_t type1; + uint32_t type2; + uint32_t val1; + uint32_t val2; + int res = GNUNET_OK; + + for (c_o = 0; c_o < ats_count_is; c_o++) + { + for (c_i = 0; c_i < ats_count_should; c_i++) + { + type1 = ntohl(ats_is[c_o].type); + type2 = ntohl(ats_should[c_i].type); + if (type1 == type2) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "ATS type `%s'\n", + prop[type1]); + val1 = ntohl(ats_is[c_o].value); + val2 = ntohl(ats_should[c_i].value); + if (val1 != val2) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "ATS value `%s' not equal: %u != %u\n", + prop[type1], + val1, val2); + res = GNUNET_SYSERR; + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "ATS value `%s' equal: %u == %u\n", + prop[type1], + val1, val2); + } + } + } + } + return res; +} + + +/* end of file test_ats_api_common.c */ diff --git a/src/ats/test_ats_api_common.h b/src/ats/test_ats_api_common.h new file mode 100644 index 0000000..04dd11b --- /dev/null +++ b/src/ats/test_ats_api_common.h @@ -0,0 +1,75 @@ +/* + This file is part of GNUnet. + (C) 2010,2011 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ +/** + * @file ats/test_ats_api_common.h + * @brief shared definitions for ats testcases + * @author Christian Grothoff + * @author Matthias Wachs + */ + +#include "platform.h" +#include "gnunet_common.h" +#include "gnunet_ats_service.h" + +#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 30) + +#define PEERID0 "2AK99KD8RM9UA9LC3QKA0IQ5UBFC0FBB50EBGCFQT8448DGGACNAC4CJQDD1CPFS494O41U88DJD1FLIG8VA5CQR9IN4L96GP104MVO" +#define PEERID1 "5ED7I0AR3MSTAL7FQN04S22E0EQ3CR9RLASCDLVMM1BNFPUPTCT46DLKNJ4DACASJ6U0DR5J8S3R2UJL49682JS7MOVRAB8P8A4PJH0" + +struct Test_Address +{ + char *plugin; + size_t plugin_len; + + void *addr; + size_t addr_len; + + struct GNUNET_ATS_Information *ats; + int ats_count; + + void *session; +}; + +struct PeerContext +{ + struct GNUNET_PeerIdentity id; + + struct Test_Address *addr; + + unsigned long long bw_out_assigned; + + unsigned long long bw_in_assigned; +}; + +void +free_test_address (struct Test_Address *dest); + +void +create_test_address (struct Test_Address *dest, char * plugin, void *session, void *addr, size_t addrlen); + +int +compare_addresses (const struct GNUNET_HELLO_Address *address1, void *session1, + const struct GNUNET_HELLO_Address *address2, void *session2); + +int +compare_ats (const struct GNUNET_ATS_Information *ats_is, uint32_t ats_count_is, + const struct GNUNET_ATS_Information *ats_should, uint32_t ats_count_should); + +/* end of file test_ats_api_common.h */ diff --git a/src/ats/test_ats_api_performance.c b/src/ats/test_ats_api_performance.c new file mode 100644 index 0000000..64737d8 --- /dev/null +++ b/src/ats/test_ats_api_performance.c @@ -0,0 +1,596 @@ +/* + This file is part of GNUnet. + (C) 2010,2011 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ +/** + * @file ats/test_ats_api_performance.c + * @brief test adding addresses in automatic transport selection performance API + * @author Christian Grothoff + * @author Matthias Wachs + */ +#include "platform.h" +#include "gnunet_ats_service.h" +#include "gnunet_testing_lib.h" +#include "ats.h" + +#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 10) + +static GNUNET_SCHEDULER_TaskIdentifier die_task; + +struct GNUNET_CONFIGURATION_Handle *cfg; + +static struct GNUNET_ATS_SchedulingHandle *atsh; +static struct GNUNET_ATS_PerformanceHandle *ph; +struct GNUNET_ATS_AddressListHandle* phal; + +static int ret; + +struct Address +{ + char *plugin; + size_t plugin_len; + + void *addr; + size_t addr_len; + + struct GNUNET_ATS_Information *ats; + int ats_count; + + void *session; +}; + +struct PeerContext +{ + struct GNUNET_PeerIdentity id; + + struct Address *addr; +}; + + + +static struct PeerContext p[2]; + +static struct Address p0_addresses[2]; +static struct Address p1_addresses[2]; + +struct GNUNET_HELLO_Address p0_ha[2]; +struct GNUNET_HELLO_Address p1_ha[2]; +struct GNUNET_HELLO_Address *s_ha[2]; + +static unsigned int stage = 0; + +static void +end_badly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + die_task = GNUNET_SCHEDULER_NO_TASK; + + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Timeout in stage %u\n", stage); + + if (NULL != atsh) + GNUNET_ATS_scheduling_done (atsh); + if (phal != NULL) + GNUNET_ATS_performance_list_addresses_cancel (phal); + phal = NULL; + if (ph != NULL) + GNUNET_ATS_performance_done (ph); + ph = NULL; + + GNUNET_free_non_null (p0_addresses[0].addr); + GNUNET_free_non_null (p0_addresses[1].addr); + GNUNET_free_non_null (p1_addresses[0].addr); + GNUNET_free_non_null (p1_addresses[1].addr); + + ret = GNUNET_SYSERR; +} + + +static void +end () +{ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Shutting down\n"); + if (die_task != GNUNET_SCHEDULER_NO_TASK) + { + GNUNET_SCHEDULER_cancel (die_task); + die_task = GNUNET_SCHEDULER_NO_TASK; + } + if (NULL != atsh) + GNUNET_ATS_scheduling_done (atsh); + if (phal != NULL) + GNUNET_ATS_performance_list_addresses_cancel (phal); + phal = NULL; + if (ph != NULL) + GNUNET_ATS_performance_done (ph); + ph = NULL; + + GNUNET_free_non_null (p0_addresses[0].addr); + GNUNET_free_non_null (p0_addresses[1].addr); + GNUNET_free_non_null (p1_addresses[0].addr); + GNUNET_free_non_null (p1_addresses[1].addr); + + ret = 0; +} + +static void +test_performance_api (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc); + +void all_active_addresses_peer_cb (void *cls, + const struct + GNUNET_HELLO_Address * + address, + struct + GNUNET_BANDWIDTH_Value32NBO + bandwidth_out, + struct + GNUNET_BANDWIDTH_Value32NBO + bandwidth_in, + const struct + GNUNET_ATS_Information * + ats, uint32_t ats_count) +{ + static int cb = 0; + int fail = GNUNET_NO; + + if (address != NULL) + { + if (0 == memcmp (&address->peer, &p[0].id, + sizeof (struct GNUNET_PeerIdentity))) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Did not expected callback for peer 0 address `%s', got address `%s'!\n", + s_ha[0]->address, address->address); + GNUNET_ATS_performance_list_addresses_cancel (phal); + fail = GNUNET_YES; + } + + if (0 == memcmp (&address->peer, &p[1].id, + sizeof (struct GNUNET_PeerIdentity))) + { + if (0 == strcmp(address->address, s_ha[1]->address)) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Callback for peer 1 suggested address %s\n", + s_ha[1]->address); + cb ++; + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Expected callback for peer 1 address `%s', got address `%s'!\n", + s_ha[1]->address, address->address); + GNUNET_ATS_performance_list_addresses_cancel (phal); + fail = GNUNET_YES; + } + } + } + if ((address == NULL) || (GNUNET_YES == fail)) + { + phal = NULL; + if ((1 == cb) && (GNUNET_NO == fail)) + { + /* Received all addresses + terminator cb, next stage */ + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Stage %i: SUCCESS\n", stage); + GNUNET_SCHEDULER_add_now (&test_performance_api, NULL); + return; + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Stage %i: FAIL\n", stage); + GNUNET_SCHEDULER_add_now (&end, NULL); + ret = 5; + return; + } + } +} + +void all_active_addresses_cb (void *cls, + const struct + GNUNET_HELLO_Address * + address, + struct + GNUNET_BANDWIDTH_Value32NBO + bandwidth_out, + struct + GNUNET_BANDWIDTH_Value32NBO + bandwidth_in, + const struct + GNUNET_ATS_Information * + ats, uint32_t ats_count) +{ + static int cb = 0; + int fail = GNUNET_NO; + + if (address != NULL) + { + if (0 == memcmp (&address->peer, &p[0].id, + sizeof (struct GNUNET_PeerIdentity))) + { + if (0 == strcmp(address->address, s_ha[0]->address)) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Callback for peer 0 suggested address %s\n", + s_ha[0]->address); + cb ++; + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Expected callback for peer 0 address `%s', got address `%s'!\n", + s_ha[0]->address, address->address); + GNUNET_ATS_performance_list_addresses_cancel (phal); + fail = GNUNET_YES; + } + } + + if (0 == memcmp (&address->peer, &p[1].id, + sizeof (struct GNUNET_PeerIdentity))) + { + if (0 == strcmp(address->address, s_ha[1]->address)) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Callback for peer 1 suggested address %s\n", + s_ha[1]->address); + cb ++; + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Expected callback for peer 1 address `%s', got address `%s'!\n", + s_ha[1]->address, address->address); + GNUNET_ATS_performance_list_addresses_cancel (phal); + fail = GNUNET_YES; + } + } + } + if ((address == NULL) || (GNUNET_YES == fail)) + { + phal = NULL; + if ((2 == cb) && (GNUNET_NO == fail)) + { + /* Received all addresses + terminator cb, next stage */ + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Stage %i: SUCCESS\n", stage); + GNUNET_SCHEDULER_add_now (&test_performance_api, NULL); + return; + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Stage %i: FAIL\n", stage); + GNUNET_SCHEDULER_add_now (&end, NULL); + ret = 5; + return; + } + } +} + + + +void all_addresses_peer_cb (void *cls, + const struct + GNUNET_HELLO_Address * + address, + struct + GNUNET_BANDWIDTH_Value32NBO + bandwidth_out, + struct + GNUNET_BANDWIDTH_Value32NBO + bandwidth_in, + const struct + GNUNET_ATS_Information * + ats, uint32_t ats_count) +{ + static int cb = 0; + int fail = GNUNET_NO; + + if (address != NULL) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Callback for peer `%s' address `%s'\n", + GNUNET_i2s (&address->peer), address->address); + + if (0 != memcmp (&address->peer, &p[1].id, + sizeof (struct GNUNET_PeerIdentity))) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Stage %i: Received address for wrong peer\n", stage); + GNUNET_ATS_performance_list_addresses_cancel (phal); + fail = GNUNET_YES; + ret = 4; + } + cb ++; + } + + if ((NULL == address) || (fail)) + { + phal = NULL; + if ((2 == cb) && (GNUNET_NO == fail)) + { + /* Received all addresses + terminator cb, next stage */ + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Stage %i: SUCCESS\n", stage); + GNUNET_SCHEDULER_add_now (&test_performance_api, NULL); + return; + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Stage %i: FAIL\n", stage); + GNUNET_SCHEDULER_add_now (&end, NULL); + ret = 5; + return; + } + } +} + +void all_addresses_cb (void *cls, + const struct + GNUNET_HELLO_Address * + address, + struct + GNUNET_BANDWIDTH_Value32NBO + bandwidth_out, + struct + GNUNET_BANDWIDTH_Value32NBO + bandwidth_in, + const struct + GNUNET_ATS_Information * + ats, uint32_t ats_count) +{ + static int cb = 0; + + if (address != NULL) + { + if (0 == memcmp (&address->peer, &p[0].id, + sizeof (struct GNUNET_PeerIdentity))) + { + if (0 == strcmp(address->address, p0_addresses[0].addr)) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Callback for peer 0 address 0\n"); + cb |= 1; + } + if (0 == strcmp(address->address, p0_addresses[1].addr)) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Callback for peer 0 address 1\n"); + cb |= 2; + } + } + if (0 == memcmp (&address->peer, &p[1].id, + sizeof (struct GNUNET_PeerIdentity))) + { + if (0 == strcmp(address->address, p1_addresses[0].addr)) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Callback for peer 1 address 0\n"); + cb |= 4; + } + if (0 == strcmp(address->address, p1_addresses[1].addr)) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Callback for peer 1 address 1\n"); + cb |= 8; + } + } + } + else + { + phal = NULL; + if (((1 << 4) - 1) == cb) + { + /* Received all addresses + terminator cb, next stage */ + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Stage %i: SUCCESS\n", stage); + GNUNET_SCHEDULER_add_now (&test_performance_api, NULL); + return; + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Stage %i: FAIL\n", stage); + GNUNET_SCHEDULER_add_now (&end, NULL); + ret = 3; + return; + } + } +} + +static void +test_performance_api (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + if (NULL == ph) + ph = GNUNET_ATS_performance_init (cfg, NULL, NULL); + if (NULL == ph) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Failed to initialize performance handle\n"); + ret = 2; + } + stage++; + switch (stage) { + case 1: /* Get all peers, all addresses */ + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Run stage 1: \n"); + phal = GNUNET_ATS_performance_list_addresses (ph, + NULL, + GNUNET_YES, + &all_addresses_cb, NULL); + GNUNET_assert (NULL != phal); + break; + case 2: /* Get specific peer, all addresses */ + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Run stage 2: \n"); + phal = GNUNET_ATS_performance_list_addresses (ph, + &p[1].id, + GNUNET_YES, + &all_addresses_peer_cb, NULL); + GNUNET_assert (NULL != phal); + break; + case 3: /* Get all peers, active addresses */ + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Run stage 3: \n"); + phal = GNUNET_ATS_performance_list_addresses (ph, + NULL, + GNUNET_NO, + &all_active_addresses_cb, NULL); + GNUNET_assert (NULL != phal); + break; + case 4: /* Get specific peers, active addresses */ + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Run stage 4: \n"); + phal = GNUNET_ATS_performance_list_addresses (ph, + &p[1].id, + GNUNET_NO, + &all_active_addresses_peer_cb, NULL); + GNUNET_assert (NULL != phal); + break; + default: + /* done */ + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "All tests successful, shutdown... \n"); + GNUNET_SCHEDULER_add_now (&end, NULL); + return; + } +} + + +static void +address_suggest_cb (void *cls, const struct GNUNET_HELLO_Address *address, + struct Session *session, + struct GNUNET_BANDWIDTH_Value32NBO bandwidth_out, + struct GNUNET_BANDWIDTH_Value32NBO bandwidth_in, + const struct GNUNET_ATS_Information *ats, + uint32_t ats_count) +{ + static int suggest_p0 = GNUNET_NO; + static int suggest_p1 = GNUNET_NO; + static int running = GNUNET_NO; + + if ((GNUNET_NO == suggest_p0) && (0 == memcmp (&address->peer, &p[0].id, + sizeof (struct GNUNET_PeerIdentity)))) + { + suggest_p0 = GNUNET_YES;; + + if (s_ha[0] != NULL) + GNUNET_free (s_ha[0]); + s_ha[0] = GNUNET_HELLO_address_copy (address); + GNUNET_ATS_suggest_address_cancel (atsh, &p[0].id); + } + if ((GNUNET_NO == suggest_p1) && (0 == memcmp (&address->peer, &p[1].id, + sizeof (struct GNUNET_PeerIdentity)))) + { + suggest_p1 = GNUNET_YES; + + if (s_ha[1] != NULL) + GNUNET_free (s_ha[1]); + s_ha[1] = GNUNET_HELLO_address_copy (address); + GNUNET_ATS_suggest_address_cancel (atsh, &p[1].id); + } + + + if ((GNUNET_NO == running) && (GNUNET_YES == suggest_p0) && (GNUNET_YES == suggest_p1)) + { + running = GNUNET_YES; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Have address suggestion for both peers\n"); + GNUNET_SCHEDULER_add_now (&test_performance_api, NULL); + } + +} + + +static void +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *mycfg, + struct GNUNET_TESTING_Peer *peer) +{ + ret = 1; + cfg = (struct GNUNET_CONFIGURATION_Handle *) mycfg; + die_task = GNUNET_SCHEDULER_add_delayed (TIMEOUT, &end_badly, NULL); + + + /* set up peer 0 */ + GNUNET_CRYPTO_hash_create_random (GNUNET_CRYPTO_QUALITY_WEAK, + &p[0].id.hashPubKey); + + p0_addresses[0].plugin = "test"; + p0_addresses[0].session = NULL; + p0_addresses[0].addr = GNUNET_strdup ("test_p0_a0"); + p0_addresses[0].addr_len = strlen (p0_addresses[0].addr) + 1; + + p0_ha[0].address = p0_addresses[0].addr; + p0_ha[0].address_length = p0_addresses[0].addr_len; + p0_ha[0].peer = p[0].id; + p0_ha[0].transport_name = p0_addresses[0].plugin; + + p0_addresses[1].plugin = "test"; + p0_addresses[1].session = NULL; + p0_addresses[1].addr = GNUNET_strdup ("test_p0_a1"); + p0_addresses[1].addr_len = strlen(p0_addresses[1].addr) + 1; + + p0_ha[1].address = p0_addresses[1].addr; + p0_ha[1].address_length = p0_addresses[1].addr_len; + p0_ha[1].peer = p[0].id; + p0_ha[1].transport_name = p0_addresses[1].plugin; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Created peer 0: `%s'\n", + GNUNET_i2s (&p[0].id)); + + GNUNET_CRYPTO_hash_create_random (GNUNET_CRYPTO_QUALITY_WEAK, + &p[1].id.hashPubKey); + + p1_addresses[0].plugin = "test"; + p1_addresses[0].session = NULL; + p1_addresses[0].addr = GNUNET_strdup ("test_p1_a0"); + p1_addresses[0].addr_len = strlen(p1_addresses[0].addr) + 1; + + p1_ha[0].address = p1_addresses[0].addr; + p1_ha[0].address_length = p1_addresses[0].addr_len; + p1_ha[0].peer = p[1].id; + p1_ha[0].transport_name = p1_addresses[0].plugin; + + p1_addresses[1].plugin = "test"; + p1_addresses[1].session = NULL; + p1_addresses[1].addr = GNUNET_strdup ("test_p1_a1"); + p1_addresses[1].addr_len = strlen(p1_addresses[1].addr) + 1; + + p1_ha[1].address = p1_addresses[1].addr; + p1_ha[1].address_length = p1_addresses[1].addr_len; + p1_ha[1].peer = p[1].id; + p1_ha[1].transport_name = p1_addresses[1].plugin; + + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Created peer 1: `%s'\n", + GNUNET_i2s (&p[1].id)); + + + /* Add addresses */ + atsh = GNUNET_ATS_scheduling_init (cfg, &address_suggest_cb, NULL); + if (atsh == NULL) + { + ret = GNUNET_SYSERR; + end (); + return; + } + + GNUNET_ATS_address_add (atsh, &p0_ha[0], NULL, NULL, 0); + GNUNET_ATS_address_add (atsh, &p0_ha[1], NULL, NULL, 0); + + GNUNET_ATS_address_add (atsh, &p1_ha[0], NULL, NULL, 0); + GNUNET_ATS_address_add (atsh, &p1_ha[1], NULL, NULL, 0); + + + GNUNET_ATS_suggest_address (atsh, &p[0].id); + GNUNET_ATS_suggest_address (atsh, &p[1].id); +} + + +int +main (int argc, char *argv[]) +{ + if (0 != GNUNET_TESTING_peer_run ("test_ats_api_performance", + "test_ats_api.conf", + &run, NULL)) + return 1; + return ret; +} + +/* end of file test_ats_api_performance.c */ diff --git a/src/ats/test_ats_api_reset_backoff.c b/src/ats/test_ats_api_reset_backoff.c deleted file mode 100644 index 38c18e1..0000000 --- a/src/ats/test_ats_api_reset_backoff.c +++ /dev/null @@ -1,308 +0,0 @@ -/* - This file is part of GNUnet. - (C) 2010,2011 Christian Grothoff (and other contributing authors) - - GNUnet is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published - by the Free Software Foundation; either version 3, or (at your - option) any later version. - - GNUnet is distributed in the hope that it will be useful, but - WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - General Public License for more details. - - You should have received a copy of the GNU General Public License - along with GNUnet; see the file COPYING. If not, write to the - Free Software Foundation, Inc., 59 Temple Place - Suite 330, - Boston, MA 02111-1307, USA. -*/ -/** - * @file ats/test_ats_api_reset_backoff.c - * @brief test case for block reset api - * @author Christian Grothoff - * @author Matthias Wachs - */ -#include "platform.h" -#include "gnunet_ats_service.h" -#include "ats.h" - -#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 10) -#define ATS_TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MILLISECONDS, 90) - -static GNUNET_SCHEDULER_TaskIdentifier die_task; - -static GNUNET_SCHEDULER_TaskIdentifier suggest_timeout_task; - -static struct GNUNET_ATS_SchedulingHandle *ats; - -struct GNUNET_OS_Process *arm_proc; - -static int ret; - -struct Address -{ - char *plugin; - size_t plugin_len; - - void *addr; - size_t addr_len; - - struct GNUNET_ATS_Information *ats; - int ats_count; - - void *session; -}; - -struct PeerContext -{ - struct GNUNET_PeerIdentity id; - - struct Address *addr; -}; - -struct GNUNET_HELLO_Address hello_addr; -struct Address address; -struct PeerContext peer; -struct GNUNET_ATS_Information atsi[2]; - -static void -stop_arm () -{ - if (0 != GNUNET_OS_process_kill (arm_proc, SIGTERM)) - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); - GNUNET_OS_process_wait (arm_proc); - GNUNET_OS_process_destroy (arm_proc); - arm_proc = NULL; -} - - -static void -end_badly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - die_task = GNUNET_SCHEDULER_NO_TASK; - - if (suggest_timeout_task != GNUNET_SCHEDULER_NO_TASK) - { - GNUNET_SCHEDULER_cancel (suggest_timeout_task); - suggest_timeout_task = GNUNET_SCHEDULER_NO_TASK; - } - - if (ats != NULL) - { - GNUNET_ATS_scheduling_done (ats); - ats = NULL; - } - - ret = GNUNET_SYSERR; - - stop_arm (); -} - - -static void -end () -{ - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Shutting down\n"); - if (die_task != GNUNET_SCHEDULER_NO_TASK) - { - GNUNET_SCHEDULER_cancel (die_task); - die_task = GNUNET_SCHEDULER_NO_TASK; - } - - if (suggest_timeout_task != GNUNET_SCHEDULER_NO_TASK) - { - GNUNET_SCHEDULER_cancel (suggest_timeout_task); - suggest_timeout_task = GNUNET_SCHEDULER_NO_TASK; - } - - GNUNET_ATS_scheduling_done (ats); - - ret = 0; - - stop_arm (); -} - - -static void -suggest_timeout (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - suggest_timeout_task = GNUNET_SCHEDULER_NO_TASK; - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Requesting address for peer timed out\n"); - - if (die_task != GNUNET_SCHEDULER_NO_TASK) - { - GNUNET_SCHEDULER_cancel (die_task); - die_task = GNUNET_SCHEDULER_NO_TASK; - } - - die_task = GNUNET_SCHEDULER_add_now (&end_badly, NULL); -} - -static void -address_suggest_cb (void *cls, const struct GNUNET_HELLO_Address *a, - struct Session *session, - struct GNUNET_BANDWIDTH_Value32NBO bandwidth_out, - struct GNUNET_BANDWIDTH_Value32NBO bandwidth_in, - const struct GNUNET_ATS_Information *atsi, - uint32_t ats_count) -{ - static int suggestions; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "ATS suggests address `%s'\n", - GNUNET_i2s (&a->peer)); - - if (0 != memcmp (&a->peer, &peer.id, - sizeof (struct GNUNET_PeerIdentity))) - { - GNUNET_break (0); - if (die_task != GNUNET_SCHEDULER_NO_TASK) - { - GNUNET_SCHEDULER_cancel (die_task); - die_task = GNUNET_SCHEDULER_NO_TASK; - } - GNUNET_SCHEDULER_add_now (&end_badly, NULL); - return; - } - - if (0 != strcmp (a->transport_name, address.plugin)) - { - GNUNET_break (0); - if (die_task != GNUNET_SCHEDULER_NO_TASK) - { - GNUNET_SCHEDULER_cancel (die_task); - die_task = GNUNET_SCHEDULER_NO_TASK; - } - GNUNET_SCHEDULER_add_now (&end_badly, NULL); - return; - } - - if (a->address_length != address.addr_len) - { - GNUNET_break (0); - if (die_task != GNUNET_SCHEDULER_NO_TASK) - { - GNUNET_SCHEDULER_cancel (die_task); - die_task = GNUNET_SCHEDULER_NO_TASK; - } - GNUNET_SCHEDULER_add_now (&end_badly, NULL); - return; - } - - if (0 != memcmp (a->address, address.addr, - a->address_length)) - { - GNUNET_break (0); - if (die_task != GNUNET_SCHEDULER_NO_TASK) - { - GNUNET_SCHEDULER_cancel (die_task); - die_task = GNUNET_SCHEDULER_NO_TASK; - } - GNUNET_SCHEDULER_add_now (&end_badly, NULL); - return; - } - - if (session != address.session) - { - GNUNET_break (0); - if (die_task != GNUNET_SCHEDULER_NO_TASK) - { - GNUNET_SCHEDULER_cancel (die_task); - die_task = GNUNET_SCHEDULER_NO_TASK; - } - GNUNET_SCHEDULER_add_now (&end_badly, NULL); - return; - } - - suggestions ++; - - if (2 == suggestions) - { - GNUNET_SCHEDULER_add_now(&end, NULL); - return; - } - - if (suggest_timeout_task != GNUNET_SCHEDULER_NO_TASK) - { - GNUNET_SCHEDULER_cancel (suggest_timeout_task); - suggest_timeout_task = GNUNET_SCHEDULER_NO_TASK; - } - suggest_timeout_task = GNUNET_SCHEDULER_add_delayed(ATS_TIMEOUT, &suggest_timeout, NULL); -} - -void -start_arm (const char *cfgname) -{ - arm_proc = - GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-arm", - "gnunet-service-arm", - "-c", cfgname, NULL); -} - -static void -check (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) -{ - ret = GNUNET_SYSERR; - - die_task = GNUNET_SCHEDULER_add_delayed (TIMEOUT, &end_badly, NULL); - start_arm (cfgfile); - - ats = GNUNET_ATS_scheduling_init (cfg, &address_suggest_cb, NULL); - - if (ats == NULL) - { - ret = GNUNET_SYSERR; - end (); - return; - } - - /* set up peer */ - GNUNET_CRYPTO_hash_create_random (GNUNET_CRYPTO_QUALITY_WEAK, - &peer.id.hashPubKey); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Created peer `%s'\n", GNUNET_i2s (&peer.id)); - - address.plugin = "test"; - address.session = NULL; - address.addr = GNUNET_strdup ("test"); - address.addr_len = 4; - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Adding address\n"); - - hello_addr.peer = peer.id; - hello_addr.transport_name = address.plugin; - hello_addr.address = address.addr; - hello_addr.address_length = address.addr_len; - GNUNET_ATS_address_update (ats, &hello_addr, address.session, NULL, 0); - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Requesting address for peer `%s'\n", - GNUNET_i2s (&peer.id)); - /* Increase block timout far beyond ATS_TIMEOUT */ - GNUNET_ATS_suggest_address (ats, &peer.id); - - GNUNET_ATS_reset_backoff(ats, &peer.id); - GNUNET_ATS_suggest_address (ats, &peer.id); -} - -int -main (int argc, char *argv[]) -{ - static char *const argv2[] = { "test_ats_api_scheduling", - "-c", - "test_ats_api.conf", - "-L", "WARNING", - NULL - }; - - static struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - - GNUNET_PROGRAM_run ((sizeof (argv2) / sizeof (char *)) - 1, argv2, - "test_ats_api_scheduling", "nohelp", options, &check, - NULL); - - - return ret; -} -/* end of file test_ats_api_reset_backoff.c */ diff --git a/src/ats/test_ats_api_scheduling.c b/src/ats/test_ats_api_scheduling.c deleted file mode 100644 index c9d2206..0000000 --- a/src/ats/test_ats_api_scheduling.c +++ /dev/null @@ -1,253 +0,0 @@ -/* - This file is part of GNUnet. - (C) 2010,2011 Christian Grothoff (and other contributing authors) - - GNUnet is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published - by the Free Software Foundation; either version 3, or (at your - option) any later version. - - GNUnet is distributed in the hope that it will be useful, but - WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - General Public License for more details. - - You should have received a copy of the GNU General Public License - along with GNUnet; see the file COPYING. If not, write to the - Free Software Foundation, Inc., 59 Temple Place - Suite 330, - Boston, MA 02111-1307, USA. -*/ -/** - * @file ats/test_ats_api_scheduling.c - * @brief test automatic transport selection scheduling API - * @author Christian Grothoff - * @author Matthias Wachs - * - * TODO: - * - write test case - * - extend API to get performance data - * - implement simplistic strategy based on say 'lowest latency' or strict ordering - * - extend API to get peer preferences, implement proportional bandwidth assignment - * - re-implement API against a real ATS service (!) - */ -#include "platform.h" -#include "gnunet_ats_service.h" -#include "ats.h" - -#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 10) - -static GNUNET_SCHEDULER_TaskIdentifier die_task; - -static struct GNUNET_ATS_SchedulingHandle *ats; - -struct GNUNET_OS_Process *arm_proc; - - - -static int ret; - -struct Address -{ - char *plugin; - size_t plugin_len; - - void *addr; - size_t addr_len; - - struct GNUNET_ATS_Information *ats; - int ats_count; - - void *session; -}; - -struct PeerContext -{ - struct GNUNET_PeerIdentity id; - - struct Address *addr; -}; - -struct Address addr[2]; -struct PeerContext p[2]; -struct GNUNET_ATS_Information atsi[2]; - -static void -stop_arm () -{ - if (0 != GNUNET_OS_process_kill (arm_proc, SIGTERM)) - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); - GNUNET_OS_process_wait (arm_proc); - GNUNET_OS_process_destroy (arm_proc); - arm_proc = NULL; -} - - -static void -end_badly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - die_task = GNUNET_SCHEDULER_NO_TASK; - if (ats != NULL) - GNUNET_ATS_scheduling_done (ats); - - ret = GNUNET_SYSERR; - - stop_arm (); -} - - -static void -end () -{ - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Shutting down\n"); - if (die_task != GNUNET_SCHEDULER_NO_TASK) - { - GNUNET_SCHEDULER_cancel (die_task); - die_task = GNUNET_SCHEDULER_NO_TASK; - } - - GNUNET_ATS_scheduling_done (ats); - - ret = 0; - - stop_arm (); -} - - -static void -address_suggest_cb (void *cls, const struct GNUNET_HELLO_Address *address, - struct Session *session, - struct GNUNET_BANDWIDTH_Value32NBO bandwidth_out, - struct GNUNET_BANDWIDTH_Value32NBO bandwidth_in, - const struct GNUNET_ATS_Information *ats, - uint32_t ats_count) -{ - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "ATS suggests address `%s'\n", - GNUNET_i2s (&address->peer)); - - GNUNET_assert (0 == - memcmp (&address->peer, &p[0].id, - sizeof (struct GNUNET_PeerIdentity))); - GNUNET_assert (0 == strcmp (address->transport_name, addr[0].plugin)); - GNUNET_assert (address->address_length == addr[0].addr_len); - GNUNET_assert (0 == - memcmp (address->address, addr[0].plugin, - address->address_length)); - GNUNET_assert (addr[0].session == session); - - - /* TODO ats merge - * GNUNET_assert (ats_count == 2); - * GNUNET_assert (atsi[0].type == htons (1)); - * GNUNET_assert (atsi[0].type == htons (2)); - * GNUNET_assert (atsi[1].type == htons (2)); - * GNUNET_assert (atsi[1].type == htons (2)); - */ - - ret = 0; - - GNUNET_SCHEDULER_add_now (&end, NULL); -} - -void -start_arm (const char *cfgname) -{ - arm_proc = - GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-arm", - "gnunet-service-arm", - "-c", cfgname, NULL); -} - -static void -check (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) -{ - struct GNUNET_HELLO_Address address0; - - ret = GNUNET_SYSERR; - - die_task = GNUNET_SCHEDULER_add_delayed (TIMEOUT, &end_badly, NULL); - start_arm (cfgfile); - - ats = GNUNET_ATS_scheduling_init (cfg, &address_suggest_cb, NULL); - - if (ats == NULL) - { - ret = GNUNET_SYSERR; - end (); - return; - } - - /* set up peer */ - GNUNET_CRYPTO_hash_create_random (GNUNET_CRYPTO_QUALITY_WEAK, - &p[0].id.hashPubKey); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Created peer `%s'\n", - GNUNET_i2s (&p[0].id)); - - GNUNET_CRYPTO_hash_create_random (GNUNET_CRYPTO_QUALITY_WEAK, - &p[1].id.hashPubKey); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Created peer `%s'\n", - GNUNET_i2s (&p[1].id)); - - addr[0].plugin = "test"; - addr[0].session = NULL; - addr[0].addr = GNUNET_strdup ("test"); - addr[0].addr_len = 4; - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Testing address creation\n"); - - address0.peer = p[0].id; - address0.transport_name = addr[0].plugin; - address0.address = addr[0].addr; - address0.address_length = addr[0].addr_len; - GNUNET_ATS_address_update (ats, &address0, addr[0].session, NULL, 0); - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Testing ATS info creation\n"); - - atsi[0].type = htonl (GNUNET_ATS_UTILIZATION_UP); - atsi[0].value = htonl (1024); - - GNUNET_ATS_address_update (ats, &address0, addr[0].session, atsi, 1); - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Testing ATS info update\n"); - - atsi[0].type = htonl (GNUNET_ATS_UTILIZATION_UP); - atsi[0].value = htonl (2048); - - atsi[1].type = htonl (GNUNET_ATS_UTILIZATION_DOWN); - atsi[1].value = htonl (1024); - - GNUNET_ATS_address_update (ats, &address0, addr[0].session, atsi, 2); - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Testing manual address deletion \n"); - address0.peer = p[1].id; // FIXME: why? typo in old code? - GNUNET_ATS_address_update (ats, &address0, addr[0].session, NULL, 0); - GNUNET_ATS_address_destroyed (ats, &address0, addr[0].session); - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Requesting peer `%s'\n", - GNUNET_i2s (&p[0].id)); - GNUNET_ATS_suggest_address (ats, &p[0].id); -} - -int -main (int argc, char *argv[]) -{ - static char *const argv2[] = { "test_ats_api_scheduling", - "-c", - "test_ats_api.conf", - "-L", "WARNING", - NULL - }; - - static struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - - GNUNET_PROGRAM_run ((sizeof (argv2) / sizeof (char *)) - 1, argv2, - "test_ats_api_scheduling", "nohelp", options, &check, - NULL); - - - return ret; -} - -/* end of file test_ats_api_scheduling.c */ diff --git a/src/ats/test_ats_api_scheduling_add_address.c b/src/ats/test_ats_api_scheduling_add_address.c new file mode 100644 index 0000000..f7ee195 --- /dev/null +++ b/src/ats/test_ats_api_scheduling_add_address.c @@ -0,0 +1,199 @@ +/* + This file is part of GNUnet. + (C) 2010,2011 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ +/** + * @file ats/test_ats_api_scheduling_add_address.c + * @brief test adding addresses in automatic transport selection scheduling API + * @author Christian Grothoff + * @author Matthias Wachs + */ +#include "platform.h" +#include "gnunet_ats_service.h" +#include "gnunet_testing_lib.h" +#include "ats.h" +#include "test_ats_api_common.h" + +static GNUNET_SCHEDULER_TaskIdentifier die_task; + +/** + * Scheduling handle + */ +static struct GNUNET_ATS_SchedulingHandle *sched_ats; + +/** + * Return value + */ +static int ret; + +/** + * Test address + */ +static struct Test_Address test_addr; + +/** + * Test peer + */ +static struct PeerContext p; + +/** + * HELLO address + */ +struct GNUNET_HELLO_Address test_hello_address; + +/** + * Session + */ +static void *test_session; + +/** + * Test ats info + */ +struct GNUNET_ATS_Information test_ats_info[2]; + +/** + * Test ats count + */ +uint32_t test_ats_count; + + +static void +end_badly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + die_task = GNUNET_SCHEDULER_NO_TASK; + + if (sched_ats != NULL) + GNUNET_ATS_scheduling_done (sched_ats); + free_test_address (&test_addr); + ret = GNUNET_SYSERR; +} + + +static void +end () +{ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Shutting down\n"); + if (die_task != GNUNET_SCHEDULER_NO_TASK) + { + GNUNET_SCHEDULER_cancel (die_task); + die_task = GNUNET_SCHEDULER_NO_TASK; + } + if (NULL != sched_ats) + GNUNET_ATS_scheduling_done (sched_ats); + sched_ats = NULL; + free_test_address (&test_addr); +} + +static void +address_suggest_cb (void *cls, const struct GNUNET_HELLO_Address *address, + struct Session *session, + struct GNUNET_BANDWIDTH_Value32NBO bandwidth_out, + struct GNUNET_BANDWIDTH_Value32NBO bandwidth_in, + const struct GNUNET_ATS_Information *atsi, + uint32_t ats_count) +{ + static int stage = 0; + if (0 == stage) + { + if (GNUNET_OK == compare_addresses (address, session, &test_hello_address, test_session)) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stage 0: Callback with correct address `%s'\n", + GNUNET_i2s (&address->peer)); + ret = 0; + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stage 0: Callback with invalid address `%s'\n", + GNUNET_i2s (&address->peer)); + ret = 1; + } + + if (GNUNET_OK != compare_ats(atsi, ats_count, test_ats_info, test_ats_count)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Stage 0: Callback with incorrect ats info \n"); + ret = 1; + } + stage ++; + GNUNET_ATS_suggest_address_cancel (sched_ats, &p.id); + GNUNET_SCHEDULER_add_now (&end, NULL); + } +} + +static void +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) +{ + + die_task = GNUNET_SCHEDULER_add_delayed (TIMEOUT, &end_badly, NULL); + + /* Connect to ATS scheduling */ + sched_ats = GNUNET_ATS_scheduling_init (cfg, &address_suggest_cb, NULL); + if (sched_ats == NULL) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Could not connect to ATS scheduling!\n"); + ret = 1; + end (); + return; + } + + /* Set up peer */ + if (GNUNET_SYSERR == GNUNET_CRYPTO_hash_from_string(PEERID0, &p.id.hashPubKey)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Could not setup peer!\n"); + ret = GNUNET_SYSERR; + end (); + return; + } + + GNUNET_assert (0 == strcmp (PEERID0, GNUNET_i2s_full (&p.id))); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Created peer `%s'\n", + GNUNET_i2s_full(&p.id)); + + /* Prepare ATS Information */ + test_ats_info[0].type = htonl (GNUNET_ATS_NETWORK_TYPE); + test_ats_info[0].value = htonl(GNUNET_ATS_NET_WAN); + test_ats_info[1].type = htonl (GNUNET_ATS_QUALITY_NET_DISTANCE); + test_ats_info[1].value = htonl(1); + test_ats_count = 2; + + /* Adding address without session */ + test_session = NULL; + create_test_address (&test_addr, "test", test_session, "test", strlen ("test") + 1); + test_hello_address.peer = p.id; + test_hello_address.transport_name = test_addr.plugin; + test_hello_address.address = test_addr.addr; + test_hello_address.address_length = test_addr.addr_len; + GNUNET_ATS_address_add (sched_ats, &test_hello_address, test_session, test_ats_info, test_ats_count); + + GNUNET_ATS_suggest_address (sched_ats, &p.id); +} + + +int +main (int argc, char *argv[]) +{ + if (0 != GNUNET_TESTING_peer_run ("test_ats_api_scheduling_add_address", + "test_ats_api.conf", + &run, NULL)) + return 1; + return ret; +} + +/* end of file test_ats_api_scheduling_add_address.c */ diff --git a/src/ats/test_ats_api_scheduling_add_session.c b/src/ats/test_ats_api_scheduling_add_session.c new file mode 100644 index 0000000..9394484 --- /dev/null +++ b/src/ats/test_ats_api_scheduling_add_session.c @@ -0,0 +1,237 @@ +/* + This file is part of GNUnet. + (C) 2010,2011 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ +/** + * @file ats/test_ats_api_scheduling_add_session.c + * @brief test adding a session to an existing addresses + * @author Christian Grothoff + * @author Matthias Wachs + */ +#include "platform.h" +#include "gnunet_ats_service.h" +#include "gnunet_testing_lib.h" +#include "ats.h" +#include "test_ats_api_common.h" + +static GNUNET_SCHEDULER_TaskIdentifier die_task; + +/** + * Scheduling handle + */ +static struct GNUNET_ATS_SchedulingHandle *sched_ats; + +/** + * Return value + */ +static int ret; + +/** + * Test address + */ +static struct Test_Address test_addr; + +/** + * Test peer + */ +static struct PeerContext p; + +/** + * HELLO address + */ +struct GNUNET_HELLO_Address test_hello_address; + +/** + * Session + */ +static void *test_session; + +/** + * Test ats info + */ +struct GNUNET_ATS_Information test_ats_info[2]; + +/** + * Test ats count + */ +uint32_t test_ats_count; + + +static void +end_badly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + die_task = GNUNET_SCHEDULER_NO_TASK; + + if (sched_ats != NULL) + GNUNET_ATS_scheduling_done (sched_ats); + free_test_address (&test_addr); + ret = GNUNET_SYSERR; +} + + +static void +end () +{ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Shutting down\n"); + if (die_task != GNUNET_SCHEDULER_NO_TASK) + { + GNUNET_SCHEDULER_cancel (die_task); + die_task = GNUNET_SCHEDULER_NO_TASK; + } + if (NULL != sched_ats) + GNUNET_ATS_scheduling_done (sched_ats); + sched_ats = NULL; + free_test_address (&test_addr); +} + +static void +address_suggest_cb (void *cls, const struct GNUNET_HELLO_Address *address, + struct Session *session, + struct GNUNET_BANDWIDTH_Value32NBO bandwidth_out, + struct GNUNET_BANDWIDTH_Value32NBO bandwidth_in, + const struct GNUNET_ATS_Information *atsi, + uint32_t ats_count) +{ + static int stage = 0; + if (0 == stage) + { + if (GNUNET_OK == compare_addresses (address, session, &test_hello_address, test_session)) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stage 0: Callback with correct address `%s'\n", + GNUNET_i2s (&address->peer)); + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stage 0: Callback with invalid address `%s'\n", + GNUNET_i2s (&address->peer)); + ret = 1; + } + + if (GNUNET_OK != compare_ats(atsi, ats_count, test_ats_info, test_ats_count)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Stage 0: Callback with incorrect ats info \n"); + ret = 1; + } + stage ++; + + GNUNET_ATS_suggest_address_cancel (sched_ats, &p.id); + + /* Adding address with session */ + test_session = &test_hello_address; + create_test_address (&test_addr, "test", test_session, "test", strlen ("test") + 1); + test_hello_address.peer = p.id; + test_hello_address.transport_name = test_addr.plugin; + test_hello_address.address = test_addr.addr; + test_hello_address.address_length = test_addr.addr_len; + GNUNET_ATS_address_add (sched_ats, &test_hello_address, test_session, test_ats_info, test_ats_count); + + GNUNET_ATS_suggest_address (sched_ats, &p.id); + return; + } + if (1 == stage) + { + if (GNUNET_OK == compare_addresses (address, session, &test_hello_address, test_session)) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stage 1: Callback with correct address `%s'\n", + GNUNET_i2s (&address->peer)); + ret = 0; + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stage 1: Callback with invalid address `%s'\n", + GNUNET_i2s (&address->peer)); + ret = 1; + } + + if (GNUNET_OK != compare_ats(atsi, ats_count, test_ats_info, test_ats_count)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Stage 1: Callback with incorrect ats info \n"); + ret = 1; + } + stage ++; + + GNUNET_ATS_suggest_address_cancel (sched_ats, &p.id); + GNUNET_SCHEDULER_add_now (&end, NULL); + return; + } + +} + +static void +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) +{ + + die_task = GNUNET_SCHEDULER_add_delayed (TIMEOUT, &end_badly, NULL); + + /* Connect to ATS scheduling */ + sched_ats = GNUNET_ATS_scheduling_init (cfg, &address_suggest_cb, NULL); + if (sched_ats == NULL) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Could not connect to ATS scheduling!\n"); + ret = 1; + end (); + return; + } + + /* Set up peer */ + if (GNUNET_SYSERR == GNUNET_CRYPTO_hash_from_string(PEERID0, &p.id.hashPubKey)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Could not setup peer!\n"); + ret = GNUNET_SYSERR; + end (); + return; + } + + GNUNET_assert (0 == strcmp (PEERID0, GNUNET_i2s_full (&p.id))); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Created peer `%s'\n", + GNUNET_i2s_full(&p.id)); + + /* Prepare ATS Information */ + test_ats_info[0].type = htonl (GNUNET_ATS_NETWORK_TYPE); + test_ats_info[0].value = htonl(GNUNET_ATS_NET_WAN); + test_ats_info[1].type = htonl (GNUNET_ATS_QUALITY_NET_DISTANCE); + test_ats_info[1].value = htonl(1); + test_ats_count = 2; + + /* Adding address without session */ + test_session = NULL; + create_test_address (&test_addr, "test", test_session, "test", strlen ("test") + 1); + test_hello_address.peer = p.id; + test_hello_address.transport_name = test_addr.plugin; + test_hello_address.address = test_addr.addr; + test_hello_address.address_length = test_addr.addr_len; + GNUNET_ATS_address_add (sched_ats, &test_hello_address, test_session, test_ats_info, test_ats_count); + + GNUNET_ATS_suggest_address (sched_ats, &p.id); +} + + +int +main (int argc, char *argv[]) +{ + if (0 != GNUNET_TESTING_peer_run ("test_ats_api_scheduling_add_address", + "test_ats_api.conf", + &run, NULL)) + return 1; + return ret; +} + +/* end of file test_ats_api_scheduling_add_session.c */ diff --git a/src/ats/test_ats_api_scheduling_block_and_reset.c b/src/ats/test_ats_api_scheduling_block_and_reset.c new file mode 100644 index 0000000..b799a5d --- /dev/null +++ b/src/ats/test_ats_api_scheduling_block_and_reset.c @@ -0,0 +1,364 @@ +/* + This file is part of GNUnet. + (C) 2010,2011 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ +/** + * @file ats/test_ats_api_scheduling_reset_backoff.c + * @brief test case for blocking suggests and blocking reset API + * measure duration of initial suggest, measure blocking duration, + * reset block, measure suggest, compare time + * @author Christian Grothoff + * @author Matthias Wachs + */ +#include "platform.h" +#include "gnunet_ats_service.h" +#include "gnunet_testing_lib.h" +#include "ats.h" +#include "test_ats_api_common.h" + +#define WAIT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MILLISECONDS, 10) + +static GNUNET_SCHEDULER_TaskIdentifier die_task; + +static GNUNET_SCHEDULER_TaskIdentifier wait_task; + +/** + * Scheduling handle + */ +static struct GNUNET_ATS_SchedulingHandle *sched_ats; + +/** + * Return value + */ +static int ret; + +/** + * Test address + */ +static struct Test_Address test_addr; + +/** + * Test peer + */ +static struct PeerContext p; + +/** + * HELLO address + */ +struct GNUNET_HELLO_Address test_hello_address; + +/** + * Session + */ +static void *test_session; + +/** + * Test ats info + */ +struct GNUNET_ATS_Information test_ats_info[2]; + +/** + * Test ats count + */ +uint32_t test_ats_count; + + +struct GNUNET_TIME_Absolute initial_start; + +struct GNUNET_TIME_Relative initial_duration; + +/** + * Blocking start + */ +struct GNUNET_TIME_Absolute block_start; + +struct GNUNET_TIME_Relative block_duration; + +struct GNUNET_TIME_Absolute reset_block_start; + +struct GNUNET_TIME_Relative reset_block_duration; + +static void +end_badly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + die_task = GNUNET_SCHEDULER_NO_TASK; + if (wait_task != GNUNET_SCHEDULER_NO_TASK) + { + GNUNET_SCHEDULER_cancel (wait_task); + wait_task = GNUNET_SCHEDULER_NO_TASK; + } + if (sched_ats != NULL) + GNUNET_ATS_scheduling_done (sched_ats); + free_test_address (&test_addr); + ret = GNUNET_SYSERR; +} + + +static void +end () +{ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Shutting down\n"); + if (die_task != GNUNET_SCHEDULER_NO_TASK) + { + GNUNET_SCHEDULER_cancel (die_task); + die_task = GNUNET_SCHEDULER_NO_TASK; + } + if (wait_task != GNUNET_SCHEDULER_NO_TASK) + { + GNUNET_SCHEDULER_cancel (wait_task); + wait_task = GNUNET_SCHEDULER_NO_TASK; + } + GNUNET_ATS_scheduling_done (sched_ats); + sched_ats = NULL; + free_test_address (&test_addr); +} + +static void +request_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + wait_task = GNUNET_SCHEDULER_NO_TASK; + GNUNET_ATS_suggest_address (sched_ats, &p.id); + wait_task = GNUNET_SCHEDULER_add_delayed (WAIT, &request_task, NULL); +} + +static void +address_suggest_cb (void *cls, const struct GNUNET_HELLO_Address *address, + struct Session *session, + struct GNUNET_BANDWIDTH_Value32NBO bandwidth_out, + struct GNUNET_BANDWIDTH_Value32NBO bandwidth_in, + const struct GNUNET_ATS_Information *atsi, + uint32_t ats_count) +{ + static int stage = 0; + + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Stage %u\n", stage); + if (3 == stage) + { + /* Suggestion after resetting block interval */ + reset_block_duration = GNUNET_TIME_absolute_get_difference(reset_block_start, GNUNET_TIME_absolute_get()); + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Address suggestion after resetting blocking took about %llu ms!\n", + (long long unsigned int) reset_block_duration.rel_value); + if ((block_duration.rel_value <= (initial_duration.rel_value * 3)) || + (initial_duration.rel_value <= (block_duration.rel_value * 3))) + { + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + "Address suggestion after resetting blocking (%llu ms) took about the same as initial suggestion (%llu ms)\n", + (long long unsigned int) reset_block_duration.rel_value, + (long long unsigned int) initial_duration.rel_value); + ret = 0; + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Address suggestion after resetting blocking (%llu ms) has too big difference to initial suggestion (%llu ms)\n", + (long long unsigned int) reset_block_duration.rel_value, + (long long unsigned int) initial_duration.rel_value); + ret = 1; + GNUNET_ATS_suggest_address_cancel (sched_ats, &p.id); + GNUNET_SCHEDULER_add_now (&end, NULL); + return; + } + + if (((initial_duration.rel_value * 3) <= block_duration.rel_value ) && + ((reset_block_duration.rel_value * 3) <= block_duration.rel_value)) + { + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Address suggestion after resetting blocking (%llu ms) and initial suggestion (%llu ms) much faster than with blocking (%llu ms)\n", + (long long unsigned int) reset_block_duration.rel_value, + (long long unsigned int) initial_duration.rel_value, + (long long unsigned int) block_duration.rel_value); + ret = 0; + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Address suggestion after resetting blocking (%llu ms) and initial suggestion (%llu ms) not faster than with blocking (%llu ms)\n", + (long long unsigned int) reset_block_duration.rel_value, + (long long unsigned int) initial_duration.rel_value, + (long long unsigned int) block_duration.rel_value); + ret = 1; + } + + + GNUNET_ATS_suggest_address_cancel (sched_ats, &p.id); + GNUNET_SCHEDULER_add_now (&end, NULL); + + } + if (2 == stage) + { + /* Suggestion after block*/ + block_duration = GNUNET_TIME_absolute_get_difference(block_start, GNUNET_TIME_absolute_get()); + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Address suggestion was blocked for about %llu ms!\n", + (long long unsigned int) block_duration.rel_value); + + if (GNUNET_OK == compare_addresses (address, session, &test_hello_address, test_session)) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stage %u: Callback with correct address `%s'\n", stage, + GNUNET_i2s (&address->peer)); + ret = 0; + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stage %u: Callback with invalid address `%s'\n", stage, + GNUNET_i2s (&address->peer)); + GNUNET_ATS_suggest_address_cancel (sched_ats, &p.id); + GNUNET_SCHEDULER_add_now (&end, NULL); + ret = 1; + } + + if (GNUNET_OK != compare_ats(atsi, ats_count, test_ats_info, test_ats_count)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Stage %u: Callback with incorrect ats info \n"); + GNUNET_ATS_suggest_address_cancel (sched_ats, &p.id); + GNUNET_SCHEDULER_add_now (&end, NULL); + ret = 1; + } + stage ++; + + /* Reset block interval */ + GNUNET_ATS_reset_backoff (sched_ats, &address->peer); + reset_block_start = GNUNET_TIME_absolute_get(); + GNUNET_ATS_suggest_address (sched_ats, &p.id); + } + if (1 == stage) + { + /* Initial suggestion */ + if (GNUNET_OK == compare_addresses (address, session, &test_hello_address, test_session)) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stage %u: Callback with correct address `%s'\n", stage, + GNUNET_i2s (&address->peer)); + ret = 0; + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stage %u: Callback with invalid address `%s'\n", stage, + GNUNET_i2s (&address->peer)); + GNUNET_ATS_suggest_address_cancel (sched_ats, &p.id); + GNUNET_SCHEDULER_add_now (&end, NULL); + ret = 1; + } + + if (GNUNET_OK != compare_ats(atsi, ats_count, test_ats_info, test_ats_count)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Stage %u: Callback with incorrect ats info \n"); + GNUNET_ATS_suggest_address_cancel (sched_ats, &p.id); + GNUNET_SCHEDULER_add_now (&end, NULL); + ret = 1; + } + stage ++; + initial_duration = GNUNET_TIME_absolute_get_difference(initial_start, GNUNET_TIME_absolute_get()); + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Stage %u: Initial suggestion took about %llu ms\n", stage, + (long long unsigned int) block_duration.rel_value); + + block_start = GNUNET_TIME_absolute_get(); + wait_task = GNUNET_SCHEDULER_add_delayed (WAIT, &request_task, NULL); + } + if (0 == stage) + { + /* Startup suggestion */ + if (GNUNET_OK == compare_addresses (address, session, &test_hello_address, test_session)) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stage %u: Callback with correct address `%s'\n", stage, + GNUNET_i2s (&address->peer)); + ret = 0; + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stage %u: Callback with invalid address `%s'\n", stage, + GNUNET_i2s (&address->peer)); + GNUNET_ATS_suggest_address_cancel (sched_ats, &p.id); + GNUNET_SCHEDULER_add_now (&end, NULL); + ret = 1; + } + + if (GNUNET_OK != compare_ats(atsi, ats_count, test_ats_info, test_ats_count)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Stage %u: Callback with incorrect ats info \n"); + GNUNET_ATS_suggest_address_cancel (sched_ats, &p.id); + GNUNET_SCHEDULER_add_now (&end, NULL); + ret = 1; + } + stage ++; + + GNUNET_ATS_suggest_address_cancel (sched_ats, &p.id); + + initial_start = GNUNET_TIME_absolute_get(); + GNUNET_ATS_suggest_address (sched_ats, &p.id); + } +} + + +static void +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) +{ + + die_task = GNUNET_SCHEDULER_add_delayed (TIMEOUT, &end_badly, NULL); + + /* Connect to ATS scheduling */ + sched_ats = GNUNET_ATS_scheduling_init (cfg, &address_suggest_cb, NULL); + if (sched_ats == NULL) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Could not connect to ATS scheduling!\n"); + ret = 1; + end (); + return; + } + + /* Set up peer */ + if (GNUNET_SYSERR == GNUNET_CRYPTO_hash_from_string(PEERID0, &p.id.hashPubKey)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Could not setup peer!\n"); + ret = GNUNET_SYSERR; + end (); + return; + } + GNUNET_assert (0 == strcmp (PEERID0, GNUNET_i2s_full (&p.id))); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Created peer `%s'\n", + GNUNET_i2s_full(&p.id)); + + /* Prepare ATS Information */ + test_ats_info[0].type = htonl (GNUNET_ATS_NETWORK_TYPE); + test_ats_info[0].value = htonl(GNUNET_ATS_NET_WAN); + test_ats_info[1].type = htonl (GNUNET_ATS_QUALITY_NET_DISTANCE); + test_ats_info[1].value = htonl(1); + test_ats_count = 2; + + /* Adding address without session */ + test_session = &test_addr; + create_test_address (&test_addr, "test", test_session, "test", strlen ("test") + 1); + test_hello_address.peer = p.id; + test_hello_address.transport_name = test_addr.plugin; + test_hello_address.address = test_addr.addr; + test_hello_address.address_length = test_addr.addr_len; + GNUNET_ATS_address_add (sched_ats, &test_hello_address, test_session, test_ats_info, test_ats_count); + + initial_start = GNUNET_TIME_absolute_get(); + GNUNET_ATS_suggest_address (sched_ats, &p.id); +} + + +int +main (int argc, char *argv[]) +{ + if (0 != GNUNET_TESTING_peer_run ("test_ats_api_scheduling_add_address", + "test_ats_api.conf", + &run, NULL)) + return 1; + return ret; +} +/* end of file test_ats_api_scheduling_reset_backoff.c */ diff --git a/src/ats/test_ats_api_scheduling_check_min_bw_alt.c b/src/ats/test_ats_api_scheduling_check_min_bw_alt.c new file mode 100644 index 0000000..bf23ad2 --- /dev/null +++ b/src/ats/test_ats_api_scheduling_check_min_bw_alt.c @@ -0,0 +1,417 @@ +/* + This file is part of GNUnet. + (C) 2010,2011 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ +/** + * @file ats/test_ats_mlp.c + * @brief test for the MLP solver + * @author Christian Grothoff + * @author Matthias Wachs + + */ +/** + * @file ats/test_ats_api_scheduling_check_min_bw_alt.c + * @brief alternative suggestion on network change if no bw is available + * @author Christian Grothoff + * @author Matthias Wachs + */ +#include "platform.h" +#include "gnunet_ats_service.h" +#include "gnunet_testing_lib.h" +#include "ats.h" +#include "test_ats_api_common.h" + +#define DEBUG_ATS_INFO GNUNET_NO + +static GNUNET_SCHEDULER_TaskIdentifier die_task; + +/** + * Scheduling handle + */ +static struct GNUNET_ATS_SchedulingHandle *sched_ats; + +/** + * Return value + */ +static int ret; + +/** + * Test address + */ +static struct Test_Address test_addr[2]; + +/** + * Test peer + */ +static struct PeerContext p[2]; + + +/** + * HELLO address + */ +struct GNUNET_HELLO_Address test_hello_address[2]; + +/** + * Session + */ +static void *test_session[2]; + +/** + * Test ats info + */ +struct GNUNET_ATS_Information test_ats_info[2][2]; + +/** + * Test ats count + */ +uint32_t test_ats_count; + +/** + * Configured WAN out quota + */ +unsigned long long wan_quota_out; + +/** + * Configured WAN in quota + */ +unsigned long long wan_quota_in; + + +static void +end_badly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + die_task = GNUNET_SCHEDULER_NO_TASK; + + if (sched_ats != NULL) + GNUNET_ATS_scheduling_done (sched_ats); + free_test_address (&test_addr[0]); + free_test_address (&test_addr[1]); + ret = GNUNET_SYSERR; +} + + +static void +end () +{ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Shutting down\n"); + if (die_task != GNUNET_SCHEDULER_NO_TASK) + { + GNUNET_SCHEDULER_cancel (die_task); + die_task = GNUNET_SCHEDULER_NO_TASK; + } + GNUNET_ATS_scheduling_done (sched_ats); + sched_ats = NULL; + free_test_address (&test_addr[0]); + free_test_address (&test_addr[1]); +} + + +static void +address_suggest_cb (void *cls, const struct GNUNET_HELLO_Address *address, + struct Session *session, + struct GNUNET_BANDWIDTH_Value32NBO bandwidth_out, + struct GNUNET_BANDWIDTH_Value32NBO bandwidth_in, + const struct GNUNET_ATS_Information *atsi, + uint32_t ats_count) +{ + static int stage = 0; + unsigned int bw_in = ntohl(bandwidth_in.value__); + unsigned int bw_out = ntohl(bandwidth_out.value__); + + if (0 == stage) + { + /* Initial suggestion for 1st address */ + if (GNUNET_OK == compare_addresses (address, session, &test_hello_address[0], test_session[0])) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stage %u: Callback with correct address `%s'\n", + stage, GNUNET_i2s (&address->peer)); + ret = 0; + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stage %u: Callback with invalid address `%s'\n", + stage, GNUNET_i2s (&address->peer)); + ret = 1; + } + + if (GNUNET_OK != compare_ats(atsi, ats_count, test_ats_info[0], test_ats_count)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Stage %u: Callback with incorrect ats info \n"); + ret = 1; + } + + if (bw_in > wan_quota_in) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Stage %u: Suggested WAN inbound quota %u bigger than allowed quota %llu \n", + stage, bw_in, wan_quota_in); + ret = 1; + } + else + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stage %u: Suggested WAN inbound quota %u, allowed quota %llu \n", + stage, bw_in, wan_quota_in); + + if (bw_out > wan_quota_out) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Stage %u: Suggested WAN outbound quota %u bigger than allowed quota %llu \n", + stage, bw_out, wan_quota_out); + ret = 1; + } + else + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stage %u: Suggested WAN outbound quota %u, allowed quota %llu \n", + stage, bw_out, wan_quota_out); + + if (1 == ret) + { + GNUNET_ATS_suggest_address_cancel (sched_ats, &p[0].id); + GNUNET_SCHEDULER_add_now (&end, NULL); + return; + } + + p[0].bw_out_assigned = bw_out; + p[0].bw_in_assigned = bw_in; + stage ++; + + /* Add a 2nd address to give ATS an suggestion alternative */ + /* Prepare ATS Information */ + test_ats_info[1][0].type = htonl (GNUNET_ATS_NETWORK_TYPE); + test_ats_info[1][0].value = htonl(GNUNET_ATS_NET_LAN); + test_ats_info[1][1].type = htonl (GNUNET_ATS_QUALITY_NET_DISTANCE); + test_ats_info[1][1].value = htonl(1); + test_ats_count = 2; + + /* Adding address with session */ + test_session[1] = &test_addr[1]; + create_test_address (&test_addr[1], "test1", test_session[1], "test1", strlen ("test1") + 1); + test_hello_address[1].peer = p[0].id; + test_hello_address[1].transport_name = test_addr[1].plugin; + test_hello_address[1].address = test_addr[1].addr; + test_hello_address[1].address_length = test_addr[1].addr_len; + GNUNET_ATS_address_add (sched_ats, &test_hello_address[1], test_session[1], + test_ats_info[1], test_ats_count); + + + /* Changing 1st address to network with now bw available (WLAN) */ + test_ats_info[0][0].type = htonl (GNUNET_ATS_NETWORK_TYPE); + test_ats_info[0][0].value = htonl(GNUNET_ATS_NET_WLAN); + test_ats_info[0][1].type = htonl (GNUNET_ATS_QUALITY_NET_DISTANCE); + test_ats_info[0][1].value = htonl(1); + test_ats_count = 2; + + GNUNET_ATS_address_update (sched_ats, &test_hello_address[0], test_session[0], + test_ats_info[0], test_ats_count); + return; + } + if (1 == stage) + { + /* Bandwidth update to (in/out) 0/0 for 1st address */ + if (GNUNET_OK == compare_addresses (address, session, &test_hello_address[0], test_session[0])) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stage %u: Callback with correct address `%s'\n", + stage, GNUNET_i2s (&address->peer)); + ret = 0; + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stage %u: Callback with invalid address `%s'\n", + stage, GNUNET_i2s (&address->peer)); + ret = 1; + } + + if (GNUNET_OK != compare_ats(atsi, ats_count, test_ats_info[0], test_ats_count)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Stage %u: Callback with incorrect ats info \n"); + ret = 1; + } + + if ((bw_in != 0) || (bw_out != 0)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Stage %u: ATS did not set bandwidth to 0 but instead to %u/%u \n", + stage, bw_in, wan_quota_in); + ret = 1; + } + + if (1 == ret) + { + GNUNET_ATS_suggest_address_cancel (sched_ats, &p[0].id); + GNUNET_SCHEDULER_add_now (&end, NULL); + return; + } + p[0].bw_out_assigned = bw_out; + p[0].bw_in_assigned = bw_in; + stage ++; + return; + } + if (2 == stage) + { + /* Expecting suggestion of alternative 2nd address*/ + if (GNUNET_OK == compare_addresses (address, session, &test_hello_address[1], test_session[1])) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stage %u: Callback with correct address `%s'\n", + stage, GNUNET_i2s (&address->peer)); + ret = 0; + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stage %u: Callback with invalid address `%s'\n", + stage, GNUNET_i2s (&address->peer)); + ret = 1; + } + + if (GNUNET_OK != compare_ats(atsi, ats_count, test_ats_info[1], test_ats_count)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Stage %u: Callback with incorrect ats info \n", + stage); + ret = 1; + } + + if ((bw_in == 0) || (bw_out == 0)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Stage %u: ATS did not set bandwidth correctly \n", + stage); + ret = 1; + } + + if (1 == ret) + { + GNUNET_ATS_suggest_address_cancel (sched_ats, &p[0].id); + GNUNET_SCHEDULER_add_now (&end, NULL); + return; + } + + GNUNET_ATS_suggest_address_cancel (sched_ats, &p[0].id); + GNUNET_SCHEDULER_add_now (&end, NULL); + ret = 0; + return; + } +} + +static void +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) +{ + char *quota_str; + + if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_string(cfg, "ats", "WAN_QUOTA_OUT", "a_str)) + { + fprintf (stderr, "Cannot load WAN outbound quota from configuration, exit!\n"); + ret = 1; + return; + } + if (GNUNET_SYSERR == GNUNET_STRINGS_fancy_size_to_bytes (quota_str, &wan_quota_out)) + { + fprintf (stderr, "Cannot load WAN outbound quota from configuration, exit!\n"); + ret = 1; + GNUNET_free (quota_str); + return; + } + GNUNET_free (quota_str); + quota_str = NULL; + + if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_string(cfg, "ats", "WAN_QUOTA_IN", "a_str)) + { + fprintf (stderr, "Cannot load WAN inbound quota from configuration, exit!\n"); + ret = 1; + return; + } + if (GNUNET_SYSERR == GNUNET_STRINGS_fancy_size_to_bytes (quota_str, &wan_quota_in)) + { + fprintf (stderr, "Cannot load WAN inbound quota from configuration, exit!\n"); + GNUNET_free (quota_str); + ret = 1; + return; + } + GNUNET_free (quota_str); + quota_str = NULL; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Configured WAN inbound quota: %llu\n", wan_quota_in); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Configured WAN outbound quota: %llu\n", wan_quota_out); + + + die_task = GNUNET_SCHEDULER_add_delayed (TIMEOUT, &end_badly, NULL); + + /* Connect to ATS scheduling */ + sched_ats = GNUNET_ATS_scheduling_init (cfg, &address_suggest_cb, NULL); + if (sched_ats == NULL) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Could not connect to ATS scheduling!\n"); + ret = 1; + end (); + return; + } + + /* Set up peer 0 */ + if (GNUNET_SYSERR == GNUNET_CRYPTO_hash_from_string(PEERID0, &p[0].id.hashPubKey)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Could not setup peer!\n"); + ret = GNUNET_SYSERR; + end (); + return; + } + + GNUNET_assert (0 == strcmp (PEERID0, GNUNET_i2s_full (&p[0].id))); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Created peer `%s'\n", + GNUNET_i2s(&p[0].id)); + + /* Set up peer 1*/ + if (GNUNET_SYSERR == GNUNET_CRYPTO_hash_from_string(PEERID1, &p[1].id.hashPubKey)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Could not setup peer!\n"); + ret = GNUNET_SYSERR; + end (); + return; + } + + GNUNET_assert (0 == strcmp (PEERID1, GNUNET_i2s_full (&p[1].id))); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Created peer `%s'\n", + GNUNET_i2s(&p[1].id)); + + /* Prepare ATS Information */ + test_ats_info[0][0].type = htonl (GNUNET_ATS_NETWORK_TYPE); + test_ats_info[0][0].value = htonl(GNUNET_ATS_NET_WAN); + test_ats_info[0][1].type = htonl (GNUNET_ATS_QUALITY_NET_DISTANCE); + test_ats_info[0][1].value = htonl(1); + test_ats_count = 2; + + /* Adding address with session */ + test_session[0] = &test_addr[0]; + create_test_address (&test_addr[0], "test0", test_session[0], "test0", strlen ("test0") + 1); + test_hello_address[0].peer = p[0].id; + test_hello_address[0].transport_name = test_addr[0].plugin; + test_hello_address[0].address = test_addr[0].addr; + test_hello_address[0].address_length = test_addr[0].addr_len; + GNUNET_ATS_address_add (sched_ats, &test_hello_address[0], test_session[0], + test_ats_info[0], test_ats_count); + + GNUNET_ATS_suggest_address (sched_ats, &p[0].id); +} + + +int +main (int argc, char *argv[]) +{ + if (0 != GNUNET_TESTING_peer_run ("test_ats_api_scheduling_check_min_bw_alt", + "test_ats_api.conf", + &run, NULL)) + return 1; + return ret; +} + + +/* end of file test_ats_api_scheduling_check_min_bw_alt.c */ diff --git a/src/ats/test_ats_api_scheduling_destroy_address.c b/src/ats/test_ats_api_scheduling_destroy_address.c new file mode 100644 index 0000000..93b90da --- /dev/null +++ b/src/ats/test_ats_api_scheduling_destroy_address.c @@ -0,0 +1,218 @@ +/* + This file is part of GNUnet. + (C) 2010,2011 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ +/** + * @file ats/test_ats_api_scheduling_destroy_address.c + * @brief test destroying addresses in automatic transport selection scheduling API + * @author Christian Grothoff + * @author Matthias Wachs + * + */ +#include "platform.h" +#include "gnunet_ats_service.h" +#include "gnunet_testing_lib.h" +#include "ats.h" +#include "test_ats_api_common.h" + +static GNUNET_SCHEDULER_TaskIdentifier die_task; + +static GNUNET_SCHEDULER_TaskIdentifier wait_task; + +#define WAIT_TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 5) + + +/** + * Scheduling handle + */ +static struct GNUNET_ATS_SchedulingHandle *sched_ats; + +/** + * Return value + */ +static int ret; + +/** + * Test address + */ +static struct Test_Address test_addr; + +/** + * Test peer + */ +static struct PeerContext p; + +/** + * HELLO address + */ +struct GNUNET_HELLO_Address test_hello_address; + +/** + * Session + */ +static void *test_session; + +/** + * Test ats info + */ +struct GNUNET_ATS_Information test_ats_info[2]; + +/** + * Test ats count + */ +uint32_t test_ats_count; + + +static void +end_badly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + die_task = GNUNET_SCHEDULER_NO_TASK; + if (GNUNET_SCHEDULER_NO_TASK != wait_task) + { + GNUNET_SCHEDULER_cancel (wait_task); + wait_task = GNUNET_SCHEDULER_NO_TASK; + } + if (sched_ats != NULL) + GNUNET_ATS_scheduling_done (sched_ats); + free_test_address (&test_addr); + ret = GNUNET_SYSERR; +} + + +static void +end () +{ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Shutting down\n"); + wait_task = GNUNET_SCHEDULER_NO_TASK; + if (die_task != GNUNET_SCHEDULER_NO_TASK) + { + GNUNET_SCHEDULER_cancel (die_task); + die_task = GNUNET_SCHEDULER_NO_TASK; + } + free_test_address (&test_addr); + GNUNET_ATS_scheduling_done (sched_ats); + sched_ats = NULL; +} + +static void +address_suggest_cb (void *cls, const struct GNUNET_HELLO_Address *address, + struct Session *session, + struct GNUNET_BANDWIDTH_Value32NBO bandwidth_out, + struct GNUNET_BANDWIDTH_Value32NBO bandwidth_in, + const struct GNUNET_ATS_Information *atsi, + uint32_t ats_count) +{ + static int stage = 0; + + if (0 ==stage) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stage 0: Received suggestion for peer `%s'\n", + GNUNET_i2s(&address->peer)); + + GNUNET_ATS_suggest_address_cancel (sched_ats, &p.id); + if (GNUNET_OK == compare_addresses (address, session, &test_hello_address, test_session)) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Callback with correct address `%s'\n", + GNUNET_i2s (&address->peer)); + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Callback with invalid address `%s'\n", + GNUNET_i2s (&address->peer)); + GNUNET_SCHEDULER_add_now (&end, NULL); + ret = 1; + return; + } + stage ++; + ret = 0; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Destroying address for `%s'\n", + GNUNET_i2s (&address->peer)); + /* Destroying address */ + GNUNET_ATS_address_destroyed (sched_ats, &test_hello_address, test_addr.session); + /* Request address */ + GNUNET_ATS_suggest_address (sched_ats, &p.id); + /* Wait for timeout */ + wait_task = GNUNET_SCHEDULER_add_delayed (WAIT_TIMEOUT, &end, NULL); + return; + } + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Stage 1: Unexpected address suggestion\n"); + ret = 1; + +} + + +static void +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) +{ + die_task = GNUNET_SCHEDULER_add_delayed (TIMEOUT, &end_badly, NULL); + + /* Connect to ATS scheduling */ + sched_ats = GNUNET_ATS_scheduling_init (cfg, &address_suggest_cb, NULL); + if (sched_ats == NULL) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Could not connect to ATS scheduling!\n"); + ret = 1; + end (); + return; + } + + /* Set up peer */ + if (GNUNET_SYSERR == GNUNET_CRYPTO_hash_from_string(PEERID0, &p.id.hashPubKey)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Could not setup peer!\n"); + ret = GNUNET_SYSERR; + end (); + return; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Created peer `%s'\n", + GNUNET_i2s_full(&p.id)); + + /* Prepare ATS Information */ + test_ats_info[0].type = htonl (GNUNET_ATS_NETWORK_TYPE); + test_ats_info[0].value = htonl(GNUNET_ATS_NET_WAN); + test_ats_info[1].type = htonl (GNUNET_ATS_QUALITY_NET_DISTANCE); + test_ats_info[1].value = htonl(1); + test_ats_count = 2; + + /* Adding address without session */ + test_session = NULL; + create_test_address (&test_addr, "test", test_session, "test", strlen ("test") + 1); + test_hello_address.peer = p.id; + test_hello_address.transport_name = test_addr.plugin; + test_hello_address.address = test_addr.addr; + test_hello_address.address_length = test_addr.addr_len; + GNUNET_ATS_address_add (sched_ats, &test_hello_address, test_session, test_ats_info, 2); + + /* Request address */ + GNUNET_ATS_suggest_address (sched_ats, &p.id); +} + + +int +main (int argc, char *argv[]) +{ + if (0 != GNUNET_TESTING_peer_run ("test_ats_api_scheduling_add_address", + "test_ats_api.conf", + &run, NULL)) + return 1; + return ret; +} + +/* end of file test_ats_api_scheduling_destroy_address.c */ diff --git a/src/ats/test_ats_api_scheduling_destroy_inbound_connection.c b/src/ats/test_ats_api_scheduling_destroy_inbound_connection.c new file mode 100644 index 0000000..fe98859 --- /dev/null +++ b/src/ats/test_ats_api_scheduling_destroy_inbound_connection.c @@ -0,0 +1,223 @@ +/* + This file is part of GNUnet. + (C) 2010,2011 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ +/** + * @file ats/test_ats_api_scheduling_destroy_inbound_connection.c + * @brief test destroying sessions for inbound connections: first add an address with a session, + * request the address and compare, delete the session, request and + * compare again, delete whole address, request and wait for timeout, + * shutdown + * @author Christian Grothoff + * @author Matthias Wachs + * + */ +#include "platform.h" +#include "gnunet_ats_service.h" +#include "gnunet_testing_lib.h" +#include "ats.h" +#include "test_ats_api_common.h" + +static GNUNET_SCHEDULER_TaskIdentifier die_task; + +static GNUNET_SCHEDULER_TaskIdentifier wait_task; + +#define WAIT_TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 5) + + +/** + * Scheduling handle + */ +static struct GNUNET_ATS_SchedulingHandle *sched_ats; + +/** + * Return value + */ +static int ret; + +/** + * Test address + */ +static struct Test_Address test_addr; + +/** + * Test peer + */ +static struct PeerContext p; + +/** + * HELLO address + */ +struct GNUNET_HELLO_Address test_hello_address; + +/** + * Session + */ +static void *test_session; + +/** + * Test ats info + */ +struct GNUNET_ATS_Information test_ats_info[2]; + +/** + * Test ats count + */ +uint32_t test_ats_count; + + +static void +end_badly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + die_task = GNUNET_SCHEDULER_NO_TASK; + if (wait_task != GNUNET_SCHEDULER_NO_TASK) + { + GNUNET_SCHEDULER_cancel (wait_task); + wait_task = GNUNET_SCHEDULER_NO_TASK; + } + if (sched_ats != NULL) + GNUNET_ATS_scheduling_done (sched_ats); + free_test_address (&test_addr); + ret = GNUNET_SYSERR; +} + + +static void +end () +{ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Shutting down\n"); + wait_task = GNUNET_SCHEDULER_NO_TASK; + if (die_task != GNUNET_SCHEDULER_NO_TASK) + { + GNUNET_SCHEDULER_cancel (die_task); + die_task = GNUNET_SCHEDULER_NO_TASK; + } + free_test_address (&test_addr); + GNUNET_ATS_scheduling_done (sched_ats); + sched_ats = NULL; +} + + +static void +address_suggest_cb (void *cls, const struct GNUNET_HELLO_Address *address, + struct Session *session, + struct GNUNET_BANDWIDTH_Value32NBO bandwidth_out, + struct GNUNET_BANDWIDTH_Value32NBO bandwidth_in, + const struct GNUNET_ATS_Information *atsi, + uint32_t ats_count) +{ + static int stage = 0; + + if (0 == stage) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stage 0: Received suggestion for peer `%s'\n", + GNUNET_i2s(&address->peer)); + + GNUNET_ATS_suggest_address_cancel (sched_ats, &p.id); + if (GNUNET_OK == compare_addresses (address, session, &test_hello_address, test_session)) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stage 0: Callback with correct address `%s'\n", + GNUNET_i2s (&address->peer)); + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stage 0: Callback with invalid address `%s'\n", + GNUNET_i2s (&address->peer)); + GNUNET_SCHEDULER_add_now (&end, NULL); + ret = 1; + return; + } + stage ++; + ret = 0; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Destroying address for `%s'\n", + GNUNET_i2s (&address->peer)); + /* Destroying session for address */ + test_session = NULL; + GNUNET_ATS_address_destroyed (sched_ats, &test_hello_address, test_addr.session); + /* Request address */ + GNUNET_ATS_suggest_address (sched_ats, &p.id); + + /* Wait for timeout */ + wait_task = GNUNET_SCHEDULER_add_delayed (WAIT_TIMEOUT, &end, NULL); + return; + } + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Stage %u: Unexpected address suggestion\n", stage); + ret = 1; +} + + +static void +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) +{ + die_task = GNUNET_SCHEDULER_add_delayed (TIMEOUT, &end_badly, NULL); + + /* Connect to ATS scheduling */ + sched_ats = GNUNET_ATS_scheduling_init (cfg, &address_suggest_cb, NULL); + if (sched_ats == NULL) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Could not connect to ATS scheduling!\n"); + ret = 1; + end (); + return; + } + + /* Set up peer */ + if (GNUNET_SYSERR == GNUNET_CRYPTO_hash_from_string(PEERID0, &p.id.hashPubKey)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Could not setup peer!\n"); + ret = GNUNET_SYSERR; + end (); + return; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Created peer `%s'\n", + GNUNET_i2s_full(&p.id)); + + /* Prepare ATS Information */ + test_ats_info[0].type = htonl (GNUNET_ATS_NETWORK_TYPE); + test_ats_info[0].value = htonl(GNUNET_ATS_NET_WAN); + test_ats_info[1].type = htonl (GNUNET_ATS_QUALITY_NET_DISTANCE); + test_ats_info[1].value = htonl(1); + test_ats_count = 2; + + /* Adding address with session */ + create_test_address (&test_addr, "test", &test_addr, NULL, 0); + test_session = &test_addr; + test_hello_address.peer = p.id; + test_hello_address.transport_name = test_addr.plugin; + test_hello_address.address = test_addr.addr; + test_hello_address.address_length = test_addr.addr_len; + GNUNET_ATS_address_add (sched_ats, &test_hello_address, test_addr.session, test_ats_info, test_ats_count); + + /* Request address */ + GNUNET_ATS_suggest_address (sched_ats, &p.id); +} + + +int +main (int argc, char *argv[]) +{ + if (0 != GNUNET_TESTING_peer_run ("test_ats_api_scheduling_add_address", + "test_ats_api.conf", + &run, NULL)) + return 1; + return ret; +} + +/* end of file test_ats_api_scheduling_destroy_inbound_connection.c */ diff --git a/src/ats/test_ats_api_scheduling_destroy_session.c b/src/ats/test_ats_api_scheduling_destroy_session.c new file mode 100644 index 0000000..9467bdc --- /dev/null +++ b/src/ats/test_ats_api_scheduling_destroy_session.c @@ -0,0 +1,235 @@ +/* + This file is part of GNUnet. + (C) 2010,2011 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ +/** + * @file ats/test_ats_api_scheduling_destroy_session.c + * @brief test destroying sessions: first add an address with a session, + * request the address and compare, delete the session, request and + * compare again, delete whole address, request and wait for timeout, + * shutdown + * @author Christian Grothoff + * @author Matthias Wachs + * + */ +#include "platform.h" +#include "gnunet_ats_service.h" +#include "gnunet_testing_lib.h" +#include "ats.h" +#include "test_ats_api_common.h" + +static GNUNET_SCHEDULER_TaskIdentifier die_task; + +static GNUNET_SCHEDULER_TaskIdentifier wait_task; + +#define WAIT_TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 5) + + +/** + * Scheduling handle + */ +static struct GNUNET_ATS_SchedulingHandle *sched_ats; + +/** + * Return value + */ +static int ret; + +/** + * Test address + */ +static struct Test_Address test_addr; + +/** + * Test peer + */ +static struct PeerContext p; + +/** + * HELLO address + */ +struct GNUNET_HELLO_Address test_hello_address; + +/** + * Session + */ +static void *test_session; + + +static void +end_badly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + die_task = GNUNET_SCHEDULER_NO_TASK; + if (wait_task != GNUNET_SCHEDULER_NO_TASK) + { + GNUNET_SCHEDULER_cancel (wait_task); + wait_task = GNUNET_SCHEDULER_NO_TASK; + } + if (sched_ats != NULL) + GNUNET_ATS_scheduling_done (sched_ats); + free_test_address (&test_addr); + ret = GNUNET_SYSERR; +} + + +static void +end () +{ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Shutting down\n"); + wait_task = GNUNET_SCHEDULER_NO_TASK; + if (die_task != GNUNET_SCHEDULER_NO_TASK) + { + GNUNET_SCHEDULER_cancel (die_task); + die_task = GNUNET_SCHEDULER_NO_TASK; + } + free_test_address (&test_addr); + GNUNET_ATS_scheduling_done (sched_ats); + sched_ats = NULL; +} + + +static void +address_suggest_cb (void *cls, const struct GNUNET_HELLO_Address *address, + struct Session *session, + struct GNUNET_BANDWIDTH_Value32NBO bandwidth_out, + struct GNUNET_BANDWIDTH_Value32NBO bandwidth_in, + const struct GNUNET_ATS_Information *atsi, + uint32_t ats_count) +{ + static int stage = 0; + + if (0 == stage) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stage 0: Received suggestion for peer `%s'\n", + GNUNET_i2s(&address->peer)); + + GNUNET_ATS_suggest_address_cancel (sched_ats, &p.id); + if (GNUNET_OK == compare_addresses (address, session, &test_hello_address, test_session)) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stage 0: Callback with correct address `%s'\n", + GNUNET_i2s (&address->peer)); + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stage 0: Callback with invalid address `%s'\n", + GNUNET_i2s (&address->peer)); + GNUNET_SCHEDULER_add_now (&end, NULL); + ret = 1; + return; + } + stage ++; + ret = 0; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Destroying address for `%s'\n", + GNUNET_i2s (&address->peer)); + /* Destroying session for address */ + test_session = NULL; + GNUNET_ATS_address_destroyed (sched_ats, &test_hello_address, test_addr.session); + /* Request address */ + GNUNET_ATS_suggest_address (sched_ats, &p.id); + return; + } + else if (1 == stage) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stage 1: Received suggestion for peer `%s'\n", + GNUNET_i2s(&address->peer)); + + + GNUNET_ATS_suggest_address_cancel (sched_ats, &p.id); + if (GNUNET_OK == compare_addresses (address, session, &test_hello_address, test_session)) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stage 1: Callback with correct address `%s'\n", + GNUNET_i2s (&address->peer)); + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stage 1: Callback with invalid address `%s'\n", + GNUNET_i2s (&address->peer)); + GNUNET_SCHEDULER_add_now (&end, NULL); + ret = 1; + return; + } + stage ++; + ret = 0; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Destroying address for `%s'\n", + GNUNET_i2s (&address->peer)); + /* Destroying complete address */ + GNUNET_ATS_address_destroyed (sched_ats, &test_hello_address, session); + /* Request address */ + GNUNET_ATS_suggest_address (sched_ats, &p.id); + wait_task = GNUNET_SCHEDULER_add_delayed (WAIT_TIMEOUT, &end, NULL); + return; + } + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Stage 1: Unexpected address suggestion\n"); + ret = 1; + +} + + +static void +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) +{ + die_task = GNUNET_SCHEDULER_add_delayed (TIMEOUT, &end_badly, NULL); + + /* Connect to ATS scheduling */ + sched_ats = GNUNET_ATS_scheduling_init (cfg, &address_suggest_cb, NULL); + if (sched_ats == NULL) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Could not connect to ATS scheduling!\n"); + ret = 1; + end (); + return; + } + + /* Set up peer */ + if (GNUNET_SYSERR == GNUNET_CRYPTO_hash_from_string(PEERID0, &p.id.hashPubKey)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Could not setup peer!\n"); + ret = GNUNET_SYSERR; + end (); + return; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Created peer `%s'\n", + GNUNET_i2s_full(&p.id)); + + /* Adding address with session */ + create_test_address (&test_addr, "test", &test_addr, "test", strlen ("test") + 1); + test_session = &test_addr; + test_hello_address.peer = p.id; + test_hello_address.transport_name = test_addr.plugin; + test_hello_address.address = test_addr.addr; + test_hello_address.address_length = test_addr.addr_len; + GNUNET_ATS_address_add (sched_ats, &test_hello_address, test_addr.session, NULL, 0); + + /* Request address */ + GNUNET_ATS_suggest_address (sched_ats, &p.id); +} + + +int +main (int argc, char *argv[]) +{ + if (0 != GNUNET_TESTING_peer_run ("test_ats_api_scheduling_add_address", + "test_ats_api.conf", + &run, NULL)) + return 1; + return ret; +} + +/* end of file test_ats_api_scheduling_destroy_session.c */ diff --git a/src/ats/test_ats_api_scheduling_init.c b/src/ats/test_ats_api_scheduling_init.c new file mode 100644 index 0000000..bd96a4d --- /dev/null +++ b/src/ats/test_ats_api_scheduling_init.c @@ -0,0 +1,141 @@ +/* + This file is part of GNUnet. + (C) 2010,2011 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ +/** + * @file ats/test_ats_api_scheduling_init.c + * @brief test automatic transport selection scheduling API init/shutdown + * @author Christian Grothoff + * @author Matthias Wachs + * + */ +#include "platform.h" +#include "gnunet_ats_service.h" +#include "gnunet_testing_lib.h" +#include "ats.h" + +#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 30) +#define DELAY GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 5) + +static GNUNET_SCHEDULER_TaskIdentifier die_task; +static GNUNET_SCHEDULER_TaskIdentifier wait_task; + +static struct GNUNET_ATS_SchedulingHandle *ats; + +static int ret; + +static void +end_badly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + die_task = GNUNET_SCHEDULER_NO_TASK; + if (GNUNET_SCHEDULER_NO_TASK != wait_task) + { + GNUNET_SCHEDULER_cancel (wait_task); + wait_task = GNUNET_SCHEDULER_NO_TASK; + } + if (ats != NULL) + { + GNUNET_ATS_scheduling_done (ats); + ats = NULL; + } + ret = 1; +} + +static void +end_badly_now () +{ + if (die_task != GNUNET_SCHEDULER_NO_TASK) + { + GNUNET_SCHEDULER_cancel (die_task); + die_task = GNUNET_SCHEDULER_NO_TASK; + } + die_task = GNUNET_SCHEDULER_add_now (&end_badly, NULL); +} + +static void +delay (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + static int v_delay = 5; + static int v_cur = 0; + + if (v_cur < v_delay) + { + wait_task = GNUNET_SCHEDULER_NO_TASK; + wait_task = GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_SECONDS, &delay, NULL); + fprintf (stderr,"."); + v_cur ++; + return; + } + + fprintf (stderr,"\n"); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Shutdown ATS\n"); + GNUNET_ATS_scheduling_done (ats); + ats = NULL; + if (die_task != GNUNET_SCHEDULER_NO_TASK) + { + GNUNET_SCHEDULER_cancel (die_task); + die_task = GNUNET_SCHEDULER_NO_TASK; + } + ret = 0; +} + +static void +address_suggest_cb (void *cls, const struct GNUNET_HELLO_Address *address, + struct Session *session, + struct GNUNET_BANDWIDTH_Value32NBO bandwidth_out, + struct GNUNET_BANDWIDTH_Value32NBO bandwidth_in, + const struct GNUNET_ATS_Information *ats, + uint32_t ats_count) +{ + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Received address without asking for it!\n"); + end_badly_now (); +} + + +static void +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) +{ + ret = 1; + die_task = GNUNET_SCHEDULER_add_delayed (TIMEOUT, &end_badly, NULL); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Initializing ATS\n"); + ats = GNUNET_ATS_scheduling_init (cfg, &address_suggest_cb, NULL); + if (ats == NULL) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Failed to initialize ATS\n"); + end_badly_now (); + return; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Waiting for %llu sec\n", (long long unsigned int) DELAY.rel_value); + wait_task = GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_SECONDS, &delay, NULL); +} + + +int +main (int argc, char *argv[]) +{ + if (0 != GNUNET_TESTING_peer_run ("test_ats_api_scheduling_init", + "test_ats_api.conf", + &run, NULL)) + return 1; + return ret; +} + +/* end of file test_ats_api_scheduling_init.c */ diff --git a/src/ats/test_ats_api_scheduling_min_bw.c b/src/ats/test_ats_api_scheduling_min_bw.c new file mode 100644 index 0000000..5a59c23 --- /dev/null +++ b/src/ats/test_ats_api_scheduling_min_bw.c @@ -0,0 +1,185 @@ +/* + This file is part of GNUnet. + (C) 2010,2011 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ +/** + * @file ats/test_ats_api_scheduling_min_bw.c + * @brief add in address for a network where quota is below min bw: no suggest expected + * @author Christian Grothoff + * @author Matthias Wachs + */ +#include "platform.h" +#include "gnunet_ats_service.h" +#include "gnunet_testing_lib.h" +#include "ats.h" +#include "test_ats_api_common.h" + +#define WAIT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 3) + +static GNUNET_SCHEDULER_TaskIdentifier die_task; +static GNUNET_SCHEDULER_TaskIdentifier wait_task; + +/** + * Scheduling handle + */ +static struct GNUNET_ATS_SchedulingHandle *sched_ats; + +/** + * Return value + */ +static int ret; + +/** + * Test address + */ +static struct Test_Address test_addr; + +/** + * Test peer + */ +static struct PeerContext p; + +/** + * HELLO address + */ +struct GNUNET_HELLO_Address test_hello_address; + +/** + * Session + */ +static void *test_session; + +/** + * Test ats info + */ +struct GNUNET_ATS_Information test_ats_info[2]; + +/** + * Test ats count + */ +uint32_t test_ats_count; + + +static void +end_badly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + die_task = GNUNET_SCHEDULER_NO_TASK; + + if (sched_ats != NULL) + GNUNET_ATS_scheduling_done (sched_ats); + free_test_address (&test_addr); + ret = GNUNET_SYSERR; +} + + +static void +end (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Shutting down\n"); + if (die_task != GNUNET_SCHEDULER_NO_TASK) + { + GNUNET_SCHEDULER_cancel (die_task); + die_task = GNUNET_SCHEDULER_NO_TASK; + } + if (NULL != sched_ats) + GNUNET_ATS_scheduling_done (sched_ats); + sched_ats = NULL; + free_test_address (&test_addr); +} + +static void +address_suggest_cb (void *cls, const struct GNUNET_HELLO_Address *address, + struct Session *session, + struct GNUNET_BANDWIDTH_Value32NBO bandwidth_out, + struct GNUNET_BANDWIDTH_Value32NBO bandwidth_in, + const struct GNUNET_ATS_Information *atsi, + uint32_t ats_count) +{ + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Did not expect suggestion!\n"); + GNUNET_ATS_suggest_address_cancel (sched_ats, &p.id); + GNUNET_SCHEDULER_add_now (&end, NULL); + ret = 1; +} + +static void +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) +{ + + die_task = GNUNET_SCHEDULER_add_delayed (TIMEOUT, &end_badly, NULL); + + /* Connect to ATS scheduling */ + sched_ats = GNUNET_ATS_scheduling_init (cfg, &address_suggest_cb, NULL); + if (sched_ats == NULL) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Could not connect to ATS scheduling!\n"); + ret = 1; + GNUNET_SCHEDULER_add_now (&end , NULL); + return; + } + + /* Set up peer */ + if (GNUNET_SYSERR == GNUNET_CRYPTO_hash_from_string(PEERID0, &p.id.hashPubKey)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Could not setup peer!\n"); + ret = GNUNET_SYSERR; + GNUNET_SCHEDULER_add_now (&end , NULL); + return; + } + + GNUNET_assert (0 == strcmp (PEERID0, GNUNET_i2s_full (&p.id))); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Created peer `%s'\n", + GNUNET_i2s_full(&p.id)); + + /* Prepare ATS Information */ + test_ats_info[0].type = htonl (GNUNET_ATS_NETWORK_TYPE); + test_ats_info[0].value = htonl(GNUNET_ATS_NET_WLAN); /* WLAN quota is below min bw */ + test_ats_info[1].type = htonl (GNUNET_ATS_QUALITY_NET_DISTANCE); + test_ats_info[1].value = htonl(1); + test_ats_count = 2; + + /* Adding address without session */ + test_session = NULL; + create_test_address (&test_addr, "test", test_session, "test", strlen ("test") + 1); + test_hello_address.peer = p.id; + test_hello_address.transport_name = test_addr.plugin; + test_hello_address.address = test_addr.addr; + test_hello_address.address_length = test_addr.addr_len; + GNUNET_ATS_address_add (sched_ats, &test_hello_address, test_session, test_ats_info, test_ats_count); + + GNUNET_ATS_suggest_address (sched_ats, &p.id); + + ret = 0; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Waiting for wait period for no suggest...\n"); + wait_task = GNUNET_SCHEDULER_add_delayed (WAIT, &end, NULL); +} + + +int +main (int argc, char *argv[]) +{ + if (0 != GNUNET_TESTING_peer_run ("test_ats_api_scheduling_add_address", + "test_ats_api.conf", + &run, NULL)) + return 1; + return ret; +} + +/* end of file test_ats_api_scheduling_min_bw.c */ diff --git a/src/ats/test_ats_api_scheduling_update_address.c b/src/ats/test_ats_api_scheduling_update_address.c new file mode 100644 index 0000000..2f52d64 --- /dev/null +++ b/src/ats/test_ats_api_scheduling_update_address.c @@ -0,0 +1,247 @@ +/* + This file is part of GNUnet. + (C) 2010,2011 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ +/** + * @file ats/test_ats_api_scheduling_update_address.c + * @brief test updating an address: add address, get and compare it, update it + * get it again and compre + * @author Christian Grothoff + * @author Matthias Wachs + */ +#include "platform.h" +#include "gnunet_ats_service.h" +#include "gnunet_testing_lib.h" +#include "ats.h" +#include "test_ats_api_common.h" + +static GNUNET_SCHEDULER_TaskIdentifier die_task; + +/** + * Scheduling handle + */ +static struct GNUNET_ATS_SchedulingHandle *sched_ats; + +/** + * Return value + */ +static int ret; + +/** + * Test address + */ +static struct Test_Address test_addr; + +/** + * Test peer + */ +static struct PeerContext p; + +/** + * HELLO test address + */ + +struct GNUNET_HELLO_Address test_hello_address; + +/** + * Test session + */ +static void *test_session; + +/** + * Test ats info + */ +struct GNUNET_ATS_Information test_ats_info[3]; + +/** + * Test ats count + */ +uint32_t test_ats_count; + + +static void +end_badly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + die_task = GNUNET_SCHEDULER_NO_TASK; + + if (sched_ats != NULL) + GNUNET_ATS_scheduling_done (sched_ats); + free_test_address (&test_addr); + ret = GNUNET_SYSERR; +} + + +static void +end () +{ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Shutting down\n"); + if (die_task != GNUNET_SCHEDULER_NO_TASK) + { + GNUNET_SCHEDULER_cancel (die_task); + die_task = GNUNET_SCHEDULER_NO_TASK; + } + GNUNET_ATS_scheduling_done (sched_ats); + sched_ats = NULL; + free_test_address (&test_addr); +} + + +static void +address_suggest_cb (void *cls, const struct GNUNET_HELLO_Address *address, + struct Session *session, + struct GNUNET_BANDWIDTH_Value32NBO bandwidth_out, + struct GNUNET_BANDWIDTH_Value32NBO bandwidth_in, + const struct GNUNET_ATS_Information *atsi, + uint32_t ats_count) +{ + static int stage = 0; + if (0 == stage) + { + GNUNET_ATS_suggest_address_cancel (sched_ats, &p.id); + if (GNUNET_OK == compare_addresses(address, session, &test_hello_address, test_session)) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stage 0: Callback for correct address `%s'\n", + GNUNET_i2s (&address->peer)); + ret = 0; + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Stage 0: Callback with incorrect address `%s'\n", + GNUNET_i2s (&address->peer)); + ret = 1; + GNUNET_SCHEDULER_add_now (&end, NULL); + return; + } + + if (GNUNET_OK != compare_ats(atsi, ats_count, test_ats_info, test_ats_count)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Stage 0: Callback with incorrect ats info \n"); + ret = 1; + GNUNET_SCHEDULER_add_now (&end, NULL); + return; + } + + /* Update address */ + /* Prepare ATS Information */ + test_ats_info[0].type = htonl (GNUNET_ATS_NETWORK_TYPE); + test_ats_info[0].value = htonl(GNUNET_ATS_NET_WAN); + test_ats_info[1].type = htonl (GNUNET_ATS_QUALITY_NET_DISTANCE); + test_ats_info[1].value = htonl(3); + test_ats_info[1].type = htonl (GNUNET_ATS_QUALITY_NET_DELAY); + test_ats_info[1].value = htonl(30); + test_ats_count = 2; + + GNUNET_ATS_address_update (sched_ats, &test_hello_address, test_session, test_ats_info, test_ats_count); + + /* Request address */ + GNUNET_ATS_suggest_address (sched_ats, &p.id); + stage ++; + } + else if (1 == stage) + { + GNUNET_ATS_suggest_address_cancel (sched_ats, &p.id); + if (GNUNET_OK == compare_addresses(address, session, &test_hello_address, test_session)) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stage 1: Callback with correct address `%s'\n", + GNUNET_i2s (&address->peer)); + ret = 0; + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Stage 1: Callback with incorrect address `%s'\n", + GNUNET_i2s (&address->peer)); + ret = 1; + } + + if (GNUNET_OK != compare_ats(atsi, ats_count, test_ats_info, test_ats_count)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Stage 1: Callback with incorrect ats info \n"); + ret = 1; + GNUNET_SCHEDULER_add_now (&end, NULL); + return; + } + + GNUNET_SCHEDULER_add_now (&end, NULL); + } +} + +static void +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) +{ + die_task = GNUNET_SCHEDULER_add_delayed (TIMEOUT, &end_badly, NULL); + + /* Connect to ATS scheduling */ + sched_ats = GNUNET_ATS_scheduling_init (cfg, &address_suggest_cb, NULL); + if (sched_ats == NULL) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Could not connect to ATS scheduling!\n"); + ret = 1; + end (); + return; + } + + /* Set up peer */ + if (GNUNET_SYSERR == GNUNET_CRYPTO_hash_from_string(PEERID0, &p.id.hashPubKey)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Could not setup peer!\n"); + ret = GNUNET_SYSERR; + end (); + return; + } + + GNUNET_assert (0 == strcmp (PEERID0, GNUNET_i2s_full (&p.id))); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Created peer `%s'\n", + GNUNET_i2s_full(&p.id)); + + /* Prepare ATS Information */ + test_ats_info[0].type = htonl (GNUNET_ATS_NETWORK_TYPE); + test_ats_info[0].value = htonl(GNUNET_ATS_NET_WAN); + test_ats_info[1].type = htonl (GNUNET_ATS_QUALITY_NET_DISTANCE); + test_ats_info[1].value = htonl(1); + test_ats_info[1].type = htonl (GNUNET_ATS_QUALITY_NET_DELAY); + test_ats_info[1].value = htonl(10); + test_ats_count = 2; + + /* Adding address without session */ + test_session = &test_addr; + create_test_address (&test_addr, "test", &test_addr, "test", strlen ("test") + 1); + test_hello_address.peer = p.id; + test_hello_address.transport_name = test_addr.plugin; + test_hello_address.address = test_addr.addr; + test_hello_address.address_length = test_addr.addr_len; + GNUNET_ATS_address_add (sched_ats, &test_hello_address, test_session, test_ats_info, test_ats_count); + + /* Request address */ + GNUNET_ATS_suggest_address (sched_ats, &p.id); +} + + +int +main (int argc, char *argv[]) +{ + if (0 != GNUNET_TESTING_peer_run ("test_ats_api_scheduling_update_address", + "test_ats_api.conf", + &run, NULL)) + return 1; + return ret; +} + +/* end of file test_ats_api_scheduling_update_address.c */ diff --git a/src/ats/test_ats_mlp.c b/src/ats/test_ats_mlp.c deleted file mode 100644 index c467210..0000000 --- a/src/ats/test_ats_mlp.c +++ /dev/null @@ -1,195 +0,0 @@ -/* - This file is part of GNUnet. - (C) 2010,2011 Christian Grothoff (and other contributing authors) - - GNUnet is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published - by the Free Software Foundation; either version 3, or (at your - option) any later version. - - GNUnet is distributed in the hope that it will be useful, but - WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - General Public License for more details. - - You should have received a copy of the GNU General Public License - along with GNUnet; see the file COPYING. If not, write to the - Free Software Foundation, Inc., 59 Temple Place - Suite 330, - Boston, MA 02111-1307, USA. -*/ -/** - * @file ats/test_ats_mlp.c - * @brief test for the MLP solver - * @author Christian Grothoff - * @author Matthias Wachs - - */ -#include "platform.h" -#include "gnunet_util_lib.h" -#include "gnunet_statistics_service.h" -#include "gnunet_ats_service.h" -#include "gnunet-service-ats_addresses_mlp.h" - -#define MLP_MAX_EXEC_DURATION GNUNET_TIME_relative_multiply(GNUNET_TIME_UNIT_SECONDS, 3) -#define MLP_MAX_ITERATIONS INT_MAX - - -static int ret; - -struct GNUNET_STATISTICS_Handle * stats; - -struct GNUNET_CONTAINER_MultiHashMap * addresses; - -struct GAS_MLP_Handle *mlp; - - -static void -create_address (struct ATS_Address *addr, char * plugin, int ats_count, struct GNUNET_ATS_Information *ats) -{ - addr->mlp_information = NULL; - addr->next = NULL; - addr->prev = NULL; - addr->plugin = GNUNET_strdup (plugin); - addr->ats_count = ats_count; - addr->ats = ats; -} - -static void -set_ats (struct GNUNET_ATS_Information *ats, uint32_t type, uint32_t value) -{ - ats->type = type; - ats->value = value; -} - -static void -check (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) -{ -#if !HAVE_LIBGLPK - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "GLPK not installed!"); - ret = 1; - return; -#endif - struct ATS_Address addr[10]; - struct ATS_PreferedAddress *res[10]; - struct GAS_MLP_SolutionContext ctx; - - stats = GNUNET_STATISTICS_create("ats", cfg); - - addresses = GNUNET_CONTAINER_multihashmap_create (10); - - mlp = GAS_mlp_init (cfg, NULL, MLP_MAX_EXEC_DURATION, MLP_MAX_ITERATIONS); - mlp->auto_solve = GNUNET_NO; - - struct GNUNET_PeerIdentity p[10]; - - /* Creating peer 1 */ - GNUNET_CRYPTO_hash_create_random(GNUNET_CRYPTO_QUALITY_WEAK, &p[0].hashPubKey); - /* Creating peer 2 */ - GNUNET_CRYPTO_hash_create_random(GNUNET_CRYPTO_QUALITY_WEAK, &p[1].hashPubKey); - - /* Creating peer 1 address 1 */ - addr[0].peer.hashPubKey = p[0].hashPubKey; - struct GNUNET_ATS_Information a1_ats[3]; - set_ats (&a1_ats[0], GNUNET_ATS_QUALITY_NET_DISTANCE, 1); - set_ats (&a1_ats[1], GNUNET_ATS_QUALITY_NET_DELAY, 1); - set_ats (&a1_ats[2], GNUNET_ATS_ARRAY_TERMINATOR, 0); - create_address (&addr[0], "dummy", 3, &a1_ats[0]); - addr[0].atsp_network_type = GNUNET_ATS_NET_WAN; - - /* Creating peer 1 address 2 */ - addr[1].peer.hashPubKey = p[0].hashPubKey; - struct GNUNET_ATS_Information a2_ats[3]; - set_ats (&a2_ats[1], GNUNET_ATS_QUALITY_NET_DISTANCE, 1); - set_ats (&a2_ats[0], GNUNET_ATS_QUALITY_NET_DELAY, 1); - set_ats (&a2_ats[2], GNUNET_ATS_ARRAY_TERMINATOR, 0); - create_address (&addr[1], "dummy2", 3, &a2_ats[0]); - addr[1].atsp_network_type = GNUNET_ATS_NET_LAN; - - /* Creating peer 2 address 1 */ - addr[2].peer.hashPubKey = p[1].hashPubKey; - struct GNUNET_ATS_Information a3_ats[3]; - set_ats (&a3_ats[1], GNUNET_ATS_QUALITY_NET_DISTANCE, 1); - set_ats (&a3_ats[0], GNUNET_ATS_QUALITY_NET_DELAY, 1); - set_ats (&a3_ats[2], GNUNET_ATS_ARRAY_TERMINATOR, 0); - create_address (&addr[2], "dummy3", 3, &a3_ats[0]); - addr[2].atsp_network_type = GNUNET_ATS_NET_LAN; - - GNUNET_CONTAINER_multihashmap_put(addresses, &addr[0].peer.hashPubKey, &addr[0], GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE); - - /* Add peer 1 address 1 */ - GAS_mlp_address_update (mlp, addresses, &addr[0]); - - GNUNET_assert (mlp != NULL); - GNUNET_assert (mlp->addr_in_problem == 1); - - /* Update an peer 1 address 1 */ - set_ats (&a1_ats[1], GNUNET_ATS_QUALITY_NET_DELAY, 1); - GAS_mlp_address_update (mlp, addresses, &addr[0]); - GNUNET_assert (mlp->addr_in_problem == 1); - - /* Add peer 1 address 2 */ - GNUNET_CONTAINER_multihashmap_put(addresses, &addr[0].peer.hashPubKey, &addr[1], GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE); - GAS_mlp_address_update (mlp, addresses, &addr[1]); - GNUNET_assert (mlp->addr_in_problem == 2); - - /* Add peer 2 address 1 */ - GNUNET_CONTAINER_multihashmap_put(addresses, &addr[2].peer.hashPubKey, &addr[2], GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE); - GAS_mlp_address_update (mlp, addresses, &addr[2]); - GNUNET_assert (mlp->addr_in_problem == 3); - - GNUNET_assert (GNUNET_OK == GAS_mlp_solve_problem(mlp, &ctx)); - GNUNET_assert (GNUNET_OK == ctx.lp_result); - GNUNET_assert (GNUNET_OK == ctx.mlp_result); - - res[0] = GAS_mlp_get_preferred_address(mlp, addresses, &p[0]); - GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Preferred address `%s' outbound bandwidth: %u Bps\n",res[0]->address->plugin, res[0]->bandwidth_out); - res[1] = GAS_mlp_get_preferred_address(mlp, addresses, &p[1]); - GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Preferred address `%s' outbound bandwidth: %u Bps\n",res[1]->address->plugin, res[1]->bandwidth_out); - - /* Delete an address */ - GNUNET_CONTAINER_multihashmap_remove (addresses, &addr[0].peer.hashPubKey, &addr[0]); - GAS_mlp_address_delete (mlp, addresses, &addr[0]); - GNUNET_CONTAINER_multihashmap_remove (addresses, &addr[1].peer.hashPubKey, &addr[1]); - GAS_mlp_address_delete (mlp, addresses, &addr[1]); - GNUNET_CONTAINER_multihashmap_remove (addresses, &addr[2].peer.hashPubKey, &addr[2]); - GAS_mlp_address_delete (mlp, addresses, &addr[2]); - - GNUNET_assert (mlp->addr_in_problem == 0); - - GAS_mlp_done (mlp); - - GNUNET_free (addr[0].plugin); - GNUNET_free (addr[1].plugin); - GNUNET_CONTAINER_multihashmap_destroy (addresses); - GNUNET_STATISTICS_destroy(stats, GNUNET_NO); - - ret = 0; - return; -} - - -int -main (int argc, char *argv[]) -{ - - static char *const argv2[] = { "test_ats_mlp", - "-c", - "test_ats_api.conf", - "-L", "WARNING", - NULL - }; - - static struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - - GNUNET_PROGRAM_run ((sizeof (argv2) / sizeof (char *)) - 1, argv2, - "test_ats_mlp", "nohelp", options, - &check, NULL); - - - return ret; -} - -/* end of file test_ats_api_bandwidth_consumption.c */ diff --git a/src/ats/test_ats_mlp_averaging.c b/src/ats/test_ats_mlp_averaging.c deleted file mode 100644 index 97e9aa7..0000000 --- a/src/ats/test_ats_mlp_averaging.c +++ /dev/null @@ -1,178 +0,0 @@ -/* - This file is part of GNUnet. - (C) 2010,2011 Christian Grothoff (and other contributing authors) - - GNUnet is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published - by the Free Software Foundation; either version 3, or (at your - option) any later version. - - GNUnet is distributed in the hope that it will be useful, but - WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - General Public License for more details. - - You should have received a copy of the GNU General Public License - along with GNUnet; see the file COPYING. If not, write to the - Free Software Foundation, Inc., 59 Temple Place - Suite 330, - Boston, MA 02111-1307, USA. -*/ -/** - * @file ats/test_ats_mlp.c - * @brief test for the MLP solver - * @author Christian Grothoff - * @author Matthias Wachs - - */ -#include "platform.h" -#include "gnunet_util_lib.h" -#include "gnunet_statistics_service.h" -#include "gnunet_ats_service.h" -#include "gnunet-service-ats_addresses_mlp.h" - -#define MLP_MAX_EXEC_DURATION GNUNET_TIME_relative_multiply(GNUNET_TIME_UNIT_SECONDS, 3) -#define MLP_MAX_ITERATIONS INT_MAX - - -static int ret; - -struct GNUNET_STATISTICS_Handle * stats; - -struct GNUNET_CONTAINER_MultiHashMap * addresses; - -struct GAS_MLP_Handle *mlp; - - -static void -create_address (struct ATS_Address *addr, char * plugin, int ats_count, struct GNUNET_ATS_Information *ats) -{ - addr->mlp_information = NULL; - addr->next = NULL; - addr->prev = NULL; - addr->plugin = GNUNET_strdup (plugin); - addr->ats_count = ats_count; - addr->ats = ats; -} - -static void -set_ats (struct GNUNET_ATS_Information *ats, uint32_t type, uint32_t value) -{ - ats->type = type; - ats->value = value; -} - -static void -check (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) -{ -#if !HAVE_LIBGLPK - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "GLPK not installed!"); - ret = 1; - return; -#endif - struct ATS_Address addr[10]; - struct ATS_PreferedAddress *res[10]; - struct MLP_information *mlpi; - struct GAS_MLP_SolutionContext ctx; - - stats = GNUNET_STATISTICS_create("ats", cfg); - - addresses = GNUNET_CONTAINER_multihashmap_create (10); - - mlp = GAS_mlp_init (cfg, NULL, MLP_MAX_EXEC_DURATION, MLP_MAX_ITERATIONS); - mlp->auto_solve = GNUNET_NO; - - struct GNUNET_PeerIdentity p[10]; - - /* Creating peer 1 */ - GNUNET_CRYPTO_hash_create_random(GNUNET_CRYPTO_QUALITY_WEAK, &p[0].hashPubKey); - - /* Creating peer 1 address 1 */ - addr[0].peer.hashPubKey = p[0].hashPubKey; - struct GNUNET_ATS_Information a1_ats[3]; - set_ats (&a1_ats[0], GNUNET_ATS_QUALITY_NET_DISTANCE, 1); - set_ats (&a1_ats[1], GNUNET_ATS_QUALITY_NET_DELAY, 0); - set_ats (&a1_ats[2], GNUNET_ATS_ARRAY_TERMINATOR, 0); - create_address (&addr[0], "dummy", 3, &a1_ats[0]); - addr[0].atsp_network_type = GNUNET_ATS_NET_LAN; - - GNUNET_CONTAINER_multihashmap_put(addresses, &addr[0].peer.hashPubKey, &addr[0], GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE); - - /* Add peer 1 address 1 */ - GAS_mlp_address_update (mlp, addresses, &addr[0]); - mlpi = addr[0].mlp_information; - - GNUNET_assert (mlp != NULL); - GNUNET_assert (mlp->addr_in_problem == 1); - - /* Update an peer 1 address 1 */ - set_ats (&a1_ats[1], GNUNET_ATS_QUALITY_NET_DELAY, 20); - GAS_mlp_address_update (mlp, addresses, &addr[0]); - GNUNET_assert (mlp->addr_in_problem == 1); - - - /* Update an peer 1 address 1 */ - set_ats (&a1_ats[1], GNUNET_ATS_QUALITY_NET_DELAY, 10); - GAS_mlp_address_update (mlp, addresses, &addr[0]); - GNUNET_assert (mlp->addr_in_problem == 1); - - /* Update an peer 1 address 1 */ - set_ats (&a1_ats[1], GNUNET_ATS_QUALITY_NET_DELAY, 10); - GAS_mlp_address_update (mlp, addresses, &addr[0]); - GNUNET_assert (mlp->addr_in_problem == 1); - - /* Update an peer 1 address 1 */ - set_ats (&a1_ats[1], GNUNET_ATS_QUALITY_NET_DELAY, 30); - GAS_mlp_address_update (mlp, addresses, &addr[0]); - GNUNET_assert (mlp->addr_in_problem == 1); - - - GNUNET_assert (GNUNET_OK == GAS_mlp_solve_problem(mlp, &ctx)); - GNUNET_assert (GNUNET_OK == ctx.lp_result); - GNUNET_assert (GNUNET_OK == ctx.mlp_result); - - res[0] = GAS_mlp_get_preferred_address(mlp, addresses, &p[0]); - GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Preferred address `%s' outbound bandwidth: %u Bps\n",res[0]->address->plugin, res[0]->bandwidth_out); - GNUNET_free (res[0]); - - /* Delete an address */ - GNUNET_CONTAINER_multihashmap_remove (addresses, &addr[0].peer.hashPubKey, &addr[0]); - GAS_mlp_address_delete (mlp, addresses, &addr[0]); - - GNUNET_assert (mlp->addr_in_problem == 0); - - GAS_mlp_done (mlp); - - GNUNET_free (addr[0].plugin); - GNUNET_CONTAINER_multihashmap_destroy (addresses); - GNUNET_STATISTICS_destroy(stats, GNUNET_NO); - - ret = 0; - return; -} - - -int -main (int argc, char *argv[]) -{ - - static char *const argv2[] = { "test_ats_mlp", - "-c", - "test_ats_api.conf", - "-L", "WARNING", - NULL - }; - - static struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - - GNUNET_PROGRAM_run ((sizeof (argv2) / sizeof (char *)) - 1, argv2, - "test_ats_mlp", "nohelp", options, - &check, NULL); - - - return ret; -} - -/* end of file test_ats_api_bandwidth_consumption.c */ diff --git a/src/ats/test_ats_simplistic.c b/src/ats/test_ats_simplistic.c new file mode 100644 index 0000000..b11ae4e --- /dev/null +++ b/src/ats/test_ats_simplistic.c @@ -0,0 +1,380 @@ +/* + This file is part of GNUnet. + (C) 2010,2011 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ +/** + * @file ats/test_ats_mlp.c + * @brief test for the MLP solver + * @author Christian Grothoff + * @author Matthias Wachs + + */ +/** + * @file ats/test_ats_api_scheduling_add_address.c + * @brief test for ats simplistic solver + * @author Christian Grothoff + * @author Matthias Wachs + */ +#include "platform.h" +#include "gnunet_ats_service.h" +#include "gnunet_testing_lib.h" +#include "ats.h" +#include "test_ats_api_common.h" + +#define DEBUG_ATS_INFO GNUNET_NO + +static GNUNET_SCHEDULER_TaskIdentifier die_task; + +/** + * Scheduling handle + */ +static struct GNUNET_ATS_SchedulingHandle *sched_ats; + +/** + * Return value + */ +static int ret; + +/** + * Test address + */ +static struct Test_Address test_addr[2]; + +/** + * Test peer + */ +static struct PeerContext p[2]; + + +/** + * HELLO address + */ +struct GNUNET_HELLO_Address test_hello_address[2]; + +/** + * Session + */ +static void *test_session[2]; + +/** + * Test ats info + */ +struct GNUNET_ATS_Information test_ats_info[2]; + +/** + * Test ats count + */ +uint32_t test_ats_count; + +/** + * Configured WAN out quota + */ +unsigned long long wan_quota_out; + +/** + * Configured WAN in quota + */ +unsigned long long wan_quota_in; + + +static void +end_badly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + die_task = GNUNET_SCHEDULER_NO_TASK; + + if (sched_ats != NULL) + GNUNET_ATS_scheduling_done (sched_ats); + free_test_address (&test_addr[0]); + ret = GNUNET_SYSERR; +} + + +static void +end () +{ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Shutting down\n"); + if (die_task != GNUNET_SCHEDULER_NO_TASK) + { + GNUNET_SCHEDULER_cancel (die_task); + die_task = GNUNET_SCHEDULER_NO_TASK; + } + GNUNET_ATS_scheduling_done (sched_ats); + sched_ats = NULL; + free_test_address (&test_addr[0]); +} + + +static void +address_suggest_cb (void *cls, const struct GNUNET_HELLO_Address *address, + struct Session *session, + struct GNUNET_BANDWIDTH_Value32NBO bandwidth_out, + struct GNUNET_BANDWIDTH_Value32NBO bandwidth_in, + const struct GNUNET_ATS_Information *atsi, + uint32_t ats_count) +{ + static int stage = 0; + unsigned int bw_in = ntohl(bandwidth_in.value__); + unsigned int bw_out = ntohl(bandwidth_out.value__); + if (0 == stage) + { + if (GNUNET_OK == compare_addresses (address, session, &test_hello_address[0], test_session[0])) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stage 0: Callback with correct address `%s'\n", + GNUNET_i2s (&address->peer)); + ret = 0; + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stage 0: Callback with invalid address `%s'\n", + GNUNET_i2s (&address->peer)); + ret = 1; + } + + if (GNUNET_OK != compare_ats(atsi, ats_count, test_ats_info, test_ats_count)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Stage 0: Callback with incorrect ats info \n"); + ret = 1; + } + + if (bw_in > wan_quota_in) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Suggested WAN inbound quota %u bigger than allowed quota %llu \n", + bw_in, wan_quota_in); + ret = 1; + } + else + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Suggested WAN inbound quota %u, allowed quota %llu \n", + bw_in, wan_quota_in); + + if (bw_out > wan_quota_out) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Suggested WAN outbound quota %u bigger than allowed quota %llu \n", + bw_out, wan_quota_out); + ret = 1; + } + else + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Suggested WAN outbound quota %u, allowed quota %llu \n", + bw_out, wan_quota_out); + + if (1 == ret) + { + GNUNET_ATS_suggest_address_cancel (sched_ats, &p[0].id); + GNUNET_SCHEDULER_add_now (&end, NULL); + return; + } + p[0].bw_out_assigned = bw_out; + p[0].bw_in_assigned = bw_in; + stage ++; + + /* Add a 2nd address */ + /* Prepare ATS Information */ + test_ats_info[0].type = htonl (GNUNET_ATS_NETWORK_TYPE); + test_ats_info[0].value = htonl(GNUNET_ATS_NET_WAN); + test_ats_info[1].type = htonl (GNUNET_ATS_QUALITY_NET_DISTANCE); + test_ats_info[1].value = htonl(1); + test_ats_count = 2; + + /* Adding address with session */ + test_session[1] = &test_addr[1]; + create_test_address (&test_addr[1], "test1", test_session[1], "test1", strlen ("test1") + 1); + test_hello_address[1].peer = p[1].id; + test_hello_address[1].transport_name = test_addr[1].plugin; + test_hello_address[1].address = test_addr[1].addr; + test_hello_address[1].address_length = test_addr[1].addr_len; + GNUNET_ATS_address_add (sched_ats, &test_hello_address[1], test_session[1], test_ats_info, test_ats_count); + } + if (1 == stage) + { + /* Expecting callback for address[0] with updated quota and no callback for address[1]*/ + if (GNUNET_OK == compare_addresses (address, session, &test_hello_address[0], test_session[0])) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stage 1: Callback with correct address `%s'\n", + GNUNET_i2s (&address->peer)); + ret = 0; + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stage 1: Callback with invalid address `%s'\n", + GNUNET_i2s (&address->peer)); + ret = 1; + } + + if (GNUNET_OK != compare_ats(atsi, ats_count, test_ats_info, test_ats_count)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Stage 1: Callback with incorrect ats info \n"); + ret = 1; + } + + if (bw_in > wan_quota_in) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Suggested WAN inbound quota %u bigger than allowed quota %llu \n", + bw_in, wan_quota_in); + ret = 1; + } + else if (p[0].bw_in_assigned > bw_in) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Suggested WAN inbound quota %u bigger than last quota %llu \n", + bw_in, p[0].bw_in_assigned); + ret = 1; + } + else + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Suggested WAN inbound quota %u, allowed quota %llu \n", + bw_in, wan_quota_in); + + if (bw_out > wan_quota_out) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Suggested WAN outbound quota %u bigger than allowed quota %llu \n", + bw_out, wan_quota_out); + ret = 1; + } + else if (p[0].bw_out_assigned > bw_out) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Suggested WAN inbound quota %u bigger than last quota %llu \n", + bw_out, p[0].bw_out_assigned); + ret = 1; + } + else + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Suggested WAN outbound quota %u, allowed quota %llu \n", + bw_out, wan_quota_out); + + if (1 == ret) + { + GNUNET_SCHEDULER_add_now (&end, NULL); + return; + } + stage ++; + GNUNET_SCHEDULER_add_now (&end, NULL); + return; + } + +} + +static void +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) +{ + char *quota_str; + + if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_string(cfg, "ats", "WAN_QUOTA_OUT", "a_str)) + { + fprintf (stderr, "Cannot load WAN outbound quota from configuration, exit!\n"); + ret = 1; + return; + } + if (GNUNET_SYSERR == GNUNET_STRINGS_fancy_size_to_bytes (quota_str, &wan_quota_out)) + { + fprintf (stderr, "Cannot load WAN outbound quota from configuration, exit!\n"); + ret = 1; + GNUNET_free (quota_str); + return; + } + GNUNET_free (quota_str); + quota_str = NULL; + + if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_string(cfg, "ats", "WAN_QUOTA_IN", "a_str)) + { + fprintf (stderr, "Cannot load WAN inbound quota from configuration, exit!\n"); + ret = 1; + return; + } + if (GNUNET_SYSERR == GNUNET_STRINGS_fancy_size_to_bytes (quota_str, &wan_quota_in)) + { + fprintf (stderr, "Cannot load WAN inbound quota from configuration, exit!\n"); + GNUNET_free (quota_str); + ret = 1; + return; + } + GNUNET_free (quota_str); + quota_str = NULL; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Configured WAN inbound quota: %llu\n", wan_quota_in); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Configured WAN outbound quota: %llu\n", wan_quota_out); + + + die_task = GNUNET_SCHEDULER_add_delayed (TIMEOUT, &end_badly, NULL); + + /* Connect to ATS scheduling */ + sched_ats = GNUNET_ATS_scheduling_init (cfg, &address_suggest_cb, NULL); + if (sched_ats == NULL) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Could not connect to ATS scheduling!\n"); + ret = 1; + end (); + return; + } + + /* Set up peer 0 */ + if (GNUNET_SYSERR == GNUNET_CRYPTO_hash_from_string(PEERID0, &p[0].id.hashPubKey)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Could not setup peer!\n"); + ret = GNUNET_SYSERR; + end (); + return; + } + + GNUNET_assert (0 == strcmp (PEERID0, GNUNET_i2s_full (&p[0].id))); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Created peer `%s'\n", + GNUNET_i2s(&p[0].id)); + + /* Set up peer 1*/ + if (GNUNET_SYSERR == GNUNET_CRYPTO_hash_from_string(PEERID1, &p[1].id.hashPubKey)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Could not setup peer!\n"); + ret = GNUNET_SYSERR; + end (); + return; + } + + GNUNET_assert (0 == strcmp (PEERID1, GNUNET_i2s_full (&p[1].id))); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Created peer `%s'\n", + GNUNET_i2s(&p[1].id)); + + /* Prepare ATS Information */ + test_ats_info[0].type = htonl (GNUNET_ATS_NETWORK_TYPE); + test_ats_info[0].value = htonl(GNUNET_ATS_NET_WAN); + test_ats_info[1].type = htonl (GNUNET_ATS_QUALITY_NET_DISTANCE); + test_ats_info[1].value = htonl(1); + test_ats_count = 2; + + /* Adding address with session */ + test_session[0] = &test_addr[0]; + create_test_address (&test_addr[0], "test0", test_session[0], "test0", strlen ("test0") + 1); + test_hello_address[0].peer = p[0].id; + test_hello_address[0].transport_name = test_addr[0].plugin; + test_hello_address[0].address = test_addr[0].addr; + test_hello_address[0].address_length = test_addr[0].addr_len; + GNUNET_ATS_address_add (sched_ats, &test_hello_address[0], test_session[0], test_ats_info, test_ats_count); + + GNUNET_ATS_suggest_address (sched_ats, &p[0].id); +} + + +int +main (int argc, char *argv[]) +{ + if (0 != GNUNET_TESTING_peer_run ("test_ats_simplististic", + "test_ats_api.conf", + &run, NULL)) + return 1; + return ret; +} + + +/* end of file test_ats_api_bandwidth_consumption.c */ diff --git a/src/ats/test_ats_simplistic_change_preference.c b/src/ats/test_ats_simplistic_change_preference.c new file mode 100644 index 0000000..793d0cb --- /dev/null +++ b/src/ats/test_ats_simplistic_change_preference.c @@ -0,0 +1,418 @@ +/* + This file is part of GNUnet. + (C) 2010,2011 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ +/** + * @file ats/test_ats_mlp.c + * @brief test for the MLP solver + * @author Christian Grothoff + * @author Matthias Wachs + + */ +/** + * @file ats/test_ats_simplistic_change_preference.c + * @brief test for changing preferences in ats simplistic solver + * @author Christian Grothoff + * @author Matthias Wachs + */ +#include "platform.h" +#include "gnunet_ats_service.h" +#include "gnunet_testing_lib.h" +#include "ats.h" +#include "test_ats_api_common.h" + +#define DEBUG_ATS_INFO GNUNET_NO + +#define SLEEP GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 5) + +static GNUNET_SCHEDULER_TaskIdentifier die_task; + +/** + * Scheduling handle + */ +static struct GNUNET_ATS_SchedulingHandle *sched_ats; + +/** + * Scheduling handle + */ +static struct GNUNET_ATS_PerformanceHandle *perf_ats; + + +/** + * Return value + */ +static int ret; + +/** + * Test address + */ +static struct Test_Address test_addr[2]; + +/** + * Test peer + */ +static struct PeerContext p[2]; + + +/** + * HELLO address + */ +struct GNUNET_HELLO_Address test_hello_address[2]; + +/** + * Session + */ +static void *test_session[2]; + +/** + * Test ats info + */ +struct GNUNET_ATS_Information test_ats_info[2]; + +/** + * Test ats count + */ +uint32_t test_ats_count; + +/** + * Configured WAN out quota + */ +unsigned long long wan_quota_out; + +/** + * Configured WAN in quota + */ +unsigned long long wan_quota_in; + + +static void +end_badly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + die_task = GNUNET_SCHEDULER_NO_TASK; + + if (sched_ats != NULL) + GNUNET_ATS_scheduling_done (sched_ats); + if (perf_ats != NULL) + GNUNET_ATS_performance_done (perf_ats); + free_test_address (&test_addr[0]); + ret = GNUNET_SYSERR; +} + + +static void +end () +{ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Shutting down\n"); + if (die_task != GNUNET_SCHEDULER_NO_TASK) + { + GNUNET_SCHEDULER_cancel (die_task); + die_task = GNUNET_SCHEDULER_NO_TASK; + } + GNUNET_ATS_performance_done (perf_ats); + perf_ats = NULL; + GNUNET_ATS_scheduling_done (sched_ats); + sched_ats = NULL; + free_test_address (&test_addr[0]); +} + + +static void +address_suggest_cb (void *cls, const struct GNUNET_HELLO_Address *address, + struct Session *session, + struct GNUNET_BANDWIDTH_Value32NBO bandwidth_out, + struct GNUNET_BANDWIDTH_Value32NBO bandwidth_in, + const struct GNUNET_ATS_Information *atsi, + uint32_t ats_count) +{ + static int stage = 0; + unsigned int bw_in = ntohl(bandwidth_in.value__); + unsigned int bw_out = ntohl(bandwidth_out.value__); + if (0 == stage) + { + if (GNUNET_OK == compare_addresses (address, session, &test_hello_address[0], test_session[0])) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stage %u: Callback with correct address `%s'\n", + stage, + GNUNET_i2s (&address->peer)); + ret = 0; + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stage %u: Callback with invalid address `%s'\n", + stage, + GNUNET_i2s (&address->peer)); + ret = 1; + } + + if (GNUNET_OK != compare_ats(atsi, ats_count, test_ats_info, test_ats_count)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Stage %u: Callback with incorrect ats info \n", + stage); + ret = 1; + } + + if (bw_in > wan_quota_in) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Suggested WAN inbound quota %u bigger than allowed quota %llu \n", + bw_in, wan_quota_in); + ret = 1; + } + else + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Suggested WAN inbound quota %u, allowed quota %llu \n", + bw_in, wan_quota_in); + + if (bw_out > wan_quota_out) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Suggested WAN outbound quota %u bigger than allowed quota %llu \n", + bw_out, wan_quota_out); + ret = 1; + } + else + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Suggested WAN outbound quota %u, allowed quota %llu \n", + bw_out, wan_quota_out); + + if (1 == ret) + { + GNUNET_ATS_suggest_address_cancel (sched_ats, &p[0].id); + GNUNET_SCHEDULER_add_now (&end, NULL); + return; + } + + stage ++; + + GNUNET_ATS_suggest_address_cancel (sched_ats, &p[0].id); + GNUNET_ATS_suggest_address (sched_ats, &p[1].id); + return; + } + if (1 == stage) + { + if (GNUNET_OK == compare_addresses (address, session, &test_hello_address[1], test_session[1])) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stage %u: Callback with correct address `%s'\n", + stage, + GNUNET_i2s (&address->peer)); + ret = 0; + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stage %u: Callback with invalid address `%s'\n", + stage, + GNUNET_i2s (&address->peer)); + ret = 1; + } + + if (GNUNET_OK != compare_ats(atsi, ats_count, test_ats_info, test_ats_count)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Stage %u: Callback with incorrect ats info \n", + stage); + ret = 1; + } + + if (bw_in > wan_quota_in) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Suggested WAN inbound quota %u bigger than allowed quota %llu \n", + bw_in, wan_quota_in); + ret = 1; + } + else + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Suggested WAN inbound quota %u, allowed quota %llu \n", + bw_in, wan_quota_in); + + if (bw_out > wan_quota_out) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Suggested WAN outbound quota %u bigger than allowed quota %llu \n", + bw_out, wan_quota_out); + ret = 1; + } + else + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Suggested WAN outbound quota %u, allowed quota %llu \n", + bw_out, wan_quota_out); + + if (1 == ret) + { + GNUNET_ATS_suggest_address_cancel (sched_ats, &p[0].id); + GNUNET_SCHEDULER_add_now (&end, NULL); + return; + } + + stage ++; + GNUNET_ATS_suggest_address_cancel (sched_ats, &p[1].id); + GNUNET_SCHEDULER_add_now (&end, NULL); + + return; + } +} + +static void +sleep_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + GNUNET_ATS_suggest_address (sched_ats, &p[0].id); +} + +static void +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) +{ + char *quota_str; + + if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_string(cfg, "ats", "WAN_QUOTA_OUT", "a_str)) + { + fprintf (stderr, "Cannot load WAN outbound quota from configuration, exit!\n"); + ret = 1; + return; + } + if (GNUNET_SYSERR == GNUNET_STRINGS_fancy_size_to_bytes (quota_str, &wan_quota_out)) + { + fprintf (stderr, "Cannot load WAN outbound quota from configuration, exit!\n"); + ret = 1; + GNUNET_free (quota_str); + return; + } + GNUNET_free (quota_str); + quota_str = NULL; + + if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_string(cfg, "ats", "WAN_QUOTA_IN", "a_str)) + { + fprintf (stderr, "Cannot load WAN inbound quota from configuration, exit!\n"); + ret = 1; + return; + } + if (GNUNET_SYSERR == GNUNET_STRINGS_fancy_size_to_bytes (quota_str, &wan_quota_in)) + { + fprintf (stderr, "Cannot load WAN inbound quota from configuration, exit!\n"); + GNUNET_free (quota_str); + ret = 1; + return; + } + GNUNET_free (quota_str); + quota_str = NULL; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Configured WAN inbound quota: %llu\n", wan_quota_in); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Configured WAN outbound quota: %llu\n", wan_quota_out); + + + die_task = GNUNET_SCHEDULER_add_delayed (TIMEOUT, &end_badly, NULL); + + /* Connect to ATS scheduling */ + sched_ats = GNUNET_ATS_scheduling_init (cfg, &address_suggest_cb, NULL); + if (sched_ats == NULL) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Could not connect to ATS scheduling!\n"); + ret = 1; + end (); + return; + } + + perf_ats = GNUNET_ATS_performance_init (cfg, NULL, NULL); + if (perf_ats == NULL) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Could not connect to ATS performance!\n"); + ret = 1; + end (); + return; + } + + /* Set up peer 0 */ + if (GNUNET_SYSERR == GNUNET_CRYPTO_hash_from_string(PEERID0, &p[0].id.hashPubKey)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Could not setup peer!\n"); + ret = GNUNET_SYSERR; + end (); + return; + } + + GNUNET_assert (0 == strcmp (PEERID0, GNUNET_i2s_full (&p[0].id))); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Created peer `%s'\n", + GNUNET_i2s(&p[0].id)); + + + /* Set up peer 0 */ + if (GNUNET_SYSERR == GNUNET_CRYPTO_hash_from_string(PEERID1, &p[1].id.hashPubKey)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Could not setup peer!\n"); + ret = GNUNET_SYSERR; + end (); + return; + } + + GNUNET_assert (0 == strcmp (PEERID1, GNUNET_i2s_full (&p[1].id))); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Created peer `%s'\n", + GNUNET_i2s(&p[1].id)); + + /* Prepare ATS Information */ + test_ats_info[0].type = htonl (GNUNET_ATS_NETWORK_TYPE); + test_ats_info[0].value = htonl(GNUNET_ATS_NET_WAN); + test_ats_info[1].type = htonl (GNUNET_ATS_QUALITY_NET_DISTANCE); + test_ats_info[1].value = htonl(1); + test_ats_count = 2; + + /* Adding address with session */ + test_session[0] = &test_addr[0]; + create_test_address (&test_addr[0], "test0", test_session[0], "test0", strlen ("test0") + 1); + test_hello_address[0].peer = p[0].id; + test_hello_address[0].transport_name = test_addr[0].plugin; + test_hello_address[0].address = test_addr[0].addr; + test_hello_address[0].address_length = test_addr[0].addr_len; + GNUNET_ATS_address_add (sched_ats, &test_hello_address[0], test_session[0], test_ats_info, test_ats_count); + + + /* Adding address with session */ + test_session[1] = &test_addr[1]; + create_test_address (&test_addr[1], "test1", test_session[1], "test1", strlen ("test1") + 1); + test_hello_address[1].peer = p[1].id; + test_hello_address[1].transport_name = test_addr[0].plugin; + test_hello_address[1].address = test_addr[0].addr; + test_hello_address[1].address_length = test_addr[0].addr_len; + GNUNET_ATS_address_add (sched_ats, &test_hello_address[1], test_session[1], test_ats_info, test_ats_count); + + + /* Change bandwidth preference */ + GNUNET_ATS_change_preference (perf_ats, + &p[0].id, + GNUNET_ATS_PREFERENCE_BANDWIDTH,(double) 1000, GNUNET_ATS_PREFERENCE_END); + GNUNET_ATS_change_preference (perf_ats, + &p[1].id, + GNUNET_ATS_PREFERENCE_BANDWIDTH,(double) 1000, GNUNET_ATS_PREFERENCE_END); + + + /* Change latency preference */ + + GNUNET_ATS_change_preference (perf_ats, + &p[0].id, + GNUNET_ATS_PREFERENCE_LATENCY,(double) 10, GNUNET_ATS_PREFERENCE_END); + GNUNET_ATS_change_preference (perf_ats, + &p[1].id, + GNUNET_ATS_PREFERENCE_LATENCY,(double) 100, GNUNET_ATS_PREFERENCE_END); + GNUNET_SCHEDULER_add_delayed (SLEEP, &sleep_task, NULL); +} + + +int +main (int argc, char *argv[]) +{ + if (0 != GNUNET_TESTING_peer_run ("test_ats_simplistic_change_preference", + "test_ats_api.conf", + &run, NULL)) + return 1; + return ret; +} + + +/* end of file test_ats_simplistic_change_preference.c */ diff --git a/src/ats/test_ats_simplistic_pref_aging.c b/src/ats/test_ats_simplistic_pref_aging.c new file mode 100644 index 0000000..8591ef1 --- /dev/null +++ b/src/ats/test_ats_simplistic_pref_aging.c @@ -0,0 +1,448 @@ +/* + This file is part of GNUnet. + (C) 2010,2011 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ +/** + * @file ats/test_ats_mlp.c + * @brief test for the MLP solver + * @author Christian Grothoff + * @author Matthias Wachs + + */ +/** + * @file ats/test_ats_api_scheduling_add_address.c + * @brief test for ats simplistic solver preference aging: + * Add 2 addresses and set high preference for one. Expect higher bw for this + * address, wait. Preferences should age and so bw assigned should decrease. + * @author Christian Grothoff + * @author Matthias Wachs + */ +#include "platform.h" +#include "gnunet_ats_service.h" +#include "gnunet_testing_lib.h" +#include "ats.h" +#include "test_ats_api_common.h" + +#define DEBUG_ATS_INFO GNUNET_NO + +static GNUNET_SCHEDULER_TaskIdentifier die_task; + +/** + * Scheduling handle + */ +static struct GNUNET_ATS_SchedulingHandle *sched_ats; + +/** + * Performance handle + */ +static struct GNUNET_ATS_PerformanceHandle *perf_ats; + +/** + * Return value + */ +static int ret; + +/** + * Test address + */ +static struct Test_Address test_addr[2]; + +/** + * Test peer + */ +static struct PeerContext p[2]; + + +/** + * HELLO address + */ +struct GNUNET_HELLO_Address test_hello_address[2]; + +/** + * Session + */ +static void *test_session[2]; + +/** + * Test ats info + */ +struct GNUNET_ATS_Information test_ats_info[2]; + +/** + * Test ats count + */ +uint32_t test_ats_count; + +/** + * Configured WAN out quota + */ +unsigned long long wan_quota_out; + +/** + * Configured WAN in quota + */ +unsigned long long wan_quota_in; + + +static void +end_badly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + die_task = GNUNET_SCHEDULER_NO_TASK; + + if (sched_ats != NULL) + { + GNUNET_ATS_scheduling_done (sched_ats); + sched_ats = NULL; + } + if (perf_ats != NULL) + { + GNUNET_ATS_performance_done (perf_ats); + perf_ats = NULL; + } + free_test_address (&test_addr[0]); + ret = GNUNET_SYSERR; +} + + +static void +end () +{ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Shutting down\n"); + if (die_task != GNUNET_SCHEDULER_NO_TASK) + { + GNUNET_SCHEDULER_cancel (die_task); + die_task = GNUNET_SCHEDULER_NO_TASK; + } + + GNUNET_ATS_suggest_address_cancel (sched_ats, &p[0].id); + GNUNET_ATS_suggest_address_cancel (sched_ats, &p[1].id); + + if (NULL != sched_ats) + GNUNET_ATS_scheduling_done (sched_ats); + if (NULL != perf_ats) + GNUNET_ATS_performance_done (perf_ats); + sched_ats = NULL; + perf_ats = NULL; + free_test_address (&test_addr[0]); + free_test_address (&test_addr[1]); +} + + +static void +address_suggest_cb (void *cls, const struct GNUNET_HELLO_Address *address, + struct Session *session, + struct GNUNET_BANDWIDTH_Value32NBO bandwidth_out, + struct GNUNET_BANDWIDTH_Value32NBO bandwidth_in, + const struct GNUNET_ATS_Information *atsi, + uint32_t ats_count) +{ + static int stage = 0; + static int sug_p0 = GNUNET_NO; + static int sug_p1 = GNUNET_NO; + + static uint32_t p0_last_bandwidth_out; + static uint32_t p0_last_bandwidth_in; + + static uint32_t p1_last_bandwidth_out; + static uint32_t p1_last_bandwidth_in; + + uint32_t cur_bandwidth_out = ntohl (bandwidth_out.value__); + uint32_t cur_bandwidth_in = ntohl (bandwidth_in.value__); + + if (0 == stage) + { + /* Callback for initial suggestion */ + if (0 == memcmp (&address->peer, &p[0].id, sizeof (p[0].id))) + { + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Stage %u: Callback for peer 0 `%s': (in/out) %llu/%llu\n", + stage, + GNUNET_i2s (&address->peer), + ntohl (bandwidth_in.value__), + ntohl (bandwidth_out.value__)); + sug_p0 = GNUNET_YES; + p0_last_bandwidth_out = ntohl(bandwidth_out.value__); + p0_last_bandwidth_in = ntohl(bandwidth_in.value__); + } + if (0 == memcmp (&address->peer, &p[1].id, sizeof (p[1].id))) + { + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Stage %u: Callback for peer 1 `%s': (in/out) %llu/%llu\n", + stage, + GNUNET_i2s (&address->peer), + ntohl (bandwidth_in.value__), + ntohl (bandwidth_out.value__)); + sug_p1 = GNUNET_YES; + p1_last_bandwidth_out = ntohl(bandwidth_out.value__); + p1_last_bandwidth_in = ntohl(bandwidth_in.value__); + } + if ((GNUNET_YES == sug_p0) && (GNUNET_YES == sug_p1)) + { + /* Changing preference for peer 0 */ + stage ++; + GNUNET_ATS_change_preference (perf_ats, &p[0].id, GNUNET_ATS_PREFERENCE_BANDWIDTH,(double) 1000, GNUNET_ATS_PREFERENCE_END); + sug_p0 = GNUNET_NO; + sug_p1 = GNUNET_NO; + return; + } + + } + if (1 == stage) + { + /* Callback due to preference change */ + if (0 == memcmp (&address->peer, &p[0].id, sizeof (p[0].id))) + { + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Stage %u: Callback for peer 0 `%s': (in/out) %llu/%llu\n", + stage, + GNUNET_i2s (&address->peer), + ntohl (bandwidth_in.value__), + ntohl (bandwidth_out.value__)); + sug_p0 = GNUNET_YES; + + /* Peer 0 should get more bandwidth */ + if (cur_bandwidth_out <= p0_last_bandwidth_out) + GNUNET_break (0); + if (cur_bandwidth_in <= p0_last_bandwidth_in) + GNUNET_break (0); + p0_last_bandwidth_out = ntohl(bandwidth_out.value__); + p0_last_bandwidth_in = ntohl(bandwidth_in.value__); + } + if (0 == memcmp (&address->peer, &p[1].id, sizeof (p[1].id))) + { + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Stage %u: Callback for peer 1 `%s': (in/out) %llu/%llu\n", + stage, + GNUNET_i2s (&address->peer), + ntohl (bandwidth_in.value__), + ntohl (bandwidth_out.value__)); + sug_p1 = GNUNET_YES; + + /* Peer 1 should get less bandwidth */ + if (cur_bandwidth_out >= p1_last_bandwidth_out) + { + GNUNET_break (0); + goto error; + } + if (cur_bandwidth_in >= p1_last_bandwidth_in) + { + GNUNET_break (0); + goto error; + } + p1_last_bandwidth_out = ntohl(bandwidth_out.value__); + p1_last_bandwidth_in = ntohl(bandwidth_in.value__); + } + if ((GNUNET_YES == sug_p0) && (GNUNET_YES == sug_p1)) + { + stage ++; + sug_p0 = GNUNET_NO; + sug_p1 = GNUNET_NO; + return; + } + } + if (2 == stage) + { + /* Callback due to preference aging */ + if (0 == memcmp (&address->peer, &p[0].id, sizeof (p[0].id))) + { + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Stage %u: Callback for peer 0 `%s': (in/out) %llu/%llu\n", + stage, + GNUNET_i2s (&address->peer), + ntohl (bandwidth_in.value__), + ntohl (bandwidth_out.value__)); + sug_p0 = GNUNET_YES; + + /* Peer 0 should get less bandwidth */ + if (cur_bandwidth_out <= p0_last_bandwidth_out) + GNUNET_break (0); + if (cur_bandwidth_in <= p0_last_bandwidth_in) + GNUNET_break (0); + p0_last_bandwidth_out = ntohl(bandwidth_out.value__); + p0_last_bandwidth_in = ntohl(bandwidth_in.value__); + } + if (0 == memcmp (&address->peer, &p[1].id, sizeof (p[1].id))) + { + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Stage %u: Callback for peer 1 `%s': (in/out) %llu/%llu\n", + stage, + GNUNET_i2s (&address->peer), + ntohl (bandwidth_in.value__), + ntohl (bandwidth_out.value__)); + sug_p1 = GNUNET_YES; + /* Peer 1 should get more bandwidth */ + if (cur_bandwidth_out <= p1_last_bandwidth_out) + { + GNUNET_break (0); + goto error; + } + if (cur_bandwidth_in <= p1_last_bandwidth_in) + { + GNUNET_break (0); + goto error; + } + p0_last_bandwidth_out = ntohl(bandwidth_out.value__); + p0_last_bandwidth_in = ntohl(bandwidth_in.value__); + } + + if ((GNUNET_YES == sug_p0) && (GNUNET_YES == sug_p1)) + { + /* Done ! */ + stage ++; + ret = 0; + GNUNET_SCHEDULER_add_now (&end,NULL); + return; + } + } + return; + +error: + /* Error ! */ + ret = 1; + GNUNET_SCHEDULER_add_now (&end,NULL); +} + +static void +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) +{ + char *quota_str; + + if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_string(cfg, "ats", "WAN_QUOTA_OUT", "a_str)) + { + fprintf (stderr, "Cannot load WAN outbound quota from configuration, exit!\n"); + ret = 1; + return; + } + if (GNUNET_SYSERR == GNUNET_STRINGS_fancy_size_to_bytes (quota_str, &wan_quota_out)) + { + fprintf (stderr, "Cannot load WAN outbound quota from configuration, exit!\n"); + ret = 1; + GNUNET_free (quota_str); + return; + } + GNUNET_free (quota_str); + quota_str = NULL; + + if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_string(cfg, "ats", "WAN_QUOTA_IN", "a_str)) + { + fprintf (stderr, "Cannot load WAN inbound quota from configuration, exit!\n"); + ret = 1; + return; + } + if (GNUNET_SYSERR == GNUNET_STRINGS_fancy_size_to_bytes (quota_str, &wan_quota_in)) + { + fprintf (stderr, "Cannot load WAN inbound quota from configuration, exit!\n"); + GNUNET_free (quota_str); + ret = 1; + return; + } + GNUNET_free (quota_str); + quota_str = NULL; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Configured WAN inbound quota: %llu\n", wan_quota_in); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Configured WAN outbound quota: %llu\n", wan_quota_out); + + + die_task = GNUNET_SCHEDULER_add_delayed (TIMEOUT, &end_badly, NULL); + + /* Connect to ATS scheduling */ + sched_ats = GNUNET_ATS_scheduling_init (cfg, &address_suggest_cb, NULL); + if (sched_ats == NULL) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Could not connect to ATS scheduling!\n"); + ret = 1; + end (); + return; + } + + /* Connect to ATS performance */ + perf_ats = GNUNET_ATS_performance_init(cfg, NULL, NULL); + if (sched_ats == NULL) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Could not connect to ATS scheduling!\n"); + ret = 1; + end (); + return; + } + + + /* Set up peer 0 */ + if (GNUNET_SYSERR == GNUNET_CRYPTO_hash_from_string(PEERID0, &p[0].id.hashPubKey)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Could not setup peer!\n"); + ret = GNUNET_SYSERR; + end (); + return; + } + + GNUNET_assert (0 == strcmp (PEERID0, GNUNET_i2s_full (&p[0].id))); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Created peer `%s'\n", + GNUNET_i2s(&p[0].id)); + + /* Set up peer 1*/ + if (GNUNET_SYSERR == GNUNET_CRYPTO_hash_from_string(PEERID1, &p[1].id.hashPubKey)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Could not setup peer!\n"); + ret = GNUNET_SYSERR; + end (); + return; + } + + GNUNET_assert (0 == strcmp (PEERID1, GNUNET_i2s_full (&p[1].id))); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Created peer `%s'\n", + GNUNET_i2s(&p[1].id)); + + /* Prepare ATS Information */ + test_ats_info[0].type = htonl (GNUNET_ATS_NETWORK_TYPE); + test_ats_info[0].value = htonl(GNUNET_ATS_NET_WAN); + test_ats_info[1].type = htonl (GNUNET_ATS_QUALITY_NET_DISTANCE); + test_ats_info[1].value = htonl(1); + test_ats_count = 2; + + /* Peer 0: Adding address with session */ + test_session[0] = &test_addr[0]; + create_test_address (&test_addr[0], "test0", test_session[0], "test0", strlen ("test0") + 1); + test_hello_address[0].peer = p[0].id; + test_hello_address[0].transport_name = test_addr[0].plugin; + test_hello_address[0].address = test_addr[0].addr; + test_hello_address[0].address_length = test_addr[0].addr_len; + GNUNET_ATS_address_add (sched_ats, &test_hello_address[0], test_session[0], test_ats_info, test_ats_count); + + /* Peer 1: Adding address with session */ + test_session[1] = &test_addr[1]; + create_test_address (&test_addr[1], "test1", test_session[1], "test1", strlen ("test1") + 1); + test_hello_address[1].peer = p[1].id; + test_hello_address[1].transport_name = test_addr[1].plugin; + test_hello_address[1].address = test_addr[1].addr; + test_hello_address[1].address_length = test_addr[1].addr_len; + GNUNET_ATS_address_add (sched_ats, &test_hello_address[1], test_session[1], test_ats_info, test_ats_count); + + GNUNET_ATS_suggest_address (sched_ats, &p[0].id); + GNUNET_ATS_suggest_address (sched_ats, &p[1].id); +} + + +int +main (int argc, char *argv[]) +{ + if (0 != GNUNET_TESTING_peer_run ("test_ats_simplistic_pref_aging", + "test_ats_api.conf", + &run, NULL)) + return 1; + return ret; +} + + +/* end of file test_ats_simplistic_pref_aging.c */ diff --git a/src/ats/test_ats_simplistic_switch_networks.c b/src/ats/test_ats_simplistic_switch_networks.c new file mode 100644 index 0000000..47a4e44 --- /dev/null +++ b/src/ats/test_ats_simplistic_switch_networks.c @@ -0,0 +1,451 @@ +/* + This file is part of GNUnet. + (C) 2010,2011 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ +/** + * @file ats/test_ats_api_scheduling_update_address.c + * @brief test updating networtk type of an address + * @author Christian Grothoff + * @author Matthias Wachs + */ +#include "platform.h" +#include "gnunet_ats_service.h" +#include "gnunet_testing_lib.h" +#include "ats.h" +#include "test_ats_api_common.h" + +#define BIG_M_STRING "unlimited" + + +static GNUNET_SCHEDULER_TaskIdentifier die_task; + +/** + * Scheduling handle + */ +static struct GNUNET_ATS_SchedulingHandle *sched_ats; + +/** + * Return value + */ +static int ret; + +/** + * Test address + */ +static struct Test_Address test_addr; + +/** + * Test peer + */ +static struct PeerContext p; + +/** + * HELLO test address + */ + +struct GNUNET_HELLO_Address test_hello_address; + +/** + * Test session + */ +static void *test_session; + +/** + * Test ats info + */ +struct GNUNET_ATS_Information test_ats_info[3]; + +/** + * Test ats count + */ +uint32_t test_ats_count; + +unsigned long long int quota_out[GNUNET_ATS_NetworkTypeCount]; +unsigned long long int quota_in[GNUNET_ATS_NetworkTypeCount]; + +static void +end_badly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + die_task = GNUNET_SCHEDULER_NO_TASK; + + if (sched_ats != NULL) + GNUNET_ATS_scheduling_done (sched_ats); + free_test_address (&test_addr); + ret = GNUNET_SYSERR; +} + + +static void +end () +{ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Shutting down\n"); + if (die_task != GNUNET_SCHEDULER_NO_TASK) + { + GNUNET_SCHEDULER_cancel (die_task); + die_task = GNUNET_SCHEDULER_NO_TASK; + } + GNUNET_ATS_scheduling_done (sched_ats); + sched_ats = NULL; + free_test_address (&test_addr); +} + +static uint32_t +find_ats_value (const struct GNUNET_ATS_Information *atsi, + uint32_t ats_count, + uint32_t value) +{ + int c; + for (c = 0; c < ats_count; c ++) + { + if (ntohl(atsi[c].type) == value) + return ntohl (atsi[c].value); + } + GNUNET_break (0); + return UINT32_MAX; +} + + +static void +address_suggest_cb (void *cls, const struct GNUNET_HELLO_Address *address, + struct Session *session, + struct GNUNET_BANDWIDTH_Value32NBO bandwidth_out, + struct GNUNET_BANDWIDTH_Value32NBO bandwidth_in, + const struct GNUNET_ATS_Information *atsi, + uint32_t ats_count) +{ + static int stage = 0; + int level; + char *text; + if (0 == stage) + { + GNUNET_ATS_suggest_address_cancel (sched_ats, &p.id); + if (GNUNET_OK == compare_addresses(address, session, &test_hello_address, test_session)) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stage %u: Callback for correct address `%s'\n", + stage, GNUNET_i2s (&address->peer)); + ret = 0; + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Stage %u: Callback with incorrect address `%s'\n", + stage, GNUNET_i2s (&address->peer)); + ret = 1; + GNUNET_SCHEDULER_add_now (&end, NULL); + return; + } + + if (GNUNET_OK != compare_ats(atsi, ats_count, test_ats_info, test_ats_count)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Stage %u: Callback with incorrect ats info \n", stage); + ret = 1; + GNUNET_SCHEDULER_add_now (&end, NULL); + return; + } + + if (ntohl(bandwidth_out.value__) == quota_out[GNUNET_ATS_NET_WAN]) + { + level = GNUNET_ERROR_TYPE_DEBUG; + text = "correct"; + ret = 0; + } + else + { + level = GNUNET_ERROR_TYPE_ERROR; + text = "wrong"; + ret = 1; + } + + GNUNET_log (level, "Stage %u: WAN outbound quota out %s: Received %llu, configured %llu\n", + stage, + text, + (unsigned long long int) ntohl(bandwidth_out.value__), + quota_out[GNUNET_ATS_NET_WAN]); + + if (ntohl(bandwidth_in.value__) == quota_in[GNUNET_ATS_NET_WAN]) + { + level = GNUNET_ERROR_TYPE_DEBUG; + text = "correct"; + ret = 0; + } + else + { + level = GNUNET_ERROR_TYPE_ERROR; + text = "wrong"; + ret = 1; + } + + GNUNET_log (level, "Stage %u: WAN inbound quota out %s: Received %llu, configured %llu\n", + stage, + text, + (unsigned long long int) ntohl(bandwidth_out.value__), + quota_out[GNUNET_ATS_NET_WAN]); + + if (GNUNET_ATS_NET_WAN != find_ats_value (atsi, ats_count, GNUNET_ATS_NETWORK_TYPE)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Stage %u: Incorrect network type, exptected %s, got %s \n", + stage, + GNUNET_ATS_print_network_type(GNUNET_ATS_NET_WAN), + GNUNET_ATS_print_network_type(find_ats_value (atsi, ats_count, GNUNET_ATS_NETWORK_TYPE))); + ret = 1; + } + + if (1 == ret) + { + GNUNET_SCHEDULER_add_now (&end, NULL); + return; + } + + /* Update address */ + /* Prepare ATS Information: change network */ + test_ats_info[0].type = htonl (GNUNET_ATS_NETWORK_TYPE); + test_ats_info[0].value = htonl(GNUNET_ATS_NET_LAN); + test_ats_info[1].type = htonl (GNUNET_ATS_QUALITY_NET_DISTANCE); + test_ats_info[1].value = htonl(3); + test_ats_info[1].type = htonl (GNUNET_ATS_QUALITY_NET_DELAY); + test_ats_info[1].value = htonl(30); + test_ats_count = 2; + + GNUNET_ATS_address_update (sched_ats, &test_hello_address, test_session, test_ats_info, test_ats_count); + + /* Request address */ + GNUNET_ATS_suggest_address (sched_ats, &p.id); + stage ++; + } + else if (1 == stage) + { + GNUNET_ATS_suggest_address_cancel (sched_ats, &p.id); + if (GNUNET_OK == compare_addresses(address, session, &test_hello_address, test_session)) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stage %u: Callback with correct address `%s'\n", stage, + GNUNET_i2s (&address->peer)); + ret = 0; + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Stage %u: Callback with incorrect address `%s'\n", stage, + GNUNET_i2s (&address->peer)); + ret = 1; + } + + if (GNUNET_OK != compare_ats(atsi, ats_count, test_ats_info, test_ats_count)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Stage %u: Callback with incorrect ats info \n"); + ret = 1; + GNUNET_SCHEDULER_add_now (&end, NULL); + return; + } + + if (ntohl(bandwidth_out.value__) == quota_out[GNUNET_ATS_NET_LAN]) + { + level = GNUNET_ERROR_TYPE_DEBUG; + text = "correct"; + ret = 0; + } + else + { + level = GNUNET_ERROR_TYPE_ERROR; + text = "wrong"; + ret = 1; + } + + GNUNET_log (level, "Stage %u: LAN outbound quota out %s: Received %llu, configured %llu\n", + stage, + text, + (unsigned long long int) ntohl(bandwidth_out.value__), + quota_out[GNUNET_ATS_NET_LAN]); + + if (ntohl(bandwidth_in.value__) == quota_in[GNUNET_ATS_NET_LAN]) + { + level = GNUNET_ERROR_TYPE_DEBUG; + text = "correct"; + ret = 0; + } + else + { + level = GNUNET_ERROR_TYPE_ERROR; + text = "wrong"; + ret = 1; + } + + GNUNET_log (level, "Stage %u: LAN inbound quota out %s: Received %llu, configured %llu\n", + stage, + text, + (unsigned long long int) ntohl(bandwidth_out.value__), + quota_out[GNUNET_ATS_NET_LAN]); + + if (GNUNET_ATS_NET_LAN != find_ats_value (atsi, ats_count, GNUNET_ATS_NETWORK_TYPE)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Stage %u: Incorrect network type, exptected %s, got %s \n", + stage, + GNUNET_ATS_print_network_type(GNUNET_ATS_NET_LAN), + GNUNET_ATS_print_network_type(find_ats_value (atsi, ats_count, GNUNET_ATS_NETWORK_TYPE))); + ret = 1; + } + + GNUNET_SCHEDULER_add_now (&end, NULL); + } +} + +static unsigned int +load_quotas (const struct GNUNET_CONFIGURATION_Handle *cfg, unsigned long long *out_dest, unsigned long long *in_dest, int dest_length) +{ + int quotas[GNUNET_ATS_NetworkTypeCount] = GNUNET_ATS_NetworkType; + char * entry_in = NULL; + char * entry_out = NULL; + char * quota_out_str; + char * quota_in_str; + int c; + + for (c = 0; (c < GNUNET_ATS_NetworkTypeCount) && (c < dest_length); c++) + { + in_dest[c] = 0; + out_dest[c] = 0; + switch (quotas[c]) { + case GNUNET_ATS_NET_UNSPECIFIED: + entry_out = "UNSPECIFIED_QUOTA_OUT"; + entry_in = "UNSPECIFIED_QUOTA_IN"; + break; + case GNUNET_ATS_NET_LOOPBACK: + entry_out = "LOOPBACK_QUOTA_OUT"; + entry_in = "LOOPBACK_QUOTA_IN"; + break; + case GNUNET_ATS_NET_LAN: + entry_out = "LAN_QUOTA_OUT"; + entry_in = "LAN_QUOTA_IN"; + break; + case GNUNET_ATS_NET_WAN: + entry_out = "WAN_QUOTA_OUT"; + entry_in = "WAN_QUOTA_IN"; + break; + case GNUNET_ATS_NET_WLAN: + entry_out = "WLAN_QUOTA_OUT"; + entry_in = "WLAN_QUOTA_IN"; + break; + default: + break; + } + + if ((entry_in == NULL) || (entry_out == NULL)) + continue; + + /* quota out */ + if (GNUNET_OK == GNUNET_CONFIGURATION_get_value_string(cfg, "ats", entry_out, "a_out_str)) + { + if (0 == strcmp(quota_out_str, BIG_M_STRING) || + (GNUNET_SYSERR == GNUNET_STRINGS_fancy_size_to_bytes (quota_out_str, &out_dest[c]))) + out_dest[c] = UINT32_MAX; + + GNUNET_free (quota_out_str); + quota_out_str = NULL; + } + else if (GNUNET_ATS_NET_UNSPECIFIED == quotas[c]) + out_dest[c] = UINT32_MAX; + else + out_dest[c] = UINT32_MAX; + + /* quota in */ + if (GNUNET_OK == GNUNET_CONFIGURATION_get_value_string(cfg, "ats", entry_in, "a_in_str)) + { + if (0 == strcmp(quota_in_str, BIG_M_STRING) || + (GNUNET_SYSERR == GNUNET_STRINGS_fancy_size_to_bytes (quota_in_str, &in_dest[c]))) + in_dest[c] = UINT32_MAX; + + GNUNET_free (quota_in_str); + quota_in_str = NULL; + } + else if (GNUNET_ATS_NET_UNSPECIFIED == quotas[c]) + { + in_dest[c] = UINT32_MAX; + } + else + { + in_dest[c] = UINT32_MAX; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Loaded quota: %s %u, %s %u\n", entry_in, in_dest[c], entry_out, out_dest[c]); + + } + return GNUNET_ATS_NetworkTypeCount; +} + +static void +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) +{ + die_task = GNUNET_SCHEDULER_add_delayed (TIMEOUT, &end_badly, NULL); + + load_quotas (cfg, quota_out, quota_in, GNUNET_ATS_NetworkTypeCount); + + /* Connect to ATS scheduling */ + sched_ats = GNUNET_ATS_scheduling_init (cfg, &address_suggest_cb, NULL); + if (sched_ats == NULL) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Could not connect to ATS scheduling!\n"); + ret = 1; + end (); + return; + } + + /* Set up peer */ + if (GNUNET_SYSERR == GNUNET_CRYPTO_hash_from_string(PEERID0, &p.id.hashPubKey)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Could not setup peer!\n"); + ret = GNUNET_SYSERR; + end (); + return; + } + + GNUNET_assert (0 == strcmp (PEERID0, GNUNET_i2s_full (&p.id))); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Created peer `%s'\n", + GNUNET_i2s_full(&p.id)); + + /* Prepare ATS Information */ + test_ats_info[0].type = htonl (GNUNET_ATS_NETWORK_TYPE); + test_ats_info[0].value = htonl(GNUNET_ATS_NET_WAN); + test_ats_info[1].type = htonl (GNUNET_ATS_QUALITY_NET_DISTANCE); + test_ats_info[1].value = htonl(1); + test_ats_info[1].type = htonl (GNUNET_ATS_QUALITY_NET_DELAY); + test_ats_info[1].value = htonl(10); + test_ats_count = 2; + + /* Adding address without session */ + test_session = &test_addr; + create_test_address (&test_addr, "test", &test_addr, "test", strlen ("test") + 1); + test_hello_address.peer = p.id; + test_hello_address.transport_name = test_addr.plugin; + test_hello_address.address = test_addr.addr; + test_hello_address.address_length = test_addr.addr_len; + GNUNET_ATS_address_add (sched_ats, &test_hello_address, test_session, test_ats_info, test_ats_count); + + /* Request address */ + GNUNET_ATS_suggest_address (sched_ats, &p.id); +} + + +int +main (int argc, char *argv[]) +{ + if (0 != GNUNET_TESTING_peer_run ("test_ats_api_scheduling_update_address", + "test_ats_api.conf", + &run, NULL)) + return 1; + return ret; +} + +/* end of file test_ats_api_scheduling_update_address.c */ diff --git a/src/block/Makefile.am b/src/block/Makefile.am index 78680ee..d0a5ae7 100644 --- a/src/block/Makefile.am +++ b/src/block/Makefile.am @@ -20,15 +20,20 @@ plugin_LTLIBRARIES = \ libgnunet_plugin_block_template_la_SOURCES = \ plugin_block_template.c libgnunet_plugin_block_template_la_LIBADD = \ - $(top_builddir)/src/util/libgnunetutil.la + $(top_builddir)/src/block/libgnunetblock.la \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(LTLIBINTL) libgnunet_plugin_block_template_la_LDFLAGS = \ $(GN_PLUGIN_LDFLAGS) +libgnunet_plugin_block_template_la_DEPENDENCIES = \ + libgnunetblock.la libgnunet_plugin_block_test_la_SOURCES = \ plugin_block_test.c libgnunet_plugin_block_test_la_LIBADD = \ $(top_builddir)/src/block/libgnunetblock.la \ - $(top_builddir)/src/util/libgnunetutil.la + $(top_builddir)/src/util/libgnunetutil.la \ + $(LTLIBINTL) libgnunet_plugin_block_test_la_LDFLAGS = \ $(GN_PLUGIN_LDFLAGS) libgnunet_plugin_block_test_la_DEPENDENCIES = \ @@ -38,21 +43,9 @@ libgnunet_plugin_block_test_la_DEPENDENCIES = \ libgnunetblock_la_SOURCES = \ block.c libgnunetblock_la_LIBADD = \ - $(top_builddir)/src/util/libgnunetutil.la + $(top_builddir)/src/util/libgnunetutil.la libgnunetblock_la_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la libgnunetblock_la_LDFLAGS = \ $(GN_LIB_LDFLAGS) \ -version-info 0:0:0 - -check_PROGRAMS = \ - test_block - -#TESTS = $(check_PROGRAMS) - -test_block_SOURCES = \ - test_block.c -test_block_LDADD = \ - $(top_builddir)/src/block/libgnunetblock.la \ - $(top_builddir)/src/util/libgnunetutil.la - diff --git a/src/block/Makefile.in b/src/block/Makefile.in index 37701e8..03ff751 100644 --- a/src/block/Makefile.in +++ b/src/block/Makefile.in @@ -1,9 +1,9 @@ -# Makefile.in generated by automake 1.11.1 from Makefile.am. +# Makefile.in generated by automake 1.11.6 from Makefile.am. # @configure_input@ # Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, -# 2003, 2004, 2005, 2006, 2007, 2008, 2009 Free Software Foundation, -# Inc. +# 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Free Software +# Foundation, Inc. # This Makefile.in is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. @@ -16,6 +16,23 @@ @SET_MAKE@ VPATH = @srcdir@ +am__make_dryrun = \ + { \ + am__dry=no; \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + echo 'am--echo: ; @echo "AM" OK' | $(MAKE) -f - 2>/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } pkgdatadir = $(datadir)/@PACKAGE@ pkgincludedir = $(includedir)/@PACKAGE@ pkglibdir = $(libdir)/@PACKAGE@ @@ -35,20 +52,20 @@ POST_UNINSTALL = : build_triplet = @build@ host_triplet = @host@ target_triplet = @target@ -check_PROGRAMS = test_block$(EXEEXT) subdir = src/block DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 am__aclocal_m4_deps = $(top_srcdir)/m4/absolute-header.m4 \ $(top_srcdir)/m4/align.m4 $(top_srcdir)/m4/argz.m4 \ - $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/iconv.m4 \ - $(top_srcdir)/m4/lib-ld.m4 $(top_srcdir)/m4/lib-link.m4 \ - $(top_srcdir)/m4/lib-prefix.m4 $(top_srcdir)/m4/libcurl.m4 \ - $(top_srcdir)/m4/libgcrypt.m4 $(top_srcdir)/m4/libtool.m4 \ - $(top_srcdir)/m4/libunistring.m4 $(top_srcdir)/m4/ltdl.m4 \ - $(top_srcdir)/m4/ltoptions.m4 $(top_srcdir)/m4/ltsugar.m4 \ - $(top_srcdir)/m4/ltversion.m4 $(top_srcdir)/m4/lt~obsolete.m4 \ - $(top_srcdir)/m4/nls.m4 $(top_srcdir)/m4/po.m4 \ + $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/glib-2.0.m4 \ + $(top_srcdir)/m4/iconv.m4 $(top_srcdir)/m4/lib-ld.m4 \ + $(top_srcdir)/m4/lib-link.m4 $(top_srcdir)/m4/lib-prefix.m4 \ + $(top_srcdir)/m4/libcurl.m4 $(top_srcdir)/m4/libgcrypt.m4 \ + $(top_srcdir)/m4/libtool.m4 $(top_srcdir)/m4/libunistring.m4 \ + $(top_srcdir)/m4/ltdl.m4 $(top_srcdir)/m4/ltoptions.m4 \ + $(top_srcdir)/m4/ltsugar.m4 $(top_srcdir)/m4/ltversion.m4 \ + $(top_srcdir)/m4/lt~obsolete.m4 $(top_srcdir)/m4/nls.m4 \ + $(top_srcdir)/m4/pkg.m4 $(top_srcdir)/m4/po.m4 \ $(top_srcdir)/m4/progtest.m4 $(top_srcdir)/acinclude.m4 \ $(top_srcdir)/configure.ac am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ @@ -78,16 +95,21 @@ am__nobase_list = $(am__nobase_strip_setup); \ am__base_list = \ sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \ sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g' +am__uninstall_files_from_dir = { \ + test -z "$$files" \ + || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \ + || { echo " ( cd '$$dir' && rm -f" $$files ")"; \ + $(am__cd) "$$dir" && rm -f $$files; }; \ + } am__installdirs = "$(DESTDIR)$(libdir)" "$(DESTDIR)$(plugindir)" LTLIBRARIES = $(lib_LTLIBRARIES) $(plugin_LTLIBRARIES) -libgnunet_plugin_block_template_la_DEPENDENCIES = \ - $(top_builddir)/src/util/libgnunetutil.la +am__DEPENDENCIES_1 = am_libgnunet_plugin_block_template_la_OBJECTS = \ plugin_block_template.lo libgnunet_plugin_block_template_la_OBJECTS = \ $(am_libgnunet_plugin_block_template_la_OBJECTS) -AM_V_lt = $(am__v_lt_$(V)) -am__v_lt_ = $(am__v_lt_$(AM_DEFAULT_VERBOSITY)) +AM_V_lt = $(am__v_lt_@AM_V@) +am__v_lt_ = $(am__v_lt_@AM_DEFAULT_V@) am__v_lt_0 = --silent libgnunet_plugin_block_template_la_LINK = $(LIBTOOL) $(AM_V_lt) \ --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link \ @@ -106,10 +128,6 @@ libgnunetblock_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ $(AM_CFLAGS) $(CFLAGS) $(libgnunetblock_la_LDFLAGS) $(LDFLAGS) \ -o $@ -am_test_block_OBJECTS = test_block.$(OBJEXT) -test_block_OBJECTS = $(am_test_block_OBJECTS) -test_block_DEPENDENCIES = $(top_builddir)/src/block/libgnunetblock.la \ - $(top_builddir)/src/util/libgnunetutil.la DEFAULT_INCLUDES = -I.@am__isrc@ -I$(top_builddir) depcomp = $(SHELL) $(top_srcdir)/depcomp am__depfiles_maybe = depfiles @@ -120,28 +138,33 @@ LTCOMPILE = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) \ $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) \ $(AM_CFLAGS) $(CFLAGS) -AM_V_CC = $(am__v_CC_$(V)) -am__v_CC_ = $(am__v_CC_$(AM_DEFAULT_VERBOSITY)) +AM_V_CC = $(am__v_CC_@AM_V@) +am__v_CC_ = $(am__v_CC_@AM_DEFAULT_V@) am__v_CC_0 = @echo " CC " $@; -AM_V_at = $(am__v_at_$(V)) -am__v_at_ = $(am__v_at_$(AM_DEFAULT_VERBOSITY)) +AM_V_at = $(am__v_at_@AM_V@) +am__v_at_ = $(am__v_at_@AM_DEFAULT_V@) am__v_at_0 = @ CCLD = $(CC) LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ $(AM_LDFLAGS) $(LDFLAGS) -o $@ -AM_V_CCLD = $(am__v_CCLD_$(V)) -am__v_CCLD_ = $(am__v_CCLD_$(AM_DEFAULT_VERBOSITY)) +AM_V_CCLD = $(am__v_CCLD_@AM_V@) +am__v_CCLD_ = $(am__v_CCLD_@AM_DEFAULT_V@) am__v_CCLD_0 = @echo " CCLD " $@; -AM_V_GEN = $(am__v_GEN_$(V)) -am__v_GEN_ = $(am__v_GEN_$(AM_DEFAULT_VERBOSITY)) +AM_V_GEN = $(am__v_GEN_@AM_V@) +am__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@) am__v_GEN_0 = @echo " GEN " $@; SOURCES = $(libgnunet_plugin_block_template_la_SOURCES) \ $(libgnunet_plugin_block_test_la_SOURCES) \ - $(libgnunetblock_la_SOURCES) $(test_block_SOURCES) + $(libgnunetblock_la_SOURCES) DIST_SOURCES = $(libgnunet_plugin_block_template_la_SOURCES) \ $(libgnunet_plugin_block_test_la_SOURCES) \ - $(libgnunetblock_la_SOURCES) $(test_block_SOURCES) + $(libgnunetblock_la_SOURCES) +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac ETAGS = etags CTAGS = ctags DISTFILES = $(DIST_COMMON) $(DIST_SOURCES) $(TEXINFOS) $(EXTRA_DIST) @@ -180,6 +203,10 @@ EXEEXT = @EXEEXT@ EXT_LIBS = @EXT_LIBS@ EXT_LIB_PATH = @EXT_LIB_PATH@ FGREP = @FGREP@ +GLIB_CFLAGS = @GLIB_CFLAGS@ +GLIB_GENMARSHAL = @GLIB_GENMARSHAL@ +GLIB_LIBS = @GLIB_LIBS@ +GLIB_MKENUMS = @GLIB_MKENUMS@ GMSGFMT = @GMSGFMT@ GMSGFMT_015 = @GMSGFMT_015@ GNUNETDNS_GROUP = @GNUNETDNS_GROUP@ @@ -190,6 +217,7 @@ GN_LIBINTL = @GN_LIBINTL@ GN_LIB_LDFLAGS = @GN_LIB_LDFLAGS@ GN_PLUGIN_LDFLAGS = @GN_PLUGIN_LDFLAGS@ GN_USER_HOME_DIR = @GN_USER_HOME_DIR@ +GOBJECT_QUERY = @GOBJECT_QUERY@ GREP = @GREP@ HAVE_LIBUNISTRING = @HAVE_LIBUNISTRING@ INCLTDL = @INCLTDL@ @@ -212,6 +240,8 @@ LIBCURL_CPPFLAGS = @LIBCURL_CPPFLAGS@ LIBGCRYPT_CFLAGS = @LIBGCRYPT_CFLAGS@ LIBGCRYPT_CONFIG = @LIBGCRYPT_CONFIG@ LIBGCRYPT_LIBS = @LIBGCRYPT_LIBS@ +LIBGTOP_CFLAGS = @LIBGTOP_CFLAGS@ +LIBGTOP_LIBS = @LIBGTOP_LIBS@ LIBICONV = @LIBICONV@ LIBINTL = @LIBINTL@ LIBLTDL = @LIBLTDL@ @@ -233,6 +263,7 @@ LT_CONFIG_H = @LT_CONFIG_H@ LT_DLLOADERS = @LT_DLLOADERS@ LT_DLPREOPEN = @LT_DLPREOPEN@ MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ MKDIR_P = @MKDIR_P@ MONKEYPREFIX = @MONKEYPREFIX@ MSGFMT = @MSGFMT@ @@ -242,6 +273,7 @@ MYSQL_CPPFLAGS = @MYSQL_CPPFLAGS@ MYSQL_LDFLAGS = @MYSQL_LDFLAGS@ NM = @NM@ NMEDIT = @NMEDIT@ +NSS_DIR = @NSS_DIR@ OBJC = @OBJC@ OBJCDEPMODE = @OBJCDEPMODE@ OBJCFLAGS = @OBJCFLAGS@ @@ -257,6 +289,7 @@ PACKAGE_TARNAME = @PACKAGE_TARNAME@ PACKAGE_URL = @PACKAGE_URL@ PACKAGE_VERSION = @PACKAGE_VERSION@ PATH_SEPARATOR = @PATH_SEPARATOR@ +PKG_CONFIG = @PKG_CONFIG@ POSTGRES_CPPFLAGS = @POSTGRES_CPPFLAGS@ POSTGRES_LDFLAGS = @POSTGRES_LDFLAGS@ POSUB = @POSUB@ @@ -288,6 +321,7 @@ abs_builddir = @abs_builddir@ abs_srcdir = @abs_srcdir@ abs_top_builddir = @abs_top_builddir@ abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ ac_ct_CC = @ac_ct_CC@ ac_ct_CXX = @ac_ct_CXX@ ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ @@ -310,6 +344,7 @@ datarootdir = @datarootdir@ docdir = @docdir@ dvidir = @dvidir@ exec_prefix = @exec_prefix@ +gitcommand = @gitcommand@ host = @host@ host_alias = @host_alias@ host_cpu = @host_cpu@ @@ -323,7 +358,6 @@ libdir = @libdir@ libexecdir = @libexecdir@ localedir = @localedir@ localstatedir = @localstatedir@ -lt_ECHO = @lt_ECHO@ ltdl_LIBOBJS = @ltdl_LIBOBJS@ ltdl_LTLIBOBJS = @ltdl_LTLIBOBJS@ mandir = @mandir@ @@ -341,6 +375,7 @@ sbindir = @sbindir@ sharedstatedir = @sharedstatedir@ srcdir = @srcdir@ subdirs = @subdirs@ +svnversioncommand = @svnversioncommand@ sys_symbol_underscore = @sys_symbol_underscore@ sysconfdir = @sysconfdir@ target = @target@ @@ -364,17 +399,23 @@ libgnunet_plugin_block_template_la_SOURCES = \ plugin_block_template.c libgnunet_plugin_block_template_la_LIBADD = \ - $(top_builddir)/src/util/libgnunetutil.la + $(top_builddir)/src/block/libgnunetblock.la \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(LTLIBINTL) libgnunet_plugin_block_template_la_LDFLAGS = \ $(GN_PLUGIN_LDFLAGS) +libgnunet_plugin_block_template_la_DEPENDENCIES = \ + libgnunetblock.la + libgnunet_plugin_block_test_la_SOURCES = \ plugin_block_test.c libgnunet_plugin_block_test_la_LIBADD = \ $(top_builddir)/src/block/libgnunetblock.la \ - $(top_builddir)/src/util/libgnunetutil.la + $(top_builddir)/src/util/libgnunetutil.la \ + $(LTLIBINTL) libgnunet_plugin_block_test_la_LDFLAGS = \ $(GN_PLUGIN_LDFLAGS) @@ -386,7 +427,7 @@ libgnunetblock_la_SOURCES = \ block.c libgnunetblock_la_LIBADD = \ - $(top_builddir)/src/util/libgnunetutil.la + $(top_builddir)/src/util/libgnunetutil.la libgnunetblock_la_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la @@ -395,15 +436,6 @@ libgnunetblock_la_LDFLAGS = \ $(GN_LIB_LDFLAGS) \ -version-info 0:0:0 - -#TESTS = $(check_PROGRAMS) -test_block_SOURCES = \ - test_block.c - -test_block_LDADD = \ - $(top_builddir)/src/block/libgnunetblock.la \ - $(top_builddir)/src/util/libgnunetutil.la - all: all-am .SUFFIXES: @@ -440,7 +472,6 @@ $(ACLOCAL_M4): $(am__aclocal_m4_deps) $(am__aclocal_m4_deps): install-libLTLIBRARIES: $(lib_LTLIBRARIES) @$(NORMAL_INSTALL) - test -z "$(libdir)" || $(MKDIR_P) "$(DESTDIR)$(libdir)" @list='$(lib_LTLIBRARIES)'; test -n "$(libdir)" || list=; \ list2=; for p in $$list; do \ if test -f $$p; then \ @@ -448,6 +479,8 @@ install-libLTLIBRARIES: $(lib_LTLIBRARIES) else :; fi; \ done; \ test -z "$$list2" || { \ + echo " $(MKDIR_P) '$(DESTDIR)$(libdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libdir)" || exit 1; \ echo " $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 '$(DESTDIR)$(libdir)'"; \ $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 "$(DESTDIR)$(libdir)"; \ } @@ -471,7 +504,6 @@ clean-libLTLIBRARIES: done install-pluginLTLIBRARIES: $(plugin_LTLIBRARIES) @$(NORMAL_INSTALL) - test -z "$(plugindir)" || $(MKDIR_P) "$(DESTDIR)$(plugindir)" @list='$(plugin_LTLIBRARIES)'; test -n "$(plugindir)" || list=; \ list2=; for p in $$list; do \ if test -f $$p; then \ @@ -479,6 +511,8 @@ install-pluginLTLIBRARIES: $(plugin_LTLIBRARIES) else :; fi; \ done; \ test -z "$$list2" || { \ + echo " $(MKDIR_P) '$(DESTDIR)$(plugindir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(plugindir)" || exit 1; \ echo " $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 '$(DESTDIR)$(plugindir)'"; \ $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 "$(DESTDIR)$(plugindir)"; \ } @@ -500,25 +534,13 @@ clean-pluginLTLIBRARIES: echo "rm -f \"$${dir}/so_locations\""; \ rm -f "$${dir}/so_locations"; \ done -libgnunet_plugin_block_template.la: $(libgnunet_plugin_block_template_la_OBJECTS) $(libgnunet_plugin_block_template_la_DEPENDENCIES) +libgnunet_plugin_block_template.la: $(libgnunet_plugin_block_template_la_OBJECTS) $(libgnunet_plugin_block_template_la_DEPENDENCIES) $(EXTRA_libgnunet_plugin_block_template_la_DEPENDENCIES) $(AM_V_CCLD)$(libgnunet_plugin_block_template_la_LINK) -rpath $(plugindir) $(libgnunet_plugin_block_template_la_OBJECTS) $(libgnunet_plugin_block_template_la_LIBADD) $(LIBS) -libgnunet_plugin_block_test.la: $(libgnunet_plugin_block_test_la_OBJECTS) $(libgnunet_plugin_block_test_la_DEPENDENCIES) +libgnunet_plugin_block_test.la: $(libgnunet_plugin_block_test_la_OBJECTS) $(libgnunet_plugin_block_test_la_DEPENDENCIES) $(EXTRA_libgnunet_plugin_block_test_la_DEPENDENCIES) $(AM_V_CCLD)$(libgnunet_plugin_block_test_la_LINK) -rpath $(plugindir) $(libgnunet_plugin_block_test_la_OBJECTS) $(libgnunet_plugin_block_test_la_LIBADD) $(LIBS) -libgnunetblock.la: $(libgnunetblock_la_OBJECTS) $(libgnunetblock_la_DEPENDENCIES) +libgnunetblock.la: $(libgnunetblock_la_OBJECTS) $(libgnunetblock_la_DEPENDENCIES) $(EXTRA_libgnunetblock_la_DEPENDENCIES) $(AM_V_CCLD)$(libgnunetblock_la_LINK) -rpath $(libdir) $(libgnunetblock_la_OBJECTS) $(libgnunetblock_la_LIBADD) $(LIBS) -clean-checkPROGRAMS: - @list='$(check_PROGRAMS)'; test -n "$$list" || exit 0; \ - echo " rm -f" $$list; \ - rm -f $$list || exit $$?; \ - test -n "$(EXEEXT)" || exit 0; \ - list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ - echo " rm -f" $$list; \ - rm -f $$list -test_block$(EXEEXT): $(test_block_OBJECTS) $(test_block_DEPENDENCIES) - @rm -f test_block$(EXEEXT) - $(AM_V_CCLD)$(LINK) $(test_block_OBJECTS) $(test_block_LDADD) $(LIBS) - mostlyclean-compile: -rm -f *.$(OBJEXT) @@ -528,31 +550,27 @@ distclean-compile: @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/block.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/plugin_block_template.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/plugin_block_test.Plo@am__quote@ -@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_block.Po@am__quote@ .c.o: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c $< .c.obj: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'` @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c `$(CYGPATH_W) '$<'` +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c `$(CYGPATH_W) '$<'` .c.lo: @am__fastdepCC_TRUE@ $(AM_V_CC)$(LTCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LTCOMPILE) -c -o $@ $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LTCOMPILE) -c -o $@ $< mostlyclean-libtool: -rm -f *.lo @@ -643,7 +661,6 @@ distdir: $(DISTFILES) fi; \ done check-am: all-am - $(MAKE) $(AM_MAKEFLAGS) $(check_PROGRAMS) check: check-am all-am: Makefile $(LTLIBRARIES) installdirs: @@ -660,10 +677,15 @@ install-am: all-am installcheck: installcheck-am install-strip: - $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ - install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ - `test -z '$(STRIP)' || \ - echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi mostlyclean-generic: clean-generic: @@ -677,8 +699,8 @@ maintainer-clean-generic: @echo "it deletes files that may require special tools to rebuild." clean: clean-am -clean-am: clean-checkPROGRAMS clean-generic clean-libLTLIBRARIES \ - clean-libtool clean-pluginLTLIBRARIES mostlyclean-am +clean-am: clean-generic clean-libLTLIBRARIES clean-libtool \ + clean-pluginLTLIBRARIES mostlyclean-am distclean: distclean-am -rm -rf ./$(DEPDIR) @@ -746,23 +768,23 @@ ps-am: uninstall-am: uninstall-libLTLIBRARIES uninstall-pluginLTLIBRARIES -.MAKE: check-am install-am install-strip - -.PHONY: CTAGS GTAGS all all-am check check-am clean \ - clean-checkPROGRAMS clean-generic clean-libLTLIBRARIES \ - clean-libtool clean-pluginLTLIBRARIES ctags distclean \ - distclean-compile distclean-generic distclean-libtool \ - distclean-tags distdir dvi dvi-am html html-am info info-am \ - install install-am install-data install-data-am install-dvi \ - install-dvi-am install-exec install-exec-am install-html \ - install-html-am install-info install-info-am \ - install-libLTLIBRARIES install-man install-pdf install-pdf-am \ - install-pluginLTLIBRARIES install-ps install-ps-am \ - install-strip installcheck installcheck-am installdirs \ - maintainer-clean maintainer-clean-generic mostlyclean \ - mostlyclean-compile mostlyclean-generic mostlyclean-libtool \ - pdf pdf-am ps ps-am tags uninstall uninstall-am \ - uninstall-libLTLIBRARIES uninstall-pluginLTLIBRARIES +.MAKE: install-am install-strip + +.PHONY: CTAGS GTAGS all all-am check check-am clean clean-generic \ + clean-libLTLIBRARIES clean-libtool clean-pluginLTLIBRARIES \ + ctags distclean distclean-compile distclean-generic \ + distclean-libtool distclean-tags distdir dvi dvi-am html \ + html-am info info-am install install-am install-data \ + install-data-am install-dvi install-dvi-am install-exec \ + install-exec-am install-html install-html-am install-info \ + install-info-am install-libLTLIBRARIES install-man install-pdf \ + install-pdf-am install-pluginLTLIBRARIES install-ps \ + install-ps-am install-strip installcheck installcheck-am \ + installdirs maintainer-clean maintainer-clean-generic \ + mostlyclean mostlyclean-compile mostlyclean-generic \ + mostlyclean-libtool pdf pdf-am ps ps-am tags uninstall \ + uninstall-am uninstall-libLTLIBRARIES \ + uninstall-pluginLTLIBRARIES # Tell versions [3.59,3.63) of GNU make to not export all variables. diff --git a/src/block/block.c b/src/block/block.c index 51dab78..344038d 100644 --- a/src/block/block.c +++ b/src/block/block.c @@ -78,10 +78,10 @@ struct GNUNET_BLOCK_Context * @param hc where to store the result. */ void -GNUNET_BLOCK_mingle_hash (const GNUNET_HashCode * in, uint32_t mingle_number, - GNUNET_HashCode * hc) +GNUNET_BLOCK_mingle_hash (const struct GNUNET_HashCode * in, uint32_t mingle_number, + struct GNUNET_HashCode * hc) { - GNUNET_HashCode m; + struct GNUNET_HashCode m; GNUNET_CRYPTO_hash (&mingle_number, sizeof (uint32_t), &m); GNUNET_CRYPTO_hash_xor (&m, in, hc); @@ -204,7 +204,7 @@ find_plugin (struct GNUNET_BLOCK_Context *ctx, enum GNUNET_BLOCK_Type type) enum GNUNET_BLOCK_EvaluationResult GNUNET_BLOCK_evaluate (struct GNUNET_BLOCK_Context *ctx, enum GNUNET_BLOCK_Type type, - const GNUNET_HashCode * query, + const struct GNUNET_HashCode * query, struct GNUNET_CONTAINER_BloomFilter **bf, int32_t bf_mutator, const void *xquery, size_t xquery_size, const void *reply_block, @@ -233,7 +233,7 @@ GNUNET_BLOCK_evaluate (struct GNUNET_BLOCK_Context *ctx, int GNUNET_BLOCK_get_key (struct GNUNET_BLOCK_Context *ctx, enum GNUNET_BLOCK_Type type, const void *block, - size_t block_size, GNUNET_HashCode * key) + size_t block_size, struct GNUNET_HashCode * key) { struct GNUNET_BLOCK_PluginFunctions *plugin = find_plugin (ctx, type); @@ -285,11 +285,11 @@ compute_bloomfilter_size (unsigned int entry_count) */ struct GNUNET_CONTAINER_BloomFilter * GNUNET_BLOCK_construct_bloomfilter (int32_t bf_mutator, - const GNUNET_HashCode * seen_results, + const struct GNUNET_HashCode * seen_results, unsigned int seen_results_count) { struct GNUNET_CONTAINER_BloomFilter *bf; - GNUNET_HashCode mhash; + struct GNUNET_HashCode mhash; unsigned int i; size_t nsize; diff --git a/src/block/plugin_block_template.c b/src/block/plugin_block_template.c index 6ed675d..1675fdb 100644 --- a/src/block/plugin_block_template.c +++ b/src/block/plugin_block_template.c @@ -47,12 +47,33 @@ */ static enum GNUNET_BLOCK_EvaluationResult block_plugin_template_evaluate (void *cls, enum GNUNET_BLOCK_Type type, - const GNUNET_HashCode * query, + const struct GNUNET_HashCode * query, struct GNUNET_CONTAINER_BloomFilter **bf, int32_t bf_mutator, const void *xquery, size_t xquery_size, const void *reply_block, size_t reply_block_size) { + struct GNUNET_HashCode chash; + struct GNUNET_HashCode mhash; + /* FIXME: check validity first... */ + + /* mandatory duplicate-detection code... */ + if (NULL != bf) + { + GNUNET_CRYPTO_hash (reply_block, reply_block_size, &chash); + GNUNET_BLOCK_mingle_hash (&chash, bf_mutator, &mhash); + if (NULL != *bf) + { + if (GNUNET_YES == GNUNET_CONTAINER_bloomfilter_test (*bf, &mhash)) + return GNUNET_BLOCK_EVALUATION_OK_DUPLICATE; + } + else + { + *bf = GNUNET_CONTAINER_bloomfilter_init (NULL, 8, 64 /* BLOOMFILTER_K */); + } + GNUNET_CONTAINER_bloomfilter_add (*bf, &mhash); + } + /* FIXME: other stuff here... */ return GNUNET_BLOCK_EVALUATION_TYPE_NOT_SUPPORTED; } @@ -71,7 +92,7 @@ block_plugin_template_evaluate (void *cls, enum GNUNET_BLOCK_Type type, static int block_plugin_template_get_key (void *cls, enum GNUNET_BLOCK_Type type, const void *block, size_t block_size, - GNUNET_HashCode * key) + struct GNUNET_HashCode * key) { return GNUNET_SYSERR; } diff --git a/src/block/plugin_block_test.c b/src/block/plugin_block_test.c index 81e80e3..dacf045 100644 --- a/src/block/plugin_block_test.c +++ b/src/block/plugin_block_test.c @@ -28,8 +28,6 @@ #include "platform.h" #include "gnunet_block_plugin.h" -#define DEBUG_TEST GNUNET_EXTRA_LOGGING - /** * Number of bits we set per entry in the bloomfilter. @@ -54,18 +52,18 @@ */ static enum GNUNET_BLOCK_EvaluationResult block_plugin_test_evaluate (void *cls, enum GNUNET_BLOCK_Type type, - const GNUNET_HashCode * query, + const struct GNUNET_HashCode * query, struct GNUNET_CONTAINER_BloomFilter **bf, int32_t bf_mutator, const void *xquery, size_t xquery_size, const void *reply_block, size_t reply_block_size) { - GNUNET_HashCode chash; - GNUNET_HashCode mhash; + struct GNUNET_HashCode chash; + struct GNUNET_HashCode mhash; - if (type != GNUNET_BLOCK_TYPE_TEST) + if ( GNUNET_BLOCK_TYPE_TEST != type) return GNUNET_BLOCK_EVALUATION_TYPE_NOT_SUPPORTED; - if (xquery_size != 0) + if (0 != xquery_size) { GNUNET_break_op (0); return GNUNET_BLOCK_EVALUATION_REQUEST_INVALID; @@ -106,7 +104,7 @@ block_plugin_test_evaluate (void *cls, enum GNUNET_BLOCK_Type type, static int block_plugin_test_get_key (void *cls, enum GNUNET_BLOCK_Type type, const void *block, size_t block_size, - GNUNET_HashCode * key) + struct GNUNET_HashCode * key) { /* always fails since there is no fixed relationship between * keys and values for test values */ diff --git a/src/block/test_block.c b/src/block/test_block.c deleted file mode 100644 index e57b891..0000000 --- a/src/block/test_block.c +++ /dev/null @@ -1,77 +0,0 @@ -/* - This file is part of GNUnet - (C) 2010 Christian Grothoff (and other contributing authors) - - GNUnet is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published - by the Free Software Foundation; either version 3, or (at your - option) any later version. - - GNUnet is distributed in the hope that it will be useful, but - WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - General Public License for more details. - - You should have received a copy of the GNU General Public License - along with GNUnet; see the file COPYING. If not, write to the - Free Software Foundation, Inc., 59 Temple Place - Suite 330, - Boston, MA 02111-1307, USA. -*/ -/** - * @file block/test_block.c - * @brief test for block.c - * @author Christian Grothoff - */ -#include "platform.h" -#include "gnunet_block_lib.h" - -#define DEBUG GNUNET_EXTRA_LOGGING - -#define VERBOSE GNUNET_NO - -static int -test_fs (struct GNUNET_BLOCK_Context *ctx) -{ - GNUNET_HashCode key; - char block[4]; - - memset (block, 1, sizeof (block)); - if (GNUNET_OK != - GNUNET_BLOCK_get_key (ctx, GNUNET_BLOCK_TYPE_FS_DBLOCK, block, - sizeof (block), &key)) - return 1; - if (GNUNET_BLOCK_EVALUATION_OK_LAST != - GNUNET_BLOCK_evaluate (ctx, GNUNET_BLOCK_TYPE_FS_DBLOCK, &key, NULL, 0, - NULL, 0, block, sizeof (block))) - return 2; - if (GNUNET_BLOCK_EVALUATION_REQUEST_VALID != - GNUNET_BLOCK_evaluate (ctx, GNUNET_BLOCK_TYPE_FS_DBLOCK, &key, NULL, 0, - NULL, 0, NULL, 0)) - return 4; - GNUNET_log_skip (1, GNUNET_NO); - if (GNUNET_BLOCK_EVALUATION_REQUEST_INVALID != - GNUNET_BLOCK_evaluate (ctx, GNUNET_BLOCK_TYPE_FS_DBLOCK, &key, NULL, 0, - "bogus", 5, NULL, 0)) - return 8; - GNUNET_log_skip (0, GNUNET_YES); - return 0; -} - -int -main (int argc, char *argv[]) -{ - int ret; - struct GNUNET_BLOCK_Context *ctx; - struct GNUNET_CONFIGURATION_Handle *cfg; - - GNUNET_log_setup ("test-block", "WARNING", NULL); - cfg = GNUNET_CONFIGURATION_create (); - GNUNET_CONFIGURATION_set_value_string (cfg, "block", "PLUGINS", "fs"); - ctx = GNUNET_BLOCK_context_create (cfg); - ret = test_fs (ctx); - GNUNET_BLOCK_context_destroy (ctx); - GNUNET_CONFIGURATION_destroy (cfg); - if (ret != 0) - FPRINTF (stderr, "Tests failed: %d\n", ret); - return ret; -} diff --git a/src/chat/Makefile.am b/src/chat/Makefile.am index 2132836..af33a8b 100644 --- a/src/chat/Makefile.am +++ b/src/chat/Makefile.am @@ -2,6 +2,8 @@ INCLUDES = -I$(top_srcdir)/src/include pkgcfgdir= $(pkgdatadir)/config.d/ +libexecdir= $(pkglibdir)/libexec/ + pkgcfg_DATA = \ chat.conf @@ -25,8 +27,10 @@ libgnunetchat_la_LDFLAGS = \ $(GN_LIB_LDFLAGS) $(WINFLAGS) \ -version-info 0:0:0 +libexec_PROGRAMS = \ + gnunet-service-chat + bin_PROGRAMS = \ - gnunet-service-chat \ gnunet-chat gnunet_service_chat_SOURCES = \ diff --git a/src/chat/Makefile.in b/src/chat/Makefile.in index fe310ce..014e215 100644 --- a/src/chat/Makefile.in +++ b/src/chat/Makefile.in @@ -1,9 +1,9 @@ -# Makefile.in generated by automake 1.11.1 from Makefile.am. +# Makefile.in generated by automake 1.11.6 from Makefile.am. # @configure_input@ # Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, -# 2003, 2004, 2005, 2006, 2007, 2008, 2009 Free Software Foundation, -# Inc. +# 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Free Software +# Foundation, Inc. # This Makefile.in is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. @@ -18,6 +18,23 @@ VPATH = @srcdir@ +am__make_dryrun = \ + { \ + am__dry=no; \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + echo 'am--echo: ; @echo "AM" OK' | $(MAKE) -f - 2>/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } pkgdatadir = $(datadir)/@PACKAGE@ pkgincludedir = $(includedir)/@PACKAGE@ pkglibdir = $(libdir)/@PACKAGE@ @@ -37,7 +54,8 @@ POST_UNINSTALL = : build_triplet = @build@ host_triplet = @host@ target_triplet = @target@ -bin_PROGRAMS = gnunet-service-chat$(EXEEXT) gnunet-chat$(EXEEXT) +libexec_PROGRAMS = gnunet-service-chat$(EXEEXT) +bin_PROGRAMS = gnunet-chat$(EXEEXT) check_PROGRAMS = test_chat$(EXEEXT) test_chat_acknowledgement$(EXEEXT) \ test_chat_anonymous$(EXEEXT) test_chat_authentication$(EXEEXT) \ test_chat_p2p$(EXEEXT) test_chat_acknowledgement_p2p$(EXEEXT) \ @@ -50,14 +68,15 @@ DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in \ ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 am__aclocal_m4_deps = $(top_srcdir)/m4/absolute-header.m4 \ $(top_srcdir)/m4/align.m4 $(top_srcdir)/m4/argz.m4 \ - $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/iconv.m4 \ - $(top_srcdir)/m4/lib-ld.m4 $(top_srcdir)/m4/lib-link.m4 \ - $(top_srcdir)/m4/lib-prefix.m4 $(top_srcdir)/m4/libcurl.m4 \ - $(top_srcdir)/m4/libgcrypt.m4 $(top_srcdir)/m4/libtool.m4 \ - $(top_srcdir)/m4/libunistring.m4 $(top_srcdir)/m4/ltdl.m4 \ - $(top_srcdir)/m4/ltoptions.m4 $(top_srcdir)/m4/ltsugar.m4 \ - $(top_srcdir)/m4/ltversion.m4 $(top_srcdir)/m4/lt~obsolete.m4 \ - $(top_srcdir)/m4/nls.m4 $(top_srcdir)/m4/po.m4 \ + $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/glib-2.0.m4 \ + $(top_srcdir)/m4/iconv.m4 $(top_srcdir)/m4/lib-ld.m4 \ + $(top_srcdir)/m4/lib-link.m4 $(top_srcdir)/m4/lib-prefix.m4 \ + $(top_srcdir)/m4/libcurl.m4 $(top_srcdir)/m4/libgcrypt.m4 \ + $(top_srcdir)/m4/libtool.m4 $(top_srcdir)/m4/libunistring.m4 \ + $(top_srcdir)/m4/ltdl.m4 $(top_srcdir)/m4/ltoptions.m4 \ + $(top_srcdir)/m4/ltsugar.m4 $(top_srcdir)/m4/ltversion.m4 \ + $(top_srcdir)/m4/lt~obsolete.m4 $(top_srcdir)/m4/nls.m4 \ + $(top_srcdir)/m4/pkg.m4 $(top_srcdir)/m4/po.m4 \ $(top_srcdir)/m4/progtest.m4 $(top_srcdir)/acinclude.m4 \ $(top_srcdir)/configure.ac am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ @@ -87,21 +106,27 @@ am__nobase_list = $(am__nobase_strip_setup); \ am__base_list = \ sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \ sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g' +am__uninstall_files_from_dir = { \ + test -z "$$files" \ + || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \ + || { echo " ( cd '$$dir' && rm -f" $$files ")"; \ + $(am__cd) "$$dir" && rm -f $$files; }; \ + } am__installdirs = "$(DESTDIR)$(libdir)" "$(DESTDIR)$(bindir)" \ - "$(DESTDIR)$(pkgcfgdir)" + "$(DESTDIR)$(libexecdir)" "$(DESTDIR)$(pkgcfgdir)" LTLIBRARIES = $(lib_LTLIBRARIES) libgnunetchat_la_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la am_libgnunetchat_la_OBJECTS = chat.lo libgnunetchat_la_OBJECTS = $(am_libgnunetchat_la_OBJECTS) -AM_V_lt = $(am__v_lt_$(V)) -am__v_lt_ = $(am__v_lt_$(AM_DEFAULT_VERBOSITY)) +AM_V_lt = $(am__v_lt_@AM_V@) +am__v_lt_ = $(am__v_lt_@AM_DEFAULT_V@) am__v_lt_0 = --silent libgnunetchat_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ $(AM_CFLAGS) $(CFLAGS) $(libgnunetchat_la_LDFLAGS) $(LDFLAGS) \ -o $@ -PROGRAMS = $(bin_PROGRAMS) +PROGRAMS = $(bin_PROGRAMS) $(libexec_PROGRAMS) am_gnunet_chat_OBJECTS = gnunet-chat.$(OBJEXT) gnunet_chat_OBJECTS = $(am_gnunet_chat_OBJECTS) am__DEPENDENCIES_1 = @@ -175,21 +200,21 @@ LTCOMPILE = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) \ $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) \ $(AM_CFLAGS) $(CFLAGS) -AM_V_CC = $(am__v_CC_$(V)) -am__v_CC_ = $(am__v_CC_$(AM_DEFAULT_VERBOSITY)) +AM_V_CC = $(am__v_CC_@AM_V@) +am__v_CC_ = $(am__v_CC_@AM_DEFAULT_V@) am__v_CC_0 = @echo " CC " $@; -AM_V_at = $(am__v_at_$(V)) -am__v_at_ = $(am__v_at_$(AM_DEFAULT_VERBOSITY)) +AM_V_at = $(am__v_at_@AM_V@) +am__v_at_ = $(am__v_at_@AM_DEFAULT_V@) am__v_at_0 = @ CCLD = $(CC) LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ $(AM_LDFLAGS) $(LDFLAGS) -o $@ -AM_V_CCLD = $(am__v_CCLD_$(V)) -am__v_CCLD_ = $(am__v_CCLD_$(AM_DEFAULT_VERBOSITY)) +AM_V_CCLD = $(am__v_CCLD_@AM_V@) +am__v_CCLD_ = $(am__v_CCLD_@AM_DEFAULT_V@) am__v_CCLD_0 = @echo " CCLD " $@; -AM_V_GEN = $(am__v_GEN_$(V)) -am__v_GEN_ = $(am__v_GEN_$(AM_DEFAULT_VERBOSITY)) +AM_V_GEN = $(am__v_GEN_@AM_V@) +am__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@) am__v_GEN_0 = @echo " GEN " $@; SOURCES = $(libgnunetchat_la_SOURCES) $(gnunet_chat_SOURCES) \ $(gnunet_service_chat_SOURCES) $(test_chat_SOURCES) \ @@ -211,6 +236,11 @@ DIST_SOURCES = $(libgnunetchat_la_SOURCES) $(gnunet_chat_SOURCES) \ $(test_chat_authentication_p2p_SOURCES) \ $(test_chat_p2p_SOURCES) $(test_chat_private_SOURCES) \ $(test_chat_private_p2p_SOURCES) +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac DATA = $(pkgcfg_DATA) ETAGS = etags CTAGS = ctags @@ -252,6 +282,10 @@ EXEEXT = @EXEEXT@ EXT_LIBS = @EXT_LIBS@ EXT_LIB_PATH = @EXT_LIB_PATH@ FGREP = @FGREP@ +GLIB_CFLAGS = @GLIB_CFLAGS@ +GLIB_GENMARSHAL = @GLIB_GENMARSHAL@ +GLIB_LIBS = @GLIB_LIBS@ +GLIB_MKENUMS = @GLIB_MKENUMS@ GMSGFMT = @GMSGFMT@ GMSGFMT_015 = @GMSGFMT_015@ GNUNETDNS_GROUP = @GNUNETDNS_GROUP@ @@ -262,6 +296,7 @@ GN_LIBINTL = @GN_LIBINTL@ GN_LIB_LDFLAGS = @GN_LIB_LDFLAGS@ GN_PLUGIN_LDFLAGS = @GN_PLUGIN_LDFLAGS@ GN_USER_HOME_DIR = @GN_USER_HOME_DIR@ +GOBJECT_QUERY = @GOBJECT_QUERY@ GREP = @GREP@ HAVE_LIBUNISTRING = @HAVE_LIBUNISTRING@ INCLTDL = @INCLTDL@ @@ -284,6 +319,8 @@ LIBCURL_CPPFLAGS = @LIBCURL_CPPFLAGS@ LIBGCRYPT_CFLAGS = @LIBGCRYPT_CFLAGS@ LIBGCRYPT_CONFIG = @LIBGCRYPT_CONFIG@ LIBGCRYPT_LIBS = @LIBGCRYPT_LIBS@ +LIBGTOP_CFLAGS = @LIBGTOP_CFLAGS@ +LIBGTOP_LIBS = @LIBGTOP_LIBS@ LIBICONV = @LIBICONV@ LIBINTL = @LIBINTL@ LIBLTDL = @LIBLTDL@ @@ -305,6 +342,7 @@ LT_CONFIG_H = @LT_CONFIG_H@ LT_DLLOADERS = @LT_DLLOADERS@ LT_DLPREOPEN = @LT_DLPREOPEN@ MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ MKDIR_P = @MKDIR_P@ MONKEYPREFIX = @MONKEYPREFIX@ MSGFMT = @MSGFMT@ @@ -314,6 +352,7 @@ MYSQL_CPPFLAGS = @MYSQL_CPPFLAGS@ MYSQL_LDFLAGS = @MYSQL_LDFLAGS@ NM = @NM@ NMEDIT = @NMEDIT@ +NSS_DIR = @NSS_DIR@ OBJC = @OBJC@ OBJCDEPMODE = @OBJCDEPMODE@ OBJCFLAGS = @OBJCFLAGS@ @@ -329,6 +368,7 @@ PACKAGE_TARNAME = @PACKAGE_TARNAME@ PACKAGE_URL = @PACKAGE_URL@ PACKAGE_VERSION = @PACKAGE_VERSION@ PATH_SEPARATOR = @PATH_SEPARATOR@ +PKG_CONFIG = @PKG_CONFIG@ POSTGRES_CPPFLAGS = @POSTGRES_CPPFLAGS@ POSTGRES_LDFLAGS = @POSTGRES_LDFLAGS@ POSUB = @POSUB@ @@ -360,6 +400,7 @@ abs_builddir = @abs_builddir@ abs_srcdir = @abs_srcdir@ abs_top_builddir = @abs_top_builddir@ abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ ac_ct_CC = @ac_ct_CC@ ac_ct_CXX = @ac_ct_CXX@ ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ @@ -382,6 +423,7 @@ datarootdir = @datarootdir@ docdir = @docdir@ dvidir = @dvidir@ exec_prefix = @exec_prefix@ +gitcommand = @gitcommand@ host = @host@ host_alias = @host_alias@ host_cpu = @host_cpu@ @@ -392,10 +434,9 @@ includedir = @includedir@ infodir = @infodir@ install_sh = @install_sh@ libdir = @libdir@ -libexecdir = @libexecdir@ +libexecdir = $(pkglibdir)/libexec/ localedir = @localedir@ localstatedir = @localstatedir@ -lt_ECHO = @lt_ECHO@ ltdl_LIBOBJS = @ltdl_LIBOBJS@ ltdl_LTLIBOBJS = @ltdl_LTLIBOBJS@ mandir = @mandir@ @@ -413,6 +454,7 @@ sbindir = @sbindir@ sharedstatedir = @sharedstatedir@ srcdir = @srcdir@ subdirs = @subdirs@ +svnversioncommand = @svnversioncommand@ sys_symbol_underscore = @sys_symbol_underscore@ sysconfdir = @sysconfdir@ target = @target@ @@ -575,7 +617,6 @@ chat.conf: $(top_builddir)/config.status $(srcdir)/chat.conf.in cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ install-libLTLIBRARIES: $(lib_LTLIBRARIES) @$(NORMAL_INSTALL) - test -z "$(libdir)" || $(MKDIR_P) "$(DESTDIR)$(libdir)" @list='$(lib_LTLIBRARIES)'; test -n "$(libdir)" || list=; \ list2=; for p in $$list; do \ if test -f $$p; then \ @@ -583,6 +624,8 @@ install-libLTLIBRARIES: $(lib_LTLIBRARIES) else :; fi; \ done; \ test -z "$$list2" || { \ + echo " $(MKDIR_P) '$(DESTDIR)$(libdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libdir)" || exit 1; \ echo " $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 '$(DESTDIR)$(libdir)'"; \ $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 "$(DESTDIR)$(libdir)"; \ } @@ -604,12 +647,15 @@ clean-libLTLIBRARIES: echo "rm -f \"$${dir}/so_locations\""; \ rm -f "$${dir}/so_locations"; \ done -libgnunetchat.la: $(libgnunetchat_la_OBJECTS) $(libgnunetchat_la_DEPENDENCIES) +libgnunetchat.la: $(libgnunetchat_la_OBJECTS) $(libgnunetchat_la_DEPENDENCIES) $(EXTRA_libgnunetchat_la_DEPENDENCIES) $(AM_V_CCLD)$(libgnunetchat_la_LINK) -rpath $(libdir) $(libgnunetchat_la_OBJECTS) $(libgnunetchat_la_LIBADD) $(LIBS) install-binPROGRAMS: $(bin_PROGRAMS) @$(NORMAL_INSTALL) - test -z "$(bindir)" || $(MKDIR_P) "$(DESTDIR)$(bindir)" @list='$(bin_PROGRAMS)'; test -n "$(bindir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(bindir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(bindir)" || exit 1; \ + fi; \ for p in $$list; do echo "$$p $$p"; done | \ sed 's/$(EXEEXT)$$//' | \ while read p p1; do if test -f $$p || test -f $$p1; \ @@ -658,40 +704,86 @@ clean-checkPROGRAMS: list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ echo " rm -f" $$list; \ rm -f $$list -gnunet-chat$(EXEEXT): $(gnunet_chat_OBJECTS) $(gnunet_chat_DEPENDENCIES) +install-libexecPROGRAMS: $(libexec_PROGRAMS) + @$(NORMAL_INSTALL) + @list='$(libexec_PROGRAMS)'; test -n "$(libexecdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(libexecdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libexecdir)" || exit 1; \ + fi; \ + for p in $$list; do echo "$$p $$p"; done | \ + sed 's/$(EXEEXT)$$//' | \ + while read p p1; do if test -f $$p || test -f $$p1; \ + then echo "$$p"; echo "$$p"; else :; fi; \ + done | \ + sed -e 'p;s,.*/,,;n;h' -e 's|.*|.|' \ + -e 'p;x;s,.*/,,;s/$(EXEEXT)$$//;$(transform);s/$$/$(EXEEXT)/' | \ + sed 'N;N;N;s,\n, ,g' | \ + $(AWK) 'BEGIN { files["."] = ""; dirs["."] = 1 } \ + { d=$$3; if (dirs[d] != 1) { print "d", d; dirs[d] = 1 } \ + if ($$2 == $$4) files[d] = files[d] " " $$1; \ + else { print "f", $$3 "/" $$4, $$1; } } \ + END { for (d in files) print "f", d, files[d] }' | \ + while read type dir files; do \ + if test "$$dir" = .; then dir=; else dir=/$$dir; fi; \ + test -z "$$files" || { \ + echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files '$(DESTDIR)$(libexecdir)$$dir'"; \ + $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files "$(DESTDIR)$(libexecdir)$$dir" || exit $$?; \ + } \ + ; done + +uninstall-libexecPROGRAMS: + @$(NORMAL_UNINSTALL) + @list='$(libexec_PROGRAMS)'; test -n "$(libexecdir)" || list=; \ + files=`for p in $$list; do echo "$$p"; done | \ + sed -e 'h;s,^.*/,,;s/$(EXEEXT)$$//;$(transform)' \ + -e 's/$$/$(EXEEXT)/' `; \ + test -n "$$list" || exit 0; \ + echo " ( cd '$(DESTDIR)$(libexecdir)' && rm -f" $$files ")"; \ + cd "$(DESTDIR)$(libexecdir)" && rm -f $$files + +clean-libexecPROGRAMS: + @list='$(libexec_PROGRAMS)'; test -n "$$list" || exit 0; \ + echo " rm -f" $$list; \ + rm -f $$list || exit $$?; \ + test -n "$(EXEEXT)" || exit 0; \ + list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ + echo " rm -f" $$list; \ + rm -f $$list +gnunet-chat$(EXEEXT): $(gnunet_chat_OBJECTS) $(gnunet_chat_DEPENDENCIES) $(EXTRA_gnunet_chat_DEPENDENCIES) @rm -f gnunet-chat$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_chat_OBJECTS) $(gnunet_chat_LDADD) $(LIBS) -gnunet-service-chat$(EXEEXT): $(gnunet_service_chat_OBJECTS) $(gnunet_service_chat_DEPENDENCIES) +gnunet-service-chat$(EXEEXT): $(gnunet_service_chat_OBJECTS) $(gnunet_service_chat_DEPENDENCIES) $(EXTRA_gnunet_service_chat_DEPENDENCIES) @rm -f gnunet-service-chat$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_service_chat_OBJECTS) $(gnunet_service_chat_LDADD) $(LIBS) -test_chat$(EXEEXT): $(test_chat_OBJECTS) $(test_chat_DEPENDENCIES) +test_chat$(EXEEXT): $(test_chat_OBJECTS) $(test_chat_DEPENDENCIES) $(EXTRA_test_chat_DEPENDENCIES) @rm -f test_chat$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_chat_OBJECTS) $(test_chat_LDADD) $(LIBS) -test_chat_acknowledgement$(EXEEXT): $(test_chat_acknowledgement_OBJECTS) $(test_chat_acknowledgement_DEPENDENCIES) +test_chat_acknowledgement$(EXEEXT): $(test_chat_acknowledgement_OBJECTS) $(test_chat_acknowledgement_DEPENDENCIES) $(EXTRA_test_chat_acknowledgement_DEPENDENCIES) @rm -f test_chat_acknowledgement$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_chat_acknowledgement_OBJECTS) $(test_chat_acknowledgement_LDADD) $(LIBS) -test_chat_acknowledgement_p2p$(EXEEXT): $(test_chat_acknowledgement_p2p_OBJECTS) $(test_chat_acknowledgement_p2p_DEPENDENCIES) +test_chat_acknowledgement_p2p$(EXEEXT): $(test_chat_acknowledgement_p2p_OBJECTS) $(test_chat_acknowledgement_p2p_DEPENDENCIES) $(EXTRA_test_chat_acknowledgement_p2p_DEPENDENCIES) @rm -f test_chat_acknowledgement_p2p$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_chat_acknowledgement_p2p_OBJECTS) $(test_chat_acknowledgement_p2p_LDADD) $(LIBS) -test_chat_anonymous$(EXEEXT): $(test_chat_anonymous_OBJECTS) $(test_chat_anonymous_DEPENDENCIES) +test_chat_anonymous$(EXEEXT): $(test_chat_anonymous_OBJECTS) $(test_chat_anonymous_DEPENDENCIES) $(EXTRA_test_chat_anonymous_DEPENDENCIES) @rm -f test_chat_anonymous$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_chat_anonymous_OBJECTS) $(test_chat_anonymous_LDADD) $(LIBS) -test_chat_anonymous_p2p$(EXEEXT): $(test_chat_anonymous_p2p_OBJECTS) $(test_chat_anonymous_p2p_DEPENDENCIES) +test_chat_anonymous_p2p$(EXEEXT): $(test_chat_anonymous_p2p_OBJECTS) $(test_chat_anonymous_p2p_DEPENDENCIES) $(EXTRA_test_chat_anonymous_p2p_DEPENDENCIES) @rm -f test_chat_anonymous_p2p$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_chat_anonymous_p2p_OBJECTS) $(test_chat_anonymous_p2p_LDADD) $(LIBS) -test_chat_authentication$(EXEEXT): $(test_chat_authentication_OBJECTS) $(test_chat_authentication_DEPENDENCIES) +test_chat_authentication$(EXEEXT): $(test_chat_authentication_OBJECTS) $(test_chat_authentication_DEPENDENCIES) $(EXTRA_test_chat_authentication_DEPENDENCIES) @rm -f test_chat_authentication$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_chat_authentication_OBJECTS) $(test_chat_authentication_LDADD) $(LIBS) -test_chat_authentication_p2p$(EXEEXT): $(test_chat_authentication_p2p_OBJECTS) $(test_chat_authentication_p2p_DEPENDENCIES) +test_chat_authentication_p2p$(EXEEXT): $(test_chat_authentication_p2p_OBJECTS) $(test_chat_authentication_p2p_DEPENDENCIES) $(EXTRA_test_chat_authentication_p2p_DEPENDENCIES) @rm -f test_chat_authentication_p2p$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_chat_authentication_p2p_OBJECTS) $(test_chat_authentication_p2p_LDADD) $(LIBS) -test_chat_p2p$(EXEEXT): $(test_chat_p2p_OBJECTS) $(test_chat_p2p_DEPENDENCIES) +test_chat_p2p$(EXEEXT): $(test_chat_p2p_OBJECTS) $(test_chat_p2p_DEPENDENCIES) $(EXTRA_test_chat_p2p_DEPENDENCIES) @rm -f test_chat_p2p$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_chat_p2p_OBJECTS) $(test_chat_p2p_LDADD) $(LIBS) -test_chat_private$(EXEEXT): $(test_chat_private_OBJECTS) $(test_chat_private_DEPENDENCIES) +test_chat_private$(EXEEXT): $(test_chat_private_OBJECTS) $(test_chat_private_DEPENDENCIES) $(EXTRA_test_chat_private_DEPENDENCIES) @rm -f test_chat_private$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_chat_private_OBJECTS) $(test_chat_private_LDADD) $(LIBS) -test_chat_private_p2p$(EXEEXT): $(test_chat_private_p2p_OBJECTS) $(test_chat_private_p2p_DEPENDENCIES) +test_chat_private_p2p$(EXEEXT): $(test_chat_private_p2p_OBJECTS) $(test_chat_private_p2p_DEPENDENCIES) $(EXTRA_test_chat_private_p2p_DEPENDENCIES) @rm -f test_chat_private_p2p$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_chat_private_p2p_OBJECTS) $(test_chat_private_p2p_LDADD) $(LIBS) @@ -710,26 +802,23 @@ distclean-compile: .c.o: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c $< .c.obj: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'` @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c `$(CYGPATH_W) '$<'` +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c `$(CYGPATH_W) '$<'` .c.lo: @am__fastdepCC_TRUE@ $(AM_V_CC)$(LTCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LTCOMPILE) -c -o $@ $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LTCOMPILE) -c -o $@ $< mostlyclean-libtool: -rm -f *.lo @@ -738,8 +827,11 @@ clean-libtool: -rm -rf .libs _libs install-pkgcfgDATA: $(pkgcfg_DATA) @$(NORMAL_INSTALL) - test -z "$(pkgcfgdir)" || $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" @list='$(pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(pkgcfgdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" || exit 1; \ + fi; \ for p in $$list; do \ if test -f "$$p"; then d=; else d="$(srcdir)/"; fi; \ echo "$$d$$p"; \ @@ -753,9 +845,7 @@ uninstall-pkgcfgDATA: @$(NORMAL_UNINSTALL) @list='$(pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ files=`for p in $$list; do echo $$p; done | sed -e 's|^.*/||'`; \ - test -n "$$files" || exit 0; \ - echo " ( cd '$(DESTDIR)$(pkgcfgdir)' && rm -f" $$files ")"; \ - cd "$(DESTDIR)$(pkgcfgdir)" && rm -f $$files + dir='$(DESTDIR)$(pkgcfgdir)'; $(am__uninstall_files_from_dir) ID: $(HEADERS) $(SOURCES) $(LISP) $(TAGS_FILES) list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ @@ -890,14 +980,15 @@ check-TESTS: $(TESTS) fi; \ dashes=`echo "$$dashes" | sed s/./=/g`; \ if test "$$failed" -eq 0; then \ - echo "$$grn$$dashes"; \ + col="$$grn"; \ else \ - echo "$$red$$dashes"; \ + col="$$red"; \ fi; \ - echo "$$banner"; \ - test -z "$$skipped" || echo "$$skipped"; \ - test -z "$$report" || echo "$$report"; \ - echo "$$dashes$$std"; \ + echo "$${col}$$dashes$${std}"; \ + echo "$${col}$$banner$${std}"; \ + test -z "$$skipped" || echo "$${col}$$skipped$${std}"; \ + test -z "$$report" || echo "$${col}$$report$${std}"; \ + echo "$${col}$$dashes$${std}"; \ test "$$failed" -eq 0; \ else :; fi @@ -939,7 +1030,7 @@ all-am: Makefile $(LTLIBRARIES) $(PROGRAMS) $(DATA) install-binPROGRAMS: install-libLTLIBRARIES installdirs: - for dir in "$(DESTDIR)$(libdir)" "$(DESTDIR)$(bindir)" "$(DESTDIR)$(pkgcfgdir)"; do \ + for dir in "$(DESTDIR)$(libdir)" "$(DESTDIR)$(bindir)" "$(DESTDIR)$(libexecdir)" "$(DESTDIR)$(pkgcfgdir)"; do \ test -z "$$dir" || $(MKDIR_P) "$$dir"; \ done install: install-am @@ -952,10 +1043,15 @@ install-am: all-am installcheck: installcheck-am install-strip: - $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ - install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ - `test -z '$(STRIP)' || \ - echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi mostlyclean-generic: clean-generic: @@ -970,7 +1066,8 @@ maintainer-clean-generic: clean: clean-am clean-am: clean-binPROGRAMS clean-checkPROGRAMS clean-generic \ - clean-libLTLIBRARIES clean-libtool mostlyclean-am + clean-libLTLIBRARIES clean-libexecPROGRAMS clean-libtool \ + mostlyclean-am distclean: distclean-am -rm -rf ./$(DEPDIR) @@ -996,7 +1093,8 @@ install-dvi: install-dvi-am install-dvi-am: -install-exec-am: install-binPROGRAMS install-libLTLIBRARIES +install-exec-am: install-binPROGRAMS install-libLTLIBRARIES \ + install-libexecPROGRAMS install-html: install-html-am @@ -1037,25 +1135,26 @@ ps: ps-am ps-am: uninstall-am: uninstall-binPROGRAMS uninstall-libLTLIBRARIES \ - uninstall-pkgcfgDATA + uninstall-libexecPROGRAMS uninstall-pkgcfgDATA .MAKE: check-am install-am install-strip .PHONY: CTAGS GTAGS all all-am check check-TESTS check-am clean \ clean-binPROGRAMS clean-checkPROGRAMS clean-generic \ - clean-libLTLIBRARIES clean-libtool ctags distclean \ - distclean-compile distclean-generic distclean-libtool \ - distclean-tags distdir dvi dvi-am html html-am info info-am \ - install install-am install-binPROGRAMS install-data \ - install-data-am install-dvi install-dvi-am install-exec \ - install-exec-am install-html install-html-am install-info \ - install-info-am install-libLTLIBRARIES install-man install-pdf \ - install-pdf-am install-pkgcfgDATA install-ps install-ps-am \ - install-strip installcheck installcheck-am installdirs \ - maintainer-clean maintainer-clean-generic mostlyclean \ - mostlyclean-compile mostlyclean-generic mostlyclean-libtool \ - pdf pdf-am ps ps-am tags uninstall uninstall-am \ - uninstall-binPROGRAMS uninstall-libLTLIBRARIES \ + clean-libLTLIBRARIES clean-libexecPROGRAMS clean-libtool ctags \ + distclean distclean-compile distclean-generic \ + distclean-libtool distclean-tags distdir dvi dvi-am html \ + html-am info info-am install install-am install-binPROGRAMS \ + install-data install-data-am install-dvi install-dvi-am \ + install-exec install-exec-am install-html install-html-am \ + install-info install-info-am install-libLTLIBRARIES \ + install-libexecPROGRAMS install-man install-pdf install-pdf-am \ + install-pkgcfgDATA install-ps install-ps-am install-strip \ + installcheck installcheck-am installdirs maintainer-clean \ + maintainer-clean-generic mostlyclean mostlyclean-compile \ + mostlyclean-generic mostlyclean-libtool pdf pdf-am ps ps-am \ + tags uninstall uninstall-am uninstall-binPROGRAMS \ + uninstall-libLTLIBRARIES uninstall-libexecPROGRAMS \ uninstall-pkgcfgDATA diff --git a/src/chat/chat.c b/src/chat/chat.c index 72c49a0..cdcf282 100644 --- a/src/chat/chat.c +++ b/src/chat/chat.c @@ -92,7 +92,7 @@ struct MemberList /** * Member ID (pseudonym). */ - GNUNET_HashCode id; + struct GNUNET_HashCode id; }; @@ -224,8 +224,8 @@ process_result (struct GNUNET_CHAT_Room *room, struct ReceiveNotificationMessage *received_msg; struct ConfirmationReceiptMessage *receipt; struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded pkey; - GNUNET_HashCode id; - const GNUNET_HashCode *sender; + struct GNUNET_HashCode id; + const struct GNUNET_HashCode *sender; struct GNUNET_CONTAINER_MetaData *meta; struct GNUNET_CHAT_SendReceiptContext *src; struct MemberList *pos; @@ -308,7 +308,7 @@ process_result (struct GNUNET_CHAT_Room *room, prev = NULL; pos = room->members; while ((NULL != pos) && - (0 != memcmp (&pos->id, &id, sizeof (GNUNET_HashCode)))) + (0 != memcmp (&pos->id, &id, sizeof (struct GNUNET_HashCode)))) { prev = pos; pos = pos->next; @@ -379,7 +379,7 @@ process_result (struct GNUNET_CHAT_Room *room, while ((NULL != pos) && (0 != memcmp (&pos->id, &received_msg->sender, - sizeof (GNUNET_HashCode)))) + sizeof (struct GNUNET_HashCode)))) pos = pos->next; GNUNET_assert (NULL != pos); sender = &received_msg->sender; @@ -468,13 +468,12 @@ init_private_key (const struct GNUNET_CONFIGURATION_Handle *cfg, if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_filename (cfg, "chat", "HOME", &home)) { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - _("Configuration option `%s' in section `%s' missing\n"), - "HOME", "chat"); + GNUNET_log_config_missing (GNUNET_ERROR_TYPE_ERROR, + "chat", "HOME"); return NULL; } GNUNET_DISK_directory_create (home); - if (GNUNET_OK != GNUNET_DISK_directory_test (home)) + if (GNUNET_YES != GNUNET_DISK_directory_test (home, GNUNET_YES)) { GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("Failed to access chat home directory `%s'\n"), home); @@ -649,7 +648,7 @@ GNUNET_CHAT_join_room (const struct GNUNET_CONFIGURATION_Handle *cfg, GNUNET_CHAT_MemberListCallback memberCallback, void *member_cls, GNUNET_CHAT_MessageConfirmation confirmationCallback, - void *confirmation_cls, GNUNET_HashCode * me) + void *confirmation_cls, struct GNUNET_HashCode * me) { struct GNUNET_CHAT_Room *chat_room; struct GNUNET_CRYPTO_RsaPrivateKey *priv_key; @@ -755,7 +754,7 @@ transmit_send_request (void *cls, size_t size, void *buf) GNUNET_TIME_absolute_hton (GNUNET_TIME_absolute_get ()); msg_to_send->reserved = htonl (0); if (NULL == smc->receiver) - memset (&msg_to_send->target, 0, sizeof (GNUNET_HashCode)); + memset (&msg_to_send->target, 0, sizeof (struct GNUNET_HashCode)); else GNUNET_CRYPTO_hash (smc->receiver, sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded), diff --git a/src/chat/chat.conf.in b/src/chat/chat.conf.in index 41fe9b4..560931e 100644 --- a/src/chat/chat.conf.in +++ b/src/chat/chat.conf.in @@ -3,7 +3,6 @@ AUTOSTART = YES @UNIXONLY@ PORT = 2090 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-chat ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; diff --git a/src/chat/chat.h b/src/chat/chat.h index 5df7773..c65b75d 100644 --- a/src/chat/chat.h +++ b/src/chat/chat.h @@ -80,7 +80,7 @@ struct ReceiveNotificationMessage * Hash of the public key of the pseudonym of the sender of the message. * Should be all zeros for anonymous. */ - GNUNET_HashCode sender; + struct GNUNET_HashCode sender; /** * The encrypted session key. @@ -136,7 +136,7 @@ struct TransmitRequestMessage /** * Who should receive this message? Set to all zeros for "everyone". */ - GNUNET_HashCode target; + struct GNUNET_HashCode target; }; @@ -189,17 +189,17 @@ struct ConfirmationReceiptMessage /** * Who is confirming the receipt? */ - GNUNET_HashCode target; + struct GNUNET_HashCode target; /** * Who is the author of the chat message? */ - GNUNET_HashCode author; + struct GNUNET_HashCode author; /** * Hash of the (possibly encrypted) content. */ - GNUNET_HashCode content; + struct GNUNET_HashCode content; }; @@ -406,12 +406,12 @@ struct P2PReceiveNotificationMessage * Hash of the public key of the pseudonym of the sender of the message * Should be all zeros for anonymous. */ - GNUNET_HashCode sender; + struct GNUNET_HashCode sender; /** * Who should receive this message? Set to all zeros for "everyone". */ - GNUNET_HashCode target; + struct GNUNET_HashCode target; /** * The encrypted session key. @@ -465,17 +465,17 @@ struct P2PConfirmationReceiptMessage /** * Who is confirming the receipt? */ - GNUNET_HashCode target; + struct GNUNET_HashCode target; /** * Who is the author of the chat message? */ - GNUNET_HashCode author; + struct GNUNET_HashCode author; /** * Hash of the (possibly encrypted) content. */ - GNUNET_HashCode content; + struct GNUNET_HashCode content; }; GNUNET_NETWORK_STRUCT_END diff --git a/src/chat/gnunet-chat.c b/src/chat/gnunet-chat.c index 7b11c0d..8e6ba9b 100644 --- a/src/chat/gnunet-chat.c +++ b/src/chat/gnunet-chat.c @@ -110,7 +110,7 @@ join_cb (void *cls) */ static int receive_cb (void *cls, struct GNUNET_CHAT_Room *room, - const GNUNET_HashCode * sender, + const struct GNUNET_HashCode * sender, const struct GNUNET_CONTAINER_MetaData *member_info, const char *message, struct GNUNET_TIME_Absolute timestamp, enum GNUNET_CHAT_MsgOptions options) @@ -118,7 +118,7 @@ receive_cb (void *cls, struct GNUNET_CHAT_Room *room, char *non_unique_nick; char *nick; int nick_is_a_dup; - char *time; + const char *timestr; const char *fmt; if (NULL == sender) @@ -176,10 +176,9 @@ receive_cb (void *cls, struct GNUNET_CHAT_Room *room, fmt = _("(%s) <%s> said using an unknown message type: %s\n"); break; } - time = GNUNET_STRINGS_absolute_time_to_string (timestamp); - FPRINTF (stdout, fmt, time, nick, message); + timestr = GNUNET_STRINGS_absolute_time_to_string (timestamp); + FPRINTF (stdout, fmt, timestr, nick, message); GNUNET_free (nick); - GNUNET_free (time); return GNUNET_OK; } @@ -199,7 +198,7 @@ static int confirmation_cb (void *cls, struct GNUNET_CHAT_Room *room, uint32_t orig_seq_number, struct GNUNET_TIME_Absolute timestamp, - const GNUNET_HashCode * receiver) + const struct GNUNET_HashCode * receiver) { char *nick; char *unique_nick; @@ -238,7 +237,7 @@ member_list_cb (void *cls, const struct GNUNET_CONTAINER_MetaData *member_info, char *nick; char *non_unique_nick; int nick_is_a_dup; - GNUNET_HashCode id; + struct GNUNET_HashCode id; struct UserList *pos; struct UserList *prev; @@ -304,7 +303,7 @@ do_join (const char *arg, const void *xtra) { char *my_name; int my_name_is_a_dup; - GNUNET_HashCode me; + struct GNUNET_HashCode me; if (arg[0] == '#') arg++; /* ignore first hash */ @@ -343,7 +342,7 @@ do_nick (const char *msg, const void *xtra) { char *my_name; int my_name_is_a_dup; - GNUNET_HashCode me; + struct GNUNET_HashCode me; GNUNET_CHAT_leave_room (room); free_user_list (); @@ -383,7 +382,7 @@ do_names (const char *msg, const void *xtra) char *unique_name; int name_is_a_dup; struct UserList *pos; - GNUNET_HashCode pid; + struct GNUNET_HashCode pid; FPRINTF (stdout, _("Users in room `%s': "), room_name); pos = users; @@ -424,8 +423,8 @@ static int do_send_pm (const char *msg, const void *xtra) { char *user; - GNUNET_HashCode uid; - GNUNET_HashCode pid; + struct GNUNET_HashCode uid; + struct GNUNET_HashCode pid; uint32_t seq; struct UserList *pos; @@ -451,7 +450,7 @@ do_send_pm (const char *msg, const void *xtra) GNUNET_CRYPTO_hash (&pos->pkey, sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded), &pid); - if (0 == memcmp (&pid, &uid, sizeof (GNUNET_HashCode))) + if (0 == memcmp (&pid, &uid, sizeof (struct GNUNET_HashCode))) break; pos = pos->next; } @@ -661,7 +660,7 @@ static void run (void *cls, char *const *args, const char *cfgfile, const struct GNUNET_CONFIGURATION_Handle *c) { - GNUNET_HashCode me; + struct GNUNET_HashCode me; char *my_name; int my_name_is_a_dup; @@ -737,6 +736,10 @@ main (int argc, char *const *argv) flags |= O_NONBLOCK; fcntl (0, F_SETFL, flags); #endif + + if (GNUNET_OK != GNUNET_STRINGS_get_utf8_args (argc, argv, &argc, &argv)) + return 2; + return (GNUNET_OK == GNUNET_PROGRAM_run (argc, argv, "gnunet-chat", gettext_noop ("Join a chat on GNUnet."), options, diff --git a/src/chat/gnunet-service-chat.c b/src/chat/gnunet-service-chat.c index fb127b2..ec988e8 100644 --- a/src/chat/gnunet-service-chat.c +++ b/src/chat/gnunet-service-chat.c @@ -36,7 +36,6 @@ #define DEBUG_CHAT_SERVICE GNUNET_EXTRA_LOGGING #define MAX_TRANSMIT_DELAY GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 60) #define EXPECTED_NEIGHBOUR_COUNT 16 -#define QUEUE_SIZE 16 #define MAX_ANONYMOUS_MSG_LIST_LENGTH 16 @@ -70,7 +69,7 @@ struct ChatClient /** * Hash of the public key (for convenience). */ - GNUNET_HashCode id; + struct GNUNET_HashCode id; /** * Options which the client is willing to receive. @@ -118,7 +117,7 @@ struct AnonymousMessage /** * Hash of the message. */ - GNUNET_HashCode hash; + struct GNUNET_HashCode hash; }; @@ -136,7 +135,7 @@ static const struct GNUNET_CONFIGURATION_Handle *cfg; /** * The identity of this host. */ -static const struct GNUNET_PeerIdentity *me; +static struct GNUNET_PeerIdentity me; /** * Head of the list of current clients. @@ -163,7 +162,7 @@ static void remember_anonymous_message (const struct P2PReceiveNotificationMessage *p2p_rnmsg) { - static GNUNET_HashCode hash; + static struct GNUNET_HashCode hash; struct AnonymousMessage *anon_msg; struct AnonymousMessage *prev; int anon_list_len; @@ -193,13 +192,13 @@ remember_anonymous_message (const struct P2PReceiveNotificationMessage static int lookup_anonymous_message (const struct P2PReceiveNotificationMessage *p2p_rnmsg) { - static GNUNET_HashCode hash; + static struct GNUNET_HashCode hash; struct AnonymousMessage *anon_msg; GNUNET_CRYPTO_hash (p2p_rnmsg, ntohs (p2p_rnmsg->header.size), &hash); anon_msg = anonymous_list_head; while ((NULL != anon_msg) && - (0 != memcmp (&anon_msg->hash, &hash, sizeof (GNUNET_HashCode)))) + (0 != memcmp (&anon_msg->hash, &hash, sizeof (struct GNUNET_HashCode)))) anon_msg = anon_msg->next; return (NULL != anon_msg); } @@ -245,7 +244,7 @@ transmit_message_notification_to_peer (void *cls, size_t size, void *buf) * Ask to send a message notification to the peer. */ static int -send_message_noficiation (void *cls, const GNUNET_HashCode * key, void *value) +send_message_noficiation (void *cls, const struct GNUNET_HashCode * key, void *value) { struct P2PReceiveNotificationMessage *msg = cls; struct ConnectedPeer *cp = value; @@ -281,7 +280,7 @@ static void handle_transmit_request (void *cls, struct GNUNET_SERVER_Client *client, const struct GNUNET_MessageHeader *message) { - static GNUNET_HashCode all_zeros; + static struct GNUNET_HashCode all_zeros; const struct TransmitRequestMessage *trmsg; struct ReceiveNotificationMessage *rnmsg; struct P2PReceiveNotificationMessage *p2p_rnmsg; @@ -350,7 +349,7 @@ handle_transmit_request (void *cls, struct GNUNET_SERVER_Client *client, is_anon = (0 != (ntohl (trmsg->msg_options) & GNUNET_CHAT_MSG_ANONYMOUS)); if (is_anon) { - memset (&rnmsg->sender, 0, sizeof (GNUNET_HashCode)); + memset (&rnmsg->sender, 0, sizeof (struct GNUNET_HashCode)); rnmsg->sequence_number = 0; } else @@ -365,7 +364,7 @@ handle_transmit_request (void *cls, struct GNUNET_SERVER_Client *client, "Encrypting the session key using the public key of '%s'\n", GNUNET_h2s (&trmsg->target)); #endif - if (0 == memcmp (&all_zeros, &trmsg->target, sizeof (GNUNET_HashCode))) + if (0 == memcmp (&all_zeros, &trmsg->target, sizeof (struct GNUNET_HashCode))) { GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Malformed message: private, but no target\n"); @@ -378,7 +377,7 @@ handle_transmit_request (void *cls, struct GNUNET_SERVER_Client *client, target = client_list_head; while ((NULL != target) && (0 != - memcmp (&target->id, &trmsg->target, sizeof (GNUNET_HashCode)))) + memcmp (&target->id, &trmsg->target, sizeof (struct GNUNET_HashCode)))) target = target->next; if (NULL == target) { @@ -417,7 +416,7 @@ handle_transmit_request (void *cls, struct GNUNET_SERVER_Client *client, (pos->client != client)) { if (((!is_priv) || - (0 == memcmp (&trmsg->target, &pos->id, sizeof (GNUNET_HashCode)))) + (0 == memcmp (&trmsg->target, &pos->id, sizeof (struct GNUNET_HashCode)))) && (0 == (ntohl (trmsg->msg_options) & (~pos->msg_options)))) { GNUNET_SERVER_notification_context_unicast (nc, pos->client, @@ -522,7 +521,7 @@ transmit_join_notification_to_peer (void *cls, size_t size, void *buf) * Ask to send a join notification to the peer. */ static int -send_join_noficiation (void *cls, const GNUNET_HashCode * key, void *value) +send_join_noficiation (void *cls, const struct GNUNET_HashCode * key, void *value) { struct ChatClient *entry = cls; struct ConnectedPeer *cp = value; @@ -704,7 +703,7 @@ transmit_confirmation_receipt_to_peer (void *cls, size_t size, void *buf) * Ask to send a confirmation receipt to the peer. */ static int -send_confirmation_receipt (void *cls, const GNUNET_HashCode * key, void *value) +send_confirmation_receipt (void *cls, const struct GNUNET_HashCode * key, void *value) { struct P2PConfirmationReceiptMessage *receipt = cls; struct ConnectedPeer *cp = value; @@ -755,7 +754,7 @@ handle_acknowledge_request (void *cls, struct GNUNET_SERVER_Client *client, author = client_list_head; while ((NULL != author) && (0 != - memcmp (&receipt->author, &author->id, sizeof (GNUNET_HashCode)))) + memcmp (&receipt->author, &author->id, sizeof (struct GNUNET_HashCode)))) author = author->next; if (NULL == author) { @@ -768,7 +767,7 @@ handle_acknowledge_request (void *cls, struct GNUNET_SERVER_Client *client, target = client_list_head; while ((NULL != target) && (0 != - memcmp (&receipt->target, &target->id, sizeof (GNUNET_HashCode)))) + memcmp (&receipt->target, &target->id, sizeof (struct GNUNET_HashCode)))) target = target->next; if (NULL == target) { @@ -881,7 +880,7 @@ transmit_leave_notification_to_peer (void *cls, size_t size, void *buf) * Ask to send a leave notification to the peer. */ static int -send_leave_noficiation (void *cls, const GNUNET_HashCode * key, void *value) +send_leave_noficiation (void *cls, const struct GNUNET_HashCode * key, void *value) { struct ChatClient *entry = cls; struct ConnectedPeer *cp = value; @@ -1001,7 +1000,7 @@ handle_p2p_join_notification (void *cls, struct ChatClient *new_entry; struct ChatClient *entry; struct JoinNotificationMessage *jnmsg; - GNUNET_HashCode id; + struct GNUNET_HashCode id; GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Got P2P join notification\n"); if (ntohs (message->size) <= sizeof (struct P2PJoinNotificationMessage)) @@ -1026,7 +1025,7 @@ handle_p2p_join_notification (void *cls, entry = client_list_head; while (NULL != entry) { - if (0 == memcmp (&entry->id, &id, sizeof (GNUNET_HashCode))) + if (0 == memcmp (&entry->id, &id, sizeof (struct GNUNET_HashCode))) { #if DEBUG_CHAT_SERVICE GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, @@ -1110,7 +1109,7 @@ handle_p2p_leave_notification (void *cls, unsigned int atsi_count) { const struct P2PLeaveNotificationMessage *p2p_lnmsg; - GNUNET_HashCode id; + struct GNUNET_HashCode id; struct ChatClient *pos; struct ChatClient *prev; struct ChatClient *entry; @@ -1125,7 +1124,7 @@ handle_p2p_leave_notification (void *cls, prev = NULL; while (NULL != pos) { - if (0 == memcmp (&pos->id, &id, sizeof (GNUNET_HashCode))) + if (0 == memcmp (&pos->id, &id, sizeof (struct GNUNET_HashCode))) break; prev = pos; pos = pos->next; @@ -1196,7 +1195,7 @@ handle_p2p_message_notification (void *cls, struct ReceiveNotificationMessage *rnmsg; struct ChatClient *sender; struct ChatClient *pos; - static GNUNET_HashCode all_zeros; + static struct GNUNET_HashCode all_zeros; int is_priv; int is_anon; uint16_t msg_len; @@ -1247,7 +1246,7 @@ handle_p2p_message_notification (void *cls, sender = client_list_head; while ((NULL != sender) && (0 != - memcmp (&sender->id, &p2p_rnmsg->sender, sizeof (GNUNET_HashCode)))) + memcmp (&sender->id, &p2p_rnmsg->sender, sizeof (struct GNUNET_HashCode)))) sender = sender->next; if (NULL == sender) { @@ -1288,7 +1287,7 @@ handle_p2p_message_notification (void *cls, rnmsg->reserved = htonl (0); rnmsg->timestamp = p2p_rnmsg->timestamp; is_priv = - (0 != memcmp (&all_zeros, &p2p_rnmsg->target, sizeof (GNUNET_HashCode))); + (0 != memcmp (&all_zeros, &p2p_rnmsg->target, sizeof (struct GNUNET_HashCode))); if (is_priv) memcpy (&rnmsg->encrypted_key, &p2p_rnmsg->encrypted_key, sizeof (struct GNUNET_CRYPTO_RsaEncryptedData)); @@ -1301,7 +1300,7 @@ handle_p2p_message_notification (void *cls, { if (((!is_priv) || (0 == - memcmp (&p2p_rnmsg->target, &pos->id, sizeof (GNUNET_HashCode)))) && + memcmp (&p2p_rnmsg->target, &pos->id, sizeof (struct GNUNET_HashCode)))) && (0 == (ntohl (p2p_rnmsg->msg_options) & (~pos->msg_options)))) { GNUNET_SERVER_notification_context_unicast (nc, pos->client, @@ -1397,7 +1396,7 @@ handle_p2p_confirmation_receipt (void *cls, target = client_list_head; while ((NULL != target) && (0 != - memcmp (&target->id, &p2p_crmsg->target, sizeof (GNUNET_HashCode)))) + memcmp (&target->id, &p2p_crmsg->target, sizeof (struct GNUNET_HashCode)))) target = target->next; if (NULL == target) { @@ -1421,7 +1420,7 @@ handle_p2p_confirmation_receipt (void *cls, author = client_list_head; while ((NULL != author) && (0 != - memcmp (&author->id, &p2p_crmsg->author, sizeof (GNUNET_HashCode)))) + memcmp (&author->id, &p2p_crmsg->author, sizeof (struct GNUNET_HashCode)))) author = author->next; if (NULL == author) { @@ -1531,7 +1530,7 @@ peer_connect_handler (void *cls, const struct GNUNET_PeerIdentity *peer, struct ConnectedPeer *cp; struct GNUNET_CORE_TransmitHandle *th; - if (0 == memcmp (peer, me, sizeof (struct GNUNET_PeerIdentity))) + if (0 == memcmp (peer, &me, sizeof (struct GNUNET_PeerIdentity))) return; GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Peer connected: %s\n", GNUNET_i2s (peer)); @@ -1564,7 +1563,7 @@ peer_connect_handler (void *cls, const struct GNUNET_PeerIdentity *peer, * @return GNUNET_YES (we should continue to iterate) */ static int -clean_peer (void *cls, const GNUNET_HashCode * key, void *value) +clean_peer (void *cls, const struct GNUNET_HashCode * key, void *value) { struct ConnectedPeer *cp; const struct GNUNET_PeerIdentity *peer = @@ -1592,11 +1591,11 @@ static void peer_disconnect_handler (void *cls, const struct GNUNET_PeerIdentity *peer) { - if (0 == memcmp (peer, me, sizeof (struct GNUNET_PeerIdentity))) + if (0 == memcmp (peer, &me, sizeof (struct GNUNET_PeerIdentity))) return; GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Peer disconnected: %s\n", GNUNET_i2s (peer)); - clean_peer (NULL, (const GNUNET_HashCode *) peer, NULL); + clean_peer (NULL, (const struct GNUNET_HashCode *) peer, NULL); } @@ -1655,7 +1654,7 @@ core_init (void *cls, struct GNUNET_CORE_Handle *server, const struct GNUNET_PeerIdentity *my_identity) { GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Core initialized\n"); - me = my_identity; + me = *my_identity; } @@ -1707,10 +1706,10 @@ run (void *cls, struct GNUNET_SERVER_Handle *server, cfg = c; nc = GNUNET_SERVER_notification_context_create (server, 16); connected_peers = - GNUNET_CONTAINER_multihashmap_create (EXPECTED_NEIGHBOUR_COUNT); + GNUNET_CONTAINER_multihashmap_create (EXPECTED_NEIGHBOUR_COUNT, GNUNET_NO); GNUNET_SERVER_add_handlers (server, handlers); core = - GNUNET_CORE_connect (cfg, QUEUE_SIZE, NULL, &core_init, + GNUNET_CORE_connect (cfg, NULL, &core_init, &peer_connect_handler, &peer_disconnect_handler, NULL, GNUNET_NO, NULL, GNUNET_NO, p2p_handlers); GNUNET_SERVER_disconnect_notify (server, &handle_client_disconnect, NULL); diff --git a/src/chat/test_chat.c b/src/chat/test_chat.c index 2e8272d..78b31f1 100644 --- a/src/chat/test_chat.c +++ b/src/chat/test_chat.c @@ -37,10 +37,6 @@ #include "gnunet_arm_service.h" #include "gnunet_chat_service.h" -#define VERBOSE GNUNET_NO - -#define START_ARM GNUNET_YES - /** * How long until we give up on passing the test? */ @@ -49,16 +45,14 @@ struct PeerContext { struct GNUNET_CONFIGURATION_Handle *cfg; -#if START_ARM struct GNUNET_OS_Process *arm_proc; -#endif }; struct Wanted { struct GNUNET_CONTAINER_MetaData *meta; - GNUNET_HashCode *sender; + struct GNUNET_HashCode *sender; char *msg; @@ -80,9 +74,9 @@ static struct PeerContext p1; static struct PeerContext p2; -static GNUNET_HashCode alice; +static struct GNUNET_HashCode alice; -static GNUNET_HashCode bob; +static struct GNUNET_HashCode bob; static struct GNUNET_CHAT_Room *alice_room; @@ -116,24 +110,22 @@ static int is_auth; static void setup_peer (struct PeerContext *p, const char *cfgname) { + char *binary; + + binary = GNUNET_OS_get_libexec_binary_path ("gnunet-service-arm"); p->cfg = GNUNET_CONFIGURATION_create (); -#if START_ARM p->arm_proc = - GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-arm", + GNUNET_OS_start_process (GNUNET_YES, GNUNET_OS_INHERIT_STD_OUT_AND_ERR, NULL, NULL, binary, "gnunet-service-arm", -#if VERBOSE - "-L", "DEBUG", -#endif "-c", cfgname, NULL); -#endif GNUNET_assert (GNUNET_OK == GNUNET_CONFIGURATION_load (p->cfg, cfgname)); + GNUNET_free (binary); } static void stop_arm (struct PeerContext *p) { -#if START_ARM if (0 != GNUNET_OS_process_kill (p->arm_proc, SIGTERM)) GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); if (GNUNET_OS_process_wait (p->arm_proc) != GNUNET_OK) @@ -142,7 +134,6 @@ stop_arm (struct PeerContext *p) GNUNET_OS_process_get_pid (p->arm_proc)); GNUNET_OS_process_destroy (p->arm_proc); p->arm_proc = NULL; -#endif GNUNET_CONFIGURATION_destroy (p->cfg); } @@ -167,9 +158,8 @@ abort_test (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) static void timeout_kill (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { -#if VERBOSE - printf ("Timed out, stopping the test.\n"); -#endif + fprintf (stderr, + "Timed out, stopping the test.\n"); kill_task = GNUNET_SCHEDULER_NO_TASK; if (wait_task != GNUNET_SCHEDULER_NO_TASK) { @@ -186,9 +176,8 @@ join_cb (void *cls) { struct Wanted *want = cls; -#if VERBOSE - printf ("%s has joined\n", want->me); -#endif + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "%s has joined\n", want->me); if (NULL != want->next_task) GNUNET_SCHEDULER_add_now (want->next_task, want->next_task_cls); return GNUNET_OK; @@ -201,19 +190,18 @@ member_list_cb (void *cls, const struct GNUNET_CONTAINER_MetaData *member_info, enum GNUNET_CHAT_MsgOptions options) { struct Wanted *want = cls; - GNUNET_HashCode sender; - -#if VERBOSE - printf ("%s - told that %s has %s\n", want->me, - member_info == - NULL ? NULL : GNUNET_CONTAINER_meta_data_get_by_type (member_info, - EXTRACTOR_METATYPE_TITLE), - member_info == NULL ? "left" : "joined"); -#endif + struct GNUNET_HashCode sender; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "%s - told that %s has %s\n", want->me, + member_info == + NULL ? NULL : GNUNET_CONTAINER_meta_data_get_by_type (member_info, + EXTRACTOR_METATYPE_TITLE), + member_info == NULL ? "left" : "joined"); GNUNET_CRYPTO_hash (member_id, sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded), &sender); - if ((0 == memcmp (&sender, want->sender, sizeof (GNUNET_HashCode))) && + if ((0 == memcmp (&sender, want->sender, sizeof (struct GNUNET_HashCode))) && (((member_info == NULL) && (want->meta == NULL)) || ((member_info != NULL) && (want->meta != NULL) && (GNUNET_CONTAINER_meta_data_test_equal (member_info, want->meta)))) && @@ -234,23 +222,23 @@ member_list_cb (void *cls, const struct GNUNET_CONTAINER_MetaData *member_info, static int receive_cb (void *cls, struct GNUNET_CHAT_Room *room, - const GNUNET_HashCode * sender, + const struct GNUNET_HashCode * sender, const struct GNUNET_CONTAINER_MetaData *meta, const char *message, struct GNUNET_TIME_Absolute timestamp, enum GNUNET_CHAT_MsgOptions options) { struct Wanted *want = cls; -#if VERBOSE - printf ("%s - told that %s said %s\n", want->me, - meta == NULL ? NULL : GNUNET_CONTAINER_meta_data_get_by_type (meta, - EXTRACTOR_METATYPE_TITLE), - message); -#endif + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + + "%s - told that %s said %s\n", want->me, + meta == NULL ? NULL : GNUNET_CONTAINER_meta_data_get_by_type (meta, + EXTRACTOR_METATYPE_TITLE), + message); if ((0 == strcmp (message, want->msg)) && (((sender == NULL) && (want->sender == NULL)) || ((sender != NULL) && (want->sender != NULL) && - (0 == memcmp (sender, want->sender, sizeof (GNUNET_HashCode))))) && + (0 == memcmp (sender, want->sender, sizeof (struct GNUNET_HashCode))))) && (GNUNET_CONTAINER_meta_data_test_equal (meta, want->meta)) && (options == want->opt) && /* Not == since the library sets the actual timestamp, so it may be @@ -275,17 +263,16 @@ static int confirmation_cb (void *cls, struct GNUNET_CHAT_Room *room, uint32_t orig_seq_number, struct GNUNET_TIME_Absolute timestamp, - const GNUNET_HashCode * receiver) + const struct GNUNET_HashCode * receiver) { struct Wanted *want = cls; -#if VERBOSE - printf ("%s - told that %s acknowledged message #%d\n", want->me, - GNUNET_CONTAINER_meta_data_get_by_type (want->meta, - EXTRACTOR_METATYPE_TITLE), - orig_seq_number); -#endif - if ((0 == memcmp (receiver, want->sender, sizeof (GNUNET_HashCode))) && + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "%s - told that %s acknowledged message #%d\n", want->me, + GNUNET_CONTAINER_meta_data_get_by_type (want->meta, + EXTRACTOR_METATYPE_TITLE), + orig_seq_number); + if ((0 == memcmp (receiver, want->sender, sizeof (struct GNUNET_HashCode))) && (orig_seq_number == want->sequence_number) && (timestamp.abs_value >= want->timestamp.abs_value)) { @@ -307,9 +294,6 @@ wait_until_ready (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { GNUNET_SCHEDULER_Task task = cls; -#if VERBOSE - printf ("Waiting...\n"); -#endif if (is_ready) { wait_task = GNUNET_SCHEDULER_NO_TASK; @@ -326,9 +310,8 @@ wait_until_ready (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) static void disconnect_alice (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { -#if VERBOSE - printf ("Alice is leaving.\n"); -#endif + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Alice is leaving.\n"); if (is_p2p) stop_arm (&p2); GNUNET_CHAT_leave_room (alice_room); @@ -341,9 +324,8 @@ disconnect_alice (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) static void disconnect_bob (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { -#if VERBOSE - printf ("Bod is leaving.\n"); -#endif + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Bob is leaving.\n"); alice_wanted.meta = NULL; alice_wanted.sender = &bob; alice_wanted.msg = NULL; @@ -365,10 +347,8 @@ set_ready (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) static void send_to_alice (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { -#if VERBOSE - printf ("Bob says 'Hi!'\n"); -#endif - + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Bob says 'Hi!'\n"); alice_wanted.meta = bob_meta; alice_wanted.sender = &bob; alice_wanted.msg = "Hi Alice!"; @@ -387,9 +367,8 @@ send_to_bob (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) enum GNUNET_CHAT_MsgOptions options; uint32_t *seq = NULL; -#if VERBOSE - printf ("Alice says 'Hi!'\n"); -#endif + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Alice says 'Hi!'\n"); if (is_ackn) { options = GNUNET_CHAT_MSG_ACKNOWLEDGED; @@ -448,9 +427,8 @@ prepare_for_alice_task (void *cls, static void join_bob_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { -#if VERBOSE - printf ("Bob joining\n"); -#endif + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Bob joining\n"); alice_wanted.meta = bob_meta; alice_wanted.sender = &bob; alice_wanted.msg = NULL; @@ -479,9 +457,8 @@ join_bob_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) static void join_alice_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { -#if VERBOSE - printf ("Alice joining\n"); -#endif + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Alice joining\n"); alice_wanted.next_task = &join_bob_task; alice_wanted.next_task_cls = NULL; alice_room = @@ -536,9 +513,6 @@ main (int argc, char *argv[]) "test-chat", "-c", "test_chat_data.conf", -#if VERBOSE - "-L", "DEBUG", -#endif NULL }; struct GNUNET_GETOPT_CommandLineOption options[] = { @@ -546,11 +520,7 @@ main (int argc, char *argv[]) }; GNUNET_log_setup ("test_chat", -#if VERBOSE - "DEBUG", -#else "WARNING", -#endif NULL); if (strstr (argv[0], "p2p") != NULL) { diff --git a/src/chat/test_chat_data.conf b/src/chat/test_chat_data.conf index 3052a4f..45a6ce7 100644 --- a/src/chat/test_chat_data.conf +++ b/src/chat/test_chat_data.conf @@ -1,6 +1,5 @@ [PATHS] SERVICEHOME = /tmp/gnunet-test-chat/ -DEFAULTCONFIG = test_chat_data.conf [gnunetd] HOSTKEY = $SERVICEHOME/.hostkey @@ -30,7 +29,6 @@ HOSTNAME = localhost PORT = 42471 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-chat [testing] @@ -48,7 +46,8 @@ EXTERNAL_ADDRESS = 127.0.0.1 [dns] AUTOSTART = NO - +[consensus] +AUTOSTART = NO [nse] AUTOSTART = NO diff --git a/src/chat/test_chat_peer1.conf b/src/chat/test_chat_peer1.conf index 73280da..0193188 100644 --- a/src/chat/test_chat_peer1.conf +++ b/src/chat/test_chat_peer1.conf @@ -1,6 +1,5 @@ [PATHS] SERVICEHOME = /tmp/gnunet-test-chat-peer-1/ -DEFAULTCONFIG = test_chat_peer1.conf [gnunetd] HOSTKEY = $SERVICEHOME/.hostkey @@ -41,7 +40,6 @@ FRIENDS-ONLY = NO AUTOCONNECT = YES TARGET-CONNECTION-COUNT = 16 FRIENDS = $SERVICEHOME/friends -CONFIG = $DEFAULTCONFIG BINARY = gnunet-daemon-topology [peerinfo] @@ -58,7 +56,6 @@ UNIXPATH = /tmp/gnunet-chat-p1-service-statistics.sock PORT = 31008 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-chat [testing] diff --git a/src/chat/test_chat_peer2.conf b/src/chat/test_chat_peer2.conf index 00808b5..c4a31a0 100644 --- a/src/chat/test_chat_peer2.conf +++ b/src/chat/test_chat_peer2.conf @@ -1,6 +1,5 @@ [PATHS] SERVICEHOME = /tmp/gnunet-test-chat-peer-2/ -DEFAULTCONFIG = test_chat_peer2.conf [gnunetd] HOSTKEY = $SERVICEHOME/.hostkey @@ -41,7 +40,6 @@ FRIENDS-ONLY = NO AUTOCONNECT = YES TARGET-CONNECTION-COUNT = 16 FRIENDS = $SERVICEHOME/friends -CONFIG = $DEFAULTCONFIG BINARY = gnunet-daemon-topology [peerinfo] @@ -58,7 +56,6 @@ UNIXPATH = /tmp/gnunet-chat-p2-service-statistics.sock PORT = 32008 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-chat [testing] diff --git a/src/chat/test_chat_peer3.conf b/src/chat/test_chat_peer3.conf index a394523..d8dcedc 100644 --- a/src/chat/test_chat_peer3.conf +++ b/src/chat/test_chat_peer3.conf @@ -1,6 +1,5 @@ [PATHS] SERVICEHOME = /tmp/gnunet-test-chat-peer-3/ -DEFAULTCONFIG = test_chat_peer3.conf [gnunetd] HOSTKEY = $SERVICEHOME/.hostkey @@ -41,7 +40,6 @@ FRIENDS-ONLY = NO AUTOCONNECT = YES TARGET-CONNECTION-COUNT = 16 FRIENDS = $SERVICEHOME/friends -CONFIG = $DEFAULTCONFIG BINARY = gnunet-daemon-topology [peerinfo] @@ -58,7 +56,6 @@ UNIXPATH = /tmp/gnunet-chat-p3-service-statistics.sock PORT = 33008 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-chat [testing] diff --git a/src/chat/test_chat_private.c b/src/chat/test_chat_private.c index 8b61392..b911d09 100644 --- a/src/chat/test_chat_private.c +++ b/src/chat/test_chat_private.c @@ -32,8 +32,6 @@ #define VERBOSE GNUNET_NO -#define START_ARM GNUNET_YES - /** * How long until we give up on passing the test? */ @@ -47,16 +45,14 @@ struct PeerContext { struct GNUNET_CONFIGURATION_Handle *cfg; -#if START_ARM struct GNUNET_OS_Process *arm_proc; -#endif }; struct Wanted { struct GNUNET_CONTAINER_MetaData *meta; - GNUNET_HashCode *sender; + struct GNUNET_HashCode *sender; /** * Alternative meta/sender is used when we expect join/leave notification @@ -64,7 +60,7 @@ struct Wanted */ struct GNUNET_CONTAINER_MetaData *meta2; - GNUNET_HashCode *sender2; + struct GNUNET_HashCode *sender2; char *msg; @@ -86,11 +82,11 @@ static struct PeerContext p2; static struct PeerContext p3; -static GNUNET_HashCode alice; +static struct GNUNET_HashCode alice; -static GNUNET_HashCode bob; +static struct GNUNET_HashCode bob; -static GNUNET_HashCode carol; +static struct GNUNET_HashCode carol; static struct GNUNET_CHAT_Room *alice_room; @@ -124,30 +120,28 @@ static int bob_ready; static int is_p2p; -struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *bob_public_key = NULL; +static struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *bob_public_key; static void setup_peer (struct PeerContext *p, const char *cfgname) { + char *binary; + + binary = GNUNET_OS_get_libexec_binary_path ("gnunet-service-arm"); p->cfg = GNUNET_CONFIGURATION_create (); -#if START_ARM p->arm_proc = - GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-arm", + GNUNET_OS_start_process (GNUNET_YES, GNUNET_OS_INHERIT_STD_OUT_AND_ERR, NULL, NULL, binary, "gnunet-service-arm", -#if VERBOSE - "-L", "DEBUG", -#endif "-c", cfgname, NULL); -#endif GNUNET_assert (GNUNET_OK == GNUNET_CONFIGURATION_load (p->cfg, cfgname)); + GNUNET_free (binary); } static void stop_arm (struct PeerContext *p) { -#if START_ARM if (0 != GNUNET_OS_process_kill (p->arm_proc, SIGTERM)) GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); if (GNUNET_OS_process_wait (p->arm_proc) != GNUNET_OK) @@ -156,7 +150,6 @@ stop_arm (struct PeerContext *p) GNUNET_OS_process_get_pid (p->arm_proc)); GNUNET_OS_process_destroy (p->arm_proc); p->arm_proc = NULL; -#endif GNUNET_CONFIGURATION_destroy (p->cfg); } @@ -220,7 +213,7 @@ member_list_cb (void *cls, const struct GNUNET_CONTAINER_MetaData *member_info, enum GNUNET_CHAT_MsgOptions options) { struct Wanted *want = cls; - GNUNET_HashCode sender; + struct GNUNET_HashCode sender; #if VERBOSE printf ("%s - told that %s has %s\n", want->me, @@ -233,9 +226,9 @@ member_list_cb (void *cls, const struct GNUNET_CONTAINER_MetaData *member_info, sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded), &sender); /* entertain both primary and an alternative sender/meta */ - if (((0 == memcmp (&sender, want->sender, sizeof (GNUNET_HashCode))) || + if (((0 == memcmp (&sender, want->sender, sizeof (struct GNUNET_HashCode))) || ((want->sender2 != NULL) && - (0 == memcmp (&sender, want->sender2, sizeof (GNUNET_HashCode))))) && + (0 == memcmp (&sender, want->sender2, sizeof (struct GNUNET_HashCode))))) && (((member_info == NULL) && (want->meta == NULL)) || ((member_info != NULL) && (((want->meta != NULL) && @@ -246,7 +239,7 @@ member_list_cb (void *cls, const struct GNUNET_CONTAINER_MetaData *member_info, { /* remember Bob's public key, we need it to send private message */ if (NULL == bob_public_key && - (0 == memcmp (&bob, want->sender, sizeof (GNUNET_HashCode)))) + (0 == memcmp (&bob, want->sender, sizeof (struct GNUNET_HashCode)))) bob_public_key = GNUNET_memdup (member_id, sizeof (struct @@ -254,7 +247,7 @@ member_list_cb (void *cls, const struct GNUNET_CONTAINER_MetaData *member_info, if (want->sender2 != NULL) { /* flush alternative sender */ - if (0 == memcmp (&sender, want->sender, sizeof (GNUNET_HashCode))) + if (0 == memcmp (&sender, want->sender, sizeof (struct GNUNET_HashCode))) { want->sender = want->sender2; want->meta = want->meta2; @@ -277,7 +270,7 @@ member_list_cb (void *cls, const struct GNUNET_CONTAINER_MetaData *member_info, static int receive_cb (void *cls, struct GNUNET_CHAT_Room *room, - const GNUNET_HashCode * sender, + const struct GNUNET_HashCode * sender, const struct GNUNET_CONTAINER_MetaData *meta, const char *message, struct GNUNET_TIME_Absolute timestamp, enum GNUNET_CHAT_MsgOptions options) @@ -294,7 +287,7 @@ receive_cb (void *cls, struct GNUNET_CHAT_Room *room, if ((want->msg != NULL) && (0 == strcmp (message, want->msg)) && (((sender == NULL) && (want->sender == NULL)) || ((sender != NULL) && (want->sender != NULL) && - (0 == memcmp (sender, want->sender, sizeof (GNUNET_HashCode))))) && + (0 == memcmp (sender, want->sender, sizeof (struct GNUNET_HashCode))))) && (GNUNET_CONTAINER_meta_data_test_equal (meta, want->meta)) && (options == want->opt) && /* Not == since the library sets the actual timestamp, so it may be @@ -614,9 +607,6 @@ main (int argc, char *argv[]) "test-chat", "-c", "test_chat_data.conf", -#if VERBOSE - "-L", "DEBUG", -#endif NULL }; struct GNUNET_GETOPT_CommandLineOption options[] = { @@ -624,11 +614,7 @@ main (int argc, char *argv[]) }; GNUNET_log_setup ("test_chat", -#if VERBOSE - "DEBUG", -#else "WARNING", -#endif NULL); if (strstr (argv[0], "p2p") != NULL) { diff --git a/src/consensus/Makefile.am b/src/consensus/Makefile.am new file mode 100644 index 0000000..f5a5c5c --- /dev/null +++ b/src/consensus/Makefile.am @@ -0,0 +1,90 @@ +INCLUDES = -I$(top_srcdir)/src/include + +pkgcfgdir= $(pkgdatadir)/config.d/ + +libexecdir= $(pkglibdir)/libexec/ + +pkgcfg_DATA = \ + consensus.conf + +if MINGW + WINFLAGS = -Wl,--no-undefined -Wl,--export-all-symbols +endif + +if USE_COVERAGE + AM_CFLAGS = -fprofile-arcs -ftest-coverage +endif + +bin_PROGRAMS = \ + gnunet-consensus \ + gnunet-consensus-start-peers \ + gnunet-consensus-ibf + +libexec_PROGRAMS = \ + gnunet-service-consensus + +lib_LTLIBRARIES = \ + libgnunetconsensus.la + +gnunet_consensus_SOURCES = \ + gnunet-consensus.c +gnunet_consensus_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/consensus/libgnunetconsensus.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la \ + $(GN_LIBINTL) +gnunet_consensus_DEPENDENCIES = \ + libgnunetconsensus.la + +gnunet_consensus_start_peers_SOURCES = \ + gnunet-consensus-start-peers.c +gnunet_consensus_start_peers_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la \ + $(top_builddir)/src/consensus/libgnunetconsensus.la \ + $(GN_LIBINTL) +gnunet_consensus_start_peers_DEPENDENCIES = \ + libgnunetconsensus.la + +gnunet_consensus_ibf_SOURCES = \ + gnunet-consensus-ibf.c \ + ibf.c +gnunet_consensus_ibf_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(GN_LIBINTL) + +gnunet_service_consensus_SOURCES = \ + gnunet-service-consensus.c \ + ibf.c +gnunet_service_consensus_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/core/libgnunetcore.la \ + $(top_builddir)/src/stream/libgnunetstream.la \ + $(top_builddir)/src/mesh/libgnunetmesh.la \ + $(GN_LIBINTL) + +libgnunetconsensus_la_SOURCES = \ + consensus_api.c +libgnunetconsensus_la_LIBADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(LTLIBINTL) +libgnunetconsensus_la_LDFLAGS = \ + $(GN_LIB_LDFLAGS) + +check_PROGRAMS = \ + test_consensus_api + +if ENABLE_TEST_RUN +TESTS = $(check_PROGRAMS) +endif + +test_consensus_api_SOURCES = \ + test_consensus_api.c +test_consensus_api_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/consensus/libgnunetconsensus.la + +EXTRA_DIST = \ + test_consensus.conf + diff --git a/src/consensus/Makefile.in b/src/consensus/Makefile.in new file mode 100644 index 0000000..696bb18 --- /dev/null +++ b/src/consensus/Makefile.in @@ -0,0 +1,1059 @@ +# Makefile.in generated by automake 1.11.6 from Makefile.am. +# @configure_input@ + +# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, +# 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Free Software +# Foundation, Inc. +# This Makefile.in is free software; the Free Software Foundation +# gives unlimited permission to copy and/or distribute it, +# with or without modifications, as long as this notice is preserved. + +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY, to the extent permitted by law; without +# even the implied warranty of MERCHANTABILITY or FITNESS FOR A +# PARTICULAR PURPOSE. + +@SET_MAKE@ + + + +VPATH = @srcdir@ +am__make_dryrun = \ + { \ + am__dry=no; \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + echo 'am--echo: ; @echo "AM" OK' | $(MAKE) -f - 2>/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } +pkgdatadir = $(datadir)/@PACKAGE@ +pkgincludedir = $(includedir)/@PACKAGE@ +pkglibdir = $(libdir)/@PACKAGE@ +pkglibexecdir = $(libexecdir)/@PACKAGE@ +am__cd = CDPATH="$${ZSH_VERSION+.}$(PATH_SEPARATOR)" && cd +install_sh_DATA = $(install_sh) -c -m 644 +install_sh_PROGRAM = $(install_sh) -c +install_sh_SCRIPT = $(install_sh) -c +INSTALL_HEADER = $(INSTALL_DATA) +transform = $(program_transform_name) +NORMAL_INSTALL = : +PRE_INSTALL = : +POST_INSTALL = : +NORMAL_UNINSTALL = : +PRE_UNINSTALL = : +POST_UNINSTALL = : +build_triplet = @build@ +host_triplet = @host@ +target_triplet = @target@ +bin_PROGRAMS = gnunet-consensus$(EXEEXT) \ + gnunet-consensus-start-peers$(EXEEXT) \ + gnunet-consensus-ibf$(EXEEXT) +libexec_PROGRAMS = gnunet-service-consensus$(EXEEXT) +check_PROGRAMS = test_consensus_api$(EXEEXT) +subdir = src/consensus +DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in \ + $(srcdir)/consensus.conf.in +ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 +am__aclocal_m4_deps = $(top_srcdir)/m4/absolute-header.m4 \ + $(top_srcdir)/m4/align.m4 $(top_srcdir)/m4/argz.m4 \ + $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/glib-2.0.m4 \ + $(top_srcdir)/m4/iconv.m4 $(top_srcdir)/m4/lib-ld.m4 \ + $(top_srcdir)/m4/lib-link.m4 $(top_srcdir)/m4/lib-prefix.m4 \ + $(top_srcdir)/m4/libcurl.m4 $(top_srcdir)/m4/libgcrypt.m4 \ + $(top_srcdir)/m4/libtool.m4 $(top_srcdir)/m4/libunistring.m4 \ + $(top_srcdir)/m4/ltdl.m4 $(top_srcdir)/m4/ltoptions.m4 \ + $(top_srcdir)/m4/ltsugar.m4 $(top_srcdir)/m4/ltversion.m4 \ + $(top_srcdir)/m4/lt~obsolete.m4 $(top_srcdir)/m4/nls.m4 \ + $(top_srcdir)/m4/pkg.m4 $(top_srcdir)/m4/po.m4 \ + $(top_srcdir)/m4/progtest.m4 $(top_srcdir)/acinclude.m4 \ + $(top_srcdir)/configure.ac +am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ + $(ACLOCAL_M4) +mkinstalldirs = $(install_sh) -d +CONFIG_HEADER = $(top_builddir)/gnunet_config.h +CONFIG_CLEAN_FILES = consensus.conf +CONFIG_CLEAN_VPATH_FILES = +am__vpath_adj_setup = srcdirstrip=`echo "$(srcdir)" | sed 's|.|.|g'`; +am__vpath_adj = case $$p in \ + $(srcdir)/*) f=`echo "$$p" | sed "s|^$$srcdirstrip/||"`;; \ + *) f=$$p;; \ + esac; +am__strip_dir = f=`echo $$p | sed -e 's|^.*/||'`; +am__install_max = 40 +am__nobase_strip_setup = \ + srcdirstrip=`echo "$(srcdir)" | sed 's/[].[^$$\\*|]/\\\\&/g'` +am__nobase_strip = \ + for p in $$list; do echo "$$p"; done | sed -e "s|$$srcdirstrip/||" +am__nobase_list = $(am__nobase_strip_setup); \ + for p in $$list; do echo "$$p $$p"; done | \ + sed "s| $$srcdirstrip/| |;"' / .*\//!s/ .*/ ./; s,\( .*\)/[^/]*$$,\1,' | \ + $(AWK) 'BEGIN { files["."] = "" } { files[$$2] = files[$$2] " " $$1; \ + if (++n[$$2] == $(am__install_max)) \ + { print $$2, files[$$2]; n[$$2] = 0; files[$$2] = "" } } \ + END { for (dir in files) print dir, files[dir] }' +am__base_list = \ + sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \ + sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g' +am__uninstall_files_from_dir = { \ + test -z "$$files" \ + || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \ + || { echo " ( cd '$$dir' && rm -f" $$files ")"; \ + $(am__cd) "$$dir" && rm -f $$files; }; \ + } +am__installdirs = "$(DESTDIR)$(libdir)" "$(DESTDIR)$(bindir)" \ + "$(DESTDIR)$(libexecdir)" "$(DESTDIR)$(pkgcfgdir)" +LTLIBRARIES = $(lib_LTLIBRARIES) +am__DEPENDENCIES_1 = +libgnunetconsensus_la_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(am__DEPENDENCIES_1) +am_libgnunetconsensus_la_OBJECTS = consensus_api.lo +libgnunetconsensus_la_OBJECTS = $(am_libgnunetconsensus_la_OBJECTS) +AM_V_lt = $(am__v_lt_@AM_V@) +am__v_lt_ = $(am__v_lt_@AM_DEFAULT_V@) +am__v_lt_0 = --silent +libgnunetconsensus_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ + $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ + $(AM_CFLAGS) $(CFLAGS) $(libgnunetconsensus_la_LDFLAGS) \ + $(LDFLAGS) -o $@ +PROGRAMS = $(bin_PROGRAMS) $(libexec_PROGRAMS) +am_gnunet_consensus_OBJECTS = gnunet-consensus.$(OBJEXT) +gnunet_consensus_OBJECTS = $(am_gnunet_consensus_OBJECTS) +am_gnunet_consensus_ibf_OBJECTS = gnunet-consensus-ibf.$(OBJEXT) \ + ibf.$(OBJEXT) +gnunet_consensus_ibf_OBJECTS = $(am_gnunet_consensus_ibf_OBJECTS) +gnunet_consensus_ibf_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(am__DEPENDENCIES_1) +am_gnunet_consensus_start_peers_OBJECTS = \ + gnunet-consensus-start-peers.$(OBJEXT) +gnunet_consensus_start_peers_OBJECTS = \ + $(am_gnunet_consensus_start_peers_OBJECTS) +am_gnunet_service_consensus_OBJECTS = \ + gnunet-service-consensus.$(OBJEXT) ibf.$(OBJEXT) +gnunet_service_consensus_OBJECTS = \ + $(am_gnunet_service_consensus_OBJECTS) +gnunet_service_consensus_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/core/libgnunetcore.la \ + $(top_builddir)/src/stream/libgnunetstream.la \ + $(top_builddir)/src/mesh/libgnunetmesh.la \ + $(am__DEPENDENCIES_1) +am_test_consensus_api_OBJECTS = test_consensus_api.$(OBJEXT) +test_consensus_api_OBJECTS = $(am_test_consensus_api_OBJECTS) +test_consensus_api_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/consensus/libgnunetconsensus.la +DEFAULT_INCLUDES = -I.@am__isrc@ -I$(top_builddir) +depcomp = $(SHELL) $(top_srcdir)/depcomp +am__depfiles_maybe = depfiles +am__mv = mv -f +COMPILE = $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) \ + $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) +LTCOMPILE = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ + $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) \ + $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) \ + $(AM_CFLAGS) $(CFLAGS) +AM_V_CC = $(am__v_CC_@AM_V@) +am__v_CC_ = $(am__v_CC_@AM_DEFAULT_V@) +am__v_CC_0 = @echo " CC " $@; +AM_V_at = $(am__v_at_@AM_V@) +am__v_at_ = $(am__v_at_@AM_DEFAULT_V@) +am__v_at_0 = @ +CCLD = $(CC) +LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ + $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ + $(AM_LDFLAGS) $(LDFLAGS) -o $@ +AM_V_CCLD = $(am__v_CCLD_@AM_V@) +am__v_CCLD_ = $(am__v_CCLD_@AM_DEFAULT_V@) +am__v_CCLD_0 = @echo " CCLD " $@; +AM_V_GEN = $(am__v_GEN_@AM_V@) +am__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@) +am__v_GEN_0 = @echo " GEN " $@; +SOURCES = $(libgnunetconsensus_la_SOURCES) $(gnunet_consensus_SOURCES) \ + $(gnunet_consensus_ibf_SOURCES) \ + $(gnunet_consensus_start_peers_SOURCES) \ + $(gnunet_service_consensus_SOURCES) \ + $(test_consensus_api_SOURCES) +DIST_SOURCES = $(libgnunetconsensus_la_SOURCES) \ + $(gnunet_consensus_SOURCES) $(gnunet_consensus_ibf_SOURCES) \ + $(gnunet_consensus_start_peers_SOURCES) \ + $(gnunet_service_consensus_SOURCES) \ + $(test_consensus_api_SOURCES) +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac +DATA = $(pkgcfg_DATA) +ETAGS = etags +CTAGS = ctags +am__tty_colors = \ +red=; grn=; lgn=; blu=; std= +DISTFILES = $(DIST_COMMON) $(DIST_SOURCES) $(TEXINFOS) $(EXTRA_DIST) +ACLOCAL = @ACLOCAL@ +AMTAR = @AMTAR@ +AM_DEFAULT_VERBOSITY = @AM_DEFAULT_VERBOSITY@ +AR = @AR@ +ARGZ_H = @ARGZ_H@ +AS = @AS@ +AUTOCONF = @AUTOCONF@ +AUTOHEADER = @AUTOHEADER@ +AUTOMAKE = @AUTOMAKE@ +AWK = @AWK@ +CC = @CC@ +CCDEPMODE = @CCDEPMODE@ +CFLAGS = @CFLAGS@ +CPP = @CPP@ +CPPFLAGS = @CPPFLAGS@ +CXX = @CXX@ +CXXCPP = @CXXCPP@ +CXXDEPMODE = @CXXDEPMODE@ +CXXFLAGS = @CXXFLAGS@ +CYGPATH_W = @CYGPATH_W@ +DEFAULT_INTERFACE = @DEFAULT_INTERFACE@ +DEFS = @DEFS@ +DEPDIR = @DEPDIR@ +DLLDIR = @DLLDIR@ +DLLTOOL = @DLLTOOL@ +DSYMUTIL = @DSYMUTIL@ +DUMPBIN = @DUMPBIN@ +ECHO_C = @ECHO_C@ +ECHO_N = @ECHO_N@ +ECHO_T = @ECHO_T@ +EGREP = @EGREP@ +EXEEXT = @EXEEXT@ +EXT_LIBS = @EXT_LIBS@ +EXT_LIB_PATH = @EXT_LIB_PATH@ +FGREP = @FGREP@ +GLIB_CFLAGS = @GLIB_CFLAGS@ +GLIB_GENMARSHAL = @GLIB_GENMARSHAL@ +GLIB_LIBS = @GLIB_LIBS@ +GLIB_MKENUMS = @GLIB_MKENUMS@ +GMSGFMT = @GMSGFMT@ +GMSGFMT_015 = @GMSGFMT_015@ +GNUNETDNS_GROUP = @GNUNETDNS_GROUP@ +GN_DAEMON_CONFIG_DIR = @GN_DAEMON_CONFIG_DIR@ +GN_DAEMON_HOME_DIR = @GN_DAEMON_HOME_DIR@ +GN_INTLINCL = @GN_INTLINCL@ +GN_LIBINTL = @GN_LIBINTL@ +GN_LIB_LDFLAGS = @GN_LIB_LDFLAGS@ +GN_PLUGIN_LDFLAGS = @GN_PLUGIN_LDFLAGS@ +GN_USER_HOME_DIR = @GN_USER_HOME_DIR@ +GOBJECT_QUERY = @GOBJECT_QUERY@ +GREP = @GREP@ +HAVE_LIBUNISTRING = @HAVE_LIBUNISTRING@ +INCLTDL = @INCLTDL@ +INSTALL = @INSTALL@ +INSTALL_DATA = @INSTALL_DATA@ +INSTALL_PROGRAM = @INSTALL_PROGRAM@ +INSTALL_SCRIPT = @INSTALL_SCRIPT@ +INSTALL_STRIP_PROGRAM = @INSTALL_STRIP_PROGRAM@ +INTLLIBS = @INTLLIBS@ +INTL_MACOSX_LIBS = @INTL_MACOSX_LIBS@ +JAVAPORT = @JAVAPORT@ +LD = @LD@ +LDFLAGS = @LDFLAGS@ +LIBADD_DL = @LIBADD_DL@ +LIBADD_DLD_LINK = @LIBADD_DLD_LINK@ +LIBADD_DLOPEN = @LIBADD_DLOPEN@ +LIBADD_SHL_LOAD = @LIBADD_SHL_LOAD@ +LIBCURL = @LIBCURL@ +LIBCURL_CPPFLAGS = @LIBCURL_CPPFLAGS@ +LIBGCRYPT_CFLAGS = @LIBGCRYPT_CFLAGS@ +LIBGCRYPT_CONFIG = @LIBGCRYPT_CONFIG@ +LIBGCRYPT_LIBS = @LIBGCRYPT_LIBS@ +LIBGTOP_CFLAGS = @LIBGTOP_CFLAGS@ +LIBGTOP_LIBS = @LIBGTOP_LIBS@ +LIBICONV = @LIBICONV@ +LIBINTL = @LIBINTL@ +LIBLTDL = @LIBLTDL@ +LIBOBJS = @LIBOBJS@ +LIBPREFIX = @LIBPREFIX@ +LIBS = @LIBS@ +LIBTOOL = @LIBTOOL@ +LIBUNISTRING = @LIBUNISTRING@ +LIPO = @LIPO@ +LN_S = @LN_S@ +LTDLDEPS = @LTDLDEPS@ +LTDLINCL = @LTDLINCL@ +LTDLOPEN = @LTDLOPEN@ +LTLIBICONV = @LTLIBICONV@ +LTLIBINTL = @LTLIBINTL@ +LTLIBOBJS = @LTLIBOBJS@ +LTLIBUNISTRING = @LTLIBUNISTRING@ +LT_CONFIG_H = @LT_CONFIG_H@ +LT_DLLOADERS = @LT_DLLOADERS@ +LT_DLPREOPEN = @LT_DLPREOPEN@ +MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ +MKDIR_P = @MKDIR_P@ +MONKEYPREFIX = @MONKEYPREFIX@ +MSGFMT = @MSGFMT@ +MSGFMT_015 = @MSGFMT_015@ +MSGMERGE = @MSGMERGE@ +MYSQL_CPPFLAGS = @MYSQL_CPPFLAGS@ +MYSQL_LDFLAGS = @MYSQL_LDFLAGS@ +NM = @NM@ +NMEDIT = @NMEDIT@ +NSS_DIR = @NSS_DIR@ +OBJC = @OBJC@ +OBJCDEPMODE = @OBJCDEPMODE@ +OBJCFLAGS = @OBJCFLAGS@ +OBJDUMP = @OBJDUMP@ +OBJEXT = @OBJEXT@ +OTOOL = @OTOOL@ +OTOOL64 = @OTOOL64@ +PACKAGE = @PACKAGE@ +PACKAGE_BUGREPORT = @PACKAGE_BUGREPORT@ +PACKAGE_NAME = @PACKAGE_NAME@ +PACKAGE_STRING = @PACKAGE_STRING@ +PACKAGE_TARNAME = @PACKAGE_TARNAME@ +PACKAGE_URL = @PACKAGE_URL@ +PACKAGE_VERSION = @PACKAGE_VERSION@ +PATH_SEPARATOR = @PATH_SEPARATOR@ +PKG_CONFIG = @PKG_CONFIG@ +POSTGRES_CPPFLAGS = @POSTGRES_CPPFLAGS@ +POSTGRES_LDFLAGS = @POSTGRES_LDFLAGS@ +POSUB = @POSUB@ +PYTHON = @PYTHON@ +PYTHON_EXEC_PREFIX = @PYTHON_EXEC_PREFIX@ +PYTHON_PLATFORM = @PYTHON_PLATFORM@ +PYTHON_PREFIX = @PYTHON_PREFIX@ +PYTHON_VERSION = @PYTHON_VERSION@ +RANLIB = @RANLIB@ +SED = @SED@ +SET_MAKE = @SET_MAKE@ +SHELL = @SHELL@ +SQLITE_CPPFLAGS = @SQLITE_CPPFLAGS@ +SQLITE_LDFLAGS = @SQLITE_LDFLAGS@ +STRIP = @STRIP@ +SUDO_BINARY = @SUDO_BINARY@ +UNIXONLY = @UNIXONLY@ +USE_NLS = @USE_NLS@ +VERSION = @VERSION@ +XGETTEXT = @XGETTEXT@ +XGETTEXT_015 = @XGETTEXT_015@ +XMKMF = @XMKMF@ +X_CFLAGS = @X_CFLAGS@ +X_EXTRA_LIBS = @X_EXTRA_LIBS@ +X_LIBS = @X_LIBS@ +X_PRE_LIBS = @X_PRE_LIBS@ +_libcurl_config = @_libcurl_config@ +abs_builddir = @abs_builddir@ +abs_srcdir = @abs_srcdir@ +abs_top_builddir = @abs_top_builddir@ +abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ +ac_ct_CC = @ac_ct_CC@ +ac_ct_CXX = @ac_ct_CXX@ +ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ +ac_ct_OBJC = @ac_ct_OBJC@ +am__include = @am__include@ +am__leading_dot = @am__leading_dot@ +am__quote = @am__quote@ +am__tar = @am__tar@ +am__untar = @am__untar@ +bindir = @bindir@ +build = @build@ +build_alias = @build_alias@ +build_cpu = @build_cpu@ +build_os = @build_os@ +build_target = @build_target@ +build_vendor = @build_vendor@ +builddir = @builddir@ +datadir = @datadir@ +datarootdir = @datarootdir@ +docdir = @docdir@ +dvidir = @dvidir@ +exec_prefix = @exec_prefix@ +gitcommand = @gitcommand@ +host = @host@ +host_alias = @host_alias@ +host_cpu = @host_cpu@ +host_os = @host_os@ +host_vendor = @host_vendor@ +htmldir = @htmldir@ +includedir = @includedir@ +infodir = @infodir@ +install_sh = @install_sh@ +libdir = @libdir@ +libexecdir = $(pkglibdir)/libexec/ +localedir = @localedir@ +localstatedir = @localstatedir@ +ltdl_LIBOBJS = @ltdl_LIBOBJS@ +ltdl_LTLIBOBJS = @ltdl_LTLIBOBJS@ +mandir = @mandir@ +mkdir_p = @mkdir_p@ +oldincludedir = @oldincludedir@ +pdfdir = @pdfdir@ +pkgpyexecdir = @pkgpyexecdir@ +pkgpythondir = @pkgpythondir@ +prefix = @prefix@ +program_transform_name = @program_transform_name@ +psdir = @psdir@ +pyexecdir = @pyexecdir@ +pythondir = @pythondir@ +sbindir = @sbindir@ +sharedstatedir = @sharedstatedir@ +srcdir = @srcdir@ +subdirs = @subdirs@ +svnversioncommand = @svnversioncommand@ +sys_symbol_underscore = @sys_symbol_underscore@ +sysconfdir = @sysconfdir@ +target = @target@ +target_alias = @target_alias@ +target_cpu = @target_cpu@ +target_os = @target_os@ +target_vendor = @target_vendor@ +top_build_prefix = @top_build_prefix@ +top_builddir = @top_builddir@ +top_srcdir = @top_srcdir@ +INCLUDES = -I$(top_srcdir)/src/include +pkgcfgdir = $(pkgdatadir)/config.d/ +pkgcfg_DATA = \ + consensus.conf + +@MINGW_TRUE@WINFLAGS = -Wl,--no-undefined -Wl,--export-all-symbols +@USE_COVERAGE_TRUE@AM_CFLAGS = -fprofile-arcs -ftest-coverage +lib_LTLIBRARIES = \ + libgnunetconsensus.la + +gnunet_consensus_SOURCES = \ + gnunet-consensus.c + +gnunet_consensus_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/consensus/libgnunetconsensus.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la \ + $(GN_LIBINTL) + +gnunet_consensus_DEPENDENCIES = \ + libgnunetconsensus.la + +gnunet_consensus_start_peers_SOURCES = \ + gnunet-consensus-start-peers.c + +gnunet_consensus_start_peers_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la \ + $(top_builddir)/src/consensus/libgnunetconsensus.la \ + $(GN_LIBINTL) + +gnunet_consensus_start_peers_DEPENDENCIES = \ + libgnunetconsensus.la + +gnunet_consensus_ibf_SOURCES = \ + gnunet-consensus-ibf.c \ + ibf.c + +gnunet_consensus_ibf_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(GN_LIBINTL) + +gnunet_service_consensus_SOURCES = \ + gnunet-service-consensus.c \ + ibf.c + +gnunet_service_consensus_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/core/libgnunetcore.la \ + $(top_builddir)/src/stream/libgnunetstream.la \ + $(top_builddir)/src/mesh/libgnunetmesh.la \ + $(GN_LIBINTL) + +libgnunetconsensus_la_SOURCES = \ + consensus_api.c + +libgnunetconsensus_la_LIBADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(LTLIBINTL) + +libgnunetconsensus_la_LDFLAGS = \ + $(GN_LIB_LDFLAGS) + +@ENABLE_TEST_RUN_TRUE@TESTS = $(check_PROGRAMS) +test_consensus_api_SOURCES = \ + test_consensus_api.c + +test_consensus_api_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/consensus/libgnunetconsensus.la + +EXTRA_DIST = \ + test_consensus.conf + +all: all-am + +.SUFFIXES: +.SUFFIXES: .c .lo .o .obj +$(srcdir)/Makefile.in: $(srcdir)/Makefile.am $(am__configure_deps) + @for dep in $?; do \ + case '$(am__configure_deps)' in \ + *$$dep*) \ + ( cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh ) \ + && { if test -f $@; then exit 0; else break; fi; }; \ + exit 1;; \ + esac; \ + done; \ + echo ' cd $(top_srcdir) && $(AUTOMAKE) --gnu src/consensus/Makefile'; \ + $(am__cd) $(top_srcdir) && \ + $(AUTOMAKE) --gnu src/consensus/Makefile +.PRECIOUS: Makefile +Makefile: $(srcdir)/Makefile.in $(top_builddir)/config.status + @case '$?' in \ + *config.status*) \ + cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh;; \ + *) \ + echo ' cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ $(am__depfiles_maybe)'; \ + cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ $(am__depfiles_maybe);; \ + esac; + +$(top_builddir)/config.status: $(top_srcdir)/configure $(CONFIG_STATUS_DEPENDENCIES) + cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh + +$(top_srcdir)/configure: $(am__configure_deps) + cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh +$(ACLOCAL_M4): $(am__aclocal_m4_deps) + cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh +$(am__aclocal_m4_deps): +consensus.conf: $(top_builddir)/config.status $(srcdir)/consensus.conf.in + cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ +install-libLTLIBRARIES: $(lib_LTLIBRARIES) + @$(NORMAL_INSTALL) + @list='$(lib_LTLIBRARIES)'; test -n "$(libdir)" || list=; \ + list2=; for p in $$list; do \ + if test -f $$p; then \ + list2="$$list2 $$p"; \ + else :; fi; \ + done; \ + test -z "$$list2" || { \ + echo " $(MKDIR_P) '$(DESTDIR)$(libdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libdir)" || exit 1; \ + echo " $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 '$(DESTDIR)$(libdir)'"; \ + $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 "$(DESTDIR)$(libdir)"; \ + } + +uninstall-libLTLIBRARIES: + @$(NORMAL_UNINSTALL) + @list='$(lib_LTLIBRARIES)'; test -n "$(libdir)" || list=; \ + for p in $$list; do \ + $(am__strip_dir) \ + echo " $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=uninstall rm -f '$(DESTDIR)$(libdir)/$$f'"; \ + $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=uninstall rm -f "$(DESTDIR)$(libdir)/$$f"; \ + done + +clean-libLTLIBRARIES: + -test -z "$(lib_LTLIBRARIES)" || rm -f $(lib_LTLIBRARIES) + @list='$(lib_LTLIBRARIES)'; for p in $$list; do \ + dir="`echo $$p | sed -e 's|/[^/]*$$||'`"; \ + test "$$dir" != "$$p" || dir=.; \ + echo "rm -f \"$${dir}/so_locations\""; \ + rm -f "$${dir}/so_locations"; \ + done +libgnunetconsensus.la: $(libgnunetconsensus_la_OBJECTS) $(libgnunetconsensus_la_DEPENDENCIES) $(EXTRA_libgnunetconsensus_la_DEPENDENCIES) + $(AM_V_CCLD)$(libgnunetconsensus_la_LINK) -rpath $(libdir) $(libgnunetconsensus_la_OBJECTS) $(libgnunetconsensus_la_LIBADD) $(LIBS) +install-binPROGRAMS: $(bin_PROGRAMS) + @$(NORMAL_INSTALL) + @list='$(bin_PROGRAMS)'; test -n "$(bindir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(bindir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(bindir)" || exit 1; \ + fi; \ + for p in $$list; do echo "$$p $$p"; done | \ + sed 's/$(EXEEXT)$$//' | \ + while read p p1; do if test -f $$p || test -f $$p1; \ + then echo "$$p"; echo "$$p"; else :; fi; \ + done | \ + sed -e 'p;s,.*/,,;n;h' -e 's|.*|.|' \ + -e 'p;x;s,.*/,,;s/$(EXEEXT)$$//;$(transform);s/$$/$(EXEEXT)/' | \ + sed 'N;N;N;s,\n, ,g' | \ + $(AWK) 'BEGIN { files["."] = ""; dirs["."] = 1 } \ + { d=$$3; if (dirs[d] != 1) { print "d", d; dirs[d] = 1 } \ + if ($$2 == $$4) files[d] = files[d] " " $$1; \ + else { print "f", $$3 "/" $$4, $$1; } } \ + END { for (d in files) print "f", d, files[d] }' | \ + while read type dir files; do \ + if test "$$dir" = .; then dir=; else dir=/$$dir; fi; \ + test -z "$$files" || { \ + echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files '$(DESTDIR)$(bindir)$$dir'"; \ + $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files "$(DESTDIR)$(bindir)$$dir" || exit $$?; \ + } \ + ; done + +uninstall-binPROGRAMS: + @$(NORMAL_UNINSTALL) + @list='$(bin_PROGRAMS)'; test -n "$(bindir)" || list=; \ + files=`for p in $$list; do echo "$$p"; done | \ + sed -e 'h;s,^.*/,,;s/$(EXEEXT)$$//;$(transform)' \ + -e 's/$$/$(EXEEXT)/' `; \ + test -n "$$list" || exit 0; \ + echo " ( cd '$(DESTDIR)$(bindir)' && rm -f" $$files ")"; \ + cd "$(DESTDIR)$(bindir)" && rm -f $$files + +clean-binPROGRAMS: + @list='$(bin_PROGRAMS)'; test -n "$$list" || exit 0; \ + echo " rm -f" $$list; \ + rm -f $$list || exit $$?; \ + test -n "$(EXEEXT)" || exit 0; \ + list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ + echo " rm -f" $$list; \ + rm -f $$list + +clean-checkPROGRAMS: + @list='$(check_PROGRAMS)'; test -n "$$list" || exit 0; \ + echo " rm -f" $$list; \ + rm -f $$list || exit $$?; \ + test -n "$(EXEEXT)" || exit 0; \ + list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ + echo " rm -f" $$list; \ + rm -f $$list +install-libexecPROGRAMS: $(libexec_PROGRAMS) + @$(NORMAL_INSTALL) + @list='$(libexec_PROGRAMS)'; test -n "$(libexecdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(libexecdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libexecdir)" || exit 1; \ + fi; \ + for p in $$list; do echo "$$p $$p"; done | \ + sed 's/$(EXEEXT)$$//' | \ + while read p p1; do if test -f $$p || test -f $$p1; \ + then echo "$$p"; echo "$$p"; else :; fi; \ + done | \ + sed -e 'p;s,.*/,,;n;h' -e 's|.*|.|' \ + -e 'p;x;s,.*/,,;s/$(EXEEXT)$$//;$(transform);s/$$/$(EXEEXT)/' | \ + sed 'N;N;N;s,\n, ,g' | \ + $(AWK) 'BEGIN { files["."] = ""; dirs["."] = 1 } \ + { d=$$3; if (dirs[d] != 1) { print "d", d; dirs[d] = 1 } \ + if ($$2 == $$4) files[d] = files[d] " " $$1; \ + else { print "f", $$3 "/" $$4, $$1; } } \ + END { for (d in files) print "f", d, files[d] }' | \ + while read type dir files; do \ + if test "$$dir" = .; then dir=; else dir=/$$dir; fi; \ + test -z "$$files" || { \ + echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files '$(DESTDIR)$(libexecdir)$$dir'"; \ + $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files "$(DESTDIR)$(libexecdir)$$dir" || exit $$?; \ + } \ + ; done + +uninstall-libexecPROGRAMS: + @$(NORMAL_UNINSTALL) + @list='$(libexec_PROGRAMS)'; test -n "$(libexecdir)" || list=; \ + files=`for p in $$list; do echo "$$p"; done | \ + sed -e 'h;s,^.*/,,;s/$(EXEEXT)$$//;$(transform)' \ + -e 's/$$/$(EXEEXT)/' `; \ + test -n "$$list" || exit 0; \ + echo " ( cd '$(DESTDIR)$(libexecdir)' && rm -f" $$files ")"; \ + cd "$(DESTDIR)$(libexecdir)" && rm -f $$files + +clean-libexecPROGRAMS: + @list='$(libexec_PROGRAMS)'; test -n "$$list" || exit 0; \ + echo " rm -f" $$list; \ + rm -f $$list || exit $$?; \ + test -n "$(EXEEXT)" || exit 0; \ + list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ + echo " rm -f" $$list; \ + rm -f $$list +gnunet-consensus$(EXEEXT): $(gnunet_consensus_OBJECTS) $(gnunet_consensus_DEPENDENCIES) $(EXTRA_gnunet_consensus_DEPENDENCIES) + @rm -f gnunet-consensus$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(gnunet_consensus_OBJECTS) $(gnunet_consensus_LDADD) $(LIBS) +gnunet-consensus-ibf$(EXEEXT): $(gnunet_consensus_ibf_OBJECTS) $(gnunet_consensus_ibf_DEPENDENCIES) $(EXTRA_gnunet_consensus_ibf_DEPENDENCIES) + @rm -f gnunet-consensus-ibf$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(gnunet_consensus_ibf_OBJECTS) $(gnunet_consensus_ibf_LDADD) $(LIBS) +gnunet-consensus-start-peers$(EXEEXT): $(gnunet_consensus_start_peers_OBJECTS) $(gnunet_consensus_start_peers_DEPENDENCIES) $(EXTRA_gnunet_consensus_start_peers_DEPENDENCIES) + @rm -f gnunet-consensus-start-peers$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(gnunet_consensus_start_peers_OBJECTS) $(gnunet_consensus_start_peers_LDADD) $(LIBS) +gnunet-service-consensus$(EXEEXT): $(gnunet_service_consensus_OBJECTS) $(gnunet_service_consensus_DEPENDENCIES) $(EXTRA_gnunet_service_consensus_DEPENDENCIES) + @rm -f gnunet-service-consensus$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(gnunet_service_consensus_OBJECTS) $(gnunet_service_consensus_LDADD) $(LIBS) +test_consensus_api$(EXEEXT): $(test_consensus_api_OBJECTS) $(test_consensus_api_DEPENDENCIES) $(EXTRA_test_consensus_api_DEPENDENCIES) + @rm -f test_consensus_api$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_consensus_api_OBJECTS) $(test_consensus_api_LDADD) $(LIBS) + +mostlyclean-compile: + -rm -f *.$(OBJEXT) + +distclean-compile: + -rm -f *.tab.c + +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/consensus_api.Plo@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-consensus-ibf.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-consensus-start-peers.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-consensus.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-service-consensus.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/ibf.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_consensus_api.Po@am__quote@ + +.c.o: +@am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c $< + +.c.obj: +@am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'` +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c `$(CYGPATH_W) '$<'` + +.c.lo: +@am__fastdepCC_TRUE@ $(AM_V_CC)$(LTCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LTCOMPILE) -c -o $@ $< + +mostlyclean-libtool: + -rm -f *.lo + +clean-libtool: + -rm -rf .libs _libs +install-pkgcfgDATA: $(pkgcfg_DATA) + @$(NORMAL_INSTALL) + @list='$(pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(pkgcfgdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" || exit 1; \ + fi; \ + for p in $$list; do \ + if test -f "$$p"; then d=; else d="$(srcdir)/"; fi; \ + echo "$$d$$p"; \ + done | $(am__base_list) | \ + while read files; do \ + echo " $(INSTALL_DATA) $$files '$(DESTDIR)$(pkgcfgdir)'"; \ + $(INSTALL_DATA) $$files "$(DESTDIR)$(pkgcfgdir)" || exit $$?; \ + done + +uninstall-pkgcfgDATA: + @$(NORMAL_UNINSTALL) + @list='$(pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ + files=`for p in $$list; do echo $$p; done | sed -e 's|^.*/||'`; \ + dir='$(DESTDIR)$(pkgcfgdir)'; $(am__uninstall_files_from_dir) + +ID: $(HEADERS) $(SOURCES) $(LISP) $(TAGS_FILES) + list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ + unique=`for i in $$list; do \ + if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \ + done | \ + $(AWK) '{ files[$$0] = 1; nonempty = 1; } \ + END { if (nonempty) { for (i in files) print i; }; }'`; \ + mkid -fID $$unique +tags: TAGS + +TAGS: $(HEADERS) $(SOURCES) $(TAGS_DEPENDENCIES) \ + $(TAGS_FILES) $(LISP) + set x; \ + here=`pwd`; \ + list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ + unique=`for i in $$list; do \ + if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \ + done | \ + $(AWK) '{ files[$$0] = 1; nonempty = 1; } \ + END { if (nonempty) { for (i in files) print i; }; }'`; \ + shift; \ + if test -z "$(ETAGS_ARGS)$$*$$unique"; then :; else \ + test -n "$$unique" || unique=$$empty_fix; \ + if test $$# -gt 0; then \ + $(ETAGS) $(ETAGSFLAGS) $(AM_ETAGSFLAGS) $(ETAGS_ARGS) \ + "$$@" $$unique; \ + else \ + $(ETAGS) $(ETAGSFLAGS) $(AM_ETAGSFLAGS) $(ETAGS_ARGS) \ + $$unique; \ + fi; \ + fi +ctags: CTAGS +CTAGS: $(HEADERS) $(SOURCES) $(TAGS_DEPENDENCIES) \ + $(TAGS_FILES) $(LISP) + list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ + unique=`for i in $$list; do \ + if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \ + done | \ + $(AWK) '{ files[$$0] = 1; nonempty = 1; } \ + END { if (nonempty) { for (i in files) print i; }; }'`; \ + test -z "$(CTAGS_ARGS)$$unique" \ + || $(CTAGS) $(CTAGSFLAGS) $(AM_CTAGSFLAGS) $(CTAGS_ARGS) \ + $$unique + +GTAGS: + here=`$(am__cd) $(top_builddir) && pwd` \ + && $(am__cd) $(top_srcdir) \ + && gtags -i $(GTAGS_ARGS) "$$here" + +distclean-tags: + -rm -f TAGS ID GTAGS GRTAGS GSYMS GPATH tags + +check-TESTS: $(TESTS) + @failed=0; all=0; xfail=0; xpass=0; skip=0; \ + srcdir=$(srcdir); export srcdir; \ + list=' $(TESTS) '; \ + $(am__tty_colors); \ + if test -n "$$list"; then \ + for tst in $$list; do \ + if test -f ./$$tst; then dir=./; \ + elif test -f $$tst; then dir=; \ + else dir="$(srcdir)/"; fi; \ + if $(TESTS_ENVIRONMENT) $${dir}$$tst; then \ + all=`expr $$all + 1`; \ + case " $(XFAIL_TESTS) " in \ + *[\ \ ]$$tst[\ \ ]*) \ + xpass=`expr $$xpass + 1`; \ + failed=`expr $$failed + 1`; \ + col=$$red; res=XPASS; \ + ;; \ + *) \ + col=$$grn; res=PASS; \ + ;; \ + esac; \ + elif test $$? -ne 77; then \ + all=`expr $$all + 1`; \ + case " $(XFAIL_TESTS) " in \ + *[\ \ ]$$tst[\ \ ]*) \ + xfail=`expr $$xfail + 1`; \ + col=$$lgn; res=XFAIL; \ + ;; \ + *) \ + failed=`expr $$failed + 1`; \ + col=$$red; res=FAIL; \ + ;; \ + esac; \ + else \ + skip=`expr $$skip + 1`; \ + col=$$blu; res=SKIP; \ + fi; \ + echo "$${col}$$res$${std}: $$tst"; \ + done; \ + if test "$$all" -eq 1; then \ + tests="test"; \ + All=""; \ + else \ + tests="tests"; \ + All="All "; \ + fi; \ + if test "$$failed" -eq 0; then \ + if test "$$xfail" -eq 0; then \ + banner="$$All$$all $$tests passed"; \ + else \ + if test "$$xfail" -eq 1; then failures=failure; else failures=failures; fi; \ + banner="$$All$$all $$tests behaved as expected ($$xfail expected $$failures)"; \ + fi; \ + else \ + if test "$$xpass" -eq 0; then \ + banner="$$failed of $$all $$tests failed"; \ + else \ + if test "$$xpass" -eq 1; then passes=pass; else passes=passes; fi; \ + banner="$$failed of $$all $$tests did not behave as expected ($$xpass unexpected $$passes)"; \ + fi; \ + fi; \ + dashes="$$banner"; \ + skipped=""; \ + if test "$$skip" -ne 0; then \ + if test "$$skip" -eq 1; then \ + skipped="($$skip test was not run)"; \ + else \ + skipped="($$skip tests were not run)"; \ + fi; \ + test `echo "$$skipped" | wc -c` -le `echo "$$banner" | wc -c` || \ + dashes="$$skipped"; \ + fi; \ + report=""; \ + if test "$$failed" -ne 0 && test -n "$(PACKAGE_BUGREPORT)"; then \ + report="Please report to $(PACKAGE_BUGREPORT)"; \ + test `echo "$$report" | wc -c` -le `echo "$$banner" | wc -c` || \ + dashes="$$report"; \ + fi; \ + dashes=`echo "$$dashes" | sed s/./=/g`; \ + if test "$$failed" -eq 0; then \ + col="$$grn"; \ + else \ + col="$$red"; \ + fi; \ + echo "$${col}$$dashes$${std}"; \ + echo "$${col}$$banner$${std}"; \ + test -z "$$skipped" || echo "$${col}$$skipped$${std}"; \ + test -z "$$report" || echo "$${col}$$report$${std}"; \ + echo "$${col}$$dashes$${std}"; \ + test "$$failed" -eq 0; \ + else :; fi + +distdir: $(DISTFILES) + @srcdirstrip=`echo "$(srcdir)" | sed 's/[].[^$$\\*]/\\\\&/g'`; \ + topsrcdirstrip=`echo "$(top_srcdir)" | sed 's/[].[^$$\\*]/\\\\&/g'`; \ + list='$(DISTFILES)'; \ + dist_files=`for file in $$list; do echo $$file; done | \ + sed -e "s|^$$srcdirstrip/||;t" \ + -e "s|^$$topsrcdirstrip/|$(top_builddir)/|;t"`; \ + case $$dist_files in \ + */*) $(MKDIR_P) `echo "$$dist_files" | \ + sed '/\//!d;s|^|$(distdir)/|;s,/[^/]*$$,,' | \ + sort -u` ;; \ + esac; \ + for file in $$dist_files; do \ + if test -f $$file || test -d $$file; then d=.; else d=$(srcdir); fi; \ + if test -d $$d/$$file; then \ + dir=`echo "/$$file" | sed -e 's,/[^/]*$$,,'`; \ + if test -d "$(distdir)/$$file"; then \ + find "$(distdir)/$$file" -type d ! -perm -700 -exec chmod u+rwx {} \;; \ + fi; \ + if test -d $(srcdir)/$$file && test $$d != $(srcdir); then \ + cp -fpR $(srcdir)/$$file "$(distdir)$$dir" || exit 1; \ + find "$(distdir)/$$file" -type d ! -perm -700 -exec chmod u+rwx {} \;; \ + fi; \ + cp -fpR $$d/$$file "$(distdir)$$dir" || exit 1; \ + else \ + test -f "$(distdir)/$$file" \ + || cp -p $$d/$$file "$(distdir)/$$file" \ + || exit 1; \ + fi; \ + done +check-am: all-am + $(MAKE) $(AM_MAKEFLAGS) $(check_PROGRAMS) + $(MAKE) $(AM_MAKEFLAGS) check-TESTS +check: check-am +all-am: Makefile $(LTLIBRARIES) $(PROGRAMS) $(DATA) +install-binPROGRAMS: install-libLTLIBRARIES + +installdirs: + for dir in "$(DESTDIR)$(libdir)" "$(DESTDIR)$(bindir)" "$(DESTDIR)$(libexecdir)" "$(DESTDIR)$(pkgcfgdir)"; do \ + test -z "$$dir" || $(MKDIR_P) "$$dir"; \ + done +install: install-am +install-exec: install-exec-am +install-data: install-data-am +uninstall: uninstall-am + +install-am: all-am + @$(MAKE) $(AM_MAKEFLAGS) install-exec-am install-data-am + +installcheck: installcheck-am +install-strip: + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi +mostlyclean-generic: + +clean-generic: + +distclean-generic: + -test -z "$(CONFIG_CLEAN_FILES)" || rm -f $(CONFIG_CLEAN_FILES) + -test . = "$(srcdir)" || test -z "$(CONFIG_CLEAN_VPATH_FILES)" || rm -f $(CONFIG_CLEAN_VPATH_FILES) + +maintainer-clean-generic: + @echo "This command is intended for maintainers to use" + @echo "it deletes files that may require special tools to rebuild." +clean: clean-am + +clean-am: clean-binPROGRAMS clean-checkPROGRAMS clean-generic \ + clean-libLTLIBRARIES clean-libexecPROGRAMS clean-libtool \ + mostlyclean-am + +distclean: distclean-am + -rm -rf ./$(DEPDIR) + -rm -f Makefile +distclean-am: clean-am distclean-compile distclean-generic \ + distclean-tags + +dvi: dvi-am + +dvi-am: + +html: html-am + +html-am: + +info: info-am + +info-am: + +install-data-am: install-pkgcfgDATA + +install-dvi: install-dvi-am + +install-dvi-am: + +install-exec-am: install-binPROGRAMS install-libLTLIBRARIES \ + install-libexecPROGRAMS + +install-html: install-html-am + +install-html-am: + +install-info: install-info-am + +install-info-am: + +install-man: + +install-pdf: install-pdf-am + +install-pdf-am: + +install-ps: install-ps-am + +install-ps-am: + +installcheck-am: + +maintainer-clean: maintainer-clean-am + -rm -rf ./$(DEPDIR) + -rm -f Makefile +maintainer-clean-am: distclean-am maintainer-clean-generic + +mostlyclean: mostlyclean-am + +mostlyclean-am: mostlyclean-compile mostlyclean-generic \ + mostlyclean-libtool + +pdf: pdf-am + +pdf-am: + +ps: ps-am + +ps-am: + +uninstall-am: uninstall-binPROGRAMS uninstall-libLTLIBRARIES \ + uninstall-libexecPROGRAMS uninstall-pkgcfgDATA + +.MAKE: check-am install-am install-strip + +.PHONY: CTAGS GTAGS all all-am check check-TESTS check-am clean \ + clean-binPROGRAMS clean-checkPROGRAMS clean-generic \ + clean-libLTLIBRARIES clean-libexecPROGRAMS clean-libtool ctags \ + distclean distclean-compile distclean-generic \ + distclean-libtool distclean-tags distdir dvi dvi-am html \ + html-am info info-am install install-am install-binPROGRAMS \ + install-data install-data-am install-dvi install-dvi-am \ + install-exec install-exec-am install-html install-html-am \ + install-info install-info-am install-libLTLIBRARIES \ + install-libexecPROGRAMS install-man install-pdf install-pdf-am \ + install-pkgcfgDATA install-ps install-ps-am install-strip \ + installcheck installcheck-am installdirs maintainer-clean \ + maintainer-clean-generic mostlyclean mostlyclean-compile \ + mostlyclean-generic mostlyclean-libtool pdf pdf-am ps ps-am \ + tags uninstall uninstall-am uninstall-binPROGRAMS \ + uninstall-libLTLIBRARIES uninstall-libexecPROGRAMS \ + uninstall-pkgcfgDATA + + +# Tell versions [3.59,3.63) of GNU make to not export all variables. +# Otherwise a system limit (for SysV at least) may be exceeded. +.NOEXPORT: diff --git a/src/consensus/consensus.conf.in b/src/consensus/consensus.conf.in new file mode 100644 index 0000000..18e976d --- /dev/null +++ b/src/consensus/consensus.conf.in @@ -0,0 +1,11 @@ +[consensus] +AUTOSTART = YES +@UNIXONLY@ PORT = 2103 +HOSTNAME = localhost +HOME = $SERVICEHOME +BINARY = gnunet-service-consensus +ACCEPT_FROM = 127.0.0.1; +ACCEPT_FROM6 = ::1; +UNIXPATH = /tmp/gnunet-service-consensus.sock +UNIX_MATCH_UID = YES +UNIX_MATCH_GID = YES diff --git a/src/consensus/consensus_api.c b/src/consensus/consensus_api.c new file mode 100644 index 0000000..7ebb0a9 --- /dev/null +++ b/src/consensus/consensus_api.c @@ -0,0 +1,535 @@ +/* + This file is part of GNUnet. + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @file consensus/consensus_api.c + * @brief + * @author Florian Dold + */ +#include "platform.h" +#include "gnunet_util_lib.h" +#include "gnunet_protocols.h" +#include "gnunet_client_lib.h" +#include "gnunet_consensus_service.h" +#include "consensus.h" + + +#define LOG(kind,...) GNUNET_log_from (kind, "consensus-api",__VA_ARGS__) + +/** + * Actions that can be queued. + */ +struct QueuedMessage +{ + /** + * Queued messages are stored in a doubly linked list. + */ + struct QueuedMessage *next; + + /** + * Queued messages are stored in a doubly linked list. + */ + struct QueuedMessage *prev; + + /** + * The actual queued message. + */ + struct GNUNET_MessageHeader *msg; + + /** + * Will be called after transmit, if not NULL + */ + GNUNET_CONSENSUS_InsertDoneCallback idc; + + /** + * Closure for idc + */ + void *idc_cls; +}; + + +/** + * Handle for the service. + */ +struct GNUNET_CONSENSUS_Handle +{ + /** + * Configuration to use. + */ + const struct GNUNET_CONFIGURATION_Handle *cfg; + + /** + * Client connected to the consensus service, may be NULL if not connected. + */ + struct GNUNET_CLIENT_Connection *client; + + /** + * Callback for new elements. Not called for elements added locally. + */ + GNUNET_CONSENSUS_ElementCallback new_element_cb; + + /** + * Closure for new_element_cb + */ + void *new_element_cls; + + /** + * The (local) session identifier for the consensus session. + */ + struct GNUNET_HashCode session_id; + + /** + * Number of peers in the consensus. Optionally includes the local peer. + */ + int num_peers; + + /** + * Peer identities of peers participating in the consensus, includes the local peer. + */ + struct GNUNET_PeerIdentity **peers; + + /** + * Currently active transmit request. + */ + struct GNUNET_CLIENT_TransmitHandle *th; + + /** + * GNUNES_YES iff the join message has been sent to the service. + */ + int joined; + + /** + * Closure for the insert done callback. + */ + void *idc_cls; + + /** + * Called when the conclude operation finishes or fails. + */ + GNUNET_CONSENSUS_ConcludeCallback conclude_cb; + + /** + * Closure for the conclude callback. + */ + void *conclude_cls; + + /** + * Deadline for the conclude operation. + */ + struct GNUNET_TIME_Absolute conclude_deadline; + + unsigned int conclude_min_size; + + struct QueuedMessage *messages_head; + struct QueuedMessage *messages_tail; +}; + + + +/** + * Schedule transmitting the next message. + * + * @param consensus consensus handle + */ +static void +send_next (struct GNUNET_CONSENSUS_Handle *consensus); + + +/** + * Function called to notify a client about the connection + * begin ready to queue more data. "buf" will be + * NULL and "size" zero if the connection was closed for + * writing in the meantime. + * + * @param cls closure + * @param size number of bytes available in buf + * @param buf where the callee should write the message + * @return number of bytes written to buf + */ +static size_t +transmit_queued (void *cls, size_t size, + void *buf) +{ + struct GNUNET_CONSENSUS_Handle *consensus; + struct QueuedMessage *qmsg; + size_t msg_size; + + consensus = (struct GNUNET_CONSENSUS_Handle *) cls; + consensus->th = NULL; + + qmsg = consensus->messages_head; + GNUNET_CONTAINER_DLL_remove (consensus->messages_head, consensus->messages_tail, qmsg); + + if (NULL == buf) + { + if (NULL != qmsg->idc) + { + qmsg->idc (qmsg->idc_cls, GNUNET_YES); + } + return 0; + } + + msg_size = ntohs (qmsg->msg->size); + + GNUNET_assert (size >= msg_size); + + memcpy (buf, qmsg->msg, msg_size); + if (NULL != qmsg->idc) + { + qmsg->idc (qmsg->idc_cls, GNUNET_YES); + } + + /* FIXME: free the messages */ + + send_next (consensus); + + return msg_size; +} + + +/** + * Schedule transmitting the next message. + * + * @param consensus consensus handle + */ +static void +send_next (struct GNUNET_CONSENSUS_Handle *consensus) +{ + if (NULL != consensus->th) + return; + + if (NULL != consensus->messages_head) + { + consensus->th = + GNUNET_CLIENT_notify_transmit_ready (consensus->client, ntohs (consensus->messages_head->msg->size), + GNUNET_TIME_UNIT_FOREVER_REL, + GNUNET_NO, &transmit_queued, consensus); + } +} + +static void +queue_message (struct GNUNET_CONSENSUS_Handle *consensus, struct GNUNET_MessageHeader *msg) +{ + struct QueuedMessage *qm; + qm = GNUNET_malloc (sizeof *qm); + qm->msg = msg; + GNUNET_CONTAINER_DLL_insert_tail (consensus->messages_head, consensus->messages_tail, qm); +} + + +/** + * Called when the server has sent is a new element + * + * @param consensus consensus handle + * @param msg element message + */ +static void +handle_new_element (struct GNUNET_CONSENSUS_Handle *consensus, + struct GNUNET_CONSENSUS_ElementMessage *msg) +{ + struct GNUNET_CONSENSUS_Element element; + struct GNUNET_CONSENSUS_AckMessage *ack_msg; + int ret; + + LOG (GNUNET_ERROR_TYPE_DEBUG, "received new element\n"); + + element.type = msg->element_type; + element.size = ntohs (msg->header.size) - sizeof (struct GNUNET_CONSENSUS_ElementMessage); + element.data = &msg[1]; + + ret = consensus->new_element_cb (consensus->new_element_cls, &element); + + ack_msg = GNUNET_malloc (sizeof *ack_msg); + ack_msg->header.size = htons (sizeof *ack_msg); + ack_msg->header.type = htons (GNUNET_MESSAGE_TYPE_CONSENSUS_CLIENT_ACK); + ack_msg->keep = ret; + + queue_message (consensus, (struct GNUNET_MessageHeader *) ack_msg); + + send_next (consensus); +} + + +/** + * Called when the server has announced + * that the conclusion is over. + * + * @param consensus consensus handle + * @param msg conclude done message + */ +static void +handle_conclude_done (struct GNUNET_CONSENSUS_Handle *consensus, + struct GNUNET_CONSENSUS_ConcludeDoneMessage *msg) +{ + GNUNET_assert (NULL != consensus->conclude_cb); + consensus->conclude_cb (consensus->conclude_cls, NULL); + consensus->conclude_cb = NULL; +} + + + +/** + * Type of a function to call when we receive a message + * from the service. + * + * @param cls closure + * @param msg message received, NULL on timeout or fatal error + */ +static void +message_handler (void *cls, const struct GNUNET_MessageHeader *msg) +{ + struct GNUNET_CONSENSUS_Handle *consensus = cls; + + LOG (GNUNET_ERROR_TYPE_DEBUG, "received message from consensus service\n"); + + if (msg == NULL) + { + /* Error, timeout, death */ + LOG (GNUNET_ERROR_TYPE_ERROR, "error receiving\n"); + GNUNET_CLIENT_disconnect (consensus->client); + consensus->client = NULL; + consensus->new_element_cb (NULL, NULL); + return; + } + + switch (ntohs (msg->type)) + { + case GNUNET_MESSAGE_TYPE_CONSENSUS_CLIENT_RECEIVED_ELEMENT: + handle_new_element (consensus, (struct GNUNET_CONSENSUS_ElementMessage *) msg); + break; + case GNUNET_MESSAGE_TYPE_CONSENSUS_CLIENT_CONCLUDE_DONE: + handle_conclude_done (consensus, (struct GNUNET_CONSENSUS_ConcludeDoneMessage *) msg); + break; + default: + GNUNET_break (0); + } + GNUNET_CLIENT_receive (consensus->client, &message_handler, consensus, + GNUNET_TIME_UNIT_FOREVER_REL); +} + +/** + * Function called to notify a client about the connection + * begin ready to queue more data. "buf" will be + * NULL and "size" zero if the connection was closed for + * writing in the meantime. + * + * @param cls closure + * @param size number of bytes available in buf + * @param buf where the callee should write the message + * @return number of bytes written to buf + */ +static size_t +transmit_join (void *cls, size_t size, void *buf) +{ + struct GNUNET_CONSENSUS_JoinMessage *msg; + struct GNUNET_CONSENSUS_Handle *consensus; + int msize; + + GNUNET_assert (NULL != buf); + + LOG (GNUNET_ERROR_TYPE_DEBUG, "transmitting join message\n"); + + consensus = cls; + consensus->th = NULL; + consensus->joined = 1; + + msg = buf; + + msize = sizeof (struct GNUNET_CONSENSUS_JoinMessage) + + consensus->num_peers * sizeof (struct GNUNET_PeerIdentity); + + msg->header.type = htons (GNUNET_MESSAGE_TYPE_CONSENSUS_CLIENT_JOIN); + msg->header.size = htons (msize); + msg->session_id = consensus->session_id; + msg->num_peers = htons (consensus->num_peers); + if (0 != msg->num_peers) + memcpy(&msg[1], + consensus->peers, + consensus->num_peers * sizeof (struct GNUNET_PeerIdentity)); + + send_next (consensus); + + GNUNET_CLIENT_receive (consensus->client, &message_handler, consensus, + GNUNET_TIME_UNIT_FOREVER_REL); + + return msize; +} + +/** + * Create a consensus session. + * + * @param cfg configuration to use for connecting to the consensus service + * @param num_peers number of peers in the peers array + * @param peers array of peers participating in this consensus session + * Inclusion of the local peer is optional. + * @param session_id session identifier + * Allows a group of peers to have more than consensus session. + * @param new_element_cb callback, called when a new element is added to the set by + * another peer + * @param new_element_cls closure for new_element + * @return handle to use, NULL on error + */ +struct GNUNET_CONSENSUS_Handle * +GNUNET_CONSENSUS_create (const struct GNUNET_CONFIGURATION_Handle *cfg, + unsigned int num_peers, + const struct GNUNET_PeerIdentity *peers, + const struct GNUNET_HashCode *session_id, + GNUNET_CONSENSUS_ElementCallback new_element_cb, + void *new_element_cls) +{ + struct GNUNET_CONSENSUS_Handle *consensus; + size_t join_message_size; + + consensus = GNUNET_malloc (sizeof (struct GNUNET_CONSENSUS_Handle)); + consensus->cfg = cfg; + consensus->new_element_cb = new_element_cb; + consensus->new_element_cls = new_element_cls; + consensus->num_peers = num_peers; + consensus->session_id = *session_id; + + if (0 == num_peers) + consensus->peers = NULL; + else if (num_peers > 0) + consensus->peers = + GNUNET_memdup (peers, num_peers * sizeof (struct GNUNET_PeerIdentity)); + + consensus->client = GNUNET_CLIENT_connect ("consensus", cfg); + + GNUNET_assert (consensus->client != NULL); + + join_message_size = (sizeof (struct GNUNET_CONSENSUS_JoinMessage)) + + (num_peers * sizeof (struct GNUNET_PeerIdentity)); + + consensus->th = + GNUNET_CLIENT_notify_transmit_ready (consensus->client, + join_message_size, + GNUNET_TIME_UNIT_FOREVER_REL, + GNUNET_NO, &transmit_join, consensus); + + + GNUNET_assert (consensus->th != NULL); + return consensus; +} + + + +/** + * Insert an element in the set being reconsiled. Must not be called after + * "GNUNET_CONSENSUS_conclude". + * + * @param consensus handle for the consensus session + * @param element the element to be inserted + * @param idc function called when we are done with this element and it + * is thus allowed to call GNUNET_CONSENSUS_insert again + * @param idc_cls closure for 'idc' + */ +void +GNUNET_CONSENSUS_insert (struct GNUNET_CONSENSUS_Handle *consensus, + const struct GNUNET_CONSENSUS_Element *element, + GNUNET_CONSENSUS_InsertDoneCallback idc, + void *idc_cls) +{ + struct QueuedMessage *qmsg; + struct GNUNET_CONSENSUS_ElementMessage *element_msg; + size_t element_msg_size; + + LOG (GNUNET_ERROR_TYPE_DEBUG, "inserting, size=%llu\n", element->size); + + element_msg_size = (sizeof (struct GNUNET_CONSENSUS_ElementMessage) + + element->size); + + element_msg = GNUNET_malloc (element_msg_size); + element_msg->header.type = htons (GNUNET_MESSAGE_TYPE_CONSENSUS_CLIENT_INSERT); + element_msg->header.size = htons (element_msg_size); + memcpy (&element_msg[1], element->data, element->size); + + qmsg = GNUNET_malloc (sizeof (struct QueuedMessage)); + qmsg->msg = (struct GNUNET_MessageHeader *) element_msg; + qmsg->idc = idc; + qmsg->idc_cls = idc_cls; + + GNUNET_CONTAINER_DLL_insert_tail (consensus->messages_head, consensus->messages_tail, qmsg); + + send_next (consensus); +} + + +/** + * We are done with inserting new elements into the consensus; + * try to conclude the consensus within a given time window. + * After conclude has been called, no further elements may be + * inserted by the client. + * + * @param consensus consensus session + * @param timeout timeout after which the conculde callback + * must be called + * @param conclude called when the conclusion was successful + * @param conclude_cls closure for the conclude callback + */ +void +GNUNET_CONSENSUS_conclude (struct GNUNET_CONSENSUS_Handle *consensus, + struct GNUNET_TIME_Relative timeout, + unsigned int min_group_size_in_consensus, + GNUNET_CONSENSUS_ConcludeCallback conclude, + void *conclude_cls) +{ + struct QueuedMessage *qmsg; + struct GNUNET_CONSENSUS_ConcludeMessage *conclude_msg; + + GNUNET_assert (NULL != conclude); + GNUNET_assert (NULL == consensus->conclude_cb); + + consensus->conclude_cls = conclude_cls; + consensus->conclude_cb = conclude; + + conclude_msg = GNUNET_malloc (sizeof (struct GNUNET_CONSENSUS_ConcludeMessage)); + conclude_msg->header.type = htons (GNUNET_MESSAGE_TYPE_CONSENSUS_CLIENT_CONCLUDE); + conclude_msg->header.size = htons (sizeof (struct GNUNET_CONSENSUS_ConcludeMessage)); + conclude_msg->timeout = GNUNET_TIME_relative_hton (timeout); + conclude_msg->min_group_size = min_group_size_in_consensus; + + qmsg = GNUNET_malloc (sizeof (struct QueuedMessage)); + qmsg->msg = (struct GNUNET_MessageHeader *) conclude_msg; + + GNUNET_CONTAINER_DLL_insert_tail (consensus->messages_head, consensus->messages_tail, qmsg); + + send_next (consensus); +} + + +/** + * Destroy a consensus handle (free all state associated with + * it, no longer call any of the callbacks). + * + * @param consensus handle to destroy + */ +void +GNUNET_CONSENSUS_destroy (struct GNUNET_CONSENSUS_Handle *consensus) +{ + if (consensus->client != NULL) + { + GNUNET_CLIENT_disconnect (consensus->client); + consensus->client = NULL; + } + if (NULL != consensus->peers) + GNUNET_free (consensus->peers); + GNUNET_free (consensus); +} + diff --git a/src/consensus/gnunet-consensus-ibf.c b/src/consensus/gnunet-consensus-ibf.c new file mode 100644 index 0000000..c9bcc1a --- /dev/null +++ b/src/consensus/gnunet-consensus-ibf.c @@ -0,0 +1,197 @@ +/* + This file is part of GNUnet. + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @file consensus/gnunet-consensus-ibf + * @brief tool for reconciling data with invertible bloom filters + * @author Florian Dold + */ + + +#include "platform.h" +#include "gnunet_common.h" +#include "gnunet_container_lib.h" +#include "gnunet_util_lib.h" + +#include "ibf.h" + +static unsigned int asize = 10; +static unsigned int bsize = 10; +static unsigned int csize = 10; +static unsigned int hash_num = 3; +static unsigned int ibf_size = 80; + + +static struct GNUNET_CONTAINER_MultiHashMap *set_a; +static struct GNUNET_CONTAINER_MultiHashMap *set_b; +/* common elements in a and b */ +static struct GNUNET_CONTAINER_MultiHashMap *set_c; + +static struct InvertibleBloomFilter *ibf_a; +static struct InvertibleBloomFilter *ibf_b; + + + +static int +insert_iterator (void *cls, + const struct GNUNET_HashCode *key, + void *value) +{ + struct InvertibleBloomFilter *ibf = (struct InvertibleBloomFilter *) cls; + ibf_insert (ibf, key); + return GNUNET_YES; +} + + +static void +run (void *cls, char *const *args, const char *cfgfile, + const struct GNUNET_CONFIGURATION_Handle *cfg) +{ + struct GNUNET_HashCode id; + int i; + int side; + int res; + struct GNUNET_TIME_Absolute start_time; + struct GNUNET_TIME_Relative delta_time; + + set_a = GNUNET_CONTAINER_multihashmap_create (((asize == 0) ? 1 : (asize + csize)), + GNUNET_NO); + set_b = GNUNET_CONTAINER_multihashmap_create (((bsize == 0) ? 1 : (bsize + csize)), + GNUNET_NO); + set_c = GNUNET_CONTAINER_multihashmap_create (((csize == 0) ? 1 : csize), + GNUNET_NO); + + printf ("hash-num=%u, size=%u, #(A-B)=%u, #(B-A)=%u, #(A&B)=%u\n", + hash_num, ibf_size, asize, bsize, csize); + + i = 0; + while (i < asize) + { + GNUNET_CRYPTO_hash_create_random (GNUNET_CRYPTO_QUALITY_WEAK, &id); + if (GNUNET_YES == GNUNET_CONTAINER_multihashmap_contains (set_a, &id)) + continue; + GNUNET_CONTAINER_multihashmap_put ( + set_a, &id, NULL, GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY); + i++; + } + i = 0; + while (i < bsize) + { + GNUNET_CRYPTO_hash_create_random (GNUNET_CRYPTO_QUALITY_WEAK, &id); + if (GNUNET_YES == GNUNET_CONTAINER_multihashmap_contains (set_a, &id)) + continue; + if (GNUNET_YES == GNUNET_CONTAINER_multihashmap_contains (set_b, &id)) + continue; + GNUNET_CONTAINER_multihashmap_put ( + set_b, &id, NULL, GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY); + i++; + } + i = 0; + while (i < csize) + { + GNUNET_CRYPTO_hash_create_random (GNUNET_CRYPTO_QUALITY_WEAK, &id); + if (GNUNET_YES == GNUNET_CONTAINER_multihashmap_contains (set_a, &id)) + continue; + if (GNUNET_YES == GNUNET_CONTAINER_multihashmap_contains (set_b, &id)) + continue; + GNUNET_CONTAINER_multihashmap_put ( + set_c, &id, NULL, GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY); + i++; + } + + ibf_a = ibf_create (ibf_size, hash_num, 0); + ibf_b = ibf_create (ibf_size, hash_num, 0); + + start_time = GNUNET_TIME_absolute_get (); + + GNUNET_CONTAINER_multihashmap_iterate (set_a, &insert_iterator, ibf_a); + GNUNET_CONTAINER_multihashmap_iterate (set_b, &insert_iterator, ibf_b); + GNUNET_CONTAINER_multihashmap_iterate (set_c, &insert_iterator, ibf_a); + GNUNET_CONTAINER_multihashmap_iterate (set_c, &insert_iterator, ibf_b); + + delta_time = GNUNET_TIME_absolute_get_duration (start_time); + + printf ("encoded in: %s\n", GNUNET_STRINGS_relative_time_to_string (delta_time, GNUNET_NO)); + + ibf_subtract (ibf_a, ibf_b); + + + start_time = GNUNET_TIME_absolute_get (); + + for (;;) + { + res = ibf_decode (ibf_a, &side, &id); + if (GNUNET_SYSERR == res) + { + printf ("decode failed\n"); + return; + } + if (GNUNET_NO == res) + { + if ((0 == GNUNET_CONTAINER_multihashmap_size (set_b)) && + (0 == GNUNET_CONTAINER_multihashmap_size (set_a))) + { + delta_time = GNUNET_TIME_absolute_get_duration (start_time); + printf ("decoded successfully in: %s\n", GNUNET_STRINGS_relative_time_to_string (delta_time, GNUNET_NO)); + } + else + printf ("decode missed elements\n"); + return; + } + + if (side == 1) + res = GNUNET_CONTAINER_multihashmap_remove (set_a, &id, NULL); + if (side == -1) + res = GNUNET_CONTAINER_multihashmap_remove (set_b, &id, NULL); + if (GNUNET_YES != res) + { + printf ("decoded wrong element\n"); + return; + } + } +} + +int +main (int argc, char **argv) +{ + static const struct GNUNET_GETOPT_CommandLineOption options[] = { + {'A', "asize", NULL, + gettext_noop ("number of element in set A-B"), 1, + &GNUNET_GETOPT_set_uint, &asize}, + {'B', "bsize", NULL, + gettext_noop ("number of element in set B-A"), 1, + &GNUNET_GETOPT_set_uint, &bsize}, + {'C', "csize", NULL, + gettext_noop ("number of common elements in A and B"), 1, + &GNUNET_GETOPT_set_uint, &csize}, + {'k', "hash-num", NULL, + gettext_noop ("hash num"), 1, + &GNUNET_GETOPT_set_uint, &hash_num}, + {'s', "ibf-size", NULL, + gettext_noop ("ibf size"), 1, + &GNUNET_GETOPT_set_uint, &ibf_size}, + GNUNET_GETOPT_OPTION_END + }; + GNUNET_PROGRAM_run2 (argc, argv, "gnunet-consensus-ibf", + "help", + options, &run, NULL, GNUNET_YES); + return 0; +} + diff --git a/src/consensus/gnunet-consensus-start-peers.c b/src/consensus/gnunet-consensus-start-peers.c new file mode 100644 index 0000000..fb7f047 --- /dev/null +++ b/src/consensus/gnunet-consensus-start-peers.c @@ -0,0 +1,172 @@ + +/* + This file is part of GNUnet + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 2, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. + */ + +/** + * @file consensus/gnunet-consensus-start-peers.c + * @brief Starts peers with testebed on localhost, + * prints their configuration files and waits for ^C. + * @author Florian Dold + */ +#include "platform.h" +#include "gnunet_util_lib.h" +#include "gnunet_testbed_service.h" + + +static char *config_template_file; +static unsigned int num_peers_requested = 2; +static struct GNUNET_TESTBED_Peer **peers; + + +/** + * Callback to be called when the requested peer information is available + * + * @param cb_cls the closure from GNUNET_TETSBED_peer_get_information() + * @param op the operation this callback corresponds to + * @param pinfo the result; will be NULL if the operation has failed + * @param emsg error message if the operation has failed; will be NULL if the + * operation is successfull + */ +static void +peer_info_cb (void *cb_cls, + struct GNUNET_TESTBED_Operation + *op, + const struct + GNUNET_TESTBED_PeerInformation + *pinfo, + const char *emsg) +{ + GNUNET_assert (NULL == emsg); + if (pinfo->pit == GNUNET_TESTBED_PIT_IDENTITY) + { + struct GNUNET_CRYPTO_HashAsciiEncoded enc; + GNUNET_CRYPTO_hash_to_enc (&pinfo->result.id->hashPubKey, &enc); + printf("peer %td identity:\n", ((struct GNUNET_TESTBED_Peer **) cb_cls) - &peers[0]); + printf("%s\n", (char *)&enc); + } + else if (pinfo->pit == GNUNET_TESTBED_PIT_CONFIGURATION) + { + char *tmpfilename; + if (NULL == (tmpfilename = GNUNET_DISK_mktemp ("gnunet-consensus"))) + { + GNUNET_break (0); + GNUNET_SCHEDULER_shutdown (); + return; + } + if (GNUNET_SYSERR == + GNUNET_CONFIGURATION_write (pinfo->result.cfg, + tmpfilename)) + { + GNUNET_break (0); + return; + } + printf("peer %td config file:\n", ((struct GNUNET_TESTBED_Peer **) cb_cls) - &peers[0]); + printf("%s\n", tmpfilename); + } + else + { + GNUNET_assert (0); + } +} + + + +/** + * Signature of the event handler function called by the + * respective event controller. + * + * @param cls closure + * @param event information about the event + */ +static void +controller_cb(void *cls, + const struct GNUNET_TESTBED_EventInformation *event) +{ + GNUNET_assert (0); +} + + + + +static void +test_master (void *cls, + unsigned int num_peers, + struct GNUNET_TESTBED_Peer **started_peers) +{ + int i; + + printf("started %d peers\n", num_peers); + peers = started_peers; + + for (i = 0; i < num_peers; i++) + { + GNUNET_TESTBED_peer_get_information (peers[i], + GNUNET_TESTBED_PIT_IDENTITY, + peer_info_cb, + &peers[i]); + GNUNET_TESTBED_peer_get_information (peers[i], + GNUNET_TESTBED_PIT_CONFIGURATION, + peer_info_cb, + &peers[i]); + } +} + + +static void +run (void *cls, char *const *args, const char *cfgfile, + const struct GNUNET_CONFIGURATION_Handle *config) +{ + if (NULL == config_template_file) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "no template file specified\n"); + return; + } + + (void) GNUNET_TESTBED_test_run ("gnunet-consensus-start-peers", + config_template_file, + num_peers_requested, + 0, + controller_cb, + NULL, + test_master, + NULL); +} + + +int +main (int argc, char **argv) +{ + static const struct GNUNET_GETOPT_CommandLineOption options[] = { + { 't', "config-template", "TEMPLATE", + gettext_noop ("start peers with the given template configuration"), + GNUNET_YES, &GNUNET_GETOPT_set_string, &config_template_file }, + { 'n', "num-peers", "NUM", + gettext_noop ("number of peers to start"), + GNUNET_YES, &GNUNET_GETOPT_set_uint, &num_peers_requested }, + GNUNET_GETOPT_OPTION_END + }; + + /* run without scheduler, as test_run already does this */ + GNUNET_PROGRAM_run2 (argc, argv, "gnunet-consensus-start-peers", + "help", + options, &run, NULL, GNUNET_YES); + return 0; +} + diff --git a/src/consensus/gnunet-consensus.c b/src/consensus/gnunet-consensus.c new file mode 100644 index 0000000..a635758 --- /dev/null +++ b/src/consensus/gnunet-consensus.c @@ -0,0 +1,336 @@ +/* + This file is part of GNUnet + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 2, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. + */ + +/** + * @file consensus/gnunet-consensus.c + * @brief profiling tool for gnunet-consensus + * @author Florian Dold + */ +#include "platform.h" +#include "gnunet_common.h" +#include "gnunet_util_lib.h" +#include "gnunet_consensus_service.h" +#include "gnunet_testbed_service.h" + +static unsigned int num_peers = 2; + +static unsigned int replication = 1; + +static unsigned int num_values = 5; + +static struct GNUNET_TIME_Relative conclude_timeout; + +static struct GNUNET_CONSENSUS_Handle **consensus_handles; + +static unsigned int num_connected_handles; + +static struct GNUNET_TESTBED_Peer **peers; + +static struct GNUNET_PeerIdentity *peer_ids; + +static unsigned int num_retrieved_peer_ids; + +static struct GNUNET_HashCode session_id; + + +/** + * Signature of the event handler function called by the + * respective event controller. + * + * @param cls closure + * @param event information about the event + */ +static void +controller_cb(void *cls, + const struct GNUNET_TESTBED_EventInformation *event) +{ + GNUNET_assert (0); +} + + +/** + * Called when a conclusion was successful. + * + * @param cls + * @param group + * @return GNUNET_YES if more consensus groups should be offered, GNUNET_NO if not + */ +static int +conclude_cb (void *cls, const struct GNUNET_CONSENSUS_Group *group) +{ + return GNUNET_NO; +} + + + +static void +generate_indices (int *indices) +{ + int j; + j = 0; + while (j < replication) + { + int n; + int k; + int repeat; + n = GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK, num_peers); + repeat = GNUNET_NO; + for (k = 0; k < j; k++) + if (indices[k] == n) + { + repeat = GNUNET_YES; + break; + } + if (GNUNET_NO == repeat) + indices[j++] = n; + } +} + + +static void +do_consensus () +{ + int unique_indices[replication]; + int i; + + for (i = 0; i < num_values; i++) + { + int j; + struct GNUNET_HashCode *val; + struct GNUNET_CONSENSUS_Element *element; + generate_indices(unique_indices); + + val = GNUNET_malloc (sizeof *val); + GNUNET_CRYPTO_hash_create_random (GNUNET_CRYPTO_QUALITY_WEAK, val); + + element = GNUNET_malloc (sizeof *element); + element->data = val; + element->size = sizeof *val; + + for (j = 0; j < replication; j++) + { + int cid; + cid = unique_indices[j]; + GNUNET_CONSENSUS_insert (consensus_handles[cid], element, NULL, NULL); + } + } + + for (i = 0; i < num_peers; i++) + GNUNET_CONSENSUS_conclude (consensus_handles[i], conclude_timeout, 0, conclude_cb, consensus_handles[i]); +} + + +/** + * Callback to be called when a service connect operation is completed + * + * @param cls the callback closure from functions generating an operation + * @param op the operation that has been finished + * @param ca_result the service handle returned from GNUNET_TESTBED_ConnectAdapter() + * @param emsg error message in case the operation has failed; will be NULL if + * operation has executed successfully. + */ +static void +connect_complete (void *cls, + struct GNUNET_TESTBED_Operation *op, + void *ca_result, + const char *emsg) +{ + struct GNUNET_CONSENSUS_Handle **chp; + + if (NULL != emsg) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "testbed connect emsg: %s\n", emsg); + GNUNET_assert (0); + } + + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "connect complete\n"); + + chp = (struct GNUNET_CONSENSUS_Handle **) cls; + *chp = (struct GNUNET_CONSENSUS_Handle *) ca_result; + num_connected_handles++; + + if (num_connected_handles == num_peers) + { + do_consensus (); + } +} + + +static int +new_element_cb (void *cls, + struct GNUNET_CONSENSUS_Element *element) +{ + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "received new element\n"); + return GNUNET_YES; +} + + +/** + * Adapter function called to establish a connection to + * a service. + * + * @param cls closure + * @param cfg configuration of the peer to connect to; will be available until + * GNUNET_TESTBED_operation_done() is called on the operation returned + * from GNUNET_TESTBED_service_connect() + * @return service handle to return in 'op_result', NULL on error + */ +static void * +connect_adapter (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg) +{ + struct GNUNET_CONSENSUS_Handle *consensus; + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "connect adapter, %d peers\n", num_peers); + consensus = GNUNET_CONSENSUS_create (cfg, num_peers, peer_ids, &session_id, new_element_cb, NULL); + GNUNET_assert (NULL != consensus); + return consensus; +} + + +/** + * Adapter function called to destroy a connection to + * a service. + * + * @param cls closure + * @param op_result service handle returned from the connect adapter + */ +static void +disconnect_adapter(void *cls, void *op_result) +{ + /* FIXME: what to do here? */ +} + + +/** + * Callback to be called when the requested peer information is available + * + * @param cb_cls the closure from GNUNET_TETSBED_peer_get_information() + * @param op the operation this callback corresponds to + * @param pinfo the result; will be NULL if the operation has failed + * @param emsg error message if the operation has failed; will be NULL if the + * operation is successfull + */ +static void +peer_info_cb (void *cb_cls, + struct GNUNET_TESTBED_Operation *op, + const struct GNUNET_TESTBED_PeerInformation *pinfo, + const char *emsg) +{ + struct GNUNET_PeerIdentity *p; + int i; + + GNUNET_assert (NULL == emsg); + + p = (struct GNUNET_PeerIdentity *) cb_cls; + + if (pinfo->pit == GNUNET_TESTBED_PIT_IDENTITY) + { + *p = *pinfo->result.id; + num_retrieved_peer_ids++; + if (num_retrieved_peer_ids == num_peers) + for (i = 0; i < num_peers; i++) + GNUNET_TESTBED_service_connect (NULL, peers[i], "consensus", connect_complete, &consensus_handles[i], + connect_adapter, disconnect_adapter, NULL); + } + else + { + GNUNET_assert (0); + } +} + + +static void +test_master (void *cls, + unsigned int num_peers, + struct GNUNET_TESTBED_Peer **started_peers) +{ + int i; + + + GNUNET_log_setup ("gnunet-consensus", "INFO", NULL); + + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "test master\n"); + + + peers = started_peers; + + peer_ids = GNUNET_malloc (num_peers * sizeof (struct GNUNET_PeerIdentity)); + + consensus_handles = GNUNET_malloc (num_peers * sizeof (struct ConsensusHandle *)); + + for (i = 0; i < num_peers; i++) + GNUNET_TESTBED_peer_get_information (peers[i], + GNUNET_TESTBED_PIT_IDENTITY, + peer_info_cb, + &peer_ids[i]); +} + +static void +run (void *cls, char *const *args, const char *cfgfile, + const struct GNUNET_CONFIGURATION_Handle *cfg) +{ + static char *session_str = "gnunet-consensus/test"; + + if (num_peers < replication) + { + fprintf (stderr, "k must be <=n\n"); + return; + } + + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "running gnunet-consensus\n"); + + GNUNET_CRYPTO_hash (session_str, strlen(session_str), &session_id); + + (void) GNUNET_TESTBED_test_run ("gnunet-consensus", + cfgfile, + num_peers, + 0, + controller_cb, + NULL, + test_master, + NULL); +} + + +int +main (int argc, char **argv) +{ + static const struct GNUNET_GETOPT_CommandLineOption options[] = { + { 'n', "num-peers", NULL, + gettext_noop ("number of peers in consensus"), + GNUNET_YES, &GNUNET_GETOPT_set_uint, &num_peers }, + { 'k', "value-replication", NULL, + gettext_noop ("how many peers receive one value?"), + GNUNET_YES, &GNUNET_GETOPT_set_uint, &replication }, + { 'x', "num-values", NULL, + gettext_noop ("number of values"), + GNUNET_YES, &GNUNET_GETOPT_set_uint, &num_values }, + { 't', "timeout", NULL, + gettext_noop ("consensus timeout"), + GNUNET_YES, &GNUNET_GETOPT_set_relative_time, &conclude_timeout }, + GNUNET_GETOPT_OPTION_END + }; + conclude_timeout = GNUNET_TIME_UNIT_SECONDS; + GNUNET_PROGRAM_run2 (argc, argv, "gnunet-consensus", + "help", + options, &run, NULL, GNUNET_YES); + return 0; +} + diff --git a/src/consensus/gnunet-service-consensus.c b/src/consensus/gnunet-service-consensus.c new file mode 100644 index 0000000..1cbb9d0 --- /dev/null +++ b/src/consensus/gnunet-service-consensus.c @@ -0,0 +1,1835 @@ +/* + This file is part of GNUnet + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 2, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + + +/** + * @file consensus/gnunet-service-consensus.c + * @brief + * @author Florian Dold + */ + +#include "platform.h" +#include "gnunet_common.h" +#include "gnunet_protocols.h" +#include "gnunet_applications.h" +#include "gnunet_util_lib.h" +#include "gnunet_consensus_service.h" +#include "gnunet_core_service.h" +#include "gnunet_stream_lib.h" +#include "consensus_protocol.h" +#include "ibf.h" +#include "consensus.h" + + +/** + * Number of IBFs in a strata estimator. + */ +#define STRATA_COUNT 32 +/** + * Number of buckets per IBF. + */ +#define STRATA_IBF_BUCKETS 80 +/** + * hash num parameter of the IBF + */ +#define STRATA_HASH_NUM 3 +/** + * Number of strata that can be transmitted in one message. + */ +#define STRATA_PER_MESSAGE ((1<<15) / (IBF_BUCKET_SIZE * STRATA_IBF_BUCKETS)) + +#define BUCKETS_PER_MESSAGE ((1<<15) / IBF_BUCKET_SIZE) + +#define MAX_IBF_ORDER (64) + + +/* forward declarations */ + +struct ConsensusSession; +struct IncomingSocket; +struct ConsensusPeerInformation; + +static void +send_next (struct ConsensusSession *session); + +static void +write_strata (void *cls, enum GNUNET_STREAM_Status status, size_t size); + +static void +write_ibf (void *cls, enum GNUNET_STREAM_Status status, size_t size); + +static void +write_values (void *cls, enum GNUNET_STREAM_Status status, size_t size); + +static int +get_peer_idx (const struct GNUNET_PeerIdentity *peer, const struct ConsensusSession *session); + + +/** + * An element that is waiting to be transmitted to a client. + */ +struct PendingElement +{ + /** + * Pending elements are kept in a DLL. + */ + struct PendingElement *next; + + /** + * Pending elements are kept in a DLL. + */ + struct PendingElement *prev; + + /** + * The actual element + */ + struct GNUNET_CONSENSUS_Element *element; + + /* peer this element is coming from */ + struct ConsensusPeerInformation *cpi; +}; + +struct ConsensusPeerInformation +{ + struct GNUNET_STREAM_Socket *socket; + + /** + * Is socket's connection established, i.e. can we write to it? + * Only relevent on outgoing cpi. + */ + int is_connected; + + /** + * Type of the peer in the all-to-all rounds, + * GNUNET_YES if we initiate reconciliation. + */ + int is_outgoing; + + /** + * Did we receive/send a consensus hello? + */ + int hello; + + /** + * Handle for currently active read + */ + struct GNUNET_STREAM_ReadHandle *rh; + + /** + * Handle for currently active read + */ + struct GNUNET_STREAM_WriteHandle *wh; + + /** + * How many of the strate in the ibf were + * sent or received in this round? + */ + int strata_counter; + + int ibf_order; + + struct InvertibleBloomFilter *outgoing_ibf; + + int outgoing_bucket_counter; + + struct InvertibleBloomFilter *incoming_ibf; + + int incoming_bucket_counter; + + /** + * NULL or incoming_ibf - outgoing_ibf. + * Decoded values of side '1' are to be requested from the the peer. + */ + struct InvertibleBloomFilter *diff_ibf; + + /** + * Strata estimator of the peer, NULL if our peer + * initiated the reconciliation. + */ + struct InvertibleBloomFilter **strata; + + unsigned int diff; + + struct GNUNET_SERVER_MessageStreamTokenizer *mst; + + struct ConsensusSession *session; +}; + +struct QueuedMessage +{ + struct GNUNET_MessageHeader *msg; + + /** + * Queued messages are stored in a doubly linked list. + */ + struct QueuedMessage *next; + + /** + * Queued messages are stored in a doubly linked list. + */ + struct QueuedMessage *prev; +}; + + +/** + * A consensus session consists of one local client and the remote authorities. + */ +struct ConsensusSession +{ + /** + * Consensus sessions are kept in a DLL. + */ + struct ConsensusSession *next; + + /** + * Consensus sessions are kept in a DLL. + */ + struct ConsensusSession *prev; + + /** + * Join message. Used to initialize the session later, + * if the identity of the local peer is not yet known. + * NULL if the session has been fully initialized. + */ + struct GNUNET_CONSENSUS_JoinMessage *join_msg; + + /** + * Global consensus identification, computed + * from the local id and participating authorities. + */ + struct GNUNET_HashCode global_id; + + /** + * Local client in this consensus session. + * There is only one client per consensus session. + */ + struct GNUNET_SERVER_Client *client; + + /** + * Values in the consensus set of this session, + * all of them either have been sent by or approved by the client. + */ + struct GNUNET_CONTAINER_MultiHashMap *values; + + /** + * Elements that have not been approved (or rejected) by the client yet. + */ + struct PendingElement *approval_pending_head; + + /** + * Elements that have not been approved (or rejected) by the client yet. + */ + struct PendingElement *approval_pending_tail; + + struct QueuedMessage *client_messages_head; + + struct QueuedMessage *client_messages_tail; + + /** + * Currently active transmit handle for sending to the client + */ + struct GNUNET_SERVER_TransmitHandle *th; + + /** + * Once conclude_requested is GNUNET_YES, the client may not + * insert any more values. + */ + int conclude_requested; + + /** + * Minimum number of peers to form a consensus group + */ + int conclude_group_min; + + /** + * Current round of the conclusion + */ + int current_round; + + /** + * Soft deadline for conclude. + * Speed up the speed of the consensus at the cost of consensus quality, as + * the time approached or crosses the deadline. + */ + struct GNUNET_TIME_Absolute conclude_deadline; + + /** + * Number of other peers in the consensus + */ + unsigned int num_peers; + + struct ConsensusPeerInformation *info; + + /** + * Sorted array of peer identities in this consensus session, + * includes the local peer. + */ + struct GNUNET_PeerIdentity *peers; + + /** + * Index of the local peer in the peers array + */ + int local_peer_idx; + + /** + * Task identifier for the round timeout task + */ + GNUNET_SCHEDULER_TaskIdentifier round_timeout_tid; + + struct InvertibleBloomFilter **strata; + + struct InvertibleBloomFilter **ibfs; +}; + + +/** + * Sockets from other peers who want to communicate with us. + * It may not be known yet which consensus session they belong to. + */ +struct IncomingSocket +{ + /** + * Incoming sockets are kept in a double linked list. + */ + struct IncomingSocket *next; + + /** + * Incoming sockets are kept in a double linked list. + */ + struct IncomingSocket *prev; + + /** + * The actual socket. + */ + struct GNUNET_STREAM_Socket *socket; + + /** + * Handle for currently active read + */ + struct GNUNET_STREAM_ReadHandle *rh; + + /** + * Peer that connected to us with the socket. + */ + struct GNUNET_PeerIdentity *peer; + + /** + * Message stream tokenizer for this socket. + */ + struct GNUNET_SERVER_MessageStreamTokenizer *mst; + + /** + * Peer-in-session this socket belongs to, once known, otherwise NULL. + */ + struct ConsensusPeerInformation *cpi; +}; + +static struct IncomingSocket *incoming_sockets_head; +static struct IncomingSocket *incoming_sockets_tail; + +/** + * Linked list of sesstions this peer participates in. + */ +static struct ConsensusSession *sessions_head; + +/** + * Linked list of sesstions this peer participates in. + */ +static struct ConsensusSession *sessions_tail; + +/** + * Configuration of the consensus service. + */ +static const struct GNUNET_CONFIGURATION_Handle *cfg; + +/** + * Handle to the server for this service. + */ +static struct GNUNET_SERVER_Handle *srv; + +/** + * Peer that runs this service. + */ +static struct GNUNET_PeerIdentity *my_peer; + +/** + * Handle to the core service. Only used during service startup, will be NULL after that. + */ +static struct GNUNET_CORE_Handle *core; + +/** + * Listener for sockets from peers that want to reconcile with us. + */ +static struct GNUNET_STREAM_ListenSocket *listener; + + +static void +queue_client_message (struct ConsensusSession *session, struct GNUNET_MessageHeader *msg) +{ + struct QueuedMessage *qm; + qm = GNUNET_malloc (sizeof *qm); + qm->msg = msg; + GNUNET_CONTAINER_DLL_insert_tail (session->client_messages_head, session->client_messages_tail, qm); +} + + +static int +estimate_difference (struct InvertibleBloomFilter** strata1, + struct InvertibleBloomFilter** strata2) +{ + int i; + int count; + count = 0; + for (i = STRATA_COUNT - 1; i >= 0; i--) + { + struct InvertibleBloomFilter *diff; + int ibf_count; + int more; + ibf_count = 0; + diff = ibf_dup (strata1[i]); + ibf_subtract (diff, strata2[i]); + for (;;) + { + more = ibf_decode (diff, NULL, NULL); + if (GNUNET_NO == more) + { + count += ibf_count; + break; + } + if (GNUNET_SYSERR == more) + { + return count * (1 << (i + 1)); + } + ibf_count++; + } + ibf_destroy (diff); + } + return count; +} + + + +/** + * Functions of this signature are called whenever data is available from the + * stream. + * + * @param cls the closure from GNUNET_STREAM_read + * @param status the status of the stream at the time this function is called + * @param data traffic from the other side + * @param size the number of bytes available in data read; will be 0 on timeout + * @return number of bytes of processed from 'data' (any data remaining should be + * given to the next time the read processor is called). + */ +static size_t +session_stream_data_processor (void *cls, + enum GNUNET_STREAM_Status status, + const void *data, + size_t size) +{ + struct ConsensusPeerInformation *cpi; + int ret; + + GNUNET_assert (GNUNET_STREAM_OK == status); + + cpi = cls; + + GNUNET_assert (NULL != cpi->mst); + + ret = GNUNET_SERVER_mst_receive (cpi->mst, cpi, data, size, GNUNET_NO, GNUNET_YES); + if (GNUNET_SYSERR == ret) + { + /* FIXME: handle this correctly */ + GNUNET_assert (0); + } + + /* read again */ + cpi->rh = GNUNET_STREAM_read (cpi->socket, GNUNET_TIME_UNIT_FOREVER_REL, + &session_stream_data_processor, cpi); + + /* we always read all data */ + return size; +} + +/** + * Functions of this signature are called whenever data is available from the + * stream. + * + * @param cls the closure from GNUNET_STREAM_read + * @param status the status of the stream at the time this function is called + * @param data traffic from the other side + * @param size the number of bytes available in data read; will be 0 on timeout + * @return number of bytes of processed from 'data' (any data remaining should be + * given to the next time the read processor is called). + */ +static size_t +incoming_stream_data_processor (void *cls, + enum GNUNET_STREAM_Status status, + const void *data, + size_t size) +{ + struct IncomingSocket *incoming; + int ret; + + GNUNET_assert (GNUNET_STREAM_OK == status); + + incoming = cls; + + ret = GNUNET_SERVER_mst_receive (incoming->mst, incoming, data, size, GNUNET_NO, GNUNET_YES); + if (GNUNET_SYSERR == ret) + { + /* FIXME: handle this correctly */ + GNUNET_assert (0); + } + + /* read again */ + incoming->rh = GNUNET_STREAM_read (incoming->socket, GNUNET_TIME_UNIT_FOREVER_REL, + &incoming_stream_data_processor, incoming); + + /* we always read all data */ + return size; +} + + +/** + * Iterator over hash map entries. + * + * @param cls closure + * @param key current key code + * @param value value in the hash map + * @return GNUNET_YES if we should continue to + * iterate, + * GNUNET_NO if not. + */ +static int +ibf_values_iterator (void *cls, + const struct GNUNET_HashCode *key, + void *value) +{ + struct ConsensusPeerInformation *cpi; + cpi = cls; + ibf_insert (cpi->session->ibfs[cpi->ibf_order], key); + return GNUNET_YES; +} + + +static void +create_outgoing_ibf (struct ConsensusPeerInformation *cpi) +{ + if (NULL == cpi->session->ibfs[cpi->ibf_order]) + { + cpi->session->ibfs[cpi->ibf_order] = ibf_create (1 << cpi->ibf_order, STRATA_HASH_NUM, 0); + GNUNET_CONTAINER_multihashmap_iterate (cpi->session->values, ibf_values_iterator, cpi); + } + cpi->outgoing_ibf = ibf_dup (cpi->session->ibfs[cpi->ibf_order]); +} + +static int +handle_p2p_strata (struct ConsensusPeerInformation *cpi, const struct StrataMessage *strata_msg) +{ + int i; + int num_strata; + struct GNUNET_HashCode *hash_src; + uint8_t *count_src; + + GNUNET_assert (GNUNET_NO == cpi->is_outgoing); + + if (NULL == cpi->strata) + { + cpi->strata = GNUNET_malloc (STRATA_COUNT * sizeof (struct InvertibleBloomFilter *)); + for (i = 0; i < STRATA_COUNT; i++) + cpi->strata[i] = ibf_create (STRATA_IBF_BUCKETS, STRATA_HASH_NUM, 0); + } + + num_strata = ntohs (strata_msg->num_strata); + + /* for correct message alignment, copy bucket types seperately */ + hash_src = (struct GNUNET_HashCode *) &strata_msg[1]; + + for (i = 0; i < num_strata; i++) + { + memcpy (cpi->strata[cpi->strata_counter+i]->hash_sum, hash_src, STRATA_IBF_BUCKETS * sizeof *hash_src); + hash_src += STRATA_IBF_BUCKETS; + } + + for (i = 0; i < num_strata; i++) + { + memcpy (cpi->strata[cpi->strata_counter+i]->id_sum, hash_src, STRATA_IBF_BUCKETS * sizeof *hash_src); + hash_src += STRATA_IBF_BUCKETS; + } + + count_src = (uint8_t *) hash_src; + + for (i = 0; i < num_strata; i++) + { + memcpy (cpi->strata[cpi->strata_counter+i]->count, count_src, STRATA_IBF_BUCKETS); + count_src += STRATA_IBF_BUCKETS; + } + + GNUNET_assert (count_src == (((uint8_t *) &strata_msg[1]) + STRATA_IBF_BUCKETS * num_strata * IBF_BUCKET_SIZE)); + + cpi->strata_counter += num_strata; + + if (STRATA_COUNT == cpi->strata_counter) + { + + cpi->diff = estimate_difference (cpi->session->strata, cpi->strata); + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "received strata, diff=%d\n", cpi->diff); + cpi->ibf_order = 0; + while ((1 << cpi->ibf_order) < cpi->diff) + cpi->ibf_order++; + if (cpi->ibf_order > MAX_IBF_ORDER) + cpi->ibf_order = MAX_IBF_ORDER; + cpi->ibf_order += 2; + create_outgoing_ibf (cpi); + write_ibf (cpi, GNUNET_STREAM_OK, 0); + } + + return GNUNET_YES; +} + + +static int +handle_p2p_ibf (struct ConsensusPeerInformation *cpi, const struct DifferenceDigest *digest) +{ + struct GNUNET_HashCode *hash_src; + int num_buckets; + uint8_t *count_src; + + num_buckets = (ntohs (digest->header.size) - (sizeof *digest)) / IBF_BUCKET_SIZE; + + if (cpi->is_outgoing == GNUNET_YES) + { + /* we receive the ibf as an initiator, thus we're interested in the order */ + cpi->ibf_order = digest->order; + if ((0 == cpi->outgoing_bucket_counter) && (NULL == cpi->wh)) + { + create_outgoing_ibf (cpi); + write_ibf (cpi, GNUNET_STREAM_OK, 0); + } + /* FIXME: ensure that orders do not differ each time */ + } + else + { + /* FIXME: handle correctly */ + GNUNET_assert (cpi->ibf_order == digest->order); + } + + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "receiving %d buckets at %d of %d\n", num_buckets, cpi->incoming_bucket_counter, (1 << cpi->ibf_order)); + + if (cpi->incoming_bucket_counter + num_buckets > (1 << cpi->ibf_order)) + { + /* TODO: handle this */ + GNUNET_assert (0); + } + + if (NULL == cpi->incoming_ibf) + cpi->incoming_ibf = ibf_create (1 << cpi->ibf_order, STRATA_HASH_NUM, 0); + + hash_src = (struct GNUNET_HashCode *) &digest[1]; + + memcpy (cpi->incoming_ibf->hash_sum, hash_src, num_buckets * sizeof *hash_src); + hash_src += num_buckets; + + memcpy (cpi->incoming_ibf->id_sum, hash_src, num_buckets * sizeof *hash_src); + hash_src += num_buckets; + + count_src = (uint8_t *) hash_src; + + memcpy (cpi->incoming_ibf->count, count_src, num_buckets * sizeof *count_src); + + cpi->incoming_bucket_counter += num_buckets; + + if (cpi->incoming_bucket_counter == (1 << cpi->ibf_order)) + { + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "received full ibf\n"); + if ((NULL == cpi->wh) && (cpi->outgoing_bucket_counter == (1 << cpi->ibf_order))) + write_values (cpi, GNUNET_STREAM_OK, 0); + } + return GNUNET_YES; +} + + +static int +handle_p2p_element (struct ConsensusPeerInformation *cpi, const struct GNUNET_MessageHeader *element_msg) +{ + struct PendingElement *pending_element; + struct GNUNET_CONSENSUS_Element *element; + struct GNUNET_CONSENSUS_ElementMessage *client_element_msg; + size_t size; + + size = ntohs (element_msg->size) - sizeof *element_msg; + + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "receiving element, size=%d\n", size); + + element = GNUNET_malloc (size + sizeof *element); + element->size = size; + memcpy (&element[1], &element_msg[1], size); + element->data = &element[1]; + + pending_element = GNUNET_malloc (sizeof *pending_element); + pending_element->element = element; + GNUNET_CONTAINER_DLL_insert_tail (cpi->session->approval_pending_head, cpi->session->approval_pending_tail, pending_element); + + client_element_msg = GNUNET_malloc (size + sizeof *client_element_msg); + client_element_msg->header.type = htons (GNUNET_MESSAGE_TYPE_CONSENSUS_CLIENT_RECEIVED_ELEMENT); + client_element_msg->header.size = htons (size + sizeof *client_element_msg); + memcpy (&client_element_msg[1], &element[1], size); + + queue_client_message (cpi->session, (struct GNUNET_MessageHeader *) client_element_msg); + + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "received element\n"); + + send_next (cpi->session); + + return GNUNET_YES; +} + + +static int +handle_p2p_hello (struct IncomingSocket *inc, const struct ConsensusHello *hello) +{ + /* FIXME: session might not exist yet */ + struct ConsensusSession *session; + session = sessions_head; + while (NULL != session) + { + if (0 == GNUNET_CRYPTO_hash_cmp (&session->global_id, &hello->global_id)) + { + int idx; + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "peer helloed session\n"); + idx = get_peer_idx (inc->peer, session); + GNUNET_assert (-1 != idx); + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "idx is %d\n", idx); + inc->cpi = &session->info[idx]; + GNUNET_assert (GNUNET_NO == inc->cpi->is_outgoing); + inc->cpi->mst = inc->mst; + inc->cpi->hello = GNUNET_YES; + inc->cpi->socket = inc->socket; + return GNUNET_YES; + } + session = session->next; + } + GNUNET_assert (0); + return GNUNET_NO; +} + + +/** + * Functions with this signature are called whenever a + * complete message is received by the tokenizer. + * + * Do not call GNUNET_SERVER_mst_destroy in callback + * + * @param cls closure + * @param client identification of the client + * @param message the actual message + * + * @return GNUNET_OK on success, GNUNET_SYSERR to stop further processing + */ +static int +mst_session_callback (void *cls, void *client, const struct GNUNET_MessageHeader *message) +{ + struct ConsensusPeerInformation *cpi; + cpi = cls; + switch (ntohs (message->type)) + { + case GNUNET_MESSAGE_TYPE_CONSENSUS_P2P_DELTA_ESTIMATE: + return handle_p2p_strata (cpi, (struct StrataMessage *) message); + case GNUNET_MESSAGE_TYPE_CONSENSUS_P2P_DIFFERENCE_DIGEST: + return handle_p2p_ibf (cpi, (struct DifferenceDigest *) message); + case GNUNET_MESSAGE_TYPE_CONSENSUS_P2P_ELEMENTS: + return handle_p2p_element (cpi, message); + default: + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "unexpected message type from peer: %u\n", ntohs (message->type)); + /* FIXME: handle correctly */ + GNUNET_assert (0); + } + return GNUNET_OK; +} + + +/** + * Handle tokenized messages from stream sockets. + * Delegate them if the socket belongs to a session, + * handle hello messages otherwise. + * + * Do not call GNUNET_SERVER_mst_destroy in callback + * + * @param cls closure, unused + * @param client incoming socket this message comes from + * @param message the actual message + * + * @return GNUNET_OK on success, GNUNET_SYSERR to stop further processing + */ +static int +mst_incoming_callback (void *cls, void *client, const struct GNUNET_MessageHeader *message) +{ + struct IncomingSocket *inc; + inc = (struct IncomingSocket *) client; + switch (ntohs( message->type)) + { + case GNUNET_MESSAGE_TYPE_CONSENSUS_P2P_HELLO: + return handle_p2p_hello (inc, (struct ConsensusHello *) message); + default: + if (NULL != inc->cpi) + return mst_session_callback (inc->cpi, client, message); + /* FIXME: disconnect peer properly */ + GNUNET_assert (0); + } + return GNUNET_OK; +} + + +/** + * Functions of this type are called upon new stream connection from other peers + * or upon binding error which happen when the app_port given in + * GNUNET_STREAM_listen() is already taken. + * + * @param cls the closure from GNUNET_STREAM_listen + * @param socket the socket representing the stream; NULL on binding error + * @param initiator the identity of the peer who wants to establish a stream + * with us; NULL on binding error + * @return GNUNET_OK to keep the socket open, GNUNET_SYSERR to close the + * stream (the socket will be invalid after the call) + */ +static int +listen_cb (void *cls, + struct GNUNET_STREAM_Socket *socket, + const struct GNUNET_PeerIdentity *initiator) +{ + struct IncomingSocket *incoming; + + GNUNET_assert (NULL != socket); + + incoming = GNUNET_malloc (sizeof *incoming); + + incoming->socket = socket; + incoming->peer = GNUNET_memdup (initiator, sizeof *initiator); + + incoming->rh = GNUNET_STREAM_read (socket, GNUNET_TIME_UNIT_FOREVER_REL, + &incoming_stream_data_processor, incoming); + + + incoming->mst = GNUNET_SERVER_mst_create (mst_incoming_callback, incoming); + + GNUNET_CONTAINER_DLL_insert_tail (incoming_sockets_head, incoming_sockets_tail, incoming); + + return GNUNET_OK; +} + + +static void +destroy_session (struct ConsensusSession *session) +{ + /* FIXME: more stuff to free! */ + GNUNET_CONTAINER_DLL_remove (sessions_head, sessions_tail, session); + GNUNET_SERVER_client_drop (session->client); + GNUNET_free (session); +} + + +/** + * Disconnect a client, and destroy all sessions associated with it. + * + * @param client the client to disconnect + */ +static void +disconnect_client (struct GNUNET_SERVER_Client *client) +{ + struct ConsensusSession *session; + GNUNET_SERVER_client_disconnect (client); + + /* if the client owns a session, remove it */ + session = sessions_head; + while (NULL != session) + { + if (client == session->client) + { + destroy_session (session); + break; + } + session = session->next; + } +} + + +/** + * Compute a global, (hopefully) unique consensus session id, + * from the local id of the consensus session, and the identities of all participants. + * Thus, if the local id of two consensus sessions coincide, but are not comprised of + * exactly the same peers, the global id will be different. + * + * @param local_id local id of the consensus session + * @param peers array of all peers participating in the consensus session + * @param num_peers number of elements in the peers array + * @param dst where the result is stored, may not be NULL + */ +static void +compute_global_id (const struct GNUNET_HashCode *local_id, + const struct GNUNET_PeerIdentity *peers, int num_peers, + struct GNUNET_HashCode *dst) +{ + int i; + struct GNUNET_HashCode tmp; + + *dst = *local_id; + for (i = 0; i < num_peers; ++i) + { + GNUNET_CRYPTO_hash_xor (dst, &peers[0].hashPubKey, &tmp); + *dst = tmp; + GNUNET_CRYPTO_hash (dst, sizeof (struct GNUNET_PeerIdentity), &tmp); + *dst = tmp; + } +} + + +/** + * Function called to notify a client about the connection + * begin ready to queue more data. "buf" will be + * NULL and "size" zero if the connection was closed for + * writing in the meantime. + * + * @param cls consensus session + * @param size number of bytes available in buf + * @param buf where the callee should write the message + * @return number of bytes written to buf + */ +static size_t +transmit_queued (void *cls, size_t size, + void *buf) +{ + struct ConsensusSession *session; + struct QueuedMessage *qmsg; + size_t msg_size; + + session = cls; + session->th = NULL; + + + qmsg = session->client_messages_head; + GNUNET_CONTAINER_DLL_remove (session->client_messages_head, session->client_messages_tail, qmsg); + GNUNET_assert (qmsg); + + if (NULL == buf) + { + destroy_session (session); + return 0; + } + + msg_size = ntohs (qmsg->msg->size); + + GNUNET_assert (size >= msg_size); + + memcpy (buf, qmsg->msg, msg_size); + GNUNET_free (qmsg->msg); + GNUNET_free (qmsg); + + send_next (session); + + return msg_size; +} + + +/** + * Schedule sending the next message (if there is any) to a client. + * + * @param cli the client to send the next message to + */ +static void +send_next (struct ConsensusSession *session) +{ + + GNUNET_assert (NULL != session); + + if (NULL != session->th) + return; + + if (NULL != session->client_messages_head) + { + int msize; + msize = ntohs (session->client_messages_head->msg->size); + session->th = GNUNET_SERVER_notify_transmit_ready (session->client, msize, + GNUNET_TIME_UNIT_FOREVER_REL, + &transmit_queued, session); + } +} + + +/** + * Although GNUNET_CRYPTO_hash_cmp exisits, it does not have + * the correct signature to be used with e.g. qsort. + * We use this function instead. + * + * @param h1 some hash code + * @param h2 some hash code + * @return 1 if h1 > h2, -1 if h1 < h2 and 0 if h1 == h2. + */ +static int +hash_cmp (const void *a, const void *b) +{ + return GNUNET_CRYPTO_hash_cmp ((struct GNUNET_HashCode *) a, (struct GNUNET_HashCode *) b); +} + + +/** + * Search peer in the list of peers in session. + * + * @param peer peer to find + * @param session session with peer + * @return index of peer, -1 if peer is not in session + */ +static int +get_peer_idx (const struct GNUNET_PeerIdentity *peer, const struct ConsensusSession *session) +{ + const struct GNUNET_PeerIdentity *needle; + needle = bsearch (peer, session->peers, session->num_peers, sizeof (struct GNUNET_PeerIdentity), &hash_cmp); + if (NULL == needle) + return -1; + return needle - session->peers; +} + + + +static void +hello_cont (void *cls, enum GNUNET_STREAM_Status status, size_t size) +{ + struct ConsensusPeerInformation *cpi; + + cpi = cls; + cpi->hello = GNUNET_YES; + + GNUNET_assert (GNUNET_STREAM_OK == status); + + if (cpi->session->conclude_requested) + { + write_strata (cpi, GNUNET_STREAM_OK, 0); + } +} + + +/** + * Functions of this type will be called when a stream is established + * + * @param cls the closure from GNUNET_STREAM_open + * @param socket socket to use to communicate with the other side (read/write) + */ +static void +open_cb (void *cls, struct GNUNET_STREAM_Socket *socket) +{ + struct ConsensusPeerInformation *cpi; + struct ConsensusHello *hello; + + + cpi = cls; + cpi->is_connected = GNUNET_YES; + + hello = GNUNET_malloc (sizeof *hello); + hello->header.size = htons (sizeof *hello); + hello->header.type = htons (GNUNET_MESSAGE_TYPE_CONSENSUS_P2P_HELLO); + memcpy (&hello->global_id, &cpi->session->global_id, sizeof (struct GNUNET_HashCode)); + + cpi->wh = + GNUNET_STREAM_write (socket, hello, sizeof *hello, GNUNET_TIME_UNIT_FOREVER_REL, hello_cont, cpi); + + cpi->rh = GNUNET_STREAM_read (socket, GNUNET_TIME_UNIT_FOREVER_REL, + &session_stream_data_processor, cpi); + +} + + +static void +initialize_session_info (struct ConsensusSession *session) +{ + int i; + int last; + + for (i = 0; i < session->num_peers; ++i) + { + /* initialize back-references, so consensus peer information can + * be used as closure */ + session->info[i].session = session; + } + + last = (session->local_peer_idx + ((session->num_peers - 1) / 2) + 1) % session->num_peers; + i = (session->local_peer_idx + 1) % session->num_peers; + while (i != last) + { + session->info[i].is_outgoing = GNUNET_YES; + session->info[i].socket = GNUNET_STREAM_open (cfg, &session->peers[i], GNUNET_APPLICATION_TYPE_CONSENSUS, + open_cb, &session->info[i], GNUNET_STREAM_OPTION_END); + session->info[i].mst = GNUNET_SERVER_mst_create (mst_session_callback, &session->info[i]); + i = (i + 1) % session->num_peers; + + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "peer %d contacts peer %d\n", session->local_peer_idx, i); + } + // tie-breaker for even number of peers + if (((session->num_peers % 2) == 0) && (session->local_peer_idx < last)) + { + session->info[last].is_outgoing = GNUNET_YES; + session->info[last].socket = GNUNET_STREAM_open (cfg, &session->peers[last], GNUNET_APPLICATION_TYPE_CONSENSUS, + open_cb, &session->info[last], GNUNET_STREAM_OPTION_END); + session->info[last].mst = GNUNET_SERVER_mst_create (mst_session_callback, &session->info[last]); + + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "peer %d contacts peer %d (tiebreaker)\n", session->local_peer_idx, last); + } +} + + +/** + * Create the sorted list of peers for the session, + * add the local peer if not in the join message. + */ +static void +initialize_session_peer_list (struct ConsensusSession *session) +{ + int local_peer_in_list; + int listed_peers; + const struct GNUNET_PeerIdentity *msg_peers; + unsigned int i; + + GNUNET_assert (NULL != session->join_msg); + + /* peers in the join message, may or may not include the local peer */ + listed_peers = ntohs (session->join_msg->num_peers); + + session->num_peers = listed_peers; + + msg_peers = (struct GNUNET_PeerIdentity *) &session->join_msg[1]; + + local_peer_in_list = GNUNET_NO; + for (i = 0; i < listed_peers; i++) + { + if (0 == memcmp (&msg_peers[i], my_peer, sizeof (struct GNUNET_PeerIdentity))) + { + local_peer_in_list = GNUNET_YES; + break; + } + } + + if (GNUNET_NO == local_peer_in_list) + session->num_peers++; + + session->peers = GNUNET_malloc (session->num_peers * sizeof (struct GNUNET_PeerIdentity)); + + if (GNUNET_NO == local_peer_in_list) + session->peers[session->num_peers - 1] = *my_peer; + + memcpy (session->peers, msg_peers, listed_peers * sizeof (struct GNUNET_PeerIdentity)); + qsort (session->peers, session->num_peers, sizeof (struct GNUNET_PeerIdentity), &hash_cmp); +} + + +static void +strata_insert (struct InvertibleBloomFilter **strata, struct GNUNET_HashCode *key) +{ + uint32_t v; + int i; + v = key->bits[0]; + /* count trailing '1'-bits of v */ + for (i = 0; v & 1; v>>=1, i++); + ibf_insert (strata[i], key); +} + + +/** + * Initialize the session, continue receiving messages from the owning client + * + * @param session the session to initialize + */ +static void +initialize_session (struct ConsensusSession *session) +{ + const struct ConsensusSession *other_session; + int i; + + GNUNET_assert (NULL != session->join_msg); + + initialize_session_peer_list (session); + + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "session with %u peers\n", session->num_peers); + + compute_global_id (&session->join_msg->session_id, session->peers, session->num_peers, &session->global_id); + + /* Check if some local client already owns the session. */ + other_session = sessions_head; + while (NULL != other_session) + { + if ((other_session != session) && + (0 == GNUNET_CRYPTO_hash_cmp (&session->global_id, &other_session->global_id))) + { + /* session already owned by another client */ + GNUNET_break (0); + disconnect_client (session->client); + return; + } + other_session = other_session->next; + } + + session->values = GNUNET_CONTAINER_multihashmap_create (256, GNUNET_NO); + + session->local_peer_idx = get_peer_idx (my_peer, session); + GNUNET_assert (-1 != session->local_peer_idx); + + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "%d is the local peer\n", session->local_peer_idx); + + session->strata = GNUNET_malloc (STRATA_COUNT * sizeof (struct InvertibleBloomFilter *)); + for (i = 0; i < STRATA_COUNT; i++) + session->strata[i] = ibf_create (STRATA_IBF_BUCKETS, STRATA_HASH_NUM, 0); + + session->ibfs = GNUNET_malloc (MAX_IBF_ORDER * sizeof (struct InvertibleBloomFilter *)); + + session->info = GNUNET_malloc (session->num_peers * sizeof (struct ConsensusPeerInformation)); + initialize_session_info (session); + + GNUNET_free (session->join_msg); + session->join_msg = NULL; + + GNUNET_SERVER_receive_done (session->client, GNUNET_OK); + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "session %s initialized\n", GNUNET_h2s (&session->global_id)); +} + + +/** + * Called when a client wants to join a consensus session. + * + * @param cls unused + * @param client client that sent the message + * @param m message sent by the client + */ +static void +client_join (void *cls, + struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *m) +{ + struct ConsensusSession *session; + + // make sure the client has not already joined a session + session = sessions_head; + while (NULL != session) + { + if (session->client == client) + { + GNUNET_break (0); + disconnect_client (client); + return; + } + session = session->next; + } + + session = GNUNET_malloc (sizeof (struct ConsensusSession)); + session->join_msg = (struct GNUNET_CONSENSUS_JoinMessage *) GNUNET_copy_message (m); + session->client = client; + GNUNET_SERVER_client_keep (client); + + GNUNET_CONTAINER_DLL_insert (sessions_head, sessions_tail, session); + + // Initialize session later if local peer identity is not known yet. + if (NULL == my_peer) + { + GNUNET_SERVER_disable_receive_done_warning (client); + return; + } + + initialize_session (session); +} + + +/** + * Called when a client performs an insert operation. + * + * @param cls (unused) + * @param client client handle + * @param message message sent by the client + */ +void +client_insert (void *cls, + struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *m) +{ + struct ConsensusSession *session; + struct GNUNET_CONSENSUS_ElementMessage *msg; + struct GNUNET_CONSENSUS_Element *element; + struct GNUNET_HashCode key; + int element_size; + + session = sessions_head; + while (NULL != session) + { + if (session->client == client) + break; + } + + if (NULL == session) + { + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "client tried to insert, but client is not in any session\n"); + GNUNET_SERVER_client_disconnect (client); + return; + } + + msg = (struct GNUNET_CONSENSUS_ElementMessage *) m; + element_size = ntohs (msg->header.size )- sizeof (struct GNUNET_CONSENSUS_ElementMessage); + + element = GNUNET_malloc (sizeof (struct GNUNET_CONSENSUS_Element) + element_size); + + element->type = msg->element_type; + element->size = element_size; + memcpy (&element[1], &msg[1], element_size); + element->data = &element[1]; + + GNUNET_assert (NULL != element->data); + + GNUNET_CRYPTO_hash (element, element_size, &key); + + GNUNET_CONTAINER_multihashmap_put (session->values, &key, element, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE); + + strata_insert (session->strata, &key); + + GNUNET_SERVER_receive_done (client, GNUNET_OK); + + send_next (session); +} + + + +/** + * Functions of this signature are called whenever writing operations + * on a stream are executed + * + * @param cls the closure from GNUNET_STREAM_write + * @param status the status of the stream at the time this function is called; + * GNUNET_STREAM_OK if writing to stream was completed successfully; + * GNUNET_STREAM_TIMEOUT if the given data is not sent successfully + * (this doesn't mean that the data is never sent, the receiver may + * have read the data but its ACKs may have been lost); + * GNUNET_STREAM_SHUTDOWN if the stream is shutdown for writing in the + * mean time; GNUNET_STREAM_SYSERR if the stream is broken and cannot + * be processed. + * @param size the number of bytes written + */ +static void +write_strata (void *cls, enum GNUNET_STREAM_Status status, size_t size) +{ + struct ConsensusPeerInformation *cpi; + struct StrataMessage *strata_msg; + size_t msize; + int i; + struct GNUNET_HashCode *hash_dst; + uint8_t *count_dst; + int num_strata; + + cpi = cls; + cpi->wh = NULL; + + GNUNET_assert (GNUNET_YES == cpi->is_outgoing); + + /* FIXME: handle this */ + GNUNET_assert (GNUNET_STREAM_OK == status); + + if (STRATA_COUNT == cpi->strata_counter) + { + /* strata have been written, wait for other side's IBF */ + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "strata written\n"); + return; + } + + if ((STRATA_COUNT - cpi->strata_counter) < STRATA_PER_MESSAGE) + num_strata = (STRATA_COUNT - cpi->strata_counter); + else + num_strata = STRATA_PER_MESSAGE; + + + msize = (sizeof *strata_msg) + (num_strata * IBF_BUCKET_SIZE * STRATA_IBF_BUCKETS); + + strata_msg = GNUNET_malloc (msize); + strata_msg->header.size = htons (msize); + strata_msg->header.type = htons (GNUNET_MESSAGE_TYPE_CONSENSUS_P2P_DELTA_ESTIMATE); + strata_msg->num_strata = htons (num_strata); + + /* for correct message alignment, copy bucket types seperately */ + hash_dst = (struct GNUNET_HashCode *) &strata_msg[1]; + + for (i = 0; i < num_strata; i++) + { + memcpy (hash_dst, cpi->session->strata[cpi->strata_counter+i]->hash_sum, STRATA_IBF_BUCKETS * sizeof *hash_dst); + hash_dst += STRATA_IBF_BUCKETS; + } + + for (i = 0; i < num_strata; i++) + { + memcpy (hash_dst, cpi->session->strata[cpi->strata_counter+i]->id_sum, STRATA_IBF_BUCKETS * sizeof *hash_dst); + hash_dst += STRATA_IBF_BUCKETS; + } + + count_dst = (uint8_t *) hash_dst; + + for (i = 0; i < num_strata; i++) + { + memcpy (count_dst, cpi->session->strata[cpi->strata_counter+i]->count, STRATA_IBF_BUCKETS); + count_dst += STRATA_IBF_BUCKETS; + } + + cpi->strata_counter += num_strata; + + cpi->wh = GNUNET_STREAM_write (cpi->socket, strata_msg, msize, GNUNET_TIME_UNIT_FOREVER_REL, + write_strata, cpi); + + GNUNET_assert (NULL != cpi->wh); +} + + +/** + * Functions of this signature are called whenever writing operations + * on a stream are executed + * + * @param cls the closure from GNUNET_STREAM_write + * @param status the status of the stream at the time this function is called; + * GNUNET_STREAM_OK if writing to stream was completed successfully; + * GNUNET_STREAM_TIMEOUT if the given data is not sent successfully + * (this doesn't mean that the data is never sent, the receiver may + * have read the data but its ACKs may have been lost); + * GNUNET_STREAM_SHUTDOWN if the stream is shutdown for writing in the + * mean time; GNUNET_STREAM_SYSERR if the stream is broken and cannot + * be processed. + * @param size the number of bytes written + */ +static void +write_ibf (void *cls, enum GNUNET_STREAM_Status status, size_t size) +{ + struct ConsensusPeerInformation *cpi; + struct DifferenceDigest *digest; + int msize; + struct GNUNET_HashCode *hash_dst; + uint8_t *count_dst; + int num_buckets; + + cpi = cls; + cpi->wh = NULL; + + if (cpi->outgoing_bucket_counter == (1 << cpi->ibf_order)) + { + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "ibf completely written\n"); + if (cpi->incoming_bucket_counter == (1 << cpi->ibf_order)) + write_values (cpi, GNUNET_STREAM_OK, 0); + return; + } + + /* remaining buckets */ + num_buckets = (1 << cpi->ibf_order) - cpi->outgoing_bucket_counter; + + /* limit to maximum */ + if (num_buckets > BUCKETS_PER_MESSAGE) + num_buckets = BUCKETS_PER_MESSAGE; + + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "writing ibf buckets at %d/%d\n", cpi->outgoing_bucket_counter, (1<ibf_order)); + + msize = (sizeof *digest) + (num_buckets * IBF_BUCKET_SIZE); + + digest = GNUNET_malloc (msize); + digest->header.size = htons (msize); + digest->header.type = htons (GNUNET_MESSAGE_TYPE_CONSENSUS_P2P_DIFFERENCE_DIGEST); + digest->order = cpi->ibf_order; + + hash_dst = (struct GNUNET_HashCode *) &digest[1]; + + memcpy (hash_dst, cpi->outgoing_ibf->hash_sum, num_buckets * sizeof *hash_dst); + hash_dst += num_buckets; + + memcpy (hash_dst, cpi->outgoing_ibf->id_sum, num_buckets * sizeof *hash_dst); + hash_dst += num_buckets; + + count_dst = (uint8_t *) hash_dst; + + memcpy (count_dst, cpi->outgoing_ibf->count, num_buckets * sizeof *count_dst); + + cpi->outgoing_bucket_counter += num_buckets; + + cpi->wh = GNUNET_STREAM_write (cpi->socket, digest, msize, GNUNET_TIME_UNIT_FOREVER_REL, + write_ibf, cpi); + + GNUNET_assert (NULL != cpi->wh); +} + + +/** + * Functions of this signature are called whenever writing operations + * on a stream are executed + * + * @param cls the closure from GNUNET_STREAM_write + * @param status the status of the stream at the time this function is called; + * GNUNET_STREAM_OK if writing to stream was completed successfully; + * GNUNET_STREAM_TIMEOUT if the given data is not sent successfully + * (this doesn't mean that the data is never sent, the receiver may + * have read the data but its ACKs may have been lost); + * GNUNET_STREAM_SHUTDOWN if the stream is shutdown for writing in the + * mean time; GNUNET_STREAM_SYSERR if the stream is broken and cannot + * be processed. + * @param size the number of bytes written + */ +static void +write_values (void *cls, enum GNUNET_STREAM_Status status, size_t size) +{ + struct ConsensusPeerInformation *cpi; + struct GNUNET_HashCode key; + struct GNUNET_CONSENSUS_Element *element; + struct GNUNET_MessageHeader *element_msg; + int side; + int msize; + + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "transmitting value\n"); + + cpi = cls; + cpi->wh = NULL; + + if (NULL == cpi->diff_ibf) + { + GNUNET_assert (NULL != cpi->incoming_ibf); + GNUNET_assert (NULL != cpi->outgoing_ibf); + GNUNET_assert (cpi->outgoing_ibf->size == cpi->incoming_ibf->size); + cpi->diff_ibf = ibf_dup (cpi->incoming_ibf); + ibf_subtract (cpi->diff_ibf, cpi->outgoing_ibf); + } + + for (;;) + { + int res; + res = ibf_decode (cpi->diff_ibf, &side, &key); + if (GNUNET_SYSERR == res) + { + /* TODO: handle this correctly, request new ibf */ + GNUNET_break (0); + return; + } + if (GNUNET_NO == res) + { + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "transmitted all values\n"); + return; + } + if (-1 == side) + break; + } + + element = GNUNET_CONTAINER_multihashmap_get (cpi->session->values, &key); + + if (NULL == element) + { + /* FIXME: handle correctly */ + GNUNET_break (0); + return; + } + + msize = sizeof (struct GNUNET_MessageHeader) + element->size; + + element_msg = GNUNET_malloc (msize); + element_msg->size = htons (msize); + element_msg->type = htons (GNUNET_MESSAGE_TYPE_CONSENSUS_P2P_ELEMENTS); + + + GNUNET_assert (NULL != element->data); + + + memcpy (&element_msg[1], element->data, element->size); + + cpi->wh = GNUNET_STREAM_write (cpi->socket, element_msg, msize, GNUNET_TIME_UNIT_FOREVER_REL, + write_values, cpi); + + GNUNET_free (element_msg); + + + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "transmitted value\n"); + + GNUNET_assert (NULL != cpi->wh); +} + + +/** + * Called when a client performs the conclude operation. + * + * @param cls (unused) + * @param client client handle + * @param message message sent by the client + */ +void +client_conclude (void *cls, + struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) +{ + struct ConsensusSession *session; + int i; + + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "conclude requested\n"); + + session = sessions_head; + while ((session != NULL) && (session->client != client)) + session = session->next; + if (NULL == session) + { + /* client not found */ + GNUNET_break (0); + GNUNET_SERVER_client_disconnect (client); + return; + } + + if (GNUNET_YES == session->conclude_requested) + { + /* client requested conclude twice */ + GNUNET_break (0); + disconnect_client (client); + return; + } + + session->conclude_requested = GNUNET_YES; + + /* FIXME: write to already connected sockets */ + + for (i = 0; i < session->num_peers; i++) + { + if ( (GNUNET_YES == session->info[i].is_outgoing) && + (GNUNET_YES == session->info[i].hello) ) + { + /* kick off transmitting strata by calling the write continuation */ + write_strata (&session->info[i], GNUNET_STREAM_OK, 0); + } + } + + GNUNET_SERVER_receive_done (client, GNUNET_OK); + send_next (session); +} + + +/** + * Called when a client sends an ack + * + * @param cls (unused) + * @param client client handle + * @param message message sent by the client + */ +void +client_ack (void *cls, + struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) +{ + struct ConsensusSession *session; + struct GNUNET_CONSENSUS_AckMessage *msg; + struct PendingElement *pending; + struct GNUNET_CONSENSUS_Element *element; + struct GNUNET_HashCode key; + + session = sessions_head; + while (NULL != session) + { + if (session->client == client) + break; + } + + if (NULL == session) + { + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "client tried to ack, but client is not in any session\n"); + GNUNET_SERVER_client_disconnect (client); + return; + } + + pending = session->approval_pending_head; + + GNUNET_CONTAINER_DLL_remove (session->approval_pending_head, session->approval_pending_tail, pending); + + msg = (struct GNUNET_CONSENSUS_AckMessage *) message; + + if (msg->keep) + { + + element = pending->element; + + GNUNET_CRYPTO_hash (element, element->size, &key); + + GNUNET_CONTAINER_multihashmap_put (session->values, &key, element, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE); + + strata_insert (session->strata, &key); + } + + /* FIXME: also remove element from strata */ + + GNUNET_SERVER_receive_done (client, GNUNET_OK); +} + +/** + * Task that disconnects from core. + * + * @param cls core handle + * @param tc context information (why was this task triggered now) + */ +static void +disconnect_core (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + GNUNET_CORE_disconnect (core); + core = NULL; + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "disconnected from core\n"); +} + + +static void +core_startup (void *cls, + struct GNUNET_CORE_Handle *core, + const struct GNUNET_PeerIdentity *peer) +{ + struct ConsensusSession *session; + + my_peer = GNUNET_memdup(peer, sizeof (struct GNUNET_PeerIdentity)); + /* core can't be disconnected directly in the core startup callback, schedule a task to do it! */ + GNUNET_SCHEDULER_add_now (&disconnect_core, core); + GNUNET_log(GNUNET_ERROR_TYPE_INFO, "connected to core\n"); + + session = sessions_head; + while (NULL != session) + { + if (NULL != session->join_msg) + initialize_session (session); + session = session->next; + } +} + + +/** + * Called to clean up, after a shutdown has been requested. + * + * @param cls closure + * @param tc context information (why was this task triggered now) + */ +static void +shutdown_task (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + + /* FIXME: complete; write separate destructors for different data types */ + + while (NULL != incoming_sockets_head) + { + struct IncomingSocket *socket; + socket = incoming_sockets_head; + if (NULL == socket->cpi) + { + GNUNET_STREAM_close (socket->socket); + } + incoming_sockets_head = incoming_sockets_head->next; + GNUNET_free (socket); + } + + while (NULL != sessions_head) + { + struct ConsensusSession *session; + int i; + + session = sessions_head; + + for (i = 0; session->num_peers; i++) + { + struct ConsensusPeerInformation *cpi; + cpi = &session->info[i]; + if ((NULL != cpi) && (NULL != cpi->socket)) + { + GNUNET_STREAM_close (cpi->socket); + } + } + + if (NULL != session->client) + GNUNET_SERVER_client_disconnect (session->client); + + sessions_head = sessions_head->next; + GNUNET_free (session); + } + + if (NULL != core) + { + GNUNET_CORE_disconnect (core); + core = NULL; + } + + if (NULL != listener) + { + GNUNET_STREAM_listen_close (listener); + listener = NULL; + } + + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "handled shutdown request\n"); +} + + +/** + * Start processing consensus requests. + * + * @param cls closure + * @param server the initialized server + * @param c configuration to use + */ +static void +run (void *cls, struct GNUNET_SERVER_Handle *server, const struct GNUNET_CONFIGURATION_Handle *c) +{ + static const struct GNUNET_CORE_MessageHandler core_handlers[] = { + {NULL, 0, 0} + }; + static const struct GNUNET_SERVER_MessageHandler server_handlers[] = { + {&client_join, NULL, GNUNET_MESSAGE_TYPE_CONSENSUS_CLIENT_JOIN, 0}, + {&client_insert, NULL, GNUNET_MESSAGE_TYPE_CONSENSUS_CLIENT_INSERT, 0}, + {&client_conclude, NULL, GNUNET_MESSAGE_TYPE_CONSENSUS_CLIENT_CONCLUDE, + sizeof (struct GNUNET_CONSENSUS_ConcludeMessage)}, + {&client_ack, NULL, GNUNET_MESSAGE_TYPE_CONSENSUS_CLIENT_ACK, + sizeof (struct GNUNET_CONSENSUS_AckMessage)}, + {NULL, NULL, 0, 0} + }; + + cfg = c; + srv = server; + + GNUNET_SERVER_add_handlers (server, server_handlers); + + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, &shutdown_task, NULL); + + + listener = GNUNET_STREAM_listen (cfg, GNUNET_APPLICATION_TYPE_CONSENSUS, + listen_cb, NULL, + GNUNET_STREAM_OPTION_END); + + + /* we have to wait for the core_startup callback before proceeding with the consensus service startup */ + core = GNUNET_CORE_connect (c, NULL, &core_startup, NULL, NULL, NULL, GNUNET_NO, NULL, GNUNET_NO, core_handlers); + GNUNET_assert (NULL != core); + + GNUNET_log(GNUNET_ERROR_TYPE_INFO, "consensus running\n"); +} + + +/** + * The main function for the consensus service. + * + * @param argc number of arguments from the command line + * @param argv command line arguments + * @return 0 ok, 1 on error + */ +int +main (int argc, char *const *argv) +{ + int ret; + ret = GNUNET_SERVICE_run (argc, argv, "consensus", GNUNET_SERVICE_OPTION_NONE, &run, NULL); + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "exit\n"); + return (GNUNET_OK == ret) ? 0 : 1; +} + diff --git a/src/consensus/ibf.c b/src/consensus/ibf.c new file mode 100644 index 0000000..629fde3 --- /dev/null +++ b/src/consensus/ibf.c @@ -0,0 +1,262 @@ +/* + This file is part of GNUnet + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 2, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + + +/** + * @file consensus/ibf.c + * @brief implementation of the invertible bloom filter + * @author Florian Dold + */ + + +#include "ibf.h" + + +/** + * Create an invertible bloom filter. + * + * @param size number of IBF buckets + * @param hash_num number of buckets one element is hashed in + * @param salt salt for mingling hashes, different salt may + * result in less (or more) collisions + * @return the newly created invertible bloom filter + */ +struct InvertibleBloomFilter * +ibf_create (unsigned int size, unsigned int hash_num, uint32_t salt) +{ + struct InvertibleBloomFilter *ibf; + + ibf = GNUNET_malloc (sizeof (struct InvertibleBloomFilter)); + ibf->count = GNUNET_malloc (size * sizeof (uint8_t)); + ibf->id_sum = GNUNET_malloc (size * sizeof (struct GNUNET_HashCode)); + ibf->hash_sum = GNUNET_malloc (size * sizeof (struct GNUNET_HashCode)); + ibf->size = size; + ibf->hash_num = hash_num; + + return ibf; +} + + + +/** + * Insert an element into an IBF, with either positive or negative sign. + * + * @param ibf the IBF + * @param id the element's hash code + * @param side the sign of side determines the sign of the + * inserted element. + */ +void +ibf_insert_on_side (struct InvertibleBloomFilter *ibf, + const struct GNUNET_HashCode *key, + int side) +{ + struct GNUNET_HashCode bucket_indices; + struct GNUNET_HashCode key_copy; + struct GNUNET_HashCode key_hash; + unsigned int i; + + + GNUNET_assert ((1 == side) || (-1 == side)); + GNUNET_assert (NULL != ibf); + + { + int used_buckets[ibf->hash_num]; + + /* copy the key, if key and an entry in the IBF alias */ + key_copy = *key; + + bucket_indices = key_copy; + GNUNET_CRYPTO_hash (key, sizeof (struct GNUNET_HashCode), &key_hash); + + for (i = 0; i < ibf->hash_num; i++) + { + unsigned int bucket; + unsigned int j; + int collided; + + if ( (0 != i) && + (0 == (i % 16)) ) + GNUNET_CRYPTO_hash (&bucket_indices, sizeof (struct GNUNET_HashCode), + &bucket_indices); + + bucket = bucket_indices.bits[i%16] % ibf->size; + collided = GNUNET_NO; + for (j = 0; j < i; j++) + if (used_buckets[j] == bucket) + collided = GNUNET_YES; + if (GNUNET_YES == collided) + { + used_buckets[i] = -1; + continue; + } + used_buckets[i] = bucket; + + ibf->count[bucket] += side; + + GNUNET_CRYPTO_hash_xor (&key_copy, &ibf->id_sum[bucket], + &ibf->id_sum[bucket]); + GNUNET_CRYPTO_hash_xor (&key_hash, &ibf->hash_sum[bucket], + &ibf->hash_sum[bucket]); + } + } +} + +/** + * Insert an element into an IBF. + * + * @param ibf the IBF + * @param id the element's hash code + */ +void +ibf_insert (struct InvertibleBloomFilter *ibf, const struct GNUNET_HashCode *key) +{ + ibf_insert_on_side (ibf, key, 1); +} + +static int +ibf_is_empty (struct InvertibleBloomFilter *ibf) +{ + int i; + for (i = 0; i < ibf->size; i++) + { + int j; + if (0 != ibf->count[i]) + return GNUNET_NO; + for (j = 0; j < 16; ++j) + { + if (0 != ibf->hash_sum[i].bits[j]) + return GNUNET_NO; + if (0 != ibf->id_sum[i].bits[j]) + return GNUNET_NO; + } + } + return GNUNET_YES; +} + + +/** + * Decode and remove an element from the IBF, if possible. + * + * @param ibf the invertible bloom filter to decode + * @param side sign of the cell's count where the decoded element came from. + * A negative sign indicates that the element was recovered + * resides in an IBF that was previously subtracted from. + * @param ret_id the hash code of the decoded element, if successful + * @return GNUNET_YES if decoding an element was successful, + * GNUNET_NO if the IBF is empty, + * GNUNET_SYSERR if the decoding has failed + */ +int +ibf_decode (struct InvertibleBloomFilter *ibf, + int *ret_side, struct GNUNET_HashCode *ret_id) +{ + struct GNUNET_HashCode hash; + int i; + + GNUNET_assert (NULL != ibf); + + for (i = 0; i < ibf->size; i++) + { + if ((1 != ibf->count[i]) && (-1 != ibf->count[i])) + continue; + + GNUNET_CRYPTO_hash (&ibf->id_sum[i], sizeof (struct GNUNET_HashCode), &hash); + + if (0 != memcmp (&hash, &ibf->hash_sum[i], sizeof (struct GNUNET_HashCode))) + continue; + + if (NULL != ret_side) + *ret_side = ibf->count[i]; + if (NULL != ret_id) + *ret_id = ibf->id_sum[i]; + + /* insert on the opposite side, effectively removing the element */ + ibf_insert_on_side (ibf, &ibf->id_sum[i], -ibf->count[i]); + + return GNUNET_YES; + } + + if (GNUNET_YES == ibf_is_empty (ibf)) + return GNUNET_NO; + return GNUNET_SYSERR; +} + + + +/** + * Subtract ibf2 from ibf1, storing the result in ibf1. + * The two IBF's must have the same parameters size and hash_num. + * + * @param ibf1 IBF that is subtracted from + * @param ibf2 IBF that will be subtracted from ibf1 + */ +void +ibf_subtract (struct InvertibleBloomFilter *ibf1, struct InvertibleBloomFilter *ibf2) +{ + int i; + + GNUNET_assert (ibf1->size == ibf2->size); + GNUNET_assert (ibf1->hash_num == ibf2->hash_num); + GNUNET_assert (ibf1->salt == ibf2->salt); + + for (i = 0; i < ibf1->size; i++) + { + ibf1->count[i] -= ibf2->count[i]; + GNUNET_CRYPTO_hash_xor (&ibf1->id_sum[i], &ibf2->id_sum[i], + &ibf1->id_sum[i]); + GNUNET_CRYPTO_hash_xor (&ibf1->hash_sum[i], &ibf2->hash_sum[i], + &ibf1->hash_sum[i]); + } +} + +/** + * Create a copy of an IBF, the copy has to be destroyed properly. + * + * @param ibf the IBF to copy + */ +struct InvertibleBloomFilter * +ibf_dup (struct InvertibleBloomFilter *ibf) +{ + struct InvertibleBloomFilter *copy; + copy = GNUNET_malloc (sizeof *copy); + copy->hash_num = ibf->hash_num; + copy->salt = ibf->salt; + copy->size = ibf->size; + copy->hash_sum = GNUNET_memdup (ibf->hash_sum, ibf->size * sizeof (struct GNUNET_HashCode)); + copy->id_sum = GNUNET_memdup (ibf->id_sum, ibf->size * sizeof (struct GNUNET_HashCode)); + copy->count = GNUNET_memdup (ibf->count, ibf->size * sizeof (uint8_t)); + return copy; +} + +/** + * Destroy all resources associated with the invertible bloom filter. + * No more ibf_*-functions may be called on ibf after calling destroy. + * + * @param ibf the intertible bloom filter to destroy + */ +void +ibf_destroy (struct InvertibleBloomFilter *ibf) +{ + GNUNET_free (ibf->hash_sum); + GNUNET_free (ibf->id_sum); + GNUNET_free (ibf->count); + GNUNET_free (ibf); +} diff --git a/src/consensus/test_consensus.conf b/src/consensus/test_consensus.conf new file mode 100644 index 0000000..61c382f --- /dev/null +++ b/src/consensus/test_consensus.conf @@ -0,0 +1,26 @@ +[consensus] +AUTOSTART = YES +PORT = 2110 +HOSTNAME = localhost +HOME = $SERVICEHOME +BINARY = gnunet-service-consensus +#PREFIX = gdbserver :12345 +PREFIX = valgrind +ACCEPT_FROM = 127.0.0.1; +ACCEPT_FROM6 = ::1; +UNIXPATH = /tmp/gnunet-service-consensus.sock +UNIX_MATCH_UID = YES +UNIX_MATCH_GID = YES +OPTIONS = -L INFO + + +[transport] +OPTIONS = -LERROR + + +[arm] +DEFAULTSERVICES = core consensus + + +[testbed] +OVERLAY_TOPOLOGY = CLIQUE diff --git a/src/consensus/test_consensus_api.c b/src/consensus/test_consensus_api.c new file mode 100644 index 0000000..c79a622 --- /dev/null +++ b/src/consensus/test_consensus_api.c @@ -0,0 +1,124 @@ +/* + This file is part of GNUnet. + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @file consensus/test_consensus_api.c + * @brief testcase for consensus_api.c + */ +#include "platform.h" +#include "gnunet_util_lib.h" +#include "gnunet_consensus_service.h" +#include "gnunet_testing_lib.h" + + +static struct GNUNET_CONSENSUS_Handle *consensus; + +static struct GNUNET_HashCode session_id; + + +static int +conclude_done (void *cls, const struct GNUNET_CONSENSUS_Group *group) +{ + if (NULL == group) + { + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "conclude over\n"); + GNUNET_SCHEDULER_shutdown (); + return GNUNET_NO; + } + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "concluded\n"); + return GNUNET_YES; +} + +static int +on_new_element (void *cls, + struct GNUNET_CONSENSUS_Element *element) +{ + GNUNET_assert (0); + return GNUNET_YES; +} + +static void +insert_done (void *cls, int success) +{ + /* make sure cb is only called once */ + static int called = GNUNET_NO; + GNUNET_assert (GNUNET_NO == called); + called = GNUNET_YES; + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "insert done\n"); + GNUNET_CONSENSUS_conclude (consensus, GNUNET_TIME_UNIT_SECONDS, 0, &conclude_done, NULL); +} + + +/** + * Signature of the main function of a task. + * + * @param cls closure + * @param tc context information (why was this task triggered now) + */ +static void +on_shutdown (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + if (NULL != consensus) + { + GNUNET_CONSENSUS_destroy (consensus); + consensus = NULL; + } +} + + +static void +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) +{ + char *str = "foo"; + + struct GNUNET_CONSENSUS_Element el1 = {"foo", 4, 0}; + struct GNUNET_CONSENSUS_Element el2 = {"bar", 4, 0}; + + GNUNET_log_setup ("test_consensus_api", + "INFO", + NULL); + + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "testing consensus api\n"); + + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, &on_shutdown, NULL); + + GNUNET_CRYPTO_hash (str, strlen (str), &session_id); + consensus = GNUNET_CONSENSUS_create (cfg, 0, NULL, &session_id, on_new_element, &consensus); + GNUNET_assert (consensus != NULL); + + GNUNET_CONSENSUS_insert (consensus, &el1, NULL, &consensus); + GNUNET_CONSENSUS_insert (consensus, &el2, &insert_done, &consensus); +} + + +int +main (int argc, char **argv) +{ + int ret; + + ret = GNUNET_TESTING_peer_run ("test_consensus_api", + "test_consensus.conf", + &run, NULL); + return ret; +} + diff --git a/src/core/Makefile.am b/src/core/Makefile.am index e95cbcf..6d073da 100644 --- a/src/core/Makefile.am +++ b/src/core/Makefile.am @@ -2,6 +2,8 @@ INCLUDES = -I$(top_srcdir)/src/include pkgcfgdir= $(pkgdatadir)/config.d/ +libexecdir= $(pkglibdir)/libexec/ + pkgcfg_DATA = \ core.conf @@ -27,11 +29,13 @@ libgnunetcore_la_LIBADD = \ $(GN_LIBINTL) $(XLIB) libgnunetcore_la_LDFLAGS = \ $(GN_LIB_LDFLAGS) $(WINFLAGS) \ - -version-info 0:0:0 + -version-info 0:1:0 + +libexec_PROGRAMS = \ + gnunet-service-core bin_PROGRAMS = \ - gnunet-service-core \ gnunet-core gnunet_service_core_SOURCES = \ @@ -89,12 +93,14 @@ test_core_api_send_to_self_SOURCES = \ test_core_api_send_to_self.c test_core_api_send_to_self_LDADD = \ $(top_builddir)/src/core/libgnunetcore.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/transport/libgnunettransport.la \ $(top_builddir)/src/util/libgnunetutil.la test_core_api_start_only_SOURCES = \ test_core_api_start_only.c test_core_api_start_only_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/core/libgnunetcore.la \ $(top_builddir)/src/util/libgnunetutil.la diff --git a/src/core/Makefile.in b/src/core/Makefile.in index f181a54..c44ac57 100644 --- a/src/core/Makefile.in +++ b/src/core/Makefile.in @@ -1,9 +1,9 @@ -# Makefile.in generated by automake 1.11.1 from Makefile.am. +# Makefile.in generated by automake 1.11.6 from Makefile.am. # @configure_input@ # Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, -# 2003, 2004, 2005, 2006, 2007, 2008, 2009 Free Software Foundation, -# Inc. +# 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Free Software +# Foundation, Inc. # This Makefile.in is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. @@ -18,6 +18,23 @@ VPATH = @srcdir@ +am__make_dryrun = \ + { \ + am__dry=no; \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + echo 'am--echo: ; @echo "AM" OK' | $(MAKE) -f - 2>/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } pkgdatadir = $(datadir)/@PACKAGE@ pkgincludedir = $(includedir)/@PACKAGE@ pkglibdir = $(libdir)/@PACKAGE@ @@ -37,7 +54,8 @@ POST_UNINSTALL = : build_triplet = @build@ host_triplet = @host@ target_triplet = @target@ -bin_PROGRAMS = gnunet-service-core$(EXEEXT) gnunet-core$(EXEEXT) +libexec_PROGRAMS = gnunet-service-core$(EXEEXT) +bin_PROGRAMS = gnunet-core$(EXEEXT) check_PROGRAMS = test_core_api_start_only$(EXEEXT) \ test_core_api$(EXEEXT) test_core_api_reliability$(EXEEXT) \ test_core_quota_compliance_symmetric$(EXEEXT) \ @@ -50,14 +68,15 @@ DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in \ ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 am__aclocal_m4_deps = $(top_srcdir)/m4/absolute-header.m4 \ $(top_srcdir)/m4/align.m4 $(top_srcdir)/m4/argz.m4 \ - $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/iconv.m4 \ - $(top_srcdir)/m4/lib-ld.m4 $(top_srcdir)/m4/lib-link.m4 \ - $(top_srcdir)/m4/lib-prefix.m4 $(top_srcdir)/m4/libcurl.m4 \ - $(top_srcdir)/m4/libgcrypt.m4 $(top_srcdir)/m4/libtool.m4 \ - $(top_srcdir)/m4/libunistring.m4 $(top_srcdir)/m4/ltdl.m4 \ - $(top_srcdir)/m4/ltoptions.m4 $(top_srcdir)/m4/ltsugar.m4 \ - $(top_srcdir)/m4/ltversion.m4 $(top_srcdir)/m4/lt~obsolete.m4 \ - $(top_srcdir)/m4/nls.m4 $(top_srcdir)/m4/po.m4 \ + $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/glib-2.0.m4 \ + $(top_srcdir)/m4/iconv.m4 $(top_srcdir)/m4/lib-ld.m4 \ + $(top_srcdir)/m4/lib-link.m4 $(top_srcdir)/m4/lib-prefix.m4 \ + $(top_srcdir)/m4/libcurl.m4 $(top_srcdir)/m4/libgcrypt.m4 \ + $(top_srcdir)/m4/libtool.m4 $(top_srcdir)/m4/libunistring.m4 \ + $(top_srcdir)/m4/ltdl.m4 $(top_srcdir)/m4/ltoptions.m4 \ + $(top_srcdir)/m4/ltsugar.m4 $(top_srcdir)/m4/ltversion.m4 \ + $(top_srcdir)/m4/lt~obsolete.m4 $(top_srcdir)/m4/nls.m4 \ + $(top_srcdir)/m4/pkg.m4 $(top_srcdir)/m4/po.m4 \ $(top_srcdir)/m4/progtest.m4 $(top_srcdir)/acinclude.m4 \ $(top_srcdir)/configure.ac am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ @@ -87,8 +106,14 @@ am__nobase_list = $(am__nobase_strip_setup); \ am__base_list = \ sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \ sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g' +am__uninstall_files_from_dir = { \ + test -z "$$files" \ + || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \ + || { echo " ( cd '$$dir' && rm -f" $$files ")"; \ + $(am__cd) "$$dir" && rm -f $$files; }; \ + } am__installdirs = "$(DESTDIR)$(libdir)" "$(DESTDIR)$(bindir)" \ - "$(DESTDIR)$(pkgcfgdir)" + "$(DESTDIR)$(libexecdir)" "$(DESTDIR)$(pkgcfgdir)" LTLIBRARIES = $(lib_LTLIBRARIES) am__DEPENDENCIES_1 = libgnunetcore_la_DEPENDENCIES = \ @@ -97,14 +122,14 @@ libgnunetcore_la_DEPENDENCIES = \ am_libgnunetcore_la_OBJECTS = core_api.lo core_api_iterate_peers.lo \ core_api_is_connected.lo libgnunetcore_la_OBJECTS = $(am_libgnunetcore_la_OBJECTS) -AM_V_lt = $(am__v_lt_$(V)) -am__v_lt_ = $(am__v_lt_$(AM_DEFAULT_VERBOSITY)) +AM_V_lt = $(am__v_lt_@AM_V@) +am__v_lt_ = $(am__v_lt_@AM_DEFAULT_V@) am__v_lt_0 = --silent libgnunetcore_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ $(AM_CFLAGS) $(CFLAGS) $(libgnunetcore_la_LDFLAGS) $(LDFLAGS) \ -o $@ -PROGRAMS = $(bin_PROGRAMS) +PROGRAMS = $(bin_PROGRAMS) $(libexec_PROGRAMS) am_gnunet_core_OBJECTS = gnunet-core.$(OBJEXT) gnunet_core_OBJECTS = $(am_gnunet_core_OBJECTS) am_gnunet_service_core_OBJECTS = gnunet-service-core.$(OBJEXT) \ @@ -141,6 +166,7 @@ test_core_api_send_to_self_OBJECTS = \ $(am_test_core_api_send_to_self_OBJECTS) test_core_api_send_to_self_DEPENDENCIES = \ $(top_builddir)/src/core/libgnunetcore.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/transport/libgnunettransport.la \ $(top_builddir)/src/util/libgnunetutil.la am_test_core_api_start_only_OBJECTS = \ @@ -148,6 +174,7 @@ am_test_core_api_start_only_OBJECTS = \ test_core_api_start_only_OBJECTS = \ $(am_test_core_api_start_only_OBJECTS) test_core_api_start_only_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/core/libgnunetcore.la \ $(top_builddir)/src/util/libgnunetutil.la am_test_core_quota_compliance_asymmetric_recv_limited_OBJECTS = \ @@ -185,21 +212,21 @@ LTCOMPILE = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) \ $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) \ $(AM_CFLAGS) $(CFLAGS) -AM_V_CC = $(am__v_CC_$(V)) -am__v_CC_ = $(am__v_CC_$(AM_DEFAULT_VERBOSITY)) +AM_V_CC = $(am__v_CC_@AM_V@) +am__v_CC_ = $(am__v_CC_@AM_DEFAULT_V@) am__v_CC_0 = @echo " CC " $@; -AM_V_at = $(am__v_at_$(V)) -am__v_at_ = $(am__v_at_$(AM_DEFAULT_VERBOSITY)) +AM_V_at = $(am__v_at_@AM_V@) +am__v_at_ = $(am__v_at_@AM_DEFAULT_V@) am__v_at_0 = @ CCLD = $(CC) LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ $(AM_LDFLAGS) $(LDFLAGS) -o $@ -AM_V_CCLD = $(am__v_CCLD_$(V)) -am__v_CCLD_ = $(am__v_CCLD_$(AM_DEFAULT_VERBOSITY)) +AM_V_CCLD = $(am__v_CCLD_@AM_V@) +am__v_CCLD_ = $(am__v_CCLD_@AM_DEFAULT_V@) am__v_CCLD_0 = @echo " CCLD " $@; -AM_V_GEN = $(am__v_GEN_$(V)) -am__v_GEN_ = $(am__v_GEN_$(AM_DEFAULT_VERBOSITY)) +AM_V_GEN = $(am__v_GEN_@AM_V@) +am__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@) am__v_GEN_0 = @echo " GEN " $@; SOURCES = $(libgnunetcore_la_SOURCES) $(gnunet_core_SOURCES) \ $(gnunet_service_core_SOURCES) $(test_core_api_SOURCES) \ @@ -217,6 +244,11 @@ DIST_SOURCES = $(libgnunetcore_la_SOURCES) $(gnunet_core_SOURCES) \ $(test_core_quota_compliance_asymmetric_recv_limited_SOURCES) \ $(test_core_quota_compliance_asymmetric_send_limited_SOURCES) \ $(test_core_quota_compliance_symmetric_SOURCES) +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac DATA = $(pkgcfg_DATA) ETAGS = etags CTAGS = ctags @@ -258,6 +290,10 @@ EXEEXT = @EXEEXT@ EXT_LIBS = @EXT_LIBS@ EXT_LIB_PATH = @EXT_LIB_PATH@ FGREP = @FGREP@ +GLIB_CFLAGS = @GLIB_CFLAGS@ +GLIB_GENMARSHAL = @GLIB_GENMARSHAL@ +GLIB_LIBS = @GLIB_LIBS@ +GLIB_MKENUMS = @GLIB_MKENUMS@ GMSGFMT = @GMSGFMT@ GMSGFMT_015 = @GMSGFMT_015@ GNUNETDNS_GROUP = @GNUNETDNS_GROUP@ @@ -268,6 +304,7 @@ GN_LIBINTL = @GN_LIBINTL@ GN_LIB_LDFLAGS = @GN_LIB_LDFLAGS@ GN_PLUGIN_LDFLAGS = @GN_PLUGIN_LDFLAGS@ GN_USER_HOME_DIR = @GN_USER_HOME_DIR@ +GOBJECT_QUERY = @GOBJECT_QUERY@ GREP = @GREP@ HAVE_LIBUNISTRING = @HAVE_LIBUNISTRING@ INCLTDL = @INCLTDL@ @@ -290,6 +327,8 @@ LIBCURL_CPPFLAGS = @LIBCURL_CPPFLAGS@ LIBGCRYPT_CFLAGS = @LIBGCRYPT_CFLAGS@ LIBGCRYPT_CONFIG = @LIBGCRYPT_CONFIG@ LIBGCRYPT_LIBS = @LIBGCRYPT_LIBS@ +LIBGTOP_CFLAGS = @LIBGTOP_CFLAGS@ +LIBGTOP_LIBS = @LIBGTOP_LIBS@ LIBICONV = @LIBICONV@ LIBINTL = @LIBINTL@ LIBLTDL = @LIBLTDL@ @@ -311,6 +350,7 @@ LT_CONFIG_H = @LT_CONFIG_H@ LT_DLLOADERS = @LT_DLLOADERS@ LT_DLPREOPEN = @LT_DLPREOPEN@ MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ MKDIR_P = @MKDIR_P@ MONKEYPREFIX = @MONKEYPREFIX@ MSGFMT = @MSGFMT@ @@ -320,6 +360,7 @@ MYSQL_CPPFLAGS = @MYSQL_CPPFLAGS@ MYSQL_LDFLAGS = @MYSQL_LDFLAGS@ NM = @NM@ NMEDIT = @NMEDIT@ +NSS_DIR = @NSS_DIR@ OBJC = @OBJC@ OBJCDEPMODE = @OBJCDEPMODE@ OBJCFLAGS = @OBJCFLAGS@ @@ -335,6 +376,7 @@ PACKAGE_TARNAME = @PACKAGE_TARNAME@ PACKAGE_URL = @PACKAGE_URL@ PACKAGE_VERSION = @PACKAGE_VERSION@ PATH_SEPARATOR = @PATH_SEPARATOR@ +PKG_CONFIG = @PKG_CONFIG@ POSTGRES_CPPFLAGS = @POSTGRES_CPPFLAGS@ POSTGRES_LDFLAGS = @POSTGRES_LDFLAGS@ POSUB = @POSUB@ @@ -366,6 +408,7 @@ abs_builddir = @abs_builddir@ abs_srcdir = @abs_srcdir@ abs_top_builddir = @abs_top_builddir@ abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ ac_ct_CC = @ac_ct_CC@ ac_ct_CXX = @ac_ct_CXX@ ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ @@ -388,6 +431,7 @@ datarootdir = @datarootdir@ docdir = @docdir@ dvidir = @dvidir@ exec_prefix = @exec_prefix@ +gitcommand = @gitcommand@ host = @host@ host_alias = @host_alias@ host_cpu = @host_cpu@ @@ -398,10 +442,9 @@ includedir = @includedir@ infodir = @infodir@ install_sh = @install_sh@ libdir = @libdir@ -libexecdir = @libexecdir@ +libexecdir = $(pkglibdir)/libexec/ localedir = @localedir@ localstatedir = @localstatedir@ -lt_ECHO = @lt_ECHO@ ltdl_LIBOBJS = @ltdl_LIBOBJS@ ltdl_LTLIBOBJS = @ltdl_LTLIBOBJS@ mandir = @mandir@ @@ -419,6 +462,7 @@ sbindir = @sbindir@ sharedstatedir = @sharedstatedir@ srcdir = @srcdir@ subdirs = @subdirs@ +svnversioncommand = @svnversioncommand@ sys_symbol_underscore = @sys_symbol_underscore@ sysconfdir = @sysconfdir@ target = @target@ @@ -451,7 +495,7 @@ libgnunetcore_la_LIBADD = \ libgnunetcore_la_LDFLAGS = \ $(GN_LIB_LDFLAGS) $(WINFLAGS) \ - -version-info 0:0:0 + -version-info 0:1:0 gnunet_service_core_SOURCES = \ gnunet-service-core.c gnunet-service-core.h \ @@ -501,6 +545,7 @@ test_core_api_send_to_self_SOURCES = \ test_core_api_send_to_self_LDADD = \ $(top_builddir)/src/core/libgnunetcore.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/transport/libgnunettransport.la \ $(top_builddir)/src/util/libgnunetutil.la @@ -508,6 +553,7 @@ test_core_api_start_only_SOURCES = \ test_core_api_start_only.c test_core_api_start_only_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/core/libgnunetcore.la \ $(top_builddir)/src/util/libgnunetutil.la @@ -589,7 +635,6 @@ core.conf: $(top_builddir)/config.status $(srcdir)/core.conf.in cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ install-libLTLIBRARIES: $(lib_LTLIBRARIES) @$(NORMAL_INSTALL) - test -z "$(libdir)" || $(MKDIR_P) "$(DESTDIR)$(libdir)" @list='$(lib_LTLIBRARIES)'; test -n "$(libdir)" || list=; \ list2=; for p in $$list; do \ if test -f $$p; then \ @@ -597,6 +642,8 @@ install-libLTLIBRARIES: $(lib_LTLIBRARIES) else :; fi; \ done; \ test -z "$$list2" || { \ + echo " $(MKDIR_P) '$(DESTDIR)$(libdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libdir)" || exit 1; \ echo " $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 '$(DESTDIR)$(libdir)'"; \ $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 "$(DESTDIR)$(libdir)"; \ } @@ -618,12 +665,15 @@ clean-libLTLIBRARIES: echo "rm -f \"$${dir}/so_locations\""; \ rm -f "$${dir}/so_locations"; \ done -libgnunetcore.la: $(libgnunetcore_la_OBJECTS) $(libgnunetcore_la_DEPENDENCIES) +libgnunetcore.la: $(libgnunetcore_la_OBJECTS) $(libgnunetcore_la_DEPENDENCIES) $(EXTRA_libgnunetcore_la_DEPENDENCIES) $(AM_V_CCLD)$(libgnunetcore_la_LINK) -rpath $(libdir) $(libgnunetcore_la_OBJECTS) $(libgnunetcore_la_LIBADD) $(LIBS) install-binPROGRAMS: $(bin_PROGRAMS) @$(NORMAL_INSTALL) - test -z "$(bindir)" || $(MKDIR_P) "$(DESTDIR)$(bindir)" @list='$(bin_PROGRAMS)'; test -n "$(bindir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(bindir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(bindir)" || exit 1; \ + fi; \ for p in $$list; do echo "$$p $$p"; done | \ sed 's/$(EXEEXT)$$//' | \ while read p p1; do if test -f $$p || test -f $$p1; \ @@ -672,31 +722,77 @@ clean-checkPROGRAMS: list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ echo " rm -f" $$list; \ rm -f $$list -gnunet-core$(EXEEXT): $(gnunet_core_OBJECTS) $(gnunet_core_DEPENDENCIES) +install-libexecPROGRAMS: $(libexec_PROGRAMS) + @$(NORMAL_INSTALL) + @list='$(libexec_PROGRAMS)'; test -n "$(libexecdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(libexecdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libexecdir)" || exit 1; \ + fi; \ + for p in $$list; do echo "$$p $$p"; done | \ + sed 's/$(EXEEXT)$$//' | \ + while read p p1; do if test -f $$p || test -f $$p1; \ + then echo "$$p"; echo "$$p"; else :; fi; \ + done | \ + sed -e 'p;s,.*/,,;n;h' -e 's|.*|.|' \ + -e 'p;x;s,.*/,,;s/$(EXEEXT)$$//;$(transform);s/$$/$(EXEEXT)/' | \ + sed 'N;N;N;s,\n, ,g' | \ + $(AWK) 'BEGIN { files["."] = ""; dirs["."] = 1 } \ + { d=$$3; if (dirs[d] != 1) { print "d", d; dirs[d] = 1 } \ + if ($$2 == $$4) files[d] = files[d] " " $$1; \ + else { print "f", $$3 "/" $$4, $$1; } } \ + END { for (d in files) print "f", d, files[d] }' | \ + while read type dir files; do \ + if test "$$dir" = .; then dir=; else dir=/$$dir; fi; \ + test -z "$$files" || { \ + echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files '$(DESTDIR)$(libexecdir)$$dir'"; \ + $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files "$(DESTDIR)$(libexecdir)$$dir" || exit $$?; \ + } \ + ; done + +uninstall-libexecPROGRAMS: + @$(NORMAL_UNINSTALL) + @list='$(libexec_PROGRAMS)'; test -n "$(libexecdir)" || list=; \ + files=`for p in $$list; do echo "$$p"; done | \ + sed -e 'h;s,^.*/,,;s/$(EXEEXT)$$//;$(transform)' \ + -e 's/$$/$(EXEEXT)/' `; \ + test -n "$$list" || exit 0; \ + echo " ( cd '$(DESTDIR)$(libexecdir)' && rm -f" $$files ")"; \ + cd "$(DESTDIR)$(libexecdir)" && rm -f $$files + +clean-libexecPROGRAMS: + @list='$(libexec_PROGRAMS)'; test -n "$$list" || exit 0; \ + echo " rm -f" $$list; \ + rm -f $$list || exit $$?; \ + test -n "$(EXEEXT)" || exit 0; \ + list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ + echo " rm -f" $$list; \ + rm -f $$list +gnunet-core$(EXEEXT): $(gnunet_core_OBJECTS) $(gnunet_core_DEPENDENCIES) $(EXTRA_gnunet_core_DEPENDENCIES) @rm -f gnunet-core$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_core_OBJECTS) $(gnunet_core_LDADD) $(LIBS) -gnunet-service-core$(EXEEXT): $(gnunet_service_core_OBJECTS) $(gnunet_service_core_DEPENDENCIES) +gnunet-service-core$(EXEEXT): $(gnunet_service_core_OBJECTS) $(gnunet_service_core_DEPENDENCIES) $(EXTRA_gnunet_service_core_DEPENDENCIES) @rm -f gnunet-service-core$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_service_core_OBJECTS) $(gnunet_service_core_LDADD) $(LIBS) -test_core_api$(EXEEXT): $(test_core_api_OBJECTS) $(test_core_api_DEPENDENCIES) +test_core_api$(EXEEXT): $(test_core_api_OBJECTS) $(test_core_api_DEPENDENCIES) $(EXTRA_test_core_api_DEPENDENCIES) @rm -f test_core_api$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_core_api_OBJECTS) $(test_core_api_LDADD) $(LIBS) -test_core_api_reliability$(EXEEXT): $(test_core_api_reliability_OBJECTS) $(test_core_api_reliability_DEPENDENCIES) +test_core_api_reliability$(EXEEXT): $(test_core_api_reliability_OBJECTS) $(test_core_api_reliability_DEPENDENCIES) $(EXTRA_test_core_api_reliability_DEPENDENCIES) @rm -f test_core_api_reliability$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_core_api_reliability_OBJECTS) $(test_core_api_reliability_LDADD) $(LIBS) -test_core_api_send_to_self$(EXEEXT): $(test_core_api_send_to_self_OBJECTS) $(test_core_api_send_to_self_DEPENDENCIES) +test_core_api_send_to_self$(EXEEXT): $(test_core_api_send_to_self_OBJECTS) $(test_core_api_send_to_self_DEPENDENCIES) $(EXTRA_test_core_api_send_to_self_DEPENDENCIES) @rm -f test_core_api_send_to_self$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_core_api_send_to_self_OBJECTS) $(test_core_api_send_to_self_LDADD) $(LIBS) -test_core_api_start_only$(EXEEXT): $(test_core_api_start_only_OBJECTS) $(test_core_api_start_only_DEPENDENCIES) +test_core_api_start_only$(EXEEXT): $(test_core_api_start_only_OBJECTS) $(test_core_api_start_only_DEPENDENCIES) $(EXTRA_test_core_api_start_only_DEPENDENCIES) @rm -f test_core_api_start_only$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_core_api_start_only_OBJECTS) $(test_core_api_start_only_LDADD) $(LIBS) -test_core_quota_compliance_asymmetric_recv_limited$(EXEEXT): $(test_core_quota_compliance_asymmetric_recv_limited_OBJECTS) $(test_core_quota_compliance_asymmetric_recv_limited_DEPENDENCIES) +test_core_quota_compliance_asymmetric_recv_limited$(EXEEXT): $(test_core_quota_compliance_asymmetric_recv_limited_OBJECTS) $(test_core_quota_compliance_asymmetric_recv_limited_DEPENDENCIES) $(EXTRA_test_core_quota_compliance_asymmetric_recv_limited_DEPENDENCIES) @rm -f test_core_quota_compliance_asymmetric_recv_limited$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_core_quota_compliance_asymmetric_recv_limited_OBJECTS) $(test_core_quota_compliance_asymmetric_recv_limited_LDADD) $(LIBS) -test_core_quota_compliance_asymmetric_send_limited$(EXEEXT): $(test_core_quota_compliance_asymmetric_send_limited_OBJECTS) $(test_core_quota_compliance_asymmetric_send_limited_DEPENDENCIES) +test_core_quota_compliance_asymmetric_send_limited$(EXEEXT): $(test_core_quota_compliance_asymmetric_send_limited_OBJECTS) $(test_core_quota_compliance_asymmetric_send_limited_DEPENDENCIES) $(EXTRA_test_core_quota_compliance_asymmetric_send_limited_DEPENDENCIES) @rm -f test_core_quota_compliance_asymmetric_send_limited$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_core_quota_compliance_asymmetric_send_limited_OBJECTS) $(test_core_quota_compliance_asymmetric_send_limited_LDADD) $(LIBS) -test_core_quota_compliance_symmetric$(EXEEXT): $(test_core_quota_compliance_symmetric_OBJECTS) $(test_core_quota_compliance_symmetric_DEPENDENCIES) +test_core_quota_compliance_symmetric$(EXEEXT): $(test_core_quota_compliance_symmetric_OBJECTS) $(test_core_quota_compliance_symmetric_DEPENDENCIES) $(EXTRA_test_core_quota_compliance_symmetric_DEPENDENCIES) @rm -f test_core_quota_compliance_symmetric$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_core_quota_compliance_symmetric_OBJECTS) $(test_core_quota_compliance_symmetric_LDADD) $(LIBS) @@ -725,26 +821,23 @@ distclean-compile: .c.o: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c $< .c.obj: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'` @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c `$(CYGPATH_W) '$<'` +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c `$(CYGPATH_W) '$<'` .c.lo: @am__fastdepCC_TRUE@ $(AM_V_CC)$(LTCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LTCOMPILE) -c -o $@ $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LTCOMPILE) -c -o $@ $< mostlyclean-libtool: -rm -f *.lo @@ -753,8 +846,11 @@ clean-libtool: -rm -rf .libs _libs install-pkgcfgDATA: $(pkgcfg_DATA) @$(NORMAL_INSTALL) - test -z "$(pkgcfgdir)" || $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" @list='$(pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(pkgcfgdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" || exit 1; \ + fi; \ for p in $$list; do \ if test -f "$$p"; then d=; else d="$(srcdir)/"; fi; \ echo "$$d$$p"; \ @@ -768,9 +864,7 @@ uninstall-pkgcfgDATA: @$(NORMAL_UNINSTALL) @list='$(pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ files=`for p in $$list; do echo $$p; done | sed -e 's|^.*/||'`; \ - test -n "$$files" || exit 0; \ - echo " ( cd '$(DESTDIR)$(pkgcfgdir)' && rm -f" $$files ")"; \ - cd "$(DESTDIR)$(pkgcfgdir)" && rm -f $$files + dir='$(DESTDIR)$(pkgcfgdir)'; $(am__uninstall_files_from_dir) ID: $(HEADERS) $(SOURCES) $(LISP) $(TAGS_FILES) list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ @@ -905,14 +999,15 @@ check-TESTS: $(TESTS) fi; \ dashes=`echo "$$dashes" | sed s/./=/g`; \ if test "$$failed" -eq 0; then \ - echo "$$grn$$dashes"; \ + col="$$grn"; \ else \ - echo "$$red$$dashes"; \ + col="$$red"; \ fi; \ - echo "$$banner"; \ - test -z "$$skipped" || echo "$$skipped"; \ - test -z "$$report" || echo "$$report"; \ - echo "$$dashes$$std"; \ + echo "$${col}$$dashes$${std}"; \ + echo "$${col}$$banner$${std}"; \ + test -z "$$skipped" || echo "$${col}$$skipped$${std}"; \ + test -z "$$report" || echo "$${col}$$report$${std}"; \ + echo "$${col}$$dashes$${std}"; \ test "$$failed" -eq 0; \ else :; fi @@ -954,7 +1049,7 @@ all-am: Makefile $(LTLIBRARIES) $(PROGRAMS) $(DATA) install-binPROGRAMS: install-libLTLIBRARIES installdirs: - for dir in "$(DESTDIR)$(libdir)" "$(DESTDIR)$(bindir)" "$(DESTDIR)$(pkgcfgdir)"; do \ + for dir in "$(DESTDIR)$(libdir)" "$(DESTDIR)$(bindir)" "$(DESTDIR)$(libexecdir)" "$(DESTDIR)$(pkgcfgdir)"; do \ test -z "$$dir" || $(MKDIR_P) "$$dir"; \ done install: install-am @@ -967,10 +1062,15 @@ install-am: all-am installcheck: installcheck-am install-strip: - $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ - install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ - `test -z '$(STRIP)' || \ - echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi mostlyclean-generic: clean-generic: @@ -985,7 +1085,8 @@ maintainer-clean-generic: clean: clean-am clean-am: clean-binPROGRAMS clean-checkPROGRAMS clean-generic \ - clean-libLTLIBRARIES clean-libtool mostlyclean-am + clean-libLTLIBRARIES clean-libexecPROGRAMS clean-libtool \ + mostlyclean-am distclean: distclean-am -rm -rf ./$(DEPDIR) @@ -1011,7 +1112,8 @@ install-dvi: install-dvi-am install-dvi-am: -install-exec-am: install-binPROGRAMS install-libLTLIBRARIES +install-exec-am: install-binPROGRAMS install-libLTLIBRARIES \ + install-libexecPROGRAMS install-html: install-html-am @@ -1052,25 +1154,26 @@ ps: ps-am ps-am: uninstall-am: uninstall-binPROGRAMS uninstall-libLTLIBRARIES \ - uninstall-pkgcfgDATA + uninstall-libexecPROGRAMS uninstall-pkgcfgDATA .MAKE: check-am install-am install-strip .PHONY: CTAGS GTAGS all all-am check check-TESTS check-am clean \ clean-binPROGRAMS clean-checkPROGRAMS clean-generic \ - clean-libLTLIBRARIES clean-libtool ctags distclean \ - distclean-compile distclean-generic distclean-libtool \ - distclean-tags distdir dvi dvi-am html html-am info info-am \ - install install-am install-binPROGRAMS install-data \ - install-data-am install-dvi install-dvi-am install-exec \ - install-exec-am install-html install-html-am install-info \ - install-info-am install-libLTLIBRARIES install-man install-pdf \ - install-pdf-am install-pkgcfgDATA install-ps install-ps-am \ - install-strip installcheck installcheck-am installdirs \ - maintainer-clean maintainer-clean-generic mostlyclean \ - mostlyclean-compile mostlyclean-generic mostlyclean-libtool \ - pdf pdf-am ps ps-am tags uninstall uninstall-am \ - uninstall-binPROGRAMS uninstall-libLTLIBRARIES \ + clean-libLTLIBRARIES clean-libexecPROGRAMS clean-libtool ctags \ + distclean distclean-compile distclean-generic \ + distclean-libtool distclean-tags distdir dvi dvi-am html \ + html-am info info-am install install-am install-binPROGRAMS \ + install-data install-data-am install-dvi install-dvi-am \ + install-exec install-exec-am install-html install-html-am \ + install-info install-info-am install-libLTLIBRARIES \ + install-libexecPROGRAMS install-man install-pdf install-pdf-am \ + install-pkgcfgDATA install-ps install-ps-am install-strip \ + installcheck installcheck-am installdirs maintainer-clean \ + maintainer-clean-generic mostlyclean mostlyclean-compile \ + mostlyclean-generic mostlyclean-libtool pdf pdf-am ps ps-am \ + tags uninstall uninstall-am uninstall-binPROGRAMS \ + uninstall-libLTLIBRARIES uninstall-libexecPROGRAMS \ uninstall-pkgcfgDATA diff --git a/src/core/core.conf.in b/src/core/core.conf.in index 61ac84e..ad39a8a 100644 --- a/src/core/core.conf.in +++ b/src/core/core.conf.in @@ -3,7 +3,6 @@ AUTOSTART = YES @JAVAPORT@PORT = 2092 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-core ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -11,7 +10,6 @@ UNIXPATH = /tmp/gnunet-service-core.sock UNIX_MATCH_UID = YES UNIX_MATCH_GID = YES # DISABLE_SOCKET_FORWARDING = NO -# DEBUG = YES # USERNAME = # MAXBUF = # TIMEOUT = diff --git a/src/core/core.h b/src/core/core.h index 03e328c..9b1802f 100644 --- a/src/core/core.h +++ b/src/core/core.h @@ -257,9 +257,9 @@ struct SendMessageRequest struct GNUNET_PeerIdentity peer; /** - * How large is the client's message queue for this peer? + * Always zero. */ - uint32_t queue_size GNUNET_PACKED; + uint32_t reserved GNUNET_PACKED; /** * How large is the message? diff --git a/src/core/core_api.c b/src/core/core_api.c index 526dc9f..2b1291d 100644 --- a/src/core/core_api.c +++ b/src/core/core_api.c @@ -31,6 +31,65 @@ #define LOG(kind,...) GNUNET_log_from (kind, "core-api",__VA_ARGS__) + +/** + * Handle for a transmission request. + */ +struct GNUNET_CORE_TransmitHandle +{ + + /** + * Corresponding peer record. + */ + struct PeerRecord *peer; + + /** + * Corresponding SEND_REQUEST message. Only non-NULL + * while SEND_REQUEST message is pending. + */ + struct ControlMessage *cm; + + /** + * Function that will be called to get the actual request + * (once we are ready to transmit this request to the core). + * The function will be called with a NULL buffer to signal + * timeout. + */ + GNUNET_CONNECTION_TransmitReadyNotify get_message; + + /** + * Closure for get_message. + */ + void *get_message_cls; + + /** + * Timeout for this handle. + */ + struct GNUNET_TIME_Absolute timeout; + + /** + * How important is this message? + */ + uint32_t priority; + + /** + * Size of this request. + */ + uint16_t msize; + + /** + * Send message request ID for this request. + */ + uint16_t smr_id; + + /** + * Is corking allowed? + */ + int cork; + +}; + + /** * Information we track for each peer. */ @@ -62,16 +121,10 @@ struct PeerRecord struct GNUNET_CORE_Handle *ch; /** - * Head of doubly-linked list of pending requests. - * Requests are sorted by deadline *except* for HEAD, - * which is only modified upon transmission to core. - */ - struct GNUNET_CORE_TransmitHandle *pending_head; - - /** - * Tail of doubly-linked list of pending requests. + * Pending request, if any. 'th->peer' is set to NULL if the + * request is not active. */ - struct GNUNET_CORE_TransmitHandle *pending_tail; + struct GNUNET_CORE_TransmitHandle th; /** * ID of timeout task for the 'pending_head' handle @@ -84,11 +137,6 @@ struct PeerRecord */ GNUNET_SCHEDULER_TaskIdentifier ntr_task; - /** - * Current size of the queue of pending requests. - */ - unsigned int queue_size; - /** * SendMessageRequest ID generator for this peer. */ @@ -246,11 +294,6 @@ struct GNUNET_CORE_Handle */ struct GNUNET_TIME_Relative retry_backoff; - /** - * Number of messages we are allowed to queue per target. - */ - unsigned int queue_size; - /** * Number of entries in the handlers array. */ @@ -277,74 +320,6 @@ struct GNUNET_CORE_Handle }; -/** - * Handle for a transmission request. - */ -struct GNUNET_CORE_TransmitHandle -{ - - /** - * We keep active transmit handles in a doubly-linked list. - */ - struct GNUNET_CORE_TransmitHandle *next; - - /** - * We keep active transmit handles in a doubly-linked list. - */ - struct GNUNET_CORE_TransmitHandle *prev; - - /** - * Corresponding peer record. - */ - struct PeerRecord *peer; - - /** - * Corresponding SEND_REQUEST message. Only non-NULL - * while SEND_REQUEST message is pending. - */ - struct ControlMessage *cm; - - /** - * Function that will be called to get the actual request - * (once we are ready to transmit this request to the core). - * The function will be called with a NULL buffer to signal - * timeout. - */ - GNUNET_CONNECTION_TransmitReadyNotify get_message; - - /** - * Closure for get_message. - */ - void *get_message_cls; - - /** - * Timeout for this handle. - */ - struct GNUNET_TIME_Absolute timeout; - - /** - * How important is this message? - */ - uint32_t priority; - - /** - * Size of this request. - */ - uint16_t msize; - - /** - * Send message request ID for this request. - */ - uint16_t smr_id; - - /** - * Is corking allowed? - */ - int cork; - -}; - - /** * Our current client connection went down. Clean it up * and try to reconnect! @@ -382,47 +357,42 @@ reconnect_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) * @return GNUNET_YES (continue) */ static int -disconnect_and_free_peer_entry (void *cls, const GNUNET_HashCode * key, +disconnect_and_free_peer_entry (void *cls, const struct GNUNET_HashCode * key, void *value) { struct GNUNET_CORE_Handle *h = cls; struct GNUNET_CORE_TransmitHandle *th; struct PeerRecord *pr = value; - if (pr->timeout_task != GNUNET_SCHEDULER_NO_TASK) + if (GNUNET_SCHEDULER_NO_TASK != pr->timeout_task) { GNUNET_SCHEDULER_cancel (pr->timeout_task); pr->timeout_task = GNUNET_SCHEDULER_NO_TASK; } - if (pr->ntr_task != GNUNET_SCHEDULER_NO_TASK) + if (GNUNET_SCHEDULER_NO_TASK != pr->ntr_task) { GNUNET_SCHEDULER_cancel (pr->ntr_task); pr->ntr_task = GNUNET_SCHEDULER_NO_TASK; } - if ((pr->prev != NULL) || (pr->next != NULL) || (h->ready_peer_head == pr)) + if ((NULL != pr->prev) || (NULL != pr->next) || (h->ready_peer_head == pr)) GNUNET_CONTAINER_DLL_remove (h->ready_peer_head, h->ready_peer_tail, pr); - if (h->disconnects != NULL) + if (NULL != h->disconnects) h->disconnects (h->cls, &pr->peer); /* all requests should have been cancelled, clean up anyway, just in case */ - GNUNET_break (pr->queue_size == 0); - while (NULL != (th = pr->pending_head)) + th = &pr->th; + if (NULL != th->peer) { GNUNET_break (0); - GNUNET_CONTAINER_DLL_remove (pr->pending_head, pr->pending_tail, th); - pr->queue_size--; - if (th->cm != NULL) + th->peer = NULL; + if (NULL != th->cm) th->cm->th = NULL; - GNUNET_free (th); } /* done with 'voluntary' cleanups, now on to normal freeing */ GNUNET_assert (GNUNET_YES == GNUNET_CONTAINER_multihashmap_remove (h->peers, key, pr)); - GNUNET_assert (pr->pending_head == NULL); - GNUNET_assert (pr->pending_tail == NULL); GNUNET_assert (pr->ch == h); - GNUNET_assert (pr->queue_size == 0); - GNUNET_assert (pr->timeout_task == GNUNET_SCHEDULER_NO_TASK); - GNUNET_assert (pr->ntr_task == GNUNET_SCHEDULER_NO_TASK); + GNUNET_assert (GNUNET_SCHEDULER_NO_TASK == pr->timeout_task); + GNUNET_assert (GNUNET_SCHEDULER_NO_TASK == pr->ntr_task); GNUNET_free (pr); return GNUNET_YES; } @@ -440,13 +410,13 @@ reconnect_later (struct GNUNET_CORE_Handle *h) struct ControlMessage *cm; struct PeerRecord *pr; - GNUNET_assert (h->reconnect_task == GNUNET_SCHEDULER_NO_TASK); + GNUNET_assert (GNUNET_SCHEDULER_NO_TASK == h->reconnect_task); if (NULL != h->cth) { GNUNET_CLIENT_notify_transmit_ready_cancel (h->cth); h->cth = NULL; } - if (h->client != NULL) + if (NULL != h->client) { GNUNET_CLIENT_disconnect (h->client); h->client = NULL; @@ -459,9 +429,9 @@ reconnect_later (struct GNUNET_CORE_Handle *h) { GNUNET_CONTAINER_DLL_remove (h->control_pending_head, h->control_pending_tail, cm); - if (cm->th != NULL) + if (NULL != cm->th) cm->th->cm = NULL; - if (cm->cont != NULL) + if (NULL != cm->cont) cm->cont (cm->cont_cls, GNUNET_NO); GNUNET_free (cm); } @@ -470,9 +440,7 @@ reconnect_later (struct GNUNET_CORE_Handle *h) while (NULL != (pr = h->ready_peer_head)) GNUNET_CONTAINER_DLL_remove (h->ready_peer_head, h->ready_peer_tail, pr); GNUNET_assert (h->control_pending_head == NULL); - h->retry_backoff = - GNUNET_TIME_relative_min (GNUNET_TIME_UNIT_SECONDS, h->retry_backoff); - h->retry_backoff = GNUNET_TIME_relative_multiply (h->retry_backoff, 2); + h->retry_backoff = GNUNET_TIME_STD_BACKOFF (h->retry_backoff); } @@ -517,7 +485,8 @@ request_next_transmission (struct PeerRecord *pr) GNUNET_SCHEDULER_cancel (pr->timeout_task); pr->timeout_task = GNUNET_SCHEDULER_NO_TASK; } - if (NULL == (th = pr->pending_head)) + th = &pr->th; + if (NULL == th->peer) { trigger_next_request (h, GNUNET_NO); return; @@ -539,7 +508,7 @@ request_next_transmission (struct PeerRecord *pr) smr->priority = htonl (th->priority); smr->deadline = GNUNET_TIME_absolute_hton (th->timeout); smr->peer = pr->peer; - smr->queue_size = htonl (pr->queue_size); + smr->reserved = htonl (0); smr->size = htons (th->msize); smr->smr_id = htons (th->smr_id = pr->smr_id_gen++); GNUNET_CONTAINER_DLL_insert_tail (h->control_pending_head, @@ -566,10 +535,14 @@ transmission_timeout (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) struct GNUNET_CORE_TransmitHandle *th; pr->timeout_task = GNUNET_SCHEDULER_NO_TASK; - th = pr->pending_head; - GNUNET_CONTAINER_DLL_remove (pr->pending_head, pr->pending_tail, th); - pr->queue_size--; - if ((pr->prev != NULL) || (pr->next != NULL) || (pr == h->ready_peer_head)) + if (GNUNET_SCHEDULER_NO_TASK != pr->ntr_task) + { + GNUNET_SCHEDULER_cancel (pr->ntr_task); + pr->ntr_task = GNUNET_SCHEDULER_NO_TASK; + } + th = &pr->th; + th->peer = NULL; + if ((NULL != pr->prev) || (NULL != pr->next) || (pr == h->ready_peer_head)) { /* the request that was 'approved' by core was * canceled before it could be transmitted; remove @@ -584,10 +557,11 @@ transmission_timeout (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) GNUNET_free (th->cm); } LOG (GNUNET_ERROR_TYPE_DEBUG, - "Signalling timeout of request for transmission to CORE service\n"); - request_next_transmission (pr); + "Signalling timeout of request for transmission to peer `%s' via CORE\n", + GNUNET_i2s (&pr->peer)); + trigger_next_request (h, GNUNET_NO); + GNUNET_assert (0 == th->get_message (th->get_message_cls, 0, NULL)); - GNUNET_free (th); } @@ -613,7 +587,7 @@ transmit_message (void *cls, size_t size, void *buf) GNUNET_assert (h->reconnect_task == GNUNET_SCHEDULER_NO_TASK); h->cth = NULL; - if (buf == NULL) + if (NULL == buf) { LOG (GNUNET_ERROR_TYPE_DEBUG, "Transmission failed, initiating reconnect\n"); @@ -636,7 +610,7 @@ transmit_message (void *cls, size_t size, void *buf) memcpy (buf, hdr, msize); GNUNET_CONTAINER_DLL_remove (h->control_pending_head, h->control_pending_tail, cm); - if (cm->th != NULL) + if (NULL != cm->th) cm->th->cm = NULL; if (NULL != cm->cont) cm->cont (cm->cont_cls, GNUNET_OK); @@ -645,67 +619,63 @@ transmit_message (void *cls, size_t size, void *buf) return msize; } /* now check for 'ready' P2P messages */ - if (NULL != (pr = h->ready_peer_head)) + if (NULL == (pr = h->ready_peer_head)) + return 0; + GNUNET_assert (NULL != pr->th.peer); + th = &pr->th; + if (size < th->msize + sizeof (struct SendMessage)) + { + trigger_next_request (h, GNUNET_NO); + return 0; + } + GNUNET_CONTAINER_DLL_remove (h->ready_peer_head, h->ready_peer_tail, pr); + th->peer = NULL; + if (GNUNET_SCHEDULER_NO_TASK != pr->timeout_task) + { + GNUNET_SCHEDULER_cancel (pr->timeout_task); + pr->timeout_task = GNUNET_SCHEDULER_NO_TASK; + } + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Transmitting SEND request to `%s' with %u bytes.\n", + GNUNET_i2s (&pr->peer), (unsigned int) th->msize); + sm = (struct SendMessage *) buf; + sm->header.type = htons (GNUNET_MESSAGE_TYPE_CORE_SEND); + sm->priority = htonl (th->priority); + sm->deadline = GNUNET_TIME_absolute_hton (th->timeout); + sm->peer = pr->peer; + sm->cork = htonl ((uint32_t) th->cork); + sm->reserved = htonl (0); + ret = + th->get_message (th->get_message_cls, + size - sizeof (struct SendMessage), &sm[1]); + + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Transmitting SEND request to `%s' yielded %u bytes.\n", + GNUNET_i2s (&pr->peer), ret); + if (0 == ret) { - GNUNET_assert (pr->pending_head != NULL); - th = pr->pending_head; - if (size < th->msize + sizeof (struct SendMessage)) - { - trigger_next_request (h, GNUNET_NO); - return 0; - } - GNUNET_CONTAINER_DLL_remove (h->ready_peer_head, h->ready_peer_tail, pr); - GNUNET_CONTAINER_DLL_remove (pr->pending_head, pr->pending_tail, th); - pr->queue_size--; - if (pr->timeout_task != GNUNET_SCHEDULER_NO_TASK) - { - GNUNET_SCHEDULER_cancel (pr->timeout_task); - pr->timeout_task = GNUNET_SCHEDULER_NO_TASK; - } - LOG (GNUNET_ERROR_TYPE_DEBUG, - "Transmitting SEND request to `%s' with %u bytes.\n", - GNUNET_i2s (&pr->peer), (unsigned int) th->msize); - sm = (struct SendMessage *) buf; - sm->header.type = htons (GNUNET_MESSAGE_TYPE_CORE_SEND); - sm->priority = htonl (th->priority); - sm->deadline = GNUNET_TIME_absolute_hton (th->timeout); - sm->peer = pr->peer; - sm->cork = htonl ((uint32_t) th->cork); - sm->reserved = htonl (0); - ret = - th->get_message (th->get_message_cls, - size - sizeof (struct SendMessage), &sm[1]); - - LOG (GNUNET_ERROR_TYPE_DEBUG, - "Transmitting SEND request to `%s' yielded %u bytes.\n", - GNUNET_i2s (&pr->peer), ret); - GNUNET_free (th); - if (0 == ret) - { - LOG (GNUNET_ERROR_TYPE_DEBUG, - "Size of clients message to peer %s is 0!\n", - GNUNET_i2s (&pr->peer)); - /* client decided to send nothing! */ - request_next_transmission (pr); - return 0; - } LOG (GNUNET_ERROR_TYPE_DEBUG, - "Produced SEND message to core with %u bytes payload\n", - (unsigned int) ret); - GNUNET_assert (ret >= sizeof (struct GNUNET_MessageHeader)); - if (ret + sizeof (struct SendMessage) >= GNUNET_SERVER_MAX_MESSAGE_SIZE) - { - GNUNET_break (0); - request_next_transmission (pr); - return 0; - } - ret += sizeof (struct SendMessage); - sm->header.size = htons (ret); - GNUNET_assert (ret <= size); + "Size of clients message to peer %s is 0!\n", + GNUNET_i2s (&pr->peer)); + /* client decided to send nothing! */ request_next_transmission (pr); - return ret; + return 0; } - return 0; + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Produced SEND message to core with %u bytes payload\n", + (unsigned int) ret); + GNUNET_assert (ret >= sizeof (struct GNUNET_MessageHeader)); + if (ret + sizeof (struct SendMessage) >= GNUNET_SERVER_MAX_MESSAGE_SIZE) + { + GNUNET_break (0); + request_next_transmission (pr); + return 0; + } + ret += sizeof (struct SendMessage); + sm->header.size = htons (ret); + GNUNET_assert (ret <= size); + request_next_transmission (pr); + return ret; } @@ -732,13 +702,13 @@ trigger_next_request (struct GNUNET_CORE_Handle *h, int ignore_currently_down) LOG (GNUNET_ERROR_TYPE_DEBUG, "Request pending, not processing queue\n"); return; } - if (h->control_pending_head != NULL) + if (NULL != h->control_pending_head) msize = ntohs (((struct GNUNET_MessageHeader *) &h-> control_pending_head[1])->size); else if (h->ready_peer_head != NULL) msize = - h->ready_peer_head->pending_head->msize + sizeof (struct SendMessage); + h->ready_peer_head->th.msize + sizeof (struct SendMessage); else { LOG (GNUNET_ERROR_TYPE_DEBUG, @@ -782,8 +752,7 @@ main_notify_handler (void *cls, const struct GNUNET_MessageHeader *msg) if (NULL == msg) { LOG (GNUNET_ERROR_TYPE_INFO, - _ - ("Client was disconnected from core service, trying to reconnect.\n")); + _("Client was disconnected from core service, trying to reconnect.\n")); reconnect_later (h); return; } @@ -951,9 +920,9 @@ main_notify_handler (void *cls, const struct GNUNET_MessageHeader *msg) continue; if ((mh->expected_size != ntohs (em->size)) && (mh->expected_size != 0)) { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "Unexpected message size %u for message of type %u from peer `%4s'\n", - htons (em->size), mh->type, GNUNET_i2s (&ntm->peer)); + LOG (GNUNET_ERROR_TYPE_ERROR, + "Unexpected message size %u for message of type %u from peer `%4s'\n", + htons (em->size), mh->type, GNUNET_i2s (&ntm->peer)); GNUNET_break_op (0); continue; } @@ -1032,14 +1001,14 @@ main_notify_handler (void *cls, const struct GNUNET_MessageHeader *msg) LOG (GNUNET_ERROR_TYPE_DEBUG, "Received notification about transmission readiness to `%s'.\n", GNUNET_i2s (&smr->peer)); - if (NULL == pr->pending_head) + if (NULL == pr->th.peer) { /* request must have been cancelled between the original request * and the response from core, ignore core's readiness */ break; } - th = pr->pending_head; + th = &pr->th; if (ntohs (smr->smr_id) != th->smr_id) { /* READY message is for expired or cancelled message, @@ -1158,7 +1127,6 @@ reconnect (struct GNUNET_CORE_Handle *h) * complete (or fail) asynchronously. * * @param cfg configuration to use - * @param queue_size size of the per-peer message queue * @param cls closure for the various callbacks that follow (including handlers in the handlers array) * @param init callback to call once we have successfully * connected to the core service @@ -1178,7 +1146,7 @@ reconnect (struct GNUNET_CORE_Handle *h) */ struct GNUNET_CORE_Handle * GNUNET_CORE_connect (const struct GNUNET_CONFIGURATION_Handle *cfg, - unsigned int queue_size, void *cls, + void *cls, GNUNET_CORE_StartupCallback init, GNUNET_CORE_ConnectEventHandler connects, GNUNET_CORE_DisconnectEventHandler disconnects, @@ -1192,7 +1160,6 @@ GNUNET_CORE_connect (const struct GNUNET_CONFIGURATION_Handle *cfg, h = GNUNET_malloc (sizeof (struct GNUNET_CORE_Handle)); h->cfg = cfg; - h->queue_size = queue_size; h->cls = cls; h->init = init; h->connects = connects; @@ -1204,8 +1171,7 @@ GNUNET_CORE_connect (const struct GNUNET_CONFIGURATION_Handle *cfg, h->handlers = handlers; h->hcnt = 0; h->currently_down = GNUNET_YES; - h->peers = GNUNET_CONTAINER_multihashmap_create (128); - h->retry_backoff = GNUNET_TIME_UNIT_MILLISECONDS; + h->peers = GNUNET_CONTAINER_multihashmap_create (128, GNUNET_NO); if (NULL != handlers) while (handlers[h->hcnt].callback != NULL) h->hcnt++; @@ -1285,9 +1251,13 @@ run_request_next_transmission (void *cls, /** * Ask the core to call "notify" once it is ready to transmit the - * given number of bytes to the specified "target". Must only be + * given number of bytes to the specified "target". Must only be * called after a connection to the respective peer has been - * established (and the client has been informed about this). + * established (and the client has been informed about this). You may + * have one request of this type pending for each connected peer at + * any time. If a peer disconnects, the application MUST call + * "GNUNET_CORE_notify_transmit_ready_cancel" on the respective + * transmission request, if one such request is pending. * * @param handle connection to core service * @param cork is corking allowed for this transmission? @@ -1295,11 +1265,14 @@ run_request_next_transmission (void *cls, * @param maxdelay how long can the message wait? * @param target who should receive the message, never NULL (can be this peer's identity for loopback) * @param notify_size how many bytes of buffer space does notify want? - * @param notify function to call when buffer space is available + * @param notify function to call when buffer space is available; + * will be called with NULL on timeout; clients MUST cancel + * all pending transmission requests DURING the disconnect + * handler * @param notify_cls closure for notify * @return non-NULL if the notify callback was queued, - * NULL if we can not even queue the request (insufficient - * memory); if NULL is returned, "notify" will NOT be called. + * NULL if we can not even queue the request (request already pending); + * if NULL is returned, "notify" will NOT be called. */ struct GNUNET_CORE_TransmitHandle * GNUNET_CORE_notify_transmit_ready (struct GNUNET_CORE_Handle *handle, int cork, @@ -1312,89 +1285,45 @@ GNUNET_CORE_notify_transmit_ready (struct GNUNET_CORE_Handle *handle, int cork, { struct PeerRecord *pr; struct GNUNET_CORE_TransmitHandle *th; - struct GNUNET_CORE_TransmitHandle *pos; - struct GNUNET_CORE_TransmitHandle *prev; - struct GNUNET_CORE_TransmitHandle *minp; + if (notify_size > GNUNET_CONSTANTS_MAX_ENCRYPTED_MESSAGE_SIZE) + { + GNUNET_break (0); + return NULL; + } + GNUNET_assert (NULL != notify); + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Asking core for transmission of %u bytes to `%s'\n", + (unsigned int) notify_size, + GNUNET_i2s (target)); pr = GNUNET_CONTAINER_multihashmap_get (handle->peers, &target->hashPubKey); if (NULL == pr) { /* attempt to send to peer that is not connected */ - LOG (GNUNET_ERROR_TYPE_WARNING, - "Attempting to send to peer `%s' from peer `%s', but not connected!\n", - GNUNET_i2s (target), GNUNET_h2s (&handle->me.hashPubKey)); + GNUNET_break (0); + return NULL; + } + if (NULL != pr->th.peer) + { + /* attempting to queue a second request for the same destination */ GNUNET_break (0); return NULL; } GNUNET_assert (notify_size + sizeof (struct SendMessage) < GNUNET_SERVER_MAX_MESSAGE_SIZE); - th = GNUNET_malloc (sizeof (struct GNUNET_CORE_TransmitHandle)); + th = &pr->th; + memset (th, 0, sizeof (struct GNUNET_CORE_TransmitHandle)); th->peer = pr; - GNUNET_assert (NULL != notify); th->get_message = notify; th->get_message_cls = notify_cls; th->timeout = GNUNET_TIME_relative_to_absolute (maxdelay); th->priority = priority; th->msize = notify_size; th->cork = cork; - /* bound queue size */ - if (pr->queue_size == handle->queue_size) - { - /* find lowest-priority entry, but skip the head of the list */ - minp = pr->pending_head->next; - prev = minp; - while (prev != NULL) - { - if (prev->priority < minp->priority) - minp = prev; - prev = prev->next; - } - if (minp == NULL) - { - GNUNET_break (handle->queue_size != 0); - GNUNET_break (pr->queue_size == 1); - GNUNET_free (th); - LOG (GNUNET_ERROR_TYPE_DEBUG, - "Dropping transmission request: cannot drop queue head and limit is one\n"); - return NULL; - } - if (priority <= minp->priority) - { - LOG (GNUNET_ERROR_TYPE_DEBUG, - "Dropping transmission request: priority too low\n"); - GNUNET_free (th); - return NULL; /* priority too low */ - } - GNUNET_CONTAINER_DLL_remove (pr->pending_head, pr->pending_tail, minp); - pr->queue_size--; - GNUNET_assert (0 == minp->get_message (minp->get_message_cls, 0, NULL)); - GNUNET_free (minp); - } - - /* Order entries by deadline, but SKIP 'HEAD' (as we may have transmitted - * that request already or might even already be approved to transmit that - * message to core) */ - pos = pr->pending_head; - if (pos != NULL) - pos = pos->next; /* skip head */ - - /* insertion sort */ - prev = pos; - while ((NULL != pos) && (pos->timeout.abs_value < th->timeout.abs_value)) - { - prev = pos; - pos = pos->next; - } - GNUNET_CONTAINER_DLL_insert_after (pr->pending_head, pr->pending_tail, prev, - th); - pr->queue_size++; - /* was the request queue previously empty? */ + GNUNET_assert (GNUNET_SCHEDULER_NO_TASK == pr->ntr_task); + pr->ntr_task = + GNUNET_SCHEDULER_add_now (&run_request_next_transmission, pr); LOG (GNUNET_ERROR_TYPE_DEBUG, "Transmission request added to queue\n"); - if ((pr->pending_head == th) && (pr->ntr_task == GNUNET_SCHEDULER_NO_TASK) && - (pr->next == NULL) && (pr->prev == NULL) && - (handle->ready_peer_head != pr)) - pr->ntr_task = - GNUNET_SCHEDULER_add_now (&run_request_next_transmission, pr); return th; } @@ -1408,33 +1337,61 @@ void GNUNET_CORE_notify_transmit_ready_cancel (struct GNUNET_CORE_TransmitHandle *th) { struct PeerRecord *pr = th->peer; - struct GNUNET_CORE_Handle *h = pr->ch; - int was_head; + struct GNUNET_CORE_Handle *h; - was_head = (pr->pending_head == th); - GNUNET_CONTAINER_DLL_remove (pr->pending_head, pr->pending_tail, th); - pr->queue_size--; + GNUNET_assert (NULL != pr); + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Aborting transmission request to core for %u bytes to `%s'\n", + (unsigned int) th->msize, + GNUNET_i2s (&pr->peer)); + th->peer = NULL; + h = pr->ch; if (NULL != th->cm) { /* we're currently in the control queue, remove */ GNUNET_CONTAINER_DLL_remove (h->control_pending_head, h->control_pending_tail, th->cm); GNUNET_free (th->cm); + th->cm = NULL; } - GNUNET_free (th); - if (was_head) + if ((NULL != pr->prev) || (NULL != pr->next) || (pr == h->ready_peer_head)) { - if ((NULL != pr->prev) || (NULL != pr->next) || (pr == h->ready_peer_head)) - { - /* the request that was 'approved' by core was - * canceled before it could be transmitted; remove - * us from the 'ready' list */ - GNUNET_CONTAINER_DLL_remove (h->ready_peer_head, h->ready_peer_tail, pr); - } - if (NULL != h->client) - request_next_transmission (pr); + /* the request that was 'approved' by core was + * canceled before it could be transmitted; remove + * us from the 'ready' list */ + GNUNET_CONTAINER_DLL_remove (h->ready_peer_head, h->ready_peer_tail, pr); + } + if (GNUNET_SCHEDULER_NO_TASK != pr->ntr_task) + { + GNUNET_SCHEDULER_cancel (pr->ntr_task); + pr->ntr_task = GNUNET_SCHEDULER_NO_TASK; } } +/** + * Check if the given peer is currently connected. This function is for special + * cirumstances (GNUNET_TESTBED uses it), normal users of the CORE API are + * expected to track which peers are connected based on the connect/disconnect + * callbacks from GNUNET_CORE_connect. This function is NOT part of the + * 'versioned', 'official' API. The difference between this function and the + * function GNUNET_CORE_is_peer_connected() is that this one returns + * synchronously after looking in the CORE API cache. The function + * GNUNET_CORE_is_peer_connected() sends a message to the CORE service and hence + * its response is given asynchronously. + * + * @param h the core handle + * @param pid the identity of the peer to check if it has been connected to us + * @return GNUNET_YES if the peer is connected to us; GNUNET_NO if not + */ +int +GNUNET_CORE_is_peer_connected_sync (const struct GNUNET_CORE_Handle *h, + const struct GNUNET_PeerIdentity *pid) +{ + GNUNET_assert (NULL != h); + GNUNET_assert (NULL != pid); + return GNUNET_CONTAINER_multihashmap_contains (h->peers, &pid->hashPubKey); +} + + /* end of core_api.c */ diff --git a/src/core/gnunet-core.c b/src/core/gnunet-core.c index 4fe0a4f..17b8404 100644 --- a/src/core/gnunet-core.c +++ b/src/core/gnunet-core.c @@ -32,6 +32,38 @@ #include "gnunet_core_service.h" #include "gnunet_program_lib.h" +/** + * Option -m. + */ +static int monitor_connections; + +/** + * Current number of connections in monitor mode + */ +static int monitor_connections_counter; + +static struct GNUNET_CORE_Handle *ch; + +static struct GNUNET_PeerIdentity my_id; + +/** + * Task run in monitor mode when the user presses CTRL-C to abort. + * Stops monitoring activity. + * + * @param cls the 'struct GNUNET_TRANSPORT_PeerIterateContext *' + * @param tc scheduler context + */ +static void +shutdown_task (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + if (NULL != ch) + { + GNUNET_CORE_disconnect (ch); + ch = NULL; + } +} + /** * Callback for retrieving a list of connected peers. @@ -54,6 +86,73 @@ connected_peer_callback (void *cls, const struct GNUNET_PeerIdentity *peer, printf (_("Peer `%s'\n"), (const char *) &enc); } +void +monitor_notify_startup (void *cls, + struct GNUNET_CORE_Handle * server, + const struct GNUNET_PeerIdentity * + my_identity) +{ + my_id = (*my_identity); +} + + +/** + * Function called to notify core users that another + * peer connected to us. + * + * @param cls closure + * @param peer the peer that connected + * @param ats performance data + * @param ats_count number of entries in ats (excluding 0-termination) + */ +static void +monitor_notify_connect (void *cls, const struct GNUNET_PeerIdentity *peer, + const struct GNUNET_ATS_Information *ats, uint32_t ats_count) +{ + struct GNUNET_TIME_Absolute now = GNUNET_TIME_absolute_get(); + const char *now_str; + + if (0 != memcmp (&my_id, peer, sizeof (my_id))) + { + monitor_connections_counter ++; + now_str = GNUNET_STRINGS_absolute_time_to_string (now); + FPRINTF (stdout, _("%24s: %-17s %4s (%u connections in total)\n"), + now_str, + _("Connected to"), + GNUNET_i2s (peer), + monitor_connections_counter); + } +} + + +/** + * Function called to notify core users that another + * peer disconnected from us. + * + * @param cls closure + * @param peer the peer that disconnected + */ +static void +monitor_notify_disconnect (void *cls, const struct GNUNET_PeerIdentity *peer) +{ + struct GNUNET_TIME_Absolute now = GNUNET_TIME_absolute_get(); + const char *now_str; + + if (0 != memcmp (&my_id, peer, sizeof (my_id))) + { + now_str = GNUNET_STRINGS_absolute_time_to_string (now); + + GNUNET_assert (monitor_connections_counter > 0); + monitor_connections_counter--; + FPRINTF (stdout, _("%24s: %-17s %4s (%u connections in total)\n"), + now_str, + _("Disconnected from"), + GNUNET_i2s (peer), + monitor_connections_counter); + } +} + + /** * Main function that will be run by the scheduler. @@ -67,12 +166,32 @@ static void run (void *cls, char *const *args, const char *cfgfile, const struct GNUNET_CONFIGURATION_Handle *cfg) { + static const struct GNUNET_CORE_MessageHandler handlers[] = { + {NULL, 0, 0} + }; if (args[0] != NULL) { FPRINTF (stderr, _("Invalid command line argument `%s'\n"), args[0]); return; } - GNUNET_CORE_iterate_peers (cfg, &connected_peer_callback, NULL); + if (GNUNET_NO == monitor_connections) + GNUNET_CORE_iterate_peers (cfg, &connected_peer_callback, NULL); + else + { + memset(&my_id, '\0', sizeof (my_id)); + ch = GNUNET_CORE_connect (cfg, NULL, + monitor_notify_startup, + monitor_notify_connect, + monitor_notify_disconnect, + NULL, GNUNET_NO, + NULL, GNUNET_NO, + handlers); + + if (NULL == ch) + GNUNET_SCHEDULER_add_now (shutdown_task, NULL); + else + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, shutdown_task, NULL); + } } @@ -86,14 +205,29 @@ run (void *cls, char *const *args, const char *cfgfile, int main (int argc, char *const *argv) { + int res; static const struct GNUNET_GETOPT_CommandLineOption options[] = { + {'m', "monitor", NULL, + gettext_noop ("provide information about all current connections (continuously)"), + 0, &GNUNET_GETOPT_set_one, &monitor_connections}, GNUNET_GETOPT_OPTION_END }; - return (GNUNET_OK == - GNUNET_PROGRAM_run (argc, argv, "gnunet-core", - gettext_noop - ("Print information about connected peers."), - options, &run, NULL)) ? 0 : 1; + + if (GNUNET_OK != GNUNET_STRINGS_get_utf8_args (argc, argv, &argc, &argv)) + return 2; + + + res = GNUNET_PROGRAM_run (argc, argv, "gnunet-core", + gettext_noop + ("Print information about connected peers."), + options, &run, NULL); + + GNUNET_free ((void *) argv); + + if (GNUNET_OK == res) + return 0; + else + return 1; } /* end of gnunet-core.c */ diff --git a/src/core/gnunet-service-core.c b/src/core/gnunet-service-core.c index 59d9383..095e124 100644 --- a/src/core/gnunet-service-core.c +++ b/src/core/gnunet-service-core.c @@ -48,21 +48,39 @@ const struct GNUNET_CONFIGURATION_Handle *GSC_cfg; */ struct GNUNET_STATISTICS_Handle *GSC_stats; +/** + * Handle to the server of the core service. + */ +static struct GNUNET_SERVER_Handle *GSC_server; + +/** + * Hostkey generation context + */ +static struct GNUNET_CRYPTO_RsaKeyGenerationContext *keygen; + /** * Last task run during shutdown. Disconnects us from * the transport. + * + * @param cls NULL, unused + * @param tc scheduler context, unused */ static void -cleaning_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +shutdown_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Core service shutting down.\n"); + if (NULL != keygen) + { + GNUNET_CRYPTO_rsa_key_create_stop (keygen); + keygen = NULL; + } GSC_CLIENTS_done (); GSC_NEIGHBOURS_done (); GSC_SESSIONS_done (); GSC_KX_done (); GSC_TYPEMAP_done (); - if (GSC_stats != NULL) + if (NULL != GSC_stats) { GNUNET_STATISTICS_destroy (GSC_stats, GNUNET_NO); GSC_stats = NULL; @@ -71,6 +89,42 @@ cleaning_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) } + +/** + * Callback for hostkey read/generation + * + * @param cls NULL + * @param pk the private key + * @param emsg error message + */ +static void +key_generation_cb (void *cls, + struct GNUNET_CRYPTO_RsaPrivateKey *pk, + const char *emsg) +{ + keygen = NULL; + if (NULL == pk) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Failed to read hostkey: %s\n"), + emsg); + GNUNET_SCHEDULER_shutdown (); + return; + } + if ((GNUNET_OK != GSC_KX_init (pk)) || + (GNUNET_OK != GSC_NEIGHBOURS_init ())) + { + GNUNET_SCHEDULER_shutdown (); + return; + } + GSC_SESSIONS_init (); + GSC_CLIENTS_init (GSC_server); + GNUNET_SERVER_resume (GSC_server); + GNUNET_log (GNUNET_ERROR_TYPE_INFO, _("Core service of `%4s' ready.\n"), + GNUNET_i2s (&GSC_my_identity)); +} + + /** * Initiate core service. * @@ -82,24 +136,36 @@ static void run (void *cls, struct GNUNET_SERVER_Handle *server, const struct GNUNET_CONFIGURATION_Handle *c) { + char *keyfile; + GSC_cfg = c; + GSC_server = server; + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_filename (GSC_cfg, "GNUNETD", "HOSTKEY", + &keyfile)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _ + ("Core service is lacking HOSTKEY configuration setting. Exiting.\n")); + GNUNET_SCHEDULER_shutdown (); + return; + } GSC_stats = GNUNET_STATISTICS_create ("core", GSC_cfg); - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, &cleaning_task, + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, &shutdown_task, NULL); + GNUNET_SERVER_suspend (server); GSC_TYPEMAP_init (); - if ((GNUNET_OK != GSC_KX_init ()) || (GNUNET_OK != GSC_NEIGHBOURS_init ())) + keygen = GNUNET_CRYPTO_rsa_key_create_start (keyfile, &key_generation_cb, NULL); + GNUNET_free (keyfile); + if (NULL == keygen) { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Transport service is unable to access hostkey. Exiting.\n")); GNUNET_SCHEDULER_shutdown (); - return; } - GSC_SESSIONS_init (); - GSC_CLIENTS_init (server); - GNUNET_log (GNUNET_ERROR_TYPE_INFO, _("Core service of `%4s' ready.\n"), - GNUNET_i2s (&GSC_my_identity)); } - /** * The main function for the transport service. * diff --git a/src/core/gnunet-service-core_clients.c b/src/core/gnunet-service-core_clients.c index 1076f34..1d299da 100644 --- a/src/core/gnunet-service-core_clients.c +++ b/src/core/gnunet-service-core_clients.c @@ -239,7 +239,7 @@ send_to_all_clients (const struct GNUNET_PeerIdentity *partner, if ( (0 != (options & GNUNET_CORE_OPTION_SEND_HDR_OUTBOUND)) && (0 != (c->options & GNUNET_CORE_OPTION_SEND_FULL_OUTBOUND)) ) continue; - GNUNET_log (GNUNET_ERROR_TYPE_INFO, + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Sending %u message with %u bytes to client interested in messages of type %u.\n", options, ntohs (msg->size), @@ -298,7 +298,7 @@ handle_client_init (void *cls, struct GNUNET_SERVER_Client *client, c->options = ntohl (im->options); all_client_options |= c->options; c->types = (const uint16_t *) &c[1]; - c->connectmap = GNUNET_CONTAINER_multihashmap_create (16); + c->connectmap = GNUNET_CONTAINER_multihashmap_create (16, GNUNET_NO); GNUNET_assert (GNUNET_YES == GNUNET_CONTAINER_multihashmap_put (c->connectmap, &GSC_my_identity.hashPubKey, @@ -349,7 +349,7 @@ handle_client_send_request (void *cls, struct GNUNET_SERVER_Client *client, return; } if (c->requests == NULL) - c->requests = GNUNET_CONTAINER_multihashmap_create (16); + c->requests = GNUNET_CONTAINER_multihashmap_create (16, GNUNET_NO); GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Client asked for transmission to `%s'\n", GNUNET_i2s (&req->peer)); @@ -512,7 +512,12 @@ client_tokenizer_callback (void *cls, void *client, { struct TokenizerContext *tc = client; struct GSC_ClientActiveRequest *car = tc->car; + char buf[92]; + GNUNET_snprintf (buf, sizeof (buf), + gettext_noop ("# bytes of messages of type %u received"), + (unsigned int) ntohs (message->type)); + GNUNET_STATISTICS_update (GSC_stats, buf, ntohs (message->size), GNUNET_NO); if (0 == memcmp (&car->target, &GSC_my_identity, sizeof (struct GNUNET_PeerIdentity))) @@ -559,7 +564,7 @@ client_tokenizer_callback (void *cls, void *client, * @return GNUNET_YES (continue iteration) */ static int -destroy_active_client_request (void *cls, const GNUNET_HashCode * key, +destroy_active_client_request (void *cls, const struct GNUNET_HashCode * key, void *value) { struct GSC_ClientActiveRequest *car = value; @@ -812,13 +817,6 @@ GSC_CLIENTS_deliver_message (const struct GNUNET_PeerIdentity *sender, struct NotifyTrafficMessage *ntm; struct GNUNET_ATS_Information *a; - if (0 == options) - { - GNUNET_snprintf (buf, sizeof (buf), - gettext_noop ("# bytes of messages of type %u received"), - (unsigned int) ntohs (msg->type)); - GNUNET_STATISTICS_update (GSC_stats, buf, msize, GNUNET_NO); - } if (size >= GNUNET_SERVER_MAX_MESSAGE_SIZE) { GNUNET_break (0); @@ -899,8 +897,11 @@ GSC_CLIENTS_done () GNUNET_SERVER_notification_context_destroy (notifier); notifier = NULL; } - GNUNET_SERVER_mst_destroy (client_mst); - client_mst = NULL; + if (NULL != client_mst) + { + GNUNET_SERVER_mst_destroy (client_mst); + client_mst = NULL; + } } /* end of gnunet-service-core_clients.c */ diff --git a/src/core/gnunet-service-core_kx.c b/src/core/gnunet-service-core_kx.c index 1fce2e5..b2fc2a9 100644 --- a/src/core/gnunet-service-core_kx.c +++ b/src/core/gnunet-service-core_kx.c @@ -207,7 +207,7 @@ struct EncryptedMessage * (excluding this value itself) will be encrypted and authenticated. * ENCRYPTED_HEADER_SIZE must be set to the offset of the *next* field. */ - GNUNET_HashCode hmac; + struct GNUNET_HashCode hmac; /** * Sequence number, in network byte order. This field @@ -1357,6 +1357,8 @@ send_key (struct GSC_KeyExchangeInfo *kx) return; /* nothing to do */ if (NULL == kx->public_key) { + if (NULL != kx->pitr) + return; /* lookup public key, then try again */ GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Trying to obtain public key for `%s'\n", @@ -1513,7 +1515,7 @@ GSC_KX_handle_encrypted_message (struct GSC_KeyExchangeInfo *kx, { const struct EncryptedMessage *m; struct EncryptedMessage *pt; /* plaintext */ - GNUNET_HashCode ph; + struct GNUNET_HashCode ph; uint32_t snum; struct GNUNET_TIME_Absolute t; struct GNUNET_CRYPTO_AesInitializationVector iv; @@ -1550,10 +1552,10 @@ GSC_KX_handle_encrypted_message (struct GSC_KeyExchangeInfo *kx, kx->decrypt_key_created); GNUNET_CRYPTO_hmac (&auth_key, &m->sequence_number, size - ENCRYPTED_HEADER_SIZE, &ph); - if (0 != memcmp (&ph, &m->hmac, sizeof (GNUNET_HashCode))) + if (0 != memcmp (&ph, &m->hmac, sizeof (struct GNUNET_HashCode))) { /* checksum failed */ - GNUNET_break_op (0); + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Failed checksum validation for a message from `%s'\n", GNUNET_i2s (&kx->peer)); return; } derive_iv (&iv, &kx->decrypt_key, m->iv_seed, &GSC_my_identity); @@ -1623,8 +1625,8 @@ GSC_KX_handle_encrypted_message (struct GSC_KeyExchangeInfo *kx, MAX_MESSAGE_AGE.rel_value) { GNUNET_log (GNUNET_ERROR_TYPE_INFO, - _("Message received far too old (%llu ms). Content ignored.\n"), - GNUNET_TIME_absolute_get_duration (t).rel_value); + _("Message received far too old (%s). Content ignored.\n"), + GNUNET_STRINGS_relative_time_to_string (GNUNET_TIME_absolute_get_duration (t), GNUNET_YES)); GNUNET_STATISTICS_update (GSC_stats, gettext_noop ("# bytes dropped (ancient message)"), size, @@ -1684,30 +1686,13 @@ deliver_message (void *cls, void *client, const struct GNUNET_MessageHeader *m) /** * Initialize KX subsystem. * + * @param pk private key to use for the peer * @return GNUNET_OK on success, GNUNET_SYSERR on failure */ int -GSC_KX_init () +GSC_KX_init (struct GNUNET_CRYPTO_RsaPrivateKey *pk) { - char *keyfile; - - if (GNUNET_OK != - GNUNET_CONFIGURATION_get_value_filename (GSC_cfg, "GNUNETD", "HOSTKEY", - &keyfile)) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - _ - ("Core service is lacking HOSTKEY configuration setting. Exiting.\n")); - return GNUNET_SYSERR; - } - my_private_key = GNUNET_CRYPTO_rsa_key_create_from_file (keyfile); - GNUNET_free (keyfile); - if (NULL == my_private_key) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - _("Core service could not access hostkey. Exiting.\n")); - return GNUNET_SYSERR; - } + my_private_key = pk; GNUNET_CRYPTO_rsa_key_get_public (my_private_key, &my_public_key); GNUNET_CRYPTO_hash (&my_public_key, sizeof (my_public_key), &GSC_my_identity.hashPubKey); diff --git a/src/core/gnunet-service-core_kx.h b/src/core/gnunet-service-core_kx.h index 5ecd2c1..fcb561e 100644 --- a/src/core/gnunet-service-core_kx.h +++ b/src/core/gnunet-service-core_kx.h @@ -121,10 +121,11 @@ GSC_KX_stop (struct GSC_KeyExchangeInfo *kx); /** * Initialize KX subsystem. * + * @param pk private key to use for the peer * @return GNUNET_OK on success, GNUNET_SYSERR on failure */ int -GSC_KX_init (void); +GSC_KX_init (struct GNUNET_CRYPTO_RsaPrivateKey *pk); /** diff --git a/src/core/gnunet-service-core_neighbours.c b/src/core/gnunet-service-core_neighbours.c index 97737a6..aa77fe4 100644 --- a/src/core/gnunet-service-core_neighbours.c +++ b/src/core/gnunet-service-core_neighbours.c @@ -412,6 +412,9 @@ handle_transport_receive (void *cls, const struct GNUNET_PeerIdentity *peer, case GNUNET_MESSAGE_TYPE_CORE_ENCRYPTED_MESSAGE: GSC_KX_handle_encrypted_message (n->kxinfo, message, atsi, atsi_count); break; + case GNUNET_MESSAGE_TYPE_DUMMY: + /* Dummy messages for testing / benchmarking, just discard */ + break; default: GNUNET_log (GNUNET_ERROR_TYPE_WARNING, _ @@ -461,7 +464,7 @@ GSC_NEIGHBOURS_transmit (const struct GNUNET_PeerIdentity *target, int GSC_NEIGHBOURS_init () { - neighbours = GNUNET_CONTAINER_multihashmap_create (128); + neighbours = GNUNET_CONTAINER_multihashmap_create (128, GNUNET_NO); transport = GNUNET_TRANSPORT_connect (GSC_cfg, &GSC_my_identity, NULL, &handle_transport_receive, @@ -486,7 +489,7 @@ GSC_NEIGHBOURS_init () * @return GNUNET_OK (continue to iterate) */ static int -free_neighbour_helper (void *cls, const GNUNET_HashCode * key, void *value) +free_neighbour_helper (void *cls, const struct GNUNET_HashCode * key, void *value) { struct Neighbour *n = value; @@ -503,14 +506,18 @@ free_neighbour_helper (void *cls, const GNUNET_HashCode * key, void *value) void GSC_NEIGHBOURS_done () { - if (NULL == transport) - return; - GNUNET_TRANSPORT_disconnect (transport); - transport = NULL; - GNUNET_CONTAINER_multihashmap_iterate (neighbours, &free_neighbour_helper, - NULL); - GNUNET_CONTAINER_multihashmap_destroy (neighbours); - neighbours = NULL; + if (NULL != transport) + { + GNUNET_TRANSPORT_disconnect (transport); + transport = NULL; + } + if (NULL != neighbours) + { + GNUNET_CONTAINER_multihashmap_iterate (neighbours, &free_neighbour_helper, + NULL); + GNUNET_CONTAINER_multihashmap_destroy (neighbours); + neighbours = NULL; + } } /* end of gnunet-service-core_neighbours.c */ diff --git a/src/core/gnunet-service-core_sessions.c b/src/core/gnunet-service-core_sessions.c index 054ad97..3a603bc 100644 --- a/src/core/gnunet-service-core_sessions.c +++ b/src/core/gnunet-service-core_sessions.c @@ -283,7 +283,7 @@ GSC_SESSIONS_create (const struct GNUNET_PeerIdentity *peer, * @return GNUNET_OK (continue to iterate) */ static int -notify_client_about_session (void *cls, const GNUNET_HashCode * key, +notify_client_about_session (void *cls, const struct GNUNET_HashCode * key, void *value) { struct GSC_Client *client = cls; @@ -549,7 +549,7 @@ try_transmission (struct Session *session) * @return always GNUNET_OK */ static int -do_send_message (void *cls, const GNUNET_HashCode * key, void *value) +do_send_message (void *cls, const struct GNUNET_HashCode * key, void *value) { const struct GNUNET_MessageHeader *hdr = cls; struct Session *session = value; @@ -642,7 +642,7 @@ GSC_SESSIONS_transmit (struct GSC_ClientActiveRequest *car, */ #include "core.h" static int -queue_connect_message (void *cls, const GNUNET_HashCode * key, void *value) +queue_connect_message (void *cls, const struct GNUNET_HashCode * key, void *value) { struct GNUNET_SERVER_TransmitContext *tc = cls; struct Session *session = value; @@ -782,7 +782,7 @@ GSC_SESSIONS_add_to_typemap (const struct GNUNET_PeerIdentity *peer, void GSC_SESSIONS_init () { - sessions = GNUNET_CONTAINER_multihashmap_create (128); + sessions = GNUNET_CONTAINER_multihashmap_create (128, GNUNET_NO); } @@ -795,7 +795,7 @@ GSC_SESSIONS_init () * @return GNUNET_OK (continue to iterate) */ static int -free_session_helper (void *cls, const GNUNET_HashCode * key, void *value) +free_session_helper (void *cls, const struct GNUNET_HashCode * key, void *value) { struct Session *session = value; @@ -810,9 +810,12 @@ free_session_helper (void *cls, const GNUNET_HashCode * key, void *value) void GSC_SESSIONS_done () { - GNUNET_CONTAINER_multihashmap_iterate (sessions, &free_session_helper, NULL); - GNUNET_CONTAINER_multihashmap_destroy (sessions); - sessions = NULL; + if (NULL != sessions) + { + GNUNET_CONTAINER_multihashmap_iterate (sessions, &free_session_helper, NULL); + GNUNET_CONTAINER_multihashmap_destroy (sessions); + sessions = NULL; + } } /* end of gnunet-service-core_sessions.c */ diff --git a/src/core/test_core_api.c b/src/core/test_core_api.c index 37d1669..ab96fb4 100644 --- a/src/core/test_core_api.c +++ b/src/core/test_core_api.c @@ -31,10 +31,6 @@ #include "gnunet_scheduler_lib.h" #include "gnunet_transport_service.h" -#define VERBOSE GNUNET_NO - -#define START_ARM GNUNET_YES - #define MTYPE 12345 struct PeerContext @@ -46,9 +42,7 @@ struct PeerContext struct GNUNET_TRANSPORT_GetHelloHandle *ghh; struct GNUNET_MessageHeader *hello; int connect_status; -#if START_ARM struct GNUNET_OS_Process *arm_proc; -#endif }; static struct PeerContext p1; @@ -61,11 +55,7 @@ static GNUNET_SCHEDULER_TaskIdentifier con_task; static int ok; -#if VERBOSE #define OKPP do { ok++; GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Now at stage %u at %s:%u\n", ok, __FILE__, __LINE__); } while (0) -#else -#define OKPP do { ok++; } while (0) -#endif static void @@ -111,9 +101,8 @@ terminate_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) static void terminate_task_error (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { -#if VERBOSE - FPRINTF (stderr, "ENDING ANGRILY %u\n", ok); -#endif + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "ENDING ANGRILY %u\n", ok); GNUNET_break (0); if (NULL != p1.ch) { @@ -278,7 +267,7 @@ connect_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Asking transport (1) to connect to peer `%4s'\n", GNUNET_i2s (&p2.id)); - GNUNET_TRANSPORT_try_connect (p1.th, &p2.id); + GNUNET_TRANSPORT_try_connect (p1.th, &p2.id, NULL, NULL); /*FIXME TRY_CONNECT change */ } @@ -299,7 +288,7 @@ init_notify (void *cls, struct GNUNET_CORE_Handle *server, OKPP; /* connect p2 */ p2.ch = - GNUNET_CORE_connect (p2.cfg, 1, &p2, &init_notify, &connect_notify, + GNUNET_CORE_connect (p2.cfg, &p2, &init_notify, &connect_notify, &disconnect_notify, &inbound_notify, GNUNET_YES, &outbound_notify, GNUNET_YES, handlers); } @@ -316,20 +305,21 @@ init_notify (void *cls, struct GNUNET_CORE_Handle *server, static void setup_peer (struct PeerContext *p, const char *cfgname) { + char *binary; + + binary = GNUNET_OS_get_libexec_binary_path ("gnunet-service-arm"); p->cfg = GNUNET_CONFIGURATION_create (); -#if START_ARM p->arm_proc = - GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-arm", - "gnunet-service-arm", -#if VERBOSE - "-L", "DEBUG", -#endif + GNUNET_OS_start_process (GNUNET_YES, GNUNET_OS_INHERIT_STD_OUT_AND_ERR, + NULL, NULL, + binary, + "gnunet-service-arm", "-c", cfgname, NULL); -#endif GNUNET_assert (GNUNET_OK == GNUNET_CONFIGURATION_load (p->cfg, cfgname)); p->th = GNUNET_TRANSPORT_connect (p->cfg, NULL, p, NULL, NULL, NULL); GNUNET_assert (p->th != NULL); p->ghh = GNUNET_TRANSPORT_get_hello (p->th, &process_hello, p); + GNUNET_free (binary); } @@ -346,7 +336,7 @@ run (void *cls, char *const *args, const char *cfgfile, (GNUNET_TIME_UNIT_SECONDS, 300), &terminate_task_error, NULL); p1.ch = - GNUNET_CORE_connect (p1.cfg, 1, &p1, &init_notify, &connect_notify, + GNUNET_CORE_connect (p1.cfg, &p1, &init_notify, &connect_notify, &disconnect_notify, &inbound_notify, GNUNET_YES, &outbound_notify, GNUNET_YES, handlers); } @@ -355,7 +345,6 @@ run (void *cls, char *const *args, const char *cfgfile, static void stop_arm (struct PeerContext *p) { -#if START_ARM if (0 != GNUNET_OS_process_kill (p->arm_proc, SIGTERM)) GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); if (GNUNET_OS_process_wait (p->arm_proc) != GNUNET_OK) @@ -364,19 +353,16 @@ stop_arm (struct PeerContext *p) GNUNET_OS_process_get_pid (p->arm_proc)); GNUNET_OS_process_destroy (p->arm_proc); p->arm_proc = NULL; -#endif GNUNET_CONFIGURATION_destroy (p->cfg); } + static int check () { char *const argv[] = { "test-core-api", "-c", "test_core_api_data.conf", -#if VERBOSE - "-L", "DEBUG", -#endif NULL }; struct GNUNET_GETOPT_CommandLineOption options[] = { @@ -396,11 +382,7 @@ main (int argc, char *argv[]) int ret; GNUNET_log_setup ("test-core-api", -#if VERBOSE - "DEBUG", -#else "WARNING", -#endif NULL); ret = check (); GNUNET_DISK_directory_remove ("/tmp/test-gnunet-core-peer-1"); diff --git a/src/core/test_core_api_data.conf b/src/core/test_core_api_data.conf index 30eea2d..440dac5 100644 --- a/src/core/test_core_api_data.conf +++ b/src/core/test_core_api_data.conf @@ -1,6 +1,5 @@ @INLINE@ test_core_defaults.conf [PATHS] -DEFAULTCONFIG = test_core_api_data.conf [arm] DEFAULTSERVICES = topology hostlist diff --git a/src/core/test_core_api_peer1.conf b/src/core/test_core_api_peer1.conf index 662318a..119354c 100644 --- a/src/core/test_core_api_peer1.conf +++ b/src/core/test_core_api_peer1.conf @@ -1,7 +1,6 @@ @INLINE@ test_core_defaults.conf [PATHS] SERVICEHOME = /tmp/test-gnunet-core-peer-1/ -DEFAULTCONFIG = test_core_api_peer1.conf [transport-tcp] PORT = 12468 diff --git a/src/core/test_core_api_peer2.conf b/src/core/test_core_api_peer2.conf index cd29e3f..e66c74c 100644 --- a/src/core/test_core_api_peer2.conf +++ b/src/core/test_core_api_peer2.conf @@ -1,7 +1,6 @@ @INLINE@ test_core_defaults.conf [PATHS] SERVICEHOME = /tmp/test-gnunet-core-peer-2/ -DEFAULTCONFIG = test_core_api_peer2.conf [arm] PORT = 22460 @@ -38,4 +37,4 @@ PORT = 22467 PORT = 22468 [transport-http] -PORT = 22469 \ No newline at end of file +PORT = 22469 diff --git a/src/core/test_core_api_reliability.c b/src/core/test_core_api_reliability.c index e18d8c4..061158d 100644 --- a/src/core/test_core_api_reliability.c +++ b/src/core/test_core_api_reliability.c @@ -33,8 +33,6 @@ #include "gnunet_transport_service.h" #include -#define START_ARM GNUNET_YES - /** * Note that this value must not significantly exceed * 'MAX_PENDING' in 'gnunet-service-transport.c', otherwise @@ -73,9 +71,7 @@ struct PeerContext struct GNUNET_MessageHeader *hello; struct GNUNET_TRANSPORT_GetHelloHandle *ghh; int connect_status; -#if START_ARM struct GNUNET_OS_Process *arm_proc; -#endif }; static struct PeerContext p1; @@ -121,8 +117,10 @@ terminate_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) GNUNET_TRANSPORT_get_hello_cancel (p2.ghh); GNUNET_CORE_disconnect (p1.ch); p1.ch = NULL; + GNUNET_free_non_null (p1.hello); GNUNET_CORE_disconnect (p2.ch); p2.ch = NULL; + GNUNET_free_non_null (p2.hello); if (connect_task != GNUNET_SCHEDULER_NO_TASK) GNUNET_SCHEDULER_cancel (connect_task); GNUNET_TRANSPORT_disconnect (p1.th); @@ -176,7 +174,7 @@ try_connect (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) connect_task = GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_SECONDS, &try_connect, NULL); - GNUNET_TRANSPORT_try_connect (p1.th, &p2.id); + GNUNET_TRANSPORT_try_connect (p1.th, &p2.id, NULL, NULL); /*FIXME TRY_CONNECT change */ } @@ -384,7 +382,7 @@ init_notify (void *cls, struct GNUNET_CORE_Handle *server, GNUNET_assert (ok == 2); OKPP; /* connect p2 */ - GNUNET_CORE_connect (p2.cfg, 1, &p2, &init_notify, &connect_notify, + GNUNET_CORE_connect (p2.cfg, &p2, &init_notify, &connect_notify, &disconnect_notify, &inbound_notify, GNUNET_YES, &outbound_notify, GNUNET_YES, handlers); } @@ -409,8 +407,7 @@ process_hello (void *cls, const struct GNUNET_MessageHeader *message) GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received (my) `%s' from transport service\n", "HELLO"); GNUNET_assert (message != NULL); - p->hello = GNUNET_malloc (ntohs (message->size)); - memcpy (p->hello, message, ntohs (message->size)); + p->hello = GNUNET_copy_message (message); if ((p == &p1) && (p2.th != NULL)) GNUNET_TRANSPORT_offer_hello (p2.th, message, NULL, NULL); if ((p == &p2) && (p1.th != NULL)) @@ -426,17 +423,19 @@ process_hello (void *cls, const struct GNUNET_MessageHeader *message) static void setup_peer (struct PeerContext *p, const char *cfgname) { + char *binary; + + binary = GNUNET_OS_get_libexec_binary_path ("gnunet-service-arm"); p->cfg = GNUNET_CONFIGURATION_create (); -#if START_ARM p->arm_proc = - GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-arm", + GNUNET_OS_start_process (GNUNET_YES, GNUNET_OS_INHERIT_STD_OUT_AND_ERR, NULL, NULL, binary, "gnunet-service-arm", "-c", cfgname, NULL); -#endif GNUNET_assert (GNUNET_OK == GNUNET_CONFIGURATION_load (p->cfg, cfgname)); p->th = GNUNET_TRANSPORT_connect (p->cfg, NULL, p, NULL, NULL, NULL); GNUNET_assert (p->th != NULL); p->ghh = GNUNET_TRANSPORT_get_hello (p->th, &process_hello, p); + GNUNET_free (binary); } @@ -450,7 +449,7 @@ run (void *cls, char *const *args, const char *cfgfile, setup_peer (&p2, "test_core_api_peer2.conf"); err_task = GNUNET_SCHEDULER_add_delayed (TIMEOUT, &terminate_task_error, NULL); - GNUNET_CORE_connect (p1.cfg, 1, &p1, &init_notify, &connect_notify, + GNUNET_CORE_connect (p1.cfg, &p1, &init_notify, &connect_notify, &disconnect_notify, &inbound_notify, GNUNET_YES, &outbound_notify, GNUNET_YES, handlers); } @@ -459,7 +458,6 @@ run (void *cls, char *const *args, const char *cfgfile, static void stop_arm (struct PeerContext *p) { -#if START_ARM if (0 != GNUNET_OS_process_kill (p->arm_proc, SIGTERM)) GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); if (GNUNET_OS_process_wait (p->arm_proc) != GNUNET_OK) @@ -468,7 +466,6 @@ stop_arm (struct PeerContext *p) GNUNET_OS_process_get_pid (p->arm_proc)); GNUNET_OS_process_destroy (p->arm_proc); p->arm_proc = NULL; -#endif GNUNET_CONFIGURATION_destroy (p->cfg); } diff --git a/src/core/test_core_api_send_to_self.c b/src/core/test_core_api_send_to_self.c index b1340dc..c56e227 100644 --- a/src/core/test_core_api_send_to_self.c +++ b/src/core/test_core_api_send_to_self.c @@ -23,12 +23,12 @@ * @brief * @author Philipp Toelke */ -#include -#include -#include -#include -#include -#include +#include "platform.h" +#include "gnunet_util_lib.h" +#include "gnunet_testing_lib.h" +#include "gnunet_protocols.h" +#include "gnunet_core_service.h" +#include "gnunet_constants.h" /** * Final status code. @@ -40,22 +40,16 @@ static int ret; */ GNUNET_SCHEDULER_TaskIdentifier die_task; -static struct GNUNET_PeerIdentity myself; - /** - * Configuration to load for the new peer. + * Identity of this peer. */ -struct GNUNET_CONFIGURATION_Handle *core_cfg; +static struct GNUNET_PeerIdentity myself; /** * The handle to core */ struct GNUNET_CORE_Handle *core; -/** - * Handle to gnunet-service-arm. - */ -struct GNUNET_OS_Process *arm_proc; /** * Function scheduled as very last function, cleans up after us @@ -71,22 +65,10 @@ cleanup (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tskctx) GNUNET_CORE_disconnect (core); core = NULL; } - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stopping peer\n"); - if (0 != GNUNET_OS_process_kill (arm_proc, SIGTERM)) - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); - - if (GNUNET_OS_process_wait (arm_proc) != GNUNET_OK) - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "waitpid"); - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "ARM process %u stopped\n", - GNUNET_OS_process_get_pid (arm_proc)); - GNUNET_OS_process_destroy (arm_proc); - arm_proc = NULL; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Ending test.\n"); } + static int receive (void *cls, const struct GNUNET_PeerIdentity *other, const struct GNUNET_MessageHeader *message, @@ -96,11 +78,14 @@ receive (void *cls, const struct GNUNET_PeerIdentity *other, GNUNET_SCHEDULER_cancel (die_task); GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received message from peer %s\n", GNUNET_i2s (other)); + GNUNET_assert (GNUNET_MESSAGE_TYPE_DUMMY == ntohs (message->type)); + GNUNET_assert (0 == memcmp (other, &myself, sizeof (myself))); GNUNET_SCHEDULER_add_now (&cleanup, NULL); ret = 0; return GNUNET_OK; } + static size_t send_message (void *cls, size_t size, void *buf) { @@ -117,6 +102,7 @@ send_message (void *cls, size_t size, void *buf) return ntohs (hdr->size); } + static void init (void *cls, struct GNUNET_CORE_Handle *core, const struct GNUNET_PeerIdentity *my_identity) @@ -132,6 +118,7 @@ init (void *cls, struct GNUNET_CORE_Handle *core, memcpy (&myself, my_identity, sizeof (struct GNUNET_PeerIdentity)); } + static void connect_cb (void *cls, const struct GNUNET_PeerIdentity *peer, const struct GNUNET_ATS_Information *atsi, unsigned int atsi_count) @@ -154,71 +141,29 @@ connect_cb (void *cls, const struct GNUNET_PeerIdentity *peer, * Main function that will be run by the scheduler. * * @param cls closure - * @param args remaining command-line arguments - * @param cfgfile name of the configuration file used (for saving, can be NULL!) * @param cfg configuration */ static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) { const static struct GNUNET_CORE_MessageHandler handlers[] = { {&receive, GNUNET_MESSAGE_TYPE_DUMMY, 0}, {NULL, 0, 0} }; - - core_cfg = GNUNET_CONFIGURATION_create (); - - arm_proc = - GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-arm", - "gnunet-service-arm", -#if VERBOSE - "-L", "DEBUG", -#endif - "-c", "test_core_api_peer1.conf", NULL); - - GNUNET_assert (GNUNET_OK == - GNUNET_CONFIGURATION_load (core_cfg, - "test_core_api_peer1.conf")); - core = - GNUNET_CORE_connect (core_cfg, 42, NULL, &init, &connect_cb, NULL, NULL, - 0, NULL, 0, handlers); - + GNUNET_CORE_connect (cfg, NULL, &init, &connect_cb, NULL, NULL, + 0, NULL, 0, handlers); die_task = GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 300), &cleanup, - cls); + NULL); } -static int -check () -{ - char *const argv[] = { "test-core-api-send-to-self", - "-c", - "test_core_api_data.conf", -#if VERBOSE - "-L", "DEBUG", -#endif - NULL - }; - - static const struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - - ret = 1; - - return (GNUNET_OK == - GNUNET_PROGRAM_run ((sizeof (argv) / sizeof (char *)) - 1, argv, - "test_core_api_send_to_self", - gettext_noop ("help text"), options, &run, - NULL)) ? ret : 1; -} - /** - * The main function to obtain template from gnunetd. + * The main function to test sending a message to the local peer via core * * @param argc number of arguments from the command line * @param argv command line arguments @@ -227,15 +172,10 @@ check () int main (int argc, char *argv[]) { - GNUNET_log_setup ("test-core-api-send-to-self", -#if VERBOSE - "DEBUG", -#else - "WARNING", -#endif - NULL); - ret = check (); - GNUNET_DISK_directory_remove ("/tmp/test-gnunet-core-peer-1"); + if (0 != GNUNET_TESTING_peer_run ("test-core-api-send-to-self", + "test_core_api_peer1.conf", + &run, NULL)) + return 1; return ret; } diff --git a/src/core/test_core_api_send_to_self.conf b/src/core/test_core_api_send_to_self.conf index 6737726..704a2b6 100644 --- a/src/core/test_core_api_send_to_self.conf +++ b/src/core/test_core_api_send_to_self.conf @@ -1,7 +1,6 @@ @INLINE@ test_core_defaults.conf [PATHS] SERVICEHOME = ~/.gnunet/ -DEFAULTCONFIG = test_core_api_send_to_self.conf [arm] PORT = 2425 @@ -22,7 +21,6 @@ AUTOSTART = YES PORT = 9252 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = test_core_api_send_to_self ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; diff --git a/src/core/test_core_api_start_only.c b/src/core/test_core_api_start_only.c index 8c81320..d9cb415 100644 --- a/src/core/test_core_api_start_only.c +++ b/src/core/test_core_api_start_only.c @@ -31,12 +31,8 @@ #include "gnunet_program_lib.h" #include "gnunet_scheduler_lib.h" -#define VERBOSE GNUNET_NO - #define TIMEOUT 5 -#define START_ARM GNUNET_YES - #define MTYPE 12345 struct PeerContext @@ -44,9 +40,7 @@ struct PeerContext struct GNUNET_CONFIGURATION_Handle *cfg; struct GNUNET_CORE_Handle *ch; struct GNUNET_PeerIdentity id; -#if START_ARM struct GNUNET_OS_Process *arm_proc; -#endif }; static struct PeerContext p1; @@ -115,8 +109,6 @@ shutdown_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) } - - static void init_notify (void *cls, struct GNUNET_CORE_Handle *server, const struct GNUNET_PeerIdentity *my_identity) @@ -129,7 +121,7 @@ init_notify (void *cls, struct GNUNET_CORE_Handle *server, { /* connect p2 */ p2.ch = - GNUNET_CORE_connect (p2.cfg, 1, &p2, &init_notify, &connect_notify, + GNUNET_CORE_connect (p2.cfg, &p2, &init_notify, &connect_notify, &disconnect_notify, &inbound_notify, GNUNET_YES, &outbound_notify, GNUNET_YES, handlers); } @@ -145,17 +137,18 @@ init_notify (void *cls, struct GNUNET_CORE_Handle *server, static void setup_peer (struct PeerContext *p, const char *cfgname) { + char *binary; + + binary = GNUNET_OS_get_libexec_binary_path ("gnunet-service-arm"); p->cfg = GNUNET_CONFIGURATION_create (); -#if START_ARM p->arm_proc = - GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-arm", - "gnunet-service-arm", -#if VERBOSE - "-L", "DEBUG", -#endif - "-c", cfgname, NULL); -#endif + GNUNET_OS_start_process (GNUNET_YES, GNUNET_OS_INHERIT_STD_OUT_AND_ERR, + NULL, NULL, + binary, + "gnunet-service-arm", + "-c", cfgname, NULL); GNUNET_assert (GNUNET_OK == GNUNET_CONFIGURATION_load (p->cfg, cfgname)); + GNUNET_free (binary); } @@ -177,7 +170,6 @@ timeout_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) } - static void run (void *cls, char *const *args, const char *cfgfile, const struct GNUNET_CONFIGURATION_Handle *cfg) @@ -191,7 +183,7 @@ run (void *cls, char *const *args, const char *cfgfile, (GNUNET_TIME_UNIT_MINUTES, TIMEOUT), &timeout_task, NULL); p1.ch = - GNUNET_CORE_connect (p1.cfg, 1, &p1, &init_notify, &connect_notify, + GNUNET_CORE_connect (p1.cfg, &p1, &init_notify, &connect_notify, &disconnect_notify, &inbound_notify, GNUNET_YES, &outbound_notify, GNUNET_YES, handlers); } @@ -201,7 +193,6 @@ static void stop_arm (struct PeerContext *p) { GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stopping peer\n"); -#if START_ARM if (0 != GNUNET_OS_process_kill (p->arm_proc, SIGTERM)) GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); if (GNUNET_OS_process_wait (p->arm_proc) != GNUNET_OK) @@ -210,7 +201,6 @@ stop_arm (struct PeerContext *p) GNUNET_OS_process_get_pid (p->arm_proc)); GNUNET_OS_process_destroy (p->arm_proc); p->arm_proc = NULL; -#endif GNUNET_CONFIGURATION_destroy (p->cfg); } @@ -221,9 +211,6 @@ check () char *const argv[] = { "test-core-api-start-only", "-c", "test_core_api_data.conf", -#if VERBOSE - "-L", "DEBUG", -#endif NULL }; struct GNUNET_GETOPT_CommandLineOption options[] = { @@ -241,17 +228,14 @@ check () return ok; } + int main (int argc, char *argv[]) { int ret; GNUNET_log_setup ("test-core-api-start-only", -#if VERBOSE - "DEBUG", -#else "WARNING", -#endif NULL); ret = check (); GNUNET_DISK_directory_remove ("/tmp/test-gnunet-core-peer-1"); diff --git a/src/core/test_core_defaults.conf b/src/core/test_core_defaults.conf index 9525ca2..4110186 100644 --- a/src/core/test_core_defaults.conf +++ b/src/core/test_core_defaults.conf @@ -1,6 +1,5 @@ [PATHS] SERVICEHOME = /tmp/test-gnunet-core/ -DEFAULTCONFIG = test_core_defaults.conf [arm] DEFAULTSERVICES = @@ -63,3 +62,6 @@ AUTOSTART = NO [lockmanager] AUTOSTART = NO + +[consensus] +AUTOSTART = NO diff --git a/src/core/test_core_quota_asymmetric_recv_limited_peer1.conf b/src/core/test_core_quota_asymmetric_recv_limited_peer1.conf index 5501fb8..af5453f 100644 --- a/src/core/test_core_quota_asymmetric_recv_limited_peer1.conf +++ b/src/core/test_core_quota_asymmetric_recv_limited_peer1.conf @@ -1,7 +1,6 @@ @INLINE@ test_core_defaults.conf [PATHS] SERVICEHOME = /tmp/test-gnunet-core-quota-asym-recv-lim-peer-1/ -DEFAULTCONFIG = test_core_quota_asymmetric_recv_limited_peer1.conf [transport-tcp] PORT = 12488 @@ -29,11 +28,24 @@ UNIXPATH = /tmp/gnunet-core-asym-recv-p1-service-transport.sock [ats] PORT = 12491 UNIXPATH = /tmp/gnunet-core-asym-recv-p1-service-ats.sock +# UNSPECIFIED +UNSPECIFIED_QUOTA_IN = 1 MB +UNSPECIFIED_QUOTA_OUT = 1 MB +# LOOPBACK +LOOPBACK_QUOTA_IN = 1 MB +LOOPBACK_QUOTA_OUT = 1 MB +# LAN +LAN_QUOTA_IN = 1 MB +LAN_QUOTA_OUT = 1 MB +# WAN WAN_QUOTA_IN = 1 MB WAN_QUOTA_OUT = 1 MB +# WLAN +WLAN_QUOTA_IN = 1 MB +WLAN_QUOTA_OUT = 1 MB + [core] PORT = 12490 UNIXPATH = /tmp/gnunet-core-asym-recv-p1-service-core.sock -DEBUG = NO diff --git a/src/core/test_core_quota_asymmetric_recv_limited_peer2.conf b/src/core/test_core_quota_asymmetric_recv_limited_peer2.conf index 62fc69e..e3ae70e 100644 --- a/src/core/test_core_quota_asymmetric_recv_limited_peer2.conf +++ b/src/core/test_core_quota_asymmetric_recv_limited_peer2.conf @@ -1,7 +1,6 @@ @INLINE@ test_core_defaults.conf [PATHS] SERVICEHOME = /tmp/test-gnunet-core-quota-asym-recv-lim-peer-2/ -DEFAULTCONFIG = test_core_quota_asymmetric_recv_limited_peer2.conf [arm] @@ -27,13 +26,25 @@ UNIXPATH = /tmp/gnunet-core-asym-recv-p2-service-transport.sock [core] PORT = 22490 UNIXPATH = /tmp/gnunet-core-asym-recv-p2-service-core.sock -DEBUG = NO [ats] PORT = 22491 UNIXPATH = /tmp/gnunet-core-asym-recv-p2-service-ats.sock -WAN_QUOTA_IN = 10 kiB -WAN_QUOTA_OUT = 10 kiB +# UNSPECIFIED +UNSPECIFIED_QUOTA_IN = 10240 +UNSPECIFIED_QUOTA_OUT = 10240 +# LOOPBACK +LOOPBACK_QUOTA_IN = 10240 +LOOPBACK_QUOTA_OUT = 10240 +# LAN +LAN_QUOTA_IN = 10240 +LAN_QUOTA_OUT = 10240 +# WAN +WAN_QUOTA_IN = 10240 +WAN_QUOTA_OUT = 10240 +# WLAN +WLAN_QUOTA_IN = 10240 +WLAN_QUOTA_OUT = 10240 [transport-tcp] PORT = 22467 @@ -42,4 +53,4 @@ PORT = 22467 PORT = 22468 [transport-http] -PORT = 22469 \ No newline at end of file +PORT = 22469 diff --git a/src/core/test_core_quota_asymmetric_send_limit_peer1.conf b/src/core/test_core_quota_asymmetric_send_limit_peer1.conf index 568cf6b..89cdc15 100644 --- a/src/core/test_core_quota_asymmetric_send_limit_peer1.conf +++ b/src/core/test_core_quota_asymmetric_send_limit_peer1.conf @@ -1,7 +1,6 @@ @INLINE@ test_core_defaults.conf [PATHS] SERVICEHOME = /tmp/test-gnunet-core-quota-asym-send-lim-peer-1/ -DEFAULTCONFIG = test_core_quota_asymmetric_send_limit_peer1.conf [transport-tcp] PORT = 12488 @@ -27,12 +26,24 @@ PORT = 12485 UNIXPATH = /tmp/gnunet-core-asym-send-p1-service-transport.sock [ats] -WAN_QUOTA_IN = 10240 -WAN_QUOTA_OUT = 10240 PORT = 12491 UNIXPATH = /tmp/gnunet-core-asym-send-p1-service-ats.sock +# UNSPECIFIED +UNSPECIFIED_QUOTA_IN = 10240 +UNSPECIFIED_QUOTA_OUT = 10240 +# LOOPBACK +LOOPBACK_QUOTA_IN = 10240 +LOOPBACK_QUOTA_OUT = 10240 +# LAN +LAN_QUOTA_IN = 10240 +LAN_QUOTA_OUT = 10240 +# WAN +WAN_QUOTA_IN = 10240 +WAN_QUOTA_OUT = 10240 +# WLAN +WLAN_QUOTA_IN = 10240 +WLAN_QUOTA_OUT = 10240 [core] PORT = 12490 UNIXPATH = /tmp/gnunet-core-asym-send-p1-service-core.sock -DEBUG = NO diff --git a/src/core/test_core_quota_asymmetric_send_limit_peer2.conf b/src/core/test_core_quota_asymmetric_send_limit_peer2.conf index 614358b..0707ac1 100644 --- a/src/core/test_core_quota_asymmetric_send_limit_peer2.conf +++ b/src/core/test_core_quota_asymmetric_send_limit_peer2.conf @@ -1,7 +1,6 @@ @INLINE@ test_core_defaults.conf [PATHS] SERVICEHOME = /tmp/test-gnunet-core-quota-asym-send-lim-peer-2/ -DEFAULTCONFIG = test_core_quota_asymmetric_send_limit_peer2.conf [arm] PORT = 22486 @@ -26,7 +25,6 @@ UNIXPATH = /tmp/gnunet-core-asym-send-p2-service-transport.sock [core] PORT = 22490 UNIXPATH = /tmp/gnunet-core-asym-send-p2-service-core.sock -DEBUG = NO [ats] PORT = 22491 @@ -34,6 +32,25 @@ UNIXPATH = /tmp/gnunet-core-asym-send-p2-service-ats.sock WAN_QUOTA_IN = 1 MB WAN_QUOTA_OUT = 1 MB +[ats] +PORT = 12471 +UNIXPATH = /tmp/gnunet-core-sym-p1-service-ats.sock +# UNSPECIFIED +UNSPECIFIED_QUOTA_IN = 1 MB +UNSPECIFIED_QUOTA_OUT = 1 MB +# LOOPBACK +LOOPBACK_QUOTA_IN = 1 MB +LOOPBACK_QUOTA_OUT = 1 MB +# LAN +LAN_QUOTA_IN = 1 MB +LAN_QUOTA_OUT = 1 MB +# WAN +WAN_QUOTA_IN = 1 MB +WAN_QUOTA_OUT = 1 MB +# WLAN +WLAN_QUOTA_IN = 1 MB +WLAN_QUOTA_OUT = 1 MB + [transport-tcp] PORT = 22467 @@ -41,4 +58,4 @@ PORT = 22467 PORT = 22468 [transport-http] -PORT = 22469 \ No newline at end of file +PORT = 22469 diff --git a/src/core/test_core_quota_compliance.c b/src/core/test_core_quota_compliance.c index df602b3..884d5fa 100644 --- a/src/core/test_core_quota_compliance.c +++ b/src/core/test_core_quota_compliance.c @@ -38,8 +38,6 @@ #define ASYMMETRIC_SEND_LIMITED 1 #define ASYMMETRIC_RECV_LIMITED 2 -#define START_ARM GNUNET_YES - /** * Note that this value must not significantly exceed * 'MAX_PENDING' in 'gnunet-service-transport.c', otherwise @@ -84,9 +82,7 @@ struct PeerContext struct GNUNET_STATISTICS_Handle *stats; struct GNUNET_TRANSPORT_GetHelloHandle *ghh; int connect_status; -#if START_ARM struct GNUNET_OS_Process *arm_proc; -#endif }; static struct PeerContext p1; @@ -146,6 +142,8 @@ terminate_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) p1.th = NULL; GNUNET_TRANSPORT_disconnect (p2.th); p2.th = NULL; + GNUNET_free_non_null (p1.hello); + GNUNET_free_non_null (p2.hello); } @@ -191,8 +189,8 @@ try_connect (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) connect_task = GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_SECONDS, &try_connect, NULL); - GNUNET_TRANSPORT_try_connect (p1.th, &p2.id); - GNUNET_TRANSPORT_try_connect (p2.th, &p1.id); + GNUNET_TRANSPORT_try_connect (p1.th, &p2.id, NULL, NULL); /*FIXME TRY_CONNECT change */ + GNUNET_TRANSPORT_try_connect (p2.th, &p1.id, NULL, NULL); /*FIXME TRY_CONNECT change */ } /** @@ -527,7 +525,7 @@ init_notify (void *cls, struct GNUNET_CORE_Handle *server, OKPP; /* connect p2 */ p2.ch = - GNUNET_CORE_connect (p2.cfg, 1, &p2, &init_notify, &connect_notify, + GNUNET_CORE_connect (p2.cfg, &p2, &init_notify, &connect_notify, &disconnect_notify, &inbound_notify, GNUNET_YES, &outbound_notify, GNUNET_YES, handlers); } @@ -570,19 +568,21 @@ process_hello (void *cls, const struct GNUNET_MessageHeader *message) static void setup_peer (struct PeerContext *p, const char *cfgname) { + char *binary; + + binary = GNUNET_OS_get_libexec_binary_path ("gnunet-service-arm"); p->cfg = GNUNET_CONFIGURATION_create (); -#if START_ARM p->arm_proc = - GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-arm", + GNUNET_OS_start_process (GNUNET_YES, GNUNET_OS_INHERIT_STD_OUT_AND_ERR, NULL, NULL, binary, "gnunet-service-arm", "-c", cfgname, NULL); -#endif GNUNET_assert (GNUNET_OK == GNUNET_CONFIGURATION_load (p->cfg, cfgname)); p->stats = GNUNET_STATISTICS_create ("core", p->cfg); GNUNET_assert (p->stats != NULL); p->th = GNUNET_TRANSPORT_connect (p->cfg, NULL, p, NULL, NULL, NULL); GNUNET_assert (p->th != NULL); p->ghh = GNUNET_TRANSPORT_get_hello (p->th, &process_hello, p); + GNUNET_free (binary); } @@ -629,7 +629,7 @@ run (void *cls, char *const *args, const char *cfgfile, ¤t_quota_p2_out)); p1.ch = - GNUNET_CORE_connect (p1.cfg, 1, &p1, &init_notify, &connect_notify, + GNUNET_CORE_connect (p1.cfg, &p1, &init_notify, &connect_notify, &disconnect_notify, &inbound_notify, GNUNET_YES, &outbound_notify, GNUNET_YES, handlers); } @@ -638,7 +638,6 @@ run (void *cls, char *const *args, const char *cfgfile, static void stop_arm (struct PeerContext *p) { -#if START_ARM if (0 != GNUNET_OS_process_kill (p->arm_proc, SIGTERM)) GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); if (GNUNET_OS_process_wait (p->arm_proc) != GNUNET_OK) @@ -647,7 +646,6 @@ stop_arm (struct PeerContext *p) GNUNET_OS_process_get_pid (p->arm_proc)); GNUNET_OS_process_destroy (p->arm_proc); p->arm_proc = NULL; -#endif GNUNET_CONFIGURATION_destroy (p->cfg); } diff --git a/src/core/test_core_quota_peer1.conf b/src/core/test_core_quota_peer1.conf index 4ff2ee4..dbe8714 100644 --- a/src/core/test_core_quota_peer1.conf +++ b/src/core/test_core_quota_peer1.conf @@ -1,7 +1,6 @@ @INLINE@ test_core_defaults.conf [PATHS] SERVICEHOME = /tmp/test-gnunet-core-quota-sym-peer-1/ -DEFAULTCONFIG = test_core_quota_peer1.conf [transport-tcp] PORT = 12468 @@ -27,13 +26,27 @@ PORT = 12475 UNIXPATH = /tmp/gnunet-core-sym-p1-service-transport.sock [ats] +PORT = 12471 +UNIXPATH = /tmp/gnunet-core-sym-p1-service-ats.sock +# UNSPECIFIED +UNSPECIFIED_QUOTA_IN = 10240 +UNSPECIFIED_QUOTA_OUT = 10240 +# LOOPBACK +LOOPBACK_QUOTA_IN = 10240 +LOOPBACK_QUOTA_OUT = 10240 +# LAN +LAN_QUOTA_IN = 10240 +LAN_QUOTA_OUT = 10240 +# WAN WAN_QUOTA_IN = 10240 WAN_QUOTA_OUT = 10240 +# WLAN +WLAN_QUOTA_IN = 10240 +WLAN_QUOTA_OUT = 10240 [core] PORT = 12480 UNIXPATH = /tmp/gnunet-core-sym-p1-service-core.sock -DEBUG = NO [ats] PORT = 12481 diff --git a/src/core/test_core_quota_peer2.conf b/src/core/test_core_quota_peer2.conf index 1fd4ec8..6dec73a 100644 --- a/src/core/test_core_quota_peer2.conf +++ b/src/core/test_core_quota_peer2.conf @@ -1,7 +1,6 @@ @INLINE@ test_core_defaults.conf [PATHS] SERVICEHOME = /tmp/test-gnunet-core-quota-sym-peer-2/ -DEFAULTCONFIG = test_core_quota_peer2.conf [arm] PORT = 22476 @@ -26,13 +25,25 @@ UNIXPATH = /tmp/gnunet-core-sym-p2-service-transport.sock [core] PORT = 22480 UNIXPATH = /tmp/gnunet-core-sym-p2-service-core.sock -DEBUG = NO [ats] PORT = 22482 UNIXPATH = /tmp/gnunet-core-sym-p2-service-ats.sock -WAN_QUOTA_IN = 10 kiB -WAN_QUOTA_OUT = 10 kiB +# UNSPECIFIED +UNSPECIFIED_QUOTA_IN = 10240 +UNSPECIFIED_QUOTA_OUT = 10240 +# LOOPBACK +LOOPBACK_QUOTA_IN = 10240 +LOOPBACK_QUOTA_OUT = 10240 +# LAN +LAN_QUOTA_IN = 10240 +LAN_QUOTA_OUT = 10240 +# WAN +WAN_QUOTA_IN = 10240 +WAN_QUOTA_OUT = 10240 +# WLAN +WLAN_QUOTA_IN = 10240 +WLAN_QUOTA_OUT = 10240 [transport-tcp] PORT = 22467 @@ -41,4 +52,4 @@ PORT = 22467 PORT = 22468 [transport-http] -PORT = 22469 \ No newline at end of file +PORT = 22469 diff --git a/src/datacache/Makefile.am b/src/datacache/Makefile.am index d34e6e8..c6c27b3 100644 --- a/src/datacache/Makefile.am +++ b/src/datacache/Makefile.am @@ -19,9 +19,6 @@ endif if HAVE_SQLITE SQLITE_PLUGIN = libgnunet_plugin_datacache_sqlite.la endif -if HAVE_MYSQL - MYSQL_PLUGIN = libgnunet_plugin_datacache_mysql.la -endif if HAVE_POSTGRES POSTGRES_PLUGIN = libgnunet_plugin_datacache_postgres.la endif @@ -42,8 +39,8 @@ libgnunetdatacache_la_LDFLAGS = \ plugin_LTLIBRARIES = \ $(SQLITE_PLUGIN) \ - $(MYSQL_PLUGIN) \ $(POSTGRES_PLUGIN) \ + libgnunet_plugin_datacache_heap.la \ libgnunet_plugin_datacache_template.la @@ -51,21 +48,19 @@ libgnunet_plugin_datacache_sqlite_la_SOURCES = \ plugin_datacache_sqlite.c libgnunet_plugin_datacache_sqlite_la_LIBADD = \ $(top_builddir)/src/statistics/libgnunetstatistics.la \ - $(top_builddir)/src/util/libgnunetutil.la $(XLIBS) -lsqlite3 + $(top_builddir)/src/util/libgnunetutil.la $(XLIBS) -lsqlite3 \ + $(LTLIBINTL) libgnunet_plugin_datacache_sqlite_la_LDFLAGS = \ $(GN_PLUGIN_LDFLAGS) -libgnunet_plugin_datacache_mysql_la_SOURCES = \ - plugin_datacache_mysql.c -libgnunet_plugin_datacache_mysql_la_LIBADD = \ +libgnunet_plugin_datacache_heap_la_SOURCES = \ + plugin_datacache_heap.c +libgnunet_plugin_datacache_heap_la_LIBADD = \ $(top_builddir)/src/statistics/libgnunetstatistics.la \ - $(top_builddir)/src/mysql/libgnunetmysql.la \ - $(top_builddir)/src/util/libgnunetutil.la \ - $(GN_PLUGIN_LDFLAGS) $(MYSQL_LDFLAGS) -lmysqlclient -libgnunet_plugin_datacache_mysql_la_CPPFLAGS = \ - $(MYSQL_CPPFLAGS) -libgnunet_plugin_datacache_mysql_la_LDFLAGS = \ - $(GN_PLUGIN_LDFLAGS) $(MYSQL_LDFLAGS) -lmysqlclient + $(top_builddir)/src/util/libgnunetutil.la $(XLIBS) \ + $(LTLIBINTL) +libgnunet_plugin_datacache_heap_la_LDFLAGS = \ + $(GN_PLUGIN_LDFLAGS) libgnunet_plugin_datacache_postgres_la_SOURCES = \ plugin_datacache_postgres.c @@ -82,7 +77,8 @@ libgnunet_plugin_datacache_postgres_la_LDFLAGS = \ libgnunet_plugin_datacache_template_la_SOURCES = \ plugin_datacache_template.c libgnunet_plugin_datacache_template_la_LIBADD = \ - $(top_builddir)/src/util/libgnunetutil.la $(XLIBS) + $(top_builddir)/src/util/libgnunetutil.la $(XLIBS) \ + $(LTLIBINTL) libgnunet_plugin_datacache_template_la_LDFLAGS = \ $(GN_PLUGIN_LDFLAGS) @@ -98,16 +94,14 @@ SQLITE_TESTS = \ $(SQLITE_BENCHMARKS) endif -if HAVE_MYSQL if HAVE_BENCHMARKS - MYSQL_BENCHMARKS = \ - perf_datacache_mysql -endif -MYSQL_TESTS = \ - test_datacache_mysql \ - test_datacache_quota_mysql \ - $(MYSQL_BENCHMARKS) + HEAP_BENCHMARKS = \ + perf_datacache_heap endif +HEAP_TESTS = \ + test_datacache_heap \ + test_datacache_quota_heap \ + $(HEAP_BENCHMARKS) if HAVE_POSTGRES if HAVE_BENCHMARKS @@ -122,7 +116,7 @@ endif check_PROGRAMS = \ $(SQLITE_TESTS) \ - $(MYSQL_TESTS) \ + $(HEAP_TESTS) \ $(POSTGRES_TESTS) if ENABLE_TEST_RUN @@ -132,61 +126,70 @@ endif test_datacache_sqlite_SOURCES = \ test_datacache.c test_datacache_sqlite_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/datacache/libgnunetdatacache.la \ $(top_builddir)/src/util/libgnunetutil.la test_datacache_quota_sqlite_SOURCES = \ test_datacache_quota.c test_datacache_quota_sqlite_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/datacache/libgnunetdatacache.la \ $(top_builddir)/src/util/libgnunetutil.la perf_datacache_sqlite_SOURCES = \ perf_datacache.c perf_datacache_sqlite_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/datacache/libgnunetdatacache.la \ $(top_builddir)/src/util/libgnunetutil.la -test_datacache_mysql_SOURCES = \ +test_datacache_heap_SOURCES = \ test_datacache.c -test_datacache_mysql_LDADD = \ +test_datacache_heap_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/datacache/libgnunetdatacache.la \ $(top_builddir)/src/util/libgnunetutil.la -test_datacache_quota_mysql_SOURCES = \ +test_datacache_quota_heap_SOURCES = \ test_datacache_quota.c -test_datacache_quota_mysql_LDADD = \ +test_datacache_quota_heap_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/datacache/libgnunetdatacache.la \ $(top_builddir)/src/util/libgnunetutil.la -perf_datacache_mysql_SOURCES = \ +perf_datacache_heap_SOURCES = \ perf_datacache.c -perf_datacache_mysql_LDADD = \ +perf_datacache_heap_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/datacache/libgnunetdatacache.la \ $(top_builddir)/src/util/libgnunetutil.la test_datacache_postgres_SOURCES = \ test_datacache.c test_datacache_postgres_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/datacache/libgnunetdatacache.la \ $(top_builddir)/src/util/libgnunetutil.la test_datacache_quota_postgres_SOURCES = \ test_datacache_quota.c test_datacache_quota_postgres_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/datacache/libgnunetdatacache.la \ $(top_builddir)/src/util/libgnunetutil.la perf_datacache_postgres_SOURCES = \ perf_datacache.c perf_datacache_postgres_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/datacache/libgnunetdatacache.la \ $(top_builddir)/src/util/libgnunetutil.la EXTRA_DIST = \ test_datacache_data_sqlite.conf \ perf_datacache_data_sqlite.conf \ - test_datacache_data_mysql.conf \ - perf_datacache_data_mysql.conf \ + test_datacache_data_heap.conf \ + perf_datacache_data_heap.conf \ test_datacache_data_postgres.conf \ perf_datacache_data_postgres.conf diff --git a/src/datacache/Makefile.in b/src/datacache/Makefile.in index 2acd972..a564d52 100644 --- a/src/datacache/Makefile.in +++ b/src/datacache/Makefile.in @@ -1,9 +1,9 @@ -# Makefile.in generated by automake 1.11.1 from Makefile.am. +# Makefile.in generated by automake 1.11.6 from Makefile.am. # @configure_input@ # Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, -# 2003, 2004, 2005, 2006, 2007, 2008, 2009 Free Software Foundation, -# Inc. +# 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Free Software +# Foundation, Inc. # This Makefile.in is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. @@ -17,6 +17,23 @@ VPATH = @srcdir@ +am__make_dryrun = \ + { \ + am__dry=no; \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + echo 'am--echo: ; @echo "AM" OK' | $(MAKE) -f - 2>/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } pkgdatadir = $(datadir)/@PACKAGE@ pkgincludedir = $(includedir)/@PACKAGE@ pkglibdir = $(libdir)/@PACKAGE@ @@ -43,14 +60,15 @@ DIST_COMMON = $(dist_pkgcfg_DATA) $(srcdir)/Makefile.am \ ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 am__aclocal_m4_deps = $(top_srcdir)/m4/absolute-header.m4 \ $(top_srcdir)/m4/align.m4 $(top_srcdir)/m4/argz.m4 \ - $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/iconv.m4 \ - $(top_srcdir)/m4/lib-ld.m4 $(top_srcdir)/m4/lib-link.m4 \ - $(top_srcdir)/m4/lib-prefix.m4 $(top_srcdir)/m4/libcurl.m4 \ - $(top_srcdir)/m4/libgcrypt.m4 $(top_srcdir)/m4/libtool.m4 \ - $(top_srcdir)/m4/libunistring.m4 $(top_srcdir)/m4/ltdl.m4 \ - $(top_srcdir)/m4/ltoptions.m4 $(top_srcdir)/m4/ltsugar.m4 \ - $(top_srcdir)/m4/ltversion.m4 $(top_srcdir)/m4/lt~obsolete.m4 \ - $(top_srcdir)/m4/nls.m4 $(top_srcdir)/m4/po.m4 \ + $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/glib-2.0.m4 \ + $(top_srcdir)/m4/iconv.m4 $(top_srcdir)/m4/lib-ld.m4 \ + $(top_srcdir)/m4/lib-link.m4 $(top_srcdir)/m4/lib-prefix.m4 \ + $(top_srcdir)/m4/libcurl.m4 $(top_srcdir)/m4/libgcrypt.m4 \ + $(top_srcdir)/m4/libtool.m4 $(top_srcdir)/m4/libunistring.m4 \ + $(top_srcdir)/m4/ltdl.m4 $(top_srcdir)/m4/ltoptions.m4 \ + $(top_srcdir)/m4/ltsugar.m4 $(top_srcdir)/m4/ltversion.m4 \ + $(top_srcdir)/m4/lt~obsolete.m4 $(top_srcdir)/m4/nls.m4 \ + $(top_srcdir)/m4/pkg.m4 $(top_srcdir)/m4/po.m4 \ $(top_srcdir)/m4/progtest.m4 $(top_srcdir)/acinclude.m4 \ $(top_srcdir)/configure.ac am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ @@ -80,29 +98,31 @@ am__nobase_list = $(am__nobase_strip_setup); \ am__base_list = \ sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \ sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g' +am__uninstall_files_from_dir = { \ + test -z "$$files" \ + || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \ + || { echo " ( cd '$$dir' && rm -f" $$files ")"; \ + $(am__cd) "$$dir" && rm -f $$files; }; \ + } am__installdirs = "$(DESTDIR)$(libdir)" "$(DESTDIR)$(plugindir)" \ "$(DESTDIR)$(pkgcfgdir)" LTLIBRARIES = $(lib_LTLIBRARIES) $(plugin_LTLIBRARIES) am__DEPENDENCIES_1 = -libgnunet_plugin_datacache_mysql_la_DEPENDENCIES = \ +libgnunet_plugin_datacache_heap_la_DEPENDENCIES = \ $(top_builddir)/src/statistics/libgnunetstatistics.la \ - $(top_builddir)/src/mysql/libgnunetmysql.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(am__DEPENDENCIES_1) $(am__DEPENDENCIES_1) -am_libgnunet_plugin_datacache_mysql_la_OBJECTS = \ - libgnunet_plugin_datacache_mysql_la-plugin_datacache_mysql.lo -libgnunet_plugin_datacache_mysql_la_OBJECTS = \ - $(am_libgnunet_plugin_datacache_mysql_la_OBJECTS) -AM_V_lt = $(am__v_lt_$(V)) -am__v_lt_ = $(am__v_lt_$(AM_DEFAULT_VERBOSITY)) +am_libgnunet_plugin_datacache_heap_la_OBJECTS = \ + plugin_datacache_heap.lo +libgnunet_plugin_datacache_heap_la_OBJECTS = \ + $(am_libgnunet_plugin_datacache_heap_la_OBJECTS) +AM_V_lt = $(am__v_lt_@AM_V@) +am__v_lt_ = $(am__v_lt_@AM_DEFAULT_V@) am__v_lt_0 = --silent -libgnunet_plugin_datacache_mysql_la_LINK = $(LIBTOOL) $(AM_V_lt) \ +libgnunet_plugin_datacache_heap_la_LINK = $(LIBTOOL) $(AM_V_lt) \ --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link \ $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ - $(libgnunet_plugin_datacache_mysql_la_LDFLAGS) $(LDFLAGS) -o \ - $@ -@HAVE_MYSQL_TRUE@am_libgnunet_plugin_datacache_mysql_la_rpath = \ -@HAVE_MYSQL_TRUE@ -rpath $(plugindir) + $(libgnunet_plugin_datacache_heap_la_LDFLAGS) $(LDFLAGS) -o $@ libgnunet_plugin_datacache_postgres_la_DEPENDENCIES = \ $(top_builddir)/src/postgres/libgnunetpostgres.la \ $(top_builddir)/src/statistics/libgnunetstatistics.la \ @@ -121,7 +141,7 @@ libgnunet_plugin_datacache_postgres_la_LINK = $(LIBTOOL) $(AM_V_lt) \ libgnunet_plugin_datacache_sqlite_la_DEPENDENCIES = \ $(top_builddir)/src/statistics/libgnunetstatistics.la \ $(top_builddir)/src/util/libgnunetutil.la \ - $(am__DEPENDENCIES_1) + $(am__DEPENDENCIES_1) $(am__DEPENDENCIES_1) am_libgnunet_plugin_datacache_sqlite_la_OBJECTS = \ plugin_datacache_sqlite.lo libgnunet_plugin_datacache_sqlite_la_OBJECTS = \ @@ -135,7 +155,7 @@ libgnunet_plugin_datacache_sqlite_la_LINK = $(LIBTOOL) $(AM_V_lt) \ @HAVE_SQLITE_TRUE@ -rpath $(plugindir) libgnunet_plugin_datacache_template_la_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la \ - $(am__DEPENDENCIES_1) + $(am__DEPENDENCIES_1) $(am__DEPENDENCIES_1) am_libgnunet_plugin_datacache_template_la_OBJECTS = \ plugin_datacache_template.lo libgnunet_plugin_datacache_template_la_OBJECTS = \ @@ -159,46 +179,50 @@ libgnunetdatacache_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ @HAVE_SQLITE_TRUE@am__EXEEXT_2 = test_datacache_sqlite$(EXEEXT) \ @HAVE_SQLITE_TRUE@ test_datacache_quota_sqlite$(EXEEXT) \ @HAVE_SQLITE_TRUE@ $(am__EXEEXT_1) -@HAVE_BENCHMARKS_TRUE@@HAVE_MYSQL_TRUE@am__EXEEXT_3 = perf_datacache_mysql$(EXEEXT) -@HAVE_MYSQL_TRUE@am__EXEEXT_4 = test_datacache_mysql$(EXEEXT) \ -@HAVE_MYSQL_TRUE@ test_datacache_quota_mysql$(EXEEXT) \ -@HAVE_MYSQL_TRUE@ $(am__EXEEXT_3) +@HAVE_BENCHMARKS_TRUE@am__EXEEXT_3 = perf_datacache_heap$(EXEEXT) +am__EXEEXT_4 = test_datacache_heap$(EXEEXT) \ + test_datacache_quota_heap$(EXEEXT) $(am__EXEEXT_3) @HAVE_BENCHMARKS_TRUE@@HAVE_POSTGRES_TRUE@am__EXEEXT_5 = perf_datacache_postgres$(EXEEXT) @HAVE_POSTGRES_TRUE@am__EXEEXT_6 = test_datacache_postgres$(EXEEXT) \ @HAVE_POSTGRES_TRUE@ test_datacache_quota_postgres$(EXEEXT) \ @HAVE_POSTGRES_TRUE@ $(am__EXEEXT_5) -am_perf_datacache_mysql_OBJECTS = perf_datacache.$(OBJEXT) -perf_datacache_mysql_OBJECTS = $(am_perf_datacache_mysql_OBJECTS) -perf_datacache_mysql_DEPENDENCIES = \ +am_perf_datacache_heap_OBJECTS = perf_datacache.$(OBJEXT) +perf_datacache_heap_OBJECTS = $(am_perf_datacache_heap_OBJECTS) +perf_datacache_heap_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/datacache/libgnunetdatacache.la \ $(top_builddir)/src/util/libgnunetutil.la am_perf_datacache_postgres_OBJECTS = perf_datacache.$(OBJEXT) perf_datacache_postgres_OBJECTS = \ $(am_perf_datacache_postgres_OBJECTS) perf_datacache_postgres_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/datacache/libgnunetdatacache.la \ $(top_builddir)/src/util/libgnunetutil.la am_perf_datacache_sqlite_OBJECTS = perf_datacache.$(OBJEXT) perf_datacache_sqlite_OBJECTS = $(am_perf_datacache_sqlite_OBJECTS) perf_datacache_sqlite_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/datacache/libgnunetdatacache.la \ $(top_builddir)/src/util/libgnunetutil.la -am_test_datacache_mysql_OBJECTS = test_datacache.$(OBJEXT) -test_datacache_mysql_OBJECTS = $(am_test_datacache_mysql_OBJECTS) -test_datacache_mysql_DEPENDENCIES = \ +am_test_datacache_heap_OBJECTS = test_datacache.$(OBJEXT) +test_datacache_heap_OBJECTS = $(am_test_datacache_heap_OBJECTS) +test_datacache_heap_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/datacache/libgnunetdatacache.la \ $(top_builddir)/src/util/libgnunetutil.la am_test_datacache_postgres_OBJECTS = test_datacache.$(OBJEXT) test_datacache_postgres_OBJECTS = \ $(am_test_datacache_postgres_OBJECTS) test_datacache_postgres_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/datacache/libgnunetdatacache.la \ $(top_builddir)/src/util/libgnunetutil.la -am_test_datacache_quota_mysql_OBJECTS = \ - test_datacache_quota.$(OBJEXT) -test_datacache_quota_mysql_OBJECTS = \ - $(am_test_datacache_quota_mysql_OBJECTS) -test_datacache_quota_mysql_DEPENDENCIES = \ +am_test_datacache_quota_heap_OBJECTS = test_datacache_quota.$(OBJEXT) +test_datacache_quota_heap_OBJECTS = \ + $(am_test_datacache_quota_heap_OBJECTS) +test_datacache_quota_heap_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/datacache/libgnunetdatacache.la \ $(top_builddir)/src/util/libgnunetutil.la am_test_datacache_quota_postgres_OBJECTS = \ @@ -206,6 +230,7 @@ am_test_datacache_quota_postgres_OBJECTS = \ test_datacache_quota_postgres_OBJECTS = \ $(am_test_datacache_quota_postgres_OBJECTS) test_datacache_quota_postgres_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/datacache/libgnunetdatacache.la \ $(top_builddir)/src/util/libgnunetutil.la am_test_datacache_quota_sqlite_OBJECTS = \ @@ -213,11 +238,13 @@ am_test_datacache_quota_sqlite_OBJECTS = \ test_datacache_quota_sqlite_OBJECTS = \ $(am_test_datacache_quota_sqlite_OBJECTS) test_datacache_quota_sqlite_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/datacache/libgnunetdatacache.la \ $(top_builddir)/src/util/libgnunetutil.la am_test_datacache_sqlite_OBJECTS = test_datacache.$(OBJEXT) test_datacache_sqlite_OBJECTS = $(am_test_datacache_sqlite_OBJECTS) test_datacache_sqlite_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/datacache/libgnunetdatacache.la \ $(top_builddir)/src/util/libgnunetutil.la DEFAULT_INCLUDES = -I.@am__isrc@ -I$(top_builddir) @@ -230,50 +257,55 @@ LTCOMPILE = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) \ $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) \ $(AM_CFLAGS) $(CFLAGS) -AM_V_CC = $(am__v_CC_$(V)) -am__v_CC_ = $(am__v_CC_$(AM_DEFAULT_VERBOSITY)) +AM_V_CC = $(am__v_CC_@AM_V@) +am__v_CC_ = $(am__v_CC_@AM_DEFAULT_V@) am__v_CC_0 = @echo " CC " $@; -AM_V_at = $(am__v_at_$(V)) -am__v_at_ = $(am__v_at_$(AM_DEFAULT_VERBOSITY)) +AM_V_at = $(am__v_at_@AM_V@) +am__v_at_ = $(am__v_at_@AM_DEFAULT_V@) am__v_at_0 = @ CCLD = $(CC) LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ $(AM_LDFLAGS) $(LDFLAGS) -o $@ -AM_V_CCLD = $(am__v_CCLD_$(V)) -am__v_CCLD_ = $(am__v_CCLD_$(AM_DEFAULT_VERBOSITY)) +AM_V_CCLD = $(am__v_CCLD_@AM_V@) +am__v_CCLD_ = $(am__v_CCLD_@AM_DEFAULT_V@) am__v_CCLD_0 = @echo " CCLD " $@; -AM_V_GEN = $(am__v_GEN_$(V)) -am__v_GEN_ = $(am__v_GEN_$(AM_DEFAULT_VERBOSITY)) +AM_V_GEN = $(am__v_GEN_@AM_V@) +am__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@) am__v_GEN_0 = @echo " GEN " $@; -SOURCES = $(libgnunet_plugin_datacache_mysql_la_SOURCES) \ +SOURCES = $(libgnunet_plugin_datacache_heap_la_SOURCES) \ $(libgnunet_plugin_datacache_postgres_la_SOURCES) \ $(libgnunet_plugin_datacache_sqlite_la_SOURCES) \ $(libgnunet_plugin_datacache_template_la_SOURCES) \ $(libgnunetdatacache_la_SOURCES) \ - $(perf_datacache_mysql_SOURCES) \ + $(perf_datacache_heap_SOURCES) \ $(perf_datacache_postgres_SOURCES) \ $(perf_datacache_sqlite_SOURCES) \ - $(test_datacache_mysql_SOURCES) \ + $(test_datacache_heap_SOURCES) \ $(test_datacache_postgres_SOURCES) \ - $(test_datacache_quota_mysql_SOURCES) \ + $(test_datacache_quota_heap_SOURCES) \ $(test_datacache_quota_postgres_SOURCES) \ $(test_datacache_quota_sqlite_SOURCES) \ $(test_datacache_sqlite_SOURCES) -DIST_SOURCES = $(libgnunet_plugin_datacache_mysql_la_SOURCES) \ +DIST_SOURCES = $(libgnunet_plugin_datacache_heap_la_SOURCES) \ $(libgnunet_plugin_datacache_postgres_la_SOURCES) \ $(libgnunet_plugin_datacache_sqlite_la_SOURCES) \ $(libgnunet_plugin_datacache_template_la_SOURCES) \ $(libgnunetdatacache_la_SOURCES) \ - $(perf_datacache_mysql_SOURCES) \ + $(perf_datacache_heap_SOURCES) \ $(perf_datacache_postgres_SOURCES) \ $(perf_datacache_sqlite_SOURCES) \ - $(test_datacache_mysql_SOURCES) \ + $(test_datacache_heap_SOURCES) \ $(test_datacache_postgres_SOURCES) \ - $(test_datacache_quota_mysql_SOURCES) \ + $(test_datacache_quota_heap_SOURCES) \ $(test_datacache_quota_postgres_SOURCES) \ $(test_datacache_quota_sqlite_SOURCES) \ $(test_datacache_sqlite_SOURCES) +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac DATA = $(dist_pkgcfg_DATA) ETAGS = etags CTAGS = ctags @@ -315,6 +347,10 @@ EXEEXT = @EXEEXT@ EXT_LIBS = @EXT_LIBS@ EXT_LIB_PATH = @EXT_LIB_PATH@ FGREP = @FGREP@ +GLIB_CFLAGS = @GLIB_CFLAGS@ +GLIB_GENMARSHAL = @GLIB_GENMARSHAL@ +GLIB_LIBS = @GLIB_LIBS@ +GLIB_MKENUMS = @GLIB_MKENUMS@ GMSGFMT = @GMSGFMT@ GMSGFMT_015 = @GMSGFMT_015@ GNUNETDNS_GROUP = @GNUNETDNS_GROUP@ @@ -325,6 +361,7 @@ GN_LIBINTL = @GN_LIBINTL@ GN_LIB_LDFLAGS = @GN_LIB_LDFLAGS@ GN_PLUGIN_LDFLAGS = @GN_PLUGIN_LDFLAGS@ GN_USER_HOME_DIR = @GN_USER_HOME_DIR@ +GOBJECT_QUERY = @GOBJECT_QUERY@ GREP = @GREP@ HAVE_LIBUNISTRING = @HAVE_LIBUNISTRING@ INCLTDL = @INCLTDL@ @@ -347,6 +384,8 @@ LIBCURL_CPPFLAGS = @LIBCURL_CPPFLAGS@ LIBGCRYPT_CFLAGS = @LIBGCRYPT_CFLAGS@ LIBGCRYPT_CONFIG = @LIBGCRYPT_CONFIG@ LIBGCRYPT_LIBS = @LIBGCRYPT_LIBS@ +LIBGTOP_CFLAGS = @LIBGTOP_CFLAGS@ +LIBGTOP_LIBS = @LIBGTOP_LIBS@ LIBICONV = @LIBICONV@ LIBINTL = @LIBINTL@ LIBLTDL = @LIBLTDL@ @@ -368,6 +407,7 @@ LT_CONFIG_H = @LT_CONFIG_H@ LT_DLLOADERS = @LT_DLLOADERS@ LT_DLPREOPEN = @LT_DLPREOPEN@ MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ MKDIR_P = @MKDIR_P@ MONKEYPREFIX = @MONKEYPREFIX@ MSGFMT = @MSGFMT@ @@ -377,6 +417,7 @@ MYSQL_CPPFLAGS = @MYSQL_CPPFLAGS@ MYSQL_LDFLAGS = @MYSQL_LDFLAGS@ NM = @NM@ NMEDIT = @NMEDIT@ +NSS_DIR = @NSS_DIR@ OBJC = @OBJC@ OBJCDEPMODE = @OBJCDEPMODE@ OBJCFLAGS = @OBJCFLAGS@ @@ -392,6 +433,7 @@ PACKAGE_TARNAME = @PACKAGE_TARNAME@ PACKAGE_URL = @PACKAGE_URL@ PACKAGE_VERSION = @PACKAGE_VERSION@ PATH_SEPARATOR = @PATH_SEPARATOR@ +PKG_CONFIG = @PKG_CONFIG@ POSTGRES_CPPFLAGS = @POSTGRES_CPPFLAGS@ POSTGRES_LDFLAGS = @POSTGRES_LDFLAGS@ POSUB = @POSUB@ @@ -423,6 +465,7 @@ abs_builddir = @abs_builddir@ abs_srcdir = @abs_srcdir@ abs_top_builddir = @abs_top_builddir@ abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ ac_ct_CC = @ac_ct_CC@ ac_ct_CXX = @ac_ct_CXX@ ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ @@ -445,6 +488,7 @@ datarootdir = @datarootdir@ docdir = @docdir@ dvidir = @dvidir@ exec_prefix = @exec_prefix@ +gitcommand = @gitcommand@ host = @host@ host_alias = @host_alias@ host_cpu = @host_cpu@ @@ -458,7 +502,6 @@ libdir = @libdir@ libexecdir = @libexecdir@ localedir = @localedir@ localstatedir = @localstatedir@ -lt_ECHO = @lt_ECHO@ ltdl_LIBOBJS = @ltdl_LIBOBJS@ ltdl_LTLIBOBJS = @ltdl_LTLIBOBJS@ mandir = @mandir@ @@ -476,6 +519,7 @@ sbindir = @sbindir@ sharedstatedir = @sharedstatedir@ srcdir = @srcdir@ subdirs = @subdirs@ +svnversioncommand = @svnversioncommand@ sys_symbol_underscore = @sys_symbol_underscore@ sysconfdir = @sysconfdir@ target = @target@ @@ -496,7 +540,6 @@ dist_pkgcfg_DATA = \ @USE_COVERAGE_TRUE@AM_CFLAGS = --coverage -O0 @USE_COVERAGE_TRUE@XLIBS = -lgcov @HAVE_SQLITE_TRUE@SQLITE_PLUGIN = libgnunet_plugin_datacache_sqlite.la -@HAVE_MYSQL_TRUE@MYSQL_PLUGIN = libgnunet_plugin_datacache_mysql.la @HAVE_POSTGRES_TRUE@POSTGRES_PLUGIN = libgnunet_plugin_datacache_postgres.la lib_LTLIBRARIES = \ libgnunetdatacache.la @@ -515,8 +558,8 @@ libgnunetdatacache_la_LDFLAGS = \ plugin_LTLIBRARIES = \ $(SQLITE_PLUGIN) \ - $(MYSQL_PLUGIN) \ $(POSTGRES_PLUGIN) \ + libgnunet_plugin_datacache_heap.la \ libgnunet_plugin_datacache_template.la libgnunet_plugin_datacache_sqlite_la_SOURCES = \ @@ -524,25 +567,22 @@ libgnunet_plugin_datacache_sqlite_la_SOURCES = \ libgnunet_plugin_datacache_sqlite_la_LIBADD = \ $(top_builddir)/src/statistics/libgnunetstatistics.la \ - $(top_builddir)/src/util/libgnunetutil.la $(XLIBS) -lsqlite3 + $(top_builddir)/src/util/libgnunetutil.la $(XLIBS) -lsqlite3 \ + $(LTLIBINTL) libgnunet_plugin_datacache_sqlite_la_LDFLAGS = \ $(GN_PLUGIN_LDFLAGS) -libgnunet_plugin_datacache_mysql_la_SOURCES = \ - plugin_datacache_mysql.c +libgnunet_plugin_datacache_heap_la_SOURCES = \ + plugin_datacache_heap.c -libgnunet_plugin_datacache_mysql_la_LIBADD = \ +libgnunet_plugin_datacache_heap_la_LIBADD = \ $(top_builddir)/src/statistics/libgnunetstatistics.la \ - $(top_builddir)/src/mysql/libgnunetmysql.la \ - $(top_builddir)/src/util/libgnunetutil.la \ - $(GN_PLUGIN_LDFLAGS) $(MYSQL_LDFLAGS) -lmysqlclient + $(top_builddir)/src/util/libgnunetutil.la $(XLIBS) \ + $(LTLIBINTL) -libgnunet_plugin_datacache_mysql_la_CPPFLAGS = \ - $(MYSQL_CPPFLAGS) - -libgnunet_plugin_datacache_mysql_la_LDFLAGS = \ - $(GN_PLUGIN_LDFLAGS) $(MYSQL_LDFLAGS) -lmysqlclient +libgnunet_plugin_datacache_heap_la_LDFLAGS = \ + $(GN_PLUGIN_LDFLAGS) libgnunet_plugin_datacache_postgres_la_SOURCES = \ plugin_datacache_postgres.c @@ -563,7 +603,8 @@ libgnunet_plugin_datacache_template_la_SOURCES = \ plugin_datacache_template.c libgnunet_plugin_datacache_template_la_LIBADD = \ - $(top_builddir)/src/util/libgnunetutil.la $(XLIBS) + $(top_builddir)/src/util/libgnunetutil.la $(XLIBS) \ + $(LTLIBINTL) libgnunet_plugin_datacache_template_la_LDFLAGS = \ $(GN_PLUGIN_LDFLAGS) @@ -576,13 +617,13 @@ libgnunet_plugin_datacache_template_la_LDFLAGS = \ @HAVE_SQLITE_TRUE@ test_datacache_quota_sqlite \ @HAVE_SQLITE_TRUE@ $(SQLITE_BENCHMARKS) -@HAVE_BENCHMARKS_TRUE@@HAVE_MYSQL_TRUE@MYSQL_BENCHMARKS = \ -@HAVE_BENCHMARKS_TRUE@@HAVE_MYSQL_TRUE@ perf_datacache_mysql +@HAVE_BENCHMARKS_TRUE@HEAP_BENCHMARKS = \ +@HAVE_BENCHMARKS_TRUE@ perf_datacache_heap -@HAVE_MYSQL_TRUE@MYSQL_TESTS = \ -@HAVE_MYSQL_TRUE@ test_datacache_mysql \ -@HAVE_MYSQL_TRUE@ test_datacache_quota_mysql \ -@HAVE_MYSQL_TRUE@ $(MYSQL_BENCHMARKS) +HEAP_TESTS = \ + test_datacache_heap \ + test_datacache_quota_heap \ + $(HEAP_BENCHMARKS) @HAVE_BENCHMARKS_TRUE@@HAVE_POSTGRES_TRUE@POSTGRES_BENCHMARKS = \ @HAVE_BENCHMARKS_TRUE@@HAVE_POSTGRES_TRUE@ perf_datacache_postgres @@ -597,6 +638,7 @@ test_datacache_sqlite_SOURCES = \ test_datacache.c test_datacache_sqlite_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/datacache/libgnunetdatacache.la \ $(top_builddir)/src/util/libgnunetutil.la @@ -604,6 +646,7 @@ test_datacache_quota_sqlite_SOURCES = \ test_datacache_quota.c test_datacache_quota_sqlite_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/datacache/libgnunetdatacache.la \ $(top_builddir)/src/util/libgnunetutil.la @@ -611,27 +654,31 @@ perf_datacache_sqlite_SOURCES = \ perf_datacache.c perf_datacache_sqlite_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/datacache/libgnunetdatacache.la \ $(top_builddir)/src/util/libgnunetutil.la -test_datacache_mysql_SOURCES = \ +test_datacache_heap_SOURCES = \ test_datacache.c -test_datacache_mysql_LDADD = \ +test_datacache_heap_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/datacache/libgnunetdatacache.la \ $(top_builddir)/src/util/libgnunetutil.la -test_datacache_quota_mysql_SOURCES = \ +test_datacache_quota_heap_SOURCES = \ test_datacache_quota.c -test_datacache_quota_mysql_LDADD = \ +test_datacache_quota_heap_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/datacache/libgnunetdatacache.la \ $(top_builddir)/src/util/libgnunetutil.la -perf_datacache_mysql_SOURCES = \ +perf_datacache_heap_SOURCES = \ perf_datacache.c -perf_datacache_mysql_LDADD = \ +perf_datacache_heap_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/datacache/libgnunetdatacache.la \ $(top_builddir)/src/util/libgnunetutil.la @@ -639,6 +686,7 @@ test_datacache_postgres_SOURCES = \ test_datacache.c test_datacache_postgres_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/datacache/libgnunetdatacache.la \ $(top_builddir)/src/util/libgnunetutil.la @@ -646,6 +694,7 @@ test_datacache_quota_postgres_SOURCES = \ test_datacache_quota.c test_datacache_quota_postgres_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/datacache/libgnunetdatacache.la \ $(top_builddir)/src/util/libgnunetutil.la @@ -653,14 +702,15 @@ perf_datacache_postgres_SOURCES = \ perf_datacache.c perf_datacache_postgres_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/datacache/libgnunetdatacache.la \ $(top_builddir)/src/util/libgnunetutil.la EXTRA_DIST = \ test_datacache_data_sqlite.conf \ perf_datacache_data_sqlite.conf \ - test_datacache_data_mysql.conf \ - perf_datacache_data_mysql.conf \ + test_datacache_data_heap.conf \ + perf_datacache_data_heap.conf \ test_datacache_data_postgres.conf \ perf_datacache_data_postgres.conf @@ -700,7 +750,6 @@ $(ACLOCAL_M4): $(am__aclocal_m4_deps) $(am__aclocal_m4_deps): install-libLTLIBRARIES: $(lib_LTLIBRARIES) @$(NORMAL_INSTALL) - test -z "$(libdir)" || $(MKDIR_P) "$(DESTDIR)$(libdir)" @list='$(lib_LTLIBRARIES)'; test -n "$(libdir)" || list=; \ list2=; for p in $$list; do \ if test -f $$p; then \ @@ -708,6 +757,8 @@ install-libLTLIBRARIES: $(lib_LTLIBRARIES) else :; fi; \ done; \ test -z "$$list2" || { \ + echo " $(MKDIR_P) '$(DESTDIR)$(libdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libdir)" || exit 1; \ echo " $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 '$(DESTDIR)$(libdir)'"; \ $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 "$(DESTDIR)$(libdir)"; \ } @@ -731,7 +782,6 @@ clean-libLTLIBRARIES: done install-pluginLTLIBRARIES: $(plugin_LTLIBRARIES) @$(NORMAL_INSTALL) - test -z "$(plugindir)" || $(MKDIR_P) "$(DESTDIR)$(plugindir)" @list='$(plugin_LTLIBRARIES)'; test -n "$(plugindir)" || list=; \ list2=; for p in $$list; do \ if test -f $$p; then \ @@ -739,6 +789,8 @@ install-pluginLTLIBRARIES: $(plugin_LTLIBRARIES) else :; fi; \ done; \ test -z "$$list2" || { \ + echo " $(MKDIR_P) '$(DESTDIR)$(plugindir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(plugindir)" || exit 1; \ echo " $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 '$(DESTDIR)$(plugindir)'"; \ $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 "$(DESTDIR)$(plugindir)"; \ } @@ -760,15 +812,15 @@ clean-pluginLTLIBRARIES: echo "rm -f \"$${dir}/so_locations\""; \ rm -f "$${dir}/so_locations"; \ done -libgnunet_plugin_datacache_mysql.la: $(libgnunet_plugin_datacache_mysql_la_OBJECTS) $(libgnunet_plugin_datacache_mysql_la_DEPENDENCIES) - $(AM_V_CCLD)$(libgnunet_plugin_datacache_mysql_la_LINK) $(am_libgnunet_plugin_datacache_mysql_la_rpath) $(libgnunet_plugin_datacache_mysql_la_OBJECTS) $(libgnunet_plugin_datacache_mysql_la_LIBADD) $(LIBS) -libgnunet_plugin_datacache_postgres.la: $(libgnunet_plugin_datacache_postgres_la_OBJECTS) $(libgnunet_plugin_datacache_postgres_la_DEPENDENCIES) +libgnunet_plugin_datacache_heap.la: $(libgnunet_plugin_datacache_heap_la_OBJECTS) $(libgnunet_plugin_datacache_heap_la_DEPENDENCIES) $(EXTRA_libgnunet_plugin_datacache_heap_la_DEPENDENCIES) + $(AM_V_CCLD)$(libgnunet_plugin_datacache_heap_la_LINK) -rpath $(plugindir) $(libgnunet_plugin_datacache_heap_la_OBJECTS) $(libgnunet_plugin_datacache_heap_la_LIBADD) $(LIBS) +libgnunet_plugin_datacache_postgres.la: $(libgnunet_plugin_datacache_postgres_la_OBJECTS) $(libgnunet_plugin_datacache_postgres_la_DEPENDENCIES) $(EXTRA_libgnunet_plugin_datacache_postgres_la_DEPENDENCIES) $(AM_V_CCLD)$(libgnunet_plugin_datacache_postgres_la_LINK) $(am_libgnunet_plugin_datacache_postgres_la_rpath) $(libgnunet_plugin_datacache_postgres_la_OBJECTS) $(libgnunet_plugin_datacache_postgres_la_LIBADD) $(LIBS) -libgnunet_plugin_datacache_sqlite.la: $(libgnunet_plugin_datacache_sqlite_la_OBJECTS) $(libgnunet_plugin_datacache_sqlite_la_DEPENDENCIES) +libgnunet_plugin_datacache_sqlite.la: $(libgnunet_plugin_datacache_sqlite_la_OBJECTS) $(libgnunet_plugin_datacache_sqlite_la_DEPENDENCIES) $(EXTRA_libgnunet_plugin_datacache_sqlite_la_DEPENDENCIES) $(AM_V_CCLD)$(libgnunet_plugin_datacache_sqlite_la_LINK) $(am_libgnunet_plugin_datacache_sqlite_la_rpath) $(libgnunet_plugin_datacache_sqlite_la_OBJECTS) $(libgnunet_plugin_datacache_sqlite_la_LIBADD) $(LIBS) -libgnunet_plugin_datacache_template.la: $(libgnunet_plugin_datacache_template_la_OBJECTS) $(libgnunet_plugin_datacache_template_la_DEPENDENCIES) +libgnunet_plugin_datacache_template.la: $(libgnunet_plugin_datacache_template_la_OBJECTS) $(libgnunet_plugin_datacache_template_la_DEPENDENCIES) $(EXTRA_libgnunet_plugin_datacache_template_la_DEPENDENCIES) $(AM_V_CCLD)$(libgnunet_plugin_datacache_template_la_LINK) -rpath $(plugindir) $(libgnunet_plugin_datacache_template_la_OBJECTS) $(libgnunet_plugin_datacache_template_la_LIBADD) $(LIBS) -libgnunetdatacache.la: $(libgnunetdatacache_la_OBJECTS) $(libgnunetdatacache_la_DEPENDENCIES) +libgnunetdatacache.la: $(libgnunetdatacache_la_OBJECTS) $(libgnunetdatacache_la_DEPENDENCIES) $(EXTRA_libgnunetdatacache_la_DEPENDENCIES) $(AM_V_CCLD)$(libgnunetdatacache_la_LINK) -rpath $(libdir) $(libgnunetdatacache_la_OBJECTS) $(libgnunetdatacache_la_LIBADD) $(LIBS) clean-checkPROGRAMS: @@ -779,31 +831,31 @@ clean-checkPROGRAMS: list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ echo " rm -f" $$list; \ rm -f $$list -perf_datacache_mysql$(EXEEXT): $(perf_datacache_mysql_OBJECTS) $(perf_datacache_mysql_DEPENDENCIES) - @rm -f perf_datacache_mysql$(EXEEXT) - $(AM_V_CCLD)$(LINK) $(perf_datacache_mysql_OBJECTS) $(perf_datacache_mysql_LDADD) $(LIBS) -perf_datacache_postgres$(EXEEXT): $(perf_datacache_postgres_OBJECTS) $(perf_datacache_postgres_DEPENDENCIES) +perf_datacache_heap$(EXEEXT): $(perf_datacache_heap_OBJECTS) $(perf_datacache_heap_DEPENDENCIES) $(EXTRA_perf_datacache_heap_DEPENDENCIES) + @rm -f perf_datacache_heap$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(perf_datacache_heap_OBJECTS) $(perf_datacache_heap_LDADD) $(LIBS) +perf_datacache_postgres$(EXEEXT): $(perf_datacache_postgres_OBJECTS) $(perf_datacache_postgres_DEPENDENCIES) $(EXTRA_perf_datacache_postgres_DEPENDENCIES) @rm -f perf_datacache_postgres$(EXEEXT) $(AM_V_CCLD)$(LINK) $(perf_datacache_postgres_OBJECTS) $(perf_datacache_postgres_LDADD) $(LIBS) -perf_datacache_sqlite$(EXEEXT): $(perf_datacache_sqlite_OBJECTS) $(perf_datacache_sqlite_DEPENDENCIES) +perf_datacache_sqlite$(EXEEXT): $(perf_datacache_sqlite_OBJECTS) $(perf_datacache_sqlite_DEPENDENCIES) $(EXTRA_perf_datacache_sqlite_DEPENDENCIES) @rm -f perf_datacache_sqlite$(EXEEXT) $(AM_V_CCLD)$(LINK) $(perf_datacache_sqlite_OBJECTS) $(perf_datacache_sqlite_LDADD) $(LIBS) -test_datacache_mysql$(EXEEXT): $(test_datacache_mysql_OBJECTS) $(test_datacache_mysql_DEPENDENCIES) - @rm -f test_datacache_mysql$(EXEEXT) - $(AM_V_CCLD)$(LINK) $(test_datacache_mysql_OBJECTS) $(test_datacache_mysql_LDADD) $(LIBS) -test_datacache_postgres$(EXEEXT): $(test_datacache_postgres_OBJECTS) $(test_datacache_postgres_DEPENDENCIES) +test_datacache_heap$(EXEEXT): $(test_datacache_heap_OBJECTS) $(test_datacache_heap_DEPENDENCIES) $(EXTRA_test_datacache_heap_DEPENDENCIES) + @rm -f test_datacache_heap$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_datacache_heap_OBJECTS) $(test_datacache_heap_LDADD) $(LIBS) +test_datacache_postgres$(EXEEXT): $(test_datacache_postgres_OBJECTS) $(test_datacache_postgres_DEPENDENCIES) $(EXTRA_test_datacache_postgres_DEPENDENCIES) @rm -f test_datacache_postgres$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_datacache_postgres_OBJECTS) $(test_datacache_postgres_LDADD) $(LIBS) -test_datacache_quota_mysql$(EXEEXT): $(test_datacache_quota_mysql_OBJECTS) $(test_datacache_quota_mysql_DEPENDENCIES) - @rm -f test_datacache_quota_mysql$(EXEEXT) - $(AM_V_CCLD)$(LINK) $(test_datacache_quota_mysql_OBJECTS) $(test_datacache_quota_mysql_LDADD) $(LIBS) -test_datacache_quota_postgres$(EXEEXT): $(test_datacache_quota_postgres_OBJECTS) $(test_datacache_quota_postgres_DEPENDENCIES) +test_datacache_quota_heap$(EXEEXT): $(test_datacache_quota_heap_OBJECTS) $(test_datacache_quota_heap_DEPENDENCIES) $(EXTRA_test_datacache_quota_heap_DEPENDENCIES) + @rm -f test_datacache_quota_heap$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_datacache_quota_heap_OBJECTS) $(test_datacache_quota_heap_LDADD) $(LIBS) +test_datacache_quota_postgres$(EXEEXT): $(test_datacache_quota_postgres_OBJECTS) $(test_datacache_quota_postgres_DEPENDENCIES) $(EXTRA_test_datacache_quota_postgres_DEPENDENCIES) @rm -f test_datacache_quota_postgres$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_datacache_quota_postgres_OBJECTS) $(test_datacache_quota_postgres_LDADD) $(LIBS) -test_datacache_quota_sqlite$(EXEEXT): $(test_datacache_quota_sqlite_OBJECTS) $(test_datacache_quota_sqlite_DEPENDENCIES) +test_datacache_quota_sqlite$(EXEEXT): $(test_datacache_quota_sqlite_OBJECTS) $(test_datacache_quota_sqlite_DEPENDENCIES) $(EXTRA_test_datacache_quota_sqlite_DEPENDENCIES) @rm -f test_datacache_quota_sqlite$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_datacache_quota_sqlite_OBJECTS) $(test_datacache_quota_sqlite_LDADD) $(LIBS) -test_datacache_sqlite$(EXEEXT): $(test_datacache_sqlite_OBJECTS) $(test_datacache_sqlite_DEPENDENCIES) +test_datacache_sqlite$(EXEEXT): $(test_datacache_sqlite_OBJECTS) $(test_datacache_sqlite_DEPENDENCIES) $(EXTRA_test_datacache_sqlite_DEPENDENCIES) @rm -f test_datacache_sqlite$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_datacache_sqlite_OBJECTS) $(test_datacache_sqlite_LDADD) $(LIBS) @@ -814,9 +866,9 @@ distclean-compile: -rm -f *.tab.c @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/datacache.Plo@am__quote@ -@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libgnunet_plugin_datacache_mysql_la-plugin_datacache_mysql.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libgnunet_plugin_datacache_postgres_la-plugin_datacache_postgres.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/perf_datacache.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/plugin_datacache_heap.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/plugin_datacache_sqlite.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/plugin_datacache_template.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_datacache.Po@am__quote@ @@ -825,42 +877,30 @@ distclean-compile: .c.o: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c $< .c.obj: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'` @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c `$(CYGPATH_W) '$<'` +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c `$(CYGPATH_W) '$<'` .c.lo: @am__fastdepCC_TRUE@ $(AM_V_CC)$(LTCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LTCOMPILE) -c -o $@ $< - -libgnunet_plugin_datacache_mysql_la-plugin_datacache_mysql.lo: plugin_datacache_mysql.c -@am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(libgnunet_plugin_datacache_mysql_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT libgnunet_plugin_datacache_mysql_la-plugin_datacache_mysql.lo -MD -MP -MF $(DEPDIR)/libgnunet_plugin_datacache_mysql_la-plugin_datacache_mysql.Tpo -c -o libgnunet_plugin_datacache_mysql_la-plugin_datacache_mysql.lo `test -f 'plugin_datacache_mysql.c' || echo '$(srcdir)/'`plugin_datacache_mysql.c -@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/libgnunet_plugin_datacache_mysql_la-plugin_datacache_mysql.Tpo $(DEPDIR)/libgnunet_plugin_datacache_mysql_la-plugin_datacache_mysql.Plo -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='plugin_datacache_mysql.c' object='libgnunet_plugin_datacache_mysql_la-plugin_datacache_mysql.lo' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(libgnunet_plugin_datacache_mysql_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o libgnunet_plugin_datacache_mysql_la-plugin_datacache_mysql.lo `test -f 'plugin_datacache_mysql.c' || echo '$(srcdir)/'`plugin_datacache_mysql.c +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LTCOMPILE) -c -o $@ $< libgnunet_plugin_datacache_postgres_la-plugin_datacache_postgres.lo: plugin_datacache_postgres.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(libgnunet_plugin_datacache_postgres_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT libgnunet_plugin_datacache_postgres_la-plugin_datacache_postgres.lo -MD -MP -MF $(DEPDIR)/libgnunet_plugin_datacache_postgres_la-plugin_datacache_postgres.Tpo -c -o libgnunet_plugin_datacache_postgres_la-plugin_datacache_postgres.lo `test -f 'plugin_datacache_postgres.c' || echo '$(srcdir)/'`plugin_datacache_postgres.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/libgnunet_plugin_datacache_postgres_la-plugin_datacache_postgres.Tpo $(DEPDIR)/libgnunet_plugin_datacache_postgres_la-plugin_datacache_postgres.Plo -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='plugin_datacache_postgres.c' object='libgnunet_plugin_datacache_postgres_la-plugin_datacache_postgres.lo' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='plugin_datacache_postgres.c' object='libgnunet_plugin_datacache_postgres_la-plugin_datacache_postgres.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(libgnunet_plugin_datacache_postgres_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o libgnunet_plugin_datacache_postgres_la-plugin_datacache_postgres.lo `test -f 'plugin_datacache_postgres.c' || echo '$(srcdir)/'`plugin_datacache_postgres.c +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(libgnunet_plugin_datacache_postgres_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o libgnunet_plugin_datacache_postgres_la-plugin_datacache_postgres.lo `test -f 'plugin_datacache_postgres.c' || echo '$(srcdir)/'`plugin_datacache_postgres.c mostlyclean-libtool: -rm -f *.lo @@ -869,8 +909,11 @@ clean-libtool: -rm -rf .libs _libs install-dist_pkgcfgDATA: $(dist_pkgcfg_DATA) @$(NORMAL_INSTALL) - test -z "$(pkgcfgdir)" || $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" @list='$(dist_pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(pkgcfgdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" || exit 1; \ + fi; \ for p in $$list; do \ if test -f "$$p"; then d=; else d="$(srcdir)/"; fi; \ echo "$$d$$p"; \ @@ -884,9 +927,7 @@ uninstall-dist_pkgcfgDATA: @$(NORMAL_UNINSTALL) @list='$(dist_pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ files=`for p in $$list; do echo $$p; done | sed -e 's|^.*/||'`; \ - test -n "$$files" || exit 0; \ - echo " ( cd '$(DESTDIR)$(pkgcfgdir)' && rm -f" $$files ")"; \ - cd "$(DESTDIR)$(pkgcfgdir)" && rm -f $$files + dir='$(DESTDIR)$(pkgcfgdir)'; $(am__uninstall_files_from_dir) ID: $(HEADERS) $(SOURCES) $(LISP) $(TAGS_FILES) list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ @@ -1021,14 +1062,15 @@ check-TESTS: $(TESTS) fi; \ dashes=`echo "$$dashes" | sed s/./=/g`; \ if test "$$failed" -eq 0; then \ - echo "$$grn$$dashes"; \ + col="$$grn"; \ else \ - echo "$$red$$dashes"; \ + col="$$red"; \ fi; \ - echo "$$banner"; \ - test -z "$$skipped" || echo "$$skipped"; \ - test -z "$$report" || echo "$$report"; \ - echo "$$dashes$$std"; \ + echo "$${col}$$dashes$${std}"; \ + echo "$${col}$$banner$${std}"; \ + test -z "$$skipped" || echo "$${col}$$skipped$${std}"; \ + test -z "$$report" || echo "$${col}$$report$${std}"; \ + echo "$${col}$$dashes$${std}"; \ test "$$failed" -eq 0; \ else :; fi @@ -1081,10 +1123,15 @@ install-am: all-am installcheck: installcheck-am install-strip: - $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ - install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ - `test -z '$(STRIP)' || \ - echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi mostlyclean-generic: clean-generic: diff --git a/src/datacache/datacache.c b/src/datacache/datacache.c index b440af1..0cd6f88 100644 --- a/src/datacache/datacache.c +++ b/src/datacache/datacache.c @@ -103,7 +103,7 @@ struct GNUNET_DATACACHE_Handle * @param size number of bytes that were made available */ static void -env_delete_notify (void *cls, const GNUNET_HashCode * key, size_t size) +env_delete_notify (void *cls, const struct GNUNET_HashCode * key, size_t size) { struct GNUNET_DATACACHE_Handle *h = cls; @@ -112,7 +112,9 @@ env_delete_notify (void *cls, const GNUNET_HashCode * key, size_t size) GNUNET_assert (h->utilization >= size); h->utilization -= size; GNUNET_CONTAINER_bloomfilter_remove (h->filter, key); - GNUNET_STATISTICS_update (h->stats, gettext_noop ("# bytes stored"), -size, + GNUNET_STATISTICS_update (h->stats, gettext_noop ("# bytes stored"), - (long long) size, + GNUNET_NO); + GNUNET_STATISTICS_update (h->stats, gettext_noop ("# items stored"), -1, GNUNET_NO); } @@ -152,22 +154,24 @@ GNUNET_DATACACHE_create (const struct GNUNET_CONFIGURATION_Handle *cfg, bf_size = quota / 32; /* 8 bit per entry, 1 bit per 32 kb in DB */ ret = GNUNET_malloc (sizeof (struct GNUNET_DATACACHE_Handle)); - ret->bloom_name = GNUNET_DISK_mktemp ("gnunet-datacachebloom"); - if (NULL != ret->bloom_name) - { - ret->filter = GNUNET_CONTAINER_bloomfilter_load (ret->bloom_name, quota / 1024, /* 8 bit per entry in DB, expect 1k entries */ - 5); - } - if (NULL == ret->filter) + + if (GNUNET_YES != + GNUNET_CONFIGURATION_get_value_yesno (cfg, section, "DISABLE_BF")) { - ret->filter = GNUNET_CONTAINER_bloomfilter_init (NULL, bf_size, 5); /* approx. 3% false positives at max use */ - } - if (NULL == ret->filter) - { - GNUNET_free (name); - GNUNET_free (ret->bloom_name); - GNUNET_free (ret); - return NULL; + if (GNUNET_YES != + GNUNET_CONFIGURATION_get_value_yesno (cfg, section, "DISABLE_BF_RC")) + { + ret->bloom_name = GNUNET_DISK_mktemp ("gnunet-datacachebloom"); + } + if (NULL != ret->bloom_name) + { + ret->filter = GNUNET_CONTAINER_bloomfilter_load (ret->bloom_name, quota / 1024, /* 8 bit per entry in DB, expect 1k entries */ + 5); + } + if (NULL == ret->filter) + { + ret->filter = GNUNET_CONTAINER_bloomfilter_init (NULL, bf_size, 5); /* approx. 3% false positives at max use */ + } } ret->stats = GNUNET_STATISTICS_create ("datacache", cfg); ret->section = GNUNET_strdup (section); @@ -201,7 +205,7 @@ GNUNET_DATACACHE_create (const struct GNUNET_CONFIGURATION_Handle *cfg, void GNUNET_DATACACHE_destroy (struct GNUNET_DATACACHE_Handle *h) { - if (h->filter != NULL) + if (NULL != h->filter) GNUNET_CONTAINER_bloomfilter_free (h->filter); if (h->api != NULL) GNUNET_break (NULL == GNUNET_PLUGIN_unload (h->lib_name, h->api)); @@ -229,27 +233,42 @@ GNUNET_DATACACHE_destroy (struct GNUNET_DATACACHE_Handle *h) * @param data data to store * @param type type of the value * @param discard_time when to discard the value in any case - * @return GNUNET_OK on success, GNUNET_SYSERR on error (full, etc.) + * @param path_info_len number of entries in 'path_info' + * @param path_info a path through the network + * @return GNUNET_OK on success, GNUNET_SYSERR on error, GNUNET_NO if duplicate */ int GNUNET_DATACACHE_put (struct GNUNET_DATACACHE_Handle *h, - const GNUNET_HashCode * key, size_t size, + const struct GNUNET_HashCode * key, size_t size, const char *data, enum GNUNET_BLOCK_Type type, - struct GNUNET_TIME_Absolute discard_time) + struct GNUNET_TIME_Absolute discard_time, + unsigned int path_info_len, + const struct GNUNET_PeerIdentity *path_info) { - uint32_t used; + ssize_t used; - used = h->api->put (h->api->cls, key, size, data, type, discard_time); - if (used == 0) + used = h->api->put (h->api->cls, key, + size, data, + type, discard_time, + path_info_len, path_info); + if (-1 == used) { GNUNET_break (0); return GNUNET_SYSERR; } + if (0 == used) + { + /* duplicate */ + return GNUNET_NO; + } LOG (GNUNET_ERROR_TYPE_DEBUG, "Stored data under key `%s' in cache\n", GNUNET_h2s (key)); GNUNET_STATISTICS_update (h->stats, gettext_noop ("# bytes stored"), size, GNUNET_NO); - GNUNET_CONTAINER_bloomfilter_add (h->filter, key); + GNUNET_STATISTICS_update (h->stats, gettext_noop ("# items stored"), 1, + GNUNET_NO); + if (NULL != h->filter) + GNUNET_CONTAINER_bloomfilter_add (h->filter, key); while (h->utilization + used > h->env.quota) GNUNET_assert (GNUNET_OK == h->api->del (h->api->cls)); h->utilization += used; @@ -270,14 +289,15 @@ GNUNET_DATACACHE_put (struct GNUNET_DATACACHE_Handle *h, */ unsigned int GNUNET_DATACACHE_get (struct GNUNET_DATACACHE_Handle *h, - const GNUNET_HashCode * key, enum GNUNET_BLOCK_Type type, + const struct GNUNET_HashCode * key, enum GNUNET_BLOCK_Type type, GNUNET_DATACACHE_Iterator iter, void *iter_cls) { GNUNET_STATISTICS_update (h->stats, gettext_noop ("# requests received"), 1, GNUNET_NO); LOG (GNUNET_ERROR_TYPE_DEBUG, "Processing request for key `%s'\n", GNUNET_h2s (key)); - if (GNUNET_OK != GNUNET_CONTAINER_bloomfilter_test (h->filter, key)) + if ( (NULL != h->filter) && + (GNUNET_OK != GNUNET_CONTAINER_bloomfilter_test (h->filter, key)) ) { GNUNET_STATISTICS_update (h->stats, gettext_noop diff --git a/src/datacache/datacache.conf b/src/datacache/datacache.conf index 125a4e5..033b56d 100644 --- a/src/datacache/datacache.conf +++ b/src/datacache/datacache.conf @@ -1,10 +1,2 @@ -[datacache-mysql] -DATABASE = gnunet -CONFIG = ~/.my.cnf -# USER = gnunet -# PASSWORD = -# HOST = localhost -# PORT = 3306 - [datacache-postgres] CONFIG = connect_timeout=10; dbname=gnunet diff --git a/src/datacache/perf_datacache.c b/src/datacache/perf_datacache.c index 77edbf9..84775a3 100644 --- a/src/datacache/perf_datacache.c +++ b/src/datacache/perf_datacache.c @@ -25,9 +25,9 @@ #include "platform.h" #include "gnunet_util_lib.h" #include "gnunet_datacache_lib.h" +#include "gnunet_testing_lib.h" #include -#define VERBOSE GNUNET_NO #define ASSERT(x) do { if (! (x)) { printf("Error at %s:%d\n", __FILE__, __LINE__); goto FAILURE;} } while (0) @@ -44,11 +44,14 @@ static const char *plugin_name; static int -checkIt (void *cls, struct GNUNET_TIME_Absolute exp, - const GNUNET_HashCode * key, size_t size, const char *data, - enum GNUNET_BLOCK_Type type) +checkIt (void *cls, + const struct GNUNET_HashCode * key, size_t size, const char *data, + enum GNUNET_BLOCK_Type type, + struct GNUNET_TIME_Absolute exp, + unsigned int path_len, + const struct GNUNET_PeerIdentity *path) { - if ((size == sizeof (GNUNET_HashCode)) && (0 == memcmp (data, cls, size))) + if ((size == sizeof (struct GNUNET_HashCode)) && (0 == memcmp (data, cls, size))) found++; return GNUNET_OK; } @@ -59,8 +62,8 @@ run (void *cls, char *const *args, const char *cfgfile, const struct GNUNET_CONFIGURATION_Handle *cfg) { struct GNUNET_DATACACHE_Handle *h; - GNUNET_HashCode k; - GNUNET_HashCode n; + struct GNUNET_HashCode k; + struct GNUNET_HashCode n; struct GNUNET_TIME_Absolute exp; struct GNUNET_TIME_Absolute start; unsigned int i; @@ -76,41 +79,40 @@ run (void *cls, char *const *args, const char *cfgfile, } exp = GNUNET_TIME_relative_to_absolute (GNUNET_TIME_UNIT_HOURS); start = GNUNET_TIME_absolute_get (); - memset (&k, 0, sizeof (GNUNET_HashCode)); + memset (&k, 0, sizeof (struct GNUNET_HashCode)); for (i = 0; i < ITERATIONS; i++) { if (0 == i % (ITERATIONS / 80)) FPRINTF (stderr, "%s", "."); - GNUNET_CRYPTO_hash (&k, sizeof (GNUNET_HashCode), &n); + GNUNET_CRYPTO_hash (&k, sizeof (struct GNUNET_HashCode), &n); ASSERT (GNUNET_OK == - GNUNET_DATACACHE_put (h, &k, sizeof (GNUNET_HashCode), - (const char *) &n, 1 + i % 16, exp)); + GNUNET_DATACACHE_put (h, &k, sizeof (struct GNUNET_HashCode), + (const char *) &n, 1 + i % 16, exp, + 0, NULL)); k = n; } FPRINTF (stderr, "%s", "\n"); - FPRINTF (stdout, "Stored %u items in %llums\n", ITERATIONS, - (unsigned long long) - GNUNET_TIME_absolute_get_duration (start).rel_value); + FPRINTF (stdout, "Stored %u items in %s\n", ITERATIONS, + GNUNET_STRINGS_relative_time_to_string (GNUNET_TIME_absolute_get_duration (start), GNUNET_YES)); GNUNET_snprintf (gstr, sizeof (gstr), "DATACACHE-%s", plugin_name); GAUGER (gstr, "Time to PUT item in datacache", GNUNET_TIME_absolute_get_duration (start).rel_value / ITERATIONS, "ms/item"); start = GNUNET_TIME_absolute_get (); - memset (&k, 0, sizeof (GNUNET_HashCode)); + memset (&k, 0, sizeof (struct GNUNET_HashCode)); for (i = 0; i < ITERATIONS; i++) { if (0 == i % (ITERATIONS / 80)) FPRINTF (stderr, "%s", "."); - GNUNET_CRYPTO_hash (&k, sizeof (GNUNET_HashCode), &n); + GNUNET_CRYPTO_hash (&k, sizeof (struct GNUNET_HashCode), &n); GNUNET_DATACACHE_get (h, &k, 1 + i % 16, &checkIt, &n); k = n; } FPRINTF (stderr, "%s", "\n"); FPRINTF (stdout, - "Found %u/%u items in %llums (%u were deleted during storage processing)\n", + "Found %u/%u items in %s (%u were deleted during storage processing)\n", found, ITERATIONS, - (unsigned long long) - GNUNET_TIME_absolute_get_duration (start).rel_value, + GNUNET_STRINGS_relative_time_to_string (GNUNET_TIME_absolute_get_duration (start), GNUNET_YES), ITERATIONS - found); if (found > 0) GAUGER (gstr, "Time to GET item from datacache", @@ -129,16 +131,11 @@ FAILURE: int main (int argc, char *argv[]) { - char *pos; char cfg_name[128]; - char *const xargv[] = { "perf-datacache", "-c", cfg_name, -#if VERBOSE - "-L", "DEBUG", -#endif NULL }; struct GNUNET_GETOPT_CommandLineOption options[] = { @@ -146,25 +143,11 @@ main (int argc, char *argv[]) }; GNUNET_log_setup ("perf-datacache", -#if VERBOSE - "DEBUG", -#else "WARNING", -#endif NULL); - /* determine name of plugin to use */ - plugin_name = argv[0]; - while (NULL != (pos = strstr (plugin_name, "_"))) - plugin_name = pos + 1; - if (NULL != (pos = strstr (plugin_name, "."))) - pos[0] = 0; - else - pos = (char *) plugin_name; - + plugin_name = GNUNET_TESTING_get_testname_from_underscore (argv[0]); GNUNET_snprintf (cfg_name, sizeof (cfg_name), "perf_datacache_data_%s.conf", plugin_name); - if (pos != plugin_name) - pos[0] = '.'; GNUNET_PROGRAM_run ((sizeof (xargv) / sizeof (char *)) - 1, xargv, "perf-datacache", "nohelp", options, &run, NULL); if (ok != 0) diff --git a/src/datacache/perf_datacache_data_heap.conf b/src/datacache/perf_datacache_data_heap.conf new file mode 100644 index 0000000..3680c02 --- /dev/null +++ b/src/datacache/perf_datacache_data_heap.conf @@ -0,0 +1,5 @@ +[perfcache] +QUOTA = 500 KB +DATABASE = heap + + diff --git a/src/datacache/perf_datacache_data_mysql.conf b/src/datacache/perf_datacache_data_mysql.conf deleted file mode 100644 index 1760f7d..0000000 --- a/src/datacache/perf_datacache_data_mysql.conf +++ /dev/null @@ -1,13 +0,0 @@ -[perfcache] -QUOTA = 500 KB -DATABASE = mysql - -[datacache-mysql] -DATABASE = gnunetcheck -# CONFIG = ~/.my.cnf -# USER = -# PASSWORD = -# HOST = -# PORT = - - diff --git a/src/datacache/plugin_datacache_heap.c b/src/datacache/plugin_datacache_heap.c new file mode 100644 index 0000000..41dd089 --- /dev/null +++ b/src/datacache/plugin_datacache_heap.c @@ -0,0 +1,441 @@ +/* + This file is part of GNUnet + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @file datacache/plugin_datacache_heap.c + * @brief heap-only implementation of a database backend for the datacache + * @author Christian Grothoff + */ +#include "platform.h" +#include "gnunet_util_lib.h" +#include "gnunet_datacache_plugin.h" + +#define LOG(kind,...) GNUNET_log_from (kind, "datacache-heap", __VA_ARGS__) + +#define LOG_STRERROR_FILE(kind,op,fn) GNUNET_log_from_strerror_file (kind, "datacache-heap", op, fn) + + + +/** + * Context for all functions in this plugin. + */ +struct Plugin +{ + /** + * Our execution environment. + */ + struct GNUNET_DATACACHE_PluginEnvironment *env; + + /** + * Our hash map. + */ + struct GNUNET_CONTAINER_MultiHashMap *map; + + /** + * Heap for expirations. + */ + struct GNUNET_CONTAINER_Heap *heap; + +}; + + +/** + * Entry in the hash map. + */ +struct Value +{ + /** + * Key for the entry. + */ + struct GNUNET_HashCode key; + + /** + * Expiration time. + */ + struct GNUNET_TIME_Absolute discard_time; + + /** + * Corresponding node in the heap. + */ + struct GNUNET_CONTAINER_HeapNode *hn; + + /** + * Path information. + */ + struct GNUNET_PeerIdentity *path_info; + + /** + * Payload (actual payload follows this struct) + */ + size_t size; + + /** + * Number of entries in 'path_info'. + */ + unsigned int path_info_len; + + /** + * Type of the block. + */ + enum GNUNET_BLOCK_Type type; + +}; + + +#define OVERHEAD (sizeof (struct Value) + 64) + + +/** + * Closure for 'put_cb'. + */ +struct PutContext +{ + /** + * Expiration time for the new value. + */ + struct GNUNET_TIME_Absolute discard_time; + + /** + * Data for the new value. + */ + const char *data; + + /** + * Heap from the plugin. + */ + struct GNUNET_CONTAINER_Heap *heap; + + /** + * Path information. + */ + const struct GNUNET_PeerIdentity *path_info; + + /** + * Number of bytes in 'data'. + */ + size_t size; + + /** + * Type of the node. + */ + enum GNUNET_BLOCK_Type type; + + /** + * Number of entries in 'path_info'. + */ + unsigned int path_info_len; + + /** + * Value to set to GNUNET_YES if an equivalent block was found. + */ + int found; +}; + + +/** + * Function called during PUT to detect if an equivalent block + * already exists. + * + * @param cls the 'struct PutContext' + * @param key the key for the value(s) + * @param value an existing value + * @return GNUNET_YES if not found (to continue to iterate) + */ +static int +put_cb (void *cls, + const struct GNUNET_HashCode *key, + void *value) +{ + struct PutContext *put_ctx = cls; + struct Value *val = value; + + if ( (val->size == put_ctx->size) && + (val->type == put_ctx->type) && + (0 == memcmp (&val[1], put_ctx->data, put_ctx->size)) ) + { + put_ctx->found = GNUNET_YES; + val->discard_time = GNUNET_TIME_absolute_max (val->discard_time, + put_ctx->discard_time); + /* replace old path with new path */ + GNUNET_array_grow (val->path_info, + val->path_info_len, + put_ctx->path_info_len); + memcpy (val->path_info, + put_ctx->path_info, + put_ctx->path_info_len * sizeof (struct GNUNET_PeerIdentity)); + GNUNET_CONTAINER_heap_update_cost (put_ctx->heap, + val->hn, + val->discard_time.abs_value); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Got same value for key %s and type %d (size %u vs %u)\n", + GNUNET_h2s (key), + val->type, + (unsigned int) val->size, + (unsigned int) put_ctx->size); + return GNUNET_NO; + } + return GNUNET_YES; +} + + +/** + * Store an item in the datastore. + * + * @param cls closure (our "struct Plugin") + * @param key key to store data under + * @param size number of bytes in data + * @param data data to store + * @param type type of the value + * @param discard_time when to discard the value in any case + * @param path_info_len number of entries in 'path_info' + * @param path_info a path through the network + * @return 0 if duplicate, -1 on error, number of bytes used otherwise + */ +static ssize_t +heap_plugin_put (void *cls, const struct GNUNET_HashCode * key, size_t size, + const char *data, enum GNUNET_BLOCK_Type type, + struct GNUNET_TIME_Absolute discard_time, + unsigned int path_info_len, + const struct GNUNET_PeerIdentity *path_info) +{ + struct Plugin *plugin = cls; + struct Value *val; + struct PutContext put_ctx; + + put_ctx.found = GNUNET_NO; + put_ctx.heap = plugin->heap; + put_ctx.data = data; + put_ctx.size = size; + put_ctx.path_info = path_info; + put_ctx.path_info_len = path_info_len; + put_ctx.discard_time = discard_time; + put_ctx.type = type; + GNUNET_CONTAINER_multihashmap_get_multiple (plugin->map, + key, + put_cb, + &put_ctx); + if (GNUNET_YES == put_ctx.found) + return 0; + val = GNUNET_malloc (sizeof (struct Value) + size); + memcpy (&val[1], data, size); + val->key = *key; + val->type = type; + val->discard_time = discard_time; + val->size = size; + GNUNET_array_grow (val->path_info, + val->path_info_len, + path_info_len); + memcpy (val->path_info, path_info, + path_info_len * sizeof (struct GNUNET_PeerIdentity)); + (void) GNUNET_CONTAINER_multihashmap_put (plugin->map, + &val->key, + val, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE); + val->hn = GNUNET_CONTAINER_heap_insert (plugin->heap, + val, + val->discard_time.abs_value); + return size + OVERHEAD; +} + + +/** + * Closure for 'get_cb'. + */ +struct GetContext +{ + /** + * Function to call for each result. + */ + GNUNET_DATACACHE_Iterator iter; + + /** + * Closure for 'iter'. + */ + void *iter_cls; + + /** + * Number of results found. + */ + unsigned int cnt; + + /** + * Block type requested. + */ + enum GNUNET_BLOCK_Type type; +}; + + + +/** + * Function called during GET to find matching blocks. + * Only matches by type. + * + * @param cls the 'struct GetContext' + * @param key the key for the value(s) + * @param value an existing value + * @return GNUNET_YES to continue to iterate + */ +static int +get_cb (void *cls, + const struct GNUNET_HashCode *key, + void *value) +{ + struct GetContext *get_ctx = cls; + struct Value *val = value; + int ret; + + if ( (get_ctx->type != val->type) && + (GNUNET_BLOCK_TYPE_ANY != get_ctx->type) ) + return GNUNET_OK; + if (NULL != get_ctx->iter) + ret = get_ctx->iter (get_ctx->iter_cls, + key, + val->size, + (const char *) &val[1], + val->type, + val->discard_time, + val->path_info_len, + val->path_info); + else + ret = GNUNET_YES; + get_ctx->cnt++; + return ret; +} + + +/** + * Iterate over the results for a particular key + * in the datastore. + * + * @param cls closure (our "struct Plugin") + * @param key + * @param type entries of which type are relevant? + * @param iter maybe NULL (to just count) + * @param iter_cls closure for iter + * @return the number of results found + */ +static unsigned int +heap_plugin_get (void *cls, const struct GNUNET_HashCode * key, + enum GNUNET_BLOCK_Type type, GNUNET_DATACACHE_Iterator iter, + void *iter_cls) +{ + struct Plugin *plugin = cls; + struct GetContext get_ctx; + + get_ctx.type = type; + get_ctx.iter = iter; + get_ctx.iter_cls = iter_cls; + get_ctx.cnt = 0; + GNUNET_CONTAINER_multihashmap_get_multiple (plugin->map, + key, + get_cb, + &get_ctx); + return get_ctx.cnt; +} + + +/** + * Delete the entry with the lowest expiration value + * from the datacache right now. + * + * @param cls closure (our "struct Plugin") + * @return GNUNET_OK on success, GNUNET_SYSERR on error + */ +static int +heap_plugin_del (void *cls) +{ + struct Plugin *plugin = cls; + struct Value *val; + + val = GNUNET_CONTAINER_heap_remove_root (plugin->heap); + if (NULL == val) + return GNUNET_SYSERR; + GNUNET_assert (GNUNET_YES == + GNUNET_CONTAINER_multihashmap_remove (plugin->map, + &val->key, + val)); + plugin->env->delete_notify (plugin->env->cls, + &val->key, + val->size + OVERHEAD); + GNUNET_free_non_null (val->path_info); + GNUNET_free (val); + return GNUNET_OK; +} + + +/** + * Entry point for the plugin. + * + * @param cls closure (the "struct GNUNET_DATACACHE_PluginEnvironmnet") + * @return the plugin's closure (our "struct Plugin") + */ +void * +libgnunet_plugin_datacache_heap_init (void *cls) +{ + struct GNUNET_DATACACHE_PluginEnvironment *env = cls; + struct GNUNET_DATACACHE_PluginFunctions *api; + struct Plugin *plugin; + + plugin = GNUNET_malloc (sizeof (struct Plugin)); + plugin->map = GNUNET_CONTAINER_multihashmap_create (1024, /* FIXME: base on quota! */ + GNUNET_YES); + plugin->heap = GNUNET_CONTAINER_heap_create (GNUNET_CONTAINER_HEAP_ORDER_MIN); + plugin->env = env; + api = GNUNET_malloc (sizeof (struct GNUNET_DATACACHE_PluginFunctions)); + api->cls = plugin; + api->get = &heap_plugin_get; + api->put = &heap_plugin_put; + api->del = &heap_plugin_del; + LOG (GNUNET_ERROR_TYPE_INFO, _("Heap datacache running\n")); + return api; +} + + +/** + * Exit point from the plugin. + * + * @param cls closure (our "struct Plugin") + * @return NULL + */ +void * +libgnunet_plugin_datacache_heap_done (void *cls) +{ + struct GNUNET_DATACACHE_PluginFunctions *api = cls; + struct Plugin *plugin = api->cls; + struct Value *val; + + while (NULL != (val = GNUNET_CONTAINER_heap_remove_root (plugin->heap))) + { + GNUNET_assert (GNUNET_YES == + GNUNET_CONTAINER_multihashmap_remove (plugin->map, + &val->key, + val)); + GNUNET_free (val); + } + GNUNET_CONTAINER_heap_destroy (plugin->heap); + GNUNET_CONTAINER_multihashmap_destroy (plugin->map); + GNUNET_free (plugin); + GNUNET_free (api); + return NULL; +} + + + +/* end of plugin_datacache_heap.c */ diff --git a/src/datacache/plugin_datacache_mysql.c b/src/datacache/plugin_datacache_mysql.c deleted file mode 100644 index 8103429..0000000 --- a/src/datacache/plugin_datacache_mysql.c +++ /dev/null @@ -1,474 +0,0 @@ -/* - This file is part of GNUnet - (C) 2006, 2009, 2010 Christian Grothoff (and other contributing authors) - - GNUnet is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published - by the Free Software Foundation; either version 3, or (at your - option) any later version. - - GNUnet is distributed in the hope that it will be useful, but - WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - General Public License for more details. - - You should have received a copy of the GNU General Public License - along with GNUnet; see the file COPYING. If not, write to the - Free Software Foundation, Inc., 59 Temple Place - Suite 330, - Boston, MA 02111-1307, USA. -*/ - -/** - * @file datacache/plugin_datacache_mysql.c - * @brief mysql for an implementation of a database backend for the datacache - * @author Christian Grothoff - * - * SETUP INSTRUCTIONS: - * - * 1) Access mysql as root, - *
- *
- *    $ mysql -u root -p
- *
- *    
- * and do the following. [You should replace $USER with the username - * that will be running the gnunetd process]. - * @verbatim - CREATE DATABASE gnunet; - GRANT select,insert,update,delete,create,alter,drop,create temporary tables - ON gnunet.* TO $USER@localhost; - SET PASSWORD FOR $USER@localhost=PASSWORD('$the_password_you_like'); - FLUSH PRIVILEGES; - @endverbatim - * 2) In the $HOME directory of $USER, create a ".my.cnf" file - * with the following lines - * @verbatim - [client] - user=$USER - password=$the_password_you_like - @endverbatim - * - * Thats it -- now you can configure your datastores in GNUnet to - * use MySQL. Note that .my.cnf file is a security risk unless its on - * a safe partition etc. The $HOME/.my.cnf can of course be a symbolic - * link. Even greater security risk can be achieved by setting no - * password for $USER. Luckily $USER has only priviledges to mess - * up GNUnet's tables, nothing else (unless you give him more, - * of course).

- * - * 3) Still, perhaps you should briefly try if the DB connection - * works. First, login as $USER. Then use, - * @verbatim - $ mysql -u $USER -p $the_password_you_like - mysql> use gnunet; - @endverbatim - * - * If you get the message "Database changed" it probably works. - * - * [If you get "ERROR 2002: Can't connect to local MySQL server - * through socket '/tmp/mysql.sock' (2)" it may be resolvable by - * "ln -s /var/run/mysqld/mysqld.sock /tmp/mysql.sock" - * so there may be some additional trouble depending on your mysql setup.] - * - * PROBLEMS? - * - * If you have problems related to the mysql module, your best - * friend is probably the mysql manual. The first thing to check - * is that mysql is basically operational, that you can connect - * to it, create tables, issue queries etc. - */ -#include "platform.h" -#include "gnunet_util_lib.h" -#include "gnunet_datacache_plugin.h" -#include "gnunet_mysql_lib.h" -#include - - -/** - * Estimate of the per-entry overhead (including indices). - */ -#define OVERHEAD ((4*2+4*2+8*2+8*2+sizeof(GNUNET_HashCode)*5+8)) - -/** - * Die with an error message that indicates - * a failure of the command 'cmd' with the message given - * by strerror(errno). - */ -#define DIE_MYSQL(cmd, dbh) do { GNUNET_log(GNUNET_ERROR_TYPE__ERROR, _("`%s' failed at %s:%d with error: %s\n"), cmd, __FILE__, __LINE__, mysql_error((dbh)->dbf)); GNUNET_abort(); } while(0); - -/** - * Log an error message at log-level 'level' that indicates - * a failure of the command 'cmd' on file 'filename' - * with the message given by strerror(errno). - */ -#define LOG_MYSQL(level, cmd, dbh) do { GNUNET_log(level, _("`%s' failed at %s:%d with error: %s\n"), cmd, __FILE__, __LINE__, mysql_error((dbh)->dbf)); } while(0); - - -/** - * Context for all functions in this plugin. - */ -struct Plugin -{ - /** - * Our execution environment. - */ - struct GNUNET_DATACACHE_PluginEnvironment *env; - - /** - * Handle to the mysql database. - */ - struct GNUNET_MYSQL_Context *mc; - -#define SELECT_VALUE_STMT "SELECT value,expire FROM gn080dstore FORCE INDEX (hashidx) WHERE hash=? AND type=? AND expire >= ? LIMIT 1 OFFSET ?" - struct GNUNET_MYSQL_StatementHandle *select_value; - -#define COUNT_VALUE_STMT "SELECT count(*) FROM gn080dstore FORCE INDEX (hashidx) WHERE hash=? AND type=? AND expire >= ?" - struct GNUNET_MYSQL_StatementHandle *count_value; - -#define SELECT_OLD_VALUE_STMT "SELECT hash, vhash, type, value FROM gn080dstore FORCE INDEX (expireidx) ORDER BY puttime ASC LIMIT 1" - struct GNUNET_MYSQL_StatementHandle *select_old_value; - -#define DELETE_VALUE_STMT "DELETE FROM gn080dstore WHERE hash = ? AND vhash = ? AND type = ? AND value = ?" - struct GNUNET_MYSQL_StatementHandle *delete_value; - -#define INSERT_VALUE_STMT "INSERT INTO gn080dstore (type, puttime, expire, hash, vhash, value) "\ - "VALUES (?, ?, ?, ?, ?, ?)" - struct GNUNET_MYSQL_StatementHandle *insert_value; - -#define UPDATE_VALUE_STMT "UPDATE gn080dstore FORCE INDEX (allidx) SET puttime=?, expire=? "\ - "WHERE hash=? AND vhash=? AND type=?" - struct GNUNET_MYSQL_StatementHandle *update_value; - -}; - - -/** - * Create temporary table and prepare statements. - * - * @param plugin plugin context - * @return GNUNET_OK on success - */ -static int -itable (struct Plugin *plugin) -{ -#define MRUNS(a) (GNUNET_OK != GNUNET_MYSQL_statement_run (plugin->mc, a) ) - if (MRUNS - ("CREATE TEMPORARY TABLE gn080dstore (" - " type INT(11) UNSIGNED NOT NULL DEFAULT 0," - " puttime BIGINT UNSIGNED NOT NULL DEFAULT 0," - " expire BIGINT UNSIGNED NOT NULL DEFAULT 0," - " hash BINARY(64) NOT NULL DEFAULT ''," - " vhash BINARY(64) NOT NULL DEFAULT ''," - " value BLOB NOT NULL DEFAULT ''," - " INDEX hashidx (hash(64),type,expire)," - " INDEX allidx (hash(64),vhash(64),type)," " INDEX expireidx (puttime)" - ") ENGINE=InnoDB") || MRUNS ("SET AUTOCOMMIT = 1")) - return GNUNET_SYSERR; -#undef MRUNS -#define PINIT(a,b) (NULL == (a = GNUNET_MYSQL_statement_prepare (plugin->mc, b))) - if (PINIT (plugin->select_value, SELECT_VALUE_STMT) || - PINIT (plugin->count_value, COUNT_VALUE_STMT) || - PINIT (plugin->select_old_value, SELECT_OLD_VALUE_STMT) || - PINIT (plugin->delete_value, DELETE_VALUE_STMT) || - PINIT (plugin->insert_value, INSERT_VALUE_STMT) || - PINIT (plugin->update_value, UPDATE_VALUE_STMT)) - return GNUNET_SYSERR; -#undef PINIT - return GNUNET_OK; -} - - -/** - * Store an item in the datastore. - * - * @param cls closure (our "struct Plugin") - * @param key key to store data under - * @param size number of bytes in data - * @param data data to store - * @param type type of the value - * @param discard_time when to discard the value in any case - * @return 0 on error, number of bytes used otherwise - */ -static size_t -mysql_plugin_put (void *cls, const GNUNET_HashCode * key, size_t size, - const char *data, enum GNUNET_BLOCK_Type type, - struct GNUNET_TIME_Absolute discard_time) -{ - struct Plugin *plugin = cls; - struct GNUNET_TIME_Absolute now; - unsigned long k_length; - unsigned long h_length; - unsigned long v_length; - unsigned long long v_now; - unsigned long long v_discard_time; - unsigned int v_type; - GNUNET_HashCode vhash; - int ret; - - if (size > GNUNET_SERVER_MAX_MESSAGE_SIZE) - return GNUNET_SYSERR; - GNUNET_CRYPTO_hash (data, size, &vhash); - now = GNUNET_TIME_absolute_get (); - - /* first try UPDATE */ - h_length = sizeof (GNUNET_HashCode); - k_length = sizeof (GNUNET_HashCode); - v_length = size; - v_type = type; - v_now = (unsigned long long) now.abs_value; - v_discard_time = (unsigned long long) discard_time.abs_value; - if (GNUNET_OK == - GNUNET_MYSQL_statement_run_prepared (plugin->mc, plugin->update_value, NULL, - MYSQL_TYPE_LONGLONG, &v_now, GNUNET_YES, - MYSQL_TYPE_LONGLONG, &v_discard_time, GNUNET_YES, - MYSQL_TYPE_BLOB, key, sizeof (GNUNET_HashCode), - &k_length, MYSQL_TYPE_BLOB, &vhash, - sizeof (GNUNET_HashCode), &h_length, - MYSQL_TYPE_LONG, &v_type, GNUNET_YES, -1)) - return GNUNET_OK; - - /* now try INSERT */ - h_length = sizeof (GNUNET_HashCode); - k_length = sizeof (GNUNET_HashCode); - v_length = size; - if (GNUNET_OK != - (ret = - GNUNET_MYSQL_statement_run_prepared (plugin->mc, plugin->insert_value, NULL, - MYSQL_TYPE_LONG, &type, GNUNET_YES, - MYSQL_TYPE_LONGLONG, &v_now, GNUNET_YES, - MYSQL_TYPE_LONGLONG, &v_discard_time, GNUNET_YES, - MYSQL_TYPE_BLOB, key, sizeof (GNUNET_HashCode), - &k_length, MYSQL_TYPE_BLOB, &vhash, - sizeof (GNUNET_HashCode), &h_length, - MYSQL_TYPE_BLOB, data, (unsigned long) size, - &v_length, -1))) - { - if (ret == GNUNET_SYSERR) - itable (plugin); - return GNUNET_SYSERR; - } - return size + OVERHEAD; -} - - -static int -return_ok (void *cls, unsigned int num_values, MYSQL_BIND * values) -{ - return GNUNET_OK; -} - - -/** - * Iterate over the results for a particular key - * in the datastore. - * - * @param cls closure (our "struct Plugin") - * @param key - * @param type entries of which type are relevant? - * @param iter maybe NULL (to just count) - * @param iter_cls closure for iter - * @return the number of results found - */ -static unsigned int -mysql_plugin_get (void *cls, const GNUNET_HashCode * key, - enum GNUNET_BLOCK_Type type, GNUNET_DATACACHE_Iterator iter, - void *iter_cls) -{ - struct Plugin *plugin = cls; - MYSQL_BIND rbind[3]; - unsigned long h_length; - unsigned long v_length; - unsigned long long v_expire; - struct GNUNET_TIME_Absolute now; - struct GNUNET_TIME_Absolute expire; - unsigned int cnt; - unsigned long long total; - unsigned long long v_now; - unsigned int off; - unsigned int v_type; - int ret; - char buffer[GNUNET_SERVER_MAX_MESSAGE_SIZE]; - - now = GNUNET_TIME_absolute_get (); - h_length = sizeof (GNUNET_HashCode); - v_length = sizeof (buffer); - total = -1; - memset (rbind, 0, sizeof (rbind)); - rbind[0].buffer_type = MYSQL_TYPE_LONGLONG; - rbind[0].buffer = &total; - rbind[0].is_unsigned = GNUNET_YES; - v_type = type; - v_now = (unsigned long long) now.abs_value; - if ((GNUNET_OK != - (ret = - GNUNET_MYSQL_statement_run_prepared_select (plugin->mc, plugin->count_value, 1, rbind, - return_ok, NULL, MYSQL_TYPE_BLOB, key, - sizeof (GNUNET_HashCode), &h_length, - MYSQL_TYPE_LONG, &v_type, GNUNET_YES, - MYSQL_TYPE_LONGLONG, &v_now, GNUNET_YES, - -1))) || (-1 == total)) - { - if (ret == GNUNET_SYSERR) - itable (plugin); - return GNUNET_SYSERR; - } - if ((iter == NULL) || (total == 0)) - return (int) total; - - off = GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK, total); - cnt = 0; - while (cnt < total) - { - memset (rbind, 0, sizeof (rbind)); - rbind[0].buffer_type = MYSQL_TYPE_BLOB; - rbind[0].buffer_length = sizeof (buffer); - rbind[0].length = &v_length; - rbind[0].buffer = buffer; - rbind[1].buffer_type = MYSQL_TYPE_LONGLONG; - rbind[1].is_unsigned = 1; - rbind[1].buffer = &v_expire; - off = (off + 1) % total; - if (GNUNET_OK != - (ret = - GNUNET_MYSQL_statement_run_prepared_select (plugin->mc, plugin->select_value, 2, rbind, - return_ok, NULL, MYSQL_TYPE_BLOB, key, - sizeof (GNUNET_HashCode), &h_length, - MYSQL_TYPE_LONG, &v_type, GNUNET_YES, - MYSQL_TYPE_LONGLONG, &v_now, GNUNET_YES, - MYSQL_TYPE_LONG, &off, GNUNET_YES, -1))) - { - if (ret == GNUNET_SYSERR) - itable (plugin); - return GNUNET_SYSERR; - } - cnt++; - expire.abs_value = v_expire; - if (GNUNET_OK != iter (iter_cls, expire, key, v_length, buffer, type)) - break; - } - return cnt; -} - - -/** - * Delete the entry with the lowest expiration value - * from the datacache right now. - * - * @param cls closure (our "struct Plugin") - * @return GNUNET_OK on success, GNUNET_SYSERR on error - */ -static int -mysql_plugin_del (void *cls) -{ - struct Plugin *plugin = cls; - - MYSQL_BIND rbind[5]; - unsigned int v_type; - GNUNET_HashCode v_key; - GNUNET_HashCode vhash; - unsigned long k_length; - unsigned long h_length; - unsigned long v_length; - int ret; - char buffer[GNUNET_SERVER_MAX_MESSAGE_SIZE]; - - k_length = sizeof (GNUNET_HashCode); - h_length = sizeof (GNUNET_HashCode); - v_length = sizeof (buffer); - memset (rbind, 0, sizeof (rbind)); - rbind[0].buffer_type = MYSQL_TYPE_BLOB; - rbind[0].buffer_length = sizeof (GNUNET_HashCode); - rbind[0].length = &k_length; - rbind[0].buffer = &v_key; - rbind[1].buffer_type = MYSQL_TYPE_BLOB; - rbind[1].buffer_length = sizeof (GNUNET_HashCode); - rbind[1].length = &h_length; - rbind[1].buffer = &vhash; - rbind[2].buffer_type = MYSQL_TYPE_LONG; - rbind[2].is_unsigned = 1; - rbind[2].buffer = &v_type; - rbind[3].buffer_type = MYSQL_TYPE_BLOB; - rbind[3].buffer_length = sizeof (buffer); - rbind[3].length = &v_length; - rbind[3].buffer = buffer; - if ((GNUNET_OK != - (ret = - GNUNET_MYSQL_statement_run_prepared_select (plugin->mc, plugin->select_old_value, 4, - rbind, return_ok, NULL, -1))) || - (GNUNET_OK != - (ret = - GNUNET_MYSQL_statement_run_prepared (plugin->mc, plugin->delete_value, NULL, - MYSQL_TYPE_BLOB, &v_key, - sizeof (GNUNET_HashCode), &k_length, - MYSQL_TYPE_BLOB, &vhash, - sizeof (GNUNET_HashCode), &h_length, - MYSQL_TYPE_LONG, &v_type, GNUNET_YES, - MYSQL_TYPE_BLOB, buffer, - (unsigned long) sizeof (buffer), &v_length, - -1)))) - { - if (ret == GNUNET_SYSERR) - itable (plugin); - return GNUNET_SYSERR; - } - plugin->env->delete_notify (plugin->env->cls, &v_key, v_length + OVERHEAD); - - return GNUNET_OK; -} - - -/** - * Entry point for the plugin. - * - * @param cls closure (the "struct GNUNET_DATACACHE_PluginEnvironmnet") - * @return the plugin's closure (our "struct Plugin") - */ -void * -libgnunet_plugin_datacache_mysql_init (void *cls) -{ - struct GNUNET_DATACACHE_PluginEnvironment *env = cls; - struct GNUNET_DATACACHE_PluginFunctions *api; - struct Plugin *plugin; - - plugin = GNUNET_malloc (sizeof (struct Plugin)); - plugin->env = env; - plugin->mc = GNUNET_MYSQL_context_create (env->cfg, "datacache-mysql"); - if ( (NULL == plugin->mc) || - (GNUNET_OK != itable (plugin)) ) - { - if (NULL != plugin->mc) - GNUNET_MYSQL_context_destroy (plugin->mc); - GNUNET_free (plugin); - return NULL; - } - api = GNUNET_malloc (sizeof (struct GNUNET_DATACACHE_PluginFunctions)); - api->cls = plugin; - api->get = &mysql_plugin_get; - api->put = &mysql_plugin_put; - api->del = &mysql_plugin_del; - GNUNET_log_from (GNUNET_ERROR_TYPE_INFO, "mysql", - _("MySQL datacache running\n")); - return api; -} - - -/** - * Exit point from the plugin. - * - * @param cls closure (our "struct Plugin") - * @return NULL - */ -void * -libgnunet_plugin_datacache_mysql_done (void *cls) -{ - struct GNUNET_DATACACHE_PluginFunctions *api = cls; - struct Plugin *plugin = api->cls; - - GNUNET_MYSQL_context_destroy (plugin->mc); - GNUNET_free (plugin); - GNUNET_free (api); - return NULL; -} - - -/* end of plugin_datacache_mysql.c */ diff --git a/src/datacache/plugin_datacache_postgres.c b/src/datacache/plugin_datacache_postgres.c index b40f1fd..e7d2e72 100644 --- a/src/datacache/plugin_datacache_postgres.c +++ b/src/datacache/plugin_datacache_postgres.c @@ -34,7 +34,7 @@ /** * Per-entry overhead estimate */ -#define OVERHEAD (sizeof(GNUNET_HashCode) + 24) +#define OVERHEAD (sizeof(struct GNUNET_HashCode) + 24) /** * Context for all functions in this plugin. @@ -75,13 +75,18 @@ init_connection (struct Plugin *plugin) " type INTEGER NOT NULL DEFAULT 0," " discard_time BIGINT NOT NULL DEFAULT 0," " key BYTEA NOT NULL DEFAULT ''," - " value BYTEA NOT NULL DEFAULT '')" "WITH OIDS"); - if ((ret == NULL) || ((PQresultStatus (ret) != PGRES_COMMAND_OK) && (0 != strcmp ("42P07", /* duplicate table */ - PQresultErrorField - (ret, - PG_DIAG_SQLSTATE))))) + " value BYTEA NOT NULL DEFAULT ''," + " path BYTEA DEFAULT '')" + "WITH OIDS"); + if ( (ret == NULL) || + ((PQresultStatus (ret) != PGRES_COMMAND_OK) && + (0 != strcmp ("42P07", /* duplicate table */ + PQresultErrorField + (ret, + PG_DIAG_SQLSTATE))))) { - (void) GNUNET_POSTGRES_check_result (plugin->dbh, ret, PGRES_COMMAND_OK, "CREATE TABLE", + (void) GNUNET_POSTGRES_check_result (plugin->dbh, ret, + PGRES_COMMAND_OK, "CREATE TABLE", "gn090dc"); PQfinish (plugin->dbh); plugin->dbh = NULL; @@ -123,11 +128,11 @@ init_connection (struct Plugin *plugin) PQclear (ret); if ((GNUNET_OK != GNUNET_POSTGRES_prepare (plugin->dbh, "getkt", - "SELECT discard_time,type,value FROM gn090dc " + "SELECT discard_time,type,value,path FROM gn090dc " "WHERE key=$1 AND type=$2 ", 2)) || (GNUNET_OK != GNUNET_POSTGRES_prepare (plugin->dbh, "getk", - "SELECT discard_time,type,value FROM gn090dc " + "SELECT discard_time,type,value,path FROM gn090dc " "WHERE key=$1", 1)) || (GNUNET_OK != GNUNET_POSTGRES_prepare (plugin->dbh, "getm", @@ -137,8 +142,8 @@ init_connection (struct Plugin *plugin) GNUNET_POSTGRES_prepare (plugin->dbh, "delrow", "DELETE FROM gn090dc WHERE oid=$1", 1)) || (GNUNET_OK != GNUNET_POSTGRES_prepare (plugin->dbh, "put", - "INSERT INTO gn090dc (type, discard_time, key, value) " - "VALUES ($1, $2, $3, $4)", 4))) + "INSERT INTO gn090dc (type, discard_time, key, value, path) " + "VALUES ($1, $2, $3, $4, $5)", 5))) { PQfinish (plugin->dbh); plugin->dbh = NULL; @@ -157,12 +162,16 @@ init_connection (struct Plugin *plugin) * @param data data to store * @param type type of the value * @param discard_time when to discard the value in any case - * @return 0 on error, number of bytes used otherwise + * @param path_info_len number of entries in 'path_info' + * @param path_info a path through the network + * @return 0 if duplicate, -1 on error, number of bytes used otherwise */ -static size_t -postgres_plugin_put (void *cls, const GNUNET_HashCode * key, size_t size, +static ssize_t +postgres_plugin_put (void *cls, const struct GNUNET_HashCode * key, size_t size, const char *data, enum GNUNET_BLOCK_Type type, - struct GNUNET_TIME_Absolute discard_time) + struct GNUNET_TIME_Absolute discard_time, + unsigned int path_info_len, + const struct GNUNET_PeerIdentity *path_info) { struct Plugin *plugin = cls; PGresult *ret; @@ -173,22 +182,25 @@ postgres_plugin_put (void *cls, const GNUNET_HashCode * key, size_t size, (const char *) &btype, (const char *) &bexpi, (const char *) key, - (const char *) data + (const char *) data, + (const char *) path_info }; int paramLengths[] = { sizeof (btype), sizeof (bexpi), - sizeof (GNUNET_HashCode), - size + sizeof (struct GNUNET_HashCode), + size, + path_info_len * sizeof (struct GNUNET_PeerIdentity) }; - const int paramFormats[] = { 1, 1, 1, 1 }; + const int paramFormats[] = { 1, 1, 1, 1, 1 }; ret = - PQexecPrepared (plugin->dbh, "put", 4, paramValues, paramLengths, + PQexecPrepared (plugin->dbh, "put", 5, paramValues, paramLengths, paramFormats, 1); if (GNUNET_OK != - GNUNET_POSTGRES_check_result (plugin->dbh, ret, PGRES_COMMAND_OK, "PQexecPrepared", "put")) - return GNUNET_SYSERR; + GNUNET_POSTGRES_check_result (plugin->dbh, ret, + PGRES_COMMAND_OK, "PQexecPrepared", "put")) + return -1; PQclear (ret); return size + OVERHEAD; } @@ -206,7 +218,7 @@ postgres_plugin_put (void *cls, const GNUNET_HashCode * key, size_t size, * @return the number of results found */ static unsigned int -postgres_plugin_get (void *cls, const GNUNET_HashCode * key, +postgres_plugin_get (void *cls, const struct GNUNET_HashCode * key, enum GNUNET_BLOCK_Type type, GNUNET_DATACACHE_Iterator iter, void *iter_cls) { @@ -218,7 +230,7 @@ postgres_plugin_get (void *cls, const GNUNET_HashCode * key, (const char *) &btype, }; int paramLengths[] = { - sizeof (GNUNET_HashCode), + sizeof (struct GNUNET_HashCode), sizeof (btype), }; const int paramFormats[] = { 1, 1 }; @@ -226,6 +238,8 @@ postgres_plugin_get (void *cls, const GNUNET_HashCode * key, uint32_t size; unsigned int cnt; unsigned int i; + unsigned int path_len; + const struct GNUNET_PeerIdentity *path; PGresult *res; res = @@ -254,7 +268,7 @@ postgres_plugin_get (void *cls, const GNUNET_HashCode * key, PQclear (res); return cnt; } - if ((3 != PQnfields (res)) || (sizeof (uint64_t) != PQfsize (res, 0)) || + if ((4 != PQnfields (res)) || (sizeof (uint64_t) != PQfsize (res, 0)) || (sizeof (uint32_t) != PQfsize (res, 1))) { GNUNET_break (0); @@ -267,12 +281,23 @@ postgres_plugin_get (void *cls, const GNUNET_HashCode * key, GNUNET_ntohll (*(uint64_t *) PQgetvalue (res, i, 0)); type = ntohl (*(uint32_t *) PQgetvalue (res, i, 1)); size = PQgetlength (res, i, 2); + path_len = PQgetlength (res, i, 3); + if (0 != (path_len % sizeof (struct GNUNET_PeerIdentity))) + { + GNUNET_break (0); + path_len = 0; + } + path_len %= sizeof (struct GNUNET_PeerIdentity); + path = (const struct GNUNET_PeerIdentity *) PQgetvalue (res, i, 3); LOG (GNUNET_ERROR_TYPE_DEBUG, "Found result of size %u bytes and type %u in database\n", (unsigned int) size, (unsigned int) type); if (GNUNET_SYSERR == - iter (iter_cls, expiration_time, key, size, PQgetvalue (res, i, 2), - (enum GNUNET_BLOCK_Type) type)) + iter (iter_cls, key, size, PQgetvalue (res, i, 2), + (enum GNUNET_BLOCK_Type) type, + expiration_time, + path_len, + path)) { LOG (GNUNET_ERROR_TYPE_DEBUG, "Ending iteration (client error)\n"); @@ -298,7 +323,7 @@ postgres_plugin_del (void *cls) struct Plugin *plugin = cls; uint32_t size; uint32_t oid; - GNUNET_HashCode key; + struct GNUNET_HashCode key; PGresult *res; res = PQexecPrepared (plugin->dbh, "getm", 0, NULL, NULL, NULL, 1); @@ -319,7 +344,7 @@ postgres_plugin_del (void *cls) } if ((3 != PQnfields (res)) || (sizeof (size) != PQfsize (res, 0)) || (sizeof (oid) != PQfsize (res, 1)) || - (sizeof (GNUNET_HashCode) != PQgetlength (res, 0, 2))) + (sizeof (struct GNUNET_HashCode) != PQgetlength (res, 0, 2))) { GNUNET_break (0); PQclear (res); @@ -327,7 +352,7 @@ postgres_plugin_del (void *cls) } size = ntohl (*(uint32_t *) PQgetvalue (res, 0, 0)); oid = ntohl (*(uint32_t *) PQgetvalue (res, 0, 1)); - memcpy (&key, PQgetvalue (res, 0, 2), sizeof (GNUNET_HashCode)); + memcpy (&key, PQgetvalue (res, 0, 2), sizeof (struct GNUNET_HashCode)); PQclear (res); if (GNUNET_OK != GNUNET_POSTGRES_delete_by_rowid (plugin->dbh, "delrow", oid)) return GNUNET_SYSERR; diff --git a/src/datacache/plugin_datacache_sqlite.c b/src/datacache/plugin_datacache_sqlite.c index db27de3..bf76f31 100644 --- a/src/datacache/plugin_datacache_sqlite.c +++ b/src/datacache/plugin_datacache_sqlite.c @@ -37,7 +37,7 @@ * How much overhead do we assume per entry in the * datacache? */ -#define OVERHEAD (sizeof(GNUNET_HashCode) + 32) +#define OVERHEAD (sizeof(struct GNUNET_HashCode) + 32) /** * Context for all functions in this plugin. @@ -95,52 +95,64 @@ sq_prepare (sqlite3 * dbh, const char *zSql, /* SQL statement, UTF-8 encoded * @param data data to store * @param type type of the value * @param discard_time when to discard the value in any case - * @return 0 on error, number of bytes used otherwise + * @param path_info_len number of entries in 'path_info' + * @param path_info array of peers that have processed the request + * @return 0 if duplicate, -1 on error, number of bytes used otherwise */ -static size_t -sqlite_plugin_put (void *cls, const GNUNET_HashCode * key, size_t size, - const char *data, enum GNUNET_BLOCK_Type type, - struct GNUNET_TIME_Absolute discard_time) +static ssize_t +sqlite_plugin_put (void *cls, + const struct GNUNET_HashCode *key, + size_t size, const char *data, + enum GNUNET_BLOCK_Type type, + struct GNUNET_TIME_Absolute discard_time, + unsigned int path_info_len, + const struct GNUNET_PeerIdentity *path_info) { struct Plugin *plugin = cls; sqlite3_stmt *stmt; int64_t dval; LOG (GNUNET_ERROR_TYPE_DEBUG, - "Processing `%s' of %u bytes with key `%4s' and expiration %llums\n", + "Processing `%s' of %u bytes with key `%4s' and expiration %s\n", "PUT", (unsigned int) size, GNUNET_h2s (key), - (unsigned long long) - GNUNET_TIME_absolute_get_remaining (discard_time).rel_value); + GNUNET_STRINGS_relative_time_to_string (GNUNET_TIME_absolute_get_remaining (discard_time), GNUNET_YES)); dval = (int64_t) discard_time.abs_value; if (dval < 0) dval = INT64_MAX; if (sq_prepare (plugin->dbh, - "INSERT INTO ds090 (type, expire, key, value) VALUES (?, ?, ?, ?)", + "INSERT INTO ds090 (type, expire, key, value, path) VALUES (?, ?, ?, ?, ?)", &stmt) != SQLITE_OK) { LOG_SQLITE (plugin->dbh, GNUNET_ERROR_TYPE_ERROR | GNUNET_ERROR_TYPE_BULK, "sq_prepare"); - return 0; + return -1; } if ((SQLITE_OK != sqlite3_bind_int (stmt, 1, type)) || (SQLITE_OK != sqlite3_bind_int64 (stmt, 2, dval)) || (SQLITE_OK != - sqlite3_bind_blob (stmt, 3, key, sizeof (GNUNET_HashCode), + sqlite3_bind_blob (stmt, 3, + key, sizeof (struct GNUNET_HashCode), SQLITE_TRANSIENT)) || - (SQLITE_OK != sqlite3_bind_blob (stmt, 4, data, size, SQLITE_TRANSIENT))) + (SQLITE_OK != sqlite3_bind_blob (stmt, 4, + data, size, + SQLITE_TRANSIENT)) || + (SQLITE_OK != sqlite3_bind_blob (stmt, 5, + path_info, + path_info_len * sizeof (struct GNUNET_PeerIdentity), + SQLITE_TRANSIENT))) { LOG_SQLITE (plugin->dbh, GNUNET_ERROR_TYPE_ERROR | GNUNET_ERROR_TYPE_BULK, "sqlite3_bind_xxx"); sqlite3_finalize (stmt); - return 0; + return -1; } if (SQLITE_DONE != sqlite3_step (stmt)) { LOG_SQLITE (plugin->dbh, GNUNET_ERROR_TYPE_ERROR | GNUNET_ERROR_TYPE_BULK, "sqlite3_step"); sqlite3_finalize (stmt); - return 0; + return -1; } if (SQLITE_OK != sqlite3_finalize (stmt)) LOG_SQLITE (plugin->dbh, GNUNET_ERROR_TYPE_ERROR | GNUNET_ERROR_TYPE_BULK, @@ -161,7 +173,7 @@ sqlite_plugin_put (void *cls, const GNUNET_HashCode * key, size_t size, * @return the number of results found */ static unsigned int -sqlite_plugin_get (void *cls, const GNUNET_HashCode * key, +sqlite_plugin_get (void *cls, const struct GNUNET_HashCode * key, enum GNUNET_BLOCK_Type type, GNUNET_DATACACHE_Iterator iter, void *iter_cls) { @@ -174,8 +186,10 @@ sqlite_plugin_get (void *cls, const GNUNET_HashCode * key, unsigned int cnt; unsigned int off; unsigned int total; + unsigned int psize; char scratch[256]; int64_t ntime; + const struct GNUNET_PeerIdentity *path; now = GNUNET_TIME_absolute_get (); LOG (GNUNET_ERROR_TYPE_DEBUG, "Processing `%s' for key `%4s'\n", "GET", @@ -192,7 +206,7 @@ sqlite_plugin_get (void *cls, const GNUNET_HashCode * key, ntime = (int64_t) now.abs_value; GNUNET_assert (ntime >= 0); if ((SQLITE_OK != - sqlite3_bind_blob (stmt, 1, key, sizeof (GNUNET_HashCode), + sqlite3_bind_blob (stmt, 1, key, sizeof (struct GNUNET_HashCode), SQLITE_TRANSIENT)) || (SQLITE_OK != sqlite3_bind_int (stmt, 2, type)) || (SQLITE_OK != sqlite3_bind_int64 (stmt, 3, now.abs_value))) @@ -230,7 +244,7 @@ sqlite_plugin_get (void *cls, const GNUNET_HashCode * key, { off = (off + 1) % total; GNUNET_snprintf (scratch, sizeof (scratch), - "SELECT value,expire FROM ds090 WHERE key=? AND type=? AND expire >= ? LIMIT 1 OFFSET %u", + "SELECT value,expire,path FROM ds090 WHERE key=? AND type=? AND expire >= ? LIMIT 1 OFFSET %u", off); if (sq_prepare (plugin->dbh, scratch, &stmt) != SQLITE_OK) { @@ -239,7 +253,7 @@ sqlite_plugin_get (void *cls, const GNUNET_HashCode * key, return cnt; } if ((SQLITE_OK != - sqlite3_bind_blob (stmt, 1, key, sizeof (GNUNET_HashCode), + sqlite3_bind_blob (stmt, 1, key, sizeof (struct GNUNET_HashCode), SQLITE_TRANSIENT)) || (SQLITE_OK != sqlite3_bind_int (stmt, 2, type)) || (SQLITE_OK != sqlite3_bind_int64 (stmt, 3, now.abs_value))) @@ -254,6 +268,17 @@ sqlite_plugin_get (void *cls, const GNUNET_HashCode * key, size = sqlite3_column_bytes (stmt, 0); dat = sqlite3_column_blob (stmt, 0); exp.abs_value = sqlite3_column_int64 (stmt, 1); + psize = sqlite3_column_bytes (stmt, 2); + if (0 != psize % sizeof (struct GNUNET_PeerIdentity)) + { + GNUNET_break (0); + psize = 0; + } + psize /= sizeof (struct GNUNET_PeerIdentity); + if (0 != psize) + path = sqlite3_column_blob (stmt, 2); + else + path = NULL; ntime = (int64_t) exp.abs_value; if (ntime == INT64_MAX) exp = GNUNET_TIME_UNIT_FOREVER_ABS; @@ -261,7 +286,7 @@ sqlite_plugin_get (void *cls, const GNUNET_HashCode * key, LOG (GNUNET_ERROR_TYPE_DEBUG, "Found %u-byte result when processing `%s' for key `%4s'\n", (unsigned int) size, "GET", GNUNET_h2s (key)); - if (GNUNET_OK != iter (iter_cls, exp, key, size, dat, type)) + if (GNUNET_OK != iter (iter_cls, key, size, dat, type, exp, psize, path)) { sqlite3_finalize (stmt); break; @@ -287,7 +312,7 @@ sqlite_plugin_del (void *cls) unsigned int dsize; sqlite3_stmt *stmt; sqlite3_stmt *dstmt; - GNUNET_HashCode hc; + struct GNUNET_HashCode hc; LOG (GNUNET_ERROR_TYPE_DEBUG, "Processing `%s'\n", "DEL"); stmt = NULL; @@ -311,8 +336,8 @@ sqlite_plugin_del (void *cls) return GNUNET_SYSERR; } rowid = sqlite3_column_int64 (stmt, 0); - GNUNET_assert (sqlite3_column_bytes (stmt, 1) == sizeof (GNUNET_HashCode)); - memcpy (&hc, sqlite3_column_blob (stmt, 1), sizeof (GNUNET_HashCode)); + GNUNET_assert (sqlite3_column_bytes (stmt, 1) == sizeof (struct GNUNET_HashCode)); + memcpy (&hc, sqlite3_column_blob (stmt, 1), sizeof (struct GNUNET_HashCode)); dsize = sqlite3_column_bytes (stmt, 2); if (SQLITE_OK != sqlite3_finalize (stmt)) LOG_SQLITE (plugin->dbh, GNUNET_ERROR_TYPE_ERROR | GNUNET_ERROR_TYPE_BULK, @@ -365,25 +390,33 @@ libgnunet_plugin_datacache_sqlite_init (void *cls) sqlite3 *dbh; char *emsg; - fn = GNUNET_DISK_mktemp ("gnunet-datacache"); - if (fn == NULL) + if (GNUNET_YES == + GNUNET_CONFIGURATION_get_value_yesno (env->cfg, + "datacache-sqlite", + "IN_MEMORY")) { - GNUNET_break (0); - return NULL; + if (SQLITE_OK != sqlite3_open (":memory:", &dbh)) + return NULL; + fn_utf8 = NULL; } -#ifdef ENABLE_NLS - fn_utf8 = GNUNET_STRINGS_to_utf8 (fn, strlen (fn), nl_langinfo (CODESET)); -#else - /* good luck */ - fn_utf8 = GNUNET_STRINGS_to_utf8 (fn, strlen (fn), "UTF-8"); -#endif - if (SQLITE_OK != sqlite3_open (fn_utf8, &dbh)) + else { + fn = GNUNET_DISK_mktemp ("gnunet-datacache"); + if (fn == NULL) + { + GNUNET_break (0); + return NULL; + } + /* fn should be UTF-8-encoded. If it isn't, it's a bug. */ + fn_utf8 = GNUNET_strdup (fn); + if (SQLITE_OK != sqlite3_open (fn_utf8, &dbh)) + { + GNUNET_free (fn); + GNUNET_free (fn_utf8); + return NULL; + } GNUNET_free (fn); - GNUNET_free (fn_utf8); - return NULL; } - GNUNET_free (fn); SQLITE3_EXEC (dbh, "PRAGMA temp_store=MEMORY"); SQLITE3_EXEC (dbh, "PRAGMA locking_mode=EXCLUSIVE"); @@ -391,11 +424,18 @@ libgnunet_plugin_datacache_sqlite_init (void *cls) SQLITE3_EXEC (dbh, "PRAGMA synchronous=OFF"); SQLITE3_EXEC (dbh, "PRAGMA count_changes=OFF"); SQLITE3_EXEC (dbh, "PRAGMA page_size=4092"); + if (GNUNET_YES == + GNUNET_CONFIGURATION_get_value_yesno (env->cfg, + "datacache-sqlite", + "IN_MEMORY")) + SQLITE3_EXEC (dbh, "PRAGMA sqlite_temp_store=3"); + SQLITE3_EXEC (dbh, "CREATE TABLE ds090 (" " type INTEGER NOT NULL DEFAULT 0," " expire INTEGER NOT NULL DEFAULT 0," " key BLOB NOT NULL DEFAULT ''," - " value BLOB NOT NULL DEFAULT '')"); + " value BLOB NOT NULL DEFAULT ''," + " path BLOB DEFAULT '')"); SQLITE3_EXEC (dbh, "CREATE INDEX idx_hashidx ON ds090 (key,type,expire)"); SQLITE3_EXEC (dbh, "CREATE INDEX idx_expire ON ds090 (expire)"); plugin = GNUNET_malloc (sizeof (struct Plugin)); @@ -430,9 +470,10 @@ libgnunet_plugin_datacache_sqlite_done (void *cls) #endif #if !WINDOWS || defined(__CYGWIN__) - if (0 != UNLINK (plugin->fn)) + if ( (NULL != plugin->fn) && + (0 != UNLINK (plugin->fn)) ) LOG_STRERROR_FILE (GNUNET_ERROR_TYPE_WARNING, "unlink", plugin->fn); - GNUNET_free (plugin->fn); + GNUNET_free_non_null (plugin->fn); #endif result = sqlite3_close (plugin->dbh); #if SQLITE_VERSION_NUMBER >= 3007000 @@ -458,9 +499,10 @@ libgnunet_plugin_datacache_sqlite_done (void *cls) LOG_SQLITE (plugin->dbh, GNUNET_ERROR_TYPE_ERROR, "sqlite3_close"); #if WINDOWS && !defined(__CYGWIN__) - if (0 != UNLINK (plugin->fn)) + if ( (NULL != plugin->fn) && + (0 != UNLINK (plugin->fn)) ) LOG_STRERROR_FILE (GNUNET_ERROR_TYPE_WARNING, "unlink", plugin->fn); - GNUNET_free (plugin->fn); + GNUNET_free_non_null (plugin->fn); #endif GNUNET_free (plugin); GNUNET_free (api); diff --git a/src/datacache/plugin_datacache_template.c b/src/datacache/plugin_datacache_template.c index 2d3f160..3066155 100644 --- a/src/datacache/plugin_datacache_template.c +++ b/src/datacache/plugin_datacache_template.c @@ -49,15 +49,19 @@ struct Plugin * @param data data to store * @param type type of the value * @param discard_time when to discard the value in any case - * @return 0 on error, number of bytes used otherwise + * @param path_info_len number of entries in 'path_info' + * @param path_info a path through the network + * @return 0 if duplicate, -1 on error, number of bytes used otherwise */ -static size_t -template_plugin_put (void *cls, const GNUNET_HashCode * key, size_t size, +static ssize_t +template_plugin_put (void *cls, const struct GNUNET_HashCode * key, size_t size, const char *data, enum GNUNET_BLOCK_Type type, - struct GNUNET_TIME_Absolute discard_time) + struct GNUNET_TIME_Absolute discard_time, + unsigned int path_info_len, + const struct GNUNET_PeerIdentity *path_info) { GNUNET_break (0); - return 0; + return -1; } @@ -73,7 +77,7 @@ template_plugin_put (void *cls, const GNUNET_HashCode * key, size_t size, * @return the number of results found */ static unsigned int -template_plugin_get (void *cls, const GNUNET_HashCode * key, +template_plugin_get (void *cls, const struct GNUNET_HashCode * key, enum GNUNET_BLOCK_Type type, GNUNET_DATACACHE_Iterator iter, void *iter_cls) { diff --git a/src/datacache/test_datacache.c b/src/datacache/test_datacache.c index d8d2f05..8c429cc 100644 --- a/src/datacache/test_datacache.c +++ b/src/datacache/test_datacache.c @@ -25,8 +25,7 @@ #include "platform.h" #include "gnunet_util_lib.h" #include "gnunet_datacache_lib.h" - -#define VERBOSE GNUNET_NO +#include "gnunet_testing_lib.h" #define ASSERT(x) do { if (! (x)) { printf("Error at %s:%d\n", __FILE__, __LINE__); goto FAILURE;} } while (0) @@ -39,18 +38,22 @@ static const char *plugin_name; static int -checkIt (void *cls, struct GNUNET_TIME_Absolute exp, - const GNUNET_HashCode * key, size_t size, const char *data, - enum GNUNET_BLOCK_Type type) +checkIt (void *cls, + const struct GNUNET_HashCode *key, + size_t size, const char *data, + enum GNUNET_BLOCK_Type type, + struct GNUNET_TIME_Absolute exp, + unsigned int path_len, + const struct GNUNET_PeerIdentity *path) { - if (size != sizeof (GNUNET_HashCode)) + if (size != sizeof (struct GNUNET_HashCode)) { - printf ("ERROR: Invalid size\n"); + GNUNET_break (0); ok = 2; } if (0 != memcmp (data, cls, size)) { - printf ("ERROR: Invalid data\n"); + GNUNET_break (0); ok = 3; } return GNUNET_OK; @@ -62,8 +65,8 @@ run (void *cls, char *const *args, const char *cfgfile, const struct GNUNET_CONFIGURATION_Handle *cfg) { struct GNUNET_DATACACHE_Handle *h; - GNUNET_HashCode k; - GNUNET_HashCode n; + struct GNUNET_HashCode k; + struct GNUNET_HashCode n; struct GNUNET_TIME_Absolute exp; unsigned int i; @@ -78,29 +81,31 @@ run (void *cls, char *const *args, const char *cfgfile, } exp = GNUNET_TIME_absolute_get (); exp.abs_value += 5 * 60 * 1000; - memset (&k, 0, sizeof (GNUNET_HashCode)); + memset (&k, 0, sizeof (struct GNUNET_HashCode)); for (i = 0; i < 100; i++) { - GNUNET_CRYPTO_hash (&k, sizeof (GNUNET_HashCode), &n); + GNUNET_CRYPTO_hash (&k, sizeof (struct GNUNET_HashCode), &n); ASSERT (GNUNET_OK == - GNUNET_DATACACHE_put (h, &k, sizeof (GNUNET_HashCode), - (const char *) &n, 1 + i % 16, exp)); + GNUNET_DATACACHE_put (h, &k, sizeof (struct GNUNET_HashCode), + (const char *) &n, 1 + i % 16, exp, + 0, NULL)); k = n; } - memset (&k, 0, sizeof (GNUNET_HashCode)); + memset (&k, 0, sizeof (struct GNUNET_HashCode)); for (i = 0; i < 100; i++) { - GNUNET_CRYPTO_hash (&k, sizeof (GNUNET_HashCode), &n); + GNUNET_CRYPTO_hash (&k, sizeof (struct GNUNET_HashCode), &n); ASSERT (1 == GNUNET_DATACACHE_get (h, &k, 1 + i % 16, &checkIt, &n)); k = n; } - memset (&k, 42, sizeof (GNUNET_HashCode)); - GNUNET_CRYPTO_hash (&k, sizeof (GNUNET_HashCode), &n); + memset (&k, 42, sizeof (struct GNUNET_HashCode)); + GNUNET_CRYPTO_hash (&k, sizeof (struct GNUNET_HashCode), &n); ASSERT (GNUNET_OK == - GNUNET_DATACACHE_put (h, &k, sizeof (GNUNET_HashCode), + GNUNET_DATACACHE_put (h, &k, sizeof (struct GNUNET_HashCode), (const char *) &n, 792, - GNUNET_TIME_UNIT_FOREVER_ABS)); + GNUNET_TIME_UNIT_FOREVER_ABS, + 0, NULL)); ASSERT (0 != GNUNET_DATACACHE_get (h, &k, 792, &checkIt, &n)); GNUNET_DATACACHE_destroy (h); @@ -116,16 +121,11 @@ FAILURE: int main (int argc, char *argv[]) { - char *pos; char cfg_name[128]; - char *const xargv[] = { "test-datacache", "-c", cfg_name, -#if VERBOSE - "-L", "DEBUG", -#endif NULL }; struct GNUNET_GETOPT_CommandLineOption options[] = { @@ -133,28 +133,14 @@ main (int argc, char *argv[]) }; GNUNET_log_setup ("test-datacache", -#if VERBOSE - "DEBUG", -#else "WARNING", -#endif NULL); - /* determine name of plugin to use */ - plugin_name = argv[0]; - while (NULL != (pos = strstr (plugin_name, "_"))) - plugin_name = pos + 1; - if (NULL != (pos = strstr (plugin_name, "."))) - pos[0] = 0; - else - pos = (char *) plugin_name; - + plugin_name = GNUNET_TESTING_get_testname_from_underscore (argv[0]); GNUNET_snprintf (cfg_name, sizeof (cfg_name), "test_datacache_data_%s.conf", plugin_name); - if (pos != plugin_name) - pos[0] = '.'; GNUNET_PROGRAM_run ((sizeof (xargv) / sizeof (char *)) - 1, xargv, "test-datacache", "nohelp", options, &run, NULL); - if (ok != 0) + if (0 != ok) FPRINTF (stderr, "Missed some testcases: %d\n", ok); return ok; } diff --git a/src/datacache/test_datacache_data_heap.conf b/src/datacache/test_datacache_data_heap.conf new file mode 100644 index 0000000..082cf48 --- /dev/null +++ b/src/datacache/test_datacache_data_heap.conf @@ -0,0 +1,4 @@ +[testcache] +QUOTA = 1 MB +DATABASE = heap + diff --git a/src/datacache/test_datacache_data_mysql.conf b/src/datacache/test_datacache_data_mysql.conf deleted file mode 100644 index bc9daa3..0000000 --- a/src/datacache/test_datacache_data_mysql.conf +++ /dev/null @@ -1,13 +0,0 @@ -[testcache] -QUOTA = 1 MB -DATABASE = mysql - -[datacache-mysql] -DATABASE = gnunetcheck -# CONFIG = ~/.my.cnf -# USER = -# PASSWORD = -# HOST = -# PORT = - - diff --git a/src/datacache/test_datacache_quota.c b/src/datacache/test_datacache_quota.c index cc47bdb..0400b50 100644 --- a/src/datacache/test_datacache_quota.c +++ b/src/datacache/test_datacache_quota.c @@ -25,8 +25,7 @@ #include "platform.h" #include "gnunet_util_lib.h" #include "gnunet_datacache_lib.h" - -#define VERBOSE GNUNET_NO +#include "gnunet_testing_lib.h" #define ASSERT(x) do { if (! (x)) { printf("Error at %s:%d\n", __FILE__, __LINE__); goto FAILURE;} } while (0) @@ -48,8 +47,8 @@ run (void *cls, char *const *args, const char *cfgfile, const struct GNUNET_CONFIGURATION_Handle *cfg) { struct GNUNET_DATACACHE_Handle *h; - GNUNET_HashCode k; - GNUNET_HashCode n; + struct GNUNET_HashCode k; + struct GNUNET_HashCode n; unsigned int i; unsigned int j; char buf[3200]; @@ -65,26 +64,26 @@ run (void *cls, char *const *args, const char *cfgfile, } exp = GNUNET_TIME_relative_to_absolute (GNUNET_TIME_UNIT_HOURS); memset (buf, 1, sizeof (buf)); - memset (&k, 0, sizeof (GNUNET_HashCode)); + memset (&k, 0, sizeof (struct GNUNET_HashCode)); for (i = 0; i < 10; i++) { FPRINTF (stderr, "%s", "."); - GNUNET_CRYPTO_hash (&k, sizeof (GNUNET_HashCode), &n); + GNUNET_CRYPTO_hash (&k, sizeof (struct GNUNET_HashCode), &n); for (j = i; j < sizeof (buf); j += 10) { exp.abs_value++; buf[j] = i; - ASSERT (GNUNET_OK == GNUNET_DATACACHE_put (h, &k, j, buf, 1 + i, exp)); + ASSERT (GNUNET_OK == GNUNET_DATACACHE_put (h, &k, j, buf, 1 + i, exp, 0, NULL)); ASSERT (0 < GNUNET_DATACACHE_get (h, &k, 1 + i, NULL, NULL)); } k = n; } FPRINTF (stderr, "%s", "\n"); - memset (&k, 0, sizeof (GNUNET_HashCode)); + memset (&k, 0, sizeof (struct GNUNET_HashCode)); for (i = 0; i < 10; i++) { FPRINTF (stderr, "%s", "."); - GNUNET_CRYPTO_hash (&k, sizeof (GNUNET_HashCode), &n); + GNUNET_CRYPTO_hash (&k, sizeof (struct GNUNET_HashCode), &n); if (i < 2) ASSERT (0 == GNUNET_DATACACHE_get (h, &k, 1 + i, NULL, NULL)); if (i == 9) @@ -104,16 +103,11 @@ FAILURE: int main (int argc, char *argv[]) { - char *pos; char cfg_name[128]; - char *const xargv[] = { "test-datacache-quota", "-c", cfg_name, -#if VERBOSE - "-L", "DEBUG", -#endif NULL }; struct GNUNET_GETOPT_CommandLineOption options[] = { @@ -121,29 +115,15 @@ main (int argc, char *argv[]) }; GNUNET_log_setup ("test-datacache-quota", -#if VERBOSE - "DEBUG", -#else "WARNING", -#endif NULL); - /* determine name of plugin to use */ - plugin_name = argv[0]; - while (NULL != (pos = strstr (plugin_name, "_"))) - plugin_name = pos + 1; - if (NULL != (pos = strstr (plugin_name, "."))) - pos[0] = 0; - else - pos = (char *) plugin_name; - + plugin_name = GNUNET_TESTING_get_testname_from_underscore (argv[0]); GNUNET_snprintf (cfg_name, sizeof (cfg_name), "test_datacache_data_%s.conf", plugin_name); - if (pos != plugin_name) - pos[0] = '.'; GNUNET_PROGRAM_run ((sizeof (xargv) / sizeof (char *)) - 1, xargv, "test-datacache-quota", "nohelp", options, &run, NULL); - if (ok != 0) + if (0 != ok) FPRINTF (stderr, "Missed some testcases: %d\n", ok); return ok; } diff --git a/src/datastore/Makefile.am b/src/datastore/Makefile.am index e7bccbc..57639fa 100644 --- a/src/datastore/Makefile.am +++ b/src/datastore/Makefile.am @@ -4,6 +4,8 @@ plugindir = $(libdir)/gnunet pkgcfgdir= $(pkgdatadir)/config.d/ +libexecdir= $(pkglibdir)/libexec/ + pkgcfg_DATA = \ datastore.conf @@ -31,7 +33,7 @@ libgnunetdatastore_la_LDFLAGS = \ -version-info 1:0:0 -bin_PROGRAMS = \ +libexec_PROGRAMS = \ gnunet-service-datastore gnunet_service_datastore_SOURCES = \ @@ -85,6 +87,7 @@ plugin_LTLIBRARIES = \ $(SQLITE_PLUGIN) \ $(MYSQL_PLUGIN) \ $(POSTGRES_PLUGIN) \ + libgnunet_plugin_datastore_heap.la \ libgnunet_plugin_datastore_template.la @@ -92,11 +95,21 @@ libgnunet_plugin_datastore_sqlite_la_SOURCES = \ plugin_datastore_sqlite.c libgnunet_plugin_datastore_sqlite_la_LIBADD = \ $(top_builddir)/src/statistics/libgnunetstatistics.la \ - $(top_builddir)/src/util/libgnunetutil.la $(XLIBS) -lsqlite3 + $(top_builddir)/src/util/libgnunetutil.la $(XLIBS) -lsqlite3 \ + $(LTLIBINTL) libgnunet_plugin_datastore_sqlite_la_LDFLAGS = \ $(GN_PLUGIN_LDFLAGS) +libgnunet_plugin_datastore_heap_la_SOURCES = \ + plugin_datastore_heap.c +libgnunet_plugin_datastore_heap_la_LIBADD = \ + $(top_builddir)/src/util/libgnunetutil.la $(XLIBS) \ + $(LTLIBINTL) +libgnunet_plugin_datastore_heap_la_LDFLAGS = \ + $(GN_PLUGIN_LDFLAGS) + + libgnunet_plugin_datastore_mysql_la_SOURCES = \ plugin_datastore_mysql.c libgnunet_plugin_datastore_mysql_la_LIBADD = \ @@ -123,11 +136,17 @@ libgnunet_plugin_datastore_postgres_la_CPPFLAGS = \ libgnunet_plugin_datastore_template_la_SOURCES = \ plugin_datastore_template.c libgnunet_plugin_datastore_template_la_LIBADD = \ - $(top_builddir)/src/util/libgnunetutil.la $(XLIBS) + $(top_builddir)/src/util/libgnunetutil.la $(XLIBS) \ + $(LTLIBINTL) libgnunet_plugin_datastore_template_la_LDFLAGS = \ $(GN_PLUGIN_LDFLAGS) check_PROGRAMS = \ + test_datastore_api_heap \ + test_datastore_api_management_heap \ + perf_datastore_api_heap \ + perf_plugin_datastore_heap \ + test_plugin_datastore_heap \ $(SQLITE_TESTS) \ $(MYSQL_TESTS) \ $(POSTGRES_TESTS) @@ -136,90 +155,139 @@ if ENABLE_TEST_RUN TESTS = $(check_PROGRAMS) endif +test_datastore_api_heap_SOURCES = \ + test_datastore_api.c +test_datastore_api_heap_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/datastore/libgnunetdatastore.la \ + $(top_builddir)/src/util/libgnunetutil.la + +test_datastore_api_management_heap_SOURCES = \ + test_datastore_api_management.c +test_datastore_api_management_heap_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/datastore/libgnunetdatastore.la \ + $(top_builddir)/src/util/libgnunetutil.la + +perf_datastore_api_heap_SOURCES = \ + perf_datastore_api.c +perf_datastore_api_heap_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/datastore/libgnunetdatastore.la \ + $(top_builddir)/src/util/libgnunetutil.la + +perf_plugin_datastore_heap_SOURCES = \ + perf_plugin_datastore.c +perf_plugin_datastore_heap_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/util/libgnunetutil.la + +test_plugin_datastore_heap_SOURCES = \ + test_plugin_datastore.c +test_plugin_datastore_heap_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/util/libgnunetutil.la + + test_datastore_api_sqlite_SOURCES = \ test_datastore_api.c test_datastore_api_sqlite_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/datastore/libgnunetdatastore.la \ $(top_builddir)/src/util/libgnunetutil.la test_datastore_api_management_sqlite_SOURCES = \ test_datastore_api_management.c test_datastore_api_management_sqlite_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/datastore/libgnunetdatastore.la \ $(top_builddir)/src/util/libgnunetutil.la perf_datastore_api_sqlite_SOURCES = \ perf_datastore_api.c perf_datastore_api_sqlite_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/datastore/libgnunetdatastore.la \ $(top_builddir)/src/util/libgnunetutil.la perf_plugin_datastore_sqlite_SOURCES = \ perf_plugin_datastore.c perf_plugin_datastore_sqlite_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la test_plugin_datastore_sqlite_SOURCES = \ test_plugin_datastore.c test_plugin_datastore_sqlite_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la test_datastore_api_mysql_SOURCES = \ test_datastore_api.c test_datastore_api_mysql_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/datastore/libgnunetdatastore.la \ $(top_builddir)/src/util/libgnunetutil.la test_datastore_api_management_mysql_SOURCES = \ test_datastore_api_management.c test_datastore_api_management_mysql_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/datastore/libgnunetdatastore.la \ $(top_builddir)/src/util/libgnunetutil.la perf_datastore_api_mysql_SOURCES = \ perf_datastore_api.c perf_datastore_api_mysql_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/datastore/libgnunetdatastore.la \ $(top_builddir)/src/util/libgnunetutil.la test_plugin_datastore_mysql_SOURCES = \ test_plugin_datastore.c test_plugin_datastore_mysql_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la perf_plugin_datastore_mysql_SOURCES = \ perf_plugin_datastore.c perf_plugin_datastore_mysql_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la test_datastore_api_postgres_SOURCES = \ test_datastore_api.c test_datastore_api_postgres_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/datastore/libgnunetdatastore.la \ $(top_builddir)/src/util/libgnunetutil.la test_datastore_api_management_postgres_SOURCES = \ test_datastore_api_management.c test_datastore_api_management_postgres_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/datastore/libgnunetdatastore.la \ $(top_builddir)/src/util/libgnunetutil.la perf_datastore_api_postgres_SOURCES = \ perf_datastore_api.c perf_datastore_api_postgres_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/datastore/libgnunetdatastore.la \ $(top_builddir)/src/util/libgnunetutil.la test_plugin_datastore_postgres_SOURCES = \ test_plugin_datastore.c test_plugin_datastore_postgres_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la perf_plugin_datastore_postgres_SOURCES = \ perf_plugin_datastore.c perf_plugin_datastore_postgres_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la @@ -227,10 +295,13 @@ EXTRA_DIST = \ test_defaults.conf \ test_datastore_api_data_sqlite.conf \ perf_plugin_datastore_data_sqlite.conf \ + test_plugin_datastore_data_sqlite.conf \ + test_datastore_api_data_heap.conf \ + perf_plugin_datastore_data_heap.conf \ + test_plugin_datastore_data_heap.conf \ test_datastore_api_data_mysql.conf \ perf_plugin_datastore_data_mysql.conf \ + test_plugin_datastore_data_mysql.conf \ test_datastore_api_data_postgres.conf \ perf_plugin_datastore_data_postgres.conf \ - test_plugin_datastore_data_mysql.conf \ - test_plugin_datastore_data_postgres.conf \ - test_plugin_datastore_data_sqlite.conf \ No newline at end of file + test_plugin_datastore_data_postgres.conf diff --git a/src/datastore/Makefile.in b/src/datastore/Makefile.in index 2488d24..8aa07ba 100644 --- a/src/datastore/Makefile.in +++ b/src/datastore/Makefile.in @@ -1,9 +1,9 @@ -# Makefile.in generated by automake 1.11.1 from Makefile.am. +# Makefile.in generated by automake 1.11.6 from Makefile.am. # @configure_input@ # Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, -# 2003, 2004, 2005, 2006, 2007, 2008, 2009 Free Software Foundation, -# Inc. +# 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Free Software +# Foundation, Inc. # This Makefile.in is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. @@ -18,6 +18,23 @@ VPATH = @srcdir@ +am__make_dryrun = \ + { \ + am__dry=no; \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + echo 'am--echo: ; @echo "AM" OK' | $(MAKE) -f - 2>/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } pkgdatadir = $(datadir)/@PACKAGE@ pkgincludedir = $(includedir)/@PACKAGE@ pkglibdir = $(libdir)/@PACKAGE@ @@ -37,22 +54,28 @@ POST_UNINSTALL = : build_triplet = @build@ host_triplet = @host@ target_triplet = @target@ -bin_PROGRAMS = gnunet-service-datastore$(EXEEXT) -check_PROGRAMS = $(am__EXEEXT_2) $(am__EXEEXT_4) $(am__EXEEXT_6) +libexec_PROGRAMS = gnunet-service-datastore$(EXEEXT) +check_PROGRAMS = test_datastore_api_heap$(EXEEXT) \ + test_datastore_api_management_heap$(EXEEXT) \ + perf_datastore_api_heap$(EXEEXT) \ + perf_plugin_datastore_heap$(EXEEXT) \ + test_plugin_datastore_heap$(EXEEXT) $(am__EXEEXT_2) \ + $(am__EXEEXT_4) $(am__EXEEXT_6) subdir = src/datastore DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in \ $(srcdir)/datastore.conf.in ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 am__aclocal_m4_deps = $(top_srcdir)/m4/absolute-header.m4 \ $(top_srcdir)/m4/align.m4 $(top_srcdir)/m4/argz.m4 \ - $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/iconv.m4 \ - $(top_srcdir)/m4/lib-ld.m4 $(top_srcdir)/m4/lib-link.m4 \ - $(top_srcdir)/m4/lib-prefix.m4 $(top_srcdir)/m4/libcurl.m4 \ - $(top_srcdir)/m4/libgcrypt.m4 $(top_srcdir)/m4/libtool.m4 \ - $(top_srcdir)/m4/libunistring.m4 $(top_srcdir)/m4/ltdl.m4 \ - $(top_srcdir)/m4/ltoptions.m4 $(top_srcdir)/m4/ltsugar.m4 \ - $(top_srcdir)/m4/ltversion.m4 $(top_srcdir)/m4/lt~obsolete.m4 \ - $(top_srcdir)/m4/nls.m4 $(top_srcdir)/m4/po.m4 \ + $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/glib-2.0.m4 \ + $(top_srcdir)/m4/iconv.m4 $(top_srcdir)/m4/lib-ld.m4 \ + $(top_srcdir)/m4/lib-link.m4 $(top_srcdir)/m4/lib-prefix.m4 \ + $(top_srcdir)/m4/libcurl.m4 $(top_srcdir)/m4/libgcrypt.m4 \ + $(top_srcdir)/m4/libtool.m4 $(top_srcdir)/m4/libunistring.m4 \ + $(top_srcdir)/m4/ltdl.m4 $(top_srcdir)/m4/ltoptions.m4 \ + $(top_srcdir)/m4/ltsugar.m4 $(top_srcdir)/m4/ltversion.m4 \ + $(top_srcdir)/m4/lt~obsolete.m4 $(top_srcdir)/m4/nls.m4 \ + $(top_srcdir)/m4/pkg.m4 $(top_srcdir)/m4/po.m4 \ $(top_srcdir)/m4/progtest.m4 $(top_srcdir)/acinclude.m4 \ $(top_srcdir)/configure.ac am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ @@ -82,10 +105,30 @@ am__nobase_list = $(am__nobase_strip_setup); \ am__base_list = \ sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \ sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g' +am__uninstall_files_from_dir = { \ + test -z "$$files" \ + || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \ + || { echo " ( cd '$$dir' && rm -f" $$files ")"; \ + $(am__cd) "$$dir" && rm -f $$files; }; \ + } am__installdirs = "$(DESTDIR)$(libdir)" "$(DESTDIR)$(plugindir)" \ - "$(DESTDIR)$(bindir)" "$(DESTDIR)$(pkgcfgdir)" + "$(DESTDIR)$(libexecdir)" "$(DESTDIR)$(pkgcfgdir)" LTLIBRARIES = $(lib_LTLIBRARIES) $(plugin_LTLIBRARIES) am__DEPENDENCIES_1 = +libgnunet_plugin_datastore_heap_la_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(am__DEPENDENCIES_1) $(am__DEPENDENCIES_1) +am_libgnunet_plugin_datastore_heap_la_OBJECTS = \ + plugin_datastore_heap.lo +libgnunet_plugin_datastore_heap_la_OBJECTS = \ + $(am_libgnunet_plugin_datastore_heap_la_OBJECTS) +AM_V_lt = $(am__v_lt_@AM_V@) +am__v_lt_ = $(am__v_lt_@AM_DEFAULT_V@) +am__v_lt_0 = --silent +libgnunet_plugin_datastore_heap_la_LINK = $(LIBTOOL) $(AM_V_lt) \ + --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link \ + $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ + $(libgnunet_plugin_datastore_heap_la_LDFLAGS) $(LDFLAGS) -o $@ libgnunet_plugin_datastore_mysql_la_DEPENDENCIES = \ $(top_builddir)/src/mysql/libgnunetmysql.la \ $(top_builddir)/src/statistics/libgnunetstatistics.la \ @@ -95,9 +138,6 @@ am_libgnunet_plugin_datastore_mysql_la_OBJECTS = \ libgnunet_plugin_datastore_mysql_la-plugin_datastore_mysql.lo libgnunet_plugin_datastore_mysql_la_OBJECTS = \ $(am_libgnunet_plugin_datastore_mysql_la_OBJECTS) -AM_V_lt = $(am__v_lt_$(V)) -am__v_lt_ = $(am__v_lt_$(AM_DEFAULT_VERBOSITY)) -am__v_lt_0 = --silent libgnunet_plugin_datastore_mysql_la_LINK = $(LIBTOOL) $(AM_V_lt) \ --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link \ $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ @@ -123,7 +163,7 @@ libgnunet_plugin_datastore_postgres_la_LINK = $(LIBTOOL) $(AM_V_lt) \ libgnunet_plugin_datastore_sqlite_la_DEPENDENCIES = \ $(top_builddir)/src/statistics/libgnunetstatistics.la \ $(top_builddir)/src/util/libgnunetutil.la \ - $(am__DEPENDENCIES_1) + $(am__DEPENDENCIES_1) $(am__DEPENDENCIES_1) am_libgnunet_plugin_datastore_sqlite_la_OBJECTS = \ plugin_datastore_sqlite.lo libgnunet_plugin_datastore_sqlite_la_OBJECTS = \ @@ -137,7 +177,7 @@ libgnunet_plugin_datastore_sqlite_la_LINK = $(LIBTOOL) $(AM_V_lt) \ @HAVE_SQLITE_TRUE@ -rpath $(plugindir) libgnunet_plugin_datastore_template_la_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la \ - $(am__DEPENDENCIES_1) + $(am__DEPENDENCIES_1) $(am__DEPENDENCIES_1) am_libgnunet_plugin_datastore_template_la_OBJECTS = \ plugin_datastore_template.lo libgnunet_plugin_datastore_template_la_OBJECTS = \ @@ -176,7 +216,7 @@ libgnunetdatastore_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ @HAVE_POSTGRES_TRUE@ test_datastore_api_management_postgres$(EXEEXT) \ @HAVE_POSTGRES_TRUE@ test_plugin_datastore_postgres$(EXEEXT) \ @HAVE_POSTGRES_TRUE@ $(am__EXEEXT_5) -PROGRAMS = $(bin_PROGRAMS) +PROGRAMS = $(libexec_PROGRAMS) am_gnunet_service_datastore_OBJECTS = \ gnunet-service-datastore.$(OBJEXT) gnunet_service_datastore_OBJECTS = \ @@ -185,47 +225,83 @@ gnunet_service_datastore_DEPENDENCIES = \ $(top_builddir)/src/statistics/libgnunetstatistics.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(am__DEPENDENCIES_1) +am_perf_datastore_api_heap_OBJECTS = perf_datastore_api.$(OBJEXT) +perf_datastore_api_heap_OBJECTS = \ + $(am_perf_datastore_api_heap_OBJECTS) +perf_datastore_api_heap_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/datastore/libgnunetdatastore.la \ + $(top_builddir)/src/util/libgnunetutil.la am_perf_datastore_api_mysql_OBJECTS = perf_datastore_api.$(OBJEXT) perf_datastore_api_mysql_OBJECTS = \ $(am_perf_datastore_api_mysql_OBJECTS) perf_datastore_api_mysql_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/datastore/libgnunetdatastore.la \ $(top_builddir)/src/util/libgnunetutil.la am_perf_datastore_api_postgres_OBJECTS = perf_datastore_api.$(OBJEXT) perf_datastore_api_postgres_OBJECTS = \ $(am_perf_datastore_api_postgres_OBJECTS) perf_datastore_api_postgres_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/datastore/libgnunetdatastore.la \ $(top_builddir)/src/util/libgnunetutil.la am_perf_datastore_api_sqlite_OBJECTS = perf_datastore_api.$(OBJEXT) perf_datastore_api_sqlite_OBJECTS = \ $(am_perf_datastore_api_sqlite_OBJECTS) perf_datastore_api_sqlite_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/datastore/libgnunetdatastore.la \ $(top_builddir)/src/util/libgnunetutil.la +am_perf_plugin_datastore_heap_OBJECTS = \ + perf_plugin_datastore.$(OBJEXT) +perf_plugin_datastore_heap_OBJECTS = \ + $(am_perf_plugin_datastore_heap_OBJECTS) +perf_plugin_datastore_heap_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/util/libgnunetutil.la am_perf_plugin_datastore_mysql_OBJECTS = \ perf_plugin_datastore.$(OBJEXT) perf_plugin_datastore_mysql_OBJECTS = \ $(am_perf_plugin_datastore_mysql_OBJECTS) perf_plugin_datastore_mysql_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la am_perf_plugin_datastore_postgres_OBJECTS = \ perf_plugin_datastore.$(OBJEXT) perf_plugin_datastore_postgres_OBJECTS = \ $(am_perf_plugin_datastore_postgres_OBJECTS) perf_plugin_datastore_postgres_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la am_perf_plugin_datastore_sqlite_OBJECTS = \ perf_plugin_datastore.$(OBJEXT) perf_plugin_datastore_sqlite_OBJECTS = \ $(am_perf_plugin_datastore_sqlite_OBJECTS) perf_plugin_datastore_sqlite_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/util/libgnunetutil.la +am_test_datastore_api_heap_OBJECTS = test_datastore_api.$(OBJEXT) +test_datastore_api_heap_OBJECTS = \ + $(am_test_datastore_api_heap_OBJECTS) +test_datastore_api_heap_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/datastore/libgnunetdatastore.la \ + $(top_builddir)/src/util/libgnunetutil.la +am_test_datastore_api_management_heap_OBJECTS = \ + test_datastore_api_management.$(OBJEXT) +test_datastore_api_management_heap_OBJECTS = \ + $(am_test_datastore_api_management_heap_OBJECTS) +test_datastore_api_management_heap_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/datastore/libgnunetdatastore.la \ $(top_builddir)/src/util/libgnunetutil.la am_test_datastore_api_management_mysql_OBJECTS = \ test_datastore_api_management.$(OBJEXT) test_datastore_api_management_mysql_OBJECTS = \ $(am_test_datastore_api_management_mysql_OBJECTS) test_datastore_api_management_mysql_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/datastore/libgnunetdatastore.la \ $(top_builddir)/src/util/libgnunetutil.la am_test_datastore_api_management_postgres_OBJECTS = \ @@ -233,6 +309,7 @@ am_test_datastore_api_management_postgres_OBJECTS = \ test_datastore_api_management_postgres_OBJECTS = \ $(am_test_datastore_api_management_postgres_OBJECTS) test_datastore_api_management_postgres_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/datastore/libgnunetdatastore.la \ $(top_builddir)/src/util/libgnunetutil.la am_test_datastore_api_management_sqlite_OBJECTS = \ @@ -240,43 +317,57 @@ am_test_datastore_api_management_sqlite_OBJECTS = \ test_datastore_api_management_sqlite_OBJECTS = \ $(am_test_datastore_api_management_sqlite_OBJECTS) test_datastore_api_management_sqlite_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/datastore/libgnunetdatastore.la \ $(top_builddir)/src/util/libgnunetutil.la am_test_datastore_api_mysql_OBJECTS = test_datastore_api.$(OBJEXT) test_datastore_api_mysql_OBJECTS = \ $(am_test_datastore_api_mysql_OBJECTS) test_datastore_api_mysql_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/datastore/libgnunetdatastore.la \ $(top_builddir)/src/util/libgnunetutil.la am_test_datastore_api_postgres_OBJECTS = test_datastore_api.$(OBJEXT) test_datastore_api_postgres_OBJECTS = \ $(am_test_datastore_api_postgres_OBJECTS) test_datastore_api_postgres_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/datastore/libgnunetdatastore.la \ $(top_builddir)/src/util/libgnunetutil.la am_test_datastore_api_sqlite_OBJECTS = test_datastore_api.$(OBJEXT) test_datastore_api_sqlite_OBJECTS = \ $(am_test_datastore_api_sqlite_OBJECTS) test_datastore_api_sqlite_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/datastore/libgnunetdatastore.la \ $(top_builddir)/src/util/libgnunetutil.la +am_test_plugin_datastore_heap_OBJECTS = \ + test_plugin_datastore.$(OBJEXT) +test_plugin_datastore_heap_OBJECTS = \ + $(am_test_plugin_datastore_heap_OBJECTS) +test_plugin_datastore_heap_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/util/libgnunetutil.la am_test_plugin_datastore_mysql_OBJECTS = \ test_plugin_datastore.$(OBJEXT) test_plugin_datastore_mysql_OBJECTS = \ $(am_test_plugin_datastore_mysql_OBJECTS) test_plugin_datastore_mysql_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la am_test_plugin_datastore_postgres_OBJECTS = \ test_plugin_datastore.$(OBJEXT) test_plugin_datastore_postgres_OBJECTS = \ $(am_test_plugin_datastore_postgres_OBJECTS) test_plugin_datastore_postgres_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la am_test_plugin_datastore_sqlite_OBJECTS = \ test_plugin_datastore.$(OBJEXT) test_plugin_datastore_sqlite_OBJECTS = \ $(am_test_plugin_datastore_sqlite_OBJECTS) test_plugin_datastore_sqlite_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la DEFAULT_INCLUDES = -I.@am__isrc@ -I$(top_builddir) depcomp = $(SHELL) $(top_srcdir)/depcomp @@ -288,64 +379,81 @@ LTCOMPILE = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) \ $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) \ $(AM_CFLAGS) $(CFLAGS) -AM_V_CC = $(am__v_CC_$(V)) -am__v_CC_ = $(am__v_CC_$(AM_DEFAULT_VERBOSITY)) +AM_V_CC = $(am__v_CC_@AM_V@) +am__v_CC_ = $(am__v_CC_@AM_DEFAULT_V@) am__v_CC_0 = @echo " CC " $@; -AM_V_at = $(am__v_at_$(V)) -am__v_at_ = $(am__v_at_$(AM_DEFAULT_VERBOSITY)) +AM_V_at = $(am__v_at_@AM_V@) +am__v_at_ = $(am__v_at_@AM_DEFAULT_V@) am__v_at_0 = @ CCLD = $(CC) LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ $(AM_LDFLAGS) $(LDFLAGS) -o $@ -AM_V_CCLD = $(am__v_CCLD_$(V)) -am__v_CCLD_ = $(am__v_CCLD_$(AM_DEFAULT_VERBOSITY)) +AM_V_CCLD = $(am__v_CCLD_@AM_V@) +am__v_CCLD_ = $(am__v_CCLD_@AM_DEFAULT_V@) am__v_CCLD_0 = @echo " CCLD " $@; -AM_V_GEN = $(am__v_GEN_$(V)) -am__v_GEN_ = $(am__v_GEN_$(AM_DEFAULT_VERBOSITY)) +AM_V_GEN = $(am__v_GEN_@AM_V@) +am__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@) am__v_GEN_0 = @echo " GEN " $@; -SOURCES = $(libgnunet_plugin_datastore_mysql_la_SOURCES) \ +SOURCES = $(libgnunet_plugin_datastore_heap_la_SOURCES) \ + $(libgnunet_plugin_datastore_mysql_la_SOURCES) \ $(libgnunet_plugin_datastore_postgres_la_SOURCES) \ $(libgnunet_plugin_datastore_sqlite_la_SOURCES) \ $(libgnunet_plugin_datastore_template_la_SOURCES) \ $(libgnunetdatastore_la_SOURCES) \ $(gnunet_service_datastore_SOURCES) \ + $(perf_datastore_api_heap_SOURCES) \ $(perf_datastore_api_mysql_SOURCES) \ $(perf_datastore_api_postgres_SOURCES) \ $(perf_datastore_api_sqlite_SOURCES) \ + $(perf_plugin_datastore_heap_SOURCES) \ $(perf_plugin_datastore_mysql_SOURCES) \ $(perf_plugin_datastore_postgres_SOURCES) \ $(perf_plugin_datastore_sqlite_SOURCES) \ + $(test_datastore_api_heap_SOURCES) \ + $(test_datastore_api_management_heap_SOURCES) \ $(test_datastore_api_management_mysql_SOURCES) \ $(test_datastore_api_management_postgres_SOURCES) \ $(test_datastore_api_management_sqlite_SOURCES) \ $(test_datastore_api_mysql_SOURCES) \ $(test_datastore_api_postgres_SOURCES) \ $(test_datastore_api_sqlite_SOURCES) \ + $(test_plugin_datastore_heap_SOURCES) \ $(test_plugin_datastore_mysql_SOURCES) \ $(test_plugin_datastore_postgres_SOURCES) \ $(test_plugin_datastore_sqlite_SOURCES) -DIST_SOURCES = $(libgnunet_plugin_datastore_mysql_la_SOURCES) \ +DIST_SOURCES = $(libgnunet_plugin_datastore_heap_la_SOURCES) \ + $(libgnunet_plugin_datastore_mysql_la_SOURCES) \ $(libgnunet_plugin_datastore_postgres_la_SOURCES) \ $(libgnunet_plugin_datastore_sqlite_la_SOURCES) \ $(libgnunet_plugin_datastore_template_la_SOURCES) \ $(libgnunetdatastore_la_SOURCES) \ $(gnunet_service_datastore_SOURCES) \ + $(perf_datastore_api_heap_SOURCES) \ $(perf_datastore_api_mysql_SOURCES) \ $(perf_datastore_api_postgres_SOURCES) \ $(perf_datastore_api_sqlite_SOURCES) \ + $(perf_plugin_datastore_heap_SOURCES) \ $(perf_plugin_datastore_mysql_SOURCES) \ $(perf_plugin_datastore_postgres_SOURCES) \ $(perf_plugin_datastore_sqlite_SOURCES) \ + $(test_datastore_api_heap_SOURCES) \ + $(test_datastore_api_management_heap_SOURCES) \ $(test_datastore_api_management_mysql_SOURCES) \ $(test_datastore_api_management_postgres_SOURCES) \ $(test_datastore_api_management_sqlite_SOURCES) \ $(test_datastore_api_mysql_SOURCES) \ $(test_datastore_api_postgres_SOURCES) \ $(test_datastore_api_sqlite_SOURCES) \ + $(test_plugin_datastore_heap_SOURCES) \ $(test_plugin_datastore_mysql_SOURCES) \ $(test_plugin_datastore_postgres_SOURCES) \ $(test_plugin_datastore_sqlite_SOURCES) +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac DATA = $(pkgcfg_DATA) ETAGS = etags CTAGS = ctags @@ -387,6 +495,10 @@ EXEEXT = @EXEEXT@ EXT_LIBS = @EXT_LIBS@ EXT_LIB_PATH = @EXT_LIB_PATH@ FGREP = @FGREP@ +GLIB_CFLAGS = @GLIB_CFLAGS@ +GLIB_GENMARSHAL = @GLIB_GENMARSHAL@ +GLIB_LIBS = @GLIB_LIBS@ +GLIB_MKENUMS = @GLIB_MKENUMS@ GMSGFMT = @GMSGFMT@ GMSGFMT_015 = @GMSGFMT_015@ GNUNETDNS_GROUP = @GNUNETDNS_GROUP@ @@ -397,6 +509,7 @@ GN_LIBINTL = @GN_LIBINTL@ GN_LIB_LDFLAGS = @GN_LIB_LDFLAGS@ GN_PLUGIN_LDFLAGS = @GN_PLUGIN_LDFLAGS@ GN_USER_HOME_DIR = @GN_USER_HOME_DIR@ +GOBJECT_QUERY = @GOBJECT_QUERY@ GREP = @GREP@ HAVE_LIBUNISTRING = @HAVE_LIBUNISTRING@ INCLTDL = @INCLTDL@ @@ -419,6 +532,8 @@ LIBCURL_CPPFLAGS = @LIBCURL_CPPFLAGS@ LIBGCRYPT_CFLAGS = @LIBGCRYPT_CFLAGS@ LIBGCRYPT_CONFIG = @LIBGCRYPT_CONFIG@ LIBGCRYPT_LIBS = @LIBGCRYPT_LIBS@ +LIBGTOP_CFLAGS = @LIBGTOP_CFLAGS@ +LIBGTOP_LIBS = @LIBGTOP_LIBS@ LIBICONV = @LIBICONV@ LIBINTL = @LIBINTL@ LIBLTDL = @LIBLTDL@ @@ -440,6 +555,7 @@ LT_CONFIG_H = @LT_CONFIG_H@ LT_DLLOADERS = @LT_DLLOADERS@ LT_DLPREOPEN = @LT_DLPREOPEN@ MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ MKDIR_P = @MKDIR_P@ MONKEYPREFIX = @MONKEYPREFIX@ MSGFMT = @MSGFMT@ @@ -449,6 +565,7 @@ MYSQL_CPPFLAGS = @MYSQL_CPPFLAGS@ MYSQL_LDFLAGS = @MYSQL_LDFLAGS@ NM = @NM@ NMEDIT = @NMEDIT@ +NSS_DIR = @NSS_DIR@ OBJC = @OBJC@ OBJCDEPMODE = @OBJCDEPMODE@ OBJCFLAGS = @OBJCFLAGS@ @@ -464,6 +581,7 @@ PACKAGE_TARNAME = @PACKAGE_TARNAME@ PACKAGE_URL = @PACKAGE_URL@ PACKAGE_VERSION = @PACKAGE_VERSION@ PATH_SEPARATOR = @PATH_SEPARATOR@ +PKG_CONFIG = @PKG_CONFIG@ POSTGRES_CPPFLAGS = @POSTGRES_CPPFLAGS@ POSTGRES_LDFLAGS = @POSTGRES_LDFLAGS@ POSUB = @POSUB@ @@ -495,6 +613,7 @@ abs_builddir = @abs_builddir@ abs_srcdir = @abs_srcdir@ abs_top_builddir = @abs_top_builddir@ abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ ac_ct_CC = @ac_ct_CC@ ac_ct_CXX = @ac_ct_CXX@ ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ @@ -517,6 +636,7 @@ datarootdir = @datarootdir@ docdir = @docdir@ dvidir = @dvidir@ exec_prefix = @exec_prefix@ +gitcommand = @gitcommand@ host = @host@ host_alias = @host_alias@ host_cpu = @host_cpu@ @@ -527,10 +647,9 @@ includedir = @includedir@ infodir = @infodir@ install_sh = @install_sh@ libdir = @libdir@ -libexecdir = @libexecdir@ +libexecdir = $(pkglibdir)/libexec/ localedir = @localedir@ localstatedir = @localstatedir@ -lt_ECHO = @lt_ECHO@ ltdl_LIBOBJS = @ltdl_LIBOBJS@ ltdl_LTLIBOBJS = @ltdl_LTLIBOBJS@ mandir = @mandir@ @@ -548,6 +667,7 @@ sbindir = @sbindir@ sharedstatedir = @sharedstatedir@ srcdir = @srcdir@ subdirs = @subdirs@ +svnversioncommand = @svnversioncommand@ sys_symbol_underscore = @sys_symbol_underscore@ sysconfdir = @sysconfdir@ target = @target@ @@ -627,6 +747,7 @@ plugin_LTLIBRARIES = \ $(SQLITE_PLUGIN) \ $(MYSQL_PLUGIN) \ $(POSTGRES_PLUGIN) \ + libgnunet_plugin_datastore_heap.la \ libgnunet_plugin_datastore_template.la libgnunet_plugin_datastore_sqlite_la_SOURCES = \ @@ -634,11 +755,22 @@ libgnunet_plugin_datastore_sqlite_la_SOURCES = \ libgnunet_plugin_datastore_sqlite_la_LIBADD = \ $(top_builddir)/src/statistics/libgnunetstatistics.la \ - $(top_builddir)/src/util/libgnunetutil.la $(XLIBS) -lsqlite3 + $(top_builddir)/src/util/libgnunetutil.la $(XLIBS) -lsqlite3 \ + $(LTLIBINTL) libgnunet_plugin_datastore_sqlite_la_LDFLAGS = \ $(GN_PLUGIN_LDFLAGS) +libgnunet_plugin_datastore_heap_la_SOURCES = \ + plugin_datastore_heap.c + +libgnunet_plugin_datastore_heap_la_LIBADD = \ + $(top_builddir)/src/util/libgnunetutil.la $(XLIBS) \ + $(LTLIBINTL) + +libgnunet_plugin_datastore_heap_la_LDFLAGS = \ + $(GN_PLUGIN_LDFLAGS) + libgnunet_plugin_datastore_mysql_la_SOURCES = \ plugin_datastore_mysql.c @@ -671,16 +803,56 @@ libgnunet_plugin_datastore_template_la_SOURCES = \ plugin_datastore_template.c libgnunet_plugin_datastore_template_la_LIBADD = \ - $(top_builddir)/src/util/libgnunetutil.la $(XLIBS) + $(top_builddir)/src/util/libgnunetutil.la $(XLIBS) \ + $(LTLIBINTL) libgnunet_plugin_datastore_template_la_LDFLAGS = \ $(GN_PLUGIN_LDFLAGS) @ENABLE_TEST_RUN_TRUE@TESTS = $(check_PROGRAMS) +test_datastore_api_heap_SOURCES = \ + test_datastore_api.c + +test_datastore_api_heap_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/datastore/libgnunetdatastore.la \ + $(top_builddir)/src/util/libgnunetutil.la + +test_datastore_api_management_heap_SOURCES = \ + test_datastore_api_management.c + +test_datastore_api_management_heap_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/datastore/libgnunetdatastore.la \ + $(top_builddir)/src/util/libgnunetutil.la + +perf_datastore_api_heap_SOURCES = \ + perf_datastore_api.c + +perf_datastore_api_heap_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/datastore/libgnunetdatastore.la \ + $(top_builddir)/src/util/libgnunetutil.la + +perf_plugin_datastore_heap_SOURCES = \ + perf_plugin_datastore.c + +perf_plugin_datastore_heap_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/util/libgnunetutil.la + +test_plugin_datastore_heap_SOURCES = \ + test_plugin_datastore.c + +test_plugin_datastore_heap_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/util/libgnunetutil.la + test_datastore_api_sqlite_SOURCES = \ test_datastore_api.c test_datastore_api_sqlite_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/datastore/libgnunetdatastore.la \ $(top_builddir)/src/util/libgnunetutil.la @@ -688,6 +860,7 @@ test_datastore_api_management_sqlite_SOURCES = \ test_datastore_api_management.c test_datastore_api_management_sqlite_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/datastore/libgnunetdatastore.la \ $(top_builddir)/src/util/libgnunetutil.la @@ -695,6 +868,7 @@ perf_datastore_api_sqlite_SOURCES = \ perf_datastore_api.c perf_datastore_api_sqlite_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/datastore/libgnunetdatastore.la \ $(top_builddir)/src/util/libgnunetutil.la @@ -702,18 +876,21 @@ perf_plugin_datastore_sqlite_SOURCES = \ perf_plugin_datastore.c perf_plugin_datastore_sqlite_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la test_plugin_datastore_sqlite_SOURCES = \ test_plugin_datastore.c test_plugin_datastore_sqlite_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la test_datastore_api_mysql_SOURCES = \ test_datastore_api.c test_datastore_api_mysql_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/datastore/libgnunetdatastore.la \ $(top_builddir)/src/util/libgnunetutil.la @@ -721,6 +898,7 @@ test_datastore_api_management_mysql_SOURCES = \ test_datastore_api_management.c test_datastore_api_management_mysql_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/datastore/libgnunetdatastore.la \ $(top_builddir)/src/util/libgnunetutil.la @@ -728,6 +906,7 @@ perf_datastore_api_mysql_SOURCES = \ perf_datastore_api.c perf_datastore_api_mysql_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/datastore/libgnunetdatastore.la \ $(top_builddir)/src/util/libgnunetutil.la @@ -735,18 +914,21 @@ test_plugin_datastore_mysql_SOURCES = \ test_plugin_datastore.c test_plugin_datastore_mysql_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la perf_plugin_datastore_mysql_SOURCES = \ perf_plugin_datastore.c perf_plugin_datastore_mysql_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la test_datastore_api_postgres_SOURCES = \ test_datastore_api.c test_datastore_api_postgres_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/datastore/libgnunetdatastore.la \ $(top_builddir)/src/util/libgnunetutil.la @@ -754,6 +936,7 @@ test_datastore_api_management_postgres_SOURCES = \ test_datastore_api_management.c test_datastore_api_management_postgres_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/datastore/libgnunetdatastore.la \ $(top_builddir)/src/util/libgnunetutil.la @@ -761,6 +944,7 @@ perf_datastore_api_postgres_SOURCES = \ perf_datastore_api.c perf_datastore_api_postgres_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/datastore/libgnunetdatastore.la \ $(top_builddir)/src/util/libgnunetutil.la @@ -768,25 +952,30 @@ test_plugin_datastore_postgres_SOURCES = \ test_plugin_datastore.c test_plugin_datastore_postgres_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la perf_plugin_datastore_postgres_SOURCES = \ perf_plugin_datastore.c perf_plugin_datastore_postgres_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la EXTRA_DIST = \ test_defaults.conf \ test_datastore_api_data_sqlite.conf \ perf_plugin_datastore_data_sqlite.conf \ + test_plugin_datastore_data_sqlite.conf \ + test_datastore_api_data_heap.conf \ + perf_plugin_datastore_data_heap.conf \ + test_plugin_datastore_data_heap.conf \ test_datastore_api_data_mysql.conf \ perf_plugin_datastore_data_mysql.conf \ + test_plugin_datastore_data_mysql.conf \ test_datastore_api_data_postgres.conf \ perf_plugin_datastore_data_postgres.conf \ - test_plugin_datastore_data_mysql.conf \ - test_plugin_datastore_data_postgres.conf \ - test_plugin_datastore_data_sqlite.conf + test_plugin_datastore_data_postgres.conf all: all-am @@ -826,7 +1015,6 @@ datastore.conf: $(top_builddir)/config.status $(srcdir)/datastore.conf.in cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ install-libLTLIBRARIES: $(lib_LTLIBRARIES) @$(NORMAL_INSTALL) - test -z "$(libdir)" || $(MKDIR_P) "$(DESTDIR)$(libdir)" @list='$(lib_LTLIBRARIES)'; test -n "$(libdir)" || list=; \ list2=; for p in $$list; do \ if test -f $$p; then \ @@ -834,6 +1022,8 @@ install-libLTLIBRARIES: $(lib_LTLIBRARIES) else :; fi; \ done; \ test -z "$$list2" || { \ + echo " $(MKDIR_P) '$(DESTDIR)$(libdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libdir)" || exit 1; \ echo " $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 '$(DESTDIR)$(libdir)'"; \ $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 "$(DESTDIR)$(libdir)"; \ } @@ -857,7 +1047,6 @@ clean-libLTLIBRARIES: done install-pluginLTLIBRARIES: $(plugin_LTLIBRARIES) @$(NORMAL_INSTALL) - test -z "$(plugindir)" || $(MKDIR_P) "$(DESTDIR)$(plugindir)" @list='$(plugin_LTLIBRARIES)'; test -n "$(plugindir)" || list=; \ list2=; for p in $$list; do \ if test -f $$p; then \ @@ -865,6 +1054,8 @@ install-pluginLTLIBRARIES: $(plugin_LTLIBRARIES) else :; fi; \ done; \ test -z "$$list2" || { \ + echo " $(MKDIR_P) '$(DESTDIR)$(plugindir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(plugindir)" || exit 1; \ echo " $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 '$(DESTDIR)$(plugindir)'"; \ $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 "$(DESTDIR)$(plugindir)"; \ } @@ -886,20 +1077,34 @@ clean-pluginLTLIBRARIES: echo "rm -f \"$${dir}/so_locations\""; \ rm -f "$${dir}/so_locations"; \ done -libgnunet_plugin_datastore_mysql.la: $(libgnunet_plugin_datastore_mysql_la_OBJECTS) $(libgnunet_plugin_datastore_mysql_la_DEPENDENCIES) +libgnunet_plugin_datastore_heap.la: $(libgnunet_plugin_datastore_heap_la_OBJECTS) $(libgnunet_plugin_datastore_heap_la_DEPENDENCIES) $(EXTRA_libgnunet_plugin_datastore_heap_la_DEPENDENCIES) + $(AM_V_CCLD)$(libgnunet_plugin_datastore_heap_la_LINK) -rpath $(plugindir) $(libgnunet_plugin_datastore_heap_la_OBJECTS) $(libgnunet_plugin_datastore_heap_la_LIBADD) $(LIBS) +libgnunet_plugin_datastore_mysql.la: $(libgnunet_plugin_datastore_mysql_la_OBJECTS) $(libgnunet_plugin_datastore_mysql_la_DEPENDENCIES) $(EXTRA_libgnunet_plugin_datastore_mysql_la_DEPENDENCIES) $(AM_V_CCLD)$(libgnunet_plugin_datastore_mysql_la_LINK) $(am_libgnunet_plugin_datastore_mysql_la_rpath) $(libgnunet_plugin_datastore_mysql_la_OBJECTS) $(libgnunet_plugin_datastore_mysql_la_LIBADD) $(LIBS) -libgnunet_plugin_datastore_postgres.la: $(libgnunet_plugin_datastore_postgres_la_OBJECTS) $(libgnunet_plugin_datastore_postgres_la_DEPENDENCIES) +libgnunet_plugin_datastore_postgres.la: $(libgnunet_plugin_datastore_postgres_la_OBJECTS) $(libgnunet_plugin_datastore_postgres_la_DEPENDENCIES) $(EXTRA_libgnunet_plugin_datastore_postgres_la_DEPENDENCIES) $(AM_V_CCLD)$(libgnunet_plugin_datastore_postgres_la_LINK) $(am_libgnunet_plugin_datastore_postgres_la_rpath) $(libgnunet_plugin_datastore_postgres_la_OBJECTS) $(libgnunet_plugin_datastore_postgres_la_LIBADD) $(LIBS) -libgnunet_plugin_datastore_sqlite.la: $(libgnunet_plugin_datastore_sqlite_la_OBJECTS) $(libgnunet_plugin_datastore_sqlite_la_DEPENDENCIES) +libgnunet_plugin_datastore_sqlite.la: $(libgnunet_plugin_datastore_sqlite_la_OBJECTS) $(libgnunet_plugin_datastore_sqlite_la_DEPENDENCIES) $(EXTRA_libgnunet_plugin_datastore_sqlite_la_DEPENDENCIES) $(AM_V_CCLD)$(libgnunet_plugin_datastore_sqlite_la_LINK) $(am_libgnunet_plugin_datastore_sqlite_la_rpath) $(libgnunet_plugin_datastore_sqlite_la_OBJECTS) $(libgnunet_plugin_datastore_sqlite_la_LIBADD) $(LIBS) -libgnunet_plugin_datastore_template.la: $(libgnunet_plugin_datastore_template_la_OBJECTS) $(libgnunet_plugin_datastore_template_la_DEPENDENCIES) +libgnunet_plugin_datastore_template.la: $(libgnunet_plugin_datastore_template_la_OBJECTS) $(libgnunet_plugin_datastore_template_la_DEPENDENCIES) $(EXTRA_libgnunet_plugin_datastore_template_la_DEPENDENCIES) $(AM_V_CCLD)$(libgnunet_plugin_datastore_template_la_LINK) -rpath $(plugindir) $(libgnunet_plugin_datastore_template_la_OBJECTS) $(libgnunet_plugin_datastore_template_la_LIBADD) $(LIBS) -libgnunetdatastore.la: $(libgnunetdatastore_la_OBJECTS) $(libgnunetdatastore_la_DEPENDENCIES) +libgnunetdatastore.la: $(libgnunetdatastore_la_OBJECTS) $(libgnunetdatastore_la_DEPENDENCIES) $(EXTRA_libgnunetdatastore_la_DEPENDENCIES) $(AM_V_CCLD)$(libgnunetdatastore_la_LINK) -rpath $(libdir) $(libgnunetdatastore_la_OBJECTS) $(libgnunetdatastore_la_LIBADD) $(LIBS) -install-binPROGRAMS: $(bin_PROGRAMS) + +clean-checkPROGRAMS: + @list='$(check_PROGRAMS)'; test -n "$$list" || exit 0; \ + echo " rm -f" $$list; \ + rm -f $$list || exit $$?; \ + test -n "$(EXEEXT)" || exit 0; \ + list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ + echo " rm -f" $$list; \ + rm -f $$list +install-libexecPROGRAMS: $(libexec_PROGRAMS) @$(NORMAL_INSTALL) - test -z "$(bindir)" || $(MKDIR_P) "$(DESTDIR)$(bindir)" - @list='$(bin_PROGRAMS)'; test -n "$(bindir)" || list=; \ + @list='$(libexec_PROGRAMS)'; test -n "$(libexecdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(libexecdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libexecdir)" || exit 1; \ + fi; \ for p in $$list; do echo "$$p $$p"; done | \ sed 's/$(EXEEXT)$$//' | \ while read p p1; do if test -f $$p || test -f $$p1; \ @@ -916,84 +1121,90 @@ install-binPROGRAMS: $(bin_PROGRAMS) while read type dir files; do \ if test "$$dir" = .; then dir=; else dir=/$$dir; fi; \ test -z "$$files" || { \ - echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files '$(DESTDIR)$(bindir)$$dir'"; \ - $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files "$(DESTDIR)$(bindir)$$dir" || exit $$?; \ + echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files '$(DESTDIR)$(libexecdir)$$dir'"; \ + $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files "$(DESTDIR)$(libexecdir)$$dir" || exit $$?; \ } \ ; done -uninstall-binPROGRAMS: +uninstall-libexecPROGRAMS: @$(NORMAL_UNINSTALL) - @list='$(bin_PROGRAMS)'; test -n "$(bindir)" || list=; \ + @list='$(libexec_PROGRAMS)'; test -n "$(libexecdir)" || list=; \ files=`for p in $$list; do echo "$$p"; done | \ sed -e 'h;s,^.*/,,;s/$(EXEEXT)$$//;$(transform)' \ -e 's/$$/$(EXEEXT)/' `; \ test -n "$$list" || exit 0; \ - echo " ( cd '$(DESTDIR)$(bindir)' && rm -f" $$files ")"; \ - cd "$(DESTDIR)$(bindir)" && rm -f $$files + echo " ( cd '$(DESTDIR)$(libexecdir)' && rm -f" $$files ")"; \ + cd "$(DESTDIR)$(libexecdir)" && rm -f $$files -clean-binPROGRAMS: - @list='$(bin_PROGRAMS)'; test -n "$$list" || exit 0; \ +clean-libexecPROGRAMS: + @list='$(libexec_PROGRAMS)'; test -n "$$list" || exit 0; \ echo " rm -f" $$list; \ rm -f $$list || exit $$?; \ test -n "$(EXEEXT)" || exit 0; \ list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ echo " rm -f" $$list; \ rm -f $$list - -clean-checkPROGRAMS: - @list='$(check_PROGRAMS)'; test -n "$$list" || exit 0; \ - echo " rm -f" $$list; \ - rm -f $$list || exit $$?; \ - test -n "$(EXEEXT)" || exit 0; \ - list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ - echo " rm -f" $$list; \ - rm -f $$list -gnunet-service-datastore$(EXEEXT): $(gnunet_service_datastore_OBJECTS) $(gnunet_service_datastore_DEPENDENCIES) +gnunet-service-datastore$(EXEEXT): $(gnunet_service_datastore_OBJECTS) $(gnunet_service_datastore_DEPENDENCIES) $(EXTRA_gnunet_service_datastore_DEPENDENCIES) @rm -f gnunet-service-datastore$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_service_datastore_OBJECTS) $(gnunet_service_datastore_LDADD) $(LIBS) -perf_datastore_api_mysql$(EXEEXT): $(perf_datastore_api_mysql_OBJECTS) $(perf_datastore_api_mysql_DEPENDENCIES) +perf_datastore_api_heap$(EXEEXT): $(perf_datastore_api_heap_OBJECTS) $(perf_datastore_api_heap_DEPENDENCIES) $(EXTRA_perf_datastore_api_heap_DEPENDENCIES) + @rm -f perf_datastore_api_heap$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(perf_datastore_api_heap_OBJECTS) $(perf_datastore_api_heap_LDADD) $(LIBS) +perf_datastore_api_mysql$(EXEEXT): $(perf_datastore_api_mysql_OBJECTS) $(perf_datastore_api_mysql_DEPENDENCIES) $(EXTRA_perf_datastore_api_mysql_DEPENDENCIES) @rm -f perf_datastore_api_mysql$(EXEEXT) $(AM_V_CCLD)$(LINK) $(perf_datastore_api_mysql_OBJECTS) $(perf_datastore_api_mysql_LDADD) $(LIBS) -perf_datastore_api_postgres$(EXEEXT): $(perf_datastore_api_postgres_OBJECTS) $(perf_datastore_api_postgres_DEPENDENCIES) +perf_datastore_api_postgres$(EXEEXT): $(perf_datastore_api_postgres_OBJECTS) $(perf_datastore_api_postgres_DEPENDENCIES) $(EXTRA_perf_datastore_api_postgres_DEPENDENCIES) @rm -f perf_datastore_api_postgres$(EXEEXT) $(AM_V_CCLD)$(LINK) $(perf_datastore_api_postgres_OBJECTS) $(perf_datastore_api_postgres_LDADD) $(LIBS) -perf_datastore_api_sqlite$(EXEEXT): $(perf_datastore_api_sqlite_OBJECTS) $(perf_datastore_api_sqlite_DEPENDENCIES) +perf_datastore_api_sqlite$(EXEEXT): $(perf_datastore_api_sqlite_OBJECTS) $(perf_datastore_api_sqlite_DEPENDENCIES) $(EXTRA_perf_datastore_api_sqlite_DEPENDENCIES) @rm -f perf_datastore_api_sqlite$(EXEEXT) $(AM_V_CCLD)$(LINK) $(perf_datastore_api_sqlite_OBJECTS) $(perf_datastore_api_sqlite_LDADD) $(LIBS) -perf_plugin_datastore_mysql$(EXEEXT): $(perf_plugin_datastore_mysql_OBJECTS) $(perf_plugin_datastore_mysql_DEPENDENCIES) +perf_plugin_datastore_heap$(EXEEXT): $(perf_plugin_datastore_heap_OBJECTS) $(perf_plugin_datastore_heap_DEPENDENCIES) $(EXTRA_perf_plugin_datastore_heap_DEPENDENCIES) + @rm -f perf_plugin_datastore_heap$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(perf_plugin_datastore_heap_OBJECTS) $(perf_plugin_datastore_heap_LDADD) $(LIBS) +perf_plugin_datastore_mysql$(EXEEXT): $(perf_plugin_datastore_mysql_OBJECTS) $(perf_plugin_datastore_mysql_DEPENDENCIES) $(EXTRA_perf_plugin_datastore_mysql_DEPENDENCIES) @rm -f perf_plugin_datastore_mysql$(EXEEXT) $(AM_V_CCLD)$(LINK) $(perf_plugin_datastore_mysql_OBJECTS) $(perf_plugin_datastore_mysql_LDADD) $(LIBS) -perf_plugin_datastore_postgres$(EXEEXT): $(perf_plugin_datastore_postgres_OBJECTS) $(perf_plugin_datastore_postgres_DEPENDENCIES) +perf_plugin_datastore_postgres$(EXEEXT): $(perf_plugin_datastore_postgres_OBJECTS) $(perf_plugin_datastore_postgres_DEPENDENCIES) $(EXTRA_perf_plugin_datastore_postgres_DEPENDENCIES) @rm -f perf_plugin_datastore_postgres$(EXEEXT) $(AM_V_CCLD)$(LINK) $(perf_plugin_datastore_postgres_OBJECTS) $(perf_plugin_datastore_postgres_LDADD) $(LIBS) -perf_plugin_datastore_sqlite$(EXEEXT): $(perf_plugin_datastore_sqlite_OBJECTS) $(perf_plugin_datastore_sqlite_DEPENDENCIES) +perf_plugin_datastore_sqlite$(EXEEXT): $(perf_plugin_datastore_sqlite_OBJECTS) $(perf_plugin_datastore_sqlite_DEPENDENCIES) $(EXTRA_perf_plugin_datastore_sqlite_DEPENDENCIES) @rm -f perf_plugin_datastore_sqlite$(EXEEXT) $(AM_V_CCLD)$(LINK) $(perf_plugin_datastore_sqlite_OBJECTS) $(perf_plugin_datastore_sqlite_LDADD) $(LIBS) -test_datastore_api_management_mysql$(EXEEXT): $(test_datastore_api_management_mysql_OBJECTS) $(test_datastore_api_management_mysql_DEPENDENCIES) +test_datastore_api_heap$(EXEEXT): $(test_datastore_api_heap_OBJECTS) $(test_datastore_api_heap_DEPENDENCIES) $(EXTRA_test_datastore_api_heap_DEPENDENCIES) + @rm -f test_datastore_api_heap$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_datastore_api_heap_OBJECTS) $(test_datastore_api_heap_LDADD) $(LIBS) +test_datastore_api_management_heap$(EXEEXT): $(test_datastore_api_management_heap_OBJECTS) $(test_datastore_api_management_heap_DEPENDENCIES) $(EXTRA_test_datastore_api_management_heap_DEPENDENCIES) + @rm -f test_datastore_api_management_heap$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_datastore_api_management_heap_OBJECTS) $(test_datastore_api_management_heap_LDADD) $(LIBS) +test_datastore_api_management_mysql$(EXEEXT): $(test_datastore_api_management_mysql_OBJECTS) $(test_datastore_api_management_mysql_DEPENDENCIES) $(EXTRA_test_datastore_api_management_mysql_DEPENDENCIES) @rm -f test_datastore_api_management_mysql$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_datastore_api_management_mysql_OBJECTS) $(test_datastore_api_management_mysql_LDADD) $(LIBS) -test_datastore_api_management_postgres$(EXEEXT): $(test_datastore_api_management_postgres_OBJECTS) $(test_datastore_api_management_postgres_DEPENDENCIES) +test_datastore_api_management_postgres$(EXEEXT): $(test_datastore_api_management_postgres_OBJECTS) $(test_datastore_api_management_postgres_DEPENDENCIES) $(EXTRA_test_datastore_api_management_postgres_DEPENDENCIES) @rm -f test_datastore_api_management_postgres$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_datastore_api_management_postgres_OBJECTS) $(test_datastore_api_management_postgres_LDADD) $(LIBS) -test_datastore_api_management_sqlite$(EXEEXT): $(test_datastore_api_management_sqlite_OBJECTS) $(test_datastore_api_management_sqlite_DEPENDENCIES) +test_datastore_api_management_sqlite$(EXEEXT): $(test_datastore_api_management_sqlite_OBJECTS) $(test_datastore_api_management_sqlite_DEPENDENCIES) $(EXTRA_test_datastore_api_management_sqlite_DEPENDENCIES) @rm -f test_datastore_api_management_sqlite$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_datastore_api_management_sqlite_OBJECTS) $(test_datastore_api_management_sqlite_LDADD) $(LIBS) -test_datastore_api_mysql$(EXEEXT): $(test_datastore_api_mysql_OBJECTS) $(test_datastore_api_mysql_DEPENDENCIES) +test_datastore_api_mysql$(EXEEXT): $(test_datastore_api_mysql_OBJECTS) $(test_datastore_api_mysql_DEPENDENCIES) $(EXTRA_test_datastore_api_mysql_DEPENDENCIES) @rm -f test_datastore_api_mysql$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_datastore_api_mysql_OBJECTS) $(test_datastore_api_mysql_LDADD) $(LIBS) -test_datastore_api_postgres$(EXEEXT): $(test_datastore_api_postgres_OBJECTS) $(test_datastore_api_postgres_DEPENDENCIES) +test_datastore_api_postgres$(EXEEXT): $(test_datastore_api_postgres_OBJECTS) $(test_datastore_api_postgres_DEPENDENCIES) $(EXTRA_test_datastore_api_postgres_DEPENDENCIES) @rm -f test_datastore_api_postgres$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_datastore_api_postgres_OBJECTS) $(test_datastore_api_postgres_LDADD) $(LIBS) -test_datastore_api_sqlite$(EXEEXT): $(test_datastore_api_sqlite_OBJECTS) $(test_datastore_api_sqlite_DEPENDENCIES) +test_datastore_api_sqlite$(EXEEXT): $(test_datastore_api_sqlite_OBJECTS) $(test_datastore_api_sqlite_DEPENDENCIES) $(EXTRA_test_datastore_api_sqlite_DEPENDENCIES) @rm -f test_datastore_api_sqlite$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_datastore_api_sqlite_OBJECTS) $(test_datastore_api_sqlite_LDADD) $(LIBS) -test_plugin_datastore_mysql$(EXEEXT): $(test_plugin_datastore_mysql_OBJECTS) $(test_plugin_datastore_mysql_DEPENDENCIES) +test_plugin_datastore_heap$(EXEEXT): $(test_plugin_datastore_heap_OBJECTS) $(test_plugin_datastore_heap_DEPENDENCIES) $(EXTRA_test_plugin_datastore_heap_DEPENDENCIES) + @rm -f test_plugin_datastore_heap$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_plugin_datastore_heap_OBJECTS) $(test_plugin_datastore_heap_LDADD) $(LIBS) +test_plugin_datastore_mysql$(EXEEXT): $(test_plugin_datastore_mysql_OBJECTS) $(test_plugin_datastore_mysql_DEPENDENCIES) $(EXTRA_test_plugin_datastore_mysql_DEPENDENCIES) @rm -f test_plugin_datastore_mysql$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_plugin_datastore_mysql_OBJECTS) $(test_plugin_datastore_mysql_LDADD) $(LIBS) -test_plugin_datastore_postgres$(EXEEXT): $(test_plugin_datastore_postgres_OBJECTS) $(test_plugin_datastore_postgres_DEPENDENCIES) +test_plugin_datastore_postgres$(EXEEXT): $(test_plugin_datastore_postgres_OBJECTS) $(test_plugin_datastore_postgres_DEPENDENCIES) $(EXTRA_test_plugin_datastore_postgres_DEPENDENCIES) @rm -f test_plugin_datastore_postgres$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_plugin_datastore_postgres_OBJECTS) $(test_plugin_datastore_postgres_LDADD) $(LIBS) -test_plugin_datastore_sqlite$(EXEEXT): $(test_plugin_datastore_sqlite_OBJECTS) $(test_plugin_datastore_sqlite_DEPENDENCIES) +test_plugin_datastore_sqlite$(EXEEXT): $(test_plugin_datastore_sqlite_OBJECTS) $(test_plugin_datastore_sqlite_DEPENDENCIES) $(EXTRA_test_plugin_datastore_sqlite_DEPENDENCIES) @rm -f test_plugin_datastore_sqlite$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_plugin_datastore_sqlite_OBJECTS) $(test_plugin_datastore_sqlite_LDADD) $(LIBS) @@ -1009,6 +1220,7 @@ distclean-compile: @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libgnunet_plugin_datastore_postgres_la-plugin_datastore_postgres.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/perf_datastore_api.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/perf_plugin_datastore.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/plugin_datastore_heap.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/plugin_datastore_sqlite.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/plugin_datastore_template.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_datastore_api.Po@am__quote@ @@ -1018,42 +1230,37 @@ distclean-compile: .c.o: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c $< .c.obj: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'` @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c `$(CYGPATH_W) '$<'` +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c `$(CYGPATH_W) '$<'` .c.lo: @am__fastdepCC_TRUE@ $(AM_V_CC)$(LTCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LTCOMPILE) -c -o $@ $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LTCOMPILE) -c -o $@ $< libgnunet_plugin_datastore_mysql_la-plugin_datastore_mysql.lo: plugin_datastore_mysql.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(libgnunet_plugin_datastore_mysql_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT libgnunet_plugin_datastore_mysql_la-plugin_datastore_mysql.lo -MD -MP -MF $(DEPDIR)/libgnunet_plugin_datastore_mysql_la-plugin_datastore_mysql.Tpo -c -o libgnunet_plugin_datastore_mysql_la-plugin_datastore_mysql.lo `test -f 'plugin_datastore_mysql.c' || echo '$(srcdir)/'`plugin_datastore_mysql.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/libgnunet_plugin_datastore_mysql_la-plugin_datastore_mysql.Tpo $(DEPDIR)/libgnunet_plugin_datastore_mysql_la-plugin_datastore_mysql.Plo -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='plugin_datastore_mysql.c' object='libgnunet_plugin_datastore_mysql_la-plugin_datastore_mysql.lo' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='plugin_datastore_mysql.c' object='libgnunet_plugin_datastore_mysql_la-plugin_datastore_mysql.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(libgnunet_plugin_datastore_mysql_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o libgnunet_plugin_datastore_mysql_la-plugin_datastore_mysql.lo `test -f 'plugin_datastore_mysql.c' || echo '$(srcdir)/'`plugin_datastore_mysql.c +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(libgnunet_plugin_datastore_mysql_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o libgnunet_plugin_datastore_mysql_la-plugin_datastore_mysql.lo `test -f 'plugin_datastore_mysql.c' || echo '$(srcdir)/'`plugin_datastore_mysql.c libgnunet_plugin_datastore_postgres_la-plugin_datastore_postgres.lo: plugin_datastore_postgres.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(libgnunet_plugin_datastore_postgres_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT libgnunet_plugin_datastore_postgres_la-plugin_datastore_postgres.lo -MD -MP -MF $(DEPDIR)/libgnunet_plugin_datastore_postgres_la-plugin_datastore_postgres.Tpo -c -o libgnunet_plugin_datastore_postgres_la-plugin_datastore_postgres.lo `test -f 'plugin_datastore_postgres.c' || echo '$(srcdir)/'`plugin_datastore_postgres.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/libgnunet_plugin_datastore_postgres_la-plugin_datastore_postgres.Tpo $(DEPDIR)/libgnunet_plugin_datastore_postgres_la-plugin_datastore_postgres.Plo -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='plugin_datastore_postgres.c' object='libgnunet_plugin_datastore_postgres_la-plugin_datastore_postgres.lo' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='plugin_datastore_postgres.c' object='libgnunet_plugin_datastore_postgres_la-plugin_datastore_postgres.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(libgnunet_plugin_datastore_postgres_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o libgnunet_plugin_datastore_postgres_la-plugin_datastore_postgres.lo `test -f 'plugin_datastore_postgres.c' || echo '$(srcdir)/'`plugin_datastore_postgres.c +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(libgnunet_plugin_datastore_postgres_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o libgnunet_plugin_datastore_postgres_la-plugin_datastore_postgres.lo `test -f 'plugin_datastore_postgres.c' || echo '$(srcdir)/'`plugin_datastore_postgres.c mostlyclean-libtool: -rm -f *.lo @@ -1062,8 +1269,11 @@ clean-libtool: -rm -rf .libs _libs install-pkgcfgDATA: $(pkgcfg_DATA) @$(NORMAL_INSTALL) - test -z "$(pkgcfgdir)" || $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" @list='$(pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(pkgcfgdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" || exit 1; \ + fi; \ for p in $$list; do \ if test -f "$$p"; then d=; else d="$(srcdir)/"; fi; \ echo "$$d$$p"; \ @@ -1077,9 +1287,7 @@ uninstall-pkgcfgDATA: @$(NORMAL_UNINSTALL) @list='$(pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ files=`for p in $$list; do echo $$p; done | sed -e 's|^.*/||'`; \ - test -n "$$files" || exit 0; \ - echo " ( cd '$(DESTDIR)$(pkgcfgdir)' && rm -f" $$files ")"; \ - cd "$(DESTDIR)$(pkgcfgdir)" && rm -f $$files + dir='$(DESTDIR)$(pkgcfgdir)'; $(am__uninstall_files_from_dir) ID: $(HEADERS) $(SOURCES) $(LISP) $(TAGS_FILES) list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ @@ -1214,14 +1422,15 @@ check-TESTS: $(TESTS) fi; \ dashes=`echo "$$dashes" | sed s/./=/g`; \ if test "$$failed" -eq 0; then \ - echo "$$grn$$dashes"; \ + col="$$grn"; \ else \ - echo "$$red$$dashes"; \ + col="$$red"; \ fi; \ - echo "$$banner"; \ - test -z "$$skipped" || echo "$$skipped"; \ - test -z "$$report" || echo "$$report"; \ - echo "$$dashes$$std"; \ + echo "$${col}$$dashes$${std}"; \ + echo "$${col}$$banner$${std}"; \ + test -z "$$skipped" || echo "$${col}$$skipped$${std}"; \ + test -z "$$report" || echo "$${col}$$report$${std}"; \ + echo "$${col}$$dashes$${std}"; \ test "$$failed" -eq 0; \ else :; fi @@ -1260,10 +1469,8 @@ check-am: all-am $(MAKE) $(AM_MAKEFLAGS) check-TESTS check: check-am all-am: Makefile $(LTLIBRARIES) $(PROGRAMS) $(DATA) -install-binPROGRAMS: install-libLTLIBRARIES - installdirs: - for dir in "$(DESTDIR)$(libdir)" "$(DESTDIR)$(plugindir)" "$(DESTDIR)$(bindir)" "$(DESTDIR)$(pkgcfgdir)"; do \ + for dir in "$(DESTDIR)$(libdir)" "$(DESTDIR)$(plugindir)" "$(DESTDIR)$(libexecdir)" "$(DESTDIR)$(pkgcfgdir)"; do \ test -z "$$dir" || $(MKDIR_P) "$$dir"; \ done install: install-am @@ -1276,10 +1483,15 @@ install-am: all-am installcheck: installcheck-am install-strip: - $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ - install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ - `test -z '$(STRIP)' || \ - echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi mostlyclean-generic: clean-generic: @@ -1293,8 +1505,8 @@ maintainer-clean-generic: @echo "it deletes files that may require special tools to rebuild." clean: clean-am -clean-am: clean-binPROGRAMS clean-checkPROGRAMS clean-generic \ - clean-libLTLIBRARIES clean-libtool clean-pluginLTLIBRARIES \ +clean-am: clean-checkPROGRAMS clean-generic clean-libLTLIBRARIES \ + clean-libexecPROGRAMS clean-libtool clean-pluginLTLIBRARIES \ mostlyclean-am distclean: distclean-am @@ -1321,7 +1533,7 @@ install-dvi: install-dvi-am install-dvi-am: -install-exec-am: install-binPROGRAMS install-libLTLIBRARIES +install-exec-am: install-libLTLIBRARIES install-libexecPROGRAMS install-html: install-html-am @@ -1361,27 +1573,27 @@ ps: ps-am ps-am: -uninstall-am: uninstall-binPROGRAMS uninstall-libLTLIBRARIES \ +uninstall-am: uninstall-libLTLIBRARIES uninstall-libexecPROGRAMS \ uninstall-pkgcfgDATA uninstall-pluginLTLIBRARIES .MAKE: check-am install-am install-strip .PHONY: CTAGS GTAGS all all-am check check-TESTS check-am clean \ - clean-binPROGRAMS clean-checkPROGRAMS clean-generic \ - clean-libLTLIBRARIES clean-libtool clean-pluginLTLIBRARIES \ + clean-checkPROGRAMS clean-generic clean-libLTLIBRARIES \ + clean-libexecPROGRAMS clean-libtool clean-pluginLTLIBRARIES \ ctags distclean distclean-compile distclean-generic \ distclean-libtool distclean-tags distdir dvi dvi-am html \ - html-am info info-am install install-am install-binPROGRAMS \ - install-data install-data-am install-dvi install-dvi-am \ - install-exec install-exec-am install-html install-html-am \ - install-info install-info-am install-libLTLIBRARIES \ + html-am info info-am install install-am install-data \ + install-data-am install-dvi install-dvi-am install-exec \ + install-exec-am install-html install-html-am install-info \ + install-info-am install-libLTLIBRARIES install-libexecPROGRAMS \ install-man install-pdf install-pdf-am install-pkgcfgDATA \ install-pluginLTLIBRARIES install-ps install-ps-am \ install-strip installcheck installcheck-am installdirs \ maintainer-clean maintainer-clean-generic mostlyclean \ mostlyclean-compile mostlyclean-generic mostlyclean-libtool \ pdf pdf-am ps ps-am tags uninstall uninstall-am \ - uninstall-binPROGRAMS uninstall-libLTLIBRARIES \ + uninstall-libLTLIBRARIES uninstall-libexecPROGRAMS \ uninstall-pkgcfgDATA uninstall-pluginLTLIBRARIES diff --git a/src/datastore/datastore.conf.in b/src/datastore/datastore.conf.in index 837c619..7a92070 100644 --- a/src/datastore/datastore.conf.in +++ b/src/datastore/datastore.conf.in @@ -1,16 +1,15 @@ [datastore] AUTOSTART = YES UNIXPATH = /tmp/gnunet-service-datastore.sock -UNIX_MATCH_UID = YES +UNIX_MATCH_UID = NO UNIX_MATCH_GID = YES @UNIXONLY@ PORT = 2093 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-datastore ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; -QUOTA = 100 MB +QUOTA = 5 GB BLOOMFILTER = $SERVICEHOME/datastore/bloomfilter DATABASE = sqlite # DISABLE_SOCKET_FORWARDING = NO @@ -30,4 +29,5 @@ CONFIG = ~/.my.cnf # PORT = 3306 - +[datastore-heap] +HASHMAPSIZE = 1024 diff --git a/src/datastore/datastore.h b/src/datastore/datastore.h index 87ceb01..4f43185 100644 --- a/src/datastore/datastore.h +++ b/src/datastore/datastore.h @@ -111,7 +111,7 @@ struct GetMessage /** * Type is GNUNET_MESSAGE_TYPE_DATASTORE_GET. Size * can either be "sizeof(struct GetMessage)" or - * "sizeof(struct GetMessage) - sizeof(GNUNET_HashCode)"! + * "sizeof(struct GetMessage) - sizeof(struct GNUNET_HashCode)"! */ struct GNUNET_MessageHeader header; @@ -129,7 +129,7 @@ struct GetMessage * Desired key (optional). Check the "size" of the * header to see if the key is actually present. */ - GNUNET_HashCode key; + struct GNUNET_HashCode key; }; @@ -252,7 +252,7 @@ struct DataMessage /** * Key under which the item can be found. */ - GNUNET_HashCode key; + struct GNUNET_HashCode key; }; GNUNET_NETWORK_STRUCT_END diff --git a/src/datastore/datastore_api.c b/src/datastore/datastore_api.c index 57663e9..fab3bf0 100644 --- a/src/datastore/datastore_api.c +++ b/src/datastore/datastore_api.c @@ -33,6 +33,11 @@ #define LOG(kind,...) GNUNET_log_from (kind, "datastore-api",__VA_ARGS__) +/** + * Collect an instane number of statistics? May cause excessive IPC. + */ +#define INSANE_STATISTICS GNUNET_NO + /** * If a client stopped asking for more results, how many more do * we receive from the DB before killing the connection? Trade-off @@ -388,7 +393,7 @@ timeout_queue_entry (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) gettext_noop ("# queue entry timeouts"), 1, GNUNET_NO); qe->task = GNUNET_SCHEDULER_NO_TASK; - GNUNET_assert (qe->was_transmitted == GNUNET_NO); + GNUNET_assert (GNUNET_NO == qe->was_transmitted); LOG (GNUNET_ERROR_TYPE_DEBUG, "Timeout of request in datastore queue\n"); qe->response_proc (qe->h, NULL); } @@ -456,20 +461,21 @@ make_queue_entry (struct GNUNET_DATASTORE_Handle *h, size_t msize, pos = h->queue_head; } c++; +#if INSANE_STATISTICS GNUNET_STATISTICS_update (h->stats, gettext_noop ("# queue entries created"), 1, GNUNET_NO); +#endif GNUNET_CONTAINER_DLL_insert_after (h->queue_head, h->queue_tail, pos, ret); h->queue_size++; ret->task = GNUNET_SCHEDULER_add_delayed (timeout, &timeout_queue_entry, ret); - pos = ret->next; - while (pos != NULL) + for (pos = ret->next; NULL != pos; pos = pos->next) { if ((pos->max_queue < h->queue_size) && (pos->was_transmitted == GNUNET_NO)) { GNUNET_assert (pos->response_proc != NULL); /* move 'pos' element to head so that it will be * killed on 'NULL' call below */ - LOG (GNUNET_ERROR_TYPE_DEBUG, "Dropping request from datastore queue\n"); + LOG (GNUNET_ERROR_TYPE_DEBUG, "Dropping request from datastore queue\n"); GNUNET_CONTAINER_DLL_remove (h->queue_head, h->queue_tail, pos); GNUNET_CONTAINER_DLL_insert (h->queue_head, h->queue_tail, pos); GNUNET_STATISTICS_update (h->stats, @@ -480,7 +486,6 @@ make_queue_entry (struct GNUNET_DATASTORE_Handle *h, size_t msize, pos->response_proc (h, NULL); break; } - pos = pos->next; } return ret; } @@ -507,12 +512,7 @@ try_reconnect (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { struct GNUNET_DATASTORE_Handle *h = cls; - if (h->retry_time.rel_value < GNUNET_CONSTANTS_SERVICE_RETRY.rel_value) - h->retry_time = GNUNET_CONSTANTS_SERVICE_RETRY; - else - h->retry_time = GNUNET_TIME_relative_multiply (h->retry_time, 2); - if (h->retry_time.rel_value > GNUNET_CONSTANTS_SERVICE_TIMEOUT.rel_value) - h->retry_time = GNUNET_CONSTANTS_SERVICE_TIMEOUT; + h->retry_time = GNUNET_TIME_STD_BACKOFF (h->retry_time); h->reconnect_task = GNUNET_SCHEDULER_NO_TASK; h->client = GNUNET_CLIENT_connect ("datastore", h->cfg); if (h->client == NULL) @@ -544,10 +544,6 @@ do_disconnect (struct GNUNET_DATASTORE_Handle *h) "client NULL in disconnect, will not try to reconnect\n"); return; } -#if 0 - GNUNET_STATISTICS_update (stats, gettext_noop ("# reconnected to DATASTORE"), - 1, GNUNET_NO); -#endif GNUNET_CLIENT_disconnect (h->client); h->skip_next_messages = 0; h->client = NULL; @@ -629,9 +625,11 @@ transmit_request (void *cls, size_t size, void *buf) h->in_receive = GNUNET_YES; GNUNET_CLIENT_receive (h->client, &receive_cb, h, GNUNET_TIME_absolute_get_remaining (qe->timeout)); +#if INSANE_STATISTICS GNUNET_STATISTICS_update (h->stats, gettext_noop ("# bytes sent to datastore"), 1, GNUNET_NO); +#endif return msize; } @@ -799,7 +797,7 @@ process_status_message (void *cls, const struct GNUNET_MessageHeader *msg) GNUNET_STATISTICS_update (h->stats, gettext_noop ("# status messages received"), 1, GNUNET_NO); - h->retry_time.rel_value = 0; + h->retry_time = GNUNET_TIME_UNIT_ZERO; process_queue (h); if (rc.cont != NULL) rc.cont (rc.cont_cls, status, @@ -836,7 +834,7 @@ process_status_message (void *cls, const struct GNUNET_MessageHeader *msg) */ struct GNUNET_DATASTORE_QueueEntry * GNUNET_DATASTORE_put (struct GNUNET_DATASTORE_Handle *h, uint32_t rid, - const GNUNET_HashCode * key, size_t size, + const struct GNUNET_HashCode * key, size_t size, const void *data, enum GNUNET_BLOCK_Type type, uint32_t priority, uint32_t anonymity, uint32_t replication, @@ -1087,7 +1085,7 @@ GNUNET_DATASTORE_update (struct GNUNET_DATASTORE_Handle *h, uint64_t uid, */ struct GNUNET_DATASTORE_QueueEntry * GNUNET_DATASTORE_remove (struct GNUNET_DATASTORE_Handle *h, - const GNUNET_HashCode * key, size_t size, + const struct GNUNET_HashCode * key, size_t size, const void *data, unsigned int queue_priority, unsigned int max_queue_size, struct GNUNET_TIME_Relative timeout, @@ -1150,14 +1148,14 @@ process_result_message (void *cls, const struct GNUNET_MessageHeader *msg) const struct DataMessage *dm; int was_transmitted; - if (msg == NULL) + if (NULL == msg) { qe = h->queue_head; GNUNET_assert (NULL != qe); rc = qe->qc.rc; was_transmitted = qe->was_transmitted; free_queue_entry (qe); - if (was_transmitted == GNUNET_YES) + if (GNUNET_YES == was_transmitted) { LOG (GNUNET_ERROR_TYPE_WARNING, _("Failed to receive response from database.\n")); @@ -1167,7 +1165,7 @@ process_result_message (void *cls, const struct GNUNET_MessageHeader *msg) { process_queue (h); } - if (rc.proc != NULL) + if (NULL != rc.proc) rc.proc (rc.proc_cls, NULL, 0, NULL, 0, 0, 0, GNUNET_TIME_UNIT_ZERO_ABS, 0); return; @@ -1181,7 +1179,7 @@ process_result_message (void *cls, const struct GNUNET_MessageHeader *msg) free_queue_entry (qe); LOG (GNUNET_ERROR_TYPE_DEBUG, "Received end of result set, new queue size is %u\n", h->queue_size); - h->retry_time.rel_value = 0; + h->retry_time = GNUNET_TIME_UNIT_ZERO; h->result_count = 0; process_queue (h); if (rc.proc != NULL) @@ -1218,15 +1216,17 @@ process_result_message (void *cls, const struct GNUNET_MessageHeader *msg) 0); return; } +#if INSANE_STATISTICS GNUNET_STATISTICS_update (h->stats, gettext_noop ("# Results received"), 1, GNUNET_NO); +#endif dm = (const struct DataMessage *) msg; LOG (GNUNET_ERROR_TYPE_DEBUG, "Received result %llu with type %u and size %u with key %s\n", (unsigned long long) GNUNET_ntohll (dm->uid), ntohl (dm->type), ntohl (dm->size), GNUNET_h2s (&dm->key)); free_queue_entry (qe); - h->retry_time.rel_value = 0; + h->retry_time = GNUNET_TIME_UNIT_ZERO; process_queue (h); if (rc.proc != NULL) rc.proc (rc.proc_cls, &dm->key, ntohl (dm->size), &dm[1], ntohl (dm->type), @@ -1381,7 +1381,7 @@ GNUNET_DATASTORE_get_zero_anonymity (struct GNUNET_DATASTORE_Handle *h, */ struct GNUNET_DATASTORE_QueueEntry * GNUNET_DATASTORE_get_key (struct GNUNET_DATASTORE_Handle *h, uint64_t offset, - const GNUNET_HashCode * key, + const struct GNUNET_HashCode * key, enum GNUNET_BLOCK_Type type, unsigned int queue_priority, unsigned int max_queue_size, @@ -1406,8 +1406,10 @@ GNUNET_DATASTORE_get_key (struct GNUNET_DATASTORE_Handle *h, uint64_t offset, GNUNET_h2s (key)); return NULL; } +#if INSANE_STATISTICS GNUNET_STATISTICS_update (h->stats, gettext_noop ("# GET requests executed"), 1, GNUNET_NO); +#endif gm = (struct GetMessage *) &qe[1]; gm->header.type = htons (GNUNET_MESSAGE_TYPE_DATASTORE_GET); gm->type = htonl (type); @@ -1420,7 +1422,7 @@ GNUNET_DATASTORE_get_key (struct GNUNET_DATASTORE_Handle *h, uint64_t offset, else { gm->header.size = - htons (sizeof (struct GetMessage) - sizeof (GNUNET_HashCode)); + htons (sizeof (struct GetMessage) - sizeof (struct GNUNET_HashCode)); } process_queue (h); return qe; diff --git a/src/datastore/gnunet-service-datastore.c b/src/datastore/gnunet-service-datastore.c index 49b9db8..93b43b1 100644 --- a/src/datastore/gnunet-service-datastore.c +++ b/src/datastore/gnunet-service-datastore.c @@ -316,7 +316,7 @@ delete_expired (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc); * GNUNET_NO to delete the item and continue (if supported) */ static int -expired_processor (void *cls, const GNUNET_HashCode * key, uint32_t size, +expired_processor (void *cls, const struct GNUNET_HashCode * key, uint32_t size, const void *data, enum GNUNET_BLOCK_Type type, uint32_t priority, uint32_t anonymity, struct GNUNET_TIME_Absolute expiration, uint64_t uid) @@ -394,7 +394,7 @@ delete_expired (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) * GNUNET_NO to delete the item and continue (if supported) */ static int -quota_processor (void *cls, const GNUNET_HashCode * key, uint32_t size, +quota_processor (void *cls, const struct GNUNET_HashCode * key, uint32_t size, const void *data, enum GNUNET_BLOCK_Type type, uint32_t priority, uint32_t anonymity, struct GNUNET_TIME_Absolute expiration, uint64_t uid) @@ -581,7 +581,7 @@ transmit_status (struct GNUNET_SERVER_Client *client, int code, const char *msg) * GNUNET_NO to delete the item and continue (if supported) */ static int -transmit_item (void *cls, const GNUNET_HashCode * key, uint32_t size, +transmit_item (void *cls, const struct GNUNET_HashCode * key, uint32_t size, const void *data, enum GNUNET_BLOCK_Type type, uint32_t priority, uint32_t anonymity, struct GNUNET_TIME_Absolute expiration, uint64_t uid) @@ -871,7 +871,7 @@ execute_put (struct GNUNET_SERVER_Client *client, const struct DataMessage *dm) * GNUNET_NO to delete the item */ static int -check_present (void *cls, const GNUNET_HashCode * key, uint32_t size, +check_present (void *cls, const struct GNUNET_HashCode * key, uint32_t size, const void *data, enum GNUNET_BLOCK_Type type, uint32_t priority, uint32_t anonymity, struct GNUNET_TIME_Absolute expiration, uint64_t uid) @@ -930,7 +930,7 @@ handle_put (void *cls, struct GNUNET_SERVER_Client *client, int rid; struct ReservationList *pos; struct PutContext *pc; - GNUNET_HashCode vhash; + struct GNUNET_HashCode vhash; uint32_t size; if ((dm == NULL) || (ntohl (dm->type) == 0)) @@ -993,7 +993,7 @@ handle_get (void *cls, struct GNUNET_SERVER_Client *client, size = ntohs (message->size); if ((size != sizeof (struct GetMessage)) && - (size != sizeof (struct GetMessage) - sizeof (GNUNET_HashCode))) + (size != sizeof (struct GetMessage) - sizeof (struct GNUNET_HashCode))) { GNUNET_break (0); GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); @@ -1120,7 +1120,7 @@ handle_get_zero_anonymity (void *cls, struct GNUNET_SERVER_Client *client, * in to be deleted (by returning GNUNET_NO). */ static int -remove_callback (void *cls, const GNUNET_HashCode * key, uint32_t size, +remove_callback (void *cls, const struct GNUNET_HashCode * key, uint32_t size, const void *data, enum GNUNET_BLOCK_Type type, uint32_t priority, uint32_t anonymity, struct GNUNET_TIME_Absolute expiration, uint64_t uid) @@ -1160,7 +1160,7 @@ handle_remove (void *cls, struct GNUNET_SERVER_Client *client, const struct GNUNET_MessageHeader *message) { const struct DataMessage *dm = check_data (message); - GNUNET_HashCode vhash; + struct GNUNET_HashCode vhash; if (dm == NULL) { @@ -1428,7 +1428,7 @@ cleanup_reservations (void *cls, struct GNUNET_SERVER_Client *client) */ static void add_key_to_bloomfilter (void *cls, - const GNUNET_HashCode *key, + const struct GNUNET_HashCode *key, unsigned int count) { struct GNUNET_CONTAINER_BloomFilter *bf = cls; @@ -1549,7 +1549,7 @@ run (void *cls, struct GNUNET_SERVER_Handle *server, pfn); GNUNET_free (pfn); pfn = NULL; - filter = GNUNET_CONTAINER_bloomfilter_load (NULL, bf_size, 5); /* approx. 3% false positives at max use */ + filter = GNUNET_CONTAINER_bloomfilter_init (NULL, bf_size, 5); /* approx. 3% false positives at max use */ } } } diff --git a/src/datastore/perf_datastore_api.c b/src/datastore/perf_datastore_api.c index cdbd6ae..cf21ebe 100644 --- a/src/datastore/perf_datastore_api.c +++ b/src/datastore/perf_datastore_api.c @@ -36,19 +36,14 @@ #include "gnunet_util_lib.h" #include "gnunet_protocols.h" #include "gnunet_datastore_service.h" +#include "gnunet_testing_lib.h" #include -#define VERBOSE GNUNET_NO - /** * How long until we give up on transmitting the message? */ #define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 15) -static const char *plugin_name; - -static struct GNUNET_DATASTORE_Handle *datastore; - /** * Target datastore size (in bytes). */ @@ -81,8 +76,13 @@ static unsigned long long stored_ops; static struct GNUNET_TIME_Absolute start_time; +static const char *plugin_name; + +static struct GNUNET_DATASTORE_Handle *datastore; + static int ok; + enum RunPhase { RP_DONE = 0, @@ -103,13 +103,10 @@ struct CpsRunContext }; - static void run_continuation (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc); - - static void check_success (void *cls, int success, struct GNUNET_TIME_Absolute min_expiration, const char *msg) { @@ -174,7 +171,7 @@ remove_next (void *cls, int success, struct GNUNET_TIME_Absolute min_expiration, static void -delete_value (void *cls, const GNUNET_HashCode * key, size_t size, +delete_value (void *cls, const struct GNUNET_HashCode * key, size_t size, const void *data, enum GNUNET_BLOCK_Type type, uint32_t priority, uint32_t anonymity, struct GNUNET_TIME_Absolute expiration, uint64_t uid) @@ -199,7 +196,7 @@ run_continuation (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { struct CpsRunContext *crc = cls; size_t size; - static GNUNET_HashCode key; + static struct GNUNET_HashCode key; static char data[65536]; int i; int k; @@ -209,7 +206,7 @@ run_continuation (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) switch (crc->phase) { case RP_PUT: - memset (&key, 256 - crc->i, sizeof (GNUNET_HashCode)); + memset (&key, 256 - crc->i, sizeof (struct GNUNET_HashCode)); i = crc->j; k = crc->i; /* most content is 32k */ @@ -217,7 +214,7 @@ run_continuation (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) if (GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK, 16) == 0) /* but some of it is less! */ size = GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK, 32 * 1024); crc->size = size = size - (size & 7); /* always multiple of 8 */ - GNUNET_CRYPTO_hash (&key, sizeof (GNUNET_HashCode), &key); + GNUNET_CRYPTO_hash (&key, sizeof (struct GNUNET_HashCode), &key); memset (data, i, size); if (i > 255) memset (data, i - 255, size / 2); @@ -297,11 +294,12 @@ run_tests (void *cls, int success, struct GNUNET_TIME_Absolute min_expiration, c static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) { struct CpsRunContext *crc; - static GNUNET_HashCode zkey; + static struct GNUNET_HashCode zkey; datastore = GNUNET_DATASTORE_connect (cfg); start_time = GNUNET_TIME_absolute_get (); @@ -322,85 +320,22 @@ run (void *cls, char *const *args, const char *cfgfile, } -static int -check () +int +main (int argc, char *argv[]) { - struct GNUNET_OS_Process *proc; char cfg_name[128]; - char *const argv[] = { - "perf-datastore-api", - "-c", - cfg_name, -#if VERBOSE - "-L", "DEBUG", -#endif - NULL - }; - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - + plugin_name = GNUNET_TESTING_get_testname_from_underscore (argv[0]); GNUNET_snprintf (cfg_name, sizeof (cfg_name), "test_datastore_api_data_%s.conf", plugin_name); - proc = - GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-arm", - "gnunet-service-arm", -#if VERBOSE - "-L", "DEBUG", -#endif - "-c", cfg_name, NULL); - GNUNET_assert (NULL != proc); - GNUNET_PROGRAM_run ((sizeof (argv) / sizeof (char *)) - 1, argv, - "perf-datastore-api", "nohelp", options, &run, NULL); - sleep (1); /* give datastore chance to process 'DROP' */ - if (0 != GNUNET_OS_process_kill (proc, SIGTERM)) - { - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); - ok = 1; - } - GNUNET_OS_process_wait (proc); - GNUNET_OS_process_destroy (proc); - proc = NULL; + if (0 != + GNUNET_TESTING_peer_run ("perf-gnunet-datastore", + cfg_name, + &run, + NULL)) + return 1; + FPRINTF (stderr, "%s", "\n"); return ok; } - -int -main (int argc, char *argv[]) -{ - int ret; - char *pos; - char dir_name[128]; - - sleep (1); - /* determine name of plugin to use */ - plugin_name = argv[0]; - while (NULL != (pos = strstr (plugin_name, "_"))) - plugin_name = pos + 1; - if (NULL != (pos = strstr (plugin_name, "."))) - pos[0] = 0; - else - pos = (char *) plugin_name; - - GNUNET_snprintf (dir_name, sizeof (dir_name), "/tmp/test-gnunet-datastore-%s", - plugin_name); - GNUNET_DISK_directory_remove (dir_name); - GNUNET_log_setup ("perf-datastore-api", -#if VERBOSE - "DEBUG", -#else - "WARNING", -#endif - NULL); - ret = check (); - if (pos != plugin_name) - pos[0] = '.'; -#if REPORT_ID - FPRINTF (stderr, "%s", "\n"); -#endif - GNUNET_DISK_directory_remove (dir_name); - return ret; -} - /* end of perf_datastore_api.c */ diff --git a/src/datastore/perf_plugin_datastore.c b/src/datastore/perf_plugin_datastore.c index 1860374..56e2b87 100644 --- a/src/datastore/perf_plugin_datastore.c +++ b/src/datastore/perf_plugin_datastore.c @@ -27,10 +27,9 @@ #include "gnunet_util_lib.h" #include "gnunet_protocols.h" #include "gnunet_datastore_plugin.h" +#include "gnunet_testing_lib.h" #include -#define VERBOSE GNUNET_NO - /** * Target datastore size (in bytes). Realistic sizes are * more like 16 GB (not the default of 16 MB); however, @@ -104,7 +103,7 @@ putValue (struct GNUNET_DATASTORE_PluginFunctions *api, int i, int k) { char value[65536]; size_t size; - static GNUNET_HashCode key; + static struct GNUNET_HashCode key; static int ic; char *msg; unsigned int prio; @@ -117,7 +116,7 @@ putValue (struct GNUNET_DATASTORE_PluginFunctions *api, int i, int k) /* generate random key */ key.bits[0] = (unsigned int) GNUNET_TIME_absolute_get ().abs_value; - GNUNET_CRYPTO_hash (&key, sizeof (GNUNET_HashCode), &key); + GNUNET_CRYPTO_hash (&key, sizeof (struct GNUNET_HashCode), &key); memset (value, i, size); if (i > 255) memset (value, i - 255, size / 2); @@ -150,7 +149,7 @@ test (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc); static int -iterate_zeros (void *cls, const GNUNET_HashCode * key, uint32_t size, +iterate_zeros (void *cls, const struct GNUNET_HashCode * key, uint32_t size, const void *data, enum GNUNET_BLOCK_Type type, uint32_t priority, uint32_t anonymity, struct GNUNET_TIME_Absolute expiration, uint64_t uid) @@ -164,10 +163,10 @@ iterate_zeros (void *cls, const GNUNET_HashCode * key, uint32_t size, memcpy (&i, &cdata[4], sizeof (i)); hits[i / 8] |= (1 << (i % 8)); -#if VERBOSE - FPRINTF (stderr, "Found result type=%u, priority=%u, size=%u, expire=%llu\n", - type, priority, size, (unsigned long long) expiration.abs_value); -#endif + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Found result %d type=%u, priority=%u, size=%u, expire=%llu\n", + i, + type, priority, size, (unsigned long long) expiration.abs_value); crc->cnt++; if (crc->cnt == PUT_10 / 4 - 1) { @@ -198,7 +197,7 @@ iterate_zeros (void *cls, const GNUNET_HashCode * key, uint32_t size, static int -expiration_get (void *cls, const GNUNET_HashCode * key, uint32_t size, +expiration_get (void *cls, const struct GNUNET_HashCode * key, uint32_t size, const void *data, enum GNUNET_BLOCK_Type type, uint32_t priority, uint32_t anonymity, struct GNUNET_TIME_Absolute expiration, uint64_t uid) @@ -243,7 +242,7 @@ expiration_get (void *cls, const GNUNET_HashCode * key, uint32_t size, static int -replication_get (void *cls, const GNUNET_HashCode * key, uint32_t size, +replication_get (void *cls, const struct GNUNET_HashCode * key, uint32_t size, const void *data, enum GNUNET_BLOCK_Type type, uint32_t priority, uint32_t anonymity, struct GNUNET_TIME_Absolute expiration, uint64_t uid) @@ -343,9 +342,8 @@ test (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) GNUNET_break (0); crc->phase = RP_ERROR; } -#if VERBOSE - FPRINTF (stderr, "In phase %d, iteration %u\n", crc->phase, crc->cnt); -#endif + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "In phase %d, iteration %u\n", crc->phase, crc->cnt); switch (crc->phase) { case RP_ERROR: @@ -438,6 +436,11 @@ run (void *cls, char *const *args, const char *cfgfile, struct GNUNET_DATASTORE_PluginFunctions *api; struct CpsRunContext *crc; + if (NULL == c) + { + GNUNET_break (0); + return; + } api = load_plugin (c); if (api == NULL) { @@ -454,68 +457,38 @@ run (void *cls, char *const *args, const char *cfgfile, } -static int -check () +int +main (int argc, char *argv[]) { + char dir_name[128]; char cfg_name[128]; - - char *const argv[] = { + char *const xargv[] = { "perf-plugin-datastore", "-c", cfg_name, -#if VERBOSE - "-L", "DEBUG", -#endif NULL }; struct GNUNET_GETOPT_CommandLineOption options[] = { GNUNET_GETOPT_OPTION_END }; - GNUNET_snprintf (category, sizeof (category), "DATASTORE-%s", plugin_name); - GNUNET_snprintf (cfg_name, sizeof (cfg_name), - "perf_plugin_datastore_data_%s.conf", plugin_name); - GNUNET_PROGRAM_run ((sizeof (argv) / sizeof (char *)) - 1, argv, - "perf-plugin-datastore", "nohelp", options, &run, NULL); - if (ok != 0) - FPRINTF (stderr, "Missed some testcases: %u\n", ok); - return ok; -} - - -int -main (int argc, char *argv[]) -{ - int ret; - char *pos; - char dir_name[128]; - - sleep (1); - /* determine name of plugin to use */ - plugin_name = argv[0]; - while (NULL != (pos = strstr (plugin_name, "_"))) - plugin_name = pos + 1; - if (NULL != (pos = strstr (plugin_name, "."))) - pos[0] = 0; - else - pos = (char *) plugin_name; - + plugin_name = GNUNET_TESTING_get_testname_from_underscore (argv[0]); GNUNET_snprintf (dir_name, sizeof (dir_name), "/tmp/perf-gnunet-datastore-%s", plugin_name); GNUNET_DISK_directory_remove (dir_name); GNUNET_log_setup ("perf-plugin-datastore", -#if VERBOSE - "DEBUG", -#else "WARNING", -#endif NULL); - ret = check (); - if (pos != plugin_name) - pos[0] = '.'; + GNUNET_snprintf (category, sizeof (category), "DATASTORE-%s", plugin_name); + GNUNET_snprintf (cfg_name, sizeof (cfg_name), + "perf_plugin_datastore_data_%s.conf", plugin_name); + GNUNET_PROGRAM_run ((sizeof (xargv) / sizeof (char *)) - 1, xargv, + "perf-plugin-datastore", "nohelp", options, &run, NULL); + if (ok != 0) + FPRINTF (stderr, "Missed some testcases: %u\n", ok); GNUNET_DISK_directory_remove (dir_name); - return ret; + return ok; } /* end of perf_plugin_datastore.c */ diff --git a/src/datastore/perf_plugin_datastore_data_heap.conf b/src/datastore/perf_plugin_datastore_data_heap.conf new file mode 100644 index 0000000..7ee215c --- /dev/null +++ b/src/datastore/perf_plugin_datastore_data_heap.conf @@ -0,0 +1,7 @@ +@INLINE@ test_defaults.conf +[PATHS] +SERVICEHOME = /tmp/perf-gnunet-datastore-heap/ + + +[datastore] +DATABASE = heap diff --git a/src/datastore/perf_plugin_datastore_data_mysql.conf b/src/datastore/perf_plugin_datastore_data_mysql.conf index dd26512..006b146 100644 --- a/src/datastore/perf_plugin_datastore_data_mysql.conf +++ b/src/datastore/perf_plugin_datastore_data_mysql.conf @@ -1,7 +1,6 @@ @INLINE@ test_defaults.conf [PATHS] SERVICEHOME = /tmp/perf-gnunet-datastore-mysql/ -DEFAULTCONFIG = perf_plugin_datastore_data_mysql.conf [datastore] DATABASE = mysql diff --git a/src/datastore/perf_plugin_datastore_data_postgres.conf b/src/datastore/perf_plugin_datastore_data_postgres.conf index 53ce6cf..052fa48 100644 --- a/src/datastore/perf_plugin_datastore_data_postgres.conf +++ b/src/datastore/perf_plugin_datastore_data_postgres.conf @@ -1,7 +1,6 @@ @INLINE@ test_defaults.conf [PATHS] SERVICEHOME = /tmp/perf-gnunet-datastore-postgres/ -DEFAULTCONFIG = perf_plugin_datastore_data_postgres.conf [datastore] DATABASE = postgres diff --git a/src/datastore/perf_plugin_datastore_data_sqlite.conf b/src/datastore/perf_plugin_datastore_data_sqlite.conf index 241d85e..5f97597 100644 --- a/src/datastore/perf_plugin_datastore_data_sqlite.conf +++ b/src/datastore/perf_plugin_datastore_data_sqlite.conf @@ -1,5 +1,4 @@ @INLINE@ test_defaults.conf [PATHS] SERVICEHOME = /tmp/perf-gnunet-datastore-sqlite/ -DEFAULTCONFIG = perf_plugin_datastore_data_sqlite.conf diff --git a/src/datastore/plugin_datastore_heap.c b/src/datastore/plugin_datastore_heap.c new file mode 100644 index 0000000..9f9360b --- /dev/null +++ b/src/datastore/plugin_datastore_heap.c @@ -0,0 +1,868 @@ +/* + This file is part of GNUnet + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @file datastore/plugin_datastore_heap.c + * @brief heap-based datastore backend; usually we want the datastore + * to be persistent, and storing data in the heap is obviously + * NOT going to be persistent; still, this plugin is useful for + * testing/benchmarking --- but never for production! + * @author Christian Grothoff + */ + +#include "platform.h" +#include "gnunet_datastore_plugin.h" + + +/** + * A value that we are storing. + */ +struct Value +{ + + /** + * Key for the value. + */ + struct GNUNET_HashCode key; + + /** + * Pointer to the value's data (allocated at the end of this struct). + */ + const void *data; + + /** + * Entry for this value in the 'expire' heap. + */ + struct GNUNET_CONTAINER_HeapNode *expire_heap; + + /** + * Entry for this value in the 'replication' heap. + */ + struct GNUNET_CONTAINER_HeapNode *replication_heap; + + /** + * Expiration time for this value. + */ + struct GNUNET_TIME_Absolute expiration; + + /** + * Offset of this value in the array of the 'struct ZeroAnonByType'; + * only used if anonymity is zero. + */ + unsigned int zero_anon_offset; + + /** + * Number of bytes in 'data'. + */ + uint32_t size; + + /** + * Priority of the value. + */ + uint32_t priority; + + /** + * Anonymity level for the value. + */ + uint32_t anonymity; + + /** + * Replication level for the value. + */ + uint32_t replication; + + /** + * Type of 'data'. + */ + enum GNUNET_BLOCK_Type type; + +}; + + +/** + * We organize 0-anonymity values in arrays "by type". + */ +struct ZeroAnonByType +{ + + /** + * We keep these in a DLL. + */ + struct ZeroAnonByType *next; + + /** + * We keep these in a DLL. + */ + struct ZeroAnonByType *prev; + + /** + * Array of 0-anonymity items of the given type. + */ + struct Value **array; + + /** + * Allocated size of the array. + */ + unsigned int array_size; + + /** + * First unused offset in 'array'. + */ + unsigned int array_pos; + + /** + * Type of all of the values in 'array'. + */ + enum GNUNET_BLOCK_Type type; +}; + + +/** + * Context for all functions in this plugin. + */ +struct Plugin +{ + /** + * Our execution environment. + */ + struct GNUNET_DATASTORE_PluginEnvironment *env; + + /** + * Mapping from keys to 'struct Value's. + */ + struct GNUNET_CONTAINER_MultiHashMap *keyvalue; + + /** + * Heap organized by minimum expiration time. + */ + struct GNUNET_CONTAINER_Heap *by_expiration; + + /** + * Heap organized by maximum replication value. + */ + struct GNUNET_CONTAINER_Heap *by_replication; + + /** + * Head of list of arrays containing zero-anonymity values by type. + */ + struct ZeroAnonByType *zero_head; + + /** + * Tail of list of arrays containing zero-anonymity values by type. + */ + struct ZeroAnonByType *zero_tail; + + /** + * Size of all values we're storing. + */ + unsigned long long size; + +}; + + +/** + * Get an estimate of how much space the database is + * currently using. + * + * @param cls our "struct Plugin*" + * @return number of bytes used on disk + */ +static unsigned long long +heap_plugin_estimate_size (void *cls) +{ + struct Plugin *plugin = cls; + + return plugin->size; +} + + +/** + * Store an item in the datastore. + * + * @param cls closure + * @param key key for the item + * @param size number of bytes in data + * @param data content stored + * @param type type of the content + * @param priority priority of the content + * @param anonymity anonymity-level for the content + * @param replication replication-level for the content + * @param expiration expiration time for the content + * @param msg set to error message + * @return GNUNET_OK on success + */ +static int +heap_plugin_put (void *cls, + const struct GNUNET_HashCode * key, + uint32_t size, + const void *data, + enum GNUNET_BLOCK_Type type, + uint32_t priority, uint32_t anonymity, + uint32_t replication, + struct GNUNET_TIME_Absolute expiration, char **msg) +{ + struct Plugin *plugin = cls; + struct Value *value; + + value = GNUNET_malloc (sizeof (struct Value) + size); + value->key = *key; + value->data = &value[1]; + value->expire_heap = GNUNET_CONTAINER_heap_insert (plugin->by_expiration, + value, + expiration.abs_value); + value->replication_heap = GNUNET_CONTAINER_heap_insert (plugin->by_replication, + value, + replication); + value->expiration = expiration; + if (0 == anonymity) + { + struct ZeroAnonByType *zabt; + + for (zabt = plugin->zero_head; NULL != zabt; zabt = zabt->next) + if (zabt->type == type) + break; + if (NULL == zabt) + { + zabt = GNUNET_malloc (sizeof (struct ZeroAnonByType)); + zabt->type = type; + GNUNET_CONTAINER_DLL_insert (plugin->zero_head, + plugin->zero_tail, + zabt); + } + if (zabt->array_size == zabt->array_pos) + { + GNUNET_array_grow (zabt->array, + zabt->array_size, + zabt->array_size * 2 + 4); + } + value->zero_anon_offset = zabt->array_pos; + zabt->array[zabt->array_pos++] = value; + } + value->size = size; + value->priority = priority; + value->anonymity = anonymity; + value->replication = replication; + value->type = type; + memcpy (&value[1], data, size); + GNUNET_CONTAINER_multihashmap_put (plugin->keyvalue, + &value->key, + value, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE); + plugin->size += size; + return GNUNET_OK; +} + + +/** + * Delete the given value, removing it from the plugin's data + * structures. + * + * @param plugin the plugin + * @param value value to delete + */ +static void +delete_value (struct Plugin *plugin, + struct Value *value) +{ + GNUNET_assert (GNUNET_YES == + GNUNET_CONTAINER_multihashmap_remove (plugin->keyvalue, + &value->key, + value)); + GNUNET_assert (value == GNUNET_CONTAINER_heap_remove_node (value->expire_heap)); + GNUNET_assert (value == GNUNET_CONTAINER_heap_remove_node (value->replication_heap)); + if (0 == value->anonymity) + { + struct ZeroAnonByType *zabt; + + for (zabt = plugin->zero_head; NULL != zabt; zabt = zabt->next) + if (zabt->type == value->type) + break; + GNUNET_assert (NULL != zabt); + zabt->array[value->zero_anon_offset] = zabt->array[--zabt->array_pos]; + zabt->array[value->zero_anon_offset]->zero_anon_offset = value->zero_anon_offset; + if (0 == zabt->array_pos) + { + GNUNET_array_grow (zabt->array, + zabt->array_size, + 0); + GNUNET_CONTAINER_DLL_remove (plugin->zero_head, + plugin->zero_tail, + zabt); + GNUNET_free (zabt); + } + } + plugin->size -= value->size; + GNUNET_free (value); +} + + +/** + * Closure for iterator called during 'get_key'. + */ +struct GetContext +{ + + /** + * Desired result offset / number of results. + */ + uint64_t offset; + + /** + * The plugin. + */ + struct Plugin *plugin; + + /** + * Requested value hash. + */ + const struct GNUNET_HashCode * vhash; + + /** + * Requested type. + */ + enum GNUNET_BLOCK_Type type; + + /** + * Function to call with the result. + */ + PluginDatumProcessor proc; + + /** + * Closure for 'proc'. + */ + void *proc_cls; +}; + + +/** + * Test if a value matches the specification from the 'get' context + * + * @param gc query + * @param value the value to check against the query + * @return GNUNET_YES if the value matches + */ +static int +match (const struct GetContext *gc, + struct Value *value) +{ + struct GNUNET_HashCode vh; + + if ( (gc->type != GNUNET_BLOCK_TYPE_ANY) && + (gc->type != value->type) ) + return GNUNET_NO; + if (NULL != gc->vhash) + { + GNUNET_CRYPTO_hash (&value[1], value->size, &vh); + if (0 != memcmp (&vh, gc->vhash, sizeof (struct GNUNET_HashCode))) + return GNUNET_NO; + } + return GNUNET_YES; +} + + +/** + * Count number of matching values. + * + * @param cls the 'struct GetContext' + * @param key unused + * @param val the 'struct Value' + * @return GNUNET_YES (continue iteration) + */ +static int +count_iterator (void *cls, + const struct GNUNET_HashCode *key, + void *val) +{ + struct GetContext *gc = cls; + struct Value *value = val; + + if (GNUNET_NO == match (gc, value)) + return GNUNET_OK; + gc->offset++; + return GNUNET_OK; +} + + +/** + * Obtain matching value at 'offset'. + * + * @param cls the 'struct GetContext' + * @param key unused + * @param val the 'struct Value' + * @return GNUNET_YES (continue iteration), GNUNET_NO if result was found + */ +static int +get_iterator (void *cls, + const struct GNUNET_HashCode *key, + void *val) +{ + struct GetContext *gc = cls; + struct Value *value = val; + + if (GNUNET_NO == match (gc, value)) + return GNUNET_OK; + if (0 != gc->offset--) + return GNUNET_OK; + if (GNUNET_NO == + gc->proc (gc->proc_cls, + key, + value->size, + &value[1], + value->type, + value->priority, + value->anonymity, + value->expiration, + (uint64_t) (long) value)) + delete_value (gc->plugin, value); + return GNUNET_NO; +} + + +/** + * Get one of the results for a particular key in the datastore. + * + * @param cls closure + * @param offset offset of the result (modulo num-results); + * specific ordering does not matter for the offset + * @param key maybe NULL (to match all entries) + * @param vhash hash of the value, maybe NULL (to + * match all values that have the right key). + * Note that for DBlocks there is no difference + * betwen key and vhash, but for other blocks + * there may be! + * @param type entries of which type are relevant? + * Use 0 for any type. + * @param proc function to call on each matching value; + * will be called with NULL if nothing matches + * @param proc_cls closure for proc + */ +static void +heap_plugin_get_key (void *cls, uint64_t offset, + const struct GNUNET_HashCode *key, + const struct GNUNET_HashCode *vhash, + enum GNUNET_BLOCK_Type type, PluginDatumProcessor proc, + void *proc_cls) +{ + struct Plugin *plugin = cls; + struct GetContext gc; + + gc.plugin = plugin; + gc.offset = 0; + gc.vhash = vhash; + gc.type = type; + gc.proc = proc; + gc.proc_cls = proc_cls; + if (NULL == key) + { + GNUNET_CONTAINER_multihashmap_iterate (plugin->keyvalue, + &count_iterator, + &gc); + if (0 == gc.offset) + { + proc (proc_cls, + NULL, 0, NULL, 0, 0, 0, GNUNET_TIME_UNIT_ZERO_ABS, 0); + return; + } + gc.offset = offset % gc.offset; + GNUNET_CONTAINER_multihashmap_iterate (plugin->keyvalue, + &get_iterator, + &gc); + } + else + { + GNUNET_CONTAINER_multihashmap_get_multiple (plugin->keyvalue, + key, + &count_iterator, + &gc); + if (0 == gc.offset) + { + proc (proc_cls, + NULL, 0, NULL, 0, 0, 0, GNUNET_TIME_UNIT_ZERO_ABS, 0); + return; + } + gc.offset = offset % gc.offset; + GNUNET_CONTAINER_multihashmap_get_multiple (plugin->keyvalue, + key, + &get_iterator, + &gc); + } +} + + +/** + * Get a random item for replication. Returns a single, not expired, + * random item from those with the highest replication counters. The + * item's replication counter is decremented by one IF it was positive + * before. Call 'proc' with all values ZERO or NULL if the datastore + * is empty. + * + * @param cls closure + * @param proc function to call the value (once only). + * @param proc_cls closure for proc + */ +static void +heap_plugin_get_replication (void *cls, + PluginDatumProcessor proc, + void *proc_cls) +{ + struct Plugin *plugin = cls; + struct Value *value; + + value = GNUNET_CONTAINER_heap_remove_root (plugin->by_replication); + if (NULL == value) + { + proc (proc_cls, + NULL, 0, NULL, 0, 0, 0, GNUNET_TIME_UNIT_ZERO_ABS, 0); + return; + } + if (value->replication > 0) + { + value->replication--; + value->replication_heap = GNUNET_CONTAINER_heap_insert (plugin->by_replication, + value, + value->replication); + } + else + { + /* need a better way to pick a random item, replication level is always 0 */ + value->replication_heap = GNUNET_CONTAINER_heap_insert (plugin->by_replication, + value, + value->replication); + value = GNUNET_CONTAINER_heap_walk_get_next (plugin->by_replication); + } + if (GNUNET_NO == + proc (proc_cls, + &value->key, + value->size, + &value[1], + value->type, + value->priority, + value->anonymity, + value->expiration, + (uint64_t) (long) value)) + delete_value (plugin, value); +} + + +/** + * Get a random item for expiration. Call 'proc' with all values ZERO + * or NULL if the datastore is empty. + * + * @param cls closure + * @param proc function to call the value (once only). + * @param proc_cls closure for proc + */ +static void +heap_plugin_get_expiration (void *cls, PluginDatumProcessor proc, + void *proc_cls) +{ + struct Plugin *plugin = cls; + struct Value *value; + + value = GNUNET_CONTAINER_heap_peek (plugin->by_expiration); + if (NULL == value) + { + proc (proc_cls, + NULL, 0, NULL, 0, 0, 0, GNUNET_TIME_UNIT_ZERO_ABS, 0); + return; + } + if (GNUNET_NO == + proc (proc_cls, + &value->key, + value->size, + &value[1], + value->type, + value->priority, + value->anonymity, + value->expiration, + (uint64_t) (long) value)) + delete_value (plugin, value); +} + + +/** + * Update the priority for a particular key in the datastore. If + * the expiration time in value is different than the time found in + * the datastore, the higher value should be kept. For the + * anonymity level, the lower value is to be used. The specified + * priority should be added to the existing priority, ignoring the + * priority in value. + * + * @param cls our "struct Plugin*" + * @param uid unique identifier of the datum + * @param delta by how much should the priority + * change? If priority + delta < 0 the + * priority should be set to 0 (never go + * negative). + * @param expire new expiration time should be the + * MAX of any existing expiration time and + * this value + * @param msg set to error message + * @return GNUNET_OK on success + */ +static int +heap_plugin_update (void *cls, + uint64_t uid, + int delta, + struct GNUNET_TIME_Absolute expire, char **msg) +{ + struct Plugin *plugin = cls; + struct Value *value; + + value = (struct Value*) (long) uid; + GNUNET_assert (NULL != value); + if (value->expiration.abs_value != expire.abs_value) + { + value->expiration = expire; + GNUNET_CONTAINER_heap_update_cost (plugin->by_expiration, + value->expire_heap, + expire.abs_value); + } + if ( (delta < 0) && (value->priority < - delta) ) + value->priority = 0; + else + value->priority += delta; + return GNUNET_OK; +} + + +/** + * Call the given processor on an item with zero anonymity. + * + * @param cls our "struct Plugin*" + * @param offset offset of the result (modulo num-results); + * specific ordering does not matter for the offset + * @param type entries of which type should be considered? + * Use 0 for any type. + * @param proc function to call on each matching value; + * will be called with NULL if no value matches + * @param proc_cls closure for proc + */ +static void +heap_plugin_get_zero_anonymity (void *cls, uint64_t offset, + enum GNUNET_BLOCK_Type type, + PluginDatumProcessor proc, void *proc_cls) +{ + struct Plugin *plugin = cls; + struct ZeroAnonByType *zabt; + struct Value *value; + uint64_t count; + + count = 0; + for (zabt = plugin->zero_head; NULL != zabt; zabt = zabt->next) + { + if ( (type != GNUNET_BLOCK_TYPE_ANY) && + (type != zabt->type) ) + continue; + count += zabt->array_pos; + } + if (0 == count) + { + proc (proc_cls, + NULL, 0, NULL, 0, 0, 0, GNUNET_TIME_UNIT_ZERO_ABS, 0); + return; + } + offset = offset % count; + for (zabt = plugin->zero_head; NULL != zabt; zabt = zabt->next) + { + if ( (type != GNUNET_BLOCK_TYPE_ANY) && + (type != zabt->type) ) + continue; + if (offset >= zabt->array_pos) + { + offset -= zabt->array_pos; + continue; + } + break; + } + GNUNET_assert (NULL != zabt); + value = zabt->array[offset]; + if (GNUNET_NO == + proc (proc_cls, + &value->key, + value->size, + &value[1], + value->type, + value->priority, + value->anonymity, + value->expiration, + (uint64_t) (long) value)) + delete_value (plugin, value); +} + + +/** + * Drop database. + */ +static void +heap_plugin_drop (void *cls) +{ + /* nothing needs to be done */ +} + + +/** + * Closure for the 'return_value' function. + */ +struct GetAllContext +{ + /** + * Function to call. + */ + PluginKeyProcessor proc; + + /** + * Closure for 'proc'. + */ + void *proc_cls; +}; + + +/** + * Callback invoked to call callback on each value. + * + * @param cls the plugin + * @param key unused + * @param val the value + * @return GNUNET_OK (continue to iterate) + */ +static int +return_value (void *cls, + const struct GNUNET_HashCode *key, + void *val) +{ + struct GetAllContext *gac = cls; + + gac->proc (gac->proc_cls, + key, + 1); + return GNUNET_OK; +} + + +/** + * Get all of the keys in the datastore. + * + * @param cls closure + * @param proc function to call on each key + * @param proc_cls closure for proc + */ +static void +heap_get_keys (void *cls, + PluginKeyProcessor proc, + void *proc_cls) +{ + struct Plugin *plugin = cls; + struct GetAllContext gac; + + gac.proc = proc; + gac.proc_cls = proc_cls; + GNUNET_CONTAINER_multihashmap_iterate (plugin->keyvalue, + &return_value, + &gac); +} + + +/** + * Entry point for the plugin. + * + * @param cls the "struct GNUNET_DATASTORE_PluginEnvironment*" + * @return our "struct Plugin*" + */ +void * +libgnunet_plugin_datastore_heap_init (void *cls) +{ + struct GNUNET_DATASTORE_PluginEnvironment *env = cls; + struct GNUNET_DATASTORE_PluginFunctions *api; + struct Plugin *plugin; + unsigned long long esize; + + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_number (env->cfg, + "datastore-heap", + "HASHMAPSIZE", + &esize)) + esize = 128 * 1024; + plugin = GNUNET_malloc (sizeof (struct Plugin)); + plugin->env = env; + plugin->keyvalue = GNUNET_CONTAINER_multihashmap_create (esize, GNUNET_YES); + plugin->by_expiration = GNUNET_CONTAINER_heap_create (GNUNET_CONTAINER_HEAP_ORDER_MIN); + plugin->by_replication = GNUNET_CONTAINER_heap_create (GNUNET_CONTAINER_HEAP_ORDER_MAX); + api = GNUNET_malloc (sizeof (struct GNUNET_DATASTORE_PluginFunctions)); + api->cls = plugin; + api->estimate_size = &heap_plugin_estimate_size; + api->put = &heap_plugin_put; + api->update = &heap_plugin_update; + api->get_key = &heap_plugin_get_key; + api->get_replication = &heap_plugin_get_replication; + api->get_expiration = &heap_plugin_get_expiration; + api->get_zero_anonymity = &heap_plugin_get_zero_anonymity; + api->drop = &heap_plugin_drop; + api->get_keys = &heap_get_keys; + GNUNET_log_from (GNUNET_ERROR_TYPE_INFO, "heap", + _("Heap database running\n")); + return api; +} + + +/** + * Callback invoked to free all value. + * + * @param cls the plugin + * @param key unused + * @param val the value + * @return GNUNET_OK (continue to iterate) + */ +static int +free_value (void *cls, + const struct GNUNET_HashCode *key, + void *val) +{ + struct Plugin *plugin = cls; + struct Value *value = val; + + delete_value (plugin, value); + return GNUNET_OK; +} + + +/** + * Exit point from the plugin. + * @param cls our "struct Plugin*" + * @return always NULL + */ +void * +libgnunet_plugin_datastore_heap_done (void *cls) +{ + struct GNUNET_DATASTORE_PluginFunctions *api = cls; + struct Plugin *plugin = api->cls; + + GNUNET_CONTAINER_multihashmap_iterate (plugin->keyvalue, + &free_value, + plugin); + GNUNET_CONTAINER_multihashmap_destroy (plugin->keyvalue); + GNUNET_CONTAINER_heap_destroy (plugin->by_expiration); + GNUNET_CONTAINER_heap_destroy (plugin->by_replication); + GNUNET_free (plugin); + GNUNET_free (api); + return NULL; +} + +/* end of plugin_datastore_heap.c */ diff --git a/src/datastore/plugin_datastore_mysql.c b/src/datastore/plugin_datastore_mysql.c index ed7741c..ad70e73 100644 --- a/src/datastore/plugin_datastore_mysql.c +++ b/src/datastore/plugin_datastore_mysql.c @@ -176,7 +176,7 @@ struct Plugin #define UPDATE_ENTRY "UPDATE gn090 SET prio=prio+?,expire=IF(expire>=?,expire,?) WHERE uid=?" struct GNUNET_MYSQL_StatementHandle *update_entry; -#define DEC_REPL "UPDATE gn090 SET repl=GREATEST (0, repl - 1) WHERE uid=?" +#define DEC_REPL "UPDATE gn090 SET repl=GREATEST (1, repl) - 1 WHERE uid=?" struct GNUNET_MYSQL_StatementHandle *dec_repl; #define SELECT_SIZE "SELECT SUM(BIT_LENGTH(value) DIV 8) FROM gn090" @@ -281,7 +281,7 @@ mysql_plugin_estimate_size (void *cls) * @return GNUNET_OK on success */ static int -mysql_plugin_put (void *cls, const GNUNET_HashCode * key, uint32_t size, +mysql_plugin_put (void *cls, const struct GNUNET_HashCode * key, uint32_t size, const void *data, enum GNUNET_BLOCK_Type type, uint32_t priority, uint32_t anonymity, uint32_t replication, struct GNUNET_TIME_Absolute expiration, char **msg) @@ -297,15 +297,15 @@ mysql_plugin_put (void *cls, const GNUNET_HashCode * key, uint32_t size, unsigned long hashSize; unsigned long hashSize2; unsigned long lsize; - GNUNET_HashCode vhash; + struct GNUNET_HashCode vhash; if (size > MAX_DATUM_SIZE) { GNUNET_break (0); return GNUNET_SYSERR; } - hashSize = sizeof (GNUNET_HashCode); - hashSize2 = sizeof (GNUNET_HashCode); + hashSize = sizeof (struct GNUNET_HashCode); + hashSize2 = sizeof (struct GNUNET_HashCode); lsize = size; GNUNET_CRYPTO_hash (data, size, &vhash); if (GNUNET_OK != @@ -403,11 +403,11 @@ execute_select (struct Plugin *plugin, struct GNUNET_MYSQL_StatementHandle *stmt unsigned long size; unsigned long long uid; char value[GNUNET_DATASTORE_MAX_VALUE_SIZE]; - GNUNET_HashCode key; + struct GNUNET_HashCode key; struct GNUNET_TIME_Absolute expiration; MYSQL_BIND rbind[7]; - hashSize = sizeof (GNUNET_HashCode); + hashSize = sizeof (struct GNUNET_HashCode); memset (rbind, 0, sizeof (rbind)); rbind[0].buffer_type = MYSQL_TYPE_LONG; rbind[0].buffer = &type; @@ -442,8 +442,8 @@ execute_select (struct Plugin *plugin, struct GNUNET_MYSQL_StatementHandle *stmt return; } GNUNET_assert (size <= sizeof (value)); - if ((rbind[4].buffer_length != sizeof (GNUNET_HashCode)) || - (hashSize != sizeof (GNUNET_HashCode))) + if ((rbind[4].buffer_length != sizeof (struct GNUNET_HashCode)) || + (hashSize != sizeof (struct GNUNET_HashCode))) { GNUNET_break (0); proc (proc_cls, NULL, 0, NULL, 0, 0, 0, GNUNET_TIME_UNIT_ZERO_ABS, 0); @@ -486,8 +486,8 @@ execute_select (struct Plugin *plugin, struct GNUNET_MYSQL_StatementHandle *stmt * @param proc_cls closure for proc */ static void -mysql_plugin_get_key (void *cls, uint64_t offset, const GNUNET_HashCode * key, - const GNUNET_HashCode * vhash, +mysql_plugin_get_key (void *cls, uint64_t offset, const struct GNUNET_HashCode * key, + const struct GNUNET_HashCode * vhash, enum GNUNET_BLOCK_Type type, PluginDatumProcessor proc, void *proc_cls) { @@ -501,8 +501,8 @@ mysql_plugin_get_key (void *cls, uint64_t offset, const GNUNET_HashCode * key, GNUNET_assert (key != NULL); GNUNET_assert (NULL != proc); - hashSize = sizeof (GNUNET_HashCode); - hashSize2 = sizeof (GNUNET_HashCode); + hashSize = sizeof (struct GNUNET_HashCode); + hashSize2 = sizeof (struct GNUNET_HashCode); memset (cbind, 0, sizeof (cbind)); total = -1; cbind[0].buffer_type = MYSQL_TYPE_LONGLONG; @@ -669,7 +669,7 @@ struct ReplCtx * GNUNET_NO to delete the item and continue (if supported) */ static int -repl_proc (void *cls, const GNUNET_HashCode * key, uint32_t size, +repl_proc (void *cls, const struct GNUNET_HashCode * key, uint32_t size, const void *data, enum GNUNET_BLOCK_Type type, uint32_t priority, uint32_t anonymity, struct GNUNET_TIME_Absolute expiration, uint64_t uid) @@ -763,7 +763,7 @@ mysql_plugin_get_keys (void *cls, const char *query = "SELECT hash FROM gn090"; int ret; MYSQL_STMT *statement; - GNUNET_HashCode key; + struct GNUNET_HashCode key; MYSQL_BIND cbind[1]; unsigned long length; @@ -808,7 +808,7 @@ mysql_plugin_get_keys (void *cls, } while (0 == (ret = mysql_stmt_fetch (statement))) { - if (sizeof (GNUNET_HashCode) == length) + if (sizeof (struct GNUNET_HashCode) == length) proc (proc_cls, &key, 1); } if (ret != MYSQL_NO_DATA) @@ -869,7 +869,7 @@ struct ExpiCtx * GNUNET_NO to delete the item and continue (if supported) */ static int -expi_proc (void *cls, const GNUNET_HashCode * key, uint32_t size, +expi_proc (void *cls, const struct GNUNET_HashCode * key, uint32_t size, const void *data, enum GNUNET_BLOCK_Type type, uint32_t priority, uint32_t anonymity, struct GNUNET_TIME_Absolute expiration, uint64_t uid) diff --git a/src/datastore/plugin_datastore_postgres.c b/src/datastore/plugin_datastore_postgres.c index 6dec314..83fc423 100644 --- a/src/datastore/plugin_datastore_postgres.c +++ b/src/datastore/plugin_datastore_postgres.c @@ -270,14 +270,14 @@ postgres_plugin_estimate_size (void *cls) * @return GNUNET_OK on success */ static int -postgres_plugin_put (void *cls, const GNUNET_HashCode * key, uint32_t size, +postgres_plugin_put (void *cls, const struct GNUNET_HashCode * key, uint32_t size, const void *data, enum GNUNET_BLOCK_Type type, uint32_t priority, uint32_t anonymity, uint32_t replication, struct GNUNET_TIME_Absolute expiration, char **msg) { struct Plugin *plugin = cls; - GNUNET_HashCode vhash; + struct GNUNET_HashCode vhash; PGresult *ret; uint32_t btype = htonl (type); uint32_t bprio = htonl (priority); @@ -301,8 +301,8 @@ postgres_plugin_put (void *cls, const GNUNET_HashCode * key, uint32_t size, sizeof (bprio), sizeof (banon), sizeof (bexpi), - sizeof (GNUNET_HashCode), - sizeof (GNUNET_HashCode), + sizeof (struct GNUNET_HashCode), + sizeof (struct GNUNET_HashCode), size }; const int paramFormats[] = { 1, 1, 1, 1, 1, 1, 1, 1 }; @@ -345,7 +345,7 @@ process_result (struct Plugin *plugin, PluginDatumProcessor proc, uint32_t size; unsigned int rowid; struct GNUNET_TIME_Absolute expiration_time; - GNUNET_HashCode key; + struct GNUNET_HashCode key; if (GNUNET_OK != GNUNET_POSTGRES_check_result_ (plugin->dbh, res, PGRES_TUPLES_OK, "PQexecPrepared", "select", @@ -380,7 +380,7 @@ process_result (struct Plugin *plugin, PluginDatumProcessor proc, (sizeof (uint32_t) != PQfsize (res, 1)) || (sizeof (uint32_t) != PQfsize (res, 2)) || (sizeof (uint64_t) != PQfsize (res, 3)) || - (sizeof (GNUNET_HashCode) != PQgetlength (res, 0, 4))) + (sizeof (struct GNUNET_HashCode) != PQgetlength (res, 0, 4))) { GNUNET_break (0); PQclear (res); @@ -394,7 +394,7 @@ process_result (struct Plugin *plugin, PluginDatumProcessor proc, anonymity = ntohl (*(uint32_t *) PQgetvalue (res, 0, 2)); expiration_time.abs_value = GNUNET_ntohll (*(uint64_t *) PQgetvalue (res, 0, 3)); - memcpy (&key, PQgetvalue (res, 0, 4), sizeof (GNUNET_HashCode)); + memcpy (&key, PQgetvalue (res, 0, 4), sizeof (struct GNUNET_HashCode)); size = PQgetlength (res, 0, 5); GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, "datastore-postgres", "Found result of size %u bytes and type %u in database\n", @@ -443,8 +443,8 @@ process_result (struct Plugin *plugin, PluginDatumProcessor proc, */ static void postgres_plugin_get_key (void *cls, uint64_t offset, - const GNUNET_HashCode * key, - const GNUNET_HashCode * vhash, + const struct GNUNET_HashCode * key, + const struct GNUNET_HashCode * vhash, enum GNUNET_BLOCK_Type type, PluginDatumProcessor proc, void *proc_cls) { @@ -461,14 +461,14 @@ postgres_plugin_get_key (void *cls, uint64_t offset, GNUNET_assert (key != NULL); paramValues[0] = (const char *) key; - paramLengths[0] = sizeof (GNUNET_HashCode); + paramLengths[0] = sizeof (struct GNUNET_HashCode); btype = htonl (type); if (type != 0) { if (vhash != NULL) { paramValues[1] = (const char *) vhash; - paramLengths[1] = sizeof (GNUNET_HashCode); + paramLengths[1] = sizeof (struct GNUNET_HashCode); paramValues[2] = (const char *) &btype; paramLengths[2] = sizeof (btype); paramValues[3] = (const char *) &blimit_off; @@ -499,7 +499,7 @@ postgres_plugin_get_key (void *cls, uint64_t offset, if (vhash != NULL) { paramValues[1] = (const char *) vhash; - paramLengths[1] = sizeof (GNUNET_HashCode); + paramLengths[1] = sizeof (struct GNUNET_HashCode); paramValues[2] = (const char *) &blimit_off; paramLengths[2] = sizeof (blimit_off); nparams = 3; @@ -628,7 +628,7 @@ struct ReplCtx * GNUNET_NO to delete the item and continue (if supported) */ static int -repl_proc (void *cls, const GNUNET_HashCode * key, uint32_t size, +repl_proc (void *cls, const struct GNUNET_HashCode * key, uint32_t size, const void *data, enum GNUNET_BLOCK_Type type, uint32_t priority, uint32_t anonymity, struct GNUNET_TIME_Absolute expiration, uint64_t uid) @@ -792,16 +792,16 @@ postgres_plugin_get_keys (void *cls, struct Plugin *plugin = cls; int ret; int i; - GNUNET_HashCode key; + struct GNUNET_HashCode key; PGresult * res; res = PQexecPrepared (plugin->dbh, "get_keys", 0, NULL, NULL, NULL, 1); ret = PQntuples (res); for (i=0;ienv->duc (plugin->env->cls, 0); } -#ifdef ENABLE_NLS - plugin->fn = - GNUNET_STRINGS_to_utf8 (afsdir, strlen (afsdir), nl_langinfo (CODESET)); -#else - plugin->fn = GNUNET_STRINGS_to_utf8 (afsdir, strlen (afsdir), "UTF-8"); /* good luck */ -#endif - GNUNET_free (afsdir); + /* afsdir should be UTF-8-encoded. If it isn't, it's a bug */ + plugin->fn = afsdir; /* Open database and precompile statements */ if (sqlite3_open (plugin->fn, &plugin->dbh) != SQLITE_OK) @@ -480,7 +473,7 @@ delete_by_rowid (struct Plugin *plugin, unsigned long long rid) * @return GNUNET_OK on success */ static int -sqlite_plugin_put (void *cls, const GNUNET_HashCode * key, uint32_t size, +sqlite_plugin_put (void *cls, const struct GNUNET_HashCode * key, uint32_t size, const void *data, enum GNUNET_BLOCK_Type type, uint32_t priority, uint32_t anonymity, uint32_t replication, struct GNUNET_TIME_Absolute expiration, char **msg) @@ -489,7 +482,7 @@ sqlite_plugin_put (void *cls, const GNUNET_HashCode * key, uint32_t size, int n; int ret; sqlite3_stmt *stmt; - GNUNET_HashCode vhash; + struct GNUNET_HashCode vhash; uint64_t rvalue; if (size > MAX_ITEM_SIZE) @@ -510,10 +503,10 @@ sqlite_plugin_put (void *cls, const GNUNET_HashCode * key, uint32_t size, (SQLITE_OK != sqlite3_bind_int64 (stmt, 5, expiration.abs_value)) || (SQLITE_OK != sqlite3_bind_int64 (stmt, 6, rvalue)) || (SQLITE_OK != - sqlite3_bind_blob (stmt, 7, key, sizeof (GNUNET_HashCode), + sqlite3_bind_blob (stmt, 7, key, sizeof (struct GNUNET_HashCode), SQLITE_TRANSIENT)) || (SQLITE_OK != - sqlite3_bind_blob (stmt, 8, &vhash, sizeof (GNUNET_HashCode), + sqlite3_bind_blob (stmt, 8, &vhash, sizeof (struct GNUNET_HashCode), SQLITE_TRANSIENT)) || (SQLITE_OK != sqlite3_bind_blob (stmt, 9, data, size, SQLITE_TRANSIENT))) { @@ -648,7 +641,7 @@ execute_get (struct Plugin *plugin, sqlite3_stmt * stmt, case SQLITE_ROW: size = sqlite3_column_bytes (stmt, 5); rowid = sqlite3_column_int64 (stmt, 6); - if (sqlite3_column_bytes (stmt, 4) != sizeof (GNUNET_HashCode)) + if (sqlite3_column_bytes (stmt, 4) != sizeof (struct GNUNET_HashCode)) { GNUNET_log_from (GNUNET_ERROR_TYPE_WARNING, "sqlite", _ @@ -768,8 +761,8 @@ sqlite_plugin_get_zero_anonymity (void *cls, uint64_t offset, * @param proc_cls closure for proc */ static void -sqlite_plugin_get_key (void *cls, uint64_t offset, const GNUNET_HashCode * key, - const GNUNET_HashCode * vhash, +sqlite_plugin_get_key (void *cls, uint64_t offset, const struct GNUNET_HashCode * key, + const struct GNUNET_HashCode * vhash, enum GNUNET_BLOCK_Type type, PluginDatumProcessor proc, void *proc_cls) { @@ -796,11 +789,11 @@ sqlite_plugin_get_key (void *cls, uint64_t offset, const GNUNET_HashCode * key, } sqoff = 1; ret = - sqlite3_bind_blob (stmt, sqoff++, key, sizeof (GNUNET_HashCode), + sqlite3_bind_blob (stmt, sqoff++, key, sizeof (struct GNUNET_HashCode), SQLITE_TRANSIENT); if ((vhash != NULL) && (ret == SQLITE_OK)) ret = - sqlite3_bind_blob (stmt, sqoff++, vhash, sizeof (GNUNET_HashCode), + sqlite3_bind_blob (stmt, sqoff++, vhash, sizeof (struct GNUNET_HashCode), SQLITE_TRANSIENT); if ((type != 0) && (ret == SQLITE_OK)) ret = sqlite3_bind_int (stmt, sqoff++, type); @@ -845,11 +838,11 @@ sqlite_plugin_get_key (void *cls, uint64_t offset, const GNUNET_HashCode * key, } sqoff = 1; ret = - sqlite3_bind_blob (stmt, sqoff++, key, sizeof (GNUNET_HashCode), + sqlite3_bind_blob (stmt, sqoff++, key, sizeof (struct GNUNET_HashCode), SQLITE_TRANSIENT); if ((vhash != NULL) && (ret == SQLITE_OK)) ret = - sqlite3_bind_blob (stmt, sqoff++, vhash, sizeof (GNUNET_HashCode), + sqlite3_bind_blob (stmt, sqoff++, vhash, sizeof (struct GNUNET_HashCode), SQLITE_TRANSIENT); if ((type != 0) && (ret == SQLITE_OK)) ret = sqlite3_bind_int (stmt, sqoff++, type); @@ -916,7 +909,7 @@ struct ReplCtx * GNUNET_NO to delete the item */ static int -repl_proc (void *cls, const GNUNET_HashCode * key, uint32_t size, +repl_proc (void *cls, const struct GNUNET_HashCode * key, uint32_t size, const void *data, enum GNUNET_BLOCK_Type type, uint32_t priority, uint32_t anonymity, struct GNUNET_TIME_Absolute expiration, uint64_t uid) @@ -1076,7 +1069,7 @@ sqlite_plugin_get_keys (void *cls, void *proc_cls) { struct Plugin *plugin = cls; - const GNUNET_HashCode *key; + const struct GNUNET_HashCode *key; sqlite3_stmt *stmt; int ret; @@ -1089,9 +1082,11 @@ sqlite_plugin_get_keys (void *cls, } while (SQLITE_ROW == (ret = sqlite3_step (stmt))) { - key = sqlite3_column_blob (stmt, 1); - if (sizeof (GNUNET_HashCode) == sqlite3_column_bytes (stmt, 1)) + key = sqlite3_column_blob (stmt, 0); + if (sizeof (struct GNUNET_HashCode) == sqlite3_column_bytes (stmt, 0)) proc (proc_cls, key, 1); + else + GNUNET_break (0); } if (SQLITE_DONE != ret) LOG_SQLITE (plugin, NULL, GNUNET_ERROR_TYPE_ERROR, "sqlite_step"); diff --git a/src/datastore/plugin_datastore_template.c b/src/datastore/plugin_datastore_template.c index 174d3d2..2978de4 100644 --- a/src/datastore/plugin_datastore_template.c +++ b/src/datastore/plugin_datastore_template.c @@ -71,7 +71,7 @@ template_plugin_estimate_size (void *cls) * @return GNUNET_OK on success */ static int -template_plugin_put (void *cls, const GNUNET_HashCode * key, uint32_t size, +template_plugin_put (void *cls, const struct GNUNET_HashCode * key, uint32_t size, const void *data, enum GNUNET_BLOCK_Type type, uint32_t priority, uint32_t anonymity, uint32_t replication, @@ -103,8 +103,8 @@ template_plugin_put (void *cls, const GNUNET_HashCode * key, uint32_t size, */ static void template_plugin_get_key (void *cls, uint64_t offset, - const GNUNET_HashCode * key, - const GNUNET_HashCode * vhash, + const struct GNUNET_HashCode * key, + const struct GNUNET_HashCode * vhash, enum GNUNET_BLOCK_Type type, PluginDatumProcessor proc, void *proc_cls) { @@ -212,6 +212,21 @@ template_plugin_drop (void *cls) } +/** + * Get all of the keys in the datastore. + * + * @param cls closure + * @param proc function to call on each key + * @param proc_cls closure for proc + */ +static void +template_get_keys (void *cls, + PluginKeyProcessor proc, + void *proc_cls) +{ +} + + /** * Entry point for the plugin. * @@ -237,6 +252,7 @@ libgnunet_plugin_datastore_template_init (void *cls) api->get_expiration = &template_plugin_get_expiration; api->get_zero_anonymity = &template_plugin_get_zero_anonymity; api->drop = &template_plugin_drop; + api->get_keys = &template_get_keys; GNUNET_log_from (GNUNET_ERROR_TYPE_INFO, "template", _("Template database running\n")); return api; diff --git a/src/datastore/test_datastore_api.c b/src/datastore/test_datastore_api.c index 4c07366..66ba416 100644 --- a/src/datastore/test_datastore_api.c +++ b/src/datastore/test_datastore_api.c @@ -30,10 +30,8 @@ #include "gnunet_util_lib.h" #include "gnunet_protocols.h" #include "gnunet_datastore_service.h" +#include "gnunet_testing_lib.h" -#define VERBOSE GNUNET_NO - -#define START_DATASTORE GNUNET_YES /** * How long until we give up on transmitting the message? @@ -121,7 +119,7 @@ enum RunPhase struct CpsRunContext { - GNUNET_HashCode key; + struct GNUNET_HashCode key; int i; int rid; const struct GNUNET_CONFIGURATION_Handle *cfg; @@ -173,7 +171,7 @@ get_reserved (void *cls, int success, struct GNUNET_TIME_Absolute min_expiration static void -check_value (void *cls, const GNUNET_HashCode * key, size_t size, +check_value (void *cls, const struct GNUNET_HashCode * key, size_t size, const void *data, enum GNUNET_BLOCK_Type type, uint32_t priority, uint32_t anonymity, struct GNUNET_TIME_Absolute expiration, uint64_t uid) @@ -219,7 +217,7 @@ check_value (void *cls, const GNUNET_HashCode * key, size_t size, static void -delete_value (void *cls, const GNUNET_HashCode * key, size_t size, +delete_value (void *cls, const struct GNUNET_HashCode * key, size_t size, const void *data, enum GNUNET_BLOCK_Type type, uint32_t priority, uint32_t anonymity, struct GNUNET_TIME_Absolute expiration, uint64_t uid) @@ -239,7 +237,7 @@ delete_value (void *cls, const GNUNET_HashCode * key, size_t size, static void -check_nothing (void *cls, const GNUNET_HashCode * key, size_t size, +check_nothing (void *cls, const struct GNUNET_HashCode * key, size_t size, const void *data, enum GNUNET_BLOCK_Type type, uint32_t priority, uint32_t anonymity, struct GNUNET_TIME_Absolute expiration, uint64_t uid) @@ -255,7 +253,7 @@ check_nothing (void *cls, const GNUNET_HashCode * key, size_t size, static void -check_multiple (void *cls, const GNUNET_HashCode * key, size_t size, +check_multiple (void *cls, const struct GNUNET_HashCode * key, size_t size, const void *data, enum GNUNET_BLOCK_Type type, uint32_t priority, uint32_t anonymity, struct GNUNET_TIME_Absolute expiration, uint64_t uid) @@ -287,7 +285,7 @@ check_multiple (void *cls, const GNUNET_HashCode * key, size_t size, static void -check_update (void *cls, const GNUNET_HashCode * key, size_t size, +check_update (void *cls, const struct GNUNET_HashCode * key, size_t size, const void *data, enum GNUNET_BLOCK_Type type, uint32_t priority, uint32_t anonymity, struct GNUNET_TIME_Absolute expiration, uint64_t uid) @@ -314,16 +312,12 @@ run_continuation (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) struct CpsRunContext *crc = cls; ok = (int) crc->phase; -#if VERBOSE GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Test in phase %u\n", crc->phase); -#endif switch (crc->phase) { case RP_PUT: -#if VERBOSE GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Executing `%s' number %u\n", "PUT", crc->i); -#endif GNUNET_CRYPTO_hash (&crc->i, sizeof (int), &crc->key); GNUNET_DATASTORE_put (datastore, 0, &crc->key, get_size (crc->i), get_data (crc->i), get_type (crc->i), @@ -336,10 +330,8 @@ run_continuation (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) break; case RP_GET: crc->i--; -#if VERBOSE GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Executing `%s' number %u\n", "GET", crc->i); -#endif GNUNET_CRYPTO_hash (&crc->i, sizeof (int), &crc->key); GNUNET_DATASTORE_get_key (datastore, crc->offset, &crc->key, get_type (crc->i), 1, 1, TIMEOUT, &check_value, @@ -347,10 +339,8 @@ run_continuation (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) break; case RP_DEL: crc->i--; -#if VERBOSE GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Executing `%s' number %u\n", "DEL", crc->i); -#endif crc->data = NULL; GNUNET_CRYPTO_hash (&crc->i, sizeof (int), &crc->key); GNUNET_assert (NULL != @@ -359,10 +349,8 @@ run_continuation (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) &delete_value, crc)); break; case RP_DO_DEL: -#if VERBOSE GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Executing `%s' number %u\n", "DO_DEL", crc->i); -#endif if (crc->i == 0) { crc->i = ITERATIONS; @@ -379,10 +367,8 @@ run_continuation (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) break; case RP_DELVALIDATE: crc->i--; -#if VERBOSE GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Executing `%s' number %u\n", "DEL-VALIDATE", crc->i); -#endif GNUNET_CRYPTO_hash (&crc->i, sizeof (int), &crc->key); GNUNET_assert (NULL != GNUNET_DATASTORE_get_key (datastore, crc->offset, &crc->key, @@ -433,9 +419,7 @@ run_continuation (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) &check_update, crc)); break; case RP_DONE: -#if VERBOSE GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Finished, disconnecting\n"); -#endif GNUNET_DATASTORE_disconnect (datastore, GNUNET_YES); GNUNET_free (crc); ok = 0; @@ -479,11 +463,12 @@ run_tests (void *cls, int32_t success, struct GNUNET_TIME_Absolute min_expiratio static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) { struct CpsRunContext *crc; - static GNUNET_HashCode zkey; + static struct GNUNET_HashCode zkey; crc = GNUNET_malloc (sizeof (struct CpsRunContext)); crc->cfg = cfg; @@ -504,88 +489,21 @@ run (void *cls, char *const *args, const char *cfgfile, } -static int -check () +int +main (int argc, char *argv[]) { char cfg_name[128]; -#if START_DATASTORE - struct GNUNET_OS_Process *proc; -#endif - char *const argv[] = { - "test-datastore-api", - "-c", - cfg_name, -#if VERBOSE - "-L", "DEBUG", -#endif - NULL - }; - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; + plugin_name = GNUNET_TESTING_get_testname_from_underscore (argv[0]); GNUNET_snprintf (cfg_name, sizeof (cfg_name), "test_datastore_api_data_%s.conf", plugin_name); -#if START_DATASTORE - proc = - GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-arm", - "gnunet-service-arm", -#if VERBOSE - "-L", "DEBUG", -#endif - "-c", cfg_name, NULL); -#endif - GNUNET_assert (NULL != proc); - GNUNET_PROGRAM_run ((sizeof (argv) / sizeof (char *)) - 1, argv, - "test-datastore-api", "nohelp", options, &run, NULL); -#if START_DATASTORE - sleep (1); /* give datastore chance to receive 'DROP' request */ - if (0 != GNUNET_OS_process_kill (proc, SIGTERM)) - { - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); - ok = 1; - } - GNUNET_OS_process_wait (proc); - GNUNET_OS_process_destroy (proc); - proc = NULL; -#endif - if (ok != 0) - FPRINTF (stderr, "Missed some testcases: %u\n", ok); + if (0 != + GNUNET_TESTING_peer_run ("test-gnunet-datastore", + cfg_name, + &run, + NULL)) + return 1; return ok; } -int -main (int argc, char *argv[]) -{ - int ret; - char *pos; - char dir_name[128]; - - sleep (1); - /* determine name of plugin to use */ - plugin_name = argv[0]; - while (NULL != (pos = strstr (plugin_name, "_"))) - plugin_name = pos + 1; - if (NULL != (pos = strstr (plugin_name, "."))) - pos[0] = 0; - else - pos = (char *) plugin_name; - - GNUNET_snprintf (dir_name, sizeof (dir_name), "/tmp/test-gnunet-datastore-%s", - plugin_name); - GNUNET_DISK_directory_remove (dir_name); - GNUNET_log_setup ("test-datastore-api", -#if VERBOSE - "DEBUG", -#else - "WARNING", -#endif - NULL); - ret = check (); - if (pos != plugin_name) - pos[0] = '.'; - GNUNET_DISK_directory_remove (dir_name); - return ret; -} - /* end of test_datastore_api.c */ diff --git a/src/datastore/test_datastore_api_data_heap.conf b/src/datastore/test_datastore_api_data_heap.conf new file mode 100644 index 0000000..0e6994d --- /dev/null +++ b/src/datastore/test_datastore_api_data_heap.conf @@ -0,0 +1,20 @@ +@INLINE@ test_defaults.conf +[PATHS] +SERVICEHOME = /tmp/test-gnunet-datastore-heap/ + +[TESTING] +WEAKRANDOM = YES + +[arm] +PORT = 42466 +DEFAULTSERVICES = + +[statistics] +PORT = 22667 + +[resolver] +PORT = 42464 + +[datastore] +QUOTA = 10 MB +DATABASE = heap diff --git a/src/datastore/test_datastore_api_data_mysql.conf b/src/datastore/test_datastore_api_data_mysql.conf index 8e5a3dc..92967b9 100644 --- a/src/datastore/test_datastore_api_data_mysql.conf +++ b/src/datastore/test_datastore_api_data_mysql.conf @@ -1,7 +1,6 @@ @INLINE@ test_defaults.conf [PATHS] SERVICEHOME = /tmp/test-gnunet-datastore-mysql/ -DEFAULTCONFIG = test_datastore_api_data_mysql.conf [TESTING] WEAKRANDOM = YES diff --git a/src/datastore/test_datastore_api_data_postgres.conf b/src/datastore/test_datastore_api_data_postgres.conf index 046c561..a1a2168 100644 --- a/src/datastore/test_datastore_api_data_postgres.conf +++ b/src/datastore/test_datastore_api_data_postgres.conf @@ -1,7 +1,6 @@ @INLINE@ test_defaults.conf [PATHS] SERVICEHOME = /tmp/test-gnunet-datastore-postgres/ -DEFAULTCONFIG = test_datastore_api_data_postgres.conf [TESTING] WEAKRANDOM = YES diff --git a/src/datastore/test_datastore_api_data_sqlite.conf b/src/datastore/test_datastore_api_data_sqlite.conf index 098f9d2..953aef2 100644 --- a/src/datastore/test_datastore_api_data_sqlite.conf +++ b/src/datastore/test_datastore_api_data_sqlite.conf @@ -1,7 +1,6 @@ @INLINE@ test_defaults.conf [PATHS] SERVICEHOME = /tmp/test-gnunet-datastore-sqlite/ -DEFAULTCONFIG = test_datastore_api_data_sqlite.conf [TESTING] WEAKRANDOM = YES @@ -19,6 +18,4 @@ PORT = 42464 [datastore] QUOTA = 10 MB -[fs] -AUTOSTART = NO diff --git a/src/datastore/test_datastore_api_management.c b/src/datastore/test_datastore_api_management.c index bb3898e..9eae32f 100644 --- a/src/datastore/test_datastore_api_management.c +++ b/src/datastore/test_datastore_api_management.c @@ -22,13 +22,12 @@ * @brief Test for the space management functions of the datastore implementation. * @author Christian Grothoff */ - #include "platform.h" #include "gnunet_util_lib.h" #include "gnunet_protocols.h" #include "gnunet_datastore_service.h" +#include "gnunet_testing_lib.h" -#define VERBOSE GNUNET_NO /** * How long until we give up on transmitting the message? @@ -41,6 +40,27 @@ */ #define ITERATIONS 5000 +enum RunPhase +{ + RP_PUT, + RP_GET, + RP_DONE, + RP_GET_FAIL +}; + + +struct CpsRunContext +{ + struct GNUNET_HashCode key; + int i; + int found; + const struct GNUNET_CONFIGURATION_Handle *cfg; + void *data; + enum RunPhase phase; + uint64_t offset; +}; + + static struct GNUNET_DATASTORE_Handle *datastore; static struct GNUNET_TIME_Absolute now; @@ -49,6 +69,7 @@ static int ok; static const char *plugin_name; + static size_t get_size (int i) { @@ -96,26 +117,6 @@ get_expiration (int i) return av; } -enum RunPhase -{ - RP_PUT, - RP_GET, - RP_DONE, - RP_GET_FAIL -}; - - -struct CpsRunContext -{ - GNUNET_HashCode key; - int i; - int found; - const struct GNUNET_CONFIGURATION_Handle *cfg; - void *data; - enum RunPhase phase; - uint64_t offset; -}; - static void run_continuation (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc); @@ -137,7 +138,7 @@ check_success (void *cls, int success, struct GNUNET_TIME_Absolute min_expiratio static void -check_value (void *cls, const GNUNET_HashCode * key, size_t size, +check_value (void *cls, const struct GNUNET_HashCode * key, size_t size, const void *data, enum GNUNET_BLOCK_Type type, uint32_t priority, uint32_t anonymity, struct GNUNET_TIME_Absolute expiration, uint64_t uid) @@ -169,7 +170,7 @@ check_value (void *cls, const GNUNET_HashCode * key, size_t size, static void -check_nothing (void *cls, const GNUNET_HashCode * key, size_t size, +check_nothing (void *cls, const struct GNUNET_HashCode * key, size_t size, const void *data, enum GNUNET_BLOCK_Type type, uint32_t priority, uint32_t anonymity, struct GNUNET_TIME_Absolute expiration, uint64_t uid) @@ -193,10 +194,8 @@ run_continuation (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) switch (crc->phase) { case RP_PUT: -#if VERBOSE GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Executing `%s' number %u\n", "PUT", crc->i); -#endif GNUNET_CRYPTO_hash (&crc->i, sizeof (int), &crc->key); GNUNET_DATASTORE_put (datastore, 0, &crc->key, get_size (crc->i), get_data (crc->i), get_type (crc->i), @@ -214,20 +213,16 @@ run_continuation (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) } break; case RP_GET: -#if VERBOSE GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Executing `%s' number %u\n", "GET", crc->i); -#endif GNUNET_CRYPTO_hash (&crc->i, sizeof (int), &crc->key); GNUNET_DATASTORE_get_key (datastore, crc->offset++, &crc->key, get_type (crc->i), 1, 1, TIMEOUT, &check_value, crc); break; case RP_GET_FAIL: -#if VERBOSE GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Executing `%s' number %u\n", "GET(f)", crc->i); -#endif GNUNET_CRYPTO_hash (&crc->i, sizeof (int), &crc->key); GNUNET_DATASTORE_get_key (datastore, crc->offset++, &crc->key, get_type (crc->i), 1, 1, TIMEOUT, &check_nothing, @@ -235,9 +230,7 @@ run_continuation (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) break; case RP_DONE: GNUNET_assert (0 == crc->i); -#if VERBOSE GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Finished, disconnecting\n"); -#endif GNUNET_DATASTORE_disconnect (datastore, GNUNET_YES); GNUNET_free (crc); ok = 0; @@ -265,11 +258,12 @@ run_tests (void *cls, int success, struct GNUNET_TIME_Absolute min_expiration, c static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) { struct CpsRunContext *crc; - static GNUNET_HashCode zkey; + static struct GNUNET_HashCode zkey; crc = GNUNET_malloc (sizeof (struct CpsRunContext)); crc->cfg = cfg; @@ -290,85 +284,21 @@ run (void *cls, char *const *args, const char *cfgfile, } - -static int -check () +int +main (int argc, char *argv[]) { - struct GNUNET_OS_Process *proc; char cfg_name[128]; - char *const argv[] = { - "test-datastore-api-management", - "-c", - cfg_name, -#if VERBOSE - "-L", "DEBUG", -#endif - NULL - }; - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; + plugin_name = GNUNET_TESTING_get_testname_from_underscore (argv[0]); GNUNET_snprintf (cfg_name, sizeof (cfg_name), "test_datastore_api_data_%s.conf", plugin_name); - proc = - GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-arm", - "gnunet-service-arm", -#if VERBOSE - "-L", "DEBUG", -#endif - "-c", cfg_name, NULL); - GNUNET_assert (NULL != proc); - GNUNET_PROGRAM_run ((sizeof (argv) / sizeof (char *)) - 1, argv, - "test-datastore-api-management", "nohelp", options, &run, - NULL); - sleep (1); /* give datastore chance to process 'DROP' request */ - if (0 != GNUNET_OS_process_kill (proc, SIGTERM)) - { - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); - ok = 1; - } - GNUNET_OS_process_wait (proc); - GNUNET_OS_process_destroy (proc); - proc = NULL; - if (ok != 0) - FPRINTF (stderr, "Missed some testcases: %u\n", ok); + if (0 != + GNUNET_TESTING_peer_run ("test-gnunet-datastore-management", + cfg_name, + &run, + NULL)) + return 1; return ok; } -int -main (int argc, char *argv[]) -{ - int ret; - - char *pos; - char dir_name[128]; - - sleep (1); - /* determine name of plugin to use */ - plugin_name = argv[0]; - while (NULL != (pos = strstr (plugin_name, "_"))) - plugin_name = pos + 1; - if (NULL != (pos = strstr (plugin_name, "."))) - pos[0] = 0; - else - pos = (char *) plugin_name; - - GNUNET_snprintf (dir_name, sizeof (dir_name), "/tmp/test-gnunet-datastore-%s", - plugin_name); - GNUNET_DISK_directory_remove (dir_name); - GNUNET_log_setup ("test-datastore-api-management", -#if VERBOSE - "DEBUG", -#else - "WARNING", -#endif - NULL); - ret = check (); - if (pos != plugin_name) - pos[0] = '.'; - GNUNET_DISK_directory_remove (dir_name); - return ret; -} - /* end of test_datastore_api_management.c */ diff --git a/src/datastore/test_defaults.conf b/src/datastore/test_defaults.conf index ce27c01..53bd66c 100644 --- a/src/datastore/test_defaults.conf +++ b/src/datastore/test_defaults.conf @@ -31,3 +31,9 @@ AUTOSTART = NO [namestore] AUTOSTART = NO + +[fs] +AUTOSTART = NO + +[consensus] +AUTOSTART = NO diff --git a/src/datastore/test_plugin_datastore.c b/src/datastore/test_plugin_datastore.c index 16fe40c..adfacef 100644 --- a/src/datastore/test_plugin_datastore.c +++ b/src/datastore/test_plugin_datastore.c @@ -27,8 +27,7 @@ #include "gnunet_util_lib.h" #include "gnunet_protocols.h" #include "gnunet_datastore_plugin.h" - -#define VERBOSE GNUNET_NO +#include "gnunet_testing_lib.h" /** * Number of put operations to perform. @@ -85,11 +84,11 @@ disk_utilization_change_cb (void *cls, int delta) static void -gen_key (int i, GNUNET_HashCode * key) +gen_key (int i, struct GNUNET_HashCode * key) { - memset (key, 0, sizeof (GNUNET_HashCode)); + memset (key, 0, sizeof (struct GNUNET_HashCode)); key->bits[0] = (unsigned int) i; - GNUNET_CRYPTO_hash (key, sizeof (GNUNET_HashCode), key); + GNUNET_CRYPTO_hash (key, sizeof (struct GNUNET_HashCode), key); } @@ -98,7 +97,7 @@ put_value (struct GNUNET_DATASTORE_PluginFunctions *api, int i, int k) { char value[65536]; size_t size; - GNUNET_HashCode key; + struct GNUNET_HashCode key; char *msg; unsigned int prio; @@ -117,10 +116,9 @@ put_value (struct GNUNET_DATASTORE_PluginFunctions *api, int i, int k) value[0] = k; msg = NULL; prio = GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK, 100); -#if VERBOSE - FPRINTF (stderr, "putting type %u, anon %u under key %s\n", i + 1, i, - GNUNET_h2s (&key)); -#endif + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "putting type %u, anon %u under key %s\n", i + 1, i, + GNUNET_h2s (&key)); if (GNUNET_OK != api->put (api->cls, &key, size, value, i + 1 /* type */ , prio, i /* anonymity */ , 0 /* replication */ , @@ -149,7 +147,7 @@ static uint64_t guid; static int -iterate_one_shot (void *cls, const GNUNET_HashCode * key, uint32_t size, +iterate_one_shot (void *cls, const struct GNUNET_HashCode * key, uint32_t size, const void *data, enum GNUNET_BLOCK_Type type, uint32_t priority, uint32_t anonymity, struct GNUNET_TIME_Absolute expiration, uint64_t uid) @@ -159,12 +157,10 @@ iterate_one_shot (void *cls, const GNUNET_HashCode * key, uint32_t size, GNUNET_assert (key != NULL); guid = uid; crc->phase++; -#if VERBOSE - FPRINTF (stderr, - "Found result type=%u, priority=%u, size=%u, expire=%llu, key %s\n", - type, priority, size, (unsigned long long) expiration.abs_value, - GNUNET_h2s (key)); -#endif + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Found result type=%u, priority=%u, size=%u, expire=%llu, key %s\n", + type, priority, size, (unsigned long long) expiration.abs_value, + GNUNET_h2s (key)); GNUNET_SCHEDULER_add_now (&test, crc); return GNUNET_OK; } @@ -222,16 +218,15 @@ test (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) int j; unsigned long long os; unsigned long long cs; - GNUNET_HashCode key; + struct GNUNET_HashCode key; if (0 != (tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN)) { GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Test aborted.\n"); crc->phase = RP_ERROR; } -#if VERBOSE - FPRINTF (stderr, "In phase %d, iteration %u\n", crc->phase, crc->cnt); -#endif + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "In phase %d, iteration %u\n", crc->phase, crc->cnt); switch (crc->phase) { case RP_ERROR: @@ -325,6 +320,8 @@ load_plugin (const struct GNUNET_CONFIGURATION_Handle *cfg) if (NULL == (ret = GNUNET_PLUGIN_load (libname, &env))) { FPRINTF (stderr, "Failed to load plugin `%s'!\n", name); + GNUNET_free (libname); + GNUNET_free (name); return NULL; } GNUNET_free (libname); @@ -355,67 +352,37 @@ run (void *cls, char *const *args, const char *cfgfile, } -static int -check () +int +main (int argc, char *argv[]) { + char dir_name[128]; char cfg_name[128]; - - char *const argv[] = { + char *const xargv[] = { "test-plugin-datastore", "-c", cfg_name, -#if VERBOSE - "-L", "DEBUG", -#endif NULL }; - struct GNUNET_GETOPT_CommandLineOption options[] = { + static struct GNUNET_GETOPT_CommandLineOption options[] = { GNUNET_GETOPT_OPTION_END }; - GNUNET_snprintf (cfg_name, sizeof (cfg_name), - "test_plugin_datastore_data_%s.conf", plugin_name); - GNUNET_PROGRAM_run ((sizeof (argv) / sizeof (char *)) - 1, argv, - "test-plugin-datastore", "nohelp", options, &run, NULL); - if (ok != 0) - FPRINTF (stderr, "Missed some testcases: %u\n", ok); - return ok; -} - - -int -main (int argc, char *argv[]) -{ - int ret; - char *pos; - char dir_name[128]; - - sleep (1); /* determine name of plugin to use */ - plugin_name = argv[0]; - while (NULL != (pos = strstr (plugin_name, "_"))) - plugin_name = pos + 1; - if (NULL != (pos = strstr (plugin_name, "."))) - pos[0] = 0; - else - pos = (char *) plugin_name; - + plugin_name = GNUNET_TESTING_get_testname_from_underscore (argv[0]); GNUNET_snprintf (dir_name, sizeof (dir_name), "/tmp/test-gnunet-datastore-plugin-%s", plugin_name); GNUNET_DISK_directory_remove (dir_name); GNUNET_log_setup ("test-plugin-datastore", -#if VERBOSE - "DEBUG", -#else "WARNING", -#endif NULL); - ret = check (); - if (pos != plugin_name) - pos[0] = '.'; + GNUNET_snprintf (cfg_name, sizeof (cfg_name), + "test_plugin_datastore_data_%s.conf", plugin_name); + GNUNET_PROGRAM_run ((sizeof (xargv) / sizeof (char *)) - 1, xargv, + "test-plugin-datastore", "nohelp", options, &run, NULL); + if (0 != ok) + FPRINTF (stderr, "Missed some testcases: %u\n", ok); GNUNET_DISK_directory_remove (dir_name); - - return ret; + return ok; } /* end of test_plugin_datastore.c */ diff --git a/src/datastore/test_plugin_datastore_data_heap.conf b/src/datastore/test_plugin_datastore_data_heap.conf new file mode 100644 index 0000000..6e352b9 --- /dev/null +++ b/src/datastore/test_plugin_datastore_data_heap.conf @@ -0,0 +1,6 @@ +@INLINE@ test_defaults.conf +[PATHS] +SERVICEHOME = /tmp/test-gnunet-datastore-plugin-heap/ + +[datastore] +DATABASE = heap diff --git a/src/datastore/test_plugin_datastore_data_mysql.conf b/src/datastore/test_plugin_datastore_data_mysql.conf index 957818a..845454b 100644 --- a/src/datastore/test_plugin_datastore_data_mysql.conf +++ b/src/datastore/test_plugin_datastore_data_mysql.conf @@ -1,7 +1,6 @@ @INLINE@ test_defaults.conf [PATHS] SERVICEHOME = /tmp/test-gnunet-datastore-plugin-mysql/ -DEFAULTCONFIG = test_plugin_datastore_data_mysql.conf [datastore] DATABASE = mysql diff --git a/src/datastore/test_plugin_datastore_data_postgres.conf b/src/datastore/test_plugin_datastore_data_postgres.conf index d796496..8b8523d 100644 --- a/src/datastore/test_plugin_datastore_data_postgres.conf +++ b/src/datastore/test_plugin_datastore_data_postgres.conf @@ -1,7 +1,6 @@ @INLINE@ test_defaults.conf [PATHS] SERVICEHOME = /tmp/test-gnunet-datastore-plugin-postgres/ -DEFAULTCONFIG = test_plugin_datastore_data_postgres.conf [datastore] DATABASE = postgres diff --git a/src/datastore/test_plugin_datastore_data_sqlite.conf b/src/datastore/test_plugin_datastore_data_sqlite.conf index f1fcf5f..dcdea7d 100644 --- a/src/datastore/test_plugin_datastore_data_sqlite.conf +++ b/src/datastore/test_plugin_datastore_data_sqlite.conf @@ -1,5 +1,4 @@ @INLINE@ test_defaults.conf [PATHS] SERVICEHOME = /tmp/test-gnunet-datastore-plugin-sqlite/ -DEFAULTCONFIG = test_plugin_datastore_data_sqlite.conf diff --git a/src/dht/Makefile.am b/src/dht/Makefile.am index b2d18d2..6bbc191 100644 --- a/src/dht/Makefile.am +++ b/src/dht/Makefile.am @@ -7,6 +7,8 @@ plugindir = $(libdir)/gnunet pkgcfgdir= $(pkgdatadir)/config.d/ +libexecdir= $(pkglibdir)/libexec/ + pkgcfg_DATA = \ dht.conf @@ -26,10 +28,11 @@ libgnunetdht_la_SOURCES = \ dht_api.c dht.h libgnunetdht_la_LIBADD = \ $(top_builddir)/src/util/libgnunetutil.la \ - $(XLIB) + $(XLIB) \ + $(LTLIBINTL) libgnunetdht_la_LDFLAGS = \ $(GN_LIB_LDFLAGS) $(WINFLAGS) \ - -version-info 1:0:1 + -version-info 2:0:2 plugin_LTLIBRARIES = \ @@ -40,7 +43,8 @@ libgnunet_plugin_block_dht_la_SOURCES = \ libgnunet_plugin_block_dht_la_LIBADD = \ $(top_builddir)/src/hello/libgnunethello.la \ $(top_builddir)/src/block/libgnunetblock.la \ - $(top_builddir)/src/util/libgnunetutil.la + $(top_builddir)/src/util/libgnunetutil.la \ + $(LTLIBINTL) libgnunet_plugin_block_dht_la_LDFLAGS = \ $(GN_PLUGIN_LDFLAGS) libgnunet_plugin_block_dht_la_DEPENDENCIES = \ @@ -48,8 +52,10 @@ libgnunet_plugin_block_dht_la_DEPENDENCIES = \ -bin_PROGRAMS = \ - gnunet-service-dht \ +libexec_PROGRAMS = \ + gnunet-service-dht + +noinst_PROGRAMS = \ gnunet-dht-monitor \ gnunet-dht-get \ gnunet-dht-put @@ -103,83 +109,66 @@ gnunet_dht_monitor_DEPENDENCIES = \ libgnunetdht.la +noinst_LIBRARIES = libgnunetdhttest.a + +libgnunetdhttest_a_SOURCES = \ + dht_test_lib.c dht_test_lib.h +libgnunetdhttest_a_LIBADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la \ + $(top_builddir)/src/dht/libgnunetdht.la +libgnunetdhttest_a_DEPENDENCIES = \ + libgnunetdht.la + check_PROGRAMS = \ test_dht_api \ test_dht_twopeer \ - test_dht_twopeer_put_get \ - test_dht_twopeer_get_put \ - test_dht_twopeer_path_tracking \ test_dht_multipeer \ test_dht_line \ test_dht_2dtorus \ test_dht_monitor +if HAVE_EXPERIMENTAL +# These tests still do not work as testbed does +# not support the respective topology op + NEW_TESTS = test_dht_2dtorus test_dht_multipeer +endif + if ENABLE_TEST_RUN TESTS = test_dht_api $(check_SCRIPTS) \ test_dht_twopeer \ - test_dht_twopeer_put_get \ - test_dht_twopeer_get_put \ - test_dht_twopeer_path_tracking \ - test_dht_multipeer \ test_dht_line \ - test_dht_2dtorus \ - test_dht_monitor + test_dht_monitor \ + $(NEW_TESTS) endif test_dht_api_SOURCES = \ test_dht_api.c test_dht_api_LDADD = \ $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/hello/libgnunethello.la \ $(top_builddir)/src/dht/libgnunetdht.la test_dht_api_DEPENDENCIES = \ libgnunetdht.la test_dht_twopeer_SOURCES = \ - test_dht_twopeer.c + test_dht_topo.c test_dht_twopeer_LDADD = \ + $(top_builddir)/src/dht/libgnunetdhttest.a \ $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/dht/libgnunetdhttest.a \ + $(top_builddir)/src/testbed/libgnunettestbed.la \ $(top_builddir)/src/dht/libgnunetdht.la test_dht_twopeer_DEPENDENCIES = \ libgnunetdht.la -test_dht_twopeer_put_get_SOURCES = \ - test_dht_twopeer_put_get.c -test_dht_twopeer_put_get_LDADD = \ - $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/dht/libgnunetdht.la - -test_dht_twopeer_get_put_SOURCES = \ - test_dht_twopeer_get_put.c -test_dht_twopeer_get_put_LDADD = \ - $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/dht/libgnunetdht.la - -test_dht_twopeer_path_tracking_SOURCES = \ - test_dht_twopeer_path_tracking.c -test_dht_twopeer_path_tracking_LDADD = \ - $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/dht/libgnunetdht.la - -test_dht_multipeer_SOURCES = \ - test_dht_multipeer.c -test_dht_multipeer_LDADD = \ - $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/statistics/libgnunetstatistics.la \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/dht/libgnunetdht.la -test_dht_multipeer_DEPENDENCIES = \ - libgnunetdht.la - test_dht_2dtorus_SOURCES = \ test_dht_topo.c test_dht_2dtorus_LDADD = \ + $(top_builddir)/src/dht/libgnunetdhttest.a \ $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la \ $(top_builddir)/src/dht/libgnunetdht.la test_dht_2dtorus_DEPENDENCIES = \ libgnunetdht.la @@ -187,16 +176,30 @@ test_dht_2dtorus_DEPENDENCIES = \ test_dht_line_SOURCES = \ test_dht_topo.c test_dht_line_LDADD = \ + $(top_builddir)/src/dht/libgnunetdhttest.a \ $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/dht/libgnunetdht.la + $(top_builddir)/src/testbed/libgnunettestbed.la \ + $(top_builddir)/src/dht/libgnunetdht.la test_dht_line_DEPENDENCIES = \ libgnunetdht.la -test_dht_monitor_SOURCES = test_dht_monitor.c +test_dht_multipeer_SOURCES = \ + test_dht_topo.c +test_dht_multipeer_LDADD = \ + $(top_builddir)/src/dht/libgnunetdhttest.a \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/statistics/libgnunetstatistics.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la \ + $(top_builddir)/src/dht/libgnunetdht.la +test_dht_multipeer_DEPENDENCIES = \ + libgnunetdht.la + +test_dht_monitor_SOURCES = \ + test_dht_monitor.c test_dht_monitor_LDADD = \ + $(top_builddir)/src/dht/libgnunetdhttest.a \ $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la \ $(top_builddir)/src/dht/libgnunetdht.la test_dht_monitor_DEPENDENCIES = \ libgnunetdht.la @@ -205,11 +208,22 @@ EXTRA_DIST = \ $(check_SCRIPTS) \ test_dht_api_data.conf \ test_dht_api_peer1.conf \ - test_dht_twopeer_data.conf \ - test_dht_multipeer_data.conf \ + test_dht_monitor.conf \ + test_dht_multipeer.conf \ test_dht_2dtorus.conf \ test_dht_line.conf \ - multipeer_topo.dat + test_dht_tools.py.in \ + test_dht_multipeer_topology.dat check_SCRIPTS = \ - test_dht_tools.sh + test_dht_tools.py + +do_subst = $(SED) -e 's,[@]PYTHON[@],$(PYTHON),g' + +%.py: %.py.in Makefile + $(do_subst) < $(srcdir)/$< > $@ + chmod +x $@ + +test_dht_tools.py: test_dht_tools.py.in Makefile + $(do_subst) < $(srcdir)/test_dht_tools.py.in > test_dht_tools.py + chmod +x test_dht_tools.py diff --git a/src/dht/Makefile.in b/src/dht/Makefile.in index 12ce558..fbac460 100644 --- a/src/dht/Makefile.in +++ b/src/dht/Makefile.in @@ -1,9 +1,9 @@ -# Makefile.in generated by automake 1.11.1 from Makefile.am. +# Makefile.in generated by automake 1.11.6 from Makefile.am. # @configure_input@ # Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, -# 2003, 2004, 2005, 2006, 2007, 2008, 2009 Free Software Foundation, -# Inc. +# 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Free Software +# Foundation, Inc. # This Makefile.in is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. @@ -17,7 +17,25 @@ + VPATH = @srcdir@ +am__make_dryrun = \ + { \ + am__dry=no; \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + echo 'am--echo: ; @echo "AM" OK' | $(MAKE) -f - 2>/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } pkgdatadir = $(datadir)/@PACKAGE@ pkgincludedir = $(includedir)/@PACKAGE@ pkglibdir = $(libdir)/@PACKAGE@ @@ -37,37 +55,32 @@ POST_UNINSTALL = : build_triplet = @build@ host_triplet = @host@ target_triplet = @target@ -bin_PROGRAMS = gnunet-service-dht$(EXEEXT) gnunet-dht-monitor$(EXEEXT) \ - gnunet-dht-get$(EXEEXT) gnunet-dht-put$(EXEEXT) +libexec_PROGRAMS = gnunet-service-dht$(EXEEXT) +noinst_PROGRAMS = gnunet-dht-monitor$(EXEEXT) gnunet-dht-get$(EXEEXT) \ + gnunet-dht-put$(EXEEXT) check_PROGRAMS = test_dht_api$(EXEEXT) test_dht_twopeer$(EXEEXT) \ - test_dht_twopeer_put_get$(EXEEXT) \ - test_dht_twopeer_get_put$(EXEEXT) \ - test_dht_twopeer_path_tracking$(EXEEXT) \ test_dht_multipeer$(EXEEXT) test_dht_line$(EXEEXT) \ test_dht_2dtorus$(EXEEXT) test_dht_monitor$(EXEEXT) @ENABLE_TEST_RUN_TRUE@TESTS = test_dht_api$(EXEEXT) $(check_SCRIPTS) \ @ENABLE_TEST_RUN_TRUE@ test_dht_twopeer$(EXEEXT) \ -@ENABLE_TEST_RUN_TRUE@ test_dht_twopeer_put_get$(EXEEXT) \ -@ENABLE_TEST_RUN_TRUE@ test_dht_twopeer_get_put$(EXEEXT) \ -@ENABLE_TEST_RUN_TRUE@ test_dht_twopeer_path_tracking$(EXEEXT) \ -@ENABLE_TEST_RUN_TRUE@ test_dht_multipeer$(EXEEXT) \ @ENABLE_TEST_RUN_TRUE@ test_dht_line$(EXEEXT) \ -@ENABLE_TEST_RUN_TRUE@ test_dht_2dtorus$(EXEEXT) \ -@ENABLE_TEST_RUN_TRUE@ test_dht_monitor$(EXEEXT) +@ENABLE_TEST_RUN_TRUE@ test_dht_monitor$(EXEEXT) \ +@ENABLE_TEST_RUN_TRUE@ $(am__EXEEXT_1) subdir = src/dht DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in \ $(srcdir)/dht.conf.in ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 am__aclocal_m4_deps = $(top_srcdir)/m4/absolute-header.m4 \ $(top_srcdir)/m4/align.m4 $(top_srcdir)/m4/argz.m4 \ - $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/iconv.m4 \ - $(top_srcdir)/m4/lib-ld.m4 $(top_srcdir)/m4/lib-link.m4 \ - $(top_srcdir)/m4/lib-prefix.m4 $(top_srcdir)/m4/libcurl.m4 \ - $(top_srcdir)/m4/libgcrypt.m4 $(top_srcdir)/m4/libtool.m4 \ - $(top_srcdir)/m4/libunistring.m4 $(top_srcdir)/m4/ltdl.m4 \ - $(top_srcdir)/m4/ltoptions.m4 $(top_srcdir)/m4/ltsugar.m4 \ - $(top_srcdir)/m4/ltversion.m4 $(top_srcdir)/m4/lt~obsolete.m4 \ - $(top_srcdir)/m4/nls.m4 $(top_srcdir)/m4/po.m4 \ + $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/glib-2.0.m4 \ + $(top_srcdir)/m4/iconv.m4 $(top_srcdir)/m4/lib-ld.m4 \ + $(top_srcdir)/m4/lib-link.m4 $(top_srcdir)/m4/lib-prefix.m4 \ + $(top_srcdir)/m4/libcurl.m4 $(top_srcdir)/m4/libgcrypt.m4 \ + $(top_srcdir)/m4/libtool.m4 $(top_srcdir)/m4/libunistring.m4 \ + $(top_srcdir)/m4/ltdl.m4 $(top_srcdir)/m4/ltoptions.m4 \ + $(top_srcdir)/m4/ltsugar.m4 $(top_srcdir)/m4/ltversion.m4 \ + $(top_srcdir)/m4/lt~obsolete.m4 $(top_srcdir)/m4/nls.m4 \ + $(top_srcdir)/m4/pkg.m4 $(top_srcdir)/m4/po.m4 \ $(top_srcdir)/m4/progtest.m4 $(top_srcdir)/acinclude.m4 \ $(top_srcdir)/configure.ac am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ @@ -76,6 +89,17 @@ mkinstalldirs = $(install_sh) -d CONFIG_HEADER = $(top_builddir)/gnunet_config.h CONFIG_CLEAN_FILES = dht.conf CONFIG_CLEAN_VPATH_FILES = +LIBRARIES = $(noinst_LIBRARIES) +ARFLAGS = cru +AM_V_AR = $(am__v_AR_@AM_V@) +am__v_AR_ = $(am__v_AR_@AM_DEFAULT_V@) +am__v_AR_0 = @echo " AR " $@; +AM_V_at = $(am__v_at_@AM_V@) +am__v_at_ = $(am__v_at_@AM_DEFAULT_V@) +am__v_at_0 = @ +libgnunetdhttest_a_AR = $(AR) $(ARFLAGS) +am_libgnunetdhttest_a_OBJECTS = dht_test_lib.$(OBJEXT) +libgnunetdhttest_a_OBJECTS = $(am_libgnunetdhttest_a_OBJECTS) am__vpath_adj_setup = srcdirstrip=`echo "$(srcdir)" | sed 's|.|.|g'`; am__vpath_adj = case $$p in \ $(srcdir)/*) f=`echo "$$p" | sed "s|^$$srcdirstrip/||"`;; \ @@ -97,30 +121,36 @@ am__nobase_list = $(am__nobase_strip_setup); \ am__base_list = \ sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \ sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g' +am__uninstall_files_from_dir = { \ + test -z "$$files" \ + || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \ + || { echo " ( cd '$$dir' && rm -f" $$files ")"; \ + $(am__cd) "$$dir" && rm -f $$files; }; \ + } am__installdirs = "$(DESTDIR)$(libdir)" "$(DESTDIR)$(plugindir)" \ - "$(DESTDIR)$(bindir)" "$(DESTDIR)$(pkgcfgdir)" + "$(DESTDIR)$(libexecdir)" "$(DESTDIR)$(pkgcfgdir)" LTLIBRARIES = $(lib_LTLIBRARIES) $(plugin_LTLIBRARIES) +am__DEPENDENCIES_1 = am_libgnunet_plugin_block_dht_la_OBJECTS = plugin_block_dht.lo libgnunet_plugin_block_dht_la_OBJECTS = \ $(am_libgnunet_plugin_block_dht_la_OBJECTS) -AM_V_lt = $(am__v_lt_$(V)) -am__v_lt_ = $(am__v_lt_$(AM_DEFAULT_VERBOSITY)) +AM_V_lt = $(am__v_lt_@AM_V@) +am__v_lt_ = $(am__v_lt_@AM_DEFAULT_V@) am__v_lt_0 = --silent libgnunet_plugin_block_dht_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ $(AM_CFLAGS) $(CFLAGS) \ $(libgnunet_plugin_block_dht_la_LDFLAGS) $(LDFLAGS) -o $@ -am__DEPENDENCIES_1 = libgnunetdht_la_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la \ - $(am__DEPENDENCIES_1) + $(am__DEPENDENCIES_1) $(am__DEPENDENCIES_1) am_libgnunetdht_la_OBJECTS = dht_api.lo libgnunetdht_la_OBJECTS = $(am_libgnunetdht_la_OBJECTS) libgnunetdht_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ $(AM_CFLAGS) $(CFLAGS) $(libgnunetdht_la_LDFLAGS) $(LDFLAGS) \ -o $@ -PROGRAMS = $(bin_PROGRAMS) +PROGRAMS = $(libexec_PROGRAMS) $(noinst_PROGRAMS) am_gnunet_dht_get_OBJECTS = gnunet-dht-get.$(OBJEXT) gnunet_dht_get_OBJECTS = $(am_gnunet_dht_get_OBJECTS) am_gnunet_dht_monitor_OBJECTS = gnunet-dht-monitor.$(OBJEXT) @@ -154,34 +184,10 @@ am_test_dht_line_OBJECTS = test_dht_topo.$(OBJEXT) test_dht_line_OBJECTS = $(am_test_dht_line_OBJECTS) am_test_dht_monitor_OBJECTS = test_dht_monitor.$(OBJEXT) test_dht_monitor_OBJECTS = $(am_test_dht_monitor_OBJECTS) -am_test_dht_multipeer_OBJECTS = test_dht_multipeer.$(OBJEXT) +am_test_dht_multipeer_OBJECTS = test_dht_topo.$(OBJEXT) test_dht_multipeer_OBJECTS = $(am_test_dht_multipeer_OBJECTS) -am_test_dht_twopeer_OBJECTS = test_dht_twopeer.$(OBJEXT) +am_test_dht_twopeer_OBJECTS = test_dht_topo.$(OBJEXT) test_dht_twopeer_OBJECTS = $(am_test_dht_twopeer_OBJECTS) -am_test_dht_twopeer_get_put_OBJECTS = \ - test_dht_twopeer_get_put.$(OBJEXT) -test_dht_twopeer_get_put_OBJECTS = \ - $(am_test_dht_twopeer_get_put_OBJECTS) -test_dht_twopeer_get_put_DEPENDENCIES = \ - $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/dht/libgnunetdht.la -am_test_dht_twopeer_path_tracking_OBJECTS = \ - test_dht_twopeer_path_tracking.$(OBJEXT) -test_dht_twopeer_path_tracking_OBJECTS = \ - $(am_test_dht_twopeer_path_tracking_OBJECTS) -test_dht_twopeer_path_tracking_DEPENDENCIES = \ - $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/dht/libgnunetdht.la -am_test_dht_twopeer_put_get_OBJECTS = \ - test_dht_twopeer_put_get.$(OBJEXT) -test_dht_twopeer_put_get_OBJECTS = \ - $(am_test_dht_twopeer_put_get_OBJECTS) -test_dht_twopeer_put_get_DEPENDENCIES = \ - $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/dht/libgnunetdht.la DEFAULT_INCLUDES = -I.@am__isrc@ -I$(top_builddir) depcomp = $(SHELL) $(top_srcdir)/depcomp am__depfiles_maybe = depfiles @@ -192,47 +198,47 @@ LTCOMPILE = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) \ $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) \ $(AM_CFLAGS) $(CFLAGS) -AM_V_CC = $(am__v_CC_$(V)) -am__v_CC_ = $(am__v_CC_$(AM_DEFAULT_VERBOSITY)) +AM_V_CC = $(am__v_CC_@AM_V@) +am__v_CC_ = $(am__v_CC_@AM_DEFAULT_V@) am__v_CC_0 = @echo " CC " $@; -AM_V_at = $(am__v_at_$(V)) -am__v_at_ = $(am__v_at_$(AM_DEFAULT_VERBOSITY)) -am__v_at_0 = @ CCLD = $(CC) LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ $(AM_LDFLAGS) $(LDFLAGS) -o $@ -AM_V_CCLD = $(am__v_CCLD_$(V)) -am__v_CCLD_ = $(am__v_CCLD_$(AM_DEFAULT_VERBOSITY)) +AM_V_CCLD = $(am__v_CCLD_@AM_V@) +am__v_CCLD_ = $(am__v_CCLD_@AM_DEFAULT_V@) am__v_CCLD_0 = @echo " CCLD " $@; -AM_V_GEN = $(am__v_GEN_$(V)) -am__v_GEN_ = $(am__v_GEN_$(AM_DEFAULT_VERBOSITY)) +AM_V_GEN = $(am__v_GEN_@AM_V@) +am__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@) am__v_GEN_0 = @echo " GEN " $@; -SOURCES = $(libgnunet_plugin_block_dht_la_SOURCES) \ +SOURCES = $(libgnunetdhttest_a_SOURCES) \ + $(libgnunet_plugin_block_dht_la_SOURCES) \ $(libgnunetdht_la_SOURCES) $(gnunet_dht_get_SOURCES) \ $(gnunet_dht_monitor_SOURCES) $(gnunet_dht_put_SOURCES) \ $(gnunet_service_dht_SOURCES) $(test_dht_2dtorus_SOURCES) \ $(test_dht_api_SOURCES) $(test_dht_line_SOURCES) \ $(test_dht_monitor_SOURCES) $(test_dht_multipeer_SOURCES) \ - $(test_dht_twopeer_SOURCES) \ - $(test_dht_twopeer_get_put_SOURCES) \ - $(test_dht_twopeer_path_tracking_SOURCES) \ - $(test_dht_twopeer_put_get_SOURCES) -DIST_SOURCES = $(libgnunet_plugin_block_dht_la_SOURCES) \ + $(test_dht_twopeer_SOURCES) +DIST_SOURCES = $(libgnunetdhttest_a_SOURCES) \ + $(libgnunet_plugin_block_dht_la_SOURCES) \ $(libgnunetdht_la_SOURCES) $(gnunet_dht_get_SOURCES) \ $(gnunet_dht_monitor_SOURCES) $(gnunet_dht_put_SOURCES) \ $(gnunet_service_dht_SOURCES) $(test_dht_2dtorus_SOURCES) \ $(test_dht_api_SOURCES) $(test_dht_line_SOURCES) \ $(test_dht_monitor_SOURCES) $(test_dht_multipeer_SOURCES) \ - $(test_dht_twopeer_SOURCES) \ - $(test_dht_twopeer_get_put_SOURCES) \ - $(test_dht_twopeer_path_tracking_SOURCES) \ - $(test_dht_twopeer_put_get_SOURCES) + $(test_dht_twopeer_SOURCES) +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac DATA = $(pkgcfg_DATA) ETAGS = etags CTAGS = ctags am__tty_colors = \ red=; grn=; lgn=; blu=; std= +@HAVE_EXPERIMENTAL_TRUE@am__EXEEXT_1 = test_dht_2dtorus$(EXEEXT) \ +@HAVE_EXPERIMENTAL_TRUE@ test_dht_multipeer$(EXEEXT) DISTFILES = $(DIST_COMMON) $(DIST_SOURCES) $(TEXINFOS) $(EXTRA_DIST) ACLOCAL = @ACLOCAL@ AMTAR = @AMTAR@ @@ -269,6 +275,10 @@ EXEEXT = @EXEEXT@ EXT_LIBS = @EXT_LIBS@ EXT_LIB_PATH = @EXT_LIB_PATH@ FGREP = @FGREP@ +GLIB_CFLAGS = @GLIB_CFLAGS@ +GLIB_GENMARSHAL = @GLIB_GENMARSHAL@ +GLIB_LIBS = @GLIB_LIBS@ +GLIB_MKENUMS = @GLIB_MKENUMS@ GMSGFMT = @GMSGFMT@ GMSGFMT_015 = @GMSGFMT_015@ GNUNETDNS_GROUP = @GNUNETDNS_GROUP@ @@ -279,6 +289,7 @@ GN_LIBINTL = @GN_LIBINTL@ GN_LIB_LDFLAGS = @GN_LIB_LDFLAGS@ GN_PLUGIN_LDFLAGS = @GN_PLUGIN_LDFLAGS@ GN_USER_HOME_DIR = @GN_USER_HOME_DIR@ +GOBJECT_QUERY = @GOBJECT_QUERY@ GREP = @GREP@ HAVE_LIBUNISTRING = @HAVE_LIBUNISTRING@ INCLTDL = @INCLTDL@ @@ -301,6 +312,8 @@ LIBCURL_CPPFLAGS = @LIBCURL_CPPFLAGS@ LIBGCRYPT_CFLAGS = @LIBGCRYPT_CFLAGS@ LIBGCRYPT_CONFIG = @LIBGCRYPT_CONFIG@ LIBGCRYPT_LIBS = @LIBGCRYPT_LIBS@ +LIBGTOP_CFLAGS = @LIBGTOP_CFLAGS@ +LIBGTOP_LIBS = @LIBGTOP_LIBS@ LIBICONV = @LIBICONV@ LIBINTL = @LIBINTL@ LIBLTDL = @LIBLTDL@ @@ -322,6 +335,7 @@ LT_CONFIG_H = @LT_CONFIG_H@ LT_DLLOADERS = @LT_DLLOADERS@ LT_DLPREOPEN = @LT_DLPREOPEN@ MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ MKDIR_P = @MKDIR_P@ MONKEYPREFIX = @MONKEYPREFIX@ MSGFMT = @MSGFMT@ @@ -331,6 +345,7 @@ MYSQL_CPPFLAGS = @MYSQL_CPPFLAGS@ MYSQL_LDFLAGS = @MYSQL_LDFLAGS@ NM = @NM@ NMEDIT = @NMEDIT@ +NSS_DIR = @NSS_DIR@ OBJC = @OBJC@ OBJCDEPMODE = @OBJCDEPMODE@ OBJCFLAGS = @OBJCFLAGS@ @@ -346,6 +361,7 @@ PACKAGE_TARNAME = @PACKAGE_TARNAME@ PACKAGE_URL = @PACKAGE_URL@ PACKAGE_VERSION = @PACKAGE_VERSION@ PATH_SEPARATOR = @PATH_SEPARATOR@ +PKG_CONFIG = @PKG_CONFIG@ POSTGRES_CPPFLAGS = @POSTGRES_CPPFLAGS@ POSTGRES_LDFLAGS = @POSTGRES_LDFLAGS@ POSUB = @POSUB@ @@ -377,6 +393,7 @@ abs_builddir = @abs_builddir@ abs_srcdir = @abs_srcdir@ abs_top_builddir = @abs_top_builddir@ abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ ac_ct_CC = @ac_ct_CC@ ac_ct_CXX = @ac_ct_CXX@ ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ @@ -399,6 +416,7 @@ datarootdir = @datarootdir@ docdir = @docdir@ dvidir = @dvidir@ exec_prefix = @exec_prefix@ +gitcommand = @gitcommand@ host = @host@ host_alias = @host_alias@ host_cpu = @host_cpu@ @@ -409,10 +427,9 @@ includedir = @includedir@ infodir = @infodir@ install_sh = @install_sh@ libdir = @libdir@ -libexecdir = @libexecdir@ +libexecdir = $(pkglibdir)/libexec/ localedir = @localedir@ localstatedir = @localstatedir@ -lt_ECHO = @lt_ECHO@ ltdl_LIBOBJS = @ltdl_LIBOBJS@ ltdl_LTLIBOBJS = @ltdl_LTLIBOBJS@ mandir = @mandir@ @@ -430,6 +447,7 @@ sbindir = @sbindir@ sharedstatedir = @sharedstatedir@ srcdir = @srcdir@ subdirs = @subdirs@ +svnversioncommand = @svnversioncommand@ sys_symbol_underscore = @sys_symbol_underscore@ sysconfdir = @sysconfdir@ target = @target@ @@ -458,11 +476,12 @@ libgnunetdht_la_SOURCES = \ libgnunetdht_la_LIBADD = \ $(top_builddir)/src/util/libgnunetutil.la \ - $(XLIB) + $(XLIB) \ + $(LTLIBINTL) libgnunetdht_la_LDFLAGS = \ $(GN_LIB_LDFLAGS) $(WINFLAGS) \ - -version-info 1:0:1 + -version-info 2:0:2 plugin_LTLIBRARIES = \ libgnunet_plugin_block_dht.la @@ -473,7 +492,8 @@ libgnunet_plugin_block_dht_la_SOURCES = \ libgnunet_plugin_block_dht_la_LIBADD = \ $(top_builddir)/src/hello/libgnunethello.la \ $(top_builddir)/src/block/libgnunetblock.la \ - $(top_builddir)/src/util/libgnunetutil.la + $(top_builddir)/src/util/libgnunetutil.la \ + $(LTLIBINTL) libgnunet_plugin_block_dht_la_LDFLAGS = \ $(GN_PLUGIN_LDFLAGS) @@ -536,11 +556,28 @@ gnunet_dht_monitor_LDADD = \ gnunet_dht_monitor_DEPENDENCIES = \ libgnunetdht.la +noinst_LIBRARIES = libgnunetdhttest.a +libgnunetdhttest_a_SOURCES = \ + dht_test_lib.c dht_test_lib.h + +libgnunetdhttest_a_LIBADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la \ + $(top_builddir)/src/dht/libgnunetdht.la + +libgnunetdhttest_a_DEPENDENCIES = \ + libgnunetdht.la + + +# These tests still do not work as testbed does +# not support the respective topology op +@HAVE_EXPERIMENTAL_TRUE@NEW_TESTS = test_dht_2dtorus test_dht_multipeer test_dht_api_SOURCES = \ test_dht_api.c test_dht_api_LDADD = \ $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/hello/libgnunethello.la \ $(top_builddir)/src/dht/libgnunetdht.la @@ -548,58 +585,25 @@ test_dht_api_DEPENDENCIES = \ libgnunetdht.la test_dht_twopeer_SOURCES = \ - test_dht_twopeer.c + test_dht_topo.c test_dht_twopeer_LDADD = \ + $(top_builddir)/src/dht/libgnunetdhttest.a \ $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/dht/libgnunetdhttest.a \ + $(top_builddir)/src/testbed/libgnunettestbed.la \ $(top_builddir)/src/dht/libgnunetdht.la test_dht_twopeer_DEPENDENCIES = \ libgnunetdht.la -test_dht_twopeer_put_get_SOURCES = \ - test_dht_twopeer_put_get.c - -test_dht_twopeer_put_get_LDADD = \ - $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/dht/libgnunetdht.la - -test_dht_twopeer_get_put_SOURCES = \ - test_dht_twopeer_get_put.c - -test_dht_twopeer_get_put_LDADD = \ - $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/dht/libgnunetdht.la - -test_dht_twopeer_path_tracking_SOURCES = \ - test_dht_twopeer_path_tracking.c - -test_dht_twopeer_path_tracking_LDADD = \ - $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/dht/libgnunetdht.la - -test_dht_multipeer_SOURCES = \ - test_dht_multipeer.c - -test_dht_multipeer_LDADD = \ - $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/statistics/libgnunetstatistics.la \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/dht/libgnunetdht.la - -test_dht_multipeer_DEPENDENCIES = \ - libgnunetdht.la - test_dht_2dtorus_SOURCES = \ test_dht_topo.c test_dht_2dtorus_LDADD = \ + $(top_builddir)/src/dht/libgnunetdhttest.a \ $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la \ $(top_builddir)/src/dht/libgnunetdht.la test_dht_2dtorus_DEPENDENCIES = \ @@ -609,17 +613,34 @@ test_dht_line_SOURCES = \ test_dht_topo.c test_dht_line_LDADD = \ + $(top_builddir)/src/dht/libgnunetdhttest.a \ $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/dht/libgnunetdht.la + $(top_builddir)/src/testbed/libgnunettestbed.la \ + $(top_builddir)/src/dht/libgnunetdht.la test_dht_line_DEPENDENCIES = \ libgnunetdht.la -test_dht_monitor_SOURCES = test_dht_monitor.c +test_dht_multipeer_SOURCES = \ + test_dht_topo.c + +test_dht_multipeer_LDADD = \ + $(top_builddir)/src/dht/libgnunetdhttest.a \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/statistics/libgnunetstatistics.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la \ + $(top_builddir)/src/dht/libgnunetdht.la + +test_dht_multipeer_DEPENDENCIES = \ + libgnunetdht.la + +test_dht_monitor_SOURCES = \ + test_dht_monitor.c + test_dht_monitor_LDADD = \ + $(top_builddir)/src/dht/libgnunetdhttest.a \ $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la \ $(top_builddir)/src/dht/libgnunetdht.la test_dht_monitor_DEPENDENCIES = \ @@ -629,15 +650,17 @@ EXTRA_DIST = \ $(check_SCRIPTS) \ test_dht_api_data.conf \ test_dht_api_peer1.conf \ - test_dht_twopeer_data.conf \ - test_dht_multipeer_data.conf \ + test_dht_monitor.conf \ + test_dht_multipeer.conf \ test_dht_2dtorus.conf \ test_dht_line.conf \ - multipeer_topo.dat + test_dht_tools.py.in \ + test_dht_multipeer_topology.dat check_SCRIPTS = \ - test_dht_tools.sh + test_dht_tools.py +do_subst = $(SED) -e 's,[@]PYTHON[@],$(PYTHON),g' all: all-am .SUFFIXES: @@ -674,9 +697,15 @@ $(ACLOCAL_M4): $(am__aclocal_m4_deps) $(am__aclocal_m4_deps): dht.conf: $(top_builddir)/config.status $(srcdir)/dht.conf.in cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ + +clean-noinstLIBRARIES: + -test -z "$(noinst_LIBRARIES)" || rm -f $(noinst_LIBRARIES) +libgnunetdhttest.a: $(libgnunetdhttest_a_OBJECTS) $(libgnunetdhttest_a_DEPENDENCIES) $(EXTRA_libgnunetdhttest_a_DEPENDENCIES) + $(AM_V_at)-rm -f libgnunetdhttest.a + $(AM_V_AR)$(libgnunetdhttest_a_AR) libgnunetdhttest.a $(libgnunetdhttest_a_OBJECTS) $(libgnunetdhttest_a_LIBADD) + $(AM_V_at)$(RANLIB) libgnunetdhttest.a install-libLTLIBRARIES: $(lib_LTLIBRARIES) @$(NORMAL_INSTALL) - test -z "$(libdir)" || $(MKDIR_P) "$(DESTDIR)$(libdir)" @list='$(lib_LTLIBRARIES)'; test -n "$(libdir)" || list=; \ list2=; for p in $$list; do \ if test -f $$p; then \ @@ -684,6 +713,8 @@ install-libLTLIBRARIES: $(lib_LTLIBRARIES) else :; fi; \ done; \ test -z "$$list2" || { \ + echo " $(MKDIR_P) '$(DESTDIR)$(libdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libdir)" || exit 1; \ echo " $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 '$(DESTDIR)$(libdir)'"; \ $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 "$(DESTDIR)$(libdir)"; \ } @@ -707,7 +738,6 @@ clean-libLTLIBRARIES: done install-pluginLTLIBRARIES: $(plugin_LTLIBRARIES) @$(NORMAL_INSTALL) - test -z "$(plugindir)" || $(MKDIR_P) "$(DESTDIR)$(plugindir)" @list='$(plugin_LTLIBRARIES)'; test -n "$(plugindir)" || list=; \ list2=; for p in $$list; do \ if test -f $$p; then \ @@ -715,6 +745,8 @@ install-pluginLTLIBRARIES: $(plugin_LTLIBRARIES) else :; fi; \ done; \ test -z "$$list2" || { \ + echo " $(MKDIR_P) '$(DESTDIR)$(plugindir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(plugindir)" || exit 1; \ echo " $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 '$(DESTDIR)$(plugindir)'"; \ $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 "$(DESTDIR)$(plugindir)"; \ } @@ -736,14 +768,26 @@ clean-pluginLTLIBRARIES: echo "rm -f \"$${dir}/so_locations\""; \ rm -f "$${dir}/so_locations"; \ done -libgnunet_plugin_block_dht.la: $(libgnunet_plugin_block_dht_la_OBJECTS) $(libgnunet_plugin_block_dht_la_DEPENDENCIES) +libgnunet_plugin_block_dht.la: $(libgnunet_plugin_block_dht_la_OBJECTS) $(libgnunet_plugin_block_dht_la_DEPENDENCIES) $(EXTRA_libgnunet_plugin_block_dht_la_DEPENDENCIES) $(AM_V_CCLD)$(libgnunet_plugin_block_dht_la_LINK) -rpath $(plugindir) $(libgnunet_plugin_block_dht_la_OBJECTS) $(libgnunet_plugin_block_dht_la_LIBADD) $(LIBS) -libgnunetdht.la: $(libgnunetdht_la_OBJECTS) $(libgnunetdht_la_DEPENDENCIES) +libgnunetdht.la: $(libgnunetdht_la_OBJECTS) $(libgnunetdht_la_DEPENDENCIES) $(EXTRA_libgnunetdht_la_DEPENDENCIES) $(AM_V_CCLD)$(libgnunetdht_la_LINK) -rpath $(libdir) $(libgnunetdht_la_OBJECTS) $(libgnunetdht_la_LIBADD) $(LIBS) -install-binPROGRAMS: $(bin_PROGRAMS) + +clean-checkPROGRAMS: + @list='$(check_PROGRAMS)'; test -n "$$list" || exit 0; \ + echo " rm -f" $$list; \ + rm -f $$list || exit $$?; \ + test -n "$(EXEEXT)" || exit 0; \ + list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ + echo " rm -f" $$list; \ + rm -f $$list +install-libexecPROGRAMS: $(libexec_PROGRAMS) @$(NORMAL_INSTALL) - test -z "$(bindir)" || $(MKDIR_P) "$(DESTDIR)$(bindir)" - @list='$(bin_PROGRAMS)'; test -n "$(bindir)" || list=; \ + @list='$(libexec_PROGRAMS)'; test -n "$(libexecdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(libexecdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libexecdir)" || exit 1; \ + fi; \ for p in $$list; do echo "$$p $$p"; done | \ sed 's/$(EXEEXT)$$//' | \ while read p p1; do if test -f $$p || test -f $$p1; \ @@ -760,23 +804,23 @@ install-binPROGRAMS: $(bin_PROGRAMS) while read type dir files; do \ if test "$$dir" = .; then dir=; else dir=/$$dir; fi; \ test -z "$$files" || { \ - echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files '$(DESTDIR)$(bindir)$$dir'"; \ - $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files "$(DESTDIR)$(bindir)$$dir" || exit $$?; \ + echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files '$(DESTDIR)$(libexecdir)$$dir'"; \ + $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files "$(DESTDIR)$(libexecdir)$$dir" || exit $$?; \ } \ ; done -uninstall-binPROGRAMS: +uninstall-libexecPROGRAMS: @$(NORMAL_UNINSTALL) - @list='$(bin_PROGRAMS)'; test -n "$(bindir)" || list=; \ + @list='$(libexec_PROGRAMS)'; test -n "$(libexecdir)" || list=; \ files=`for p in $$list; do echo "$$p"; done | \ sed -e 'h;s,^.*/,,;s/$(EXEEXT)$$//;$(transform)' \ -e 's/$$/$(EXEEXT)/' `; \ test -n "$$list" || exit 0; \ - echo " ( cd '$(DESTDIR)$(bindir)' && rm -f" $$files ")"; \ - cd "$(DESTDIR)$(bindir)" && rm -f $$files + echo " ( cd '$(DESTDIR)$(libexecdir)' && rm -f" $$files ")"; \ + cd "$(DESTDIR)$(libexecdir)" && rm -f $$files -clean-binPROGRAMS: - @list='$(bin_PROGRAMS)'; test -n "$$list" || exit 0; \ +clean-libexecPROGRAMS: + @list='$(libexec_PROGRAMS)'; test -n "$$list" || exit 0; \ echo " rm -f" $$list; \ rm -f $$list || exit $$?; \ test -n "$(EXEEXT)" || exit 0; \ @@ -784,53 +828,44 @@ clean-binPROGRAMS: echo " rm -f" $$list; \ rm -f $$list -clean-checkPROGRAMS: - @list='$(check_PROGRAMS)'; test -n "$$list" || exit 0; \ +clean-noinstPROGRAMS: + @list='$(noinst_PROGRAMS)'; test -n "$$list" || exit 0; \ echo " rm -f" $$list; \ rm -f $$list || exit $$?; \ test -n "$(EXEEXT)" || exit 0; \ list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ echo " rm -f" $$list; \ rm -f $$list -gnunet-dht-get$(EXEEXT): $(gnunet_dht_get_OBJECTS) $(gnunet_dht_get_DEPENDENCIES) +gnunet-dht-get$(EXEEXT): $(gnunet_dht_get_OBJECTS) $(gnunet_dht_get_DEPENDENCIES) $(EXTRA_gnunet_dht_get_DEPENDENCIES) @rm -f gnunet-dht-get$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_dht_get_OBJECTS) $(gnunet_dht_get_LDADD) $(LIBS) -gnunet-dht-monitor$(EXEEXT): $(gnunet_dht_monitor_OBJECTS) $(gnunet_dht_monitor_DEPENDENCIES) +gnunet-dht-monitor$(EXEEXT): $(gnunet_dht_monitor_OBJECTS) $(gnunet_dht_monitor_DEPENDENCIES) $(EXTRA_gnunet_dht_monitor_DEPENDENCIES) @rm -f gnunet-dht-monitor$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_dht_monitor_OBJECTS) $(gnunet_dht_monitor_LDADD) $(LIBS) -gnunet-dht-put$(EXEEXT): $(gnunet_dht_put_OBJECTS) $(gnunet_dht_put_DEPENDENCIES) +gnunet-dht-put$(EXEEXT): $(gnunet_dht_put_OBJECTS) $(gnunet_dht_put_DEPENDENCIES) $(EXTRA_gnunet_dht_put_DEPENDENCIES) @rm -f gnunet-dht-put$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_dht_put_OBJECTS) $(gnunet_dht_put_LDADD) $(LIBS) -gnunet-service-dht$(EXEEXT): $(gnunet_service_dht_OBJECTS) $(gnunet_service_dht_DEPENDENCIES) +gnunet-service-dht$(EXEEXT): $(gnunet_service_dht_OBJECTS) $(gnunet_service_dht_DEPENDENCIES) $(EXTRA_gnunet_service_dht_DEPENDENCIES) @rm -f gnunet-service-dht$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_service_dht_OBJECTS) $(gnunet_service_dht_LDADD) $(LIBS) -test_dht_2dtorus$(EXEEXT): $(test_dht_2dtorus_OBJECTS) $(test_dht_2dtorus_DEPENDENCIES) +test_dht_2dtorus$(EXEEXT): $(test_dht_2dtorus_OBJECTS) $(test_dht_2dtorus_DEPENDENCIES) $(EXTRA_test_dht_2dtorus_DEPENDENCIES) @rm -f test_dht_2dtorus$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_dht_2dtorus_OBJECTS) $(test_dht_2dtorus_LDADD) $(LIBS) -test_dht_api$(EXEEXT): $(test_dht_api_OBJECTS) $(test_dht_api_DEPENDENCIES) +test_dht_api$(EXEEXT): $(test_dht_api_OBJECTS) $(test_dht_api_DEPENDENCIES) $(EXTRA_test_dht_api_DEPENDENCIES) @rm -f test_dht_api$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_dht_api_OBJECTS) $(test_dht_api_LDADD) $(LIBS) -test_dht_line$(EXEEXT): $(test_dht_line_OBJECTS) $(test_dht_line_DEPENDENCIES) +test_dht_line$(EXEEXT): $(test_dht_line_OBJECTS) $(test_dht_line_DEPENDENCIES) $(EXTRA_test_dht_line_DEPENDENCIES) @rm -f test_dht_line$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_dht_line_OBJECTS) $(test_dht_line_LDADD) $(LIBS) -test_dht_monitor$(EXEEXT): $(test_dht_monitor_OBJECTS) $(test_dht_monitor_DEPENDENCIES) +test_dht_monitor$(EXEEXT): $(test_dht_monitor_OBJECTS) $(test_dht_monitor_DEPENDENCIES) $(EXTRA_test_dht_monitor_DEPENDENCIES) @rm -f test_dht_monitor$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_dht_monitor_OBJECTS) $(test_dht_monitor_LDADD) $(LIBS) -test_dht_multipeer$(EXEEXT): $(test_dht_multipeer_OBJECTS) $(test_dht_multipeer_DEPENDENCIES) +test_dht_multipeer$(EXEEXT): $(test_dht_multipeer_OBJECTS) $(test_dht_multipeer_DEPENDENCIES) $(EXTRA_test_dht_multipeer_DEPENDENCIES) @rm -f test_dht_multipeer$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_dht_multipeer_OBJECTS) $(test_dht_multipeer_LDADD) $(LIBS) -test_dht_twopeer$(EXEEXT): $(test_dht_twopeer_OBJECTS) $(test_dht_twopeer_DEPENDENCIES) +test_dht_twopeer$(EXEEXT): $(test_dht_twopeer_OBJECTS) $(test_dht_twopeer_DEPENDENCIES) $(EXTRA_test_dht_twopeer_DEPENDENCIES) @rm -f test_dht_twopeer$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_dht_twopeer_OBJECTS) $(test_dht_twopeer_LDADD) $(LIBS) -test_dht_twopeer_get_put$(EXEEXT): $(test_dht_twopeer_get_put_OBJECTS) $(test_dht_twopeer_get_put_DEPENDENCIES) - @rm -f test_dht_twopeer_get_put$(EXEEXT) - $(AM_V_CCLD)$(LINK) $(test_dht_twopeer_get_put_OBJECTS) $(test_dht_twopeer_get_put_LDADD) $(LIBS) -test_dht_twopeer_path_tracking$(EXEEXT): $(test_dht_twopeer_path_tracking_OBJECTS) $(test_dht_twopeer_path_tracking_DEPENDENCIES) - @rm -f test_dht_twopeer_path_tracking$(EXEEXT) - $(AM_V_CCLD)$(LINK) $(test_dht_twopeer_path_tracking_OBJECTS) $(test_dht_twopeer_path_tracking_LDADD) $(LIBS) -test_dht_twopeer_put_get$(EXEEXT): $(test_dht_twopeer_put_get_OBJECTS) $(test_dht_twopeer_put_get_DEPENDENCIES) - @rm -f test_dht_twopeer_put_get$(EXEEXT) - $(AM_V_CCLD)$(LINK) $(test_dht_twopeer_put_get_OBJECTS) $(test_dht_twopeer_put_get_LDADD) $(LIBS) mostlyclean-compile: -rm -f *.$(OBJEXT) @@ -839,6 +874,7 @@ distclean-compile: -rm -f *.tab.c @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/dht_api.Plo@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/dht_test_lib.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-dht-get.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-dht-monitor.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-dht-put.Po@am__quote@ @@ -852,36 +888,28 @@ distclean-compile: @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/plugin_block_dht.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_dht_api.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_dht_monitor.Po@am__quote@ -@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_dht_multipeer.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_dht_topo.Po@am__quote@ -@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_dht_twopeer.Po@am__quote@ -@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_dht_twopeer_get_put.Po@am__quote@ -@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_dht_twopeer_path_tracking.Po@am__quote@ -@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_dht_twopeer_put_get.Po@am__quote@ .c.o: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c $< .c.obj: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'` @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c `$(CYGPATH_W) '$<'` +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c `$(CYGPATH_W) '$<'` .c.lo: @am__fastdepCC_TRUE@ $(AM_V_CC)$(LTCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LTCOMPILE) -c -o $@ $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LTCOMPILE) -c -o $@ $< mostlyclean-libtool: -rm -f *.lo @@ -890,8 +918,11 @@ clean-libtool: -rm -rf .libs _libs install-pkgcfgDATA: $(pkgcfg_DATA) @$(NORMAL_INSTALL) - test -z "$(pkgcfgdir)" || $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" @list='$(pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(pkgcfgdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" || exit 1; \ + fi; \ for p in $$list; do \ if test -f "$$p"; then d=; else d="$(srcdir)/"; fi; \ echo "$$d$$p"; \ @@ -905,9 +936,7 @@ uninstall-pkgcfgDATA: @$(NORMAL_UNINSTALL) @list='$(pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ files=`for p in $$list; do echo $$p; done | sed -e 's|^.*/||'`; \ - test -n "$$files" || exit 0; \ - echo " ( cd '$(DESTDIR)$(pkgcfgdir)' && rm -f" $$files ")"; \ - cd "$(DESTDIR)$(pkgcfgdir)" && rm -f $$files + dir='$(DESTDIR)$(pkgcfgdir)'; $(am__uninstall_files_from_dir) ID: $(HEADERS) $(SOURCES) $(LISP) $(TAGS_FILES) list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ @@ -1042,14 +1071,15 @@ check-TESTS: $(TESTS) fi; \ dashes=`echo "$$dashes" | sed s/./=/g`; \ if test "$$failed" -eq 0; then \ - echo "$$grn$$dashes"; \ + col="$$grn"; \ else \ - echo "$$red$$dashes"; \ + col="$$red"; \ fi; \ - echo "$$banner"; \ - test -z "$$skipped" || echo "$$skipped"; \ - test -z "$$report" || echo "$$report"; \ - echo "$$dashes$$std"; \ + echo "$${col}$$dashes$${std}"; \ + echo "$${col}$$banner$${std}"; \ + test -z "$$skipped" || echo "$${col}$$skipped$${std}"; \ + test -z "$$report" || echo "$${col}$$report$${std}"; \ + echo "$${col}$$dashes$${std}"; \ test "$$failed" -eq 0; \ else :; fi @@ -1087,11 +1117,9 @@ check-am: all-am $(MAKE) $(AM_MAKEFLAGS) $(check_PROGRAMS) $(check_SCRIPTS) $(MAKE) $(AM_MAKEFLAGS) check-TESTS check: check-am -all-am: Makefile $(LTLIBRARIES) $(PROGRAMS) $(DATA) -install-binPROGRAMS: install-libLTLIBRARIES - +all-am: Makefile $(LIBRARIES) $(LTLIBRARIES) $(PROGRAMS) $(DATA) installdirs: - for dir in "$(DESTDIR)$(libdir)" "$(DESTDIR)$(plugindir)" "$(DESTDIR)$(bindir)" "$(DESTDIR)$(pkgcfgdir)"; do \ + for dir in "$(DESTDIR)$(libdir)" "$(DESTDIR)$(plugindir)" "$(DESTDIR)$(libexecdir)" "$(DESTDIR)$(pkgcfgdir)"; do \ test -z "$$dir" || $(MKDIR_P) "$$dir"; \ done install: install-am @@ -1104,10 +1132,15 @@ install-am: all-am installcheck: installcheck-am install-strip: - $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ - install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ - `test -z '$(STRIP)' || \ - echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi mostlyclean-generic: clean-generic: @@ -1121,9 +1154,9 @@ maintainer-clean-generic: @echo "it deletes files that may require special tools to rebuild." clean: clean-am -clean-am: clean-binPROGRAMS clean-checkPROGRAMS clean-generic \ - clean-libLTLIBRARIES clean-libtool clean-pluginLTLIBRARIES \ - mostlyclean-am +clean-am: clean-checkPROGRAMS clean-generic clean-libLTLIBRARIES \ + clean-libexecPROGRAMS clean-libtool clean-noinstLIBRARIES \ + clean-noinstPROGRAMS clean-pluginLTLIBRARIES mostlyclean-am distclean: distclean-am -rm -rf ./$(DEPDIR) @@ -1149,7 +1182,7 @@ install-dvi: install-dvi-am install-dvi-am: -install-exec-am: install-binPROGRAMS install-libLTLIBRARIES +install-exec-am: install-libLTLIBRARIES install-libexecPROGRAMS install-html: install-html-am @@ -1189,30 +1222,39 @@ ps: ps-am ps-am: -uninstall-am: uninstall-binPROGRAMS uninstall-libLTLIBRARIES \ +uninstall-am: uninstall-libLTLIBRARIES uninstall-libexecPROGRAMS \ uninstall-pkgcfgDATA uninstall-pluginLTLIBRARIES .MAKE: check-am install-am install-strip .PHONY: CTAGS GTAGS all all-am check check-TESTS check-am clean \ - clean-binPROGRAMS clean-checkPROGRAMS clean-generic \ - clean-libLTLIBRARIES clean-libtool clean-pluginLTLIBRARIES \ - ctags distclean distclean-compile distclean-generic \ - distclean-libtool distclean-tags distdir dvi dvi-am html \ - html-am info info-am install install-am install-binPROGRAMS \ - install-data install-data-am install-dvi install-dvi-am \ - install-exec install-exec-am install-html install-html-am \ - install-info install-info-am install-libLTLIBRARIES \ - install-man install-pdf install-pdf-am install-pkgcfgDATA \ + clean-checkPROGRAMS clean-generic clean-libLTLIBRARIES \ + clean-libexecPROGRAMS clean-libtool clean-noinstLIBRARIES \ + clean-noinstPROGRAMS clean-pluginLTLIBRARIES ctags distclean \ + distclean-compile distclean-generic distclean-libtool \ + distclean-tags distdir dvi dvi-am html html-am info info-am \ + install install-am install-data install-data-am install-dvi \ + install-dvi-am install-exec install-exec-am install-html \ + install-html-am install-info install-info-am \ + install-libLTLIBRARIES install-libexecPROGRAMS install-man \ + install-pdf install-pdf-am install-pkgcfgDATA \ install-pluginLTLIBRARIES install-ps install-ps-am \ install-strip installcheck installcheck-am installdirs \ maintainer-clean maintainer-clean-generic mostlyclean \ mostlyclean-compile mostlyclean-generic mostlyclean-libtool \ pdf pdf-am ps ps-am tags uninstall uninstall-am \ - uninstall-binPROGRAMS uninstall-libLTLIBRARIES \ + uninstall-libLTLIBRARIES uninstall-libexecPROGRAMS \ uninstall-pkgcfgDATA uninstall-pluginLTLIBRARIES +%.py: %.py.in Makefile + $(do_subst) < $(srcdir)/$< > $@ + chmod +x $@ + +test_dht_tools.py: test_dht_tools.py.in Makefile + $(do_subst) < $(srcdir)/test_dht_tools.py.in > test_dht_tools.py + chmod +x test_dht_tools.py + # Tell versions [3.59,3.63) of GNU make to not export all variables. # Otherwise a system limit (for SysV at least) may be exceeded. .NOEXPORT: diff --git a/src/dht/dht.conf.in b/src/dht/dht.conf.in index 59581dc..2802111 100644 --- a/src/dht/dht.conf.in +++ b/src/dht/dht.conf.in @@ -3,7 +3,6 @@ AUTOSTART = YES @JAVAPORT@PORT = 2095 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-dht ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -13,7 +12,6 @@ UNIXPATH = /tmp/gnunet-service-dht.sock UNIX_MATCH_UID = YES UNIX_MATCH_GID = YES # DISABLE_SOCKET_FORWARDING = NO -# DEBUG = YES # USERNAME = # MAXBUF = # TIMEOUT = @@ -22,18 +20,15 @@ UNIX_MATCH_GID = YES # REJECT_FROM = # REJECT_FROM6 = # PREFIX = -# DO_FIND_PEER = -# STRICT_KADEMLIA = -# USE_MAX_HOPS = -# MAX_HOPS = -# REPUBLISH = YES -# REPLICATION_FREQUENCY = 60 -# STOP_ON_CLOSEST = -# STOP_FOUND = -# CONVERGE_MODIFIER = + + +# Special option to disable DHT calling 'try_connect' (for testing) +DISABLE_TRY_CONNECT = NO [dhtcache] -DATABASE = sqlite -QUOTA = 1 MB +DATABASE = heap +QUOTA = 50 MB +# Disable RC-file for Bloom filter? (for benchmarking with limited IO availability) +DISABLE_BF_RC = NO diff --git a/src/dht/dht.h b/src/dht/dht.h index 8adf49f..f736c8d 100644 --- a/src/dht/dht.h +++ b/src/dht/dht.h @@ -60,7 +60,7 @@ struct GNUNET_DHT_ClientGetStopMessage /** * Key of this request */ - GNUNET_HashCode key; + struct GNUNET_HashCode key; }; @@ -95,7 +95,7 @@ struct GNUNET_DHT_ClientGetMessage /** * The key to search for */ - GNUNET_HashCode key; + struct GNUNET_HashCode key; /** * Unique ID identifying this request, if 0 then @@ -108,6 +108,39 @@ struct GNUNET_DHT_ClientGetMessage }; +/** + * DHT GET RESULTS KNOWN message sent from clients to service. Indicates that a GET + * request should exclude certain results which are already known. + */ +struct GNUNET_DHT_ClientGetResultSeenMessage +{ + /** + * Type: GNUNET_MESSAGE_TYPE_DHT_CLIENT_GET_RESULTS_KNOWN + */ + struct GNUNET_MessageHeader header; + + /** + * Reserved, always 0. + */ + uint32_t reserved GNUNET_PACKED; + + /** + * The key we are searching for (to make it easy to find the corresponding + * GET inside the service). + */ + struct GNUNET_HashCode key; + + /** + * Unique ID identifying this request. + */ + uint64_t unique_id GNUNET_PACKED; + + /* Followed by an array of the hash codes of known results */ + +}; + + + /** * Reply to a GET send from the service to a client. */ @@ -148,7 +181,7 @@ struct GNUNET_DHT_ClientResultMessage /** * The key that was searched for */ - GNUNET_HashCode key; + struct GNUNET_HashCode key; /* put path, get path and actual data are copied to end of this dealy do */ @@ -193,7 +226,7 @@ struct GNUNET_DHT_ClientPutMessage /** * The key to store the value under. */ - GNUNET_HashCode key; + struct GNUNET_HashCode key; /* DATA copied to end of this message */ @@ -268,7 +301,7 @@ struct GNUNET_DHT_MonitorPutMessage /** * The key to store the value under. */ - GNUNET_HashCode key; + struct GNUNET_HashCode key; /* put path (if tracked) */ @@ -315,7 +348,7 @@ struct GNUNET_DHT_MonitorStartStopMessage /** * The key to filter messages by. */ - GNUNET_HashCode key; + struct GNUNET_HashCode key; }; @@ -325,7 +358,7 @@ struct GNUNET_DHT_MonitorStartStopMessage struct GNUNET_DHT_MonitorGetMessage { /** - * Type: GNUNET_MESSAGE_TYPE_DHT_MONITOR_PUT + * Type: GNUNET_MESSAGE_TYPE_DHT_MONITOR_GET */ struct GNUNET_MessageHeader header; @@ -358,7 +391,7 @@ struct GNUNET_DHT_MonitorGetMessage /** * The key to store the value under. */ - GNUNET_HashCode key; + struct GNUNET_HashCode key; /* get path (if tracked) */ @@ -397,7 +430,7 @@ struct GNUNET_DHT_MonitorGetRespMessage /** * The key of the corresponding GET request. */ - GNUNET_HashCode key; + struct GNUNET_HashCode key; /* put path (if tracked) */ diff --git a/src/dht/dht_api.c b/src/dht/dht_api.c index 420eacb..96ca6ab 100644 --- a/src/dht/dht_api.c +++ b/src/dht/dht_api.c @@ -172,16 +172,43 @@ struct GNUNET_DHT_GetHandle */ struct PendingMessage *message; + /** + * Array of hash codes over the results that we have already + * seen. + */ + struct GNUNET_HashCode *seen_results; + /** * Key that this get request is for */ - GNUNET_HashCode key; + struct GNUNET_HashCode key; /** * Unique identifier for this request (for key collisions). */ uint64_t unique_id; + /** + * Size of the 'seen_results' array. Note that not + * all positions might be used (as we over-allocate). + */ + unsigned int seen_results_size; + + /** + * Offset into the 'seen_results' array marking the + * end of the positions that are actually used. + */ + unsigned int seen_results_end; + + /** + * Offset into the 'seen_results' array marking the + * position up to where we've send the hash codes to + * the DHT for blocking (needed as we might not be + * able to send all hash codes at once). + */ + unsigned int seen_results_transmission_offset; + + }; @@ -213,7 +240,7 @@ struct GNUNET_DHT_MonitorHandle /** * Key being looked for, NULL == all. */ - GNUNET_HashCode *key; + struct GNUNET_HashCode *key; /** * Callback for each received message of type get. @@ -352,6 +379,50 @@ try_connect (struct GNUNET_DHT_Handle *handle) } +/** + * Queue messages to DHT to block certain results from the result set. + * + * @param get_handle GET to generate messages for. + */ +static void +queue_filter_messages (struct GNUNET_DHT_GetHandle *get_handle) +{ + struct PendingMessage *pm; + struct GNUNET_DHT_ClientGetResultSeenMessage *msg; + uint16_t msize; + unsigned int delta; + unsigned int max; + + while (get_handle->seen_results_transmission_offset < get_handle->seen_results_end) + { + delta = get_handle->seen_results_end - get_handle->seen_results_transmission_offset; + max = (GNUNET_SERVER_MAX_MESSAGE_SIZE - sizeof (struct GNUNET_DHT_ClientGetResultSeenMessage)) / sizeof (struct GNUNET_HashCode); + if (delta > max) + delta = max; + msize = sizeof (struct GNUNET_DHT_ClientGetResultSeenMessage) + delta * sizeof (struct GNUNET_HashCode); + + pm = GNUNET_malloc (sizeof (struct PendingMessage) + msize); + msg = (struct GNUNET_DHT_ClientGetResultSeenMessage *) &pm[1]; + pm->msg = &msg->header; + pm->handle = get_handle->dht_handle; + pm->unique_id = get_handle->unique_id; + pm->free_on_send = GNUNET_YES; + pm->in_pending_queue = GNUNET_YES; + msg->header.type = htons (GNUNET_MESSAGE_TYPE_DHT_CLIENT_GET_RESULTS_KNOWN); + msg->header.size = htons (msize); + msg->key = get_handle->key; + msg->unique_id = get_handle->unique_id; + memcpy (&msg[1], + &get_handle->seen_results[get_handle->seen_results_transmission_offset], + sizeof (struct GNUNET_HashCode) * delta); + get_handle->seen_results_transmission_offset += delta; + GNUNET_CONTAINER_DLL_insert_tail (get_handle->dht_handle->pending_head, + get_handle->dht_handle->pending_tail, + pm); + } +} + + /** * Add the request corresponding to the given route handle * to the pending queue (if it is not already in there). @@ -362,19 +433,21 @@ try_connect (struct GNUNET_DHT_Handle *handle) * @return GNUNET_YES (always) */ static int -add_request_to_pending (void *cls, const GNUNET_HashCode * key, void *value) +add_request_to_pending (void *cls, const struct GNUNET_HashCode * key, void *value) { struct GNUNET_DHT_Handle *handle = cls; - struct GNUNET_DHT_GetHandle *rh = value; + struct GNUNET_DHT_GetHandle *get_handle = value; - if (GNUNET_NO == rh->message->in_pending_queue) + if (GNUNET_NO == get_handle->message->in_pending_queue) { LOG (GNUNET_ERROR_TYPE_DEBUG, "Retransmitting request related to %s to DHT %p\n", GNUNET_h2s (key), handle); + get_handle->seen_results_transmission_offset = 0; GNUNET_CONTAINER_DLL_insert (handle->pending_head, handle->pending_tail, - rh->message); - rh->message->in_pending_queue = GNUNET_YES; + get_handle->message); + queue_filter_messages (get_handle); + get_handle->message->in_pending_queue = GNUNET_YES; } return GNUNET_YES; } @@ -401,13 +474,7 @@ try_reconnect (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) struct GNUNET_DHT_Handle *handle = cls; LOG (GNUNET_ERROR_TYPE_DEBUG, "Reconnecting with DHT %p\n", handle); - handle->reconnect_task = GNUNET_SCHEDULER_NO_TASK; - if (handle->retry_time.rel_value < GNUNET_CONSTANTS_SERVICE_RETRY.rel_value) - handle->retry_time = GNUNET_CONSTANTS_SERVICE_RETRY; - else - handle->retry_time = GNUNET_TIME_relative_multiply (handle->retry_time, 2); - if (handle->retry_time.rel_value > GNUNET_CONSTANTS_SERVICE_TIMEOUT.rel_value) - handle->retry_time = GNUNET_CONSTANTS_SERVICE_TIMEOUT; + handle->retry_time = GNUNET_TIME_STD_BACKOFF (handle->retry_time); handle->reconnect_task = GNUNET_SCHEDULER_NO_TASK; if (GNUNET_YES != try_connect (handle)) { @@ -438,8 +505,9 @@ do_disconnect (struct GNUNET_DHT_Handle *handle) GNUNET_CLIENT_notify_transmit_ready_cancel (handle->th); handle->th = NULL; GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Disconnecting from DHT service, will try to reconnect in %llu ms\n", - (unsigned long long) handle->retry_time.rel_value); + "Disconnecting from DHT service, will try to reconnect in %s\n", + GNUNET_STRINGS_relative_time_to_string (handle->retry_time, + GNUNET_YES)); GNUNET_CLIENT_disconnect (handle->client); handle->client = NULL; @@ -574,15 +642,16 @@ transmit_pending (void *cls, size_t size, void *buf) * @param key query of the request * @param value the 'struct GNUNET_DHT_RouteHandle' of a request matching the same key * @return GNUNET_YES to continue to iterate over all results, - * GNUNET_NO if the reply is malformed + * GNUNET_NO if the reply is malformed or we found a matching request */ static int -process_reply (void *cls, const GNUNET_HashCode * key, void *value) +process_reply (void *cls, const struct GNUNET_HashCode * key, void *value) { const struct GNUNET_DHT_ClientResultMessage *dht_msg = cls; struct GNUNET_DHT_GetHandle *get_handle = value; const struct GNUNET_PeerIdentity *put_path; const struct GNUNET_PeerIdentity *get_path; + struct GNUNET_HashCode hc; uint32_t put_path_length; uint32_t get_path_length; size_t data_length; @@ -619,11 +688,22 @@ process_reply (void *cls, const GNUNET_HashCode * key, void *value) put_path = (const struct GNUNET_PeerIdentity *) &dht_msg[1]; get_path = &put_path[put_path_length]; data = &get_path[get_path_length]; + /* remember that we've seen this result */ + GNUNET_CRYPTO_hash (data, data_length, &hc); + if (get_handle->seen_results_size == get_handle->seen_results_end) + GNUNET_array_grow (get_handle->seen_results, + get_handle->seen_results_size, + get_handle->seen_results_size * 2 + 1); + GNUNET_assert (get_handle->seen_results_end == get_handle->seen_results_transmission_offset); + get_handle->seen_results[get_handle->seen_results_end++] = hc; + /* no need to block it explicitly, service already knows about it! */ + get_handle->seen_results_transmission_offset++; + get_handle->iter (get_handle->iter_cls, GNUNET_TIME_absolute_ntoh (dht_msg->expiration), key, get_path, get_path_length, put_path, put_path_length, ntohl (dht_msg->type), data_length, data); - return GNUNET_YES; + return GNUNET_NO; } /** @@ -648,7 +728,7 @@ process_monitor_get_message (struct GNUNET_DHT_Handle *handle, type_ok = (GNUNET_BLOCK_TYPE_ANY == h->type) || (h->type == ntohl(msg->type)); key_ok = (NULL == h->key) || (0 == memcmp (h->key, &msg->key, - sizeof (GNUNET_HashCode))); + sizeof (struct GNUNET_HashCode))); if (type_ok && key_ok && (NULL != h->get_cb)) h->get_cb (h->cb_cls, ntohl (msg->options), @@ -699,7 +779,7 @@ process_monitor_get_resp_message (struct GNUNET_DHT_Handle *handle, type_ok = (GNUNET_BLOCK_TYPE_ANY == h->type) || (h->type == ntohl(msg->type)); key_ok = (NULL == h->key) || (0 == memcmp (h->key, &msg->key, - sizeof (GNUNET_HashCode))); + sizeof (struct GNUNET_HashCode))); if (type_ok && key_ok && (NULL != h->get_resp_cb)) h->get_resp_cb (h->cb_cls, (enum GNUNET_BLOCK_Type) ntohl(msg->type), @@ -749,7 +829,7 @@ process_monitor_put_message (struct GNUNET_DHT_Handle *handle, type_ok = (GNUNET_BLOCK_TYPE_ANY == h->type) || (h->type == ntohl(msg->type)); key_ok = (NULL == h->key) || (0 == memcmp (h->key, &msg->key, - sizeof (GNUNET_HashCode))); + sizeof (struct GNUNET_HashCode))); if (type_ok && key_ok && (NULL != h->put_cb)) h->put_cb (h->cb_cls, ntohl (msg->options), @@ -820,6 +900,8 @@ service_message_handler (void *cls, const struct GNUNET_MessageHeader *msg) do_disconnect (handle); return; } + GNUNET_CLIENT_receive (handle->client, &service_message_handler, handle, + GNUNET_TIME_UNIT_FOREVER_REL); ret = GNUNET_SYSERR; msize = ntohs (msg->size); switch (ntohs (msg->type)) @@ -861,13 +943,15 @@ service_message_handler (void *cls, const struct GNUNET_MessageHeader *msg) GNUNET_break (0); break; } - ret = GNUNET_OK; dht_msg = (const struct GNUNET_DHT_ClientResultMessage *) msg; - LOG (GNUNET_ERROR_TYPE_DEBUG, "Received reply for `%s' from DHT service %p\n", - GNUNET_h2s (&dht_msg->key), handle); + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Received reply for `%s' from DHT service %p\n", + GNUNET_h2s (&dht_msg->key), handle); GNUNET_CONTAINER_multihashmap_get_multiple (handle->active_requests, - &dht_msg->key, &process_reply, - (void *) dht_msg); + &dht_msg->key, + &process_reply, + (void *) dht_msg); + ret = GNUNET_OK; break; case GNUNET_MESSAGE_TYPE_DHT_CLIENT_PUT_OK: if (ntohs (msg->size) != sizeof (struct GNUNET_DHT_ClientPutConfirmationMessage)) @@ -880,6 +964,9 @@ service_message_handler (void *cls, const struct GNUNET_MessageHeader *msg) break; default: GNUNET_break(0); + LOG (GNUNET_ERROR_TYPE_WARNING, + "Unknown DHT message type: %hu (%hu) size: %hu\n", + ntohs (msg->type), msg->type, msize); break; } if (GNUNET_OK != ret) @@ -888,8 +975,6 @@ service_message_handler (void *cls, const struct GNUNET_MessageHeader *msg) do_disconnect (handle); return; } - GNUNET_CLIENT_receive (handle->client, &service_message_handler, handle, - GNUNET_TIME_UNIT_FOREVER_REL); } @@ -912,7 +997,7 @@ GNUNET_DHT_connect (const struct GNUNET_CONFIGURATION_Handle *cfg, handle->cfg = cfg; handle->uid_gen = GNUNET_CRYPTO_random_u64 (GNUNET_CRYPTO_QUALITY_WEAK, UINT64_MAX); - handle->active_requests = GNUNET_CONTAINER_multihashmap_create (ht_len); + handle->active_requests = GNUNET_CONTAINER_multihashmap_create (ht_len, GNUNET_NO); if (GNUNET_NO == try_connect (handle)) { GNUNET_DHT_disconnect (handle); @@ -1040,10 +1125,10 @@ mark_put_message_gone (void *cls, * @param cont_cls closure for cont */ struct GNUNET_DHT_PutHandle * -GNUNET_DHT_put (struct GNUNET_DHT_Handle *handle, const GNUNET_HashCode * key, +GNUNET_DHT_put (struct GNUNET_DHT_Handle *handle, const struct GNUNET_HashCode * key, uint32_t desired_replication_level, enum GNUNET_DHT_RouteOption options, - enum GNUNET_BLOCK_Type type, size_t size, const char *data, + enum GNUNET_BLOCK_Type type, size_t size, const void *data, struct GNUNET_TIME_Absolute exp, struct GNUNET_TIME_Relative timeout, GNUNET_DHT_PutContinuation cont, void *cont_cls) @@ -1148,7 +1233,7 @@ GNUNET_DHT_put_cancel (struct GNUNET_DHT_PutHandle *ph) */ struct GNUNET_DHT_GetHandle * GNUNET_DHT_get_start (struct GNUNET_DHT_Handle *handle, - enum GNUNET_BLOCK_Type type, const GNUNET_HashCode * key, + enum GNUNET_BLOCK_Type type, const struct GNUNET_HashCode * key, uint32_t desired_replication_level, enum GNUNET_DHT_RouteOption options, const void *xquery, size_t xquery_size, GNUNET_DHT_GetIterator iter, @@ -1185,6 +1270,7 @@ GNUNET_DHT_get_start (struct GNUNET_DHT_Handle *handle, pending); pending->in_pending_queue = GNUNET_YES; get_handle = GNUNET_malloc (sizeof (struct GNUNET_DHT_GetHandle)); + get_handle->dht_handle = handle; get_handle->iter = iter; get_handle->iter_cls = iter_cls; get_handle->message = pending; @@ -1196,6 +1282,38 @@ GNUNET_DHT_get_start (struct GNUNET_DHT_Handle *handle, } + +/** + * Tell the DHT not to return any of the following known results + * to this client. + * + * @param get_handle get operation for which results should be filtered + * @param num_results number of results to be blocked that are + * provided in this call (size of the 'results' array) + * @param results array of hash codes over the 'data' of the results + * to be blocked + */ +void +GNUNET_DHT_get_filter_known_results (struct GNUNET_DHT_GetHandle *get_handle, + unsigned int num_results, + const struct GNUNET_HashCode *results) +{ + unsigned int needed; + + needed = get_handle->seen_results_end + num_results; + if (needed > get_handle->seen_results_size) + GNUNET_array_grow (get_handle->seen_results, + get_handle->seen_results_size, + needed); + memcpy (&get_handle->seen_results[get_handle->seen_results_end], + results, + num_results * sizeof (struct GNUNET_HashCode)); + get_handle->seen_results_end += num_results; + queue_filter_messages (get_handle); + process_pending_messages (get_handle->dht_handle); +} + + /** * Stop async DHT-get. * @@ -1244,8 +1362,10 @@ GNUNET_DHT_get_stop (struct GNUNET_DHT_GetHandle *get_handle) get_handle->message->in_pending_queue = GNUNET_NO; } GNUNET_free (get_handle->message); + GNUNET_array_grow (get_handle->seen_results, + get_handle->seen_results_end, + 0); GNUNET_free (get_handle); - process_pending_messages (handle); } @@ -1266,7 +1386,7 @@ GNUNET_DHT_get_stop (struct GNUNET_DHT_GetHandle *get_handle) struct GNUNET_DHT_MonitorHandle * GNUNET_DHT_monitor_start (struct GNUNET_DHT_Handle *handle, enum GNUNET_BLOCK_Type type, - const GNUNET_HashCode *key, + const struct GNUNET_HashCode *key, GNUNET_DHT_MonitorGetCB get_cb, GNUNET_DHT_MonitorGetRespCB get_resp_cb, GNUNET_DHT_MonitorPutCB put_cb, @@ -1287,8 +1407,8 @@ GNUNET_DHT_monitor_start (struct GNUNET_DHT_Handle *handle, h->dht_handle = handle; if (NULL != key) { - h->key = GNUNET_malloc (sizeof(GNUNET_HashCode)); - memcpy (h->key, key, sizeof(GNUNET_HashCode)); + h->key = GNUNET_malloc (sizeof(struct GNUNET_HashCode)); + memcpy (h->key, key, sizeof(struct GNUNET_HashCode)); } pending = GNUNET_malloc (sizeof (struct GNUNET_DHT_MonitorStartStopMessage) + @@ -1305,7 +1425,7 @@ GNUNET_DHT_monitor_start (struct GNUNET_DHT_Handle *handle, m->put = htons(NULL != put_cb); if (NULL != key) { m->filter_key = htons(1); - memcpy (&m->key, key, sizeof(GNUNET_HashCode)); + memcpy (&m->key, key, sizeof(struct GNUNET_HashCode)); } GNUNET_CONTAINER_DLL_insert (handle->pending_head, handle->pending_tail, pending); @@ -1347,7 +1467,7 @@ GNUNET_DHT_monitor_stop (struct GNUNET_DHT_MonitorHandle *handle) m->put = htons(NULL != handle->put_cb); if (NULL != handle->key) { m->filter_key = htons(1); - memcpy (&m->key, handle->key, sizeof(GNUNET_HashCode)); + memcpy (&m->key, handle->key, sizeof(struct GNUNET_HashCode)); } GNUNET_CONTAINER_DLL_insert (handle->dht_handle->pending_head, handle->dht_handle->pending_tail, diff --git a/src/dht/dht_test_lib.c b/src/dht/dht_test_lib.c new file mode 100644 index 0000000..365804b --- /dev/null +++ b/src/dht/dht_test_lib.c @@ -0,0 +1,214 @@ +/* + This file is part of GNUnet. + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ +/** + * @file dht/dht_test_lib.c + * @author Christian Grothoff + * @brief library for writing DHT tests + */ +#include "platform.h" +#include "dht_test_lib.h" + +/** + * Test context for a DHT Test. + */ +struct GNUNET_DHT_TEST_Context +{ + /** + * Array of running peers. + */ + struct GNUNET_TESTBED_Peer **peers; + + /** + * Array of handles to the DHT for each peer. + */ + struct GNUNET_DHT_Handle **dhts; + + /** + * Operation associated with the connection to the DHT. + */ + struct GNUNET_TESTBED_Operation **ops; + + /** + * Main function of the test to run once all DHTs are available. + */ + GNUNET_DHT_TEST_AppMain app_main; + + /** + * Closure for 'app_main'. + */ + void *app_main_cls; + + /** + * Number of peers running, size of the arrays above. + */ + unsigned int num_peers; + +}; + + +/** + * Adapter function called to establish a connection to + * the DHT service. + * + * @param cls closure + * @param cfg configuration of the peer to connect to; will be available until + * GNUNET_TESTBED_operation_done() is called on the operation returned + * from GNUNET_TESTBED_service_connect() + * @return service handle to return in 'op_result', NULL on error + */ +static void * +dht_connect_adapter (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg) +{ + return GNUNET_DHT_connect (cfg, 16); +} + + +/** + * Adapter function called to destroy a connection to + * the DHT service. + * + * @param cls closure + * @param op_result service handle returned from the connect adapter + */ +static void +dht_disconnect_adapter (void *cls, + void *op_result) +{ + struct GNUNET_DHT_Handle *dht = op_result; + + GNUNET_DHT_disconnect (dht); +} + + +/** + * Callback to be called when a service connect operation is completed + * + * @param cls the callback closure from functions generating an operation + * @param op the operation that has been finished + * @param ca_result the service handle returned from GNUNET_TESTBED_ConnectAdapter() + * @param emsg error message in case the operation has failed; will be NULL if + * operation has executed successfully. + */ +static void +dht_connect_cb (void *cls, + struct GNUNET_TESTBED_Operation *op, + void *ca_result, + const char *emsg) +{ + struct GNUNET_DHT_TEST_Context *ctx = cls; + unsigned int i; + + if (NULL != emsg) + { + fprintf (stderr, "Failed to connect to DHT service: %s\n", + emsg); + GNUNET_SCHEDULER_shutdown (); + return; + } + for (i=0;inum_peers;i++) + if (op == ctx->ops[i]) + ctx->dhts[i] = ca_result; + for (i=0;inum_peers;i++) + if (NULL == ctx->dhts[i]) + return; /* still some DHT connections missing */ + /* all DHT connections ready! */ + ctx->app_main (ctx->app_main_cls, + ctx, + ctx->num_peers, + ctx->peers, + ctx->dhts); +} + + +/** + * Clean up the testbed. + * + * @param ctx handle for the testbed + */ +void +GNUNET_DHT_TEST_cleanup (struct GNUNET_DHT_TEST_Context *ctx) +{ + unsigned int i; + + for (i=0;inum_peers;i++) + GNUNET_TESTBED_operation_done (ctx->ops[i]); + GNUNET_free (ctx->ops); + GNUNET_free (ctx->dhts); + GNUNET_free (ctx); + GNUNET_SCHEDULER_shutdown (); +} + + +static void +dht_test_run (void *cls, + unsigned int num_peers, + struct GNUNET_TESTBED_Peer **peers) +{ + struct GNUNET_DHT_TEST_Context *ctx = cls; + unsigned int i; + + GNUNET_assert (num_peers == ctx->num_peers); + ctx->peers = peers; + for (i=0;iops[i] = GNUNET_TESTBED_service_connect (ctx, + peers[i], + "dht", + &dht_connect_cb, + ctx, + &dht_connect_adapter, + &dht_disconnect_adapter, + ctx); +} + + +/** + * Run a test using the given name, configuration file and number of + * peers. + * + * @param testname name of the test (for logging) + * @param cfgname name of the configuration file + * @param num_peers number of peers to start + * @param tmain main function to run once the testbed is ready + * @param tmain_cls closure for 'tmain' + */ +void +GNUNET_DHT_TEST_run (const char *testname, + const char *cfgname, + unsigned int num_peers, + GNUNET_DHT_TEST_AppMain tmain, + void *tmain_cls) +{ + struct GNUNET_DHT_TEST_Context *ctx; + + ctx = GNUNET_malloc (sizeof (struct GNUNET_DHT_TEST_Context)); + ctx->num_peers = num_peers; + ctx->ops = GNUNET_malloc (num_peers * sizeof (struct GNUNET_TESTBED_Operation *)); + ctx->dhts = GNUNET_malloc (num_peers * sizeof (struct GNUNET_DHT_Handle *)); + ctx->app_main = tmain; + ctx->app_main_cls = tmain_cls; + (void) GNUNET_TESTBED_test_run (testname, + cfgname, + num_peers, + 0LL, NULL, NULL, + &dht_test_run, ctx); +} + +/* end of dht_test_lib.c */ diff --git a/src/dht/dht_test_lib.h b/src/dht/dht_test_lib.h new file mode 100644 index 0000000..061794a --- /dev/null +++ b/src/dht/dht_test_lib.h @@ -0,0 +1,95 @@ +/* + This file is part of GNUnet. + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ +/** + * @file dht/dht_test_lib.h + * @author Christian Grothoff + * @brief library for writing DHT tests + */ +#ifndef DHT_TEST_LIB_H +#define DHT_TEST_LIB_H + +#ifdef __cplusplus +extern "C" +{ +#if 0 /* keep Emacsens' auto-indent happy */ +} +#endif +#endif + +#include "gnunet_testbed_service.h" +#include "gnunet_dht_service.h" + +/** + * Test context for a DHT Test. + */ +struct GNUNET_DHT_TEST_Context; + + +/** + * Main function of a DHT test. + * + * @param cls closure + * @param ctx argument to give to GNUNET_DHT_TEST_cleanup on test end + * @param num_peers number of peers that are running + * @param peers array of peers + * @param dhts handle to each of the DHTs of the peers + */ +typedef void (*GNUNET_DHT_TEST_AppMain) (void *cls, + struct GNUNET_DHT_TEST_Context *ctx, + unsigned int num_peers, + struct GNUNET_TESTBED_Peer **peers, + struct GNUNET_DHT_Handle **dhts); + + +/** + * Run a test using the given name, configuration file and number of + * peers. + * + * @param testname name of the test (for logging) + * @param cfgname name of the configuration file + * @param num_peers number of peers to start + * @param tmain main function to run once the testbed is ready + * @param tmain_cls closure for 'tmain' + */ +void +GNUNET_DHT_TEST_run (const char *testname, + const char *cfgname, + unsigned int num_peers, + GNUNET_DHT_TEST_AppMain tmain, + void *tmain_cls); + + +/** + * Clean up the testbed. + * + * @param ctx handle for the testbed + */ +void +GNUNET_DHT_TEST_cleanup (struct GNUNET_DHT_TEST_Context *ctx); + +#if 0 /* keep Emacsens' auto-indent happy */ +{ +#endif +#ifdef __cplusplus +} +#endif + +/* ifndef DHT_TEST_LIB_H */ +#endif diff --git a/src/dht/gnunet-dht-get.c b/src/dht/gnunet-dht-get.c index fb185c4..345a58a 100644 --- a/src/dht/gnunet-dht-get.c +++ b/src/dht/gnunet-dht-get.c @@ -42,19 +42,19 @@ static unsigned int replication = 5; static char *query_key; /** - * User supplied timeout value (in seconds) + * User supplied timeout value */ -static unsigned long long timeout_request = 5; +static struct GNUNET_TIME_Relative timeout_request = { 60000 }; /** - * When this request should really die + * Be verbose */ -struct GNUNET_TIME_Absolute absolute_timeout; +static int verbose; /** - * Be verbose + * Use DHT demultixplex_everywhere */ -static int verbose; +static int demultixplex_everywhere; /** * Handle to the DHT @@ -82,26 +82,25 @@ static unsigned int result_count; static int ret; -static void -shutdown_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - if (dht_handle != NULL) - { - GNUNET_DHT_disconnect (dht_handle); - dht_handle = NULL; - } -} - - +/** + * Task run to clean up on timeout. + * + * @param cls unused + * @param tc unused + */ static void cleanup_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { - if (get_handle != NULL) + if (NULL != get_handle) { GNUNET_DHT_get_stop (get_handle); get_handle = NULL; } - GNUNET_SCHEDULER_add_now (&shutdown_task, NULL); + if (NULL != dht_handle) + { + GNUNET_DHT_disconnect (dht_handle); + dht_handle = NULL; + } } @@ -122,14 +121,16 @@ cleanup_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) */ static void get_result_iterator (void *cls, struct GNUNET_TIME_Absolute exp, - const GNUNET_HashCode * key, + const struct GNUNET_HashCode * key, const struct GNUNET_PeerIdentity *get_path, unsigned int get_path_length, const struct GNUNET_PeerIdentity *put_path, unsigned int put_path_length, enum GNUNET_BLOCK_Type type, size_t size, const void *data) { - FPRINTF (stdout, "Result %d, type %d:\n%.*s\n", result_count, type, + FPRINTF (stdout, + _("Result %d, type %d:\n%.*s\n"), + result_count, type, (unsigned int) size, (char *) data); result_count++; } @@ -147,48 +148,32 @@ static void run (void *cls, char *const *args, const char *cfgfile, const struct GNUNET_CONFIGURATION_Handle *c) { - struct GNUNET_TIME_Relative timeout; - GNUNET_HashCode key; + struct GNUNET_HashCode key; cfg = c; - - if (query_key == NULL) + if (NULL == query_key) { - if (verbose) - FPRINTF (stderr, "%s", "Must provide key for DHT GET!\n"); + FPRINTF (stderr, "%s", _("Must provide key for DHT GET!\n")); ret = 1; return; } - - dht_handle = GNUNET_DHT_connect (cfg, 1); - - if (dht_handle == NULL) + if (NULL == (dht_handle = GNUNET_DHT_connect (cfg, 1))) { - if (verbose) - FPRINTF (stderr, "%s", "Couldn't connect to DHT service!\n"); + FPRINTF (stderr, "%s", _("Failed to connect to DHT service!\n")); ret = 1; return; } - else if (verbose) - FPRINTF (stderr, "%s", "Connected to DHT service!\n"); - if (query_type == GNUNET_BLOCK_TYPE_ANY) /* Type of data not set */ query_type = GNUNET_BLOCK_TYPE_TEST; - GNUNET_CRYPTO_hash (query_key, strlen (query_key), &key); - - timeout = - GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, timeout_request); - absolute_timeout = GNUNET_TIME_relative_to_absolute (timeout); - if (verbose) - FPRINTF (stderr, "Issuing GET request for %s!\n", query_key); - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_absolute_get_remaining - (absolute_timeout), &cleanup_task, NULL); + FPRINTF (stderr, "%s `%s' \n", _("Issueing DHT GET with key"), GNUNET_h2s_full (&key)); + GNUNET_SCHEDULER_add_delayed (timeout_request, + &cleanup_task, NULL); get_handle = GNUNET_DHT_get_start (dht_handle, query_type, &key, replication, - GNUNET_DHT_RO_NONE, NULL, 0, &get_result_iterator, - NULL); + (demultixplex_everywhere) ? GNUNET_DHT_RO_DEMULTIPLEX_EVERYWHERE : GNUNET_DHT_RO_NONE, + NULL, 0, &get_result_iterator, NULL); } @@ -208,7 +193,10 @@ static struct GNUNET_GETOPT_CommandLineOption options[] = { 1, &GNUNET_GETOPT_set_uint, &query_type}, {'T', "timeout", "TIMEOUT", gettext_noop ("how long to execute this query before giving up?"), - 1, &GNUNET_GETOPT_set_ulong, &timeout_request}, + 1, &GNUNET_GETOPT_set_relative_time, &timeout_request}, + {'x', "demultiplex", NULL, + gettext_noop ("use DHT's demultiplex everywhere option"), + 0, &GNUNET_GETOPT_set_one, &demultixplex_everywhere}, {'V', "verbose", NULL, gettext_noop ("be verbose (print progress information)"), 0, &GNUNET_GETOPT_set_one, &verbose}, @@ -226,6 +214,8 @@ static struct GNUNET_GETOPT_CommandLineOption options[] = { int main (int argc, char *const *argv) { + if (GNUNET_OK != GNUNET_STRINGS_get_utf8_args (argc, argv, &argc, &argv)) + return 2; return (GNUNET_OK == GNUNET_PROGRAM_run (argc, argv, "gnunet-dht-get", gettext_noop diff --git a/src/dht/gnunet-dht-monitor.c b/src/dht/gnunet-dht-monitor.c index 8ca3beb..b03c7c7 100644 --- a/src/dht/gnunet-dht-monitor.c +++ b/src/dht/gnunet-dht-monitor.c @@ -39,7 +39,7 @@ static char *query_key; /** * User supplied timeout value (in seconds) */ -static unsigned long long timeout_request = 5; +static struct GNUNET_TIME_Relative timeout_request = { 60000 }; /** * Be verbose @@ -72,25 +72,6 @@ static unsigned int result_count; static int ret; -/** - * Function called on shutdown, disconnects from DHT if necessary. - * - * @param cls closure (unused) - * @param tc Task Context - */ -static void -shutdown_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - if (verbose) - FPRINTF (stderr, "%s", "Shutting down!\n"); - if (dht_handle != NULL) - { - GNUNET_DHT_disconnect (dht_handle); - dht_handle = NULL; - } -} - - /** * Stop monitoring request and start shutdown * @@ -102,12 +83,16 @@ cleanup_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { if (verbose) FPRINTF (stderr, "%s", "Cleaning up!\n"); - if (monitor_handle != NULL) + if (NULL != monitor_handle) { GNUNET_DHT_monitor_stop (monitor_handle); monitor_handle = NULL; } - GNUNET_SCHEDULER_add_now (&shutdown_task, NULL); + if (NULL != dht_handle) + { + GNUNET_DHT_disconnect (dht_handle); + dht_handle = NULL; + } } @@ -131,16 +116,16 @@ get_callback (void *cls, uint32_t desired_replication_level, unsigned int path_length, const struct GNUNET_PeerIdentity *path, - const GNUNET_HashCode * key) + const struct GNUNET_HashCode * key) { - FPRINTF (stdout, "Result %d, operation: %s, type %d\n Key: %s", + FPRINTF (stdout, "GET #%u: type %d, key `%s'\n", result_count, - "GET", - type, + (int) type, GNUNET_h2s_full(key)); result_count++; } + /** * Callback called on each GET reply going through the DHT. * @@ -163,20 +148,21 @@ get_resp_callback (void *cls, const struct GNUNET_PeerIdentity *put_path, unsigned int put_path_length, struct GNUNET_TIME_Absolute exp, - const GNUNET_HashCode * key, + const struct GNUNET_HashCode * key, const void *data, size_t size) { - FPRINTF (stdout, "Result %d, operation: %s, type %d:\n Key: %s\n %.*s\n", + FPRINTF (stdout, + "RESPONSE #%u: type %d, key `%s', data `%.*s'\n", result_count, - "GET_RESP", - type, - GNUNET_h2s_full(key), + (int) type, + GNUNET_h2s_full (key), (unsigned int) size, (char *) data); result_count++; } + /** * Callback called on each PUT request going through the DHT. * @@ -201,20 +187,21 @@ put_callback (void *cls, unsigned int path_length, const struct GNUNET_PeerIdentity *path, struct GNUNET_TIME_Absolute exp, - const GNUNET_HashCode * key, + const struct GNUNET_HashCode * key, const void *data, size_t size) { - FPRINTF (stdout, "Result %d, operation: %s, type %d:\n Key: %s\n %.*s\n", + FPRINTF (stdout, + "PUT %u: type %d, key `%s', data `%.*s'\n", result_count, - "PUT", - type, + (int) type, GNUNET_h2s_full(key), (unsigned int) size, (char *) data); result_count++; } + /** * Main function that will be run by the scheduler. * @@ -227,50 +214,36 @@ static void run (void *cls, char *const *args, const char *cfgfile, const struct GNUNET_CONFIGURATION_Handle *c) { - struct GNUNET_TIME_Relative timeout; - GNUNET_HashCode *key; + struct GNUNET_HashCode *key; + struct GNUNET_HashCode hc; cfg = c; - dht_handle = GNUNET_DHT_connect (cfg, 1); - - if (dht_handle == NULL) + if (NULL == (dht_handle = GNUNET_DHT_connect (cfg, 1))) { - if (verbose) - FPRINTF (stderr, "%s", "Couldn't connect to DHT service!\n"); + FPRINTF (stderr, "%s", + _("Failed to connect to DHT service!\n")); ret = 1; return; } - else if (verbose) - FPRINTF (stderr, "%s", "Connected to DHT service!\n"); - - if (block_type == GNUNET_BLOCK_TYPE_ANY) /* Type of data not set */ + if (GNUNET_BLOCK_TYPE_ANY == block_type) /* Type of data not set */ block_type = GNUNET_BLOCK_TYPE_TEST; - - if (query_key != NULL) { - key = GNUNET_malloc (sizeof(GNUNET_HashCode)); - GNUNET_CRYPTO_hash (query_key, strlen (query_key), key); - } - else - key = NULL; - - if (0 != timeout_request) - { - timeout = GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, - timeout_request); - if (verbose) - FPRINTF (stderr, "Monitoring for %llus\n", timeout_request); - } + if (NULL != query_key) + { + key = &hc; + if (GNUNET_OK != + GNUNET_CRYPTO_hash_from_string (query_key, key)) + GNUNET_CRYPTO_hash (query_key, strlen (query_key), key); + } else - { - timeout = GNUNET_TIME_UNIT_FOREVER_REL; - if (verbose) - FPRINTF (stderr, "%s", "Monitoring indefinitely (close with Ctrl+C)\n"); - } - - GNUNET_SCHEDULER_add_delayed (timeout, &cleanup_task, NULL); + { + key = NULL; + } if (verbose) - FPRINTF (stderr, "Issuing MONITOR request for %s!\n", query_key); + FPRINTF (stderr, + "Monitoring for %s\n", + GNUNET_STRINGS_relative_time_to_string (timeout_request, GNUNET_NO)); + GNUNET_SCHEDULER_add_delayed (timeout_request, &cleanup_task, NULL); monitor_handle = GNUNET_DHT_monitor_start (dht_handle, block_type, key, @@ -278,15 +251,11 @@ run (void *cls, char *const *args, const char *cfgfile, &get_resp_callback, &put_callback, NULL); - if (verbose) - FPRINTF (stderr, "%s", "MONITOR started!\n"); - GNUNET_free_non_null (key); - } /** - * gnunet-dht-get command line options + * gnunet-dht-monitor command line options */ static struct GNUNET_GETOPT_CommandLineOption options[] = { {'k', "key", "KEY", @@ -296,8 +265,8 @@ static struct GNUNET_GETOPT_CommandLineOption options[] = { gettext_noop ("the type of data to look for"), 1, &GNUNET_GETOPT_set_uint, &block_type}, {'T', "timeout", "TIMEOUT", - gettext_noop ("how long to execute? 0 = forever"), - 1, &GNUNET_GETOPT_set_ulong, &timeout_request}, + gettext_noop ("how long should the monitor command run"), + 1, &GNUNET_GETOPT_set_relative_time, &timeout_request}, {'V', "verbose", NULL, gettext_noop ("be verbose (print progress information)"), 0, &GNUNET_GETOPT_set_one, &verbose}, @@ -315,8 +284,11 @@ static struct GNUNET_GETOPT_CommandLineOption options[] = { int main (int argc, char *const *argv) { + if (GNUNET_OK != GNUNET_STRINGS_get_utf8_args (argc, argv, &argc, &argv)) + return 2; + return (GNUNET_OK == - GNUNET_PROGRAM_run (argc, argv, "gnunet-dht-get", + GNUNET_PROGRAM_run (argc, argv, "gnunet-dht-monitor", gettext_noop ("Prints all packets that go through the DHT."), options, &run, NULL)) ? ret : 1; diff --git a/src/dht/gnunet-dht-put.c b/src/dht/gnunet-dht-put.c index 59acc79..67884c4 100644 --- a/src/dht/gnunet-dht-put.c +++ b/src/dht/gnunet-dht-put.c @@ -31,6 +31,11 @@ */ static unsigned int query_type; +/** + * The key used in the DHT + */ +struct GNUNET_HashCode key; + /** * The key for the query */ @@ -56,6 +61,11 @@ static unsigned int replication = 5; */ static int verbose; +/** + * Use DHT demultixplex_everywhere + */ +static int demultixplex_everywhere; + /** * Handle to the DHT */ @@ -105,7 +115,7 @@ message_sent_cont (void *cls, int success) switch (success) { case GNUNET_OK: - FPRINTF (stderr, "%s", _("PUT request sent!\n")); + FPRINTF (stderr, "%s `%s'!\n", _("PUT request sent with key"), GNUNET_h2s_full(&key)); break; case GNUNET_NO: FPRINTF (stderr, "%s", _("Timeout sending PUT request!\n")); @@ -135,28 +145,23 @@ run (void *cls, char *const *args, const char *cfgfile, { struct GNUNET_TIME_Relative timeout; struct GNUNET_TIME_Absolute expiration; - GNUNET_HashCode key; cfg = c; - if ((query_key == NULL) || (data == NULL)) + if ((NULL == query_key) || (NULL == data)) { FPRINTF (stderr, "%s", _("Must provide KEY and DATA for DHT put!\n")); ret = 1; return; } - dht_handle = GNUNET_DHT_connect (cfg, 1); - if (dht_handle == NULL) + if (NULL == (dht_handle = GNUNET_DHT_connect (cfg, 1))) { FPRINTF (stderr, _("Could not connect to %s service!\n"), "DHT"); ret = 1; return; } - else if (verbose) - FPRINTF (stderr, _("Connected to %s service!\n"), "DHT"); - - if (query_type == GNUNET_BLOCK_TYPE_ANY) /* Type of data not set */ + if (GNUNET_BLOCK_TYPE_ANY == query_type) /* Type of data not set */ query_type = GNUNET_BLOCK_TYPE_TEST; GNUNET_CRYPTO_hash (query_key, strlen (query_key), &key); @@ -167,11 +172,12 @@ run (void *cls, char *const *args, const char *cfgfile, GNUNET_TIME_relative_to_absolute (GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, expiration_seconds)); - if (verbose) FPRINTF (stderr, _("Issuing put request for `%s' with data `%s'!\n"), query_key, data); - GNUNET_DHT_put (dht_handle, &key, replication, GNUNET_DHT_RO_NONE, query_type, + GNUNET_DHT_put (dht_handle, &key, replication, + (demultixplex_everywhere) ? GNUNET_DHT_RO_DEMULTIPLEX_EVERYWHERE : GNUNET_DHT_RO_NONE, + query_type, strlen (data), data, expiration, timeout, &message_sent_cont, NULL); @@ -191,6 +197,9 @@ static struct GNUNET_GETOPT_CommandLineOption options[] = { {'k', "key", "KEY", gettext_noop ("the query key"), 1, &GNUNET_GETOPT_set_string, &query_key}, + {'x', "demultiplex", NULL, + gettext_noop ("use DHT's demultiplex everywhere option"), + 0, &GNUNET_GETOPT_set_one, &demultixplex_everywhere}, {'r', "replication", "LEVEL", gettext_noop ("how many replicas to create"), 1, &GNUNET_GETOPT_set_uint, &replication}, @@ -217,6 +226,9 @@ static struct GNUNET_GETOPT_CommandLineOption options[] = { int main (int argc, char *const *argv) { + if (GNUNET_OK != GNUNET_STRINGS_get_utf8_args (argc, argv, &argc, &argv)) + return 2; + return (GNUNET_OK == GNUNET_PROGRAM_run (argc, argv, "gnunet-dht-put", gettext_noop diff --git a/src/dht/gnunet-service-dht.c b/src/dht/gnunet-service-dht.c index 72575ac..5efa9dd 100644 --- a/src/dht/gnunet-service-dht.c +++ b/src/dht/gnunet-service-dht.c @@ -66,12 +66,16 @@ struct GNUNET_MessageHeader *GDS_my_hello; */ struct GNUNET_TRANSPORT_Handle *GDS_transport_handle; - /** * Handle to get our current HELLO. */ static struct GNUNET_TRANSPORT_GetHelloHandle *ghh; +/** + * Hello address expiration + */ +struct GNUNET_TIME_Relative hello_expiration; + /** * Receive the HELLO from transport service, free current and replace @@ -141,6 +145,11 @@ run (void *cls, struct GNUNET_SERVER_Handle *server, const struct GNUNET_CONFIGURATION_Handle *c) { GDS_cfg = c; + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_time (c, "transport", "HELLO_EXPIRATION", &hello_expiration)) + { + hello_expiration = GNUNET_CONSTANTS_HELLO_ADDRESS_EXPIRATION; + } GDS_block_context = GNUNET_BLOCK_context_create (GDS_cfg); GDS_stats = GNUNET_STATISTICS_create ("dht", GDS_cfg); GDS_ROUTING_init (); diff --git a/src/dht/gnunet-service-dht_clients.c b/src/dht/gnunet-service-dht_clients.c index d897d1f..3d9d5be 100644 --- a/src/dht/gnunet-service-dht_clients.c +++ b/src/dht/gnunet-service-dht_clients.c @@ -36,6 +36,12 @@ #include "dht.h" +/** + * Should routing details be logged to stderr (for debugging)? + */ +#define LOG_ROUTE_DETAILS_STDERR GNUNET_NO + + /** * Linked list of messages to send to clients. */ @@ -111,7 +117,7 @@ struct ClientQueryRecord /** * The key this request was about */ - GNUNET_HashCode key; + struct GNUNET_HashCode key; /** * Client responsible for the request. @@ -126,7 +132,7 @@ struct ClientQueryRecord /** * Replies we have already seen for this request. */ - GNUNET_HashCode *seen_replies; + struct GNUNET_HashCode *seen_replies; /** * Pointer to this nodes heap location in the retry-heap (for fast removal) @@ -201,7 +207,7 @@ struct ClientMonitorRecord /** * Key of data of interest, NULL for all. */ - GNUNET_HashCode *key; + struct GNUNET_HashCode *key; /** * Flag whether to notify about GET messages. @@ -322,7 +328,7 @@ find_active_client (struct GNUNET_SERVER_Client *client) * @return GNUNET_YES (we should continue to iterate) */ static int -remove_client_records (void *cls, const GNUNET_HashCode * key, void *value) +remove_client_records (void *cls, const struct GNUNET_HashCode * key, void *value) { struct ClientList *client = cls; struct ClientQueryRecord *record = value; @@ -423,10 +429,7 @@ transmit_request (struct ClientQueryRecord *cqr) GNUNET_CONTAINER_bloomfilter_free (peer_bf); /* exponential back-off for retries, max 1h */ - cqr->retry_frequency = - GNUNET_TIME_relative_min (GNUNET_TIME_UNIT_HOURS, - GNUNET_TIME_relative_multiply - (cqr->retry_frequency, 2)); + cqr->retry_frequency = GNUNET_TIME_STD_BACKOFF (cqr->retry_frequency); cqr->retry_time = GNUNET_TIME_relative_to_absolute (cqr->retry_frequency); } @@ -551,9 +554,7 @@ handle_dht_local_put (void *cls, struct GNUNET_SERVER_Client *client, /** - * Handler for any generic DHT messages, calls the appropriate handler - * depending on message type, sends confirmation if responses aren't otherwise - * expected. + * Handler for DHT GET messages from the client. * * @param cls closure for the service * @param client the client we received this message from @@ -586,19 +587,30 @@ handle_dht_local_get (void *cls, struct GNUNET_SERVER_Client *client, GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received request for %s from local client %p\n", GNUNET_h2s (&get->key), client); + + if (LOG_ROUTE_DETAILS_STDERR) + { + fprintf (stderr, + "XDHT CLIENT-GET %s @ %u\n", + GNUNET_h2s (&get->key), + getpid ()); + } + + cqr = GNUNET_malloc (sizeof (struct ClientQueryRecord) + xquery_size); cqr->key = get->key; cqr->client = find_active_client (client); cqr->xquery = (void *) &cqr[1]; memcpy (&cqr[1], xquery, xquery_size); cqr->hnode = GNUNET_CONTAINER_heap_insert (retry_heap, cqr, 0); - cqr->retry_frequency = GNUNET_TIME_UNIT_MILLISECONDS; + cqr->retry_frequency = GNUNET_TIME_UNIT_SECONDS; cqr->retry_time = GNUNET_TIME_absolute_get (); cqr->unique_id = get->unique_id; cqr->xquery_size = xquery_size; cqr->replication = ntohl (get->desired_replication_level); cqr->msg_options = ntohl (get->options); cqr->type = ntohl (get->type); + // FIXME use cqr->key, set multihashmap create to GNUNET_YES GNUNET_CONTAINER_multihashmap_put (forward_map, &get->key, cqr, GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE); GDS_CLIENTS_process_get (ntohl (get->options), @@ -619,6 +631,103 @@ handle_dht_local_get (void *cls, struct GNUNET_SERVER_Client *client, } +/** + * Closure for 'find_by_unique_id'. + */ +struct FindByUniqueIdContext +{ + /** + * Where to store the result, if found. + */ + struct ClientQueryRecord *cqr; + + uint64_t unique_id; +}; + + +/** + * Function called for each existing DHT record for the given + * query. Checks if it matches the UID given in the closure + * and if so returns the entry as a result. + * + * @param cls the search context + * @param key query for the lookup (not used) + * @param value the 'struct ClientQueryRecord' + * @return GNUNET_YES to continue iteration (result not yet found) + */ +static int +find_by_unique_id (void *cls, + const struct GNUNET_HashCode *key, + void *value) +{ + struct FindByUniqueIdContext *fui_ctx = cls; + struct ClientQueryRecord *cqr = value; + + if (cqr->unique_id != fui_ctx->unique_id) + return GNUNET_YES; + fui_ctx->cqr = cqr; + return GNUNET_NO; +} + + +/** + * Handler for "GET result seen" messages from the client. + * + * @param cls closure for the service + * @param client the client we received this message from + * @param message the actual message received + */ +static void +handle_dht_local_get_result_seen (void *cls, struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) +{ + const struct GNUNET_DHT_ClientGetResultSeenMessage *seen; + uint16_t size; + unsigned int hash_count; + unsigned int old_count; + const struct GNUNET_HashCode *hc; + struct FindByUniqueIdContext fui_ctx; + struct ClientQueryRecord *cqr; + + size = ntohs (message->size); + if (size < sizeof (struct GNUNET_DHT_ClientGetResultSeenMessage)) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + seen = (const struct GNUNET_DHT_ClientGetResultSeenMessage *) message; + hash_count = (size - sizeof (struct GNUNET_DHT_ClientGetResultSeenMessage)) / sizeof (struct GNUNET_HashCode); + if (size != sizeof (struct GNUNET_DHT_ClientGetResultSeenMessage) + hash_count * sizeof (struct GNUNET_HashCode)) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + hc = (const struct GNUNET_HashCode*) &seen[1]; + fui_ctx.unique_id = seen->unique_id; + fui_ctx.cqr = NULL; + GNUNET_CONTAINER_multihashmap_get_multiple (forward_map, + &seen->key, + &find_by_unique_id, + &fui_ctx); + if (NULL == (cqr = fui_ctx.cqr)) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + /* finally, update 'seen' list */ + old_count = cqr->seen_replies_count; + GNUNET_array_grow (cqr->seen_replies, + cqr->seen_replies_count, + cqr->seen_replies_count + hash_count); + memcpy (&cqr->seen_replies[old_count], + hc, + sizeof (struct GNUNET_HashCode) * hash_count); +} + + /** * Closure for 'remove_by_unique_id'. */ @@ -646,7 +755,7 @@ struct RemoveByUniqueIdContext * @return GNUNET_YES (we should continue to iterate) */ static int -remove_by_unique_id (void *cls, const GNUNET_HashCode * key, void *value) +remove_by_unique_id (void *cls, const struct GNUNET_HashCode * key, void *value) { const struct RemoveByUniqueIdContext *ctx = cls; struct ClientQueryRecord *record = value; @@ -718,8 +827,8 @@ handle_dht_local_monitor (void *cls, struct GNUNET_SERVER_Client *client, r->key = NULL; else { - r->key = GNUNET_malloc (sizeof (GNUNET_HashCode)); - memcpy (r->key, &msg->key, sizeof (GNUNET_HashCode)); + r->key = GNUNET_malloc (sizeof (struct GNUNET_HashCode)); + memcpy (r->key, &msg->key, sizeof (struct GNUNET_HashCode)); } GNUNET_CONTAINER_DLL_insert (monitor_head, monitor_tail, r); GNUNET_SERVER_receive_done (client, GNUNET_OK); @@ -751,7 +860,7 @@ handle_dht_local_monitor_stop (void *cls, struct GNUNET_SERVER_Client *client, else { keys_match = (0 != ntohs(msg->filter_key) - && !memcmp(r->key, &msg->key, sizeof(GNUNET_HashCode))); + && !memcmp(r->key, &msg->key, sizeof(struct GNUNET_HashCode))); } if (find_active_client(client) == r->client && ntohl(msg->type) == r->type @@ -898,7 +1007,7 @@ struct ForwardReplyContext * if the result is mal-formed, GNUNET_NO */ static int -forward_reply (void *cls, const GNUNET_HashCode * key, void *value) +forward_reply (void *cls, const struct GNUNET_HashCode * key, void *value) { struct ForwardReplyContext *frc = cls; struct ClientQueryRecord *record = value; @@ -906,9 +1015,16 @@ forward_reply (void *cls, const GNUNET_HashCode * key, void *value) struct GNUNET_DHT_ClientResultMessage *reply; enum GNUNET_BLOCK_EvaluationResult eval; int do_free; - GNUNET_HashCode ch; + struct GNUNET_HashCode ch; unsigned int i; + if (LOG_ROUTE_DETAILS_STDERR) + { + fprintf (stderr, + "XDHT CLIENT-RESULT %s @ %u\n", + GNUNET_h2s (key), + getpid ()); + } if ((record->type != GNUNET_BLOCK_TYPE_ANY) && (record->type != frc->type)) { GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, @@ -922,7 +1038,7 @@ forward_reply (void *cls, const GNUNET_HashCode * key, void *value) } GNUNET_CRYPTO_hash (frc->data, frc->data_size, &ch); for (i = 0; i < record->seen_replies_count; i++) - if (0 == memcmp (&record->seen_replies[i], &ch, sizeof (GNUNET_HashCode))) + if (0 == memcmp (&record->seen_replies[i], &ch, sizeof (struct GNUNET_HashCode))) { GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Duplicate reply, not passing request for key %s to local client\n", @@ -962,6 +1078,8 @@ forward_reply (void *cls, const GNUNET_HashCode * key, void *value) case GNUNET_BLOCK_EVALUATION_REQUEST_INVALID: GNUNET_break (0); return GNUNET_NO; + case GNUNET_BLOCK_EVALUATION_RESULT_IRRELEVANT: + return GNUNET_YES; case GNUNET_BLOCK_EVALUATION_TYPE_NOT_SUPPORTED: GNUNET_log (GNUNET_ERROR_TYPE_WARNING, _("Unsupported block type (%u) in request!\n"), record->type); @@ -984,6 +1102,7 @@ forward_reply (void *cls, const GNUNET_HashCode * key, void *value) memcpy (pm, frc->pm, sizeof (struct PendingMessage) + ntohs (frc->pm->msg->size)); pm->next = pm->prev = NULL; + pm->msg = (struct GNUNET_MessageHeader *) &pm[1]; } GNUNET_STATISTICS_update (GDS_stats, gettext_noop ("# RESULTS queued for clients"), 1, @@ -1017,7 +1136,7 @@ forward_reply (void *cls, const GNUNET_HashCode * key, void *value) */ void GDS_CLIENTS_handle_reply (struct GNUNET_TIME_Absolute expiration, - const GNUNET_HashCode * key, + const struct GNUNET_HashCode *key, unsigned int get_path_length, const struct GNUNET_PeerIdentity *get_path, unsigned int put_path_length, @@ -1048,8 +1167,7 @@ GDS_CLIENTS_handle_reply (struct GNUNET_TIME_Absolute expiration, _("Could not pass reply to client, message too big!\n")); return; } - pm = (struct PendingMessage *) GNUNET_malloc (msize + - sizeof (struct PendingMessage)); + pm = GNUNET_malloc (msize + sizeof (struct PendingMessage)); reply = (struct GNUNET_DHT_ClientResultMessage *) &pm[1]; pm->msg = &reply->header; reply->header.size = htons ((uint16_t) msize); @@ -1104,7 +1222,7 @@ GDS_CLIENTS_process_get (uint32_t options, uint32_t desired_replication_level, unsigned int path_length, const struct GNUNET_PeerIdentity *path, - const GNUNET_HashCode * key) + const struct GNUNET_HashCode * key) { struct ClientMonitorRecord *m; struct ClientList **cl; @@ -1116,7 +1234,7 @@ GDS_CLIENTS_process_get (uint32_t options, { if ((GNUNET_BLOCK_TYPE_ANY == m->type || m->type == type) && (NULL == m->key || - memcmp (key, m->key, sizeof(GNUNET_HashCode)) == 0)) + memcmp (key, m->key, sizeof(struct GNUNET_HashCode)) == 0)) { struct PendingMessage *pm; struct GNUNET_DHT_MonitorGetMessage *mmsg; @@ -1135,7 +1253,7 @@ GDS_CLIENTS_process_get (uint32_t options, msize = path_length * sizeof (struct GNUNET_PeerIdentity); msize += sizeof (struct GNUNET_DHT_MonitorGetMessage); msize += sizeof (struct PendingMessage); - pm = (struct PendingMessage *) GNUNET_malloc (msize); + pm = GNUNET_malloc (msize); mmsg = (struct GNUNET_DHT_MonitorGetMessage *) &pm[1]; pm->msg = &mmsg->header; mmsg->header.size = htons (msize - sizeof (struct PendingMessage)); @@ -1145,7 +1263,7 @@ GDS_CLIENTS_process_get (uint32_t options, mmsg->hop_count = htonl(hop_count); mmsg->desired_replication_level = htonl(desired_replication_level); mmsg->get_path_length = htonl(path_length); - memcpy (&mmsg->key, key, sizeof (GNUNET_HashCode)); + memcpy (&mmsg->key, key, sizeof (struct GNUNET_HashCode)); msg_path = (struct GNUNET_PeerIdentity *) &mmsg[1]; if (path_length > 0) memcpy (msg_path, path, @@ -1178,7 +1296,7 @@ GDS_CLIENTS_process_get_resp (enum GNUNET_BLOCK_Type type, const struct GNUNET_PeerIdentity *put_path, unsigned int put_path_length, struct GNUNET_TIME_Absolute exp, - const GNUNET_HashCode * key, + const struct GNUNET_HashCode * key, const void *data, size_t size) { @@ -1192,7 +1310,7 @@ GDS_CLIENTS_process_get_resp (enum GNUNET_BLOCK_Type type, { if ((GNUNET_BLOCK_TYPE_ANY == m->type || m->type == type) && (NULL == m->key || - memcmp (key, m->key, sizeof(GNUNET_HashCode)) == 0)) + memcmp (key, m->key, sizeof(struct GNUNET_HashCode)) == 0)) { struct PendingMessage *pm; struct GNUNET_DHT_MonitorGetRespMessage *mmsg; @@ -1213,7 +1331,7 @@ GDS_CLIENTS_process_get_resp (enum GNUNET_BLOCK_Type type, * sizeof (struct GNUNET_PeerIdentity); msize += sizeof (struct GNUNET_DHT_MonitorGetRespMessage); msize += sizeof (struct PendingMessage); - pm = (struct PendingMessage *) GNUNET_malloc (msize); + pm = GNUNET_malloc (msize); mmsg = (struct GNUNET_DHT_MonitorGetRespMessage *) &pm[1]; pm->msg = (struct GNUNET_MessageHeader *) mmsg; mmsg->header.size = htons (msize - sizeof (struct PendingMessage)); @@ -1232,7 +1350,7 @@ GDS_CLIENTS_process_get_resp (enum GNUNET_BLOCK_Type type, memcpy (path, get_path, get_path_length * sizeof (struct GNUNET_PeerIdentity)); mmsg->expiration_time = GNUNET_TIME_absolute_hton(exp); - memcpy (&mmsg->key, key, sizeof (GNUNET_HashCode)); + memcpy (&mmsg->key, key, sizeof (struct GNUNET_HashCode)); if (size > 0) memcpy (&path[get_path_length], data, size); add_pending_message (m->client, pm); @@ -1265,7 +1383,7 @@ GDS_CLIENTS_process_put (uint32_t options, unsigned int path_length, const struct GNUNET_PeerIdentity *path, struct GNUNET_TIME_Absolute exp, - const GNUNET_HashCode * key, + const struct GNUNET_HashCode * key, const void *data, size_t size) { @@ -1279,7 +1397,7 @@ GDS_CLIENTS_process_put (uint32_t options, { if ((GNUNET_BLOCK_TYPE_ANY == m->type || m->type == type) && (NULL == m->key || - memcmp (key, m->key, sizeof(GNUNET_HashCode)) == 0)) + memcmp (key, m->key, sizeof(struct GNUNET_HashCode)) == 0)) { struct PendingMessage *pm; struct GNUNET_DHT_MonitorPutMessage *mmsg; @@ -1299,7 +1417,7 @@ GDS_CLIENTS_process_put (uint32_t options, msize += path_length * sizeof (struct GNUNET_PeerIdentity); msize += sizeof (struct GNUNET_DHT_MonitorPutMessage); msize += sizeof (struct PendingMessage); - pm = (struct PendingMessage *) GNUNET_malloc (msize); + pm = GNUNET_malloc (msize); mmsg = (struct GNUNET_DHT_MonitorPutMessage *) &pm[1]; pm->msg = (struct GNUNET_MessageHeader *) mmsg; mmsg->header.size = htons (msize - sizeof (struct PendingMessage)); @@ -1316,7 +1434,7 @@ GDS_CLIENTS_process_put (uint32_t options, path_length * sizeof (struct GNUNET_PeerIdentity)); } mmsg->expiration_time = GNUNET_TIME_absolute_hton(exp); - memcpy (&mmsg->key, key, sizeof (GNUNET_HashCode)); + memcpy (&mmsg->key, key, sizeof (struct GNUNET_HashCode)); if (size > 0) memcpy (&msg_path[path_length], data, size); add_pending_message (m->client, pm); @@ -1348,9 +1466,11 @@ GDS_CLIENTS_init (struct GNUNET_SERVER_Handle *server) {&handle_dht_local_monitor_stop, NULL, GNUNET_MESSAGE_TYPE_DHT_MONITOR_STOP, sizeof (struct GNUNET_DHT_MonitorStartStopMessage)}, + {&handle_dht_local_get_result_seen, NULL, + GNUNET_MESSAGE_TYPE_DHT_CLIENT_GET_RESULTS_KNOWN, 0}, {NULL, NULL, 0, 0} }; - forward_map = GNUNET_CONTAINER_multihashmap_create (1024); + forward_map = GNUNET_CONTAINER_multihashmap_create (1024, GNUNET_NO); retry_heap = GNUNET_CONTAINER_heap_create (GNUNET_CONTAINER_HEAP_ORDER_MIN); GNUNET_SERVER_add_handlers (server, plugin_handlers); GNUNET_SERVER_disconnect_notify (server, &handle_client_disconnect, NULL); diff --git a/src/dht/gnunet-service-dht_clients.h b/src/dht/gnunet-service-dht_clients.h index 9f3d2dd..f6d4253 100644 --- a/src/dht/gnunet-service-dht_clients.h +++ b/src/dht/gnunet-service-dht_clients.h @@ -47,7 +47,7 @@ */ void GDS_CLIENTS_handle_reply (struct GNUNET_TIME_Absolute expiration, - const GNUNET_HashCode * key, + const struct GNUNET_HashCode * key, unsigned int get_path_length, const struct GNUNET_PeerIdentity *get_path, unsigned int put_path_length, @@ -75,7 +75,7 @@ GDS_CLIENTS_process_get (uint32_t options, uint32_t desired_replication_level, unsigned int path_length, const struct GNUNET_PeerIdentity *path, - const GNUNET_HashCode * key); + const struct GNUNET_HashCode * key); /** * Check if some client is monitoring GET RESP messages and notify @@ -98,7 +98,7 @@ GDS_CLIENTS_process_get_resp (enum GNUNET_BLOCK_Type type, const struct GNUNET_PeerIdentity *put_path, unsigned int put_path_length, struct GNUNET_TIME_Absolute exp, - const GNUNET_HashCode * key, + const struct GNUNET_HashCode * key, const void *data, size_t size); @@ -125,7 +125,7 @@ GDS_CLIENTS_process_put (uint32_t options, unsigned int path_length, const struct GNUNET_PeerIdentity *path, struct GNUNET_TIME_Absolute exp, - const GNUNET_HashCode * key, + const struct GNUNET_HashCode * key, const void *data, size_t size); diff --git a/src/dht/gnunet-service-dht_datacache.c b/src/dht/gnunet-service-dht_datacache.c index 4d1dd6f..87c93f5 100644 --- a/src/dht/gnunet-service-dht_datacache.c +++ b/src/dht/gnunet-service-dht_datacache.c @@ -38,28 +38,6 @@ static struct GNUNET_DATACACHE_Handle *datacache; -/** - * Entry for inserting data into datacache from the DHT. - */ -struct DHTPutEntry -{ - /** - * Size of data. - */ - uint16_t data_size; - - /** - * Length of recorded path. - */ - uint16_t path_length; - - /* PATH ENTRIES */ - - /* PUT DATA */ - -}; - - /** * Handle a datum we've received from another peer. Cache if * possible. @@ -74,20 +52,13 @@ struct DHTPutEntry */ void GDS_DATACACHE_handle_put (struct GNUNET_TIME_Absolute expiration, - const GNUNET_HashCode * key, + const struct GNUNET_HashCode * key, unsigned int put_path_length, const struct GNUNET_PeerIdentity *put_path, enum GNUNET_BLOCK_Type type, size_t data_size, const void *data) { - size_t plen = - data_size + put_path_length * sizeof (struct GNUNET_PeerIdentity) + - sizeof (struct DHTPutEntry); - char buf[plen]; - struct DHTPutEntry *pe; - struct GNUNET_PeerIdentity *pp; - - if (datacache == NULL) + if (NULL == datacache) { GNUNET_log (GNUNET_ERROR_TYPE_WARNING, _("%s request received, but have no datacache!\n"), "PUT"); @@ -102,14 +73,9 @@ GDS_DATACACHE_handle_put (struct GNUNET_TIME_Absolute expiration, GNUNET_STATISTICS_update (GDS_stats, gettext_noop ("# ITEMS stored in datacache"), 1, GNUNET_NO); - pe = (struct DHTPutEntry *) buf; - pe->data_size = htons (data_size); - pe->path_length = htons ((uint16_t) put_path_length); - pp = (struct GNUNET_PeerIdentity *) &pe[1]; - memcpy (pp, put_path, put_path_length * sizeof (struct GNUNET_PeerIdentity)); - memcpy (&pp[put_path_length], data, data_size); - (void) GNUNET_DATACACHE_put (datacache, key, plen, (const char *) pe, type, - expiration); + (void) GNUNET_DATACACHE_put (datacache, key, + data_size, data, type, + expiration, put_path_length, put_path); } @@ -131,7 +97,7 @@ struct GetRequestContext /** * The key this request was about */ - GNUNET_HashCode key; + struct GNUNET_HashCode key; /** * Number of bytes in xquery. @@ -159,40 +125,26 @@ struct GetRequestContext * @param size the size of the data identified by key * @param data the actual data * @param type the type of the data - * + * @param put_path_length number of peers in 'put_path' + * @param put_path path the reply took on put * @return GNUNET_OK to continue iteration, anything else * to stop iteration. */ static int -datacache_get_iterator (void *cls, struct GNUNET_TIME_Absolute exp, - const GNUNET_HashCode * key, size_t size, - const char *data, enum GNUNET_BLOCK_Type type) +datacache_get_iterator (void *cls, + const struct GNUNET_HashCode * key, size_t size, + const char *data, enum GNUNET_BLOCK_Type type, + struct GNUNET_TIME_Absolute exp, + unsigned int put_path_length, + const struct GNUNET_PeerIdentity *put_path) { struct GetRequestContext *ctx = cls; - const struct DHTPutEntry *pe; - const struct GNUNET_PeerIdentity *pp; - const char *rdata; - size_t rdata_size; - uint16_t put_path_length; enum GNUNET_BLOCK_EvaluationResult eval; - pe = (const struct DHTPutEntry *) data; - put_path_length = ntohs (pe->path_length); - rdata_size = ntohs (pe->data_size); - - if (size != - sizeof (struct DHTPutEntry) + rdata_size + - (put_path_length * sizeof (struct GNUNET_PeerIdentity))) - { - GNUNET_break (0); - return GNUNET_OK; - } - pp = (const struct GNUNET_PeerIdentity *) &pe[1]; - rdata = (const char *) &pp[put_path_length]; eval = GNUNET_BLOCK_evaluate (GDS_block_context, type, key, ctx->reply_bf, ctx->reply_bf_mutator, ctx->xquery, - ctx->xquery_size, rdata, rdata_size); + ctx->xquery_size, data, size); GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Found reply for query %s in datacache, evaluation result is %d\n", GNUNET_h2s (key), (int) eval); @@ -206,11 +158,11 @@ datacache_get_iterator (void *cls, struct GNUNET_TIME_Absolute exp, gettext_noop ("# Good RESULTS found in datacache"), 1, GNUNET_NO); - GDS_CLIENTS_handle_reply (exp, key, 0, NULL, put_path_length, pp, type, - rdata_size, rdata); + GDS_CLIENTS_handle_reply (exp, key, 0, NULL, put_path_length, put_path, type, + size, data); /* forward to other peers */ - GDS_ROUTING_process (type, exp, key, put_path_length, pp, 0, NULL, rdata, - rdata_size); + GDS_ROUTING_process (type, exp, key, put_path_length, put_path, 0, NULL, data, + size); break; case GNUNET_BLOCK_EVALUATION_OK_DUPLICATE: GNUNET_STATISTICS_update (GDS_stats, @@ -224,6 +176,12 @@ datacache_get_iterator (void *cls, struct GNUNET_TIME_Absolute exp, ("# Invalid RESULTS found in datacache"), 1, GNUNET_NO); break; + case GNUNET_BLOCK_EVALUATION_RESULT_IRRELEVANT: + GNUNET_STATISTICS_update (GDS_stats, + gettext_noop + ("# Irrelevant RESULTS found in datacache"), 1, + GNUNET_NO); + break; case GNUNET_BLOCK_EVALUATION_REQUEST_VALID: GNUNET_break (0); break; @@ -255,7 +213,7 @@ datacache_get_iterator (void *cls, struct GNUNET_TIME_Absolute exp, * @return evaluation result for the local replies */ enum GNUNET_BLOCK_EvaluationResult -GDS_DATACACHE_handle_get (const GNUNET_HashCode * key, +GDS_DATACACHE_handle_get (const struct GNUNET_HashCode * key, enum GNUNET_BLOCK_Type type, const void *xquery, size_t xquery_size, struct GNUNET_CONTAINER_BloomFilter **reply_bf, diff --git a/src/dht/gnunet-service-dht_datacache.h b/src/dht/gnunet-service-dht_datacache.h index 926ad53..3889883 100644 --- a/src/dht/gnunet-service-dht_datacache.h +++ b/src/dht/gnunet-service-dht_datacache.h @@ -44,7 +44,7 @@ */ void GDS_DATACACHE_handle_put (struct GNUNET_TIME_Absolute expiration, - const GNUNET_HashCode * key, + const struct GNUNET_HashCode * key, unsigned int put_path_length, const struct GNUNET_PeerIdentity *put_path, enum GNUNET_BLOCK_Type type, size_t data_size, @@ -63,7 +63,7 @@ GDS_DATACACHE_handle_put (struct GNUNET_TIME_Absolute expiration, * @return evaluation result for the local replies */ enum GNUNET_BLOCK_EvaluationResult -GDS_DATACACHE_handle_get (const GNUNET_HashCode * key, +GDS_DATACACHE_handle_get (const struct GNUNET_HashCode * key, enum GNUNET_BLOCK_Type type, const void *xquery, size_t xquery_size, struct GNUNET_CONTAINER_BloomFilter **reply_bf, diff --git a/src/dht/gnunet-service-dht_hello.c b/src/dht/gnunet-service-dht_hello.c index b9cc450..19da79e 100644 --- a/src/dht/gnunet-service-dht_hello.c +++ b/src/dht/gnunet-service-dht_hello.c @@ -99,7 +99,7 @@ void GDS_HELLO_init () { pnc = GNUNET_PEERINFO_notify (GDS_cfg, &process_hello, NULL); - peer_to_hello = GNUNET_CONTAINER_multihashmap_create (256); + peer_to_hello = GNUNET_CONTAINER_multihashmap_create (256, GNUNET_NO); } @@ -107,7 +107,7 @@ GDS_HELLO_init () * Free memory occopied by the HELLO. */ static int -free_hello (void *cls, const GNUNET_HashCode * key, void *hello) +free_hello (void *cls, const struct GNUNET_HashCode * key, void *hello) { GNUNET_free (hello); return GNUNET_OK; diff --git a/src/dht/gnunet-service-dht_neighbours.c b/src/dht/gnunet-service-dht_neighbours.c index 083b499..4872b58 100644 --- a/src/dht/gnunet-service-dht_neighbours.c +++ b/src/dht/gnunet-service-dht_neighbours.c @@ -52,7 +52,7 @@ /** * How many buckets will we allow total. */ -#define MAX_BUCKETS sizeof (GNUNET_HashCode) * 8 +#define MAX_BUCKETS sizeof (struct GNUNET_HashCode) * 8 /** * What is the maximum number of peers in a given bucket. @@ -69,6 +69,11 @@ */ #define MAXIMUM_REPLICATION_LEVEL 16 +/** + * Maximum allowed number of pending messages per peer. + */ +#define MAXIMUM_PENDING_PER_PEER 64 + /** * How often to update our preference levels for peers in our routing tables. */ @@ -89,6 +94,17 @@ */ #define GET_TIMEOUT GNUNET_TIME_relative_multiply(GNUNET_TIME_UNIT_MINUTES, 2) +/** + * Should routing details be logged to stderr (for debugging)? + */ +#define LOG_ROUTE_DETAILS_STDERR GNUNET_NO + + +/** + * Hello address expiration + */ +extern struct GNUNET_TIME_Relative hello_expiration; + GNUNET_NETWORK_STRUCT_BEGIN @@ -140,7 +156,7 @@ struct PeerPutMessage /** * The key we are storing under. */ - GNUNET_HashCode key; + struct GNUNET_HashCode key; /* put path (if tracked) */ @@ -182,7 +198,7 @@ struct PeerResultMessage /** * The key of the corresponding GET request. */ - GNUNET_HashCode key; + struct GNUNET_HashCode key; /* put path (if tracked) */ @@ -241,7 +257,7 @@ struct PeerGetMessage /** * The key we are looking for. */ - GNUNET_HashCode key; + struct GNUNET_HashCode key; /* xquery */ @@ -301,8 +317,7 @@ struct PeerInfo struct PeerInfo *prev; /** - * Count of outstanding messages for peer. FIXME: NEEDED? - * FIXME: bound queue size!? + * Count of outstanding messages for peer. */ unsigned int pending_count; @@ -379,6 +394,11 @@ static unsigned int closest_bucket; */ static unsigned int newly_found_peers; +/** + * Option for testing that disables the 'connect' function of the DHT. + */ +static int disable_try_connect; + /** * The buckets. Array of size MAX_BUCKET_SIZE. Offset 0 means 0 bits matching. */ @@ -424,7 +444,7 @@ static struct GNUNET_ATS_PerformanceHandle *atsAPI; * on error (same hashcode) */ static int -find_bucket (const GNUNET_HashCode * hc) +find_bucket (const struct GNUNET_HashCode * hc) { unsigned int bits; @@ -518,10 +538,10 @@ struct BloomConstructorContext * @return GNUNET_YES (we should continue to iterate) */ static int -add_known_to_bloom (void *cls, const GNUNET_HashCode * key, void *value) +add_known_to_bloom (void *cls, const struct GNUNET_HashCode * key, void *value) { struct BloomConstructorContext *ctx = cls; - GNUNET_HashCode mh; + struct GNUNET_HashCode mh; GNUNET_BLOCK_mingle_hash (key, ctx->bf_mutator, &mh); GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, @@ -807,7 +827,7 @@ process_peer_queue (struct PeerInfo *peer) return; GNUNET_STATISTICS_update (GDS_stats, gettext_noop - ("# Bytes of bandwdith requested from core"), + ("# Bytes of bandwidth requested from core"), ntohs (pending->msg->size), GNUNET_NO); peer->th = GNUNET_CORE_notify_transmit_ready (coreAPI, GNUNET_YES, @@ -874,7 +894,7 @@ get_forward_count (uint32_t hop_count, uint32_t target_replication) * the two hash codes increases */ static unsigned int -get_distance (const GNUNET_HashCode * target, const GNUNET_HashCode * have) +get_distance (const struct GNUNET_HashCode * target, const struct GNUNET_HashCode * have) { unsigned int bucket; unsigned int msb; @@ -911,7 +931,7 @@ get_distance (const GNUNET_HashCode * target, const GNUNET_HashCode * have) * mismatching bit at 'bucket' */ lsb = 0; for (i = bucket + 1; - (i < sizeof (GNUNET_HashCode) * 8) && (i < bucket + 1 + 32 - 9); i++) + (i < sizeof (struct GNUNET_HashCode) * 8) && (i < bucket + 1 + 32 - 9); i++) { if (GNUNET_CRYPTO_hash_get_bit (target, i) != GNUNET_CRYPTO_hash_get_bit (have, i)) @@ -934,7 +954,7 @@ get_distance (const GNUNET_HashCode * target, const GNUNET_HashCode * have) * GNUNET_NO otherwise. */ static int -am_closest_peer (const GNUNET_HashCode * key, +am_closest_peer (const struct GNUNET_HashCode * key, const struct GNUNET_CONTAINER_BloomFilter *bloom) { int bits; @@ -943,7 +963,7 @@ am_closest_peer (const GNUNET_HashCode * key, int count; struct PeerInfo *pos; - if (0 == memcmp (&my_identity.hashPubKey, key, sizeof (GNUNET_HashCode))) + if (0 == memcmp (&my_identity.hashPubKey, key, sizeof (struct GNUNET_HashCode))) return GNUNET_YES; bucket_num = find_bucket (key); GNUNET_assert (bucket_num >= 0); @@ -989,7 +1009,7 @@ am_closest_peer (const GNUNET_HashCode * key, * @return Peer to route to, or NULL on error */ static struct PeerInfo * -select_peer (const GNUNET_HashCode * key, +select_peer (const struct GNUNET_HashCode * key, const struct GNUNET_CONTAINER_BloomFilter *bloom, uint32_t hops) { unsigned int bc; @@ -1081,19 +1101,16 @@ select_peer (const GNUNET_HashCode * key, count = 0; for (bc = 0; bc <= closest_bucket; bc++) { - pos = k_buckets[bc].head; - while ((pos != NULL) && (count < bucket_size)) + for (pos = k_buckets[bc].head; ((pos != NULL) && (count < bucket_size)); pos = pos->next) { if ((bloom != NULL) && (GNUNET_YES == GNUNET_CONTAINER_bloomfilter_test (bloom, &pos->id.hashPubKey))) { - pos = pos->next; continue; /* Ignore bloomfiltered peers */ } if (0 == selected--) return pos; - pos = pos->next; } } GNUNET_break (0); @@ -1115,7 +1132,7 @@ select_peer (const GNUNET_HashCode * key, * @return number of peers returned in 'targets'. */ static unsigned int -get_target_peers (const GNUNET_HashCode * key, +get_target_peers (const struct GNUNET_HashCode *key, struct GNUNET_CONTAINER_BloomFilter *bloom, uint32_t hop_count, uint32_t target_replication, struct PeerInfo ***targets) @@ -1126,7 +1143,7 @@ get_target_peers (const GNUNET_HashCode * key, struct PeerInfo *nxt; GNUNET_assert (NULL != bloom); - ret = get_forward_count (hop_count, target_replication); + ret = get_forward_count (hop_count, target_replication); if (ret == 0) { *targets = NULL; @@ -1155,6 +1172,11 @@ get_target_peers (const GNUNET_HashCode * key, return 0; } *targets = rtargets; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Forwarding query `%s' to %u peers (goal was %u peers)\n", + GNUNET_h2s (key), + off, + ret); return off; } @@ -1185,7 +1207,7 @@ GDS_NEIGHBOURS_handle_put (enum GNUNET_BLOCK_Type type, struct GNUNET_TIME_Absolute expiration_time, uint32_t hop_count, struct GNUNET_CONTAINER_BloomFilter *bf, - const GNUNET_HashCode * key, + const struct GNUNET_HashCode * key, unsigned int put_path_length, struct GNUNET_PeerIdentity *put_path, const void *data, size_t data_size) @@ -1238,6 +1260,12 @@ GDS_NEIGHBOURS_handle_put (enum GNUNET_BLOCK_Type type, for (i = 0; i < target_count; i++) { target = targets[i]; + if (target->pending_count >= MAXIMUM_PENDING_PER_PEER) + { + GNUNET_STATISTICS_update (GDS_stats, gettext_noop ("# P2P messages dropped due to full queue"), + 1, GNUNET_NO); + continue; /* skip */ + } GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Routing PUT for %s after %u hops to %s\n", GNUNET_h2s (key), (unsigned int) hop_count, GNUNET_i2s (&target->id)); @@ -1295,7 +1323,7 @@ void GDS_NEIGHBOURS_handle_get (enum GNUNET_BLOCK_Type type, enum GNUNET_DHT_RouteOption options, uint32_t desired_replication_level, - uint32_t hop_count, const GNUNET_HashCode * key, + uint32_t hop_count, const struct GNUNET_HashCode * key, const void *xquery, size_t xquery_size, const struct GNUNET_CONTAINER_BloomFilter *reply_bf, uint32_t reply_bf_mutator, @@ -1345,6 +1373,12 @@ GDS_NEIGHBOURS_handle_get (enum GNUNET_BLOCK_Type type, for (i = 0; i < target_count; i++) { target = targets[i]; + if (target->pending_count >= MAXIMUM_PENDING_PER_PEER) + { + GNUNET_STATISTICS_update (GDS_stats, gettext_noop ("# P2P messages dropped due to full queue"), + 1, GNUNET_NO); + continue; /* skip */ + } GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Routing GET for %s after %u hops to %s\n", GNUNET_h2s (key), (unsigned int) hop_count, GNUNET_i2s (&target->id)); @@ -1405,7 +1439,7 @@ void GDS_NEIGHBOURS_handle_reply (const struct GNUNET_PeerIdentity *target, enum GNUNET_BLOCK_Type type, struct GNUNET_TIME_Absolute expiration_time, - const GNUNET_HashCode * key, + const struct GNUNET_HashCode * key, unsigned int put_path_length, const struct GNUNET_PeerIdentity *put_path, unsigned int get_path_length, @@ -1438,6 +1472,14 @@ GDS_NEIGHBOURS_handle_reply (const struct GNUNET_PeerIdentity *target, /* peer disconnected in the meantime, drop reply */ return; } + if (pi->pending_count >= MAXIMUM_PENDING_PER_PEER) + { + /* skip */ + GNUNET_STATISTICS_update (GDS_stats, gettext_noop ("# P2P messages dropped due to full queue"), + 1, GNUNET_NO); + return; + } + GNUNET_STATISTICS_update (GDS_stats, gettext_noop ("# RESULT messages queued for transmission"), 1, @@ -1508,7 +1550,7 @@ handle_dht_p2p_put (void *cls, const struct GNUNET_PeerIdentity *peer, size_t payload_size; enum GNUNET_DHT_RouteOption options; struct GNUNET_CONTAINER_BloomFilter *bf; - GNUNET_HashCode test_key; + struct GNUNET_HashCode test_key; msize = ntohs (message->size); if (msize < sizeof (struct PeerPutMessage)) @@ -1541,7 +1583,7 @@ handle_dht_p2p_put (void *cls, const struct GNUNET_PeerIdentity *peer, &test_key)) { case GNUNET_YES: - if (0 != memcmp (&test_key, &put->key, sizeof (GNUNET_HashCode))) + if (0 != memcmp (&test_key, &put->key, sizeof (struct GNUNET_HashCode))) { GNUNET_break_op (0); return GNUNET_YES; @@ -1556,6 +1598,19 @@ handle_dht_p2p_put (void *cls, const struct GNUNET_PeerIdentity *peer, } GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "PUT for `%s' from %s\n", GNUNET_h2s (&put->key), GNUNET_i2s (peer)); + + if (LOG_ROUTE_DETAILS_STDERR) + { + char *tmp; + + tmp = GNUNET_strdup (GNUNET_i2s (&my_identity)); + fprintf (stderr, "XDHT PUT %s: %s(%u)<-%s\n", + GNUNET_h2s (&put->key), tmp, getpid (), + GNUNET_i2s (peer)); + GNUNET_free (tmp); + } + + bf = GNUNET_CONTAINER_bloomfilter_init (put->bloomfilter, DHT_BLOOM_SIZE, GNUNET_CONSTANTS_BLOOMFILTER_K); GNUNET_break_op (GNUNET_YES == @@ -1615,14 +1670,14 @@ handle_dht_p2p_put (void *cls, const struct GNUNET_PeerIdentity *peer, */ static void handle_find_peer (const struct GNUNET_PeerIdentity *sender, - const GNUNET_HashCode * key, + const struct GNUNET_HashCode * key, struct GNUNET_CONTAINER_BloomFilter *bf, uint32_t bf_mutator) { int bucket_idx; struct PeerBucket *bucket; struct PeerInfo *peer; unsigned int choice; - GNUNET_HashCode mhash; + struct GNUNET_HashCode mhash; const struct GNUNET_HELLO_Message *hello; /* first, check about our own HELLO */ @@ -1634,7 +1689,7 @@ handle_find_peer (const struct GNUNET_PeerIdentity *sender, { GDS_NEIGHBOURS_handle_reply (sender, GNUNET_BLOCK_TYPE_DHT_HELLO, GNUNET_TIME_relative_to_absolute - (GNUNET_CONSTANTS_HELLO_ADDRESS_EXPIRATION), + (hello_expiration), key, 0, NULL, 0, NULL, GDS_my_hello, GNUNET_HELLO_size ((const struct GNUNET_HELLO_Message *) @@ -1657,7 +1712,7 @@ handle_find_peer (const struct GNUNET_PeerIdentity *sender, } /* then, also consider sending a random HELLO from the closest bucket */ - if (0 == memcmp (&my_identity.hashPubKey, key, sizeof (GNUNET_HashCode))) + if (0 == memcmp (&my_identity.hashPubKey, key, sizeof (struct GNUNET_HashCode))) bucket_idx = closest_bucket; else bucket_idx = GNUNET_MIN (closest_bucket, find_bucket (key)); @@ -1803,6 +1858,19 @@ handle_dht_p2p_get (void *cls, const struct GNUNET_PeerIdentity *peer, 1, GNUNET_NO); } + if (LOG_ROUTE_DETAILS_STDERR) + { + char *tmp; + + tmp = GNUNET_strdup (GNUNET_i2s (&my_identity)); + fprintf (stderr, "XDHT GET %s: %s(%u)<-%s\n", + GNUNET_h2s (&get->key), tmp, getpid(), + GNUNET_i2s (peer)); + GNUNET_free (tmp); + } + + + /* FIXME Path */ GDS_CLIENTS_process_get (options, type, @@ -1917,12 +1985,27 @@ handle_dht_p2p_result (void *cls, const struct GNUNET_PeerIdentity *peer, if (NULL != GDS_transport_handle) { GNUNET_TRANSPORT_offer_hello (GDS_transport_handle, h, NULL, NULL); - GNUNET_TRANSPORT_try_connect (GDS_transport_handle, &pid); + if (GNUNET_YES != + disable_try_connect) + GNUNET_TRANSPORT_try_connect (GDS_transport_handle, &pid, NULL, NULL); /*FIXME TRY_CONNECT change */ } } } } + + if (LOG_ROUTE_DETAILS_STDERR) + { + char *tmp; + + tmp = GNUNET_strdup (GNUNET_i2s (&my_identity)); + fprintf (stderr, + "XDHT RESULT %s: %s(%u)<-%s\n", + GNUNET_h2s (&prm->key), tmp, + getpid(), GNUNET_i2s (peer)); + GNUNET_free (tmp); + } + /* append 'peer' to 'get_path' */ { struct GNUNET_PeerIdentity xget_path[get_path_length + 1]; @@ -1974,18 +2057,20 @@ GDS_NEIGHBOURS_init () }; unsigned long long temp_config_num; + disable_try_connect + = GNUNET_CONFIGURATION_get_value_yesno (GDS_cfg, "DHT", "DISABLE_TRY_CONNECT"); if (GNUNET_OK == GNUNET_CONFIGURATION_get_value_number (GDS_cfg, "DHT", "bucket_size", &temp_config_num)) bucket_size = (unsigned int) temp_config_num; atsAPI = GNUNET_ATS_performance_init (GDS_cfg, NULL, NULL); coreAPI = - GNUNET_CORE_connect (GDS_cfg, 1, NULL, &core_init, &handle_core_connect, + GNUNET_CORE_connect (GDS_cfg, NULL, &core_init, &handle_core_connect, &handle_core_disconnect, NULL, GNUNET_NO, NULL, GNUNET_NO, core_handlers); if (coreAPI == NULL) return GNUNET_SYSERR; - all_known_peers = GNUNET_CONTAINER_multihashmap_create (256); + all_known_peers = GNUNET_CONTAINER_multihashmap_create (256, GNUNET_NO); return GNUNET_OK; } diff --git a/src/dht/gnunet-service-dht_neighbours.h b/src/dht/gnunet-service-dht_neighbours.h index 3297638..b3b33e3 100644 --- a/src/dht/gnunet-service-dht_neighbours.h +++ b/src/dht/gnunet-service-dht_neighbours.h @@ -57,7 +57,7 @@ GDS_NEIGHBOURS_handle_put (enum GNUNET_BLOCK_Type type, struct GNUNET_TIME_Absolute expiration_time, uint32_t hop_count, struct GNUNET_CONTAINER_BloomFilter *bf, - const GNUNET_HashCode * key, + const struct GNUNET_HashCode * key, unsigned int put_path_length, struct GNUNET_PeerIdentity *put_path, const void *data, size_t data_size); @@ -84,7 +84,7 @@ void GDS_NEIGHBOURS_handle_get (enum GNUNET_BLOCK_Type type, enum GNUNET_DHT_RouteOption options, uint32_t desired_replication_level, - uint32_t hop_count, const GNUNET_HashCode * key, + uint32_t hop_count, const struct GNUNET_HashCode * key, const void *xquery, size_t xquery_size, const struct GNUNET_CONTAINER_BloomFilter *reply_bf, uint32_t reply_bf_mutator, @@ -111,7 +111,7 @@ void GDS_NEIGHBOURS_handle_reply (const struct GNUNET_PeerIdentity *target, enum GNUNET_BLOCK_Type type, struct GNUNET_TIME_Absolute expiration_time, - const GNUNET_HashCode * key, + const struct GNUNET_HashCode * key, unsigned int put_path_length, const struct GNUNET_PeerIdentity *put_path, unsigned int get_path_length, diff --git a/src/dht/gnunet-service-dht_nse.c b/src/dht/gnunet-service-dht_nse.c index 7779989..11c02e1 100644 --- a/src/dht/gnunet-service-dht_nse.c +++ b/src/dht/gnunet-service-dht_nse.c @@ -81,6 +81,21 @@ GDS_NSE_get () void GDS_NSE_init () { + unsigned long long hops; + + if ( (GNUNET_YES == + GNUNET_CONFIGURATION_have_value (GDS_cfg, + "dht", + "FORCE_NSE")) && + (GNUNET_OK == + GNUNET_CONFIGURATION_get_value_number (GDS_cfg, + "dht", + "FORCE_NSE", + &hops)) ) + { + log_of_network_size_estimate = (double) hops; + return; + } nse = GNUNET_NSE_connect (GDS_cfg, &update_network_size_estimate, NULL); } diff --git a/src/dht/gnunet-service-dht_routing.c b/src/dht/gnunet-service-dht_routing.c index 013d856..2d0d778 100644 --- a/src/dht/gnunet-service-dht_routing.c +++ b/src/dht/gnunet-service-dht_routing.c @@ -50,7 +50,7 @@ struct RecentRequest /** * Key of this request. */ - GNUNET_HashCode key; + struct GNUNET_HashCode key; /** * Position of this node in the min heap. @@ -160,15 +160,15 @@ struct ProcessContext * GNUNET_SYSERR if the result is malformed or type unsupported */ static int -process (void *cls, const GNUNET_HashCode * key, void *value) +process (void *cls, const struct GNUNET_HashCode * key, void *value) { struct ProcessContext *pc = cls; struct RecentRequest *rr = value; enum GNUNET_BLOCK_EvaluationResult eval; unsigned int gpl; unsigned int ppl; - GNUNET_HashCode hc; - const GNUNET_HashCode *eval_key; + struct GNUNET_HashCode hc; + const struct GNUNET_HashCode *eval_key; if ((rr->type != GNUNET_BLOCK_TYPE_ANY) && (rr->type != pc->type)) return GNUNET_OK; /* type missmatch */ @@ -226,6 +226,12 @@ process (void *cls, const GNUNET_HashCode * key, void *value) ("# Invalid REPLIES matched against routing table"), 1, GNUNET_NO); return GNUNET_SYSERR; + case GNUNET_BLOCK_EVALUATION_RESULT_IRRELEVANT: + GNUNET_STATISTICS_update (GDS_stats, + gettext_noop + ("# Irrelevant REPLIES matched against routing table"), + 1, GNUNET_NO); + return GNUNET_OK; case GNUNET_BLOCK_EVALUATION_REQUEST_VALID: GNUNET_break (0); return GNUNET_OK; @@ -266,7 +272,7 @@ process (void *cls, const GNUNET_HashCode * key, void *value) void GDS_ROUTING_process (enum GNUNET_BLOCK_Type type, struct GNUNET_TIME_Absolute expiration_time, - const GNUNET_HashCode * key, unsigned int put_path_length, + const struct GNUNET_HashCode * key, unsigned int put_path_length, const struct GNUNET_PeerIdentity *put_path, unsigned int get_path_length, const struct GNUNET_PeerIdentity *get_path, @@ -322,6 +328,48 @@ expire_oldest_entry () } +/** + * Try to combine multiple recent requests for the same value + * (if they come from the same peer). + * + * @param cls the new 'struct RecentRequest' (to discard upon successful combination) + * @param key the query + * @param value the existing 'struct RecentRequest' (to update upon successful combination) + * @return GNUNET_OK (continue to iterate), + * GNUNET_SYSERR if the request was successfully combined + */ +static int +try_combine_recent (void *cls, const struct GNUNET_HashCode * key, void *value) +{ + struct RecentRequest *in = cls; + struct RecentRequest *rr = value; + + if ( (0 != memcmp (&in->peer, + &rr->peer, + sizeof (struct GNUNET_PeerIdentity))) || + (in->type != rr->type) || + (in->xquery_size != rr->xquery_size) || + (0 != memcmp (in->xquery, + rr->xquery, + in->xquery_size)) ) + return GNUNET_OK; + if (in->reply_bf_mutator != rr->reply_bf_mutator) + { + rr->reply_bf_mutator = in->reply_bf_mutator; + GNUNET_CONTAINER_bloomfilter_free (rr->reply_bf); + rr->reply_bf = in->reply_bf; + } + else + { + GNUNET_CONTAINER_bloomfilter_or2 (rr->reply_bf, + in->reply_bf, + GNUNET_CONTAINER_bloomfilter_get_size (in->reply_bf)); + GNUNET_CONTAINER_bloomfilter_free (in->reply_bf); + } + GNUNET_free (in); + return GNUNET_SYSERR; +} + /** * Add a new entry to our routing table. @@ -339,7 +387,7 @@ void GDS_ROUTING_add (const struct GNUNET_PeerIdentity *sender, enum GNUNET_BLOCK_Type type, enum GNUNET_DHT_RouteOption options, - const GNUNET_HashCode * key, const void *xquery, + const struct GNUNET_HashCode * key, const void *xquery, size_t xquery_size, const struct GNUNET_CONTAINER_BloomFilter *reply_bf, uint32_t reply_bf_mutator) @@ -354,15 +402,26 @@ GDS_ROUTING_add (const struct GNUNET_PeerIdentity *sender, recent_req = GNUNET_malloc (sizeof (struct RecentRequest) + xquery_size); recent_req->peer = *sender; recent_req->key = *key; - recent_req->heap_node = - GNUNET_CONTAINER_heap_insert (recent_heap, recent_req, - GNUNET_TIME_absolute_get ().abs_value); recent_req->reply_bf = GNUNET_CONTAINER_bloomfilter_copy (reply_bf); recent_req->type = type; recent_req->options = options; recent_req->xquery = &recent_req[1]; + memcpy (&recent_req[1], xquery, xquery_size); recent_req->xquery_size = xquery_size; recent_req->reply_bf_mutator = reply_bf_mutator; + if (GNUNET_SYSERR == + GNUNET_CONTAINER_multihashmap_get_multiple (recent_map, key, + &try_combine_recent, recent_req)) + { + GNUNET_STATISTICS_update (GDS_stats, + gettext_noop + ("# DHT requests combined"), + 1, GNUNET_NO); + return; + } + recent_req->heap_node = + GNUNET_CONTAINER_heap_insert (recent_heap, recent_req, + GNUNET_TIME_absolute_get ().abs_value); GNUNET_CONTAINER_multihashmap_put (recent_map, key, recent_req, GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE); @@ -377,7 +436,7 @@ void GDS_ROUTING_init () { recent_heap = GNUNET_CONTAINER_heap_create (GNUNET_CONTAINER_HEAP_ORDER_MIN); - recent_map = GNUNET_CONTAINER_multihashmap_create (DHT_MAX_RECENT * 4 / 3); + recent_map = GNUNET_CONTAINER_multihashmap_create (DHT_MAX_RECENT * 4 / 3, GNUNET_NO); } diff --git a/src/dht/gnunet-service-dht_routing.h b/src/dht/gnunet-service-dht_routing.h index 9b12c71..56326aa 100644 --- a/src/dht/gnunet-service-dht_routing.h +++ b/src/dht/gnunet-service-dht_routing.h @@ -51,7 +51,7 @@ void GDS_ROUTING_process (enum GNUNET_BLOCK_Type type, struct GNUNET_TIME_Absolute expiration_time, - const GNUNET_HashCode * key, unsigned int put_path_length, + const struct GNUNET_HashCode * key, unsigned int put_path_length, const struct GNUNET_PeerIdentity *put_path, unsigned int get_path_length, const struct GNUNET_PeerIdentity *get_path, @@ -74,7 +74,7 @@ void GDS_ROUTING_add (const struct GNUNET_PeerIdentity *sender, enum GNUNET_BLOCK_Type type, enum GNUNET_DHT_RouteOption options, - const GNUNET_HashCode * key, const void *xquery, + const struct GNUNET_HashCode * key, const void *xquery, size_t xquery_size, const struct GNUNET_CONTAINER_BloomFilter *reply_bf, uint32_t reply_bf_mutator); diff --git a/src/dht/multipeer_topo.dat b/src/dht/multipeer_topo.dat deleted file mode 100644 index 1233e6b..0000000 --- a/src/dht/multipeer_topo.dat +++ /dev/null @@ -1,31 +0,0 @@ -10 -1:2 -2:3 -3:4 -4:5 -5:6 -6:7 -7:8 -8:9 -9:10 -10:1 -4:2 -5:3 -6:4 -7:5 -8:6 -9:7 -10:8 -1:9 -2:10 -3:1 -6:2 -7:3 -8:4 -9:5 -10:6 -1:7 -2:8 -3:9 -4:10 -5:1 diff --git a/src/dht/plugin_block_dht.c b/src/dht/plugin_block_dht.c index 3c016ae..ac4732c 100644 --- a/src/dht/plugin_block_dht.c +++ b/src/dht/plugin_block_dht.c @@ -51,13 +51,13 @@ */ static enum GNUNET_BLOCK_EvaluationResult block_plugin_dht_evaluate (void *cls, enum GNUNET_BLOCK_Type type, - const GNUNET_HashCode * query, + const struct GNUNET_HashCode * query, struct GNUNET_CONTAINER_BloomFilter **bf, int32_t bf_mutator, const void *xquery, size_t xquery_size, const void *reply_block, size_t reply_block_size) { - GNUNET_HashCode mhash; + struct GNUNET_HashCode mhash; const struct GNUNET_HELLO_Message *hello; struct GNUNET_PeerIdentity pid; const struct GNUNET_MessageHeader *msg; @@ -122,7 +122,7 @@ block_plugin_dht_evaluate (void *cls, enum GNUNET_BLOCK_Type type, static int block_plugin_dht_get_key (void *cls, enum GNUNET_BLOCK_Type type, const void *block, size_t block_size, - GNUNET_HashCode * key) + struct GNUNET_HashCode * key) { const struct GNUNET_MessageHeader *msg; const struct GNUNET_HELLO_Message *hello; diff --git a/src/dht/test_dht_2dtorus.conf b/src/dht/test_dht_2dtorus.conf index d7a3d8a..29188cb 100644 --- a/src/dht/test_dht_2dtorus.conf +++ b/src/dht/test_dht_2dtorus.conf @@ -1,35 +1,15 @@ [PATHS] -SERVICEHOME = /tmp/test_dht_topo/ -DEFAULTCONFIG = test_dht_2dtours.conf +SERVICEHOME = /tmp/test_dht_2dtorus/ [arm] -PORT = 10010 DEFAULTSERVICES = core dht -#DEBUG = YES - -[statistics] -AUTOSTART = YES -PORT = 10000 - -[dht] -DEBUG = NO -AUTOSTART = YES -ACCEPT_FROM6 = ::1; -ACCEPT_FROM = 127.0.0.1; -HOSTNAME = localhost -PORT = 10001 [dns] AUTOSTART = NO -PORT = 10011 - -[transport] -PORT = 10002 -AUTOSTART = YES [nat] DISABLEV6 = YES -BINDTO = 127.0.0.1 +RETURN_LOCAL_ADDRESSES = YES ENABLE_UPNP = NO BEHIND_NAT = NO ALLOW_NAT = NO @@ -40,48 +20,18 @@ EXTERNAL_ADDRESS = 127.0.0.1 WAN_QUOTA_IN = 1 GB WAN_QUOTA_OUT = 1 GB -[core] -AUTOSTART = YES -PORT = 10003 - -[peerinfo] -AUTOSTART = YES -PORT = 10004 - [testing] -NUM_PEERS = 16 WEAKRANDOM = YES -TOPOLOGY = NONE -CONNECT_TOPOLOGY = 2D_TORUS -BLACKLIST_TOPOLOGY = 2D_TORUS -#TOPOLOGY_FILE = small.dat -#CONNECT_TOPOLOGY = ERDOS_RENYI -#CONNECT_TOPOLOGY_OPTION = CONNECT_MINIMUM -#CONNECT_TOPOLOGY_OPTION_MODIFIER = 25 -#PERCENTAGE = 3 -#PROBABILITY = .1 -F2F = NO -CONNECT_TIMEOUT = 60 s -CONNECT_ATTEMPTS = 3 -DEBUG = YES -HOSTKEYSFILE = ../../contrib/testing_hostkeys.dat -MAX_CONCURRENT_SSH = 20 -USE_PROGRESSBARS = YES -PEERGROUP_TIMEOUT = 2400 s -TOPOLOGY_OUTPUT_FILE = 2dtorus_topo_initial -MAX_OUTSTANDING_CONNECTIONS = 75 -#SINGLE_PEERINFO_PER_HOST = YES -#NUM_PEERINFO_PER_HOST = 10 -#SINGLE_STATISTICS_PER_HOST = YES -#NUM_STATISTICS_PER_HOST = 10 -DELETE_FILES = YES - -[test_dht_topo] -CONNECTION_LIMIT = 20 -#DATA_OUTPUT_FILE=data_output +[testbed] +OVERLAY_TOPOLOGY = 2D_TORUS [nse] WORKDELAY = 500 ms INTERVAL = 60 s WORKBITS = 0 + +[vpn] +AUTOSTART = NO + + diff --git a/src/dht/test_dht_api.c b/src/dht/test_dht_api.c index 000ad33..b1c39e8 100644 --- a/src/dht/test_dht_api.c +++ b/src/dht/test_dht_api.c @@ -25,20 +25,11 @@ * */ #include "platform.h" -#include "gnunet_common.h" +#include "gnunet_util_lib.h" #include "gnunet_hello_lib.h" -#include "gnunet_getopt_lib.h" -#include "gnunet_os_lib.h" -#include "gnunet_program_lib.h" -#include "gnunet_scheduler_lib.h" +#include "gnunet_testing_lib.h" #include "gnunet_dht_service.h" -#include "gnunet_hello_lib.h" - -#define VERBOSE GNUNET_NO - -#define VERBOSE_ARM GNUNET_NO -#define START_ARM GNUNET_YES /** * How long until we really give up on a particular testcase portion? @@ -52,6 +43,7 @@ #define MTYPE 12345 + struct RetryContext { /** @@ -64,11 +56,6 @@ struct RetryContext */ struct GNUNET_TIME_Relative next_timeout; - /** - * The context of the peer we are dealing with. - */ - struct PeerContext *peer_ctx; - /** * The task identifier of the retry task, so it can be cancelled. */ @@ -76,26 +63,18 @@ struct RetryContext }; -struct PeerContext -{ - struct GNUNET_CONFIGURATION_Handle *cfg; - struct GNUNET_DHT_Handle *dht_handle; - struct GNUNET_PeerIdentity id; - struct GNUNET_DHT_GetHandle *get_handle; -#if START_ARM - struct GNUNET_OS_Process *arm_proc; -#endif -}; -static struct PeerContext p1; +static struct GNUNET_DHT_Handle *dht_handle; -struct RetryContext retry_context; +static struct GNUNET_DHT_GetHandle *get_handle; +struct RetryContext retry_context; -static int ok; +static int ok = 1; static GNUNET_SCHEDULER_TaskIdentifier die_task; + #if VERBOSE #define OKPP do { ok++; FPRINTF (stderr, "Now at stage %u at %s:%u\n", ok, __FILE__, __LINE__); } while (0) #else @@ -108,43 +87,28 @@ end (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { GNUNET_SCHEDULER_cancel (die_task); die_task = GNUNET_SCHEDULER_NO_TASK; - GNUNET_DHT_disconnect (p1.dht_handle); + GNUNET_DHT_disconnect (dht_handle); + dht_handle = NULL; GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "DHT disconnected, returning success!\n"); ok = 0; } -static void -stop_arm (struct PeerContext *p) -{ -#if START_ARM - if (0 != GNUNET_OS_process_kill (p->arm_proc, SIGTERM)) - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); - GNUNET_OS_process_wait (p->arm_proc); - GNUNET_OS_process_destroy (p->arm_proc); - p->arm_proc = NULL; -#endif - GNUNET_CONFIGURATION_destroy (p->cfg); -} - static void end_badly () { /* do work here */ -#if VERBOSE FPRINTF (stderr, "%s", "Ending on an unhappy note.\n"); -#endif - - if ((retry_context.peer_ctx != NULL) && - (retry_context.peer_ctx->get_handle != NULL)) + if (get_handle != NULL) { GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stopping get request!\n"); - GNUNET_DHT_get_stop (retry_context.peer_ctx->get_handle); + GNUNET_DHT_get_stop (get_handle); } if (retry_context.retry_task != GNUNET_SCHEDULER_NO_TASK) GNUNET_SCHEDULER_cancel (retry_context.retry_task); - GNUNET_DHT_disconnect (p1.dht_handle); + GNUNET_DHT_disconnect (dht_handle); + dht_handle = NULL; ok = 1; } @@ -158,8 +122,6 @@ end_badly () static void test_get_stop (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { - struct PeerContext *peer = cls; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Called test_get_stop!\n"); if ((tc->reason & GNUNET_SCHEDULER_REASON_TIMEOUT) != 0) { @@ -168,16 +130,16 @@ test_get_stop (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) die_task = GNUNET_SCHEDULER_add_now (&end_badly, NULL); return; } - GNUNET_assert (peer->dht_handle != NULL); - GNUNET_DHT_get_stop (peer->get_handle); - peer->get_handle = NULL; - GNUNET_SCHEDULER_add_now (&end, &p1); + GNUNET_assert (dht_handle != NULL); + GNUNET_DHT_get_stop (get_handle); + get_handle = NULL; + GNUNET_SCHEDULER_add_now (&end, NULL); } static void test_get_iterator (void *cls, struct GNUNET_TIME_Absolute exp, - const GNUNET_HashCode * key, + const struct GNUNET_HashCode * key, const struct GNUNET_PeerIdentity *get_path, unsigned int get_path_length, const struct GNUNET_PeerIdentity *put_path, @@ -186,11 +148,11 @@ test_get_iterator (void *cls, struct GNUNET_TIME_Absolute exp, { GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test_get_iterator called (we got a result), stopping get request!\n"); - - GNUNET_SCHEDULER_add_continuation (&test_get_stop, &p1, + GNUNET_SCHEDULER_add_continuation (&test_get_stop, NULL, GNUNET_SCHEDULER_REASON_PREREQ_DONE); } + /** * Signature of the main function of a task. * @@ -200,140 +162,69 @@ test_get_iterator (void *cls, struct GNUNET_TIME_Absolute exp, static void test_get (void *cls, int success) { - struct PeerContext *peer = cls; - GNUNET_HashCode hash; + struct GNUNET_HashCode hash; - memset (&hash, 42, sizeof (GNUNET_HashCode)); + memset (&hash, 42, sizeof (struct GNUNET_HashCode)); GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Called test_get!\n"); - - GNUNET_assert (peer->dht_handle != NULL); + GNUNET_assert (dht_handle != NULL); retry_context.real_timeout = GNUNET_TIME_relative_to_absolute (TOTAL_TIMEOUT); retry_context.next_timeout = BASE_TIMEOUT; - peer->get_handle = - GNUNET_DHT_get_start (peer->dht_handle, + get_handle = + GNUNET_DHT_get_start (dht_handle, GNUNET_BLOCK_TYPE_TEST, &hash, 1, GNUNET_DHT_RO_NONE, NULL, 0, &test_get_iterator, NULL); - if (peer->get_handle == NULL) + if (get_handle == NULL) { GNUNET_break (0); GNUNET_SCHEDULER_cancel (die_task); - die_task = GNUNET_SCHEDULER_add_now (&end_badly, &p1); + die_task = GNUNET_SCHEDULER_add_now (&end_badly, NULL); return; } - - retry_context.peer_ctx = peer; } -/** - * Signature of the main function of a task. - * - * @param cls closure - * @param tc context information (why was this task triggered now) - */ + static void -test_put (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) { - struct PeerContext *peer = cls; - GNUNET_HashCode hash; + struct GNUNET_HashCode hash; char *data; size_t data_size = 42; - memset (&hash, 42, sizeof (GNUNET_HashCode)); - data = GNUNET_malloc (data_size); - memset (data, 43, data_size); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Called test_put!\n"); - peer->dht_handle = GNUNET_DHT_connect (peer->cfg, 100); - - GNUNET_assert (peer->dht_handle != NULL); - - GNUNET_DHT_put (peer->dht_handle, &hash, 1, GNUNET_DHT_RO_NONE, - GNUNET_BLOCK_TYPE_TEST, data_size, data, - GNUNET_TIME_relative_to_absolute (TOTAL_TIMEOUT), - TOTAL_TIMEOUT, &test_get, &p1); - GNUNET_free (data); -} - -static void -setup_peer (struct PeerContext *p, const char *cfgname) -{ - p->cfg = GNUNET_CONFIGURATION_create (); -#if START_ARM - p->arm_proc = - GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-arm", - "gnunet-service-arm", -#if VERBOSE_ARM - "-L", "DEBUG", -#endif - "-c", cfgname, NULL); -#endif - GNUNET_assert (GNUNET_OK == GNUNET_CONFIGURATION_load (p->cfg, cfgname)); - -} - -static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) -{ GNUNET_assert (ok == 1); OKPP; - die_task = GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MINUTES, 1), &end_badly, NULL); - setup_peer (&p1, "test_dht_api_peer1.conf"); - - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply - (GNUNET_TIME_UNIT_SECONDS, 1), &test_put, &p1); -} - -static int -check () -{ - - char *const argv[] = { "test-dht-api", - "-c", - "test_dht_api_data.conf", -#if VERBOSE - "-L", "DEBUG", -#endif - NULL - }; - - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - - ok = 1; - GNUNET_PROGRAM_run ((sizeof (argv) / sizeof (char *)) - 1, argv, - "test-dht-api", "nohelp", options, &run, &ok); - stop_arm (&p1); - return ok; + memset (&hash, 42, sizeof (struct GNUNET_HashCode)); + data = GNUNET_malloc (data_size); + memset (data, 43, data_size); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Called test_put!\n"); + dht_handle = GNUNET_DHT_connect (cfg, 100); + GNUNET_assert (dht_handle != NULL); + GNUNET_DHT_put (dht_handle, &hash, 1, GNUNET_DHT_RO_NONE, + GNUNET_BLOCK_TYPE_TEST, data_size, data, + GNUNET_TIME_relative_to_absolute (TOTAL_TIMEOUT), + TOTAL_TIMEOUT, &test_get, NULL); + GNUNET_free (data); } int main (int argc, char *argv[]) { - int ret; - - GNUNET_log_setup ("test-dht-api", -#if VERBOSE - "DEBUG", -#else - "WARNING", -#endif - NULL); - ret = check (); - - GNUNET_DISK_directory_remove ("/tmp/test-gnunetd-dht-peer-1"); - - return ret; + if (0 != GNUNET_TESTING_peer_run ("test-dht-api", + "test_dht_api_data.conf", + &run, NULL)) + return 1; + return ok; } /* end of test_dht_api.c */ diff --git a/src/dht/test_dht_api_data.conf b/src/dht/test_dht_api_data.conf index 032416c..58e509c 100644 --- a/src/dht/test_dht_api_data.conf +++ b/src/dht/test_dht_api_data.conf @@ -1,6 +1,5 @@ [PATHS] SERVICEHOME = /tmp/test-dht-api/ -DEFAULTCONFIG = test_dht_api_data.conf [fs] AUTOSTART = NO @@ -28,7 +27,6 @@ WAN_QUOTA_OUT = 1 GB PORT = 2092 [dht] -DEBUG = NO PORT = 12370 [block] @@ -36,7 +34,6 @@ plugins = dht test [transport] plugins = tcp -DEBUG = NO NEIGHBOUR_LIMIT = 50 PORT = 2091 @@ -59,7 +56,9 @@ PORT = 2094 [TESTING] WEAKRANDOM = NO -HOSTKEYSFILE = ../../contrib/testing_hostkeys.dat + +[testing_old] +HOSTKEYSFILE = ${DATADIR}/testing_hostkeys.dat [gnunetd] HOSTKEY = $SERVICEHOME/.hostkey @@ -84,3 +83,7 @@ AUTOSTART = NO AUTOSTART = NO +[vpn] +AUTOSTART=NO + + diff --git a/src/dht/test_dht_api_peer1.conf b/src/dht/test_dht_api_peer1.conf index d9db7c4..fd2ee80 100644 --- a/src/dht/test_dht_api_peer1.conf +++ b/src/dht/test_dht_api_peer1.conf @@ -5,7 +5,6 @@ AUTOSTART = NO AUTOSTART = NO [dht] -DEBUG = NO AUTOSTART = YES ACCEPT_FROM6 = ::1; ACCEPT_FROM = 127.0.0.1; @@ -22,7 +21,6 @@ DATABASE = sqlite [transport] PLUGINS = tcp -DEBUG = NO ACCEPT_FROM6 = ::1; ACCEPT_FROM = 127.0.0.1; NEIGHBOUR_LIMIT = 50 @@ -38,7 +36,6 @@ PORT = 12092 [arm] DEFAULTSERVICES = core PORT = 12366 -DEBUG = NO [transport-tcp] TIMEOUT = 300 s @@ -52,7 +49,6 @@ WEAKRANDOM = YES HOSTKEY = $SERVICEHOME/.hostkey [PATHS] -DEFAULTCONFIG = test_dht_api_peer1.conf SERVICEHOME = /tmp/test-gnunetd-dht-peer-1/ @@ -74,3 +70,7 @@ AUTOSTART = NO AUTOSTART = NO +[vpn] +AUTOSTART=NO + + diff --git a/src/dht/test_dht_line.conf b/src/dht/test_dht_line.conf index 6be3559..0c790aa 100644 --- a/src/dht/test_dht_line.conf +++ b/src/dht/test_dht_line.conf @@ -1,35 +1,16 @@ [PATHS] -SERVICEHOME = /tmp/test_dht_topo/ -DEFAULTCONFIG = test_dht_line.conf +SERVICEHOME = /tmp/test_dht_line/ [arm] -PORT = 10010 DEFAULTSERVICES = core dht -#DEBUG = YES - -[statistics] -AUTOSTART = YES -PORT = 10000 - -[dht] -DEBUG = NO -AUTOSTART = YES -ACCEPT_FROM6 = ::1; -ACCEPT_FROM = 127.0.0.1; -HOSTNAME = localhost -PORT = 10001 [dns] AUTOSTART = NO -PORT = 10011 - -[transport] -PORT = 10002 -AUTOSTART = YES [nat] DISABLEV6 = YES -BINDTO = 127.0.0.1 +RETURN_LOCAL_ADDRESSES = YES +USE_LOCALADDR = YES ENABLE_UPNP = NO BEHIND_NAT = NO ALLOW_NAT = NO @@ -40,45 +21,11 @@ EXTERNAL_ADDRESS = 127.0.0.1 WAN_QUOTA_IN = 1 GB WAN_QUOTA_OUT = 1 GB -[core] -AUTOSTART = YES -PORT = 10003 - -[peerinfo] -AUTOSTART = YES -PORT = 10004 - [testing] -NUM_PEERS = 5 WEAKRANDOM = YES -TOPOLOGY = NONE -CONNECT_TOPOLOGY = LINE -BLACKLIST_TOPOLOGY = LINE -#TOPOLOGY_FILE = small.dat -#CONNECT_TOPOLOGY = ERDOS_RENYI -#CONNECT_TOPOLOGY_OPTION = CONNECT_MINIMUM -#CONNECT_TOPOLOGY_OPTION_MODIFIER = 25 -#PERCENTAGE = 3 -#PROBABILITY = .1 -F2F = NO -CONNECT_TIMEOUT = 60 s -CONNECT_ATTEMPTS = 3 -DEBUG = YES -HOSTKEYSFILE = ../../contrib/testing_hostkeys.dat -MAX_CONCURRENT_SSH = 10 -USE_PROGRESSBARS = YES -PEERGROUP_TIMEOUT = 2400 s -TOPOLOGY_OUTPUT_FILE = line_topo_initial -MAX_OUTSTANDING_CONNECTIONS = 75 -#SINGLE_PEERINFO_PER_HOST = YES -#NUM_PEERINFO_PER_HOST = 10 -#SINGLE_STATISTICS_PER_HOST = YES -#NUM_STATISTICS_PER_HOST = 10 -DELETE_FILES = YES -[test_dht_topo] -CONNECTION_LIMIT = 5 -#DATA_OUTPUT_FILE=data_output +[testbed] +OVERLAY_TOPOLOGY = LINE [namestore] AUTOSTART = NO @@ -87,3 +34,8 @@ AUTOSTART = NO WORKDELAY = 500 ms INTERVAL = 60 s WORKBITS = 0 + +[vpn] +AUTOSTART = NO + + diff --git a/src/dht/test_dht_monitor.c b/src/dht/test_dht_monitor.c index ca6704a..74024ed 100644 --- a/src/dht/test_dht_monitor.c +++ b/src/dht/test_dht_monitor.c @@ -1,6 +1,6 @@ /* This file is part of GNUnet. - (C) 2011 Christian Grothoff (and other contributing authors) + (C) 2011, 2012 Christian Grothoff (and other contributing authors) GNUnet is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published @@ -19,280 +19,215 @@ */ /** * @file dht/test_dht_monitor.c - * - * @brief Test for the dht service: store, retrieve and monitor in a line. - * TODO: update this description - * Each peer stores it own ID in the DHT and then a different peer tries to - * retrieve that key from it. The GET starts after a first round of PUTS has - * been made. Periodically, each peer stores its ID into the DHT. If after - * a timeout no result has been returned, the test fails. + * @brief Test for the dht monitoring API; checks that we receive "some" monitor events + * @author Christian Grothoff */ #include "platform.h" -#include "gnunet_testing_lib.h" +#include "gnunet_testbed_service.h" #include "gnunet_dht_service.h" - -#define REMOVE_DIR GNUNET_YES +#include "dht_test_lib.h" /** - * How long until we give up on connecting the peers? + * How long do we run the test at most? */ -#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 1500) - -#define GET_TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 120) +#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 300) +/** + * How often do we run the PUTs? + */ #define PUT_FREQUENCY GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 10) -static int ok; /** - * Be verbose + * Information we keep for each GET operation. */ -static int verbose; +struct GetOperation +{ + /** + * DLL. + */ + struct GetOperation *next; -/** - * Total number of peers in the test. - */ -static unsigned long long num_peers; + /** + * DLL. + */ + struct GetOperation *prev; -/** - * Global configuration file - */ -static struct GNUNET_CONFIGURATION_Handle *testing_cfg; + /** + * Handle for the operation. + */ + struct GNUNET_DHT_GetHandle *get; + +}; -/** - * Total number of currently running peers. - */ -static unsigned long long peers_running; /** - * Total number of connections in the whole network. + * Return value from 'main'. */ -static unsigned int total_connections; +static int ok; /** - * The currently running peer group. + * Head of list of active GET operations. */ -static struct GNUNET_TESTING_PeerGroup *pg; +static struct GetOperation *get_head; /** - * File to report results to. + * Tail of list of active GET operations. */ -static struct GNUNET_DISK_FileHandle *output_file; +static struct GetOperation *get_tail; /** - * File to log connection info, statistics to. - */ -static struct GNUNET_DISK_FileHandle *data_file; + * Array of the testbed's peers. + */ +static struct GNUNET_TESTBED_Peer **my_peers; /** - * Task called to disconnect peers. + * Number of peers to run. */ -static GNUNET_SCHEDULER_TaskIdentifier disconnect_task; +static unsigned int NUM_PEERS = 3; /** - * Task To perform tests + * Task called to disconnect peers. */ -static GNUNET_SCHEDULER_TaskIdentifier test_task; +static GNUNET_SCHEDULER_TaskIdentifier timeout_task; /** * Task to do DHT_puts */ static GNUNET_SCHEDULER_TaskIdentifier put_task; -/** - * Task called to shutdown test. - */ -static GNUNET_SCHEDULER_TaskIdentifier shutdown_handle; - -static char *topology_file; - -struct GNUNET_TESTING_Daemon *d1; - -struct GNUNET_TESTING_Daemon *d2; - -struct GNUNET_DHT_Handle **hs; - -struct GNUNET_DHT_MonitorHandle **mhs; - -struct GNUNET_DHT_GetHandle *get_h_far; +static struct GNUNET_DHT_MonitorHandle **monitors; -const char *id_origin = "FC74"; -const char *id_far = "2UVH"; +static unsigned int monitor_counter; -struct GNUNET_TESTING_Daemon *d_far; -struct GNUNET_TESTING_Daemon *o; - -unsigned int monitor_counter; - -int in_test; /** - * Check whether peers successfully shut down. - */ -static void -shutdown_callback (void *cls, const char *emsg) -{ - if (emsg != NULL) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "test: Shutdown of peers failed: %s\n", - emsg); - ok++; - } - else - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "test: All peers successfully shut down!\n"); - } - GNUNET_CONFIGURATION_destroy (testing_cfg); -} - - -static void -shutdown_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: Ending test.\n"); - if (disconnect_task != GNUNET_SCHEDULER_NO_TASK) - { - GNUNET_SCHEDULER_cancel (disconnect_task); - disconnect_task = GNUNET_SCHEDULER_NO_TASK; - } - if (data_file != NULL) - GNUNET_DISK_file_close (data_file); - GNUNET_TESTING_daemons_stop (pg, TIMEOUT, &shutdown_callback, NULL); -} - - + * Task run on success or timeout to clean up. + * Terminates active get operations and shuts down + * the testbed. + * + * @param cls the 'struct GNUNET_DHT_TestContext' + * @param tc scheduler context + */ static void -disconnect_peers (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +shutdown_task (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) { + struct GNUNET_DHT_TEST_Context *ctx = cls; unsigned int i; + struct GetOperation *get_op; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: disconnecting peers\n"); - disconnect_task = GNUNET_SCHEDULER_NO_TASK; - GNUNET_SCHEDULER_cancel (put_task); - if (NULL != get_h_far) - GNUNET_DHT_get_stop (get_h_far); - for (i = 0; i < num_peers; i++) + ok = (monitor_counter > NUM_PEERS) ? 0 : 2; + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + "Received %u monitor events\n", + monitor_counter); + while (NULL != (get_op = get_tail)) { - GNUNET_DHT_monitor_stop(mhs[i]); - GNUNET_DHT_disconnect (hs[i]); + GNUNET_DHT_get_stop (get_op->get); + GNUNET_CONTAINER_DLL_remove (get_head, + get_tail, + get_op); + GNUNET_free (get_op); } - GNUNET_SCHEDULER_cancel (shutdown_handle); - shutdown_handle = GNUNET_SCHEDULER_add_now (&shutdown_task, NULL); + for (i=0;i= 0; i--) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: %s\n", - GNUNET_i2s (&get_path[i])); - } - for (i = put_path_length - 1; i >= 0; i--) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: %s\n", - GNUNET_i2s (&put_path[i])); - } - if (monitor_counter >= get_path_length + put_path_length) - { - ok = 0; - GNUNET_log (GNUNET_ERROR_TYPE_INFO, "expected at least %u hops, got %u\n", - get_path_length + put_path_length, monitor_counter); - } - else - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "expected at least %u hops, got %u\n", - get_path_length + put_path_length, monitor_counter); - GNUNET_SCHEDULER_cancel (disconnect_task); - disconnect_task = GNUNET_SCHEDULER_add_now (&disconnect_peers, NULL); -} /** - * Start test: start GET request from the first node in the line looking for - * the ID of the last node in the line. - * - * @param cls Closure (not used). - * @param tc Task context. + * Iterator called on each result obtained for a DHT + * operation that expects a reply + * + * @param cls closure with our 'struct GetOperation' + * @param exp when will this value expire + * @param key key of the result + * @param get_path peers on reply path (or NULL if not recorded) + * @param get_path_length number of entries in get_path + * @param put_path peers on the PUT path (or NULL if not recorded) + * @param put_path_length number of entries in get_path + * @param type type of the result + * @param size number of bytes in data + * @param data pointer to the result data */ static void -do_test (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +dht_get_handler (void *cls, struct GNUNET_TIME_Absolute exp, + const struct GNUNET_HashCode * key, + const struct GNUNET_PeerIdentity *get_path, + unsigned int get_path_length, + const struct GNUNET_PeerIdentity *put_path, + unsigned int put_path_length, enum GNUNET_BLOCK_Type type, + size_t size, const void *data) { - if ((tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN) != 0) + struct GetOperation *get_op = cls; + struct GNUNET_HashCode want; + struct GNUNET_DHT_TestContext *ctx; + + if (sizeof (struct GNUNET_HashCode) != size) + { + GNUNET_break (0); + return; + } + GNUNET_CRYPTO_hash (key, sizeof (*key), &want); + if (0 != memcmp (&want, data, sizeof (want))) { + GNUNET_break (0); return; } - - in_test = GNUNET_YES; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: test_task\n"); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: looking for %s\n", - GNUNET_h2s_full (&d_far->id.hashPubKey)); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: from %s\n", - GNUNET_h2s_full (&o->id.hashPubKey)); - get_h_far = GNUNET_DHT_get_start (hs[0], - GNUNET_BLOCK_TYPE_TEST, /* type */ - &d_far->id.hashPubKey, /*key to search */ - 4U, /* replication level */ - GNUNET_DHT_RO_RECORD_ROUTE | GNUNET_DHT_RO_DEMULTIPLEX_EVERYWHERE, NULL, /* xquery */ - 0, /* xquery bits */ - &dht_get_id_handler, NULL); - GNUNET_SCHEDULER_cancel (disconnect_task); - disconnect_task = - GNUNET_SCHEDULER_add_delayed (GET_TIMEOUT, &disconnect_peers, NULL); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Get successful\n"); + GNUNET_DHT_get_stop (get_op->get); + GNUNET_CONTAINER_DLL_remove (get_head, + get_tail, + get_op); + GNUNET_free (get_op); + if (NULL != get_head) + return; + /* all DHT GET operations successful; terminate! */ + ok = 0; + ctx = GNUNET_SCHEDULER_cancel (timeout_task); + timeout_task = GNUNET_SCHEDULER_add_now (&shutdown_task, ctx); } /** - * Periodic function used to put the ID of the far peer in the DHT. + * Task to put the id of each peer into the DHT. * - * @param cls Closure (not used). - * @param tc Task context. + * @param cls array with NUM_PEERS DHT handles + * @param tc Task context */ static void -put_id (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +do_puts (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) { - struct GNUNET_TESTING_Daemon *d; + struct GNUNET_DHT_Handle **hs = cls; + struct GNUNET_HashCode key; + struct GNUNET_HashCode value; + unsigned int i; - if ((tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN) != 0) + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Putting values into DHT\n"); + for (i = 0; i < NUM_PEERS; i++) { - put_task = GNUNET_SCHEDULER_NO_TASK; - return; + GNUNET_CRYPTO_hash (&i, sizeof (i), &key); + GNUNET_CRYPTO_hash (&key, sizeof (key), &value); + GNUNET_DHT_put (hs[i], &key, 10U, + GNUNET_DHT_RO_RECORD_ROUTE | + GNUNET_DHT_RO_DEMULTIPLEX_EVERYWHERE, + GNUNET_BLOCK_TYPE_TEST, + sizeof (value), &value, + GNUNET_TIME_UNIT_FOREVER_ABS, + GNUNET_TIME_UNIT_FOREVER_REL, + NULL, NULL); } - - d = GNUNET_TESTING_daemon_get (pg, 4); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: putting into DHT: %s\n", - GNUNET_h2s_full (&d->id.hashPubKey)); - GNUNET_DHT_put (hs[4], &d->id.hashPubKey, 10U, - GNUNET_DHT_RO_RECORD_ROUTE | - GNUNET_DHT_RO_DEMULTIPLEX_EVERYWHERE, - GNUNET_BLOCK_TYPE_TEST, sizeof (struct GNUNET_PeerIdentity), - (const char *) &d->id, GNUNET_TIME_UNIT_FOREVER_ABS, - GNUNET_TIME_UNIT_FOREVER_REL, NULL, NULL); - - put_task = GNUNET_SCHEDULER_add_delayed (PUT_FREQUENCY, &put_id, NULL); + put_task = GNUNET_SCHEDULER_add_delayed (PUT_FREQUENCY, + &do_puts, hs); } + /** * Callback called on each GET request going through the DHT. * Prints the info about the intercepted packet and increments a counter. @@ -306,7 +241,7 @@ put_id (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) * @param desired_replication_level Desired replication level. * @param key Key of the requested data. */ -void +static void monitor_get_cb (void *cls, enum GNUNET_DHT_RouteOption options, enum GNUNET_BLOCK_Type type, @@ -314,19 +249,16 @@ monitor_get_cb (void *cls, uint32_t desired_replication_level, unsigned int path_length, const struct GNUNET_PeerIdentity *path, - const GNUNET_HashCode * key) + const struct GNUNET_HashCode * key) { - const char *s_key; unsigned int i; i = (unsigned int) (long) cls; - s_key = GNUNET_h2s(key); GNUNET_log (GNUNET_ERROR_TYPE_INFO, "%u got a GET message for key %s\n", - i, s_key); - - if (strncmp (s_key, id_far, 4) == 0 && in_test == GNUNET_YES) - monitor_counter++; + i, + GNUNET_h2s (key)); + monitor_counter++; } @@ -346,7 +278,7 @@ monitor_get_cb (void *cls, * @param data Pointer to the data carried. * @param size Number of bytes in data. */ -void +static void monitor_put_cb (void *cls, enum GNUNET_DHT_RouteOption options, enum GNUNET_BLOCK_Type type, @@ -355,22 +287,18 @@ monitor_put_cb (void *cls, unsigned int path_length, const struct GNUNET_PeerIdentity *path, struct GNUNET_TIME_Absolute exp, - const GNUNET_HashCode * key, + const struct GNUNET_HashCode * key, const void *data, size_t size) { - const char *s_key; unsigned int i; i = (unsigned int) (long) cls; - s_key = GNUNET_h2s(key); - GNUNET_log (GNUNET_ERROR_TYPE_INFO, "%u got a PUT message for key %s with %u bytes\n", - i, s_key, size); - - if (strncmp (s_key, id_far, 4) == 0 && in_test == GNUNET_YES) - monitor_counter++; + i, + GNUNET_h2s (key), size); + monitor_counter++; } @@ -389,7 +317,7 @@ monitor_put_cb (void *cls, * @param data Pointer to the result data. * @param size Number of bytes in data. */ -void +static void monitor_res_cb (void *cls, enum GNUNET_BLOCK_Type type, const struct GNUNET_PeerIdentity *get_path, @@ -397,267 +325,92 @@ monitor_res_cb (void *cls, const struct GNUNET_PeerIdentity *put_path, unsigned int put_path_length, struct GNUNET_TIME_Absolute exp, - const GNUNET_HashCode * key, + const struct GNUNET_HashCode * key, const void *data, size_t size) { - const char *s_key; unsigned int i; i = (unsigned int) (long) cls; - s_key = GNUNET_h2s(key); GNUNET_log (GNUNET_ERROR_TYPE_INFO, "%u got a REPLY message for key %s with %u bytes\n", - i, s_key, size); - - if (strncmp (s_key, id_far, 4) == 0 && in_test == GNUNET_YES) - monitor_counter++; + i, + GNUNET_h2s (key), size); + monitor_counter++; } /** - * peergroup_ready: start test when all peers are connected + * Main function of the test. * - * @param cls closure - * @param emsg error message + * @param cls closure (NULL) + * @param ctx argument to give to GNUNET_DHT_TEST_cleanup on test end + * @param num_peers number of peers that are running + * @param peers array of peers + * @param dhts handle to each of the DHTs of the peers */ static void -peergroup_ready (void *cls, const char *emsg) +run (void *cls, + struct GNUNET_DHT_TEST_Context *ctx, + unsigned int num_peers, + struct GNUNET_TESTBED_Peer **peers, + struct GNUNET_DHT_Handle **dhts) { - struct GNUNET_TESTING_Daemon *d; - char *buf; - int buf_len; unsigned int i; + unsigned int j; + struct GNUNET_HashCode key; + struct GetOperation *get_op; - if (emsg != NULL) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "test: Peergroup callback called with error, aborting test!\n"); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: Error from testing: `%s'\n", - emsg); - ok++; - GNUNET_TESTING_daemons_stop (pg, TIMEOUT, &shutdown_callback, NULL); - return; - } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "test: Peer Group started successfully with %u connections\n", - total_connections); - if (data_file != NULL) - { - buf = NULL; - buf_len = GNUNET_asprintf (&buf, "CONNECTIONS_0: %u\n", total_connections); - if (buf_len > 0) - GNUNET_DISK_file_write (data_file, buf, buf_len); - GNUNET_free (buf); - } - peers_running = GNUNET_TESTING_daemons_running (pg); - - GNUNET_assert (peers_running == num_peers); - hs = GNUNET_malloc (num_peers * sizeof (struct GNUNET_DHT_Handle *)); - mhs = GNUNET_malloc (num_peers * sizeof (struct GNUNET_DHT_MonitorHandle *)); - d_far = o = NULL; - o = GNUNET_TESTING_daemon_get (pg, 0); - d_far = GNUNET_TESTING_daemon_get (pg, 4); - + GNUNET_assert (NUM_PEERS == num_peers); + my_peers = peers; + monitors = GNUNET_malloc (num_peers * sizeof (struct GNUNET_DHT_MonitorHandle *)); for (i = 0; i < num_peers; i++) + monitors[i] = GNUNET_DHT_monitor_start (dhts[i], + GNUNET_BLOCK_TYPE_ANY, + NULL, + &monitor_get_cb, + &monitor_res_cb, + &monitor_put_cb, + (void *)(long)i); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Peers setup, starting test\n"); + put_task = GNUNET_SCHEDULER_add_now (&do_puts, dhts); + for (i=0;icfg, 32); - mhs[i] = GNUNET_DHT_monitor_start(hs[i], - GNUNET_BLOCK_TYPE_ANY, - NULL, - &monitor_get_cb, - &monitor_res_cb, - &monitor_put_cb, - (void *)(long)i); - } - - if ((NULL == o) || (NULL == d_far)) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "test: Error getting daemons from pg\n"); - GNUNET_SCHEDULER_cancel (disconnect_task); - disconnect_task = GNUNET_SCHEDULER_add_now (&disconnect_peers, NULL); - return; - } - monitor_counter = 0; - put_task = GNUNET_SCHEDULER_add_now (&put_id, NULL); - test_task = - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply - (GNUNET_TIME_UNIT_SECONDS, 2), &do_test, - NULL); - disconnect_task = - GNUNET_SCHEDULER_add_delayed (GET_TIMEOUT, &disconnect_peers, NULL); - -} - - -/** - * Function that will be called whenever two daemons are connected by - * the testing library. - * - * @param cls closure - * @param first peer id for first daemon - * @param second peer id for the second daemon - * @param distance distance between the connected peers - * @param first_cfg config for the first daemon - * @param second_cfg config for the second daemon - * @param first_daemon handle for the first daemon - * @param second_daemon handle for the second daemon - * @param emsg error message (NULL on success) - */ -static void -connect_cb (void *cls, const struct GNUNET_PeerIdentity *first, - const struct GNUNET_PeerIdentity *second, uint32_t distance, - const struct GNUNET_CONFIGURATION_Handle *first_cfg, - const struct GNUNET_CONFIGURATION_Handle *second_cfg, - struct GNUNET_TESTING_Daemon *first_daemon, - struct GNUNET_TESTING_Daemon *second_daemon, const char *emsg) -{ - - if (emsg == NULL) - { - total_connections++; - GNUNET_PEER_intern (first); - GNUNET_PEER_intern (second); - } - else - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "test: Problem with new connection (%s)\n", emsg); - } - -} - - -/** - * run: load configuration options and schedule test to run (start peergroup) - * @param cls closure - * @param args argv - * @param cfgfile configuration file name (can be NULL) - * @param cfg configuration handle - */ -static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) -{ - char *temp_str; - struct GNUNET_TESTING_Host *hosts; - char *data_filename; - - ok = 1; - testing_cfg = GNUNET_CONFIGURATION_dup (cfg); - - GNUNET_log_setup ("test_dht_monitor", - "WARNING", - NULL); - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: Starting daemons.\n"); - GNUNET_CONFIGURATION_set_value_string (testing_cfg, "testing", - "use_progressbars", "YES"); - if (GNUNET_OK != - GNUNET_CONFIGURATION_get_value_number (testing_cfg, "testing", - "num_peers", &num_peers)) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "Option TESTING:NUM_PEERS is required!\n"); - return; - } - - if (GNUNET_OK != - GNUNET_CONFIGURATION_get_value_string (testing_cfg, "testing", - "topology_output_file", - &topology_file)) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "Option test_dht_monitor:topology_output_file is required!\n"); - return; - } - - if (GNUNET_OK == - GNUNET_CONFIGURATION_get_value_string (testing_cfg, "test_dht_topo", - "data_output_file", - &data_filename)) - { - data_file = - GNUNET_DISK_file_open (data_filename, - GNUNET_DISK_OPEN_READWRITE | - GNUNET_DISK_OPEN_CREATE, - GNUNET_DISK_PERM_USER_READ | - GNUNET_DISK_PERM_USER_WRITE); - if (data_file == NULL) + GNUNET_CRYPTO_hash (&i, sizeof (i), &key); + for (j=0;jget = GNUNET_DHT_get_start (dhts[j], + GNUNET_BLOCK_TYPE_TEST, /* type */ + &key, /*key to search */ + 4U, /* replication level */ + GNUNET_DHT_RO_DEMULTIPLEX_EVERYWHERE, + NULL, /* xquery */ + 0, /* xquery bits */ + &dht_get_handler, get_op); } } - - if (GNUNET_YES == - GNUNET_CONFIGURATION_get_value_string (cfg, "test_dht_topo", - "output_file", &temp_str)) - { - output_file = - GNUNET_DISK_file_open (temp_str, - GNUNET_DISK_OPEN_READWRITE | - GNUNET_DISK_OPEN_CREATE, - GNUNET_DISK_PERM_USER_READ | - GNUNET_DISK_PERM_USER_WRITE); - if (output_file == NULL) - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Failed to open %s for output!\n", - temp_str); - } - GNUNET_free_non_null (temp_str); - - hosts = GNUNET_TESTING_hosts_load (testing_cfg); - - pg = GNUNET_TESTING_peergroup_start (testing_cfg, num_peers, TIMEOUT, - &connect_cb, &peergroup_ready, NULL, - hosts); - GNUNET_assert (pg != NULL); - shutdown_handle = - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, - &shutdown_task, NULL); + timeout_task = GNUNET_SCHEDULER_add_delayed (TIMEOUT, + &shutdown_task, ctx); } - -/** - * test_dht_monitor command line options - */ -static struct GNUNET_GETOPT_CommandLineOption options[] = { - {'V', "verbose", NULL, - gettext_noop ("be verbose (print progress information)"), - 0, &GNUNET_GETOPT_set_one, &verbose}, - GNUNET_GETOPT_OPTION_END -}; - - /** * Main: start test */ int main (int xargc, char *xargv[]) { - char *const argv[] = { "test-dht-monitor", - "-c", - "test_dht_line.conf", - NULL - }; - - in_test = GNUNET_NO; - GNUNET_PROGRAM_run (sizeof (argv) / sizeof (char *) - 1, argv, - "test_dht_monitor", - gettext_noop ("Test dht monitoring in a line."), - options, &run, NULL); -#if REMOVE_DIR - GNUNET_DISK_directory_remove ("/tmp/test_dht_monitor"); -#endif - if (0 != ok) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "test: FAILED!\n"); - } + GNUNET_DHT_TEST_run ("test-dht-monitor", + "test_dht_monitor.conf", + NUM_PEERS, + &run, NULL); return ok; } + /* end of test_dht_monitor.c */ diff --git a/src/dht/test_dht_monitor.conf b/src/dht/test_dht_monitor.conf new file mode 100644 index 0000000..ebefcca --- /dev/null +++ b/src/dht/test_dht_monitor.conf @@ -0,0 +1,57 @@ +[fs] +AUTOSTART = NO + +[resolver] +AUTOSTART = NO + +[block] +plugins = test dht + +[dhtcache] +QUOTA = 1 MB +DATABASE = sqlite + +[transport] +PLUGINS = tcp + +[ats] +WAN_QUOTA_IN = 1 GB +WAN_QUOTA_OUT = 1 GB + +[arm] +DEFAULTSERVICES = dht core + +[TESTING] +WEAKRANDOM = YES + +[testbed] +OVERLAY_TOPOLOGY = LINE + +[gnunetd] +HOSTKEY = $SERVICEHOME/.hostkey + +[PATHS] +SERVICEHOME = /tmp/test-dht-multipeer/ + +[nat] +DISABLEV6 = YES +ENABLE_UPNP = NO +BEHIND_NAT = NO +ALLOW_NAT = NO +INTERNAL_ADDRESS = 127.0.0.1 +EXTERNAL_ADDRESS = 127.0.0.1 +USE_LOCALADDR = YES +RETURN_LOCAL_ADDRESSES = YES + +[dns] +AUTOSTART = NO + +[namestore] +AUTOSTART = NO + +[nse] +AUTOSTART = NO + +[vpn] +AUTOSTART=NO + diff --git a/src/dht/test_dht_multipeer.c b/src/dht/test_dht_multipeer.c deleted file mode 100644 index ab7d90e..0000000 --- a/src/dht/test_dht_multipeer.c +++ /dev/null @@ -1,859 +0,0 @@ -/* - This file is part of GNUnet. - (C) 2009 Christian Grothoff (and other contributing authors) - - GNUnet is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published - by the Free Software Foundation; either version 3, or (at your - option) any later version. - - GNUnet is distributed in the hope that it will be useful, but - WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - General Public License for more details. - - You should have received a copy of the GNU General Public License - along with GNUnet; see the file COPYING. If not, write to the - Free Software Foundation, Inc., 59 Temple Place - Suite 330, - Boston, MA 02111-1307, USA. -*/ -/** - * @file dht/test_dht_multipeer.c - * @brief testcase for testing DHT service with - * multiple peers. - */ -#include "platform.h" -#include "gnunet_testing_lib.h" -#include "gnunet_core_service.h" -#include "gnunet_dht_service.h" - -/* Timeout for entire testcase */ -#define TIMEOUT GNUNET_TIME_relative_multiply(GNUNET_TIME_UNIT_MINUTES, 30) - -/* Timeout for waiting for replies to get requests */ -#define GET_TIMEOUT GNUNET_TIME_relative_multiply(GNUNET_TIME_UNIT_SECONDS, 300) - -/* */ -#define START_DELAY GNUNET_TIME_relative_multiply(GNUNET_TIME_UNIT_SECONDS, 30) - -/* Timeout for waiting for gets to complete */ -#define GET_DELAY GNUNET_TIME_relative_multiply(GNUNET_TIME_UNIT_MILLISECONDS, 50) - -/* Timeout for waiting for puts to complete */ -#define PUT_DELAY GNUNET_TIME_relative_multiply(GNUNET_TIME_UNIT_MILLISECONDS, 50) - -/* If number of peers not in config file, use this number */ -#define DEFAULT_NUM_PEERS 10 - -#define TEST_DATA_SIZE 8 - -#define MAX_OUTSTANDING_PUTS 100 - -#define MAX_OUTSTANDING_GETS 100 - -#define PATH_TRACKING GNUNET_NO - - - -struct TestPutContext -{ - /** - * This is a linked list - */ - struct TestPutContext *next; - - /** - * This is a linked list - */ - struct TestPutContext *prev; - - /** - * Handle to the first peers DHT service (via the API) - */ - struct GNUNET_DHT_Handle *dht_handle; - - /** - * Handle to the PUT peer daemon - */ - struct GNUNET_TESTING_Daemon *daemon; - - /** - * Identifier for this PUT - */ - uint32_t uid; - - /** - * Task handle for processing of the put. - */ - GNUNET_SCHEDULER_TaskIdentifier task; -}; - - -struct TestGetContext -{ - /** - * This is a linked list - */ - struct TestGetContext *next; - - /** - * This is a linked list - */ - struct TestGetContext *prev; - - /** - * Handle to the first peers DHT service (via the API) - */ - struct GNUNET_DHT_Handle *dht_handle; - - /** - * Handle for the DHT get request - */ - struct GNUNET_DHT_GetHandle *get_handle; - - /** - * Handle to the GET peer daemon - */ - struct GNUNET_TESTING_Daemon *daemon; - - /** - * Identifier for this GET - */ - uint32_t uid; - - /** - * Task for disconnecting DHT handles (and stopping GET) - */ - GNUNET_SCHEDULER_TaskIdentifier task; - - /** - * Whether or not this request has been fulfilled already. - */ - int succeeded; -}; - - -/** - * List of GETS to perform - */ -static struct TestGetContext *all_gets_head; - -/** - * List of GETS to perform - */ -static struct TestGetContext *all_gets_tail; - -/** - * List of PUTS to perform - */ -static struct TestPutContext *all_puts_head; - -/** - * List of PUTS to perform - */ -static struct TestPutContext *all_puts_tail; - -/** - * Handle to the set of all peers run for this test. - */ -static struct GNUNET_TESTING_PeerGroup *pg; - -/** - * Total number of peers to run, set based on config file. - */ -static unsigned long long num_peers; - -/** - * How many puts do we currently have in flight? - */ -static unsigned long long outstanding_puts; - -/** - * How many puts are done? - */ -static unsigned long long puts_completed; - -/** - * How many puts do we currently have in flight? - */ -static unsigned long long outstanding_gets; - -/** - * How many gets are done? - */ -static unsigned long long gets_completed; - -/** - * How many gets failed? - */ -static unsigned long long gets_failed; - -/** - * Directory to remove on shutdown. - */ -static char *test_directory; - -/** - * Option to use when routing. - */ -static enum GNUNET_DHT_RouteOption route_option; - -/** - * Task handle to use to schedule test failure / success. - */ -static GNUNET_SCHEDULER_TaskIdentifier die_task; - -/** - * Task handle to use to schedule test shutdown - */ -GNUNET_SCHEDULER_TaskIdentifier shutdown_task; - -/** - * Global return value (0 for success, anything else for failure) - */ -static int ok; - - -/** - * Check whether peers successfully shut down. - */ -static void -shutdown_callback (void *cls, const char *emsg) -{ - if (emsg != NULL) - { - FPRINTF (stderr, "Failed to shutdown testing topology: %s\n", emsg); - if (ok == 0) - ok = 2; - } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Shutdown callback completed.\n"); -} - -static void -do_stop (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - if ((tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN) == 0) - { - if (GNUNET_SCHEDULER_NO_TASK != shutdown_task) - { - GNUNET_SCHEDULER_cancel(shutdown_task); - shutdown_task = GNUNET_SCHEDULER_NO_TASK; - } - } - else - { - shutdown_task = GNUNET_SCHEDULER_NO_TASK ; - } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Shutdown requested.\n"); - if (NULL != pg) - GNUNET_TESTING_daemons_stop (pg, TIMEOUT, &shutdown_callback, NULL); - pg = NULL; -} - - -/** - * Master context for 'stat_run'. - */ -struct StatMaster -{ - struct GNUNET_STATISTICS_Handle *stat; - unsigned int daemon; - unsigned int value; -}; - -struct StatValues -{ - const char *subsystem; - const char *name; - unsigned long long total; -}; - -/** - * Statistics we print out. - */ -static struct StatValues stats[] = { - {"core", "# bytes decrypted", 0}, - {"core", "# bytes encrypted", 0}, - {"core", "# type maps received", 0}, - {"core", "# session keys confirmed via PONG", 0}, - {"core", "# peers connected", 0}, - {"core", "# key exchanges initiated", 0}, - {"core", "# send requests dropped (disconnected)", 0}, - {"core", "# transmissions delayed due to corking", 0}, - {"core", "# messages discarded (expired prior to transmission)", 0}, - {"core", "# messages discarded (disconnected)", 0}, - {"core", "# discarded CORE_SEND requests", 0}, - {"core", "# discarded lower priority CORE_SEND requests", 0}, - {"transport", "# bytes received via TCP", 0}, - {"transport", "# bytes transmitted via TCP", 0}, - {"dht", "# PUT messages queued for transmission", 0}, - {"dht", "# P2P PUT requests received", 0}, - {"dht", "# GET messages queued for transmission", 0}, - {"dht", "# P2P GET requests received", 0}, - {"dht", "# RESULT messages queued for transmission", 0}, - {"dht", "# P2P RESULTS received", 0}, - {"dht", "# Queued messages discarded (peer disconnected)", 0}, - {"dht", "# Peers excluded from routing due to Bloomfilter", 0}, - {"dht", "# Peer selection failed", 0}, - {"dht", "# FIND PEER requests ignored due to Bloomfilter", 0}, - {"dht", "# FIND PEER requests ignored due to lack of HELLO", 0}, - {"dht", "# P2P FIND PEER requests processed", 0}, - {"dht", "# P2P GET requests ONLY routed", 0}, - {"dht", "# Preference updates given to core", 0}, - {"dht", "# REPLIES ignored for CLIENTS (no match)", 0}, - {"dht", "# GET requests from clients injected", 0}, - {"dht", "# GET requests received from clients", 0}, - {"dht", "# GET STOP requests received from clients", 0}, - {"dht", "# ITEMS stored in datacache", 0}, - {"dht", "# Good RESULTS found in datacache", 0}, - {"dht", "# GET requests given to datacache", 0}, - {NULL, NULL, 0} -}; - - -/** - * Callback function to process statistic values. - * - * @param cls closure - * @param subsystem name of subsystem that created the statistic - * @param name the name of the datum - * @param value the current value - * @param is_persistent GNUNET_YES if the value is persistent, GNUNET_NO if not - * @return GNUNET_OK to continue, GNUNET_SYSERR to abort iteration - */ -static int -print_stat (void *cls, const char *subsystem, const char *name, uint64_t value, - int is_persistent) -{ - struct StatMaster *sm = cls; - - stats[sm->value].total += value; - FPRINTF (stderr, "Peer %2u: %12s/%50s = %12llu\n", sm->daemon, subsystem, - name, (unsigned long long) value); - return GNUNET_OK; -} - - -/** - * Function that gathers stats from all daemons. - */ -static void -stat_run (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc); - - -/** - * Function called when GET operation on stats is done. - */ -static void -get_done (void *cls, int success) -{ - struct StatMaster *sm = cls; - - GNUNET_break (GNUNET_OK == success); - sm->value++; - GNUNET_SCHEDULER_add_now (&stat_run, sm); -} - - -/** - * Function that gathers stats from all daemons. - */ -static void -stat_run (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - struct StatMaster *sm = cls; - unsigned int i; - - die_task = GNUNET_SCHEDULER_NO_TASK; - if (stats[sm->value].name != NULL) - { - GNUNET_STATISTICS_get (sm->stat, -#if 0 - NULL, NULL, -#else - stats[sm->value].subsystem, stats[sm->value].name, -#endif - GNUNET_TIME_UNIT_FOREVER_REL, &get_done, &print_stat, - sm); - return; - } - GNUNET_STATISTICS_destroy (sm->stat, GNUNET_NO); - sm->value = 0; - sm->daemon++; - if (sm->daemon == num_peers) - { - GNUNET_free (sm); - i = 0; - while (stats[i].name != NULL) - { - FPRINTF (stderr, "Total : %12s/%50s = %12llu\n", stats[i].subsystem, - stats[i].name, (unsigned long long) stats[i].total); - i++; - } - die_task = GNUNET_SCHEDULER_add_now (&do_stop, NULL); - return; - } - sm->stat = - GNUNET_STATISTICS_create ("", - GNUNET_TESTING_daemon_get (pg, - sm->daemon)->cfg); - die_task = GNUNET_SCHEDULER_add_now (&stat_run, sm); -} - - -/** - * Function scheduled to be run on the successful completion of this - * testcase. - */ -static void -finish_testing (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - struct TestPutContext *test_put; - struct TestGetContext *test_get; - struct StatMaster *sm; - - die_task = GNUNET_SCHEDULER_NO_TASK; - while (NULL != (test_put = all_puts_head)) - { - if (test_put->task != GNUNET_SCHEDULER_NO_TASK) - GNUNET_SCHEDULER_cancel (test_put->task); - if (test_put->dht_handle != NULL) - GNUNET_DHT_disconnect (test_put->dht_handle); - GNUNET_CONTAINER_DLL_remove (all_puts_head, all_puts_tail, test_put); - GNUNET_free (test_put); - } - - while (NULL != (test_get = all_gets_head)) - { - if (test_get->task != GNUNET_SCHEDULER_NO_TASK) - GNUNET_SCHEDULER_cancel (test_get->task); - if (test_get->get_handle != NULL) - GNUNET_DHT_get_stop (test_get->get_handle); - if (test_get->dht_handle != NULL) - GNUNET_DHT_disconnect (test_get->dht_handle); - GNUNET_CONTAINER_DLL_remove (all_gets_head, all_gets_tail, test_get); - GNUNET_free (test_get); - } - sm = GNUNET_malloc (sizeof (struct StatMaster)); - sm->stat = - GNUNET_STATISTICS_create ("", - GNUNET_TESTING_daemon_get (pg, - sm->daemon)->cfg); - die_task = GNUNET_SCHEDULER_add_now (&stat_run, sm); -} - - -/** - * Check if the get_handle is being used, if so stop the request. Either - * way, schedule the end_badly_cont function which actually shuts down the - * test. - */ -static void -end_badly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - const char *emsg = cls; - struct TestPutContext *test_put; - struct TestGetContext *test_get; - - die_task = GNUNET_SCHEDULER_NO_TASK; - FPRINTF (stderr, "Failing test with error: `%s'!\n", emsg); - while (NULL != (test_put = all_puts_head)) - { - if (test_put->task != GNUNET_SCHEDULER_NO_TASK) - GNUNET_SCHEDULER_cancel (test_put->task); - if (test_put->dht_handle != NULL) - GNUNET_DHT_disconnect (test_put->dht_handle); - GNUNET_CONTAINER_DLL_remove (all_puts_head, all_puts_tail, test_put); - GNUNET_free (test_put); - } - - while (NULL != (test_get = all_gets_head)) - { - if (test_get->task != GNUNET_SCHEDULER_NO_TASK) - GNUNET_SCHEDULER_cancel (test_get->task); - if (test_get->get_handle != NULL) - GNUNET_DHT_get_stop (test_get->get_handle); - if (test_get->dht_handle != NULL) - GNUNET_DHT_disconnect (test_get->dht_handle); - GNUNET_CONTAINER_DLL_remove (all_gets_head, all_gets_tail, test_get); - GNUNET_free (test_get); - } - ok = 1; - /* testing_peergroup will do that in its own end_badly() handler */ - /*GNUNET_TESTING_daemons_stop (pg, TIMEOUT, &shutdown_callback, NULL); */ - pg = NULL; -} - - -/** - * Task to release get handle. - */ -static void -get_stop_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - struct TestGetContext *test_get = cls; - GNUNET_HashCode search_key; /* Key stored under */ - char original_data[TEST_DATA_SIZE]; /* Made up data to store */ - - test_get->task = GNUNET_SCHEDULER_NO_TASK; - memset (original_data, test_get->uid, sizeof (original_data)); - GNUNET_CRYPTO_hash (original_data, TEST_DATA_SIZE, &search_key); - if (test_get->succeeded != GNUNET_YES) - { - gets_failed++; - FPRINTF (stderr, "Get from peer %s for key %s failed!\n", - GNUNET_i2s (&test_get->daemon->id), GNUNET_h2s (&search_key)); - } - GNUNET_assert (test_get->get_handle != NULL); - GNUNET_DHT_get_stop (test_get->get_handle); - test_get->get_handle = NULL; - - outstanding_gets--; /* GET is really finished */ - GNUNET_DHT_disconnect (test_get->dht_handle); - test_get->dht_handle = NULL; - - GNUNET_CONTAINER_DLL_remove (all_gets_head, all_gets_tail, test_get); - GNUNET_free (test_get); - if ((gets_failed > 10) && (outstanding_gets == 0)) - { - /* Had more than 10% failures */ - FPRINTF (stderr, "%llu gets succeeded, %llu gets failed!\n", gets_completed, - gets_failed); - GNUNET_SCHEDULER_cancel (die_task); - ok = 1; - die_task = - GNUNET_SCHEDULER_add_now (&finish_testing, "not all gets succeeded"); - return; - } - if ((gets_completed + gets_failed == num_peers * num_peers) && (outstanding_gets == 0)) /* All gets successful */ - { - FPRINTF (stderr, "%llu gets succeeded, %llu gets failed!\n", gets_completed, - gets_failed); - GNUNET_SCHEDULER_cancel (die_task); - ok = 0; - die_task = GNUNET_SCHEDULER_add_now (&finish_testing, NULL); - } -} - - -/** - * Iterator called if the GET request initiated returns a response. - * - * @param cls closure - * @param exp when will this value expire - * @param key key of the result - * @param type type of the result - * @param size number of bytes in data - * @param data pointer to the result data - */ -static void -get_result_iterator (void *cls, struct GNUNET_TIME_Absolute exp, - const GNUNET_HashCode * key, - const struct GNUNET_PeerIdentity *get_path, - unsigned int get_path_length, - const struct GNUNET_PeerIdentity *put_path, - unsigned int put_path_length, enum GNUNET_BLOCK_Type type, - size_t size, const void *data) -{ - struct TestGetContext *test_get = cls; - GNUNET_HashCode search_key; /* Key stored under */ - char original_data[TEST_DATA_SIZE]; /* Made up data to store */ - - memset (original_data, test_get->uid, sizeof (original_data)); - GNUNET_CRYPTO_hash (original_data, TEST_DATA_SIZE, &search_key); - if (test_get->succeeded == GNUNET_YES) - return; /* Get has already been successful, probably ending now */ - -#if PATH_TRACKING - if (put_path != NULL) - { - unsigned int i; - - FPRINTF (stderr, "PUT (%u) Path: ", test_get->uid); - for (i = 0; i < put_path_length; i++) - FPRINTF (stderr, "%s%s", i == 0 ? "" : "->", GNUNET_i2s (&put_path[i])); - FPRINTF (stderr, "%s", "\n"); - } - if (get_path != NULL) - { - unsigned int i; - - FPRINTF (stderr, "GET (%u) Path: ", test_get->uid); - for (i = 0; i < get_path_length; i++) - FPRINTF (stderr, "%s%s", i == 0 ? "" : "->", GNUNET_i2s (&get_path[i])); - FPRINTF (stderr, "%s%s\n", get_path_length > 0 ? "->" : "", - GNUNET_i2s (&test_get->daemon->id)); - } -#endif - - if ((0 != memcmp (&search_key, key, sizeof (GNUNET_HashCode))) || - (0 != memcmp (original_data, data, sizeof (original_data)))) - { - FPRINTF (stderr, "%s", "Key or data is not the same as was inserted!\n"); - return; - } - gets_completed++; - test_get->succeeded = GNUNET_YES; - GNUNET_SCHEDULER_cancel (test_get->task); - test_get->task = GNUNET_SCHEDULER_add_now (&get_stop_task, test_get); -} - - -/** - * Set up some data, and call API PUT function - */ -static void -do_get (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - struct TestGetContext *test_get = cls; - GNUNET_HashCode key; /* Made up key to store data under */ - char data[TEST_DATA_SIZE]; /* Made up data to store */ - - if (outstanding_gets > MAX_OUTSTANDING_GETS) - { - test_get->task = - GNUNET_SCHEDULER_add_delayed (GET_DELAY, &do_get, test_get); - return; - } - memset (data, test_get->uid, sizeof (data)); - GNUNET_CRYPTO_hash (data, TEST_DATA_SIZE, &key); - test_get->dht_handle = GNUNET_DHT_connect (test_get->daemon->cfg, 10); - GNUNET_assert (test_get->dht_handle != NULL); - outstanding_gets++; - test_get->get_handle = - GNUNET_DHT_get_start (test_get->dht_handle, - GNUNET_BLOCK_TYPE_TEST, &key, 1, route_option, NULL, - 0, &get_result_iterator, test_get); - test_get->task = - GNUNET_SCHEDULER_add_delayed (GET_TIMEOUT, &get_stop_task, test_get); -} - - -/** - * Task to release DHT handles for PUT - */ -static void -put_disconnect_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - struct TestPutContext *test_put = cls; - - test_put->task = GNUNET_SCHEDULER_NO_TASK; - GNUNET_DHT_disconnect (test_put->dht_handle); - test_put->dht_handle = NULL; - GNUNET_CONTAINER_DLL_remove (all_puts_head, all_puts_tail, test_put); - GNUNET_free (test_put); -} - - -/** - * Schedule the GET requests - */ -static void -start_gets (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - unsigned long long i; - unsigned long long j; - struct TestGetContext *test_get; - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Issuing %llu GETs\n", - (unsigned long long) (num_peers * num_peers)); - for (i = 0; i < num_peers; i++) - for (j = 0; j < num_peers; j++) - { - test_get = GNUNET_malloc (sizeof (struct TestGetContext)); - test_get->uid = i + j * num_peers; - test_get->daemon = GNUNET_TESTING_daemon_get (pg, j); - GNUNET_CONTAINER_DLL_insert (all_gets_head, all_gets_tail, test_get); - test_get->task = GNUNET_SCHEDULER_add_now (&do_get, test_get); - } -} - - -/** - * Called when the PUT request has been transmitted to the DHT service. - */ -static void -put_finished (void *cls, int success) -{ - struct TestPutContext *test_put = cls; - - outstanding_puts--; - puts_completed++; - if (GNUNET_SCHEDULER_NO_TASK != test_put->task) - { - GNUNET_SCHEDULER_cancel (test_put->task); - } - test_put->task = GNUNET_SCHEDULER_add_now (&put_disconnect_task, test_put); - if (puts_completed != num_peers * num_peers) - return; - - GNUNET_assert (outstanding_puts == 0); - GNUNET_SCHEDULER_add_delayed (START_DELAY, &start_gets, NULL); -} - - -/** - * Set up some data, and call API PUT function - */ -static void -do_put (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - struct TestPutContext *test_put = cls; - GNUNET_HashCode key; /* Made up key to store data under */ - char data[TEST_DATA_SIZE]; /* Made up data to store */ - - test_put->task = GNUNET_SCHEDULER_NO_TASK; - if (outstanding_puts > MAX_OUTSTANDING_PUTS) - { - test_put->task = - GNUNET_SCHEDULER_add_delayed (PUT_DELAY, &do_put, test_put); - return; - } - memset (data, test_put->uid, sizeof (data)); - GNUNET_CRYPTO_hash (data, TEST_DATA_SIZE, &key); - test_put->dht_handle = GNUNET_DHT_connect (test_put->daemon->cfg, 10); - GNUNET_assert (test_put->dht_handle != NULL); - outstanding_puts++; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "PUT %u at `%s'\n", test_put->uid, - GNUNET_i2s (&test_put->daemon->id)); - GNUNET_DHT_put (test_put->dht_handle, &key, 1, route_option, - GNUNET_BLOCK_TYPE_TEST, sizeof (data), data, - GNUNET_TIME_UNIT_FOREVER_ABS, GNUNET_TIME_UNIT_FOREVER_REL, - &put_finished, test_put); - test_put->task = - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, - &put_disconnect_task, test_put); -} - - -static void -run_dht_test (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - unsigned long long i; - struct TestPutContext *test_put; - - if ((tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN) != 0) - { - ok = 1; - return; - } -#if PATH_TRACKING - route_option = - GNUNET_DHT_RO_RECORD_ROUTE | GNUNET_DHT_RO_DEMULTIPLEX_EVERYWHERE; -#else - route_option = GNUNET_DHT_RO_DEMULTIPLEX_EVERYWHERE; -#endif - die_task = - GNUNET_SCHEDULER_add_delayed (TIMEOUT, &end_badly, - "from setup puts/gets"); - FPRINTF (stderr, "Issuing %llu PUTs (one per peer)\n", - (unsigned long long) (num_peers * num_peers)); - for (i = 0; i < num_peers * num_peers; i++) - { - test_put = GNUNET_malloc (sizeof (struct TestPutContext)); - test_put->uid = i; - test_put->daemon = GNUNET_TESTING_daemon_get (pg, i % num_peers); - test_put->task = GNUNET_SCHEDULER_add_now (&do_put, test_put); - GNUNET_CONTAINER_DLL_insert (all_puts_head, all_puts_tail, test_put); - } -} - - -/** - * This function is called once testing has finished setting up the topology. - * - * @param cls unused - * @param emsg variable is NULL on success (peers connected), and non-NULL on - * failure (peers failed to connect). - */ -static void -startup_done (void *cls, const char *emsg) -{ - if (emsg != NULL) - { - FPRINTF (stderr, "Failed to setup topology: %s\n", emsg); - die_task = GNUNET_SCHEDULER_add_now (&end_badly, "topology setup failed"); - return; - } - die_task = - GNUNET_SCHEDULER_add_delayed (START_DELAY, &run_dht_test, - "from setup puts/gets"); -} - - -static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) -{ - /* Get path from configuration file */ - if (GNUNET_YES != - GNUNET_CONFIGURATION_get_value_string (cfg, "paths", "servicehome", - &test_directory)) - { - GNUNET_break (0); - ok = 404; - return; - } - if (GNUNET_SYSERR == - GNUNET_CONFIGURATION_get_value_number (cfg, "testing", "num_peers", - &num_peers)) - num_peers = DEFAULT_NUM_PEERS; - pg = GNUNET_TESTING_peergroup_start (cfg, num_peers, TIMEOUT, NULL, - &startup_done, NULL, NULL); - GNUNET_assert (NULL != pg); - shutdown_task = GNUNET_SCHEDULER_add_delayed(GNUNET_TIME_UNIT_FOREVER_REL, - &do_stop, NULL); -} - - -static int -check () -{ - int ret; - - /* Arguments for GNUNET_PROGRAM_run */ - char *const argv[] = { "test-dht-multipeer", /* Name to give running binary */ - "-c", - "test_dht_multipeer_data.conf", /* Config file to use */ - NULL - }; - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - /* Run the run function as a new program */ - ret = - GNUNET_PROGRAM_run ((sizeof (argv) / sizeof (char *)) - 1, argv, - "test-dht-multipeer", "nohelp", options, &run, &ok); - if (ret != GNUNET_OK) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "`test-dht-multipeer': Failed with error code %d\n", ret); - } - return ok; -} - - -int -main (int argc, char *argv[]) -{ - int ret; - - GNUNET_log_setup ("test-dht-multipeer", - "WARNING", - NULL); - ret = check (); - /** - * Need to remove base directory, subdirectories taken care - * of by the testing framework. - */ - if (GNUNET_DISK_directory_remove (test_directory) != GNUNET_OK) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Failed to remove testing directory %s\n", test_directory); - } - return ret; -} - -/* end of test_dht_multipeer.c */ diff --git a/src/dht/test_dht_multipeer.conf b/src/dht/test_dht_multipeer.conf new file mode 100644 index 0000000..1408f05 --- /dev/null +++ b/src/dht/test_dht_multipeer.conf @@ -0,0 +1,59 @@ +[fs] +AUTOSTART = NO + +[resolver] +AUTOSTART = NO + +[block] +plugins = test dht + +[dhtcache] +QUOTA = 1 MB +DATABASE = sqlite + +[transport] +PLUGINS = tcp + +[ats] +WAN_QUOTA_IN = 1 GB +WAN_QUOTA_OUT = 1 GB + +[arm] +DEFAULTSERVICES = dht core + +[TESTING] +WEAKRANDOM = YES + +[testbed] +OVERLAY_TOPOLOGY = FROM_FILE +OVERLAY_TOPOLOGY_FILE = test_dht_multipeer_topology.dat + +[gnunetd] +HOSTKEY = $SERVICEHOME/.hostkey + +[PATHS] +SERVICEHOME = /tmp/test-dht-multipeer/ + +[nat] +DISABLEV6 = YES +RETURN_LOCAL_ADDRESSES = YES +ENABLE_UPNP = NO +BEHIND_NAT = NO +ALLOW_NAT = NO +INTERNAL_ADDRESS = 127.0.0.1 +EXTERNAL_ADDRESS = 127.0.0.1 +USE_LOCALADDR = YES + +[dns] +AUTOSTART = NO + +[namestore] +AUTOSTART = NO + +[nse] +AUTOSTART = NO + +[vpn] +AUTOSTART=NO + + diff --git a/src/dht/test_dht_multipeer_data.conf b/src/dht/test_dht_multipeer_data.conf deleted file mode 100644 index f181594..0000000 --- a/src/dht/test_dht_multipeer_data.conf +++ /dev/null @@ -1,129 +0,0 @@ -[fs] -AUTOSTART = NO - -[resolver] -AUTOSTART = NO - -[dht] -DEBUG = NO -STOP_ON_CLOSEST = YES -AUTOSTART = YES -ACCEPT_FROM6 = ::1; -ACCEPT_FROM = 127.0.0.1; -#BINARY = /home/mrwiggles/documents/research/gnunet/gnunet-ng/src/dht/.libs/gnunet-service-dht -#PREFIX = xterm -T dht -e gdb --args -#PREFIX = valgrind --log-file=dht_%p -CONFIG = $DEFAULTCONFIG -HOME = $SERVICEHOME -HOSTNAME = localhost -PORT = 12100 -STOP_FOUND = YES -USE_MAX_HOPS = YES -MAX_HOPS = 16 -CONVERGE_BINARY = YES -CONVERGE_MODIFIER = 4 - -[block] -plugins = test dht - -[dhtcache] -QUOTA = 1 MB -DATABASE = sqlite - -[transport] -PLUGINS = tcp -DEBUG = NO -ACCEPT_FROM6 = ::1; -ACCEPT_FROM = 127.0.0.1; -NEIGHBOUR_LIMIT = 50 -BINARY = gnunet-service-transport -CONFIG = $DEFAULTCONFIG -HOME = $SERVICEHOME -HOSTNAME = localhost -PORT = 12365 - -[DHTLOG] -PLUGIN = mysql_dump - -[ats] -WAN_QUOTA_IN = 1 GB -WAN_QUOTA_OUT = 1 GB - -[core] -ACCEPT_FROM6 = ::1; -ACCEPT_FROM = 127.0.0.1; -BINARY = gnunet-service-core -CONFIG = $DEFAULTCONFIG -HOME = $SERVICEHOME -HOSTNAME = localhost -PORT = 12092 -DEBUG = NO - -[arm] -DEFAULTSERVICES = dht core -ACCEPT_FROM6 = ::1; -ACCEPT_FROM = 127.0.0.1; -BINARY = gnunet-service-arm -CONFIG = $DEFAULTCONFIG -HOME = $SERVICEHOME -HOSTNAME = localhost -PORT = 12366 -DEBUG = NO - -[transport-tcp] -TIMEOUT = 300 s -PORT = 12368 -BINDTO = 127.0.0.1 - -[DHT_TESTING] -MYSQL_LOGGING_EXTENDED = NO -MYSQL_LOGGING = NO -NUM_GETS = 5 -NUM_PUTS = 5 - -[TESTING] -TOPOLOGY = FROM_FILE -# file contains a ring -CONNECT_TOPOLOGY = NONE -# None == use all allowed connections -# BLACKLIST_TOPOLOGY = X -# No additional restrictions... - -TOPOLOGY_FILE = multipeer_topo.dat -MAX_CONCURRENT_SSH = 1 -PEERGROUP_TIMEOUT = 2400 s -USE_PROGRESSBARS = YES -#CONNECT_TOPOLOGY_OPTION = CONNECT_RANDOM_SUBSET -#CONNECT_TOPOLOGY_OPTION_MODIFIER = 2 -#LOGNMODIFIER = .65 -#PERCENTAGE = .75 -WEAKRANDOM = YES -NUM_PEERS = 10 -HOSTKEYSFILE = ../../contrib/testing_hostkeys.dat - -[gnunetd] -HOSTKEY = $SERVICEHOME/.hostkey - -[PATHS] -DEFAULTCONFIG = test_dht_multipeer_data.conf -SERVICEHOME = /tmp/test-dht-multipeer/ - -[nat] -DISABLEV6 = YES -ENABLE_UPNP = NO -BEHIND_NAT = NO -ALLOW_NAT = NO -INTERNAL_ADDRESS = 127.0.0.1 -EXTERNAL_ADDRESS = 127.0.0.1 -USE_LOCALADDR = YES - -[dns] -AUTOSTART = NO - -[namestore] -AUTOSTART = NO - -[nse] -AUTOSTART = NO - - diff --git a/src/dht/test_dht_multipeer_topology.dat b/src/dht/test_dht_multipeer_topology.dat new file mode 100644 index 0000000..2268c85 --- /dev/null +++ b/src/dht/test_dht_multipeer_topology.dat @@ -0,0 +1,11 @@ +0:1|6|8 +1:2|7|9 +2:0|3|8 +3:1|4|9 +4:0|2|5 +5:1|3|6 +6:2|4|7 +7:3|5|8 +8:4|6|9 +9:0|5|7 + diff --git a/src/dht/test_dht_tools.py b/src/dht/test_dht_tools.py new file mode 100755 index 0000000..c2e7646 --- /dev/null +++ b/src/dht/test_dht_tools.py @@ -0,0 +1,123 @@ +#!/usr/bin/python +from __future__ import print_function +import os +import sys +import shutil +import re +import subprocess +import time +import tempfile + +if os.name == "nt": + tmp = os.getenv ("TEMP") +else: + tmp = "/tmp" + +if os.name == 'nt': + pif = 'gnunet-peerinfo.exe' + get = 'gnunet-dht-get.exe' + put = 'gnunet-dht-put.exe' + arm = 'gnunet-arm.exe' +else: + pif = 'gnunet-peerinfo' + get = './gnunet-dht-get' + put = './gnunet-dht-put' + arm = 'gnunet-arm' + +tf, tempcfg = tempfile.mkstemp (prefix='test_dht_api_peer1.') +os.close (tf) + +run_pif = [pif, '-c', tempcfg, '-sq'] +run_get = [get, '-c', tempcfg] +run_put = [put, '-c', tempcfg] +run_arm = [arm, '-c', tempcfg] +debug = os.getenv ('DEBUG') +if debug: + run_arm += [debug.split (' ')] + +def cleanup (exitcode): + os.remove (tempcfg) + sys.exit (exitcode) + +def sub_run (args, want_stdo = True, want_stde = False, nofail = False): + if want_stdo: + stdo = subprocess.PIPE + else: + stdo = None + if want_stde: + stde = subprocess.PIPE + else: + stde = None + p = subprocess.Popen (args, stdout = stdo, stderr = stde) + stdo, stde = p.communicate () + if not nofail: + if p.returncode != 0: + sys.exit (p.returncode) + return (p.returncode, stdo, stde) + +def fail (result): + print (result) + r_arm (['-e'], want_stdo = False) + cleanup (1) + +def r_something (to_run, extra_args, failer = None, normal = True, **kw): + rc, stdo, stde = sub_run (to_run + extra_args, nofail = True, **kw) + if failer is not None: + failer (to_run + extra_args, rc, stdo, stde, normal) + return (rc, stdo, stde) + +def r_arm (extra_args, **kw): + return r_something (run_arm, extra_args, **kw) + +def r_pif (extra_args, **kw): + return r_something (run_pif, extra_args, **kw) + +def r_get (extra_args, **kw): + return r_something (run_get, extra_args, **kw) + +def r_put (extra_args, **kw): + return r_something (run_put, extra_args, **kw) + +def end_arm_failer (command, rc, stdo, stde, normal): + if normal: + if rc != 0: + fail ("FAIL: error running {}\nCommand output was:\n{}\n{}".format (command, stdo, stde)) + else: + if rc == 0: + fail ("FAIL: expected error while running {}\nCommand output was:\n{}\n{}".format (command, stdo, stde)) + +def print_only_failer (command, rc, stdo, stde, normal): + if normal: + if rc != 0: + print ("FAIL: error running {}\nCommand output was:\n{}\n{}".format (command, stdo, stde)) + cleanup (1) + else: + if rc == 0: + print ("FAIL: expected error while running {}\nCommand output was:\n{}\n{}".format (command, stdo, stde)) + cleanup (1) + +shutil.copyfile ('test_dht_api_peer1.conf', tempcfg) + +print ("TEST: Generating hostkey...", end='') +r_pif ([], failer = print_only_failer) +print ("PASS") + +print ("TEST: Starting ARM...", end='') +r_arm (['-s'], failer = end_arm_failer, want_stdo = False, want_stde = False) +print ("PASS") +time.sleep (1) + +print ("TEST: Testing put...", end='') +r_put (['-k', 'testkey', '-d', 'testdata', '-t', '8'], failer = end_arm_failer) +print ("PASS") +time.sleep (1) + +print ("TEST: Testing get...", end='') +rc, stdo, stde = r_get (['-k', 'testkey', '-T', '5', '-t', '8'], want_stdo = True, failer = end_arm_failer) +stdo = stdo.replace ('\r', '').splitlines () +expect = "Result 0, type 8:\ntestdata".splitlines() +if len (stdo) != 2 or len (expect) != 2 or stdo[0] != expect[0] or stdo[1] != expect[1]: + fail ("output `{}' differs from expected `{}'".format (stdo, expect)) +print ("PASS") + +r_arm (['-e', '-d'], failer = print_only_failer) diff --git a/src/dht/test_dht_tools.py.in b/src/dht/test_dht_tools.py.in new file mode 100644 index 0000000..7247836 --- /dev/null +++ b/src/dht/test_dht_tools.py.in @@ -0,0 +1,123 @@ +#!@PYTHON@ +from __future__ import print_function +import os +import sys +import shutil +import re +import subprocess +import time +import tempfile + +if os.name == "nt": + tmp = os.getenv ("TEMP") +else: + tmp = "/tmp" + +if os.name == 'nt': + pif = 'gnunet-peerinfo.exe' + get = 'gnunet-dht-get.exe' + put = 'gnunet-dht-put.exe' + arm = 'gnunet-arm.exe' +else: + pif = 'gnunet-peerinfo' + get = './gnunet-dht-get' + put = './gnunet-dht-put' + arm = 'gnunet-arm' + +tf, tempcfg = tempfile.mkstemp (prefix='test_dht_api_peer1.') +os.close (tf) + +run_pif = [pif, '-c', tempcfg, '-sq'] +run_get = [get, '-c', tempcfg] +run_put = [put, '-c', tempcfg] +run_arm = [arm, '-c', tempcfg] +debug = os.getenv ('DEBUG') +if debug: + run_arm += [debug.split (' ')] + +def cleanup (exitcode): + os.remove (tempcfg) + sys.exit (exitcode) + +def sub_run (args, want_stdo = True, want_stde = False, nofail = False): + if want_stdo: + stdo = subprocess.PIPE + else: + stdo = None + if want_stde: + stde = subprocess.PIPE + else: + stde = None + p = subprocess.Popen (args, stdout = stdo, stderr = stde) + stdo, stde = p.communicate () + if not nofail: + if p.returncode != 0: + sys.exit (p.returncode) + return (p.returncode, stdo, stde) + +def fail (result): + print (result) + r_arm (['-e'], want_stdo = False) + cleanup (1) + +def r_something (to_run, extra_args, failer = None, normal = True, **kw): + rc, stdo, stde = sub_run (to_run + extra_args, nofail = True, **kw) + if failer is not None: + failer (to_run + extra_args, rc, stdo, stde, normal) + return (rc, stdo, stde) + +def r_arm (extra_args, **kw): + return r_something (run_arm, extra_args, **kw) + +def r_pif (extra_args, **kw): + return r_something (run_pif, extra_args, **kw) + +def r_get (extra_args, **kw): + return r_something (run_get, extra_args, **kw) + +def r_put (extra_args, **kw): + return r_something (run_put, extra_args, **kw) + +def end_arm_failer (command, rc, stdo, stde, normal): + if normal: + if rc != 0: + fail ("FAIL: error running {}\nCommand output was:\n{}\n{}".format (command, stdo, stde)) + else: + if rc == 0: + fail ("FAIL: expected error while running {}\nCommand output was:\n{}\n{}".format (command, stdo, stde)) + +def print_only_failer (command, rc, stdo, stde, normal): + if normal: + if rc != 0: + print ("FAIL: error running {}\nCommand output was:\n{}\n{}".format (command, stdo, stde)) + cleanup (1) + else: + if rc == 0: + print ("FAIL: expected error while running {}\nCommand output was:\n{}\n{}".format (command, stdo, stde)) + cleanup (1) + +shutil.copyfile ('test_dht_api_peer1.conf', tempcfg) + +print ("TEST: Generating hostkey...", end='') +r_pif ([], failer = print_only_failer) +print ("PASS") + +print ("TEST: Starting ARM...", end='') +r_arm (['-s'], failer = end_arm_failer, want_stdo = False, want_stde = False) +print ("PASS") +time.sleep (1) + +print ("TEST: Testing put...", end='') +r_put (['-k', 'testkey', '-d', 'testdata', '-t', '8'], failer = end_arm_failer) +print ("PASS") +time.sleep (1) + +print ("TEST: Testing get...", end='') +rc, stdo, stde = r_get (['-k', 'testkey', '-T', '5', '-t', '8'], want_stdo = True, failer = end_arm_failer) +stdo = stdo.replace ('\r', '').splitlines () +expect = "Result 0, type 8:\ntestdata".splitlines() +if len (stdo) != 2 or len (expect) != 2 or stdo[0] != expect[0] or stdo[1] != expect[1]: + fail ("output `{}' differs from expected `{}'".format (stdo, expect)) +print ("PASS") + +r_arm (['-e', '-d'], failer = print_only_failer) diff --git a/src/dht/test_dht_tools.sh b/src/dht/test_dht_tools.sh deleted file mode 100755 index f83c26a..0000000 --- a/src/dht/test_dht_tools.sh +++ /dev/null @@ -1,73 +0,0 @@ -#!/bin/sh - -out=`mktemp /tmp/test-gnunet-dht-logXXXXXXXX` -tempcfg=`mktemp /tmp/test_dht_api_peer1.XXXXXXXX` -checkout="check.out" -armexe="gnunet-arm -c $tempcfg " -putexe="gnunet-dht-put -c $tempcfg " -getexe="gnunet-dht-get -c $tempcfg " -peerinfo="gnunet-peerinfo -c $tempcfg -sq" -stop_arm() -{ - if ! $armexe $DEBUG -e -d > $out ; then - echo "FAIL: error running $armexe" - echo "Command output was:" - cat $out - rm -f $out $tempcfg - exit 1 - fi - rm -f $out $tempcfg -} - -cp test_dht_api_peer1.conf $tempcfg - -echo -n "TEST: Generating hostkey..." -if ! $peerinfo > $out ; then - echo "FAIL: error running $peerinfo" - echo "Command output was:" - cat $out - exit 1 -fi -echo "PASS" - -echo -n "TEST: Starting ARM..." -if ! $armexe $DEBUG -s > $out ; then - echo "FAIL: error running $armexe" - echo "Command output was:" - cat $out - stop_arm - exit 1 -fi -echo "PASS" -sleep 1 - -echo -n "TEST: Testing put..." -if ! $putexe -k testkey -d testdata -t 8 > $out ; then - echo "FAIL: error running $putexe" - echo "Command output was:" - cat $out - stop_arm - exit 1 -fi -echo "PASS" -sleep 1 - -echo -n "TEST: Testing get..." -echo "Result 0, type 8:" > $checkout -echo "testdata" >> $checkout - -if ! $getexe -k testkey -T 5 -t 8 > $out ; then - echo "FAIL: error running $putexe" - echo "Command output was:" - cat $out - stop_arm - exit 1 -fi - -if ! diff --strip-trailing-cr -q $out $checkout ; then - echo "FAIL: $out and $checkout differ" - stop_arm - exit 1 -fi -echo "PASS" -stop_arm diff --git a/src/dht/test_dht_topo.c b/src/dht/test_dht_topo.c index f51f3a6..c9036d2 100644 --- a/src/dht/test_dht_topo.c +++ b/src/dht/test_dht_topo.c @@ -19,535 +19,384 @@ */ /** * @file dht/test_dht_topo.c - * + * @author Christian Grothoff * @brief Test for the dht service: store and retrieve in various topologies. - * Each peer stores it own ID in the DHT and then a different peer tries to - * retrieve that key from it. The GET starts after a first round of PUTS has - * been made. Periodically, each peer stores its ID into the DHT. If after - * a timeout no result has been returned, the test fails. + * Each peer stores a value from the DHT and then each peer tries to get each + * value from each other peer. */ #include "platform.h" -#include "gnunet_testing_lib.h" +#include "gnunet_util_lib.h" #include "gnunet_dht_service.h" - -#define REMOVE_DIR GNUNET_YES +#include "dht_test_lib.h" /** - * DIFFERENT TESTS TO RUN + * How long until we give up on fetching the data? */ -#define LINE 0 -#define TORUS 1 +#define GET_TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 120) /** - * How long until we give up on connecting the peers? + * How frequently do we execute the PUTs? */ -#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 1500) - -#define GET_TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 120) - #define PUT_FREQUENCY GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 5) -/** - * Result of the test. - */ -static int ok; /** - * Total number of peers in the test. + * Information we keep for each GET operation. */ -static unsigned long long num_peers; +struct GetOperation +{ + /** + * DLL. + */ + struct GetOperation *next; -/** - * Global configuration file - */ -static struct GNUNET_CONFIGURATION_Handle *testing_cfg; + /** + * DLL. + */ + struct GetOperation *prev; -/** - * Total number of currently running peers. - */ -static unsigned long long peers_running; + /** + * Handle for the operation. + */ + struct GNUNET_DHT_GetHandle *get; + +}; -/** - * Total number of connections in the whole network. - */ -static unsigned int total_connections; /** - * The currently running peer group. + * Result of the test. */ -static struct GNUNET_TESTING_PeerGroup *pg; +static int ok = 1; /** - * File to report results to. + * Task to do DHT_puts */ -static struct GNUNET_DISK_FileHandle *output_file; +static GNUNET_SCHEDULER_TaskIdentifier put_task; /** - * File to log connection info, statistics to. + * Task to time out / regular shutdown. */ -static struct GNUNET_DISK_FileHandle *data_file; +static GNUNET_SCHEDULER_TaskIdentifier timeout_task; /** - * Task called to disconnect peers. + * Head of list of active GET operations. */ -static GNUNET_SCHEDULER_TaskIdentifier disconnect_task; +static struct GetOperation *get_head; /** - * Task To perform tests + * Tail of list of active GET operations. */ -static GNUNET_SCHEDULER_TaskIdentifier test_task; +static struct GetOperation *get_tail; /** - * Task to do DHT_puts - */ -static GNUNET_SCHEDULER_TaskIdentifier put_task; + * Array of the testbed's peers. + */ +static struct GNUNET_TESTBED_Peer **my_peers; /** - * Task called to shutdown test. + * Number of peers to run. */ -static GNUNET_SCHEDULER_TaskIdentifier shutdown_handle; - -static char *topology_file; - -static struct GNUNET_DHT_Handle **hs; - -static struct GNUNET_DHT_GetHandle *get_h; - -static struct GNUNET_DHT_GetHandle *get_h_2; - -static struct GNUNET_DHT_GetHandle *get_h_far; - -static int found_1; +static unsigned int NUM_PEERS; -static int found_2; - -static int found_far; /** - * Which topology are we to run + * Statistics we print out. */ -static int test_topology; +static struct +{ + const char *subsystem; + const char *name; + unsigned long long total; +} stats[] = { + {"core", "# bytes decrypted", 0}, + {"core", "# bytes encrypted", 0}, + {"core", "# type maps received", 0}, + {"core", "# session keys confirmed via PONG", 0}, + {"core", "# peers connected", 0}, + {"core", "# key exchanges initiated", 0}, + {"core", "# send requests dropped (disconnected)", 0}, + {"core", "# transmissions delayed due to corking", 0}, + {"core", "# messages discarded (expired prior to transmission)", 0}, + {"core", "# messages discarded (disconnected)", 0}, + {"core", "# discarded CORE_SEND requests", 0}, + {"core", "# discarded lower priority CORE_SEND requests", 0}, + {"transport", "# bytes received via TCP", 0}, + {"transport", "# bytes transmitted via TCP", 0}, + {"dht", "# PUT messages queued for transmission", 0}, + {"dht", "# P2P PUT requests received", 0}, + {"dht", "# GET messages queued for transmission", 0}, + {"dht", "# P2P GET requests received", 0}, + {"dht", "# RESULT messages queued for transmission", 0}, + {"dht", "# P2P RESULTS received", 0}, + {"dht", "# Queued messages discarded (peer disconnected)", 0}, + {"dht", "# Peers excluded from routing due to Bloomfilter", 0}, + {"dht", "# Peer selection failed", 0}, + {"dht", "# FIND PEER requests ignored due to Bloomfilter", 0}, + {"dht", "# FIND PEER requests ignored due to lack of HELLO", 0}, + {"dht", "# P2P FIND PEER requests processed", 0}, + {"dht", "# P2P GET requests ONLY routed", 0}, + {"dht", "# Preference updates given to core", 0}, + {"dht", "# REPLIES ignored for CLIENTS (no match)", 0}, + {"dht", "# GET requests from clients injected", 0}, + {"dht", "# GET requests received from clients", 0}, + {"dht", "# GET STOP requests received from clients", 0}, + {"dht", "# ITEMS stored in datacache", 0}, + {"dht", "# Good RESULTS found in datacache", 0}, + {"dht", "# GET requests given to datacache", 0}, + {NULL, NULL, 0} +}; /** - * Check whether peers successfully shut down. + * Function called once we're done processing stats. + * + * @param cls the test context + * @param op the stats operation + * @param emsg error message on failure */ static void -shutdown_callback (void *cls, const char *emsg) +stats_finished (void *cls, + struct GNUNET_TESTBED_Operation *op, + const char *emsg) { - if (emsg != NULL) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Shutdown of peers failed!\n"); - ok++; - } - else + struct GNUNET_DHT_TEST_Context *ctx = cls; + unsigned int i; + + if (NULL != op) + GNUNET_TESTBED_operation_done (op); // needed? + if (NULL != emsg) { - GNUNET_log (GNUNET_ERROR_TYPE_INFO, "All peers successfully shut down!\n"); + fprintf (stderr, _("Gathering statistics failed: %s\n"), + emsg); + GNUNET_SCHEDULER_cancel (put_task); + GNUNET_DHT_TEST_cleanup (ctx); + return; } - GNUNET_CONFIGURATION_destroy (testing_cfg); + for (i = 0; NULL != stats[i].name; i++) + FPRINTF (stderr, + "%6s/%60s = %12llu\n", + stats[i].subsystem, + stats[i].name, + stats[i].total); + GNUNET_SCHEDULER_cancel (put_task); + GNUNET_DHT_TEST_cleanup (ctx); } -static void -shutdown_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +/** + * Function called to process statistic values from all peers. + * + * @param cls closure + * @param peer the peer the statistic belong to + * @param subsystem name of subsystem that created the statistic + * @param name the name of the datum + * @param value the current value + * @param is_persistent GNUNET_YES if the value is persistent, GNUNET_NO if not + * @return GNUNET_OK to continue, GNUNET_SYSERR to abort iteration + */ +static int +handle_stats (void *cls, + const struct GNUNET_TESTBED_Peer *peer, + const char *subsystem, + const char *name, + uint64_t value, + int is_persistent) { - GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Ending test.\n"); - - if (disconnect_task != GNUNET_SCHEDULER_NO_TASK) - { - GNUNET_SCHEDULER_cancel (disconnect_task); - disconnect_task = GNUNET_SCHEDULER_NO_TASK; - } + unsigned int i; - if (data_file != NULL) - GNUNET_DISK_file_close (data_file); - GNUNET_TESTING_daemons_stop (pg, TIMEOUT, &shutdown_callback, NULL); + for (i = 0; NULL != stats[i].name; i++) + if ( (0 == strcasecmp (subsystem, + stats[i].subsystem)) && + (0 == strcasecmp (name, + stats[i].name)) ) + stats[i].total += value; + return GNUNET_OK; } +/** + * Task run on success or timeout to clean up. + * Terminates active get operations and shuts down + * the testbed. + * + * @param cls the 'struct GNUNET_DHT_TestContext' + * @param tc scheduler context + */ static void -disconnect_peers (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +shutdown_task (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) { - unsigned int i; + struct GNUNET_DHT_TEST_Context *ctx = cls; + struct GetOperation *get_op; - GNUNET_log (GNUNET_ERROR_TYPE_INFO, "disconnecting peers\n"); - disconnect_task = GNUNET_SCHEDULER_NO_TASK; - GNUNET_SCHEDULER_cancel (put_task); - if (NULL != get_h) - GNUNET_DHT_get_stop (get_h); - if (NULL != get_h_2) - GNUNET_DHT_get_stop (get_h_2); - if (NULL != get_h_far) - GNUNET_DHT_get_stop (get_h_far); - for (i = 0; i < num_peers; i++) + while (NULL != (get_op = get_tail)) { - GNUNET_DHT_disconnect (hs[i]); + GNUNET_DHT_get_stop (get_op->get); + GNUNET_CONTAINER_DLL_remove (get_head, + get_tail, + get_op); + GNUNET_free (get_op); } - GNUNET_SCHEDULER_cancel (shutdown_handle); - shutdown_handle = GNUNET_SCHEDULER_add_now (&shutdown_task, NULL); + (void) GNUNET_TESTBED_get_statistics (NUM_PEERS, + my_peers, + &handle_stats, + &stats_finished, + ctx); } +/** + * Iterator called on each result obtained for a DHT + * operation that expects a reply + * + * @param cls closure with our 'struct GetOperation' + * @param exp when will this value expire + * @param key key of the result + * @param get_path peers on reply path (or NULL if not recorded) + * @param get_path_length number of entries in get_path + * @param put_path peers on the PUT path (or NULL if not recorded) + * @param put_path_length number of entries in get_path + * @param type type of the result + * @param size number of bytes in data + * @param data pointer to the result data + */ static void -dht_get_id_handler (void *cls, struct GNUNET_TIME_Absolute exp, - const GNUNET_HashCode * key, - const struct GNUNET_PeerIdentity *get_path, - unsigned int get_path_length, - const struct GNUNET_PeerIdentity *put_path, - unsigned int put_path_length, enum GNUNET_BLOCK_Type type, - size_t size, const void *data) +dht_get_handler (void *cls, struct GNUNET_TIME_Absolute exp, + const struct GNUNET_HashCode * key, + const struct GNUNET_PeerIdentity *get_path, + unsigned int get_path_length, + const struct GNUNET_PeerIdentity *put_path, + unsigned int put_path_length, enum GNUNET_BLOCK_Type type, + size_t size, const void *data) { - int i; + struct GetOperation *get_op = cls; + struct GNUNET_HashCode want; + struct GNUNET_DHT_TestContext *ctx; - if (sizeof (GNUNET_HashCode) == size) + if (sizeof (struct GNUNET_HashCode) != size) { - const GNUNET_HashCode *h = data; - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " Contents: %s\n", - GNUNET_h2s_full (h)); - - } - else - { - GNUNET_break(0); - } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "PATH: (get %u, put %u)\n", - get_path_length, put_path_length); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " LOCAL\n"); - for (i = get_path_length - 1; i >= 0; i--) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " %s\n", - GNUNET_i2s (&get_path[i])); + GNUNET_break (0); + return; } - for (i = put_path_length - 1; i >= 0; i--) + GNUNET_CRYPTO_hash (key, sizeof (*key), &want); + if (0 != memcmp (&want, data, sizeof (want))) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " %s\n", - GNUNET_i2s (&put_path[i])); + GNUNET_break (0); + return; } - switch ((long)cls) + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Get successful\n"); +#if 0 { - case 1: - found_1++; - GNUNET_log (GNUNET_ERROR_TYPE_INFO, "FOUND 1!\n"); - break; - case 2: - found_2++; - GNUNET_log (GNUNET_ERROR_TYPE_INFO, "FOUND 2!\n"); - break; - case 3: - found_far++; - GNUNET_log (GNUNET_ERROR_TYPE_INFO, "FOUND FAR!\n"); - break; - default: - GNUNET_break(0); + int i; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "PATH: (get %u, put %u)\n", + get_path_length, put_path_length); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " LOCAL\n"); + for (i = get_path_length - 1; i >= 0; i--) + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " %s\n", + GNUNET_i2s (&get_path[i])); + for (i = put_path_length - 1; i >= 0; i--) + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " %s\n", + GNUNET_i2s (&put_path[i])); } - if ( (TORUS == test_topology) && - ( (found_1 == 0) || (found_2 == 0) || (found_far == 0)) ) +#endif + GNUNET_DHT_get_stop (get_op->get); + GNUNET_CONTAINER_DLL_remove (get_head, + get_tail, + get_op); + GNUNET_free (get_op); + if (NULL != get_head) return; + /* all DHT GET operations successful; terminate! */ ok = 0; - GNUNET_SCHEDULER_cancel (disconnect_task); - disconnect_task = GNUNET_SCHEDULER_add_now (&disconnect_peers, NULL); + ctx = GNUNET_SCHEDULER_cancel (timeout_task); + timeout_task = GNUNET_SCHEDULER_add_now (&shutdown_task, ctx); } -static void -do_test (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - struct GNUNET_TESTING_Daemon *d; - struct GNUNET_TESTING_Daemon *d2; - struct GNUNET_TESTING_Daemon *d_far; - struct GNUNET_TESTING_Daemon *o; - struct GNUNET_TESTING_Daemon *aux; - const char *id_aux; - const char *id_origin = "FC74"; - const char *id_near = "9P6V"; - const char *id_near2 = "2GDS"; - const char *id_far = "KPST"; - unsigned int i; - - d = d2 = d_far = o = NULL; - found_1 = found_2 = found_far = 0; - if (LINE == test_topology) - { - o = GNUNET_TESTING_daemon_get (pg, 0); - d = GNUNET_TESTING_daemon_get (pg, 4); - } - else if (TORUS == test_topology) - { - for (i = 0; i < num_peers; i++) - { - aux = GNUNET_TESTING_daemon_get (pg, i); - id_aux = GNUNET_i2s (&aux->id); - if (strcmp (id_aux, id_origin) == 0) - o = aux; - if (strcmp (id_aux, id_far) == 0) - d_far = aux; - if (strcmp (id_aux, id_near) == 0) - d = aux; - if (strcmp (id_aux, id_near2) == 0) - d2 = aux; - } - if ((NULL == o) || (NULL == d) || (NULL == d2) || (NULL == d_far)) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "Peers not found (hostkey file changed?)\n"); - GNUNET_SCHEDULER_cancel (disconnect_task); - disconnect_task = GNUNET_SCHEDULER_add_now (&disconnect_peers, NULL); - return; - } - } - else - { - GNUNET_assert (0); - } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test_task\nfrom %s\n", - GNUNET_h2s_full (&o->id.hashPubKey)); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " looking for %s\n", - GNUNET_h2s_full (&d->id.hashPubKey)); - get_h = GNUNET_DHT_get_start (hs[0], - GNUNET_BLOCK_TYPE_TEST, /* type */ - &d->id.hashPubKey, /*key to search */ - 4U, /* replication level */ - GNUNET_DHT_RO_RECORD_ROUTE | GNUNET_DHT_RO_DEMULTIPLEX_EVERYWHERE, NULL, /* xquery */ - 0, /* xquery bits */ - &dht_get_id_handler, (void *)1); - if (TORUS == test_topology) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " looking for %s\n", - GNUNET_h2s_full (&d2->id.hashPubKey)); - get_h_2 = GNUNET_DHT_get_start (hs[0], - GNUNET_BLOCK_TYPE_TEST, /* type */ - &d2->id.hashPubKey, /*key to search */ - 4U, /* replication level */ - GNUNET_DHT_RO_RECORD_ROUTE | GNUNET_DHT_RO_DEMULTIPLEX_EVERYWHERE, NULL, /* xquery */ - 0, /* xquery bits */ - &dht_get_id_handler, (void *)2); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " looking for %s\n", - GNUNET_h2s_full (&d_far->id.hashPubKey)); - get_h_far = GNUNET_DHT_get_start (hs[0], - GNUNET_BLOCK_TYPE_TEST, /* type */ - &d_far->id.hashPubKey, /*key to search */ - 4U, /* replication level */ - GNUNET_DHT_RO_RECORD_ROUTE | GNUNET_DHT_RO_DEMULTIPLEX_EVERYWHERE, NULL, /* xquery */ - 0, /* xquery bits */ - &dht_get_id_handler, (void *)3); - } - GNUNET_SCHEDULER_cancel (disconnect_task); - disconnect_task = - GNUNET_SCHEDULER_add_delayed (GET_TIMEOUT, &disconnect_peers, NULL); -} - /** - * Task to put the id of each peer into teh DHT. + * Task to put the id of each peer into the DHT. * - * @param cls Closure (unused) + * @param cls array with NUM_PEERS DHT handles * @param tc Task context - * */ static void -put_id (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +do_puts (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) { - struct GNUNET_TESTING_Daemon *d; + struct GNUNET_DHT_Handle **hs = cls; + struct GNUNET_HashCode key; + struct GNUNET_HashCode value; unsigned int i; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "putting id's in DHT\n"); - for (i = 0; i < num_peers; i++) + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Putting values into DHT\n"); + for (i = 0; i < NUM_PEERS; i++) { - d = GNUNET_TESTING_daemon_get (pg, i); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " putting into DHT: %s\n", - GNUNET_h2s_full (&d->id.hashPubKey)); - GNUNET_DHT_put (hs[i], &d->id.hashPubKey, 10U, + GNUNET_CRYPTO_hash (&i, sizeof (i), &key); + GNUNET_CRYPTO_hash (&key, sizeof (key), &value); + GNUNET_DHT_put (hs[i], &key, 10U, GNUNET_DHT_RO_RECORD_ROUTE | GNUNET_DHT_RO_DEMULTIPLEX_EVERYWHERE, - GNUNET_BLOCK_TYPE_TEST, sizeof (struct GNUNET_PeerIdentity), - (const char *) &d->id, GNUNET_TIME_UNIT_FOREVER_ABS, - GNUNET_TIME_UNIT_FOREVER_REL, NULL, NULL); - + GNUNET_BLOCK_TYPE_TEST, + sizeof (value), &value, + GNUNET_TIME_UNIT_FOREVER_ABS, + GNUNET_TIME_UNIT_FOREVER_REL, + NULL, NULL); } - put_task = GNUNET_SCHEDULER_add_delayed (PUT_FREQUENCY, &put_id, NULL); - if (GNUNET_SCHEDULER_NO_TASK == test_task) - test_task = GNUNET_SCHEDULER_add_now (&do_test, NULL); + put_task = GNUNET_SCHEDULER_add_delayed (PUT_FREQUENCY, + &do_puts, hs); } /** - * peergroup_ready: start test when all peers are connected - * - * @param cls closure - * @param emsg error message - * - */ -static void -peergroup_ready (void *cls, const char *emsg) -{ - struct GNUNET_TESTING_Daemon *d; - char *buf; - int buf_len; - unsigned int i; - - if (emsg != NULL) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Peergroup callback called with error, aborting test!\n"); - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "Error from testing: `%s'\n", - emsg); - ok++; - GNUNET_TESTING_daemons_stop (pg, TIMEOUT, &shutdown_callback, NULL); - return; - } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Peer Group started successfully with %u connections\n", - total_connections); - if (data_file != NULL) - { - buf = NULL; - buf_len = GNUNET_asprintf (&buf, "CONNECTIONS_0: %u\n", total_connections); - if (buf_len > 0) - GNUNET_DISK_file_write (data_file, buf, buf_len); - GNUNET_free (buf); - } - peers_running = GNUNET_TESTING_daemons_running (pg); - - GNUNET_assert (peers_running == num_peers); - hs = GNUNET_malloc (num_peers * sizeof (struct GNUNET_DHT_Handle *)); - for (i = 0; i < num_peers; i++) - { - d = GNUNET_TESTING_daemon_get (pg, i); - hs[i] = GNUNET_DHT_connect (d->cfg, 32); - } - - test_task = GNUNET_SCHEDULER_NO_TASK; - put_task = GNUNET_SCHEDULER_add_now (&put_id, NULL); - disconnect_task = - GNUNET_SCHEDULER_add_delayed (GET_TIMEOUT, &disconnect_peers, NULL); - -} - - -/** - * Function that will be called whenever two daemons are connected by - * the testing library. + * Main function of the test. * - * @param cls closure - * @param first peer id for first daemon - * @param second peer id for the second daemon - * @param distance distance between the connected peers - * @param first_cfg config for the first daemon - * @param second_cfg config for the second daemon - * @param first_daemon handle for the first daemon - * @param second_daemon handle for the second daemon - * @param emsg error message (NULL on success) - */ -static void -connect_cb (void *cls, const struct GNUNET_PeerIdentity *first, - const struct GNUNET_PeerIdentity *second, uint32_t distance, - const struct GNUNET_CONFIGURATION_Handle *first_cfg, - const struct GNUNET_CONFIGURATION_Handle *second_cfg, - struct GNUNET_TESTING_Daemon *first_daemon, - struct GNUNET_TESTING_Daemon *second_daemon, const char *emsg) -{ - if (emsg == NULL) - { - total_connections++; - GNUNET_PEER_intern (first); - GNUNET_PEER_intern (second); - } - else - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Problem with new connection (%s)\n", emsg); - } -} - - -/** - * run: load configuration options and schedule test to run (start peergroup) - * @param cls closure - * @param args argv - * @param cfgfile configuration file name (can be NULL) - * @param cfg configuration handle + * @param cls closure (NULL) + * @param ctx argument to give to GNUNET_DHT_TEST_cleanup on test end + * @param num_peers number of peers that are running + * @param peers array of peers + * @param dhts handle to each of the DHTs of the peers */ static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) +run (void *cls, + struct GNUNET_DHT_TEST_Context *ctx, + unsigned int num_peers, + struct GNUNET_TESTBED_Peer **peers, + struct GNUNET_DHT_Handle **dhts) { - char *temp_str; - struct GNUNET_TESTING_Host *hosts; - char *data_filename; - - ok = 1; - testing_cfg = GNUNET_CONFIGURATION_dup (cfg); - - GNUNET_log_setup ("test_dht_topo", - "WARNING", - NULL); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Starting daemons.\n"); - GNUNET_CONFIGURATION_set_value_string (testing_cfg, "testing", - "use_progressbars", "YES"); - if (GNUNET_OK != - GNUNET_CONFIGURATION_get_value_number (testing_cfg, "testing", - "num_peers", &num_peers)) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "Option TESTING:NUM_PEERS is required!\n"); - return; - } - - if (GNUNET_OK != - GNUNET_CONFIGURATION_get_value_string (testing_cfg, "testing", - "topology_output_file", - &topology_file)) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "Option test_dht_topo:topology_output_file is required!\n"); - return; - } - - if (GNUNET_OK == - GNUNET_CONFIGURATION_get_value_string (testing_cfg, "test_dht_topo", - "data_output_file", - &data_filename)) + unsigned int i; + unsigned int j; + struct GNUNET_HashCode key; + struct GetOperation *get_op; + + GNUNET_assert (NUM_PEERS == num_peers); + my_peers = peers; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Peers setup, starting test\n"); + put_task = GNUNET_SCHEDULER_add_now (&do_puts, dhts); + for (i=0;iget = GNUNET_DHT_get_start (dhts[j], + GNUNET_BLOCK_TYPE_TEST, /* type */ + &key, /*key to search */ + 4U, /* replication level */ + GNUNET_DHT_RO_RECORD_ROUTE | GNUNET_DHT_RO_DEMULTIPLEX_EVERYWHERE, + NULL, /* xquery */ + 0, /* xquery bits */ + &dht_get_handler, get_op); } } - - if (GNUNET_YES == - GNUNET_CONFIGURATION_get_value_string (cfg, "test_dht_topo", - "output_file", &temp_str)) - { - output_file = - GNUNET_DISK_file_open (temp_str, - GNUNET_DISK_OPEN_READWRITE | - GNUNET_DISK_OPEN_CREATE, - GNUNET_DISK_PERM_USER_READ | - GNUNET_DISK_PERM_USER_WRITE); - if (output_file == NULL) - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Failed to open %s for output!\n", - temp_str); - } - GNUNET_free_non_null (temp_str); - - hosts = GNUNET_TESTING_hosts_load (testing_cfg); - - pg = GNUNET_TESTING_peergroup_start (testing_cfg, num_peers, TIMEOUT, - &connect_cb, &peergroup_ready, NULL, - hosts); - GNUNET_assert (pg != NULL); - shutdown_handle = - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, - &shutdown_task, NULL); + timeout_task = GNUNET_SCHEDULER_add_delayed (GET_TIMEOUT, + &shutdown_task, ctx); } @@ -557,62 +406,42 @@ run (void *cls, char *const *args, const char *cfgfile, int main (int xargc, char *xargv[]) { - static struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - static char *const argv_torus[] = { "test-dht-2dtorus", - "-c", - "test_dht_2dtorus.conf", - NULL - }; - static char *const argv_line[] = { "test-dht-line", - "-c", - "test_dht_line.conf", - NULL - }; - char *const *argv; - int argc; + const char *cfg_filename; + const char *test_name; - if (strstr (xargv[0], "test_dht_2dtorus") != NULL) + if (NULL != strstr (xargv[0], "test_dht_2dtorus")) { - argv = argv_torus; - argc = sizeof (argv_torus) / sizeof (char *); - test_topology = TORUS; + cfg_filename = "test_dht_2dtorus.conf"; + test_name = "test-dht-2dtorus"; + NUM_PEERS = 16; } - else if (strstr (xargv[0], "test_dht_line") != NULL) + else if (NULL != strstr (xargv[0], "test_dht_line")) { - argv = argv_line; - argc = sizeof (argv_line) / sizeof (char *); - test_topology = LINE; + cfg_filename = "test_dht_line.conf"; + test_name = "test-dht-line"; + NUM_PEERS = 5; } - else + else if (NULL != strstr (xargv[0], "test_dht_twopeer")) { - GNUNET_break (0); - return 1; + cfg_filename = "test_dht_line.conf"; + test_name = "test-dht-twopeer"; + NUM_PEERS = 2; } - GNUNET_PROGRAM_run (argc - 1, argv, - xargv[0], - gettext_noop ("Test dht in different topologies."), - options, - &run, NULL); -#if REMOVE_DIR - GNUNET_DISK_directory_remove ("/tmp/test_dht_topo"); -#endif - if (0 == found_1) + else if (NULL != strstr (xargv[0], "test_dht_multipeer")) { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "ID 1 not found!\n"); + cfg_filename = "test_dht_multipeer.conf"; + test_name = "test-dht-multipeer"; + NUM_PEERS = 10; } - if (TORUS == test_topology) + else { - if (0 == found_2) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "ID 2 not found!\n"); - } - if (0 == found_far) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "ID far not found!\n"); - } + GNUNET_break (0); + return 1; } + GNUNET_DHT_TEST_run (test_name, + cfg_filename, + NUM_PEERS, + &run, NULL); return ok; } diff --git a/src/dht/test_dht_twopeer.c b/src/dht/test_dht_twopeer.c deleted file mode 100644 index f0ac05b..0000000 --- a/src/dht/test_dht_twopeer.c +++ /dev/null @@ -1,494 +0,0 @@ -/* - This file is part of GNUnet. - (C) 2009 Christian Grothoff (and other contributing authors) - - GNUnet is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published - by the Free Software Foundation; either version 3, or (at your - option) any later version. - - GNUnet is distributed in the hope that it will be useful, but - WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - General Public License for more details. - - You should have received a copy of the GNU General Public License - along with GNUnet; see the file COPYING. If not, write to the - Free Software Foundation, Inc., 59 Temple Place - Suite 330, - Boston, MA 02111-1307, USA. -*/ -/** - * @file dht/test_dht_twopeer.c - * @brief base testcase for testing DHT service with - * two running peers - */ -#include "platform.h" -#include "gnunet_testing_lib.h" -#include "gnunet_core_service.h" -#include "gnunet_dht_service.h" - -/* DEFINES */ -#define MAX_GET_ATTEMPTS 10 - -#define TIMEOUT GNUNET_TIME_relative_multiply(GNUNET_TIME_UNIT_MINUTES, 5) - -#define DEFAULT_NUM_PEERS 2 - -/* Structs */ - -struct PeerGetContext -{ - struct GNUNET_PeerIdentity *peer; - - struct GNUNET_DHT_Handle *dht_handle; - - struct GNUNET_DHT_GetHandle *get_handle; - - unsigned int get_attempts; - - GNUNET_SCHEDULER_TaskIdentifier retry_task; -}; - -/* Globals */ -static char *test_directory; - -static struct PeerGetContext curr_get_ctx; - -static unsigned int expected_connections; - -static unsigned long long peers_left; - -static struct GNUNET_TESTING_PeerGroup *pg; - -static unsigned long long num_peers; - -static unsigned int total_gets; - -static unsigned int gets_succeeded; - -static unsigned int total_connections; - -static unsigned int failed_connections; - -static GNUNET_SCHEDULER_TaskIdentifier die_task; - -static int ok; - -static struct GNUNET_PeerIdentity peer1id; - -static struct GNUNET_PeerIdentity peer2id; - -static struct GNUNET_DHT_Handle *peer1dht; - -static struct GNUNET_DHT_Handle *peer2dht; - -/** - * Check whether peers successfully shut down. - */ -static void -shutdown_callback (void *cls, const char *emsg) -{ - if (emsg != NULL) - { - if (ok == 0) - ok = 2; - } -} - -static void -finish_testing (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - GNUNET_assert (pg != NULL); - GNUNET_assert (peer1dht != NULL); - GNUNET_assert (peer2dht != NULL); - GNUNET_DHT_disconnect (peer1dht); - GNUNET_DHT_disconnect (peer2dht); - GNUNET_TESTING_daemons_stop (pg, TIMEOUT, &shutdown_callback, NULL); - pg = NULL; - ok = 0; -} - -static void -end_badly_cont (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - if (peer1dht != NULL) - GNUNET_DHT_disconnect (peer1dht); - - if (peer2dht != NULL) - GNUNET_DHT_disconnect (peer2dht); - - if (pg != NULL) - { - GNUNET_TESTING_daemons_stop (pg, TIMEOUT, &shutdown_callback, NULL); - pg = NULL; - } - - if (curr_get_ctx.retry_task != GNUNET_SCHEDULER_NO_TASK) - { - GNUNET_SCHEDULER_cancel (curr_get_ctx.retry_task); - curr_get_ctx.retry_task = GNUNET_SCHEDULER_NO_TASK; - } -} - - -static void -end_badly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - const char *emsg = cls; - - FPRINTF (stderr, "Error: %s\n", emsg); - if (curr_get_ctx.retry_task != GNUNET_SCHEDULER_NO_TASK) - { - GNUNET_SCHEDULER_cancel (curr_get_ctx.retry_task); - curr_get_ctx.retry_task = GNUNET_SCHEDULER_NO_TASK; - } - if (curr_get_ctx.get_handle != NULL) - { - GNUNET_DHT_get_stop (curr_get_ctx.get_handle); - } - - GNUNET_SCHEDULER_add_now (&end_badly_cont, NULL); - ok = 1; -} - - -/* Forward declaration */ -static void -do_get (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc); - -/** - * Iterator called on each result obtained for a DHT - * operation that expects a reply - * - * @param cls closure - * @param exp when will this value expire - * @param key key of the result - * @param type type of the result - * @param size number of bytes in data - * @param data pointer to the result data - */ -static void -get_result_iterator (void *cls, struct GNUNET_TIME_Absolute exp, - const GNUNET_HashCode * key, - const struct GNUNET_PeerIdentity *get_path, - unsigned int get_path_length, - const struct GNUNET_PeerIdentity *put_path, - unsigned int put_path_length, enum GNUNET_BLOCK_Type type, - size_t size, const void *data) -{ - struct PeerGetContext *get_context = cls; - - if (0 != - memcmp (&get_context->peer->hashPubKey, key, sizeof (GNUNET_HashCode))) - { - FPRINTF (stderr, "%s", "??\n"); - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "Key returned is not the same key as was searched for!\n"); - GNUNET_SCHEDULER_cancel (die_task); - die_task = - GNUNET_SCHEDULER_add_now (&end_badly, - "key mismatch in get response!\n"); - return; - } - if (get_context->retry_task != GNUNET_SCHEDULER_NO_TASK) - { - GNUNET_SCHEDULER_cancel (get_context->retry_task); - get_context->retry_task = GNUNET_SCHEDULER_NO_TASK; - } - - if (get_context->peer == &peer2id) - { - get_context->peer = &peer1id; - get_context->dht_handle = peer2dht; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Received first correct GET request response!\n"); - GNUNET_DHT_get_stop (get_context->get_handle); - GNUNET_SCHEDULER_add_now (&do_get, get_context); - } - else - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Received second correct GET request response!\n"); - GNUNET_SCHEDULER_cancel (die_task); - GNUNET_DHT_get_stop (get_context->get_handle); - die_task = GNUNET_SCHEDULER_add_now (&finish_testing, NULL); - } - -} - -static void -stop_retry_get (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc); - - -static void -get_stop_finished (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - struct PeerGetContext *get_context = cls; - - if (get_context->get_attempts >= MAX_GET_ATTEMPTS) - { - FPRINTF (stderr, "%s", "?\n"); - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "Too many attempts failed, ending test!\n", - get_context->get_attempts); - GNUNET_SCHEDULER_cancel (die_task); - die_task = - GNUNET_SCHEDULER_add_now (&end_badly, - "GET attempt failed, ending test!\n"); - return; - } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Get attempt %u failed, retrying request!\n", - get_context->get_attempts); - FPRINTF (stderr, "%s", "."); - get_context->get_attempts++; - get_context->retry_task = - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply - (GNUNET_TIME_UNIT_SECONDS, 60), - &stop_retry_get, get_context); - get_context->get_handle = - GNUNET_DHT_get_start (get_context->dht_handle, - GNUNET_BLOCK_TYPE_DHT_HELLO, - &get_context->peer->hashPubKey, 1, - GNUNET_DHT_RO_NONE, NULL, 0, &get_result_iterator, - get_context); -} - - -static void -stop_retry_get (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - struct PeerGetContext *get_context = cls; - - get_context->retry_task = GNUNET_SCHEDULER_NO_TASK; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Get attempt %u failed, canceling request!\n", - get_context->get_attempts); - GNUNET_DHT_get_stop (get_context->get_handle); - get_context->get_handle = NULL; - GNUNET_SCHEDULER_add_now (&get_stop_finished, get_context); -} - - -static void -do_get (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - struct PeerGetContext *get_context = cls; - - get_context->retry_task = - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply - (GNUNET_TIME_UNIT_SECONDS, 10), - &stop_retry_get, get_context); - get_context->get_handle = - GNUNET_DHT_get_start (get_context->dht_handle, - GNUNET_BLOCK_TYPE_DHT_HELLO, - &get_context->peer->hashPubKey, 1, - GNUNET_DHT_RO_FIND_PEER, NULL, 0, - &get_result_iterator, get_context); -} - - -static void -topology_callback (void *cls, const struct GNUNET_PeerIdentity *first, - const struct GNUNET_PeerIdentity *second, uint32_t distance, - const struct GNUNET_CONFIGURATION_Handle *first_cfg, - const struct GNUNET_CONFIGURATION_Handle *second_cfg, - struct GNUNET_TESTING_Daemon *first_daemon, - struct GNUNET_TESTING_Daemon *second_daemon, - const char *emsg) -{ - if (emsg == NULL) - { - total_connections++; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "connected peer %s to peer %s, distance %u\n", - first_daemon->shortname, second_daemon->shortname, distance); - } - else - { - failed_connections++; - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Failed to connect peer %s to peer %s with error :\n%s\n", - first_daemon->shortname, second_daemon->shortname, emsg); - } - - if (total_connections == expected_connections) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Created %d total connections, which is our target number! Starting next phase of testing.\n", - total_connections); - GNUNET_SCHEDULER_cancel (die_task); - die_task = - GNUNET_SCHEDULER_add_delayed (TIMEOUT, &end_badly, - "Timeout trying to GET"); - - curr_get_ctx.dht_handle = peer1dht; - curr_get_ctx.peer = &peer2id; - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply - (GNUNET_TIME_UNIT_SECONDS, 2), &do_get, - &curr_get_ctx); - } - else if (total_connections + failed_connections == expected_connections) - { - GNUNET_SCHEDULER_cancel (die_task); - die_task = - GNUNET_SCHEDULER_add_now (&end_badly, - "from topology_callback (too many failed connections)"); - } -} - - -static void -connect_topology (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - expected_connections = -1; - if ((pg != NULL) && (peers_left == 0)) - expected_connections = - GNUNET_TESTING_connect_topology (pg, GNUNET_TESTING_TOPOLOGY_CLIQUE, - GNUNET_TESTING_TOPOLOGY_OPTION_ALL, - 0.0, TIMEOUT, 12, NULL, NULL); - - GNUNET_SCHEDULER_cancel (die_task); - if (expected_connections == GNUNET_SYSERR) - die_task = - GNUNET_SCHEDULER_add_now (&end_badly, - "from connect topology (bad return)"); - else - die_task = - GNUNET_SCHEDULER_add_delayed (TIMEOUT, &end_badly, - "from connect topology (timeout)"); -} - - -static void -peers_started_callback (void *cls, const struct GNUNET_PeerIdentity *id, - const struct GNUNET_CONFIGURATION_Handle *cfg, - struct GNUNET_TESTING_Daemon *d, const char *emsg) -{ - if (emsg != NULL) - { - FPRINTF (stderr, "Failed to start daemon: `%s'\n", emsg); - return; - } - GNUNET_assert (id != NULL); - if (peers_left == num_peers) - { - memcpy (&peer1id, id, sizeof (struct GNUNET_PeerIdentity)); - peer1dht = GNUNET_DHT_connect (cfg, 100); - if (peer1dht == NULL) - { - GNUNET_SCHEDULER_cancel (die_task); - die_task = - GNUNET_SCHEDULER_add_now (&end_badly, "Failed to get dht handle!\n"); - } - } - else - { - memcpy (&peer2id, id, sizeof (struct GNUNET_PeerIdentity)); - peer2dht = GNUNET_DHT_connect (cfg, 100); - if (peer2dht == NULL) - { - GNUNET_SCHEDULER_cancel (die_task); - die_task = - GNUNET_SCHEDULER_add_now (&end_badly, "Failed to get dht handle!\n"); - } - } - - - peers_left--; - - if (peers_left == 0) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "All %d daemons started, now connecting peers!\n", num_peers); - GNUNET_SCHEDULER_cancel (die_task); - /* Set up task in case topology creation doesn't finish - * within a reasonable amount of time */ - die_task = - GNUNET_SCHEDULER_add_delayed (TIMEOUT, &end_badly, - "from peers_started_callback"); - - GNUNET_SCHEDULER_add_now (&connect_topology, NULL); - ok = 0; - } -} - - -static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) -{ - - if (GNUNET_YES != - GNUNET_CONFIGURATION_get_value_string (cfg, "paths", "servicehome", - &test_directory)) - { - ok = 404; - return; - } - - if (GNUNET_SYSERR == - GNUNET_CONFIGURATION_get_value_number (cfg, "testing", "num_peers", - &num_peers)) - num_peers = DEFAULT_NUM_PEERS; - - peers_left = num_peers; - total_gets = num_peers; - gets_succeeded = 0; - /* Set up a task to end testing if peer start fails */ - die_task = - GNUNET_SCHEDULER_add_delayed (TIMEOUT, &end_badly, - "didn't start all daemons in reasonable amount of time!!!"); - - pg = GNUNET_TESTING_daemons_start (cfg, num_peers, 10, num_peers, TIMEOUT, - NULL, NULL, &peers_started_callback, NULL, - &topology_callback, NULL, NULL); - -} - -static int -check () -{ - int ret; - - char *const argv[] = { "test-dht-twopeer", - "-c", - "test_dht_twopeer_data.conf", - NULL - }; - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - ret = - GNUNET_PROGRAM_run ((sizeof (argv) / sizeof (char *)) - 1, argv, - "test-dht-twopeer", "nohelp", options, &run, &ok); - if (ret != GNUNET_OK) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "`test-dht-twopeer': Failed with error code %d\n", ret); - } - return ok; -} - -int -main (int argc, char *argv[]) -{ - int ret; - - GNUNET_log_setup ("test-dht-twopeer", - "WARNING", - NULL); - ret = check (); - /** - * Need to remove base directory, subdirectories taken care - * of by the testing framework. - */ - if (GNUNET_DISK_directory_remove (test_directory) != GNUNET_OK) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Failed to remove testing directory %s\n", test_directory); - } - return ret; -} - -/* end of test_dht_twopeer.c */ diff --git a/src/dht/test_dht_twopeer_data.conf b/src/dht/test_dht_twopeer_data.conf deleted file mode 100644 index 2889a41..0000000 --- a/src/dht/test_dht_twopeer_data.conf +++ /dev/null @@ -1,76 +0,0 @@ -[PATHS] -DEFAULTCONFIG = test_dht_twopeer_data.conf -SERVICEHOME = /tmp/test-dht-twopeer/ - -[resolver] -AUTOSTART = YES - -[dht] -DEBUG = NO -AUTOSTART = YES -#PREFIX = xterm -T dht -e gdb --args -PORT = 12100 -BINARY = gnunet-service-dht - -[block] -plugins = test dht dns - -[dhtcache] -QUOTA = 1 MB -DATABASE = sqlite - -[transport] -PLUGINS = tcp -DEBUG = NO -NEIGHBOUR_LIMIT = 50 -PORT = 12365 - -[ats] -WAN_QUOTA_IN = 1 GB -WAN_QUOTA_OUT = 1 GB - -[core] -HOSTNAME = localhost -PORT = 12092 - -[arm] -DEFAULTSERVICES = core dht -PORT = 12366 -DEBUG = NO - -[transport-tcp] -TIMEOUT = 300 s -PORT = 12368 -BINDTO = 127.0.0.1 - -[TESTING] -WEAKRANDOM = YES -NUM_PEERS = 2 -HOSTKEYSFILE = ../../contrib/testing_hostkeys.dat - -[gnunetd] -HOSTKEY = $SERVICEHOME/.hostkey - -[nat] -DISABLEV6 = YES -ENABLE_UPNP = NO -BEHIND_NAT = NO -ALLOW_NAT = NO -INTERNAL_ADDRESS = 127.0.0.1 -EXTERNAL_ADDRESS = 127.0.0.1 -USE_LOCALADDR = YES - -[dns] -AUTOSTART = NO - -[mesh] -AUTOSTART = NO - -[nse] -AUTOSTART = NO - -[fs] -AUTOSTART = NO - -[namestore] -AUTOSTART = NO diff --git a/src/dht/test_dht_twopeer_get_put.c b/src/dht/test_dht_twopeer_get_put.c deleted file mode 100644 index 3271d04..0000000 --- a/src/dht/test_dht_twopeer_get_put.c +++ /dev/null @@ -1,590 +0,0 @@ -/* - This file is part of GNUnet. - (C) 2009 Christian Grothoff (and other contributing authors) - - GNUnet is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published - by the Free Software Foundation; either version 3, or (at your - option) any later version. - - GNUnet is distributed in the hope that it will be useful, but - WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - General Public License for more details. - - You should have received a copy of the GNU General Public License - along with GNUnet; see the file COPYING. If not, write to the - Free Software Foundation, Inc., 59 Temple Place - Suite 330, - Boston, MA 02111-1307, USA. -*/ -/** - * @file dht/test_dht_twopeer_get_put.c - * @brief base testcase for testing DHT service with - * two running peers. - * - * This testcase starts peers using the GNUNET_TESTING_daemons_start - * function call. On peer start, connects to the peers DHT service - * by calling GNUNET_DHT_connected. Once notified about all peers - * being started (by the peers_started_callback function), calls - * GNUNET_TESTING_connect_topology, which connects the peers in a - * "straight line" topology. On notification that all peers have - * been properly connected, calls the do_get function which initiates - * a GNUNET_DHT_get from the *second* peer. Once the GNUNET_DHT_get - * function starts, runs the do_put function to insert data at the first peer. - * If the GET is successful, schedules finish_testing - * to stop the test and shut down peers. If GET is unsuccessful - * after GET_TIMEOUT seconds, prints an error message and shuts down - * the peers. - */ -#include "platform.h" -#include "gnunet_testing_lib.h" -#include "gnunet_core_service.h" -#include "gnunet_dht_service.h" -#include "block_dns.h" -#include "gnunet_signatures.h" - -/* DEFINES */ -#define VERBOSE GNUNET_NO - -/* Timeout for entire testcase */ -#define TIMEOUT GNUNET_TIME_relative_multiply(GNUNET_TIME_UNIT_SECONDS, 40) - -/* Timeout for waiting for replies to get requests */ -#define GET_TIMEOUT GNUNET_TIME_relative_multiply(GNUNET_TIME_UNIT_SECONDS, 30) - -/* If number of peers not in config file, use this number */ -#define DEFAULT_NUM_PEERS 2 - -#define DNS GNUNET_NO - -/* Globals */ - -/** - * Directory to store temp data in, defined in config file - */ -static char *test_directory; - -/** - * Variable used to store the number of connections we should wait for. - */ -static unsigned int expected_connections; - -/** - * Variable used to keep track of how many peers aren't yet started. - */ -static unsigned long long peers_left; - -/** - * Handle to the set of all peers run for this test. - */ -static struct GNUNET_TESTING_PeerGroup *pg; - -/** - * Global handle we will use for GET requests. - */ -struct GNUNET_DHT_GetHandle *global_get_handle; - - -/** - * Total number of peers to run, set based on config file. - */ -static unsigned long long num_peers; - -/** - * Global used to count how many connections we have currently - * been notified about (how many times has topology_callback been called - * with success?) - */ -static unsigned int total_connections; - -/** - * Global used to count how many failed connections we have - * been notified about (how many times has topology_callback - * been called with failure?) - */ -static unsigned int failed_connections; - -/* Task handle to use to schedule test failure */ -GNUNET_SCHEDULER_TaskIdentifier die_task; - -/* Global return value (0 for success, anything else for failure) */ -static int ok; - -#if DNS -struct GNUNET_DNS_Record data; -#endif - -/** - * Peer identity of the first peer started. - */ -static struct GNUNET_PeerIdentity peer1id; - -/** - * Peer identity of the second peer started. - */ -static struct GNUNET_PeerIdentity peer2id; - -/** - * Handle to the first peers DHT service (via the API) - */ -static struct GNUNET_DHT_Handle *peer1dht; - -/** - * Handle to the second peers DHT service (via the API) - */ -static struct GNUNET_DHT_Handle *peer2dht; - -static void -do_put (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc); - -/** - * Check whether peers successfully shut down. - */ -void -shutdown_callback (void *cls, const char *emsg) -{ - if (emsg != NULL) - { - if (ok == 0) - ok = 2; - } -} - -/** - * Function scheduled to be run on the successful completion of this - * testcase. Specifically, called when our get request completes. - */ -static void -finish_testing (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - GNUNET_assert (pg != NULL); - GNUNET_assert (peer1dht != NULL); - GNUNET_assert (peer2dht != NULL); - GNUNET_DHT_disconnect (peer1dht); - GNUNET_DHT_disconnect (peer2dht); - GNUNET_TESTING_daemons_stop (pg, TIMEOUT, &shutdown_callback, NULL); - ok = 0; -} - -/** - * Continuation for the GNUNET_DHT_get_stop call, so that we don't shut - * down the peers without freeing memory associated with GET request. - */ -static void -end_badly_cont (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - if (peer1dht != NULL) - GNUNET_DHT_disconnect (peer1dht); - - if (peer2dht != NULL) - GNUNET_DHT_disconnect (peer2dht); - - if (pg != NULL) - GNUNET_TESTING_daemons_stop (pg, TIMEOUT, &shutdown_callback, NULL); -} - -/** - * Check if the get_handle is being used, if so stop the request. Either - * way, schedule the end_badly_cont function which actually shuts down the - * test. - */ -static void -end_badly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Failing test with error: `%s'!\n", - (char *) cls); - if (global_get_handle != NULL) - { - GNUNET_DHT_get_stop (global_get_handle); - global_get_handle = NULL; - } - GNUNET_SCHEDULER_add_now (&end_badly_cont, NULL); - ok = 1; -} - -/** - * Iterator called if the GET request initiated returns a response. - * - * @param cls closure - * @param exp when will this value expire - * @param key key of the result - * @param type type of the result - * @param size number of bytes in data - * @param data pointer to the result data - */ -void -get_result_iterator (void *cls, struct GNUNET_TIME_Absolute exp, - const GNUNET_HashCode * key, - const struct GNUNET_PeerIdentity *get_path, - unsigned int get_path_size, - const struct GNUNET_PeerIdentity *put_path, - unsigned int put_path_size, enum GNUNET_BLOCK_Type type, - size_t size, const void *result_data) -{ - GNUNET_HashCode original_key; /* Key data was stored data under */ - char original_data[4]; /* Made up data that was stored */ - - memset (&original_key, 42, sizeof (GNUNET_HashCode)); /* Set the key to what it was set to previously */ - memset (original_data, 43, sizeof (original_data)); - -#if DNS - if ((sizeof (original_data) != size) || - (0 != memcmp (&data.service_descriptor, key, sizeof (GNUNET_HashCode))) || - (0 != memcmp ((char *) &data, result_data, sizeof (original_data)))) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Key or data is not the same as was inserted!\n"); - GNUNET_SCHEDULER_cancel (die_task); - GNUNET_SCHEDULER_add_now (&end_badly, - "key or data mismatch in get response!\n"); - return; - } -#else - if ((sizeof (original_data) != size) || - (0 != memcmp (&original_key, key, sizeof (GNUNET_HashCode))) || - (0 != memcmp (original_data, result_data, sizeof (original_data)))) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Key or data is not the same as was inserted!\n"); - GNUNET_SCHEDULER_cancel (die_task); - GNUNET_SCHEDULER_add_now (&end_badly, - "key or data mismatch in get response!\n"); - return; - } -#endif - - GNUNET_SCHEDULER_cancel (die_task); - GNUNET_DHT_get_stop (global_get_handle); - GNUNET_SCHEDULER_add_now (&finish_testing, NULL); -} - -/** - * Start the GET request for the same key/data that was inserted. - */ -static void -do_get (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - GNUNET_HashCode key; /* Key for data lookup */ - -#if DNS - memcpy (&key, &data.service_descriptor, sizeof (GNUNET_HashCode)); -#else - memset (&key, 42, sizeof (GNUNET_HashCode)); /* Set the key to the same thing as when data was inserted */ -#endif - global_get_handle = - GNUNET_DHT_get_start (peer2dht, -#if DNS - GNUNET_BLOCK_TYPE_DNS, -#else - GNUNET_BLOCK_TYPE_TEST, -#endif - &key, 1, GNUNET_DHT_RO_NONE, NULL, 0, - &get_result_iterator, NULL); - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply - (GNUNET_TIME_UNIT_SECONDS, 10), &do_put, NULL); -} - -/** - * Called when the PUT request has been transmitted to the DHT service. - * Schedule the GET request for some time in the future. - */ -static void -put_finished (void *cls, int success) -{ - GNUNET_SCHEDULER_cancel (die_task); - die_task = - GNUNET_SCHEDULER_add_delayed (GET_TIMEOUT, &end_badly, - "waiting for get response (data not found)"); -} - - -#if !DNS -/** - * Set up some data, and call API PUT function - */ -static void -do_put (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - GNUNET_HashCode key; /* Made up key to store data under */ - char data[4]; /* Made up data to store */ - - memset (&key, 42, sizeof (GNUNET_HashCode)); /* Set the key to something simple so we can issue GET request */ - memset (data, 43, sizeof (data)); - - /* Insert the data at the first peer */ - GNUNET_DHT_put (peer1dht, &key, 1, GNUNET_DHT_RO_NONE, GNUNET_BLOCK_TYPE_TEST, - sizeof (data), data, GNUNET_TIME_UNIT_FOREVER_ABS, - GNUNET_TIME_UNIT_FOREVER_REL, &put_finished, NULL); -} -#else - -/** - * Set up some data, and call API PUT function - */ -static void -do_put (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - char *name = "philipptoelke.gnunet."; - size_t size = sizeof (struct GNUNET_DNS_Record); - - memset (&data, 0, size); - - data.purpose.size = htonl (size - sizeof (struct GNUNET_CRYPTO_RsaSignature)); - data.purpose.purpose = GNUNET_SIGNATURE_PURPOSE_DNS_RECORD; - - GNUNET_CRYPTO_hash (name, strlen (name) + 1, &data.service_descriptor); - - data.service_type = htonl (GNUNET_DNS_SERVICE_TYPE_UDP); - data.ports = htons (69); - - char *keyfile; - - GNUNET_asprintf (&keyfile, "/tmp/test_dns_data_key"); - struct GNUNET_CRYPTO_RsaPrivateKey *my_private_key = - GNUNET_CRYPTO_rsa_key_create_from_file (keyfile); - GNUNET_free (keyfile); - GNUNET_assert (my_private_key != NULL); - - GNUNET_CRYPTO_rsa_key_get_public (my_private_key, &data.peer); - - data.expiration_time = - GNUNET_TIME_relative_to_absolute (GNUNET_TIME_UNIT_HOURS); - - /* Sign the block */ - if (GNUNET_OK != - GNUNET_CRYPTO_rsa_sign (my_private_key, &data.purpose, &data.signature)) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "could not sign DNS_Record\n"); - return; - } - GNUNET_CRYPTO_rsa_key_free (my_private_key); - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Putting with key %08x\n", - *((unsigned int *) &data.service_descriptor)); - - GNUNET_DHT_put (peer1dht, &data.service_descriptor, DEFAULT_PUT_REPLICATION, - GNUNET_DHT_RO_NONE, GNUNET_BLOCK_TYPE_DNS, size, - (char *) &data, - GNUNET_TIME_relative_to_absolute (GNUNET_TIME_UNIT_HOURS), - GNUNET_TIME_UNIT_MINUTES, &put_finished, NULL); -} -#endif - -/** - * This function is called whenever a connection attempt is finished between two of - * the started peers (started with GNUNET_TESTING_daemons_start). The total - * number of times this function is called should equal the number returned - * from the GNUNET_TESTING_connect_topology call. - * - * The emsg variable is NULL on success (peers connected), and non-NULL on - * failure (peers failed to connect). - */ -void -topology_callback (void *cls, const struct GNUNET_PeerIdentity *first, - const struct GNUNET_PeerIdentity *second, uint32_t distance, - const struct GNUNET_CONFIGURATION_Handle *first_cfg, - const struct GNUNET_CONFIGURATION_Handle *second_cfg, - struct GNUNET_TESTING_Daemon *first_daemon, - struct GNUNET_TESTING_Daemon *second_daemon, - const char *emsg) -{ - if (emsg == NULL) - { - total_connections++; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "connected peer %s to peer %s, distance %u\n", - first_daemon->shortname, second_daemon->shortname, distance); - } - else - { - failed_connections++; - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Failed to connect peer %s to peer %s with error :\n%s\n", - first_daemon->shortname, second_daemon->shortname, emsg); - } - - if (total_connections == expected_connections) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Created %d total connections, which is our target number! Starting next phase of testing.\n", - total_connections); - GNUNET_SCHEDULER_cancel (die_task); - die_task = - GNUNET_SCHEDULER_add_delayed (TIMEOUT, &end_badly, "from test gets"); - - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply - (GNUNET_TIME_UNIT_SECONDS, 2), &do_get, NULL); - } - else if (total_connections + failed_connections == expected_connections) - { - GNUNET_SCHEDULER_cancel (die_task); - die_task = - GNUNET_SCHEDULER_add_now (&end_badly, - "from topology_callback (too many failed connections)"); - } -} - - -/** - * Callback which is called whenever a peer is started (as a result of the - * GNUNET_TESTING_daemons_start call. - * - * @param cls closure argument given to GNUNET_TESTING_daemons_start - * @param id the GNUNET_PeerIdentity of the started peer - * @param cfg the configuration for this specific peer (needed to connect - * to the DHT) - * @param d the handle to the daemon started - * @param emsg NULL if peer started, non-NULL on error - */ -static void -peers_started_callback (void *cls, const struct GNUNET_PeerIdentity *id, - const struct GNUNET_CONFIGURATION_Handle *cfg, - struct GNUNET_TESTING_Daemon *d, const char *emsg) -{ - if (emsg != NULL) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Failed to start daemon with error: `%s'\n", emsg); - return; - } - GNUNET_assert (id != NULL); - - /* This is the first peer started */ - if (peers_left == num_peers) - { - memcpy (&peer1id, id, sizeof (struct GNUNET_PeerIdentity)); /* Save the peer id */ - peer1dht = GNUNET_DHT_connect (cfg, 100); /* Connect to the first peers DHT service */ - if (peer1dht == NULL) /* If DHT connect failed */ - { - GNUNET_SCHEDULER_cancel (die_task); - GNUNET_SCHEDULER_add_now (&end_badly, "Failed to get dht handle!\n"); - } - } - else /* This is the second peer started */ - { - memcpy (&peer2id, id, sizeof (struct GNUNET_PeerIdentity)); /* Same as for first peer... */ - peer2dht = GNUNET_DHT_connect (cfg, 100); - if (peer2dht == NULL) - { - GNUNET_SCHEDULER_cancel (die_task); - GNUNET_SCHEDULER_add_now (&end_badly, "Failed to get dht handle!\n"); - } - } - - /* Decrement number of peers left to start */ - peers_left--; - - if (peers_left == 0) /* Indicates all peers started */ - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "All %d daemons started, now connecting peers!\n", num_peers); - expected_connections = -1; - if ((pg != NULL)) /* Sanity check */ - { - /* Connect peers in a "straight line" topology, return the number of expected connections */ - expected_connections = - GNUNET_TESTING_connect_topology (pg, GNUNET_TESTING_TOPOLOGY_LINE, - GNUNET_TESTING_TOPOLOGY_OPTION_ALL, - 0.0, TIMEOUT, 12, NULL, NULL); - } - - /* Cancel current timeout fail task */ - GNUNET_SCHEDULER_cancel (die_task); - if (expected_connections == GNUNET_SYSERR) /* Some error happened */ - die_task = - GNUNET_SCHEDULER_add_now (&end_badly, - "from connect topology (bad return)"); - - /* Schedule timeout on failure task */ - die_task = - GNUNET_SCHEDULER_add_delayed (TIMEOUT, &end_badly, - "from connect topology (timeout)"); - ok = 0; - } -} - -static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) -{ - - /* Get path from configuration file */ - if (GNUNET_YES != - GNUNET_CONFIGURATION_get_value_string (cfg, "paths", "servicehome", - &test_directory)) - { - ok = 404; - return; - } - - /* Get number of peers to start from configuration (should be two) */ - if (GNUNET_SYSERR == - GNUNET_CONFIGURATION_get_value_number (cfg, "testing", "num_peers", - &num_peers)) - num_peers = DEFAULT_NUM_PEERS; - - /* Set peers_left so we know when all peers started */ - peers_left = num_peers; - - /* Set up a task to end testing if peer start fails */ - die_task = - GNUNET_SCHEDULER_add_delayed (TIMEOUT, &end_badly, - "didn't start all daemons in reasonable amount of time!!!"); - - /* Start num_peers peers, call peers_started_callback on peer start, topology_callback on peer connect */ - /* Read the API documentation for other parameters! */ - pg = GNUNET_TESTING_daemons_start (cfg, num_peers, 2, 2, TIMEOUT, NULL, NULL, - &peers_started_callback, NULL, - &topology_callback, NULL, NULL); - -} - -static int -check () -{ - int ret; - - /* Arguments for GNUNET_PROGRAM_run */ - char *const argv[] = { "test-dht-twopeer-get-put", /* Name to give running binary */ - "-c", - "test_dht_twopeer_data.conf", /* Config file to use */ - NULL - }; - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - /* Run the run function as a new program */ - ret = - GNUNET_PROGRAM_run ((sizeof (argv) / sizeof (char *)) - 1, argv, - "test-dht-twopeer-get-put", "nohelp", options, &run, - &ok); - if (ret != GNUNET_OK) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "`test-dht-twopeer': Failed with error code %d\n", ret); - } - return ok; -} - -int -main (int argc, char *argv[]) -{ - int ret; - - GNUNET_log_setup ("test-dht-twopeer", - "WARNING", - NULL); - ret = check (); - /** - * Need to remove base directory, subdirectories taken care - * of by the testing framework. - */ - if (GNUNET_DISK_directory_remove (test_directory) != GNUNET_OK) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Failed to remove testing directory %s\n", test_directory); - } - return ret; -} - -/* end of test_dht_twopeer_get_put.c */ diff --git a/src/dht/test_dht_twopeer_path_tracking.c b/src/dht/test_dht_twopeer_path_tracking.c deleted file mode 100644 index 6ecf6a3..0000000 --- a/src/dht/test_dht_twopeer_path_tracking.c +++ /dev/null @@ -1,522 +0,0 @@ -/* - This file is part of GNUnet. - (C) 2009 Christian Grothoff (and other contributing authors) - - GNUnet is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published - by the Free Software Foundation; either version 3, or (at your - option) any later version. - - GNUnet is distributed in the hope that it will be useful, but - WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - General Public License for more details. - - You should have received a copy of the GNU General Public License - along with GNUnet; see the file COPYING. If not, write to the - Free Software Foundation, Inc., 59 Temple Place - Suite 330, - Boston, MA 02111-1307, USA. -*/ -/** - * @file dht/test_dht_twopeer_path_tracking.c - * @brief testcase for testing DHT service with - * two running peers, logging the path of the dht requests. - */ -#include "platform.h" -#include "gnunet_testing_lib.h" -#include "gnunet_core_service.h" -#include "gnunet_dht_service.h" - -/* DEFINES */ -#define VERBOSE GNUNET_NO - -/* Timeout for entire testcase */ -#define TIMEOUT GNUNET_TIME_relative_multiply(GNUNET_TIME_UNIT_MINUTES, 5) - -/* Timeout for waiting for replies to get requests */ -#define GET_TIMEOUT GNUNET_TIME_relative_multiply(GNUNET_TIME_UNIT_SECONDS, 30) - -/* If number of peers not in config file, use this number */ -#define DEFAULT_NUM_PEERS 2 - -/* Globals */ - -/** - * Directory to store temp data in, defined in config file - */ -static char *test_directory; - -/** - * Variable used to store the number of connections we should wait for. - */ -static unsigned int expected_connections; - -/** - * Variable used to keep track of how many peers aren't yet started. - */ -static unsigned long long peers_left; - -/** - * Handle to the set of all peers run for this test. - */ -static struct GNUNET_TESTING_PeerGroup *pg; - -/** - * Global handle we will use for GET requests. - */ -struct GNUNET_DHT_GetHandle *global_get_handle; - - -/** - * Total number of peers to run, set based on config file. - */ -static unsigned long long num_peers; - -/** - * Global used to count how many connections we have currently - * been notified about (how many times has topology_callback been called - * with success?) - */ -static unsigned int total_connections; - -/** - * Global used to count how many failed connections we have - * been notified about (how many times has topology_callback - * been called with failure?) - */ -static unsigned int failed_connections; - -/** - * Task handle to use to schedule test failure - */ -GNUNET_SCHEDULER_TaskIdentifier die_task; - -/** - * Global return value (0 for success, anything else for failure) - */ -static int ok; - -/** - * Peer identity of the first peer started. - */ -static struct GNUNET_PeerIdentity peer1id; - -/** - * Peer identity of the second peer started. - */ -static struct GNUNET_PeerIdentity peer2id; - -/** - * Handle to the first peers DHT service (via the API) - */ -static struct GNUNET_DHT_Handle *peer1dht; - -/** - * Handle to the second peers DHT service (via the API) - */ -static struct GNUNET_DHT_Handle *peer2dht; - -/** - * Check whether peers successfully shut down. - */ -void -shutdown_callback (void *cls, const char *emsg) -{ - if (emsg != NULL) - { - if (ok == 0) - ok = 2; - } -} - -/** - * Function scheduled to be run on the successful completion of this - * testcase. Specifically, called when our get request completes. - */ -static void -finish_testing (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - GNUNET_assert (pg != NULL); - GNUNET_assert (peer1dht != NULL); - GNUNET_assert (peer2dht != NULL); - GNUNET_DHT_disconnect (peer1dht); - GNUNET_DHT_disconnect (peer2dht); - GNUNET_TESTING_daemons_stop (pg, TIMEOUT, &shutdown_callback, NULL); - ok = 0; -} - -/** - * Continuation for the GNUNET_DHT_get_stop call, so that we don't shut - * down the peers without freeing memory associated with GET request. - */ -static void -end_badly_cont (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - if (peer1dht != NULL) - GNUNET_DHT_disconnect (peer1dht); - - if (peer2dht != NULL) - GNUNET_DHT_disconnect (peer2dht); - - if (pg != NULL) - GNUNET_TESTING_daemons_stop (pg, TIMEOUT, &shutdown_callback, NULL); -} - -/** - * Check if the get_handle is being used, if so stop the request. Either - * way, schedule the end_badly_cont function which actually shuts down the - * test. - */ -static void -end_badly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Failing test with error: `%s'!\n", - (char *) cls); - if (global_get_handle != NULL) - { - GNUNET_DHT_get_stop (global_get_handle); - global_get_handle = NULL; - } - GNUNET_SCHEDULER_add_now (&end_badly_cont, NULL); - ok = 1; -} - -/** - * Iterator called if the GET request initiated returns a response. - * - * @param cls closure - * @param exp when will this value expire - * @param key key of the result - * @param type type of the result - * @param size number of bytes in data - * @param data pointer to the result data - */ -static void -get_result_iterator (void *cls, struct GNUNET_TIME_Absolute exp, - const GNUNET_HashCode * key, - const struct GNUNET_PeerIdentity *get_path, - unsigned int get_path_length, - const struct GNUNET_PeerIdentity *put_path, - unsigned int put_path_length, enum GNUNET_BLOCK_Type type, - size_t size, const void *data) -{ - GNUNET_HashCode original_key; /* Key data was stored data under */ - char original_data[4]; /* Made up data that was stored */ - - memset (&original_key, 42, sizeof (GNUNET_HashCode)); /* Set the key to what it was set to previously */ - memset (original_data, 43, sizeof (original_data)); -#if VERBOSE - unsigned int i; -#endif - - if ((0 != memcmp (&original_key, key, sizeof (GNUNET_HashCode))) || - (0 != memcmp (original_data, data, sizeof (original_data)))) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Key or data is not the same as was inserted!\n"); - GNUNET_SCHEDULER_cancel (die_task); - GNUNET_SCHEDULER_add_now (&end_badly, - "key or data mismatch in get response!\n"); - return; - } - -#if VERBOSE - if (put_path != NULL) - { - FPRINTF (stderr, "%s", "PUT Path: "); - for (i = 0; i < put_path_length; i++) - FPRINTF (stderr, "%s%s", i == 0 ? "" : "->", GNUNET_i2s (&put_path[i])); - FPRINTF (stderr, "%s", "\n"); - } - if (get_path != NULL) - { - FPRINTF (stderr, "%s", "GET Path: "); - for (i = 0; i < get_path_length; i++) - FPRINTF (stderr, "%s%s", i == 0 ? "" : "->", GNUNET_i2s (&get_path[i])); - FPRINTF (stderr, "%s", "\n"); - } -#endif - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received correct GET response!\n"); - GNUNET_SCHEDULER_cancel (die_task); - GNUNET_DHT_get_stop (global_get_handle); - GNUNET_SCHEDULER_add_now (&finish_testing, NULL); -} - - -/** - * Called when the PUT request has been transmitted to the DHT service. - * Schedule the GET request for some time in the future. - */ -static void -put_finished (void *cls, int success) -{ - GNUNET_HashCode key; /* Key for data lookup */ - - GNUNET_SCHEDULER_cancel (die_task); - die_task = - GNUNET_SCHEDULER_add_delayed (GET_TIMEOUT, &end_badly, - "waiting for get response (data not found)"); - memset (&key, 42, sizeof (GNUNET_HashCode)); /* Set the key to the same thing as when data was inserted */ - global_get_handle = - GNUNET_DHT_get_start (peer2dht, - GNUNET_BLOCK_TYPE_TEST, &key, 1, - GNUNET_DHT_RO_RECORD_ROUTE, NULL, 0, - &get_result_iterator, NULL); -} - -/** - * Set up some data, and call API PUT function - */ -static void -do_put (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - GNUNET_HashCode key; /* Made up key to store data under */ - char data[4]; /* Made up data to store */ - - memset (&key, 42, sizeof (GNUNET_HashCode)); /* Set the key to something simple so we can issue GET request */ - memset (data, 43, sizeof (data)); - - /* Insert the data at the first peer */ - GNUNET_DHT_put (peer1dht, &key, 1, GNUNET_DHT_RO_RECORD_ROUTE, - GNUNET_BLOCK_TYPE_TEST, sizeof (data), data, - GNUNET_TIME_UNIT_FOREVER_ABS, GNUNET_TIME_UNIT_FOREVER_REL, - &put_finished, NULL); -} - -/** - * This function is called whenever a connection attempt is finished between two of - * the started peers (started with GNUNET_TESTING_daemons_start). The total - * number of times this function is called should equal the number returned - * from the GNUNET_TESTING_connect_topology call. - * - * The emsg variable is NULL on success (peers connected), and non-NULL on - * failure (peers failed to connect). - */ -static void -topology_callback (void *cls, const struct GNUNET_PeerIdentity *first, - const struct GNUNET_PeerIdentity *second, uint32_t distance, - const struct GNUNET_CONFIGURATION_Handle *first_cfg, - const struct GNUNET_CONFIGURATION_Handle *second_cfg, - struct GNUNET_TESTING_Daemon *first_daemon, - struct GNUNET_TESTING_Daemon *second_daemon, - const char *emsg) -{ - if (emsg == NULL) - { - total_connections++; -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "connected peer %s to peer %s, distance %u\n", - first_daemon->shortname, second_daemon->shortname, distance); -#endif - } -#if VERBOSE - else - { - failed_connections++; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Failed to connect peer %s to peer %s with error :\n%s\n", - first_daemon->shortname, second_daemon->shortname, emsg); - } -#endif - - if (total_connections == expected_connections) - { -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Created %d total connections, which is our target number! Starting next phase of testing.\n", - total_connections); -#endif - GNUNET_SCHEDULER_cancel (die_task); - die_task = - GNUNET_SCHEDULER_add_delayed (TIMEOUT, &end_badly, "from test gets"); - - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply - (GNUNET_TIME_UNIT_SECONDS, 2), &do_put, NULL); - } - else if (total_connections + failed_connections == expected_connections) - { - GNUNET_SCHEDULER_cancel (die_task); - die_task = - GNUNET_SCHEDULER_add_now (&end_badly, - "from topology_callback (too many failed connections)"); - } -} - - -/** - * Callback which is called whenever a peer is started (as a result of the - * GNUNET_TESTING_daemons_start call. - * - * @param cls closure argument given to GNUNET_TESTING_daemons_start - * @param id the GNUNET_PeerIdentity of the started peer - * @param cfg the configuration for this specific peer (needed to connect - * to the DHT) - * @param d the handle to the daemon started - * @param emsg NULL if peer started, non-NULL on error - */ -static void -peers_started_callback (void *cls, const struct GNUNET_PeerIdentity *id, - const struct GNUNET_CONFIGURATION_Handle *cfg, - struct GNUNET_TESTING_Daemon *d, const char *emsg) -{ - if (emsg != NULL) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Failed to start daemon with error: `%s'\n", emsg); - return; - } - GNUNET_assert (id != NULL); - - /* This is the first peer started */ - if (peers_left == num_peers) - { - memcpy (&peer1id, id, sizeof (struct GNUNET_PeerIdentity)); /* Save the peer id */ - peer1dht = GNUNET_DHT_connect (cfg, 100); /* Connect to the first peers DHT service */ - if (peer1dht == NULL) /* If DHT connect failed */ - { - GNUNET_SCHEDULER_cancel (die_task); - GNUNET_SCHEDULER_add_now (&end_badly, "Failed to get dht handle!\n"); - } - } - else /* This is the second peer started */ - { - memcpy (&peer2id, id, sizeof (struct GNUNET_PeerIdentity)); /* Same as for first peer... */ - peer2dht = GNUNET_DHT_connect (cfg, 100); - if (peer2dht == NULL) - { - GNUNET_SCHEDULER_cancel (die_task); - GNUNET_SCHEDULER_add_now (&end_badly, "Failed to get dht handle!\n"); - } - } - - /* Decrement number of peers left to start */ - peers_left--; - - if (peers_left == 0) /* Indicates all peers started */ - { -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "All %d daemons started, now connecting peers!\n", num_peers); -#endif - expected_connections = -1; - if ((pg != NULL)) /* Sanity check */ - { - /* Connect peers in a "straight line" topology, return the number of expected connections */ - expected_connections = - GNUNET_TESTING_connect_topology (pg, GNUNET_TESTING_TOPOLOGY_LINE, - GNUNET_TESTING_TOPOLOGY_OPTION_ALL, - 0.0, TIMEOUT, 2, NULL, NULL); - } - - /* Cancel current timeout fail task */ - GNUNET_SCHEDULER_cancel (die_task); - if (expected_connections == GNUNET_SYSERR) /* Some error happened */ - die_task = - GNUNET_SCHEDULER_add_now (&end_badly, - "from connect topology (bad return)"); - - /* Schedule timeout on failure task */ - die_task = - GNUNET_SCHEDULER_add_delayed (TIMEOUT, &end_badly, - "from connect topology (timeout)"); - ok = 0; - } -} - -static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) -{ - - /* Get path from configuration file */ - if (GNUNET_YES != - GNUNET_CONFIGURATION_get_value_string (cfg, "paths", "servicehome", - &test_directory)) - { - ok = 404; - return; - } - - /* Get number of peers to start from configuration (should be two) */ - if (GNUNET_SYSERR == - GNUNET_CONFIGURATION_get_value_number (cfg, "testing", "num_peers", - &num_peers)) - num_peers = DEFAULT_NUM_PEERS; - - /* Set peers_left so we know when all peers started */ - peers_left = num_peers; - - /* Set up a task to end testing if peer start fails */ - die_task = - GNUNET_SCHEDULER_add_delayed (TIMEOUT, &end_badly, - "didn't start all daemons in reasonable amount of time!!!"); - - /* Start num_peers peers, call peers_started_callback on peer start, topology_callback on peer connect */ - /* Read the API documentation for other parameters! */ - pg = GNUNET_TESTING_daemons_start (cfg, peers_left, /* Total number of peers */ - peers_left, /* Number of outstanding connections */ - peers_left, /* Number of parallel ssh connections, or peers being started at once */ - TIMEOUT, NULL, NULL, - &peers_started_callback, NULL, - &topology_callback, NULL, NULL); - -} - -static int -check () -{ - int ret; - - /* Arguments for GNUNET_PROGRAM_run */ - char *const argv[] = { "test-dht-twopeer-put-get", /* Name to give running binary */ - "-c", - "test_dht_twopeer_data.conf", /* Config file to use */ -#if VERBOSE - "-L", "DEBUG", -#endif - NULL - }; - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - /* Run the run function as a new program */ - ret = - GNUNET_PROGRAM_run ((sizeof (argv) / sizeof (char *)) - 1, argv, - "test-dht-twopeer-put-get", "nohelp", options, &run, - &ok); - if (ret != GNUNET_OK) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "`test-dht-twopeer': Failed with error code %d\n", ret); - } - return ok; -} - -int -main (int argc, char *argv[]) -{ - int ret; - - GNUNET_log_setup ("test-dht-twopeer", -#if VERBOSE - "DEBUG", -#else - "WARNING", -#endif - NULL); - ret = check (); - /** - * Need to remove base directory, subdirectories taken care - * of by the testing framework. - */ - if (GNUNET_DISK_directory_remove (test_directory) != GNUNET_OK) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Failed to remove testing directory %s\n", test_directory); - } - return ret; -} - -/* end of test_dht_twopeer_put_get.c */ diff --git a/src/dht/test_dht_twopeer_put_get.c b/src/dht/test_dht_twopeer_put_get.c deleted file mode 100644 index 44150e3..0000000 --- a/src/dht/test_dht_twopeer_put_get.c +++ /dev/null @@ -1,510 +0,0 @@ -/* - This file is part of GNUnet. - (C) 2009 Christian Grothoff (and other contributing authors) - - GNUnet is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published - by the Free Software Foundation; either version 3, or (at your - option) any later version. - - GNUnet is distributed in the hope that it will be useful, but - WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - General Public License for more details. - - You should have received a copy of the GNU General Public License - along with GNUnet; see the file COPYING. If not, write to the - Free Software Foundation, Inc., 59 Temple Place - Suite 330, - Boston, MA 02111-1307, USA. -*/ -/** - * @file dht/test_dht_twopeer_put_get.c - * @brief base testcase for testing DHT service with - * two running peers. - * - * This testcase starts peers using the GNUNET_TESTING_daemons_start - * function call. On peer start, connects to the peers DHT service - * by calling GNUNET_DHT_connected. Once notified about all peers - * being started (by the peers_started_callback function), calls - * GNUNET_TESTING_connect_topology, which connects the peers in a - * "straight line" topology. On notification that all peers have - * been properly connected, runs the do_put function to insert data - * at the first peer. Once the GNUNET_DHT_put function completes, - * calls the do_get function which initiates a GNUNET_DHT_get from - * the *second* peer. If the GET is successful, schedules finish_testing - * to stop the test and shut down peers. If GET is unsuccessful - * after GET_TIMEOUT seconds, prints an error message and shuts down - * the peers. - */ -#include "platform.h" -#include "gnunet_testing_lib.h" -#include "gnunet_core_service.h" -#include "gnunet_dht_service.h" -#include "block_dns.h" -#include "gnunet_signatures.h" - -/* DEFINES */ -#define VERBOSE GNUNET_NO - -/* Timeout for entire testcase */ -#define TIMEOUT GNUNET_TIME_relative_multiply(GNUNET_TIME_UNIT_MINUTES, 5) - -/* Timeout for waiting for replies to get requests */ -#define GET_TIMEOUT GNUNET_TIME_relative_multiply(GNUNET_TIME_UNIT_SECONDS, 30) - -/* If number of peers not in config file, use this number */ -#define DEFAULT_NUM_PEERS 2 - -/* Globals */ - -/** - * Directory to store temp data in, defined in config file - */ -static char *test_directory; - -/** - * Variable used to store the number of connections we should wait for. - */ -static unsigned int expected_connections; - -/** - * Variable used to keep track of how many peers aren't yet started. - */ -static unsigned long long peers_left; - -/** - * Handle to the set of all peers run for this test. - */ -static struct GNUNET_TESTING_PeerGroup *pg; - -/** - * Global handle we will use for GET requests. - */ -struct GNUNET_DHT_GetHandle *global_get_handle; - - -/** - * Total number of peers to run, set based on config file. - */ -static unsigned long long num_peers; - -/** - * Global used to count how many connections we have currently - * been notified about (how many times has topology_callback been called - * with success?) - */ -static unsigned int total_connections; - -/** - * Global used to count how many failed connections we have - * been notified about (how many times has topology_callback - * been called with failure?) - */ -static unsigned int failed_connections; - -/* Task handle to use to schedule test failure */ -static GNUNET_SCHEDULER_TaskIdentifier die_task; - -/* Global return value (0 for success, anything else for failure) */ -static int ok; - -/** - * Peer identity of the first peer started. - */ -static struct GNUNET_PeerIdentity peer1id; - -/** - * Peer identity of the second peer started. - */ -static struct GNUNET_PeerIdentity peer2id; - -/** - * Handle to the first peers DHT service (via the API) - */ -static struct GNUNET_DHT_Handle *peer1dht; - -/** - * Handle to the second peers DHT service (via the API) - */ -static struct GNUNET_DHT_Handle *peer2dht; - -/** - * Handle for our PUT operation. - */ -static struct GNUNET_DHT_PutHandle *put_op; - - -/** - * Check whether peers successfully shut down. - */ -static void -shutdown_callback (void *cls, const char *emsg) -{ - if (emsg != NULL) - { - if (ok == 0) - ok = 2; - } -} - -/** - * Function scheduled to be run on the successful completion of this - * testcase. Specifically, called when our get request completes. - */ -static void -finish_testing (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - GNUNET_assert (pg != NULL); - GNUNET_assert (peer1dht != NULL); - GNUNET_assert (peer2dht != NULL); - GNUNET_DHT_disconnect (peer1dht); - GNUNET_DHT_disconnect (peer2dht); - GNUNET_TESTING_daemons_stop (pg, TIMEOUT, &shutdown_callback, NULL); - ok = 0; -} - -/** - * Continuation for the GNUNET_DHT_get_stop call, so that we don't shut - * down the peers without freeing memory associated with GET request. - */ -static void -end_badly_cont (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - if (NULL != put_op) - { - GNUNET_DHT_put_cancel (put_op); - put_op = NULL; - } - if (peer1dht != NULL) - GNUNET_DHT_disconnect (peer1dht); - - if (peer2dht != NULL) - GNUNET_DHT_disconnect (peer2dht); - - if (pg != NULL) - GNUNET_TESTING_daemons_stop (pg, TIMEOUT, &shutdown_callback, NULL); -} - - -/** - * Check if the get_handle is being used, if so stop the request. Either - * way, schedule the end_badly_cont function which actually shuts down the - * test. - */ -static void -end_badly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Failing test with error: `%s'!\n", - (char *) cls); - if (global_get_handle != NULL) - { - GNUNET_DHT_get_stop (global_get_handle); - global_get_handle = NULL; - } - GNUNET_SCHEDULER_add_now (&end_badly_cont, NULL); - ok = 1; -} - -/** - * Iterator called if the GET request initiated returns a response. - * - * @param cls closure - * @param exp when will this value expire - * @param key key of the result - * @param type type of the result - * @param size number of bytes in data - * @param data pointer to the result data - */ -static void -get_result_iterator (void *cls, struct GNUNET_TIME_Absolute exp, - const GNUNET_HashCode * key, - const struct GNUNET_PeerIdentity *get_path, - unsigned int get_path_size, - const struct GNUNET_PeerIdentity *put_path, - unsigned int put_path_size, enum GNUNET_BLOCK_Type type, - size_t size, const void *result_data) -{ - GNUNET_HashCode original_key; /* Key data was stored data under */ - char original_data[4]; /* Made up data that was stored */ - - memset (&original_key, 42, sizeof (GNUNET_HashCode)); /* Set the key to what it was set to previously */ - memset (original_data, 43, sizeof (original_data)); - - if ((sizeof (original_data) != size) || - (0 != memcmp (&original_key, key, sizeof (GNUNET_HashCode))) || - (0 != memcmp (original_data, result_data, sizeof (original_data)))) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Key or data is not the same as was inserted!\n"); - GNUNET_SCHEDULER_cancel (die_task); - GNUNET_SCHEDULER_add_now (&end_badly, - "key or data mismatch in get response!\n"); - return; - } - - GNUNET_SCHEDULER_cancel (die_task); - GNUNET_DHT_get_stop (global_get_handle); - global_get_handle = NULL; - GNUNET_SCHEDULER_add_now (&finish_testing, NULL); -} - - -/** - * Called when the PUT request has been transmitted to the DHT service. - * Schedule the GET request for some time in the future. - */ -static void -put_finished (void *cls, int success) -{ - GNUNET_HashCode key; /* Key for data lookup */ - - put_op = NULL; - GNUNET_SCHEDULER_cancel (die_task); - die_task = - GNUNET_SCHEDULER_add_delayed (GET_TIMEOUT, &end_badly, - "waiting for get response (data not found)"); - - memset (&key, 42, sizeof (GNUNET_HashCode)); /* Set the key to the same thing as when data was inserted */ - global_get_handle = - GNUNET_DHT_get_start (peer2dht, - GNUNET_BLOCK_TYPE_TEST, &key, 1, GNUNET_DHT_RO_NONE, - NULL, 0, &get_result_iterator, NULL); -} - - -/** - * Set up some data, and call API PUT function - */ -static void -do_put (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - GNUNET_HashCode key; /* Made up key to store data under */ - char data[4]; /* Made up data to store */ - - memset (&key, 42, sizeof (GNUNET_HashCode)); /* Set the key to something simple so we can issue GET request */ - memset (data, 43, sizeof (data)); - - /* Insert the data at the first peer */ - put_op = GNUNET_DHT_put (peer1dht, &key, 1, GNUNET_DHT_RO_NONE, GNUNET_BLOCK_TYPE_TEST, - sizeof (data), data, GNUNET_TIME_UNIT_FOREVER_ABS, - GNUNET_TIME_UNIT_FOREVER_REL, &put_finished, NULL); -} - - -/** - * This function is called whenever a connection attempt is finished between two of - * the started peers (started with GNUNET_TESTING_daemons_start). The total - * number of times this function is called should equal the number returned - * from the GNUNET_TESTING_connect_topology call. - * - * The emsg variable is NULL on success (peers connected), and non-NULL on - * failure (peers failed to connect). - */ -static void -topology_callback (void *cls, const struct GNUNET_PeerIdentity *first, - const struct GNUNET_PeerIdentity *second, uint32_t distance, - const struct GNUNET_CONFIGURATION_Handle *first_cfg, - const struct GNUNET_CONFIGURATION_Handle *second_cfg, - struct GNUNET_TESTING_Daemon *first_daemon, - struct GNUNET_TESTING_Daemon *second_daemon, - const char *emsg) -{ - if (emsg == NULL) - { - total_connections++; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "connected peer %s to peer %s, distance %u\n", - first_daemon->shortname, second_daemon->shortname, distance); - } - else - { - failed_connections++; - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Failed to connect peer %s to peer %s with error :\n%s\n", - first_daemon->shortname, second_daemon->shortname, emsg); - } - - if (total_connections == expected_connections) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Created %d total connections, which is our target number! Starting next phase of testing.\n", - total_connections); - GNUNET_SCHEDULER_cancel (die_task); - die_task = - GNUNET_SCHEDULER_add_delayed (TIMEOUT, &end_badly, "from test gets"); - - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_SECONDS, &do_put, NULL); - } - else if (total_connections + failed_connections == expected_connections) - { - GNUNET_SCHEDULER_cancel (die_task); - die_task = - GNUNET_SCHEDULER_add_now (&end_badly, - "from topology_callback (too many failed connections)"); - } -} - - -/** - * Callback which is called whenever a peer is started (as a result of the - * GNUNET_TESTING_daemons_start call. - * - * @param cls closure argument given to GNUNET_TESTING_daemons_start - * @param id the GNUNET_PeerIdentity of the started peer - * @param cfg the configuration for this specific peer (needed to connect - * to the DHT) - * @param d the handle to the daemon started - * @param emsg NULL if peer started, non-NULL on error - */ -static void -peers_started_callback (void *cls, const struct GNUNET_PeerIdentity *id, - const struct GNUNET_CONFIGURATION_Handle *cfg, - struct GNUNET_TESTING_Daemon *d, const char *emsg) -{ - if (emsg != NULL) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Failed to start daemon with error: `%s'\n", emsg); - return; - } - GNUNET_assert (id != NULL); - - /* This is the first peer started */ - if (peers_left == num_peers) - { - memcpy (&peer1id, id, sizeof (struct GNUNET_PeerIdentity)); /* Save the peer id */ - peer1dht = GNUNET_DHT_connect (cfg, 100); /* Connect to the first peers DHT service */ - if (peer1dht == NULL) /* If DHT connect failed */ - { - GNUNET_SCHEDULER_cancel (die_task); - GNUNET_SCHEDULER_add_now (&end_badly, "Failed to get dht handle!\n"); - } - } - else /* This is the second peer started */ - { - memcpy (&peer2id, id, sizeof (struct GNUNET_PeerIdentity)); /* Same as for first peer... */ - peer2dht = GNUNET_DHT_connect (cfg, 100); - if (peer2dht == NULL) - { - GNUNET_SCHEDULER_cancel (die_task); - GNUNET_SCHEDULER_add_now (&end_badly, "Failed to get dht handle!\n"); - } - } - - /* Decrement number of peers left to start */ - peers_left--; - - if (peers_left == 0) /* Indicates all peers started */ - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "All %d daemons started, now connecting peers!\n", num_peers); - expected_connections = -1; - if ((pg != NULL)) /* Sanity check */ - { - /* Connect peers in a "straight line" topology, return the number of expected connections */ - expected_connections = - GNUNET_TESTING_connect_topology (pg, GNUNET_TESTING_TOPOLOGY_LINE, - GNUNET_TESTING_TOPOLOGY_OPTION_ALL, - 0.0, TIMEOUT, 12, NULL, NULL); - } - - /* Cancel current timeout fail task */ - GNUNET_SCHEDULER_cancel (die_task); - if (expected_connections == GNUNET_SYSERR) /* Some error happened */ - die_task = - GNUNET_SCHEDULER_add_now (&end_badly, - "from connect topology (bad return)"); - - /* Schedule timeout on failure task */ - die_task = - GNUNET_SCHEDULER_add_delayed (TIMEOUT, &end_badly, - "from connect topology (timeout)"); - ok = 0; - } -} - -static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) -{ - - /* Get path from configuration file */ - if (GNUNET_YES != - GNUNET_CONFIGURATION_get_value_string (cfg, "paths", "servicehome", - &test_directory)) - { - ok = 404; - return; - } - - /* Get number of peers to start from configuration (should be two) */ - if (GNUNET_SYSERR == - GNUNET_CONFIGURATION_get_value_number (cfg, "testing", "num_peers", - &num_peers)) - num_peers = DEFAULT_NUM_PEERS; - - /* Set peers_left so we know when all peers started */ - peers_left = num_peers; - - /* Set up a task to end testing if peer start fails */ - die_task = - GNUNET_SCHEDULER_add_delayed (TIMEOUT, &end_badly, - "didn't start all daemons in reasonable amount of time!!!"); - - /* Start num_peers peers, call peers_started_callback on peer start, topology_callback on peer connect */ - /* Read the API documentation for other parameters! */ - pg = GNUNET_TESTING_daemons_start (cfg, num_peers, 2, 2, TIMEOUT, NULL, NULL, - &peers_started_callback, NULL, - &topology_callback, NULL, NULL); - -} - -static int -check () -{ - int ret; - - /* Arguments for GNUNET_PROGRAM_run */ - char *const argv[] = { "test-dht-twopeer-put-get", /* Name to give running binary */ - "-c", - "test_dht_twopeer_data.conf", /* Config file to use */ - NULL - }; - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - /* Run the run function as a new program */ - ret = - GNUNET_PROGRAM_run ((sizeof (argv) / sizeof (char *)) - 1, argv, - "test-dht-twopeer-put-get", "nohelp", options, &run, - &ok); - if (ret != GNUNET_OK) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "`test-dht-twopeer': Failed with error code %d\n", ret); - } - return ok; -} - -int -main (int argc, char *argv[]) -{ - int ret; - - GNUNET_log_setup ("test-dht-twopeer", - "WARNING", - NULL); - ret = check (); - /** - * Need to remove base directory, subdirectories taken care - * of by the testing framework. - */ - if (GNUNET_DISK_directory_remove (test_directory) != GNUNET_OK) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Failed to remove testing directory %s\n", test_directory); - } - return ret; -} - -/* end of test_dht_twopeer_put_get.c */ diff --git a/src/dns/Makefile.am b/src/dns/Makefile.am index ed000aa..345c131 100644 --- a/src/dns/Makefile.am +++ b/src/dns/Makefile.am @@ -10,6 +10,8 @@ endif pkgcfgdir= $(pkgdatadir)/config.d/ +libexecdir= $(pkglibdir)/libexec/ + plugindir = $(libdir)/gnunet pkgcfg_DATA = \ @@ -18,20 +20,17 @@ pkgcfg_DATA = \ if LINUX HIJACKBIN = gnunet-helper-dns install-exec-hook: - $(SUDO_BINARY) chown root $(bindir)/gnunet-helper-dns || true - $(SUDO_BINARY) chgrp $(GNUNETDNS_GROUP) $(bindir)/gnunet-helper-dns || true - $(SUDO_BINARY) chmod 4750 $(bindir)/gnunet-helper-dns || true - $(SUDO_BINARY) chown gnunet:$(GNUNETDNS_GROUP) $(bindir)/gnunet-service-dns || true - $(SUDO_BINARY) chmod 2750 $(bindir)/gnunet-service-dns || true + $(top_srcdir)/src/dns/install-dns-helper.sh $(libexecdir) $(GNUNETDNS_GROUP) $(SUDO_BINARY) || true else install-exec-hook: endif lib_LTLIBRARIES = \ libgnunetdnsparser.la \ + libgnunetdnsstub.la \ libgnunetdns.la -bin_PROGRAMS = \ +libexec_PROGRAMS = \ gnunet-service-dns $(HIJACKBIN) noinst_PROGRAMS = \ @@ -74,17 +73,28 @@ gnunet_dns_redirector_DEPENDENCIES = \ gnunet_service_dns_SOURCES = \ gnunet-service-dns.c gnunet_service_dns_LDADD = \ + $(top_builddir)/src/dns/libgnunetdnsstub.la \ $(top_builddir)/src/tun/libgnunettun.la \ - $(top_builddir)/src/mesh/libgnunetmesh.la \ $(top_builddir)/src/statistics/libgnunetstatistics.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(GN_LIBINTL) +gnunet_service_dns_DEPENDENCIES = \ + libgnunetdnsstub.la libgnunetdnsparser_la_SOURCES = \ - dnsparser.c + dnsparser.c dnsparser.h libgnunetdnsparser_la_LIBADD = \ - $(top_builddir)/src/util/libgnunetutil.la $(XLIB) + $(top_builddir)/src/util/libgnunetutil.la $(XLIB) \ + -lidn libgnunetdnsparser_la_LDFLAGS = \ + $(GN_LIB_LDFLAGS) \ + -version-info 1:0:1 + +libgnunetdnsstub_la_SOURCES = \ + dnsstub.c +libgnunetdnsstub_la_LIBADD = \ + $(top_builddir)/src/util/libgnunetutil.la $(XLIB) +libgnunetdnsstub_la_LDFLAGS = \ $(GN_LIB_LDFLAGS) \ -version-info 0:0:0 diff --git a/src/dns/Makefile.in b/src/dns/Makefile.in index 3a717ab..5047c5c 100644 --- a/src/dns/Makefile.in +++ b/src/dns/Makefile.in @@ -1,9 +1,9 @@ -# Makefile.in generated by automake 1.11.1 from Makefile.am. +# Makefile.in generated by automake 1.11.6 from Makefile.am. # @configure_input@ # Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, -# 2003, 2004, 2005, 2006, 2007, 2008, 2009 Free Software Foundation, -# Inc. +# 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Free Software +# Foundation, Inc. # This Makefile.in is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. @@ -18,6 +18,23 @@ VPATH = @srcdir@ +am__make_dryrun = \ + { \ + am__dry=no; \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + echo 'am--echo: ; @echo "AM" OK' | $(MAKE) -f - 2>/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } pkgdatadir = $(datadir)/@PACKAGE@ pkgincludedir = $(includedir)/@PACKAGE@ pkglibdir = $(libdir)/@PACKAGE@ @@ -37,7 +54,7 @@ POST_UNINSTALL = : build_triplet = @build@ host_triplet = @host@ target_triplet = @target@ -bin_PROGRAMS = gnunet-service-dns$(EXEEXT) $(am__EXEEXT_1) +libexec_PROGRAMS = gnunet-service-dns$(EXEEXT) $(am__EXEEXT_1) noinst_PROGRAMS = gnunet-dns-monitor$(EXEEXT) \ gnunet-dns-redirector$(EXEEXT) @ENABLE_TEST_RUN_TRUE@TESTS = $(check_SCRIPTS) @@ -47,14 +64,15 @@ DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in \ ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 am__aclocal_m4_deps = $(top_srcdir)/m4/absolute-header.m4 \ $(top_srcdir)/m4/align.m4 $(top_srcdir)/m4/argz.m4 \ - $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/iconv.m4 \ - $(top_srcdir)/m4/lib-ld.m4 $(top_srcdir)/m4/lib-link.m4 \ - $(top_srcdir)/m4/lib-prefix.m4 $(top_srcdir)/m4/libcurl.m4 \ - $(top_srcdir)/m4/libgcrypt.m4 $(top_srcdir)/m4/libtool.m4 \ - $(top_srcdir)/m4/libunistring.m4 $(top_srcdir)/m4/ltdl.m4 \ - $(top_srcdir)/m4/ltoptions.m4 $(top_srcdir)/m4/ltsugar.m4 \ - $(top_srcdir)/m4/ltversion.m4 $(top_srcdir)/m4/lt~obsolete.m4 \ - $(top_srcdir)/m4/nls.m4 $(top_srcdir)/m4/po.m4 \ + $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/glib-2.0.m4 \ + $(top_srcdir)/m4/iconv.m4 $(top_srcdir)/m4/lib-ld.m4 \ + $(top_srcdir)/m4/lib-link.m4 $(top_srcdir)/m4/lib-prefix.m4 \ + $(top_srcdir)/m4/libcurl.m4 $(top_srcdir)/m4/libgcrypt.m4 \ + $(top_srcdir)/m4/libtool.m4 $(top_srcdir)/m4/libunistring.m4 \ + $(top_srcdir)/m4/ltdl.m4 $(top_srcdir)/m4/ltoptions.m4 \ + $(top_srcdir)/m4/ltsugar.m4 $(top_srcdir)/m4/ltversion.m4 \ + $(top_srcdir)/m4/lt~obsolete.m4 $(top_srcdir)/m4/nls.m4 \ + $(top_srcdir)/m4/pkg.m4 $(top_srcdir)/m4/po.m4 \ $(top_srcdir)/m4/progtest.m4 $(top_srcdir)/acinclude.m4 \ $(top_srcdir)/configure.ac am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ @@ -84,16 +102,22 @@ am__nobase_list = $(am__nobase_strip_setup); \ am__base_list = \ sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \ sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g' +am__uninstall_files_from_dir = { \ + test -z "$$files" \ + || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \ + || { echo " ( cd '$$dir' && rm -f" $$files ")"; \ + $(am__cd) "$$dir" && rm -f $$files; }; \ + } am__installdirs = "$(DESTDIR)$(libdir)" "$(DESTDIR)$(plugindir)" \ - "$(DESTDIR)$(bindir)" "$(DESTDIR)$(pkgcfgdir)" + "$(DESTDIR)$(libexecdir)" "$(DESTDIR)$(pkgcfgdir)" LTLIBRARIES = $(lib_LTLIBRARIES) $(plugin_LTLIBRARIES) libgnunet_plugin_block_dns_la_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la am_libgnunet_plugin_block_dns_la_OBJECTS = plugin_block_dns.lo libgnunet_plugin_block_dns_la_OBJECTS = \ $(am_libgnunet_plugin_block_dns_la_OBJECTS) -AM_V_lt = $(am__v_lt_$(V)) -am__v_lt_ = $(am__v_lt_$(AM_DEFAULT_VERBOSITY)) +AM_V_lt = $(am__v_lt_@AM_V@) +am__v_lt_ = $(am__v_lt_@AM_DEFAULT_V@) am__v_lt_0 = --silent libgnunet_plugin_block_dns_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ @@ -115,8 +139,16 @@ libgnunetdnsparser_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ $(AM_CFLAGS) $(CFLAGS) $(libgnunetdnsparser_la_LDFLAGS) \ $(LDFLAGS) -o $@ +libgnunetdnsstub_la_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la +am_libgnunetdnsstub_la_OBJECTS = dnsstub.lo +libgnunetdnsstub_la_OBJECTS = $(am_libgnunetdnsstub_la_OBJECTS) +libgnunetdnsstub_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ + $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ + $(AM_CFLAGS) $(CFLAGS) $(libgnunetdnsstub_la_LDFLAGS) \ + $(LDFLAGS) -o $@ @LINUX_TRUE@am__EXEEXT_1 = gnunet-helper-dns$(EXEEXT) -PROGRAMS = $(bin_PROGRAMS) $(noinst_PROGRAMS) +PROGRAMS = $(libexec_PROGRAMS) $(noinst_PROGRAMS) am_gnunet_dns_monitor_OBJECTS = gnunet-dns-monitor.$(OBJEXT) gnunet_dns_monitor_OBJECTS = $(am_gnunet_dns_monitor_OBJECTS) am__DEPENDENCIES_1 = @@ -127,12 +159,6 @@ gnunet_helper_dns_OBJECTS = $(am_gnunet_helper_dns_OBJECTS) gnunet_helper_dns_LDADD = $(LDADD) am_gnunet_service_dns_OBJECTS = gnunet-service-dns.$(OBJEXT) gnunet_service_dns_OBJECTS = $(am_gnunet_service_dns_OBJECTS) -gnunet_service_dns_DEPENDENCIES = \ - $(top_builddir)/src/tun/libgnunettun.la \ - $(top_builddir)/src/mesh/libgnunetmesh.la \ - $(top_builddir)/src/statistics/libgnunetstatistics.la \ - $(top_builddir)/src/util/libgnunetutil.la \ - $(am__DEPENDENCIES_1) DEFAULT_INCLUDES = -I.@am__isrc@ -I$(top_builddir) depcomp = $(SHELL) $(top_srcdir)/depcomp am__depfiles_maybe = depfiles @@ -143,30 +169,37 @@ LTCOMPILE = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) \ $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) \ $(AM_CFLAGS) $(CFLAGS) -AM_V_CC = $(am__v_CC_$(V)) -am__v_CC_ = $(am__v_CC_$(AM_DEFAULT_VERBOSITY)) +AM_V_CC = $(am__v_CC_@AM_V@) +am__v_CC_ = $(am__v_CC_@AM_DEFAULT_V@) am__v_CC_0 = @echo " CC " $@; -AM_V_at = $(am__v_at_$(V)) -am__v_at_ = $(am__v_at_$(AM_DEFAULT_VERBOSITY)) +AM_V_at = $(am__v_at_@AM_V@) +am__v_at_ = $(am__v_at_@AM_DEFAULT_V@) am__v_at_0 = @ CCLD = $(CC) LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ $(AM_LDFLAGS) $(LDFLAGS) -o $@ -AM_V_CCLD = $(am__v_CCLD_$(V)) -am__v_CCLD_ = $(am__v_CCLD_$(AM_DEFAULT_VERBOSITY)) +AM_V_CCLD = $(am__v_CCLD_@AM_V@) +am__v_CCLD_ = $(am__v_CCLD_@AM_DEFAULT_V@) am__v_CCLD_0 = @echo " CCLD " $@; -AM_V_GEN = $(am__v_GEN_$(V)) -am__v_GEN_ = $(am__v_GEN_$(AM_DEFAULT_VERBOSITY)) +AM_V_GEN = $(am__v_GEN_@AM_V@) +am__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@) am__v_GEN_0 = @echo " GEN " $@; SOURCES = $(libgnunet_plugin_block_dns_la_SOURCES) \ $(libgnunetdns_la_SOURCES) $(libgnunetdnsparser_la_SOURCES) \ - $(gnunet_dns_monitor_SOURCES) $(gnunet_dns_redirector_SOURCES) \ - $(gnunet_helper_dns_SOURCES) $(gnunet_service_dns_SOURCES) + $(libgnunetdnsstub_la_SOURCES) $(gnunet_dns_monitor_SOURCES) \ + $(gnunet_dns_redirector_SOURCES) $(gnunet_helper_dns_SOURCES) \ + $(gnunet_service_dns_SOURCES) DIST_SOURCES = $(libgnunet_plugin_block_dns_la_SOURCES) \ $(libgnunetdns_la_SOURCES) $(libgnunetdnsparser_la_SOURCES) \ - $(gnunet_dns_monitor_SOURCES) $(gnunet_dns_redirector_SOURCES) \ - $(gnunet_helper_dns_SOURCES) $(gnunet_service_dns_SOURCES) + $(libgnunetdnsstub_la_SOURCES) $(gnunet_dns_monitor_SOURCES) \ + $(gnunet_dns_redirector_SOURCES) $(gnunet_helper_dns_SOURCES) \ + $(gnunet_service_dns_SOURCES) +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac DATA = $(pkgcfg_DATA) ETAGS = etags CTAGS = ctags @@ -208,6 +241,10 @@ EXEEXT = @EXEEXT@ EXT_LIBS = @EXT_LIBS@ EXT_LIB_PATH = @EXT_LIB_PATH@ FGREP = @FGREP@ +GLIB_CFLAGS = @GLIB_CFLAGS@ +GLIB_GENMARSHAL = @GLIB_GENMARSHAL@ +GLIB_LIBS = @GLIB_LIBS@ +GLIB_MKENUMS = @GLIB_MKENUMS@ GMSGFMT = @GMSGFMT@ GMSGFMT_015 = @GMSGFMT_015@ GNUNETDNS_GROUP = @GNUNETDNS_GROUP@ @@ -218,6 +255,7 @@ GN_LIBINTL = @GN_LIBINTL@ GN_LIB_LDFLAGS = @GN_LIB_LDFLAGS@ GN_PLUGIN_LDFLAGS = @GN_PLUGIN_LDFLAGS@ GN_USER_HOME_DIR = @GN_USER_HOME_DIR@ +GOBJECT_QUERY = @GOBJECT_QUERY@ GREP = @GREP@ HAVE_LIBUNISTRING = @HAVE_LIBUNISTRING@ INCLTDL = @INCLTDL@ @@ -240,6 +278,8 @@ LIBCURL_CPPFLAGS = @LIBCURL_CPPFLAGS@ LIBGCRYPT_CFLAGS = @LIBGCRYPT_CFLAGS@ LIBGCRYPT_CONFIG = @LIBGCRYPT_CONFIG@ LIBGCRYPT_LIBS = @LIBGCRYPT_LIBS@ +LIBGTOP_CFLAGS = @LIBGTOP_CFLAGS@ +LIBGTOP_LIBS = @LIBGTOP_LIBS@ LIBICONV = @LIBICONV@ LIBINTL = @LIBINTL@ LIBLTDL = @LIBLTDL@ @@ -261,6 +301,7 @@ LT_CONFIG_H = @LT_CONFIG_H@ LT_DLLOADERS = @LT_DLLOADERS@ LT_DLPREOPEN = @LT_DLPREOPEN@ MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ MKDIR_P = @MKDIR_P@ MONKEYPREFIX = @MONKEYPREFIX@ MSGFMT = @MSGFMT@ @@ -270,6 +311,7 @@ MYSQL_CPPFLAGS = @MYSQL_CPPFLAGS@ MYSQL_LDFLAGS = @MYSQL_LDFLAGS@ NM = @NM@ NMEDIT = @NMEDIT@ +NSS_DIR = @NSS_DIR@ OBJC = @OBJC@ OBJCDEPMODE = @OBJCDEPMODE@ OBJCFLAGS = @OBJCFLAGS@ @@ -285,6 +327,7 @@ PACKAGE_TARNAME = @PACKAGE_TARNAME@ PACKAGE_URL = @PACKAGE_URL@ PACKAGE_VERSION = @PACKAGE_VERSION@ PATH_SEPARATOR = @PATH_SEPARATOR@ +PKG_CONFIG = @PKG_CONFIG@ POSTGRES_CPPFLAGS = @POSTGRES_CPPFLAGS@ POSTGRES_LDFLAGS = @POSTGRES_LDFLAGS@ POSUB = @POSUB@ @@ -316,6 +359,7 @@ abs_builddir = @abs_builddir@ abs_srcdir = @abs_srcdir@ abs_top_builddir = @abs_top_builddir@ abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ ac_ct_CC = @ac_ct_CC@ ac_ct_CXX = @ac_ct_CXX@ ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ @@ -338,6 +382,7 @@ datarootdir = @datarootdir@ docdir = @docdir@ dvidir = @dvidir@ exec_prefix = @exec_prefix@ +gitcommand = @gitcommand@ host = @host@ host_alias = @host_alias@ host_cpu = @host_cpu@ @@ -348,10 +393,9 @@ includedir = @includedir@ infodir = @infodir@ install_sh = @install_sh@ libdir = @libdir@ -libexecdir = @libexecdir@ +libexecdir = $(pkglibdir)/libexec/ localedir = @localedir@ localstatedir = @localstatedir@ -lt_ECHO = @lt_ECHO@ ltdl_LIBOBJS = @ltdl_LIBOBJS@ ltdl_LTLIBOBJS = @ltdl_LTLIBOBJS@ mandir = @mandir@ @@ -369,6 +413,7 @@ sbindir = @sbindir@ sharedstatedir = @sharedstatedir@ srcdir = @srcdir@ subdirs = @subdirs@ +svnversioncommand = @svnversioncommand@ sys_symbol_underscore = @sys_symbol_underscore@ sysconfdir = @sysconfdir@ target = @target@ @@ -390,6 +435,7 @@ pkgcfg_DATA = \ @LINUX_TRUE@HIJACKBIN = gnunet-helper-dns lib_LTLIBRARIES = \ libgnunetdnsparser.la \ + libgnunetdnsstub.la \ libgnunetdns.la plugin_LTLIBRARIES = \ @@ -431,19 +477,33 @@ gnunet_service_dns_SOURCES = \ gnunet-service-dns.c gnunet_service_dns_LDADD = \ + $(top_builddir)/src/dns/libgnunetdnsstub.la \ $(top_builddir)/src/tun/libgnunettun.la \ - $(top_builddir)/src/mesh/libgnunetmesh.la \ $(top_builddir)/src/statistics/libgnunetstatistics.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(GN_LIBINTL) +gnunet_service_dns_DEPENDENCIES = \ + libgnunetdnsstub.la + libgnunetdnsparser_la_SOURCES = \ - dnsparser.c + dnsparser.c dnsparser.h libgnunetdnsparser_la_LIBADD = \ - $(top_builddir)/src/util/libgnunetutil.la $(XLIB) + $(top_builddir)/src/util/libgnunetutil.la $(XLIB) \ + -lidn libgnunetdnsparser_la_LDFLAGS = \ + $(GN_LIB_LDFLAGS) \ + -version-info 1:0:1 + +libgnunetdnsstub_la_SOURCES = \ + dnsstub.c + +libgnunetdnsstub_la_LIBADD = \ + $(top_builddir)/src/util/libgnunetutil.la $(XLIB) + +libgnunetdnsstub_la_LDFLAGS = \ $(GN_LIB_LDFLAGS) \ -version-info 0:0:0 @@ -507,7 +567,6 @@ dns.conf: $(top_builddir)/config.status $(srcdir)/dns.conf.in cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ install-libLTLIBRARIES: $(lib_LTLIBRARIES) @$(NORMAL_INSTALL) - test -z "$(libdir)" || $(MKDIR_P) "$(DESTDIR)$(libdir)" @list='$(lib_LTLIBRARIES)'; test -n "$(libdir)" || list=; \ list2=; for p in $$list; do \ if test -f $$p; then \ @@ -515,6 +574,8 @@ install-libLTLIBRARIES: $(lib_LTLIBRARIES) else :; fi; \ done; \ test -z "$$list2" || { \ + echo " $(MKDIR_P) '$(DESTDIR)$(libdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libdir)" || exit 1; \ echo " $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 '$(DESTDIR)$(libdir)'"; \ $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 "$(DESTDIR)$(libdir)"; \ } @@ -538,7 +599,6 @@ clean-libLTLIBRARIES: done install-pluginLTLIBRARIES: $(plugin_LTLIBRARIES) @$(NORMAL_INSTALL) - test -z "$(plugindir)" || $(MKDIR_P) "$(DESTDIR)$(plugindir)" @list='$(plugin_LTLIBRARIES)'; test -n "$(plugindir)" || list=; \ list2=; for p in $$list; do \ if test -f $$p; then \ @@ -546,6 +606,8 @@ install-pluginLTLIBRARIES: $(plugin_LTLIBRARIES) else :; fi; \ done; \ test -z "$$list2" || { \ + echo " $(MKDIR_P) '$(DESTDIR)$(plugindir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(plugindir)" || exit 1; \ echo " $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 '$(DESTDIR)$(plugindir)'"; \ $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 "$(DESTDIR)$(plugindir)"; \ } @@ -567,16 +629,21 @@ clean-pluginLTLIBRARIES: echo "rm -f \"$${dir}/so_locations\""; \ rm -f "$${dir}/so_locations"; \ done -libgnunet_plugin_block_dns.la: $(libgnunet_plugin_block_dns_la_OBJECTS) $(libgnunet_plugin_block_dns_la_DEPENDENCIES) +libgnunet_plugin_block_dns.la: $(libgnunet_plugin_block_dns_la_OBJECTS) $(libgnunet_plugin_block_dns_la_DEPENDENCIES) $(EXTRA_libgnunet_plugin_block_dns_la_DEPENDENCIES) $(AM_V_CCLD)$(libgnunet_plugin_block_dns_la_LINK) -rpath $(plugindir) $(libgnunet_plugin_block_dns_la_OBJECTS) $(libgnunet_plugin_block_dns_la_LIBADD) $(LIBS) -libgnunetdns.la: $(libgnunetdns_la_OBJECTS) $(libgnunetdns_la_DEPENDENCIES) +libgnunetdns.la: $(libgnunetdns_la_OBJECTS) $(libgnunetdns_la_DEPENDENCIES) $(EXTRA_libgnunetdns_la_DEPENDENCIES) $(AM_V_CCLD)$(libgnunetdns_la_LINK) -rpath $(libdir) $(libgnunetdns_la_OBJECTS) $(libgnunetdns_la_LIBADD) $(LIBS) -libgnunetdnsparser.la: $(libgnunetdnsparser_la_OBJECTS) $(libgnunetdnsparser_la_DEPENDENCIES) +libgnunetdnsparser.la: $(libgnunetdnsparser_la_OBJECTS) $(libgnunetdnsparser_la_DEPENDENCIES) $(EXTRA_libgnunetdnsparser_la_DEPENDENCIES) $(AM_V_CCLD)$(libgnunetdnsparser_la_LINK) -rpath $(libdir) $(libgnunetdnsparser_la_OBJECTS) $(libgnunetdnsparser_la_LIBADD) $(LIBS) -install-binPROGRAMS: $(bin_PROGRAMS) +libgnunetdnsstub.la: $(libgnunetdnsstub_la_OBJECTS) $(libgnunetdnsstub_la_DEPENDENCIES) $(EXTRA_libgnunetdnsstub_la_DEPENDENCIES) + $(AM_V_CCLD)$(libgnunetdnsstub_la_LINK) -rpath $(libdir) $(libgnunetdnsstub_la_OBJECTS) $(libgnunetdnsstub_la_LIBADD) $(LIBS) +install-libexecPROGRAMS: $(libexec_PROGRAMS) @$(NORMAL_INSTALL) - test -z "$(bindir)" || $(MKDIR_P) "$(DESTDIR)$(bindir)" - @list='$(bin_PROGRAMS)'; test -n "$(bindir)" || list=; \ + @list='$(libexec_PROGRAMS)'; test -n "$(libexecdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(libexecdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libexecdir)" || exit 1; \ + fi; \ for p in $$list; do echo "$$p $$p"; done | \ sed 's/$(EXEEXT)$$//' | \ while read p p1; do if test -f $$p || test -f $$p1; \ @@ -593,23 +660,23 @@ install-binPROGRAMS: $(bin_PROGRAMS) while read type dir files; do \ if test "$$dir" = .; then dir=; else dir=/$$dir; fi; \ test -z "$$files" || { \ - echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files '$(DESTDIR)$(bindir)$$dir'"; \ - $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files "$(DESTDIR)$(bindir)$$dir" || exit $$?; \ + echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files '$(DESTDIR)$(libexecdir)$$dir'"; \ + $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files "$(DESTDIR)$(libexecdir)$$dir" || exit $$?; \ } \ ; done -uninstall-binPROGRAMS: +uninstall-libexecPROGRAMS: @$(NORMAL_UNINSTALL) - @list='$(bin_PROGRAMS)'; test -n "$(bindir)" || list=; \ + @list='$(libexec_PROGRAMS)'; test -n "$(libexecdir)" || list=; \ files=`for p in $$list; do echo "$$p"; done | \ sed -e 'h;s,^.*/,,;s/$(EXEEXT)$$//;$(transform)' \ -e 's/$$/$(EXEEXT)/' `; \ test -n "$$list" || exit 0; \ - echo " ( cd '$(DESTDIR)$(bindir)' && rm -f" $$files ")"; \ - cd "$(DESTDIR)$(bindir)" && rm -f $$files + echo " ( cd '$(DESTDIR)$(libexecdir)' && rm -f" $$files ")"; \ + cd "$(DESTDIR)$(libexecdir)" && rm -f $$files -clean-binPROGRAMS: - @list='$(bin_PROGRAMS)'; test -n "$$list" || exit 0; \ +clean-libexecPROGRAMS: + @list='$(libexec_PROGRAMS)'; test -n "$$list" || exit 0; \ echo " rm -f" $$list; \ rm -f $$list || exit $$?; \ test -n "$(EXEEXT)" || exit 0; \ @@ -625,16 +692,16 @@ clean-noinstPROGRAMS: list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ echo " rm -f" $$list; \ rm -f $$list -gnunet-dns-monitor$(EXEEXT): $(gnunet_dns_monitor_OBJECTS) $(gnunet_dns_monitor_DEPENDENCIES) +gnunet-dns-monitor$(EXEEXT): $(gnunet_dns_monitor_OBJECTS) $(gnunet_dns_monitor_DEPENDENCIES) $(EXTRA_gnunet_dns_monitor_DEPENDENCIES) @rm -f gnunet-dns-monitor$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_dns_monitor_OBJECTS) $(gnunet_dns_monitor_LDADD) $(LIBS) -gnunet-dns-redirector$(EXEEXT): $(gnunet_dns_redirector_OBJECTS) $(gnunet_dns_redirector_DEPENDENCIES) +gnunet-dns-redirector$(EXEEXT): $(gnunet_dns_redirector_OBJECTS) $(gnunet_dns_redirector_DEPENDENCIES) $(EXTRA_gnunet_dns_redirector_DEPENDENCIES) @rm -f gnunet-dns-redirector$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_dns_redirector_OBJECTS) $(gnunet_dns_redirector_LDADD) $(LIBS) -gnunet-helper-dns$(EXEEXT): $(gnunet_helper_dns_OBJECTS) $(gnunet_helper_dns_DEPENDENCIES) +gnunet-helper-dns$(EXEEXT): $(gnunet_helper_dns_OBJECTS) $(gnunet_helper_dns_DEPENDENCIES) $(EXTRA_gnunet_helper_dns_DEPENDENCIES) @rm -f gnunet-helper-dns$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_helper_dns_OBJECTS) $(gnunet_helper_dns_LDADD) $(LIBS) -gnunet-service-dns$(EXEEXT): $(gnunet_service_dns_OBJECTS) $(gnunet_service_dns_DEPENDENCIES) +gnunet-service-dns$(EXEEXT): $(gnunet_service_dns_OBJECTS) $(gnunet_service_dns_DEPENDENCIES) $(EXTRA_gnunet_service_dns_DEPENDENCIES) @rm -f gnunet-service-dns$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_service_dns_OBJECTS) $(gnunet_service_dns_LDADD) $(LIBS) @@ -646,6 +713,7 @@ distclean-compile: @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/dns_api.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/dnsparser.Plo@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/dnsstub.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-dns-monitor.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-dns-redirector.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-helper-dns.Po@am__quote@ @@ -655,26 +723,23 @@ distclean-compile: .c.o: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c $< .c.obj: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'` @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c `$(CYGPATH_W) '$<'` +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c `$(CYGPATH_W) '$<'` .c.lo: @am__fastdepCC_TRUE@ $(AM_V_CC)$(LTCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LTCOMPILE) -c -o $@ $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LTCOMPILE) -c -o $@ $< mostlyclean-libtool: -rm -f *.lo @@ -683,8 +748,11 @@ clean-libtool: -rm -rf .libs _libs install-pkgcfgDATA: $(pkgcfg_DATA) @$(NORMAL_INSTALL) - test -z "$(pkgcfgdir)" || $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" @list='$(pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(pkgcfgdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" || exit 1; \ + fi; \ for p in $$list; do \ if test -f "$$p"; then d=; else d="$(srcdir)/"; fi; \ echo "$$d$$p"; \ @@ -698,9 +766,7 @@ uninstall-pkgcfgDATA: @$(NORMAL_UNINSTALL) @list='$(pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ files=`for p in $$list; do echo $$p; done | sed -e 's|^.*/||'`; \ - test -n "$$files" || exit 0; \ - echo " ( cd '$(DESTDIR)$(pkgcfgdir)' && rm -f" $$files ")"; \ - cd "$(DESTDIR)$(pkgcfgdir)" && rm -f $$files + dir='$(DESTDIR)$(pkgcfgdir)'; $(am__uninstall_files_from_dir) ID: $(HEADERS) $(SOURCES) $(LISP) $(TAGS_FILES) list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ @@ -835,14 +901,15 @@ check-TESTS: $(TESTS) fi; \ dashes=`echo "$$dashes" | sed s/./=/g`; \ if test "$$failed" -eq 0; then \ - echo "$$grn$$dashes"; \ + col="$$grn"; \ else \ - echo "$$red$$dashes"; \ + col="$$red"; \ fi; \ - echo "$$banner"; \ - test -z "$$skipped" || echo "$$skipped"; \ - test -z "$$report" || echo "$$report"; \ - echo "$$dashes$$std"; \ + echo "$${col}$$dashes$${std}"; \ + echo "$${col}$$banner$${std}"; \ + test -z "$$skipped" || echo "$${col}$$skipped$${std}"; \ + test -z "$$report" || echo "$${col}$$report$${std}"; \ + echo "$${col}$$dashes$${std}"; \ test "$$failed" -eq 0; \ else :; fi @@ -881,10 +948,8 @@ check-am: all-am $(MAKE) $(AM_MAKEFLAGS) check-TESTS check: check-am all-am: Makefile $(LTLIBRARIES) $(PROGRAMS) $(DATA) -install-binPROGRAMS: install-libLTLIBRARIES - installdirs: - for dir in "$(DESTDIR)$(libdir)" "$(DESTDIR)$(plugindir)" "$(DESTDIR)$(bindir)" "$(DESTDIR)$(pkgcfgdir)"; do \ + for dir in "$(DESTDIR)$(libdir)" "$(DESTDIR)$(plugindir)" "$(DESTDIR)$(libexecdir)" "$(DESTDIR)$(pkgcfgdir)"; do \ test -z "$$dir" || $(MKDIR_P) "$$dir"; \ done install: install-am @@ -897,10 +962,15 @@ install-am: all-am installcheck: installcheck-am install-strip: - $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ - install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ - `test -z '$(STRIP)' || \ - echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi mostlyclean-generic: clean-generic: @@ -914,7 +984,7 @@ maintainer-clean-generic: @echo "it deletes files that may require special tools to rebuild." clean: clean-am -clean-am: clean-binPROGRAMS clean-generic clean-libLTLIBRARIES \ +clean-am: clean-generic clean-libLTLIBRARIES clean-libexecPROGRAMS \ clean-libtool clean-noinstPROGRAMS clean-pluginLTLIBRARIES \ mostlyclean-am @@ -942,7 +1012,7 @@ install-dvi: install-dvi-am install-dvi-am: -install-exec-am: install-binPROGRAMS install-libLTLIBRARIES +install-exec-am: install-libLTLIBRARIES install-libexecPROGRAMS @$(NORMAL_INSTALL) $(MAKE) $(AM_MAKEFLAGS) install-exec-hook install-html: install-html-am @@ -983,35 +1053,32 @@ ps: ps-am ps-am: -uninstall-am: uninstall-binPROGRAMS uninstall-libLTLIBRARIES \ +uninstall-am: uninstall-libLTLIBRARIES uninstall-libexecPROGRAMS \ uninstall-pkgcfgDATA uninstall-pluginLTLIBRARIES .MAKE: check-am install-am install-exec-am install-strip .PHONY: CTAGS GTAGS all all-am check check-TESTS check-am clean \ - clean-binPROGRAMS clean-generic clean-libLTLIBRARIES \ + clean-generic clean-libLTLIBRARIES clean-libexecPROGRAMS \ clean-libtool clean-noinstPROGRAMS clean-pluginLTLIBRARIES \ ctags distclean distclean-compile distclean-generic \ distclean-libtool distclean-tags distdir dvi dvi-am html \ - html-am info info-am install install-am install-binPROGRAMS \ - install-data install-data-am install-dvi install-dvi-am \ - install-exec install-exec-am install-exec-hook install-html \ - install-html-am install-info install-info-am \ - install-libLTLIBRARIES install-man install-pdf install-pdf-am \ + html-am info info-am install install-am install-data \ + install-data-am install-dvi install-dvi-am install-exec \ + install-exec-am install-exec-hook install-html install-html-am \ + install-info install-info-am install-libLTLIBRARIES \ + install-libexecPROGRAMS install-man install-pdf install-pdf-am \ install-pkgcfgDATA install-pluginLTLIBRARIES install-ps \ install-ps-am install-strip installcheck installcheck-am \ installdirs maintainer-clean maintainer-clean-generic \ mostlyclean mostlyclean-compile mostlyclean-generic \ mostlyclean-libtool pdf pdf-am ps ps-am tags uninstall \ - uninstall-am uninstall-binPROGRAMS uninstall-libLTLIBRARIES \ - uninstall-pkgcfgDATA uninstall-pluginLTLIBRARIES + uninstall-am uninstall-libLTLIBRARIES \ + uninstall-libexecPROGRAMS uninstall-pkgcfgDATA \ + uninstall-pluginLTLIBRARIES @LINUX_TRUE@install-exec-hook: -@LINUX_TRUE@ $(SUDO_BINARY) chown root $(bindir)/gnunet-helper-dns || true -@LINUX_TRUE@ $(SUDO_BINARY) chgrp $(GNUNETDNS_GROUP) $(bindir)/gnunet-helper-dns || true -@LINUX_TRUE@ $(SUDO_BINARY) chmod 4750 $(bindir)/gnunet-helper-dns || true -@LINUX_TRUE@ $(SUDO_BINARY) chown gnunet:$(GNUNETDNS_GROUP) $(bindir)/gnunet-service-dns || true -@LINUX_TRUE@ $(SUDO_BINARY) chmod 2750 $(bindir)/gnunet-service-dns || true +@LINUX_TRUE@ $(top_srcdir)/src/dns/install-dns-helper.sh $(libexecdir) $(GNUNETDNS_GROUP) $(SUDO_BINARY) || true @LINUX_FALSE@install-exec-hook: # Tell versions [3.59,3.63) of GNU make to not export all variables. diff --git a/src/dns/dns.conf.in b/src/dns/dns.conf.in index d2c6795..7944b41 100644 --- a/src/dns/dns.conf.in +++ b/src/dns/dns.conf.in @@ -2,7 +2,6 @@ AUTOSTART = YES HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-dns UNIXPATH = /tmp/gnunet-service-dns.sock @@ -16,14 +15,6 @@ UNIX_MATCH_GID = YES # we never use it, even if @UNIXONLY@ is not set (just to be safe) @UNIXONLY@ PORT = 0 -# This option should be set to YES to allow the DNS service to -# perform lookups against the locally configured DNS resolver. -# (set to "NO" if no normal ISP is locally available and thus -# requests for normal ".com"/".org"/etc. must be routed via -# the GNUnet VPN (the GNUNET PT daemon then needs to be configured -# to intercept and route DNS queries via mesh). -PROVIDE_EXIT = YES - # Name of the virtual interface we use to intercept DNS traffic. IFNAME = gnunet-dns @@ -40,5 +31,5 @@ IPV4MASK = 255.255.0.0 # of a DNS resolver to use. Only works if "PROVIDE_EXIT" is also set to YES. Must absolutely # NOT be an address of any of GNUnet's virtual tunnel interfaces. Use a well-known # public DNS resolver or your ISP's resolver from /etc/resolv.conf. -# DNS_EXIT = 8.8.8.8 +DNS_EXIT = 8.8.8.8 diff --git a/src/dns/dnsparser.c b/src/dns/dnsparser.c index 0e658bd..6ddfebb 100644 --- a/src/dns/dnsparser.c +++ b/src/dns/dnsparser.c @@ -25,47 +25,80 @@ * @author Christian Grothoff */ #include "platform.h" +#include +#if WINDOWS +#include +#endif #include "gnunet_util_lib.h" #include "gnunet_dnsparser_lib.h" +#include "dnsparser.h" -// DNS-Stuff -GNUNET_NETWORK_STRUCT_BEGIN -/* FIXME: replace this one with the one from tcpip_tun.h! */ -struct GNUNET_TUN_DnsHeader -{ - uint16_t id GNUNET_PACKED; - struct GNUNET_DNSPARSER_Flags flags; - uint16_t query_count GNUNET_PACKED; // number of questions - uint16_t answer_rcount GNUNET_PACKED; // number of answers - uint16_t authority_rcount GNUNET_PACKED; // number of authority-records - uint16_t additional_rcount GNUNET_PACKED; // number of additional records -}; - -struct query_line +/** + * Check if a label in UTF-8 format can be coded into valid IDNA. + * This can fail if the ASCII-conversion becomes longer than 63 characters. + * + * @param label label to check (UTF-8 string) + * @return GNUNET_OK if the label can be converted to IDNA, + * GNUNET_SYSERR if the label is not valid for DNS names + */ +int +GNUNET_DNSPARSER_check_label (const char *label) { - uint16_t type GNUNET_PACKED; - uint16_t class GNUNET_PACKED; -}; + char *output; + size_t slen; + + if (NULL != strchr (label, '.')) + return GNUNET_SYSERR; /* not a label! Did you mean GNUNET_DNSPARSER_check_name? */ + if (IDNA_SUCCESS != + idna_to_ascii_8z (label, &output, IDNA_USE_STD3_ASCII_RULES)) + return GNUNET_SYSERR; + slen = strlen (output); +#if WINDOWS + idn_free (output); +#else + free (output); +#endif + return (slen > 63) ? GNUNET_SYSERR : GNUNET_OK; +} -struct record_line -{ - uint16_t type GNUNET_PACKED; - uint16_t class GNUNET_PACKED; - uint32_t ttl GNUNET_PACKED; - uint16_t data_len GNUNET_PACKED; -}; -struct soa_data +/** + * Check if a label in UTF-8 format can be coded into valid IDNA. + * This can fail if the ASCII-conversion becomes longer than 253 characters. + * + * @param name name to check (UTF-8 string) + * @return GNUNET_OK if the label can be converted to IDNA, + * GNUNET_SYSERR if the label is not valid for DNS names + */ +int +GNUNET_DNSPARSER_check_name (const char *name) { - uint32_t serial GNUNET_PACKED; - uint32_t refresh GNUNET_PACKED; - uint32_t retry GNUNET_PACKED; - uint32_t expire GNUNET_PACKED; - uint32_t minimum GNUNET_PACKED; -}; - -GNUNET_NETWORK_STRUCT_END + char *ldup; + char *output; + size_t slen; + char *tok; + + ldup = GNUNET_strdup (name); + for (tok = strtok (ldup, "."); NULL != tok; tok = strtok (NULL, ".")) + if (GNUNET_OK != + GNUNET_DNSPARSER_check_label (tok)) + { + GNUNET_free (ldup); + return GNUNET_SYSERR; + } + GNUNET_free (ldup); + if (IDNA_SUCCESS != + idna_to_ascii_8z (name, &output, IDNA_USE_STD3_ASCII_RULES)) + return GNUNET_SYSERR; + slen = strlen (output); +#if WINDOWS + idn_free (output); +#else + free (output); +#endif + return (slen > 253) ? GNUNET_SYSERR : GNUNET_OK; +} /** @@ -90,6 +123,8 @@ parse_name (const char *udp_payload, char *xstr; uint8_t len; size_t xoff; + char *utf8; + Idna_rc rc; ret = GNUNET_strdup (""); while (1) @@ -107,10 +142,36 @@ parse_name (const char *udp_payload, if (*off + 1 + len > udp_payload_length) goto error; GNUNET_asprintf (&tmp, - "%s%.*s.", - ret, + "%.*s", (int) len, &udp_payload[*off + 1]); + if (IDNA_SUCCESS != + (rc = idna_to_unicode_8z8z (tmp, &utf8, IDNA_USE_STD3_ASCII_RULES))) + { + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + _("Failed to convert DNS IDNA name `%s' to UTF-8: %s\n"), + tmp, + idna_strerror (rc)); + GNUNET_free (tmp); + GNUNET_asprintf (&tmp, + "%s%.*s.", + ret, + (int) len, + &udp_payload[*off + 1]); + } + else + { + GNUNET_free (tmp); + GNUNET_asprintf (&tmp, + "%s%s.", + ret, + utf8); +#if WINDOWS + idn_free (utf8); +#else + free (utf8); +#endif + } GNUNET_free (ret); ret = tmp; *off += 1 + len; @@ -214,6 +275,9 @@ parse_record (const char *udp_payload, struct soa_data soa; uint16_t mxpref; uint16_t data_len; + struct srv_data srv; + char *ndup; + char *tok; name = parse_name (udp_payload, udp_payload_length, @@ -282,6 +346,50 @@ parse_record (const char *udp_payload, if (old_off + data_len != *off) return GNUNET_SYSERR; return GNUNET_OK; + case GNUNET_DNSPARSER_TYPE_SRV: + if ('_' != *r->name) + return GNUNET_SYSERR; /* all valid srv names must start with "_" */ + if (NULL == strstr (r->name, "._")) + return GNUNET_SYSERR; /* necessary string from "._$PROTO" not present */ + old_off = *off; + if (*off + sizeof (struct srv_data) > udp_payload_length) + return GNUNET_SYSERR; + memcpy (&srv, &udp_payload[*off], sizeof (struct srv_data)); + (*off) += sizeof (struct srv_data); + r->data.srv = GNUNET_malloc (sizeof (struct GNUNET_DNSPARSER_SrvRecord)); + r->data.srv->priority = ntohs (srv.prio); + r->data.srv->weight = ntohs (srv.weight); + r->data.srv->port = ntohs (srv.port); + /* parse 'data.hostname' into components, which are + "_$SERVICE._$PROTO.$DOMAIN_NAME" */ + ndup = GNUNET_strdup (r->name); + tok = strtok (ndup, "."); + GNUNET_assert (NULL != tok); + GNUNET_assert ('_' == *tok); + r->data.srv->service = GNUNET_strdup (&tok[1]); + tok = strtok (NULL, "."); + if ( (NULL == tok) || ('_' != *tok) ) + { + GNUNET_free (r->data.srv); + GNUNET_free (ndup); + return GNUNET_SYSERR; + } + r->data.srv->proto = GNUNET_strdup (&tok[1]); + tok = strtok (NULL, "."); + if (NULL == tok) + { + GNUNET_free (r->data.srv); + GNUNET_free (ndup); + return GNUNET_SYSERR; + } + r->data.srv->domain_name = GNUNET_strdup (tok); + GNUNET_free (ndup); + r->data.srv->target = parse_name (udp_payload, + udp_payload_length, + off, 0); + if (old_off + data_len != *off) + return GNUNET_SYSERR; + return GNUNET_OK; default: r->data.raw.data = GNUNET_malloc (data_len); r->data.raw.data_len = data_len; @@ -393,6 +501,24 @@ free_soa (struct GNUNET_DNSPARSER_SoaRecord *soa) } +/** + * Free SRV information record. + * + * @param srv record to free + */ +static void +free_srv (struct GNUNET_DNSPARSER_SrvRecord *srv) +{ + if (NULL == srv) + return; + GNUNET_free_non_null (srv->target); + GNUNET_free_non_null (srv->domain_name); + GNUNET_free_non_null (srv->proto); + GNUNET_free_non_null (srv->service); + GNUNET_free (srv); +} + + /** * Free MX information record. * @@ -420,6 +546,9 @@ free_record (struct GNUNET_DNSPARSER_Record *r) case GNUNET_DNSPARSER_TYPE_SOA: free_soa (r->data.soa); break; + case GNUNET_DNSPARSER_TYPE_SRV: + free_srv (r->data.srv); + break; case GNUNET_DNSPARSER_TYPE_NS: case GNUNET_DNSPARSER_TYPE_CNAME: case GNUNET_DNSPARSER_TYPE_PTR: @@ -480,34 +609,60 @@ add_name (char *dst, const char *name) { const char *dot; + const char *idna_name; + char *idna_start; size_t start; size_t pos; size_t len; + Idna_rc rc; if (NULL == name) return GNUNET_SYSERR; - start = *off; - if (start + strlen (name) + 2 > dst_len) + + if (IDNA_SUCCESS != + (rc = idna_to_ascii_8z (name, &idna_start, IDNA_USE_STD3_ASCII_RULES))) + { + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + _("Failed to convert UTF-8 name `%s' to DNS IDNA format: %s\n"), + name, + idna_strerror (rc)); return GNUNET_NO; + } + idna_name = idna_start; + start = *off; + if (start + strlen (idna_name) + 2 > dst_len) + goto fail; pos = start; do { - dot = strchr (name, '.'); + dot = strchr (idna_name, '.'); if (NULL == dot) - len = strlen (name); + len = strlen (idna_name); else - len = dot - name; + len = dot - idna_name; if ( (len >= 64) || (len == 0) ) - return GNUNET_NO; /* segment too long or empty */ + goto fail; /* segment too long or empty */ dst[pos++] = (char) (uint8_t) len; - memcpy (&dst[pos], name, len); + memcpy (&dst[pos], idna_name, len); pos += len; - name += len + 1; /* also skip dot */ + idna_name += len + 1; /* also skip dot */ } while (NULL != dot); dst[pos++] = '\0'; /* terminator */ *off = pos; +#if WINDOWS + idn_free (idna_start); +#else + free (idna_start); +#endif return GNUNET_OK; + fail: +#if WINDOWS + idn_free (idna_start); +#else + free (idna_start); +#endif + return GNUNET_NO; } @@ -615,6 +770,43 @@ add_soa (char *dst, } +/** + * Add an SRV record to the UDP packet at the given location. + * + * @param dst where to write the SRV record + * @param dst_len number of bytes in dst + * @param off pointer to offset where to write the SRV information (increment by bytes used) + * can also change if there was an error + * @param srv SRV information to write + * @return GNUNET_SYSERR if 'srv' is invalid + * GNUNET_NO if 'srv' did not fit + * GNUNET_OK if 'srv' was added to 'dst' + */ +static int +add_srv (char *dst, + size_t dst_len, + size_t *off, + const struct GNUNET_DNSPARSER_SrvRecord *srv) +{ + struct srv_data sd; + int ret; + + if (*off + sizeof (struct srv_data) > dst_len) + return GNUNET_NO; + sd.prio = htons (srv->priority); + sd.weight = htons (srv->weight); + sd.port = htons (srv->port); + memcpy (&dst[*off], &sd, sizeof (sd)); + (*off) += sizeof (sd); + if (GNUNET_OK != (ret = add_name (dst, + dst_len, + off, + srv->target))) + return ret; + return GNUNET_OK; +} + + /** * Add a DNS record to the UDP packet at the given location. * @@ -637,10 +829,23 @@ add_record (char *dst, size_t start; size_t pos; struct record_line rl; - + char *name; + start = *off; - ret = add_name (dst, dst_len - sizeof (struct record_line), off, record->name); - if (ret != GNUNET_OK) + /* for SRV records, we can create the name from the details + of the record if needed */ + name = record->name; + if ( (GNUNET_DNSPARSER_TYPE_SRV == record->type) && + (NULL == name) ) + GNUNET_asprintf (&name, + "_%s._%s.%s", + record->data.srv->service, + record->data.srv->proto, + record->data.srv->domain_name); + ret = add_name (dst, dst_len - sizeof (struct record_line), off, name); + if (name != record->name) + GNUNET_free (name); + if (GNUNET_OK != ret) return ret; /* '*off' is now the position where we will need to write the record line */ @@ -658,6 +863,9 @@ add_record (char *dst, case GNUNET_DNSPARSER_TYPE_PTR: ret = add_name (dst, dst_len, &pos, record->data.hostname); break; + case GNUNET_DNSPARSER_TYPE_SRV: + ret = add_srv (dst, dst_len, &pos, record->data.srv); + break; default: if (pos + record->data.raw.data_len > dst_len) { @@ -669,7 +877,7 @@ add_record (char *dst, ret = GNUNET_OK; break; } - if (ret != GNUNET_OK) + if (GNUNET_OK != ret) { *off = start; return GNUNET_NO; diff --git a/src/dns/dnsparser.h b/src/dns/dnsparser.h new file mode 100644 index 0000000..d312f89 --- /dev/null +++ b/src/dns/dnsparser.h @@ -0,0 +1,195 @@ +/* + This file is part of GNUnet + (C) 2010, 2011, 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 2, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. + */ + +/** + * @file dns/dnsparser.h + * @brief helper library to parse DNS packets. + * @author Philipp Toelke + * @author Christian Grothoff + * @author Martin Schanzenbach + */ +GNUNET_NETWORK_STRUCT_BEGIN + +/* FIXME: replace this one with the one from tcpip_tun.h!? */ +/** + * Head of a any DNS message. + */ +struct GNUNET_TUN_DnsHeader +{ + /** + * Request/response ID. (NBO) + */ + uint16_t id GNUNET_PACKED; + + /** + * Flags for the operation. + */ + struct GNUNET_DNSPARSER_Flags flags; + + /** + * number of questions (NBO) + */ + uint16_t query_count GNUNET_PACKED; + + /** + * number of answers (NBO) + */ + uint16_t answer_rcount GNUNET_PACKED; + + /** + * number of authority-records (NBO) + */ + uint16_t authority_rcount GNUNET_PACKED; + + /** + * number of additional records (NBO) + */ + uint16_t additional_rcount GNUNET_PACKED; +}; + + +/** + * DNS query prefix. + */ +struct query_line +{ + /** + * Desired type (GNUNET_DNSPARSER_TYPE_XXX). (NBO) + */ + uint16_t type GNUNET_PACKED; + + /** + * Desired class (usually GNUNET_DNSPARSER_CLASS_INTERNET). (NBO) + */ + uint16_t class GNUNET_PACKED; +}; + + +/** + * General DNS record prefix. + */ +struct record_line +{ + /** + * Record type (GNUNET_DNSPARSER_TYPE_XXX). (NBO) + */ + uint16_t type GNUNET_PACKED; + + /** + * Record class (usually GNUNET_DNSPARSER_CLASS_INTERNET). (NBO) + */ + uint16_t class GNUNET_PACKED; + + /** + * Expiration for the record (in seconds). (NBO) + */ + uint32_t ttl GNUNET_PACKED; + + /** + * Number of bytes of data that follow. (NBO) + */ + uint16_t data_len GNUNET_PACKED; +}; + + +/** + * Payload of DNS SOA record (header). + */ +struct soa_data +{ + /** + * The version number of the original copy of the zone. (NBO) + */ + uint32_t serial GNUNET_PACKED; + + /** + * Time interval before the zone should be refreshed. (NBO) + */ + uint32_t refresh GNUNET_PACKED; + + /** + * Time interval that should elapse before a failed refresh should + * be retried. (NBO) + */ + uint32_t retry GNUNET_PACKED; + + /** + * Time value that specifies the upper limit on the time interval + * that can elapse before the zone is no longer authoritative. (NBO) + */ + uint32_t expire GNUNET_PACKED; + + /** + * The bit minimum TTL field that should be exported with any RR + * from this zone. (NBO) + */ + uint32_t minimum GNUNET_PACKED; +}; + + +/** + * Payload of DNS SRV record (header). + */ +struct srv_data +{ + + /** + * Preference for this entry (lower value is higher preference). Clients + * will contact hosts from the lowest-priority group first and fall back + * to higher priorities if the low-priority entries are unavailable. (NBO) + */ + uint16_t prio GNUNET_PACKED; + + /** + * Relative weight for records with the same priority. Clients will use + * the hosts of the same (lowest) priority with a probability proportional + * to the weight given. (NBO) + */ + uint16_t weight GNUNET_PACKED; + + /** + * TCP or UDP port of the service. (NBO) + */ + uint16_t port GNUNET_PACKED; + + /* followed by 'target' name */ +}; + + +/** + * Payload of GNS VPN record + */ +struct vpn_data +{ + /** + * The peer to contact + */ + struct GNUNET_HashCode peer; + + /** + * The protocol to use + */ + uint16_t proto GNUNET_PACKED; + + + /* followed by the servicename / identifier / password (0-terminated) */ +}; + +GNUNET_NETWORK_STRUCT_END diff --git a/src/dns/dnsstub.c b/src/dns/dnsstub.c new file mode 100644 index 0000000..c755aff --- /dev/null +++ b/src/dns/dnsstub.c @@ -0,0 +1,561 @@ +/* + This file is part of GNUnet. + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ +/** + * @file dns/dnsstub.c + * @brief DNS stub resolver which sends DNS requests to an actual resolver + * @author Christian Grothoff + */ +#include "platform.h" +#include "gnunet_util_lib.h" +#include "gnunet_dnsstub_lib.h" + +/** + * Timeout for an external (Internet-DNS) DNS resolution + */ +#define REQUEST_TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 5) + +/** + * How many DNS sockets do we open at most at the same time? + * (technical socket maximum is this number x2 for IPv4+IPv6) + */ +#define DNS_SOCKET_MAX 128 + + +/** + * UDP socket we are using for sending DNS requests to the Internet. + */ +struct GNUNET_DNSSTUB_RequestSocket +{ + + /** + * UDP socket we use for this request for IPv4 + */ + struct GNUNET_NETWORK_Handle *dnsout4; + + /** + * UDP socket we use for this request for IPv6 + */ + struct GNUNET_NETWORK_Handle *dnsout6; + + /** + * Function to call with result. + */ + GNUNET_DNSSTUB_ResultCallback rc; + + /** + * Closure for 'rc'. + */ + void *rc_cls; + + /** + * Task for reading from dnsout4 and dnsout6. + */ + GNUNET_SCHEDULER_TaskIdentifier read_task; + + /** + * When should this request time out? + */ + struct GNUNET_TIME_Absolute timeout; + + /** + * Address we sent the DNS request to. + */ + struct sockaddr_storage addr; + + /** + * Number of bytes in 'addr'. + */ + socklen_t addrlen; + +}; + + +/** + * Handle to the stub resolver. + */ +struct GNUNET_DNSSTUB_Context +{ + + /** + * Array of all open sockets for DNS requests. + */ + struct GNUNET_DNSSTUB_RequestSocket sockets[DNS_SOCKET_MAX]; + + /** + * IP address to use for the DNS server if we are a DNS exit service + * (for VPN via mesh); otherwise NULL. + */ + char *dns_exit; +}; + + + +/** + * We're done with a GNUNET_DNSSTUB_RequestSocket, close it for now. + * + * @param rs request socket to clean up + */ +static void +cleanup_rs (struct GNUNET_DNSSTUB_RequestSocket *rs) +{ + if (NULL != rs->dnsout4) + { + GNUNET_NETWORK_socket_close (rs->dnsout4); + rs->dnsout4 = NULL; + } + if (NULL != rs->dnsout6) + { + GNUNET_NETWORK_socket_close (rs->dnsout6); + rs->dnsout6 = NULL; + } + if (GNUNET_SCHEDULER_NO_TASK != rs->read_task) + { + GNUNET_SCHEDULER_cancel (rs->read_task); + rs->read_task = GNUNET_SCHEDULER_NO_TASK; + } +} + + +/** + * Open source port for sending DNS requests + * + * @param af AF_INET or AF_INET6 + * @return GNUNET_OK on success + */ +static struct GNUNET_NETWORK_Handle * +open_socket (int af) +{ + struct sockaddr_in a4; + struct sockaddr_in6 a6; + struct sockaddr *sa; + socklen_t alen; + struct GNUNET_NETWORK_Handle *ret; + + ret = GNUNET_NETWORK_socket_create (af, SOCK_DGRAM, 0); + if (NULL == ret) + return NULL; + switch (af) + { + case AF_INET: + memset (&a4, 0, alen = sizeof (struct sockaddr_in)); + sa = (struct sockaddr *) &a4; + break; + case AF_INET6: + memset (&a6, 0, alen = sizeof (struct sockaddr_in6)); + sa = (struct sockaddr *) &a6; + break; + default: + GNUNET_break (0); + GNUNET_NETWORK_socket_close (ret); + return NULL; + } + sa->sa_family = af; + if (GNUNET_OK != GNUNET_NETWORK_socket_bind (ret, + sa, + alen)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Could not bind to any port: %s\n"), + STRERROR (errno)); + GNUNET_NETWORK_socket_close (ret); + return NULL; + } + return ret; +} + + +/** + * Read a DNS response from the (unhindered) UDP-Socket + * + * @param cls socket to read from + * @param tc scheduler context (must be shutdown or read ready) + */ +static void +read_response (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc); + + +/** + * Get a socket of the specified address family to send out a + * UDP DNS request to the Internet. + * + * @param ctx the DNSSTUB context + * @param af desired address family + * @return NULL on error (given AF not "supported") + */ +static struct GNUNET_DNSSTUB_RequestSocket * +get_request_socket (struct GNUNET_DNSSTUB_Context *ctx, + int af) +{ + struct GNUNET_DNSSTUB_RequestSocket *rs; + struct GNUNET_NETWORK_FDSet *rset; + + rs = &ctx->sockets[GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_NONCE, + DNS_SOCKET_MAX)]; + rs->timeout = GNUNET_TIME_relative_to_absolute (REQUEST_TIMEOUT); + switch (af) + { + case AF_INET: + if (NULL == rs->dnsout4) + rs->dnsout4 = open_socket (AF_INET); + break; + case AF_INET6: + if (NULL == rs->dnsout6) + rs->dnsout6 = open_socket (AF_INET6); + break; + default: + return NULL; + } + if (GNUNET_SCHEDULER_NO_TASK != rs->read_task) + { + GNUNET_SCHEDULER_cancel (rs->read_task); + rs->read_task = GNUNET_SCHEDULER_NO_TASK; + } + if ( (NULL == rs->dnsout4) && + (NULL == rs->dnsout6) ) + return NULL; + rset = GNUNET_NETWORK_fdset_create (); + if (NULL != rs->dnsout4) + GNUNET_NETWORK_fdset_set (rset, rs->dnsout4); + if (NULL != rs->dnsout6) + GNUNET_NETWORK_fdset_set (rset, rs->dnsout6); + rs->read_task = GNUNET_SCHEDULER_add_select (GNUNET_SCHEDULER_PRIORITY_DEFAULT, + REQUEST_TIMEOUT, + rset, + NULL, + &read_response, rs); + GNUNET_NETWORK_fdset_destroy (rset); + return rs; +} + + +/** + * Perform DNS resolution. + * + * @param ctx stub resolver to use + * @param sa the socket address + * @param sa_len the socket length + * @param request DNS request to transmit + * @param request_len number of bytes in msg + * @param rc function to call with result + * @param rc_cls closure for 'rc' + * @return socket used for the request, NULL on error + */ +struct GNUNET_DNSSTUB_RequestSocket * +GNUNET_DNSSTUB_resolve (struct GNUNET_DNSSTUB_Context *ctx, + const struct sockaddr *sa, + socklen_t sa_len, + const void *request, + size_t request_len, + GNUNET_DNSSTUB_ResultCallback rc, + void *rc_cls) +{ + struct GNUNET_DNSSTUB_RequestSocket *rs; + struct GNUNET_NETWORK_Handle *ret; + int af; + + af = sa->sa_family; + if (NULL == (rs = get_request_socket (ctx, af))) + return NULL; + if (NULL != rs->dnsout4) + ret = rs->dnsout4; + else + ret = rs->dnsout6; + GNUNET_assert (NULL != ret); + memcpy (&rs->addr, + sa, + sa_len); + rs->addrlen = sa_len; + rs->rc = rc; + rs->rc_cls = rc_cls; + if (GNUNET_SYSERR == + GNUNET_NETWORK_socket_sendto (ret, + request, + request_len, + sa, + sa_len)) + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + _("Failed to send DNS request to %s\n"), + GNUNET_a2s (sa, sa_len)); + else + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + _("Sent DNS request to %s\n"), + GNUNET_a2s (sa, sa_len)); + return rs; +} + + +/** + * Perform DNS resolution using our default IP from init. + * + * @param ctx stub resolver to use + * @param request DNS request to transmit + * @param request_len number of bytes in msg + * @param rc function to call with result + * @param rc_cls closure for 'rc' + * @return socket used for the request, NULL on error + */ +struct GNUNET_DNSSTUB_RequestSocket * +GNUNET_DNSSTUB_resolve2 (struct GNUNET_DNSSTUB_Context *ctx, + const void *request, + size_t request_len, + GNUNET_DNSSTUB_ResultCallback rc, + void *rc_cls) +{ + int af; + struct sockaddr_in v4; + struct sockaddr_in6 v6; + struct sockaddr *sa; + socklen_t salen; + struct GNUNET_NETWORK_Handle *dnsout; + struct GNUNET_DNSSTUB_RequestSocket *rs; + + memset (&v4, 0, sizeof (v4)); + memset (&v6, 0, sizeof (v6)); + if (1 == inet_pton (AF_INET, ctx->dns_exit, &v4.sin_addr)) + { + salen = sizeof (v4); + v4.sin_family = AF_INET; + v4.sin_port = htons (53); +#if HAVE_SOCKADDR_IN_SIN_LEN + v4.sin_len = (u_char) salen; +#endif + sa = (struct sockaddr *) &v4; + af = AF_INET; + } + else if (1 == inet_pton (AF_INET6, ctx->dns_exit, &v6.sin6_addr)) + { + salen = sizeof (v6); + v6.sin6_family = AF_INET6; + v6.sin6_port = htons (53); +#if HAVE_SOCKADDR_IN_SIN_LEN + v6.sin6_len = (u_char) salen; +#endif + sa = (struct sockaddr *) &v6; + af = AF_INET6; + } + else + { + GNUNET_break (0); + return NULL; + } + if (NULL == (rs = get_request_socket (ctx, af))) + return NULL; + if (NULL != rs->dnsout4) + dnsout = rs->dnsout4; + else + dnsout = rs->dnsout6; + if (NULL == dnsout) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Configured DNS exit `%s' is not working / valid.\n"), + ctx->dns_exit); + return NULL; + } + memcpy (&rs->addr, + sa, + salen); + rs->addrlen = salen; + rs->rc = rc; + rs->rc_cls = rc_cls; + if (GNUNET_SYSERR == + GNUNET_NETWORK_socket_sendto (dnsout, + request, + request_len, sa, salen)) + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + _("Failed to send DNS request to %s\n"), + GNUNET_a2s (sa, salen)); + rs->timeout = GNUNET_TIME_relative_to_absolute (REQUEST_TIMEOUT); + + return rs; + +} + + +/** + * Actually do the reading of a DNS packet from our UDP socket and see + * if we have a valid, matching, pending request. + * + * @param rs request socket with callback details + * @param dnsout socket to read from + * @return GNUNET_OK on success, GNUNET_NO on drop, GNUNET_SYSERR on IO-errors (closed socket) + */ +static int +do_dns_read (struct GNUNET_DNSSTUB_RequestSocket *rs, + struct GNUNET_NETWORK_Handle *dnsout) +{ + struct sockaddr_storage addr; + socklen_t addrlen; + struct GNUNET_TUN_DnsHeader *dns; + ssize_t r; + int len; + +#ifndef MINGW + if (0 != ioctl (GNUNET_NETWORK_get_fd (dnsout), FIONREAD, &len)) + { + /* conservative choice: */ + len = UINT16_MAX; + } +#else + /* port the code above? */ + len = UINT16_MAX; +#endif + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Receiving %d byte DNS reply\n", + len); + { + unsigned char buf[len] GNUNET_ALIGN; + + addrlen = sizeof (addr); + memset (&addr, 0, sizeof (addr)); + r = GNUNET_NETWORK_socket_recvfrom (dnsout, + buf, sizeof (buf), + (struct sockaddr*) &addr, &addrlen); + if (-1 == r) + { + GNUNET_log_strerror (GNUNET_ERROR_TYPE_ERROR, "recvfrom"); + GNUNET_NETWORK_socket_close (dnsout); + return GNUNET_SYSERR; + } + if (sizeof (struct GNUNET_TUN_DnsHeader) > r) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Received DNS response that is too small (%u bytes)"), + r); + return GNUNET_NO; + } + dns = (struct GNUNET_TUN_DnsHeader *) buf; + if ( (addrlen != rs->addrlen) || + (0 != memcmp (&rs->addr, + &addr, + addrlen)) || + (0 == GNUNET_TIME_absolute_get_remaining (rs->timeout).rel_value) ) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Request timeout or invalid sender address; ignoring reply\n"); + return GNUNET_NO; + } + if (NULL != rs->rc) + rs->rc (rs->rc_cls, + rs, + dns, + r); + } + return GNUNET_OK; +} + + +/** + * Read a DNS response from the (unhindered) UDP-Socket + * + * @param cls socket to read from + * @param tc scheduler context (must be shutdown or read ready) + */ +static void +read_response (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct GNUNET_DNSSTUB_RequestSocket *rs = cls; + struct GNUNET_NETWORK_FDSet *rset; + + rs->read_task = GNUNET_SCHEDULER_NO_TASK; + if (0 == (tc->reason & GNUNET_SCHEDULER_REASON_READ_READY)) + { + /* timeout or shutdown */ + cleanup_rs (rs); + return; + } + /* read and process ready sockets */ + if ((NULL != rs->dnsout4) && + (GNUNET_NETWORK_fdset_isset (tc->read_ready, rs->dnsout4)) && + (GNUNET_SYSERR == do_dns_read (rs, rs->dnsout4))) + rs->dnsout4 = NULL; + if ((NULL != rs->dnsout6) && + (GNUNET_NETWORK_fdset_isset (tc->read_ready, rs->dnsout6)) && + (GNUNET_SYSERR == do_dns_read (rs, rs->dnsout6))) + rs->dnsout6 = NULL; + + /* re-schedule read task */ + rset = GNUNET_NETWORK_fdset_create (); + if (NULL != rs->dnsout4) + GNUNET_NETWORK_fdset_set (rset, rs->dnsout4); + if (NULL != rs->dnsout6) + GNUNET_NETWORK_fdset_set (rset, rs->dnsout6); + rs->read_task = GNUNET_SCHEDULER_add_select (GNUNET_SCHEDULER_PRIORITY_DEFAULT, + GNUNET_TIME_absolute_get_remaining (rs->timeout), + rset, + NULL, + &read_response, rs); + GNUNET_NETWORK_fdset_destroy (rset); +} + + +/** + * Cancel DNS resolution. + * + * @param rs resolution to cancel + */ +void +GNUNET_DNSSTUB_resolve_cancel (struct GNUNET_DNSSTUB_RequestSocket *rs) +{ + rs->rc = NULL; +} + + +/** + * Start a DNS stub resolver. + * + * @param dns_ip target IP address to use + * @return NULL on error + */ +struct GNUNET_DNSSTUB_Context * +GNUNET_DNSSTUB_start (const char *dns_ip) +{ + struct GNUNET_DNSSTUB_Context *ctx; + + ctx = GNUNET_malloc (sizeof (struct GNUNET_DNSSTUB_Context)); + if (NULL != dns_ip) + ctx->dns_exit = GNUNET_strdup (dns_ip); + return ctx; +} + + +/** + * Cleanup DNSSTUB resolver. + * + * @param ctx stub resolver to clean up + */ +void +GNUNET_DNSSTUB_stop (struct GNUNET_DNSSTUB_Context *ctx) +{ + unsigned int i; + + for (i=0;isockets[i]); + if (NULL != ctx->dns_exit) + { + GNUNET_free (ctx->dns_exit); + ctx->dns_exit = NULL; + } + GNUNET_free (ctx); +} + + +/* end of dnsstub.c */ diff --git a/src/dns/gnunet-dns-monitor.c b/src/dns/gnunet-dns-monitor.c index 82715aa..747a875 100644 --- a/src/dns/gnunet-dns-monitor.c +++ b/src/dns/gnunet-dns-monitor.c @@ -75,6 +75,7 @@ get_type (uint16_t type) case GNUNET_DNSPARSER_TYPE_MX: return "MX"; case GNUNET_DNSPARSER_TYPE_TXT: return "TXT"; case GNUNET_DNSPARSER_TYPE_AAAA: return "AAAA"; + case GNUNET_DNSPARSER_TYPE_SRV: return "SRV"; } GNUNET_snprintf (buf, sizeof (buf), "%u", (unsigned int) type); return buf; @@ -151,7 +152,7 @@ display_record (const struct GNUNET_DNSPARSER_Record *record) format = record->data.hostname; break; case GNUNET_DNSPARSER_TYPE_SOA: - if (record->data.soa == NULL) + if (NULL == record->data.soa) format = ""; else { @@ -179,6 +180,23 @@ display_record (const struct GNUNET_DNSPARSER_Record *record) format = tmp; } break; + case GNUNET_DNSPARSER_TYPE_SRV: + if (NULL == record->data.srv) + format = ""; + else + { + GNUNET_asprintf (&tmp, + "service: %s, protocol: %s, domain_name = %s, priority %u, weight = %s, port = %u, target = %s", + record->data.srv->service, + record->data.srv->proto, + record->data.srv->domain_name, + (unsigned int) record->data.srv->priority, + (unsigned int) record->data.srv->weight, + (unsigned int) record->data.srv->port, + record->data.srv->target); + format = tmp; + } + break; case GNUNET_DNSPARSER_TYPE_TXT: GNUNET_asprintf (&tmp, "%.*s", @@ -342,11 +360,16 @@ main (int argc, char *const *argv) GNUNET_GETOPT_OPTION_VERBOSE (&verbosity), GNUNET_GETOPT_OPTION_END }; - return (GNUNET_OK == - GNUNET_PROGRAM_run (argc, argv, "gnunet-dns-monitor", - gettext_noop - ("Monitor DNS queries."), options, - &run, NULL)) ? ret : 1; + + if (GNUNET_OK != GNUNET_STRINGS_get_utf8_args (argc, argv, &argc, &argv)) + return 2; + ret = (GNUNET_OK == + GNUNET_PROGRAM_run (argc, argv, "gnunet-dns-monitor", + gettext_noop + ("Monitor DNS queries."), options, + &run, NULL)) ? ret : 1; + GNUNET_free ((void*) argv); + return ret; } diff --git a/src/dns/gnunet-dns-redirector.c b/src/dns/gnunet-dns-redirector.c index a45b896..3df2ac2 100644 --- a/src/dns/gnunet-dns-redirector.c +++ b/src/dns/gnunet-dns-redirector.c @@ -241,11 +241,17 @@ main (int argc, char *const *argv) GNUNET_GETOPT_OPTION_VERBOSE (&verbosity), GNUNET_GETOPT_OPTION_END }; - return (GNUNET_OK == - GNUNET_PROGRAM_run (argc, argv, "gnunet-dns-redirector", - gettext_noop - ("Change DNS replies to point elsewhere."), options, - &run, NULL)) ? ret : 1; + + if (GNUNET_OK != GNUNET_STRINGS_get_utf8_args (argc, argv, &argc, &argv)) + return 2; + + ret = (GNUNET_OK == + GNUNET_PROGRAM_run (argc, argv, "gnunet-dns-redirector", + gettext_noop + ("Change DNS replies to point elsewhere."), options, + &run, NULL)) ? ret : 1; + GNUNET_free ((void*) argv); + return ret; } diff --git a/src/dns/gnunet-helper-dns.c b/src/dns/gnunet-helper-dns.c index dfeb45a..c230ec5 100644 --- a/src/dns/gnunet-helper-dns.c +++ b/src/dns/gnunet-helper-dns.c @@ -99,6 +99,11 @@ struct in6_ifreq */ static const char *sbin_iptables; +/** + * Name and full path of sysctl binary + */ +static const char *sbin_sysctl; + /** * Name and full path of IPTABLES binary. */ @@ -149,6 +154,33 @@ signal_handler (int signal) } +/** + * Open '/dev/null' and make the result the given + * file descriptor. + * + * @param target_fd desired FD to point to /dev/null + * @param flags open flags (O_RDONLY, O_WRONLY) + */ +static void +open_dev_null (int target_fd, + int flags) +{ + int fd; + + fd = open ("/dev/null", flags); + if (-1 == fd) + abort (); + if (fd == target_fd) + return; + if (-1 == dup2 (fd, target_fd)) + { + (void) close (fd); + abort (); + } + (void) close (fd); +} + + /** * Run the given command and wait for it to complete. * @@ -178,7 +210,9 @@ fork_and_exec (const char *file, /* close stdin/stdout to not cause interference with the helper's main protocol! */ (void) close (0); + open_dev_null (0, O_RDONLY); (void) close (1); + open_dev_null (1, O_WRONLY); (void) execv (file, cmd); /* can only get here on error */ fprintf (stderr, @@ -492,7 +526,7 @@ run (int fd_tun) * We are supposed to read and the buffer is not empty * -> select on write to stdout */ - if (0 != buftun_size) + if (0 < buftun_size) FD_SET (1, &fds_w); /* @@ -536,7 +570,10 @@ run (int fd_tun) { if ( (errno == EINTR) || (errno == EAGAIN) ) - continue; + { + buftun_size = 0; + continue; + } fprintf (stderr, "read-error: %s\n", strerror (errno)); return; } @@ -675,6 +712,7 @@ PROCESS_BUFFER: * 25-39 failed to drop privs and then failed to undo some changes to routing table * 40 failed to regain privs * 41-55 failed to regain prisv and then failed to undo some changes to routing table + * 254 insufficient priviledges * 255 failed to handle kill signal properly */ int @@ -684,6 +722,7 @@ main (int argc, char *const*argv) char dev[IFNAMSIZ]; char mygid[32]; int fd_tun; + uid_t uid; if (6 != argc) { @@ -691,6 +730,22 @@ main (int argc, char *const*argv) return 1; } + /* assert privs so we can modify the firewall rules! */ + uid = getuid (); +#ifdef HAVE_SETRESUID + if (0 != setresuid (uid, 0, 0)) + { + fprintf (stderr, "Failed to setresuid to root: %s\n", strerror (errno)); + return 254; + } +#else + if (0 != seteuid (0)) + { + fprintf (stderr, "Failed to seteuid back to root: %s\n", strerror (errno)); + return 254; + } +#endif + /* verify that the binaries were care about are executable */ if (0 == access ("/sbin/iptables", X_OK)) sbin_iptables = "/sbin/iptables"; @@ -714,6 +769,17 @@ main (int argc, char *const*argv) strerror (errno)); return 4; } + if (0 == access ("/sbin/sysctl", X_OK)) + sbin_sysctl = "/sbin/sysctl"; + else if (0 == access ("/usr/sbin/sysctl", X_OK)) + sbin_sysctl = "/usr/sbin/sysctl"; + else + { + fprintf (stderr, + "Fatal: executable sysctl not found in approved directories: %s\n", + strerror (errno)); + return 5; + } /* setup 'mygid' string */ snprintf (mygid, sizeof (mygid), "%d", (int) getegid()); @@ -778,6 +844,22 @@ main (int argc, char *const*argv) strncpy (dev, argv[1], IFNAMSIZ); dev[IFNAMSIZ - 1] = '\0'; + /* Disable rp filtering */ + { + char *const sysctl_args[] = {"sysctl", "-w", + "net.ipv4.conf.all.rp_filter=0", NULL}; + char *const sysctl_args2[] = {"sysctl", "-w", + "net.ipv4.conf.default.rp_filter=0", NULL}; + if ((0 != fork_and_exec (sbin_sysctl, sysctl_args)) || + (0 != fork_and_exec (sbin_sysctl, sysctl_args2))) + { + fprintf (stderr, + "Failed to disable rp filtering.\n"); + return 5; + } + } + + /* now open virtual interface (first part that requires root) */ if (-1 == (fd_tun = init_tun (dev))) { @@ -814,6 +896,7 @@ main (int argc, char *const*argv) set_address4 (dev, address, mask); } + /* update routing tables -- next part why we need SUID! */ /* Forward everything from our EGID (which should only be held @@ -863,7 +946,6 @@ main (int argc, char *const*argv) /* drop privs *except* for the saved UID; this is not perfect, but better than doing nothing */ - uid_t uid = getuid (); #ifdef HAVE_SETRESUID if (0 != setresuid (uid, uid, 0)) { diff --git a/src/dns/gnunet-service-dns.c b/src/dns/gnunet-service-dns.c index 6337538..d1689f4 100644 --- a/src/dns/gnunet-service-dns.c +++ b/src/dns/gnunet-service-dns.c @@ -45,21 +45,22 @@ #include "dns.h" #include "gnunet_dns_service.h" #include "gnunet_dnsparser_lib.h" -#include "gnunet_mesh_service.h" +#include "gnunet_dnsstub_lib.h" #include "gnunet_statistics_service.h" #include "gnunet_tun_lib.h" - /** - * Timeout for an external (Internet-DNS) DNS resolution + * Port number for DNS */ -#define REQUEST_TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 5) +#define DNS_PORT 53 + /** - * How many DNS sockets do we open at most at the same time? - * (technical socket maximum is this number x2 for IPv4+IPv6) + * Generic logging shorthand */ -#define DNS_SOCKET_MAX 128 +#define LOG(kind, ...) \ + GNUNET_log_from (kind, "dns", __VA_ARGS__); + /** * Phases each request goes through. @@ -136,34 +137,6 @@ struct ClientRecord }; -/** - * UDP socket we are using for sending DNS requests to the Internet. - */ -struct RequestSocket -{ - - /** - * UDP socket we use for this request for IPv4 - */ - struct GNUNET_NETWORK_Handle *dnsout4; - - /** - * UDP socket we use for this request for IPv6 - */ - struct GNUNET_NETWORK_Handle *dnsout6; - - /** - * Task for reading from dnsout4 and dnsout6. - */ - GNUNET_SCHEDULER_TaskIdentifier read_task; - - /** - * When should this socket be closed? - */ - struct GNUNET_TIME_Absolute timeout; -}; - - /** * Entry we keep for each active request. */ @@ -184,10 +157,9 @@ struct RequestRecord /** * Socket we are using to transmit this request (must match if we receive - * a response). Must NOT be freed as part of this request record (as it - * might be shared with other requests). + * a response). */ - struct GNUNET_NETWORK_Handle *dnsout; + struct GNUNET_DNSSTUB_RequestSocket *rs; /** * Source address of the original request (for sending response). @@ -199,11 +171,6 @@ struct RequestRecord */ struct sockaddr_storage dst_addr; - /** - * When should this request time out? - */ - struct GNUNET_TIME_Absolute timeout; - /** * ID of this request, also basis for hashing. Lowest 16 bit will * be our message ID when doing a global DNS request and our index @@ -229,66 +196,6 @@ struct RequestRecord }; -/** - * State we keep for each DNS tunnel that terminates at this node. - */ -struct TunnelState -{ - - /** - * Associated MESH tunnel. - */ - struct GNUNET_MESH_Tunnel *tunnel; - - /** - * Active request for sending a reply. - */ - struct GNUNET_MESH_TransmitHandle *th; - - /** - * DNS reply ready for transmission. - */ - char *reply; - - /** - * Socket we are using to transmit this request (must match if we receive - * a response). Must NOT be freed as part of this request record (as it - * might be shared with other requests). - */ - struct GNUNET_NETWORK_Handle *dnsout; - - /** - * Address we sent the DNS request to. - */ - struct sockaddr_storage addr; - - /** - * When should this request time out? - */ - struct GNUNET_TIME_Absolute timeout; - - /** - * Number of bytes in 'addr'. - */ - socklen_t addrlen; - - /** - * Number of bytes in 'reply'. - */ - size_t reply_length; - - /** - * Original DNS request ID as used by the client. - */ - uint16_t original_id; - - /** - * DNS request ID that we used for forwarding. - */ - uint16_t my_id; -}; - - /** * Global return value from 'main'. */ @@ -334,58 +241,15 @@ static struct GNUNET_SERVER_NotificationContext *nc; */ static struct RequestRecord requests[UINT16_MAX + 1]; -/** - * Array of all open requests from tunnels. - */ -static struct TunnelState *tunnels[UINT16_MAX + 1]; - -/** - * Array of all open sockets for DNS requests. - */ -static struct RequestSocket sockets[DNS_SOCKET_MAX]; - /** * Generator for unique request IDs. */ static uint64_t request_id_gen; /** - * IP address to use for the DNS server if we are a DNS exit service - * (for VPN via mesh); otherwise NULL. - */ -static char *dns_exit; - -/** - * Handle to the MESH service (for receiving DNS queries), or NULL - * if we are not a DNS exit. - */ -static struct GNUNET_MESH_Handle *mesh; - - -/** - * We're done with a RequestSocket, close it for now. - * - * @param rs request socket to clean up + * Handle to the DNS Stub resolver. */ -static void -cleanup_rs (struct RequestSocket *rs) -{ - if (NULL != rs->dnsout4) - { - GNUNET_NETWORK_socket_close (rs->dnsout4); - rs->dnsout4 = NULL; - } - if (NULL != rs->dnsout6) - { - GNUNET_NETWORK_socket_close (rs->dnsout6); - rs->dnsout6 = NULL; - } - if (GNUNET_SCHEDULER_NO_TASK != rs->read_task) - { - GNUNET_SCHEDULER_cancel (rs->read_task); - rs->read_task = GNUNET_SCHEDULER_NO_TASK; - } -} +static struct GNUNET_DNSSTUB_Context *dnsstub; /** @@ -430,64 +294,11 @@ cleanup_task (void *cls GNUNET_UNUSED, GNUNET_STATISTICS_destroy (stats, GNUNET_NO); stats = NULL; } - if (NULL != dns_exit) - { - GNUNET_free (dns_exit); - dns_exit = NULL; - } - if (NULL != mesh) - { - GNUNET_MESH_disconnect(mesh); - mesh = NULL; - } -} - - -/** - * Open source port for sending DNS requests - * - * @param af AF_INET or AF_INET6 - * @return GNUNET_OK on success - */ -static struct GNUNET_NETWORK_Handle * -open_socket (int af) -{ - struct sockaddr_in a4; - struct sockaddr_in6 a6; - struct sockaddr *sa; - socklen_t alen; - struct GNUNET_NETWORK_Handle *ret; - - ret = GNUNET_NETWORK_socket_create (af, SOCK_DGRAM, 0); - if (NULL == ret) - return NULL; - switch (af) - { - case AF_INET: - memset (&a4, 0, alen = sizeof (struct sockaddr_in)); - sa = (struct sockaddr *) &a4; - break; - case AF_INET6: - memset (&a6, 0, alen = sizeof (struct sockaddr_in6)); - sa = (struct sockaddr *) &a6; - break; - default: - GNUNET_break (0); - GNUNET_NETWORK_socket_close (ret); - return NULL; - } - sa->sa_family = af; - if (GNUNET_OK != GNUNET_NETWORK_socket_bind (ret, - sa, - alen)) + if (NULL != dnsstub) { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - _("Could not bind to any port: %s\n"), - STRERROR (errno)); - GNUNET_NETWORK_socket_close (ret); - return NULL; + GNUNET_DNSSTUB_stop (dnsstub); + dnsstub = NULL; } - return ret; } @@ -510,10 +321,16 @@ request_done (struct RequestRecord *rr) if (RP_RESPONSE_MONITOR != rr->phase) { /* no response, drop */ + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Got no response for request %llu, dropping\n", + (unsigned long long) rr->request_id); cleanup_rr (rr); return; } - + + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Transmitting response for request %llu\n", + (unsigned long long) rr->request_id); /* send response via hijacker */ reply_len = sizeof (struct GNUNET_MessageHeader); reply_len += sizeof (struct GNUNET_TUN_Layer2PacketHeader); @@ -664,6 +481,9 @@ send_request_to_client (struct RequestRecord *rr, cleanup_rr (rr); return; } + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Sending information about request %llu to local client\n", + (unsigned long long) rr->request_id); req = (struct GNUNET_DNS_Request*) buf; req->header.type = htons (GNUNET_MESSAGE_TYPE_DNS_CLIENT_REQUEST); req->header.size = htons (sizeof (buf)); @@ -677,70 +497,21 @@ send_request_to_client (struct RequestRecord *rr, } -/** - * Read a DNS response from the (unhindered) UDP-Socket - * - * @param cls socket to read from - * @param tc scheduler context (must be shutdown or read ready) - */ -static void -read_response (void *cls, - const struct GNUNET_SCHEDULER_TaskContext *tc); - /** - * Get a socket of the specified address family to send out a - * UDP DNS request to the Internet. + * Callback called from DNSSTUB resolver when a resolution + * succeeded. * - * @param af desired address family - * @return NULL on error (given AF not "supported") + * @param cls NULL + * @param rs the socket that received the response + * @param dns the response itself + * @param r number of bytes in dns */ -static struct GNUNET_NETWORK_Handle * -get_request_socket (int af) -{ - struct RequestSocket *rs; - struct GNUNET_NETWORK_FDSet *rset; - static struct GNUNET_NETWORK_Handle *ret; - - rs = &sockets[GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_NONCE, - DNS_SOCKET_MAX)]; - rs->timeout = GNUNET_TIME_relative_to_absolute (REQUEST_TIMEOUT); - switch (af) - { - case AF_INET: - if (NULL == rs->dnsout4) - rs->dnsout4 = open_socket (AF_INET); - ret = rs->dnsout4; - break; - case AF_INET6: - if (NULL == rs->dnsout6) - rs->dnsout6 = open_socket (AF_INET6); - ret = rs->dnsout6; - break; - default: - return NULL; - } - if (GNUNET_SCHEDULER_NO_TASK != rs->read_task) - { - GNUNET_SCHEDULER_cancel (rs->read_task); - rs->read_task = GNUNET_SCHEDULER_NO_TASK; - } - if ( (NULL == rs->dnsout4) && - (NULL == rs->dnsout6) ) - return NULL; - rset = GNUNET_NETWORK_fdset_create (); - if (NULL != rs->dnsout4) - GNUNET_NETWORK_fdset_set (rset, rs->dnsout4); - if (NULL != rs->dnsout6) - GNUNET_NETWORK_fdset_set (rset, rs->dnsout6); - rs->read_task = GNUNET_SCHEDULER_add_select (GNUNET_SCHEDULER_PRIORITY_DEFAULT, - REQUEST_TIMEOUT, - rset, - NULL, - &read_response, rs); - GNUNET_NETWORK_fdset_destroy (rset); - return ret; -} +static void +process_dns_result (void *cls, + struct GNUNET_DNSSTUB_RequestSocket *rs, + const struct GNUNET_TUN_DnsHeader *dns, + size_t r); /** @@ -777,6 +548,10 @@ next_phase (struct RequestRecord *rr) return; } /* done with current phase, advance! */ + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Request %llu now in phase %d\n", + rr->request_id, + rr->phase); switch (rr->phase) { case RP_INIT: @@ -815,8 +590,14 @@ next_phase (struct RequestRecord *rr) } rr->phase = RP_INTERNET_DNS; - rr->dnsout = get_request_socket (rr->dst_addr.ss_family); - if (NULL == rr->dnsout) + rr->rs = GNUNET_DNSSTUB_resolve (dnsstub, + (struct sockaddr*) &rr->dst_addr, + salen, + rr->payload, + rr->payload_length, + &process_dns_result, + NULL); + if (NULL == rr->rs) { GNUNET_STATISTICS_update (stats, gettext_noop ("# DNS exit failed (failed to open socket)"), @@ -824,12 +605,6 @@ next_phase (struct RequestRecord *rr) cleanup_rr (rr); return; } - GNUNET_NETWORK_socket_sendto (rr->dnsout, - rr->payload, - rr->payload_length, - (struct sockaddr*) &rr->dst_addr, - salen); - rr->timeout = GNUNET_TIME_relative_to_absolute (REQUEST_TIMEOUT); return; case RP_INTERNET_DNS: rr->phase = RP_MODIFY; @@ -911,199 +686,45 @@ client_disconnect (void *cls, struct GNUNET_SERVER_Client *client) /** - * We got a reply from DNS for a request of a MESH tunnel. Send it - * via the tunnel (after changing the request ID back). + * Callback called from DNSSTUB resolver when a resolution + * succeeded. * - * @param cls the 'struct TunnelState' - * @param size number of bytes available in buf - * @param buf where to copy the reply - * @return number of bytes written to buf - */ -static size_t -transmit_reply_to_mesh (void *cls, - size_t size, - void *buf) -{ - struct TunnelState *ts = cls; - size_t off; - size_t ret; - char *cbuf = buf; - struct GNUNET_MessageHeader hdr; - struct GNUNET_TUN_DnsHeader dns; - - ts->th = NULL; - GNUNET_assert (ts->reply != NULL); - if (size == 0) - return 0; - ret = sizeof (struct GNUNET_MessageHeader) + ts->reply_length; - GNUNET_assert (ret <= size); - hdr.size = htons (ret); - hdr.type = htons (GNUNET_MESSAGE_TYPE_VPN_DNS_FROM_INTERNET); - memcpy (&dns, ts->reply, sizeof (dns)); - dns.id = ts->original_id; - off = 0; - memcpy (&cbuf[off], &hdr, sizeof (hdr)); - off += sizeof (hdr); - memcpy (&cbuf[off], &dns, sizeof (dns)); - off += sizeof (dns); - memcpy (&cbuf[off], &ts->reply[sizeof (dns)], ts->reply_length - sizeof (dns)); - off += ts->reply_length - sizeof (dns); - GNUNET_free (ts->reply); - ts->reply = NULL; - ts->reply_length = 0; - GNUNET_assert (ret == off); - return ret; -} - - -/** - * Actually do the reading of a DNS packet from our UDP socket and see - * if we have a valid, matching, pending request. - * - * @param dnsout socket to read from - * @return GNUNET_OK on success, GNUNET_NO on drop, GNUNET_SYSERR on IO-errors (closed socket) - */ -static int -do_dns_read (struct GNUNET_NETWORK_Handle *dnsout) -{ - struct sockaddr_storage addr; - socklen_t addrlen; - struct GNUNET_TUN_DnsHeader *dns; - struct RequestRecord *rr; - struct TunnelState *ts; - ssize_t r; - int len; - -#ifndef MINGW - if (0 != ioctl (GNUNET_NETWORK_get_fd (dnsout), FIONREAD, &len)) - { - /* conservative choice: */ - len = UINT16_MAX; - } -#else - /* port the code above? */ - len = UINT16_MAX; -#endif - - { - unsigned char buf[len] GNUNET_ALIGN; - - addrlen = sizeof (addr); - memset (&addr, 0, sizeof (addr)); - r = GNUNET_NETWORK_socket_recvfrom (dnsout, - buf, sizeof (buf), - (struct sockaddr*) &addr, &addrlen); - if (-1 == r) - { - GNUNET_log_strerror (GNUNET_ERROR_TYPE_ERROR, "recvfrom"); - GNUNET_NETWORK_socket_close (dnsout); - return GNUNET_SYSERR; - } - if (sizeof (struct GNUNET_TUN_DnsHeader) > r) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - _("Received DNS response that is too small (%u bytes)"), - r); - return GNUNET_NO; - } - dns = (struct GNUNET_TUN_DnsHeader *) buf; - /* Handle case that this is a reply to a request from a MESH DNS tunnel */ - ts = tunnels[dns->id]; - if ( (NULL == ts) || - (ts->dnsout != dnsout) || - (addrlen != ts->addrlen) || - (0 != memcmp (&ts->addr, - &addr, - addrlen)) || - (0 == GNUNET_TIME_absolute_get_remaining (ts->timeout).rel_value) ) - ts = NULL; /* DNS responder address missmatch */ - if (NULL != ts) - { - tunnels[dns->id] = NULL; - GNUNET_free_non_null (ts->reply); - ts->reply = GNUNET_malloc (r); - ts->reply_length = r; - memcpy (ts->reply, dns, r); - if (ts->th != NULL) - GNUNET_MESH_notify_transmit_ready_cancel (ts->th); - ts->th = GNUNET_MESH_notify_transmit_ready (ts->tunnel, - GNUNET_NO, 0, - GNUNET_TIME_UNIT_FOREVER_REL, - NULL, - sizeof (struct GNUNET_MessageHeader) + r, - &transmit_reply_to_mesh, - ts); - } - /* Handle case that this is a reply to a local request (intercepted from TUN interface) */ - rr = &requests[dns->id]; - if ( (rr->phase != RP_INTERNET_DNS) || - (rr->dnsout != dnsout) || - (0 != memcmp (&rr->dst_addr, - &addr, - addrlen)) || - (0 == GNUNET_TIME_absolute_get_remaining (rr->timeout).rel_value) ) - { - if (NULL == ts) - { - /* unexpected / bogus reply */ - GNUNET_STATISTICS_update (stats, - gettext_noop ("# External DNS response discarded (no matching request)"), - 1, GNUNET_NO); - } - return GNUNET_NO; - } - GNUNET_free_non_null (rr->payload); - rr->payload = GNUNET_malloc (r); - memcpy (rr->payload, buf, r); - rr->payload_length = r; - next_phase (rr); - } - return GNUNET_OK; -} - - -/** - * Read a DNS response from the (unhindered) UDP-Socket - * - * @param cls socket to read from - * @param tc scheduler context (must be shutdown or read ready) + * @param cls NULL + * @param rs the socket that received the response + * @param dns the response itself + * @param r number of bytes in dns */ static void -read_response (void *cls, - const struct GNUNET_SCHEDULER_TaskContext *tc) +process_dns_result (void *cls, + struct GNUNET_DNSSTUB_RequestSocket *rs, + const struct GNUNET_TUN_DnsHeader *dns, + size_t r) { - struct RequestSocket *rs = cls; - struct GNUNET_NETWORK_FDSet *rset; + struct RequestRecord *rr; - rs->read_task = GNUNET_SCHEDULER_NO_TASK; - if (0 == (tc->reason & GNUNET_SCHEDULER_REASON_READ_READY)) + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Processing DNS result from stub resolver\n"); + GNUNET_assert (NULL == cls); + rr = &requests[dns->id]; + if ( (rr->phase != RP_INTERNET_DNS) || + (rr->rs != rs) ) { - /* timeout or shutdown */ - cleanup_rs (rs); - return; + /* unexpected / bogus reply */ + GNUNET_STATISTICS_update (stats, + gettext_noop ("# External DNS response discarded (no matching request)"), + 1, GNUNET_NO); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Received DNS reply that does not match any pending request. Dropping.\n"); + return; } - /* read and process ready sockets */ - if ((NULL != rs->dnsout4) && - (GNUNET_NETWORK_fdset_isset (tc->read_ready, rs->dnsout4)) && - (GNUNET_SYSERR == do_dns_read (rs->dnsout4))) - rs->dnsout4 = NULL; - if ((NULL != rs->dnsout6) && - (GNUNET_NETWORK_fdset_isset (tc->read_ready, rs->dnsout6)) && - (GNUNET_SYSERR == do_dns_read (rs->dnsout6))) - rs->dnsout6 = NULL; - - /* re-schedule read task */ - rset = GNUNET_NETWORK_fdset_create (); - if (NULL != rs->dnsout4) - GNUNET_NETWORK_fdset_set (rset, rs->dnsout4); - if (NULL != rs->dnsout6) - GNUNET_NETWORK_fdset_set (rset, rs->dnsout6); - rs->read_task = GNUNET_SCHEDULER_add_select (GNUNET_SCHEDULER_PRIORITY_DEFAULT, - GNUNET_TIME_absolute_get_remaining (rs->timeout), - rset, - NULL, - &read_response, rs); - GNUNET_NETWORK_fdset_destroy (rset); + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Got a response from the stub resolver for DNS request %llu intercepted locally!\n", + (unsigned long long) rr->request_id); + GNUNET_free_non_null (rr->payload); + rr->payload = GNUNET_malloc (r); + memcpy (rr->payload, dns, r); + rr->payload_length = r; + next_phase (rr); } @@ -1162,6 +783,9 @@ handle_client_response (void *cls GNUNET_UNUSED, resp = (const struct GNUNET_DNS_Response*) message; off = (uint16_t) resp->request_id; rr = &requests[off]; + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Received DNS response with ID %llu from local client!\n", + (unsigned long long) resp->request_id); if (rr->request_id != resp->request_id) { GNUNET_STATISTICS_update (stats, @@ -1255,6 +879,8 @@ process_helper_messages (void *cls GNUNET_UNUSED, void *client, struct sockaddr_in *dsta4; struct sockaddr_in6 *dsta6; + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Intercepted message via DNS hijacker\n"); msize = ntohs (message->size); if (msize < sizeof (struct GNUNET_MessageHeader) + sizeof (struct GNUNET_TUN_Layer2PacketHeader) + sizeof (struct GNUNET_TUN_IPv4Header)) { @@ -1308,7 +934,8 @@ process_helper_messages (void *cls GNUNET_UNUSED, void *client, ntohs (tun->proto)); return GNUNET_OK; } - if (msize <= sizeof (struct GNUNET_TUN_UdpHeader) + sizeof (struct GNUNET_TUN_DnsHeader)) + if ( (msize <= sizeof (struct GNUNET_TUN_UdpHeader) + sizeof (struct GNUNET_TUN_DnsHeader)) || + (DNS_PORT != ntohs (udp->destination_port)) ) { /* non-DNS packet received on TUN, ignore */ GNUNET_STATISTICS_update (stats, @@ -1375,7 +1002,9 @@ process_helper_messages (void *cls GNUNET_UNUSED, void *client, memcpy (rr->payload, dns, msize); rr->request_id = dns->id | (request_id_gen << 16); request_id_gen++; - + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Creating new DNS request %llu\n", + (unsigned long long) rr->request_id); GNUNET_STATISTICS_update (stats, gettext_noop ("# DNS requests received via TUN interface"), 1, GNUNET_NO); @@ -1385,150 +1014,6 @@ process_helper_messages (void *cls GNUNET_UNUSED, void *client, } -/** - * Process a request via mesh to perform a DNS query. - * - * @param cls closure, NULL - * @param tunnel connection to the other end - * @param tunnel_ctx pointer to our 'struct TunnelState *' - * @param sender who sent the message - * @param message the actual message - * @param atsi performance data for the connection - * @return GNUNET_OK to keep the connection open, - * GNUNET_SYSERR to close it (signal serious error) - */ -static int -receive_dns_request (void *cls GNUNET_UNUSED, struct GNUNET_MESH_Tunnel *tunnel, - void **tunnel_ctx, - const struct GNUNET_PeerIdentity *sender GNUNET_UNUSED, - const struct GNUNET_MessageHeader *message, - const struct GNUNET_ATS_Information *atsi GNUNET_UNUSED) -{ - struct TunnelState *ts = *tunnel_ctx; - const struct GNUNET_TUN_DnsHeader *dns; - size_t mlen = ntohs (message->size); - size_t dlen = mlen - sizeof (struct GNUNET_MessageHeader); - char buf[dlen] GNUNET_ALIGN; - struct GNUNET_TUN_DnsHeader *dout; - struct sockaddr_in v4; - struct sockaddr_in6 v6; - struct sockaddr *so; - socklen_t salen; - - if (dlen < sizeof (struct GNUNET_TUN_DnsHeader)) - { - GNUNET_break_op (0); - return GNUNET_SYSERR; - } - dns = (const struct GNUNET_TUN_DnsHeader *) &message[1]; - ts->original_id = dns->id; - if (tunnels[ts->my_id] == ts) - tunnels[ts->my_id] = NULL; - ts->my_id = (uint16_t) GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK, - UINT16_MAX + 1); - tunnels[ts->my_id] = ts; - memcpy (buf, dns, dlen); - dout = (struct GNUNET_TUN_DnsHeader*) buf; - dout->id = ts->my_id; - memset (&v4, 0, sizeof (v4)); - memset (&v6, 0, sizeof (v6)); - if (1 == inet_pton (AF_INET, dns_exit, &v4.sin_addr)) - { - salen = sizeof (v4); - v4.sin_family = AF_INET; - v4.sin_port = htons (53); -#if HAVE_SOCKADDR_IN_SIN_LEN - v4.sin_len = (u_char) salen; -#endif - so = (struct sockaddr *) &v4; - ts->dnsout = get_request_socket (AF_INET); - } - else if (1 == inet_pton (AF_INET6, dns_exit, &v6.sin6_addr)) - { - salen = sizeof (v6); - v6.sin6_family = AF_INET6; - v6.sin6_port = htons (53); -#if HAVE_SOCKADDR_IN_SIN_LEN - v6.sin6_len = (u_char) salen; -#endif - so = (struct sockaddr *) &v6; - ts->dnsout = get_request_socket (AF_INET6); - } - else - { - GNUNET_break (0); - return GNUNET_SYSERR; - } - if (NULL == ts->dnsout) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - _("Configured DNS exit `%s' is not working / valid.\n"), - dns_exit); - return GNUNET_SYSERR; - } - memcpy (&ts->addr, - so, - salen); - ts->addrlen = salen; - GNUNET_NETWORK_socket_sendto (ts->dnsout, - buf, dlen, so, salen); - ts->timeout = GNUNET_TIME_relative_to_absolute (REQUEST_TIMEOUT); - return GNUNET_OK; -} - - -/** - * Callback from GNUNET_MESH for new tunnels. - * - * @param cls closure - * @param tunnel new handle to the tunnel - * @param initiator peer that started the tunnel - * @param ats performance information for the tunnel - * @return initial tunnel context for the tunnel - */ -static void * -accept_dns_tunnel (void *cls GNUNET_UNUSED, struct GNUNET_MESH_Tunnel *tunnel, - const struct GNUNET_PeerIdentity *initiator GNUNET_UNUSED, - const struct GNUNET_ATS_Information *ats GNUNET_UNUSED) -{ - struct TunnelState *ts = GNUNET_malloc (sizeof (struct TunnelState)); - - GNUNET_STATISTICS_update (stats, - gettext_noop ("# Inbound MESH tunnels created"), - 1, GNUNET_NO); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Received inbound tunnel from `%s'\n", - GNUNET_i2s (initiator)); - ts->tunnel = tunnel; - return ts; -} - - -/** - * Function called by mesh whenever an inbound tunnel is destroyed. - * Should clean up any associated state. - * - * @param cls closure (set from GNUNET_MESH_connect) - * @param tunnel connection to the other end (henceforth invalid) - * @param tunnel_ctx place where local state associated - * with the tunnel is stored - */ -static void -destroy_dns_tunnel (void *cls GNUNET_UNUSED, - const struct GNUNET_MESH_Tunnel *tunnel, - void *tunnel_ctx) -{ - struct TunnelState *ts = tunnel_ctx; - - if (tunnels[ts->my_id] == ts) - tunnels[ts->my_id] = NULL; - if (NULL != ts->th) - GNUNET_MESH_notify_transmit_ready_cancel (ts->th); - GNUNET_free_non_null (ts->reply); - GNUNET_free (ts); -} - - /** * @param cls closure * @param server the initialized server @@ -1552,37 +1037,40 @@ run (void *cls, struct GNUNET_SERVER_Handle *server, char *ipv6prefix; struct in_addr dns_exit4; struct in6_addr dns_exit6; + char *dns_exit; + char *binary; cfg = cfg_; + binary = GNUNET_OS_get_libexec_binary_path ("gnunet-helper-dns"); if (GNUNET_YES != - GNUNET_OS_check_helper_binary ("gnunet-helper-dns")) + GNUNET_OS_check_helper_binary (binary)) { GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("`%s' must be installed SUID, refusing to run\n"), - "gnunet-helper-dns"); + binary); global_ret = 1; + GNUNET_free (binary); return; } - + GNUNET_free (binary); stats = GNUNET_STATISTICS_create ("dns", cfg); nc = GNUNET_SERVER_notification_context_create (server, 1); GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, &cleanup_task, cls); - if ( (GNUNET_YES == - GNUNET_CONFIGURATION_get_value_yesno (cfg_, "dns", "PROVIDE_EXIT")) && - ( (GNUNET_OK != + dns_exit = NULL; + if ( ( (GNUNET_OK != GNUNET_CONFIGURATION_get_value_string (cfg, "dns", "DNS_EXIT", &dns_exit)) || ( (1 != inet_pton (AF_INET, dns_exit, &dns_exit4)) && (1 != inet_pton (AF_INET6, dns_exit, &dns_exit6)) ) ) ) { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - _("Configured to provide DNS exit, but no valid DNS server configured!\n")); + GNUNET_log_config_invalid (GNUNET_ERROR_TYPE_ERROR, "dns", "DNS_EXIT", + _("need a valid IPv4 or IPv6 address\n")); GNUNET_free_non_null (dns_exit); dns_exit = NULL; } - + dnsstub = GNUNET_DNSSTUB_start (dns_exit); helper_argv[0] = GNUNET_strdup ("gnunet-dns"); if (GNUNET_SYSERR == GNUNET_CONFIGURATION_get_value_string (cfg, "dns", "IFNAME", &ifc_name)) @@ -1635,28 +1123,11 @@ run (void *cls, struct GNUNET_SERVER_Handle *server, } helper_argv[5] = ipv4mask; helper_argv[6] = NULL; - - if (NULL != dns_exit) - { - static struct GNUNET_MESH_MessageHandler mesh_handlers[] = { - {&receive_dns_request, GNUNET_MESSAGE_TYPE_VPN_DNS_TO_INTERNET, 0}, - {NULL, 0, 0} - }; - static GNUNET_MESH_ApplicationType mesh_types[] = { - GNUNET_APPLICATION_TYPE_INTERNET_RESOLVER, - GNUNET_APPLICATION_TYPE_END - }; - mesh = GNUNET_MESH_connect (cfg, - 1, NULL, - &accept_dns_tunnel, - &destroy_dns_tunnel, - mesh_handlers, - mesh_types); - } - hijacker = GNUNET_HELPER_start ("gnunet-helper-dns", + hijacker = GNUNET_HELPER_start (GNUNET_NO, + "gnunet-helper-dns", helper_argv, &process_helper_messages, - NULL); + NULL, NULL); GNUNET_SERVER_add_handlers (server, handlers); GNUNET_SERVER_disconnect_notify (server, &client_disconnect, NULL); } @@ -1672,6 +1143,25 @@ run (void *cls, struct GNUNET_SERVER_Handle *server, int main (int argc, char *const *argv) { + /* make use of SGID capabilities on POSIX */ + /* FIXME: this might need a port on systems without 'getresgid' */ +#if HAVE_GETRESGID + gid_t rgid; + gid_t egid; + gid_t sgid; + + if (-1 == getresgid (&rgid, &egid, &sgid)) + { + fprintf (stderr, + "getresgid failed: %s\n", + strerror (errno)); + } + else if (sgid != rgid) + { + if (-1 == setregid (sgid, sgid)) + fprintf (stderr, "setregid failed: %s\n", strerror (errno)); + } +#endif return (GNUNET_OK == GNUNET_SERVICE_run (argc, argv, "dns", GNUNET_SERVICE_OPTION_NONE, &run, NULL)) ? global_ret : 1; diff --git a/src/dns/plugin_block_dns.c b/src/dns/plugin_block_dns.c index da8add5..8ac1ef2 100644 --- a/src/dns/plugin_block_dns.c +++ b/src/dns/plugin_block_dns.c @@ -48,7 +48,7 @@ */ static enum GNUNET_BLOCK_EvaluationResult block_plugin_dns_evaluate (void *cls, enum GNUNET_BLOCK_Type type, - const GNUNET_HashCode * query, + const struct GNUNET_HashCode * query, struct GNUNET_CONTAINER_BloomFilter **bf, int32_t bf_mutator, const void *xquery, size_t xquery_size, const void *reply_block, @@ -124,13 +124,13 @@ block_plugin_dns_evaluate (void *cls, enum GNUNET_BLOCK_Type type, static int block_plugin_dns_get_key (void *cls, enum GNUNET_BLOCK_Type type, const void *block, size_t block_size, - GNUNET_HashCode * key) + struct GNUNET_HashCode * key) { if (type != GNUNET_BLOCK_TYPE_DNS) return GNUNET_SYSERR; const struct GNUNET_DNS_Record *rec = block; - memcpy (key, &rec->service_descriptor, sizeof (GNUNET_HashCode)); + memcpy (key, &rec->service_descriptor, sizeof (struct GNUNET_HashCode)); return GNUNET_OK; } diff --git a/src/dns/test_gnunet_dns.sh b/src/dns/test_gnunet_dns.sh index 35585d4..33dfd6c 100755 --- a/src/dns/test_gnunet_dns.sh +++ b/src/dns/test_gnunet_dns.sh @@ -6,13 +6,39 @@ then echo "This test only works if run as root. Skipping." exit 0 fi +if ! which sudo > /dev/null +then + echo "This test requires sudo. Skipping." + exit 0 +fi +if [ ! -x `which sudo` ] +then + echo "This test requires sudo. Skipping." + exit 0 +fi +if ! which nslookup +then + echo "This test requires nslookup. Skipping." + exit 0 +fi +if [ ! -x `which nslookup` ] +then + echo "This test requires nslookup. Skipping." + exit 0 +fi export PATH=".:$PATH" gnunet-service-dns -c dns.conf & gnunet-dns-redirector -c dns.conf -4 127.0.0.1 & sleep 1 -LO=`nslookup gnunet.org | grep Address | tail -n1` +# need to run 'nslookup' as 'nobody', as gnunet-service-dns runs as root +# and thus 'root' is excepted from DNS interception! +LO=`sudo -u nobody nslookup gnunet.org | grep Address | tail -n1` if [ "$LO" != "Address: 127.0.0.1" ] then - echo "Fail: $LO" + echo "Fail: got address $LO, wanted 127.0.0.1" + ret=1 +else + ret=0 fi kill `jobs -p` +exit $ret diff --git a/src/dv/Makefile.am b/src/dv/Makefile.am index e0cd2e4..0fa26a9 100644 --- a/src/dv/Makefile.am +++ b/src/dv/Makefile.am @@ -11,6 +11,8 @@ endif plugindir = $(libdir)/gnunet +libexecdir= $(pkglibdir)/libexec/ + pkgcfgdir= $(pkgdatadir)/config.d/ pkgcfg_DATA = \ @@ -31,7 +33,7 @@ libgnunetdv_la_LDFLAGS = \ -version-info 0:0:0 -bin_PROGRAMS = \ +libexec_PROGRAMS = \ gnunet-service-dv gnunet_service_dv_SOURCES = \ @@ -59,21 +61,20 @@ libgnunet_plugin_transport_dv_la_LDFLAGS = \ libgnunet_plugin_transport_dv_la_DEPENDENCIES = \ libgnunetdv.la -check_PROGRAMS = \ - test_transport_api_dv +#check_PROGRAMS = \ +# test_transport_api_dv # test_dv_topology if ENABLE_TEST_RUN TESTS = $(check_PROGRAMS) $(check_SCRIPTS) endif -test_transport_api_dv_SOURCES = \ - test_transport_api_dv.c -test_transport_api_dv_LDADD = \ - $(top_builddir)/src/core/libgnunetcore.la \ - $(top_builddir)/src/transport/libgnunettransport.la \ - $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/testing/libgnunettesting.la +#test_transport_api_dv_SOURCES = \ +# test_transport_api_dv.c +#test_transport_api_dv_LDADD = \ +# $(top_builddir)/src/core/libgnunetcore.la \ +# $(top_builddir)/src/transport/libgnunettransport.la \ +# $(top_builddir)/src/util/libgnunetutil.la EXTRA_DIST = \ test_transport_dv_data.conf diff --git a/src/dv/Makefile.in b/src/dv/Makefile.in index 3389e56..9d47dfd 100644 --- a/src/dv/Makefile.in +++ b/src/dv/Makefile.in @@ -1,9 +1,9 @@ -# Makefile.in generated by automake 1.11.1 from Makefile.am. +# Makefile.in generated by automake 1.11.6 from Makefile.am. # @configure_input@ # Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, -# 2003, 2004, 2005, 2006, 2007, 2008, 2009 Free Software Foundation, -# Inc. +# 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Free Software +# Foundation, Inc. # This Makefile.in is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. @@ -18,6 +18,23 @@ VPATH = @srcdir@ +am__make_dryrun = \ + { \ + am__dry=no; \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + echo 'am--echo: ; @echo "AM" OK' | $(MAKE) -f - 2>/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } pkgdatadir = $(datadir)/@PACKAGE@ pkgincludedir = $(includedir)/@PACKAGE@ pkglibdir = $(libdir)/@PACKAGE@ @@ -37,23 +54,23 @@ POST_UNINSTALL = : build_triplet = @build@ host_triplet = @host@ target_triplet = @target@ -bin_PROGRAMS = gnunet-service-dv$(EXEEXT) -check_PROGRAMS = test_transport_api_dv$(EXEEXT) -@ENABLE_TEST_RUN_TRUE@TESTS = $(check_PROGRAMS) +libexec_PROGRAMS = gnunet-service-dv$(EXEEXT) +TESTS = subdir = src/dv DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in \ $(srcdir)/dv.conf.in ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 am__aclocal_m4_deps = $(top_srcdir)/m4/absolute-header.m4 \ $(top_srcdir)/m4/align.m4 $(top_srcdir)/m4/argz.m4 \ - $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/iconv.m4 \ - $(top_srcdir)/m4/lib-ld.m4 $(top_srcdir)/m4/lib-link.m4 \ - $(top_srcdir)/m4/lib-prefix.m4 $(top_srcdir)/m4/libcurl.m4 \ - $(top_srcdir)/m4/libgcrypt.m4 $(top_srcdir)/m4/libtool.m4 \ - $(top_srcdir)/m4/libunistring.m4 $(top_srcdir)/m4/ltdl.m4 \ - $(top_srcdir)/m4/ltoptions.m4 $(top_srcdir)/m4/ltsugar.m4 \ - $(top_srcdir)/m4/ltversion.m4 $(top_srcdir)/m4/lt~obsolete.m4 \ - $(top_srcdir)/m4/nls.m4 $(top_srcdir)/m4/po.m4 \ + $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/glib-2.0.m4 \ + $(top_srcdir)/m4/iconv.m4 $(top_srcdir)/m4/lib-ld.m4 \ + $(top_srcdir)/m4/lib-link.m4 $(top_srcdir)/m4/lib-prefix.m4 \ + $(top_srcdir)/m4/libcurl.m4 $(top_srcdir)/m4/libgcrypt.m4 \ + $(top_srcdir)/m4/libtool.m4 $(top_srcdir)/m4/libunistring.m4 \ + $(top_srcdir)/m4/ltdl.m4 $(top_srcdir)/m4/ltoptions.m4 \ + $(top_srcdir)/m4/ltsugar.m4 $(top_srcdir)/m4/ltversion.m4 \ + $(top_srcdir)/m4/lt~obsolete.m4 $(top_srcdir)/m4/nls.m4 \ + $(top_srcdir)/m4/pkg.m4 $(top_srcdir)/m4/po.m4 \ $(top_srcdir)/m4/progtest.m4 $(top_srcdir)/acinclude.m4 \ $(top_srcdir)/configure.ac am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ @@ -83,14 +100,20 @@ am__nobase_list = $(am__nobase_strip_setup); \ am__base_list = \ sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \ sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g' +am__uninstall_files_from_dir = { \ + test -z "$$files" \ + || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \ + || { echo " ( cd '$$dir' && rm -f" $$files ")"; \ + $(am__cd) "$$dir" && rm -f $$files; }; \ + } am__installdirs = "$(DESTDIR)$(libdir)" "$(DESTDIR)$(plugindir)" \ - "$(DESTDIR)$(bindir)" "$(DESTDIR)$(pkgcfgdir)" + "$(DESTDIR)$(libexecdir)" "$(DESTDIR)$(pkgcfgdir)" LTLIBRARIES = $(lib_LTLIBRARIES) $(plugin_LTLIBRARIES) am_libgnunet_plugin_transport_dv_la_OBJECTS = plugin_transport_dv.lo libgnunet_plugin_transport_dv_la_OBJECTS = \ $(am_libgnunet_plugin_transport_dv_la_OBJECTS) -AM_V_lt = $(am__v_lt_$(V)) -am__v_lt_ = $(am__v_lt_$(AM_DEFAULT_VERBOSITY)) +AM_V_lt = $(am__v_lt_@AM_V@) +am__v_lt_ = $(am__v_lt_@AM_DEFAULT_V@) am__v_lt_0 = --silent libgnunet_plugin_transport_dv_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ @@ -107,16 +130,9 @@ libgnunetdv_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ $(AM_CFLAGS) $(CFLAGS) $(libgnunetdv_la_LDFLAGS) $(LDFLAGS) -o \ $@ -PROGRAMS = $(bin_PROGRAMS) +PROGRAMS = $(libexec_PROGRAMS) am_gnunet_service_dv_OBJECTS = gnunet-service-dv.$(OBJEXT) gnunet_service_dv_OBJECTS = $(am_gnunet_service_dv_OBJECTS) -am_test_transport_api_dv_OBJECTS = test_transport_api_dv.$(OBJEXT) -test_transport_api_dv_OBJECTS = $(am_test_transport_api_dv_OBJECTS) -test_transport_api_dv_DEPENDENCIES = \ - $(top_builddir)/src/core/libgnunetcore.la \ - $(top_builddir)/src/transport/libgnunettransport.la \ - $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/testing/libgnunettesting.la DEFAULT_INCLUDES = -I.@am__isrc@ -I$(top_builddir) depcomp = $(SHELL) $(top_srcdir)/depcomp am__depfiles_maybe = depfiles @@ -127,28 +143,31 @@ LTCOMPILE = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) \ $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) \ $(AM_CFLAGS) $(CFLAGS) -AM_V_CC = $(am__v_CC_$(V)) -am__v_CC_ = $(am__v_CC_$(AM_DEFAULT_VERBOSITY)) +AM_V_CC = $(am__v_CC_@AM_V@) +am__v_CC_ = $(am__v_CC_@AM_DEFAULT_V@) am__v_CC_0 = @echo " CC " $@; -AM_V_at = $(am__v_at_$(V)) -am__v_at_ = $(am__v_at_$(AM_DEFAULT_VERBOSITY)) +AM_V_at = $(am__v_at_@AM_V@) +am__v_at_ = $(am__v_at_@AM_DEFAULT_V@) am__v_at_0 = @ CCLD = $(CC) LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ $(AM_LDFLAGS) $(LDFLAGS) -o $@ -AM_V_CCLD = $(am__v_CCLD_$(V)) -am__v_CCLD_ = $(am__v_CCLD_$(AM_DEFAULT_VERBOSITY)) +AM_V_CCLD = $(am__v_CCLD_@AM_V@) +am__v_CCLD_ = $(am__v_CCLD_@AM_DEFAULT_V@) am__v_CCLD_0 = @echo " CCLD " $@; -AM_V_GEN = $(am__v_GEN_$(V)) -am__v_GEN_ = $(am__v_GEN_$(AM_DEFAULT_VERBOSITY)) +AM_V_GEN = $(am__v_GEN_@AM_V@) +am__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@) am__v_GEN_0 = @echo " GEN " $@; SOURCES = $(libgnunet_plugin_transport_dv_la_SOURCES) \ - $(libgnunetdv_la_SOURCES) $(gnunet_service_dv_SOURCES) \ - $(test_transport_api_dv_SOURCES) + $(libgnunetdv_la_SOURCES) $(gnunet_service_dv_SOURCES) DIST_SOURCES = $(libgnunet_plugin_transport_dv_la_SOURCES) \ - $(libgnunetdv_la_SOURCES) $(gnunet_service_dv_SOURCES) \ - $(test_transport_api_dv_SOURCES) + $(libgnunetdv_la_SOURCES) $(gnunet_service_dv_SOURCES) +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac DATA = $(pkgcfg_DATA) ETAGS = etags CTAGS = ctags @@ -190,6 +209,10 @@ EXEEXT = @EXEEXT@ EXT_LIBS = @EXT_LIBS@ EXT_LIB_PATH = @EXT_LIB_PATH@ FGREP = @FGREP@ +GLIB_CFLAGS = @GLIB_CFLAGS@ +GLIB_GENMARSHAL = @GLIB_GENMARSHAL@ +GLIB_LIBS = @GLIB_LIBS@ +GLIB_MKENUMS = @GLIB_MKENUMS@ GMSGFMT = @GMSGFMT@ GMSGFMT_015 = @GMSGFMT_015@ GNUNETDNS_GROUP = @GNUNETDNS_GROUP@ @@ -200,6 +223,7 @@ GN_LIBINTL = @GN_LIBINTL@ GN_LIB_LDFLAGS = @GN_LIB_LDFLAGS@ GN_PLUGIN_LDFLAGS = @GN_PLUGIN_LDFLAGS@ GN_USER_HOME_DIR = @GN_USER_HOME_DIR@ +GOBJECT_QUERY = @GOBJECT_QUERY@ GREP = @GREP@ HAVE_LIBUNISTRING = @HAVE_LIBUNISTRING@ INCLTDL = @INCLTDL@ @@ -222,6 +246,8 @@ LIBCURL_CPPFLAGS = @LIBCURL_CPPFLAGS@ LIBGCRYPT_CFLAGS = @LIBGCRYPT_CFLAGS@ LIBGCRYPT_CONFIG = @LIBGCRYPT_CONFIG@ LIBGCRYPT_LIBS = @LIBGCRYPT_LIBS@ +LIBGTOP_CFLAGS = @LIBGTOP_CFLAGS@ +LIBGTOP_LIBS = @LIBGTOP_LIBS@ LIBICONV = @LIBICONV@ LIBINTL = @LIBINTL@ LIBLTDL = @LIBLTDL@ @@ -243,6 +269,7 @@ LT_CONFIG_H = @LT_CONFIG_H@ LT_DLLOADERS = @LT_DLLOADERS@ LT_DLPREOPEN = @LT_DLPREOPEN@ MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ MKDIR_P = @MKDIR_P@ MONKEYPREFIX = @MONKEYPREFIX@ MSGFMT = @MSGFMT@ @@ -252,6 +279,7 @@ MYSQL_CPPFLAGS = @MYSQL_CPPFLAGS@ MYSQL_LDFLAGS = @MYSQL_LDFLAGS@ NM = @NM@ NMEDIT = @NMEDIT@ +NSS_DIR = @NSS_DIR@ OBJC = @OBJC@ OBJCDEPMODE = @OBJCDEPMODE@ OBJCFLAGS = @OBJCFLAGS@ @@ -267,6 +295,7 @@ PACKAGE_TARNAME = @PACKAGE_TARNAME@ PACKAGE_URL = @PACKAGE_URL@ PACKAGE_VERSION = @PACKAGE_VERSION@ PATH_SEPARATOR = @PATH_SEPARATOR@ +PKG_CONFIG = @PKG_CONFIG@ POSTGRES_CPPFLAGS = @POSTGRES_CPPFLAGS@ POSTGRES_LDFLAGS = @POSTGRES_LDFLAGS@ POSUB = @POSUB@ @@ -298,6 +327,7 @@ abs_builddir = @abs_builddir@ abs_srcdir = @abs_srcdir@ abs_top_builddir = @abs_top_builddir@ abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ ac_ct_CC = @ac_ct_CC@ ac_ct_CXX = @ac_ct_CXX@ ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ @@ -320,6 +350,7 @@ datarootdir = @datarootdir@ docdir = @docdir@ dvidir = @dvidir@ exec_prefix = @exec_prefix@ +gitcommand = @gitcommand@ host = @host@ host_alias = @host_alias@ host_cpu = @host_cpu@ @@ -330,10 +361,9 @@ includedir = @includedir@ infodir = @infodir@ install_sh = @install_sh@ libdir = @libdir@ -libexecdir = @libexecdir@ +libexecdir = $(pkglibdir)/libexec/ localedir = @localedir@ localstatedir = @localstatedir@ -lt_ECHO = @lt_ECHO@ ltdl_LIBOBJS = @ltdl_LIBOBJS@ ltdl_LTLIBOBJS = @ltdl_LTLIBOBJS@ mandir = @mandir@ @@ -351,6 +381,7 @@ sbindir = @sbindir@ sharedstatedir = @sharedstatedir@ srcdir = @srcdir@ subdirs = @subdirs@ +svnversioncommand = @svnversioncommand@ sys_symbol_underscore = @sys_symbol_underscore@ sysconfdir = @sysconfdir@ target = @target@ @@ -414,15 +445,13 @@ libgnunet_plugin_transport_dv_la_LDFLAGS = \ libgnunet_plugin_transport_dv_la_DEPENDENCIES = \ libgnunetdv.la -test_transport_api_dv_SOURCES = \ - test_transport_api_dv.c - -test_transport_api_dv_LDADD = \ - $(top_builddir)/src/core/libgnunetcore.la \ - $(top_builddir)/src/transport/libgnunettransport.la \ - $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/testing/libgnunettesting.la +#test_transport_api_dv_SOURCES = \ +# test_transport_api_dv.c +#test_transport_api_dv_LDADD = \ +# $(top_builddir)/src/core/libgnunetcore.la \ +# $(top_builddir)/src/transport/libgnunettransport.la \ +# $(top_builddir)/src/util/libgnunetutil.la EXTRA_DIST = \ test_transport_dv_data.conf @@ -464,7 +493,6 @@ dv.conf: $(top_builddir)/config.status $(srcdir)/dv.conf.in cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ install-libLTLIBRARIES: $(lib_LTLIBRARIES) @$(NORMAL_INSTALL) - test -z "$(libdir)" || $(MKDIR_P) "$(DESTDIR)$(libdir)" @list='$(lib_LTLIBRARIES)'; test -n "$(libdir)" || list=; \ list2=; for p in $$list; do \ if test -f $$p; then \ @@ -472,6 +500,8 @@ install-libLTLIBRARIES: $(lib_LTLIBRARIES) else :; fi; \ done; \ test -z "$$list2" || { \ + echo " $(MKDIR_P) '$(DESTDIR)$(libdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libdir)" || exit 1; \ echo " $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 '$(DESTDIR)$(libdir)'"; \ $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 "$(DESTDIR)$(libdir)"; \ } @@ -495,7 +525,6 @@ clean-libLTLIBRARIES: done install-pluginLTLIBRARIES: $(plugin_LTLIBRARIES) @$(NORMAL_INSTALL) - test -z "$(plugindir)" || $(MKDIR_P) "$(DESTDIR)$(plugindir)" @list='$(plugin_LTLIBRARIES)'; test -n "$(plugindir)" || list=; \ list2=; for p in $$list; do \ if test -f $$p; then \ @@ -503,6 +532,8 @@ install-pluginLTLIBRARIES: $(plugin_LTLIBRARIES) else :; fi; \ done; \ test -z "$$list2" || { \ + echo " $(MKDIR_P) '$(DESTDIR)$(plugindir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(plugindir)" || exit 1; \ echo " $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 '$(DESTDIR)$(plugindir)'"; \ $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 "$(DESTDIR)$(plugindir)"; \ } @@ -524,14 +555,17 @@ clean-pluginLTLIBRARIES: echo "rm -f \"$${dir}/so_locations\""; \ rm -f "$${dir}/so_locations"; \ done -libgnunet_plugin_transport_dv.la: $(libgnunet_plugin_transport_dv_la_OBJECTS) $(libgnunet_plugin_transport_dv_la_DEPENDENCIES) +libgnunet_plugin_transport_dv.la: $(libgnunet_plugin_transport_dv_la_OBJECTS) $(libgnunet_plugin_transport_dv_la_DEPENDENCIES) $(EXTRA_libgnunet_plugin_transport_dv_la_DEPENDENCIES) $(AM_V_CCLD)$(libgnunet_plugin_transport_dv_la_LINK) -rpath $(plugindir) $(libgnunet_plugin_transport_dv_la_OBJECTS) $(libgnunet_plugin_transport_dv_la_LIBADD) $(LIBS) -libgnunetdv.la: $(libgnunetdv_la_OBJECTS) $(libgnunetdv_la_DEPENDENCIES) +libgnunetdv.la: $(libgnunetdv_la_OBJECTS) $(libgnunetdv_la_DEPENDENCIES) $(EXTRA_libgnunetdv_la_DEPENDENCIES) $(AM_V_CCLD)$(libgnunetdv_la_LINK) -rpath $(libdir) $(libgnunetdv_la_OBJECTS) $(libgnunetdv_la_LIBADD) $(LIBS) -install-binPROGRAMS: $(bin_PROGRAMS) +install-libexecPROGRAMS: $(libexec_PROGRAMS) @$(NORMAL_INSTALL) - test -z "$(bindir)" || $(MKDIR_P) "$(DESTDIR)$(bindir)" - @list='$(bin_PROGRAMS)'; test -n "$(bindir)" || list=; \ + @list='$(libexec_PROGRAMS)'; test -n "$(libexecdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(libexecdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libexecdir)" || exit 1; \ + fi; \ for p in $$list; do echo "$$p $$p"; done | \ sed 's/$(EXEEXT)$$//' | \ while read p p1; do if test -f $$p || test -f $$p1; \ @@ -548,44 +582,32 @@ install-binPROGRAMS: $(bin_PROGRAMS) while read type dir files; do \ if test "$$dir" = .; then dir=; else dir=/$$dir; fi; \ test -z "$$files" || { \ - echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files '$(DESTDIR)$(bindir)$$dir'"; \ - $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files "$(DESTDIR)$(bindir)$$dir" || exit $$?; \ + echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files '$(DESTDIR)$(libexecdir)$$dir'"; \ + $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files "$(DESTDIR)$(libexecdir)$$dir" || exit $$?; \ } \ ; done -uninstall-binPROGRAMS: +uninstall-libexecPROGRAMS: @$(NORMAL_UNINSTALL) - @list='$(bin_PROGRAMS)'; test -n "$(bindir)" || list=; \ + @list='$(libexec_PROGRAMS)'; test -n "$(libexecdir)" || list=; \ files=`for p in $$list; do echo "$$p"; done | \ sed -e 'h;s,^.*/,,;s/$(EXEEXT)$$//;$(transform)' \ -e 's/$$/$(EXEEXT)/' `; \ test -n "$$list" || exit 0; \ - echo " ( cd '$(DESTDIR)$(bindir)' && rm -f" $$files ")"; \ - cd "$(DESTDIR)$(bindir)" && rm -f $$files - -clean-binPROGRAMS: - @list='$(bin_PROGRAMS)'; test -n "$$list" || exit 0; \ - echo " rm -f" $$list; \ - rm -f $$list || exit $$?; \ - test -n "$(EXEEXT)" || exit 0; \ - list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ - echo " rm -f" $$list; \ - rm -f $$list + echo " ( cd '$(DESTDIR)$(libexecdir)' && rm -f" $$files ")"; \ + cd "$(DESTDIR)$(libexecdir)" && rm -f $$files -clean-checkPROGRAMS: - @list='$(check_PROGRAMS)'; test -n "$$list" || exit 0; \ +clean-libexecPROGRAMS: + @list='$(libexec_PROGRAMS)'; test -n "$$list" || exit 0; \ echo " rm -f" $$list; \ rm -f $$list || exit $$?; \ test -n "$(EXEEXT)" || exit 0; \ list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ echo " rm -f" $$list; \ rm -f $$list -gnunet-service-dv$(EXEEXT): $(gnunet_service_dv_OBJECTS) $(gnunet_service_dv_DEPENDENCIES) +gnunet-service-dv$(EXEEXT): $(gnunet_service_dv_OBJECTS) $(gnunet_service_dv_DEPENDENCIES) $(EXTRA_gnunet_service_dv_DEPENDENCIES) @rm -f gnunet-service-dv$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_service_dv_OBJECTS) $(gnunet_service_dv_LDADD) $(LIBS) -test_transport_api_dv$(EXEEXT): $(test_transport_api_dv_OBJECTS) $(test_transport_api_dv_DEPENDENCIES) - @rm -f test_transport_api_dv$(EXEEXT) - $(AM_V_CCLD)$(LINK) $(test_transport_api_dv_OBJECTS) $(test_transport_api_dv_LDADD) $(LIBS) mostlyclean-compile: -rm -f *.$(OBJEXT) @@ -596,31 +618,27 @@ distclean-compile: @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/dv_api.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-service-dv.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/plugin_transport_dv.Plo@am__quote@ -@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_transport_api_dv.Po@am__quote@ .c.o: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c $< .c.obj: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'` @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c `$(CYGPATH_W) '$<'` +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c `$(CYGPATH_W) '$<'` .c.lo: @am__fastdepCC_TRUE@ $(AM_V_CC)$(LTCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LTCOMPILE) -c -o $@ $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LTCOMPILE) -c -o $@ $< mostlyclean-libtool: -rm -f *.lo @@ -629,8 +647,11 @@ clean-libtool: -rm -rf .libs _libs install-pkgcfgDATA: $(pkgcfg_DATA) @$(NORMAL_INSTALL) - test -z "$(pkgcfgdir)" || $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" @list='$(pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(pkgcfgdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" || exit 1; \ + fi; \ for p in $$list; do \ if test -f "$$p"; then d=; else d="$(srcdir)/"; fi; \ echo "$$d$$p"; \ @@ -644,9 +665,7 @@ uninstall-pkgcfgDATA: @$(NORMAL_UNINSTALL) @list='$(pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ files=`for p in $$list; do echo $$p; done | sed -e 's|^.*/||'`; \ - test -n "$$files" || exit 0; \ - echo " ( cd '$(DESTDIR)$(pkgcfgdir)' && rm -f" $$files ")"; \ - cd "$(DESTDIR)$(pkgcfgdir)" && rm -f $$files + dir='$(DESTDIR)$(pkgcfgdir)'; $(am__uninstall_files_from_dir) ID: $(HEADERS) $(SOURCES) $(LISP) $(TAGS_FILES) list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ @@ -781,14 +800,15 @@ check-TESTS: $(TESTS) fi; \ dashes=`echo "$$dashes" | sed s/./=/g`; \ if test "$$failed" -eq 0; then \ - echo "$$grn$$dashes"; \ + col="$$grn"; \ else \ - echo "$$red$$dashes"; \ + col="$$red"; \ fi; \ - echo "$$banner"; \ - test -z "$$skipped" || echo "$$skipped"; \ - test -z "$$report" || echo "$$report"; \ - echo "$$dashes$$std"; \ + echo "$${col}$$dashes$${std}"; \ + echo "$${col}$$banner$${std}"; \ + test -z "$$skipped" || echo "$${col}$$skipped$${std}"; \ + test -z "$$report" || echo "$${col}$$report$${std}"; \ + echo "$${col}$$dashes$${std}"; \ test "$$failed" -eq 0; \ else :; fi @@ -823,14 +843,11 @@ distdir: $(DISTFILES) fi; \ done check-am: all-am - $(MAKE) $(AM_MAKEFLAGS) $(check_PROGRAMS) $(MAKE) $(AM_MAKEFLAGS) check-TESTS check: check-am all-am: Makefile $(LTLIBRARIES) $(PROGRAMS) $(DATA) -install-binPROGRAMS: install-libLTLIBRARIES - installdirs: - for dir in "$(DESTDIR)$(libdir)" "$(DESTDIR)$(plugindir)" "$(DESTDIR)$(bindir)" "$(DESTDIR)$(pkgcfgdir)"; do \ + for dir in "$(DESTDIR)$(libdir)" "$(DESTDIR)$(plugindir)" "$(DESTDIR)$(libexecdir)" "$(DESTDIR)$(pkgcfgdir)"; do \ test -z "$$dir" || $(MKDIR_P) "$$dir"; \ done install: install-am @@ -843,10 +860,15 @@ install-am: all-am installcheck: installcheck-am install-strip: - $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ - install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ - `test -z '$(STRIP)' || \ - echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi mostlyclean-generic: clean-generic: @@ -860,9 +882,8 @@ maintainer-clean-generic: @echo "it deletes files that may require special tools to rebuild." clean: clean-am -clean-am: clean-binPROGRAMS clean-checkPROGRAMS clean-generic \ - clean-libLTLIBRARIES clean-libtool clean-pluginLTLIBRARIES \ - mostlyclean-am +clean-am: clean-generic clean-libLTLIBRARIES clean-libexecPROGRAMS \ + clean-libtool clean-pluginLTLIBRARIES mostlyclean-am distclean: distclean-am -rm -rf ./$(DEPDIR) @@ -888,7 +909,7 @@ install-dvi: install-dvi-am install-dvi-am: -install-exec-am: install-binPROGRAMS install-libLTLIBRARIES +install-exec-am: install-libLTLIBRARIES install-libexecPROGRAMS install-html: install-html-am @@ -928,27 +949,27 @@ ps: ps-am ps-am: -uninstall-am: uninstall-binPROGRAMS uninstall-libLTLIBRARIES \ +uninstall-am: uninstall-libLTLIBRARIES uninstall-libexecPROGRAMS \ uninstall-pkgcfgDATA uninstall-pluginLTLIBRARIES .MAKE: check-am install-am install-strip .PHONY: CTAGS GTAGS all all-am check check-TESTS check-am clean \ - clean-binPROGRAMS clean-checkPROGRAMS clean-generic \ - clean-libLTLIBRARIES clean-libtool clean-pluginLTLIBRARIES \ - ctags distclean distclean-compile distclean-generic \ - distclean-libtool distclean-tags distdir dvi dvi-am html \ - html-am info info-am install install-am install-binPROGRAMS \ - install-data install-data-am install-dvi install-dvi-am \ - install-exec install-exec-am install-html install-html-am \ - install-info install-info-am install-libLTLIBRARIES \ - install-man install-pdf install-pdf-am install-pkgcfgDATA \ + clean-generic clean-libLTLIBRARIES clean-libexecPROGRAMS \ + clean-libtool clean-pluginLTLIBRARIES ctags distclean \ + distclean-compile distclean-generic distclean-libtool \ + distclean-tags distdir dvi dvi-am html html-am info info-am \ + install install-am install-data install-data-am install-dvi \ + install-dvi-am install-exec install-exec-am install-html \ + install-html-am install-info install-info-am \ + install-libLTLIBRARIES install-libexecPROGRAMS install-man \ + install-pdf install-pdf-am install-pkgcfgDATA \ install-pluginLTLIBRARIES install-ps install-ps-am \ install-strip installcheck installcheck-am installdirs \ maintainer-clean maintainer-clean-generic mostlyclean \ mostlyclean-compile mostlyclean-generic mostlyclean-libtool \ pdf pdf-am ps ps-am tags uninstall uninstall-am \ - uninstall-binPROGRAMS uninstall-libLTLIBRARIES \ + uninstall-libLTLIBRARIES uninstall-libexecPROGRAMS \ uninstall-pkgcfgDATA uninstall-pluginLTLIBRARIES diff --git a/src/dv/dv.conf.in b/src/dv/dv.conf.in index 93278df..c0dc21b 100644 --- a/src/dv/dv.conf.in +++ b/src/dv/dv.conf.in @@ -1,10 +1,8 @@ [dv] AUTOSTART = YES -DEBUG = NO ACCEPT_FROM6 = ::1; ACCEPT_FROM = 127.0.0.1; BINARY = gnunet-service-dv -CONFIG = $DEFAULTCONFIG HOME = $SERVICEHOME HOSTNAME = localhost @UNIXONLY@ PORT = 2571 diff --git a/src/dv/dv_api.c b/src/dv/dv_api.c index 93891ca..d3cdb0f 100644 --- a/src/dv/dv_api.c +++ b/src/dv/dv_api.c @@ -145,6 +145,16 @@ struct SendCallbackContext * Target of the message. */ struct GNUNET_PeerIdentity target; + + /** + * Payload size in bytes + */ + size_t payload_size; + + /** + * DV message size + */ + size_t msg_size; }; /** @@ -154,9 +164,9 @@ struct SendCallbackContext * @param hash set to uid (extended with zeros) */ static void -hash_from_uid (uint32_t uid, GNUNET_HashCode * hash) +hash_from_uid (uint32_t uid, struct GNUNET_HashCode * hash) { - memset (hash, 0, sizeof (GNUNET_HashCode)); + memset (hash, 0, sizeof (struct GNUNET_HashCode)); *((uint32_t *) hash) = uid; } @@ -351,7 +361,7 @@ handle_message_receipt (void *cls, const struct GNUNET_MessageHeader *msg) char *sender_address; char *packed_msg; char *packed_msg_start; - GNUNET_HashCode uidhash; + struct GNUNET_HashCode uidhash; struct SendCallbackContext *send_ctx; if (msg == NULL) @@ -416,11 +426,13 @@ handle_message_receipt (void *cls, const struct GNUNET_MessageHeader *msg) { if (ntohl (send_result_msg->result) == 0) { - send_ctx->cont (send_ctx->cont_cls, &send_ctx->target, GNUNET_OK); + send_ctx->cont (send_ctx->cont_cls, &send_ctx->target, GNUNET_OK, + send_ctx->payload_size, send_ctx->msg_size); } else { - send_ctx->cont (send_ctx->cont_cls, &send_ctx->target, GNUNET_SYSERR); + send_ctx->cont (send_ctx->cont_cls, &send_ctx->target, GNUNET_SYSERR, + send_ctx->payload_size, 0); } } GNUNET_free_non_null (send_ctx); @@ -459,7 +471,7 @@ GNUNET_DV_send (struct GNUNET_DV_Handle *dv_handle, struct GNUNET_DV_SendMessage *msg; struct SendCallbackContext *send_ctx; char *end_of_message; - GNUNET_HashCode uidhash; + struct GNUNET_HashCode uidhash; int msize; #if DEBUG_DV_MESSAGES @@ -484,6 +496,8 @@ GNUNET_DV_send (struct GNUNET_DV_Handle *dv_handle, memcpy (end_of_message, msgbuf, msgbuf_size); add_pending (dv_handle, msg); send_ctx = GNUNET_malloc (sizeof (struct SendCallbackContext)); + send_ctx->payload_size = msgbuf_size; + send_ctx->msg_size = msize; send_ctx->cont = cont; send_ctx->cont_cls = cont_cls; memcpy (&send_ctx->target, target, sizeof (struct GNUNET_PeerIdentity)); @@ -587,7 +601,7 @@ GNUNET_DV_connect (const struct GNUNET_CONFIGURATION_Handle *cfg, GNUNET_YES, &transmit_start, start_context); - handle->send_callbacks = GNUNET_CONTAINER_multihashmap_create (100); + handle->send_callbacks = GNUNET_CONTAINER_multihashmap_create (100, GNUNET_NO); return handle; } diff --git a/src/dv/gnunet-service-dv.c b/src/dv/gnunet-service-dv.c index 956595f..ca881aa 100644 --- a/src/dv/gnunet-service-dv.c +++ b/src/dv/gnunet-service-dv.c @@ -681,7 +681,7 @@ find_destination (void *cls, struct GNUNET_CONTAINER_HeapNode *node, * respective neighbor. */ static int -find_specific_id (void *cls, const GNUNET_HashCode * key, void *value) +find_specific_id (void *cls, const struct GNUNET_HashCode * key, void *value) { struct FindIDContext *fdc = cls; struct DistantNeighbor *dn = value; @@ -704,7 +704,7 @@ find_specific_id (void *cls, const GNUNET_HashCode * key, void *value) * route. */ static int -find_distant_peer (void *cls, const GNUNET_HashCode * key, void *value) +find_distant_peer (void *cls, const struct GNUNET_HashCode * key, void *value) { struct FindDestinationContext *fdc = cls; struct DistantNeighbor *distant = value; @@ -1085,7 +1085,7 @@ send_message_via (const struct GNUNET_PeerIdentity *sender, * @return GNUNET_YES to continue iteration, GNUNET_NO to stop */ static int -find_least_cost_peer (void *cls, const GNUNET_HashCode * key, void *value) +find_least_cost_peer (void *cls, const struct GNUNET_HashCode * key, void *value) { struct FindLeastCostContext *find_context = cls; struct DistantNeighbor *dn = value; @@ -1264,7 +1264,7 @@ struct CheckPeerContext * GNUNET_NO if not. */ int -checkPeerID (void *cls, const GNUNET_HashCode * key, void *value) +checkPeerID (void *cls, const struct GNUNET_HashCode * key, void *value) { struct CheckPeerContext *ctx = cls; struct DistantNeighbor *distant = value; @@ -1661,7 +1661,7 @@ handle_dv_data_message (void *cls, const struct GNUNET_PeerIdentity *peer, * GNUNET_NO if not. */ int -print_neighbors (void *cls, const GNUNET_HashCode * key, void *abs_value) +print_neighbors (void *cls, const struct GNUNET_HashCode * key, void *abs_value) { struct DistantNeighbor *distant_neighbor = abs_value; char my_shortname[5]; @@ -1849,7 +1849,7 @@ handle_start (void *cls, struct GNUNET_SERVER_Client *client, * GNUNET_NO if not. */ int -send_iterator (void *cls, const GNUNET_HashCode * key, void *abs_value) +send_iterator (void *cls, const struct GNUNET_HashCode * key, void *abs_value) { struct DV_SendContext *send_context = cls; struct DistantNeighbor *distant_neighbor = abs_value; @@ -2174,7 +2174,7 @@ direct_neighbor_free (struct DirectNeighbor *direct) * @return GNUNET_YES to continue iteration, GNUNET_NO to stop */ static int -schedule_disconnect_messages (void *cls, const GNUNET_HashCode * key, +schedule_disconnect_messages (void *cls, const struct GNUNET_HashCode * key, void *value) { struct DisconnectContext *disconnect_context = cls; @@ -2222,7 +2222,7 @@ schedule_disconnect_messages (void *cls, const GNUNET_HashCode * key, * @return GNUNET_YES to continue iteration, GNUNET_NO to stop */ static int -free_extended_neighbors (void *cls, const GNUNET_HashCode * key, void *value) +free_extended_neighbors (void *cls, const struct GNUNET_HashCode * key, void *value) { struct DistantNeighbor *distant = value; @@ -2240,7 +2240,7 @@ free_extended_neighbors (void *cls, const GNUNET_HashCode * key, void *value) * @return GNUNET_YES to continue iteration, GNUNET_NO to stop */ static int -free_direct_neighbors (void *cls, const GNUNET_HashCode * key, void *value) +free_direct_neighbors (void *cls, const struct GNUNET_HashCode * key, void *value) { struct DirectNeighbor *direct = value; @@ -2320,7 +2320,7 @@ core_init (void *cls, struct GNUNET_CORE_Handle *server, * GNUNET_NO if not. */ static int -add_pkey_to_extended (void *cls, const GNUNET_HashCode * key, void *abs_value) +add_pkey_to_extended (void *cls, const struct GNUNET_HashCode * key, void *abs_value) { struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *pkey = cls; struct DistantNeighbor *distant_neighbor = abs_value; @@ -2348,7 +2348,7 @@ add_pkey_to_extended (void *cls, const GNUNET_HashCode * key, void *abs_value) * GNUNET_NO if not. */ static int -update_matching_neighbors (void *cls, const GNUNET_HashCode * key, void *value) +update_matching_neighbors (void *cls, const struct GNUNET_HashCode * key, void *value) { struct NeighborUpdateInfo *update_info = cls; struct DistantNeighbor *distant_neighbor = value; @@ -2384,7 +2384,7 @@ update_matching_neighbors (void *cls, const GNUNET_HashCode * key, void *value) * @return GNUNET_YES to continue iteration, GNUNET_NO otherwise */ static int -add_distant_all_direct_neighbors (void *cls, const GNUNET_HashCode * key, +add_distant_all_direct_neighbors (void *cls, const struct GNUNET_HashCode * key, void *value) { struct DirectNeighbor *direct = (struct DirectNeighbor *) value; @@ -2837,7 +2837,7 @@ handle_dv_gossip_message (void *cls, const struct GNUNET_PeerIdentity *peer, * @return GNUNET_YES to continue iteration, GNUNET_NO otherwise */ static int -add_all_extended_peers (void *cls, const GNUNET_HashCode * key, void *value) +add_all_extended_peers (void *cls, const struct GNUNET_HashCode * key, void *value) { struct NeighborSendContext *send_context = (struct NeighborSendContext *) cls; struct DistantNeighbor *distant = (struct DistantNeighbor *) value; @@ -2875,7 +2875,7 @@ add_all_extended_peers (void *cls, const GNUNET_HashCode * key, void *value) * GNUNET_NO if not. */ static int -gossip_all_to_all_iterator (void *cls, const GNUNET_HashCode * key, +gossip_all_to_all_iterator (void *cls, const struct GNUNET_HashCode * key, void *abs_value) { struct DirectNeighbor *direct = abs_value; @@ -2922,7 +2922,7 @@ gossip_all_to_all (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) * @return GNUNET_YES to continue iteration, GNUNET_NO otherwise */ static int -add_all_direct_neighbors (void *cls, const GNUNET_HashCode * key, void *value) +add_all_direct_neighbors (void *cls, const struct GNUNET_HashCode * key, void *value) { struct DirectNeighbor *direct = (struct DirectNeighbor *) value; struct DirectNeighbor *to = (struct DirectNeighbor *) cls; @@ -3290,12 +3290,12 @@ run (void *cls, struct GNUNET_SERVER_Handle *server, neighbor_max_heap = GNUNET_CONTAINER_heap_create (GNUNET_CONTAINER_HEAP_ORDER_MAX); - direct_neighbors = GNUNET_CONTAINER_multihashmap_create (max_hosts); + direct_neighbors = GNUNET_CONTAINER_multihashmap_create (max_hosts, GNUNET_NO); extended_neighbors = - GNUNET_CONTAINER_multihashmap_create (max_table_size * 3); + GNUNET_CONTAINER_multihashmap_create (max_table_size * 3, GNUNET_NO); GNUNET_SERVER_add_handlers (server, plugin_handlers); - coreAPI = GNUNET_CORE_connect (cfg, 1, NULL, /* FIXME: anything we want to pass around? */ + coreAPI = GNUNET_CORE_connect (cfg, NULL, /* FIXME: anything we want to pass around? */ &core_init, &handle_core_connect, &handle_core_disconnect, NULL, GNUNET_NO, NULL, GNUNET_NO, core_handlers); diff --git a/src/dv/test_transport_api_dv.c b/src/dv/test_transport_api_dv.c deleted file mode 100644 index 6165a9d..0000000 --- a/src/dv/test_transport_api_dv.c +++ /dev/null @@ -1,1247 +0,0 @@ -/* - This file is part of GNUnet. - (C) 2009 Christian Grothoff (and other contributing authors) - - GNUnet is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published - by the Free Software Foundation; either version 3, or (at your - option) any later version. - - GNUnet is distributed in the hope that it will be useful, but - WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - General Public License for more details. - - You should have received a copy of the GNU General Public License - along with GNUnet; see the file COPYING. If not, write to the - Free Software Foundation, Inc., 59 Temple Place - Suite 330, - Boston, MA 02111-1307, USA. -*/ -/** - * @file dv/test_transport_api_dv.c - * @brief base testcase for testing distance vector transport - */ -#include "platform.h" -#include "gnunet_testing_lib.h" -#include "gnunet_core_service.h" - -#define VERBOSE 1 - -#define TEST_ALL GNUNET_NO - -/** - * How long until we fail the whole testcase? - */ -#define TEST_TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 600) - -/** - * How long until we give up on starting the peers? - */ -#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 500) - -#define DEFAULT_NUM_PEERS 4 - -#define DEFAULT_ADDITIONAL_MESSAGES 2 - -#define MAX_OUTSTANDING_CONNECTIONS 100 - -static float fail_percentage = 0.00; - -static int ok; - -static unsigned long long num_additional_messages; - -static unsigned long long num_peers; - -static unsigned int total_connections; - -static unsigned int failed_connections; - -static unsigned int total_server_connections; - -static unsigned int total_messages_received; - -static unsigned int total_other_expected_messages; - -static unsigned int temp_total_other_messages; - -static unsigned int total_other_messages; - -static unsigned int expected_messages; - -static unsigned int expected_connections; - -static unsigned long long peers_left; - -static struct GNUNET_TESTING_PeerGroup *pg; - -const struct GNUNET_CONFIGURATION_Handle *main_cfg; - -static GNUNET_SCHEDULER_TaskIdentifier die_task; - -static char *dotOutFileName = "topology.dot"; - -static FILE *dotOutFile; - -static char *blacklist_transports; - -static int transmit_ready_scheduled; - -static int transmit_ready_failed; - -static int transmit_ready_called; - -static enum GNUNET_TESTING_Topology topology; - -static enum GNUNET_TESTING_Topology blacklist_topology = GNUNET_TESTING_TOPOLOGY_NONE; /* Don't do any blacklisting */ - -static enum GNUNET_TESTING_Topology connection_topology = GNUNET_TESTING_TOPOLOGY_NONE; /* NONE actually means connect all allowed peers */ - -static enum GNUNET_TESTING_TopologyOption connect_topology_option = - GNUNET_TESTING_TOPOLOGY_OPTION_ALL; - -static double connect_topology_option_modifier = 0.0; - -static char *test_directory; - -struct GNUNET_CONTAINER_MultiHashMap *peer_daemon_hash; - -#define MTYPE 12345 - -GNUNET_NETWORK_STRUCT_BEGIN - -struct GNUNET_TestMessage -{ - /** - * Header of the message - */ - struct GNUNET_MessageHeader header; - - /** - * Unique identifier for this message. - */ - uint32_t uid; -}; -GNUNET_NETWORK_STRUCT_END - -struct PeerContext -{ - /* This is a linked list */ - struct PeerContext *next; - - /** - * Handle to the daemon - */ - struct GNUNET_TESTING_Daemon *daemon; - - /* Handle to the peer core */ - struct GNUNET_CORE_Handle *peer_handle; -}; - -static struct PeerContext *all_peers; - -struct TestMessageContext -{ - /* This is a linked list */ - struct TestMessageContext *next; - - /* Handle to the sending peer core */ - struct GNUNET_CORE_Handle *peer1handle; - - /* Handle to the receiving peer core */ - struct GNUNET_CORE_Handle *peer2handle; - - /* Handle to the sending peer daemon */ - struct GNUNET_TESTING_Daemon *peer1; - - /* Handle to the receiving peer daemon */ - struct GNUNET_TESTING_Daemon *peer2; - - /* Identifier for this message, so we don't disconnect other peers! */ - uint32_t uid; - - /* Task for disconnecting cores, allow task to be cancelled on shutdown */ - GNUNET_SCHEDULER_TaskIdentifier disconnect_task; -}; - -static struct TestMessageContext *test_messages; - -static struct TestMessageContext *other_test_messages; - -/** - * Check whether peers successfully shut down. - */ -void -shutdown_callback (void *cls, const char *emsg) -{ - if (emsg != NULL) - { -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Shutdown of peers failed!\n"); -#endif - if (ok == 0) - ok = 666; - } - else - { -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "All peers successfully shut down!\n"); -#endif - } -} - -static void -finish_testing (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - GNUNET_assert (pg != NULL); - struct PeerContext *peer_pos; - struct PeerContext *free_peer_pos; - struct TestMessageContext *pos; - struct TestMessageContext *free_pos; - - die_task = GNUNET_SCHEDULER_NO_TASK; -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Called finish testing, stopping daemons.\n"); -#endif - peer_pos = all_peers; - while (peer_pos != NULL) - { - if (peer_pos->peer_handle != NULL) - GNUNET_CORE_disconnect (peer_pos->peer_handle); - free_peer_pos = peer_pos; - peer_pos = peer_pos->next; - GNUNET_free (free_peer_pos); - } - all_peers = NULL; - - pos = test_messages; - while (pos != NULL) - { - if (pos->peer1handle != NULL) - { - GNUNET_CORE_disconnect (pos->peer1handle); - pos->peer1handle = NULL; - } - if (pos->peer2handle != NULL) - { - GNUNET_CORE_disconnect (pos->peer2handle); - pos->peer2handle = NULL; - } - free_pos = pos; - pos = pos->next; - if (free_pos->disconnect_task != GNUNET_SCHEDULER_NO_TASK) - { - GNUNET_SCHEDULER_cancel (free_pos->disconnect_task); - } - GNUNET_free (free_pos); - } - - pos = other_test_messages; - while (pos != NULL) - { - if (pos->peer1handle != NULL) - { - GNUNET_CORE_disconnect (pos->peer1handle); - pos->peer1handle = NULL; - } - if (pos->peer2handle != NULL) - { - GNUNET_CORE_disconnect (pos->peer2handle); - pos->peer2handle = NULL; - } - free_pos = pos; - pos = pos->next; - if (free_pos->disconnect_task != GNUNET_SCHEDULER_NO_TASK) - { - GNUNET_SCHEDULER_cancel (free_pos->disconnect_task); - } - GNUNET_free (free_pos); - } -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "transmit_ready's scheduled %d, failed %d, transmit_ready's called %d\n", - transmit_ready_scheduled, transmit_ready_failed, - transmit_ready_called); -#endif - -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Calling daemons_stop\n"); -#endif - GNUNET_TESTING_daemons_stop (pg, TIMEOUT, &shutdown_callback, NULL); -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "daemons_stop finished\n"); -#endif - if (dotOutFile != NULL) - { - FPRINTF (dotOutFile, "%s", "}"); - FCLOSE (dotOutFile); - } - - ok = 0; -} - - -static void -disconnect_cores (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - struct TestMessageContext *pos = cls; - - /* Disconnect from the respective cores */ -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Disconnecting from peer 1 `%4s'\n", - GNUNET_i2s (&pos->peer1->id)); -#endif - if (pos->peer1handle != NULL) - GNUNET_CORE_disconnect (pos->peer1handle); -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Disconnecting from peer 2 `%4s'\n", - GNUNET_i2s (&pos->peer2->id)); -#endif - if (pos->peer2handle != NULL) - GNUNET_CORE_disconnect (pos->peer2handle); - /* Set handles to NULL so test case can be ended properly */ - pos->peer1handle = NULL; - pos->peer2handle = NULL; - pos->disconnect_task = GNUNET_SCHEDULER_NO_TASK; - /* Decrement total connections so new can be established */ - total_server_connections -= 2; -} - -static void -end_badly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - char *msg = cls; - struct TestMessageContext *pos; - struct TestMessageContext *free_pos; - struct PeerContext *peer_pos; - struct PeerContext *free_peer_pos; - - die_task = GNUNET_SCHEDULER_NO_TASK; - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "End badly was called (%s)... stopping daemons.\n", msg); - - peer_pos = all_peers; - while (peer_pos != NULL) - { - if (peer_pos->peer_handle != NULL) - GNUNET_CORE_disconnect (peer_pos->peer_handle); - free_peer_pos = peer_pos; - peer_pos = peer_pos->next; - GNUNET_free (free_peer_pos); - } - all_peers = NULL; - - pos = test_messages; - while (pos != NULL) - { - if (pos->peer1handle != NULL) - { - GNUNET_CORE_disconnect (pos->peer1handle); - pos->peer1handle = NULL; - } - if (pos->peer2handle != NULL) - { - GNUNET_CORE_disconnect (pos->peer2handle); - pos->peer2handle = NULL; - } - free_pos = pos; - pos = pos->next; - GNUNET_free (free_pos); - } - - pos = other_test_messages; - while (pos != NULL) - { - if (pos->peer1handle != NULL) - { - GNUNET_CORE_disconnect (pos->peer1handle); - pos->peer1handle = NULL; - } - if (pos->peer2handle != NULL) - { - GNUNET_CORE_disconnect (pos->peer2handle); - pos->peer2handle = NULL; - } - free_pos = pos; - pos = pos->next; - if (free_pos->disconnect_task != GNUNET_SCHEDULER_NO_TASK) - { - GNUNET_SCHEDULER_cancel (free_pos->disconnect_task); - } - GNUNET_free (free_pos); - } - - if (pg != NULL) - { - GNUNET_TESTING_daemons_stop (pg, TIMEOUT, &shutdown_callback, NULL); - ok = 7331; /* Opposite of leet */ - } - else - ok = 401; /* Never got peers started */ - - if (dotOutFile != NULL) - { - FPRINTF (dotOutFile, "%s", "}"); - FCLOSE (dotOutFile); - } -} - -static void -send_other_messages (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc); - -/** - * Get distance information from 'atsi'. - * - * @param atsi performance data - * @return connected transport distance - */ -static uint32_t -get_atsi_distance (const struct GNUNET_ATS_Information *atsi, - unsigned int atsi_count) -{ - unsigned int i; - - for (i = 0; i < atsi_count; i++) - { - if (ntohl (atsi->type) == GNUNET_ATS_QUALITY_NET_DISTANCE) - return ntohl (atsi->value); - } - - GNUNET_break (0); - /* FIXME: we do not have distance data? Assume direct neighbor. */ - return 1; -} - - -static int -process_mtype (void *cls, const struct GNUNET_PeerIdentity *peer, - const struct GNUNET_MessageHeader *message, - const struct GNUNET_ATS_Information *atsi, - unsigned int atsi_count) -{ - struct TestMessageContext *pos = cls; - struct GNUNET_TestMessage *msg = (struct GNUNET_TestMessage *) message; - -#if VERBOSE - uint32_t distance; -#endif - if (pos->uid != ntohl (msg->uid)) - return GNUNET_OK; - -#if VERBOSE - distance = get_atsi_distance (atsi, atsi_count); -#endif - GNUNET_assert (0 == - memcmp (peer, &pos->peer1->id, - sizeof (struct GNUNET_PeerIdentity))); - if (total_other_expected_messages == 0) - { - total_messages_received++; -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Received message from `%4s', type %d, uid %u, distance %u.\n", - GNUNET_i2s (peer), ntohs (message->type), ntohl (msg->uid), - distance); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Total messages received %d, expected %d.\n", - total_messages_received, expected_messages); -#endif - } - else - { - total_other_messages++; -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Received message from `%4s', type %d, uid %u, distance %u.\n", - GNUNET_i2s (peer), ntohs (message->type), ntohl (msg->uid), - distance); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Total OTHER messages received %d, expected %d.\n", - total_other_messages, total_other_expected_messages); -#endif - } - - if ((total_messages_received == expected_messages) && - (total_other_messages == 0)) - { - GNUNET_SCHEDULER_cancel (die_task); -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Scheduling timeout from DV connections.\n"); -#endif - die_task = - GNUNET_SCHEDULER_add_delayed (TEST_TIMEOUT, &end_badly, - "waiting for DV peers to connect!"); - } - else if ((total_other_expected_messages > 0) && - (total_other_messages == total_other_expected_messages)) - { - GNUNET_SCHEDULER_cancel (die_task); - die_task = GNUNET_SCHEDULER_add_now (&finish_testing, NULL); - } - else - { - pos->disconnect_task = GNUNET_SCHEDULER_add_now (&disconnect_cores, pos); - } - - return GNUNET_OK; -} - -static size_t -transmit_ready (void *cls, size_t size, void *buf) -{ - struct GNUNET_TestMessage *m; - struct TestMessageContext *pos = cls; - - GNUNET_assert (buf != NULL); - m = (struct GNUNET_TestMessage *) buf; - m->header.type = htons (MTYPE); - m->header.size = htons (sizeof (struct GNUNET_TestMessage)); - m->uid = htonl (pos->uid); - transmit_ready_called++; -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "transmit ready for peer %s\ntransmit_ready's scheduled %d, transmit_ready's called %d\n", - GNUNET_i2s (&pos->peer1->id), transmit_ready_scheduled, - transmit_ready_called); -#endif - return sizeof (struct GNUNET_TestMessage); -} - - -static struct GNUNET_CORE_MessageHandler no_handlers[] = { - {NULL, 0, 0} -}; - -static struct GNUNET_CORE_MessageHandler handlers[] = { - {&process_mtype, MTYPE, sizeof (struct GNUNET_TestMessage)}, - {NULL, 0, 0} -}; - -/** - * Notify of all peer1's peers, once peer 2 is found, schedule connect - * to peer two for message send. - * - * @param cls closure - * @param peer peer identity this notification is about - * @param atsi performance data for the connection - * @param atsi_count number of ATS information included - */ -static void -connect_notify_peer2 (void *cls, const struct GNUNET_PeerIdentity *peer, - const struct GNUNET_ATS_Information *atsi, - unsigned int atsi_count) -{ - struct TestMessageContext *pos = cls; - - if (0 == memcmp (&pos->peer1->id, peer, sizeof (struct GNUNET_PeerIdentity))) - { -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Core connection from `%s' to `%4s' verfied, sending message!\n", - GNUNET_i2s (&pos->peer2->id), GNUNET_h2s (&peer->hashPubKey)); -#endif - if (NULL == - GNUNET_CORE_notify_transmit_ready (pos->peer1handle, GNUNET_YES, 0, - TIMEOUT, &pos->peer2->id, - sizeof (struct GNUNET_TestMessage), - &transmit_ready, pos)) - { - /* This probably shouldn't happen, but it does (timing issue?) */ - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "RECEIVED NULL when asking core (1) for transmission to peer `%4s'\n", - GNUNET_i2s (&pos->peer2->id)); - transmit_ready_failed++; - total_other_expected_messages--; - } - else - { - transmit_ready_scheduled++; - } - } -} - -static void -init_notify_peer2 (void *cls, struct GNUNET_CORE_Handle *server, - const struct GNUNET_PeerIdentity *my_identity) -{ -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Core connection to `%4s' established, awaiting connections.\n", - GNUNET_i2s (my_identity)); -#endif - total_server_connections++; -} - -/** - * Notify of all peer1's peers, once peer 2 is found, schedule connect - * to peer two for message send. - * - * @param cls closure - * @param peer peer identity this notification is about - * @param atsi performance data for the connection - * @param atsi_count number of atsi datums - */ -static void -connect_notify_peer1 (void *cls, const struct GNUNET_PeerIdentity *peer, - const struct GNUNET_ATS_Information *atsi, - unsigned int atsi_count) -{ - struct TestMessageContext *pos = cls; - - if (0 == memcmp (&pos->peer2->id, peer, sizeof (struct GNUNET_PeerIdentity))) - { -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Core connection from `%s' to `%4s' verified.\n", - GNUNET_i2s (&pos->peer1->id), GNUNET_h2s (&peer->hashPubKey)); -#endif - /* - * Connect to the receiving peer - */ - pos->peer2handle = - GNUNET_CORE_connect (pos->peer2->cfg, 1, pos, &init_notify_peer2, - &connect_notify_peer2, NULL, NULL, GNUNET_YES, - NULL, GNUNET_YES, handlers); - } -} - -static void -init_notify_peer1 (void *cls, struct GNUNET_CORE_Handle *server, - const struct GNUNET_PeerIdentity *my_identity) -{ - total_server_connections++; -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Core connection to `%4s' established, awaiting connections...\n", - GNUNET_i2s (my_identity)); -#endif -} - - -static void -send_test_messages (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - struct TestMessageContext *pos = cls; - - if (((tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN) != 0) || (cls == NULL)) - return; - - if (die_task == GNUNET_SCHEDULER_NO_TASK) - { - die_task = - GNUNET_SCHEDULER_add_delayed (TEST_TIMEOUT, &end_badly, - "from create topology (timeout)"); - } - - if (total_server_connections >= MAX_OUTSTANDING_CONNECTIONS) - { - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply - (GNUNET_TIME_UNIT_SECONDS, 1), - &send_test_messages, pos); - return; /* Otherwise we'll double schedule messages here! */ - } -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Attempting to send test message from %s to %s\n", - pos->peer1->shortname, pos->peer2->shortname); -#endif - /* - * Connect to the sending peer - */ - pos->peer1handle = - GNUNET_CORE_connect (pos->peer1->cfg, 1, pos, &init_notify_peer1, - &connect_notify_peer1, NULL, NULL, GNUNET_NO, NULL, - GNUNET_NO, no_handlers); - - GNUNET_assert (pos->peer1handle != NULL); - - if (total_server_connections < MAX_OUTSTANDING_CONNECTIONS) - { - GNUNET_SCHEDULER_add_now (&send_test_messages, pos->next); - } - else - { - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply - (GNUNET_TIME_UNIT_SECONDS, 1), - &send_test_messages, pos->next); - } -} - -static void -send_other_messages (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - struct TestMessageContext *pos; - struct TestMessageContext *free_pos; - struct PeerContext *peer_pos; - -#if TEST_ALL - struct PeerContext *inner_peer_pos; - struct TestMessageContext *temp_context; -#endif - peer_pos = all_peers; - while (peer_pos != NULL) - { - if (peer_pos->peer_handle != NULL) - { - GNUNET_CORE_disconnect (peer_pos->peer_handle); - peer_pos->peer_handle = NULL; - } -#if TEST_ALL - inner_peer_pos = all_peers; - while (inner_peer_pos != NULL) - { - if (inner_peer_pos != peer_pos) - { - temp_total_other_messages++; - temp_context = GNUNET_malloc (sizeof (struct TestMessageContext)); - temp_context->peer1 = peer_pos->daemon; - temp_context->peer2 = inner_peer_pos->daemon; - temp_context->next = other_test_messages; - temp_context->uid = total_connections + temp_total_other_messages; - temp_context->disconnect_task = GNUNET_SCHEDULER_NO_TASK; - other_test_messages = temp_context; - } - inner_peer_pos = inner_peer_pos->next; - } -#endif - peer_pos = peer_pos->next; - } - all_peers = NULL; - - pos = test_messages; - while (pos != NULL) - { - if (pos->peer1handle != NULL) - { - GNUNET_CORE_disconnect (pos->peer1handle); - pos->peer1handle = NULL; - } - if (pos->peer2handle != NULL) - { - GNUNET_CORE_disconnect (pos->peer2handle); - pos->peer2handle = NULL; - } - free_pos = pos; - pos = pos->next; - if (free_pos->disconnect_task != GNUNET_SCHEDULER_NO_TASK) - { - GNUNET_SCHEDULER_cancel (free_pos->disconnect_task); - } - GNUNET_free (free_pos); - } - test_messages = NULL; - - total_other_expected_messages = temp_total_other_messages; - if (total_other_expected_messages == 0) - { - GNUNET_SCHEDULER_add_now (&end_badly, - "send_other_messages had 0 messages to send, no DV connections made!"); - } -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Preparing to send %d other test messages\n", - total_other_expected_messages); -#endif - - GNUNET_SCHEDULER_add_now (&send_test_messages, other_test_messages); - if (GNUNET_SCHEDULER_NO_TASK != die_task) - GNUNET_SCHEDULER_cancel (die_task); - die_task = - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply - (GNUNET_TIME_UNIT_SECONDS, 250), &end_badly, - "from send_other_messages"); -} - -static void -topology_callback (void *cls, const struct GNUNET_PeerIdentity *first, - const struct GNUNET_PeerIdentity *second, uint32_t distance, - const struct GNUNET_CONFIGURATION_Handle *first_cfg, - const struct GNUNET_CONFIGURATION_Handle *second_cfg, - struct GNUNET_TESTING_Daemon *first_daemon, - struct GNUNET_TESTING_Daemon *second_daemon, - const char *emsg) -{ - struct TestMessageContext *temp_context; - - if (emsg == NULL) - { - total_connections++; -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "connected peer %s to peer %s, distance %u\n", - first_daemon->shortname, second_daemon->shortname, distance); -#endif - temp_context = GNUNET_malloc (sizeof (struct TestMessageContext)); - temp_context->peer1 = first_daemon; - temp_context->peer2 = second_daemon; - temp_context->next = test_messages; - temp_context->uid = total_connections; - temp_context->disconnect_task = GNUNET_SCHEDULER_NO_TASK; - test_messages = temp_context; - expected_messages++; - } -#if VERBOSE - else - { - failed_connections++; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Failed to connect peer %s to peer %s with error :\n%s\n", - first_daemon->shortname, second_daemon->shortname, emsg); - } -#endif - - if (total_connections == expected_connections) - { -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Created %u total connections, which is our target number! Calling send messages.\n", - total_connections); -#endif - if (GNUNET_SCHEDULER_NO_TASK != die_task) - GNUNET_SCHEDULER_cancel (die_task); - die_task = GNUNET_SCHEDULER_NO_TASK; - GNUNET_SCHEDULER_add_now (&send_test_messages, test_messages); - } - else if (total_connections + failed_connections == expected_connections) - { - if (failed_connections < - (unsigned int) (fail_percentage * total_connections)) - { - GNUNET_SCHEDULER_cancel (die_task); - die_task = GNUNET_SCHEDULER_NO_TASK; - /* FIXME: ret value!? */ GNUNET_SCHEDULER_add_now (&send_test_messages, - test_messages); - } - else - { - if (die_task != GNUNET_SCHEDULER_NO_TASK) - GNUNET_SCHEDULER_cancel (die_task); - die_task = - GNUNET_SCHEDULER_add_now (&end_badly, - "from topology_callback (too many failed connections)"); - } - } - else - { -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Have %d total connections, %d failed connections, Want %d (at least %d)\n", - total_connections, failed_connections, expected_connections, - expected_connections - - (unsigned int) (fail_percentage * expected_connections)); -#endif - } -} - - -/** - * Method called whenever a given peer connects. - * - * @param cls closure - * @param peer peer identity this notification is about - * @param atsi performance data about this peer's connection - * @param atsi_count number of atsi datums - * - */ -static void -all_connect_handler (void *cls, const struct GNUNET_PeerIdentity *peer, - const struct GNUNET_ATS_Information *atsi, - unsigned int atsi_count) -{ - struct GNUNET_TESTING_Daemon *d = cls; - struct GNUNET_TESTING_Daemon *second_daemon; - char *second_shortname; - -#if !TEST_ALL - struct TestMessageContext *temp_context; -#endif - uint32_t distance; - - if (0 == memcmp (&d->id, peer, sizeof (struct GNUNET_PeerIdentity))) - return; - second_shortname = GNUNET_strdup (GNUNET_i2s (peer)); - distance = get_atsi_distance (atsi, atsi_count); - -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "connected peer %s to peer %s, distance %u\n", d->shortname, - second_shortname, distance); -#endif - - second_daemon = - GNUNET_CONTAINER_multihashmap_get (peer_daemon_hash, &peer->hashPubKey); - - if (second_daemon == NULL) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Couldn't find second peer!\n"); - GNUNET_free (second_shortname); - return; - } -#if !TEST_ALL - if (distance > 1) - { - temp_total_other_messages++; - temp_context = GNUNET_malloc (sizeof (struct TestMessageContext)); - temp_context->peer1 = d; - temp_context->peer2 = second_daemon; - temp_context->next = other_test_messages; - temp_context->uid = total_connections + temp_total_other_messages; - temp_context->disconnect_task = GNUNET_SCHEDULER_NO_TASK; - other_test_messages = temp_context; - } -#endif - - if (dotOutFile != NULL) - { - if (distance == 1) - FPRINTF (dotOutFile, "\tn%s -- n%s;\n", d->shortname, second_shortname); - else if (distance == 2) - FPRINTF (dotOutFile, "\tn%s -- n%s [color=blue];\n", d->shortname, - second_shortname); - else if (distance == 3) - FPRINTF (dotOutFile, "\tn%s -- n%s [color=red];\n", d->shortname, - second_shortname); - else if (distance == 4) - FPRINTF (dotOutFile, "\tn%s -- n%s [color=green];\n", d->shortname, - second_shortname); - else - FPRINTF (dotOutFile, "\tn%s -- n%s [color=brown];\n", d->shortname, - second_shortname); - } - GNUNET_free (second_shortname); - - if (temp_total_other_messages == num_additional_messages) - { - /* FIXME: ret value!? */ GNUNET_SCHEDULER_add_now (&send_other_messages, - NULL); - } -} - -static void -peers_started_callback (void *cls, const struct GNUNET_PeerIdentity *id, - const struct GNUNET_CONFIGURATION_Handle *cfg, - struct GNUNET_TESTING_Daemon *d, const char *emsg) -{ - struct PeerContext *new_peer; - - if (emsg != NULL) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Failed to start daemon with error: `%s'\n", emsg); - return; - } - GNUNET_assert (id != NULL); -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Started daemon %llu out of %llu\n", - (num_peers - peers_left) + 1, num_peers); -#endif - GNUNET_assert (GNUNET_SYSERR != - GNUNET_CONTAINER_multihashmap_put (peer_daemon_hash, - &id->hashPubKey, d, - GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY)); - - new_peer = GNUNET_malloc (sizeof (struct PeerContext)); - new_peer->peer_handle = - GNUNET_CORE_connect (cfg, 1, d, NULL, &all_connect_handler, NULL, NULL, - GNUNET_NO, NULL, GNUNET_NO, no_handlers); - new_peer->daemon = d; - new_peer->next = all_peers; - all_peers = new_peer; - peers_left--; - - if (peers_left == 0) - { -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "All %d daemons started, now creating topology!\n", num_peers); -#endif - GNUNET_SCHEDULER_cancel (die_task); - die_task = GNUNET_SCHEDULER_NO_TASK; - expected_connections = -1; - if ((pg != NULL) && (peers_left == 0)) - { - expected_connections = - GNUNET_TESTING_connect_topology (pg, connection_topology, - connect_topology_option, - connect_topology_option_modifier, - TIMEOUT, 12, NULL, NULL); -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Have %d expected connections\n", - expected_connections); -#endif - } - - if (expected_connections == GNUNET_SYSERR) - { - die_task = - GNUNET_SCHEDULER_add_now (&end_badly, - "from connect topology (bad return)"); - } - else - { - /* Set up task in case topology creation doesn't finish - * within a reasonable amount of time */ - die_task = - GNUNET_SCHEDULER_add_delayed (TEST_TIMEOUT, &end_badly, - "from connect topology (timeout)"); - } - ok = 0; - } -} - -/** - * Callback indicating that the hostkey was created for a peer. - * - * @param cls NULL - * @param id the peer identity - * @param d the daemon handle (pretty useless at this point, remove?) - * @param emsg non-null on failure - */ -static void -hostkey_callback (void *cls, const struct GNUNET_PeerIdentity *id, - struct GNUNET_TESTING_Daemon *d, const char *emsg) -{ - if (emsg != NULL) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Hostkey callback received error: %s\n", emsg); - } - -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Hostkey created for peer `%s'\n", - GNUNET_i2s (id)); -#endif - peers_left--; - if (peers_left == 0) - { -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "All %d hostkeys created, now creating topology!\n", num_peers); -#endif - if (GNUNET_SCHEDULER_NO_TASK != die_task) - { - GNUNET_SCHEDULER_cancel (die_task); - die_task = GNUNET_SCHEDULER_NO_TASK; - } - /* create topology */ - peers_left = num_peers; /* Reset counter */ - if (GNUNET_TESTING_create_topology - (pg, topology, blacklist_topology, - blacklist_transports) != GNUNET_SYSERR) - { -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Topology set up, now starting peers!\n"); -#endif - GNUNET_TESTING_daemons_continue_startup (pg); - /* Set up task in case topology creation doesn't finish - * within a reasonable amount of time */ - die_task = - GNUNET_SCHEDULER_add_delayed (TEST_TIMEOUT, &end_badly, - "from continue startup (timeout)"); - } - else - { - die_task = - GNUNET_SCHEDULER_add_now (&end_badly, - "from create topology (bad return)"); - } - ok = 0; - } -} - -static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) -{ - char *topology_str; - char *connect_topology_str; - char *blacklist_topology_str; - char *connect_topology_option_str; - char *connect_topology_option_modifier_string; - - ok = 1; - - dotOutFile = fopen (dotOutFileName, "w"); - if (dotOutFile != NULL) - { - FPRINTF (dotOutFile, "%s", "strict graph G {\n"); - } - -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Starting daemons based on config file %s\n", cfgfile); -#endif - - if (GNUNET_YES != - GNUNET_CONFIGURATION_get_value_string (cfg, "paths", "servicehome", - &test_directory)) - { - ok = 404; - return; - } - - if ((GNUNET_YES == - GNUNET_CONFIGURATION_get_value_string (cfg, "testing", "topology", - &topology_str)) && - (GNUNET_NO == GNUNET_TESTING_topology_get (&topology, topology_str))) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Invalid topology `%s' given for section %s option %s\n", - topology_str, "TESTING", "TOPOLOGY"); - topology = GNUNET_TESTING_TOPOLOGY_CLIQUE; /* Defaults to NONE, so set better default here */ - } - - if ((GNUNET_YES == - GNUNET_CONFIGURATION_get_value_string (cfg, "testing", - "connect_topology", - &connect_topology_str)) && - (GNUNET_NO == - GNUNET_TESTING_topology_get (&connection_topology, - connect_topology_str))) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Invalid connect topology `%s' given for section %s option %s\n", - connect_topology_str, "TESTING", "CONNECT_TOPOLOGY"); - } - GNUNET_free_non_null (connect_topology_str); - if ((GNUNET_YES == - GNUNET_CONFIGURATION_get_value_string (cfg, "testing", - "connect_topology_option", - &connect_topology_option_str)) && - (GNUNET_NO == - GNUNET_TESTING_topology_option_get (&connect_topology_option, - connect_topology_option_str))) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Invalid connect topology option `%s' given for section %s option %s\n", - connect_topology_option_str, "TESTING", - "CONNECT_TOPOLOGY_OPTION"); - connect_topology_option = GNUNET_TESTING_TOPOLOGY_OPTION_ALL; /* Defaults to NONE, set to ALL */ - } - GNUNET_free_non_null (connect_topology_option_str); - if (GNUNET_YES == - GNUNET_CONFIGURATION_get_value_string (cfg, "testing", - "connect_topology_option_modifier", - &connect_topology_option_modifier_string)) - { - if (SSCANF - (connect_topology_option_modifier_string, "%lf", - &connect_topology_option_modifier) != 1) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - _ - ("Invalid value `%s' for option `%s' in section `%s': expected float\n"), - connect_topology_option_modifier_string, - "connect_topology_option_modifier", "TESTING"); - } - GNUNET_free (connect_topology_option_modifier_string); - } - - if (GNUNET_YES != - GNUNET_CONFIGURATION_get_value_string (cfg, "testing", - "blacklist_transports", - &blacklist_transports)) - blacklist_transports = NULL; - - if ((GNUNET_YES == - GNUNET_CONFIGURATION_get_value_string (cfg, "testing", - "blacklist_topology", - &blacklist_topology_str)) && - (GNUNET_NO == - GNUNET_TESTING_topology_get (&blacklist_topology, - blacklist_topology_str))) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Invalid topology `%s' given for section %s option %s\n", - topology_str, "TESTING", "BLACKLIST_TOPOLOGY"); - } - GNUNET_free_non_null (topology_str); - GNUNET_free_non_null (blacklist_topology_str); - if (GNUNET_SYSERR == - GNUNET_CONFIGURATION_get_value_number (cfg, "testing", "num_peers", - &num_peers)) - num_peers = DEFAULT_NUM_PEERS; - - if (GNUNET_SYSERR == - GNUNET_CONFIGURATION_get_value_number (cfg, "testing", - "additional_messages", - &num_additional_messages)) - num_additional_messages = DEFAULT_ADDITIONAL_MESSAGES; - - main_cfg = cfg; - - GNUNET_assert (num_peers > 0 && num_peers < (unsigned int) -1); - peers_left = num_peers; - - /* Set up a task to end testing if peer start fails */ - die_task = - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply - (GNUNET_TIME_UNIT_MINUTES, 5), &end_badly, - "didn't start all daemons in reasonable amount of time!!!"); - - peer_daemon_hash = GNUNET_CONTAINER_multihashmap_create (peers_left); - pg = GNUNET_TESTING_daemons_start (cfg, peers_left, /* Total number of peers */ - peers_left, /* Number of outstanding connections */ - peers_left, /* Number of parallel ssh connections, or peers being started at once */ - TIMEOUT, &hostkey_callback, NULL, - &peers_started_callback, NULL, - &topology_callback, NULL, NULL); - -} - -static int -check () -{ - int ret; - - char *const argv[] = { "test-transport-dv", - "-c", - "test_transport_dv_data.conf", -#if VERBOSE - "-L", "DEBUG", -#endif - NULL - }; - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - ret = - GNUNET_PROGRAM_run ((sizeof (argv) / sizeof (char *)) - 1, argv, - "test-transport-dv", "nohelp", options, &run, &ok); - if (ret != GNUNET_OK) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "`test-transport-dv': Failed with error code %d\n", ret); - } - return ok; -} - -int -main (int argc, char *argv[]) -{ - int ret; - - GNUNET_log_setup ("test-transport-dv", -#if VERBOSE - "DEBUG", -#else - "WARNING", -#endif - NULL); - ret = check (); - /** - * Need to remove base directory, subdirectories taken care - * of by the testing framework. - */ - if (GNUNET_DISK_directory_remove (test_directory) != GNUNET_OK) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Failed to remove testing directory %s\n", test_directory); - } - return ret; -} - -/* end of test_transport_api_dv.c */ diff --git a/src/dv/test_transport_dv_data.conf b/src/dv/test_transport_dv_data.conf index 80eb873..8232461 100644 --- a/src/dv/test_transport_dv_data.conf +++ b/src/dv/test_transport_dv_data.conf @@ -1,12 +1,10 @@ [PATHS] SERVICEHOME = /tmp/test-gnunet-dv-testing/ -DEFAULTCONFIG = test_transport_dv_data.conf [resolver] PORT = 2564 [transport] -DEBUG = YES PORT = 2565 PLUGINS = tcp dv BLACKLIST_FILE = $SERVICEHOME/blacklist @@ -35,11 +33,9 @@ PORT = 2570 [dv] AUTOSTART = YES -DEBUG = NO ACCEPT_FROM6 = ::1; ACCEPT_FROM = 127.0.0.1; BINARY = gnunet-service-dv -CONFIG = $DEFAULTCONFIG HOME = $SERVICEHOME HOSTNAME = localhost PORT = 2571 @@ -47,14 +43,13 @@ PORT = 2571 [testing] NUM_PEERS = 3 ADDITIONAL_MESSAGES = 10 -DEBUG = NO WEAKRANDOM = YES TOPOLOGY = CLIQUE CONNECT_TOPOLOGY = LINE BLACKLIST_TOPOLOGY = LINE BLACKLIST_TRANSPORTS = tcp F2F = YES -HOSTKEYSFILE = ../../contrib/testing_hostkeys.dat +HOSTKEYSFILE = ${DATADIR}/testing_hostkeys.dat [fs] AUTOSTART = NO diff --git a/src/exit/Makefile.am b/src/exit/Makefile.am index 5a047a1..eb2a7a9 100644 --- a/src/exit/Makefile.am +++ b/src/exit/Makefile.am @@ -1,7 +1,8 @@ INCLUDES = -I$(top_srcdir)/src/include if MINGW - WINFLAGS = -Wl,--no-undefined -Wl,--export-all-symbols + WINFLAGS = -Wl,--no-undefined, --export-all-symbols + EXITBIN = gnunet-helper-exit endif if USE_COVERAGE @@ -10,6 +11,8 @@ endif pkgcfgdir= $(pkgdatadir)/config.d/ +libexecdir= $(pkglibdir)/libexec/ + plugindir = $(libdir)/gnunet dist_pkgcfg_DATA = \ @@ -18,26 +21,38 @@ dist_pkgcfg_DATA = \ if LINUX EXITBIN = gnunet-helper-exit install-exec-hook: - $(SUDO_BINARY) chown root:root $(bindir)/gnunet-helper-exit || true - $(SUDO_BINARY) chmod u+s $(bindir)/gnunet-helper-exit || true + $(top_srcdir)/src/exit/install-exit-helper.sh $(libexecdir) $(SUDO_BINARY) || true else install-exec-hook: endif -bin_PROGRAMS = \ - gnunet-daemon-exit $(EXITBIN) - - -gnunet_helper_exit_SOURCES = \ - gnunet-helper-exit.c +libexec_PROGRAMS = \ + gnunet-daemon-exit \ + $(EXITBIN) +if MINGW + gnunet_helper_exit_LDFLAGS = \ + -no-undefined -Wl,--export-all-symbols + + gnunet_helper_exit_LDADD = \ + -lsetupapi -lnewdev -lshell32 -liconv -lstdc++ \ + -lcomdlg32 -lgdi32 -liphlpapi + + gnunet_helper_exit_SOURCES = \ + gnunet-helper-exit-windows.c +else + gnunet_helper_exit_SOURCES = \ + gnunet-helper-exit.c +endif gnunet_daemon_exit_SOURCES = \ gnunet-daemon-exit.c exit.h gnunet_daemon_exit_LDADD = \ + $(top_builddir)/src/dns/libgnunetdnsstub.la \ $(top_builddir)/src/core/libgnunetcore.la \ $(top_builddir)/src/statistics/libgnunetstatistics.la \ $(top_builddir)/src/tun/libgnunettun.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/mesh/libgnunetmesh.la \ + $(top_builddir)/src/regex/libgnunetregex.la \ $(GN_LIBINTL) diff --git a/src/exit/Makefile.in b/src/exit/Makefile.in index 0caead9..9bbc0f4 100644 --- a/src/exit/Makefile.in +++ b/src/exit/Makefile.in @@ -1,9 +1,9 @@ -# Makefile.in generated by automake 1.11.1 from Makefile.am. +# Makefile.in generated by automake 1.11.6 from Makefile.am. # @configure_input@ # Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, -# 2003, 2004, 2005, 2006, 2007, 2008, 2009 Free Software Foundation, -# Inc. +# 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Free Software +# Foundation, Inc. # This Makefile.in is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. @@ -17,6 +17,23 @@ VPATH = @srcdir@ +am__make_dryrun = \ + { \ + am__dry=no; \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + echo 'am--echo: ; @echo "AM" OK' | $(MAKE) -f - 2>/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } pkgdatadir = $(datadir)/@PACKAGE@ pkgincludedir = $(includedir)/@PACKAGE@ pkglibdir = $(libdir)/@PACKAGE@ @@ -36,21 +53,22 @@ POST_UNINSTALL = : build_triplet = @build@ host_triplet = @host@ target_triplet = @target@ -bin_PROGRAMS = gnunet-daemon-exit$(EXEEXT) $(am__EXEEXT_1) +libexec_PROGRAMS = gnunet-daemon-exit$(EXEEXT) $(am__EXEEXT_1) subdir = src/exit DIST_COMMON = $(dist_pkgcfg_DATA) $(srcdir)/Makefile.am \ $(srcdir)/Makefile.in ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 am__aclocal_m4_deps = $(top_srcdir)/m4/absolute-header.m4 \ $(top_srcdir)/m4/align.m4 $(top_srcdir)/m4/argz.m4 \ - $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/iconv.m4 \ - $(top_srcdir)/m4/lib-ld.m4 $(top_srcdir)/m4/lib-link.m4 \ - $(top_srcdir)/m4/lib-prefix.m4 $(top_srcdir)/m4/libcurl.m4 \ - $(top_srcdir)/m4/libgcrypt.m4 $(top_srcdir)/m4/libtool.m4 \ - $(top_srcdir)/m4/libunistring.m4 $(top_srcdir)/m4/ltdl.m4 \ - $(top_srcdir)/m4/ltoptions.m4 $(top_srcdir)/m4/ltsugar.m4 \ - $(top_srcdir)/m4/ltversion.m4 $(top_srcdir)/m4/lt~obsolete.m4 \ - $(top_srcdir)/m4/nls.m4 $(top_srcdir)/m4/po.m4 \ + $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/glib-2.0.m4 \ + $(top_srcdir)/m4/iconv.m4 $(top_srcdir)/m4/lib-ld.m4 \ + $(top_srcdir)/m4/lib-link.m4 $(top_srcdir)/m4/lib-prefix.m4 \ + $(top_srcdir)/m4/libcurl.m4 $(top_srcdir)/m4/libgcrypt.m4 \ + $(top_srcdir)/m4/libtool.m4 $(top_srcdir)/m4/libunistring.m4 \ + $(top_srcdir)/m4/ltdl.m4 $(top_srcdir)/m4/ltoptions.m4 \ + $(top_srcdir)/m4/ltsugar.m4 $(top_srcdir)/m4/ltversion.m4 \ + $(top_srcdir)/m4/lt~obsolete.m4 $(top_srcdir)/m4/nls.m4 \ + $(top_srcdir)/m4/pkg.m4 $(top_srcdir)/m4/po.m4 \ $(top_srcdir)/m4/progtest.m4 $(top_srcdir)/acinclude.m4 \ $(top_srcdir)/configure.ac am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ @@ -59,25 +77,37 @@ mkinstalldirs = $(install_sh) -d CONFIG_HEADER = $(top_builddir)/gnunet_config.h CONFIG_CLEAN_FILES = CONFIG_CLEAN_VPATH_FILES = +@LINUX_FALSE@@MINGW_TRUE@am__EXEEXT_1 = gnunet-helper-exit$(EXEEXT) @LINUX_TRUE@am__EXEEXT_1 = gnunet-helper-exit$(EXEEXT) -am__installdirs = "$(DESTDIR)$(bindir)" "$(DESTDIR)$(pkgcfgdir)" -PROGRAMS = $(bin_PROGRAMS) +am__installdirs = "$(DESTDIR)$(libexecdir)" "$(DESTDIR)$(pkgcfgdir)" +PROGRAMS = $(libexec_PROGRAMS) am_gnunet_daemon_exit_OBJECTS = gnunet-daemon-exit.$(OBJEXT) gnunet_daemon_exit_OBJECTS = $(am_gnunet_daemon_exit_OBJECTS) am__DEPENDENCIES_1 = gnunet_daemon_exit_DEPENDENCIES = \ + $(top_builddir)/src/dns/libgnunetdnsstub.la \ $(top_builddir)/src/core/libgnunetcore.la \ $(top_builddir)/src/statistics/libgnunetstatistics.la \ $(top_builddir)/src/tun/libgnunettun.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/mesh/libgnunetmesh.la \ + $(top_builddir)/src/regex/libgnunetregex.la \ $(am__DEPENDENCIES_1) -AM_V_lt = $(am__v_lt_$(V)) -am__v_lt_ = $(am__v_lt_$(AM_DEFAULT_VERBOSITY)) +AM_V_lt = $(am__v_lt_@AM_V@) +am__v_lt_ = $(am__v_lt_@AM_DEFAULT_V@) am__v_lt_0 = --silent -am_gnunet_helper_exit_OBJECTS = gnunet-helper-exit.$(OBJEXT) +am__gnunet_helper_exit_SOURCES_DIST = gnunet-helper-exit.c \ + gnunet-helper-exit-windows.c +@MINGW_FALSE@am_gnunet_helper_exit_OBJECTS = \ +@MINGW_FALSE@ gnunet-helper-exit.$(OBJEXT) +@MINGW_TRUE@am_gnunet_helper_exit_OBJECTS = \ +@MINGW_TRUE@ gnunet-helper-exit-windows.$(OBJEXT) gnunet_helper_exit_OBJECTS = $(am_gnunet_helper_exit_OBJECTS) -gnunet_helper_exit_LDADD = $(LDADD) +gnunet_helper_exit_DEPENDENCIES = +gnunet_helper_exit_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ + $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ + $(AM_CFLAGS) $(CFLAGS) $(gnunet_helper_exit_LDFLAGS) \ + $(LDFLAGS) -o $@ DEFAULT_INCLUDES = -I.@am__isrc@ -I$(top_builddir) depcomp = $(SHELL) $(top_srcdir)/depcomp am__depfiles_maybe = depfiles @@ -88,25 +118,30 @@ LTCOMPILE = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) \ $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) \ $(AM_CFLAGS) $(CFLAGS) -AM_V_CC = $(am__v_CC_$(V)) -am__v_CC_ = $(am__v_CC_$(AM_DEFAULT_VERBOSITY)) +AM_V_CC = $(am__v_CC_@AM_V@) +am__v_CC_ = $(am__v_CC_@AM_DEFAULT_V@) am__v_CC_0 = @echo " CC " $@; -AM_V_at = $(am__v_at_$(V)) -am__v_at_ = $(am__v_at_$(AM_DEFAULT_VERBOSITY)) +AM_V_at = $(am__v_at_@AM_V@) +am__v_at_ = $(am__v_at_@AM_DEFAULT_V@) am__v_at_0 = @ CCLD = $(CC) LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ $(AM_LDFLAGS) $(LDFLAGS) -o $@ -AM_V_CCLD = $(am__v_CCLD_$(V)) -am__v_CCLD_ = $(am__v_CCLD_$(AM_DEFAULT_VERBOSITY)) +AM_V_CCLD = $(am__v_CCLD_@AM_V@) +am__v_CCLD_ = $(am__v_CCLD_@AM_DEFAULT_V@) am__v_CCLD_0 = @echo " CCLD " $@; -AM_V_GEN = $(am__v_GEN_$(V)) -am__v_GEN_ = $(am__v_GEN_$(AM_DEFAULT_VERBOSITY)) +AM_V_GEN = $(am__v_GEN_@AM_V@) +am__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@) am__v_GEN_0 = @echo " GEN " $@; SOURCES = $(gnunet_daemon_exit_SOURCES) $(gnunet_helper_exit_SOURCES) DIST_SOURCES = $(gnunet_daemon_exit_SOURCES) \ - $(gnunet_helper_exit_SOURCES) + $(am__gnunet_helper_exit_SOURCES_DIST) +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac am__vpath_adj_setup = srcdirstrip=`echo "$(srcdir)" | sed 's|.|.|g'`; am__vpath_adj = case $$p in \ $(srcdir)/*) f=`echo "$$p" | sed "s|^$$srcdirstrip/||"`;; \ @@ -128,6 +163,12 @@ am__nobase_list = $(am__nobase_strip_setup); \ am__base_list = \ sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \ sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g' +am__uninstall_files_from_dir = { \ + test -z "$$files" \ + || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \ + || { echo " ( cd '$$dir' && rm -f" $$files ")"; \ + $(am__cd) "$$dir" && rm -f $$files; }; \ + } DATA = $(dist_pkgcfg_DATA) ETAGS = etags CTAGS = ctags @@ -167,6 +208,10 @@ EXEEXT = @EXEEXT@ EXT_LIBS = @EXT_LIBS@ EXT_LIB_PATH = @EXT_LIB_PATH@ FGREP = @FGREP@ +GLIB_CFLAGS = @GLIB_CFLAGS@ +GLIB_GENMARSHAL = @GLIB_GENMARSHAL@ +GLIB_LIBS = @GLIB_LIBS@ +GLIB_MKENUMS = @GLIB_MKENUMS@ GMSGFMT = @GMSGFMT@ GMSGFMT_015 = @GMSGFMT_015@ GNUNETDNS_GROUP = @GNUNETDNS_GROUP@ @@ -177,6 +222,7 @@ GN_LIBINTL = @GN_LIBINTL@ GN_LIB_LDFLAGS = @GN_LIB_LDFLAGS@ GN_PLUGIN_LDFLAGS = @GN_PLUGIN_LDFLAGS@ GN_USER_HOME_DIR = @GN_USER_HOME_DIR@ +GOBJECT_QUERY = @GOBJECT_QUERY@ GREP = @GREP@ HAVE_LIBUNISTRING = @HAVE_LIBUNISTRING@ INCLTDL = @INCLTDL@ @@ -199,6 +245,8 @@ LIBCURL_CPPFLAGS = @LIBCURL_CPPFLAGS@ LIBGCRYPT_CFLAGS = @LIBGCRYPT_CFLAGS@ LIBGCRYPT_CONFIG = @LIBGCRYPT_CONFIG@ LIBGCRYPT_LIBS = @LIBGCRYPT_LIBS@ +LIBGTOP_CFLAGS = @LIBGTOP_CFLAGS@ +LIBGTOP_LIBS = @LIBGTOP_LIBS@ LIBICONV = @LIBICONV@ LIBINTL = @LIBINTL@ LIBLTDL = @LIBLTDL@ @@ -220,6 +268,7 @@ LT_CONFIG_H = @LT_CONFIG_H@ LT_DLLOADERS = @LT_DLLOADERS@ LT_DLPREOPEN = @LT_DLPREOPEN@ MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ MKDIR_P = @MKDIR_P@ MONKEYPREFIX = @MONKEYPREFIX@ MSGFMT = @MSGFMT@ @@ -229,6 +278,7 @@ MYSQL_CPPFLAGS = @MYSQL_CPPFLAGS@ MYSQL_LDFLAGS = @MYSQL_LDFLAGS@ NM = @NM@ NMEDIT = @NMEDIT@ +NSS_DIR = @NSS_DIR@ OBJC = @OBJC@ OBJCDEPMODE = @OBJCDEPMODE@ OBJCFLAGS = @OBJCFLAGS@ @@ -244,6 +294,7 @@ PACKAGE_TARNAME = @PACKAGE_TARNAME@ PACKAGE_URL = @PACKAGE_URL@ PACKAGE_VERSION = @PACKAGE_VERSION@ PATH_SEPARATOR = @PATH_SEPARATOR@ +PKG_CONFIG = @PKG_CONFIG@ POSTGRES_CPPFLAGS = @POSTGRES_CPPFLAGS@ POSTGRES_LDFLAGS = @POSTGRES_LDFLAGS@ POSUB = @POSUB@ @@ -275,6 +326,7 @@ abs_builddir = @abs_builddir@ abs_srcdir = @abs_srcdir@ abs_top_builddir = @abs_top_builddir@ abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ ac_ct_CC = @ac_ct_CC@ ac_ct_CXX = @ac_ct_CXX@ ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ @@ -297,6 +349,7 @@ datarootdir = @datarootdir@ docdir = @docdir@ dvidir = @dvidir@ exec_prefix = @exec_prefix@ +gitcommand = @gitcommand@ host = @host@ host_alias = @host_alias@ host_cpu = @host_cpu@ @@ -307,10 +360,9 @@ includedir = @includedir@ infodir = @infodir@ install_sh = @install_sh@ libdir = @libdir@ -libexecdir = @libexecdir@ +libexecdir = $(pkglibdir)/libexec/ localedir = @localedir@ localstatedir = @localstatedir@ -lt_ECHO = @lt_ECHO@ ltdl_LIBOBJS = @ltdl_LIBOBJS@ ltdl_LTLIBOBJS = @ltdl_LTLIBOBJS@ mandir = @mandir@ @@ -328,6 +380,7 @@ sbindir = @sbindir@ sharedstatedir = @sharedstatedir@ srcdir = @srcdir@ subdirs = @subdirs@ +svnversioncommand = @svnversioncommand@ sys_symbol_underscore = @sys_symbol_underscore@ sysconfdir = @sysconfdir@ target = @target@ @@ -339,26 +392,39 @@ top_build_prefix = @top_build_prefix@ top_builddir = @top_builddir@ top_srcdir = @top_srcdir@ INCLUDES = -I$(top_srcdir)/src/include -@MINGW_TRUE@WINFLAGS = -Wl,--no-undefined -Wl,--export-all-symbols +@MINGW_TRUE@WINFLAGS = -Wl,--no-undefined, --export-all-symbols +@LINUX_TRUE@EXITBIN = gnunet-helper-exit +@MINGW_TRUE@EXITBIN = gnunet-helper-exit @USE_COVERAGE_TRUE@AM_CFLAGS = --coverage -O0 pkgcfgdir = $(pkgdatadir)/config.d/ plugindir = $(libdir)/gnunet dist_pkgcfg_DATA = \ exit.conf -@LINUX_TRUE@EXITBIN = gnunet-helper-exit -gnunet_helper_exit_SOURCES = \ - gnunet-helper-exit.c +@MINGW_TRUE@gnunet_helper_exit_LDFLAGS = \ +@MINGW_TRUE@ -no-undefined -Wl,--export-all-symbols + +@MINGW_TRUE@gnunet_helper_exit_LDADD = \ +@MINGW_TRUE@ -lsetupapi -lnewdev -lshell32 -liconv -lstdc++ \ +@MINGW_TRUE@ -lcomdlg32 -lgdi32 -liphlpapi + +@MINGW_FALSE@gnunet_helper_exit_SOURCES = \ +@MINGW_FALSE@ gnunet-helper-exit.c + +@MINGW_TRUE@gnunet_helper_exit_SOURCES = \ +@MINGW_TRUE@ gnunet-helper-exit-windows.c gnunet_daemon_exit_SOURCES = \ gnunet-daemon-exit.c exit.h gnunet_daemon_exit_LDADD = \ + $(top_builddir)/src/dns/libgnunetdnsstub.la \ $(top_builddir)/src/core/libgnunetcore.la \ $(top_builddir)/src/statistics/libgnunetstatistics.la \ $(top_builddir)/src/tun/libgnunettun.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/mesh/libgnunetmesh.la \ + $(top_builddir)/src/regex/libgnunetregex.la \ $(GN_LIBINTL) all: all-am @@ -395,10 +461,13 @@ $(top_srcdir)/configure: $(am__configure_deps) $(ACLOCAL_M4): $(am__aclocal_m4_deps) cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh $(am__aclocal_m4_deps): -install-binPROGRAMS: $(bin_PROGRAMS) +install-libexecPROGRAMS: $(libexec_PROGRAMS) @$(NORMAL_INSTALL) - test -z "$(bindir)" || $(MKDIR_P) "$(DESTDIR)$(bindir)" - @list='$(bin_PROGRAMS)'; test -n "$(bindir)" || list=; \ + @list='$(libexec_PROGRAMS)'; test -n "$(libexecdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(libexecdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libexecdir)" || exit 1; \ + fi; \ for p in $$list; do echo "$$p $$p"; done | \ sed 's/$(EXEEXT)$$//' | \ while read p p1; do if test -f $$p || test -f $$p1; \ @@ -415,35 +484,35 @@ install-binPROGRAMS: $(bin_PROGRAMS) while read type dir files; do \ if test "$$dir" = .; then dir=; else dir=/$$dir; fi; \ test -z "$$files" || { \ - echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files '$(DESTDIR)$(bindir)$$dir'"; \ - $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files "$(DESTDIR)$(bindir)$$dir" || exit $$?; \ + echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files '$(DESTDIR)$(libexecdir)$$dir'"; \ + $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files "$(DESTDIR)$(libexecdir)$$dir" || exit $$?; \ } \ ; done -uninstall-binPROGRAMS: +uninstall-libexecPROGRAMS: @$(NORMAL_UNINSTALL) - @list='$(bin_PROGRAMS)'; test -n "$(bindir)" || list=; \ + @list='$(libexec_PROGRAMS)'; test -n "$(libexecdir)" || list=; \ files=`for p in $$list; do echo "$$p"; done | \ sed -e 'h;s,^.*/,,;s/$(EXEEXT)$$//;$(transform)' \ -e 's/$$/$(EXEEXT)/' `; \ test -n "$$list" || exit 0; \ - echo " ( cd '$(DESTDIR)$(bindir)' && rm -f" $$files ")"; \ - cd "$(DESTDIR)$(bindir)" && rm -f $$files + echo " ( cd '$(DESTDIR)$(libexecdir)' && rm -f" $$files ")"; \ + cd "$(DESTDIR)$(libexecdir)" && rm -f $$files -clean-binPROGRAMS: - @list='$(bin_PROGRAMS)'; test -n "$$list" || exit 0; \ +clean-libexecPROGRAMS: + @list='$(libexec_PROGRAMS)'; test -n "$$list" || exit 0; \ echo " rm -f" $$list; \ rm -f $$list || exit $$?; \ test -n "$(EXEEXT)" || exit 0; \ list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ echo " rm -f" $$list; \ rm -f $$list -gnunet-daemon-exit$(EXEEXT): $(gnunet_daemon_exit_OBJECTS) $(gnunet_daemon_exit_DEPENDENCIES) +gnunet-daemon-exit$(EXEEXT): $(gnunet_daemon_exit_OBJECTS) $(gnunet_daemon_exit_DEPENDENCIES) $(EXTRA_gnunet_daemon_exit_DEPENDENCIES) @rm -f gnunet-daemon-exit$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_daemon_exit_OBJECTS) $(gnunet_daemon_exit_LDADD) $(LIBS) -gnunet-helper-exit$(EXEEXT): $(gnunet_helper_exit_OBJECTS) $(gnunet_helper_exit_DEPENDENCIES) +gnunet-helper-exit$(EXEEXT): $(gnunet_helper_exit_OBJECTS) $(gnunet_helper_exit_DEPENDENCIES) $(EXTRA_gnunet_helper_exit_DEPENDENCIES) @rm -f gnunet-helper-exit$(EXEEXT) - $(AM_V_CCLD)$(LINK) $(gnunet_helper_exit_OBJECTS) $(gnunet_helper_exit_LDADD) $(LIBS) + $(AM_V_CCLD)$(gnunet_helper_exit_LINK) $(gnunet_helper_exit_OBJECTS) $(gnunet_helper_exit_LDADD) $(LIBS) mostlyclean-compile: -rm -f *.$(OBJEXT) @@ -452,31 +521,29 @@ distclean-compile: -rm -f *.tab.c @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-daemon-exit.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-helper-exit-windows.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-helper-exit.Po@am__quote@ .c.o: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c $< .c.obj: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'` @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c `$(CYGPATH_W) '$<'` +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c `$(CYGPATH_W) '$<'` .c.lo: @am__fastdepCC_TRUE@ $(AM_V_CC)$(LTCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LTCOMPILE) -c -o $@ $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LTCOMPILE) -c -o $@ $< mostlyclean-libtool: -rm -f *.lo @@ -485,8 +552,11 @@ clean-libtool: -rm -rf .libs _libs install-dist_pkgcfgDATA: $(dist_pkgcfg_DATA) @$(NORMAL_INSTALL) - test -z "$(pkgcfgdir)" || $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" @list='$(dist_pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(pkgcfgdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" || exit 1; \ + fi; \ for p in $$list; do \ if test -f "$$p"; then d=; else d="$(srcdir)/"; fi; \ echo "$$d$$p"; \ @@ -500,9 +570,7 @@ uninstall-dist_pkgcfgDATA: @$(NORMAL_UNINSTALL) @list='$(dist_pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ files=`for p in $$list; do echo $$p; done | sed -e 's|^.*/||'`; \ - test -n "$$files" || exit 0; \ - echo " ( cd '$(DESTDIR)$(pkgcfgdir)' && rm -f" $$files ")"; \ - cd "$(DESTDIR)$(pkgcfgdir)" && rm -f $$files + dir='$(DESTDIR)$(pkgcfgdir)'; $(am__uninstall_files_from_dir) ID: $(HEADERS) $(SOURCES) $(LISP) $(TAGS_FILES) list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ @@ -590,7 +658,7 @@ check-am: all-am check: check-am all-am: Makefile $(PROGRAMS) $(DATA) installdirs: - for dir in "$(DESTDIR)$(bindir)" "$(DESTDIR)$(pkgcfgdir)"; do \ + for dir in "$(DESTDIR)$(libexecdir)" "$(DESTDIR)$(pkgcfgdir)"; do \ test -z "$$dir" || $(MKDIR_P) "$$dir"; \ done install: install-am @@ -603,10 +671,15 @@ install-am: all-am installcheck: installcheck-am install-strip: - $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ - install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ - `test -z '$(STRIP)' || \ - echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi mostlyclean-generic: clean-generic: @@ -620,7 +693,8 @@ maintainer-clean-generic: @echo "it deletes files that may require special tools to rebuild." clean: clean-am -clean-am: clean-binPROGRAMS clean-generic clean-libtool mostlyclean-am +clean-am: clean-generic clean-libexecPROGRAMS clean-libtool \ + mostlyclean-am distclean: distclean-am -rm -rf ./$(DEPDIR) @@ -646,7 +720,7 @@ install-dvi: install-dvi-am install-dvi-am: -install-exec-am: install-binPROGRAMS +install-exec-am: install-libexecPROGRAMS @$(NORMAL_INSTALL) $(MAKE) $(AM_MAKEFLAGS) install-exec-hook install-html: install-html-am @@ -687,28 +761,28 @@ ps: ps-am ps-am: -uninstall-am: uninstall-binPROGRAMS uninstall-dist_pkgcfgDATA +uninstall-am: uninstall-dist_pkgcfgDATA uninstall-libexecPROGRAMS .MAKE: install-am install-exec-am install-strip -.PHONY: CTAGS GTAGS all all-am check check-am clean clean-binPROGRAMS \ - clean-generic clean-libtool ctags distclean distclean-compile \ - distclean-generic distclean-libtool distclean-tags distdir dvi \ - dvi-am html html-am info info-am install install-am \ - install-binPROGRAMS install-data install-data-am \ +.PHONY: CTAGS GTAGS all all-am check check-am clean clean-generic \ + clean-libexecPROGRAMS clean-libtool ctags distclean \ + distclean-compile distclean-generic distclean-libtool \ + distclean-tags distdir dvi dvi-am html html-am info info-am \ + install install-am install-data install-data-am \ install-dist_pkgcfgDATA install-dvi install-dvi-am \ install-exec install-exec-am install-exec-hook install-html \ - install-html-am install-info install-info-am install-man \ - install-pdf install-pdf-am install-ps install-ps-am \ - install-strip installcheck installcheck-am installdirs \ - maintainer-clean maintainer-clean-generic mostlyclean \ - mostlyclean-compile mostlyclean-generic mostlyclean-libtool \ - pdf pdf-am ps ps-am tags uninstall uninstall-am \ - uninstall-binPROGRAMS uninstall-dist_pkgcfgDATA + install-html-am install-info install-info-am \ + install-libexecPROGRAMS install-man install-pdf install-pdf-am \ + install-ps install-ps-am install-strip installcheck \ + installcheck-am installdirs maintainer-clean \ + maintainer-clean-generic mostlyclean mostlyclean-compile \ + mostlyclean-generic mostlyclean-libtool pdf pdf-am ps ps-am \ + tags uninstall uninstall-am uninstall-dist_pkgcfgDATA \ + uninstall-libexecPROGRAMS @LINUX_TRUE@install-exec-hook: -@LINUX_TRUE@ $(SUDO_BINARY) chown root:root $(bindir)/gnunet-helper-exit || true -@LINUX_TRUE@ $(SUDO_BINARY) chmod u+s $(bindir)/gnunet-helper-exit || true +@LINUX_TRUE@ $(top_srcdir)/src/exit/install-exit-helper.sh $(libexecdir) $(SUDO_BINARY) || true @LINUX_FALSE@install-exec-hook: # Tell versions [3.59,3.63) of GNU make to not export all variables. diff --git a/src/exit/exit.conf b/src/exit/exit.conf index 0d48de9..aadcee4 100644 --- a/src/exit/exit.conf +++ b/src/exit/exit.conf @@ -1,5 +1,4 @@ [exit] -CONFIG = $DEFAULTCONFIG BINARY = gnunet-daemon-exit # IPv6 address for the TUN interface (must be changed as this @@ -17,6 +16,14 @@ IPV4ADDR = 169.254.86.1 # Netmask for the IPv4 subnet on the TUN interface. IPV4MASK = 255.255.255.0 +# Regular expression matching IPv4 addresses in binary (32 values of 0 or 1) +# format for which this system is willing to serve as an exit. +EXIT_RANGE_IPV4_REGEX = (0|1)* + +# Regular expression matching IPv4 addresses in binary (128 values of 0 or 1) +# format for which this system is willing to serve as an exit. +EXIT_RANGE_IPV6_REGEX = (0|1)* + # Name of the (virtual) tunnel interface the exit daemon will manage TUN_IFNAME = exit-gnunet @@ -36,6 +43,18 @@ EXIT_IPV4 = NO # Set this to YES to allow exiting this system via IPv6 to the Internet EXIT_IPV6 = NO +# This option should be set to YES to allow the DNS service to +# perform lookups against the locally configured DNS resolver. +# (set to "NO" if no normal ISP is locally available and thus +# requests for normal ".com"/".org"/etc. must be routed via +# the GNUnet VPN (the GNUNET PT daemon then needs to be configured +# to intercept and route DNS queries via mesh). +# Set this to YES to allow using this system for DNS queries. +EXIT_DNS = NO + +# Set this to an IPv4 or IPv6 address of a DNS resolver to use for DNS queries +DNS_RESOLVER = 8.8.8.8 + # For IPv4-services offered by this peer, we need to at least enable IPv4 ENABLE_IPV4 = YES diff --git a/src/exit/exit.h b/src/exit/exit.h index 90df26d..ff5e3f5 100644 --- a/src/exit/exit.h +++ b/src/exit/exit.h @@ -49,7 +49,7 @@ struct GNUNET_EXIT_TcpServiceStartMessage /** * Identification for the desired service. */ - GNUNET_HashCode service_descriptor; + struct GNUNET_HashCode service_descriptor; /** * Skeleton of the TCP header to send. Port numbers are to @@ -142,7 +142,7 @@ struct GNUNET_EXIT_UdpServiceMessage /** * Identification for the desired service. */ - GNUNET_HashCode service_descriptor; + struct GNUNET_HashCode service_descriptor; /* followed by UDP payload */ }; @@ -230,7 +230,7 @@ struct GNUNET_EXIT_IcmpServiceMessage /** * Identification for the desired service. */ - GNUNET_HashCode service_descriptor; + struct GNUNET_HashCode service_descriptor; /** * ICMP header to use. diff --git a/src/exit/gnunet-daemon-exit.c b/src/exit/gnunet-daemon-exit.c index 26f3e75..92f3866 100644 --- a/src/exit/gnunet-daemon-exit.c +++ b/src/exit/gnunet-daemon-exit.c @@ -39,11 +39,35 @@ #include "gnunet_protocols.h" #include "gnunet_applications.h" #include "gnunet_mesh_service.h" +#include "gnunet_dnsparser_lib.h" +#include "gnunet_dnsstub_lib.h" #include "gnunet_statistics_service.h" #include "gnunet_constants.h" #include "gnunet_tun_lib.h" +#include "gnunet_regex_lib.h" #include "exit.h" +/** + * Maximum path compression length for mesh regex announcing for IPv4 address + * based regex. + */ +#define REGEX_MAX_PATH_LEN_IPV4 4 + +/** + * Maximum path compression length for mesh regex announcing for IPv6 address + * based regex. + */ +#define REGEX_MAX_PATH_LEN_IPV6 8 + + +/** + * Generic logging shorthand + */ +#define LOG(kind, ...) \ + GNUNET_log_from (kind, "exit", __VA_ARGS__); + + + /** * Information about an address. */ @@ -182,39 +206,85 @@ struct TunnelState struct GNUNET_MESH_Tunnel *tunnel; /** - * Heap node for this state in the connections_heap. + * Active tunnel transmission request (or NULL). */ - struct GNUNET_CONTAINER_HeapNode *heap_node; + struct GNUNET_MESH_TransmitHandle *th; /** - * Key this state has in the connections_map. + * GNUNET_NO if this is a tunnel for TCP/UDP, + * GNUNET_YES if this is a tunnel for DNS, + * GNUNET_SYSERR if the tunnel is not yet initialized. */ - GNUNET_HashCode state_key; + int is_dns; - /** - * Associated service record, or NULL for no service. - */ - struct LocalService *serv; + union + { + struct + { - /** - * Head of DLL of messages for this tunnel. - */ - struct TunnelMessageQueue *head; + /** + * Heap node for this state in the connections_heap. + */ + struct GNUNET_CONTAINER_HeapNode *heap_node; + + /** + * Key this state has in the connections_map. + */ + struct GNUNET_HashCode state_key; + + /** + * Associated service record, or NULL for no service. + */ + struct LocalService *serv; + + /** + * Head of DLL of messages for this tunnel. + */ + struct TunnelMessageQueue *head; + + /** + * Tail of DLL of messages for this tunnel. + */ + struct TunnelMessageQueue *tail; + + /** + * Primary redirection information for this connection. + */ + struct RedirectInformation ri; + } tcp_udp; - /** - * Tail of DLL of messages for this tunnel. - */ - struct TunnelMessageQueue *tail; + struct + { - /** - * Active tunnel transmission request (or NULL). - */ - struct GNUNET_MESH_TransmitHandle *th; + /** + * DNS reply ready for transmission. + */ + char *reply; + + /** + * Socket we are using to transmit this request (must match if we receive + * a response). + */ + struct GNUNET_DNSSTUB_RequestSocket *rs; + + /** + * Number of bytes in 'reply'. + */ + size_t reply_length; + + /** + * Original DNS request ID as used by the client. + */ + uint16_t original_id; + + /** + * DNS request ID that we used for forwarding. + */ + uint16_t my_id; + + } dns; - /** - * Primary redirection information for this connection. - */ - struct RedirectInformation ri; + } specifics; }; @@ -259,7 +329,6 @@ static struct in_addr exit_ipv4addr; */ static struct in_addr exit_ipv4mask; - /** * Statistics. */ @@ -296,6 +365,16 @@ static struct GNUNET_CONTAINER_MultiHashMap *udp_services; */ static struct GNUNET_CONTAINER_MultiHashMap *tcp_services; +/** + * Array of all open DNS requests from tunnels. + */ +static struct TunnelState *tunnels[UINT16_MAX + 1]; + +/** + * Handle to the DNS Stub resolver. + */ +static struct GNUNET_DNSSTUB_Context *dnsstub; + /** * Are we an IPv4-exit? */ @@ -317,6 +396,160 @@ static int ipv4_enabled; static int ipv6_enabled; +/** + * We got a reply from DNS for a request of a MESH tunnel. Send it + * via the tunnel (after changing the request ID back). + * + * @param cls the 'struct TunnelState' + * @param size number of bytes available in buf + * @param buf where to copy the reply + * @return number of bytes written to buf + */ +static size_t +transmit_reply_to_mesh (void *cls, + size_t size, + void *buf) +{ + struct TunnelState *ts = cls; + size_t off; + size_t ret; + char *cbuf = buf; + struct GNUNET_MessageHeader hdr; + struct GNUNET_TUN_DnsHeader dns; + + GNUNET_assert (GNUNET_YES == ts->is_dns); + ts->th = NULL; + GNUNET_assert (ts->specifics.dns.reply != NULL); + if (size == 0) + return 0; + ret = sizeof (struct GNUNET_MessageHeader) + ts->specifics.dns.reply_length; + GNUNET_assert (ret <= size); + hdr.size = htons (ret); + hdr.type = htons (GNUNET_MESSAGE_TYPE_VPN_DNS_FROM_INTERNET); + memcpy (&dns, ts->specifics.dns.reply, sizeof (dns)); + dns.id = ts->specifics.dns.original_id; + off = 0; + memcpy (&cbuf[off], &hdr, sizeof (hdr)); + off += sizeof (hdr); + memcpy (&cbuf[off], &dns, sizeof (dns)); + off += sizeof (dns); + memcpy (&cbuf[off], &ts->specifics.dns.reply[sizeof (dns)], ts->specifics.dns.reply_length - sizeof (dns)); + off += ts->specifics.dns.reply_length - sizeof (dns); + GNUNET_free (ts->specifics.dns.reply); + ts->specifics.dns.reply = NULL; + ts->specifics.dns.reply_length = 0; + GNUNET_assert (ret == off); + return ret; +} + + +/** + * Callback called from DNSSTUB resolver when a resolution + * succeeded. + * + * @param cls NULL + * @param rs the socket that received the response + * @param dns the response itself + * @param r number of bytes in dns + */ +static void +process_dns_result (void *cls, + struct GNUNET_DNSSTUB_RequestSocket *rs, + const struct GNUNET_TUN_DnsHeader *dns, + size_t r) +{ + struct TunnelState *ts; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Processing DNS result from stub resolver\n"); + GNUNET_assert (NULL == cls); + /* Handle case that this is a reply to a request from a MESH DNS tunnel */ + ts = tunnels[dns->id]; + if ( (NULL == ts) || + (ts->specifics.dns.rs != rs) ) + return; + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Got a response from the stub resolver for DNS request received via MESH!\n"); + tunnels[dns->id] = NULL; + GNUNET_free_non_null (ts->specifics.dns.reply); + ts->specifics.dns.reply = GNUNET_malloc (r); + ts->specifics.dns.reply_length = r; + memcpy (ts->specifics.dns.reply, dns, r); + if (NULL != ts->th) + GNUNET_MESH_notify_transmit_ready_cancel (ts->th); + ts->th = GNUNET_MESH_notify_transmit_ready (ts->tunnel, + GNUNET_NO, + GNUNET_TIME_UNIT_FOREVER_REL, + NULL, + sizeof (struct GNUNET_MessageHeader) + r, + &transmit_reply_to_mesh, + ts); +} + + +/** + * Process a request via mesh to perform a DNS query. + * + * @param cls closure, NULL + * @param tunnel connection to the other end + * @param tunnel_ctx pointer to our 'struct TunnelState *' + * @param sender who sent the message + * @param message the actual message + * @param atsi performance data for the connection + * @return GNUNET_OK to keep the connection open, + * GNUNET_SYSERR to close it (signal serious error) + */ +static int +receive_dns_request (void *cls GNUNET_UNUSED, struct GNUNET_MESH_Tunnel *tunnel, + void **tunnel_ctx, + const struct GNUNET_PeerIdentity *sender GNUNET_UNUSED, + const struct GNUNET_MessageHeader *message, + const struct GNUNET_ATS_Information *atsi GNUNET_UNUSED) +{ + struct TunnelState *ts = *tunnel_ctx; + const struct GNUNET_TUN_DnsHeader *dns; + size_t mlen = ntohs (message->size); + size_t dlen = mlen - sizeof (struct GNUNET_MessageHeader); + char buf[dlen] GNUNET_ALIGN; + struct GNUNET_TUN_DnsHeader *dout; + + if (NULL == dnsstub) + return GNUNET_SYSERR; + if (GNUNET_NO == ts->is_dns) + { + GNUNET_break_op (0); + return GNUNET_SYSERR; + } + if (GNUNET_SYSERR == ts->is_dns) + { + /* tunnel is DNS from now on */ + ts->is_dns = GNUNET_YES; + } + if (dlen < sizeof (struct GNUNET_TUN_DnsHeader)) + { + GNUNET_break_op (0); + return GNUNET_SYSERR; + } + dns = (const struct GNUNET_TUN_DnsHeader *) &message[1]; + ts->specifics.dns.original_id = dns->id; + if (tunnels[ts->specifics.dns.my_id] == ts) + tunnels[ts->specifics.dns.my_id] = NULL; + ts->specifics.dns.my_id = (uint16_t) GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK, + UINT16_MAX + 1); + tunnels[ts->specifics.dns.my_id] = ts; + memcpy (buf, dns, dlen); + dout = (struct GNUNET_TUN_DnsHeader *) buf; + dout->id = ts->specifics.dns.my_id; + ts->specifics.dns.rs = GNUNET_DNSSTUB_resolve2 (dnsstub, + buf, dlen, + &process_dns_result, + NULL); + if (NULL == ts->specifics.dns.rs) + return GNUNET_SYSERR; + return GNUNET_OK; +} + + /** * Given IP information about a connection, calculate the respective * hash we would use for the 'connections_map'. @@ -325,12 +558,12 @@ static int ipv6_enabled; * @param ri information about the connection */ static void -hash_redirect_info (GNUNET_HashCode *hash, +hash_redirect_info (struct GNUNET_HashCode *hash, const struct RedirectInformation *ri) { char *off; - memset (hash, 0, sizeof (GNUNET_HashCode)); + memset (hash, 0, sizeof (struct GNUNET_HashCode)); /* the GNUnet hashmap only uses the first sizeof(unsigned int) of the hash, so we put the IP address in there (and hope for few collisions) */ off = (char*) hash; @@ -389,10 +622,10 @@ get_redirect_state (int af, uint16_t destination_port, const void *local_ip, uint16_t local_port, - GNUNET_HashCode *state_key) + struct GNUNET_HashCode *state_key) { struct RedirectInformation ri; - GNUNET_HashCode key; + struct GNUNET_HashCode key; struct TunnelState *state; if ( ( (af == AF_INET) && (protocol == IPPROTO_ICMP) ) || @@ -425,7 +658,7 @@ get_redirect_state (int af, /* Mark this connection as freshly used */ if (NULL == state_key) GNUNET_CONTAINER_heap_update_cost (connections_heap, - state->heap_node, + state->specifics.tcp_udp.heap_node, GNUNET_TIME_absolute_get ().abs_value); return state; } @@ -442,15 +675,15 @@ get_redirect_state (int af, */ static struct LocalService * find_service (struct GNUNET_CONTAINER_MultiHashMap *service_map, - const GNUNET_HashCode *desc, + const struct GNUNET_HashCode *desc, uint16_t destination_port) { - char key[sizeof (GNUNET_HashCode) + sizeof (uint16_t)]; + char key[sizeof (struct GNUNET_HashCode) + sizeof (uint16_t)]; memcpy (&key[0], &destination_port, sizeof (uint16_t)); - memcpy (&key[sizeof(uint16_t)], desc, sizeof (GNUNET_HashCode)); + memcpy (&key[sizeof(uint16_t)], desc, sizeof (struct GNUNET_HashCode)); return GNUNET_CONTAINER_multihashmap_get (service_map, - (GNUNET_HashCode *) key); + (struct GNUNET_HashCode *) key); } @@ -464,7 +697,7 @@ find_service (struct GNUNET_CONTAINER_MultiHashMap *service_map, */ static int free_service_record (void *cls, - const GNUNET_HashCode *key, + const struct GNUNET_HashCode *key, void *value) { struct LocalService *service = value; @@ -490,20 +723,20 @@ store_service (struct GNUNET_CONTAINER_MultiHashMap *service_map, uint16_t destination_port, struct LocalService *service) { - char key[sizeof (GNUNET_HashCode) + sizeof (uint16_t)]; - GNUNET_HashCode desc; + char key[sizeof (struct GNUNET_HashCode) + sizeof (uint16_t)]; + struct GNUNET_HashCode desc; GNUNET_CRYPTO_hash (name, strlen (name) + 1, &desc); service->name = GNUNET_strdup (name); memcpy (&key[0], &destination_port, sizeof (uint16_t)); - memcpy (&key[sizeof(uint16_t)], &desc, sizeof (GNUNET_HashCode)); + memcpy (&key[sizeof(uint16_t)], &desc, sizeof (struct GNUNET_HashCode)); if (GNUNET_OK != GNUNET_CONTAINER_multihashmap_put (service_map, - (GNUNET_HashCode *) key, + (struct GNUNET_HashCode *) key, service, GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY)) { - free_service_record (NULL, (GNUNET_HashCode *) key, service); + free_service_record (NULL, (struct GNUNET_HashCode *) key, service); GNUNET_log (GNUNET_ERROR_TYPE_WARNING, _("Got duplicate service records for `%s:%u'\n"), name, @@ -528,14 +761,13 @@ send_to_peer_notify_callback (void *cls, size_t size, void *buf) struct TunnelMessageQueue *tnq; s->th = NULL; - tnq = s->head; + tnq = s->specifics.tcp_udp.head; if (NULL == tnq) return 0; if (0 == size) { s->th = GNUNET_MESH_notify_transmit_ready (tunnel, GNUNET_NO /* corking */, - 0 /* priority */, GNUNET_TIME_UNIT_FOREVER_REL, NULL, tnq->len, @@ -546,14 +778,13 @@ send_to_peer_notify_callback (void *cls, size_t size, void *buf) GNUNET_assert (size >= tnq->len); memcpy (buf, tnq->payload, tnq->len); size = tnq->len; - GNUNET_CONTAINER_DLL_remove (s->head, - s->tail, + GNUNET_CONTAINER_DLL_remove (s->specifics.tcp_udp.head, + s->specifics.tcp_udp.tail, tnq); GNUNET_free (tnq); - if (NULL != (tnq = s->head)) + if (NULL != (tnq = s->specifics.tcp_udp.head)) s->th = GNUNET_MESH_notify_transmit_ready (tunnel, GNUNET_NO /* corking */, - 0 /* priority */, GNUNET_TIME_UNIT_FOREVER_REL, NULL, tnq->len, @@ -580,9 +811,10 @@ send_packet_to_mesh_tunnel (struct GNUNET_MESH_Tunnel *mesh_tunnel, s = GNUNET_MESH_tunnel_get_data (mesh_tunnel); GNUNET_assert (NULL != s); - GNUNET_CONTAINER_DLL_insert_tail (s->head, s->tail, tnq); + GNUNET_CONTAINER_DLL_insert_tail (s->specifics.tcp_udp.head, s->specifics.tcp_udp.tail, tnq); if (NULL == s->th) - s->th = GNUNET_MESH_notify_transmit_ready (mesh_tunnel, GNUNET_NO /* cork */, 0 /* priority */, + s->th = GNUNET_MESH_notify_transmit_ready (mesh_tunnel, + GNUNET_NO /* cork */, GNUNET_TIME_UNIT_FOREVER_REL, NULL, tnq->len, &send_to_peer_notify_callback, @@ -1207,7 +1439,7 @@ setup_fresh_address (int af, * cleaning up 'old' states. * * @param state skeleton state to setup a record for; should - * 'state->ri.remote_address' filled in so that + * 'state->specifics.tcp_udp.ri.remote_address' filled in so that * this code can determine which AF/protocol is * going to be used (the 'tunnel' should also * already be set); after calling this function, @@ -1218,53 +1450,53 @@ setup_fresh_address (int af, static void setup_state_record (struct TunnelState *state) { - GNUNET_HashCode key; + struct GNUNET_HashCode key; struct TunnelState *s; /* generate fresh, unique address */ do { - if (NULL == state->serv) - setup_fresh_address (state->ri.remote_address.af, - state->ri.remote_address.proto, - &state->ri.local_address); + if (NULL == state->specifics.tcp_udp.serv) + setup_fresh_address (state->specifics.tcp_udp.ri.remote_address.af, + state->specifics.tcp_udp.ri.remote_address.proto, + &state->specifics.tcp_udp.ri.local_address); else - setup_fresh_address (state->serv->address.af, - state->serv->address.proto, - &state->ri.local_address); - } while (NULL != get_redirect_state (state->ri.remote_address.af, - state->ri.remote_address.proto, - &state->ri.remote_address.address, - state->ri.remote_address.port, - &state->ri.local_address.address, - state->ri.local_address.port, + setup_fresh_address (state->specifics.tcp_udp.serv->address.af, + state->specifics.tcp_udp.serv->address.proto, + &state->specifics.tcp_udp.ri.local_address); + } while (NULL != get_redirect_state (state->specifics.tcp_udp.ri.remote_address.af, + state->specifics.tcp_udp.ri.remote_address.proto, + &state->specifics.tcp_udp.ri.remote_address.address, + state->specifics.tcp_udp.ri.remote_address.port, + &state->specifics.tcp_udp.ri.local_address.address, + state->specifics.tcp_udp.ri.local_address.port, &key)); { char buf[INET6_ADDRSTRLEN]; GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Picked local address %s:%u for new connection\n", - inet_ntop (state->ri.local_address.af, - &state->ri.local_address.address, + inet_ntop (state->specifics.tcp_udp.ri.local_address.af, + &state->specifics.tcp_udp.ri.local_address.address, buf, sizeof (buf)), - (unsigned int) state->ri.local_address.port); + (unsigned int) state->specifics.tcp_udp.ri.local_address.port); } - state->state_key = key; + state->specifics.tcp_udp.state_key = key; GNUNET_assert (GNUNET_OK == GNUNET_CONTAINER_multihashmap_put (connections_map, &key, state, GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY)); - state->heap_node = GNUNET_CONTAINER_heap_insert (connections_heap, + state->specifics.tcp_udp.heap_node = GNUNET_CONTAINER_heap_insert (connections_heap, state, GNUNET_TIME_absolute_get ().abs_value); while (GNUNET_CONTAINER_heap_get_size (connections_heap) > max_connections) { s = GNUNET_CONTAINER_heap_remove_root (connections_heap); GNUNET_assert (state != s); - s->heap_node = NULL; + s->specifics.tcp_udp.heap_node = NULL; GNUNET_MESH_tunnel_destroy (s->tunnel); GNUNET_assert (GNUNET_OK == GNUNET_CONTAINER_multihashmap_remove (connections_map, - &s->state_key, + &s->specifics.tcp_udp.state_key, s)); GNUNET_free (s); } @@ -1535,10 +1767,11 @@ send_tcp_packet_via_tun (const struct SocketAddress *destination_address, GNUNET_assert (0); break; } - (void) GNUNET_HELPER_send (helper_handle, - (const struct GNUNET_MessageHeader*) buf, - GNUNET_YES, - NULL, NULL); + if (NULL != helper_handle) + (void) GNUNET_HELPER_send (helper_handle, + (const struct GNUNET_MessageHeader*) buf, + GNUNET_YES, + NULL, NULL); } } @@ -1567,6 +1800,16 @@ receive_tcp_service (void *cls GNUNET_UNUSED, struct GNUNET_MESH_Tunnel *tunnel, const struct GNUNET_EXIT_TcpServiceStartMessage *start; uint16_t pkt_len = ntohs (message->size); + if (GNUNET_YES == state->is_dns) + { + GNUNET_break_op (0); + return GNUNET_SYSERR; + } + if (GNUNET_SYSERR == state->is_dns) + { + /* tunnel is UDP/TCP from now on */ + state->is_dns = GNUNET_NO; + } GNUNET_STATISTICS_update (stats, gettext_noop ("# TCP service creation requests received via mesh"), 1, GNUNET_NO); @@ -1582,8 +1825,8 @@ receive_tcp_service (void *cls GNUNET_UNUSED, struct GNUNET_MESH_Tunnel *tunnel, start = (const struct GNUNET_EXIT_TcpServiceStartMessage*) message; pkt_len -= sizeof (struct GNUNET_EXIT_TcpServiceStartMessage); if ( (NULL == state) || - (NULL != state->serv) || - (NULL != state->heap_node) ) + (NULL != state->specifics.tcp_udp.serv) || + (NULL != state->specifics.tcp_udp.heap_node) ) { GNUNET_break_op (0); return GNUNET_SYSERR; @@ -1600,8 +1843,8 @@ receive_tcp_service (void *cls GNUNET_UNUSED, struct GNUNET_MESH_Tunnel *tunnel, GNUNET_i2s (sender), GNUNET_h2s (&start->service_descriptor), (unsigned int) ntohs (start->tcp_header.destination_port)); - if (NULL == (state->serv = find_service (tcp_services, &start->service_descriptor, - ntohs (start->tcp_header.destination_port)))) + if (NULL == (state->specifics.tcp_udp.serv = find_service (tcp_services, &start->service_descriptor, + ntohs (start->tcp_header.destination_port)))) { GNUNET_log (GNUNET_ERROR_TYPE_INFO, _("No service found for %s on port %d!\n"), @@ -1612,10 +1855,10 @@ receive_tcp_service (void *cls GNUNET_UNUSED, struct GNUNET_MESH_Tunnel *tunnel, 1, GNUNET_NO); return GNUNET_SYSERR; } - state->ri.remote_address = state->serv->address; + state->specifics.tcp_udp.ri.remote_address = state->specifics.tcp_udp.serv->address; setup_state_record (state); - send_tcp_packet_via_tun (&state->ri.remote_address, - &state->ri.local_address, + send_tcp_packet_via_tun (&state->specifics.tcp_udp.ri.remote_address, + &state->specifics.tcp_udp.ri.local_address, &start->tcp_header, &start[1], pkt_len); return GNUNET_YES; @@ -1649,6 +1892,16 @@ receive_tcp_remote (void *cls GNUNET_UNUSED, struct GNUNET_MESH_Tunnel *tunnel, const void *payload; int af; + if (GNUNET_YES == state->is_dns) + { + GNUNET_break_op (0); + return GNUNET_SYSERR; + } + if (GNUNET_SYSERR == state->is_dns) + { + /* tunnel is UDP/TCP from now on */ + state->is_dns = GNUNET_NO; + } GNUNET_STATISTICS_update (stats, gettext_noop ("# Bytes received from MESH"), pkt_len, GNUNET_NO); @@ -1663,8 +1916,8 @@ receive_tcp_remote (void *cls GNUNET_UNUSED, struct GNUNET_MESH_Tunnel *tunnel, start = (const struct GNUNET_EXIT_TcpInternetStartMessage*) message; pkt_len -= sizeof (struct GNUNET_EXIT_TcpInternetStartMessage); if ( (NULL == state) || - (NULL != state->serv) || - (NULL != state->heap_node) ) + (NULL != state->specifics.tcp_udp.serv) || + (NULL != state->specifics.tcp_udp.heap_node) ) { GNUNET_break_op (0); return GNUNET_SYSERR; @@ -1675,7 +1928,7 @@ receive_tcp_remote (void *cls GNUNET_UNUSED, struct GNUNET_MESH_Tunnel *tunnel, return GNUNET_SYSERR; } af = (int) ntohl (start->af); - state->ri.remote_address.af = af; + state->specifics.tcp_udp.ri.remote_address.af = af; switch (af) { case AF_INET: @@ -1692,7 +1945,7 @@ receive_tcp_remote (void *cls GNUNET_UNUSED, struct GNUNET_MESH_Tunnel *tunnel, v4 = (const struct in_addr*) &start[1]; payload = &v4[1]; pkt_len -= sizeof (struct in_addr); - state->ri.remote_address.address.ipv4 = *v4; + state->specifics.tcp_udp.ri.remote_address.address.ipv4 = *v4; break; case AF_INET6: if (pkt_len < sizeof (struct in6_addr)) @@ -1708,7 +1961,7 @@ receive_tcp_remote (void *cls GNUNET_UNUSED, struct GNUNET_MESH_Tunnel *tunnel, v6 = (const struct in6_addr*) &start[1]; payload = &v6[1]; pkt_len -= sizeof (struct in6_addr); - state->ri.remote_address.address.ipv6 = *v6; + state->specifics.tcp_udp.ri.remote_address.address.ipv6 = *v6; break; default: GNUNET_break_op (0); @@ -1720,15 +1973,15 @@ receive_tcp_remote (void *cls GNUNET_UNUSED, struct GNUNET_MESH_Tunnel *tunnel, "Received data from %s for starting TCP stream to %s:%u\n", GNUNET_i2s (sender), inet_ntop (af, - &state->ri.remote_address.address, + &state->specifics.tcp_udp.ri.remote_address.address, buf, sizeof (buf)), (unsigned int) ntohs (start->tcp_header.destination_port)); } - state->ri.remote_address.proto = IPPROTO_TCP; - state->ri.remote_address.port = ntohs (start->tcp_header.destination_port); + state->specifics.tcp_udp.ri.remote_address.proto = IPPROTO_TCP; + state->specifics.tcp_udp.ri.remote_address.port = ntohs (start->tcp_header.destination_port); setup_state_record (state); - send_tcp_packet_via_tun (&state->ri.remote_address, - &state->ri.local_address, + send_tcp_packet_via_tun (&state->specifics.tcp_udp.ri.remote_address, + &state->specifics.tcp_udp.ri.local_address, &start->tcp_header, payload, pkt_len); return GNUNET_YES; @@ -1759,6 +2012,16 @@ receive_tcp_data (void *cls GNUNET_UNUSED, struct GNUNET_MESH_Tunnel *tunnel, const struct GNUNET_EXIT_TcpDataMessage *data; uint16_t pkt_len = ntohs (message->size); + if (GNUNET_YES == state->is_dns) + { + GNUNET_break_op (0); + return GNUNET_SYSERR; + } + if (GNUNET_SYSERR == state->is_dns) + { + /* tunnel is UDP/TCP from now on */ + state->is_dns = GNUNET_NO; + } GNUNET_STATISTICS_update (stats, gettext_noop ("# Bytes received from MESH"), pkt_len, GNUNET_NO); @@ -1773,7 +2036,7 @@ receive_tcp_data (void *cls GNUNET_UNUSED, struct GNUNET_MESH_Tunnel *tunnel, data = (const struct GNUNET_EXIT_TcpDataMessage*) message; pkt_len -= sizeof (struct GNUNET_EXIT_TcpDataMessage); if ( (NULL == state) || - (NULL == state->heap_node) ) + (NULL == state->specifics.tcp_udp.heap_node) ) { /* connection should have been up! */ GNUNET_STATISTICS_update (stats, @@ -1794,14 +2057,14 @@ receive_tcp_data (void *cls GNUNET_UNUSED, struct GNUNET_MESH_Tunnel *tunnel, "Received additional %u bytes of data from %s for TCP stream to %s:%u\n", pkt_len, GNUNET_i2s (sender), - inet_ntop (state->ri.remote_address.af, - &state->ri.remote_address.address, + inet_ntop (state->specifics.tcp_udp.ri.remote_address.af, + &state->specifics.tcp_udp.ri.remote_address.address, buf, sizeof (buf)), - (unsigned int) state->ri.remote_address.port); + (unsigned int) state->specifics.tcp_udp.ri.remote_address.port); } - send_tcp_packet_via_tun (&state->ri.remote_address, - &state->ri.local_address, + send_tcp_packet_via_tun (&state->specifics.tcp_udp.ri.remote_address, + &state->specifics.tcp_udp.ri.local_address, &data->tcp_header, &data[1], pkt_len); return GNUNET_YES; @@ -1901,10 +2164,11 @@ send_icmp_packet_via_tun (const struct SocketAddress *destination_address, GNUNET_TUN_calculate_icmp_checksum (icmp, payload, payload_length); - (void) GNUNET_HELPER_send (helper_handle, - (const struct GNUNET_MessageHeader*) buf, - GNUNET_YES, - NULL, NULL); + if (NULL != helper_handle) + (void) GNUNET_HELPER_send (helper_handle, + (const struct GNUNET_MessageHeader*) buf, + GNUNET_YES, + NULL, NULL); } } @@ -1924,12 +2188,12 @@ make_up_icmpv4_payload (struct TunnelState *state, struct GNUNET_TUN_UdpHeader *udp) { GNUNET_TUN_initialize_ipv4_header (ipp, - state->ri.remote_address.proto, + state->specifics.tcp_udp.ri.remote_address.proto, sizeof (struct GNUNET_TUN_TcpHeader), - &state->ri.remote_address.address.ipv4, - &state->ri.local_address.address.ipv4); - udp->source_port = htons (state->ri.remote_address.port); - udp->destination_port = htons (state->ri.local_address.port); + &state->specifics.tcp_udp.ri.remote_address.address.ipv4, + &state->specifics.tcp_udp.ri.local_address.address.ipv4); + udp->source_port = htons (state->specifics.tcp_udp.ri.remote_address.port); + udp->destination_port = htons (state->specifics.tcp_udp.ri.local_address.port); udp->len = htons (0); udp->crc = htons (0); } @@ -1950,12 +2214,12 @@ make_up_icmpv6_payload (struct TunnelState *state, struct GNUNET_TUN_UdpHeader *udp) { GNUNET_TUN_initialize_ipv6_header (ipp, - state->ri.remote_address.proto, + state->specifics.tcp_udp.ri.remote_address.proto, sizeof (struct GNUNET_TUN_TcpHeader), - &state->ri.remote_address.address.ipv6, - &state->ri.local_address.address.ipv6); - udp->source_port = htons (state->ri.remote_address.port); - udp->destination_port = htons (state->ri.local_address.port); + &state->specifics.tcp_udp.ri.remote_address.address.ipv6, + &state->specifics.tcp_udp.ri.local_address.address.ipv6); + udp->source_port = htons (state->specifics.tcp_udp.ri.remote_address.port); + udp->destination_port = htons (state->specifics.tcp_udp.ri.local_address.port); udp->len = htons (0); udp->crc = htons (0); } @@ -1989,6 +2253,16 @@ receive_icmp_remote (void *cls GNUNET_UNUSED, struct GNUNET_MESH_Tunnel *tunnel, char buf[sizeof (struct GNUNET_TUN_IPv6Header) + 8] GNUNET_ALIGN; int af; + if (GNUNET_YES == state->is_dns) + { + GNUNET_break_op (0); + return GNUNET_SYSERR; + } + if (GNUNET_SYSERR == state->is_dns) + { + /* tunnel is UDP/TCP from now on */ + state->is_dns = GNUNET_NO; + } GNUNET_STATISTICS_update (stats, gettext_noop ("# Bytes received from MESH"), pkt_len, GNUNET_NO); @@ -2004,8 +2278,8 @@ receive_icmp_remote (void *cls GNUNET_UNUSED, struct GNUNET_MESH_Tunnel *tunnel, pkt_len -= sizeof (struct GNUNET_EXIT_IcmpInternetMessage); af = (int) ntohl (msg->af); - if ( (NULL != state->heap_node) && - (af != state->ri.remote_address.af) ) + if ( (NULL != state->specifics.tcp_udp.heap_node) && + (af != state->specifics.tcp_udp.ri.remote_address.af) ) { /* other peer switched AF on this tunnel; not allowed */ GNUNET_break_op (0); @@ -2028,11 +2302,11 @@ receive_icmp_remote (void *cls GNUNET_UNUSED, struct GNUNET_MESH_Tunnel *tunnel, v4 = (const struct in_addr*) &msg[1]; payload = &v4[1]; pkt_len -= sizeof (struct in_addr); - state->ri.remote_address.address.ipv4 = *v4; - if (NULL == state->heap_node) + state->specifics.tcp_udp.ri.remote_address.address.ipv4 = *v4; + if (NULL == state->specifics.tcp_udp.heap_node) { - state->ri.remote_address.af = af; - state->ri.remote_address.proto = IPPROTO_ICMP; + state->specifics.tcp_udp.ri.remote_address.af = af; + state->specifics.tcp_udp.ri.remote_address.proto = IPPROTO_ICMP; setup_state_record (state); } /* check that ICMP type is something we want to support @@ -2086,11 +2360,11 @@ receive_icmp_remote (void *cls GNUNET_UNUSED, struct GNUNET_MESH_Tunnel *tunnel, v6 = (const struct in6_addr*) &msg[1]; payload = &v6[1]; pkt_len -= sizeof (struct in6_addr); - state->ri.remote_address.address.ipv6 = *v6; - if (NULL == state->heap_node) + state->specifics.tcp_udp.ri.remote_address.address.ipv6 = *v6; + if (NULL == state->specifics.tcp_udp.heap_node) { - state->ri.remote_address.af = af; - state->ri.remote_address.proto = IPPROTO_ICMPV6; + state->specifics.tcp_udp.ri.remote_address.af = af; + state->specifics.tcp_udp.ri.remote_address.proto = IPPROTO_ICMPV6; setup_state_record (state); } /* check that ICMP type is something we want to support @@ -2143,11 +2417,11 @@ receive_icmp_remote (void *cls GNUNET_UNUSED, struct GNUNET_MESH_Tunnel *tunnel, "Received ICMP data from %s for forwarding to %s\n", GNUNET_i2s (sender), inet_ntop (af, - &state->ri.remote_address.address, + &state->specifics.tcp_udp.ri.remote_address.address, buf, sizeof (buf))); } - send_icmp_packet_via_tun (&state->ri.remote_address, - &state->ri.local_address, + send_icmp_packet_via_tun (&state->specifics.tcp_udp.ri.remote_address, + &state->specifics.tcp_udp.ri.local_address, &msg->icmp_header, payload, pkt_len); return GNUNET_YES; @@ -2167,7 +2441,7 @@ static uint16_t make_up_icmp_service_payload (struct TunnelState *state, char *buf) { - switch (state->serv->address.af) + switch (state->specifics.tcp_udp.serv->address.af) { case AF_INET: { @@ -2231,6 +2505,16 @@ receive_icmp_service (void *cls GNUNET_UNUSED, struct GNUNET_MESH_Tunnel *tunnel char buf[sizeof (struct GNUNET_TUN_IPv6Header) + 8] GNUNET_ALIGN; const void *payload; + if (GNUNET_YES == state->is_dns) + { + GNUNET_break_op (0); + return GNUNET_SYSERR; + } + if (GNUNET_SYSERR == state->is_dns) + { + /* tunnel is UDP/TCP from now on */ + state->is_dns = GNUNET_NO; + } GNUNET_STATISTICS_update (stats, gettext_noop ("# Bytes received from MESH"), pkt_len, GNUNET_NO); @@ -2249,7 +2533,7 @@ receive_icmp_service (void *cls GNUNET_UNUSED, struct GNUNET_MESH_Tunnel *tunnel "Received data from %s for forwarding to ICMP service %s\n", GNUNET_i2s (sender), GNUNET_h2s (&msg->service_descriptor)); - if (NULL == state->serv) + if (NULL == state->specifics.tcp_udp.serv) { /* first packet to service must not be ICMP (cannot determine service!) */ GNUNET_break_op (0); @@ -2257,7 +2541,7 @@ receive_icmp_service (void *cls GNUNET_UNUSED, struct GNUNET_MESH_Tunnel *tunnel } icmp = msg->icmp_header; payload = &msg[1]; - state->ri.remote_address = state->serv->address; + state->specifics.tcp_udp.ri.remote_address = state->specifics.tcp_udp.serv->address; setup_state_record (state); /* check that ICMP type is something we want to support, @@ -2268,15 +2552,15 @@ receive_icmp_service (void *cls GNUNET_UNUSED, struct GNUNET_MESH_Tunnel *tunnel switch (msg->icmp_header.type) { case GNUNET_TUN_ICMPTYPE_ECHO_REPLY: - if (state->serv->address.af == AF_INET6) + if (state->specifics.tcp_udp.serv->address.af == AF_INET6) icmp.type = GNUNET_TUN_ICMPTYPE6_ECHO_REPLY; break; case GNUNET_TUN_ICMPTYPE_ECHO_REQUEST: - if (state->serv->address.af == AF_INET6) + if (state->specifics.tcp_udp.serv->address.af == AF_INET6) icmp.type = GNUNET_TUN_ICMPTYPE6_ECHO_REQUEST; break; case GNUNET_TUN_ICMPTYPE_DESTINATION_UNREACHABLE: - if (state->serv->address.af == AF_INET6) + if (state->specifics.tcp_udp.serv->address.af == AF_INET6) icmp.type = GNUNET_TUN_ICMPTYPE6_DESTINATION_UNREACHABLE; if (0 != pkt_len) { @@ -2287,7 +2571,7 @@ receive_icmp_service (void *cls GNUNET_UNUSED, struct GNUNET_MESH_Tunnel *tunnel pkt_len = make_up_icmp_service_payload (state, buf); break; case GNUNET_TUN_ICMPTYPE_TIME_EXCEEDED: - if (state->serv->address.af == AF_INET6) + if (state->specifics.tcp_udp.serv->address.af == AF_INET6) icmp.type = GNUNET_TUN_ICMPTYPE6_TIME_EXCEEDED; if (0 != pkt_len) { @@ -2298,7 +2582,7 @@ receive_icmp_service (void *cls GNUNET_UNUSED, struct GNUNET_MESH_Tunnel *tunnel pkt_len = make_up_icmp_service_payload (state, buf); break; case GNUNET_TUN_ICMPTYPE_SOURCE_QUENCH: - if (state->serv->address.af == AF_INET6) + if (state->specifics.tcp_udp.serv->address.af == AF_INET6) { GNUNET_STATISTICS_update (stats, gettext_noop ("# ICMPv4 packets dropped (impossible PT to v6)"), @@ -2326,15 +2610,15 @@ receive_icmp_service (void *cls GNUNET_UNUSED, struct GNUNET_MESH_Tunnel *tunnel switch (msg->icmp_header.type) { case GNUNET_TUN_ICMPTYPE6_ECHO_REPLY: - if (state->serv->address.af == AF_INET) + if (state->specifics.tcp_udp.serv->address.af == AF_INET) icmp.type = GNUNET_TUN_ICMPTYPE_ECHO_REPLY; break; case GNUNET_TUN_ICMPTYPE6_ECHO_REQUEST: - if (state->serv->address.af == AF_INET) + if (state->specifics.tcp_udp.serv->address.af == AF_INET) icmp.type = GNUNET_TUN_ICMPTYPE_ECHO_REQUEST; break; case GNUNET_TUN_ICMPTYPE6_DESTINATION_UNREACHABLE: - if (state->serv->address.af == AF_INET) + if (state->specifics.tcp_udp.serv->address.af == AF_INET) icmp.type = GNUNET_TUN_ICMPTYPE_DESTINATION_UNREACHABLE; if (0 != pkt_len) { @@ -2345,7 +2629,7 @@ receive_icmp_service (void *cls GNUNET_UNUSED, struct GNUNET_MESH_Tunnel *tunnel pkt_len = make_up_icmp_service_payload (state, buf); break; case GNUNET_TUN_ICMPTYPE6_TIME_EXCEEDED: - if (state->serv->address.af == AF_INET) + if (state->specifics.tcp_udp.serv->address.af == AF_INET) icmp.type = GNUNET_TUN_ICMPTYPE_TIME_EXCEEDED; if (0 != pkt_len) { @@ -2357,7 +2641,7 @@ receive_icmp_service (void *cls GNUNET_UNUSED, struct GNUNET_MESH_Tunnel *tunnel break; case GNUNET_TUN_ICMPTYPE6_PACKET_TOO_BIG: case GNUNET_TUN_ICMPTYPE6_PARAMETER_PROBLEM: - if (state->serv->address.af == AF_INET) + if (state->specifics.tcp_udp.serv->address.af == AF_INET) { GNUNET_STATISTICS_update (stats, gettext_noop ("# ICMPv6 packets dropped (impossible PT to v4)"), @@ -2386,8 +2670,8 @@ receive_icmp_service (void *cls GNUNET_UNUSED, struct GNUNET_MESH_Tunnel *tunnel return GNUNET_SYSERR; } - send_icmp_packet_via_tun (&state->ri.remote_address, - &state->ri.local_address, + send_icmp_packet_via_tun (&state->specifics.tcp_udp.ri.remote_address, + &state->specifics.tcp_udp.ri.local_address, &icmp, payload, pkt_len); return GNUNET_YES; @@ -2477,10 +2761,11 @@ send_udp_packet_via_tun (const struct SocketAddress *destination_address, GNUNET_assert (0); break; } - (void) GNUNET_HELPER_send (helper_handle, - (const struct GNUNET_MessageHeader*) buf, - GNUNET_YES, - NULL, NULL); + if (NULL != helper_handle) + (void) GNUNET_HELPER_send (helper_handle, + (const struct GNUNET_MessageHeader*) buf, + GNUNET_YES, + NULL, NULL); } } @@ -2512,6 +2797,16 @@ receive_udp_remote (void *cls GNUNET_UNUSED, struct GNUNET_MESH_Tunnel *tunnel, const void *payload; int af; + if (GNUNET_YES == state->is_dns) + { + GNUNET_break_op (0); + return GNUNET_SYSERR; + } + if (GNUNET_SYSERR == state->is_dns) + { + /* tunnel is UDP/TCP from now on */ + state->is_dns = GNUNET_NO; + } GNUNET_STATISTICS_update (stats, gettext_noop ("# Bytes received from MESH"), pkt_len, GNUNET_NO); @@ -2526,7 +2821,7 @@ receive_udp_remote (void *cls GNUNET_UNUSED, struct GNUNET_MESH_Tunnel *tunnel, msg = (const struct GNUNET_EXIT_UdpInternetMessage*) message; pkt_len -= sizeof (struct GNUNET_EXIT_UdpInternetMessage); af = (int) ntohl (msg->af); - state->ri.remote_address.af = af; + state->specifics.tcp_udp.ri.remote_address.af = af; switch (af) { case AF_INET: @@ -2543,7 +2838,7 @@ receive_udp_remote (void *cls GNUNET_UNUSED, struct GNUNET_MESH_Tunnel *tunnel, v4 = (const struct in_addr*) &msg[1]; payload = &v4[1]; pkt_len -= sizeof (struct in_addr); - state->ri.remote_address.address.ipv4 = *v4; + state->specifics.tcp_udp.ri.remote_address.address.ipv4 = *v4; break; case AF_INET6: if (pkt_len < sizeof (struct in6_addr)) @@ -2559,7 +2854,7 @@ receive_udp_remote (void *cls GNUNET_UNUSED, struct GNUNET_MESH_Tunnel *tunnel, v6 = (const struct in6_addr*) &msg[1]; payload = &v6[1]; pkt_len -= sizeof (struct in6_addr); - state->ri.remote_address.address.ipv6 = *v6; + state->specifics.tcp_udp.ri.remote_address.address.ipv6 = *v6; break; default: GNUNET_break_op (0); @@ -2571,18 +2866,18 @@ receive_udp_remote (void *cls GNUNET_UNUSED, struct GNUNET_MESH_Tunnel *tunnel, "Received data from %s for forwarding to UDP %s:%u\n", GNUNET_i2s (sender), inet_ntop (af, - &state->ri.remote_address.address, + &state->specifics.tcp_udp.ri.remote_address.address, buf, sizeof (buf)), (unsigned int) ntohs (msg->destination_port)); } - state->ri.remote_address.proto = IPPROTO_UDP; - state->ri.remote_address.port = msg->destination_port; - if (NULL == state->heap_node) + state->specifics.tcp_udp.ri.remote_address.proto = IPPROTO_UDP; + state->specifics.tcp_udp.ri.remote_address.port = msg->destination_port; + if (NULL == state->specifics.tcp_udp.heap_node) setup_state_record (state); if (0 != ntohs (msg->source_port)) - state->ri.local_address.port = msg->source_port; - send_udp_packet_via_tun (&state->ri.remote_address, - &state->ri.local_address, + state->specifics.tcp_udp.ri.local_address.port = msg->source_port; + send_udp_packet_via_tun (&state->specifics.tcp_udp.ri.remote_address, + &state->specifics.tcp_udp.ri.local_address, payload, pkt_len); return GNUNET_YES; } @@ -2612,6 +2907,16 @@ receive_udp_service (void *cls GNUNET_UNUSED, struct GNUNET_MESH_Tunnel *tunnel, const struct GNUNET_EXIT_UdpServiceMessage *msg; uint16_t pkt_len = ntohs (message->size); + if (GNUNET_YES == state->is_dns) + { + GNUNET_break_op (0); + return GNUNET_SYSERR; + } + if (GNUNET_SYSERR == state->is_dns) + { + /* tunnel is UDP/TCP from now on */ + state->is_dns = GNUNET_NO; + } GNUNET_STATISTICS_update (stats, gettext_noop ("# Bytes received from MESH"), pkt_len, GNUNET_NO); @@ -2626,13 +2931,13 @@ receive_udp_service (void *cls GNUNET_UNUSED, struct GNUNET_MESH_Tunnel *tunnel, } msg = (const struct GNUNET_EXIT_UdpServiceMessage*) message; pkt_len -= sizeof (struct GNUNET_EXIT_UdpServiceMessage); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Received data from %s for forwarding to UDP service %s on port %u\n", - GNUNET_i2s (sender), - GNUNET_h2s (&msg->service_descriptor), - (unsigned int) ntohs (msg->destination_port)); - if (NULL == (state->serv = find_service (udp_services, &msg->service_descriptor, - ntohs (msg->destination_port)))) + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Received data from %s for forwarding to UDP service %s on port %u\n", + GNUNET_i2s (sender), + GNUNET_h2s (&msg->service_descriptor), + (unsigned int) ntohs (msg->destination_port)); + if (NULL == (state->specifics.tcp_udp.serv = find_service (udp_services, &msg->service_descriptor, + ntohs (msg->destination_port)))) { GNUNET_log (GNUNET_ERROR_TYPE_INFO, _("No service found for %s on port %d!\n"), @@ -2643,12 +2948,12 @@ receive_udp_service (void *cls GNUNET_UNUSED, struct GNUNET_MESH_Tunnel *tunnel, 1, GNUNET_NO); return GNUNET_SYSERR; } - state->ri.remote_address = state->serv->address; + state->specifics.tcp_udp.ri.remote_address = state->specifics.tcp_udp.serv->address; setup_state_record (state); if (0 != ntohs (msg->source_port)) - state->ri.local_address.port = msg->source_port; - send_udp_packet_via_tun (&state->ri.remote_address, - &state->ri.local_address, + state->specifics.tcp_udp.ri.local_address.port = msg->source_port; + send_udp_packet_via_tun (&state->specifics.tcp_udp.ri.remote_address, + &state->specifics.tcp_udp.ri.local_address, &msg[1], pkt_len); return GNUNET_YES; } @@ -2670,6 +2975,7 @@ new_tunnel (void *cls GNUNET_UNUSED, struct GNUNET_MESH_Tunnel *tunnel, { struct TunnelState *s = GNUNET_malloc (sizeof (struct TunnelState)); + s->is_dns = GNUNET_SYSERR; GNUNET_STATISTICS_update (stats, gettext_noop ("# Inbound MESH tunnels created"), 1, GNUNET_NO); @@ -2697,23 +3003,37 @@ clean_tunnel (void *cls GNUNET_UNUSED, const struct GNUNET_MESH_Tunnel *tunnel, struct TunnelState *s = tunnel_ctx; struct TunnelMessageQueue *tnq; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Tunnel destroyed\n"); - while (NULL != (tnq = s->head)) + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Tunnel destroyed\n"); + if (GNUNET_SYSERR == s->is_dns) { - GNUNET_CONTAINER_DLL_remove (s->head, - s->tail, - tnq); - GNUNET_free (tnq); + GNUNET_free (s); + return; } - if (s->heap_node != NULL) + if (GNUNET_YES == s->is_dns) { - GNUNET_assert (GNUNET_YES == - GNUNET_CONTAINER_multihashmap_remove (connections_map, - &s->state_key, - s)); - GNUNET_CONTAINER_heap_remove_node (s->heap_node); - s->heap_node = NULL; + if (tunnels[s->specifics.dns.my_id] == s) + tunnels[s->specifics.dns.my_id] = NULL; + GNUNET_free_non_null (s->specifics.dns.reply); + } + else + { + while (NULL != (tnq = s->specifics.tcp_udp.head)) + { + GNUNET_CONTAINER_DLL_remove (s->specifics.tcp_udp.head, + s->specifics.tcp_udp.tail, + tnq); + GNUNET_free (tnq); + } + if (NULL != s->specifics.tcp_udp.heap_node) + { + GNUNET_assert (GNUNET_YES == + GNUNET_CONTAINER_multihashmap_remove (connections_map, + &s->specifics.tcp_udp.state_key, + s)); + GNUNET_CONTAINER_heap_remove_node (s->specifics.tcp_udp.heap_node); + s->specifics.tcp_udp.heap_node = NULL; + } } if (NULL != s->th) { @@ -2733,7 +3053,7 @@ clean_tunnel (void *cls GNUNET_UNUSED, const struct GNUNET_MESH_Tunnel *tunnel, */ static int free_iterate (void *cls GNUNET_UNUSED, - const GNUNET_HashCode * hash GNUNET_UNUSED, void *value) + const struct GNUNET_HashCode * hash GNUNET_UNUSED, void *value) { GNUNET_free (value); return GNUNET_YES; @@ -2751,6 +3071,7 @@ cleanup (void *cls GNUNET_UNUSED, GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Exit service is shutting down now\n"); + if (helper_handle != NULL) { GNUNET_HELPER_stop (helper_handle); @@ -2784,6 +3105,11 @@ cleanup (void *cls GNUNET_UNUSED, GNUNET_CONTAINER_multihashmap_destroy (udp_services); udp_services = NULL; } + if (NULL != dnsstub) + { + GNUNET_DNSSTUB_stop (dnsstub); + dnsstub = NULL; + } if (stats != NULL) { GNUNET_STATISTICS_destroy (stats, GNUNET_NO); @@ -2854,18 +3180,19 @@ add_services (int proto, } serv = GNUNET_malloc (sizeof (struct LocalService)); + serv->address.proto = proto; serv->my_port = (uint16_t) local_port; serv->address.port = remote_port; if (0 == strcmp ("localhost4", hostname)) { - const char *ip4addr = exit_argv[4]; + const char *ip4addr = exit_argv[5]; serv->address.af = AF_INET; - GNUNET_assert (1 != inet_pton (AF_INET, ip4addr, &serv->address.address.ipv4)); + GNUNET_assert (1 == inet_pton (AF_INET, ip4addr, &serv->address.address.ipv4)); } else if (0 == strcmp ("localhost6", hostname)) { - const char *ip6addr = exit_argv[2]; + const char *ip6addr = exit_argv[3]; serv->address.af = AF_INET6; GNUNET_assert (1 == inet_pton (AF_INET6, ip6addr, &serv->address.address.ipv6)); @@ -2963,31 +3290,6 @@ read_service_conf (void *cls GNUNET_UNUSED, const char *section) } -/** - * Test if the given AF is supported by this system. - * - * @param af to test - * @return GNUNET_OK if the AF is supported - */ -static int -test_af (int af) -{ - int s; - - s = socket (af, SOCK_STREAM, 0); - if (-1 == s) - { - if (EAFNOSUPPORT == errno) - return GNUNET_NO; - GNUNET_log_strerror (GNUNET_ERROR_TYPE_ERROR, - "socket"); - return GNUNET_SYSERR; - } - close (s); - return GNUNET_OK; -} - - /** * @brief Main function that will be run by the scheduler. * @@ -3009,10 +3311,12 @@ run (void *cls, char *const *args GNUNET_UNUSED, {&receive_tcp_service, GNUNET_MESSAGE_TYPE_VPN_TCP_TO_SERVICE_START, 0}, {&receive_tcp_remote, GNUNET_MESSAGE_TYPE_VPN_TCP_TO_INTERNET_START, 0}, {&receive_tcp_data, GNUNET_MESSAGE_TYPE_VPN_TCP_DATA_TO_EXIT, 0}, + {&receive_dns_request, GNUNET_MESSAGE_TYPE_VPN_DNS_TO_INTERNET, 0}, {NULL, 0, 0} }; static GNUNET_MESH_ApplicationType apptypes[] = { + GNUNET_APPLICATION_TYPE_END, GNUNET_APPLICATION_TYPE_END, GNUNET_APPLICATION_TYPE_END, GNUNET_APPLICATION_TYPE_END @@ -3024,25 +3328,37 @@ run (void *cls, char *const *args GNUNET_UNUSED, char *ipv6prefix_s; char *ipv4addr; char *ipv4mask; + char *binary; + char *regex; + char *prefixed_regex; + struct in_addr dns_exit4; + struct in6_addr dns_exit6; + char *dns_exit; - if (GNUNET_YES != - GNUNET_OS_check_helper_binary ("gnunet-helper-exit")) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - _("`%s' must be installed SUID, refusing to run\n"), - "gnunet-helper-exit"); - global_ret = 1; - return; - } cfg = cfg_; - stats = GNUNET_STATISTICS_create ("exit", cfg); ipv4_exit = GNUNET_CONFIGURATION_get_value_yesno (cfg, "exit", "EXIT_IPV4"); ipv6_exit = GNUNET_CONFIGURATION_get_value_yesno (cfg, "exit", "EXIT_IPV6"); ipv4_enabled = GNUNET_CONFIGURATION_get_value_yesno (cfg, "exit", "ENABLE_IPV4"); ipv6_enabled = GNUNET_CONFIGURATION_get_value_yesno (cfg, "exit", "ENABLE_IPV6"); + if ( (ipv4_exit) || (ipv6_exit) ) + { + binary = GNUNET_OS_get_libexec_binary_path ("gnunet-helper-exit"); + if (GNUNET_YES != + GNUNET_OS_check_helper_binary (binary)) + { + GNUNET_free (binary); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("`%s' must be installed SUID, refusing to run\n"), + "gnunet-helper-exit"); + global_ret = 1; + return; + } + GNUNET_free (binary); + } + stats = GNUNET_STATISTICS_create ("exit", cfg); if ( (ipv4_exit || ipv4_enabled) && - GNUNET_OK != test_af (AF_INET)) + GNUNET_OK != GNUNET_NETWORK_test_pf (PF_INET)) { GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("This system does not support IPv4, will disable IPv4 functions despite them being enabled in the configuration\n")); @@ -3050,7 +3366,7 @@ run (void *cls, char *const *args GNUNET_UNUSED, ipv4_enabled = GNUNET_NO; } if ( (ipv6_exit || ipv6_enabled) && - GNUNET_OK != test_af (AF_INET6)) + GNUNET_OK != GNUNET_NETWORK_test_pf (PF_INET6)) { GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("This system does not support IPv6, will disable IPv6 functions despite them being enabled in the configuration\n")); @@ -3076,6 +3392,26 @@ run (void *cls, char *const *args GNUNET_UNUSED, GNUNET_SCHEDULER_shutdown (); return; } + + dns_exit = NULL; + if ( (GNUNET_YES == + GNUNET_CONFIGURATION_get_value_yesno (cfg_, "exit", "ENABLE_DNS")) && + ( (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_string (cfg, "exit", + "DNS_RESOLVER", + &dns_exit)) || + ( (1 != inet_pton (AF_INET, dns_exit, &dns_exit4)) && + (1 != inet_pton (AF_INET6, dns_exit, &dns_exit6)) ) ) ) + { + GNUNET_log_config_invalid (GNUNET_ERROR_TYPE_ERROR, "dns", "DNS_RESOLVER", + _("need a valid IPv4 or IPv6 address\n")); + GNUNET_free_non_null (dns_exit); + dns_exit = NULL; + } + if (NULL != dns_exit) + dnsstub = GNUNET_DNSSTUB_start (dns_exit); + + app_idx = 0; if (GNUNET_YES == ipv4_exit) { @@ -3087,6 +3423,11 @@ run (void *cls, char *const *args GNUNET_UNUSED, apptypes[app_idx] = GNUNET_APPLICATION_TYPE_IPV6_GATEWAY; app_idx++; } + if (NULL != dns_exit) + { + apptypes[app_idx] = GNUNET_APPLICATION_TYPE_INTERNET_RESOLVER; + app_idx++; + } GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, &cleanup, cls); @@ -3194,14 +3535,14 @@ run (void *cls, char *const *args GNUNET_UNUSED, } exit_argv[7] = NULL; - udp_services = GNUNET_CONTAINER_multihashmap_create (65536); - tcp_services = GNUNET_CONTAINER_multihashmap_create (65536); + udp_services = GNUNET_CONTAINER_multihashmap_create (65536, GNUNET_NO); + tcp_services = GNUNET_CONTAINER_multihashmap_create (65536, GNUNET_NO); GNUNET_CONFIGURATION_iterate_sections (cfg, &read_service_conf, NULL); - connections_map = GNUNET_CONTAINER_multihashmap_create (65536); + connections_map = GNUNET_CONTAINER_multihashmap_create (65536, GNUNET_NO); connections_heap = GNUNET_CONTAINER_heap_create (GNUNET_CONTAINER_HEAP_ORDER_MIN); mesh_handle - = GNUNET_MESH_connect (cfg, 42 /* queue size */, NULL, + = GNUNET_MESH_connect (cfg, NULL, &new_tunnel, &clean_tunnel, handlers, apptypes); @@ -3210,9 +3551,49 @@ run (void *cls, char *const *args GNUNET_UNUSED, GNUNET_SCHEDULER_shutdown (); return; } - helper_handle = GNUNET_HELPER_start ("gnunet-helper-exit", - exit_argv, - &message_token, NULL); + + /* Mesh handle acquired, now announce regular expressions matching our exit */ + if ( (GNUNET_YES == ipv4_enabled) && (GNUNET_YES == ipv4_exit) ) + { + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_string (cfg, + "exit", + "EXIT_RANGE_IPV4_REGEX", + ®ex)) + regex = GNUNET_strdup ("(0|1)*"); + (void) GNUNET_asprintf (&prefixed_regex, "%s%s%s", + GNUNET_APPLICATION_TYPE_EXIT_REGEX_PREFIX, + "4", regex); + GNUNET_MESH_announce_regex (mesh_handle, + prefixed_regex, + REGEX_MAX_PATH_LEN_IPV4); + GNUNET_free (regex); + GNUNET_free (prefixed_regex); + } + + if (GNUNET_YES == ipv6_enabled && GNUNET_YES == ipv6_exit) + { + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_string (cfg, + "exit", + "EXIT_RANGE_IPV6_REGEX", + ®ex)) + regex = GNUNET_strdup ("(0|1)*"); + (void) GNUNET_asprintf (&prefixed_regex, "%s%s%s", + GNUNET_APPLICATION_TYPE_EXIT_REGEX_PREFIX, + "6", regex); + GNUNET_MESH_announce_regex (mesh_handle, + prefixed_regex, + REGEX_MAX_PATH_LEN_IPV6); + GNUNET_free (regex); + GNUNET_free (prefixed_regex); + } + if ((ipv4_exit) || (ipv6_exit)) + helper_handle = GNUNET_HELPER_start (GNUNET_NO, + "gnunet-helper-exit", + exit_argv, + &message_token, + NULL, NULL); } @@ -3230,6 +3611,9 @@ main (int argc, char *const *argv) GNUNET_GETOPT_OPTION_END }; + if (GNUNET_OK != GNUNET_STRINGS_get_utf8_args (argc, argv, &argc, &argv)) + return 2; + return (GNUNET_OK == GNUNET_PROGRAM_run (argc, argv, "gnunet-daemon-exit", gettext_noop diff --git a/src/exit/gnunet-helper-exit-windows.c b/src/exit/gnunet-helper-exit-windows.c new file mode 100644 index 0000000..c4519fb --- /dev/null +++ b/src/exit/gnunet-helper-exit-windows.c @@ -0,0 +1,1568 @@ +/* + This file is part of GNUnet. + (C) 2010, 2012 Christian Grothoff + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. + */ +/** + * @file exit/gnunet-helper-exit-windows.c + * @brief the helper for the EXIT service in win32 builds. + * Opens a virtual network-interface, sends data received on the if to stdout, + * sends data received on stdin to the interface + * @author Christian M. Fuchs + * + * The following list of people have reviewed this code and considered + * it safe since the last modification (if you reviewed it, please + * have your name added to the list): + * + */ +#include +#include +#include +#include +#include +#include +#include +#include "platform.h" +#include "tap-windows.h" +/** + * Need 'struct GNUNET_MessageHeader'. + */ +#include "gnunet_common.h" + +/** + * Need VPN message types. + */ +#include "gnunet_protocols.h" + +/** + * Should we print (interesting|debug) messages that can happen during + * normal operation? + */ +#define DEBUG GNUNET_NO + +#if DEBUG +/* FIXME: define with varargs... */ +#define LOG_DEBUG(msg) fprintf (stderr, "%s", msg); +#else +#define LOG_DEBUG(msg) do {} while (0) +#endif + + +/** + * Maximum size of a GNUnet message (GNUNET_SERVER_MAX_MESSAGE_SIZE) + */ +#define MAX_SIZE 65536 + +/** + * Name or Path+Name of our win32 driver. + * The .sys and .cat files HAVE to be in the same location as this file! + */ +#define INF_FILE "share/gnunet/tapw32/OemWin2k.inf" + +/** + * Name or Path+Name of our win64 driver. + * The .sys and .cat files HAVE to be in the same location as this file! + */ +#define INF_FILE64 "share/gnunet/tapw64/OemWin2k.inf" + +/** + * Hardware ID used in the inf-file. + * This might change over time, as openvpn advances their driver + */ +#define HARDWARE_ID "tap0901" + +/** + * Minimum major-id of the driver version we can work with + */ +#define TAP_WIN_MIN_MAJOR 9 + +/** + * Minimum minor-id of the driver version we can work with. + * v <= 7 has buggy IPv6. + * v == 8 is broken for small IPv4 Packets + */ +#define TAP_WIN_MIN_MINOR 9 + +/** + * Time in seconds to wait for our virtual device to go up after telling it to do so. + * + * openvpn doesn't specify a value, 4 seems sane for testing, even for openwrt + * (in fact, 4 was chosen by a fair dice roll...) + */ +#define TAP32_POSTUP_WAITTIME 4 + +/** + * Location of the network interface list resides in registry. + */ +#define INTERFACE_REGISTRY_LOCATION "SYSTEM\\CurrentControlSet\\Control\\Network\\{4D36E972-E325-11CE-BFC1-08002BE10318}" + +/** + * Our local process' PID. Used for creating a sufficiently unique additional + * hardware ID for our device. + */ +static char secondary_hwid[LINE_LEN / 2]; + +/** + * Device's visible Name, used to identify a network device in netsh. + * eg: "Local Area Connection 9" + */ +static char device_visible_name[256]; + +/** + * This is our own local instance of a virtual network interface + * It is (somewhat) equivalent to using tun/tap in unixoid systems + * + * Upon initialization, we create such an device node. + * Upon termination, we remove it again. + * + * If we crash this device might stay around. + */ +static HDEVINFO DeviceInfo = INVALID_HANDLE_VALUE; + +/** + * Registry Key we hand over to windows to spawn a new virtual interface + */ +static SP_DEVINFO_DATA DeviceNode; + +/** + * GUID of our virtual device in the form of + * {12345678-1234-1234-1234-123456789abc} - in hex + */ +static char device_guid[256]; + + +/** + * Possible states of an IO facility. + */ +enum IO_State +{ + + /** + * overlapped I/O is ready for work + */ + IOSTATE_READY = 0, + + /** + * overlapped I/O has been queued + */ + IOSTATE_QUEUED, + + /** + * overlapped I/O has finished, but is waiting for it's write-partner + */ + IOSTATE_WAITING, + + /** + * there is a full buffer waiting + */ + IOSTATE_RESUME, + + /** + * Operlapped IO states for facility objects + * overlapped I/O has failed, stop processing + */ + IOSTATE_FAILED + +}; + + +/** + * A IO Object + read/writebuffer + buffer-size for windows asynchronous IO handling + */ +struct io_facility +{ + /** + * The mode the state machine associated with this object is in. + */ + enum IO_State facility_state; + + /** + * If the path is open or blocked in general (used for quickly checking) + */ + BOOL path_open; // BOOL is winbool (int), NOT boolean (unsigned char)! + + /** + * Windows Object-Handle (used for accessing TAP and STDIN/STDOUT) + */ + HANDLE handle; + + /** + * Overlaped IO structure used for asynchronous IO in windows. + */ + OVERLAPPED overlapped; + + /** + * Buffer for reading things to and writing from... + */ + unsigned char buffer[MAX_SIZE]; + + /** + * How much of this buffer was used when reading or how much data can be written + */ + DWORD buffer_size; + + /** + * Amount of data actually written or read by readfile/writefile. + */ + DWORD buffer_size_processed; + + /** + * How much of this buffer we have written in total + */ + DWORD buffer_size_written; +}; + +/** + * ReOpenFile is only available as of XP SP2 and 2003 SP1 + */ +WINBASEAPI HANDLE WINAPI ReOpenFile (HANDLE, DWORD, DWORD, DWORD); + +/** + * IsWow64Process definition for our is_win64, as this is a kernel function + */ +typedef BOOL (WINAPI *LPFN_ISWOW64PROCESS) (HANDLE, PBOOL); + +/** + * Determines if the host OS is win32 or win64 + * + * @return true if + */ +BOOL +is_win64 () +{ +#if defined(_WIN64) + //this is a win64 binary, + return TRUE; +#elif defined(_WIN32) + //this is a 32bit binary, and we need to check if we are running in WOW64 + BOOL success = FALSE; + BOOL on_wow64 = FALSE; + LPFN_ISWOW64PROCESS IsWow64Process = (LPFN_ISWOW64PROCESS) GetProcAddress (GetModuleHandle ("kernel32"), "IsWow64Process"); + + if (NULL != IsWow64Process) + success = IsWow64Process (GetCurrentProcess (), &on_wow64); + + return success && on_wow64; +#endif +} +/** + * Wrapper for executing a shellcommand in windows. + * + * @param command - the command + parameters to execute + * @return * exitcode of the program executed, + * * EINVAL (cmd/file not found) + * * EPIPE (could not read STDOUT) + */ +static int +execute_shellcommand (const char *command) +{ + FILE *pipe; + + if ( (NULL == command) || + (NULL == (pipe = _popen (command, "rt"))) ) + return EINVAL; + +#if DEBUG + fprintf (stderr, "DEBUG: Command output: \n"); + char output[LINE_LEN]; + while (NULL != fgets (output, sizeof (output), pipe)) + fprintf (stderr, "%s", output); +#endif + + return _pclose (pipe); +} + + +/** + * @brief Sets the IPv6-Address given in address on the interface dev + * + * @param address the IPv6-Address + * @param prefix_len the length of the network-prefix + */ +static int +set_address6 (const char *address, unsigned long prefix_len) +{ + int ret = EINVAL; + char command[LINE_LEN]; + struct sockaddr_in6 sa6; + + /* + * parse the new address + */ + memset (&sa6, 0, sizeof (struct sockaddr_in6)); + sa6.sin6_family = AF_INET6; + if (1 != inet_pton (AF_INET6, address, &sa6.sin6_addr.s6_addr)) + { + fprintf (stderr, "ERROR: Failed to parse address `%s': %s\n", address, + strerror (errno)); + return -1; + } + + /* + * prepare the command + */ + snprintf (command, LINE_LEN, + "netsh interface ipv6 add address \"%s\" %s/%d store=active", + device_visible_name, address, prefix_len); + /* + * Set the address + */ + ret = execute_shellcommand (command); + + /* Did it work?*/ + if (0 != ret) + fprintf (stderr, "FATAL: Setting IPv6 address failed: %s\n", strerror (ret)); + return ret; +} + + +/** + * @brief Removes the IPv6-Address given in address from the interface dev + * + * @param dev the interface to remove + * @param address the IPv4-Address + * @param mask the netmask + */ +static void +remove_address6 (const char *address) +{ + char command[LINE_LEN]; + int ret = EINVAL; + + // sanity checking was already done in set_address6 + /* + * prepare the command + */ + snprintf (command, LINE_LEN, + "netsh interface ipv6 delete address \"%s\" store=persistent", + device_visible_name, address); + /* + * Set the address + */ + ret = execute_shellcommand (command); + + /* Did it work?*/ + if (0 != ret) + fprintf (stderr, "FATAL: removing IPv6 address failed: %s\n", strerror (ret)); +} + + +/** + * @brief Sets the IPv4-Address given in address on the interface dev + * + * @param dev the interface to configure + * @param address the IPv4-Address + * @param mask the netmask + */ +static int +set_address4 (const char *address, const char *mask) +{ + int ret = EINVAL; + char command[LINE_LEN]; + + struct sockaddr_in addr; + addr.sin_family = AF_INET; + + /* + * Parse the address + */ + if (1 != inet_pton (AF_INET, address, &addr.sin_addr.s_addr)) + { + fprintf (stderr, "ERROR: Failed to parse address `%s': %s\n", address, + strerror (errno)); + return -1; + } + // Set Device to Subnet-Mode? + // do we really need tun.c:2925 ? + + /* + * prepare the command + */ + snprintf (command, LINE_LEN, + "netsh interface ipv4 add address \"%s\" %s %s store=active", + device_visible_name, address, mask); + /* + * Set the address + */ + ret = execute_shellcommand (command); + + /* Did it work?*/ + if (0 != ret) + fprintf (stderr, "FATAL: Setting IPv4 address failed: %s\n", strerror (ret)); + return ret; +} + + +/** + * @brief Removes the IPv4-Address given in address from the interface dev + * + * @param dev the interface to remove + * @param address the IPv4-Address + * @param mask the netmask + */ +static void +remove_address4 (const char *address) +{ + char command[LINE_LEN]; + int ret = EINVAL; + + // sanity checking was already done in set_address4 + + /* + * prepare the command + */ + snprintf (command, LINE_LEN, + "netsh interface ipv4 delete address \"%s\" gateway=all store=persistent", + device_visible_name, address); + /* + * Set the address + */ + ret = execute_shellcommand (command); + + /* Did it work?*/ + if (0 != ret) + fprintf (stderr, "FATAL: removing IPv4 address failed: %s\n", strerror (ret)); +} + + +/** + * Setup a new virtual interface to use for tunneling. + * + * @return: TRUE if setup was successful, else FALSE + */ +static BOOL +setup_interface () +{ + /* + * where to find our inf-file. (+ the "full" path, after windows found") + * + * We do not directly input all the props here, because openvpn will update + * these details over time. + */ + char inf_file_path[MAX_PATH]; + char * temp_inf_filename; + char hwidlist[LINE_LEN + 4]; + char class_name[128]; + GUID class_guid; + int str_length = 0; + + /** + * Set the device's hardware ID and add it to a list. + * This information will later on identify this device in registry. + */ + strncpy (hwidlist, HARDWARE_ID, LINE_LEN); + /** + * this is kind of over-complicated, but allows keeps things independent of + * how the openvpn-hwid is actually stored. + * + * A HWID list is double-\0 terminated and \0 separated + */ + str_length = strlen (hwidlist) + 1; + strncpy (&hwidlist[str_length], secondary_hwid, LINE_LEN); + str_length += strlen (&hwidlist[str_length]) + 1; + + /** + * Locate the inf-file, we need to store it somewhere where the system can + * find it. We need to pick the correct driver for win32/win64. + */ + if (is_win64()) + GetFullPathNameA (INF_FILE64, MAX_PATH, inf_file_path, &temp_inf_filename); + else + GetFullPathNameA (INF_FILE, MAX_PATH, inf_file_path, &temp_inf_filename); + + fprintf (stderr, "INFO: Located our driver's .inf file at %s\n", inf_file_path); + /** + * Bootstrap our device info using the drivers inf-file + */ + if ( ! SetupDiGetINFClassA (inf_file_path, + &class_guid, + class_name, sizeof (class_name) / sizeof (char), + NULL)) + return FALSE; + + /** + * Collect all the other needed information... + * let the system fill our this form + */ + DeviceInfo = SetupDiCreateDeviceInfoList (&class_guid, NULL); + if (DeviceInfo == INVALID_HANDLE_VALUE) + return FALSE; + + DeviceNode.cbSize = sizeof (SP_DEVINFO_DATA); + if ( ! SetupDiCreateDeviceInfoA (DeviceInfo, + class_name, + &class_guid, + NULL, + 0, + DICD_GENERATE_ID, + &DeviceNode)) + return FALSE; + + /* Deploy all the information collected into the registry */ + if ( ! SetupDiSetDeviceRegistryPropertyA (DeviceInfo, + &DeviceNode, + SPDRP_HARDWAREID, + (LPBYTE) hwidlist, + str_length * sizeof (char))) + return FALSE; + + /* Install our new class(=device) into the system */ + if ( ! SetupDiCallClassInstaller (DIF_REGISTERDEVICE, + DeviceInfo, + &DeviceNode)) + return FALSE; + + /* This system call tends to take a while (several seconds!) on + "modern" Windoze systems */ + if ( ! UpdateDriverForPlugAndPlayDevicesA (NULL, + secondary_hwid, + inf_file_path, + INSTALLFLAG_FORCE | INSTALLFLAG_NONINTERACTIVE, + NULL)) //reboot required? NEVER! + return FALSE; + + fprintf (stderr, "DEBUG: successfully created a network device\n"); + return TRUE; +} + + +/** + * Remove our new virtual interface to use for tunneling. + * This function must be called AFTER setup_interface! + * + * @return: TRUE if destruction was successful, else FALSE + */ +static BOOL +remove_interface () +{ + SP_REMOVEDEVICE_PARAMS remove; + + if (INVALID_HANDLE_VALUE == DeviceInfo) + return FALSE; + + remove.ClassInstallHeader.cbSize = sizeof (SP_CLASSINSTALL_HEADER); + remove.HwProfile = 0; + remove.Scope = DI_REMOVEDEVICE_GLOBAL; + remove.ClassInstallHeader.InstallFunction = DIF_REMOVE; + /* + * 1. Prepare our existing device information set, and place the + * uninstall related information into the structure + */ + if ( ! SetupDiSetClassInstallParamsA (DeviceInfo, + (PSP_DEVINFO_DATA) & DeviceNode, + &remove.ClassInstallHeader, + sizeof (remove))) + return FALSE; + /* + * 2. Uninstall the virtual interface using the class installer + */ + if ( ! SetupDiCallClassInstaller (DIF_REMOVE, + DeviceInfo, + (PSP_DEVINFO_DATA) & DeviceNode)) + return FALSE; + + SetupDiDestroyDeviceInfoList (DeviceInfo); + + fprintf (stderr, "DEBUG: removed interface successfully\n"); + + return TRUE; +} + + +/** + * Do all the lookup necessary to retrieve the inteface's actual name + * off the registry. + * + * @return: TRUE if we were able to lookup the interface's name, else FALSE + */ +static BOOL +resolve_interface_name () +{ + SP_DEVINFO_LIST_DETAIL_DATA device_details; + char pnp_instance_id [MAX_DEVICE_ID_LEN]; + HKEY adapter_key_handle; + LONG status; + DWORD len; + int i = 0; + int retrys; + BOOL retval = FALSE; + char adapter[] = INTERFACE_REGISTRY_LOCATION; + + /* We can obtain the PNP instance ID from our setupapi handle */ + device_details.cbSize = sizeof (device_details); + if (CR_SUCCESS != CM_Get_Device_ID_ExA (DeviceNode.DevInst, + (PCHAR) pnp_instance_id, + MAX_DEVICE_ID_LEN, + 0, //must be 0 + NULL)) //hMachine, we are local + return FALSE; + + fprintf (stderr, "DEBUG: Resolving interface name for network device %s\n",pnp_instance_id); + + /* Registry is incredibly slow, retry for up to 30 seconds to allow registry to refresh */ + for (retrys = 0; retrys < 120 && !retval; retrys++) + { + /* sleep for 250ms*/ + Sleep (250); + + /* Now we can use this ID to locate the correct networks interface in registry */ + if (ERROR_SUCCESS != RegOpenKeyExA ( + HKEY_LOCAL_MACHINE, + adapter, + 0, + KEY_READ, + &adapter_key_handle)) + return FALSE; + + /* Of course there is a multitude of entries here, with arbitrary names, + * thus we need to iterate through there. + */ + while (!retval) + { + char instance_key[256]; + char query_key [256]; + HKEY instance_key_handle; + char pnpinstanceid_name[] = "PnpInstanceID"; + char pnpinstanceid_value[256]; + char adaptername_name[] = "Name"; + DWORD data_type; + + len = 256 * sizeof (char); + /* optain a subkey of {4D36E972-E325-11CE-BFC1-08002BE10318} */ + status = RegEnumKeyExA ( + adapter_key_handle, + i, + instance_key, + &len, + NULL, + NULL, + NULL, + NULL); + + /* this may fail due to one of two reasons: + * we are at the end of the list*/ + if (ERROR_NO_MORE_ITEMS == status) + break; + // * we found a broken registry key, continue with the next key. + if (ERROR_SUCCESS != status) + goto cleanup; + + /* prepare our new query string: */ + snprintf (query_key, 256, "%s\\%s\\Connection", + adapter, + instance_key); + + /* look inside instance_key\\Connection */ + if (ERROR_SUCCESS != RegOpenKeyExA ( + HKEY_LOCAL_MACHINE, + query_key, + 0, + KEY_READ, + &instance_key_handle)) + goto cleanup; + + /* now, read our PnpInstanceID */ + len = sizeof (pnpinstanceid_value); + status = RegQueryValueExA (instance_key_handle, + pnpinstanceid_name, + NULL, //reserved, always NULL according to MSDN + &data_type, + (LPBYTE) pnpinstanceid_value, + &len); + + if (status != ERROR_SUCCESS || data_type != REG_SZ) + goto cleanup; + + /* compare the value we got to our devices PNPInstanceID*/ + if (0 != strncmp (pnpinstanceid_value, pnp_instance_id, + sizeof (pnpinstanceid_value) / sizeof (char))) + goto cleanup; + + len = sizeof (device_visible_name); + status = RegQueryValueExA ( + instance_key_handle, + adaptername_name, + NULL, //reserved, always NULL according to MSDN + &data_type, + (LPBYTE) device_visible_name, + &len); + + if (status != ERROR_SUCCESS || data_type != REG_SZ) + goto cleanup; + + /* + * we have successfully found OUR instance, + * save the device GUID before exiting + */ + + strncpy (device_guid, instance_key, 256); + retval = TRUE; + fprintf (stderr, "DEBUG: Interface Name lookup succeeded on retry %d, got \"%s\" %s\n", retrys, device_visible_name, device_guid); + +cleanup: + RegCloseKey (instance_key_handle); + + ++i; + } + + RegCloseKey (adapter_key_handle); + } + return retval; +} + + +/** + * Determines the version of the installed TAP32 driver and checks if it's sufficiently new for GNUNET + * + * @param handle the handle to our tap device + * @return TRUE if the version is sufficient, else FALSE + */ +static BOOL +check_tapw32_version (HANDLE handle) +{ + ULONG version[3]; + DWORD len; + memset (&(version), 0, sizeof (version)); + + if (DeviceIoControl (handle, TAP_WIN_IOCTL_GET_VERSION, + &version, sizeof (version), + &version, sizeof (version), &len, NULL)) + fprintf (stderr, "INFO: TAP-Windows Driver Version %d.%d %s\n", + (int) version[0], + (int) version[1], + (version[2] ? "(DEBUG)" : "")); + + if ((version[0] != TAP_WIN_MIN_MAJOR) || + (version[1] < TAP_WIN_MIN_MINOR )){ + fprintf (stderr, "FATAL: This version of gnunet requires a TAP-Windows driver that is at least version %d.%d\n", + TAP_WIN_MIN_MAJOR, + TAP_WIN_MIN_MINOR); + return FALSE; + } + + return TRUE; +} + + +/** + * Creates a tun-interface called dev; + * + * @return the fd to the tun or -1 on error + */ +static HANDLE +init_tun () +{ + char device_path[256]; + HANDLE handle; + + if (! setup_interface ()) + { + errno = ENODEV; + return INVALID_HANDLE_VALUE; + } + + if (! resolve_interface_name ()) + { + errno = ENODEV; + return INVALID_HANDLE_VALUE; + } + + /* Open Windows TAP-Windows adapter */ + snprintf (device_path, sizeof (device_path), "%s%s%s", + USERMODEDEVICEDIR, + device_guid, + TAP_WIN_SUFFIX); + + handle = CreateFile ( + device_path, + GENERIC_READ | GENERIC_WRITE, + 0, /* was: FILE_SHARE_READ */ + 0, + OPEN_EXISTING, + FILE_ATTRIBUTE_SYSTEM | FILE_FLAG_OVERLAPPED, + 0 + ); + + if (INVALID_HANDLE_VALUE == handle) + { + fprintf (stderr, "FATAL: CreateFile failed on TAP device: %s\n", device_path); + return handle; + } + + /* get driver version info */ + if (! check_tapw32_version (handle)) + { + CloseHandle (handle); + return INVALID_HANDLE_VALUE; + } + + /* TODO (opt?): get MTU-Size */ + + fprintf (stderr, "DEBUG: successfully opened TAP device\n"); + return handle; +} + + +/** + * Brings a TAP device up and sets it to connected state. + * + * @param handle the handle to our TAP device + * @return True if the operation succeeded, else false + */ +static BOOL +tun_up (HANDLE handle) +{ + ULONG status = TRUE; + DWORD len; + if (! DeviceIoControl (handle, TAP_WIN_IOCTL_SET_MEDIA_STATUS, + &status, sizeof (status), + &status, sizeof (status), &len, NULL)) + { + fprintf (stderr, "FATAL: TAP driver ignored request to UP interface (DeviceIoControl call)\n"); + return FALSE; + } + + /* Wait for the device to go UP, might take some time. */ + Sleep (TAP32_POSTUP_WAITTIME * 1000); + fprintf (stderr, "DEBUG: successfully set TAP device to UP\n"); + + return TRUE; +} + + +/** + * Attempts to read off an input facility (tap or named pipe) in overlapped mode. + * + * 1. + * If the input facility is in IOSTATE_READY, it will issue a new read operation to the + * input handle. Then it goes into IOSTATE_QUEUED state. + * In case the read succeeded instantly the input facility enters 3. + * + * 2. + * If the input facility is in IOSTATE_QUEUED state, it will check if the queued read has finished already. + * If it has finished, go to state 3. + * If it has failed, set IOSTATE_FAILED + * + * 3. + * If the output facility is in state IOSTATE_READY, the read-buffer is copied to the output buffer. + * The input facility enters state IOSTATE_READY + * The output facility enters state IOSTATE_READY + * If the output facility is in state IOSTATE_QUEUED, the input facility enters IOSTATE_WAITING + * + * IOSTATE_WAITING is reset by the output facility, once it has completed. + * + * @param input_facility input named pipe or file to work with. + * @param output_facility output pipe or file to hand over data to. + * @return false if an event reset was impossible (OS error), else true + */ +static BOOL +attempt_read_tap (struct io_facility * input_facility, + struct io_facility * output_facility) +{ + struct GNUNET_MessageHeader * hdr; + unsigned short size; + + switch (input_facility->facility_state) + { + case IOSTATE_READY: + { + if (! ResetEvent (input_facility->overlapped.hEvent)) + { + return FALSE; + } + + input_facility->buffer_size = 0; + + /* Check how the task is handled */ + if (ReadFile (input_facility->handle, + input_facility->buffer, + sizeof (input_facility->buffer) - sizeof (struct GNUNET_MessageHeader), + &input_facility->buffer_size, + &input_facility->overlapped)) + {/* async event processed immediately*/ + + /* reset event manually*/ + if (! SetEvent (input_facility->overlapped.hEvent)) + return FALSE; + + fprintf (stderr, "DEBUG: tap read succeeded immediately\n"); + + /* we successfully read something from the TAP and now need to + * send it our via STDOUT. Is that possible at the moment? */ + if ((IOSTATE_READY == output_facility->facility_state || + IOSTATE_WAITING == output_facility->facility_state) + && (0 < input_facility->buffer_size)) + { /* hand over this buffers content and apply message header for gnunet */ + hdr = (struct GNUNET_MessageHeader *) output_facility->buffer; + size = input_facility->buffer_size + sizeof (struct GNUNET_MessageHeader); + + memcpy (output_facility->buffer + sizeof (struct GNUNET_MessageHeader), + input_facility->buffer, + input_facility->buffer_size); + + output_facility->buffer_size = size; + hdr->size = htons (size); + hdr->type = htons (GNUNET_MESSAGE_TYPE_VPN_HELPER); + output_facility->facility_state = IOSTATE_READY; + } + else if (0 < input_facility->buffer_size) + /* If we have have read our buffer, wait for our write-partner*/ + input_facility->facility_state = IOSTATE_WAITING; + } + else /* operation was either queued or failed*/ + { + int err = GetLastError (); + if (ERROR_IO_PENDING == err) + { /* operation queued */ + input_facility->facility_state = IOSTATE_QUEUED; + } + else + { /* error occurred, let the rest of the elements finish */ + input_facility->path_open = FALSE; + input_facility->facility_state = IOSTATE_FAILED; + if (IOSTATE_WAITING == output_facility->facility_state) + output_facility->path_open = FALSE; + + fprintf (stderr, "FATAL: Read from handle failed, allowing write to finish\n"); + } + } + } + return TRUE; + // We are queued and should check if the read has finished + case IOSTATE_QUEUED: + { + // there was an operation going on already, check if that has completed now. + + if (GetOverlappedResult (input_facility->handle, + &input_facility->overlapped, + &input_facility->buffer_size, + FALSE)) + {/* successful return for a queued operation */ + if (! ResetEvent (input_facility->overlapped.hEvent)) + return FALSE; + + fprintf (stderr, "DEBUG: tap read succeeded delayed\n"); + + /* we successfully read something from the TAP and now need to + * send it our via STDOUT. Is that possible at the moment? */ + if ((IOSTATE_READY == output_facility->facility_state || + IOSTATE_WAITING == output_facility->facility_state) + && 0 < input_facility->buffer_size) + { /* hand over this buffers content and apply message header for gnunet */ + hdr = (struct GNUNET_MessageHeader *) output_facility->buffer; + size = input_facility->buffer_size + sizeof (struct GNUNET_MessageHeader); + + memcpy (output_facility->buffer + sizeof (struct GNUNET_MessageHeader), + input_facility->buffer, + input_facility->buffer_size); + + output_facility->buffer_size = size; + hdr->size = htons(size); + hdr->type = htons (GNUNET_MESSAGE_TYPE_VPN_HELPER); + output_facility->facility_state = IOSTATE_READY; + input_facility->facility_state = IOSTATE_READY; + } + else if (0 < input_facility->buffer_size) + { /* If we have have read our buffer, wait for our write-partner*/ + input_facility->facility_state = IOSTATE_WAITING; + // TODO: shall we attempt to fill our buffer or should we wait for our write-partner to finish? + } + } + else + { /* operation still pending/queued or failed? */ + int err = GetLastError (); + if ((ERROR_IO_INCOMPLETE != err) && (ERROR_IO_PENDING != err)) + { /* error occurred, let the rest of the elements finish */ + input_facility->path_open = FALSE; + input_facility->facility_state = IOSTATE_FAILED; + if (IOSTATE_WAITING == output_facility->facility_state) + output_facility->path_open = FALSE; + fprintf (stderr, "FATAL: Read from handle failed, allowing write to finish\n"); + } + } + } + return TRUE; + case IOSTATE_RESUME: + hdr = (struct GNUNET_MessageHeader *) output_facility->buffer; + size = input_facility->buffer_size + sizeof (struct GNUNET_MessageHeader); + + memcpy (output_facility->buffer + sizeof (struct GNUNET_MessageHeader), + input_facility->buffer, + input_facility->buffer_size); + + output_facility->buffer_size = size; + hdr->size = htons (size); + hdr->type = htons (GNUNET_MESSAGE_TYPE_VPN_HELPER); + output_facility->facility_state = IOSTATE_READY; + input_facility->facility_state = IOSTATE_READY; + return TRUE; + default: + return TRUE; + } +} + + +/** + * Attempts to read off an input facility (tap or named pipe) in overlapped mode. + * + * 1. + * If the input facility is in IOSTATE_READY, it will issue a new read operation to the + * input handle. Then it goes into IOSTATE_QUEUED state. + * In case the read succeeded instantly the input facility enters 3. + * + * 2. + * If the input facility is in IOSTATE_QUEUED state, it will check if the queued read has finished already. + * If it has finished, go to state 3. + * If it has failed, set IOSTATE_FAILED + * + * 3. + * If the facility is finished with ready + * The read-buffer is copied to the output buffer, except for the GNUNET_MessageHeader. + * The input facility enters state IOSTATE_READY + * The output facility enters state IOSTATE_READY + * If the output facility is in state IOSTATE_QUEUED, the input facility enters IOSTATE_WAITING + * + * IOSTATE_WAITING is reset by the output facility, once it has completed. + * + * @param input_facility input named pipe or file to work with. + * @param output_facility output pipe or file to hand over data to. + * @return false if an event reset was impossible (OS error), else true + */ +static BOOL +attempt_read_stdin (struct io_facility * input_facility, + struct io_facility * output_facility) +{ + struct GNUNET_MessageHeader * hdr; + + switch (input_facility->facility_state) + { + case IOSTATE_READY: + { + input_facility->buffer_size = 0; + +partial_read_iostate_ready: + if (! ResetEvent (input_facility->overlapped.hEvent)) + return FALSE; + + /* Check how the task is handled */ + if (ReadFile (input_facility->handle, + input_facility->buffer + input_facility->buffer_size, + sizeof (input_facility->buffer) - input_facility->buffer_size, + &input_facility->buffer_size_processed, + &input_facility->overlapped)) + {/* async event processed immediately*/ + hdr = (struct GNUNET_MessageHeader *) input_facility->buffer; + + /* reset event manually*/ + if (!SetEvent (input_facility->overlapped.hEvent)) + return FALSE; + + fprintf (stderr, "DEBUG: stdin read succeeded immediately\n"); + input_facility->buffer_size += input_facility->buffer_size_processed; + + if (ntohs (hdr->type) != GNUNET_MESSAGE_TYPE_VPN_HELPER || + ntohs (hdr->size) > sizeof (input_facility->buffer)) + { + fprintf (stderr, "WARNING: Protocol violation, got GNUnet Message type %h, size %h\n", ntohs (hdr->type), ntohs (hdr->size)); + input_facility->facility_state = IOSTATE_READY; + return TRUE; + } + /* we got the a part of a packet */ + if (ntohs (hdr->size) > input_facility->buffer_size) + goto partial_read_iostate_ready; + + /* have we read more than 0 bytes of payload? (sizeread > header)*/ + if (input_facility->buffer_size > sizeof (struct GNUNET_MessageHeader) && + ((IOSTATE_READY == output_facility->facility_state) || + (IOSTATE_WAITING == output_facility->facility_state))) + {/* we successfully read something from the TAP and now need to + * send it our via STDOUT. Is that possible at the moment? */ + + /* hand over this buffers content and strip gnunet message header */ + memcpy (output_facility->buffer, + input_facility->buffer + sizeof (struct GNUNET_MessageHeader), + input_facility->buffer_size - sizeof (struct GNUNET_MessageHeader)); + output_facility->buffer_size = input_facility->buffer_size - sizeof (struct GNUNET_MessageHeader); + output_facility->facility_state = IOSTATE_READY; + input_facility->facility_state = IOSTATE_READY; + } + else if (input_facility->buffer_size > sizeof (struct GNUNET_MessageHeader)) + /* If we have have read our buffer, wait for our write-partner*/ + input_facility->facility_state = IOSTATE_WAITING; + else /* we read nothing */ + input_facility->facility_state = IOSTATE_READY; + } + else /* operation was either queued or failed*/ + { + int err = GetLastError (); + if (ERROR_IO_PENDING == err) /* operation queued */ + input_facility->facility_state = IOSTATE_QUEUED; + else + { /* error occurred, let the rest of the elements finish */ + input_facility->path_open = FALSE; + input_facility->facility_state = IOSTATE_FAILED; + if (IOSTATE_WAITING == output_facility->facility_state) + output_facility->path_open = FALSE; + + fprintf (stderr, "FATAL: Read from handle failed, allowing write to finish\n"); + } + } + } + return TRUE; + // We are queued and should check if the read has finished + case IOSTATE_QUEUED: + { + // there was an operation going on already, check if that has completed now. + if (GetOverlappedResult (input_facility->handle, + &input_facility->overlapped, + &input_facility->buffer_size_processed, + FALSE)) + {/* successful return for a queued operation */ + hdr = (struct GNUNET_MessageHeader *) input_facility->buffer; + + if (! ResetEvent (input_facility->overlapped.hEvent)) + return FALSE; + + fprintf (stderr, "DEBUG: stdin read succeeded delayed\n"); + input_facility->buffer_size += input_facility->buffer_size_processed; + + if ((ntohs (hdr->type) != GNUNET_MESSAGE_TYPE_VPN_HELPER) || + (ntohs (hdr->size) > sizeof (input_facility->buffer))) + { + fprintf (stderr, "WARNING: Protocol violation, got GNUnet Message type %h, size %h\n", ntohs (hdr->type), ntohs (hdr->size)); + input_facility->facility_state = IOSTATE_READY; + return TRUE; + } + /* we got the a part of a packet */ + if (ntohs (hdr->size) > input_facility->buffer_size ); + goto partial_read_iostate_ready; + + /* we successfully read something from the TAP and now need to + * send it our via STDOUT. Is that possible at the moment? */ + if ((IOSTATE_READY == output_facility->facility_state || + IOSTATE_WAITING == output_facility->facility_state) + && input_facility->buffer_size > sizeof(struct GNUNET_MessageHeader)) + { /* hand over this buffers content and strip gnunet message header */ + memcpy (output_facility->buffer, + input_facility->buffer + sizeof(struct GNUNET_MessageHeader), + input_facility->buffer_size - sizeof(struct GNUNET_MessageHeader)); + output_facility->buffer_size = input_facility->buffer_size - sizeof(struct GNUNET_MessageHeader); + output_facility->facility_state = IOSTATE_READY; + input_facility->facility_state = IOSTATE_READY; + } + else if (input_facility->buffer_size > sizeof(struct GNUNET_MessageHeader)) + input_facility->facility_state = IOSTATE_WAITING; + else + input_facility->facility_state = IOSTATE_READY; + } + else + { /* operation still pending/queued or failed? */ + int err = GetLastError (); + if ((ERROR_IO_INCOMPLETE != err) && (ERROR_IO_PENDING != err)) + { /* error occurred, let the rest of the elements finish */ + input_facility->path_open = FALSE; + input_facility->facility_state = IOSTATE_FAILED; + if (IOSTATE_WAITING == output_facility->facility_state) + output_facility->path_open = FALSE; + fprintf (stderr, "FATAL: Read from handle failed, allowing write to finish\n"); + } + } + } + return TRUE; + case IOSTATE_RESUME: /* Our buffer was filled already but our write facility was busy. */ + memcpy (output_facility->buffer, + input_facility->buffer + sizeof (struct GNUNET_MessageHeader), + input_facility->buffer_size - sizeof (struct GNUNET_MessageHeader)); + output_facility->buffer_size = input_facility->buffer_size - sizeof (struct GNUNET_MessageHeader); + output_facility->facility_state = IOSTATE_READY; + input_facility->facility_state = IOSTATE_READY; + return TRUE; + default: + return TRUE; + } +} + + +/** + * Attempts to write to an output facility (tap or named pipe) in overlapped mode. + * + * TODO: high level description + * + * @param output_facility output pipe or file to hand over data to. + * @param input_facility input named pipe or file to work with. + * @return false if an event reset was impossible (OS error), else true + */ +static BOOL +attempt_write (struct io_facility * output_facility, + struct io_facility * input_facility) +{ + switch (output_facility->facility_state) + { + case IOSTATE_READY: + output_facility->buffer_size_written = 0; + +continue_partial_write: + if (! ResetEvent (output_facility->overlapped.hEvent)) + return FALSE; + + /* Check how the task was handled */ + if (WriteFile (output_facility->handle, + output_facility->buffer + output_facility->buffer_size_written, + output_facility->buffer_size - output_facility->buffer_size_written, + &output_facility->buffer_size_processed, + &output_facility->overlapped)) + {/* async event processed immediately*/ + + fprintf (stderr, "DEBUG: write succeeded immediately\n"); + output_facility->buffer_size_written += output_facility->buffer_size_processed; + + /* reset event manually*/ + if (! SetEvent (output_facility->overlapped.hEvent)) + return FALSE; + + /* partial write */ + if (output_facility->buffer_size_written < output_facility->buffer_size) + goto continue_partial_write; + + /* we are now waiting for our buffer to be filled*/ + output_facility->facility_state = IOSTATE_WAITING; + + /* we successfully wrote something and now need to reset our reader */ + if (IOSTATE_WAITING == input_facility->facility_state) + input_facility->facility_state = IOSTATE_RESUME; + else if (IOSTATE_FAILED == input_facility->facility_state) + output_facility->path_open = FALSE; + } + else /* operation was either queued or failed*/ + { + int err = GetLastError (); + if (ERROR_IO_PENDING == err) + { /* operation queued */ + output_facility->facility_state = IOSTATE_QUEUED; + } + else + { /* error occurred, close this path */ + output_facility->path_open = FALSE; + output_facility->facility_state = IOSTATE_FAILED; + fprintf (stderr, "FATAL: Write to handle failed, exiting\n"); + } + } + return TRUE; + case IOSTATE_QUEUED: + // there was an operation going on already, check if that has completed now. + + if (GetOverlappedResult (output_facility->handle, + &output_facility->overlapped, + &output_facility->buffer_size_processed, + FALSE)) + {/* successful return for a queued operation */ + if (! ResetEvent (output_facility->overlapped.hEvent)) + return FALSE; + + fprintf (stderr, "DEBUG: write succeeded delayed\n"); + output_facility->buffer_size_written += output_facility->buffer_size_processed; + + /* partial write */ + if (output_facility->buffer_size_written < output_facility->buffer_size) + goto continue_partial_write; + + /* we are now waiting for our buffer to be filled*/ + output_facility->facility_state = IOSTATE_WAITING; + + /* we successfully wrote something and now need to reset our reader */ + if (IOSTATE_WAITING == input_facility->facility_state) + input_facility->facility_state = IOSTATE_RESUME; + else if (IOSTATE_FAILED == input_facility->facility_state) + output_facility->path_open = FALSE; + } + else + { /* operation still pending/queued or failed? */ + int err = GetLastError (); + if ((ERROR_IO_INCOMPLETE != err) && (ERROR_IO_PENDING != err)) + { /* error occurred, close this path */ + output_facility->path_open = FALSE; + output_facility->facility_state = IOSTATE_FAILED; + fprintf (stderr, "FATAL: Write to handle failed, exiting\n"); + } + } + default: + return TRUE; + } +} + + +/** + * Initialize a overlapped structure + * + * @param elem the element to initilize + * @param initial_state the initial state for this instance + * @param signaled if the hEvent created should default to signaled or not + * @return true on success, else false + */ +static BOOL +initialize_io_facility (struct io_facility * elem, + int initial_state, + BOOL signaled) +{ + elem->path_open = TRUE; + elem->handle = INVALID_HANDLE_VALUE; + elem->facility_state = initial_state; + elem->buffer_size = 0; + elem->overlapped.hEvent = CreateEvent (NULL, TRUE, signaled, NULL); + if (NULL == elem->overlapped.hEvent) + return FALSE; + + return TRUE; +} + + +/** + * Start forwarding to and from the tunnel. + * + * @param fd_tun tunnel FD + */ +static void +run (HANDLE tap_handle) +{ + /* IO-Facility for reading from our virtual interface */ + struct io_facility tap_read; + /* IO-Facility for writing to our virtual interface */ + struct io_facility tap_write; + /* IO-Facility for reading from stdin */ + struct io_facility std_in; + /* IO-Facility for writing to stdout */ + struct io_facility std_out; + + HANDLE parent_std_in_handle = GetStdHandle (STD_INPUT_HANDLE); + HANDLE parent_std_out_handle = GetStdHandle (STD_OUTPUT_HANDLE); + + /* tun up: */ + /* we do this HERE and not beforehand (in init_tun()), in contrast to openvpn + * to remove the need to flush the arp cache, handle DHCP and wrong IPs. + * + * DHCP and such are all features we will never use in gnunet afaik. + * But for openvpn those are essential. + */ + if (! tun_up (tap_handle)) + return; + + /* Initialize our overlapped IO structures*/ + if (! (initialize_io_facility (&tap_read, IOSTATE_READY, FALSE) + && initialize_io_facility (&tap_write, IOSTATE_WAITING, TRUE) + && initialize_io_facility (&std_in, IOSTATE_READY, FALSE) + && initialize_io_facility (&std_out, IOSTATE_WAITING, TRUE))) + goto teardown_final; + + /* Handles for STDIN and STDOUT */ + tap_read.handle = tap_handle; + tap_write.handle = tap_handle; + +#ifdef DEBUG_TO_CONSOLE + /* Debug output to console STDIN/STDOUT*/ + std_in.handle = parent_std_in_handle; + std_out.handle = parent_std_out_handle; + +#else + fprintf (stderr, "DEBUG: reopening stdin/out for overlapped IO\n"); + /* + * Find out the types of our handles. + * This part is a problem, because in windows we need to handle files, + * pipes and the console differently. + */ + if ((FILE_TYPE_PIPE != GetFileType (parent_std_in_handle)) || + (FILE_TYPE_PIPE != GetFileType (parent_std_out_handle))) + { + fprintf (stderr, "ERROR: stdin/stdout must be named pipes\n"); + goto teardown; + } + + std_in.handle = ReOpenFile (parent_std_in_handle, + GENERIC_READ, + FILE_SHARE_WRITE | FILE_SHARE_READ, + FILE_FLAG_OVERLAPPED); + + if (INVALID_HANDLE_VALUE == std_in.handle) + { + fprintf (stderr, "FATAL: Could not reopen stdin for in overlapped mode, has to be a named pipe\n"); + goto teardown; + } + + std_out.handle = ReOpenFile (parent_std_out_handle, + GENERIC_WRITE, + FILE_SHARE_READ, + FILE_FLAG_OVERLAPPED); + + if (INVALID_HANDLE_VALUE == std_out.handle) + { + fprintf (stderr, "FATAL: Could not reopen stdout for in overlapped mode, has to be a named pipe\n"); + goto teardown; + } +#endif + + fprintf (stderr, "DEBUG: mainloop has begun\n"); + + while (std_out.path_open || tap_write.path_open) + { + /* perform READ from stdin if possible */ + if (std_in.path_open && (! attempt_read_stdin (&std_in, &tap_write))) + break; + + /* perform READ from tap if possible */ + if (tap_read.path_open && (! attempt_read_tap (&tap_read, &std_out))) + break; + + /* perform WRITE to tap if possible */ + if (tap_write.path_open && (! attempt_write (&tap_write, &std_in))) + break; + + /* perform WRITE to STDOUT if possible */ + if (std_out.path_open && (! attempt_write (&std_out, &tap_read))) + break; + } + +teardown: + + fprintf (stderr, "DEBUG: teardown initiated\n"); + + CancelIo (tap_handle); + CancelIo (std_in.handle); + CancelIo (std_out.handle); + +teardown_final: + + CloseHandle (tap_handle); +} + + +/** + * Open VPN tunnel interface. + * + * @param argc must be 6 + * @param argv 0: binary name ("gnunet-helper-exit") + * 1: tunnel interface name ("gnunet-exit") + * 2: IPv4 "physical" interface name ("eth0"), or "%" to not do IPv4 NAT + * 3: IPv6 address ("::1"), or "-" to skip IPv6 + * 4: IPv6 netmask length in bits ("64") [ignored if #4 is "-"] + * 5: IPv4 address ("1.2.3.4"), or "-" to skip IPv4 + * 6: IPv4 netmask ("255.255.0.0") [ignored if #4 is "-"] + */ +int +main (int argc, char **argv) +{ + char hwid[LINE_LEN]; + HANDLE handle; + int global_ret = 0; + BOOL have_ip4 = FALSE; + BOOL have_ip6 = FALSE; + + if (6 != argc) + { + fprintf (stderr, "FATAL: must supply 5 arguments\nUsage:\ngnunet-helper-vpn \n", argv[0]); + return 1; + } + + strncpy (hwid, argv[1], LINE_LEN); + hwid[LINE_LEN - 1] = '\0'; + + /* + * We use our PID for finding/resolving the control-panel name of our virtual + * device. PIDs are (of course) unique at runtime, thus we can safely use it + * as additional hardware-id for our device. + */ + snprintf (secondary_hwid, LINE_LEN / 2, "%s-%d", + hwid, + _getpid ()); + + if (INVALID_HANDLE_VALUE == (handle = init_tun ())) + { + fprintf (stderr, "FATAL: could not initialize virtual-interface %s with IPv6 %s/%s and IPv4 %s/%s\n", + hwid, + argv[3], + argv[4], + argv[5], + argv[6]); + global_ret = -1; + goto cleanup; + } + + fprintf (stderr, "DEBUG: Setting IPs, if needed\n"); + if (0 != strcmp (argv[3], "-")) + { + const char *address = argv[3]; + long prefix_len = atol (argv[4]); + + if ((prefix_len < 1) || (prefix_len > 127)) + { + fprintf (stderr, "FATAL: ipv6 prefix_len out of range\n"); + global_ret = -1; + goto cleanup; + } + + fprintf (stderr, "DEBUG: Setting IP6 address: %s/%d\n",address,prefix_len); + if (0 != (global_ret = set_address6 (address, prefix_len))) + goto cleanup; + + have_ip6 = TRUE; + } + + if (0 != strcmp (argv[5], "-")) + { + const char *address = argv[5]; + const char *mask = argv[6]; + + fprintf (stderr, "DEBUG: Setting IP4 address: %s/%s\n",address,mask); + if (0 != (global_ret = set_address4 (address, mask))) + goto cleanup; + + // setup NAT, if possible + if (0 != strcmp (argv[2], "%")) + { + /* TODO: " Windows Firewall with Advanced Security" (lol) + * + * MS has REMOVED the routing/nat capabilities since Vista, thus + * we can not setup NAT like in XP. Our best bet is + * to determine if we are running on XP, if we do, use netsh routing + * else we need to use WFAS and do things ourselfs + */ + } + + have_ip4 = TRUE; + } + + run (handle); + global_ret = 0; +cleanup: + + if (have_ip4) + { + const char *address = argv[5]; + fprintf (stderr, "DEBUG: Removing IP4 address\n"); + remove_address4 (address); + } + if (have_ip6) + { + const char *address = argv[3]; + fprintf (stderr, "DEBUG: Removing IP6 address\n"); + remove_address6 (address); + } + + fprintf (stderr, "DEBUG: removing interface\n"); + remove_interface (); + fprintf (stderr, "DEBUG: graceful exit completed\n"); + + return global_ret; +} diff --git a/src/exit/gnunet-helper-exit.c b/src/exit/gnunet-helper-exit.c index 573bb7a..882778b 100644 --- a/src/exit/gnunet-helper-exit.c +++ b/src/exit/gnunet-helper-exit.c @@ -83,12 +83,38 @@ static const char *sbin_iptables; struct in6_ifreq { struct in6_addr ifr6_addr; - __u32 ifr6_prefixlen; + uint32_t ifr6_prefixlen; /* __u32 in the original */ int ifr6_ifindex; }; #endif +/** + * Open '/dev/null' and make the result the given + * file descriptor. + * + * @param target_fd desired FD to point to /dev/null + * @param flags open flags (O_RDONLY, O_WRONLY) + */ +static void +open_dev_null (int target_fd, + int flags) +{ + int fd; + + fd = open ("/dev/null", flags); + if (-1 == fd) + abort (); + if (fd == target_fd) + return; + if (-1 == dup2 (fd, target_fd)) + { + (void) close (fd); + abort (); + } + (void) close (fd); +} + /** * Run the given command and wait for it to complete. @@ -119,7 +145,9 @@ fork_and_exec (const char *file, /* close stdin/stdout to not cause interference with the helper's main protocol! */ (void) close (0); + open_dev_null (0, O_RDONLY); (void) close (1); + open_dev_null (1, O_WRONLY); (void) execv (file, cmd); /* can only get here on error */ fprintf (stderr, @@ -760,7 +788,7 @@ main (int argc, char **argv) run (fd_tun); global_ret = 0; cleanup: - close (fd_tun); + (void) close (fd_tun); return global_ret; } diff --git a/src/fragmentation/Makefile.am b/src/fragmentation/Makefile.am index c5027c7..333a270 100644 --- a/src/fragmentation/Makefile.am +++ b/src/fragmentation/Makefile.am @@ -15,10 +15,11 @@ libgnunetfragmentation_la_SOURCES = \ defragmentation.c libgnunetfragmentation_la_LIBADD = -lm \ $(top_builddir)/src/statistics/libgnunetstatistics.la \ - $(top_builddir)/src/util/libgnunetutil.la + $(top_builddir)/src/util/libgnunetutil.la \ + $(LTLIBINTL) libgnunetfragmentation_la_LDFLAGS = \ $(GN_LIB_LDFLAGS) \ - -version-info 1:0:1 + -version-info 2:0:0 check_PROGRAMS = \ test_fragmentation @@ -33,4 +34,4 @@ test_fragmentation_LDADD = \ $(top_builddir)/src/fragmentation/libgnunetfragmentation.la \ $(top_builddir)/src/util/libgnunetutil.la -EXTRA_DIST = test_fragmentation_data.conf \ No newline at end of file +EXTRA_DIST = test_fragmentation_data.conf diff --git a/src/fragmentation/Makefile.in b/src/fragmentation/Makefile.in index 2c297cb..90f155e 100644 --- a/src/fragmentation/Makefile.in +++ b/src/fragmentation/Makefile.in @@ -1,9 +1,9 @@ -# Makefile.in generated by automake 1.11.1 from Makefile.am. +# Makefile.in generated by automake 1.11.6 from Makefile.am. # @configure_input@ # Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, -# 2003, 2004, 2005, 2006, 2007, 2008, 2009 Free Software Foundation, -# Inc. +# 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Free Software +# Foundation, Inc. # This Makefile.in is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. @@ -16,6 +16,23 @@ @SET_MAKE@ VPATH = @srcdir@ +am__make_dryrun = \ + { \ + am__dry=no; \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + echo 'am--echo: ; @echo "AM" OK' | $(MAKE) -f - 2>/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } pkgdatadir = $(datadir)/@PACKAGE@ pkgincludedir = $(includedir)/@PACKAGE@ pkglibdir = $(libdir)/@PACKAGE@ @@ -41,14 +58,15 @@ DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 am__aclocal_m4_deps = $(top_srcdir)/m4/absolute-header.m4 \ $(top_srcdir)/m4/align.m4 $(top_srcdir)/m4/argz.m4 \ - $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/iconv.m4 \ - $(top_srcdir)/m4/lib-ld.m4 $(top_srcdir)/m4/lib-link.m4 \ - $(top_srcdir)/m4/lib-prefix.m4 $(top_srcdir)/m4/libcurl.m4 \ - $(top_srcdir)/m4/libgcrypt.m4 $(top_srcdir)/m4/libtool.m4 \ - $(top_srcdir)/m4/libunistring.m4 $(top_srcdir)/m4/ltdl.m4 \ - $(top_srcdir)/m4/ltoptions.m4 $(top_srcdir)/m4/ltsugar.m4 \ - $(top_srcdir)/m4/ltversion.m4 $(top_srcdir)/m4/lt~obsolete.m4 \ - $(top_srcdir)/m4/nls.m4 $(top_srcdir)/m4/po.m4 \ + $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/glib-2.0.m4 \ + $(top_srcdir)/m4/iconv.m4 $(top_srcdir)/m4/lib-ld.m4 \ + $(top_srcdir)/m4/lib-link.m4 $(top_srcdir)/m4/lib-prefix.m4 \ + $(top_srcdir)/m4/libcurl.m4 $(top_srcdir)/m4/libgcrypt.m4 \ + $(top_srcdir)/m4/libtool.m4 $(top_srcdir)/m4/libunistring.m4 \ + $(top_srcdir)/m4/ltdl.m4 $(top_srcdir)/m4/ltoptions.m4 \ + $(top_srcdir)/m4/ltsugar.m4 $(top_srcdir)/m4/ltversion.m4 \ + $(top_srcdir)/m4/lt~obsolete.m4 $(top_srcdir)/m4/nls.m4 \ + $(top_srcdir)/m4/pkg.m4 $(top_srcdir)/m4/po.m4 \ $(top_srcdir)/m4/progtest.m4 $(top_srcdir)/acinclude.m4 \ $(top_srcdir)/configure.ac am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ @@ -78,17 +96,25 @@ am__nobase_list = $(am__nobase_strip_setup); \ am__base_list = \ sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \ sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g' +am__uninstall_files_from_dir = { \ + test -z "$$files" \ + || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \ + || { echo " ( cd '$$dir' && rm -f" $$files ")"; \ + $(am__cd) "$$dir" && rm -f $$files; }; \ + } am__installdirs = "$(DESTDIR)$(libdir)" LTLIBRARIES = $(lib_LTLIBRARIES) +am__DEPENDENCIES_1 = libgnunetfragmentation_la_DEPENDENCIES = \ $(top_builddir)/src/statistics/libgnunetstatistics.la \ - $(top_builddir)/src/util/libgnunetutil.la + $(top_builddir)/src/util/libgnunetutil.la \ + $(am__DEPENDENCIES_1) am_libgnunetfragmentation_la_OBJECTS = fragmentation.lo \ defragmentation.lo libgnunetfragmentation_la_OBJECTS = \ $(am_libgnunetfragmentation_la_OBJECTS) -AM_V_lt = $(am__v_lt_$(V)) -am__v_lt_ = $(am__v_lt_$(AM_DEFAULT_VERBOSITY)) +AM_V_lt = $(am__v_lt_@AM_V@) +am__v_lt_ = $(am__v_lt_@AM_DEFAULT_V@) am__v_lt_0 = --silent libgnunetfragmentation_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ @@ -109,26 +135,31 @@ LTCOMPILE = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) \ $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) \ $(AM_CFLAGS) $(CFLAGS) -AM_V_CC = $(am__v_CC_$(V)) -am__v_CC_ = $(am__v_CC_$(AM_DEFAULT_VERBOSITY)) +AM_V_CC = $(am__v_CC_@AM_V@) +am__v_CC_ = $(am__v_CC_@AM_DEFAULT_V@) am__v_CC_0 = @echo " CC " $@; -AM_V_at = $(am__v_at_$(V)) -am__v_at_ = $(am__v_at_$(AM_DEFAULT_VERBOSITY)) +AM_V_at = $(am__v_at_@AM_V@) +am__v_at_ = $(am__v_at_@AM_DEFAULT_V@) am__v_at_0 = @ CCLD = $(CC) LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ $(AM_LDFLAGS) $(LDFLAGS) -o $@ -AM_V_CCLD = $(am__v_CCLD_$(V)) -am__v_CCLD_ = $(am__v_CCLD_$(AM_DEFAULT_VERBOSITY)) +AM_V_CCLD = $(am__v_CCLD_@AM_V@) +am__v_CCLD_ = $(am__v_CCLD_@AM_DEFAULT_V@) am__v_CCLD_0 = @echo " CCLD " $@; -AM_V_GEN = $(am__v_GEN_$(V)) -am__v_GEN_ = $(am__v_GEN_$(AM_DEFAULT_VERBOSITY)) +AM_V_GEN = $(am__v_GEN_@AM_V@) +am__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@) am__v_GEN_0 = @echo " GEN " $@; SOURCES = $(libgnunetfragmentation_la_SOURCES) \ $(test_fragmentation_SOURCES) DIST_SOURCES = $(libgnunetfragmentation_la_SOURCES) \ $(test_fragmentation_SOURCES) +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac ETAGS = etags CTAGS = ctags am__tty_colors = \ @@ -169,6 +200,10 @@ EXEEXT = @EXEEXT@ EXT_LIBS = @EXT_LIBS@ EXT_LIB_PATH = @EXT_LIB_PATH@ FGREP = @FGREP@ +GLIB_CFLAGS = @GLIB_CFLAGS@ +GLIB_GENMARSHAL = @GLIB_GENMARSHAL@ +GLIB_LIBS = @GLIB_LIBS@ +GLIB_MKENUMS = @GLIB_MKENUMS@ GMSGFMT = @GMSGFMT@ GMSGFMT_015 = @GMSGFMT_015@ GNUNETDNS_GROUP = @GNUNETDNS_GROUP@ @@ -179,6 +214,7 @@ GN_LIBINTL = @GN_LIBINTL@ GN_LIB_LDFLAGS = @GN_LIB_LDFLAGS@ GN_PLUGIN_LDFLAGS = @GN_PLUGIN_LDFLAGS@ GN_USER_HOME_DIR = @GN_USER_HOME_DIR@ +GOBJECT_QUERY = @GOBJECT_QUERY@ GREP = @GREP@ HAVE_LIBUNISTRING = @HAVE_LIBUNISTRING@ INCLTDL = @INCLTDL@ @@ -201,6 +237,8 @@ LIBCURL_CPPFLAGS = @LIBCURL_CPPFLAGS@ LIBGCRYPT_CFLAGS = @LIBGCRYPT_CFLAGS@ LIBGCRYPT_CONFIG = @LIBGCRYPT_CONFIG@ LIBGCRYPT_LIBS = @LIBGCRYPT_LIBS@ +LIBGTOP_CFLAGS = @LIBGTOP_CFLAGS@ +LIBGTOP_LIBS = @LIBGTOP_LIBS@ LIBICONV = @LIBICONV@ LIBINTL = @LIBINTL@ LIBLTDL = @LIBLTDL@ @@ -222,6 +260,7 @@ LT_CONFIG_H = @LT_CONFIG_H@ LT_DLLOADERS = @LT_DLLOADERS@ LT_DLPREOPEN = @LT_DLPREOPEN@ MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ MKDIR_P = @MKDIR_P@ MONKEYPREFIX = @MONKEYPREFIX@ MSGFMT = @MSGFMT@ @@ -231,6 +270,7 @@ MYSQL_CPPFLAGS = @MYSQL_CPPFLAGS@ MYSQL_LDFLAGS = @MYSQL_LDFLAGS@ NM = @NM@ NMEDIT = @NMEDIT@ +NSS_DIR = @NSS_DIR@ OBJC = @OBJC@ OBJCDEPMODE = @OBJCDEPMODE@ OBJCFLAGS = @OBJCFLAGS@ @@ -246,6 +286,7 @@ PACKAGE_TARNAME = @PACKAGE_TARNAME@ PACKAGE_URL = @PACKAGE_URL@ PACKAGE_VERSION = @PACKAGE_VERSION@ PATH_SEPARATOR = @PATH_SEPARATOR@ +PKG_CONFIG = @PKG_CONFIG@ POSTGRES_CPPFLAGS = @POSTGRES_CPPFLAGS@ POSTGRES_LDFLAGS = @POSTGRES_LDFLAGS@ POSUB = @POSUB@ @@ -277,6 +318,7 @@ abs_builddir = @abs_builddir@ abs_srcdir = @abs_srcdir@ abs_top_builddir = @abs_top_builddir@ abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ ac_ct_CC = @ac_ct_CC@ ac_ct_CXX = @ac_ct_CXX@ ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ @@ -299,6 +341,7 @@ datarootdir = @datarootdir@ docdir = @docdir@ dvidir = @dvidir@ exec_prefix = @exec_prefix@ +gitcommand = @gitcommand@ host = @host@ host_alias = @host_alias@ host_cpu = @host_cpu@ @@ -312,7 +355,6 @@ libdir = @libdir@ libexecdir = @libexecdir@ localedir = @localedir@ localstatedir = @localstatedir@ -lt_ECHO = @lt_ECHO@ ltdl_LIBOBJS = @ltdl_LIBOBJS@ ltdl_LTLIBOBJS = @ltdl_LTLIBOBJS@ mandir = @mandir@ @@ -330,6 +372,7 @@ sbindir = @sbindir@ sharedstatedir = @sharedstatedir@ srcdir = @srcdir@ subdirs = @subdirs@ +svnversioncommand = @svnversioncommand@ sys_symbol_underscore = @sys_symbol_underscore@ sysconfdir = @sysconfdir@ target = @target@ @@ -350,11 +393,12 @@ libgnunetfragmentation_la_SOURCES = \ libgnunetfragmentation_la_LIBADD = -lm \ $(top_builddir)/src/statistics/libgnunetstatistics.la \ - $(top_builddir)/src/util/libgnunetutil.la + $(top_builddir)/src/util/libgnunetutil.la \ + $(LTLIBINTL) libgnunetfragmentation_la_LDFLAGS = \ $(GN_LIB_LDFLAGS) \ - -version-info 1:0:1 + -version-info 2:0:0 @ENABLE_TEST_RUN_TRUE@TESTS = $(check_PROGRAMS) test_fragmentation_SOURCES = \ @@ -401,7 +445,6 @@ $(ACLOCAL_M4): $(am__aclocal_m4_deps) $(am__aclocal_m4_deps): install-libLTLIBRARIES: $(lib_LTLIBRARIES) @$(NORMAL_INSTALL) - test -z "$(libdir)" || $(MKDIR_P) "$(DESTDIR)$(libdir)" @list='$(lib_LTLIBRARIES)'; test -n "$(libdir)" || list=; \ list2=; for p in $$list; do \ if test -f $$p; then \ @@ -409,6 +452,8 @@ install-libLTLIBRARIES: $(lib_LTLIBRARIES) else :; fi; \ done; \ test -z "$$list2" || { \ + echo " $(MKDIR_P) '$(DESTDIR)$(libdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libdir)" || exit 1; \ echo " $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 '$(DESTDIR)$(libdir)'"; \ $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 "$(DESTDIR)$(libdir)"; \ } @@ -430,7 +475,7 @@ clean-libLTLIBRARIES: echo "rm -f \"$${dir}/so_locations\""; \ rm -f "$${dir}/so_locations"; \ done -libgnunetfragmentation.la: $(libgnunetfragmentation_la_OBJECTS) $(libgnunetfragmentation_la_DEPENDENCIES) +libgnunetfragmentation.la: $(libgnunetfragmentation_la_OBJECTS) $(libgnunetfragmentation_la_DEPENDENCIES) $(EXTRA_libgnunetfragmentation_la_DEPENDENCIES) $(AM_V_CCLD)$(libgnunetfragmentation_la_LINK) -rpath $(libdir) $(libgnunetfragmentation_la_OBJECTS) $(libgnunetfragmentation_la_LIBADD) $(LIBS) clean-checkPROGRAMS: @@ -441,7 +486,7 @@ clean-checkPROGRAMS: list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ echo " rm -f" $$list; \ rm -f $$list -test_fragmentation$(EXEEXT): $(test_fragmentation_OBJECTS) $(test_fragmentation_DEPENDENCIES) +test_fragmentation$(EXEEXT): $(test_fragmentation_OBJECTS) $(test_fragmentation_DEPENDENCIES) $(EXTRA_test_fragmentation_DEPENDENCIES) @rm -f test_fragmentation$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_fragmentation_OBJECTS) $(test_fragmentation_LDADD) $(LIBS) @@ -458,26 +503,23 @@ distclean-compile: .c.o: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c $< .c.obj: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'` @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c `$(CYGPATH_W) '$<'` +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c `$(CYGPATH_W) '$<'` .c.lo: @am__fastdepCC_TRUE@ $(AM_V_CC)$(LTCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LTCOMPILE) -c -o $@ $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LTCOMPILE) -c -o $@ $< mostlyclean-libtool: -rm -f *.lo @@ -618,14 +660,15 @@ check-TESTS: $(TESTS) fi; \ dashes=`echo "$$dashes" | sed s/./=/g`; \ if test "$$failed" -eq 0; then \ - echo "$$grn$$dashes"; \ + col="$$grn"; \ else \ - echo "$$red$$dashes"; \ + col="$$red"; \ fi; \ - echo "$$banner"; \ - test -z "$$skipped" || echo "$$skipped"; \ - test -z "$$report" || echo "$$report"; \ - echo "$$dashes$$std"; \ + echo "$${col}$$dashes$${std}"; \ + echo "$${col}$$banner$${std}"; \ + test -z "$$skipped" || echo "$${col}$$skipped$${std}"; \ + test -z "$$report" || echo "$${col}$$report$${std}"; \ + echo "$${col}$$dashes$${std}"; \ test "$$failed" -eq 0; \ else :; fi @@ -678,10 +721,15 @@ install-am: all-am installcheck: installcheck-am install-strip: - $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ - install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ - `test -z '$(STRIP)' || \ - echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi mostlyclean-generic: clean-generic: diff --git a/src/fragmentation/fragmentation.c b/src/fragmentation/fragmentation.c index 4749f53..f859b32 100644 --- a/src/fragmentation/fragmentation.c +++ b/src/fragmentation/fragmentation.c @@ -52,7 +52,12 @@ struct GNUNET_FRAGMENT_Context /** * Current expected delay for ACKs. */ - struct GNUNET_TIME_Relative delay; + struct GNUNET_TIME_Relative ack_delay; + + /** + * Current expected delay between messages. + */ + struct GNUNET_TIME_Relative msg_delay; /** * Next allowed transmission time. @@ -181,11 +186,11 @@ transmit_next (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) return; } fc->next_transmission = (fc->next_transmission + 1) % 64; - wrap |= (fc->next_transmission == 0); + wrap |= (0 == fc->next_transmission); while (0 == (fc->acks & (1LL << fc->next_transmission))) { fc->next_transmission = (fc->next_transmission + 1) % 64; - wrap |= (fc->next_transmission == 0); + wrap |= (0 == fc->next_transmission); } /* assemble fragmentation message */ @@ -217,16 +222,16 @@ transmit_next (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) delay = GNUNET_BANDWIDTH_tracker_get_delay (fc->tracker, fsize); else delay = GNUNET_TIME_UNIT_ZERO; + delay = GNUNET_TIME_relative_max (delay, + GNUNET_TIME_relative_multiply (fc->msg_delay, + (1 << fc->num_rounds))); if (wrap) { /* full round transmitted wait 2x delay for ACK before going again */ fc->num_rounds++; - delay = - GNUNET_TIME_relative_max (GNUNET_TIME_relative_multiply (delay, 2), - GNUNET_TIME_relative_multiply (fc->delay, - fc->num_rounds)); + delay = GNUNET_TIME_relative_multiply (fc->ack_delay, 2); /* never use zero, need some time for ACK always */ - delay = GNUNET_TIME_relative_max (MIN_ACK_DELAY, delay); + delay = GNUNET_TIME_relative_max (MIN_ACK_DELAY, delay); fc->wack = GNUNET_YES; fc->last_round = GNUNET_TIME_absolute_get (); GNUNET_STATISTICS_update (fc->stats, _("# fragments wrap arounds"), 1, @@ -250,7 +255,9 @@ transmit_next (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) * @param stats statistics context * @param mtu the maximum message size for each fragment * @param tracker bandwidth tracker to use for flow control (can be NULL) - * @param delay expected delay between fragment transmission + * @param msg_delay initial delay to insert between fragment transmissions + * based on previous messages + * @param ack_delay expected delay between fragment transmission * and ACK based on previous messages * @param msg the message to fragment * @param proc function to call for each fragment to transmit @@ -261,7 +268,8 @@ struct GNUNET_FRAGMENT_Context * GNUNET_FRAGMENT_context_create (struct GNUNET_STATISTICS_Handle *stats, uint16_t mtu, struct GNUNET_BANDWIDTH_Tracker *tracker, - struct GNUNET_TIME_Relative delay, + struct GNUNET_TIME_Relative msg_delay, + struct GNUNET_TIME_Relative ack_delay, const struct GNUNET_MessageHeader *msg, GNUNET_FRAGMENT_MessageProcessor proc, void *proc_cls) @@ -280,7 +288,8 @@ GNUNET_FRAGMENT_context_create (struct GNUNET_STATISTICS_Handle *stats, fc->stats = stats; fc->mtu = mtu; fc->tracker = tracker; - fc->delay = delay; + fc->ack_delay = ack_delay; + fc->msg_delay = msg_delay; fc->msg = (const struct GNUNET_MessageHeader *) &fc[1]; fc->proc = proc; fc->proc_cls = proc_cls; @@ -339,6 +348,9 @@ GNUNET_FRAGMENT_process_ack (struct GNUNET_FRAGMENT_Context *fc, const struct FragmentAcknowledgement *fa; uint64_t abits; struct GNUNET_TIME_Relative ndelay; + unsigned int ack_cnt; + unsigned int snd_cnt; + unsigned int i; if (sizeof (struct FragmentAcknowledgement) != ntohs (msg->size)) { @@ -355,9 +367,39 @@ GNUNET_FRAGMENT_process_ack (struct GNUNET_FRAGMENT_Context *fc, /* normal ACK, can update running average of delay... */ fc->wack = GNUNET_NO; ndelay = GNUNET_TIME_absolute_get_duration (fc->last_round); - fc->delay.rel_value = - (ndelay.rel_value / fc->num_transmissions + 3 * fc->delay.rel_value) / 4; + fc->ack_delay.rel_value = + (ndelay.rel_value / fc->num_transmissions + 3 * fc->ack_delay.rel_value) / 4; fc->num_transmissions = 0; + /* calculate ratio msg sent vs. msg acked */ + ack_cnt = 0; + snd_cnt = 0; + for (i=0;i<64;i++) + { + if (1 == (fc->acks_mask & (1 << i))) + { + snd_cnt++; + if (0 == (abits & (1 << i))) + ack_cnt++; + } + } + if (0 == ack_cnt) + { + /* complete loss */ + fc->msg_delay = GNUNET_TIME_relative_multiply (fc->msg_delay, + snd_cnt); + } + else if (snd_cnt > ack_cnt) + { + /* some loss, slow down proportionally */ + fprintf (stderr, "Prop loss\n"); + fc->msg_delay.rel_value = ((fc->msg_delay.rel_value * ack_cnt) / snd_cnt); + } + else if (1 < fc->msg_delay.rel_value) + { + fc->msg_delay.rel_value--; /* try a bit faster */ + } + fc->msg_delay = GNUNET_TIME_relative_min (fc->msg_delay, + GNUNET_TIME_UNIT_SECONDS); } GNUNET_STATISTICS_update (fc->stats, _("# fragment acknowledgements received"), 1, @@ -406,19 +448,24 @@ GNUNET_FRAGMENT_process_ack (struct GNUNET_FRAGMENT_Context *fc, * resources). * * @param fc fragmentation context - * @return average delay between transmission and ACK for the - * last message, FOREVER if the message was not fully transmitted + * @param msg_delay where to store average delay between individual message transmissions the + * last message (OUT only) + * @param ack_delay where to store average delay between transmission and ACK for the + * last message, set to FOREVER if the message was not fully transmitted (OUT only) */ -struct GNUNET_TIME_Relative -GNUNET_FRAGMENT_context_destroy (struct GNUNET_FRAGMENT_Context *fc) +void +GNUNET_FRAGMENT_context_destroy (struct GNUNET_FRAGMENT_Context *fc, + struct GNUNET_TIME_Relative *msg_delay, + struct GNUNET_TIME_Relative *ack_delay) { - struct GNUNET_TIME_Relative ret; - if (fc->task != GNUNET_SCHEDULER_NO_TASK) GNUNET_SCHEDULER_cancel (fc->task); - ret = fc->delay; + if (NULL != ack_delay) + *ack_delay = fc->ack_delay; + if (NULL != msg_delay) + *msg_delay = GNUNET_TIME_relative_multiply (fc->msg_delay, + fc->num_rounds); GNUNET_free (fc); - return ret; } diff --git a/src/fragmentation/test_fragmentation.c b/src/fragmentation/test_fragmentation.c index c409bf3..2a30d7d 100644 --- a/src/fragmentation/test_fragmentation.c +++ b/src/fragmentation/test_fragmentation.c @@ -25,14 +25,12 @@ #include "platform.h" #include "gnunet_fragmentation_lib.h" -#define VERBOSE GNUNET_NO - #define DETAILS GNUNET_NO /** * Number of messages to transmit (note: each uses ~32k memory!) */ -#define NUM_MSGS 5000 +#define NUM_MSGS 500 /** * MTU to force on fragmentation (must be > 1k + 12) @@ -42,7 +40,7 @@ /** * Simulate dropping of 1 out of how many messages? (must be > 1) */ -#define DROPRATE 10 +#define DROPRATE 5 static int ret = 1; @@ -77,7 +75,7 @@ do_shutdown (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { if (frags[i] == NULL) continue; - GNUNET_FRAGMENT_context_destroy (frags[i]); + GNUNET_FRAGMENT_context_destroy (frags[i], NULL, NULL); frags[i] = NULL; } } @@ -134,7 +132,7 @@ proc_acks (void *cls, uint32_t msg_id, const struct GNUNET_MessageHeader *hdr) #if DETAILS FPRINTF (stderr, "%s", "@"); /* good ACK */ #endif - GNUNET_FRAGMENT_context_destroy (frags[i]); + GNUNET_FRAGMENT_context_destroy (frags[i], NULL, NULL); frags[i] = NULL; acks++; return; @@ -215,7 +213,9 @@ run (void *cls, char *const *args, const char *cfgfile, htons (sizeof (struct GNUNET_MessageHeader) + (17 * i) % (32 * 1024)); frags[i] = GNUNET_FRAGMENT_context_create (NULL /* no stats */ , MTU, &trackers[i], - GNUNET_TIME_UNIT_SECONDS, msg, + GNUNET_TIME_UNIT_MILLISECONDS, + GNUNET_TIME_UNIT_SECONDS, + msg, &proc_frac, &frags[i]); } } @@ -232,21 +232,13 @@ main (int argc, char *argv[]) "-c", "test_fragmentation_data.conf", "-L", -#if VERBOSE - "DEBUG", -#else "WARNING", -#endif NULL }; unsigned int i; GNUNET_log_setup ("test-fragmentation", -#if VERBOSE - "DEBUG", -#else "WARNING", -#endif NULL); for (i = 0; i < NUM_MSGS; i++) GNUNET_BANDWIDTH_tracker_init (&trackers[i], diff --git a/src/fs/Makefile.am b/src/fs/Makefile.am index b916e4e..84c0a61 100644 --- a/src/fs/Makefile.am +++ b/src/fs/Makefile.am @@ -11,6 +11,8 @@ endif pkgcfgdir= $(pkgdatadir)/config.d/ +libexecdir= $(pkglibdir)/libexec/ + pkgcfg_DATA = \ fs.conf @@ -50,23 +52,31 @@ libgnunetfs_la_LIBADD = \ libgnunetfs_la_LDFLAGS = \ $(GN_LIB_LDFLAGS) $(WINFLAGS) \ - -version-info 2:1:0 + -version-info 3:0:1 libgnunetfstest_a_SOURCES = \ fs_test_lib.c fs_test_lib.h libgnunetfstest_a_LIBADD = \ - $(top_builddir)/src/testing/libgnunettesting.la + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la + +libexec_PROGRAMS = \ + gnunet-helper-fs-publish \ + gnunet-service-fs + +noinst_PROGRAMS = \ + gnunet-fs-profiler \ + gnunet-daemon-fsprofiler bin_PROGRAMS = \ + gnunet-auto-share \ gnunet-directory \ gnunet-download \ gnunet-publish \ - gnunet-helper-fs-publish \ gnunet-pseudonym \ gnunet-search \ - gnunet-service-fs \ gnunet-fs \ gnunet-unindex @@ -83,6 +93,13 @@ gnunet_directory_LDADD = \ gnunet_directory_DEPENDENCIES = \ libgnunetfs.la +gnunet_fs_profiler_SOURCES = \ + gnunet-fs-profiler.c +gnunet_fs_profiler_LDADD = \ + $(top_builddir)/src/testbed/libgnunettestbed.la \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(GN_LIBINTL) + gnunet_fs_SOURCES = \ gnunet-fs.c gnunet_fs_LDADD = \ @@ -112,6 +129,15 @@ gnunet_publish_LDADD = \ gnunet_publish_DEPENDENCIES = \ libgnunetfs.la +gnunet_auto_share_SOURCES = \ + gnunet-auto-share.c +gnunet_auto_share_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + -lextractor \ + $(GN_LIBINTL) +gnunet_auto_share_DEPENDENCIES = \ + libgnunetfs.la + gnunet_helper_fs_publish_SOURCES = \ gnunet-helper-fs-publish.c gnunet_helper_fs_publish_LDADD = \ @@ -141,6 +167,16 @@ gnunet_search_LDADD = \ gnunet_search_DEPENDENCIES = \ libgnunetfs.la +gnunet_daemon_fsprofiler_SOURCES = \ + gnunet-daemon-fsprofiler.c +gnunet_daemon_fsprofiler_LDADD = \ + $(top_builddir)/src/fs/libgnunetfs.la \ + $(top_builddir)/src/statistics/libgnunetstatistics.la \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(GN_LIBINTL) +gnunet_daemon_fsprofiler_DEPENDENCIES = \ + libgnunetfs.la + gnunet_service_fs_SOURCES = \ gnunet-service-fs.c gnunet-service-fs.h \ gnunet-service-fs_cp.c gnunet-service-fs_cp.h \ @@ -149,13 +185,15 @@ gnunet_service_fs_SOURCES = \ gnunet-service-fs_pe.c gnunet-service-fs_pe.h \ gnunet-service-fs_pr.c gnunet-service-fs_pr.h \ gnunet-service-fs_push.c gnunet-service-fs_push.h \ - gnunet-service-fs_put.c gnunet-service-fs_put.h + gnunet-service-fs_put.c gnunet-service-fs_put.h \ + gnunet-service-fs_stream.c gnunet-service-fs_stream.h gnunet_service_fs_LDADD = \ $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/dht/libgnunetdht.la \ $(top_builddir)/src/block/libgnunetblock.la \ $(top_builddir)/src/datastore/libgnunetdatastore.la \ $(top_builddir)/src/statistics/libgnunetstatistics.la \ + $(top_builddir)/src/stream/libgnunetstream.la \ $(top_builddir)/src/ats/libgnunetats.la \ $(top_builddir)/src/core/libgnunetcore.la \ $(top_builddir)/src/util/libgnunetutil.la \ @@ -177,7 +215,8 @@ libgnunet_plugin_block_fs_la_SOURCES = \ plugin_block_fs.c libgnunet_plugin_block_fs_la_LIBADD = \ $(top_builddir)/src/block/libgnunetblock.la \ - $(top_builddir)/src/util/libgnunetutil.la + $(top_builddir)/src/util/libgnunetutil.la \ + $(LTLIBINTL) libgnunet_plugin_block_fs_la_LDFLAGS = \ $(GN_PLUGIN_LDFLAGS) libgnunet_plugin_block_fs_la_DEPENDENCIES = \ @@ -190,12 +229,14 @@ if HAVE_BENCHMARKS perf_gnunet_service_fs_p2p \ perf_gnunet_service_fs_p2p_dht \ perf_gnunet_service_fs_p2p_index \ - perf_gnunet_service_fs_p2p_trust + perf_gnunet_service_fs_p2p_respect endif check_PROGRAMS = \ + test_plugin_block_fs \ test_fs_directory \ test_fs_download \ + test_fs_download_stream \ test_fs_download_indexed \ test_fs_download_persistence \ test_fs_file_information \ @@ -215,10 +256,16 @@ check_PROGRAMS = \ test_fs_uri \ test_gnunet_service_fs_migration \ test_gnunet_service_fs_p2p \ + test_gnunet_service_fs_p2p_stream \ $(FS_BENCHMARKS) +test_plugin_block_fs_SOURCES = \ + test_plugin_block_fs.c +test_plugin_block_fs_LDADD = \ + $(top_builddir)/src/block/libgnunetblock.la \ + $(top_builddir)/src/util/libgnunetutil.la -if HAVE_PYTHON_PEXPECT +if HAVE_PYTHON check_SCRIPTS = \ test_gnunet_fs_psd.py \ test_gnunet_fs_rec.py \ @@ -254,15 +301,14 @@ TESTS = \ test_fs_test_lib \ test_gnunet_service_fs_migration \ test_gnunet_service_fs_p2p \ + test_gnunet_service_fs_p2p_stream \ perf_gnunet_service_fs_p2p \ perf_gnunet_service_fs_p2p_index \ - perf_gnunet_service_fs_p2p_trust \ + perf_gnunet_service_fs_p2p_respect \ $(check_SCRIPTS) endif - - test_fs_directory_SOURCES = \ test_fs_directory.c test_fs_directory_LDADD = \ @@ -273,18 +319,28 @@ test_fs_directory_LDADD = \ test_fs_download_SOURCES = \ test_fs_download.c test_fs_download_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la test_fs_download_indexed_SOURCES = \ - test_fs_download_indexed.c + test_fs_download.c test_fs_download_indexed_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/fs/libgnunetfs.la \ + $(top_builddir)/src/util/libgnunetutil.la + +test_fs_download_stream_SOURCES = \ + test_fs_download.c +test_fs_download_stream_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la test_fs_download_persistence_SOURCES = \ test_fs_download_persistence.c test_fs_download_persistence_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la @@ -304,64 +360,78 @@ test_fs_getopt_LDADD = \ test_fs_list_indexed_SOURCES = \ test_fs_list_indexed.c test_fs_list_indexed_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la test_fs_namespace_SOURCES = \ test_fs_namespace.c test_fs_namespace_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la test_fs_namespace_list_updateable_SOURCES = \ test_fs_namespace_list_updateable.c test_fs_namespace_list_updateable_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la test_fs_publish_SOURCES = \ test_fs_publish.c test_fs_publish_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la test_fs_publish_persistence_SOURCES = \ test_fs_publish_persistence.c test_fs_publish_persistence_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la test_fs_search_SOURCES = \ test_fs_search.c -test_fs_search_LDADD = $(top_builddir)/src/fs/libgnunetfs.la \ +test_fs_search_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la test_fs_search_probes_SOURCES = \ test_fs_search_probes.c -test_fs_search_probes_LDADD = $(top_builddir)/src/fs/libgnunetfs.la \ +test_fs_search_probes_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la test_fs_search_persistence_SOURCES = \ test_fs_search_persistence.c -test_fs_search_persistence_LDADD = $(top_builddir)/src/fs/libgnunetfs.la \ +test_fs_search_persistence_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la test_fs_start_stop_SOURCES = \ test_fs_start_stop.c test_fs_start_stop_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la test_fs_unindex_SOURCES = \ test_fs_unindex.c test_fs_unindex_LDADD = \ - $(top_builddir)/src/fs/libgnunetfs.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la test_fs_unindex_persistence_SOURCES = \ test_fs_unindex_persistence.c test_fs_unindex_persistence_LDADD = \ - $(top_builddir)/src/fs/libgnunetfs.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la test_fs_uri_SOURCES = \ @@ -374,7 +444,7 @@ test_fs_test_lib_SOURCES = \ test_fs_test_lib.c test_fs_test_lib_LDADD = \ $(top_builddir)/src/fs/libgnunetfstest.a \ - $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la \ $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la @@ -382,7 +452,15 @@ test_gnunet_service_fs_p2p_SOURCES = \ test_gnunet_service_fs_p2p.c test_gnunet_service_fs_p2p_LDADD = \ $(top_builddir)/src/fs/libgnunetfstest.a \ - $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la \ + $(top_builddir)/src/fs/libgnunetfs.la \ + $(top_builddir)/src/util/libgnunetutil.la + +test_gnunet_service_fs_p2p_stream_SOURCES = \ + test_gnunet_service_fs_p2p.c +test_gnunet_service_fs_p2p_stream_LDADD = \ + $(top_builddir)/src/fs/libgnunetfstest.a \ + $(top_builddir)/src/testbed/libgnunettestbed.la \ $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la @@ -390,7 +468,7 @@ test_gnunet_service_fs_migration_SOURCES = \ test_gnunet_service_fs_migration.c test_gnunet_service_fs_migration_LDADD = \ $(top_builddir)/src/fs/libgnunetfstest.a \ - $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la \ $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la @@ -399,7 +477,7 @@ perf_gnunet_service_fs_p2p_SOURCES = \ perf_gnunet_service_fs_p2p_LDADD = \ $(top_builddir)/src/fs/libgnunetfstest.a \ $(top_builddir)/src/statistics/libgnunetstatistics.la \ - $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la \ $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la @@ -408,7 +486,7 @@ perf_gnunet_service_fs_p2p_index_SOURCES = \ perf_gnunet_service_fs_p2p_index_LDADD = \ $(top_builddir)/src/fs/libgnunetfstest.a \ $(top_builddir)/src/statistics/libgnunetstatistics.la \ - $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la \ $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la @@ -417,16 +495,16 @@ perf_gnunet_service_fs_p2p_dht_SOURCES = \ perf_gnunet_service_fs_p2p_dht_LDADD = \ $(top_builddir)/src/fs/libgnunetfstest.a \ $(top_builddir)/src/statistics/libgnunetstatistics.la \ - $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la \ $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la -perf_gnunet_service_fs_p2p_trust_SOURCES = \ - perf_gnunet_service_fs_p2p_trust.c -perf_gnunet_service_fs_p2p_trust_LDADD = \ +perf_gnunet_service_fs_p2p_respect_SOURCES = \ + perf_gnunet_service_fs_p2p_respect.c +perf_gnunet_service_fs_p2p_respect_LDADD = \ $(top_builddir)/src/fs/libgnunetfstest.a \ $(top_builddir)/src/statistics/libgnunetstatistics.la \ - $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la \ $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la @@ -455,6 +533,8 @@ EXTRA_DIST = \ fs_test_lib_data.conf \ test_fs_data.conf \ test_fs_download_data.conf \ + test_fs_download_indexed.conf \ + test_fs_download_stream.conf \ test_fs_file_information_data.conf \ fs_test_lib_data.conf \ test_fs_list_indexed_data.conf \ @@ -464,10 +544,12 @@ EXTRA_DIST = \ test_fs_unindex_data.conf \ test_fs_uri_data.conf \ test_gnunet_service_fs_migration_data.conf \ + test_gnunet_service_fs_p2p_stream.conf \ test_gnunet_fs_idx_data.conf \ test_gnunet_fs_ns_data.conf \ test_gnunet_fs_psd_data.conf \ test_gnunet_fs_rec_data.conf \ + perf_gnunet_service_fs_p2p.conf \ test_gnunet_fs_rec_data.tgz \ test_gnunet_fs_psd.py.in \ test_gnunet_fs_rec.py.in \ diff --git a/src/fs/Makefile.in b/src/fs/Makefile.in index 1dc8dba..2f24490 100644 --- a/src/fs/Makefile.in +++ b/src/fs/Makefile.in @@ -1,9 +1,9 @@ -# Makefile.in generated by automake 1.11.1 from Makefile.am. +# Makefile.in generated by automake 1.11.6 from Makefile.am. # @configure_input@ # Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, -# 2003, 2004, 2005, 2006, 2007, 2008, 2009 Free Software Foundation, -# Inc. +# 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Free Software +# Foundation, Inc. # This Makefile.in is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. @@ -20,6 +20,23 @@ VPATH = @srcdir@ +am__make_dryrun = \ + { \ + am__dry=no; \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + echo 'am--echo: ; @echo "AM" OK' | $(MAKE) -f - 2>/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } pkgdatadir = $(datadir)/@PACKAGE@ pkgincludedir = $(includedir)/@PACKAGE@ pkglibdir = $(libdir)/@PACKAGE@ @@ -39,12 +56,17 @@ POST_UNINSTALL = : build_triplet = @build@ host_triplet = @host@ target_triplet = @target@ -bin_PROGRAMS = gnunet-directory$(EXEEXT) gnunet-download$(EXEEXT) \ - gnunet-publish$(EXEEXT) gnunet-helper-fs-publish$(EXEEXT) \ +libexec_PROGRAMS = gnunet-helper-fs-publish$(EXEEXT) \ + gnunet-service-fs$(EXEEXT) +noinst_PROGRAMS = gnunet-fs-profiler$(EXEEXT) \ + gnunet-daemon-fsprofiler$(EXEEXT) +bin_PROGRAMS = gnunet-auto-share$(EXEEXT) gnunet-directory$(EXEEXT) \ + gnunet-download$(EXEEXT) gnunet-publish$(EXEEXT) \ gnunet-pseudonym$(EXEEXT) gnunet-search$(EXEEXT) \ - gnunet-service-fs$(EXEEXT) gnunet-fs$(EXEEXT) \ - gnunet-unindex$(EXEEXT) -check_PROGRAMS = test_fs_directory$(EXEEXT) test_fs_download$(EXEEXT) \ + gnunet-fs$(EXEEXT) gnunet-unindex$(EXEEXT) +check_PROGRAMS = test_plugin_block_fs$(EXEEXT) \ + test_fs_directory$(EXEEXT) test_fs_download$(EXEEXT) \ + test_fs_download_stream$(EXEEXT) \ test_fs_download_indexed$(EXEEXT) \ test_fs_download_persistence$(EXEEXT) \ test_fs_file_information$(EXEEXT) test_fs_getopt$(EXEEXT) \ @@ -56,7 +78,8 @@ check_PROGRAMS = test_fs_directory$(EXEEXT) test_fs_download$(EXEEXT) \ test_fs_start_stop$(EXEEXT) test_fs_test_lib$(EXEEXT) \ test_fs_unindex$(EXEEXT) test_fs_unindex_persistence$(EXEEXT) \ test_fs_uri$(EXEEXT) test_gnunet_service_fs_migration$(EXEEXT) \ - test_gnunet_service_fs_p2p$(EXEEXT) $(am__EXEEXT_1) + test_gnunet_service_fs_p2p$(EXEEXT) \ + test_gnunet_service_fs_p2p_stream$(EXEEXT) $(am__EXEEXT_1) @ENABLE_TEST_RUN_TRUE@TESTS = test_fs_directory$(EXEEXT) \ @ENABLE_TEST_RUN_TRUE@ test_fs_download$(EXEEXT) \ @ENABLE_TEST_RUN_TRUE@ test_fs_download_indexed$(EXEEXT) \ @@ -77,9 +100,10 @@ check_PROGRAMS = test_fs_directory$(EXEEXT) test_fs_download$(EXEEXT) \ @ENABLE_TEST_RUN_TRUE@ test_fs_test_lib$(EXEEXT) \ @ENABLE_TEST_RUN_TRUE@ test_gnunet_service_fs_migration$(EXEEXT) \ @ENABLE_TEST_RUN_TRUE@ test_gnunet_service_fs_p2p$(EXEEXT) \ +@ENABLE_TEST_RUN_TRUE@ test_gnunet_service_fs_p2p_stream$(EXEEXT) \ @ENABLE_TEST_RUN_TRUE@ perf_gnunet_service_fs_p2p$(EXEEXT) \ @ENABLE_TEST_RUN_TRUE@ perf_gnunet_service_fs_p2p_index$(EXEEXT) \ -@ENABLE_TEST_RUN_TRUE@ perf_gnunet_service_fs_p2p_trust$(EXEEXT) \ +@ENABLE_TEST_RUN_TRUE@ perf_gnunet_service_fs_p2p_respect$(EXEEXT) \ @ENABLE_TEST_RUN_TRUE@ $(check_SCRIPTS) subdir = src/fs DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in \ @@ -87,14 +111,15 @@ DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in \ ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 am__aclocal_m4_deps = $(top_srcdir)/m4/absolute-header.m4 \ $(top_srcdir)/m4/align.m4 $(top_srcdir)/m4/argz.m4 \ - $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/iconv.m4 \ - $(top_srcdir)/m4/lib-ld.m4 $(top_srcdir)/m4/lib-link.m4 \ - $(top_srcdir)/m4/lib-prefix.m4 $(top_srcdir)/m4/libcurl.m4 \ - $(top_srcdir)/m4/libgcrypt.m4 $(top_srcdir)/m4/libtool.m4 \ - $(top_srcdir)/m4/libunistring.m4 $(top_srcdir)/m4/ltdl.m4 \ - $(top_srcdir)/m4/ltoptions.m4 $(top_srcdir)/m4/ltsugar.m4 \ - $(top_srcdir)/m4/ltversion.m4 $(top_srcdir)/m4/lt~obsolete.m4 \ - $(top_srcdir)/m4/nls.m4 $(top_srcdir)/m4/po.m4 \ + $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/glib-2.0.m4 \ + $(top_srcdir)/m4/iconv.m4 $(top_srcdir)/m4/lib-ld.m4 \ + $(top_srcdir)/m4/lib-link.m4 $(top_srcdir)/m4/lib-prefix.m4 \ + $(top_srcdir)/m4/libcurl.m4 $(top_srcdir)/m4/libgcrypt.m4 \ + $(top_srcdir)/m4/libtool.m4 $(top_srcdir)/m4/libunistring.m4 \ + $(top_srcdir)/m4/ltdl.m4 $(top_srcdir)/m4/ltoptions.m4 \ + $(top_srcdir)/m4/ltsugar.m4 $(top_srcdir)/m4/ltversion.m4 \ + $(top_srcdir)/m4/lt~obsolete.m4 $(top_srcdir)/m4/nls.m4 \ + $(top_srcdir)/m4/pkg.m4 $(top_srcdir)/m4/po.m4 \ $(top_srcdir)/m4/progtest.m4 $(top_srcdir)/acinclude.m4 \ $(top_srcdir)/configure.ac am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ @@ -105,15 +130,16 @@ CONFIG_CLEAN_FILES = fs.conf CONFIG_CLEAN_VPATH_FILES = LIBRARIES = $(noinst_LIBRARIES) ARFLAGS = cru -AM_V_AR = $(am__v_AR_$(V)) -am__v_AR_ = $(am__v_AR_$(AM_DEFAULT_VERBOSITY)) +AM_V_AR = $(am__v_AR_@AM_V@) +am__v_AR_ = $(am__v_AR_@AM_DEFAULT_V@) am__v_AR_0 = @echo " AR " $@; -AM_V_at = $(am__v_at_$(V)) -am__v_at_ = $(am__v_at_$(AM_DEFAULT_VERBOSITY)) +AM_V_at = $(am__v_at_@AM_V@) +am__v_at_ = $(am__v_at_@AM_DEFAULT_V@) am__v_at_0 = @ libgnunetfstest_a_AR = $(AR) $(ARFLAGS) libgnunetfstest_a_DEPENDENCIES = \ - $(top_builddir)/src/testing/libgnunettesting.la + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la am_libgnunetfstest_a_OBJECTS = fs_test_lib.$(OBJEXT) libgnunetfstest_a_OBJECTS = $(am_libgnunetfstest_a_OBJECTS) am__vpath_adj_setup = srcdirstrip=`echo "$(srcdir)" | sed 's|.|.|g'`; @@ -137,21 +163,27 @@ am__nobase_list = $(am__nobase_strip_setup); \ am__base_list = \ sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \ sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g' +am__uninstall_files_from_dir = { \ + test -z "$$files" \ + || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \ + || { echo " ( cd '$$dir' && rm -f" $$files ")"; \ + $(am__cd) "$$dir" && rm -f $$files; }; \ + } am__installdirs = "$(DESTDIR)$(libdir)" "$(DESTDIR)$(plugindir)" \ - "$(DESTDIR)$(bindir)" "$(DESTDIR)$(bindir)" \ - "$(DESTDIR)$(pkgcfgdir)" + "$(DESTDIR)$(bindir)" "$(DESTDIR)$(libexecdir)" \ + "$(DESTDIR)$(bindir)" "$(DESTDIR)$(pkgcfgdir)" LTLIBRARIES = $(lib_LTLIBRARIES) $(plugin_LTLIBRARIES) +am__DEPENDENCIES_1 = am_libgnunet_plugin_block_fs_la_OBJECTS = plugin_block_fs.lo libgnunet_plugin_block_fs_la_OBJECTS = \ $(am_libgnunet_plugin_block_fs_la_OBJECTS) -AM_V_lt = $(am__v_lt_$(V)) -am__v_lt_ = $(am__v_lt_$(AM_DEFAULT_VERBOSITY)) +AM_V_lt = $(am__v_lt_@AM_V@) +am__v_lt_ = $(am__v_lt_@AM_DEFAULT_V@) am__v_lt_0 = --silent libgnunet_plugin_block_fs_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ $(AM_CFLAGS) $(CFLAGS) $(libgnunet_plugin_block_fs_la_LDFLAGS) \ $(LDFLAGS) -o $@ -am__DEPENDENCIES_1 = libgnunetfs_la_DEPENDENCIES = \ $(top_builddir)/src/datastore/libgnunetdatastore.la \ $(top_builddir)/src/util/libgnunetutil.la \ @@ -171,14 +203,26 @@ libgnunetfs_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ @HAVE_BENCHMARKS_TRUE@ perf_gnunet_service_fs_p2p$(EXEEXT) \ @HAVE_BENCHMARKS_TRUE@ perf_gnunet_service_fs_p2p_dht$(EXEEXT) \ @HAVE_BENCHMARKS_TRUE@ perf_gnunet_service_fs_p2p_index$(EXEEXT) \ -@HAVE_BENCHMARKS_TRUE@ perf_gnunet_service_fs_p2p_trust$(EXEEXT) -PROGRAMS = $(bin_PROGRAMS) +@HAVE_BENCHMARKS_TRUE@ perf_gnunet_service_fs_p2p_respect$(EXEEXT) +PROGRAMS = $(bin_PROGRAMS) $(libexec_PROGRAMS) $(noinst_PROGRAMS) +am_gnunet_auto_share_OBJECTS = gnunet-auto-share.$(OBJEXT) +gnunet_auto_share_OBJECTS = $(am_gnunet_auto_share_OBJECTS) +am_gnunet_daemon_fsprofiler_OBJECTS = \ + gnunet-daemon-fsprofiler.$(OBJEXT) +gnunet_daemon_fsprofiler_OBJECTS = \ + $(am_gnunet_daemon_fsprofiler_OBJECTS) am_gnunet_directory_OBJECTS = gnunet-directory.$(OBJEXT) gnunet_directory_OBJECTS = $(am_gnunet_directory_OBJECTS) am_gnunet_download_OBJECTS = gnunet-download.$(OBJEXT) gnunet_download_OBJECTS = $(am_gnunet_download_OBJECTS) am_gnunet_fs_OBJECTS = gnunet-fs.$(OBJEXT) gnunet_fs_OBJECTS = $(am_gnunet_fs_OBJECTS) +am_gnunet_fs_profiler_OBJECTS = gnunet-fs-profiler.$(OBJEXT) +gnunet_fs_profiler_OBJECTS = $(am_gnunet_fs_profiler_OBJECTS) +gnunet_fs_profiler_DEPENDENCIES = \ + $(top_builddir)/src/testbed/libgnunettestbed.la \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(am__DEPENDENCIES_1) am_gnunet_helper_fs_publish_OBJECTS = \ gnunet-helper-fs-publish.$(OBJEXT) gnunet_helper_fs_publish_OBJECTS = \ @@ -195,7 +239,8 @@ am_gnunet_service_fs_OBJECTS = gnunet-service-fs.$(OBJEXT) \ gnunet-service-fs_lc.$(OBJEXT) gnunet-service-fs_pe.$(OBJEXT) \ gnunet-service-fs_pr.$(OBJEXT) \ gnunet-service-fs_push.$(OBJEXT) \ - gnunet-service-fs_put.$(OBJEXT) + gnunet-service-fs_put.$(OBJEXT) \ + gnunet-service-fs_stream.$(OBJEXT) gnunet_service_fs_OBJECTS = $(am_gnunet_service_fs_OBJECTS) am_gnunet_unindex_OBJECTS = gnunet-unindex.$(OBJEXT) gnunet_unindex_OBJECTS = $(am_gnunet_unindex_OBJECTS) @@ -206,7 +251,7 @@ perf_gnunet_service_fs_p2p_OBJECTS = \ perf_gnunet_service_fs_p2p_DEPENDENCIES = \ $(top_builddir)/src/fs/libgnunetfstest.a \ $(top_builddir)/src/statistics/libgnunetstatistics.la \ - $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la \ $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la am_perf_gnunet_service_fs_p2p_dht_OBJECTS = \ @@ -216,7 +261,7 @@ perf_gnunet_service_fs_p2p_dht_OBJECTS = \ perf_gnunet_service_fs_p2p_dht_DEPENDENCIES = \ $(top_builddir)/src/fs/libgnunetfstest.a \ $(top_builddir)/src/statistics/libgnunetstatistics.la \ - $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la \ $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la am_perf_gnunet_service_fs_p2p_index_OBJECTS = \ @@ -226,17 +271,17 @@ perf_gnunet_service_fs_p2p_index_OBJECTS = \ perf_gnunet_service_fs_p2p_index_DEPENDENCIES = \ $(top_builddir)/src/fs/libgnunetfstest.a \ $(top_builddir)/src/statistics/libgnunetstatistics.la \ - $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la \ $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la -am_perf_gnunet_service_fs_p2p_trust_OBJECTS = \ - perf_gnunet_service_fs_p2p_trust.$(OBJEXT) -perf_gnunet_service_fs_p2p_trust_OBJECTS = \ - $(am_perf_gnunet_service_fs_p2p_trust_OBJECTS) -perf_gnunet_service_fs_p2p_trust_DEPENDENCIES = \ +am_perf_gnunet_service_fs_p2p_respect_OBJECTS = \ + perf_gnunet_service_fs_p2p_respect.$(OBJEXT) +perf_gnunet_service_fs_p2p_respect_OBJECTS = \ + $(am_perf_gnunet_service_fs_p2p_respect_OBJECTS) +perf_gnunet_service_fs_p2p_respect_DEPENDENCIES = \ $(top_builddir)/src/fs/libgnunetfstest.a \ $(top_builddir)/src/statistics/libgnunetstatistics.la \ - $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la \ $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la am_test_fs_directory_OBJECTS = test_fs_directory.$(OBJEXT) @@ -246,13 +291,15 @@ test_fs_directory_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la am_test_fs_download_OBJECTS = test_fs_download.$(OBJEXT) test_fs_download_OBJECTS = $(am_test_fs_download_OBJECTS) -test_fs_download_DEPENDENCIES = $(top_builddir)/src/fs/libgnunetfs.la \ +test_fs_download_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la -am_test_fs_download_indexed_OBJECTS = \ - test_fs_download_indexed.$(OBJEXT) +am_test_fs_download_indexed_OBJECTS = test_fs_download.$(OBJEXT) test_fs_download_indexed_OBJECTS = \ $(am_test_fs_download_indexed_OBJECTS) test_fs_download_indexed_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la am_test_fs_download_persistence_OBJECTS = \ @@ -260,6 +307,14 @@ am_test_fs_download_persistence_OBJECTS = \ test_fs_download_persistence_OBJECTS = \ $(am_test_fs_download_persistence_OBJECTS) test_fs_download_persistence_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/fs/libgnunetfs.la \ + $(top_builddir)/src/util/libgnunetutil.la +am_test_fs_download_stream_OBJECTS = test_fs_download.$(OBJEXT) +test_fs_download_stream_OBJECTS = \ + $(am_test_fs_download_stream_OBJECTS) +test_fs_download_stream_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la am_test_fs_file_information_OBJECTS = \ @@ -276,11 +331,13 @@ test_fs_getopt_DEPENDENCIES = $(top_builddir)/src/fs/libgnunetfs.la \ am_test_fs_list_indexed_OBJECTS = test_fs_list_indexed.$(OBJEXT) test_fs_list_indexed_OBJECTS = $(am_test_fs_list_indexed_OBJECTS) test_fs_list_indexed_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la am_test_fs_namespace_OBJECTS = test_fs_namespace.$(OBJEXT) test_fs_namespace_OBJECTS = $(am_test_fs_namespace_OBJECTS) test_fs_namespace_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la am_test_fs_namespace_list_updateable_OBJECTS = \ @@ -288,56 +345,68 @@ am_test_fs_namespace_list_updateable_OBJECTS = \ test_fs_namespace_list_updateable_OBJECTS = \ $(am_test_fs_namespace_list_updateable_OBJECTS) test_fs_namespace_list_updateable_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la am_test_fs_publish_OBJECTS = test_fs_publish.$(OBJEXT) test_fs_publish_OBJECTS = $(am_test_fs_publish_OBJECTS) -test_fs_publish_DEPENDENCIES = $(top_builddir)/src/fs/libgnunetfs.la \ +test_fs_publish_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la am_test_fs_publish_persistence_OBJECTS = \ test_fs_publish_persistence.$(OBJEXT) test_fs_publish_persistence_OBJECTS = \ $(am_test_fs_publish_persistence_OBJECTS) test_fs_publish_persistence_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la am_test_fs_search_OBJECTS = test_fs_search.$(OBJEXT) test_fs_search_OBJECTS = $(am_test_fs_search_OBJECTS) -test_fs_search_DEPENDENCIES = $(top_builddir)/src/fs/libgnunetfs.la \ +test_fs_search_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la am_test_fs_search_persistence_OBJECTS = \ test_fs_search_persistence.$(OBJEXT) test_fs_search_persistence_OBJECTS = \ $(am_test_fs_search_persistence_OBJECTS) test_fs_search_persistence_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la am_test_fs_search_probes_OBJECTS = test_fs_search_probes.$(OBJEXT) test_fs_search_probes_OBJECTS = $(am_test_fs_search_probes_OBJECTS) test_fs_search_probes_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la am_test_fs_start_stop_OBJECTS = test_fs_start_stop.$(OBJEXT) test_fs_start_stop_OBJECTS = $(am_test_fs_start_stop_OBJECTS) test_fs_start_stop_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la am_test_fs_test_lib_OBJECTS = test_fs_test_lib.$(OBJEXT) test_fs_test_lib_OBJECTS = $(am_test_fs_test_lib_OBJECTS) test_fs_test_lib_DEPENDENCIES = \ $(top_builddir)/src/fs/libgnunetfstest.a \ - $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la \ $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la am_test_fs_unindex_OBJECTS = test_fs_unindex.$(OBJEXT) test_fs_unindex_OBJECTS = $(am_test_fs_unindex_OBJECTS) -test_fs_unindex_DEPENDENCIES = $(top_builddir)/src/fs/libgnunetfs.la \ +test_fs_unindex_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la am_test_fs_unindex_persistence_OBJECTS = \ test_fs_unindex_persistence.$(OBJEXT) test_fs_unindex_persistence_OBJECTS = \ $(am_test_fs_unindex_persistence_OBJECTS) test_fs_unindex_persistence_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la am_test_fs_uri_OBJECTS = test_fs_uri.$(OBJEXT) @@ -350,7 +419,7 @@ test_gnunet_service_fs_migration_OBJECTS = \ $(am_test_gnunet_service_fs_migration_OBJECTS) test_gnunet_service_fs_migration_DEPENDENCIES = \ $(top_builddir)/src/fs/libgnunetfstest.a \ - $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la \ $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la am_test_gnunet_service_fs_p2p_OBJECTS = \ @@ -359,9 +428,23 @@ test_gnunet_service_fs_p2p_OBJECTS = \ $(am_test_gnunet_service_fs_p2p_OBJECTS) test_gnunet_service_fs_p2p_DEPENDENCIES = \ $(top_builddir)/src/fs/libgnunetfstest.a \ - $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la \ + $(top_builddir)/src/fs/libgnunetfs.la \ + $(top_builddir)/src/util/libgnunetutil.la +am_test_gnunet_service_fs_p2p_stream_OBJECTS = \ + test_gnunet_service_fs_p2p.$(OBJEXT) +test_gnunet_service_fs_p2p_stream_OBJECTS = \ + $(am_test_gnunet_service_fs_p2p_stream_OBJECTS) +test_gnunet_service_fs_p2p_stream_DEPENDENCIES = \ + $(top_builddir)/src/fs/libgnunetfstest.a \ + $(top_builddir)/src/testbed/libgnunettestbed.la \ $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la +am_test_plugin_block_fs_OBJECTS = test_plugin_block_fs.$(OBJEXT) +test_plugin_block_fs_OBJECTS = $(am_test_plugin_block_fs_OBJECTS) +test_plugin_block_fs_DEPENDENCIES = \ + $(top_builddir)/src/block/libgnunetblock.la \ + $(top_builddir)/src/util/libgnunetutil.la SCRIPTS = $(bin_SCRIPTS) DEFAULT_INCLUDES = -I.@am__isrc@ -I$(top_builddir) depcomp = $(SHELL) $(top_srcdir)/depcomp @@ -373,23 +456,25 @@ LTCOMPILE = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) \ $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) \ $(AM_CFLAGS) $(CFLAGS) -AM_V_CC = $(am__v_CC_$(V)) -am__v_CC_ = $(am__v_CC_$(AM_DEFAULT_VERBOSITY)) +AM_V_CC = $(am__v_CC_@AM_V@) +am__v_CC_ = $(am__v_CC_@AM_DEFAULT_V@) am__v_CC_0 = @echo " CC " $@; CCLD = $(CC) LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ $(AM_LDFLAGS) $(LDFLAGS) -o $@ -AM_V_CCLD = $(am__v_CCLD_$(V)) -am__v_CCLD_ = $(am__v_CCLD_$(AM_DEFAULT_VERBOSITY)) +AM_V_CCLD = $(am__v_CCLD_@AM_V@) +am__v_CCLD_ = $(am__v_CCLD_@AM_DEFAULT_V@) am__v_CCLD_0 = @echo " CCLD " $@; -AM_V_GEN = $(am__v_GEN_$(V)) -am__v_GEN_ = $(am__v_GEN_$(AM_DEFAULT_VERBOSITY)) +AM_V_GEN = $(am__v_GEN_@AM_V@) +am__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@) am__v_GEN_0 = @echo " GEN " $@; SOURCES = $(libgnunetfstest_a_SOURCES) \ $(libgnunet_plugin_block_fs_la_SOURCES) \ - $(libgnunetfs_la_SOURCES) $(gnunet_directory_SOURCES) \ - $(gnunet_download_SOURCES) $(gnunet_fs_SOURCES) \ + $(libgnunetfs_la_SOURCES) $(gnunet_auto_share_SOURCES) \ + $(gnunet_daemon_fsprofiler_SOURCES) \ + $(gnunet_directory_SOURCES) $(gnunet_download_SOURCES) \ + $(gnunet_fs_SOURCES) $(gnunet_fs_profiler_SOURCES) \ $(gnunet_helper_fs_publish_SOURCES) \ $(gnunet_pseudonym_SOURCES) $(gnunet_publish_SOURCES) \ $(gnunet_search_SOURCES) $(gnunet_service_fs_SOURCES) \ @@ -397,10 +482,11 @@ SOURCES = $(libgnunetfstest_a_SOURCES) \ $(perf_gnunet_service_fs_p2p_SOURCES) \ $(perf_gnunet_service_fs_p2p_dht_SOURCES) \ $(perf_gnunet_service_fs_p2p_index_SOURCES) \ - $(perf_gnunet_service_fs_p2p_trust_SOURCES) \ + $(perf_gnunet_service_fs_p2p_respect_SOURCES) \ $(test_fs_directory_SOURCES) $(test_fs_download_SOURCES) \ $(test_fs_download_indexed_SOURCES) \ $(test_fs_download_persistence_SOURCES) \ + $(test_fs_download_stream_SOURCES) \ $(test_fs_file_information_SOURCES) $(test_fs_getopt_SOURCES) \ $(test_fs_list_indexed_SOURCES) $(test_fs_namespace_SOURCES) \ $(test_fs_namespace_list_updateable_SOURCES) \ @@ -412,11 +498,15 @@ SOURCES = $(libgnunetfstest_a_SOURCES) \ $(test_fs_test_lib_SOURCES) $(test_fs_unindex_SOURCES) \ $(test_fs_unindex_persistence_SOURCES) $(test_fs_uri_SOURCES) \ $(test_gnunet_service_fs_migration_SOURCES) \ - $(test_gnunet_service_fs_p2p_SOURCES) + $(test_gnunet_service_fs_p2p_SOURCES) \ + $(test_gnunet_service_fs_p2p_stream_SOURCES) \ + $(test_plugin_block_fs_SOURCES) DIST_SOURCES = $(libgnunetfstest_a_SOURCES) \ $(libgnunet_plugin_block_fs_la_SOURCES) \ - $(libgnunetfs_la_SOURCES) $(gnunet_directory_SOURCES) \ - $(gnunet_download_SOURCES) $(gnunet_fs_SOURCES) \ + $(libgnunetfs_la_SOURCES) $(gnunet_auto_share_SOURCES) \ + $(gnunet_daemon_fsprofiler_SOURCES) \ + $(gnunet_directory_SOURCES) $(gnunet_download_SOURCES) \ + $(gnunet_fs_SOURCES) $(gnunet_fs_profiler_SOURCES) \ $(gnunet_helper_fs_publish_SOURCES) \ $(gnunet_pseudonym_SOURCES) $(gnunet_publish_SOURCES) \ $(gnunet_search_SOURCES) $(gnunet_service_fs_SOURCES) \ @@ -424,10 +514,11 @@ DIST_SOURCES = $(libgnunetfstest_a_SOURCES) \ $(perf_gnunet_service_fs_p2p_SOURCES) \ $(perf_gnunet_service_fs_p2p_dht_SOURCES) \ $(perf_gnunet_service_fs_p2p_index_SOURCES) \ - $(perf_gnunet_service_fs_p2p_trust_SOURCES) \ + $(perf_gnunet_service_fs_p2p_respect_SOURCES) \ $(test_fs_directory_SOURCES) $(test_fs_download_SOURCES) \ $(test_fs_download_indexed_SOURCES) \ $(test_fs_download_persistence_SOURCES) \ + $(test_fs_download_stream_SOURCES) \ $(test_fs_file_information_SOURCES) $(test_fs_getopt_SOURCES) \ $(test_fs_list_indexed_SOURCES) $(test_fs_namespace_SOURCES) \ $(test_fs_namespace_list_updateable_SOURCES) \ @@ -439,7 +530,14 @@ DIST_SOURCES = $(libgnunetfstest_a_SOURCES) \ $(test_fs_test_lib_SOURCES) $(test_fs_unindex_SOURCES) \ $(test_fs_unindex_persistence_SOURCES) $(test_fs_uri_SOURCES) \ $(test_gnunet_service_fs_migration_SOURCES) \ - $(test_gnunet_service_fs_p2p_SOURCES) + $(test_gnunet_service_fs_p2p_SOURCES) \ + $(test_gnunet_service_fs_p2p_stream_SOURCES) \ + $(test_plugin_block_fs_SOURCES) +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac DATA = $(pkgcfg_DATA) ETAGS = etags CTAGS = ctags @@ -481,6 +579,10 @@ EXEEXT = @EXEEXT@ EXT_LIBS = @EXT_LIBS@ EXT_LIB_PATH = @EXT_LIB_PATH@ FGREP = @FGREP@ +GLIB_CFLAGS = @GLIB_CFLAGS@ +GLIB_GENMARSHAL = @GLIB_GENMARSHAL@ +GLIB_LIBS = @GLIB_LIBS@ +GLIB_MKENUMS = @GLIB_MKENUMS@ GMSGFMT = @GMSGFMT@ GMSGFMT_015 = @GMSGFMT_015@ GNUNETDNS_GROUP = @GNUNETDNS_GROUP@ @@ -491,6 +593,7 @@ GN_LIBINTL = @GN_LIBINTL@ GN_LIB_LDFLAGS = @GN_LIB_LDFLAGS@ GN_PLUGIN_LDFLAGS = @GN_PLUGIN_LDFLAGS@ GN_USER_HOME_DIR = @GN_USER_HOME_DIR@ +GOBJECT_QUERY = @GOBJECT_QUERY@ GREP = @GREP@ HAVE_LIBUNISTRING = @HAVE_LIBUNISTRING@ INCLTDL = @INCLTDL@ @@ -513,6 +616,8 @@ LIBCURL_CPPFLAGS = @LIBCURL_CPPFLAGS@ LIBGCRYPT_CFLAGS = @LIBGCRYPT_CFLAGS@ LIBGCRYPT_CONFIG = @LIBGCRYPT_CONFIG@ LIBGCRYPT_LIBS = @LIBGCRYPT_LIBS@ +LIBGTOP_CFLAGS = @LIBGTOP_CFLAGS@ +LIBGTOP_LIBS = @LIBGTOP_LIBS@ LIBICONV = @LIBICONV@ LIBINTL = @LIBINTL@ LIBLTDL = @LIBLTDL@ @@ -534,6 +639,7 @@ LT_CONFIG_H = @LT_CONFIG_H@ LT_DLLOADERS = @LT_DLLOADERS@ LT_DLPREOPEN = @LT_DLPREOPEN@ MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ MKDIR_P = @MKDIR_P@ MONKEYPREFIX = @MONKEYPREFIX@ MSGFMT = @MSGFMT@ @@ -543,6 +649,7 @@ MYSQL_CPPFLAGS = @MYSQL_CPPFLAGS@ MYSQL_LDFLAGS = @MYSQL_LDFLAGS@ NM = @NM@ NMEDIT = @NMEDIT@ +NSS_DIR = @NSS_DIR@ OBJC = @OBJC@ OBJCDEPMODE = @OBJCDEPMODE@ OBJCFLAGS = @OBJCFLAGS@ @@ -558,6 +665,7 @@ PACKAGE_TARNAME = @PACKAGE_TARNAME@ PACKAGE_URL = @PACKAGE_URL@ PACKAGE_VERSION = @PACKAGE_VERSION@ PATH_SEPARATOR = @PATH_SEPARATOR@ +PKG_CONFIG = @PKG_CONFIG@ POSTGRES_CPPFLAGS = @POSTGRES_CPPFLAGS@ POSTGRES_LDFLAGS = @POSTGRES_LDFLAGS@ POSUB = @POSUB@ @@ -589,6 +697,7 @@ abs_builddir = @abs_builddir@ abs_srcdir = @abs_srcdir@ abs_top_builddir = @abs_top_builddir@ abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ ac_ct_CC = @ac_ct_CC@ ac_ct_CXX = @ac_ct_CXX@ ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ @@ -611,6 +720,7 @@ datarootdir = @datarootdir@ docdir = @docdir@ dvidir = @dvidir@ exec_prefix = @exec_prefix@ +gitcommand = @gitcommand@ host = @host@ host_alias = @host_alias@ host_cpu = @host_cpu@ @@ -621,10 +731,9 @@ includedir = @includedir@ infodir = @infodir@ install_sh = @install_sh@ libdir = @libdir@ -libexecdir = @libexecdir@ +libexecdir = $(pkglibdir)/libexec/ localedir = @localedir@ localstatedir = @localstatedir@ -lt_ECHO = @lt_ECHO@ ltdl_LIBOBJS = @ltdl_LIBOBJS@ ltdl_LTLIBOBJS = @ltdl_LTLIBOBJS@ mandir = @mandir@ @@ -642,6 +751,7 @@ sbindir = @sbindir@ sharedstatedir = @sharedstatedir@ srcdir = @srcdir@ subdirs = @subdirs@ +svnversioncommand = @svnversioncommand@ sys_symbol_underscore = @sys_symbol_underscore@ sysconfdir = @sysconfdir@ target = @target@ @@ -692,13 +802,14 @@ libgnunetfs_la_LIBADD = \ libgnunetfs_la_LDFLAGS = \ $(GN_LIB_LDFLAGS) $(WINFLAGS) \ - -version-info 2:1:0 + -version-info 3:0:1 libgnunetfstest_a_SOURCES = \ fs_test_lib.c fs_test_lib.h libgnunetfstest_a_LIBADD = \ - $(top_builddir)/src/testing/libgnunettesting.la + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la bin_SCRIPTS = \ gnunet-download-manager.scm @@ -715,6 +826,14 @@ gnunet_directory_LDADD = \ gnunet_directory_DEPENDENCIES = \ libgnunetfs.la +gnunet_fs_profiler_SOURCES = \ + gnunet-fs-profiler.c + +gnunet_fs_profiler_LDADD = \ + $(top_builddir)/src/testbed/libgnunettestbed.la \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(GN_LIBINTL) + gnunet_fs_SOURCES = \ gnunet-fs.c @@ -750,6 +869,17 @@ gnunet_publish_LDADD = \ gnunet_publish_DEPENDENCIES = \ libgnunetfs.la +gnunet_auto_share_SOURCES = \ + gnunet-auto-share.c + +gnunet_auto_share_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + -lextractor \ + $(GN_LIBINTL) + +gnunet_auto_share_DEPENDENCIES = \ + libgnunetfs.la + gnunet_helper_fs_publish_SOURCES = \ gnunet-helper-fs-publish.c @@ -785,6 +915,18 @@ gnunet_search_LDADD = \ gnunet_search_DEPENDENCIES = \ libgnunetfs.la +gnunet_daemon_fsprofiler_SOURCES = \ + gnunet-daemon-fsprofiler.c + +gnunet_daemon_fsprofiler_LDADD = \ + $(top_builddir)/src/fs/libgnunetfs.la \ + $(top_builddir)/src/statistics/libgnunetstatistics.la \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(GN_LIBINTL) + +gnunet_daemon_fsprofiler_DEPENDENCIES = \ + libgnunetfs.la + gnunet_service_fs_SOURCES = \ gnunet-service-fs.c gnunet-service-fs.h \ gnunet-service-fs_cp.c gnunet-service-fs_cp.h \ @@ -793,7 +935,8 @@ gnunet_service_fs_SOURCES = \ gnunet-service-fs_pe.c gnunet-service-fs_pe.h \ gnunet-service-fs_pr.c gnunet-service-fs_pr.h \ gnunet-service-fs_push.c gnunet-service-fs_push.h \ - gnunet-service-fs_put.c gnunet-service-fs_put.h + gnunet-service-fs_put.c gnunet-service-fs_put.h \ + gnunet-service-fs_stream.c gnunet-service-fs_stream.h gnunet_service_fs_LDADD = \ $(top_builddir)/src/fs/libgnunetfs.la \ @@ -801,6 +944,7 @@ gnunet_service_fs_LDADD = \ $(top_builddir)/src/block/libgnunetblock.la \ $(top_builddir)/src/datastore/libgnunetdatastore.la \ $(top_builddir)/src/statistics/libgnunetstatistics.la \ + $(top_builddir)/src/stream/libgnunetstream.la \ $(top_builddir)/src/ats/libgnunetats.la \ $(top_builddir)/src/core/libgnunetcore.la \ $(top_builddir)/src/util/libgnunetutil.la \ @@ -825,7 +969,8 @@ libgnunet_plugin_block_fs_la_SOURCES = \ libgnunet_plugin_block_fs_la_LIBADD = \ $(top_builddir)/src/block/libgnunetblock.la \ - $(top_builddir)/src/util/libgnunetutil.la + $(top_builddir)/src/util/libgnunetutil.la \ + $(LTLIBINTL) libgnunet_plugin_block_fs_la_LDFLAGS = \ $(GN_PLUGIN_LDFLAGS) @@ -837,13 +982,20 @@ libgnunet_plugin_block_fs_la_DEPENDENCIES = \ @HAVE_BENCHMARKS_TRUE@ perf_gnunet_service_fs_p2p \ @HAVE_BENCHMARKS_TRUE@ perf_gnunet_service_fs_p2p_dht \ @HAVE_BENCHMARKS_TRUE@ perf_gnunet_service_fs_p2p_index \ -@HAVE_BENCHMARKS_TRUE@ perf_gnunet_service_fs_p2p_trust +@HAVE_BENCHMARKS_TRUE@ perf_gnunet_service_fs_p2p_respect -@HAVE_PYTHON_PEXPECT_TRUE@check_SCRIPTS = \ -@HAVE_PYTHON_PEXPECT_TRUE@ test_gnunet_fs_psd.py \ -@HAVE_PYTHON_PEXPECT_TRUE@ test_gnunet_fs_rec.py \ -@HAVE_PYTHON_PEXPECT_TRUE@ test_gnunet_fs_idx.py \ -@HAVE_PYTHON_PEXPECT_TRUE@ test_gnunet_fs_ns.py +test_plugin_block_fs_SOURCES = \ + test_plugin_block_fs.c + +test_plugin_block_fs_LDADD = \ + $(top_builddir)/src/block/libgnunetblock.la \ + $(top_builddir)/src/util/libgnunetutil.la + +@HAVE_PYTHON_TRUE@check_SCRIPTS = \ +@HAVE_PYTHON_TRUE@ test_gnunet_fs_psd.py \ +@HAVE_PYTHON_TRUE@ test_gnunet_fs_rec.py \ +@HAVE_PYTHON_TRUE@ test_gnunet_fs_idx.py \ +@HAVE_PYTHON_TRUE@ test_gnunet_fs_ns.py @ENABLE_MONKEY_TRUE@TESTS_ENVIRONMENT = @MONKEYPREFIX@ @ENABLE_MONKEY_TRUE@AM_LDFLAGS = -no-install @@ -859,13 +1011,23 @@ test_fs_download_SOURCES = \ test_fs_download.c test_fs_download_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la test_fs_download_indexed_SOURCES = \ - test_fs_download_indexed.c + test_fs_download.c test_fs_download_indexed_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/fs/libgnunetfs.la \ + $(top_builddir)/src/util/libgnunetutil.la + +test_fs_download_stream_SOURCES = \ + test_fs_download.c + +test_fs_download_stream_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la @@ -873,6 +1035,7 @@ test_fs_download_persistence_SOURCES = \ test_fs_download_persistence.c test_fs_download_persistence_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la @@ -895,6 +1058,7 @@ test_fs_list_indexed_SOURCES = \ test_fs_list_indexed.c test_fs_list_indexed_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la @@ -902,6 +1066,7 @@ test_fs_namespace_SOURCES = \ test_fs_namespace.c test_fs_namespace_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la @@ -909,6 +1074,7 @@ test_fs_namespace_list_updateable_SOURCES = \ test_fs_namespace_list_updateable.c test_fs_namespace_list_updateable_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la @@ -916,6 +1082,7 @@ test_fs_publish_SOURCES = \ test_fs_publish.c test_fs_publish_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la @@ -923,31 +1090,39 @@ test_fs_publish_persistence_SOURCES = \ test_fs_publish_persistence.c test_fs_publish_persistence_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la test_fs_search_SOURCES = \ test_fs_search.c -test_fs_search_LDADD = $(top_builddir)/src/fs/libgnunetfs.la \ +test_fs_search_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la test_fs_search_probes_SOURCES = \ test_fs_search_probes.c -test_fs_search_probes_LDADD = $(top_builddir)/src/fs/libgnunetfs.la \ +test_fs_search_probes_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la test_fs_search_persistence_SOURCES = \ test_fs_search_persistence.c -test_fs_search_persistence_LDADD = $(top_builddir)/src/fs/libgnunetfs.la \ +test_fs_search_persistence_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la test_fs_start_stop_SOURCES = \ test_fs_start_stop.c test_fs_start_stop_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la @@ -955,14 +1130,16 @@ test_fs_unindex_SOURCES = \ test_fs_unindex.c test_fs_unindex_LDADD = \ - $(top_builddir)/src/fs/libgnunetfs.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la test_fs_unindex_persistence_SOURCES = \ test_fs_unindex_persistence.c test_fs_unindex_persistence_LDADD = \ - $(top_builddir)/src/fs/libgnunetfs.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la test_fs_uri_SOURCES = \ @@ -977,7 +1154,7 @@ test_fs_test_lib_SOURCES = \ test_fs_test_lib_LDADD = \ $(top_builddir)/src/fs/libgnunetfstest.a \ - $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la \ $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la @@ -986,7 +1163,16 @@ test_gnunet_service_fs_p2p_SOURCES = \ test_gnunet_service_fs_p2p_LDADD = \ $(top_builddir)/src/fs/libgnunetfstest.a \ - $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la \ + $(top_builddir)/src/fs/libgnunetfs.la \ + $(top_builddir)/src/util/libgnunetutil.la + +test_gnunet_service_fs_p2p_stream_SOURCES = \ + test_gnunet_service_fs_p2p.c + +test_gnunet_service_fs_p2p_stream_LDADD = \ + $(top_builddir)/src/fs/libgnunetfstest.a \ + $(top_builddir)/src/testbed/libgnunettestbed.la \ $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la @@ -995,7 +1181,7 @@ test_gnunet_service_fs_migration_SOURCES = \ test_gnunet_service_fs_migration_LDADD = \ $(top_builddir)/src/fs/libgnunetfstest.a \ - $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la \ $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la @@ -1005,7 +1191,7 @@ perf_gnunet_service_fs_p2p_SOURCES = \ perf_gnunet_service_fs_p2p_LDADD = \ $(top_builddir)/src/fs/libgnunetfstest.a \ $(top_builddir)/src/statistics/libgnunetstatistics.la \ - $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la \ $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la @@ -1015,7 +1201,7 @@ perf_gnunet_service_fs_p2p_index_SOURCES = \ perf_gnunet_service_fs_p2p_index_LDADD = \ $(top_builddir)/src/fs/libgnunetfstest.a \ $(top_builddir)/src/statistics/libgnunetstatistics.la \ - $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la \ $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la @@ -1025,17 +1211,17 @@ perf_gnunet_service_fs_p2p_dht_SOURCES = \ perf_gnunet_service_fs_p2p_dht_LDADD = \ $(top_builddir)/src/fs/libgnunetfstest.a \ $(top_builddir)/src/statistics/libgnunetstatistics.la \ - $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la \ $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la -perf_gnunet_service_fs_p2p_trust_SOURCES = \ - perf_gnunet_service_fs_p2p_trust.c +perf_gnunet_service_fs_p2p_respect_SOURCES = \ + perf_gnunet_service_fs_p2p_respect.c -perf_gnunet_service_fs_p2p_trust_LDADD = \ +perf_gnunet_service_fs_p2p_respect_LDADD = \ $(top_builddir)/src/fs/libgnunetfstest.a \ $(top_builddir)/src/statistics/libgnunetstatistics.la \ - $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la \ $(top_builddir)/src/fs/libgnunetfs.la \ $(top_builddir)/src/util/libgnunetutil.la @@ -1045,6 +1231,8 @@ EXTRA_DIST = \ fs_test_lib_data.conf \ test_fs_data.conf \ test_fs_download_data.conf \ + test_fs_download_indexed.conf \ + test_fs_download_stream.conf \ test_fs_file_information_data.conf \ fs_test_lib_data.conf \ test_fs_list_indexed_data.conf \ @@ -1054,10 +1242,12 @@ EXTRA_DIST = \ test_fs_unindex_data.conf \ test_fs_uri_data.conf \ test_gnunet_service_fs_migration_data.conf \ + test_gnunet_service_fs_p2p_stream.conf \ test_gnunet_fs_idx_data.conf \ test_gnunet_fs_ns_data.conf \ test_gnunet_fs_psd_data.conf \ test_gnunet_fs_rec_data.conf \ + perf_gnunet_service_fs_p2p.conf \ test_gnunet_fs_rec_data.tgz \ test_gnunet_fs_psd.py.in \ test_gnunet_fs_rec.py.in \ @@ -1105,13 +1295,12 @@ fs.conf: $(top_builddir)/config.status $(srcdir)/fs.conf.in clean-noinstLIBRARIES: -test -z "$(noinst_LIBRARIES)" || rm -f $(noinst_LIBRARIES) -libgnunetfstest.a: $(libgnunetfstest_a_OBJECTS) $(libgnunetfstest_a_DEPENDENCIES) +libgnunetfstest.a: $(libgnunetfstest_a_OBJECTS) $(libgnunetfstest_a_DEPENDENCIES) $(EXTRA_libgnunetfstest_a_DEPENDENCIES) $(AM_V_at)-rm -f libgnunetfstest.a $(AM_V_AR)$(libgnunetfstest_a_AR) libgnunetfstest.a $(libgnunetfstest_a_OBJECTS) $(libgnunetfstest_a_LIBADD) $(AM_V_at)$(RANLIB) libgnunetfstest.a install-libLTLIBRARIES: $(lib_LTLIBRARIES) @$(NORMAL_INSTALL) - test -z "$(libdir)" || $(MKDIR_P) "$(DESTDIR)$(libdir)" @list='$(lib_LTLIBRARIES)'; test -n "$(libdir)" || list=; \ list2=; for p in $$list; do \ if test -f $$p; then \ @@ -1119,6 +1308,8 @@ install-libLTLIBRARIES: $(lib_LTLIBRARIES) else :; fi; \ done; \ test -z "$$list2" || { \ + echo " $(MKDIR_P) '$(DESTDIR)$(libdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libdir)" || exit 1; \ echo " $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 '$(DESTDIR)$(libdir)'"; \ $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 "$(DESTDIR)$(libdir)"; \ } @@ -1142,7 +1333,6 @@ clean-libLTLIBRARIES: done install-pluginLTLIBRARIES: $(plugin_LTLIBRARIES) @$(NORMAL_INSTALL) - test -z "$(plugindir)" || $(MKDIR_P) "$(DESTDIR)$(plugindir)" @list='$(plugin_LTLIBRARIES)'; test -n "$(plugindir)" || list=; \ list2=; for p in $$list; do \ if test -f $$p; then \ @@ -1150,6 +1340,8 @@ install-pluginLTLIBRARIES: $(plugin_LTLIBRARIES) else :; fi; \ done; \ test -z "$$list2" || { \ + echo " $(MKDIR_P) '$(DESTDIR)$(plugindir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(plugindir)" || exit 1; \ echo " $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 '$(DESTDIR)$(plugindir)'"; \ $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 "$(DESTDIR)$(plugindir)"; \ } @@ -1171,14 +1363,17 @@ clean-pluginLTLIBRARIES: echo "rm -f \"$${dir}/so_locations\""; \ rm -f "$${dir}/so_locations"; \ done -libgnunet_plugin_block_fs.la: $(libgnunet_plugin_block_fs_la_OBJECTS) $(libgnunet_plugin_block_fs_la_DEPENDENCIES) +libgnunet_plugin_block_fs.la: $(libgnunet_plugin_block_fs_la_OBJECTS) $(libgnunet_plugin_block_fs_la_DEPENDENCIES) $(EXTRA_libgnunet_plugin_block_fs_la_DEPENDENCIES) $(AM_V_CCLD)$(libgnunet_plugin_block_fs_la_LINK) -rpath $(plugindir) $(libgnunet_plugin_block_fs_la_OBJECTS) $(libgnunet_plugin_block_fs_la_LIBADD) $(LIBS) -libgnunetfs.la: $(libgnunetfs_la_OBJECTS) $(libgnunetfs_la_DEPENDENCIES) +libgnunetfs.la: $(libgnunetfs_la_OBJECTS) $(libgnunetfs_la_DEPENDENCIES) $(EXTRA_libgnunetfs_la_DEPENDENCIES) $(AM_V_CCLD)$(libgnunetfs_la_LINK) -rpath $(libdir) $(libgnunetfs_la_OBJECTS) $(libgnunetfs_la_LIBADD) $(LIBS) install-binPROGRAMS: $(bin_PROGRAMS) @$(NORMAL_INSTALL) - test -z "$(bindir)" || $(MKDIR_P) "$(DESTDIR)$(bindir)" @list='$(bin_PROGRAMS)'; test -n "$(bindir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(bindir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(bindir)" || exit 1; \ + fi; \ for p in $$list; do echo "$$p $$p"; done | \ sed 's/$(EXEEXT)$$//' | \ while read p p1; do if test -f $$p || test -f $$p1; \ @@ -1227,112 +1422,188 @@ clean-checkPROGRAMS: list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ echo " rm -f" $$list; \ rm -f $$list -gnunet-directory$(EXEEXT): $(gnunet_directory_OBJECTS) $(gnunet_directory_DEPENDENCIES) +install-libexecPROGRAMS: $(libexec_PROGRAMS) + @$(NORMAL_INSTALL) + @list='$(libexec_PROGRAMS)'; test -n "$(libexecdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(libexecdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libexecdir)" || exit 1; \ + fi; \ + for p in $$list; do echo "$$p $$p"; done | \ + sed 's/$(EXEEXT)$$//' | \ + while read p p1; do if test -f $$p || test -f $$p1; \ + then echo "$$p"; echo "$$p"; else :; fi; \ + done | \ + sed -e 'p;s,.*/,,;n;h' -e 's|.*|.|' \ + -e 'p;x;s,.*/,,;s/$(EXEEXT)$$//;$(transform);s/$$/$(EXEEXT)/' | \ + sed 'N;N;N;s,\n, ,g' | \ + $(AWK) 'BEGIN { files["."] = ""; dirs["."] = 1 } \ + { d=$$3; if (dirs[d] != 1) { print "d", d; dirs[d] = 1 } \ + if ($$2 == $$4) files[d] = files[d] " " $$1; \ + else { print "f", $$3 "/" $$4, $$1; } } \ + END { for (d in files) print "f", d, files[d] }' | \ + while read type dir files; do \ + if test "$$dir" = .; then dir=; else dir=/$$dir; fi; \ + test -z "$$files" || { \ + echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files '$(DESTDIR)$(libexecdir)$$dir'"; \ + $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files "$(DESTDIR)$(libexecdir)$$dir" || exit $$?; \ + } \ + ; done + +uninstall-libexecPROGRAMS: + @$(NORMAL_UNINSTALL) + @list='$(libexec_PROGRAMS)'; test -n "$(libexecdir)" || list=; \ + files=`for p in $$list; do echo "$$p"; done | \ + sed -e 'h;s,^.*/,,;s/$(EXEEXT)$$//;$(transform)' \ + -e 's/$$/$(EXEEXT)/' `; \ + test -n "$$list" || exit 0; \ + echo " ( cd '$(DESTDIR)$(libexecdir)' && rm -f" $$files ")"; \ + cd "$(DESTDIR)$(libexecdir)" && rm -f $$files + +clean-libexecPROGRAMS: + @list='$(libexec_PROGRAMS)'; test -n "$$list" || exit 0; \ + echo " rm -f" $$list; \ + rm -f $$list || exit $$?; \ + test -n "$(EXEEXT)" || exit 0; \ + list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ + echo " rm -f" $$list; \ + rm -f $$list + +clean-noinstPROGRAMS: + @list='$(noinst_PROGRAMS)'; test -n "$$list" || exit 0; \ + echo " rm -f" $$list; \ + rm -f $$list || exit $$?; \ + test -n "$(EXEEXT)" || exit 0; \ + list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ + echo " rm -f" $$list; \ + rm -f $$list +gnunet-auto-share$(EXEEXT): $(gnunet_auto_share_OBJECTS) $(gnunet_auto_share_DEPENDENCIES) $(EXTRA_gnunet_auto_share_DEPENDENCIES) + @rm -f gnunet-auto-share$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(gnunet_auto_share_OBJECTS) $(gnunet_auto_share_LDADD) $(LIBS) +gnunet-daemon-fsprofiler$(EXEEXT): $(gnunet_daemon_fsprofiler_OBJECTS) $(gnunet_daemon_fsprofiler_DEPENDENCIES) $(EXTRA_gnunet_daemon_fsprofiler_DEPENDENCIES) + @rm -f gnunet-daemon-fsprofiler$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(gnunet_daemon_fsprofiler_OBJECTS) $(gnunet_daemon_fsprofiler_LDADD) $(LIBS) +gnunet-directory$(EXEEXT): $(gnunet_directory_OBJECTS) $(gnunet_directory_DEPENDENCIES) $(EXTRA_gnunet_directory_DEPENDENCIES) @rm -f gnunet-directory$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_directory_OBJECTS) $(gnunet_directory_LDADD) $(LIBS) -gnunet-download$(EXEEXT): $(gnunet_download_OBJECTS) $(gnunet_download_DEPENDENCIES) +gnunet-download$(EXEEXT): $(gnunet_download_OBJECTS) $(gnunet_download_DEPENDENCIES) $(EXTRA_gnunet_download_DEPENDENCIES) @rm -f gnunet-download$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_download_OBJECTS) $(gnunet_download_LDADD) $(LIBS) -gnunet-fs$(EXEEXT): $(gnunet_fs_OBJECTS) $(gnunet_fs_DEPENDENCIES) +gnunet-fs$(EXEEXT): $(gnunet_fs_OBJECTS) $(gnunet_fs_DEPENDENCIES) $(EXTRA_gnunet_fs_DEPENDENCIES) @rm -f gnunet-fs$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_fs_OBJECTS) $(gnunet_fs_LDADD) $(LIBS) -gnunet-helper-fs-publish$(EXEEXT): $(gnunet_helper_fs_publish_OBJECTS) $(gnunet_helper_fs_publish_DEPENDENCIES) +gnunet-fs-profiler$(EXEEXT): $(gnunet_fs_profiler_OBJECTS) $(gnunet_fs_profiler_DEPENDENCIES) $(EXTRA_gnunet_fs_profiler_DEPENDENCIES) + @rm -f gnunet-fs-profiler$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(gnunet_fs_profiler_OBJECTS) $(gnunet_fs_profiler_LDADD) $(LIBS) +gnunet-helper-fs-publish$(EXEEXT): $(gnunet_helper_fs_publish_OBJECTS) $(gnunet_helper_fs_publish_DEPENDENCIES) $(EXTRA_gnunet_helper_fs_publish_DEPENDENCIES) @rm -f gnunet-helper-fs-publish$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_helper_fs_publish_OBJECTS) $(gnunet_helper_fs_publish_LDADD) $(LIBS) -gnunet-pseudonym$(EXEEXT): $(gnunet_pseudonym_OBJECTS) $(gnunet_pseudonym_DEPENDENCIES) +gnunet-pseudonym$(EXEEXT): $(gnunet_pseudonym_OBJECTS) $(gnunet_pseudonym_DEPENDENCIES) $(EXTRA_gnunet_pseudonym_DEPENDENCIES) @rm -f gnunet-pseudonym$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_pseudonym_OBJECTS) $(gnunet_pseudonym_LDADD) $(LIBS) -gnunet-publish$(EXEEXT): $(gnunet_publish_OBJECTS) $(gnunet_publish_DEPENDENCIES) +gnunet-publish$(EXEEXT): $(gnunet_publish_OBJECTS) $(gnunet_publish_DEPENDENCIES) $(EXTRA_gnunet_publish_DEPENDENCIES) @rm -f gnunet-publish$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_publish_OBJECTS) $(gnunet_publish_LDADD) $(LIBS) -gnunet-search$(EXEEXT): $(gnunet_search_OBJECTS) $(gnunet_search_DEPENDENCIES) +gnunet-search$(EXEEXT): $(gnunet_search_OBJECTS) $(gnunet_search_DEPENDENCIES) $(EXTRA_gnunet_search_DEPENDENCIES) @rm -f gnunet-search$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_search_OBJECTS) $(gnunet_search_LDADD) $(LIBS) -gnunet-service-fs$(EXEEXT): $(gnunet_service_fs_OBJECTS) $(gnunet_service_fs_DEPENDENCIES) +gnunet-service-fs$(EXEEXT): $(gnunet_service_fs_OBJECTS) $(gnunet_service_fs_DEPENDENCIES) $(EXTRA_gnunet_service_fs_DEPENDENCIES) @rm -f gnunet-service-fs$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_service_fs_OBJECTS) $(gnunet_service_fs_LDADD) $(LIBS) -gnunet-unindex$(EXEEXT): $(gnunet_unindex_OBJECTS) $(gnunet_unindex_DEPENDENCIES) +gnunet-unindex$(EXEEXT): $(gnunet_unindex_OBJECTS) $(gnunet_unindex_DEPENDENCIES) $(EXTRA_gnunet_unindex_DEPENDENCIES) @rm -f gnunet-unindex$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_unindex_OBJECTS) $(gnunet_unindex_LDADD) $(LIBS) -perf_gnunet_service_fs_p2p$(EXEEXT): $(perf_gnunet_service_fs_p2p_OBJECTS) $(perf_gnunet_service_fs_p2p_DEPENDENCIES) +perf_gnunet_service_fs_p2p$(EXEEXT): $(perf_gnunet_service_fs_p2p_OBJECTS) $(perf_gnunet_service_fs_p2p_DEPENDENCIES) $(EXTRA_perf_gnunet_service_fs_p2p_DEPENDENCIES) @rm -f perf_gnunet_service_fs_p2p$(EXEEXT) $(AM_V_CCLD)$(LINK) $(perf_gnunet_service_fs_p2p_OBJECTS) $(perf_gnunet_service_fs_p2p_LDADD) $(LIBS) -perf_gnunet_service_fs_p2p_dht$(EXEEXT): $(perf_gnunet_service_fs_p2p_dht_OBJECTS) $(perf_gnunet_service_fs_p2p_dht_DEPENDENCIES) +perf_gnunet_service_fs_p2p_dht$(EXEEXT): $(perf_gnunet_service_fs_p2p_dht_OBJECTS) $(perf_gnunet_service_fs_p2p_dht_DEPENDENCIES) $(EXTRA_perf_gnunet_service_fs_p2p_dht_DEPENDENCIES) @rm -f perf_gnunet_service_fs_p2p_dht$(EXEEXT) $(AM_V_CCLD)$(LINK) $(perf_gnunet_service_fs_p2p_dht_OBJECTS) $(perf_gnunet_service_fs_p2p_dht_LDADD) $(LIBS) -perf_gnunet_service_fs_p2p_index$(EXEEXT): $(perf_gnunet_service_fs_p2p_index_OBJECTS) $(perf_gnunet_service_fs_p2p_index_DEPENDENCIES) +perf_gnunet_service_fs_p2p_index$(EXEEXT): $(perf_gnunet_service_fs_p2p_index_OBJECTS) $(perf_gnunet_service_fs_p2p_index_DEPENDENCIES) $(EXTRA_perf_gnunet_service_fs_p2p_index_DEPENDENCIES) @rm -f perf_gnunet_service_fs_p2p_index$(EXEEXT) $(AM_V_CCLD)$(LINK) $(perf_gnunet_service_fs_p2p_index_OBJECTS) $(perf_gnunet_service_fs_p2p_index_LDADD) $(LIBS) -perf_gnunet_service_fs_p2p_trust$(EXEEXT): $(perf_gnunet_service_fs_p2p_trust_OBJECTS) $(perf_gnunet_service_fs_p2p_trust_DEPENDENCIES) - @rm -f perf_gnunet_service_fs_p2p_trust$(EXEEXT) - $(AM_V_CCLD)$(LINK) $(perf_gnunet_service_fs_p2p_trust_OBJECTS) $(perf_gnunet_service_fs_p2p_trust_LDADD) $(LIBS) -test_fs_directory$(EXEEXT): $(test_fs_directory_OBJECTS) $(test_fs_directory_DEPENDENCIES) +perf_gnunet_service_fs_p2p_respect$(EXEEXT): $(perf_gnunet_service_fs_p2p_respect_OBJECTS) $(perf_gnunet_service_fs_p2p_respect_DEPENDENCIES) $(EXTRA_perf_gnunet_service_fs_p2p_respect_DEPENDENCIES) + @rm -f perf_gnunet_service_fs_p2p_respect$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(perf_gnunet_service_fs_p2p_respect_OBJECTS) $(perf_gnunet_service_fs_p2p_respect_LDADD) $(LIBS) +test_fs_directory$(EXEEXT): $(test_fs_directory_OBJECTS) $(test_fs_directory_DEPENDENCIES) $(EXTRA_test_fs_directory_DEPENDENCIES) @rm -f test_fs_directory$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_fs_directory_OBJECTS) $(test_fs_directory_LDADD) $(LIBS) -test_fs_download$(EXEEXT): $(test_fs_download_OBJECTS) $(test_fs_download_DEPENDENCIES) +test_fs_download$(EXEEXT): $(test_fs_download_OBJECTS) $(test_fs_download_DEPENDENCIES) $(EXTRA_test_fs_download_DEPENDENCIES) @rm -f test_fs_download$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_fs_download_OBJECTS) $(test_fs_download_LDADD) $(LIBS) -test_fs_download_indexed$(EXEEXT): $(test_fs_download_indexed_OBJECTS) $(test_fs_download_indexed_DEPENDENCIES) +test_fs_download_indexed$(EXEEXT): $(test_fs_download_indexed_OBJECTS) $(test_fs_download_indexed_DEPENDENCIES) $(EXTRA_test_fs_download_indexed_DEPENDENCIES) @rm -f test_fs_download_indexed$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_fs_download_indexed_OBJECTS) $(test_fs_download_indexed_LDADD) $(LIBS) -test_fs_download_persistence$(EXEEXT): $(test_fs_download_persistence_OBJECTS) $(test_fs_download_persistence_DEPENDENCIES) +test_fs_download_persistence$(EXEEXT): $(test_fs_download_persistence_OBJECTS) $(test_fs_download_persistence_DEPENDENCIES) $(EXTRA_test_fs_download_persistence_DEPENDENCIES) @rm -f test_fs_download_persistence$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_fs_download_persistence_OBJECTS) $(test_fs_download_persistence_LDADD) $(LIBS) -test_fs_file_information$(EXEEXT): $(test_fs_file_information_OBJECTS) $(test_fs_file_information_DEPENDENCIES) +test_fs_download_stream$(EXEEXT): $(test_fs_download_stream_OBJECTS) $(test_fs_download_stream_DEPENDENCIES) $(EXTRA_test_fs_download_stream_DEPENDENCIES) + @rm -f test_fs_download_stream$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_fs_download_stream_OBJECTS) $(test_fs_download_stream_LDADD) $(LIBS) +test_fs_file_information$(EXEEXT): $(test_fs_file_information_OBJECTS) $(test_fs_file_information_DEPENDENCIES) $(EXTRA_test_fs_file_information_DEPENDENCIES) @rm -f test_fs_file_information$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_fs_file_information_OBJECTS) $(test_fs_file_information_LDADD) $(LIBS) -test_fs_getopt$(EXEEXT): $(test_fs_getopt_OBJECTS) $(test_fs_getopt_DEPENDENCIES) +test_fs_getopt$(EXEEXT): $(test_fs_getopt_OBJECTS) $(test_fs_getopt_DEPENDENCIES) $(EXTRA_test_fs_getopt_DEPENDENCIES) @rm -f test_fs_getopt$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_fs_getopt_OBJECTS) $(test_fs_getopt_LDADD) $(LIBS) -test_fs_list_indexed$(EXEEXT): $(test_fs_list_indexed_OBJECTS) $(test_fs_list_indexed_DEPENDENCIES) +test_fs_list_indexed$(EXEEXT): $(test_fs_list_indexed_OBJECTS) $(test_fs_list_indexed_DEPENDENCIES) $(EXTRA_test_fs_list_indexed_DEPENDENCIES) @rm -f test_fs_list_indexed$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_fs_list_indexed_OBJECTS) $(test_fs_list_indexed_LDADD) $(LIBS) -test_fs_namespace$(EXEEXT): $(test_fs_namespace_OBJECTS) $(test_fs_namespace_DEPENDENCIES) +test_fs_namespace$(EXEEXT): $(test_fs_namespace_OBJECTS) $(test_fs_namespace_DEPENDENCIES) $(EXTRA_test_fs_namespace_DEPENDENCIES) @rm -f test_fs_namespace$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_fs_namespace_OBJECTS) $(test_fs_namespace_LDADD) $(LIBS) -test_fs_namespace_list_updateable$(EXEEXT): $(test_fs_namespace_list_updateable_OBJECTS) $(test_fs_namespace_list_updateable_DEPENDENCIES) +test_fs_namespace_list_updateable$(EXEEXT): $(test_fs_namespace_list_updateable_OBJECTS) $(test_fs_namespace_list_updateable_DEPENDENCIES) $(EXTRA_test_fs_namespace_list_updateable_DEPENDENCIES) @rm -f test_fs_namespace_list_updateable$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_fs_namespace_list_updateable_OBJECTS) $(test_fs_namespace_list_updateable_LDADD) $(LIBS) -test_fs_publish$(EXEEXT): $(test_fs_publish_OBJECTS) $(test_fs_publish_DEPENDENCIES) +test_fs_publish$(EXEEXT): $(test_fs_publish_OBJECTS) $(test_fs_publish_DEPENDENCIES) $(EXTRA_test_fs_publish_DEPENDENCIES) @rm -f test_fs_publish$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_fs_publish_OBJECTS) $(test_fs_publish_LDADD) $(LIBS) -test_fs_publish_persistence$(EXEEXT): $(test_fs_publish_persistence_OBJECTS) $(test_fs_publish_persistence_DEPENDENCIES) +test_fs_publish_persistence$(EXEEXT): $(test_fs_publish_persistence_OBJECTS) $(test_fs_publish_persistence_DEPENDENCIES) $(EXTRA_test_fs_publish_persistence_DEPENDENCIES) @rm -f test_fs_publish_persistence$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_fs_publish_persistence_OBJECTS) $(test_fs_publish_persistence_LDADD) $(LIBS) -test_fs_search$(EXEEXT): $(test_fs_search_OBJECTS) $(test_fs_search_DEPENDENCIES) +test_fs_search$(EXEEXT): $(test_fs_search_OBJECTS) $(test_fs_search_DEPENDENCIES) $(EXTRA_test_fs_search_DEPENDENCIES) @rm -f test_fs_search$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_fs_search_OBJECTS) $(test_fs_search_LDADD) $(LIBS) -test_fs_search_persistence$(EXEEXT): $(test_fs_search_persistence_OBJECTS) $(test_fs_search_persistence_DEPENDENCIES) +test_fs_search_persistence$(EXEEXT): $(test_fs_search_persistence_OBJECTS) $(test_fs_search_persistence_DEPENDENCIES) $(EXTRA_test_fs_search_persistence_DEPENDENCIES) @rm -f test_fs_search_persistence$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_fs_search_persistence_OBJECTS) $(test_fs_search_persistence_LDADD) $(LIBS) -test_fs_search_probes$(EXEEXT): $(test_fs_search_probes_OBJECTS) $(test_fs_search_probes_DEPENDENCIES) +test_fs_search_probes$(EXEEXT): $(test_fs_search_probes_OBJECTS) $(test_fs_search_probes_DEPENDENCIES) $(EXTRA_test_fs_search_probes_DEPENDENCIES) @rm -f test_fs_search_probes$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_fs_search_probes_OBJECTS) $(test_fs_search_probes_LDADD) $(LIBS) -test_fs_start_stop$(EXEEXT): $(test_fs_start_stop_OBJECTS) $(test_fs_start_stop_DEPENDENCIES) +test_fs_start_stop$(EXEEXT): $(test_fs_start_stop_OBJECTS) $(test_fs_start_stop_DEPENDENCIES) $(EXTRA_test_fs_start_stop_DEPENDENCIES) @rm -f test_fs_start_stop$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_fs_start_stop_OBJECTS) $(test_fs_start_stop_LDADD) $(LIBS) -test_fs_test_lib$(EXEEXT): $(test_fs_test_lib_OBJECTS) $(test_fs_test_lib_DEPENDENCIES) +test_fs_test_lib$(EXEEXT): $(test_fs_test_lib_OBJECTS) $(test_fs_test_lib_DEPENDENCIES) $(EXTRA_test_fs_test_lib_DEPENDENCIES) @rm -f test_fs_test_lib$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_fs_test_lib_OBJECTS) $(test_fs_test_lib_LDADD) $(LIBS) -test_fs_unindex$(EXEEXT): $(test_fs_unindex_OBJECTS) $(test_fs_unindex_DEPENDENCIES) +test_fs_unindex$(EXEEXT): $(test_fs_unindex_OBJECTS) $(test_fs_unindex_DEPENDENCIES) $(EXTRA_test_fs_unindex_DEPENDENCIES) @rm -f test_fs_unindex$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_fs_unindex_OBJECTS) $(test_fs_unindex_LDADD) $(LIBS) -test_fs_unindex_persistence$(EXEEXT): $(test_fs_unindex_persistence_OBJECTS) $(test_fs_unindex_persistence_DEPENDENCIES) +test_fs_unindex_persistence$(EXEEXT): $(test_fs_unindex_persistence_OBJECTS) $(test_fs_unindex_persistence_DEPENDENCIES) $(EXTRA_test_fs_unindex_persistence_DEPENDENCIES) @rm -f test_fs_unindex_persistence$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_fs_unindex_persistence_OBJECTS) $(test_fs_unindex_persistence_LDADD) $(LIBS) -test_fs_uri$(EXEEXT): $(test_fs_uri_OBJECTS) $(test_fs_uri_DEPENDENCIES) +test_fs_uri$(EXEEXT): $(test_fs_uri_OBJECTS) $(test_fs_uri_DEPENDENCIES) $(EXTRA_test_fs_uri_DEPENDENCIES) @rm -f test_fs_uri$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_fs_uri_OBJECTS) $(test_fs_uri_LDADD) $(LIBS) -test_gnunet_service_fs_migration$(EXEEXT): $(test_gnunet_service_fs_migration_OBJECTS) $(test_gnunet_service_fs_migration_DEPENDENCIES) +test_gnunet_service_fs_migration$(EXEEXT): $(test_gnunet_service_fs_migration_OBJECTS) $(test_gnunet_service_fs_migration_DEPENDENCIES) $(EXTRA_test_gnunet_service_fs_migration_DEPENDENCIES) @rm -f test_gnunet_service_fs_migration$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_gnunet_service_fs_migration_OBJECTS) $(test_gnunet_service_fs_migration_LDADD) $(LIBS) -test_gnunet_service_fs_p2p$(EXEEXT): $(test_gnunet_service_fs_p2p_OBJECTS) $(test_gnunet_service_fs_p2p_DEPENDENCIES) +test_gnunet_service_fs_p2p$(EXEEXT): $(test_gnunet_service_fs_p2p_OBJECTS) $(test_gnunet_service_fs_p2p_DEPENDENCIES) $(EXTRA_test_gnunet_service_fs_p2p_DEPENDENCIES) @rm -f test_gnunet_service_fs_p2p$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_gnunet_service_fs_p2p_OBJECTS) $(test_gnunet_service_fs_p2p_LDADD) $(LIBS) +test_gnunet_service_fs_p2p_stream$(EXEEXT): $(test_gnunet_service_fs_p2p_stream_OBJECTS) $(test_gnunet_service_fs_p2p_stream_DEPENDENCIES) $(EXTRA_test_gnunet_service_fs_p2p_stream_DEPENDENCIES) + @rm -f test_gnunet_service_fs_p2p_stream$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_gnunet_service_fs_p2p_stream_OBJECTS) $(test_gnunet_service_fs_p2p_stream_LDADD) $(LIBS) +test_plugin_block_fs$(EXEEXT): $(test_plugin_block_fs_OBJECTS) $(test_plugin_block_fs_DEPENDENCIES) $(EXTRA_test_plugin_block_fs_DEPENDENCIES) + @rm -f test_plugin_block_fs$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_plugin_block_fs_OBJECTS) $(test_plugin_block_fs_LDADD) $(LIBS) install-binSCRIPTS: $(bin_SCRIPTS) @$(NORMAL_INSTALL) - test -z "$(bindir)" || $(MKDIR_P) "$(DESTDIR)$(bindir)" @list='$(bin_SCRIPTS)'; test -n "$(bindir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(bindir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(bindir)" || exit 1; \ + fi; \ for p in $$list; do \ if test -f "$$p"; then d=; else d="$(srcdir)/"; fi; \ if test -f "$$d$$p"; then echo "$$d$$p"; echo "$$p"; else :; fi; \ @@ -1360,9 +1631,7 @@ uninstall-binSCRIPTS: @list='$(bin_SCRIPTS)'; test -n "$(bindir)" || exit 0; \ files=`for p in $$list; do echo "$$p"; done | \ sed -e 's,.*/,,;$(transform)'`; \ - test -n "$$list" || exit 0; \ - echo " ( cd '$(DESTDIR)$(bindir)' && rm -f" $$files ")"; \ - cd "$(DESTDIR)$(bindir)" && rm -f $$files + dir='$(DESTDIR)$(bindir)'; $(am__uninstall_files_from_dir) mostlyclean-compile: -rm -f *.$(OBJEXT) @@ -1388,8 +1657,11 @@ distclean-compile: @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/fs_tree.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/fs_unindex.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/fs_uri.Plo@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-auto-share.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-daemon-fsprofiler.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-directory.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-download.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-fs-profiler.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-fs.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-helper-fs-publish.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-pseudonym.Po@am__quote@ @@ -1403,13 +1675,13 @@ distclean-compile: @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-service-fs_pr.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-service-fs_push.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-service-fs_put.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-service-fs_stream.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-unindex.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/perf_gnunet_service_fs_p2p.Po@am__quote@ -@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/perf_gnunet_service_fs_p2p_trust.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/perf_gnunet_service_fs_p2p_respect.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/plugin_block_fs.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_fs_directory.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_fs_download.Po@am__quote@ -@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_fs_download_indexed.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_fs_download_persistence.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_fs_file_information.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_fs_getopt.Po@am__quote@ @@ -1428,30 +1700,28 @@ distclean-compile: @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_fs_uri.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_gnunet_service_fs_migration.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_gnunet_service_fs_p2p.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_plugin_block_fs.Po@am__quote@ .c.o: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c $< .c.obj: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'` @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c `$(CYGPATH_W) '$<'` +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c `$(CYGPATH_W) '$<'` .c.lo: @am__fastdepCC_TRUE@ $(AM_V_CC)$(LTCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LTCOMPILE) -c -o $@ $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LTCOMPILE) -c -o $@ $< mostlyclean-libtool: -rm -f *.lo @@ -1460,8 +1730,11 @@ clean-libtool: -rm -rf .libs _libs install-pkgcfgDATA: $(pkgcfg_DATA) @$(NORMAL_INSTALL) - test -z "$(pkgcfgdir)" || $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" @list='$(pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(pkgcfgdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" || exit 1; \ + fi; \ for p in $$list; do \ if test -f "$$p"; then d=; else d="$(srcdir)/"; fi; \ echo "$$d$$p"; \ @@ -1475,9 +1748,7 @@ uninstall-pkgcfgDATA: @$(NORMAL_UNINSTALL) @list='$(pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ files=`for p in $$list; do echo $$p; done | sed -e 's|^.*/||'`; \ - test -n "$$files" || exit 0; \ - echo " ( cd '$(DESTDIR)$(pkgcfgdir)' && rm -f" $$files ")"; \ - cd "$(DESTDIR)$(pkgcfgdir)" && rm -f $$files + dir='$(DESTDIR)$(pkgcfgdir)'; $(am__uninstall_files_from_dir) ID: $(HEADERS) $(SOURCES) $(LISP) $(TAGS_FILES) list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ @@ -1612,14 +1883,15 @@ check-TESTS: $(TESTS) fi; \ dashes=`echo "$$dashes" | sed s/./=/g`; \ if test "$$failed" -eq 0; then \ - echo "$$grn$$dashes"; \ + col="$$grn"; \ else \ - echo "$$red$$dashes"; \ + col="$$red"; \ fi; \ - echo "$$banner"; \ - test -z "$$skipped" || echo "$$skipped"; \ - test -z "$$report" || echo "$$report"; \ - echo "$$dashes$$std"; \ + echo "$${col}$$dashes$${std}"; \ + echo "$${col}$$banner$${std}"; \ + test -z "$$skipped" || echo "$${col}$$skipped$${std}"; \ + test -z "$$report" || echo "$${col}$$report$${std}"; \ + echo "$${col}$$dashes$${std}"; \ test "$$failed" -eq 0; \ else :; fi @@ -1662,7 +1934,7 @@ all-am: Makefile $(LIBRARIES) $(LTLIBRARIES) $(PROGRAMS) $(SCRIPTS) \ install-binPROGRAMS: install-libLTLIBRARIES installdirs: - for dir in "$(DESTDIR)$(libdir)" "$(DESTDIR)$(plugindir)" "$(DESTDIR)$(bindir)" "$(DESTDIR)$(bindir)" "$(DESTDIR)$(pkgcfgdir)"; do \ + for dir in "$(DESTDIR)$(libdir)" "$(DESTDIR)$(plugindir)" "$(DESTDIR)$(bindir)" "$(DESTDIR)$(libexecdir)" "$(DESTDIR)$(bindir)" "$(DESTDIR)$(pkgcfgdir)"; do \ test -z "$$dir" || $(MKDIR_P) "$$dir"; \ done install: install-am @@ -1675,10 +1947,15 @@ install-am: all-am installcheck: installcheck-am install-strip: - $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ - install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ - `test -z '$(STRIP)' || \ - echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi mostlyclean-generic: clean-generic: @@ -1694,7 +1971,8 @@ maintainer-clean-generic: clean: clean-am clean-am: clean-binPROGRAMS clean-checkPROGRAMS clean-generic \ - clean-libLTLIBRARIES clean-libtool clean-noinstLIBRARIES \ + clean-libLTLIBRARIES clean-libexecPROGRAMS clean-libtool \ + clean-noinstLIBRARIES clean-noinstPROGRAMS \ clean-pluginLTLIBRARIES mostlyclean-am distclean: distclean-am @@ -1722,7 +2000,7 @@ install-dvi: install-dvi-am install-dvi-am: install-exec-am: install-binPROGRAMS install-binSCRIPTS \ - install-libLTLIBRARIES + install-libLTLIBRARIES install-libexecPROGRAMS install-html: install-html-am @@ -1763,28 +2041,30 @@ ps: ps-am ps-am: uninstall-am: uninstall-binPROGRAMS uninstall-binSCRIPTS \ - uninstall-libLTLIBRARIES uninstall-pkgcfgDATA \ - uninstall-pluginLTLIBRARIES + uninstall-libLTLIBRARIES uninstall-libexecPROGRAMS \ + uninstall-pkgcfgDATA uninstall-pluginLTLIBRARIES .MAKE: check-am install-am install-strip .PHONY: CTAGS GTAGS all all-am check check-TESTS check-am clean \ clean-binPROGRAMS clean-checkPROGRAMS clean-generic \ - clean-libLTLIBRARIES clean-libtool clean-noinstLIBRARIES \ + clean-libLTLIBRARIES clean-libexecPROGRAMS clean-libtool \ + clean-noinstLIBRARIES clean-noinstPROGRAMS \ clean-pluginLTLIBRARIES ctags distclean distclean-compile \ distclean-generic distclean-libtool distclean-tags distdir dvi \ dvi-am html html-am info info-am install install-am \ install-binPROGRAMS install-binSCRIPTS install-data \ install-data-am install-dvi install-dvi-am install-exec \ install-exec-am install-html install-html-am install-info \ - install-info-am install-libLTLIBRARIES install-man install-pdf \ - install-pdf-am install-pkgcfgDATA install-pluginLTLIBRARIES \ - install-ps install-ps-am install-strip installcheck \ - installcheck-am installdirs maintainer-clean \ - maintainer-clean-generic mostlyclean mostlyclean-compile \ - mostlyclean-generic mostlyclean-libtool pdf pdf-am ps ps-am \ - tags uninstall uninstall-am uninstall-binPROGRAMS \ - uninstall-binSCRIPTS uninstall-libLTLIBRARIES \ + install-info-am install-libLTLIBRARIES install-libexecPROGRAMS \ + install-man install-pdf install-pdf-am install-pkgcfgDATA \ + install-pluginLTLIBRARIES install-ps install-ps-am \ + install-strip installcheck installcheck-am installdirs \ + maintainer-clean maintainer-clean-generic mostlyclean \ + mostlyclean-compile mostlyclean-generic mostlyclean-libtool \ + pdf pdf-am ps ps-am tags uninstall uninstall-am \ + uninstall-binPROGRAMS uninstall-binSCRIPTS \ + uninstall-libLTLIBRARIES uninstall-libexecPROGRAMS \ uninstall-pkgcfgDATA uninstall-pluginLTLIBRARIES diff --git a/src/fs/fs.conf.in b/src/fs/fs.conf.in index a908b1f..f45a78f 100644 --- a/src/fs/fs.conf.in +++ b/src/fs/fs.conf.in @@ -1,33 +1,71 @@ [fs] AUTOSTART = YES INDEXDB = $SERVICEHOME/fs/idxinfo.lst -TRUST = $SERVICEHOME/fs/credit/ +RESPECT = $SERVICEHOME/fs/credit/ IDENTITY_DIR = $SERVICEHOME/fs/identities/ STATE_DIR = $SERVICEHOME/fs/persistence/ UPDATE_DIR = $SERVICEHOME/fs/updates/ @UNIXONLY@ PORT = 2094 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-fs ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; +# Do we introduce artificial delays? (may improve anonymity) DELAY = YES + +# Do we cache content from other nodes? (may improve anonymity) CONTENT_CACHING = YES + +# Do we send unsolicited data to other nodes if we have excess bandwidth? +# (may improve anonymity, probably not a good idea if content_caching is NO) CONTENT_PUSHING = YES UNIXPATH = /tmp/gnunet-service-fs.sock + +# Do we require users that want to access file-sharing to run this process +# (usually not a good idea) UNIX_MATCH_UID = NO + +# Do we require users that want to access file-sharing to be in the 'gnunet' group? UNIX_MATCH_GID = YES -# DEBUG = YES + +# Maximum number of requests this peer tracks (important for +# memory consumption; 2k RAM/request is not unusual) MAX_PENDING_REQUESTS = 65536 + +# How many requests do we have at most waiting in the queue towards +# the datastore? (important for memory consumption) +DATASTORE_QUEUE_SIZE = 1024 + # Maximum frequency we're allowed to poll the datastore # for content for migration (can be used to reduce # GNUnet's disk-IO rate) MIN_MIGRATION_DELAY = 100 ms + +# For how many neighbouring peers should we allocate hash maps? EXPECTED_NEIGHBOUR_COUNT = 128 # Enable monkey? -PREFIX = @MONKEYPREFIX@ +# PREFIX = @MONKEYPREFIX@ + +# Disable anonymous file-sharing (but keep non-anonymous transfers)? +# This option is mostly for testing. +DISABLE_ANON_TRANSFER = NO + +# Maximum number of non-anonymous transfers this peer will support +# at the same time. Excessive values mostly have the problem that +# the service might use more memory, so we need to bound this at +# some reasonable level. And if we have a very, very large +# number, we probably won't have enough bandwidth to suppor them +# well anyway, so better have a moderate cap. +MAX_STREAM_CLIENTS = 128 + + +[gnunet-auto-share] +BINARY = gnunet-auto-share +# Note: MUST specify path to auto-share directory and CAN specify other options +# to gnunet-auto-share here! +OPTIONS = $SERVICEHOME/fs/share/ diff --git a/src/fs/fs.h b/src/fs/fs.h index 059b892..ffd448d 100644 --- a/src/fs/fs.h +++ b/src/fs/fs.h @@ -1,6 +1,6 @@ /* This file is part of GNUnet. - (C) 2003, 2004, 2005, 2006, 2007, 2008, 2009 Christian Grothoff (and other contributing authors) + (C) 2003--2012 Christian Grothoff (and other contributing authors) GNUnet is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published @@ -55,12 +55,12 @@ struct ContentHashKey /** * Hash of the original content, used for encryption. */ - GNUNET_HashCode key; + struct GNUNET_HashCode key; /** * Hash of the encrypted content, used for querying. */ - GNUNET_HashCode query; + struct GNUNET_HashCode query; }; @@ -112,7 +112,7 @@ struct IndexStartMessage /** * Hash of the file that we would like to index. */ - GNUNET_HashCode file_id; + struct GNUNET_HashCode file_id; /* this is followed by a 0-terminated * filename of a file with the hash @@ -141,7 +141,7 @@ struct IndexInfoMessage /** * Hash of the indexed file. */ - GNUNET_HashCode file_id; + struct GNUNET_HashCode file_id; /* this is followed by a 0-terminated * filename of a file with the hash @@ -174,7 +174,7 @@ struct UnindexMessage /** * Hash of the file that we will unindex. */ - GNUNET_HashCode file_id; + struct GNUNET_HashCode file_id; }; @@ -245,7 +245,7 @@ struct SearchMessage *

* If the request is for a KBLOCK, "target" must be all zeros. */ - GNUNET_HashCode target; + struct GNUNET_HashCode target; /** * Hash of the keyword (aka query) for KBLOCKs; Hash of @@ -253,7 +253,7 @@ struct SearchMessage * and hash of the identifier XORed with the target for * SBLOCKS (aka query). */ - GNUNET_HashCode query; + struct GNUNET_HashCode query; /* this is followed by the hash codes of already-known * results (which should hence be excluded from what @@ -321,6 +321,18 @@ struct ClientPutMessage */ struct GNUNET_TIME_AbsoluteNBO last_transmission; + /** + * How often did we transmit this query before getting an + * answer (estimate). + */ + uint32_t num_transmissions; + + /** + * How much respect did we offer (in total) before getting an + * answer (estimate). + */ + uint32_t respect_offered; + /* this is followed by the actual encrypted content */ }; diff --git a/src/fs/fs_api.c b/src/fs/fs_api.c index 651c174..2770e86 100644 --- a/src/fs/fs_api.c +++ b/src/fs/fs_api.c @@ -1,6 +1,6 @@ /* This file is part of GNUnet. - (C) 2001, 2002, 2003, 2004, 2005, 2006, 2008, 2009, 2010, 2011 Christian Grothoff (and other contributing authors) + (C) 2001--2012 Christian Grothoff (and other contributing authors) GNUnet is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published @@ -51,7 +51,7 @@ start_job (struct GNUNET_FS_QueueEntry *qe) { GNUNET_assert (NULL == qe->client); qe->client = GNUNET_CLIENT_connect ("fs", qe->h->cfg); - if (qe->client == NULL) + if (NULL == qe->client) { GNUNET_break (0); return; @@ -59,7 +59,12 @@ start_job (struct GNUNET_FS_QueueEntry *qe) qe->start (qe->cls, qe->client); qe->start_times++; qe->h->active_blocks += qe->blocks; + qe->h->active_downloads++; qe->start_time = GNUNET_TIME_absolute_get (); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Starting job %p (%u active)\n", + qe, + qe->h->active_downloads); GNUNET_CONTAINER_DLL_remove (qe->h->pending_head, qe->h->pending_tail, qe); GNUNET_CONTAINER_DLL_insert_after (qe->h->running_head, qe->h->running_tail, qe->h->running_tail, qe); @@ -77,12 +82,17 @@ stop_job (struct GNUNET_FS_QueueEntry *qe) { qe->client = NULL; qe->stop (qe->cls); + GNUNET_assert (0 < qe->h->active_downloads); qe->h->active_downloads--; qe->h->active_blocks -= qe->blocks; qe->run_time = GNUNET_TIME_relative_add (qe->run_time, GNUNET_TIME_absolute_get_duration (qe->start_time)); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Stopping job %p (%u active)\n", + qe, + qe->h->active_downloads); GNUNET_CONTAINER_DLL_remove (qe->h->running_head, qe->h->running_tail, qe); GNUNET_CONTAINER_DLL_insert_after (qe->h->pending_head, qe->h->pending_tail, qe->h->pending_tail, qe); @@ -106,71 +116,180 @@ process_job_queue (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) struct GNUNET_TIME_Relative restart_at; struct GNUNET_TIME_Relative rst; struct GNUNET_TIME_Absolute end_time; + unsigned int num_downloads_waiting; + unsigned int num_downloads_active; + unsigned int num_downloads_expired; + unsigned int num_probes_active; + unsigned int num_probes_waiting; + unsigned int num_probes_expired; + int num_probes_change; + int num_downloads_change; + int block_limit_hit; h->queue_job = GNUNET_SCHEDULER_NO_TASK; + /* restart_at will be set to the time when it makes sense to + re-evaluate the job queue (unless, of course, jobs complete + or are added, then we'll be triggered immediately */ restart_at = GNUNET_TIME_UNIT_FOREVER_REL; - /* first, see if we can start all the jobs */ - next = h->pending_head; - while (NULL != (qe = next)) + /* first, calculate some basic statistics on pending jobs */ + num_probes_waiting = 0; + num_downloads_waiting = 0; + for (qe = h->pending_head; NULL != qe; qe = qe->next) { - next = qe->next; - if (h->running_head == NULL) - { - start_job (qe); - continue; - } - if ((qe->blocks + h->active_blocks <= h->max_parallel_requests) && - (h->active_downloads < h->max_parallel_downloads)) + switch (qe->priority) { - start_job (qe); - continue; + case GNUNET_FS_QUEUE_PRIORITY_PROBE: + num_probes_waiting++; + break; + case GNUNET_FS_QUEUE_PRIORITY_NORMAL: + num_downloads_waiting++; + break; + default: + GNUNET_break (0); + break; } } - if (h->pending_head == NULL) - return; /* no need to stop anything */ - /* then, check if we should stop some jobs */ + /* now, calculate some basic statistics on running jobs */ + num_probes_active = 0; + num_probes_expired = 0; + num_downloads_active = 0; + num_downloads_expired = 0; next = h->running_head; while (NULL != (qe = next)) { next = qe->next; - run_time = + switch (qe->priority) + { + case GNUNET_FS_QUEUE_PRIORITY_PROBE: + run_time = GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MINUTES, 2); + end_time = GNUNET_TIME_absolute_add (qe->start_time, run_time); + rst = GNUNET_TIME_absolute_get_remaining (end_time); + if (0 == rst.rel_value) + { + num_probes_expired++; + stop_job (qe); + } + else + { + num_probes_active++; + restart_at = GNUNET_TIME_relative_min (rst, restart_at); + } + break; + case GNUNET_FS_QUEUE_PRIORITY_NORMAL: + run_time = GNUNET_TIME_relative_multiply (h->avg_block_latency, qe->blocks * qe->start_times); - switch (qe->priority) + end_time = GNUNET_TIME_absolute_add (qe->start_time, run_time); + rst = GNUNET_TIME_absolute_get_remaining (end_time); + if (0 == rst.rel_value) { - case GNUNET_FS_QUEUE_PRIORITY_PROBE: - /* run probes for at most 1s * number-of-restarts; note that - as the total runtime of a probe is limited to 2m, we don't - need to additionally limit the total time of a probe to - strictly limit its lifetime. */ - run_time = GNUNET_TIME_relative_min (run_time, - GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, - 1 + qe->start_times)); - break; - case GNUNET_FS_QUEUE_PRIORITY_NORMAL: - break; - default: - GNUNET_break (0); + num_downloads_expired++; + stop_job (qe); + } + else + { + num_downloads_active++; + restart_at = GNUNET_TIME_relative_min (rst, restart_at); } - end_time = GNUNET_TIME_absolute_add (qe->start_time, run_time); - rst = GNUNET_TIME_absolute_get_remaining (end_time); - restart_at = GNUNET_TIME_relative_min (rst, restart_at); - if (rst.rel_value > 0) + break; + default: + GNUNET_break (0); + break; + } + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "PA: %u, PE: %u, PW: %u; DA: %u, DE: %u, DW: %u\n", + num_probes_active, + num_probes_expired, + num_probes_waiting, + num_downloads_active, + num_downloads_expired, + num_downloads_waiting); + /* calculate start/stop decisions */ + if (h->active_downloads + num_downloads_waiting > h->max_parallel_requests) + { + /* stop probes if possible */ + num_probes_change = - num_probes_active; + num_downloads_change = h->max_parallel_requests - h->active_downloads; + } + else + { + /* start all downloads */ + num_downloads_change = num_downloads_waiting; + /* start as many probes as we can */ + num_probes_change = GNUNET_MIN (num_probes_waiting, + h->max_parallel_requests - (h->active_downloads + num_downloads_waiting)); + } + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Changing %d probes and %d downloads\n", + num_probes_change, + num_downloads_change); + /* actually stop probes */ + next = h->running_head; + while (NULL != (qe = next)) + { + next = qe->next; + if (GNUNET_FS_QUEUE_PRIORITY_PROBE != qe->priority) continue; - stop_job (qe); + if (num_probes_change < 0) + { + stop_job (qe); + num_probes_change++; + if (0 == num_probes_change) + break; + } } - /* finally, start some more tasks if we now have empty slots */ + GNUNET_break (0 <= num_probes_change); + + /* start some more tasks if we now have empty slots */ + block_limit_hit = GNUNET_NO; next = h->pending_head; - while (NULL != (qe = next)) + while ( (NULL != (qe = next)) && + ( (num_probes_change > 0) || + (num_downloads_change > 0) ) ) { next = qe->next; - if ((qe->blocks + h->active_blocks <= h->max_parallel_requests) && - (h->active_downloads < h->max_parallel_downloads)) + switch (qe->priority) { - start_job (qe); - continue; + case GNUNET_FS_QUEUE_PRIORITY_PROBE: + if (num_probes_change > 0) + { + start_job (qe); + num_probes_change--; + run_time = GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MINUTES, 2); + restart_at = GNUNET_TIME_relative_min (run_time, restart_at); + } + break; + case GNUNET_FS_QUEUE_PRIORITY_NORMAL: + if ( (num_downloads_change > 0) && + ( (qe->blocks + h->active_blocks <= h->max_parallel_requests) || + ( (qe->blocks > h->max_parallel_requests) && + (0 == h->active_downloads) ) ) ) + { + start_job (qe); + num_downloads_change--; + } + else if (num_downloads_change > 0) + block_limit_hit = GNUNET_YES; + break; + default: + GNUNET_break (0); + break; } } + GNUNET_break ( (0 == num_downloads_change) || (GNUNET_YES == block_limit_hit) ); + GNUNET_break (0 == num_probes_change); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "AD: %u, MP: %u; %d probes and %d downloads to start, will run again in %s\n", + h->active_downloads, + h->max_parallel_requests, + num_probes_change, + num_downloads_change, + GNUNET_STRINGS_relative_time_to_string (restart_at, GNUNET_YES)); + + /* make sure we run again */ h->queue_job = GNUNET_SCHEDULER_add_delayed (restart_at, &process_job_queue, h); } @@ -207,24 +326,31 @@ GNUNET_FS_queue_ (struct GNUNET_FS_Handle *h, GNUNET_FS_QueueStart start, if (h->queue_job != GNUNET_SCHEDULER_NO_TASK) GNUNET_SCHEDULER_cancel (h->queue_job); h->queue_job = GNUNET_SCHEDULER_add_now (&process_job_queue, h); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Queueing job %p\n", + qe); return qe; } /** * Dequeue a job from the queue. - * @param qh handle for the job + * + * @param qe handle for the job */ void -GNUNET_FS_dequeue_ (struct GNUNET_FS_QueueEntry *qh) +GNUNET_FS_dequeue_ (struct GNUNET_FS_QueueEntry *qe) { struct GNUNET_FS_Handle *h; - h = qh->h; - if (qh->client != NULL) - stop_job (qh); - GNUNET_CONTAINER_DLL_remove (h->pending_head, h->pending_tail, qh); - GNUNET_free (qh); + h = qe->h; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Dequeueing job %p\n", + qe); + if (NULL != qe->client) + stop_job (qe); + GNUNET_CONTAINER_DLL_remove (h->pending_head, h->pending_tail, qe); + GNUNET_free (qe); if (h->queue_job != GNUNET_SCHEDULER_NO_TASK) GNUNET_SCHEDULER_cancel (h->queue_job); h->queue_job = GNUNET_SCHEDULER_add_now (&process_job_queue, h); @@ -341,9 +467,9 @@ GNUNET_FS_data_reader_file_ (void *cls, uint64_t offset, size_t max, void *buf, return 0; } } - GNUNET_DISK_file_seek (fi->fd, offset, GNUNET_DISK_SEEK_SET); - ret = GNUNET_DISK_file_read (fi->fd, buf, max); - if (-1 == ret) + if ( (GNUNET_SYSERR == + GNUNET_DISK_file_seek (fi->fd, offset, GNUNET_DISK_SEEK_SET)) || + (-1 == (ret = GNUNET_DISK_file_read (fi->fd, buf, max))) ) { GNUNET_asprintf (emsg, _("Could not read file `%s': %s"), fi->filename, STRERROR (errno)); @@ -372,7 +498,7 @@ GNUNET_FS_make_file_reader_context_ (const char *filename) fi = GNUNET_malloc (sizeof (struct FileInfo)); fi->filename = GNUNET_STRINGS_filename_expand (filename); - if (fi->filename == NULL) + if (NULL == fi->filename) { GNUNET_free (fi); return NULL; @@ -409,7 +535,7 @@ GNUNET_FS_data_reader_copy_ (void *cls, uint64_t offset, size_t max, void *buf, if (UINT64_MAX == offset) return 0; - if (max == 0) + if (0 == max) { GNUNET_free_non_null (data); return 0; @@ -496,7 +622,7 @@ get_read_handle (struct GNUNET_FS_Handle *h, const char *ext, const char *ent) struct GNUNET_BIO_ReadHandle *ret; fn = get_serialization_file_name (h, ext, ent); - if (fn == NULL) + if (NULL == fn) return NULL; ret = GNUNET_BIO_read_open (fn); GNUNET_free (fn); @@ -519,13 +645,10 @@ get_write_handle (struct GNUNET_FS_Handle *h, const char *ext, const char *ent) struct GNUNET_BIO_WriteHandle *ret; fn = get_serialization_file_name (h, ext, ent); - if (fn == NULL) - { + if (NULL == fn) return NULL; - } ret = GNUNET_BIO_write_open (fn); - if (ret == NULL) - GNUNET_break (0); + GNUNET_break (NULL != ret); GNUNET_free (fn); return ret; } @@ -548,7 +671,7 @@ get_write_handle_in_dir (struct GNUNET_FS_Handle *h, const char *ext, struct GNUNET_BIO_WriteHandle *ret; fn = get_serialization_file_name_in_dir (h, ext, uni, ent); - if (fn == NULL) + if (NULL == fn) return NULL; ret = GNUNET_BIO_write_open (fn); GNUNET_free (fn); @@ -575,7 +698,7 @@ GNUNET_FS_remove_sync_file_ (struct GNUNET_FS_Handle *h, const char *ext, return; } filename = get_serialization_file_name (h, ext, ent); - if (filename != NULL) + if (NULL != filename) { if (0 != UNLINK (filename)) GNUNET_log_strerror_file (GNUNET_ERROR_TYPE_WARNING, "unlink", filename); @@ -604,12 +727,11 @@ remove_sync_file_in_dir (struct GNUNET_FS_Handle *h, const char *ext, return; } filename = get_serialization_file_name_in_dir (h, ext, uni, ent); - if (filename != NULL) - { - if (0 != UNLINK (filename)) - GNUNET_log_strerror_file (GNUNET_ERROR_TYPE_WARNING, "unlink", filename); - GNUNET_free (filename); - } + if (NULL == filename) + return; + if (0 != UNLINK (filename)) + GNUNET_log_strerror_file (GNUNET_ERROR_TYPE_WARNING, "unlink", filename); + GNUNET_free (filename); } @@ -626,12 +748,12 @@ GNUNET_FS_remove_sync_dir_ (struct GNUNET_FS_Handle *h, const char *ext, { char *dn; - if (uni == NULL) + if (NULL == uni) return; dn = get_serialization_file_name_in_dir (h, ext, uni, ""); - if (dn == NULL) + if (NULL == dn) return; - if ((GNUNET_OK == GNUNET_DISK_directory_test (dn)) && + if ((GNUNET_YES == GNUNET_DISK_directory_test (dn, GNUNET_YES)) && (GNUNET_OK != GNUNET_DISK_directory_remove (dn))) GNUNET_log_strerror_file (GNUNET_ERROR_TYPE_WARNING, "rmdir", dn); GNUNET_free (dn); @@ -822,7 +944,7 @@ deserialize_fi_node (struct GNUNET_FS_Handle *h, const char *fn, if ((GNUNET_OK != GNUNET_BIO_read_int64 (rh, &ret->data.file.file_size)) || (GNUNET_OK != GNUNET_BIO_read (rh, "fileid", &ret->data.file.file_id, - sizeof (GNUNET_HashCode)))) + sizeof (struct GNUNET_HashCode)))) { GNUNET_break (0); goto cleanup; @@ -844,7 +966,7 @@ deserialize_fi_node (struct GNUNET_FS_Handle *h, const char *fn, if ((GNUNET_OK != GNUNET_BIO_read_int64 (rh, &ret->data.file.file_size)) || (GNUNET_OK != GNUNET_BIO_read (rh, "fileid", &ret->data.file.file_id, - sizeof (GNUNET_HashCode)))) + sizeof (struct GNUNET_HashCode)))) { GNUNET_break (0); goto cleanup; @@ -870,13 +992,13 @@ deserialize_fi_node (struct GNUNET_FS_Handle *h, const char *fn, goto cleanup; } ret->data.dir.dir_size = (uint32_t) dsize; - if (filename != NULL) + if (NULL != filename) { ret->data.dir.entries = deserialize_file_information (h, filename); GNUNET_free (filename); filename = NULL; nxt = ret->data.dir.entries; - while (nxt != NULL) + while (NULL != nxt) { nxt->dir = ret; nxt = nxt->next; @@ -894,7 +1016,7 @@ deserialize_fi_node (struct GNUNET_FS_Handle *h, const char *fn, GNUNET_break (0); goto cleanup; } - if (filename != NULL) + if (NULL != filename) { ret->next = deserialize_file_information (h, filename); GNUNET_free (filename); @@ -927,9 +1049,10 @@ deserialize_file_information (struct GNUNET_FS_Handle *h, const char *filename) struct GNUNET_FS_FileInformation *ret; struct GNUNET_BIO_ReadHandle *rh; char *emsg; + char *fn; rh = get_read_handle (h, GNUNET_FS_SYNC_PATH_FILE_INFO, filename); - if (rh == NULL) + if (NULL == rh) return NULL; ret = deserialize_fi_node (h, filename, rh); if (GNUNET_OK != GNUNET_BIO_read_close (rh, &emsg)) @@ -939,10 +1062,15 @@ deserialize_file_information (struct GNUNET_FS_Handle *h, const char *filename) filename, emsg); GNUNET_free (emsg); } - if (ret == NULL) + if (NULL == ret) { - if (0 != UNLINK (filename)) - GNUNET_log_strerror_file (GNUNET_ERROR_TYPE_WARNING, "unlink", filename); + fn = get_serialization_file_name (h, GNUNET_FS_SYNC_PATH_FILE_INFO, filename); + if (NULL != fn) + { + if (0 != UNLINK (fn)) + GNUNET_log_strerror_file (GNUNET_ERROR_TYPE_WARNING, "unlink", fn); + GNUNET_free (fn); + } } return ret; } @@ -972,7 +1100,7 @@ get_serialization_short_name (const char *fullname) end = nxt + 1; nxt++; } - if ((end == NULL) || (strlen (end) == 0)) + if ((NULL == end) || (0 == strlen (end))) { GNUNET_break (0); return NULL; @@ -1000,7 +1128,7 @@ make_serialization_file_name (struct GNUNET_FS_Handle *h, const char *ext) if (0 == (h->flags & GNUNET_FS_FLAGS_PERSISTENCE)) return NULL; /* persistence not requested */ dn = get_serialization_file_name (h, ext, ""); - if (dn == NULL) + if (NULL == dn) return NULL; if (GNUNET_OK != GNUNET_DISK_directory_create_for_file (dn)) { @@ -1009,7 +1137,7 @@ make_serialization_file_name (struct GNUNET_FS_Handle *h, const char *ext) } fn = GNUNET_DISK_mktemp (dn); GNUNET_free (dn); - if (fn == NULL) + if (NULL == fn) return NULL; /* epic fail */ ret = get_serialization_short_name (fn); GNUNET_free (fn); @@ -1037,7 +1165,7 @@ make_serialization_file_name_in_dir (struct GNUNET_FS_Handle *h, if (0 == (h->flags & GNUNET_FS_FLAGS_PERSISTENCE)) return NULL; /* persistence not requested */ dn = get_serialization_file_name_in_dir (h, ext, uni, ""); - if (dn == NULL) + if (NULL == dn) return NULL; if (GNUNET_OK != GNUNET_DISK_directory_create_for_file (dn)) { @@ -1046,7 +1174,7 @@ make_serialization_file_name_in_dir (struct GNUNET_FS_Handle *h, } fn = GNUNET_DISK_mktemp (dn); GNUNET_free (dn); - if (fn == NULL) + if (NULL == fn) return NULL; /* epic fail */ ret = get_serialization_short_name (fn); GNUNET_free (fn); @@ -1078,7 +1206,7 @@ copy_from_reader (struct GNUNET_BIO_WriteHandle *wh, left = GNUNET_MIN (sizeof (buf), fi->data.file.file_size - off); ret = fi->data.file.reader (fi->data.file.reader_cls, off, left, buf, &emsg); - if (ret == 0) + if (0 == ret) { GNUNET_free (emsg); return GNUNET_SYSERR; @@ -1113,7 +1241,7 @@ GNUNET_FS_file_information_sync_ (struct GNUNET_FS_FileInformation *fi) return; wh = get_write_handle (fi->h, GNUNET_FS_SYNC_PATH_FILE_INFO, fi->serialization); - if (wh == NULL) + if (NULL == wh) { GNUNET_free (fi->serialization); fi->serialization = NULL; @@ -1129,11 +1257,11 @@ GNUNET_FS_file_information_sync_ (struct GNUNET_FS_FileInformation *fi) b = 1; else b = 0; - if (fi->keywords != NULL) + if (NULL != fi->keywords) ksks = GNUNET_FS_uri_to_string (fi->keywords); else ksks = NULL; - if (fi->chk_uri != NULL) + if (NULL != fi->chk_uri) chks = GNUNET_FS_uri_to_string (fi->chk_uri); else chks = NULL; @@ -1195,7 +1323,7 @@ GNUNET_FS_file_information_sync_ (struct GNUNET_FS_FileInformation *fi) if ((GNUNET_OK != GNUNET_BIO_write_int64 (wh, fi->data.file.file_size)) || (GNUNET_OK != GNUNET_BIO_write (wh, &fi->data.file.file_id, - sizeof (GNUNET_HashCode)))) + sizeof (struct GNUNET_HashCode)))) { GNUNET_break (0); goto cleanup; @@ -1236,7 +1364,7 @@ GNUNET_FS_file_information_sync_ (struct GNUNET_FS_FileInformation *fi) } return; /* done! */ cleanup: - if (wh != NULL) + if (NULL != wh) (void) GNUNET_BIO_write_close (wh); GNUNET_free_non_null (chks); GNUNET_free_non_null (ksks); @@ -1267,16 +1395,13 @@ find_file_position (struct GNUNET_FS_FileInformation *pos, const char *srch) { struct GNUNET_FS_FileInformation *r; - while (pos != NULL) + while (NULL != pos) { if (0 == strcmp (srch, pos->serialization)) return pos; - if (pos->is_directory == GNUNET_YES) - { - r = find_file_position (pos->data.dir.entries, srch); - if (r != NULL) - return r; - } + if ( (GNUNET_YES == pos->is_directory) && + (NULL != (r = find_file_position (pos->data.dir.entries, srch))) ) + return r; pos = pos->next; } return NULL; @@ -1354,7 +1479,7 @@ deserialize_publish_file (void *cls, const char *filename) fi_pos = NULL; ns = NULL; rh = GNUNET_BIO_read_open (filename); - if (rh == NULL) + if (NULL == rh) { GNUNET_break (0); goto cleanup; @@ -1380,15 +1505,15 @@ deserialize_publish_file (void *cls, const char *filename) goto cleanup; } pc->fi = deserialize_file_information (h, fi_root); - if (pc->fi == NULL) + if (NULL == pc->fi) { GNUNET_break (0); goto cleanup; } - if (ns != NULL) + if (NULL != ns) { - pc->namespace = GNUNET_FS_namespace_create (h, ns); - if (pc->namespace == NULL) + pc->ns = GNUNET_FS_namespace_create (h, ns); + if (NULL == pc->ns) { GNUNET_log (GNUNET_ERROR_TYPE_WARNING, _ @@ -1404,16 +1529,16 @@ deserialize_publish_file (void *cls, const char *filename) if (NULL == pc->dsh) goto cleanup; } - if (fi_pos != NULL) + if (NULL != fi_pos) { pc->fi_pos = find_file_position (pc->fi, fi_pos); GNUNET_free (fi_pos); fi_pos = NULL; - if (pc->fi_pos == NULL) + if (NULL == pc->fi_pos) { /* failed to find position for resuming, outch! Will start from root! */ GNUNET_break (0); - if (pc->all_done != GNUNET_YES) + if (GNUNET_YES != pc->all_done) pc->fi_pos = pc->fi; } } @@ -1423,7 +1548,7 @@ deserialize_publish_file (void *cls, const char *filename) GNUNET_FS_file_information_inspect (pc->fi, &fip_signal_resume, pc); /* re-start publishing (if needed)... */ - if (pc->all_done != GNUNET_YES) + if (GNUNET_YES != pc->all_done) { GNUNET_assert (GNUNET_SCHEDULER_NO_TASK == pc->upload_task); pc->upload_task = @@ -1447,14 +1572,14 @@ cleanup: GNUNET_free_non_null (fi_root); GNUNET_free_non_null (fi_pos); GNUNET_free_non_null (ns); - if ((rh != NULL) && (GNUNET_OK != GNUNET_BIO_read_close (rh, &emsg))) + if ((NULL != rh) && (GNUNET_OK != GNUNET_BIO_read_close (rh, &emsg))) { GNUNET_log (GNUNET_ERROR_TYPE_WARNING, _("Failed to resume publishing operation `%s': %s\n"), filename, emsg); GNUNET_free (emsg); } - if (pc->fi != NULL) + if (NULL != pc->fi) GNUNET_FS_file_information_destroy (pc->fi, NULL, NULL); if (0 != UNLINK (filename)) GNUNET_log_strerror_file (GNUNET_ERROR_TYPE_WARNING, "unlink", filename); @@ -1492,7 +1617,7 @@ GNUNET_FS_publish_sync_ (struct GNUNET_FS_PublishContext *pc) } wh = get_write_handle (pc->h, GNUNET_FS_SYNC_PATH_MASTER_PUBLISH, pc->serialization); - if (wh == NULL) + if (NULL == wh) { GNUNET_break (0); goto cleanup; @@ -1504,12 +1629,10 @@ GNUNET_FS_publish_sync_ (struct GNUNET_FS_PublishContext *pc) (GNUNET_OK != GNUNET_BIO_write_string (wh, pc->fi->serialization)) || (GNUNET_OK != GNUNET_BIO_write_string (wh, - (pc->fi_pos == - NULL) ? NULL : pc->fi_pos->serialization)) || + (NULL == pc->fi_pos) ? NULL : pc->fi_pos->serialization)) || (GNUNET_OK != GNUNET_BIO_write_string (wh, - (pc->namespace == - NULL) ? NULL : pc->namespace->name))) + (NULL == pc->ns) ? NULL : pc->ns->name))) { GNUNET_break (0); goto cleanup; @@ -1522,7 +1645,7 @@ GNUNET_FS_publish_sync_ (struct GNUNET_FS_PublishContext *pc) } return; cleanup: - if (wh != NULL) + if (NULL != wh) (void) GNUNET_BIO_write_close (wh); GNUNET_FS_remove_sync_file_ (pc->h, GNUNET_FS_SYNC_PATH_MASTER_PUBLISH, pc->serialization); @@ -1553,7 +1676,7 @@ GNUNET_FS_unindex_sync_ (struct GNUNET_FS_UnindexContext *uc) return; wh = get_write_handle (uc->h, GNUNET_FS_SYNC_PATH_MASTER_UNINDEX, uc->serialization); - if (wh == NULL) + if (NULL == wh) { GNUNET_break (0); goto cleanup; @@ -1572,7 +1695,7 @@ GNUNET_FS_unindex_sync_ (struct GNUNET_FS_UnindexContext *uc) (GNUNET_OK != GNUNET_BIO_write_int32 (wh, (uint32_t) uc->ksk_offset)) || ((uc->state == UNINDEX_STATE_FS_NOTIFY) && (GNUNET_OK != - GNUNET_BIO_write (wh, &uc->file_id, sizeof (GNUNET_HashCode)))) || + GNUNET_BIO_write (wh, &uc->file_id, sizeof (struct GNUNET_HashCode)))) || ((uc->state == UNINDEX_STATE_ERROR) && (GNUNET_OK != GNUNET_BIO_write_string (wh, uc->emsg)))) { @@ -1587,7 +1710,7 @@ GNUNET_FS_unindex_sync_ (struct GNUNET_FS_UnindexContext *uc) } return; cleanup: - if (wh != NULL) + if (NULL != wh) (void) GNUNET_BIO_write_close (wh); GNUNET_FS_remove_sync_file_ (uc->h, GNUNET_FS_SYNC_PATH_MASTER_UNINDEX, uc->serialization); @@ -1614,7 +1737,7 @@ write_download_request (struct GNUNET_BIO_WriteHandle *wh, (GNUNET_OK != GNUNET_BIO_write_int32 (wh, dr->num_children)) || (GNUNET_OK != GNUNET_BIO_write_int32 (wh, dr->depth))) return GNUNET_NO; - if ((dr->state == BRS_CHK_SET) && + if ((BRS_CHK_SET == dr->state) && (GNUNET_OK != GNUNET_BIO_write (wh, &dr->chk, sizeof (struct ContentHashKey)))) return GNUNET_NO; @@ -1638,16 +1761,15 @@ read_download_request (struct GNUNET_BIO_ReadHandle *rh) unsigned int i; dr = GNUNET_malloc (sizeof (struct DownloadRequest)); - if ((GNUNET_OK != GNUNET_BIO_read_int32 (rh, &dr->state)) || (GNUNET_OK != GNUNET_BIO_read_int64 (rh, &dr->offset)) || (GNUNET_OK != GNUNET_BIO_read_int32 (rh, &dr->num_children)) || (dr->num_children > CHK_PER_INODE) || - (GNUNET_OK != GNUNET_BIO_read_int32 (rh, &dr->depth)) || ((dr->depth == 0) + (GNUNET_OK != GNUNET_BIO_read_int32 (rh, &dr->depth)) || ((0 == dr->depth) && (dr->num_children > 0)) || - ((dr->depth > 0) && (dr->num_children == 0))) + ((dr->depth > 0) && (0 == dr->num_children))) { GNUNET_break (0); dr->num_children = 0; @@ -1655,7 +1777,7 @@ read_download_request (struct GNUNET_BIO_ReadHandle *rh) } if (dr->num_children > 0) dr->children = - GNUNET_malloc (dr->num_children * sizeof (struct ContentHashKey)); + GNUNET_malloc (dr->num_children * sizeof (struct DownloadRequest *)); switch (dr->state) { case BRS_INIT: @@ -1711,10 +1833,10 @@ get_download_sync_filename (struct GNUNET_FS_DownloadContext *dc, GNUNET_FS_SYNC_PATH_CHILD_DOWNLOAD : GNUNET_FS_SYNC_PATH_MASTER_DOWNLOAD, uni); - if (dc->parent->serialization == NULL) + if (NULL == dc->parent->serialization) return NULL; par = get_download_sync_filename (dc->parent, dc->parent->serialization, ""); - if (par == NULL) + if (NULL == par) return NULL; GNUNET_asprintf (&epar, "%s.dir%s%s%s", par, DIR_SEPARATOR_STR, uni, ext); GNUNET_free (par); @@ -1743,7 +1865,7 @@ GNUNET_FS_download_sync_ (struct GNUNET_FS_DownloadContext *dc) if (NULL == dc->serialization) { dir = get_download_sync_filename (dc, "", ""); - if (dir == NULL) + if (NULL == dir) return; if (GNUNET_OK != GNUNET_DISK_directory_create_for_file (dir)) { @@ -1752,14 +1874,14 @@ GNUNET_FS_download_sync_ (struct GNUNET_FS_DownloadContext *dc) } fn = GNUNET_DISK_mktemp (dir); GNUNET_free (dir); - if (fn == NULL) + if (NULL == fn) return; dc->serialization = get_serialization_short_name (fn); } else { fn = get_download_sync_filename (dc, dc->serialization, ""); - if (fn == NULL) + if (NULL == fn) { GNUNET_free (dc->serialization); dc->serialization = NULL; @@ -1768,7 +1890,7 @@ GNUNET_FS_download_sync_ (struct GNUNET_FS_DownloadContext *dc) } } wh = GNUNET_BIO_write_open (fn); - if (wh == NULL) + if (NULL == wh) { GNUNET_free (dc->serialization); dc->serialization = NULL; @@ -1856,7 +1978,7 @@ GNUNET_FS_search_result_sync_ (struct GNUNET_FS_SearchResult *sr) NULL) ? GNUNET_FS_SYNC_PATH_MASTER_SEARCH : GNUNET_FS_SYNC_PATH_CHILD_SEARCH, sr->sc->serialization, sr->serialization); - if (wh == NULL) + if (NULL == wh) { GNUNET_break (0); goto cleanup; @@ -1872,7 +1994,7 @@ GNUNET_FS_search_result_sync_ (struct GNUNET_FS_SearchResult *sr) sr->update_search != NULL ? sr->update_search->serialization : NULL)) || (GNUNET_OK != GNUNET_BIO_write_meta_data (wh, sr->meta)) || - (GNUNET_OK != GNUNET_BIO_write (wh, &sr->key, sizeof (GNUNET_HashCode))) + (GNUNET_OK != GNUNET_BIO_write (wh, &sr->key, sizeof (struct GNUNET_HashCode))) || (GNUNET_OK != GNUNET_BIO_write_int32 (wh, sr->mandatory_missing)) || (GNUNET_OK != GNUNET_BIO_write_int32 (wh, sr->optional_support)) || (GNUNET_OK != GNUNET_BIO_write_int32 (wh, sr->availability_success)) || @@ -1881,8 +2003,8 @@ GNUNET_FS_search_result_sync_ (struct GNUNET_FS_SearchResult *sr) GNUNET_break (0); goto cleanup; } - if ( (sr->uri != NULL) && - (sr->sc->uri->type == ksk) && + if ( (NULL != sr->uri) && + (ksk == sr->sc->uri->type) && (GNUNET_OK != GNUNET_BIO_write (wh, sr->keyword_bitmap, (sr->sc->uri->data.ksk.keywordCount + 7) / 8)) ) { @@ -1899,12 +2021,12 @@ GNUNET_FS_search_result_sync_ (struct GNUNET_FS_SearchResult *sr) return; cleanup: GNUNET_free_non_null (uris); - if (wh != NULL) + if (NULL != wh) (void) GNUNET_BIO_write_close (wh); remove_sync_file_in_dir (sr->sc->h, - (sr->sc->psearch_result == - NULL) ? GNUNET_FS_SYNC_PATH_MASTER_SEARCH : - GNUNET_FS_SYNC_PATH_CHILD_SEARCH, + (NULL == sr->sc->psearch_result) + ? GNUNET_FS_SYNC_PATH_MASTER_SEARCH + : GNUNET_FS_SYNC_PATH_CHILD_SEARCH, sr->sc->serialization, sr->serialization); GNUNET_free (sr->serialization); sr->serialization = NULL; @@ -1928,16 +2050,16 @@ GNUNET_FS_search_sync_ (struct GNUNET_FS_SearchContext *sc) const char *category; category = - (sc->psearch_result == - NULL) ? GNUNET_FS_SYNC_PATH_MASTER_SEARCH : - GNUNET_FS_SYNC_PATH_CHILD_SEARCH; + (NULL == sc->psearch_result) + ? GNUNET_FS_SYNC_PATH_MASTER_SEARCH + : GNUNET_FS_SYNC_PATH_CHILD_SEARCH; if (NULL == sc->serialization) sc->serialization = make_serialization_file_name (sc->h, category); if (NULL == sc->serialization) return; uris = NULL; wh = get_write_handle (sc->h, category, sc->serialization); - if (wh == NULL) + if (NULL == wh) { GNUNET_break (0); goto cleanup; @@ -1966,7 +2088,7 @@ GNUNET_FS_search_sync_ (struct GNUNET_FS_SearchContext *sc) } return; cleanup: - if (wh != NULL) + if (NULL != wh) (void) GNUNET_BIO_write_close (wh); GNUNET_free_non_null (uris); GNUNET_FS_remove_sync_file_ (sc->h, category, sc->serialization); @@ -1998,7 +2120,7 @@ deserialize_unindex_file (void *cls, const char *filename) uc->h = h; uc->serialization = get_serialization_short_name (filename); rh = GNUNET_BIO_read_open (filename); - if (rh == NULL) + if (NULL == rh) { GNUNET_break (0); goto cleanup; @@ -2024,6 +2146,7 @@ deserialize_unindex_file (void *cls, const char *filename) if (NULL == uc->ksk_uri) { GNUNET_break (0); + GNUNET_free_non_null (emsg); goto cleanup; } } @@ -2042,7 +2165,7 @@ deserialize_unindex_file (void *cls, const char *filename) case UNINDEX_STATE_FS_NOTIFY: if (GNUNET_OK != GNUNET_BIO_read (rh, "unindex-hash", &uc->file_id, - sizeof (GNUNET_HashCode))) + sizeof (struct GNUNET_HashCode))) { GNUNET_break (0); goto cleanup; @@ -2110,14 +2233,14 @@ deserialize_unindex_file (void *cls, const char *filename) return GNUNET_OK; cleanup: GNUNET_free_non_null (uc->filename); - if ((rh != NULL) && (GNUNET_OK != GNUNET_BIO_read_close (rh, &emsg))) + if ((NULL != rh) && (GNUNET_OK != GNUNET_BIO_read_close (rh, &emsg))) { GNUNET_log (GNUNET_ERROR_TYPE_WARNING, _("Failed to resume unindexing operation `%s': %s\n"), filename, emsg); GNUNET_free (emsg); } - if (uc->serialization != NULL) + if (NULL != uc->serialization) GNUNET_FS_remove_sync_file_ (h, GNUNET_FS_SYNC_PATH_MASTER_UNINDEX, uc->serialization); GNUNET_free_non_null (uc->serialization); @@ -2181,14 +2304,14 @@ deserialize_search_result (void *cls, const char *filename) ser = get_serialization_short_name (filename); rh = GNUNET_BIO_read_open (filename); - if (rh == NULL) + if (NULL == rh) { - if (ser != NULL) + if (NULL != ser) { remove_sync_file_in_dir (sc->h, - (sc->psearch_result == - NULL) ? GNUNET_FS_SYNC_PATH_MASTER_SEARCH : - GNUNET_FS_SYNC_PATH_CHILD_SEARCH, + (NULL == sc->psearch_result) + ? GNUNET_FS_SYNC_PATH_MASTER_SEARCH + : GNUNET_FS_SYNC_PATH_CHILD_SEARCH, sc->serialization, ser); GNUNET_free (ser); } @@ -2208,7 +2331,7 @@ deserialize_search_result (void *cls, const char *filename) GNUNET_BIO_read_string (rh, "search-lnk", &update_srch, 16)) || (GNUNET_OK != GNUNET_BIO_read_meta_data (rh, "result-meta", &sr->meta)) || (GNUNET_OK != - GNUNET_BIO_read (rh, "result-key", &sr->key, sizeof (GNUNET_HashCode))) + GNUNET_BIO_read (rh, "result-key", &sr->key, sizeof (struct GNUNET_HashCode))) || (GNUNET_OK != GNUNET_BIO_read_int32 (rh, &sr->mandatory_missing)) || (GNUNET_OK != GNUNET_BIO_read_int32 (rh, &sr->optional_support)) || (GNUNET_OK != GNUNET_BIO_read_int32 (rh, &sr->availability_success)) || @@ -2217,7 +2340,7 @@ deserialize_search_result (void *cls, const char *filename) GNUNET_break (0); goto cleanup; } - if (sr->sc->uri->type == ksk) + if (ksk == sr->sc->uri->type) { sr->keyword_bitmap = GNUNET_malloc ((sr->sc->uri->data.ksk.keywordCount + 7) / 8); /* round up, count bits */ if (GNUNET_OK != GNUNET_BIO_read (rh, "keyword-bitmap", @@ -2229,10 +2352,10 @@ deserialize_search_result (void *cls, const char *filename) } } GNUNET_free (uris); - if (download != NULL) + if (NULL != download) { drh = get_read_handle (sc->h, GNUNET_FS_SYNC_PATH_CHILD_DOWNLOAD, download); - if (drh != NULL) + if (NULL != drh) { deserialize_download (sc->h, drh, NULL, sr, download); if (GNUNET_OK != GNUNET_BIO_read_close (drh, &emsg)) @@ -2245,11 +2368,11 @@ deserialize_search_result (void *cls, const char *filename) } GNUNET_free (download); } - if (update_srch != NULL) + if (NULL != update_srch) { drh = get_read_handle (sc->h, GNUNET_FS_SYNC_PATH_CHILD_SEARCH, update_srch); - if (drh != NULL) + if (NULL != drh) { deserialize_search (sc->h, drh, sr, update_srch); if (GNUNET_OK != GNUNET_BIO_read_close (drh, &emsg)) @@ -2262,8 +2385,9 @@ deserialize_search_result (void *cls, const char *filename) } GNUNET_free (update_srch); } - GNUNET_CONTAINER_multihashmap_put (sc->master_result_map, &sr->key, sr, - GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE); + GNUNET_break (GNUNET_YES == + GNUNET_CONTAINER_multihashmap_put (sc->master_result_map, &sr->key, sr, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE)); if (GNUNET_OK != GNUNET_BIO_read_close (rh, &emsg)) { GNUNET_log (GNUNET_ERROR_TYPE_WARNING, @@ -2277,9 +2401,9 @@ cleanup: GNUNET_free_non_null (emsg); GNUNET_free_non_null (uris); GNUNET_free_non_null (update_srch); - if (sr->uri != NULL) + if (NULL != sr->uri) GNUNET_FS_uri_destroy (sr->uri); - if (sr->meta != NULL) + if (NULL != sr->meta) GNUNET_CONTAINER_meta_data_destroy (sr->meta); GNUNET_free (sr->serialization); GNUNET_free (sr); @@ -2318,7 +2442,7 @@ signal_download_resume (struct GNUNET_FS_DownloadContext *dc) signal_download_resume (dcc); dcc = dcc->next; } - if (dc->pending_head != NULL) + if (NULL != dc->pending_head) GNUNET_FS_download_start_downloading_ (dc); } @@ -2343,7 +2467,7 @@ signal_search_resume (struct GNUNET_FS_SearchContext *sc); * @return GNUNET_YES (we should continue to iterate) */ static int -signal_result_resume (void *cls, const GNUNET_HashCode * key, void *value) +signal_result_resume (void *cls, const struct GNUNET_HashCode * key, void *value) { struct GNUNET_FS_SearchContext *sc = cls; struct GNUNET_FS_ProgressInfo pi; @@ -2363,7 +2487,7 @@ signal_result_resume (void *cls, const GNUNET_HashCode * key, void *value) sr->optional_support; sr->client_info = GNUNET_FS_search_make_status_ (&pi, sc); } - if (sr->download != NULL) + if (NULL != sr->download) { signal_download_resume (sr->download); } @@ -2371,7 +2495,7 @@ signal_result_resume (void *cls, const GNUNET_HashCode * key, void *value) { GNUNET_FS_search_start_probe_ (sr); } - if (sr->update_search != NULL) + if (NULL != sr->update_search) signal_search_resume (sr->update_search); return GNUNET_YES; } @@ -2395,11 +2519,11 @@ free_search_context (struct GNUNET_FS_SearchContext *sc); * @return GNUNET_YES (we should continue to iterate) */ static int -free_result (void *cls, const GNUNET_HashCode * key, void *value) +free_result (void *cls, const struct GNUNET_HashCode * key, void *value) { struct GNUNET_FS_SearchResult *sr = value; - if (sr->update_search != NULL) + if (NULL != sr->update_search) { free_search_context (sr->update_search); GNUNET_assert (NULL == sr->update_search); @@ -2419,7 +2543,7 @@ free_result (void *cls, const GNUNET_HashCode * key, void *value) static void free_search_context (struct GNUNET_FS_SearchContext *sc) { - if (sc->serialization != NULL) + if (NULL != sc->serialization) { GNUNET_FS_remove_sync_file_ (sc->h, (sc->psearch_result == @@ -2434,9 +2558,9 @@ free_search_context (struct GNUNET_FS_SearchContext *sc) } GNUNET_free_non_null (sc->serialization); GNUNET_free_non_null (sc->emsg); - if (sc->uri != NULL) + if (NULL != sc->uri) GNUNET_FS_uri_destroy (sc->uri); - if (sc->master_result_map != NULL) + if (NULL != sc->master_result_map) { GNUNET_CONTAINER_multihashmap_iterate (sc->master_result_map, &free_result, sc); @@ -2464,7 +2588,7 @@ deserialize_subdownload (void *cls, const char *filename) ser = get_serialization_short_name (filename); rh = GNUNET_BIO_read_open (filename); - if (rh == NULL) + if (NULL == rh) { GNUNET_log (GNUNET_ERROR_TYPE_WARNING, _ @@ -2497,9 +2621,9 @@ free_download_context (struct GNUNET_FS_DownloadContext *dc) { struct GNUNET_FS_DownloadContext *dcc; - if (dc->meta != NULL) + if (NULL != dc->meta) GNUNET_CONTAINER_meta_data_destroy (dc->meta); - if (dc->uri != NULL) + if (NULL != dc->uri) GNUNET_FS_uri_destroy (dc->uri); GNUNET_free_non_null (dc->temp_filename); GNUNET_free_non_null (dc->emsg); @@ -2573,40 +2697,40 @@ deserialize_download (struct GNUNET_FS_Handle *h, } dc->options = (enum GNUNET_FS_DownloadOptions) options; dc->active = - GNUNET_CONTAINER_multihashmap_create (1 + 2 * (dc->length / DBLOCK_SIZE)); + GNUNET_CONTAINER_multihashmap_create (1 + 2 * (dc->length / DBLOCK_SIZE), GNUNET_NO); dc->has_finished = (int) status; dc->treedepth = GNUNET_FS_compute_depth (GNUNET_FS_uri_chk_get_file_size (dc->uri)); if (GNUNET_FS_uri_test_loc (dc->uri)) GNUNET_assert (GNUNET_OK == GNUNET_FS_uri_loc_get_peer_identity (dc->uri, &dc->target)); - if (dc->emsg == NULL) + if (NULL == dc->emsg) { dc->top_request = read_download_request (rh); - if (dc->top_request == NULL) + if (NULL == dc->top_request) { GNUNET_break (0); goto cleanup; } } dn = get_download_sync_filename (dc, dc->serialization, ".dir"); - if (dn != NULL) + if (NULL != dn) { - if (GNUNET_YES == GNUNET_DISK_directory_test (dn)) + if (GNUNET_YES == GNUNET_DISK_directory_test (dn, GNUNET_YES)) GNUNET_DISK_directory_scan (dn, &deserialize_subdownload, dc); GNUNET_free (dn); } - if (parent != NULL) + if (NULL != parent) { GNUNET_abort (); // for debugging for now - FIXME GNUNET_CONTAINER_DLL_insert (parent->child_head, parent->child_tail, dc); } - if (search != NULL) + if (NULL != search) { dc->search = search; search->download = dc; } - if ((parent == NULL) && (search == NULL)) + if ((NULL == parent) && (NULL == search)) { dc->top = GNUNET_FS_make_top (dc->h, &GNUNET_FS_download_signal_suspend_, dc); @@ -2636,7 +2760,7 @@ signal_search_resume (struct GNUNET_FS_SearchContext *sc) pi.status = GNUNET_FS_STATUS_SEARCH_RESUME; pi.value.search.specifics.resume.message = sc->emsg; pi.value.search.specifics.resume.is_paused = - (sc->client == NULL) ? GNUNET_YES : GNUNET_NO; + (NULL == sc->client) ? GNUNET_YES : GNUNET_NO; sc->client_info = GNUNET_FS_search_make_status_ (&pi, sc); GNUNET_CONTAINER_multihashmap_iterate (sc->master_result_map, &signal_result_resume, sc); @@ -2665,7 +2789,7 @@ deserialize_search (struct GNUNET_FS_Handle *h, uint32_t options; char in_pause; - if ((psearch_result != NULL) && (psearch_result->update_search != NULL)) + if ((NULL != psearch_result) && (NULL != psearch_result->update_search)) { GNUNET_break (0); return NULL; @@ -2673,7 +2797,7 @@ deserialize_search (struct GNUNET_FS_Handle *h, uris = NULL; emsg = NULL; sc = GNUNET_malloc (sizeof (struct GNUNET_FS_SearchContext)); - if (psearch_result != NULL) + if (NULL != psearch_result) { sc->psearch_result = psearch_result; psearch_result->update_search = sc; @@ -2696,16 +2820,16 @@ deserialize_search (struct GNUNET_FS_Handle *h, goto cleanup; } sc->options = (enum GNUNET_FS_SearchOptions) options; - sc->master_result_map = GNUNET_CONTAINER_multihashmap_create (16); + sc->master_result_map = GNUNET_CONTAINER_multihashmap_create (16, GNUNET_NO); dn = get_serialization_file_name_in_dir (h, (sc->psearch_result == NULL) ? GNUNET_FS_SYNC_PATH_MASTER_SEARCH : GNUNET_FS_SYNC_PATH_CHILD_SEARCH, sc->serialization, ""); - if (dn != NULL) + if (NULL != dn) { - if (GNUNET_YES == GNUNET_DISK_directory_test (dn)) + if (GNUNET_YES == GNUNET_DISK_directory_test (dn, GNUNET_YES)) GNUNET_DISK_directory_scan (dn, &deserialize_search_result, sc); GNUNET_free (dn); } @@ -2754,9 +2878,9 @@ deserialize_search_file (void *cls, const char *filename) return GNUNET_OK; /* skip directories */ ser = get_serialization_short_name (filename); rh = GNUNET_BIO_read_open (filename); - if (rh == NULL) + if (NULL == rh) { - if (ser != NULL) + if (NULL != ser) { GNUNET_FS_remove_sync_file_ (h, GNUNET_FS_SYNC_PATH_MASTER_SEARCH, ser); GNUNET_free (ser); @@ -2764,7 +2888,7 @@ deserialize_search_file (void *cls, const char *filename) return GNUNET_OK; } sc = deserialize_search (h, rh, NULL, ser); - if (sc != NULL) + if (NULL != sc) sc->top = GNUNET_FS_make_top (h, &GNUNET_FS_search_signal_suspend_, sc); GNUNET_free (ser); if (GNUNET_OK != GNUNET_BIO_read_close (rh, &emsg)) @@ -2796,7 +2920,7 @@ deserialize_download_file (void *cls, const char *filename) ser = get_serialization_short_name (filename); rh = GNUNET_BIO_read_open (filename); - if (rh == NULL) + if (NULL == rh) { if (0 != UNLINK (filename)) GNUNET_log_strerror_file (GNUNET_ERROR_TYPE_WARNING, "unlink", filename); @@ -2830,9 +2954,9 @@ deserialization_master (const char *master_path, GNUNET_FileNameCallback proc, char *dn; dn = get_serialization_file_name (h, master_path, ""); - if (dn == NULL) + if (NULL == dn) return; - if (GNUNET_YES == GNUNET_DISK_directory_test (dn)) + if (GNUNET_YES == GNUNET_DISK_directory_test (dn, GNUNET_YES)) GNUNET_DISK_directory_scan (dn, proc, h); GNUNET_free (dn); } diff --git a/src/fs/fs_api.h b/src/fs/fs_api.h index e75b75f..12d4ae4 100644 --- a/src/fs/fs_api.h +++ b/src/fs/fs_api.h @@ -205,7 +205,7 @@ struct GNUNET_FS_Uri /** * Hash of the public key for the namespace. */ - GNUNET_HashCode namespace; + struct GNUNET_HashCode ns; /** * Human-readable identifier chosen for this @@ -333,7 +333,7 @@ struct GNUNET_FS_FileInformation * over the entire file (when the indexing process is started). * Otherwise this field is not used. */ - GNUNET_HashCode file_id; + struct GNUNET_HashCode file_id; /** * Size of the file (in bytes). @@ -568,7 +568,7 @@ struct GNUNET_FS_SearchResult /** * Key for the search result */ - GNUNET_HashCode key; + struct GNUNET_HashCode key; /** * ID of the task that will clean up the probe_ctx should it not @@ -577,6 +577,12 @@ struct GNUNET_FS_SearchResult */ GNUNET_SCHEDULER_TaskIdentifier probe_cancel_task; + /** + * Task we use to report periodically to the application that the + * probe is still running. + */ + GNUNET_SCHEDULER_TaskIdentifier probe_ping_task; + /** * When did the current probe become active? */ @@ -633,10 +639,11 @@ GNUNET_FS_queue_ (struct GNUNET_FS_Handle *h, GNUNET_FS_QueueStart start, /** * Dequeue a job from the queue. - * @param qh handle for the job + * + * @param qe handle for the job */ void -GNUNET_FS_dequeue_ (struct GNUNET_FS_QueueEntry *qh); +GNUNET_FS_dequeue_ (struct GNUNET_FS_QueueEntry *qe); /** @@ -730,7 +737,7 @@ GNUNET_FS_publish_main_ (void *cls, * @param file_id computed hash, NULL on error */ void -GNUNET_FS_unindex_process_hash_ (void *cls, const GNUNET_HashCode * file_id); +GNUNET_FS_unindex_process_hash_ (void *cls, const struct GNUNET_HashCode * file_id); /** @@ -1159,7 +1166,7 @@ struct GNUNET_FS_PublishContext /** * Namespace that we are publishing in, NULL if we have no namespace. */ - struct GNUNET_FS_Namespace *namespace; + struct GNUNET_FS_Namespace *ns; /** * ID of the content in the namespace, NULL if we have no namespace. @@ -1384,12 +1391,12 @@ struct GNUNET_FS_UnindexContext /** * Current key for decrypting KBLocks from 'get_key' operation. */ - GNUNET_HashCode key; + struct GNUNET_HashCode key; /** * Current query of 'get_key' operation. */ - GNUNET_HashCode query; + struct GNUNET_HashCode query; /** * First content UID, 0 for none. @@ -1424,7 +1431,7 @@ struct GNUNET_FS_UnindexContext /** * Hash of the file's contents (once computed). */ - GNUNET_HashCode file_id; + struct GNUNET_HashCode file_id; /** * Current operatinonal phase. @@ -1444,12 +1451,12 @@ struct SearchRequestEntry * Hash of the original keyword, also known as the * key (for decrypting the KBlock). */ - GNUNET_HashCode key; + struct GNUNET_HashCode key; /** * Hash of the public key, also known as the query. */ - GNUNET_HashCode query; + struct GNUNET_HashCode query; /** * Map that contains a "struct GNUNET_FS_SearchResult" for each result that @@ -1535,6 +1542,11 @@ struct GNUNET_FS_SearchContext */ struct GNUNET_TIME_Absolute start_time; + /** + * How long to wait before we try to reconnect to FS service? + */ + struct GNUNET_TIME_Relative reconnect_backoff; + /** * ID of a task that is using this struct and that must be cancelled * when the search is being stopped (if not @@ -1899,6 +1911,11 @@ struct GNUNET_FS_DownloadContext */ struct GNUNET_TIME_Absolute start_time; + /** + * How long to wait before we try to reconnect to FS service? + */ + struct GNUNET_TIME_Relative reconnect_backoff; + /** * Desired level of anonymity. */ diff --git a/src/fs/fs_dirmetascan.c b/src/fs/fs_dirmetascan.c index 6dac690..e5a575a 100644 --- a/src/fs/fs_dirmetascan.c +++ b/src/fs/fs_dirmetascan.c @@ -232,8 +232,11 @@ finish_scan (void *cls, struct GNUNET_FS_DirScanner *ds = cls; ds->stop_task = GNUNET_SCHEDULER_NO_TASK; - GNUNET_HELPER_stop (ds->helper); - ds->helper = NULL; + if (NULL != ds->helper) + { + GNUNET_HELPER_stop (ds->helper); + ds->helper = NULL; + } ds->progress_callback (ds->progress_callback_cls, NULL, GNUNET_SYSERR, GNUNET_FS_DIRSCANNER_FINISHED); @@ -414,6 +417,25 @@ process_helper_msgs (void *cls, } +/** + * Function called if our helper process died. + * + * @param cls the 'struct GNUNET_FS_DirScanner' callback. + */ +static void +helper_died_cb (void *cls) +{ + struct GNUNET_FS_DirScanner *ds = cls; + + ds->helper = NULL; + if (GNUNET_SCHEDULER_NO_TASK != ds->stop_task) + return; /* normal death, was finished */ + ds->progress_callback (ds->progress_callback_cls, + NULL, GNUNET_SYSERR, + GNUNET_FS_DIRSCANNER_INTERNAL_ERROR); +} + + /** * Start a directory scanner thread. * @@ -454,12 +476,13 @@ GNUNET_FS_directory_scan_start (const char *filename, ds->args[1] = ds->filename_expanded; ds->args[2] = ds->ex_arg; ds->args[3] = NULL; - ds->helper = GNUNET_HELPER_start ("gnunet-helper-fs-publish", + ds->helper = GNUNET_HELPER_start (GNUNET_NO, + "gnunet-helper-fs-publish", ds->args, &process_helper_msgs, - ds); + &helper_died_cb, ds); if (NULL == ds->helper) - { + { GNUNET_free (filename_expanded); GNUNET_free (ds); return NULL; diff --git a/src/fs/fs_download.c b/src/fs/fs_download.c index 7c4dccb..82fc391 100644 --- a/src/fs/fs_download.c +++ b/src/fs/fs_download.c @@ -153,7 +153,7 @@ struct ProcessResultClosure /** * Hash of data. */ - GNUNET_HashCode query; + struct GNUNET_HashCode query; /** * Data found in P2P network. @@ -165,6 +165,11 @@ struct ProcessResultClosure */ struct GNUNET_FS_DownloadContext *dc; + /** + * When did we last transmit the request? + */ + struct GNUNET_TIME_Absolute last_transmission; + /** * Number of bytes in data. */ @@ -181,9 +186,14 @@ struct ProcessResultClosure int do_store; /** - * When did we last transmit the request? + * how much respect did we offer to get this reply? */ - struct GNUNET_TIME_Absolute last_transmission; + uint32_t respect_offered; + + /** + * how often did we transmit the query? + */ + uint32_t num_transmissions; }; @@ -198,7 +208,7 @@ struct ProcessResultClosure * @return GNUNET_YES (we should continue to iterate); unless serious error */ static int -process_result_with_request (void *cls, const GNUNET_HashCode * key, +process_result_with_request (void *cls, const struct GNUNET_HashCode * key, void *value); @@ -225,7 +235,7 @@ encrypt_existing_match (struct GNUNET_FS_DownloadContext *dc, char enc[len]; struct GNUNET_CRYPTO_AesSessionKey sk; struct GNUNET_CRYPTO_AesInitializationVector iv; - GNUNET_HashCode query; + struct GNUNET_HashCode query; GNUNET_CRYPTO_hash_to_aes_key (&chk->key, &sk, &iv); if (-1 == GNUNET_CRYPTO_aes_encrypt (block, len, &sk, &iv, enc)) @@ -234,7 +244,7 @@ encrypt_existing_match (struct GNUNET_FS_DownloadContext *dc, return GNUNET_SYSERR; } GNUNET_CRYPTO_hash (enc, len, &query); - if (0 != memcmp (&query, &chk->query, sizeof (GNUNET_HashCode))) + if (0 != memcmp (&query, &chk->query, sizeof (struct GNUNET_HashCode))) { GNUNET_break_op (0); return GNUNET_SYSERR; @@ -525,7 +535,7 @@ try_match_block (struct GNUNET_FS_DownloadContext *dc, pi.value.download.specifics.progress.offset = 0; pi.value.download.specifics.progress.data_len = dlen; pi.value.download.specifics.progress.depth = 0; - pi.value.download.specifics.progress.trust_offered = 0; + pi.value.download.specifics.progress.respect_offered = 0; pi.value.download.specifics.progress.block_download_duration = GNUNET_TIME_UNIT_ZERO; GNUNET_FS_download_make_status_ (&pi, dc); if ((NULL != dc->filename) && @@ -624,7 +634,7 @@ try_top_down_reconstruction (struct GNUNET_FS_DownloadContext *dc, { uint64_t off; char block[DBLOCK_SIZE]; - GNUNET_HashCode key; + struct GNUNET_HashCode key; uint64_t total; size_t len; unsigned int i; @@ -653,7 +663,7 @@ try_top_down_reconstruction (struct GNUNET_FS_DownloadContext *dc, return; /* failure */ } GNUNET_CRYPTO_hash (block, len, &key); - if (0 != memcmp (&key, &dr->chk.key, sizeof (GNUNET_HashCode))) + if (0 != memcmp (&key, &dr->chk.key, sizeof (struct GNUNET_HashCode))) return; /* mismatch */ if (GNUNET_OK != encrypt_existing_match (dc, &dr->chk, dr, block, len, GNUNET_NO)) @@ -926,7 +936,7 @@ GNUNET_FS_free_download_request_ (struct DownloadRequest *dr) * @return GNUNET_YES (we should continue to iterate); unless serious error */ static int -process_result_with_request (void *cls, const GNUNET_HashCode * key, +process_result_with_request (void *cls, const struct GNUNET_HashCode * key, void *value) { struct ProcessResultClosure *prc = cls; @@ -1069,7 +1079,8 @@ process_result_with_request (void *cls, const GNUNET_HashCode * key, pi.value.download.specifics.progress.offset = dr->offset; pi.value.download.specifics.progress.data_len = prc->size; pi.value.download.specifics.progress.depth = dr->depth; - pi.value.download.specifics.progress.trust_offered = 0; + pi.value.download.specifics.progress.respect_offered = prc->respect_offered; + pi.value.download.specifics.progress.num_transmissions = prc->num_transmissions; if (prc->last_transmission.abs_value != GNUNET_TIME_UNIT_FOREVER_ABS.abs_value) pi.value.download.specifics.progress.block_download_duration = GNUNET_TIME_absolute_get_duration (prc->last_transmission); @@ -1121,7 +1132,7 @@ process_result_with_request (void *cls, const GNUNET_HashCode * key, { /* 'chkarr' does not have enough space for this chk_idx; internal error! */ - GNUNET_break (0); + GNUNET_break (0); GNUNET_assert (0); dc->emsg = GNUNET_strdup (_("internal error decoding tree")); goto signal_error; } @@ -1178,6 +1189,11 @@ signal_error: dc->top_request = NULL; GNUNET_CONTAINER_multihashmap_destroy (dc->active); dc->active = NULL; + if (NULL != dc->job_queue) + { + GNUNET_FS_dequeue_ (dc->job_queue); + dc->job_queue = NULL; + } dc->pending_head = NULL; dc->pending_tail = NULL; GNUNET_FS_download_sync_ (dc); @@ -1190,6 +1206,8 @@ signal_error: * * @param dc our download context * @param type type of the result + * @param respect_offered how much respect did we offer to get this reply? + * @param num_transmissions how often did we transmit the query? * @param last_transmission when was this block requested the last time? (FOREVER if unknown/not applicable) * @param data the (encrypted) response * @param size size of data @@ -1197,6 +1215,8 @@ signal_error: static void process_result (struct GNUNET_FS_DownloadContext *dc, enum GNUNET_BLOCK_Type type, + uint32_t respect_offered, + uint32_t num_transmissions, struct GNUNET_TIME_Absolute last_transmission, const void *data, size_t size) { @@ -1204,10 +1224,12 @@ process_result (struct GNUNET_FS_DownloadContext *dc, prc.dc = dc; prc.data = data; + prc.last_transmission = last_transmission; prc.size = size; prc.type = type; prc.do_store = GNUNET_YES; - prc.last_transmission = last_transmission; + prc.respect_offered = respect_offered; + prc.num_transmissions = num_transmissions; GNUNET_CRYPTO_hash (data, size, &prc.query); GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received result for query `%s' from `%s'-service\n", @@ -1242,6 +1264,8 @@ receive_results (void *cls, const struct GNUNET_MessageHeader *msg) msize = ntohs (msg->size); cm = (const struct ClientPutMessage *) msg; process_result (dc, ntohl (cm->type), + ntohl (cm->respect_offered), + ntohl (cm->num_transmissions), GNUNET_TIME_absolute_ntoh (cm->last_transmission), &cm[1], msize - sizeof (struct ClientPutMessage)); if (NULL == dc->client) @@ -1371,7 +1395,7 @@ do_reconnect (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) * @return GNUNET_OK */ static int -retry_entry (void *cls, const GNUNET_HashCode * key, void *entry) +retry_entry (void *cls, const struct GNUNET_HashCode * key, void *entry) { struct GNUNET_FS_DownloadContext *dc = cls; struct DownloadRequest *dr = entry; @@ -1412,10 +1436,17 @@ try_reconnect (struct GNUNET_FS_DownloadContext *dc) dc->in_receive = GNUNET_NO; dc->client = NULL; } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Will try to reconnect in 1s\n"); + if (0 == dc->reconnect_backoff.rel_value) + dc->reconnect_backoff = GNUNET_TIME_UNIT_MILLISECONDS; + else + dc->reconnect_backoff = GNUNET_TIME_STD_BACKOFF (dc->reconnect_backoff); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Will try to reconnect in %s\n", + GNUNET_STRINGS_relative_time_to_string (dc->reconnect_backoff, GNUNET_YES)); dc->task = - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_SECONDS, &do_reconnect, - dc); + GNUNET_SCHEDULER_add_delayed (dc->reconnect_backoff, + &do_reconnect, + dc); } @@ -1435,6 +1466,7 @@ activate_fs_download (void *cls, struct GNUNET_CLIENT_Connection *client) GNUNET_assert (NULL != client); GNUNET_assert (NULL == dc->client); GNUNET_assert (NULL == dc->th); + GNUNET_assert (NULL != dc->active); dc->client = client; pi.status = GNUNET_FS_STATUS_DOWNLOAD_ACTIVE; GNUNET_FS_download_make_status_ (&pi, dc); @@ -1530,15 +1562,20 @@ create_download_request (struct DownloadRequest *parent, * from the start (rounded down), either because of the requested * file offset or because this IBlock is further along */ if (dr_offset < file_start_offset) - head_skip = file_start_offset / child_block_size; + { + head_skip = (file_start_offset - dr_offset) / child_block_size; + } else + { head_skip = 0; + } /* calculate index of last block at this level that is interesting (rounded up) */ dr->num_children = (file_start_offset + desired_length - dr_offset) / child_block_size; if (dr->num_children * child_block_size < file_start_offset + desired_length - dr_offset) dr->num_children++; /* round up */ + GNUNET_assert (dr->num_children > head_skip); dr->num_children -= head_skip; if (dr->num_children > CHK_PER_INODE) dr->num_children = CHK_PER_INODE; /* cap at max */ @@ -1556,10 +1593,12 @@ create_download_request (struct DownloadRequest *parent, dr->children = GNUNET_malloc (dr->num_children * sizeof (struct DownloadRequest *)); for (i = 0; i < dr->num_children; i++) + { dr->children[i] = create_download_request (dr, i + head_skip, depth - 1, dr_offset + (i + head_skip) * child_block_size, file_start_offset, desired_length); + } return dr; } @@ -1712,7 +1751,7 @@ reconstruct_cb (void *cls, const struct ContentHashKey *chk, uint64_t offset, pi.value.download.specifics.progress.offset = offset; pi.value.download.specifics.progress.data_len = 0; pi.value.download.specifics.progress.depth = 0; - pi.value.download.specifics.progress.trust_offered = 0; + pi.value.download.specifics.progress.respect_offered = 0; pi.value.download.specifics.progress.block_download_duration = GNUNET_TIME_UNIT_ZERO; GNUNET_FS_download_make_status_ (&pi, dc); /* FIXME: duplicated code from 'process_result_with_request - refactor */ @@ -2000,6 +2039,7 @@ GNUNET_FS_download_signal_suspend_ (void *cls) GNUNET_FS_uri_destroy (dc->uri); GNUNET_free_non_null (dc->temp_filename); GNUNET_free_non_null (dc->serialization); + GNUNET_assert (NULL == dc->job_queue); GNUNET_free (dc); } @@ -2041,6 +2081,11 @@ create_download_context (struct GNUNET_FS_Handle *h, return NULL; } dc = GNUNET_malloc (sizeof (struct GNUNET_FS_DownloadContext)); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Starting download %p, %u bytes at offset %llu\n", + dc, + (unsigned long long) length, + (unsigned long long) offset); dc->h = h; dc->uri = GNUNET_FS_uri_dup (uri); dc->meta = GNUNET_CONTAINER_meta_data_duplicate (meta); @@ -2060,7 +2105,7 @@ create_download_context (struct GNUNET_FS_Handle *h, dc->anonymity = anonymity; dc->options = options; dc->active = - GNUNET_CONTAINER_multihashmap_create (1 + 2 * (length / DBLOCK_SIZE)); + GNUNET_CONTAINER_multihashmap_create (1 + 2 * (length / DBLOCK_SIZE), GNUNET_NO); dc->treedepth = GNUNET_FS_compute_depth (GNUNET_FS_uri_chk_get_file_size (dc->uri)); if ((NULL == filename) && (is_recursive_download (dc))) @@ -2128,7 +2173,7 @@ GNUNET_FS_download_start (struct GNUNET_FS_Handle *h, dc->parent = parent; if (NULL != parent) GNUNET_CONTAINER_DLL_insert (parent->child_head, parent->child_tail, dc); - else + else if (0 == (GNUNET_FS_DOWNLOAD_IS_PROBE & options) ) dc->top = GNUNET_FS_make_top (dc->h, &GNUNET_FS_download_signal_suspend_, dc); return dc; @@ -2196,6 +2241,11 @@ GNUNET_FS_download_start_from_search (struct GNUNET_FS_Handle *h, GNUNET_FS_download_stop (sr->probe_ctx, GNUNET_YES); sr->probe_ctx = NULL; } + if (GNUNET_SCHEDULER_NO_TASK != sr->probe_ping_task) + { + GNUNET_SCHEDULER_cancel (sr->probe_ping_task); + sr->probe_ping_task = GNUNET_SCHEDULER_NO_TASK; + } return dc; } @@ -2211,12 +2261,17 @@ GNUNET_FS_download_start_downloading_ (struct GNUNET_FS_DownloadContext *dc) if (dc->completed == dc->length) return; GNUNET_assert (NULL == dc->job_queue); + GNUNET_assert (NULL != dc->active); dc->job_queue = GNUNET_FS_queue_ (dc->h, &activate_fs_download, &deactivate_fs_download, dc, (dc->length + DBLOCK_SIZE - 1) / DBLOCK_SIZE, (0 == (dc->options & GNUNET_FS_DOWNLOAD_IS_PROBE)) ? GNUNET_FS_QUEUE_PRIORITY_NORMAL : GNUNET_FS_QUEUE_PRIORITY_PROBE); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Download %p put into queue as job %p\n", + dc, + dc->job_queue); } @@ -2287,7 +2342,8 @@ GNUNET_FS_download_stop (struct GNUNET_FS_DownloadContext *dc, int do_delete) { if ((dc->completed != dc->length) && (GNUNET_YES == do_delete)) { - if (0 != UNLINK (dc->filename)) + if ( (0 != UNLINK (dc->filename)) && + (ENOENT != errno) ) GNUNET_log_strerror_file (GNUNET_ERROR_TYPE_WARNING, "unlink", dc->filename); } @@ -2303,6 +2359,7 @@ GNUNET_FS_download_stop (struct GNUNET_FS_DownloadContext *dc, int do_delete) GNUNET_free (dc->temp_filename); } GNUNET_free_non_null (dc->serialization); + GNUNET_assert (NULL == dc->job_queue); GNUNET_free (dc); } diff --git a/src/fs/fs_file_information.c b/src/fs/fs_file_information.c index 8065927..7726fc7 100644 --- a/src/fs/fs_file_information.c +++ b/src/fs/fs_file_information.c @@ -367,7 +367,8 @@ GNUNET_FS_file_information_inspect (struct GNUNET_FS_FileInformation *dir, if (GNUNET_OK != proc (proc_cls, dir, (dir->is_directory == GNUNET_YES) ? dir->data.dir.dir_size : dir->data. - file.file_size, dir->meta, &dir->keywords, &dir->bo, + file.file_size, + dir->meta, &dir->keywords, &dir->bo, (dir->is_directory == GNUNET_YES) ? &no : &dir->data.file.do_index, &dir->client_info)) return; diff --git a/src/fs/fs_getopt.c b/src/fs/fs_getopt.c index 0374774..6cc4021 100644 --- a/src/fs/fs_getopt.c +++ b/src/fs/fs_getopt.c @@ -139,11 +139,12 @@ GNUNET_FS_getopt_set_metadata (struct GNUNET_GETOPT_CommandLineProcessorContext *mm = meta; } -#if ENABLE_NLS - tmp = GNUNET_STRINGS_to_utf8 (value, strlen (value), nl_langinfo (CODESET)); -#else - tmp = GNUNET_STRINGS_to_utf8 (value, strlen (value), "utf-8"); -#endif + /* Use GNUNET_STRINGS_get_utf8_args() in main() to acquire utf-8-encoded + * commandline arguments, so that the following line is not needed. + */ + /*tmp = GNUNET_STRINGS_to_utf8 (value, strlen (value), locale_charset ());*/ + tmp = GNUNET_strdup (value); + type = EXTRACTOR_metatype_get_max (); while (type > 0) { diff --git a/src/fs/fs_namespace.c b/src/fs/fs_namespace.c index bfd7594..5c16ea4 100644 --- a/src/fs/fs_namespace.c +++ b/src/fs/fs_namespace.c @@ -53,9 +53,8 @@ get_namespace_directory (struct GNUNET_FS_Handle *h) GNUNET_CONFIGURATION_get_value_filename (h->cfg, "FS", "IDENTITY_DIR", &dn)) { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - _("Configuration fails to specify `%s' in section `%s'\n"), - "IDENTITY_DIR", "fs"); + GNUNET_log_config_missing (GNUNET_ERROR_TYPE_ERROR, + "fs", "IDENTITY_DIR"); return NULL; } return dn; @@ -79,9 +78,8 @@ get_update_information_directory (struct GNUNET_FS_Namespace *ns) GNUNET_CONFIGURATION_get_value_filename (ns->h->cfg, "FS", "UPDATE_DIR", &dn)) { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - _("Configuration fails to specify `%s' in section `%s'\n"), - "UPDATE_DIR", "fs"); + GNUNET_log_config_missing (GNUNET_ERROR_TYPE_ERROR, + "fs", "UPDATE_DIR"); return NULL; } GNUNET_asprintf (&ret, "%s%s%s", dn, DIR_SEPARATOR_STR, ns->name); @@ -106,7 +104,7 @@ write_update_information_graph (struct GNUNET_FS_Namespace *ns) fn = get_update_information_directory (ns); wh = GNUNET_BIO_write_open (fn); - if (wh == NULL) + if (NULL == wh) { GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("Failed to open `%s' for writing: %s\n"), STRERROR (errno)); @@ -160,7 +158,7 @@ read_update_information_graph (struct GNUNET_FS_Namespace *ns) return; } rh = GNUNET_BIO_read_open (fn); - if (rh == NULL) + if (NULL == rh) { GNUNET_free (fn); return; @@ -175,7 +173,7 @@ read_update_information_graph (struct GNUNET_FS_Namespace *ns) GNUNET_break (0); goto END; } - if (count == 0) + if (0 == count) { GNUNET_break (GNUNET_OK == GNUNET_BIO_read_close (rh, NULL)); GNUNET_free (fn); @@ -226,15 +224,13 @@ END: } - - /** * Create a namespace with the given name; if one already * exists, return a handle to the existing namespace. * * @param h handle to the file sharing subsystem * @param name name to use for the namespace - * @return handle to the namespace, NULL on error + * @return handle to the namespace, NULL on error (i.e. invalid filename) */ struct GNUNET_FS_Namespace * GNUNET_FS_namespace_create (struct GNUNET_FS_Handle *h, const char *name) @@ -250,7 +246,7 @@ GNUNET_FS_namespace_create (struct GNUNET_FS_Handle *h, const char *name) ret->h = h; ret->rc = 1; ret->key = GNUNET_CRYPTO_rsa_key_create_from_file (fn); - if (ret->key == NULL) + if (NULL == ret->key) { GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("Failed to create or read private key for namespace `%s'\n"), @@ -284,44 +280,44 @@ GNUNET_FS_namespace_dup (struct GNUNET_FS_Namespace *ns) * memory) or also to freeze the namespace to prevent further * insertions by anyone. * - * @param namespace handle to the namespace that should be deleted / freed + * @param ns handle to the namespace that should be deleted / freed * @param freeze prevents future insertions; creating a namespace * with the same name again will create a fresh namespace instead * * @return GNUNET_OK on success, GNUNET_SYSERR on error */ int -GNUNET_FS_namespace_delete (struct GNUNET_FS_Namespace *namespace, int freeze) +GNUNET_FS_namespace_delete (struct GNUNET_FS_Namespace *ns, int freeze) { unsigned int i; struct NamespaceUpdateNode *nsn; - namespace->rc--; + ns->rc--; if (freeze) { - if (0 != UNLINK (namespace->filename)) + if (0 != UNLINK (ns->filename)) GNUNET_log_strerror_file (GNUNET_ERROR_TYPE_ERROR, "unlink", - namespace->filename); + ns->filename); } - if (0 != namespace->rc) + if (0 != ns->rc) return GNUNET_OK; - GNUNET_CRYPTO_rsa_key_free (namespace->key); - GNUNET_free (namespace->filename); - GNUNET_free (namespace->name); - for (i = 0; i < namespace->update_node_count; i++) + GNUNET_CRYPTO_rsa_key_free (ns->key); + GNUNET_free (ns->filename); + GNUNET_free (ns->name); + for (i = 0; i < ns->update_node_count; i++) { - nsn = namespace->update_nodes[i]; + nsn = ns->update_nodes[i]; GNUNET_CONTAINER_meta_data_destroy (nsn->md); GNUNET_FS_uri_destroy (nsn->uri); GNUNET_free (nsn->id); GNUNET_free (nsn->update); GNUNET_free (nsn); } - GNUNET_array_grow (namespace->update_nodes, namespace->update_node_count, + GNUNET_array_grow (ns->update_nodes, ns->update_node_count, 0); - if (namespace->update_map != NULL) - GNUNET_CONTAINER_multihashmap_destroy (namespace->update_map); - GNUNET_free (namespace); + if (ns->update_map != NULL) + GNUNET_CONTAINER_multihashmap_destroy (ns->update_map); + GNUNET_free (ns); return GNUNET_OK; } @@ -359,12 +355,12 @@ process_namespace (void *cls, const char *filename) struct ProcessNamespaceContext *pnc = cls; struct GNUNET_CRYPTO_RsaPrivateKey *key; struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded pk; - GNUNET_HashCode id; + struct GNUNET_HashCode id; const char *name; const char *t; key = GNUNET_CRYPTO_rsa_key_create_from_file (filename); - if (key == NULL) + if (NULL == key) { GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _ @@ -402,7 +398,7 @@ GNUNET_FS_namespace_list (struct GNUNET_FS_Handle *h, struct ProcessNamespaceContext ctx; dn = get_namespace_directory (h); - if (dn == NULL) + if (NULL == dn) return; ctx.cb = cb; ctx.cb_cls = cb_cls; @@ -431,7 +427,7 @@ struct GNUNET_FS_PublishSksContext /** * Namespace we're publishing to. */ - struct GNUNET_FS_Namespace *namespace; + struct GNUNET_FS_Namespace *ns; /** * Handle to the datastore. @@ -470,7 +466,7 @@ sb_put_cont (void *cls, int success, const char *msg) { struct GNUNET_FS_PublishSksContext *psc = cls; - GNUNET_HashCode hc; + struct GNUNET_HashCode hc; psc->dqe = NULL; if (GNUNET_OK != success) @@ -485,19 +481,19 @@ sb_put_cont (void *cls, int success, /* FIXME: this can be done much more * efficiently by simply appending to the * file and overwriting the 4-byte header */ - if (psc->namespace->update_nodes == NULL) - read_update_information_graph (psc->namespace); - GNUNET_array_append (psc->namespace->update_nodes, - psc->namespace->update_node_count, psc->nsn); - if (psc->namespace->update_map != NULL) + if (psc->ns->update_nodes == NULL) + read_update_information_graph (psc->ns); + GNUNET_array_append (psc->ns->update_nodes, + psc->ns->update_node_count, psc->nsn); + if (psc->ns->update_map != NULL) { GNUNET_CRYPTO_hash (psc->nsn->id, strlen (psc->nsn->id), &hc); - GNUNET_CONTAINER_multihashmap_put (psc->namespace->update_map, &hc, + GNUNET_CONTAINER_multihashmap_put (psc->ns->update_map, &hc, psc->nsn, GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE); } psc->nsn = NULL; - write_update_information_graph (psc->namespace); + write_update_information_graph (psc->ns); } if (NULL != psc->cont) psc->cont (psc->cont_cls, psc->uri, NULL); @@ -509,7 +505,7 @@ sb_put_cont (void *cls, int success, * Publish an SBlock on GNUnet. * * @param h handle to the file sharing subsystem - * @param namespace namespace to publish in + * @param ns namespace to publish in * @param identifier identifier to use * @param update update identifier to use * @param meta metadata to use @@ -522,7 +518,7 @@ sb_put_cont (void *cls, int success, */ struct GNUNET_FS_PublishSksContext * GNUNET_FS_publish_sks (struct GNUNET_FS_Handle *h, - struct GNUNET_FS_Namespace *namespace, + struct GNUNET_FS_Namespace *ns, const char *identifier, const char *update, const struct GNUNET_CONTAINER_MetaData *meta, const struct GNUNET_FS_Uri *uri, @@ -544,31 +540,40 @@ GNUNET_FS_publish_sks (struct GNUNET_FS_Handle *h, struct SBlock *sb_enc; char *dest; struct GNUNET_CONTAINER_MetaData *mmeta; - GNUNET_HashCode key; /* hash of thisId = key */ - GNUNET_HashCode id; /* hash of hc = identifier */ - GNUNET_HashCode query; /* id ^ nsid = DB query */ + struct GNUNET_HashCode key; /* hash of thisId = key */ + struct GNUNET_HashCode id; /* hash of hc = identifier */ + struct GNUNET_HashCode query; /* id ^ nsid = DB query */ - if (NULL == meta) - mmeta = GNUNET_CONTAINER_meta_data_create (); - else - mmeta = GNUNET_CONTAINER_meta_data_duplicate (meta); - uris = GNUNET_FS_uri_to_string (uri); - slen = strlen (uris) + 1; idlen = strlen (identifier); - if (update != NULL) + if (NULL != update) nidlen = strlen (update) + 1; else nidlen = 1; + uris = GNUNET_FS_uri_to_string (uri); + slen = strlen (uris) + 1; + if ( (slen >= MAX_SBLOCK_SIZE - sizeof (struct SBlock)) || + (nidlen >= MAX_SBLOCK_SIZE - sizeof (struct SBlock) - slen) ) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Identifiers or URI too long to create SBlock")); + GNUNET_free (uris); + return NULL; + } + if (NULL == meta) + mmeta = GNUNET_CONTAINER_meta_data_create (); + else + mmeta = GNUNET_CONTAINER_meta_data_duplicate (meta); mdsize = GNUNET_CONTAINER_meta_data_get_serialized_size (mmeta); size = sizeof (struct SBlock) + slen + nidlen + mdsize; - if (size > MAX_SBLOCK_SIZE) + if ( (size > MAX_SBLOCK_SIZE) || + (size < sizeof (struct SBlock) + slen + nidlen) ) { size = MAX_SBLOCK_SIZE; - mdsize = size - (sizeof (struct SBlock) + slen + nidlen); + mdsize = MAX_SBLOCK_SIZE - (sizeof (struct SBlock) + slen + nidlen); } sb = GNUNET_malloc (sizeof (struct SBlock) + size); dest = (char *) &sb[1]; - if (update != NULL) + if (NULL != update) memcpy (dest, update, nidlen); else memset (dest, 0, 1); @@ -580,7 +585,7 @@ GNUNET_FS_publish_sks (struct GNUNET_FS_Handle *h, GNUNET_CONTAINER_meta_data_serialize (mmeta, &dest, mdsize, GNUNET_CONTAINER_META_DATA_SERIALIZE_PART); GNUNET_CONTAINER_meta_data_destroy (mmeta); - if (mdsize == -1) + if (-1 == mdsize) { GNUNET_break (0); GNUNET_free (sb); @@ -591,15 +596,15 @@ GNUNET_FS_publish_sks (struct GNUNET_FS_Handle *h, size = sizeof (struct SBlock) + mdsize + slen + nidlen; sb_enc = GNUNET_malloc (size); GNUNET_CRYPTO_hash (identifier, idlen, &key); - GNUNET_CRYPTO_hash (&key, sizeof (GNUNET_HashCode), &id); + GNUNET_CRYPTO_hash (&key, sizeof (struct GNUNET_HashCode), &id); sks_uri = GNUNET_malloc (sizeof (struct GNUNET_FS_Uri)); sks_uri->type = sks; - GNUNET_CRYPTO_rsa_key_get_public (namespace->key, &sb_enc->subspace); + GNUNET_CRYPTO_rsa_key_get_public (ns->key, &sb_enc->subspace); GNUNET_CRYPTO_hash (&sb_enc->subspace, sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded), - &sks_uri->data.sks.namespace); + &sks_uri->data.sks.ns); sks_uri->data.sks.identifier = GNUNET_strdup (identifier); - GNUNET_CRYPTO_hash_xor (&id, &sks_uri->data.sks.namespace, + GNUNET_CRYPTO_hash_xor (&id, &sks_uri->data.sks.ns, &sb_enc->identifier); GNUNET_CRYPTO_hash_to_aes_key (&key, &sk, &iv); GNUNET_CRYPTO_aes_encrypt (&sb[1], size - sizeof (struct SBlock), &sk, &iv, @@ -609,12 +614,12 @@ GNUNET_FS_publish_sks (struct GNUNET_FS_Handle *h, htonl (slen + mdsize + nidlen + sizeof (struct SBlock) - sizeof (struct GNUNET_CRYPTO_RsaSignature)); GNUNET_assert (GNUNET_OK == - GNUNET_CRYPTO_rsa_sign (namespace->key, &sb_enc->purpose, + GNUNET_CRYPTO_rsa_sign (ns->key, &sb_enc->purpose, &sb_enc->signature)); psc = GNUNET_malloc (sizeof (struct GNUNET_FS_PublishSksContext)); psc->uri = sks_uri; psc->cont = cont; - psc->namespace = GNUNET_FS_namespace_dup (namespace); + psc->ns = GNUNET_FS_namespace_dup (ns); psc->cont_cls = cont_cls; if (0 != (options & GNUNET_FS_PUBLISH_OPTION_SIMULATE_ONLY)) { @@ -631,7 +636,7 @@ GNUNET_FS_publish_sks (struct GNUNET_FS_Handle *h, sb_put_cont (psc, GNUNET_NO, GNUNET_TIME_UNIT_ZERO_ABS, _("Failed to connect to datastore.")); return NULL; } - GNUNET_CRYPTO_hash_xor (&sks_uri->data.sks.namespace, &id, &query); + GNUNET_CRYPTO_hash_xor (&sks_uri->data.sks.ns, &id, &query); if (NULL != update) { psc->nsn = GNUNET_malloc (sizeof (struct NamespaceUpdateNode)); @@ -669,7 +674,7 @@ GNUNET_FS_publish_sks_cancel (struct GNUNET_FS_PublishSksContext *psc) GNUNET_DATASTORE_disconnect (psc->dsh, GNUNET_NO); psc->dsh = NULL; } - GNUNET_FS_namespace_delete (psc->namespace, GNUNET_NO); + GNUNET_FS_namespace_delete (psc->ns, GNUNET_NO); GNUNET_FS_uri_destroy (psc->uri); if (NULL != psc->nsn) { @@ -711,7 +716,7 @@ struct ProcessUpdateClosure * GNUNET_NO if not. */ static int -process_update_node (void *cls, const GNUNET_HashCode * key, void *value) +process_update_node (void *cls, const struct GNUNET_HashCode * key, void *value) { struct ProcessUpdateClosure *pc = cls; struct NamespaceUpdateNode *nsn = value; @@ -729,7 +734,7 @@ struct FindTreeClosure /** * Namespace we are operating on. */ - struct GNUNET_FS_Namespace *namespace; + struct GNUNET_FS_Namespace *ns; /** * Array with 'head's of TREEs. @@ -774,15 +779,15 @@ struct FindTreeClosure * GNUNET_NO if not. */ static int -find_trees (void *cls, const GNUNET_HashCode * key, void *value) +find_trees (void *cls, const struct GNUNET_HashCode * key, void *value) { struct FindTreeClosure *fc = cls; struct NamespaceUpdateNode *nsn = value; - GNUNET_HashCode hc; + struct GNUNET_HashCode hc; if (nsn->nug == fc->nug) { - if (nsn->tree_id == UINT_MAX) + if (UINT_MAX == nsn->tree_id) return GNUNET_YES; /* circular */ GNUNET_assert (nsn->tree_id < fc->tree_array_size); if (fc->tree_array[nsn->tree_id] != nsn) @@ -792,7 +797,7 @@ find_trees (void *cls, const GNUNET_HashCode * key, void *value) return GNUNET_YES; /* that's our own root (can this be?) */ /* merge existing TREE, we have a root for both */ fc->tree_array[nsn->tree_id] = NULL; - if (fc->id == UINT_MAX) + if (UINT_MAX == fc->id) fc->id = nsn->tree_id; /* take over ID */ } else @@ -801,7 +806,7 @@ find_trees (void *cls, const GNUNET_HashCode * key, void *value) nsn->tree_id = UINT_MAX; /* mark as undef */ /* trace */ GNUNET_CRYPTO_hash (nsn->update, strlen (nsn->update), &hc); - GNUNET_CONTAINER_multihashmap_get_multiple (fc->namespace->update_map, &hc, + GNUNET_CONTAINER_multihashmap_get_multiple (fc->ns->update_map, &hc, &find_trees, fc); } return GNUNET_YES; @@ -825,66 +830,67 @@ find_trees (void *cls, const GNUNET_HashCode * key, void *value) * I know, odd definition of a tree, but the GUI will display an actual * tree (GtkTreeView), so that's what counts for the term here. * - * @param namespace namespace to inspect for updateable content + * @param ns namespace to inspect for updateable content * @param next_id ID to look for; use NULL to look for tree roots * @param ip function to call on each updateable identifier * @param ip_cls closure for ip */ void -GNUNET_FS_namespace_list_updateable (struct GNUNET_FS_Namespace *namespace, +GNUNET_FS_namespace_list_updateable (struct GNUNET_FS_Namespace *ns, const char *next_id, GNUNET_FS_IdentifierProcessor ip, void *ip_cls) { unsigned int i; unsigned int nug; - GNUNET_HashCode hc; + struct GNUNET_HashCode hc; struct NamespaceUpdateNode *nsn; struct ProcessUpdateClosure pc; struct FindTreeClosure fc; - if (namespace->update_nodes == NULL) - read_update_information_graph (namespace); - if (namespace->update_nodes == NULL) + if (NULL == ns->update_nodes) + read_update_information_graph (ns); + if (NULL == ns->update_nodes) { GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "No updateable nodes found for ID `%s'\n", next_id); return; /* no nodes */ } - if (namespace->update_map == NULL) + if (NULL == ns->update_map) { /* need to construct */ - namespace->update_map = + ns->update_map = GNUNET_CONTAINER_multihashmap_create (2 + - 3 * namespace->update_node_count / - 4); - for (i = 0; i < namespace->update_node_count; i++) + 3 * ns->update_node_count / + 4, + GNUNET_NO); + for (i = 0; i < ns->update_node_count; i++) { - nsn = namespace->update_nodes[i]; + nsn = ns->update_nodes[i]; GNUNET_CRYPTO_hash (nsn->id, strlen (nsn->id), &hc); - GNUNET_CONTAINER_multihashmap_put (namespace->update_map, &hc, nsn, + GNUNET_CONTAINER_multihashmap_put (ns->update_map, &hc, nsn, GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE); } } - if (next_id != NULL) + if (NULL != next_id) { GNUNET_CRYPTO_hash (next_id, strlen (next_id), &hc); pc.ip = ip; pc.ip_cls = ip_cls; - GNUNET_CONTAINER_multihashmap_get_multiple (namespace->update_map, &hc, + GNUNET_CONTAINER_multihashmap_get_multiple (ns->update_map, &hc, &process_update_node, &pc); return; } GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Calculating TREEs to find roots of update trees\n"); /* Find heads of TREEs in update graph */ - nug = ++namespace->nug_gen; + nug = ++ns->nug_gen; fc.tree_array = NULL; fc.tree_array_size = 0; - for (i = 0; i < namespace->update_node_count; i++) + for (i = 0; i < ns->update_node_count; i++) { - nsn = namespace->update_nodes[i]; + nsn = ns->update_nodes[i]; if (nsn->nug == nug) { GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "TREE of node `%s' is %u\n", nsn->id, @@ -896,10 +902,10 @@ GNUNET_FS_namespace_list_updateable (struct GNUNET_FS_Namespace *namespace, nsn->tree_id = UINT_MAX; fc.id = UINT_MAX; fc.nug = nug; - fc.namespace = namespace; - GNUNET_CONTAINER_multihashmap_get_multiple (namespace->update_map, &hc, + fc.ns = ns; + GNUNET_CONTAINER_multihashmap_get_multiple (ns->update_map, &hc, &find_trees, &fc); - if (fc.id == UINT_MAX) + if (UINT_MAX == fc.id) { /* start new TREE */ for (fc.id = 0; fc.id < fc.tree_array_size; fc.id++) @@ -923,8 +929,8 @@ GNUNET_FS_namespace_list_updateable (struct GNUNET_FS_Namespace *namespace, GNUNET_CRYPTO_hash (nsn->id, strlen (nsn->id), &hc); fc.id = nsn->tree_id; fc.nug = nug; - fc.namespace = namespace; - GNUNET_CONTAINER_multihashmap_get_multiple (namespace->update_map, &hc, + fc.ns = ns; + GNUNET_CONTAINER_multihashmap_get_multiple (ns->update_map, &hc, &find_trees, &fc); } else diff --git a/src/fs/fs_namespace_advertise.c b/src/fs/fs_namespace_advertise.c index e0226ca..3b64e61 100644 --- a/src/fs/fs_namespace_advertise.c +++ b/src/fs/fs_namespace_advertise.c @@ -132,8 +132,8 @@ advertisement_cont (void *cls, int success, { struct GNUNET_FS_AdvertisementContext *ac = cls; const char *keyword; - GNUNET_HashCode key; - GNUNET_HashCode query; + struct GNUNET_HashCode key; + struct GNUNET_HashCode query; struct GNUNET_CRYPTO_AesSessionKey skey; struct GNUNET_CRYPTO_AesInitializationVector iv; struct GNUNET_CRYPTO_RsaPrivateKey *pk; @@ -204,7 +204,7 @@ advertisement_cont (void *cls, int success, * * @param h handle to the file sharing subsystem * @param ksk_uri keywords to use for advertisment - * @param namespace handle for the namespace that should be advertised + * @param ns handle for the namespace that should be advertised * @param meta meta-data for the namespace advertisement * @param bo block options * @param rootEntry name of the root of the namespace @@ -215,7 +215,7 @@ advertisement_cont (void *cls, int success, struct GNUNET_FS_AdvertisementContext * GNUNET_FS_namespace_advertise (struct GNUNET_FS_Handle *h, struct GNUNET_FS_Uri *ksk_uri, - struct GNUNET_FS_Namespace *namespace, + struct GNUNET_FS_Namespace *ns, const struct GNUNET_CONTAINER_MetaData *meta, const struct GNUNET_FS_BlockOptions *bo, const char *rootEntry, @@ -261,7 +261,7 @@ GNUNET_FS_namespace_advertise (struct GNUNET_FS_Handle *h, } size = mdsize + sizeof (struct NBlock) + reslen; nb = GNUNET_malloc (size); - GNUNET_CRYPTO_rsa_key_get_public (namespace->key, &nb->subspace); + GNUNET_CRYPTO_rsa_key_get_public (ns->key, &nb->subspace); nb->ns_purpose.size = htonl (mdsize + reslen + sizeof (struct GNUNET_CRYPTO_RsaSignaturePurpose) + @@ -286,7 +286,7 @@ GNUNET_FS_namespace_advertise (struct GNUNET_FS_Handle *h, ctx->nb = nb; ctx->pt = pt; ctx->pt_size = mdsize + reslen; - ctx->ns = namespace; + ctx->ns = ns; ctx->ns->rc++; ctx->bo = *bo; advertisement_cont (ctx, GNUNET_OK, GNUNET_TIME_UNIT_ZERO_ABS, NULL); diff --git a/src/fs/fs_publish.c b/src/fs/fs_publish.c index 93c3046..30ab1ee 100644 --- a/src/fs/fs_publish.c +++ b/src/fs/fs_publish.c @@ -83,10 +83,10 @@ publish_cleanup (struct GNUNET_FS_PublishContext *pc) pc->fhc = NULL; } GNUNET_FS_file_information_destroy (pc->fi, NULL, NULL); - if (pc->namespace != NULL) + if (pc->ns != NULL) { - GNUNET_FS_namespace_delete (pc->namespace, GNUNET_NO); - pc->namespace = NULL; + GNUNET_FS_namespace_delete (pc->ns, GNUNET_NO); + pc->ns = NULL; } GNUNET_free_non_null (pc->nid); GNUNET_free_non_null (pc->nuid); @@ -269,8 +269,8 @@ publish_sblocks_cont (void *cls, const struct GNUNET_FS_Uri *uri, static void publish_sblock (struct GNUNET_FS_PublishContext *pc) { - if (NULL != pc->namespace) - pc->sks_pc = GNUNET_FS_publish_sks (pc->h, pc->namespace, pc->nid, pc->nuid, + if (NULL != pc->ns) + pc->sks_pc = GNUNET_FS_publish_sks (pc->h, pc->ns, pc->nid, pc->nuid, pc->fi->meta, pc->fi->chk_uri, &pc->fi->bo, pc->options, &publish_sblocks_cont, pc); else @@ -569,6 +569,7 @@ publish_content (struct GNUNET_FS_PublishContext *pc) GNUNET_free (raw_data); raw_data = NULL; } + dirpos->data.file.reader (dirpos->data.file.reader_cls, UINT64_MAX, 0, 0, NULL); } } GNUNET_FS_directory_builder_add (db, dirpos->chk_uri, dirpos->meta, @@ -657,7 +658,7 @@ process_index_start_response (void *cls, const struct GNUNET_MessageHeader *msg) * @param res resulting hash, NULL on error */ static void -hash_for_index_cb (void *cls, const GNUNET_HashCode * res) +hash_for_index_cb (void *cls, const struct GNUNET_HashCode * res) { struct GNUNET_FS_PublishContext *pc = cls; struct GNUNET_FS_FileInformation *p; @@ -958,41 +959,19 @@ fip_signal_start (void *cls, struct GNUNET_FS_FileInformation *fi, /** - * Signal the FS's progress function that we are suspending + * Actually signal the FS's progress function that we are suspending * an upload. * - * @param cls closure (of type "struct GNUNET_FS_PublishContext*") * @param fi the entry in the publish-structure - * @param length length of the file or directory - * @param meta metadata for the file or directory (can be modified) - * @param uri pointer to the keywords that will be used for this entry (can be modified) - * @param bo block options - * @param do_index should we index? - * @param client_info pointer to client context set upon creation (can be modified) - * @return GNUNET_OK to continue (always) + * @param pc the publish context of which a file is being suspended */ -static int -fip_signal_suspend (void *cls, struct GNUNET_FS_FileInformation *fi, - uint64_t length, struct GNUNET_CONTAINER_MetaData *meta, - struct GNUNET_FS_Uri **uri, - struct GNUNET_FS_BlockOptions *bo, int *do_index, - void **client_info) +static void +suspend_operation (struct GNUNET_FS_FileInformation *fi, + struct GNUNET_FS_PublishContext *pc) { - struct GNUNET_FS_PublishContext *pc = cls; struct GNUNET_FS_ProgressInfo pi; uint64_t off; - if (GNUNET_YES == pc->skip_next_fi_callback) - { - pc->skip_next_fi_callback = GNUNET_NO; - return GNUNET_OK; - } - if (GNUNET_YES == GNUNET_FS_meta_data_test_for_directory (meta)) - { - /* process entries in directory */ - pc->skip_next_fi_callback = GNUNET_YES; - GNUNET_FS_file_information_inspect (fi, &fip_signal_suspend, pc); - } if (NULL != pc->ksk_pc) { GNUNET_FS_publish_ksk_cancel (pc->ksk_pc); @@ -1006,10 +985,9 @@ fip_signal_suspend (void *cls, struct GNUNET_FS_FileInformation *fi, GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Suspending publish operation\n"); GNUNET_free_non_null (fi->serialization); fi->serialization = NULL; - off = (fi->chk_uri == NULL) ? 0 : length; + off = (fi->chk_uri == NULL) ? 0 : (fi->is_directory == GNUNET_YES) ? fi->data.dir.dir_size : fi->data.file.file_size; pi.status = GNUNET_FS_STATUS_PUBLISH_SUSPEND; GNUNET_break (NULL == GNUNET_FS_publish_make_status_ (&pi, pc, fi, off)); - *client_info = NULL; if (NULL != pc->qre) { GNUNET_DATASTORE_cancel (pc->qre); @@ -1021,6 +999,45 @@ fip_signal_suspend (void *cls, struct GNUNET_FS_FileInformation *fi, pc->dsh = NULL; } pc->rid = 0; +} + + +/** + * Signal the FS's progress function that we are suspending + * an upload. Performs the recursion. + * + * @param cls closure (of type "struct GNUNET_FS_PublishContext*") + * @param fi the entry in the publish-structure + * @param length length of the file or directory + * @param meta metadata for the file or directory (can be modified) + * @param uri pointer to the keywords that will be used for this entry (can be modified) + * @param bo block options + * @param do_index should we index? + * @param client_info pointer to client context set upon creation (can be modified) + * @return GNUNET_OK to continue (always) + */ +static int +fip_signal_suspend (void *cls, struct GNUNET_FS_FileInformation *fi, + uint64_t length, struct GNUNET_CONTAINER_MetaData *meta, + struct GNUNET_FS_Uri **uri, + struct GNUNET_FS_BlockOptions *bo, int *do_index, + void **client_info) +{ + struct GNUNET_FS_PublishContext *pc = cls; + + if (GNUNET_YES == pc->skip_next_fi_callback) + { + pc->skip_next_fi_callback = GNUNET_NO; + return GNUNET_OK; + } + if (GNUNET_YES == GNUNET_FS_meta_data_test_for_directory (meta)) + { + /* process entries in directory */ + pc->skip_next_fi_callback = GNUNET_YES; + GNUNET_FS_file_information_inspect (fi, &fip_signal_suspend, pc); + } + suspend_operation (fi, pc); + *client_info = NULL; return GNUNET_OK; } @@ -1041,7 +1058,9 @@ GNUNET_FS_publish_signal_suspend_ (void *cls) GNUNET_SCHEDULER_cancel (pc->upload_task); pc->upload_task = GNUNET_SCHEDULER_NO_TASK; } + pc->skip_next_fi_callback = GNUNET_YES; GNUNET_FS_file_information_inspect (pc->fi, &fip_signal_suspend, pc); + suspend_operation (pc->fi, pc); GNUNET_FS_end_top (pc->h, pc->top); pc->top = NULL; publish_cleanup (pc); @@ -1086,7 +1105,7 @@ finish_reserve (void *cls, int success, * * @param h handle to the file sharing subsystem * @param fi information about the file or directory structure to publish - * @param namespace namespace to publish the file in, NULL for no namespace + * @param ns namespace to publish the file in, NULL for no namespace * @param nid identifier to use for the publishd content in the namespace * (can be NULL, must be NULL if namespace is NULL) * @param nuid update-identifier that will be used for future updates @@ -1097,7 +1116,7 @@ finish_reserve (void *cls, int success, struct GNUNET_FS_PublishContext * GNUNET_FS_publish_start (struct GNUNET_FS_Handle *h, struct GNUNET_FS_FileInformation *fi, - struct GNUNET_FS_Namespace *namespace, const char *nid, + struct GNUNET_FS_Namespace *ns, const char *nid, const char *nuid, enum GNUNET_FS_PublishOptions options) { @@ -1119,11 +1138,11 @@ GNUNET_FS_publish_start (struct GNUNET_FS_Handle *h, ret->dsh = dsh; ret->h = h; ret->fi = fi; - ret->namespace = namespace; + ret->ns = ns; ret->options = options; - if (namespace != NULL) + if (ns != NULL) { - namespace->rc++; + ns->rc++; GNUNET_assert (NULL != nid); ret->nid = GNUNET_strdup (nid); if (NULL != nuid) diff --git a/src/fs/fs_publish_ksk.c b/src/fs/fs_publish_ksk.c index 0b6d407..5511fb9 100644 --- a/src/fs/fs_publish_ksk.c +++ b/src/fs/fs_publish_ksk.c @@ -172,8 +172,8 @@ publish_ksk_cont (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { struct GNUNET_FS_PublishKskContext *pkc = cls; const char *keyword; - GNUNET_HashCode key; - GNUNET_HashCode query; + struct GNUNET_HashCode key; + struct GNUNET_HashCode query; struct GNUNET_CRYPTO_AesSessionKey skey; struct GNUNET_CRYPTO_AesInitializationVector iv; struct GNUNET_CRYPTO_RsaPrivateKey *pk; diff --git a/src/fs/fs_search.c b/src/fs/fs_search.c index b280670..3f0a4a3 100644 --- a/src/fs/fs_search.c +++ b/src/fs/fs_search.c @@ -74,7 +74,7 @@ GNUNET_FS_search_make_status_ (struct GNUNET_FS_ProgressInfo *pi, * GNUNET_OK otherwise */ static int -test_result_present (void *cls, const GNUNET_HashCode * key, void *value) +test_result_present (void *cls, const struct GNUNET_HashCode * key, void *value) { const struct GNUNET_FS_Uri *uri = cls; struct GNUNET_FS_SearchResult *sr = value; @@ -129,6 +129,8 @@ notify_client_chk_update (struct GNUNET_FS_SearchContext *sc, pi.value.search.specifics.update.availability_certainty = sr->availability_trials; pi.value.search.specifics.update.applicability_rank = sr->optional_support; + pi.value.search.specifics.update.current_probe_time + = GNUNET_TIME_absolute_get_duration (sr->probe_active_time); sr->client_info = GNUNET_FS_search_make_status_ (&pi, sc); } @@ -162,7 +164,7 @@ struct GetResultContext * @return GNUNET_OK */ static int -get_result_present (void *cls, const GNUNET_HashCode * key, void *value) +get_result_present (void *cls, const struct GNUNET_HashCode * key, void *value) { struct GetResultContext *grc = cls; struct GNUNET_FS_SearchResult *sr = value; @@ -186,10 +188,13 @@ signal_probe_result (struct GNUNET_FS_SearchResult *sr) pi.value.search.specifics.update.cctx = sr->client_info; pi.value.search.specifics.update.meta = sr->meta; pi.value.search.specifics.update.uri = sr->uri; - pi.value.search.specifics.update.availability_rank = sr->availability_success; - pi.value.search.specifics.update.availability_certainty = - sr->availability_trials; + pi.value.search.specifics.update.availability_rank + = 2 * sr->availability_success - sr->availability_trials; + pi.value.search.specifics.update.availability_certainty + = sr->availability_trials; pi.value.search.specifics.update.applicability_rank = sr->optional_support; + pi.value.search.specifics.update.current_probe_time + = GNUNET_TIME_absolute_get_duration (sr->probe_active_time); sr->client_info = GNUNET_FS_search_make_status_ (&pi, sr->sc); GNUNET_FS_search_start_probe_ (sr); } @@ -210,7 +215,16 @@ probe_failure_handler (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) sr->availability_trials++; GNUNET_FS_download_stop (sr->probe_ctx, GNUNET_YES); sr->probe_ctx = NULL; + if (GNUNET_SCHEDULER_NO_TASK != sr->probe_ping_task) + { + GNUNET_SCHEDULER_cancel (sr->probe_ping_task); + sr->probe_ping_task = GNUNET_SCHEDULER_NO_TASK; + } GNUNET_FS_search_result_sync_ (sr); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Probe #%u for search result %p failed\n", + sr->availability_trials, + sr); signal_probe_result (sr); } @@ -231,7 +245,16 @@ probe_success_handler (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) sr->availability_success++; GNUNET_FS_download_stop (sr->probe_ctx, GNUNET_YES); sr->probe_ctx = NULL; + if (GNUNET_SCHEDULER_NO_TASK != sr->probe_ping_task) + { + GNUNET_SCHEDULER_cancel (sr->probe_ping_task); + sr->probe_ping_task = GNUNET_SCHEDULER_NO_TASK; + } GNUNET_FS_search_result_sync_ (sr); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Probe #%u for search result %p succeeded\n", + sr->availability_trials, + sr); signal_probe_result (sr); } @@ -302,11 +325,19 @@ GNUNET_FS_search_probe_progress_ (void *cls, sr = NULL; break; case GNUNET_FS_STATUS_DOWNLOAD_ACTIVE: - GNUNET_assert (GNUNET_SCHEDULER_NO_TASK == sr->probe_cancel_task); - sr->probe_active_time = GNUNET_TIME_absolute_get (); - sr->probe_cancel_task = + if (GNUNET_SCHEDULER_NO_TASK == sr->probe_cancel_task) + { + sr->probe_active_time = GNUNET_TIME_absolute_get (); + sr->probe_cancel_task = GNUNET_SCHEDULER_add_delayed (sr->remaining_probe_time, &probe_failure_handler, sr); + } + else + { + /* should only happen if the cancel task was already + created on 'DOWNLOAD_INACTIVE' as we were out of time */ + GNUNET_break (0 == sr->remaining_probe_time.rel_value); + } break; case GNUNET_FS_STATUS_DOWNLOAD_INACTIVE: if (GNUNET_SCHEDULER_NO_TASK != sr->probe_cancel_task) @@ -317,6 +348,9 @@ GNUNET_FS_search_probe_progress_ (void *cls, dur = GNUNET_TIME_absolute_get_duration (sr->probe_active_time); sr->remaining_probe_time = GNUNET_TIME_relative_subtract (sr->remaining_probe_time, dur); + if (0 == sr->remaining_probe_time.rel_value) + sr->probe_cancel_task = + GNUNET_SCHEDULER_add_now (&probe_failure_handler, sr); GNUNET_FS_search_result_sync_ (sr); break; default: @@ -327,6 +361,26 @@ GNUNET_FS_search_probe_progress_ (void *cls, } +/** + * Task run periodically to remind clients that a probe is active. + * + * @param cls the 'struct GNUNET_FS_SearchResult' that we are probing for + * @param tc scheduler context + */ +static void +probe_ping_task (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct GNUNET_FS_SearchResult *sr = cls; + + signal_probe_result (sr); + sr->probe_ping_task + = GNUNET_SCHEDULER_add_delayed (GNUNET_FS_PROBE_UPDATE_FREQUENCY, + &probe_ping_task, + sr); +} + + /** * Start download probes for the given search result. * @@ -361,6 +415,11 @@ GNUNET_FS_search_start_probe_ (struct GNUNET_FS_SearchResult *sr) len = len - off; else len = DBLOCK_SIZE; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Starting probe #%u (at offset %llu) for search result %p\n", + sr->availability_trials + 1, + (unsigned long long) off, + sr); sr->remaining_probe_time = GNUNET_TIME_relative_multiply (sr->sc->h->avg_block_latency, 2 * (1 + sr->availability_trials)); @@ -369,6 +428,9 @@ GNUNET_FS_search_start_probe_ (struct GNUNET_FS_SearchResult *sr) len, sr->sc->anonymity, GNUNET_FS_DOWNLOAD_NO_TEMPORARIES | GNUNET_FS_DOWNLOAD_IS_PROBE, sr, NULL); + sr->probe_ping_task + = GNUNET_SCHEDULER_add_now (&probe_ping_task, + sr); } @@ -388,7 +450,7 @@ process_ksk_result (struct GNUNET_FS_SearchContext *sc, const struct GNUNET_FS_Uri *uri, const struct GNUNET_CONTAINER_MetaData *meta) { - GNUNET_HashCode key; + struct GNUNET_HashCode key; struct GNUNET_FS_SearchResult *sr; struct GetResultContext grc; int is_new; @@ -477,7 +539,7 @@ process_sks_result (struct GNUNET_FS_SearchContext *sc, const char *id_update, const struct GNUNET_CONTAINER_MetaData *meta) { struct GNUNET_FS_Uri uu; - GNUNET_HashCode key; + struct GNUNET_HashCode key; struct GNUNET_FS_SearchResult *sr; /* check if new */ @@ -505,7 +567,7 @@ process_sks_result (struct GNUNET_FS_SearchContext *sc, const char *id_update, if (0 == strlen (id_update)) return; /* no updates */ uu.type = sks; - uu.data.sks.namespace = sc->uri->data.sks.namespace; + uu.data.sks.ns = sc->uri->data.sks.ns; uu.data.sks.identifier = GNUNET_strdup (id_update); (void) search_start (sc->h, &uu, sc->anonymity, sc->options, NULL, sr); GNUNET_free (uu.data.sks.identifier); @@ -533,7 +595,7 @@ decrypt_block_with_keyword (const struct GNUNET_FS_SearchContext *sc, size_t edata_size, char *data) { - GNUNET_HashCode q; + struct GNUNET_HashCode q; struct GNUNET_CRYPTO_AesSessionKey skey; struct GNUNET_CRYPTO_AesInitializationVector iv; int i; @@ -543,7 +605,7 @@ decrypt_block_with_keyword (const struct GNUNET_FS_SearchContext *sc, &q); /* find key */ for (i = 0; i < sc->uri->data.ksk.keywordCount; i++) - if (0 == memcmp (&q, &sc->requests[i].query, sizeof (GNUNET_HashCode))) + if (0 == memcmp (&q, &sc->requests[i].query, sizeof (struct GNUNET_HashCode))) break; if (i == sc->uri->data.ksk.keywordCount) { @@ -671,13 +733,13 @@ process_nblock (struct GNUNET_FS_SearchContext *sc, const struct NBlock *nb, uri->data.sks.identifier = GNUNET_strdup (pt); GNUNET_CRYPTO_hash (&nb->subspace, sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded), - &uri->data.sks.namespace); + &uri->data.sks.ns); uris = GNUNET_FS_uri_to_string (uri); GNUNET_CONTAINER_meta_data_insert (meta, "", EXTRACTOR_METATYPE_URI, EXTRACTOR_METAFORMAT_UTF8, "text/plain", uris, strlen (uris) + 1); GNUNET_free (uris); - GNUNET_PSEUDONYM_add (sc->h->cfg, &uri->data.sks.namespace, meta); + GNUNET_PSEUDONYM_add (sc->h->cfg, &uri->data.sks.ns, meta); /* process */ process_ksk_result (sc, &sc->requests[i], uri, meta); @@ -708,7 +770,7 @@ process_sblock (struct GNUNET_FS_SearchContext *sc, const struct SBlock *sb, const char *uris; size_t off; char *emsg; - GNUNET_HashCode key; + struct GNUNET_HashCode key; char *identifier; /* decrypt */ @@ -762,7 +824,8 @@ process_sblock (struct GNUNET_FS_SearchContext *sc, const struct SBlock *sb, */ static void process_result (struct GNUNET_FS_SearchContext *sc, enum GNUNET_BLOCK_Type type, - struct GNUNET_TIME_Absolute expiration, const void *data, + struct GNUNET_TIME_Absolute expiration, + const void *data, size_t size) { if (GNUNET_TIME_absolute_get_duration (expiration).rel_value > 0) @@ -904,7 +967,7 @@ struct MessageBuilderContext /** * Where to store the keys. */ - GNUNET_HashCode *xoff; + struct GNUNET_HashCode *xoff; /** * Search context we are iterating for. @@ -928,7 +991,7 @@ struct MessageBuilderContext * @return GNUNET_OK to continue iterating */ static int -build_result_set (void *cls, const GNUNET_HashCode * key, void *value) +build_result_set (void *cls, const struct GNUNET_HashCode * key, void *value) { struct MessageBuilderContext *mbc = cls; struct GNUNET_FS_SearchResult *sr = value; @@ -960,7 +1023,7 @@ build_result_set (void *cls, const GNUNET_HashCode * key, void *value) * @return GNUNET_OK to continue iterating */ static int -find_result_set (void *cls, const GNUNET_HashCode * key, void *value) +find_result_set (void *cls, const struct GNUNET_HashCode * key, void *value) { struct MessageBuilderContext *mbc = cls; struct GNUNET_FS_SearchResult *sr = value; @@ -990,8 +1053,8 @@ transmit_search_request (void *cls, size_t size, void *buf) size_t msize; struct SearchMessage *sm; const char *identifier; - GNUNET_HashCode key; - GNUNET_HashCode idh; + struct GNUNET_HashCode key; + struct GNUNET_HashCode idh; unsigned int sqms; uint32_t options; @@ -1004,7 +1067,7 @@ transmit_search_request (void *cls, size_t size, void *buf) mbc.skip_cnt = sc->search_request_map_offset; sm = buf; sm->header.type = htons (GNUNET_MESSAGE_TYPE_FS_START_SEARCH); - mbc.xoff = (GNUNET_HashCode *) & sm[1]; + mbc.xoff = (struct GNUNET_HashCode *) & sm[1]; options = SEARCH_MESSAGE_OPTION_NONE; if (0 != (sc->options & GNUNET_FS_SEARCH_OPTION_LOOPBACK_ONLY)) options |= SEARCH_MESSAGE_OPTION_LOOPBACK_ONLY; @@ -1013,24 +1076,26 @@ transmit_search_request (void *cls, size_t size, void *buf) msize = sizeof (struct SearchMessage); GNUNET_assert (size >= msize); mbc.keyword_offset = sc->keyword_offset; + /* calculate total number of known results (in put_cnt => sqms) */ mbc.put_cnt = 0; GNUNET_CONTAINER_multihashmap_iterate (sc->master_result_map, &find_result_set, &mbc); sqms = mbc.put_cnt; - mbc.put_cnt = (size - msize) / sizeof (GNUNET_HashCode); + /* calculate how many results we can send in this message */ + mbc.put_cnt = (size - msize) / sizeof (struct GNUNET_HashCode); mbc.put_cnt = GNUNET_MIN (mbc.put_cnt, sqms - mbc.skip_cnt); if (sc->search_request_map_offset < sqms) GNUNET_assert (mbc.put_cnt > 0); + /* now build message */ + msize += sizeof (struct GNUNET_HashCode) * mbc.put_cnt; sm->header.size = htons (msize); sm->type = htonl (GNUNET_BLOCK_TYPE_ANY); sm->anonymity_level = htonl (sc->anonymity); - memset (&sm->target, 0, sizeof (GNUNET_HashCode)); + memset (&sm->target, 0, sizeof (struct GNUNET_HashCode)); sm->query = sc->requests[sc->keyword_offset].query; - msize += sizeof (GNUNET_HashCode) * mbc.put_cnt; GNUNET_CONTAINER_multihashmap_iterate (sc->master_result_map, &build_result_set, &mbc); - sm->header.size = htons (msize); GNUNET_assert (sqms >= sc->search_request_map_offset); if (sqms != sc->search_request_map_offset) { @@ -1055,18 +1120,18 @@ transmit_search_request (void *cls, size_t size, void *buf) GNUNET_assert (size >= msize); sm->type = htonl (GNUNET_BLOCK_TYPE_FS_SBLOCK); sm->anonymity_level = htonl (sc->anonymity); - sm->target = sc->uri->data.sks.namespace; + sm->target = sc->uri->data.sks.ns; identifier = sc->uri->data.sks.identifier; GNUNET_CRYPTO_hash (identifier, strlen (identifier), &key); - GNUNET_CRYPTO_hash (&key, sizeof (GNUNET_HashCode), &idh); + GNUNET_CRYPTO_hash (&key, sizeof (struct GNUNET_HashCode), &idh); GNUNET_CRYPTO_hash_xor (&idh, &sm->target, &sm->query); - mbc.put_cnt = (size - msize) / sizeof (GNUNET_HashCode); + mbc.put_cnt = (size - msize) / sizeof (struct GNUNET_HashCode); sqms = GNUNET_CONTAINER_multihashmap_size (sc->master_result_map); mbc.put_cnt = GNUNET_MIN (mbc.put_cnt, sqms - mbc.skip_cnt); mbc.keyword_offset = 0; if (sc->search_request_map_offset < sqms) GNUNET_assert (mbc.put_cnt > 0); - msize += sizeof (GNUNET_HashCode) * mbc.put_cnt; + msize += sizeof (struct GNUNET_HashCode) * mbc.put_cnt; GNUNET_CONTAINER_multihashmap_iterate (sc->master_result_map, &build_result_set, &mbc); sm->header.size = htons (msize); @@ -1103,9 +1168,9 @@ schedule_transmit_search_request (struct GNUNET_FS_SearchContext *sc) sqms = GNUNET_CONTAINER_multihashmap_size (sc->master_result_map) - sc->search_request_map_offset; - fit = (GNUNET_SERVER_MAX_MESSAGE_SIZE - 1 - size) / sizeof (GNUNET_HashCode); + fit = (GNUNET_SERVER_MAX_MESSAGE_SIZE - 1 - size) / sizeof (struct GNUNET_HashCode); fit = GNUNET_MIN (fit, sqms); - size += sizeof (GNUNET_HashCode) * fit; + size += sizeof (struct GNUNET_HashCode) * fit; GNUNET_CLIENT_notify_transmit_ready (sc->client, size, GNUNET_CONSTANTS_SERVICE_TIMEOUT, GNUNET_NO, &transmit_search_request, sc); @@ -1155,8 +1220,10 @@ try_reconnect (struct GNUNET_FS_SearchContext *sc) GNUNET_CLIENT_disconnect (sc->client); sc->client = NULL; } + sc->reconnect_backoff = GNUNET_TIME_STD_BACKOFF (sc->reconnect_backoff); sc->task = - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_SECONDS, &do_reconnect, + GNUNET_SCHEDULER_add_delayed (sc->reconnect_backoff, + &do_reconnect, sc); } @@ -1192,7 +1259,7 @@ search_start (struct GNUNET_FS_Handle *h, const struct GNUNET_FS_Uri *uri, sc->psearch_result = psearch; psearch->update_search = sc; } - sc->master_result_map = GNUNET_CONTAINER_multihashmap_create (16); + sc->master_result_map = GNUNET_CONTAINER_multihashmap_create (16, GNUNET_NO); sc->client_info = cctx; if (GNUNET_OK != GNUNET_FS_search_start_searching_ (sc)) { @@ -1220,7 +1287,7 @@ GNUNET_FS_search_start_searching_ (struct GNUNET_FS_SearchContext *sc) { unsigned int i; const char *keyword; - GNUNET_HashCode hc; + struct GNUNET_HashCode hc; struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded pub; struct GNUNET_CRYPTO_RsaPrivateKey *pk; @@ -1246,7 +1313,7 @@ GNUNET_FS_search_start_searching_ (struct GNUNET_FS_SearchContext *sc) sc->requests[i].mandatory = (sc->uri->data.ksk.keywords[i][0] == '+'); if (sc->requests[i].mandatory) sc->mandatory_count++; - sc->requests[i].results = GNUNET_CONTAINER_multihashmap_create (4); + sc->requests[i].results = GNUNET_CONTAINER_multihashmap_create (4, GNUNET_NO); GNUNET_CRYPTO_hash (keyword, strlen (keyword), &sc->requests[i].key); } } @@ -1267,7 +1334,7 @@ GNUNET_FS_search_start_searching_ (struct GNUNET_FS_SearchContext *sc) * @return GNUNET_OK */ static int -search_result_freeze_probes (void *cls, const GNUNET_HashCode * key, +search_result_freeze_probes (void *cls, const struct GNUNET_HashCode * key, void *value) { struct GNUNET_FS_SearchResult *sr = value; @@ -1277,6 +1344,11 @@ search_result_freeze_probes (void *cls, const GNUNET_HashCode * key, GNUNET_FS_download_stop (sr->probe_ctx, GNUNET_YES); sr->probe_ctx = NULL; } + if (GNUNET_SCHEDULER_NO_TASK != sr->probe_ping_task) + { + GNUNET_SCHEDULER_cancel (sr->probe_ping_task); + sr->probe_ping_task = GNUNET_SCHEDULER_NO_TASK; + } if (GNUNET_SCHEDULER_NO_TASK != sr->probe_cancel_task) { GNUNET_SCHEDULER_cancel (sr->probe_cancel_task); @@ -1297,7 +1369,7 @@ search_result_freeze_probes (void *cls, const GNUNET_HashCode * key, * @return GNUNET_OK */ static int -search_result_resume_probes (void *cls, const GNUNET_HashCode * key, +search_result_resume_probes (void *cls, const struct GNUNET_HashCode * key, void *value) { struct GNUNET_FS_SearchResult *sr = value; @@ -1318,7 +1390,7 @@ search_result_resume_probes (void *cls, const GNUNET_HashCode * key, * @return GNUNET_OK */ static int -search_result_suspend (void *cls, const GNUNET_HashCode * key, void *value) +search_result_suspend (void *cls, const struct GNUNET_HashCode * key, void *value) { struct GNUNET_FS_SearchContext *sc = cls; struct GNUNET_FS_SearchResult *sr = value; @@ -1334,6 +1406,11 @@ search_result_suspend (void *cls, const GNUNET_HashCode * key, void *value) GNUNET_FS_download_stop (sr->probe_ctx, GNUNET_YES); sr->probe_ctx = NULL; } + if (GNUNET_SCHEDULER_NO_TASK != sr->probe_ping_task) + { + GNUNET_SCHEDULER_cancel (sr->probe_ping_task); + sr->probe_ping_task = GNUNET_SCHEDULER_NO_TASK; + } if (NULL != sr->update_search) { GNUNET_FS_search_signal_suspend_ (sr->update_search); @@ -1477,12 +1554,28 @@ GNUNET_FS_search_continue (struct GNUNET_FS_SearchContext *sc) * @return GNUNET_OK */ static int -search_result_stop (void *cls, const GNUNET_HashCode * key, void *value) +search_result_stop (void *cls, const struct GNUNET_HashCode * key, void *value) { struct GNUNET_FS_SearchContext *sc = cls; struct GNUNET_FS_SearchResult *sr = value; struct GNUNET_FS_ProgressInfo pi; + if (NULL != sr->probe_ctx) + { + GNUNET_FS_download_stop (sr->probe_ctx, GNUNET_YES); + sr->probe_ctx = NULL; + } + if (GNUNET_SCHEDULER_NO_TASK != sr->probe_ping_task) + { + GNUNET_SCHEDULER_cancel (sr->probe_ping_task); + sr->probe_ping_task = GNUNET_SCHEDULER_NO_TASK; + } + if (GNUNET_SCHEDULER_NO_TASK != sr->probe_cancel_task) + { + GNUNET_SCHEDULER_cancel (sr->probe_cancel_task); + sr->probe_cancel_task = GNUNET_SCHEDULER_NO_TASK; + } + if (NULL != sr->download) { sr->download->search = NULL; @@ -1519,7 +1612,7 @@ search_result_stop (void *cls, const GNUNET_HashCode * key, void *value) * @return GNUNET_OK */ static int -search_result_free (void *cls, const GNUNET_HashCode * key, void *value) +search_result_free (void *cls, const struct GNUNET_HashCode * key, void *value) { struct GNUNET_FS_SearchResult *sr = value; @@ -1528,14 +1621,13 @@ search_result_free (void *cls, const GNUNET_HashCode * key, void *value) GNUNET_FS_search_stop (sr->update_search); GNUNET_assert (NULL == sr->update_search); } + GNUNET_break (NULL == sr->probe_ctx); + GNUNET_break (GNUNET_SCHEDULER_NO_TASK == sr->probe_cancel_task); + GNUNET_break (GNUNET_SCHEDULER_NO_TASK == sr->probe_ping_task); GNUNET_break (NULL == sr->client_info); GNUNET_free_non_null (sr->serialization); GNUNET_FS_uri_destroy (sr->uri); GNUNET_CONTAINER_meta_data_destroy (sr->meta); - if (NULL != sr->probe_ctx) - GNUNET_FS_download_stop (sr->probe_ctx, GNUNET_YES); - if (GNUNET_SCHEDULER_NO_TASK != sr->probe_cancel_task) - GNUNET_SCHEDULER_cancel (sr->probe_cancel_task); GNUNET_free_non_null (sr->keyword_bitmap); GNUNET_free (sr); return GNUNET_OK; diff --git a/src/fs/fs_sharetree.c b/src/fs/fs_sharetree.c index c929428..5e96390 100644 --- a/src/fs/fs_sharetree.c +++ b/src/fs/fs_sharetree.c @@ -162,7 +162,7 @@ add_to_keyword_counter (void *cls, const char *keyword, int is_mandatory) { struct GNUNET_CONTAINER_MultiHashMap *mcm = cls; struct KeywordCounter *cnt; - GNUNET_HashCode hc; + struct GNUNET_HashCode hc; size_t klen; klen = strlen (keyword) + 1; @@ -206,7 +206,7 @@ add_to_meta_counter (void *cls, const char *plugin_name, const char *data_mime_type, const char *data, size_t data_len) { struct GNUNET_CONTAINER_MultiHashMap *map = cls; - GNUNET_HashCode key; + struct GNUNET_HashCode key; struct MetaCounter *cnt; GNUNET_CRYPTO_hash (data, data_len, &key); @@ -243,7 +243,7 @@ remove_high_frequency_keywords (void *cls, const char *keyword, int is_mandatory { struct TrimContext *tc = cls; struct KeywordCounter *counter; - GNUNET_HashCode hc; + struct GNUNET_HashCode hc; size_t klen; klen = strlen (keyword) + 1; @@ -268,7 +268,7 @@ remove_high_frequency_keywords (void *cls, const char *keyword, int is_mandatory * @return GNUNET_YES (always) */ static int -migrate_and_drop_keywords (void *cls, const GNUNET_HashCode * key, void *value) +migrate_and_drop_keywords (void *cls, const struct GNUNET_HashCode * key, void *value) { struct TrimContext *tc = cls; struct KeywordCounter *counter = value; @@ -299,7 +299,7 @@ migrate_and_drop_keywords (void *cls, const GNUNET_HashCode * key, void *value) * @return GNUNET_YES (always) */ static int -migrate_and_drop_metadata (void *cls, const GNUNET_HashCode * key, void *value) +migrate_and_drop_metadata (void *cls, const struct GNUNET_HashCode * key, void *value) { struct TrimContext *tc = cls; struct MetaCounter *counter = value; @@ -415,8 +415,8 @@ GNUNET_FS_share_tree_trim (struct GNUNET_FS_ShareTreeItem *toplevel) if (toplevel == NULL) return; - tc.keywordcounter = GNUNET_CONTAINER_multihashmap_create (1024); - tc.metacounter = GNUNET_CONTAINER_multihashmap_create (1024); + tc.keywordcounter = GNUNET_CONTAINER_multihashmap_create (1024, GNUNET_NO); + tc.metacounter = GNUNET_CONTAINER_multihashmap_create (1024, GNUNET_NO); share_tree_trim (&tc, toplevel); GNUNET_CONTAINER_multihashmap_destroy (tc.keywordcounter); GNUNET_CONTAINER_multihashmap_destroy (tc.metacounter); diff --git a/src/fs/fs_test_lib.c b/src/fs/fs_test_lib.c index 06ab01f..758220f 100644 --- a/src/fs/fs_test_lib.c +++ b/src/fs/fs_test_lib.c @@ -1,6 +1,6 @@ /* This file is part of GNUnet. - (C) 2010, 2011 Christian Grothoff (and other contributing authors) + (C) 2010, 2011, 2012 Christian Grothoff (and other contributing authors) GNUnet is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published @@ -20,8 +20,8 @@ /** * @file fs/fs_test_lib.c - * @brief library routines for testing FS publishing and downloading - * with multiple peers; this code is limited to flat files + * @brief library routines for testing FS publishing and downloading; + * this code is limited to flat files * and no keywords (those functions can be tested with * single-peer setups; this is for testing routing). * @author Christian Grothoff @@ -29,50 +29,27 @@ #include "platform.h" #include "fs_api.h" #include "fs_test_lib.h" -#include "gnunet_testing_lib.h" -#define CONNECT_ATTEMPTS 4 #define CONTENT_LIFETIME GNUNET_TIME_UNIT_HOURS + /** - * Handle for a daemon started for testing FS. + * Handle for a publishing operation started for testing FS. */ -struct GNUNET_FS_TestDaemon +struct TestPublishOperation { /** - * Global configuration, only stored in first test daemon, - * otherwise NULL. + * Handle for the operation to connect to the peer's 'fs' service. */ - struct GNUNET_CONFIGURATION_Handle *gcfg; + struct GNUNET_TESTBED_Operation *fs_op; /** * Handle to the file sharing context using this daemon. */ struct GNUNET_FS_Handle *fs; - /** - * Handle to the daemon via testing. - */ - struct GNUNET_TESTING_Daemon *daemon; - - /** - * Note that 'group' will be the same value for all of the - * daemons started jointly. - */ - struct GNUNET_TESTING_PeerGroup *group; - - /** - * Configuration for accessing this peer. - */ - struct GNUNET_CONFIGURATION_Handle *cfg; - - /** - * ID of this peer. - */ - struct GNUNET_PeerIdentity id; - /** * Function to call when upload is done. */ @@ -108,6 +85,49 @@ struct GNUNET_FS_TestDaemon */ char *publish_tmp_file; + /** + * Size of the file. + */ + uint64_t size; + + /** + * Anonymity level used. + */ + uint32_t anonymity; + + /** + * Verbosity level of the current operation. + */ + unsigned int verbose; + + /** + * Are we testing indexing? (YES: index, NO: insert, SYSERR: simulate) + */ + int do_index; +}; + + +/** + * Handle for a download operation started for testing FS. + */ +struct TestDownloadOperation +{ + + /** + * Handle for the operation to connect to the peer's 'fs' service. + */ + struct GNUNET_TESTBED_Operation *fs_op; + + /** + * Handle to the file sharing context using this daemon. + */ + struct GNUNET_FS_Handle *fs; + + /** + * Handle to the daemon via testing. + */ + struct GNUNET_TESTING_Daemon *daemon; + /** * Function to call when download is done. */ @@ -119,9 +139,9 @@ struct GNUNET_FS_TestDaemon void *download_cont_cls; /** - * Seed for download verification. + * URI to download. */ - uint32_t download_seed; + struct GNUNET_FS_Uri *uri; /** * Task to abort downloading (timeout). @@ -134,107 +154,114 @@ struct GNUNET_FS_TestDaemon struct GNUNET_FS_DownloadContext *download_context; /** - * Verbosity level of the current operation. + * Size of the file. */ - int verbose; + uint64_t size; + /** + * Anonymity level used. + */ + uint32_t anonymity; -}; + /** + * Seed for download verification. + */ + uint32_t download_seed; -/** - * Check whether peers successfully shut down. - */ -static void -shutdown_callback (void *cls, const char *emsg) -{ - struct GNUNET_CONFIGURATION_Handle *gcfg = cls; + /** + * Verbosity level of the current operation. + */ + unsigned int verbose; - if (emsg != NULL) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Shutdown of peers failed: %s\n", - emsg); - } - else - { -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "All peers successfully shut down!\n"); -#endif - } - if (gcfg != NULL) - GNUNET_CONFIGURATION_destroy (gcfg); -} +}; +/** + * Task scheduled to report on the completion of our publish operation. + * + * @param cls the publish operation context + * @param tc scheduler context (unused) + */ static void -report_uri (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +report_uri (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) { - struct GNUNET_FS_TestDaemon *daemon = cls; - GNUNET_FS_TEST_UriContinuation cont; - struct GNUNET_FS_Uri *uri; - - GNUNET_FS_publish_stop (daemon->publish_context); - daemon->publish_context = NULL; - cont = daemon->publish_cont; - daemon->publish_cont = NULL; - uri = daemon->publish_uri; - cont (daemon->publish_cont_cls, uri); - GNUNET_FS_uri_destroy (uri); + struct TestPublishOperation *po = cls; + + GNUNET_FS_publish_stop (po->publish_context); + GNUNET_TESTBED_operation_done (po->fs_op); + po->publish_cont (po->publish_cont_cls, + po->publish_uri, + (GNUNET_YES == po->do_index) + ? po->publish_tmp_file + : NULL); + GNUNET_FS_uri_destroy (po->publish_uri); + if (GNUNET_YES != po->do_index) + (void) GNUNET_DISK_directory_remove (po->publish_tmp_file); + GNUNET_free_non_null (po->publish_tmp_file); + GNUNET_free (po); } +/** + * Task scheduled to run when publish operation times out. + * + * @param cls the publish operation context + * @param tc scheduler context (unused) + */ static void -report_success (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +publish_timeout (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { - struct GNUNET_FS_TestDaemon *daemon = cls; + struct TestPublishOperation *po = cls; - GNUNET_FS_download_stop (daemon->download_context, GNUNET_YES); - daemon->download_context = NULL; - GNUNET_SCHEDULER_add_continuation (daemon->download_cont, - daemon->download_cont_cls, - GNUNET_SCHEDULER_REASON_PREREQ_DONE); - daemon->download_cont = NULL; + po->publish_timeout_task = GNUNET_SCHEDULER_NO_TASK; + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Timeout while trying to publish data\n"); + if (NULL == po->fs) + GNUNET_TESTBED_operation_done (po->fs_op); + else + GNUNET_TESTBED_operation_done (po->fs_op); + GNUNET_FS_publish_stop (po->publish_context); + po->publish_cont (po->publish_cont_cls, NULL, NULL); + (void) GNUNET_DISK_directory_remove (po->publish_tmp_file); + GNUNET_free_non_null (po->publish_tmp_file); + GNUNET_free (po); } +/** + * Progress callback for file-sharing events while publishing. + * + * @param cls the publish operation context + * @param info information about the event + */ static void * -progress_cb (void *cls, const struct GNUNET_FS_ProgressInfo *info) +publish_progress_cb (void *cls, const struct GNUNET_FS_ProgressInfo *info) { - struct GNUNET_FS_TestDaemon *daemon = cls; + struct TestPublishOperation *po = cls; switch (info->status) { case GNUNET_FS_STATUS_PUBLISH_COMPLETED: - GNUNET_SCHEDULER_cancel (daemon->publish_timeout_task); - daemon->publish_timeout_task = GNUNET_SCHEDULER_NO_TASK; - daemon->publish_uri = + GNUNET_SCHEDULER_cancel (po->publish_timeout_task); + po->publish_timeout_task = GNUNET_SCHEDULER_NO_TASK; + po->publish_uri = GNUNET_FS_uri_dup (info->value.publish.specifics.completed.chk_uri); - GNUNET_SCHEDULER_add_continuation (&report_uri, daemon, + GNUNET_SCHEDULER_add_continuation (&report_uri, po, GNUNET_SCHEDULER_REASON_PREREQ_DONE); break; case GNUNET_FS_STATUS_PUBLISH_PROGRESS: - if (daemon->verbose) + if (po->verbose) GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Publishing at %llu/%llu bytes\n", (unsigned long long) info->value.publish.completed, (unsigned long long) info->value.publish.size); break; case GNUNET_FS_STATUS_DOWNLOAD_PROGRESS: - if (daemon->verbose) + if (po->verbose) GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Download at %llu/%llu bytes\n", (unsigned long long) info->value.download.completed, (unsigned long long) info->value.download.size); break; - case GNUNET_FS_STATUS_DOWNLOAD_COMPLETED: - GNUNET_SCHEDULER_cancel (daemon->download_timeout_task); - daemon->download_timeout_task = GNUNET_SCHEDULER_NO_TASK; - GNUNET_SCHEDULER_add_continuation (&report_success, daemon, - GNUNET_SCHEDULER_REASON_PREREQ_DONE); - break; - case GNUNET_FS_STATUS_DOWNLOAD_ACTIVE: - case GNUNET_FS_STATUS_DOWNLOAD_INACTIVE: - break; - /* FIXME: monitor data correctness during download progress */ - /* FIXME: do performance reports given sufficient verbosity */ - /* FIXME: advance timeout task to "immediate" on error */ default: break; } @@ -242,460 +269,351 @@ progress_cb (void *cls, const struct GNUNET_FS_ProgressInfo *info) } -struct StartContext -{ - struct GNUNET_TIME_Relative timeout; - unsigned int total; - unsigned int have; - struct GNUNET_FS_TestDaemon **daemons; - GNUNET_SCHEDULER_Task cont; - void *cont_cls; - struct GNUNET_TESTING_PeerGroup *group; - struct GNUNET_CONFIGURATION_Handle *cfg; - GNUNET_SCHEDULER_TaskIdentifier timeout_task; -}; - - -static void -notify_running (void *cls, const struct GNUNET_PeerIdentity *id, - const struct GNUNET_CONFIGURATION_Handle *cfg, - struct GNUNET_TESTING_Daemon *d, const char *emsg) +/** + * Generate test data for publishing test. + * + * @param cls pointer to uint32_t with publishing seed + * @param offset offset to generate data for + * @param max maximum number of bytes to generate + * @param buf where to write generated data + * @param emsg where to store error message (unused) + * @return number of bytes written to buf + */ +static size_t +file_generator (void *cls, + uint64_t offset, + size_t max, + void *buf, + char **emsg) { - struct StartContext *sctx = cls; - unsigned int i; + uint32_t *publish_seed = cls; + uint64_t pos; + uint8_t *cbuf = buf; + int mod; if (emsg != NULL) + *emsg = NULL; + if (buf == NULL) + return 0; + for (pos = 0; pos < 8; pos++) + cbuf[pos] = (uint8_t) (offset >> pos * 8); + for (pos = 8; pos < max; pos++) { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("Failed to start daemon: %s\n"), - emsg); - return; - } - i = 0; - while (i < sctx->total) - { - if (GNUNET_TESTING_daemon_get (sctx->group, i) == d) - break; - i++; - } - GNUNET_assert (i < sctx->total); - GNUNET_assert (sctx->have < sctx->total); - GNUNET_assert (sctx->daemons[i]->cfg == NULL); - sctx->daemons[i]->cfg = GNUNET_CONFIGURATION_dup (cfg); - sctx->daemons[i]->group = sctx->group; - sctx->daemons[i]->daemon = d; - sctx->daemons[i]->id = *id; - sctx->have++; - if (sctx->have == sctx->total) - { - GNUNET_SCHEDULER_add_continuation (sctx->cont, sctx->cont_cls, - GNUNET_SCHEDULER_REASON_PREREQ_DONE); - sctx->daemons[0]->gcfg = sctx->cfg; - GNUNET_SCHEDULER_cancel (sctx->timeout_task); - for (i = 0; i < sctx->total; i++) - { - sctx->daemons[i]->fs = - GNUNET_FS_start (sctx->daemons[i]->cfg, "", &progress_cb, - sctx->daemons[i], GNUNET_FS_FLAGS_NONE, - GNUNET_FS_OPTIONS_END); - } - GNUNET_free (sctx); + mod = (255 - (offset / 1024 / 32)); + if (mod == 0) + mod = 1; + cbuf[pos] = (uint8_t) ((offset * (*publish_seed)) % mod); } + return max; } -static void -start_timeout (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +/** + * Connect adapter for publishing operation. + * + * @param cls the 'struct TestPublishOperation' + * @param cfg configuration of the peer to connect to; will be available until + * GNUNET_TESTBED_operation_done() is called on the operation returned + * from GNUNET_TESTBED_service_connect() + * @return service handle to return in 'op_result', NULL on error + */ +static void * +publish_connect_adapter (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg) { - struct StartContext *sctx = cls; - unsigned int i; - - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "Timeout while trying to start daemons\n"); - GNUNET_TESTING_daemons_stop (sctx->group, - GNUNET_TIME_relative_multiply - (GNUNET_TIME_UNIT_SECONDS, 30), - &shutdown_callback, NULL); - for (i = 0; i < sctx->total; i++) - { - if (i < sctx->have) - GNUNET_CONFIGURATION_destroy (sctx->daemons[i]->cfg); - GNUNET_free (sctx->daemons[i]); - sctx->daemons[i] = NULL; - } - GNUNET_CONFIGURATION_destroy (sctx->cfg); - GNUNET_SCHEDULER_add_continuation (sctx->cont, sctx->cont_cls, - GNUNET_SCHEDULER_REASON_TIMEOUT); - GNUNET_free (sctx); + struct TestPublishOperation *po = cls; + + return GNUNET_FS_start (cfg, + "fs-test-publish", + &publish_progress_cb, po, + GNUNET_FS_FLAGS_NONE, + GNUNET_FS_OPTIONS_END); } /** - * Start daemons for testing. - * - * @param template_cfg_file configuration template to use - * @param timeout if this operation cannot be completed within the - * given period, call the continuation with an error code - * @param total number of daemons to start - * @param daemons array of 'total' entries to be initialized - * (array must already be allocated, will be filled) - * @param cont function to call when done - * @param cont_cls closure for cont + * Adapter function called to destroy connection to file-sharing service. + * + * @param cls the 'struct GNUNET_FS_Handle' + * @param op_result unused (different for publish/download!) */ -void -GNUNET_FS_TEST_daemons_start (const char *template_cfg_file, - struct GNUNET_TIME_Relative timeout, - unsigned int total, - struct GNUNET_FS_TestDaemon **daemons, - GNUNET_SCHEDULER_Task cont, void *cont_cls) +static void +fs_disconnect_adapter (void *cls, + void *op_result) { - struct StartContext *sctx; - unsigned int i; - - GNUNET_assert (total > 0); - sctx = GNUNET_malloc (sizeof (struct StartContext)); - sctx->daemons = daemons; - sctx->total = total; - sctx->cont = cont; - sctx->cont_cls = cont_cls; - sctx->cfg = GNUNET_CONFIGURATION_create (); - if (GNUNET_OK != GNUNET_CONFIGURATION_load (sctx->cfg, template_cfg_file)) - { - GNUNET_break (0); - GNUNET_CONFIGURATION_destroy (sctx->cfg); - GNUNET_free (sctx); - GNUNET_SCHEDULER_add_continuation (cont, cont_cls, - GNUNET_SCHEDULER_REASON_TIMEOUT); - return; - } - for (i = 0; i < total; i++) - daemons[i] = GNUNET_malloc (sizeof (struct GNUNET_FS_TestDaemon)); - sctx->group = GNUNET_TESTING_daemons_start (sctx->cfg, total, total, /* Outstanding connections */ - total, /* Outstanding ssh connections */ - timeout, NULL, NULL, - ¬ify_running, sctx, NULL, NULL, - NULL); - sctx->timeout_task = - GNUNET_SCHEDULER_add_delayed (timeout, &start_timeout, sctx); -} + struct GNUNET_FS_Handle *fs = op_result; - -struct GNUNET_FS_TEST_ConnectContext -{ - GNUNET_SCHEDULER_Task cont; - void *cont_cls; - struct GNUNET_TESTING_ConnectContext *cc; -}; + GNUNET_FS_stop (fs); +} /** - * Prototype of a function that will be called whenever - * two daemons are connected by the testing library. + * Callback to be called when testbed has connected to the fs service * - * @param cls closure - * @param first peer id for first daemon - * @param second peer id for the second daemon - * @param distance distance between the connected peers - * @param first_cfg config for the first daemon - * @param second_cfg config for the second daemon - * @param first_daemon handle for the first daemon - * @param second_daemon handle for the second daemon - * @param emsg error message (NULL on success) + * @param cls the 'struct TestPublishOperation' + * @param op the operation that has been finished + * @param ca_result the 'struct GNUNET_FS_Handle ' (NULL on error) + * @param emsg error message in case the operation has failed; will be NULL if + * operation has executed successfully. */ static void -notify_connection (void *cls, const struct GNUNET_PeerIdentity *first, - const struct GNUNET_PeerIdentity *second, uint32_t distance, - const struct GNUNET_CONFIGURATION_Handle *first_cfg, - const struct GNUNET_CONFIGURATION_Handle *second_cfg, - struct GNUNET_TESTING_Daemon *first_daemon, - struct GNUNET_TESTING_Daemon *second_daemon, - const char *emsg) +publish_fs_connect_complete_cb (void *cls, + struct GNUNET_TESTBED_Operation *op, + void *ca_result, + const char *emsg) { - struct GNUNET_FS_TEST_ConnectContext *cc = cls; + struct TestPublishOperation *po = cls; + struct GNUNET_FS_FileInformation *fi; + struct GNUNET_DISK_FileHandle *fh; + char *em; + uint64_t off; + char buf[DBLOCK_SIZE]; + size_t bsize; + struct GNUNET_FS_BlockOptions bo; - cc->cc = NULL; - if (emsg != NULL) - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Failed to connect peers: %s\n", - emsg); - GNUNET_SCHEDULER_add_continuation (cc->cont, cc->cont_cls, - (emsg != - NULL) ? GNUNET_SCHEDULER_REASON_TIMEOUT : - GNUNET_SCHEDULER_REASON_PREREQ_DONE); - GNUNET_free (cc); + if (NULL == ca_result) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Failed to connect to FS for publishing: %s\n", emsg); + po->publish_cont (po->publish_cont_cls, + NULL, NULL); + GNUNET_TESTBED_operation_done (po->fs_op); + GNUNET_free (po); + return; + } + po->fs = ca_result; + + bo.expiration_time = GNUNET_TIME_relative_to_absolute (CONTENT_LIFETIME); + bo.anonymity_level = po->anonymity; + bo.content_priority = 42; + bo.replication_level = 1; + if (GNUNET_YES == po->do_index) + { + po->publish_tmp_file = GNUNET_DISK_mktemp ("fs-test-publish-index"); + GNUNET_assert (po->publish_tmp_file != NULL); + fh = GNUNET_DISK_file_open (po->publish_tmp_file, + GNUNET_DISK_OPEN_WRITE | + GNUNET_DISK_OPEN_CREATE, + GNUNET_DISK_PERM_USER_READ | + GNUNET_DISK_PERM_USER_WRITE); + GNUNET_assert (NULL != fh); + off = 0; + while (off < po->size) + { + bsize = GNUNET_MIN (sizeof (buf), po->size - off); + emsg = NULL; + GNUNET_assert (bsize == file_generator (&po->publish_seed, off, bsize, buf, &em)); + GNUNET_assert (em == NULL); + GNUNET_assert (bsize == GNUNET_DISK_file_write (fh, buf, bsize)); + off += bsize; + } + GNUNET_assert (GNUNET_OK == GNUNET_DISK_file_close (fh)); + fi = GNUNET_FS_file_information_create_from_file (po->fs, po, + po->publish_tmp_file, + NULL, NULL, po->do_index, + &bo); + } + else + { + fi = GNUNET_FS_file_information_create_from_reader (po->fs, po, + po->size, + &file_generator, &po->publish_seed, + NULL, NULL, + po->do_index, &bo); + } + po->publish_context = + GNUNET_FS_publish_start (po->fs, fi, NULL, NULL, NULL, + GNUNET_FS_PUBLISH_OPTION_NONE); } /** - * Connect two daemons for testing. + * Publish a file at the given peer. * - * @param daemon1 first daemon to connect - * @param daemon2 second first daemon to connect + * @param peer where to publish * @param timeout if this operation cannot be completed within the * given period, call the continuation with an error code + * @param anonymity option for publication + * @param do_index GNUNET_YES for index, GNUNET_NO for insertion, + * GNUNET_SYSERR for simulation + * @param size size of the file to publish + * @param seed seed to use for file generation + * @param verbose how verbose to be in reporting * @param cont function to call when done * @param cont_cls closure for cont */ -struct GNUNET_FS_TEST_ConnectContext * -GNUNET_FS_TEST_daemons_connect (struct GNUNET_FS_TestDaemon *daemon1, - struct GNUNET_FS_TestDaemon *daemon2, - struct GNUNET_TIME_Relative timeout, - GNUNET_SCHEDULER_Task cont, void *cont_cls) +void +GNUNET_FS_TEST_publish (struct GNUNET_TESTBED_Peer *peer, + struct GNUNET_TIME_Relative timeout, uint32_t anonymity, + int do_index, uint64_t size, uint32_t seed, + unsigned int verbose, + GNUNET_FS_TEST_UriContinuation cont, void *cont_cls) { - struct GNUNET_FS_TEST_ConnectContext *ncc; - - ncc = GNUNET_malloc (sizeof (struct GNUNET_FS_TEST_ConnectContext)); - ncc->cont = cont; - ncc->cont_cls = cont_cls; - ncc->cc = - GNUNET_TESTING_daemons_connect (daemon1->daemon, daemon2->daemon, timeout, - CONNECT_ATTEMPTS, GNUNET_YES, - ¬ify_connection, ncc); - return ncc; + struct TestPublishOperation *po; + + po = GNUNET_malloc (sizeof (struct TestPublishOperation)); + po->publish_cont = cont; + po->publish_cont_cls = cont_cls; + po->publish_seed = seed; + po->anonymity = anonymity; + po->size = size; + po->verbose = verbose; + po->do_index = do_index; + po->fs_op = GNUNET_TESTBED_service_connect (po, + peer, + "fs", + &publish_fs_connect_complete_cb, + po, + &publish_connect_adapter, + &fs_disconnect_adapter, + po); + po->publish_timeout_task = + GNUNET_SCHEDULER_add_delayed (timeout, &publish_timeout, po); } -/** - * Cancel connect operation. - * - * @param cc operation to cancel - */ -void -GNUNET_FS_TEST_daemons_connect_cancel (struct GNUNET_FS_TEST_ConnectContext *cc) -{ - GNUNET_TESTING_daemons_connect_cancel (cc->cc); - GNUNET_free (cc); -} +/* ************************** download ************************ */ /** - * Obtain peer configuration used for testing. + * Task scheduled to run when download operation times out. * - * @param daemons array with the daemons - * @param off which configuration to get - * @return peer configuration + * @param cls the download operation context + * @param tc scheduler context (unused) */ -const struct GNUNET_CONFIGURATION_Handle * -GNUNET_FS_TEST_get_configuration (struct GNUNET_FS_TestDaemon **daemons, - unsigned int off) +static void +download_timeout (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { - return daemons[off]->cfg; -} + struct TestDownloadOperation *dop = cls; -/** - * Obtain peer group used for testing. - * - * @param daemons array with the daemons (must contain at least one) - * @return peer group - */ -struct GNUNET_TESTING_PeerGroup * -GNUNET_FS_TEST_get_group (struct GNUNET_FS_TestDaemon **daemons) -{ - return daemons[0]->group; + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Timeout while trying to download file\n"); + dop->download_timeout_task = GNUNET_SCHEDULER_NO_TASK; + GNUNET_FS_download_stop (dop->download_context, GNUNET_YES); + GNUNET_SCHEDULER_add_continuation (dop->download_cont, + dop->download_cont_cls, + GNUNET_SCHEDULER_REASON_TIMEOUT); + if (NULL == dop->fs) + GNUNET_TESTBED_operation_done (dop->fs_op); + else + GNUNET_TESTBED_operation_done (dop->fs_op); + GNUNET_FS_uri_destroy (dop->uri); + GNUNET_free (dop); } /** - * Stop daemons used for testing. + * Task scheduled to report on the completion of our download operation. * - * @param total number of daemons to stop - * @param daemons array with the daemons (values will be clobbered) + * @param cls the download operation context + * @param tc scheduler context (unused) */ -void -GNUNET_FS_TEST_daemons_stop (unsigned int total, - struct GNUNET_FS_TestDaemon **daemons) -{ - unsigned int i; - struct GNUNET_TESTING_PeerGroup *pg; - struct GNUNET_CONFIGURATION_Handle *gcfg; - struct GNUNET_FS_TestDaemon *daemon; - - GNUNET_assert (total > 0); - GNUNET_assert (daemons[0] != NULL); - pg = daemons[0]->group; - gcfg = daemons[0]->gcfg; - for (i = 0; i < total; i++) - { - daemon = daemons[i]; - if (daemon->download_timeout_task != GNUNET_SCHEDULER_NO_TASK) - { - GNUNET_SCHEDULER_cancel (daemon->download_timeout_task); - daemon->download_timeout_task = GNUNET_SCHEDULER_NO_TASK; - } - if (daemon->publish_timeout_task != GNUNET_SCHEDULER_NO_TASK) - { - GNUNET_SCHEDULER_cancel (daemon->publish_timeout_task); - daemon->publish_timeout_task = GNUNET_SCHEDULER_NO_TASK; - } - if (NULL != daemon->download_context) - { - GNUNET_FS_download_stop (daemon->download_context, GNUNET_YES); - daemon->download_context = NULL; - } - if (daemon->fs != NULL) - GNUNET_FS_stop (daemon->fs); - if (daemon->cfg != NULL) - GNUNET_CONFIGURATION_destroy (daemon->cfg); - if (NULL != daemon->publish_tmp_file) - { - GNUNET_break (GNUNET_OK == - GNUNET_DISK_directory_remove (daemon->publish_tmp_file)); - GNUNET_free (daemon->publish_tmp_file); - daemon->publish_tmp_file = NULL; - } - GNUNET_free (daemon); - daemons[i] = NULL; - } - GNUNET_TESTING_daemons_stop (pg, - GNUNET_TIME_relative_multiply - (GNUNET_TIME_UNIT_SECONDS, 30), - &shutdown_callback, gcfg); -} - - static void -publish_timeout (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +report_success (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) { - struct GNUNET_FS_TestDaemon *daemon = cls; - GNUNET_FS_TEST_UriContinuation cont; + struct TestDownloadOperation *dop = cls; - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "Timeout while trying to publish data\n"); - cont = daemon->publish_cont; - daemon->publish_timeout_task = GNUNET_SCHEDULER_NO_TASK; - daemon->publish_cont = NULL; - GNUNET_FS_publish_stop (daemon->publish_context); - daemon->publish_context = NULL; - cont (daemon->publish_cont_cls, NULL); + GNUNET_FS_download_stop (dop->download_context, GNUNET_YES); + GNUNET_SCHEDULER_add_continuation (dop->download_cont, + dop->download_cont_cls, + GNUNET_SCHEDULER_REASON_PREREQ_DONE); + GNUNET_TESTBED_operation_done (dop->fs_op); + GNUNET_FS_uri_destroy (dop->uri); + GNUNET_free (dop); } -static size_t -file_generator (void *cls, uint64_t offset, size_t max, void *buf, char **emsg) +/** + * Progress callback for file-sharing events while downloading. + * + * @param cls the download operation context + * @param info information about the event + */ +static void * +download_progress_cb (void *cls, const struct GNUNET_FS_ProgressInfo *info) { - struct GNUNET_FS_TestDaemon *daemon = cls; - uint64_t pos; - uint8_t *cbuf = buf; - int mod; + struct TestDownloadOperation *dop = cls; - if (emsg != NULL) - *emsg = NULL; - if (buf == NULL) - return 0; - for (pos = 0; pos < 8; pos++) - cbuf[pos] = (uint8_t) (offset >> pos * 8); - for (pos = 8; pos < max; pos++) + switch (info->status) { - mod = (255 - (offset / 1024 / 32)); - if (mod == 0) - mod = 1; - cbuf[pos] = (uint8_t) ((offset * daemon->publish_seed) % mod); + case GNUNET_FS_STATUS_DOWNLOAD_PROGRESS: + if (dop->verbose) + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Download at %llu/%llu bytes\n", + (unsigned long long) info->value.download.completed, + (unsigned long long) info->value.download.size); + break; + case GNUNET_FS_STATUS_DOWNLOAD_COMPLETED: + GNUNET_SCHEDULER_cancel (dop->download_timeout_task); + dop->download_timeout_task = GNUNET_SCHEDULER_NO_TASK; + GNUNET_SCHEDULER_add_continuation (&report_success, dop, + GNUNET_SCHEDULER_REASON_PREREQ_DONE); + break; + case GNUNET_FS_STATUS_DOWNLOAD_ACTIVE: + case GNUNET_FS_STATUS_DOWNLOAD_INACTIVE: + break; + /* FIXME: monitor data correctness during download progress */ + /* FIXME: do performance reports given sufficient verbosity */ + /* FIXME: advance timeout task to "immediate" on error */ + default: + break; } - return max; + return NULL; } - /** - * Publish a file at the given daemon. - * - * @param daemon where to publish - * @param timeout if this operation cannot be completed within the - * given period, call the continuation with an error code - * @param anonymity option for publication - * @param do_index GNUNET_YES for index, GNUNET_NO for insertion, - * GNUNET_SYSERR for simulation - * @param size size of the file to publish - * @param seed seed to use for file generation - * @param verbose how verbose to be in reporting - * @param cont function to call when done - * @param cont_cls closure for cont + * Connect adapter for download operation. + * + * @param cls the 'struct TestDownloadOperation' + * @param cfg configuration of the peer to connect to; will be available until + * GNUNET_TESTBED_operation_done() is called on the operation returned + * from GNUNET_TESTBED_service_connect() + * @return service handle to return in 'op_result', NULL on error */ -void -GNUNET_FS_TEST_publish (struct GNUNET_FS_TestDaemon *daemon, - struct GNUNET_TIME_Relative timeout, uint32_t anonymity, - int do_index, uint64_t size, uint32_t seed, - unsigned int verbose, - GNUNET_FS_TEST_UriContinuation cont, void *cont_cls) +static void * +download_connect_adapter (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg) { - struct GNUNET_FS_FileInformation *fi; - struct GNUNET_DISK_FileHandle *fh; - char *emsg; - uint64_t off; - char buf[DBLOCK_SIZE]; - size_t bsize; - struct GNUNET_FS_BlockOptions bo; - - GNUNET_assert (daemon->publish_cont == NULL); - daemon->publish_cont = cont; - daemon->publish_cont_cls = cont_cls; - daemon->publish_seed = seed; - daemon->verbose = verbose; - bo.expiration_time = GNUNET_TIME_relative_to_absolute (CONTENT_LIFETIME); - bo.anonymity_level = anonymity; - bo.content_priority = 42; - bo.replication_level = 1; - if (GNUNET_YES == do_index) - { - GNUNET_assert (daemon->publish_tmp_file == NULL); - daemon->publish_tmp_file = GNUNET_DISK_mktemp ("fs-test-publish-index"); - GNUNET_assert (daemon->publish_tmp_file != NULL); - fh = GNUNET_DISK_file_open (daemon->publish_tmp_file, - GNUNET_DISK_OPEN_WRITE | - GNUNET_DISK_OPEN_CREATE, - GNUNET_DISK_PERM_USER_READ | - GNUNET_DISK_PERM_USER_WRITE); - GNUNET_assert (NULL != fh); - off = 0; - while (off < size) - { - bsize = GNUNET_MIN (sizeof (buf), size - off); - emsg = NULL; - GNUNET_assert (bsize == file_generator (daemon, off, bsize, buf, &emsg)); - GNUNET_assert (emsg == NULL); - GNUNET_assert (bsize == GNUNET_DISK_file_write (fh, buf, bsize)); - off += bsize; - } - GNUNET_assert (GNUNET_OK == GNUNET_DISK_file_close (fh)); - fi = GNUNET_FS_file_information_create_from_file (daemon->fs, daemon, - daemon->publish_tmp_file, - NULL, NULL, do_index, - &bo); - } - else - { - fi = GNUNET_FS_file_information_create_from_reader (daemon->fs, daemon, - size, &file_generator, - daemon, NULL, NULL, - do_index, &bo); - } - daemon->publish_context = - GNUNET_FS_publish_start (daemon->fs, fi, NULL, NULL, NULL, - GNUNET_FS_PUBLISH_OPTION_NONE); - daemon->publish_timeout_task = - GNUNET_SCHEDULER_add_delayed (timeout, &publish_timeout, daemon); + struct TestPublishOperation *po = cls; + + return GNUNET_FS_start (cfg, + "fs-test-download", + &download_progress_cb, po, + GNUNET_FS_FLAGS_NONE, + GNUNET_FS_OPTIONS_END); } +/** + * Callback to be called when testbed has connected to the fs service + * + * @param cls the 'struct TestPublishOperation' + * @param op the operation that has been finished + * @param ca_result the 'struct GNUNET_FS_Handle ' (NULL on error) + * @param emsg error message in case the operation has failed; will be NULL if + * operation has executed successfully. + */ static void -download_timeout (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +download_fs_connect_complete_cb (void *cls, + struct GNUNET_TESTBED_Operation *op, + void *ca_result, + const char *emsg) { - struct GNUNET_FS_TestDaemon *daemon = cls; - - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "Timeout while trying to download file\n"); - daemon->download_timeout_task = GNUNET_SCHEDULER_NO_TASK; - GNUNET_FS_download_stop (daemon->download_context, GNUNET_YES); - daemon->download_context = NULL; - GNUNET_SCHEDULER_add_continuation (daemon->download_cont, - daemon->download_cont_cls, - GNUNET_SCHEDULER_REASON_TIMEOUT); - daemon->download_cont = NULL; + struct TestDownloadOperation *dop = cls; + + dop->fs = ca_result; + GNUNET_assert (NULL != dop->fs); + dop->download_context = + GNUNET_FS_download_start (dop->fs, dop->uri, NULL, NULL, NULL, 0, dop->size, + dop->anonymity, GNUNET_FS_DOWNLOAD_OPTION_NONE, + NULL, NULL); } /** * Perform test download. * - * @param daemon which peer to download from + * @param peer which peer to download from * @param timeout if this operation cannot be completed within the * given period, call the continuation with an error code * @param anonymity option for download @@ -706,26 +624,34 @@ download_timeout (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) * @param cont_cls closure for cont */ void -GNUNET_FS_TEST_download (struct GNUNET_FS_TestDaemon *daemon, +GNUNET_FS_TEST_download (struct GNUNET_TESTBED_Peer *peer, struct GNUNET_TIME_Relative timeout, uint32_t anonymity, uint32_t seed, const struct GNUNET_FS_Uri *uri, unsigned int verbose, GNUNET_SCHEDULER_Task cont, void *cont_cls) { - uint64_t size; - - GNUNET_assert (daemon->download_cont == NULL); - size = GNUNET_FS_uri_chk_get_file_size (uri); - daemon->verbose = verbose; - daemon->download_cont = cont; - daemon->download_cont_cls = cont_cls; - daemon->download_seed = seed; - daemon->download_context = - GNUNET_FS_download_start (daemon->fs, uri, NULL, NULL, NULL, 0, size, - anonymity, GNUNET_FS_DOWNLOAD_OPTION_NONE, NULL, - NULL); - daemon->download_timeout_task = - GNUNET_SCHEDULER_add_delayed (timeout, &download_timeout, daemon); + struct TestDownloadOperation *dop; + + dop = GNUNET_malloc (sizeof (struct TestDownloadOperation)); + dop->uri = GNUNET_FS_uri_dup (uri); + dop->size = GNUNET_FS_uri_chk_get_file_size (uri); + dop->verbose = verbose; + dop->anonymity = anonymity; + dop->download_cont = cont; + dop->download_cont_cls = cont_cls; + dop->download_seed = seed; + + dop->fs_op = GNUNET_TESTBED_service_connect (dop, + peer, + "fs", + &download_fs_connect_complete_cb, + dop, + &download_connect_adapter, + &fs_disconnect_adapter, + dop); + dop->download_timeout_task = + GNUNET_SCHEDULER_add_delayed (timeout, &download_timeout, dop); } -/* end of test_fs_lib.c */ + +/* end of fs_test_lib.c */ diff --git a/src/fs/fs_test_lib.h b/src/fs/fs_test_lib.h index 81125ca..679e074 100644 --- a/src/fs/fs_test_lib.h +++ b/src/fs/fs_test_lib.h @@ -1,6 +1,6 @@ /* This file is part of GNUnet. - (C) 2010 Christian Grothoff (and other contributing authors) + (C) 2010, 2012 Christian Grothoff (and other contributing authors) GNUnet is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published @@ -20,8 +20,8 @@ /** * @file fs/fs_test_lib.h - * @brief library routines for testing FS publishing and downloading - * with multiple peers; this code is limited to flat files + * @brief library routines for testing FS publishing and downloading; + * this code is limited to flat files * and no keywords (those functions can be tested with * single-peer setups; this is for testing routing). * @author Christian Grothoff @@ -31,97 +31,7 @@ #include "gnunet_util_lib.h" #include "gnunet_fs_service.h" - -/** - * Handle for a daemon started for testing FS. - */ -struct GNUNET_FS_TestDaemon; - - -/** - * Start daemons for testing. - * - * @param template_cfg_file configuration template to use - * @param timeout if this operation cannot be completed within the - * given period, call the continuation with an error code - * @param total number of daemons to start - * @param daemons array of 'total' entries to be initialized - * (array must already be allocated, will be filled) - * @param cont function to call when done; note that if 'cont' - * is called with reason "TIMEOUT", then starting the - * daemons has failed and the client MUST NOT call - * 'GNUNET_FS_TEST_daemons_stop'! - * @param cont_cls closure for cont - */ -void -GNUNET_FS_TEST_daemons_start (const char *template_cfg_file, - struct GNUNET_TIME_Relative timeout, - unsigned int total, - struct GNUNET_FS_TestDaemon **daemons, - GNUNET_SCHEDULER_Task cont, void *cont_cls); - - -struct GNUNET_FS_TEST_ConnectContext; - - -/** - * Connect two daemons for testing. - * - * @param daemon1 first daemon to connect - * @param daemon2 second first daemon to connect - * @param timeout if this operation cannot be completed within the - * given period, call the continuation with an error code - * @param cont function to call when done - * @param cont_cls closure for cont - */ -struct GNUNET_FS_TEST_ConnectContext * -GNUNET_FS_TEST_daemons_connect (struct GNUNET_FS_TestDaemon *daemon1, - struct GNUNET_FS_TestDaemon *daemon2, - struct GNUNET_TIME_Relative timeout, - GNUNET_SCHEDULER_Task cont, void *cont_cls); - - -/** - * Cancel connect operation. - * - * @param cc operation to cancel - */ -void -GNUNET_FS_TEST_daemons_connect_cancel (struct GNUNET_FS_TEST_ConnectContext - *cc); - - -/** - * Obtain peer group used for testing. - * - * @param daemons array with the daemons (must contain at least one) - * @return peer group - */ -struct GNUNET_TESTING_PeerGroup * -GNUNET_FS_TEST_get_group (struct GNUNET_FS_TestDaemon **daemons); - - - -/** - * Obtain peer configuration used for testing. - * - * @param daemons array with the daemons - * @param off which configuration to get - * @return peer configuration - */ -const struct GNUNET_CONFIGURATION_Handle * -GNUNET_FS_TEST_get_configuration (struct GNUNET_FS_TestDaemon **daemons, - unsigned int off); - -/** - * Stop daemons used for testing. - * - * @param total number of daemons to stop - * @param daemons array with the daemons (values will be clobbered) - */ -void -GNUNET_FS_TEST_daemons_stop (unsigned int total, - struct GNUNET_FS_TestDaemon **daemons); +#include "gnunet_testbed_service.h" /** @@ -129,16 +39,19 @@ GNUNET_FS_TEST_daemons_stop (unsigned int total, * * @param cls closure (user defined) * @param uri a URI, NULL for errors + * @param fn name of the file on disk to be removed upon + * completion, or NULL for inserted files (also NULL on error) */ typedef void (*GNUNET_FS_TEST_UriContinuation) (void *cls, const struct GNUNET_FS_Uri * - uri); + uri, + const char *fn); /** * Publish a file at the given daemon. * - * @param daemon where to publish + * @param peer where to publish * @param timeout if this operation cannot be completed within the * given period, call the continuation with an error code * @param anonymity option for publication @@ -151,7 +64,7 @@ typedef void (*GNUNET_FS_TEST_UriContinuation) (void *cls, * @param cont_cls closure for cont */ void -GNUNET_FS_TEST_publish (struct GNUNET_FS_TestDaemon *daemon, +GNUNET_FS_TEST_publish (struct GNUNET_TESTBED_Peer *peer, struct GNUNET_TIME_Relative timeout, uint32_t anonymity, int do_index, uint64_t size, uint32_t seed, unsigned int verbose, @@ -161,7 +74,7 @@ GNUNET_FS_TEST_publish (struct GNUNET_FS_TestDaemon *daemon, /** * Perform test download. * - * @param daemon which peer to download from + * @param peer which peer to download from * @param timeout if this operation cannot be completed within the * given period, call the continuation with an error code * @param anonymity option for download @@ -172,7 +85,7 @@ GNUNET_FS_TEST_publish (struct GNUNET_FS_TestDaemon *daemon, * @param cont_cls closure for cont */ void -GNUNET_FS_TEST_download (struct GNUNET_FS_TestDaemon *daemon, +GNUNET_FS_TEST_download (struct GNUNET_TESTBED_Peer *peer, struct GNUNET_TIME_Relative timeout, uint32_t anonymity, uint32_t seed, const struct GNUNET_FS_Uri *uri, unsigned int verbose, diff --git a/src/fs/fs_test_lib_data.conf b/src/fs/fs_test_lib_data.conf index e6c2abd..89b89aa 100644 --- a/src/fs/fs_test_lib_data.conf +++ b/src/fs/fs_test_lib_data.conf @@ -8,4 +8,10 @@ WAN_QUOTA_OUT = 3932160 [datastore] QUOTA = 2 GB +#PLUGIN = heap +# +#[fs] +#DELAY = YES +[testbed] +OVERLAY_TOPOLOGY = CLIQUE diff --git a/src/fs/fs_unindex.c b/src/fs/fs_unindex.c index 6910321..2217603 100644 --- a/src/fs/fs_unindex.c +++ b/src/fs/fs_unindex.c @@ -341,12 +341,13 @@ unindex_directory_scan_cb (void *cls, { uc->ksk_uri = GNUNET_FS_uri_dup (directory_scan_result->ksk_uri); uc->state = UNINDEX_STATE_DS_REMOVE_KBLOCKS; - uc->emsg = GNUNET_strdup (_("Failed to get KSKs from directory scan.")); GNUNET_FS_unindex_sync_ (uc); GNUNET_FS_unindex_do_remove_kblocks_ (uc); } else { + uc->emsg = GNUNET_strdup (_("Failed to get KSKs from directory scan.")); + GNUNET_FS_unindex_sync_ (uc); unindex_finish (uc); } GNUNET_FS_share_tree_free (directory_scan_result); @@ -355,11 +356,15 @@ unindex_directory_scan_cb (void *cls, GNUNET_log (GNUNET_ERROR_TYPE_WARNING, _("Internal error scanning `%s'.\n"), uc->filename); + GNUNET_FS_directory_scan_abort (uc->dscan); + uc->dscan = NULL; + uc->emsg = GNUNET_strdup (_("Failed to get KSKs from directory scan.")); + GNUNET_FS_unindex_sync_ (uc); + unindex_finish (uc); break; default: break; } - } @@ -437,7 +442,7 @@ continue_after_remove (void *cls, */ static void process_kblock_for_unindex (void *cls, - const GNUNET_HashCode * key, + const struct GNUNET_HashCode * key, size_t size, const void *data, enum GNUNET_BLOCK_Type type, uint32_t priority, @@ -649,7 +654,7 @@ GNUNET_FS_unindex_do_remove_ (struct GNUNET_FS_UnindexContext *uc) * @param file_id computed hash, NULL on error */ void -GNUNET_FS_unindex_process_hash_ (void *cls, const GNUNET_HashCode * file_id) +GNUNET_FS_unindex_process_hash_ (void *cls, const struct GNUNET_HashCode * file_id) { struct GNUNET_FS_UnindexContext *uc = cls; diff --git a/src/fs/fs_uri.c b/src/fs/fs_uri.c index 0c2d64c..fa6d411 100644 --- a/src/fs/fs_uri.c +++ b/src/fs/fs_uri.c @@ -98,7 +98,7 @@ * @param key wherer to store the unique key */ void -GNUNET_FS_uri_to_key (const struct GNUNET_FS_Uri *uri, GNUNET_HashCode * key) +GNUNET_FS_uri_to_key (const struct GNUNET_FS_Uri *uri, struct GNUNET_HashCode * key) { switch (uri->type) { @@ -121,7 +121,7 @@ GNUNET_FS_uri_to_key (const struct GNUNET_FS_Uri *uri, GNUNET_HashCode * key) key); break; default: - memset (key, 0, sizeof (GNUNET_HashCode)); + memset (key, 0, sizeof (struct GNUNET_HashCode)); break; } } @@ -217,7 +217,8 @@ percent_decode_keyword (const char *in, char **emsg) if (1 != SSCANF (&out[rpos + 1], "%2X", &hx)) { GNUNET_free (out); - *emsg = GNUNET_strdup (_("`%' must be followed by HEX number")); + *emsg = GNUNET_strdup (_(/* xgettext:no-c-format */ + "`%' must be followed by HEX number")); return NULL; } rpos += 3; @@ -355,7 +356,7 @@ static struct GNUNET_FS_Uri * uri_sks_parse (const char *s, char **emsg) { struct GNUNET_FS_Uri *ret; - GNUNET_HashCode namespace; + struct GNUNET_HashCode ns; char *identifier; unsigned int pos; size_t slen; @@ -374,7 +375,7 @@ uri_sks_parse (const char *s, char **emsg) } memcpy (enc, &s[pos], sizeof (struct GNUNET_CRYPTO_HashAsciiEncoded)); enc[sizeof (struct GNUNET_CRYPTO_HashAsciiEncoded) - 1] = '\0'; - if (GNUNET_OK != GNUNET_CRYPTO_hash_from_string (enc, &namespace)) + if (GNUNET_OK != GNUNET_CRYPTO_hash_from_string (enc, &ns)) { *emsg = GNUNET_strdup (_("Malformed SKS URI")); return NULL; @@ -383,7 +384,7 @@ uri_sks_parse (const char *s, char **emsg) GNUNET_strdup (&s[pos + sizeof (struct GNUNET_CRYPTO_HashAsciiEncoded)]); ret = GNUNET_malloc (sizeof (struct GNUNET_FS_Uri)); ret->type = sks; - ret->data.sks.namespace = namespace; + ret->data.sks.ns = ns; ret->data.sks.identifier = identifier; return ret; } @@ -903,8 +904,7 @@ GNUNET_FS_uri_loc_create (const struct GNUNET_FS_Uri *baseUri, _("Lacking key configuration settings.\n")); return NULL; } - my_private_key = GNUNET_CRYPTO_rsa_key_create_from_file (keyfile); - if (my_private_key == NULL) + if (NULL == (my_private_key = GNUNET_CRYPTO_rsa_key_create_from_file (keyfile))) { GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("Could not access hostkey file `%s'.\n"), keyfile); @@ -949,7 +949,7 @@ GNUNET_FS_uri_sks_create (struct GNUNET_FS_Namespace *ns, const char *id, ns_uri = GNUNET_malloc (sizeof (struct GNUNET_FS_Uri)); ns_uri->type = sks; GNUNET_CRYPTO_rsa_key_get_public (ns->key, &pk); - GNUNET_CRYPTO_hash (&pk, sizeof (pk), &ns_uri->data.sks.namespace); + GNUNET_CRYPTO_hash (&pk, sizeof (pk), &ns_uri->data.sks.ns); ns_uri->data.sks.identifier = GNUNET_strdup (id); return ns_uri; } @@ -963,13 +963,13 @@ GNUNET_FS_uri_sks_create (struct GNUNET_FS_Namespace *ns, const char *id, * @return an FS URI for the given namespace and identifier */ struct GNUNET_FS_Uri * -GNUNET_FS_uri_sks_create_from_nsid (GNUNET_HashCode * nsid, const char *id) +GNUNET_FS_uri_sks_create_from_nsid (struct GNUNET_HashCode * nsid, const char *id) { struct GNUNET_FS_Uri *ns_uri; ns_uri = GNUNET_malloc (sizeof (struct GNUNET_FS_Uri)); ns_uri->type = sks; - ns_uri->data.sks.namespace = *nsid; + ns_uri->data.sks.ns = *nsid; ns_uri->data.sks.identifier = GNUNET_strdup (id); return ns_uri; } @@ -1272,8 +1272,8 @@ GNUNET_FS_uri_test_equal (const struct GNUNET_FS_Uri *u1, return GNUNET_NO; case sks: if ((0 == - memcmp (&u1->data.sks.namespace, &u2->data.sks.namespace, - sizeof (GNUNET_HashCode))) && + memcmp (&u1->data.sks.ns, &u2->data.sks.ns, + sizeof (struct GNUNET_HashCode))) && (0 == strcmp (u1->data.sks.identifier, u2->data.sks.identifier))) return GNUNET_YES; @@ -1334,14 +1334,14 @@ GNUNET_FS_uri_test_sks (const struct GNUNET_FS_Uri *uri) */ int GNUNET_FS_uri_sks_get_namespace (const struct GNUNET_FS_Uri *uri, - GNUNET_HashCode * nsid) + struct GNUNET_HashCode * nsid) { if (!GNUNET_FS_uri_test_sks (uri)) { GNUNET_break (0); return GNUNET_SYSERR; } - *nsid = uri->data.sks.namespace; + *nsid = uri->data.sks.ns; return GNUNET_OK; } @@ -1382,9 +1382,9 @@ GNUNET_FS_uri_sks_to_string_fancy (struct GNUNET_CONFIGURATION_Handle *cfg, if (uri->type != sks) return NULL; - (void) GNUNET_PSEUDONYM_get_info (cfg, &uri->data.sks.namespace, + (void) GNUNET_PSEUDONYM_get_info (cfg, &uri->data.sks.ns, NULL, NULL, &name, NULL); - unique_name = GNUNET_PSEUDONYM_name_uniquify (cfg, &uri->data.sks.namespace, name, NULL); + unique_name = GNUNET_PSEUDONYM_name_uniquify (cfg, &uri->data.sks.ns, name, NULL); GNUNET_free (name); GNUNET_asprintf (&ret, "%s: %s", unique_name, uri->data.sks.identifier); GNUNET_free (unique_name); @@ -1665,7 +1665,7 @@ get_keywords_from_parens (const char *s, char **array, int index) /** * Where to break up keywords */ -#define TOKENS "_. /-!?#&+@\"\'\\;:," +#define TOKENS "_. /-!?#&+@\"\'\\;:,()[]{}$<>|" /** * Break the filename up by TOKENS to make @@ -1907,7 +1907,7 @@ uri_ksk_to_string (const struct GNUNET_FS_Uri *uri) continue; /* skip leading space */ if (needs_percent (keyword[j])) { - sprintf (&ret[wpos], "%%%02X", keyword[j]); + sprintf (&ret[wpos], "%%%02X", (unsigned char) keyword[j]); wpos += 3; } else @@ -1931,18 +1931,18 @@ uri_ksk_to_string (const struct GNUNET_FS_Uri *uri) static char * uri_sks_to_string (const struct GNUNET_FS_Uri *uri) { - const GNUNET_HashCode *namespace; + const struct GNUNET_HashCode *ns; const char *identifier; char *ret; - struct GNUNET_CRYPTO_HashAsciiEncoded ns; + struct GNUNET_CRYPTO_HashAsciiEncoded nsasc; if (uri->type != sks) return NULL; - namespace = &uri->data.sks.namespace; + ns = &uri->data.sks.ns; identifier = uri->data.sks.identifier; - GNUNET_CRYPTO_hash_to_enc (namespace, &ns); + GNUNET_CRYPTO_hash_to_enc (ns, &nsasc); GNUNET_asprintf (&ret, "%s%s%s/%s", GNUNET_FS_URI_PREFIX, - GNUNET_FS_URI_SKS_INFIX, (const char *) &ns, identifier); + GNUNET_FS_URI_SKS_INFIX, (const char *) &nsasc, identifier); return ret; } diff --git a/src/fs/gnunet-auto-share.c b/src/fs/gnunet-auto-share.c new file mode 100644 index 0000000..86cab55 --- /dev/null +++ b/src/fs/gnunet-auto-share.c @@ -0,0 +1,795 @@ +/* + This file is part of GNUnet. + (C) 2001--2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ +/** + * @file fs/gnunet-auto-share.c + * @brief automatically publish files on GNUnet + * @author Christian Grothoff + * + * TODO: + * - support loading meta data / keywords from resource file + * - add stability timer (a la buildbot) + */ +#include "platform.h" +#include "gnunet_util_lib.h" + +#define MIN_FREQUENCY GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_HOURS, 4) + +#define MAX_FREQUENCY GNUNET_TIME_UNIT_MINUTES + + +/** + * Item in our work queue (or in the set of files/directories + * we have successfully published). + */ +struct WorkItem +{ + + /** + * PENDING Work is kept in a linked list. + */ + struct WorkItem *prev; + + /** + * PENDING Work is kept in a linked list. + */ + struct WorkItem *next; + + /** + * Filename of the work item. + */ + char *filename; + + /** + * Unique identity for this work item (used to detect + * if we need to do the work again). + */ + struct GNUNET_HashCode id; +}; + + +/** + * Global return value from 'main'. + */ +static int ret; + +/** + * Are we running 'verbosely'? + */ +static int verbose; + +/** + * Configuration to use. + */ +static const struct GNUNET_CONFIGURATION_Handle *cfg; + +/** + * Name of the configuration file. + */ +static char *cfg_filename; + +/** + * Disable extractor option to use for publishing. + */ +static int disable_extractor; + +/** + * Disable creation time option to use for publishing. + */ +static int do_disable_creation_time; + +/** + * Handle for the 'shutdown' task. + */ +static GNUNET_SCHEDULER_TaskIdentifier kill_task; + +/** + * Handle for the main task that does scanning and working. + */ +static GNUNET_SCHEDULER_TaskIdentifier run_task; + +/** + * Anonymity level option to use for publishing. + */ +static unsigned int anonymity_level = 1; + +/** + * Content priority option to use for publishing. + */ +static unsigned int content_priority = 365; + +/** + * Replication level option to use for publishing. + */ +static unsigned int replication_level = 1; + +/** + * Top-level directory we monitor to auto-publish. + */ +static const char *dir_name; + +/** + * Head of linked list of files still to publish. + */ +static struct WorkItem *work_head; + +/** + * Tail of linked list of files still to publish. + */ +static struct WorkItem *work_tail; + +/** + * Map from the hash of the filename (!) to a 'struct WorkItem' + * that was finished. + */ +static struct GNUNET_CONTAINER_MultiHashMap *work_finished; + +/** + * Set to GNUNET_YES if we are shutting down. + */ +static int do_shutdown; + +/** + * Start time of the current round; used to determine how long + * one iteration takes (which influences how fast we schedule + * the next one). + */ +static struct GNUNET_TIME_Absolute start_time; + +/** + * Pipe used to communicate 'gnunet-publish' completion (SIGCHLD) via signal. + */ +static struct GNUNET_DISK_PipeHandle *sigpipe; + +/** + * Handle to the 'gnunet-publish' process that we executed. + */ +static struct GNUNET_OS_Process *publish_proc; + + +/** + * Compute the name of the state database file we will use. + */ +static char * +get_state_file () +{ + char *ret; + + GNUNET_asprintf (&ret, + "%s%s.auto-share", + dir_name, + (DIR_SEPARATOR == dir_name[strlen(dir_name)-1]) ? "" : DIR_SEPARATOR_STR); + return ret; +} + + +/** + * Load the set of 'work_finished' items from disk. + */ +static void +load_state () +{ + char *fn; + struct GNUNET_BIO_ReadHandle *rh; + uint32_t n; + struct GNUNET_HashCode id; + struct WorkItem *wi; + char *emsg; + + emsg = NULL; + fn = get_state_file (); + rh = GNUNET_BIO_read_open (fn); + GNUNET_free (fn); + if (NULL == rh) + return; + fn = NULL; + if (GNUNET_OK != GNUNET_BIO_read_int32 (rh, &n)) + goto error; + while (n-- > 0) + { + if ( (GNUNET_OK != + GNUNET_BIO_read_string (rh, "filename", &fn, 1024)) || + (GNUNET_OK != + GNUNET_BIO_read (rh, "id", &id, sizeof (struct GNUNET_HashCode))) ) + goto error; + wi = GNUNET_malloc (sizeof (struct WorkItem)); + wi->id = id; + wi->filename = fn; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Loaded serialization ID for `%s' is `%s'\n", + wi->filename, + GNUNET_h2s (&id)); + fn = NULL; + GNUNET_CRYPTO_hash (wi->filename, + strlen (wi->filename), + &id); + GNUNET_CONTAINER_multihashmap_put (work_finished, + &id, + wi, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY); + } + if (GNUNET_OK == + GNUNET_BIO_read_close (rh, &emsg)) + return; + rh = NULL; + error: + GNUNET_free_non_null (fn); + if (NULL != rh) + (void) GNUNET_BIO_read_close (rh, &emsg); + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + _("Failed to load state: %s\n"), + emsg); + GNUNET_free_non_null (emsg); +} + + +/** + * Write work item from the work_finished map to the given write handle. + * + * @param cls the 'struct GNUNET_BIO_WriteHandle*' + * @param key key of the item in the map (unused) + * @param value the 'struct WorkItem' to write + * @return GNUNET_OK to continue to iterate (if write worked) + */ +static int +write_item (void *cls, + const struct GNUNET_HashCode *key, + void *value) +{ + struct GNUNET_BIO_WriteHandle *wh = cls; + struct WorkItem *wi = value; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Saving serialization ID of file `%s' with value `%s'\n", + wi->filename, + GNUNET_h2s (&wi->id)); + if ( (GNUNET_OK != + GNUNET_BIO_write_string (wh, wi->filename)) || + (GNUNET_OK != + GNUNET_BIO_write (wh, + &wi->id, + sizeof (struct GNUNET_HashCode))) ) + return GNUNET_SYSERR; /* write error, abort iteration */ + return GNUNET_OK; +} + + +/** + * Save the set of 'work_finished' items on disk. + */ +static void +save_state () +{ + uint32_t n; + struct GNUNET_BIO_WriteHandle *wh; + char *fn; + + n = GNUNET_CONTAINER_multihashmap_size (work_finished); + fn = get_state_file (); + wh = GNUNET_BIO_write_open (fn); + if (NULL == wh) + { + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + _("Failed to save state to file %s\n"), + fn); + GNUNET_free (fn); + return; + } + if (GNUNET_OK != + GNUNET_BIO_write_int32 (wh, n)) + { + (void) GNUNET_BIO_write_close (wh); + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + _("Failed to save state to file %s\n"), + fn); + GNUNET_free (fn); + return; + } + (void) GNUNET_CONTAINER_multihashmap_iterate (work_finished, + &write_item, + wh); + if (GNUNET_OK != GNUNET_BIO_write_close (wh)) + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + _("Failed to save state to file %s\n"), + fn); + GNUNET_free (fn); +} + + +/** + * Task run on shutdown. Serializes our current state to disk. + * + * @param cls closure, unused + * @param tc scheduler context, unused + */ +static void +do_stop_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + kill_task = GNUNET_SCHEDULER_NO_TASK; + do_shutdown = GNUNET_YES; + if (NULL != publish_proc) + { + GNUNET_OS_process_kill (publish_proc, SIGKILL); + return; + } + if (GNUNET_SCHEDULER_NO_TASK != run_task) + { + GNUNET_SCHEDULER_cancel (run_task); + run_task = GNUNET_SCHEDULER_NO_TASK; + } +} + + +/** + * Decide what the next task is (working or scanning) and schedule it. + */ +static void +schedule_next_task (void); + + +/** + * Task triggered whenever we receive a SIGCHLD (child + * process died). + * + * @param cls the 'struct WorkItem' we were working on + * @param tc context + */ +static void +maint_child_death (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct WorkItem *wi = cls; + struct GNUNET_HashCode key; + enum GNUNET_OS_ProcessStatusType type; + unsigned long code; + int ret; + char c; + const struct GNUNET_DISK_FileHandle *pr; + + + run_task = GNUNET_SCHEDULER_NO_TASK; + pr = GNUNET_DISK_pipe_handle (sigpipe, GNUNET_DISK_PIPE_END_READ); + if (0 == (tc->reason & GNUNET_SCHEDULER_REASON_READ_READY)) + { + /* shutdown scheduled us, ignore! */ + run_task = + GNUNET_SCHEDULER_add_read_file (GNUNET_TIME_UNIT_FOREVER_REL, + pr, &maint_child_death, wi); + return; + } + + ret = GNUNET_OS_process_status (publish_proc, + &type, + &code); + GNUNET_assert (GNUNET_SYSERR != ret); + if (GNUNET_NO == ret) + { + GNUNET_break (0); + GNUNET_OS_process_kill (publish_proc, SIGKILL); + type = GNUNET_OS_PROCESS_SIGNALED; + } + GNUNET_OS_process_destroy (publish_proc); + publish_proc = NULL; + /* consume the signal */ + GNUNET_break (0 < GNUNET_DISK_file_read (pr, &c, sizeof (c))); + + if (GNUNET_YES == do_shutdown) + { + GNUNET_free (wi->filename); + GNUNET_free (wi); + return; + } + if ( (GNUNET_OS_PROCESS_EXITED == type) && + (0 == code) ) + { + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + _("Publication of `%s' done\n"), + wi->filename); + GNUNET_CRYPTO_hash (wi->filename, + strlen (wi->filename), + &key); + GNUNET_CONTAINER_multihashmap_put (work_finished, + &key, + wi, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY); + } + else + { + GNUNET_CONTAINER_DLL_insert_tail (work_head, + work_tail, + wi); + } + save_state (); + schedule_next_task (); +} + + +/** + * Signal handler called for SIGCHLD. Triggers the + * respective handler by writing to the trigger pipe. + */ +static void +sighandler_child_death () +{ + static char c; + int old_errno = errno; /* back-up errno */ + + GNUNET_break (1 == + GNUNET_DISK_file_write (GNUNET_DISK_pipe_handle + (sigpipe, GNUNET_DISK_PIPE_END_WRITE), + &c, sizeof (c))); + errno = old_errno; /* restore errno */ +} + + +/** + * Function called to process work items. + * + * @param cls closure, NULL + * @param tc scheduler context (unused) + */ +static void +work (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + static char *argv[14]; + static char anon_level[20]; + static char content_prio[20]; + static char repl_level[20]; + struct WorkItem *wi; + const struct GNUNET_DISK_FileHandle *pr; + int argc; + + run_task = GNUNET_SCHEDULER_NO_TASK; + wi = work_head; + GNUNET_CONTAINER_DLL_remove (work_head, + work_tail, + wi); + argc = 0; + argv[argc++] = "gnunet-publish"; + if (verbose) + argv[argc++] = "-V"; + if (disable_extractor) + argv[argc++] = "-D"; + if (do_disable_creation_time) + argv[argc++] = "-d"; + argv[argc++] = "-c"; + argv[argc++] = cfg_filename; + GNUNET_snprintf (anon_level, sizeof (anon_level), + "%u", anonymity_level); + argv[argc++] = "-a"; + argv[argc++] = anon_level; + GNUNET_snprintf (content_prio, sizeof (content_prio), + "%u", content_priority); + argv[argc++] = "-p"; + argv[argc++] = content_prio; + GNUNET_snprintf (repl_level, sizeof (repl_level), + "%u", replication_level); + argv[argc++] = "-r"; + argv[argc++] = repl_level; + argv[argc++] = wi->filename; + argv[argc] = NULL; + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + _("Publishing `%s'\n"), + wi->filename); + publish_proc = GNUNET_OS_start_process_vap (GNUNET_YES, + 0, NULL, NULL, + "gnunet-publish", + argv); + if (NULL == publish_proc) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Failed to run `%s'\n"), + "gnunet-publish"); + GNUNET_CONTAINER_DLL_insert (work_head, + work_tail, + wi); + run_task = GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_MINUTES, + &work, + NULL); + return; + } + pr = GNUNET_DISK_pipe_handle (sigpipe, GNUNET_DISK_PIPE_END_READ); + run_task = + GNUNET_SCHEDULER_add_read_file (GNUNET_TIME_UNIT_FOREVER_REL, + pr, &maint_child_death, wi); +} + + +/** + * Recursively scan the given file/directory structure to determine + * a unique ID that represents the current state of the hierarchy. + * + * @param cls where to store the unique ID we are computing + * @param filename file to scan + * @return GNUNET_OK (always) + */ +static int +determine_id (void *cls, + const char *filename) +{ + struct GNUNET_HashCode *id = cls; + struct stat sbuf; + struct GNUNET_HashCode fx[2]; + struct GNUNET_HashCode ft; + + if (0 != STAT (filename, &sbuf)) + { + GNUNET_log_strerror_file (GNUNET_ERROR_TYPE_WARNING, "stat", filename); + return GNUNET_OK; + } + GNUNET_CRYPTO_hash (filename, strlen (filename), &fx[0]); + if (!S_ISDIR (sbuf.st_mode)) + { + uint64_t fattr[2]; + + fattr[0] = GNUNET_htonll (sbuf.st_size); + fattr[0] = GNUNET_htonll (sbuf.st_mtime); + + GNUNET_CRYPTO_hash (fattr, sizeof (fattr), &fx[1]); + } + else + { + memset (&fx[1], 1, sizeof (struct GNUNET_HashCode)); + GNUNET_DISK_directory_scan (filename, + &determine_id, + &fx[1]); + } + /* use hash here to make hierarchical structure distinct from + all files on the same level */ + GNUNET_CRYPTO_hash (fx, sizeof (fx), &ft); + /* use XOR here so that order of the files in the directory + does not matter! */ + GNUNET_CRYPTO_hash_xor (&ft, id, id); + return GNUNET_OK; +} + + +/** + * Function called with a filename (or directory name) to publish + * (if it has changed since the last time we published it). This function + * is called for the top-level files only. + * + * @param cls closure, NULL + * @param filename complete filename (absolute path) + * @return GNUNET_OK to continue to iterate, GNUNET_SYSERR during shutdown + */ +static int +add_file (void *cls, + const char *filename) +{ + struct WorkItem *wi; + struct GNUNET_HashCode key; + struct GNUNET_HashCode id; + + if (GNUNET_YES == do_shutdown) + return GNUNET_SYSERR; + if ( (NULL != strstr (filename, + "/.auto-share")) || + (NULL != strstr (filename, + "\\.auto-share")) ) + return GNUNET_OK; /* skip internal file */ + GNUNET_CRYPTO_hash (filename, + strlen (filename), + &key); + wi = GNUNET_CONTAINER_multihashmap_get (work_finished, + &key); + memset (&id, 0, sizeof (struct GNUNET_HashCode)); + determine_id (&id, filename); + if (NULL != wi) + { + if (0 == memcmp (&id, + &wi->id, + sizeof (struct GNUNET_HashCode))) + return GNUNET_OK; /* skip: we did this one already */ + /* contents changed, need to re-do the directory... */ + GNUNET_assert (GNUNET_YES == + GNUNET_CONTAINER_multihashmap_remove (work_finished, + &key, + wi)); + } + else + { + wi = GNUNET_malloc (sizeof (struct WorkItem)); + wi->filename = GNUNET_strdup (filename); + } + wi->id = id; + GNUNET_CONTAINER_DLL_insert (work_head, + work_tail, + wi); + if (GNUNET_YES == do_shutdown) + return GNUNET_SYSERR; + return GNUNET_OK; +} + + +/** + * Periodically run task to update our view of the directory to share. + * + * @param cls NULL + * @param tc scheduler context, unused + */ +static void +scan (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + run_task = GNUNET_SCHEDULER_NO_TASK; + start_time = GNUNET_TIME_absolute_get (); + (void) GNUNET_DISK_directory_scan (dir_name, + &add_file, + NULL); + schedule_next_task (); +} + + +/** + * Decide what the next task is (working or scanning) and schedule it. + */ +static void +schedule_next_task () +{ + struct GNUNET_TIME_Relative delay; + + if (GNUNET_YES == do_shutdown) + return; + if (NULL == work_head) + { + /* delay by at most 4h, at least 1s, and otherwise in between depending + on how long it took to scan */ + delay = GNUNET_TIME_absolute_get_duration (start_time); + delay = GNUNET_TIME_relative_min (MIN_FREQUENCY, + GNUNET_TIME_relative_multiply (delay, + 100)); + delay = GNUNET_TIME_relative_max (delay, + MAX_FREQUENCY); + run_task = GNUNET_SCHEDULER_add_delayed (delay, + &scan, + NULL); + } + else + { + run_task = GNUNET_SCHEDULER_add_now (&work, NULL); + } +} + + +/** + * Main function that will be run by the scheduler. + * + * @param cls closure + * @param args remaining command-line arguments + * @param cfgfile name of the configuration file used (for saving, can be NULL!) + * @param c configuration + */ +static void +run (void *cls, char *const *args, const char *cfgfile, + const struct GNUNET_CONFIGURATION_Handle *c) +{ + /* check arguments */ + if ((args[0] == NULL) || (args[1] != NULL) || + (GNUNET_YES != GNUNET_DISK_directory_test (args[0], GNUNET_YES))) + { + printf (_("You must specify one and only one directory name for automatic publication.\n")); + ret = -1; + return; + } + cfg_filename = GNUNET_strdup (cfgfile); + cfg = c; + dir_name = args[0]; + work_finished = GNUNET_CONTAINER_multihashmap_create (1024, GNUNET_NO); + load_state (); + run_task = GNUNET_SCHEDULER_add_with_priority (GNUNET_SCHEDULER_PRIORITY_IDLE, + &scan, NULL); + + kill_task = + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, &do_stop_task, + NULL); +} + + +/** + * Free memory associated with the work item from the work_finished map. + * + * @param cls NULL (unused) + * @param key key of the item in the map (unused) + * @param value the 'struct WorkItem' to free + * @return GNUNET_OK to continue to iterate + */ +static int +free_item (void *cls, + const struct GNUNET_HashCode *key, + void *value) +{ + struct WorkItem *wi = value; + + GNUNET_free (wi->filename); + GNUNET_free (wi); + return GNUNET_OK; +} + + +/** + * The main function to automatically publish content to GNUnet. + * + * @param argc number of arguments from the command line + * @param argv command line arguments + * @return 0 ok, 1 on error + */ +int +main (int argc, char *const *argv) +{ + static const struct GNUNET_GETOPT_CommandLineOption options[] = { + {'a', "anonymity", "LEVEL", + gettext_noop ("set the desired LEVEL of sender-anonymity"), + 1, &GNUNET_GETOPT_set_uint, &anonymity_level}, + {'d', "disable-creation-time", NULL, + gettext_noop + ("disable adding the creation time to the metadata of the uploaded file"), + 0, &GNUNET_GETOPT_set_one, &do_disable_creation_time}, + {'D', "disable-extractor", NULL, + gettext_noop ("do not use libextractor to add keywords or metadata"), + 0, &GNUNET_GETOPT_set_one, &disable_extractor}, + {'p', "priority", "PRIORITY", + gettext_noop ("specify the priority of the content"), + 1, &GNUNET_GETOPT_set_uint, &content_priority}, + {'r', "replication", "LEVEL", + gettext_noop ("set the desired replication LEVEL"), + 1, &GNUNET_GETOPT_set_uint, &replication_level}, + {'V', "verbose", NULL, + gettext_noop ("be verbose (print progress information)"), + 0, &GNUNET_GETOPT_set_one, &verbose}, + GNUNET_GETOPT_OPTION_END + }; + struct WorkItem *wi; + int ok; + struct GNUNET_SIGNAL_Context *shc_chld; + + if (GNUNET_OK != GNUNET_STRINGS_get_utf8_args (argc, argv, &argc, &argv)) + return 2; + sigpipe = GNUNET_DISK_pipe (GNUNET_NO, GNUNET_NO, GNUNET_NO, GNUNET_NO); + GNUNET_assert (sigpipe != NULL); + shc_chld = + GNUNET_SIGNAL_handler_install (GNUNET_SIGCHLD, &sighandler_child_death); + ok = (GNUNET_OK == + GNUNET_PROGRAM_run (argc, argv, "gnunet-auto-share [OPTIONS] FILENAME", + gettext_noop + ("Automatically publish files from a directory on GNUnet"), + options, &run, NULL)) ? ret : 1; + if (NULL != work_finished) + { + (void) GNUNET_CONTAINER_multihashmap_iterate (work_finished, + &free_item, + NULL); + GNUNET_CONTAINER_multihashmap_destroy (work_finished); + } + while (NULL != (wi = work_head)) + { + GNUNET_CONTAINER_DLL_remove (work_head, work_tail, wi); + GNUNET_free (wi->filename); + GNUNET_free (wi); + } + GNUNET_SIGNAL_handler_uninstall (shc_chld); + shc_chld = NULL; + GNUNET_DISK_pipe_close (sigpipe); + sigpipe = NULL; + GNUNET_free (cfg_filename); + cfg_filename = NULL; + GNUNET_free ((void*) argv); + return ok; +} + +/* end of gnunet-auto-share.c */ diff --git a/src/fs/gnunet-daemon-fsprofiler.c b/src/fs/gnunet-daemon-fsprofiler.c new file mode 100644 index 0000000..16a74b8 --- /dev/null +++ b/src/fs/gnunet-daemon-fsprofiler.c @@ -0,0 +1,660 @@ +/* + This file is part of GNUnet. + (C) 2012 Christian Grothoff + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @file fs/gnunet-daemon-fsprofiler.c + * @brief daemon that publishes and downloads (random) files + * @author Christian Grothoff + * + * TODO: + * - how to signal driver that we're done? + */ +#include "platform.h" +#include "gnunet_fs_service.h" +#include "gnunet_statistics_service.h" + +/** + * We use 'patterns' of the form (x,y,t) to specify desired download/publish + * activities of a peer. They are stored in a DLL. + */ +struct Pattern +{ + /** + * Kept in a DLL. + */ + struct Pattern *next; + + /** + * Kept in a DLL. + */ + struct Pattern *prev; + + /** + * Execution context for the pattern (FS-handle to the operation). + */ + void *ctx; + + /** + * Secondary execution context for the pattern (FS-handle to the operation). + */ + void *sctx; + + /** + * When did the operation start? + */ + struct GNUNET_TIME_Absolute start_time; + + /** + * With how much delay should this operation be started? + */ + struct GNUNET_TIME_Relative delay; + + /** + * Task to run the operation. + */ + GNUNET_SCHEDULER_TaskIdentifier task; + + /** + * Secondary task to run the operation. + */ + GNUNET_SCHEDULER_TaskIdentifier stask; + + /** + * X-value. + */ + unsigned long long x; + + /** + * Y-value. + */ + unsigned long long y; +}; + + +/** + * Return value from 'main'. + */ +static int global_ret; + +/** + * Configuration we use. + */ +static const struct GNUNET_CONFIGURATION_Handle *cfg; + +/** + * Handle to the statistics service. + */ +static struct GNUNET_STATISTICS_Handle *stats_handle; + +/** + * Peer's FS handle. + */ +static struct GNUNET_FS_Handle *fs_handle; + +/** + * Unique number for this peer in the testbed. + */ +static unsigned long long my_peerid; + +/** + * Desired anonymity level. + */ +static unsigned long long anonymity_level; + +/** + * Desired replication level. + */ +static unsigned long long replication_level; + +/** + * String describing which publishing operations this peer should + * perform. The format is "(SIZE,SEED,TIME)*", for example: + * "(1,5,0)(7,3,13)" means to publish a file with 1 byte and + * seed/keyword 5 immediately and another file with 7 bytes and + * seed/keyword 3 after 13 ms. + */ +static char *publish_pattern; + +/** + * Head of the DLL of publish patterns. + */ +static struct Pattern *publish_head; + +/** + * Tail of the DLL of publish patterns. + */ +static struct Pattern *publish_tail; + +/** + * String describing which download operations this peer should + * perform. The format is "(KEYWORD,SIZE,DELAY)*"; for example, + * "(1,7,3)(3,8,8)" means to download one file of 7 bytes under + * keyword "1" starting the search after 3 ms; and another one of 8 + * bytes under keyword '3' starting after 8 ms. The file size is + * used to determine which search result(s) should be used or ignored. + */ +static char *download_pattern; + +/** + * Head of the DLL of publish patterns. + */ +static struct Pattern *download_head; + +/** + * Tail of the DLL of publish patterns. + */ +static struct Pattern *download_tail; + + +/** + * Parse a pattern string and store the corresponding + * 'struct Pattern' in the given head/tail. + * + * @param head where to store the head + * @param tail where to store the tail + * @param pattern pattern to parse + * @return GNUNET_OK on success + */ +static int +parse_pattern (struct Pattern **head, + struct Pattern **tail, + const char *pattern) +{ + struct Pattern *p; + unsigned long long x; + unsigned long long y; + unsigned long long t; + + while (3 == sscanf (pattern, + "(%llu,%llu,%llu)", + &x, &y, &t)) + { + p = GNUNET_malloc (sizeof (struct Pattern)); + p->x = x; + p->y = y; + p->delay.rel_value = (uint64_t) t; + GNUNET_CONTAINER_DLL_insert (*head, *tail, p); + pattern = strstr (pattern, ")"); + GNUNET_assert (NULL != pattern); + pattern++; + } + return (0 == strlen (pattern)) ? GNUNET_OK : GNUNET_SYSERR; +} + + +/** + * Create a KSK URI from a number. + * + * @param kval the number + * @return corresponding KSK URI + */ +static struct GNUNET_FS_Uri * +make_keywords (uint64_t kval) +{ + char kw[128]; + + GNUNET_snprintf (kw, sizeof (kw), + "%llu", (unsigned long long) kval); + return GNUNET_FS_uri_ksk_create (kw, NULL); +} + + +/** + * Create a file of the given length with a deterministic amount + * of data to be published under keyword 'kval'. + * + * @param length number of bytes in the file + * @param kval keyword value and seed for the data of the file + * @param ctx context to pass to 'fi' + * @return file information handle for the file + */ +static struct GNUNET_FS_FileInformation * +make_file (uint64_t length, + uint64_t kval, + void *ctx) +{ + struct GNUNET_FS_FileInformation *fi; + struct GNUNET_FS_BlockOptions bo; + char *data; + struct GNUNET_FS_Uri *keywords; + unsigned long long i; + uint64_t xor; + + data = NULL; /* to make compilers happy */ + if ( (0 != length) && + (NULL == (data = GNUNET_malloc_large ((size_t) length))) ) + return NULL; + /* initialize data with 'unique' data only depending on 'kval' and 'size', + making sure that blocks do not repeat */ + for (i=0;itask) + GNUNET_SCHEDULER_cancel (p->task); + if (NULL != p->ctx) + GNUNET_FS_publish_stop (p->ctx); + GNUNET_CONTAINER_DLL_remove (publish_head, publish_tail, p); + GNUNET_free (p); + } + while (NULL != (p = download_head)) + { + if (GNUNET_SCHEDULER_NO_TASK != p->task) + GNUNET_SCHEDULER_cancel (p->task); + if (GNUNET_SCHEDULER_NO_TASK != p->stask) + GNUNET_SCHEDULER_cancel (p->stask); + if (NULL != p->ctx) + GNUNET_FS_download_stop (p->ctx, GNUNET_YES); + if (NULL != p->sctx) + GNUNET_FS_search_stop (p->sctx); + GNUNET_CONTAINER_DLL_remove (download_head, download_tail, p); + GNUNET_free (p); + } + if (NULL != fs_handle) + { + GNUNET_FS_stop (fs_handle); + fs_handle = NULL; + } + if (NULL != stats_handle) + { + GNUNET_STATISTICS_destroy (stats_handle, GNUNET_YES); + stats_handle = NULL; + } +} + + +/** + * Task run when a publish operation should be stopped. + * + * @param cls the 'struct Pattern' of the publish operation to stop + * @param tc unused + */ +static void +publish_stop_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct Pattern *p = cls; + + p->task = GNUNET_SCHEDULER_NO_TASK; + GNUNET_FS_publish_stop (p->ctx); +} + + +/** + * Task run when a download operation should be stopped. + * + * @param cls the 'struct Pattern' of the download operation to stop + * @param tc unused + */ +static void +download_stop_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct Pattern *p = cls; + + p->task = GNUNET_SCHEDULER_NO_TASK; + GNUNET_FS_download_stop (p->ctx, GNUNET_YES); +} + + +/** + * Task run when a download operation should be stopped. + * + * @param cls the 'struct Pattern' of the download operation to stop + * @param tc unused + */ +static void +search_stop_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct Pattern *p = cls; + + p->stask = GNUNET_SCHEDULER_NO_TASK; + GNUNET_FS_search_stop (p->sctx); +} + + +/** + * Notification of FS to a client about the progress of an + * operation. Callbacks of this type will be used for uploads, + * downloads and searches. Some of the arguments depend a bit + * in their meaning on the context in which the callback is used. + * + * @param cls closure + * @param info details about the event, specifying the event type + * and various bits about the event + * @return client-context (for the next progress call + * for this operation; should be set to NULL for + * SUSPEND and STOPPED events). The value returned + * will be passed to future callbacks in the respective + * field in the GNUNET_FS_ProgressInfo struct. + */ +static void * +progress_cb (void *cls, + const struct GNUNET_FS_ProgressInfo *info) +{ + struct Pattern *p; + const struct GNUNET_FS_Uri *uri; + + switch (info->status) + { + case GNUNET_FS_STATUS_PUBLISH_START: + case GNUNET_FS_STATUS_PUBLISH_PROGRESS: + p = info->value.publish.cctx; + return p; + case GNUNET_FS_STATUS_PUBLISH_ERROR: + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Publishing failed\n"); + GNUNET_STATISTICS_update (stats_handle, + "# failed publish operations", 1, GNUNET_NO); + p = info->value.publish.cctx; + p->task = GNUNET_SCHEDULER_add_now (&publish_stop_task, p); + return p; + case GNUNET_FS_STATUS_PUBLISH_COMPLETED: + p = info->value.publish.cctx; + GNUNET_STATISTICS_update (stats_handle, + "# publishing time (ms)", + (long long) GNUNET_TIME_absolute_get_duration (p->start_time).rel_value, + GNUNET_NO); + p->task = GNUNET_SCHEDULER_add_now (&publish_stop_task, p); + return p; + case GNUNET_FS_STATUS_PUBLISH_STOPPED: + p = info->value.publish.cctx; + p->ctx = NULL; + GNUNET_CONTAINER_DLL_remove (publish_head, publish_tail, p); + GNUNET_free (p); + return NULL; + case GNUNET_FS_STATUS_DOWNLOAD_START: + case GNUNET_FS_STATUS_DOWNLOAD_PROGRESS: + case GNUNET_FS_STATUS_DOWNLOAD_ACTIVE: + case GNUNET_FS_STATUS_DOWNLOAD_INACTIVE: + p = info->value.download.cctx; + return p; + case GNUNET_FS_STATUS_DOWNLOAD_ERROR: + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Download failed\n"); + GNUNET_STATISTICS_update (stats_handle, + "# failed downloads", 1, GNUNET_NO); + p = info->value.download.cctx; + p->task = GNUNET_SCHEDULER_add_now (&download_stop_task, p); + return p; + case GNUNET_FS_STATUS_DOWNLOAD_COMPLETED: + p = info->value.download.cctx; + GNUNET_STATISTICS_update (stats_handle, + "# download time (ms)", + (long long) GNUNET_TIME_absolute_get_duration (p->start_time).rel_value, + GNUNET_NO); p->task = GNUNET_SCHEDULER_add_now (&download_stop_task, p); + return p; + case GNUNET_FS_STATUS_DOWNLOAD_STOPPED: + p = info->value.download.cctx; + p->ctx = NULL; + if (NULL == p->sctx) + { + GNUNET_CONTAINER_DLL_remove (download_head, download_tail, p); + GNUNET_free (p); + } + return NULL; + case GNUNET_FS_STATUS_SEARCH_START: + case GNUNET_FS_STATUS_SEARCH_RESULT_NAMESPACE: + p = info->value.search.cctx; + return p; + case GNUNET_FS_STATUS_SEARCH_RESULT: + p = info->value.search.cctx; + uri = info->value.search.specifics.result.uri; + if (GNUNET_YES != GNUNET_FS_uri_test_chk (uri)) + return NULL; /* not what we want */ + if (p->y != GNUNET_FS_uri_chk_get_file_size (uri)) + return NULL; /* not what we want */ + GNUNET_STATISTICS_update (stats_handle, + "# search time (ms)", + (long long) GNUNET_TIME_absolute_get_duration (p->start_time).rel_value, + GNUNET_NO); + p->start_time = GNUNET_TIME_absolute_get (); + p->ctx = GNUNET_FS_download_start (fs_handle, uri, + NULL, NULL, NULL, + 0, GNUNET_FS_uri_chk_get_file_size (uri), + anonymity_level, + GNUNET_FS_DOWNLOAD_NO_TEMPORARIES, + p, + NULL); + p->stask = GNUNET_SCHEDULER_add_now (&search_stop_task, p); + return NULL; + case GNUNET_FS_STATUS_SEARCH_UPDATE: + case GNUNET_FS_STATUS_SEARCH_RESULT_STOPPED: + return NULL; /* don't care */ + case GNUNET_FS_STATUS_SEARCH_ERROR: + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Search failed\n"); + GNUNET_STATISTICS_update (stats_handle, + "# failed searches", 1, GNUNET_NO); + p = info->value.search.cctx; + p->stask = GNUNET_SCHEDULER_add_now (&search_stop_task, p); + return p; + case GNUNET_FS_STATUS_SEARCH_STOPPED: + p = info->value.search.cctx; + p->sctx = NULL; + if (NULL == p->ctx) + { + GNUNET_CONTAINER_DLL_remove (download_head, download_tail, p); + GNUNET_free (p); + } + return NULL; + default: + /* unexpected event during profiling */ + GNUNET_break (0); + return NULL; + } +} + + +/** + * Start publish operation. + * + * @param cls the 'struct Pattern' specifying the operation to perform + * @param tc scheduler context + */ +static void +start_publish (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct Pattern *p = cls; + struct GNUNET_FS_FileInformation *fi; + + p->task = GNUNET_SCHEDULER_NO_TASK; + if (0 != (tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN)) + return; + fi = make_file (p->x, p->y, p); + p->start_time = GNUNET_TIME_absolute_get (); + p->ctx = GNUNET_FS_publish_start (fs_handle, + fi, + NULL, NULL, NULL, + GNUNET_FS_PUBLISH_OPTION_NONE); +} + + +/** + * Start download operation. + * + * @param cls the 'struct Pattern' specifying the operation to perform + * @param tc scheduler context + */ +static void +start_download (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct Pattern *p = cls; + struct GNUNET_FS_Uri *keywords; + + p->task = GNUNET_SCHEDULER_NO_TASK; + if (0 != (tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN)) + return; + keywords = make_keywords (p->x); + p->start_time = GNUNET_TIME_absolute_get (); + p->sctx = GNUNET_FS_search_start (fs_handle, keywords, + anonymity_level, + GNUNET_FS_SEARCH_OPTION_NONE, + p); +} + + +/** + * @brief Main function that will be run by the scheduler. + * + * @param cls closure + * @param args remaining command-line arguments + * @param cfgfile name of the configuration file used (for saving, can be NULL!) + * @param cfg_ configuration + */ +static void +run (void *cls, char *const *args GNUNET_UNUSED, + const char *cfgfile GNUNET_UNUSED, + const struct GNUNET_CONFIGURATION_Handle *cfg_) +{ + char myoptname[128]; + struct Pattern *p; + + cfg = cfg_; + /* Scheduled the task to clean up when shutdown is called */ + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, &shutdown_task, + NULL); + + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_number (cfg, + "TESTBED", "PEERID", + &my_peerid)) + { + GNUNET_log_config_missing (GNUNET_ERROR_TYPE_ERROR, + "TESTBED", "PEERID"); + global_ret = GNUNET_SYSERR; + GNUNET_SCHEDULER_shutdown (); + return; + } + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_number (cfg, + "FSPROFILER", "ANONYMITY_LEVEL", + &anonymity_level)) + anonymity_level = 1; + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_number (cfg, + "FSPROFILER", "REPLICATION_LEVEL", + &replication_level)) + replication_level = 1; + GNUNET_snprintf (myoptname, sizeof (myoptname), + "DOWNLOAD-PATTERN-%u", my_peerid); + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_string (cfg, + "FSPROFILER", myoptname, + &download_pattern)) + download_pattern = GNUNET_strdup (""); + GNUNET_snprintf (myoptname, sizeof (myoptname), + "PUBLISH-PATTERN-%u", my_peerid); + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_string (cfg, + "FSPROFILER", myoptname, + &publish_pattern)) + publish_pattern = GNUNET_strdup (""); + if ( (GNUNET_OK != + parse_pattern (&download_head, + &download_tail, + download_pattern)) || + (GNUNET_OK != + parse_pattern (&publish_head, + &publish_tail, + publish_pattern)) ) + { + GNUNET_SCHEDULER_shutdown (); + return; + } + + stats_handle = GNUNET_STATISTICS_create ("fsprofiler", cfg); + fs_handle = + GNUNET_FS_start (cfg, + "fsprofiler", + &progress_cb, NULL, + GNUNET_FS_FLAGS_NONE, + GNUNET_FS_OPTIONS_DOWNLOAD_PARALLELISM, 1, + GNUNET_FS_OPTIONS_REQUEST_PARALLELISM, 1, + GNUNET_FS_OPTIONS_END); + if (NULL == fs_handle) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Could not acquire FS handle. Exiting.\n"); + global_ret = GNUNET_SYSERR; + GNUNET_SCHEDULER_shutdown (); + return; + } + for (p = publish_head; NULL != p; p = p->next) + p->task = GNUNET_SCHEDULER_add_delayed (p->delay, + &start_publish, p); + for (p = download_head; NULL != p; p = p->next) + p->task = GNUNET_SCHEDULER_add_delayed (p->delay, + &start_download, p); +} + + +/** + * Program that performs various "random" FS activities. + * + * @param argc number of arguments from the command line + * @param argv command line arguments + * @return 0 ok, 1 on error + */ +int +main (int argc, char *const *argv) +{ + static const struct GNUNET_GETOPT_CommandLineOption options[] = { + GNUNET_GETOPT_OPTION_END + }; + + if (GNUNET_OK != GNUNET_STRINGS_get_utf8_args (argc, argv, &argc, &argv)) + return 2; + return (GNUNET_OK == + GNUNET_PROGRAM_run (argc, argv, "gnunet-daemon-fsprofiler", + gettext_noop + ("Daemon to use file-sharing to measure its performance."), + options, &run, NULL)) ? global_ret : 1; +} + +/* end of gnunet-daemon-fsprofiler.c */ diff --git a/src/fs/gnunet-directory.c b/src/fs/gnunet-directory.c index c722f57..2f25e28 100644 --- a/src/fs/gnunet-directory.c +++ b/src/fs/gnunet-directory.c @@ -173,11 +173,17 @@ main (int argc, char *const *argv) static struct GNUNET_GETOPT_CommandLineOption options[] = { GNUNET_GETOPT_OPTION_END }; - return (GNUNET_OK == - GNUNET_PROGRAM_run (argc, argv, "gnunet-directory [OPTIONS] FILENAME", - gettext_noop - ("Display contents of a GNUnet directory"), - options, &run, NULL)) ? ret : 1; + + if (GNUNET_OK != GNUNET_STRINGS_get_utf8_args (argc, argv, &argc, &argv)) + return 2; + + ret = (GNUNET_OK == + GNUNET_PROGRAM_run (argc, argv, "gnunet-directory [OPTIONS] FILENAME", + gettext_noop + ("Display contents of a GNUnet directory"), + options, &run, NULL)) ? ret : 1; + GNUNET_free ((void*) argv); + return ret; } /* end of gnunet-directory.c */ diff --git a/src/fs/gnunet-download.c b/src/fs/gnunet-download.c index 5a66aea..04edc66 100644 --- a/src/fs/gnunet-download.c +++ b/src/fs/gnunet-download.c @@ -52,6 +52,7 @@ static char *filename; static int local_only; + static void cleanup_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { @@ -63,17 +64,52 @@ cleanup_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) static void shutdown_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { - struct GNUNET_FS_DownloadContext *d; - - if (dc != NULL) + if (NULL != dc) { - d = dc; + GNUNET_FS_download_stop (dc, delete_incomplete); dc = NULL; - GNUNET_FS_download_stop (d, delete_incomplete); } } +/** + * Display progress bar (if tty). + * + * @param x current position in the download + * @param n total size of the download + * @param w desired number of steps in the progress bar + */ +static void +display_bar (unsigned long long x, + unsigned long long n, + unsigned int w) +{ + char buf[w + 20]; + unsigned int p; + unsigned int endeq; + float ratio_complete; + +#if !WINDOWS + if (0 == isatty (1)) + return; +#else + if (FILE_TYPE_CHAR != GetFileType (GetStdHandle (STD_OUTPUT_HANDLE))) + return; +#endif + ratio_complete = x/(float)n; + endeq = ratio_complete * w; + GNUNET_snprintf (buf, sizeof (buf), + "%3d%% [", (int)(ratio_complete*100) ); + for (p=0; pstatus) @@ -104,13 +140,15 @@ progress_cb (void *cls, const struct GNUNET_FS_ProgressInfo *info) case GNUNET_FS_STATUS_DOWNLOAD_PROGRESS: if (verbose) { - s = GNUNET_STRINGS_relative_time_to_string (info->value.download.eta); + s = GNUNET_strdup (GNUNET_STRINGS_relative_time_to_string (info->value.download.eta, + GNUNET_YES)); if (info->value.download.specifics.progress.block_download_duration.rel_value == GNUNET_TIME_UNIT_FOREVER_REL.rel_value) - s2 = GNUNET_strdup (_("")); + s2 = _(""); else s2 = GNUNET_STRINGS_relative_time_to_string ( - info->value.download.specifics.progress.block_download_duration); + info->value.download.specifics.progress.block_download_duration, + GNUNET_YES); t = GNUNET_STRINGS_byte_size_fancy (info->value.download.completed * 1000LL / (info->value.download. @@ -121,11 +159,23 @@ progress_cb (void *cls, const struct GNUNET_FS_ProgressInfo *info) (unsigned long long) info->value.download.completed, (unsigned long long) info->value.download.size, s, t, s2); GNUNET_free (s); - GNUNET_free (s2); GNUNET_free (t); } + else + { + display_bar (info->value.download.completed, + info->value.download.size, + 60); + } break; case GNUNET_FS_STATUS_DOWNLOAD_ERROR: +#if !WINDOWS + if (0 != isatty (1)) + fprintf (stdout, "\n"); +#else + if (FILE_TYPE_CHAR == GetFileType (GetStdHandle (STD_OUTPUT_HANDLE))) + fprintf (stdout, "\n"); +#endif FPRINTF (stderr, _("Error downloading: %s.\n"), info->value.download.specifics.error.message); GNUNET_SCHEDULER_shutdown (); @@ -134,6 +184,13 @@ progress_cb (void *cls, const struct GNUNET_FS_ProgressInfo *info) s = GNUNET_STRINGS_byte_size_fancy (info->value.download.completed * 1000 / (info->value.download. duration.rel_value + 1)); +#if !WINDOWS + if (0 != isatty (1)) + fprintf (stdout, "\n"); +#else + if (FILE_TYPE_CHAR == GetFileType (GetStdHandle (STD_OUTPUT_HANDLE))) + fprintf (stdout, "\n"); +#endif FPRINTF (stdout, _("Downloading `%s' done (%s/s).\n"), info->value.download.filename, s); GNUNET_free (s); @@ -272,11 +329,17 @@ main (int argc, char *const *argv) 0, &GNUNET_GETOPT_increment_value, &verbose}, GNUNET_GETOPT_OPTION_END }; - return (GNUNET_OK == - GNUNET_PROGRAM_run (argc, argv, "gnunet-download [OPTIONS] URI", - gettext_noop - ("Download files from GNUnet using a GNUnet CHK or LOC URI (gnunet://fs/chk/...)"), - options, &run, NULL)) ? ret : 1; + + if (GNUNET_OK != GNUNET_STRINGS_get_utf8_args (argc, argv, &argc, &argv)) + return 2; + + ret = (GNUNET_OK == + GNUNET_PROGRAM_run (argc, argv, "gnunet-download [OPTIONS] URI", + gettext_noop + ("Download files from GNUnet using a GNUnet CHK or LOC URI (gnunet://fs/chk/...)"), + options, &run, NULL)) ? ret : 1; + GNUNET_free ((void*) argv); + return ret; } /* end of gnunet-download.c */ diff --git a/src/fs/gnunet-fs-profiler.c b/src/fs/gnunet-fs-profiler.c new file mode 100644 index 0000000..7a0b7e8 --- /dev/null +++ b/src/fs/gnunet-fs-profiler.c @@ -0,0 +1,203 @@ +/* + This file is part of GNUnet. + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @file fs/gnunet-fs-profiler.c + * @brief tool to benchmark/profile file-sharing + * @author Christian Grothoff + */ +#include "platform.h" +#include "gnunet_util_lib.h" +#include "gnunet_testbed_service.h" + +/** + * Final status code. + */ +static int ret; + +/** + * Data file with the hosts for the testbed. + */ +static char *host_filename; + +/** + * Number of peers to run in the experiment. + */ +static unsigned int num_peers; + +/** + * After how long do we abort the test? + */ +static struct GNUNET_TIME_Relative timeout; + +/** + * Handle to the task run during termination. + */ +static GNUNET_SCHEDULER_TaskIdentifier terminate_taskid; + + +/** + * Function called after we've collected the statistics. + * + * @param cls NULL + * @param op the operation that has been finished + * @param emsg error message in case the operation has failed; will be NULL if + * operation has executed successfully. + */ +static void +shutdown_task (void *cls, + struct GNUNET_TESTBED_Operation *op, + const char *emsg) +{ + if (NULL != emsg) + fprintf (stderr, + "Error collecting statistics: %s\n", + emsg); + GNUNET_SCHEDULER_shutdown (); +} + + +/** + * Callback function to process statistic values from all peers. + * Prints them out. + * + * @param cls closure + * @param peer the peer the statistic belong to + * @param subsystem name of subsystem that created the statistic + * @param name the name of the datum + * @param value the current value + * @param is_persistent GNUNET_YES if the value is persistent, GNUNET_NO if not + * @return GNUNET_OK to continue, GNUNET_SYSERR to abort iteration + */ +static int +process_stats (void *cls, + const struct GNUNET_TESTBED_Peer *peer, + const char *subsystem, + const char *name, + uint64_t value, + int is_persistent) +{ + fprintf (stdout, + "%p-%s: %s = %llu\n", + peer, + subsystem, + name, + (unsigned long long) value); + return GNUNET_OK; +} + + +/** + * Task run on timeout to terminate. Triggers printing out + * all statistics. + * + * @param cls NULL + * @param tc unused + */ +static void +terminate_task (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + terminate_taskid = GNUNET_SCHEDULER_NO_TASK; + GNUNET_TESTBED_get_statistics (0, NULL, + &process_stats, + &shutdown_task, + NULL); +} + + +/** + * Signature of a main function for a testcase. + * + * @param cls closure + * @param num_peers number of peers in 'peers' + * @param peers handle to peers run in the testbed + */ +static void +test_master (void *cls, unsigned int num_peers, struct GNUNET_TESTBED_Peer **peers) +{ + // const struct GNUNET_CONFIGURATION_Handle *cfg = cls; + // FIXME: enable clients to signal 'completion' before timeout; + // in that case, run the 'terminate_task' "immediately" + + if (0 != timeout.rel_value) + terminate_taskid = GNUNET_SCHEDULER_add_delayed (timeout, + &terminate_task, NULL); + else + terminate_taskid = GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, + &terminate_task, + NULL); +} + + +/** + * Main function that will be run by the scheduler. + * + * @param cls closure + * @param args remaining command-line arguments + * @param cfgfile name of the configuration file used (for saving, can be NULL!) + * @param cfg configuration + */ +static void +run (void *cls, char *const *args, const char *cfgfile, + const struct GNUNET_CONFIGURATION_Handle *cfg) +{ + GNUNET_TESTBED_run (host_filename, + cfg, + num_peers, + 0, NULL, NULL, + &test_master, (void *) cfg); +} + + +/** + * Program to run a file-sharing testbed. + * + * @param argc number of arguments from the command line + * @param argv command line arguments + * @return 0 ok, 1 on error + */ +int +main (int argc, char *const *argv) +{ + static const struct GNUNET_GETOPT_CommandLineOption options[] = { + {'n', "num-peers", "COUNT", + gettext_noop ("run the experiment with COUNT peers"), + 1, &GNUNET_GETOPT_set_uint, &num_peers}, + {'H', "hosts", "HOSTFILE", + gettext_noop ("specifies name of a file with the HOSTS the testbed should use"), + 1, &GNUNET_GETOPT_set_string, &host_filename}, + {'t', "timeout", "DELAY", + gettext_noop ("automatically terminate experiment after DELAY"), + 1, &GNUNET_GETOPT_set_relative_time, &timeout}, + GNUNET_GETOPT_OPTION_END + }; + if (GNUNET_OK != GNUNET_STRINGS_get_utf8_args (argc, argv, &argc, &argv)) + return 2; + + ret = (GNUNET_OK == + GNUNET_PROGRAM_run (argc, argv, "gnunet-fs-profiler", + gettext_noop ("run a testbed to measure file-sharing performance"), options, &run, + NULL)) ? ret : 1; + GNUNET_free ((void*) argv); + return ret; +} + +/* end of gnunet-fs-profiler.c */ diff --git a/src/fs/gnunet-fs.c b/src/fs/gnunet-fs.c index 0b28923..1d79137 100644 --- a/src/fs/gnunet-fs.c +++ b/src/fs/gnunet-fs.c @@ -55,7 +55,7 @@ static int verbose; * @return GNUNET_OK to continue iteration */ static int -print_indexed (void *cls, const char *filename, const GNUNET_HashCode * file_id) +print_indexed (void *cls, const char *filename, const struct GNUNET_HashCode * file_id) { if (NULL == filename) { @@ -119,10 +119,15 @@ main (int argc, char *const *argv) GNUNET_GETOPT_OPTION_VERBOSE (&verbose), GNUNET_GETOPT_OPTION_END }; - return (GNUNET_OK == - GNUNET_PROGRAM_run (argc, argv, "gnunet-fs [OPTIONS]", - gettext_noop ("Special file-sharing operations"), - options, &run, NULL)) ? ret : 1; + + if (GNUNET_OK != GNUNET_STRINGS_get_utf8_args (argc, argv, &argc, &argv)) + return 2; + ret = (GNUNET_OK == + GNUNET_PROGRAM_run (argc, argv, "gnunet-fs [OPTIONS]", + gettext_noop ("Special file-sharing operations"), + options, &run, NULL)) ? ret : 1; + GNUNET_free ((void*) argv); + return ret; } /* end of gnunet-fs.c */ diff --git a/src/fs/gnunet-helper-fs-publish.c b/src/fs/gnunet-helper-fs-publish.c index 86b0249..7ea9499 100644 --- a/src/fs/gnunet-helper-fs-publish.c +++ b/src/fs/gnunet-helper-fs-publish.c @@ -364,8 +364,7 @@ extract_files (struct ScanTreeNode *item) /* this is the expensive operation, *afterwards* we'll check for aborts */ meta = GNUNET_CONTAINER_meta_data_create (); - if (NULL != plugins) - EXTRACTOR_extract (plugins, item->filename, NULL, 0, &add_to_md, meta); + EXTRACTOR_extract (plugins, item->filename, NULL, 0, &add_to_md, meta); slen = strlen (item->filename) + 1; size = GNUNET_CONTAINER_meta_data_get_serialized_size (meta); if (-1 == size) @@ -378,6 +377,11 @@ extract_files (struct ScanTreeNode *item) return GNUNET_SYSERR; return GNUNET_OK; } + else if (size > (UINT16_MAX - sizeof (struct GNUNET_MessageHeader) - slen)) + { + /* We can't transfer more than 64k bytes in one message. */ + size = UINT16_MAX - sizeof (struct GNUNET_MessageHeader) - slen; + } { char buf[size + slen]; char *dst = &buf[slen]; @@ -402,6 +406,31 @@ extract_files (struct ScanTreeNode *item) } +#ifndef WINDOWS +/** + * Install a signal handler to ignore SIGPIPE. + */ +static void +ignore_sigpipe () +{ + struct sigaction oldsig; + struct sigaction sig; + + memset (&sig, 0, sizeof (struct sigaction)); + sig.sa_handler = SIG_IGN; + sigemptyset (&sig.sa_mask); +#ifdef SA_INTERRUPT + sig.sa_flags = SA_INTERRUPT; /* SunOS */ +#else + sig.sa_flags = SA_RESTART; +#endif + if (0 != sigaction (SIGPIPE, &sig, &oldsig)) + fprintf (stderr, + "Failed to install SIGPIPE handler: %s\n", strerror (errno)); +} +#endif + + /** * Main function of the helper process to extract meta data. * @@ -413,7 +442,7 @@ extract_files (struct ScanTreeNode *item) * @return 0 on success */ int main(int argc, - char **argv) + char *const *argv) { const char *filename_expanded; const char *ex; @@ -424,6 +453,11 @@ int main(int argc, * binary mode. */ _setmode (1, _O_BINARY); + /* Get utf-8-encoded arguments */ + if (GNUNET_OK != GNUNET_STRINGS_get_utf8_args (argc, argv, &argc, &argv)) + return 5; +#else + ignore_sigpipe (); #endif /* parse command line */ @@ -432,6 +466,9 @@ int main(int argc, FPRINTF (stderr, "%s", "gnunet-helper-fs-publish needs exactly one or two arguments\n"); +#if WINDOWS + GNUNET_free ((void*) argv); +#endif return 1; } filename_expanded = argv[1]; @@ -450,13 +487,23 @@ int main(int argc, &root)) { (void) write_message (GNUNET_MESSAGE_TYPE_FS_PUBLISH_HELPER_ERROR, NULL, 0); + EXTRACTOR_plugin_remove_all (plugins); +#if WINDOWS + GNUNET_free ((void*) argv); +#endif return 2; } /* signal that we're done counting files, so that a percentage of progress can now be calculated */ if (GNUNET_OK != write_message (GNUNET_MESSAGE_TYPE_FS_PUBLISH_HELPER_COUNTING_DONE, NULL, 0)) + { + EXTRACTOR_plugin_remove_all (plugins); +#if WINDOWS + GNUNET_free ((void*) argv); +#endif return 3; + } if (NULL != root) { if (GNUNET_OK != @@ -464,15 +511,20 @@ int main(int argc, { (void) write_message (GNUNET_MESSAGE_TYPE_FS_PUBLISH_HELPER_ERROR, NULL, 0); free_tree (root); + EXTRACTOR_plugin_remove_all (plugins); +#if WINDOWS + GNUNET_free ((void*) argv); +#endif return 4; } free_tree (root); } /* enable "clean" shutdown by telling parent that we are done */ (void) write_message (GNUNET_MESSAGE_TYPE_FS_PUBLISH_HELPER_FINISHED, NULL, 0); - if (NULL != plugins) - EXTRACTOR_plugin_remove_all (plugins); - + EXTRACTOR_plugin_remove_all (plugins); +#if WINDOWS + GNUNET_free ((void*) argv); +#endif return 0; } diff --git a/src/fs/gnunet-pseudonym.c b/src/fs/gnunet-pseudonym.c index 38826d1..a692917 100644 --- a/src/fs/gnunet-pseudonym.c +++ b/src/fs/gnunet-pseudonym.c @@ -95,7 +95,7 @@ progress_cb (void *cls, const struct GNUNET_FS_ProgressInfo *info) static void -ns_printer (void *cls, const char *name, const GNUNET_HashCode * id) +ns_printer (void *cls, const char *name, const struct GNUNET_HashCode * id) { struct GNUNET_CRYPTO_HashAsciiEncoded enc; @@ -105,7 +105,7 @@ ns_printer (void *cls, const char *name, const GNUNET_HashCode * id) static int -pseudo_printer (void *cls, const GNUNET_HashCode * pseudonym, +pseudo_printer (void *cls, const struct GNUNET_HashCode * pseudonym, const char *name, const char *unique_name, const struct GNUNET_CONTAINER_MetaData *md, int rating) { @@ -136,7 +136,7 @@ pseudo_printer (void *cls, const GNUNET_HashCode * pseudonym, static void post_advertising (void *cls, const struct GNUNET_FS_Uri *uri, const char *emsg) { - GNUNET_HashCode nsid; + struct GNUNET_HashCode nsid; char *set; int delta; @@ -313,10 +313,16 @@ main (int argc, char *const *argv) }; bo.expiration_time = GNUNET_FS_year_to_time (GNUNET_FS_get_current_year () + 2); - return (GNUNET_OK == - GNUNET_PROGRAM_run (argc, argv, "gnunet-pseudonym [OPTIONS]", - gettext_noop ("Manage GNUnet pseudonyms."), - options, &run, NULL)) ? ret : 1; + + if (GNUNET_OK != GNUNET_STRINGS_get_utf8_args (argc, argv, &argc, &argv)) + return 2; + + ret = (GNUNET_OK == + GNUNET_PROGRAM_run (argc, argv, "gnunet-pseudonym [OPTIONS]", + gettext_noop ("Manage GNUnet pseudonyms."), + options, &run, NULL)) ? ret : 1; + GNUNET_free ((void*) argv); + return ret; } /* end of gnunet-pseudonym.c */ diff --git a/src/fs/gnunet-publish.c b/src/fs/gnunet-publish.c index a1b26db..08b34c6 100644 --- a/src/fs/gnunet-publish.c +++ b/src/fs/gnunet-publish.c @@ -28,7 +28,7 @@ #include "platform.h" #include "gnunet_fs_service.h" -static int ret; +static int ret = 1; static int verbose; @@ -105,8 +105,11 @@ static void stop_scanner_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { kill_task = GNUNET_SCHEDULER_NO_TASK; - GNUNET_FS_directory_scan_abort (ds); - ds = NULL; + if (NULL != ds) + { + GNUNET_FS_directory_scan_abort (ds); + ds = NULL; + } if (namespace != NULL) { GNUNET_FS_namespace_delete (namespace, GNUNET_NO); @@ -134,7 +137,8 @@ stop_scanner_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) static void * progress_cb (void *cls, const struct GNUNET_FS_ProgressInfo *info) { - char *s; + const char *s; + char *suri; switch (info->status) { @@ -143,12 +147,12 @@ progress_cb (void *cls, const struct GNUNET_FS_ProgressInfo *info) case GNUNET_FS_STATUS_PUBLISH_PROGRESS: if (verbose) { - s = GNUNET_STRINGS_relative_time_to_string (info->value.publish.eta); + s = GNUNET_STRINGS_relative_time_to_string (info->value.publish.eta, + GNUNET_YES); FPRINTF (stdout, _("Publishing `%s' at %llu/%llu (%s remaining)\n"), info->value.publish.filename, (unsigned long long) info->value.publish.completed, (unsigned long long) info->value.publish.size, s); - GNUNET_free (s); } break; case GNUNET_FS_STATUS_PUBLISH_ERROR: @@ -164,10 +168,10 @@ progress_cb (void *cls, const struct GNUNET_FS_ProgressInfo *info) case GNUNET_FS_STATUS_PUBLISH_COMPLETED: FPRINTF (stdout, _("Publishing `%s' done.\n"), info->value.publish.filename); - s = GNUNET_FS_uri_to_string (info->value.publish.specifics. + suri = GNUNET_FS_uri_to_string (info->value.publish.specifics. completed.chk_uri); - FPRINTF (stdout, _("URI is `%s'.\n"), s); - GNUNET_free (s); + FPRINTF (stdout, _("URI is `%s'.\n"), suri); + GNUNET_free (suri); if (info->value.publish.pctx == NULL) { if (kill_task != GNUNET_SCHEDULER_NO_TASK) @@ -177,6 +181,7 @@ progress_cb (void *cls, const struct GNUNET_FS_ProgressInfo *info) } kill_task = GNUNET_SCHEDULER_add_now (&do_stop_task, NULL); } + ret = 0; break; case GNUNET_FS_STATUS_PUBLISH_STOPPED: GNUNET_break (NULL == pc); @@ -268,6 +273,12 @@ publish_inspector (void *cls, struct GNUNET_FS_FileInformation *fi, if (cls == fi) return GNUNET_OK; + if ( (disable_extractor) && + (NULL != *uri) ) + { + GNUNET_FS_uri_destroy (*uri); + *uri = NULL; + } if (NULL != topKeywords) { if (*uri != NULL) @@ -291,12 +302,6 @@ publish_inspector (void *cls, struct GNUNET_FS_FileInformation *fi, } if (!do_disable_creation_time) GNUNET_CONTAINER_meta_data_add_publication_date (m); - if ( (disable_extractor) && - (NULL != *uri) ) - { - GNUNET_FS_uri_destroy (*uri); - *uri = NULL; - } if (extract_only) { fn = GNUNET_CONTAINER_meta_data_get_by_type (m, @@ -355,7 +360,7 @@ uri_ksk_continuation (void *cls, const struct GNUNET_FS_Uri *ksk_uri, ns = GNUNET_FS_namespace_create (ctx, pseudonym); if (ns == NULL) { - FPRINTF (stderr, _("Failed to create namespace `%s'\n"), pseudonym); + FPRINTF (stderr, _("Failed to create namespace `%s' (illegal filename?)\n"), pseudonym); ret = 1; } else @@ -609,7 +614,7 @@ run (void *cls, char *const *args, const char *cfgfile, namespace = GNUNET_FS_namespace_create (ctx, pseudonym); if (NULL == namespace) { - FPRINTF (stderr, _("Could not create namespace `%s'\n"), pseudonym); + FPRINTF (stderr, _("Failed to create namespace `%s' (illegal filename?)\n"), pseudonym); GNUNET_FS_stop (ctx); ret = 1; return; @@ -732,15 +737,18 @@ main (int argc, char *const *argv) 0, &GNUNET_GETOPT_set_one, &verbose}, GNUNET_GETOPT_OPTION_END }; - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "GNUnet publish starts\n"); bo.expiration_time = GNUNET_FS_year_to_time (GNUNET_FS_get_current_year () + 2); - return (GNUNET_OK == - GNUNET_PROGRAM_run (argc, argv, "gnunet-publish [OPTIONS] FILENAME", - gettext_noop - ("Publish a file or directory on GNUnet"), - options, &run, NULL)) ? ret : 1; + + if (GNUNET_OK != GNUNET_STRINGS_get_utf8_args (argc, argv, &argc, &argv)) + return 2; + ret = (GNUNET_OK == + GNUNET_PROGRAM_run (argc, argv, "gnunet-publish [OPTIONS] FILENAME", + gettext_noop + ("Publish a file or directory on GNUnet"), + options, &run, NULL)) ? ret : 1; + GNUNET_free ((void*) argv); + return ret; } /* end of gnunet-publish.c */ diff --git a/src/fs/gnunet-search.c b/src/fs/gnunet-search.c index 60620a4..e90b761 100644 --- a/src/fs/gnunet-search.c +++ b/src/fs/gnunet-search.c @@ -42,11 +42,14 @@ static struct GNUNET_FS_DirectoryBuilder *db; static unsigned int anonymity = 1; -static unsigned long long timeout; +/** + * Timeout for the search, 0 means to wait for CTRL-C. + */ +static struct GNUNET_TIME_Relative timeout; static unsigned int results_limit; -static unsigned int results = 0; +static unsigned int results; static int verbose; @@ -220,7 +223,6 @@ run (void *cls, char *const *args, const char *cfgfile, struct GNUNET_FS_Uri *uri; unsigned int argc; enum GNUNET_FS_SearchOptions options; - struct GNUNET_TIME_Relative delay; argc = 0; while (NULL != args[argc]) @@ -257,16 +259,11 @@ run (void *cls, char *const *args, const char *cfgfile, ret = 1; return; } - if (timeout != 0) - { - delay.rel_value = timeout; - GNUNET_SCHEDULER_add_delayed (delay, &shutdown_task, NULL); - } + if (0 != timeout.rel_value) + GNUNET_SCHEDULER_add_delayed (timeout, &shutdown_task, NULL); else - { GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, &shutdown_task, NULL); - } } @@ -290,9 +287,9 @@ main (int argc, char *const *argv) {'o', "output", "PREFIX", gettext_noop ("write search results to file starting with PREFIX"), 1, &GNUNET_GETOPT_set_string, &output_filename}, - {'t', "timeout", "VALUE", - gettext_noop ("automatically terminate search after VALUE ms"), - 1, &GNUNET_GETOPT_set_ulong, &timeout}, + {'t', "timeout", "DELAY", + gettext_noop ("automatically terminate search after DELAY"), + 1, &GNUNET_GETOPT_set_relative_time, &timeout}, {'V', "verbose", NULL, gettext_noop ("be verbose (print progress information)"), 0, &GNUNET_GETOPT_set_one, &verbose}, @@ -302,11 +299,17 @@ main (int argc, char *const *argv) 1, &GNUNET_GETOPT_set_uint, &results_limit}, GNUNET_GETOPT_OPTION_END }; - return (GNUNET_OK == - GNUNET_PROGRAM_run (argc, argv, "gnunet-search [OPTIONS] KEYWORD", - gettext_noop - ("Search GNUnet for files that were published on GNUnet"), - options, &run, NULL)) ? ret : 1; + + if (GNUNET_OK != GNUNET_STRINGS_get_utf8_args (argc, argv, &argc, &argv)) + return 2; + + ret = (GNUNET_OK == + GNUNET_PROGRAM_run (argc, argv, "gnunet-search [OPTIONS] KEYWORD", + gettext_noop + ("Search GNUnet for files that were published on GNUnet"), + options, &run, NULL)) ? ret : 1; + GNUNET_free ((void*) argv); + return ret; } /* end of gnunet-search.c */ diff --git a/src/fs/gnunet-service-fs.c b/src/fs/gnunet-service-fs.c index 06ac91c..0f4d513 100644 --- a/src/fs/gnunet-service-fs.c +++ b/src/fs/gnunet-service-fs.c @@ -22,9 +22,6 @@ * @file fs/gnunet-service-fs.c * @brief gnunet anonymity protocol implementation * @author Christian Grothoff - * - * To use: - * - consider re-issue GSF_dht_lookup_ after non-DHT reply received */ #include "platform.h" #include @@ -46,6 +43,7 @@ #include "gnunet-service-fs_pr.h" #include "gnunet-service-fs_push.h" #include "gnunet-service-fs_put.h" +#include "gnunet-service-fs_stream.h" #include "fs.h" /** @@ -63,6 +61,11 @@ */ #define COVER_AGE_FREQUENCY GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 5) +/** + * Collect an instane number of statistics? May cause excessive IPC. + */ +#define INSANE_STATISTICS GNUNET_NO + /* ****************************** globals ****************************** */ @@ -109,6 +112,11 @@ struct GNUNET_TIME_Relative GSF_avg_latency = { 500 }; */ double GSF_current_priorities; +/** + * Size of the datastore queue we assume for common requests. + */ +unsigned int GSF_datastore_queue_size; + /** * How many query messages have we received 'recently' that * have not yet been claimed as cover traffic? @@ -296,9 +304,11 @@ consider_request_for_forwarding (void *cls, if (GNUNET_YES != GSF_pending_request_test_target_ (pr, peer)) { +#if INSANE_STATISTICS GNUNET_STATISTICS_update (GSF_stats, gettext_noop ("# Loopback routes suppressed"), 1, GNUNET_NO); +#endif return; } GSF_plan_add_ (cp, pr); @@ -384,7 +394,30 @@ start_p2p_processing (void *cls, struct GSF_PendingRequest *pr, GSF_pending_request_cancel_ (pr, GNUNET_YES); return; } - GSF_dht_lookup_ (pr); + if (0 == prd->anonymity_level) + { + switch (prd->type) + { + case GNUNET_BLOCK_TYPE_FS_DBLOCK: + case GNUNET_BLOCK_TYPE_FS_IBLOCK: + /* the above block types MAY be available via 'stream' */ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Considering stream-based download for block\n"); + GSF_stream_lookup_ (pr); + break; + case GNUNET_BLOCK_TYPE_FS_KBLOCK: + case GNUNET_BLOCK_TYPE_FS_SBLOCK: + case GNUNET_BLOCK_TYPE_FS_NBLOCK: + /* the above block types are in the DHT */ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Considering DHT-based search for block\n"); + GSF_dht_lookup_ (pr); + break; + default: + GNUNET_break (0); + break; + } + } consider_forwarding (NULL, pr, result); } @@ -432,6 +465,7 @@ handle_start_search (void *cls, struct GNUNET_SERVER_Client *client, static void shutdown_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { + GSF_stream_stop (); if (NULL != GSF_core) { GNUNET_CORE_disconnect (GSF_core); @@ -476,7 +510,7 @@ shutdown_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) * @return GNUNET_YES to continue to iterate */ static int -consider_peer_for_forwarding (void *cls, const GNUNET_HashCode * key, +consider_peer_for_forwarding (void *cls, const struct GNUNET_HashCode * key, struct GSF_PendingRequest *pr) { struct GSF_ConnectedPeer *cp = cls; @@ -548,6 +582,9 @@ static int main_init (struct GNUNET_SERVER_Handle *server, const struct GNUNET_CONFIGURATION_Handle *c) { + static const struct GNUNET_CORE_MessageHandler no_p2p_handlers[] = { + {NULL, 0, 0} + }; static const struct GNUNET_CORE_MessageHandler p2p_handlers[] = { {&handle_p2p_get, GNUNET_MESSAGE_TYPE_FS_GET, 0}, @@ -570,11 +607,21 @@ main_init (struct GNUNET_SERVER_Handle *server, 0}, {NULL, NULL, 0, 0} }; - + int anon_p2p_off; + + /* this option is really only for testcases that need to disable + _anonymous_ file-sharing for some reason */ + anon_p2p_off = (GNUNET_YES == + GNUNET_CONFIGURATION_get_value_yesno (GSF_cfg, + "fs", + "DISABLE_ANON_TRANSFER")); GSF_core = - GNUNET_CORE_connect (GSF_cfg, 1, NULL, &peer_init_handler, + GNUNET_CORE_connect (GSF_cfg, NULL, &peer_init_handler, &peer_connect_handler, &GSF_peer_disconnect_handler_, - NULL, GNUNET_NO, NULL, GNUNET_NO, p2p_handlers); + NULL, GNUNET_NO, NULL, GNUNET_NO, + (GNUNET_YES == anon_p2p_off) + ? no_p2p_handlers + : p2p_handlers); if (NULL == GSF_core) { GNUNET_log (GNUNET_ERROR_TYPE_ERROR, @@ -588,6 +635,7 @@ main_init (struct GNUNET_SERVER_Handle *server, GNUNET_SCHEDULER_add_delayed (COVER_AGE_FREQUENCY, &age_cover_counters, NULL); datastore_get_load = GNUNET_LOAD_value_init (DATASTORE_LOAD_AUTODECLINE); + GSF_stream_start (); GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, &shutdown_task, NULL); return GNUNET_OK; @@ -605,7 +653,18 @@ static void run (void *cls, struct GNUNET_SERVER_Handle *server, const struct GNUNET_CONFIGURATION_Handle *cfg) { + unsigned long long dqs; + GSF_cfg = cfg; + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_size (GSF_cfg, "fs", "DATASTORE_QUEUE_SIZE", + &dqs)) + { + GNUNET_log_config_missing (GNUNET_ERROR_TYPE_INFO, + "fs", "DATASTORE_QUEUE_SIZE"); + dqs = 1024; + } + GSF_datastore_queue_size = (unsigned int) dqs; GSF_enable_randomized_delays = GNUNET_CONFIGURATION_get_value_yesno (cfg, "fs", "DELAY"); GSF_dsh = GNUNET_DATASTORE_connect (cfg); diff --git a/src/fs/gnunet-service-fs.h b/src/fs/gnunet-service-fs.h index 0c796bf..3213712 100644 --- a/src/fs/gnunet-service-fs.h +++ b/src/fs/gnunet-service-fs.h @@ -119,7 +119,7 @@ struct GetMessage /** * Which of the optional hash codes are present at the end of the * message? See GET_MESSAGE_BIT_xx constants. For each bit that is - * set, an additional GNUNET_HashCode with the respective content + * set, an additional struct GNUNET_HashCode with the respective content * (in order of the bits) will be appended to the end of the GET * message. */ @@ -129,7 +129,7 @@ struct GetMessage * Hashcodes of the file(s) we're looking for. * Details depend on the query type. */ - GNUNET_HashCode query; + struct GNUNET_HashCode query; /* this is followed by hash codes as specified in the "hash_bitmap"; * after that, an optional bloomfilter (with bits set for replies @@ -183,10 +183,9 @@ struct GSF_LocalClient; struct GSF_RequestPlan; /** - * DLL of request plans a particular pending request is - * involved with. + * Bijection between request plans and pending requests. */ -struct GSF_RequestPlanReference; +struct GSF_PendingRequestPlanBijection; /** * Our connection to the datastore. @@ -258,6 +257,12 @@ extern struct GNUNET_BLOCK_Context *GSF_block_ctx; */ extern int GSF_enable_randomized_delays; +/** + * Size of the datastore queue we assume for common requests. + */ +extern unsigned int GSF_datastore_queue_size; + + /** * Test if the DATABASE (GET) load on this peer is too high * to even consider processing the query at diff --git a/src/fs/gnunet-service-fs_cp.c b/src/fs/gnunet-service-fs_cp.c index e84993b..e389a24 100644 --- a/src/fs/gnunet-service-fs_cp.c +++ b/src/fs/gnunet-service-fs_cp.c @@ -41,15 +41,20 @@ #define RUNAVG_DELAY_N 16 /** - * How often do we flush trust values to disk? + * How often do we flush respect values to disk? */ -#define TRUST_FLUSH_FREQ GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MINUTES, 5) +#define RESPECT_FLUSH_FREQ GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MINUTES, 5) /** * After how long do we discard a reply? */ #define REPLY_TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MINUTES, 2) +/** + * Collect an instane number of statistics? May cause excessive IPC. + */ +#define INSANE_STATISTICS GNUNET_NO + /** * Handle to cancel a transmission request. @@ -67,12 +72,6 @@ struct GSF_PeerTransmitHandle */ struct GSF_PeerTransmitHandle *prev; - /** - * Handle for an active request for transmission to this - * peer, or NULL (if core queue was full). - */ - struct GNUNET_CORE_TransmitHandle *cth; - /** * Time when this transmission request was issued. */ @@ -108,14 +107,6 @@ struct GSF_PeerTransmitHandle */ size_t size; - /** - * Set to 1 if we're currently in the process of calling - * 'GNUNET_CORE_notify_transmit_ready' (so while cth is - * NULL, we should not call notify_transmit_ready for this - * handle right now). - */ - unsigned int cth_in_progress; - /** * GNUNET_YES if this is a query, GNUNET_NO for content. */ @@ -263,6 +254,12 @@ struct GSF_ConnectedPeer */ struct GNUNET_CONTAINER_MultiHashMap *request_map; + /** + * Handle for an active request for transmission to this + * peer, or NULL (if core queue was full). + */ + struct GNUNET_CORE_TransmitHandle *cth; + /** * Increase in traffic preference still to be submitted * to the core service for this peer. @@ -270,9 +267,17 @@ struct GSF_ConnectedPeer uint64_t inc_preference; /** - * Trust rating for this peer on disk. + * Set to 1 if we're currently in the process of calling + * 'GNUNET_CORE_notify_transmit_ready' (so while cth is + * NULL, we should not call notify_transmit_ready for this + * handle right now). + */ + unsigned int cth_in_progress; + + /** + * Respect rating for this peer on disk. */ - uint32_t disk_trust; + uint32_t disk_respect; /** * Which offset in "last_p2p_replies" will be updated next? @@ -306,28 +311,31 @@ struct GSF_ConnectedPeer static struct GNUNET_CONTAINER_MultiHashMap *cp_map; /** - * Where do we store trust information? + * Where do we store respect information? */ -static char *trustDirectory; +static char *respectDirectory; /** * Handle to ATS service. */ static struct GNUNET_ATS_PerformanceHandle *ats; + /** - * Get the filename under which we would store the GNUNET_HELLO_Message - * for the given host and protocol. - * @return filename of the form DIRECTORY/HOSTID + * Get the filename under which we would store respect + * for the given peer. + * + * @param id peer to get the filename for + * @return filename of the form DIRECTORY/PEERID */ static char * -get_trust_filename (const struct GNUNET_PeerIdentity *id) +get_respect_filename (const struct GNUNET_PeerIdentity *id) { struct GNUNET_CRYPTO_HashAsciiEncoded fil; char *fn; GNUNET_CRYPTO_hash_to_enc (&id->hashPubKey, &fil); - GNUNET_asprintf (&fn, "%s%s%s", trustDirectory, DIR_SEPARATOR_STR, &fil); + GNUNET_asprintf (&fn, "%s%s%s", respectDirectory, DIR_SEPARATOR_STR, &fil); return fn; } @@ -423,9 +431,9 @@ schedule_transmission (struct GSF_PeerTransmitHandle *pth) struct GSF_ConnectedPeer *cp; struct GNUNET_PeerIdentity target; - if ((NULL != pth->cth) || (0 != pth->cth_in_progress)) - return; /* already done */ cp = pth->cp; + if ((NULL != cp->cth) || (0 != cp->cth_in_progress)) + return; /* already done */ GNUNET_assert (0 != cp->ppd.pid); GNUNET_PEER_resolve (cp->ppd.pid, &target); @@ -448,15 +456,17 @@ schedule_transmission (struct GSF_PeerTransmitHandle *pth) cp->rc = GNUNET_ATS_reserve_bandwidth (ats, &target, DBLOCK_SIZE, &ats_reserve_callback, cp); + return; } - GNUNET_assert (pth->cth == NULL); - pth->cth_in_progress++; - pth->cth = - GNUNET_CORE_notify_transmit_ready (GSF_core, GNUNET_YES, pth->priority, - GNUNET_TIME_absolute_get_remaining - (pth->timeout), &target, pth->size, - &peer_transmit_ready_cb, pth); - GNUNET_assert (0 < pth->cth_in_progress--); + GNUNET_assert (NULL == cp->cth); + cp->cth_in_progress++; + cp->cth = + GNUNET_CORE_notify_transmit_ready (GSF_core, GNUNET_YES, pth->priority, + GNUNET_TIME_absolute_get_remaining + (pth->timeout), &target, pth->size, + &peer_transmit_ready_cb, cp); + GNUNET_assert (NULL != cp->cth); + GNUNET_assert (0 < cp->cth_in_progress--); } @@ -471,19 +481,24 @@ schedule_transmission (struct GSF_PeerTransmitHandle *pth) static size_t peer_transmit_ready_cb (void *cls, size_t size, void *buf) { - struct GSF_PeerTransmitHandle *pth = cls; + struct GSF_ConnectedPeer *cp = cls; + struct GSF_PeerTransmitHandle *pth = cp->pth_head; struct GSF_PeerTransmitHandle *pos; - struct GSF_ConnectedPeer *cp; size_t ret; - GNUNET_assert ((NULL == buf) || (pth->size <= size)); - pth->cth = NULL; - if (pth->timeout_task != GNUNET_SCHEDULER_NO_TASK) + cp->cth = NULL; + if (NULL == pth) + return 0; + if (pth->size > size) + { + schedule_transmission (pth); + return 0; + } + if (GNUNET_SCHEDULER_NO_TASK != pth->timeout_task) { GNUNET_SCHEDULER_cancel (pth->timeout_task); pth->timeout_task = GNUNET_SCHEDULER_NO_TASK; } - cp = pth->cp; GNUNET_CONTAINER_DLL_remove (cp->pth_head, cp->pth_tail, pth); if (GNUNET_YES == pth->is_query) { @@ -500,14 +515,11 @@ peer_transmit_ready_cb (void *cls, size_t size, void *buf) GNUNET_TIME_absolute_get_duration (pth->transmission_request_start_time).rel_value); ret = pth->gmc (pth->gmc_cls, size, buf); - GNUNET_assert (NULL == pth->cth); - for (pos = cp->pth_head; pos != NULL; pos = pos->next) + if (NULL != (pos = cp->pth_head)) { GNUNET_assert (pos != pth); schedule_transmission (pos); } - GNUNET_assert (pth->cth == NULL); - GNUNET_assert (pth->cth_in_progress == 0); GNUNET_free (pth); return ret; } @@ -551,8 +563,9 @@ ats_reserve_callback (void *cls, const struct GNUNET_PeerIdentity *peer, struct GSF_PeerTransmitHandle *pth; GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Reserved %d bytes / need to wait %llu ms for reservation\n", - (int) amount, (unsigned long long) res_delay.rel_value); + "Reserved %d bytes / need to wait %s for reservation\n", + (int) amount, + GNUNET_STRINGS_relative_time_to_string (res_delay, GNUNET_YES)); cp->rc = NULL; if (0 == amount) { @@ -562,16 +575,17 @@ ats_reserve_callback (void *cls, const struct GNUNET_PeerIdentity *peer, } cp->did_reserve = GNUNET_YES; pth = cp->pth_head; - if ((NULL != pth) && (NULL == pth->cth)) + if ((NULL != pth) && (NULL == cp->cth) && (0 == cp->cth_in_progress)) { /* reservation success, try transmission now! */ - pth->cth_in_progress++; - pth->cth = + cp->cth_in_progress++; + cp->cth = GNUNET_CORE_notify_transmit_ready (GSF_core, GNUNET_YES, pth->priority, GNUNET_TIME_absolute_get_remaining (pth->timeout), peer, pth->size, - &peer_transmit_ready_cb, pth); - GNUNET_assert (0 < pth->cth_in_progress--); + &peer_transmit_ready_cb, cp); + GNUNET_assert (NULL != cp->cth); + GNUNET_assert (0 < cp->cth_in_progress--); } } @@ -592,7 +606,7 @@ GSF_peer_connect_handler_ (const struct GNUNET_PeerIdentity *peer, { struct GSF_ConnectedPeer *cp; char *fn; - uint32_t trust; + uint32_t respect; GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Connected to peer %s\n", GNUNET_i2s (peer)); @@ -602,14 +616,15 @@ GSF_peer_connect_handler_ (const struct GNUNET_PeerIdentity *peer, cp->rc = GNUNET_ATS_reserve_bandwidth (ats, peer, DBLOCK_SIZE, &ats_reserve_callback, cp); - fn = get_trust_filename (peer); - if ((GNUNET_DISK_file_test (fn) == GNUNET_YES) && - (sizeof (trust) == GNUNET_DISK_fn_read (fn, &trust, sizeof (trust)))) - cp->disk_trust = cp->ppd.trust = ntohl (trust); + fn = get_respect_filename (peer); + if ((GNUNET_YES == GNUNET_DISK_file_test (fn)) && + (sizeof (respect) == GNUNET_DISK_fn_read (fn, &respect, sizeof (respect)))) + cp->disk_respect = cp->ppd.respect = ntohl (respect); GNUNET_free (fn); - cp->request_map = GNUNET_CONTAINER_multihashmap_create (128); + cp->request_map = GNUNET_CONTAINER_multihashmap_create (128, GNUNET_NO); GNUNET_break (GNUNET_OK == - GNUNET_CONTAINER_multihashmap_put (cp_map, &peer->hashPubKey, + GNUNET_CONTAINER_multihashmap_put (cp_map, + &GSF_connected_peer_get_identity2_ (cp)->hashPubKey, cp, GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY)); GNUNET_STATISTICS_set (GSF_stats, gettext_noop ("# peers connected"), @@ -687,7 +702,7 @@ GSF_handle_p2p_migration_stop_ (void *cls, msm = (const struct MigrationStopMessage *) message; cp = GSF_peer_get_ (other); - if (cp == NULL) + if (NULL == cp) { GNUNET_break (0); return GNUNET_OK; @@ -697,10 +712,11 @@ GSF_handle_p2p_migration_stop_ (void *cls, 1, GNUNET_NO); bt = GNUNET_TIME_relative_ntoh (msm->duration); GNUNET_log (GNUNET_ERROR_TYPE_INFO, - _("Migration of content to peer `%s' blocked for %llu ms\n"), - GNUNET_i2s (other), (unsigned long long) bt.rel_value); + _("Migration of content to peer `%s' blocked for %s\n"), + GNUNET_i2s (other), + GNUNET_STRINGS_relative_time_to_string (bt, GNUNET_YES)); cp->ppd.migration_blocked_until = GNUNET_TIME_relative_to_absolute (bt); - if (cp->mig_revive_task == GNUNET_SCHEDULER_NO_TASK) + if (GNUNET_SCHEDULER_NO_TASK == cp->mig_revive_task) { GSF_push_stop_ (cp); cp->mig_revive_task = @@ -725,7 +741,7 @@ copy_reply (void *cls, size_t buf_size, void *buf) struct PutMessage *pm = cls; size_t size; - if (buf != NULL) + if (NULL != buf) { GNUNET_assert (buf_size >= ntohs (pm->header.size)); size = ntohs (pm->header.size); @@ -754,11 +770,11 @@ copy_reply (void *cls, size_t buf_size, void *buf) */ static void free_pending_request (struct PeerRequest *peerreq, - const GNUNET_HashCode *query) + const struct GNUNET_HashCode *query) { struct GSF_ConnectedPeer *cp = peerreq->cp; - if (peerreq->kill_task != GNUNET_SCHEDULER_NO_TASK) + if (GNUNET_SCHEDULER_NO_TASK != peerreq->kill_task) { GNUNET_SCHEDULER_cancel (peerreq->kill_task); peerreq->kill_task = GNUNET_SCHEDULER_NO_TASK; @@ -781,7 +797,7 @@ free_pending_request (struct PeerRequest *peerreq, * @return GNUNET_YES (continue to iterate) */ static int -cancel_pending_request (void *cls, const GNUNET_HashCode * query, void *value) +cancel_pending_request (void *cls, const struct GNUNET_HashCode * query, void *value) { struct PeerRequest *peerreq = value; struct GSF_PendingRequest *pr = peerreq->pr; @@ -853,11 +869,12 @@ get_randomized_delay () GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK, 2 * GSF_avg_latency.rel_value + 1)); +#if INSANE_STATISTICS GNUNET_STATISTICS_update (GSF_stats, gettext_noop ("# artificial delays introduced (ms)"), ret.rel_value, GNUNET_NO); - +#endif return ret; } @@ -903,8 +920,8 @@ handle_p2p_reply (void *cls, enum GNUNET_BLOCK_EvaluationResult eval, free_pending_request (peerreq, &prd->query); return; } - GNUNET_break (type != GNUNET_BLOCK_TYPE_ANY); - if ((prd->type != type) && (prd->type != GNUNET_BLOCK_TYPE_ANY)) + GNUNET_break (GNUNET_BLOCK_TYPE_ANY != type); + if ((prd->type != type) && (GNUNET_BLOCK_TYPE_ANY != prd->type)) { GNUNET_STATISTICS_update (GSF_stats, gettext_noop @@ -924,7 +941,7 @@ handle_p2p_reply (void *cls, enum GNUNET_BLOCK_EvaluationResult eval, GNUNET_break (0); return; } - if ((reply_anonymity_level != UINT32_MAX) && (reply_anonymity_level > 1)) + if ((UINT32_MAX != reply_anonymity_level) && (reply_anonymity_level > 1)) { if (reply_anonymity_level - 1 > GSF_cover_content_count) { @@ -943,8 +960,8 @@ handle_p2p_reply (void *cls, enum GNUNET_BLOCK_EvaluationResult eval, pm->type = htonl (type); pm->expiration = GNUNET_TIME_absolute_hton (expiration); memcpy (&pm[1], data, data_len); - if ((reply_anonymity_level != UINT32_MAX) && (reply_anonymity_level != 0) && - (GSF_enable_randomized_delays == GNUNET_YES)) + if ((UINT32_MAX != reply_anonymity_level) && (0 != reply_anonymity_level) && + (GNUNET_YES == GSF_enable_randomized_delays)) { struct GSF_DelayedHandle *dh; @@ -962,7 +979,7 @@ handle_p2p_reply (void *cls, enum GNUNET_BLOCK_EvaluationResult eval, (void) GSF_peer_transmit_ (cp, GNUNET_NO, UINT32_MAX, REPLY_TIMEOUT, msize, ©_reply, pm); } - if (eval != GNUNET_BLOCK_EVALUATION_OK_LAST) + if (GNUNET_BLOCK_EVALUATION_OK_LAST != eval) return; if (GNUNET_SCHEDULER_NO_TASK == peerreq->kill_task) { @@ -977,38 +994,38 @@ handle_p2p_reply (void *cls, enum GNUNET_BLOCK_EvaluationResult eval, /** - * Increase the host credit by a value. + * Increase the peer's respect by a value. * - * @param cp which peer to change the trust value on + * @param cp which peer to change the respect value on * @param value is the int value by which the - * host credit is to be increased or decreased - * @returns the actual change in trust (positive or negative) + * peer's credit is to be increased or decreased + * @returns the actual change in respect (positive or negative) */ static int -change_host_trust (struct GSF_ConnectedPeer *cp, int value) +change_peer_respect (struct GSF_ConnectedPeer *cp, int value) { - if (value == 0) + if (0 == value) return 0; - GNUNET_assert (cp != NULL); + GNUNET_assert (NULL != cp); if (value > 0) { - if (cp->ppd.trust + value < cp->ppd.trust) + if (cp->ppd.respect + value < cp->ppd.respect) { - value = UINT32_MAX - cp->ppd.trust; - cp->ppd.trust = UINT32_MAX; + value = UINT32_MAX - cp->ppd.respect; + cp->ppd.respect = UINT32_MAX; } else - cp->ppd.trust += value; + cp->ppd.respect += value; } else { - if (cp->ppd.trust < -value) + if (cp->ppd.respect < -value) { - value = -cp->ppd.trust; - cp->ppd.trust = 0; + value = -cp->ppd.respect; + cp->ppd.respect = 0; } else - cp->ppd.trust += value; + cp->ppd.respect += value; } return value; } @@ -1016,7 +1033,7 @@ change_host_trust (struct GSF_ConnectedPeer *cp, int value) /** * We've received a request with the specified priority. Bound it - * according to how much we trust the given peer. + * according to how much we respect the given peer. * * @param prio_in requested priority * @param cp the peer making the request @@ -1031,17 +1048,19 @@ bound_priority (uint32_t prio_in, struct GSF_ConnectedPeer *cp) int ld; ld = GSF_test_get_load_too_high_ (0); - if (ld == GNUNET_SYSERR) + if (GNUNET_SYSERR == ld) { +#if INSANE_STATISTICS GNUNET_STATISTICS_update (GSF_stats, gettext_noop ("# requests done for free (low load)"), 1, GNUNET_NO); +#endif return 0; /* excess resources */ } if (prio_in > INT32_MAX) prio_in = INT32_MAX; - ret = -change_host_trust (cp, -(int) prio_in); + ret = -change_peer_respect (cp, -(int) prio_in); if (ret > 0) { if (ret > GSF_current_priorities + N) @@ -1050,19 +1069,19 @@ bound_priority (uint32_t prio_in, struct GSF_ConnectedPeer *cp) rret = ret; GSF_current_priorities = (GSF_current_priorities * (N - 1) + rret) / N; } - if ((ld == GNUNET_YES) && (ret > 0)) + if ((GNUNET_YES == ld) && (ret > 0)) { /* try with charging */ ld = GSF_test_get_load_too_high_ (ret); } - if (ld == GNUNET_YES) + if (GNUNET_YES == ld) { GNUNET_STATISTICS_update (GSF_stats, gettext_noop ("# request dropped, priority insufficient"), 1, GNUNET_NO); /* undo charge */ - change_host_trust (cp, (int) ret); + change_peer_respect (cp, (int) ret); return -1; /* not enough resources */ } else @@ -1124,13 +1143,13 @@ GSF_handle_p2p_query_ (const struct GNUNET_PeerIdentity *other, struct GSF_PendingRequestData *prd; struct GSF_ConnectedPeer *cp; struct GSF_ConnectedPeer *cps; - const GNUNET_HashCode *namespace; + const struct GNUNET_HashCode *namespace; const struct GNUNET_PeerIdentity *target; enum GSF_PendingRequestOptions options; uint16_t msize; const struct GetMessage *gm; unsigned int bits; - const GNUNET_HashCode *opt; + const struct GNUNET_HashCode *opt; uint32_t bm; size_t bfsize; uint32_t ttl_decrement; @@ -1160,13 +1179,13 @@ GSF_handle_p2p_query_ (const struct GNUNET_PeerIdentity *other, bits++; bm >>= 1; } - if (msize < sizeof (struct GetMessage) + bits * sizeof (GNUNET_HashCode)) + if (msize < sizeof (struct GetMessage) + bits * sizeof (struct GNUNET_HashCode)) { GNUNET_break_op (0); return NULL; } - opt = (const GNUNET_HashCode *) &gm[1]; - bfsize = msize - sizeof (struct GetMessage) - bits * sizeof (GNUNET_HashCode); + opt = (const struct GNUNET_HashCode *) &gm[1]; + bfsize = msize - sizeof (struct GetMessage) - bits * sizeof (struct GNUNET_HashCode); /* bfsize must be power of 2, check! */ if (0 != ((bfsize - 1) & bfsize)) { @@ -1190,7 +1209,7 @@ GSF_handle_p2p_query_ (const struct GNUNET_PeerIdentity *other, cp = GSF_peer_get_ ((const struct GNUNET_PeerIdentity *) &opt[bits++]); else cp = cps; - if (cp == NULL) + if (NULL == cp) { if (0 != (bm & GET_MESSAGE_BIT_RETURN_TO)) GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, @@ -1202,10 +1221,12 @@ GSF_handle_p2p_query_ (const struct GNUNET_PeerIdentity *other, GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Failed to find peer `%4s' in connection set. Dropping query.\n", GNUNET_i2s (other)); +#if INSANE_STATISTICS GNUNET_STATISTICS_update (GSF_stats, gettext_noop ("# requests dropped due to missing reverse route"), 1, GNUNET_NO); +#endif return NULL; } /* note that we can really only check load here since otherwise @@ -1224,12 +1245,12 @@ GSF_handle_p2p_query_ (const struct GNUNET_PeerIdentity *other, GNUNET_h2s (&gm->query), (unsigned int) type, GNUNET_i2s (other), (unsigned int) bm); namespace = (0 != (bm & GET_MESSAGE_BIT_SKS_NAMESPACE)) ? &opt[bits++] : NULL; - if ((type == GNUNET_BLOCK_TYPE_FS_SBLOCK) && (namespace == NULL)) + if ((GNUNET_BLOCK_TYPE_FS_SBLOCK == type) && (NULL == namespace)) { GNUNET_break_op (0); return NULL; } - if ((type != GNUNET_BLOCK_TYPE_FS_SBLOCK) && (namespace != NULL)) + if ((GNUNET_BLOCK_TYPE_FS_SBLOCK != type) && (NULL != namespace)) { GNUNET_break_op (0); return NULL; @@ -1279,7 +1300,7 @@ GSF_handle_p2p_query_ (const struct GNUNET_PeerIdentity *other, prd = GSF_pending_request_get_data_ (pr); if ((prd->type == type) && ((type != GNUNET_BLOCK_TYPE_FS_SBLOCK) || - (0 == memcmp (&prd->namespace, namespace, sizeof (GNUNET_HashCode))))) + (0 == memcmp (&prd->namespace, namespace, sizeof (struct GNUNET_HashCode))))) { if (prd->ttl.abs_value >= GNUNET_TIME_absolute_get ().abs_value + ttl) { @@ -1350,13 +1371,13 @@ peer_transmit_timeout (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) else if (GNUNET_NO == pth->is_query) GNUNET_assert (0 < cp->ppd.pending_replies--); GNUNET_LOAD_update (cp->ppd.transmission_delay, UINT64_MAX); - if (NULL != pth->cth) + if (NULL != cp->cth) { - GNUNET_CORE_notify_transmit_ready_cancel (pth->cth); - pth->cth = NULL; + GNUNET_CORE_notify_transmit_ready_cancel (cp->cth); + cp->cth = NULL; } pth->gmc (pth->gmc_cls, 0, NULL); - GNUNET_assert (0 == pth->cth_in_progress); + GNUNET_assert (0 == cp->cth_in_progress); GNUNET_free (pth); } @@ -1396,15 +1417,12 @@ GSF_peer_transmit_ (struct GSF_ConnectedPeer *cp, int is_query, /* insertion sort (by priority, descending) */ prev = NULL; pos = cp->pth_head; - while ((pos != NULL) && (pos->priority > priority)) + while ((NULL != pos) && (pos->priority > priority)) { prev = pos; pos = pos->next; } - if (prev == NULL) - GNUNET_CONTAINER_DLL_insert (cp->pth_head, cp->pth_tail, pth); - else - GNUNET_CONTAINER_DLL_insert_after (cp->pth_head, cp->pth_tail, prev, pth); + GNUNET_CONTAINER_DLL_insert_after (cp->pth_head, cp->pth_tail, prev, pth); if (GNUNET_YES == is_query) cp->ppd.pending_queries++; else if (GNUNET_NO == is_query) @@ -1426,23 +1444,17 @@ GSF_peer_transmit_cancel_ (struct GSF_PeerTransmitHandle *pth) { struct GSF_ConnectedPeer *cp; - if (pth->timeout_task != GNUNET_SCHEDULER_NO_TASK) + if (GNUNET_SCHEDULER_NO_TASK != pth->timeout_task) { GNUNET_SCHEDULER_cancel (pth->timeout_task); pth->timeout_task = GNUNET_SCHEDULER_NO_TASK; } - if (NULL != pth->cth) - { - GNUNET_CORE_notify_transmit_ready_cancel (pth->cth); - pth->cth = NULL; - } cp = pth->cp; GNUNET_CONTAINER_DLL_remove (cp->pth_head, cp->pth_tail, pth); if (GNUNET_YES == pth->is_query) GNUNET_assert (0 < cp->ppd.pending_queries--); else if (GNUNET_NO == pth->is_query) GNUNET_assert (0 < cp->ppd.pending_replies--); - GNUNET_assert (0 == pth->cth_in_progress); GNUNET_free (pth); } @@ -1556,20 +1568,20 @@ GSF_peer_disconnect_handler_ (void *cls, const struct GNUNET_PeerIdentity *peer) GNUNET_PEER_decrement_rcs (cp->ppd.last_p2p_replies, P2P_SUCCESS_LIST_SIZE); memset (cp->ppd.last_p2p_replies, 0, sizeof (cp->ppd.last_p2p_replies)); GSF_push_stop_ (cp); + if (NULL != cp->cth) + { + GNUNET_CORE_notify_transmit_ready_cancel (cp->cth); + cp->cth = NULL; + } + GNUNET_assert (0 == cp->cth_in_progress); while (NULL != (pth = cp->pth_head)) { - if (NULL != pth->cth) - { - GNUNET_CORE_notify_transmit_ready_cancel (pth->cth); - pth->cth = NULL; - } if (pth->timeout_task != GNUNET_SCHEDULER_NO_TASK) { GNUNET_SCHEDULER_cancel (pth->timeout_task); pth->timeout_task = GNUNET_SCHEDULER_NO_TASK; } GNUNET_CONTAINER_DLL_remove (cp->pth_head, cp->pth_tail, pth); - GNUNET_assert (0 == pth->cth_in_progress); pth->gmc (pth->gmc_cls, 0, NULL); GNUNET_free (pth); } @@ -1616,7 +1628,7 @@ struct IterationContext * @return GNUNET_YES to continue iteration */ static int -call_iterator (void *cls, const GNUNET_HashCode * key, void *value) +call_iterator (void *cls, const struct GNUNET_HashCode * key, void *value) { struct IterationContext *ic = cls; struct GSF_ConnectedPeer *cp = value; @@ -1646,7 +1658,7 @@ GSF_iterate_connected_peers_ (GSF_ConnectedPeerIterator it, void *it_cls) /** * Obtain the identity of a connected peer. * - * @param cp peer to reserve bandwidth from + * @param cp peer to get identity of * @param id identity to set (written to) */ void @@ -1658,6 +1670,20 @@ GSF_connected_peer_get_identity_ (const struct GSF_ConnectedPeer *cp, } +/** + * Obtain the identity of a connected peer. + * + * @param cp peer to get identity of + * @return reference to peer identity, valid until peer disconnects (!) + */ +const struct GNUNET_PeerIdentity * +GSF_connected_peer_get_identity2_ (const struct GSF_ConnectedPeer *cp) +{ + GNUNET_assert (0 != cp->ppd.pid); + return GNUNET_PEER_resolve2 (cp->ppd.pid); +} + + /** * Assemble a migration stop message for transmission. * @@ -1704,16 +1730,15 @@ GSF_block_peer_migration_ (struct GSF_ConnectedPeer *cp, if (cp->last_migration_block.abs_value > block_time.abs_value) { GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Migration already blocked for another %llu ms\n", - (unsigned long long) - GNUNET_TIME_absolute_get_remaining - (cp->last_migration_block).rel_value); + "Migration already blocked for another %s\n", + GNUNET_STRINGS_relative_time_to_string (GNUNET_TIME_absolute_get_remaining + (cp->last_migration_block), GNUNET_YES)); return; /* already blocked */ } GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Asking to stop migration for %llu ms\n", (unsigned long long) GNUNET_TIME_absolute_get_remaining (block_time).rel_value); cp->last_migration_block = block_time; - if (cp->migration_pth != NULL) + if (NULL != cp->migration_pth) GSF_peer_transmit_cancel_ (cp->migration_pth); cp->migration_pth = GSF_peer_transmit_ (cp, GNUNET_SYSERR, UINT32_MAX, @@ -1724,27 +1749,27 @@ GSF_block_peer_migration_ (struct GSF_ConnectedPeer *cp, /** - * Write host-trust information to a file - flush the buffer entry! + * Write peer-respect information to a file - flush the buffer entry! * - * @param cls closure, not used - * @param key host identity + * @param cls unused + * @param key peer identity * @param value the 'struct GSF_ConnectedPeer' to flush * @return GNUNET_OK to continue iteration */ static int -flush_trust (void *cls, const GNUNET_HashCode * key, void *value) +flush_respect (void *cls, const struct GNUNET_HashCode * key, void *value) { struct GSF_ConnectedPeer *cp = value; char *fn; - uint32_t trust; + uint32_t respect; struct GNUNET_PeerIdentity pid; - if (cp->ppd.trust == cp->disk_trust) + if (cp->ppd.respect == cp->disk_respect) return GNUNET_OK; /* unchanged */ GNUNET_assert (0 != cp->ppd.pid); GNUNET_PEER_resolve (cp->ppd.pid, &pid); - fn = get_trust_filename (&pid); - if (cp->ppd.trust == 0) + fn = get_respect_filename (&pid); + if (cp->ppd.respect == 0) { if ((0 != UNLINK (fn)) && (errno != ENOENT)) GNUNET_log_strerror_file (GNUNET_ERROR_TYPE_WARNING | @@ -1752,14 +1777,14 @@ flush_trust (void *cls, const GNUNET_HashCode * key, void *value) } else { - trust = htonl (cp->ppd.trust); + respect = htonl (cp->ppd.respect); if (sizeof (uint32_t) == - GNUNET_DISK_fn_write (fn, &trust, sizeof (uint32_t), + GNUNET_DISK_fn_write (fn, &respect, sizeof (uint32_t), GNUNET_DISK_PERM_USER_READ | GNUNET_DISK_PERM_USER_WRITE | GNUNET_DISK_PERM_GROUP_READ | GNUNET_DISK_PERM_OTHER_READ)) - cp->disk_trust = cp->ppd.trust; + cp->disk_respect = cp->ppd.respect; } GNUNET_free (fn); return GNUNET_OK; @@ -1784,25 +1809,25 @@ GSF_connected_peer_change_preference_ (struct GSF_ConnectedPeer *cp, /** - * Call this method periodically to flush trust information to disk. + * Call this method periodically to flush respect information to disk. * * @param cls closure, not used * @param tc task context, not used */ static void -cron_flush_trust (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +cron_flush_respect (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { if (NULL == cp_map) return; - GNUNET_CONTAINER_multihashmap_iterate (cp_map, &flush_trust, NULL); + GNUNET_CONTAINER_multihashmap_iterate (cp_map, &flush_respect, NULL); if (NULL == tc) return; if (0 != (tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN)) return; - GNUNET_SCHEDULER_add_delayed_with_priority (TRUST_FLUSH_FREQ, + GNUNET_SCHEDULER_add_delayed_with_priority (RESPECT_FLUSH_FREQ, GNUNET_SCHEDULER_PRIORITY_HIGH, - &cron_flush_trust, NULL); + &cron_flush_respect, NULL); } @@ -1812,15 +1837,15 @@ cron_flush_trust (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) void GSF_connected_peer_init_ () { - cp_map = GNUNET_CONTAINER_multihashmap_create (128); + cp_map = GNUNET_CONTAINER_multihashmap_create (128, GNUNET_YES); ats = GNUNET_ATS_performance_init (GSF_cfg, NULL, NULL); GNUNET_assert (GNUNET_OK == GNUNET_CONFIGURATION_get_value_filename (GSF_cfg, "fs", - "TRUST", - &trustDirectory)); - GNUNET_DISK_directory_create (trustDirectory); + "RESPECT", + &respectDirectory)); + GNUNET_DISK_directory_create (respectDirectory); GNUNET_SCHEDULER_add_with_priority (GNUNET_SCHEDULER_PRIORITY_HIGH, - &cron_flush_trust, NULL); + &cron_flush_respect, NULL); } @@ -1833,7 +1858,7 @@ GSF_connected_peer_init_ () * @return GNUNET_YES (we should continue to iterate) */ static int -clean_peer (void *cls, const GNUNET_HashCode * key, void *value) +clean_peer (void *cls, const struct GNUNET_HashCode * key, void *value) { GSF_peer_disconnect_handler_ (NULL, (const struct GNUNET_PeerIdentity *) key); return GNUNET_YES; @@ -1846,12 +1871,12 @@ clean_peer (void *cls, const GNUNET_HashCode * key, void *value) void GSF_connected_peer_done_ () { - cron_flush_trust (NULL, NULL); + cron_flush_respect (NULL, NULL); GNUNET_CONTAINER_multihashmap_iterate (cp_map, &clean_peer, NULL); GNUNET_CONTAINER_multihashmap_destroy (cp_map); cp_map = NULL; - GNUNET_free (trustDirectory); - trustDirectory = NULL; + GNUNET_free (respectDirectory); + respectDirectory = NULL; GNUNET_ATS_performance_done (ats); ats = NULL; } @@ -1866,7 +1891,7 @@ GSF_connected_peer_done_ () * @return GNUNET_YES (we should continue to iterate) */ static int -clean_local_client (void *cls, const GNUNET_HashCode * key, void *value) +clean_local_client (void *cls, const struct GNUNET_HashCode * key, void *value) { const struct GSF_LocalClient *lc = cls; struct GSF_ConnectedPeer *cp = value; diff --git a/src/fs/gnunet-service-fs_cp.h b/src/fs/gnunet-service-fs_cp.h index e3c7cd2..3bb05ac 100644 --- a/src/fs/gnunet-service-fs_cp.h +++ b/src/fs/gnunet-service-fs_cp.h @@ -133,9 +133,9 @@ struct GSF_PeerPerformanceData GNUNET_PEER_Id pid; /** - * Trust rating for this peer + * Respect rating for this peer */ - uint32_t trust; + uint32_t respect; /** * Number of pending queries (replies are not counted) @@ -384,7 +384,7 @@ GSF_connected_peer_change_preference_ (struct GSF_ConnectedPeer *cp, /** * Obtain the identity of a connected peer. * - * @param cp peer to reserve bandwidth from + * @param cp peer to get identity of * @param id identity to set (written to) */ void @@ -392,6 +392,17 @@ GSF_connected_peer_get_identity_ (const struct GSF_ConnectedPeer *cp, struct GNUNET_PeerIdentity *id); +/** + * Obtain the identity of a connected peer. + * + * @param cp peer to get identity of + * @return reference to peer identity, valid until peer disconnects (!) + */ +const struct GNUNET_PeerIdentity * +GSF_connected_peer_get_identity2_ (const struct GSF_ConnectedPeer *cp); + + + /** * Iterate over all connected peers. * diff --git a/src/fs/gnunet-service-fs_indexing.c b/src/fs/gnunet-service-fs_indexing.c index e452894..1baab4c 100644 --- a/src/fs/gnunet-service-fs_indexing.c +++ b/src/fs/gnunet-service-fs_indexing.c @@ -43,10 +43,15 @@ struct IndexInfo { /** - * This is a linked list. + * This is a doubly linked list. */ struct IndexInfo *next; + /** + * This is a doubly linked list. + */ + struct IndexInfo *prev; + /** * Name of the indexed file. Memory allocated * at the end of this struct (do not free). @@ -67,18 +72,23 @@ struct IndexInfo /** * Hash of the contents of the file. */ - GNUNET_HashCode file_id; + struct GNUNET_HashCode file_id; }; /** - * Linked list of indexed files. + * Head of linked list of indexed files. + */ +static struct IndexInfo *indexed_files_head; + +/** + * Tail of linked list of indexed files. */ -static struct IndexInfo *indexed_files; +static struct IndexInfo *indexed_files_tail; /** - * Maps hash over content of indexed files to the respective filename. + * Maps hash over content of indexed files to the respective 'struct IndexInfo'. * The filenames are pointers into the indexed_files linked list and * do not need to be freed. */ @@ -109,9 +119,8 @@ write_index_list () if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_filename (cfg, "FS", "INDEXDB", &fn)) { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR | GNUNET_ERROR_TYPE_BULK, - _("Configuration option `%s' in section `%s' missing.\n"), - "INDEXDB", "FS"); + GNUNET_log_config_missing (GNUNET_ERROR_TYPE_ERROR | GNUNET_ERROR_TYPE_BULK, + "fs", "INDEXDB"); return; } wh = GNUNET_BIO_write_open (fn); @@ -122,15 +131,11 @@ write_index_list () GNUNET_free (fn); return; } - pos = indexed_files; - while (pos != NULL) - { + for (pos = indexed_files_head; NULL != pos; pos = pos->next) if ((GNUNET_OK != - GNUNET_BIO_write (wh, &pos->file_id, sizeof (GNUNET_HashCode))) || + GNUNET_BIO_write (wh, &pos->file_id, sizeof (struct GNUNET_HashCode))) || (GNUNET_OK != GNUNET_BIO_write_string (wh, pos->filename))) break; - pos = pos->next; - } if (GNUNET_OK != GNUNET_BIO_write_close (wh)) { GNUNET_log (GNUNET_ERROR_TYPE_ERROR | GNUNET_ERROR_TYPE_BULK, @@ -152,16 +157,15 @@ read_index_list () char *fn; struct IndexInfo *pos; char *fname; - GNUNET_HashCode hc; + struct GNUNET_HashCode hc; size_t slen; char *emsg; if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_filename (cfg, "FS", "INDEXDB", &fn)) { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR | GNUNET_ERROR_TYPE_BULK, - _("Configuration option `%s' in section `%s' missing.\n"), - "INDEXDB", "FS"); + GNUNET_log_config_missing (GNUNET_ERROR_TYPE_ERROR | GNUNET_ERROR_TYPE_BULK, + "fs", "INDEXDB"); return; } if (GNUNET_NO == GNUNET_DISK_file_test (fn)) @@ -180,7 +184,7 @@ read_index_list () } while ((GNUNET_OK == GNUNET_BIO_read (rh, "Hash of indexed file", &hc, - sizeof (GNUNET_HashCode))) && + sizeof (struct GNUNET_HashCode))) && (GNUNET_OK == GNUNET_BIO_read_string (rh, "Name of indexed file", &fname, 1024 * 16)) && (fname != NULL)) @@ -191,15 +195,16 @@ read_index_list () pos->filename = (const char *) &pos[1]; memcpy (&pos[1], fname, slen); if (GNUNET_SYSERR == - GNUNET_CONTAINER_multihashmap_put (ifm, &hc, (void *) pos->filename, + GNUNET_CONTAINER_multihashmap_put (ifm, &pos->file_id, pos, GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY)) { GNUNET_free (pos); } else { - pos->next = indexed_files; - indexed_files = pos; + GNUNET_CONTAINER_DLL_insert (indexed_files_head, + indexed_files_tail, + pos); } GNUNET_free (fname); } @@ -218,25 +223,29 @@ read_index_list () static void signal_index_ok (struct IndexInfo *ii) { + struct IndexInfo *ir; if (GNUNET_SYSERR == GNUNET_CONTAINER_multihashmap_put (ifm, &ii->file_id, - (void *) ii->filename, + ii, GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY)) { + ir = GNUNET_CONTAINER_multihashmap_get (ifm, + &ii->file_id); + GNUNET_assert (NULL != ir); GNUNET_log (GNUNET_ERROR_TYPE_INFO, _ ("Index request received for file `%s' is already indexed as `%s'. Permitting anyway.\n"), ii->filename, - (const char *) GNUNET_CONTAINER_multihashmap_get (ifm, - &ii->file_id)); + ir->filename); GNUNET_SERVER_transmit_context_append_data (ii->tc, NULL, 0, GNUNET_MESSAGE_TYPE_FS_INDEX_START_OK); GNUNET_SERVER_transmit_context_run (ii->tc, GNUNET_TIME_UNIT_MINUTES); GNUNET_free (ii); return; } - ii->next = indexed_files; - indexed_files = ii; + GNUNET_CONTAINER_DLL_insert (indexed_files_head, + indexed_files_tail, + ii); write_index_list (); GNUNET_SERVER_transmit_context_append_data (ii->tc, NULL, 0, GNUNET_MESSAGE_TYPE_FS_INDEX_START_OK); @@ -253,13 +262,13 @@ signal_index_ok (struct IndexInfo *ii) * @param res resulting hash, NULL on error */ static void -hash_for_index_val (void *cls, const GNUNET_HashCode * res) +hash_for_index_val (void *cls, const struct GNUNET_HashCode * res) { struct IndexInfo *ii = cls; ii->fhc = NULL; if ((res == NULL) || - (0 != memcmp (res, &ii->file_id, sizeof (GNUNET_HashCode)))) + (0 != memcmp (res, &ii->file_id, sizeof (struct GNUNET_HashCode)))) { GNUNET_log (GNUNET_ERROR_TYPE_WARNING, _ @@ -375,8 +384,7 @@ GNUNET_FS_handle_index_list_get (void *cls, struct GNUNET_SERVER_Client *client, tc = GNUNET_SERVER_transmit_context_create (client); iim = (struct IndexInfoMessage *) buf; - pos = indexed_files; - while (NULL != pos) + for (pos = indexed_files_head; NULL != pos; pos = pos->next) { fn = pos->filename; slen = strlen (fn) + 1; @@ -392,7 +400,6 @@ GNUNET_FS_handle_index_list_get (void *cls, struct GNUNET_SERVER_Client *client, iim->file_id = pos->file_id; memcpy (&iim[1], fn, slen); GNUNET_SERVER_transmit_context_append_message (tc, &iim->header); - pos = pos->next; } GNUNET_SERVER_transmit_context_append_data (tc, NULL, 0, GNUNET_MESSAGE_TYPE_FS_INDEX_LIST_END); @@ -413,8 +420,6 @@ GNUNET_FS_handle_unindex (void *cls, struct GNUNET_SERVER_Client *client, { const struct UnindexMessage *um; struct IndexInfo *pos; - struct IndexInfo *prev; - struct IndexInfo *next; struct GNUNET_SERVER_TransmitContext *tc; int found; @@ -426,29 +431,20 @@ GNUNET_FS_handle_unindex (void *cls, struct GNUNET_SERVER_Client *client, return; } found = GNUNET_NO; - prev = NULL; - pos = indexed_files; - while (NULL != pos) + for (pos = indexed_files_head; NULL != pos; pos = pos->next) { - next = pos->next; - if (0 == memcmp (&pos->file_id, &um->file_id, sizeof (GNUNET_HashCode))) + if (0 == memcmp (&pos->file_id, &um->file_id, sizeof (struct GNUNET_HashCode))) { - if (prev == NULL) - indexed_files = next; - else - prev->next = next; + GNUNET_CONTAINER_DLL_remove (indexed_files_head, + indexed_files_tail, + pos); GNUNET_break (GNUNET_OK == GNUNET_CONTAINER_multihashmap_remove (ifm, &pos->file_id, - (void *) - pos->filename)); + pos)); GNUNET_free (pos); found = GNUNET_YES; + break; } - else - { - prev = pos; - } - pos = next; } GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Client requested unindexing of file `%s': %s\n", @@ -502,7 +498,7 @@ remove_cont (void *cls, int success, * @return GNUNET_OK on success */ int -GNUNET_FS_handle_on_demand_block (const GNUNET_HashCode * key, uint32_t size, +GNUNET_FS_handle_on_demand_block (const struct GNUNET_HashCode * key, uint32_t size, const void *data, enum GNUNET_BLOCK_Type type, uint32_t priority, uint32_t anonymity, struct GNUNET_TIME_Absolute expiration, @@ -511,16 +507,17 @@ GNUNET_FS_handle_on_demand_block (const GNUNET_HashCode * key, uint32_t size, void *cont_cls) { const struct OnDemandBlock *odb; - GNUNET_HashCode nkey; + struct GNUNET_HashCode nkey; struct GNUNET_CRYPTO_AesSessionKey skey; struct GNUNET_CRYPTO_AesInitializationVector iv; - GNUNET_HashCode query; + struct GNUNET_HashCode query; ssize_t nsize; char ndata[DBLOCK_SIZE]; char edata[DBLOCK_SIZE]; const char *fn; struct GNUNET_DISK_FileHandle *fh; uint64_t off; + struct IndexInfo *ii; if (size != sizeof (struct OnDemandBlock)) { @@ -531,7 +528,13 @@ GNUNET_FS_handle_on_demand_block (const GNUNET_HashCode * key, uint32_t size, } odb = (const struct OnDemandBlock *) data; off = GNUNET_ntohll (odb->offset); - fn = (const char *) GNUNET_CONTAINER_multihashmap_get (ifm, &odb->file_id); + ii = GNUNET_CONTAINER_multihashmap_get (ifm, &odb->file_id); + if (NULL == ii) + { + GNUNET_break (0); + return GNUNET_SYSERR; + } + fn = ii->filename; if ((NULL == fn) || (0 != ACCESS (fn, R_OK))) { GNUNET_STATISTICS_update (GSF_stats, @@ -565,7 +568,7 @@ GNUNET_FS_handle_on_demand_block (const GNUNET_HashCode * key, uint32_t size, GNUNET_CRYPTO_hash_to_aes_key (&nkey, &skey, &iv); GNUNET_CRYPTO_aes_encrypt (ndata, nsize, &skey, &iv, edata); GNUNET_CRYPTO_hash (edata, nsize, &query); - if (0 != memcmp (&query, key, sizeof (GNUNET_HashCode))) + if (0 != memcmp (&query, key, sizeof (struct GNUNET_HashCode))) { GNUNET_log (GNUNET_ERROR_TYPE_WARNING, _("Indexed file `%s' changed at offset %llu\n"), fn, @@ -590,15 +593,20 @@ GNUNET_FS_indexing_done () { struct IndexInfo *pos; - GNUNET_CONTAINER_multihashmap_destroy (ifm); - ifm = NULL; - while (NULL != (pos = indexed_files)) + while (NULL != (pos = indexed_files_head)) { - indexed_files = pos->next; + GNUNET_CONTAINER_DLL_remove (indexed_files_head, + indexed_files_tail, + pos); if (pos->fhc != NULL) GNUNET_CRYPTO_hash_file_cancel (pos->fhc); + GNUNET_break (GNUNET_OK == + GNUNET_CONTAINER_multihashmap_remove (ifm, + &pos->file_id, pos)); GNUNET_free (pos); } + GNUNET_CONTAINER_multihashmap_destroy (ifm); + ifm = NULL; cfg = NULL; } @@ -615,7 +623,7 @@ GNUNET_FS_indexing_init (const struct GNUNET_CONFIGURATION_Handle *c, { cfg = c; dsh = d; - ifm = GNUNET_CONTAINER_multihashmap_create (128); + ifm = GNUNET_CONTAINER_multihashmap_create (128, GNUNET_YES); read_index_list (); return GNUNET_OK; } diff --git a/src/fs/gnunet-service-fs_indexing.h b/src/fs/gnunet-service-fs_indexing.h index 4295b20..3bb0af2 100644 --- a/src/fs/gnunet-service-fs_indexing.h +++ b/src/fs/gnunet-service-fs_indexing.h @@ -55,7 +55,7 @@ * @return GNUNET_OK on success */ int -GNUNET_FS_handle_on_demand_block (const GNUNET_HashCode * key, uint32_t size, +GNUNET_FS_handle_on_demand_block (const struct GNUNET_HashCode * key, uint32_t size, const void *data, enum GNUNET_BLOCK_Type type, uint32_t priority, uint32_t anonymity, struct GNUNET_TIME_Absolute expiration, diff --git a/src/fs/gnunet-service-fs_lc.c b/src/fs/gnunet-service-fs_lc.c index 20d430e..c3b6f40 100644 --- a/src/fs/gnunet-service-fs_lc.c +++ b/src/fs/gnunet-service-fs_lc.c @@ -197,7 +197,7 @@ client_request_destroy (void *cls, cr->kill_task = GNUNET_SCHEDULER_NO_TASK; lc = cr->lc; GNUNET_CONTAINER_DLL_remove (lc->cr_head, lc->cr_tail, cr); - GSF_pending_request_cancel_ (cr->pr, GNUNET_NO); + GSF_pending_request_cancel_ (cr->pr, GNUNET_YES); GNUNET_STATISTICS_update (GSF_stats, gettext_noop ("# client searches active"), -1, GNUNET_NO); @@ -267,15 +267,22 @@ client_response_handler (void *cls, enum GNUNET_BLOCK_EvaluationResult eval, pm->type = htonl (type); pm->expiration = GNUNET_TIME_absolute_hton (expiration); pm->last_transmission = GNUNET_TIME_absolute_hton (last_transmission); + pm->num_transmissions = htonl (prd->num_transmissions); + pm->respect_offered = htonl (prd->respect_offered); memcpy (&pm[1], data, data_len); GSF_local_client_transmit_ (lc, &pm->header); } GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Queued reply to query `%s' for local client\n", GNUNET_h2s (&prd->query), (unsigned int) prd->type); - if (eval != GNUNET_BLOCK_EVALUATION_OK_LAST) + if (GNUNET_BLOCK_EVALUATION_OK_LAST != eval) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Evaluation %d - keeping query alive\n", + (int) eval); return; - if (GNUNET_SCHEDULER_NO_TASK != cr->kill_task) + } + if (GNUNET_SCHEDULER_NO_TASK == cr->kill_task) cr->kill_task = GNUNET_SCHEDULER_add_now (&client_request_destroy, cr); } @@ -299,7 +306,7 @@ GSF_local_client_start_search_handler_ (struct GNUNET_SERVER_Client *client, *message, struct GSF_PendingRequest **prptr) { - static GNUNET_HashCode all_zeros; + static struct GNUNET_HashCode all_zeros; const struct SearchMessage *sm; struct GSF_LocalClient *lc; struct ClientRequest *cr; @@ -311,7 +318,7 @@ GSF_local_client_start_search_handler_ (struct GNUNET_SERVER_Client *client, msize = ntohs (message->size); if ((msize < sizeof (struct SearchMessage)) || - (0 != (msize - sizeof (struct SearchMessage)) % sizeof (GNUNET_HashCode))) + (0 != (msize - sizeof (struct SearchMessage)) % sizeof (struct GNUNET_HashCode))) { GNUNET_break (0); *prptr = NULL; @@ -320,7 +327,7 @@ GSF_local_client_start_search_handler_ (struct GNUNET_SERVER_Client *client, GNUNET_STATISTICS_update (GSF_stats, gettext_noop ("# client searches received"), 1, GNUNET_NO); - sc = (msize - sizeof (struct SearchMessage)) / sizeof (GNUNET_HashCode); + sc = (msize - sizeof (struct SearchMessage)) / sizeof (struct GNUNET_HashCode); sm = (const struct SearchMessage *) message; type = ntohl (sm->type); GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, @@ -340,7 +347,7 @@ GSF_local_client_start_search_handler_ (struct GNUNET_SERVER_Client *client, (SEARCH_MESSAGE_OPTION_CONTINUED was always set) and that have a matching query and type */ if ((GNUNET_YES != prd->has_started) && - (0 != memcmp (&prd->query, &sm->query, sizeof (GNUNET_HashCode))) && + (0 != memcmp (&prd->query, &sm->query, sizeof (struct GNUNET_HashCode))) && (prd->type == type)) break; cr = cr->next; @@ -350,7 +357,7 @@ GSF_local_client_start_search_handler_ (struct GNUNET_SERVER_Client *client, { GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Have existing request, merging content-seen lists.\n"); - GSF_pending_request_update_ (cr->pr, (const GNUNET_HashCode *) &sm[1], sc); + GSF_pending_request_update_ (cr->pr, (const struct GNUNET_HashCode *) &sm[1], sc); GNUNET_STATISTICS_update (GSF_stats, gettext_noop ("# client searches updated (merged content seen list)"), @@ -371,7 +378,7 @@ GSF_local_client_start_search_handler_ (struct GNUNET_SERVER_Client *client, : NULL, (0 != memcmp (&sm->target, &all_zeros, - sizeof (GNUNET_HashCode))) + sizeof (struct GNUNET_HashCode))) ? (const struct GNUNET_PeerIdentity *) &sm->target : NULL, NULL, 0, 0 /* bf */ , @@ -380,7 +387,7 @@ GSF_local_client_start_search_handler_ (struct GNUNET_SERVER_Client *client, 0 /* ttl */ , 0 /* sender PID */ , 0 /* origin PID */ , - (const GNUNET_HashCode *) &sm[1], sc, + (const struct GNUNET_HashCode *) &sm[1], sc, &client_response_handler, cr); } *prptr = cr->pr; @@ -478,18 +485,13 @@ GSF_client_disconnect_handler_ (void *cls, struct GNUNET_SERVER_Client *client) pos = client_head; while ((pos != NULL) && (pos->client != client)) pos = pos->next; - if (pos == NULL) + if (NULL == pos) return; while (NULL != (cr = pos->cr_head)) { - GNUNET_CONTAINER_DLL_remove (pos->cr_head, pos->cr_tail, cr); - GSF_pending_request_cancel_ (cr->pr, GNUNET_NO); - GNUNET_STATISTICS_update (GSF_stats, - gettext_noop ("# client searches active"), -1, - GNUNET_NO); if (GNUNET_SCHEDULER_NO_TASK != cr->kill_task) GNUNET_SCHEDULER_cancel (cr->kill_task); - GNUNET_free (cr); + client_request_destroy (cr, NULL); } while (NULL != (res = pos->res_head)) { diff --git a/src/fs/gnunet-service-fs_pe.c b/src/fs/gnunet-service-fs_pe.c index 71b0fc0..0992d21 100644 --- a/src/fs/gnunet-service-fs_pe.c +++ b/src/fs/gnunet-service-fs_pe.c @@ -29,6 +29,10 @@ #include "gnunet-service-fs_pe.h" #include "gnunet-service-fs_pr.h" +/** + * Collect an instane number of statistics? May cause excessive IPC. + */ +#define INSANE_STATISTICS GNUNET_NO /** * List of GSF_PendingRequests this request plan @@ -43,61 +47,55 @@ struct PeerPlan; /** - * DLL of request plans a particular pending request is - * involved with. + * M:N binding of plans to pending requests. + * Each pending request can be in a number of plans, + * and each plan can have a number of pending requests. + * Objects of this type indicate a mapping of a plan to + * a particular pending request. + * + * The corresponding head and tail of the "PE" MDLL + * are stored in a 'struct GSF_RequestPlan'. (We need + * to be able to lookup all pending requests corresponding + * to a given plan entry.) + * + * Similarly head and tail of the "PR" MDLL are stored + * with the 'struct GSF_PendingRequest'. (We need + * to be able to lookup all plan entries corresponding + * to a given pending request.) */ -struct GSF_RequestPlanReference +struct GSF_PendingRequestPlanBijection { /** * This is a doubly-linked list. */ - struct GSF_RequestPlanReference *next; + struct GSF_PendingRequestPlanBijection *next_PR; /** * This is a doubly-linked list. */ - struct GSF_RequestPlanReference *prev; + struct GSF_PendingRequestPlanBijection *prev_PR; /** - * Associated request plan. - */ - struct GSF_RequestPlan *rp; - - /** - * Corresponding PendingRequestList. + * This is a doubly-linked list. */ - struct PendingRequestList *prl; -}; - - -/** - * List of GSF_PendingRequests this request plan - * participates with. - */ -struct PendingRequestList -{ + struct GSF_PendingRequestPlanBijection *next_PE; /** * This is a doubly-linked list. */ - struct PendingRequestList *next; + struct GSF_PendingRequestPlanBijection *prev_PE; /** - * This is a doubly-linked list. + * Associated request plan. */ - struct PendingRequestList *prev; + struct GSF_RequestPlan *rp; /** * Associated pending request. */ struct GSF_PendingRequest *pr; - /** - * Corresponding GSF_RequestPlanReference. - */ - struct GSF_RequestPlanReference *rpr; - }; @@ -133,12 +131,12 @@ struct GSF_RequestPlan /** * Head of list of associated pending requests. */ - struct PendingRequestList *prl_head; + struct GSF_PendingRequestPlanBijection *pe_head; /** * Tail of list of associated pending requests. */ - struct PendingRequestList *prl_tail; + struct GSF_PendingRequestPlanBijection *pe_tail; /** * Earliest time we'd be happy to (re)transmit this request. @@ -220,14 +218,20 @@ static unsigned long long plan_count; /** * Return the query (key in the plan_map) for the given request plan. + * Note that this key may change as there can be multiple pending + * requests for the same key and we just return _one_ of them; this + * particular one might complete while another one might still be + * active, hence the lifetime of the returned hash code is NOT + * necessarily identical to that of the 'struct GSF_RequestPlan' + * given. * * @param rp a request plan * @return the associated query */ -static const GNUNET_HashCode * +static const struct GNUNET_HashCode * get_rp_key (struct GSF_RequestPlan *rp) { - return &GSF_pending_request_get_data_ (rp->prl_head->pr)->query; + return &GSF_pending_request_get_data_ (rp->pe_head->pr)->query; } @@ -264,7 +268,7 @@ plan (struct PeerPlan *pp, struct GSF_RequestPlan *rp) GNUNET_STATISTICS_set (GSF_stats, gettext_noop ("# average retransmission delay (ms)"), total_delay * 1000LL / plan_count, GNUNET_NO); - prd = GSF_pending_request_get_data_ (rp->prl_head->pr); + prd = GSF_pending_request_get_data_ (rp->pe_head->pr); if (rp->transmission_counter < 8) delay = @@ -350,17 +354,19 @@ struct GSF_PendingRequest * get_latest (const struct GSF_RequestPlan *rp) { struct GSF_PendingRequest *ret; - struct PendingRequestList *prl; - - prl = rp->prl_head; - ret = prl->pr; - prl = prl->next; - while (NULL != prl) + struct GSF_PendingRequestPlanBijection *bi; + + bi = rp->pe_head; + if (NULL == bi) + return NULL; /* should never happen */ + ret = bi->pr; + bi = bi->next_PE; + while (NULL != bi) { - if (GSF_pending_request_get_data_ (prl->pr)->ttl.abs_value > + if (GSF_pending_request_get_data_ (bi->pr)->ttl.abs_value > GSF_pending_request_get_data_ (ret)->ttl.abs_value) - ret = prl->pr; - prl = prl->next; + ret = bi->pr; + bi = bi->next_PE; } return ret; } @@ -385,6 +391,9 @@ transmit_message_callback (void *cls, size_t buf_size, void *buf) if (NULL == buf) { /* failed, try again... */ + if (GNUNET_SCHEDULER_NO_TASK != pp->task) + GNUNET_SCHEDULER_cancel (pp->task); + pp->task = GNUNET_SCHEDULER_add_now (&schedule_peer_transmission, pp); GNUNET_STATISTICS_update (GSF_stats, gettext_noop @@ -395,12 +404,16 @@ transmit_message_callback (void *cls, size_t buf_size, void *buf) rp = GNUNET_CONTAINER_heap_peek (pp->priority_heap); if (NULL == rp) { + if (GNUNET_SCHEDULER_NO_TASK != pp->task) + GNUNET_SCHEDULER_cancel (pp->task); pp->task = GNUNET_SCHEDULER_add_now (&schedule_peer_transmission, pp); return 0; } msize = GSF_pending_request_get_message_ (get_latest (rp), buf_size, buf); if (msize > buf_size) { + if (GNUNET_SCHEDULER_NO_TASK != pp->task) + GNUNET_SCHEDULER_cancel (pp->task); /* buffer to small (message changed), try again */ pp->task = GNUNET_SCHEDULER_add_now (&schedule_peer_transmission, pp); return 0; @@ -439,7 +452,7 @@ schedule_peer_transmission (void *cls, struct GNUNET_TIME_Relative delay; pp->task = GNUNET_SCHEDULER_NO_TASK; - if (pp->pth != NULL) + if (NULL != pp->pth) { GSF_peer_transmit_cancel_ (pp->pth); pp->pth = NULL; @@ -473,8 +486,10 @@ schedule_peer_transmission (void *cls, GNUNET_SCHEDULER_add_delayed (delay, &schedule_peer_transmission, pp); return; } +#if INSANE_STATISTICS GNUNET_STATISTICS_update (GSF_stats, gettext_noop ("# query plans executed"), 1, GNUNET_NO); +#endif /* process from priority heap */ rp = GNUNET_CONTAINER_heap_peek (pp->priority_heap); GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Executing query plan %p\n", rp); @@ -512,37 +527,37 @@ struct MergeContext * GNUNET_NO if not (merge success) */ static int -merge_pr (void *cls, const GNUNET_HashCode * query, void *element) +merge_pr (void *cls, const struct GNUNET_HashCode * query, void *element) { struct MergeContext *mpr = cls; struct GSF_RequestPlan *rp = element; struct GSF_PendingRequestData *prd; - struct GSF_RequestPlanReference *rpr; - struct PendingRequestList *prl; + struct GSF_PendingRequestPlanBijection *bi; struct GSF_PendingRequest *latest; if (GNUNET_OK != - GSF_pending_request_is_compatible_ (mpr->pr, rp->prl_head->pr)) + GSF_pending_request_is_compatible_ (mpr->pr, rp->pe_head->pr)) return GNUNET_YES; /* merge new request with existing request plan */ - rpr = GNUNET_malloc (sizeof (struct GSF_RequestPlanReference)); - prl = GNUNET_malloc (sizeof (struct PendingRequestList)); - rpr->rp = rp; - rpr->prl = prl; - prl->rpr = rpr; - prl->pr = mpr->pr; + bi = GNUNET_malloc (sizeof (struct GSF_PendingRequestPlanBijection)); + bi->rp = rp; + bi->pr = mpr->pr; prd = GSF_pending_request_get_data_ (mpr->pr); - GNUNET_CONTAINER_DLL_insert (prd->rpr_head, prd->rpr_tail, rpr); - GNUNET_CONTAINER_DLL_insert (rp->prl_head, rp->prl_tail, prl); + GNUNET_CONTAINER_MDLL_insert (PR, prd->pr_head, prd->pr_tail, bi); + GNUNET_CONTAINER_MDLL_insert (PE, rp->pe_head, rp->pe_tail, bi); mpr->merged = GNUNET_YES; +#if INSANE_STATISTICS GNUNET_STATISTICS_update (GSF_stats, gettext_noop ("# requests merged"), 1, GNUNET_NO); +#endif latest = get_latest (rp); if (GSF_pending_request_get_data_ (latest)->ttl.abs_value < prd->ttl.abs_value) { +#if INSANE_STATISTICS GNUNET_STATISTICS_update (GSF_stats, gettext_noop ("# requests refreshed"), 1, GNUNET_NO); +#endif rp->transmission_counter = 0; /* reset */ } return GNUNET_NO; @@ -558,40 +573,40 @@ merge_pr (void *cls, const GNUNET_HashCode * query, void *element) void GSF_plan_add_ (struct GSF_ConnectedPeer *cp, struct GSF_PendingRequest *pr) { - struct GNUNET_PeerIdentity id; + const struct GNUNET_PeerIdentity *id; struct PeerPlan *pp; struct GSF_PendingRequestData *prd; struct GSF_RequestPlan *rp; - struct GSF_RequestPlanReference *rpr; - struct PendingRequestList *prl; + struct GSF_PendingRequestPlanBijection *bi; struct MergeContext mpc; GNUNET_assert (NULL != cp); - GSF_connected_peer_get_identity_ (cp, &id); - pp = GNUNET_CONTAINER_multihashmap_get (plans, &id.hashPubKey); + id = GSF_connected_peer_get_identity2_ (cp); + pp = GNUNET_CONTAINER_multihashmap_get (plans, &id->hashPubKey); if (NULL == pp) { pp = GNUNET_malloc (sizeof (struct PeerPlan)); - pp->plan_map = GNUNET_CONTAINER_multihashmap_create (128); + pp->plan_map = GNUNET_CONTAINER_multihashmap_create (128, GNUNET_NO); pp->priority_heap = GNUNET_CONTAINER_heap_create (GNUNET_CONTAINER_HEAP_ORDER_MAX); pp->delay_heap = GNUNET_CONTAINER_heap_create (GNUNET_CONTAINER_HEAP_ORDER_MIN); pp->cp = cp; - GNUNET_CONTAINER_multihashmap_put (plans, &id.hashPubKey, pp, + GNUNET_CONTAINER_multihashmap_put (plans, + &id->hashPubKey, pp, GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY); } mpc.merged = GNUNET_NO; mpc.pr = pr; GNUNET_CONTAINER_multihashmap_get_multiple (pp->plan_map, &GSF_pending_request_get_data_ - (pr)->query, &merge_pr, &mpc); - if (mpc.merged != GNUNET_NO) + (pr)->query, &merge_pr, &mpc); // 8 MB in 'merge_pr' + if (GNUNET_NO != mpc.merged) return; GNUNET_CONTAINER_multihashmap_get_multiple (pp->plan_map, &GSF_pending_request_get_data_ (pr)->query, &merge_pr, &mpc); - if (mpc.merged != GNUNET_NO) + if (GNUNET_NO != mpc.merged) return; plan_count++; GNUNET_STATISTICS_update (GSF_stats, gettext_noop ("# query plan entries"), 1, @@ -599,22 +614,19 @@ GSF_plan_add_ (struct GSF_ConnectedPeer *cp, struct GSF_PendingRequest *pr) prd = GSF_pending_request_get_data_ (pr); GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Planning transmission of query `%s' to peer `%s'\n", - GNUNET_h2s (&prd->query), GNUNET_i2s (&id)); - rp = GNUNET_malloc (sizeof (struct GSF_RequestPlan)); - rpr = GNUNET_malloc (sizeof (struct GSF_RequestPlanReference)); - prl = GNUNET_malloc (sizeof (struct PendingRequestList)); - rpr->rp = rp; - rpr->prl = prl; - prl->rpr = rpr; - prl->pr = pr; - GNUNET_CONTAINER_DLL_insert (prd->rpr_head, prd->rpr_tail, rpr); - GNUNET_CONTAINER_DLL_insert (rp->prl_head, rp->prl_tail, prl); + GNUNET_h2s (&prd->query), GNUNET_i2s (id)); + rp = GNUNET_malloc (sizeof (struct GSF_RequestPlan)); // 8 MB + bi = GNUNET_malloc (sizeof (struct GSF_PendingRequestPlanBijection)); + bi->rp = rp; + bi->pr = pr; + GNUNET_CONTAINER_MDLL_insert (PR, prd->pr_head, prd->pr_tail, bi); + GNUNET_CONTAINER_MDLL_insert (PE, rp->pe_head, rp->pe_tail, bi); rp->pp = pp; GNUNET_assert (GNUNET_YES == GNUNET_CONTAINER_multihashmap_put (pp->plan_map, get_rp_key (rp), rp, - GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE)); - plan (pp, rp); + GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE)); // 8 MB + plan (pp, rp); // +5 MB (plan/heap-insert) } @@ -627,21 +639,24 @@ GSF_plan_add_ (struct GSF_ConnectedPeer *cp, struct GSF_PendingRequest *pr) void GSF_plan_notify_peer_disconnect_ (const struct GSF_ConnectedPeer *cp) { - struct GNUNET_PeerIdentity id; + const struct GNUNET_PeerIdentity *id; struct PeerPlan *pp; struct GSF_RequestPlan *rp; struct GSF_PendingRequestData *prd; - struct PendingRequestList *prl; + struct GSF_PendingRequestPlanBijection *bi; - GSF_connected_peer_get_identity_ (cp, &id); - pp = GNUNET_CONTAINER_multihashmap_get (plans, &id.hashPubKey); + id = GSF_connected_peer_get_identity2_ (cp); + pp = GNUNET_CONTAINER_multihashmap_get (plans, &id->hashPubKey); if (NULL == pp) return; /* nothing was ever planned for this peer */ GNUNET_assert (GNUNET_YES == - GNUNET_CONTAINER_multihashmap_remove (plans, &id.hashPubKey, + GNUNET_CONTAINER_multihashmap_remove (plans, &id->hashPubKey, pp)); if (NULL != pp->pth) + { GSF_peer_transmit_cancel_ (pp->pth); + pp->pth = NULL; + } if (GNUNET_SCHEDULER_NO_TASK != pp->task) { GNUNET_SCHEDULER_cancel (pp->task); @@ -652,14 +667,14 @@ GSF_plan_notify_peer_disconnect_ (const struct GSF_ConnectedPeer *cp) GNUNET_break (GNUNET_YES == GNUNET_CONTAINER_multihashmap_remove (pp->plan_map, get_rp_key (rp), rp)); - while (NULL != (prl = rp->prl_head)) + while (NULL != (bi = rp->pe_head)) { - GNUNET_CONTAINER_DLL_remove (rp->prl_head, rp->prl_tail, prl); - prd = GSF_pending_request_get_data_ (prl->pr); - GNUNET_CONTAINER_DLL_remove (prd->rpr_head, prd->rpr_tail, prl->rpr); - GNUNET_free (prl->rpr); - GNUNET_free (prl); + GNUNET_CONTAINER_MDLL_remove (PE, rp->pe_head, rp->pe_tail, bi); + prd = GSF_pending_request_get_data_ (bi->pr); + GNUNET_CONTAINER_MDLL_remove (PR, prd->pr_head, prd->pr_tail, bi); + GNUNET_free (bi); } + plan_count--; GNUNET_free (rp); } GNUNET_CONTAINER_heap_destroy (pp->priority_heap); @@ -668,50 +683,55 @@ GSF_plan_notify_peer_disconnect_ (const struct GSF_ConnectedPeer *cp) GNUNET_break (GNUNET_YES == GNUNET_CONTAINER_multihashmap_remove (pp->plan_map, get_rp_key (rp), rp)); - while (NULL != (prl = rp->prl_head)) + while (NULL != (bi = rp->pe_head)) { - GNUNET_CONTAINER_DLL_remove (rp->prl_head, rp->prl_tail, prl); - prd = GSF_pending_request_get_data_ (prl->pr); - GNUNET_CONTAINER_DLL_remove (prd->rpr_head, prd->rpr_tail, prl->rpr); - GNUNET_free (prl->rpr); - GNUNET_free (prl); + prd = GSF_pending_request_get_data_ (bi->pr); + GNUNET_CONTAINER_MDLL_remove (PE, rp->pe_head, rp->pe_tail, bi); + GNUNET_CONTAINER_MDLL_remove (PR, prd->pr_head, prd->pr_tail, bi); + GNUNET_free (bi); } + plan_count--; GNUNET_free (rp); } GNUNET_STATISTICS_set (GSF_stats, gettext_noop ("# query plan entries"), plan_count, GNUNET_NO); - GNUNET_CONTAINER_heap_destroy (pp->delay_heap); GNUNET_CONTAINER_multihashmap_destroy (pp->plan_map); GNUNET_free (pp); } + /** * Get the last transmission attempt time for the request plan list - * referenced by 'rpr_head', that was sent to 'sender' + * referenced by 'pr_head', that was sent to 'sender' * - * @param rpr_head request plan reference list to check. + * @param pr_head request plan reference list to check. * @param sender the peer that we've sent the request to. - * @param result the timestamp to fill. + * @param result the timestamp to fill, set to "FOREVER" if never transmitted * @return GNUNET_YES if 'result' was changed, GNUNET_NO otherwise. */ int GSF_request_plan_reference_get_last_transmission_ ( - struct GSF_RequestPlanReference *rpr_head, struct GSF_ConnectedPeer *sender, + struct GSF_PendingRequestPlanBijection *pr_head, struct GSF_ConnectedPeer *sender, struct GNUNET_TIME_Absolute *result) { - struct GSF_RequestPlanReference *rpr; - for (rpr = rpr_head; rpr; rpr = rpr->next) + struct GSF_PendingRequestPlanBijection *bi; + + for (bi = pr_head; NULL != bi; bi = bi->next_PR) { - if (rpr->rp->pp->cp == sender) + if (bi->rp->pp->cp == sender) { - *result = rpr->rp->last_transmission; + if (0 == bi->rp->last_transmission.abs_value) + *result = GNUNET_TIME_UNIT_FOREVER_ABS; + else + *result = bi->rp->last_transmission; return GNUNET_YES; } } return GNUNET_NO; } + /** * Notify the plan about a request being done; destroy all entries * associated with this request. @@ -723,27 +743,26 @@ GSF_plan_notify_request_done_ (struct GSF_PendingRequest *pr) { struct GSF_RequestPlan *rp; struct GSF_PendingRequestData *prd; - struct GSF_RequestPlanReference *rpr; + struct GSF_PendingRequestPlanBijection *bi; prd = GSF_pending_request_get_data_ (pr); - while (NULL != (rpr = prd->rpr_head)) + while (NULL != (bi = prd->pr_head)) { - GNUNET_CONTAINER_DLL_remove (prd->rpr_head, prd->rpr_tail, rpr); - rp = rpr->rp; - GNUNET_CONTAINER_DLL_remove (rp->prl_head, rp->prl_tail, rpr->prl); - if (NULL == rp->prl_head) + rp = bi->rp; + GNUNET_CONTAINER_MDLL_remove (PR, prd->pr_head, prd->pr_tail, bi); + GNUNET_CONTAINER_MDLL_remove (PE, rp->pe_head, rp->pe_tail, bi); + if (NULL == rp->pe_head) { GNUNET_CONTAINER_heap_remove_node (rp->hn); plan_count--; GNUNET_break (GNUNET_YES == GNUNET_CONTAINER_multihashmap_remove (rp->pp->plan_map, - &GSF_pending_request_get_data_ - (rpr->prl->pr)->query, + &GSF_pending_request_get_data_ + (bi->pr)->query, rp)); GNUNET_free (rp); } - GNUNET_free (rpr->prl); - GNUNET_free (rpr); + GNUNET_free (bi); } GNUNET_STATISTICS_set (GSF_stats, gettext_noop ("# query plan entries"), plan_count, GNUNET_NO); @@ -756,7 +775,7 @@ GSF_plan_notify_request_done_ (struct GSF_PendingRequest *pr) void GSF_plan_init () { - plans = GNUNET_CONTAINER_multihashmap_create (256); + plans = GNUNET_CONTAINER_multihashmap_create (256, GNUNET_YES); } diff --git a/src/fs/gnunet-service-fs_pe.h b/src/fs/gnunet-service-fs_pe.h index 3a18715..d136267 100644 --- a/src/fs/gnunet-service-fs_pe.h +++ b/src/fs/gnunet-service-fs_pe.h @@ -62,15 +62,15 @@ GSF_plan_notify_request_done_ (struct GSF_PendingRequest *pr); * Get the last transmission attempt time for the request plan list * referenced by 'rpr_head', that was sent to 'sender' * - * @param rpr_head request plan reference list to check. + * @param pr_head request plan reference list to check. * @param sender the peer that we've sent the request to. * @param result the timestamp to fill. * @return GNUNET_YES if 'result' was changed, GNUNET_NO otherwise. */ int -GSF_request_plan_reference_get_last_transmission_ ( - struct GSF_RequestPlanReference *rpr_head, struct GSF_ConnectedPeer *sender, - struct GNUNET_TIME_Absolute *result); +GSF_request_plan_reference_get_last_transmission_ (struct GSF_PendingRequestPlanBijection *pr_head, + struct GSF_ConnectedPeer *sender, + struct GNUNET_TIME_Absolute *result); /** * Initialize plan subsystem. diff --git a/src/fs/gnunet-service-fs_pr.c b/src/fs/gnunet-service-fs_pr.c index 8ca4121..76e04f5 100644 --- a/src/fs/gnunet-service-fs_pr.c +++ b/src/fs/gnunet-service-fs_pr.c @@ -1,6 +1,6 @@ /* This file is part of GNUnet. - (C) 2009, 2010, 2011 Christian Grothoff (and other contributing authors) + (C) 2009, 2010, 2011, 2012 Christian Grothoff (and other contributing authors) GNUnet is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published @@ -30,6 +30,13 @@ #include "gnunet-service-fs_indexing.h" #include "gnunet-service-fs_pe.h" #include "gnunet-service-fs_pr.h" +#include "gnunet-service-fs_stream.h" + + +/** + * Desired replication level for GETs. + */ +#define DHT_GET_REPLICATION 5 /** * Maximum size of the datastore queue for P2P operations. Needs to @@ -51,6 +58,18 @@ */ #define MAX_RESULTS (100 * 1024) +/** + * Collect an instane number of statistics? May cause excessive IPC. + */ +#define INSANE_STATISTICS GNUNET_NO + +/** + * If obtaining a block via stream fails, how often do we retry it before + * giving up for good (and sticking to non-anonymous transfer)? + */ +#define STREAM_RETRY_MAX 3 + + /** * An active request. */ @@ -74,7 +93,7 @@ struct GSF_PendingRequest /** * Array of hash codes of replies we've already seen. */ - GNUNET_HashCode *replies_seen; + struct GNUNET_HashCode *replies_seen; /** * Bloomfilter masking replies we've already seen. @@ -96,6 +115,11 @@ struct GSF_PendingRequest */ struct GNUNET_DHT_GetHandle *gh; + /** + * Stream request handle for this request (or NULL for none). + */ + struct GSF_StreamRequest *stream_request; + /** * Function to call upon completion of the local get * request, or NULL for none. @@ -148,6 +172,12 @@ struct GSF_PendingRequest */ uint64_t first_uid; + /** + * How often have we retried this request via 'stream'? + * (used to bound overall retries). + */ + unsigned int stream_retry_count; + /** * Number of valid entries in the 'replies_seen' array. */ @@ -190,12 +220,6 @@ static struct GNUNET_LOAD_Value *datastore_put_load; static int active_to_migration; -/** - * Size of the datastore queue we assume for common requests. - * Determined based on the network quota. - */ -static unsigned int datastore_queue_size; - /** * Heap with the request that will expire next at the top. Contains * pointers of type "struct PendingRequest*"; these will *also* be @@ -263,40 +287,52 @@ refresh_bloomfilter (struct GSF_PendingRequest *pr) struct GSF_PendingRequest * GSF_pending_request_create_ (enum GSF_PendingRequestOptions options, enum GNUNET_BLOCK_Type type, - const GNUNET_HashCode * query, - const GNUNET_HashCode * namespace, + const struct GNUNET_HashCode *query, + const struct GNUNET_HashCode *namespace, const struct GNUNET_PeerIdentity *target, const char *bf_data, size_t bf_size, uint32_t mingle, uint32_t anonymity_level, uint32_t priority, int32_t ttl, GNUNET_PEER_Id sender_pid, GNUNET_PEER_Id origin_pid, - const GNUNET_HashCode * replies_seen, + const struct GNUNET_HashCode *replies_seen, unsigned int replies_seen_count, GSF_PendingRequestReplyHandler rh, void *rh_cls) { struct GSF_PendingRequest *pr; struct GSF_PendingRequest *dpr; + size_t extra; + struct GNUNET_HashCode *eptr; GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Creating request handle for `%s' of type %d\n", GNUNET_h2s (query), type); +#if INSANE_STATISTICS GNUNET_STATISTICS_update (GSF_stats, gettext_noop ("# Pending requests created"), 1, GNUNET_NO); - pr = GNUNET_malloc (sizeof (struct GSF_PendingRequest)); +#endif + extra = 0; + if (GNUNET_BLOCK_TYPE_FS_SBLOCK == type) + extra += sizeof (struct GNUNET_HashCode); + if (NULL != target) + extra += sizeof (struct GNUNET_PeerIdentity); + pr = GNUNET_malloc (sizeof (struct GSF_PendingRequest) + extra); pr->local_result_offset = GNUNET_CRYPTO_random_u64 (GNUNET_CRYPTO_QUALITY_WEAK, UINT64_MAX); pr->public_data.query = *query; + eptr = (struct GNUNET_HashCode *) &pr[1]; if (GNUNET_BLOCK_TYPE_FS_SBLOCK == type) { - GNUNET_assert (NULL != namespace); - pr->public_data.namespace = *namespace; + GNUNET_assert (NULL != namespace); + pr->public_data.namespace = eptr; + memcpy (eptr, namespace, sizeof (struct GNUNET_HashCode)); + eptr++; } if (NULL != target) { - pr->public_data.target = *target; - pr->public_data.has_target = GNUNET_YES; + pr->public_data.target = (struct GNUNET_PeerIdentity *) eptr; + memcpy (eptr, target, sizeof (struct GNUNET_PeerIdentity)); } pr->public_data.anonymity_level = anonymity_level; pr->public_data.priority = priority; @@ -324,9 +360,9 @@ GSF_pending_request_create_ (enum GSF_PendingRequestOptions options, { pr->replies_seen_size = replies_seen_count; pr->replies_seen = - GNUNET_malloc (sizeof (GNUNET_HashCode) * pr->replies_seen_size); + GNUNET_malloc (sizeof (struct GNUNET_HashCode) * pr->replies_seen_size); memcpy (pr->replies_seen, replies_seen, - replies_seen_count * sizeof (GNUNET_HashCode)); + replies_seen_count * sizeof (struct GNUNET_HashCode)); pr->replies_seen_count = replies_seen_count; } if (NULL != bf_data) @@ -341,7 +377,8 @@ GSF_pending_request_create_ (enum GSF_PendingRequestOptions options, { refresh_bloomfilter (pr); } - GNUNET_CONTAINER_multihashmap_put (pr_map, query, pr, + GNUNET_CONTAINER_multihashmap_put (pr_map, + &pr->public_data.query, pr, GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE); if (0 == (options & GSF_PRO_REQUEST_NEVER_EXPIRES)) { @@ -398,11 +435,12 @@ GSF_pending_request_is_compatible_ (struct GSF_PendingRequest *pra, if ((pra->public_data.type != prb->public_data.type) || (0 != memcmp (&pra->public_data.query, &prb->public_data.query, - sizeof (GNUNET_HashCode))) || + sizeof (struct GNUNET_HashCode))) || ((pra->public_data.type == GNUNET_BLOCK_TYPE_FS_SBLOCK) && (0 != - memcmp (&pra->public_data.namespace, &prb->public_data.namespace, - sizeof (GNUNET_HashCode))))) + memcmp (pra->public_data.namespace, + prb->public_data.namespace, + sizeof (struct GNUNET_HashCode))))) return GNUNET_NO; return GNUNET_OK; } @@ -419,11 +457,11 @@ GSF_pending_request_is_compatible_ (struct GSF_PendingRequest *pra, */ void GSF_pending_request_update_ (struct GSF_PendingRequest *pr, - const GNUNET_HashCode * replies_seen, + const struct GNUNET_HashCode * replies_seen, unsigned int replies_seen_count) { unsigned int i; - GNUNET_HashCode mhash; + struct GNUNET_HashCode mhash; if (replies_seen_count + pr->replies_seen_count < pr->replies_seen_count) return; /* integer overflow */ @@ -434,7 +472,7 @@ GSF_pending_request_update_ (struct GSF_PendingRequest *pr, GNUNET_array_grow (pr->replies_seen, pr->replies_seen_size, replies_seen_count + pr->replies_seen_count); memcpy (&pr->replies_seen[pr->replies_seen_count], replies_seen, - sizeof (GNUNET_HashCode) * replies_seen_count); + sizeof (struct GNUNET_HashCode) * replies_seen_count); pr->replies_seen_count += replies_seen_count; refresh_bloomfilter (pr); } @@ -459,6 +497,10 @@ GSF_pending_request_update_ (struct GSF_PendingRequest *pr, } } } + if (NULL != pr->gh) + GNUNET_DHT_get_filter_known_results (pr->gh, + replies_seen_count, + replies_seen); } @@ -477,7 +519,7 @@ GSF_pending_request_get_message_ (struct GSF_PendingRequest *pr, { char lbuf[GNUNET_SERVER_MAX_MESSAGE_SIZE]; struct GetMessage *gm; - GNUNET_HashCode *ext; + struct GNUNET_HashCode *ext; size_t msize; unsigned int k; uint32_t bm; @@ -509,13 +551,13 @@ GSF_pending_request_get_message_ (struct GSF_PendingRequest *pr, bm |= GET_MESSAGE_BIT_SKS_NAMESPACE; k++; } - if (GNUNET_YES == pr->public_data.has_target) + if (NULL != pr->public_data.target) { bm |= GET_MESSAGE_BIT_TRANSMIT_TO; k++; } bf_size = GNUNET_CONTAINER_bloomfilter_get_size (pr->bf); - msize = sizeof (struct GetMessage) + bf_size + k * sizeof (GNUNET_HashCode); + msize = sizeof (struct GetMessage) + bf_size + k * sizeof (struct GNUNET_HashCode); GNUNET_assert (msize < GNUNET_SERVER_MAX_MESSAGE_SIZE); if (buf_size < msize) return msize; @@ -530,6 +572,8 @@ GSF_pending_request_get_message_ (struct GSF_PendingRequest *pr, else prio = 0; pr->public_data.priority -= prio; + pr->public_data.num_transmissions++; + pr->public_data.respect_offered += prio; gm->priority = htonl (prio); now = GNUNET_TIME_absolute_get (); ttl = (int64_t) (pr->public_data.ttl.abs_value - now.abs_value); @@ -537,15 +581,17 @@ GSF_pending_request_get_message_ (struct GSF_PendingRequest *pr, gm->filter_mutator = htonl (pr->mingle); gm->hash_bitmap = htonl (bm); gm->query = pr->public_data.query; - ext = (GNUNET_HashCode *) & gm[1]; + ext = (struct GNUNET_HashCode *) & gm[1]; k = 0; if (!do_route) GNUNET_PEER_resolve (pr->sender_pid, (struct GNUNET_PeerIdentity *) &ext[k++]); if (GNUNET_BLOCK_TYPE_FS_SBLOCK == pr->public_data.type) - memcpy (&ext[k++], &pr->public_data.namespace, sizeof (GNUNET_HashCode)); - if (GNUNET_YES == pr->public_data.has_target) - ext[k++] = pr->public_data.target.hashPubKey; + memcpy (&ext[k++], pr->public_data.namespace, sizeof (struct GNUNET_HashCode)); + if (NULL != pr->public_data.target) + memcpy (&ext[k++], + pr->public_data.target, + sizeof (struct GNUNET_PeerIdentity)); if (pr->bf != NULL) GNUNET_assert (GNUNET_SYSERR != GNUNET_CONTAINER_bloomfilter_get_raw_data (pr->bf, @@ -565,7 +611,7 @@ GSF_pending_request_get_message_ (struct GSF_PendingRequest *pr, * @return GNUNET_YES (we should continue to iterate) */ static int -clean_request (void *cls, const GNUNET_HashCode * key, void *value) +clean_request (void *cls, const struct GNUNET_HashCode * key, void *value) { struct GSF_PendingRequest *pr = value; GSF_LocalLookupContinuation cont; @@ -603,6 +649,11 @@ clean_request (void *cls, const GNUNET_HashCode * key, void *value) GNUNET_DHT_get_stop (pr->gh); pr->gh = NULL; } + if (NULL != pr->stream_request) + { + GSF_stream_query_cancel (pr->stream_request); + pr->stream_request = NULL; + } if (GNUNET_SCHEDULER_NO_TASK != pr->warn_task) { GNUNET_SCHEDULER_cancel (pr->warn_task); @@ -655,6 +706,11 @@ GSF_pending_request_cancel_ (struct GSF_PendingRequest *pr, int full_cleanup) GNUNET_DHT_get_stop (pr->gh); pr->gh = NULL; } + if (NULL != pr->stream_request) + { + GSF_stream_query_cancel (pr->stream_request); + pr->stream_request = NULL; + } if (GNUNET_SCHEDULER_NO_TASK != pr->warn_task) { GNUNET_SCHEDULER_cancel (pr->warn_task); @@ -763,11 +819,11 @@ update_request_performance_data (struct ProcessReplyClosure *prq, * @return GNUNET_YES (we should continue to iterate) */ static int -process_reply (void *cls, const GNUNET_HashCode * key, void *value) +process_reply (void *cls, const struct GNUNET_HashCode * key, void *value) { struct ProcessReplyClosure *prq = cls; struct GSF_PendingRequest *pr = value; - GNUNET_HashCode chash; + struct GNUNET_HashCode chash; struct GNUNET_TIME_Absolute last_transmission; if (NULL == pr->rh) @@ -780,10 +836,10 @@ process_reply (void *cls, const GNUNET_HashCode * key, void *value) GNUNET_NO); prq->eval = GNUNET_BLOCK_evaluate (GSF_block_ctx, prq->type, key, &pr->bf, pr->mingle, - &pr->public_data.namespace, + pr->public_data.namespace, (prq->type == GNUNET_BLOCK_TYPE_FS_SBLOCK) ? - sizeof (GNUNET_HashCode) : 0, prq->data, + sizeof (struct GNUNET_HashCode) : 0, prq->data, prq->size); switch (prq->eval) { @@ -796,20 +852,33 @@ process_reply (void *cls, const GNUNET_HashCode * key, void *value) GNUNET_LOAD_update (GSF_rt_entry_lifetime, GNUNET_TIME_absolute_get_duration (pr-> public_data.start_time).rel_value); - if (!GSF_request_plan_reference_get_last_transmission_ (pr->public_data.rpr_head, prq->sender, &last_transmission)) + if (GNUNET_YES != + GSF_request_plan_reference_get_last_transmission_ (pr->public_data.pr_head, + prq->sender, + &last_transmission)) last_transmission.abs_value = GNUNET_TIME_UNIT_FOREVER_ABS.abs_value; /* pass on to other peers / local clients */ pr->rh (pr->rh_cls, prq->eval, pr, prq->anonymity_level, prq->expiration, last_transmission, prq->type, prq->data, prq->size); return GNUNET_YES; case GNUNET_BLOCK_EVALUATION_OK_DUPLICATE: +#if INSANE_STATISTICS GNUNET_STATISTICS_update (GSF_stats, gettext_noop ("# duplicate replies discarded (bloomfilter)"), 1, GNUNET_NO); +#endif GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Duplicate response, discarding.\n"); return GNUNET_YES; /* duplicate */ + case GNUNET_BLOCK_EVALUATION_RESULT_IRRELEVANT: + GNUNET_STATISTICS_update (GSF_stats, + gettext_noop + ("# irrelevant replies discarded"), + 1, GNUNET_NO); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Irrelevant response, ignoring.\n"); + return GNUNET_YES; case GNUNET_BLOCK_EVALUATION_RESULT_INVALID: return GNUNET_YES; /* wrong namespace */ case GNUNET_BLOCK_EVALUATION_REQUEST_VALID: @@ -845,9 +914,12 @@ process_reply (void *cls, const GNUNET_HashCode * key, void *value) pr->public_data.results_found++; prq->request_found = GNUNET_YES; /* finally, pass on to other peer / local client */ - if (!GSF_request_plan_reference_get_last_transmission_ (pr->public_data.rpr_head, prq->sender, &last_transmission)) + if (! GSF_request_plan_reference_get_last_transmission_ (pr->public_data.pr_head, + prq->sender, + &last_transmission)) last_transmission.abs_value = GNUNET_TIME_UNIT_FOREVER_ABS.abs_value; - pr->rh (pr->rh_cls, prq->eval, pr, prq->anonymity_level, prq->expiration, + pr->rh (pr->rh_cls, prq->eval, pr, + prq->anonymity_level, prq->expiration, last_transmission, prq->type, prq->data, prq->size); return GNUNET_YES; } @@ -929,8 +1001,8 @@ put_migration_continuation (void *cls, int success, if (min_expiration.abs_value > 0) { GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Asking to stop migration for %llu ms because datastore is full\n", - (unsigned long long) GNUNET_TIME_absolute_get_remaining (min_expiration).rel_value); + "Asking to stop migration for %s because datastore is full\n", + GNUNET_STRINGS_relative_time_to_string (GNUNET_TIME_absolute_get_remaining (min_expiration), GNUNET_YES)); GSF_block_peer_migration_ (cp, min_expiration); } else @@ -943,8 +1015,8 @@ put_migration_continuation (void *cls, int success, ppd->migration_delay.rel_value); ppd->migration_delay = GNUNET_TIME_relative_multiply (ppd->migration_delay, 2); GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Replicated content already exists locally, asking to stop migration for %llu ms\n", - (unsigned long long) mig_pause.rel_value); + "Replicated content already exists locally, asking to stop migration for %s\n", + GNUNET_STRINGS_relative_time_to_string (mig_pause, GNUNET_YES)); GSF_block_peer_migration_ (cp, GNUNET_TIME_relative_to_absolute (mig_pause)); } } @@ -1000,7 +1072,7 @@ test_put_load_too_high (uint32_t priority) */ static void handle_dht_reply (void *cls, struct GNUNET_TIME_Absolute exp, - const GNUNET_HashCode * key, + const struct GNUNET_HashCode * key, const struct GNUNET_PeerIdentity *get_path, unsigned int get_path_length, const struct GNUNET_PeerIdentity *put_path, @@ -1057,7 +1129,7 @@ GSF_dht_lookup_ (struct GSF_PendingRequest *pr) const void *xquery; size_t xquery_size; struct GNUNET_PeerIdentity pi; - char buf[sizeof (GNUNET_HashCode) * 2] GNUNET_ALIGN; + char buf[sizeof (struct GNUNET_HashCode) * 2] GNUNET_ALIGN; if (0 != pr->public_data.anonymity_level) return; @@ -1071,8 +1143,8 @@ GSF_dht_lookup_ (struct GSF_PendingRequest *pr) if (GNUNET_BLOCK_TYPE_FS_SBLOCK == pr->public_data.type) { xquery = buf; - memcpy (buf, &pr->public_data.namespace, sizeof (GNUNET_HashCode)); - xquery_size = sizeof (GNUNET_HashCode); + memcpy (buf, pr->public_data.namespace, sizeof (struct GNUNET_HashCode)); + xquery_size = sizeof (struct GNUNET_HashCode); } if (0 != (pr->public_data.options & GSF_PRO_FORWARD_ONLY)) { @@ -1084,10 +1156,105 @@ GSF_dht_lookup_ (struct GSF_PendingRequest *pr) pr->gh = GNUNET_DHT_get_start (GSF_dht, pr->public_data.type, &pr->public_data.query, - 5 /* DEFAULT_GET_REPLICATION */ , + DHT_GET_REPLICATION, GNUNET_DHT_RO_DEMULTIPLEX_EVERYWHERE, - /* FIXME: can no longer pass pr->bf/pr->mingle... */ xquery, xquery_size, &handle_dht_reply, pr); + if ( (NULL != pr->gh) && + (0 != pr->replies_seen_count) ) + GNUNET_DHT_get_filter_known_results (pr->gh, + pr->replies_seen_count, + pr->replies_seen); +} + + +/** + * Function called with a reply from the stream. + * + * @param cls the pending request struct + * @param type type of the block, ANY on error + * @param expiration expiration time for the block + * @param data_size number of bytes in 'data', 0 on error + * @param data reply block data, NULL on error + */ +static void +stream_reply_proc (void *cls, + enum GNUNET_BLOCK_Type type, + struct GNUNET_TIME_Absolute expiration, + size_t data_size, + const void *data) +{ + struct GSF_PendingRequest *pr = cls; + struct ProcessReplyClosure prq; + struct GNUNET_HashCode query; + + pr->stream_request = NULL; + if (GNUNET_BLOCK_TYPE_ANY == type) + { + GNUNET_break (NULL == data); + GNUNET_break (0 == data_size); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Error retrieiving block via stream\n"); + pr->stream_retry_count++; + if (pr->stream_retry_count >= STREAM_RETRY_MAX) + return; /* give up on stream */ + /* retry -- without delay, as this is non-anonymous + and mesh/stream connect will take some time anyway */ + pr->stream_request = GSF_stream_query (pr->public_data.target, + &pr->public_data.query, + pr->public_data.type, + &stream_reply_proc, + pr); + return; + } + if (GNUNET_YES != + GNUNET_BLOCK_get_key (GSF_block_ctx, + type, + data, data_size, &query)) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Failed to derive key for block of type %d\n", + (int) type); + GNUNET_break_op (0); + return; + } + GNUNET_STATISTICS_update (GSF_stats, + gettext_noop ("# Replies received from STREAM"), 1, + GNUNET_NO); + memset (&prq, 0, sizeof (prq)); + prq.data = data; + prq.expiration = expiration; + /* do not allow migrated content to live longer than 1 year */ + prq.expiration = GNUNET_TIME_absolute_min (GNUNET_TIME_relative_to_absolute (GNUNET_TIME_UNIT_YEARS), + prq.expiration); + prq.size = data_size; + prq.type = type; + process_reply (&prq, &query, pr); +} + + +/** + * Consider downloading via stream (if possible) + * + * @param pr the pending request to process + */ +void +GSF_stream_lookup_ (struct GSF_PendingRequest *pr) +{ + if (0 != pr->public_data.anonymity_level) + return; + if (0 == pr->public_data.target) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Cannot do stream-based download, target peer not known\n"); + return; + } + if (NULL != pr->stream_request) + return; + pr->stream_request = GSF_stream_query (pr->public_data.target, + &pr->public_data.query, + pr->public_data.type, + &stream_reply_proc, + pr); } @@ -1103,9 +1270,8 @@ warn_delay_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) struct GSF_PendingRequest *pr = cls; GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - _("Datastore lookup already took %llu ms!\n"), - (unsigned long long) - GNUNET_TIME_absolute_get_duration (pr->qe_start).rel_value); + _("Datastore lookup already took %s!\n"), + GNUNET_STRINGS_relative_time_to_string (GNUNET_TIME_absolute_get_duration (pr->qe_start), GNUNET_YES)); pr->warn_task = GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_MINUTES, &warn_delay_task, pr); @@ -1124,9 +1290,8 @@ odc_warn_delay_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) struct GSF_PendingRequest *pr = cls; GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - _("On-demand lookup already took %llu ms!\n"), - (unsigned long long) - GNUNET_TIME_absolute_get_duration (pr->qe_start).rel_value); + _("On-demand lookup already took %s!\n"), + GNUNET_STRINGS_relative_time_to_string (GNUNET_TIME_absolute_get_duration (pr->qe_start), GNUNET_YES)); pr->warn_task = GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_MINUTES, &odc_warn_delay_task, pr); @@ -1151,7 +1316,7 @@ odc_warn_delay_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) * maybe 0 if no unique identifier is available */ static void -process_local_reply (void *cls, const GNUNET_HashCode * key, size_t size, +process_local_reply (void *cls, const struct GNUNET_HashCode * key, size_t size, const void *data, enum GNUNET_BLOCK_Type type, uint32_t priority, uint32_t anonymity, struct GNUNET_TIME_Absolute expiration, uint64_t uid) @@ -1159,7 +1324,7 @@ process_local_reply (void *cls, const GNUNET_HashCode * key, size_t size, struct GSF_PendingRequest *pr = cls; GSF_LocalLookupContinuation cont; struct ProcessReplyClosure prq; - GNUNET_HashCode query; + struct GNUNET_HashCode query; unsigned int old_rf; GNUNET_SCHEDULER_cancel (pr->warn_task); @@ -1169,10 +1334,12 @@ process_local_reply (void *cls, const GNUNET_HashCode * key, size_t size, pr->qe = NULL; if (NULL == key) { +#if INSANE_STATISTICS GNUNET_STATISTICS_update (GSF_stats, gettext_noop ("# Datastore lookups concluded (no results)"), 1, GNUNET_NO); +#endif } if (GNUNET_NO == pr->have_first_uid) { @@ -1204,12 +1371,14 @@ process_local_reply (void *cls, const GNUNET_HashCode * key, size_t size, { GNUNET_log (GNUNET_ERROR_TYPE_DEBUG | GNUNET_ERROR_TYPE_BULK, "No further local responses available.\n"); +#if INSANE_STATISTICS if ((pr->public_data.type == GNUNET_BLOCK_TYPE_FS_DBLOCK) || (pr->public_data.type == GNUNET_BLOCK_TYPE_FS_IBLOCK)) GNUNET_STATISTICS_update (GSF_stats, gettext_noop ("# requested DBLOCK or IBLOCK not found"), 1, GNUNET_NO); +#endif goto check_error_and_continue; } GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, @@ -1258,7 +1427,7 @@ process_local_reply (void *cls, const GNUNET_HashCode * key, size_t size, (0 != (GSF_PRO_PRIORITY_UNLIMITED & pr->public_data.options)) ? UINT_MAX : - datastore_queue_size + GSF_datastore_queue_size /* max queue size */ , GNUNET_TIME_UNIT_FOREVER_REL, &process_local_reply, pr); @@ -1298,7 +1467,7 @@ process_local_reply (void *cls, const GNUNET_HashCode * key, size_t size, (0 != (GSF_PRO_PRIORITY_UNLIMITED & pr->public_data.options)) ? UINT_MAX : - datastore_queue_size + GSF_datastore_queue_size /* max queue size */ , GNUNET_TIME_UNIT_FOREVER_REL, &process_local_reply, pr); @@ -1356,7 +1525,7 @@ process_local_reply (void *cls, const GNUNET_HashCode * key, size_t size, (0 != (GSF_PRO_PRIORITY_UNLIMITED & pr-> public_data.options)) ? UINT_MAX : - datastore_queue_size + GSF_datastore_queue_size /* max queue size */ , GNUNET_TIME_UNIT_FOREVER_REL, &process_local_reply, pr); @@ -1413,6 +1582,7 @@ GSF_local_lookup_ (struct GSF_PendingRequest *pr, GSF_LocalLookupContinuation cont, void *cont_cls) { GNUNET_assert (NULL == pr->gh); + GNUNET_assert (NULL == pr->stream_request); GNUNET_assert (NULL == pr->llc_cont); pr->llc_cont = cont; pr->llc_cont_cls = cont_cls; @@ -1420,9 +1590,11 @@ GSF_local_lookup_ (struct GSF_PendingRequest *pr, pr->warn_task = GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_MINUTES, &warn_delay_task, pr); +#if INSANE_STATISTICS GNUNET_STATISTICS_update (GSF_stats, gettext_noop ("# Datastore lookups initiated"), 1, GNUNET_NO); +#endif pr->qe = GNUNET_DATASTORE_get_key (GSF_dsh, pr->local_result_offset++, &pr->public_data.query, @@ -1436,7 +1608,7 @@ GSF_local_lookup_ (struct GSF_PendingRequest *pr, (0 != (GSF_PRO_PRIORITY_UNLIMITED & pr-> public_data.options)) ? UINT_MAX : - datastore_queue_size + GSF_datastore_queue_size /* max queue size */ , GNUNET_TIME_UNIT_FOREVER_REL, &process_local_reply, pr); @@ -1477,7 +1649,7 @@ GSF_handle_p2p_content_ (struct GSF_ConnectedPeer *cp, size_t dsize; enum GNUNET_BLOCK_Type type; struct GNUNET_TIME_Absolute expiration; - GNUNET_HashCode query; + struct GNUNET_HashCode query; struct ProcessReplyClosure prq; struct GNUNET_TIME_Relative block_time; double putl; @@ -1509,10 +1681,7 @@ GSF_handle_p2p_content_ (struct GSF_ConnectedPeer *cp, GNUNET_NO); /* now, lookup 'query' */ prq.data = (const void *) &put[1]; - if (NULL != cp) - prq.sender = cp; - else - prq.sender = NULL; + prq.sender = cp; prq.size = dsize; prq.type = type; prq.expiration = expiration; @@ -1526,9 +1695,10 @@ GSF_handle_p2p_content_ (struct GSF_ConnectedPeer *cp, GSF_connected_peer_change_preference_ (cp, CONTENT_BANDWIDTH_VALUE + 1000 * prq.priority); - GSF_get_peer_performance_data_ (cp)->trust += prq.priority; + GSF_get_peer_performance_data_ (cp)->respect += prq.priority; } if ((GNUNET_YES == active_to_migration) && + (NULL != cp) && (GNUNET_NO == test_put_load_too_high (prq.priority))) { GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, @@ -1551,7 +1721,7 @@ GSF_handle_p2p_content_ (struct GSF_ConnectedPeer *cp, put_migration_continuation (pmc, GNUNET_SYSERR, GNUNET_TIME_UNIT_ZERO_ABS, NULL); } } - else + else if (NULL != cp) { GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Choosing not to keep content `%s' (%d/%d)\n", @@ -1559,9 +1729,10 @@ GSF_handle_p2p_content_ (struct GSF_ConnectedPeer *cp, test_put_load_too_high (prq.priority)); } putl = GNUNET_LOAD_get_load (datastore_put_load); - if ((NULL != (cp = prq.sender)) && (GNUNET_NO == prq.request_found) && - ((GNUNET_YES != active_to_migration) || - (putl > 2.5 * (1 + prq.priority)))) + if ( (NULL != cp) && + (GNUNET_NO == prq.request_found) && + ( (GNUNET_YES != active_to_migration) || + (putl > 2.5 * (1 + prq.priority)) ) ) { if (GNUNET_YES != active_to_migration) putl = 1.0 + GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK, 5); @@ -1589,37 +1760,18 @@ GSF_handle_p2p_content_ (struct GSF_ConnectedPeer *cp, void GSF_pending_request_init_ () { - unsigned long long bps; - if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_number (GSF_cfg, "fs", "MAX_PENDING_REQUESTS", &max_pending_requests)) { - GNUNET_log (GNUNET_ERROR_TYPE_INFO, - _ - ("Configuration fails to specify `%s', assuming default value."), - "MAX_PENDING_REQUESTS"); + GNUNET_log_config_missing (GNUNET_ERROR_TYPE_INFO, + "fs", "MAX_PENDING_REQUESTS"); } - if (GNUNET_OK != - GNUNET_CONFIGURATION_get_value_size (GSF_cfg, "ats", "WAN_QUOTA_OUT", - &bps)) - { - GNUNET_log (GNUNET_ERROR_TYPE_INFO, - _ - ("Configuration fails to specify `%s', assuming default value."), - "WAN_QUOTA_OUT"); - bps = 65536; - } - /* queue size should be #queries we can have pending and satisfy within - * a carry interval: */ - datastore_queue_size = - bps * GNUNET_CONSTANTS_MAX_BANDWIDTH_CARRY_S / DBLOCK_SIZE; - active_to_migration = GNUNET_CONFIGURATION_get_value_yesno (GSF_cfg, "FS", "CONTENT_CACHING"); datastore_put_load = GNUNET_LOAD_value_init (DATASTORE_LOAD_AUTODECLINE); - pr_map = GNUNET_CONTAINER_multihashmap_create (32 * 1024); + pr_map = GNUNET_CONTAINER_multihashmap_create (32 * 1024, GNUNET_YES); requests_by_expiration_heap = GNUNET_CONTAINER_heap_create (GNUNET_CONTAINER_HEAP_ORDER_MIN); } diff --git a/src/fs/gnunet-service-fs_pr.h b/src/fs/gnunet-service-fs_pr.h index 92827f7..371aa66 100644 --- a/src/fs/gnunet-service-fs_pr.h +++ b/src/fs/gnunet-service-fs_pr.h @@ -84,28 +84,29 @@ struct GSF_PendingRequestData /** * Primary query hash for this request. */ - GNUNET_HashCode query; + struct GNUNET_HashCode query; /** * Namespace to query, only set if the type is SBLOCK. + * Allocated after struct only if needed. Do not free! */ - GNUNET_HashCode namespace; + const struct GNUNET_HashCode *namespace; /** - * Identity of a peer hosting the content, only set if - * 'has_target' is GNUNET_YES. + * Identity of a peer hosting the content, otherwise NULl. + * Allocated after struct only if needed. Do not free! */ - struct GNUNET_PeerIdentity target; + const struct GNUNET_PeerIdentity *target; /** * Fields for the plan module to track a DLL with the request. */ - struct GSF_RequestPlanReference *rpr_head; + struct GSF_PendingRequestPlanBijection *pr_head; /** * Fields for the plan module to track a DLL with the request. */ - struct GSF_RequestPlanReference *rpr_tail; + struct GSF_PendingRequestPlanBijection *pr_tail; /** * Current TTL for the request. @@ -132,6 +133,22 @@ struct GSF_PendingRequestData */ uint32_t original_priority; + /** + * Counter for how often this request has been transmitted (estimate, + * because we might have the same request pending for multiple clients, + * and of course because a transmission may have failed at a lower + * layer). + */ + uint32_t num_transmissions; + + /** + * How much respect did we (in total) offer for this request so far (estimate, + * because we might have the same request pending for multiple clients, + * and of course because a transmission may have failed at a lower + * layer). + */ + uint32_t respect_offered; + /** * Options for the request. */ @@ -147,11 +164,6 @@ struct GSF_PendingRequestData */ unsigned int results_found; - /** - * Is the 'target' value set to a valid peer identity? - */ - int has_target; - /** * Has this request been started yet (local/p2p operations)? Or are * we still constructing it? @@ -220,15 +232,15 @@ typedef void (*GSF_PendingRequestReplyHandler) (void *cls, struct GSF_PendingRequest * GSF_pending_request_create_ (enum GSF_PendingRequestOptions options, enum GNUNET_BLOCK_Type type, - const GNUNET_HashCode * query, - const GNUNET_HashCode * namespace, + const struct GNUNET_HashCode * query, + const struct GNUNET_HashCode * namespace, const struct GNUNET_PeerIdentity *target, const char *bf_data, size_t bf_size, uint32_t mingle, uint32_t anonymity_level, uint32_t priority, int32_t ttl, GNUNET_PEER_Id sender_pid, GNUNET_PEER_Id origin_pid, - const GNUNET_HashCode * replies_seen, + const struct GNUNET_HashCode * replies_seen, unsigned int replies_seen_count, GSF_PendingRequestReplyHandler rh, void *rh_cls); @@ -243,7 +255,7 @@ GSF_pending_request_create_ (enum GSF_PendingRequestOptions options, */ void GSF_pending_request_update_ (struct GSF_PendingRequest *pr, - const GNUNET_HashCode * replies_seen, + const struct GNUNET_HashCode * replies_seen, unsigned int replies_seen_count); @@ -305,7 +317,7 @@ GSF_pending_request_cancel_ (struct GSF_PendingRequest *pr, int full_cleanup); * @return GNUNET_YES to continue to iterate */ typedef int (*GSF_PendingRequestIterator) (void *cls, - const GNUNET_HashCode * key, + const struct GNUNET_HashCode * key, struct GSF_PendingRequest * pr); @@ -346,6 +358,15 @@ void GSF_dht_lookup_ (struct GSF_PendingRequest *pr); +/** + * Consider downloading via stream (if possible) + * + * @param pr the pending request to process + */ +void +GSF_stream_lookup_ (struct GSF_PendingRequest *pr); + + /** * Function to be called after we're done processing * replies from the local lookup. diff --git a/src/fs/gnunet-service-fs_push.c b/src/fs/gnunet-service-fs_push.c index 22a76f3..936cf51 100644 --- a/src/fs/gnunet-service-fs_push.c +++ b/src/fs/gnunet-service-fs_push.c @@ -71,7 +71,7 @@ struct MigrationReadyBlock /** * Query for the block. */ - GNUNET_HashCode query; + struct GNUNET_HashCode query; /** * When does this block expire? @@ -467,7 +467,7 @@ consider_gathering () * maybe 0 if no unique identifier is available */ static void -process_migration_content (void *cls, const GNUNET_HashCode * key, size_t size, +process_migration_content (void *cls, const struct GNUNET_HashCode * key, size_t size, const void *data, enum GNUNET_BLOCK_Type type, uint32_t priority, uint32_t anonymity, struct GNUNET_TIME_Absolute expiration, uint64_t uid) @@ -624,10 +624,9 @@ GSF_push_init_ () GNUNET_CONFIGURATION_get_value_time (GSF_cfg, "fs", "MIN_MIGRATION_DELAY", &min_migration_delay)) { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - _ - ("Invalid value specified for option `%s' in section `%s', content pushing disabled\n"), - "MIN_MIGRATION_DELAY", "fs"); + GNUNET_log_config_invalid (GNUNET_ERROR_TYPE_WARNING, + "fs", "MIN_MIGRATION_DELAY", + _("time required, content pushing disabled")); return; } consider_gathering (); diff --git a/src/fs/gnunet-service-fs_put.c b/src/fs/gnunet-service-fs_put.c index 463acc0..49962d3 100644 --- a/src/fs/gnunet-service-fs_put.c +++ b/src/fs/gnunet-service-fs_put.c @@ -180,8 +180,11 @@ delay_dht_put_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) * maybe 0 if no unique identifier is available */ static void -process_dht_put_content (void *cls, const GNUNET_HashCode * key, size_t size, - const void *data, enum GNUNET_BLOCK_Type type, +process_dht_put_content (void *cls, + const struct GNUNET_HashCode * key, + size_t size, + const void *data, + enum GNUNET_BLOCK_Type type, uint32_t priority, uint32_t anonymity, struct GNUNET_TIME_Absolute expiration, uint64_t uid) { diff --git a/src/fs/gnunet-service-fs_stream.c b/src/fs/gnunet-service-fs_stream.c new file mode 100644 index 0000000..3838b1c --- /dev/null +++ b/src/fs/gnunet-service-fs_stream.c @@ -0,0 +1,1466 @@ +/* + This file is part of GNUnet. + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @file fs/gnunet-service-fs_stream.c + * @brief non-anonymous file-transfer + * @author Christian Grothoff + */ +#include "platform.h" +#include "gnunet_constants.h" +#include "gnunet_util_lib.h" +#include "gnunet_stream_lib.h" +#include "gnunet_protocols.h" +#include "gnunet_applications.h" +#include "gnunet-service-fs.h" +#include "gnunet-service-fs_indexing.h" +#include "gnunet-service-fs_stream.h" + +/** + * After how long do we termiante idle connections? + */ +#define IDLE_TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MINUTES, 2) + +/** + * After how long do we reset connections without replies? + */ +#define CLIENT_RETRY_TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 30) + + +/** + * A message in the queue to be written to the stream. + */ +struct WriteQueueItem +{ + /** + * Kept in a DLL. + */ + struct WriteQueueItem *next; + + /** + * Kept in a DLL. + */ + struct WriteQueueItem *prev; + + /** + * Number of bytes of payload, allocated at the end of this struct. + */ + size_t msize; +}; + + +/** + * Information we keep around for each active streaming client. + */ +struct StreamClient +{ + /** + * DLL + */ + struct StreamClient *next; + + /** + * DLL + */ + struct StreamClient *prev; + + /** + * Socket for communication. + */ + struct GNUNET_STREAM_Socket *socket; + + /** + * Handle for active read operation, or NULL. + */ + struct GNUNET_STREAM_ReadHandle *rh; + + /** + * Handle for active write operation, or NULL. + */ + struct GNUNET_STREAM_WriteHandle *wh; + + /** + * Head of write queue. + */ + struct WriteQueueItem *wqi_head; + + /** + * Tail of write queue. + */ + struct WriteQueueItem *wqi_tail; + + /** + * Tokenizer for requests. + */ + struct GNUNET_SERVER_MessageStreamTokenizer *mst; + + /** + * Current active request to the datastore, if we have one pending. + */ + struct GNUNET_DATASTORE_QueueEntry *qe; + + /** + * Task that is scheduled to asynchronously terminate the connection. + */ + GNUNET_SCHEDULER_TaskIdentifier terminate_task; + + /** + * Task that is scheduled to terminate idle connections. + */ + GNUNET_SCHEDULER_TaskIdentifier timeout_task; + + /** + * Size of the last write that was initiated. + */ + size_t reply_size; + +}; + + +/** + * Query from one peer, asking the other for CHK-data. + */ +struct StreamQueryMessage +{ + + /** + * Type is GNUNET_MESSAGE_TYPE_FS_STREAM_QUERY. + */ + struct GNUNET_MessageHeader header; + + /** + * Block type must be DBLOCK or IBLOCK. + */ + uint32_t type; + + /** + * Query hash from CHK (hash of encrypted block). + */ + struct GNUNET_HashCode query; + +}; + + +/** + * Reply to a StreamQueryMessage. + */ +struct StreamReplyMessage +{ + + /** + * Type is GNUNET_MESSAGE_TYPE_FS_STREAM_REPLY. + */ + struct GNUNET_MessageHeader header; + + /** + * Block type must be DBLOCK or IBLOCK. + */ + uint32_t type; + + /** + * Expiration time for the block. + */ + struct GNUNET_TIME_AbsoluteNBO expiration; + + /* followed by the encrypted block */ + +}; + + +/** + * Handle for a stream to another peer. + */ +struct StreamHandle; + + +/** + * Handle for a request that is going out via stream API. + */ +struct GSF_StreamRequest +{ + + /** + * DLL. + */ + struct GSF_StreamRequest *next; + + /** + * DLL. + */ + struct GSF_StreamRequest *prev; + + /** + * Which stream is this request associated with? + */ + struct StreamHandle *sh; + + /** + * Function to call with the result. + */ + GSF_StreamReplyProcessor proc; + + /** + * Closure for 'proc' + */ + void *proc_cls; + + /** + * Query to transmit to the other peer. + */ + struct GNUNET_HashCode query; + + /** + * Desired type for the reply. + */ + enum GNUNET_BLOCK_Type type; + + /** + * Did we transmit this request already? YES if we are + * in the 'waiting' DLL, NO if we are in the 'pending' DLL. + */ + int was_transmitted; +}; + + +/** + * Handle for a stream to another peer. + */ +struct StreamHandle +{ + /** + * Head of DLL of pending requests on this stream. + */ + struct GSF_StreamRequest *pending_head; + + /** + * Tail of DLL of pending requests on this stream. + */ + struct GSF_StreamRequest *pending_tail; + + /** + * Map from query to 'struct GSF_StreamRequest's waiting for + * a reply. + */ + struct GNUNET_CONTAINER_MultiHashMap *waiting_map; + + /** + * Connection to the other peer. + */ + struct GNUNET_STREAM_Socket *stream; + + /** + * Handle for active read operation, or NULL. + */ + struct GNUNET_STREAM_ReadHandle *rh; + + /** + * Handle for active write operation, or NULL. + */ + struct GNUNET_STREAM_WriteHandle *wh; + + /** + * Tokenizer for replies. + */ + struct GNUNET_SERVER_MessageStreamTokenizer *mst; + + /** + * Which peer does this stream go to? + */ + struct GNUNET_PeerIdentity target; + + /** + * Task to kill inactive streams (we keep them around for + * a few seconds to give the application a chance to give + * us another query). + */ + GNUNET_SCHEDULER_TaskIdentifier timeout_task; + + /** + * Task to reset streams that had errors (asynchronously, + * as we may not be able to do it immediately during a + * callback from the stream API). + */ + GNUNET_SCHEDULER_TaskIdentifier reset_task; + + /** + * Is this stream ready for transmission? + */ + int is_ready; + +}; + + +/** + * Listen socket for incoming requests. + */ +static struct GNUNET_STREAM_ListenSocket *listen_socket; + +/** + * Head of DLL of stream clients. + */ +static struct StreamClient *sc_head; + +/** + * Tail of DLL of stream clients. + */ +static struct StreamClient *sc_tail; + +/** + * Number of active stream clients in the 'sc_*'-DLL. + */ +static unsigned int sc_count; + +/** + * Maximum allowed number of stream clients. + */ +static unsigned long long sc_count_max; + +/** + * Map from peer identities to 'struct StreamHandles' with streams to + * those peers. + */ +static struct GNUNET_CONTAINER_MultiHashMap *stream_map; + + +/* ********************* client-side code ************************* */ + +/** + * Iterator called on each entry in a waiting map to + * call the 'proc' continuation and release associated + * resources. + * + * @param cls the 'struct StreamHandle' + * @param key the key of the entry in the map (the query) + * @param value the 'struct GSF_StreamRequest' to clean up + * @return GNUNET_YES (continue to iterate) + */ +static int +free_waiting_entry (void *cls, + const struct GNUNET_HashCode *key, + void *value) +{ + struct GSF_StreamRequest *sr = value; + + sr->proc (sr->proc_cls, GNUNET_BLOCK_TYPE_ANY, + GNUNET_TIME_UNIT_FOREVER_ABS, + 0, NULL); + GSF_stream_query_cancel (sr); + return GNUNET_YES; +} + + +/** + * Destroy a stream handle. + * + * @param sh stream to process + */ +static void +destroy_stream_handle (struct StreamHandle *sh) +{ + struct GSF_StreamRequest *sr; + + while (NULL != (sr = sh->pending_head)) + { + sr->proc (sr->proc_cls, GNUNET_BLOCK_TYPE_ANY, + GNUNET_TIME_UNIT_FOREVER_ABS, + 0, NULL); + GSF_stream_query_cancel (sr); + } + GNUNET_CONTAINER_multihashmap_iterate (sh->waiting_map, + &free_waiting_entry, + sh); + if (NULL != sh->wh) + GNUNET_STREAM_write_cancel (sh->wh); + if (NULL != sh->rh) + GNUNET_STREAM_read_cancel (sh->rh); + if (GNUNET_SCHEDULER_NO_TASK != sh->timeout_task) + GNUNET_SCHEDULER_cancel (sh->timeout_task); + if (GNUNET_SCHEDULER_NO_TASK != sh->reset_task) + GNUNET_SCHEDULER_cancel (sh->reset_task); + GNUNET_STREAM_close (sh->stream); + GNUNET_assert (GNUNET_OK == + GNUNET_CONTAINER_multihashmap_remove (stream_map, + &sh->target.hashPubKey, + sh)); + GNUNET_CONTAINER_multihashmap_destroy (sh->waiting_map); + GNUNET_free (sh); +} + + +/** + * Transmit pending requests via the stream. + * + * @param sh stream to process + */ +static void +transmit_pending (struct StreamHandle *sh); + + +/** + * Function called once the stream is ready for transmission. + * + * @param cls the 'struct StreamHandle' + * @param socket stream socket handle + */ +static void +stream_ready_cb (void *cls, + struct GNUNET_STREAM_Socket *socket) +{ + struct StreamHandle *sh = cls; + + sh->is_ready = GNUNET_YES; + transmit_pending (sh); +} + + +/** + * Iterator called on each entry in a waiting map to + * move it back to the pending list. + * + * @param cls the 'struct StreamHandle' + * @param key the key of the entry in the map (the query) + * @param value the 'struct GSF_StreamRequest' to move to pending + * @return GNUNET_YES (continue to iterate) + */ +static int +move_to_pending (void *cls, + const struct GNUNET_HashCode *key, + void *value) +{ + struct StreamHandle *sh = cls; + struct GSF_StreamRequest *sr = value; + + GNUNET_assert (GNUNET_YES == + GNUNET_CONTAINER_multihashmap_remove (sh->waiting_map, + key, + value)); + GNUNET_CONTAINER_DLL_insert (sh->pending_head, + sh->pending_tail, + sr); + sr->was_transmitted = GNUNET_NO; + return GNUNET_YES; +} + + +/** + * We had a serious error, tear down and re-create stream from scratch. + * + * @param sh stream to reset + */ +static void +reset_stream (struct StreamHandle *sh) +{ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Resetting stream to %s\n", + GNUNET_i2s (&sh->target)); + if (NULL != sh->rh) + { + GNUNET_STREAM_read_cancel (sh->rh); + sh->rh = NULL; + } + GNUNET_STREAM_close (sh->stream); + sh->is_ready = GNUNET_NO; + GNUNET_CONTAINER_multihashmap_iterate (sh->waiting_map, + &move_to_pending, + sh); + sh->stream = GNUNET_STREAM_open (GSF_cfg, + &sh->target, + GNUNET_APPLICATION_TYPE_FS_BLOCK_TRANSFER, + &stream_ready_cb, sh, + GNUNET_STREAM_OPTION_END); +} + + +/** + * Task called when it is time to destroy an inactive stream. + * + * @param cls the 'struct StreamHandle' to tear down + * @param tc scheduler context, unused + */ +static void +stream_timeout (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct StreamHandle *sh = cls; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Timeout on stream to %s\n", + GNUNET_i2s (&sh->target)); + sh->timeout_task = GNUNET_SCHEDULER_NO_TASK; + destroy_stream_handle (sh); +} + + +/** + * Task called when it is time to reset an stream. + * + * @param cls the 'struct StreamHandle' to tear down + * @param tc scheduler context, unused + */ +static void +reset_stream_task (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct StreamHandle *sh = cls; + + sh->reset_task = GNUNET_SCHEDULER_NO_TASK; + reset_stream (sh); +} + + +/** + * We had a serious error, tear down and re-create stream from scratch, + * but do so asynchronously. + * + * @param sh stream to reset + */ +static void +reset_stream_async (struct StreamHandle *sh) +{ + if (GNUNET_SCHEDULER_NO_TASK != sh->reset_task) + GNUNET_SCHEDULER_cancel (sh->reset_task); + sh->reset_task = GNUNET_SCHEDULER_add_now (&reset_stream_task, + sh); +} + + +/** + * We got a reply from the stream. Process it. + * + * @param cls the struct StreamHandle + * @param status the status of the stream at the time this function is called + * @param data traffic from the other side + * @param size the number of bytes available in data read; will be 0 on timeout + * @return number of bytes of processed from 'data' (any data remaining should be + * given to the next time the read processor is called). + */ +static size_t +handle_stream_reply (void *cls, + enum GNUNET_STREAM_Status status, + const void *data, + size_t size) +{ + struct StreamHandle *sh = cls; + + sh->rh = NULL; + GNUNET_SCHEDULER_cancel (sh->reset_task); + sh->reset_task = GNUNET_SCHEDULER_add_delayed (CLIENT_RETRY_TIMEOUT, + &reset_stream_task, + sh); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Received %u bytes from stream to %s\n", + (unsigned int) size, + GNUNET_i2s (&sh->target)); + if (GNUNET_SYSERR == + GNUNET_SERVER_mst_receive (sh->mst, + NULL, + data, size, + GNUNET_NO, GNUNET_NO)) + { + GNUNET_break_op (0); + reset_stream_async (sh); + return size; + } + if (NULL == sh->rh) + sh->rh = GNUNET_STREAM_read (sh->stream, + GNUNET_TIME_UNIT_FOREVER_REL, + &handle_stream_reply, + sh); + return size; +} + + +/** + * Functions of this signature are called whenever we transmitted a + * query via a stream. + * + * @param cls the struct StreamHandle for which we did the write call + * @param status the status of the stream at the time this function is called; + * GNUNET_OK if writing to stream was completed successfully, + * GNUNET_STREAM_SHUTDOWN if the stream is shutdown for writing in the + * mean time. + * @param size the number of bytes written + */ +static void +query_write_continuation (void *cls, + enum GNUNET_STREAM_Status status, + size_t size) +{ + struct StreamHandle *sh = cls; + + sh->wh = NULL; + if ( (GNUNET_STREAM_OK != status) || + (sizeof (struct StreamQueryMessage) != size) ) + { + reset_stream (sh); + return; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Successfully transmitted %u bytes via stream to %s\n", + (unsigned int) size, + GNUNET_i2s (&sh->target)); + if (NULL == sh->rh) + sh->rh = GNUNET_STREAM_read (sh->stream, + GNUNET_TIME_UNIT_FOREVER_REL, + &handle_stream_reply, + sh); + transmit_pending (sh); +} + + +/** + * Transmit pending requests via the stream. + * + * @param sh stream to process + */ +static void +transmit_pending (struct StreamHandle *sh) +{ + struct StreamQueryMessage sqm; + struct GSF_StreamRequest *sr; + + if (NULL != sh->wh) + return; + sr = sh->pending_head; + if (NULL == sr) + return; + GNUNET_CONTAINER_DLL_remove (sh->pending_head, + sh->pending_tail, + sr); + GNUNET_CONTAINER_multihashmap_put (sh->waiting_map, + &sr->query, + sr, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Sending query via stream to %s\n", + GNUNET_i2s (&sh->target)); + sr->was_transmitted = GNUNET_YES; + sqm.header.size = htons (sizeof (sqm)); + sqm.header.type = htons (GNUNET_MESSAGE_TYPE_FS_STREAM_QUERY); + sqm.type = htonl (sr->type); + sqm.query = sr->query; + sh->wh = GNUNET_STREAM_write (sh->stream, + &sqm, sizeof (sqm), + GNUNET_TIME_UNIT_FOREVER_REL, + &query_write_continuation, + sh); +} + + +/** + * Closure for 'handle_reply'. + */ +struct HandleReplyClosure +{ + + /** + * Reply payload. + */ + const void *data; + + /** + * Expiration time for the block. + */ + struct GNUNET_TIME_Absolute expiration; + + /** + * Number of bytes in 'data'. + */ + size_t data_size; + + /** + * Type of the block. + */ + enum GNUNET_BLOCK_Type type; + + /** + * Did we have a matching query? + */ + int found; +}; + + +/** + * Iterator called on each entry in a waiting map to + * process a result. + * + * @param cls the 'struct HandleReplyClosure' + * @param key the key of the entry in the map (the query) + * @param value the 'struct GSF_StreamRequest' to handle result for + * @return GNUNET_YES (continue to iterate) + */ +static int +handle_reply (void *cls, + const struct GNUNET_HashCode *key, + void *value) +{ + struct HandleReplyClosure *hrc = cls; + struct GSF_StreamRequest *sr = value; + + sr->proc (sr->proc_cls, + hrc->type, + hrc->expiration, + hrc->data_size, + hrc->data); + GSF_stream_query_cancel (sr); + hrc->found = GNUNET_YES; + return GNUNET_YES; +} + + +/** + * Functions with this signature are called whenever a + * complete reply is received. + * + * Do not call GNUNET_SERVER_mst_destroy in callback + * + * @param cls closure with the 'struct StreamHandle' + * @param client identification of the client, NULL + * @param message the actual message + * @return GNUNET_OK on success, GNUNET_SYSERR to stop further processing + */ +static int +reply_cb (void *cls, + void *client, + const struct GNUNET_MessageHeader *message) +{ + struct StreamHandle *sh = cls; + const struct StreamReplyMessage *srm; + struct HandleReplyClosure hrc; + uint16_t msize; + enum GNUNET_BLOCK_Type type; + struct GNUNET_HashCode query; + + msize = ntohs (message->size); + switch (ntohs (message->type)) + { + case GNUNET_MESSAGE_TYPE_FS_STREAM_REPLY: + if (sizeof (struct StreamReplyMessage) > msize) + { + GNUNET_break_op (0); + reset_stream_async (sh); + return GNUNET_SYSERR; + } + srm = (const struct StreamReplyMessage *) message; + msize -= sizeof (struct StreamReplyMessage); + type = (enum GNUNET_BLOCK_Type) ntohl (srm->type); + if (GNUNET_YES != + GNUNET_BLOCK_get_key (GSF_block_ctx, + type, + &srm[1], msize, &query)) + { + GNUNET_break_op (0); + reset_stream_async (sh); + return GNUNET_SYSERR; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Received reply `%s' via stream\n", + GNUNET_h2s (&query)); + GNUNET_STATISTICS_update (GSF_stats, + gettext_noop ("# replies received via stream"), 1, + GNUNET_NO); + hrc.data = &srm[1]; + hrc.data_size = msize; + hrc.expiration = GNUNET_TIME_absolute_ntoh (srm->expiration); + hrc.type = type; + hrc.found = GNUNET_NO; + GNUNET_CONTAINER_multihashmap_get_multiple (sh->waiting_map, + &query, + &handle_reply, + &hrc); + if (GNUNET_NO == hrc.found) + { + GNUNET_STATISTICS_update (GSF_stats, + gettext_noop ("# replies received via stream dropped"), 1, + GNUNET_NO); + return GNUNET_OK; + } + return GNUNET_OK; + default: + GNUNET_break_op (0); + reset_stream_async (sh); + return GNUNET_SYSERR; + } +} + + +/** + * Get (or create) a stream to talk to the given peer. + * + * @param target peer we want to communicate with + */ +static struct StreamHandle * +get_stream (const struct GNUNET_PeerIdentity *target) +{ + struct StreamHandle *sh; + + sh = GNUNET_CONTAINER_multihashmap_get (stream_map, + &target->hashPubKey); + if (NULL != sh) + { + if (GNUNET_SCHEDULER_NO_TASK != sh->timeout_task) + { + GNUNET_SCHEDULER_cancel (sh->timeout_task); + sh->timeout_task = GNUNET_SCHEDULER_NO_TASK; + } + return sh; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Creating stream to %s\n", + GNUNET_i2s (target)); + sh = GNUNET_malloc (sizeof (struct StreamHandle)); + sh->reset_task = GNUNET_SCHEDULER_add_delayed (CLIENT_RETRY_TIMEOUT, + &reset_stream_task, + sh); + sh->mst = GNUNET_SERVER_mst_create (&reply_cb, + sh); + sh->waiting_map = GNUNET_CONTAINER_multihashmap_create (512, GNUNET_YES); + sh->target = *target; + sh->stream = GNUNET_STREAM_open (GSF_cfg, + &sh->target, + GNUNET_APPLICATION_TYPE_FS_BLOCK_TRANSFER, + &stream_ready_cb, sh, + GNUNET_STREAM_OPTION_END); + GNUNET_assert (GNUNET_OK == + GNUNET_CONTAINER_multihashmap_put (stream_map, + &sh->target.hashPubKey, + sh, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY)); + return sh; +} + + +/** + * Look for a block by directly contacting a particular peer. + * + * @param target peer that should have the block + * @param query hash to query for the block + * @param type desired type for the block + * @param proc function to call with result + * @param proc_cls closure for 'proc' + * @return handle to cancel the operation + */ +struct GSF_StreamRequest * +GSF_stream_query (const struct GNUNET_PeerIdentity *target, + const struct GNUNET_HashCode *query, + enum GNUNET_BLOCK_Type type, + GSF_StreamReplyProcessor proc, void *proc_cls) +{ + struct StreamHandle *sh; + struct GSF_StreamRequest *sr; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Preparing to send query for %s via stream to %s\n", + GNUNET_h2s (query), + GNUNET_i2s (target)); + sh = get_stream (target); + sr = GNUNET_malloc (sizeof (struct GSF_StreamRequest)); + sr->sh = sh; + sr->proc = proc; + sr->proc_cls = proc_cls; + sr->type = type; + sr->query = *query; + GNUNET_CONTAINER_DLL_insert (sh->pending_head, + sh->pending_tail, + sr); + if (GNUNET_YES == sh->is_ready) + transmit_pending (sh); + return sr; +} + + +/** + * Cancel an active request; must not be called after 'proc' + * was calld. + * + * @param sr request to cancel + */ +void +GSF_stream_query_cancel (struct GSF_StreamRequest *sr) +{ + struct StreamHandle *sh = sr->sh; + + if (GNUNET_YES == sr->was_transmitted) + GNUNET_assert (GNUNET_OK == + GNUNET_CONTAINER_multihashmap_remove (sh->waiting_map, + &sr->query, + sr)); + else + GNUNET_CONTAINER_DLL_remove (sh->pending_head, + sh->pending_tail, + sr); + GNUNET_free (sr); + if ( (0 == GNUNET_CONTAINER_multihashmap_size (sh->waiting_map)) && + (NULL == sh->pending_head) ) + sh->timeout_task = GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_SECONDS, + &stream_timeout, + sh); +} + + +/* ********************* server-side code ************************* */ + + +/** + * We're done with a particular client, clean up. + * + * @param sc client to clean up + */ +static void +terminate_stream (struct StreamClient *sc) +{ + GNUNET_STATISTICS_update (GSF_stats, + gettext_noop ("# stream connections active"), -1, + GNUNET_NO); + if (GNUNET_SCHEDULER_NO_TASK != sc->terminate_task) + GNUNET_SCHEDULER_cancel (sc->terminate_task); + if (GNUNET_SCHEDULER_NO_TASK != sc->timeout_task) + GNUNET_SCHEDULER_cancel (sc->timeout_task); + if (NULL != sc->rh) + GNUNET_STREAM_read_cancel (sc->rh); + if (NULL != sc->wh) + GNUNET_STREAM_write_cancel (sc->wh); + if (NULL != sc->qe) + GNUNET_DATASTORE_cancel (sc->qe); + GNUNET_SERVER_mst_destroy (sc->mst); + GNUNET_STREAM_close (sc->socket); + struct WriteQueueItem *wqi; + while (NULL != (wqi = sc->wqi_head)) + { + GNUNET_CONTAINER_DLL_remove (sc->wqi_head, + sc->wqi_tail, + wqi); + GNUNET_free (wqi); + } + + + GNUNET_CONTAINER_DLL_remove (sc_head, + sc_tail, + sc); + sc_count--; + GNUNET_free (sc); +} + + +/** + * Task run to asynchronously terminate the stream. + * + * @param cls the 'struct StreamClient' + * @param tc scheduler context + */ +static void +terminate_stream_task (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct StreamClient *sc = cls; + + sc->terminate_task = GNUNET_SCHEDULER_NO_TASK; + terminate_stream (sc); +} + + +/** + * Task run to asynchronously terminate the stream due to timeout. + * + * @param cls the 'struct StreamClient' + * @param tc scheduler context + */ +static void +timeout_stream_task (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct StreamClient *sc = cls; + + sc->timeout_task = GNUNET_SCHEDULER_NO_TASK; + terminate_stream (sc); +} + + +/** + * Reset the timeout for the stream client (due to activity). + * + * @param sc client handle to reset timeout for + */ +static void +refresh_timeout_task (struct StreamClient *sc) +{ + if (GNUNET_SCHEDULER_NO_TASK != sc->timeout_task) + GNUNET_SCHEDULER_cancel (sc->timeout_task); + sc->timeout_task = GNUNET_SCHEDULER_add_delayed (IDLE_TIMEOUT, + &timeout_stream_task, + sc); +} + + +/** + * We had a serious error, termiante stream, + * but do so asynchronously. + * + * @param sc stream to reset + */ +static void +terminate_stream_async (struct StreamClient *sc) +{ + if (GNUNET_SCHEDULER_NO_TASK == sc->terminate_task) + sc->terminate_task = GNUNET_SCHEDULER_add_now (&terminate_stream_task, + sc); +} + + +/** + * Functions of this signature are called whenever data is available from the + * stream. + * + * @param cls the closure from GNUNET_STREAM_read + * @param status the status of the stream at the time this function is called + * @param data traffic from the other side + * @param size the number of bytes available in data read; will be 0 on timeout + * @return number of bytes of processed from 'data' (any data remaining should be + * given to the next time the read processor is called). + */ +static size_t +process_request (void *cls, + enum GNUNET_STREAM_Status status, + const void *data, + size_t size); + + +/** + * We're done handling a request from a client, read the next one. + * + * @param sc client to continue reading requests from + */ +static void +continue_reading (struct StreamClient *sc) +{ + int ret; + + ret = + GNUNET_SERVER_mst_receive (sc->mst, + NULL, + NULL, 0, + GNUNET_NO, GNUNET_NO); + if (GNUNET_NO == ret) + return; + refresh_timeout_task (sc); + if (NULL != sc->rh) + return; + sc->rh = GNUNET_STREAM_read (sc->socket, + GNUNET_TIME_UNIT_FOREVER_REL, + &process_request, + sc); +} + + +/** + * Transmit the next entry from the write queue. + * + * @param sc where to process the write queue + */ +static void +continue_writing (struct StreamClient *sc); + + +/** + * Functions of this signature are called whenever data is available from the + * stream. + * + * @param cls the closure from GNUNET_STREAM_read + * @param status the status of the stream at the time this function is called + * @param data traffic from the other side + * @param size the number of bytes available in data read; will be 0 on timeout + * @return number of bytes of processed from 'data' (any data remaining should be + * given to the next time the read processor is called). + */ +static size_t +process_request (void *cls, + enum GNUNET_STREAM_Status status, + const void *data, + size_t size) +{ + struct StreamClient *sc = cls; + int ret; + + sc->rh = NULL; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Received %u byte query via stream\n", + (unsigned int) size); + switch (status) + { + case GNUNET_STREAM_OK: + ret = + GNUNET_SERVER_mst_receive (sc->mst, + NULL, + data, size, + GNUNET_NO, GNUNET_NO); + if (GNUNET_NO == ret) + return size; /* more messages in MST */ + if (GNUNET_SYSERR == ret) + { + GNUNET_break_op (0); + terminate_stream_async (sc); + return size; + } + break; + case GNUNET_STREAM_TIMEOUT: + case GNUNET_STREAM_SHUTDOWN: + case GNUNET_STREAM_SYSERR: + terminate_stream_async (sc); + return size; + default: + GNUNET_break (0); + return size; + } + continue_writing (sc); + return size; +} + + +/** + * Sending a reply was completed, continue processing. + * + * @param cls closure with the struct StreamClient which sent the query + * @param status result code for the operation + * @param size number of bytes that were transmitted + */ +static void +write_continuation (void *cls, + enum GNUNET_STREAM_Status status, + size_t size) +{ + struct StreamClient *sc = cls; + + sc->wh = NULL; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Write continuation called on 'server' side with status %d\n", + status); + if ( (GNUNET_STREAM_OK != status) || + (size != sc->reply_size) ) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Transmission of reply failed, terminating stream\n"); + terminate_stream (sc); + return; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Transmitted %u byte reply via stream\n", + (unsigned int) size); + GNUNET_STATISTICS_update (GSF_stats, + gettext_noop ("# Blocks transferred via stream"), 1, + GNUNET_NO); + continue_writing (sc); +} + + +/** + * Transmit the next entry from the write queue. + * + * @param sc where to process the write queue + */ +static void +continue_writing (struct StreamClient *sc) +{ + struct WriteQueueItem *wqi; + + if (NULL != sc->wh) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Write pending, waiting for it to complete\n"); + return; /* write already pending */ + } + if (NULL == (wqi = sc->wqi_head)) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Write queue empty, reading more requests\n"); + continue_reading (sc); + return; + } + GNUNET_CONTAINER_DLL_remove (sc->wqi_head, + sc->wqi_tail, + wqi); + sc->wh = GNUNET_STREAM_write (sc->socket, + &wqi[1], wqi->msize, + GNUNET_TIME_UNIT_FOREVER_REL, + &write_continuation, + sc); + if (NULL != sc->wh) + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Gave %u bytes for stream for transmission\n", + (unsigned int) wqi->msize); + GNUNET_free (wqi); + if (NULL == sc->wh) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Write failed; terminating stream\n"); + terminate_stream (sc); + return; + } +} + + +/** + * Process a datum that was stored in the datastore. + * + * @param cls closure with the struct StreamClient which sent the query + * @param key key for the content + * @param size number of bytes in data + * @param data content stored + * @param type type of the content + * @param priority priority of the content + * @param anonymity anonymity-level for the content + * @param expiration expiration time for the content + * @param uid unique identifier for the datum; + * maybe 0 if no unique identifier is available + */ +static void +handle_datastore_reply (void *cls, + const struct GNUNET_HashCode * key, + size_t size, const void *data, + enum GNUNET_BLOCK_Type type, + uint32_t priority, + uint32_t anonymity, + struct GNUNET_TIME_Absolute + expiration, uint64_t uid) +{ + struct StreamClient *sc = cls; + size_t msize = size + sizeof (struct StreamReplyMessage); + struct WriteQueueItem *wqi; + struct StreamReplyMessage *srm; + + sc->qe = NULL; + if (GNUNET_BLOCK_TYPE_FS_ONDEMAND == type) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Performing on-demand encoding\n"); + if (GNUNET_OK != + GNUNET_FS_handle_on_demand_block (key, + size, data, type, + priority, anonymity, + expiration, uid, + &handle_datastore_reply, + sc)) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "On-demand encoding request failed\n"); + continue_writing (sc); + } + return; + } + if (msize > GNUNET_SERVER_MAX_MESSAGE_SIZE) + { + GNUNET_break (0); + continue_writing (sc); + return; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Starting transmission of %u byte reply for query `%s' via stream\n", + (unsigned int) size, + GNUNET_h2s (key)); + wqi = GNUNET_malloc (sizeof (struct WriteQueueItem) + msize); + wqi->msize = msize; + srm = (struct StreamReplyMessage *) &wqi[1]; + srm->header.size = htons ((uint16_t) msize); + srm->header.type = htons (GNUNET_MESSAGE_TYPE_FS_STREAM_REPLY); + srm->type = htonl (type); + srm->expiration = GNUNET_TIME_absolute_hton (expiration); + memcpy (&srm[1], data, size); + sc->reply_size = msize; + GNUNET_CONTAINER_DLL_insert (sc->wqi_head, + sc->wqi_tail, + wqi); + continue_writing (sc); +} + + +/** + * Functions with this signature are called whenever a + * complete query message is received. + * + * Do not call GNUNET_SERVER_mst_destroy in callback + * + * @param cls closure with the 'struct StreamClient' + * @param client identification of the client, NULL + * @param message the actual message + * @return GNUNET_OK on success, GNUNET_SYSERR to stop further processing + */ +static int +request_cb (void *cls, + void *client, + const struct GNUNET_MessageHeader *message) +{ + struct StreamClient *sc = cls; + const struct StreamQueryMessage *sqm; + + switch (ntohs (message->type)) + { + case GNUNET_MESSAGE_TYPE_FS_STREAM_QUERY: + if (sizeof (struct StreamQueryMessage) != + ntohs (message->size)) + { + GNUNET_break_op (0); + terminate_stream_async (sc); + return GNUNET_SYSERR; + } + sqm = (const struct StreamQueryMessage *) message; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Received query for `%s' via stream\n", + GNUNET_h2s (&sqm->query)); + GNUNET_STATISTICS_update (GSF_stats, + gettext_noop ("# queries received via stream"), 1, + GNUNET_NO); + refresh_timeout_task (sc); + sc->qe = GNUNET_DATASTORE_get_key (GSF_dsh, + 0, + &sqm->query, + ntohl (sqm->type), + 0 /* priority */, + GSF_datastore_queue_size, + GNUNET_TIME_UNIT_FOREVER_REL, + &handle_datastore_reply, sc); + if (NULL == sc->qe) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Queueing request with datastore failed (queue full?)\n"); + continue_writing (sc); + } + return GNUNET_OK; + default: + GNUNET_break_op (0); + terminate_stream_async (sc); + return GNUNET_SYSERR; + } +} + + +/** + * Functions of this type are called upon new stream connection from other peers + * or upon binding error which happen when the app_port given in + * GNUNET_STREAM_listen() is already taken. + * + * @param cls the closure from GNUNET_STREAM_listen + * @param socket the socket representing the stream; NULL on binding error + * @param initiator the identity of the peer who wants to establish a stream + * with us; NULL on binding error + * @return GNUNET_OK to keep the socket open, GNUNET_SYSERR to close the + * stream (the socket will be invalid after the call) + */ +static int +accept_cb (void *cls, + struct GNUNET_STREAM_Socket *socket, + const struct GNUNET_PeerIdentity *initiator) +{ + struct StreamClient *sc; + + if (NULL == socket) + return GNUNET_SYSERR; + if (sc_count >= sc_count_max) + { + GNUNET_STATISTICS_update (GSF_stats, + gettext_noop ("# stream client connections rejected"), 1, + GNUNET_NO); + return GNUNET_SYSERR; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Accepting inbound stream connection from `%s'\n", + GNUNET_i2s (initiator)); + GNUNET_STATISTICS_update (GSF_stats, + gettext_noop ("# stream connections active"), 1, + GNUNET_NO); + sc = GNUNET_malloc (sizeof (struct StreamClient)); + sc->socket = socket; + sc->mst = GNUNET_SERVER_mst_create (&request_cb, + sc); + sc->rh = GNUNET_STREAM_read (sc->socket, + GNUNET_TIME_UNIT_FOREVER_REL, + &process_request, + sc); + GNUNET_CONTAINER_DLL_insert (sc_head, + sc_tail, + sc); + sc_count++; + refresh_timeout_task (sc); + return GNUNET_OK; +} + + +/** + * Initialize subsystem for non-anonymous file-sharing. + */ +void +GSF_stream_start () +{ + stream_map = GNUNET_CONTAINER_multihashmap_create (16, GNUNET_YES); + if (GNUNET_YES == + GNUNET_CONFIGURATION_get_value_number (GSF_cfg, + "fs", + "MAX_STREAM_CLIENTS", + &sc_count_max)) + { + listen_socket = GNUNET_STREAM_listen (GSF_cfg, + GNUNET_APPLICATION_TYPE_FS_BLOCK_TRANSFER, + &accept_cb, NULL, + GNUNET_STREAM_OPTION_END); + } +} + + +/** + * Function called on each active streams to shut them down. + * + * @param cls NULL + * @param key target peer, unused + * @param value the 'struct StreamHandle' to destroy + * @return GNUNET_YES (continue to iterate) + */ +static int +release_streams (void *cls, + const struct GNUNET_HashCode *key, + void *value) +{ + struct StreamHandle *sh = value; + + destroy_stream_handle (sh); + return GNUNET_YES; +} + + +/** + * Shutdown subsystem for non-anonymous file-sharing. + */ +void +GSF_stream_stop () +{ + struct StreamClient *sc; + + while (NULL != (sc = sc_head)) + terminate_stream (sc); + if (NULL != listen_socket) + { + GNUNET_STREAM_listen_close (listen_socket); + listen_socket = NULL; + } + GNUNET_CONTAINER_multihashmap_iterate (stream_map, + &release_streams, + NULL); + GNUNET_CONTAINER_multihashmap_destroy (stream_map); + stream_map = NULL; +} + +/* end of gnunet-service-fs_stream.c */ diff --git a/src/fs/gnunet-service-fs_stream.h b/src/fs/gnunet-service-fs_stream.h new file mode 100644 index 0000000..9827667 --- /dev/null +++ b/src/fs/gnunet-service-fs_stream.h @@ -0,0 +1,91 @@ +/* + This file is part of GNUnet. + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @file fs/gnunet-service-fs_stream.h + * @brief non-anonymous file-transfer + * @author Christian Grothoff + */ +#ifndef GNUNET_SERVICE_FS_STREAM_H +#define GNUNET_SERVICE_FS_STREAM_H + +/** + * Handle for a request that is going out via stream API. + */ +struct GSF_StreamRequest; + + +/** + * Function called with a reply from the stream. + * + * @param cls closure + * @param type type of the block, ANY on error + * @param expiration expiration time for the block + * @param data_size number of bytes in 'data', 0 on error + * @param data reply block data, NULL on error + */ +typedef void (*GSF_StreamReplyProcessor)(void *cls, + enum GNUNET_BLOCK_Type type, + struct GNUNET_TIME_Absolute expiration, + size_t data_size, + const void *data); + + +/** + * Look for a block by directly contacting a particular peer. + * + * @param target peer that should have the block + * @param query hash to query for the block + * @param type desired type for the block + * @param proc function to call with result + * @param proc_cls closure for 'proc' + * @return handle to cancel the operation + */ +struct GSF_StreamRequest * +GSF_stream_query (const struct GNUNET_PeerIdentity *target, + const struct GNUNET_HashCode *query, + enum GNUNET_BLOCK_Type type, + GSF_StreamReplyProcessor proc, void *proc_cls); + + +/** + * Cancel an active request; must not be called after 'proc' + * was calld. + * + * @param sr request to cancel + */ +void +GSF_stream_query_cancel (struct GSF_StreamRequest *sr); + + +/** + * Initialize subsystem for non-anonymous file-sharing. + */ +void +GSF_stream_start (void); + + +/** + * Shutdown subsystem for non-anonymous file-sharing. + */ +void +GSF_stream_stop (void); + +#endif diff --git a/src/fs/gnunet-unindex.c b/src/fs/gnunet-unindex.c index 3e8308d..094d886 100644 --- a/src/fs/gnunet-unindex.c +++ b/src/fs/gnunet-unindex.c @@ -76,7 +76,7 @@ shutdown_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) static void * progress_cb (void *cls, const struct GNUNET_FS_ProgressInfo *info) { - char *s; + const char *s; switch (info->status) { @@ -85,11 +85,10 @@ progress_cb (void *cls, const struct GNUNET_FS_ProgressInfo *info) case GNUNET_FS_STATUS_UNINDEX_PROGRESS: if (verbose) { - s = GNUNET_STRINGS_relative_time_to_string (info->value.unindex.eta); + s = GNUNET_STRINGS_relative_time_to_string (info->value.unindex.eta, GNUNET_YES); FPRINTF (stdout, _("Unindexing at %llu/%llu (%s remaining)\n"), (unsigned long long) info->value.unindex.completed, (unsigned long long) info->value.unindex.size, s); - GNUNET_free (s); } break; case GNUNET_FS_STATUS_UNINDEX_ERROR: @@ -170,11 +169,17 @@ main (int argc, char *const *argv) 0, &GNUNET_GETOPT_set_one, &verbose}, GNUNET_GETOPT_OPTION_END }; - return (GNUNET_OK == - GNUNET_PROGRAM_run (argc, argv, "gnunet-unindex [OPTIONS] FILENAME", - gettext_noop - ("Unindex a file that was previously indexed with gnunet-publish."), - options, &run, NULL)) ? ret : 1; + + if (GNUNET_OK != GNUNET_STRINGS_get_utf8_args (argc, argv, &argc, &argv)) + return 2; + + ret = (GNUNET_OK == + GNUNET_PROGRAM_run (argc, argv, "gnunet-unindex [OPTIONS] FILENAME", + gettext_noop + ("Unindex a file that was previously indexed with gnunet-publish."), + options, &run, NULL)) ? ret : 1; + GNUNET_free ((void*) argv); + return ret; } /* end of gnunet-unindex.c */ diff --git a/src/fs/perf_gnunet_service_fs_p2p.c b/src/fs/perf_gnunet_service_fs_p2p.c index 7b2c044..89db80c 100644 --- a/src/fs/perf_gnunet_service_fs_p2p.c +++ b/src/fs/perf_gnunet_service_fs_p2p.c @@ -1,6 +1,6 @@ /* This file is part of GNUnet. - (C) 2010 Christian Grothoff (and other contributing authors) + (C) 2010, 2012 Christian Grothoff (and other contributing authors) GNUnet is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published @@ -25,7 +25,7 @@ */ #include "platform.h" #include "fs_test_lib.h" -#include "gnunet_testing_lib.h" +#include "gnunet_testbed_service.h" #define VERBOSE GNUNET_NO @@ -43,7 +43,7 @@ #define SEED 42 -static struct GNUNET_FS_TestDaemon *daemons[NUM_DAEMONS]; +static struct GNUNET_TESTBED_Peer *daemons[NUM_DAEMONS]; static int ok; @@ -51,12 +51,6 @@ static struct GNUNET_TIME_Absolute start_time; static const char *progname; -static void -do_stop (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - GNUNET_FS_TEST_daemons_stop (NUM_DAEMONS, daemons); -} - /** * Master context for 'stat_run'. @@ -64,6 +58,7 @@ do_stop (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) struct StatMaster { struct GNUNET_STATISTICS_Handle *stat; + struct GNUNET_TESTBED_Operation *op; unsigned int daemon; unsigned int value; }; @@ -78,7 +73,6 @@ struct StatValues * Statistics we print out. */ static struct StatValues stats[] = { - {"fs", "# artificial delays introduced (ms)"}, {"fs", "# queries forwarded"}, {"fs", "# replies received and matched"}, {"fs", "# results found locally"}, @@ -130,7 +124,10 @@ print_stat (void *cls, const char *subsystem, const char *name, uint64_t value, * Function that gathers stats from all daemons. */ static void -stat_run (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc); +stat_run (void *cls, + struct GNUNET_TESTBED_Operation *op, + void *ca_result, + const char *emsg); /** @@ -143,7 +140,41 @@ get_done (void *cls, int success) GNUNET_break (GNUNET_OK == success); sm->value++; - GNUNET_SCHEDULER_add_now (&stat_run, sm); + stat_run (sm, sm->op, sm->stat, NULL); +} + + +/** + * Adapter function called to establish a connection to + * statistics service. + * + * @param cls closure + * @param cfg configuration of the peer to connect to; will be available until + * GNUNET_TESTBED_operation_done() is called on the operation returned + * from GNUNET_TESTBED_service_connect() + * @return service handle to return in 'op_result', NULL on error + */ +static void * +statistics_connect_adapter (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg) +{ + return GNUNET_STATISTICS_create ("", + cfg); +} + + +/** + * Adapter function called to destroy a connection to + * statistics service. + * + * @param cls closure + * @param op_result service handle returned from the connect adapter + */ +static void +statistics_disconnect_adapter (void *cls, + void *op_result) +{ + GNUNET_STATISTICS_destroy (op_result, GNUNET_NO); } @@ -151,10 +182,23 @@ get_done (void *cls, int success) * Function that gathers stats from all daemons. */ static void -stat_run (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +stat_run (void *cls, + struct GNUNET_TESTBED_Operation *op, + void *ca_result, + const char *emsg) { struct StatMaster *sm = cls; + if (NULL != emsg) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Failed to statistics service: %s\n", + emsg); + GNUNET_SCHEDULER_shutdown (); + return; + } + sm->stat = ca_result; + if (stats[sm->value].name != NULL) { GNUNET_STATISTICS_get (sm->stat, @@ -167,67 +211,80 @@ stat_run (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) sm); return; } - GNUNET_STATISTICS_destroy (sm->stat, GNUNET_NO); + GNUNET_TESTBED_operation_done (sm->op); sm->value = 0; sm->daemon++; - if (sm->daemon == NUM_DAEMONS) + if (NUM_DAEMONS == sm->daemon) { GNUNET_free (sm); - GNUNET_SCHEDULER_add_now (&do_stop, NULL); + GNUNET_SCHEDULER_shutdown (); return; } - sm->stat = - GNUNET_STATISTICS_create ("", - GNUNET_FS_TEST_get_configuration (daemons, - sm->daemon)); - GNUNET_SCHEDULER_add_now (&stat_run, sm); + sm->op = + GNUNET_TESTBED_service_connect (NULL, + daemons[sm->daemon], + "statistics", + &stat_run, sm, + &statistics_connect_adapter, + &statistics_disconnect_adapter, + NULL); } static void do_report (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { + char *fn = cls; struct GNUNET_TIME_Relative del; char *fancy; struct StatMaster *sm; - if (0 == (tc->reason & GNUNET_SCHEDULER_REASON_TIMEOUT)) + if (NULL != fn) { - del = GNUNET_TIME_absolute_get_duration (start_time); - if (del.rel_value == 0) - del.rel_value = 1; - fancy = - GNUNET_STRINGS_byte_size_fancy (((unsigned long long) FILESIZE) * - 1000LL / del.rel_value); - FPRINTF (stdout, "Download speed was %s/s\n", fancy); - GNUNET_free (fancy); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Finished download, shutting down\n", - (unsigned long long) FILESIZE); - sm = GNUNET_malloc (sizeof (struct StatMaster)); - sm->stat = - GNUNET_STATISTICS_create ("", - GNUNET_FS_TEST_get_configuration (daemons, - sm->daemon)); - GNUNET_SCHEDULER_add_now (&stat_run, sm); + GNUNET_DISK_directory_remove (fn); + GNUNET_free (fn); } - else + if (0 != (tc->reason & GNUNET_SCHEDULER_REASON_TIMEOUT)) { GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Timeout during download, shutting down with error\n"); ok = 1; - GNUNET_SCHEDULER_add_now (&do_stop, NULL); + GNUNET_SCHEDULER_shutdown (); + return; } + + del = GNUNET_TIME_absolute_get_duration (start_time); + if (del.rel_value == 0) + del.rel_value = 1; + fancy = + GNUNET_STRINGS_byte_size_fancy (((unsigned long long) FILESIZE) * + 1000LL / del.rel_value); + FPRINTF (stdout, "Download speed was %s/s\n", fancy); + GNUNET_free (fancy); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Finished download, shutting down\n", + (unsigned long long) FILESIZE); + sm = GNUNET_malloc (sizeof (struct StatMaster)); + sm->op = + GNUNET_TESTBED_service_connect (NULL, + daemons[sm->daemon], + "statistics", + &stat_run, sm, + &statistics_connect_adapter, + &statistics_disconnect_adapter, + NULL); } static void -do_download (void *cls, const struct GNUNET_FS_Uri *uri) +do_download (void *cls, + const struct GNUNET_FS_Uri *uri, + const char *fn) { int anonymity; if (NULL == uri) - { - GNUNET_FS_TEST_daemons_stop (NUM_DAEMONS, daemons); + { + GNUNET_SCHEDULER_shutdown (); GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Timeout during upload attempt, shutting down with error\n"); ok = 1; @@ -241,23 +298,23 @@ do_download (void *cls, const struct GNUNET_FS_Uri *uri) else anonymity = 1; GNUNET_FS_TEST_download (daemons[0], TIMEOUT, anonymity, SEED, uri, VERBOSE, - &do_report, NULL); + &do_report, + (NULL == fn) ? NULL : GNUNET_strdup (fn)); } static void -do_publish (void *cls, const char *emsg) +do_publish (void *cls, + unsigned int num_peers, + struct GNUNET_TESTBED_Peer **peers) { + unsigned int i; int do_index; int anonymity; - - if (NULL != emsg) - { - GNUNET_FS_TEST_daemons_stop (NUM_DAEMONS, daemons); - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Error trying to connect: %s\n", emsg); - ok = 1; - return; - } + + GNUNET_assert (NUM_DAEMONS == num_peers); + for (i=0;ireason & GNUNET_SCHEDULER_REASON_PREREQ_DONE)); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Daemons started, will now try to connect them\n"); - pg = GNUNET_FS_TEST_get_group (daemons); - GNUNET_break ((NUM_DAEMONS - 1) * 2 == - (GNUNET_TESTING_create_topology - (pg, GNUNET_TESTING_TOPOLOGY_LINE, - GNUNET_TESTING_TOPOLOGY_NONE, NULL))); - GNUNET_TESTING_connect_topology (pg, GNUNET_TESTING_TOPOLOGY_LINE, - GNUNET_TESTING_TOPOLOGY_OPTION_NONE, 0.0, - TIMEOUT, NUM_DAEMONS, &do_publish, NULL); -} - - -static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) -{ - GNUNET_FS_TEST_daemons_start ("fs_test_lib_data.conf", TIMEOUT, NUM_DAEMONS, - daemons, &do_connect, NULL); -} - - int main (int argc, char *argv[]) { - char *const argvx[] = { - "perf-gnunet-service-fs-p2p", - "-c", - "fs_test_lib_data.conf", -#if VERBOSE - "-L", "DEBUG", -#endif - NULL - }; - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; progname = argv[0]; - GNUNET_DISK_directory_remove ("/tmp/gnunet-test-fs-lib/"); - GNUNET_log_setup ("perf_gnunet_service_fs_p2p_index", -#if VERBOSE - "DEBUG", -#else - "WARNING", -#endif - NULL); - GNUNET_PROGRAM_run ((sizeof (argvx) / sizeof (char *)) - 1, argvx, - "perf-gnunet-service-fs-p2p-index", "nohelp", options, - &run, NULL); + (void) GNUNET_TESTBED_test_run ("perf-gnunet-service-fs-p2p", + "perf_gnunet_service_fs_p2p.conf", + NUM_DAEMONS, + 0, NULL, NULL, + &do_publish, NULL); GNUNET_DISK_directory_remove ("/tmp/gnunet-test-fs-lib/"); return ok; } diff --git a/src/fs/perf_gnunet_service_fs_p2p.conf b/src/fs/perf_gnunet_service_fs_p2p.conf new file mode 100644 index 0000000..c9e472e --- /dev/null +++ b/src/fs/perf_gnunet_service_fs_p2p.conf @@ -0,0 +1,7 @@ +@INLINE@ fs_test_lib_data.conf +[PATHS] +SERVICEHOME = /tmp/gnunet-fs-test-lib/ + +[fs] +GAUGER_HEAP = "2-peer 10 MB P2P download" +# PREFIX = valgrind diff --git a/src/fs/perf_gnunet_service_fs_p2p_respect.c b/src/fs/perf_gnunet_service_fs_p2p_respect.c new file mode 100644 index 0000000..0a5dc05 --- /dev/null +++ b/src/fs/perf_gnunet_service_fs_p2p_respect.c @@ -0,0 +1,473 @@ +/* + This file is part of GNUnet. + (C) 2010, 2011, 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @file fs/perf_gnunet_service_fs_p2p_respect.c + * @brief profile P2P routing respect mechanism. Creates + * a clique of NUM_DAEMONS (i.e. 3) where two + * peers share (seed) different files and download + * them from each other while all the other peers + * just "leach" those files. Ideally, the seeders + * "learn" that they contribute (to each other), + * and give the other seeder higher priority; + * naturally, this only happens nicely for larger + * files; finally, once the seeders are done, the + * leachers should see fast download rates as well. + * @author Christian Grothoff + * + * Sample output: + * - 10 MB, 3 peers, with delays: + * Download speed of type `seeder 1' was 757 KiB/s + * Download speed of type `seeder 2' was 613 KiB/s + * Download speed of type `leach` was 539 KiB/s + * + * - 10 MB, 3 peers, without delays: + * Download speed of type `seeder 1' was 1784 KiB/s + * Download speed of type `seeder 2' was 1604 KiB/s + * Download speed of type `leach` was 1384 KiB/s + */ +#include "platform.h" +#include "fs_test_lib.h" +#include "gnunet_testbed_service.h" + +#define VERBOSE GNUNET_NO + +/** + * File-size we use for testing. + */ +#define FILESIZE (1024 * 1024 * 1) + +/** + * How long until we give up on transmitting the message? + */ +#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MINUTES, 30) + +/** + * Number of daemons in clique, must be at least 3 (!). + */ +#define NUM_DAEMONS 3 + +/** + * Seed for first file on offer. + */ +#define SEED1 42 + +/** + * Seed for second file on offer. + */ +#define SEED2 43 + +static struct GNUNET_TESTBED_Peer *daemons[NUM_DAEMONS]; + +static int ok; + +static struct GNUNET_TIME_Absolute start_time; + +static const char *progname; + +static struct GNUNET_FS_Uri *uri1; + +static struct GNUNET_FS_Uri *uri2; + +static char *fn1; + +static char *fn2; + +/** + * Master context for 'stat_run'. + */ +struct StatMaster +{ + struct GNUNET_STATISTICS_Handle *stat; + struct GNUNET_TESTBED_Operation *op; + unsigned int daemon; + unsigned int value; +}; + +struct StatValues +{ + const char *subsystem; + const char *name; +}; + +/** + * Statistics we print out. + */ +static struct StatValues stats[] = { + {"fs", "# artificial delays introduced (ms)"}, + {"fs", "# queries forwarded"}, + {"fs", "# replies received and matched"}, + {"fs", "# results found locally"}, + {"fs", "# requests forwarded due to high load"}, + {"fs", "# requests done for free (low load)"}, + {"fs", "# requests dropped, priority insufficient"}, + {"fs", "# requests done for a price (normal load)"}, + {"fs", "# requests dropped by datastore (queue length limit)"}, + {"fs", "# P2P searches received"}, + {"fs", "# P2P searches discarded (queue length bound)"}, + {"fs", "# replies received for local clients"}, + {"fs", "# queries retransmitted to same target"}, + {"core", "# bytes decrypted"}, + {"core", "# bytes encrypted"}, + {"core", "# discarded CORE_SEND requests"}, + {"core", "# discarded lower priority CORE_SEND requests"}, + {"transport", "# bytes received via TCP"}, + {"transport", "# bytes transmitted via TCP"}, + {"datacache", "# bytes stored"}, + {NULL, NULL} +}; + + +static void +cleanup () +{ + GNUNET_SCHEDULER_shutdown (); + if (NULL != fn1) + { + GNUNET_DISK_directory_remove (fn1); + GNUNET_free (fn1); + } + if (NULL != fn2) + { + GNUNET_DISK_directory_remove (fn2); + GNUNET_free (fn2); + } +} + + +/** + * Callback function to process statistic values. + * + * @param cls closure + * @param subsystem name of subsystem that created the statistic + * @param name the name of the datum + * @param value the current value + * @param is_persistent GNUNET_YES if the value is persistent, GNUNET_NO if not + * @return GNUNET_OK to continue, GNUNET_SYSERR to abort iteration + */ +static int +print_stat (void *cls, const char *subsystem, const char *name, uint64_t value, + int is_persistent) +{ + struct StatMaster *sm = cls; + + FPRINTF (stderr, "Peer %2u: %12s/%50s = %12llu\n", sm->daemon, subsystem, + name, (unsigned long long) value); + return GNUNET_OK; +} + + +/** + * Function that gathers stats from all daemons. + */ +static void +stat_run (void *cls, + struct GNUNET_TESTBED_Operation *op, + void *ca_result, + const char *emsg); + + +/** + * Function called when GET operation on stats is done. + */ +static void +get_done (void *cls, int success) +{ + struct StatMaster *sm = cls; + + GNUNET_break (GNUNET_OK == success); + sm->value++; + stat_run (sm, sm->op, sm->stat, NULL); +} + + + +/** + * Adapter function called to establish a connection to + * statistics service. + * + * @param cls closure + * @param cfg configuration of the peer to connect to; will be available until + * GNUNET_TESTBED_operation_done() is called on the operation returned + * from GNUNET_TESTBED_service_connect() + * @return service handle to return in 'op_result', NULL on error + */ +static void * +statistics_connect_adapter (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg) +{ + return GNUNET_STATISTICS_create ("", + cfg); +} + + +/** + * Adapter function called to destroy a connection to + * statistics service. + * + * @param cls closure + * @param op_result service handle returned from the connect adapter + */ +static void +statistics_disconnect_adapter (void *cls, + void *op_result) +{ + GNUNET_STATISTICS_destroy (op_result, GNUNET_NO); +} + + +/** + * Function that gathers stats from all daemons. + */ +static void +stat_run (void *cls, + struct GNUNET_TESTBED_Operation *op, + void *ca_result, + const char *emsg) +{ + struct StatMaster *sm = cls; + + sm->stat = ca_result; + GNUNET_assert (NULL != sm->stat); + if (NULL != stats[sm->value].name) + { + GNUNET_STATISTICS_get (sm->stat, +#if 0 + NULL, NULL, +#else + stats[sm->value].subsystem, stats[sm->value].name, +#endif + GNUNET_TIME_UNIT_FOREVER_REL, &get_done, &print_stat, + sm); + return; + } + GNUNET_TESTBED_operation_done (sm->op); + sm->value = 0; + sm->daemon++; + if (NUM_DAEMONS == sm->daemon) + { + GNUNET_free (sm); + cleanup (); + return; + } + sm->op = + GNUNET_TESTBED_service_connect (NULL, + daemons[sm->daemon], + "statistics", + &stat_run, sm, + &statistics_connect_adapter, + &statistics_disconnect_adapter, + NULL); +} + + +static void +do_report (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + static int download_counter; + const char *type = cls; + struct GNUNET_TIME_Relative del; + char *fancy; + struct StatMaster *sm; + + if (0 == (tc->reason & GNUNET_SCHEDULER_REASON_PREREQ_DONE)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Timeout during download for type `%s', shutting down with error\n", + type); + ok = 1; + cleanup (); + return; + } + del = GNUNET_TIME_absolute_get_duration (start_time); + if (del.rel_value == 0) + del.rel_value = 1; + fancy = + GNUNET_STRINGS_byte_size_fancy (((unsigned long long) FILESIZE) * + 1000LL / del.rel_value); + FPRINTF (stderr, "Download speed of type `%s' was %s/s\n", type, fancy); + GNUNET_free (fancy); + if (NUM_DAEMONS != ++download_counter) + return; /* more downloads to come */ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Finished all downloads, getting statistics\n"); + sm = GNUNET_malloc (sizeof (struct StatMaster)); + sm->op = + GNUNET_TESTBED_service_connect (NULL, + daemons[sm->daemon], + "statistics", + &stat_run, sm, + &statistics_connect_adapter, + &statistics_disconnect_adapter, + NULL); +} + + +static void +do_downloads (void *cls, const struct GNUNET_FS_Uri *u2, + const char *fn) +{ + int anonymity; + unsigned int i; + + if (NULL == u2) + { + cleanup (); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Timeout during upload attempt, shutting down with error\n"); + ok = 1; + return; + } + if (NULL != fn) + fn2 = GNUNET_strdup (fn); + uri2 = GNUNET_FS_uri_dup (u2); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Downloading %llu bytes\n", + (unsigned long long) FILESIZE); + start_time = GNUNET_TIME_absolute_get (); + if (NULL != strstr (progname, "dht")) + anonymity = 0; + else + anonymity = 1; + /* (semi) leach-download(s); not true leaches since + * these peers do participate in sharing, they just + * don't have to offer anything *initially*. */ + for (i = 0; i < NUM_DAEMONS - 2; i++) + GNUNET_FS_TEST_download (daemons[i], TIMEOUT, anonymity, + 0 == (i % 2) ? SEED1 : SEED2, + 0 == (i % 2) ? uri1 : uri2, VERBOSE, &do_report, + "leach"); + /* mutual downloads of (primary) sharing peers */ + GNUNET_FS_TEST_download (daemons[NUM_DAEMONS - 2], TIMEOUT, anonymity, SEED1, + uri1, VERBOSE, &do_report, "seeder 2"); + GNUNET_FS_TEST_download (daemons[NUM_DAEMONS - 1], TIMEOUT, anonymity, SEED2, + uri2, VERBOSE, &do_report, "seeder 1"); +} + + +static void +do_publish2 (void *cls, + const struct GNUNET_FS_Uri *u1, + const char *fn) +{ + int do_index; + int anonymity; + + if (NULL == u1) + { + cleanup (); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Timeout during upload attempt, shutting down with error\n"); + ok = 1; + return; + } + if (NULL != fn) + fn1 = GNUNET_strdup (fn); + uri1 = GNUNET_FS_uri_dup (u1); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Publishing %llu bytes\n", + (unsigned long long) FILESIZE); + if (NULL != strstr (progname, "index")) + do_index = GNUNET_YES; + else + do_index = GNUNET_NO; + if (NULL != strstr (progname, "dht")) + anonymity = 0; + else + anonymity = 1; + + GNUNET_FS_TEST_publish (daemons[NUM_DAEMONS - 2], TIMEOUT, anonymity, + do_index, FILESIZE, SEED2, VERBOSE, &do_downloads, + NULL); +} + + +static void +do_publish1 (void *cls, + struct GNUNET_TESTBED_Operation *op, + const char *emsg) +{ + unsigned int *coco = cls; + int do_index; + int anonymity; + + GNUNET_TESTBED_operation_done (op); + if (NULL != emsg) + { + cleanup (); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Error trying to connect: %s\n", emsg); + ok = 1; + return; + } + if (0 != (--(*coco))) + return; /* more connections to be created */ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Publishing %llu bytes\n", + (unsigned long long) FILESIZE); + if (NULL != strstr (progname, "index")) + do_index = GNUNET_YES; + else + do_index = GNUNET_NO; + if (NULL != strstr (progname, "dht")) + anonymity = 0; + else + anonymity = 1; + GNUNET_FS_TEST_publish (daemons[NUM_DAEMONS - 1], TIMEOUT, anonymity, + do_index, FILESIZE, SEED1, VERBOSE, &do_publish2, + NULL); +} + + +static void +do_connect (void *cls, + unsigned int num_peers, + struct GNUNET_TESTBED_Peer **peers) +{ + static unsigned int coco; + unsigned int i; + unsigned int j; + + GNUNET_assert (NUM_DAEMONS == num_peers); + for (i=0;idaemon, subsystem, - name, (unsigned long long) value); - return GNUNET_OK; -} - - -/** - * Function that gathers stats from all daemons. - */ -static void -stat_run (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc); - - -/** - * Function called when GET operation on stats is done. - */ -static void -get_done (void *cls, int success) -{ - struct StatMaster *sm = cls; - - GNUNET_break (GNUNET_OK == success); - sm->value++; - GNUNET_SCHEDULER_add_now (&stat_run, sm); -} - - -/** - * Function that gathers stats from all daemons. - */ -static void -stat_run (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - struct StatMaster *sm = cls; - - if (stats[sm->value].name != NULL) - { - GNUNET_STATISTICS_get (sm->stat, -#if 0 - NULL, NULL, -#else - stats[sm->value].subsystem, stats[sm->value].name, -#endif - GNUNET_TIME_UNIT_FOREVER_REL, &get_done, &print_stat, - sm); - return; - } - GNUNET_STATISTICS_destroy (sm->stat, GNUNET_NO); - sm->value = 0; - sm->daemon++; - if (sm->daemon == NUM_DAEMONS) - { - GNUNET_free (sm); - GNUNET_SCHEDULER_add_now (&do_stop, NULL); - return; - } - sm->stat = - GNUNET_STATISTICS_create ("", - GNUNET_FS_TEST_get_configuration (daemons, - sm->daemon)); - GNUNET_SCHEDULER_add_now (&stat_run, sm); -} - - -static void -do_report (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - static int download_counter; - const char *type = cls; - struct GNUNET_TIME_Relative del; - char *fancy; - struct StatMaster *sm; - - if (0 != (tc->reason & GNUNET_SCHEDULER_REASON_PREREQ_DONE)) - { - del = GNUNET_TIME_absolute_get_duration (start_time); - if (del.rel_value == 0) - del.rel_value = 1; - fancy = - GNUNET_STRINGS_byte_size_fancy (((unsigned long long) FILESIZE) * - 1000LL / del.rel_value); - FPRINTF (stderr, "Download speed of type `%s' was %s/s\n", type, fancy); - GNUNET_free (fancy); - if (NUM_DAEMONS != ++download_counter) - return; /* more downloads to come */ - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Finished all downloads, shutting down\n", - (unsigned long long) FILESIZE); - sm = GNUNET_malloc (sizeof (struct StatMaster)); - sm->stat = - GNUNET_STATISTICS_create ("", - GNUNET_FS_TEST_get_configuration (daemons, - sm->daemon)); - GNUNET_SCHEDULER_add_now (&stat_run, sm); - } - else - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "Timeout during download for type `%s', shutting down with error\n", - type); - ok = 1; - GNUNET_SCHEDULER_add_now (&do_stop, NULL); - } -} - - -static void -do_downloads (void *cls, const struct GNUNET_FS_Uri *u2) -{ - int anonymity; - unsigned int i; - - if (NULL == u2) - { - GNUNET_FS_TEST_daemons_stop (NUM_DAEMONS, daemons); - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "Timeout during upload attempt, shutting down with error\n"); - ok = 1; - return; - } - uri2 = GNUNET_FS_uri_dup (u2); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Downloading %llu bytes\n", - (unsigned long long) FILESIZE); - start_time = GNUNET_TIME_absolute_get (); - if (NULL != strstr (progname, "dht")) - anonymity = 0; - else - anonymity = 1; - /* (semi) leach-download(s); not true leaches since - * these peers do participate in sharing, they just - * don't have to offer anything *initially*. */ - for (i = 0; i < NUM_DAEMONS - 2; i++) - GNUNET_FS_TEST_download (daemons[i], TIMEOUT, anonymity, - 0 == (i % 2) ? SEED1 : SEED2, - 0 == (i % 2) ? uri1 : uri2, VERBOSE, &do_report, - "leach"); - /* mutual downloads of (primary) sharing peers */ - GNUNET_FS_TEST_download (daemons[NUM_DAEMONS - 2], TIMEOUT, anonymity, SEED1, - uri1, VERBOSE, &do_report, "seeder 2"); - GNUNET_FS_TEST_download (daemons[NUM_DAEMONS - 1], TIMEOUT, anonymity, SEED2, - uri2, VERBOSE, &do_report, "seeder 1"); -} - - -static void -do_publish2 (void *cls, const struct GNUNET_FS_Uri *u1) -{ - int do_index; - int anonymity; - - if (NULL == u1) - { - GNUNET_FS_TEST_daemons_stop (NUM_DAEMONS, daemons); - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "Timeout during upload attempt, shutting down with error\n"); - ok = 1; - return; - } - uri1 = GNUNET_FS_uri_dup (u1); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Publishing %llu bytes\n", - (unsigned long long) FILESIZE); - if (NULL != strstr (progname, "index")) - do_index = GNUNET_YES; - else - do_index = GNUNET_NO; - if (NULL != strstr (progname, "dht")) - anonymity = 0; - else - anonymity = 1; - - GNUNET_FS_TEST_publish (daemons[NUM_DAEMONS - 2], TIMEOUT, anonymity, - do_index, FILESIZE, SEED2, VERBOSE, &do_downloads, - NULL); -} - -static void -do_publish1 (void *cls, const char *emsg) -{ - int do_index; - int anonymity; - - if (NULL != emsg) - { - GNUNET_FS_TEST_daemons_stop (NUM_DAEMONS, daemons); - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Error trying to connect: %s\n", emsg); - ok = 1; - return; - } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Publishing %llu bytes\n", - (unsigned long long) FILESIZE); - if (NULL != strstr (progname, "index")) - do_index = GNUNET_YES; - else - do_index = GNUNET_NO; - if (NULL != strstr (progname, "dht")) - anonymity = 0; - else - anonymity = 1; - - GNUNET_FS_TEST_publish (daemons[NUM_DAEMONS - 1], TIMEOUT, anonymity, - do_index, FILESIZE, SEED1, VERBOSE, &do_publish2, - NULL); -} - - -static void -do_connect (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - struct GNUNET_TESTING_PeerGroup *pg; - - GNUNET_assert (0 != (tc->reason & GNUNET_SCHEDULER_REASON_PREREQ_DONE)); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Daemons started, will now try to connect them\n"); - pg = GNUNET_FS_TEST_get_group (daemons); - GNUNET_TESTING_create_topology (pg, GNUNET_TESTING_TOPOLOGY_CLIQUE, - GNUNET_TESTING_TOPOLOGY_NONE, NULL); - GNUNET_TESTING_connect_topology (pg, GNUNET_TESTING_TOPOLOGY_CLIQUE, - GNUNET_TESTING_TOPOLOGY_OPTION_NONE, 0.0, - TIMEOUT, NUM_DAEMONS, &do_publish1, NULL); -} - - -static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) -{ - GNUNET_FS_TEST_daemons_start ("fs_test_lib_data.conf", TIMEOUT, NUM_DAEMONS, - daemons, &do_connect, NULL); -} - - -int -main (int argc, char *argv[]) -{ - char *const argvx[] = { - "perf-gnunet-service-fs-p2p", - "-c", - "fs_test_lib_data.conf", -#if VERBOSE - "-L", "DEBUG", -#endif - NULL - }; - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - progname = argv[0]; - GNUNET_DISK_directory_remove ("/tmp/gnunet-test-fs-lib/"); - GNUNET_log_setup ("perf_gnunet_service_fs_p2p_trust", -#if VERBOSE - "DEBUG", -#else - "WARNING", -#endif - NULL); - GNUNET_PROGRAM_run ((sizeof (argvx) / sizeof (char *)) - 1, argvx, - "perf-gnunet-service-fs-p2p-trust", "nohelp", options, - &run, NULL); - GNUNET_DISK_directory_remove ("/tmp/gnunet-test-fs-lib/"); - return ok; -} - -/* end of perf_gnunet_service_fs_p2p_trust.c */ diff --git a/src/fs/plugin_block_fs.c b/src/fs/plugin_block_fs.c index 9b73f24..8e90589 100644 --- a/src/fs/plugin_block_fs.c +++ b/src/fs/plugin_block_fs.c @@ -29,7 +29,6 @@ #include "block_fs.h" #include "gnunet_signatures.h" -#define DEBUG_FS_BLOCK GNUNET_EXTRA_LOGGING /** * Number of bits we set per entry in the bloomfilter. @@ -57,17 +56,17 @@ */ static enum GNUNET_BLOCK_EvaluationResult block_plugin_fs_evaluate (void *cls, enum GNUNET_BLOCK_Type type, - const GNUNET_HashCode * query, + const struct GNUNET_HashCode * query, struct GNUNET_CONTAINER_BloomFilter **bf, int32_t bf_mutator, const void *xquery, size_t xquery_size, const void *reply_block, size_t reply_block_size) { const struct SBlock *sb; - GNUNET_HashCode chash; - GNUNET_HashCode mhash; - const GNUNET_HashCode *nsid; - GNUNET_HashCode sh; + struct GNUNET_HashCode chash; + struct GNUNET_HashCode mhash; + const struct GNUNET_HashCode *nsid; + struct GNUNET_HashCode sh; switch (type) { @@ -107,7 +106,7 @@ block_plugin_fs_evaluate (void *cls, enum GNUNET_BLOCK_Type type, } return GNUNET_BLOCK_EVALUATION_OK_MORE; case GNUNET_BLOCK_TYPE_FS_SBLOCK: - if (xquery_size != sizeof (GNUNET_HashCode)) + if (xquery_size != sizeof (struct GNUNET_HashCode)) { GNUNET_break_op (0); return GNUNET_BLOCK_EVALUATION_REQUEST_INVALID; @@ -124,13 +123,8 @@ block_plugin_fs_evaluate (void *cls, enum GNUNET_BLOCK_Type type, GNUNET_CRYPTO_hash (&sb->subspace, sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded), &sh); - if (0 != memcmp (nsid, &sh, sizeof (GNUNET_HashCode))) - { - GNUNET_log_from (GNUNET_ERROR_TYPE_WARNING, "block-fs", - _ - ("Reply mismatched in terms of namespace. Discarded.\n")); - return GNUNET_BLOCK_EVALUATION_RESULT_INVALID; - } + if (0 != memcmp (nsid, &sh, sizeof (struct GNUNET_HashCode))) + return GNUNET_BLOCK_EVALUATION_RESULT_IRRELEVANT; if (NULL != bf) { GNUNET_CRYPTO_hash (reply_block, reply_block_size, &chash); @@ -167,7 +161,7 @@ block_plugin_fs_evaluate (void *cls, enum GNUNET_BLOCK_Type type, static int block_plugin_fs_get_key (void *cls, enum GNUNET_BLOCK_Type type, const void *block, size_t block_size, - GNUNET_HashCode * key) + struct GNUNET_HashCode * key) { const struct KBlock *kb; const struct SBlock *sb; diff --git a/src/fs/test_fs_data.conf b/src/fs/test_fs_data.conf index f2b4e1e..40e85ad 100644 --- a/src/fs/test_fs_data.conf +++ b/src/fs/test_fs_data.conf @@ -1,7 +1,6 @@ @INLINE@ test_fs_defaults.conf [PATHS] SERVICEHOME = /tmp/gnunet-test-fs-data/ -DEFAULTCONFIG = test_fs_data.conf [fs] ACTIVEMIGRATION = NO diff --git a/src/fs/test_fs_defaults.conf b/src/fs/test_fs_defaults.conf index fcb888c..278e659 100644 --- a/src/fs/test_fs_defaults.conf +++ b/src/fs/test_fs_defaults.conf @@ -1,16 +1,15 @@ [PATHS] SERVICEHOME = /tmp/gnunet-test-fs-lib/ -DEFAULTCONFIG = fs_test_lib_data.conf [gnunetd] HOSTKEY = $SERVICEHOME/.hostkey [resolver] -PORT = 43464 +PORT = 4364 HOSTNAME = localhost [transport] -PORT = 43465 +PORT = 4365 PLUGINS = tcp [nat] @@ -20,10 +19,11 @@ BEHIND_NAT = NO ALLOW_NAT = NO INTERNAL_ADDRESS = 127.0.0.1 EXTERNAL_ADDRESS = 127.0.0.1 -USE_LOCALADDR = NO +USE_LOCALADDR = YES +RETURN_LOCAL_ADDRESSES = YES [arm] -PORT = 43466 +PORT = 4366 HOSTNAME = localhost DEFAULTSERVICES = fs @@ -31,15 +31,15 @@ DEFAULTSERVICES = fs QUOTA = 100 MB [statistics] -PORT = 43467 +PORT = 4367 HOSTNAME = localhost [transport-tcp] BINDTO = 127.0.0.1 -PORT = 43468 +PORT = 4368 [peerinfo] -PORT = 43469 +PORT = 4369 HOSTNAME = localhost [ats] @@ -47,11 +47,11 @@ WAN_QUOTA_IN = 65536 WAN_QUOTA_OUT = 65536 [core] -PORT = 43470 +PORT = 4370 HOSTNAME = localhost [fs] -PORT = 43471 +PORT = 4371 HOSTNAME = localhost CONTENT_CACHING = YES CONTENT_PUSHING = YES @@ -59,15 +59,14 @@ DELAY = YES [testing] WEAKRANDOM = YES -HOSTKEYSFILE = ../../contrib/testing_hostkeys.dat + +[testing_old] +HOSTKEYSFILE = ${DATADIR}/testing_hostkeys.dat [dhtcache] QUOTA=65536 DATABASE=sqlite -[mesh] -AUTOSTART = NO - [dns] AUTOSTART = NO @@ -88,3 +87,6 @@ AUTOSTART = NO [namestore] AUTOSTART = NO + +[consensus] +AUTOSTART = NO diff --git a/src/fs/test_fs_directory.c b/src/fs/test_fs_directory.c index 96ad29c..95225d7 100644 --- a/src/fs/test_fs_directory.c +++ b/src/fs/test_fs_directory.c @@ -79,7 +79,7 @@ testDirectory (unsigned int i) char txt[128]; int ret = 0; struct GNUNET_TIME_Absolute start; - char *s; + const char *s; cls.max = i; uris = GNUNET_malloc (sizeof (struct GNUNET_FS_Uri *) * i); @@ -130,11 +130,11 @@ testDirectory (unsigned int i) GNUNET_FS_directory_builder_add (db, uris[p], mds[p], NULL); GNUNET_FS_directory_builder_finish (db, &dlen, (void **) &data); s = GNUNET_STRINGS_relative_time_to_string (GNUNET_TIME_absolute_get_duration - (start)); + (start), + GNUNET_YES); FPRINTF (stdout, "Creating directory with %u entires and total size %llu took %s\n", i, (unsigned long long) dlen, s); - GNUNET_free (s); if (i < 100) { cls.pos = 0; diff --git a/src/fs/test_fs_download.c b/src/fs/test_fs_download.c index 2781974..a62cf23 100644 --- a/src/fs/test_fs_download.c +++ b/src/fs/test_fs_download.c @@ -1,6 +1,6 @@ /* This file is part of GNUnet. - (C) 2004, 2005, 2006, 2008, 2009, 2011 Christian Grothoff (and other contributing authors) + (C) 2004, 2005, 2006, 2008, 2009, 2011, 2012 Christian Grothoff (and other contributing authors) GNUnet is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published @@ -26,14 +26,10 @@ #include "platform.h" #include "gnunet_util_lib.h" -#include "gnunet_arm_service.h" #include "gnunet_fs_service.h" +#include "gnunet_testing_lib.h" #include -#define VERBOSE GNUNET_NO - -#define START_ARM GNUNET_YES - /** * File-size we use for testing. */ @@ -49,15 +45,9 @@ */ #define LIFETIME GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MINUTES, 15) -struct PeerContext -{ - struct GNUNET_CONFIGURATION_Handle *cfg; -#if START_ARM - struct GNUNET_OS_Process *arm_proc; -#endif -}; +static unsigned int anonymity_level; -static struct PeerContext p1; +static int indexed; static struct GNUNET_TIME_Absolute start; @@ -71,17 +61,20 @@ static GNUNET_SCHEDULER_TaskIdentifier timeout_kill; static char *fn; +static char *fn1; + static int err; + static void timeout_kill_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { - if (download != NULL) + if (NULL != download) { GNUNET_FS_download_stop (download, GNUNET_YES); download = NULL; } - else if (publish != NULL) + else if (NULL != publish) { GNUNET_FS_publish_stop (publish); publish = NULL; @@ -91,16 +84,18 @@ timeout_kill_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) err = 1; } + static void abort_publish_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { - if (publish != NULL) + if (NULL != publish) { GNUNET_FS_publish_stop (publish); publish = NULL; } } + static void stop_fs_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { @@ -108,12 +103,13 @@ stop_fs_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) fs = NULL; } + static void abort_download_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { uint64_t size; - if (download != NULL) + if (NULL != download) { GNUNET_FS_download_stop (download, GNUNET_YES); download = NULL; @@ -135,43 +131,51 @@ progress_cb (void *cls, const struct GNUNET_FS_ProgressInfo *event) switch (event->status) { case GNUNET_FS_STATUS_PUBLISH_PROGRESS: -#if VERBOSE - printf ("Publish is progressing (%llu/%llu at level %u off %llu)...\n", - (unsigned long long) event->value.publish.completed, - (unsigned long long) event->value.publish.size, - event->value.publish.specifics.progress.depth, - (unsigned long long) event->value.publish.specifics. - progress.offset); -#endif + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Publish is progressing (%llu/%llu at level %u off %llu)...\n", + (unsigned long long) event->value.publish.completed, + (unsigned long long) event->value.publish.size, + event->value.publish.specifics.progress.depth, + (unsigned long long) event->value.publish.specifics. + progress.offset); break; case GNUNET_FS_STATUS_PUBLISH_COMPLETED: - printf ("Publishing complete, %llu kb/s.\n", - (unsigned long long) (FILESIZE * 1000LL / - (1 + - GNUNET_TIME_absolute_get_duration - (start).rel_value) / 1024LL)); - GAUGER ("FS", "Publishing speed (insertion)", - (unsigned long long) (FILESIZE * 1000LL / - (1 + - GNUNET_TIME_absolute_get_duration - (start).rel_value) / 1024LL), "kb/s"); + fprintf (stdout, + "Publishing complete, %llu kb/s.\n", + (unsigned long long) (FILESIZE * 1000LL / + (1 + + GNUNET_TIME_absolute_get_duration + (start).rel_value) / 1024LL)); + GAUGER ("FS", + (GNUNET_YES == indexed) + ? "Publishing speed (indexing)" + : "Publishing speed (insertion)", + (unsigned long long) (FILESIZE * 1000LL / + (1 + + GNUNET_TIME_absolute_get_duration + (start).rel_value) / 1024LL), "kb/s"); fn = GNUNET_DISK_mktemp ("gnunet-download-test-dst"); start = GNUNET_TIME_absolute_get (); download = GNUNET_FS_download_start (fs, event->value.publish.specifics. completed.chk_uri, NULL, fn, NULL, 0, - FILESIZE, 1, GNUNET_FS_DOWNLOAD_OPTION_NONE, + FILESIZE, anonymity_level, + GNUNET_FS_DOWNLOAD_OPTION_NONE, "download", NULL); GNUNET_assert (download != NULL); break; case GNUNET_FS_STATUS_DOWNLOAD_COMPLETED: - printf ("Download complete, %llu kb/s.\n", - (unsigned long long) (FILESIZE * 1000LL / - (1 + - GNUNET_TIME_absolute_get_duration - (start).rel_value) / 1024LL)); - GAUGER ("FS", "Local download speed (inserted)", + fprintf (stdout, + "Download complete, %llu kb/s.\n", + (unsigned long long) (FILESIZE * 1000LL / + (1 + + GNUNET_TIME_absolute_get_duration + (start).rel_value) / 1024LL)); + GAUGER ("FS", + (GNUNET_YES == indexed) + ? "Local download speed (indexed)" + : "Local download speed (inserted)", (unsigned long long) (FILESIZE * 1000LL / (1 + GNUNET_TIME_absolute_get_duration @@ -180,14 +184,13 @@ progress_cb (void *cls, const struct GNUNET_FS_ProgressInfo *event) break; case GNUNET_FS_STATUS_DOWNLOAD_PROGRESS: GNUNET_assert (download == event->value.download.dc); -#if VERBOSE - printf ("Download is progressing (%llu/%llu at level %u off %llu)...\n", - (unsigned long long) event->value.download.completed, - (unsigned long long) event->value.download.size, - event->value.download.specifics.progress.depth, - (unsigned long long) event->value.download.specifics. - progress.offset); -#endif + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Download is progressing (%llu/%llu at level %u off %llu)...\n", + (unsigned long long) event->value.download.completed, + (unsigned long long) event->value.download.size, + event->value.download.specifics.progress.depth, + (unsigned long long) event->value.download.specifics. + progress.offset); break; case GNUNET_FS_STATUS_PUBLISH_ERROR: FPRINTF (stderr, "Error publishing file: %s\n", @@ -240,46 +243,11 @@ progress_cb (void *cls, const struct GNUNET_FS_ProgressInfo *event) static void -setup_peer (struct PeerContext *p, const char *cfgname) -{ - p->cfg = GNUNET_CONFIGURATION_create (); -#if START_ARM - p->arm_proc = - GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-arm", - "gnunet-service-arm", -#if VERBOSE - "-L", "DEBUG", -#endif - "-c", cfgname, NULL); -#endif - GNUNET_assert (GNUNET_OK == GNUNET_CONFIGURATION_load (p->cfg, cfgname)); -} - - -static void -stop_arm (struct PeerContext *p) -{ -#if START_ARM - if (NULL != p->arm_proc) - { - if (0 != GNUNET_OS_process_kill (p->arm_proc, SIGTERM)) - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); - if (GNUNET_OS_process_wait (p->arm_proc) != GNUNET_OK) - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "waitpid"); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "ARM process %u stopped\n", - GNUNET_OS_process_get_pid (p->arm_proc)); - GNUNET_OS_process_destroy (p->arm_proc); - p->arm_proc = NULL; - } -#endif - GNUNET_CONFIGURATION_destroy (p->cfg); -} - - -static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) { + const char *binary_name = cls; const char *keywords[] = { "down_foo", "down_bar", @@ -291,8 +259,14 @@ run (void *cls, char *const *args, const char *cfgfile, size_t i; struct GNUNET_FS_BlockOptions bo; - setup_peer (&p1, "test_fs_download_data.conf"); - fs = GNUNET_FS_start (cfg, "test-fs-download", &progress_cb, NULL, + if (GNUNET_YES == + GNUNET_CONFIGURATION_get_value_yesno (cfg, + "download-test", + "USE_STREAM")) + anonymity_level = 0; + else + anonymity_level = 1; + fs = GNUNET_FS_start (cfg, binary_name, &progress_cb, NULL, GNUNET_FS_FLAGS_NONE, GNUNET_FS_OPTIONS_END); GNUNET_assert (NULL != fs); buf = GNUNET_malloc (FILESIZE); @@ -301,12 +275,34 @@ run (void *cls, char *const *args, const char *cfgfile, meta = GNUNET_CONTAINER_meta_data_create (); kuri = GNUNET_FS_uri_ksk_create_from_args (2, keywords); bo.content_priority = 42; - bo.anonymity_level = 1; + bo.anonymity_level = anonymity_level; bo.replication_level = 0; bo.expiration_time = GNUNET_TIME_relative_to_absolute (LIFETIME); - fi = GNUNET_FS_file_information_create_from_data (fs, "publish-context", - FILESIZE, buf, kuri, meta, - GNUNET_NO, &bo); + + if (GNUNET_YES == + GNUNET_CONFIGURATION_get_value_yesno (cfg, + "download-test", + "USE_INDEX")) + { + fn1 = GNUNET_DISK_mktemp ("gnunet-download-indexed-test"); + GNUNET_assert (FILESIZE == + GNUNET_DISK_fn_write (fn1, buf, FILESIZE, + GNUNET_DISK_PERM_USER_READ | + GNUNET_DISK_PERM_USER_WRITE)); + GNUNET_free (buf); + fi = GNUNET_FS_file_information_create_from_file (fs, "publish-context", fn1, + kuri, meta, GNUNET_YES, + &bo); + indexed = GNUNET_YES; + } + else + { + fi = GNUNET_FS_file_information_create_from_data (fs, "publish-context", + FILESIZE, buf, kuri, meta, + GNUNET_NO, &bo); + /* note: buf will be free'd as part of 'fi' now */ + indexed = GNUNET_NO; + } GNUNET_FS_uri_destroy (kuri); GNUNET_CONTAINER_meta_data_destroy (meta); GNUNET_assert (NULL != fi); @@ -323,30 +319,30 @@ run (void *cls, char *const *args, const char *cfgfile, int main (int argc, char *argv[]) { - char *const argvx[] = { - "test-fs-download", - "-c", - "test_fs_download_data.conf", -#if VERBOSE - "-L", "DEBUG", -#endif - NULL - }; - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; + const char *binary_name; + const char *config_name; - GNUNET_log_setup ("test_fs_download", -#if VERBOSE - "DEBUG", -#else - "WARNING", -#endif - NULL); - GNUNET_PROGRAM_run ((sizeof (argvx) / sizeof (char *)) - 1, argvx, - "test-fs-download", "nohelp", options, &run, NULL); - stop_arm (&p1); - GNUNET_DISK_directory_remove ("/tmp/gnunet-test-fs-download/"); + binary_name = "test-fs-download"; + config_name = "test_fs_download_data.conf"; + if (NULL != strstr (argv[0], "indexed")) + { + binary_name = "test-fs-download-indexed"; + config_name = "test_fs_download_indexed.conf"; + } + if (NULL != strstr (argv[0], "stream")) + { + binary_name = "test-fs-download-stream"; + config_name = "test_fs_download_stream.conf"; + } + if (0 != GNUNET_TESTING_peer_run (binary_name, + config_name, + &run, (void *) binary_name)) + return 1; + if (NULL != fn1) + { + UNLINK (fn1); + GNUNET_free (fn1); + } return err; } diff --git a/src/fs/test_fs_download_data.conf b/src/fs/test_fs_download_data.conf index 25aad51..694926a 100644 --- a/src/fs/test_fs_download_data.conf +++ b/src/fs/test_fs_download_data.conf @@ -1,5 +1,10 @@ @INLINE@ test_fs_defaults.conf [PATHS] SERVICEHOME = /tmp/gnunet-test-fs-download/ -DEFAULTCONFIG = test_fs_download_data.conf +[download-test] +# set to 'YES' to test non-anonymous download +USE_STREAM = NO + +# set to 'YES' to use indexing +USE_INDEX = NO \ No newline at end of file diff --git a/src/fs/test_fs_download_indexed.c b/src/fs/test_fs_download_indexed.c deleted file mode 100644 index d16aa97..0000000 --- a/src/fs/test_fs_download_indexed.c +++ /dev/null @@ -1,366 +0,0 @@ -/* - This file is part of GNUnet. - (C) 2004, 2005, 2006, 2008, 2009, 2011 Christian Grothoff (and other contributing authors) - - GNUnet is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published - by the Free Software Foundation; either version 3, or (at your - option) any later version. - - GNUnet is distributed in the hope that it will be useful, but - WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - General Public License for more details. - - You should have received a copy of the GNU General Public License - along with GNUnet; see the file COPYING. If not, write to the - Free Software Foundation, Inc., 59 Temple Place - Suite 330, - Boston, MA 02111-1307, USA. -*/ - -/** - * @file fs/test_fs_download_indexed.c - * @brief simple testcase for downloading of indexed file - * @author Christian Grothoff - */ - -#include "platform.h" -#include "gnunet_util_lib.h" -#include "gnunet_arm_service.h" -#include "gnunet_fs_service.h" -#include - -#define VERBOSE GNUNET_NO - -#define START_ARM GNUNET_YES - -/** - * File-size we use for testing. - */ -#define FILESIZE (1024 * 1024 * 2) - -/** - * How long until we give up on transmitting the message? - */ -#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 120) - -/** - * How long should our test-content live? - */ -#define LIFETIME GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MINUTES, 15) - -struct PeerContext -{ - struct GNUNET_CONFIGURATION_Handle *cfg; -#if START_ARM - struct GNUNET_OS_Process *arm_proc; -#endif -}; - -static struct PeerContext p1; - -static struct GNUNET_TIME_Absolute start; - -static struct GNUNET_FS_Handle *fs; - -static struct GNUNET_FS_DownloadContext *download; - -static struct GNUNET_FS_PublishContext *publish; - -static GNUNET_SCHEDULER_TaskIdentifier timeout_kill; - -static char *fn; - -static char *fn1; - -static int err; - - -static void -timeout_kill_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - fprintf (stderr, "Download not fast enough, timeout!\n"); - if (download != NULL) - { - GNUNET_FS_download_stop (download, GNUNET_YES); - download = NULL; - } - else if (publish != NULL) - { - GNUNET_FS_publish_stop (publish); - publish = NULL; - } - timeout_kill = GNUNET_SCHEDULER_NO_TASK; - err = 1; -} - -static void -abort_publish_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - if (publish != NULL) - { - GNUNET_FS_publish_stop (publish); - publish = NULL; - } -} - - -static void -stop_fs_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - GNUNET_FS_stop (fs); - fs = NULL; -} - - -static void -abort_download_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - uint64_t size; - - if (download != NULL) - { - GNUNET_FS_download_stop (download, GNUNET_YES); - download = NULL; - } - GNUNET_assert (GNUNET_OK == GNUNET_DISK_file_size (fn, &size, GNUNET_YES, GNUNET_NO)); - GNUNET_assert (size == FILESIZE); - GNUNET_DISK_directory_remove (fn); - GNUNET_free (fn); - fn = NULL; - GNUNET_SCHEDULER_cancel (timeout_kill); - timeout_kill = GNUNET_SCHEDULER_NO_TASK; -} - - -static void * -progress_cb (void *cls, const struct GNUNET_FS_ProgressInfo *event) -{ - - switch (event->status) - { - case GNUNET_FS_STATUS_PUBLISH_PROGRESS: -#if VERBOSE - printf ("Publish is progressing (%llu/%llu at level %u off %llu)...\n", - (unsigned long long) event->value.publish.completed, - (unsigned long long) event->value.publish.size, - event->value.publish.specifics.progress.depth, - (unsigned long long) event->value.publish.specifics. - progress.offset); -#endif - break; - case GNUNET_FS_STATUS_PUBLISH_COMPLETED: - printf ("Publishing complete, %llu kbps.\n", - (unsigned long long) (FILESIZE * 1000LL / - (1 + - GNUNET_TIME_absolute_get_duration - (start).rel_value) / 1024LL)); - GAUGER ("FS", "Publishing speed (indexing)", - (unsigned long long) (FILESIZE * 1000LL / - (1 + - GNUNET_TIME_absolute_get_duration - (start).rel_value) / 1024LL), "kb/s"); - fn = GNUNET_DISK_mktemp ("gnunet-download-test-dst"); - start = GNUNET_TIME_absolute_get (); - download = - GNUNET_FS_download_start (fs, - event->value.publish.specifics. - completed.chk_uri, NULL, fn, NULL, 0, - FILESIZE, 1, GNUNET_FS_DOWNLOAD_OPTION_NONE, - "download", NULL); - GNUNET_assert (download != NULL); - break; - case GNUNET_FS_STATUS_DOWNLOAD_COMPLETED: - printf ("Download complete, %llu kbps.\n", - (unsigned long long) (FILESIZE * 1000LL / - (1 + - GNUNET_TIME_absolute_get_duration - (start).rel_value) / 1024LL)); - GAUGER ("FS", "Local download speed (indexed)", - (unsigned long long) (FILESIZE * 1000LL / - (1 + - GNUNET_TIME_absolute_get_duration - (start).rel_value) / 1024LL), "kb/s"); - GNUNET_SCHEDULER_add_now (&abort_download_task, NULL); - break; - case GNUNET_FS_STATUS_DOWNLOAD_PROGRESS: - GNUNET_assert (download == event->value.download.dc); -#if VERBOSE - printf ("Download is progressing (%llu/%llu at level %u off %llu)...\n", - (unsigned long long) event->value.download.completed, - (unsigned long long) event->value.download.size, - event->value.download.specifics.progress.depth, - (unsigned long long) event->value.download.specifics. - progress.offset); -#endif - break; - case GNUNET_FS_STATUS_PUBLISH_ERROR: - FPRINTF (stderr, "Error publishing file: %s\n", - event->value.publish.specifics.error.message); - GNUNET_break (0); - GNUNET_SCHEDULER_add_continuation (&abort_publish_task, NULL, - GNUNET_SCHEDULER_REASON_PREREQ_DONE); - break; - case GNUNET_FS_STATUS_DOWNLOAD_ERROR: - FPRINTF (stderr, "Error downloading file: %s\n", - event->value.download.specifics.error.message); - GNUNET_SCHEDULER_add_now (&abort_download_task, NULL); - break; - case GNUNET_FS_STATUS_DOWNLOAD_ACTIVE: - case GNUNET_FS_STATUS_DOWNLOAD_INACTIVE: - break; - case GNUNET_FS_STATUS_PUBLISH_START: - GNUNET_assert (0 == strcmp ("publish-context", event->value.publish.cctx)); - GNUNET_assert (NULL == event->value.publish.pctx); - GNUNET_assert (FILESIZE == event->value.publish.size); - GNUNET_assert (0 == event->value.publish.completed); - GNUNET_assert (1 == event->value.publish.anonymity); - break; - case GNUNET_FS_STATUS_PUBLISH_STOPPED: - GNUNET_assert (publish == event->value.publish.pc); - GNUNET_assert (FILESIZE == event->value.publish.size); - GNUNET_assert (1 == event->value.publish.anonymity); - GNUNET_SCHEDULER_add_now (&stop_fs_task, NULL); - break; - case GNUNET_FS_STATUS_DOWNLOAD_START: - GNUNET_assert (0 == strcmp ("download", event->value.download.cctx)); - GNUNET_assert (NULL == event->value.download.pctx); - GNUNET_assert (NULL != event->value.download.uri); - GNUNET_assert (0 == strcmp (fn, event->value.download.filename)); - GNUNET_assert (FILESIZE == event->value.download.size); - GNUNET_assert (0 == event->value.download.completed); - GNUNET_assert (1 == event->value.download.anonymity); - break; - case GNUNET_FS_STATUS_DOWNLOAD_STOPPED: - GNUNET_assert (download == event->value.download.dc); - GNUNET_SCHEDULER_add_continuation (&abort_publish_task, NULL, - GNUNET_SCHEDULER_REASON_PREREQ_DONE); - break; - default: - printf ("Unexpected event: %d\n", event->status); - break; - } - return NULL; -} - - -static void -setup_peer (struct PeerContext *p, const char *cfgname) -{ - p->cfg = GNUNET_CONFIGURATION_create (); -#if START_ARM - p->arm_proc = - GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-arm", - "gnunet-service-arm", - "-c", cfgname, NULL); -#endif - GNUNET_assert (GNUNET_OK == GNUNET_CONFIGURATION_load (p->cfg, cfgname)); -} - - -static void -stop_arm (struct PeerContext *p) -{ -#if START_ARM - if (NULL != p->arm_proc) - { - if (0 != GNUNET_OS_process_kill (p->arm_proc, SIGTERM)) - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); - if (GNUNET_OS_process_wait (p->arm_proc) != GNUNET_OK) - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "waitpid"); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "ARM process %u stopped\n", - GNUNET_OS_process_get_pid (p->arm_proc)); - GNUNET_OS_process_destroy (p->arm_proc); - p->arm_proc = NULL; - } -#endif - GNUNET_CONFIGURATION_destroy (p->cfg); -} - - -static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) -{ - const char *keywords[] = { - "down_foo", - "down_bar", - }; - char *buf; - struct GNUNET_CONTAINER_MetaData *meta; - struct GNUNET_FS_Uri *kuri; - struct GNUNET_FS_FileInformation *fi; - struct GNUNET_FS_BlockOptions bo; - size_t i; - - setup_peer (&p1, "test_fs_download_data.conf"); - fs = GNUNET_FS_start (cfg, "test-fs-download-indexed", &progress_cb, NULL, - GNUNET_FS_FLAGS_NONE, GNUNET_FS_OPTIONS_END); - GNUNET_assert (NULL != fs); - - fn1 = GNUNET_DISK_mktemp ("gnunet-download-indexed-test"); - buf = GNUNET_malloc (FILESIZE); - for (i = 0; i < FILESIZE; i++) - buf[i] = GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK, 256); - GNUNET_assert (FILESIZE == - GNUNET_DISK_fn_write (fn1, buf, FILESIZE, - GNUNET_DISK_PERM_USER_READ | - GNUNET_DISK_PERM_USER_WRITE)); - GNUNET_free (buf); - meta = GNUNET_CONTAINER_meta_data_create (); - kuri = GNUNET_FS_uri_ksk_create_from_args (2, keywords); - bo.content_priority = 42; - bo.anonymity_level = 1; - bo.replication_level = 0; - bo.expiration_time = GNUNET_TIME_relative_to_absolute (LIFETIME); - fi = GNUNET_FS_file_information_create_from_file (fs, "publish-context", fn1, - kuri, meta, GNUNET_YES, - &bo); - GNUNET_FS_uri_destroy (kuri); - GNUNET_CONTAINER_meta_data_destroy (meta); - GNUNET_assert (NULL != fi); - timeout_kill = - GNUNET_SCHEDULER_add_delayed (TIMEOUT, &timeout_kill_task, NULL); - start = GNUNET_TIME_absolute_get (); - publish = - GNUNET_FS_publish_start (fs, fi, NULL, NULL, NULL, - GNUNET_FS_PUBLISH_OPTION_NONE); - GNUNET_assert (publish != NULL); -} - - -int -main (int argc, char *argv[]) -{ - char *const argvx[] = { - "test-fs-download-indexed", - "-c", - "test_fs_download_data.conf", - NULL - }; - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - - GNUNET_log_setup ("test_fs_download_indexed", - "WARNING", - NULL); - GNUNET_PROGRAM_run ((sizeof (argvx) / sizeof (char *)) - 1, argvx, - "test-fs-download-indexed", "nohelp", options, &run, - NULL); - stop_arm (&p1); - if (fn1 != NULL) - { - GNUNET_DISK_directory_remove (fn1); - GNUNET_free (fn1); - } - if (fn != NULL) - { - GNUNET_DISK_directory_remove (fn); - GNUNET_free (fn); - } - GNUNET_DISK_directory_remove ("/tmp/gnunet-test-fs-download/"); - return err; -} - -/* end of test_fs_download_indexed.c */ diff --git a/src/fs/test_fs_download_indexed.conf b/src/fs/test_fs_download_indexed.conf new file mode 100644 index 0000000..61954c1 --- /dev/null +++ b/src/fs/test_fs_download_indexed.conf @@ -0,0 +1,10 @@ +@INLINE@ test_fs_defaults.conf +[PATHS] +SERVICEHOME = /tmp/gnunet-test-fs-download/ + +[download-test] +# set to 'YES' to test non-anonymous download +USE_STREAM = NO + +# set to 'YES' to use indexing +USE_INDEX = YES diff --git a/src/fs/test_fs_download_persistence.c b/src/fs/test_fs_download_persistence.c index ba776dd..d588387 100644 --- a/src/fs/test_fs_download_persistence.c +++ b/src/fs/test_fs_download_persistence.c @@ -23,16 +23,11 @@ * @brief simple testcase for persistence of simple download operation * @author Christian Grothoff */ - #include "platform.h" #include "gnunet_util_lib.h" -#include "gnunet_arm_service.h" +#include "gnunet_testing_lib.h" #include "gnunet_fs_service.h" -#define VERBOSE GNUNET_NO - -#define START_ARM GNUNET_YES - /** * File-size we use for testing. */ @@ -48,15 +43,6 @@ */ #define LIFETIME GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MINUTES, 15) -struct PeerContext -{ - struct GNUNET_CONFIGURATION_Handle *cfg; -#if START_ARM - struct GNUNET_OS_Process *arm_proc; -#endif -}; - -static struct PeerContext p1; static struct GNUNET_TIME_Absolute start; @@ -74,6 +60,7 @@ static char *fn; static int err; + static void timeout_kill_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { @@ -92,6 +79,7 @@ timeout_kill_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) err = 1; } + static void abort_publish_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { @@ -166,14 +154,13 @@ progress_cb (void *cls, const struct GNUNET_FS_ProgressInfo *event) switch (event->status) { case GNUNET_FS_STATUS_PUBLISH_PROGRESS: -#if VERBOSE - printf ("Publish is progressing (%llu/%llu at level %u off %llu)...\n", - (unsigned long long) event->value.publish.completed, - (unsigned long long) event->value.publish.size, - event->value.publish.specifics.progress.depth, - (unsigned long long) event->value.publish.specifics. - progress.offset); -#endif + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Publish is progressing (%llu/%llu at level %u off %llu)...\n", + (unsigned long long) event->value.publish.completed, + (unsigned long long) event->value.publish.size, + event->value.publish.specifics.progress.depth, + (unsigned long long) event->value.publish.specifics. + progress.offset); break; case GNUNET_FS_STATUS_PUBLISH_COMPLETED: printf ("Publishing complete, %llu kbps.\n", @@ -201,14 +188,13 @@ progress_cb (void *cls, const struct GNUNET_FS_ProgressInfo *event) case GNUNET_FS_STATUS_DOWNLOAD_PROGRESS: consider_restart (event->status); GNUNET_assert (download == event->value.download.dc); -#if VERBOSE - printf ("Download is progressing (%llu/%llu at level %u off %llu)...\n", - (unsigned long long) event->value.download.completed, - (unsigned long long) event->value.download.size, - event->value.download.specifics.progress.depth, - (unsigned long long) event->value.download.specifics. - progress.offset); -#endif + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Download is progressing (%llu/%llu at level %u off %llu)...\n", + (unsigned long long) event->value.download.completed, + (unsigned long long) event->value.download.size, + event->value.download.specifics.progress.depth, + (unsigned long long) event->value.download.specifics. + progress.offset); break; case GNUNET_FS_STATUS_PUBLISH_ERROR: FPRINTF (stderr, "Error publishing file: %s\n", @@ -290,45 +276,9 @@ progress_cb (void *cls, const struct GNUNET_FS_ProgressInfo *event) static void -setup_peer (struct PeerContext *p, const char *cfgname) -{ - p->cfg = GNUNET_CONFIGURATION_create (); -#if START_ARM - p->arm_proc = - GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-arm", - "gnunet-service-arm", -#if VERBOSE - "-L", "DEBUG", -#endif - "-c", cfgname, NULL); -#endif - GNUNET_assert (GNUNET_OK == GNUNET_CONFIGURATION_load (p->cfg, cfgname)); -} - - -static void -stop_arm (struct PeerContext *p) -{ -#if START_ARM - if (NULL != p->arm_proc) - { - if (0 != GNUNET_OS_process_kill (p->arm_proc, SIGTERM)) - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); - if (GNUNET_OS_process_wait (p->arm_proc) != GNUNET_OK) - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "waitpid"); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "ARM process %u stopped\n", - GNUNET_OS_process_get_pid (p->arm_proc)); - GNUNET_OS_process_destroy (p->arm_proc); - p->arm_proc = NULL; - } -#endif - GNUNET_CONFIGURATION_destroy (p->cfg); -} - - -static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *c) +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *c, + struct GNUNET_TESTING_Peer *peer) { const char *keywords[] = { "down_foo", @@ -342,7 +292,6 @@ run (void *cls, char *const *args, const char *cfgfile, struct GNUNET_FS_BlockOptions bo; cfg = c; - setup_peer (&p1, "test_fs_download_data.conf"); fs = GNUNET_FS_start (cfg, "test-fs-download-persistence", &progress_cb, NULL, GNUNET_FS_FLAGS_PERSISTENCE, GNUNET_FS_OPTIONS_END); GNUNET_assert (NULL != fs); @@ -374,31 +323,10 @@ run (void *cls, char *const *args, const char *cfgfile, int main (int argc, char *argv[]) { - char *const argvx[] = { - "test-fs-download-persistence", - "-c", - "test_fs_download_data.conf", -#if VERBOSE - "-L", "DEBUG", -#endif - NULL - }; - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - GNUNET_log_setup ("test_fs_download_persistence", -#if VERBOSE - "DEBUG", -#else - "WARNING", -#endif - NULL); - GNUNET_DISK_directory_remove ("/tmp/gnunet-test-fs-download/"); - GNUNET_PROGRAM_run ((sizeof (argvx) / sizeof (char *)) - 1, argvx, - "test-fs-download-persistence", "nohelp", options, &run, - NULL); - stop_arm (&p1); - GNUNET_DISK_directory_remove ("/tmp/gnunet-test-fs-download/"); + if (0 != GNUNET_TESTING_peer_run ("test-fs-download-persistence", + "test_fs_download_data.conf", + &run, NULL)) + return 1; return err; } diff --git a/src/fs/test_fs_download_stream.conf b/src/fs/test_fs_download_stream.conf new file mode 100644 index 0000000..3ee0b41 --- /dev/null +++ b/src/fs/test_fs_download_stream.conf @@ -0,0 +1,10 @@ +@INLINE@ test_fs_defaults.conf +[PATHS] +SERVICEHOME = /tmp/gnunet-test-fs-download/ + +[download-test] +# set to 'YES' to test non-anonymous download +USE_STREAM = NO + +# set to 'YES' to use indexing +USE_INDEX = NO diff --git a/src/fs/test_fs_file_information.c b/src/fs/test_fs_file_information.c index fb7de7d..cc79c80 100644 --- a/src/fs/test_fs_file_information.c +++ b/src/fs/test_fs_file_information.c @@ -31,12 +31,10 @@ * - other API functions may not yet be tested (such as * filedata-from-callback) */ - #include "platform.h" #include "gnunet_util_lib.h" #include "gnunet_fs_service.h" -#define VERBOSE GNUNET_NO /** * File-size we use for testing. @@ -137,9 +135,6 @@ run (void *cls, char *const *args, const char *cfgfile, } - - - int main (int argc, char *argv[]) { @@ -147,9 +142,6 @@ main (int argc, char *argv[]) "test-fs-file_information", "-c", "test_fs_file_information_data.conf", -#if VERBOSE - "-L", "DEBUG", -#endif NULL }; struct GNUNET_GETOPT_CommandLineOption options[] = { @@ -157,11 +149,7 @@ main (int argc, char *argv[]) }; GNUNET_log_setup ("test_fs_file_information", -#if VERBOSE - "DEBUG", -#else "WARNING", -#endif NULL); GNUNET_PROGRAM_run ((sizeof (argvx) / sizeof (char *)) - 1, argvx, "test-fs-file_information", "nohelp", options, &run, diff --git a/src/fs/test_fs_file_information_data.conf b/src/fs/test_fs_file_information_data.conf index 09cedf8..ea43807 100644 --- a/src/fs/test_fs_file_information_data.conf +++ b/src/fs/test_fs_file_information_data.conf @@ -1,7 +1,6 @@ @INLINE@ test_fs_defaults.conf [PATHS] SERVICEHOME = /tmp/gnunet-test-fs-file-information/ -DEFAULTCONFIG = test_fs_file_information_data.conf [transport] PLUGINS = diff --git a/src/fs/test_fs_getopt.c b/src/fs/test_fs_getopt.c index 571346f..7551202 100644 --- a/src/fs/test_fs_getopt.c +++ b/src/fs/test_fs_getopt.c @@ -25,15 +25,12 @@ #include "platform.h" #include "gnunet_fs_service.h" + int main (int argc, char *argv[]) { - GNUNET_log_setup ("test_fs_directory", -#if VERBOSE - "DEBUG", -#else + GNUNET_log_setup ("test_fs_getopt", "WARNING", -#endif NULL); FPRINTF (stderr, "%s", "WARNING: testcase not yet written.\n"); return 0; /* testcase passed */ diff --git a/src/fs/test_fs_list_indexed.c b/src/fs/test_fs_list_indexed.c index d046a20..91dad7c 100644 --- a/src/fs/test_fs_list_indexed.c +++ b/src/fs/test_fs_list_indexed.c @@ -27,16 +27,11 @@ * TODO: * - actually call list_indexed API! */ - #include "platform.h" #include "gnunet_util_lib.h" -#include "gnunet_arm_service.h" +#include "gnunet_testing_lib.h" #include "gnunet_fs_service.h" -#define VERBOSE GNUNET_NO - -#define START_ARM GNUNET_YES - /** * File-size we use for testing. */ @@ -52,15 +47,6 @@ */ #define LIFETIME GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MINUTES, 15) -struct PeerContext -{ - struct GNUNET_CONFIGURATION_Handle *cfg; -#if START_ARM - struct GNUNET_OS_Process *arm_proc; -#endif -}; - -static struct PeerContext p1; static struct GNUNET_TIME_Absolute start; @@ -74,6 +60,7 @@ static char *fn2; static int err; + static void abort_publish_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { @@ -120,14 +107,13 @@ progress_cb (void *cls, const struct GNUNET_FS_ProgressInfo *event) case GNUNET_FS_STATUS_PUBLISH_PROGRESS: ret = event->value.publish.cctx; GNUNET_assert (publish == event->value.publish.pc); -#if VERBOSE - printf ("Publish is progressing (%llu/%llu at level %u off %llu)...\n", - (unsigned long long) event->value.publish.completed, - (unsigned long long) event->value.publish.size, - event->value.publish.specifics.progress.depth, - (unsigned long long) event->value.publish.specifics. - progress.offset); -#endif + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Publish is progressing (%llu/%llu at level %u off %llu)...\n", + (unsigned long long) event->value.publish.completed, + (unsigned long long) event->value.publish.size, + event->value.publish.specifics.progress.depth, + (unsigned long long) event->value.publish.specifics. + progress.offset); break; case GNUNET_FS_STATUS_PUBLISH_ERROR: ret = event->value.publish.cctx; @@ -183,45 +169,9 @@ progress_cb (void *cls, const struct GNUNET_FS_ProgressInfo *event) static void -setup_peer (struct PeerContext *p, const char *cfgname) -{ - p->cfg = GNUNET_CONFIGURATION_create (); -#if START_ARM - p->arm_proc = - GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-arm", - "gnunet-service-arm", -#if VERBOSE - "-L", "DEBUG", -#endif - "-c", cfgname, NULL); -#endif - GNUNET_assert (GNUNET_OK == GNUNET_CONFIGURATION_load (p->cfg, cfgname)); -} - - -static void -stop_arm (struct PeerContext *p) -{ -#if START_ARM - if (NULL != p->arm_proc) - { - if (0 != GNUNET_OS_process_kill (p->arm_proc, SIGTERM)) - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); - if (GNUNET_OS_process_wait (p->arm_proc) != GNUNET_OK) - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "waitpid"); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "ARM process %u stopped\n", - GNUNET_OS_process_get_pid (p->arm_proc)); - GNUNET_OS_process_destroy (p->arm_proc); - p->arm_proc = NULL; - } -#endif - GNUNET_CONFIGURATION_destroy (p->cfg); -} - - -static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) { const char *keywords[] = { "down_foo", @@ -236,7 +186,6 @@ run (void *cls, char *const *args, const char *cfgfile, size_t i; struct GNUNET_FS_BlockOptions bo; - setup_peer (&p1, "test_fs_list_indexed_data.conf"); fs = GNUNET_FS_start (cfg, "test-fs-list_indexed", &progress_cb, NULL, GNUNET_FS_FLAGS_NONE, GNUNET_FS_OPTIONS_END); GNUNET_assert (NULL != fs); @@ -298,41 +247,11 @@ run (void *cls, char *const *args, const char *cfgfile, int main (int argc, char *argv[]) { - char *const argvx[] = { - "test-fs-list_indexed", - "-c", - "test_fs_list_indexed_data.conf", -#if VERBOSE - "-L", "DEBUG", -#endif - NULL - }; - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - - GNUNET_log_setup ("test_fs_list_indexed", -#if VERBOSE - "DEBUG", -#else - "WARNING", -#endif - NULL); - GNUNET_PROGRAM_run ((sizeof (argvx) / sizeof (char *)) - 1, argvx, - "test-fs-list_indexed", "nohelp", options, &run, NULL); - stop_arm (&p1); - GNUNET_DISK_directory_remove ("/tmp/gnunet-test-fs-list-indexed/"); - if (fn1 != NULL) - { - GNUNET_DISK_directory_remove (fn1); - GNUNET_free (fn1); - } - if (fn2 != NULL) - { - GNUNET_DISK_directory_remove (fn2); - GNUNET_free (fn2); - } - return err; + if (0 != GNUNET_TESTING_peer_run ("test-fs-list-indexed", + "test_fs_list_indexed_data.conf", + &run, NULL)) + return 1; + return 0; } /* end of test_fs_list_indexed.c */ diff --git a/src/fs/test_fs_list_indexed_data.conf b/src/fs/test_fs_list_indexed_data.conf index 704ba4d..99d4466 100644 --- a/src/fs/test_fs_list_indexed_data.conf +++ b/src/fs/test_fs_list_indexed_data.conf @@ -1,7 +1,6 @@ @INLINE@ test_fs_defaults.conf [PATHS] SERVICEHOME = /tmp/gnunet-test-fs-list-indexed/ -DEFAULTCONFIG = test_fs_list_indexed_data.conf [transport] PLUGINS = diff --git a/src/fs/test_fs_namespace.c b/src/fs/test_fs_namespace.c index 78af1f1..e4ac493 100644 --- a/src/fs/test_fs_namespace.c +++ b/src/fs/test_fs_namespace.c @@ -25,16 +25,11 @@ */ #include "platform.h" #include "gnunet_util_lib.h" -#include "gnunet_arm_service.h" +#include "gnunet_testing_lib.h" #include "gnunet_fs_service.h" -#define VERBOSE GNUNET_NO -#define START_ARM GNUNET_YES - -static struct PeerContext p1; - -static GNUNET_HashCode nsid; +static struct GNUNET_HashCode nsid; static struct GNUNET_FS_Uri *sks_expect_uri; @@ -52,48 +47,6 @@ static int update_started; static int err; -struct PeerContext -{ - struct GNUNET_CONFIGURATION_Handle *cfg; -#if START_ARM - struct GNUNET_OS_Process *arm_proc; -#endif -}; - - -static void -setup_peer (struct PeerContext *p, const char *cfgname) -{ - p->cfg = GNUNET_CONFIGURATION_create (); -#if START_ARM - p->arm_proc = - GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-arm", - "gnunet-service-arm", - "-c", cfgname, NULL); -#endif - GNUNET_assert (GNUNET_OK == GNUNET_CONFIGURATION_load (p->cfg, cfgname)); -} - - -static void -stop_arm (struct PeerContext *p) -{ -#if START_ARM - if (NULL != p->arm_proc) - { - if (0 != GNUNET_OS_process_kill (p->arm_proc, SIGTERM)) - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); - if (GNUNET_OS_process_wait (p->arm_proc) != GNUNET_OK) - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "waitpid"); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "ARM process %u stopped\n", - GNUNET_OS_process_get_pid (p->arm_proc)); - GNUNET_OS_process_destroy (p->arm_proc); - p->arm_proc = NULL; - } -#endif - GNUNET_CONFIGURATION_destroy (p->cfg); -} - static void abort_ksk_search_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) @@ -143,7 +96,6 @@ do_timeout (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) } - static void * progress_cb (void *cls, const struct GNUNET_FS_ProgressInfo *event) { @@ -314,7 +266,7 @@ adv_cont (void *cls, const struct GNUNET_FS_Uri *uri, const char *emsg) static void -ns_iterator (void *cls, const char *name, const GNUNET_HashCode * id) +ns_iterator (void *cls, const char *name, const struct GNUNET_HashCode * id) { int *ok = cls; @@ -365,10 +317,10 @@ testNamespace () static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) { - setup_peer (&p1, "test_fs_namespace_data.conf"); fs = GNUNET_FS_start (cfg, "test-fs-namespace", &progress_cb, NULL, GNUNET_FS_FLAGS_NONE, GNUNET_FS_OPTIONS_END); testNamespace (); @@ -378,28 +330,10 @@ run (void *cls, char *const *args, const char *cfgfile, int main (int argc, char *argv[]) { - char *const argvx[] = { - "test-fs-namespace", - "-c", - "test_fs_namespace_data.conf", - NULL - }; - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - - GNUNET_log_setup ("test_fs_namespace", - "WARNING", - NULL); - GNUNET_PROGRAM_run ((sizeof (argvx) / sizeof (char *)) - 1, argvx, - "test-fs-namespace", "nohelp", options, &run, NULL); - stop_arm (&p1); - if (GNUNET_YES != update_started) - { - FPRINTF (stderr, "%s", "Update search never started!\n"); - err = 1; - } - GNUNET_DISK_directory_remove ("/tmp/gnunet-test-fs-namespace/"); + if (0 != GNUNET_TESTING_peer_run ("test-fs-namespace", + "test_fs_namespace_data.conf", + &run, NULL)) + return 1; return err; } diff --git a/src/fs/test_fs_namespace_data.conf b/src/fs/test_fs_namespace_data.conf index 3cdd241..625eb2d 100644 --- a/src/fs/test_fs_namespace_data.conf +++ b/src/fs/test_fs_namespace_data.conf @@ -1,7 +1,6 @@ @INLINE@ test_fs_defaults.conf [PATHS] SERVICEHOME = /tmp/gnunet-test-fs-namespace/ -DEFAULTCONFIG = test_fs_namespace_data.conf [transport] PLUGINS = diff --git a/src/fs/test_fs_namespace_list_updateable.c b/src/fs/test_fs_namespace_list_updateable.c index 2cec67d..dc17ce4 100644 --- a/src/fs/test_fs_namespace_list_updateable.c +++ b/src/fs/test_fs_namespace_list_updateable.c @@ -25,14 +25,9 @@ */ #include "platform.h" #include "gnunet_util_lib.h" -#include "gnunet_arm_service.h" +#include "gnunet_testing_lib.h" #include "gnunet_fs_service.h" -#define VERBOSE GNUNET_NO - -#define START_ARM GNUNET_YES - -static struct PeerContext p1; static struct GNUNET_FS_Handle *fs; @@ -49,15 +44,6 @@ static struct GNUNET_FS_Uri *uri_next; static struct GNUNET_FS_BlockOptions bo; -struct PeerContext -{ - struct GNUNET_CONFIGURATION_Handle *cfg; -#if START_ARM - struct GNUNET_OS_Process *arm_proc; -#endif -}; - - static void * progress_cb (void *cls, const struct GNUNET_FS_ProgressInfo *event) { @@ -66,38 +52,8 @@ progress_cb (void *cls, const struct GNUNET_FS_ProgressInfo *event) static void -setup_peer (struct PeerContext *p, const char *cfgname) +do_shutdown () { - p->cfg = GNUNET_CONFIGURATION_create (); -#if START_ARM - p->arm_proc = - GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-arm", - "gnunet-service-arm", -#if VERBOSE - "-L", "DEBUG", -#endif - "-c", cfgname, NULL); -#endif - GNUNET_assert (GNUNET_OK == GNUNET_CONFIGURATION_load (p->cfg, cfgname)); -} - - -static void -stop_arm (struct PeerContext *p) -{ -#if START_ARM - if (NULL != p->arm_proc) - { - if (0 != GNUNET_OS_process_kill (p->arm_proc, SIGTERM)) - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); - if (GNUNET_OS_process_wait (p->arm_proc) != GNUNET_OK) - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "waitpid"); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "ARM process %u stopped\n", - GNUNET_OS_process_get_pid (p->arm_proc)); - GNUNET_OS_process_destroy (p->arm_proc); - p->arm_proc = NULL; - } -#endif if (uri_this != NULL) GNUNET_FS_uri_destroy (uri_this); if (uri_next != NULL) @@ -106,11 +62,9 @@ stop_arm (struct PeerContext *p) GNUNET_FS_namespace_delete (ns, GNUNET_NO); if (meta != NULL) GNUNET_CONTAINER_meta_data_destroy (meta); - GNUNET_CONFIGURATION_destroy (p->cfg); } - static void check_next (void *cls, const char *last_id, const struct GNUNET_FS_Uri *last_uri, @@ -143,7 +97,6 @@ sks_cont_next (void *cls, const struct GNUNET_FS_Uri *uri, const char *emsg) GNUNET_assert (NULL == emsg); err += 2; GNUNET_FS_namespace_list_updateable (ns, NULL, &check_this_next, NULL); - } @@ -162,7 +115,6 @@ check_this (void *cls, const char *last_id, static void sks_cont_this (void *cls, const struct GNUNET_FS_Uri *uri, const char *emsg) { - GNUNET_assert (NULL == emsg); err = 1; GNUNET_FS_namespace_list_updateable (ns, NULL, &check_this, NULL); @@ -172,11 +124,9 @@ sks_cont_this (void *cls, const struct GNUNET_FS_Uri *uri, const char *emsg) } - static void testNamespace () { - ns = GNUNET_FS_namespace_create (fs, "testNamespace"); GNUNET_assert (NULL != ns); bo.content_priority = 1; @@ -200,10 +150,10 @@ testNamespace () static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) { - setup_peer (&p1, "test_fs_namespace_data.conf"); fs = GNUNET_FS_start (cfg, "test-fs-namespace", &progress_cb, NULL, GNUNET_FS_FLAGS_NONE, GNUNET_FS_OPTIONS_END); testNamespace (); @@ -213,30 +163,11 @@ run (void *cls, char *const *args, const char *cfgfile, int main (int argc, char *argv[]) { - char *const argvx[] = { - "test-fs-namespace", - "-c", - "test_fs_namespace_data.conf", -#if VERBOSE - "-L", "DEBUG", -#endif - NULL - }; - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - - GNUNET_log_setup ("test_fs_namespace_list_updateable", -#if VERBOSE - "DEBUG", -#else - "WARNING", -#endif - NULL); - GNUNET_PROGRAM_run ((sizeof (argvx) / sizeof (char *)) - 1, argvx, - "test-fs-namespace", "nohelp", options, &run, NULL); - stop_arm (&p1); - GNUNET_DISK_directory_remove ("/tmp/gnunet-test-fs-namespace/"); + if (0 != GNUNET_TESTING_peer_run ("test-fs-namespace-list-updateable", + "test_fs_namespace_data.conf", + &run, NULL)) + return 1; + do_shutdown (); return err; } diff --git a/src/fs/test_fs_publish.c b/src/fs/test_fs_publish.c index 1560f4e..e51d6e5 100644 --- a/src/fs/test_fs_publish.c +++ b/src/fs/test_fs_publish.c @@ -17,23 +17,17 @@ Free Software Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */ - /** * @file fs/test_fs_publish.c * @brief simple testcase for publish operation (indexing, listing * indexed, directory structure) * @author Christian Grothoff */ - #include "platform.h" #include "gnunet_util_lib.h" -#include "gnunet_arm_service.h" +#include "gnunet_testing_lib.h" #include "gnunet_fs_service.h" -#define VERBOSE GNUNET_NO - -#define START_ARM GNUNET_YES - /** * File-size we use for testing. */ @@ -49,15 +43,6 @@ */ #define LIFETIME GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MINUTES, 15) -struct PeerContext -{ - struct GNUNET_CONFIGURATION_Handle *cfg; -#if START_ARM - struct GNUNET_OS_Process *arm_proc; -#endif -}; - -static struct PeerContext p1; static struct GNUNET_TIME_Absolute start; @@ -71,6 +56,7 @@ static char *fn2; static int err; + static void abort_publish_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { @@ -107,14 +93,13 @@ progress_cb (void *cls, const struct GNUNET_FS_ProgressInfo *event) case GNUNET_FS_STATUS_PUBLISH_PROGRESS: ret = event->value.publish.cctx; GNUNET_assert (publish == event->value.publish.pc); -#if VERBOSE - printf ("Publish is progressing (%llu/%llu at level %u off %llu)...\n", - (unsigned long long) event->value.publish.completed, - (unsigned long long) event->value.publish.size, - event->value.publish.specifics.progress.depth, - (unsigned long long) event->value.publish.specifics. - progress.offset); -#endif + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Publish is progressing (%llu/%llu at level %u off %llu)...\n", + (unsigned long long) event->value.publish.completed, + (unsigned long long) event->value.publish.size, + event->value.publish.specifics.progress.depth, + (unsigned long long) event->value.publish.specifics. + progress.offset); break; case GNUNET_FS_STATUS_PUBLISH_ERROR: ret = event->value.publish.cctx; @@ -168,45 +153,9 @@ progress_cb (void *cls, const struct GNUNET_FS_ProgressInfo *event) static void -setup_peer (struct PeerContext *p, const char *cfgname) -{ - p->cfg = GNUNET_CONFIGURATION_create (); -#if START_ARM - p->arm_proc = - GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-arm", - "gnunet-service-arm", -#if VERBOSE - "-L", "DEBUG", -#endif - "-c", cfgname, NULL); -#endif - GNUNET_assert (GNUNET_OK == GNUNET_CONFIGURATION_load (p->cfg, cfgname)); -} - - -static void -stop_arm (struct PeerContext *p) -{ -#if START_ARM - if (NULL != p->arm_proc) - { - if (0 != GNUNET_OS_process_kill (p->arm_proc, SIGTERM)) - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); - if (GNUNET_OS_process_wait (p->arm_proc) != GNUNET_OK) - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "waitpid"); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "ARM process %u stopped\n", - GNUNET_OS_process_get_pid (p->arm_proc)); - GNUNET_OS_process_destroy (p->arm_proc); - p->arm_proc = NULL; - } -#endif - GNUNET_CONFIGURATION_destroy (p->cfg); -} - - -static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) { const char *keywords[] = { "down_foo", @@ -221,7 +170,6 @@ run (void *cls, char *const *args, const char *cfgfile, size_t i; struct GNUNET_FS_BlockOptions bo; - setup_peer (&p1, "test_fs_publish_data.conf"); fs = GNUNET_FS_start (cfg, "test-fs-publish", &progress_cb, NULL, GNUNET_FS_FLAGS_NONE, GNUNET_FS_OPTIONS_END); GNUNET_assert (NULL != fs); @@ -283,40 +231,10 @@ run (void *cls, char *const *args, const char *cfgfile, int main (int argc, char *argv[]) { - char *const argvx[] = { - "test-fs-publish", - "-c", - "test_fs_publish_data.conf", -#if VERBOSE - "-L", "DEBUG", -#endif - NULL - }; - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - - GNUNET_log_setup ("test_fs_publish", -#if VERBOSE - "DEBUG", -#else - "WARNING", -#endif - NULL); - GNUNET_PROGRAM_run ((sizeof (argvx) / sizeof (char *)) - 1, argvx, - "test-fs-publish", "nohelp", options, &run, NULL); - stop_arm (&p1); - GNUNET_DISK_directory_remove ("/tmp/gnunet-test-fs-publish/"); - if (fn1 != NULL) - { - GNUNET_DISK_directory_remove (fn1); - GNUNET_free (fn1); - } - if (fn2 != NULL) - { - GNUNET_DISK_directory_remove (fn2); - GNUNET_free (fn2); - } + if (0 != GNUNET_TESTING_peer_run ("test-fs-publish", + "test_fs_publish_data.conf", + &run, NULL)) + return 1; return err; } diff --git a/src/fs/test_fs_publish_data.conf b/src/fs/test_fs_publish_data.conf index 234f2b0..14e6919 100644 --- a/src/fs/test_fs_publish_data.conf +++ b/src/fs/test_fs_publish_data.conf @@ -1,7 +1,6 @@ @INLINE@ test_fs_defaults.conf [PATHS] SERVICEHOME = /tmp/gnunet-test-fs-publish/ -DEFAULTCONFIG = test_fs_publish_data.conf [transport] PLUGINS = diff --git a/src/fs/test_fs_publish_persistence.c b/src/fs/test_fs_publish_persistence.c index 7d3bc32..577831a 100644 --- a/src/fs/test_fs_publish_persistence.c +++ b/src/fs/test_fs_publish_persistence.c @@ -17,21 +17,16 @@ Free Software Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */ - /** * @file fs/test_fs_publish_persistence.c * @brief simple testcase for persistence of simple publish operation * @author Christian Grothoff */ - #include "platform.h" #include "gnunet_util_lib.h" -#include "gnunet_arm_service.h" +#include "gnunet_testing_lib.h" #include "gnunet_fs_service.h" -#define VERBOSE GNUNET_NO - -#define START_ARM GNUNET_YES /** * File-size we use for testing. @@ -48,15 +43,6 @@ */ #define LIFETIME GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MINUTES, 15) -struct PeerContext -{ - struct GNUNET_CONFIGURATION_Handle *cfg; -#if START_ARM - struct GNUNET_OS_Process *arm_proc; -#endif -}; - -static struct PeerContext p1; static struct GNUNET_TIME_Absolute start; @@ -76,6 +62,7 @@ static int err; static GNUNET_SCHEDULER_TaskIdentifier rtask; + static void abort_publish_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { @@ -231,45 +218,9 @@ progress_cb (void *cls, const struct GNUNET_FS_ProgressInfo *event) static void -setup_peer (struct PeerContext *p, const char *cfgname) -{ - p->cfg = GNUNET_CONFIGURATION_create (); -#if START_ARM - p->arm_proc = - GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-arm", - "gnunet-service-arm", -#if VERBOSE - "-L", "DEBUG", -#endif - "-c", cfgname, NULL); -#endif - GNUNET_assert (GNUNET_OK == GNUNET_CONFIGURATION_load (p->cfg, cfgname)); -} - - -static void -stop_arm (struct PeerContext *p) -{ -#if START_ARM - if (NULL != p->arm_proc) - { - if (0 != GNUNET_OS_process_kill (p->arm_proc, SIGTERM)) - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); - if (GNUNET_OS_process_wait (p->arm_proc) != GNUNET_OK) - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "waitpid"); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "ARM process %u stopped\n", - GNUNET_OS_process_get_pid (p->arm_proc)); - GNUNET_OS_process_destroy (p->arm_proc); - p->arm_proc = NULL; - } -#endif - GNUNET_CONFIGURATION_destroy (p->cfg); -} - - -static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *c) +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *c, + struct GNUNET_TESTING_Peer *peer) { const char *keywords[] = { "down_foo", @@ -285,7 +236,6 @@ run (void *cls, char *const *args, const char *cfgfile, struct GNUNET_FS_BlockOptions bo; cfg = c; - setup_peer (&p1, "test_fs_publish_data.conf"); fs = GNUNET_FS_start (cfg, "test-fs-publish-persistence", &progress_cb, NULL, GNUNET_FS_FLAGS_PERSISTENCE, GNUNET_FS_OPTIONS_END); GNUNET_assert (NULL != fs); @@ -344,40 +294,10 @@ run (void *cls, char *const *args, const char *cfgfile, int main (int argc, char *argv[]) { - char *const argvx[] = { - "test-fs-publish-persistence", - "-c", - "test_fs_publish_data.conf", -#if VERBOSE - "-L", "DEBUG", -#endif - NULL - }; - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - - GNUNET_log_setup ("test_fs_publish_persistence", -#if VERBOSE - "DEBUG", -#else - "WARNING", -#endif - NULL); - GNUNET_PROGRAM_run ((sizeof (argvx) / sizeof (char *)) - 1, argvx, - "test-fs-publish", "nohelp", options, &run, NULL); - stop_arm (&p1); - GNUNET_DISK_directory_remove ("/tmp/gnunet-test-fs-publish/"); - if (fn1 != NULL) - { - GNUNET_DISK_directory_remove (fn1); - GNUNET_free (fn1); - } - if (fn2 != NULL) - { - GNUNET_DISK_directory_remove (fn2); - GNUNET_free (fn2); - } + if (0 != GNUNET_TESTING_peer_run ("test-fs-publish-persistence", + "test_fs_publish_data.conf", + &run, NULL)) + return 1; return err; } diff --git a/src/fs/test_fs_search.c b/src/fs/test_fs_search.c index 04c5897..cf4a9cb 100644 --- a/src/fs/test_fs_search.c +++ b/src/fs/test_fs_search.c @@ -17,21 +17,16 @@ Free Software Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */ - /** * @file fs/test_fs_search.c * @brief simple testcase for simple publish + search operation * @author Christian Grothoff */ - #include "platform.h" #include "gnunet_util_lib.h" -#include "gnunet_arm_service.h" +#include "gnunet_testing_lib.h" #include "gnunet_fs_service.h" -#define VERBOSE GNUNET_NO - -#define START_ARM GNUNET_YES /** * File-size we use for testing. @@ -48,16 +43,6 @@ */ #define LIFETIME GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MINUTES, 15) -struct PeerContext -{ - struct GNUNET_CONFIGURATION_Handle *cfg; - struct GNUNET_PeerIdentity id; -#if START_ARM - struct GNUNET_OS_Process *arm_proc; -#endif -}; - -static struct PeerContext p1; static struct GNUNET_TIME_Absolute start; @@ -96,14 +81,13 @@ progress_cb (void *cls, const struct GNUNET_FS_ProgressInfo *event) switch (event->status) { case GNUNET_FS_STATUS_PUBLISH_PROGRESS: -#if VERBOSE - printf ("Publish is progressing (%llu/%llu at level %u off %llu)...\n", - (unsigned long long) event->value.publish.completed, - (unsigned long long) event->value.publish.size, - event->value.publish.specifics.progress.depth, - (unsigned long long) event->value.publish.specifics. - progress.offset); -#endif + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Publish is progressing (%llu/%llu at level %u off %llu)...\n", + (unsigned long long) event->value.publish.completed, + (unsigned long long) event->value.publish.size, + event->value.publish.specifics.progress.depth, + (unsigned long long) event->value.publish.specifics. + progress.offset); break; case GNUNET_FS_STATUS_PUBLISH_COMPLETED: kuri = GNUNET_FS_uri_ksk_create_from_args (1, keywords); @@ -115,9 +99,8 @@ progress_cb (void *cls, const struct GNUNET_FS_ProgressInfo *event) GNUNET_assert (search != NULL); break; case GNUNET_FS_STATUS_SEARCH_RESULT: -#if VERBOSE - printf ("Search complete.\n"); -#endif + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Search complete.\n"); GNUNET_SCHEDULER_add_continuation (&abort_search_task, NULL, GNUNET_SCHEDULER_REASON_PREREQ_DONE); break; @@ -169,42 +152,9 @@ progress_cb (void *cls, const struct GNUNET_FS_ProgressInfo *event) static void -setup_peer (struct PeerContext *p, const char *cfgname) -{ - p->cfg = GNUNET_CONFIGURATION_create (); -#if START_ARM - p->arm_proc = - GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-arm", - "gnunet-service-arm", - "-c", cfgname, NULL); -#endif - GNUNET_assert (GNUNET_OK == GNUNET_CONFIGURATION_load (p->cfg, cfgname)); -} - - -static void -stop_arm (struct PeerContext *p) -{ -#if START_ARM - if (NULL != p->arm_proc) - { - if (0 != GNUNET_OS_process_kill (p->arm_proc, SIGTERM)) - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); - if (GNUNET_OS_process_wait (p->arm_proc) != GNUNET_OK) - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "waitpid"); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "ARM process %u stopped\n", - GNUNET_OS_process_get_pid (p->arm_proc)); - GNUNET_OS_process_destroy (p->arm_proc); - p->arm_proc = NULL; - } -#endif - GNUNET_CONFIGURATION_destroy (p->cfg); -} - - -static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) { const char *keywords[] = { "down_foo", @@ -217,7 +167,6 @@ run (void *cls, char *const *args, const char *cfgfile, struct GNUNET_FS_FileInformation *fi; size_t i; - setup_peer (&p1, "test_fs_search_data.conf"); fs = GNUNET_FS_start (cfg, "test-fs-search", &progress_cb, NULL, GNUNET_FS_FLAGS_NONE, GNUNET_FS_OPTIONS_END); GNUNET_assert (NULL != fs); @@ -247,23 +196,10 @@ run (void *cls, char *const *args, const char *cfgfile, int main (int argc, char *argv[]) { - char *const argvx[] = { - "test-fs-search", - "-c", - "test_fs_search_data.conf", - NULL - }; - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - - GNUNET_log_setup ("test_fs_search", - "WARNING", - NULL); - GNUNET_PROGRAM_run ((sizeof (argvx) / sizeof (char *)) - 1, argvx, - "test-fs-search", "nohelp", options, &run, NULL); - stop_arm (&p1); - GNUNET_DISK_directory_remove ("/tmp/gnunet-test-fs-search/"); + if (0 != GNUNET_TESTING_peer_run ("test-fs-search", + "test_fs_search_data.conf", + &run, NULL)) + return 1; return 0; } diff --git a/src/fs/test_fs_search_data.conf b/src/fs/test_fs_search_data.conf index ea5e4c5..812a7bf 100644 --- a/src/fs/test_fs_search_data.conf +++ b/src/fs/test_fs_search_data.conf @@ -1,7 +1,6 @@ @INLINE@ test_fs_defaults.conf [PATHS] SERVICEHOME = /tmp/gnunet-test-fs-search/ -DEFAULTCONFIG = test_fs_search_data.conf [transport] PLUGINS = diff --git a/src/fs/test_fs_search_persistence.c b/src/fs/test_fs_search_persistence.c index d18b50e..d66c5ec 100644 --- a/src/fs/test_fs_search_persistence.c +++ b/src/fs/test_fs_search_persistence.c @@ -17,21 +17,16 @@ Free Software Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */ - /** * @file fs/test_fs_search_persistence.c * @brief simple testcase for persistence of search operation * @author Christian Grothoff */ - #include "platform.h" #include "gnunet_util_lib.h" -#include "gnunet_arm_service.h" +#include "gnunet_testing_lib.h" #include "gnunet_fs_service.h" -#define VERBOSE GNUNET_NO - -#define START_ARM GNUNET_YES /** * File-size we use for testing. @@ -48,16 +43,6 @@ */ #define LIFETIME GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MINUTES, 15) -struct PeerContext -{ - struct GNUNET_CONFIGURATION_Handle *cfg; - struct GNUNET_PeerIdentity id; -#if START_ARM - struct GNUNET_OS_Process *arm_proc; -#endif -}; - -static struct PeerContext p1; static struct GNUNET_TIME_Absolute start; @@ -69,6 +54,7 @@ static struct GNUNET_FS_PublishContext *publish; static const struct GNUNET_CONFIGURATION_Handle *cfg; + static void abort_publish_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { @@ -99,8 +85,6 @@ restart_fs_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) } - - /** * Consider scheduling the restart-task. * Only runs the restart task once per event @@ -135,14 +119,13 @@ progress_cb (void *cls, const struct GNUNET_FS_ProgressInfo *event) switch (event->status) { case GNUNET_FS_STATUS_PUBLISH_PROGRESS: -#if VERBOSE - printf ("Publish is progressing (%llu/%llu at level %u off %llu)...\n", - (unsigned long long) event->value.publish.completed, - (unsigned long long) event->value.publish.size, - event->value.publish.specifics.progress.depth, - (unsigned long long) event->value.publish.specifics. - progress.offset); -#endif + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Publish is progressing (%llu/%llu at level %u off %llu)...\n", + (unsigned long long) event->value.publish.completed, + (unsigned long long) event->value.publish.size, + event->value.publish.specifics.progress.depth, + (unsigned long long) event->value.publish.specifics. + progress.offset); break; case GNUNET_FS_STATUS_PUBLISH_COMPLETED: kuri = GNUNET_FS_uri_ksk_create_from_args (1, keywords); @@ -163,9 +146,8 @@ progress_cb (void *cls, const struct GNUNET_FS_ProgressInfo *event) case GNUNET_FS_STATUS_SEARCH_RESULT: /* FIXME: consider_restart (event->status); cannot be tested with * search result since we exit here after the first one... */ -#if VERBOSE - printf ("Search complete.\n"); -#endif + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Search complete.\n"); GNUNET_SCHEDULER_add_continuation (&abort_search_task, NULL, GNUNET_SCHEDULER_REASON_PREREQ_DONE); break; @@ -231,45 +213,9 @@ progress_cb (void *cls, const struct GNUNET_FS_ProgressInfo *event) static void -setup_peer (struct PeerContext *p, const char *cfgname) -{ - p->cfg = GNUNET_CONFIGURATION_create (); -#if START_ARM - p->arm_proc = - GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-arm", - "gnunet-service-arm", -#if VERBOSE - "-L", "DEBUG", -#endif - "-c", cfgname, NULL); -#endif - GNUNET_assert (GNUNET_OK == GNUNET_CONFIGURATION_load (p->cfg, cfgname)); -} - - -static void -stop_arm (struct PeerContext *p) -{ -#if START_ARM - if (NULL != p->arm_proc) - { - if (0 != GNUNET_OS_process_kill (p->arm_proc, SIGTERM)) - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); - if (GNUNET_OS_process_wait (p->arm_proc) != GNUNET_OK) - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "waitpid"); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "ARM process %u stopped\n", - GNUNET_OS_process_get_pid (p->arm_proc)); - GNUNET_OS_process_destroy (p->arm_proc); - p->arm_proc = NULL; - } -#endif - GNUNET_CONFIGURATION_destroy (p->cfg); -} - - -static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *c) +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *c, + struct GNUNET_TESTING_Peer *peer) { const char *keywords[] = { "down_foo", @@ -283,7 +229,6 @@ run (void *cls, char *const *args, const char *cfgfile, struct GNUNET_FS_BlockOptions bo; cfg = c; - setup_peer (&p1, "test_fs_search_data.conf"); fs = GNUNET_FS_start (cfg, "test-fs-search-persistence", &progress_cb, NULL, GNUNET_FS_FLAGS_PERSISTENCE, GNUNET_FS_OPTIONS_END); GNUNET_assert (NULL != fs); @@ -313,32 +258,10 @@ run (void *cls, char *const *args, const char *cfgfile, int main (int argc, char *argv[]) { - char *const argvx[] = { - "test-fs-search-persistence", - "-c", - "test_fs_search_data.conf", -#if VERBOSE - "-L", "DEBUG", -#endif - NULL - }; - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - - GNUNET_DISK_directory_remove ("/tmp/gnunet-test-fs-search/"); - GNUNET_log_setup ("test_fs_search_persistence", -#if VERBOSE - "DEBUG", -#else - "WARNING", -#endif - NULL); - GNUNET_PROGRAM_run ((sizeof (argvx) / sizeof (char *)) - 1, argvx, - "test-fs-search-persistence", "nohelp", options, &run, - NULL); - stop_arm (&p1); - GNUNET_DISK_directory_remove ("/tmp/gnunet-test-fs-search/"); + if (0 != GNUNET_TESTING_peer_run ("test-fs-search-persistence", + "test_fs_search_data.conf", + &run, NULL)) + return 1; return 0; } diff --git a/src/fs/test_fs_search_probes.c b/src/fs/test_fs_search_probes.c index b816598..0b02532 100644 --- a/src/fs/test_fs_search_probes.c +++ b/src/fs/test_fs_search_probes.c @@ -25,10 +25,9 @@ */ #include "platform.h" #include "gnunet_util_lib.h" -#include "gnunet_arm_service.h" +#include "gnunet_testing_lib.h" #include "gnunet_fs_service.h" -#define START_ARM GNUNET_YES /** * File-size we use for testing. @@ -45,16 +44,6 @@ */ #define LIFETIME GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MINUTES, 15) -struct PeerContext -{ - struct GNUNET_CONFIGURATION_Handle *cfg; - struct GNUNET_PeerIdentity id; -#if START_ARM - struct GNUNET_OS_Process *arm_proc; -#endif -}; - -static struct PeerContext p1; static struct GNUNET_TIME_Absolute start; @@ -141,9 +130,9 @@ progress_cb (void *cls, const struct GNUNET_FS_ProgressInfo *event) fs = NULL; break; case GNUNET_FS_STATUS_SEARCH_UPDATE: - GNUNET_assert (0 < event->value.search.specifics.update.availability_rank); - GNUNET_assert (0 < event->value.search.specifics.update.availability_certainty); - GNUNET_SCHEDULER_add_now (&abort_search_task, NULL); + if ( (0 < event->value.search.specifics.update.availability_rank) && + (0 < event->value.search.specifics.update.availability_certainty) ) + GNUNET_SCHEDULER_add_now (&abort_search_task, NULL); break; case GNUNET_FS_STATUS_SEARCH_START: GNUNET_assert (search == NULL); @@ -166,42 +155,9 @@ progress_cb (void *cls, const struct GNUNET_FS_ProgressInfo *event) static void -setup_peer (struct PeerContext *p, const char *cfgname) -{ - p->cfg = GNUNET_CONFIGURATION_create (); -#if START_ARM - p->arm_proc = - GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-arm", - "gnunet-service-arm", - "-c", cfgname, NULL); -#endif - GNUNET_assert (GNUNET_OK == GNUNET_CONFIGURATION_load (p->cfg, cfgname)); -} - - -static void -stop_arm (struct PeerContext *p) -{ -#if START_ARM - if (NULL != p->arm_proc) - { - if (0 != GNUNET_OS_process_kill (p->arm_proc, SIGTERM)) - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); - if (GNUNET_OS_process_wait (p->arm_proc) != GNUNET_OK) - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "waitpid"); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "ARM process %u stopped\n", - GNUNET_OS_process_get_pid (p->arm_proc)); - GNUNET_OS_process_destroy (p->arm_proc); - p->arm_proc = NULL; - } -#endif - GNUNET_CONFIGURATION_destroy (p->cfg); -} - - -static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) { const char *keywords[] = { "down_foo", @@ -214,7 +170,6 @@ run (void *cls, char *const *args, const char *cfgfile, struct GNUNET_FS_FileInformation *fi; size_t i; - setup_peer (&p1, "test_fs_search_data.conf"); fs = GNUNET_FS_start (cfg, "test-fs-search", &progress_cb, NULL, GNUNET_FS_FLAGS_DO_PROBES, GNUNET_FS_OPTIONS_END); @@ -245,23 +200,10 @@ run (void *cls, char *const *args, const char *cfgfile, int main (int argc, char *argv[]) { - char *const argvx[] = { - "test-fs-search-probes", - "-c", - "test_fs_search_data.conf", - NULL - }; - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - - GNUNET_log_setup ("test_fs_search_probes", - "WARNING", - NULL); - GNUNET_PROGRAM_run ((sizeof (argvx) / sizeof (char *)) - 1, argvx, - "test-fs-search", "nohelp", options, &run, NULL); - stop_arm (&p1); - GNUNET_DISK_directory_remove ("/tmp/gnunet-test-fs-search/"); + if (0 != GNUNET_TESTING_peer_run ("test-fs-search-probes", + "test_fs_search_data.conf", + &run, NULL)) + return 1; return 0; } diff --git a/src/fs/test_fs_start_stop.c b/src/fs/test_fs_start_stop.c index 6bd698a..463274e 100644 --- a/src/fs/test_fs_start_stop.c +++ b/src/fs/test_fs_start_stop.c @@ -17,7 +17,6 @@ Free Software Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */ - /** * @file fs/test_fs_start_stop.c * @brief testcase for fs.c (start-stop only) @@ -26,23 +25,9 @@ #include "platform.h" #include "gnunet_util_lib.h" -#include "gnunet_arm_service.h" +#include "gnunet_testing_lib.h" #include "gnunet_fs_service.h" -#define VERBOSE GNUNET_NO - -#define START_ARM GNUNET_YES - -static struct PeerContext p1; - -struct PeerContext -{ - struct GNUNET_CONFIGURATION_Handle *cfg; -#if START_ARM - struct GNUNET_OS_Process *arm_proc; -#endif -}; - static void * progress_cb (void *cls, const struct GNUNET_FS_ProgressInfo *event) @@ -52,49 +37,12 @@ progress_cb (void *cls, const struct GNUNET_FS_ProgressInfo *event) static void -setup_peer (struct PeerContext *p, const char *cfgname) -{ - p->cfg = GNUNET_CONFIGURATION_create (); -#if START_ARM - p->arm_proc = - GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-arm", - "gnunet-service-arm", -#if VERBOSE - "-L", "DEBUG", -#endif - "-c", cfgname, NULL); -#endif - GNUNET_assert (GNUNET_OK == GNUNET_CONFIGURATION_load (p->cfg, cfgname)); -} - - -static void -stop_arm (struct PeerContext *p) -{ -#if START_ARM - if (NULL != p->arm_proc) - { - if (0 != GNUNET_OS_process_kill (p->arm_proc, SIGTERM)) - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); - if (GNUNET_OS_process_wait (p->arm_proc) != GNUNET_OK) - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "waitpid"); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "ARM process %u stopped\n", - GNUNET_OS_process_get_pid (p->arm_proc)); - GNUNET_OS_process_destroy (p->arm_proc); - p->arm_proc = NULL; - } -#endif - GNUNET_CONFIGURATION_destroy (p->cfg); -} - - -static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) { struct GNUNET_FS_Handle *fs; - setup_peer (&p1, "test_fs_data.conf"); fs = GNUNET_FS_start (cfg, "test-fs-start-stop", &progress_cb, NULL, GNUNET_FS_FLAGS_NONE, GNUNET_FS_OPTIONS_END); GNUNET_assert (NULL != fs); @@ -105,30 +53,10 @@ run (void *cls, char *const *args, const char *cfgfile, int main (int argc, char *argv[]) { - char *const argvx[] = { - "test-fs-start-stop", - "-c", - "test_fs_data.conf", -#if VERBOSE - "-L", "DEBUG", -#endif - NULL - }; - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - - GNUNET_log_setup ("test_fs_start_stop", -#if VERBOSE - "DEBUG", -#else - "WARNING", -#endif - NULL); - GNUNET_PROGRAM_run ((sizeof (argvx) / sizeof (char *)) - 1, argvx, - "test-fs-start-stop", "nohelp", options, &run, NULL); - stop_arm (&p1); - GNUNET_DISK_directory_remove ("/tmp/gnunet-test-fs/"); + if (0 != GNUNET_TESTING_peer_run ("test-fs-start-stop", + "test_fs_data.conf", + &run, NULL)) + return 1; return 0; } diff --git a/src/fs/test_fs_test_lib.c b/src/fs/test_fs_test_lib.c index 29d5fe4..2fe5a81 100644 --- a/src/fs/test_fs_test_lib.c +++ b/src/fs/test_fs_test_lib.c @@ -1,6 +1,6 @@ /* This file is part of GNUnet. - (C) 2010 Christian Grothoff (and other contributing authors) + (C) 2010, 2012 Christian Grothoff (and other contributing authors) GNUnet is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published @@ -42,20 +42,16 @@ #define SEED 42 -static struct GNUNET_FS_TestDaemon *daemons[NUM_DAEMONS]; - -static struct GNUNET_FS_TEST_ConnectContext *cc; +static struct GNUNET_TESTBED_Peer *the_peers[NUM_DAEMONS]; static int ret; + static void do_stop (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { - if (NULL != cc) - { - GNUNET_FS_TEST_daemons_connect_cancel (cc); - cc = NULL; - } + char *fn = cls; + if (0 == (tc->reason & GNUNET_SCHEDULER_REASON_PREREQ_DONE)) { GNUNET_break (0); @@ -66,90 +62,96 @@ do_stop (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Finished download, shutting down\n", (unsigned long long) FILESIZE); } - GNUNET_FS_TEST_daemons_stop (NUM_DAEMONS, daemons); + if (NULL != fn) + { + GNUNET_DISK_directory_remove (fn); + GNUNET_free (fn); + } + GNUNET_SCHEDULER_shutdown (); } static void -do_download (void *cls, const struct GNUNET_FS_Uri *uri) +do_download (void *cls, const struct GNUNET_FS_Uri *uri, + const char *fn) { if (NULL == uri) { GNUNET_break (0); - GNUNET_SCHEDULER_add_now (&do_stop, NULL); + GNUNET_SCHEDULER_shutdown (); ret = 1; return; } GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Downloading %llu bytes\n", (unsigned long long) FILESIZE); - GNUNET_FS_TEST_download (daemons[0], TIMEOUT, 1, SEED, uri, VERBOSE, &do_stop, - NULL); + GNUNET_FS_TEST_download (the_peers[0], TIMEOUT, 1, SEED, uri, VERBOSE, &do_stop, + (NULL == fn) ? NULL : GNUNET_strdup (fn)); } static void -do_publish (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +do_publish (void *cls, + struct GNUNET_TESTBED_Operation *op, + const char *emsg) { - cc = NULL; - if (0 == (tc->reason & GNUNET_SCHEDULER_REASON_PREREQ_DONE)) + GNUNET_TESTBED_operation_done (op); + if (NULL != emsg) { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Failed to connect peers: %s\n", emsg); GNUNET_break (0); ret = 1; - GNUNET_SCHEDULER_add_now (&do_stop, NULL); + GNUNET_SCHEDULER_shutdown (); return; } GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Publishing %llu bytes\n", (unsigned long long) FILESIZE); - GNUNET_FS_TEST_publish (daemons[0], TIMEOUT, 1, GNUNET_NO, FILESIZE, SEED, + GNUNET_FS_TEST_publish (the_peers[0], TIMEOUT, 1, GNUNET_NO, FILESIZE, SEED, VERBOSE, &do_download, NULL); -} - -static void -do_connect (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - if (0 == (tc->reason & GNUNET_SCHEDULER_REASON_PREREQ_DONE)) - { - GNUNET_break (0); - ret = 1; - GNUNET_SCHEDULER_add_now (&do_stop, NULL); - return; - } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Daemons started, will now try to connect them\n"); - cc = GNUNET_FS_TEST_daemons_connect (daemons[0], daemons[1], TIMEOUT, - &do_publish, NULL); } +/** + * Actual main function for the test. + * + * @param cls closure + * @param num_peers number of peers in 'peers' + * @param peers handle to peers run in the testbed + */ static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) +run (void *cls, + unsigned int num_peers, + struct GNUNET_TESTBED_Peer **peers) { - GNUNET_FS_TEST_daemons_start ("fs_test_lib_data.conf", TIMEOUT, NUM_DAEMONS, - daemons, &do_connect, NULL); + unsigned int i; + + GNUNET_assert (NUM_DAEMONS == num_peers); + for (i=0;istatus) { case GNUNET_FS_STATUS_PUBLISH_PROGRESS: -#if VERBOSE - printf ("Publish is progressing (%llu/%llu at level %u off %llu)...\n", - (unsigned long long) event->value.publish.completed, - (unsigned long long) event->value.publish.size, - event->value.publish.specifics.progress.depth, - (unsigned long long) event->value.publish.specifics. - progress.offset); -#endif + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Publish is progressing (%llu/%llu at level %u off %llu)...\n", + (unsigned long long) event->value.publish.completed, + (unsigned long long) event->value.publish.size, + event->value.publish.specifics.progress.depth, + (unsigned long long) event->value.publish.specifics. + progress.offset); break; case GNUNET_FS_STATUS_PUBLISH_COMPLETED: printf ("Publishing complete, %llu kbps.\n", @@ -125,14 +111,13 @@ progress_cb (void *cls, const struct GNUNET_FS_ProgressInfo *event) break; case GNUNET_FS_STATUS_UNINDEX_PROGRESS: GNUNET_assert (unindex == event->value.unindex.uc); -#if VERBOSE - printf ("Unindex is progressing (%llu/%llu at level %u off %llu)...\n", - (unsigned long long) event->value.unindex.completed, - (unsigned long long) event->value.unindex.size, - event->value.unindex.specifics.progress.depth, - (unsigned long long) event->value.unindex.specifics. - progress.offset); -#endif + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Unindex is progressing (%llu/%llu at level %u off %llu)...\n", + (unsigned long long) event->value.unindex.completed, + (unsigned long long) event->value.unindex.size, + event->value.unindex.specifics.progress.depth, + (unsigned long long) event->value.unindex.specifics. + progress.offset); break; case GNUNET_FS_STATUS_PUBLISH_ERROR: FPRINTF (stderr, "Error publishing file: %s\n", @@ -182,45 +167,9 @@ progress_cb (void *cls, const struct GNUNET_FS_ProgressInfo *event) static void -setup_peer (struct PeerContext *p, const char *cfgname) -{ - p->cfg = GNUNET_CONFIGURATION_create (); -#if START_ARM - p->arm_proc = - GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-arm", - "gnunet-service-arm", -#if VERBOSE - "-L", "DEBUG", -#endif - "-c", cfgname, NULL); -#endif - GNUNET_assert (GNUNET_OK == GNUNET_CONFIGURATION_load (p->cfg, cfgname)); -} - - -static void -stop_arm (struct PeerContext *p) -{ -#if START_ARM - if (NULL != p->arm_proc) - { - if (0 != GNUNET_OS_process_kill (p->arm_proc, SIGTERM)) - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); - if (GNUNET_OS_process_wait (p->arm_proc) != GNUNET_OK) - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "waitpid"); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "ARM process %u stopped\n", - GNUNET_OS_process_get_pid (p->arm_proc)); - GNUNET_OS_process_destroy (p->arm_proc); - p->arm_proc = NULL; - } -#endif - GNUNET_CONFIGURATION_destroy (p->cfg); -} - - -static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) { const char *keywords[] = { "down_foo", @@ -233,7 +182,6 @@ run (void *cls, char *const *args, const char *cfgfile, size_t i; struct GNUNET_FS_BlockOptions bo; - setup_peer (&p1, "test_fs_unindex_data.conf"); fn = GNUNET_DISK_mktemp ("gnunet-unindex-test-dst"); fs = GNUNET_FS_start (cfg, "test-fs-unindex", &progress_cb, NULL, GNUNET_FS_FLAGS_NONE, GNUNET_FS_OPTIONS_END); @@ -269,35 +217,10 @@ run (void *cls, char *const *args, const char *cfgfile, int main (int argc, char *argv[]) { - char *const argvx[] = { - "test-fs-unindex", - "-c", - "test_fs_unindex_data.conf", -#if VERBOSE - "-L", "DEBUG", -#endif - NULL - }; - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - - GNUNET_log_setup ("test_fs_unindex", -#if VERBOSE - "DEBUG", -#else - "WARNING", -#endif - NULL); - GNUNET_PROGRAM_run ((sizeof (argvx) / sizeof (char *)) - 1, argvx, - "test-fs-unindex", "nohelp", options, &run, NULL); - stop_arm (&p1); - GNUNET_DISK_directory_remove ("/tmp/gnunet-test-fs-unindex/"); - if (NULL != fn) - { - GNUNET_DISK_directory_remove (fn); - GNUNET_free (fn); - } + if (0 != GNUNET_TESTING_peer_run ("test-fs-unindex", + "test_fs_unindex_data.conf", + &run, NULL)) + return 1; return 0; } diff --git a/src/fs/test_fs_unindex_data.conf b/src/fs/test_fs_unindex_data.conf index 977d6e7..fa28fbb 100644 --- a/src/fs/test_fs_unindex_data.conf +++ b/src/fs/test_fs_unindex_data.conf @@ -1,7 +1,6 @@ @INLINE@ test_fs_defaults.conf [PATHS] SERVICEHOME = /tmp/gnunet-test-fs-unindex/ -DEFAULTCONFIG = test_fs_unindex_data.conf [transport] PLUGINS = diff --git a/src/fs/test_fs_unindex_persistence.c b/src/fs/test_fs_unindex_persistence.c index c6b1062..3e2cd98 100644 --- a/src/fs/test_fs_unindex_persistence.c +++ b/src/fs/test_fs_unindex_persistence.c @@ -25,13 +25,9 @@ */ #include "platform.h" #include "gnunet_util_lib.h" -#include "gnunet_arm_service.h" +#include "gnunet_testing_lib.h" #include "gnunet_fs_service.h" -#define VERBOSE GNUNET_NO - -#define START_ARM GNUNET_YES - /** * File-size we use for testing. */ @@ -47,15 +43,6 @@ */ #define LIFETIME GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MINUTES, 15) -struct PeerContext -{ - struct GNUNET_CONFIGURATION_Handle *cfg; -#if START_ARM - struct GNUNET_OS_Process *arm_proc; -#endif -}; - -static struct PeerContext p1; static struct GNUNET_TIME_Absolute start; @@ -69,6 +56,7 @@ static char *fn; static const struct GNUNET_CONFIGURATION_Handle *cfg; + static void abort_publish_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { @@ -136,14 +124,13 @@ progress_cb (void *cls, const struct GNUNET_FS_ProgressInfo *event) switch (event->status) { case GNUNET_FS_STATUS_PUBLISH_PROGRESS: -#if VERBOSE - printf ("Publish is progressing (%llu/%llu at level %u off %llu)...\n", - (unsigned long long) event->value.publish.completed, - (unsigned long long) event->value.publish.size, - event->value.publish.specifics.progress.depth, - (unsigned long long) event->value.publish.specifics. - progress.offset); -#endif + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Publish is progressing (%llu/%llu at level %u off %llu)...\n", + (unsigned long long) event->value.publish.completed, + (unsigned long long) event->value.publish.size, + event->value.publish.specifics.progress.depth, + (unsigned long long) event->value.publish.specifics. + progress.offset); break; case GNUNET_FS_STATUS_PUBLISH_COMPLETED: printf ("Publishing complete, %llu kbps.\n", @@ -167,14 +154,13 @@ progress_cb (void *cls, const struct GNUNET_FS_ProgressInfo *event) case GNUNET_FS_STATUS_UNINDEX_PROGRESS: consider_restart (event->status); GNUNET_assert (unindex == event->value.unindex.uc); -#if VERBOSE - printf ("Unindex is progressing (%llu/%llu at level %u off %llu)...\n", - (unsigned long long) event->value.unindex.completed, - (unsigned long long) event->value.unindex.size, - event->value.unindex.specifics.progress.depth, - (unsigned long long) event->value.unindex.specifics. - progress.offset); -#endif + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Unindex is progressing (%llu/%llu at level %u off %llu)...\n", + (unsigned long long) event->value.unindex.completed, + (unsigned long long) event->value.unindex.size, + event->value.unindex.specifics.progress.depth, + (unsigned long long) event->value.unindex.specifics. + progress.offset); break; case GNUNET_FS_STATUS_PUBLISH_SUSPEND: if (event->value.publish.pc == publish) @@ -244,45 +230,9 @@ progress_cb (void *cls, const struct GNUNET_FS_ProgressInfo *event) static void -setup_peer (struct PeerContext *p, const char *cfgname) -{ - p->cfg = GNUNET_CONFIGURATION_create (); -#if START_ARM - p->arm_proc = - GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-arm", - "gnunet-service-arm", -#if VERBOSE - "-L", "DEBUG", -#endif - "-c", cfgname, NULL); -#endif - GNUNET_assert (GNUNET_OK == GNUNET_CONFIGURATION_load (p->cfg, cfgname)); -} - - -static void -stop_arm (struct PeerContext *p) -{ -#if START_ARM - if (NULL != p->arm_proc) - { - if (0 != GNUNET_OS_process_kill (p->arm_proc, SIGTERM)) - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); - if (GNUNET_OS_process_wait (p->arm_proc) != GNUNET_OK) - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "waitpid"); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "ARM process %u stopped\n", - GNUNET_OS_process_get_pid (p->arm_proc)); - GNUNET_OS_process_destroy (p->arm_proc); - p->arm_proc = NULL; - } -#endif - GNUNET_CONFIGURATION_destroy (p->cfg); -} - - -static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *c) +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *c, + struct GNUNET_TESTING_Peer *peer) { const char *keywords[] = { "down_foo", @@ -296,7 +246,6 @@ run (void *cls, char *const *args, const char *cfgfile, struct GNUNET_FS_BlockOptions bo; cfg = c; - setup_peer (&p1, "test_fs_unindex_data.conf"); fn = GNUNET_DISK_mktemp ("gnunet-unindex-test-dst"); fs = GNUNET_FS_start (cfg, "test-fs-unindex-persistence", &progress_cb, NULL, GNUNET_FS_FLAGS_PERSISTENCE, GNUNET_FS_OPTIONS_END); @@ -332,35 +281,10 @@ run (void *cls, char *const *args, const char *cfgfile, int main (int argc, char *argv[]) { - char *const argvx[] = { - "test-fs-unindex", - "-c", - "test_fs_unindex_data.conf", -#if VERBOSE - "-L", "DEBUG", -#endif - NULL - }; - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - - GNUNET_log_setup ("test_fs_unindex_persistence", -#if VERBOSE - "DEBUG", -#else - "WARNING", -#endif - NULL); - GNUNET_PROGRAM_run ((sizeof (argvx) / sizeof (char *)) - 1, argvx, - "test-fs-unindex", "nohelp", options, &run, NULL); - stop_arm (&p1); - GNUNET_DISK_directory_remove ("/tmp/gnunet-test-fs-unindex/"); - if (NULL != fn) - { - GNUNET_DISK_directory_remove (fn); - GNUNET_free (fn); - } + if (0 != GNUNET_TESTING_peer_run ("test-fs-unindex-persistence", + "test_fs_unindex_data.conf", + &run, NULL)) + return 1; return 0; } diff --git a/src/fs/test_fs_uri.c b/src/fs/test_fs_uri.c index b7a58ec..9d6c4ab 100644 --- a/src/fs/test_fs_uri.c +++ b/src/fs/test_fs_uri.c @@ -17,19 +17,16 @@ Free Software Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */ - /** * @file fs/test_fs_uri.c * @brief Test for fs_uri.c * @author Christian Grothoff */ - #include "platform.h" #include "gnunet_util_lib.h" #include "gnunet_fs_service.h" #include "fs_api.h" -#define ABORT() { fprintf(stderr, "Error at %s:%d\n", __FILE__, __LINE__); return 1; } static int testKeyword () @@ -41,26 +38,26 @@ testKeyword () if (NULL != (ret = GNUNET_FS_uri_parse ("gnunet://fs/ksk/++", &emsg))) { GNUNET_FS_uri_destroy (ret); - ABORT (); + GNUNET_assert (0); } GNUNET_free (emsg); ret = GNUNET_FS_uri_parse ("gnunet://fs/ksk/foo+bar", &emsg); if (ret == NULL) { GNUNET_free (emsg); - ABORT (); + GNUNET_assert (0); } if (!GNUNET_FS_uri_test_ksk (ret)) { GNUNET_FS_uri_destroy (ret); - ABORT (); + GNUNET_assert (0); } if ((2 != ret->data.ksk.keywordCount) || (0 != strcmp (" foo", ret->data.ksk.keywords[0])) || (0 != strcmp (" bar", ret->data.ksk.keywords[1]))) { GNUNET_FS_uri_destroy (ret); - ABORT (); + GNUNET_assert (0); } uri = GNUNET_FS_uri_to_string (ret); @@ -68,13 +65,14 @@ testKeyword () { GNUNET_free (uri); GNUNET_FS_uri_destroy (ret); - ABORT (); + GNUNET_assert (0); } GNUNET_free (uri); GNUNET_FS_uri_destroy (ret); return 0; } + static int testLocation () { @@ -157,6 +155,7 @@ testLocation () return 0; } + static int testNamespace (int i) { @@ -170,7 +169,7 @@ testNamespace (int i) &emsg))) { GNUNET_FS_uri_destroy (ret); - ABORT (); + GNUNET_assert (0); } GNUNET_free (emsg); if (NULL != @@ -179,13 +178,13 @@ testNamespace (int i) ("gnunet://fs/sks/D1KJS9H2A82Q65VKQ0ML3RFU6U1D3V/test", &emsg))) { GNUNET_FS_uri_destroy (ret); - ABORT (); + GNUNET_assert (0); } GNUNET_free (emsg); if (NULL != (ret = GNUNET_FS_uri_parse ("gnunet://fs/sks/test", &emsg))) { GNUNET_FS_uri_destroy (ret); - ABORT (); + GNUNET_assert (0); } GNUNET_free (emsg); ret = @@ -195,17 +194,17 @@ testNamespace (int i) if (ret == NULL) { GNUNET_free (emsg); - ABORT (); + GNUNET_assert (0); } if (GNUNET_FS_uri_test_ksk (ret)) { GNUNET_FS_uri_destroy (ret); - ABORT (); + GNUNET_assert (0); } if (!GNUNET_FS_uri_test_sks (ret)) { GNUNET_FS_uri_destroy (ret); - ABORT (); + GNUNET_assert (0); } uri = GNUNET_FS_uri_to_string (ret); @@ -215,7 +214,7 @@ testNamespace (int i) { GNUNET_FS_uri_destroy (ret); GNUNET_free (uri); - ABORT (); + GNUNET_assert (0); } GNUNET_free (uri); GNUNET_FS_uri_destroy (ret); @@ -236,7 +235,7 @@ testFile (int i) &emsg))) { GNUNET_FS_uri_destroy (ret); - ABORT (); + GNUNET_assert (0); } GNUNET_free (emsg); if (NULL != @@ -246,7 +245,7 @@ testFile (int i) &emsg))) { GNUNET_FS_uri_destroy (ret); - ABORT (); + GNUNET_assert (0); } GNUNET_free (emsg); if (NULL != @@ -256,7 +255,7 @@ testFile (int i) &emsg))) { GNUNET_FS_uri_destroy (ret); - ABORT (); + GNUNET_assert (0); } GNUNET_free (emsg); ret = @@ -266,22 +265,22 @@ testFile (int i) if (ret == NULL) { GNUNET_free (emsg); - ABORT (); + GNUNET_assert (0); } if (GNUNET_FS_uri_test_ksk (ret)) { GNUNET_FS_uri_destroy (ret); - ABORT (); + GNUNET_assert (0); } if (GNUNET_FS_uri_test_sks (ret)) { GNUNET_FS_uri_destroy (ret); - ABORT (); + GNUNET_assert (0); } if (GNUNET_ntohll (ret->data.chk.file_length) != 42) { GNUNET_FS_uri_destroy (ret); - ABORT (); + GNUNET_assert (0); } uri = GNUNET_FS_uri_to_string (ret); @@ -291,13 +290,14 @@ testFile (int i) { GNUNET_free (uri); GNUNET_FS_uri_destroy (ret); - ABORT (); + GNUNET_assert (0); } GNUNET_free (uri); GNUNET_FS_uri_destroy (ret); return 0; } + int main (int argc, char *argv[]) { @@ -305,11 +305,7 @@ main (int argc, char *argv[]) int i; GNUNET_log_setup ("test_fs_uri", -#if VERBOSE - "DEBUG", -#else "WARNING", -#endif NULL); GNUNET_CRYPTO_random_disable_entropy_gathering (); failureCount += testKeyword (); diff --git a/src/fs/test_gnunet_fs_idx.py.in b/src/fs/test_gnunet_fs_idx.py.in old mode 100644 new mode 100755 index 6bb7d0d..c7858d9 --- a/src/fs/test_gnunet_fs_idx.py.in +++ b/src/fs/test_gnunet_fs_idx.py.in @@ -52,16 +52,17 @@ arm.communicate () try: pub = pexpect () - pub.spawn (None, [publish, '-c', 'test_gnunet_fs_idx_data.conf', '-m', "description:The GNU Public License", '-k', 'gpl', '../../COPYING'], stdout=subprocess.PIPE, stderr=subprocess.STDOUT) - pub.expect ("stdout", re.compile (r"URI is `gnunet://fs/chk/PC0M19QMQC0BPSHR6BGA228PP6INER1D610MGEMOMEM87222FN8HVUO7PQGO0O9HD2GVLHF2N5IDHEQUNK6LKE428FPO96SKQEA486O\.PG7K85JGQ6N599MD5HEP3CHEVFPKQD9JB6NPSLVA3T1SKDS66CFI499VS6MGQ88B0QUAVT1282TCRD4GGFVUKDLGI8F0SPIANA3J2LG\.35147'\.\r?\n")) + + pub.spawn (None, [publish, '-c', 'test_gnunet_fs_idx_data.conf', '-m', "description:Test archive", '-k', 'tst', 'test_gnunet_fs_rec_data.tgz'], stdout=subprocess.PIPE, stderr=subprocess.STDOUT) + pub.expect ("stdout", re.compile (r"URI is `gnunet://fs/chk/2VKHJMR74CB6GB1GFJNOO95BTINA2PEO25FL48GAS7SPBMA0GDEK5U74R1VIHK0LA6919QRS376BHQFDOE3OUP0JOU92K1NIRJMHFCO\.FPEBEAL6HCABM5LMFNNJOPPLKAF5TLUC86A11EIS1HLMIUBP8VEUTU7FT50OLF9ESKP7GTBUE7GDN392J2VKL6JKM1VT1KB4C7Q1U48\.17822'\.\r?\n")) down = pexpect () - down.spawn (None, [download, '-c', 'test_gnunet_fs_idx_data.conf', '-o', 'COPYING', 'gnunet://fs/chk/PC0M19QMQC0BPSHR6BGA228PP6INER1D610MGEMOMEM87222FN8HVUO7PQGO0O9HD2GVLHF2N5IDHEQUNK6LKE428FPO96SKQEA486O.PG7K85JGQ6N599MD5HEP3CHEVFPKQD9JB6NPSLVA3T1SKDS66CFI499VS6MGQ88B0QUAVT1282TCRD4GGFVUKDLGI8F0SPIANA3J2LG.35147'], stdout=subprocess.PIPE, stderr=subprocess.STDOUT) - down.expect ("stdout", re.compile (r"Downloading `COPYING' done (.*).\r?\n")) - os.remove ("COPYING") + down.spawn (None, [download, '-c', 'test_gnunet_fs_idx_data.conf', '-o', 'test_gnunet_fs_rec_data.tar.gz', 'gnunet://fs/chk/2VKHJMR74CB6GB1GFJNOO95BTINA2PEO25FL48GAS7SPBMA0GDEK5U74R1VIHK0LA6919QRS376BHQFDOE3OUP0JOU92K1NIRJMHFCO.FPEBEAL6HCABM5LMFNNJOPPLKAF5TLUC86A11EIS1HLMIUBP8VEUTU7FT50OLF9ESKP7GTBUE7GDN392J2VKL6JKM1VT1KB4C7Q1U48.17822'], stdout=subprocess.PIPE, stderr=subprocess.STDOUT) + down.expect ("stdout", re.compile (r"Downloading `test_gnunet_fs_rec_data.tar.gz' done (.*).\r?\n")) + os.remove ("test_gnunet_fs_rec_data.tar.gz") un = pexpect () - un.spawn (None, [unindex, '-c', 'test_gnunet_fs_idx_data.conf', '../../COPYING'], stdout=subprocess.PIPE, stderr=subprocess.STDOUT) + un.spawn (None, [unindex, '-c', 'test_gnunet_fs_idx_data.conf', 'test_gnunet_fs_rec_data.tgz'], stdout=subprocess.PIPE, stderr=subprocess.STDOUT) un.expect ("stdout", re.compile (r'Unindexing done\.\r?\n')) finally: diff --git a/src/fs/test_gnunet_fs_idx_data.conf b/src/fs/test_gnunet_fs_idx_data.conf index f852011..4394805 100644 --- a/src/fs/test_gnunet_fs_idx_data.conf +++ b/src/fs/test_gnunet_fs_idx_data.conf @@ -1,7 +1,6 @@ @INLINE@ test_fs_defaults.conf [PATHS] SERVICEHOME = /tmp/gnunet-test-fs-py-idx/ -DEFAULTCONFIG = test_gnunet_fs_idx_data.conf [transport] PLUGINS = diff --git a/src/fs/test_gnunet_fs_ns.py.in b/src/fs/test_gnunet_fs_ns.py.in old mode 100644 new mode 100755 diff --git a/src/fs/test_gnunet_fs_ns_data.conf b/src/fs/test_gnunet_fs_ns_data.conf index 5f297ab..57e3432 100644 --- a/src/fs/test_gnunet_fs_ns_data.conf +++ b/src/fs/test_gnunet_fs_ns_data.conf @@ -1,7 +1,6 @@ @INLINE@ test_fs_defaults.conf [PATHS] SERVICEHOME = /tmp/gnunet-test-fs-py-ns/ -DEFAULTCONFIG = test_gnunet_fs_ns_data.conf [transport] PLUGINS = diff --git a/src/fs/test_gnunet_fs_psd.py.in b/src/fs/test_gnunet_fs_psd.py.in old mode 100644 new mode 100755 index 9790e13..f12c6b7 --- a/src/fs/test_gnunet_fs_psd.py.in +++ b/src/fs/test_gnunet_fs_psd.py.in @@ -55,20 +55,20 @@ arm.communicate () # first, basic publish-search-download run try: pub = pexpect () - pub.spawn (None, [publish, '-c', 'test_gnunet_fs_psd_data.conf', '-n', '-m', "description:The GNU Public License", '-k', 'gpl', '../../COPYING'], stdout=subprocess.PIPE, stderr=subprocess.STDOUT) - pub.expect ("stdout", re.compile (r"Publishing `.+[\\/]..[\\/]..[\\/]COPYING' done\.\r?\n")) - pub.expect ("stdout", re.compile (r"URI is `gnunet://fs/chk/PC0M19QMQC0BPSHR6BGA228PP6INER1D610MGEMOMEM87222FN8HVUO7PQGO0O9HD2GVLHF2N5IDHEQUNK6LKE428FPO96SKQEA486O\.PG7K85JGQ6N599MD5HEP3CHEVFPKQD9JB6NPSLVA3T1SKDS66CFI499VS6MGQ88B0QUAVT1282TCRD4GGFVUKDLGI8F0SPIANA3J2LG\.35147'\.\r?\n")) + pub.spawn (None, [publish, '-c', 'test_gnunet_fs_psd_data.conf', '-n', '-m', "description:Test archive", '-k', 'tst', 'test_gnunet_fs_rec_data.tgz'], stdout=subprocess.PIPE, stderr=subprocess.STDOUT) + pub.expect ("stdout", re.compile (r"Publishing `.+test_gnunet_fs_rec_data.tgz' done\.\r?\n")) + pub.expect ("stdout", re.compile (r"URI is `gnunet://fs/chk/2VKHJMR74CB6GB1GFJNOO95BTINA2PEO25FL48GAS7SPBMA0GDEK5U74R1VIHK0LA6919QRS376BHQFDOE3OUP0JOU92K1NIRJMHFCO\.FPEBEAL6HCABM5LMFNNJOPPLKAF5TLUC86A11EIS1HLMIUBP8VEUTU7FT50OLF9ESKP7GTBUE7GDN392J2VKL6JKM1VT1KB4C7Q1U48\.17822'\.\r?\n")) s = pexpect () - s.spawn (None, [search, '-V', '-t', '1000', '-N', '1', '-c', 'test_gnunet_fs_psd_data.conf', 'gpl'], stdout=subprocess.PIPE, stderr=subprocess.STDOUT) + s.spawn (None, [search, '-V', '-t', '1000', '-N', '1', '-c', 'test_gnunet_fs_psd_data.conf', 'tst'], stdout=subprocess.PIPE, stderr=subprocess.STDOUT) s.expect ("stdout", re.compile (r'#0:\r?\n')) - s.expect ("stdout", re.compile (r'gnunet-download -o "COPYING" gnunet://fs/chk/PC0M19QMQC0BPSHR6BGA228PP6INER1D610MGEMOMEM87222FN8HVUO7PQGO0O9HD2GVLHF2N5IDHEQUNK6LKE428FPO96SKQEA486O\.PG7K85JGQ6N599MD5HEP3CHEVFPKQD9JB6NPSLVA3T1SKDS66CFI499VS6MGQ88B0QUAVT1282TCRD4GGFVUKDLGI8F0SPIANA3J2LG\.35147\r?\n')) - s.expect ("stdout", re.compile (r"\s*description: The GNU Public License\r?\n")) + s.expect ("stdout", re.compile (r'gnunet-download -o "test_gnunet_fs_rec_data.tgz" gnunet://fs/chk/2VKHJMR74CB6GB1GFJNOO95BTINA2PEO25FL48GAS7SPBMA0GDEK5U74R1VIHK0LA6919QRS376BHQFDOE3OUP0JOU92K1NIRJMHFCO\.FPEBEAL6HCABM5LMFNNJOPPLKAF5TLUC86A11EIS1HLMIUBP8VEUTU7FT50OLF9ESKP7GTBUE7GDN392J2VKL6JKM1VT1KB4C7Q1U48\.17822\r?\n')) + s.expect ("stdout", re.compile (r"\s*description: Test archive\r?\n")) down = pexpect () - down.spawn (None, [download, '-c', 'test_gnunet_fs_psd_data.conf', '-o', 'COPYING', 'gnunet://fs/chk/PC0M19QMQC0BPSHR6BGA228PP6INER1D610MGEMOMEM87222FN8HVUO7PQGO0O9HD2GVLHF2N5IDHEQUNK6LKE428FPO96SKQEA486O.PG7K85JGQ6N599MD5HEP3CHEVFPKQD9JB6NPSLVA3T1SKDS66CFI499VS6MGQ88B0QUAVT1282TCRD4GGFVUKDLGI8F0SPIANA3J2LG.35147'], stdout=subprocess.PIPE, stderr=subprocess.STDOUT) - down.expect ("stdout", re.compile (r"Downloading `COPYING' done (.*).\r?\n")) - os.remove ("COPYING") + down.spawn (None, [download, '-c', 'test_gnunet_fs_psd_data.conf', '-o', 'test_gnunet_fs_rec_data.tar.gz', 'gnunet://fs/chk/2VKHJMR74CB6GB1GFJNOO95BTINA2PEO25FL48GAS7SPBMA0GDEK5U74R1VIHK0LA6919QRS376BHQFDOE3OUP0JOU92K1NIRJMHFCO.FPEBEAL6HCABM5LMFNNJOPPLKAF5TLUC86A11EIS1HLMIUBP8VEUTU7FT50OLF9ESKP7GTBUE7GDN392J2VKL6JKM1VT1KB4C7Q1U48.17822'], stdout=subprocess.PIPE, stderr=subprocess.STDOUT) + down.expect ("stdout", re.compile (r"Downloading `test_gnunet_fs_rec_data.tar.gz' done (.*).\r?\n")) + os.remove ("test_gnunet_fs_rec_data.tar.gz") finally: arm = subprocess.Popen ([gnunetarm, '-eq', '-c', 'test_gnunet_fs_psd_data.conf']) diff --git a/src/fs/test_gnunet_fs_psd_data.conf b/src/fs/test_gnunet_fs_psd_data.conf index b68c6b5..e41f6bf 100644 --- a/src/fs/test_gnunet_fs_psd_data.conf +++ b/src/fs/test_gnunet_fs_psd_data.conf @@ -1,7 +1,6 @@ @INLINE@ test_fs_defaults.conf [PATHS] SERVICEHOME = /tmp/gnunet-test-fs-py-psd/ -DEFAULTCONFIG = test_gnunet_fs_psd_data.conf [transport] PLUGINS = diff --git a/src/fs/test_gnunet_fs_rec.py.in b/src/fs/test_gnunet_fs_rec.py.in old mode 100644 new mode 100755 index e86bb0a..4f955b4 --- a/src/fs/test_gnunet_fs_rec.py.in +++ b/src/fs/test_gnunet_fs_rec.py.in @@ -23,6 +23,8 @@ import os import subprocess import re import shutil +import tarfile +import filecmp srcdir = "../.." gnunet_pyexpect_dir = os.path.join (srcdir, "contrib") @@ -30,6 +32,7 @@ if gnunet_pyexpect_dir not in sys.path: sys.path.append (gnunet_pyexpect_dir) from gnunet_pyexpect import pexpect +from pydiffer import dcdiff if os.name == 'posix': download = 'gnunet-download' @@ -55,7 +58,8 @@ arm = subprocess.Popen ([gnunetarm, '-sq', '-c', 'test_gnunet_fs_rec_data.conf'] arm.communicate () # pray that `tar' is in PATH -os.system ('tar xfz test_gnunet_fs_rec_data.tgz') +tar = tarfile.open ('test_gnunet_fs_rec_data.tgz') +tar.extractall () # first, basic publish-search-download run try: pub = pexpect () @@ -93,8 +97,9 @@ try: os.remove ("rdir/b.gnd") os.remove ("rdir/a.gnd") - if 0 != os.system ("diff -r dir rdir"): - raise Exception ("Unexpected difference between source directory and downloaded result") + diff = dcdiff ('dir', 'rdir') + if len (diff) != 0: + raise Exception ("Unexpected difference between source directory and downloaded result:\n{}".format (diff)) finally: diff --git a/src/fs/test_gnunet_fs_rec_data.conf b/src/fs/test_gnunet_fs_rec_data.conf index dae8b19..fcdcda9 100644 --- a/src/fs/test_gnunet_fs_rec_data.conf +++ b/src/fs/test_gnunet_fs_rec_data.conf @@ -1,7 +1,6 @@ @INLINE@ test_fs_defaults.conf [PATHS] SERVICEHOME = /tmp/gnunet-test-fs-py-rec/ -DEFAULTCONFIG = test_gnunet_fs_rec_data.conf [transport] PLUGINS = diff --git a/src/fs/test_gnunet_service_fs_migration.c b/src/fs/test_gnunet_service_fs_migration.c index 00aab4f..2bc5354 100644 --- a/src/fs/test_gnunet_service_fs_migration.c +++ b/src/fs/test_gnunet_service_fs_migration.c @@ -1,6 +1,6 @@ /* This file is part of GNUnet. - (C) 2010 Christian Grothoff (and other contributing authors) + (C) 2010, 2012 Christian Grothoff (and other contributing authors) GNUnet is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published @@ -25,7 +25,7 @@ */ #include "platform.h" #include "fs_test_lib.h" -#include "gnunet_testing_lib.h" +#include "gnunet_testbed_service.h" #define VERBOSE GNUNET_NO @@ -46,13 +46,22 @@ #define SEED 42 -static struct GNUNET_FS_TestDaemon *daemons[2]; +static struct GNUNET_TESTBED_Peer *daemons[2]; static int ok; static struct GNUNET_TIME_Absolute start_time; -static struct GNUNET_FS_TEST_ConnectContext *cc; +static struct GNUNET_TESTBED_Operation *op; + + +struct DownloadContext +{ + char *fn; + + struct GNUNET_FS_Uri *uri; +}; + static void do_stop (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) @@ -60,12 +69,7 @@ do_stop (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) struct GNUNET_TIME_Relative del; char *fancy; - if (NULL != cc) - { - GNUNET_FS_TEST_daemons_connect_cancel (cc); - cc = NULL; - } - GNUNET_FS_TEST_daemons_stop (2, daemons); + GNUNET_SCHEDULER_shutdown (); if (0 == (tc->reason & GNUNET_SCHEDULER_REASON_TIMEOUT)) { del = GNUNET_TIME_absolute_get_duration (start_time); @@ -89,13 +93,23 @@ do_stop (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) static void -do_download (void *cls, const char *emsg) +do_download (void *cls, + const char *emsg) { - struct GNUNET_FS_Uri *uri = cls; + struct DownloadContext *dc = cls; + struct GNUNET_FS_Uri *uri = dc->uri; - if (emsg != NULL) + GNUNET_TESTBED_operation_done (op); + op = NULL; + if (NULL != dc->fn) + { + GNUNET_DISK_directory_remove (dc->fn); + GNUNET_free (dc->fn); + } + GNUNET_free (dc); + if (NULL != emsg) { - GNUNET_FS_TEST_daemons_stop (2, daemons); + GNUNET_SCHEDULER_shutdown (); GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Failed to stop source daemon: %s\n", emsg); GNUNET_FS_uri_destroy (uri); @@ -114,46 +128,47 @@ do_download (void *cls, const char *emsg) static void stop_source_peer (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { - struct GNUNET_FS_Uri *uri = cls; - struct GNUNET_TESTING_PeerGroup *pg; + struct DownloadContext *dc = cls; GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stopping source peer\n"); - pg = GNUNET_FS_TEST_get_group (daemons); - GNUNET_TESTING_daemons_vary (pg, 1, GNUNET_NO, TIMEOUT, &do_download, uri); + op = GNUNET_TESTBED_peer_stop (daemons[1], &do_download, dc); + GNUNET_assert (NULL != op); } static void -do_wait (void *cls, const struct GNUNET_FS_Uri *uri) +do_wait (void *cls, const struct GNUNET_FS_Uri *uri, + const char *fn) { - struct GNUNET_FS_Uri *d; + struct DownloadContext *dc; if (NULL == uri) { - GNUNET_FS_TEST_daemons_stop (2, daemons); + GNUNET_SCHEDULER_shutdown (); GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Timeout during upload attempt, shutting down with error\n"); ok = 1; return; } GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Waiting to allow content to migrate\n"); - d = GNUNET_FS_uri_dup (uri); - (void) GNUNET_SCHEDULER_add_delayed (MIGRATION_DELAY, &stop_source_peer, d); + dc = GNUNET_malloc (sizeof (struct DownloadContext)); + dc->uri = GNUNET_FS_uri_dup (uri); + if (NULL != fn) + dc->fn = GNUNET_strdup (fn); + (void) GNUNET_SCHEDULER_add_delayed (MIGRATION_DELAY, &stop_source_peer, dc); } static void -do_publish (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +do_publish (void *cls, + unsigned int num_peers, + struct GNUNET_TESTBED_Peer **peers) { - cc = NULL; - if (0 != (tc->reason & GNUNET_SCHEDULER_REASON_TIMEOUT)) - { - GNUNET_FS_TEST_daemons_stop (2, daemons); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Timeout during connect attempt, shutting down with error\n"); - ok = 1; - return; - } + unsigned int i; + + GNUNET_assert (2 == num_peers); + for (i=0;ireason & GNUNET_SCHEDULER_REASON_PREREQ_DONE)) - { - FPRINTF (stderr, "%s", "Daemons failed to start!\n"); - GNUNET_break (0); - ok = 1; - return; - } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Daemons started, will now try to connect them\n"); - cc = GNUNET_FS_TEST_daemons_connect (daemons[0], daemons[1], TIMEOUT, - &do_publish, NULL); -} - - -static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) -{ - GNUNET_FS_TEST_daemons_start ("test_gnunet_service_fs_migration_data.conf", - TIMEOUT, 2, daemons, &do_connect, NULL); -} - - int main (int argc, char *argv[]) { - char *const argvx[] = { - "test-gnunet-service-fs-migration", - "-c", - "fs_test_lib_data.conf", -#if VERBOSE - "-L", "DEBUG", -#endif - NULL - }; - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - - GNUNET_DISK_directory_remove ("/tmp/test-gnunet-service-fs-migration/"); - GNUNET_log_setup ("test_gnunet_service_fs_migration", -#if VERBOSE - "DEBUG", -#else - "WARNING", -#endif - NULL); - GNUNET_PROGRAM_run ((sizeof (argvx) / sizeof (char *)) - 1, argvx, - "test-gnunet-service-fs-migration", "nohelp", options, - &run, NULL); + (void) GNUNET_TESTBED_test_run ("test-gnunet-service-fs-migration", + "fs_test_lib_data.conf", + 2, + 0, NULL, NULL, + &do_publish, + NULL); GNUNET_DISK_directory_remove ("/tmp/test-gnunet-service-fs-migration/"); return ok; } diff --git a/src/fs/test_gnunet_service_fs_migration_data.conf b/src/fs/test_gnunet_service_fs_migration_data.conf index 9c05a88..3d740e4 100644 --- a/src/fs/test_gnunet_service_fs_migration_data.conf +++ b/src/fs/test_gnunet_service_fs_migration_data.conf @@ -1,8 +1,9 @@ @INLINE@ test_fs_defaults.conf [PATHS] SERVICEHOME = /tmp/test-gnunet-service-fs-migration/ -DEFAULTCONFIG = test_gnunet_service_fs_migration_data.conf +[testbed] +OVERLAY_TOPOLOGY = CLIQUE [ats] WAN_QUOTA_IN = 3932160 diff --git a/src/fs/test_gnunet_service_fs_p2p.c b/src/fs/test_gnunet_service_fs_p2p.c index 7ca786e..d293bd6 100644 --- a/src/fs/test_gnunet_service_fs_p2p.c +++ b/src/fs/test_gnunet_service_fs_p2p.c @@ -1,6 +1,6 @@ /* This file is part of GNUnet. - (C) 2010 Christian Grothoff (and other contributing authors) + (C) 2010, 2012 Christian Grothoff (and other contributing authors) GNUnet is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published @@ -42,26 +42,25 @@ #define SEED 42 -static struct GNUNET_FS_TestDaemon *daemons[NUM_DAEMONS]; +static const char *progname; + +static unsigned int anonymity_level; + +static struct GNUNET_TESTBED_Peer *daemons[NUM_DAEMONS]; static int ok; static struct GNUNET_TIME_Absolute start_time; -static struct GNUNET_FS_TEST_ConnectContext *cc; static void do_stop (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { + char *fn = cls; struct GNUNET_TIME_Relative del; char *fancy; - if (NULL != cc) - { - GNUNET_FS_TEST_daemons_connect_cancel (cc); - cc = NULL; - } - GNUNET_FS_TEST_daemons_stop (NUM_DAEMONS, daemons); + GNUNET_SCHEDULER_shutdown (); if (0 == (tc->reason & GNUNET_SCHEDULER_REASON_TIMEOUT)) { del = GNUNET_TIME_absolute_get_duration (start_time); @@ -81,15 +80,21 @@ do_stop (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) "Timeout during download, shutting down with error\n"); ok = 1; } + if (NULL != fn) + { + GNUNET_DISK_directory_remove (fn); + GNUNET_free (fn); + } } static void -do_download (void *cls, const struct GNUNET_FS_Uri *uri) +do_download (void *cls, const struct GNUNET_FS_Uri *uri, + const char *fn) { if (NULL == uri) { - GNUNET_FS_TEST_daemons_stop (NUM_DAEMONS, daemons); + GNUNET_SCHEDULER_shutdown (); GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Timeout during upload attempt, shutting down with error\n"); ok = 1; @@ -98,77 +103,53 @@ do_download (void *cls, const struct GNUNET_FS_Uri *uri) GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Downloading %llu bytes\n", (unsigned long long) FILESIZE); start_time = GNUNET_TIME_absolute_get (); - GNUNET_FS_TEST_download (daemons[0], TIMEOUT, 1, SEED, uri, VERBOSE, &do_stop, - NULL); + GNUNET_FS_TEST_download (daemons[0], TIMEOUT, + anonymity_level, SEED, uri, + VERBOSE, &do_stop, + (NULL == fn) + ? NULL + : GNUNET_strdup (fn)); } static void -do_publish (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +do_publish (void *cls, + unsigned int num_peers, + struct GNUNET_TESTBED_Peer **peers) { - cc = NULL; - if (0 == (tc->reason & GNUNET_SCHEDULER_REASON_PREREQ_DONE)) - { - GNUNET_FS_TEST_daemons_stop (NUM_DAEMONS, daemons); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Timeout during connect attempt, shutting down with error\n"); - ok = 1; - return; - } + unsigned int i; + + if (NULL != strstr (progname, "stream")) + anonymity_level = 0; + else + anonymity_level = 1; + GNUNET_assert (NUM_DAEMONS == num_peers); + for (i=0;ireason & GNUNET_SCHEDULER_REASON_PREREQ_DONE)); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Daemons started, will now try to connect them\n"); - cc = GNUNET_FS_TEST_daemons_connect (daemons[0], daemons[1], TIMEOUT, - &do_publish, NULL); -} - - -static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) -{ - GNUNET_FS_TEST_daemons_start ("fs_test_lib_data.conf", TIMEOUT, NUM_DAEMONS, - daemons, &do_connect, NULL); -} - - int main (int argc, char *argv[]) { - char *const argvx[] = { - "test-gnunet-service-fs-p2p", - "-c", - "fs_test_lib_data.conf", -#if VERBOSE - "-L", "DEBUG", -#endif - NULL - }; - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; + const char *config; - GNUNET_DISK_directory_remove ("/tmp/gnunet-test-fs-lib/"); - GNUNET_log_setup ("test_gnunet_service_fs_p2p", -#if VERBOSE - "DEBUG", -#else - "WARNING", -#endif - NULL); - GNUNET_PROGRAM_run ((sizeof (argvx) / sizeof (char *)) - 1, argvx, - "test-gnunet-service-fs-p2p", "nohelp", options, &run, - NULL); + progname = argv[0]; + if (NULL != strstr (progname, "stream")) + config = "test_gnunet_service_fs_p2p_stream.conf"; + else + config = "fs_test_lib_data.conf"; + (void) GNUNET_TESTBED_test_run ("test-gnunet-service-fs-p2p", + config, + NUM_DAEMONS, + 0, NULL, NULL, + &do_publish, NULL); GNUNET_DISK_directory_remove ("/tmp/gnunet-test-fs-lib/"); return ok; } diff --git a/src/fs/test_gnunet_service_fs_p2p_stream.conf b/src/fs/test_gnunet_service_fs_p2p_stream.conf new file mode 100644 index 0000000..9d01208 --- /dev/null +++ b/src/fs/test_gnunet_service_fs_p2p_stream.conf @@ -0,0 +1,16 @@ +@INLINE@ fs_test_lib_data.conf + +[fs] +# FIXME: this option needs to be set for the +# testcase to truly work; however, as the code +# is not finished, not setting the option should +# allow the test to at least pass for now... +DISABLE_ANON_TRANSFER = YES + +# Do we cache content from other nodes? (may improve anonymity) +CONTENT_CACHING = NO + +# Do we send unsolicited data to other nodes if we have excess bandwidth? +# (may improve anonymity, probably not a good idea if content_caching is NO) +CONTENT_PUSHING = NO + diff --git a/src/fs/test_plugin_block_fs.c b/src/fs/test_plugin_block_fs.c new file mode 100644 index 0000000..a9f5ce3 --- /dev/null +++ b/src/fs/test_plugin_block_fs.c @@ -0,0 +1,77 @@ +/* + This file is part of GNUnet + (C) 2010, 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ +/** + * @file fs/test_plugin_block_fs.c + * @brief test for plugin_block_fs.c + * @author Christian Grothoff + */ +#include "platform.h" +#include "gnunet_block_lib.h" + + +static int +test_fs (struct GNUNET_BLOCK_Context *ctx) +{ + struct GNUNET_HashCode key; + char block[4]; + + memset (block, 1, sizeof (block)); + if (GNUNET_OK != + GNUNET_BLOCK_get_key (ctx, GNUNET_BLOCK_TYPE_FS_DBLOCK, block, + sizeof (block), &key)) + return 1; + if (GNUNET_BLOCK_EVALUATION_OK_LAST != + GNUNET_BLOCK_evaluate (ctx, GNUNET_BLOCK_TYPE_FS_DBLOCK, &key, NULL, 0, + NULL, 0, block, sizeof (block))) + return 2; + if (GNUNET_BLOCK_EVALUATION_REQUEST_VALID != + GNUNET_BLOCK_evaluate (ctx, GNUNET_BLOCK_TYPE_FS_DBLOCK, &key, NULL, 0, + NULL, 0, NULL, 0)) + return 4; + GNUNET_log_skip (1, GNUNET_NO); + if (GNUNET_BLOCK_EVALUATION_REQUEST_INVALID != + GNUNET_BLOCK_evaluate (ctx, GNUNET_BLOCK_TYPE_FS_DBLOCK, &key, NULL, 0, + "bogus", 5, NULL, 0)) + return 8; + GNUNET_log_skip (0, GNUNET_YES); + return 0; +} + + +int +main (int argc, char *argv[]) +{ + int ret; + struct GNUNET_BLOCK_Context *ctx; + struct GNUNET_CONFIGURATION_Handle *cfg; + + GNUNET_log_setup ("test-block", "WARNING", NULL); + cfg = GNUNET_CONFIGURATION_create (); + GNUNET_CONFIGURATION_set_value_string (cfg, "block", "PLUGINS", "fs"); + ctx = GNUNET_BLOCK_context_create (cfg); + ret = test_fs (ctx); + GNUNET_BLOCK_context_destroy (ctx); + GNUNET_CONFIGURATION_destroy (cfg); + if (ret != 0) + FPRINTF (stderr, "Tests failed: %d\n", ret); + return ret; +} + +/* end of test_plugin_block_fs.c */ diff --git a/src/gns/Makefile.am b/src/gns/Makefile.am index 10b9ff3..d4fcb6b 100644 --- a/src/gns/Makefile.am +++ b/src/gns/Makefile.am @@ -6,37 +6,202 @@ endif SUBDIRS = . $(NSS_SUBDIR) +EXTRA_DIST = \ + test_gns_defaults.conf \ + test_gns_simple_lookup.conf \ + test_gns_dht_default.conf \ + gns-helper-service-w32.conf \ + gnunet-gns-proxy-setup-ca \ + zonefiles/188JSUMKEF25GVU8TTV0PBNNN8JVCPUEDFV1UHJJU884JD25V0T0.zkey \ + zonefiles/OEFL7A4VEF1B40QLEMTG5D8G1CN6EN16QUSG5R2DT71GRJN34LSG.zkey \ + zonefiles/test_zonekey + if MINGW WINFLAGS = -Wl,--no-undefined -Wl,--export-all-symbols + DO_W32_HELPER = gnunet-gns-helper-service-w32 + DO_W32_NSP = libw32nsp.la + DO_W32_NSPTOOLS = w32nsp-install w32nsp-uninstall w32nsp-resolve + DO_W32_HS_CONF = gns-helper-service-w32.conf +else + USE_VPN = $(top_builddir)/src/vpn/libgnunetvpn.la endif if USE_COVERAGE AM_CFLAGS = --coverage -O0 endif -pkgcfgdir= $(pkgdatadir)/config.d/ +pkgcfgdir = $(pkgdatadir)/config.d/ + +libexecdir= $(pkglibdir)/libexec/ plugindir = $(libdir)/gnunet pkgcfg_DATA = \ - gns.conf + gns.conf \ + $(DO_W32_HS_CONF) lib_LTLIBRARIES = \ - libgnunetgns.la + $(DO_W32_NSP) \ + libgnunetgns.la \ + libgnunetgns_common.la + if HAVE_MHD DO_FCFSD=gnunet-gns-fcfsd +if HAVE_GNUTLS DO_PROXY=gnunet-gns-proxy endif +endif + +libexec_PROGRAMS = \ + gnunet-service-gns $(DO_FCFSD) \ + $(DO_PROXY) \ + $(DO_W32_HELPER) \ + gnunet-dns2gns bin_PROGRAMS = \ - gnunet-service-gns \ - $(DO_FCFSD) \ - $(DO_PROXY) \ - gnunet-gns + $(DO_W32_NSPTOOLS) \ + gnunet-gns + +bin_SCRIPTS = gnunet-gns-proxy-setup-ca + +plugin_LTLIBRARIES = \ + libgnunet_plugin_block_gns.la + +gnunet_gns_SOURCES = \ + gnunet-gns.c +gnunet_gns_LDADD = \ + $(top_builddir)/src/gns/libgnunetgns.la \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/namestore/libgnunetnamestore.la \ + $(GN_LIBINTL) +gnunet_gns_DEPENDENCIES = \ + libgnunetgns.la + +gnunet_dns2gns_SOURCES = \ + gnunet-dns2gns.c +gnunet_dns2gns_LDADD = \ + $(top_builddir)/src/gns/libgnunetgns.la \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/namestore/libgnunetnamestore.la \ + $(top_builddir)/src/dns/libgnunetdnsparser.la \ + $(top_builddir)/src/dns/libgnunetdnsstub.la \ + $(GN_LIBINTL) +gnunet_dns2gns_DEPENDENCIES = \ + libgnunetgns.la + +gnunet_gns_proxy_SOURCES = \ + gnunet-gns-proxy.c gns_proxy_proto.h +gnunet_gns_proxy_LDADD = -lmicrohttpd -lcurl -lgnutls \ + $(top_builddir)/src/gns/libgnunetgns.la \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(GN_LIBINTL) +gnunet_gns_proxy_DEPENDENCIES = \ + libgnunetgns.la + +gnunet_gns_helper_service_w32_SOURCES = \ + gnunet-gns-helper-service-w32.c +gnunet_gns_helper_service_w32_LDADD = \ + $(top_builddir)/src/gns/libgnunetgns.la \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(GN_LIBINTL) +gnunet_gns_helper_service_w32_DEPENDENCIES = \ + libgnunetgns.la + +w32nsp_install_SOURCES = \ + w32nsp-install.c +w32nsp_install_LDADD = -lws2_32 + +w32nsp_uninstall_SOURCES = \ + w32nsp-uninstall.c +w32nsp_uninstall_LDADD = -lws2_32 + +w32nsp_resolve_SOURCES = \ + w32nsp-resolve.c +w32nsp_resolve_LDADD = -lws2_32 + +gnunet_service_gns_SOURCES = \ + gnunet-service-gns.c \ + gnunet-service-gns_resolver.c gnunet-service-gns_resolver.h \ + gnunet-service-gns_interceptor.c gnunet-service-gns_interceptor.h +gnunet_service_gns_LDADD = \ + -lm \ + $(top_builddir)/src/statistics/libgnunetstatistics.la \ + $(top_builddir)/src/util/libgnunetutil.la \ + libgnunetgns_common.la \ + $(top_builddir)/src/dns/libgnunetdns.la \ + $(top_builddir)/src/dns/libgnunetdnsparser.la \ + $(top_builddir)/src/dht/libgnunetdht.la \ + $(top_builddir)/src/namestore/libgnunetnamestore.la \ + $(USE_VPN) \ + $(GN_LIBINTL) +gnunet_service_gns_DEPENDENCIES = \ + $(top_builddir)/src/statistics/libgnunetstatistics.la \ + $(top_builddir)/src/util/libgnunetutil.la \ + libgnunetgns_common.la \ + $(top_builddir)/src/dns/libgnunetdns.la \ + $(top_builddir)/src/dns/libgnunetdnsparser.la \ + $(top_builddir)/src/dht/libgnunetdht.la \ + $(top_builddir)/src/namestore/libgnunetnamestore.la \ + $(USE_VPN) + + + +gnunet_gns_fcfsd_SOURCES = \ + gnunet-gns-fcfsd.c +gnunet_gns_fcfsd_LDADD = -lmicrohttpd \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/namestore/libgnunetnamestore.la \ + $(GN_LIBINTL) +gnunet_gns_fcfsd_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/namestore/libgnunetnamestore.la + +libw32nsp_la_SOURCES = \ + w32nsp.c +libw32nsp_la_LIBADD = \ + -lole32 -lws2_32 +libw32nsp_la_LDFLAGS = \ + -export-symbols $(top_srcdir)/src/gns/w32nsp.def \ + $(GN_LIB_LDFLAGS) + +libgnunetgns_la_SOURCES = \ + gns_api.c gns.h +libgnunetgns_la_LIBADD = \ + $(top_builddir)/src/util/libgnunetutil.la $(XLIB) \ + $(top_builddir)/src/namestore/libgnunetnamestore.la +libgnunetgns_la_LDFLAGS = \ + $(GN_LIB_LDFLAGS) +libgnunetgns_la_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/namestore/libgnunetnamestore.la + + +libgnunetgns_common_la_SOURCES = \ + gns_common.c gns_common.h +libgnunetgns_common_la_LDFLAGS = \ + $(GN_LIB_LDFLAGS) +libgnunetgns_common_la_LIBADD = \ + $(top_builddir)/src/util/libgnunetutil.la +libgnunetgns_common_la_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la + + +libgnunet_plugin_block_gns_la_SOURCES = \ + plugin_block_gns.c +libgnunet_plugin_block_gns_la_LIBADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/block/libgnunetblock.la \ + $(top_builddir)/src/gns/libgnunetgns_common.la \ + $(top_builddir)/src/namestore/libgnunetnamestore.la +libgnunet_plugin_block_gns_la_LDFLAGS = \ + $(GN_PLUGIN_LDFLAGS) +libgnunet_plugin_block_gns_la_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la \ + libgnunetgns_common.la \ + $(top_builddir)/src/block/libgnunetblock.la \ + $(top_builddir)/src/namestore/libgnunetnamestore.la -#noinst_PROGRAMS = \ -# gnunet-gns-lookup check_PROGRAMS = \ test_gns_simple_shorten \ @@ -44,11 +209,22 @@ check_PROGRAMS = \ test_gns_simple_lookup \ test_gns_simple_delegated_lookup \ test_gns_simple_mx_lookup \ + test_gns_simple_srv_lookup \ test_gns_simple_zkey_lookup \ test_gns_dht_delegated_lookup \ test_gns_pseu_shorten \ test_gns_max_queries \ - test_gns_dht_threepeer + test_gns_cname_lookup \ + test_gns_ns_lookup \ + test_gns_revocation \ + test_gns_dht_three_peers + #test_gns_proxy + +if ENABLE_TEST_RUN +if LINUX +TESTS = $(check_PROGRAMS) +endif +endif # test_gns_simple_lookup @@ -56,21 +232,33 @@ check_PROGRAMS = \ # test_gns_dht_delegated_lookup -plugin_LTLIBRARIES = \ - libgnunet_plugin_block_gns.la - -test_gns_dht_threepeer_SOURCES = \ - test_gns_dht_threepeer.c -test_gns_dht_threepeer_LDADD = \ +#test_gns_proxy_SOURCES = \ +# test_gns_proxy.c +#test_gns_proxy_LDADD = -lmicrohttpd @LIBCURL@ \ +# $(top_builddir)/src/util/libgnunetutil.la \ +# $(top_builddir)/src/namestore/libgnunetnamestore.la \ +# $(top_builddir)/src/gns/libgnunetgns.la \ +# $(top_builddir)/src/testing/libgnunettesting.la +#test_gns_proxy_DEPENDENCIES = \ +# $(top_builddir)/src/util/libgnunetutil.la \ +# $(top_builddir)/src/namestore/libgnunetnamestore.la \ +# libgnunetgns.la \ +# $(top_builddir)/src/testing/libgnunettesting.la + +test_gns_dht_three_peers_SOURCES = \ + test_gns_dht_three_peers.c +test_gns_dht_three_peers_LDADD = \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la \ $(top_builddir)/src/gns/libgnunetgns.la \ - $(top_builddir)/src/testing/libgnunettesting.la -test_gns_dht_threepeer_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la +test_gns_dht_three_peers_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la \ - $(top_builddir)/src/gns/libgnunetgns.la \ - $(top_builddir)/src/testing/libgnunettesting.la + libgnunetgns.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la test_gns_simple_lookup_SOURCES = \ test_gns_simple_lookup.c @@ -82,7 +270,7 @@ test_gns_simple_lookup_LDADD = \ test_gns_simple_lookup_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la \ - $(top_builddir)/src/gns/libgnunetgns.la \ + libgnunetgns.la \ $(top_builddir)/src/testing/libgnunettesting.la test_gns_simple_delegated_lookup_SOURCES = \ @@ -95,7 +283,7 @@ test_gns_simple_delegated_lookup_LDADD = \ test_gns_simple_delegated_lookup_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la \ - $(top_builddir)/src/gns/libgnunetgns.la \ + libgnunetgns.la \ $(top_builddir)/src/testing/libgnunettesting.la test_gns_simple_mx_lookup_SOURCES = \ @@ -106,10 +294,23 @@ test_gns_simple_mx_lookup_LDADD = \ $(top_builddir)/src/gns/libgnunetgns.la \ $(top_builddir)/src/testing/libgnunettesting.la test_gns_simple_mx_lookup_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/namestore/libgnunetnamestore.la \ + libgnunetgns.la \ + $(top_builddir)/src/testing/libgnunettesting.la + +test_gns_simple_srv_lookup_SOURCES = \ + test_gns_simple_srv_lookup.c +test_gns_simple_srv_lookup_LDADD = \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la \ $(top_builddir)/src/gns/libgnunetgns.la \ $(top_builddir)/src/testing/libgnunettesting.la +test_gns_simple_srv_lookup_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/namestore/libgnunetnamestore.la \ + libgnunetgns.la \ + $(top_builddir)/src/testing/libgnunettesting.la test_gns_simple_zkey_lookup_SOURCES = \ test_gns_simple_zkey_lookup.c @@ -121,7 +322,7 @@ test_gns_simple_zkey_lookup_LDADD = \ test_gns_simple_zkey_lookup_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la \ - $(top_builddir)/src/gns/libgnunetgns.la \ + libgnunetgns.la \ $(top_builddir)/src/testing/libgnunettesting.la test_gns_dht_delegated_lookup_SOURCES = \ @@ -136,7 +337,7 @@ test_gns_dht_delegated_lookup_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la \ $(top_builddir)/src/dht/libgnunetdht.la \ - $(top_builddir)/src/gns/libgnunetgns.la \ + libgnunetgns.la \ $(top_builddir)/src/testing/libgnunettesting.la test_gns_simple_shorten_SOURCES = \ @@ -149,7 +350,7 @@ test_gns_simple_shorten_LDADD = \ test_gns_simple_shorten_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la \ - $(top_builddir)/src/gns/libgnunetgns.la \ + libgnunetgns.la \ $(top_builddir)/src/testing/libgnunettesting.la test_gns_simple_get_authority_SOURCES = \ @@ -162,7 +363,7 @@ test_gns_simple_get_authority_LDADD = \ test_gns_simple_get_authority_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la \ - $(top_builddir)/src/gns/libgnunetgns.la \ + libgnunetgns.la \ $(top_builddir)/src/testing/libgnunettesting.la @@ -178,7 +379,7 @@ test_gns_pseu_shorten_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la \ $(top_builddir)/src/dht/libgnunetdht.la \ - $(top_builddir)/src/gns/libgnunetgns.la \ + libgnunetgns.la \ $(top_builddir)/src/testing/libgnunettesting.la @@ -192,83 +393,51 @@ test_gns_max_queries_LDADD = \ test_gns_max_queries_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la \ - $(top_builddir)/src/gns/libgnunetgns.la \ + libgnunetgns.la \ $(top_builddir)/src/testing/libgnunettesting.la -gnunet_gns_SOURCES = \ - gnunet-gns.c -gnunet_gns_LDADD = \ - $(top_builddir)/src/gns/libgnunetgns.la \ +test_gns_cname_lookup_SOURCES = \ + test_gns_cname_lookup.c +test_gns_cname_lookup_LDADD = \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la \ - $(GN_LIBINTL) -gnunet_gns_DEPENDENCIES = \ - libgnunetgns.la - -gnunet_gns_proxy_SOURCES = \ - gnunet-gns-proxy.c gns_proxy_proto.h -gnunet_gns_proxy_LDADD = -lmicrohttpd \ $(top_builddir)/src/gns/libgnunetgns.la \ + $(top_builddir)/src/testing/libgnunettesting.la +test_gns_cname_lookup_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la \ - $(GN_LIBINTL) -gnunet_gns_proxy_DEPENDENCIES = \ - libgnunetgns.la + $(top_builddir)/src/namestore/libgnunetnamestore.la \ + libgnunetgns.la \ + $(top_builddir)/src/testing/libgnunettesting.la -gnunet_service_gns_SOURCES = \ - gnunet-service-gns.c \ - gnunet-service-gns_resolver.c gnunet-service-gns_resolver.h \ - gnunet-service-gns_interceptor.c gnunet-service-gns_interceptor.h -gnunet_service_gns_LDADD = \ - $(top_builddir)/src/statistics/libgnunetstatistics.la \ + +test_gns_ns_lookup_SOURCES = \ + test_gns_ns_lookup.c +test_gns_ns_lookup_LDADD = \ $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/dns/libgnunetdns.la \ - $(top_builddir)/src/dns/libgnunetdnsparser.la \ - $(top_builddir)/src/dht/libgnunetdht.la \ - $(top_builddir)/src/namestore/libgnunetnamestore.la \ - $(GN_LIBINTL) -gnunet_service_gns_DEPENDENCIES = \ - $(top_builddir)/src/statistics/libgnunetstatistics.la \ + $(top_builddir)/src/namestore/libgnunetnamestore.la \ + $(top_builddir)/src/gns/libgnunetgns.la \ + $(top_builddir)/src/testing/libgnunettesting.la +test_gns_ns_lookup_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/dns/libgnunetdns.la \ - $(top_builddir)/src/dns/libgnunetdnsparser.la \ - $(top_builddir)/src/dht/libgnunetdht.la \ - $(top_builddir)/src/namestore/libgnunetnamestore.la + $(top_builddir)/src/namestore/libgnunetnamestore.la \ + libgnunetgns.la \ + $(top_builddir)/src/testing/libgnunettesting.la -gnunet_gns_fcfsd_SOURCES = \ - gnunet-gns-fcfsd.c -gnunet_gns_fcfsd_LDADD = -lmicrohttpd \ +test_gns_revocation_SOURCES = \ + test_gns_revocation.c +test_gns_revocation_LDADD = \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la \ - $(GN_LIBINTL) -gnunet_gns_fcfsd_DEPENDENCIES = \ + $(top_builddir)/src/gns/libgnunetgns.la \ + $(top_builddir)/src/testing/libgnunettesting.la +test_gns_revocation_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/namestore/libgnunetnamestore.la + $(top_builddir)/src/namestore/libgnunetnamestore.la \ + libgnunetgns.la \ + $(top_builddir)/src/testing/libgnunettesting.la -libgnunetgns_la_SOURCES = \ - gns_api.c gns.h -libgnunetgns_la_LIBADD = \ - $(top_builddir)/src/util/libgnunetutil.la $(XLIB) \ - $(top_builddir)/src/namestore/libgnunetnamestore.la -libgnunetgns_la_LDFLAGS = \ - $(GN_LIB_LDFLAGS) -libgnunetgns_la_DEPENDENCIES = \ - $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/namestore/libgnunetnamestore.la - -libgnunet_plugin_block_gns_la_SOURCES = \ - plugin_block_gns.c -libgnunet_plugin_block_gns_la_LIBADD = \ - $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/block/libgnunetblock.la \ - $(top_builddir)/src/namestore/libgnunetnamestore.la -libgnunet_plugin_block_gns_la_LDFLAGS = \ - $(GN_PLUGIN_LDFLAGS) -libgnunet_plugin_block_gns_la_DEPENDENCIES = \ - $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/block/libgnunetblock.la \ - $(top_builddir)/src/namestore/libgnunetnamestore.la #Build stub api #libgnunetnamestore_la_SOURCES = \ @@ -280,14 +449,5 @@ libgnunet_plugin_block_gns_la_DEPENDENCIES = \ #libgnunetnamestore_la_DEPENDENCIES = \ # $(top_builddir)/src/util/libgnunetutil.la -if ENABLE_TEST_RUN -if LINUX -TESTS = $(check_PROGRAMS) -endif -endif -EXTRA_DIST = \ - test_gns_defaults.conf \ - test_gns_simple_lookup.conf \ - test_gns_dht_default.conf diff --git a/src/gns/Makefile.in b/src/gns/Makefile.in index 5bdd92a..819f891 100644 --- a/src/gns/Makefile.in +++ b/src/gns/Makefile.in @@ -1,9 +1,9 @@ -# Makefile.in generated by automake 1.11.1 from Makefile.am. +# Makefile.in generated by automake 1.11.6 from Makefile.am. # @configure_input@ # Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, -# 2003, 2004, 2005, 2006, 2007, 2008, 2009 Free Software Foundation, -# Inc. +# 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Free Software +# Foundation, Inc. # This Makefile.in is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. @@ -17,7 +17,25 @@ + VPATH = @srcdir@ +am__make_dryrun = \ + { \ + am__dry=no; \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + echo 'am--echo: ; @echo "AM" OK' | $(MAKE) -f - 2>/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } pkgdatadir = $(datadir)/@PACKAGE@ pkgincludedir = $(includedir)/@PACKAGE@ pkglibdir = $(libdir)/@PACKAGE@ @@ -37,31 +55,35 @@ POST_UNINSTALL = : build_triplet = @build@ host_triplet = @host@ target_triplet = @target@ -bin_PROGRAMS = gnunet-service-gns$(EXEEXT) $(am__EXEEXT_1) \ - $(am__EXEEXT_2) gnunet-gns$(EXEEXT) +libexec_PROGRAMS = gnunet-service-gns$(EXEEXT) $(am__EXEEXT_2) \ + $(am__EXEEXT_3) $(am__EXEEXT_4) gnunet-dns2gns$(EXEEXT) +bin_PROGRAMS = $(am__EXEEXT_1) gnunet-gns$(EXEEXT) check_PROGRAMS = test_gns_simple_shorten$(EXEEXT) \ test_gns_simple_get_authority$(EXEEXT) \ test_gns_simple_lookup$(EXEEXT) \ test_gns_simple_delegated_lookup$(EXEEXT) \ test_gns_simple_mx_lookup$(EXEEXT) \ + test_gns_simple_srv_lookup$(EXEEXT) \ test_gns_simple_zkey_lookup$(EXEEXT) \ test_gns_dht_delegated_lookup$(EXEEXT) \ test_gns_pseu_shorten$(EXEEXT) test_gns_max_queries$(EXEEXT) \ - test_gns_dht_threepeer$(EXEEXT) + test_gns_cname_lookup$(EXEEXT) test_gns_ns_lookup$(EXEEXT) \ + test_gns_revocation$(EXEEXT) test_gns_dht_three_peers$(EXEEXT) subdir = src/gns DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in \ $(srcdir)/gns.conf.in ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 am__aclocal_m4_deps = $(top_srcdir)/m4/absolute-header.m4 \ $(top_srcdir)/m4/align.m4 $(top_srcdir)/m4/argz.m4 \ - $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/iconv.m4 \ - $(top_srcdir)/m4/lib-ld.m4 $(top_srcdir)/m4/lib-link.m4 \ - $(top_srcdir)/m4/lib-prefix.m4 $(top_srcdir)/m4/libcurl.m4 \ - $(top_srcdir)/m4/libgcrypt.m4 $(top_srcdir)/m4/libtool.m4 \ - $(top_srcdir)/m4/libunistring.m4 $(top_srcdir)/m4/ltdl.m4 \ - $(top_srcdir)/m4/ltoptions.m4 $(top_srcdir)/m4/ltsugar.m4 \ - $(top_srcdir)/m4/ltversion.m4 $(top_srcdir)/m4/lt~obsolete.m4 \ - $(top_srcdir)/m4/nls.m4 $(top_srcdir)/m4/po.m4 \ + $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/glib-2.0.m4 \ + $(top_srcdir)/m4/iconv.m4 $(top_srcdir)/m4/lib-ld.m4 \ + $(top_srcdir)/m4/lib-link.m4 $(top_srcdir)/m4/lib-prefix.m4 \ + $(top_srcdir)/m4/libcurl.m4 $(top_srcdir)/m4/libgcrypt.m4 \ + $(top_srcdir)/m4/libtool.m4 $(top_srcdir)/m4/libunistring.m4 \ + $(top_srcdir)/m4/ltdl.m4 $(top_srcdir)/m4/ltoptions.m4 \ + $(top_srcdir)/m4/ltsugar.m4 $(top_srcdir)/m4/ltversion.m4 \ + $(top_srcdir)/m4/lt~obsolete.m4 $(top_srcdir)/m4/nls.m4 \ + $(top_srcdir)/m4/pkg.m4 $(top_srcdir)/m4/po.m4 \ $(top_srcdir)/m4/progtest.m4 $(top_srcdir)/acinclude.m4 \ $(top_srcdir)/configure.ac am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ @@ -91,14 +113,21 @@ am__nobase_list = $(am__nobase_strip_setup); \ am__base_list = \ sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \ sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g' +am__uninstall_files_from_dir = { \ + test -z "$$files" \ + || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \ + || { echo " ( cd '$$dir' && rm -f" $$files ")"; \ + $(am__cd) "$$dir" && rm -f $$files; }; \ + } am__installdirs = "$(DESTDIR)$(libdir)" "$(DESTDIR)$(plugindir)" \ + "$(DESTDIR)$(bindir)" "$(DESTDIR)$(libexecdir)" \ "$(DESTDIR)$(bindir)" "$(DESTDIR)$(pkgcfgdir)" LTLIBRARIES = $(lib_LTLIBRARIES) $(plugin_LTLIBRARIES) am_libgnunet_plugin_block_gns_la_OBJECTS = plugin_block_gns.lo libgnunet_plugin_block_gns_la_OBJECTS = \ $(am_libgnunet_plugin_block_gns_la_OBJECTS) -AM_V_lt = $(am__v_lt_$(V)) -am__v_lt_ = $(am__v_lt_$(AM_DEFAULT_VERBOSITY)) +AM_V_lt = $(am__v_lt_@AM_V@) +am__v_lt_ = $(am__v_lt_@AM_DEFAULT_V@) am__v_lt_0 = --silent libgnunet_plugin_block_gns_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ @@ -110,30 +139,61 @@ libgnunetgns_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ $(AM_CFLAGS) $(CFLAGS) $(libgnunetgns_la_LDFLAGS) $(LDFLAGS) \ -o $@ -@HAVE_MHD_TRUE@am__EXEEXT_1 = gnunet-gns-fcfsd$(EXEEXT) -@HAVE_MHD_TRUE@am__EXEEXT_2 = gnunet-gns-proxy$(EXEEXT) -PROGRAMS = $(bin_PROGRAMS) +am_libgnunetgns_common_la_OBJECTS = gns_common.lo +libgnunetgns_common_la_OBJECTS = $(am_libgnunetgns_common_la_OBJECTS) +libgnunetgns_common_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ + $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ + $(AM_CFLAGS) $(CFLAGS) $(libgnunetgns_common_la_LDFLAGS) \ + $(LDFLAGS) -o $@ +libw32nsp_la_DEPENDENCIES = +am_libw32nsp_la_OBJECTS = w32nsp.lo +libw32nsp_la_OBJECTS = $(am_libw32nsp_la_OBJECTS) +libw32nsp_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ + $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ + $(libw32nsp_la_LDFLAGS) $(LDFLAGS) -o $@ +@MINGW_TRUE@am_libw32nsp_la_rpath = -rpath $(libdir) +@MINGW_TRUE@am__EXEEXT_1 = w32nsp-install$(EXEEXT) \ +@MINGW_TRUE@ w32nsp-uninstall$(EXEEXT) w32nsp-resolve$(EXEEXT) +@HAVE_MHD_TRUE@am__EXEEXT_2 = gnunet-gns-fcfsd$(EXEEXT) +@HAVE_GNUTLS_TRUE@@HAVE_MHD_TRUE@am__EXEEXT_3 = \ +@HAVE_GNUTLS_TRUE@@HAVE_MHD_TRUE@ gnunet-gns-proxy$(EXEEXT) +@MINGW_TRUE@am__EXEEXT_4 = gnunet-gns-helper-service-w32$(EXEEXT) +PROGRAMS = $(bin_PROGRAMS) $(libexec_PROGRAMS) +am_gnunet_dns2gns_OBJECTS = gnunet-dns2gns.$(OBJEXT) +gnunet_dns2gns_OBJECTS = $(am_gnunet_dns2gns_OBJECTS) +am__DEPENDENCIES_1 = am_gnunet_gns_OBJECTS = gnunet-gns.$(OBJEXT) gnunet_gns_OBJECTS = $(am_gnunet_gns_OBJECTS) -am__DEPENDENCIES_1 = am_gnunet_gns_fcfsd_OBJECTS = gnunet-gns-fcfsd.$(OBJEXT) gnunet_gns_fcfsd_OBJECTS = $(am_gnunet_gns_fcfsd_OBJECTS) +am_gnunet_gns_helper_service_w32_OBJECTS = \ + gnunet-gns-helper-service-w32.$(OBJEXT) +gnunet_gns_helper_service_w32_OBJECTS = \ + $(am_gnunet_gns_helper_service_w32_OBJECTS) am_gnunet_gns_proxy_OBJECTS = gnunet-gns-proxy.$(OBJEXT) gnunet_gns_proxy_OBJECTS = $(am_gnunet_gns_proxy_OBJECTS) am_gnunet_service_gns_OBJECTS = gnunet-service-gns.$(OBJEXT) \ gnunet-service-gns_resolver.$(OBJEXT) \ gnunet-service-gns_interceptor.$(OBJEXT) gnunet_service_gns_OBJECTS = $(am_gnunet_service_gns_OBJECTS) +am_test_gns_cname_lookup_OBJECTS = test_gns_cname_lookup.$(OBJEXT) +test_gns_cname_lookup_OBJECTS = $(am_test_gns_cname_lookup_OBJECTS) am_test_gns_dht_delegated_lookup_OBJECTS = \ test_gns_dht_delegated_lookup.$(OBJEXT) test_gns_dht_delegated_lookup_OBJECTS = \ $(am_test_gns_dht_delegated_lookup_OBJECTS) -am_test_gns_dht_threepeer_OBJECTS = test_gns_dht_threepeer.$(OBJEXT) -test_gns_dht_threepeer_OBJECTS = $(am_test_gns_dht_threepeer_OBJECTS) +am_test_gns_dht_three_peers_OBJECTS = \ + test_gns_dht_three_peers.$(OBJEXT) +test_gns_dht_three_peers_OBJECTS = \ + $(am_test_gns_dht_three_peers_OBJECTS) am_test_gns_max_queries_OBJECTS = test_gns_max_queries.$(OBJEXT) test_gns_max_queries_OBJECTS = $(am_test_gns_max_queries_OBJECTS) +am_test_gns_ns_lookup_OBJECTS = test_gns_ns_lookup.$(OBJEXT) +test_gns_ns_lookup_OBJECTS = $(am_test_gns_ns_lookup_OBJECTS) am_test_gns_pseu_shorten_OBJECTS = test_gns_pseu_shorten.$(OBJEXT) test_gns_pseu_shorten_OBJECTS = $(am_test_gns_pseu_shorten_OBJECTS) +am_test_gns_revocation_OBJECTS = test_gns_revocation.$(OBJEXT) +test_gns_revocation_OBJECTS = $(am_test_gns_revocation_OBJECTS) am_test_gns_simple_delegated_lookup_OBJECTS = \ test_gns_simple_delegated_lookup.$(OBJEXT) test_gns_simple_delegated_lookup_OBJECTS = \ @@ -152,10 +212,24 @@ am_test_gns_simple_shorten_OBJECTS = \ test_gns_simple_shorten.$(OBJEXT) test_gns_simple_shorten_OBJECTS = \ $(am_test_gns_simple_shorten_OBJECTS) +am_test_gns_simple_srv_lookup_OBJECTS = \ + test_gns_simple_srv_lookup.$(OBJEXT) +test_gns_simple_srv_lookup_OBJECTS = \ + $(am_test_gns_simple_srv_lookup_OBJECTS) am_test_gns_simple_zkey_lookup_OBJECTS = \ test_gns_simple_zkey_lookup.$(OBJEXT) test_gns_simple_zkey_lookup_OBJECTS = \ $(am_test_gns_simple_zkey_lookup_OBJECTS) +am_w32nsp_install_OBJECTS = w32nsp-install.$(OBJEXT) +w32nsp_install_OBJECTS = $(am_w32nsp_install_OBJECTS) +w32nsp_install_DEPENDENCIES = +am_w32nsp_resolve_OBJECTS = w32nsp-resolve.$(OBJEXT) +w32nsp_resolve_OBJECTS = $(am_w32nsp_resolve_OBJECTS) +w32nsp_resolve_DEPENDENCIES = +am_w32nsp_uninstall_OBJECTS = w32nsp-uninstall.$(OBJEXT) +w32nsp_uninstall_OBJECTS = $(am_w32nsp_uninstall_OBJECTS) +w32nsp_uninstall_DEPENDENCIES = +SCRIPTS = $(bin_SCRIPTS) DEFAULT_INCLUDES = -I.@am__isrc@ -I$(top_builddir) depcomp = $(SHELL) $(top_srcdir)/depcomp am__depfiles_maybe = depfiles @@ -166,50 +240,64 @@ LTCOMPILE = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) \ $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) \ $(AM_CFLAGS) $(CFLAGS) -AM_V_CC = $(am__v_CC_$(V)) -am__v_CC_ = $(am__v_CC_$(AM_DEFAULT_VERBOSITY)) +AM_V_CC = $(am__v_CC_@AM_V@) +am__v_CC_ = $(am__v_CC_@AM_DEFAULT_V@) am__v_CC_0 = @echo " CC " $@; -AM_V_at = $(am__v_at_$(V)) -am__v_at_ = $(am__v_at_$(AM_DEFAULT_VERBOSITY)) +AM_V_at = $(am__v_at_@AM_V@) +am__v_at_ = $(am__v_at_@AM_DEFAULT_V@) am__v_at_0 = @ CCLD = $(CC) LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ $(AM_LDFLAGS) $(LDFLAGS) -o $@ -AM_V_CCLD = $(am__v_CCLD_$(V)) -am__v_CCLD_ = $(am__v_CCLD_$(AM_DEFAULT_VERBOSITY)) +AM_V_CCLD = $(am__v_CCLD_@AM_V@) +am__v_CCLD_ = $(am__v_CCLD_@AM_DEFAULT_V@) am__v_CCLD_0 = @echo " CCLD " $@; -AM_V_GEN = $(am__v_GEN_$(V)) -am__v_GEN_ = $(am__v_GEN_$(AM_DEFAULT_VERBOSITY)) +AM_V_GEN = $(am__v_GEN_@AM_V@) +am__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@) am__v_GEN_0 = @echo " GEN " $@; SOURCES = $(libgnunet_plugin_block_gns_la_SOURCES) \ - $(libgnunetgns_la_SOURCES) $(gnunet_gns_SOURCES) \ - $(gnunet_gns_fcfsd_SOURCES) $(gnunet_gns_proxy_SOURCES) \ - $(gnunet_service_gns_SOURCES) \ + $(libgnunetgns_la_SOURCES) $(libgnunetgns_common_la_SOURCES) \ + $(libw32nsp_la_SOURCES) $(gnunet_dns2gns_SOURCES) \ + $(gnunet_gns_SOURCES) $(gnunet_gns_fcfsd_SOURCES) \ + $(gnunet_gns_helper_service_w32_SOURCES) \ + $(gnunet_gns_proxy_SOURCES) $(gnunet_service_gns_SOURCES) \ + $(test_gns_cname_lookup_SOURCES) \ $(test_gns_dht_delegated_lookup_SOURCES) \ - $(test_gns_dht_threepeer_SOURCES) \ - $(test_gns_max_queries_SOURCES) \ + $(test_gns_dht_three_peers_SOURCES) \ + $(test_gns_max_queries_SOURCES) $(test_gns_ns_lookup_SOURCES) \ $(test_gns_pseu_shorten_SOURCES) \ + $(test_gns_revocation_SOURCES) \ $(test_gns_simple_delegated_lookup_SOURCES) \ $(test_gns_simple_get_authority_SOURCES) \ $(test_gns_simple_lookup_SOURCES) \ $(test_gns_simple_mx_lookup_SOURCES) \ $(test_gns_simple_shorten_SOURCES) \ - $(test_gns_simple_zkey_lookup_SOURCES) + $(test_gns_simple_srv_lookup_SOURCES) \ + $(test_gns_simple_zkey_lookup_SOURCES) \ + $(w32nsp_install_SOURCES) $(w32nsp_resolve_SOURCES) \ + $(w32nsp_uninstall_SOURCES) DIST_SOURCES = $(libgnunet_plugin_block_gns_la_SOURCES) \ - $(libgnunetgns_la_SOURCES) $(gnunet_gns_SOURCES) \ - $(gnunet_gns_fcfsd_SOURCES) $(gnunet_gns_proxy_SOURCES) \ - $(gnunet_service_gns_SOURCES) \ + $(libgnunetgns_la_SOURCES) $(libgnunetgns_common_la_SOURCES) \ + $(libw32nsp_la_SOURCES) $(gnunet_dns2gns_SOURCES) \ + $(gnunet_gns_SOURCES) $(gnunet_gns_fcfsd_SOURCES) \ + $(gnunet_gns_helper_service_w32_SOURCES) \ + $(gnunet_gns_proxy_SOURCES) $(gnunet_service_gns_SOURCES) \ + $(test_gns_cname_lookup_SOURCES) \ $(test_gns_dht_delegated_lookup_SOURCES) \ - $(test_gns_dht_threepeer_SOURCES) \ - $(test_gns_max_queries_SOURCES) \ + $(test_gns_dht_three_peers_SOURCES) \ + $(test_gns_max_queries_SOURCES) $(test_gns_ns_lookup_SOURCES) \ $(test_gns_pseu_shorten_SOURCES) \ + $(test_gns_revocation_SOURCES) \ $(test_gns_simple_delegated_lookup_SOURCES) \ $(test_gns_simple_get_authority_SOURCES) \ $(test_gns_simple_lookup_SOURCES) \ $(test_gns_simple_mx_lookup_SOURCES) \ $(test_gns_simple_shorten_SOURCES) \ - $(test_gns_simple_zkey_lookup_SOURCES) + $(test_gns_simple_srv_lookup_SOURCES) \ + $(test_gns_simple_zkey_lookup_SOURCES) \ + $(w32nsp_install_SOURCES) $(w32nsp_resolve_SOURCES) \ + $(w32nsp_uninstall_SOURCES) RECURSIVE_TARGETS = all-recursive check-recursive dvi-recursive \ html-recursive info-recursive install-data-recursive \ install-dvi-recursive install-exec-recursive \ @@ -217,6 +305,11 @@ RECURSIVE_TARGETS = all-recursive check-recursive dvi-recursive \ install-pdf-recursive install-ps-recursive install-recursive \ installcheck-recursive installdirs-recursive pdf-recursive \ ps-recursive uninstall-recursive +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac DATA = $(pkgcfg_DATA) RECURSIVE_CLEAN_TARGETS = mostlyclean-recursive clean-recursive \ distclean-recursive maintainer-clean-recursive @@ -289,6 +382,10 @@ EXEEXT = @EXEEXT@ EXT_LIBS = @EXT_LIBS@ EXT_LIB_PATH = @EXT_LIB_PATH@ FGREP = @FGREP@ +GLIB_CFLAGS = @GLIB_CFLAGS@ +GLIB_GENMARSHAL = @GLIB_GENMARSHAL@ +GLIB_LIBS = @GLIB_LIBS@ +GLIB_MKENUMS = @GLIB_MKENUMS@ GMSGFMT = @GMSGFMT@ GMSGFMT_015 = @GMSGFMT_015@ GNUNETDNS_GROUP = @GNUNETDNS_GROUP@ @@ -299,6 +396,7 @@ GN_LIBINTL = @GN_LIBINTL@ GN_LIB_LDFLAGS = @GN_LIB_LDFLAGS@ GN_PLUGIN_LDFLAGS = @GN_PLUGIN_LDFLAGS@ GN_USER_HOME_DIR = @GN_USER_HOME_DIR@ +GOBJECT_QUERY = @GOBJECT_QUERY@ GREP = @GREP@ HAVE_LIBUNISTRING = @HAVE_LIBUNISTRING@ INCLTDL = @INCLTDL@ @@ -321,6 +419,8 @@ LIBCURL_CPPFLAGS = @LIBCURL_CPPFLAGS@ LIBGCRYPT_CFLAGS = @LIBGCRYPT_CFLAGS@ LIBGCRYPT_CONFIG = @LIBGCRYPT_CONFIG@ LIBGCRYPT_LIBS = @LIBGCRYPT_LIBS@ +LIBGTOP_CFLAGS = @LIBGTOP_CFLAGS@ +LIBGTOP_LIBS = @LIBGTOP_LIBS@ LIBICONV = @LIBICONV@ LIBINTL = @LIBINTL@ LIBLTDL = @LIBLTDL@ @@ -342,6 +442,7 @@ LT_CONFIG_H = @LT_CONFIG_H@ LT_DLLOADERS = @LT_DLLOADERS@ LT_DLPREOPEN = @LT_DLPREOPEN@ MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ MKDIR_P = @MKDIR_P@ MONKEYPREFIX = @MONKEYPREFIX@ MSGFMT = @MSGFMT@ @@ -351,6 +452,7 @@ MYSQL_CPPFLAGS = @MYSQL_CPPFLAGS@ MYSQL_LDFLAGS = @MYSQL_LDFLAGS@ NM = @NM@ NMEDIT = @NMEDIT@ +NSS_DIR = @NSS_DIR@ OBJC = @OBJC@ OBJCDEPMODE = @OBJCDEPMODE@ OBJCFLAGS = @OBJCFLAGS@ @@ -366,6 +468,7 @@ PACKAGE_TARNAME = @PACKAGE_TARNAME@ PACKAGE_URL = @PACKAGE_URL@ PACKAGE_VERSION = @PACKAGE_VERSION@ PATH_SEPARATOR = @PATH_SEPARATOR@ +PKG_CONFIG = @PKG_CONFIG@ POSTGRES_CPPFLAGS = @POSTGRES_CPPFLAGS@ POSTGRES_LDFLAGS = @POSTGRES_LDFLAGS@ POSUB = @POSUB@ @@ -397,6 +500,7 @@ abs_builddir = @abs_builddir@ abs_srcdir = @abs_srcdir@ abs_top_builddir = @abs_top_builddir@ abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ ac_ct_CC = @ac_ct_CC@ ac_ct_CXX = @ac_ct_CXX@ ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ @@ -419,6 +523,7 @@ datarootdir = @datarootdir@ docdir = @docdir@ dvidir = @dvidir@ exec_prefix = @exec_prefix@ +gitcommand = @gitcommand@ host = @host@ host_alias = @host_alias@ host_cpu = @host_cpu@ @@ -429,10 +534,9 @@ includedir = @includedir@ infodir = @infodir@ install_sh = @install_sh@ libdir = @libdir@ -libexecdir = @libexecdir@ +libexecdir = $(pkglibdir)/libexec/ localedir = @localedir@ localstatedir = @localstatedir@ -lt_ECHO = @lt_ECHO@ ltdl_LIBOBJS = @ltdl_LIBOBJS@ ltdl_LTLIBOBJS = @ltdl_LTLIBOBJS@ mandir = @mandir@ @@ -450,6 +554,7 @@ sbindir = @sbindir@ sharedstatedir = @sharedstatedir@ srcdir = @srcdir@ subdirs = @subdirs@ +svnversioncommand = @svnversioncommand@ sys_symbol_underscore = @sys_symbol_underscore@ sysconfdir = @sysconfdir@ target = @target@ @@ -463,39 +568,227 @@ top_srcdir = @top_srcdir@ INCLUDES = -I$(top_srcdir)/src/include @HAVE_GLIBCNSS_TRUE@NSS_SUBDIR = nss SUBDIRS = . $(NSS_SUBDIR) +EXTRA_DIST = \ + test_gns_defaults.conf \ + test_gns_simple_lookup.conf \ + test_gns_dht_default.conf \ + gns-helper-service-w32.conf \ + gnunet-gns-proxy-setup-ca \ + zonefiles/188JSUMKEF25GVU8TTV0PBNNN8JVCPUEDFV1UHJJU884JD25V0T0.zkey \ + zonefiles/OEFL7A4VEF1B40QLEMTG5D8G1CN6EN16QUSG5R2DT71GRJN34LSG.zkey \ + zonefiles/test_zonekey + @MINGW_TRUE@WINFLAGS = -Wl,--no-undefined -Wl,--export-all-symbols +@MINGW_TRUE@DO_W32_HELPER = gnunet-gns-helper-service-w32 +@MINGW_TRUE@DO_W32_NSP = libw32nsp.la +@MINGW_TRUE@DO_W32_NSPTOOLS = w32nsp-install w32nsp-uninstall w32nsp-resolve +@MINGW_TRUE@DO_W32_HS_CONF = gns-helper-service-w32.conf +@MINGW_FALSE@USE_VPN = $(top_builddir)/src/vpn/libgnunetvpn.la @USE_COVERAGE_TRUE@AM_CFLAGS = --coverage -O0 pkgcfgdir = $(pkgdatadir)/config.d/ plugindir = $(libdir)/gnunet pkgcfg_DATA = \ - gns.conf + gns.conf \ + $(DO_W32_HS_CONF) lib_LTLIBRARIES = \ - libgnunetgns.la + $(DO_W32_NSP) \ + libgnunetgns.la \ + libgnunetgns_common.la @HAVE_MHD_TRUE@DO_FCFSD = gnunet-gns-fcfsd -@HAVE_MHD_TRUE@DO_PROXY = gnunet-gns-proxy - -# test_gns_simple_lookup -# test_gns_simple_delegated_lookup -# test_gns_dht_delegated_lookup +@HAVE_GNUTLS_TRUE@@HAVE_MHD_TRUE@DO_PROXY = gnunet-gns-proxy +bin_SCRIPTS = gnunet-gns-proxy-setup-ca plugin_LTLIBRARIES = \ libgnunet_plugin_block_gns.la -test_gns_dht_threepeer_SOURCES = \ - test_gns_dht_threepeer.c +gnunet_gns_SOURCES = \ + gnunet-gns.c -test_gns_dht_threepeer_LDADD = \ +gnunet_gns_LDADD = \ + $(top_builddir)/src/gns/libgnunetgns.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la \ + $(GN_LIBINTL) + +gnunet_gns_DEPENDENCIES = \ + libgnunetgns.la + +gnunet_dns2gns_SOURCES = \ + gnunet-dns2gns.c + +gnunet_dns2gns_LDADD = \ $(top_builddir)/src/gns/libgnunetgns.la \ - $(top_builddir)/src/testing/libgnunettesting.la + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/namestore/libgnunetnamestore.la \ + $(top_builddir)/src/dns/libgnunetdnsparser.la \ + $(top_builddir)/src/dns/libgnunetdnsstub.la \ + $(GN_LIBINTL) + +gnunet_dns2gns_DEPENDENCIES = \ + libgnunetgns.la -test_gns_dht_threepeer_DEPENDENCIES = \ +gnunet_gns_proxy_SOURCES = \ + gnunet-gns-proxy.c gns_proxy_proto.h + +gnunet_gns_proxy_LDADD = -lmicrohttpd -lcurl -lgnutls \ + $(top_builddir)/src/gns/libgnunetgns.la \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(GN_LIBINTL) + +gnunet_gns_proxy_DEPENDENCIES = \ + libgnunetgns.la + +gnunet_gns_helper_service_w32_SOURCES = \ + gnunet-gns-helper-service-w32.c + +gnunet_gns_helper_service_w32_LDADD = \ + $(top_builddir)/src/gns/libgnunetgns.la \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(GN_LIBINTL) + +gnunet_gns_helper_service_w32_DEPENDENCIES = \ + libgnunetgns.la + +w32nsp_install_SOURCES = \ + w32nsp-install.c + +w32nsp_install_LDADD = -lws2_32 +w32nsp_uninstall_SOURCES = \ + w32nsp-uninstall.c + +w32nsp_uninstall_LDADD = -lws2_32 +w32nsp_resolve_SOURCES = \ + w32nsp-resolve.c + +w32nsp_resolve_LDADD = -lws2_32 +gnunet_service_gns_SOURCES = \ + gnunet-service-gns.c \ + gnunet-service-gns_resolver.c gnunet-service-gns_resolver.h \ + gnunet-service-gns_interceptor.c gnunet-service-gns_interceptor.h + +gnunet_service_gns_LDADD = \ + -lm \ + $(top_builddir)/src/statistics/libgnunetstatistics.la \ + $(top_builddir)/src/util/libgnunetutil.la \ + libgnunetgns_common.la \ + $(top_builddir)/src/dns/libgnunetdns.la \ + $(top_builddir)/src/dns/libgnunetdnsparser.la \ + $(top_builddir)/src/dht/libgnunetdht.la \ + $(top_builddir)/src/namestore/libgnunetnamestore.la \ + $(USE_VPN) \ + $(GN_LIBINTL) + +gnunet_service_gns_DEPENDENCIES = \ + $(top_builddir)/src/statistics/libgnunetstatistics.la \ + $(top_builddir)/src/util/libgnunetutil.la \ + libgnunetgns_common.la \ + $(top_builddir)/src/dns/libgnunetdns.la \ + $(top_builddir)/src/dns/libgnunetdnsparser.la \ + $(top_builddir)/src/dht/libgnunetdht.la \ + $(top_builddir)/src/namestore/libgnunetnamestore.la \ + $(USE_VPN) + +gnunet_gns_fcfsd_SOURCES = \ + gnunet-gns-fcfsd.c + +gnunet_gns_fcfsd_LDADD = -lmicrohttpd \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/namestore/libgnunetnamestore.la \ + $(GN_LIBINTL) + +gnunet_gns_fcfsd_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/namestore/libgnunetnamestore.la + +libw32nsp_la_SOURCES = \ + w32nsp.c + +libw32nsp_la_LIBADD = \ + -lole32 -lws2_32 + +libw32nsp_la_LDFLAGS = \ + -export-symbols $(top_srcdir)/src/gns/w32nsp.def \ + $(GN_LIB_LDFLAGS) + +libgnunetgns_la_SOURCES = \ + gns_api.c gns.h + +libgnunetgns_la_LIBADD = \ + $(top_builddir)/src/util/libgnunetutil.la $(XLIB) \ + $(top_builddir)/src/namestore/libgnunetnamestore.la + +libgnunetgns_la_LDFLAGS = \ + $(GN_LIB_LDFLAGS) + +libgnunetgns_la_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/namestore/libgnunetnamestore.la + +libgnunetgns_common_la_SOURCES = \ + gns_common.c gns_common.h + +libgnunetgns_common_la_LDFLAGS = \ + $(GN_LIB_LDFLAGS) + +libgnunetgns_common_la_LIBADD = \ + $(top_builddir)/src/util/libgnunetutil.la + +libgnunetgns_common_la_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la + +libgnunet_plugin_block_gns_la_SOURCES = \ + plugin_block_gns.c + +libgnunet_plugin_block_gns_la_LIBADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/block/libgnunetblock.la \ + $(top_builddir)/src/gns/libgnunetgns_common.la \ + $(top_builddir)/src/namestore/libgnunetnamestore.la + +libgnunet_plugin_block_gns_la_LDFLAGS = \ + $(GN_PLUGIN_LDFLAGS) + +libgnunet_plugin_block_gns_la_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la \ + libgnunetgns_common.la \ + $(top_builddir)/src/block/libgnunetblock.la \ + $(top_builddir)/src/namestore/libgnunetnamestore.la + +@ENABLE_TEST_RUN_TRUE@@LINUX_TRUE@TESTS = $(check_PROGRAMS) + +# test_gns_simple_lookup +# test_gns_simple_delegated_lookup +# test_gns_dht_delegated_lookup + +#test_gns_proxy_SOURCES = \ +# test_gns_proxy.c +#test_gns_proxy_LDADD = -lmicrohttpd @LIBCURL@ \ +# $(top_builddir)/src/util/libgnunetutil.la \ +# $(top_builddir)/src/namestore/libgnunetnamestore.la \ +# $(top_builddir)/src/gns/libgnunetgns.la \ +# $(top_builddir)/src/testing/libgnunettesting.la +#test_gns_proxy_DEPENDENCIES = \ +# $(top_builddir)/src/util/libgnunetutil.la \ +# $(top_builddir)/src/namestore/libgnunetnamestore.la \ +# libgnunetgns.la \ +# $(top_builddir)/src/testing/libgnunettesting.la +test_gns_dht_three_peers_SOURCES = \ + test_gns_dht_three_peers.c + +test_gns_dht_three_peers_LDADD = \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la \ $(top_builddir)/src/gns/libgnunetgns.la \ - $(top_builddir)/src/testing/libgnunettesting.la + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la + +test_gns_dht_three_peers_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/namestore/libgnunetnamestore.la \ + libgnunetgns.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la test_gns_simple_lookup_SOURCES = \ test_gns_simple_lookup.c @@ -509,7 +802,7 @@ test_gns_simple_lookup_LDADD = \ test_gns_simple_lookup_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la \ - $(top_builddir)/src/gns/libgnunetgns.la \ + libgnunetgns.la \ $(top_builddir)/src/testing/libgnunettesting.la test_gns_simple_delegated_lookup_SOURCES = \ @@ -524,7 +817,7 @@ test_gns_simple_delegated_lookup_LDADD = \ test_gns_simple_delegated_lookup_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la \ - $(top_builddir)/src/gns/libgnunetgns.la \ + libgnunetgns.la \ $(top_builddir)/src/testing/libgnunettesting.la test_gns_simple_mx_lookup_SOURCES = \ @@ -537,11 +830,26 @@ test_gns_simple_mx_lookup_LDADD = \ $(top_builddir)/src/testing/libgnunettesting.la test_gns_simple_mx_lookup_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/namestore/libgnunetnamestore.la \ + libgnunetgns.la \ + $(top_builddir)/src/testing/libgnunettesting.la + +test_gns_simple_srv_lookup_SOURCES = \ + test_gns_simple_srv_lookup.c + +test_gns_simple_srv_lookup_LDADD = \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la \ $(top_builddir)/src/gns/libgnunetgns.la \ $(top_builddir)/src/testing/libgnunettesting.la +test_gns_simple_srv_lookup_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/namestore/libgnunetnamestore.la \ + libgnunetgns.la \ + $(top_builddir)/src/testing/libgnunettesting.la + test_gns_simple_zkey_lookup_SOURCES = \ test_gns_simple_zkey_lookup.c @@ -554,7 +862,7 @@ test_gns_simple_zkey_lookup_LDADD = \ test_gns_simple_zkey_lookup_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la \ - $(top_builddir)/src/gns/libgnunetgns.la \ + libgnunetgns.la \ $(top_builddir)/src/testing/libgnunettesting.la test_gns_dht_delegated_lookup_SOURCES = \ @@ -571,7 +879,7 @@ test_gns_dht_delegated_lookup_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la \ $(top_builddir)/src/dht/libgnunetdht.la \ - $(top_builddir)/src/gns/libgnunetgns.la \ + libgnunetgns.la \ $(top_builddir)/src/testing/libgnunettesting.la test_gns_simple_shorten_SOURCES = \ @@ -586,7 +894,7 @@ test_gns_simple_shorten_LDADD = \ test_gns_simple_shorten_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la \ - $(top_builddir)/src/gns/libgnunetgns.la \ + libgnunetgns.la \ $(top_builddir)/src/testing/libgnunettesting.la test_gns_simple_get_authority_SOURCES = \ @@ -601,7 +909,7 @@ test_gns_simple_get_authority_LDADD = \ test_gns_simple_get_authority_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la \ - $(top_builddir)/src/gns/libgnunetgns.la \ + libgnunetgns.la \ $(top_builddir)/src/testing/libgnunettesting.la test_gns_pseu_shorten_SOURCES = \ @@ -618,7 +926,7 @@ test_gns_pseu_shorten_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la \ $(top_builddir)/src/dht/libgnunetdht.la \ - $(top_builddir)/src/gns/libgnunetgns.la \ + libgnunetgns.la \ $(top_builddir)/src/testing/libgnunettesting.la test_gns_max_queries_SOURCES = \ @@ -633,111 +941,53 @@ test_gns_max_queries_LDADD = \ test_gns_max_queries_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la \ - $(top_builddir)/src/gns/libgnunetgns.la \ + libgnunetgns.la \ $(top_builddir)/src/testing/libgnunettesting.la -gnunet_gns_SOURCES = \ - gnunet-gns.c +test_gns_cname_lookup_SOURCES = \ + test_gns_cname_lookup.c -gnunet_gns_LDADD = \ - $(top_builddir)/src/gns/libgnunetgns.la \ +test_gns_cname_lookup_LDADD = \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la \ - $(GN_LIBINTL) - -gnunet_gns_DEPENDENCIES = \ - libgnunetgns.la - -gnunet_gns_proxy_SOURCES = \ - gnunet-gns-proxy.c gns_proxy_proto.h - -gnunet_gns_proxy_LDADD = -lmicrohttpd \ $(top_builddir)/src/gns/libgnunetgns.la \ - $(top_builddir)/src/util/libgnunetutil.la \ - $(GN_LIBINTL) - -gnunet_gns_proxy_DEPENDENCIES = \ - libgnunetgns.la - -gnunet_service_gns_SOURCES = \ - gnunet-service-gns.c \ - gnunet-service-gns_resolver.c gnunet-service-gns_resolver.h \ - gnunet-service-gns_interceptor.c gnunet-service-gns_interceptor.h - -gnunet_service_gns_LDADD = \ - $(top_builddir)/src/statistics/libgnunetstatistics.la \ - $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/dns/libgnunetdns.la \ - $(top_builddir)/src/dns/libgnunetdnsparser.la \ - $(top_builddir)/src/dht/libgnunetdht.la \ - $(top_builddir)/src/namestore/libgnunetnamestore.la \ - $(GN_LIBINTL) + $(top_builddir)/src/testing/libgnunettesting.la -gnunet_service_gns_DEPENDENCIES = \ - $(top_builddir)/src/statistics/libgnunetstatistics.la \ +test_gns_cname_lookup_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/dns/libgnunetdns.la \ - $(top_builddir)/src/dns/libgnunetdnsparser.la \ - $(top_builddir)/src/dht/libgnunetdht.la \ - $(top_builddir)/src/namestore/libgnunetnamestore.la + $(top_builddir)/src/namestore/libgnunetnamestore.la \ + libgnunetgns.la \ + $(top_builddir)/src/testing/libgnunettesting.la -gnunet_gns_fcfsd_SOURCES = \ - gnunet-gns-fcfsd.c +test_gns_ns_lookup_SOURCES = \ + test_gns_ns_lookup.c -gnunet_gns_fcfsd_LDADD = -lmicrohttpd \ +test_gns_ns_lookup_LDADD = \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la \ - $(GN_LIBINTL) + $(top_builddir)/src/gns/libgnunetgns.la \ + $(top_builddir)/src/testing/libgnunettesting.la -gnunet_gns_fcfsd_DEPENDENCIES = \ +test_gns_ns_lookup_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/namestore/libgnunetnamestore.la - -libgnunetgns_la_SOURCES = \ - gns_api.c gns.h - -libgnunetgns_la_LIBADD = \ - $(top_builddir)/src/util/libgnunetutil.la $(XLIB) \ - $(top_builddir)/src/namestore/libgnunetnamestore.la - -libgnunetgns_la_LDFLAGS = \ - $(GN_LIB_LDFLAGS) - -libgnunetgns_la_DEPENDENCIES = \ - $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/namestore/libgnunetnamestore.la + $(top_builddir)/src/namestore/libgnunetnamestore.la \ + libgnunetgns.la \ + $(top_builddir)/src/testing/libgnunettesting.la -libgnunet_plugin_block_gns_la_SOURCES = \ - plugin_block_gns.c +test_gns_revocation_SOURCES = \ + test_gns_revocation.c -libgnunet_plugin_block_gns_la_LIBADD = \ +test_gns_revocation_LDADD = \ $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/block/libgnunetblock.la \ - $(top_builddir)/src/namestore/libgnunetnamestore.la - -libgnunet_plugin_block_gns_la_LDFLAGS = \ - $(GN_PLUGIN_LDFLAGS) + $(top_builddir)/src/namestore/libgnunetnamestore.la \ + $(top_builddir)/src/gns/libgnunetgns.la \ + $(top_builddir)/src/testing/libgnunettesting.la -libgnunet_plugin_block_gns_la_DEPENDENCIES = \ +test_gns_revocation_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/block/libgnunetblock.la \ - $(top_builddir)/src/namestore/libgnunetnamestore.la - - -#Build stub api -#libgnunetnamestore_la_SOURCES = \ -# namestore_stub_api.c -#libgnunetnamestore_la_LIBADD = \ -# $(top_builddir)/src/util/libgnunetutil.la $(XLIB) -#libgnunetnamestore_la_LDFLAGS = \ -# $(GN_LIB_LDFLAGS) -#libgnunetnamestore_la_DEPENDENCIES = \ -# $(top_builddir)/src/util/libgnunetutil.la -@ENABLE_TEST_RUN_TRUE@@LINUX_TRUE@TESTS = $(check_PROGRAMS) -EXTRA_DIST = \ - test_gns_defaults.conf \ - test_gns_simple_lookup.conf \ - test_gns_dht_default.conf + $(top_builddir)/src/namestore/libgnunetnamestore.la \ + libgnunetgns.la \ + $(top_builddir)/src/testing/libgnunettesting.la all: all-recursive @@ -777,7 +1027,6 @@ gns.conf: $(top_builddir)/config.status $(srcdir)/gns.conf.in cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ install-libLTLIBRARIES: $(lib_LTLIBRARIES) @$(NORMAL_INSTALL) - test -z "$(libdir)" || $(MKDIR_P) "$(DESTDIR)$(libdir)" @list='$(lib_LTLIBRARIES)'; test -n "$(libdir)" || list=; \ list2=; for p in $$list; do \ if test -f $$p; then \ @@ -785,6 +1034,8 @@ install-libLTLIBRARIES: $(lib_LTLIBRARIES) else :; fi; \ done; \ test -z "$$list2" || { \ + echo " $(MKDIR_P) '$(DESTDIR)$(libdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libdir)" || exit 1; \ echo " $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 '$(DESTDIR)$(libdir)'"; \ $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 "$(DESTDIR)$(libdir)"; \ } @@ -808,7 +1059,6 @@ clean-libLTLIBRARIES: done install-pluginLTLIBRARIES: $(plugin_LTLIBRARIES) @$(NORMAL_INSTALL) - test -z "$(plugindir)" || $(MKDIR_P) "$(DESTDIR)$(plugindir)" @list='$(plugin_LTLIBRARIES)'; test -n "$(plugindir)" || list=; \ list2=; for p in $$list; do \ if test -f $$p; then \ @@ -816,6 +1066,8 @@ install-pluginLTLIBRARIES: $(plugin_LTLIBRARIES) else :; fi; \ done; \ test -z "$$list2" || { \ + echo " $(MKDIR_P) '$(DESTDIR)$(plugindir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(plugindir)" || exit 1; \ echo " $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 '$(DESTDIR)$(plugindir)'"; \ $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 "$(DESTDIR)$(plugindir)"; \ } @@ -837,14 +1089,21 @@ clean-pluginLTLIBRARIES: echo "rm -f \"$${dir}/so_locations\""; \ rm -f "$${dir}/so_locations"; \ done -libgnunet_plugin_block_gns.la: $(libgnunet_plugin_block_gns_la_OBJECTS) $(libgnunet_plugin_block_gns_la_DEPENDENCIES) +libgnunet_plugin_block_gns.la: $(libgnunet_plugin_block_gns_la_OBJECTS) $(libgnunet_plugin_block_gns_la_DEPENDENCIES) $(EXTRA_libgnunet_plugin_block_gns_la_DEPENDENCIES) $(AM_V_CCLD)$(libgnunet_plugin_block_gns_la_LINK) -rpath $(plugindir) $(libgnunet_plugin_block_gns_la_OBJECTS) $(libgnunet_plugin_block_gns_la_LIBADD) $(LIBS) -libgnunetgns.la: $(libgnunetgns_la_OBJECTS) $(libgnunetgns_la_DEPENDENCIES) +libgnunetgns.la: $(libgnunetgns_la_OBJECTS) $(libgnunetgns_la_DEPENDENCIES) $(EXTRA_libgnunetgns_la_DEPENDENCIES) $(AM_V_CCLD)$(libgnunetgns_la_LINK) -rpath $(libdir) $(libgnunetgns_la_OBJECTS) $(libgnunetgns_la_LIBADD) $(LIBS) +libgnunetgns_common.la: $(libgnunetgns_common_la_OBJECTS) $(libgnunetgns_common_la_DEPENDENCIES) $(EXTRA_libgnunetgns_common_la_DEPENDENCIES) + $(AM_V_CCLD)$(libgnunetgns_common_la_LINK) -rpath $(libdir) $(libgnunetgns_common_la_OBJECTS) $(libgnunetgns_common_la_LIBADD) $(LIBS) +libw32nsp.la: $(libw32nsp_la_OBJECTS) $(libw32nsp_la_DEPENDENCIES) $(EXTRA_libw32nsp_la_DEPENDENCIES) + $(AM_V_CCLD)$(libw32nsp_la_LINK) $(am_libw32nsp_la_rpath) $(libw32nsp_la_OBJECTS) $(libw32nsp_la_LIBADD) $(LIBS) install-binPROGRAMS: $(bin_PROGRAMS) @$(NORMAL_INSTALL) - test -z "$(bindir)" || $(MKDIR_P) "$(DESTDIR)$(bindir)" @list='$(bin_PROGRAMS)'; test -n "$(bindir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(bindir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(bindir)" || exit 1; \ + fi; \ for p in $$list; do echo "$$p $$p"; done | \ sed 's/$(EXEEXT)$$//' | \ while read p p1; do if test -f $$p || test -f $$p1; \ @@ -893,48 +1152,156 @@ clean-checkPROGRAMS: list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ echo " rm -f" $$list; \ rm -f $$list -gnunet-gns$(EXEEXT): $(gnunet_gns_OBJECTS) $(gnunet_gns_DEPENDENCIES) +install-libexecPROGRAMS: $(libexec_PROGRAMS) + @$(NORMAL_INSTALL) + @list='$(libexec_PROGRAMS)'; test -n "$(libexecdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(libexecdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libexecdir)" || exit 1; \ + fi; \ + for p in $$list; do echo "$$p $$p"; done | \ + sed 's/$(EXEEXT)$$//' | \ + while read p p1; do if test -f $$p || test -f $$p1; \ + then echo "$$p"; echo "$$p"; else :; fi; \ + done | \ + sed -e 'p;s,.*/,,;n;h' -e 's|.*|.|' \ + -e 'p;x;s,.*/,,;s/$(EXEEXT)$$//;$(transform);s/$$/$(EXEEXT)/' | \ + sed 'N;N;N;s,\n, ,g' | \ + $(AWK) 'BEGIN { files["."] = ""; dirs["."] = 1 } \ + { d=$$3; if (dirs[d] != 1) { print "d", d; dirs[d] = 1 } \ + if ($$2 == $$4) files[d] = files[d] " " $$1; \ + else { print "f", $$3 "/" $$4, $$1; } } \ + END { for (d in files) print "f", d, files[d] }' | \ + while read type dir files; do \ + if test "$$dir" = .; then dir=; else dir=/$$dir; fi; \ + test -z "$$files" || { \ + echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files '$(DESTDIR)$(libexecdir)$$dir'"; \ + $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files "$(DESTDIR)$(libexecdir)$$dir" || exit $$?; \ + } \ + ; done + +uninstall-libexecPROGRAMS: + @$(NORMAL_UNINSTALL) + @list='$(libexec_PROGRAMS)'; test -n "$(libexecdir)" || list=; \ + files=`for p in $$list; do echo "$$p"; done | \ + sed -e 'h;s,^.*/,,;s/$(EXEEXT)$$//;$(transform)' \ + -e 's/$$/$(EXEEXT)/' `; \ + test -n "$$list" || exit 0; \ + echo " ( cd '$(DESTDIR)$(libexecdir)' && rm -f" $$files ")"; \ + cd "$(DESTDIR)$(libexecdir)" && rm -f $$files + +clean-libexecPROGRAMS: + @list='$(libexec_PROGRAMS)'; test -n "$$list" || exit 0; \ + echo " rm -f" $$list; \ + rm -f $$list || exit $$?; \ + test -n "$(EXEEXT)" || exit 0; \ + list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ + echo " rm -f" $$list; \ + rm -f $$list +gnunet-dns2gns$(EXEEXT): $(gnunet_dns2gns_OBJECTS) $(gnunet_dns2gns_DEPENDENCIES) $(EXTRA_gnunet_dns2gns_DEPENDENCIES) + @rm -f gnunet-dns2gns$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(gnunet_dns2gns_OBJECTS) $(gnunet_dns2gns_LDADD) $(LIBS) +gnunet-gns$(EXEEXT): $(gnunet_gns_OBJECTS) $(gnunet_gns_DEPENDENCIES) $(EXTRA_gnunet_gns_DEPENDENCIES) @rm -f gnunet-gns$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_gns_OBJECTS) $(gnunet_gns_LDADD) $(LIBS) -gnunet-gns-fcfsd$(EXEEXT): $(gnunet_gns_fcfsd_OBJECTS) $(gnunet_gns_fcfsd_DEPENDENCIES) +gnunet-gns-fcfsd$(EXEEXT): $(gnunet_gns_fcfsd_OBJECTS) $(gnunet_gns_fcfsd_DEPENDENCIES) $(EXTRA_gnunet_gns_fcfsd_DEPENDENCIES) @rm -f gnunet-gns-fcfsd$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_gns_fcfsd_OBJECTS) $(gnunet_gns_fcfsd_LDADD) $(LIBS) -gnunet-gns-proxy$(EXEEXT): $(gnunet_gns_proxy_OBJECTS) $(gnunet_gns_proxy_DEPENDENCIES) +gnunet-gns-helper-service-w32$(EXEEXT): $(gnunet_gns_helper_service_w32_OBJECTS) $(gnunet_gns_helper_service_w32_DEPENDENCIES) $(EXTRA_gnunet_gns_helper_service_w32_DEPENDENCIES) + @rm -f gnunet-gns-helper-service-w32$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(gnunet_gns_helper_service_w32_OBJECTS) $(gnunet_gns_helper_service_w32_LDADD) $(LIBS) +gnunet-gns-proxy$(EXEEXT): $(gnunet_gns_proxy_OBJECTS) $(gnunet_gns_proxy_DEPENDENCIES) $(EXTRA_gnunet_gns_proxy_DEPENDENCIES) @rm -f gnunet-gns-proxy$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_gns_proxy_OBJECTS) $(gnunet_gns_proxy_LDADD) $(LIBS) -gnunet-service-gns$(EXEEXT): $(gnunet_service_gns_OBJECTS) $(gnunet_service_gns_DEPENDENCIES) +gnunet-service-gns$(EXEEXT): $(gnunet_service_gns_OBJECTS) $(gnunet_service_gns_DEPENDENCIES) $(EXTRA_gnunet_service_gns_DEPENDENCIES) @rm -f gnunet-service-gns$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_service_gns_OBJECTS) $(gnunet_service_gns_LDADD) $(LIBS) -test_gns_dht_delegated_lookup$(EXEEXT): $(test_gns_dht_delegated_lookup_OBJECTS) $(test_gns_dht_delegated_lookup_DEPENDENCIES) +test_gns_cname_lookup$(EXEEXT): $(test_gns_cname_lookup_OBJECTS) $(test_gns_cname_lookup_DEPENDENCIES) $(EXTRA_test_gns_cname_lookup_DEPENDENCIES) + @rm -f test_gns_cname_lookup$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_gns_cname_lookup_OBJECTS) $(test_gns_cname_lookup_LDADD) $(LIBS) +test_gns_dht_delegated_lookup$(EXEEXT): $(test_gns_dht_delegated_lookup_OBJECTS) $(test_gns_dht_delegated_lookup_DEPENDENCIES) $(EXTRA_test_gns_dht_delegated_lookup_DEPENDENCIES) @rm -f test_gns_dht_delegated_lookup$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_gns_dht_delegated_lookup_OBJECTS) $(test_gns_dht_delegated_lookup_LDADD) $(LIBS) -test_gns_dht_threepeer$(EXEEXT): $(test_gns_dht_threepeer_OBJECTS) $(test_gns_dht_threepeer_DEPENDENCIES) - @rm -f test_gns_dht_threepeer$(EXEEXT) - $(AM_V_CCLD)$(LINK) $(test_gns_dht_threepeer_OBJECTS) $(test_gns_dht_threepeer_LDADD) $(LIBS) -test_gns_max_queries$(EXEEXT): $(test_gns_max_queries_OBJECTS) $(test_gns_max_queries_DEPENDENCIES) +test_gns_dht_three_peers$(EXEEXT): $(test_gns_dht_three_peers_OBJECTS) $(test_gns_dht_three_peers_DEPENDENCIES) $(EXTRA_test_gns_dht_three_peers_DEPENDENCIES) + @rm -f test_gns_dht_three_peers$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_gns_dht_three_peers_OBJECTS) $(test_gns_dht_three_peers_LDADD) $(LIBS) +test_gns_max_queries$(EXEEXT): $(test_gns_max_queries_OBJECTS) $(test_gns_max_queries_DEPENDENCIES) $(EXTRA_test_gns_max_queries_DEPENDENCIES) @rm -f test_gns_max_queries$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_gns_max_queries_OBJECTS) $(test_gns_max_queries_LDADD) $(LIBS) -test_gns_pseu_shorten$(EXEEXT): $(test_gns_pseu_shorten_OBJECTS) $(test_gns_pseu_shorten_DEPENDENCIES) +test_gns_ns_lookup$(EXEEXT): $(test_gns_ns_lookup_OBJECTS) $(test_gns_ns_lookup_DEPENDENCIES) $(EXTRA_test_gns_ns_lookup_DEPENDENCIES) + @rm -f test_gns_ns_lookup$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_gns_ns_lookup_OBJECTS) $(test_gns_ns_lookup_LDADD) $(LIBS) +test_gns_pseu_shorten$(EXEEXT): $(test_gns_pseu_shorten_OBJECTS) $(test_gns_pseu_shorten_DEPENDENCIES) $(EXTRA_test_gns_pseu_shorten_DEPENDENCIES) @rm -f test_gns_pseu_shorten$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_gns_pseu_shorten_OBJECTS) $(test_gns_pseu_shorten_LDADD) $(LIBS) -test_gns_simple_delegated_lookup$(EXEEXT): $(test_gns_simple_delegated_lookup_OBJECTS) $(test_gns_simple_delegated_lookup_DEPENDENCIES) +test_gns_revocation$(EXEEXT): $(test_gns_revocation_OBJECTS) $(test_gns_revocation_DEPENDENCIES) $(EXTRA_test_gns_revocation_DEPENDENCIES) + @rm -f test_gns_revocation$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_gns_revocation_OBJECTS) $(test_gns_revocation_LDADD) $(LIBS) +test_gns_simple_delegated_lookup$(EXEEXT): $(test_gns_simple_delegated_lookup_OBJECTS) $(test_gns_simple_delegated_lookup_DEPENDENCIES) $(EXTRA_test_gns_simple_delegated_lookup_DEPENDENCIES) @rm -f test_gns_simple_delegated_lookup$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_gns_simple_delegated_lookup_OBJECTS) $(test_gns_simple_delegated_lookup_LDADD) $(LIBS) -test_gns_simple_get_authority$(EXEEXT): $(test_gns_simple_get_authority_OBJECTS) $(test_gns_simple_get_authority_DEPENDENCIES) +test_gns_simple_get_authority$(EXEEXT): $(test_gns_simple_get_authority_OBJECTS) $(test_gns_simple_get_authority_DEPENDENCIES) $(EXTRA_test_gns_simple_get_authority_DEPENDENCIES) @rm -f test_gns_simple_get_authority$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_gns_simple_get_authority_OBJECTS) $(test_gns_simple_get_authority_LDADD) $(LIBS) -test_gns_simple_lookup$(EXEEXT): $(test_gns_simple_lookup_OBJECTS) $(test_gns_simple_lookup_DEPENDENCIES) +test_gns_simple_lookup$(EXEEXT): $(test_gns_simple_lookup_OBJECTS) $(test_gns_simple_lookup_DEPENDENCIES) $(EXTRA_test_gns_simple_lookup_DEPENDENCIES) @rm -f test_gns_simple_lookup$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_gns_simple_lookup_OBJECTS) $(test_gns_simple_lookup_LDADD) $(LIBS) -test_gns_simple_mx_lookup$(EXEEXT): $(test_gns_simple_mx_lookup_OBJECTS) $(test_gns_simple_mx_lookup_DEPENDENCIES) +test_gns_simple_mx_lookup$(EXEEXT): $(test_gns_simple_mx_lookup_OBJECTS) $(test_gns_simple_mx_lookup_DEPENDENCIES) $(EXTRA_test_gns_simple_mx_lookup_DEPENDENCIES) @rm -f test_gns_simple_mx_lookup$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_gns_simple_mx_lookup_OBJECTS) $(test_gns_simple_mx_lookup_LDADD) $(LIBS) -test_gns_simple_shorten$(EXEEXT): $(test_gns_simple_shorten_OBJECTS) $(test_gns_simple_shorten_DEPENDENCIES) +test_gns_simple_shorten$(EXEEXT): $(test_gns_simple_shorten_OBJECTS) $(test_gns_simple_shorten_DEPENDENCIES) $(EXTRA_test_gns_simple_shorten_DEPENDENCIES) @rm -f test_gns_simple_shorten$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_gns_simple_shorten_OBJECTS) $(test_gns_simple_shorten_LDADD) $(LIBS) -test_gns_simple_zkey_lookup$(EXEEXT): $(test_gns_simple_zkey_lookup_OBJECTS) $(test_gns_simple_zkey_lookup_DEPENDENCIES) +test_gns_simple_srv_lookup$(EXEEXT): $(test_gns_simple_srv_lookup_OBJECTS) $(test_gns_simple_srv_lookup_DEPENDENCIES) $(EXTRA_test_gns_simple_srv_lookup_DEPENDENCIES) + @rm -f test_gns_simple_srv_lookup$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_gns_simple_srv_lookup_OBJECTS) $(test_gns_simple_srv_lookup_LDADD) $(LIBS) +test_gns_simple_zkey_lookup$(EXEEXT): $(test_gns_simple_zkey_lookup_OBJECTS) $(test_gns_simple_zkey_lookup_DEPENDENCIES) $(EXTRA_test_gns_simple_zkey_lookup_DEPENDENCIES) @rm -f test_gns_simple_zkey_lookup$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_gns_simple_zkey_lookup_OBJECTS) $(test_gns_simple_zkey_lookup_LDADD) $(LIBS) +w32nsp-install$(EXEEXT): $(w32nsp_install_OBJECTS) $(w32nsp_install_DEPENDENCIES) $(EXTRA_w32nsp_install_DEPENDENCIES) + @rm -f w32nsp-install$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(w32nsp_install_OBJECTS) $(w32nsp_install_LDADD) $(LIBS) +w32nsp-resolve$(EXEEXT): $(w32nsp_resolve_OBJECTS) $(w32nsp_resolve_DEPENDENCIES) $(EXTRA_w32nsp_resolve_DEPENDENCIES) + @rm -f w32nsp-resolve$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(w32nsp_resolve_OBJECTS) $(w32nsp_resolve_LDADD) $(LIBS) +w32nsp-uninstall$(EXEEXT): $(w32nsp_uninstall_OBJECTS) $(w32nsp_uninstall_DEPENDENCIES) $(EXTRA_w32nsp_uninstall_DEPENDENCIES) + @rm -f w32nsp-uninstall$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(w32nsp_uninstall_OBJECTS) $(w32nsp_uninstall_LDADD) $(LIBS) +install-binSCRIPTS: $(bin_SCRIPTS) + @$(NORMAL_INSTALL) + @list='$(bin_SCRIPTS)'; test -n "$(bindir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(bindir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(bindir)" || exit 1; \ + fi; \ + for p in $$list; do \ + if test -f "$$p"; then d=; else d="$(srcdir)/"; fi; \ + if test -f "$$d$$p"; then echo "$$d$$p"; echo "$$p"; else :; fi; \ + done | \ + sed -e 'p;s,.*/,,;n' \ + -e 'h;s|.*|.|' \ + -e 'p;x;s,.*/,,;$(transform)' | sed 'N;N;N;s,\n, ,g' | \ + $(AWK) 'BEGIN { files["."] = ""; dirs["."] = 1; } \ + { d=$$3; if (dirs[d] != 1) { print "d", d; dirs[d] = 1 } \ + if ($$2 == $$4) { files[d] = files[d] " " $$1; \ + if (++n[d] == $(am__install_max)) { \ + print "f", d, files[d]; n[d] = 0; files[d] = "" } } \ + else { print "f", d "/" $$4, $$1 } } \ + END { for (d in files) print "f", d, files[d] }' | \ + while read type dir files; do \ + if test "$$dir" = .; then dir=; else dir=/$$dir; fi; \ + test -z "$$files" || { \ + echo " $(INSTALL_SCRIPT) $$files '$(DESTDIR)$(bindir)$$dir'"; \ + $(INSTALL_SCRIPT) $$files "$(DESTDIR)$(bindir)$$dir" || exit $$?; \ + } \ + ; done + +uninstall-binSCRIPTS: + @$(NORMAL_UNINSTALL) + @list='$(bin_SCRIPTS)'; test -n "$(bindir)" || exit 0; \ + files=`for p in $$list; do echo "$$p"; done | \ + sed -e 's,.*/,,;$(transform)'`; \ + dir='$(DESTDIR)$(bindir)'; $(am__uninstall_files_from_dir) mostlyclean-compile: -rm -f *.$(OBJEXT) @@ -943,47 +1310,55 @@ distclean-compile: -rm -f *.tab.c @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gns_api.Plo@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gns_common.Plo@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-dns2gns.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-gns-fcfsd.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-gns-helper-service-w32.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-gns-proxy.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-gns.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-service-gns.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-service-gns_interceptor.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-service-gns_resolver.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/plugin_block_gns.Plo@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_gns_cname_lookup.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_gns_dht_delegated_lookup.Po@am__quote@ -@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_gns_dht_threepeer.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_gns_dht_three_peers.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_gns_max_queries.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_gns_ns_lookup.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_gns_pseu_shorten.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_gns_revocation.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_gns_simple_delegated_lookup.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_gns_simple_get_authority.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_gns_simple_lookup.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_gns_simple_mx_lookup.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_gns_simple_shorten.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_gns_simple_srv_lookup.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_gns_simple_zkey_lookup.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/w32nsp-install.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/w32nsp-resolve.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/w32nsp-uninstall.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/w32nsp.Plo@am__quote@ .c.o: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c $< .c.obj: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'` @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c `$(CYGPATH_W) '$<'` +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c `$(CYGPATH_W) '$<'` .c.lo: @am__fastdepCC_TRUE@ $(AM_V_CC)$(LTCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LTCOMPILE) -c -o $@ $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LTCOMPILE) -c -o $@ $< mostlyclean-libtool: -rm -f *.lo @@ -992,8 +1367,11 @@ clean-libtool: -rm -rf .libs _libs install-pkgcfgDATA: $(pkgcfg_DATA) @$(NORMAL_INSTALL) - test -z "$(pkgcfgdir)" || $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" @list='$(pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(pkgcfgdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" || exit 1; \ + fi; \ for p in $$list; do \ if test -f "$$p"; then d=; else d="$(srcdir)/"; fi; \ echo "$$d$$p"; \ @@ -1007,9 +1385,7 @@ uninstall-pkgcfgDATA: @$(NORMAL_UNINSTALL) @list='$(pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ files=`for p in $$list; do echo $$p; done | sed -e 's|^.*/||'`; \ - test -n "$$files" || exit 0; \ - echo " ( cd '$(DESTDIR)$(pkgcfgdir)' && rm -f" $$files ")"; \ - cd "$(DESTDIR)$(pkgcfgdir)" && rm -f $$files + dir='$(DESTDIR)$(pkgcfgdir)'; $(am__uninstall_files_from_dir) # This directory's subdirectories are mostly independent; you can cd # into them and run `make' without going through this Makefile. @@ -1227,14 +1603,15 @@ check-TESTS: $(TESTS) fi; \ dashes=`echo "$$dashes" | sed s/./=/g`; \ if test "$$failed" -eq 0; then \ - echo "$$grn$$dashes"; \ + col="$$grn"; \ else \ - echo "$$red$$dashes"; \ + col="$$red"; \ fi; \ - echo "$$banner"; \ - test -z "$$skipped" || echo "$$skipped"; \ - test -z "$$report" || echo "$$report"; \ - echo "$$dashes$$std"; \ + echo "$${col}$$dashes$${std}"; \ + echo "$${col}$$banner$${std}"; \ + test -z "$$skipped" || echo "$${col}$$skipped$${std}"; \ + test -z "$$report" || echo "$${col}$$report$${std}"; \ + echo "$${col}$$dashes$${std}"; \ test "$$failed" -eq 0; \ else :; fi @@ -1270,13 +1647,10 @@ distdir: $(DISTFILES) done @list='$(DIST_SUBDIRS)'; for subdir in $$list; do \ if test "$$subdir" = .; then :; else \ - test -d "$(distdir)/$$subdir" \ - || $(MKDIR_P) "$(distdir)/$$subdir" \ - || exit 1; \ - fi; \ - done - @list='$(DIST_SUBDIRS)'; for subdir in $$list; do \ - if test "$$subdir" = .; then :; else \ + $(am__make_dryrun) \ + || test -d "$(distdir)/$$subdir" \ + || $(MKDIR_P) "$(distdir)/$$subdir" \ + || exit 1; \ dir1=$$subdir; dir2="$(distdir)/$$subdir"; \ $(am__relativize); \ new_distdir=$$reldir; \ @@ -1300,12 +1674,12 @@ check-am: all-am $(MAKE) $(AM_MAKEFLAGS) $(check_PROGRAMS) $(MAKE) $(AM_MAKEFLAGS) check-TESTS check: check-recursive -all-am: Makefile $(LTLIBRARIES) $(PROGRAMS) $(DATA) +all-am: Makefile $(LTLIBRARIES) $(PROGRAMS) $(SCRIPTS) $(DATA) install-binPROGRAMS: install-libLTLIBRARIES installdirs: installdirs-recursive installdirs-am: - for dir in "$(DESTDIR)$(libdir)" "$(DESTDIR)$(plugindir)" "$(DESTDIR)$(bindir)" "$(DESTDIR)$(pkgcfgdir)"; do \ + for dir in "$(DESTDIR)$(libdir)" "$(DESTDIR)$(plugindir)" "$(DESTDIR)$(bindir)" "$(DESTDIR)$(libexecdir)" "$(DESTDIR)$(bindir)" "$(DESTDIR)$(pkgcfgdir)"; do \ test -z "$$dir" || $(MKDIR_P) "$$dir"; \ done install: install-recursive @@ -1318,10 +1692,15 @@ install-am: all-am installcheck: installcheck-recursive install-strip: - $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ - install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ - `test -z '$(STRIP)' || \ - echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi mostlyclean-generic: clean-generic: @@ -1336,8 +1715,8 @@ maintainer-clean-generic: clean: clean-recursive clean-am: clean-binPROGRAMS clean-checkPROGRAMS clean-generic \ - clean-libLTLIBRARIES clean-libtool clean-pluginLTLIBRARIES \ - mostlyclean-am + clean-libLTLIBRARIES clean-libexecPROGRAMS clean-libtool \ + clean-pluginLTLIBRARIES mostlyclean-am distclean: distclean-recursive -rm -rf ./$(DEPDIR) @@ -1363,7 +1742,8 @@ install-dvi: install-dvi-recursive install-dvi-am: -install-exec-am: install-binPROGRAMS install-libLTLIBRARIES +install-exec-am: install-binPROGRAMS install-binSCRIPTS \ + install-libLTLIBRARIES install-libexecPROGRAMS install-html: install-html-recursive @@ -1403,7 +1783,8 @@ ps: ps-recursive ps-am: -uninstall-am: uninstall-binPROGRAMS uninstall-libLTLIBRARIES \ +uninstall-am: uninstall-binPROGRAMS uninstall-binSCRIPTS \ + uninstall-libLTLIBRARIES uninstall-libexecPROGRAMS \ uninstall-pkgcfgDATA uninstall-pluginLTLIBRARIES .MAKE: $(RECURSIVE_CLEAN_TARGETS) $(RECURSIVE_TARGETS) check-am \ @@ -1412,13 +1793,14 @@ uninstall-am: uninstall-binPROGRAMS uninstall-libLTLIBRARIES \ .PHONY: $(RECURSIVE_CLEAN_TARGETS) $(RECURSIVE_TARGETS) CTAGS GTAGS \ all all-am check check-TESTS check-am clean clean-binPROGRAMS \ clean-checkPROGRAMS clean-generic clean-libLTLIBRARIES \ - clean-libtool clean-pluginLTLIBRARIES ctags ctags-recursive \ - distclean distclean-compile distclean-generic \ - distclean-libtool distclean-tags distdir dvi dvi-am html \ - html-am info info-am install install-am install-binPROGRAMS \ - install-data install-data-am install-dvi install-dvi-am \ - install-exec install-exec-am install-html install-html-am \ - install-info install-info-am install-libLTLIBRARIES \ + clean-libexecPROGRAMS clean-libtool clean-pluginLTLIBRARIES \ + ctags ctags-recursive distclean distclean-compile \ + distclean-generic distclean-libtool distclean-tags distdir dvi \ + dvi-am html html-am info info-am install install-am \ + install-binPROGRAMS install-binSCRIPTS install-data \ + install-data-am install-dvi install-dvi-am install-exec \ + install-exec-am install-html install-html-am install-info \ + install-info-am install-libLTLIBRARIES install-libexecPROGRAMS \ install-man install-pdf install-pdf-am install-pkgcfgDATA \ install-pluginLTLIBRARIES install-ps install-ps-am \ install-strip installcheck installcheck-am installdirs \ @@ -1426,9 +1808,21 @@ uninstall-am: uninstall-binPROGRAMS uninstall-libLTLIBRARIES \ mostlyclean mostlyclean-compile mostlyclean-generic \ mostlyclean-libtool pdf pdf-am ps ps-am tags tags-recursive \ uninstall uninstall-am uninstall-binPROGRAMS \ - uninstall-libLTLIBRARIES uninstall-pkgcfgDATA \ + uninstall-binSCRIPTS uninstall-libLTLIBRARIES \ + uninstall-libexecPROGRAMS uninstall-pkgcfgDATA \ uninstall-pluginLTLIBRARIES + #test_gns_proxy + +#Build stub api +#libgnunetnamestore_la_SOURCES = \ +# namestore_stub_api.c +#libgnunetnamestore_la_LIBADD = \ +# $(top_builddir)/src/util/libgnunetutil.la $(XLIB) +#libgnunetnamestore_la_LDFLAGS = \ +# $(GN_LIB_LDFLAGS) +#libgnunetnamestore_la_DEPENDENCIES = \ +# $(top_builddir)/src/util/libgnunetutil.la # Tell versions [3.59,3.63) of GNU make to not export all variables. # Otherwise a system limit (for SysV at least) may be exceeded. diff --git a/src/gns/gns-helper-service-w32.conf b/src/gns/gns-helper-service-w32.conf new file mode 100644 index 0000000..4865217 --- /dev/null +++ b/src/gns/gns-helper-service-w32.conf @@ -0,0 +1,4 @@ +[gns-helper-service-w32] +AUTOSTART = YES +BINARY = gnunet-gns-helper-service-w32 +PORT = 5353 diff --git a/src/gns/gns.conf.in b/src/gns/gns.conf.in index 80fb8c8..a6075f3 100644 --- a/src/gns/gns.conf.in +++ b/src/gns/gns.conf.in @@ -2,23 +2,72 @@ AUTOSTART = YES HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-gns UNIXPATH = /tmp/gnunet-service-gns.sock +@UNIXONLY@PORT = 2102 + +# Where to store the key for the Master zone ZONEKEY = $SERVICEHOME/gns/zonekey.zkey + +# Where to store the key for the Private zone +PRIVATE_ZONEKEY = $SERVICEHOME/gns/zonekey_priv.zkey + +# Where to store the key for the Shorten zone +SHORTEN_ZONEKEY = $SERVICEHOME/gns/zonekey_short.zkey + +# Should we hijack DNS queries using the Linux firewall? +# (this only works on GNU/Linux systems) HIJACK_DNS = NO + +# Automatically import PKEYs we learn into the shorten zone? AUTO_IMPORT_PKEY = YES + +# When we automatically import PKEYs into shorten zone, require confirmation +# before they become active? (Not useful right now as the GUI to confirm +# doesn't exist) AUTO_IMPORT_CONFIRMATION_REQ = NO + +# How many queries is GADS allowed to perform in the background at the same time? MAX_PARALLEL_BACKGROUND_QUERIES = 25 -DEFAULT_LOOKUP_TIMEOUT = 10 -RECORD_PUT_INTERVAL = 60 -ZONE_PUT_INTERVAL = 900 + +# When do queries fail with timeout? +DEFAULT_LOOKUP_TIMEOUT = 10 s + +# How frequently do we try to publish our full zone? +ZONE_PUBLISH_TIME_WINDOW = 4 h + +# PREFIX = valgrind --leak-check=full --track-origins=yes + +[gns-proxy] +BINARY = gnunet-gns-proxy +AUTOSTART = NO + +# Where is the certificate for the GNS proxy stored? +PROXY_CACERT = $SERVICEHOME/gns/gnsCAcert.pem +PROXY_UNIXPATH = /tmp/gnunet-gns-proxy.sock + [fcfsd] +# Name of the fcfs binary (for ARM) +BINARY = gnunet-gns-fcfsd +AUTOSTART = NO + +# On what port does the FCFS daemon listen for HTTP clients? HTTPPORT = 18080 + +# Where is the zone key for the FCFS zone stored? ZONEKEY = $SERVICEHOME/fcfsd/zonekey.zkey + +# For ARM, not very useful. FIXME: Dead option? HOSTNAME = localhost + +# FIXME: Dead option? HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG -BINARY = gnunet-gns-fcfsd + +[dns2gns] +BINARY = gnunet-dns2gns +AUTOSTART = NO + +# -d: DNS resolver to use, -s: suffix to use, -f: fcfs suffix to use +OPTIONS = -d 8.8.8.8 diff --git a/src/gns/gns.h b/src/gns/gns.h index 408b686..e5d48fa 100644 --- a/src/gns/gns.h +++ b/src/gns/gns.h @@ -17,9 +17,6 @@ Free Software Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */ - -#include "gnunet_gns_service.h" - /** * @file gns/gns.h * @brief IPC messages between GNS API and GNS service @@ -28,12 +25,23 @@ #ifndef GNS_H #define GNS_H -#define GNUNET_GNS_TLD "gnunet" +#include "gnunet_gns_service.h" + +/** + * Name of the GADS TLD. + */ +#define GNUNET_GNS_TLD "gads" + +/** + * Name of the zone key TLD. + */ #define GNUNET_GNS_TLD_ZKEY "zkey" -#define GNUNET_GNS_DHT_MAX_UPDATE_INTERVAL 3600 -#define MAX_DNS_LABEL_LENGTH 63 -#define MAX_DNS_NAME_LENGTH 253 +/** + * TLD name used to indicate relative names. + */ +#define GNUNET_GNS_TLD_PLUS "+" + GNUNET_NETWORK_STRUCT_BEGIN @@ -43,7 +51,7 @@ GNUNET_NETWORK_STRUCT_BEGIN struct GNUNET_GNS_ClientLookupMessage { /** - * Header of type GNUNET_MESSAGE_TYPE_GNS_CLIENT_LOOKUP + * Header of type GNUNET_MESSAGE_TYPE_GNS_CLIENT_LOOKUP */ struct GNUNET_MessageHeader header; @@ -52,20 +60,32 @@ struct GNUNET_GNS_ClientLookupMessage */ uint32_t id GNUNET_PACKED; + /** + * If use_default_zone is empty this zone is used for lookup + */ + struct GNUNET_CRYPTO_ShortHashCode zone; + + /** + * Only check cached results + */ + uint32_t only_cached GNUNET_PACKED; + /** * Should we look up in the default zone? */ uint32_t use_default_zone GNUNET_PACKED; /** - * If use_default_zone is empty this zone is used for lookup + * Is a shorten key attached? */ - struct GNUNET_CRYPTO_ShortHashCode zone; + uint32_t have_key GNUNET_PACKED; /** * the type of record to look up */ - enum GNUNET_GNS_RecordType type; + /* enum GNUNET_GNS_RecordType */ uint32_t type; + + /* Followed by the key for shorten (optional) see have_key */ /* Followed by the name to look up */ }; @@ -91,18 +111,18 @@ struct GNUNET_GNS_ClientLookupResultMessage */ uint32_t rd_count; - // FIXME: what format has a GNS_Record? /* followed by rd_count GNUNET_NAMESTORE_RecordData structs*/ }; + /** * Message from client to GNS service to shorten names. */ struct GNUNET_GNS_ClientShortenMessage { /** - * Header of type GNUNET_MESSAGE_TYPE_GNS_CLIENT_SHORTEN + * Header of type GNUNET_MESSAGE_TYPE_GNS_CLIENT_SHORTEN */ struct GNUNET_MessageHeader header; @@ -112,15 +132,25 @@ struct GNUNET_GNS_ClientShortenMessage uint32_t id GNUNET_PACKED; /** - * Should we look up in the default zone? + * If use_default_zone is empty this zone is used for lookup */ - uint32_t use_default_zone GNUNET_PACKED; + struct GNUNET_CRYPTO_ShortHashCode zone; /** - * If use_default_zone is empty this zone is used for lookup + * Shorten zone */ - struct GNUNET_CRYPTO_ShortHashCode zone; + struct GNUNET_CRYPTO_ShortHashCode shorten_zone; + /** + * Private zone + */ + struct GNUNET_CRYPTO_ShortHashCode private_zone; + + /** + * Should we look up in the default zone? + */ + uint32_t use_default_zone GNUNET_PACKED; + /* Followed by the name to shorten up */ }; @@ -131,7 +161,7 @@ struct GNUNET_GNS_ClientShortenMessage struct GNUNET_GNS_ClientShortenResultMessage { /** - * Header of type GNUNET_MESSAGE_TYPE_GNS_CLIENT_SHORTEN_RESULT + * Header of type GNUNET_MESSAGE_TYPE_GNS_CLIENT_SHORTEN_RESULT */ struct GNUNET_MessageHeader header; @@ -144,13 +174,14 @@ struct GNUNET_GNS_ClientShortenResultMessage }; + /** * Message from client to GNS service to lookup an authority of a name. */ struct GNUNET_GNS_ClientGetAuthMessage { /** - * Header of type GNUNET_MESSAGE_TYPE_GNS_CLIENT_GET_AUTH + * Header of type GNUNET_MESSAGE_TYPE_GNS_CLIENT_GET_AUTH */ struct GNUNET_MessageHeader header; @@ -169,7 +200,7 @@ struct GNUNET_GNS_ClientGetAuthMessage struct GNUNET_GNS_ClientGetAuthResultMessage { /** - * Header of type GNUNET_MESSAGE_TYPE_GNS_CLIENT_GET_AUTH_RESULT + * Header of type GNUNET_MESSAGE_TYPE_GNS_CLIENT_GET_AUTH_RESULT */ struct GNUNET_MessageHeader header; @@ -181,6 +212,7 @@ struct GNUNET_GNS_ClientGetAuthResultMessage /* followed by the authority part of the name or '\0' for no result*/ }; + GNUNET_NETWORK_STRUCT_END #endif diff --git a/src/gns/gns_api.c b/src/gns/gns_api.c index a92280f..1e3cb01 100644 --- a/src/gns/gns_api.c +++ b/src/gns/gns_api.c @@ -1,6 +1,6 @@ /* This file is part of GNUnet. - (C) 2009, 2010 Christian Grothoff (and other contributing authors) + (C) 2009, 2010, 2012 Christian Grothoff (and other contributing authors) GNUnet is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published @@ -17,14 +17,12 @@ Free Software Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */ - /** - * * @file gns/gns_api.c * @brief library to access the GNS service * @author Martin Schanzenbach + * @author Christian Grothoff */ - #include "platform.h" #include "gnunet_util_lib.h" #include "gnunet_constants.h" @@ -35,47 +33,119 @@ #include "gns.h" #include "gnunet_gns_service.h" -/* TODO into gnunet_protocols */ -#define GNUNET_MESSAGE_TYPE_GNS_LOOKUP 23 -#define GNUNET_MESSAGE_TYPE_GNS_LOOKUP_RESULT 24 -#define GNUNET_MESSAGE_TYPE_GNS_SHORTEN 25 -#define GNUNET_MESSAGE_TYPE_GNS_SHORTEN_RESULT 26 -#define GNUNET_MESSAGE_TYPE_GNS_GET_AUTH 27 -#define GNUNET_MESSAGE_TYPE_GNS_GET_AUTH_RESULT 28 /** - * A QueueEntry. + * Handle to a lookup request */ -struct GNUNET_GNS_QueueEntry +struct GNUNET_GNS_LookupRequest { + /** * DLL */ - struct GNUNET_GNS_QueueEntry *next; + struct GNUNET_GNS_LookupRequest *next; /** * DLL */ - struct GNUNET_GNS_QueueEntry *prev; + struct GNUNET_GNS_LookupRequest *prev; + + /** + * handle to gns + */ + struct GNUNET_GNS_Handle *gns_handle; + + /** + * processor to call on lookup result + */ + GNUNET_GNS_LookupResultProcessor lookup_proc; - /* request id */ + /** + * processor closure + */ + void *proc_cls; + + /** + * request id + */ uint32_t r_id; + +}; + + +/** + * Handle to a shorten request + */ +struct GNUNET_GNS_ShortenRequest +{ + /** + * DLL + */ + struct GNUNET_GNS_ShortenRequest *next; - /* handle to gns */ + /** + * DLL + */ + struct GNUNET_GNS_ShortenRequest *prev; + + /** + * handle to gns + */ struct GNUNET_GNS_Handle *gns_handle; - /* processor to call on shorten result */ + /** + * processor to call on shorten result + */ GNUNET_GNS_ShortenResultProcessor shorten_proc; - /* processor to call on lookup result */ - GNUNET_GNS_LookupResultProcessor lookup_proc; + /** + * processor closure + */ + void *proc_cls; - /* processor to call on authority lookup result */ + /** + * request id + */ + uint32_t r_id; + +}; + + +/** + * Handle to GetAuthorityRequest + */ +struct GNUNET_GNS_GetAuthRequest +{ + /** + * DLL + */ + struct GNUNET_GNS_GetAuthRequest *next; + + /** + * DLL + */ + struct GNUNET_GNS_GetAuthRequest *prev; + + /** + * handle to gns + */ + struct GNUNET_GNS_Handle *gns_handle; + + /** + * processor to call on authority lookup result + */ GNUNET_GNS_GetAuthResultProcessor auth_proc; - /* processor closure */ + /** + * processor closure + */ void *proc_cls; + /** + * request id + */ + uint32_t r_id; + }; @@ -99,6 +169,18 @@ struct PendingMessage */ size_t size; + /** + * request id + */ + uint32_t r_id; + + /** + * This message has been transmitted. GNUNET_NO if the message is + * in the "pending" DLL, GNUNET_YES if it has been transmitted to + * the service via the current client connection. + */ + int transmitted; + }; @@ -123,8 +205,6 @@ struct GNUNET_GNS_Handle */ struct GNUNET_CLIENT_TransmitHandle *th; - uint32_t r_id; - /** * Head of linked list of shorten messages we would like to transmit. */ @@ -138,49 +218,56 @@ struct GNUNET_GNS_Handle /** * Head of linked list of shorten messages we would like to transmit. */ - struct GNUNET_GNS_QueueEntry *shorten_head; + struct GNUNET_GNS_ShortenRequest *shorten_head; /** * Tail of linked list of shorten messages we would like to transmit. */ - struct GNUNET_GNS_QueueEntry *shorten_tail; + struct GNUNET_GNS_ShortenRequest *shorten_tail; /** * Head of linked list of lookup messages we would like to transmit. */ - struct GNUNET_GNS_QueueEntry *lookup_head; + struct GNUNET_GNS_LookupRequest *lookup_head; /** * Tail of linked list of lookup messages we would like to transmit. */ - struct GNUNET_GNS_QueueEntry *lookup_tail; + struct GNUNET_GNS_LookupRequest *lookup_tail; /** * Head of linked list of authority lookup messages we would like to transmit. */ - struct GNUNET_GNS_QueueEntry *get_auth_head; + struct GNUNET_GNS_GetAuthRequest *get_auth_head; /** * Tail of linked list of authority lookup messages we would like to transmit. */ - struct GNUNET_GNS_QueueEntry *get_auth_tail; + struct GNUNET_GNS_GetAuthRequest *get_auth_tail; /** * Reconnect task */ GNUNET_SCHEDULER_TaskIdentifier reconnect_task; + + /** + * How long do we wait until we try to reconnect? + */ + struct GNUNET_TIME_Relative reconnect_backoff; + /** + * Request Id generator. Incremented by one for each request. + */ + uint32_t r_id_gen; + /** * Did we start our receive loop yet? */ int in_receive; - /** - * Reconnect necessary - */ - int reconnect; }; + /** * Try to send messages from list of messages to send * @param handle GNS_Handle @@ -192,18 +279,20 @@ process_pending_messages (struct GNUNET_GNS_Handle *handle); /** * Reconnect to GNS service. * - * @param h the handle to the namestore service + * @param handle the handle to the GNS service */ static void -reconnect (struct GNUNET_GNS_Handle *h) +reconnect (struct GNUNET_GNS_Handle *handle) { - GNUNET_assert (NULL == h->client); - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "Trying to connect to GNS...\n"); - h->client = GNUNET_CLIENT_connect ("gns", h->cfg); - GNUNET_assert (NULL != h->client); + GNUNET_assert (NULL == handle->client); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Trying to connect to GNS\n"); + handle->client = GNUNET_CLIENT_connect ("gns", handle->cfg); + GNUNET_assert (NULL != handle->client); + process_pending_messages (handle); } + /** * Reconnect to GNS * @@ -213,35 +302,78 @@ reconnect (struct GNUNET_GNS_Handle *h) static void reconnect_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { - struct GNUNET_GNS_Handle *h = cls; + struct GNUNET_GNS_Handle *handle = cls; - h->reconnect_task = GNUNET_SCHEDULER_NO_TASK; - reconnect (h); + handle->reconnect_task = GNUNET_SCHEDULER_NO_TASK; + reconnect (handle); } /** * Disconnect from service and then reconnect. * - * @param h our handle + * @param handle our handle */ static void -force_reconnect (struct GNUNET_GNS_Handle *h) +force_reconnect (struct GNUNET_GNS_Handle *handle) { - h->reconnect = GNUNET_NO; - GNUNET_CLIENT_disconnect (h->client); - h->client = NULL; - h->reconnect_task = GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_SECONDS, + struct GNUNET_GNS_ShortenRequest *st; + struct GNUNET_GNS_LookupRequest *lh; + struct GNUNET_GNS_GetAuthRequest *ga; + struct PendingMessage *p; + + GNUNET_CLIENT_disconnect (handle->client); + handle->client = NULL; + handle->in_receive = GNUNET_NO; + for (st = handle->shorten_head; NULL != st; st = st->next) + { + p = (struct PendingMessage *) &st[1]; + if (GNUNET_NO == p->transmitted) + continue; + p->transmitted = GNUNET_NO; + GNUNET_CONTAINER_DLL_insert (handle->pending_head, + handle->pending_tail, + p); + } + for (lh = handle->lookup_head; NULL != lh; lh = lh->next) + { + p = (struct PendingMessage *) &lh[1]; + if (GNUNET_NO == p->transmitted) + continue; + p->transmitted = GNUNET_NO; + GNUNET_CONTAINER_DLL_insert (handle->pending_head, + handle->pending_tail, + p); + } + for (ga = handle->get_auth_head; NULL != ga; ga = ga->next) + { + p = (struct PendingMessage *) &ga[1]; + if (GNUNET_NO == p->transmitted) + continue; + p->transmitted = GNUNET_NO; + GNUNET_CONTAINER_DLL_insert (handle->pending_head, + handle->pending_tail, + p); + } + handle->reconnect_backoff = GNUNET_TIME_STD_BACKOFF (handle->reconnect_backoff); + handle->reconnect_task = GNUNET_SCHEDULER_add_delayed (handle->reconnect_backoff, &reconnect_task, - h); + handle); } + /** * Transmit the next pending message, called by notify_transmit_ready + * + * @param cls the closure + * @param size size of pending data + * @param buf buffer with pending data + * @return size data transmitted */ static size_t transmit_pending (void *cls, size_t size, void *buf); + /** * Handler for messages received from the GNS service * @@ -251,93 +383,92 @@ transmit_pending (void *cls, size_t size, void *buf); static void process_message (void *cls, const struct GNUNET_MessageHeader *msg); + /** * Try to send messages from list of messages to send + * + * @param handle the GNS handle */ static void process_pending_messages (struct GNUNET_GNS_Handle *handle) { - struct PendingMessage *p; + struct PendingMessage *p = handle->pending_head; - if (handle->client == NULL) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "process_pending_messages called, but client is null\n"); - return; - } - - if (handle->th != NULL) - return; - - if (NULL == (p = handle->pending_head)) - return; - - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "Trying to transmit %d bytes...\n", p->size); + if (NULL == handle->client) + return; /* wait for reconnect */ + if (NULL != handle->th) + return; /* transmission request already pending */ + while ((NULL != p) && (p->transmitted == GNUNET_YES)) + p = p->next; + if (NULL == p) + return; /* no messages pending */ + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Trying to transmit %u bytes\n", + (unsigned int) p->size); handle->th = GNUNET_CLIENT_notify_transmit_ready (handle->client, p->size, GNUNET_TIME_UNIT_FOREVER_REL, GNUNET_NO, &transmit_pending, handle); - if (NULL != handle->th) - return; - - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "notify_transmit_ready returned NULL!\n"); + GNUNET_break (NULL != handle->th); } /** * Transmit the next pending message, called by notify_transmit_ready + * + * @param cls the closure + * @param size size of pending data + * @param buf buffer with pending data + * @return size data transmitted */ static size_t transmit_pending (void *cls, size_t size, void *buf) { struct GNUNET_GNS_Handle *handle = cls; + char *cbuf = buf; struct PendingMessage *p; size_t tsize; - char *cbuf; handle->th = NULL; - - if ((size == 0) || (buf == NULL)) + if ((0 == size) || (NULL == buf)) { GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Transmission to GNS service failed!\n"); - force_reconnect(handle); + "Transmission to GNS service failed!\n"); + force_reconnect (handle); return 0; - } - - tsize = 0; - cbuf = buf; - + } if (NULL == (p = handle->pending_head)) return 0; + tsize = 0; while ((NULL != (p = handle->pending_head)) && (p->size <= size)) { memcpy (&cbuf[tsize], &p[1], p->size); tsize += p->size; size -= p->size; - GNUNET_CONTAINER_DLL_remove (handle->pending_head, handle->pending_tail, p); + p->transmitted = GNUNET_YES; + GNUNET_CONTAINER_DLL_remove (handle->pending_head, + handle->pending_tail, + p); if (GNUNET_YES != handle->in_receive) { GNUNET_CLIENT_receive (handle->client, &process_message, handle, GNUNET_TIME_UNIT_FOREVER_REL); handle->in_receive = GNUNET_YES; } - GNUNET_free(p); } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Sending %d bytes\n", tsize); - - process_pending_messages(handle); + "Sending %u bytes\n", + (unsigned int) tsize); + process_pending_messages (handle); return tsize; } + /** * Process a given reply that might match the given * request. @@ -346,34 +477,43 @@ transmit_pending (void *cls, size_t size, void *buf) * @param msg the shorten msg received */ static void -process_shorten_reply (struct GNUNET_GNS_QueueEntry *qe, +process_shorten_reply (struct GNUNET_GNS_ShortenRequest *qe, const struct GNUNET_GNS_ClientShortenResultMessage *msg) { - struct GNUNET_GNS_Handle *h = qe->gns_handle; + struct GNUNET_GNS_Handle *handle = qe->gns_handle; + struct PendingMessage *p = (struct PendingMessage *)&qe[1]; const char *short_name; - - GNUNET_CONTAINER_DLL_remove(h->shorten_head, h->shorten_tail, qe); - - short_name = (char*)(&msg[1]); - - if (ntohs (((struct GNUNET_MessageHeader*)msg)->size) < - sizeof (struct GNUNET_GNS_ClientShortenResultMessage)) + size_t mlen; + + if (GNUNET_YES != p->transmitted) { + /* service send reply to query we never managed to send!? */ GNUNET_break (0); - force_reconnect (h); - GNUNET_free(qe); + force_reconnect (handle); return; } - + mlen = ntohs (msg->header.size); + if (ntohs (msg->header.size) == sizeof (struct GNUNET_GNS_ClientShortenResultMessage)) + { + /* service reports resolution failed */ + short_name = NULL; + } + else + { + short_name = (const char *) &msg[1]; + if ('\0' != short_name[mlen - sizeof (struct GNUNET_GNS_ClientShortenResultMessage) - 1]) + { + GNUNET_break (0); + force_reconnect (handle); + return; + } + } + GNUNET_CONTAINER_DLL_remove (handle->shorten_head, handle->shorten_tail, qe); GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received shortened reply `%s' from GNS service\n", short_name); - - GNUNET_CLIENT_receive (h->client, &process_message, h, - GNUNET_TIME_UNIT_FOREVER_REL); - qe->shorten_proc(qe->proc_cls, short_name); - GNUNET_free(qe); - + qe->shorten_proc (qe->proc_cls, short_name); + GNUNET_free (qe); } @@ -385,35 +525,45 @@ process_shorten_reply (struct GNUNET_GNS_QueueEntry *qe, * @param msg the message to process */ static void -process_get_auth_reply (struct GNUNET_GNS_QueueEntry *qe, +process_get_auth_reply (struct GNUNET_GNS_GetAuthRequest *qe, const struct GNUNET_GNS_ClientGetAuthResultMessage *msg) { - struct GNUNET_GNS_Handle *h = qe->gns_handle; + struct GNUNET_GNS_Handle *handle = qe->gns_handle; + struct PendingMessage *p = (struct PendingMessage *)&qe[1]; const char *auth_name; + size_t mlen; - GNUNET_CONTAINER_DLL_remove(h->get_auth_head, h->get_auth_tail, qe); - - auth_name = (char*)(&msg[1]); - - if (ntohs (((struct GNUNET_MessageHeader*)msg)->size) < - sizeof (struct GNUNET_GNS_ClientGetAuthResultMessage)) + if (GNUNET_YES != p->transmitted) { - GNUNET_free(qe); + /* service send reply to query we never managed to send!? */ GNUNET_break (0); - force_reconnect (h); + force_reconnect (handle); return; } - + mlen = ntohs (msg->header.size); + if (mlen == sizeof (struct GNUNET_GNS_ClientGetAuthResultMessage)) + { + auth_name = NULL; + } + else + { + auth_name = (const char*) &msg[1]; + if ('\0' != auth_name[mlen - sizeof (struct GNUNET_GNS_ClientGetAuthResultMessage) - 1]) + { + GNUNET_break (0); + force_reconnect (handle); + return; + } + } + GNUNET_CONTAINER_DLL_remove (handle->get_auth_head, handle->get_auth_tail, qe); GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received GET_AUTH reply `%s' from GNS service\n", auth_name); - - GNUNET_CLIENT_receive (h->client, &process_message, h, - GNUNET_TIME_UNIT_FOREVER_REL); - qe->auth_proc(qe->proc_cls, auth_name); - GNUNET_free(qe); - + qe->auth_proc (qe->proc_cls, auth_name); + GNUNET_free (qe); } + + /** * Process a given reply to the lookup request * @@ -421,48 +571,45 @@ process_get_auth_reply (struct GNUNET_GNS_QueueEntry *qe, * @param msg the lookup message received */ static void -process_lookup_reply (struct GNUNET_GNS_QueueEntry *qe, +process_lookup_reply (struct GNUNET_GNS_LookupRequest *qe, const struct GNUNET_GNS_ClientLookupResultMessage *msg) { - struct GNUNET_GNS_Handle *h = qe->gns_handle; - int rd_count = ntohl(msg->rd_count); - size_t len = ntohs (((struct GNUNET_MessageHeader*)msg)->size); + struct GNUNET_GNS_Handle *handle = qe->gns_handle; + struct PendingMessage *p = (struct PendingMessage *) &qe[1]; + uint32_t rd_count = ntohl (msg->rd_count); struct GNUNET_NAMESTORE_RecordData rd[rd_count]; + size_t mlen; - GNUNET_CONTAINER_DLL_remove(h->lookup_head, h->lookup_tail, qe); - - if (len < sizeof (struct GNUNET_GNS_ClientLookupResultMessage)) + if (GNUNET_YES != p->transmitted) { - GNUNET_free(qe); + /* service send reply to query we never managed to send!? */ GNUNET_break (0); - force_reconnect (h); + force_reconnect (handle); return; } - - len -= sizeof(struct GNUNET_GNS_ClientLookupResultMessage); - - GNUNET_CLIENT_receive (h->client, &process_message, h, - GNUNET_TIME_UNIT_FOREVER_REL); - if (GNUNET_SYSERR == GNUNET_NAMESTORE_records_deserialize (len, - (char*)&msg[1], + mlen = ntohs (msg->header.size); + mlen -= sizeof (struct GNUNET_GNS_ClientLookupResultMessage); + if (GNUNET_SYSERR == GNUNET_NAMESTORE_records_deserialize (mlen, + (const char*) &msg[1], rd_count, rd)) { GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "Failed to serialize lookup reply from GNS service!\n"); - qe->lookup_proc(qe->proc_cls, 0, NULL); + _("Failed to serialize lookup reply from GNS service!\n")); + qe->lookup_proc (qe->proc_cls, 0, NULL); } else - { - + { GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Received lookup reply from GNS service (count=%d)\n", - ntohl(msg->rd_count)); - qe->lookup_proc(qe->proc_cls, rd_count, rd); + "Received lookup reply from GNS service (%u records)\n", + (unsigned int) rd_count); + qe->lookup_proc (qe->proc_cls, rd_count, rd); } - GNUNET_free(qe); + GNUNET_CONTAINER_DLL_remove (handle->lookup_head, handle->lookup_tail, qe); + GNUNET_free (qe); } + /** * Handler for messages received from the GNS service * @@ -473,109 +620,82 @@ static void process_message (void *cls, const struct GNUNET_MessageHeader *msg) { struct GNUNET_GNS_Handle *handle = cls; - struct GNUNET_GNS_QueueEntry *qe; + struct GNUNET_GNS_LookupRequest *lr; + struct GNUNET_GNS_ShortenRequest *sr; + struct GNUNET_GNS_GetAuthRequest *gar; const struct GNUNET_GNS_ClientLookupResultMessage *lookup_msg; const struct GNUNET_GNS_ClientShortenResultMessage *shorten_msg; const struct GNUNET_GNS_ClientGetAuthResultMessage *get_auth_msg; - uint16_t type; uint32_t r_id; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Got message\n"); - if (msg == NULL) + if (NULL == msg) { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "Error receiving data from GNS service, reconnecting\n"); force_reconnect (handle); return; } - - type = ntohs (msg->type); - - if (type == GNUNET_MESSAGE_TYPE_GNS_LOOKUP_RESULT) + switch (ntohs (msg->type)) { + case GNUNET_MESSAGE_TYPE_GNS_LOOKUP_RESULT: GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Got lookup msg\n"); - lookup_msg = (const struct GNUNET_GNS_ClientLookupResultMessage *) msg; - r_id = ntohl (lookup_msg->id); - - if (r_id > handle->r_id) + "Got LOOKUP_RESULT msg\n"); + if (ntohs (msg->size) < sizeof (struct GNUNET_GNS_ClientLookupResultMessage)) { - /** no request found */ - GNUNET_break_op (0); - GNUNET_CLIENT_receive (handle->client, &process_message, handle, - GNUNET_TIME_UNIT_FOREVER_REL); + GNUNET_break (0); + force_reconnect (handle); return; } - - for (qe = handle->lookup_head; qe != NULL; qe = qe->next) - { - if (qe->r_id == r_id) - break; - } - if (qe) - process_lookup_reply(qe, lookup_msg); - - return; - - } - else if (type == GNUNET_MESSAGE_TYPE_GNS_SHORTEN_RESULT) - { + lookup_msg = (const struct GNUNET_GNS_ClientLookupResultMessage *) msg; + r_id = ntohl (lookup_msg->id); + for (lr = handle->lookup_head; NULL != lr; lr = lr->next) + if (lr->r_id == r_id) + { + process_lookup_reply(lr, lookup_msg); + break; + } + break; + case GNUNET_MESSAGE_TYPE_GNS_SHORTEN_RESULT: GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Got SHORTEN_RESULT msg\n"); - shorten_msg = (struct GNUNET_GNS_ClientShortenResultMessage *) msg; - - r_id = ntohl (shorten_msg->id); - - if (r_id > handle->r_id) + if (ntohs (msg->size) < sizeof (struct GNUNET_GNS_ClientShortenResultMessage)) { - /** no request found */ - GNUNET_break_op (0); - GNUNET_CLIENT_receive (handle->client, &process_message, handle, - GNUNET_TIME_UNIT_FOREVER_REL); + GNUNET_break (0); + force_reconnect (handle); return; } - - for (qe = handle->shorten_head; qe != NULL; qe = qe->next) - { - if (qe->r_id == r_id) - break; - } - if (qe) - process_shorten_reply(qe, shorten_msg); - return; - } - else if (type == GNUNET_MESSAGE_TYPE_GNS_GET_AUTH_RESULT) - { + shorten_msg = (const struct GNUNET_GNS_ClientShortenResultMessage *) msg; + r_id = ntohl (shorten_msg->id); + for (sr = handle->shorten_head; NULL != sr; sr = sr->next) + if (sr->r_id == r_id) + { + process_shorten_reply (sr, shorten_msg); + break; + } + break; + case GNUNET_MESSAGE_TYPE_GNS_GET_AUTH_RESULT: GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Got GET_AUTH_RESULT msg\n"); - get_auth_msg = (struct GNUNET_GNS_ClientGetAuthResultMessage *) msg; - - r_id = ntohl (get_auth_msg->id); - - if (r_id > handle->r_id) + if (ntohs (msg->size) < sizeof (struct GNUNET_GNS_ClientGetAuthResultMessage)) { - /** no request found */ - GNUNET_break_op (0); - GNUNET_CLIENT_receive (handle->client, &process_message, handle, - GNUNET_TIME_UNIT_FOREVER_REL); + GNUNET_break (0); + force_reconnect (handle); return; } - - for (qe = handle->get_auth_head; qe != NULL; qe = qe->next) - { - if (qe->r_id == r_id) - break; - } - if (qe) - process_get_auth_reply(qe, get_auth_msg); + get_auth_msg = (const struct GNUNET_GNS_ClientGetAuthResultMessage *) msg; + r_id = ntohl (get_auth_msg->id); + for (gar = handle->get_auth_head; NULL != gar; gar = gar->next) + if (gar->r_id == r_id) + { + process_get_auth_reply (gar, get_auth_msg); + break; + } + break; + default: + GNUNET_break (0); + force_reconnect (handle); return; } - - - if (GNUNET_YES == handle->reconnect) - force_reconnect (handle); - + GNUNET_CLIENT_receive (handle->client, &process_message, handle, + GNUNET_TIME_UNIT_FOREVER_REL); } @@ -591,13 +711,8 @@ GNUNET_GNS_connect (const struct GNUNET_CONFIGURATION_Handle *cfg) struct GNUNET_GNS_Handle *handle; handle = GNUNET_malloc (sizeof (struct GNUNET_GNS_Handle)); - handle->reconnect = GNUNET_NO; handle->cfg = cfg; reconnect (handle); - //handle->reconnect_task = GNUNET_SCHEDULER_add_now (&reconnect_task, handle); - handle->reconnect_task = GNUNET_SCHEDULER_NO_TASK; - handle->r_id = 0; - handle->in_receive = GNUNET_NO; return handle; } @@ -616,24 +731,79 @@ GNUNET_GNS_disconnect (struct GNUNET_GNS_Handle *handle) GNUNET_SCHEDULER_cancel (handle->reconnect_task); handle->reconnect_task = GNUNET_SCHEDULER_NO_TASK; } - GNUNET_free(handle); - /* disco from GNS */ + GNUNET_assert (NULL == handle->lookup_head); + GNUNET_assert (NULL == handle->shorten_head); + GNUNET_assert (NULL == handle->get_auth_head); + GNUNET_free (handle); } -/* - * Helper function to generate request ids - * - * @param h handle - * @return a new id + +/** + * Cancel pending lookup request + * + * @param lr the lookup request to cancel */ -static uint32_t -get_request_id (struct GNUNET_GNS_Handle *h) +void +GNUNET_GNS_cancel_lookup_request (struct GNUNET_GNS_LookupRequest *lr) { - uint32_t r_id = h->r_id; - h->r_id++; - return r_id; + struct PendingMessage *p = (struct PendingMessage*) &lr[1]; + + GNUNET_assert (NULL != lr->gns_handle); + if (GNUNET_NO == p->transmitted) + GNUNET_CONTAINER_DLL_remove (lr->gns_handle->pending_head, + lr->gns_handle->pending_tail, + p); + GNUNET_CONTAINER_DLL_remove (lr->gns_handle->lookup_head, + lr->gns_handle->lookup_tail, + lr); + GNUNET_free (lr); } + +/** + * Cancel pending shorten request + * + * @param sr the lookup request to cancel + */ +void +GNUNET_GNS_cancel_shorten_request (struct GNUNET_GNS_ShortenRequest *sr) +{ + struct PendingMessage *p = (struct PendingMessage*) &sr[1]; + + GNUNET_assert (NULL != sr->gns_handle); + if (GNUNET_NO == p->transmitted) + GNUNET_CONTAINER_DLL_remove (sr->gns_handle->pending_head, + sr->gns_handle->pending_tail, + p); + GNUNET_CONTAINER_DLL_remove (sr->gns_handle->shorten_head, + sr->gns_handle->shorten_tail, + sr); + GNUNET_free (sr); +} + + +/** + * Cancel pending get auth request + * + * @param gar the lookup request to cancel + */ +void +GNUNET_GNS_cancel_get_auth_request (struct GNUNET_GNS_GetAuthRequest *gar) +{ + struct PendingMessage *p = (struct PendingMessage*) &gar[1]; + + GNUNET_assert (NULL != gar->gns_handle); + if (GNUNET_NO == p->transmitted) + GNUNET_CONTAINER_DLL_remove (gar->gns_handle->pending_head, + gar->gns_handle->pending_tail, + p); + GNUNET_CONTAINER_DLL_remove (gar->gns_handle->get_auth_head, + gar->gns_handle->get_auth_tail, + gar); + GNUNET_free (gar); +} + + /** * Perform an asynchronous Lookup operation on the GNS. * @@ -641,179 +811,235 @@ get_request_id (struct GNUNET_GNS_Handle *h) * @param name the name to look up * @param zone the zone to start the resolution in * @param type the record type to look up + * @param only_cached GNUNET_YES to only check locally not DHT for performance + * @param shorten_key the private key of the shorten zone (can be NULL) * @param proc processor to call on result * @param proc_cls closure for processor - * @return handle to the get + * @return handle to the get request */ -struct GNUNET_GNS_QueueEntry * +struct GNUNET_GNS_LookupRequest* GNUNET_GNS_lookup_zone (struct GNUNET_GNS_Handle *handle, - const char * name, - struct GNUNET_CRYPTO_ShortHashCode *zone, - enum GNUNET_GNS_RecordType type, - GNUNET_GNS_LookupResultProcessor proc, - void *proc_cls) + const char *name, + struct GNUNET_CRYPTO_ShortHashCode *zone, + enum GNUNET_GNS_RecordType type, + int only_cached, + struct GNUNET_CRYPTO_RsaPrivateKey *shorten_key, + GNUNET_GNS_LookupResultProcessor proc, + void *proc_cls) { /* IPC to shorten gns names, return shorten_handle */ struct GNUNET_GNS_ClientLookupMessage *lookup_msg; - struct GNUNET_GNS_QueueEntry *qe; + struct GNUNET_GNS_LookupRequest *lr; size_t msize; struct PendingMessage *pending; + struct GNUNET_CRYPTO_RsaPrivateKeyBinaryEncoded *pkey_enc; + size_t key_len; + char* pkey_tmp; if (NULL == name) { + GNUNET_break (0); return NULL; + } + if (NULL != shorten_key) + { + pkey_enc = GNUNET_CRYPTO_rsa_encode_key (shorten_key); + GNUNET_assert (pkey_enc != NULL); + key_len = ntohs (pkey_enc->len); } - - msize = sizeof (struct GNUNET_GNS_ClientLookupMessage) + strlen(name) + 1; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Trying to lookup %s in GNS\n", name); - - qe = GNUNET_malloc(sizeof (struct GNUNET_GNS_QueueEntry)); - qe->gns_handle = handle; - qe->lookup_proc = proc; - qe->proc_cls = proc_cls; - qe->r_id = get_request_id(handle); - GNUNET_CONTAINER_DLL_insert_tail(handle->lookup_head, - handle->lookup_tail, qe); - - pending = GNUNET_malloc (sizeof (struct PendingMessage) + msize); - memset(pending, 0, (sizeof (struct PendingMessage) + msize)); - + else + { + pkey_enc = NULL; + key_len = 0; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Trying to lookup `%s' in GNS\n", + name); + msize = sizeof (struct GNUNET_GNS_ClientLookupMessage) + + key_len + strlen (name) + 1; + if (msize > UINT16_MAX) + { + GNUNET_break (0); + GNUNET_free (pkey_enc); + return NULL; + } + lr = GNUNET_malloc (sizeof (struct GNUNET_GNS_LookupRequest) + + sizeof (struct PendingMessage) + msize); + lr->gns_handle = handle; + lr->lookup_proc = proc; + lr->proc_cls = proc_cls; + lr->r_id = handle->r_id_gen++; + pending = (struct PendingMessage *)&lr[1]; pending->size = msize; + pending->r_id = lr->r_id; + GNUNET_CONTAINER_DLL_insert_tail (handle->lookup_head, + handle->lookup_tail, lr); lookup_msg = (struct GNUNET_GNS_ClientLookupMessage *) &pending[1]; lookup_msg->header.type = htons (GNUNET_MESSAGE_TYPE_GNS_LOOKUP); lookup_msg->header.size = htons (msize); - lookup_msg->id = htonl(qe->r_id); - + lookup_msg->id = htonl (lr->r_id); + lookup_msg->only_cached = htonl (only_cached); if (NULL != zone) { - lookup_msg->use_default_zone = htonl(0); - memcpy(&lookup_msg->zone, zone, sizeof(struct GNUNET_CRYPTO_ShortHashCode)); + lookup_msg->use_default_zone = htonl (GNUNET_NO); + memcpy (&lookup_msg->zone, zone, sizeof (struct GNUNET_CRYPTO_ShortHashCode)); } else { - lookup_msg->use_default_zone = htonl(1); - memset(&lookup_msg->zone, 0, sizeof(struct GNUNET_CRYPTO_ShortHashCode)); + lookup_msg->use_default_zone = htonl (GNUNET_YES); + memset (&lookup_msg->zone, 0, sizeof(struct GNUNET_CRYPTO_ShortHashCode)); + } + lookup_msg->type = htonl (type); + pkey_tmp = (char *) &lookup_msg[1]; + if (pkey_enc != NULL) + { + lookup_msg->have_key = htonl (GNUNET_YES); + memcpy (pkey_tmp, pkey_enc, key_len); } + else + lookup_msg->have_key = htonl (GNUNET_NO); + GNUNET_free_non_null (pkey_enc); + memcpy (&pkey_tmp[key_len], name, strlen (name) + 1); - lookup_msg->type = htonl(type); - - memcpy(&lookup_msg[1], name, strlen(name)); - - GNUNET_CONTAINER_DLL_insert_tail (handle->pending_head, handle->pending_tail, - pending); - + GNUNET_CONTAINER_DLL_insert_tail (handle->pending_head, + handle->pending_tail, + pending); process_pending_messages (handle); - return qe; + return lr; } + /** * Perform an asynchronous Lookup operation on the GNS. * * @param handle handle to the GNS service * @param name the name to look up * @param type the record type to look up + * @param only_cached GNUNET_YES to only check locally not DHT for performance + * @param shorten_key the private key of the shorten zone (can be NULL) * @param proc processor to call on result * @param proc_cls closure for processor - * @return handle to the get + * @return handle to the lookup request */ -struct GNUNET_GNS_QueueEntry * +struct GNUNET_GNS_LookupRequest * GNUNET_GNS_lookup (struct GNUNET_GNS_Handle *handle, - const char * name, + const char *name, enum GNUNET_GNS_RecordType type, + int only_cached, + struct GNUNET_CRYPTO_RsaPrivateKey *shorten_key, GNUNET_GNS_LookupResultProcessor proc, void *proc_cls) { - return GNUNET_GNS_lookup_zone (handle, name, NULL, type, proc, proc_cls); + return GNUNET_GNS_lookup_zone (handle, name, + NULL, + type, only_cached, + shorten_key, + proc, proc_cls); } + /** * Perform a name shortening operation on the GNS. * * @param handle handle to the GNS service * @param name the name to look up + * @param private_zone the public zone of the private zone + * @param shorten_zone the public zone of the shorten zone * @param zone the zone to start the resolution in * @param proc function to call on result * @param proc_cls closure for processor * @return handle to the operation */ -struct GNUNET_GNS_QueueEntry * +struct GNUNET_GNS_ShortenRequest* GNUNET_GNS_shorten_zone (struct GNUNET_GNS_Handle *handle, - const char * name, - struct GNUNET_CRYPTO_ShortHashCode *zone, - GNUNET_GNS_ShortenResultProcessor proc, - void *proc_cls) + const char *name, + struct GNUNET_CRYPTO_ShortHashCode *private_zone, + struct GNUNET_CRYPTO_ShortHashCode *shorten_zone, + struct GNUNET_CRYPTO_ShortHashCode *zone, + GNUNET_GNS_ShortenResultProcessor proc, + void *proc_cls) { /* IPC to shorten gns names, return shorten_handle */ struct GNUNET_GNS_ClientShortenMessage *shorten_msg; - struct GNUNET_GNS_QueueEntry *qe; + struct GNUNET_GNS_ShortenRequest *sr; size_t msize; struct PendingMessage *pending; if (NULL == name) { + GNUNET_break (0); return NULL; } - - msize = sizeof (struct GNUNET_GNS_ClientShortenMessage) + strlen(name) + 1; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Trying to shorten %s in GNS\n", name); - - qe = GNUNET_malloc(sizeof (struct GNUNET_GNS_QueueEntry)); - qe->gns_handle = handle; - qe->shorten_proc = proc; - qe->proc_cls = proc_cls; - qe->r_id = get_request_id(handle); - GNUNET_CONTAINER_DLL_insert_tail(handle->shorten_head, - handle->shorten_tail, qe); - - pending = GNUNET_malloc (sizeof (struct PendingMessage) + msize); - memset(pending, 0, (sizeof (struct PendingMessage) + msize)); - + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Trying to shorten `%s' in GNS\n", name); + msize = sizeof (struct GNUNET_GNS_ClientShortenMessage) + strlen (name) + 1; + if (msize > UINT16_MAX) + { + GNUNET_break (0); + return NULL; + } + sr = GNUNET_malloc (sizeof (struct GNUNET_GNS_ShortenRequest) + + sizeof (struct PendingMessage) + msize); + sr->gns_handle = handle; + sr->shorten_proc = proc; + sr->proc_cls = proc_cls; + sr->r_id = handle->r_id_gen++; + GNUNET_CONTAINER_DLL_insert_tail (handle->shorten_head, + handle->shorten_tail, sr); + pending = (struct PendingMessage *)&sr[1]; pending->size = msize; + pending->r_id = sr->r_id; shorten_msg = (struct GNUNET_GNS_ClientShortenMessage *) &pending[1]; shorten_msg->header.type = htons (GNUNET_MESSAGE_TYPE_GNS_SHORTEN); - shorten_msg->header.size = htons (msize); - shorten_msg->id = htonl(qe->r_id); - + shorten_msg->header.size = htons ((uint16_t) msize); + shorten_msg->id = htonl (sr->r_id); + shorten_msg->private_zone = *private_zone; + shorten_msg->shorten_zone = *shorten_zone; if (NULL != zone) { - shorten_msg->use_default_zone = htonl(0); - memcpy(&shorten_msg->zone, zone, - sizeof(struct GNUNET_CRYPTO_ShortHashCode)); + shorten_msg->use_default_zone = htonl (GNUNET_NO); + memcpy (&shorten_msg->zone, zone, + sizeof (struct GNUNET_CRYPTO_ShortHashCode)); } else { - shorten_msg->use_default_zone = htonl(1); - memset(&shorten_msg->zone, 0, sizeof(struct GNUNET_CRYPTO_ShortHashCode)); - } - - memcpy(&shorten_msg[1], name, strlen(name)); - + shorten_msg->use_default_zone = htonl (GNUNET_YES); + memset (&shorten_msg->zone, 0, sizeof (struct GNUNET_CRYPTO_ShortHashCode)); + } + memcpy (&shorten_msg[1], name, strlen (name) + 1); GNUNET_CONTAINER_DLL_insert_tail (handle->pending_head, handle->pending_tail, - pending); - + pending); process_pending_messages (handle); - return qe; + return sr; } + /** * Perform a name shortening operation on the GNS. * * @param handle handle to the GNS service * @param name the name to look up + * @param private_zone the public zone of the private zone + * @param shorten_zone the public zone of the shorten zone * @param proc function to call on result * @param proc_cls closure for processor * @return handle to the operation */ -struct GNUNET_GNS_QueueEntry * +struct GNUNET_GNS_ShortenRequest* GNUNET_GNS_shorten (struct GNUNET_GNS_Handle *handle, - const char * name, + const char *name, + struct GNUNET_CRYPTO_ShortHashCode *private_zone, + struct GNUNET_CRYPTO_ShortHashCode *shorten_zone, GNUNET_GNS_ShortenResultProcessor proc, void *proc_cls) { - return GNUNET_GNS_shorten_zone (handle, name, NULL, proc, proc_cls); + return GNUNET_GNS_shorten_zone (handle, name, + private_zone, shorten_zone, + NULL, proc, proc_cls); } + + /** * Perform an authority lookup for a given name. * @@ -823,51 +1049,52 @@ GNUNET_GNS_shorten (struct GNUNET_GNS_Handle *handle, * @param proc_cls closure for processor * @return handle to the operation */ -struct GNUNET_GNS_QueueEntry * +struct GNUNET_GNS_GetAuthRequest* GNUNET_GNS_get_authority (struct GNUNET_GNS_Handle *handle, - const char * name, - GNUNET_GNS_GetAuthResultProcessor proc, - void *proc_cls) + const char *name, + GNUNET_GNS_GetAuthResultProcessor proc, + void *proc_cls) { struct GNUNET_GNS_ClientGetAuthMessage *get_auth_msg; - struct GNUNET_GNS_QueueEntry *qe; + struct GNUNET_GNS_GetAuthRequest *gar; size_t msize; struct PendingMessage *pending; if (NULL == name) { + GNUNET_break (0); return NULL; } - - msize = sizeof (struct GNUNET_GNS_ClientGetAuthMessage) + strlen(name) + 1; GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Trying to look up authority for %s in GNS\n", name); - - qe = GNUNET_malloc(sizeof (struct GNUNET_GNS_QueueEntry)); - qe->gns_handle = handle; - qe->auth_proc = proc; - qe->proc_cls = proc_cls; - qe->r_id = get_request_id(handle); - GNUNET_CONTAINER_DLL_insert_tail(handle->get_auth_head, - handle->get_auth_tail, qe); - - pending = GNUNET_malloc (sizeof (struct PendingMessage) + msize); - memset(pending, 0, (sizeof (struct PendingMessage) + msize)); - + msize = sizeof (struct GNUNET_GNS_ClientGetAuthMessage) + strlen (name) + 1; + if (msize > UINT16_MAX) + { + GNUNET_break (0); + return NULL; + } + gar = GNUNET_malloc (sizeof (struct GNUNET_GNS_GetAuthRequest) + + sizeof (struct PendingMessage) + msize); + gar->gns_handle = handle; + gar->auth_proc = proc; + gar->proc_cls = proc_cls; + gar->r_id = handle->r_id_gen++; + GNUNET_CONTAINER_DLL_insert_tail (handle->get_auth_head, + handle->get_auth_tail, gar); + + pending = (struct PendingMessage *) &gar[1]; pending->size = msize; - + pending->r_id = gar->r_id; get_auth_msg = (struct GNUNET_GNS_ClientGetAuthMessage *) &pending[1]; get_auth_msg->header.type = htons (GNUNET_MESSAGE_TYPE_GNS_GET_AUTH); get_auth_msg->header.size = htons (msize); - get_auth_msg->id = htonl(qe->r_id); - - memcpy(&get_auth_msg[1], name, strlen(name)); - - GNUNET_CONTAINER_DLL_insert_tail (handle->pending_head, handle->pending_tail, - pending); - + get_auth_msg->id = htonl (gar->r_id); + memcpy (&get_auth_msg[1], name, strlen (name) + 1); + GNUNET_CONTAINER_DLL_insert_tail (handle->pending_head, + handle->pending_tail, + pending); process_pending_messages (handle); - return qe; + return gar; } diff --git a/src/gns/gns_common.c b/src/gns/gns_common.c new file mode 100644 index 0000000..88b365d --- /dev/null +++ b/src/gns/gns_common.c @@ -0,0 +1,79 @@ +/* + This file is part of GNUnet. + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ +/** + * + * @file gns/gns_common.c + * @brief helper functions shared between GNS service and block plugin + * @author Martin Schanzenbach + */ +#include "platform.h" +#include "gns_common.h" + + +/** + * Compute the DHT key for a name in a zone. + * DHT key is H(name) xor H(pubkey). + * + * @param name name of the record + * @param zone GADS zone + * @param key where to store the DHT key for records under this name in the given zone + */ +void +GNUNET_GNS_get_key_for_record (const char *name, + const struct GNUNET_CRYPTO_ShortHashCode *zone, + struct GNUNET_HashCode *key) +{ + struct GNUNET_CRYPTO_ShortHashCode name_hash; + struct GNUNET_HashCode name_hash_double; + struct GNUNET_HashCode zone_hash_double; + + GNUNET_CRYPTO_short_hash (name, + strlen (name), + &name_hash); + GNUNET_CRYPTO_short_hash_double (&name_hash, &name_hash_double); + GNUNET_CRYPTO_short_hash_double (zone, &zone_hash_double); + GNUNET_CRYPTO_hash_xor(&name_hash_double, &zone_hash_double, key); +} + + +/** + * Compute the zone identifier from a given DHT key and record name. + * + * @param name name of the record + * @param key DHT key of the record + * @param zone set to the corresponding zone hash + */ +void +GNUNET_GNS_get_zone_from_key (const char *name, + const struct GNUNET_HashCode *key, + struct GNUNET_CRYPTO_ShortHashCode *zone) +{ + struct GNUNET_CRYPTO_ShortHashCode name_hash; + struct GNUNET_HashCode name_hash_double; + struct GNUNET_HashCode zone_hash_double; + + GNUNET_CRYPTO_short_hash(name, strlen(name), &name_hash); + GNUNET_CRYPTO_short_hash_double(&name_hash, &name_hash_double); + GNUNET_CRYPTO_hash_xor(key, &name_hash_double, &zone_hash_double); + GNUNET_CRYPTO_short_hash_from_truncation (&zone_hash_double, zone); +} + + +/* end of gns_common.c */ diff --git a/src/gns/gns_common.h b/src/gns/gns_common.h new file mode 100644 index 0000000..5b4a116 --- /dev/null +++ b/src/gns/gns_common.h @@ -0,0 +1,58 @@ +/* + This file is part of GNUnet. + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ +/** + * + * @file gns/gns_common.h + * @brief helper functions shared between GNS service and block plugin + * @author Martin Schanzenbach + */ +#ifndef GNS_COMMON_H +#define GNS_COMMON_H + +#include "gnunet_util_lib.h" + +/** + * Compute the DHT key for a name in a zone. + * + * @param name name of the record + * @param zone GADS zone + * @param key where to store the DHT key for records under this name in the given zone + */ +void +GNUNET_GNS_get_key_for_record (const char *name, + const struct GNUNET_CRYPTO_ShortHashCode *zone, + struct GNUNET_HashCode *key); + + +/** + * Compute the zone identifier from a given DHT key and record name. + * + * @param name name of the record + * @param key DHT key of the record + * @param zone set to the corresponding zone hash + */ +void +GNUNET_GNS_get_zone_from_key (const char *name, + const struct GNUNET_HashCode *key, + struct GNUNET_CRYPTO_ShortHashCode *zone); + + + +#endif diff --git a/src/gns/gnunet-dns2gns.c b/src/gns/gnunet-dns2gns.c new file mode 100644 index 0000000..8350103 --- /dev/null +++ b/src/gns/gnunet-dns2gns.c @@ -0,0 +1,708 @@ +/* + This file is part of GNUnet. + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ +/** + * @file gnunet-dns2gns.c + * @brief DNS server that translates DNS requests to GNS + * @author Christian Grothoff + */ +#include "platform.h" +#include +#include +#include +#include +#include "gns.h" + +/** + * Timeout for DNS requests. + */ +#define TIMEOUT GNUNET_TIME_UNIT_MINUTES + +/** + * Default suffix + */ +#define DNS_SUFFIX ".zkey.eu" + +/** + * FCFS suffix + */ +#define FCFS_SUFFIX "fcfs.zkey.eu" + +/** + * Data kept per request. + */ +struct Request +{ + /** + * Socket to use for sending the reply. + */ + struct GNUNET_NETWORK_Handle *lsock; + + /** + * Destination address to use. + */ + const void *addr; + + /** + * Initially, this is the DNS request, it will then be + * converted to the DNS response. + */ + struct GNUNET_DNSPARSER_Packet *packet; + + /** + * Our GNS request handle. + */ + struct GNUNET_GNS_LookupRequest *lookup; + + /** + * Our DNS request handle + */ + struct GNUNET_DNSSTUB_RequestSocket *dns_lookup; + + /** + * Task run on timeout or shutdown to clean up without + * response. + */ + GNUNET_SCHEDULER_TaskIdentifier timeout_task; + + /** + * Number of bytes in 'addr'. + */ + size_t addr_len; + +}; + + +/** + * Handle to GNS resolver. + */ +struct GNUNET_GNS_Handle *gns; + +/** + * Stub resolver + */ +struct GNUNET_DNSSTUB_Context *dns_stub; + +/** + * Listen socket for IPv4. + */ +static struct GNUNET_NETWORK_Handle *listen_socket4; + +/** + * Listen socket for IPv6. + */ +static struct GNUNET_NETWORK_Handle *listen_socket6; + +/** + * Task for IPv4 socket. + */ +static GNUNET_SCHEDULER_TaskIdentifier t4; + +/** + * Task for IPv6 socket. + */ +static GNUNET_SCHEDULER_TaskIdentifier t6; + +/** + * DNS suffix, suffix of this gateway in DNS; defaults to '.zkey.eu' + */ +static char *dns_suffix; + +/** + * FCFS suffix, suffix of FCFS-authority in DNS; defaults to 'fcfs.zkey.eu'. + */ +static char *fcfs_suffix; + +/** + * IP of DNS server + */ +static char *dns_ip; + +/** + * UDP Port we listen on for inbound DNS requests. + */ +static unsigned int listen_port = 53; + + +/** + * Task run on shutdown. Cleans up everything. + * + * @param cls unused + * @param tc scheduler context + */ +static void +do_shutdown (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + if (GNUNET_SCHEDULER_NO_TASK != t4) + GNUNET_SCHEDULER_cancel (t4); + if (GNUNET_SCHEDULER_NO_TASK != t6) + GNUNET_SCHEDULER_cancel (t6); + if (NULL != listen_socket4) + { + GNUNET_NETWORK_socket_close (listen_socket4); + listen_socket4 = NULL; + } + if (NULL != listen_socket6) + { + GNUNET_NETWORK_socket_close (listen_socket6); + listen_socket6 = NULL; + } + GNUNET_GNS_disconnect (gns); + gns = NULL; + GNUNET_DNSSTUB_stop (dns_stub); + dns_stub = NULL; +} + + +/** + * Send the response for the given request and clean up. + * + * @param request context for the request. + */ +static void +send_response (struct Request *request) +{ + char *buf; + size_t size; + + if (GNUNET_SYSERR == + GNUNET_DNSPARSER_pack (request->packet, + UINT16_MAX /* is this not too much? */, + &buf, + &size)) + { + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + _("Failed to pack DNS response into UDP packet!\n")); + } + else + { + if (size != + GNUNET_NETWORK_socket_sendto (request->lsock, + buf, size, + request->addr, + request->addr_len)) + GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "sendto"); + GNUNET_free (buf); + } + GNUNET_SCHEDULER_cancel (request->timeout_task); + GNUNET_DNSPARSER_free_packet (request->packet); + GNUNET_free (request); +} + + +/** + * Task run on timeout. Cleans up request. + * + * @param cls 'struct Request' of the request to clean up + * @param tc scheduler context + */ +static void +do_timeout (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct Request *request = cls; + + if (NULL != request->packet) + GNUNET_DNSPARSER_free_packet (request->packet); + if (NULL != request->lookup) + GNUNET_GNS_cancel_lookup_request (request->lookup); + if (NULL != request->dns_lookup) + GNUNET_DNSSTUB_resolve_cancel (request->dns_lookup); + GNUNET_free (request); +} + + +/** + * Iterator called on obtained result for a DNS + * lookup + * + * @param cls closure + * @param rs the request socket + * @param dns the DNS udp payload + * @param r size of the DNS payload + */ +static void +dns_result_processor (void *cls, + struct GNUNET_DNSSTUB_RequestSocket *rs, + const struct GNUNET_TUN_DnsHeader *dns, + size_t r) +{ + struct Request *request = cls; + + request->packet = GNUNET_DNSPARSER_parse ((char*)dns, r); + send_response (request); +} + + +/** + * Iterator called on obtained result for a GNS + * lookup + * + * @param cls closure + * @param rd_count number of records + * @param rd the records in reply + */ +static void +result_processor (void *cls, + uint32_t rd_count, + const struct GNUNET_NAMESTORE_RecordData *rd) +{ + struct Request *request = cls; + struct GNUNET_DNSPARSER_Packet *packet; + uint32_t i; + struct GNUNET_DNSPARSER_Record rec; + + request->lookup = NULL; + packet = request->packet; + packet->flags.query_or_response = 1; + packet->flags.return_code = GNUNET_DNSPARSER_RETURN_CODE_NO_ERROR; + packet->flags.checking_disabled = 0; + packet->flags.authenticated_data = 1; + packet->flags.zero = 0; + packet->flags.recursion_available = 1; + packet->flags.message_truncated = 0; + packet->flags.authoritative_answer = 0; + //packet->flags.opcode = GNUNET_DNSPARSER_OPCODE_STATUS; // ??? + for (i=0;iqueries[0].name); + rec.class = GNUNET_DNSPARSER_CLASS_INTERNET; + rec.type = GNUNET_DNSPARSER_TYPE_A; + rec.data.raw.data = GNUNET_malloc (sizeof (struct in_addr)); + memcpy (rec.data.raw.data, + rd[i].data, + rd[i].data_size); + rec.data.raw.data_len = sizeof (struct in_addr); + GNUNET_array_append (packet->answers, + packet->num_answers, + rec); + break; + case GNUNET_DNSPARSER_TYPE_AAAA: + GNUNET_assert (sizeof (struct in6_addr) == rd[i].data_size); + rec.name = GNUNET_strdup (packet->queries[0].name); + rec.data.raw.data = GNUNET_malloc (sizeof (struct in6_addr)); + rec.class = GNUNET_DNSPARSER_CLASS_INTERNET; + rec.type = GNUNET_DNSPARSER_TYPE_AAAA; + memcpy (rec.data.raw.data, + rd[i].data, + rd[i].data_size); + rec.data.raw.data_len = sizeof (struct in6_addr); + GNUNET_array_append (packet->answers, + packet->num_answers, + rec); + break; + case GNUNET_DNSPARSER_TYPE_CNAME: + rec.name = GNUNET_strdup (packet->queries[0].name); + rec.data.hostname = strdup (rd[i].data); + rec.class = GNUNET_DNSPARSER_CLASS_INTERNET; + rec.type = GNUNET_DNSPARSER_TYPE_CNAME; + memcpy (rec.data.hostname, + rd[i].data, + rd[i].data_size); + GNUNET_array_append (packet->answers, + packet->num_answers, + rec); + break; + default: + /* skip */ + break; + } + } + send_response (request); +} + + +/** + * Handle DNS request. + * + * @param lsock socket to use for sending the reply + * @param addr address to use for sending the reply + * @param addr_len number of bytes in addr + * @param udp_msg DNS request payload + * @param udp_msg_size number of bytes in udp_msg + */ +static void +handle_request (struct GNUNET_NETWORK_Handle *lsock, + const void *addr, + size_t addr_len, + const char *udp_msg, + size_t udp_msg_size) +{ + struct Request *request; + struct GNUNET_DNSPARSER_Packet *packet; + char *name; + char *dot; + char *nname; + size_t name_len; + enum GNUNET_GNS_RecordType type; + int use_gns; + struct GNUNET_CRYPTO_ShortHashCode zone; + + packet = GNUNET_DNSPARSER_parse (udp_msg, udp_msg_size); + if (NULL == packet) + { + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + _("Cannot parse DNS request from %s\n"), + GNUNET_a2s (addr, addr_len)); + return; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Received request for `%s' with flags %u, #answers %d, #auth %d, #additional %d\n", + packet->queries[0].name, + (unsigned int) packet->flags.query_or_response, + (int) packet->num_answers, + (int) packet->num_authority_records, + (int) packet->num_additional_records); + if ( (0 != packet->flags.query_or_response) || + (0 != packet->num_answers) || + (0 != packet->num_authority_records)) + { + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + _("Received malformed DNS request from %s\n"), + GNUNET_a2s (addr, addr_len)); + GNUNET_DNSPARSER_free_packet (packet); + return; + } + if ( (1 != packet->num_queries) ) + { + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + _("Received unsupported DNS request from %s\n"), + GNUNET_a2s (addr, addr_len)); + GNUNET_DNSPARSER_free_packet (packet); + return; + } + request = GNUNET_malloc (sizeof (struct Request) + addr_len); + request->lsock = lsock; + request->packet = packet; + request->addr = &request[1]; + request->addr_len = addr_len; + memcpy (&request[1], addr, addr_len); + request->timeout_task = GNUNET_SCHEDULER_add_delayed (TIMEOUT, + &do_timeout, + request); + name = GNUNET_strdup (packet->queries[0].name); + name_len = strlen (name); + use_gns = GNUNET_NO; + if ( (name_len > strlen (dns_suffix)) && + (0 == strcasecmp (dns_suffix, + &name[name_len - strlen (dns_suffix)])) ) + { + /* Test if '.zkey' was requested */ + name[name_len - strlen (dns_suffix)] = '\0'; + dot = strrchr (name, (int) '.'); + if ( (NULL != dot) && + (GNUNET_OK == + GNUNET_CRYPTO_short_hash_from_string (dot + 1, &zone)) ) + { + /* valid '.zkey' name */ + GNUNET_asprintf (&nname, + "%s.%s", + name, + GNUNET_GNS_TLD_ZKEY); + GNUNET_free (name); + name = nname; + } + else + { + /* try '.gads' name */ + GNUNET_asprintf (&nname, + "%s.%s", + name, + GNUNET_GNS_TLD); + GNUNET_free (name); + name = nname; + } + name_len = strlen (name); + } + if ( (name_len >= strlen ((GNUNET_GNS_TLD))) && + (0 == strcasecmp (GNUNET_GNS_TLD, + &name[name_len - strlen (GNUNET_GNS_TLD)])) ) + use_gns = GNUNET_YES; + + if ( (name_len > strlen (GNUNET_GNS_TLD_ZKEY)) && + (0 == strcasecmp (GNUNET_GNS_TLD_ZKEY, + &name[name_len - strlen (GNUNET_GNS_TLD_ZKEY)])) ) + use_gns = GNUNET_YES; + + if (GNUNET_YES == use_gns) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Calling GNS\n"); + type = packet->queries[0].type; + request->lookup = GNUNET_GNS_lookup (gns, + name, + type, + GNUNET_NO, + NULL, + &result_processor, + request); + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Calling DNS at %s\n", dns_ip); + GNUNET_DNSPARSER_free_packet (request->packet); + request->packet = NULL; + request->dns_lookup = GNUNET_DNSSTUB_resolve2 (dns_stub, + udp_msg, + udp_msg_size, + &dns_result_processor, + request); + } + GNUNET_free (name); +} + + +/** + * Task to read IPv4 DNS packets. + * + * @param cls the 'listen_socket4' + * @param tc scheduler context + */ +static void +read_dns4 (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct sockaddr_in v4; + socklen_t addrlen; + ssize_t size; + + GNUNET_assert (listen_socket4 == cls); + t4 = GNUNET_SCHEDULER_add_read_net (GNUNET_TIME_UNIT_FOREVER_REL, + listen_socket4, + &read_dns4, + listen_socket4); + if (0 == (GNUNET_SCHEDULER_REASON_READ_READY & tc->reason)) + return; /* shutdown? */ + size = GNUNET_NETWORK_socket_recvfrom_amount (listen_socket4); + if (0 > size) + { + GNUNET_break (0); + return; /* read error!? */ + } + { + char buf[size]; + + addrlen = sizeof (v4); + GNUNET_break (size == + GNUNET_NETWORK_socket_recvfrom (listen_socket4, + buf, + size, + (struct sockaddr *) &v4, + &addrlen)); + handle_request (listen_socket4, &v4, addrlen, + buf, size); + } +} + + +/** + * Task to read IPv6 DNS packets. + * + * @param cls the 'listen_socket6' + * @param tc scheduler context + */ +static void +read_dns6 (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct sockaddr_in6 v6; + socklen_t addrlen; + ssize_t size; + + GNUNET_assert (listen_socket6 == cls); + t6 = GNUNET_SCHEDULER_add_read_net (GNUNET_TIME_UNIT_FOREVER_REL, + listen_socket6, + &read_dns6, + listen_socket6); + if (0 == (GNUNET_SCHEDULER_REASON_READ_READY & tc->reason)) + return; /* shutdown? */ + size = GNUNET_NETWORK_socket_recvfrom_amount (listen_socket6); + if (0 > size) + { + GNUNET_break (0); + return; /* read error!? */ + } + { + char buf[size]; + + addrlen = sizeof (v6); + GNUNET_break (size == + GNUNET_NETWORK_socket_recvfrom (listen_socket6, + buf, + size, + (struct sockaddr *) &v6, + &addrlen)); + handle_request (listen_socket6, &v6, addrlen, + buf, size); + } +} + + +/** + * Main function that will be run. + * + * @param cls closure + * @param args remaining command-line arguments + * @param cfgfile name of the configuration file used (for saving, can be NULL!) + * @param cfg configuration + */ +static void +run (void *cls, char *const *args, const char *cfgfile, + const struct GNUNET_CONFIGURATION_Handle *cfg) +{ + if (NULL == dns_ip) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "No DNS server specified!\n"); + return; + } + + if (NULL == dns_suffix) + dns_suffix = DNS_SUFFIX; + if (NULL == fcfs_suffix) + fcfs_suffix = FCFS_SUFFIX; + if (NULL == (gns = GNUNET_GNS_connect (cfg))) + return; + if (NULL == (dns_stub = GNUNET_DNSSTUB_start (dns_ip))) + { + GNUNET_GNS_disconnect (gns); + gns = NULL; + return; + } + listen_socket4 = GNUNET_NETWORK_socket_create (PF_INET, + SOCK_DGRAM, + IPPROTO_UDP); + if (NULL != listen_socket4) + { + struct sockaddr_in v4; + + memset (&v4, 0, sizeof (v4)); + v4.sin_family = AF_INET; +#if HAVE_SOCKADDR_IN_SIN_LEN + v4.sin_len = sizeof (v4); +#endif + v4.sin_port = htons (listen_port); + if (GNUNET_OK != + GNUNET_NETWORK_socket_bind (listen_socket4, + (struct sockaddr *) &v4, + sizeof (v4))) + { + GNUNET_log_strerror (GNUNET_ERROR_TYPE_ERROR, "bind"); + GNUNET_NETWORK_socket_close (listen_socket4); + listen_socket4 = NULL; + } + } + listen_socket6 = GNUNET_NETWORK_socket_create (PF_INET6, + SOCK_DGRAM, + IPPROTO_UDP); + if (NULL != listen_socket6) + { + struct sockaddr_in6 v6; + + memset (&v6, 0, sizeof (v6)); + v6.sin6_family = AF_INET6; +#if HAVE_SOCKADDR_IN_SIN_LEN + v6.sin6_len = sizeof (v6); +#endif + v6.sin6_port = htons (listen_port); + if (GNUNET_OK != + GNUNET_NETWORK_socket_bind (listen_socket6, + (struct sockaddr *) &v6, + sizeof (v6))) + { + GNUNET_log_strerror (GNUNET_ERROR_TYPE_ERROR, "bind"); + GNUNET_NETWORK_socket_close (listen_socket6); + listen_socket6 = NULL; + } + } + if ( (NULL == listen_socket4) && + (NULL == listen_socket6) ) + { + GNUNET_GNS_disconnect (gns); + gns = NULL; + GNUNET_DNSSTUB_stop (dns_stub); + dns_stub = NULL; + return; + } + if (NULL != listen_socket4) + t4 = GNUNET_SCHEDULER_add_read_net (GNUNET_TIME_UNIT_FOREVER_REL, + listen_socket4, + &read_dns4, + listen_socket4); + if (NULL != listen_socket6) + t6 = GNUNET_SCHEDULER_add_read_net (GNUNET_TIME_UNIT_FOREVER_REL, + listen_socket6, + &read_dns6, + listen_socket6); + + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, + &do_shutdown, NULL); +} + + +/** + * The main function for the fcfs daemon. + * + * @param argc number of arguments from the command line + * @param argv command line arguments + * @return 0 ok, 1 on error + */ +int +main (int argc, + char *const *argv) +{ + static const struct GNUNET_GETOPT_CommandLineOption options[] = { + {'d', "dns", "IP", + gettext_noop ("IP of recursive DNS resolver to use (required)"), 1, + &GNUNET_GETOPT_set_string, &dns_ip}, + {'s', "suffix", "SUFFIX", + gettext_noop ("Authoritative DNS suffix to use (optional); default: zkey.eu"), 1, + &GNUNET_GETOPT_set_string, &dns_suffix}, + {'f', "fcfs", "NAME", + gettext_noop ("Authoritative FCFS suffix to use (optional); default: fcfs.zkey.eu"), 1, + &GNUNET_GETOPT_set_string, &fcfs_suffix}, + {'p', "port", "UDPPORT", + gettext_noop ("UDP port to listen on for inbound DNS requests; default: 53"), 1, + &GNUNET_GETOPT_set_uint, &listen_port}, + GNUNET_GETOPT_OPTION_END + }; + int ret; + + if (GNUNET_OK != GNUNET_STRINGS_get_utf8_args (argc, argv, + &argc, &argv)) + return 2; + GNUNET_log_setup ("gnunet-dns2gns", "WARNING", NULL); + ret = + (GNUNET_OK == + GNUNET_PROGRAM_run (argc, argv, "gnunet-dns2gns", + _("GNUnet DNS-to-GNS proxy (a DNS server)"), + options, + &run, NULL)) ? 0 : 1; + GNUNET_free ((void*) argv); + return ret; +} + +/* end of gnunet-dns2gns.c */ diff --git a/src/gns/gnunet-gns-fcfsd.c b/src/gns/gnunet-gns-fcfsd.c index cd4e8e7..d553964 100644 --- a/src/gns/gnunet-gns-fcfsd.c +++ b/src/gns/gnunet-gns-fcfsd.c @@ -42,13 +42,20 @@ /** * Front page. (/) */ -#define MAIN_PAGE "GNUnet FCFS Authority Name Registration Service

What is your desired domain name?

What is your public key? " +#define MAIN_PAGE "GNUnet FCFS Authority Name Registration ServiceWhat is your desired domain name? (at most 63 lowercase characters, no dots allowed.)

What is your public key? (Copy from gnunet-setup.)
List of all registered names " /** * Second page (/S) */ #define SUBMIT_PAGE "%s%s" +/** + * Fcfs zoneinfo page (/Zoneinfo) + */ +#define ZONEINFO_PAGE "FCFS Zoneinfo

FCFS Zoneinfo

%s
namePKEY
" + +#define FCFS_ZONEINFO_URL "/Zoneinfo" + /** * Mime type for HTML pages. */ @@ -59,6 +66,7 @@ */ #define COOKIE_NAME "gns-fcfs" +#define DEFAULT_ZONEINFO_BUFSIZE 2048 /** * Phases a request goes through. @@ -137,6 +145,36 @@ struct Request }; +/** + * Zoneinfo request + */ +struct ZoneinfoRequest +{ + /** + * Connection + */ + struct MHD_Connection *connection; + + /** + * List iterator + */ + struct GNUNET_NAMESTORE_ZoneIterator *list_it; + + /** + * Buffer + */ + char* zoneinfo; + + /** + * Buffer length + */ + size_t buf_len; + + /** + * Buffer write offset + */ + size_t write_offset; +}; /** * MHD deamon reference. @@ -164,6 +202,139 @@ static struct GNUNET_CRYPTO_ShortHashCode fcfsd_zone; static struct GNUNET_CRYPTO_RsaPrivateKey *fcfs_zone_pkey; +/** + * Task run whenever HTTP server operations are pending. + * + * @param cls unused + * @param tc scheduler context + */ +static void +do_httpd (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc); + + +/** + * Schedule task to run MHD server now. + */ +static void +run_httpd_now () +{ + if (GNUNET_SCHEDULER_NO_TASK != httpd_task) + { + GNUNET_SCHEDULER_cancel (httpd_task); + httpd_task = GNUNET_SCHEDULER_NO_TASK; + } + httpd_task = GNUNET_SCHEDULER_add_now (&do_httpd, NULL); +} + +static void +iterate_cb (void *cls, + const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *zone_key, + struct GNUNET_TIME_Absolute expire, + const char *name, + unsigned int rd_len, + const struct GNUNET_NAMESTORE_RecordData *rd, + const struct GNUNET_CRYPTO_RsaSignature *signature) +{ + struct ZoneinfoRequest *zr = cls; + struct MHD_Response *response; + char* full_page; + size_t bytes_free; + char* pkey; + char* new_buf; + + + if (NULL == name) + { + zr->list_it = NULL; + + /* return static form */ + GNUNET_asprintf (&full_page, + ZONEINFO_PAGE, + zr->zoneinfo, + zr->zoneinfo); + response = MHD_create_response_from_buffer (strlen (full_page), + (void *) full_page, + MHD_RESPMEM_MUST_FREE); + MHD_add_response_header (response, + MHD_HTTP_HEADER_CONTENT_TYPE, + MIME_HTML); + MHD_queue_response (zr->connection, + MHD_HTTP_OK, + response); + MHD_destroy_response (response); + GNUNET_free (zr->zoneinfo); + GNUNET_free (zr); + run_httpd_now (); + return; + } + + if (1 != rd_len) + { + GNUNET_NAMESTORE_zone_iterator_next (zr->list_it); + return; + } + + if (GNUNET_NAMESTORE_TYPE_PKEY != rd->record_type) + { + GNUNET_NAMESTORE_zone_iterator_next (zr->list_it); + return; + } + + bytes_free = zr->buf_len - zr->write_offset; + pkey = GNUNET_NAMESTORE_value_to_string (rd->record_type, + rd->data, + rd->data_size); + + if (bytes_free < (strlen (name) + strlen (pkey) + 40)) + { + new_buf = GNUNET_malloc (zr->buf_len * 2); + memcpy (new_buf, zr->zoneinfo, zr->write_offset); + GNUNET_free (zr->zoneinfo); + zr->zoneinfo = new_buf; + zr->buf_len *= 2; + } + sprintf (zr->zoneinfo + zr->write_offset, + "%s%s", + name, + pkey); + zr->write_offset = strlen (zr->zoneinfo); + GNUNET_NAMESTORE_zone_iterator_next (zr->list_it); + GNUNET_free (pkey); +} + + + +/** + * Handler that returns FCFS zoneinfo page. + * + * @param connection connection to use + * @return MHD_YES on success + */ +static int +serve_zoneinfo_page (struct MHD_Connection *connection) +{ + struct ZoneinfoRequest *zr; + + zr = GNUNET_malloc (sizeof (struct ZoneinfoRequest)); + + zr->zoneinfo = GNUNET_malloc (DEFAULT_ZONEINFO_BUFSIZE); + zr->buf_len = DEFAULT_ZONEINFO_BUFSIZE; + zr->connection = connection; + zr->write_offset = 0; + + printf ("adsadad1!\n"); + zr->list_it = GNUNET_NAMESTORE_zone_iteration_start (ns, + &fcfsd_zone, + GNUNET_NAMESTORE_RF_RELATIVE_EXPIRATION, + GNUNET_NAMESTORE_RF_PRIVATE, + &iterate_cb, + zr); + + return MHD_YES; +} + + /** * Handler that returns a simple static HTTP page. * @@ -283,30 +454,6 @@ post_iterator (void *cls, } -/** - * Task run whenever HTTP server operations are pending. - * - * @param cls unused - * @param tc scheduler context - */ -static void -do_httpd (void *cls, - const struct GNUNET_SCHEDULER_TaskContext *tc); - - -/** - * Schedule task to run MHD server now. - */ -static void -run_httpd_now () -{ - if (GNUNET_SCHEDULER_NO_TASK != httpd_task) - { - GNUNET_SCHEDULER_cancel (httpd_task); - httpd_task = GNUNET_SCHEDULER_NO_TASK; - } - httpd_task = GNUNET_SCHEDULER_add_now (&do_httpd, NULL); -} /** @@ -386,7 +533,7 @@ zone_to_name_cb (void *cls, &pub)); r.data = &pub; r.data_size = sizeof (pub); - r.expiration = GNUNET_TIME_UNIT_FOREVER_ABS; + r.expiration_time = UINT64_MAX; r.record_type = GNUNET_NAMESTORE_TYPE_PKEY; r.flags = GNUNET_NAMESTORE_RF_AUTHORITY; request->qe = GNUNET_NAMESTORE_record_create (ns, @@ -492,7 +639,10 @@ create_response (void *cls, if ( (0 == strcmp (method, MHD_HTTP_METHOD_GET)) || (0 == strcmp (method, MHD_HTTP_METHOD_HEAD)) ) { - ret = serve_main_page (connection); + if (0 == strcmp (url, FCFS_ZONEINFO_URL)) + ret = serve_zoneinfo_page (connection); + else + ret = serve_main_page (connection); if (ret != MHD_YES) GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("Failed to create page for `%s'\n"), @@ -544,6 +694,22 @@ create_response (void *cls, switch (request->phase) { case RP_START: + if (NULL != strchr (request->domain_name, (int) '.')) + { + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + _("Domain name must not contain `.'\n")); + request->phase = RP_FAIL; + return fill_s_reply ("Domain name must not contain `.', sorry.", + request, connection); + } + if (NULL != strchr (request->domain_name, (int) '+')) + { + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + _("Domain name must not contain `+'\n")); + request->phase = RP_FAIL; + return fill_s_reply ("Domain name must not contain `+', sorry.", + request, connection); + } request->phase = RP_LOOKUP; request->qe = GNUNET_NAMESTORE_lookup_record (ns, &fcfsd_zone, @@ -607,6 +773,9 @@ request_completed_callback (void *cls, } +#define UNSIGNED_MHD_LONG_LONG unsigned MHD_LONG_LONG + + /** * Schedule tasks to run MHD server. */ @@ -621,7 +790,7 @@ run_httpd () struct GNUNET_NETWORK_FDSet *wes; int max; int haveto; - unsigned MHD_LONG_LONG timeout; + UNSIGNED_MHD_LONG_LONG timeout; struct GNUNET_TIME_Relative tv; FD_ZERO (&rs); @@ -683,7 +852,7 @@ do_shutdown (void *cls, } if (NULL != ns) { - GNUNET_NAMESTORE_disconnect (ns, GNUNET_NO); + GNUNET_NAMESTORE_disconnect (ns); ns = NULL; } if (NULL != httpd) @@ -721,11 +890,9 @@ run (void *cls, char *const *args, const char *cfgfile, "HTTPPORT", &port)) { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - _("Option `%s' not specified in configuration section `%s'\n"), - "HTTPPORT", - "fcfsd"); - return; + GNUNET_log_config_missing (GNUNET_ERROR_TYPE_ERROR, + "fcfsd", "HTTPPORT"); + return; } if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_filename (cfg, @@ -733,10 +900,8 @@ run (void *cls, char *const *args, const char *cfgfile, "ZONEKEY", &keyfile)) { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - _("Option `%s' not specified in configuration section `%s'\n"), - "ZONEKEY", - "fcfsd"); + GNUNET_log_config_missing (GNUNET_ERROR_TYPE_ERROR, + "fcfsd", "ZONEKEY"); return; } fcfs_zone_pkey = GNUNET_CRYPTO_rsa_key_create_from_file (keyfile); @@ -771,7 +936,7 @@ run (void *cls, char *const *args, const char *cfgfile, { GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("Failed to start HTTP server\n")); - GNUNET_NAMESTORE_disconnect (ns, GNUNET_NO); + GNUNET_NAMESTORE_disconnect (ns); ns = NULL; return; } @@ -797,6 +962,9 @@ main (int argc, char *const *argv) int ret; + if (GNUNET_OK != GNUNET_STRINGS_get_utf8_args (argc, argv, &argc, &argv)) + return 2; + GNUNET_log_setup ("fcfsd", "WARNING", NULL); ret = (GNUNET_OK == @@ -804,7 +972,7 @@ main (int argc, char *const *argv) _("GNUnet GNS first come first serve registration service"), options, &run, NULL)) ? 0 : 1; - + GNUNET_free ((void*) argv); return ret; } diff --git a/src/gns/gnunet-gns-helper-service-w32.c b/src/gns/gnunet-gns-helper-service-w32.c new file mode 100644 index 0000000..72956c8 --- /dev/null +++ b/src/gns/gnunet-gns-helper-service-w32.c @@ -0,0 +1,749 @@ +/* + This file is part of GNUnet. + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ +/** + * @file gnunet-gns-helper-service-w32.c + * @brief an intermediary service to access distributed GNS + * @author Christian Grothoff + * @author LRN + */ +#define INITGUID +#include "platform.h" +#include +#include +#include +#include +#include "gnunet_w32nsp_lib.h" +#include "w32resolver.h" +#include +#include + +#define DEFINE_DNS_GUID(a,x) DEFINE_GUID(a, 0x00090035, 0x0000, x, 0xc0, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x46) +DEFINE_DNS_GUID(SVCID_DNS_TYPE_A, 0x0001); +DEFINE_DNS_GUID(SVCID_DNS_TYPE_NS, 0x0002); +DEFINE_DNS_GUID(SVCID_DNS_TYPE_CNAME, 0x0005); +DEFINE_DNS_GUID(SVCID_DNS_TYPE_SOA, 0x0006); +DEFINE_DNS_GUID(SVCID_DNS_TYPE_PTR, 0x000c); +DEFINE_DNS_GUID(SVCID_DNS_TYPE_MX, 0x000f); +DEFINE_DNS_GUID(SVCID_DNS_TYPE_TEXT, 0x0010); +DEFINE_DNS_GUID(SVCID_DNS_TYPE_AAAA, 0x001c); +DEFINE_DNS_GUID(SVCID_DNS_TYPE_SRV, 0x0021); +DEFINE_GUID(SVCID_HOSTNAME, 0x0002a800, 0x0000, 0x0000, 0xc0, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x46); +DEFINE_GUID(SVCID_INET_HOSTADDRBYNAME, 0x0002a803, 0x0000, 0x0000, 0xc0, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x46); + +struct request +{ + struct GNUNET_SERVER_Client *client; + GUID sc; + int af; + wchar_t *name; + char *u8name; +}; + +/** + * Handle to GNS service. + */ +static struct GNUNET_GNS_Handle *gns; + +static struct GNUNET_CRYPTO_ShortHashCode *zone = NULL; +static struct GNUNET_CRYPTO_ShortHashCode user_zone; +struct GNUNET_CRYPTO_RsaPrivateKey *shorten_key = NULL; + + +/** + * Task run on shutdown. Cleans up everything. + * + * @param cls unused + * @param tc scheduler context + */ +static void +do_shutdown (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + if (NULL != gns) + { + GNUNET_GNS_disconnect (gns); + gns = NULL; + } +} + +/** + * Context for transmitting replies to clients. + */ +struct TransmitCallbackContext +{ + + /** + * We keep these in a doubly-linked list (for cleanup). + */ + struct TransmitCallbackContext *next; + + /** + * We keep these in a doubly-linked list (for cleanup). + */ + struct TransmitCallbackContext *prev; + + /** + * The message that we're asked to transmit. + */ + struct GNUNET_MessageHeader *msg; + + /** + * Handle for the transmission request. + */ + struct GNUNET_SERVER_TransmitHandle *th; + + /** + * Client that we are transmitting to. + */ + struct GNUNET_SERVER_Client *client; + +}; + + +/** + * Head of the doubly-linked list (for cleanup). + */ +static struct TransmitCallbackContext *tcc_head; + +/** + * Tail of the doubly-linked list (for cleanup). + */ +static struct TransmitCallbackContext *tcc_tail; + +/** + * Have we already cleaned up the TCCs and are hence no longer + * willing (or able) to transmit anything to anyone? + */ +static int cleaning_done; + +/** + * Function called to notify a client about the socket + * begin ready to queue more data. "buf" will be + * NULL and "size" zero if the socket was closed for + * writing in the meantime. + * + * @param cls closure + * @param size number of bytes available in buf + * @param buf where the callee should write the message + * @return number of bytes written to buf + */ +static size_t +transmit_callback (void *cls, size_t size, void *buf) +{ + struct TransmitCallbackContext *tcc = cls; + size_t msize; + + tcc->th = NULL; + GNUNET_CONTAINER_DLL_remove (tcc_head, tcc_tail, tcc); + msize = ntohs (tcc->msg->size); + if (size == 0) + { + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + _("Transmission to client failed!\n")); + GNUNET_SERVER_client_drop (tcc->client); + GNUNET_free (tcc->msg); + GNUNET_free (tcc); + return 0; + } + GNUNET_assert (size >= msize); + memcpy (buf, tcc->msg, msize); + GNUNET_SERVER_client_drop (tcc->client); + GNUNET_free (tcc->msg); + GNUNET_free (tcc); + return msize; +} + + +/** + * Transmit the given message to the client. + * + * @param client target of the message + * @param msg message to transmit, will be freed! + */ +static void +transmit (struct GNUNET_SERVER_Client *client, + struct GNUNET_MessageHeader *msg) +{ + struct TransmitCallbackContext *tcc; + + if (GNUNET_YES == cleaning_done) + { + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + _("Shutdown in progress, aborting transmission.\n")); + GNUNET_SERVER_client_drop (client); + GNUNET_free (msg); + return; + } + tcc = GNUNET_malloc (sizeof (struct TransmitCallbackContext)); + tcc->msg = msg; + tcc->client = client; + if (NULL == + (tcc->th = + GNUNET_SERVER_notify_transmit_ready (client, + ntohs (msg->size), + GNUNET_TIME_UNIT_FOREVER_REL, + &transmit_callback, tcc))) + { + GNUNET_break (0); + GNUNET_SERVER_client_drop (client); + GNUNET_free (msg); + GNUNET_free (tcc); + return; + } + GNUNET_SERVER_client_keep (client); + GNUNET_CONTAINER_DLL_insert (tcc_head, tcc_tail, tcc); +} + +#define MarshallPtr(ptr, base, type) \ + if (ptr) \ + ptr = (type *) ((char *) ptr - (char *) base) + +void +MarshallWSAQUERYSETW (WSAQUERYSETW *qs, GUID *sc) +{ + int i; + MarshallPtr (qs->lpszServiceInstanceName, qs, wchar_t); + MarshallPtr (qs->lpServiceClassId, qs, GUID); + MarshallPtr (qs->lpVersion, qs, WSAVERSION); + MarshallPtr (qs->lpNSProviderId, qs, GUID); + MarshallPtr (qs->lpszContext, qs, wchar_t); + MarshallPtr (qs->lpafpProtocols, qs, AFPROTOCOLS); + MarshallPtr (qs->lpszQueryString, qs, wchar_t); + for (i = 0; i < qs->dwNumberOfCsAddrs; i++) + { + MarshallPtr (qs->lpcsaBuffer[i].LocalAddr.lpSockaddr, qs, SOCKADDR); + MarshallPtr (qs->lpcsaBuffer[i].RemoteAddr.lpSockaddr, qs, SOCKADDR); + } + MarshallPtr (qs->lpcsaBuffer, qs, CSADDR_INFO); + if (IsEqualGUID (&SVCID_INET_HOSTADDRBYNAME, sc) && qs->lpBlob != NULL && qs->lpBlob->pBlobData != NULL) + { + struct hostent *he; + he = (struct hostent *) qs->lpBlob->pBlobData; + for (i = 0; he->h_aliases[i] != NULL; i++) + MarshallPtr (he->h_aliases[i], he, char); + MarshallPtr (he->h_aliases, he, char *); + MarshallPtr (he->h_name, he, char); + for (i = 0; he->h_addr_list[i] != NULL; i++) + MarshallPtr (he->h_addr_list[i], he, void); + MarshallPtr (he->h_addr_list, he, char *); + MarshallPtr (qs->lpBlob->pBlobData, qs, void); + } + MarshallPtr (qs->lpBlob, qs, BLOB); +} + + +static void +process_ip_lookup_result (void* cls, + uint32_t rd_count, + const struct GNUNET_NAMESTORE_RecordData *rd) +{ + int i, j, csanum; + struct request *rq = (struct request *) cls; + struct GNUNET_W32RESOLVER_GetMessage *msg; + struct GNUNET_MessageHeader *msgend; + WSAQUERYSETW *qs; + size_t size; + size_t size_recalc; + char *ptr; + size_t blobsize = 0; + size_t blobaddrcount = 0; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Got lookup result with count %u for rq %p with client %p\n", + rd_count, rq, rq->client); + + if (rd_count == 0) + { + size = sizeof (struct GNUNET_MessageHeader); + msg = GNUNET_malloc (size); + msg->header.size = htons (size); + msg->header.type = htons (GNUNET_MESSAGE_TYPE_W32RESOLVER_RESPONSE); + transmit (rq->client, &msg->header); + return; + } + + size = sizeof (struct GNUNET_W32RESOLVER_GetMessage) + sizeof (WSAQUERYSETW); + size += (wcslen (rq->name) + 1) * sizeof (wchar_t); + size += sizeof (GUID); + /* lpszComment ? a TXT record? */ + size += sizeof (GUID); + /* lpszContext ? Not sure what it is */ + csanum = 0; + for (i = 0; i < rd_count; i++) + { + switch (rd[i].record_type) + { + case GNUNET_GNS_RECORD_A: + if (rd[i].data_size != sizeof (struct in_addr)) + continue; + size += sizeof (CSADDR_INFO) + sizeof (struct sockaddr_in) * 2; + csanum++; + break; + case GNUNET_GNS_RECORD_AAAA: + if (rd[i].data_size != sizeof (struct in6_addr)) + continue; + size += sizeof (CSADDR_INFO) + sizeof (struct sockaddr_in6) * 2; + csanum++; + break; + } + } + if (IsEqualGUID (&SVCID_INET_HOSTADDRBYNAME, &rq->sc)) + { + size += sizeof (BLOB); + blobsize += sizeof (struct hostent); + blobsize += strlen (rq->u8name) + 1; + blobsize += sizeof (void *); /* For aliases */ + blobsize += sizeof (void *); /* For addresses */ + for (i = 0; i < rd_count; i++) + { + if ((rq->af == AF_INET || rq->af == AF_UNSPEC) && rd[i].record_type == GNUNET_GNS_RECORD_A) + { + blobsize += sizeof (void *); + blobsize += sizeof (struct in_addr); + blobaddrcount++; + } + else if (rq->af == AF_INET6 && rd[i].record_type == GNUNET_GNS_RECORD_AAAA) + { + blobsize += sizeof (void *); + blobsize += sizeof (struct in6_addr); + blobaddrcount++; + } + } + size += blobsize; + } + size += sizeof (struct GNUNET_MessageHeader); + size_recalc = sizeof (struct GNUNET_W32RESOLVER_GetMessage) + sizeof (WSAQUERYSETW); + msg = GNUNET_malloc (size); + msg->header.size = htons (size - sizeof (struct GNUNET_MessageHeader)); + msg->header.type = htons (GNUNET_MESSAGE_TYPE_W32RESOLVER_RESPONSE); + msg->af = htonl (rq->af); + msg->sc_data1 = htonl (rq->sc.Data1); + msg->sc_data2 = htons (rq->sc.Data2); + msg->sc_data3 = htons (rq->sc.Data3); + msg->sc_data4 = 0; + for (i = 0; i < 8; i++) + msg->sc_data4 |= rq->sc.Data4[i] << ((7 - i) * 8); + msg->sc_data4 = GNUNET_htonll (msg->sc_data4); + qs = (WSAQUERYSETW *) &msg[1]; + ptr = (char *) &qs[1]; + GNUNET_break (size_recalc == (size_t) ((char *) ptr - (char *) msg)); + qs->dwSize = sizeof (WSAQUERYSETW); + qs->lpszServiceInstanceName = (wchar_t *) ptr; + ptr += (wcslen (rq->name) + 1) * sizeof (wchar_t); + size_recalc += (wcslen (rq->name) + 1) * sizeof (wchar_t); + GNUNET_break (size_recalc == (size_t) ((char *) ptr - (char *) msg)); + wcscpy (qs->lpszServiceInstanceName, rq->name); + qs->lpServiceClassId = (GUID *) ptr; + ptr += sizeof (GUID); + size_recalc += sizeof (GUID); + GNUNET_break (size_recalc == (size_t) ((char *) ptr - (char *) msg)); + memcpy (qs->lpServiceClassId, &rq->sc, sizeof (GUID)); + qs->lpVersion = NULL; + qs->dwNameSpace = NS_DNS; + qs->lpNSProviderId = (GUID *) ptr; + ptr += sizeof (GUID); + size_recalc += sizeof (GUID); + GNUNET_break (size_recalc == (size_t) ((char *) ptr - (char *) msg)); + memcpy (qs->lpNSProviderId, &GNUNET_NAMESPACE_PROVIDER_DNS, sizeof (GUID)); + qs->lpszContext = NULL; + qs->dwNumberOfProtocols = 0; + qs->lpafpProtocols = NULL; + /* Don't bother with this... */ + qs->lpszQueryString = NULL; + qs->dwNumberOfCsAddrs = rd_count; + qs->lpcsaBuffer = (CSADDR_INFO *) ptr; + ptr += sizeof (CSADDR_INFO) * csanum; + j = 0; + for (i = 0; i < rd_count; i++) + { + switch (rd[i].record_type) + { + case GNUNET_GNS_RECORD_A: + if (rd[i].data_size != sizeof (struct in_addr)) + continue; + qs->lpcsaBuffer[j].iSocketType = SOCK_STREAM; + qs->lpcsaBuffer[j].iProtocol = IPPROTO_TCP; + + qs->lpcsaBuffer[j].LocalAddr.iSockaddrLength = sizeof (struct sockaddr_in); + qs->lpcsaBuffer[j].LocalAddr.lpSockaddr = (SOCKADDR *) ptr; + ptr += qs->lpcsaBuffer[j].LocalAddr.iSockaddrLength; + memset (qs->lpcsaBuffer[j].LocalAddr.lpSockaddr, 0, qs->lpcsaBuffer[j].LocalAddr.iSockaddrLength); + ((struct sockaddr_in *)qs->lpcsaBuffer[j].LocalAddr.lpSockaddr)->sin_family = AF_INET; + + qs->lpcsaBuffer[j].RemoteAddr.iSockaddrLength = sizeof (struct sockaddr_in); + qs->lpcsaBuffer[j].RemoteAddr.lpSockaddr = (SOCKADDR *) ptr; + ptr += qs->lpcsaBuffer[j].RemoteAddr.iSockaddrLength; + memset (qs->lpcsaBuffer[j].RemoteAddr.lpSockaddr, 0, qs->lpcsaBuffer[j].RemoteAddr.iSockaddrLength); + ((struct sockaddr_in *)qs->lpcsaBuffer[j].RemoteAddr.lpSockaddr)->sin_family = AF_INET; + ((struct sockaddr_in *)qs->lpcsaBuffer[j].RemoteAddr.lpSockaddr)->sin_port = htonl (53); /* Don't ask why it's 53 */ + ((struct sockaddr_in *)qs->lpcsaBuffer[j].RemoteAddr.lpSockaddr)->sin_addr = *(struct in_addr *) rd[i].data; + size_recalc += sizeof (CSADDR_INFO) + sizeof (struct sockaddr_in) * 2; + j++; + break; + case GNUNET_GNS_RECORD_AAAA: + if (rd[i].data_size != sizeof (struct in6_addr)) + continue; + qs->lpcsaBuffer[j].iSocketType = SOCK_STREAM; + qs->lpcsaBuffer[j].iProtocol = IPPROTO_TCP; + + qs->lpcsaBuffer[j].LocalAddr.iSockaddrLength = sizeof (struct sockaddr_in6); + qs->lpcsaBuffer[j].LocalAddr.lpSockaddr = (SOCKADDR *) ptr; + ptr += qs->lpcsaBuffer[j].LocalAddr.iSockaddrLength; + memset (qs->lpcsaBuffer[j].LocalAddr.lpSockaddr, 0, qs->lpcsaBuffer[j].LocalAddr.iSockaddrLength); + ((struct sockaddr_in6 *)qs->lpcsaBuffer[j].LocalAddr.lpSockaddr)->sin6_family = AF_INET6; + + qs->lpcsaBuffer[j].RemoteAddr.iSockaddrLength = sizeof (struct sockaddr_in6); + qs->lpcsaBuffer[j].RemoteAddr.lpSockaddr = (SOCKADDR *) ptr; + ptr += qs->lpcsaBuffer[j].RemoteAddr.iSockaddrLength; + memset (qs->lpcsaBuffer[j].RemoteAddr.lpSockaddr, 0, qs->lpcsaBuffer[j].RemoteAddr.iSockaddrLength); + ((struct sockaddr_in6 *)qs->lpcsaBuffer[j].RemoteAddr.lpSockaddr)->sin6_family = AF_INET6; + ((struct sockaddr_in6 *)qs->lpcsaBuffer[j].RemoteAddr.lpSockaddr)->sin6_port = htonl (53); /* Don't ask why it's 53 */ + ((struct sockaddr_in6 *)qs->lpcsaBuffer[j].RemoteAddr.lpSockaddr)->sin6_addr = *(struct in6_addr *) rd[i].data; + size_recalc += sizeof (CSADDR_INFO) + sizeof (struct sockaddr_in6) * 2; + j++; + break; + default: + break; + } + } + GNUNET_break (size_recalc == (size_t) ((char *) ptr - (char *) msg)); + qs->dwOutputFlags = 0; + if (IsEqualGUID (&SVCID_INET_HOSTADDRBYNAME, &rq->sc)) + { + struct hostent *he; + qs->lpBlob = (BLOB *) ptr; + ptr += sizeof (BLOB); + + size_recalc += sizeof (BLOB); + GNUNET_break (size_recalc == (size_t) ((char *) ptr - (char *) msg)); + + qs->lpBlob->cbSize = blobsize; + qs->lpBlob->pBlobData = (BYTE *) ptr; + ptr += sizeof (struct hostent); + + size_recalc += sizeof (struct hostent); + GNUNET_break (size_recalc == (size_t) ((char *) ptr - (char *) msg)); + + he = (struct hostent *) qs->lpBlob->pBlobData; + he->h_name = (char *) ptr; + ptr += strlen (rq->u8name) + 1; + + size_recalc += strlen (rq->u8name) + 1; + GNUNET_break (size_recalc == (size_t) ((char *) ptr - (char *) msg)); + + strcpy (he->h_name, rq->u8name); + he->h_aliases = (char **) ptr; + ptr += sizeof (void *); + + size_recalc += sizeof (void *); /* For aliases */ + GNUNET_break (size_recalc == (size_t) ((char *) ptr - (char *) msg)); + + he->h_aliases[0] = NULL; + he->h_addrtype = rq->af; + he->h_length = rq->af == AF_INET || rq->af == AF_UNSPEC ? sizeof (struct in_addr) : sizeof (struct in6_addr); + he->h_addr_list = (char **) ptr; + ptr += sizeof (void *) * (blobaddrcount + 1); + + size_recalc += sizeof (void *) * (blobaddrcount + 1); /* For addresses */ + GNUNET_break (size_recalc == (size_t) ((char *) ptr - (char *) msg)); + + j = 0; + for (i = 0; i < rd_count; i++) + { + if ((rq->af == AF_INET || rq->af == AF_UNSPEC) && + rd[i].record_type == GNUNET_GNS_RECORD_A) + { + he->h_addr_list[j] = (char *) ptr; + ptr += sizeof (struct in_addr); + + size_recalc += sizeof (struct in_addr); + GNUNET_break (size_recalc == (size_t) ((char *) ptr - (char *) msg)); + + memcpy (he->h_addr_list[j], rd[i].data, sizeof (struct in_addr)); + j++; + } + else if (rq->af == AF_INET6 && rd[i].record_type == GNUNET_GNS_RECORD_AAAA) + { + he->h_addr_list[j] = (char *) ptr; + ptr += sizeof (struct in6_addr); + + size_recalc += sizeof (struct in6_addr); + GNUNET_break (size_recalc == (size_t) ((char *) ptr - (char *) msg)); + + memcpy (he->h_addr_list[j], rd[i].data, sizeof (struct in6_addr)); + j++; + } + } + he->h_addr_list[j] = NULL; + } + msgend = (struct GNUNET_MessageHeader *) ptr; + ptr += sizeof (struct GNUNET_MessageHeader); + size_recalc += sizeof (struct GNUNET_MessageHeader); + + msgend->type = htons (GNUNET_MESSAGE_TYPE_W32RESOLVER_RESPONSE); + msgend->size = htons (sizeof (struct GNUNET_MessageHeader)); + + if ((char *) ptr - (char *) msg != size || size_recalc != size || size_recalc != ((char *) ptr - (char *) msg)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Error in WSAQUERYSETW size calc: expected %lu, got %lu (recalc %lu)\n", size, (unsigned long) ((char *) ptr - (char *) msg), size_recalc); + } + MarshallWSAQUERYSETW (qs, &rq->sc); + transmit (rq->client, &msg->header); +} + +static void +get_ip_from_hostname (struct GNUNET_SERVER_Client *client, + const wchar_t *name, int af, GUID sc) +{ + struct request *rq; + char *hostname; + size_t strl; + size_t namelen; + uint32_t rtype; + + if (IsEqualGUID (&SVCID_DNS_TYPE_A, &sc)) + rtype = GNUNET_GNS_RECORD_A; + else if (IsEqualGUID (&SVCID_DNS_TYPE_NS, &sc)) + rtype = GNUNET_GNS_RECORD_NS; + else if (IsEqualGUID (&SVCID_DNS_TYPE_CNAME, &sc)) + rtype = GNUNET_GNS_RECORD_CNAME; + else if (IsEqualGUID (&SVCID_DNS_TYPE_SOA, &sc)) + rtype = GNUNET_GNS_RECORD_SOA; + else if (IsEqualGUID (&SVCID_DNS_TYPE_PTR, &sc)) + rtype = GNUNET_GNS_RECORD_PTR; + else if (IsEqualGUID (&SVCID_DNS_TYPE_MX, &sc)) + rtype = GNUNET_GNS_RECORD_MX; + else if (IsEqualGUID (&SVCID_DNS_TYPE_TEXT, &sc)) + rtype = GNUNET_GNS_RECORD_TXT; + else if (IsEqualGUID (&SVCID_DNS_TYPE_AAAA, &sc)) + rtype = GNUNET_GNS_RECORD_AAAA; + else if (IsEqualGUID (&SVCID_DNS_TYPE_SRV, &sc)) + rtype = GNUNET_GNS_RECORD_SRV; + else if (IsEqualGUID (&SVCID_INET_HOSTADDRBYNAME, &sc)) + rtype = GNUNET_GNS_RECORD_A; + else + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Unknown GUID: %08X-%04X-%04X-%02X-%02X-%02X-%02X-%02X-%02X-%02X-%02X\n", + sc.Data1, sc.Data2, sc.Data3, sc.Data4[0], sc.Data4[1], sc.Data4[2], + sc.Data4[3], sc.Data4[4], sc.Data4[5], sc.Data4[6], sc.Data4[7]); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + + if (name) + namelen = wcslen (name); + else + namelen = 0; + if (namelen > 0) + hostname = (char *) u16_to_u8 (name, namelen + 1, NULL, &strl); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "W32 DNS resolver asked to look up %s for `%s'.\n", + af == AF_INET ? "IPv4" : af == AF_INET6 ? "IPv6" : "anything", + hostname); + rq = GNUNET_malloc (sizeof (struct request)); + rq->sc = sc; + rq->client = client; + rq->af = af; + if (rq->af != AF_INET && rq->af != AF_INET6) + rq->af = AF_INET; + if (namelen) + { + rq->name = GNUNET_malloc ((namelen + 1) * sizeof (wchar_t)); + memcpy (rq->name, name, (namelen + 1) * sizeof (wchar_t)); + rq->u8name = hostname; + } + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Launching a lookup for client %p with rq %p\n", + client, rq); + + if (NULL != GNUNET_GNS_lookup_zone (gns, hostname, zone, rtype, + GNUNET_YES, shorten_key, &process_ip_lookup_result, rq)) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Lookup launched, waiting for a reply\n"); + GNUNET_SERVER_client_keep (client); + GNUNET_SERVER_receive_done (client, GNUNET_OK); + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Lookup was not, disconnecting the client\n"); + if (namelen) + { + GNUNET_free (rq->name); + free (rq->u8name); + } + GNUNET_free (rq); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + } +} + +/** + * Handle GET-message. + * + * @param cls closure + * @param client identification of the client + * @param message the actual message + */ +static void +handle_get (void *cls, struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) +{ + uint16_t msize; + const struct GNUNET_W32RESOLVER_GetMessage *msg; + GUID sc; + uint16_t size; + uint64_t data4; + int i; + const wchar_t *hostname; + int af; + + msize = ntohs (message->size); + if (msize < sizeof (struct GNUNET_W32RESOLVER_GetMessage)) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + msg = (const struct GNUNET_W32RESOLVER_GetMessage *) message; + size = msize - sizeof (struct GNUNET_W32RESOLVER_GetMessage); + af = ntohl (msg->af); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Got NBO GUID: %08X-%04X-%04X-%016llX\n", + msg->sc_data1, msg->sc_data2, msg->sc_data3, msg->sc_data4); + sc.Data1 = ntohl (msg->sc_data1); + sc.Data2 = ntohs (msg->sc_data2); + sc.Data3 = ntohs (msg->sc_data3); + data4 = GNUNET_ntohll (msg->sc_data4); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Got GUID: %08X-%04X-%04X-%016llX\n", + sc.Data1, sc.Data2, sc.Data3, data4); + for (i = 0; i < 8; i++) + sc.Data4[i] = 0xFF & (data4 >> ((7 - i) * 8)); + + hostname = (const wchar_t *) &msg[1]; + if (hostname[size - 1] != L'\0') + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "name of length %u, not 0-terminated: %*S\n", + size, size, hostname); + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + get_ip_from_hostname (client, hostname, af, sc); + return; +} + + +/** + * Start up gns-helper-w32 service. + * + * @param cls closure + * @param server the initialized server + * @param cfg configuration to use + */ +static void +run (void *cls, struct GNUNET_SERVER_Handle *server, + const struct GNUNET_CONFIGURATION_Handle *cfg) +{ + static const struct GNUNET_SERVER_MessageHandler handlers[] = { + {&handle_get, NULL, GNUNET_MESSAGE_TYPE_W32RESOLVER_REQUEST, 0}, + {NULL, NULL, 0, 0} + }; + + char* keyfile; + struct GNUNET_CRYPTO_RsaPrivateKey *key = NULL; + struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded pkey; + struct GNUNET_CRYPTO_ShortHashAsciiEncoded zonename; + + if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_filename (cfg, "gns", + "ZONEKEY", &keyfile)) + { + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + "No private key for root zone found, using default!\n"); + zone = NULL; + } + else + { + if (GNUNET_YES == GNUNET_DISK_file_test (keyfile)) + { + key = GNUNET_CRYPTO_rsa_key_create_from_file (keyfile); + GNUNET_CRYPTO_rsa_key_get_public (key, &pkey); + GNUNET_CRYPTO_short_hash(&pkey, + sizeof(struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded), + &user_zone); + zone = &user_zone; + GNUNET_CRYPTO_short_hash_to_enc (zone, &zonename); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Using zone: %s!\n", &zonename); + GNUNET_CRYPTO_rsa_key_free(key); + } + GNUNET_free(keyfile); + } + + if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_filename (cfg, "gns", + "SHORTEN_ZONEKEY", &keyfile)) + { + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + "No shorten key found!\n"); + shorten_key = NULL; + } + else + { + if (GNUNET_YES == GNUNET_DISK_file_test (keyfile)) + { + shorten_key = GNUNET_CRYPTO_rsa_key_create_from_file (keyfile); + } + GNUNET_free(keyfile); + } + + gns = GNUNET_GNS_connect (cfg); + if (gns == NULL) + return; + + GNUNET_SERVER_add_handlers (server, handlers); + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, &do_shutdown, + NULL); + +} + + +/** + * The main function for gns-helper-w32. + * + * @param argc number of arguments from the command line + * @param argv command line arguments + * @return 0 ok, 1 on error + */ +int +main (int argc, char *const *argv) +{ + int ret; + + ret = + (GNUNET_OK == + GNUNET_SERVICE_run (argc, argv, "gns-helper-service-w32", GNUNET_SERVICE_OPTION_NONE, + &run, NULL)) ? 0 : 1; + + return ret; +} + +/* end of gnunet-gns.c */ diff --git a/src/gns/gnunet-gns-proxy-setup-ca b/src/gns/gnunet-gns-proxy-setup-ca new file mode 100644 index 0000000..4564583 --- /dev/null +++ b/src/gns/gnunet-gns-proxy-setup-ca @@ -0,0 +1,31 @@ +echo "Generating CA" + +openssl req -new -x509 -days 3650 -extensions v3_ca -keyout gnscakey.pem -out gnscacert.pem -subj "/C=DE/ST=Bavaria/L=Munich/O=GADS/OU=GNUnet/CN=GADS Proxy CA/emailAddress=bounce@gnunet.org" -passout pass:"GNUnet Naming System" + +echo "Removing passphrase from key" +openssl rsa -passin pass:"GNUnet Naming System" -in gnscakey.pem -out gnscakeynoenc.pem + +cp gnscacert.pem $HOME/.gnunet/gns/gnscert.pem +cat gnscacert.pem > $HOME/.gnunet/gns/gnsCAcert.pem +cat gnscakeynoenc.pem >> $HOME/.gnunet/gns/gnsCAcert.pem + +echo "Importing CA into browsers" +for f in ~/.mozilla/firefox/*.default +do + if [ -d $f ]; then + echo "Importing CA info firefox $f" + certutil -D -n "GNS Proxy CA" -d ~/.mozilla/firefox/*.default >/dev/null 2&>1 + certutil -A -n "GNS Proxy CA" -t CT,, -d ~/.mozilla/firefox/*.default < gnscacert.pem + fi +done + +if [ -d ~/.pki/nssdb ]; then + echo "Importing CA into chrome" + certutil -D -n "GADS Proxy CA" -d ~/.pki/nssdb >/dev/null 2&>1 + certutil -A -n "GADS Proxy CA" -t CT,, -d ~/.pki/nssdb < gnscacert.pem +fi + + +rm gnscakey.pem gnscakeynoenc.pem gnscacert.pem + +echo "You can now start gnunet-gns-proxy and configure your browser to use a SOCKS proxy on port 7777" diff --git a/src/gns/gnunet-gns-proxy.c b/src/gns/gnunet-gns-proxy.c index 876f531..7b78378 100644 --- a/src/gns/gnunet-gns-proxy.c +++ b/src/gns/gnunet-gns-proxy.c @@ -17,93 +17,1865 @@ Free Software Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */ - +/** + * @author Martin Schanzenbach + * @file src/gns/gnunet-gns-proxy.c + * @brief HTTP(S) proxy that rewrites URIs and fakes certificats to make GADS work + * with legacy browsers + */ #include "platform.h" -#include #include +#include +#include +#include +#include +#include +#include +#include "gnunet_util_lib.h" +#include "gnunet_gns_service.h" #include "gns_proxy_proto.h" #include "gns.h" +#define HAVE_MHD_NO_LISTEN_SOCKET (MHD_VERSION >= 0x00091401) + #define GNUNET_GNS_PROXY_PORT 7777 +#define MHD_MAX_CONNECTIONS 300 +#define MAX_HTTP_URI_LENGTH 2048 +#define POSTBUFFERSIZE 4096 + +/* MHD/cURL defines */ +enum BufferStatus + { + BUF_WAIT_FOR_CURL, + BUF_WAIT_FOR_MHD, + BUF_WAIT_FOR_PP + }; + +#define HTML_HDR_CONTENT "Content-Type: text/html" + +/* buffer padding for proper RE matching */ +#define CURL_BUF_PADDING 1000 + +/* regexp */ +//#define RE_DOTPLUS "cURL streams + */ +struct ProxyCurlTask +{ + /* DLL for tasks */ + struct ProxyCurlTask *prev; + + /* DLL for tasks */ + struct ProxyCurlTask *next; + + /* Handle to cURL */ + CURL *curl; + + /* Optional header replacements for curl (LEHO) */ + struct curl_slist *headers; + + /* Optional resolver replacements for curl (LEHO) */ + struct curl_slist *resolver; + + /* curl response code */ + long curl_response_code; + + /* The URL to fetch */ + char url[MAX_HTTP_URI_LENGTH]; + + /* The cURL write buffer / MHD read buffer */ + char buffer[CURL_MAX_WRITE_SIZE + CURL_BUF_PADDING]; + + /* Read pos of the data in the buffer */ + char *buffer_read_ptr; + + /* Write pos in the buffer */ + char *buffer_write_ptr; + + /* connection */ + struct MHD_Connection *connection; + + /*put*/ + size_t put_read_offset; + size_t put_read_size; + + /*post*/ + struct MHD_PostProcessor *post_handler; + + /* post data */ + struct ProxyUploadData *upload_data_head; + struct ProxyUploadData *upload_data_tail; + + /* the type of POST encoding */ + char* post_type; + + struct curl_httppost *httppost; + + struct curl_httppost *httppost_last; + + /* Number of bytes in buffer */ + unsigned int bytes_in_buffer; + + /* PP task */ + GNUNET_SCHEDULER_TaskIdentifier pp_task; + + /* PP match list */ + struct ProxyREMatch *pp_match_head; + + /* PP match list */ + struct ProxyREMatch *pp_match_tail; + + /* The associated daemon list entry */ + struct MhdHttpList *mhd; + + /* The associated response */ + struct MHD_Response *response; + + /* Cookies to set */ + struct ProxySetCookieHeader *set_cookies_head; + + /* Cookies to set */ + struct ProxySetCookieHeader *set_cookies_tail; + + /* The authority of the corresponding host (site of origin) */ + char authority[256]; + + /* The hostname (Host header field) */ + char host[256]; + + /* The LEgacy HOstname (can be empty) */ + char leho[256]; + + /* The port */ + uint16_t port; + + /* The buffer status (BUF_WAIT_FOR_CURL or BUF_WAIT_FOR_MHD) */ + enum BufferStatus buf_status; + + /* connection status */ + int ready_to_queue; + + /* is curl running? */ + int curl_running; + + /* are we done */ + int fin; + + /* Already accepted */ + int accepted; + + /* Indicates wheather the download is in progress */ + int download_in_progress; + + /* Indicates wheather the download was successful */ + int download_is_finished; + + /* Indicates wheather the download failed */ + int download_error; + + /* Indicates wheather we need to parse HTML */ + int parse_content; + + /* Indicates wheather we are postprocessing the HTML right now */ + int is_postprocessing; + + /* Indicates wheather postprocessing has finished */ + int pp_finished; + + int post_done; + + int is_httppost; + +}; + +/** + * Struct for RE matches in postprocessing of HTML + */ +struct ProxyREMatch +{ + /* DLL */ + struct ProxyREMatch *next; + + /* DLL */ + struct ProxyREMatch *prev; + + /* start of match in buffer */ + char* start; + + /* end of match in buffer */ + char* end; + + /* associated proxycurltask */ + struct ProxyCurlTask *ctask; + + /* hostname found */ + char hostname[255]; + + /* PP result */ + char result[255]; + + /* shorten task */ + struct GNUNET_GNS_ShortenRequest *shorten_task; + + /* are we done */ + int done; + + /* is SSL */ + int is_ssl; + +}; + +/** + * Struct for set-cookies + */ +struct ProxySetCookieHeader +{ + /* DLL */ + struct ProxySetCookieHeader *next; + + /* DLL */ + struct ProxySetCookieHeader *prev; + + /* the cookie */ + char *cookie; +}; + +/** + * Post data structure + */ +struct ProxyUploadData +{ + /* DLL */ + struct ProxyUploadData *next; + + /* DLL */ + struct ProxyUploadData *prev; + + char *key; + + char *filename; + + char *content_type; + + size_t content_length; + + /* value */ + char *value; + + /* to copy */ + size_t bytes_left; + + /* size */ + size_t total_bytes; }; -unsigned long port = GNUNET_GNS_PROXY_PORT; + +/* The port the proxy is running on (default 7777) */ +static unsigned long port = GNUNET_GNS_PROXY_PORT; + +/* The CA file (pem) to use for the proxy CA */ +static char* cafile_opt; + +/* The listen socket of the proxy */ static struct GNUNET_NETWORK_Handle *lsock; -GNUNET_SCHEDULER_TaskIdentifier ltask; + +/* The listen task ID */ +static GNUNET_SCHEDULER_TaskIdentifier ltask; + +/* The cURL download task */ +static GNUNET_SCHEDULER_TaskIdentifier curl_download_task; + +/* The non SSL httpd daemon handle */ static struct MHD_Daemon *httpd; -static GNUNET_SCHEDULER_TaskIdentifier httpd_task; -static int -con_val_iter (void *cls, - enum MHD_ValueKind kind, - const char *key, - const char *value) +/* Number of current mhd connections */ +static unsigned int total_mhd_connections; + +/* The cURL multi handle */ +static CURLM *curl_multi; + +/* Handle to the GNS service */ +static struct GNUNET_GNS_Handle *gns_handle; + +/* DLL for ProxyCurlTasks */ +static struct ProxyCurlTask *ctasks_head; + +/* DLL for ProxyCurlTasks */ +static struct ProxyCurlTask *ctasks_tail; + +/* DLL for http daemons */ +static struct MhdHttpList *mhd_httpd_head; + +/* DLL for http daemons */ +static struct MhdHttpList *mhd_httpd_tail; + +/* Handle to the regex for dotplus (.+) replacement in HTML */ +static regex_t re_dotplus; + +/* The users local GNS zone hash */ +static struct GNUNET_CRYPTO_ShortHashCode *local_gns_zone; + +/* The users local private zone */ +static struct GNUNET_CRYPTO_ShortHashCode *local_private_zone; + +/* The users local shorten zone */ +static struct GNUNET_CRYPTO_ShortHashCode *local_shorten_zone; + +/* The CA for SSL certificate generation */ +static struct ProxyCA proxy_ca; + +/* UNIX domain socket for mhd */ +#if !HAVE_MHD_NO_LISTEN_SOCKET +static struct GNUNET_NETWORK_Handle *mhd_unix_socket; +#endif + +/* Shorten zone private key */ +static struct GNUNET_CRYPTO_RsaPrivateKey *shorten_zonekey; + + +/** + * Checks if name is in tld + * + * @param name the name to check + * @param tld the TLD to check for (must NOT begin with ".") + * @return GNUNET_YES or GNUNET_NO + */ +static int +is_tld (const char* name, const char* tld) +{ + size_t name_len = strlen (name); + size_t tld_len = strlen (tld); + + GNUNET_break ('.' != tld[0]); + return ( (tld_len < name_len) && + ( ('.' == name[name_len - tld_len - 1]) || (name_len == tld_len) ) && + (0 == memcmp (tld, + name + (name_len - tld_len), + tld_len)) ); +} + + +static int +con_post_data_iter (void *cls, + enum MHD_ValueKind kind, + const char *key, + const char *filename, + const char *content_type, + const char *transfer_encoding, + const char *data, + uint64_t off, + size_t size) +{ + struct ProxyCurlTask* ctask = cls; + struct ProxyUploadData* pdata; + char* enc; + char* new_value; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Got POST data (file: %s, content type: %s): '%s=%.*s' at offset %llu size %llu\n", + filename, content_type, + key, (int) size, data, + (unsigned long long) off, + (unsigned long long) size); + GNUNET_assert (NULL != ctask->post_type); + + if (0 == strcasecmp (MHD_HTTP_POST_ENCODING_MULTIPART_FORMDATA, + ctask->post_type)) + { + ctask->is_httppost = GNUNET_YES; + /* new part */ + if (0 == off) + { + pdata = GNUNET_malloc (sizeof (struct ProxyUploadData)); + pdata->key = GNUNET_strdup (key); + + if (NULL != filename) + pdata->filename = GNUNET_strdup (filename); + if (NULL != content_type) + pdata->content_type = GNUNET_strdup (content_type); + pdata->value = GNUNET_malloc (size); + pdata->total_bytes = size; + memcpy (pdata->value, data, size); + GNUNET_CONTAINER_DLL_insert_tail (ctask->upload_data_head, + ctask->upload_data_tail, + pdata); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Copied %llu bytes of POST Data\n", + (unsigned long long) size); + return MHD_YES; + } + + pdata = ctask->upload_data_tail; + new_value = GNUNET_malloc (size + pdata->total_bytes); + memcpy (new_value, pdata->value, pdata->total_bytes); + memcpy (new_value+off, data, size); + GNUNET_free (pdata->value); + pdata->value = new_value; + pdata->total_bytes += size; + + return MHD_YES; + } + + if (0 != strcasecmp (MHD_HTTP_POST_ENCODING_FORM_URLENCODED, + ctask->post_type)) + { + return MHD_NO; + } + + ctask->is_httppost = GNUNET_NO; + + if (NULL != ctask->curl) + curl_easy_pause (ctask->curl, CURLPAUSE_CONT); + + if (0 == off) + { + enc = curl_easy_escape (ctask->curl, key, 0); + if (NULL == enc) + { + GNUNET_break (0); + return MHD_NO; + } + /* a key */ + pdata = GNUNET_malloc (sizeof (struct ProxyUploadData)); + pdata->value = GNUNET_malloc (strlen (enc) + 3); + if (NULL != ctask->upload_data_head) + { + pdata->value[0] = '&'; + memcpy (pdata->value+1, enc, strlen (enc)); + } + else + memcpy (pdata->value, enc, strlen (enc)); + pdata->value[strlen (pdata->value)] = '='; + pdata->bytes_left = strlen (pdata->value); + pdata->total_bytes = pdata->bytes_left; + curl_free (enc); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Escaped POST key: '%s'\n", + pdata->value); + + GNUNET_CONTAINER_DLL_insert_tail (ctask->upload_data_head, + ctask->upload_data_tail, + pdata); + } + + /* a value */ + enc = curl_easy_escape (ctask->curl, data, 0); + if (NULL == enc) + { + GNUNET_break (0); + return MHD_NO; + } + pdata = GNUNET_malloc (sizeof (struct ProxyUploadData)); + pdata->value = GNUNET_malloc (strlen (enc) + 1); + memcpy (pdata->value, enc, strlen (enc)); + pdata->bytes_left = strlen (pdata->value); + pdata->total_bytes = pdata->bytes_left; + curl_free (enc); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Escaped POST value: '%s'\n", + pdata->value); + + GNUNET_CONTAINER_DLL_insert_tail (ctask->upload_data_head, + ctask->upload_data_tail, + pdata); + return MHD_YES; +} + + +/** + * Read HTTP request header field 'Host' + * + * @param cls buffer to write to + * @param kind value kind + * @param key field key + * @param value field value + * @return MHD_NO when Host found + */ +static int +con_val_iter (void *cls, + enum MHD_ValueKind kind, + const char *key, + const char *value) +{ + struct ProxyCurlTask *ctask = cls; + char* buf = ctask->host; + char* port; + char* cstr; + const char* hdr_val; + unsigned int uport; + + if (0 == strcmp ("Host", key)) + { + port = strchr (value, ':'); + if (NULL != port) + { + strncpy (buf, value, port-value); + port++; + if ((1 != sscanf (port, "%u", &uport)) || + (uport > UINT16_MAX) || + (0 == uport)) + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Unable to parse port!\n"); + else + ctask->port = (uint16_t) uport; + } + else + strcpy (buf, value); + return MHD_YES; + } + + if (0 == strcmp (MHD_HTTP_HEADER_ACCEPT_ENCODING, key)) + hdr_val = ""; + else + hdr_val = value; + + if (0 == strcasecmp (MHD_HTTP_HEADER_CONTENT_TYPE, + key)) + { + if (0 == strncasecmp (value, + MHD_HTTP_POST_ENCODING_FORM_URLENCODED, + strlen (MHD_HTTP_POST_ENCODING_FORM_URLENCODED))) + ctask->post_type = MHD_HTTP_POST_ENCODING_FORM_URLENCODED; + else if (0 == strncasecmp (value, + MHD_HTTP_POST_ENCODING_MULTIPART_FORMDATA, + strlen (MHD_HTTP_POST_ENCODING_MULTIPART_FORMDATA))) + ctask->post_type = MHD_HTTP_POST_ENCODING_MULTIPART_FORMDATA; + else + ctask->post_type = NULL; + + } + + cstr = GNUNET_malloc (strlen (key) + strlen (hdr_val) + 3); + GNUNET_snprintf (cstr, strlen (key) + strlen (hdr_val) + 3, + "%s: %s", key, hdr_val); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Client Header: %s\n", cstr); + + ctask->headers = curl_slist_append (ctask->headers, cstr); + GNUNET_free (cstr); + + return MHD_YES; +} + + +/** + * Callback for MHD response + * + * @param cls closure + * @param pos in buffer + * @param buf buffer + * @param max space in buffer + * @return number of bytes written + */ +static ssize_t +mhd_content_cb (void *cls, + uint64_t pos, + char* buf, + size_t max); + + +/** + * Check HTTP response header for mime + * + * @param buffer curl buffer + * @param size curl blocksize + * @param nmemb curl blocknumber + * @param cls handle + * @return size of read bytes + */ +static size_t +curl_check_hdr (void *buffer, size_t size, size_t nmemb, void *cls) +{ + size_t bytes = size * nmemb; + struct ProxyCurlTask *ctask = cls; + int html_mime_len = strlen (HTML_HDR_CONTENT); + int cookie_hdr_len = strlen (MHD_HTTP_HEADER_SET_COOKIE); + char hdr_mime[html_mime_len+1]; + char hdr_generic[bytes+1]; + char new_cookie_hdr[bytes+strlen (ctask->leho)+1]; + char new_location[MAX_HTTP_URI_LENGTH+500]; + char real_host[264]; + char leho_host[264]; + char* ndup; + char* tok; + char* cookie_domain; + char* hdr_type; + char* hdr_val; + int delta_cdomain; + size_t offset = 0; + char cors_hdr[strlen (ctask->leho) + strlen ("https://")]; + + if (NULL == ctask->response) + { + /* FIXME: get total size from curl (if available) */ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Creating response for %s\n", ctask->url); + ctask->response = MHD_create_response_from_callback (MHD_SIZE_UNKNOWN, + sizeof (ctask->buffer), + &mhd_content_cb, + ctask, + NULL); + + /* if we have a leho add a CORS header */ + if (0 != strcmp ("", ctask->leho)) + { + /* We could also allow ssl and http here */ + if (ctask->mhd->is_ssl) + sprintf (cors_hdr, "https://%s", ctask->leho); + else + sprintf (cors_hdr, "http://%s", ctask->leho); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "MHD: Adding CORS header field %s\n", + cors_hdr); + + if (GNUNET_NO == MHD_add_response_header (ctask->response, + "Access-Control-Allow-Origin", + cors_hdr)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "MHD: Error adding CORS header field %s\n", + cors_hdr); + } + } + ctask->ready_to_queue = GNUNET_YES; + } + + if (html_mime_len <= bytes) + { + memcpy (hdr_mime, buffer, html_mime_len); + hdr_mime[html_mime_len] = '\0'; + + if (0 == strcmp (hdr_mime, HTML_HDR_CONTENT)) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Got HTML HTTP response header\n"); + ctask->parse_content = GNUNET_YES; + } + } + + if (cookie_hdr_len > bytes) + return bytes; + + memcpy (hdr_generic, buffer, bytes); + hdr_generic[bytes] = '\0'; + /* remove crlf */ + if ('\n' == hdr_generic[bytes-1]) + hdr_generic[bytes-1] = '\0'; + + if (hdr_generic[bytes-2] == '\r') + hdr_generic[bytes-2] = '\0'; + + if (0 == memcmp (hdr_generic, + MHD_HTTP_HEADER_SET_COOKIE, + cookie_hdr_len)) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Looking for cookie in: `%s'\n", hdr_generic); + ndup = GNUNET_strdup (hdr_generic+cookie_hdr_len+1); + memset (new_cookie_hdr, 0, sizeof (new_cookie_hdr)); + for (tok = strtok (ndup, ";"); tok != NULL; tok = strtok (NULL, ";")) + { + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + "Got Cookie token: %s\n", tok); + //memcpy (new_cookie_hdr+offset, tok, strlen (tok)); + if (0 == memcmp (tok, " domain", strlen (" domain"))) + { + cookie_domain = tok + strlen (" domain") + 1; + + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + "Got Set-Cookie Domain: %s\n", cookie_domain); + + if (strlen (cookie_domain) < strlen (ctask->leho)) + { + delta_cdomain = strlen (ctask->leho) - strlen (cookie_domain); + if (0 == strcmp (cookie_domain, ctask->leho + (delta_cdomain))) + { + GNUNET_snprintf (new_cookie_hdr+offset, + sizeof (new_cookie_hdr), + " domain=%s", ctask->authority); + offset += strlen (" domain=") + strlen (ctask->authority); + new_cookie_hdr[offset] = ';'; + offset++; + continue; + } + } + else if (strlen (cookie_domain) == strlen (ctask->leho)) + { + if (0 == strcmp (cookie_domain, ctask->leho)) + { + GNUNET_snprintf (new_cookie_hdr+offset, + sizeof (new_cookie_hdr), + " domain=%s", ctask->host); + offset += strlen (" domain=") + strlen (ctask->host); + new_cookie_hdr[offset] = ';'; + offset++; + continue; + } + } + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Cookie domain invalid\n"); + + + } + memcpy (new_cookie_hdr+offset, tok, strlen (tok)); + offset += strlen (tok); + new_cookie_hdr[offset] = ';'; + offset++; + } + + GNUNET_free (ndup); + + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + "Got Set-Cookie HTTP header %s\n", new_cookie_hdr); + + if (GNUNET_NO == MHD_add_response_header (ctask->response, + MHD_HTTP_HEADER_SET_COOKIE, + new_cookie_hdr)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "MHD: Error adding set-cookie header field %s\n", + hdr_generic+cookie_hdr_len+1); + } + return bytes; + } + + ndup = GNUNET_strdup (hdr_generic); + hdr_type = strtok (ndup, ":"); + + if (NULL == hdr_type) + { + GNUNET_free (ndup); + return bytes; + } + + hdr_val = strtok (NULL, ""); + + if (NULL == hdr_val) + { + GNUNET_free (ndup); + return bytes; + } + + hdr_val++; + + if (0 == strcasecmp (MHD_HTTP_HEADER_LOCATION, hdr_type)) + { + if (ctask->mhd->is_ssl) + { + sprintf (leho_host, "https://%s", ctask->leho); + sprintf (real_host, "https://%s", ctask->host); + } + else + { + sprintf (leho_host, "http://%s", ctask->leho); + sprintf (real_host, "http://%s", ctask->host); + } + + if (0 == memcmp (leho_host, hdr_val, strlen (leho_host))) + { + sprintf (new_location, "%s%s", real_host, hdr_val+strlen (leho_host)); + hdr_val = new_location; + } + } + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Trying to set %s: %s\n", + hdr_type, + hdr_val); + if (GNUNET_NO == MHD_add_response_header (ctask->response, + hdr_type, + hdr_val)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "MHD: Error adding %s header field %s\n", + hdr_type, + hdr_val); + } + GNUNET_free (ndup); + return bytes; +} + + +/** + * schedule mhd + * + * @param hd a http daemon list entry + */ +static void +run_httpd (struct MhdHttpList *hd); + + +/** + * schedule all mhds + * + */ +static void +run_httpds (void); + + +/** + * Task run whenever HTTP server operations are pending. + * + * @param cls unused + * @param tc sched context + */ +static void +do_httpd (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc); + + +static void +run_mhd_now (struct MhdHttpList *hd) +{ + if (GNUNET_SCHEDULER_NO_TASK != hd->httpd_task) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "MHD: killing old task\n"); + GNUNET_SCHEDULER_cancel (hd->httpd_task); + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "MHD: Scheduling MHD now\n"); + hd->httpd_task = GNUNET_SCHEDULER_add_now (&do_httpd, hd); +} + + +/** + * Ask cURL for the select sets and schedule download + */ +static void +curl_download_prepare (void); + + +/** + * Callback to free content + * + * @param cls content to free + * @param tc task context + */ +static void +mhd_content_free (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct ProxyCurlTask *ctask = cls; + struct ProxyUploadData *pdata; + + GNUNET_assert (NULL == ctask->pp_match_head); + if (NULL != ctask->headers) + curl_slist_free_all (ctask->headers); + + if (NULL != ctask->headers) + curl_slist_free_all (ctask->resolver); + + if (NULL != ctask->response) + MHD_destroy_response (ctask->response); + + if (NULL != ctask->post_handler) + MHD_destroy_post_processor (ctask->post_handler); + + if (GNUNET_SCHEDULER_NO_TASK != ctask->pp_task) + GNUNET_SCHEDULER_cancel (ctask->pp_task); + + for (pdata = ctask->upload_data_head; NULL != pdata; pdata = ctask->upload_data_head) + { + GNUNET_CONTAINER_DLL_remove (ctask->upload_data_head, + ctask->upload_data_tail, + pdata); + GNUNET_free_non_null (pdata->filename); + GNUNET_free_non_null (pdata->content_type); + GNUNET_free_non_null (pdata->key); + GNUNET_free_non_null (pdata->value); + GNUNET_free (pdata); + } + GNUNET_free (ctask); +} + + +/** + * Callback for MHD response + * + * @param cls closure + * @param pos in buffer + * @param buf buffer + * @param max space in buffer + * @return number of bytes written + */ +static ssize_t +mhd_content_cb (void *cls, + uint64_t pos, + char* buf, + size_t max) +{ + struct ProxyCurlTask *ctask = cls; + struct ProxyREMatch *re_match; + ssize_t copied = 0; + size_t bytes_to_copy = ctask->buffer_write_ptr - ctask->buffer_read_ptr; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "MHD: content cb for %s. To copy: %u\n", + ctask->url, (unsigned int) bytes_to_copy); + if ((GNUNET_YES == ctask->download_is_finished) && + (GNUNET_NO == ctask->download_error) && + (0 == bytes_to_copy)) + { + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + "MHD: sending response for %s\n", ctask->url); + ctask->download_in_progress = GNUNET_NO; + run_mhd_now (ctask->mhd); + GNUNET_SCHEDULER_add_now (&mhd_content_free, ctask); + total_mhd_connections--; + return MHD_CONTENT_READER_END_OF_STREAM; + } + + if ((GNUNET_YES == ctask->download_error) && + (GNUNET_YES == ctask->download_is_finished) && + (0 == bytes_to_copy)) + { + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + "MHD: sending error response\n"); + ctask->download_in_progress = GNUNET_NO; + run_mhd_now (ctask->mhd); + GNUNET_SCHEDULER_add_now (&mhd_content_free, ctask); + total_mhd_connections--; + return MHD_CONTENT_READER_END_WITH_ERROR; + } + + if ( ctask->buf_status == BUF_WAIT_FOR_CURL ) + return 0; + + copied = 0; + for (re_match = ctask->pp_match_head; NULL != re_match; re_match = ctask->pp_match_head) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "MHD: Processing PP %s\n", + re_match->hostname); + bytes_to_copy = re_match->start - ctask->buffer_read_ptr; + if (bytes_to_copy+copied > max) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "MHD: buffer in response too small for %u. Using available space (%d). (%s)\n", + (unsigned int) bytes_to_copy, + max, + ctask->url); + memcpy (buf+copied, ctask->buffer_read_ptr, max-copied); + ctask->buffer_read_ptr += max-copied; + copied = max; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "MHD: copied %d bytes\n", (int) copied); + return copied; + } + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "MHD: copying %u bytes to mhd response at offset %d\n", + (unsigned int) bytes_to_copy, ctask->buffer_read_ptr); + memcpy (buf+copied, ctask->buffer_read_ptr, bytes_to_copy); + copied += bytes_to_copy; + + if (GNUNET_NO == re_match->done) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "MHD: Waiting for PP of %s\n", re_match->hostname); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "MHD: copied %d bytes\n", (int) copied); + ctask->buffer_read_ptr += bytes_to_copy; + return copied; + } + + if (strlen (re_match->result) > (max - copied)) + { + //FIXME partially copy domain here + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "MHD: buffer in response too small for %s! (%s)\n", + re_match->result, + ctask->url); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "MHD: copied %d bytes\n", (int) copied); + ctask->buffer_read_ptr += bytes_to_copy; + return copied; + } + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "MHD: Adding PP result %s to buffer\n", + re_match->result); + memcpy (buf + copied, re_match->result, strlen (re_match->result)); + copied += strlen (re_match->result); + ctask->buffer_read_ptr = re_match->end; + GNUNET_CONTAINER_DLL_remove (ctask->pp_match_head, + ctask->pp_match_tail, + re_match); + GNUNET_free (re_match); + } + + bytes_to_copy = ctask->buffer_write_ptr - ctask->buffer_read_ptr; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "MHD: copied: %d left: %u, space left in buf: %d\n", + copied, + (unsigned int) bytes_to_copy, (int) (max - copied)); + + if (GNUNET_NO == ctask->download_is_finished) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "MHD: Purging buffer\n"); + memmove (ctask->buffer, ctask->buffer_read_ptr, bytes_to_copy); + ctask->buffer_read_ptr = ctask->buffer; + ctask->buffer_write_ptr = ctask->buffer + bytes_to_copy; + ctask->buffer[bytes_to_copy] = '\0'; + } + + if (bytes_to_copy + copied > max) + bytes_to_copy = max - copied; + memcpy (buf+copied, ctask->buffer_read_ptr, bytes_to_copy); + ctask->buffer_read_ptr += bytes_to_copy; + copied += bytes_to_copy; + ctask->buf_status = BUF_WAIT_FOR_CURL; + + if (NULL != ctask->curl) + curl_easy_pause (ctask->curl, CURLPAUSE_CONT); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "MHD: copied %d bytes\n", (int) copied); + run_mhd_now (ctask->mhd); + return copied; +} + + +/** + * Shorten result callback + * + * @param cls the proxycurltask + * @param short_name the shortened name (NULL on error) + */ +static void +process_shorten (void* cls, const char* short_name) +{ + struct ProxyREMatch *re_match = cls; + char result[sizeof (re_match->result)]; + + if (NULL == short_name) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "PP: Unable to shorten %s\n", + re_match->hostname); + GNUNET_CONTAINER_DLL_remove (re_match->ctask->pp_match_head, + re_match->ctask->pp_match_tail, + re_match); + GNUNET_free (re_match); + return; + } + + if (0 == strcmp (short_name, re_match->ctask->leho)) + strcpy (result, re_match->ctask->host); + else + strcpy (result, short_name); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "PP: Shorten %s -> %s\n", + re_match->hostname, + result); + + if (re_match->is_ssl) + sprintf (re_match->result, "href=\"https://%s", result); + else + sprintf (re_match->result, "href=\"http://%s", result); + + re_match->done = GNUNET_YES; + run_mhd_now (re_match->ctask->mhd); +} + + +/** + * Postprocess data in buffer. From read ptr to write ptr + * + * @param cls the curlproxytask + * @param tc task context + */ +static void +postprocess_buffer (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct ProxyCurlTask *ctask = cls; + struct ProxyREMatch *re_match; + char* re_ptr = ctask->buffer_read_ptr; + char re_hostname[255]; + regmatch_t m[RE_N_MATCHES]; + + ctask->pp_task = GNUNET_SCHEDULER_NO_TASK; + + if (GNUNET_YES != ctask->parse_content) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "PP: Not parsing content\n"); + ctask->buf_status = BUF_WAIT_FOR_MHD; + run_mhd_now (ctask->mhd); + return; + } + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "PP: We need to parse the HTML\n"); + + /* 0 means match found */ + while (0 == regexec (&re_dotplus, re_ptr, RE_N_MATCHES, m, 0)) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "PP: regex match\n"); + + GNUNET_assert (m[1].rm_so != -1); + + memset (re_hostname, 0, sizeof (re_hostname)); + memcpy (re_hostname, re_ptr+m[1].rm_so, (m[3].rm_eo-m[1].rm_so)); + + + re_match = GNUNET_malloc (sizeof (struct ProxyREMatch)); + re_match->start = re_ptr + m[0].rm_so; + re_match->end = re_ptr + m[3].rm_eo; + re_match->done = GNUNET_NO; + re_match->ctask = ctask; + + if ('s' == *(re_ptr+m[1].rm_so-strlen("://")-1)) //FIXME strcmp + re_match->is_ssl = GNUNET_YES; + else + re_match->is_ssl = GNUNET_NO; + + strcpy (re_match->hostname, re_hostname); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "PP: Got hostname %s\n", re_hostname); + re_ptr += m[3].rm_eo; + + if (GNUNET_YES == is_tld (re_match->hostname, GNUNET_GNS_TLD_PLUS)) + { + re_match->hostname[strlen(re_match->hostname)-1] = '\0'; + strcpy (re_match->hostname+strlen(re_match->hostname), + ctask->authority); + } + + re_match->shorten_task = GNUNET_GNS_shorten_zone (gns_handle, + re_match->hostname, + local_private_zone, + local_shorten_zone, + local_gns_zone, + &process_shorten, + re_match); //FIXME cancel appropriately + + GNUNET_CONTAINER_DLL_insert_tail (ctask->pp_match_head, + ctask->pp_match_tail, + re_match); + } + + ctask->buf_status = BUF_WAIT_FOR_MHD; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "PP: No more matches\n"); + run_mhd_now (ctask->mhd); +} + + +/** + * Handle data from cURL + * + * @param ptr pointer to the data + * @param size number of blocks of data + * @param nmemb blocksize + * @param ctx the curlproxytask + * @return number of bytes handled + */ +static size_t +curl_download_cb (void *ptr, size_t size, size_t nmemb, void* ctx) +{ + const char *cbuf = ptr; + size_t total = size * nmemb; + struct ProxyCurlTask *ctask = ctx; + size_t buf_space = sizeof (ctask->buffer) - + (ctask->buffer_write_ptr-ctask->buffer); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "CURL: Got %d. %d free in buffer\n", + total, buf_space); + + if (BUF_WAIT_FOR_CURL != ctask->buf_status) + return CURL_WRITEFUNC_PAUSE; + + if (total > (buf_space - CURL_BUF_PADDING)) + { + if (ctask->buf_status == BUF_WAIT_FOR_CURL) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "CURL: Buffer full starting postprocessing\n"); + ctask->buf_status = BUF_WAIT_FOR_PP; + ctask->pp_task = GNUNET_SCHEDULER_add_now (&postprocess_buffer, + ctask); + return CURL_WRITEFUNC_PAUSE; + } + + /* we should not get called in that case */ + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "CURL: called out of context and no space in buffer!\n"); + return CURL_WRITEFUNC_PAUSE; + } + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "CURL: Copying %d bytes to buffer (%s)\n", total, ctask->url); + memcpy (ctask->buffer_write_ptr, cbuf, total); + ctask->bytes_in_buffer += total; + ctask->buffer_write_ptr += total; + ctask->buffer_write_ptr[0] = '\0'; + + return total; +} + + +/** + * cURL callback for put data + */ +static size_t +put_read_callback (void *buf, size_t size, size_t nmemb, void *cls) +{ + struct ProxyCurlTask *ctask = cls; + struct ProxyUploadData *pdata = ctask->upload_data_head; + size_t len = size * nmemb; + size_t to_copy; + char* pos; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "CURL: put read callback\n"); + + if (NULL == pdata) + return CURL_READFUNC_PAUSE; + + //fin + if (NULL == pdata->value) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "CURL: Terminating PUT\n"); + + GNUNET_CONTAINER_DLL_remove (ctask->upload_data_head, + ctask->upload_data_tail, + pdata); + GNUNET_free (pdata); + return 0; + } + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "CURL: read callback value %s\n", pdata->value); + + to_copy = pdata->bytes_left; + if (to_copy > len) + to_copy = len; + + pos = pdata->value + (pdata->total_bytes - pdata->bytes_left); + memcpy (buf, pos, to_copy); + pdata->bytes_left -= to_copy; + if (pdata->bytes_left <= 0) + { + GNUNET_free (pdata->value); + GNUNET_CONTAINER_DLL_remove (ctask->upload_data_head, + ctask->upload_data_tail, + pdata); + GNUNET_free (pdata); + } + return to_copy; +} + + +/** + * cURL callback for post data + */ +static size_t +post_read_callback (void *buf, size_t size, size_t nmemb, void *cls) +{ + struct ProxyCurlTask *ctask = cls; + struct ProxyUploadData *pdata = ctask->upload_data_head; + size_t len = size * nmemb; + size_t to_copy; + char* pos; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "CURL: read callback\n"); + + if (NULL == pdata) + return CURL_READFUNC_PAUSE; + + //fin + if (NULL == pdata->value) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "CURL: Terminating POST data\n"); + + GNUNET_CONTAINER_DLL_remove (ctask->upload_data_head, + ctask->upload_data_tail, + pdata); + GNUNET_free (pdata); + return 0; + } + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "CURL: read callback value %s\n", pdata->value); + + to_copy = pdata->bytes_left; + if (to_copy > len) + to_copy = len; + + pos = pdata->value + (pdata->total_bytes - pdata->bytes_left); + memcpy (buf, pos, to_copy); + pdata->bytes_left -= to_copy; + if (pdata->bytes_left <= 0) + { + GNUNET_free (pdata->value); + GNUNET_CONTAINER_DLL_remove (ctask->upload_data_head, + ctask->upload_data_tail, + pdata); + GNUNET_free (pdata); + } + return to_copy; +} + + +/** + * Task that is run when we are ready to receive more data + * from curl + * + * @param cls closure + * @param tc task context + */ +static void +curl_task_download (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc); + + +/** + * Ask cURL for the select sets and schedule download + */ +static void +curl_download_prepare () +{ + CURLMcode mret; + fd_set rs; + fd_set ws; + fd_set es; + int max; + struct GNUNET_NETWORK_FDSet *grs; + struct GNUNET_NETWORK_FDSet *gws; + long to; + struct GNUNET_TIME_Relative rtime; + + max = -1; + FD_ZERO (&rs); + FD_ZERO (&ws); + FD_ZERO (&es); + if (CURLM_OK != (mret = curl_multi_fdset (curl_multi, &rs, &ws, &es, &max))) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "%s failed at %s:%d: `%s'\n", + "curl_multi_fdset", __FILE__, __LINE__, + curl_multi_strerror (mret)); + //TODO cleanup here? + return; + } + to = -1; + GNUNET_break (CURLM_OK == curl_multi_timeout (curl_multi, &to)); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "cURL multi fds: max=%d timeout=%lld\n", max, (long long) to); + if (-1 == to) + rtime = GNUNET_TIME_UNIT_FOREVER_REL; + else + rtime = GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MILLISECONDS, to); + grs = GNUNET_NETWORK_fdset_create (); + gws = GNUNET_NETWORK_fdset_create (); + GNUNET_NETWORK_fdset_copy_native (grs, &rs, max + 1); + GNUNET_NETWORK_fdset_copy_native (gws, &ws, max + 1); + if (curl_download_task != GNUNET_SCHEDULER_NO_TASK) + GNUNET_SCHEDULER_cancel (curl_download_task); + if (-1 != max) + { + curl_download_task = + GNUNET_SCHEDULER_add_select (GNUNET_SCHEDULER_PRIORITY_DEFAULT, + rtime, + grs, gws, + &curl_task_download, curl_multi); + } + else if (NULL != ctasks_head) + { + /* as specified in curl docs */ + curl_download_task = GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_MILLISECONDS, + &curl_task_download, + curl_multi); + } + GNUNET_NETWORK_fdset_destroy (gws); + GNUNET_NETWORK_fdset_destroy (grs); +} + + +/** + * Task that is run when we are ready to receive more data + * from curl + * + * @param cls closure + * @param tc task context + */ +static void +curl_task_download (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + int running; + int msgnum; + struct CURLMsg *msg; + CURLMcode mret; + struct ProxyCurlTask *ctask; + int num_ctasks; + long resp_code; + struct ProxyCurlTask *clean_head = NULL; + struct ProxyCurlTask *clean_tail = NULL; + + curl_download_task = GNUNET_SCHEDULER_NO_TASK; + + if (0 != (tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Shutdown requested while trying to download\n"); + //TODO cleanup + return; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Ready to dl\n"); + + do + { + running = 0; + num_ctasks = 0; + + mret = curl_multi_perform (curl_multi, &running); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Running curl tasks: %d\n", running); + + for (ctask = ctasks_head; NULL != ctask; ctask = ctask->next) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "CTask: %s\n", ctask->url); + num_ctasks++; + } + + if (num_ctasks != running) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "%d ctasks, %d curl running\n", num_ctasks, running); + } + + do + { + + msg = curl_multi_info_read (curl_multi, &msgnum); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Messages left: %d\n", msgnum); + + if (msg == NULL) + break; + switch (msg->msg) + { + case CURLMSG_DONE: + if ((msg->data.result != CURLE_OK) && + (msg->data.result != CURLE_GOT_NOTHING)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Download curl failed"); + + for (ctask = ctasks_head; NULL != ctask; ctask = ctask->next) + { + if (NULL == ctask->curl) + continue; + + if (memcmp (msg->easy_handle, ctask->curl, sizeof (CURL)) != 0) + continue; + + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "CURL: Download failed for task %s: %s.\n", + ctask->url, + curl_easy_strerror (msg->data.result)); + ctask->download_is_finished = GNUNET_YES; + ctask->download_error = GNUNET_YES; + if (CURLE_OK == curl_easy_getinfo (ctask->curl, + CURLINFO_RESPONSE_CODE, + &resp_code)) + ctask->curl_response_code = resp_code; + ctask->ready_to_queue = MHD_YES; + ctask->buf_status = BUF_WAIT_FOR_MHD; + run_mhd_now (ctask->mhd); + + GNUNET_CONTAINER_DLL_remove (ctasks_head, ctasks_tail, + ctask); + GNUNET_CONTAINER_DLL_insert (clean_head, clean_tail, ctask); + break; + } + GNUNET_assert (ctask != NULL); + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "CURL: download completed.\n"); + + for (ctask = ctasks_head; NULL != ctask; ctask = ctask->next) + { + if (NULL == ctask->curl) + continue; + + if (0 != memcmp (msg->easy_handle, ctask->curl, sizeof (CURL))) + continue; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "CURL: completed task %s found.\n", ctask->url); + if (CURLE_OK == curl_easy_getinfo (ctask->curl, + CURLINFO_RESPONSE_CODE, + &resp_code)) + ctask->curl_response_code = resp_code; + + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "CURL: Completed ctask!\n"); + if (GNUNET_SCHEDULER_NO_TASK == ctask->pp_task) + { + ctask->buf_status = BUF_WAIT_FOR_PP; + ctask->pp_task = GNUNET_SCHEDULER_add_now (&postprocess_buffer, + ctask); + } + + ctask->ready_to_queue = MHD_YES; + ctask->download_is_finished = GNUNET_YES; + + /* We MUST not modify the multi handle else we loose messages */ + GNUNET_CONTAINER_DLL_remove (ctasks_head, ctasks_tail, + ctask); + GNUNET_CONTAINER_DLL_insert (clean_head, clean_tail, ctask); + + break; + } + GNUNET_assert (ctask != NULL); + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "CURL: %s\n", curl_easy_strerror(msg->data.result)); + break; + default: + GNUNET_assert (0); + break; + } + } while (msgnum > 0); + + for (ctask=clean_head; NULL != ctask; ctask = ctask->next) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "CURL: Removing task %s.\n", ctask->url); + curl_multi_remove_handle (curl_multi, ctask->curl); + curl_easy_cleanup (ctask->curl); + ctask->curl = NULL; + } + + num_ctasks=0; + for (ctask=ctasks_head; NULL != ctask; ctask = ctask->next) + num_ctasks++; + + if (num_ctasks != running) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "CURL: %d tasks, %d running\n", num_ctasks, running); + } + + GNUNET_assert ( num_ctasks == running ); + + } while (mret == CURLM_CALL_MULTI_PERFORM); + + if (mret != CURLM_OK) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "CURL: %s failed at %s:%d: `%s'\n", + "curl_multi_perform", __FILE__, __LINE__, + curl_multi_strerror (mret)); + } + curl_download_prepare(); +} + + +/** + * Process LEHO lookup + * + * @param cls the ctask + * @param rd_count number of records returned + * @param rd record data + */ +static void +process_leho_lookup (void *cls, + uint32_t rd_count, + const struct GNUNET_NAMESTORE_RecordData *rd) +{ + struct ProxyCurlTask *ctask = cls; + char hosthdr[262]; //256 + "Host: " + int i; + CURLcode ret; + CURLMcode mret; + struct hostent *phost; + char *ssl_ip; + char resolvename[512]; + char curlurl[512]; + + strcpy (ctask->leho, ""); + + if (rd_count == 0) + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "No LEHO present!\n"); + + for (i=0; ileho, rd[i].data, rd[i].data_size); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Found LEHO %s for %s\n", ctask->leho, ctask->url); + } + + if (0 != strcmp (ctask->leho, "")) + { + sprintf (hosthdr, "%s%s:%d", "Host: ", ctask->leho, ctask->port); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "New HTTP header value: %s\n", hosthdr); + ctask->headers = curl_slist_append (ctask->headers, hosthdr); + GNUNET_assert (NULL != ctask->headers); + ret = curl_easy_setopt (ctask->curl, CURLOPT_HTTPHEADER, ctask->headers); + if (CURLE_OK != ret) + { + GNUNET_log(GNUNET_ERROR_TYPE_WARNING, "%s failed at %s:%d: `%s'\n", + "curl_easy_setopt", __FILE__, __LINE__, curl_easy_strerror(ret)); + } + + } + + if (ctask->mhd->is_ssl) + { + phost = (struct hostent*)gethostbyname (ctask->host); + + if (phost!=NULL) + { + ssl_ip = inet_ntoa(*((struct in_addr*)(phost->h_addr))); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "SSL target server: %s\n", ssl_ip); + sprintf (resolvename, "%s:%d:%s", ctask->leho, HTTPS_PORT, ssl_ip); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Curl resolve: %s\n", resolvename); + ctask->resolver = curl_slist_append ( ctask->resolver, resolvename); + curl_easy_setopt (ctask->curl, CURLOPT_RESOLVE, ctask->resolver); + sprintf (curlurl, "https://%s:%d%s", ctask->leho, ctask->port, ctask->url); + curl_easy_setopt (ctask->curl, CURLOPT_URL, curlurl); + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "gethostbyname failed for %s!\n", ctask->host); + ctask->download_is_finished = GNUNET_YES; + ctask->download_error = GNUNET_YES; + return; + } + } + + if (CURLM_OK != (mret=curl_multi_add_handle (curl_multi, ctask->curl))) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "%s failed at %s:%d: `%s'\n", + "curl_multi_add_handle", __FILE__, __LINE__, + curl_multi_strerror (mret)); + ctask->download_is_finished = GNUNET_YES; + ctask->download_error = GNUNET_YES; + return; + } + GNUNET_CONTAINER_DLL_insert (ctasks_head, ctasks_tail, ctask); + + curl_download_prepare (); + +} + + +/** + * Initialize download and trigger curl + * + * @param cls the proxycurltask + * @param auth_name the name of the authority (site of origin) of ctask->host + * + */ +static void +process_get_authority (void *cls, + const char* auth_name) { - char* buf = (char*)cls; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "%s:%s\n", key, value); + struct ProxyCurlTask *ctask = cls; - if (0 == strcmp ("Host", key)) + if (NULL == auth_name) { - strcpy (buf, value); - return MHD_NO; + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Get authority failed!\n"); + strcpy (ctask->authority, ""); } - return MHD_YES; + else + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Get authority yielded %s\n", auth_name); + strcpy (ctask->authority, auth_name); + } + + GNUNET_GNS_lookup_zone (gns_handle, + ctask->host, + local_gns_zone, + GNUNET_GNS_RECORD_LEHO, + GNUNET_YES, //Only cached for performance + shorten_zonekey, + &process_leho_lookup, + ctask); +} + + +static void* +mhd_log_callback (void* cls, const char* url) +{ + struct ProxyCurlTask *ctask; + + ctask = GNUNET_malloc (sizeof (struct ProxyCurlTask)); + strcpy (ctask->url, url); + return ctask; } + /** * Main MHD callback for handling requests. * * @param cls unused - * @param connection MHD connection handle - * @param method the HTTP method used ("GET", "PUT", etc.) - * @param version the HTTP version string (i.e. "HTTP/1.1") + * @param con MHD connection handle + * @param url the url in the request + * @param meth the HTTP method used ("GET", "PUT", etc.) + * @param ver the HTTP version string (i.e. "HTTP/1.1") * @param upload_data the data being uploaded (excluding HEADERS, * for a POST that fits into memory and that is encoded * with a supported encoding, the POST data will NOT be @@ -114,7 +1886,7 @@ con_val_iter (void *cls, * @param upload_data_size set initially to the size of the * upload_data provided; the method must update this * value to the number of bytes NOT processed; - * @param ptr pointer to location where we store the 'struct Request' + * @param con_cls pointer to location where we store the 'struct Request' * @return MHD_YES if the connection was handled successfully, * MHD_NO if the socket must be closed due to a serious * error while handling the request @@ -129,58 +1901,277 @@ create_response (void *cls, size_t *upload_data_size, void **con_cls) { - static int dummy; - const char* page = "gnoxy"\ - "gnoxy demo"; - struct MHD_Response *response; - char host[265]; - int ret; + struct MhdHttpList* hd = cls; + const char* page = "gnunet-gns-proxy" + "cURL fail"; + + char curlurl[MAX_HTTP_URI_LENGTH]; // buffer overflow! + int ret = MHD_YES; + int i; + struct ProxyCurlTask *ctask = *con_cls; + struct ProxyUploadData *fin_post; + struct curl_forms forms[5]; + struct ProxyUploadData *upload_data_iter; - if (0 != strcmp (meth, "GET")) + //FIXME handle + if ((0 != strcasecmp (meth, MHD_HTTP_METHOD_GET)) && + (0 != strcasecmp (meth, MHD_HTTP_METHOD_PUT)) && + (0 != strcasecmp (meth, MHD_HTTP_METHOD_POST)) && + (0 != strcasecmp (meth, MHD_HTTP_METHOD_HEAD))) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "MHD: %s NOT IMPLEMENTED!\n", meth); return MHD_NO; - if (&dummy != *con_cls) + } + + + if (GNUNET_NO == ctask->accepted) { - *con_cls = &dummy; + + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + "Got %s request for %s\n", meth, url); + ctask->mhd = hd; + ctask->curl = curl_easy_init(); + ctask->curl_running = GNUNET_NO; + if (NULL == ctask->curl) + { + ctask->response = MHD_create_response_from_buffer (strlen (page), + (void*)page, + MHD_RESPMEM_PERSISTENT); + ret = MHD_queue_response (con, + MHD_HTTP_OK, + ctask->response); + MHD_destroy_response (ctask->response); + GNUNET_free (ctask); + return ret; + } + + if (ctask->mhd->is_ssl) + ctask->port = HTTPS_PORT; + else + ctask->port = HTTP_PORT; + + MHD_get_connection_values (con, + MHD_HEADER_KIND, + &con_val_iter, ctask); + + curl_easy_setopt (ctask->curl, CURLOPT_HEADERFUNCTION, &curl_check_hdr); + curl_easy_setopt (ctask->curl, CURLOPT_HEADERDATA, ctask); + curl_easy_setopt (ctask->curl, CURLOPT_WRITEFUNCTION, &curl_download_cb); + curl_easy_setopt (ctask->curl, CURLOPT_WRITEDATA, ctask); + curl_easy_setopt (ctask->curl, CURLOPT_FOLLOWLOCATION, 0); + curl_easy_setopt (ctask->curl, CURLOPT_IPRESOLVE, CURL_IPRESOLVE_V4); + + if (GNUNET_NO == ctask->mhd->is_ssl) + { + sprintf (curlurl, "http://%s:%d%s", ctask->host, ctask->port, ctask->url); + curl_easy_setopt (ctask->curl, CURLOPT_URL, curlurl); + } + + + curl_easy_setopt (ctask->curl, CURLOPT_FAILONERROR, 1); + curl_easy_setopt (ctask->curl, CURLOPT_CONNECTTIMEOUT, 600L); + curl_easy_setopt (ctask->curl, CURLOPT_TIMEOUT, 600L); + + /* Add GNS header */ + ctask->headers = curl_slist_append (ctask->headers, + "GNS: YES"); + ctask->accepted = GNUNET_YES; + ctask->download_in_progress = GNUNET_YES; + ctask->buf_status = BUF_WAIT_FOR_CURL; + ctask->connection = con; + ctask->curl_response_code = MHD_HTTP_OK; + ctask->buffer_read_ptr = ctask->buffer; + ctask->buffer_write_ptr = ctask->buffer; + ctask->pp_task = GNUNET_SCHEDULER_NO_TASK; + + + if (0 == strcasecmp (meth, MHD_HTTP_METHOD_PUT)) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Setting up PUT\n"); + + curl_easy_setopt (ctask->curl, CURLOPT_UPLOAD, 1); + curl_easy_setopt (ctask->curl, CURLOPT_READDATA, ctask); + curl_easy_setopt (ctask->curl, CURLOPT_READFUNCTION, &put_read_callback); + ctask->headers = curl_slist_append (ctask->headers, + "Transfer-Encoding: chunked"); + } + + if (0 == strcasecmp (meth, MHD_HTTP_METHOD_POST)) + { + //FIXME handle multipart + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Setting up POST processor\n"); + ctask->post_handler = MHD_create_post_processor (con, + POSTBUFFERSIZE, + &con_post_data_iter, + ctask); + ctask->headers = curl_slist_append (ctask->headers, + "Transfer-Encoding: chunked"); + return MHD_YES; + } + + if (0 == strcasecmp (meth, MHD_HTTP_METHOD_HEAD)) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Setting NOBODY\n"); + curl_easy_setopt (ctask->curl, CURLOPT_NOBODY, 1); + } + + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "MHD: Adding new curl task for %s\n", ctask->host); + + GNUNET_GNS_get_authority (gns_handle, + ctask->host, + &process_get_authority, + ctask); + ctask->ready_to_queue = GNUNET_NO; + ctask->fin = GNUNET_NO; + ctask->curl_running = GNUNET_YES; return MHD_YES; } - if (0 != *upload_data_size) - return MHD_NO; + ctask = (struct ProxyCurlTask *) *con_cls; + if (0 == strcasecmp (meth, MHD_HTTP_METHOD_POST)) + { + if (0 != *upload_data_size) + { + + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + "Invoking POST processor\n"); + MHD_post_process (ctask->post_handler, + upload_data, *upload_data_size); + *upload_data_size = 0; + if ((GNUNET_NO == ctask->is_httppost) && + (GNUNET_NO == ctask->curl_running)) + { + curl_easy_setopt (ctask->curl, CURLOPT_POST, 1); + curl_easy_setopt (ctask->curl, CURLOPT_READFUNCTION, + &post_read_callback); + curl_easy_setopt (ctask->curl, CURLOPT_READDATA, ctask); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "MHD: Adding new curl task for %s\n", ctask->host); + + GNUNET_GNS_get_authority (gns_handle, + ctask->host, + &process_get_authority, + ctask); + ctask->ready_to_queue = GNUNET_NO; + ctask->fin = GNUNET_NO; + ctask->curl_running = GNUNET_YES; + } + return MHD_YES; + } + else if (GNUNET_NO == ctask->post_done) + { + if (GNUNET_YES == ctask->is_httppost) + { + for (upload_data_iter = ctask->upload_data_head; + NULL != upload_data_iter; + upload_data_iter = upload_data_iter->next) + { + i = 0; + if (NULL != upload_data_iter->filename) + { + forms[i].option = CURLFORM_FILENAME; + forms[i].value = upload_data_iter->filename; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Adding filename %s\n", + forms[i].value); + i++; + } + if (NULL != upload_data_iter->content_type) + { + forms[i].option = CURLFORM_CONTENTTYPE; + forms[i].value = upload_data_iter->content_type; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Adding content type %s\n", + forms[i].value); + i++; + } + forms[i].option = CURLFORM_PTRCONTENTS; + forms[i].value = upload_data_iter->value; + forms[i+1].option = CURLFORM_END; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Adding formdata for %s (len=%lld)\n", + upload_data_iter->key, + upload_data_iter->total_bytes); + + curl_formadd(&ctask->httppost, &ctask->httppost_last, + CURLFORM_COPYNAME, upload_data_iter->key, + CURLFORM_CONTENTSLENGTH, upload_data_iter->total_bytes, + CURLFORM_ARRAY, forms, + CURLFORM_END); + } + curl_easy_setopt (ctask->curl, CURLOPT_HTTPPOST, + ctask->httppost); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "MHD: Adding new curl task for %s\n", ctask->host); + + GNUNET_GNS_get_authority (gns_handle, + ctask->host, + &process_get_authority, + ctask); + ctask->ready_to_queue = GNUNET_YES; + ctask->fin = GNUNET_NO; + ctask->curl_running = GNUNET_YES; + ctask->post_done = GNUNET_YES; + return MHD_YES; + } - *con_cls = NULL; + fin_post = GNUNET_malloc (sizeof (struct ProxyUploadData)); + GNUNET_CONTAINER_DLL_insert_tail (ctask->upload_data_head, + ctask->upload_data_tail, + fin_post); + ctask->post_done = GNUNET_YES; + return MHD_YES; + } + } + + if (GNUNET_YES != ctask->ready_to_queue) + return MHD_YES; /* wait longer */ + + if (GNUNET_YES == ctask->fin) + return MHD_YES; + ctask->fin = GNUNET_YES; GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "url %s\n", url); - - MHD_get_connection_values (con, - MHD_HEADER_KIND, - &con_val_iter, host); - - response = MHD_create_response_from_buffer (strlen (page), - (void*)page, - MHD_RESPMEM_PERSISTENT); - ret = MHD_queue_response (con, - MHD_HTTP_OK, - response); - MHD_destroy_response (response); + "MHD: Queueing response for %s\n", ctask->url); + ret = MHD_queue_response (con, ctask->curl_response_code, ctask->response); + run_mhd_now (ctask->mhd); return ret; } + /** - * Task run whenever HTTP server operations are pending. - * - * @param cls unused - * @param tc sched context + * run all httpd */ static void -do_httpd (void *cls, - const struct GNUNET_SCHEDULER_TaskContext *tc); +run_httpds () +{ + struct MhdHttpList *hd; + + for (hd=mhd_httpd_head; NULL != hd; hd = hd->next) + run_httpd (hd); + +} + + +#define UNSIGNED_MHD_LONG_LONG unsigned MHD_LONG_LONG + /** - * Schedule MHD + * schedule mhd + * + * @param hd the daemon to run */ static void -run_httpd () +run_httpd (struct MhdHttpList *hd) { fd_set rs; fd_set ws; @@ -190,7 +2181,7 @@ run_httpd () struct GNUNET_NETWORK_FDSet *wes; int max; int haveto; - unsigned MHD_LONG_LONG timeout; + UNSIGNED_MHD_LONG_LONG timeout; struct GNUNET_TIME_Relative tv; FD_ZERO (&rs); @@ -200,10 +2191,15 @@ run_httpd () wes = GNUNET_NETWORK_fdset_create (); wws = GNUNET_NETWORK_fdset_create (); max = -1; - GNUNET_assert (MHD_YES == MHD_get_fdset (httpd, &rs, &ws, &es, &max)); - haveto = MHD_get_timeout (httpd, &timeout); + GNUNET_assert (MHD_YES == MHD_get_fdset (hd->daemon, &rs, &ws, &es, &max)); + + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "MHD fds: max=%d\n", max); + + haveto = MHD_get_timeout (hd->daemon, &timeout); - if (haveto == MHD_YES) + if (MHD_YES == haveto) tv.rel_value = (uint64_t) timeout; else tv = GNUNET_TIME_UNIT_FOREVER_REL; @@ -211,17 +2207,18 @@ run_httpd () GNUNET_NETWORK_fdset_copy_native (wws, &ws, max + 1); GNUNET_NETWORK_fdset_copy_native (wes, &es, max + 1); - if (httpd_task != GNUNET_SCHEDULER_NO_TASK) - GNUNET_SCHEDULER_cancel (httpd_task); - httpd_task = + if (GNUNET_SCHEDULER_NO_TASK != hd->httpd_task) + GNUNET_SCHEDULER_cancel (hd->httpd_task); + hd->httpd_task = GNUNET_SCHEDULER_add_select (GNUNET_SCHEDULER_PRIORITY_HIGH, tv, wrs, wws, - &do_httpd, NULL); + &do_httpd, hd); GNUNET_NETWORK_fdset_destroy (wrs); GNUNET_NETWORK_fdset_destroy (wws); GNUNET_NETWORK_fdset_destroy (wes); } + /** * Task run whenever HTTP server operations are pending. * @@ -232,11 +2229,16 @@ static void do_httpd (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { - httpd_task = GNUNET_SCHEDULER_NO_TASK; - MHD_run (httpd); - run_httpd (); + struct MhdHttpList *hd = cls; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "MHD: Main loop\n"); + hd->httpd_task = GNUNET_SCHEDULER_NO_TASK; + MHD_run (hd->daemon); + run_httpd (hd); } + /** * Read data from socket * @@ -246,6 +2248,7 @@ do_httpd (void *cls, static void do_read (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc); + /** * Read from remote end * @@ -255,6 +2258,7 @@ do_read (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc); static void do_read_remote (void* cls, const struct GNUNET_SCHEDULER_TaskContext *tc); + /** * Write data to remote socket * @@ -271,8 +2275,8 @@ do_write_remote (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) if ((NULL != tc->read_ready) && (GNUNET_NETWORK_fdset_isset (tc->write_ready, s5r->remote_sock)) && - (len = GNUNET_NETWORK_socket_send (s5r->remote_sock, s5r->rbuf, - s5r->rbuf_len))) + ((len = GNUNET_NETWORK_socket_send (s5r->remote_sock, s5r->rbuf, + s5r->rbuf_len)>0))) { GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Successfully sent %d bytes to remote socket\n", @@ -281,12 +2285,11 @@ do_write_remote (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) else { GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "write remote"); - //Really!?!?!? - if (s5r->rtask != GNUNET_SCHEDULER_NO_TASK) + if (GNUNET_SCHEDULER_NO_TASK != s5r->rtask) GNUNET_SCHEDULER_cancel (s5r->rtask); - if (s5r->wtask != GNUNET_SCHEDULER_NO_TASK) + if (GNUNET_SCHEDULER_NO_TASK != s5r->wtask) GNUNET_SCHEDULER_cancel (s5r->wtask); - if (s5r->fwdrtask != GNUNET_SCHEDULER_NO_TASK) + if (GNUNET_SCHEDULER_NO_TASK != s5r->fwdrtask) GNUNET_SCHEDULER_cancel (s5r->fwdrtask); GNUNET_NETWORK_socket_close (s5r->remote_sock); GNUNET_NETWORK_socket_close (s5r->sock); @@ -301,6 +2304,29 @@ do_write_remote (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) } +/** + * Clean up s5r handles + * + * @param s5r the handle to destroy + */ +static void +cleanup_s5r (struct Socks5Request *s5r) +{ + if (GNUNET_SCHEDULER_NO_TASK != s5r->rtask) + GNUNET_SCHEDULER_cancel (s5r->rtask); + if (GNUNET_SCHEDULER_NO_TASK != s5r->fwdwtask) + GNUNET_SCHEDULER_cancel (s5r->fwdwtask); + if (GNUNET_SCHEDULER_NO_TASK != s5r->fwdrtask) + GNUNET_SCHEDULER_cancel (s5r->fwdrtask); + if (NULL != s5r->remote_sock) + GNUNET_NETWORK_socket_close (s5r->remote_sock); + if ((NULL != s5r->sock) && (s5r->cleanup_sock == GNUNET_YES)) + GNUNET_NETWORK_socket_close (s5r->sock); + + GNUNET_free(s5r); +} + + /** * Write data to socket * @@ -317,100 +2343,384 @@ do_write (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) if ((NULL != tc->read_ready) && (GNUNET_NETWORK_fdset_isset (tc->write_ready, s5r->sock)) && - (len = GNUNET_NETWORK_socket_send (s5r->sock, s5r->wbuf, - s5r->wbuf_len))) + ((len = GNUNET_NETWORK_socket_send (s5r->sock, s5r->wbuf, + s5r->wbuf_len)>0))) { GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Successfully sent %d bytes to socket\n", len); } else - { - + { GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "write"); - //Really!?!?!? - if (s5r->rtask != GNUNET_SCHEDULER_NO_TASK) - GNUNET_SCHEDULER_cancel (s5r->rtask); + s5r->cleanup = GNUNET_YES; + s5r->cleanup_sock = GNUNET_YES; + cleanup_s5r (s5r); + return; + } + + if (GNUNET_YES == s5r->cleanup) + { + cleanup_s5r (s5r); + return; + } + + if ((s5r->state == SOCKS5_DATA_TRANSFER) && + (s5r->fwdrtask == GNUNET_SCHEDULER_NO_TASK)) + s5r->fwdrtask = + GNUNET_SCHEDULER_add_read_net (GNUNET_TIME_UNIT_FOREVER_REL, + s5r->remote_sock, + &do_read_remote, s5r); +} + + +/** + * Read from remote end + * + * @param cls closure + * @param tc scheduler context + */ +static void +do_read_remote (void* cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct Socks5Request *s5r = cls; + + s5r->fwdrtask = GNUNET_SCHEDULER_NO_TASK; + if ((NULL != tc->write_ready) && + (GNUNET_NETWORK_fdset_isset (tc->read_ready, s5r->remote_sock)) && + (s5r->wbuf_len = GNUNET_NETWORK_socket_recv (s5r->remote_sock, s5r->wbuf, + sizeof (s5r->wbuf)))) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Successfully read %d bytes from remote socket\n", + s5r->wbuf_len); + } + else + { + if (0 == s5r->wbuf_len) + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "0 bytes received from remote... graceful shutdown!\n"); if (s5r->fwdwtask != GNUNET_SCHEDULER_NO_TASK) GNUNET_SCHEDULER_cancel (s5r->fwdwtask); - if (s5r->fwdrtask != GNUNET_SCHEDULER_NO_TASK) - GNUNET_SCHEDULER_cancel (s5r->fwdrtask); + if (s5r->rtask != GNUNET_SCHEDULER_NO_TASK) + GNUNET_SCHEDULER_cancel (s5r->rtask); + GNUNET_NETWORK_socket_close (s5r->remote_sock); + s5r->remote_sock = NULL; GNUNET_NETWORK_socket_close (s5r->sock); GNUNET_free(s5r); + return; } + + s5r->wtask = GNUNET_SCHEDULER_add_write_net (GNUNET_TIME_UNIT_FOREVER_REL, + s5r->sock, + &do_write, s5r); +} + + +/** + * Adds a socket to MHD + * + * @param h the handle to the socket to add + * @param daemon the daemon to add the fd to + * @return whatever MHD_add_connection returns + */ +static int +add_handle_to_mhd (struct GNUNET_NETWORK_Handle *h, struct MHD_Daemon *daemon) +{ + int fd; + struct sockaddr *addr; + socklen_t len; + + fd = dup (GNUNET_NETWORK_get_fd (h)); + addr = GNUNET_NETWORK_get_addr (h); + len = GNUNET_NETWORK_get_addrlen (h); + + return MHD_add_connection (daemon, fd, addr, len); +} + + +/** + * Read file in filename + * + * @param filename file to read + * @param size pointer where filesize is stored + * @return NULL on error + */ +static void* +load_file (const char* filename, + unsigned int* size) +{ + void *buffer; + uint64_t fsize; + + if (GNUNET_OK != + GNUNET_DISK_file_size (filename, &fsize, + GNUNET_YES, GNUNET_YES)) + return NULL; + if (fsize > MAX_PEM_SIZE) + return NULL; + *size = (unsigned int) fsize; + buffer = GNUNET_malloc (*size); + if (fsize != GNUNET_DISK_fn_read (filename, buffer, (size_t) fsize)) + { + GNUNET_free (buffer); + return NULL; + } + return buffer; +} + + +/** + * Load PEM key from file + * + * @param key where to store the data + * @param keyfile path to the PEM file + * @return GNUNET_OK on success + */ +static int +load_key_from_file (gnutls_x509_privkey_t key, const char* keyfile) +{ + gnutls_datum_t key_data; + int ret; + + key_data.data = load_file (keyfile, &key_data.size); + ret = gnutls_x509_privkey_import (key, &key_data, + GNUTLS_X509_FMT_PEM); + if (GNUTLS_E_SUCCESS != ret) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Unable to import private key from file `%s'\n"), + keyfile); + GNUNET_break (0); + } + GNUNET_free (key_data.data); + return (GNUTLS_E_SUCCESS != ret) ? GNUNET_SYSERR : GNUNET_OK; +} + + +/** + * Load cert from file + * + * @param crt struct to store data in + * @param certfile path to pem file + * @return GNUNET_OK on success + */ +static int +load_cert_from_file (gnutls_x509_crt_t crt, char* certfile) +{ + gnutls_datum_t cert_data; + int ret; + + cert_data.data = load_file (certfile, &cert_data.size); + ret = gnutls_x509_crt_import (crt, &cert_data, + GNUTLS_X509_FMT_PEM); + if (GNUTLS_E_SUCCESS != ret) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Unable to import certificate %s\n"), certfile); + GNUNET_break (0); + } + GNUNET_free (cert_data.data); + return (GNUTLS_E_SUCCESS != ret) ? GNUNET_SYSERR : GNUNET_OK; +} + + +/** + * Generate new certificate for specific name + * + * @param name the subject name to generate a cert for + * @return a struct holding the PEM data + */ +static struct ProxyGNSCertificate * +generate_gns_certificate (const char *name) +{ + int ret; + unsigned int serial; + size_t key_buf_size; + size_t cert_buf_size; + gnutls_x509_crt_t request; + time_t etime; + struct tm *tm_data; + + ret = gnutls_x509_crt_init (&request); + + if (GNUTLS_E_SUCCESS != ret) + { + GNUNET_break (0); + } + + GNUNET_break (GNUTLS_E_SUCCESS == gnutls_x509_crt_set_key (request, proxy_ca.key)); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Generating cert\n"); + + struct ProxyGNSCertificate *pgc = + GNUNET_malloc (sizeof (struct ProxyGNSCertificate)); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Adding DNs\n"); + + gnutls_x509_crt_set_dn_by_oid (request, GNUTLS_OID_X520_COUNTRY_NAME, + 0, "DE", 2); + gnutls_x509_crt_set_dn_by_oid (request, GNUTLS_OID_X520_ORGANIZATION_NAME, + 0, "GADS", 4); + gnutls_x509_crt_set_dn_by_oid (request, GNUTLS_OID_X520_COMMON_NAME, + 0, name, strlen (name)); + GNUNET_break (GNUTLS_E_SUCCESS == gnutls_x509_crt_set_version (request, 3)); + + ret = gnutls_rnd (GNUTLS_RND_NONCE, &serial, sizeof (serial)); + + etime = time (NULL); + tm_data = localtime (&etime); + + + ret = gnutls_x509_crt_set_serial (request, + &serial, + sizeof (serial)); + + ret = gnutls_x509_crt_set_activation_time (request, + etime); + tm_data->tm_year++; + etime = mktime (tm_data); + + if (-1 == etime) + { + GNUNET_break (0); + } + + ret = gnutls_x509_crt_set_expiration_time (request, + etime); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Signing...\n"); + + ret = gnutls_x509_crt_sign (request, proxy_ca.cert, proxy_ca.key); + + key_buf_size = sizeof (pgc->key); + cert_buf_size = sizeof (pgc->cert); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Exporting certificate...\n"); + + gnutls_x509_crt_export (request, GNUTLS_X509_FMT_PEM, + pgc->cert, &cert_buf_size); + + gnutls_x509_privkey_export (proxy_ca.key, GNUTLS_X509_FMT_PEM, + pgc->key, &key_buf_size); + + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Cleaning up\n"); + gnutls_x509_crt_deinit (request); + + return pgc; - if ((s5r->state == SOCKS5_DATA_TRANSFER) && - (s5r->fwdrtask == GNUNET_SCHEDULER_NO_TASK)) - s5r->fwdrtask = - GNUNET_SCHEDULER_add_read_net (GNUNET_TIME_UNIT_FOREVER_REL, - s5r->remote_sock, - &do_read_remote, s5r); } + /** - * Read from remote end + * Accept policy for mhdaemons * - * @param cls closure - * @param tc scheduler context + * @param cls NULL + * @param addr the sockaddr + * @param addrlen the sockaddr length + * @return MHD_NO if sockaddr is wrong or number of connections is too high */ -static void -do_read_remote (void* cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +static int +accept_cb (void* cls, const struct sockaddr *addr, socklen_t addrlen) { - struct Socks5Request *s5r = cls; - - s5r->fwdrtask = GNUNET_SCHEDULER_NO_TASK; - + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "In MHD accept policy cb\n"); - if ((NULL != tc->write_ready) && - (GNUNET_NETWORK_fdset_isset (tc->read_ready, s5r->remote_sock)) && - (s5r->wbuf_len = GNUNET_NETWORK_socket_recv (s5r->remote_sock, s5r->wbuf, - sizeof (s5r->wbuf)))) + if (addr != NULL) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Successfully read %d bytes from remote socket\n", - s5r->wbuf_len); + if (addr->sa_family == AF_UNIX) + return MHD_NO; } - else - { - if (s5r->wbuf_len == 0) - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "0 bytes received from remote... graceful shutdown!\n"); - if (s5r->fwdwtask != GNUNET_SCHEDULER_NO_TASK) - GNUNET_SCHEDULER_cancel (s5r->fwdwtask); - if (s5r->rtask != GNUNET_SCHEDULER_NO_TASK) - GNUNET_SCHEDULER_cancel (s5r->rtask); - - GNUNET_NETWORK_socket_close (s5r->remote_sock); - s5r->remote_sock = NULL; - GNUNET_NETWORK_socket_close (s5r->sock); - GNUNET_free(s5r); - return; - } - - s5r->wtask = GNUNET_SCHEDULER_add_write_net (GNUNET_TIME_UNIT_FOREVER_REL, - s5r->sock, - &do_write, s5r); - + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Connection accepted\n"); + + return MHD_YES; } +/** + * Adds a socket to an SSL MHD instance + * It is important the the domain name is + * correct. In most cases we need to start a new daemon + * + * @param h the handle to add to a daemon + * @param domain the domain the ssl daemon has to serve + * @return MHD_YES on success + */ static int -add_handle_to_mhd (struct GNUNET_NETWORK_Handle *h) +add_handle_to_ssl_mhd (struct GNUNET_NETWORK_Handle *h, const char* domain) { - int fd; - struct sockaddr *addr; - socklen_t len; + struct MhdHttpList *hd; + struct ProxyGNSCertificate *pgc; + struct NetworkHandleList *nh; - fd = GNUNET_NETWORK_get_fd (h); - addr = GNUNET_NETWORK_get_addr (h); - len = GNUNET_NETWORK_get_addrlen (h); + for (hd = mhd_httpd_head; NULL != hd; hd = hd->next) + if (0 == strcmp (hd->domain, domain)) + break; + + if (NULL == hd) + { + pgc = generate_gns_certificate (domain); + + hd = GNUNET_malloc (sizeof (struct MhdHttpList)); + hd->is_ssl = GNUNET_YES; + strcpy (hd->domain, domain); + hd->proxy_cert = pgc; + + /* Start new MHD */ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "No previous SSL instance found... starting new one for %s\n", + domain); +#if HAVE_MHD_NO_LISTEN_SOCKET + hd->daemon = MHD_start_daemon (MHD_USE_DEBUG | MHD_USE_SSL | MHD_USE_NO_LISTEN_SOCKET, + 0, + &accept_cb, NULL, + &create_response, hd, + MHD_OPTION_CONNECTION_LIMIT, + MHD_MAX_CONNECTIONS, + MHD_OPTION_CONNECTION_TIMEOUT, (unsigned int) 16, + MHD_OPTION_NOTIFY_COMPLETED, NULL, NULL, + MHD_OPTION_HTTPS_MEM_KEY, pgc->key, + MHD_OPTION_HTTPS_MEM_CERT, pgc->cert, + MHD_OPTION_URI_LOG_CALLBACK, &mhd_log_callback, + NULL, + MHD_OPTION_END); +#else + hd->daemon = MHD_start_daemon (MHD_USE_DEBUG | MHD_USE_SSL, + 4444 /* dummy port */, + &accept_cb, NULL, + &create_response, hd, + MHD_OPTION_LISTEN_SOCKET, GNUNET_NETWORK_get_fd (mhd_unix_socket), + MHD_OPTION_CONNECTION_LIMIT, + MHD_MAX_CONNECTIONS, + MHD_OPTION_CONNECTION_TIMEOUT, (unsigned int) 16, + MHD_OPTION_NOTIFY_COMPLETED, NULL, NULL, + MHD_OPTION_HTTPS_MEM_KEY, pgc->key, + MHD_OPTION_HTTPS_MEM_CERT, pgc->cert, + MHD_OPTION_URI_LOG_CALLBACK, &mhd_log_callback, + NULL, + MHD_OPTION_END); +#endif + GNUNET_assert (hd->daemon != NULL); + hd->httpd_task = GNUNET_SCHEDULER_NO_TASK; + + GNUNET_CONTAINER_DLL_insert (mhd_httpd_head, mhd_httpd_tail, hd); + } - return MHD_add_connection (httpd, fd, addr, len); + nh = GNUNET_malloc (sizeof (struct NetworkHandleList)); + nh->h = h; + + GNUNET_CONTAINER_DLL_insert (hd->socket_handles_head, + hd->socket_handles_tail, + nh); + + return add_handle_to_mhd (h, hd->daemon); } + /** * Read data from incoming connection * @@ -425,7 +2735,7 @@ do_read (void* cls, const struct GNUNET_SCHEDULER_TaskContext *tc) struct socks5_server_hello *s_hello; struct socks5_client_request *c_req; struct socks5_server_response *s_resp; - + int ret; char domain[256]; uint8_t dom_len; uint16_t req_port; @@ -433,6 +2743,7 @@ do_read (void* cls, const struct GNUNET_SCHEDULER_TaskContext *tc) uint32_t remote_ip; struct sockaddr_in remote_addr; struct in_addr *r_sin_addr; + struct NetworkHandleList *nh; s5r->rtask = GNUNET_SCHEDULER_NO_TASK; @@ -518,39 +2829,56 @@ do_read (void* cls, const struct GNUNET_SCHEDULER_TaskContext *tc) GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Requested connection is gnunet tld\n", domain); + + ret = MHD_NO; + if (ntohs(req_port) == HTTPS_PORT) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Requested connection is HTTPS\n"); + ret = add_handle_to_ssl_mhd ( s5r->sock, domain ); + } + else if (NULL != httpd) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Requested connection is HTTP\n"); + nh = GNUNET_malloc (sizeof (struct NetworkHandleList)); + nh->h = s5r->sock; + + GNUNET_CONTAINER_DLL_insert (mhd_httpd_head->socket_handles_head, + mhd_httpd_head->socket_handles_tail, + nh); - if (NULL == httpd) + ret = add_handle_to_mhd ( s5r->sock, httpd ); + } + + if (ret != MHD_YES) { GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("Failed to start HTTP server\n")); s_resp->version = 0x05; s_resp->reply = 0x01; + s5r->cleanup = GNUNET_YES; + s5r->cleanup_sock = GNUNET_YES; s5r->wtask = GNUNET_SCHEDULER_add_write_net (GNUNET_TIME_UNIT_FOREVER_REL, s5r->sock, &do_write, s5r); - //ERROR! - //TODO! close socket after the write! schedule task - //GNUNET_NETWORK_socket_close (s5r->sock); - //GNUNET_free(s5r); return; } - - if (MHD_YES == add_handle_to_mhd ( s5r->sock )) - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Sucessfully added client to MHD!\n"); + + /* Signal success */ s_resp->version = 0x05; s_resp->reply = 0x00; s_resp->reserved = 0x00; s_resp->addr_type = 0x01; - + + s5r->cleanup = GNUNET_YES; + s5r->cleanup_sock = GNUNET_NO; s5r->wtask = GNUNET_SCHEDULER_add_write_net (GNUNET_TIME_UNIT_FOREVER_REL, s5r->sock, &do_write, s5r); - run_httpd (); - //GNUNET_free ( s5r ); - //FIXME complete socks resp! + run_httpds (); return; } else @@ -562,14 +2890,12 @@ do_read (void* cls, const struct GNUNET_SCHEDULER_TaskContext *tc) "Resolve %s error!\n", domain ); s_resp->version = 0x05; s_resp->reply = 0x01; + s5r->cleanup = GNUNET_YES; + s5r->cleanup_sock = GNUNET_YES; s5r->wtask = GNUNET_SCHEDULER_add_write_net (GNUNET_TIME_UNIT_FOREVER_REL, s5r->sock, &do_write, s5r); - //ERROR! - //TODO! close socket after the write! schedule task - //GNUNET_NETWORK_socket_close (s5r->sock); - //GNUNET_free(s5r); return; } @@ -669,14 +2995,10 @@ do_read (void* cls, const struct GNUNET_SCHEDULER_TaskContext *tc) s5r->remote_sock, &do_read_remote, s5r); } - - } - - //GNUNET_CONTAINER_DLL_remove (s5conns.head, s5conns.tail, s5r); - } + /** * Accept new incoming connections * @@ -701,7 +3023,7 @@ do_accept (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) if (NULL == s) { - GNUNET_log_strerror (GNUNET_ERROR_TYPE_INFO, "accept"); + GNUNET_log_strerror (GNUNET_ERROR_TYPE_ERROR, "accept"); return; } @@ -717,9 +3039,251 @@ do_accept (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) s5r->rtask = GNUNET_SCHEDULER_add_read_net (GNUNET_TIME_UNIT_FOREVER_REL, s5r->sock, &do_read, s5r); - //GNUNET_CONTAINER_DLL_insert (s5conns.head, s5conns.tail, s5r); } + +/** + * Task run on shutdown + * + * @param cls closure + * @param tc task context + */ +static void +do_shutdown (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct MhdHttpList *hd; + struct MhdHttpList *tmp_hd; + struct NetworkHandleList *nh; + struct NetworkHandleList *tmp_nh; + struct ProxyCurlTask *ctask; + struct ProxyCurlTask *ctask_tmp; + struct ProxyUploadData *pdata; + + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + "Shutting down...\n"); + if (NULL != local_gns_zone) + GNUNET_free (local_gns_zone); + if (NULL != local_private_zone) + GNUNET_free (local_private_zone); + if (NULL != local_shorten_zone) + GNUNET_free (local_shorten_zone); + + if (GNUNET_SCHEDULER_NO_TASK != curl_download_task) + { + GNUNET_SCHEDULER_cancel (curl_download_task); + curl_download_task = GNUNET_SCHEDULER_NO_TASK; + } + + for (hd = mhd_httpd_head; hd != NULL; hd = tmp_hd) + { + tmp_hd = hd->next; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Stopping daemon\n"); + + if (GNUNET_SCHEDULER_NO_TASK != hd->httpd_task) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Stopping select task %d\n", + hd->httpd_task); + GNUNET_SCHEDULER_cancel (hd->httpd_task); + hd->httpd_task = GNUNET_SCHEDULER_NO_TASK; + } + if (NULL != hd->daemon) + { + MHD_stop_daemon (hd->daemon); + hd->daemon = NULL; + } + for (nh = hd->socket_handles_head; nh != NULL; nh = tmp_nh) + { + tmp_nh = nh->next; + + GNUNET_NETWORK_socket_close (nh->h); + + GNUNET_free (nh); + } + + if (NULL != hd->proxy_cert) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Free certificate\n"); + GNUNET_free (hd->proxy_cert); + } + + GNUNET_free (hd); + } + + for (ctask=ctasks_head; ctask != NULL; ctask=ctask_tmp) + { + ctask_tmp = ctask->next; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Cleaning up cURL task\n"); + + if (ctask->curl != NULL) + curl_easy_cleanup (ctask->curl); + ctask->curl = NULL; + if (NULL != ctask->headers) + curl_slist_free_all (ctask->headers); + if (NULL != ctask->resolver) + curl_slist_free_all (ctask->resolver); + + if (NULL != ctask->response) + MHD_destroy_response (ctask->response); + + pdata = ctask->upload_data_head; + + //FIXME free pdata here + for (; pdata != NULL; pdata = ctask->upload_data_head) + { + GNUNET_CONTAINER_DLL_remove (ctask->upload_data_head, + ctask->upload_data_tail, + pdata); + GNUNET_free_non_null (pdata->filename); + GNUNET_free_non_null (pdata->content_type); + GNUNET_free_non_null (pdata->key); + GNUNET_free_non_null (pdata->value); + GNUNET_free (pdata); + } + GNUNET_free (ctask); + } + curl_multi_cleanup (curl_multi); + GNUNET_GNS_disconnect (gns_handle); + gnutls_global_deinit (); +} + + +/** + * Compiles a regex for us + * + * @param re ptr to re struct + * @param rt the expression to compile + * @return 0 on success + */ +static int +compile_regex (regex_t *re, const char* rt) +{ + int status; + char err[1024]; + + status = regcomp (re, rt, REG_EXTENDED|REG_NEWLINE); + if (status) + { + regerror (status, re, err, 1024); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Regex error compiling '%s': %s\n", rt, err); + return 1; + } + return 0; +} + + +/** + * Loads the users local zone key + * + * @return GNUNET_YES on success + */ +static int +load_local_zone_key (const struct GNUNET_CONFIGURATION_Handle *cfg) +{ + char *keyfile; + struct GNUNET_CRYPTO_RsaPrivateKey *key; + struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded pkey; + struct GNUNET_CRYPTO_ShortHashCode *zone; + struct GNUNET_CRYPTO_ShortHashAsciiEncoded zonename; + + if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_filename (cfg, "gns", + "ZONEKEY", &keyfile)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Unable to load zone key config value!\n"); + return GNUNET_NO; + } + + if (GNUNET_NO == GNUNET_DISK_file_test (keyfile)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Unable to load zone key %s!\n", keyfile); + GNUNET_free(keyfile); + return GNUNET_NO; + } + + key = GNUNET_CRYPTO_rsa_key_create_from_file (keyfile); + GNUNET_CRYPTO_rsa_key_get_public (key, &pkey); + local_gns_zone = GNUNET_malloc (sizeof (struct GNUNET_CRYPTO_ShortHashCode)); + GNUNET_CRYPTO_short_hash(&pkey, + sizeof(struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded), + local_gns_zone); + zone = local_gns_zone; + GNUNET_CRYPTO_short_hash_to_enc (zone, &zonename); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Using zone: %s!\n", &zonename); + GNUNET_CRYPTO_rsa_key_free(key); + GNUNET_free(keyfile); + keyfile = NULL; + + if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_filename (cfg, "gns", + "PRIVATE_ZONEKEY", &keyfile)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Unable to load private zone key config value!\n"); + } + + if ((NULL != keyfile) && (GNUNET_NO == GNUNET_DISK_file_test (keyfile))) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Unable to load private zone key %s!\n", keyfile); + GNUNET_free(keyfile); + } + else + { + key = GNUNET_CRYPTO_rsa_key_create_from_file (keyfile); + GNUNET_CRYPTO_rsa_key_get_public (key, &pkey); + local_private_zone = GNUNET_malloc (sizeof (struct GNUNET_CRYPTO_ShortHashCode)); + GNUNET_CRYPTO_short_hash(&pkey, + sizeof(struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded), + local_private_zone); + GNUNET_CRYPTO_short_hash_to_enc (zone, &zonename); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Using private zone: %s!\n", &zonename); + GNUNET_CRYPTO_rsa_key_free(key); + GNUNET_free(keyfile); + } + keyfile = NULL; + + if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_filename (cfg, "gns", + "SHORTEN_ZONEKEY", &keyfile)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Unable to load shorten zone key config value!\n"); + } + + if ((NULL != keyfile) && (GNUNET_NO == GNUNET_DISK_file_test (keyfile))) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Unable to load shorten zone key %s!\n", keyfile); + GNUNET_free(keyfile); + } + else + { + key = GNUNET_CRYPTO_rsa_key_create_from_file (keyfile); + GNUNET_CRYPTO_rsa_key_get_public (key, &pkey); + local_shorten_zone = GNUNET_malloc (sizeof (struct GNUNET_CRYPTO_ShortHashCode)); + GNUNET_CRYPTO_short_hash(&pkey, + sizeof(struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded), + local_shorten_zone); + GNUNET_CRYPTO_short_hash_to_enc (zone, &zonename); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Using shorten zone: %s!\n", &zonename); + GNUNET_CRYPTO_rsa_key_free(key); + GNUNET_free(keyfile); + } + + return GNUNET_YES; +} + + /** * Main function that will be run * @@ -733,6 +3297,72 @@ run (void *cls, char *const *args, const char *cfgfile, const struct GNUNET_CONFIGURATION_Handle *cfg) { struct sockaddr_in sa; + struct MhdHttpList *hd; + char* cafile_cfg = NULL; + char* cafile; +#if !HAVE_MHD_NO_LISTEN_SOCKET + size_t len; + char* proxy_sockfile; + struct sockaddr_un mhd_unix_sock_addr; +#endif + + if (NULL == (curl_multi = curl_multi_init ())) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Failed to create cURL multo handle!\n"); + return; + } + + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + "Loading CA\n"); + cafile = cafile_opt; + if (NULL == cafile) + { + if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_filename (cfg, "gns-proxy", + "PROXY_CACERT", + &cafile_cfg)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Unable to load proxy CA config value!\n"); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "No proxy CA provided!\n"); + return; + } + cafile = cafile_cfg; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Using %s as CA\n", cafile); + + gnutls_global_init (); + gnutls_x509_crt_init (&proxy_ca.cert); + gnutls_x509_privkey_init (&proxy_ca.key); + + if ( (GNUNET_OK != load_cert_from_file (proxy_ca.cert, cafile)) || + (GNUNET_OK != load_key_from_file (proxy_ca.key, cafile)) ) + { + // FIXME: release resources... + return; + } + + GNUNET_free_non_null (cafile_cfg); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Loading Template\n"); + + compile_regex (&re_dotplus, (char*) RE_A_HREF); + + if (NULL == (gns_handle = GNUNET_GNS_connect (cfg))) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Unable to connect to GNS!\n"); + return; + } + if (GNUNET_NO == load_local_zone_key (cfg)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Unable to load zone!\n"); + return; + } memset (&sa, 0, sizeof (sa)); sa.sin_family = AF_INET; @@ -765,26 +3395,106 @@ run (void *cls, char *const *args, const char *cfgfile, GNUNET_a2s ((const struct sockaddr *) &sa, sizeof (sa))); return; } - ltask = GNUNET_SCHEDULER_add_read_net (GNUNET_TIME_UNIT_FOREVER_REL, lsock, &do_accept, NULL); + if (0 != curl_global_init (CURL_GLOBAL_WIN32)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "cURL global init failed!\n"); + return; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Proxy listens on port %u\n", port); - - httpd = MHD_start_daemon (MHD_USE_DEBUG, 4444, - NULL, NULL, - &create_response, NULL, - MHD_OPTION_CONNECTION_LIMIT, (unsigned int) 128, - MHD_OPTION_CONNECTION_TIMEOUT, (unsigned int) 16, - MHD_OPTION_NOTIFY_COMPLETED, - NULL, NULL, - MHD_OPTION_END); - run_httpd (); +#if ! HAVE_MHD_NO_LISTEN_SOCKET + if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_filename (cfg, "gns-proxy", + "PROXY_UNIXPATH", + &proxy_sockfile)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Specify PROXY_UNIXPATH in gns-proxy config section!\n"); + return; + } + if (NULL == (mhd_unix_socket = GNUNET_NETWORK_socket_create (AF_UNIX, + SOCK_STREAM, + 0))) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Unable to create unix domain socket!\n"); + return; + } + + mhd_unix_sock_addr.sun_family = AF_UNIX; + strcpy (mhd_unix_sock_addr.sun_path, proxy_sockfile); + +#if LINUX + mhd_unix_sock_addr.sun_path[0] = '\0'; +#endif +#if HAVE_SOCKADDR_IN_SIN_LEN + mhd_unix_sock_addr.sun_len = (u_char) sizeof (struct sockaddr_un); +#endif + len = strlen (proxy_sockfile) + sizeof(AF_UNIX); + GNUNET_free (proxy_sockfile); + + if (GNUNET_OK != GNUNET_NETWORK_socket_bind (mhd_unix_socket, + (struct sockaddr*)&mhd_unix_sock_addr, + len)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Unable to bind unix domain socket!\n"); + return; + } + + if (GNUNET_OK != GNUNET_NETWORK_socket_listen (mhd_unix_socket, + 1)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Unable to listen on unix domain socket!\n"); + return; + } +#endif + + hd = GNUNET_malloc (sizeof (struct MhdHttpList)); + hd->is_ssl = GNUNET_NO; + strcpy (hd->domain, ""); + +#if HAVE_MHD_NO_LISTEN_SOCKET + httpd = MHD_start_daemon (MHD_USE_DEBUG | MHD_USE_NO_LISTEN_SOCKET, + 0, + &accept_cb, NULL, + &create_response, hd, + MHD_OPTION_CONNECTION_LIMIT, MHD_MAX_CONNECTIONS, + MHD_OPTION_CONNECTION_TIMEOUT, (unsigned int) 16, + MHD_OPTION_NOTIFY_COMPLETED, + NULL, NULL, + MHD_OPTION_URI_LOG_CALLBACK, &mhd_log_callback, NULL, + MHD_OPTION_END); +#else + httpd = MHD_start_daemon (MHD_USE_DEBUG, + 4444 /* Dummy port */, + &accept_cb, NULL, + &create_response, hd, + MHD_OPTION_LISTEN_SOCKET, GNUNET_NETWORK_get_fd (mhd_unix_socket), + MHD_OPTION_CONNECTION_LIMIT, MHD_MAX_CONNECTIONS, + MHD_OPTION_CONNECTION_TIMEOUT, (unsigned int) 16, + MHD_OPTION_NOTIFY_COMPLETED, + NULL, NULL, + MHD_OPTION_URI_LOG_CALLBACK, &mhd_log_callback, NULL, + MHD_OPTION_END); +#endif + GNUNET_break (httpd != NULL); + hd->daemon = httpd; + hd->httpd_task = GNUNET_SCHEDULER_NO_TASK; + GNUNET_CONTAINER_DLL_insert (mhd_httpd_head, mhd_httpd_tail, hd); + run_httpds (); + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, + &do_shutdown, NULL); } + /** * The main function for gnunet-gns-proxy. * @@ -797,13 +3507,17 @@ main (int argc, char *const *argv) { static const struct GNUNET_GETOPT_CommandLineOption options[] = { {'p', "port", NULL, - gettext_noop ("listen on specified port"), 1, - &GNUNET_GETOPT_set_string, &port}, + gettext_noop ("listen on specified port (default: 7777)"), 1, + &GNUNET_GETOPT_set_ulong, &port}, + {'a', "authority", NULL, + gettext_noop ("pem file to use as CA"), 1, + &GNUNET_GETOPT_set_string, &cafile_opt}, GNUNET_GETOPT_OPTION_END }; - int ret; + if (GNUNET_OK != GNUNET_STRINGS_get_utf8_args (argc, argv, &argc, &argv)) + return 2; GNUNET_log_setup ("gnunet-gns-proxy", "WARNING", NULL); ret = (GNUNET_OK == @@ -811,5 +3525,8 @@ main (int argc, char *const *argv) _("GNUnet GNS proxy"), options, &run, NULL)) ? 0 : 1; + GNUNET_free_non_null ((char *) argv); return ret; } + +/* end of gnunet-gns-proxy.c */ diff --git a/src/gns/gnunet-gns.c b/src/gns/gnunet-gns.c index ca3a594..74212d4 100644 --- a/src/gns/gnunet-gns.c +++ b/src/gns/gnunet-gns.c @@ -22,8 +22,6 @@ * @brief command line tool to access distributed GNS * @author Christian Grothoff * - * TODO: - * - everything */ #include "platform.h" #include @@ -46,7 +44,6 @@ static char *shorten_name; */ static char *lookup_name; - /** * record type to look up (-t option) */ @@ -60,10 +57,29 @@ static char *auth_name; /** * raw output */ -static int raw = 0; +static int raw; +/** + * Requested record type. + */ static enum GNUNET_GNS_RecordType rtype; +/** + * Handle to lookup request + */ +static struct GNUNET_GNS_LookupRequest *lookup_request; + +/** + * Handle to shorten request + */ +static struct GNUNET_GNS_ShortenRequest *shorten_request; + +/** + * Handle to get authority request + */ +static struct GNUNET_GNS_GetAuthRequest *getauth_request; + + /** * Task run on shutdown. Cleans up everything. * @@ -74,6 +90,21 @@ static void do_shutdown (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { + if (NULL != lookup_request) + { + GNUNET_GNS_cancel_lookup_request (lookup_request); + lookup_request = NULL; + } + if (NULL != shorten_request) + { + GNUNET_GNS_cancel_shorten_request (shorten_request); + shorten_request = NULL; + } + if (NULL != getauth_request) + { + GNUNET_GNS_cancel_get_auth_request (getauth_request); + getauth_request = NULL; + } if (NULL != gns) { GNUNET_GNS_disconnect (gns); @@ -82,57 +113,84 @@ do_shutdown (void *cls, } +/** + * Function called with the result of a shorten operation. + * Prints the result. + * + * @param cls a 'const char *' with the original (long) name + * @param nshort the shortened name + */ static void -process_shorten_result(void* cls, const char* nshort) +process_shorten_result (void* cls, const char *nshort) { + const char *original_name = cls; + + shorten_request = NULL; if (raw) printf("%s", nshort); else - printf("%s shortened to %s\n", (char*) cls, nshort); - GNUNET_SCHEDULER_add_now (&do_shutdown, NULL); + printf("%s shortened to %s\n", original_name, nshort); + GNUNET_SCHEDULER_shutdown (); } + +/** + * Function called with the result of a GADS lookup. + * + * @param cls the 'const char *' name that was resolved + * @param rd_count number of records returned + * @param rd array of 'rd_count' records with the results + */ static void -process_lookup_result(void* cls, uint32_t rd_count, - const struct GNUNET_NAMESTORE_RecordData *rd) +process_lookup_result (void* cls, uint32_t rd_count, + const struct GNUNET_NAMESTORE_RecordData *rd) { - int i; - char* name = (char*) cls; + const char* name = cls; + uint32_t i; const char* typename; char* string_val; - - if (!raw) { - if (rd_count == 0) + + lookup_request = NULL; + if (!raw) + { + if (0 == rd_count) printf("No results.\n"); else printf("%s:\n", name); } - - - for (i=0; isignature = *signature; - nrb->public_key = *key; - - nrb->rd_count = htonl(rd_count); - - memcpy(&nrb[1], name, namelen); - - nrb_data = (char*)&nrb[1]; + nrb->rd_count = htonl (rd_count); + memcpy (&nrb[1], name, namelen); + nrb_data = (char *) &nrb[1]; nrb_data += namelen; - rd_payload_length += sizeof(struct GNSNameRecordBlock) + namelen; - + GNUNET_CRYPTO_short_hash (key, + sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded), + &zhash); if (-1 == GNUNET_NAMESTORE_records_serialize (rd_count, rd, rd_payload_length, nrb_data)) { - GNUNET_log(GNUNET_ERROR_TYPE_ERROR, - "Record serialization failed! Skipping...\n"); - GNUNET_free(nrb); - zone_update_taskid = GNUNET_SCHEDULER_add_now (&update_zone_dht_next, + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Records for name `%s' in zone %s too large to fit into DHT"), + name, + GNUNET_short_h2s (&zhash)); + GNUNET_free (nrb); + zone_publish_task = GNUNET_SCHEDULER_add_now (&publish_zone_dht_next, NULL); return; } - - /* - * calculate DHT key: H(name) xor H(pubkey) - */ - GNUNET_CRYPTO_short_hash(key, - sizeof(struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded), - &zhash); - GNUNET_CRYPTO_short_hash(name, strlen(name), &name_hash); - GNUNET_CRYPTO_short_hash_double (&name_hash, &name_hash_double); - GNUNET_CRYPTO_short_hash_double (&zhash, &zone_hash_double); - GNUNET_CRYPTO_hash_xor(&zone_hash_double, &name_hash_double, &xor_hash); - - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "zone identity: %s\n", GNUNET_h2s (&zone_hash_double)); - - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "putting records for %s under key: %s with size %d\n", - name, GNUNET_h2s (&xor_hash), rd_payload_length); - - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "DHT req to %d\n", DHT_OPERATION_TIMEOUT.rel_value); - /* FIXME: keep return value to possibly cancel? */ - GNUNET_DHT_put (dht_handle, &xor_hash, - DHT_GNS_REPLICATION_LEVEL, - GNUNET_DHT_RO_NONE, - GNUNET_BLOCK_TYPE_GNS_NAMERECORD, - rd_payload_length, - (char*)nrb, - expiration, - DHT_OPERATION_TIMEOUT, - &record_dht_put, - NULL); //cls for cont + GNUNET_GNS_get_key_for_record (name, &zhash, &dht_key); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "putting %u records from zone %s for `%s' under key: %s with size %u and timeout %s\n", + rd_count, + GNUNET_short_h2s (&zhash), + name, + GNUNET_h2s (&dht_key), + (unsigned int) rd_payload_length, + GNUNET_STRINGS_relative_time_to_string (DHT_OPERATION_TIMEOUT, GNUNET_YES)); - num_public_records++; - - /** - * Reschedule periodic put - */ - zone_update_taskid = GNUNET_SCHEDULER_add_delayed (record_put_interval, - &update_zone_dht_next, - NULL); - - GNUNET_free(nrb); - + GNUNET_STATISTICS_update (statistics, + "Record bytes put into DHT", + rd_payload_length, GNUNET_NO); + + (void) GNUNET_DHT_put (dht_handle, &dht_key, + DHT_GNS_REPLICATION_LEVEL, + GNUNET_DHT_RO_DEMULTIPLEX_EVERYWHERE, + GNUNET_BLOCK_TYPE_GNS_NAMERECORD, + rd_payload_length, + (char*)nrb, + expiration, + DHT_OPERATION_TIMEOUT, + NULL, + NULL); + GNUNET_free (nrb); + + num_public_records++; + if ( (num_public_records > last_num_public_records) + && (GNUNET_NO == first_zone_iteration) ) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Last record count was lower than current record count. Reducing interval.\n"); + put_interval = GNUNET_TIME_relative_divide (zone_publish_time_window, + num_public_records); + next_put_interval = GNUNET_TIME_relative_divide (put_interval, + LATE_ITERATION_SPEEDUP_FACTOR); + } + else + next_put_interval = put_interval; + + GNUNET_STATISTICS_set (statistics, + "Current zone iteration interval (ms)", + next_put_interval.rel_value, + GNUNET_NO); + zone_publish_task = GNUNET_SCHEDULER_add_delayed (next_put_interval, + &publish_zone_dht_next, + NULL); } + /** * Periodically iterate over our zone and store everything in dht * @@ -382,100 +549,27 @@ put_gns_record(void *cls, * @param tc task context */ static void -update_zone_dht_start(void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +publish_zone_dht_start (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) { - unsigned long long interval = 0; - - zone_update_taskid = GNUNET_SCHEDULER_NO_TASK; - - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, "Scheduling DHT zone update!\n"); - if (0 == num_public_records) - { - /** - * If no records are known (startup) or none present - * we can safely set the interval to 1s - */ - record_put_interval = GNUNET_TIME_relative_multiply( - GNUNET_TIME_UNIT_SECONDS, - 1); - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "No records in db. Adjusted record put interval to 1s\n"); - } - else - { - interval = max_record_put_interval/num_public_records; - if (interval == 0) - interval = 1; - record_put_interval = GNUNET_TIME_relative_multiply( - GNUNET_TIME_UNIT_SECONDS, - interval); - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "Adjusted DHT update interval to %ds!\n", - interval); - } + zone_publish_task = GNUNET_SCHEDULER_NO_TASK; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Scheduling DHT zone update!\n"); /* start counting again */ num_public_records = 0; namestore_iter = GNUNET_NAMESTORE_zone_iteration_start (namestore_handle, - NULL, //All zones - GNUNET_NAMESTORE_RF_AUTHORITY, - GNUNET_NAMESTORE_RF_PRIVATE, - &put_gns_record, - NULL); + NULL, /* All zones */ + GNUNET_NAMESTORE_RF_AUTHORITY, + GNUNET_NAMESTORE_RF_PRIVATE, + &put_gns_record, + NULL); } -/** - * Lookup the private key for the zone - * - * @param zone the zone we want a private key for - * @return NULL of not found else the key - */ -struct GNUNET_CRYPTO_RsaPrivateKey* -lookup_private_key(struct GNUNET_CRYPTO_ShortHashCode *zone) -{ - char* keydir; - struct GNUNET_CRYPTO_ShortHashAsciiEncoded zonename; - char* location; - struct GNUNET_CRYPTO_RsaPrivateKey *key = NULL; - - GNUNET_log (GNUNET_ERROR_TYPE_INFO, - "Looking for private key\n"); - - if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_filename (GNS_cfg, - "namestore", - "ZONEFILE_DIRECTORY", &keydir)) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "No zonefile directory!\n"); - return NULL; - } - - GNUNET_log (GNUNET_ERROR_TYPE_INFO, - "Zonefile directory is %s\n", keydir); - - GNUNET_CRYPTO_short_hash_to_enc (zone, &zonename); - - GNUNET_log (GNUNET_ERROR_TYPE_INFO, - "Zonefile is %s.zkey\n", &zonename); - - GNUNET_asprintf(&location, "%s%s%s.zkey", keydir, - DIR_SEPARATOR_STR, &zonename); - - GNUNET_log (GNUNET_ERROR_TYPE_INFO, - "Checking for %s\n", location); - - if (GNUNET_YES == GNUNET_DISK_file_test (location)) - key = GNUNET_CRYPTO_rsa_key_create_from_file (location); - - GNUNET_free(location); - GNUNET_free(keydir); - - return key; - -} /* END DHT ZONE PROPAGATION */ + /** * Send shorten response back to client * @@ -483,136 +577,291 @@ lookup_private_key(struct GNUNET_CRYPTO_ShortHashCode *zone) * @param name the shortened name result or NULL if cannot be shortened */ static void -send_shorten_response(void* cls, const char* name) +send_shorten_response (void* cls, const char* name) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Sending `%s' message with %s\n", - "SHORTEN_RESULT", name); + struct ClientShortenHandle *csh = cls; struct GNUNET_GNS_ClientShortenResultMessage *rmsg; - struct ClientShortenHandle *csh = (struct ClientShortenHandle *)cls; + size_t name_len; - if (name == NULL) - { - name = ""; - } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Sending `%s' message with %s\n", + "SHORTEN_RESULT", name); + if (NULL == name) + name_len = 0; + else + name_len = strlen (name) + 1; + GNUNET_STATISTICS_update (statistics, + "Name shorten results", 1, GNUNET_NO); - rmsg = GNUNET_malloc(sizeof(struct GNUNET_GNS_ClientShortenResultMessage) - + strlen(name) + 1); + rmsg = GNUNET_malloc (sizeof (struct GNUNET_GNS_ClientShortenResultMessage) + + name_len); - rmsg->id = csh->unique_id; + rmsg->id = csh->request_id; rmsg->header.type = htons(GNUNET_MESSAGE_TYPE_GNS_SHORTEN_RESULT); rmsg->header.size = htons(sizeof(struct GNUNET_GNS_ClientShortenResultMessage) + - strlen(name) + 1); + name_len); + memcpy (&rmsg[1], name, name_len); + GNUNET_SERVER_notification_context_unicast (nc, csh->client, + &rmsg->header, + GNUNET_NO); + if (NULL != csh->namestore_task) + GNUNET_NAMESTORE_cancel (csh->namestore_task); + GNUNET_free (rmsg); + GNUNET_free (csh); +} - strcpy((char*)&rmsg[1], name); - GNUNET_SERVER_notification_context_unicast (nc, csh->client, - (const struct GNUNET_MessageHeader *) rmsg, - GNUNET_NO); - GNUNET_SERVER_receive_done (csh->client, GNUNET_OK); +/** + * Lookup the zone infos and shorten name + * + * @param cls the client shorten handle + * @param key key of the zone + * @param expiration expiration of record + * @param name name found or null if no result + * @param rd_count number of records found + * @param rd record data + * @param signature + * + */ +static void +process_shorten_in_private_zone_lookup (void *cls, + const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *key, + struct GNUNET_TIME_Absolute expiration, + const char *name, + unsigned int rd_count, + const struct GNUNET_NAMESTORE_RecordData *rd, + const struct GNUNET_CRYPTO_RsaSignature *signature) +{ + struct ClientShortenHandle *csh = cls; + struct GNUNET_CRYPTO_ShortHashCode *szone = &csh->shorten_zone; + struct GNUNET_CRYPTO_ShortHashCode *pzone = &csh->private_zone; + + csh->namestore_task = NULL; + if (0 == strcmp (csh->private_zone_id, "")) + pzone = NULL; + if (0 == rd_count) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "No shorten zone in private zone!\n"); + strcpy (csh->shorten_zone_id, ""); + szone = NULL; + } + else + { + GNUNET_break (1 == rd_count); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Shorten zone %s found in private zone %s\n", + name, csh->private_zone_id); + + sprintf (csh->shorten_zone_id, "%s.%s", name, csh->private_zone_id); + } + GNUNET_CONTAINER_DLL_remove (csh_head, csh_tail, csh); + gns_resolver_shorten_name (&csh->root_zone, + pzone, + szone, + csh->name, + csh->private_zone_id, + csh->shorten_zone_id, + &send_shorten_response, csh); + +} + + +/** + * Lookup the zone infos and shorten name + * + * @param cls the shorten handle + * @param key key of the zone + * @param expiration expiration of record + * @param name name found or null if no result + * @param rd_count number of records found + * @param rd record data + * @param signature + * + */ +static void +process_shorten_in_root_zone_lookup (void *cls, + const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *key, + struct GNUNET_TIME_Absolute expiration, + const char *name, + unsigned int rd_count, + const struct GNUNET_NAMESTORE_RecordData *rd, + const struct GNUNET_CRYPTO_RsaSignature *signature) +{ + struct ClientShortenHandle *csh = cls; + struct GNUNET_CRYPTO_ShortHashCode *szone = &csh->shorten_zone; + struct GNUNET_CRYPTO_ShortHashCode *pzone = &csh->private_zone; - GNUNET_free(rmsg); - GNUNET_free_non_null(csh->name); - GNUNET_free_non_null(csh->zone_key); - GNUNET_free(csh); + csh->namestore_task = NULL; + if (0 == strcmp (csh->private_zone_id, "")) + pzone = NULL; + if (0 == rd_count) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "No shorten zone in zone and no private zone!\n"); + + strcpy (csh->shorten_zone_id, ""); + GNUNET_CONTAINER_DLL_remove (csh_head, csh_tail, csh); + szone = NULL; + gns_resolver_shorten_name (&csh->root_zone, + pzone, + szone, + csh->name, + csh->private_zone_id, + csh->shorten_zone_id, + &send_shorten_response, csh); + return; + } + GNUNET_break (rd_count == 1); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Private zone %s found in root zone\n", name); + strcpy (csh->private_zone_id, name); + csh->namestore_task = GNUNET_NAMESTORE_zone_to_name (namestore_handle, + pzone, + szone, + &process_shorten_in_private_zone_lookup, + csh); +} + +/** + * Lookup the zone infos and shorten name + * + * @param cls the shorten handle + * @param key key of the zone + * @param expiration expiration of record + * @param name name found or null if no result + * @param rd_count number of records found + * @param rd record data + * @param signature + */ +static void +process_private_in_root_zone_lookup (void *cls, + const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *key, + struct GNUNET_TIME_Absolute expiration, + const char *name, + unsigned int rd_count, + const struct GNUNET_NAMESTORE_RecordData *rd, + const struct GNUNET_CRYPTO_RsaSignature *signature) +{ + struct ClientShortenHandle *csh = cls; + + csh->namestore_task = NULL; + if (0 == rd_count) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "No private zone in root zone\n"); + strcpy (csh->private_zone_id, ""); + csh->namestore_task = GNUNET_NAMESTORE_zone_to_name (namestore_handle, + &csh->root_zone, + &csh->shorten_zone, + &process_shorten_in_root_zone_lookup, + csh); + return; + } + GNUNET_break (1 == rd_count); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Private zone `%s' found in root zone\n", + name); + strcpy (csh->private_zone_id, name); + csh->namestore_task = GNUNET_NAMESTORE_zone_to_name (namestore_handle, + &csh->private_zone, + &csh->shorten_zone, + &process_shorten_in_private_zone_lookup, + csh); } + /** * Handle a shorten message from the api * - * @param cls the closure + * @param cls the closure (unused) * @param client the client * @param message the message */ -static void handle_shorten(void *cls, - struct GNUNET_SERVER_Client * client, - const struct GNUNET_MessageHeader * message) +static void +handle_shorten (void *cls, + struct GNUNET_SERVER_Client * client, + const struct GNUNET_MessageHeader * message) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received `%s' message\n", "SHORTEN"); - - size_t msg_size = 0; struct ClientShortenHandle *csh; - char name[MAX_DNS_NAME_LENGTH]; + const char *utf_in; + char name[GNUNET_DNSPARSER_MAX_NAME_LENGTH]; char* nameptr = name; - struct GNUNET_CRYPTO_ShortHashCode zone; - struct GNUNET_CRYPTO_RsaPrivateKey *key; + uint16_t msg_size; + const struct GNUNET_GNS_ClientShortenMessage *sh_msg; - if (ntohs (message->size) < sizeof (struct GNUNET_GNS_ClientShortenMessage)) + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Received `%s' message\n", "SHORTEN"); + msg_size = ntohs (message->size); + if (msg_size < sizeof (struct GNUNET_GNS_ClientShortenMessage)) { - GNUNET_break_op (0); - GNUNET_SERVER_receive_done (client, GNUNET_OK); + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } - - - struct GNUNET_GNS_ClientShortenMessage *sh_msg = - (struct GNUNET_GNS_ClientShortenMessage *) message; - - msg_size = ntohs(message->size); - - if (msg_size > GNUNET_SERVER_MAX_MESSAGE_SIZE) + sh_msg = (const struct GNUNET_GNS_ClientShortenMessage *) message; + utf_in = (const char *) &sh_msg[1]; + if ('\0' != utf_in[msg_size - sizeof (struct GNUNET_GNS_ClientShortenMessage) - 1]) { - GNUNET_break_op (0); - GNUNET_SERVER_receive_done (client, GNUNET_OK); + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } - - csh = GNUNET_malloc(sizeof(struct ClientShortenHandle)); + csh = GNUNET_malloc(sizeof (struct ClientShortenHandle)); csh->client = client; - csh->unique_id = sh_msg->id; - csh->zone_key = NULL; - - GNUNET_STRINGS_utf8_tolower((char*)&sh_msg[1], &nameptr); - - if (strlen (name) < strlen(GNUNET_GNS_TLD)) { + csh->request_id = sh_msg->id; + GNUNET_CONTAINER_DLL_insert (csh_head, csh_tail, csh); + GNUNET_STRINGS_utf8_tolower (utf_in, &nameptr); + GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, + "SHORTEN: Converted `%s' to `%s'\n", + utf_in, + nameptr); + GNUNET_SERVER_notification_context_add (nc, client); + if (strlen (name) < strlen (GNUNET_GNS_TLD)) + { GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "SHORTEN: %s is too short", name); - csh->name = NULL; + "SHORTEN: %s is too short\n", name); + GNUNET_CONTAINER_DLL_remove (csh_head, csh_tail, csh); send_shorten_response(csh, name); + GNUNET_SERVER_receive_done (client, GNUNET_OK); return; } - - if (strlen (name) > MAX_DNS_NAME_LENGTH) { + if (strlen (name) > GNUNET_DNSPARSER_MAX_NAME_LENGTH) + { GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "SHORTEN: %s is too long", name); - csh->name = NULL; + "SHORTEN: %s is too long\n", name); + GNUNET_CONTAINER_DLL_remove (csh_head, csh_tail, csh); send_shorten_response(csh, name); + GNUNET_SERVER_receive_done (client, GNUNET_OK); return; - } - - if (!is_gnunet_tld(name) && !is_zkey_tld(name)) + } + if ( (! is_gads_tld (name)) && + (! is_zkey_tld (name)) ) { GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "%s is not our domain. Returning\n", name); - csh->name = NULL; - send_shorten_response(csh, name); + GNUNET_CONTAINER_DLL_remove (csh_head, csh_tail, csh); + send_shorten_response (csh, name); + GNUNET_SERVER_receive_done (client, GNUNET_OK); return; } - - GNUNET_SERVER_notification_context_add (nc, client); - + csh->shorten_zone = sh_msg->shorten_zone; + csh->private_zone = sh_msg->private_zone; + strcpy (csh->name, name); if (1 == ntohl(sh_msg->use_default_zone)) - zone = zone_hash; //Default zone + csh->root_zone = zone_hash; //Default zone else - zone = sh_msg->zone; - - /* Start shortening */ - if (GNUNET_YES == auto_import_pkey) - { - if (1 == ntohl(sh_msg->use_default_zone)) - key = zone_key; - else - { - key = lookup_private_key(&sh_msg->zone); - csh->zone_key = key; - } - gns_resolver_shorten_name(zone, zone, name, key, - &send_shorten_response, csh); - } - else - gns_resolver_shorten_name(zone, zone, name, NULL, - &send_shorten_response, csh); + csh->root_zone = sh_msg->zone; + csh->namestore_task = GNUNET_NAMESTORE_zone_to_name (namestore_handle, + &csh->root_zone, + &csh->private_zone, + &process_private_in_root_zone_lookup, + csh); + GNUNET_STATISTICS_update (statistics, + "Name shorten attempts", 1, GNUNET_NO); + GNUNET_SERVER_receive_done (client, GNUNET_OK); } @@ -620,45 +869,42 @@ static void handle_shorten(void *cls, * Send get authority response back to client * * @param cls the closure containing a client get auth handle - * @param name the shortened name result or NULL if cannot be shortened + * @param name the name of the authority, or NULL on error */ -static void -send_get_auth_response(void *cls, const char* name) +static void +send_get_auth_response (void *cls, + const char* name) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Sending `%s' message with %s\n", - "GET_AUTH_RESULT", name); + struct ClientGetAuthHandle *cah = cls; struct GNUNET_GNS_ClientGetAuthResultMessage *rmsg; - struct ClientGetAuthHandle *cah = (struct ClientGetAuthHandle *)cls; - if (name == NULL) + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Sending `%s' message with `%s'\n", + "GET_AUTH_RESULT", name); + if (NULL != name) { - name = ""; - } - - rmsg = GNUNET_malloc(sizeof(struct GNUNET_GNS_ClientGetAuthResultMessage) - + strlen(name) + 1); + GNUNET_STATISTICS_update (statistics, + "Authorities resolved", 1, GNUNET_NO); + } + if (NULL == name) + name = ""; + rmsg = GNUNET_malloc (sizeof (struct GNUNET_GNS_ClientGetAuthResultMessage) + + strlen (name) + 1); - rmsg->id = cah->unique_id; + rmsg->id = cah->request_id; rmsg->header.type = htons(GNUNET_MESSAGE_TYPE_GNS_GET_AUTH_RESULT); rmsg->header.size = htons(sizeof(struct GNUNET_GNS_ClientGetAuthResultMessage) + - strlen(name) + 1); - - strcpy((char*)&rmsg[1], name); + strlen (name) + 1); + strcpy ((char*)&rmsg[1], name); GNUNET_SERVER_notification_context_unicast (nc, cah->client, - (const struct GNUNET_MessageHeader *) rmsg, - GNUNET_NO); + &rmsg->header, + GNUNET_NO); GNUNET_SERVER_receive_done (cah->client, GNUNET_OK); - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Cleaning up handles...\n"); - GNUNET_free(rmsg); GNUNET_free_non_null(cah->name); - GNUNET_free(cah); - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "done.\n"); - + GNUNET_free(cah); } @@ -669,74 +915,67 @@ send_get_auth_response(void *cls, const char* name) * @param client the client * @param message the message */ -static void handle_get_authority(void *cls, - struct GNUNET_SERVER_Client * client, - const struct GNUNET_MessageHeader * message) +static void +handle_get_authority (void *cls, + struct GNUNET_SERVER_Client * client, + const struct GNUNET_MessageHeader * message) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received `%s' message\n", "GET_AUTH"); - - size_t msg_size = 0; struct ClientGetAuthHandle *cah; - char name[MAX_DNS_NAME_LENGTH]; + const char *utf_in; + char name[GNUNET_DNSPARSER_MAX_NAME_LENGTH]; char* nameptr = name; + uint16_t msg_size; + const struct GNUNET_GNS_ClientGetAuthMessage *sh_msg; - - if (ntohs (message->size) < sizeof (struct GNUNET_GNS_ClientGetAuthMessage)) + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Received `%s' message\n", "GET_AUTH"); + msg_size = ntohs(message->size); + if (msg_size < sizeof (struct GNUNET_GNS_ClientGetAuthMessage)) { - GNUNET_break_op (0); - GNUNET_SERVER_receive_done (client, GNUNET_OK); + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } - GNUNET_SERVER_notification_context_add (nc, client); - - struct GNUNET_GNS_ClientGetAuthMessage *sh_msg = - (struct GNUNET_GNS_ClientGetAuthMessage *) message; - - msg_size = ntohs(message->size); - - if (msg_size > GNUNET_SERVER_MAX_MESSAGE_SIZE) + sh_msg = (const struct GNUNET_GNS_ClientGetAuthMessage *) message; + utf_in = (const char *) &sh_msg[1]; + if ('\0' != utf_in[msg_size - sizeof (struct GNUNET_GNS_ClientGetAuthMessage) - 1]) { - GNUNET_break_op (0); - GNUNET_SERVER_receive_done (client, GNUNET_OK); + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; - } - - GNUNET_STRINGS_utf8_tolower((char*)&sh_msg[1], &nameptr); - - + } + GNUNET_STRINGS_utf8_tolower(utf_in, &nameptr); cah = GNUNET_malloc(sizeof(struct ClientGetAuthHandle)); cah->client = client; - cah->unique_id = sh_msg->id; - - if (strlen(name) < strlen(GNUNET_GNS_TLD)) + cah->request_id = sh_msg->id; + if (strlen (name) < strlen(GNUNET_GNS_TLD)) { GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "GET_AUTH: %s is too short. Returning\n", name); + "GET_AUTH: `%s' is too short. Returning\n", name); cah->name = NULL; send_get_auth_response(cah, name); return; - } - - if (strlen (name) > MAX_DNS_NAME_LENGTH) { + } + if (strlen (name) > GNUNET_DNSPARSER_MAX_NAME_LENGTH) + { GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GET_AUTH: %s is too long", name); + "GET_AUTH: `%s' is too long", name); cah->name = NULL; send_get_auth_response(cah, name); return; - } - - if (strcmp(name+strlen(name)-strlen(GNUNET_GNS_TLD), - GNUNET_GNS_TLD) != 0) + } + if (0 != strcmp (name + strlen (name) - strlen (GNUNET_GNS_TLD), + GNUNET_GNS_TLD)) { GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "GET_AUTH: %s is not our domain. Returning\n", name); cah->name = NULL; - send_get_auth_response(cah, name); + send_get_auth_response (cah, name); return; } - if (strcmp(name, GNUNET_GNS_TLD) == 0) + if (0 == strcmp (name, GNUNET_GNS_TLD)) { GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "GET_AUTH: %s is us. Returning\n", name); @@ -745,19 +984,19 @@ static void handle_get_authority(void *cls, return; } - cah->name = GNUNET_malloc(strlen(name) - - strlen(GNUNET_GNS_TLD) + 1); - memset(cah->name, 0, - strlen(name)-strlen(GNUNET_GNS_TLD) + 1); - memcpy(cah->name, name, - strlen(name)-strlen(GNUNET_GNS_TLD)); + cah->name = GNUNET_malloc (strlen (name) + - strlen (GNUNET_GNS_TLD) + 1); + memcpy (cah->name, name, + strlen (name) - strlen (GNUNET_GNS_TLD)); /* Start delegation resolution in our namestore */ - gns_resolver_get_authority(zone_hash, zone_hash, name, &send_get_auth_response, cah); + gns_resolver_get_authority (zone_hash, zone_hash, name, + &send_get_auth_response, cah); + GNUNET_STATISTICS_update (statistics, + "Authority lookup attempts", 1, GNUNET_NO); } - /** * Reply to client with the result from our lookup. * @@ -766,11 +1005,11 @@ static void handle_get_authority(void *cls, * @param rd the record data */ static void -send_lookup_response(void* cls, - uint32_t rd_count, - const struct GNUNET_NAMESTORE_RecordData *rd) +send_lookup_response (void* cls, + uint32_t rd_count, + const struct GNUNET_NAMESTORE_RecordData *rd) { - struct ClientLookupHandle* clh = (struct ClientLookupHandle*)cls; + struct ClientLookupHandle* clh = cls; struct GNUNET_GNS_ClientLookupResultMessage *rmsg; size_t len; @@ -778,14 +1017,14 @@ send_lookup_response(void* cls, "LOOKUP_RESULT", rd_count); len = GNUNET_NAMESTORE_records_get_size (rd_count, rd); - rmsg = GNUNET_malloc(len+sizeof(struct GNUNET_GNS_ClientLookupResultMessage)); + rmsg = GNUNET_malloc (len + sizeof (struct GNUNET_GNS_ClientLookupResultMessage)); - rmsg->id = clh->unique_id; + rmsg->id = clh->request_id; rmsg->rd_count = htonl(rd_count); rmsg->header.type = htons(GNUNET_MESSAGE_TYPE_GNS_LOOKUP_RESULT); rmsg->header.size = htons(len+sizeof(struct GNUNET_GNS_ClientLookupResultMessage)); - + GNUNET_NAMESTORE_records_serialize (rd_count, rd, len, (char*)&rmsg[1]); GNUNET_SERVER_notification_context_unicast (nc, clh->client, @@ -796,11 +1035,14 @@ send_lookup_response(void* cls, GNUNET_free(rmsg); GNUNET_free(clh->name); - if (NULL != clh->zone_key) - GNUNET_free(clh->zone_key); - - GNUNET_free(clh); - + if (NULL != clh->shorten_key) + GNUNET_CRYPTO_rsa_key_free (clh->shorten_key); + GNUNET_free (clh); + GNUNET_STATISTICS_update (statistics, + "Completed lookups", 1, GNUNET_NO); + if (NULL != rd) + GNUNET_STATISTICS_update (statistics, + "Records resolved", rd_count, GNUNET_NO); } @@ -812,94 +1054,123 @@ send_lookup_response(void* cls, * @param message the message */ static void -handle_lookup(void *cls, - struct GNUNET_SERVER_Client * client, - const struct GNUNET_MessageHeader * message) +handle_lookup (void *cls, + struct GNUNET_SERVER_Client * client, + const struct GNUNET_MessageHeader * message) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received `%s' message\n", "LOOKUP"); - - size_t msg_size = 0; size_t namelen; - char name[MAX_DNS_NAME_LENGTH]; + char name[GNUNET_DNSPARSER_MAX_NAME_LENGTH]; struct ClientLookupHandle *clh; char* nameptr = name; - struct GNUNET_CRYPTO_RsaPrivateKey *key = NULL; - struct GNUNET_CRYPTO_ShortHashCode zone; - - if (ntohs (message->size) < sizeof (struct GNUNET_GNS_ClientLookupMessage)) + const char *utf_in; + int only_cached; + struct GNUNET_CRYPTO_RsaPrivateKey *key; + struct GNUNET_CRYPTO_RsaPrivateKeyBinaryEncoded *pkey; + char* tmp_pkey; + uint16_t msg_size; + const struct GNUNET_GNS_ClientLookupMessage *sh_msg; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Received `%s' message\n", "LOOKUP"); + msg_size = ntohs(message->size); + if (msg_size < sizeof (struct GNUNET_GNS_ClientLookupMessage)) { - GNUNET_break_op (0); - GNUNET_SERVER_receive_done (client, GNUNET_OK); + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } - + sh_msg = (const struct GNUNET_GNS_ClientLookupMessage *) message; GNUNET_SERVER_notification_context_add (nc, client); + if (GNUNET_YES == ntohl (sh_msg->have_key)) + { + pkey = (struct GNUNET_CRYPTO_RsaPrivateKeyBinaryEncoded *) &sh_msg[1]; + tmp_pkey = (char*) &sh_msg[1]; + key = GNUNET_CRYPTO_rsa_decode_key (tmp_pkey, ntohs (pkey->len)); + GNUNET_STRINGS_utf8_tolower (&tmp_pkey[ntohs (pkey->len)], &nameptr); + } + else + { + key = NULL; + utf_in = (const char *) &sh_msg[1]; + if ('\0' != utf_in[msg_size - sizeof (struct GNUNET_GNS_ClientLookupMessage) - 1]) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + GNUNET_STRINGS_utf8_tolower (utf_in, &nameptr); + } + + namelen = strlen (name) + 1; + clh = GNUNET_malloc (sizeof (struct ClientLookupHandle)); + memset (clh, 0, sizeof (struct ClientLookupHandle)); + clh->client = client; + clh->name = GNUNET_malloc (namelen); + strcpy (clh->name, name); + clh->request_id = sh_msg->id; + clh->type = ntohl (sh_msg->type); + clh->shorten_key = key; - struct GNUNET_GNS_ClientLookupMessage *sh_msg = - (struct GNUNET_GNS_ClientLookupMessage *) message; + only_cached = ntohl (sh_msg->only_cached); - msg_size = ntohs(message->size); + if (strlen (name) > GNUNET_DNSPARSER_MAX_NAME_LENGTH) { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "LOOKUP: %s is too long", name); + clh->name = NULL; + send_lookup_response (clh, 0, NULL); + return; + } - if (msg_size > GNUNET_SERVER_MAX_MESSAGE_SIZE) + if ((GNUNET_GNS_RECORD_A == clh->type) && + (GNUNET_OK != v4_enabled)) { - GNUNET_break_op (0); - GNUNET_SERVER_receive_done (client, GNUNET_OK); + GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, + "LOOKUP: Query for A record but AF_INET not supported!"); + clh->name = NULL; + send_lookup_response (clh, 0, NULL); return; } - GNUNET_STRINGS_utf8_tolower((char*)&sh_msg[1], &nameptr); - namelen = strlen(name)+1; - clh = GNUNET_malloc(sizeof(struct ClientLookupHandle)); - clh->client = client; - clh->name = GNUNET_malloc(namelen); - strcpy(clh->name, name); - clh->unique_id = sh_msg->id; - clh->type = ntohl(sh_msg->type); - clh->zone_key = NULL; - - if (strlen (name) > MAX_DNS_NAME_LENGTH) { - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "LOOKUP: %s is too long", name); + if ((GNUNET_GNS_RECORD_AAAA == clh->type) && + (GNUNET_OK != v6_enabled)) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "LOOKUP: Query for AAAA record but AF_INET6 not supported!"); clh->name = NULL; - send_lookup_response(clh, 0, NULL); + send_lookup_response (clh, 0, NULL); return; } - - if (1 == ntohl(sh_msg->use_default_zone)) - zone = zone_hash; //Default zone + + if (1 == ntohl (sh_msg->use_default_zone)) + clh->zone = zone_hash; /* Default zone */ else - zone = sh_msg->zone; + clh->zone = sh_msg->zone; if (GNUNET_YES == auto_import_pkey) { - if (1 == ntohl(sh_msg->use_default_zone)) - key = zone_key; - else - { - key = lookup_private_key(&zone); - clh->zone_key = key; - } - - gns_resolver_lookup_record(zone, zone, clh->type, name, - key, - default_lookup_timeout, - &send_lookup_response, clh); + gns_resolver_lookup_record (clh->zone, clh->zone, clh->type, clh->name, + clh->shorten_key, + default_lookup_timeout, + clh->only_cached, + &send_lookup_response, clh); } else { - gns_resolver_lookup_record(zone, zone, clh->type, name, - NULL, - default_lookup_timeout, - &send_lookup_response, clh); + gns_resolver_lookup_record (clh->zone, clh->zone, clh->type, name, + NULL, + default_lookup_timeout, + only_cached, + &send_lookup_response, clh); } + GNUNET_STATISTICS_update (statistics, + "Record lookup attempts", 1, GNUNET_NO); } - /** * Process GNS requests. * - * @param cls closure) + * @param cls closure * @param server the initialized server * @param c configuration to use */ @@ -907,25 +1178,21 @@ static void run (void *cls, struct GNUNET_SERVER_Handle *server, const struct GNUNET_CONFIGURATION_Handle *c) { - - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, "Initializing GNS\n"); - - char* keyfile; - struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded pkey; - unsigned long long max_parallel_bg_queries = 0; - unsigned long long default_lookup_timeout_secs = 0; - int ignore_pending = GNUNET_NO; - static const struct GNUNET_SERVER_MessageHandler handlers[] = { {&handle_shorten, NULL, GNUNET_MESSAGE_TYPE_GNS_SHORTEN, 0}, {&handle_lookup, NULL, GNUNET_MESSAGE_TYPE_GNS_LOOKUP, 0}, {&handle_get_authority, NULL, GNUNET_MESSAGE_TYPE_GNS_GET_AUTH, 0} }; + char* keyfile; + struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded pkey; + unsigned long long max_parallel_bg_queries = 0; + int ignore_pending = GNUNET_NO; - GNS_cfg = c; + v6_enabled = GNUNET_NETWORK_test_pf (PF_INET6); + v4_enabled = GNUNET_NETWORK_test_pf (PF_INET); if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_filename (c, "gns", - "ZONEKEY", &keyfile)) + "ZONEKEY", &keyfile)) { GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "No private key for root zone specified!\n"); @@ -938,114 +1205,87 @@ run (void *cls, struct GNUNET_SERVER_Handle *server, zone_key = GNUNET_CRYPTO_rsa_key_create_from_file (keyfile); GNUNET_CRYPTO_rsa_key_get_public (zone_key, &pkey); - GNUNET_CRYPTO_short_hash(&pkey, sizeof(struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded), &zone_hash); GNUNET_free(keyfile); - - /** - * handle to our local namestore - */ - namestore_handle = GNUNET_NAMESTORE_connect(c); - + namestore_handle = GNUNET_NAMESTORE_connect (c); if (NULL == namestore_handle) { - //FIXME do error handling; - GNUNET_log(GNUNET_ERROR_TYPE_ERROR, - "Failed to connect to the namestore!\n"); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Failed to connect to the namestore!\n")); GNUNET_SCHEDULER_shutdown (); return; } - - auto_import_pkey = GNUNET_NO; - if (GNUNET_YES == GNUNET_CONFIGURATION_get_value_yesno (c, "gns", "AUTO_IMPORT_PKEY")) { - GNUNET_log(GNUNET_ERROR_TYPE_INFO, - "Automatic PKEY import is enabled.\n"); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Automatic PKEY import is enabled.\n"); auto_import_pkey = GNUNET_YES; - } - - dht_max_update_interval = GNUNET_GNS_DHT_MAX_UPDATE_INTERVAL; + put_interval = INITIAL_PUT_INTERVAL; + zone_publish_time_window = DEFAULT_ZONE_PUBLISH_TIME_WINDOW; if (GNUNET_OK == - GNUNET_CONFIGURATION_get_value_number (c, "gns", - "ZONE_PUT_INTERVAL", - &dht_max_update_interval)) + GNUNET_CONFIGURATION_get_value_time (c, "gns", + "ZONE_PUBLISH_TIME_WINDOW", + &zone_publish_time_window)) { - GNUNET_log(GNUNET_ERROR_TYPE_INFO, - "DHT zone update interval: %d\n", - dht_max_update_interval); - } - - max_record_put_interval = 1; - - if (GNUNET_OK == - GNUNET_CONFIGURATION_get_value_number (c, "gns", - "RECORD_PUT_INTERVAL", - &max_record_put_interval)) - { - GNUNET_log(GNUNET_ERROR_TYPE_INFO, - "Record put interval: %d\n", - max_record_put_interval); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Time window for zone iteration: %s\n", + GNUNET_STRINGS_relative_time_to_string (zone_publish_time_window, GNUNET_YES)); } - if (GNUNET_OK == GNUNET_CONFIGURATION_get_value_number (c, "gns", "MAX_PARALLEL_BACKGROUND_QUERIES", &max_parallel_bg_queries)) { - GNUNET_log(GNUNET_ERROR_TYPE_INFO, - "Number of allowed parallel background queries: %d\n", - max_parallel_bg_queries); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Number of allowed parallel background queries: %llu\n", + max_parallel_bg_queries); } if (GNUNET_YES == GNUNET_CONFIGURATION_get_value_yesno (c, "gns", "AUTO_IMPORT_CONFIRMATION_REQ")) { - GNUNET_log(GNUNET_ERROR_TYPE_INFO, - "Auto import requires user confirmation\n"); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Auto import requires user confirmation\n"); ignore_pending = GNUNET_YES; } if (GNUNET_OK == - GNUNET_CONFIGURATION_get_value_number(c, "gns", - "DEFAULT_LOOKUP_TIMEOUT", - &default_lookup_timeout_secs)) + GNUNET_CONFIGURATION_get_value_time (c, "gns", + "DEFAULT_LOOKUP_TIMEOUT", + &default_lookup_timeout)) { - GNUNET_log(GNUNET_ERROR_TYPE_INFO, - "Default lookup timeout: %ds\n", default_lookup_timeout_secs); - default_lookup_timeout = GNUNET_TIME_relative_multiply( - GNUNET_TIME_UNIT_SECONDS, - default_lookup_timeout_secs); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Default lookup timeout: %s\n", + GNUNET_STRINGS_relative_time_to_string (default_lookup_timeout, + GNUNET_YES)); } - /** - * handle to the dht - */ - dht_handle = GNUNET_DHT_connect(c, - //max_parallel_bg_queries); //FIXME get ht_len from cfg - 1024); - + dht_handle = GNUNET_DHT_connect (c, + (unsigned int) max_parallel_bg_queries); if (NULL == dht_handle) { - GNUNET_log(GNUNET_ERROR_TYPE_ERROR, "Could not connect to DHT!\n"); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Could not connect to DHT!\n")); + GNUNET_SCHEDULER_add_now (&shutdown_task, NULL); + return; } - if (gns_resolver_init(namestore_handle, dht_handle, zone_hash, - max_parallel_bg_queries, - ignore_pending) - == GNUNET_SYSERR) + if (GNUNET_SYSERR == + gns_resolver_init (namestore_handle, dht_handle, zone_hash, c, + max_parallel_bg_queries, + ignore_pending)) { - GNUNET_log(GNUNET_ERROR_TYPE_ERROR, - "Unable to initialize resolver!\n"); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Unable to initialize resolver!\n")); GNUNET_SCHEDULER_add_now (&shutdown_task, NULL); return; } @@ -1053,13 +1293,14 @@ run (void *cls, struct GNUNET_SERVER_Handle *server, if (GNUNET_YES == GNUNET_CONFIGURATION_get_value_yesno (c, "gns", "HIJACK_DNS")) { - GNUNET_log(GNUNET_ERROR_TYPE_INFO, - "DNS hijacking enabled... connecting to service.\n"); + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + "DNS hijacking enabled. Connecting to DNS service.\n"); - if (gns_interceptor_init(zone_hash, zone_key, c) == GNUNET_SYSERR) + if (GNUNET_SYSERR == + gns_interceptor_init (zone_hash, zone_key, c)) { GNUNET_log(GNUNET_ERROR_TYPE_ERROR, - "Failed to enable the dns interceptor!\n"); + "Failed to enable the DNS interceptor!\n"); } } @@ -1068,19 +1309,11 @@ run (void *cls, struct GNUNET_SERVER_Handle *server, * for our records * We have roughly an hour for all records; */ - record_put_interval = GNUNET_TIME_relative_multiply(GNUNET_TIME_UNIT_SECONDS, - 1); - zone_update_taskid = GNUNET_SCHEDULER_add_now (&update_zone_dht_start, NULL); - + first_zone_iteration = GNUNET_YES; + zone_publish_task = GNUNET_SCHEDULER_add_now (&publish_zone_dht_start, NULL); GNUNET_SERVER_add_handlers (server, handlers); - - //FIXME - //GNUNET_SERVER_disconnect_notify (server, - // &client_disconnect_notification, - // NULL); - + statistics = GNUNET_STATISTICS_create ("gns", c); nc = GNUNET_SERVER_notification_context_create (server, 1); - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, &shutdown_task, NULL); } diff --git a/src/gns/gnunet-service-gns_interceptor.c b/src/gns/gnunet-service-gns_interceptor.c index adb09ca..cbacc31 100644 --- a/src/gns/gnunet-service-gns_interceptor.c +++ b/src/gns/gnunet-service-gns_interceptor.c @@ -1,6 +1,6 @@ /* This file is part of GNUnet. - (C) 2009, 2010, 2011 Christian Grothoff (and other contributing authors) + (C) 2009, 2010, 2011, 2012 Christian Grothoff (and other contributing authors) GNUnet is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published @@ -17,9 +17,7 @@ Free Software Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */ - /** - * * @file gns/gnunet-service-gns_interceptor.c * @brief GNUnet GNS interceptor logic * @author Martin Schanzenbach @@ -32,21 +30,25 @@ #include "gnunet-service-gns_resolver.h" #include "gns.h" -#define MAX_DNS_LABEL_LENGTH 63 - /** * Handle to a DNS intercepted * reslution request */ struct InterceptLookupHandle { - /* the request handle to reply to */ + /** + * the request handle to reply to + */ struct GNUNET_DNS_RequestHandle *request_handle; - /* the dns parser packet received */ + /** + * the dns parser packet received + */ struct GNUNET_DNSPARSER_Packet *packet; - /* the query parsed from the packet */ + /** + * the query parsed from the packet + */ struct GNUNET_DNSPARSER_Query *query; }; @@ -71,6 +73,7 @@ static struct GNUNET_CRYPTO_RsaPrivateKey *our_key; */ static struct GNUNET_TIME_Relative default_lookup_timeout; + /** * Reply to dns request with the result from our lookup. * @@ -79,10 +82,10 @@ static struct GNUNET_TIME_Relative default_lookup_timeout; * @param rd the record data */ static void -reply_to_dns(void* cls, uint32_t rd_count, - const struct GNUNET_NAMESTORE_RecordData *rd) +reply_to_dns (void* cls, uint32_t rd_count, + const struct GNUNET_NAMESTORE_RecordData *rd) { - int i; + uint32_t i; size_t len; int ret; char *buf; @@ -120,12 +123,12 @@ reply_to_dns(void* cls, uint32_t rd_count, answer_records[i].type = rd[i].record_type; switch(rd[i].record_type) { - case GNUNET_GNS_RECORD_TYPE_NS: - case GNUNET_GNS_RECORD_TYPE_CNAME: - case GNUNET_GNS_RECORD_TYPE_PTR: + case GNUNET_GNS_RECORD_NS: + case GNUNET_GNS_RECORD_CNAME: + case GNUNET_GNS_RECORD_PTR: answer_records[i].data.hostname = (char*)rd[i].data; break; - case GNUNET_GNS_RECORD_TYPE_SOA: + case GNUNET_GNS_RECORD_SOA: answer_records[i].data.soa = (struct GNUNET_DNSPARSER_SoaRecord *)rd[i].data; break; @@ -137,7 +140,8 @@ reply_to_dns(void* cls, uint32_t rd_count, answer_records[i].data.raw.data_len = rd[i].data_size; answer_records[i].data.raw.data = (char*)rd[i].data; } - answer_records[i].expiration_time = rd[i].expiration; + GNUNET_break (0 == (rd[i].flags & GNUNET_NAMESTORE_RF_RELATIVE_EXPIRATION)); + answer_records[i].expiration_time.abs_value = rd[i].expiration_time; answer_records[i].class = GNUNET_DNSPARSER_CLASS_INTERNET;//hmmn } else @@ -146,12 +150,12 @@ reply_to_dns(void* cls, uint32_t rd_count, additional_records[i].type = rd[i].record_type; switch(rd[i].record_type) { - case GNUNET_GNS_RECORD_TYPE_NS: - case GNUNET_GNS_RECORD_TYPE_CNAME: - case GNUNET_GNS_RECORD_TYPE_PTR: + case GNUNET_GNS_RECORD_NS: + case GNUNET_GNS_RECORD_CNAME: + case GNUNET_GNS_RECORD_PTR: additional_records[i].data.hostname = (char*)rd[i].data; break; - case GNUNET_GNS_RECORD_TYPE_SOA: + case GNUNET_GNS_RECORD_SOA: additional_records[i].data.soa = (struct GNUNET_DNSPARSER_SoaRecord *)rd[i].data; break; @@ -163,7 +167,8 @@ reply_to_dns(void* cls, uint32_t rd_count, additional_records[i].data.raw.data_len = rd[i].data_size; additional_records[i].data.raw.data = (char*)rd[i].data; } - additional_records[i].expiration_time = rd[i].expiration; + GNUNET_break (0 == (rd[i].flags & GNUNET_NAMESTORE_RF_RELATIVE_EXPIRATION)); + additional_records[i].expiration_time.abs_value = rd[i].expiration_time; additional_records[i].class = GNUNET_DNSPARSER_CLASS_INTERNET;//hmmn } } @@ -190,23 +195,25 @@ reply_to_dns(void* cls, uint32_t rd_count, 1024, /* FIXME magic from dns redirector */ &buf, &len); - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "Built DNS response! (ret=%d,len=%d)\n", ret, len); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Built DNS response! (ret=%d,len=%d)\n", + ret, len); if (ret == GNUNET_OK) { - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "Answering DNS request\n"); - GNUNET_DNS_request_answer(ilh->request_handle, - len, - buf); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Answering DNS request\n"); + GNUNET_DNS_request_answer (ilh->request_handle, + len, + buf); - GNUNET_free(buf); - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, "Answered DNS request\n"); + GNUNET_free (buf); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Answered DNS request\n"); } else { - GNUNET_log(GNUNET_ERROR_TYPE_ERROR, - "Error building DNS response! (ret=%d)", ret); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Error building DNS response! (ret=%d)", ret); } packet->num_answers = 0; @@ -227,8 +234,8 @@ reply_to_dns(void* cls, uint32_t rd_count, * @param q the DNS query we received parsed from p */ static void -start_resolution_for_dns(struct GNUNET_DNS_RequestHandle *request, - struct GNUNET_DNSPARSER_Packet *p, +start_resolution_for_dns (struct GNUNET_DNS_RequestHandle *request, + struct GNUNET_DNSPARSER_Packet *p, struct GNUNET_DNSPARSER_Query *q) { struct InterceptLookupHandle* ilh; @@ -236,7 +243,6 @@ start_resolution_for_dns(struct GNUNET_DNS_RequestHandle *request, GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Starting resolution for %s (type=%d)!\n", q->name, q->type); - ilh = GNUNET_malloc(sizeof(struct InterceptLookupHandle)); ilh->packet = p; ilh->query = q; @@ -246,11 +252,11 @@ start_resolution_for_dns(struct GNUNET_DNS_RequestHandle *request, gns_resolver_lookup_record(our_zone, our_zone, q->type, q->name, our_key, default_lookup_timeout, + GNUNET_NO, &reply_to_dns, ilh); } - /** * The DNS request handler * Called for every incoming DNS request. @@ -261,17 +267,16 @@ start_resolution_for_dns(struct GNUNET_DNS_RequestHandle *request, * @param request udp payload of the DNS request */ static void -handle_dns_request(void *cls, - struct GNUNET_DNS_RequestHandle *rh, - size_t request_length, - const char *request) +handle_dns_request (void *cls, + struct GNUNET_DNS_RequestHandle *rh, + size_t request_length, + const char *request) { struct GNUNET_DNSPARSER_Packet *p; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Hijacked a DNS request...processing\n"); - p = GNUNET_DNSPARSER_parse (request, request_length); - - if (NULL == p) + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Hijacked a DNS request...processing\n"); + if (NULL == (p = GNUNET_DNSPARSER_parse (request, request_length))) { GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Received malformed DNS packet, leaving it untouched\n"); @@ -292,7 +297,7 @@ handle_dns_request(void *cls, * The way it is implemented here now is buggy and will lead to erratic * behaviour (if multiple queries are present). */ - if (p->num_queries == 0) + if (0 == p->num_queries) { GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "No Queries in DNS packet... forwarding\n"); @@ -301,35 +306,31 @@ handle_dns_request(void *cls, return; } - if (p->num_queries > 1) - { - /* Note: We could also look for .gnunet */ - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - ">1 queriy in DNS packet... odd. We only process #1\n"); - } - - /** - * Check for .gnunet/.zkey + * Check for .gads/.zkey */ - if ((is_gnunet_tld(p->queries[0].name) == GNUNET_YES) || + if ((is_gads_tld(p->queries[0].name) == GNUNET_YES) || (is_zkey_tld(p->queries[0].name) == GNUNET_YES) || (strcmp(p->queries[0].name, GNUNET_GNS_TLD) == 0)) { - start_resolution_for_dns(rh, p, p->queries); - } - else - { - /** - * This request does not concern us. Forward to real DNS. - */ - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "Request for %s is forwarded to DNS\n", p->queries[0].name); - GNUNET_DNS_request_forward (rh); - GNUNET_DNSPARSER_free_packet (p); + if (p->num_queries > 1) + { + /* Note: We could also look for .gads */ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + ">1 queriy in DNS packet... odd. We only process #1\n"); + } + start_resolution_for_dns (rh, p, p->queries); + return; } - + /** + * This request does not concern us. Forward to real DNS. + */ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Request for %s is forwarded to DNS\n", + p->queries[0].name); + GNUNET_DNS_request_forward (rh); + GNUNET_DNSPARSER_free_packet (p); } @@ -342,53 +343,48 @@ handle_dns_request(void *cls, * @return GNUNET_OK on success */ int -gns_interceptor_init(struct GNUNET_CRYPTO_ShortHashCode zone, - struct GNUNET_CRYPTO_RsaPrivateKey *key, - const struct GNUNET_CONFIGURATION_Handle *c) +gns_interceptor_init (struct GNUNET_CRYPTO_ShortHashCode zone, + struct GNUNET_CRYPTO_RsaPrivateKey *key, + const struct GNUNET_CONFIGURATION_Handle *c) { - unsigned long long default_lookup_timeout_secs = 0; - GNUNET_log(GNUNET_ERROR_TYPE_INFO, "DNS hijacking enabled... connecting to service.\n"); - our_zone = zone; our_key = key; /** * Do gnunet dns init here */ - dns_handle = GNUNET_DNS_connect(c, - GNUNET_DNS_FLAG_PRE_RESOLUTION, - &handle_dns_request, /* rh */ - NULL); /* Closure */ - - if (GNUNET_OK == - GNUNET_CONFIGURATION_get_value_number(c, "gns", - "DEFAULT_LOOKUP_TIMEOUT", - &default_lookup_timeout_secs)) - { - default_lookup_timeout = GNUNET_TIME_relative_multiply( - GNUNET_TIME_UNIT_SECONDS, - default_lookup_timeout_secs); - } - + dns_handle = GNUNET_DNS_connect (c, + GNUNET_DNS_FLAG_PRE_RESOLUTION, + &handle_dns_request, /* rh */ + NULL); /* Closure */ + + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_time (c, "gns", + "DEFAULT_LOOKUP_TIMEOUT", + &default_lookup_timeout)) + default_lookup_timeout = GNUNET_TIME_UNIT_ZERO; if (NULL == dns_handle) { GNUNET_log(GNUNET_ERROR_TYPE_ERROR, "Failed to connect to the dnsservice!\n"); return GNUNET_SYSERR; } - return GNUNET_YES; } + /** * Disconnect from interceptor */ void -gns_interceptor_stop(void) +gns_interceptor_stop () { - if (dns_handle) + if (NULL != dns_handle) + { GNUNET_DNS_disconnect(dns_handle); + dns_handle = NULL; + } } /* end of gns_interceptor.c */ diff --git a/src/gns/gnunet-service-gns_interceptor.h b/src/gns/gnunet-service-gns_interceptor.h index dc39aec..613ce8c 100644 --- a/src/gns/gnunet-service-gns_interceptor.h +++ b/src/gns/gnunet-service-gns_interceptor.h @@ -1,6 +1,32 @@ +/* + This file is part of GNUnet. + (C) 2009, 2010, 2011, 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ +/** + * @file gns/gnunet-service-gns_interceptor.h + * @brief GNUnet GNS service + * @author Martin Schanzenbach + */ #ifndef GNUNET_GNS_INTERCEPTOR_H #define GNUNET_GNS_INTERCEPTOR_H +#include "gnunet_util_lib.h" + /** * Initialize dns interceptor * @@ -10,14 +36,14 @@ * @return GNUNET_YES on success GNUNET_SYSERR on error */ int -gns_interceptor_init(struct GNUNET_CRYPTO_ShortHashCode zone, - struct GNUNET_CRYPTO_RsaPrivateKey *key, - const struct GNUNET_CONFIGURATION_Handle *c); +gns_interceptor_init (struct GNUNET_CRYPTO_ShortHashCode zone, + struct GNUNET_CRYPTO_RsaPrivateKey *key, + const struct GNUNET_CONFIGURATION_Handle *c); /** * Stops the interceptor */ void -gns_interceptor_stop(void); +gns_interceptor_stop (void); #endif diff --git a/src/gns/gnunet-service-gns_resolver.c b/src/gns/gnunet-service-gns_resolver.c index cf12e4b..627be0b 100644 --- a/src/gns/gnunet-service-gns_resolver.c +++ b/src/gns/gnunet-service-gns_resolver.c @@ -19,8 +19,6 @@ */ /** - * - * * @file gns/gnunet-service-gns_resolver.c * @brief GNUnet GNS resolver logic * @author Martin Schanzenbach @@ -32,15 +30,28 @@ #include "gnunet_dht_service.h" #include "gnunet_namestore_service.h" #include "gnunet_dns_service.h" +#include "gnunet_resolver_service.h" #include "gnunet_dnsparser_lib.h" +#include "gns_protocol.h" #include "gnunet_gns_service.h" +#include "gns_common.h" #include "block_gns.h" #include "gns.h" #include "gnunet-service-gns_resolver.h" +#ifndef WINDOWS +#include "gnunet_vpn_service.h" +#endif + +/** + * Default DHT timeout + */ #define DHT_LOOKUP_TIMEOUT DHT_OPERATION_TIMEOUT + +/** + * DHT replication level + */ #define DHT_GNS_REPLICATION_LEVEL 5 -#define MAX_DNS_LABEL_LENGTH 63 /** @@ -48,6 +59,13 @@ */ static struct GNUNET_NAMESTORE_Handle *namestore_handle; +#ifndef WINDOWS +/** + * Our handle to the vpn service + */ +static struct GNUNET_VPN_Handle *vpn_handle; +#endif + /** * Resolver handle to the dht */ @@ -58,11 +76,21 @@ static struct GNUNET_DHT_Handle *dht_handle; */ static struct GNUNET_CONTAINER_Heap *dht_lookup_heap; +/** + * Heap for namestore queues + */ +static struct GNUNET_CONTAINER_Heap *ns_task_heap; + /** * Maximum amount of parallel queries in background */ static unsigned long long max_allowed_background_queries; +/** + * Maximum amount of parallel namestore tasks in background + */ +static unsigned long long max_allowed_ns_tasks; + /** * Wheather or not to ignore pending records */ @@ -73,12 +101,159 @@ static int ignore_pending_records; */ static struct GNUNET_CRYPTO_ShortHashCode local_zone; +/** + * Background shortening handles + */ +static struct GetPseuAuthorityHandle *gph_head; + +/** + * Background shortening handles + */ +static struct GetPseuAuthorityHandle *gph_tail; + +/** + * Resolver lookup list + */ +static struct ResolverHandle *rlh_head; + +/** + * Resolver lookup list + */ +static struct ResolverHandle *rlh_tail; + +/** + * Resolver shorten list + */ +static struct ResolverHandle *nsh_head; + +/** + * Resolver shorten list + */ +static struct ResolverHandle *nsh_tail; + +/** + * Resolver get auth list + */ +static struct ResolverHandle *nah_head; + +/** + * Resolver get auth list + */ +static struct ResolverHandle *nah_tail; + +/** + * Global configuration. + */ +static const struct GNUNET_CONFIGURATION_Handle *cfg; + /** * a resolution identifier pool variable - * FIXME overflow? * This is a non critical identifier useful for debugging */ -static unsigned long long rid = 0; +static unsigned long long rid_gen; + + +/** + * Check if name is in srv format (_x._y.xxx) + * + * @param name + * @return GNUNET_YES if true + */ +static int +is_srv (const char *name) +{ + char *ndup; + int ret; + + if (*name != '_') + return GNUNET_NO; + if (NULL == strstr (name, "._")) + return GNUNET_NO; + ret = GNUNET_YES; + ndup = GNUNET_strdup (name); + strtok (ndup, "."); + if (NULL == strtok (NULL, ".")) + ret = GNUNET_NO; + if (NULL == strtok (NULL, ".")) + ret = GNUNET_NO; + if (NULL != strtok (NULL, ".")) + ret = GNUNET_NO; + GNUNET_free (ndup); + return ret; +} + + +/** + * Determine if this name is canonical (is a legal name in a zone, without delegation); + * note that we do not test that the name does not contain illegal characters, we only + * test for delegation. Note that service records (i.e. _foo._srv) are canonical names + * even though they consist of multiple labels. + * + * Examples: + * a.b.gads = not canonical + * a = canonical + * _foo._srv = canonical + * _f.bar = not canonical + * + * @param name the name to test + * @return GNUNET_YES if canonical + */ +static int +is_canonical (const char *name) +{ + const char *pos; + const char *dot; + + if (NULL == strchr (name, '.')) + return GNUNET_YES; + if ('_' != name[0]) + return GNUNET_NO; + pos = &name[1]; + while (NULL != (dot = strchr (pos, '.'))) + if ('_' != dot[1]) + return GNUNET_NO; + else + pos = dot + 1; + return GNUNET_YES; +} + + +static void +free_get_pseu_authority_handle (struct GetPseuAuthorityHandle *gph) +{ + gph->namestore_task = NULL; + GNUNET_free (gph->auth); + GNUNET_CRYPTO_rsa_key_free (gph->key); + GNUNET_CONTAINER_DLL_remove (gph_head, gph_tail, gph); + GNUNET_free (gph); +} + + +/** + * Callback that shortens authorities + * + * @param gph the handle containing the name to shorten + */ +static void +shorten_authority_chain (struct GetPseuAuthorityHandle *gph); + + +/** + * Continuation for pkey record creation (shorten) + * + * @param cls a GetPseuAuthorityHandle + * @param success unused + * @param emsg unused + */ +static void +create_pkey_cont (void* cls, int32_t success, const char* emsg) +{ + //FIXME do sth with error + struct GetPseuAuthorityHandle* gph = cls; + + free_get_pseu_authority_handle (gph); +} + /** * Namestore calls this function if we have record for this name. @@ -93,62 +268,46 @@ static unsigned long long rid = 0; * @param signature the signature of the authority for the record data */ static void -process_pseu_lookup_ns(void* cls, - const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *key, - struct GNUNET_TIME_Absolute expiration, - const char *name, unsigned int rd_count, - const struct GNUNET_NAMESTORE_RecordData *rd, - const struct GNUNET_CRYPTO_RsaSignature *signature) +process_pseu_lookup_ns (void* cls, + const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *key, + struct GNUNET_TIME_Absolute expiration, + const char *name, unsigned int rd_count, + const struct GNUNET_NAMESTORE_RecordData *rd, + const struct GNUNET_CRYPTO_RsaSignature *signature) { - struct GetPseuAuthorityHandle* gph = (struct GetPseuAuthorityHandle*)cls; + struct GetPseuAuthorityHandle* gph = cls; struct GNUNET_NAMESTORE_RecordData new_pkey; + gph->namestore_task = NULL; if (rd_count > 0) { GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, "GNS_AUTO_PSEU: Name %s already taken in NS!\n", name); - if (0 == strcmp(gph->name, name)) - { - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_AUTO_PSEU: Intelligent replacement not implemented\n", - name); - GNUNET_free(gph); - return; - } - - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_AUTO_PSEU: Trying delegated name %s\n", gph->name); - memcpy(gph->new_name, gph->name, strlen(gph->name)+1); - GNUNET_NAMESTORE_lookup_record(namestore_handle, - &gph->zone, - gph->new_name, - GNUNET_NAMESTORE_TYPE_ANY, - &process_pseu_lookup_ns, - gph); + free_get_pseu_authority_handle (gph); return; } - /** name is free */ - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_AUTO_PSEU: Name %s not taken in NS! Adding\n", gph->new_name); + /* name is free */ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_AUTO_PSEU: Name %s not taken in NS! Adding\n", + gph->test_name); - new_pkey.expiration = GNUNET_TIME_UNIT_FOREVER_ABS; - new_pkey.data_size = sizeof(struct GNUNET_CRYPTO_ShortHashCode); - new_pkey.data = &gph->new_zone; + new_pkey.expiration_time = UINT64_MAX; + new_pkey.data_size = sizeof (struct GNUNET_CRYPTO_ShortHashCode); + new_pkey.data = &gph->auth->zone; new_pkey.record_type = GNUNET_GNS_RECORD_PKEY; new_pkey.flags = GNUNET_NAMESTORE_RF_AUTHORITY | GNUNET_NAMESTORE_RF_PRIVATE | GNUNET_NAMESTORE_RF_PENDING; - GNUNET_NAMESTORE_record_create (namestore_handle, - gph->key, - gph->new_name, - &new_pkey, - NULL, //cont - NULL); //cls - GNUNET_free(gph); - + gph->namestore_task = GNUNET_NAMESTORE_record_create (namestore_handle, + gph->key, + gph->test_name, + &new_pkey, + &create_pkey_cont, + gph); } + /** * process result of a dht pseu lookup * @@ -156,31 +315,33 @@ process_pseu_lookup_ns(void* cls, * @param name the pseu result or NULL */ static void -process_pseu_result(struct GetPseuAuthorityHandle* gph, char* name) +process_pseu_result (struct GetPseuAuthorityHandle* gph, + const char* name) { if (NULL == name) { - memcpy(gph->new_name, gph->name, strlen(gph->name)+1); - } - else - { - memcpy(gph->new_name, name, strlen(name)+1); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_AUTO_PSEU: No PSEU, no shorten. Finished.\n"); + free_get_pseu_authority_handle (gph); + return; } - - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_AUTO_PSEU: Checking %s for collision in NS\n", gph->new_name); - + + memcpy (gph->test_name, name, strlen(name) + 1); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_AUTO_PSEU: Checking %s for collision in NS\n", + gph->test_name); /** * Check for collision */ - GNUNET_NAMESTORE_lookup_record(namestore_handle, - &gph->zone, - gph->new_name, - GNUNET_NAMESTORE_TYPE_ANY, - &process_pseu_lookup_ns, - gph); + gph->namestore_task = GNUNET_NAMESTORE_lookup_record (namestore_handle, + &gph->our_zone, + gph->test_name, + GNUNET_NAMESTORE_TYPE_ANY, + &process_pseu_lookup_ns, + gph); } + /** * Handle timeout for dht request * @@ -188,18 +349,19 @@ process_pseu_result(struct GetPseuAuthorityHandle* gph, char* name) * @param tc the task context */ static void -handle_auth_discovery_timeout(void *cls, - const struct GNUNET_SCHEDULER_TaskContext *tc) +handle_auth_discovery_timeout (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) { - struct GetPseuAuthorityHandle* gph = (struct GetPseuAuthorityHandle*)cls; + struct GetPseuAuthorityHandle* gph = cls; - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_GET_AUTH: dht lookup for query PSEU timed out.\n"); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_GET_AUTH: dht lookup for query PSEU timed out.\n"); GNUNET_DHT_get_stop (gph->get_handle); gph->get_handle = NULL; - process_pseu_result(gph, NULL); + process_pseu_result (gph, NULL); } + /** * Function called when we find a PSEU entry in the DHT * @@ -215,145 +377,150 @@ handle_auth_discovery_timeout(void *cls, * @param data the record data */ static void -process_auth_discovery_dht_result(void* cls, - struct GNUNET_TIME_Absolute exp, - const GNUNET_HashCode * key, - const struct GNUNET_PeerIdentity *get_path, - unsigned int get_path_length, - const struct GNUNET_PeerIdentity *put_path, - unsigned int put_path_length, - enum GNUNET_BLOCK_Type type, - size_t size, const void *data) +process_auth_discovery_dht_result (void* cls, + struct GNUNET_TIME_Absolute exp, + const struct GNUNET_HashCode * key, + const struct GNUNET_PeerIdentity *get_path, + unsigned int get_path_length, + const struct GNUNET_PeerIdentity *put_path, + unsigned int put_path_length, + enum GNUNET_BLOCK_Type type, + size_t size, + const void *data) { - struct GetPseuAuthorityHandle* gph = (struct GetPseuAuthorityHandle*)cls; + struct GetPseuAuthorityHandle* gph = cls; struct GNSNameRecordBlock *nrb; - char* rd_data = (char*)data; + const char* rd_data = data; char* name; int num_records; size_t rd_size; int i; - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_GET_AUTH: got dht result (size=%d)\n", size); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_GET_AUTH: got dht result (size=%d)\n", size); - if (data == NULL) + /* stop lookup and timeout task */ + GNUNET_DHT_get_stop (gph->get_handle); + gph->get_handle = NULL; + GNUNET_SCHEDULER_cancel (gph->timeout); + + if (NULL == data) { - GNUNET_log(GNUNET_ERROR_TYPE_ERROR, - "GNS_GET_AUTH: got dht result null!\n", size); - GNUNET_break(0); - GNUNET_free(gph); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "GNS_GET_AUTH: got dht result null!\n", size); + free_get_pseu_authority_handle (gph); return; } nrb = (struct GNSNameRecordBlock*)data; - - /* stop lookup and timeout task */ - GNUNET_DHT_get_stop (gph->get_handle); - gph->get_handle = NULL; - GNUNET_SCHEDULER_cancel(gph->timeout); - - gph->get_handle = NULL; - - nrb = (struct GNSNameRecordBlock*)data; - name = (char*)&nrb[1]; - num_records = ntohl(nrb->rd_count); + num_records = ntohl (nrb->rd_count); { struct GNUNET_NAMESTORE_RecordData rd[num_records]; - rd_data += strlen(name) + 1 + sizeof(struct GNSNameRecordBlock); - rd_size = size - strlen(name) - 1 - sizeof(struct GNSNameRecordBlock); + rd_data += strlen (name) + 1 + sizeof (struct GNSNameRecordBlock); + rd_size = size - strlen (name) - 1 - sizeof (struct GNSNameRecordBlock); if (GNUNET_SYSERR == GNUNET_NAMESTORE_records_deserialize (rd_size, rd_data, num_records, rd)) { - GNUNET_log(GNUNET_ERROR_TYPE_ERROR, - "GNS_GET_AUTH: Error deserializing data!\n"); - GNUNET_break(0); - GNUNET_free(gph); - return; + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "GNS_GET_AUTH: Error deserializing data!\n"); } - - for (i=0; inamestore_task = NULL; /* no pseu found */ - if (rd_count == 0) + if (0 == rd_count) { - /** - * check dht - */ - GNUNET_CRYPTO_short_hash("+", strlen("+"), &name_hash); - GNUNET_CRYPTO_short_hash_double (&name_hash, &name_hash_double); - GNUNET_CRYPTO_short_hash_double (&gph->new_zone, &zone_hash_double); - GNUNET_CRYPTO_hash_xor(&name_hash_double, &zone_hash_double, &lookup_key); - GNUNET_CRYPTO_hash_to_enc (&lookup_key, &lookup_key_string); - - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_AUTO_PSEU: starting dht lookup for %s with key: %s\n", - "+", (char*)&lookup_key_string); + GNUNET_GNS_get_key_for_record (GNUNET_GNS_TLD_PLUS, &gph->auth->zone, &lookup_key); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_AUTO_PSEU: starting dht lookup for %s with key: %s\n", + GNUNET_GNS_TLD_PLUS, + GNUNET_h2s (&lookup_key)); - gph->timeout = GNUNET_SCHEDULER_add_delayed(DHT_LOOKUP_TIMEOUT, - &handle_auth_discovery_timeout, gph); + gph->timeout = GNUNET_SCHEDULER_add_delayed (DHT_LOOKUP_TIMEOUT, + &handle_auth_discovery_timeout, gph); - xquery = htonl(GNUNET_GNS_RECORD_PSEU); + xquery = htonl (GNUNET_GNS_RECORD_PSEU); - GNUNET_assert(gph->get_handle == NULL); - gph->get_handle = GNUNET_DHT_get_start(dht_handle, + GNUNET_assert (gph->get_handle == NULL); + + gph->get_handle = GNUNET_DHT_get_start (dht_handle, GNUNET_BLOCK_TYPE_GNS_NAMERECORD, &lookup_key, DHT_GNS_REPLICATION_LEVEL, - GNUNET_DHT_RO_NONE, + GNUNET_DHT_RO_DEMULTIPLEX_EVERYWHERE, &xquery, sizeof(xquery), &process_auth_discovery_dht_result, gph); return; } - for (i=0; inamestore_task = NULL; + if (0 == rd_len) { - - GNUNET_NAMESTORE_lookup_record(namestore_handle, - &gph->new_zone, - "+", - GNUNET_GNS_RECORD_PSEU, - &process_auth_discovery_ns_result, - gph); + gph->namestore_task = GNUNET_NAMESTORE_lookup_record (namestore_handle, + &gph->auth->zone, + GNUNET_GNS_MASTERZONE_STR, + GNUNET_GNS_RECORD_PSEU, + &process_auth_discovery_ns_result, + gph); + return; } - - + /* we found a match in our own zone */ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_AUTO_PSEU: name for zone in our root %s\n", name); + free_get_pseu_authority_handle (gph); } /** - * Callback for new authories + * Callback that shortens authorities * - * @param name the name given by delegation - * @param zone the authority - * @param our_zone our local zone - * @param key the private key of our authority - */ -static void process_discovered_authority(char* name, - struct GNUNET_CRYPTO_ShortHashCode zone, - struct GNUNET_CRYPTO_ShortHashCode our_zone, - struct GNUNET_CRYPTO_RsaPrivateKey *key) + * @param gph the handle to the shorten request + */ +static void +shorten_authority_chain (struct GetPseuAuthorityHandle *gph) { - struct GetPseuAuthorityHandle *gph; - size_t namelen; - - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_AUTO_PSEU: New authority %s discovered\n", - name); - - gph = GNUNET_malloc(sizeof(struct GetPseuAuthorityHandle)); - namelen = strlen(name) + 1; - memcpy(gph->name, name, namelen); - - gph->new_zone = zone; - gph->zone = our_zone; - gph->key = key; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_AUTO_PSEU: New authority %s discovered\n", + gph->auth->name); - GNUNET_NAMESTORE_zone_to_name (namestore_handle, - &our_zone, - &gph->new_zone, + gph->namestore_task = GNUNET_NAMESTORE_zone_to_name (namestore_handle, + &gph->our_zone, + &gph->auth->zone, &process_zone_to_name_discover, gph); +} + +/** + * Start shortening algorithm using auth as + * authority chain + * + * @param auth the authorities that were resolved + * @param key the private key for PKEY import + */ +static void +start_shorten (struct AuthorityChain *auth, + const struct GNUNET_CRYPTO_RsaPrivateKey *key) +{ + struct GetPseuAuthorityHandle *gph; + struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded pkey; + struct GNUNET_CRYPTO_RsaPrivateKeyBinaryEncoded *pb_key; + + GNUNET_CRYPTO_rsa_key_get_public (key, &pkey); + if (NULL == (pb_key = GNUNET_CRYPTO_rsa_encode_key (key))) + { + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + "Failed to encode RSA key on shorten\n"); + return; + } + gph = GNUNET_malloc (sizeof (struct GetPseuAuthorityHandle)); + gph->key = GNUNET_CRYPTO_rsa_decode_key ((const char*) pb_key, ntohs (pb_key->len)); + GNUNET_free (pb_key); + if (NULL == gph->key) + { + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + "Failed to decode RSA key on shorten\n"); + GNUNET_free (gph); + return; + } + GNUNET_CRYPTO_short_hash (&pkey, + sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded), + &gph->our_zone); + gph->auth = GNUNET_malloc (sizeof (struct AuthorityChain)); + memcpy (gph->auth, auth, sizeof (struct AuthorityChain)); + GNUNET_CONTAINER_DLL_insert (gph_head, gph_tail, gph); + shorten_authority_chain (gph); } + /** * Initialize the resolver * * @param nh the namestore handle * @param dh the dht handle * @param lz the local zone's hash + * @param c configuration handle * @param max_bg_queries maximum number of parallel background queries in dht * @param ignore_pending ignore records that still require user confirmation * on lookup * @return GNUNET_OK on success */ int -gns_resolver_init(struct GNUNET_NAMESTORE_Handle *nh, - struct GNUNET_DHT_Handle *dh, - struct GNUNET_CRYPTO_ShortHashCode lz, - unsigned long long max_bg_queries, - int ignore_pending) +gns_resolver_init (struct GNUNET_NAMESTORE_Handle *nh, + struct GNUNET_DHT_Handle *dh, + struct GNUNET_CRYPTO_ShortHashCode lz, + const struct GNUNET_CONFIGURATION_Handle *c, + unsigned long long max_bg_queries, + int ignore_pending) { + if ( (NULL == nh) || + (NULL == dh) ) + return GNUNET_SYSERR; + + cfg = c; namestore_handle = nh; dht_handle = dh; local_zone = lz; dht_lookup_heap = - GNUNET_CONTAINER_heap_create(GNUNET_CONTAINER_HEAP_ORDER_MIN); + GNUNET_CONTAINER_heap_create (GNUNET_CONTAINER_HEAP_ORDER_MIN); + ns_task_heap = + GNUNET_CONTAINER_heap_create (GNUNET_CONTAINER_HEAP_ORDER_MIN); max_allowed_background_queries = max_bg_queries; - ignore_pending_records = ignore_pending; - - if ((namestore_handle != NULL) && (dht_handle != NULL)) - { - return GNUNET_OK; - } - return GNUNET_SYSERR; + max_allowed_ns_tasks = GNUNET_GNS_MAX_NS_TASKS; + ignore_pending_records = ignore_pending; + GNUNET_RESOLVER_connect (cfg); + return GNUNET_OK; } /** - * Cleanup background lookups + * finish lookup * - * @param cls closure to iterator - * @param node heap nodes - * @param element the resolver handle - * @param cost heap cost - * @return always GNUNET_YES - */ -static int -cleanup_pending_background_queries(void* cls, - struct GNUNET_CONTAINER_HeapNode *node, - void *element, - GNUNET_CONTAINER_HeapCostType cost) -{ - struct ResolverHandle *rh = (struct ResolverHandle *)element; - ResolverCleanupContinuation cont = cls; - - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_CLEANUP-%llu: Terminating background lookup for %s\n", - rh->id, rh->name); - GNUNET_DHT_get_stop(rh->get_handle); - rh->get_handle = NULL; - rh->proc(rh->proc_cls, rh, 0, NULL); - - GNUNET_CONTAINER_heap_remove_node(node); - - if (GNUNET_CONTAINER_heap_get_size(dht_lookup_heap) == 0) - cont(); - - - return GNUNET_YES; -} - - -/** - * Shutdown resolver + * @param rh resolver handle + * @param rlh record lookup handle + * @param rd_count number of results + * @param rd results */ -void -gns_resolver_cleanup(ResolverCleanupContinuation cont) -{ - unsigned int s = GNUNET_CONTAINER_heap_get_size(dht_lookup_heap); - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_CLEANUP: %d pending background queries to terminate\n", s); - - if (0 != s) - GNUNET_CONTAINER_heap_iterate (dht_lookup_heap, - &cleanup_pending_background_queries, - cont); - else - cont(); -} +static void +finish_lookup (struct ResolverHandle *rh, + struct RecordLookupHandle* rlh, + unsigned int rd_count, + const struct GNUNET_NAMESTORE_RecordData *rd); /** @@ -528,7 +684,7 @@ gns_resolver_cleanup(ResolverCleanupContinuation cont) * @param rh the handle to free */ static void -free_resolver_handle(struct ResolverHandle* rh) +free_resolver_handle (struct ResolverHandle* rh) { struct AuthorityChain *ac; struct AuthorityChain *ac_next; @@ -536,37 +692,145 @@ free_resolver_handle(struct ResolverHandle* rh) if (NULL == rh) return; - ac = rh->authority_chain_head; - - while (NULL != ac) + ac_next = rh->authority_chain_head; + while (NULL != (ac = ac_next)) { ac_next = ac->next; - GNUNET_free(ac); - ac = ac_next; + GNUNET_free (ac); + } + + if (NULL != rh->get_handle) + GNUNET_DHT_get_stop (rh->get_handle); + if (NULL != rh->dns_raw_packet) + GNUNET_free (rh->dns_raw_packet); + if (NULL != rh->namestore_task) + { + GNUNET_NAMESTORE_cancel (rh->namestore_task); + rh->namestore_task = NULL; } - GNUNET_free(rh); + if (GNUNET_SCHEDULER_NO_TASK != rh->dns_read_task) + GNUNET_SCHEDULER_cancel (rh->dns_read_task); + if (GNUNET_SCHEDULER_NO_TASK != rh->timeout_task) + GNUNET_SCHEDULER_cancel (rh->timeout_task); + if (NULL != rh->dns_sock) + GNUNET_NETWORK_socket_close (rh->dns_sock); + if (NULL != rh->dns_resolver_handle) + GNUNET_RESOLVER_request_cancel (rh->dns_resolver_handle); + if (NULL != rh->rd.data) + GNUNET_free ((void*)(rh->rd.data)); + if (NULL != rh->dht_heap_node) + GNUNET_CONTAINER_heap_remove_node (rh->dht_heap_node); + GNUNET_free (rh); } /** - * Callback when record data is put into namestore + * finish shorten * - * @param cls the closure - * @param success GNUNET_OK on success - * @param emsg the error message. NULL if SUCCESS==GNUNET_OK + * @param rh resolver handle + * @param nsh name shorten handle */ -void -on_namestore_record_put_result(void *cls, - int32_t success, - const char *emsg) -{ - if (GNUNET_NO == success) - { - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_NS: records already in namestore\n"); - return; - } - else if (GNUNET_YES == success) +static void +finish_shorten (struct ResolverHandle *rh, + struct NameShortenHandle *nsh); + + +/** + * finish get auth + * + * @param rh resolver handle + * @param nah get name authority handle + */ +static void +finish_get_auth (struct ResolverHandle *rh, + struct GetNameAuthorityHandle* rlh); + + +/** + * Shutdown resolver + */ +void +gns_resolver_cleanup () +{ + struct GetPseuAuthorityHandle *tmp; + struct ResolverHandle *rh; + struct NamestoreBGTask *nbg; + + while (NULL != (tmp = gph_head)) + { + if (tmp->get_handle != NULL) + { + GNUNET_DHT_get_stop (tmp->get_handle); + tmp->get_handle = NULL; + } + if (tmp->timeout != GNUNET_SCHEDULER_NO_TASK) + { + GNUNET_SCHEDULER_cancel (tmp->timeout); + tmp->timeout = GNUNET_SCHEDULER_NO_TASK; + } + if (NULL != tmp->namestore_task) + { + GNUNET_NAMESTORE_cancel (tmp->namestore_task); + tmp->namestore_task = NULL; + } + free_get_pseu_authority_handle (tmp); + } + + while (NULL != rlh_head) + { + finish_lookup (rlh_head, rlh_head->proc_cls, 0, NULL); + } + while (NULL != nsh_head) + { + finish_shorten (nsh_head, nsh_head->proc_cls); + } + while (NULL != nah_head) + { + finish_get_auth (nah_head, nah_head->proc_cls); + } + + while (NULL != (rh = GNUNET_CONTAINER_heap_remove_root(dht_lookup_heap))) + { + GNUNET_free (rh); + } + GNUNET_CONTAINER_heap_destroy (dht_lookup_heap); + dht_lookup_heap = NULL; + + while (NULL != (nbg = GNUNET_CONTAINER_heap_remove_root(ns_task_heap))) + { + GNUNET_NAMESTORE_cancel (nbg->qe); + GNUNET_free (nbg); + } + GNUNET_CONTAINER_heap_destroy (ns_task_heap); + ns_task_heap = NULL; + +} + + +/** + * Callback when record data is put into namestore + * + * @param cls the closure + * @param success GNUNET_OK on success + * @param emsg the error message. NULL if SUCCESS==GNUNET_OK + */ +void +on_namestore_record_put_result (void *cls, + int32_t success, + const char *emsg) +{ + struct NamestoreBGTask *nbg = cls; + + GNUNET_CONTAINER_heap_remove_node (nbg->node); + GNUNET_free (nbg); + + if (GNUNET_NO == success) + { + GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, + "GNS_NS: records already in namestore\n"); + return; + } + else if (GNUNET_YES == success) { GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, "GNS_NS: records successfully put in namestore\n"); @@ -577,15 +841,26 @@ on_namestore_record_put_result(void *cls, "GNS_NS: Error putting records into namestore: %s\n", emsg); } + +/** + * Lookup timeout task + * + * @param cls the ResolverHandle for the task that timed out + * @param tc the task context + */ static void -handle_lookup_timeout(void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +handle_lookup_timeout (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { struct ResolverHandle *rh = cls; - - if (rh->timeout_cont) - rh->timeout_cont(rh->timeout_cont_cls, tc); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Lookup timeout for request %llu triggered\n", + rh->id); + if (NULL != rh->timeout_cont) + rh->timeout_cont (rh->timeout_cont_cls, tc); } + /** * Processor for background lookups in the DHT * @@ -594,16 +869,17 @@ handle_lookup_timeout(void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) * @param rd record data */ static void -background_lookup_result_processor(void *cls, +background_lookup_result_processor (void *cls, uint32_t rd_count, const struct GNUNET_NAMESTORE_RecordData *rd) { //We could do sth verbose/more useful here but it doesn't make any difference - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_BG: background dht lookup for finished. (%d results)\n", - rd_count); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_BG: background dht lookup finished. (%d results)\n", + rd_count); } + /** * Handle timeout for DHT requests * @@ -611,40 +887,40 @@ background_lookup_result_processor(void *cls, * @param tc the task context */ static void -dht_lookup_timeout(void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +dht_lookup_timeout (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { struct ResolverHandle *rh = cls; - struct RecordLookupHandle *rlh = (struct RecordLookupHandle *)rh->proc_cls; - char new_name[MAX_DNS_NAME_LENGTH]; + struct RecordLookupHandle *rlh = rh->proc_cls; + char new_name[GNUNET_DNSPARSER_MAX_NAME_LENGTH]; - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_PHASE_REC-%d: dht lookup for query %s (%ds)timed out.\n", - rh->id, rh->name, rh->timeout.rel_value); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_REC-%llu: dht lookup for query %s (%llus) timed out.\n", + rh->id, rh->name, rh->timeout.rel_value); /** * Start resolution in bg */ - //strcpy(new_name, rh->name); - //memcpy(new_name+strlen(new_name), GNUNET_GNS_TLD, strlen(GNUNET_GNS_TLD)); - GNUNET_snprintf(new_name, MAX_DNS_NAME_LENGTH, "%s.%s", - rh->name, GNUNET_GNS_TLD); + GNUNET_snprintf (new_name, GNUNET_DNSPARSER_MAX_NAME_LENGTH, "%s.%s", + rh->name, GNUNET_GNS_TLD); - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_PHASE_REC-%d: Starting background lookup for %s type %d\n", - rh->id, new_name, rlh->record_type); - - gns_resolver_lookup_record(rh->authority, - rh->private_local_zone, - rlh->record_type, - new_name, - rh->priv_key, - GNUNET_TIME_UNIT_FOREVER_REL, - &background_lookup_result_processor, - NULL); - rh->timeout_task = GNUNET_SCHEDULER_NO_TASK; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_REC-%llu: Starting background lookup for %s type %d\n", + rh->id, new_name, rlh->record_type); + gns_resolver_lookup_record (rh->authority, + rh->private_local_zone, + rlh->record_type, + new_name, + NULL, + GNUNET_TIME_UNIT_FOREVER_REL, + GNUNET_NO, + &background_lookup_result_processor, + NULL); + + rh->timeout_task = GNUNET_SCHEDULER_NO_TASK; + GNUNET_DHT_get_stop (rh->get_handle); rh->get_handle = NULL; - rh->proc(rh->proc_cls, rh, 0, NULL); + rh->proc (rh->proc_cls, rh, 0, NULL); } @@ -664,93 +940,79 @@ dht_lookup_timeout(void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) * @param data the record data */ static void -process_record_result_dht(void* cls, - struct GNUNET_TIME_Absolute exp, - const GNUNET_HashCode * key, - const struct GNUNET_PeerIdentity *get_path, - unsigned int get_path_length, - const struct GNUNET_PeerIdentity *put_path, - unsigned int put_path_length, - enum GNUNET_BLOCK_Type type, - size_t size, const void *data) +process_record_result_dht (void* cls, + struct GNUNET_TIME_Absolute exp, + const struct GNUNET_HashCode * key, + const struct GNUNET_PeerIdentity *get_path, + unsigned int get_path_length, + const struct GNUNET_PeerIdentity *put_path, + unsigned int put_path_length, + enum GNUNET_BLOCK_Type type, + size_t size, const void *data) { - struct ResolverHandle *rh; - struct RecordLookupHandle *rlh; - struct GNSNameRecordBlock *nrb; + struct ResolverHandle *rh = cls; + struct RecordLookupHandle *rlh = rh->proc_cls; + const struct GNSNameRecordBlock *nrb = data; uint32_t num_records; - char* name = NULL; - char* rd_data = (char*)data; - int i; - int rd_size; - - rh = (struct ResolverHandle *)cls; - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_PHASE_REC-%d: got dht result (size=%d)\n", rh->id, size); - - if (data == NULL) - return; + const char* name; + const char* rd_data; + uint32_t i; + size_t rd_size; - //FIXME maybe check expiration here, check block type - - - rlh = (struct RecordLookupHandle *) rh->proc_cls; - nrb = (struct GNSNameRecordBlock*)data; - + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_REC-%llu: got dht result (size=%d)\n", rh->id, size); /* stop lookup and timeout task */ GNUNET_DHT_get_stop (rh->get_handle); rh->get_handle = NULL; - if (rh->dht_heap_node != NULL) { - GNUNET_CONTAINER_heap_remove_node(rh->dht_heap_node); + GNUNET_CONTAINER_heap_remove_node (rh->dht_heap_node); rh->dht_heap_node = NULL; } - if (rh->timeout_task != GNUNET_SCHEDULER_NO_TASK) { - GNUNET_SCHEDULER_cancel(rh->timeout_task); + GNUNET_SCHEDULER_cancel (rh->timeout_task); rh->timeout_task = GNUNET_SCHEDULER_NO_TASK; } - rh->get_handle = NULL; - name = (char*)&nrb[1]; - num_records = ntohl(nrb->rd_count); + name = (const char*) &nrb[1]; + num_records = ntohl (nrb->rd_count); { struct GNUNET_NAMESTORE_RecordData rd[num_records]; - - rd_data += strlen(name) + 1 + sizeof(struct GNSNameRecordBlock); - rd_size = size - strlen(name) - 1 - sizeof(struct GNSNameRecordBlock); - - if (GNUNET_SYSERR == GNUNET_NAMESTORE_records_deserialize (rd_size, - rd_data, - num_records, - rd)) + struct NamestoreBGTask *ns_heap_root; + struct NamestoreBGTask *namestore_bg_task; + + rd_data = &name[strlen (name) + 1]; + rd_size = size - strlen (name) - 1 - sizeof (struct GNSNameRecordBlock); + if (GNUNET_SYSERR == + GNUNET_NAMESTORE_records_deserialize (rd_size, + rd_data, + num_records, + rd)) { - GNUNET_log(GNUNET_ERROR_TYPE_ERROR, - "GNS_PHASE_REC-%d: Error deserializing data!\n", rh->id); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "GNS_PHASE_REC-%llu: Error deserializing data!\n", rh->id); + rh->proc (rh->proc_cls, rh, 0, NULL); return; } - - for (i=0; iid, name, rh->name); - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_PHASE_REC-%d: Got type: %d\n", - rh->id, rd[i].record_type); - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_PHASE_REC-%d: Got data length: %d\n", - rh->id, rd[i].data_size); - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_PHASE_REC-%d: Got flag %d\n", - rh->id, rd[i].flags); - - if ((strcmp(name, rh->name) == 0) && - (rd[i].record_type == rlh->record_type)) - { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_REC-%llu: Got name: %s (wanted %s)\n", + rh->id, name, rh->name); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_REC-%llu: Got type: %d (wanted %d)\n", + rh->id, rd[i].record_type, rlh->record_type); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_REC-%llu: Got data length: %d\n", + rh->id, rd[i].data_size); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_REC-%llu: Got flag %d\n", + rh->id, rd[i].flags); + + if ((strcmp (name, rh->name) == 0) && + (rd[i].record_type == rlh->record_type)) rh->answered++; - } } @@ -758,9 +1020,23 @@ process_record_result_dht(void* cls, * FIXME check pubkey against existing key in namestore? * https://gnunet.org/bugs/view.php?id=2179 */ + if (max_allowed_ns_tasks <= + GNUNET_CONTAINER_heap_get_size (ns_task_heap)) + { + ns_heap_root = GNUNET_CONTAINER_heap_remove_root (ns_task_heap); + GNUNET_NAMESTORE_cancel (ns_heap_root->qe); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_REC-%llu: Replacing oldest background ns task\n", + rh->id); + } + /* Save to namestore */ - GNUNET_NAMESTORE_record_put (namestore_handle, + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_REC-%llu: Caching record for %s\n", + rh->id, name); + namestore_bg_task = GNUNET_malloc (sizeof (struct NamestoreBGTask)); + namestore_bg_task->qe = GNUNET_NAMESTORE_record_put (namestore_handle, &nrb->public_key, name, exp, @@ -768,15 +1044,16 @@ process_record_result_dht(void* cls, rd, &nrb->signature, &on_namestore_record_put_result, //cont - NULL); //cls + namestore_bg_task); - - if (rh->answered) - rh->proc(rh->proc_cls, rh, num_records, rd); + namestore_bg_task->node = GNUNET_CONTAINER_heap_insert (ns_task_heap, + namestore_bg_task, + GNUNET_TIME_absolute_get().abs_value); + if (0 < rh->answered) + rh->proc (rh->proc_cls, rh, num_records, rd); else - rh->proc(rh->proc_cls, rh, 0, NULL); + rh->proc (rh->proc_cls, rh, 0, NULL); } - } @@ -787,51 +1064,39 @@ process_record_result_dht(void* cls, * @param rh the pending gns query context */ static void -resolve_record_dht(struct ResolverHandle *rh) +resolve_record_dht (struct ResolverHandle *rh) { + struct RecordLookupHandle *rlh = rh->proc_cls; uint32_t xquery; - struct GNUNET_CRYPTO_ShortHashCode name_hash; - GNUNET_HashCode lookup_key; - GNUNET_HashCode name_hash_double; - GNUNET_HashCode zone_hash_double; - struct GNUNET_CRYPTO_HashAsciiEncoded lookup_key_string; - struct RecordLookupHandle *rlh = (struct RecordLookupHandle *)rh->proc_cls; + struct GNUNET_HashCode lookup_key; struct ResolverHandle *rh_heap_root; - - GNUNET_CRYPTO_short_hash(rh->name, strlen(rh->name), &name_hash); - GNUNET_CRYPTO_short_hash_double(&name_hash, &name_hash_double); - GNUNET_CRYPTO_short_hash_double(&rh->authority, &zone_hash_double); - GNUNET_CRYPTO_hash_xor(&name_hash_double, &zone_hash_double, &lookup_key); - GNUNET_CRYPTO_hash_to_enc (&lookup_key, &lookup_key_string); - - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_PHASE_REC-%d: starting dht lookup for %s with key: %s\n", - rh->id, rh->name, (char*)&lookup_key_string); - //rh->timeout_task = GNUNET_SCHEDULER_NO_TASK; + GNUNET_GNS_get_key_for_record (rh->name, &rh->authority, &lookup_key); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_REC-%llu: starting dht lookup for %s with key: %s\n", + rh->id, rh->name, GNUNET_h2s (&lookup_key)); + rh->dht_heap_node = NULL; - if (rh->timeout.rel_value != GNUNET_TIME_UNIT_FOREVER_REL.rel_value) + if (GNUNET_TIME_UNIT_FOREVER_REL.rel_value != rh->timeout.rel_value) { /** * Update timeout if necessary */ - if (rh->timeout_task == GNUNET_SCHEDULER_NO_TASK) + if (GNUNET_SCHEDULER_NO_TASK == rh->timeout_task) { - - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_PHASE_REC-%d: Adjusting timeout\n", rh->id); - /* - * Set timeout for authority lookup phase to 1/2 - */ - rh->timeout_task = GNUNET_SCHEDULER_add_delayed( - GNUNET_TIME_relative_divide(rh->timeout, 2), - &handle_lookup_timeout, - rh); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_REC-%llu: Adjusting timeout to %s/2\n", + rh->id, + GNUNET_STRINGS_relative_time_to_string (rh->timeout, GNUNET_YES)); + /* + * Set timeout for authority lookup phase to 1/2 + */ + rh->timeout_task = GNUNET_SCHEDULER_add_delayed ( + GNUNET_TIME_relative_divide (rh->timeout, 2), + &handle_lookup_timeout, + rh); } - //rh->timeout_task = GNUNET_SCHEDULER_add_delayed (DHT_LOOKUP_TIMEOUT, - // &dht_lookup_timeout, - // rh); rh->timeout_cont = &dht_lookup_timeout; rh->timeout_cont_cls = rh; } @@ -841,35 +1106,35 @@ resolve_record_dht(struct ResolverHandle *rh) GNUNET_CONTAINER_heap_get_size (dht_lookup_heap)) { rh_heap_root = GNUNET_CONTAINER_heap_remove_root (dht_lookup_heap); - GNUNET_DHT_get_stop(rh_heap_root->get_handle); + GNUNET_DHT_get_stop (rh_heap_root->get_handle); rh_heap_root->get_handle = NULL; rh_heap_root->dht_heap_node = NULL; - - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_PHASE_REC-%d: Replacing oldest background query for %s\n", + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_REC-%llu: Replacing oldest background query for %s\n", rh->id, rh_heap_root->name); - rh_heap_root->proc(rh_heap_root->proc_cls, - rh_heap_root, - 0, - NULL); + rh_heap_root->proc (rh_heap_root->proc_cls, + rh_heap_root, + 0, + NULL); } rh->dht_heap_node = GNUNET_CONTAINER_heap_insert (dht_lookup_heap, rh, - GNUNET_TIME_absolute_get().abs_value); + GNUNET_TIME_absolute_get ().abs_value); } - - xquery = htonl(rlh->record_type); - - GNUNET_assert(rh->get_handle == NULL); - rh->get_handle = GNUNET_DHT_get_start(dht_handle, - GNUNET_BLOCK_TYPE_GNS_NAMERECORD, - &lookup_key, - DHT_GNS_REPLICATION_LEVEL, - GNUNET_DHT_RO_NONE, - &xquery, - sizeof(xquery), - &process_record_result_dht, - rh); + + xquery = htonl (rlh->record_type); + + GNUNET_assert (rh->get_handle == NULL); + rh->get_handle = GNUNET_DHT_get_start (dht_handle, + GNUNET_BLOCK_TYPE_GNS_NAMERECORD, + &lookup_key, + DHT_GNS_REPLICATION_LEVEL, + GNUNET_DHT_RO_DEMULTIPLEX_EVERYWHERE, + &xquery, + sizeof (xquery), + &process_record_result_dht, + rh); } @@ -887,50 +1152,43 @@ resolve_record_dht(struct ResolverHandle *rh) * @param signature the signature of the authority for the record data */ static void -process_record_result_ns(void* cls, - const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *key, - struct GNUNET_TIME_Absolute expiration, - const char *name, unsigned int rd_count, - const struct GNUNET_NAMESTORE_RecordData *rd, - const struct GNUNET_CRYPTO_RsaSignature *signature) +process_record_result_ns (void* cls, + const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *key, + struct GNUNET_TIME_Absolute expiration, + const char *name, unsigned int rd_count, + const struct GNUNET_NAMESTORE_RecordData *rd, + const struct GNUNET_CRYPTO_RsaSignature *signature) { - struct ResolverHandle *rh; - struct RecordLookupHandle *rlh; + struct ResolverHandle *rh = cls; + struct RecordLookupHandle *rlh = rh->proc_cls; struct GNUNET_TIME_Relative remaining_time; struct GNUNET_CRYPTO_ShortHashCode zone; + struct GNUNET_TIME_Absolute et; + unsigned int i; - rh = (struct ResolverHandle *) cls; - rlh = (struct RecordLookupHandle *)rh->proc_cls; - GNUNET_CRYPTO_short_hash(key, - sizeof(struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded), - &zone); + rh->namestore_task = NULL; + GNUNET_CRYPTO_short_hash (key, + sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded), + &zone); remaining_time = GNUNET_TIME_absolute_get_remaining (expiration); - - - rh->status = 0; - - if (name != NULL) + if (NULL != name) { rh->status |= RSL_RECORD_EXISTS; + if (remaining_time.rel_value == 0) + rh->status |= RSL_RECORD_EXPIRED; } - - if (remaining_time.rel_value == 0) - { - rh->status |= RSL_RECORD_EXPIRED; - } - - if (rd_count == 0) + if (0 == rd_count) { /** * Lookup terminated and no results */ GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_PHASE_REC-%d: Namestore lookup for %s terminated without results\n", - rh->id, name); + "GNS_PHASE_REC-%llu: Namestore lookup for %s terminated without results\n", + rh->id, name); GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_PHASE_REC-%d: Record %s unknown in namestore\n", + "GNS_PHASE_REC-%llu: Record %s unknown in namestore\n", rh->id, rh->name); /** * Our zone and no result? Cannot resolve TT @@ -939,163 +1197,779 @@ process_record_result_ns(void* cls, return; } - else + GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_REC-%llu: Processing additional result %s from namestore\n", + rh->id, name); + for (i = 0; i < rd_count;i++) { - - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_PHASE_REC-%d: Processing additional result %s from namestore\n", - rh->id, name); - int i; - for (i=0; irecord_type) - continue; + if (rd[i].record_type != rlh->record_type) + continue; - if (ignore_pending_records && - (rd[i].flags & GNUNET_NAMESTORE_RF_PENDING)) - { - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_PHASE_REC-%d: Record %s is awaiting user confirmation. Skipping\n", - rh->id, name); - continue; - } - - if ((GNUNET_TIME_absolute_get_remaining (rd[i].expiration)).rel_value - == 0) - { - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_PHASE_REC-%d: This record is expired. Skipping\n", - rh->id); - continue; - } - - rh->answered++; - + if (ignore_pending_records && + (rd[i].flags & GNUNET_NAMESTORE_RF_PENDING)) + { + GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_REC-%llu: Record %s is awaiting user confirmation. Skipping\n", + rh->id, name); + continue; } - /** - * no answers found - */ - if (rh->answered == 0) + //FIXME: eh? do I have to handle this here? + GNUNET_break (0 == (rd[i].flags & GNUNET_NAMESTORE_RF_RELATIVE_EXPIRATION)); + et.abs_value = rd[i].expiration_time; + if (0 == (GNUNET_TIME_absolute_get_remaining (et)).rel_value) { - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_PHASE_REC-%d: No answers found. This is odd!\n", rh->id); - rh->proc(rh->proc_cls, rh, 0, NULL); - return; + GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_REC-%llu: This record is expired. Skipping\n", + rh->id); + continue; } - - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_PHASE_REC-%d: Found %d answer(s) to query in %d records!\n", - rh->id, rh->answered, rd_count); - - rh->proc(rh->proc_cls, rh, rd_count, rd); + rh->answered++; } -} - -/** - * The final phase of resolution. - * rh->name is a name that is canonical and we do not have a delegation. - * Query namestore for this record - * - * @param rh the pending lookup - */ -static void -resolve_record_ns(struct ResolverHandle *rh) -{ - struct RecordLookupHandle *rlh = (struct RecordLookupHandle *)rh->proc_cls; - - /* We cancel here as to not include the ns lookup in the timeout */ - if (rh->timeout_task != GNUNET_SCHEDULER_NO_TASK) + /** + * no answers found + */ + if (0 == rh->answered) { - GNUNET_SCHEDULER_cancel(rh->timeout_task); - rh->timeout_task = GNUNET_SCHEDULER_NO_TASK; + GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_REC-%llu: No answers found. This is odd!\n", rh->id); + rh->proc(rh->proc_cls, rh, 0, NULL); + return; } - - /** - * Try to resolve this record in our namestore. - * The name to resolve is now in rh->authority_name - * since we tried to resolve it to an authority - * and failed. - **/ - GNUNET_NAMESTORE_lookup_record(namestore_handle, - &rh->authority, - rh->name, - rlh->record_type, - &process_record_result_ns, - rh); -} + GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_REC-%llu: Found %d answer(s) to query in %d records!\n", + rh->id, rh->answered, rd_count); + rh->proc(rh->proc_cls, rh, rd_count, rd); +} +#ifndef WINDOWS /** - * Handle timeout for DHT requests + * VPN redirect result callback * - * @param cls the request handle as closure - * @param tc the task context + * @param cls the resolver handle + * @param af the requested address family + * @param address in_addr(6) respectively */ static void -dht_authority_lookup_timeout(void *cls, - const struct GNUNET_SCHEDULER_TaskContext *tc) +process_record_result_vpn (void* cls, int af, const void *address) { struct ResolverHandle *rh = cls; struct RecordLookupHandle *rlh = rh->proc_cls; - char new_name[MAX_DNS_NAME_LENGTH]; + struct GNUNET_NAMESTORE_RecordData rd; GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_PHASE_DELEGATE_DHT-%llu: dht lookup for query %s (%ds)timed out.\n", - rh->id, rh->authority_name, rh->timeout.rel_value); - - rh->status |= RSL_TIMED_OUT; - - rh->timeout_task = GNUNET_SCHEDULER_NO_TASK; - - GNUNET_DHT_get_stop (rh->get_handle); - rh->get_handle = NULL; - - if (strcmp(rh->name, "") == 0) + "GNS_PHASE_REC_VPN-%llu: Got answer from VPN to query!\n", + rh->id); + if (AF_INET == af) { - /* - * promote authority back to name and try to resolve record - */ - strcpy(rh->name, rh->authority_name); - rh->proc(rh->proc_cls, rh, 0, NULL); + GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_REC-%llu: Answer is IPv4!\n", + rh->id); + if (GNUNET_GNS_RECORD_A != rlh->record_type) + { + GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_REC-%llu: Requested record is not IPv4!\n", + rh->id); + rh->proc (rh->proc_cls, rh, 0, NULL); + return; + } + rd.record_type = GNUNET_GNS_RECORD_A; + rd.expiration_time = UINT64_MAX; /* FIXME: should probably pick something shorter... */ + rd.data = address; + rd.data_size = sizeof (struct in_addr); + rd.flags = 0; + rh->proc (rh->proc_cls, rh, 1, &rd); + return; + } + else if (AF_INET6 == af) + { + GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_REC-%llu: Answer is IPv6!\n", + rh->id); + if (GNUNET_GNS_RECORD_AAAA != rlh->record_type) + { + GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_REC-%llu: Requested record is not IPv6!\n", + rh->id); + rh->proc (rh->proc_cls, rh, 0, NULL); + return; + } + rd.record_type = GNUNET_GNS_RECORD_AAAA; + rd.expiration_time = UINT64_MAX; /* FIXME: should probably pick something shorter... */ + rd.data = address; + rd.data_size = sizeof (struct in6_addr); + rd.flags = 0; + rh->proc (rh->proc_cls, rh, 1, &rd); + return; + } + + GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_REC-%llu: Got garbage from VPN!\n", + rh->id); + rh->proc (rh->proc_cls, rh, 0, NULL); +} +#endif + + +/** + * Process VPN lookup result for record + * + * @param cls the record lookup handle + * @param rh resolver handle + * @param rd_count number of results (1) + * @param rd record data containing the result + */ +static void +handle_record_vpn (void* cls, struct ResolverHandle *rh, + unsigned int rd_count, + const struct GNUNET_NAMESTORE_RecordData *rd) +{ + struct RecordLookupHandle* rlh = cls; + + if (0 == rd_count) + { + GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_REC_VPN-%llu: VPN returned no records. (status: %d)!\n", + rh->id, + rh->status); + /* give up, cannot resolve */ + finish_lookup(rh, rlh, 0, NULL); + return; + } + + /* results found yay */ + GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_REC_VPN-%llu: Record resolved from VPN!\n", + rh->id); + + finish_lookup(rh, rlh, rd_count, rd); +} + + +/** + * Sends a UDP dns query to a nameserver specified in the rh + * + * @param rh the resolver handle + */ +static void +send_dns_packet (struct ResolverHandle *rh); + + +/** + * Read DNS response + * + * @param cls the ResolverHandle for this lookup + * @param addr the sockaddr + * @param addrlen the socket address length + */ +static void +handle_dns_resolver (void *cls, + const struct sockaddr *addr, + socklen_t addrlen) +{ + struct ResolverHandle *rh = cls; + struct RecordLookupHandle *rlh = rh->proc_cls; + struct GNUNET_NAMESTORE_RecordData rd; + struct sockaddr_in *sai; + struct sockaddr_in6 *sai6; + + if (NULL == addr) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "No address found in DNS!\n"); + finish_lookup (rh, rlh, 0, NULL); + return; + } + + if (sizeof (struct sockaddr_in) == addrlen) + { + sai = (struct sockaddr_in*) addr; + rd.record_type = GNUNET_GNS_RECORD_A; + rd.data_size = sizeof (struct in_addr); + rd.data = &sai->sin_addr; + } + else if (sizeof (struct sockaddr_in6) == addrlen) + { + sai6 = (struct sockaddr_in6*) addr; + rd.record_type = GNUNET_GNS_RECORD_AAAA; + rd.data_size = sizeof (struct in6_addr); + rd.data = &sai6->sin6_addr; + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Address length is garbage!\n"); + finish_lookup (rh, rlh, 0, NULL); + return; + } + rd.expiration_time = UINT64_MAX; /* FIXME: should probably pick something shorter */ + rd.flags = 0; + finish_lookup (rh, rlh, 1, &rd); +} + + +/** + * Resolve DNS name via local stub resolver + * + * @param rh the resolver handle + */ +static void +resolve_dns_name (struct ResolverHandle *rh) +{ + struct RecordLookupHandle *rlh = rh->proc_cls; + int af; + + if ((GNUNET_GNS_RECORD_A != rlh->record_type) && + (GNUNET_GNS_RECORD_AAAA != rlh->record_type)) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Can only resolve A/AAAA via stub... abort\n"); + finish_lookup (rh, rlh, 0, NULL); + return; + } + + if (GNUNET_GNS_RECORD_A == rlh->record_type) + af = AF_INET; + else + af = AF_INET6; + + rh->dns_resolver_handle = GNUNET_RESOLVER_ip_get (rh->dns_name, + af, + rh->timeout, + &handle_dns_resolver, + rh); +} + + +/** + * Read DNS udp packet from socket + * + * @param cls the resolver handle + * @param tc task context + */ +static void +read_dns_response (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct ResolverHandle *rh = cls; + struct RecordLookupHandle *rlh = rh->proc_cls; + char buf[UINT16_MAX]; + ssize_t r; + struct sockaddr_in addr; + socklen_t addrlen; + struct GNUNET_DNSPARSER_Packet *packet; + struct GNUNET_NAMESTORE_RecordData rd; + int found_delegation = GNUNET_NO; + int found_cname = GNUNET_NO; + char* delegation_name = NULL; + int zone_offset = 0; + int i; + + rh->dns_read_task = GNUNET_SCHEDULER_NO_TASK; + if (0 == (tc->reason & GNUNET_SCHEDULER_REASON_READ_READY)) + { + /* timeout or shutdown */ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Terminating DNS query %d\n", tc->reason); + finish_lookup (rh, rlh, 0, NULL); + return; + } + + addrlen = sizeof (addr); + r = GNUNET_NETWORK_socket_recvfrom (rh->dns_sock, + buf, sizeof (buf), + (struct sockaddr*) &addr, + &addrlen); + + if (-1 == r) + { + GNUNET_log_strerror (GNUNET_ERROR_TYPE_ERROR, "recvfrom"); + finish_lookup (rh, rlh, 0, NULL); + return; + } + if (NULL == (packet = GNUNET_DNSPARSER_parse (buf, r))) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Failed to parse DNS reply!\n"); + finish_lookup (rh, rlh, 0, NULL); + return; + } + + for (i = 0; i < packet->num_answers; i++) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Got record type %d (want %d)\n", + packet->answers[i].type, + rlh->record_type); + /* http://tools.ietf.org/html/rfc1034#section-3.6.2 */ + if (packet->answers[i].type == GNUNET_GNS_RECORD_CNAME) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "CNAME... restarting query with %s\n", + packet->answers[i].data.hostname + ); + strcpy (rh->dns_name, packet->answers[i].data.hostname); + found_cname = GNUNET_YES; + continue; + } + + if ((packet->answers[i].type == rlh->record_type) && + (0 == strcmp (packet->answers[i].name, rh->dns_name))) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Found record!\n"); + rd.data = packet->answers[i].data.raw.data; + rd.data_size = packet->answers[i].data.raw.data_len; + rd.record_type = packet->answers[i].type; + rd.flags = 0; + rd.expiration_time = packet->answers[i].expiration_time.abs_value; + finish_lookup (rh, rlh, 1, &rd); + GNUNET_DNSPARSER_free_packet (packet); + return; + } + } + + if (GNUNET_YES == found_cname) + { + zone_offset = strlen (rh->dns_name) - strlen (rh->dns_zone) - 1; + + if (0 > zone_offset) + zone_offset = 0; + + /* restart query with CNAME */ + if (0 == strcmp (rh->dns_name+zone_offset, rh->dns_zone)) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Asking same server for %s\n", rh->dns_name); + send_dns_packet (rh); + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Trying system resolver for %s\n", rh->dns_name); + resolve_dns_name (rh); + } + + GNUNET_DNSPARSER_free_packet (packet); + return; + } + + for (i = 0; i < packet->num_authority_records; i++) + { + if (packet->authority_records[i].type == GNUNET_GNS_RECORD_NS) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Found NS delegation!\n"); + found_delegation = GNUNET_YES; + delegation_name = packet->authority_records[i].data.hostname; + break; + } + } + + for (i = 0; i < packet->num_additional_records; i++) + { + if (GNUNET_NO == found_delegation) + break; + + if ((packet->additional_records[i].type == GNUNET_GNS_RECORD_A) && + (0 == strcmp (packet->additional_records[i].name, delegation_name))) + { + GNUNET_assert (sizeof (struct in_addr) == + packet->authority_records[i].data.raw.data_len); + + rh->dns_addr.sin_addr = + *((struct in_addr*)packet->authority_records[i].data.raw.data); + send_dns_packet (rh); + GNUNET_DNSPARSER_free_packet (packet); + return; + } + } + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Nothing useful in DNS reply!\n"); + finish_lookup (rh, rlh, 0, NULL); + GNUNET_DNSPARSER_free_packet (packet); +} + + +/** + * Sends a UDP dns query to a nameserver specified in the rh + * + * @param rh the request handle + */ +static void +send_dns_packet (struct ResolverHandle *rh) +{ + struct GNUNET_NETWORK_FDSet *rset; + + rset = GNUNET_NETWORK_fdset_create (); + GNUNET_NETWORK_fdset_set (rset, rh->dns_sock); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Sending %d byte DNS query\n", + (int) rh->dns_raw_packet_size); + + if (GNUNET_SYSERR == + GNUNET_NETWORK_socket_sendto (rh->dns_sock, + rh->dns_raw_packet, + rh->dns_raw_packet_size, + (struct sockaddr*)&rh->dns_addr, + sizeof (struct sockaddr_in))) + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + _("Failed to send DNS request to %s\n"), + GNUNET_a2s ((const struct sockaddr *)&rh->dns_addr, + sizeof (struct sockaddr_in))); + + rh->dns_read_task = GNUNET_SCHEDULER_add_select (GNUNET_SCHEDULER_PRIORITY_DEFAULT, + rh->timeout, //FIXME less? + rset, + NULL, + &read_dns_response, + rh); + GNUNET_NETWORK_fdset_destroy (rset); +} + + +/** + * The final phase of resoution. + * We found a NS RR and want to resolve via DNS + * + * @param rh the pending lookup handle + * @param rd_count length of record data + * @param rd record data containing VPN RR + */ +static void +resolve_record_dns (struct ResolverHandle *rh, + unsigned int rd_count, + const struct GNUNET_NAMESTORE_RecordData *rd) +{ + struct RecordLookupHandle *rlh = rh->proc_cls; + struct GNUNET_DNSPARSER_Query query; + struct GNUNET_DNSPARSER_Packet packet; + struct GNUNET_DNSPARSER_Flags flags; + struct in_addr dnsip; + struct sockaddr_in addr; + struct sockaddr *sa; + unsigned int i; + + memset (&packet, 0, sizeof (struct GNUNET_DNSPARSER_Packet)); + memset (rh->dns_name, 0, sizeof (rh->dns_name)); + + /* We cancel here as to not include the ns lookup in the timeout */ + if (GNUNET_SCHEDULER_NO_TASK != rh->timeout_task) + { + GNUNET_SCHEDULER_cancel(rh->timeout_task); + rh->timeout_task = GNUNET_SCHEDULER_NO_TASK; + } + /* Start shortening */ + if ((NULL != rh->priv_key) && + (GNUNET_YES == is_canonical (rh->name))) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_REC_DNS-%llu: Trying to shorten authority chain\n", + rh->id); + start_shorten (rh->authority_chain_head, + rh->priv_key); + } + + for (i = 0; i < rd_count; i++) + { + /* Synthesize dns name */ + if (GNUNET_GNS_RECORD_NS == rd[i].record_type) + { + strcpy (rh->dns_zone, (char*)rd[i].data); + if (0 == strcmp (rh->name, "")) + strcpy (rh->dns_name, (char*)rd[i].data); + else + sprintf (rh->dns_name, "%s.%s", rh->name, (char*)rd[i].data); + } + /* The glue */ + if (GNUNET_GNS_RECORD_A == rd[i].record_type) + /* need to use memcpy as .data may be unaligned */ + memcpy (&dnsip, rd[i].data, sizeof (dnsip)); + } + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_REC_DNS-%llu: Looking up %s from %s\n", + rh->id, + rh->dns_name, + inet_ntoa (dnsip)); + rh->dns_sock = GNUNET_NETWORK_socket_create (AF_INET, SOCK_DGRAM, 0); + if (NULL == rh->dns_sock) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_REC_DNS-%llu: Error creating udp socket for dns!\n", + rh->id); + finish_lookup (rh, rlh, 0, NULL); + return; + } + + memset (&addr, 0, sizeof (struct sockaddr_in)); + sa = (struct sockaddr *) &addr; + sa->sa_family = AF_INET; + if (GNUNET_OK != GNUNET_NETWORK_socket_bind (rh->dns_sock, + sa, + sizeof (struct sockaddr_in))) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_REC_DNS-%llu: Error binding udp socket for dns!\n", + rh->id); + finish_lookup (rh, rlh, 0, NULL); + return; + } + query.name = rh->dns_name; + query.type = rlh->record_type; + query.class = GNUNET_DNSPARSER_CLASS_INTERNET; + memset (&flags, 0, sizeof (flags)); + flags.recursion_desired = 1; + flags.checking_disabled = 1; + packet.queries = &query; + packet.answers = NULL; + packet.authority_records = NULL; + packet.num_queries = 1; + packet.num_answers = 0; + packet.num_authority_records = 0; + packet.num_additional_records = 0; + packet.flags = flags; + packet.id = rh->id; + if (GNUNET_OK != GNUNET_DNSPARSER_pack (&packet, + UINT16_MAX, + &rh->dns_raw_packet, + &rh->dns_raw_packet_size)) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_REC_DNS-%llu: Creating raw dns packet!\n", + rh->id); + GNUNET_NETWORK_socket_close (rh->dns_sock); + finish_lookup (rh, rlh, 0, NULL); + return; + } + + rh->dns_addr.sin_family = AF_INET; + rh->dns_addr.sin_port = htons (53); //domain + rh->dns_addr.sin_addr = dnsip; +#if HAVE_SOCKADDR_IN_SIN_LEN + rh->dns_addr.sin_len = (u_char) sizeof (struct sockaddr_in); +#endif + send_dns_packet (rh); +} + + +/** + * The final phase of resoution. + * We found a VPN RR and want to request an IPv4/6 address + * + * @param rh the pending lookup handle + * @param rd_count length of record data + * @param rd record data containing VPN RR + */ +static void +resolve_record_vpn (struct ResolverHandle *rh, + unsigned int rd_count, + const struct GNUNET_NAMESTORE_RecordData *rd) +{ + struct RecordLookupHandle *rlh = rh->proc_cls; + struct GNUNET_HashCode serv_desc; + struct vpn_data* vpn; + int af; + + /* We cancel here as to not include the ns lookup in the timeout */ + if (GNUNET_SCHEDULER_NO_TASK != rh->timeout_task) + { + GNUNET_SCHEDULER_cancel(rh->timeout_task); + rh->timeout_task = GNUNET_SCHEDULER_NO_TASK; + } + /* Start shortening */ + if ((NULL != rh->priv_key) && + (GNUNET_YES == is_canonical (rh->name))) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_REC_VPN-%llu: Trying to shorten authority chain\n", + rh->id); + start_shorten (rh->authority_chain_head, + rh->priv_key); + } + + vpn = (struct vpn_data*)rd->data; + GNUNET_CRYPTO_hash ((char*)&vpn[1], + strlen ((char*)&vpn[1]) + 1, + &serv_desc); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_REC_VPN-%llu: proto %hu peer %s!\n", + rh->id, + ntohs (vpn->proto), + GNUNET_h2s (&vpn->peer)); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_REC_VPN-%llu: service %s -> %s!\n", + rh->id, + (char*)&vpn[1], + GNUNET_h2s (&serv_desc)); + rh->proc = &handle_record_vpn; + if (GNUNET_GNS_RECORD_A == rlh->record_type) + af = AF_INET; + else + af = AF_INET6; +#ifndef WINDOWS + if (NULL == vpn_handle) + { + vpn_handle = GNUNET_VPN_connect (cfg); + if (NULL == vpn_handle) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_INIT: Error connecting to VPN!\n"); + finish_lookup (rh, rh->proc_cls, 0, NULL); + return; + } + } + + rh->vpn_handle = GNUNET_VPN_redirect_to_peer (vpn_handle, + af, ntohs (vpn->proto), + (struct GNUNET_PeerIdentity *)&vpn->peer, + &serv_desc, + GNUNET_NO, //nac + GNUNET_TIME_UNIT_FOREVER_ABS, //FIXME + &process_record_result_vpn, + rh); +#else + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Error connecting to VPN (not available on W32 yet)\n"); + finish_lookup (rh, rh->proc_cls, 0, NULL); +#endif +} + + +/** + * The final phase of resolution. + * rh->name is a name that is canonical and we do not have a delegation. + * Query namestore for this record + * + * @param rh the pending lookup handle + */ +static void +resolve_record_ns(struct ResolverHandle *rh) +{ + struct RecordLookupHandle *rlh = rh->proc_cls; + + /* We cancel here as to not include the ns lookup in the timeout */ + if (GNUNET_SCHEDULER_NO_TASK != rh->timeout_task) + { + GNUNET_SCHEDULER_cancel(rh->timeout_task); + rh->timeout_task = GNUNET_SCHEDULER_NO_TASK; + } + /* Start shortening */ + if ((NULL != rh->priv_key) && + (GNUNET_YES == is_canonical (rh->name))) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_REC-%llu: Trying to shorten authority chain\n", + rh->id); + start_shorten (rh->authority_chain_head, + rh->priv_key); + } + + /** + * Try to resolve this record in our namestore. + * The name to resolve is now in rh->authority_name + * since we tried to resolve it to an authority + * and failed. + **/ + rh->namestore_task = GNUNET_NAMESTORE_lookup_record(namestore_handle, + &rh->authority, + rh->name, + rlh->record_type, + &process_record_result_ns, + rh); +} + + +/** + * Handle timeout for DHT requests + * + * @param cls the request handle as closure + * @param tc the task context + */ +static void +dht_authority_lookup_timeout (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct ResolverHandle *rh = cls; + struct RecordLookupHandle *rlh = rh->proc_cls; + char new_name[GNUNET_DNSPARSER_MAX_NAME_LENGTH]; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_DELEGATE_DHT-%llu: dht lookup for query %s (%llus) timed out.\n", + rh->id, rh->authority_name, + rh->timeout.rel_value); + + rh->status |= RSL_TIMED_OUT; + rh->timeout_task = GNUNET_SCHEDULER_NO_TASK; + if (NULL != rh->get_handle) + { + GNUNET_DHT_get_stop (rh->get_handle); + rh->get_handle = NULL; + } + if (0 != (tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN)) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_DELEGATE_DHT-%llu: Got shutdown\n", + rh->id); + rh->proc (rh->proc_cls, rh, 0, NULL); + return; + } + if (0 == strcmp (rh->name, "")) + { + /* + * promote authority back to name and try to resolve record + */ + strcpy (rh->name, rh->authority_name); + rh->proc (rh->proc_cls, rh, 0, NULL); return; } /** * Start resolution in bg */ - GNUNET_snprintf(new_name, MAX_DNS_NAME_LENGTH, - "%s.%s.%s", rh->name, rh->authority_name, GNUNET_GNS_TLD); - //strcpy(new_name, rh->name); - //strcpy(new_name+strlen(new_name), "."); - //memcpy(new_name+strlen(new_name), GNUNET_GNS_TLD, strlen(GNUNET_GNS_TLD)); - - strcpy(rh->name, new_name); + GNUNET_snprintf (new_name, GNUNET_DNSPARSER_MAX_NAME_LENGTH, + "%s.%s.%s", + rh->name, rh->authority_name, GNUNET_GNS_TLD); + strcpy (rh->name, new_name); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_DELEGATE_DHT-%llu: Starting background query for %s type %d\n", + rh->id, rh->name, + rlh->record_type); + gns_resolver_lookup_record (rh->authority, + rh->private_local_zone, + rlh->record_type, + new_name, + NULL, + GNUNET_TIME_UNIT_FOREVER_REL, + GNUNET_NO, + &background_lookup_result_processor, + NULL); + rh->proc (rh->proc_cls, rh, 0, NULL); +} - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_PHASE_DELEGATE_DHT-%llu: Starting background query for %s type %d\n", - rh->id, rh->name, rlh->record_type); - - gns_resolver_lookup_record(rh->authority, - rh->private_local_zone, - rlh->record_type, - new_name, - rh->priv_key, - GNUNET_TIME_UNIT_FOREVER_REL, - &background_lookup_result_processor, - NULL); - rh->proc(rh->proc_cls, rh, 0, NULL); -} +/** + * Start DHT lookup for a name -> PKEY (compare NS) record in + * rh->authority's zone + * + * @param rh the pending gns query + */ +static void +resolve_delegation_dht (struct ResolverHandle *rh); -/* Prototype */ -static void resolve_delegation_dht(struct ResolverHandle *rh); -/* Prototype */ -static void resolve_delegation_ns(struct ResolverHandle *rh); +/** + * Resolve the delegation chain for the request in our namestore + * + * @param rh the resolver handle + */ +static void +resolve_delegation_ns (struct ResolverHandle *rh); /** @@ -1107,9 +1981,122 @@ static void resolve_delegation_ns(struct ResolverHandle *rh); * @param rd record data (always NULL) */ static void -handle_delegation_ns(void* cls, struct ResolverHandle *rh, - unsigned int rd_count, - const struct GNUNET_NAMESTORE_RecordData *rd); +handle_delegation_ns (void* cls, struct ResolverHandle *rh, + unsigned int rd_count, + const struct GNUNET_NAMESTORE_RecordData *rd); + + +/** + * This is a callback function that checks for key revocation + * + * @param cls the pending query + * @param key the key of the zone we did the lookup + * @param expiration expiration date of the record data set in the namestore + * @param name the name for which we need an authority + * @param rd_count the number of records with 'name' + * @param rd the record data + * @param signature the signature of the authority for the record data + */ +static void +process_pkey_revocation_result_ns (void *cls, + const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *key, + struct GNUNET_TIME_Absolute expiration, + const char *name, + unsigned int rd_count, + const struct GNUNET_NAMESTORE_RecordData *rd, + const struct GNUNET_CRYPTO_RsaSignature *signature) +{ + struct ResolverHandle *rh = cls; + struct GNUNET_TIME_Relative remaining_time; + int i; + + rh->namestore_task = NULL; + remaining_time = GNUNET_TIME_absolute_get_remaining (expiration); + + for (i = 0; i < rd_count; i++) + { + if (GNUNET_GNS_RECORD_REV == rd[i].record_type) + { + GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_DELEGATE_REV-%llu: Zone has been revoked.\n", + rh->id); + rh->status |= RSL_PKEY_REVOKED; + rh->proc (rh->proc_cls, rh, 0, NULL); + return; + } + } + + if ((NULL == name) || + (0 == remaining_time.rel_value)) + { + GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_DELEGATE_REV-%llu: + Records don't exist or are expired.\n", + rh->id, name); + + if (GNUNET_TIME_UNIT_FOREVER_REL.rel_value != rh->timeout.rel_value) + { + GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_DELEGATE_REV-%llu: Starting background lookup for %s type %d\n", + rh->id, "+.gads", GNUNET_GNS_RECORD_REV); + + gns_resolver_lookup_record(rh->authority, + rh->private_local_zone, + GNUNET_GNS_RECORD_REV, + GNUNET_GNS_TLD, + NULL, + GNUNET_TIME_UNIT_FOREVER_REL, + GNUNET_NO, + &background_lookup_result_processor, + NULL); + } + } + GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_DELEGATE_REV-%llu: Revocation check passed\n", + rh->id); + /** + * We are done with PKEY resolution if name is empty + * else resolve again with new authority + */ + if (strcmp (rh->name, "") == 0) + rh->proc (rh->proc_cls, rh, rh->rd_count, &rh->rd); + else + resolve_delegation_ns (rh); +} + + +/** + * Callback when record data is put into namestore + * + * @param cls the closure + * @param success GNUNET_OK on success + * @param emsg the error message. NULL if SUCCESS==GNUNET_OK + */ +void +on_namestore_delegation_put_result(void *cls, + int32_t success, + const char *emsg) +{ + struct NamestoreBGTask *nbg = cls; + + GNUNET_CONTAINER_heap_remove_node (nbg->node); + GNUNET_free (nbg); + + if (GNUNET_NO == success) + { + GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, + "GNS_NS: records already in namestore\n"); + return; + } + else if (GNUNET_YES == success) + { + GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, + "GNS_NS: records successfully put in namestore\n"); + return; + } + + GNUNET_log(GNUNET_ERROR_TYPE_ERROR, + "GNS_NS: Error putting records into namestore: %s\n", emsg); +} /** @@ -1129,41 +2116,33 @@ handle_delegation_ns(void* cls, struct ResolverHandle *rh, * @param data the record data */ static void -process_delegation_result_dht(void* cls, - struct GNUNET_TIME_Absolute exp, - const GNUNET_HashCode * key, - const struct GNUNET_PeerIdentity *get_path, - unsigned int get_path_length, - const struct GNUNET_PeerIdentity *put_path, - unsigned int put_path_length, - enum GNUNET_BLOCK_Type type, - size_t size, const void *data) +process_delegation_result_dht (void* cls, + struct GNUNET_TIME_Absolute exp, + const struct GNUNET_HashCode * key, + const struct GNUNET_PeerIdentity *get_path, + unsigned int get_path_length, + const struct GNUNET_PeerIdentity *put_path, + unsigned int put_path_length, + enum GNUNET_BLOCK_Type type, + size_t size, const void *data) { - struct ResolverHandle *rh; - struct GNSNameRecordBlock *nrb; + struct ResolverHandle *rh = cls; + const struct GNSNameRecordBlock *nrb = data; + const char* rd_data; uint32_t num_records; - char* name = NULL; - char* rd_data = (char*) data; - int i; + const char* name; + uint32_t i; int rd_size; - struct GNUNET_CRYPTO_ShortHashCode zone, name_hash; - GNUNET_HashCode zone_hash_double, name_hash_double; - - rh = (struct ResolverHandle *)cls; - - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_PHASE_DELEGATE_DHT-%llu: Got DHT result\n", rh->id); + struct GNUNET_CRYPTO_ShortHashCode zone; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_DELEGATE_DHT-%llu: Got DHT result\n", + rh->id); if (data == NULL) return; - - nrb = (struct GNSNameRecordBlock*)data; - - /* stop dht lookup and timeout task */ + /* stop dht lookup and timeout task */ GNUNET_DHT_get_stop (rh->get_handle); - rh->get_handle = NULL; - if (rh->dht_heap_node != NULL) { GNUNET_CONTAINER_heap_remove_node(rh->dht_heap_node); @@ -1171,13 +2150,14 @@ process_delegation_result_dht(void* cls, } num_records = ntohl(nrb->rd_count); - name = (char*)&nrb[1]; + name = (const char*) &nrb[1]; { struct GNUNET_NAMESTORE_RecordData rd[num_records]; + struct NamestoreBGTask *ns_heap_root; + struct NamestoreBGTask *namestore_bg_task; - rd_data += strlen(name) + 1 + sizeof(struct GNSNameRecordBlock); - rd_size = size - strlen(name) - 1 - sizeof(struct GNSNameRecordBlock); - + rd_data = name + strlen(name) + 1; + rd_size = size - strlen(name) - 1 - sizeof (struct GNSNameRecordBlock); if (GNUNET_SYSERR == GNUNET_NAMESTORE_records_deserialize (rd_size, rd_data, num_records, @@ -1194,10 +2174,9 @@ process_delegation_result_dht(void* cls, rh->id, name, rh->authority_name); for (i=0; iid, name, rh->authority_name); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_DELEGATE_DHT-%llu: Got name: %s (wanted %s)\n", + rh->id, name, rh->authority_name); GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, "GNS_PHASE_DELEGATE_DHT-%llu: Got type: %d (wanted %d)\n", rh->id, rd[i].record_type, GNUNET_GNS_RECORD_PKEY); @@ -1207,9 +2186,25 @@ process_delegation_result_dht(void* cls, GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, "GNS_PHASE_DELEGATE_DHT-%llu: Got flag %d\n", rh->id, rd[i].flags); + + if ((GNUNET_GNS_RECORD_VPN == rd[i].record_type) || + (GNUNET_GNS_RECORD_NS == rd[i].record_type) || + (GNUNET_GNS_RECORD_CNAME == rd[i].record_type)) + { + /** + * This is a VPN,NS,CNAME entry. Let namestore handle this after caching + */ + if (0 == strcmp(rh->name, "")) + strcpy(rh->name, rh->authority_name); + else + GNUNET_snprintf(rh->name, GNUNET_DNSPARSER_MAX_NAME_LENGTH, "%s.%s", + rh->name, rh->authority_name); //FIXME ret + rh->answered = 1; + break; + } - if ((strcmp(name, rh->authority_name) == 0) && - (rd[i].record_type == GNUNET_GNS_RECORD_PKEY)) + if ((0 == strcmp(name, rh->authority_name)) && + (GNUNET_GNS_RECORD_PKEY == rd[i].record_type)) { GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, "GNS_PHASE_DELEGATE_DHT-%llu: Authority found in DHT\n", @@ -1225,38 +2220,60 @@ process_delegation_result_dht(void* cls, rh->authority_chain_tail, auth); + if (NULL != rh->rd.data) + GNUNET_free ((void*)rh->rd.data); + + memcpy (&rh->rd, &rd[i], sizeof (struct GNUNET_NAMESTORE_RecordData)); + rh->rd.data = GNUNET_malloc (rd[i].data_size); + memcpy ((void*)(rh->rd.data), rd[i].data, rd[i].data_size); + rh->rd_count = 1; + /** try to import pkey if private key available */ - if (rh->priv_key) - process_discovered_authority(name, auth->zone, - rh->authority_chain_tail->zone, - rh->priv_key); + //if (rh->priv_key && is_canonical (rh->name)) + // process_discovered_authority(name, auth->zone, + // rh->authority_chain_tail->zone, + // rh->priv_key); } } + GNUNET_GNS_get_zone_from_key (name, key, &zone); - GNUNET_CRYPTO_short_hash(name, strlen(name), &name_hash); - GNUNET_CRYPTO_short_hash_double(&name_hash, &name_hash_double); - GNUNET_CRYPTO_hash_xor(key, &name_hash_double, &zone_hash_double); - GNUNET_CRYPTO_short_hash_from_truncation (&zone_hash_double, &zone); - - /* Save to namestore */ - if (0 != GNUNET_CRYPTO_short_hash_cmp(&rh->authority_chain_tail->zone, + /* Save to namestore + if (0 != GNUNET_CRYPTO_short_hash_cmp(&rh->authority_chain_head->zone, &zone)) - { - GNUNET_NAMESTORE_record_put (namestore_handle, + {*/ + if (max_allowed_ns_tasks <= + GNUNET_CONTAINER_heap_get_size (ns_task_heap)) + { + ns_heap_root = GNUNET_CONTAINER_heap_remove_root (ns_task_heap); + GNUNET_NAMESTORE_cancel (ns_heap_root->qe); + + GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_DELEGATE_DHT-%llu: Replacing oldest background ns task\n", + rh->id); + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_DELEGATE_DHT-%llu: Caching record for %s\n", + rh->id, name); + namestore_bg_task = GNUNET_malloc (sizeof (struct NamestoreBGTask)); + + namestore_bg_task->node = GNUNET_CONTAINER_heap_insert (ns_task_heap, + namestore_bg_task, + GNUNET_TIME_absolute_get().abs_value); + namestore_bg_task->qe = GNUNET_NAMESTORE_record_put (namestore_handle, &nrb->public_key, name, exp, num_records, rd, &nrb->signature, - &on_namestore_record_put_result, //cont - NULL); //cls + &on_namestore_delegation_put_result, //cont + namestore_bg_task); //cls } - } - - if (rh->answered) + //} + + if (0 != rh->answered) { rh->answered = 0; /** @@ -1264,17 +2281,34 @@ process_delegation_result_dht(void* cls, * FIXME in this case. should we ask namestore again? */ GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_PHASE_DELEGATE_DHT-%llu: Answer from DHT for %s. Yet to resolve: %s\n", - rh->id, rh->authority_name, rh->name); - if (strcmp(rh->name, "") == 0) + "GNS_PHASE_DELEGATE_DHT-%llu: Answer from DHT for %s. Yet to resolve: %s\n", + rh->id, rh->authority_name, rh->name); + + if (0 == strcmp(rh->name, "")) { - rh->proc(rh->proc_cls, rh, 0, NULL); + /* Start shortening */ + if ((NULL != rh->priv_key) && + (GNUNET_YES == is_canonical (rh->name))) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_DELEGATE_DHT-%llu: Trying to shorten authority chain\n", + rh->id); + start_shorten (rh->authority_chain_head, + rh->priv_key); + } } else - { rh->proc = &handle_delegation_ns; - resolve_delegation_ns(rh); - } + + + /* Check for key revocation and delegate */ + rh->namestore_task = GNUNET_NAMESTORE_lookup_record (namestore_handle, + &rh->authority, + GNUNET_GNS_MASTERZONE_STR, + GNUNET_GNS_RECORD_REV, + &process_pkey_revocation_result_ns, + rh); + return; } @@ -1285,96 +2319,119 @@ process_delegation_result_dht(void* cls, GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, "GNS_PHASE_DELEGATE_DHT-%llu: Adding %s back to %s\n", rh->id, rh->authority_name, rh->name); - if (strcmp(rh->name, "") == 0) + if (0 == strcmp(rh->name, "")) strcpy(rh->name, rh->authority_name); else - GNUNET_snprintf(rh->name, MAX_DNS_NAME_LENGTH, "%s.%s", + GNUNET_snprintf(rh->name, GNUNET_DNSPARSER_MAX_NAME_LENGTH, "%s.%s", rh->name, rh->authority_name); //FIXME ret GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, "GNS_PHASE_DELEGATE_DHT-%llu: %s restored\n", rh->id, rh->name); GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_PHASE_DELEGATE_DHT-%llu: DHT authority lookup found no match!\n", + "GNS_PHASE_DELEGATE_DHT-%llu: DHT authority lookup found no match!\n", rh->id); rh->proc(rh->proc_cls, rh, 0, NULL); } +//FIXME maybe define somewhere else? #define MAX_SOA_LENGTH sizeof(uint32_t)+sizeof(uint32_t)+sizeof(uint32_t)+sizeof(uint32_t)\ - +(MAX_DNS_NAME_LENGTH*2) -#define MAX_MX_LENGTH sizeof(uint16_t)+MAX_DNS_NAME_LENGTH + +(GNUNET_DNSPARSER_MAX_NAME_LENGTH*2) +#define MAX_MX_LENGTH sizeof(uint16_t)+GNUNET_DNSPARSER_MAX_NAME_LENGTH +#define MAX_SRV_LENGTH (sizeof(uint16_t)*3)+GNUNET_DNSPARSER_MAX_NAME_LENGTH +/** + * Exands a name ending in .+ with the zone of origin. + * FIXME: funky api: 'dest' must be large enough to hold + * the result; this is a bit yucky... + * + * @param dest destination buffer + * @param src the .+ name + * @param repl the string to replace the + with + */ static void -expand_plus(char** dest, char* src, char* repl) +expand_plus (char* dest, + const char* src, + const char* repl) { char* pos; - unsigned int s_len = strlen(src)+1; + size_t s_len = strlen (src) + 1; - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_POSTPROCESS: Got %s to expand with %s\n", src, repl); - - if (s_len < 3) + //Eh? I guess this is at least strlen ('x.+') == 3 FIXME + if (3 > s_len) { - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_POSTPROCESS: %s to short\n", src); - /* no postprocessing */ - memcpy(*dest, src, s_len+1); + GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, + "GNS_POSTPROCESS: %s too short\n", src); + memcpy (dest, src, s_len); return; } - - if (0 == strcmp(src+s_len-3, ".+")) + if (0 == strcmp (src + s_len - 3, ".+")) { - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_POSTPROCESS: Expanding .+ in %s\n", src); - memset(*dest, 0, s_len+strlen(repl)+strlen(GNUNET_GNS_TLD)); - strcpy(*dest, src); - pos = *dest+s_len-2; - strcpy(pos, repl); - pos += strlen(repl); - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_POSTPROCESS: Expanded to %s\n", *dest); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_POSTPROCESS: Expanding .+ in %s\n", + src); + memset (dest, 0, s_len + strlen (repl) + strlen(GNUNET_GNS_TLD)); + strcpy (dest, src); + pos = dest + s_len - 2; + strcpy (pos, repl); + pos += strlen (repl); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_POSTPROCESS: Expanded to %s\n", + dest); } else { - memcpy(*dest, src, s_len+1); + GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, + "GNS_POSTPROCESS: No postprocessing for %s\n", src); + memcpy (dest, src, s_len); } } + /** * finish lookup */ static void -finish_lookup(struct ResolverHandle *rh, - struct RecordLookupHandle* rlh, - unsigned int rd_count, - const struct GNUNET_NAMESTORE_RecordData *rd) +finish_lookup (struct ResolverHandle *rh, + struct RecordLookupHandle* rlh, + unsigned int rd_count, + const struct GNUNET_NAMESTORE_RecordData *rd) { - int i; - char new_rr_data[MAX_DNS_NAME_LENGTH]; + unsigned int i; + char new_rr_data[GNUNET_DNSPARSER_MAX_NAME_LENGTH]; char new_mx_data[MAX_MX_LENGTH]; char new_soa_data[MAX_SOA_LENGTH]; + char new_srv_data[MAX_SRV_LENGTH]; + struct srv_data *old_srv; + struct srv_data *new_srv; + struct soa_data *old_soa; + struct soa_data *new_soa; struct GNUNET_NAMESTORE_RecordData p_rd[rd_count]; char* repl_string; char* pos; unsigned int offset; - if (rh->timeout_task != GNUNET_SCHEDULER_NO_TASK) + if (GNUNET_SCHEDULER_NO_TASK != rh->timeout_task) { GNUNET_SCHEDULER_cancel(rh->timeout_task); rh->timeout_task = GNUNET_SCHEDULER_NO_TASK; } - if (rd_count > 0) + GNUNET_CONTAINER_DLL_remove (rlh_head, rlh_tail, rh); + + if (0 < rd_count) memcpy(p_rd, rd, rd_count*sizeof(struct GNUNET_NAMESTORE_RecordData)); for (i = 0; i < rd_count; i++) { - if (rd[i].record_type != GNUNET_GNS_RECORD_TYPE_NS && - rd[i].record_type != GNUNET_GNS_RECORD_TYPE_CNAME && - rd[i].record_type != GNUNET_GNS_RECORD_MX && - rd[i].record_type != GNUNET_GNS_RECORD_TYPE_SOA) + if ((GNUNET_GNS_RECORD_NS != rd[i].record_type) && + (GNUNET_GNS_RECORD_PTR != rd[i].record_type) && + (GNUNET_GNS_RECORD_CNAME != rd[i].record_type) && + (GNUNET_GNS_RECORD_MX != rd[i].record_type) && + (GNUNET_GNS_RECORD_SOA != rd[i].record_type) && + (GNUNET_GNS_RECORD_SRV != rd[i].record_type)) { p_rd[i].data = rd[i].data; continue; @@ -1388,43 +2445,63 @@ finish_lookup(struct ResolverHandle *rh, GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, "GNS_POSTPROCESS: Postprocessing\n"); - - if (strcmp(rh->name, "+") == 0) + if (0 == strcmp(rh->name, GNUNET_GNS_MASTERZONE_STR)) repl_string = rlh->name; else repl_string = rlh->name+strlen(rh->name)+1; offset = 0; - if (rd[i].record_type == GNUNET_GNS_RECORD_MX) + if (GNUNET_GNS_RECORD_MX == rd[i].record_type) { - memcpy(new_mx_data, (char*)rd[i].data, sizeof(uint16_t)); - offset = sizeof(uint16_t); - pos = new_mx_data+offset; - expand_plus(&pos, (char*)rd[i].data+sizeof(uint16_t), - repl_string); - offset += strlen(new_mx_data+sizeof(uint16_t))+1; + memcpy (new_mx_data, (char*)rd[i].data, sizeof(uint16_t)); + offset = sizeof (uint16_t); + pos = new_mx_data + offset; + // FIXME: how do we know that 'pos' has enough space for the new name? + expand_plus (pos, (char*)rd[i].data+sizeof(uint16_t), + repl_string); + offset += strlen(new_mx_data+sizeof(uint16_t)) + 1; p_rd[i].data = new_mx_data; p_rd[i].data_size = offset; } - else if (rd[i].record_type == GNUNET_GNS_RECORD_TYPE_SOA) + else if (GNUNET_GNS_RECORD_SRV == rd[i].record_type) + { + /* + * Prio, weight and port + */ + new_srv = (struct srv_data*)new_srv_data; + old_srv = (struct srv_data*)rd[i].data; + new_srv->prio = old_srv->prio; + new_srv->weight = old_srv->weight; + new_srv->port = old_srv->port; + // FIXME: how do we know that '&new_srv[1]' has enough space for the new name? + expand_plus((char*)&new_srv[1], (char*)&old_srv[1], + repl_string); + p_rd[i].data = new_srv_data; + p_rd[i].data_size = sizeof (struct srv_data) + strlen ((char*)&new_srv[1]) + 1; + } + else if (GNUNET_GNS_RECORD_SOA == rd[i].record_type) { /* expand mname and rname */ - pos = new_soa_data; - expand_plus(&pos, (char*)rd[i].data, repl_string); - offset = strlen(new_soa_data)+1; - pos = new_soa_data+offset; - expand_plus(&pos, (char*)rd[i].data+offset, repl_string); - offset += strlen(new_soa_data+offset)+1; - /* cpy the 4 numbers serial refresh retry and expire */ - memcpy(new_soa_data+offset, (char*)rd[i].data+offset, sizeof(uint32_t)*5); - offset += sizeof(uint32_t)*5; - p_rd[i].data_size = offset; + old_soa = (struct soa_data*)rd[i].data; + new_soa = (struct soa_data*)new_soa_data; + memcpy (new_soa, old_soa, sizeof (struct soa_data)); + // FIXME: how do we know that 'new_soa[1]' has enough space for the new name? + expand_plus((char*)&new_soa[1], (char*)&old_soa[1], repl_string); + offset = strlen ((char*)&new_soa[1]) + 1; + // FIXME: how do we know that 'new_soa[1]' has enough space for the new name? + expand_plus((char*)&new_soa[1] + offset, + (char*)&old_soa[1] + strlen ((char*)&old_soa[1]) + 1, + repl_string); + p_rd[i].data_size = sizeof (struct soa_data) + + offset + + strlen ((char*)&new_soa[1] + offset); p_rd[i].data = new_soa_data; } else { pos = new_rr_data; - expand_plus(&pos, (char*)rd[i].data, repl_string); + // FIXME: how do we know that 'rd[i].data' has enough space for the new name? + expand_plus(pos, (char*)rd[i].data, repl_string); p_rd[i].data_size = strlen(new_rr_data)+1; p_rd[i].data = new_rr_data; } @@ -1433,9 +2510,10 @@ finish_lookup(struct ResolverHandle *rh, rlh->proc(rlh->proc_cls, rd_count, p_rd); GNUNET_free(rlh); - + free_resolver_handle (rh); } + /** * Process DHT lookup result for record. * @@ -1445,31 +2523,25 @@ finish_lookup(struct ResolverHandle *rh, * @param rd record data */ static void -handle_record_dht(void* cls, struct ResolverHandle *rh, - unsigned int rd_count, - const struct GNUNET_NAMESTORE_RecordData *rd) +handle_record_dht (void* cls, struct ResolverHandle *rh, + unsigned int rd_count, + const struct GNUNET_NAMESTORE_RecordData *rd) { - struct RecordLookupHandle* rlh; + struct RecordLookupHandle* rlh = cls; - rlh = (struct RecordLookupHandle*)cls; - if (rd_count == 0) + if (0 == rd_count) { - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_PHASE_REC-%d: No records for %s found in DHT. Aborting\n", + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_REC-%llu: No records for %s found in DHT. Aborting\n", rh->id, rh->name); /* give up, cannot resolve */ - finish_lookup(rh, rlh, 0, NULL); - free_resolver_handle(rh); + finish_lookup (rh, rlh, 0, NULL); return; } - /* results found yay */ - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_PHASE_REC-%d: Record resolved from DHT!", rh->id); - - finish_lookup(rh, rlh, rd_count, rd); - free_resolver_handle(rh); - + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_REC-%llu: Record resolved from DHT!", rh->id); + finish_lookup (rh, rlh, rd_count, rd); } @@ -1482,105 +2554,103 @@ handle_record_dht(void* cls, struct ResolverHandle *rh, * @param rd record data */ static void -handle_record_ns(void* cls, struct ResolverHandle *rh, - unsigned int rd_count, - const struct GNUNET_NAMESTORE_RecordData *rd) +handle_record_ns (void* cls, struct ResolverHandle *rh, + unsigned int rd_count, + const struct GNUNET_NAMESTORE_RecordData *rd) { - struct RecordLookupHandle* rlh; - rlh = (struct RecordLookupHandle*) cls; - if (rd_count == 0) + struct RecordLookupHandle* rlh = cls; + int check_dht = GNUNET_YES; + + if (0 != rd_count) { - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_PHASE_REC-%d: NS returned no records. (status: %d)!\n", - rh->id, - rh->status); - - /** - * There are 4 conditions that have to met for us to consult the DHT: - * 1. The entry in the DHT is RSL_RECORD_EXPIRED AND - * 2. No entry in the NS existed AND - * 3. The zone queried is not the local resolver's zone AND - * 4. The name that was looked up is '+' - * because if it was any other canonical name we either already queried - * the DHT for the authority in the authority lookup phase (and thus - * would already have an entry in the NS for the record) - */ - if (rh->status & (RSL_RECORD_EXPIRED | !RSL_RECORD_EXISTS) && - GNUNET_CRYPTO_short_hash_cmp(&rh->authority_chain_head->zone, - &rh->private_local_zone) && - (strcmp(rh->name, "+") == 0)) - { - rh->proc = &handle_record_dht; - resolve_record_dht(rh); - return; - } - /* give up, cannot resolve */ - finish_lookup(rh, rlh, 0, NULL); - free_resolver_handle(rh); + /* results found yay */ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_REC-%llu: Record resolved from namestore!\n", rh->id); + finish_lookup (rh, rlh, rd_count, rd); return; } + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_REC-%llu: NS returned no records. (status: %d)!\n", + rh->id, + rh->status); + /** + * There are 5 conditions that have to met for us to consult the DHT: + * 1. The entry in the DHT is RSL_RECORD_EXPIRED OR + * 2. No entry in the NS existed AND + * 3. The zone queried is not the local resolver's zone AND + * 4. The name that was looked up is '+' + * because if it was any other canonical name we either already queried + * the DHT for the authority in the authority lookup phase (and thus + * would already have an entry in the NS for the record) + * 5. We are not in cache only mode + */ + if ((0 != (rh->status & RSL_RECORD_EXPIRED)) && + (0 == (rh->status & RSL_RECORD_EXISTS)) ) + { + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_REC-%llu: Not expired and exists!\n", + rh->id); + check_dht = GNUNET_NO; + } + + if (0 == GNUNET_CRYPTO_short_hash_cmp(&rh->authority_chain_head->zone, + &rh->private_local_zone)) + { - /* results found yay */ - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_PHASE_REC-%d: Record resolved from namestore!", rh->id); - - finish_lookup(rh, rlh, rd_count, rd); - - free_resolver_handle(rh); - -} - - -/** - * Determine if this name is canonical. - * i.e. - * a.b.gnunet = not canonical - * a = canonical - * - * @param name the name to test - * @return 1 if canonical - */ -static int -is_canonical(char* name) -{ - uint32_t len = strlen(name); - int i; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_REC-%llu: Our zone!\n", + rh->id); + check_dht = GNUNET_NO; + } + + if ((0 != strcmp (rh->name, GNUNET_GNS_MASTERZONE_STR)) && (GNUNET_YES == is_srv (rh->name))) + check_dht = GNUNET_NO; - for (i=0; ionly_cached) + check_dht = GNUNET_NO; + + if (GNUNET_YES == check_dht) { - if (*(name+i) == '.') - return 0; + rh->proc = &handle_record_dht; + resolve_record_dht(rh); + return; } - return 1; + /* give up, cannot resolve */ + finish_lookup (rh, rlh, 0, NULL); } + /** * Move one level up in the domain hierarchy and return the * passed top level domain. * + * FIXME: funky API: not only 'dest' is updated, so is 'name'! + * * @param name the domain * @param dest the destination where the tld will be put */ -void -pop_tld(char* name, char* dest) +static void +pop_tld (char* name, char* dest) { uint32_t len; - if (is_canonical(name)) + if (GNUNET_YES == is_canonical (name)) { - strcpy(dest, name); - strcpy(name, ""); + strcpy (dest, name); + strcpy (name, ""); return; } - for (len = strlen(name); len > 0; len--) + for (len = strlen(name); 0 < len; len--) { if (*(name+len) == '.') break; } //Was canonical? - if (len == 0) + if (0 == len) return; name[len] = '\0'; @@ -1588,32 +2658,6 @@ pop_tld(char* name, char* dest) strcpy(dest, (name+len+1)); } -/** - * Checks if name is in tld - * - * @param name the name to check - * @param tld the TLD to check for - * @return GNUNET_YES or GNUNET_NO - */ -int -is_tld(const char* name, const char* tld) -{ - int offset = 0; - - if (strlen(name) <= strlen(tld)) - { - return GNUNET_NO; - } - - offset = strlen(name)-strlen(tld); - if (strcmp(name+offset, tld) != 0) - { - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "%s is not in .%s TLD\n", name, tld); - return GNUNET_NO; - } - return GNUNET_YES; -} /** * DHT resolution for delegation finished. Processing result. @@ -1628,19 +2672,16 @@ handle_delegation_dht(void* cls, struct ResolverHandle *rh, unsigned int rd_count, const struct GNUNET_NAMESTORE_RecordData *rd) { - struct RecordLookupHandle* rlh; - rlh = (struct RecordLookupHandle*) cls; + struct RecordLookupHandle* rlh = cls; - - if (strcmp(rh->name, "") == 0) + if (0 == strcmp(rh->name, "")) { - if ((rlh->record_type == GNUNET_GNS_RECORD_PKEY)) + if (GNUNET_GNS_RECORD_PKEY == rlh->record_type) { GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, "GNS_PHASE_DELEGATE_DHT-%llu: Resolved queried PKEY via DHT.\n", rh->id); finish_lookup(rh, rlh, rd_count, rd); - free_resolver_handle(rh); return; } /* We resolved full name for delegation. resolving record */ @@ -1656,7 +2697,7 @@ handle_delegation_dht(void* cls, struct ResolverHandle *rh, /** * we still have some left **/ - if (is_canonical(rh->name)) + if (GNUNET_YES == is_canonical (rh->name)) { GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, "GNS_PHASE_DELEGATE_DHT-%llu: Resolving canonical record %s in ns\n", @@ -1671,7 +2712,6 @@ handle_delegation_dht(void* cls, struct ResolverHandle *rh, "GNS_PHASE_DELEGATE_DHT-%llu: Cannot fully resolve delegation for %s via DHT!\n", rh->id, rh->name); finish_lookup(rh, rlh, 0, NULL); - free_resolver_handle(rh); } @@ -1682,30 +2722,19 @@ handle_delegation_dht(void* cls, struct ResolverHandle *rh, * @param rh the pending gns query */ static void -resolve_delegation_dht(struct ResolverHandle *rh) +resolve_delegation_dht (struct ResolverHandle *rh) { uint32_t xquery; - struct GNUNET_CRYPTO_ShortHashCode name_hash; - GNUNET_HashCode name_hash_double; - GNUNET_HashCode zone_hash_double; - GNUNET_HashCode lookup_key; + struct GNUNET_HashCode lookup_key; struct ResolverHandle *rh_heap_root; - pop_tld(rh->name, rh->authority_name); - GNUNET_CRYPTO_short_hash(rh->authority_name, - strlen(rh->authority_name), - &name_hash); - GNUNET_CRYPTO_short_hash_double(&name_hash, &name_hash_double); - GNUNET_CRYPTO_short_hash_double(&rh->authority, &zone_hash_double); - GNUNET_CRYPTO_hash_xor(&name_hash_double, &zone_hash_double, &lookup_key); - + pop_tld (rh->name, rh->authority_name); + GNUNET_GNS_get_key_for_record (rh->authority_name, + &rh->authority, + &lookup_key); rh->dht_heap_node = NULL; - if (rh->timeout.rel_value != GNUNET_TIME_UNIT_FOREVER_REL.rel_value) { - //rh->timeout_task = GNUNET_SCHEDULER_add_delayed (DHT_LOOKUP_TIMEOUT, - // &dht_authority_lookup_timeout, - // rh); rh->timeout_cont = &dht_authority_lookup_timeout; rh->timeout_cont_cls = rh; } @@ -1716,122 +2745,281 @@ resolve_delegation_dht(struct ResolverHandle *rh) { /* terminate oldest lookup */ rh_heap_root = GNUNET_CONTAINER_heap_remove_root (dht_lookup_heap); - GNUNET_DHT_get_stop(rh_heap_root->get_handle); + GNUNET_DHT_get_stop (rh_heap_root->get_handle); + rh_heap_root->get_handle = NULL; rh_heap_root->dht_heap_node = NULL; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_DELEGATE_DHT-%llu: Replacing oldest background query for %s\n", + rh->id, + rh_heap_root->authority_name); + rh_heap_root->proc (rh_heap_root->proc_cls, + rh_heap_root, + 0, + NULL); + } + rh->dht_heap_node = GNUNET_CONTAINER_heap_insert (dht_lookup_heap, + rh, + GNUNET_TIME_absolute_get().abs_value); + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Beginning DHT lookup for %s in zone %s for request %llu\n", + rh->authority_name, + GNUNET_short_h2s (&rh->authority), + rh->id); + xquery = htonl (GNUNET_GNS_RECORD_PKEY); + GNUNET_assert (rh->get_handle == NULL); + rh->get_handle = GNUNET_DHT_get_start (dht_handle, + GNUNET_BLOCK_TYPE_GNS_NAMERECORD, + &lookup_key, + DHT_GNS_REPLICATION_LEVEL, + GNUNET_DHT_RO_DEMULTIPLEX_EVERYWHERE, + &xquery, + sizeof(xquery), + &process_delegation_result_dht, + rh); +} + + +/** + * Checks if name is in tld + * + * @param name the name to check + * @param tld the TLD to check for + * @return GNUNET_YES or GNUNET_NO + */ +int +is_tld (const char* name, const char* tld) +{ + size_t offset = 0; + + if (strlen (name) <= strlen (tld)) + return GNUNET_NO; + + offset = strlen (name) - strlen (tld); + if (0 != strcmp (name + offset, tld)) + { + GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, + "%s is not in .%s TLD\n", name, tld); + return GNUNET_NO; + } + return GNUNET_YES; +} + + +/** + * Namestore resolution for delegation finished. Processing result. + * + * @param cls the closure + * @param rh resolver handle + * @param rd_count number of results (always 0) + * @param rd record data (always NULL) + */ +static void +handle_delegation_ns (void* cls, struct ResolverHandle *rh, + unsigned int rd_count, + const struct GNUNET_NAMESTORE_RecordData *rd) +{ + struct RecordLookupHandle* rlh = cls; + int check_dht; + size_t s_len; + + GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_DELEGATE_NS-%llu: Resolution status: %d.\n", + rh->id, rh->status); + + if (rh->status & RSL_PKEY_REVOKED) + { + finish_lookup (rh, rlh, 0, NULL); + return; + } + + if (0 == strcmp(rh->name, "")) + { + + /* We resolved full name for delegation. resolving record */ + GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_DELEGATE_NS-%llu: Resolved full name for delegation.\n", + rh->id); + if (rh->status & RSL_CNAME_FOUND) + { + if (GNUNET_GNS_RECORD_CNAME == rlh->record_type) + { + GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_DELEGATE_NS-%llu: Resolved queried CNAME in NS.\n", + rh->id); + strcpy (rh->name, rh->authority_name); + finish_lookup (rh, rlh, rd_count, rd); + return; + } + + /* A .+ CNAME */ + if (GNUNET_YES == is_tld ((char*)rd->data, GNUNET_GNS_TLD_PLUS)) + { + s_len = strlen (rd->data) - 2; + memcpy (rh->name, rd->data, s_len); + rh->name[s_len] = '\0'; + resolve_delegation_ns (rh); + return; + } + else if (GNUNET_YES == is_tld ((char*)rd->data, GNUNET_GNS_TLD_ZKEY)) + { + gns_resolver_lookup_record (rh->authority, + rh->private_local_zone, + rlh->record_type, + (char*)rd->data, + rh->priv_key, + rh->timeout, + rh->only_cached, + rlh->proc, + rlh->proc_cls); + GNUNET_free (rlh); + GNUNET_CONTAINER_DLL_remove (rlh_head, rlh_tail, rh); + free_resolver_handle (rh); + return; + } + else + { + //Try DNS resolver + strcpy (rh->dns_name, (char*)rd->data); + resolve_dns_name (rh); + return; + } + + } + else if (rh->status & RSL_DELEGATE_VPN) + { + if (GNUNET_GNS_RECORD_VPN == rlh->record_type) + { + GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_DELEGATE_NS-%llu: Resolved queried VPNRR in NS.\n", + rh->id); + finish_lookup(rh, rlh, rd_count, rd); + return; + } + GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_DELEGATE_NS-%llu: VPN delegation starting.\n", + rh->id); + GNUNET_assert (NULL != rd); + rh->proc = &handle_record_vpn; + resolve_record_vpn (rh, rd_count, rd); + return; + } + else if (rh->status & RSL_DELEGATE_NS) + { + if (GNUNET_GNS_RECORD_NS == rlh->record_type) + { + GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_DELEGATE_NS-%llu: Resolved queried NSRR in NS.\n", + rh->id); + finish_lookup(rh, rlh, rd_count, rd); + return; + } GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_PHASE_DELEGATE_DHT-%llu: Replacing oldest background query for %s\n", - rh->id, rh_heap_root->authority_name); - - rh_heap_root->proc(rh_heap_root->proc_cls, - rh_heap_root, - 0, - NULL); + "GNS_PHASE_DELEGATE_NS-%llu: NS delegation starting.\n", + rh->id); + GNUNET_assert (NULL != rd); + rh->proc = &handle_record_ns; + resolve_record_dns (rh, rd_count, rd); + return; } - rh->dht_heap_node = GNUNET_CONTAINER_heap_insert (dht_lookup_heap, - rh, - GNUNET_TIME_absolute_get().abs_value); + else if (rh->status & RSL_DELEGATE_PKEY) + { + if (rh->status & RSL_PKEY_REVOKED) + { + GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_DELEGATE_NS-%llu: Resolved PKEY is revoked.\n", + rh->id); + finish_lookup (rh, rlh, 0, NULL); + return; + } + else if (GNUNET_GNS_RECORD_PKEY == rlh->record_type) + { + GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_DELEGATE_NS-%llu: Resolved queried PKEY in NS.\n", + rh->id); + finish_lookup(rh, rlh, rd_count, rd); + return; + } + } + GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_DELEGATE_NS-%llu: Resolving record +\n", + rh->id); + strcpy(rh->name, "+\0"); + rh->proc = &handle_record_ns; + resolve_record_ns(rh); + return; } - xquery = htonl(GNUNET_GNS_RECORD_PKEY); - - GNUNET_assert(rh->get_handle == NULL); - rh->get_handle = GNUNET_DHT_get_start(dht_handle, - GNUNET_BLOCK_TYPE_GNS_NAMERECORD, - &lookup_key, - DHT_GNS_REPLICATION_LEVEL, - GNUNET_DHT_RO_NONE, - &xquery, - sizeof(xquery), - &process_delegation_result_dht, - rh); - -} - - -/** - * Namestore resolution for delegation finished. Processing result. - * - * @param cls the closure - * @param rh resolver handle - * @param rd_count number of results (always 0) - * @param rd record data (always NULL) - */ -static void -handle_delegation_ns(void* cls, struct ResolverHandle *rh, - unsigned int rd_count, - const struct GNUNET_NAMESTORE_RecordData *rd) -{ - struct RecordLookupHandle* rlh; - rlh = (struct RecordLookupHandle*) cls; - - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_PHASE_DELEGATE_NS-%llu: Resolution status: %d.\n", - rh->id, rh->status); - - if (strcmp(rh->name, "") == 0) + if (rh->status & RSL_DELEGATE_NS) { - if ((rlh->record_type == GNUNET_GNS_RECORD_PKEY)) + if (GNUNET_GNS_RECORD_NS == rlh->record_type) { - GNUNET_assert(rd_count == 1); GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_PHASE_DELEGATE_NS-%llu: Resolved queried PKEY in NS.\n", + "GNS_PHASE_DELEGATE_NS-%llu: Resolved queried NSRR in NS.\n", rh->id); finish_lookup(rh, rlh, rd_count, rd); - free_resolver_handle(rh); return; } - /* We resolved full name for delegation. resolving record */ + GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_PHASE_DELEGATE_NS-%llu: Resolved full name for delegation.\n", - rh->id); - strcpy(rh->name, "+\0"); + "GNS_PHASE_DELEGATE_NS-%llu: NS delegation starting.\n", + rh->id); + GNUNET_assert (NULL != rd); rh->proc = &handle_record_ns; - resolve_record_ns(rh); + resolve_record_dns (rh, rd_count, rd); return; } - + /** * we still have some left * check if authority in ns is fresh * and exists * or we are authority **/ - if (((rh->status & RSL_RECORD_EXISTS) && (!(rh->status & RSL_RECORD_EXPIRED))) - || !GNUNET_CRYPTO_short_hash_cmp(&rh->authority_chain_head->zone, - &rh->private_local_zone)) + + check_dht = GNUNET_YES; + if ((rh->status & RSL_RECORD_EXISTS) && + !(rh->status & RSL_RECORD_EXPIRED)) + check_dht = GNUNET_NO; + + if (0 == GNUNET_CRYPTO_short_hash_cmp(&rh->authority_chain_head->zone, + &rh->private_local_zone)) + check_dht = GNUNET_NO; + + if (GNUNET_YES == rh->only_cached) + check_dht = GNUNET_NO; + + if (GNUNET_YES == check_dht) { - if (is_canonical(rh->name)) - { - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_PHASE_DELEGATE_NS-%llu: Resolving canonical record %s\n", - rh->id, - rh->name); - rh->proc = &handle_record_ns; - resolve_record_ns(rh); - } - else - { - /* give up, cannot resolve */ - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_PHASE_DELEGATE_NS-%llu: Cannot fully resolve delegation for %s!\n", - rh->id, - rh->name); - finish_lookup(rh, rlh, rd_count, rd); - //rlh->proc(rlh->proc_cls, 0, NULL); - } + + GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_DELEGATE_NS-%llu: Trying to resolve delegation for %s via DHT\n", + rh->id, rh->name); + rh->proc = &handle_delegation_dht; + resolve_delegation_dht(rh); return; } + if (GNUNET_NO == is_canonical (rh->name)) + { + /* give up, cannot resolve */ + GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_DELEGATE_NS-%llu: Cannot fully resolve delegation for %s!\n", + rh->id, + rh->name); + finish_lookup(rh, rlh, rd_count, rd); + return; + } GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_PHASE_DELEGATE_NS-%llu: Trying to resolve delegation for %s via DHT\n", - rh->id, rh->name); - rh->proc = &handle_delegation_dht; - resolve_delegation_dht(rh); + "GNS_PHASE_DELEGATE_NS-%llu: Resolving canonical record %s\n", + rh->id, + rh->name); + rh->proc = &handle_record_ns; + resolve_record_ns(rh); } - /** * This is a callback function that should give us only PKEY * records. Used to query the namestore for the authority (PKEY) @@ -1847,45 +3035,47 @@ handle_delegation_ns(void* cls, struct ResolverHandle *rh, * @param signature the signature of the authority for the record data */ static void -process_delegation_result_ns(void* cls, - const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *key, - struct GNUNET_TIME_Absolute expiration, - const char *name, - unsigned int rd_count, - const struct GNUNET_NAMESTORE_RecordData *rd, - const struct GNUNET_CRYPTO_RsaSignature *signature) +process_delegation_result_ns (void* cls, + const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *key, + struct GNUNET_TIME_Absolute expiration, + const char *name, + unsigned int rd_count, + const struct GNUNET_NAMESTORE_RecordData *rd, + const struct GNUNET_CRYPTO_RsaSignature *signature) { - struct ResolverHandle *rh; + struct ResolverHandle *rh = cls; struct GNUNET_TIME_Relative remaining_time; struct GNUNET_CRYPTO_ShortHashCode zone; - char new_name[MAX_DNS_NAME_LENGTH]; + char new_name[GNUNET_DNSPARSER_MAX_NAME_LENGTH]; + unsigned int i; + struct GNUNET_TIME_Absolute et; - rh = (struct ResolverHandle *)cls; - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_PHASE_DELEGATE_NS-%llu: Got %d records from authority lookup\n", - rh->id, rd_count); + rh->namestore_task = NULL; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_DELEGATE_NS-%llu: Got %d records from authority lookup\n", + rh->id, rd_count); - GNUNET_CRYPTO_short_hash(key, - sizeof(struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded), - &zone); + GNUNET_CRYPTO_short_hash (key, + sizeof(struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded), + &zone); remaining_time = GNUNET_TIME_absolute_get_remaining (expiration); rh->status = 0; if (name != NULL) { - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_PHASE_DELEGATE_NS-%llu: Records with name %s exist.\n", - rh->id, name); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_DELEGATE_NS-%llu: Records with name %s exist.\n", + rh->id, name); rh->status |= RSL_RECORD_EXISTS; - } - if (remaining_time.rel_value == 0) - { - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_PHASE_DELEGATE_NS-%llu: Record set %s expired.\n", - rh->id, name); - rh->status |= RSL_RECORD_EXPIRED; + if (remaining_time.rel_value == 0) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_DELEGATE_NS-%llu: Record set %s expired.\n", + rh->id, name); + rh->status |= RSL_RECORD_EXPIRED; + } } /** @@ -1902,31 +3092,29 @@ process_delegation_result_ns(void* cls, * Promote this authority back to a name maybe it is * our record. */ - if (strcmp(rh->name, "") == 0) + if (strcmp (rh->name, "") == 0) { /* simply promote back */ - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_PHASE_DELEGATE_NS-%llu: Promoting %s back to name\n", - rh->id, rh->authority_name); - strcpy(rh->name, rh->authority_name); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_DELEGATE_NS-%llu: Promoting %s back to name\n", + rh->id, rh->authority_name); + strcpy (rh->name, rh->authority_name); } else { /* add back to existing name */ - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_PHASE_DELEGATE_NS-%llu: Adding %s back to %s\n", - rh->id, rh->authority_name, rh->name); - //memset(new_name, 0, strlen(rh->name) + strlen(rh->authority_name) + 2); - GNUNET_snprintf(new_name, MAX_DNS_NAME_LENGTH, "%s.%s", - rh->name, rh->authority_name); - //strcpy(new_name, rh->name); - //strcpy(new_name+strlen(new_name), "."); - //strcpy(new_name+strlen(new_name), rh->authority_name); - strcpy(rh->name, new_name); - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_PHASE_DELEGATE_NS-%llu: %s restored\n", rh->id, rh->name); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_DELEGATE_NS-%llu: Adding %s back to %s\n", + rh->id, rh->authority_name, rh->name); + GNUNET_snprintf (new_name, GNUNET_DNSPARSER_MAX_NAME_LENGTH, "%s.%s", + rh->name, rh->authority_name); + strcpy (rh->name, new_name); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_DELEGATE_NS-%llu: %s restored\n", + rh->id, rh->name); } - rh->proc(rh->proc_cls, rh, 0, NULL); + + rh->proc (rh->proc_cls, rh, 0, NULL); return; } @@ -1935,36 +3123,81 @@ process_delegation_result_ns(void* cls, * move on with query * Note only 1 pkey should have been returned.. anything else would be strange */ - int i; - for (i=0; iid); + + rh->status |= RSL_CNAME_FOUND; + rh->proc (rh->proc_cls, rh, rd_count, rd); + return; + } + + /** + * Redirect via VPN + */ + if (rd[i].record_type == GNUNET_GNS_RECORD_VPN) + { + GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_DELEGATE_NS-%llu: VPN found.\n", + rh->id); + rh->status |= RSL_DELEGATE_VPN; + rh->proc (rh->proc_cls, rh, rd_count, rd); + return; + } + + /** + * Redirect via NS + * FIXME make optional + */ + if (rd[i].record_type == GNUNET_GNS_RECORD_NS) + { + GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_DELEGATE_NS-%llu: NS found.\n", + rh->id); + rh->status |= RSL_DELEGATE_NS; + rh->proc (rh->proc_cls, rh, rd_count, rd); + return; + } if (rd[i].record_type != GNUNET_GNS_RECORD_PKEY) continue; - if (ignore_pending_records && + rh->status |= RSL_DELEGATE_PKEY; + + if ((ignore_pending_records != 0) && (rd[i].flags & GNUNET_NAMESTORE_RF_PENDING)) { - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_PHASE_DELEGATE_NS-%llu: PKEY for %s is pending user confirmation.\n", - name, - rh->id); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_DELEGATE_NS-%llu: PKEY for %s is pending user confirmation.\n", + rh->id, + name); continue; } - if ((GNUNET_TIME_absolute_get_remaining (rd[i].expiration)).rel_value + GNUNET_break (0 == (rd[i].flags & GNUNET_NAMESTORE_RF_RELATIVE_EXPIRATION)); + et.abs_value = rd[i].expiration_time; + if ((GNUNET_TIME_absolute_get_remaining (et)).rel_value == 0) { - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_PHASE_DELEGATE_NS-%llu: This pkey is expired.\n", - rh->id); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_DELEGATE_NS-%llu: This pkey is expired.\n", + rh->id); if (remaining_time.rel_value == 0) { - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_PHASE_DELEGATE_NS-%llu: This dht entry is expired.\n", - rh->id); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_DELEGATE_NS-%llu: This dht entry is expired.\n", + rh->id); rh->authority_chain_head->fresh = 0; - rh->proc(rh->proc_cls, rh, 0, NULL); + rh->proc (rh->proc_cls, rh, 0, NULL); return; } @@ -1974,35 +3207,33 @@ process_delegation_result_ns(void* cls, /** * Resolve rest of query with new authority */ - GNUNET_assert(rd[i].record_type == GNUNET_GNS_RECORD_PKEY); - memcpy(&rh->authority, rd[i].data, - sizeof(struct GNUNET_CRYPTO_ShortHashCode)); - struct AuthorityChain *auth = GNUNET_malloc(sizeof(struct AuthorityChain)); + GNUNET_assert (rd[i].record_type == GNUNET_GNS_RECORD_PKEY); + memcpy (&rh->authority, rd[i].data, + sizeof (struct GNUNET_CRYPTO_ShortHashCode)); + struct AuthorityChain *auth = GNUNET_malloc(sizeof (struct AuthorityChain)); auth->zone = rh->authority; - memset(auth->name, 0, strlen(rh->authority_name)+1); - strcpy(auth->name, rh->authority_name); + memset (auth->name, 0, strlen (rh->authority_name)+1); + strcpy (auth->name, rh->authority_name); GNUNET_CONTAINER_DLL_insert (rh->authority_chain_head, rh->authority_chain_tail, auth); + if (NULL != rh->rd.data) + GNUNET_free ((void*)(rh->rd.data)); - /** try to import pkey if private key available - * TODO: Only import last one? - */ - if (rh->priv_key && (name != NULL)) - process_discovered_authority((char*)name, auth->zone, - rh->authority_chain_tail->zone, - rh->priv_key); - /** - * We are done with PKEY resolution if name is empty - * else resolve again with new authority - */ - if (strcmp(rh->name, "") == 0) - rh->proc(rh->proc_cls, rh, rd_count, rd); - else - resolve_delegation_ns(rh); + memcpy (&rh->rd, &rd[i], sizeof (struct GNUNET_NAMESTORE_RecordData)); + rh->rd.data = GNUNET_malloc (rd[i].data_size); + memcpy ((void*)rh->rd.data, rd[i].data, rd[i].data_size); + rh->rd_count = 1; + /* Check for key revocation and delegate */ + rh->namestore_task = GNUNET_NAMESTORE_lookup_record (namestore_handle, + &rh->authority, + GNUNET_GNS_MASTERZONE_STR, + GNUNET_GNS_RECORD_REV, + &process_pkey_revocation_result_ns, + rh); return; } - + /** * no answers found */ @@ -2012,18 +3243,31 @@ process_delegation_result_ns(void* cls, * If we have found some records for the LAST label * we return the results. Else null. */ - if (strcmp(rh->name, "") == 0) + if (strcmp (rh->name, "") == 0) { + /* Start shortening */ + if ((rh->priv_key != NULL) && + (is_canonical (rh->name) == GNUNET_YES)) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_DELEGATE_NS-%llu: Trying to shorten authority chain\n", + rh->id); + start_shorten (rh->authority_chain_head, + rh->priv_key); + } /* simply promote back */ - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_PHASE_DELEGATE_NS-%llu: Promoting %s back to name\n", - rh->id, rh->authority_name); - strcpy(rh->name, rh->authority_name); - rh->proc(rh->proc_cls, rh, rd_count, rd); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_DELEGATE_NS-%llu: Promoting %s back to name\n", + rh->id, rh->authority_name); + strcpy (rh->name, rh->authority_name); + rh->proc (rh->proc_cls, rh, rd_count, rd); } else { - rh->proc(rh->proc_cls, rh, 0, NULL); + GNUNET_snprintf (new_name, GNUNET_DNSPARSER_MAX_NAME_LENGTH, + "%s.%s", rh->name, rh->authority_name); + strcpy (rh->name, new_name); + rh->proc (rh->proc_cls, rh, 0, NULL); } } @@ -2034,19 +3278,19 @@ process_delegation_result_ns(void* cls, * @param rh the resolver handle */ static void -resolve_delegation_ns(struct ResolverHandle *rh) +resolve_delegation_ns (struct ResolverHandle *rh) { - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_PHASE_DELEGATE_NS-%llu: Resolving delegation for %s\n", - rh->id, rh->name); - pop_tld(rh->name, rh->authority_name); - GNUNET_NAMESTORE_lookup_record(namestore_handle, - &rh->authority, - rh->authority_name, - GNUNET_GNS_RECORD_ANY, - &process_delegation_result_ns, - rh); - + pop_tld (rh->name, rh->authority_name); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "GNS_PHASE_DELEGATE_NS-%llu: Resolving delegation for %s by looking up %s\n", + rh->id, rh->name, + rh->authority_name); + rh->namestore_task = GNUNET_NAMESTORE_lookup_record (namestore_handle, + &rh->authority, + rh->authority_name, + GNUNET_GNS_RECORD_ANY, + &process_delegation_result_ns, + rh); } @@ -2060,31 +3304,34 @@ resolve_delegation_ns(struct ResolverHandle *rh) * @param name the name to look up * @param key a private key for use with PSEU import (can be NULL) * @param timeout timeout for resolution + * @param only_cached GNUNET_NO to only check locally not DHT for performance * @param proc the processor to call on result * @param cls the closure to pass to proc */ void -gns_resolver_lookup_record(struct GNUNET_CRYPTO_ShortHashCode zone, - struct GNUNET_CRYPTO_ShortHashCode pzone, - uint32_t record_type, - const char* name, - struct GNUNET_CRYPTO_RsaPrivateKey *key, - struct GNUNET_TIME_Relative timeout, - RecordLookupProcessor proc, - void* cls) +gns_resolver_lookup_record (struct GNUNET_CRYPTO_ShortHashCode zone, + struct GNUNET_CRYPTO_ShortHashCode pzone, + uint32_t record_type, + const char* name, + struct GNUNET_CRYPTO_RsaPrivateKey *key, + struct GNUNET_TIME_Relative timeout, + int only_cached, + RecordLookupProcessor proc, + void* cls) { struct ResolverHandle *rh; struct RecordLookupHandle* rlh; - char string_hash[MAX_DNS_LABEL_LENGTH]; - char nzkey[MAX_DNS_LABEL_LENGTH]; + char string_hash[GNUNET_DNSPARSER_MAX_LABEL_LENGTH]; + char nzkey[GNUNET_DNSPARSER_MAX_LABEL_LENGTH]; char* nzkey_ptr = nzkey; GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Starting resolution for %s (type=%d)!\n", - name, record_type); + "Starting resolution for %s (type=%d) with timeout %s!\n", + name, record_type, + GNUNET_STRINGS_relative_time_to_string (timeout, GNUNET_YES)); - - if (is_canonical((char*)name) && (strcmp(GNUNET_GNS_TLD, name) != 0)) + if ((is_canonical ((char*)name) == GNUNET_YES) && + (strcmp(GNUNET_GNS_TLD, name) != 0)) { GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "%s is canonical and not gnunet -> cannot resolve!\n", name); @@ -2092,16 +3339,21 @@ gns_resolver_lookup_record(struct GNUNET_CRYPTO_ShortHashCode zone, return; } - rlh = GNUNET_malloc(sizeof(struct RecordLookupHandle)); - rh = GNUNET_malloc(sizeof (struct ResolverHandle)); - + rlh = GNUNET_malloc (sizeof(struct RecordLookupHandle)); + rh = GNUNET_malloc (sizeof (struct ResolverHandle)); rh->authority = zone; - rh->id = rid++; + rh->id = rid_gen++; rh->proc_cls = rlh; rh->priv_key = key; rh->timeout = timeout; - rh->get_handle = NULL; rh->private_local_zone = pzone; + rh->only_cached = only_cached; + + GNUNET_CONTAINER_DLL_insert (rlh_head, rlh_tail, rh); + + if (NULL == key) + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "No shorten key for resolution\n"); if (timeout.rel_value != GNUNET_TIME_UNIT_FOREVER_REL.rel_value) { @@ -2109,8 +3361,9 @@ gns_resolver_lookup_record(struct GNUNET_CRYPTO_ShortHashCode zone, * Set timeout for authority lookup phase to 1/2 */ GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Timeout for lookup set to %ds\n", rh->timeout.rel_value); - rh->timeout_task = GNUNET_SCHEDULER_add_delayed( + "Timeout for lookup set to %s/2\n", + GNUNET_STRINGS_relative_time_to_string (rh->timeout, GNUNET_YES)); + rh->timeout_task = GNUNET_SCHEDULER_add_delayed ( GNUNET_TIME_relative_divide(timeout, 2), &handle_lookup_timeout, rh); @@ -2157,51 +3410,216 @@ gns_resolver_lookup_record(struct GNUNET_CRYPTO_ShortHashCode zone, &rh->authority)) { GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "Cannot convert ZKEY %s to hash!\n", string_hash); - GNUNET_free(rh); - GNUNET_free(rlh); - proc(cls, 0, NULL); + "Cannot convert ZKEY `%s' to hash!\n", string_hash); + + if (GNUNET_SCHEDULER_NO_TASK != rh->timeout_task) + GNUNET_SCHEDULER_cancel (rh->timeout_task); + GNUNET_CONTAINER_DLL_remove (rlh_head, rlh_tail, rh); + GNUNET_free (rh); + GNUNET_free (rlh); + proc (cls, 0, NULL); return; } } + else if (is_gads_tld (name) == GNUNET_YES) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "TLD is gads\n"); + /** + * Presumably GADS tld + */ + memcpy (rh->name, name, + strlen (name) - strlen(GNUNET_GNS_TLD) - 1); + rh->name[strlen (name) - strlen(GNUNET_GNS_TLD) - 1] = '\0'; + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Not a GADS TLD: `%s'\n"), + name); + if (GNUNET_SCHEDULER_NO_TASK != rh->timeout_task) + GNUNET_SCHEDULER_cancel (rh->timeout_task); + GNUNET_CONTAINER_DLL_remove (rlh_head, rlh_tail, rh); + GNUNET_free (rh); + GNUNET_free (rlh); + proc (cls, 0, NULL); + return; + } + } + + /** + * Initialize authority chain + */ + rh->authority_chain_head = GNUNET_malloc (sizeof(struct AuthorityChain)); + rh->authority_chain_tail = rh->authority_chain_head; + rh->authority_chain_head->zone = rh->authority; + strcpy (rh->authority_chain_head->name, ""); + + /** + * Copy original query into lookup handle + */ + rlh->record_type = record_type; + memset(rlh->name, 0, strlen(name) + 1); + strcpy(rlh->name, name); + rlh->proc = proc; + rlh->proc_cls = cls; + + rh->proc = &handle_delegation_ns; + resolve_delegation_ns(rh); +} + +/******** END Record Resolver ***********/ + +static void +finish_shorten (struct ResolverHandle *rh, + struct NameShortenHandle *nsh) +{ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Sending %s as shorten result\n", nsh->result); + nsh->proc (nsh->proc_cls, nsh->result); + GNUNET_CONTAINER_DLL_remove (nsh_head, nsh_tail, rh); + GNUNET_free (nsh); + free_resolver_handle (rh); +} + + +/** + * Callback calles by namestore for a zone to name + * result + * + * @param cls the closure + * @param zone_key the zone we queried + * @param expire the expiration time of the name + * @param name the name found or NULL + * @param rd_len number of records for the name + * @param rd the record data (PKEY) for the name + * @param signature the signature for the record data + */ +static void +process_zone_to_name_shorten_root (void *cls, + const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *zone_key, + struct GNUNET_TIME_Absolute expire, + const char *name, + unsigned int rd_len, + const struct GNUNET_NAMESTORE_RecordData *rd, + const struct GNUNET_CRYPTO_RsaSignature *signature); + + +/** + * Callback called by namestore for a zone to name + * result + * + * @param cls the closure + * @param zone_key the zone we queried + * @param expire the expiration time of the name + * @param name the name found or NULL + * @param rd_len number of records for the name + * @param rd the record data (PKEY) for the name + * @param signature the signature for the record data + */ +static void +process_zone_to_name_shorten_shorten (void *cls, + const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *zone_key, + struct GNUNET_TIME_Absolute expire, + const char *name, + unsigned int rd_len, + const struct GNUNET_NAMESTORE_RecordData *rd, + const struct GNUNET_CRYPTO_RsaSignature *signature) +{ + struct ResolverHandle *rh = cls; + struct NameShortenHandle* nsh = rh->proc_cls; + struct AuthorityChain *next_authority; + + char result[GNUNET_DNSPARSER_MAX_NAME_LENGTH]; + char tmp_name[GNUNET_DNSPARSER_MAX_NAME_LENGTH]; + size_t answer_len; + + rh->namestore_task = NULL; + /* we found a match in our own root zone */ + if (rd_len != 0) + { + answer_len = strlen(rh->name) + strlen(name) + strlen(GNUNET_GNS_TLD) + 3; + memset(result, 0, answer_len); + + if (strlen(rh->name) > 0) + { + sprintf (result, "%s.%s.%s.%s", + rh->name, name, + nsh->shorten_zone_name, + GNUNET_GNS_TLD); + } else { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "TLD is gnunet\n"); - /** - * Presumably GNUNET tld - */ - memset(rh->name, 0, - strlen(name)-strlen(GNUNET_GNS_TLD)); - memcpy(rh->name, name, - strlen(name)-strlen(GNUNET_GNS_TLD) - 1); + sprintf (result, "%s.%s.%s", name, + nsh->shorten_zone_name, + GNUNET_GNS_TLD); } + + GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, + "Found shorten result %s\n", result); + if (strlen (nsh->result) > strlen (result)) + strcpy (nsh->result, result); + } + else if (GNUNET_CRYPTO_short_hash_cmp(&rh->authority_chain_head->zone, + nsh->shorten_zone) == 0) + { + /** + * This is our zone append .gads unless name is empty + * (it shouldn't be, usually FIXME what happens if we + * shorten to our zone to a "" record??) + */ + + sprintf (result, "%s.%s.%s", + rh->name, + nsh->shorten_zone_name, + GNUNET_GNS_TLD); + GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, + "Our zone: Found %s as shorten result\n", result); + + if (strlen (nsh->result) > strlen (result)) + strcpy (nsh->result, result); + //nsh->proc(nsh->proc_cls, result); + //GNUNET_free(nsh); + //free_resolver_handle(rh); + //return; } - /** - * Initialize authority chain - */ - rh->authority_chain_head = GNUNET_malloc(sizeof(struct AuthorityChain)); - rh->authority_chain_head->prev = NULL; - rh->authority_chain_head->next = NULL; - rh->authority_chain_tail = rh->authority_chain_head; - rh->authority_chain_head->zone = rh->authority; /** - * Copy original query into lookup handle + * No PSEU found. + * continue with next authority if exists */ - rlh->record_type = record_type; - memset(rlh->name, 0, strlen(name) + 1); - strcpy(rlh->name, name); - rlh->proc = proc; - rlh->proc_cls = cls; + if (NULL == rh->authority_chain_head->next) + { + finish_shorten (rh, nsh); + return; + } + next_authority = rh->authority_chain_head; + + if (0 == strcmp (rh->name, "")) + strcpy (tmp_name, next_authority->name); + else + GNUNET_snprintf(tmp_name, GNUNET_DNSPARSER_MAX_NAME_LENGTH, + "%s.%s", rh->name, next_authority->name); + + strcpy(rh->name, tmp_name); + GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, + "No PSEU found for authority %s. Promoting back: %s\n", + next_authority->name, rh->name); + + GNUNET_CONTAINER_DLL_remove(rh->authority_chain_head, + rh->authority_chain_tail, + next_authority); - rh->proc = &handle_delegation_ns; - resolve_delegation_ns(rh); -} + GNUNET_free (next_authority); -/******** END Record Resolver ***********/ + rh->namestore_task = GNUNET_NAMESTORE_zone_to_name (namestore_handle, + &rh->authority_chain_tail->zone, + &rh->authority_chain_head->zone, + &process_zone_to_name_shorten_root, + rh); +} /** @@ -2217,7 +3635,7 @@ gns_resolver_lookup_record(struct GNUNET_CRYPTO_ShortHashCode zone, * @param signature the signature for the record data */ static void -process_zone_to_name_shorten(void *cls, +process_zone_to_name_shorten_private (void *cls, const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *zone_key, struct GNUNET_TIME_Absolute expire, const char *name, @@ -2225,65 +3643,79 @@ process_zone_to_name_shorten(void *cls, const struct GNUNET_NAMESTORE_RecordData *rd, const struct GNUNET_CRYPTO_RsaSignature *signature) { - struct ResolverHandle *rh = (struct ResolverHandle *)cls; - struct NameShortenHandle* nsh = (struct NameShortenHandle*)rh->proc_cls; + struct ResolverHandle *rh = cls; + struct NameShortenHandle* nsh = rh->proc_cls; struct AuthorityChain *next_authority; - char result[MAX_DNS_NAME_LENGTH]; - char tmp_name[MAX_DNS_NAME_LENGTH]; + char result[GNUNET_DNSPARSER_MAX_NAME_LENGTH]; + char tmp_name[GNUNET_DNSPARSER_MAX_NAME_LENGTH]; size_t answer_len; - /* we found a match in our own zone */ + rh->namestore_task = NULL; + /* we found a match in our own root zone */ if (rd_len != 0) { - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "result strlen %d\n", strlen(name)); answer_len = strlen(rh->name) + strlen(name) + strlen(GNUNET_GNS_TLD) + 3; memset(result, 0, answer_len); + if (strlen(rh->name) > 0) { - strcpy(result, rh->name); - strcpy(result+strlen(rh->name), "."); + sprintf (result, "%s.%s.%s", rh->name, name, GNUNET_GNS_TLD); + } + else + { + sprintf (result, "%s.%s", name, GNUNET_GNS_TLD); } - - strcpy(result+strlen(result), name); - strcpy(result+strlen(result), "."); - strcpy(result+strlen(result), GNUNET_GNS_TLD); GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "Sending shorten result %s\n", result); - - nsh->proc(nsh->proc_cls, result); - GNUNET_free(nsh); - free_resolver_handle(rh); + "Found shorten result %s\n", result); + if (strlen (nsh->result) > strlen (result)) + strcpy (nsh->result, result); } else if (GNUNET_CRYPTO_short_hash_cmp(&rh->authority_chain_head->zone, - &rh->private_local_zone) == 0) + nsh->private_zone) == 0) { - /* our zone, just append .gnunet */ - answer_len = strlen(rh->name) + strlen(GNUNET_GNS_TLD) + 2; - memset(result, 0, answer_len); - strcpy(result, rh->name); - strcpy(result+strlen(rh->name), "."); - strcpy(result+strlen(rh->name)+1, GNUNET_GNS_TLD); - - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "Our zone: Sending name as shorten result %s\n", rh->name); + /** + * This is our zone append .gads unless name is empty + * (it shouldn't be, usually FIXME what happens if we + * shorten to our zone to a "" record??) + */ - nsh->proc(nsh->proc_cls, result); - GNUNET_free(nsh); - free_resolver_handle(rh); + sprintf (result, "%s.%s.%s", + rh->name, nsh->private_zone_name, GNUNET_GNS_TLD); + GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, + "Our private zone: Found %s as shorten result %s\n", result); + if (strlen (nsh->result) > strlen (result)) + strcpy (nsh->result, result); + } + + if (0 != strcmp (nsh->shorten_zone_name, "")) + { + /* backtrack authorities for names in priv zone */ + rh->namestore_task = GNUNET_NAMESTORE_zone_to_name (namestore_handle, + nsh->shorten_zone, + &rh->authority_chain_head->zone, + &process_zone_to_name_shorten_shorten, + rh); } else { /** * No PSEU found. - * continue with next authority + * continue with next authority if exists */ + if (NULL == rh->authority_chain_head->next) + { + finish_shorten (rh, nsh); + return; + } next_authority = rh->authority_chain_head; - GNUNET_snprintf(tmp_name, MAX_DNS_NAME_LENGTH, - "%s.%s", rh->name, next_authority->name); + if (0 == strcmp (rh->name, "")) + strcpy (tmp_name, next_authority->name); + else + GNUNET_snprintf(tmp_name, GNUNET_DNSPARSER_MAX_NAME_LENGTH, + "%s.%s", rh->name, next_authority->name); strcpy(rh->name, tmp_name); GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, @@ -2294,35 +3726,139 @@ process_zone_to_name_shorten(void *cls, rh->authority_chain_tail, next_authority); - GNUNET_NAMESTORE_zone_to_name (namestore_handle, + GNUNET_free (next_authority); + + rh->namestore_task = GNUNET_NAMESTORE_zone_to_name (namestore_handle, &rh->authority_chain_tail->zone, &rh->authority_chain_head->zone, - &process_zone_to_name_shorten, + &process_zone_to_name_shorten_root, rh); } } + /** - * DHT resolution for delegation. Processing result. + * Callback calles by namestore for a zone to name + * result * * @param cls the closure - * @param rh resolver handle - * @param rd_count number of results - * @param rd record data + * @param zone_key the zone we queried + * @param expire the expiration time of the name + * @param name the name found or NULL + * @param rd_len number of records for the name + * @param rd the record data (PKEY) for the name + * @param signature the signature for the record data */ static void -handle_delegation_dht_bg_shorten(void* cls, struct ResolverHandle *rh, - unsigned int rd_count, - const struct GNUNET_NAMESTORE_RecordData *rd) +process_zone_to_name_shorten_root (void *cls, + const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *zone_key, + struct GNUNET_TIME_Absolute expire, + const char *name, + unsigned int rd_len, + const struct GNUNET_NAMESTORE_RecordData *rd, + const struct GNUNET_CRYPTO_RsaSignature *signature) { + struct ResolverHandle *rh = cls; + struct NameShortenHandle* nsh = rh->proc_cls; + struct AuthorityChain *next_authority; + char result[GNUNET_DNSPARSER_MAX_NAME_LENGTH]; + char tmp_name[GNUNET_DNSPARSER_MAX_NAME_LENGTH]; + size_t answer_len; - /* We resolved full name for delegation. resolving record */ - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_SHORTEN: Resolved up to %s for delegation via DHT in background.\n", - rh->name); - free_resolver_handle(rh); + rh->namestore_task = NULL; + /* we found a match in our own root zone */ + if (rd_len != 0) + { + answer_len = strlen(rh->name) + strlen(name) + strlen(GNUNET_GNS_TLD) + 3; + memset(result, 0, answer_len); + + if (strlen(rh->name) > 0) + { + sprintf (result, "%s.%s.%s", rh->name, name, GNUNET_GNS_TLD); + } + else + { + sprintf (result, "%s.%s", name, GNUNET_GNS_TLD); + } + + GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, + "Found shorten result %s\n", result); + if (strlen (nsh->result) > strlen (result)) + strcpy (nsh->result, result); + } + else if (GNUNET_CRYPTO_short_hash_cmp(&rh->authority_chain_head->zone, + nsh->root_zone) == 0) + { + /** + * This is our zone append .gads unless name is empty + * (it shouldn't be, usually FIXME what happens if we + * shorten to our zone to a "" record??) + */ + + sprintf (result, "%s.%s", rh->name, GNUNET_GNS_TLD); + GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, + "Our zone: Found %s as shorten result\n", result); + if (strlen (nsh->result) > strlen (result)) + strcpy (nsh->result, result); + } + + if (NULL != nsh->private_zone) + { + /* backtrack authorities for names in priv zone */ + rh->namestore_task = GNUNET_NAMESTORE_zone_to_name (namestore_handle, + nsh->private_zone, + &rh->authority_chain_head->zone, + &process_zone_to_name_shorten_private, + rh); + } + else if (NULL != nsh->shorten_zone) + { + /* backtrack authorities for names in shorten zone */ + rh->namestore_task = GNUNET_NAMESTORE_zone_to_name (namestore_handle, + nsh->shorten_zone, + &rh->authority_chain_head->zone, + &process_zone_to_name_shorten_shorten, + rh); + } + else + { + /** + * No PSEU found. + * continue with next authority if exists + */ + if (NULL == rh->authority_chain_head->next) + { + finish_shorten (rh, nsh); + return; + } + next_authority = rh->authority_chain_head; + + if (0 == strcmp (rh->name, "")) + strcpy (tmp_name, next_authority->name); + else + GNUNET_snprintf(tmp_name, GNUNET_DNSPARSER_MAX_NAME_LENGTH, + "%s.%s", rh->name, next_authority->name); + + strcpy(rh->name, tmp_name); + GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, + "No PSEU found for authority %s. Promoting back: %s\n", + next_authority->name, rh->name); + + GNUNET_CONTAINER_DLL_remove(rh->authority_chain_head, + rh->authority_chain_tail, + next_authority); + + GNUNET_free (next_authority); + + rh->namestore_task = GNUNET_NAMESTORE_zone_to_name (namestore_handle, + &rh->authority_chain_tail->zone, + &rh->authority_chain_head->zone, + &process_zone_to_name_shorten_root, + rh); + } } + /** * Process result from namestore delegation lookup * for shorten operation @@ -2332,19 +3868,17 @@ handle_delegation_dht_bg_shorten(void* cls, struct ResolverHandle *rh, * @param rd_count number of results (0) * @param rd data (NULL) */ -void -handle_delegation_ns_shorten(void* cls, +static void +handle_delegation_ns_shorten (void* cls, struct ResolverHandle *rh, uint32_t rd_count, const struct GNUNET_NAMESTORE_RecordData *rd) { struct NameShortenHandle *nsh; - char result[MAX_DNS_NAME_LENGTH]; - size_t answer_len; - struct ResolverHandle *rh_bg; + char result[GNUNET_DNSPARSER_MAX_NAME_LENGTH]; nsh = (struct NameShortenHandle *)cls; - + rh->namestore_task = NULL; /** * At this point rh->name contains the part of the name * that we do not have a PKEY in our namestore to resolve. @@ -2354,73 +3888,75 @@ handle_delegation_ns_shorten(void* cls, GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, "PKEY resolved as far as possible in ns up to %s!\n", rh->name); + memset(result, 0, sizeof (result)); - if (GNUNET_CRYPTO_short_hash_cmp(&rh->authority_chain_head->zone, - &rh->private_local_zone) == 0) + if (0 == GNUNET_CRYPTO_short_hash_cmp(&rh->authority_chain_head->zone, + nsh->root_zone)) { /** - * This is our zone append .gnunet unless name is empty + * This is our zone append .gads unless name is empty * (it shouldn't be, usually FIXME what happens if we * shorten to our zone to a "" record??) */ - answer_len = strlen(rh->name) + strlen(GNUNET_GNS_TLD) + 2; - memset(result, 0, answer_len); - strcpy(result, rh->name); - strcpy(result+strlen(rh->name), "."); - strcpy(result+strlen(rh->name)+1, GNUNET_GNS_TLD); - + sprintf (result, "%s.%s", rh->name, GNUNET_GNS_TLD); GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "Our zone: Sending name as shorten result %s\n", rh->name); + "Our zone: Found %s as shorten result\n", result); - nsh->proc(nsh->proc_cls, result); - GNUNET_free(nsh); - free_resolver_handle(rh); - return; + if (strlen (nsh->result) > strlen (result)) + strcpy (nsh->result, result); + } - - /** - * we have to this before zone to name for rh might - * be freed by then - */ - rh_bg = NULL; - if (!is_canonical(rh->name)) + else if (NULL != nsh->private_zone) { - rh_bg = GNUNET_malloc(sizeof(struct ResolverHandle)); - memcpy(rh_bg, rh, sizeof(struct ResolverHandle)); - rh_bg->id = rid++; + /** + * This is our zone append .gads unless name is empty + * (it shouldn't be, usually FIXME what happens if we + * shorten to our zone to a "" record??) + */ + if (GNUNET_CRYPTO_short_hash_cmp(&rh->authority_chain_head->zone, + nsh->private_zone) == 0) + { + + sprintf (result, "%s.%s.%s", + rh->name, nsh->private_zone_name, GNUNET_GNS_TLD); + GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, + "Our zone: Found %s as shorten result in private zone %s\n", + result); + + if (strlen (nsh->result) > strlen (result)) + strcpy (nsh->result, result); + } } - - /* backtrack authorities for names */ - GNUNET_NAMESTORE_zone_to_name (namestore_handle, - &rh->authority_chain_tail->zone, //ours - &rh->authority_chain_head->zone, - &process_zone_to_name_shorten, - rh); - - if (rh_bg == NULL) + else if (NULL != nsh->shorten_zone) { - return; + /** + * This is our zone append .gads unless name is empty + * (it shouldn't be, usually FIXME what happens if we + * shorten to our zone to a "" record??) + */ + if (GNUNET_CRYPTO_short_hash_cmp(&rh->authority_chain_head->zone, + nsh->shorten_zone) == 0) + { + sprintf (result, "%s.%s.%s", + rh->name, nsh->private_zone_name, GNUNET_GNS_TLD); + GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, + "Our zone: Found %s as shorten result in shorten zone\n", + result); + + if (strlen (nsh->result) > strlen (result)) + strcpy (nsh->result, result); + } } - - /** - * If authority resolution is incomplete we can do a background lookup - * of the full name so that next time we can (likely) fully or at least - * further shorten the name - */ - rh_bg->authority_chain_head = GNUNET_malloc(sizeof(struct AuthorityChain)); - rh_bg->authority_chain_tail = rh_bg->authority_chain_head; - rh_bg->authority_chain_head->zone = rh_bg->authority; - rh_bg->proc = &handle_delegation_dht_bg_shorten; - rh_bg->proc_cls = NULL; - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "GNS_SHORTEN: Starting background lookup for %s\n", - rh_bg->name); - - resolve_delegation_dht(rh_bg); - + /* backtrack authorities for names */ + rh->namestore_task = GNUNET_NAMESTORE_zone_to_name (namestore_handle, + nsh->root_zone, + &rh->authority_chain_head->zone, + &process_zone_to_name_shorten_root, + rh); + } @@ -2447,8 +3983,9 @@ process_zone_to_name_zkey(void *cls, { struct ResolverHandle *rh = cls; struct NameShortenHandle *nsh = rh->proc_cls; - struct GNUNET_CRYPTO_ShortHashAsciiEncoded enc; - char new_name[MAX_DNS_NAME_LENGTH]; + char new_name[GNUNET_DNSPARSER_MAX_NAME_LENGTH]; + + rh->namestore_task = NULL; /* zkey not in our zone */ if (name == NULL) @@ -2460,24 +3997,23 @@ process_zone_to_name_zkey(void *cls, * because PKEY import will happen if the user follows the zkey * link. */ - GNUNET_CRYPTO_short_hash_to_enc ((struct GNUNET_CRYPTO_ShortHashCode*)rd, - &enc); GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "No name found for zkey %s returning verbatim!\n", enc); - if (strcmp(rh->name, "") != 0) - GNUNET_snprintf(new_name, MAX_DNS_NAME_LENGTH, "%s.%s.%s", + "No name found for zkey %s returning verbatim!\n", nsh->result); + /*if (strcmp(rh->name, "") != 0) + GNUNET_snprintf(new_name, GNUNET_DNSPARSER_MAX_NAME_LENGTH, "%s.%s.%s", rh->name, enc, GNUNET_GNS_TLD_ZKEY); else - GNUNET_snprintf(new_name, MAX_DNS_NAME_LENGTH, "%s.%s", + GNUNET_snprintf(new_name, GNUNET_DNSPARSER_MAX_NAME_LENGTH, "%s.%s", enc, GNUNET_GNS_TLD_ZKEY); - nsh->proc(nsh->proc_cls, new_name); - GNUNET_free(nsh); - free_resolver_handle(rh); + + strcpy (nsh->result, new_name);*/ + + finish_shorten (rh, nsh); return; } if (strcmp(rh->name, "") != 0) - GNUNET_snprintf(new_name, MAX_DNS_NAME_LENGTH, "%s.%s", + GNUNET_snprintf(new_name, GNUNET_DNSPARSER_MAX_NAME_LENGTH, "%s.%s", rh->name, name); else strcpy(new_name, name); @@ -2493,64 +4029,71 @@ process_zone_to_name_zkey(void *cls, /* Start delegation resolution in our namestore */ - resolve_delegation_ns(rh); + resolve_delegation_ns (rh); } /** * Shorten api from resolver * - * @param zone the zone to use - * @param pzone the private local zone + * @param zone the root zone to use + * @param pzone the private zone to use + * @param szone the shorten zone to use * @param name the name to shorten - * @param key optional private key for background lookups and PSEU import + * @param private_zone_name name of the private zone + * @param shorten_zone_name name of the shorten zone * @param proc the processor to call with result * @param proc_cls closure to pass to proc */ void -gns_resolver_shorten_name(struct GNUNET_CRYPTO_ShortHashCode zone, - struct GNUNET_CRYPTO_ShortHashCode pzone, - const char* name, - struct GNUNET_CRYPTO_RsaPrivateKey *key, - ShortenResultProcessor proc, - void* proc_cls) +gns_resolver_shorten_name (struct GNUNET_CRYPTO_ShortHashCode *zone, + struct GNUNET_CRYPTO_ShortHashCode *pzone, + struct GNUNET_CRYPTO_ShortHashCode *szone, + const char* name, + const char* private_zone_name, + const char* shorten_zone_name, + ShortenResultProcessor proc, + void* proc_cls) { struct ResolverHandle *rh; struct NameShortenHandle *nsh; - char string_hash[MAX_DNS_LABEL_LENGTH]; + char string_hash[GNUNET_DNSPARSER_MAX_LABEL_LENGTH]; struct GNUNET_CRYPTO_ShortHashCode zkey; - char nzkey[MAX_DNS_LABEL_LENGTH]; + char nzkey[GNUNET_DNSPARSER_MAX_LABEL_LENGTH]; char* nzkey_ptr = nzkey; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Starting shorten for %s!\n", name); - if (is_canonical((char*)name)) + if (is_canonical ((char*)name) == GNUNET_YES) { GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "%s is canonical. Returning verbatim\n", name); - proc(proc_cls, name); + proc (proc_cls, name); return; } - nsh = GNUNET_malloc(sizeof (struct NameShortenHandle)); - + nsh = GNUNET_malloc (sizeof (struct NameShortenHandle)); nsh->proc = proc; nsh->proc_cls = proc_cls; + nsh->root_zone = zone; + nsh->private_zone = pzone; + nsh->shorten_zone = szone; + strcpy (nsh->private_zone_name, private_zone_name); + strcpy (nsh->shorten_zone_name, shorten_zone_name); + strcpy (nsh->result, name); - rh = GNUNET_malloc(sizeof (struct ResolverHandle)); - rh->authority = zone; - rh->id = rid++; - rh->priv_key = key; + rh = GNUNET_malloc (sizeof (struct ResolverHandle)); + rh->authority = *zone; + rh->id = rid_gen++; rh->proc = &handle_delegation_ns_shorten; rh->proc_cls = nsh; - rh->id = rid++; - rh->private_local_zone = pzone; - + rh->private_local_zone = *zone; + + GNUNET_CONTAINER_DLL_insert (nsh_head, nsh_tail, rh); GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Checking for TLD...\n"); - if (is_zkey_tld(name) == GNUNET_YES) + "Checking for TLD...\n"); + if (is_zkey_tld (name) == GNUNET_YES) { GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "TLD is zkey\n"); @@ -2559,60 +4102,87 @@ gns_resolver_shorten_name(struct GNUNET_CRYPTO_ShortHashCode zone, * build hash and use as initial authority * FIXME sscanf */ - memset(rh->name, 0, - strlen(name)-strlen(GNUNET_GNS_TLD_ZKEY)); - memcpy(rh->name, name, - strlen(name)-strlen(GNUNET_GNS_TLD_ZKEY) - 1); - pop_tld(rh->name, string_hash); + memset (rh->name, 0, + strlen (name)-strlen (GNUNET_GNS_TLD_ZKEY)); + memcpy (rh->name, name, + strlen(name)-strlen (GNUNET_GNS_TLD_ZKEY) - 1); + pop_tld (rh->name, string_hash); GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "ZKEY is %s!\n", string_hash); - GNUNET_STRINGS_utf8_toupper(string_hash, &nzkey_ptr); + GNUNET_STRINGS_utf8_toupper (string_hash, &nzkey_ptr); - if (GNUNET_OK != GNUNET_CRYPTO_short_hash_from_string(nzkey, - &zkey)) + if (GNUNET_OK != GNUNET_CRYPTO_short_hash_from_string (nzkey, + &zkey)) { GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Cannot convert ZKEY %s to hash!\n", nzkey); - GNUNET_free(rh); - GNUNET_free(nsh); - proc(proc_cls, name); + GNUNET_CONTAINER_DLL_remove (nsh_head, nsh_tail, rh); + GNUNET_free (rh); + GNUNET_free (nsh); + proc (proc_cls, name); return; } - - GNUNET_NAMESTORE_zone_to_name (namestore_handle, - &zone, //ours + rh->namestore_task = GNUNET_NAMESTORE_zone_to_name (namestore_handle, + zone, //ours &zkey, &process_zone_to_name_zkey, rh); return; } - else + else if (is_gads_tld (name) == GNUNET_YES) { GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "TLD is gnunet\n"); /** * Presumably GNUNET tld */ - memset(rh->name, 0, - strlen(name)-strlen(GNUNET_GNS_TLD)); - memcpy(rh->name, name, - strlen(name)-strlen(GNUNET_GNS_TLD) - 1); + memset (rh->name, 0, + strlen (name)-strlen (GNUNET_GNS_TLD)); + memcpy (rh->name, name, + strlen (name)-strlen (GNUNET_GNS_TLD) - 1); + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Unknown TLD in %s\n", name); + GNUNET_CONTAINER_DLL_remove (nsh_head, nsh_tail, rh); + GNUNET_free (rh); + GNUNET_free (nsh); + proc (proc_cls, name); + return; } - rh->authority_chain_head = GNUNET_malloc(sizeof(struct AuthorityChain)); + rh->authority_chain_head = GNUNET_malloc (sizeof (struct AuthorityChain)); rh->authority_chain_tail = rh->authority_chain_head; - rh->authority_chain_head->zone = zone; - + rh->authority_chain_head->zone = *zone; /* Start delegation resolution in our namestore */ - resolve_delegation_ns(rh); + resolve_delegation_ns (rh); } /*********** END NAME SHORTEN ********************/ +/** + * Conclude get authority lookup + * + * @param rh resolver handle + * @param nah get authority lookup handle + */ +static void +finish_get_auth (struct ResolverHandle *rh, + struct GetNameAuthorityHandle *nah) +{ + GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, + "Got authority result %s\n", nah->result); + + nah->proc (nah->proc_cls, nah->result); + GNUNET_CONTAINER_DLL_remove (nah_head, nah_tail, rh); + GNUNET_free (nah); + free_resolver_handle (rh); +} + /** * Process result from namestore delegation lookup @@ -2623,18 +4193,15 @@ gns_resolver_shorten_name(struct GNUNET_CRYPTO_ShortHashCode zone, * @param rd_count number of results (0) * @param rd data (NULL) */ -void +static void handle_delegation_result_ns_get_auth(void* cls, struct ResolverHandle *rh, uint32_t rd_count, const struct GNUNET_NAMESTORE_RecordData *rd) { - struct GetNameAuthorityHandle* nah; - char result[MAX_DNS_NAME_LENGTH]; + struct GetNameAuthorityHandle* nah = rh->proc_cls; size_t answer_len; - nah = (struct GetNameAuthorityHandle*) rh->proc_cls; - /** * At this point rh->name contains the part of the name * that we do not have a PKEY in our namestore to resolve. @@ -2647,7 +4214,7 @@ handle_delegation_result_ns_get_auth(void* cls, GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, "Building response!\n"); - if (is_canonical(rh->name)) + if (is_canonical (rh->name) == GNUNET_YES) { /** * We successfully resolved the authority in the ns @@ -2664,26 +4231,21 @@ handle_delegation_result_ns_get_auth(void* cls, answer_len = strlen(nah->name) - strlen(rh->name) + strlen(GNUNET_GNS_TLD) + 1; - memset(result, 0, answer_len); - strcpy(result, nah->name + strlen(rh->name) + 1); + memset(nah->result, 0, answer_len); + if (0 != strcmp (rh->name, "")) + strcpy(nah->result, nah->name + strlen(rh->name) + 1); + else + strcpy(nah->result, nah->name); - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, - "Got authority result %s\n", result); - - nah->proc(nah->proc_cls, result); - GNUNET_free(nah); - free_resolver_handle(rh); + finish_get_auth (rh, nah); } else { GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, "Unable to resolve authority for remaining %s!\n", rh->name); - nah->proc(nah->proc_cls, ""); - GNUNET_free(nah); - free_resolver_handle(rh); + strcpy(nah->result, ""); + finish_get_auth (rh, nah); } - - } @@ -2713,8 +4275,10 @@ gns_resolver_get_authority(struct GNUNET_CRYPTO_ShortHashCode zone, nah = GNUNET_malloc(sizeof (struct GetNameAuthorityHandle)); rh = GNUNET_malloc(sizeof (struct ResolverHandle)); rh->authority = zone; - rh->id = rid++; + rh->id = rid_gen++; rh->private_local_zone = pzone; + + GNUNET_CONTAINER_DLL_insert (nah_head, nah_tail, rh); if (strcmp(GNUNET_GNS_TLD, name) == 0) { @@ -2740,6 +4304,7 @@ gns_resolver_get_authority(struct GNUNET_CRYPTO_ShortHashCode zone, nah->proc = proc; nah->proc_cls = proc_cls; + strcpy (nah->result, ""); /* Start delegation resolution in our namestore */ resolve_delegation_ns(rh); diff --git a/src/gns/gnunet-service-gns_resolver.h b/src/gns/gnunet-service-gns_resolver.h index 8222397..650c5c5 100644 --- a/src/gns/gnunet-service-gns_resolver.h +++ b/src/gns/gnunet-service-gns_resolver.h @@ -1,3 +1,27 @@ +/* + This file is part of GNUnet. + (C) 2009, 2010, 2011, 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ +/** + * @file gns/gnunet-service-gns_resolver.h + * @brief GNUnet GNS service + * @author Martin Schanzenbach + */ #ifndef GNS_RESOLVER_H #define GNS_RESOLVER_H @@ -5,13 +29,18 @@ #include "gnunet_dht_service.h" #define DHT_OPERATION_TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 60) + #define GNUNET_GNS_DEFAULT_LOOKUP_TIMEOUT \ GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 10) + #define DHT_LOOKUP_TIMEOUT DHT_OPERATION_TIMEOUT + #define DHT_GNS_REPLICATION_LEVEL 5 #define GNUNET_GNS_MAX_PARALLEL_LOOKUPS 500 +#define GNUNET_GNS_MAX_NS_TASKS 500 + /* * DLL to hold the authority chain * we had to pass in the resolution process @@ -22,23 +51,28 @@ struct AuthorityChain struct AuthorityChain *next; - /* the zone hash of the authority */ + /** + * the zone hash of the authority + */ struct GNUNET_CRYPTO_ShortHashCode zone; - /* (local) name of the authority */ - char name[MAX_DNS_LABEL_LENGTH]; + /** + * (local) name of the authority + */ + char name[GNUNET_DNSPARSER_MAX_LABEL_LENGTH]; - /* was the ns entry fresh */ + /** + * was the ns entry fresh + */ int fresh; }; -/* handle to a resolution process */ -struct ResolverHandle; /** - * continuation called when cleanup of resolver finishes + * handle to a resolution process */ -typedef void (*ResolverCleanupContinuation) (void); +struct ResolverHandle; + /** * processor for a record lookup result @@ -48,8 +82,8 @@ typedef void (*ResolverCleanupContinuation) (void); * @param rd result data */ typedef void (*RecordLookupProcessor) (void *cls, - uint32_t rd_count, - const struct GNUNET_NAMESTORE_RecordData *rd); + uint32_t rd_count, + const struct GNUNET_NAMESTORE_RecordData *rd); /** @@ -58,16 +92,18 @@ typedef void (*RecordLookupProcessor) (void *cls, * @param cls the closure * @param name shortened name */ -typedef void (*ShortenResultProcessor) (void *cls, const char* name); +typedef void (*ShortenResultProcessor) (void *cls, + const char* name); /** * processor for an authority result * * @param cls the closure - * @param name name + * @param name name of the authority */ -typedef void (*GetAuthorityResultProcessor) (void *cls, const char* name); +typedef void (*GetAuthorityResultProcessor) (void *cls, + const char* name); /** * processor for a resolution result @@ -75,25 +111,58 @@ typedef void (*GetAuthorityResultProcessor) (void *cls, const char* name); * @param cls the closure * @param rh the resolution handle * @param rd_count number of results - * @param rd result data + * @param rd result data (array of 'rd_count' records) */ typedef void (*ResolutionResultProcessor) (void *cls, - struct ResolverHandle *rh, - uint32_t rd_count, - const struct GNUNET_NAMESTORE_RecordData *rd); + struct ResolverHandle *rh, + uint32_t rd_count, + const struct GNUNET_NAMESTORE_RecordData *rd); /** * Resolution status indicator - * RSL_RECORD_EXISTS: the name to lookup exists - * RSL_RECORD_EXPIRED: the name in the record expired - * RSL_TIMED_OUT: resolution timed out */ enum ResolutionStatus { + /** + * the name to lookup exists + */ RSL_RECORD_EXISTS = 1, + + /** + * the name in the record expired + */ RSL_RECORD_EXPIRED = 2, - RSL_TIMED_OUT = 4 + + /** + * resolution timed out + */ + RSL_TIMED_OUT = 4, + + /** + * Found VPN delegation + */ + RSL_DELEGATE_VPN = 8, + + /** + * Found NS delegation + */ + RSL_DELEGATE_NS = 16, + + /** + * Found PKEY delegation + */ + RSL_DELEGATE_PKEY = 32, + + /** + * Found CNAME record + */ + RSL_CNAME_FOUND = 64, + + /** + * Found PKEY has been revoked + */ + RSL_PKEY_REVOKED = 128 }; /** @@ -108,49 +177,150 @@ enum ResolutionStatus */ struct ResolverHandle { - /* The name to resolve */ - char name[MAX_DNS_NAME_LENGTH]; - /* has this query been answered? how many matches */ + /** + * DLL + */ + struct ResolverHandle *next; + + /** + * DLL + */ + struct ResolverHandle *prev; + + /** + * Last record data found + */ + struct GNUNET_NAMESTORE_RecordData rd; + + /** + * Number of last record data found + */ + unsigned int rd_count; + + /** + * The name to resolve + */ + char name[GNUNET_DNSPARSER_MAX_NAME_LENGTH]; + + /** + * has this query been answered? how many matches + */ int answered; - /* the authoritative zone to query */ + /** + * Use only cache + */ + int only_cached; + + /** + * the authoritative zone to query + */ struct GNUNET_CRYPTO_ShortHashCode authority; - /* the name of the authoritative zone to query */ - char authority_name[MAX_DNS_LABEL_LENGTH]; + /** + * the name of the authoritative zone to query + */ + char authority_name[GNUNET_DNSPARSER_MAX_LABEL_LENGTH]; - /* a handle for dht lookups. should be NULL if no lookups are in progress */ + /** + * a handle for dht lookups. should be NULL if no lookups are in progress + */ struct GNUNET_DHT_GetHandle *get_handle; - /* timeout set for this lookup task */ + /** + * timeout set for this lookup task + */ struct GNUNET_TIME_Relative timeout; - /* timeout task for the lookup */ + /** + * a handle to a vpn request + */ + struct GNUNET_VPN_RedirectionRequest *vpn_handle; + + /** + * a socket for a dns request + */ + struct GNUNET_NETWORK_Handle *dns_sock; + + /** + * a synthesized dns name + */ + char dns_name[GNUNET_DNSPARSER_MAX_NAME_LENGTH]; + + /** + * the authoritative dns zone + */ + char dns_zone[GNUNET_DNSPARSER_MAX_NAME_LENGTH]; + + /** + * the address of the DNS server FIXME not needed? + */ + struct sockaddr_in dns_addr; + + /** + * handle to the local stub resolver request + */ + struct GNUNET_RESOLVER_RequestHandle *dns_resolver_handle; + + /** + * select task for DNS + */ + GNUNET_SCHEDULER_TaskIdentifier dns_read_task; + + /** + * pointer to raw dns query payload FIXME needs to be freed/NULL + */ + char *dns_raw_packet; + + /** + * size of the raw dns query + */ + size_t dns_raw_packet_size; + + /** + * timeout task for the lookup + */ GNUNET_SCHEDULER_TaskIdentifier timeout_task; - /* continuation to call on timeout */ + /** + * continuation to call on timeout + */ GNUNET_SCHEDULER_Task timeout_cont; - /* closure for timeout cont */ + /** + * closure for timeout cont + */ void* timeout_cont_cls; - /* called when resolution phase finishes */ + /** + * called when resolution phase finishes + */ ResolutionResultProcessor proc; - /* closure passed to proc */ + /** + * closure passed to proc + */ void* proc_cls; - /* DLL to store the authority chain */ + /** + * DLL to store the authority chain + */ struct AuthorityChain *authority_chain_head; - /* DLL to store the authority chain */ + /** + * DLL to store the authority chain + */ struct AuthorityChain *authority_chain_tail; - /* status of the resolution result */ + /** + * status of the resolution result + */ enum ResolutionStatus status; - /* The provate local zone of this request */ + /** + * The provate local zone of this request + */ struct GNUNET_CRYPTO_ShortHashCode private_local_zone; /** @@ -170,6 +340,11 @@ struct ResolverHandle */ unsigned long long id; + /** + * Pending Namestore task + */ + struct GNUNET_NAMESTORE_QueueEntry *namestore_task; + }; @@ -178,16 +353,24 @@ struct ResolverHandle */ struct RecordLookupHandle { - /* the record type to look up */ + /** + * the record type to look up + */ enum GNUNET_GNS_RecordType record_type; - /* the name to look up */ - char name[MAX_DNS_NAME_LENGTH]; + /** + * the name to look up + */ + char name[GNUNET_DNSPARSER_MAX_NAME_LENGTH]; - /* Method to call on record resolution result */ + /** + * Method to call on record resolution result + */ RecordLookupProcessor proc; - /* closure to pass to proc */ + /** + * closure to pass to proc + */ void* proc_cls; }; @@ -198,55 +381,150 @@ struct RecordLookupHandle */ struct NameShortenHandle { - /* Method to call on shorten result */ + /** + * Method to call on shorten result + */ ShortenResultProcessor proc; - /* closure to pass to proc */ + /** + * closure to pass to proc + */ void* proc_cls; + + /** + * result of shorten + */ + char result[GNUNET_DNSPARSER_MAX_NAME_LENGTH]; + + /** + * root zone + */ + struct GNUNET_CRYPTO_ShortHashCode *root_zone; + + /** + * private zone + */ + struct GNUNET_CRYPTO_ShortHashCode *private_zone; + + /** + * name of private zone + */ + char private_zone_name[GNUNET_DNSPARSER_MAX_LABEL_LENGTH]; + + /** + * shorten zone + */ + struct GNUNET_CRYPTO_ShortHashCode *shorten_zone; + + /** + * name of shorten zone + */ + char shorten_zone_name[GNUNET_DNSPARSER_MAX_LABEL_LENGTH]; + }; + /** * Handle to a get authority context */ struct GetNameAuthorityHandle { - /* the name to look up authority for */ - char name[MAX_DNS_NAME_LENGTH]; + /** + * the name to look up authority for + */ + char name[GNUNET_DNSPARSER_MAX_NAME_LENGTH]; + + /** + * the result + */ + char result[GNUNET_DNSPARSER_MAX_NAME_LENGTH]; - /* Method to call on result */ + /** + * Method to call on result + */ GetAuthorityResultProcessor proc; - /* closure to pass to proc */ + /** + * closure to pass to proc + */ void* proc_cls; }; + /** * Handle to a pseu lookup */ struct GetPseuAuthorityHandle { - /* the name given from delegation */ - char name[MAX_DNS_LABEL_LENGTH]; + /** + * DLL + */ + struct GetPseuAuthorityHandle *next; - /* name to store the pseu under */ - char new_name[MAX_DNS_LABEL_LENGTH]; - - /* the zone of discovered authority */ - struct GNUNET_CRYPTO_ShortHashCode new_zone; + /** + * DLL + */ + struct GetPseuAuthorityHandle *prev; - /* the zone of our authority */ - struct GNUNET_CRYPTO_ShortHashCode zone; + /** + * the name to store the zone under + */ + char name[GNUNET_DNSPARSER_MAX_LABEL_LENGTH]; - /* the private key of the zone to store the pseu in */ + /** + * test name to store the zone under + */ + char test_name[GNUNET_DNSPARSER_MAX_LABEL_LENGTH]; + + /** + * the zone of our authority + */ + struct GNUNET_CRYPTO_ShortHashCode our_zone; + + /** + * the private key of the zone to store the pseu in + */ struct GNUNET_CRYPTO_RsaPrivateKey *key; - /* a handle for dht lookups. should be NULL if no lookups are in progress */ + /** + * a handle for dht lookups. should be NULL if no lookups are in progress + */ struct GNUNET_DHT_GetHandle *get_handle; - /* timeout task for lookup */ + /** + * timeout task for lookup + */ GNUNET_SCHEDULER_TaskIdentifier timeout; + + /** + * Authority to shorten + */ + struct AuthorityChain *auth; + + /** + * handle to namestore request + */ + struct GNUNET_NAMESTORE_QueueEntry* namestore_task; +}; + + +/** + * Namestore queue entries in background + */ +struct NamestoreBGTask +{ + /** + * node in heap + */ + struct GNUNET_CONTAINER_HeapNode *node; + + /** + * queue entry + */ + struct GNUNET_NAMESTORE_QueueEntry *qe; }; + /** * Initialize the resolver * MUST be called before other gns_resolver_* methods @@ -254,25 +532,27 @@ struct GetPseuAuthorityHandle * @param nh handle to the namestore * @param dh handle to the dht * @param lz the local zone + * @param c configuration handle * @param max_bg_queries maximum amount of background queries * @param ignore_pending ignore records that still require user confirmation * on lookup * @returns GNUNET_OK on success */ int -gns_resolver_init(struct GNUNET_NAMESTORE_Handle *nh, - struct GNUNET_DHT_Handle *dh, - struct GNUNET_CRYPTO_ShortHashCode lz, - unsigned long long max_bg_queries, - int ignore_pending); +gns_resolver_init (struct GNUNET_NAMESTORE_Handle *nh, + struct GNUNET_DHT_Handle *dh, + struct GNUNET_CRYPTO_ShortHashCode lz, + const struct GNUNET_CONFIGURATION_Handle *c, + unsigned long long max_bg_queries, + int ignore_pending); + /** * Cleanup resolver: Terminate pending lookups - * - * @param cont continuation to call when finished */ void -gns_resolver_cleanup(ResolverCleanupContinuation cont); +gns_resolver_cleanup (void); + /** * Lookup of a record in a specific zone @@ -284,18 +564,21 @@ gns_resolver_cleanup(ResolverCleanupContinuation cont); * @param name the name to look up * @param key optional private key for authority caching * @param timeout timeout for the resolution + * @param only_cached GNUNET_NO to only check locally not DHT for performance * @param proc the processor to call * @param cls the closure to pass to proc */ void -gns_resolver_lookup_record(struct GNUNET_CRYPTO_ShortHashCode zone, - struct GNUNET_CRYPTO_ShortHashCode pzone, - uint32_t record_type, - const char* name, - struct GNUNET_CRYPTO_RsaPrivateKey *key, - struct GNUNET_TIME_Relative timeout, - RecordLookupProcessor proc, - void* cls); +gns_resolver_lookup_record (struct GNUNET_CRYPTO_ShortHashCode zone, + struct GNUNET_CRYPTO_ShortHashCode pzone, + uint32_t record_type, + const char* name, + struct GNUNET_CRYPTO_RsaPrivateKey *key, + struct GNUNET_TIME_Relative timeout, + int only_cached, + RecordLookupProcessor proc, + void* cls); + /** * Shortens a name if possible. If the shortening fails @@ -304,20 +587,25 @@ gns_resolver_lookup_record(struct GNUNET_CRYPTO_ShortHashCode zone, * There is no guarantee that the shortened name will * actually be canonical/short etc. * - * @param zone the zone to perform the operation in - * @param pzone the private local zone + * @param zone the root zone to use + * @param pzone the private zone to use + * @param szone the shorten zone to use * @param name name to shorten - * @param key optional private key for background lookups and PSEU import + * @param private_zone_name name of the private zone + * @param shorten_zone_name name of the shorten zone * @param proc the processor to call on shorten result * @param proc_cls the closure to pass to proc */ void -gns_resolver_shorten_name(struct GNUNET_CRYPTO_ShortHashCode zone, - struct GNUNET_CRYPTO_ShortHashCode pzone, - const char* name, - struct GNUNET_CRYPTO_RsaPrivateKey *key, - ShortenResultProcessor proc, - void* proc_cls); +gns_resolver_shorten_name (struct GNUNET_CRYPTO_ShortHashCode *zone, + struct GNUNET_CRYPTO_ShortHashCode *pzone, + struct GNUNET_CRYPTO_ShortHashCode *szone, + const char* name, + const char* private_zone_name, + const char* shorten_zone_name, + ShortenResultProcessor proc, + void* proc_cls); + /** * Tries to resolve the authority for name @@ -330,11 +618,11 @@ gns_resolver_shorten_name(struct GNUNET_CRYPTO_ShortHashCode zone, * @param proc_cls the closure to pass to the processor */ void -gns_resolver_get_authority(struct GNUNET_CRYPTO_ShortHashCode zone, - struct GNUNET_CRYPTO_ShortHashCode pzone, - const char* name, - GetAuthorityResultProcessor proc, - void* proc_cls); +gns_resolver_get_authority (struct GNUNET_CRYPTO_ShortHashCode zone, + struct GNUNET_CRYPTO_ShortHashCode pzone, + const char* name, + GetAuthorityResultProcessor proc, + void* proc_cls); /** * Generic function to check for TLDs @@ -344,12 +632,14 @@ gns_resolver_get_authority(struct GNUNET_CRYPTO_ShortHashCode zone, * @return GNUNET_YES or GNUNET_NO */ int -is_tld(const char* name, const char* tld); +is_tld (const char* name, + const char* tld); + /** - * Checks for gnunet/zkey + * Checks for gads/zkey */ -#define is_gnunet_tld(name) is_tld(name, GNUNET_GNS_TLD) +#define is_gads_tld(name) is_tld(name, GNUNET_GNS_TLD) #define is_zkey_tld(name) is_tld(name, GNUNET_GNS_TLD_ZKEY) diff --git a/src/gns/nss/Makefile.am b/src/gns/nss/Makefile.am index 5e8ab5a..64bc813 100644 --- a/src/gns/nss/Makefile.am +++ b/src/gns/nss/Makefile.am @@ -3,8 +3,8 @@ # This file taken and modified from nss-gns. # # nss-gns is free software; you can redistribute it and/or modify it -# under the terms of the GNU Lesser General Public License as -# published by the Free Software Foundation; either version 2 of the +# under the terms of the GNU General Public License as +# published by the Free Software Foundation; either version 3 of the # License, or (at your option) any later version. # # nss-gns is distributed in the hope that it will be useful, but @@ -17,24 +17,24 @@ # Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 # USA. -EXTRA_DIST = map-file +EXTRA_DIST = map-file \ + install-nss-plugin.sh \ + uninstall-nss-plugin.sh AM_LDFLAGS=-avoid-version -module -export-dynamic -if HAVE_SUDO -nssdir = /lib/ -else -nssdir = $(libdir) -endif +nssdir = $(NSS_DIR) LIBTOOL = $(SUDO_BINARY) $(SHELL) $(top_builddir)/libtool if !MINGW +if INSTALL_NSS nss_LTLIBRARIES = \ libnss_gns.la \ libnss_gns4.la \ libnss_gns6.la endif +endif sources = nss_gns_query.h nss_gns_query.c @@ -51,9 +51,12 @@ libnss_gns6_la_SOURCES=$(libnss_gns_la_SOURCES) libnss_gns6_la_CFLAGS=$(libnss_gns_la_CFLAGS) -DNSS_IPV6_ONLY=1 libnss_gns6_la_LDFLAGS=$(libnss_gns_la_LDFLAGS) +if !MINGW install-data-hook: - $(SUDO_BINARY) $(SHELL) $(top_builddir)/libtool --finish $(nssdir) - $(SUDO_BINARY) rm -f $(nssdir)/libnss_gns.la $(nssdir)/libnss_gns4.la $(nssdir)/libnss_gns6.la + $(top_srcdir)/src/gns/nss/install-nss-plugin.sh $(SHELL) $(top_builddir) $(nssdir) $(SUDO_BINARY) uninstall-hook: - $(SUDO_BINARY) rm -f $(nssdir)/libnss_gns.so.2 $(nssdir)/libnss_gns4.so.2 $(nssdir)/libnss_gns6.so.2 + $(top_srcdir)/src/gns/nss/uninstall-nss-plugin.sh $(SHELL) $(top_builddir) "rm -f $(nssdir)/libnss_gns.so.2" $(SUDO_BINARY) + $(top_srcdir)/src/gns/nss/uninstall-nss-plugin.sh $(SHELL) $(top_builddir) "rm -f $(nssdir)/libnss_gns4.so.2" $(SUDO_BINARY) + $(top_srcdir)/src/gns/nss/uninstall-nss-plugin.sh $(SHELL) $(top_builddir) "rm -f $(nssdir)/libnss_gns6.so.2" $(SUDO_BINARY) +endif diff --git a/src/gns/nss/Makefile.in b/src/gns/nss/Makefile.in index 6b3b3df..9352442 100644 --- a/src/gns/nss/Makefile.in +++ b/src/gns/nss/Makefile.in @@ -1,9 +1,9 @@ -# Makefile.in generated by automake 1.11.1 from Makefile.am. +# Makefile.in generated by automake 1.11.6 from Makefile.am. # @configure_input@ # Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, -# 2003, 2004, 2005, 2006, 2007, 2008, 2009 Free Software Foundation, -# Inc. +# 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Free Software +# Foundation, Inc. # This Makefile.in is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. @@ -20,8 +20,8 @@ # This file taken and modified from nss-gns. # # nss-gns is free software; you can redistribute it and/or modify it -# under the terms of the GNU Lesser General Public License as -# published by the Free Software Foundation; either version 2 of the +# under the terms of the GNU General Public License as +# published by the Free Software Foundation; either version 3 of the # License, or (at your option) any later version. # # nss-gns is distributed in the hope that it will be useful, but @@ -35,6 +35,23 @@ # USA. VPATH = @srcdir@ +am__make_dryrun = \ + { \ + am__dry=no; \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + echo 'am--echo: ; @echo "AM" OK' | $(MAKE) -f - 2>/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } pkgdatadir = $(datadir)/@PACKAGE@ pkgincludedir = $(includedir)/@PACKAGE@ pkglibdir = $(libdir)/@PACKAGE@ @@ -59,14 +76,15 @@ DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 am__aclocal_m4_deps = $(top_srcdir)/m4/absolute-header.m4 \ $(top_srcdir)/m4/align.m4 $(top_srcdir)/m4/argz.m4 \ - $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/iconv.m4 \ - $(top_srcdir)/m4/lib-ld.m4 $(top_srcdir)/m4/lib-link.m4 \ - $(top_srcdir)/m4/lib-prefix.m4 $(top_srcdir)/m4/libcurl.m4 \ - $(top_srcdir)/m4/libgcrypt.m4 $(top_srcdir)/m4/libtool.m4 \ - $(top_srcdir)/m4/libunistring.m4 $(top_srcdir)/m4/ltdl.m4 \ - $(top_srcdir)/m4/ltoptions.m4 $(top_srcdir)/m4/ltsugar.m4 \ - $(top_srcdir)/m4/ltversion.m4 $(top_srcdir)/m4/lt~obsolete.m4 \ - $(top_srcdir)/m4/nls.m4 $(top_srcdir)/m4/po.m4 \ + $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/glib-2.0.m4 \ + $(top_srcdir)/m4/iconv.m4 $(top_srcdir)/m4/lib-ld.m4 \ + $(top_srcdir)/m4/lib-link.m4 $(top_srcdir)/m4/lib-prefix.m4 \ + $(top_srcdir)/m4/libcurl.m4 $(top_srcdir)/m4/libgcrypt.m4 \ + $(top_srcdir)/m4/libtool.m4 $(top_srcdir)/m4/libunistring.m4 \ + $(top_srcdir)/m4/ltdl.m4 $(top_srcdir)/m4/ltoptions.m4 \ + $(top_srcdir)/m4/ltsugar.m4 $(top_srcdir)/m4/ltversion.m4 \ + $(top_srcdir)/m4/lt~obsolete.m4 $(top_srcdir)/m4/nls.m4 \ + $(top_srcdir)/m4/pkg.m4 $(top_srcdir)/m4/po.m4 \ $(top_srcdir)/m4/progtest.m4 $(top_srcdir)/acinclude.m4 \ $(top_srcdir)/configure.ac am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ @@ -96,19 +114,26 @@ am__nobase_list = $(am__nobase_strip_setup); \ am__base_list = \ sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \ sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g' +am__uninstall_files_from_dir = { \ + test -z "$$files" \ + || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \ + || { echo " ( cd '$$dir' && rm -f" $$files ")"; \ + $(am__cd) "$$dir" && rm -f $$files; }; \ + } am__installdirs = "$(DESTDIR)$(nssdir)" LTLIBRARIES = $(nss_LTLIBRARIES) libnss_gns_la_LIBADD = am__objects_1 = libnss_gns_la-nss_gns_query.lo am_libnss_gns_la_OBJECTS = $(am__objects_1) libnss_gns_la-nss_gns.lo libnss_gns_la_OBJECTS = $(am_libnss_gns_la_OBJECTS) -AM_V_lt = $(am__v_lt_$(V)) -am__v_lt_ = $(am__v_lt_$(AM_DEFAULT_VERBOSITY)) +AM_V_lt = $(am__v_lt_@AM_V@) +am__v_lt_ = $(am__v_lt_@AM_DEFAULT_V@) am__v_lt_0 = --silent libnss_gns_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=link $(CCLD) $(libnss_gns_la_CFLAGS) \ $(CFLAGS) $(libnss_gns_la_LDFLAGS) $(LDFLAGS) -o $@ -@MINGW_FALSE@am_libnss_gns_la_rpath = -rpath $(nssdir) +@INSTALL_NSS_TRUE@@MINGW_FALSE@am_libnss_gns_la_rpath = -rpath \ +@INSTALL_NSS_TRUE@@MINGW_FALSE@ $(nssdir) libnss_gns4_la_LIBADD = am__objects_2 = libnss_gns4_la-nss_gns_query.lo am__objects_3 = $(am__objects_2) libnss_gns4_la-nss_gns.lo @@ -118,7 +143,8 @@ libnss_gns4_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ $(libnss_gns4_la_CFLAGS) $(CFLAGS) $(libnss_gns4_la_LDFLAGS) \ $(LDFLAGS) -o $@ -@MINGW_FALSE@am_libnss_gns4_la_rpath = -rpath $(nssdir) +@INSTALL_NSS_TRUE@@MINGW_FALSE@am_libnss_gns4_la_rpath = -rpath \ +@INSTALL_NSS_TRUE@@MINGW_FALSE@ $(nssdir) libnss_gns6_la_LIBADD = am__objects_4 = libnss_gns6_la-nss_gns_query.lo am__objects_5 = $(am__objects_4) libnss_gns6_la-nss_gns.lo @@ -128,7 +154,8 @@ libnss_gns6_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ $(libnss_gns6_la_CFLAGS) $(CFLAGS) $(libnss_gns6_la_LDFLAGS) \ $(LDFLAGS) -o $@ -@MINGW_FALSE@am_libnss_gns6_la_rpath = -rpath $(nssdir) +@INSTALL_NSS_TRUE@@MINGW_FALSE@am_libnss_gns6_la_rpath = -rpath \ +@INSTALL_NSS_TRUE@@MINGW_FALSE@ $(nssdir) DEFAULT_INCLUDES = -I.@am__isrc@ -I$(top_builddir) depcomp = $(SHELL) $(top_srcdir)/depcomp am__depfiles_maybe = depfiles @@ -139,26 +166,31 @@ LTCOMPILE = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) \ $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) \ $(AM_CFLAGS) $(CFLAGS) -AM_V_CC = $(am__v_CC_$(V)) -am__v_CC_ = $(am__v_CC_$(AM_DEFAULT_VERBOSITY)) +AM_V_CC = $(am__v_CC_@AM_V@) +am__v_CC_ = $(am__v_CC_@AM_DEFAULT_V@) am__v_CC_0 = @echo " CC " $@; -AM_V_at = $(am__v_at_$(V)) -am__v_at_ = $(am__v_at_$(AM_DEFAULT_VERBOSITY)) +AM_V_at = $(am__v_at_@AM_V@) +am__v_at_ = $(am__v_at_@AM_DEFAULT_V@) am__v_at_0 = @ CCLD = $(CC) LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ $(AM_LDFLAGS) $(LDFLAGS) -o $@ -AM_V_CCLD = $(am__v_CCLD_$(V)) -am__v_CCLD_ = $(am__v_CCLD_$(AM_DEFAULT_VERBOSITY)) +AM_V_CCLD = $(am__v_CCLD_@AM_V@) +am__v_CCLD_ = $(am__v_CCLD_@AM_DEFAULT_V@) am__v_CCLD_0 = @echo " CCLD " $@; -AM_V_GEN = $(am__v_GEN_$(V)) -am__v_GEN_ = $(am__v_GEN_$(AM_DEFAULT_VERBOSITY)) +AM_V_GEN = $(am__v_GEN_@AM_V@) +am__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@) am__v_GEN_0 = @echo " GEN " $@; SOURCES = $(libnss_gns_la_SOURCES) $(libnss_gns4_la_SOURCES) \ $(libnss_gns6_la_SOURCES) DIST_SOURCES = $(libnss_gns_la_SOURCES) $(libnss_gns4_la_SOURCES) \ $(libnss_gns6_la_SOURCES) +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac ETAGS = etags CTAGS = ctags DISTFILES = $(DIST_COMMON) $(DIST_SOURCES) $(TEXINFOS) $(EXTRA_DIST) @@ -197,6 +229,10 @@ EXEEXT = @EXEEXT@ EXT_LIBS = @EXT_LIBS@ EXT_LIB_PATH = @EXT_LIB_PATH@ FGREP = @FGREP@ +GLIB_CFLAGS = @GLIB_CFLAGS@ +GLIB_GENMARSHAL = @GLIB_GENMARSHAL@ +GLIB_LIBS = @GLIB_LIBS@ +GLIB_MKENUMS = @GLIB_MKENUMS@ GMSGFMT = @GMSGFMT@ GMSGFMT_015 = @GMSGFMT_015@ GNUNETDNS_GROUP = @GNUNETDNS_GROUP@ @@ -207,6 +243,7 @@ GN_LIBINTL = @GN_LIBINTL@ GN_LIB_LDFLAGS = @GN_LIB_LDFLAGS@ GN_PLUGIN_LDFLAGS = @GN_PLUGIN_LDFLAGS@ GN_USER_HOME_DIR = @GN_USER_HOME_DIR@ +GOBJECT_QUERY = @GOBJECT_QUERY@ GREP = @GREP@ HAVE_LIBUNISTRING = @HAVE_LIBUNISTRING@ INCLTDL = @INCLTDL@ @@ -229,6 +266,8 @@ LIBCURL_CPPFLAGS = @LIBCURL_CPPFLAGS@ LIBGCRYPT_CFLAGS = @LIBGCRYPT_CFLAGS@ LIBGCRYPT_CONFIG = @LIBGCRYPT_CONFIG@ LIBGCRYPT_LIBS = @LIBGCRYPT_LIBS@ +LIBGTOP_CFLAGS = @LIBGTOP_CFLAGS@ +LIBGTOP_LIBS = @LIBGTOP_LIBS@ LIBICONV = @LIBICONV@ LIBINTL = @LIBINTL@ LIBLTDL = @LIBLTDL@ @@ -250,6 +289,7 @@ LT_CONFIG_H = @LT_CONFIG_H@ LT_DLLOADERS = @LT_DLLOADERS@ LT_DLPREOPEN = @LT_DLPREOPEN@ MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ MKDIR_P = @MKDIR_P@ MONKEYPREFIX = @MONKEYPREFIX@ MSGFMT = @MSGFMT@ @@ -259,6 +299,7 @@ MYSQL_CPPFLAGS = @MYSQL_CPPFLAGS@ MYSQL_LDFLAGS = @MYSQL_LDFLAGS@ NM = @NM@ NMEDIT = @NMEDIT@ +NSS_DIR = @NSS_DIR@ OBJC = @OBJC@ OBJCDEPMODE = @OBJCDEPMODE@ OBJCFLAGS = @OBJCFLAGS@ @@ -274,6 +315,7 @@ PACKAGE_TARNAME = @PACKAGE_TARNAME@ PACKAGE_URL = @PACKAGE_URL@ PACKAGE_VERSION = @PACKAGE_VERSION@ PATH_SEPARATOR = @PATH_SEPARATOR@ +PKG_CONFIG = @PKG_CONFIG@ POSTGRES_CPPFLAGS = @POSTGRES_CPPFLAGS@ POSTGRES_LDFLAGS = @POSTGRES_LDFLAGS@ POSUB = @POSUB@ @@ -305,6 +347,7 @@ abs_builddir = @abs_builddir@ abs_srcdir = @abs_srcdir@ abs_top_builddir = @abs_top_builddir@ abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ ac_ct_CC = @ac_ct_CC@ ac_ct_CXX = @ac_ct_CXX@ ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ @@ -327,6 +370,7 @@ datarootdir = @datarootdir@ docdir = @docdir@ dvidir = @dvidir@ exec_prefix = @exec_prefix@ +gitcommand = @gitcommand@ host = @host@ host_alias = @host_alias@ host_cpu = @host_cpu@ @@ -340,7 +384,6 @@ libdir = @libdir@ libexecdir = @libexecdir@ localedir = @localedir@ localstatedir = @localstatedir@ -lt_ECHO = @lt_ECHO@ ltdl_LIBOBJS = @ltdl_LIBOBJS@ ltdl_LTLIBOBJS = @ltdl_LTLIBOBJS@ mandir = @mandir@ @@ -358,6 +401,7 @@ sbindir = @sbindir@ sharedstatedir = @sharedstatedir@ srcdir = @srcdir@ subdirs = @subdirs@ +svnversioncommand = @svnversioncommand@ sys_symbol_underscore = @sys_symbol_underscore@ sysconfdir = @sysconfdir@ target = @target@ @@ -368,14 +412,16 @@ target_vendor = @target_vendor@ top_build_prefix = @top_build_prefix@ top_builddir = @top_builddir@ top_srcdir = @top_srcdir@ -EXTRA_DIST = map-file +EXTRA_DIST = map-file \ + install-nss-plugin.sh \ + uninstall-nss-plugin.sh + AM_LDFLAGS = -avoid-version -module -export-dynamic -@HAVE_SUDO_FALSE@nssdir = $(libdir) -@HAVE_SUDO_TRUE@nssdir = /lib/ -@MINGW_FALSE@nss_LTLIBRARIES = \ -@MINGW_FALSE@ libnss_gns.la \ -@MINGW_FALSE@ libnss_gns4.la \ -@MINGW_FALSE@ libnss_gns6.la +nssdir = $(NSS_DIR) +@INSTALL_NSS_TRUE@@MINGW_FALSE@nss_LTLIBRARIES = \ +@INSTALL_NSS_TRUE@@MINGW_FALSE@ libnss_gns.la \ +@INSTALL_NSS_TRUE@@MINGW_FALSE@ libnss_gns4.la \ +@INSTALL_NSS_TRUE@@MINGW_FALSE@ libnss_gns6.la sources = nss_gns_query.h nss_gns_query.c @@ -425,7 +471,6 @@ $(ACLOCAL_M4): $(am__aclocal_m4_deps) $(am__aclocal_m4_deps): install-nssLTLIBRARIES: $(nss_LTLIBRARIES) @$(NORMAL_INSTALL) - test -z "$(nssdir)" || $(MKDIR_P) "$(DESTDIR)$(nssdir)" @list='$(nss_LTLIBRARIES)'; test -n "$(nssdir)" || list=; \ list2=; for p in $$list; do \ if test -f $$p; then \ @@ -433,6 +478,8 @@ install-nssLTLIBRARIES: $(nss_LTLIBRARIES) else :; fi; \ done; \ test -z "$$list2" || { \ + echo " $(MKDIR_P) '$(DESTDIR)$(nssdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(nssdir)" || exit 1; \ echo " $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 '$(DESTDIR)$(nssdir)'"; \ $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 "$(DESTDIR)$(nssdir)"; \ } @@ -454,11 +501,11 @@ clean-nssLTLIBRARIES: echo "rm -f \"$${dir}/so_locations\""; \ rm -f "$${dir}/so_locations"; \ done -libnss_gns.la: $(libnss_gns_la_OBJECTS) $(libnss_gns_la_DEPENDENCIES) +libnss_gns.la: $(libnss_gns_la_OBJECTS) $(libnss_gns_la_DEPENDENCIES) $(EXTRA_libnss_gns_la_DEPENDENCIES) $(AM_V_CCLD)$(libnss_gns_la_LINK) $(am_libnss_gns_la_rpath) $(libnss_gns_la_OBJECTS) $(libnss_gns_la_LIBADD) $(LIBS) -libnss_gns4.la: $(libnss_gns4_la_OBJECTS) $(libnss_gns4_la_DEPENDENCIES) +libnss_gns4.la: $(libnss_gns4_la_OBJECTS) $(libnss_gns4_la_DEPENDENCIES) $(EXTRA_libnss_gns4_la_DEPENDENCIES) $(AM_V_CCLD)$(libnss_gns4_la_LINK) $(am_libnss_gns4_la_rpath) $(libnss_gns4_la_OBJECTS) $(libnss_gns4_la_LIBADD) $(LIBS) -libnss_gns6.la: $(libnss_gns6_la_OBJECTS) $(libnss_gns6_la_DEPENDENCIES) +libnss_gns6.la: $(libnss_gns6_la_OBJECTS) $(libnss_gns6_la_DEPENDENCIES) $(EXTRA_libnss_gns6_la_DEPENDENCIES) $(AM_V_CCLD)$(libnss_gns6_la_LINK) $(am_libnss_gns6_la_rpath) $(libnss_gns6_la_OBJECTS) $(libnss_gns6_la_LIBADD) $(LIBS) mostlyclean-compile: @@ -477,74 +524,65 @@ distclean-compile: .c.o: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c $< .c.obj: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'` @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c `$(CYGPATH_W) '$<'` +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c `$(CYGPATH_W) '$<'` .c.lo: @am__fastdepCC_TRUE@ $(AM_V_CC)$(LTCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LTCOMPILE) -c -o $@ $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LTCOMPILE) -c -o $@ $< libnss_gns_la-nss_gns_query.lo: nss_gns_query.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libnss_gns_la_CFLAGS) $(CFLAGS) -MT libnss_gns_la-nss_gns_query.lo -MD -MP -MF $(DEPDIR)/libnss_gns_la-nss_gns_query.Tpo -c -o libnss_gns_la-nss_gns_query.lo `test -f 'nss_gns_query.c' || echo '$(srcdir)/'`nss_gns_query.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/libnss_gns_la-nss_gns_query.Tpo $(DEPDIR)/libnss_gns_la-nss_gns_query.Plo -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='nss_gns_query.c' object='libnss_gns_la-nss_gns_query.lo' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='nss_gns_query.c' object='libnss_gns_la-nss_gns_query.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libnss_gns_la_CFLAGS) $(CFLAGS) -c -o libnss_gns_la-nss_gns_query.lo `test -f 'nss_gns_query.c' || echo '$(srcdir)/'`nss_gns_query.c +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libnss_gns_la_CFLAGS) $(CFLAGS) -c -o libnss_gns_la-nss_gns_query.lo `test -f 'nss_gns_query.c' || echo '$(srcdir)/'`nss_gns_query.c libnss_gns_la-nss_gns.lo: nss_gns.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libnss_gns_la_CFLAGS) $(CFLAGS) -MT libnss_gns_la-nss_gns.lo -MD -MP -MF $(DEPDIR)/libnss_gns_la-nss_gns.Tpo -c -o libnss_gns_la-nss_gns.lo `test -f 'nss_gns.c' || echo '$(srcdir)/'`nss_gns.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/libnss_gns_la-nss_gns.Tpo $(DEPDIR)/libnss_gns_la-nss_gns.Plo -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='nss_gns.c' object='libnss_gns_la-nss_gns.lo' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='nss_gns.c' object='libnss_gns_la-nss_gns.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libnss_gns_la_CFLAGS) $(CFLAGS) -c -o libnss_gns_la-nss_gns.lo `test -f 'nss_gns.c' || echo '$(srcdir)/'`nss_gns.c +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libnss_gns_la_CFLAGS) $(CFLAGS) -c -o libnss_gns_la-nss_gns.lo `test -f 'nss_gns.c' || echo '$(srcdir)/'`nss_gns.c libnss_gns4_la-nss_gns_query.lo: nss_gns_query.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libnss_gns4_la_CFLAGS) $(CFLAGS) -MT libnss_gns4_la-nss_gns_query.lo -MD -MP -MF $(DEPDIR)/libnss_gns4_la-nss_gns_query.Tpo -c -o libnss_gns4_la-nss_gns_query.lo `test -f 'nss_gns_query.c' || echo '$(srcdir)/'`nss_gns_query.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/libnss_gns4_la-nss_gns_query.Tpo $(DEPDIR)/libnss_gns4_la-nss_gns_query.Plo -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='nss_gns_query.c' object='libnss_gns4_la-nss_gns_query.lo' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='nss_gns_query.c' object='libnss_gns4_la-nss_gns_query.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libnss_gns4_la_CFLAGS) $(CFLAGS) -c -o libnss_gns4_la-nss_gns_query.lo `test -f 'nss_gns_query.c' || echo '$(srcdir)/'`nss_gns_query.c +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libnss_gns4_la_CFLAGS) $(CFLAGS) -c -o libnss_gns4_la-nss_gns_query.lo `test -f 'nss_gns_query.c' || echo '$(srcdir)/'`nss_gns_query.c libnss_gns4_la-nss_gns.lo: nss_gns.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libnss_gns4_la_CFLAGS) $(CFLAGS) -MT libnss_gns4_la-nss_gns.lo -MD -MP -MF $(DEPDIR)/libnss_gns4_la-nss_gns.Tpo -c -o libnss_gns4_la-nss_gns.lo `test -f 'nss_gns.c' || echo '$(srcdir)/'`nss_gns.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/libnss_gns4_la-nss_gns.Tpo $(DEPDIR)/libnss_gns4_la-nss_gns.Plo -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='nss_gns.c' object='libnss_gns4_la-nss_gns.lo' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='nss_gns.c' object='libnss_gns4_la-nss_gns.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libnss_gns4_la_CFLAGS) $(CFLAGS) -c -o libnss_gns4_la-nss_gns.lo `test -f 'nss_gns.c' || echo '$(srcdir)/'`nss_gns.c +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libnss_gns4_la_CFLAGS) $(CFLAGS) -c -o libnss_gns4_la-nss_gns.lo `test -f 'nss_gns.c' || echo '$(srcdir)/'`nss_gns.c libnss_gns6_la-nss_gns_query.lo: nss_gns_query.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libnss_gns6_la_CFLAGS) $(CFLAGS) -MT libnss_gns6_la-nss_gns_query.lo -MD -MP -MF $(DEPDIR)/libnss_gns6_la-nss_gns_query.Tpo -c -o libnss_gns6_la-nss_gns_query.lo `test -f 'nss_gns_query.c' || echo '$(srcdir)/'`nss_gns_query.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/libnss_gns6_la-nss_gns_query.Tpo $(DEPDIR)/libnss_gns6_la-nss_gns_query.Plo -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='nss_gns_query.c' object='libnss_gns6_la-nss_gns_query.lo' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='nss_gns_query.c' object='libnss_gns6_la-nss_gns_query.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libnss_gns6_la_CFLAGS) $(CFLAGS) -c -o libnss_gns6_la-nss_gns_query.lo `test -f 'nss_gns_query.c' || echo '$(srcdir)/'`nss_gns_query.c +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libnss_gns6_la_CFLAGS) $(CFLAGS) -c -o libnss_gns6_la-nss_gns_query.lo `test -f 'nss_gns_query.c' || echo '$(srcdir)/'`nss_gns_query.c libnss_gns6_la-nss_gns.lo: nss_gns.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libnss_gns6_la_CFLAGS) $(CFLAGS) -MT libnss_gns6_la-nss_gns.lo -MD -MP -MF $(DEPDIR)/libnss_gns6_la-nss_gns.Tpo -c -o libnss_gns6_la-nss_gns.lo `test -f 'nss_gns.c' || echo '$(srcdir)/'`nss_gns.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/libnss_gns6_la-nss_gns.Tpo $(DEPDIR)/libnss_gns6_la-nss_gns.Plo -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='nss_gns.c' object='libnss_gns6_la-nss_gns.lo' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='nss_gns.c' object='libnss_gns6_la-nss_gns.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libnss_gns6_la_CFLAGS) $(CFLAGS) -c -o libnss_gns6_la-nss_gns.lo `test -f 'nss_gns.c' || echo '$(srcdir)/'`nss_gns.c +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libnss_gns6_la_CFLAGS) $(CFLAGS) -c -o libnss_gns6_la-nss_gns.lo `test -f 'nss_gns.c' || echo '$(srcdir)/'`nss_gns.c mostlyclean-libtool: -rm -f *.lo @@ -651,10 +689,15 @@ install-am: all-am installcheck: installcheck-am install-strip: - $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ - install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ - `test -z '$(STRIP)' || \ - echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi mostlyclean-generic: clean-generic: @@ -666,6 +709,8 @@ distclean-generic: maintainer-clean-generic: @echo "This command is intended for maintainers to use" @echo "it deletes files that may require special tools to rebuild." +@MINGW_TRUE@install-data-hook: +@MINGW_TRUE@uninstall-hook: clean: clean-am clean-am: clean-generic clean-libtool clean-nssLTLIBRARIES \ @@ -757,12 +802,13 @@ uninstall-am: uninstall-nssLTLIBRARIES uninstall-nssLTLIBRARIES -install-data-hook: - $(SUDO_BINARY) $(SHELL) $(top_builddir)/libtool --finish $(nssdir) - $(SUDO_BINARY) rm -f $(nssdir)/libnss_gns.la $(nssdir)/libnss_gns4.la $(nssdir)/libnss_gns6.la +@MINGW_FALSE@install-data-hook: +@MINGW_FALSE@ $(top_srcdir)/src/gns/nss/install-nss-plugin.sh $(SHELL) $(top_builddir) $(nssdir) $(SUDO_BINARY) -uninstall-hook: - $(SUDO_BINARY) rm -f $(nssdir)/libnss_gns.so.2 $(nssdir)/libnss_gns4.so.2 $(nssdir)/libnss_gns6.so.2 +@MINGW_FALSE@uninstall-hook: +@MINGW_FALSE@ $(top_srcdir)/src/gns/nss/uninstall-nss-plugin.sh $(SHELL) $(top_builddir) "rm -f $(nssdir)/libnss_gns.so.2" $(SUDO_BINARY) +@MINGW_FALSE@ $(top_srcdir)/src/gns/nss/uninstall-nss-plugin.sh $(SHELL) $(top_builddir) "rm -f $(nssdir)/libnss_gns4.so.2" $(SUDO_BINARY) +@MINGW_FALSE@ $(top_srcdir)/src/gns/nss/uninstall-nss-plugin.sh $(SHELL) $(top_builddir) "rm -f $(nssdir)/libnss_gns6.so.2" $(SUDO_BINARY) # Tell versions [3.59,3.63) of GNU make to not export all variables. # Otherwise a system limit (for SysV at least) may be exceeded. diff --git a/src/gns/nss/install-nss-plugin.sh b/src/gns/nss/install-nss-plugin.sh new file mode 100755 index 0000000..c87db76 --- /dev/null +++ b/src/gns/nss/install-nss-plugin.sh @@ -0,0 +1,8 @@ +#!/bin/bash +# $1 - shell +# $2 - top_builddir +# $3 - nssdir +# $4 - sudo binary (empty if root) +$4 $1 $2/libtool --mode=finish $3 +echo LTINST: $4 $1 $2/libtool --mode=finish $3 +$4 rm -f $3/libnss_gns.la $3/libnss_gns4.la $3/libnss_gns6.la diff --git a/src/gns/nss/nss_gns.c b/src/gns/nss/nss_gns.c index 3bb45a1..ce9dcf3 100644 --- a/src/gns/nss/nss_gns.c +++ b/src/gns/nss/nss_gns.c @@ -4,8 +4,8 @@ Parts taken from: nss.c in nss-mdns nss-mdns is free software; you can redistribute it and/or modify - it under the terms of the GNU Lesser General Public License as published - by the Free Software Foundation; either version 2 of the License, + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. nss-mdns is distributed in the hope that it will be useful, but1 @@ -61,13 +61,13 @@ static int ends_with(const char *name, const char* suffix) { /** - * Check if name is inside .gnunet or .zkey TLD + * Check if name is inside .gads or .zkey TLD * * @param name name to check * @return 1 if true */ static int verify_name_allowed(const char *name) { - return ends_with(name, ".gnunet") || ends_with(name, ".zkey"); + return ends_with(name, ".gads") || ends_with(name, ".zkey"); } /** @@ -140,13 +140,19 @@ enum nss_status _nss_gns_gethostbyname2_r( if (!gns_resolve_name(af, name, &u) == 0) { status = NSS_STATUS_NOTFOUND; + goto finish; } } + else + { + status = NSS_STATUS_UNAVAIL; + goto finish; + } if (u.count == 0) { *errnop = ETIMEDOUT; *h_errnop = HOST_NOT_FOUND; - printf("not found\n"); + status = NSS_STATUS_NOTFOUND; goto finish; } diff --git a/src/gns/nss/nss_gns_query.c b/src/gns/nss/nss_gns_query.c index ab88d22..33a71f7 100644 --- a/src/gns/nss/nss_gns_query.c +++ b/src/gns/nss/nss_gns_query.c @@ -1,3 +1,22 @@ +/* + This file is part of GNUnet. + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ #include #include #include @@ -14,52 +33,74 @@ * @param u the userdata (result struct) * @return -1 on error else 0 */ -int gns_resolve_name(int af, const char *name, struct userdata *u) +int +gns_resolve_name (int af, + const char *name, + struct userdata *u) { FILE *p; char *cmd; char line[128]; - if (af == AF_INET6) + if (AF_INET6 == af) { - if (-1 == asprintf(&cmd, "%s -t AAAA -u %s\n", "gnunet-gns -r", name)) + if (-1 == asprintf (&cmd, + "%s -t AAAA -u %s\n", + "gnunet-gns -r", name)) return -1; } else { - if (-1 == asprintf(&cmd, "%s %s\n", "gnunet-gns -r -u", name)) + if (-1 == asprintf (&cmd, + "%s %s\n", + "gnunet-gns -r -u", name)) return -1; } - - p = popen(cmd,"r"); - - if (p != NULL ) + if (NULL == (p = popen (cmd, "r"))) + { + free (cmd); + return -1; + } + while (NULL != fgets (line, sizeof(line), p)) { - while (fgets( line, sizeof(line), p ) != NULL) + if (u->count >= MAX_ENTRIES) + break; + if (line[strlen(line)-1] == '\n') { - - if (u->count >= MAX_ENTRIES) - break; - - if (line[strlen(line)-1] == '\n') + line[strlen(line)-1] = '\0'; + if (AF_INET == af) + { + if (inet_pton(af, line, &(u->data.ipv4[u->count]))) + { + u->count++; + u->data_len += sizeof(ipv4_address_t); + } + else + { + pclose (p); + free (cmd); + return -1; + } + } + else if (AF_INET6 == af) { - line[strlen(line)-1] = '\0'; - if (af == AF_INET) + if (inet_pton(af, line, &(u->data.ipv6[u->count]))) { - inet_pton(af, line, &(u->data.ipv4[u->count++])); - u->data_len += sizeof(ipv4_address_t); - } - else if ((af == AF_INET6)) + u->count++; + u->data_len += sizeof(ipv6_address_t); + } + else { - inet_pton(af, line, &(u->data.ipv6[u->count++])); - u->data_len += sizeof(ipv6_address_t); - } + pclose (p); + free (cmd); + return -1; + } } } } - fclose(p); - free(cmd); - + pclose (p); + free (cmd); return 0; - } + +/* end of nss_gns_query.c */ diff --git a/src/gns/nss/nss_gns_query.h b/src/gns/nss/nss_gns_query.h index 0b4dae5..65b0311 100644 --- a/src/gns/nss/nss_gns_query.h +++ b/src/gns/nss/nss_gns_query.h @@ -1,31 +1,28 @@ +/* + This file is part of GNUnet. + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ #ifndef NSS_GNS_QUERY_H #define NSS_GNS_QUERY_H /** - * Parts taken from nss-mdns. Original license statement follows + * Parts taken from nss-mdns */ - -/* $Id$ */ - -/*** - This file is part of nss-mdns. - - nss-mdns is free software; you can redistribute it and/or modify it - under the terms of the GNU Lesser General Public License as - published by the Free Software Foundation; either version 2 of the - License, or (at your option) any later version. - - nss-mdns is distributed in the hope that it will be useful, but - WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - General Public License for more details. - - You should have received a copy of the GNU Lesser General Public - License along with nss-mdns; if not, write to the Free Software - Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 - USA. -***/ - #include /* Maximum number of entries to return */ diff --git a/src/gns/nss/uninstall-nss-plugin.sh b/src/gns/nss/uninstall-nss-plugin.sh new file mode 100755 index 0000000..61c8eff --- /dev/null +++ b/src/gns/nss/uninstall-nss-plugin.sh @@ -0,0 +1,8 @@ +#!/bin/bash +# $1 - shell +# $2 - top_builddir +# $3 - nssdir+path of library to remove +# $4 - sudo binary (empty if root) +$4 $1 $2/libtool --mode=uninstall $3 + + diff --git a/src/gns/plugin_block_gns.c b/src/gns/plugin_block_gns.c index 5d986ce..50ad012 100644 --- a/src/gns/plugin_block_gns.c +++ b/src/gns/plugin_block_gns.c @@ -1,6 +1,6 @@ /* This file is part of GNUnet - (C) 2010 Christian Grothoff (and other contributing authors) + (C) 2010, 2012 Christian Grothoff (and other contributing authors) GNUnet is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published @@ -29,6 +29,7 @@ #include "gnunet_namestore_service.h" #include "block_gns.h" #include "gnunet_signatures.h" +#include "gns_common.h" /** * Number of bits we set per entry in the bloomfilter. @@ -56,24 +57,25 @@ */ static enum GNUNET_BLOCK_EvaluationResult block_plugin_gns_evaluate (void *cls, enum GNUNET_BLOCK_Type type, - const GNUNET_HashCode * query, + const struct GNUNET_HashCode * query, struct GNUNET_CONTAINER_BloomFilter **bf, int32_t bf_mutator, const void *xquery, size_t xquery_size, const void *reply_block, size_t reply_block_size) { - char* name; - GNUNET_HashCode pkey_hash_double; - GNUNET_HashCode query_key; - GNUNET_HashCode name_hash_double; - GNUNET_HashCode mhash; - GNUNET_HashCode chash; + const struct GNSNameRecordBlock *nrb; + const char* name; + const char *name_end; + const char *rd_data; + struct GNUNET_HashCode query_key; + struct GNUNET_HashCode mhash; + struct GNUNET_HashCode chash; struct GNUNET_CRYPTO_ShortHashCode pkey_hash; - struct GNUNET_CRYPTO_ShortHashCode name_hash; - struct GNSNameRecordBlock *nrb; + struct GNUNET_CRYPTO_HashAsciiEncoded xor_exp; + struct GNUNET_CRYPTO_HashAsciiEncoded xor_got; uint32_t rd_count; - char* rd_data = NULL; - int rd_len; + size_t rd_len; + size_t name_len; uint32_t record_xquery; unsigned int record_match; @@ -97,21 +99,20 @@ block_plugin_gns_evaluate (void *cls, enum GNUNET_BLOCK_Type type, /* this is a reply */ - nrb = (struct GNSNameRecordBlock *)reply_block; - name = (char*)&nrb[1]; - GNUNET_CRYPTO_short_hash(&nrb->public_key, - sizeof(nrb->public_key), - &pkey_hash); - - GNUNET_CRYPTO_short_hash(name, strlen(name), &name_hash); - - GNUNET_CRYPTO_short_hash_double(&name_hash, &name_hash_double); - GNUNET_CRYPTO_short_hash_double(&pkey_hash, &pkey_hash_double); - - GNUNET_CRYPTO_hash_xor(&pkey_hash_double, &name_hash_double, &query_key); + nrb = (const struct GNSNameRecordBlock *)reply_block; + name = (const char*) &nrb[1]; + name_end = memchr (name, 0, reply_block_size - sizeof (struct GNSNameRecordBlock)); + if (NULL == name_end) + { + GNUNET_break_op (0); + return GNUNET_BLOCK_EVALUATION_RESULT_INVALID; + } + name_len = (name_end - name) + 1; + GNUNET_CRYPTO_short_hash (&nrb->public_key, + sizeof(nrb->public_key), + &pkey_hash); + GNUNET_GNS_get_key_for_record (name, &pkey_hash, &query_key); - struct GNUNET_CRYPTO_HashAsciiEncoded xor_exp; - struct GNUNET_CRYPTO_HashAsciiEncoded xor_got; GNUNET_CRYPTO_hash_to_enc (&query_key, &xor_exp); GNUNET_CRYPTO_hash_to_enc (query, &xor_got); @@ -128,14 +129,14 @@ block_plugin_gns_evaluate (void *cls, enum GNUNET_BLOCK_Type type, record_match = 0; rd_count = ntohl(nrb->rd_count); - rd_data = (char*)&nrb[1]; - rd_data += strlen(name) + 1; - rd_len = reply_block_size - (strlen(name) + 1 + rd_data = &name[name_len]; + rd_len = reply_block_size - (name_len + sizeof(struct GNSNameRecordBlock)); { struct GNUNET_NAMESTORE_RecordData rd[rd_count]; unsigned int i; - struct GNUNET_TIME_Absolute exp = GNUNET_TIME_UNIT_FOREVER_ABS; + uint64_t exp = UINT64_MAX; + struct GNUNET_TIME_Absolute et = GNUNET_TIME_UNIT_FOREVER_ABS; if (GNUNET_SYSERR == GNUNET_NAMESTORE_records_deserialize (rd_len, rd_data, @@ -144,7 +145,6 @@ block_plugin_gns_evaluate (void *cls, enum GNUNET_BLOCK_Type type, { GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, "Data invalid (%d bytes, %d records)\n", rd_len, rd_count); - GNUNET_break_op (0); return GNUNET_BLOCK_EVALUATION_RESULT_INVALID; } @@ -154,32 +154,34 @@ block_plugin_gns_evaluate (void *cls, enum GNUNET_BLOCK_Type type, record_xquery = ntohl(*((uint32_t*)xquery)); for (i=0; ipublic_key, - exp, - name, - rd_count, - rd, - &nrb->signature)) + if (GNUNET_OK != + GNUNET_NAMESTORE_verify_signature (&nrb->public_key, + et, + name, + rd_count, + rd, + &nrb->signature)) { - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, "Signature invalid for name %s\n"); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Signature invalid for %s\n", name); GNUNET_break_op (0); return GNUNET_BLOCK_EVALUATION_RESULT_INVALID; } @@ -187,8 +189,8 @@ block_plugin_gns_evaluate (void *cls, enum GNUNET_BLOCK_Type type, if (NULL != bf) { - GNUNET_CRYPTO_hash(reply_block, reply_block_size, &chash); - GNUNET_BLOCK_mingle_hash(&chash, bf_mutator, &mhash); + GNUNET_CRYPTO_hash (reply_block, reply_block_size, &chash); + GNUNET_BLOCK_mingle_hash (&chash, bf_mutator, &mhash); if (NULL != *bf) { if (GNUNET_YES == GNUNET_CONTAINER_bloomfilter_test(*bf, &mhash)) @@ -218,27 +220,26 @@ block_plugin_gns_evaluate (void *cls, enum GNUNET_BLOCK_Type type, static int block_plugin_gns_get_key (void *cls, enum GNUNET_BLOCK_Type type, const void *block, size_t block_size, - GNUNET_HashCode * key) + struct GNUNET_HashCode * key) { - if (type != GNUNET_BLOCK_TYPE_GNS_NAMERECORD) - return GNUNET_SYSERR; - struct GNUNET_CRYPTO_ShortHashCode name_hash; struct GNUNET_CRYPTO_ShortHashCode pkey_hash; - GNUNET_HashCode name_hash_double; - GNUNET_HashCode pkey_hash_double; - - struct GNSNameRecordBlock *nrb = (struct GNSNameRecordBlock *)block; - - GNUNET_CRYPTO_short_hash(&nrb[1], strlen((char*)&nrb[1]), &name_hash); - GNUNET_CRYPTO_short_hash(&nrb->public_key, - sizeof(struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded), - &pkey_hash); - - GNUNET_CRYPTO_short_hash_double(&name_hash, &name_hash_double); - GNUNET_CRYPTO_short_hash_double(&pkey_hash, &pkey_hash_double); + const struct GNSNameRecordBlock *nrb = block; + const char *name; - GNUNET_CRYPTO_hash_xor(&name_hash_double, &pkey_hash_double, key); - + if (type != GNUNET_BLOCK_TYPE_GNS_NAMERECORD) + return GNUNET_SYSERR; + name = (const char *) &nrb[1]; + if (NULL == memchr (name, '\0', + block_size - sizeof (struct GNSNameRecordBlock))) + { + /* malformed, no 0-termination in name */ + GNUNET_break_op (0); + return GNUNET_SYSERR; + } + GNUNET_CRYPTO_short_hash (&nrb->public_key, + sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded), + &pkey_hash); + GNUNET_GNS_get_key_for_record (name, &pkey_hash, key); return GNUNET_OK; } diff --git a/src/gns/test_gns_cname_lookup.c b/src/gns/test_gns_cname_lookup.c new file mode 100644 index 0000000..6870e89 --- /dev/null +++ b/src/gns/test_gns_cname_lookup.c @@ -0,0 +1,449 @@ +/* + This file is part of GNUnet. + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ +/** + * @file gns/test_gns_cname_lookup.c + * @brief base testcase for testing a local GNS record lookup + * @author Martin Schanzenbach + */ +#include "platform.h" +#include "gnunet_testing_lib.h" +#include "gnunet_core_service.h" +#include "block_dns.h" +#include "gnunet_signatures.h" +#include "gnunet_namestore_service.h" +#include "gnunet_dnsparser_lib.h" +#include "gnunet_gns_service.h" + + +/** + * Timeout for entire testcase + */ +#define TIMEOUT GNUNET_TIME_relative_multiply(GNUNET_TIME_UNIT_SECONDS, 20) + +/* test records to resolve */ +#define TEST_DOMAIN_PLUS "www.gads" +#define TEST_DOMAIN_ZKEY "www2.gads" +#define TEST_DOMAIN_DNS "www3.gads" +#define TEST_IP_PLUS "127.0.0.1" +#define TEST_IP_ZKEY "127.0.0.2" +#define TEST_IP_DNS "131.159.74.67" +#define TEST_RECORD_CNAME_SERVER "server.gads" +#define TEST_RECORD_CNAME_PLUS "server.+" +#define TEST_RECORD_CNAME_ZKEY "www.188JSUMKEF25GVU8TTV0PBNNN8JVCPUEDFV1UHJJU884JD25V0T0.zkey" +#define TEST_RECORD_CNAME_DNS "gnunet.org" +#define TEST_RECORD_NAME_SERVER "server" +#define TEST_RECORD_NAME_PLUS "www" +#define TEST_RECORD_NAME_ZKEY "www2" +#define TEST_RECORD_NAME_DNS "www3" + +#define KEYFILE_BOB "zonefiles/188JSUMKEF25GVU8TTV0PBNNN8JVCPUEDFV1UHJJU884JD25V0T0.zkey" + + +/* Task handle to use to schedule test failure */ +static GNUNET_SCHEDULER_TaskIdentifier die_task; + +/* Global return value (0 for success, anything else for failure) */ +static int ok; + +static struct GNUNET_NAMESTORE_Handle *namestore_handle; + +static struct GNUNET_GNS_Handle *gns_handle; + +static const struct GNUNET_CONFIGURATION_Handle *cfg; + + +/** + * Check if the get_handle is being used, if so stop the request. Either + * way, schedule the end_badly_cont function which actually shuts down the + * test. + */ +static void +end_badly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + die_task = GNUNET_SCHEDULER_NO_TASK; + if (NULL != gns_handle) + { + GNUNET_GNS_disconnect (gns_handle); + gns_handle = NULL; + } + if (NULL != namestore_handle) + { + GNUNET_NAMESTORE_disconnect (namestore_handle); + namestore_handle = NULL; + } + GNUNET_break (0); + GNUNET_SCHEDULER_shutdown (); + ok = 1; +} + + +static void +shutdown_task (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + GNUNET_GNS_disconnect (gns_handle); + gns_handle = NULL; + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Shutting down peer!\n"); + GNUNET_SCHEDULER_shutdown (); +} + + +static void +on_lookup_result_cname (void *cls, + uint32_t rd_count, + const struct GNUNET_NAMESTORE_RecordData *rd) +{ + uint32_t i; + + if (GNUNET_SCHEDULER_NO_TASK != die_task) + { + GNUNET_SCHEDULER_cancel (die_task); + die_task = GNUNET_SCHEDULER_NO_TASK; + } + GNUNET_NAMESTORE_disconnect (namestore_handle); + namestore_handle = NULL; + if (rd_count == 0) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Lookup failed, rp_filtering?\n"); + ok = 2; + } + else + { + ok = 1; + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "name: %s\n", (char*)cls); + for (i=0; i bob <-----> dave + * + * alice queries for www.buddy.bob.gads + * + */ +#include "platform.h" +#include "gnunet_common.h" +#include "gnunet_disk_lib.h" +#include "gnunet_testing_lib.h" +#include "gnunet_testbed_service.h" +#include "gnunet_core_service.h" +#include "gnunet_dht_service.h" +#include "block_dns.h" +#include "gnunet_signatures.h" +#include "gnunet_namestore_service.h" +#include "gnunet_dnsparser_lib.h" +#include "gnunet_gns_service.h" + +#define ZONE_PUT_WAIT_TIME GNUNET_TIME_relative_multiply(GNUNET_TIME_UNIT_SECONDS, 10) + +#define TEST_DOMAIN "www.buddy.bob.gads" +#define TEST_IP "1.1.1.1" +#define TEST_DAVE_PSEU "hagbard" + + +/* Timeout for entire testcase */ +#define TIMEOUT GNUNET_TIME_relative_multiply(GNUNET_TIME_UNIT_SECONDS, 60) +#define SETUP_TIMEOUT GNUNET_TIME_relative_multiply(GNUNET_TIME_UNIT_SECONDS, 60) + +/* Global return value (0 for success, anything else for failure) */ +static int ok; + +/* Task handle to use to schedule test failure */ +static GNUNET_SCHEDULER_TaskIdentifier die_task; + +static GNUNET_SCHEDULER_TaskIdentifier wait_task; + +static GNUNET_SCHEDULER_TaskIdentifier setup_task; + +static struct GNUNET_CRYPTO_ShortHashCode dave_hash; + +static struct GNUNET_CRYPTO_ShortHashCode bob_hash; + +static struct GNUNET_TESTBED_Peer **cpeers; + +static struct GNUNET_GNS_Handle *gh; +static struct GNUNET_GNS_LookupRequest *lookup_handle; + +static struct GNUNET_TESTBED_Operation *get_cfg_ops[3]; +static struct GNUNET_TESTBED_Operation *topology_op; +static struct GNUNET_CONFIGURATION_Handle *cfg_handles[3]; +static struct GNUNET_NAMESTORE_Handle *nh[3]; + +static int dave_is_setup; +static int bob_is_setup; +static int alice_is_setup; + +/** + * Check if the get_handle is being used, if so stop the request. Either + * way, schedule the end_badly_cont function which actually shuts down the + * test. + */ +static void +end_badly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + die_task = GNUNET_SCHEDULER_NO_TASK; + int c; + + if (GNUNET_SCHEDULER_NO_TASK != wait_task) + { + GNUNET_SCHEDULER_cancel (wait_task); + wait_task = GNUNET_SCHEDULER_NO_TASK; + } + + for (c = 0; c < 3; c++) + { + if (NULL != nh[c]) + { + GNUNET_NAMESTORE_disconnect(nh[c]); + nh[c] = NULL; + } + + if (NULL != get_cfg_ops[c]) + { + GNUNET_TESTBED_operation_done(get_cfg_ops[c]); + get_cfg_ops[c] = NULL; + } + if (NULL != cfg_handles[c]) + { + GNUNET_CONFIGURATION_destroy (cfg_handles[c]); + cfg_handles[c] = NULL; + } + } + if (NULL != topology_op) + { + GNUNET_TESTBED_operation_done (topology_op); + topology_op = NULL; + } + if (NULL != lookup_handle) + { + GNUNET_GNS_cancel_lookup_request (lookup_handle); + lookup_handle = NULL; + } + if (NULL != gh) + { + GNUNET_GNS_disconnect(gh); + gh = NULL; + } + + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Test failed \n"); + GNUNET_SCHEDULER_shutdown (); + ok = 1; +} + +static void +end (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Finished\n"); + int c; + if (GNUNET_SCHEDULER_NO_TASK != die_task) + { + GNUNET_SCHEDULER_cancel (die_task); + die_task = GNUNET_SCHEDULER_NO_TASK; + } + + for (c = 0; c < 3; c++) + { + if (NULL != nh[c]) + { + GNUNET_NAMESTORE_disconnect(nh[c]); + nh[c] = NULL; + } + if (NULL != cfg_handles[c]) + { + GNUNET_CONFIGURATION_destroy (cfg_handles[c]); + cfg_handles[c] = NULL; + } + } + + if (NULL != gh) + { + GNUNET_GNS_disconnect(gh); + gh = NULL; + } + + if (0 == ok) + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Test ended successful\n"); + else + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Test failed\n"); + GNUNET_SCHEDULER_shutdown (); +} + +static void +setup_end_badly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + setup_task = GNUNET_SCHEDULER_NO_TASK; + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Timeout during setup, test failed\n"); + + if (NULL != topology_op) + { + GNUNET_TESTBED_operation_done (topology_op); + topology_op = NULL; + } + GNUNET_SCHEDULER_shutdown (); + ok = GNUNET_SYSERR; +} + +static void +end_now () +{ + GNUNET_SCHEDULER_add_now (&end, NULL); +} + + +static void +disconnect_ns (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + + GNUNET_NAMESTORE_disconnect (cls); + if (cls == nh[0]) + nh[0] = NULL; + if (cls == nh[1]) + nh[1] = NULL; + if (cls == nh[2]) + nh[2] = NULL; +} + + +static void +cont_ns (void* cls, int32_t s, const char* emsg) +{ + GNUNET_SCHEDULER_add_now (&disconnect_ns, cls); +} + +static void +on_lookup_result(void *cls, uint32_t rd_count, + const struct GNUNET_NAMESTORE_RecordData *rd) +{ + int i; + char* string_val; + + if (rd_count == 0) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Lookup failed!\n"); + ok = 2; + } + else + { + ok = 1; + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "name: %s\n", (char*)cls); + for (i=0; ipit); + if (GNUNET_NO == dave_is_setup) + res = setup_dave (pinfo->result.cfg); + else if (GNUNET_NO == bob_is_setup) + res = setup_bob (pinfo->result.cfg); + else + res = setup_alice (pinfo->result.cfg); + + if (get_cfg_ops[0] == op) + get_cfg_ops[0] = NULL; + else if (get_cfg_ops[1] == op) + get_cfg_ops[1] = NULL; + else + get_cfg_ops[2] = NULL; + GNUNET_TESTBED_operation_done (op); + op = NULL; + if (GNUNET_SYSERR == res) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Failed to setup peer \n"); + end_badly_now(); + } + else + connect_peers (); + /*if (get_cfg_ops[0] == op) + { + GNUNET_assert (GNUNET_TESTBED_PIT_CONFIGURATION == pinfo->pit); + res = setup_dave (pinfo->result.cfg); + GNUNET_TESTBED_operation_done (get_cfg_ops[0]); + get_cfg_ops[0] = NULL; + if (GNUNET_SYSERR == res) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Failed to setup dave \n"); + end_badly_now(); + } + else + { + connect_peers (); + } + } + else if (get_cfg_ops[1] == op) + { + GNUNET_assert (GNUNET_TESTBED_PIT_CONFIGURATION == pinfo->pit); + res = setup_bob (pinfo->result.cfg); + GNUNET_TESTBED_operation_done (get_cfg_ops[1]); + get_cfg_ops[1] = NULL; + if (GNUNET_SYSERR == res) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Failed to setup dave \n"); + end_badly_now(); + } + else + { + connect_peers (); + } + } + else if (get_cfg_ops[2] == op) + { + GNUNET_assert (GNUNET_TESTBED_PIT_CONFIGURATION == pinfo->pit); + res = setup_alice (pinfo->result.cfg); + GNUNET_TESTBED_operation_done (get_cfg_ops[2]); + get_cfg_ops[2] = NULL; + if (GNUNET_SYSERR == res) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Failed to setup dave \n"); + end_badly_now(); + } + else + { + connect_peers (); + } + }*/ +} + + +void testbed_master (void *cls, + unsigned int num_peers, + struct GNUNET_TESTBED_Peer **peers) +{ + GNUNET_assert (NULL != peers); + cpeers = peers; + + setup_task = GNUNET_SCHEDULER_add_delayed (SETUP_TIMEOUT, &setup_end_badly, NULL); + + /* peer 0: dave */ + GNUNET_assert (NULL != peers[0]); + get_cfg_ops[0] = GNUNET_TESTBED_peer_get_information (peers[0], + GNUNET_TESTBED_PIT_CONFIGURATION, + &peerinfo_cb, NULL); + + /* peer 1: bob */ + GNUNET_assert (NULL != peers[1]); + get_cfg_ops[1] = GNUNET_TESTBED_peer_get_information (peers[1], + GNUNET_TESTBED_PIT_CONFIGURATION, + &peerinfo_cb, NULL ); + + /* peer 2: alice */ + GNUNET_assert (NULL != peers[2]); + get_cfg_ops[2] = GNUNET_TESTBED_peer_get_information (peers[2], + GNUNET_TESTBED_PIT_CONFIGURATION, + &peerinfo_cb, NULL); + +} + +void testbed_controller_cb (void *cls, const struct GNUNET_TESTBED_EventInformation *event) +{ + static int connections = 0; + + switch (event->type) + { + case GNUNET_TESTBED_ET_OPERATION_FINISHED: + /* This part will still be called when + GNUNET_TESTBED_peer_get_information() succeeds. However, the code is + now more relevant in operation completion callback */ + break; + case GNUNET_TESTBED_ET_CONNECT: + connections ++; + if (connections == 3) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "All peers connected\n"); + GNUNET_TESTBED_operation_done (topology_op); + topology_op = NULL; + all_connected (); + } + break; + default: + /* whatever ... */ + break; + } +} + +int +main (int argc, char *argv[]) +{ + uint64_t event_mask; + ok = 0; + event_mask = 0; + event_mask |= (1LL << GNUNET_TESTBED_ET_CONNECT); + event_mask |= (1LL << GNUNET_TESTBED_ET_OPERATION_FINISHED); + (void) GNUNET_TESTBED_test_run ("test_gns_dht_three_peers", "test_gns_dht_default.conf", + 3, event_mask, + &testbed_controller_cb, NULL, + &testbed_master, NULL); + if (GNUNET_SYSERR == ok) + return 1; + return 0; +} + +/* end of test_gns_dht_three_peers.c */ + diff --git a/src/gns/test_gns_dht_threepeer.c b/src/gns/test_gns_dht_threepeer.c deleted file mode 100644 index ed9600f..0000000 --- a/src/gns/test_gns_dht_threepeer.c +++ /dev/null @@ -1,524 +0,0 @@ -/* - This file is part of GNUnet. - (C) 2009 Christian Grothoff (and other contributing authors) - - GNUnet is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published - by the Free Software Foundation; either version 3, or (at your - option) any later version. - - GNUnet is distributed in the hope that it will be useful, but - WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - General Public License for more details. - - You should have received a copy of the GNU General Public License - along with GNUnet; see the file COPYING. If not, write to the - Free Software Foundation, Inc., 59 Temple Place - Suite 330, - Boston, MA 02111-1307, USA. -*/ -/** - * @file gns/test_gns_dht_threepeer.c - * @brief tests dht lookup over 3 peers - * - * topology: - * alice <----> bob <-----> dave - * - * alice queries for www.buddy.bob.gnunet - * - */ -#include "platform.h" -#include "gnunet_disk_lib.h" -#include "gnunet_testing_lib.h" -#include "gnunet_core_service.h" -#include "gnunet_dht_service.h" -#include "block_dns.h" -#include "gnunet_signatures.h" -#include "gnunet_namestore_service.h" -#include "gnunet_dnsparser_lib.h" -#include "gnunet_gns_service.h" - -/* DEFINES */ -#define VERBOSE GNUNET_YES - -/* Timeout for entire testcase */ -#define TIMEOUT GNUNET_TIME_relative_multiply(GNUNET_TIME_UNIT_SECONDS, 180) -#define ZONE_PUT_WAIT_TIME GNUNET_TIME_relative_multiply(GNUNET_TIME_UNIT_SECONDS, 30) - -/* If number of peers not in config file, use this number */ -#define DEFAULT_NUM_PEERS 2 - -#define TEST_DOMAIN "www.buddy.bob.gnunet" -#define TEST_IP "1.1.1.1" -#define TEST_DAVE_PSEU "hagbard" -#define TEST_NUM_PEERS 3 -#define TEST_NUM_CON 3 - -/* Globals */ - -/** - * Directory to store temp data in, defined in config file - */ -static char *test_directory; - -/** - * Variable used to store the number of connections we should wait for. - */ -static unsigned int expected_connections; - -/** - * Variable used to keep track of how many peers aren't yet started. - */ -static unsigned long long peers_left; - -struct GNUNET_TESTING_Daemon *d1; -struct GNUNET_TESTING_Daemon *d2; -struct GNUNET_TESTING_Daemon *d3; - - -/** - * Total number of peers to run, set based on config file. - */ -static unsigned long long num_peers; - -/** - * Global used to count how many connections we have currently - * been notified about (how many times has topology_callback been called - * with success?) - */ -static unsigned int total_connections; - -/** - * Global used to count how many failed connections we have - * been notified about (how many times has topology_callback - * been called with failure?) - */ -static unsigned int failed_connections; - -/* Task handle to use to schedule test failure */ -GNUNET_SCHEDULER_TaskIdentifier die_task; - -GNUNET_SCHEDULER_TaskIdentifier bob_task; - -/* Global return value (0 for success, anything else for failure) */ -static int ok; - -int bob_online, alice_online, dave_online; - -const struct GNUNET_CONFIGURATION_Handle *alice_cfg; -struct GNUNET_CONFIGURATION_Handle *cfg_bob; -struct GNUNET_CONFIGURATION_Handle *cfg_dave; - -struct GNUNET_CRYPTO_ShortHashCode bob_hash; -struct GNUNET_CRYPTO_ShortHashCode dave_hash; -struct GNUNET_TESTING_Daemon *alice_daemon; -struct GNUNET_TESTING_Daemon *bob_daemon; -struct GNUNET_TESTING_Daemon *dave_daemon; - -struct GNUNET_TESTING_PeerGroup *pg; -struct GNUNET_GNS_Handle *gh; - -/** - * Function scheduled to be run on the successful completion of this - * testcase. Specifically, called when our get request completes. - */ -static void -finish_testing (void *cls, const char *emsg) -{ - GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Test finished! (ret=%d)\n", ok); -} - -/** - * Continuation for the GNUNET_DHT_get_stop call, so that we don't shut - * down the peers without freeing memory associated with GET request. - */ -static void -end_badly_cont (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - die_task = GNUNET_SCHEDULER_NO_TASK; - GNUNET_TESTING_daemons_stop (pg, TIMEOUT, &finish_testing, NULL); -} - -/** - * Check if the get_handle is being used, if so stop the request. Either - * way, schedule the end_badly_cont function which actually shuts down the - * test. - */ -static void -end_badly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - die_task = GNUNET_SCHEDULER_NO_TASK; - GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Failing test with error: `%s'!\n", - (char *) cls); - die_task = GNUNET_SCHEDULER_add_now (&end_badly_cont, NULL); - ok = 1; -} - - -static void -on_lookup_result(void *cls, uint32_t rd_count, - const struct GNUNET_NAMESTORE_RecordData *rd) -{ - int i; - char* string_val; - const char* typename; - - if (rd_count == 0) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "Lookup failed!\n"); - ok = 2; - } - else - { - ok = 1; - GNUNET_log (GNUNET_ERROR_TYPE_INFO, "name: %s\n", (char*)cls); - for (i=0; ishortname, second_daemon->shortname, distance); -#endif - } -#if VERBOSE - else - { - failed_connections++; - GNUNET_log (GNUNET_ERROR_TYPE_INFO, - "Failed to connect peer %s to peer %s with error :\n%s\n", - first_daemon->shortname, second_daemon->shortname, emsg); - } -#endif - - if (total_connections == expected_connections) - { -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_INFO, - "Created %d total connections, which is our target number! Starting next phase of testing.\n", - total_connections); -#endif - GNUNET_SCHEDULER_cancel (die_task); - die_task = GNUNET_SCHEDULER_NO_TASK; - //die_task = - // GNUNET_SCHEDULER_add_delayed (TIMEOUT, &end_badly, "from connect"); - - //commence_testing(); - - } - else if (total_connections + failed_connections == expected_connections) - { - GNUNET_SCHEDULER_cancel (die_task); - die_task = - GNUNET_SCHEDULER_add_now (&end_badly, - "from topology_callback (too many failed connections)"); - } -} - -void -all_connected(void *cls, const char *emsg) -{ - GNUNET_log (GNUNET_ERROR_TYPE_INFO, - "Created all connections! Starting next phase of testing.\n"); - GNUNET_SCHEDULER_add_delayed (ZONE_PUT_WAIT_TIME, &commence_testing, NULL); -} - -void -ns_create_cont(void *cls, int32_t s, const char *emsg) -{ - GNUNET_NAMESTORE_disconnect((struct GNUNET_NAMESTORE_Handle *)cls, 0); -} - -static void -daemon_started (void *cls, const struct GNUNET_PeerIdentity *id, - const struct GNUNET_CONFIGURATION_Handle *cfg, - struct GNUNET_TESTING_Daemon *d, const char *emsg) -{ - struct GNUNET_NAMESTORE_Handle *ns; - char* keyfile; - struct GNUNET_CRYPTO_RsaPrivateKey *key; - struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded pkey; - struct in_addr *web; - struct GNUNET_NAMESTORE_RecordData rd; - - rd.flags = GNUNET_NAMESTORE_RF_AUTHORITY | GNUNET_NAMESTORE_RF_NONE; - rd.expiration = GNUNET_TIME_UNIT_FOREVER_ABS; - - if (NULL == dave_daemon) - { - if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_filename (cfg, "gns", - "ZONEKEY", - &keyfile)) - { - GNUNET_log(GNUNET_ERROR_TYPE_ERROR, "Failed to get key from cfg\n"); - ok = -1; - return; - } - dave_daemon = d; - - key = GNUNET_CRYPTO_rsa_key_create_from_file (keyfile); - - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, "This is now dave\n"); - ns = GNUNET_NAMESTORE_connect(cfg); - - GNUNET_CRYPTO_rsa_key_get_public (key, &pkey); - GNUNET_CRYPTO_short_hash(&pkey, sizeof(pkey), &dave_hash); - - web = GNUNET_malloc(sizeof(struct in_addr)); - GNUNET_assert(1 == inet_pton (AF_INET, TEST_IP, web)); - rd.data_size = sizeof(struct in_addr); - rd.data = web; - rd.record_type = GNUNET_GNS_RECORD_TYPE_A; - - GNUNET_NAMESTORE_record_create (ns, key, "www", &rd, NULL, NULL); - - rd.data_size = strlen(TEST_DAVE_PSEU); - rd.data = TEST_DAVE_PSEU; - rd.record_type = GNUNET_GNS_RECORD_PSEU; - - GNUNET_NAMESTORE_record_create (ns, key, "+", &rd, ns_create_cont, ns); - - GNUNET_CRYPTO_rsa_key_free(key); - GNUNET_free(keyfile); - GNUNET_free(web); - - return; - } - - - if (NULL == bob_daemon) - { - if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_filename (cfg, "gns", - "ZONEKEY", - &keyfile)) - { - GNUNET_log(GNUNET_ERROR_TYPE_ERROR, "Failed to get key from cfg\n"); - ok = -1; - return; - } - bob_daemon = d; - - key = GNUNET_CRYPTO_rsa_key_create_from_file (keyfile); - - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, "This is now bob\n"); - ns = GNUNET_NAMESTORE_connect(cfg); - - GNUNET_CRYPTO_rsa_key_get_public (key, &pkey); - GNUNET_CRYPTO_short_hash(&pkey, sizeof(pkey), &bob_hash); - - rd.data_size = sizeof(struct GNUNET_CRYPTO_ShortHashCode); - rd.data = &dave_hash; - rd.record_type = GNUNET_GNS_RECORD_PKEY; - - GNUNET_NAMESTORE_record_create (ns, key, "buddy", &rd, ns_create_cont, ns); - - GNUNET_CRYPTO_rsa_key_free(key); - GNUNET_free(keyfile); - - return; - } - - - - if (NULL == alice_daemon) - { - - if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_filename (cfg, "gns", - "ZONEKEY", - &keyfile)) - { - GNUNET_log(GNUNET_ERROR_TYPE_ERROR, "Failed to get key from cfg\n"); - ok = -1; - return; - } - alice_daemon = d; - alice_cfg = cfg; - - key = GNUNET_CRYPTO_rsa_key_create_from_file (keyfile); - - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, "This is now alice\n"); - ns = GNUNET_NAMESTORE_connect(cfg); - - rd.data_size = sizeof(struct GNUNET_CRYPTO_ShortHashCode); - rd.data = &bob_hash; - rd.record_type = GNUNET_GNS_RECORD_PKEY; - - GNUNET_NAMESTORE_record_create (ns, key, "bob", &rd, ns_create_cont, ns); - - GNUNET_CRYPTO_rsa_key_free(key); - GNUNET_free(keyfile); - - GNUNET_TESTING_connect_topology (pg, GNUNET_TESTING_TOPOLOGY_CLIQUE, - GNUNET_TESTING_TOPOLOGY_OPTION_ALL, - 0, - TIMEOUT, - 3, - &all_connected, NULL); - return; - - } - - - - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, "This is a random guy\n"); -} - -static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) -{ - - /* Get path from configuration file */ - if (GNUNET_YES != - GNUNET_CONFIGURATION_get_value_string (cfg, "paths", "servicehome", - &test_directory)) - { - ok = 404; - return; - } - - GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, "starting\n"); - - /* Get number of peers to start from configuration (should be two) */ - if (GNUNET_SYSERR == - GNUNET_CONFIGURATION_get_value_number (cfg, "testing", "num_peers", - &num_peers)) - num_peers = DEFAULT_NUM_PEERS; - - /* Set peers_left so we know when all peers started */ - peers_left = num_peers; - - bob_daemon = NULL; - dave_daemon = NULL; - alice_daemon = NULL; - - pg = GNUNET_TESTING_daemons_start (cfg, TEST_NUM_PEERS, TEST_NUM_CON, - TEST_NUM_CON, TIMEOUT, NULL, NULL, &daemon_started, NULL, - &daemon_connected, NULL, NULL); - - /* Set up a task to end testing if peer start fails */ - die_task = - GNUNET_SCHEDULER_add_delayed (TIMEOUT, &end_badly, - "didn't start all daemons in reasonable amount of time!!!"); - - alice_online = 0; - bob_online = 0; - dave_online = 0; - expected_connections = 2; - - /* Start alice */ - //d1 = GNUNET_TESTING_daemon_start(cfg_alice, TIMEOUT, GNUNET_NO, NULL, NULL, 0, - // NULL, NULL, NULL, &alice_started, NULL); - - - - -} - -static int -check () -{ - int ret; - - /* Arguments for GNUNET_PROGRAM_run */ - char *const argv[] = { "test-gns-twopeer", /* Name to give running binary */ - "-c", - "test_gns_dht_default.conf", /* Config file to use */ -#if VERBOSE - "-L", "DEBUG", -#endif - NULL - }; - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - /* Run the run function as a new program */ - ret = - GNUNET_PROGRAM_run ((sizeof (argv) / sizeof (char *)) - 1, argv, - "test-gns-threepeer", "nohelp", options, &run, - &ok); - if (ret != GNUNET_OK) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "`test-gns-threepeer': Failed with error code %d\n", ret); - } - return ok; -} - -int -main (int argc, char *argv[]) -{ - int ret; - - GNUNET_log_setup ("test-gns-threepeer", -#if VERBOSE - "DEBUG", -#else - "WARNING", -#endif - NULL); - ret = check (); - /** - * Need to remove base directory, subdirectories taken care - * of by the testing framework. - */ - return ret; -} - -/* end of test_gns_threepeer.c */ diff --git a/src/gns/test_gns_max_queries.c b/src/gns/test_gns_max_queries.c index ad1743c..00caf83 100644 --- a/src/gns/test_gns_max_queries.c +++ b/src/gns/test_gns_max_queries.c @@ -32,18 +32,13 @@ #include "gnunet_dnsparser_lib.h" #include "gnunet_gns_service.h" -/* DEFINES */ -#define VERBOSE GNUNET_YES /* Timeout for entire testcase */ #define TIMEOUT GNUNET_TIME_relative_multiply(GNUNET_TIME_UNIT_SECONDS, 20) -/* If number of peers not in config file, use this number */ -#define DEFAULT_NUM_PEERS 2 - /* test records to resolve */ -#define TEST_DOMAIN "www.gnunet" -#define TEST_DOMAIN_NACK "doesnotexist.bob.gnunet" +#define TEST_DOMAIN "www.gads" +#define TEST_DOMAIN_NACK "doesnotexist.bob.gads" #define TEST_IP "127.0.0.1" #define TEST_RECORD_NAME "www" #define TEST_ADDITIONAL_LOOKUPS 5 @@ -51,17 +46,8 @@ #define KEYFILE_BOB "../namestore/zonefiles/HGU0A0VCU334DN7F2I9UIUMVQMM7JMSD142LIMNUGTTV9R0CF4EG.zkey" -/* Globals */ - -/** - * Directory to store temp data in, defined in config file - */ -static char *test_directory; - -static struct GNUNET_TESTING_PeerGroup *pg; - /* Task handle to use to schedule test failure */ -GNUNET_SCHEDULER_TaskIdentifier die_task; +static GNUNET_SCHEDULER_TaskIdentifier die_task; /* Global return value (0 for success, anything else for failure) */ static int ok; @@ -70,30 +56,89 @@ static struct GNUNET_NAMESTORE_Handle *namestore_handle; static struct GNUNET_GNS_Handle *gns_handle; -const struct GNUNET_CONFIGURATION_Handle *cfg; +static const struct GNUNET_CONFIGURATION_Handle *cfg; static unsigned long long max_parallel_lookups; +static struct GNUNET_GNS_LookupRequest **requests; + +static unsigned int num_requests; + + /** - * Check whether peers successfully shut down. + * Check if the get_handle is being used, if so stop the request. Either + * way, schedule the end_badly_cont function which actually shuts down the + * test. */ -void -shutdown_callback (void *cls, const char *emsg) +static void +end_badly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { - if (emsg != NULL) + unsigned int i; + + for (i=0;isin_addr))) + { + resolver_working = GNUNET_YES; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Resolver is working\n"); + } + } +} + + +/** + * Function scheduled to be run on the successful start of services + * tries to look up the dns record for TEST_DOMAIN + */ +static void +commence_testing (void *cls, int32_t success, const char *emsg) +{ + resolver_working = GNUNET_NO; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Resolving NS record\n"); + GNUNET_RESOLVER_connect (cfg); + resolver_handle = GNUNET_RESOLVER_ip_get (TEST_RECORD_NS, + AF_INET, + TIMEOUT, + &handle_dns_test, + NULL); +} + + +static void +do_check (void *cls, + const struct GNUNET_CONFIGURATION_Handle *ccfg, + struct GNUNET_TESTING_Peer *peer) +{ + struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded alice_pkey; + struct GNUNET_CRYPTO_RsaPrivateKey *alice_key; + char* alice_keyfile; + struct GNUNET_NAMESTORE_RecordData rd; + const char* ip = TEST_IP_NS; + struct in_addr ns; + + cfg = ccfg; + die_task = GNUNET_SCHEDULER_add_delayed (TIMEOUT, &end_badly, NULL); + + /* put records into namestore */ + namestore_handle = GNUNET_NAMESTORE_connect(cfg); + if (NULL == namestore_handle) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Failed to connect to namestore\n"); + end_badly_now (); + return; + } + + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_filename (cfg, "gns", + "ZONEKEY", + &alice_keyfile)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Failed to get key from cfg\n"); + end_badly_now (); + return; + } + + alice_key = GNUNET_CRYPTO_rsa_key_create_from_file (alice_keyfile); + GNUNET_CRYPTO_rsa_key_get_public (alice_key, &alice_pkey); + GNUNET_free(alice_keyfile); + + rd.expiration_time = UINT64_MAX; + GNUNET_assert(1 == inet_pton (AF_INET, ip, &ns)); + rd.data_size = sizeof(struct in_addr); + rd.data = &ns; + rd.record_type = GNUNET_DNSPARSER_TYPE_A; + rd.flags = GNUNET_NAMESTORE_RF_AUTHORITY; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Creating records\n"); + GNUNET_NAMESTORE_record_create (namestore_handle, + alice_key, + TEST_RECORD_NAME, + &rd, + NULL, + NULL); + rd.data_size = strlen (TEST_RECORD_NS); + rd.data = TEST_RECORD_NS; + rd.record_type = GNUNET_GNS_RECORD_NS; + GNUNET_NAMESTORE_record_create (namestore_handle, + alice_key, + TEST_RECORD_NAME, + &rd, + &commence_testing, + NULL); + GNUNET_CRYPTO_rsa_key_free(alice_key); +} + + +int +main (int argc, char *argv[]) +{ + ok = 1; + GNUNET_log_setup ("test-gns-simple-ns-lookup", + "WARNING", + NULL); + GNUNET_TESTING_peer_run ("test-gns-simple-ns-lookup", "test_gns_simple_lookup.conf", + &do_check, NULL); + return ok; +} + +/* end of test_gns_ns_lookup.c */ diff --git a/src/gns/test_gns_pseu_shorten.c b/src/gns/test_gns_pseu_shorten.c index 3c2d204..5e2f1fc 100644 --- a/src/gns/test_gns_pseu_shorten.c +++ b/src/gns/test_gns_pseu_shorten.c @@ -33,44 +33,33 @@ #include "gnunet_dht_service.h" #include "gnunet_gns_service.h" -/* DEFINES */ -#define VERBOSE GNUNET_YES - /* Timeout for entire testcase */ -#define TIMEOUT GNUNET_TIME_relative_multiply(GNUNET_TIME_UNIT_SECONDS, 5) - -/* If number of peers not in config file, use this number */ -#define DEFAULT_NUM_PEERS 2 +#define TIMEOUT GNUNET_TIME_relative_multiply(GNUNET_TIME_UNIT_SECONDS, 30) /* test records to resolve */ -#define TEST_DOMAIN "www.alice.bob.gnunet" +#define TEST_DOMAIN "www.alicewonderland.bobbuilder.gads" #define TEST_IP "127.0.0.1" #define TEST_RECORD_NAME "www" -#define TEST_AUTHORITY_BOB "bob" -#define TEST_AUTHORITY_ALICE "alice" +#define TEST_PRIVATE_ZONE "private" +#define TEST_SHORTEN_ZONE "short" +#define TEST_AUTHORITY_BOB "bobbuilder" +#define TEST_AUTHORITY_ALICE "alicewonderland" #define TEST_PSEU_ALICE "carol" -#define TEST_EXPECTED_RESULT "www.carol.gnunet" +#define TEST_EXPECTED_RESULT "www.carol.short.private.gads" #define DHT_OPERATION_TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 30) +#define KEYFILE_SHORTEN = "zonefiles/188JSUMKEF25GVU8TTV0PBNNN8JVCPUEDFV1UHJJU884JD25V0T0.zkey" +#define KEYFILE_PRIVATE = "zonefiles/OEFL7A4VEF1B40QLEMTG5D8G1CN6EN16QUSG5R2DT71GRJN34LSG.zkey" #define KEYFILE_BOB "../namestore/zonefiles/HGU0A0VCU334DN7F2I9UIUMVQMM7JMSD142LIMNUGTTV9R0CF4EG.zkey" #define KEYFILE_ALICE "../namestore/zonefiles/N0UJMP015AFUNR2BTNM3FKPBLG38913BL8IDMCO2H0A1LIB81960.zkey" /* Globals */ -/** - * Directory to store temp data in, defined in config file - */ -static char *test_directory; - -static struct GNUNET_TESTING_PeerGroup *pg; - /* Task handle to use to schedule test failure */ static GNUNET_SCHEDULER_TaskIdentifier die_task; -static GNUNET_SCHEDULER_TaskIdentifier disco_task; - /* Global return value (0 for success, anything else for failure) */ static int ok; @@ -80,47 +69,73 @@ static struct GNUNET_GNS_Handle *gns_handle; static struct GNUNET_DHT_Handle *dht_handle; -const struct GNUNET_CONFIGURATION_Handle *cfg; +static const struct GNUNET_CONFIGURATION_Handle *cfg; + +static struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded alice_pkey; +static struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded bob_pkey; +static struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded our_pkey; +static struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded priv_pkey; +static struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded short_pkey; +static struct GNUNET_CRYPTO_RsaPrivateKey *alice_key; +static struct GNUNET_CRYPTO_RsaPrivateKey *bob_key; +static struct GNUNET_CRYPTO_RsaPrivateKey *our_key; +static struct GNUNET_CRYPTO_RsaPrivateKey *priv_key; +static struct GNUNET_CRYPTO_RsaPrivateKey *short_key; +static struct GNUNET_CRYPTO_ShortHashCode alice_hash; +static struct GNUNET_CRYPTO_ShortHashCode bob_hash; +static struct GNUNET_CRYPTO_ShortHashCode our_zone; +static struct GNUNET_CRYPTO_ShortHashCode priv_zone; +static struct GNUNET_CRYPTO_ShortHashCode short_zone; -struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded alice_pkey; -struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded bob_pkey; -struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded our_pkey; -struct GNUNET_CRYPTO_RsaPrivateKey *alice_key; -struct GNUNET_CRYPTO_RsaPrivateKey *bob_key; -struct GNUNET_CRYPTO_RsaPrivateKey *our_key; -struct GNUNET_CRYPTO_ShortHashCode alice_hash; -struct GNUNET_CRYPTO_ShortHashCode bob_hash; /** - * Check whether peers successfully shut down. + * Check if the get_handle is being used, if so stop the request. Either + * way, schedule the end_badly_cont function which actually shuts down the + * test. */ -void -shutdown_callback (void *cls, const char *emsg) +static void +end_badly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { - if (disco_task != GNUNET_SCHEDULER_NO_TASK) + die_task = GNUNET_SCHEDULER_NO_TASK; + if (NULL != gns_handle) { - disco_task = GNUNET_SCHEDULER_NO_TASK; - GNUNET_SCHEDULER_cancel(disco_task); - GNUNET_DHT_disconnect(dht_handle); - dht_handle = NULL; + GNUNET_GNS_disconnect(gns_handle); + gns_handle = NULL; + } + + if (NULL != namestore_handle) + { + GNUNET_NAMESTORE_disconnect (namestore_handle); + namestore_handle = NULL; } - if (emsg != NULL) + if (NULL != dht_handle) { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Error on shutdown! ret=%d\n", ok); - if (ok == 0) - ok = 2; + GNUNET_DHT_disconnect (dht_handle); + dht_handle = NULL; } - GNUNET_log (GNUNET_ERROR_TYPE_INFO, "done(ret=%d)!\n", ok); + GNUNET_break (0); + GNUNET_SCHEDULER_shutdown (); + ok = 1; } + static void -disco_dht(void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +end_badly_now () +{ + GNUNET_SCHEDULER_cancel (die_task); + die_task = GNUNET_SCHEDULER_add_now (&end_badly, NULL); +} + + +static void +shutdown_task (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) { - disco_task = GNUNET_SCHEDULER_NO_TASK; - GNUNET_DHT_disconnect(dht_handle); - dht_handle = NULL; + GNUNET_GNS_disconnect(gns_handle); + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Shutting down peer!\n"); + GNUNET_SCHEDULER_shutdown (); } /** @@ -129,9 +144,18 @@ disco_dht(void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) static void process_shorten_result(void* cls, const char* sname) { - GNUNET_GNS_disconnect(gns_handle); - //GNUNET_SCHEDULER_add_now(disco_dht, NULL); - ok = 0; + + if (GNUNET_SCHEDULER_NO_TASK != die_task) + { + GNUNET_SCHEDULER_cancel (die_task); + die_task = GNUNET_SCHEDULER_NO_TASK; + } + + if (NULL != dht_handle) + { + GNUNET_DHT_disconnect (dht_handle); + dht_handle = NULL; + } if (sname == NULL) { @@ -147,23 +171,15 @@ process_shorten_result(void* cls, const char* sname) { GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "shorten test failed! (wanted: %s got: %s\n", - (char*)cls, sname); + TEST_EXPECTED_RESULT, sname); ok = 1; } GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "shorten test succeeded!\n"); } - - GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Shutting down peer1!\n"); - GNUNET_TESTING_daemons_stop (pg, TIMEOUT, &shutdown_callback, NULL); + GNUNET_SCHEDULER_add_now (&shutdown_task, NULL); } -static void -do_shorten(void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - GNUNET_GNS_shorten(gns_handle, TEST_DOMAIN, &process_shorten_result, -TEST_DOMAIN); -} static void on_lookup_result(void *cls, uint32_t rd_count, @@ -186,7 +202,7 @@ on_lookup_result(void *cls, uint32_t rd_count, for (i=0; isignature = *sig; nrb->public_key = alice_pkey; nrb->rd_count = htonl(1); - memset(&nrb[1], 0, strlen("+") + 1); - strcpy((char*)&nrb[1], "+"); + memset(&nrb[1], 0, strlen(GNUNET_GNS_MASTERZONE_STR) + 1); + strcpy((char*)&nrb[1], GNUNET_GNS_MASTERZONE_STR); nrb_data = (char*)&nrb[1]; - nrb_data += strlen("+") + 1; + nrb_data += strlen(GNUNET_GNS_MASTERZONE_STR) + 1; if (-1 == GNUNET_NAMESTORE_records_serialize (1, &rd, @@ -299,17 +308,15 @@ put_pseu_dht(void *cls, int success) { GNUNET_log(GNUNET_ERROR_TYPE_ERROR, "Record serialization failed!\n"); ok = 3; - GNUNET_DHT_disconnect(dht_handle); - - GNUNET_CRYPTO_rsa_key_free(our_key); GNUNET_CRYPTO_rsa_key_free(bob_key); GNUNET_CRYPTO_rsa_key_free(alice_key); GNUNET_free(sig); GNUNET_free (nrb); + end_badly_now (); return; } - GNUNET_CRYPTO_short_hash("+", strlen("+"), &name_hash); + GNUNET_CRYPTO_short_hash(GNUNET_GNS_MASTERZONE_STR, strlen(GNUNET_GNS_MASTERZONE_STR), &name_hash); GNUNET_CRYPTO_short_hash(&alice_pkey, sizeof(struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded), &zone_hash); @@ -319,15 +326,15 @@ put_pseu_dht(void *cls, int success) GNUNET_CRYPTO_hash_xor(&zone_hash_double, &name_hash_double, &xor_hash); rd_payload_length += sizeof(struct GNSNameRecordBlock) + - strlen("+") + 1; + strlen(GNUNET_GNS_MASTERZONE_STR) + 1; GNUNET_DHT_put (dht_handle, &xor_hash, 0, - GNUNET_DHT_RO_NONE, + GNUNET_DHT_RO_DEMULTIPLEX_EVERYWHERE, GNUNET_BLOCK_TYPE_GNS_NAMERECORD, rd_payload_length, (char*)nrb, - rd.expiration, + GNUNET_TIME_UNIT_FOREVER_ABS, DHT_OPERATION_TIMEOUT, &commence_testing, NULL); @@ -336,15 +343,16 @@ put_pseu_dht(void *cls, int success) GNUNET_free (nrb); } + static void put_www_dht(void *cls, int success) { struct GNSNameRecordBlock *nrb; struct GNUNET_CRYPTO_ShortHashCode name_hash; struct GNUNET_CRYPTO_ShortHashCode zone_hash; - GNUNET_HashCode xor_hash; - GNUNET_HashCode name_hash_double; - GNUNET_HashCode zone_hash_double; + struct GNUNET_HashCode xor_hash; + struct GNUNET_HashCode name_hash_double; + struct GNUNET_HashCode zone_hash_double; uint32_t rd_payload_length; char* nrb_data = NULL; struct GNUNET_CRYPTO_RsaSignature *sig; @@ -352,16 +360,24 @@ put_www_dht(void *cls, int success) char* ip = TEST_IP; struct in_addr *web = GNUNET_malloc(sizeof(struct in_addr)); - rd.expiration = GNUNET_TIME_UNIT_FOREVER_ABS; + rd.expiration_time = UINT64_MAX; GNUNET_assert(1 == inet_pton (AF_INET, ip, web)); rd.data_size = sizeof(struct in_addr); rd.data = web; rd.record_type = GNUNET_DNSPARSER_TYPE_A; - + rd.flags = GNUNET_NAMESTORE_RF_AUTHORITY; + sig = GNUNET_NAMESTORE_create_signature(alice_key, GNUNET_TIME_UNIT_FOREVER_ABS, TEST_RECORD_NAME, &rd, 1); + + GNUNET_break (GNUNET_OK == GNUNET_NAMESTORE_verify_signature (&alice_pkey, + GNUNET_TIME_UNIT_FOREVER_ABS, + TEST_RECORD_NAME, + 1, + &rd, + sig)); rd_payload_length = GNUNET_NAMESTORE_records_get_size (1, &rd); nrb = GNUNET_malloc(rd_payload_length + strlen(TEST_RECORD_NAME) + 1 + sizeof(struct GNSNameRecordBlock)); @@ -380,13 +396,13 @@ put_www_dht(void *cls, int success) { GNUNET_log(GNUNET_ERROR_TYPE_ERROR, "Record serialization failed!\n"); ok = 3; - GNUNET_DHT_disconnect(dht_handle); - GNUNET_CRYPTO_rsa_key_free(our_key); GNUNET_CRYPTO_rsa_key_free(bob_key); GNUNET_CRYPTO_rsa_key_free(alice_key); + GNUNET_free (sig); GNUNET_free(web); GNUNET_free (nrb); + end_badly_now(); return; } GNUNET_CRYPTO_short_hash(TEST_RECORD_NAME, strlen(TEST_RECORD_NAME), &name_hash); @@ -402,16 +418,16 @@ put_www_dht(void *cls, int success) GNUNET_DHT_put (dht_handle, &xor_hash, 0, - GNUNET_DHT_RO_NONE, + GNUNET_DHT_RO_DEMULTIPLEX_EVERYWHERE, GNUNET_BLOCK_TYPE_GNS_NAMERECORD, rd_payload_length, (char*)nrb, - rd.expiration, + GNUNET_TIME_UNIT_FOREVER_ABS, DHT_OPERATION_TIMEOUT, &put_pseu_dht, NULL); - - GNUNET_free(web); + GNUNET_free (sig); + GNUNET_free (web); GNUNET_free (nrb); } @@ -422,19 +438,20 @@ put_pkey_dht(void *cls, int32_t success, const char *emsg) struct GNSNameRecordBlock *nrb; struct GNUNET_CRYPTO_ShortHashCode name_hash; struct GNUNET_CRYPTO_ShortHashCode zone_hash; - GNUNET_HashCode xor_hash; - GNUNET_HashCode name_hash_double; - GNUNET_HashCode zone_hash_double; + struct GNUNET_HashCode xor_hash; + struct GNUNET_HashCode name_hash_double; + struct GNUNET_HashCode zone_hash_double; uint32_t rd_payload_length; char* nrb_data = NULL; struct GNUNET_CRYPTO_RsaSignature *sig; struct GNUNET_NAMESTORE_RecordData rd; - rd.expiration = GNUNET_TIME_UNIT_FOREVER_ABS; + rd.expiration_time = UINT64_MAX; rd.data_size = sizeof(struct GNUNET_CRYPTO_ShortHashCode); rd.data = &alice_hash; rd.record_type = GNUNET_GNS_RECORD_PKEY; - + rd.flags = GNUNET_NAMESTORE_RF_AUTHORITY; + sig = GNUNET_NAMESTORE_create_signature(bob_key, GNUNET_TIME_UNIT_FOREVER_ABS, TEST_AUTHORITY_ALICE, @@ -460,11 +477,12 @@ put_pkey_dht(void *cls, int32_t success, const char *emsg) GNUNET_log(GNUNET_ERROR_TYPE_ERROR, "Record serialization failed!\n"); ok = 3; - GNUNET_CRYPTO_rsa_key_free(our_key); - GNUNET_CRYPTO_rsa_key_free(bob_key); - GNUNET_CRYPTO_rsa_key_free(alice_key); - GNUNET_free(sig); + GNUNET_CRYPTO_rsa_key_free (our_key); + GNUNET_CRYPTO_rsa_key_free (bob_key); + GNUNET_CRYPTO_rsa_key_free (alice_key); + GNUNET_free (sig); GNUNET_free (nrb); + end_badly_now (); return; } @@ -482,37 +500,76 @@ put_pkey_dht(void *cls, int32_t success, const char *emsg) strlen(TEST_AUTHORITY_ALICE) + 1; GNUNET_DHT_put (dht_handle, &xor_hash, 0, - GNUNET_DHT_RO_NONE, + GNUNET_DHT_RO_DEMULTIPLEX_EVERYWHERE, GNUNET_BLOCK_TYPE_GNS_NAMERECORD, rd_payload_length, (char*)nrb, - rd.expiration, + GNUNET_TIME_UNIT_FOREVER_ABS, DHT_OPERATION_TIMEOUT, &put_www_dht, NULL); - GNUNET_NAMESTORE_disconnect(namestore_handle, GNUNET_NO); + GNUNET_free (sig); GNUNET_free (nrb); } + static void -do_lookup(void *cls, const struct GNUNET_PeerIdentity *id, - const struct GNUNET_CONFIGURATION_Handle *_cfg, - struct GNUNET_TESTING_Daemon *d, const char *emsg) +fin_init_zone (void *cls, int32_t success, const char *emsg) { + struct GNUNET_NAMESTORE_RecordData rd; + rd.expiration_time = UINT64_MAX; + rd.data_size = sizeof(struct GNUNET_CRYPTO_ShortHashCode); + rd.data = &bob_hash; + rd.record_type = GNUNET_GNS_RECORD_PKEY; + rd.flags = GNUNET_NAMESTORE_RF_AUTHORITY; - + GNUNET_NAMESTORE_record_create (namestore_handle, + our_key, + TEST_AUTHORITY_BOB, + &rd, + &put_pkey_dht, + NULL); + +} + +static void +cont_init_zone (void *cls, int32_t success, const char *emsg) +{ + + struct GNUNET_NAMESTORE_RecordData rd; + rd.expiration_time = UINT64_MAX; + rd.data_size = sizeof(struct GNUNET_CRYPTO_ShortHashCode); + rd.data = &short_zone; + rd.record_type = GNUNET_GNS_RECORD_PKEY; + rd.flags = GNUNET_NAMESTORE_RF_AUTHORITY; + + GNUNET_NAMESTORE_record_create (namestore_handle, + priv_key, + TEST_SHORTEN_ZONE, + &rd, + &fin_init_zone, + NULL); +} + + +static void +do_check (void *cls, + const struct GNUNET_CONFIGURATION_Handle *ccfg, + struct GNUNET_TESTING_Peer *peer) +{ + char* private_keyfile; + char* shorten_keyfile; char* our_keyfile; - cfg = _cfg; - - GNUNET_SCHEDULER_cancel (die_task); + cfg = ccfg; + die_task = GNUNET_SCHEDULER_add_delayed (TIMEOUT, &end_badly, NULL); /* put records into namestore */ namestore_handle = GNUNET_NAMESTORE_connect(cfg); if (NULL == namestore_handle) { GNUNET_log(GNUNET_ERROR_TYPE_ERROR, "Failed to connect to namestore\n"); - ok = -1; + end_badly_now(); return; } @@ -521,7 +578,7 @@ do_lookup(void *cls, const struct GNUNET_PeerIdentity *id, if (NULL == dht_handle) { GNUNET_log(GNUNET_ERROR_TYPE_ERROR, "Failed to connect to dht\n"); - ok = -1; + end_badly_now(); return; } @@ -530,114 +587,75 @@ do_lookup(void *cls, const struct GNUNET_PeerIdentity *id, &our_keyfile)) { GNUNET_log(GNUNET_ERROR_TYPE_ERROR, "Failed to get key from cfg\n"); - ok = -1; + end_badly_now(); + return; + } + + if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_filename (cfg, "gns", + "SHORTEN_ZONEKEY", + &shorten_keyfile)) + { + GNUNET_log(GNUNET_ERROR_TYPE_ERROR, + "Failed to get shorten zone key from cfg\n"); + end_badly_now(); + return; + } + + if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_filename (cfg, "gns", + "PRIVATE_ZONEKEY", + &private_keyfile)) + { + GNUNET_log(GNUNET_ERROR_TYPE_ERROR, + "Failed to get private zone key from cfg\n"); + end_badly_now(); return; } - our_key = GNUNET_CRYPTO_rsa_key_create_from_file (our_keyfile); + priv_key = GNUNET_CRYPTO_rsa_key_create_from_file (private_keyfile); + short_key = GNUNET_CRYPTO_rsa_key_create_from_file (shorten_keyfile); bob_key = GNUNET_CRYPTO_rsa_key_create_from_file (KEYFILE_BOB); alice_key = GNUNET_CRYPTO_rsa_key_create_from_file (KEYFILE_ALICE); GNUNET_free(our_keyfile); + GNUNET_free(shorten_keyfile); + GNUNET_free(private_keyfile); GNUNET_CRYPTO_rsa_key_get_public (our_key, &our_pkey); + GNUNET_CRYPTO_rsa_key_get_public (priv_key, &priv_pkey); + GNUNET_CRYPTO_rsa_key_get_public (short_key, &short_pkey); GNUNET_CRYPTO_rsa_key_get_public (bob_key, &bob_pkey); GNUNET_CRYPTO_rsa_key_get_public (alice_key, &alice_pkey); GNUNET_CRYPTO_short_hash(&bob_pkey, sizeof(bob_pkey), &bob_hash); GNUNET_CRYPTO_short_hash(&alice_pkey, sizeof(alice_pkey), &alice_hash); - + GNUNET_CRYPTO_short_hash(&our_pkey, sizeof(our_pkey), &our_zone); + GNUNET_CRYPTO_short_hash(&priv_pkey, sizeof(priv_pkey), &priv_zone); + GNUNET_CRYPTO_short_hash(&short_pkey, sizeof(short_pkey), &short_zone); + struct GNUNET_NAMESTORE_RecordData rd; - rd.expiration = GNUNET_TIME_UNIT_FOREVER_ABS; + rd.expiration_time = UINT64_MAX; rd.data_size = sizeof(struct GNUNET_CRYPTO_ShortHashCode); - rd.data = &bob_hash; + rd.data = &priv_zone; rd.record_type = GNUNET_GNS_RECORD_PKEY; + rd.flags = GNUNET_NAMESTORE_RF_AUTHORITY; GNUNET_NAMESTORE_record_create (namestore_handle, our_key, - TEST_AUTHORITY_BOB, + TEST_PRIVATE_ZONE, &rd, - &put_pkey_dht, + &cont_init_zone, NULL); - - } -static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *c) -{ - cfg = c; - /* Get path from configuration file */ - if (GNUNET_YES != - GNUNET_CONFIGURATION_get_value_string (cfg, "paths", "servicehome", - &test_directory)) - { - ok = 404; - return; - } - - - /* Set up a task to end testing if peer start fails */ - die_task = - GNUNET_SCHEDULER_add_delayed (TIMEOUT, &end_badly, - "didn't start all daemons in reasonable amount of time!!!"); - - /* Start alice */ - //d1 = GNUNET_TESTING_daemon_start(cfg, TIMEOUT, GNUNET_NO, NULL, NULL, 0, - // NULL, NULL, NULL, &do_lookup, NULL); - pg = GNUNET_TESTING_daemons_start(cfg, 1, 1, 1, TIMEOUT, - NULL, NULL, &do_lookup, NULL, - NULL, NULL, NULL); -} - -static int -check () -{ - int ret; - - /* Arguments for GNUNET_PROGRAM_run */ - char *const argv[] = { "test-gns-pseu-shorten", /* Name to give running binary */ - "-c", - "test_gns_simple_lookup.conf", /* Config file to use */ -#if VERBOSE - "-L", "DEBUG", -#endif - NULL - }; - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - /* Run the run function as a new program */ - ret = - GNUNET_PROGRAM_run ((sizeof (argv) / sizeof (char *)) - 1, argv, - "test-gns-pseu-shorten", "nohelp", options, &run, - &ok); - if (ret != GNUNET_OK) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "`test-gns-pseu-shorten': Failed with error code %d\n", ret); - } - return ok; -} int main (int argc, char *argv[]) { - int ret; - + ok = 1; GNUNET_log_setup ("test-gns-pseu-shorten", -#if VERBOSE - "DEBUG", -#else "WARNING", -#endif NULL); - ret = check (); - /** - * Need to remove base directory, subdirectories taken care - * of by the testing framework. - */ - return ret; + GNUNET_TESTING_peer_run ("test-gns-pseu-shorten", "test_gns_simple_lookup.conf", &do_check, NULL); + return ok; } -/* end of test_gns_twopeer.c */ +/* end of test_gns_pseu_shorten.c */ diff --git a/src/gns/test_gns_revocation.c b/src/gns/test_gns_revocation.c new file mode 100644 index 0000000..8e67788 --- /dev/null +++ b/src/gns/test_gns_revocation.c @@ -0,0 +1,285 @@ +/* + This file is part of GNUnet. + (C) 2009 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ +/** + * @file gns/test_gns_revovation.c + * @brief base testcase for testing zone revocation + * + */ +#include "platform.h" +#include "gnunet_testing_lib.h" +#include "gnunet_core_service.h" +#include "block_dns.h" +#include "gnunet_signatures.h" +#include "gnunet_namestore_service.h" +#include "../namestore/namestore.h" +#include "gnunet_dnsparser_lib.h" +#include "gnunet_gns_service.h" + +/* Timeout for entire testcase */ +#define TIMEOUT GNUNET_TIME_relative_multiply(GNUNET_TIME_UNIT_SECONDS, 20) + +/* test records to resolve */ +#define TEST_DOMAIN "www.bob.gads" +#define TEST_IP "127.0.0.1" +#define TEST_RECORD_NAME "www" + +#define TEST_AUTHORITY_NAME "bob" + +#define KEYFILE_BOB "../namestore/zonefiles/HGU0A0VCU334DN7F2I9UIUMVQMM7JMSD142LIMNUGTTV9R0CF4EG.zkey" + +/* Task handle to use to schedule test failure */ +static GNUNET_SCHEDULER_TaskIdentifier die_task; + +/* Global return value (0 for success, anything else for failure) */ +static int ok; + +static struct GNUNET_NAMESTORE_Handle *namestore_handle; + +static struct GNUNET_GNS_Handle *gns_handle; + +static const struct GNUNET_CONFIGURATION_Handle *cfg; + + +/** + * Check if the get_handle is being used, if so stop the request. Either + * way, schedule the end_badly_cont function which actually shuts down the + * test. + */ +static void +end_badly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + die_task = GNUNET_SCHEDULER_NO_TASK; + if (NULL != gns_handle) + { + GNUNET_GNS_disconnect(gns_handle); + gns_handle = NULL; + } + + if (NULL != namestore_handle) + { + GNUNET_NAMESTORE_disconnect (namestore_handle); + namestore_handle = NULL; + } + GNUNET_break (0); + GNUNET_SCHEDULER_shutdown (); + ok = 1; +} + + +static void +end_badly_now () +{ + GNUNET_SCHEDULER_cancel (die_task); + die_task = GNUNET_SCHEDULER_add_now (&end_badly, NULL); +} + + +static void +shutdown_task (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + GNUNET_GNS_disconnect(gns_handle); + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Shutting down peer!\n"); + GNUNET_SCHEDULER_shutdown (); +} + + +static void +on_lookup_result(void *cls, uint32_t rd_count, + const struct GNUNET_NAMESTORE_RecordData *rd) +{ + struct in_addr a; + int i; + char* addr; + + if (GNUNET_SCHEDULER_NO_TASK != die_task) + { + GNUNET_SCHEDULER_cancel (die_task); + die_task = GNUNET_SCHEDULER_NO_TASK; + } + + GNUNET_NAMESTORE_disconnect (namestore_handle); + namestore_handle = NULL; + if (rd_count == 0) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Lookup failed, this is good!\n"); + ok = 0; + } + else + { + ok = 1; + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "name: %s\n", (char*)cls); + for (i=0; iport = srv_port; + srv_data->prio = srv_prio; + srv_data->weight = srv_weight; + strcpy((char*)&srv_data[1], TEST_SRV_NAME); + rd.data = srv_data; + rd.record_type = GNUNET_GNS_RECORD_SRV; + sig = GNUNET_NAMESTORE_create_signature(bob_key, + GNUNET_TIME_UNIT_FOREVER_ABS, + TEST_RECORD_NAME_SRV, + &rd, 1); + et.abs_value = rd.expiration_time; + GNUNET_NAMESTORE_record_put (namestore_handle, + &bob_pkey, + TEST_RECORD_NAME_SRV, + et, + 1, + &rd, + sig, + &commence_testing, + NULL); + GNUNET_free (alice_keyfile); + GNUNET_free (srv_data); + GNUNET_free (sipserver); + GNUNET_free (sig); + GNUNET_CRYPTO_rsa_key_free (bob_key); + GNUNET_CRYPTO_rsa_key_free (alice_key); +} + + +int +main (int argc, char *argv[]) +{ + ok = 1; + GNUNET_log_setup ("test-gns-simple-srv-lookup", + "WARNING", + NULL); + GNUNET_TESTING_peer_run ("test-gns-simple-srv-lookup", "test_gns_simple_lookup.conf", &do_check, NULL); + GNUNET_DISK_directory_remove ("test-gns-simple-srv-lookup"); + return ok; +} + +/* end of test_gns_simple_srv_lookup.c */ diff --git a/src/gns/test_gns_simple_zkey_lookup.c b/src/gns/test_gns_simple_zkey_lookup.c index 8b9b78b..dd1a3f7 100644 --- a/src/gns/test_gns_simple_zkey_lookup.c +++ b/src/gns/test_gns_simple_zkey_lookup.c @@ -33,14 +33,8 @@ #include "gnunet_gns_service.h" #include "gns.h" -/* DEFINES */ -#define VERBOSE GNUNET_YES - /* Timeout for entire testcase */ -#define TIMEOUT GNUNET_TIME_relative_multiply(GNUNET_TIME_UNIT_SECONDS, 20) - -/* If number of peers not in config file, use this number */ -#define DEFAULT_NUM_PEERS 2 +#define TIMEOUT GNUNET_TIME_relative_multiply(GNUNET_TIME_UNIT_SECONDS, 40) /* test records to resolve */ #define TEST_IP "127.0.0.1" @@ -50,17 +44,8 @@ #define KEYFILE_BOB "../namestore/zonefiles/HGU0A0VCU334DN7F2I9UIUMVQMM7JMSD142LIMNUGTTV9R0CF4EG.zkey" -/* Globals */ - -/** - * Directory to store temp data in, defined in config file - */ -static char *test_directory; - -static struct GNUNET_TESTING_PeerGroup *pg; - /* Task handle to use to schedule test failure */ -GNUNET_SCHEDULER_TaskIdentifier die_task; +static GNUNET_SCHEDULER_TaskIdentifier die_task; /* Global return value (0 for success, anything else for failure) */ static int ok; @@ -69,26 +54,55 @@ static struct GNUNET_NAMESTORE_Handle *namestore_handle; static struct GNUNET_GNS_Handle *gns_handle; -const struct GNUNET_CONFIGURATION_Handle *cfg; +static const struct GNUNET_CONFIGURATION_Handle *cfg; + +static struct GNUNET_CRYPTO_ShortHashCode bob_hash; -struct GNUNET_CRYPTO_ShortHashCode bob_hash; /** - * Check whether peers successfully shut down. + * Check if the get_handle is being used, if so stop the request. Either + * way, schedule the end_badly_cont function which actually shuts down the + * test. */ -void -shutdown_callback (void *cls, const char *emsg) +static void +end_badly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { - if (emsg != NULL) + die_task = GNUNET_SCHEDULER_NO_TASK; + if (NULL != gns_handle) { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Error on shutdown! ret=%d\n", ok); - if (ok == 0) - ok = 2; + GNUNET_GNS_disconnect(gns_handle); + gns_handle = NULL; } - GNUNET_log (GNUNET_ERROR_TYPE_INFO, "done(ret=%d)!\n", ok); + if (NULL != namestore_handle) + { + GNUNET_NAMESTORE_disconnect (namestore_handle); + namestore_handle = NULL; + } + GNUNET_break (0); + GNUNET_SCHEDULER_shutdown (); + ok = 1; +} + + +static void +end_badly_now () +{ + GNUNET_SCHEDULER_cancel (die_task); + die_task = GNUNET_SCHEDULER_add_now (&end_badly, NULL); +} + + +static void +shutdown_task (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + GNUNET_GNS_disconnect(gns_handle); + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Shutting down peer!\n"); + GNUNET_SCHEDULER_shutdown (); } + static void on_lookup_result(void *cls, uint32_t rd_count, const struct GNUNET_NAMESTORE_RecordData *rd) @@ -97,10 +111,18 @@ on_lookup_result(void *cls, uint32_t rd_count, int i; char* addr; + if (GNUNET_SCHEDULER_NO_TASK != die_task) + { + GNUNET_SCHEDULER_cancel (die_task); + die_task = GNUNET_SCHEDULER_NO_TASK; + } + + GNUNET_NAMESTORE_disconnect (namestore_handle); + namestore_handle = NULL; if (rd_count == 0) { GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "Lookup failed, rp_filtering?\n"); + "Lookup failed\n"); ok = 2; } else @@ -110,7 +132,7 @@ on_lookup_result(void *cls, uint32_t rd_count, for (i=0; i +#include +#include +#include "gnunet_w32nsp_lib.h" +#include + +int +main (int argc, char **argv) +{ + int ret; + int r = 1; + WSADATA wsd; + GUID id = GNUNET_NAMESPACE_PROVIDER_DNS; + wchar_t *cmdl; + int wargc; + wchar_t **wargv; + + if (WSAStartup(MAKEWORD(2,2), &wsd) != 0) + { + fprintf (stderr, "WSAStartup() failed: %lu\n", GetLastError()); + return 5; + } + + cmdl = GetCommandLineW (); + if (cmdl == NULL) + { + WSACleanup(); + return 2; + } + wargv = CommandLineToArgvW (cmdl, &wargc); + if (wargv == NULL) + { + WSACleanup(); + return 3; + } + r = 4; + + if (wargc == 2) + { + ret = WSCInstallNameSpace (L"GNUnet DNS provider", wargv[1], NS_DNS, 1, &id); + if (ret == NO_ERROR) + { + r = 0; + } + else + { + r = 1; + fprintf (stderr, + "WSCInstallNameSpace(L\"GNUnet DNS provider\", \"%S\", %d, 0, %p) failed: %lu\n", + wargv[1], NS_DNS, &id, GetLastError ()); + } + } + WSACleanup(); + return r; +} diff --git a/src/gns/w32nsp-resolve.c b/src/gns/w32nsp-resolve.c new file mode 100644 index 0000000..3234a1e --- /dev/null +++ b/src/gns/w32nsp-resolve.c @@ -0,0 +1,369 @@ +/* + This file is part of GNUnet. + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ +/** + * @file gns/w32nsp-resolve.c + * @brief W32 integration for GNS + * @author LRN + */ +#define INITGUID +#include +#include +#include +#include +#include +#include "gnunet_w32nsp_lib.h" +#include + +typedef int (WSPAPI *LPNSPSTARTUP) (LPGUID lpProviderId, LPNSP_ROUTINE lpnspRoutines); + +GUID host = {0x0002a800,0,0,{ 0xC0,0,0,0,0,0,0,0x46 }}; +GUID ip4 = {0x00090035,0,1,{ 0xc0,0,0,0,0,0,0,0x046}}; +GUID ip6 = {0x00090035,0,0x001c, { 0xc0,0,0,0,0,0,0,0x046}}; + +DEFINE_GUID(W32_DNS, 0x22059D40, 0x7E9E, 0x11CF, 0xAE, 0x5A, 0x00, 0xAA, 0x00, 0xA7, 0x11, 0x2B); + +#define DEFINE_DNS_GUID(a,x) DEFINE_GUID(a, 0x00090035, 0x0000, x, 0xc0, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x46) +DEFINE_DNS_GUID(SVCID_DNS_TYPE_A, 0x0001); +DEFINE_DNS_GUID(SVCID_DNS_TYPE_NS, 0x0002); +DEFINE_DNS_GUID(SVCID_DNS_TYPE_CNAME, 0x0005); +DEFINE_DNS_GUID(SVCID_DNS_TYPE_SOA, 0x0006); +DEFINE_DNS_GUID(SVCID_DNS_TYPE_PTR, 0x000c); +DEFINE_DNS_GUID(SVCID_DNS_TYPE_MX, 0x000f); +DEFINE_DNS_GUID(SVCID_DNS_TYPE_TEXT, 0x0010); +DEFINE_DNS_GUID(SVCID_DNS_TYPE_AAAA, 0x001c); +DEFINE_DNS_GUID(SVCID_DNS_TYPE_SRV, 0x0021); +DEFINE_GUID(SVCID_HOSTNAME, 0x0002a800, 0x0000, 0x0000, 0xc0, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x46); +DEFINE_GUID(SVCID_INET_HOSTADDRBYNAME, 0x0002a803, 0x0000, 0x0000, 0xc0, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x46); + +// +// Utility to turn a list of offsets into a list of addresses. Used +// to convert structures returned as BLOBs. +// + +VOID +FixList(PCHAR ** List, PCHAR Base) +{ + if(*List) + { + PCHAR * Addr; + + Addr = *List = (PCHAR *)( ((DWORD)*List + Base) ); + while(*Addr) + { + *Addr = (PCHAR)(((DWORD)*Addr + Base)); + Addr++; + } + } +} + + +// +// Routine to convert a hostent returned in a BLOB to one with +// usable pointers. The structure is converted in-place. +// +VOID +UnpackHostEnt(struct hostent * hostent) +{ + PCHAR pch; + + pch = (PCHAR)hostent; + + if(hostent->h_name) + { + hostent->h_name = (PCHAR)((DWORD)hostent->h_name + pch); + } + FixList(&hostent->h_aliases, pch); + FixList(&hostent->h_addr_list, pch); +} + + +static void +print_hostent (struct hostent *he) +{ + int i; + char **pAlias; + + printf("\tOfficial name: %s\n", he->h_name); + for (i=0, pAlias = he->h_aliases; *pAlias != 0; pAlias++) { + printf("\tAlternate name #%d: %s\n", ++i, *pAlias); + } + printf("\tAddress type: "); + switch (he->h_addrtype) { + case AF_INET: + printf("AF_INET\n"); + break; + case AF_INET6: + printf("AF_INET6\n"); + break; + case AF_NETBIOS: + printf("AF_NETBIOS\n"); + break; + default: + printf(" %d\n", he->h_addrtype); + break; + } + printf("\tAddress length: %d\n", he->h_length); + + if (he->h_addrtype == AF_INET) { + struct sockaddr_in addr; + memset (&addr, 0, sizeof (addr)); + addr.sin_family = AF_INET; + addr.sin_port = 0; + i = 0; + while (he->h_addr_list[i] != 0) { + char buf[1024]; + DWORD buflen = 1024; + addr.sin_addr = *(struct in_addr *) he->h_addr_list[i++]; + if (NO_ERROR == WSAAddressToStringA ((LPSOCKADDR) &addr, sizeof (addr), NULL, buf, &buflen)) + printf("\tIPv4 Address #%d: %s\n", i, buf); + else + printf("\tIPv4 Address #%d: Can't convert: %lu\n", i, GetLastError ()); + } + } else if (he->h_addrtype == AF_INET6) { + struct sockaddr_in6 addr; + memset (&addr, 0, sizeof (addr)); + addr.sin6_family = AF_INET6; + addr.sin6_port = 0; + i = 0; + while (he->h_addr_list[i] != 0) { + char buf[1024]; + DWORD buflen = 1024; + addr.sin6_addr = *(struct in6_addr *) he->h_addr_list[i++]; + if (NO_ERROR == WSAAddressToStringA ((LPSOCKADDR) &addr, sizeof (addr), NULL, buf, &buflen)) + printf("\tIPv6 Address #%d: %s\n", i, buf); + else + printf("\tIPv6 Address #%d: Can't convert: %lu\n", i, GetLastError ()); + } + } +} + + +int +main (int argc, char **argv) +{ + int ret; + int r = 1; + WSADATA wsd; + GUID *prov = NULL; + GUID *sc = NULL; + wchar_t *cmdl; + int wargc; + wchar_t **wargv; + + if (WSAStartup(MAKEWORD(2,2), &wsd) != 0) + { + fprintf (stderr, "WSAStartup() failed: %lu\n", GetLastError()); + return 5; + } + + cmdl = GetCommandLineW (); + if (cmdl == NULL) + { + WSACleanup(); + return 2; + } + wargv = CommandLineToArgvW (cmdl, &wargc); + if (wargv == NULL) + { + WSACleanup(); + return 3; + } + r = 4; + + if (wargc == 5) + { + if (wcscmp (wargv[1], L"A") == 0) + sc = &SVCID_DNS_TYPE_A; + else if (wcscmp (wargv[1], L"AAAA") == 0) + sc = &SVCID_DNS_TYPE_AAAA; + else if (wcscmp (wargv[1], L"name") == 0) + sc = &SVCID_HOSTNAME; + else if (wcscmp (wargv[1], L"addr") == 0) + sc = &SVCID_INET_HOSTADDRBYNAME; + else + wargc -= 1; + if (wcscmp (wargv[4], L"mswdns") == 0) + prov = &W32_DNS; + else if (wcscmp (wargv[4], L"gnunetdns") == 0) + prov = &GNUNET_NAMESPACE_PROVIDER_DNS; + else + wargc -= 1; + } + + if (wargc == 5) + { + HMODULE nsp; + + nsp = LoadLibraryW (wargv[3]); + if (nsp == NULL) + { + fprintf (stderr, "Failed to load library `%S'\n", wargv[3]); + } + else + { + LPNSPSTARTUP startup = (LPNSPSTARTUP) GetProcAddress (nsp, "NSPStartup"); + if (startup != NULL) + { + NSP_ROUTINE api; + ret = startup (prov, &api); + if (NO_ERROR != ret) + fprintf (stderr, "startup failed\n"); + else + { + HANDLE lookup; + WSAQUERYSETW search; + char buf[4096]; + WSAQUERYSETW *result = (WSAQUERYSETW *) buf; + DWORD resultsize; + DWORD err; + memset (&search, 0, sizeof (search)); + search.dwSize = sizeof (search); + search.lpszServiceInstanceName = (wcscmp (wargv[2], L" ") == 0) ? NULL : wargv[2]; + search.lpServiceClassId = sc; + search.lpNSProviderId = prov; + search.dwNameSpace = NS_ALL; + ret = api.NSPLookupServiceBegin (prov, &search, NULL, LUP_RETURN_ALL, &lookup); + if (ret != NO_ERROR) + { + fprintf (stderr, "lookup start failed\n"); + } + else + { + resultsize = 4096; + ret = api.NSPLookupServiceNext (lookup, LUP_RETURN_ALL, &resultsize, result); + err = GetLastError (); + if (ret != NO_ERROR) + { + fprintf (stderr, "lookup next failed\n"); + } + else + { + int i; + printf ("Got result:\n"); + printf (" lpszServiceInstanceName: %S\n", result->lpszServiceInstanceName ? result->lpszServiceInstanceName : L"NULL"); + if (result->lpServiceClassId) + printf (" lpServiceClassId: { 0x%08lX,0x%04X,0x%04X, { 0x%02X, 0x%02X, 0x%02X, 0x%02X, 0x%02X, 0x%02X, 0x%02X, 0x%02X } }\n", + result->lpServiceClassId->Data1, result->lpServiceClassId->Data2, result->lpServiceClassId->Data3, result->lpServiceClassId->Data4[0], + result->lpServiceClassId->Data4[1], result->lpServiceClassId->Data4[2], result->lpServiceClassId->Data4[3], result->lpServiceClassId->Data4[4], + result->lpServiceClassId->Data4[5], result->lpServiceClassId->Data4[6], result->lpServiceClassId->Data4[7]); + else + printf (" lpServiceClassId: NULL\n"); + if (result->lpVersion) + printf (" lpVersion: 0x%08lX, %d\n", result->lpVersion->dwVersion, result->lpVersion->ecHow); + else + printf (" lpVersion: NULL\n"); + printf (" lpszComment: %S\n", result->lpszComment ? result->lpszComment : L"NULL"); + printf (" dwNameSpace: %lu\n", result->dwNameSpace); + if (result->lpNSProviderId) + printf (" lpNSProviderId: { 0x%08lX,0x%04X,0x%04X, { 0x%02X, 0x%02X, 0x%02X, 0x%02X, 0x%02X, 0x%02X, 0x%02X, 0x%02X } }\n", + result->lpNSProviderId->Data1, result->lpNSProviderId->Data2, result->lpNSProviderId->Data3, result->lpNSProviderId->Data4[0], + result->lpNSProviderId->Data4[1], result->lpNSProviderId->Data4[2], result->lpNSProviderId->Data4[3], result->lpNSProviderId->Data4[4], + result->lpNSProviderId->Data4[5], result->lpNSProviderId->Data4[6], result->lpNSProviderId->Data4[7]); + else + printf (" lpNSProviderId: NULL\n"); + printf (" lpszContext: %S\n", result->lpszContext ? result->lpszContext : L"NULL"); + printf (" dwNumberOfProtocols: %lu\n", result->dwNumberOfProtocols); + printf (" lpszQueryString: %S\n", result->lpszQueryString ? result->lpszQueryString : L"NULL"); + printf (" dwNumberOfCsAddrs: %lu\n", result->dwNumberOfCsAddrs); + for (i = 0; i < result->dwNumberOfCsAddrs; i++) + { + switch (result->lpcsaBuffer[i].iSocketType) + { + case SOCK_STREAM: + printf (" %d: iSocketType = SOCK_STREAM\n", i); + break; + case SOCK_DGRAM: + printf (" %d: iSocketType = SOCK_DGRAM\n", i); + break; + default: + printf (" %d: iSocketType = %d\n", i, result->lpcsaBuffer[i].iSocketType); + } + switch (result->lpcsaBuffer[i].iProtocol) + { + case IPPROTO_TCP: + printf (" %d: iProtocol = IPPROTO_TCP\n", i); + break; + case IPPROTO_UDP: + printf (" %d: iProtocol = IPPROTO_UDP\n", i); + break; + default: + printf (" %d: iProtocol = %d\n", i, result->lpcsaBuffer[i].iProtocol); + } + switch (result->lpcsaBuffer[i].LocalAddr.lpSockaddr->sa_family) + { + case AF_INET: + printf (" %d: loc family = AF_INET\n", i); + break; + case AF_INET6: + printf (" %d: loc family = AF_INET6\n", i); + break; + default: + printf (" %d: loc family = %hu\n", i, result->lpcsaBuffer[i].LocalAddr.lpSockaddr->sa_family); + } + switch (result->lpcsaBuffer[i].RemoteAddr.lpSockaddr->sa_family) + { + case AF_INET: + printf (" %d: rem family = AF_INET\n", i); + break; + case AF_INET6: + printf (" %d: rem family = AF_INET6\n", i); + break; + default: + printf (" %d: rem family = %hu\n", i, result->lpcsaBuffer[i].RemoteAddr.lpSockaddr->sa_family); + } + char buf[1024]; + DWORD buflen = 1024; + if (NO_ERROR == WSAAddressToStringA (result->lpcsaBuffer[i].LocalAddr.lpSockaddr, result->lpcsaBuffer[i].LocalAddr.iSockaddrLength, NULL, buf, &buflen)) + printf("\tLocal Address #%d: %s\n", i, buf); + else + printf("\tLocal Address #%d: Can't convert: %lu\n", i, GetLastError ()); + buflen = 1024; + if (NO_ERROR == WSAAddressToStringA (result->lpcsaBuffer[i].RemoteAddr.lpSockaddr, result->lpcsaBuffer[i].RemoteAddr.iSockaddrLength, NULL, buf, &buflen)) + printf("\tRemote Address #%d: %s\n", i, buf); + else + printf("\tRemote Address #%d: Can't convert: %lu\n", i, GetLastError ()); + } + printf (" dwOutputFlags: 0x%08lX\n", result->dwOutputFlags); + printf (" lpBlob: 0x%p\n", result->lpBlob); + if (result->lpBlob) + { + struct hostent *he = malloc (result->lpBlob->cbSize); + if (he != NULL) + { + memcpy (he, result->lpBlob->pBlobData, result->lpBlob->cbSize); + UnpackHostEnt (he); + print_hostent (he); + free (he); + } + } + } + ret = api.NSPLookupServiceEnd (lookup); + if (ret != NO_ERROR) + printf ("NSPLookupServiceEnd() failed: %lu\n", GetLastError ()); + } + api.NSPCleanup (prov); + } + } + FreeLibrary (nsp); + } + } + WSACleanup(); + return r; +} diff --git a/src/gns/w32nsp-uninstall.c b/src/gns/w32nsp-uninstall.c new file mode 100644 index 0000000..bb8db66 --- /dev/null +++ b/src/gns/w32nsp-uninstall.c @@ -0,0 +1,30 @@ +#define INITGUID +#include +#include +#include +#include "gnunet_w32nsp_lib.h" +#include + +int +main (int argc, char **argv) +{ + int ret; + GUID id = GNUNET_NAMESPACE_PROVIDER_DNS; + WSADATA wsd; + + if (WSAStartup(MAKEWORD(2,2), &wsd) != 0) + { + fprintf (stderr, "WSAStartup() failed: %lu\n", GetLastError()); + return 5; + } + + ret = WSCUnInstallNameSpace (&id); + if (ret == NO_ERROR) + { + WSACleanup (); + return 0; + } + fprintf (stderr, "WSCUnInstallNameSpace() failed: %lu\n", GetLastError ()); + WSACleanup (); + return 1; +} \ No newline at end of file diff --git a/src/gns/w32nsp.c b/src/gns/w32nsp.c new file mode 100644 index 0000000..6e58353 --- /dev/null +++ b/src/gns/w32nsp.c @@ -0,0 +1,705 @@ +/* + This file is part of GNUnet. + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ +/** + * @file gns/w32nsp.c + * @brief W32 integration for GNS + * @author LRN + */ +/* This code is partially based upon samples from the book + * "Network Programming For Microsoft Windows, 2Nd Edition". + */ + +#define INITGUID +#include +#include +#include +#include +#include + +#if 1 +# define DEBUGLOG(s, ...) +#endif +#if 0 +# define DEBUGLOG(s, ...) printf (s, ##__VA_ARGS__) +#endif + +#define WINDOWS 1 +#define MINGW 1 +#ifndef __BYTE_ORDER +#ifdef _BYTE_ORDER +#define __BYTE_ORDER _BYTE_ORDER +#else +#ifdef BYTE_ORDER +#define __BYTE_ORDER BYTE_ORDER +#endif +#endif +#endif +#ifndef __BIG_ENDIAN +#ifdef _BIG_ENDIAN +#define __BIG_ENDIAN _BIG_ENDIAN +#else +#ifdef BIG_ENDIAN +#define __BIG_ENDIAN BIG_ENDIAN +#endif +#endif +#endif +#ifndef __LITTLE_ENDIAN +#ifdef _LITTLE_ENDIAN +#define __LITTLE_ENDIAN _LITTLE_ENDIAN +#else +#ifdef LITTLE_ENDIAN +#define __LITTLE_ENDIAN LITTLE_ENDIAN +#endif +#endif +#endif +#include "gnunet_w32nsp_lib.h" +#include "w32resolver.h" + +#define NSPAPI_VERSION_MAJOR 4 +#define NSPAPI_VERSION_MINOR 4 + +#define REPLY_LIFETIME 60*5 + +#define STATE_BEGIN 0x01 +#define STATE_END 0x02 +#define STATE_REPLY 0x04 +#define STATE_GHBN 0x08 + +uint64_t +GNUNET_htonll (uint64_t n) +{ +#if __BYTE_ORDER == __BIG_ENDIAN + return n; +#elif __BYTE_ORDER == __LITTLE_ENDIAN + return (((uint64_t) htonl (n)) << 32) + htonl (n >> 32); +#else + #error byteorder undefined +#endif +} + +CRITICAL_SECTION records_cs; + +struct record +{ + SOCKET s; + DWORD flags; + uint8_t state; + char *buf; + wchar_t *name; +}; + +static struct record *records = NULL; +static size_t records_len = 0; +static size_t records_size = 0; + +int +resize_records () +{ + size_t new_size = records_len > 0 ? records_len * 2 : 5; + struct record *new_records = malloc (new_size * sizeof (struct record)); + if (new_records == NULL) + { + SetLastError (WSA_NOT_ENOUGH_MEMORY); + return 0; + } + memcpy (new_records, records, records_len * sizeof (struct record)); + memset (&new_records[records_len], 0, sizeof (struct record) * (new_size - records_len)); + records_size = new_size; + free (records); + records = new_records; + return 1; +} + +int +add_record (SOCKET s, const wchar_t *name, DWORD flags) +{ + int res = 1; + int i; + int empty = -1; + //EnterCriticalSection (&records_cs); + for (i = 0; i < records_len; i++) + if (records[i].state == 0) + break; + empty = i; + if (i == records_len) + { + res = resize_records (); + if (res) + empty = records_len++; + } + if (res) + { + struct record r; + r.s = s; + r.flags = flags; + r.name = (wchar_t *) name; + r.state = 1; + r.buf = NULL; + if (name) + r.name = wcsdup (name); + records[empty] = r; + } + //LeaveCriticalSection (&records_cs); + return res; +} + +void +free_record (int i) +{ + if (records[i].name) + free (records[i].name); + records[i].state = 0; +} + +/* These are not defined by mingw.org headers at the moment*/ +typedef INT (WSPAPI *LPNSPIOCTL) (HANDLE,DWORD,LPVOID,DWORD,LPVOID,DWORD,LPDWORD,LPWSACOMPLETION,LPWSATHREADID); +typedef struct _NSP_ROUTINE_XP { + DWORD cbSize; + DWORD dwMajorVersion; + DWORD dwMinorVersion; + LPNSPCLEANUP NSPCleanup; + LPNSPLOOKUPSERVICEBEGIN NSPLookupServiceBegin; + LPNSPLOOKUPSERVICENEXT NSPLookupServiceNext; + LPNSPLOOKUPSERVICEEND NSPLookupServiceEnd; + LPNSPSETSERVICE NSPSetService; + LPNSPINSTALLSERVICECLASS NSPInstallServiceClass; + LPNSPREMOVESERVICECLASS NSPRemoveServiceClass; + LPNSPGETSERVICECLASSINFO NSPGetServiceClassInfo; + LPNSPIOCTL NSPIoctl; +} NSP_ROUTINE_XP; + +static SOCKET +connect_to_dns_resolver () +{ + struct sockaddr_in addr; + SOCKET r; + int ret; + + r = socket (AF_INET, SOCK_STREAM, IPPROTO_TCP); + if (INVALID_SOCKET == r) + { + SetLastError (16004); + return r; + } + + addr.sin_family = AF_INET; + addr.sin_port = htons (5353); /* TCP 5353 is not registered; UDP 5353 is */ + addr.sin_addr.s_addr = inet_addr ("127.0.0.1"); + + ret = connect (r, (struct sockaddr *) &addr, sizeof (addr)); + if (SOCKET_ERROR == ret) + { + DWORD err = GetLastError (); + closesocket (r); + SetLastError (err); + SetLastError (16005); + r = INVALID_SOCKET; + } + return r; +} + +static int +send_name_to_ip_request (LPWSAQUERYSETW lpqsRestrictions, + LPWSASERVICECLASSINFOW lpServiceClassInfo, DWORD dwControlFlags, + SOCKET *resolver) +{ + struct GNUNET_W32RESOLVER_GetMessage *msg; + int af4 = 0; + int af6 = 0; + char *buf; + int ret = 1; + int i; + uint32_t id; + size_t size = sizeof (struct GNUNET_W32RESOLVER_GetMessage); + size_t namelen = 0; + if (lpqsRestrictions->lpszServiceInstanceName) + namelen = sizeof (wchar_t) * (wcslen (lpqsRestrictions->lpszServiceInstanceName) + 1); + size += namelen; + buf = malloc (size); + msg = (struct GNUNET_W32RESOLVER_GetMessage *) buf; + msg->header.size = htons (size); + msg->header.type = htons (GNUNET_MESSAGE_TYPE_W32RESOLVER_REQUEST); + if (lpqsRestrictions->dwNumberOfProtocols > 0) + { + int i; + for (i = 0; i < lpqsRestrictions->dwNumberOfProtocols; i++) + { + if (lpqsRestrictions->lpafpProtocols[0].iAddressFamily == AF_INET) + af4 = 1; + if (lpqsRestrictions->lpafpProtocols[0].iAddressFamily == AF_INET6) + af6 = 1; + } + } + if (af4 && !af6) + msg->af = htonl (AF_INET); + else if (af6 && !af4) + msg->af = htonl (AF_INET6); + else + msg->af = htonl (AF_UNSPEC); + if (lpqsRestrictions->lpszServiceInstanceName) + memcpy (&msg[1], lpqsRestrictions->lpszServiceInstanceName, namelen); + msg->sc_data1 = htonl (lpqsRestrictions->lpServiceClassId->Data1); + msg->sc_data2 = htons (lpqsRestrictions->lpServiceClassId->Data2); + msg->sc_data3 = htons (lpqsRestrictions->lpServiceClassId->Data3); + msg->sc_data4 = 0; + for (i = 0; i < 8; i++) + msg->sc_data4 |= ((uint64_t) lpqsRestrictions->lpServiceClassId->Data4[i]) << ((7 - i) * 8); + msg->sc_data4 = GNUNET_htonll (msg->sc_data4); + *resolver = connect_to_dns_resolver (); + if (*resolver != INVALID_SOCKET) + { + if (size != send (*resolver, buf, size, 0)) + { + DWORD err = GetLastError (); + closesocket (*resolver); + *resolver = INVALID_SOCKET; + DEBUGLOG ("GNUNET_W32NSP_LookupServiceBegin: failed to send request: %lu\n", err); + SetLastError (WSATRY_AGAIN); + ret = 0; + } + } + else + ret = 0; + free (buf); + return ret; +} + +int WSPAPI +NSPCleanup (LPGUID lpProviderId) +{ + DEBUGLOG ("NSPCleanup\n"); + if (IsEqualGUID (lpProviderId, &GNUNET_NAMESPACE_PROVIDER_DNS)) + { + return NO_ERROR; + } + SetLastError (WSAEINVALIDPROVIDER); + return SOCKET_ERROR; +} + +BOOL WINAPI +DllMain (HINSTANCE hinstDLL, DWORD fdwReason, LPVOID lpvReserved) +{ + switch (fdwReason) + { + case DLL_PROCESS_ATTACH: + if (!InitializeCriticalSectionAndSpinCount (&records_cs, 0x00000400)) + { + return FALSE; + } + break; + case DLL_THREAD_ATTACH: + break; + case DLL_THREAD_DETACH: + break; + case DLL_PROCESS_DETACH: + DeleteCriticalSection (&records_cs); + break; + } + return TRUE; +} + + + + +int WSPAPI +GNUNET_W32NSP_LookupServiceBegin (LPGUID lpProviderId, LPWSAQUERYSETW lpqsRestrictions, + LPWSASERVICECLASSINFOW lpServiceClassInfo, DWORD dwControlFlags, + LPHANDLE lphLookup) +{ + DEBUGLOG ("GNUNET_W32NSP_LookupServiceBegin\n"); + if (IsEqualGUID (lpProviderId, &GNUNET_NAMESPACE_PROVIDER_DNS)) + { + SOCKET s; + if (lpqsRestrictions->dwNameSpace != NS_DNS && lpqsRestrictions->dwNameSpace != NS_ALL) + { + DEBUGLOG ("GNUNET_W32NSP_LookupServiceBegin: wrong namespace\n"); + SetLastError (WSANO_DATA); + return SOCKET_ERROR; + } + if (lpqsRestrictions->lpszServiceInstanceName != NULL) + { + wchar_t *s = lpqsRestrictions->lpszServiceInstanceName; + size_t len = wcslen (s); + if (len >= 4 && wcscmp (&s[len - 4], L"zkey") == 0) + { + } + else if (len >= 4 && wcscmp (&s[len - 4], L"gads") == 0) + { + } + else + { + DEBUGLOG ("GNUNET_W32NSP_LookupServiceBegin: unsupported TLD\n"); + SetLastError (WSANO_DATA); + return SOCKET_ERROR; + } + } + + if (send_name_to_ip_request (lpqsRestrictions, + lpServiceClassInfo, dwControlFlags, &s)) + { + if (!(add_record (s, lpqsRestrictions->lpszServiceInstanceName, dwControlFlags))) + { + DWORD err = GetLastError (); + DEBUGLOG ("GNUNET_W32NSP_LookupServiceBegin: failed to add a record\n"); + closesocket (s); + SetLastError (err); + return SOCKET_ERROR; + } + *lphLookup = (HANDLE) s; + DEBUGLOG ("GNUNET_W32NSP_LookupServiceBegin: OK (%lu)\n", GetLastError ()); + return NO_ERROR; + } + return SOCKET_ERROR; + } + DEBUGLOG ("GNUNET_W32NSP_LookupServiceBegin: wrong provider\n"); + SetLastError (WSAEINVALIDPROVIDER); + return SOCKET_ERROR; +} + +#define UnmarshallPtr(ptr, ptrtype, base) \ + if (ptr) \ + ptr = (ptrtype *) (base + (uintptr_t) ptr) + +void +UnmarshallWSAQUERYSETW (LPWSAQUERYSETW req) +{ + int i; + char *base = (char *) req; + UnmarshallPtr (req->lpszServiceInstanceName, wchar_t, base); + UnmarshallPtr (req->lpServiceClassId, GUID, base); + UnmarshallPtr (req->lpVersion, WSAVERSION, base); + UnmarshallPtr (req->lpszComment, wchar_t, base); + UnmarshallPtr (req->lpNSProviderId, GUID, base); + UnmarshallPtr (req->lpszContext, wchar_t, base); + UnmarshallPtr (req->lpafpProtocols, AFPROTOCOLS, base); + UnmarshallPtr (req->lpszQueryString, wchar_t, base); + UnmarshallPtr (req->lpcsaBuffer, CSADDR_INFO, base); + for (i = 0; i < req->dwNumberOfCsAddrs; i++) + { + UnmarshallPtr (req->lpcsaBuffer[i].LocalAddr.lpSockaddr, SOCKADDR, base); + UnmarshallPtr (req->lpcsaBuffer[i].RemoteAddr.lpSockaddr, SOCKADDR, base); + } + UnmarshallPtr (req->lpBlob, BLOB, base); + if (req->lpBlob) + UnmarshallPtr (req->lpBlob->pBlobData, BYTE, base); +} + +int WSAAPI +GNUNET_W32NSP_LookupServiceNext (HANDLE hLookup, DWORD dwControlFlags, + LPDWORD lpdwBufferLength, LPWSAQUERYSET lpqsResults) +{ + DWORD effective_flags; + int i; + struct GNUNET_MessageHeader header = {0, 0}; + int rec = -1; + int rc; + int to_receive; + int t; + char *buf; + + DEBUGLOG ("GNUNET_W32NSP_LookupServiceNext\n"); + //EnterCriticalSection (&records_cs); + for (i = 0; i < records_len; i++) + { + if (records[i].s == (SOCKET) hLookup) + { + rec = i; + break; + } + } + if (rec == -1) + { + DEBUGLOG ("GNUNET_W32NSP_LookupServiceNext: invalid handle\n"); + SetLastError (WSA_INVALID_HANDLE); + //LeaveCriticalSection (&records_cs); + return SOCKET_ERROR; + } + if (records[rec].state & 4) + { + DEBUGLOG ("GNUNET_W32NSP_LookupServiceNext: session is closed\n"); + SetLastError (WSA_E_NO_MORE); + //LeaveCriticalSection (&records_cs); + return SOCKET_ERROR; + } + effective_flags = dwControlFlags & records[rec].flags; + if (records[rec].buf) + { + header = *((struct GNUNET_MessageHeader *) records[rec].buf); + if (dwControlFlags & LUP_FLUSHCACHE) + { + free (records[rec].buf); + records[rec].buf = NULL; + } + else + { + if (*lpdwBufferLength < header.size - sizeof (struct GNUNET_W32RESOLVER_GetMessage)) + { + DEBUGLOG ("GNUNET_W32NSP_LookupServiceNext: client buffer is too small\n"); + SetLastError (WSAEFAULT); + //LeaveCriticalSection (&records_cs); + return SOCKET_ERROR; + } + memcpy (lpqsResults, &((struct GNUNET_W32RESOLVER_GetMessage *)records[rec].buf)[1], header.size - sizeof (struct GNUNET_W32RESOLVER_GetMessage)); + free (records[rec].buf); + records[rec].buf = NULL; + //LeaveCriticalSection (&records_cs); + UnmarshallWSAQUERYSETW ((LPWSAQUERYSETW) lpqsResults); + DEBUGLOG ("GNUNET_W32NSP_LookupServiceNext: OK (from buffer)\n"); + return NO_ERROR; + } + } + records[rec].state |= 8; + //LeaveCriticalSection (&records_cs); + to_receive = sizeof (header); + rc = 0; + while (to_receive > 0) + { + t = recv ((SOCKET) hLookup, &((char *) &header)[rc], to_receive, 0); + if (t > 0) + { + rc += t; + to_receive -= t; + } + else + break; + } + //EnterCriticalSection (&records_cs); + records[rec].state &= ~8; + if (rc != sizeof (header)) + { + if (records[rec].state & 2) + { + DEBUGLOG ("GNUNET_W32NSP_LookupServiceNext: call cancelled\n"); + SetLastError (WSA_E_CANCELLED); + } + else + { + DEBUGLOG ("GNUNET_W32NSP_LookupServiceNext: failed to receive enough data\n"); + SetLastError (WSA_E_NO_MORE); + } + records[rec].state |= 4; + //LeaveCriticalSection (&records_cs); + return SOCKET_ERROR; + } + records[rec].state &= ~8; + header.type = ntohs (header.type); + header.size = ntohs (header.size); + if (header.type != GNUNET_MESSAGE_TYPE_W32RESOLVER_RESPONSE || + (header.type == GNUNET_MESSAGE_TYPE_W32RESOLVER_RESPONSE && + header.size == sizeof (header))) + { + records[rec].state |= 4; + DEBUGLOG ("GNUNET_W32NSP_LookupServiceNext: header is wrong or type is wrong or no data\n"); + //LeaveCriticalSection (&records_cs); + SetLastError (WSA_E_NO_MORE); + return SOCKET_ERROR; + } + buf = malloc (header.size); + if (buf == NULL) + { + records[rec].state |= 4; + DEBUGLOG ("GNUNET_W32NSP_LookupServiceNext: malloc() failed\n"); + //LeaveCriticalSection (&records_cs); + SetLastError (WSA_E_NO_MORE); + return SOCKET_ERROR; + } + records[rec].state |= 8; + //LeaveCriticalSection (&records_cs); + memcpy (buf, &header, sizeof (header)); + to_receive = header.size - sizeof (header); + rc = 0; + while (to_receive > 0) + { + t = recv ((SOCKET) hLookup, &((char *) &((struct GNUNET_MessageHeader *) buf)[1])[rc], to_receive, 0); + if (t > 0) + { + rc += t; + to_receive -= t; + } + else + break; + } + //EnterCriticalSection (&records_cs); + records[rec].state &= ~8; + if (rc != header.size - sizeof (header)) + { + free (buf); + if (records[rec].state & 2) + { + DEBUGLOG ("GNUNET_W32NSP_LookupServiceNext: call cancelled\n"); + SetLastError (WSA_E_CANCELLED); + } + else + { + DEBUGLOG ("GNUNET_W32NSP_LookupServiceNext: failed to receive enough data\n"); + SetLastError (WSA_E_NO_MORE); + } + records[rec].state |= 4; + //LeaveCriticalSection (&records_cs); + return SOCKET_ERROR; + } + if (*lpdwBufferLength < header.size - sizeof (struct GNUNET_W32RESOLVER_GetMessage)) + { + DEBUGLOG ("GNUNET_W32NSP_LookupServiceNext: client buffer is too small\n"); + SetLastError (WSAEFAULT); + records[rec].buf = buf; + //LeaveCriticalSection (&records_cs); + return SOCKET_ERROR; + } + //LeaveCriticalSection (&records_cs); + memcpy (lpqsResults, &((struct GNUNET_W32RESOLVER_GetMessage *)buf)[1], header.size - sizeof (struct GNUNET_W32RESOLVER_GetMessage)); + free (buf); + DEBUGLOG ("GNUNET_W32NSP_LookupServiceNext: OK\n"); + UnmarshallWSAQUERYSETW ((LPWSAQUERYSETW) lpqsResults); + DEBUGLOG ("GNUNET_W32NSP_LookupServiceNext: returning (%lu)\n", GetLastError ()); + return NO_ERROR; +} + +int WSPAPI +GNUNET_W32NSP_LookupServiceEnd (HANDLE hLookup) +{ + DWORD effective_flags; + int i; + struct GNUNET_MessageHeader header = {0, 0}; + int rec = -1; + int rc; + char *buf; + + DEBUGLOG ("GNUNET_W32NSP_LookupServiceEnd\n"); + //EnterCriticalSection (&records_cs); + for (i = 0; i < records_len; i++) + { + if (records[i].s == (SOCKET) hLookup) + { + rec = i; + break; + } + } + if (rec == -1) + { + SetLastError (WSA_INVALID_HANDLE); + //LeaveCriticalSection (&records_cs); + DEBUGLOG ("GNUNET_W32NSP_LookupServiceEnd: invalid handle\n"); + return SOCKET_ERROR; + } + records[rec].state |= 2; + closesocket (records[rec].s); + while (records[rec].state & 8) + { + //LeaveCriticalSection (&records_cs); + Sleep (10); + //EnterCriticalSection (&records_cs); + } + if (records[rec].buf) + free (records[rec].buf); + records[rec].buf = NULL; + records[rec].state = 0; + if (records[rec].name) + free (records[rec].name); + //LeaveCriticalSection (&records_cs); + DEBUGLOG ("GNUNET_W32NSP_LookupServiceEnd: OK\n"); + return NO_ERROR; +} + +int WSAAPI +GNUNET_W32NSP_SetService (LPGUID lpProviderId, + LPWSASERVICECLASSINFOW lpServiceClassInfo, LPWSAQUERYSETW lpqsRegInfo, + WSAESETSERVICEOP essOperation, DWORD dwControlFlags) +{ + DEBUGLOG ("GNUNET_W32NSP_SetService\n"); + SetLastError (WSAEOPNOTSUPP); + return SOCKET_ERROR; +} + +int WSAAPI +GNUNET_W32NSP_InstallServiceClass (LPGUID lpProviderId, + LPWSASERVICECLASSINFOW lpServiceClassInfo) +{ + DEBUGLOG ("GNUNET_W32NSP_InstallServiceClass\n"); + SetLastError (WSAEOPNOTSUPP); + return SOCKET_ERROR; +} + + +int WSAAPI +GNUNET_W32NSP_RemoveServiceClass (LPGUID lpProviderId, LPGUID lpServiceClassId) +{ + DEBUGLOG ("GNUNET_W32NSP_RemoveServiceClass\n"); + SetLastError (WSAEOPNOTSUPP); + return SOCKET_ERROR; +} + +int WSAAPI +GNUNET_W32NSP_GetServiceClassInfo (LPGUID lpProviderId, LPDWORD lpdwBufSize, + LPWSASERVICECLASSINFOW lpServiceClassInfo) +{ + DEBUGLOG ("GNUNET_W32NSP_GetServiceClassInfo\n"); + SetLastError (WSAEOPNOTSUPP); + return SOCKET_ERROR; +} + +int WSAAPI +GNUNET_W32NSP_Ioctl (HANDLE hLookup, DWORD dwControlCode, LPVOID lpvInBuffer, + DWORD cbInBuffer, LPVOID lpvOutBuffer, DWORD cbOutBuffer, + LPDWORD lpcbBytesReturned, LPWSACOMPLETION lpCompletion, + LPWSATHREADID lpThreadId) +{ + DEBUGLOG ("GNUNET_W32NSP_Ioctl\n"); + SetLastError (WSAEOPNOTSUPP); + return SOCKET_ERROR; +} + +/** + * This function is called by Winsock to hook up our provider. + * It is the only function that [should be/is] exported by the + * provider. All other routines are passed as pointers in lpnspRoutines. + */ +int WSPAPI +NSPStartup (LPGUID lpProviderId, LPNSP_ROUTINE lpnspRoutines) +{ + if (IsEqualGUID (lpProviderId, &GNUNET_NAMESPACE_PROVIDER_DNS)) + { + if (!connect_to_dns_resolver ()) + { + return SOCKET_ERROR; + } + /* This assumes that NSP_ROUTINE struct doesn't have a NSPIoctl member. + * If it does, you need to use FIELD_OFFSET() macro to get offset of NSPIoctl + * and use that offset as cbSize. + */ + lpnspRoutines->cbSize = sizeof(NSP_ROUTINE_XP); + + lpnspRoutines->dwMajorVersion = NSPAPI_VERSION_MAJOR; + lpnspRoutines->dwMinorVersion = NSPAPI_VERSION_MINOR; + lpnspRoutines->NSPCleanup = NSPCleanup; + lpnspRoutines->NSPLookupServiceBegin = GNUNET_W32NSP_LookupServiceBegin; + lpnspRoutines->NSPLookupServiceNext = GNUNET_W32NSP_LookupServiceNext; + lpnspRoutines->NSPLookupServiceEnd = GNUNET_W32NSP_LookupServiceEnd; + lpnspRoutines->NSPSetService = GNUNET_W32NSP_SetService; + lpnspRoutines->NSPInstallServiceClass = GNUNET_W32NSP_InstallServiceClass; + lpnspRoutines->NSPRemoveServiceClass = GNUNET_W32NSP_RemoveServiceClass; + lpnspRoutines->NSPGetServiceClassInfo = GNUNET_W32NSP_GetServiceClassInfo; + ((NSP_ROUTINE_XP *) lpnspRoutines)->NSPIoctl = GNUNET_W32NSP_Ioctl; + return NO_ERROR; + } + SetLastError (WSAEINVALIDPROVIDER); + return SOCKET_ERROR; +} + diff --git a/src/gns/zonefiles/188JSUMKEF25GVU8TTV0PBNNN8JVCPUEDFV1UHJJU884JD25V0T0.zkey b/src/gns/zonefiles/188JSUMKEF25GVU8TTV0PBNNN8JVCPUEDFV1UHJJU884JD25V0T0.zkey new file mode 100644 index 0000000..b0fae62 Binary files /dev/null and b/src/gns/zonefiles/188JSUMKEF25GVU8TTV0PBNNN8JVCPUEDFV1UHJJU884JD25V0T0.zkey differ diff --git a/src/gns/zonefiles/OEFL7A4VEF1B40QLEMTG5D8G1CN6EN16QUSG5R2DT71GRJN34LSG.zkey b/src/gns/zonefiles/OEFL7A4VEF1B40QLEMTG5D8G1CN6EN16QUSG5R2DT71GRJN34LSG.zkey new file mode 100644 index 0000000..90da077 Binary files /dev/null and b/src/gns/zonefiles/OEFL7A4VEF1B40QLEMTG5D8G1CN6EN16QUSG5R2DT71GRJN34LSG.zkey differ diff --git a/src/gns/zonefiles/test_zonekey b/src/gns/zonefiles/test_zonekey new file mode 100644 index 0000000..cfa7606 Binary files /dev/null and b/src/gns/zonefiles/test_zonekey differ diff --git a/src/hello/Makefile.am b/src/hello/Makefile.am index 26aa6c7..fd5a41b 100644 --- a/src/hello/Makefile.am +++ b/src/hello/Makefile.am @@ -14,10 +14,11 @@ lib_LTLIBRARIES = libgnunethello.la libgnunethello_la_SOURCES = \ hello.c address.c libgnunethello_la_LIBADD = \ - $(top_builddir)/src/util/libgnunetutil.la $(XLIB) + $(top_builddir)/src/util/libgnunetutil.la $(XLIB) \ + $(LTLIBINTL) libgnunethello_la_LDFLAGS = \ $(GN_LIB_LDFLAGS) \ - -version-info 0:0:0 + -version-info 1:0:1 noinst_PROGRAMS = \ gnunet-hello diff --git a/src/hello/Makefile.in b/src/hello/Makefile.in index 1887b27..f99eca2 100644 --- a/src/hello/Makefile.in +++ b/src/hello/Makefile.in @@ -1,9 +1,9 @@ -# Makefile.in generated by automake 1.11.1 from Makefile.am. +# Makefile.in generated by automake 1.11.6 from Makefile.am. # @configure_input@ # Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, -# 2003, 2004, 2005, 2006, 2007, 2008, 2009 Free Software Foundation, -# Inc. +# 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Free Software +# Foundation, Inc. # This Makefile.in is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. @@ -17,6 +17,23 @@ VPATH = @srcdir@ +am__make_dryrun = \ + { \ + am__dry=no; \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + echo 'am--echo: ; @echo "AM" OK' | $(MAKE) -f - 2>/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } pkgdatadir = $(datadir)/@PACKAGE@ pkgincludedir = $(includedir)/@PACKAGE@ pkglibdir = $(libdir)/@PACKAGE@ @@ -43,14 +60,15 @@ DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 am__aclocal_m4_deps = $(top_srcdir)/m4/absolute-header.m4 \ $(top_srcdir)/m4/align.m4 $(top_srcdir)/m4/argz.m4 \ - $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/iconv.m4 \ - $(top_srcdir)/m4/lib-ld.m4 $(top_srcdir)/m4/lib-link.m4 \ - $(top_srcdir)/m4/lib-prefix.m4 $(top_srcdir)/m4/libcurl.m4 \ - $(top_srcdir)/m4/libgcrypt.m4 $(top_srcdir)/m4/libtool.m4 \ - $(top_srcdir)/m4/libunistring.m4 $(top_srcdir)/m4/ltdl.m4 \ - $(top_srcdir)/m4/ltoptions.m4 $(top_srcdir)/m4/ltsugar.m4 \ - $(top_srcdir)/m4/ltversion.m4 $(top_srcdir)/m4/lt~obsolete.m4 \ - $(top_srcdir)/m4/nls.m4 $(top_srcdir)/m4/po.m4 \ + $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/glib-2.0.m4 \ + $(top_srcdir)/m4/iconv.m4 $(top_srcdir)/m4/lib-ld.m4 \ + $(top_srcdir)/m4/lib-link.m4 $(top_srcdir)/m4/lib-prefix.m4 \ + $(top_srcdir)/m4/libcurl.m4 $(top_srcdir)/m4/libgcrypt.m4 \ + $(top_srcdir)/m4/libtool.m4 $(top_srcdir)/m4/libunistring.m4 \ + $(top_srcdir)/m4/ltdl.m4 $(top_srcdir)/m4/ltoptions.m4 \ + $(top_srcdir)/m4/ltsugar.m4 $(top_srcdir)/m4/ltversion.m4 \ + $(top_srcdir)/m4/lt~obsolete.m4 $(top_srcdir)/m4/nls.m4 \ + $(top_srcdir)/m4/pkg.m4 $(top_srcdir)/m4/po.m4 \ $(top_srcdir)/m4/progtest.m4 $(top_srcdir)/acinclude.m4 \ $(top_srcdir)/configure.ac am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ @@ -80,16 +98,22 @@ am__nobase_list = $(am__nobase_strip_setup); \ am__base_list = \ sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \ sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g' +am__uninstall_files_from_dir = { \ + test -z "$$files" \ + || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \ + || { echo " ( cd '$$dir' && rm -f" $$files ")"; \ + $(am__cd) "$$dir" && rm -f $$files; }; \ + } am__installdirs = "$(DESTDIR)$(libdir)" LTLIBRARIES = $(lib_LTLIBRARIES) am__DEPENDENCIES_1 = libgnunethello_la_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la \ - $(am__DEPENDENCIES_1) + $(am__DEPENDENCIES_1) $(am__DEPENDENCIES_1) am_libgnunethello_la_OBJECTS = hello.lo address.lo libgnunethello_la_OBJECTS = $(am_libgnunethello_la_OBJECTS) -AM_V_lt = $(am__v_lt_$(V)) -am__v_lt_ = $(am__v_lt_$(AM_DEFAULT_VERBOSITY)) +AM_V_lt = $(am__v_lt_@AM_V@) +am__v_lt_ = $(am__v_lt_@AM_DEFAULT_V@) am__v_lt_0 = --silent libgnunethello_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ @@ -112,26 +136,31 @@ LTCOMPILE = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) \ $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) \ $(AM_CFLAGS) $(CFLAGS) -AM_V_CC = $(am__v_CC_$(V)) -am__v_CC_ = $(am__v_CC_$(AM_DEFAULT_VERBOSITY)) +AM_V_CC = $(am__v_CC_@AM_V@) +am__v_CC_ = $(am__v_CC_@AM_DEFAULT_V@) am__v_CC_0 = @echo " CC " $@; -AM_V_at = $(am__v_at_$(V)) -am__v_at_ = $(am__v_at_$(AM_DEFAULT_VERBOSITY)) +AM_V_at = $(am__v_at_@AM_V@) +am__v_at_ = $(am__v_at_@AM_DEFAULT_V@) am__v_at_0 = @ CCLD = $(CC) LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ $(AM_LDFLAGS) $(LDFLAGS) -o $@ -AM_V_CCLD = $(am__v_CCLD_$(V)) -am__v_CCLD_ = $(am__v_CCLD_$(AM_DEFAULT_VERBOSITY)) +AM_V_CCLD = $(am__v_CCLD_@AM_V@) +am__v_CCLD_ = $(am__v_CCLD_@AM_DEFAULT_V@) am__v_CCLD_0 = @echo " CCLD " $@; -AM_V_GEN = $(am__v_GEN_$(V)) -am__v_GEN_ = $(am__v_GEN_$(AM_DEFAULT_VERBOSITY)) +AM_V_GEN = $(am__v_GEN_@AM_V@) +am__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@) am__v_GEN_0 = @echo " GEN " $@; SOURCES = $(libgnunethello_la_SOURCES) $(gnunet_hello_SOURCES) \ $(test_hello_SOURCES) DIST_SOURCES = $(libgnunethello_la_SOURCES) $(gnunet_hello_SOURCES) \ $(test_hello_SOURCES) +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac ETAGS = etags CTAGS = ctags am__tty_colors = \ @@ -172,6 +201,10 @@ EXEEXT = @EXEEXT@ EXT_LIBS = @EXT_LIBS@ EXT_LIB_PATH = @EXT_LIB_PATH@ FGREP = @FGREP@ +GLIB_CFLAGS = @GLIB_CFLAGS@ +GLIB_GENMARSHAL = @GLIB_GENMARSHAL@ +GLIB_LIBS = @GLIB_LIBS@ +GLIB_MKENUMS = @GLIB_MKENUMS@ GMSGFMT = @GMSGFMT@ GMSGFMT_015 = @GMSGFMT_015@ GNUNETDNS_GROUP = @GNUNETDNS_GROUP@ @@ -182,6 +215,7 @@ GN_LIBINTL = @GN_LIBINTL@ GN_LIB_LDFLAGS = @GN_LIB_LDFLAGS@ GN_PLUGIN_LDFLAGS = @GN_PLUGIN_LDFLAGS@ GN_USER_HOME_DIR = @GN_USER_HOME_DIR@ +GOBJECT_QUERY = @GOBJECT_QUERY@ GREP = @GREP@ HAVE_LIBUNISTRING = @HAVE_LIBUNISTRING@ INCLTDL = @INCLTDL@ @@ -204,6 +238,8 @@ LIBCURL_CPPFLAGS = @LIBCURL_CPPFLAGS@ LIBGCRYPT_CFLAGS = @LIBGCRYPT_CFLAGS@ LIBGCRYPT_CONFIG = @LIBGCRYPT_CONFIG@ LIBGCRYPT_LIBS = @LIBGCRYPT_LIBS@ +LIBGTOP_CFLAGS = @LIBGTOP_CFLAGS@ +LIBGTOP_LIBS = @LIBGTOP_LIBS@ LIBICONV = @LIBICONV@ LIBINTL = @LIBINTL@ LIBLTDL = @LIBLTDL@ @@ -225,6 +261,7 @@ LT_CONFIG_H = @LT_CONFIG_H@ LT_DLLOADERS = @LT_DLLOADERS@ LT_DLPREOPEN = @LT_DLPREOPEN@ MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ MKDIR_P = @MKDIR_P@ MONKEYPREFIX = @MONKEYPREFIX@ MSGFMT = @MSGFMT@ @@ -234,6 +271,7 @@ MYSQL_CPPFLAGS = @MYSQL_CPPFLAGS@ MYSQL_LDFLAGS = @MYSQL_LDFLAGS@ NM = @NM@ NMEDIT = @NMEDIT@ +NSS_DIR = @NSS_DIR@ OBJC = @OBJC@ OBJCDEPMODE = @OBJCDEPMODE@ OBJCFLAGS = @OBJCFLAGS@ @@ -249,6 +287,7 @@ PACKAGE_TARNAME = @PACKAGE_TARNAME@ PACKAGE_URL = @PACKAGE_URL@ PACKAGE_VERSION = @PACKAGE_VERSION@ PATH_SEPARATOR = @PATH_SEPARATOR@ +PKG_CONFIG = @PKG_CONFIG@ POSTGRES_CPPFLAGS = @POSTGRES_CPPFLAGS@ POSTGRES_LDFLAGS = @POSTGRES_LDFLAGS@ POSUB = @POSUB@ @@ -280,6 +319,7 @@ abs_builddir = @abs_builddir@ abs_srcdir = @abs_srcdir@ abs_top_builddir = @abs_top_builddir@ abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ ac_ct_CC = @ac_ct_CC@ ac_ct_CXX = @ac_ct_CXX@ ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ @@ -302,6 +342,7 @@ datarootdir = @datarootdir@ docdir = @docdir@ dvidir = @dvidir@ exec_prefix = @exec_prefix@ +gitcommand = @gitcommand@ host = @host@ host_alias = @host_alias@ host_cpu = @host_cpu@ @@ -315,7 +356,6 @@ libdir = @libdir@ libexecdir = @libexecdir@ localedir = @localedir@ localstatedir = @localstatedir@ -lt_ECHO = @lt_ECHO@ ltdl_LIBOBJS = @ltdl_LIBOBJS@ ltdl_LTLIBOBJS = @ltdl_LTLIBOBJS@ mandir = @mandir@ @@ -333,6 +373,7 @@ sbindir = @sbindir@ sharedstatedir = @sharedstatedir@ srcdir = @srcdir@ subdirs = @subdirs@ +svnversioncommand = @svnversioncommand@ sys_symbol_underscore = @sys_symbol_underscore@ sysconfdir = @sysconfdir@ target = @target@ @@ -352,11 +393,12 @@ libgnunethello_la_SOURCES = \ hello.c address.c libgnunethello_la_LIBADD = \ - $(top_builddir)/src/util/libgnunetutil.la $(XLIB) + $(top_builddir)/src/util/libgnunetutil.la $(XLIB) \ + $(LTLIBINTL) libgnunethello_la_LDFLAGS = \ $(GN_LIB_LDFLAGS) \ - -version-info 0:0:0 + -version-info 1:0:1 @ENABLE_TEST_RUN_TRUE@TESTS = $(check_PROGRAMS) test_hello_SOURCES = \ @@ -413,7 +455,6 @@ $(ACLOCAL_M4): $(am__aclocal_m4_deps) $(am__aclocal_m4_deps): install-libLTLIBRARIES: $(lib_LTLIBRARIES) @$(NORMAL_INSTALL) - test -z "$(libdir)" || $(MKDIR_P) "$(DESTDIR)$(libdir)" @list='$(lib_LTLIBRARIES)'; test -n "$(libdir)" || list=; \ list2=; for p in $$list; do \ if test -f $$p; then \ @@ -421,6 +462,8 @@ install-libLTLIBRARIES: $(lib_LTLIBRARIES) else :; fi; \ done; \ test -z "$$list2" || { \ + echo " $(MKDIR_P) '$(DESTDIR)$(libdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libdir)" || exit 1; \ echo " $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 '$(DESTDIR)$(libdir)'"; \ $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 "$(DESTDIR)$(libdir)"; \ } @@ -442,7 +485,7 @@ clean-libLTLIBRARIES: echo "rm -f \"$${dir}/so_locations\""; \ rm -f "$${dir}/so_locations"; \ done -libgnunethello.la: $(libgnunethello_la_OBJECTS) $(libgnunethello_la_DEPENDENCIES) +libgnunethello.la: $(libgnunethello_la_OBJECTS) $(libgnunethello_la_DEPENDENCIES) $(EXTRA_libgnunethello_la_DEPENDENCIES) $(AM_V_CCLD)$(libgnunethello_la_LINK) -rpath $(libdir) $(libgnunethello_la_OBJECTS) $(libgnunethello_la_LIBADD) $(LIBS) clean-checkPROGRAMS: @@ -462,10 +505,10 @@ clean-noinstPROGRAMS: list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ echo " rm -f" $$list; \ rm -f $$list -gnunet-hello$(EXEEXT): $(gnunet_hello_OBJECTS) $(gnunet_hello_DEPENDENCIES) +gnunet-hello$(EXEEXT): $(gnunet_hello_OBJECTS) $(gnunet_hello_DEPENDENCIES) $(EXTRA_gnunet_hello_DEPENDENCIES) @rm -f gnunet-hello$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_hello_OBJECTS) $(gnunet_hello_LDADD) $(LIBS) -test_hello$(EXEEXT): $(test_hello_OBJECTS) $(test_hello_DEPENDENCIES) +test_hello$(EXEEXT): $(test_hello_OBJECTS) $(test_hello_DEPENDENCIES) $(EXTRA_test_hello_DEPENDENCIES) @rm -f test_hello$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_hello_OBJECTS) $(test_hello_LDADD) $(LIBS) @@ -483,26 +526,23 @@ distclean-compile: .c.o: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c $< .c.obj: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'` @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c `$(CYGPATH_W) '$<'` +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c `$(CYGPATH_W) '$<'` .c.lo: @am__fastdepCC_TRUE@ $(AM_V_CC)$(LTCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LTCOMPILE) -c -o $@ $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LTCOMPILE) -c -o $@ $< mostlyclean-libtool: -rm -f *.lo @@ -643,14 +683,15 @@ check-TESTS: $(TESTS) fi; \ dashes=`echo "$$dashes" | sed s/./=/g`; \ if test "$$failed" -eq 0; then \ - echo "$$grn$$dashes"; \ + col="$$grn"; \ else \ - echo "$$red$$dashes"; \ + col="$$red"; \ fi; \ - echo "$$banner"; \ - test -z "$$skipped" || echo "$$skipped"; \ - test -z "$$report" || echo "$$report"; \ - echo "$$dashes$$std"; \ + echo "$${col}$$dashes$${std}"; \ + echo "$${col}$$banner$${std}"; \ + test -z "$$skipped" || echo "$${col}$$skipped$${std}"; \ + test -z "$$report" || echo "$${col}$$report$${std}"; \ + echo "$${col}$$dashes$${std}"; \ test "$$failed" -eq 0; \ else :; fi @@ -703,10 +744,15 @@ install-am: all-am installcheck: installcheck-am install-strip: - $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ - install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ - `test -z '$(STRIP)' || \ - echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi mostlyclean-generic: clean-generic: diff --git a/src/hello/address.c b/src/hello/address.c index 893a6dc..67ad8a0 100644 --- a/src/hello/address.c +++ b/src/hello/address.c @@ -113,7 +113,7 @@ GNUNET_HELLO_address_cmp (const struct GNUNET_HELLO_Address *a1, return -1; if (a1->address_length > a2->address_length) return 1; - return memcmp (a1->address, a1->address, a1->address_length); + return memcmp (a1->address, a2->address, a1->address_length); } diff --git a/src/hello/gnunet-hello.c b/src/hello/gnunet-hello.c index bc35cdd..eae16a9 100644 --- a/src/hello/gnunet-hello.c +++ b/src/hello/gnunet-hello.c @@ -25,10 +25,6 @@ #include "platform.h" #include "gnunet_hello_lib.h" -#define DEBUG GNUNET_EXTRA_LOGGING - -#define VERBOSE GNUNET_NO - /** * Closure for 'add_to_buf'. */ diff --git a/src/hello/hello.c b/src/hello/hello.c index 6529c93..becc4da 100644 --- a/src/hello/hello.c +++ b/src/hello/hello.c @@ -27,6 +27,7 @@ #include "gnunet_hello_lib.h" #include "gnunet_protocols.h" #include "gnunet_util_lib.h" +#include "gnunet_transport_plugin.h" GNUNET_NETWORK_STRUCT_BEGIN @@ -63,6 +64,46 @@ struct GNUNET_HELLO_Message }; GNUNET_NETWORK_STRUCT_END + +/** + * Context used for building our own URI. + */ +struct GNUNET_HELLO_ComposeUriContext +{ + /** + * Final URI. + */ + char *uri; + + /** + * Function for finding transport plugins by name. + */ + GNUNET_HELLO_TransportPluginsFind plugins_find; +}; + + +/** + * Context for 'add_address_to_hello'. + */ +struct GNUNET_HELLO_ParseUriContext +{ + /** + * Position in the URI with the next address to parse. + */ + const char *pos; + + /** + * Set to GNUNET_SYSERR to indicate parse errors. + */ + int ret; + + /** + * Function for finding transport plugins by name. + */ + GNUNET_HELLO_TransportPluginsFind plugins_find; +}; + + /** * Copy the given address information into * the given buffer using the format of HELLOs. @@ -650,10 +691,10 @@ GNUNET_HELLO_get_last_expiration (const struct GNUNET_HELLO_Message *msg) * * The concrete URI format is: * - * "gnunet://hello/PEER[!YYYYMMDDHHNNSS!!
]...". + * "gnunet://hello/PEER[!YYYYMMDDHHMMSS!!
]...". * These URIs can be used to add a peer record to peerinfo service. * PEER is the string representation of peer's public key. - * YYYYMMDDHHNNSS is the expiration date. + * YYYYMMDDHHMMSS is the expiration date. * TYPE is a transport type. * ADDRESS is the address, its format depends upon the transport type. * The concrete transport types and corresponding address formats are: @@ -683,4 +724,316 @@ GNUNET_HELLO_get_last_expiration (const struct GNUNET_HELLO_Message *msg) *

*/ + +/* ************************* Compose HELLO URI ************************** */ + + +/** + * Replace all characters in the input 'in' according + * to the mapping. The mapping says to map each character + * in 'oldchars' to the corresponding character (by offset) + * in 'newchars'. + * + * @param in input string to remap + * @param oldchars characters to replace + * @param newchars replacement characters, must have same length as 'oldchars' + * @return copy of string with replacement applied. + */ +static char * +map_characters (const char *in, + const char *oldchars, + const char *newchars) +{ + char *ret; + const char *off; + size_t i; + + GNUNET_assert (strlen (oldchars) == strlen (newchars)); + ret = GNUNET_strdup (in); + i = 0; + while (ret[i] != '\0') + { + off = strchr (oldchars, ret[i]); + if (NULL != off) + ret[i] = newchars[off - oldchars]; + i++; + } + return ret; +} + + +/** + * Function that is called on each address of this peer. + * Expands the corresponding URI string. + * + * @param cls the 'GNUNET_HELLO_GetUriContext' + * @param address address to add + * @param expiration expiration time for the address + * @return GNUNET_OK (continue iteration). + */ +static int +add_address_to_uri (void *cls, const struct GNUNET_HELLO_Address *address, + struct GNUNET_TIME_Absolute expiration) +{ + struct GNUNET_HELLO_ComposeUriContext *ctx = cls; + struct GNUNET_TRANSPORT_PluginFunctions *papi; + const char *addr; + char *uri_addr; + char *ret; + char tbuf[16] = ""; + struct tm *t; + time_t seconds; + + papi = ctx->plugins_find (address->transport_name); + if (papi == NULL) + { + /* Not an error - we might just not have the right plugin. */ + return GNUNET_OK; + } + if (NULL == papi->address_to_string) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "URI conversion not implemented for plugin `%s'\n", + address->transport_name); + return GNUNET_OK; + } + addr = papi->address_to_string (papi->cls, address->address, address->address_length); + if ( (addr == NULL) || (strlen(addr) == 0) ) + return GNUNET_OK; + /* For URIs we use '(' and ')' instead of '[' and ']' as brackets are reserved + characters in URIs */ + uri_addr = map_characters (addr, "[]", "()"); + seconds = expiration.abs_value / 1000; + t = gmtime (&seconds); + + GNUNET_asprintf (&ret, + "%s!%s!%s!%s", + ctx->uri, + strftime (tbuf, sizeof (tbuf), "%Y%m%d%H%M%S", t) ? tbuf : "0", + address->transport_name, + uri_addr); + GNUNET_free (uri_addr); + GNUNET_free (ctx->uri); + ctx->uri = ret; + return GNUNET_OK; +} + + +/** + * Compose a hello URI string from a hello message. + * + * @param hello Hello message + * @param plugins_find Function to find transport plugins by name + * @return Hello URI string + */ +char * +GNUNET_HELLO_compose_uri (const struct GNUNET_HELLO_Message *hello, + GNUNET_HELLO_TransportPluginsFind plugins_find) +{ + struct GNUNET_HELLO_ComposeUriContext ctx; + ctx.plugins_find = plugins_find; + + char *pkey = GNUNET_CRYPTO_rsa_public_key_to_string (&(hello->publicKey)); + GNUNET_asprintf (&(ctx.uri), + "%s%s", + GNUNET_HELLO_URI_PREFIX, + pkey); + GNUNET_free (pkey); + + GNUNET_HELLO_iterate_addresses (hello, GNUNET_NO, &add_address_to_uri, &ctx); + return ctx.uri; +} + + +/* ************************* Parse HELLO URI ********************* */ + + +/** + * We're building a HELLO. Parse the next address from the + * parsing context and append it. + * + * @param cls the 'struct GNUNET_HELLO_AddressParsingContext' + * @param max number of bytes available for HELLO construction + * @param buffer where to copy the next address (in binary format) + * @return number of bytes added to buffer + */ +static size_t +add_address_to_hello (void *cls, size_t max, void *buffer) +{ + struct GNUNET_HELLO_ParseUriContext *ctx = cls; + const char *tname; + const char *address; + char *uri_address; + char *plugin_address; + const char *end; + char *plugin_name; + struct tm expiration_time; + time_t expiration_seconds; + struct GNUNET_TIME_Absolute expire; + struct GNUNET_TRANSPORT_PluginFunctions *papi; + void *addr; + size_t addr_len; + struct GNUNET_HELLO_Address haddr; + size_t ret; + + if (NULL == ctx->pos) + return 0; + if ('!' != ctx->pos[0]) + { + ctx->ret = GNUNET_SYSERR; + GNUNET_break (0); + return 0; + } + ctx->pos++; + + if ('0' == ctx->pos[0] && '!' == ctx->pos[1]) + { + expire = GNUNET_TIME_UNIT_FOREVER_ABS; + tname = ctx->pos + 1; + } + else + { + memset (&expiration_time, 0, sizeof (expiration_time)); + tname = strptime (ctx->pos, + "%Y%m%d%H%M%S", + &expiration_time); + if (NULL == tname) + { + ctx->ret = GNUNET_SYSERR; + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Failed to parse HELLO message: missing expiration time\n")); + GNUNET_break (0); + return 0; + } + + expiration_seconds = mktime (&expiration_time); + if (expiration_seconds == (time_t) -1) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Failed to parse HELLO message: invalid expiration time\n")); + ctx->ret = GNUNET_SYSERR; + GNUNET_break (0); + return 0; + } + expire.abs_value = expiration_seconds * 1000; + } + if ('!' != tname[0]) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Failed to parse HELLO message: malformed\n")); + ctx->ret = GNUNET_SYSERR; + GNUNET_break (0); + return 0; + } + tname++; + address = strchr (tname, (int) '!'); + if (NULL == address) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Failed to parse HELLO message: missing transport plugin\n")); + ctx->ret = GNUNET_SYSERR; + GNUNET_break (0); + return 0; + } + address++; + end = strchr (address, (int) '!'); + ctx->pos = end; + plugin_name = GNUNET_strndup (tname, address - (tname+1)); + papi = ctx->plugins_find (plugin_name); + if (NULL == papi) + { + /* Not an error - we might just not have the right plugin. + * Skip this part, advance to the next one and recurse. + * But only if this is not the end of string. + */ + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Plugin `%s' not found\n"), + plugin_name); + GNUNET_free (plugin_name); + GNUNET_break (0); + return 0; + } + if (NULL == papi->string_to_address) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Plugin `%s' does not support URIs yet\n"), + plugin_name); + GNUNET_free (plugin_name); + GNUNET_break (0); + return 0; + } + uri_address = GNUNET_strndup (address, end - address); + /* For URIs we use '(' and ')' instead of '[' and ']' as brackets are reserved + characters in URIs; need to convert back to '[]' for the plugin */ + plugin_address = map_characters (uri_address, "()", "[]"); + GNUNET_free (uri_address); + if (GNUNET_OK != + papi->string_to_address (papi->cls, + plugin_address, + strlen (plugin_address) + 1, + &addr, + &addr_len)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Failed to parse `%s' as an address for plugin `%s'\n"), + plugin_address, + plugin_name); + GNUNET_free (plugin_name); + GNUNET_free (plugin_address); + return 0; + } + GNUNET_free (plugin_address); + /* address.peer is unset - not used by add_address() */ + haddr.address_length = addr_len; + haddr.address = addr; + haddr.transport_name = plugin_name; + ret = GNUNET_HELLO_add_address (&haddr, expire, buffer, max); + GNUNET_free (addr); + GNUNET_free (plugin_name); + return ret; +} + + +/** + * Parse a hello URI string to a hello message. + * + * @param uri URI string to parse + * @param pubkey Pointer to struct where public key is parsed + * @param hello Pointer to struct where hello message is parsed + * @param plugins_find Function to find transport plugins by name + * @return GNUNET_OK on success, GNUNET_SYSERR if the URI was invalid, GNUNET_NO on other errors + */ +int +GNUNET_HELLO_parse_uri (const char *uri, + struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *pubkey, + struct GNUNET_HELLO_Message **hello, + GNUNET_HELLO_TransportPluginsFind plugins_find) +{ + const char *pks; + const char *exc; + struct GNUNET_HELLO_ParseUriContext ctx; + + if (0 != strncmp (uri, + GNUNET_HELLO_URI_PREFIX, + strlen (GNUNET_HELLO_URI_PREFIX))) + return GNUNET_SYSERR; + pks = &uri[strlen (GNUNET_HELLO_URI_PREFIX)]; + exc = strstr (pks, "!"); + + if (GNUNET_OK != + GNUNET_STRINGS_string_to_data (pks, + (NULL == exc) ? strlen (pks) : (exc - pks), + (unsigned char *) pubkey, + sizeof (*pubkey))) + return GNUNET_SYSERR; + + ctx.pos = exc; + ctx.ret = GNUNET_OK; + ctx.plugins_find = plugins_find; + *hello = GNUNET_HELLO_create (pubkey, &add_address_to_hello, &ctx); + + return ctx.ret; +} + + /* end of hello.c */ diff --git a/src/hello/test_hello.c b/src/hello/test_hello.c index bdabc72..28d4aec 100644 --- a/src/hello/test_hello.c +++ b/src/hello/test_hello.c @@ -25,11 +25,6 @@ #include "platform.h" #include "gnunet_hello_lib.h" -#define DEBUG GNUNET_NO - -#define VERBOSE GNUNET_NO - - static size_t my_addr_gen (void *cls, size_t max, void *buf) { @@ -37,9 +32,8 @@ my_addr_gen (void *cls, size_t max, void *buf) size_t ret; struct GNUNET_HELLO_Address address; -#if DEBUG - FPRINTF (stderr, "DEBUG: my_addr_gen called with i = %d\n", *i); -#endif + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "DEBUG: my_addr_gen called with i = %d\n", *i); if (0 == *i) return 0; memset (&address.peer, 0, sizeof (struct GNUNET_PeerIdentity)); @@ -60,10 +54,9 @@ check_addr (void *cls, const struct GNUNET_HELLO_Address *address, { unsigned int *i = cls; -#if DEBUG - FPRINTF (stderr, "DEBUG: check_addr called with i = %d and addrlen = %u\n", + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "DEBUG: check_addr called with i = %d and addrlen = %u\n", *i, (unsigned int) address->address_length); -#endif GNUNET_assert (address->address_length > 0); GNUNET_assert (*i & (1 << (address->address_length - 1))); *i -= (1 << (address->address_length - 1)); @@ -81,10 +74,9 @@ remove_some (void *cls, const struct GNUNET_HELLO_Address *address, { unsigned int *i = cls; -#if DEBUG - FPRINTF (stderr, "DEBUG: remove_some called with i = %d and addrlen = %u\n", + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "DEBUG: remove_some called with i = %d and addrlen = %u\n", *i, (unsigned int) address->address_length); -#endif GNUNET_assert (address->address_length > 0); if (*i & (1 << (address->address_length - 1))) { @@ -109,65 +101,56 @@ main (int argc, char *argv[]) GNUNET_log_setup ("test-hello", "DEBUG", NULL); startup_time = GNUNET_TIME_absolute_get (); memset (&publicKey, 42, sizeof (publicKey)); -#if VERBOSE - FPRINTF (stderr, "%s", "Testing HELLO creation (without addresses)...\n"); -#endif + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Testing HELLO creation (without addresses)...\n"); i = 0; msg1 = GNUNET_HELLO_create (&publicKey, &my_addr_gen, &i); GNUNET_assert (msg1 != NULL); GNUNET_assert (0 < GNUNET_HELLO_size (msg1)); -#if VERBOSE - FPRINTF (stderr, "%s", "Testing address iteration (empty set)...\n"); -#endif + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Testing address iteration (empty set)...\n"); GNUNET_assert (NULL == GNUNET_HELLO_iterate_addresses (msg1, GNUNET_NO, &check_addr, &i)); - -#if VERBOSE - FPRINTF (stderr, "%s", "Testing HELLO creation (with one address)...\n"); -#endif + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Testing HELLO creation (with one address)...\n"); i = 1; msg2 = GNUNET_HELLO_create (&publicKey, &my_addr_gen, &i); GNUNET_assert (msg2 != NULL); GNUNET_assert (GNUNET_HELLO_size (msg1) < GNUNET_HELLO_size (msg2)); -#if VERBOSE - FPRINTF (stderr, "%s", "Testing address iteration (one address)...\n"); -#endif + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Testing address iteration (one address)...\n"); i = 1; GNUNET_assert (NULL == GNUNET_HELLO_iterate_addresses (msg2, GNUNET_NO, &check_addr, &i)); GNUNET_assert (i == 0); -#if VERBOSE - FPRINTF (stderr, "%s", "Testing get_key from HELLO...\n"); -#endif + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Testing get_key from HELLO...\n"); GNUNET_assert (GNUNET_OK == GNUNET_HELLO_get_key (msg2, &pk)); GNUNET_assert (0 == memcmp (&publicKey, &pk, sizeof (pk))); GNUNET_free (msg1); -#if VERBOSE - FPRINTF (stderr, "%s", "Testing HELLO creation (with two addresses)...\n"); -#endif + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Testing HELLO creation (with two addresses)...\n"); i = 2; msg3 = GNUNET_HELLO_create (&publicKey, &my_addr_gen, &i); GNUNET_assert (msg3 != NULL); GNUNET_assert (GNUNET_HELLO_size (msg2) < GNUNET_HELLO_size (msg3)); -#if VERBOSE - FPRINTF (stderr, "%s", "Testing address iteration (two addresses)...\n"); -#endif + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Testing address iteration (two addresses)...\n"); i = 3; GNUNET_assert (NULL == GNUNET_HELLO_iterate_addresses (msg3, GNUNET_NO, &check_addr, &i)); GNUNET_assert (i == 0); -#if VERBOSE - FPRINTF (stderr, "%s", "Testing HELLO merge...\n"); -#endif + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Testing HELLO merge...\n"); msg1 = GNUNET_HELLO_merge (msg2, msg3); GNUNET_assert (GNUNET_HELLO_size (msg1) == GNUNET_HELLO_size (msg3)); @@ -178,9 +161,8 @@ main (int argc, char *argv[]) GNUNET_assert (i == 0); GNUNET_free (msg1); -#if VERBOSE - FPRINTF (stderr, "%s", "Testing address iteration to copy HELLO...\n"); -#endif + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Testing address iteration to copy HELLO...\n"); i = 2; msg1 = GNUNET_HELLO_iterate_addresses (msg3, GNUNET_YES, &remove_some, &i); GNUNET_assert (msg1 != NULL); @@ -192,9 +174,8 @@ main (int argc, char *argv[]) GNUNET_assert (i == 0); GNUNET_free (msg1); -#if VERBOSE - FPRINTF (stderr, "%s", "Testing delta address iteration...\n"); -#endif + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Testing delta address iteration...\n"); i = 2; GNUNET_HELLO_iterate_new_addresses (msg3, msg2, startup_time, &check_addr, &i); diff --git a/src/hostlist/Makefile.am b/src/hostlist/Makefile.am index f764f2f..726251a 100644 --- a/src/hostlist/Makefile.am +++ b/src/hostlist/Makefile.am @@ -2,6 +2,8 @@ INCLUDES = -I$(top_srcdir)/src/include pkgcfgdir= $(pkgdatadir)/config.d/ +libexecdir= $(pkglibdir)/libexec/ + dist_pkgcfg_DATA = \ hostlist.conf @@ -14,8 +16,10 @@ if HAVE_MHD GN_LIBMHD = -lmicrohttpd endif -bin_PROGRAMS = \ +if HAVE_LIBCURL +libexec_PROGRAMS = \ gnunet-daemon-hostlist +endif gnunet_daemon_hostlist_SOURCES = \ gnunet-daemon-hostlist.c gnunet-daemon-hostlist.h \ @@ -36,6 +40,7 @@ gnunet_daemon_hostlist_LDADD = \ gnunet_daemon_hostlist_CPPFLAGS = \ @LIBCURL_CPPFLAGS@ +if HAVE_LIBCURL check_PROGRAMS = \ test_gnunet_daemon_hostlist \ test_gnunet_daemon_hostlist_reconnect \ @@ -49,6 +54,7 @@ TESTS = \ test_gnunet_daemon_hostlist_learning endif endif +endif test_gnunet_daemon_hostlist_SOURCES = \ test_gnunet_daemon_hostlist.c diff --git a/src/hostlist/Makefile.in b/src/hostlist/Makefile.in index 4777316..7cd73bf 100644 --- a/src/hostlist/Makefile.in +++ b/src/hostlist/Makefile.in @@ -1,9 +1,9 @@ -# Makefile.in generated by automake 1.11.1 from Makefile.am. +# Makefile.in generated by automake 1.11.6 from Makefile.am. # @configure_input@ # Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, -# 2003, 2004, 2005, 2006, 2007, 2008, 2009 Free Software Foundation, -# Inc. +# 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Free Software +# Foundation, Inc. # This Makefile.in is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. @@ -17,6 +17,23 @@ VPATH = @srcdir@ +am__make_dryrun = \ + { \ + am__dry=no; \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + echo 'am--echo: ; @echo "AM" OK' | $(MAKE) -f - 2>/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } pkgdatadir = $(datadir)/@PACKAGE@ pkgincludedir = $(includedir)/@PACKAGE@ pkglibdir = $(libdir)/@PACKAGE@ @@ -36,27 +53,29 @@ POST_UNINSTALL = : build_triplet = @build@ host_triplet = @host@ target_triplet = @target@ -bin_PROGRAMS = gnunet-daemon-hostlist$(EXEEXT) -check_PROGRAMS = test_gnunet_daemon_hostlist$(EXEEXT) \ - test_gnunet_daemon_hostlist_reconnect$(EXEEXT) \ - test_gnunet_daemon_hostlist_learning$(EXEEXT) -@ENABLE_TEST_RUN_TRUE@@HAVE_MHD_TRUE@TESTS = test_gnunet_daemon_hostlist$(EXEEXT) \ -@ENABLE_TEST_RUN_TRUE@@HAVE_MHD_TRUE@ test_gnunet_daemon_hostlist_reconnect$(EXEEXT) \ -@ENABLE_TEST_RUN_TRUE@@HAVE_MHD_TRUE@ test_gnunet_daemon_hostlist_learning$(EXEEXT) +@HAVE_LIBCURL_TRUE@libexec_PROGRAMS = gnunet-daemon-hostlist$(EXEEXT) +@HAVE_LIBCURL_TRUE@check_PROGRAMS = \ +@HAVE_LIBCURL_TRUE@ test_gnunet_daemon_hostlist$(EXEEXT) \ +@HAVE_LIBCURL_TRUE@ test_gnunet_daemon_hostlist_reconnect$(EXEEXT) \ +@HAVE_LIBCURL_TRUE@ test_gnunet_daemon_hostlist_learning$(EXEEXT) +@ENABLE_TEST_RUN_TRUE@@HAVE_LIBCURL_TRUE@@HAVE_MHD_TRUE@TESTS = test_gnunet_daemon_hostlist$(EXEEXT) \ +@ENABLE_TEST_RUN_TRUE@@HAVE_LIBCURL_TRUE@@HAVE_MHD_TRUE@ test_gnunet_daemon_hostlist_reconnect$(EXEEXT) \ +@ENABLE_TEST_RUN_TRUE@@HAVE_LIBCURL_TRUE@@HAVE_MHD_TRUE@ test_gnunet_daemon_hostlist_learning$(EXEEXT) subdir = src/hostlist DIST_COMMON = $(dist_pkgcfg_DATA) $(srcdir)/Makefile.am \ $(srcdir)/Makefile.in ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 am__aclocal_m4_deps = $(top_srcdir)/m4/absolute-header.m4 \ $(top_srcdir)/m4/align.m4 $(top_srcdir)/m4/argz.m4 \ - $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/iconv.m4 \ - $(top_srcdir)/m4/lib-ld.m4 $(top_srcdir)/m4/lib-link.m4 \ - $(top_srcdir)/m4/lib-prefix.m4 $(top_srcdir)/m4/libcurl.m4 \ - $(top_srcdir)/m4/libgcrypt.m4 $(top_srcdir)/m4/libtool.m4 \ - $(top_srcdir)/m4/libunistring.m4 $(top_srcdir)/m4/ltdl.m4 \ - $(top_srcdir)/m4/ltoptions.m4 $(top_srcdir)/m4/ltsugar.m4 \ - $(top_srcdir)/m4/ltversion.m4 $(top_srcdir)/m4/lt~obsolete.m4 \ - $(top_srcdir)/m4/nls.m4 $(top_srcdir)/m4/po.m4 \ + $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/glib-2.0.m4 \ + $(top_srcdir)/m4/iconv.m4 $(top_srcdir)/m4/lib-ld.m4 \ + $(top_srcdir)/m4/lib-link.m4 $(top_srcdir)/m4/lib-prefix.m4 \ + $(top_srcdir)/m4/libcurl.m4 $(top_srcdir)/m4/libgcrypt.m4 \ + $(top_srcdir)/m4/libtool.m4 $(top_srcdir)/m4/libunistring.m4 \ + $(top_srcdir)/m4/ltdl.m4 $(top_srcdir)/m4/ltoptions.m4 \ + $(top_srcdir)/m4/ltsugar.m4 $(top_srcdir)/m4/ltversion.m4 \ + $(top_srcdir)/m4/lt~obsolete.m4 $(top_srcdir)/m4/nls.m4 \ + $(top_srcdir)/m4/pkg.m4 $(top_srcdir)/m4/po.m4 \ $(top_srcdir)/m4/progtest.m4 $(top_srcdir)/acinclude.m4 \ $(top_srcdir)/configure.ac am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ @@ -65,8 +84,8 @@ mkinstalldirs = $(install_sh) -d CONFIG_HEADER = $(top_builddir)/gnunet_config.h CONFIG_CLEAN_FILES = CONFIG_CLEAN_VPATH_FILES = -am__installdirs = "$(DESTDIR)$(bindir)" "$(DESTDIR)$(pkgcfgdir)" -PROGRAMS = $(bin_PROGRAMS) +am__installdirs = "$(DESTDIR)$(libexecdir)" "$(DESTDIR)$(pkgcfgdir)" +PROGRAMS = $(libexec_PROGRAMS) am__gnunet_daemon_hostlist_SOURCES_DIST = gnunet-daemon-hostlist.c \ gnunet-daemon-hostlist.h hostlist-client.c hostlist-client.h \ hostlist-server.c hostlist-server.h @@ -85,8 +104,8 @@ gnunet_daemon_hostlist_DEPENDENCIES = \ $(top_builddir)/src/transport/libgnunettransport.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(am__DEPENDENCIES_1) $(am__DEPENDENCIES_1) -AM_V_lt = $(am__v_lt_$(V)) -am__v_lt_ = $(am__v_lt_$(AM_DEFAULT_VERBOSITY)) +AM_V_lt = $(am__v_lt_@AM_V@) +am__v_lt_ = $(am__v_lt_@AM_DEFAULT_V@) am__v_lt_0 = --silent am_test_gnunet_daemon_hostlist_OBJECTS = \ test_gnunet_daemon_hostlist.$(OBJEXT) @@ -121,21 +140,21 @@ LTCOMPILE = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) \ $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) \ $(AM_CFLAGS) $(CFLAGS) -AM_V_CC = $(am__v_CC_$(V)) -am__v_CC_ = $(am__v_CC_$(AM_DEFAULT_VERBOSITY)) +AM_V_CC = $(am__v_CC_@AM_V@) +am__v_CC_ = $(am__v_CC_@AM_DEFAULT_V@) am__v_CC_0 = @echo " CC " $@; -AM_V_at = $(am__v_at_$(V)) -am__v_at_ = $(am__v_at_$(AM_DEFAULT_VERBOSITY)) +AM_V_at = $(am__v_at_@AM_V@) +am__v_at_ = $(am__v_at_@AM_DEFAULT_V@) am__v_at_0 = @ CCLD = $(CC) LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ $(AM_LDFLAGS) $(LDFLAGS) -o $@ -AM_V_CCLD = $(am__v_CCLD_$(V)) -am__v_CCLD_ = $(am__v_CCLD_$(AM_DEFAULT_VERBOSITY)) +AM_V_CCLD = $(am__v_CCLD_@AM_V@) +am__v_CCLD_ = $(am__v_CCLD_@AM_DEFAULT_V@) am__v_CCLD_0 = @echo " CCLD " $@; -AM_V_GEN = $(am__v_GEN_$(V)) -am__v_GEN_ = $(am__v_GEN_$(AM_DEFAULT_VERBOSITY)) +AM_V_GEN = $(am__v_GEN_@AM_V@) +am__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@) am__v_GEN_0 = @echo " GEN " $@; SOURCES = $(gnunet_daemon_hostlist_SOURCES) \ $(test_gnunet_daemon_hostlist_SOURCES) \ @@ -145,6 +164,11 @@ DIST_SOURCES = $(am__gnunet_daemon_hostlist_SOURCES_DIST) \ $(test_gnunet_daemon_hostlist_SOURCES) \ $(test_gnunet_daemon_hostlist_learning_SOURCES) \ $(test_gnunet_daemon_hostlist_reconnect_SOURCES) +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac am__vpath_adj_setup = srcdirstrip=`echo "$(srcdir)" | sed 's|.|.|g'`; am__vpath_adj = case $$p in \ $(srcdir)/*) f=`echo "$$p" | sed "s|^$$srcdirstrip/||"`;; \ @@ -166,6 +190,12 @@ am__nobase_list = $(am__nobase_strip_setup); \ am__base_list = \ sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \ sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g' +am__uninstall_files_from_dir = { \ + test -z "$$files" \ + || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \ + || { echo " ( cd '$$dir' && rm -f" $$files ")"; \ + $(am__cd) "$$dir" && rm -f $$files; }; \ + } DATA = $(dist_pkgcfg_DATA) ETAGS = etags CTAGS = ctags @@ -207,6 +237,10 @@ EXEEXT = @EXEEXT@ EXT_LIBS = @EXT_LIBS@ EXT_LIB_PATH = @EXT_LIB_PATH@ FGREP = @FGREP@ +GLIB_CFLAGS = @GLIB_CFLAGS@ +GLIB_GENMARSHAL = @GLIB_GENMARSHAL@ +GLIB_LIBS = @GLIB_LIBS@ +GLIB_MKENUMS = @GLIB_MKENUMS@ GMSGFMT = @GMSGFMT@ GMSGFMT_015 = @GMSGFMT_015@ GNUNETDNS_GROUP = @GNUNETDNS_GROUP@ @@ -217,6 +251,7 @@ GN_LIBINTL = @GN_LIBINTL@ GN_LIB_LDFLAGS = @GN_LIB_LDFLAGS@ GN_PLUGIN_LDFLAGS = @GN_PLUGIN_LDFLAGS@ GN_USER_HOME_DIR = @GN_USER_HOME_DIR@ +GOBJECT_QUERY = @GOBJECT_QUERY@ GREP = @GREP@ HAVE_LIBUNISTRING = @HAVE_LIBUNISTRING@ INCLTDL = @INCLTDL@ @@ -239,6 +274,8 @@ LIBCURL_CPPFLAGS = @LIBCURL_CPPFLAGS@ LIBGCRYPT_CFLAGS = @LIBGCRYPT_CFLAGS@ LIBGCRYPT_CONFIG = @LIBGCRYPT_CONFIG@ LIBGCRYPT_LIBS = @LIBGCRYPT_LIBS@ +LIBGTOP_CFLAGS = @LIBGTOP_CFLAGS@ +LIBGTOP_LIBS = @LIBGTOP_LIBS@ LIBICONV = @LIBICONV@ LIBINTL = @LIBINTL@ LIBLTDL = @LIBLTDL@ @@ -260,6 +297,7 @@ LT_CONFIG_H = @LT_CONFIG_H@ LT_DLLOADERS = @LT_DLLOADERS@ LT_DLPREOPEN = @LT_DLPREOPEN@ MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ MKDIR_P = @MKDIR_P@ MONKEYPREFIX = @MONKEYPREFIX@ MSGFMT = @MSGFMT@ @@ -269,6 +307,7 @@ MYSQL_CPPFLAGS = @MYSQL_CPPFLAGS@ MYSQL_LDFLAGS = @MYSQL_LDFLAGS@ NM = @NM@ NMEDIT = @NMEDIT@ +NSS_DIR = @NSS_DIR@ OBJC = @OBJC@ OBJCDEPMODE = @OBJCDEPMODE@ OBJCFLAGS = @OBJCFLAGS@ @@ -284,6 +323,7 @@ PACKAGE_TARNAME = @PACKAGE_TARNAME@ PACKAGE_URL = @PACKAGE_URL@ PACKAGE_VERSION = @PACKAGE_VERSION@ PATH_SEPARATOR = @PATH_SEPARATOR@ +PKG_CONFIG = @PKG_CONFIG@ POSTGRES_CPPFLAGS = @POSTGRES_CPPFLAGS@ POSTGRES_LDFLAGS = @POSTGRES_LDFLAGS@ POSUB = @POSUB@ @@ -315,6 +355,7 @@ abs_builddir = @abs_builddir@ abs_srcdir = @abs_srcdir@ abs_top_builddir = @abs_top_builddir@ abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ ac_ct_CC = @ac_ct_CC@ ac_ct_CXX = @ac_ct_CXX@ ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ @@ -337,6 +378,7 @@ datarootdir = @datarootdir@ docdir = @docdir@ dvidir = @dvidir@ exec_prefix = @exec_prefix@ +gitcommand = @gitcommand@ host = @host@ host_alias = @host_alias@ host_cpu = @host_cpu@ @@ -347,10 +389,9 @@ includedir = @includedir@ infodir = @infodir@ install_sh = @install_sh@ libdir = @libdir@ -libexecdir = @libexecdir@ +libexecdir = $(pkglibdir)/libexec/ localedir = @localedir@ localstatedir = @localstatedir@ -lt_ECHO = @lt_ECHO@ ltdl_LIBOBJS = @ltdl_LIBOBJS@ ltdl_LTLIBOBJS = @ltdl_LTLIBOBJS@ mandir = @mandir@ @@ -368,6 +409,7 @@ sbindir = @sbindir@ sharedstatedir = @sharedstatedir@ srcdir = @srcdir@ subdirs = @subdirs@ +svnversioncommand = @svnversioncommand@ sys_symbol_underscore = @sys_symbol_underscore@ sysconfdir = @sysconfdir@ target = @target@ @@ -472,10 +514,22 @@ $(top_srcdir)/configure: $(am__configure_deps) $(ACLOCAL_M4): $(am__aclocal_m4_deps) cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh $(am__aclocal_m4_deps): -install-binPROGRAMS: $(bin_PROGRAMS) + +clean-checkPROGRAMS: + @list='$(check_PROGRAMS)'; test -n "$$list" || exit 0; \ + echo " rm -f" $$list; \ + rm -f $$list || exit $$?; \ + test -n "$(EXEEXT)" || exit 0; \ + list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ + echo " rm -f" $$list; \ + rm -f $$list +install-libexecPROGRAMS: $(libexec_PROGRAMS) @$(NORMAL_INSTALL) - test -z "$(bindir)" || $(MKDIR_P) "$(DESTDIR)$(bindir)" - @list='$(bin_PROGRAMS)'; test -n "$(bindir)" || list=; \ + @list='$(libexec_PROGRAMS)'; test -n "$(libexecdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(libexecdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libexecdir)" || exit 1; \ + fi; \ for p in $$list; do echo "$$p $$p"; done | \ sed 's/$(EXEEXT)$$//' | \ while read p p1; do if test -f $$p || test -f $$p1; \ @@ -492,48 +546,39 @@ install-binPROGRAMS: $(bin_PROGRAMS) while read type dir files; do \ if test "$$dir" = .; then dir=; else dir=/$$dir; fi; \ test -z "$$files" || { \ - echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files '$(DESTDIR)$(bindir)$$dir'"; \ - $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files "$(DESTDIR)$(bindir)$$dir" || exit $$?; \ + echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files '$(DESTDIR)$(libexecdir)$$dir'"; \ + $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files "$(DESTDIR)$(libexecdir)$$dir" || exit $$?; \ } \ ; done -uninstall-binPROGRAMS: +uninstall-libexecPROGRAMS: @$(NORMAL_UNINSTALL) - @list='$(bin_PROGRAMS)'; test -n "$(bindir)" || list=; \ + @list='$(libexec_PROGRAMS)'; test -n "$(libexecdir)" || list=; \ files=`for p in $$list; do echo "$$p"; done | \ sed -e 'h;s,^.*/,,;s/$(EXEEXT)$$//;$(transform)' \ -e 's/$$/$(EXEEXT)/' `; \ test -n "$$list" || exit 0; \ - echo " ( cd '$(DESTDIR)$(bindir)' && rm -f" $$files ")"; \ - cd "$(DESTDIR)$(bindir)" && rm -f $$files + echo " ( cd '$(DESTDIR)$(libexecdir)' && rm -f" $$files ")"; \ + cd "$(DESTDIR)$(libexecdir)" && rm -f $$files -clean-binPROGRAMS: - @list='$(bin_PROGRAMS)'; test -n "$$list" || exit 0; \ +clean-libexecPROGRAMS: + @list='$(libexec_PROGRAMS)'; test -n "$$list" || exit 0; \ echo " rm -f" $$list; \ rm -f $$list || exit $$?; \ test -n "$(EXEEXT)" || exit 0; \ list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ echo " rm -f" $$list; \ rm -f $$list - -clean-checkPROGRAMS: - @list='$(check_PROGRAMS)'; test -n "$$list" || exit 0; \ - echo " rm -f" $$list; \ - rm -f $$list || exit $$?; \ - test -n "$(EXEEXT)" || exit 0; \ - list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ - echo " rm -f" $$list; \ - rm -f $$list -gnunet-daemon-hostlist$(EXEEXT): $(gnunet_daemon_hostlist_OBJECTS) $(gnunet_daemon_hostlist_DEPENDENCIES) +gnunet-daemon-hostlist$(EXEEXT): $(gnunet_daemon_hostlist_OBJECTS) $(gnunet_daemon_hostlist_DEPENDENCIES) $(EXTRA_gnunet_daemon_hostlist_DEPENDENCIES) @rm -f gnunet-daemon-hostlist$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_daemon_hostlist_OBJECTS) $(gnunet_daemon_hostlist_LDADD) $(LIBS) -test_gnunet_daemon_hostlist$(EXEEXT): $(test_gnunet_daemon_hostlist_OBJECTS) $(test_gnunet_daemon_hostlist_DEPENDENCIES) +test_gnunet_daemon_hostlist$(EXEEXT): $(test_gnunet_daemon_hostlist_OBJECTS) $(test_gnunet_daemon_hostlist_DEPENDENCIES) $(EXTRA_test_gnunet_daemon_hostlist_DEPENDENCIES) @rm -f test_gnunet_daemon_hostlist$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_gnunet_daemon_hostlist_OBJECTS) $(test_gnunet_daemon_hostlist_LDADD) $(LIBS) -test_gnunet_daemon_hostlist_learning$(EXEEXT): $(test_gnunet_daemon_hostlist_learning_OBJECTS) $(test_gnunet_daemon_hostlist_learning_DEPENDENCIES) +test_gnunet_daemon_hostlist_learning$(EXEEXT): $(test_gnunet_daemon_hostlist_learning_OBJECTS) $(test_gnunet_daemon_hostlist_learning_DEPENDENCIES) $(EXTRA_test_gnunet_daemon_hostlist_learning_DEPENDENCIES) @rm -f test_gnunet_daemon_hostlist_learning$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_gnunet_daemon_hostlist_learning_OBJECTS) $(test_gnunet_daemon_hostlist_learning_LDADD) $(LIBS) -test_gnunet_daemon_hostlist_reconnect$(EXEEXT): $(test_gnunet_daemon_hostlist_reconnect_OBJECTS) $(test_gnunet_daemon_hostlist_reconnect_DEPENDENCIES) +test_gnunet_daemon_hostlist_reconnect$(EXEEXT): $(test_gnunet_daemon_hostlist_reconnect_OBJECTS) $(test_gnunet_daemon_hostlist_reconnect_DEPENDENCIES) $(EXTRA_test_gnunet_daemon_hostlist_reconnect_DEPENDENCIES) @rm -f test_gnunet_daemon_hostlist_reconnect$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_gnunet_daemon_hostlist_reconnect_OBJECTS) $(test_gnunet_daemon_hostlist_reconnect_LDADD) $(LIBS) @@ -553,74 +598,65 @@ distclean-compile: .c.o: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c $< .c.obj: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'` @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c `$(CYGPATH_W) '$<'` +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c `$(CYGPATH_W) '$<'` .c.lo: @am__fastdepCC_TRUE@ $(AM_V_CC)$(LTCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LTCOMPILE) -c -o $@ $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LTCOMPILE) -c -o $@ $< gnunet_daemon_hostlist-gnunet-daemon-hostlist.o: gnunet-daemon-hostlist.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(gnunet_daemon_hostlist_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT gnunet_daemon_hostlist-gnunet-daemon-hostlist.o -MD -MP -MF $(DEPDIR)/gnunet_daemon_hostlist-gnunet-daemon-hostlist.Tpo -c -o gnunet_daemon_hostlist-gnunet-daemon-hostlist.o `test -f 'gnunet-daemon-hostlist.c' || echo '$(srcdir)/'`gnunet-daemon-hostlist.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/gnunet_daemon_hostlist-gnunet-daemon-hostlist.Tpo $(DEPDIR)/gnunet_daemon_hostlist-gnunet-daemon-hostlist.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='gnunet-daemon-hostlist.c' object='gnunet_daemon_hostlist-gnunet-daemon-hostlist.o' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='gnunet-daemon-hostlist.c' object='gnunet_daemon_hostlist-gnunet-daemon-hostlist.o' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(gnunet_daemon_hostlist_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o gnunet_daemon_hostlist-gnunet-daemon-hostlist.o `test -f 'gnunet-daemon-hostlist.c' || echo '$(srcdir)/'`gnunet-daemon-hostlist.c +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(gnunet_daemon_hostlist_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o gnunet_daemon_hostlist-gnunet-daemon-hostlist.o `test -f 'gnunet-daemon-hostlist.c' || echo '$(srcdir)/'`gnunet-daemon-hostlist.c gnunet_daemon_hostlist-gnunet-daemon-hostlist.obj: gnunet-daemon-hostlist.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(gnunet_daemon_hostlist_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT gnunet_daemon_hostlist-gnunet-daemon-hostlist.obj -MD -MP -MF $(DEPDIR)/gnunet_daemon_hostlist-gnunet-daemon-hostlist.Tpo -c -o gnunet_daemon_hostlist-gnunet-daemon-hostlist.obj `if test -f 'gnunet-daemon-hostlist.c'; then $(CYGPATH_W) 'gnunet-daemon-hostlist.c'; else $(CYGPATH_W) '$(srcdir)/gnunet-daemon-hostlist.c'; fi` @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/gnunet_daemon_hostlist-gnunet-daemon-hostlist.Tpo $(DEPDIR)/gnunet_daemon_hostlist-gnunet-daemon-hostlist.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='gnunet-daemon-hostlist.c' object='gnunet_daemon_hostlist-gnunet-daemon-hostlist.obj' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='gnunet-daemon-hostlist.c' object='gnunet_daemon_hostlist-gnunet-daemon-hostlist.obj' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(gnunet_daemon_hostlist_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o gnunet_daemon_hostlist-gnunet-daemon-hostlist.obj `if test -f 'gnunet-daemon-hostlist.c'; then $(CYGPATH_W) 'gnunet-daemon-hostlist.c'; else $(CYGPATH_W) '$(srcdir)/gnunet-daemon-hostlist.c'; fi` +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(gnunet_daemon_hostlist_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o gnunet_daemon_hostlist-gnunet-daemon-hostlist.obj `if test -f 'gnunet-daemon-hostlist.c'; then $(CYGPATH_W) 'gnunet-daemon-hostlist.c'; else $(CYGPATH_W) '$(srcdir)/gnunet-daemon-hostlist.c'; fi` gnunet_daemon_hostlist-hostlist-client.o: hostlist-client.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(gnunet_daemon_hostlist_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT gnunet_daemon_hostlist-hostlist-client.o -MD -MP -MF $(DEPDIR)/gnunet_daemon_hostlist-hostlist-client.Tpo -c -o gnunet_daemon_hostlist-hostlist-client.o `test -f 'hostlist-client.c' || echo '$(srcdir)/'`hostlist-client.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/gnunet_daemon_hostlist-hostlist-client.Tpo $(DEPDIR)/gnunet_daemon_hostlist-hostlist-client.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='hostlist-client.c' object='gnunet_daemon_hostlist-hostlist-client.o' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='hostlist-client.c' object='gnunet_daemon_hostlist-hostlist-client.o' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(gnunet_daemon_hostlist_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o gnunet_daemon_hostlist-hostlist-client.o `test -f 'hostlist-client.c' || echo '$(srcdir)/'`hostlist-client.c +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(gnunet_daemon_hostlist_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o gnunet_daemon_hostlist-hostlist-client.o `test -f 'hostlist-client.c' || echo '$(srcdir)/'`hostlist-client.c gnunet_daemon_hostlist-hostlist-client.obj: hostlist-client.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(gnunet_daemon_hostlist_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT gnunet_daemon_hostlist-hostlist-client.obj -MD -MP -MF $(DEPDIR)/gnunet_daemon_hostlist-hostlist-client.Tpo -c -o gnunet_daemon_hostlist-hostlist-client.obj `if test -f 'hostlist-client.c'; then $(CYGPATH_W) 'hostlist-client.c'; else $(CYGPATH_W) '$(srcdir)/hostlist-client.c'; fi` @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/gnunet_daemon_hostlist-hostlist-client.Tpo $(DEPDIR)/gnunet_daemon_hostlist-hostlist-client.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='hostlist-client.c' object='gnunet_daemon_hostlist-hostlist-client.obj' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='hostlist-client.c' object='gnunet_daemon_hostlist-hostlist-client.obj' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(gnunet_daemon_hostlist_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o gnunet_daemon_hostlist-hostlist-client.obj `if test -f 'hostlist-client.c'; then $(CYGPATH_W) 'hostlist-client.c'; else $(CYGPATH_W) '$(srcdir)/hostlist-client.c'; fi` +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(gnunet_daemon_hostlist_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o gnunet_daemon_hostlist-hostlist-client.obj `if test -f 'hostlist-client.c'; then $(CYGPATH_W) 'hostlist-client.c'; else $(CYGPATH_W) '$(srcdir)/hostlist-client.c'; fi` gnunet_daemon_hostlist-hostlist-server.o: hostlist-server.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(gnunet_daemon_hostlist_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT gnunet_daemon_hostlist-hostlist-server.o -MD -MP -MF $(DEPDIR)/gnunet_daemon_hostlist-hostlist-server.Tpo -c -o gnunet_daemon_hostlist-hostlist-server.o `test -f 'hostlist-server.c' || echo '$(srcdir)/'`hostlist-server.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/gnunet_daemon_hostlist-hostlist-server.Tpo $(DEPDIR)/gnunet_daemon_hostlist-hostlist-server.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='hostlist-server.c' object='gnunet_daemon_hostlist-hostlist-server.o' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='hostlist-server.c' object='gnunet_daemon_hostlist-hostlist-server.o' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(gnunet_daemon_hostlist_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o gnunet_daemon_hostlist-hostlist-server.o `test -f 'hostlist-server.c' || echo '$(srcdir)/'`hostlist-server.c +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(gnunet_daemon_hostlist_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o gnunet_daemon_hostlist-hostlist-server.o `test -f 'hostlist-server.c' || echo '$(srcdir)/'`hostlist-server.c gnunet_daemon_hostlist-hostlist-server.obj: hostlist-server.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(gnunet_daemon_hostlist_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT gnunet_daemon_hostlist-hostlist-server.obj -MD -MP -MF $(DEPDIR)/gnunet_daemon_hostlist-hostlist-server.Tpo -c -o gnunet_daemon_hostlist-hostlist-server.obj `if test -f 'hostlist-server.c'; then $(CYGPATH_W) 'hostlist-server.c'; else $(CYGPATH_W) '$(srcdir)/hostlist-server.c'; fi` @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/gnunet_daemon_hostlist-hostlist-server.Tpo $(DEPDIR)/gnunet_daemon_hostlist-hostlist-server.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='hostlist-server.c' object='gnunet_daemon_hostlist-hostlist-server.obj' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='hostlist-server.c' object='gnunet_daemon_hostlist-hostlist-server.obj' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(gnunet_daemon_hostlist_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o gnunet_daemon_hostlist-hostlist-server.obj `if test -f 'hostlist-server.c'; then $(CYGPATH_W) 'hostlist-server.c'; else $(CYGPATH_W) '$(srcdir)/hostlist-server.c'; fi` +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(gnunet_daemon_hostlist_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o gnunet_daemon_hostlist-hostlist-server.obj `if test -f 'hostlist-server.c'; then $(CYGPATH_W) 'hostlist-server.c'; else $(CYGPATH_W) '$(srcdir)/hostlist-server.c'; fi` mostlyclean-libtool: -rm -f *.lo @@ -629,8 +665,11 @@ clean-libtool: -rm -rf .libs _libs install-dist_pkgcfgDATA: $(dist_pkgcfg_DATA) @$(NORMAL_INSTALL) - test -z "$(pkgcfgdir)" || $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" @list='$(dist_pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(pkgcfgdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" || exit 1; \ + fi; \ for p in $$list; do \ if test -f "$$p"; then d=; else d="$(srcdir)/"; fi; \ echo "$$d$$p"; \ @@ -644,9 +683,7 @@ uninstall-dist_pkgcfgDATA: @$(NORMAL_UNINSTALL) @list='$(dist_pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ files=`for p in $$list; do echo $$p; done | sed -e 's|^.*/||'`; \ - test -n "$$files" || exit 0; \ - echo " ( cd '$(DESTDIR)$(pkgcfgdir)' && rm -f" $$files ")"; \ - cd "$(DESTDIR)$(pkgcfgdir)" && rm -f $$files + dir='$(DESTDIR)$(pkgcfgdir)'; $(am__uninstall_files_from_dir) ID: $(HEADERS) $(SOURCES) $(LISP) $(TAGS_FILES) list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ @@ -781,14 +818,15 @@ check-TESTS: $(TESTS) fi; \ dashes=`echo "$$dashes" | sed s/./=/g`; \ if test "$$failed" -eq 0; then \ - echo "$$grn$$dashes"; \ + col="$$grn"; \ else \ - echo "$$red$$dashes"; \ + col="$$red"; \ fi; \ - echo "$$banner"; \ - test -z "$$skipped" || echo "$$skipped"; \ - test -z "$$report" || echo "$$report"; \ - echo "$$dashes$$std"; \ + echo "$${col}$$dashes$${std}"; \ + echo "$${col}$$banner$${std}"; \ + test -z "$$skipped" || echo "$${col}$$skipped$${std}"; \ + test -z "$$report" || echo "$${col}$$report$${std}"; \ + echo "$${col}$$dashes$${std}"; \ test "$$failed" -eq 0; \ else :; fi @@ -828,7 +866,7 @@ check-am: all-am check: check-am all-am: Makefile $(PROGRAMS) $(DATA) installdirs: - for dir in "$(DESTDIR)$(bindir)" "$(DESTDIR)$(pkgcfgdir)"; do \ + for dir in "$(DESTDIR)$(libexecdir)" "$(DESTDIR)$(pkgcfgdir)"; do \ test -z "$$dir" || $(MKDIR_P) "$$dir"; \ done install: install-am @@ -841,10 +879,15 @@ install-am: all-am installcheck: installcheck-am install-strip: - $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ - install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ - `test -z '$(STRIP)' || \ - echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi mostlyclean-generic: clean-generic: @@ -858,7 +901,7 @@ maintainer-clean-generic: @echo "it deletes files that may require special tools to rebuild." clean: clean-am -clean-am: clean-binPROGRAMS clean-checkPROGRAMS clean-generic \ +clean-am: clean-checkPROGRAMS clean-generic clean-libexecPROGRAMS \ clean-libtool mostlyclean-am distclean: distclean-am @@ -885,7 +928,7 @@ install-dvi: install-dvi-am install-dvi-am: -install-exec-am: install-binPROGRAMS +install-exec-am: install-libexecPROGRAMS install-html: install-html-am @@ -925,25 +968,25 @@ ps: ps-am ps-am: -uninstall-am: uninstall-binPROGRAMS uninstall-dist_pkgcfgDATA +uninstall-am: uninstall-dist_pkgcfgDATA uninstall-libexecPROGRAMS .MAKE: check-am install-am install-strip .PHONY: CTAGS GTAGS all all-am check check-TESTS check-am clean \ - clean-binPROGRAMS clean-checkPROGRAMS clean-generic \ + clean-checkPROGRAMS clean-generic clean-libexecPROGRAMS \ clean-libtool ctags distclean distclean-compile \ distclean-generic distclean-libtool distclean-tags distdir dvi \ dvi-am html html-am info info-am install install-am \ - install-binPROGRAMS install-data install-data-am \ - install-dist_pkgcfgDATA install-dvi install-dvi-am \ - install-exec install-exec-am install-html install-html-am \ - install-info install-info-am install-man install-pdf \ - install-pdf-am install-ps install-ps-am install-strip \ - installcheck installcheck-am installdirs maintainer-clean \ + install-data install-data-am install-dist_pkgcfgDATA \ + install-dvi install-dvi-am install-exec install-exec-am \ + install-html install-html-am install-info install-info-am \ + install-libexecPROGRAMS install-man install-pdf install-pdf-am \ + install-ps install-ps-am install-strip installcheck \ + installcheck-am installdirs maintainer-clean \ maintainer-clean-generic mostlyclean mostlyclean-compile \ mostlyclean-generic mostlyclean-libtool pdf pdf-am ps ps-am \ - tags uninstall uninstall-am uninstall-binPROGRAMS \ - uninstall-dist_pkgcfgDATA + tags uninstall uninstall-am uninstall-dist_pkgcfgDATA \ + uninstall-libexecPROGRAMS # Tell versions [3.59,3.63) of GNU make to not export all variables. diff --git a/src/hostlist/gnunet-daemon-hostlist.c b/src/hostlist/gnunet-daemon-hostlist.c index 0eedb56..255f0d5 100644 --- a/src/hostlist/gnunet-daemon-hostlist.c +++ b/src/hostlist/gnunet-daemon-hostlist.c @@ -270,7 +270,7 @@ run (void *cls, char *const *args, const char *cfgfile, stats = GNUNET_STATISTICS_create ("hostlist", cfg); core = - GNUNET_CORE_connect (cfg, 1, NULL, &core_init, &connect_handler, + GNUNET_CORE_connect (cfg, NULL, &core_init, &connect_handler, &disconnect_handler, NULL, GNUNET_NO, NULL, GNUNET_NO, learning ? learn_handlers : no_learn_handlers); @@ -334,13 +334,16 @@ main (int argc, char *const *argv) int ret; + if (GNUNET_OK != GNUNET_STRINGS_get_utf8_args (argc, argv, &argc, &argv)) + return 2; + GNUNET_log_setup ("hostlist", "WARNING", NULL); ret = (GNUNET_OK == GNUNET_PROGRAM_run (argc, argv, "hostlist", _("GNUnet hostlist server and client"), options, &run, NULL)) ? 0 : 1; - + GNUNET_free ((void*) argv); return ret; } diff --git a/src/hostlist/hostlist-client.c b/src/hostlist/hostlist-client.c index 6be37fc..7b87196 100644 --- a/src/hostlist/hostlist-client.c +++ b/src/hostlist/hostlist-client.c @@ -298,7 +298,7 @@ callback_download (void *ptr, size_t size, size_t nmemb, void *ctx) left -= cpy; if (download_pos < sizeof (struct GNUNET_MessageHeader)) { - GNUNET_assert (left == 0); + GNUNET_assert (0 == left); break; } msg = (const struct GNUNET_MessageHeader *) download_buffer; @@ -370,10 +370,8 @@ get_bootstrap_server () GNUNET_CONFIGURATION_get_value_string (cfg, "HOSTLIST", "SERVERS", &servers)) { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - _ - ("No `%s' specified in `%s' configuration, will not bootstrap.\n"), - "SERVERS", "HOSTLIST"); + GNUNET_log_config_missing (GNUNET_ERROR_TYPE_WARNING, + "hostlist", "SERVERS"); return NULL; } @@ -391,10 +389,8 @@ get_bootstrap_server () } if (urls == 0) { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - _ - ("No `%s' specified in `%s' configuration, will not bootstrap.\n"), - "SERVERS", "HOSTLIST"); + GNUNET_log_config_missing (GNUNET_ERROR_TYPE_WARNING, + "hostlist", "SERVERS"); GNUNET_free (servers); return NULL; } @@ -470,7 +466,7 @@ download_get_url () } -#define CURL_EASY_SETOPT(c, a, b) do { ret = curl_easy_setopt(c, a, b); if (ret != CURLE_OK) GNUNET_log(GNUNET_ERROR_TYPE_WARNING, _("%s failed at %s:%d: `%s'\n"), "curl_easy_setopt", __FILE__, __LINE__, curl_easy_strerror(ret)); } while (0) +#define CURL_EASY_SETOPT(c, a, b) do { ret = curl_easy_setopt (c, a, b); if (CURLE_OK != ret) GNUNET_log(GNUNET_ERROR_TYPE_WARNING, _("%s failed at %s:%d: `%s'\n"), "curl_easy_setopt", __FILE__, __LINE__, curl_easy_strerror (ret)); } while (0) /** @@ -499,10 +495,10 @@ checked_add (uint64_t val1, uint64_t val2) temp = val1 + val2; if (temp < val1) return maxv; - else - return temp; + return temp; } + /** * Subtract val2 from val1 with underflow check * @param val1 value 1 @@ -514,10 +510,10 @@ checked_sub (uint64_t val1, uint64_t val2) { if (val1 <= val2) return 0; - else - return (val1 - val2); + return (val1 - val2); } + /** * Method to check if a URI is in hostlist linked list * @param uri uri to check @@ -647,6 +643,7 @@ update_hostlist () stat_use_bootstrap = GNUNET_YES; } + /** * Clean up the state from the task that downloaded the * hostlist and schedule the next task. @@ -998,6 +995,7 @@ task_download_dispatcher (void *cls, } } + /** * Task that checks if we should try to download a hostlist. * If so, we initiate the download, otherwise we schedule @@ -1042,10 +1040,9 @@ task_check (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) once = 1; } GNUNET_log (GNUNET_ERROR_TYPE_INFO, - _ - ("Have %u/%u connections. Will consider downloading hostlist in %llums\n"), + _("Have %u/%u connections. Will consider downloading hostlist in %s\n"), stat_connection_count, MIN_CONNECTIONS, - (unsigned long long) delay.rel_value); + GNUNET_STRINGS_relative_time_to_string (delay, GNUNET_YES)); ti_check_download = GNUNET_SCHEDULER_add_delayed (delay, &task_check, NULL); } @@ -1081,12 +1078,11 @@ task_hostlist_saving (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) ti_saving_task = GNUNET_SCHEDULER_NO_TASK; if (0 != (tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN)) return; - GNUNET_log (GNUNET_ERROR_TYPE_INFO, _("Scheduled saving of hostlists\n")); save_hostlist_file (GNUNET_NO); - GNUNET_log (GNUNET_ERROR_TYPE_INFO, - _("Hostlists will be saved to file again in %llums\n"), - (unsigned long long) SAVING_INTERVALL.rel_value); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Hostlists will be saved to file again in %s\n", + GNUNET_STRINGS_relative_time_to_string(SAVING_INTERVALL, GNUNET_YES)); ti_saving_task = GNUNET_SCHEDULER_add_delayed (SAVING_INTERVALL, &task_hostlist_saving, NULL); @@ -1214,7 +1210,6 @@ handler_advertisement (void *cls, const struct GNUNET_PeerIdentity *peer, } - /** * Continuation called by the statistics code once * we go the stat. Initiates hostlist download scheduling. @@ -1238,13 +1233,14 @@ static int process_stat (void *cls, const char *subsystem, const char *name, uint64_t value, int is_persistent) { - GNUNET_log (GNUNET_ERROR_TYPE_INFO, - _("Initial time between hostlist downloads is %llums\n"), - (unsigned long long) value); hostlist_delay.rel_value = value; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Initial time between hostlist downloads is %s\n", + GNUNET_STRINGS_relative_time_to_string (hostlist_delay, GNUNET_YES)); return GNUNET_OK; } + /** * Method to load persistent hostlist file during hostlist client startup */ @@ -1268,10 +1264,8 @@ load_hostlist_file () GNUNET_CONFIGURATION_get_value_filename (cfg, "HOSTLIST", "HOSTLISTFILE", &filename)) { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - _ - ("No `%s' specified in `%s' configuration, cannot load hostlists from file.\n"), - "HOSTLISTFILE", "HOSTLIST"); + GNUNET_log_config_missing (GNUNET_ERROR_TYPE_WARNING, + "hostlist", "HOSTLISTFILE"); return; } @@ -1280,7 +1274,7 @@ load_hostlist_file () if (GNUNET_NO == GNUNET_DISK_file_test (filename)) { GNUNET_log (GNUNET_ERROR_TYPE_INFO, - _("Hostlist file `%s' is not existing\n"), filename); + _("Hostlist file `%s' does not exist\n"), filename); GNUNET_free (filename); return; } @@ -1333,7 +1327,7 @@ load_hostlist_file () GNUNET_free_non_null (uri); emsg = NULL; - GNUNET_BIO_read_close (rh, &emsg); + (void) GNUNET_BIO_read_close (rh, &emsg); if (emsg != NULL) GNUNET_free (emsg); GNUNET_free (filename); @@ -1357,10 +1351,8 @@ save_hostlist_file (int shutdown) GNUNET_CONFIGURATION_get_value_filename (cfg, "HOSTLIST", "HOSTLISTFILE", &filename)) { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - _ - ("No `%s' specified in `%s' configuration, cannot save hostlists to file.\n"), - "HOSTLISTFILE", "HOSTLIST"); + GNUNET_log_config_missing (GNUNET_ERROR_TYPE_WARNING, + "hostlist", "HOSTLISTFILE"); return; } if (GNUNET_SYSERR == GNUNET_DISK_directory_create_for_file (filename)) @@ -1423,6 +1415,7 @@ save_hostlist_file (int shutdown) GNUNET_free (filename); } + /** * Start downloading hostlists from hostlist servers as necessary. */ @@ -1469,9 +1462,9 @@ GNUNET_HOSTLIST_client_start (const struct GNUNET_CONFIGURATION_Handle *c, GNUNET_log (GNUNET_ERROR_TYPE_INFO, _("Learning is enabled on this peer\n")); load_hostlist_file (); - GNUNET_log (GNUNET_ERROR_TYPE_INFO, - _("Hostlists will be saved to file again in %llums\n"), - (unsigned long long) SAVING_INTERVALL.rel_value); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Hostlists will be saved to file again in %s\n", + GNUNET_STRINGS_relative_time_to_string (SAVING_INTERVALL, GNUNET_YES)); ti_saving_task = GNUNET_SCHEDULER_add_delayed (SAVING_INTERVALL, &task_hostlist_saving, NULL); diff --git a/src/hostlist/hostlist-server.c b/src/hostlist/hostlist-server.c index af46110..04da6e9 100644 --- a/src/hostlist/hostlist-server.c +++ b/src/hostlist/hostlist-server.c @@ -180,7 +180,7 @@ host_processor (void *cls, const struct GNUNET_PeerIdentity *peer, { GNUNET_assert (NULL == peer); pitr = NULL; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + GNUNET_log (GNUNET_ERROR_TYPE_INFO, _("Error in communication with PEERINFO service: %s\n"), err_msg); return; @@ -270,7 +270,7 @@ access_handler_callback (void *cls, struct MHD_Connection *connection, if (NULL == *con_cls) { (*con_cls) = &dummy; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, _("Sending 100 CONTINUE reply\n")); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Sending 100 CONTINUE reply\n"); return MHD_YES; /* send 100 continue */ } if (0 != *upload_data_size) @@ -421,7 +421,7 @@ process_notify (void *cls, const struct GNUNET_PeerIdentity *peer, GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Peerinfo is notifying us to rebuild our hostlist\n"); if (NULL != err_msg) - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + GNUNET_log (GNUNET_ERROR_TYPE_INFO, _("Error in communication with PEERINFO service: %s\n"), err_msg); if (NULL != pitr) @@ -465,6 +465,7 @@ run_daemon (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) hostlist_task_v6 = prepare_daemon (daemon_handle); } +#define UNSIGNED_MHD_LONG_LONG unsigned MHD_LONG_LONG /** * Function that queries MHD's select sets and @@ -481,7 +482,7 @@ prepare_daemon (struct MHD_Daemon *daemon_handle) struct GNUNET_NETWORK_FDSet *wws; struct GNUNET_NETWORK_FDSet *wes; int max; - unsigned MHD_LONG_LONG timeout; + UNSIGNED_MHD_LONG_LONG timeout; int haveto; struct GNUNET_TIME_Relative tv; diff --git a/src/hostlist/hostlist.conf b/src/hostlist/hostlist.conf index f7c1be3..7d79720 100644 --- a/src/hostlist/hostlist.conf +++ b/src/hostlist/hostlist.conf @@ -3,11 +3,10 @@ HTTPPORT = 8080 HOME = $SERVICEHOME HOSTLISTFILE = $SERVICEHOME/hostlist/learned.data -CONFIG = $DEFAULTCONFIG BINARY = gnunet-daemon-hostlist # consider having "-e" as default as well once implemented OPTIONS = -b -SERVERS = http://v9.gnunet.org/hostlist http://ioerror.gnunet.org:65535/ +SERVERS = http://gnunet.org/hostlist http://ioerror.gnunet.org:65535/ # proxy for downloading hostlists HTTP-PROXY = # bind hostlist http server to a specific IPv4 or IPv6 diff --git a/src/hostlist/test_gnunet_daemon_hostlist.c b/src/hostlist/test_gnunet_daemon_hostlist.c index f13f86d..5602609 100644 --- a/src/hostlist/test_gnunet_daemon_hostlist.c +++ b/src/hostlist/test_gnunet_daemon_hostlist.c @@ -27,10 +27,6 @@ #include "gnunet_arm_service.h" #include "gnunet_transport_service.h" -#define VERBOSE GNUNET_NO - -#define START_ARM GNUNET_YES - /** * How long until we give up on transmitting the message? @@ -47,9 +43,7 @@ struct PeerContext struct GNUNET_TRANSPORT_Handle *th; struct GNUNET_MessageHeader *hello; struct GNUNET_TRANSPORT_GetHelloHandle *ghh; -#if START_ARM struct GNUNET_OS_Process *arm_proc; -#endif }; static struct PeerContext p1; @@ -137,18 +131,20 @@ process_hello (void *cls, const struct GNUNET_MessageHeader *message) static void setup_peer (struct PeerContext *p, const char *cfgname) { + char *binary; + + binary = GNUNET_OS_get_libexec_binary_path ("gnunet-service-arm"); p->cfg = GNUNET_CONFIGURATION_create (); -#if START_ARM p->arm_proc = - GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-arm", + GNUNET_OS_start_process (GNUNET_YES, GNUNET_OS_INHERIT_STD_OUT_AND_ERR, NULL, NULL, binary, "gnunet-service-arm", "-c", cfgname, NULL); -#endif GNUNET_assert (GNUNET_OK == GNUNET_CONFIGURATION_load (p->cfg, cfgname)); p->th = GNUNET_TRANSPORT_connect (p->cfg, NULL, p, NULL, ¬ify_connect, NULL); GNUNET_assert (p->th != NULL); p->ghh = GNUNET_TRANSPORT_get_hello (p->th, &process_hello, p); + GNUNET_free (binary); } @@ -157,7 +153,6 @@ waitpid_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { struct PeerContext *p = cls; -#if START_ARM GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Killing ARM process.\n"); if (0 != GNUNET_OS_process_kill (p->arm_proc, SIGTERM)) GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); @@ -167,7 +162,6 @@ waitpid_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) GNUNET_OS_process_get_pid (p->arm_proc)); GNUNET_OS_process_destroy (p->arm_proc); p->arm_proc = NULL; -#endif GNUNET_CONFIGURATION_destroy (p->cfg); } diff --git a/src/hostlist/test_gnunet_daemon_hostlist_learning.c b/src/hostlist/test_gnunet_daemon_hostlist_learning.c index 08ab0de..b719963 100644 --- a/src/hostlist/test_gnunet_daemon_hostlist_learning.c +++ b/src/hostlist/test_gnunet_daemon_hostlist_learning.c @@ -30,8 +30,6 @@ #include "gnunet_resolver_service.h" #include "gnunet_statistics_service.h" -#define START_ARM GNUNET_YES - #define MAX_URL_LEN 1000 /** @@ -49,9 +47,7 @@ struct PeerContext struct GNUNET_MessageHeader *hello; struct GNUNET_CORE_Handle *core; struct GNUNET_STATISTICS_Handle *stats; -#if START_ARM struct GNUNET_OS_Process *arm_proc; -#endif }; static int timeout; @@ -147,7 +143,6 @@ shutdown_testcase () GNUNET_CORE_disconnect (learn_peer.core); learn_peer.core = NULL; } -#if START_ARM GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Killing hostlist server ARM process.\n"); if (0 != GNUNET_OS_process_kill (adv_peer.arm_proc, SIGTERM)) @@ -164,7 +159,6 @@ shutdown_testcase () GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "waitpid"); GNUNET_OS_process_destroy (learn_peer.arm_proc); learn_peer.arm_proc = NULL; -#endif GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Shutdown complete....\n"); } @@ -388,14 +382,14 @@ setup_learn_peer (struct PeerContext *p, const char *cfgname) { char *filename; unsigned int result; + char *binary; + binary = GNUNET_OS_get_libexec_binary_path ("gnunet-service-arm"); p->cfg = GNUNET_CONFIGURATION_create (); -#if START_ARM p->arm_proc = - GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-arm", + GNUNET_OS_start_process (GNUNET_YES, GNUNET_OS_INHERIT_STD_OUT_AND_ERR, NULL, NULL, binary, "gnunet-service-arm", "-c", cfgname, NULL); -#endif GNUNET_assert (GNUNET_OK == GNUNET_CONFIGURATION_load (p->cfg, cfgname)); if (GNUNET_OK == GNUNET_CONFIGURATION_get_value_string (p->cfg, "HOSTLIST", "HOSTLISTFILE", @@ -411,27 +405,30 @@ setup_learn_peer (struct PeerContext *p, const char *cfgname) GNUNET_free (filename); } p->core = - GNUNET_CORE_connect (p->cfg, 1, NULL, NULL, NULL, NULL, NULL, GNUNET_NO, + GNUNET_CORE_connect (p->cfg, NULL, NULL, NULL, NULL, NULL, GNUNET_NO, NULL, GNUNET_NO, learn_handlers); GNUNET_assert (NULL != p->core); p->stats = GNUNET_STATISTICS_create ("hostlist", p->cfg); GNUNET_assert (NULL != p->stats); + GNUNET_free (binary); } static void setup_adv_peer (struct PeerContext *p, const char *cfgname) { + char *binary; + + binary = GNUNET_OS_get_libexec_binary_path ("gnunet-service-arm"); p->cfg = GNUNET_CONFIGURATION_create (); -#if START_ARM p->arm_proc = - GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-arm", + GNUNET_OS_start_process (GNUNET_YES, GNUNET_OS_INHERIT_STD_OUT_AND_ERR, NULL, NULL, binary, "gnunet-service-arm", "-c", cfgname, NULL); -#endif GNUNET_assert (GNUNET_OK == GNUNET_CONFIGURATION_load (p->cfg, cfgname)); p->stats = GNUNET_STATISTICS_create ("hostlist", p->cfg); GNUNET_assert (NULL != p->stats); + GNUNET_free (binary); } diff --git a/src/hostlist/test_gnunet_daemon_hostlist_peer1.conf b/src/hostlist/test_gnunet_daemon_hostlist_peer1.conf index 78dde57..0a345f6 100644 --- a/src/hostlist/test_gnunet_daemon_hostlist_peer1.conf +++ b/src/hostlist/test_gnunet_daemon_hostlist_peer1.conf @@ -1,7 +1,6 @@ @INLINE@ test_hostlist_defaults.conf [PATHS] SERVICEHOME = /tmp/test-gnunet-hostlist-peer-1/ -DEFAULTCONFIG = test_gnunet_daemon_hostlist_peer1.conf [transport-tcp] PORT = 12968 @@ -26,7 +25,6 @@ UNIXPATH = /tmp/gnunet-p1-service-peerinfo.sock [transport] PORT = 12965 UNIXPATH = /tmp/gnunet-p1-service-transport.sock -DEBUG = NO [core] PORT = 12970 diff --git a/src/hostlist/test_gnunet_daemon_hostlist_peer2.conf b/src/hostlist/test_gnunet_daemon_hostlist_peer2.conf index 41862da..c383338 100644 --- a/src/hostlist/test_gnunet_daemon_hostlist_peer2.conf +++ b/src/hostlist/test_gnunet_daemon_hostlist_peer2.conf @@ -1,7 +1,6 @@ @INLINE@ test_hostlist_defaults.conf [PATHS] SERVICEHOME = /tmp/test-gnunet-hostlist-peer-2/ -DEFAULTCONFIG = test_gnunet_daemon_hostlist_peer2.conf [transport-tcp] PORT = 22968 diff --git a/src/hostlist/test_gnunet_daemon_hostlist_reconnect.c b/src/hostlist/test_gnunet_daemon_hostlist_reconnect.c index ff6e417..74ef37f 100644 --- a/src/hostlist/test_gnunet_daemon_hostlist_reconnect.c +++ b/src/hostlist/test_gnunet_daemon_hostlist_reconnect.c @@ -28,11 +28,6 @@ #include "gnunet_arm_service.h" #include "gnunet_transport_service.h" -#define VERBOSE GNUNET_NO - -#define START_ARM GNUNET_YES - - /** * How long until we give up on transmitting the message? */ @@ -48,9 +43,7 @@ struct PeerContext struct GNUNET_TRANSPORT_Handle *th; struct GNUNET_MessageHeader *hello; struct GNUNET_TRANSPORT_GetHelloHandle *ghh; -#if START_ARM struct GNUNET_OS_Process *arm_proc; -#endif }; static struct PeerContext p1; @@ -112,9 +105,6 @@ notify_connect (void *cls, const struct GNUNET_PeerIdentity *peer, { if (peer == NULL) return; -#if VERBOSE - FPRINTF (stderr, "Peer %s connected\n", GNUNET_i2s (peer)); -#endif GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Peers connected, shutting down.\n"); ok = 0; if (timeout_task != GNUNET_SCHEDULER_NO_TASK) @@ -141,21 +131,20 @@ process_hello (void *cls, const struct GNUNET_MessageHeader *message) static void setup_peer (struct PeerContext *p, const char *cfgname) { + char *binary; + + binary = GNUNET_OS_get_libexec_binary_path ("gnunet-service-arm"); p->cfg = GNUNET_CONFIGURATION_create (); -#if START_ARM p->arm_proc = - GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-arm", + GNUNET_OS_start_process (GNUNET_YES, GNUNET_OS_INHERIT_STD_OUT_AND_ERR, NULL, NULL, binary, "gnunet-service-arm", -#if VERBOSE - "-L", "DEBUG", -#endif "-c", cfgname, NULL); -#endif GNUNET_assert (GNUNET_OK == GNUNET_CONFIGURATION_load (p->cfg, cfgname)); p->th = GNUNET_TRANSPORT_connect (p->cfg, NULL, p, NULL, ¬ify_connect, NULL); GNUNET_assert (p->th != NULL); p->ghh = GNUNET_TRANSPORT_get_hello (p->th, &process_hello, p); + GNUNET_free (binary); } @@ -164,7 +153,6 @@ waitpid_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { struct PeerContext *p = cls; -#if START_ARM GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Killing ARM process.\n"); if (0 != GNUNET_OS_process_kill (p->arm_proc, SIGTERM)) GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); @@ -174,7 +162,6 @@ waitpid_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) GNUNET_OS_process_get_pid (p->arm_proc)); GNUNET_OS_process_destroy (p->arm_proc); p->arm_proc = NULL; -#endif GNUNET_CONFIGURATION_destroy (p->cfg); } @@ -217,9 +204,6 @@ check () { char *const argv[] = { "test-gnunet-daemon-hostlist", "-c", "test_gnunet_daemon_hostlist_data.conf", -#if VERBOSE - "-L", "DEBUG", -#endif NULL }; struct GNUNET_GETOPT_CommandLineOption options[] = { @@ -243,11 +227,7 @@ main (int argc, char *argv[]) GNUNET_DISK_directory_remove ("/tmp/test-gnunet-hostlist-peer-2"); GNUNET_DISK_directory_remove ("/tmp/test-gnunet-hostlist-peer-3"); GNUNET_log_setup ("test-gnunet-daemon-hostlist", -#if VERBOSE - "DEBUG", -#else "WARNING", -#endif NULL); ret = check (); if (ret == 0) diff --git a/src/hostlist/test_hostlist_defaults.conf b/src/hostlist/test_hostlist_defaults.conf index c2d0a70..a9804ed 100644 --- a/src/hostlist/test_hostlist_defaults.conf +++ b/src/hostlist/test_hostlist_defaults.conf @@ -1,6 +1,5 @@ [PATHS] SERVICEHOME = /tmp/test-gnunet-hostlist/ -DEFAULTCONFIG = test_hostlist_default.conf [resolver] PORT = 12464 @@ -66,3 +65,9 @@ AUTOSTART = NO [lockmanager] AUTOSTART = NO + +[nat] +RETURN_LOCAL_ADDRESSES = YES + +[consensus] +AUTOSTART = NO diff --git a/src/hostlist/test_learning_adv_peer.conf b/src/hostlist/test_learning_adv_peer.conf index fe50bd5..b08660a 100644 --- a/src/hostlist/test_learning_adv_peer.conf +++ b/src/hostlist/test_learning_adv_peer.conf @@ -1,7 +1,6 @@ @INLINE@ test_hostlist_defaults.conf [PATHS] SERVICEHOME = /tmp/test-gnunet-hostlist-peer-1/ -DEFAULTCONFIG = test_learning_adv_peer.conf [transport-tcp] PORT = 22968 diff --git a/src/hostlist/test_learning_learn_peer.conf b/src/hostlist/test_learning_learn_peer.conf index 0136d77..95de705 100644 --- a/src/hostlist/test_learning_learn_peer.conf +++ b/src/hostlist/test_learning_learn_peer.conf @@ -1,7 +1,6 @@ @INLINE@ test_hostlist_defaults.conf [PATHS] SERVICEHOME = /tmp/test-gnunet-hostlist-peer-2/ -DEFAULTCONFIG = test_learning_learn_peer.conf [transport-tcp] PORT = 12968 diff --git a/src/hostlist/test_learning_learn_peer2.conf b/src/hostlist/test_learning_learn_peer2.conf index 4fd54bb..f70fbda 100644 --- a/src/hostlist/test_learning_learn_peer2.conf +++ b/src/hostlist/test_learning_learn_peer2.conf @@ -1,7 +1,6 @@ @INLINE@ test_hostlist_defaults.conf [PATHS] SERVICEHOME = /tmp/test-gnunet-hostlist-peer-3/ -DEFAULTCONFIG = test_learning_learn_peer2.conf [transport-tcp] PORT = 32968 diff --git a/src/include/Makefile.am b/src/include/Makefile.am index 34a879f..67cee97 100644 --- a/src/include/Makefile.am +++ b/src/include/Makefile.am @@ -3,22 +3,23 @@ SUBDIRS = . gnunetincludedir = $(includedir)/gnunet nodist_gnunetinclude_HEADERS = \ - gnunet_directories.h \ - block_fs.h + gnunet_directories.h if MINGW WINPROC = winproc.h endif -gnunetinclude_HEADERS = \ +EXTRA_DIST = \ gauger.h \ - gettext.h \ - platform.h \ - plibc.h \ - $(WINPROC) \ + block_fs.h \ block_dns.h \ block_gns.h \ - block_fs.h \ + block_mesh.h \ + block_regex.h + +gnunetinclude_HEADERS = \ + platform.h plibc.h $(WINPROC) gettext.h \ + gns_protocol.h \ gnunet_applications.h \ gnunet_arm_service.h \ gnunet_ats_service.h \ @@ -42,6 +43,7 @@ gnunetinclude_HEADERS = \ gnunet_dht_service.h \ gnunet_disk_lib.h \ gnunet_dnsparser_lib.h \ + gnunet_dnsstub_lib.h \ gnunet_dns_service.h \ gnunet_dv_service.h \ gnunet_fragmentation_lib.h \ @@ -79,7 +81,6 @@ gnunetinclude_HEADERS = \ gnunet_strings_lib.h \ gnunet_testbed_service.h \ gnunet_testing_lib.h \ - gnunet_testing_lib-new.h \ gnunet_time_lib.h \ gnunet_transport_service.h \ gnunet_transport_plugin.h \ diff --git a/src/include/Makefile.in b/src/include/Makefile.in index ac6b874..8f2880a 100644 --- a/src/include/Makefile.in +++ b/src/include/Makefile.in @@ -1,9 +1,9 @@ -# Makefile.in generated by automake 1.11.1 from Makefile.am. +# Makefile.in generated by automake 1.11.6 from Makefile.am. # @configure_input@ # Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, -# 2003, 2004, 2005, 2006, 2007, 2008, 2009 Free Software Foundation, -# Inc. +# 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Free Software +# Foundation, Inc. # This Makefile.in is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. @@ -16,6 +16,23 @@ @SET_MAKE@ VPATH = @srcdir@ +am__make_dryrun = \ + { \ + am__dry=no; \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + echo 'am--echo: ; @echo "AM" OK' | $(MAKE) -f - 2>/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } pkgdatadir = $(datadir)/@PACKAGE@ pkgincludedir = $(includedir)/@PACKAGE@ pkglibdir = $(libdir)/@PACKAGE@ @@ -41,14 +58,15 @@ DIST_COMMON = $(am__gnunetinclude_HEADERS_DIST) $(srcdir)/Makefile.am \ ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 am__aclocal_m4_deps = $(top_srcdir)/m4/absolute-header.m4 \ $(top_srcdir)/m4/align.m4 $(top_srcdir)/m4/argz.m4 \ - $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/iconv.m4 \ - $(top_srcdir)/m4/lib-ld.m4 $(top_srcdir)/m4/lib-link.m4 \ - $(top_srcdir)/m4/lib-prefix.m4 $(top_srcdir)/m4/libcurl.m4 \ - $(top_srcdir)/m4/libgcrypt.m4 $(top_srcdir)/m4/libtool.m4 \ - $(top_srcdir)/m4/libunistring.m4 $(top_srcdir)/m4/ltdl.m4 \ - $(top_srcdir)/m4/ltoptions.m4 $(top_srcdir)/m4/ltsugar.m4 \ - $(top_srcdir)/m4/ltversion.m4 $(top_srcdir)/m4/lt~obsolete.m4 \ - $(top_srcdir)/m4/nls.m4 $(top_srcdir)/m4/po.m4 \ + $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/glib-2.0.m4 \ + $(top_srcdir)/m4/iconv.m4 $(top_srcdir)/m4/lib-ld.m4 \ + $(top_srcdir)/m4/lib-link.m4 $(top_srcdir)/m4/lib-prefix.m4 \ + $(top_srcdir)/m4/libcurl.m4 $(top_srcdir)/m4/libgcrypt.m4 \ + $(top_srcdir)/m4/libtool.m4 $(top_srcdir)/m4/libunistring.m4 \ + $(top_srcdir)/m4/ltdl.m4 $(top_srcdir)/m4/ltoptions.m4 \ + $(top_srcdir)/m4/ltsugar.m4 $(top_srcdir)/m4/ltversion.m4 \ + $(top_srcdir)/m4/lt~obsolete.m4 $(top_srcdir)/m4/nls.m4 \ + $(top_srcdir)/m4/pkg.m4 $(top_srcdir)/m4/po.m4 \ $(top_srcdir)/m4/progtest.m4 $(top_srcdir)/acinclude.m4 \ $(top_srcdir)/configure.ac am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ @@ -57,11 +75,11 @@ mkinstalldirs = $(install_sh) -d CONFIG_HEADER = $(top_builddir)/gnunet_config.h CONFIG_CLEAN_FILES = gnunet_directories.h CONFIG_CLEAN_VPATH_FILES = -AM_V_GEN = $(am__v_GEN_$(V)) -am__v_GEN_ = $(am__v_GEN_$(AM_DEFAULT_VERBOSITY)) +AM_V_GEN = $(am__v_GEN_@AM_V@) +am__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@) am__v_GEN_0 = @echo " GEN " $@; -AM_V_at = $(am__v_at_$(V)) -am__v_at_ = $(am__v_at_$(AM_DEFAULT_VERBOSITY)) +AM_V_at = $(am__v_at_@AM_V@) +am__v_at_ = $(am__v_at_@AM_DEFAULT_V@) am__v_at_0 = @ SOURCES = DIST_SOURCES = @@ -72,21 +90,27 @@ RECURSIVE_TARGETS = all-recursive check-recursive dvi-recursive \ install-pdf-recursive install-ps-recursive install-recursive \ installcheck-recursive installdirs-recursive pdf-recursive \ ps-recursive uninstall-recursive -am__gnunetinclude_HEADERS_DIST = gauger.h gettext.h platform.h plibc.h \ - winproc.h block_dns.h block_gns.h block_fs.h \ - gnunet_applications.h gnunet_arm_service.h \ - gnunet_ats_service.h gnunet_bandwidth_lib.h gnunet_bio_lib.h \ - gnunet_block_lib.h gnunet_block_plugin.h gnunet_client_lib.h \ +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac +am__gnunetinclude_HEADERS_DIST = platform.h plibc.h winproc.h \ + gettext.h gns_protocol.h gnunet_applications.h \ + gnunet_arm_service.h gnunet_ats_service.h \ + gnunet_bandwidth_lib.h gnunet_bio_lib.h gnunet_block_lib.h \ + gnunet_block_plugin.h gnunet_client_lib.h \ gnunet_chat_service.h gnunet_common.h gnunet_constants.h \ gnunet_configuration_lib.h gnunet_container_lib.h \ gnunet_connection_lib.h gnunet_core_service.h \ gnunet_crypto_lib.h gnunet_datacache_lib.h \ gnunet_datacache_plugin.h gnunet_datastore_service.h \ gnunet_datastore_plugin.h gnunet_dht_service.h \ - gnunet_disk_lib.h gnunet_dnsparser_lib.h gnunet_dns_service.h \ - gnunet_dv_service.h gnunet_fragmentation_lib.h \ - gnunet_fs_service.h gnunet_getopt_lib.h gnunet_gns_service.h \ - gnunet_hello_lib.h gnunet_helper_lib.h gnunet_load_lib.h \ + gnunet_disk_lib.h gnunet_dnsparser_lib.h gnunet_dnsstub_lib.h \ + gnunet_dns_service.h gnunet_dv_service.h \ + gnunet_fragmentation_lib.h gnunet_fs_service.h \ + gnunet_getopt_lib.h gnunet_gns_service.h gnunet_hello_lib.h \ + gnunet_helper_lib.h gnunet_load_lib.h \ gnunet_lockmanager_service.h gnunet_mesh_service.h \ gnunet_mysql_lib.h gnunet_namestore_plugin.h \ gnunet_namestore_service.h gnunet_nat_lib.h \ @@ -99,10 +123,9 @@ am__gnunetinclude_HEADERS_DIST = gauger.h gettext.h platform.h plibc.h \ gnunet_service_lib.h gnunet_signal_lib.h gnunet_signatures.h \ gnunet_statistics_service.h gnunet_stream_lib.h \ gnunet_strings_lib.h gnunet_testbed_service.h \ - gnunet_testing_lib.h gnunet_testing_lib-new.h \ - gnunet_time_lib.h gnunet_transport_service.h \ - gnunet_transport_plugin.h gnunet_tun_lib.h gnunet_util_lib.h \ - gnunet_vpn_service.h + gnunet_testing_lib.h gnunet_time_lib.h \ + gnunet_transport_service.h gnunet_transport_plugin.h \ + gnunet_tun_lib.h gnunet_util_lib.h gnunet_vpn_service.h am__vpath_adj_setup = srcdirstrip=`echo "$(srcdir)" | sed 's|.|.|g'`; am__vpath_adj = case $$p in \ $(srcdir)/*) f=`echo "$$p" | sed "s|^$$srcdirstrip/||"`;; \ @@ -124,6 +147,12 @@ am__nobase_list = $(am__nobase_strip_setup); \ am__base_list = \ sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \ sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g' +am__uninstall_files_from_dir = { \ + test -z "$$files" \ + || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \ + || { echo " ( cd '$$dir' && rm -f" $$files ")"; \ + $(am__cd) "$$dir" && rm -f $$files; }; \ + } am__installdirs = "$(DESTDIR)$(gnunetincludedir)" \ "$(DESTDIR)$(gnunetincludedir)" HEADERS = $(gnunetinclude_HEADERS) $(nodist_gnunetinclude_HEADERS) @@ -196,6 +225,10 @@ EXEEXT = @EXEEXT@ EXT_LIBS = @EXT_LIBS@ EXT_LIB_PATH = @EXT_LIB_PATH@ FGREP = @FGREP@ +GLIB_CFLAGS = @GLIB_CFLAGS@ +GLIB_GENMARSHAL = @GLIB_GENMARSHAL@ +GLIB_LIBS = @GLIB_LIBS@ +GLIB_MKENUMS = @GLIB_MKENUMS@ GMSGFMT = @GMSGFMT@ GMSGFMT_015 = @GMSGFMT_015@ GNUNETDNS_GROUP = @GNUNETDNS_GROUP@ @@ -206,6 +239,7 @@ GN_LIBINTL = @GN_LIBINTL@ GN_LIB_LDFLAGS = @GN_LIB_LDFLAGS@ GN_PLUGIN_LDFLAGS = @GN_PLUGIN_LDFLAGS@ GN_USER_HOME_DIR = @GN_USER_HOME_DIR@ +GOBJECT_QUERY = @GOBJECT_QUERY@ GREP = @GREP@ HAVE_LIBUNISTRING = @HAVE_LIBUNISTRING@ INCLTDL = @INCLTDL@ @@ -228,6 +262,8 @@ LIBCURL_CPPFLAGS = @LIBCURL_CPPFLAGS@ LIBGCRYPT_CFLAGS = @LIBGCRYPT_CFLAGS@ LIBGCRYPT_CONFIG = @LIBGCRYPT_CONFIG@ LIBGCRYPT_LIBS = @LIBGCRYPT_LIBS@ +LIBGTOP_CFLAGS = @LIBGTOP_CFLAGS@ +LIBGTOP_LIBS = @LIBGTOP_LIBS@ LIBICONV = @LIBICONV@ LIBINTL = @LIBINTL@ LIBLTDL = @LIBLTDL@ @@ -249,6 +285,7 @@ LT_CONFIG_H = @LT_CONFIG_H@ LT_DLLOADERS = @LT_DLLOADERS@ LT_DLPREOPEN = @LT_DLPREOPEN@ MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ MKDIR_P = @MKDIR_P@ MONKEYPREFIX = @MONKEYPREFIX@ MSGFMT = @MSGFMT@ @@ -258,6 +295,7 @@ MYSQL_CPPFLAGS = @MYSQL_CPPFLAGS@ MYSQL_LDFLAGS = @MYSQL_LDFLAGS@ NM = @NM@ NMEDIT = @NMEDIT@ +NSS_DIR = @NSS_DIR@ OBJC = @OBJC@ OBJCDEPMODE = @OBJCDEPMODE@ OBJCFLAGS = @OBJCFLAGS@ @@ -273,6 +311,7 @@ PACKAGE_TARNAME = @PACKAGE_TARNAME@ PACKAGE_URL = @PACKAGE_URL@ PACKAGE_VERSION = @PACKAGE_VERSION@ PATH_SEPARATOR = @PATH_SEPARATOR@ +PKG_CONFIG = @PKG_CONFIG@ POSTGRES_CPPFLAGS = @POSTGRES_CPPFLAGS@ POSTGRES_LDFLAGS = @POSTGRES_LDFLAGS@ POSUB = @POSUB@ @@ -304,6 +343,7 @@ abs_builddir = @abs_builddir@ abs_srcdir = @abs_srcdir@ abs_top_builddir = @abs_top_builddir@ abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ ac_ct_CC = @ac_ct_CC@ ac_ct_CXX = @ac_ct_CXX@ ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ @@ -326,6 +366,7 @@ datarootdir = @datarootdir@ docdir = @docdir@ dvidir = @dvidir@ exec_prefix = @exec_prefix@ +gitcommand = @gitcommand@ host = @host@ host_alias = @host_alias@ host_cpu = @host_cpu@ @@ -339,7 +380,6 @@ libdir = @libdir@ libexecdir = @libexecdir@ localedir = @localedir@ localstatedir = @localstatedir@ -lt_ECHO = @lt_ECHO@ ltdl_LIBOBJS = @ltdl_LIBOBJS@ ltdl_LTLIBOBJS = @ltdl_LTLIBOBJS@ mandir = @mandir@ @@ -357,6 +397,7 @@ sbindir = @sbindir@ sharedstatedir = @sharedstatedir@ srcdir = @srcdir@ subdirs = @subdirs@ +svnversioncommand = @svnversioncommand@ sys_symbol_underscore = @sys_symbol_underscore@ sysconfdir = @sysconfdir@ target = @target@ @@ -370,19 +411,20 @@ top_srcdir = @top_srcdir@ SUBDIRS = . gnunetincludedir = $(includedir)/gnunet nodist_gnunetinclude_HEADERS = \ - gnunet_directories.h \ - block_fs.h + gnunet_directories.h @MINGW_TRUE@WINPROC = winproc.h -gnunetinclude_HEADERS = \ +EXTRA_DIST = \ gauger.h \ - gettext.h \ - platform.h \ - plibc.h \ - $(WINPROC) \ + block_fs.h \ block_dns.h \ block_gns.h \ - block_fs.h \ + block_mesh.h \ + block_regex.h + +gnunetinclude_HEADERS = \ + platform.h plibc.h $(WINPROC) gettext.h \ + gns_protocol.h \ gnunet_applications.h \ gnunet_arm_service.h \ gnunet_ats_service.h \ @@ -406,6 +448,7 @@ gnunetinclude_HEADERS = \ gnunet_dht_service.h \ gnunet_disk_lib.h \ gnunet_dnsparser_lib.h \ + gnunet_dnsstub_lib.h \ gnunet_dns_service.h \ gnunet_dv_service.h \ gnunet_fragmentation_lib.h \ @@ -443,7 +486,6 @@ gnunetinclude_HEADERS = \ gnunet_strings_lib.h \ gnunet_testbed_service.h \ gnunet_testing_lib.h \ - gnunet_testing_lib-new.h \ gnunet_time_lib.h \ gnunet_transport_service.h \ gnunet_transport_plugin.h \ @@ -494,8 +536,11 @@ clean-libtool: -rm -rf .libs _libs install-gnunetincludeHEADERS: $(gnunetinclude_HEADERS) @$(NORMAL_INSTALL) - test -z "$(gnunetincludedir)" || $(MKDIR_P) "$(DESTDIR)$(gnunetincludedir)" @list='$(gnunetinclude_HEADERS)'; test -n "$(gnunetincludedir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(gnunetincludedir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(gnunetincludedir)" || exit 1; \ + fi; \ for p in $$list; do \ if test -f "$$p"; then d=; else d="$(srcdir)/"; fi; \ echo "$$d$$p"; \ @@ -509,13 +554,14 @@ uninstall-gnunetincludeHEADERS: @$(NORMAL_UNINSTALL) @list='$(gnunetinclude_HEADERS)'; test -n "$(gnunetincludedir)" || list=; \ files=`for p in $$list; do echo $$p; done | sed -e 's|^.*/||'`; \ - test -n "$$files" || exit 0; \ - echo " ( cd '$(DESTDIR)$(gnunetincludedir)' && rm -f" $$files ")"; \ - cd "$(DESTDIR)$(gnunetincludedir)" && rm -f $$files + dir='$(DESTDIR)$(gnunetincludedir)'; $(am__uninstall_files_from_dir) install-nodist_gnunetincludeHEADERS: $(nodist_gnunetinclude_HEADERS) @$(NORMAL_INSTALL) - test -z "$(gnunetincludedir)" || $(MKDIR_P) "$(DESTDIR)$(gnunetincludedir)" @list='$(nodist_gnunetinclude_HEADERS)'; test -n "$(gnunetincludedir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(gnunetincludedir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(gnunetincludedir)" || exit 1; \ + fi; \ for p in $$list; do \ if test -f "$$p"; then d=; else d="$(srcdir)/"; fi; \ echo "$$d$$p"; \ @@ -529,9 +575,7 @@ uninstall-nodist_gnunetincludeHEADERS: @$(NORMAL_UNINSTALL) @list='$(nodist_gnunetinclude_HEADERS)'; test -n "$(gnunetincludedir)" || list=; \ files=`for p in $$list; do echo $$p; done | sed -e 's|^.*/||'`; \ - test -n "$$files" || exit 0; \ - echo " ( cd '$(DESTDIR)$(gnunetincludedir)' && rm -f" $$files ")"; \ - cd "$(DESTDIR)$(gnunetincludedir)" && rm -f $$files + dir='$(DESTDIR)$(gnunetincludedir)'; $(am__uninstall_files_from_dir) # This directory's subdirectories are mostly independent; you can cd # into them and run `make' without going through this Makefile. @@ -700,13 +744,10 @@ distdir: $(DISTFILES) done @list='$(DIST_SUBDIRS)'; for subdir in $$list; do \ if test "$$subdir" = .; then :; else \ - test -d "$(distdir)/$$subdir" \ - || $(MKDIR_P) "$(distdir)/$$subdir" \ - || exit 1; \ - fi; \ - done - @list='$(DIST_SUBDIRS)'; for subdir in $$list; do \ - if test "$$subdir" = .; then :; else \ + $(am__make_dryrun) \ + || test -d "$(distdir)/$$subdir" \ + || $(MKDIR_P) "$(distdir)/$$subdir" \ + || exit 1; \ dir1=$$subdir; dir2="$(distdir)/$$subdir"; \ $(am__relativize); \ new_distdir=$$reldir; \ @@ -744,10 +785,15 @@ install-am: all-am installcheck: installcheck-recursive install-strip: - $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ - install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ - `test -z '$(STRIP)' || \ - echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi mostlyclean-generic: clean-generic: diff --git a/src/include/block_dns.h b/src/include/block_dns.h index e047779..0ca5a47 100644 --- a/src/include/block_dns.h +++ b/src/include/block_dns.h @@ -64,7 +64,7 @@ struct GNUNET_DNS_Record * The descriptor for the service * (a peer may provide more than one service) */ - GNUNET_HashCode service_descriptor; + struct GNUNET_HashCode service_descriptor; /** * When does this record expire? diff --git a/src/include/block_fs.h b/src/include/block_fs.h index aae741e..0b77adc 100644 --- a/src/include/block_fs.h +++ b/src/include/block_fs.h @@ -78,7 +78,7 @@ struct SBlock * used as the key for decryption; the xor of this identifier * and the hash of the "keyspace" is the datastore-query hash). */ - GNUNET_HashCode identifier; + struct GNUNET_HashCode identifier; /** * Public key of the namespace. @@ -153,7 +153,7 @@ struct OnDemandBlock * file that was indexed (used to uniquely * identify the plaintext file). */ - GNUNET_HashCode file_id; + struct GNUNET_HashCode file_id; /** * At which offset should we be able to find diff --git a/src/include/block_gns.h b/src/include/block_gns.h index ffdb294..7b4ceed 100644 --- a/src/include/block_gns.h +++ b/src/include/block_gns.h @@ -30,34 +30,6 @@ GNUNET_NETWORK_STRUCT_BEGIN -/** - * @brief a simgle record inside a record block - */ -struct GNSRecordBlock -{ - /** - * the record type - */ - uint32_t type GNUNET_PACKED; - - /** - * expiration time of the record - */ - struct GNUNET_TIME_AbsoluteNBO expiration; - - /** - * length of the data - */ - uint32_t data_length GNUNET_PACKED; - - /* record flags */ - uint32_t flags GNUNET_PACKED; - - //Class of the record? - - /* followed by the record data */ -}; - /** * @brief a record block for a given name of a single authority */ @@ -79,7 +51,7 @@ struct GNSNameRecordBlock /* 0-terminated name here */ - /* variable-size GNSRecordBlocks follows here */ + /* variable-size serialized namestore record data */ }; diff --git a/src/include/block_mesh.h b/src/include/block_mesh.h new file mode 100644 index 0000000..9dfb859 --- /dev/null +++ b/src/include/block_mesh.h @@ -0,0 +1,64 @@ +/* + This file is part of GNUnet. + (C) 2012,2013 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @file include/block_mesh.h + * @brief Mesh block formats. + * @author Bartlomiej Polot + */ +#ifndef BLOCK_MESH_H +#define BLOCK_MESH_H + +#ifdef __cplusplus +extern "C" +{ +#if 0 /* keep Emacsens' auto-indent happy */ +} +#endif +#endif + +#include "gnunet_util_lib.h" +#include "gnunet_mesh_service.h" +#include + +/** + * @brief peer block (announce peer + type) + */ +struct PBlock +{ + /** + * Identity of the peer + */ + struct GNUNET_PeerIdentity id; + + /** + * Type of service offered + */ + GNUNET_MESH_ApplicationType type; +}; + +#if 0 /* keep Emacsens' auto-indent happy */ +{ +#endif +#ifdef __cplusplus +} +#endif + +#endif \ No newline at end of file diff --git a/src/include/block_regex.h b/src/include/block_regex.h new file mode 100644 index 0000000..282c626 --- /dev/null +++ b/src/include/block_regex.h @@ -0,0 +1,120 @@ +/* + This file is part of GNUnet. + (C) 2012,2013 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @file include/block_regex.h + * @brief regex block formats + * @author Bartlomiej Polot + */ +#ifndef BLOCK_REGEX_H +#define BLOCK_REGEX_H + +#ifdef __cplusplus +extern "C" +{ +#if 0 + /* keep Emacsens' auto-indent happy */ +} +#endif +#endif + +#include "gnunet_util_lib.h" +#include + + +/** + * @brief A RegexBlock contains one or more of this struct in the payload. + */ +struct RegexEdge +{ + /** + * Destination of this edge. + */ + struct GNUNET_HashCode key; + + /** + * Length of the token towards the new state. + */ + unsigned int n_token; + + /* char token[n_token] */ +}; + +/** + * @brief Block to announce a regex state. + */ +struct RegexBlock +{ + /** + * The key of the state. + */ + struct GNUNET_HashCode key; + + /** + * Length of the proof regex string. + */ + unsigned int n_proof; + + /** + * Numer of edges parting from this state. + */ + unsigned int n_edges; + + /** + * Is this state an accepting state? + */ + int accepting; + + /* char proof[n_proof] */ + /* struct RegexEdge edges[n_edges] */ +}; + +/** + * @brief Block to announce a peer accepting a state. + */ +struct RegexAccept +{ + /** + * The key of the state. + */ + struct GNUNET_HashCode key; + + /** + * Length of the proof regex string. + * FIXME necessary??? + * already present in the leading MeshRegexBlock + */ + // unsigned int n_proof; + + /** + * The identity of the peer accepting the state + */ + struct GNUNET_PeerIdentity id; + +}; + +#if 0 /* keep Emacsens' auto-indent happy */ +{ +#endif +#ifdef __cplusplus +} +#endif + +#endif \ No newline at end of file diff --git a/src/include/gauger.h b/src/include/gauger.h index 9761cbe..10ada90 100644 --- a/src/include/gauger.h +++ b/src/include/gauger.h @@ -29,14 +29,14 @@ sprintf(__gauger_s,"%Lf", (long double) (value));\ __gauger_v[0] = "gauger";\ __gauger_v[1] = "-n";\ - __gauger_v[2] = counter;\ + __gauger_v[2] = (char*) (counter); \ __gauger_v[3] = "-d";\ __gauger_v[4] = __gauger_s;\ __gauger_v[5] = "-u";\ - __gauger_v[6] = unit;\ + __gauger_v[6] = (char*) (unit); \ __gauger_v[7] = "-c";\ - __gauger_v[8] = category;\ - __gauger_v[9] = (char *)NULL;\ + __gauger_v[8] = (char*) (category); \ + __gauger_v[9] = (char*) NULL;\ execvp("gauger",__gauger_v);\ _exit(1);\ }else{\ @@ -59,30 +59,51 @@ sprintf(__gauger_s,"%Lf", (long double) (value));\ __gauger_v[0] = "gauger";\ __gauger_v[1] = "-n";\ - __gauger_v[2] = counter;\ + __gauger_v[2] = (char*) (counter); \ __gauger_v[3] = "-d";\ __gauger_v[4] = __gauger_s;\ __gauger_v[5] = "-u";\ - __gauger_v[6] = unit;\ + __gauger_v[6] = (char*) (unit); \ __gauger_v[7] = "-i";\ __gauger_v[8] = id;\ __gauger_v[9] = "-c";\ - __gauger_v[10] = category;\ - __gauger_v[11] = (char *)NULL;\ + __gauger_v[10] = (char *) (category); \ + __gauger_v[11] = (char *) NULL;\ execvp("gauger",__gauger_v);\ _exit(1);\ }else{\ _exit(0);\ }\ }else{\ - waitpid(__gauger_p,NULL,0);\ + waitpid(__gauger_p, NULL, 0);\ }\ } -#else +#else /* WINDOWS */ + +#include +#include +#include + +#define GAUGER(category, counter, value, unit)\ +{\ + char __gauger_commandline[MAX_PATH];\ + \ + snprintf (__gauger_commandline, MAX_PATH, "gauger.py -n \"%s\" -d \"%Lf\" -u \"%s\" -c \"%s\"",\ + (counter), (long double) (value), (unit), (category)); \ + __gauger_commandline[MAX_PATH - 1] = '\0';\ + system (__gauger_commandline);\ +} -#define GAUGER_ID(category, counter, value, unit, id) {} -#define GAUGER(category, counter, value, unit) {} +#define GAUGER_ID(category, counter, value, unit, id)\ +{\ + char __gauger_commandline[MAX_PATH];\ + \ + snprintf (__gauger_commandline, MAX_PATH, "gauger.py -n \"%s\" -d \"%Lf\" -u \"%s\" -i \"%s\" -c \"%s\"",\ + (counter), (long double) (value), (unit), (id), (category)); \ + __gauger_commandline[MAX_PATH - 1] = '\0';\ + system (__gauger_commandline);\ +} #endif // WINDOWS diff --git a/src/include/gns_protocol.h b/src/include/gns_protocol.h new file mode 100644 index 0000000..0d9758b --- /dev/null +++ b/src/include/gns_protocol.h @@ -0,0 +1,161 @@ +/* + This file is part of GNUnet + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 2, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. + */ + +/** + * @file include/gns_protocol.h + * @brief Resource Record definitions + * @author Martin Schanzenbach + */ +#ifndef GNS_RECORDS_H +#define GNS_RECORDS_H + +GNUNET_NETWORK_STRUCT_BEGIN + +/** + * Payload of DNS SOA record (header). + */ +struct soa_data +{ + /** + * The version number of the original copy of the zone. (NBO) + */ + uint32_t serial GNUNET_PACKED; + + /** + * Time interval before the zone should be refreshed. (NBO) + */ + uint32_t refresh GNUNET_PACKED; + + /** + * Time interval that should elapse before a failed refresh should + * be retried. (NBO) + */ + uint32_t retry GNUNET_PACKED; + + /** + * Time value that specifies the upper limit on the time interval + * that can elapse before the zone is no longer authoritative. (NBO) + */ + uint32_t expire GNUNET_PACKED; + + /** + * The bit minimum TTL field that should be exported with any RR + * from this zone. (NBO) + */ + uint32_t minimum GNUNET_PACKED; +}; + + +/** + * Payload of DNS SRV record (header). + */ +struct srv_data +{ + + /** + * Preference for this entry (lower value is higher preference). Clients + * will contact hosts from the lowest-priority group first and fall back + * to higher priorities if the low-priority entries are unavailable. (NBO) + */ + uint16_t prio GNUNET_PACKED; + + /** + * Relative weight for records with the same priority. Clients will use + * the hosts of the same (lowest) priority with a probability proportional + * to the weight given. (NBO) + */ + uint16_t weight GNUNET_PACKED; + + /** + * TCP or UDP port of the service. (NBO) + */ + uint16_t port GNUNET_PACKED; + + /* followed by 'target' name */ +}; + + +/** + * Payload of DNSSEC TLSA record. + * http://datatracker.ietf.org/doc/draft-ietf-dane-protocol/ + */ +struct tlsa_data +{ + + /** + * Certificate usage + * 0: CA cert + * 1: Entity cert + * 2: Trust anchor + * 3: domain-issued cert + */ + uint8_t usage; + + /** + * Selector + * What part will be matched against the cert + * presented by server + * 0: Full cert (in binary) + * 1: Full cert (in DER) + */ + uint8_t selector; + + /** + * Matching type (of selected content) + * 0: exact match + * 1: SHA-256 hash + * 2: SHA-512 hash + */ + uint8_t matching_type; + + /** + * followed by certificate association data + * The "certificate association data" to be matched. + * These bytes are either raw data (that is, the full certificate or + * its SubjectPublicKeyInfo, depending on the selector) for matching + * type 0, or the hash of the raw data for matching types 1 and 2. + * The data refers to the certificate in the association, not to the + * TLS ASN.1 Certificate object. + * + * The data is represented as a string of hex chars + */ +}; + +/** + * Payload of GNS VPN record + */ +struct vpn_data +{ + /** + * The peer to contact + */ + struct GNUNET_HashCode peer; + + /** + * The protocol to use + */ + uint16_t proto; + + /* followed by the servicename */ +}; + +GNUNET_NETWORK_STRUCT_END + +#endif diff --git a/src/include/gnunet_applications.h b/src/include/gnunet_applications.h index 5feaeec..5710a88 100644 --- a/src/include/gnunet_applications.h +++ b/src/include/gnunet_applications.h @@ -50,6 +50,10 @@ extern "C" */ #define GNUNET_APPLICATION_TYPE_INTERNET_RESOLVER 2 +/** + * Transfer of blocks for non-anonymmous file-sharing. + */ +#define GNUNET_APPLICATION_TYPE_FS_BLOCK_TRANSFER 3 /** * Internet IPv4 gateway (any TCP/UDP/ICMP). @@ -61,6 +65,17 @@ extern "C" */ #define GNUNET_APPLICATION_TYPE_IPV6_GATEWAY 17 +/** + * Internet exit regex prefix. Consisting of application ID, followed by version + * and padding. + */ +#define GNUNET_APPLICATION_TYPE_EXIT_REGEX_PREFIX "GNUNET-VPN-VER-0001-" + +/** + * Consensus. + */ +#define GNUNET_APPLICATION_TYPE_CONSENSUS 18 + #if 0 /* keep Emacsens' auto-indent happy */ { diff --git a/src/include/gnunet_arm_service.h b/src/include/gnunet_arm_service.h index 116bfc5..0aa916b 100644 --- a/src/include/gnunet_arm_service.h +++ b/src/include/gnunet_arm_service.h @@ -37,6 +37,7 @@ extern "C" #include "gnunet_configuration_lib.h" #include "gnunet_scheduler_lib.h" +#include "gnunet_os_lib.h" #include "gnunet_time_lib.h" /** @@ -169,12 +170,14 @@ GNUNET_ARM_disconnect (struct GNUNET_ARM_Handle *h); * * @param h handle to ARM * @param service_name name of the service + * @param std_inheritance flags controlling std descriptors inheritance * @param timeout how long to wait before failing for good * @param cb callback to invoke when service is ready * @param cb_cls closure for callback */ void GNUNET_ARM_start_service (struct GNUNET_ARM_Handle *h, const char *service_name, + enum GNUNET_OS_InheritStdioFlags std_inheritance, struct GNUNET_TIME_Relative timeout, GNUNET_ARM_Callback cb, void *cb_cls); diff --git a/src/include/gnunet_ats_service.h b/src/include/gnunet_ats_service.h index aa7a089..6578633 100644 --- a/src/include/gnunet_ats_service.h +++ b/src/include/gnunet_ats_service.h @@ -30,6 +30,20 @@ #include "gnunet_util_lib.h" #include "gnunet_hello_lib.h" +/** + * Number of network types supported by ATS + */ +#define GNUNET_ATS_NetworkTypeCount 5 + +/** + * ATS network types as array initializer + */ +#define GNUNET_ATS_NetworkType {GNUNET_ATS_NET_UNSPECIFIED, GNUNET_ATS_NET_LOOPBACK, GNUNET_ATS_NET_LAN, GNUNET_ATS_NET_WAN, GNUNET_ATS_NET_WLAN} + +/** + * ATS network types as string array initializer + */ +#define GNUNET_ATS_NetworkTypeString {"UNSPECIFIED", "LOOPBACK", "LAN", "WAN", "WLAN"} enum GNUNET_ATS_Network_Type { @@ -40,6 +54,26 @@ enum GNUNET_ATS_Network_Type GNUNET_ATS_NET_WLAN = 4, }; +/** + * Default bandwidth assigned to a network : 64 KB/s + */ +#define GNUNET_ATS_DefaultBandwidth 65536 + +/** + * Maximum bandwidth assigned to a network : 4095 MB/s + */ +#define GNUNET_ATS_MaxBandwidth UINT32_MAX + +/** + * Number of property types supported by ATS + */ +#define GNUNET_ATS_PropertyCount 9 + +/** + * ATS properties types as string array initializer + */ +#define GNUNET_ATS_PropertyStrings {"Terminator", "Utilization up", "Utilization down", "Network type", "Delay", "Distance", "Cost WAN", "Cost LAN", "Cost WLAN"} + /** * Enum defining all known property types for ATS Enum values are used * in the GNUNET_ATS_Information struct as @@ -413,14 +447,10 @@ enum GNUNET_ATS_Property #define GNUNET_ATS_QualityProperties {GNUNET_ATS_QUALITY_NET_DELAY, GNUNET_ATS_QUALITY_NET_DISTANCE} /** - * Number of ATS quality properties + * ATS quality properties as string array initializer */ -#define GNUNET_ATS_NetworkTypeCount 5 +#define GNUNET_ATS_QualityPropertiesString {"Delay", "Distance"} -/** - * ATS quality properties as array initializer - */ -#define GNUNET_ATS_NetworkType {GNUNET_ATS_NET_UNSPECIFIED, GNUNET_ATS_NET_LOOPBACK, GNUNET_ATS_NET_LAN, GNUNET_ATS_NET_WAN, GNUNET_ATS_NET_WLAN} GNUNET_NETWORK_STRUCT_BEGIN @@ -464,6 +494,13 @@ GNUNET_NETWORK_STRUCT_END */ struct GNUNET_ATS_SchedulingHandle; +/** + * Handle for address suggestion requests + * + */ +struct GNUNET_ATS_SuggestHandle; + + /** * Opaque session handle, defined by plugins. Contents not known to ATS. @@ -471,6 +508,7 @@ struct GNUNET_ATS_SchedulingHandle; struct Session; + /** * Signature of a function called by ATS with the current bandwidth * and address preferences as determined by ATS. @@ -539,8 +577,9 @@ GNUNET_ATS_reset_backoff (struct GNUNET_ATS_SchedulingHandle *sh, * * @param sh handle * @param peer identity of the peer we need an address for + * @return suggestion handle */ -void +struct GNUNET_ATS_SuggestHandle * GNUNET_ATS_suggest_address (struct GNUNET_ATS_SchedulingHandle *sh, const struct GNUNET_PeerIdentity *peer); @@ -556,6 +595,15 @@ GNUNET_ATS_suggest_address_cancel (struct GNUNET_ATS_SchedulingHandle *sh, const struct GNUNET_PeerIdentity *peer); +/** + * Convert a GNUNET_ATS_NetworkType to a string + * + * @param net the network type + * @return a string or NULL if invalid + */ +const char * +GNUNET_ATS_print_network_type (uint32_t net); + /** * Returns where the address is located: LAN or WAN or ... * @param sh the GNUNET_ATS_SchedulingHandle handle @@ -568,6 +616,23 @@ GNUNET_ATS_address_get_type (struct GNUNET_ATS_SchedulingHandle *sh, const struct sockaddr * addr, socklen_t addrlen); +/** + * We have a new address ATS should know. Addresses have to be added with this + * function before they can be: updated, set in use and destroyed + * + * @param sh handle + * @param address the address + * @param session session handle (if available) + * @param ats performance data for the address + * @param ats_count number of performance records in 'ats' + */ +int +GNUNET_ATS_address_add (struct GNUNET_ATS_SchedulingHandle *sh, + const struct GNUNET_HELLO_Address *address, + struct Session *session, + const struct GNUNET_ATS_Information *ats, + uint32_t ats_count); + /** * We have updated performance statistics for a given address. Note @@ -651,6 +716,11 @@ typedef void (*GNUNET_ATS_PeerInformationCallback) (void *cls, GNUNET_ATS_Information * ats, uint32_t ats_count); +/** + * Handle for an address listing operation + */ +struct GNUNET_ATS_AddressListHandle; + /** * Get handle to access performance API of the ATS subsystem. @@ -666,6 +736,35 @@ GNUNET_ATS_performance_init (const struct GNUNET_CONFIGURATION_Handle *cfg, void *infocb_cls); +/** + * Get information about addresses known to the ATS subsystem. + * + * @param handle the performance handle to use + * @param peer peer idm can be NULL for all peers + * @param all GNUNET_YES to get information about all addresses or GNUNET_NO to + * get only address currently used + * @param infocb callback to call with the addresses, + * will callback with address == NULL when done + * @param infocb_cls closure for infocb + * @return ats performance context + */ +struct GNUNET_ATS_AddressListHandle * +GNUNET_ATS_performance_list_addresses (struct GNUNET_ATS_PerformanceHandle *handle, + const struct GNUNET_PeerIdentity *peer, + int all, + GNUNET_ATS_PeerInformationCallback infocb, + void *infocb_cls); + + +/** + * Cancel a pending address listing operation + * + * @param handle the GNUNET_ATS_AddressListHandle handle to cancel + */ +void +GNUNET_ATS_performance_list_addresses_cancel (struct GNUNET_ATS_AddressListHandle *handle); + + /** * Client is done using the ATS performance subsystem, release resources. * @@ -730,6 +829,21 @@ void GNUNET_ATS_reserve_bandwidth_cancel (struct GNUNET_ATS_ReservationContext *rc); +/** + * Number of preference types supported by ATS + */ +#define GNUNET_ATS_PreferenceCount 3 + +/** + * ATS preference types as array initializer + */ +#define GNUNET_ATS_PreferenceType {GNUNET_ATS_PREFERENCE_END, GNUNET_ATS_PREFERENCE_BANDWIDTH, GNUNET_ATS_PREFERENCE_LATENCY} + +/** + * ATS preference types as string array initializer + */ +#define GNUNET_ATS_PreferenceTypeString {"END", "BANDWIDTH", "LATENCY"} + /** * Enum defining all known preference categories. @@ -760,6 +874,14 @@ enum GNUNET_ATS_PreferenceKind GNUNET_ATS_PREFERENCE_LATENCY }; +/** + * Convert a GNUNET_ATS_PreferenceType to a string + * + * @param type the preference type + * @return a string or NULL if invalid + */ +const char * +GNUNET_ATS_print_preference_type (uint32_t type); /** * Change preferences for the given peer. Preference changes are forgotten if peers diff --git a/src/include/gnunet_block_lib.h b/src/include/gnunet_block_lib.h index adc1775..002d5c1 100644 --- a/src/include/gnunet_block_lib.h +++ b/src/include/gnunet_block_lib.h @@ -98,7 +98,27 @@ enum GNUNET_BLOCK_Type /** * Block for storing record data */ - GNUNET_BLOCK_TYPE_GNS_NAMERECORD = 11 + GNUNET_BLOCK_TYPE_GNS_NAMERECORD = 11, + + /** + * Block for storing mesh peers + */ + GNUNET_BLOCK_TYPE_MESH_PEER = 20, + + /** + * Block for finding peers by type + */ + GNUNET_BLOCK_TYPE_MESH_PEER_BY_TYPE = 21, + + /** + * Block to store a mesh regex state + */ + GNUNET_BLOCK_TYPE_REGEX = 22, + + /** + * Block to store a mesh regex accepting state + */ + GNUNET_BLOCK_TYPE_REGEX_ACCEPT = 23 }; @@ -127,22 +147,27 @@ enum GNUNET_BLOCK_EvaluationResult */ GNUNET_BLOCK_EVALUATION_RESULT_INVALID = 3, + /** + * Block does not match xquery (valid result, not relevant for the request) + */ + GNUNET_BLOCK_EVALUATION_RESULT_IRRELEVANT = 4, + /** * Query is valid, no reply given. */ - GNUNET_BLOCK_EVALUATION_REQUEST_VALID = 4, + GNUNET_BLOCK_EVALUATION_REQUEST_VALID = 10, /** * Query format does not match block type (invalid query). For * example, xquery not given or xquery_size not appropriate for * type. */ - GNUNET_BLOCK_EVALUATION_REQUEST_INVALID = 5, + GNUNET_BLOCK_EVALUATION_REQUEST_INVALID = 11, /** * Specified block type not supported by this plugin. */ - GNUNET_BLOCK_EVALUATION_TYPE_NOT_SUPPORTED = 6 + GNUNET_BLOCK_EVALUATION_TYPE_NOT_SUPPORTED = 20 }; @@ -160,8 +185,8 @@ struct GNUNET_BLOCK_Context; * @param hc where to store the result. */ void -GNUNET_BLOCK_mingle_hash (const GNUNET_HashCode * in, uint32_t mingle_number, - GNUNET_HashCode * hc); +GNUNET_BLOCK_mingle_hash (const struct GNUNET_HashCode * in, uint32_t mingle_number, + struct GNUNET_HashCode * hc); /** @@ -204,7 +229,7 @@ GNUNET_BLOCK_context_destroy (struct GNUNET_BLOCK_Context *ctx); enum GNUNET_BLOCK_EvaluationResult GNUNET_BLOCK_evaluate (struct GNUNET_BLOCK_Context *ctx, enum GNUNET_BLOCK_Type type, - const GNUNET_HashCode * query, + const struct GNUNET_HashCode * query, struct GNUNET_CONTAINER_BloomFilter **bf, int32_t bf_mutator, const void *xquery, size_t xquery_size, const void *reply_block, @@ -227,7 +252,7 @@ GNUNET_BLOCK_evaluate (struct GNUNET_BLOCK_Context *ctx, int GNUNET_BLOCK_get_key (struct GNUNET_BLOCK_Context *ctx, enum GNUNET_BLOCK_Type type, const void *block, - size_t block_size, GNUNET_HashCode * key); + size_t block_size, struct GNUNET_HashCode * key); @@ -243,7 +268,7 @@ GNUNET_BLOCK_get_key (struct GNUNET_BLOCK_Context *ctx, */ struct GNUNET_CONTAINER_BloomFilter * GNUNET_BLOCK_construct_bloomfilter (int32_t bf_mutator, - const GNUNET_HashCode * seen_results, + const struct GNUNET_HashCode * seen_results, unsigned int seen_results_count); diff --git a/src/include/gnunet_block_plugin.h b/src/include/gnunet_block_plugin.h index 0ead4af..ac549fe 100644 --- a/src/include/gnunet_block_plugin.h +++ b/src/include/gnunet_block_plugin.h @@ -56,7 +56,7 @@ typedef enum GNUNET_BLOCK_Type type, const - GNUNET_HashCode + struct GNUNET_HashCode * query, struct GNUNET_CONTAINER_BloomFilter @@ -90,7 +90,7 @@ typedef int (*GNUNET_BLOCK_GetKeyFunction) (void *cls, enum GNUNET_BLOCK_Type type, const void *block, size_t block_size, - GNUNET_HashCode * key); + struct GNUNET_HashCode * key); diff --git a/src/include/gnunet_chat_service.h b/src/include/gnunet_chat_service.h index 938b434..8e77f9b 100644 --- a/src/include/gnunet_chat_service.h +++ b/src/include/gnunet_chat_service.h @@ -111,7 +111,7 @@ typedef int (*GNUNET_CHAT_JoinCallback) (void *cls); */ typedef int (*GNUNET_CHAT_MessageCallback) (void *cls, struct GNUNET_CHAT_Room * room, - const GNUNET_HashCode * sender, + const struct GNUNET_HashCode * sender, const struct GNUNET_CONTAINER_MetaData * member_info, const char *message, @@ -156,7 +156,7 @@ typedef int (*GNUNET_CHAT_MessageConfirmation) (void *cls, uint32_t orig_seq_number, struct GNUNET_TIME_Absolute timestamp, - const GNUNET_HashCode * + const struct GNUNET_HashCode * receiver); /** @@ -195,7 +195,7 @@ GNUNET_CHAT_join_room (const struct GNUNET_CONFIGURATION_Handle *cfg, GNUNET_CHAT_MemberListCallback memberCallback, void *member_cls, GNUNET_CHAT_MessageConfirmation confirmationCallback, - void *confirmation_cls, GNUNET_HashCode * me); + void *confirmation_cls, struct GNUNET_HashCode * me); /** * Send a message. diff --git a/src/include/gnunet_common.h b/src/include/gnunet_common.h index 9f77658..4700694 100644 --- a/src/include/gnunet_common.h +++ b/src/include/gnunet_common.h @@ -46,10 +46,18 @@ #include #endif +#ifdef __cplusplus +extern "C" +{ +#if 0 /* keep Emacsens' auto-indent happy */ +} +#endif +#endif + /** * Version of the API (for entire gnunetutil.so library). */ -#define GNUNET_UTIL_VERSION 0x00090200 +#define GNUNET_UTIL_VERSION 0x00090500 /** * Named constants for return values. The following @@ -170,9 +178,13 @@ */ #define GNUNET_NORETURN __attribute__((noreturn)) +#if MINGW #if __GNUC__ > 3 /** - * gcc 4.x-ism to pack structures even on W32 (to be used before structs) + * gcc 4.x-ism to pack structures even on W32 (to be used before structs); + * Using this would cause structs to be unaligned on the stack on Sparc, + * so we *only* use this on W32 (see #670578 from Debian); fortunately, + * W32 doesn't run on sparc anyway. */ #define GNUNET_NETWORK_STRUCT_BEGIN \ _Pragma("pack(push)") \ @@ -180,19 +192,23 @@ /** * gcc 4.x-ism to pack structures even on W32 (to be used after structs) + * Using this would cause structs to be unaligned on the stack on Sparc, + * so we *only* use this on W32 (see #670578 from Debian); fortunately, + * W32 doesn't run on sparc anyway. */ #define GNUNET_NETWORK_STRUCT_END _Pragma("pack(pop)") + #else -#ifdef MINGW #error gcc 4.x or higher required on W32 systems #endif +#else /** - * Good luck, GNUNET_PACKED should suffice, but this won't work on W32 + * Define as empty, GNUNET_PACKED should suffice, but this won't work on W32 */ #define GNUNET_NETWORK_STRUCT_BEGIN /** - * Good luck, GNUNET_PACKED should suffice, but this won't work on W32 + * Define as empty, GNUNET_PACKED should suffice, but this won't work on W32; */ #define GNUNET_NETWORK_STRUCT_END #endif @@ -222,13 +238,21 @@ struct GNUNET_MessageHeader /** - * @brief 512-bit hashcode + * @brief A SHA-512 hashcode */ -typedef struct GNUNET_HashCode +struct GNUNET_HashCode { uint32_t bits[512 / 8 / sizeof (uint32_t)]; /* = 16 */ -} -GNUNET_HashCode; +}; + + +/** + * @brief A SHA-256 hashcode + */ +struct GNUNET_CRYPTO_ShortHashCode +{ + uint32_t bits[256 / 8 / sizeof (uint32_t)]; /* = 8 */ +}; /** @@ -237,7 +261,7 @@ GNUNET_HashCode; */ struct GNUNET_PeerIdentity { - GNUNET_HashCode hashPubKey; + struct GNUNET_HashCode hashPubKey; }; GNUNET_NETWORK_STRUCT_END @@ -285,15 +309,20 @@ typedef void (*GNUNET_Logger) (void *cls, enum GNUNET_ErrorType kind, /** - * Number of log calls to ignore. + * Get the number of log calls that are going to be skipped + * + * @return number of log calls to be ignored */ -extern unsigned int skip_log; +int +GNUNET_get_log_skip (); #if !defined(GNUNET_CULL_LOGGING) int GNUNET_get_log_call_status (int caller_level, const char *comp, const char *file, const char *function, int line); #endif + + /** * Main log function. * @@ -345,7 +374,7 @@ GNUNET_log_from_nocheck (enum GNUNET_ErrorType kind, const char *comp, if ((GNUNET_EXTRA_LOGGING > 0) || ((GNUNET_ERROR_TYPE_DEBUG & (kind)) == 0)) { \ if (GN_UNLIKELY(log_call_enabled == -1))\ log_call_enabled = GNUNET_get_log_call_status ((kind) & (~GNUNET_ERROR_TYPE_BULK), (comp), __FILE__, __FUNCTION__, log_line); \ - if (GN_UNLIKELY(skip_log > 0)) {skip_log--;}\ + if (GN_UNLIKELY(GNUNET_get_log_skip () > 0)) { GNUNET_log_skip (-1, GNUNET_NO); }\ else {\ if (GN_UNLIKELY(log_call_enabled))\ GNUNET_log_from_nocheck ((kind), comp, __VA_ARGS__); \ @@ -358,7 +387,7 @@ GNUNET_log_from_nocheck (enum GNUNET_ErrorType kind, const char *comp, if ((GNUNET_EXTRA_LOGGING > 0) || ((GNUNET_ERROR_TYPE_DEBUG & (kind)) == 0)) { \ if (GN_UNLIKELY(log_call_enabled == -1))\ log_call_enabled = GNUNET_get_log_call_status ((kind) & (~GNUNET_ERROR_TYPE_BULK), NULL, __FILE__, __FUNCTION__, log_line);\ - if (GN_UNLIKELY(skip_log > 0)) {skip_log--;}\ + if (GN_UNLIKELY(GNUNET_get_log_skip () > 0)) { GNUNET_log_skip (-1, GNUNET_NO); }\ else {\ if (GN_UNLIKELY(log_call_enabled))\ GNUNET_log_nocheck ((kind), __VA_ARGS__); \ @@ -371,6 +400,34 @@ GNUNET_log_from_nocheck (enum GNUNET_ErrorType kind, const char *comp, #endif +/** + * Log error message about missing configuration option. + * + * @param kind log level + * @param section section with missing option + * @param option name of missing option + */ +void +GNUNET_log_config_missing (enum GNUNET_ErrorType kind, + const char *section, + const char *option); + + +/** + * Log error message about invalid configuration option value. + * + * @param kind log level + * @param section section with invalid option + * @param option name of invalid option + * @param required what is required that is invalid about the option + */ +void +GNUNET_log_config_invalid (enum GNUNET_ErrorType kind, + const char *section, + const char *option, + const char *required); + + /** * Abort the process, generate a core dump if possible. */ @@ -380,11 +437,11 @@ GNUNET_abort (void) GNUNET_NORETURN; /** * Ignore the next n calls to the log function. * - * @param n number of log calls to ignore + * @param n number of log calls to ignore (could be negative) * @param check_reset GNUNET_YES to assert that the log skip counter is currently zero */ void -GNUNET_log_skip (unsigned int n, int check_reset); +GNUNET_log_skip (int n, int check_reset); /** @@ -419,6 +476,31 @@ void GNUNET_logger_remove (GNUNET_Logger logger, void *logger_cls); +/** + * Convert a short hash value to a string (for printing debug messages). + * This is one of the very few calls in the entire API that is + * NOT reentrant! + * + * @param hc the short hash code + * @return string + */ +const char * +GNUNET_short_h2s (const struct GNUNET_CRYPTO_ShortHashCode * hc); + + +/** + * Convert a short hash value to a string (for printing debug messages). + * This prints all 104 characters of a hashcode! + * This is one of the very few calls in the entire API that is + * NOT reentrant! + * + * @param hc the short hash code + * @return string + */ +const char * +GNUNET_short_h2s_full (const struct GNUNET_CRYPTO_ShortHashCode * hc); + + /** * Convert a hash value to a string (for printing debug messages). * This is one of the very few calls in the entire API that is @@ -428,7 +510,7 @@ GNUNET_logger_remove (GNUNET_Logger logger, void *logger_cls); * @return string */ const char * -GNUNET_h2s (const GNUNET_HashCode * hc); +GNUNET_h2s (const struct GNUNET_HashCode * hc); /** @@ -441,7 +523,7 @@ GNUNET_h2s (const GNUNET_HashCode * hc); * @return string */ const char * -GNUNET_h2s_full (const GNUNET_HashCode * hc); +GNUNET_h2s_full (const struct GNUNET_HashCode * hc); /** @@ -855,4 +937,17 @@ GNUNET_copy_message (const struct GNUNET_MessageHeader *msg); #endif #endif + + + +#if 0 /* keep Emacsens' auto-indent happy */ +{ +#endif +#ifdef __cplusplus +} +#endif + + + + #endif /*GNUNET_COMMON_H_ */ diff --git a/src/include/gnunet_configuration_lib.h b/src/include/gnunet_configuration_lib.h index 0fcb4e0..0c87a53 100644 --- a/src/include/gnunet_configuration_lib.h +++ b/src/include/gnunet_configuration_lib.h @@ -112,6 +112,37 @@ GNUNET_CONFIGURATION_parse (struct GNUNET_CONFIGURATION_Handle *cfg, const char *filename); +/** + * Serializes the given configuration. + * + * @param cfg configuration to serialize + * @param size will be set to the size of the serialized memory block + * @return the memory block where the serialized configuration is + * present. This memory should be freed by the caller + */ +char * +GNUNET_CONFIGURATION_serialize (const struct GNUNET_CONFIGURATION_Handle *cfg, + size_t *size); + + +/** + * De-serializes configuration + * + * @param cfg configuration to update + * @param mem the memory block of serialized configuration + * @param size the size of the memory block + * @param allow_inline set to GNUNET_YES if we recursively load configuration + * from inlined configurations; GNUNET_NO if not and raise warnings + * when we come across them + * @return GNUNET_OK on success, GNUNET_ERROR on error + */ +int +GNUNET_CONFIGURATION_deserialize (struct GNUNET_CONFIGURATION_Handle *cfg, + const char *mem, + const size_t size, + int allow_inline); + + /** * Write configuration file. * @@ -123,6 +154,7 @@ int GNUNET_CONFIGURATION_write (struct GNUNET_CONFIGURATION_Handle *cfg, const char *filename); + /** * Write only configuration entries that have been changed to configuration file * @param cfgDefault default configuration @@ -136,6 +168,21 @@ GNUNET_CONFIGURATION_write_diffs (const struct GNUNET_CONFIGURATION_Handle const struct GNUNET_CONFIGURATION_Handle *cfgNew, const char *filename); + +/** + * Compute configuration with only entries that have been changed + * + * @param cfgDefault original configuration + * @param cfgNew new configuration + * @return configuration with only the differences, never NULL + */ +struct GNUNET_CONFIGURATION_Handle * +GNUNET_CONFIGURATION_get_diff (const struct GNUNET_CONFIGURATION_Handle + *cfgDefault, + const struct GNUNET_CONFIGURATION_Handle + *cfgNew); + + /** * Test if there are configuration options that were * changed since the last save. diff --git a/src/include/gnunet_constants.h b/src/include/gnunet_constants.h index 771b473..f104834 100644 --- a/src/include/gnunet_constants.h +++ b/src/include/gnunet_constants.h @@ -51,30 +51,11 @@ extern "C" */ #define GNUNET_CONSTANTS_IDLE_CONNECTION_TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MINUTES, 5) -/** - * After how long do we consider a connection to a peer dead - * if we got an explicit disconnect and were unable to reconnect? - */ -#define GNUNET_CONSTANTS_DISCONNECT_SESSION_TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 3) - /** * How long do we delay reading more from a peer after a quota violation? */ #define GNUNET_CONSTANTS_QUOTA_VIOLATION_TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 2) -/** - * How long do we wait after a FORK+EXEC before testing for the - * resulting process to be up (port open, waitpid, etc.)? - */ -#define GNUNET_CONSTANTS_EXEC_WAIT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MILLISECONDS, 200) - -/** - * After how long do we retry a service connection that was - * unavailable? Used in cases where an exponential back-off - * seems inappropriate. - */ -#define GNUNET_CONSTANTS_SERVICE_RETRY GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MILLISECONDS, 500) - /** * After how long do we consider a service unresponsive * even if we assume that the service commonly does not @@ -116,19 +97,7 @@ extern "C" * Size of the 'struct EncryptedMessage' of the core (which * is the per-message overhead of the core). */ -#define GNUNET_CONSTANTS_CORE_SIZE_ENCRYPTED_MESSAGE (24 + sizeof (GNUNET_HashCode)) - -/** - * Size of the 'struct OutboundMessage' of the transport - * (which, in combination with the - * GNUNET_CONSTANTS_CORE_SIZE_ENCRYPTED_MESSAGE) defines - * the headers that must be pre-pendable to all GNUnet - * messages. Taking GNUNET_SERVER_MAX_MESSAGE_SIZE - * and subtracting these two constants defines the largest - * message core can handle. - */ -#define GNUNET_CONSTANTS_TRANSPORT_SIZE_OUTBOUND_MESSAGE (16 + sizeof (struct GNUNET_PeerIdentity)) - +#define GNUNET_CONSTANTS_CORE_SIZE_ENCRYPTED_MESSAGE (24 + sizeof (struct GNUNET_HashCode)) /** * What is the maximum size for encrypted messages? Note that this diff --git a/src/include/gnunet_container_lib.h b/src/include/gnunet_container_lib.h index a78d8cc..0616006 100644 --- a/src/include/gnunet_container_lib.h +++ b/src/include/gnunet_container_lib.h @@ -62,7 +62,7 @@ struct GNUNET_CONTAINER_BloomFilter; * @return GNUNET_YES if next was updated * GNUNET_NO if there are no more entries */ -typedef int (*GNUNET_HashCodeIterator) (void *cls, GNUNET_HashCode * next); +typedef int (*GNUNET_HashCodeIterator) (void *cls, struct GNUNET_HashCode * next); /** @@ -121,7 +121,7 @@ GNUNET_CONTAINER_bloomfilter_get_raw_data (const struct */ int GNUNET_CONTAINER_bloomfilter_test (const struct GNUNET_CONTAINER_BloomFilter - *bf, const GNUNET_HashCode * e); + *bf, const struct GNUNET_HashCode * e); /** @@ -131,7 +131,7 @@ GNUNET_CONTAINER_bloomfilter_test (const struct GNUNET_CONTAINER_BloomFilter */ void GNUNET_CONTAINER_bloomfilter_add (struct GNUNET_CONTAINER_BloomFilter *bf, - const GNUNET_HashCode * e); + const struct GNUNET_HashCode * e); /** @@ -141,7 +141,7 @@ GNUNET_CONTAINER_bloomfilter_add (struct GNUNET_CONTAINER_BloomFilter *bf, */ void GNUNET_CONTAINER_bloomfilter_remove (struct GNUNET_CONTAINER_BloomFilter *bf, - const GNUNET_HashCode * e); + const struct GNUNET_HashCode * e); /** @@ -294,7 +294,7 @@ GNUNET_CONTAINER_meta_data_test_equal (const struct GNUNET_CONTAINER_MetaData * @param data_mime_type mime-type of data (not of the original file); * can be NULL (if mime-type is not known) * @param data actual meta-data found - * @param data_len number of bytes in data + * @param data_size number of bytes in data * @return GNUNET_OK on success, GNUNET_SYSERR if this entry already exists * data_mime_type and plugin_name are not considered for "exists" checks */ @@ -304,7 +304,7 @@ GNUNET_CONTAINER_meta_data_insert (struct GNUNET_CONTAINER_MetaData *md, enum EXTRACTOR_MetaType type, enum EXTRACTOR_MetaFormat format, const char *data_mime_type, const char *data, - size_t data_len); + size_t data_size); /** @@ -326,13 +326,13 @@ GNUNET_CONTAINER_meta_data_merge (struct GNUNET_CONTAINER_MetaData *md, * @param type type of the item to remove * @param data specific value to remove, NULL to remove all * entries of the given type - * @param data_len number of bytes in data + * @param data_size number of bytes in data * @return GNUNET_OK on success, GNUNET_SYSERR if the item does not exist in md */ int GNUNET_CONTAINER_meta_data_delete (struct GNUNET_CONTAINER_MetaData *md, enum EXTRACTOR_MetaType type, - const char *data, size_t data_len); + const char *data, size_t data_size); /** @@ -534,7 +534,7 @@ enum GNUNET_CONTAINER_MultiHashMapOption * GNUNET_NO if not. */ typedef int (*GNUNET_CONTAINER_HashMapIterator) (void *cls, - const GNUNET_HashCode * key, + const struct GNUNET_HashCode * key, void *value); @@ -542,10 +542,20 @@ typedef int (*GNUNET_CONTAINER_HashMapIterator) (void *cls, * Create a multi hash map. * * @param len initial size (map will grow as needed) + * @param do_not_copy_keys GNUNET_NO is always safe and should be used by default; + * GNUNET_YES means that on 'put', the 'key' does not have + * to be copied as the destination of the pointer is + * guaranteed to be life as long as the value is stored in + * the hashmap. This can significantly reduce memory + * consumption, but of course is also a recipie for + * heap corruption if the assumption is not true. Only + * use this if (1) memory use is important in this case and + * (2) you have triple-checked that the invariant holds * @return NULL on error */ struct GNUNET_CONTAINER_MultiHashMap * -GNUNET_CONTAINER_multihashmap_create (unsigned int len); +GNUNET_CONTAINER_multihashmap_create (unsigned int len, + int do_not_copy_keys); /** @@ -571,7 +581,7 @@ GNUNET_CONTAINER_multihashmap_destroy (struct GNUNET_CONTAINER_MultiHashMap */ void * GNUNET_CONTAINER_multihashmap_get (const struct GNUNET_CONTAINER_MultiHashMap - *map, const GNUNET_HashCode * key); + *map, const struct GNUNET_HashCode * key); /** @@ -587,7 +597,7 @@ GNUNET_CONTAINER_multihashmap_get (const struct GNUNET_CONTAINER_MultiHashMap */ int GNUNET_CONTAINER_multihashmap_remove (struct GNUNET_CONTAINER_MultiHashMap *map, - const GNUNET_HashCode * key, void *value); + const struct GNUNET_HashCode * key, void *value); /** * Remove all entries for the given key from the map. @@ -599,7 +609,7 @@ GNUNET_CONTAINER_multihashmap_remove (struct GNUNET_CONTAINER_MultiHashMap *map, */ int GNUNET_CONTAINER_multihashmap_remove_all (struct GNUNET_CONTAINER_MultiHashMap - *map, const GNUNET_HashCode * key); + *map, const struct GNUNET_HashCode * key); /** @@ -614,7 +624,7 @@ GNUNET_CONTAINER_multihashmap_remove_all (struct GNUNET_CONTAINER_MultiHashMap int GNUNET_CONTAINER_multihashmap_contains (const struct GNUNET_CONTAINER_MultiHashMap *map, - const GNUNET_HashCode * key); + const struct GNUNET_HashCode * key); /** @@ -630,7 +640,7 @@ GNUNET_CONTAINER_multihashmap_contains (const struct int GNUNET_CONTAINER_multihashmap_contains_value (const struct GNUNET_CONTAINER_MultiHashMap - *map, const GNUNET_HashCode * key, + *map, const struct GNUNET_HashCode * key, const void *value); @@ -648,7 +658,7 @@ GNUNET_CONTAINER_multihashmap_contains_value (const struct */ int GNUNET_CONTAINER_multihashmap_put (struct GNUNET_CONTAINER_MultiHashMap *map, - const GNUNET_HashCode * key, void *value, + const struct GNUNET_HashCode * key, void *value, enum GNUNET_CONTAINER_MultiHashMapOption opt); @@ -692,7 +702,7 @@ GNUNET_CONTAINER_multihashmap_iterate (const struct int GNUNET_CONTAINER_multihashmap_get_multiple (const struct GNUNET_CONTAINER_MultiHashMap *map, - const GNUNET_HashCode * key, + const struct GNUNET_HashCode * key, GNUNET_CONTAINER_HashMapIterator it, void *it_cls); @@ -822,6 +832,136 @@ GNUNET_CONTAINER_multihashmap_get_multiple (const struct (element)->prev = NULL; } while (0) +/* ************ Multi-DLL interface, allows DLL elements to be + in multiple lists at the same time *********************** */ + +/** + * Insert an element at the head of a MDLL. Assumes that head, tail and + * element are structs with prev and next fields. + * + * @param mdll suffix name for the next and prev pointers in the element + * @param head pointer to the head of the MDLL + * @param tail pointer to the tail of the MDLL + * @param element element to insert + */ +#define GNUNET_CONTAINER_MDLL_insert(mdll,head,tail,element) do { \ + GNUNET_assert ( ( (element)->prev_##mdll == NULL) && ((head) != (element))); \ + GNUNET_assert ( ( (element)->next_##mdll == NULL) && ((tail) != (element))); \ + (element)->next_##mdll = (head); \ + (element)->prev_##mdll = NULL; \ + if ((tail) == NULL) \ + (tail) = element; \ + else \ + (head)->prev_##mdll = element; \ + (head) = (element); } while (0) + + +/** + * Insert an element at the tail of a MDLL. Assumes that head, tail and + * element are structs with prev and next fields. + * + * @param mdll suffix name for the next and prev pointers in the element + * @param head pointer to the head of the MDLL + * @param tail pointer to the tail of the MDLL + * @param element element to insert + */ +#define GNUNET_CONTAINER_MDLL_insert_tail(mdll,head,tail,element) do { \ + GNUNET_assert ( ( (element)->prev_##mdll == NULL) && ((head) != (element))); \ + GNUNET_assert ( ( (element)->next_##mdll == NULL) && ((tail) != (element))); \ + (element)->prev_##mdll = (tail); \ + (element)->next_##mdll = NULL; \ + if ((head) == NULL) \ + (head) = element; \ + else \ + (tail)->next_##mdll = element; \ + (tail) = (element); } while (0) + + +/** + * Insert an element into a MDLL after the given other element. Insert + * at the head if the other element is NULL. + * + * @param mdll suffix name for the next and prev pointers in the element + * @param head pointer to the head of the MDLL + * @param tail pointer to the tail of the MDLL + * @param other prior element, NULL for insertion at head of MDLL + * @param element element to insert + */ +#define GNUNET_CONTAINER_MDLL_insert_after(mdll,head,tail,other,element) do { \ + GNUNET_assert ( ( (element)->prev_##mdll == NULL) && ((head) != (element))); \ + GNUNET_assert ( ( (element)->next_##mdll == NULL) && ((tail) != (element))); \ + (element)->prev_##mdll = (other); \ + if (NULL == other) \ + { \ + (element)->next_##mdll = (head); \ + (head) = (element); \ + } \ + else \ + { \ + (element)->next_##mdll = (other)->next_##mdll; \ + (other)->next_##mdll = (element); \ + } \ + if (NULL == (element)->next_##mdll) \ + (tail) = (element); \ + else \ + (element)->next->prev_##mdll = (element); } while (0) + + +/** + * Insert an element into a MDLL before the given other element. Insert + * at the tail if the other element is NULL. + * + * @param mdll suffix name for the next and prev pointers in the element + * @param head pointer to the head of the MDLL + * @param tail pointer to the tail of the MDLL + * @param other prior element, NULL for insertion at head of MDLL + * @param element element to insert + */ +#define GNUNET_CONTAINER_MDLL_insert_before(mdll,head,tail,other,element) do { \ + GNUNET_assert ( ( (element)->prev_##mdll == NULL) && ((head) != (element))); \ + GNUNET_assert ( ( (element)->next_##mdll == NULL) && ((tail) != (element))); \ + (element)->next_##mdll = (other); \ + if (NULL == other) \ + { \ + (element)->prev = (tail); \ + (tail) = (element); \ + } \ + else \ + { \ + (element)->prev_##mdll = (other)->prev_##mdll; \ + (other)->prev_##mdll = (element); \ + } \ + if (NULL == (element)->prev_##mdll) \ + (head) = (element); \ + else \ + (element)->prev_##mdll->next_##mdll = (element); } while (0) + + +/** + * Remove an element from a MDLL. Assumes + * that head, tail and element are structs + * with prev and next fields. + * + * @param mdll suffix name for the next and prev pointers in the element + * @param head pointer to the head of the MDLL + * @param tail pointer to the tail of the MDLL + * @param element element to remove + */ +#define GNUNET_CONTAINER_MDLL_remove(mdll,head,tail,element) do { \ + GNUNET_assert ( ( (element)->prev_##mdll != NULL) || ((head) == (element))); \ + GNUNET_assert ( ( (element)->next_##mdll != NULL) || ((tail) == (element))); \ + if ((element)->prev_##mdll == NULL) \ + (head) = (element)->next_##mdll; \ + else \ + (element)->prev_##mdll->next_##mdll = (element)->next_##mdll; \ + if ((element)->next_##mdll == NULL) \ + (tail) = (element)->prev_##mdll; \ + else \ + (element)->next_##mdll->prev_##mdll = (element)->prev_##mdll; \ + (element)->next_##mdll = NULL; \ + (element)->prev_##mdll = NULL; } while (0) + + /* ******************** Heap *************** */ @@ -942,24 +1082,6 @@ GNUNET_CONTAINER_heap_iterate (const struct GNUNET_CONTAINER_Heap *heap, GNUNET_CONTAINER_HeapIterator iterator, void *iterator_cls); - -/** - * Return a *uniform* random element from the heap. Choose a random - * number between 0 and heap size and then walk directly to it. - * This cost can be between 0 and n, amortized cost of logN. - * - * @param heap heap to choose random element from - * @param max how many nodes from the heap to choose from - * - * @return data stored at the chosen random node, - * NULL if the heap is empty. - * - */ -void * -GNUNET_CONTAINER_heap_get_random (struct GNUNET_CONTAINER_Heap *heap, - uint32_t max); - - /** * Perform a random walk of the tree. The walk is biased * towards elements closer to the root of the tree (since diff --git a/src/include/gnunet_core_service.h b/src/include/gnunet_core_service.h index cb48f41..4af8ef2 100644 --- a/src/include/gnunet_core_service.h +++ b/src/include/gnunet_core_service.h @@ -42,7 +42,7 @@ extern "C" /** * Version number of GNUnet-core API. */ -#define GNUNET_CORE_VERSION 0x00000000 +#define GNUNET_CORE_VERSION 0x00000001 /** @@ -131,7 +131,9 @@ struct GNUNET_CORE_MessageHandler * for good). Note that the private key of the peer is intentionally * not exposed here; if you need it, your process should try to read * the private key file directly (which should work if you are - * authorized...). + * authorized...). Implementations of this function must not call + * GNUNET_CORE_disconnect (other than by scheduling a new task to + * do this later). * * @param cls closure * @param server handle to the server, NULL if we failed @@ -148,14 +150,13 @@ typedef void (*GNUNET_CORE_StartupCallback) (void *cls, * (or fail) asynchronously. This function primarily causes the given * callback notification functions to be invoked whenever the * specified event happens. The maximum number of queued - * notifications (queue length) is per client but the queue is shared + * notifications (queue length) is per client; the queue is shared * across all types of notifications. So a slow client that registers * for 'outbound_notify' also risks missing 'inbound_notify' messages. * Certain events (such as connect/disconnect notifications) are not * subject to queue size limitations. * * @param cfg configuration to use - * @param queue_size size of the per-peer message queue * @param cls closure for the various callbacks that follow (including handlers in the handlers array) * @param init callback to call once we have successfully * connected to the core service @@ -190,7 +191,7 @@ typedef void (*GNUNET_CORE_StartupCallback) (void *cls, */ struct GNUNET_CORE_Handle * GNUNET_CORE_connect (const struct GNUNET_CONFIGURATION_Handle *cfg, - unsigned int queue_size, void *cls, + void *cls, GNUNET_CORE_StartupCallback init, GNUNET_CORE_ConnectEventHandler connects, GNUNET_CORE_DisconnectEventHandler disconnects, @@ -220,10 +221,13 @@ struct GNUNET_CORE_TransmitHandle; /** * Ask the core to call "notify" once it is ready to transmit the - * given number of bytes to the specified "target". Must only be + * given number of bytes to the specified "target". Must only be * called after a connection to the respective peer has been - * established (and the client has been informed about this). - * + * established (and the client has been informed about this). You may + * have one request of this type pending for each connected peer at + * any time. If a peer disconnects, the application MUST call + * "GNUNET_CORE_notify_transmit_ready_cancel" on the respective + * transmission request, if one such request is pending. * * @param handle connection to core service * @param cork is corking allowed for this transmission? @@ -232,18 +236,13 @@ struct GNUNET_CORE_TransmitHandle; * @param target who should receive the message, never NULL (can be this peer's identity for loopback) * @param notify_size how many bytes of buffer space does notify want? * @param notify function to call when buffer space is available; - * will be called with NULL on timeout or if the overall queue - * for this peer is larger than queue_size and this is currently - * the message with the lowest priority; will also be called - * with 'NULL' buf if the peer disconnects; since the disconnect - * signal will be emmitted even later, clients MUST cancel + * will be called with NULL on timeout; clients MUST cancel * all pending transmission requests DURING the disconnect - * handler (unless they ensure that 'notify' never calls - * 'GNUNET_CORE_notify_transmit_ready'). + * handler * @param notify_cls closure for notify * @return non-NULL if the notify callback was queued, - * NULL if we can not even queue the request (insufficient - * memory); if NULL is returned, "notify" will NOT be called. + * NULL if we can not even queue the request (request already pending); + * if NULL is returned, "notify" will NOT be called. */ struct GNUNET_CORE_TransmitHandle * GNUNET_CORE_notify_transmit_ready (struct GNUNET_CORE_Handle *handle, int cork, @@ -327,6 +326,26 @@ void GNUNET_CORE_is_peer_connected_cancel (struct GNUNET_CORE_ConnectTestHandle *cth); +/** + * Check if the given peer is currently connected. This function is for special + * cirumstances (GNUNET_TESTBED uses it), normal users of the CORE API are + * expected to track which peers are connected based on the connect/disconnect + * callbacks from GNUNET_CORE_connect. This function is NOT part of the + * 'versioned', 'official' API. The difference between this function and the + * function GNUNET_CORE_is_peer_connected() is that this one returns + * synchronously after looking in the CORE API cache. The function + * GNUNET_CORE_is_peer_connected() sends a message to the CORE service and hence + * its response is given asynchronously. + * + * @param h the core handle + * @param pid the identity of the peer to check if it has been connected to us + * @return GNUNET_YES if the peer is connected to us; GNUNET_NO if not + */ +int +GNUNET_CORE_is_peer_connected_sync (const struct GNUNET_CORE_Handle *h, + const struct GNUNET_PeerIdentity *pid); + + #if 0 /* keep Emacsens' auto-indent happy */ { #endif diff --git a/src/include/gnunet_crypto_lib.h b/src/include/gnunet_crypto_lib.h index 777ddd9..6120b48 100644 --- a/src/include/gnunet_crypto_lib.h +++ b/src/include/gnunet_crypto_lib.h @@ -71,7 +71,6 @@ enum GNUNET_CRYPTO_Quality */ #define GNUNET_CRYPTO_AES_KEY_LENGTH (256/8) - /** * @brief Length of RSA encrypted data (2048 bit) * @@ -84,23 +83,39 @@ enum GNUNET_CRYPTO_Quality */ #define GNUNET_CRYPTO_RSA_DATA_ENCODING_LENGTH 256 - /** * Length of an RSA KEY (n,e,len), 2048 bit (=256 octests) key n, 2 byte e */ #define GNUNET_CRYPTO_RSA_KEY_LENGTH 258 - /** * Length of a hash value */ -#define GNUNET_CRYPTO_HASH_LENGTH 512/8 +#define GNUNET_CRYPTO_HASH_LENGTH (512/8) + +/** + * Maximum length of an ECC signature. + * Note: round up to multiple of 8 minus 2 for alignment. + */ +#define GNUNET_CRYPTO_ECC_SIGNATURE_DATA_ENCODING_LENGTH 190 + +/** + * Maximum length of the public key (q-point, Q = dP) when encoded. + */ +#define GNUNET_CRYPTO_ECC_MAX_PUBLIC_KEY_LENGTH 140 + /** * The private information of an RSA key pair. */ struct GNUNET_CRYPTO_RsaPrivateKey; +/** + * The private information of an ECC private key. + */ +struct GNUNET_CRYPTO_EccPrivateKey; + + GNUNET_NETWORK_STRUCT_BEGIN /** @@ -129,7 +144,7 @@ GNUNET_NETWORK_STRUCT_END /** - * @brief 0-terminated ASCII encoding of a GNUNET_HashCode. + * @brief 0-terminated ASCII encoding of a struct GNUNET_HashCode. */ struct GNUNET_CRYPTO_HashAsciiEncoded { @@ -137,17 +152,6 @@ struct GNUNET_CRYPTO_HashAsciiEncoded }; - - -/** - * @brief 256-bit hashcode - */ -struct GNUNET_CRYPTO_ShortHashCode -{ - uint32_t bits[256 / 8 / sizeof (uint32_t)]; /* = 8 */ -}; - - /** * @brief 0-terminated ASCII encoding of a 'struct GNUNET_ShortHashCode'. */ @@ -230,6 +234,85 @@ struct GNUNET_CRYPTO_RsaEncryptedData }; +/** + * @brief header of what an ECC signature signs + * this must be followed by "size - 8" bytes of + * the actual signed data + */ +struct GNUNET_CRYPTO_EccSignaturePurpose +{ + /** + * How many bytes does this signature sign? + * (including this purpose header); in network + * byte order (!). + */ + uint32_t size GNUNET_PACKED; + + /** + * What does this signature vouch for? This + * must contain a GNUNET_SIGNATURE_PURPOSE_XXX + * constant (from gnunet_signatures.h). In + * network byte order! + */ + uint32_t purpose GNUNET_PACKED; + +}; + + +/** + * @brief an ECC signature + */ +struct GNUNET_CRYPTO_EccSignature +{ + /** + * Overall size of the signature data. + */ + uint16_t size; + + /** + * S-expression, padded with zeros. + */ + char sexpr[GNUNET_CRYPTO_ECC_SIGNATURE_DATA_ENCODING_LENGTH]; +}; + + +/** + * Public ECC key (always for NIST P-521) encoded in a format suitable + * for network transmission as created using 'gcry_sexp_sprint'. + */ +struct GNUNET_CRYPTO_EccPublicKeyBinaryEncoded +{ + /** + * Size of the encoding, in network byte order. + */ + uint16_t size; + + /** + * Actual length of the q-point binary encoding. + */ + uint16_t len; + + /** + * 0-padded q-point in binary encoding (GCRYPT_MPI_FMT_USG). + */ + unsigned char key[GNUNET_CRYPTO_ECC_MAX_PUBLIC_KEY_LENGTH]; +}; + + +struct GNUNET_CRYPTO_EccPrivateKeyBinaryEncoded +{ + /** + * Overall size of the private key. + */ + uint16_t size; + + /* followd by S-expression, opaque to applications */ + + /* FIXME: consider defining padding to make this a fixed-size struct */ + +}; + + /** * @brief type for session keys */ @@ -251,7 +334,7 @@ GNUNET_NETWORK_STRUCT_END * @brief IV for sym cipher * * NOTE: must be smaller (!) in size than the - * GNUNET_HashCode. + * struct GNUNET_HashCode. */ struct GNUNET_CRYPTO_AesInitializationVector { @@ -448,7 +531,7 @@ GNUNET_CRYPTO_aes_derive_iv_v (struct GNUNET_CRYPTO_AesInitializationVector *iv, * safely cast to char*, a '\\0' termination is set). */ void -GNUNET_CRYPTO_hash_to_enc (const GNUNET_HashCode * block, +GNUNET_CRYPTO_hash_to_enc (const struct GNUNET_HashCode * block, struct GNUNET_CRYPTO_HashAsciiEncoded *result); @@ -465,7 +548,7 @@ GNUNET_CRYPTO_short_hash_to_enc (const struct GNUNET_CRYPTO_ShortHashCode * bloc /** - * Convert ASCII encoding back to a 'GNUNET_HashCode' + * Convert ASCII encoding back to a 'struct GNUNET_HashCode' * * @param enc the encoding * @param enclen number of characters in 'enc' (without 0-terminator, which can be missing) @@ -474,7 +557,7 @@ GNUNET_CRYPTO_short_hash_to_enc (const struct GNUNET_CRYPTO_ShortHashCode * bloc */ int GNUNET_CRYPTO_hash_from_string2 (const char *enc, size_t enclen, - GNUNET_HashCode * result); + struct GNUNET_HashCode * result); /** @@ -491,7 +574,7 @@ GNUNET_CRYPTO_short_hash_from_string2 (const char *enc, size_t enclen, /** - * Convert ASCII encoding back to GNUNET_HashCode + * Convert ASCII encoding back to struct GNUNET_HashCode * * @param enc the encoding * @param result where to store the hash code @@ -536,8 +619,8 @@ GNUNET_CRYPTO_short_hash_cmp (const struct GNUNET_CRYPTO_ShortHashCode * h1, * @return number between 0 and UINT32_MAX */ uint32_t -GNUNET_CRYPTO_hash_distance_u32 (const GNUNET_HashCode * a, - const GNUNET_HashCode * b); +GNUNET_CRYPTO_hash_distance_u32 (const struct GNUNET_HashCode * a, + const struct GNUNET_HashCode * b); /** @@ -548,7 +631,7 @@ GNUNET_CRYPTO_hash_distance_u32 (const GNUNET_HashCode * a, * @param ret pointer to where to write the hashcode */ void -GNUNET_CRYPTO_hash (const void *block, size_t size, GNUNET_HashCode * ret); +GNUNET_CRYPTO_hash (const void *block, size_t size, struct GNUNET_HashCode * ret); /** @@ -598,7 +681,7 @@ GNUNET_CRYPTO_short_hash_from_truncation (const struct GNUNET_HashCode *dh, void GNUNET_CRYPTO_hmac (const struct GNUNET_CRYPTO_AuthKey *key, const void *plaintext, size_t plaintext_len, - GNUNET_HashCode * hmac); + struct GNUNET_HashCode * hmac); /** @@ -609,7 +692,7 @@ GNUNET_CRYPTO_hmac (const struct GNUNET_CRYPTO_AuthKey *key, * @param res resulting hash, NULL on error */ typedef void (*GNUNET_CRYPTO_HashCompletedCallback) (void *cls, - const GNUNET_HashCode * + const struct GNUNET_HashCode * res); @@ -652,7 +735,7 @@ GNUNET_CRYPTO_hash_file_cancel (struct GNUNET_CRYPTO_FileHashContext *fhc); */ void GNUNET_CRYPTO_hash_create_random (enum GNUNET_CRYPTO_Quality mode, - GNUNET_HashCode * result); + struct GNUNET_HashCode * result); /** @@ -663,9 +746,9 @@ GNUNET_CRYPTO_hash_create_random (enum GNUNET_CRYPTO_Quality mode, * @param result set to b - a */ void -GNUNET_CRYPTO_hash_difference (const GNUNET_HashCode * a, - const GNUNET_HashCode * b, - GNUNET_HashCode * result); +GNUNET_CRYPTO_hash_difference (const struct GNUNET_HashCode * a, + const struct GNUNET_HashCode * b, + struct GNUNET_HashCode * result); /** @@ -676,9 +759,9 @@ GNUNET_CRYPTO_hash_difference (const GNUNET_HashCode * a, * @param result set to a + delta */ void -GNUNET_CRYPTO_hash_sum (const GNUNET_HashCode * a, - const GNUNET_HashCode * delta, - GNUNET_HashCode * result); +GNUNET_CRYPTO_hash_sum (const struct GNUNET_HashCode * a, + const struct GNUNET_HashCode * delta, + struct GNUNET_HashCode * result); /** @@ -689,8 +772,8 @@ GNUNET_CRYPTO_hash_sum (const GNUNET_HashCode * a, * @param result set to a ^ b */ void -GNUNET_CRYPTO_hash_xor (const GNUNET_HashCode * a, const GNUNET_HashCode * b, - GNUNET_HashCode * result); +GNUNET_CRYPTO_hash_xor (const struct GNUNET_HashCode * a, const struct GNUNET_HashCode * b, + struct GNUNET_HashCode * result); /** @@ -701,7 +784,7 @@ GNUNET_CRYPTO_hash_xor (const GNUNET_HashCode * a, const GNUNET_HashCode * b, * @param iv set to a valid initialization vector */ void -GNUNET_CRYPTO_hash_to_aes_key (const GNUNET_HashCode * hc, +GNUNET_CRYPTO_hash_to_aes_key (const struct GNUNET_HashCode * hc, struct GNUNET_CRYPTO_AesSessionKey *skey, struct GNUNET_CRYPTO_AesInitializationVector *iv); @@ -715,11 +798,11 @@ GNUNET_CRYPTO_hash_to_aes_key (const GNUNET_HashCode * hc, * @return Bit \a bit from hashcode \a code, -1 for invalid index */ int -GNUNET_CRYPTO_hash_get_bit (const GNUNET_HashCode * code, unsigned int bit); +GNUNET_CRYPTO_hash_get_bit (const struct GNUNET_HashCode * code, unsigned int bit); /** * Determine how many low order bits match in two - * GNUNET_HashCodes. i.e. - 010011 and 011111 share + * struct GNUNET_HashCodes. i.e. - 010011 and 011111 share * the first two lowest order bits, and therefore the * return value is two (NOT XOR distance, nor how many * bits match absolutely!). @@ -730,8 +813,8 @@ GNUNET_CRYPTO_hash_get_bit (const GNUNET_HashCode * code, unsigned int bit); * @return the number of bits that match */ unsigned int -GNUNET_CRYPTO_hash_matching_bits (const GNUNET_HashCode * first, - const GNUNET_HashCode * second); +GNUNET_CRYPTO_hash_matching_bits (const struct GNUNET_HashCode * first, + const struct GNUNET_HashCode * second); /** @@ -743,7 +826,7 @@ GNUNET_CRYPTO_hash_matching_bits (const GNUNET_HashCode * first, * @return 1 if h1 > h2, -1 if h1 < h2 and 0 if h1 == h2. */ int -GNUNET_CRYPTO_hash_cmp (const GNUNET_HashCode * h1, const GNUNET_HashCode * h2); +GNUNET_CRYPTO_hash_cmp (const struct GNUNET_HashCode * h1, const struct GNUNET_HashCode * h2); /** @@ -756,9 +839,9 @@ GNUNET_CRYPTO_hash_cmp (const GNUNET_HashCode * h1, const GNUNET_HashCode * h2); * @return -1 if h1 is closer, 1 if h2 is closer and 0 if h1==h2. */ int -GNUNET_CRYPTO_hash_xorcmp (const GNUNET_HashCode * h1, - const GNUNET_HashCode * h2, - const GNUNET_HashCode * target); +GNUNET_CRYPTO_hash_xorcmp (const struct GNUNET_HashCode * h1, + const struct GNUNET_HashCode * h2, + const struct GNUNET_HashCode * target); /** @@ -859,15 +942,6 @@ GNUNET_CRYPTO_kdf (void *result, size_t out_len, const void *xts, size_t xts_len, const void *skm, size_t skm_len, ...); -/** - * Create a new private key. Caller must free return value. - * - * @return fresh private key - */ -struct GNUNET_CRYPTO_RsaPrivateKey * -GNUNET_CRYPTO_rsa_key_create (void); - - /** * Convert a public key to a string. * @@ -875,7 +949,7 @@ GNUNET_CRYPTO_rsa_key_create (void); * @return string representing 'pub' */ char * -GNUNET_CRYPTO_rsa_public_key_to_string (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *pub); +GNUNET_CRYPTO_rsa_public_key_to_string (const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *pub); /** @@ -895,22 +969,24 @@ GNUNET_CRYPTO_rsa_public_key_from_string (const char *enc, /** * Encode the private key in a format suitable for * storing it into a file. - * @returns encoding of the private key. - * The first 4 bytes give the size of the array, as usual. + * @return encoding of the private key */ struct GNUNET_CRYPTO_RsaPrivateKeyBinaryEncoded * GNUNET_CRYPTO_rsa_encode_key (const struct GNUNET_CRYPTO_RsaPrivateKey *hostkey); + /** * Decode the private key from the data-format back * to the "normal", internal format. * * @param buf the buffer where the private key data is stored * @param len the length of the data in 'buffer' + * @return NULL on error */ struct GNUNET_CRYPTO_RsaPrivateKey * GNUNET_CRYPTO_rsa_decode_key (const char *buf, uint16_t len); + /** * Create a new private key by reading it from a file. If the * files does not exist, create a new key and write it to the @@ -924,11 +1000,56 @@ GNUNET_CRYPTO_rsa_decode_key (const char *buf, uint16_t len); * @param filename name of file to use for storage * @return new private key, NULL on error (for example, * permission denied) + * @deprecated use 'GNUNET_CRYPTO_rsa_key_create_start' instead */ struct GNUNET_CRYPTO_RsaPrivateKey * GNUNET_CRYPTO_rsa_key_create_from_file (const char *filename); +/** + * Handle to cancel private key generation. + */ +struct GNUNET_CRYPTO_RsaKeyGenerationContext; + + +/** + * Function called upon completion of 'GNUNET_CRYPTO_rsa_key_create_async'. + * + * @param cls closure + * @param pk NULL on error, otherwise the private key (which must be free'd by the callee) + * @param emsg NULL on success, otherwise an error message + */ +typedef void (*GNUNET_CRYPTO_RsaKeyCallback)(void *cls, + struct GNUNET_CRYPTO_RsaPrivateKey *pk, + const char *emsg); + + +/** + * Create a new private key by reading it from a file. If the files + * does not exist, create a new key and write it to the file. If the + * contents of the file are invalid the old file is deleted and a + * fresh key is created. + * + * @param filename name of file to use for storage + * @param cont function to call when done (or on errors) + * @param cont_cls closure for 'cont' + * @return handle to abort operation, NULL on fatal errors (cont will not be called if NULL is returned) + */ +struct GNUNET_CRYPTO_RsaKeyGenerationContext * +GNUNET_CRYPTO_rsa_key_create_start (const char *filename, + GNUNET_CRYPTO_RsaKeyCallback cont, + void *cont_cls); + + +/** + * Abort RSA key generation. + * + * @param gc key generation context to abort + */ +void +GNUNET_CRYPTO_rsa_key_create_stop (struct GNUNET_CRYPTO_RsaKeyGenerationContext *gc); + + /** * Setup a hostkey file for a peer given the name of the * configuration file (!). This function is used so that @@ -938,7 +1059,7 @@ GNUNET_CRYPTO_rsa_key_create_from_file (const char *filename); * @param cfg_name name of the configuration file to use */ void -GNUNET_CRYPTO_setup_hostkey (const char *cfg_name); +GNUNET_CRYPTO_rsa_setup_hostkey (const char *cfg_name); /** @@ -949,15 +1070,16 @@ GNUNET_CRYPTO_setup_hostkey (const char *cfg_name); * @return some private key purely dependent on input */ struct GNUNET_CRYPTO_RsaPrivateKey * -GNUNET_CRYPTO_rsa_key_create_from_hash (const GNUNET_HashCode * hc); +GNUNET_CRYPTO_rsa_key_create_from_hash (const struct GNUNET_HashCode *hc); /** * Free memory occupied by the private key. - * @param hostkey pointer to the memory to free + * + * @param key pointer to the memory to free */ void -GNUNET_CRYPTO_rsa_key_free (struct GNUNET_CRYPTO_RsaPrivateKey *hostkey); +GNUNET_CRYPTO_rsa_key_free (struct GNUNET_CRYPTO_RsaPrivateKey *key); /** @@ -1039,6 +1161,202 @@ GNUNET_CRYPTO_rsa_verify (uint32_t purpose, +/** + * Function called upon completion of 'GNUNET_CRYPTO_ecc_key_create_async'. + * + * @param cls closure + * @param pk NULL on error, otherwise the private key (which must be free'd by the callee) + * @param emsg NULL on success, otherwise an error message + */ +typedef void (*GNUNET_CRYPTO_EccKeyCallback)(void *cls, + struct GNUNET_CRYPTO_EccPrivateKey *pk, + const char *emsg); + + +/** + * Free memory occupied by ECC key + * + * @param privatekey pointer to the memory to free + */ +void +GNUNET_CRYPTO_ecc_key_free (struct GNUNET_CRYPTO_EccPrivateKey *privatekey); + + +/** + * Extract the public key for the given private key. + * + * @param priv the private key + * @param pub where to write the public key + */ +void +GNUNET_CRYPTO_ecc_key_get_public (const struct GNUNET_CRYPTO_EccPrivateKey *priv, + struct GNUNET_CRYPTO_EccPublicKeyBinaryEncoded *pub); + +/** + * Convert a public key to a string. + * + * @param pub key to convert + * @return string representing 'pub' + */ +char * +GNUNET_CRYPTO_ecc_public_key_to_string (struct GNUNET_CRYPTO_EccPublicKeyBinaryEncoded *pub); + + +/** + * Convert a string representing a public key to a public key. + * + * @param enc encoded public key + * @param enclen number of bytes in enc (without 0-terminator) + * @param pub where to store the public key + * @return GNUNET_OK on success + */ +int +GNUNET_CRYPTO_ecc_public_key_from_string (const char *enc, + size_t enclen, + struct GNUNET_CRYPTO_EccPublicKeyBinaryEncoded *pub); + + +/** + * Encode the private key in a format suitable for + * storing it into a file. + * + * @param key key to encode + * @return encoding of the private key. + * The first 4 bytes give the size of the array, as usual. + */ +struct GNUNET_CRYPTO_EccPrivateKeyBinaryEncoded * +GNUNET_CRYPTO_ecc_encode_key (const struct GNUNET_CRYPTO_EccPrivateKey *key); + + +/** + * Decode the private key from the file-format back + * to the "normal", internal format. + * + * @param buf the buffer where the private key data is stored + * @param len the length of the data in 'buffer' + * @return NULL on error + */ +struct GNUNET_CRYPTO_EccPrivateKey * +GNUNET_CRYPTO_ecc_decode_key (const char *buf, + size_t len); + + +/** + * Create a new private key by reading it from a file. If the + * files does not exist, create a new key and write it to the + * file. Caller must free return value. Note that this function + * can not guarantee that another process might not be trying + * the same operation on the same file at the same time. + * If the contents of the file + * are invalid the old file is deleted and a fresh key is + * created. + * + * @return new private key, NULL on error (for example, + * permission denied) + */ +struct GNUNET_CRYPTO_EccPrivateKey * +GNUNET_CRYPTO_ecc_key_create_from_file (const char *filename); + + +/** + * Handle to cancel private key generation and state for the + * key generation operation. + */ +struct GNUNET_CRYPTO_EccKeyGenerationContext; + +/** + * Create a new private key. Caller must free return value. Blocking version + * (blocks to gather entropy). + * + * @return fresh private key + */ +struct GNUNET_CRYPTO_EccPrivateKey * +GNUNET_CRYPTO_ecc_key_create (void); + + +/** + * Create a new private key by reading it from a file. If the files + * does not exist, create a new key and write it to the file. If the + * contents of the file are invalid the old file is deleted and a + * fresh key is created. + * + * @param filename name of file to use for storage + * @param cont function to call when done (or on errors) + * @param cont_cls closure for 'cont' + * @return handle to abort operation, NULL on fatal errors (cont will not be called if NULL is returned) + */ +struct GNUNET_CRYPTO_EccKeyGenerationContext * +GNUNET_CRYPTO_ecc_key_create_start (const char *filename, + GNUNET_CRYPTO_EccKeyCallback cont, + void *cont_cls); + + +/** + * Abort ECC key generation. + * + * @param gc key generation context to abort + */ +void +GNUNET_CRYPTO_ecc_key_create_stop (struct GNUNET_CRYPTO_EccKeyGenerationContext *gc); + +/** + * Setup a hostkey file for a peer given the name of the + * configuration file (!). This function is used so that + * at a later point code can be certain that reading a + * hostkey is fast (for example in time-dependent testcases). + * + * @param cfg_name name of the configuration file to use + */ +void +GNUNET_CRYPTO_ecc_setup_hostkey (const char *cfg_name); + + +/** + * Derive key material from a public and a private ECC key. + * + * @param key private key to use for the ECDH (x) + * @param pub public key to use for the ECDY (yG) + * @param key_material where to write the key material (xyG) + * @return GNUNET_SYSERR on error, GNUNET_OK on success + */ +int +GNUNET_CRYPTO_ecc_ecdh (const struct GNUNET_CRYPTO_EccPrivateKey *key, + const struct GNUNET_CRYPTO_EccPublicKeyBinaryEncoded *pub, + struct GNUNET_HashCode *key_material); + + +/** + * Sign a given block. + * + * @param key private key to use for the signing + * @param purpose what to sign (size, purpose) + * @param sig where to write the signature + * @return GNUNET_SYSERR on error, GNUNET_OK on success + */ +int +GNUNET_CRYPTO_ecc_sign (const struct GNUNET_CRYPTO_EccPrivateKey *key, + const struct GNUNET_CRYPTO_EccSignaturePurpose *purpose, + struct GNUNET_CRYPTO_EccSignature *sig); + + +/** + * Verify signature. + * + * @param purpose what is the purpose that the signature should have? + * @param validate block to validate (size, purpose, data) + * @param sig signature that is being validated + * @param publicKey public key of the signer + * @returns GNUNET_OK if ok, GNUNET_SYSERR if invalid + */ +int +GNUNET_CRYPTO_ecc_verify (uint32_t purpose, + const struct GNUNET_CRYPTO_EccSignaturePurpose + *validate, + const struct GNUNET_CRYPTO_EccSignature *sig, + const struct GNUNET_CRYPTO_EccPublicKeyBinaryEncoded + *publicKey); + + /** * This function should only be called in testcases * where strong entropy gathering is not desired @@ -1048,6 +1366,17 @@ void GNUNET_CRYPTO_random_disable_entropy_gathering (void); +/** + * Check if we are using weak random number generation. + * + * @return GNUNET_YES if weak number generation is on + * (thus will return YES if 'GNUNET_CRYPTO_random_disable_entropy_gathering' + * was called previously). + */ +int +GNUNET_CRYPTO_random_is_weak (void); + + #if 0 /* keep Emacsens' auto-indent happy */ { #endif diff --git a/src/include/gnunet_datacache_lib.h b/src/include/gnunet_datacache_lib.h index 84cb4d6..4f97ee5 100644 --- a/src/include/gnunet_datacache_lib.h +++ b/src/include/gnunet_datacache_lib.h @@ -74,18 +74,22 @@ GNUNET_DATACACHE_destroy (struct GNUNET_DATACACHE_Handle *h); * An iterator over a set of items stored in the datacache. * * @param cls closure - * @param exp when will the content expire? * @param key key for the content * @param size number of bytes in data * @param data content stored * @param type type of the content + * @param exp when will the content expire? + * @param path_info_len number of entries in 'path_info' + * @param path_info a path through the network * @return GNUNET_OK to continue iterating, GNUNET_SYSERR to abort */ typedef int (*GNUNET_DATACACHE_Iterator) (void *cls, - struct GNUNET_TIME_Absolute exp, - const GNUNET_HashCode * key, + const struct GNUNET_HashCode *key, size_t size, const char *data, - enum GNUNET_BLOCK_Type type); + enum GNUNET_BLOCK_Type type, + struct GNUNET_TIME_Absolute exp, + unsigned int path_info_len, + const struct GNUNET_PeerIdentity *path_info); /** @@ -97,13 +101,17 @@ typedef int (*GNUNET_DATACACHE_Iterator) (void *cls, * @param data data to store * @param type type of the value * @param discard_time when to discard the value in any case - * @return GNUNET_OK on success, GNUNET_SYSERR on error (full, etc.) + * @param path_info_len number of entries in 'path_info' + * @param path_info a path through the network + * @return GNUNET_OK on success, GNUNET_SYSERR on error, GNUNET_NO if duplicate */ int GNUNET_DATACACHE_put (struct GNUNET_DATACACHE_Handle *h, - const GNUNET_HashCode * key, size_t size, + const struct GNUNET_HashCode * key, size_t size, const char *data, enum GNUNET_BLOCK_Type type, - struct GNUNET_TIME_Absolute discard_time); + struct GNUNET_TIME_Absolute discard_time, + unsigned int path_info_len, + const struct GNUNET_PeerIdentity *path_info); /** @@ -119,7 +127,7 @@ GNUNET_DATACACHE_put (struct GNUNET_DATACACHE_Handle *h, */ unsigned int GNUNET_DATACACHE_get (struct GNUNET_DATACACHE_Handle *h, - const GNUNET_HashCode * key, enum GNUNET_BLOCK_Type type, + const struct GNUNET_HashCode * key, enum GNUNET_BLOCK_Type type, GNUNET_DATACACHE_Iterator iter, void *iter_cls); diff --git a/src/include/gnunet_datacache_plugin.h b/src/include/gnunet_datacache_plugin.h index fbfcdf1..2e07501 100644 --- a/src/include/gnunet_datacache_plugin.h +++ b/src/include/gnunet_datacache_plugin.h @@ -46,7 +46,7 @@ extern "C" * @param size number of bytes that were made available */ typedef void (*GNUNET_DATACACHE_DeleteNotifyCallback) (void *cls, - const GNUNET_HashCode * + const struct GNUNET_HashCode * key, size_t size); @@ -107,11 +107,15 @@ struct GNUNET_DATACACHE_PluginFunctions * @param data data to store * @param type type of the value * @param discard_time when to discard the value in any case - * @return 0 on error, number of bytes used otherwise + * @param path_info_len number of entries in 'path_info' + * @param path_info a path through the network + * @return 0 if duplicate, -1 on error, number of bytes used otherwise */ - size_t (*put) (void *cls, const GNUNET_HashCode * key, size_t size, - const char *data, enum GNUNET_BLOCK_Type type, - struct GNUNET_TIME_Absolute discard_time); + ssize_t (*put) (void *cls, const struct GNUNET_HashCode * key, size_t size, + const char *data, enum GNUNET_BLOCK_Type type, + struct GNUNET_TIME_Absolute discard_time, + unsigned int path_info_len, + const struct GNUNET_PeerIdentity *path_info); /** @@ -125,7 +129,7 @@ struct GNUNET_DATACACHE_PluginFunctions * @param iter_cls closure for iter * @return the number of results found */ - unsigned int (*get) (void *cls, const GNUNET_HashCode * key, + unsigned int (*get) (void *cls, const struct GNUNET_HashCode * key, enum GNUNET_BLOCK_Type type, GNUNET_DATACACHE_Iterator iter, void *iter_cls); diff --git a/src/include/gnunet_datastore_plugin.h b/src/include/gnunet_datastore_plugin.h index bbf0ce2..991abb7 100644 --- a/src/include/gnunet_datastore_plugin.h +++ b/src/include/gnunet_datastore_plugin.h @@ -92,7 +92,7 @@ struct GNUNET_DATASTORE_PluginEnvironment * @return GNUNET_OK to keep the item * GNUNET_NO to delete the item */ -typedef int (*PluginDatumProcessor) (void *cls, const GNUNET_HashCode * key, +typedef int (*PluginDatumProcessor) (void *cls, const struct GNUNET_HashCode * key, uint32_t size, const void *data, enum GNUNET_BLOCK_Type type, uint32_t priority, uint32_t anonymity, @@ -127,7 +127,7 @@ typedef unsigned long long (*PluginEstimateSize) (void *cls); * @return GNUNET_OK on success, * GNUNET_SYSERR on failure */ -typedef int (*PluginPut) (void *cls, const GNUNET_HashCode * key, uint32_t size, +typedef int (*PluginPut) (void *cls, const struct GNUNET_HashCode * key, uint32_t size, const void *data, enum GNUNET_BLOCK_Type type, uint32_t priority, uint32_t anonymity, uint32_t replication, @@ -142,7 +142,7 @@ typedef int (*PluginPut) (void *cls, const GNUNET_HashCode * key, uint32_t size, * @param count how many values are stored under this key in the datastore */ typedef void (*PluginKeyProcessor) (void *cls, - const GNUNET_HashCode *key, + const struct GNUNET_HashCode *key, unsigned int count); @@ -178,8 +178,8 @@ typedef void (*PluginGetKeys) (void *cls, * @param proc_cls closure for proc */ typedef void (*PluginGetKey) (void *cls, uint64_t offset, - const GNUNET_HashCode * key, - const GNUNET_HashCode * vhash, + const struct GNUNET_HashCode * key, + const struct GNUNET_HashCode * vhash, enum GNUNET_BLOCK_Type type, PluginDatumProcessor proc, void *proc_cls); @@ -208,9 +208,6 @@ typedef void (*PluginGetRandom) (void *cls, PluginDatumProcessor proc, * priority should be added to the existing priority, ignoring the * priority in value. * - * Note that it is possible for multiple values to match this put. - * In that case, all of the respective values are updated. - * * @param cls closure * @param uid unique identifier of the datum * @param delta by how much should the priority diff --git a/src/include/gnunet_datastore_service.h b/src/include/gnunet_datastore_service.h index 2950832..721963b 100644 --- a/src/include/gnunet_datastore_service.h +++ b/src/include/gnunet_datastore_service.h @@ -153,7 +153,7 @@ GNUNET_DATASTORE_reserve (struct GNUNET_DATASTORE_Handle *h, uint64_t amount, */ struct GNUNET_DATASTORE_QueueEntry * GNUNET_DATASTORE_put (struct GNUNET_DATASTORE_Handle *h, uint32_t rid, - const GNUNET_HashCode * key, size_t size, + const struct GNUNET_HashCode * key, size_t size, const void *data, enum GNUNET_BLOCK_Type type, uint32_t priority, uint32_t anonymity, uint32_t replication, @@ -245,7 +245,7 @@ GNUNET_DATASTORE_update (struct GNUNET_DATASTORE_Handle *h, uint64_t uid, */ struct GNUNET_DATASTORE_QueueEntry * GNUNET_DATASTORE_remove (struct GNUNET_DATASTORE_Handle *h, - const GNUNET_HashCode * key, size_t size, + const struct GNUNET_HashCode * key, size_t size, const void *data, unsigned int queue_priority, unsigned int max_queue_size, struct GNUNET_TIME_Relative timeout, @@ -268,7 +268,7 @@ GNUNET_DATASTORE_remove (struct GNUNET_DATASTORE_Handle *h, * maybe 0 if no unique identifier is available */ typedef void (*GNUNET_DATASTORE_DatumProcessor) (void *cls, - const GNUNET_HashCode * key, + const struct GNUNET_HashCode * key, size_t size, const void *data, enum GNUNET_BLOCK_Type type, uint32_t priority, @@ -300,7 +300,7 @@ typedef void (*GNUNET_DATASTORE_DatumProcessor) (void *cls, */ struct GNUNET_DATASTORE_QueueEntry * GNUNET_DATASTORE_get_key (struct GNUNET_DATASTORE_Handle *h, uint64_t offset, - const GNUNET_HashCode * key, + const struct GNUNET_HashCode * key, enum GNUNET_BLOCK_Type type, unsigned int queue_priority, unsigned int max_queue_size, diff --git a/src/include/gnunet_dht_service.h b/src/include/gnunet_dht_service.h index 6606acb..0de7551 100644 --- a/src/include/gnunet_dht_service.h +++ b/src/include/gnunet_dht_service.h @@ -163,10 +163,12 @@ typedef void (*GNUNET_DHT_PutContinuation)(void *cls, * (size too big) */ struct GNUNET_DHT_PutHandle * -GNUNET_DHT_put (struct GNUNET_DHT_Handle *handle, const GNUNET_HashCode * key, +GNUNET_DHT_put (struct GNUNET_DHT_Handle *handle, + const struct GNUNET_HashCode * key, uint32_t desired_replication_level, enum GNUNET_DHT_RouteOption options, - enum GNUNET_BLOCK_Type type, size_t size, const char *data, + enum GNUNET_BLOCK_Type type, + size_t size, const void *data, struct GNUNET_TIME_Absolute exp, struct GNUNET_TIME_Relative timeout, GNUNET_DHT_PutContinuation cont, @@ -205,7 +207,7 @@ GNUNET_DHT_put_cancel (struct GNUNET_DHT_PutHandle *ph); */ typedef void (*GNUNET_DHT_GetIterator) (void *cls, struct GNUNET_TIME_Absolute exp, - const GNUNET_HashCode * key, + const struct GNUNET_HashCode * key, const struct GNUNET_PeerIdentity * get_path, unsigned int get_path_length, const struct GNUNET_PeerIdentity * @@ -234,13 +236,29 @@ typedef void (*GNUNET_DHT_GetIterator) (void *cls, */ struct GNUNET_DHT_GetHandle * GNUNET_DHT_get_start (struct GNUNET_DHT_Handle *handle, - enum GNUNET_BLOCK_Type type, const GNUNET_HashCode * key, + enum GNUNET_BLOCK_Type type, + const struct GNUNET_HashCode *key, uint32_t desired_replication_level, - enum GNUNET_DHT_RouteOption options, const void *xquery, - size_t xquery_size, GNUNET_DHT_GetIterator iter, - void *iter_cls); + enum GNUNET_DHT_RouteOption options, + const void *xquery, size_t xquery_size, + GNUNET_DHT_GetIterator iter, void *iter_cls); +/** + * Tell the DHT not to return any of the following known results + * to this client. + * + * @param get_handle get operation for which results should be filtered + * @param num_results number of results to be blocked that are + * provided in this call (size of the 'results' array) + * @param results array of hash codes over the 'data' of the results + * to be blocked + */ +void +GNUNET_DHT_get_filter_known_results (struct GNUNET_DHT_GetHandle *get_handle, + unsigned int num_results, + const struct GNUNET_HashCode *results); + /** * Stop async DHT-get. Frees associated resources. * @@ -279,7 +297,7 @@ typedef void (*GNUNET_DHT_MonitorGetCB) (void *cls, uint32_t desired_replication_level, unsigned int path_length, const struct GNUNET_PeerIdentity *path, - const GNUNET_HashCode * key); + const struct GNUNET_HashCode * key); /** * Callback called on each GET reply going through the DHT. @@ -304,7 +322,7 @@ typedef void (*GNUNET_DHT_MonitorGetRespCB) (void *cls, * put_path, unsigned int put_path_length, struct GNUNET_TIME_Absolute exp, - const GNUNET_HashCode * key, + const struct GNUNET_HashCode * key, const void *data, size_t size); @@ -331,7 +349,7 @@ typedef void (*GNUNET_DHT_MonitorPutCB) (void *cls, unsigned int path_length, const struct GNUNET_PeerIdentity *path, struct GNUNET_TIME_Absolute exp, - const GNUNET_HashCode * key, + const struct GNUNET_HashCode * key, const void *data, size_t size); @@ -351,7 +369,7 @@ typedef void (*GNUNET_DHT_MonitorPutCB) (void *cls, struct GNUNET_DHT_MonitorHandle * GNUNET_DHT_monitor_start (struct GNUNET_DHT_Handle *handle, enum GNUNET_BLOCK_Type type, - const GNUNET_HashCode *key, + const struct GNUNET_HashCode *key, GNUNET_DHT_MonitorGetCB get_cb, GNUNET_DHT_MonitorGetRespCB get_resp_cb, GNUNET_DHT_MonitorPutCB put_cb, diff --git a/src/include/gnunet_disk_lib.h b/src/include/gnunet_disk_lib.h index d6ec0fe..dd42f9e 100644 --- a/src/include/gnunet_disk_lib.h +++ b/src/include/gnunet_disk_lib.h @@ -1,6 +1,6 @@ /* This file is part of GNUnet. - (C) 2001, 2002, 2003, 2004, 2005, 2006, 2009 Christian Grothoff (and other contributing authors) + (C) 2001-2012 Christian Grothoff (and other contributing authors) GNUnet is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published @@ -17,10 +17,10 @@ Free Software Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */ - /** * @file include/gnunet_disk_lib.h * @brief disk IO apis + * @author Christian Grothoff */ #ifndef GNUNET_DISK_LIB_H #define GNUNET_DISK_LIB_H @@ -36,10 +36,20 @@ */ struct GNUNET_DISK_PipeHandle; - +/** + * Type of a handle. + */ enum GNUNET_FILE_Type { - GNUNET_DISK_FILE, GNUNET_PIPE + /** + * Handle represents a file. + */ + GNUNET_DISK_HANLDE_TYPE_FILE, + + /** + * Handle represents a pipe. + */ + GNUNET_DISK_HANLDE_TYPE_PIPE }; /** @@ -75,8 +85,7 @@ struct GNUNET_DISK_FileHandle */ int fd; -#endif /* - */ +#endif }; @@ -103,39 +112,39 @@ extern "C" enum GNUNET_DISK_OpenFlags { - /** - * Open the file for reading - */ + /** + * Open the file for reading + */ GNUNET_DISK_OPEN_READ = 1, - /** - * Open the file for writing - */ + /** + * Open the file for writing + */ GNUNET_DISK_OPEN_WRITE = 2, - /** - * Open the file for both reading and writing - */ + /** + * Open the file for both reading and writing + */ GNUNET_DISK_OPEN_READWRITE = 3, - /** - * Fail if file already exists - */ + /** + * Fail if file already exists + */ GNUNET_DISK_OPEN_FAILIFEXISTS = 4, - /** - * Truncate file if it exists - */ + /** + * Truncate file if it exists + */ GNUNET_DISK_OPEN_TRUNCATE = 8, - /** - * Create file if it doesn't exist - */ + /** + * Create file if it doesn't exist + */ GNUNET_DISK_OPEN_CREATE = 16, - /** - * Append to the file - */ + /** + * Append to the file + */ GNUNET_DISK_OPEN_APPEND = 32 }; @@ -144,18 +153,19 @@ enum GNUNET_DISK_OpenFlags */ enum GNUNET_DISK_MapType { - /** - * Read-only memory map. - */ + /** + * Read-only memory map. + */ GNUNET_DISK_MAP_TYPE_READ = 1, - - /** - * Write-able memory map. - */ + + /** + * Write-able memory map. + */ GNUNET_DISK_MAP_TYPE_WRITE = 2, - /** - * Read-write memory map. - */ + + /** + * Read-write memory map. + */ GNUNET_DISK_MAP_TYPE_READWRITE = 3 }; @@ -165,77 +175,78 @@ enum GNUNET_DISK_MapType */ enum GNUNET_DISK_AccessPermissions { - /** - * Nobody is allowed to do anything to the file. - */ + /** + * Nobody is allowed to do anything to the file. + */ GNUNET_DISK_PERM_NONE = 0, - /** - * Owner can read. - */ + /** + * Owner can read. + */ GNUNET_DISK_PERM_USER_READ = 1, - /** - * Owner can write. - */ + /** + * Owner can write. + */ GNUNET_DISK_PERM_USER_WRITE = 2, - /** - * Owner can execute. - */ + /** + * Owner can execute. + */ GNUNET_DISK_PERM_USER_EXEC = 4, - /** - * Group can read. - */ + /** + * Group can read. + */ GNUNET_DISK_PERM_GROUP_READ = 8, - /** - * Group can write. - */ + /** + * Group can write. + */ GNUNET_DISK_PERM_GROUP_WRITE = 16, - /** - * Group can execute. - */ + /** + * Group can execute. + */ GNUNET_DISK_PERM_GROUP_EXEC = 32, - /** - * Everybody can read. - */ + /** + * Everybody can read. + */ GNUNET_DISK_PERM_OTHER_READ = 64, - /** - * Everybody can write. - */ + /** + * Everybody can write. + */ GNUNET_DISK_PERM_OTHER_WRITE = 128, - /** - * Everybody can execute. - */ + /** + * Everybody can execute. + */ GNUNET_DISK_PERM_OTHER_EXEC = 256 }; /** - * Constants for specifying how to seek. + * Constants for specifying how to seek. Do not change values or order, + * some of the code depends on the specific numeric values! */ enum GNUNET_DISK_Seek { - /** - * Seek an absolute position (from the start of the file). - */ - GNUNET_DISK_SEEK_SET, - - /** - * Seek a relative position (from the current offset). - */ - GNUNET_DISK_SEEK_CUR, - - /** - * Seek an absolute position from the end of the file. - */ - GNUNET_DISK_SEEK_END + /** + * Seek an absolute position (from the start of the file). + */ + GNUNET_DISK_SEEK_SET = 0, + + /** + * Seek a relative position (from the current offset). + */ + GNUNET_DISK_SEEK_CUR = 1, + + /** + * Seek an absolute position from the end of the file. + */ + GNUNET_DISK_SEEK_END = 2 }; @@ -244,14 +255,14 @@ enum GNUNET_DISK_Seek */ enum GNUNET_DISK_PipeEnd { - /** - * The reading-end of a pipe. - */ + /** + * The reading-end of a pipe. + */ GNUNET_DISK_PIPE_END_READ = 0, - /** - * The writing-end of a pipe. - */ + /** + * The writing-end of a pipe. + */ GNUNET_DISK_PIPE_END_WRITE = 1 }; @@ -289,6 +300,17 @@ int GNUNET_DISK_file_test (const char *fil); +/** + * Move a file out of the way (create a backup) by + * renaming it to "orig.NUM~" where NUM is the smallest + * number that is not used yet. + * + * @param fil name of the file to back up + */ +void +GNUNET_DISK_file_backup (const char *fil); + + /** * Move the read/write pointer in a file * @param h handle of an open file @@ -355,6 +377,19 @@ char * GNUNET_DISK_mktemp (const char *t); +/** + * Create an (empty) temporary directory on disk. If the given name is not an + * absolute path, the current 'TMPDIR' will be prepended. In any case, 6 + * random characters will be appended to the name to create a unique name. + * + * @param t component to use for the name; + * does NOT contain "XXXXXX" or "/tmp/". + * @return NULL on error, otherwise name of freshly created directory + */ +char * +GNUNET_DISK_mkdtemp (const char *t); + + /** * Open a file. Note that the access permissions will only be * used if a new file is created and if the underlying operating @@ -410,6 +445,7 @@ GNUNET_DISK_pipe (int blocking_read, int blocking_write, int inherit_read, int i struct GNUNET_DISK_PipeHandle * GNUNET_DISK_pipe_from_fd (int blocking_read, int blocking_write, int fd[2]); + /** * Closes an interprocess channel * @param p pipe @@ -418,6 +454,7 @@ GNUNET_DISK_pipe_from_fd (int blocking_read, int blocking_write, int fd[2]); int GNUNET_DISK_pipe_close (struct GNUNET_DISK_PipeHandle *p); + /** * Closes one half of an interprocess channel * @@ -450,6 +487,17 @@ const struct GNUNET_DISK_FileHandle * GNUNET_DISK_pipe_handle (const struct GNUNET_DISK_PipeHandle *p, enum GNUNET_DISK_PipeEnd n); + +/** + * Get a handle from a native FD. + * + * @param fd native file descriptor + * @return file handle corresponding to the descriptor + */ +struct GNUNET_DISK_FileHandle * +GNUNET_DISK_get_handle_from_native (FILE *fd); + + /** * Read the contents of a binary file into a buffer. * @param h handle to an open file @@ -461,6 +509,7 @@ ssize_t GNUNET_DISK_file_read (const struct GNUNET_DISK_FileHandle *h, void *result, size_t len); + /** * Read the contents of a binary file into a buffer. * Guarantees not to block (returns GNUNET_SYSERR and sets errno to EAGAIN @@ -473,7 +522,8 @@ GNUNET_DISK_file_read (const struct GNUNET_DISK_FileHandle *h, void *result, */ ssize_t GNUNET_DISK_file_read_non_blocking (const struct GNUNET_DISK_FileHandle * h, - void *result, size_t len); + void *result, size_t len); + /** * Read the contents of a binary file into a buffer. @@ -624,28 +674,30 @@ GNUNET_DISK_directory_create_for_file (const char *filename); /** - * Test if "fil" is a directory that can be accessed. - * Will not print an error message if the directory - * does not exist. Will log errors if GNUNET_SYSERR is - * returned. + * Test if "fil" is a directory and listable. Optionally, also check if the + * directory is readable. Will not print an error message if the directory does + * not exist. Will log errors if GNUNET_SYSERR is returned (i.e., a file exists + * with the same name). * * @param fil filename to test - * @return GNUNET_YES if yes, GNUNET_NO if does not exist, GNUNET_SYSERR - * on any error and if exists but not directory + * @param is_readable GNUNET_YES to additionally check if "fil" is readable; + * GNUNET_NO to disable this check + * @return GNUNET_YES if yes, GNUNET_NO if not; GNUNET_SYSERR if it + * does not exist or stat'ed */ int -GNUNET_DISK_directory_test (const char *fil); +GNUNET_DISK_directory_test (const char *fil, int is_readable); /** * Remove all files in a directory (rm -rf). Call with * caution. * - * @param fileName the file to remove + * @param filename the file to remove * @return GNUNET_OK on success, GNUNET_SYSERR on error */ int -GNUNET_DISK_directory_remove (const char *fileName); +GNUNET_DISK_directory_remove (const char *filename); /** diff --git a/src/include/gnunet_dnsparser_lib.h b/src/include/gnunet_dnsparser_lib.h index 28cc4c0..daeb420 100644 --- a/src/include/gnunet_dnsparser_lib.h +++ b/src/include/gnunet_dnsparser_lib.h @@ -30,6 +30,17 @@ #include "platform.h" #include "gnunet_common.h" +/** + * Maximum length of a label in DNS. + */ +#define GNUNET_DNSPARSER_MAX_LABEL_LENGTH 63 + +/** + * Maximum length of a name in DNS. + */ +#define GNUNET_DNSPARSER_MAX_NAME_LENGTH 253 + + /** * A few common DNS types. */ @@ -41,6 +52,8 @@ #define GNUNET_DNSPARSER_TYPE_MX 15 #define GNUNET_DNSPARSER_TYPE_TXT 16 #define GNUNET_DNSPARSER_TYPE_AAAA 28 +#define GNUNET_DNSPARSER_TYPE_SRV 33 +#define GNUNET_DNSPARSER_TYPE_TLSA 52 /** * A few common DNS classes (ok, only one is common, but I list a @@ -78,6 +91,7 @@ */ struct GNUNET_DNSPARSER_Flags { +#if __BYTE_ORDER == __LITTLE_ENDIAN /** * Set to 1 if recursion is desired (client -> server) */ @@ -127,6 +141,61 @@ struct GNUNET_DNSPARSER_Flags * Set to 1 if recursion is available (server -> client) */ unsigned int recursion_available : 1 GNUNET_PACKED; +#elif __BYTE_ORDER == __BIG_ENDIAN + + /** + * query:0, response:1 + */ + unsigned int query_or_response : 1 GNUNET_PACKED; + + /** + * See GNUNET_DNSPARSER_OPCODE_ defines. + */ + unsigned int opcode : 4 GNUNET_PACKED; + + /** + * Set to 1 if this is an authoritative answer + */ + unsigned int authoritative_answer : 1 GNUNET_PACKED; + + /** + * Set to 1 if message is truncated + */ + unsigned int message_truncated : 1 GNUNET_PACKED; + + /** + * Set to 1 if recursion is desired (client -> server) + */ + unsigned int recursion_desired : 1 GNUNET_PACKED; + + + /** + * Set to 1 if recursion is available (server -> client) + */ + unsigned int recursion_available : 1 GNUNET_PACKED; + + /** + * Always zero. + */ + unsigned int zero : 1 GNUNET_PACKED; + + /** + * Response has been cryptographically verified, RFC 4035. + */ + unsigned int authenticated_data : 1 GNUNET_PACKED; + + /** + * See RFC 4035. + */ + unsigned int checking_disabled : 1 GNUNET_PACKED; + + /** + * See GNUNET_DNSPARSER_RETURN_CODE_ defines. + */ + unsigned int return_code : 4 GNUNET_PACKED; +#else + #error byteorder undefined +#endif } GNUNET_GCC_STRUCT_LAYOUT; @@ -139,6 +208,10 @@ struct GNUNET_DNSPARSER_Query /** * Name of the record that the query is for (0-terminated). + * In UTF-8 format. The library will convert from and to DNS-IDNA + * as necessary. Use 'GNUNET_DNSPARSER_check_label' to test if an + * individual label is well-formed. If a given name is not well-formed, + * creating the DNS packet will fail. */ char *name; @@ -168,11 +241,85 @@ struct GNUNET_DNSPARSER_MxRecord /** * Name of the mail server. + * In UTF-8 format. The library will convert from and to DNS-IDNA + * as necessary. Use 'GNUNET_DNSPARSER_check_label' to test if an + * individual label is well-formed. If a given name is not well-formed, + * creating the DNS packet will fail. */ char *mxhost; }; + +/** + * Information from SRV records (RFC 2782). The 'service', 'proto' + * and 'domain_name' fields together give the DNS-name which for SRV + * records is of the form "_$SERVICE._$PROTO.$DOMAIN_NAME". The DNS + * parser provides the full name in 'struct DNSPARSER_Record' and the + * individual components in the respective fields of this struct. + * When serializing, you CAN set the 'name' field of 'struct + * GNUNET_DNSPARSER_Record' to NULL, in which case the DNSPARSER code + * will populate 'name' from the 'service', 'proto' and 'domain_name' + * fields in this struct. + */ +struct GNUNET_DNSPARSER_SrvRecord +{ + + /** + * Service name without the underscore (!). Note that RFC 6335 clarifies the + * set of legal characters for service names. + * In UTF-8 format. The library will convert from and to DNS-IDNA + * as necessary. Use 'GNUNET_DNSPARSER_check_label' to test if an + * individual label is well-formed. If a given name is not well-formed, + * creating the DNS packet will fail. + */ + char *service; + + /** + * Transport protocol (typcially "tcp" or "udp", but others might be allowed). + * Without the underscore (!). + */ + char *proto; + + /** + * Domain name for which the record is valid + * In UTF-8 format. The library will convert from and to DNS-IDNA + * as necessary. Use 'GNUNET_DNSPARSER_check_label' to test if an + * individual label is well-formed. If a given name is not well-formed, + * creating the DNS packet will fail. + */ + char *domain_name; + + /** + * Hostname offering the service. + * In UTF-8 format. The library will convert from and to DNS-IDNA + * as necessary. Use 'GNUNET_DNSPARSER_check_label' to test if an + * individual label is well-formed. If a given name is not well-formed, + * creating the DNS packet will fail. + */ + char *target; + + /** + * Preference for this entry (lower value is higher preference). Clients + * will contact hosts from the lowest-priority group first and fall back + * to higher priorities if the low-priority entries are unavailable. + */ + uint16_t priority; + + /** + * Relative weight for records with the same priority. Clients will use + * the hosts of the same (lowest) priority with a probability proportional + * to the weight given. + */ + uint16_t weight; + + /** + * TCP or UDP port of the service. + */ + uint16_t port; + +}; + /** * Information from SOA records (RFC 1035). @@ -183,12 +330,20 @@ struct GNUNET_DNSPARSER_SoaRecord /** *The domainname of the name server that was the * original or primary source of data for this zone. + * In UTF-8 format. The library will convert from and to DNS-IDNA + * as necessary. Use 'GNUNET_DNSPARSER_check_label' to test if an + * individual label is well-formed. If a given name is not well-formed, + * creating the DNS packet will fail. */ char *mname; /** * A domainname which specifies the mailbox of the * person responsible for this zone. + * In UTF-8 format. The library will convert from and to DNS-IDNA + * as necessary. Use 'GNUNET_DNSPARSER_check_label' to test if an + * individual label is well-formed. If a given name is not well-formed, + * creating the DNS packet will fail. */ char *rname; @@ -249,14 +404,25 @@ struct GNUNET_DNSPARSER_Record /** * Name of the record that the query is for (0-terminated). + * In UTF-8 format. The library will convert from and to DNS-IDNA + * as necessary. Use 'GNUNET_DNSPARSER_check_label' to test if an + * individual label is well-formed. If a given name is not well-formed, + * creating the DNS packet will fail. */ char *name; + /** + * Payload of the record (which one of these is valid depends on the 'type'). + */ union { /** * For NS, CNAME and PTR records, this is the uncompressed 0-terminated hostname. + * In UTF-8 format. The library will convert from and to DNS-IDNA + * as necessary. Use 'GNUNET_DNSPARSER_check_label' to test if an + * individual label is well-formed. If a given name is not well-formed, + * creating the DNS packet will fail. */ char *hostname; @@ -270,6 +436,11 @@ struct GNUNET_DNSPARSER_Record */ struct GNUNET_DNSPARSER_MxRecord *mx; + /** + * SRV data for SRV records. + */ + struct GNUNET_DNSPARSER_SrvRecord *srv; + /** * Raw data for all other types. */ @@ -354,6 +525,31 @@ struct GNUNET_DNSPARSER_Packet }; +/** + * Check if a label in UTF-8 format can be coded into valid IDNA. + * This can fail if the ASCII-conversion becomes longer than 63 characters. + * + * @param label label to check (UTF-8 string) + * @return GNUNET_OK if the label can be converted to IDNA, + * GNUNET_SYSERR if the label is not valid for DNS names + */ +int +GNUNET_DNSPARSER_check_label (const char *label); + + +/** + * Check if a hostname in UTF-8 format can be coded into valid IDNA. + * This can fail if a label becomes longer than 63 characters or if + * the entire name exceeds 253 characters. + * + * @param name name to check (UTF-8 string) + * @return GNUNET_OK if the label can be converted to IDNA, + * GNUNET_SYSERR if the label is not valid for DNS names + */ +int +GNUNET_DNSPARSER_check_name (const char *name); + + /** * Parse a UDP payload of a DNS packet in to a nice struct for further * processing and manipulation. diff --git a/src/include/gnunet_dnsstub_lib.h b/src/include/gnunet_dnsstub_lib.h new file mode 100644 index 0000000..0269fac --- /dev/null +++ b/src/include/gnunet_dnsstub_lib.h @@ -0,0 +1,124 @@ +/* + This file is part of GNUnet + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. + */ + +/** + * @file include/gnunet_dnsstub_lib.h + * @brief API for helper library to send DNS requests to DNS resolver + * @author Christian Grothoff + */ +#ifndef GNUNET_DNSSTUB_LIB_H +#define GNUNET_DNSSTUB_LIB_H + +#include "gnunet_common.h" +#include "gnunet_tun_lib.h" + +/** + * Opaque handle to the stub resolver. + */ +struct GNUNET_DNSSTUB_Context; + +/** + * Opaque handle to a socket doing UDP requests. + */ +struct GNUNET_DNSSTUB_RequestSocket; + + +/** + * Start a DNS stub resolver. + * + * @param dns_ip target IP address to use + * @return NULL on error + */ +struct GNUNET_DNSSTUB_Context * +GNUNET_DNSSTUB_start (const char *dns_ip); + + +/** + * Cleanup DNSSTUB resolver. + * + * @param ctx stub resolver to clean up + */ +void +GNUNET_DNSSTUB_stop (struct GNUNET_DNSSTUB_Context *ctx); + + +/** + * Function called with the result of a DNS resolution. + * + * @param cls closure + * @param rs socket that received the response + * @param dns dns response, never NULL + * @param dns_len number of bytes in 'dns' + */ +typedef void (*GNUNET_DNSSTUB_ResultCallback)(void *cls, + struct GNUNET_DNSSTUB_RequestSocket *rs, + const struct GNUNET_TUN_DnsHeader *dns, + size_t dns_len); + + +/** + * Perform DNS resolution using given address. + * + * @param ctx stub resolver to use + * @param sa the socket address + * @param sa_len the socket length + * @param request DNS request to transmit + * @param request_len number of bytes in msg + * @param rc function to call with result + * @param rc_cls closure for 'rc' + * @return socket used for the request, NULL on error + */ +struct GNUNET_DNSSTUB_RequestSocket * +GNUNET_DNSSTUB_resolve (struct GNUNET_DNSSTUB_Context *ctx, + const struct sockaddr *sa, + socklen_t sa_len, + const void *request, + size_t request_len, + GNUNET_DNSSTUB_ResultCallback rc, + void *rc_cls); + + +/** + * Perform DNS resolution using our default IP from init. + * + * @param ctx stub resolver to use + * @param request DNS request to transmit + * @param request_len number of bytes in msg + * @param rc function to call with result + * @param rc_cls closure for 'rc' + * @return socket used for the request, NULL on error + */ +struct GNUNET_DNSSTUB_RequestSocket * +GNUNET_DNSSTUB_resolve2 (struct GNUNET_DNSSTUB_Context *ctx, + const void *request, + size_t request_len, + GNUNET_DNSSTUB_ResultCallback rc, + void *rc_cls); + + +/** + * Cancel DNS resolution. + * + * @param rs resolution to cancel + */ +void +GNUNET_DNSSTUB_resolve_cancel (struct GNUNET_DNSSTUB_RequestSocket *rs); + +#endif diff --git a/src/include/gnunet_fragmentation_lib.h b/src/include/gnunet_fragmentation_lib.h index a953bd2..b022018 100644 --- a/src/include/gnunet_fragmentation_lib.h +++ b/src/include/gnunet_fragmentation_lib.h @@ -73,7 +73,9 @@ typedef void (*GNUNET_FRAGMENT_MessageProcessor) (void *cls, * @param stats statistics context * @param mtu the maximum message size for each fragment * @param tracker bandwidth tracker to use for flow control (can be NULL) - * @param delay expected delay between fragment transmission + * @param msg_delay initial delay to insert between fragment transmissions + * based on previous messages + * @param ack_delay expected delay between fragment transmission * and ACK based on previous messages * @param msg the message to fragment * @param proc function to call for each fragment to transmit @@ -84,7 +86,8 @@ struct GNUNET_FRAGMENT_Context * GNUNET_FRAGMENT_context_create (struct GNUNET_STATISTICS_Handle *stats, uint16_t mtu, struct GNUNET_BANDWIDTH_Tracker *tracker, - struct GNUNET_TIME_Relative delay, + struct GNUNET_TIME_Relative msg_delay, + struct GNUNET_TIME_Relative ack_delay, const struct GNUNET_MessageHeader *msg, GNUNET_FRAGMENT_MessageProcessor proc, void *proc_cls); @@ -122,11 +125,15 @@ GNUNET_FRAGMENT_process_ack (struct GNUNET_FRAGMENT_Context *fc, * resources). * * @param fc fragmentation context - * @return average delay between transmission and ACK for the - * last message, FOREVER if the message was not fully transmitted + * @param msg_delay where to store average delay between individual message transmissions the + * last message (OUT only) + * @param ack_delay where to store average delay between transmission and ACK for the + * last message, set to FOREVER if the message was not fully transmitted (OUT only) */ -struct GNUNET_TIME_Relative -GNUNET_FRAGMENT_context_destroy (struct GNUNET_FRAGMENT_Context *fc); +void +GNUNET_FRAGMENT_context_destroy (struct GNUNET_FRAGMENT_Context *fc, + struct GNUNET_TIME_Relative *msg_delay, + struct GNUNET_TIME_Relative *ack_delay); /** diff --git a/src/include/gnunet_fs_service.h b/src/include/gnunet_fs_service.h index 1f1e60f..a806628 100644 --- a/src/include/gnunet_fs_service.h +++ b/src/include/gnunet_fs_service.h @@ -55,7 +55,7 @@ extern "C" * 9.0.0: CPS-style integrated API * 9.1.1: asynchronous directory scanning */ -#define GNUNET_FS_VERSION 0x00090102 +#define GNUNET_FS_VERSION 0x00090103 /* ******************** URI API *********************** */ @@ -67,6 +67,12 @@ extern "C" #define GNUNET_FS_URI_LOC_INFIX "loc/" +/** + * How often do we signal applications that a probe for a particular + * search result is running? (used to visualize probes). + */ +#define GNUNET_FS_PROBE_UPDATE_FREQUENCY GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MILLISECONDS, 250) + /** * A Universal Resource Identifier (URI), opaque. */ @@ -91,7 +97,7 @@ typedef int (*GNUNET_FS_KeywordIterator) (void *cls, const char *keyword, * @param key wherer to store the unique key */ void -GNUNET_FS_uri_to_key (const struct GNUNET_FS_Uri *uri, GNUNET_HashCode * key); +GNUNET_FS_uri_to_key (const struct GNUNET_FS_Uri *uri, struct GNUNET_HashCode * key); /** * Convert a URI to a UTF-8 String. @@ -341,7 +347,7 @@ GNUNET_FS_uri_sks_create (struct GNUNET_FS_Namespace *ns, const char *id, * @return an FS URI for the given namespace and identifier */ struct GNUNET_FS_Uri * -GNUNET_FS_uri_sks_create_from_nsid (GNUNET_HashCode * nsid, const char *id); +GNUNET_FS_uri_sks_create_from_nsid (struct GNUNET_HashCode * nsid, const char *id); /** @@ -354,7 +360,7 @@ GNUNET_FS_uri_sks_create_from_nsid (GNUNET_HashCode * nsid, const char *id); */ int GNUNET_FS_uri_sks_get_namespace (const struct GNUNET_FS_Uri *uri, - GNUNET_HashCode * nsid); + struct GNUNET_HashCode * nsid); /** @@ -1017,6 +1023,12 @@ struct GNUNET_FS_ProgressInfo */ uint64_t data_len; + /** + * How much time passed between us asking for this block and + * actually getting it? GNUNET_TIME_UNIT_FOREVER_REL if unknown. + */ + struct GNUNET_TIME_Relative block_download_duration; + /** * Depth of the given block in the tree; * 0 would be the lowest level (DBLOCKS). @@ -1024,15 +1036,20 @@ struct GNUNET_FS_ProgressInfo unsigned int depth; /** - * How much trust did we offer for downloading this block? + * How much respect did we offer for downloading this block? (estimate, + * because we might have the same request pending for multiple clients, + * and of course because a transmission may have failed at a lower + * layer). */ - unsigned int trust_offered; + uint32_t respect_offered; /** - * How much time passed between us asking for this block and - * actually getting it? GNUNET_TIME_UNIT_FOREVER_REL if unknown. + * How often did we transmit the request? (estimate, + * because we might have the same request pending for multiple clients, + * and of course because a transmission may have failed at a lower + * layer). */ - struct GNUNET_TIME_Relative block_download_duration; + uint32_t num_transmissions; } progress; @@ -1258,6 +1275,11 @@ struct GNUNET_FS_ProgressInfo */ uint32_t applicability_rank; + /** + * How long has the current probe been active? + */ + struct GNUNET_TIME_Relative current_probe_time; + } update; /** @@ -1383,9 +1405,9 @@ struct GNUNET_FS_ProgressInfo /** * Hash-identifier for the namespace. */ - GNUNET_HashCode id; + struct GNUNET_HashCode id; - } namespace; + } ns; } specifics; @@ -1531,8 +1553,7 @@ struct GNUNET_FS_ProgressInfo * field in the GNUNET_FS_ProgressInfo struct. */ typedef void *(*GNUNET_FS_ProgressCallback) (void *cls, - const struct GNUNET_FS_ProgressInfo - * info); + const struct GNUNET_FS_ProgressInfo *info); /** @@ -1559,30 +1580,31 @@ enum GNUNET_FS_Flags GNUNET_FS_FLAGS_DO_PROBES = 2 }; + /** * Options specified in the VARARGs portion of GNUNET_FS_start. */ enum GNUNET_FS_OPTIONS { - /** - * Last option in the VARARG list. - */ + /** + * Last option in the VARARG list. + */ GNUNET_FS_OPTIONS_END = 0, - /** - * Select the desired amount of parallelism (this option should be - * followed by an "unsigned int" giving the desired maximum number - * of parallel downloads). - */ + /** + * Select the desired amount of parallelism (this option should be + * followed by an "unsigned int" giving the desired maximum number + * of parallel downloads). + */ GNUNET_FS_OPTIONS_DOWNLOAD_PARALLELISM = 1, - /** - * Maximum number of requests that should be pending at a given - * point in time (invidivual downloads may go above this, but - * if we are above this threshold, we should not activate any - * additional downloads. - */ + /** + * Maximum number of requests that should be pending at a given + * point in time (invidivual downloads may go above this, but + * if we are above this threshold, we should not activate any + * additional downloads. + */ GNUNET_FS_OPTIONS_REQUEST_PARALLELISM = 2 }; @@ -1983,7 +2005,7 @@ enum GNUNET_FS_PublishOptions * * @param h handle to the file sharing subsystem * @param fi information about the file or directory structure to publish - * @param namespace namespace to publish the file in, NULL for no namespace + * @param ns namespace to publish the file in, NULL for no namespace * @param nid identifier to use for the publishd content in the namespace * (can be NULL, must be NULL if namespace is NULL) * @param nuid update-identifier that will be used for future updates @@ -1994,7 +2016,7 @@ enum GNUNET_FS_PublishOptions struct GNUNET_FS_PublishContext * GNUNET_FS_publish_start (struct GNUNET_FS_Handle *h, struct GNUNET_FS_FileInformation *fi, - struct GNUNET_FS_Namespace *namespace, const char *nid, + struct GNUNET_FS_Namespace *ns, const char *nid, const char *nuid, enum GNUNET_FS_PublishOptions options); @@ -2072,7 +2094,7 @@ struct GNUNET_FS_PublishSksContext; * Publish an SBlock on GNUnet. * * @param h handle to the file sharing subsystem - * @param namespace namespace to publish in + * @param ns namespace to publish in * @param identifier identifier to use * @param update update identifier to use * @param meta metadata to use @@ -2085,7 +2107,7 @@ struct GNUNET_FS_PublishSksContext; */ struct GNUNET_FS_PublishSksContext * GNUNET_FS_publish_sks (struct GNUNET_FS_Handle *h, - struct GNUNET_FS_Namespace *namespace, + struct GNUNET_FS_Namespace *ns, const char *identifier, const char *update, const struct GNUNET_CONTAINER_MetaData *meta, const struct GNUNET_FS_Uri *uri, @@ -2112,7 +2134,7 @@ GNUNET_FS_publish_sks_cancel (struct GNUNET_FS_PublishSksContext *psc); * @return GNUNET_OK to continue iteration, GNUNET_SYSERR to abort */ typedef int (*GNUNET_FS_IndexedFileProcessor) (void *cls, const char *filename, - const GNUNET_HashCode * file_id); + const struct GNUNET_HashCode * file_id); /** @@ -2177,7 +2199,7 @@ struct GNUNET_FS_AdvertisementContext; * * @param h handle to the file sharing subsystem * @param ksk_uri keywords to use for advertisment - * @param namespace handle for the namespace that should be advertised + * @param ns handle for the namespace that should be advertised * @param meta meta-data for the namespace advertisement * @param bo block options * @param rootEntry name of the root of the namespace @@ -2188,7 +2210,7 @@ struct GNUNET_FS_AdvertisementContext; struct GNUNET_FS_AdvertisementContext * GNUNET_FS_namespace_advertise (struct GNUNET_FS_Handle *h, struct GNUNET_FS_Uri *ksk_uri, - struct GNUNET_FS_Namespace *namespace, + struct GNUNET_FS_Namespace *ns, const struct GNUNET_CONTAINER_MetaData *meta, const struct GNUNET_FS_BlockOptions *bo, const char *rootEntry, @@ -2211,7 +2233,7 @@ GNUNET_FS_namespace_advertise_cancel (struct GNUNET_FS_AdvertisementContext *ac) * * @param h handle to the file sharing subsystem * @param name name to use for the namespace - * @return handle to the namespace, NULL on error + * @return handle to the namespace, NULL on error (i.e. invalid filename) */ struct GNUNET_FS_Namespace * GNUNET_FS_namespace_create (struct GNUNET_FS_Handle *h, const char *name); @@ -2232,14 +2254,14 @@ GNUNET_FS_namespace_dup (struct GNUNET_FS_Namespace *ns); * memory) or also to freeze the namespace to prevent further * insertions by anyone. * - * @param namespace handle to the namespace that should be deleted / freed + * @param ns handle to the namespace that should be deleted / freed * @param freeze prevents future insertions; creating a namespace * with the same name again will create a fresh namespace instead * * @return GNUNET_OK on success, GNUNET_SYSERR on error */ int -GNUNET_FS_namespace_delete (struct GNUNET_FS_Namespace *namespace, int freeze); +GNUNET_FS_namespace_delete (struct GNUNET_FS_Namespace *ns, int freeze); /** @@ -2252,7 +2274,7 @@ GNUNET_FS_namespace_delete (struct GNUNET_FS_Namespace *namespace, int freeze); * @param id hash identifier for the namespace */ typedef void (*GNUNET_FS_NamespaceInfoProcessor) (void *cls, const char *name, - const GNUNET_HashCode * id); + const struct GNUNET_HashCode * id); /** @@ -2301,13 +2323,13 @@ typedef void (*GNUNET_FS_IdentifierProcessor) (void *cls, const char *last_id, * cause the library to call "ip" with all children of the node. Note * that cycles within an SCC are possible (including self-loops). * - * @param namespace namespace to inspect for updateable content + * @param ns namespace to inspect for updateable content * @param next_id ID to look for; use NULL to look for SCC roots * @param ip function to call on each updateable identifier * @param ip_cls closure for ip */ void -GNUNET_FS_namespace_list_updateable (struct GNUNET_FS_Namespace *namespace, +GNUNET_FS_namespace_list_updateable (struct GNUNET_FS_Namespace *ns, const char *next_id, GNUNET_FS_IdentifierProcessor ip, void *ip_cls); diff --git a/src/include/gnunet_getopt_lib.h b/src/include/gnunet_getopt_lib.h index 4b1873c..a22b3f3 100644 --- a/src/include/gnunet_getopt_lib.h +++ b/src/include/gnunet_getopt_lib.h @@ -231,6 +231,24 @@ GNUNET_GETOPT_set_ulong (struct GNUNET_GETOPT_CommandLineProcessorContext *ctx, void *scls, const char *option, const char *value); +/** + * Set an option of type 'struct GNUNET_TIME_Relative' from the command line. + * A pointer to this function should be passed as part of the + * 'struct GNUNET_GETOPT_CommandLineOption' array to initialize options + * of this type. It should be followed by a pointer to a value of + * type 'struct GNUNET_TIME_Relative'. + * + * @param ctx command line processing context + * @param scls additional closure (will point to the 'struct GNUNET_TIME_Relative') + * @param option name of the option + * @param value actual value of the option as a string. + * @return GNUNET_OK if parsing the value worked + */ +int +GNUNET_GETOPT_set_relative_time (struct GNUNET_GETOPT_CommandLineProcessorContext *ctx, + void *scls, const char *option, const char *value); + + /** * Set an option of type 'unsigned int' from the command line. * A pointer to this function should be passed as part of the @@ -273,7 +291,7 @@ GNUNET_GETOPT_set_one (struct GNUNET_GETOPT_CommandLineProcessorContext *ctx, * A pointer to this function should be passed as part of the * 'struct GNUNET_GETOPT_CommandLineOption' array to initialize options * of this type. It should be followed by a pointer to a value of - * type 'char *'. + * type 'char *', which will be allocated with the requested string. * * @param ctx command line processing context * @param scls additional closure (will point to the 'char *', @@ -315,7 +333,7 @@ GNUNET_GETOPT_increment_value (struct GNUNET_GETOPT_CommandLineProcessorContext * @param scls additional closure (points to about text) * @param option name of the option * @param value not used (NULL) - * @return GNUNET_SYSERR (do not continue) + * @return GNUNET_NO (do not continue, not an error) */ int GNUNET_GETOPT_format_help_ (struct GNUNET_GETOPT_CommandLineProcessorContext @@ -329,7 +347,7 @@ GNUNET_GETOPT_format_help_ (struct GNUNET_GETOPT_CommandLineProcessorContext * @param scls additional closure (points to version string) * @param option name of the option * @param value not used (NULL) - * @return GNUNET_SYSERR (do not continue) + * @return GNUNET_NO (do not continue, not an error) */ int GNUNET_GETOPT_print_version_ (struct GNUNET_GETOPT_CommandLineProcessorContext diff --git a/src/include/gnunet_gns_service.h b/src/include/gnunet_gns_service.h index 4e040f7..8d2fde3 100644 --- a/src/include/gnunet_gns_service.h +++ b/src/include/gnunet_gns_service.h @@ -22,14 +22,7 @@ * @file include/gnunet_gns_service.h * @brief API to the GNS service * @author Martin Schanzenbach - * - * TODO: - * - decide what goes into storage API and what into GNS-service API - * - decide where to pass/expose/check keys / signatures - * - are GNS private keys per peer or per user? */ - - #ifndef GNUNET_GNS_SERVICE_H #define GNUNET_GNS_SERVICE_H @@ -46,19 +39,31 @@ extern "C" #endif +/** + * String we use to indicate the local master zone or a + * root entry in the current zone. + */ +#define GNUNET_GNS_MASTERZONE_STR "+" + /** * Connection to the GNS service. */ struct GNUNET_GNS_Handle; /** - * Handle to control a get operation. + * Handle to control a lookup operation. + */ +struct GNUNET_GNS_LookupRequest; + +/** + * Handle to control a shorten operation. */ -struct GNUNET_GNS_LookupHandle; +struct GNUNET_GNS_ShortenRequest; /** - * Handle to control a shorten operation + * Handle to control a get authority operation */ +struct GNUNET_GNS_GetAuthRequest; /** * Record types @@ -67,21 +72,52 @@ struct GNUNET_GNS_LookupHandle; enum GNUNET_GNS_RecordType { /* Standard DNS */ - GNUNET_GNS_RECORD_TYPE_A = GNUNET_DNSPARSER_TYPE_A, - GNUNET_GNS_RECORD_TYPE_NS = GNUNET_DNSPARSER_TYPE_NS, - GNUNET_GNS_RECORD_TYPE_CNAME = GNUNET_DNSPARSER_TYPE_CNAME, - GNUNET_GNS_RECORD_TYPE_SOA = GNUNET_DNSPARSER_TYPE_SOA, - GNUNET_GNS_RECORD_TYPE_PTR = GNUNET_DNSPARSER_TYPE_PTR, - GNUNET_GNS_RECORD_MX = GNUNET_DNSPARSER_TYPE_MX, - GNUNET_GNS_RECORD_TXT = GNUNET_DNSPARSER_TYPE_TXT, - GNUNET_GNS_RECORD_AAAA = GNUNET_DNSPARSER_TYPE_AAAA, + /* struct in_addr */ + GNUNET_GNS_RECORD_A = GNUNET_DNSPARSER_TYPE_A, + + /* char */ + GNUNET_GNS_RECORD_NS = GNUNET_DNSPARSER_TYPE_NS, + + /* char */ + GNUNET_GNS_RECORD_CNAME = GNUNET_DNSPARSER_TYPE_CNAME, + + /* struct soa_data */ + GNUNET_GNS_RECORD_SOA = GNUNET_DNSPARSER_TYPE_SOA, + + /* struct srv_data */ + GNUNET_GNS_RECORD_SRV = GNUNET_DNSPARSER_TYPE_SRV, + + /* char */ + GNUNET_GNS_RECORD_PTR = GNUNET_DNSPARSER_TYPE_PTR, + + /* uint16_t, char */ + GNUNET_GNS_RECORD_MX = GNUNET_DNSPARSER_TYPE_MX, + + /* char */ + GNUNET_GNS_RECORD_TXT = GNUNET_DNSPARSER_TYPE_TXT, + + /* struct in6_addr */ + GNUNET_GNS_RECORD_AAAA = GNUNET_DNSPARSER_TYPE_AAAA, /* GNS specific */ + /* struct GNUNET_CRYPTO_ShortHashCode */ GNUNET_GNS_RECORD_PKEY = GNUNET_NAMESTORE_TYPE_PKEY, + + /* char */ GNUNET_GNS_RECORD_PSEU = GNUNET_NAMESTORE_TYPE_PSEU, - GNUNET_GNS_RECORD_ANY = GNUNET_NAMESTORE_TYPE_ANY + GNUNET_GNS_RECORD_ANY = GNUNET_NAMESTORE_TYPE_ANY, + + /* char */ + GNUNET_GNS_RECORD_LEHO = GNUNET_NAMESTORE_TYPE_LEHO, + + /* struct vpn_data */ + GNUNET_GNS_RECORD_VPN = GNUNET_NAMESTORE_TYPE_VPN, + + /* revocation */ + GNUNET_GNS_RECORD_REV = GNUNET_NAMESTORE_TYPE_REV }; + /** * Initialize the connection with the GNS service. * @@ -109,13 +145,12 @@ GNUNET_GNS_disconnect (struct GNUNET_GNS_Handle *handle); * lookup * * @param cls closure - * @param name "name" of the original lookup * @param rd_count number of records * @param rd the records in reply */ typedef void (*GNUNET_GNS_LookupResultProcessor) (void *cls, - uint32_t rd_count, - const struct GNUNET_NAMESTORE_RecordData *rd); + uint32_t rd_count, + const struct GNUNET_NAMESTORE_RecordData *rd); @@ -126,17 +161,22 @@ typedef void (*GNUNET_GNS_LookupResultProcessor) (void *cls, * @param handle handle to the GNS service * @param name the name to look up * @param type the GNUNET_GNS_RecordType to look for + * @param only_cached GNUNET_NO to only check locally not DHT for performance + * @param shorten_key the private key of the shorten zone (can be NULL) * @param proc function to call on result * @param proc_cls closure for processor * * @return handle to the queued request */ -struct GNUNET_GNS_QueueEntry * +struct GNUNET_GNS_LookupRequest* GNUNET_GNS_lookup (struct GNUNET_GNS_Handle *handle, - const char * name, - enum GNUNET_GNS_RecordType type, - GNUNET_GNS_LookupResultProcessor proc, - void *proc_cls); + const char * name, + enum GNUNET_GNS_RecordType type, + int only_cached, + struct GNUNET_CRYPTO_RsaPrivateKey *shorten_key, + GNUNET_GNS_LookupResultProcessor proc, + void *proc_cls); + /** * Perform an asynchronous lookup operation on the GNS @@ -146,18 +186,31 @@ GNUNET_GNS_lookup (struct GNUNET_GNS_Handle *handle, * @param name the name to look up * @param zone the zone to start the resolution in * @param type the GNUNET_GNS_RecordType to look for + * @param only_cached GNUNET_YES to only check locally not DHT for performance + * @param shorten_key the private key of the shorten zone (can be NULL) * @param proc function to call on result * @param proc_cls closure for processor * * @return handle to the queued request */ -struct GNUNET_GNS_QueueEntry * +struct GNUNET_GNS_LookupRequest* GNUNET_GNS_lookup_zone (struct GNUNET_GNS_Handle *handle, - const char * name, - struct GNUNET_CRYPTO_ShortHashCode *zone, - enum GNUNET_GNS_RecordType type, - GNUNET_GNS_LookupResultProcessor proc, - void *proc_cls); + const char * name, + struct GNUNET_CRYPTO_ShortHashCode *zone, + enum GNUNET_GNS_RecordType type, + int only_cached, + struct GNUNET_CRYPTO_RsaPrivateKey *shorten_key, + GNUNET_GNS_LookupResultProcessor proc, + void *proc_cls); + + +/** + * Cancel pending lookup request + * + * @param lr the lookup request to cancel + */ +void +GNUNET_GNS_cancel_lookup_request (struct GNUNET_GNS_LookupRequest *lr); /* *************** Standard API: shorten ******************* */ @@ -167,10 +220,10 @@ GNUNET_GNS_lookup_zone (struct GNUNET_GNS_Handle *handle, * called only once * * @param cls closure - * @param short_name the shortened name or NULL if no result + * @param short_name the shortened name or NULL if no result / error */ typedef void (*GNUNET_GNS_ShortenResultProcessor) (void *cls, - const char* short_name); + const char* short_name); /** @@ -178,13 +231,17 @@ typedef void (*GNUNET_GNS_ShortenResultProcessor) (void *cls, * * @param handle handle to the GNS service * @param name the name to look up + * @param private_zone the public zone of the private zone + * @param shorten_zone the public zone of the shorten zone * @param proc function to call on result * @param proc_cls closure for processor * @return handle to the operation */ -struct GNUNET_GNS_QueueEntry * +struct GNUNET_GNS_ShortenRequest* GNUNET_GNS_shorten (struct GNUNET_GNS_Handle *handle, const char * name, + struct GNUNET_CRYPTO_ShortHashCode *private_zone, + struct GNUNET_CRYPTO_ShortHashCode *shorten_zone, GNUNET_GNS_ShortenResultProcessor proc, void *proc_cls); @@ -194,17 +251,31 @@ GNUNET_GNS_shorten (struct GNUNET_GNS_Handle *handle, * * @param handle handle to the GNS service * @param name the name to look up + * @param private_zone the public zone of the private zone + * @param shorten_zone the public zone of the shorten zone * @param zone the zone to start the resolution in * @param proc function to call on result * @param proc_cls closure for processor * @return handle to the operation */ -struct GNUNET_GNS_QueueEntry * +struct GNUNET_GNS_ShortenRequest* GNUNET_GNS_shorten_zone (struct GNUNET_GNS_Handle *handle, - const char * name, - struct GNUNET_CRYPTO_ShortHashCode *zone, - GNUNET_GNS_ShortenResultProcessor proc, - void *proc_cls); + const char * name, + struct GNUNET_CRYPTO_ShortHashCode *private_zone, + struct GNUNET_CRYPTO_ShortHashCode *shorten_zone, + struct GNUNET_CRYPTO_ShortHashCode *zone, + GNUNET_GNS_ShortenResultProcessor proc, + void *proc_cls); + + +/** + * Cancel pending shorten request + * + * @param sr the lookup request to cancel + */ +void +GNUNET_GNS_cancel_shorten_request (struct GNUNET_GNS_ShortenRequest *sr); + /* *************** Standard API: get authority ******************* */ @@ -217,7 +288,7 @@ GNUNET_GNS_shorten_zone (struct GNUNET_GNS_Handle *handle, * @param auth_name the name of the auhtority or NULL */ typedef void (*GNUNET_GNS_GetAuthResultProcessor) (void *cls, - const char* short_name); + const char* short_name); /** @@ -229,11 +300,20 @@ typedef void (*GNUNET_GNS_GetAuthResultProcessor) (void *cls, * @param proc_cls closure for processor * @return handle to the operation */ -struct GNUNET_GNS_QueueEntry * +struct GNUNET_GNS_GetAuthRequest* GNUNET_GNS_get_authority (struct GNUNET_GNS_Handle *handle, - const char * name, - GNUNET_GNS_GetAuthResultProcessor proc, - void *proc_cls); + const char * name, + GNUNET_GNS_GetAuthResultProcessor proc, + void *proc_cls); + + +/** + * Cancel pending get auth request + * + * @param gar the lookup request to cancel + */ +void +GNUNET_GNS_cancel_get_auth_request (struct GNUNET_GNS_GetAuthRequest *gar); #if 0 /* keep Emacsens' auto-indent happy */ { diff --git a/src/include/gnunet_hello_lib.h b/src/include/gnunet_hello_lib.h index ffddb0b..7be30cf 100644 --- a/src/include/gnunet_hello_lib.h +++ b/src/include/gnunet_hello_lib.h @@ -39,6 +39,12 @@ extern "C" #include "gnunet_crypto_lib.h" +/** + * Prefix that every HELLO URI must start with. + */ +#define GNUNET_HELLO_URI_PREFIX "gnunet://hello/" + + /** * An address for communicating with a peer. We frequently * need this tuple and the components cannot really be @@ -331,6 +337,45 @@ GNUNET_HELLO_get_id (const struct GNUNET_HELLO_Message *hello, struct GNUNET_MessageHeader * GNUNET_HELLO_get_header (struct GNUNET_HELLO_Message *hello); + +typedef struct GNUNET_TRANSPORT_PluginFunctions * +(*GNUNET_HELLO_TransportPluginsFind) (const char *name); + + +/** + * Compose a hello URI string from a hello message. + * + * @param hello Hello message + * @param plugins_find Function to find transport plugins by name + * @return Hello URI string + */ +char * +GNUNET_HELLO_compose_uri (const struct GNUNET_HELLO_Message *hello, + GNUNET_HELLO_TransportPluginsFind plugins_find); + +/** + * Parse a hello URI string to a hello message. + * + * @param uri URI string to parse + * @param pubkey Pointer to struct where public key is parsed + * @param hello Pointer to struct where hello message is parsed + * @param plugins_find Function to find transport plugins by name + * @return GNUNET_OK on success, GNUNET_SYSERR if the URI was invalid, GNUNET_NO on other errors + */ +int +GNUNET_HELLO_parse_uri (const char *uri, + struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *pubkey, + struct GNUNET_HELLO_Message **hello, + GNUNET_HELLO_TransportPluginsFind plugins_find); + +#if 0 /* keep Emacsens' auto-indent happy */ +{ +#endif +#ifdef __cplusplus +} +#endif + + /* ifndef GNUNET_HELLO_LIB_H */ #endif /* end of gnunet_hello_lib.h */ diff --git a/src/include/gnunet_helper_lib.h b/src/include/gnunet_helper_lib.h index 9c1bc21..7f43f1a 100644 --- a/src/include/gnunet_helper_lib.h +++ b/src/include/gnunet_helper_lib.h @@ -24,6 +24,7 @@ * @author Philipp Toelke * @author Christian Grothoff */ + #ifndef GNUNET_HELPER_LIB_H #define GNUNET_HELPER_LIB_H @@ -37,24 +38,41 @@ struct GNUNET_HELPER_Handle; /** - * @brief Starts a helper and begins reading from it + * Callback that will be called when the helper process dies. This is not called + * when the helper process is stoped using GNUNET_HELPER_stop() + * + * @param cls the closure from GNUNET_HELPER_start() + */ +typedef void (*GNUNET_HELPER_ExceptionCallback) (void *cls); + + +/** + * Starts a helper and begins reading from it. The helper process is + * restarted when it dies except when it is stopped using GNUNET_HELPER_stop() + * or when the exp_cb callback is not NULL. * + * @param with_control_pipe does the helper support the use of a control pipe for signalling? * @param binary_name name of the binary to run * @param binary_argv NULL-terminated list of arguments to give when starting the binary (this * argument must not be modified by the client for * the lifetime of the helper handle) * @param cb function to call if we get messages from the helper - * @param cb_cls Closure for the callback + * @param exp_cb the exception callback to call. Set this to NULL if the helper + * process has to be restarted automatically when it dies/crashes + * @param cb_cls closure for the above callbacks * @return the new Handle, NULL on error */ struct GNUNET_HELPER_Handle * -GNUNET_HELPER_start (const char *binary_name, +GNUNET_HELPER_start (int with_control_pipe, + const char *binary_name, char *const binary_argv[], - GNUNET_SERVER_MessageTokenizerCallback cb, void *cb_cls); + GNUNET_SERVER_MessageTokenizerCallback cb, + GNUNET_HELPER_ExceptionCallback exp_cb, + void *cb_cls); /** - * @brief Kills the helper, closes the pipe and frees the handle + * Kills the helper, closes the pipe and frees the handle * * @param h handle to helper to stop */ diff --git a/src/include/gnunet_lockmanager_service.h b/src/include/gnunet_lockmanager_service.h index 570cce5..23d84cd 100644 --- a/src/include/gnunet_lockmanager_service.h +++ b/src/include/gnunet_lockmanager_service.h @@ -92,7 +92,8 @@ enum GNUNET_LOCKMANAGER_Status * @param lock the lock for which this status is relevant * * @param status GNUNET_LOCKMANAGER_SUCCESS if the lock has been successfully - * acquired; GNUNET_LOCKMANAGER_RELEASE when the acquired lock is lost + * acquired; GNUNET_LOCKMANAGER_RELEASE when the acquired lock is + * lost. */ typedef void (*GNUNET_LOCKMANAGER_StatusCallback) (void *cls, @@ -142,8 +143,8 @@ GNUNET_LOCKMANAGER_acquire_lock (struct GNUNET_LOCKMANAGER_Handle *handle, /** * Function to cancel the locking request generated by - * GNUNET_LOCKMANAGER_acquire_lock. If the lock is acquired us then the lock is - * released. GNUNET_LOCKMANAGER_StatusCallback will not be called upon any + * GNUNET_LOCKMANAGER_acquire_lock. If the lock is acquired by us then the lock + * is released. GNUNET_LOCKMANAGER_StatusCallback will not be called upon any * status changes resulting due to this call. * * @param request the LockingRequest to cancel diff --git a/src/include/gnunet_mesh_service.h b/src/include/gnunet_mesh_service.h index 7c2437e..4aa5947 100644 --- a/src/include/gnunet_mesh_service.h +++ b/src/include/gnunet_mesh_service.h @@ -107,6 +107,10 @@ struct GNUNET_MESH_MessageHandler /** * Method called whenever another peer has added us to a tunnel * the other peer initiated. + * Only called (once) upon reception of data with a message type which was + * subscribed to in GNUNET_MESH_connect. A call to GNUNET_MESH_tunnel_destroy + * causes te tunnel to be ignored and no further notifications are sent about + * the same tunnel. * * @param cls closure * @param tunnel new handle to the tunnel @@ -154,9 +158,6 @@ typedef uint32_t GNUNET_MESH_ApplicationType; * Connect to the mesh service. * * @param cfg configuration to use - * @param queue_size size of the data message queue, shared among all tunnels - * (each tunnel is guaranteed to accept at least one message, - * no matter what is the status of other tunnels) * @param cls closure for the various callbacks that follow * (including handlers in the handlers array) * @param new_tunnel function called when an *inbound* tunnel is created @@ -172,8 +173,7 @@ typedef uint32_t GNUNET_MESH_ApplicationType; * (in this case, init is never called) */ struct GNUNET_MESH_Handle * -GNUNET_MESH_connect (const struct GNUNET_CONFIGURATION_Handle *cfg, - unsigned int queue_size, void *cls, +GNUNET_MESH_connect (const struct GNUNET_CONFIGURATION_Handle *cfg, void *cls, GNUNET_MESH_InboundTunnelNotificationHandler new_tunnel, GNUNET_MESH_TunnelEndHandler cleaner, const struct GNUNET_MESH_MessageHandler *handlers, @@ -223,6 +223,29 @@ typedef void (*GNUNET_MESH_PeerConnectHandler) (void *cls, GNUNET_ATS_Information * atsi); +/** + * Announce to ther peer the availability of services described by the regex, + * in order to be reachable to other peers via connect_by_string. + * + * Note that the first GNUNET_REGEX_INITIAL_BYTES characters are considered + * to be part of a prefix, (for instance 'gnunet://'). + * If you put a variable part in there (*, +. ()), all matching strings + * will be stored in the DHT. + * + * @param h Handle to mesh. + * @param regex String with the regular expression describing local services. + * @param compression_characters How many characters can be assigned to one + * edge of the graph. The bigger the variability + * of the data, the smaller this parameter should + * be (down to 1). + * For maximum compression, use strlen (regex) + * or 0 (special value). Use with care! + */ +void +GNUNET_MESH_announce_regex (struct GNUNET_MESH_Handle *h, + const char *regex, + unsigned int compression_characters); + /** * Create a new tunnel (we're initiator and will be allowed to add/remove peers @@ -250,6 +273,37 @@ void GNUNET_MESH_tunnel_destroy (struct GNUNET_MESH_Tunnel *tunnel); +/** + * Request that the tunnel data rate is limited to the speed of the slowest + * receiver. + * + * @param tunnel Tunnel affected. + */ +void +GNUNET_MESH_tunnel_speed_min (struct GNUNET_MESH_Tunnel *tunnel); + + +/** + * Request that the tunnel data rate is limited to the speed of the fastest + * receiver. This is the default behavior. + * + * @param tunnel Tunnel affected. + */ +void +GNUNET_MESH_tunnel_speed_max (struct GNUNET_MESH_Tunnel *tunnel); + + +/** + * Turn on/off the buffering status of the tunnel. + * + * @param tunnel Tunnel affected. + * @param buffer GNUNET_YES to turn buffering on (default), + * GNUNET_NO otherwise. + */ +void +GNUNET_MESH_tunnel_buffer (struct GNUNET_MESH_Tunnel *tunnel, int buffer); + + /** * Request that a peer should be added to the tunnel. The connect handler * will be called when the peer connects @@ -287,6 +341,45 @@ GNUNET_MESH_peer_request_connect_by_type (struct GNUNET_MESH_Tunnel *tunnel, GNUNET_MESH_ApplicationType app_type); +/** + * Request that the mesh should try to connect to a peer matching the + * description given in the service string. + * + * @param tunnel handle to existing tunnel + * @param description string describing the destination node requirements + */ +void +GNUNET_MESH_peer_request_connect_by_string (struct GNUNET_MESH_Tunnel *tunnel, + const char *description); + + +/** + * Request that the given peer isn't added to this tunnel in calls to + * connect_by_* calls, (due to misbehaviour, bad performance, ...). + * + * @param tunnel handle to existing tunnel. + * @param peer peer identity of the peer which should be blacklisted + * for the tunnel. + */ +void +GNUNET_MESH_peer_blacklist (struct GNUNET_MESH_Tunnel *tunnel, + const struct GNUNET_PeerIdentity *peer); + + +/** + * Request that the given peer isn't blacklisted anymore from this tunnel, + * and therefore can be added in future calls to connect_by_*. + * The peer must have been previously blacklisted for this tunnel. + * + * @param tunnel handle to existing tunnel. + * @param peer peer identity of the peer which shouldn't be blacklisted + * for the tunnel anymore. + */ +void +GNUNET_MESH_peer_unblacklist (struct GNUNET_MESH_Tunnel *tunnel, + const struct GNUNET_PeerIdentity *peer); + + /** * Handle for a transmission request. */ @@ -296,10 +389,11 @@ struct GNUNET_MESH_TransmitHandle; /** * Ask the mesh to call "notify" once it is ready to transmit the * given number of bytes to the specified tunnel or target. + * Only one call can be active at any time, to issue another request, + * wait for the callback or cancel the current request. * * @param tunnel tunnel to use for transmission * @param cork is corking allowed for this transmission? - * @param priority how important is the message? * @param maxdelay how long can the message wait? * @param target destination for the message * NULL for multicast to all tunnel targets @@ -315,7 +409,6 @@ struct GNUNET_MESH_TransmitHandle; */ struct GNUNET_MESH_TransmitHandle * GNUNET_MESH_notify_transmit_ready (struct GNUNET_MESH_Tunnel *tunnel, int cork, - uint32_t priority, struct GNUNET_TIME_Relative maxdelay, const struct GNUNET_PeerIdentity *target, size_t notify_size, @@ -333,14 +426,101 @@ GNUNET_MESH_notify_transmit_ready_cancel (struct GNUNET_MESH_TransmitHandle *th); +/** + * Method called to retrieve information about each tunnel the mesh peer + * is aware of. + * + * @param cls Closure. + * @param initiator Peer that started the tunnel (owner). + * @param tunnel_number Tunnel number. + * @param peers Array of peer identities that participate in the tunnel. + * @param npeers Number of peers in peers. + */ +typedef void (*GNUNET_MESH_TunnelsCB) (void *cls, + const struct GNUNET_PeerIdentity *owner, + unsigned int tunnel_number, + const struct GNUNET_PeerIdentity *peers, + unsigned int npeers); + + +/** + * Method called to retrieve information about a specific tunnel the mesh peer + * is aware of, including all transit nodes. + * + * @param cls Closure. + * @param peer Peer in the tunnel's tree. + * @param parent Parent of the current peer. All 0 when peer is root. + */ +typedef void (*GNUNET_MESH_TunnelCB) (void *cls, + const struct GNUNET_PeerIdentity *peer, + const struct GNUNET_PeerIdentity *parent); + + +/** + * Request information about the running mesh peer. + * The callback will be called for every tunnel known to the service, + * listing all active peers that blong to the tunnel. + * + * If called again on the same handle, it will overwrite the previous + * callback and cls. To retrieve the cls, monitor_cancel must be + * called first. + * + * WARNING: unstable API, likely to change in the future! + * + * @param h Handle to the mesh peer. + * @param callback Function to call with the requested data. + * @param callback_cls Closure for @c callback. + */ +void +GNUNET_MESH_get_tunnels (struct GNUNET_MESH_Handle *h, + GNUNET_MESH_TunnelsCB callback, + void *callback_cls); + + +/** + * Request information about a specific tunnel of the running mesh peer. + * + * WARNING: unstable API, likely to change in the future! + * + * @param h Handle to the mesh peer. + * @param initiator ID of the owner of the tunnel. + * @param tunnel_number Tunnel number. + * @param callback Function to call with the requested data. + * @param callback_cls Closure for @c callback. + */ +void +GNUNET_MESH_show_tunnel (struct GNUNET_MESH_Handle *h, + struct GNUNET_PeerIdentity *initiator, + unsigned int tunnel_number, + GNUNET_MESH_TunnelCB callback, + void *callback_cls); + + +/** + * Cancel a monitor request. The monitor callback will not be called. + * + * WARNING: unstable API, likely to change in the future! + * + * @param h Mesh handle. + * + * @return Closure given to GNUNET_MESH_monitor, if any. + */ +void * +GNUNET_MESH_get_tunnels_cancel (struct GNUNET_MESH_Handle *h); + + /** * Transition API for tunnel ctx management + * + * FIXME deprecated */ void GNUNET_MESH_tunnel_set_data (struct GNUNET_MESH_Tunnel *tunnel, void *data); /** * Transition API for tunnel ctx management + * + * FIXME deprecated */ void * GNUNET_MESH_tunnel_get_data (struct GNUNET_MESH_Tunnel *tunnel); diff --git a/src/include/gnunet_namestore_plugin.h b/src/include/gnunet_namestore_plugin.h index b27867f..1168e0d 100644 --- a/src/include/gnunet_namestore_plugin.h +++ b/src/include/gnunet_namestore_plugin.h @@ -120,6 +120,7 @@ struct GNUNET_NAMESTORE_PluginFunctions * @param iter function to call with the result * @param iter_cls closure for iter * @return GNUNET_OK on success, GNUNET_NO if there were no results, GNUNET_SYSERR on error + * 'iter' will have been called unless the return value is 'GNUNET_SYSERR' */ int (*iterate_records) (void *cls, const struct GNUNET_CRYPTO_ShortHashCode *zone, @@ -138,6 +139,7 @@ struct GNUNET_NAMESTORE_PluginFunctions * @param iter function to call with the result * @param iter_cls closure for iter * @return GNUNET_OK on success, GNUNET_NO if there were no results, GNUNET_SYSERR on error + * 'iter' will have been called unless the return value is 'GNUNET_SYSERR' */ int (*zone_to_name) (void *cls, const struct GNUNET_CRYPTO_ShortHashCode *zone, diff --git a/src/include/gnunet_namestore_service.h b/src/include/gnunet_namestore_service.h index a484601..4267e20 100644 --- a/src/include/gnunet_namestore_service.h +++ b/src/include/gnunet_namestore_service.h @@ -25,8 +25,6 @@ * * Other functions we might want: * - enumerate all known zones - * - convenience function to gather record and the full affilliated stree - * in one shot */ #ifndef GNUNET_NAMESTORE_SERVICE_H @@ -63,6 +61,16 @@ extern "C" */ #define GNUNET_NAMESTORE_TYPE_LEHO 65538 +/** + * Record type for VPN resolution + */ +#define GNUNET_NAMESTORE_TYPE_VPN 65539 + +/** + * Record type for zone revocation + */ +#define GNUNET_NAMESTORE_TYPE_REV 65540 + /** * Entry in the queue. */ @@ -100,10 +108,9 @@ GNUNET_NAMESTORE_connect (const struct GNUNET_CONFIGURATION_Handle *cfg); * resources). * * @param h handle to the namestore - * @param drop set to GNUNET_YES to delete all data in namestore (!) */ void -GNUNET_NAMESTORE_disconnect (struct GNUNET_NAMESTORE_Handle *h, int drop); +GNUNET_NAMESTORE_disconnect (struct GNUNET_NAMESTORE_Handle *h); /** @@ -149,8 +156,32 @@ enum GNUNET_NAMESTORE_RecordFlags * This record was added by the system * and is pending user confimation */ - GNUNET_NAMESTORE_RF_PENDING = 4 + GNUNET_NAMESTORE_RF_PENDING = 4, + + /** + * This expiration time of the record is a relative + * time (not an absolute time). + */ + GNUNET_NAMESTORE_RF_RELATIVE_EXPIRATION = 8, + + /** + * This record should not be used unless all (other) records with an absolute + * expiration time have expired. + */ + GNUNET_NAMESTORE_RF_SHADOW_RECORD = 16 + /** + * When comparing flags for record equality for removal, + * which flags should must match (in addition to the type, + * name, expiration value and data of the record)? All flags + * that are not listed here will be ignored for this purpose. + * (for example, we don't expect that users will remember to + * pass the '--private' option when removing a record from + * the namestore, hence we don't require this particular option + * to match upon removal). See also + * 'GNUNET_NAMESTORE_records_cmp'. + */ +#define GNUNET_NAMESTORE_RF_RCMP_FLAGS (GNUNET_NAMESTORE_RF_RELATIVE_EXPIRATION) }; @@ -162,13 +193,18 @@ struct GNUNET_NAMESTORE_RecordData /** * Binary value stored in the DNS record. + * FIXME: goofy API: sometimes 'data' is individually + * 'malloc'ed, sometimes it points into some existing + * data area (so sometimes this should be a 'void *', + * sometimes a 'const void *'). This is unclean. */ const void *data; /** - * Expiration time for the DNS record. + * Expiration time for the DNS record. Can be relative + * or absolute, depending on 'flags'. */ - struct GNUNET_TIME_Absolute expiration; + uint64_t expiration_time; /** * Number of bytes in 'data'. @@ -222,7 +258,7 @@ GNUNET_NAMESTORE_record_put (struct GNUNET_NAMESTORE_Handle *h, * to validate signatures received from the network. * * @param public_key public key of the zone - * @param expire block expiration + * @param freshness time set for block expiration * @param name name that is being mapped (at most 255 characters long) * @param rd_count number of entries in 'rd' array * @param rd array of records with data to store @@ -242,6 +278,7 @@ GNUNET_NAMESTORE_verify_signature (const struct GNUNET_CRYPTO_RsaPublicKeyBinary * Store an item in the namestore. If the item is already present, * the expiration time is updated to the max of the existing time and * the new time. This API is used by the authority of a zone. + * FIXME: consider allowing to pass multiple records in one call! * * @param h handle to the namestore * @param pkey private key of the zone @@ -289,7 +326,7 @@ GNUNET_NAMESTORE_record_remove (struct GNUNET_NAMESTORE_Handle *h, * * @param cls closure * @param zone_key public key of the zone - * @param expire when does the corresponding block in the DHT expire (until + * @param freshness when does the corresponding block in the DHT expire (until * when should we never do a DHT lookup for the same name again)?; * GNUNET_TIME_UNIT_ZERO_ABS if there are no records of any type in the namestore, * or the expiration time of the block in the namestore (even if there are zero @@ -311,7 +348,14 @@ typedef void (*GNUNET_NAMESTORE_RecordProcessor) (void *cls, /** * Get a result for a particular key from the namestore. The processor - * will only be called once. + * will only be called once. When using this functions, relative expiration + * times will be converted to absolute expiration times and a signature + * will be created if we are the authority. The record data and signature + * passed to 'proc' is thus always suitable for passing on to other peers + * (if we are the authority). If the record type is NOT set to 'ANY' and + * if we are NOT the authority, then non-matching records may be omitted + * from the result and no valid signature can be created; in this case, + * 'signature' will be NULL and the result cannot be given to other peers. * * @param h handle to the namestore * @param zone zone to look up a record from @@ -325,10 +369,10 @@ typedef void (*GNUNET_NAMESTORE_RecordProcessor) (void *cls, */ struct GNUNET_NAMESTORE_QueueEntry * GNUNET_NAMESTORE_lookup_record (struct GNUNET_NAMESTORE_Handle *h, - const struct GNUNET_CRYPTO_ShortHashCode *zone, - const char *name, - uint32_t record_type, - GNUNET_NAMESTORE_RecordProcessor proc, void *proc_cls); + const struct GNUNET_CRYPTO_ShortHashCode *zone, + const char *name, + uint32_t record_type, + GNUNET_NAMESTORE_RecordProcessor proc, void *proc_cls); /** @@ -354,9 +398,28 @@ GNUNET_NAMESTORE_zone_to_name (struct GNUNET_NAMESTORE_Handle *h, /** * Starts a new zone iteration (used to periodically PUT all of our - * records into our DHT). "proc" will be called once - * immediately, and then again after - * "GNUNET_NAMESTORE_zone_iterator_next" is invoked. + * records into our DHT). "proc" will be called once immediately, and + * then again after "GNUNET_NAMESTORE_zone_iterator_next" is invoked. + * + * By specifying a 'zone' of NULL and setting 'GNUNET_NAMESTORE_RF_AUTHORITY' + * in 'must_have_flags', we can iterate over all records for which we are + * the authority (the 'authority' flag will NOT be set in the returned + * records anyway). + * + * The 'GNUNET_NAMESTORE_RF_RELATIVE_EXPIRATION' + * bit in 'must_have_flags' has a special meaning: + * + * 0) If the bit is clear, all relative expriation times are converted to + * absolute expiration times. This is useful for performing DHT PUT + * operations (and zone transfers) of our zone. The generated signatures + * will be valid for other peers. + * 1) if it is set, it means that relative expiration times should be + * preserved when returned (this is useful for the zone editor user + * interface). No signatures will be created in this case, as + * signatures must not cover records with relative expiration times. + * + * Note that not all queries against this interface are equally performant + * as for some combinations no efficient index may exist. * * @param h handle to the namestore * @param zone zone to access, NULL for all zones @@ -388,7 +451,9 @@ GNUNET_NAMESTORE_zone_iterator_next (struct GNUNET_NAMESTORE_ZoneIterator *it); /** - * Stops iteration and releases the namestore handle for further calls. + * Stops iteration and releases the namestore handle for further calls. Must + * be called on any iteration that has not yet completed prior to calling + * 'GNUNET_NAMESTORE_disconnect'. * * @param it the iterator */ @@ -398,7 +463,9 @@ GNUNET_NAMESTORE_zone_iteration_stop (struct GNUNET_NAMESTORE_ZoneIterator *it); /** * Cancel a namestore operation. The final callback from the - * operation must not have been done yet. + * operation must not have been done yet. Must be called on any + * namestore operation that has not yet completed prior to calling + * 'GNUNET_NAMESTORE_disconnect'. * * @param qe operation to cancel */ @@ -423,6 +490,7 @@ size_t GNUNET_NAMESTORE_records_get_size (unsigned int rd_count, const struct GNUNET_NAMESTORE_RecordData *rd); + /** * Serialize the given records to the given destination buffer. * @@ -431,7 +499,7 @@ GNUNET_NAMESTORE_records_get_size (unsigned int rd_count, * @param dest_size size of the destination array * @param dest where to write the result * - * @return the size of serialized records + * @return the size of serialized records, -1 if records do not fit */ ssize_t GNUNET_NAMESTORE_records_serialize (unsigned int rd_count, @@ -457,15 +525,6 @@ GNUNET_NAMESTORE_records_deserialize (size_t len, struct GNUNET_NAMESTORE_RecordData *dest); -/** - * Checks if a name is wellformed - * - * @param name the name to check - * @return GNUNET_OK on success, GNUNET_SYSERR on error - */ -int -GNUNET_NAMESTORE_check_name (const char * name); - /** * Convert the 'value' of a record to a string. * @@ -517,6 +576,16 @@ const char * GNUNET_NAMESTORE_number_to_typename (uint32_t type); +/** + * Test if a given record is expired. + * + * @return GNUNET_YES if the record is expired, + * GNUNET_NO if not + */ +int +GNUNET_NAMESTORE_is_expired (const struct GNUNET_NAMESTORE_RecordData *rd); + + #if 0 /* keep Emacsens' auto-indent happy */ { #endif diff --git a/src/include/gnunet_nat_lib.h b/src/include/gnunet_nat_lib.h index 3a1e9a6..93b4418 100644 --- a/src/include/gnunet_nat_lib.h +++ b/src/include/gnunet_nat_lib.h @@ -1,6 +1,6 @@ /* This file is part of GNUnet. - (C) 2007, 2008, 2009, 2010, 2011 Christian Grothoff (and other contributing authors) + (C) 2007, 2008, 2009, 2010, 2011, 2012 Christian Grothoff (and other contributing authors) GNUnet is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published @@ -254,6 +254,46 @@ void GNUNET_NAT_mini_map_stop (struct GNUNET_NAT_MiniHandle *mini); +/** + * Handle to auto-configuration in progress. + */ +struct GNUNET_NAT_AutoHandle; + + +/** + * Function called with the result from the autoconfiguration. + * + * @param cls closure + * @param diff minimal suggested changes to the original configuration + * to make it work (as best as we can) + */ +typedef void (*GNUNET_NAT_AutoResultCallback)(void *cls, + const struct GNUNET_CONFIGURATION_Handle *diff); + + +/** + * Start auto-configuration routine. The resolver service should + * be available when this function is called. + * + * @param cfg initial configuration + * @param cb function to call with autoconfiguration result + * @param cb_cls closure for cb + * @return handle to cancel operation + */ +struct GNUNET_NAT_AutoHandle * +GNUNET_NAT_autoconfig_start (const struct GNUNET_CONFIGURATION_Handle *cfg, + GNUNET_NAT_AutoResultCallback cb, + void *cb_cls); + + +/** + * Abort autoconfiguration. + * + * @param ah handle for operation to abort + */ +void +GNUNET_NAT_autoconfig_cancel (struct GNUNET_NAT_AutoHandle *ah); + #endif /* end of gnunet_nat_lib.h */ diff --git a/src/include/gnunet_network_lib.h b/src/include/gnunet_network_lib.h index 085845a..1ff397e 100644 --- a/src/include/gnunet_network_lib.h +++ b/src/include/gnunet_network_lib.h @@ -67,11 +67,32 @@ struct GNUNET_NETWORK_FDSet }; - - +#include "platform.h" #include "gnunet_disk_lib.h" #include "gnunet_time_lib.h" +/** + * Test if the given protocol family is supported by this system. + * + * @param pf protocol family to test (PF_INET, PF_INET6, PF_UNIX) + * @return GNUNET_OK if the PF is supported + */ +int +GNUNET_NETWORK_test_pf (int pf); + + +/** + * Given a unixpath that is too long (larger than UNIX_PATH_MAX), + * shorten it to an acceptable length while keeping it unique + * and making sure it remains a valid filename (if possible). + * + * @param unixpath long path, will be freed (or same pointer returned + * with moved 0-termination). + * @return shortened unixpath, NULL on error + */ +char * +GNUNET_NETWORK_shorten_unixpath (char *unixpath); + /** * Accept a new connection on a socket. Configure it for non-blocking @@ -99,6 +120,18 @@ struct GNUNET_NETWORK_Handle * GNUNET_NETWORK_socket_box_native (SOCKTYPE fd); +/** + * Set if a socket should use blocking or non-blocking IO. + * + * @param fd socket + * @param doBlock blocking mode + * @return GNUNET_OK on success, GNUNET_SYSERR on error + */ +int +GNUNET_NETWORK_socket_set_blocking (struct GNUNET_NETWORK_Handle *fd, + int doBlock); + + /** * Bind to a connected socket * @@ -185,7 +218,7 @@ GNUNET_NETWORK_socket_recvfrom_amount (const struct GNUNET_NETWORK_Handle ssize_t GNUNET_NETWORK_socket_recvfrom (const struct GNUNET_NETWORK_Handle *desc, void *buffer, size_t length, - struct sockaddr *src_addr, socklen_t * addrlen); + struct sockaddr *src_addr, socklen_t *addrlen); /** diff --git a/src/include/gnunet_os_lib.h b/src/include/gnunet_os_lib.h index 67b6cce..e4bbab8 100644 --- a/src/include/gnunet_os_lib.h +++ b/src/include/gnunet_os_lib.h @@ -54,6 +54,51 @@ extern "C" #include "gnunet_configuration_lib.h" #include "gnunet_scheduler_lib.h" + +/** + * Flags that determine which of the standard streams + * should be inherited by the child process. + */ +enum GNUNET_OS_InheritStdioFlags +{ + + /** + * No standard streams should be inherited. + */ + GNUNET_OS_INHERIT_STD_NONE = 0, + + /** + * When this flag is set, the child process will + * inherit stdin of the parent. + */ + GNUNET_OS_INHERIT_STD_IN = 1, + + /** + * When this flag is set, the child process will + * inherit stdout of the parent. + */ + GNUNET_OS_INHERIT_STD_OUT = 2, + + /** + * When this flag is set, the child process will + * inherit stderr of the parent. + */ + GNUNET_OS_INHERIT_STD_ERR = 4, + + /** + * When these flags are set, the child process will + * inherit stdout and stderr of the parent. + */ + GNUNET_OS_INHERIT_STD_OUT_AND_ERR = 6, + + /** + * Use this option to have all of the standard streams + * (stdin, stdout and stderror) be inherited. + */ + GNUNET_OS_INHERIT_STD_ALL = 7 +}; + + /** * Process information (OS-dependent) */ @@ -106,7 +151,12 @@ enum GNUNET_OS_InstallationPathKind * Return the prefix of the path with documentation files, including the * license (share/doc/gnunet/). */ - GNUNET_OS_IPK_DOCDIR + GNUNET_OS_IPK_DOCDIR, + + /** + * Return the directory where helper binaries are installed (lib/gnunet/libexec/) + */ + GNUNET_OS_IPK_LIBEXECDIR }; @@ -155,6 +205,18 @@ char * GNUNET_OS_installation_get_path (enum GNUNET_OS_InstallationPathKind dirkind); +/** + * Given the name of a gnunet-helper, gnunet-service or gnunet-daemon + * binary, try to prefix it with the libexec/-directory to get the + * full path. + * + * @param progname name of the binary + * @return full path to the binary, if possible, otherwise copy of 'progname' + */ +char * +GNUNET_OS_get_libexec_binary_path (const char *progname); + + /** * Callback function invoked for each interface found. * @@ -257,6 +319,7 @@ GNUNET_OS_set_process_priority (struct GNUNET_OS_Process *proc, * Start a process. * * @param pipe_control should a pipe be used to send signals to the child? + * @param std_inheritance a set of GNUNET_OS_INHERIT_STD_* flags * @param pipe_stdin pipe to use to send input to child process (or NULL) * @param pipe_stdout pipe to use to get output from child process (or NULL) * @param filename name of the binary @@ -265,6 +328,7 @@ GNUNET_OS_set_process_priority (struct GNUNET_OS_Process *proc, */ struct GNUNET_OS_Process * GNUNET_OS_start_process_vap (int pipe_control, + enum GNUNET_OS_InheritStdioFlags std_inheritance, struct GNUNET_DISK_PipeHandle *pipe_stdin, struct GNUNET_DISK_PipeHandle *pipe_stdout, const char *filename, @@ -275,6 +339,7 @@ GNUNET_OS_start_process_vap (int pipe_control, * Start a process. * * @param pipe_control should a pipe be used to send signals to the child? + * @param std_inheritance a set of GNUNET_OS_INHERIT_STD_* flags * @param pipe_stdin pipe to use to send input to child process (or NULL) * @param pipe_stdout pipe to use to get output from child process (or NULL) * @param filename name of the binary @@ -283,6 +348,7 @@ GNUNET_OS_start_process_vap (int pipe_control, */ struct GNUNET_OS_Process * GNUNET_OS_start_process (int pipe_control, + enum GNUNET_OS_InheritStdioFlags std_inheritance, struct GNUNET_DISK_PipeHandle *pipe_stdin, struct GNUNET_DISK_PipeHandle *pipe_stdout, const char *filename, ...); @@ -292,6 +358,7 @@ GNUNET_OS_start_process (int pipe_control, * Start a process. * * @param pipe_control should a pipe be used to send signals to the child? + * @param std_inheritance a set of GNUNET_OS_INHERIT_STD_* flags * @param pipe_stdin pipe to use to send input to child process (or NULL) * @param pipe_stdout pipe to use to get output from child process (or NULL) * @param filename name of the binary @@ -300,6 +367,7 @@ GNUNET_OS_start_process (int pipe_control, */ struct GNUNET_OS_Process * GNUNET_OS_start_process_va (int pipe_control, + enum GNUNET_OS_InheritStdioFlags std_inheritance, struct GNUNET_DISK_PipeHandle *pipe_stdin, struct GNUNET_DISK_PipeHandle *pipe_stdout, const char *filename, va_list va); @@ -308,6 +376,7 @@ GNUNET_OS_start_process_va (int pipe_control, * Start a process. * * @param pipe_control should a pipe be used to send signals to the child? + * @param std_inheritance a set of GNUNET_OS_INHERIT_STD_* flags * @param lsocks array of listen sockets to dup systemd-style (or NULL); * must be NULL on platforms where dup is not supported * @param filename name of the binary @@ -317,6 +386,7 @@ GNUNET_OS_start_process_va (int pipe_control, */ struct GNUNET_OS_Process * GNUNET_OS_start_process_v (int pipe_control, + enum GNUNET_OS_InheritStdioFlags std_inheritance, const SOCKTYPE *lsocks, const char *filename, char *const argv[]); diff --git a/src/include/gnunet_peer_lib.h b/src/include/gnunet_peer_lib.h index 0121e84..6f5dee8 100644 --- a/src/include/gnunet_peer_lib.h +++ b/src/include/gnunet_peer_lib.h @@ -98,6 +98,24 @@ void GNUNET_PEER_resolve (GNUNET_PEER_Id id, struct GNUNET_PeerIdentity *pid); +/** + * Convert an interned PID to a normal peer identity. + * + * @param id interned PID to convert + * @return pointer to peer identity, valid as long 'id' is valid + */ +const struct GNUNET_PeerIdentity * +GNUNET_PEER_resolve2 (GNUNET_PEER_Id id); + + +#if 0 /* keep Emacsens' auto-indent happy */ +{ +#endif +#ifdef __cplusplus +} +#endif + + /* ifndef GNUNET_PEER_LIB_H */ #endif /* end of gnunet_peer_lib.h */ diff --git a/src/include/gnunet_protocols.h b/src/include/gnunet_protocols.h index b655f08..2ccc3e5 100644 --- a/src/include/gnunet_protocols.h +++ b/src/include/gnunet_protocols.h @@ -483,6 +483,16 @@ extern "C" */ #define GNUNET_MESSAGE_TYPE_FS_MIGRATION_STOP 139 +/** + * P2P request for content (one FS to another via a stream). + */ +#define GNUNET_MESSAGE_TYPE_FS_STREAM_QUERY 140 + +/** + * P2P answer for content (one FS to another via a stream). + */ +#define GNUNET_MESSAGE_TYPE_FS_STREAM_REPLY 141 + /******************************************************************************* * DHT message types @@ -558,6 +568,11 @@ extern "C" */ #define GNUNET_MESSAGE_TYPE_DHT_CLIENT_PUT_OK 155 +/** + * Certain results are already known to the client, filter those. + */ +#define GNUNET_MESSAGE_TYPE_DHT_CLIENT_GET_RESULTS_KNOWN 156 + /******************************************************************************* * HOSTLIST message types @@ -791,9 +806,14 @@ extern "C" #define GNUNET_MESSAGE_TYPE_MESH_TUNNEL_DESTROY 266 /** - * We need flow control + * ACK for a data packet. + */ +#define GNUNET_MESSAGE_TYPE_MESH_ACK 267 + +/** + * Poll for an ACK. */ -#define GNUNET_MESSAGE_TYPE_MESH_SPEED_NOTIFY 270 +#define GNUNET_MESSAGE_TYPE_MESH_POLL 268 /** * Connect to the mesh service, specifying subscriptions @@ -825,10 +845,65 @@ extern "C" */ #define GNUNET_MESSAGE_TYPE_MESH_LOCAL_PEER_ADD_BY_TYPE 277 +/** + * Ask the mesh service to add a peer described by a service string + */ +#define GNUNET_MESSAGE_TYPE_MESH_LOCAL_ANNOUNCE_REGEX 278 + +/** + * Ask the mesh service to add a peer described by a service string + */ +#define GNUNET_MESSAGE_TYPE_MESH_LOCAL_PEER_ADD_BY_STRING 279 + +/** + * Ask the mesh service to add a peer to the blacklist of an existing tunnel + */ +#define GNUNET_MESSAGE_TYPE_MESH_LOCAL_PEER_BLACKLIST 280 + +/** + * Ask the mesh service to remove a peer from the blacklist of a tunnel + */ +#define GNUNET_MESSAGE_TYPE_MESH_LOCAL_PEER_UNBLACKLIST 281 + +/** + * Set tunnel speed to slowest peer + */ +#define GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_MIN 282 + +/** + * Set tunnel speed to fastest peer + */ +#define GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_MAX 283 + +/** + * Set tunnel buffering on. + */ +#define GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_BUFFER 284 + +/** + * Set tunnel buffering off. + */ +#define GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_NOBUFFER 285 + +/** + * Local ACK for data. + */ +#define GNUNET_MESSAGE_TYPE_MESH_LOCAL_ACK 286 + +/** + * Local information about all tunnels of service. + */ +#define GNUNET_MESSAGE_TYPE_MESH_LOCAL_INFO_TUNNELS 287 + +/** + * Local information of service about a specific tunnel. + */ +#define GNUNET_MESSAGE_TYPE_MESH_LOCAL_INFO_TUNNEL 288 + /** * 640kb should be enough for everybody */ -#define GNUNET_MESSAGE_TYPE_MESH_RESERVE_END 288 +#define GNUNET_MESSAGE_TYPE_MESH_RESERVE_END 299 @@ -1034,6 +1109,23 @@ extern "C" */ #define GNUNET_MESSAGE_TYPE_ATS_RESET_BACKOFF 352 +/** + * Type of the 'struct AddressUpdateMessage' sent by client to ATS + * to add a new address + */ +#define GNUNET_MESSAGE_TYPE_ATS_ADDRESS_ADD 353 + +/** + * Type of the 'struct AddressListRequestMessage' sent by client to ATS + * to request information about addresses + */ +#define GNUNET_MESSAGE_TYPE_ATS_ADDRESSLIST_REQUEST 354 + +/** + * Type of the 'struct AddressListResponseMessage' sent by ATS to client + * with information about addresses + */ +#define GNUNET_MESSAGE_TYPE_ATS_ADDRESSLIST_RESPONSE 355 /******************************************************************************* * TRANSPORT message types @@ -1176,8 +1268,13 @@ extern "C" */ #define GNUNET_MESSAGE_TYPE_TRANSPORT_BROADCAST_BEACON 384 +/** + * Message containing traffic metrics for transport service + */ +#define GNUNET_MESSAGE_TYPE_TRANSPORT_TRAFFIC_METRIC 385 + /******************************************************************************* - * STREAM LIRBRARY MESSAGES + * STREAM messages types ******************************************************************************/ /** @@ -1276,15 +1373,87 @@ extern "C" */ #define GNUNET_MESSAGE_TYPE_FS_PUBLISH_HELPER_FINISHED 426 + /******************************************************************************* * NAMESTORE message types ******************************************************************************/ /** - * Request update and listing of a peer. + * Client to service: register. */ #define GNUNET_MESSAGE_TYPE_NAMESTORE_START 430 +/** + * Client to service: lookup name + */ +#define GNUNET_MESSAGE_TYPE_NAMESTORE_LOOKUP_NAME 431 + +/** + * Service to client: result of name lookup + */ +#define GNUNET_MESSAGE_TYPE_NAMESTORE_LOOKUP_NAME_RESPONSE 432 + +/** + * Client to service: put records (for caching) + */ +#define GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_PUT 433 + +/** + * Service to client: result of put operation. + */ +#define GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_PUT_RESPONSE 434 + +/** + * Client to service: create record as authority + */ +#define GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_CREATE 435 + +/** + * Service to client: result of record creation request + */ +#define GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_CREATE_RESPONSE 436 + +/** + * Client to service: remove record(s) + */ +#define GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_REMOVE 437 + +/** + * Service to client: result of removal request. + */ +#define GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_REMOVE_RESPONSE 438 + +/** + * Client to service: "reverse" lookup for zone name based on zone key + */ +#define GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_TO_NAME 439 + +/** + * Service to client: result of zone-to-name lookup. + */ +#define GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_TO_NAME_RESPONSE 440 + +/** + * Client to service: please start iteration + */ +#define GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_ITERATION_START 445 + +/** + * Service to client: current record in iteration (or end of list). + */ +#define GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_ITERATION_RESPONSE 446 + +/** + * Client to service: next record in iteration please. + */ +#define GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_ITERATION_NEXT 447 + +/** + * Client to service: stop iterating. + */ +#define GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_ITERATION_STOP 448 + + /******************************************************************************* * LOCKMANAGER message types ******************************************************************************/ @@ -1292,21 +1461,238 @@ extern "C" /** * Message to acquire Lock */ -#define GNUNET_MESSAGE_TYPE_LOCKMANAGER_ACQUIRE 440 +#define GNUNET_MESSAGE_TYPE_LOCKMANAGER_ACQUIRE 450 /** * Message to release lock */ -#define GNUNET_MESSAGE_TYPE_LOCKMANAGER_RELEASE 441 +#define GNUNET_MESSAGE_TYPE_LOCKMANAGER_RELEASE 451 /** * SUCESS reply from lockmanager */ -#define GNUNET_MESSAGE_TYPE_LOCKMANAGER_SUCCESS 442 +#define GNUNET_MESSAGE_TYPE_LOCKMANAGER_SUCCESS 452 + +/******************************************************************************* + * TESTBED message types + ******************************************************************************/ + +/** + * Initial message from a client to a testing control service + */ +#define GNUNET_MESSAGE_TYPE_TESTBED_INIT 460 + +/** + * Message to add host + */ +#define GNUNET_MESSAGE_TYPE_TESTBED_ADD_HOST 461 + +/** + * Message to signal that a add host succeeded + */ +#define GNUNET_MESSAGE_TYPE_TESTBED_ADD_HOST_SUCCESS 462 + +/** + * Message to configure a service to be shared among peers + */ +#define GNUNET_MESSAGE_TYPE_TESTBED_SHARE_SERVICE 463 /** - * Next available: 450 + * Message to link delegated controller to slave controller */ +#define GNUNET_MESSAGE_TYPE_TESTBED_LINK_CONTROLLERS 464 + +/** + * Message to create a peer at a host + */ +#define GNUNET_MESSAGE_TYPE_TESTBED_CREATE_PEER 465 + +/** + * Message to reconfigure a peer + */ +#define GNUNET_MESSAGE_TYPE_TESTBED_RECONFIGURE_PEER 466 + +/** + * Message to start a peer at a host + */ +#define GNUNET_MESSAGE_TYPE_TESTBED_START_PEER 467 + +/** + * Message to stop a peer at a host + */ +#define GNUNET_MESSAGE_TYPE_TESTBED_STOP_PEER 468 + +/** + * Message to destroy a peer + */ +#define GNUNET_MESSAGE_TYPE_TESTBED_DESTROY_PEER 469 + +/** + * Configure underlay link message + */ +#define GNUNET_MESSAGE_TYPE_TESTBED_CONFIGURE_UNDERLAY_LINK 470 + +/** + * Message to connect peers in a overlay + */ +#define GNUNET_MESSAGE_TYPE_TESTBED_OVERLAY_CONNECT 471 + +/** + * Message for peer events + */ +#define GNUNET_MESSAGE_TYPE_TESTBED_PEER_EVENT 472 + +/** + * Message for peer connect events + */ +#define GNUNET_MESSAGE_TYPE_TESTBED_PEER_CONNECT_EVENT 473 + +/** + * Message for operation events + */ +#define GNUNET_MESSAGE_TYPE_TESTBED_OPERATION_FAIL_EVENT 474 + +/** + * Message to signal successful peer creation + */ +#define GNUNET_MESSAGE_TYPE_TESTBED_CREATE_PEER_SUCCESS 475 + +/** + * Message to signal a generic operation has been successful + */ +#define GNUNET_MESSAGE_TYPE_TESTBED_GENERIC_OPERATION_SUCCESS 476 + +/** + * Message to get the configuration of a peer + */ +#define GNUNET_MESSAGE_TYPE_TESTBED_GET_PEER_CONFIGURATION 477 + +/** + * Message containing the peer configuration + */ +#define GNUNET_MESSAGE_TYPE_TESTBED_PEER_CONFIGURATION 478 + +/** + * Message to request a controller to make one of its peer to connect to another + * peer using the contained HELLO + */ +#define GNUNET_MESSAGE_TYPE_TESTBED_REMOTE_OVERLAY_CONNECT 479 + +/** + * Message to request configuration of a slave controller + */ +#define GNUNET_MESSAGE_TYPE_TESTBED_GET_SLAVE_CONFIGURATION 480 + +/** + * Message which contains the configuration of slave controller + */ +#define GNUNET_MESSAGE_TYPE_TESTBED_SLAVE_CONFIGURATION 481 + +/** + * Not really a message, but for careful checks on the testbed messages; Should + * always be the maximum and never be used to send messages with this type + */ +#define GNUNET_MESSAGE_TYPE_TESTBED_MAX 482 + +/** + * The initialization message towards gnunet-testbed-helper + */ +#define GNUNET_MESSAGE_TYPE_TESTBED_HELPER_INIT 495 + +/** + * The reply message from gnunet-testbed-helper + */ +#define GNUNET_MESSAGE_TYPE_TESTBED_HELPER_REPLY 496 + + +/** + * GNS. FIXME: document! + */ +#define GNUNET_MESSAGE_TYPE_GNS_LOOKUP 500 + +#define GNUNET_MESSAGE_TYPE_GNS_LOOKUP_RESULT 501 + +#define GNUNET_MESSAGE_TYPE_GNS_SHORTEN 502 + +#define GNUNET_MESSAGE_TYPE_GNS_SHORTEN_RESULT 503 + +#define GNUNET_MESSAGE_TYPE_GNS_GET_AUTH 504 + +#define GNUNET_MESSAGE_TYPE_GNS_GET_AUTH_RESULT 505 + + +/******************************************************************************* + * CONSENSUS message types + ******************************************************************************/ + +/** + * Join a consensus session. Sent by client to service as first message. + */ +#define GNUNET_MESSAGE_TYPE_CONSENSUS_CLIENT_JOIN 520 + +/** + * Insert an element. Sent by client to service. + */ +#define GNUNET_MESSAGE_TYPE_CONSENSUS_CLIENT_INSERT 521 + +/** + * Begin accepting new elements from other participants. + * Sent by client to service. + */ +#define GNUNET_MESSAGE_TYPE_CONSENSUS_CLIENT_BEGIN 522 + +/** + * Sent by service when a new element is added. + */ +#define GNUNET_MESSAGE_TYPE_CONSENSUS_CLIENT_RECEIVED_ELEMENT 523 + +/** + * Sent by client to service in order to start the consensus conclusion. + */ +#define GNUNET_MESSAGE_TYPE_CONSENSUS_CLIENT_CONCLUDE 524 + +/** + * Sent by service to client in order to signal a completed consensus conclusion. + * Last message sent in a consensus session. + */ +#define GNUNET_MESSAGE_TYPE_CONSENSUS_CLIENT_CONCLUDE_DONE 525 + + +/* message types 526-539 reserved for consensus client/service messages */ + + + +/** + * Sent by client to service, telling whether a received element should + * be accepted and propagated further or not. + */ +#define GNUNET_MESSAGE_TYPE_CONSENSUS_CLIENT_ACK 540 + +/** + * Strata estimator. + */ +#define GNUNET_MESSAGE_TYPE_CONSENSUS_P2P_DELTA_ESTIMATE 541 + +/** + * IBF containing all elements of a peer. + */ +#define GNUNET_MESSAGE_TYPE_CONSENSUS_P2P_DIFFERENCE_DIGEST 542 + +/** + * Elements, and requests for further elements + */ +#define GNUNET_MESSAGE_TYPE_CONSENSUS_P2P_ELEMENTS 543 + +/* + * Initialization message for consensus p2p communication. + */ +#define GNUNET_MESSAGE_TYPE_CONSENSUS_P2P_HELLO 544 + + +/** + * Next available: 570 + */ + /******************************************************************************* * TODO: we need a way to register message types centrally (via some webpage). diff --git a/src/include/gnunet_pseudonym_lib.h b/src/include/gnunet_pseudonym_lib.h index 8fd938d..6ec51b6 100644 --- a/src/include/gnunet_pseudonym_lib.h +++ b/src/include/gnunet_pseudonym_lib.h @@ -51,7 +51,7 @@ extern "C" * @return GNUNET_OK to continue iteration, GNUNET_SYSERR to abort */ typedef int (*GNUNET_PSEUDONYM_Iterator) (void *cls, - const GNUNET_HashCode * pseudonym, + const struct GNUNET_HashCode * pseudonym, const char *name, const char *unique_name, const struct GNUNET_CONTAINER_MetaData @@ -67,7 +67,7 @@ typedef int (*GNUNET_PSEUDONYM_Iterator) (void *cls, */ int GNUNET_PSEUDONYM_rank (const struct GNUNET_CONFIGURATION_Handle *cfg, - const GNUNET_HashCode * nsid, int delta); + const struct GNUNET_HashCode * nsid, int delta); /** * Add a pseudonym to the set of known pseudonyms. @@ -80,7 +80,7 @@ GNUNET_PSEUDONYM_rank (const struct GNUNET_CONFIGURATION_Handle *cfg, */ void GNUNET_PSEUDONYM_add (const struct GNUNET_CONFIGURATION_Handle *cfg, - const GNUNET_HashCode * id, + const struct GNUNET_HashCode * id, const struct GNUNET_CONTAINER_MetaData *meta); @@ -127,7 +127,7 @@ GNUNET_PSEUDONYM_discovery_callback_unregister (GNUNET_PSEUDONYM_Iterator */ char * GNUNET_PSEUDONYM_name_uniquify (const struct GNUNET_CONFIGURATION_Handle *cfg, - const GNUNET_HashCode * nsid, const char *name, unsigned int *suffix); + const struct GNUNET_HashCode * nsid, const char *name, unsigned int *suffix); /** * Get namespace name, metadata and rank @@ -152,7 +152,7 @@ GNUNET_PSEUDONYM_name_uniquify (const struct GNUNET_CONFIGURATION_Handle *cfg, */ int GNUNET_PSEUDONYM_get_info (const struct GNUNET_CONFIGURATION_Handle *cfg, - const GNUNET_HashCode * nsid, struct GNUNET_CONTAINER_MetaData **ret_meta, + const struct GNUNET_HashCode * nsid, struct GNUNET_CONTAINER_MetaData **ret_meta, int32_t *ret_rank, char **ret_name, int *name_is_a_dup); @@ -166,7 +166,7 @@ GNUNET_PSEUDONYM_get_info (const struct GNUNET_CONFIGURATION_Handle *cfg, */ int GNUNET_PSEUDONYM_name_to_id (const struct GNUNET_CONFIGURATION_Handle *cfg, - const char *ns_uname, GNUNET_HashCode * nsid); + const char *ns_uname, struct GNUNET_HashCode * nsid); /** * Set the pseudonym metadata, rank and name. @@ -182,7 +182,7 @@ GNUNET_PSEUDONYM_name_to_id (const struct GNUNET_CONFIGURATION_Handle *cfg, */ int GNUNET_PSEUDONYM_set_info (const struct GNUNET_CONFIGURATION_Handle *cfg, - const GNUNET_HashCode * nsid, const char *name, + const struct GNUNET_HashCode * nsid, const char *name, const struct GNUNET_CONTAINER_MetaData *md, int rank); diff --git a/src/include/gnunet_regex_lib.h b/src/include/gnunet_regex_lib.h index aec37c1..ebeb9e5 100644 --- a/src/include/gnunet_regex_lib.h +++ b/src/include/gnunet_regex_lib.h @@ -28,6 +28,8 @@ #define GNUNET_REGEX_LIB_H #include "gnunet_util_lib.h" +#include "gnunet_dht_service.h" +#include "gnunet_statistics_service.h" #ifdef __cplusplus extern "C" @@ -37,48 +39,69 @@ extern "C" #endif #endif + +/** + * Constant for how many bytes the initial string regex should have. + */ +#define GNUNET_REGEX_INITIAL_BYTES 24 + + +/** + * Maximum regex string length for use with GNUNET_REGEX_ipv4toregex + */ +#define GNUNET_REGEX_IPV4_REGEXLEN 32 + 6 + + +/** + * Maximum regex string length for use with GNUNET_REGEX_ipv6toregex + */ +#define GNUNET_REGEX_IPV6_REGEXLEN 128 + 6 + + /** * Automaton (NFA/DFA) representation. */ struct GNUNET_REGEX_Automaton; + /** * Edge representation. */ struct GNUNET_REGEX_Edge { /** - * Label of the edge. + * Label of the edge. FIXME: might want to not consume exactly multiples of 8 bits, need length? */ const char *label; /** * Destionation of the edge. */ - GNUNET_HashCode destination; + struct GNUNET_HashCode destination; }; -/** - * Construct an NFA by parsing the regex string of length 'len'. - * - * @param regex regular expression string. - * @param len length of the string. - * - * @return NFA, needs to be freed using GNUNET_REGEX_destroy_automaton. - */ -struct GNUNET_REGEX_Automaton * -GNUNET_REGEX_construct_nfa (const char *regex, const size_t len); /** * Construct DFA for the given 'regex' of length 'len'. * + * Path compression means, that for example a DFA o -> a -> b -> c -> o will be + * compressed to o -> abc -> o. Note that this parameter influences the + * non-determinism of states of the resulting NFA in the DHT (number of outgoing + * edges with the same label). For example for an application that stores IPv4 + * addresses as bitstrings it could make sense to limit the path compression to + * 4 or 8. + * * @param regex regular expression string. * @param len length of the regular expression. - * - * @return DFA, needs to be freed using GNUNET_REGEX_destroy_automaton. + * @param max_path_len limit the path compression length to the + * given value. If set to 1, no path compression is applied. Set to 0 for + * maximal possible path compression (generally not desireable). + * @return DFA, needs to be freed using GNUNET_REGEX_automaton_destroy. */ struct GNUNET_REGEX_Automaton * -GNUNET_REGEX_construct_dfa (const char *regex, const size_t len); +GNUNET_REGEX_construct_dfa (const char *regex, const size_t len, + unsigned int max_path_len); + /** * Free the memory allocated by constructing the GNUNET_REGEX_Automaton. @@ -89,15 +112,44 @@ GNUNET_REGEX_construct_dfa (const char *regex, const size_t len); void GNUNET_REGEX_automaton_destroy (struct GNUNET_REGEX_Automaton *a); + +/** + * Options for graph creation function + * GNUNET_REGEX_automaton_save_graph. + */ +enum GNUNET_REGEX_GraphSavingOptions +{ + /** + * Default. Do nothing special. + */ + GNUNET_REGEX_GRAPH_DEFAULT = 0, + + /** + * The generated graph will include extra information such as the NFA states + * that were used to generate the DFA state. + */ + GNUNET_REGEX_GRAPH_VERBOSE = 1, + + /** + * Enable graph coloring. Will color each SCC in a different color. + */ + GNUNET_REGEX_GRAPH_COLORING = 2 +}; + + /** * Save the given automaton as a GraphViz dot file. * * @param a the automaton to be saved. * @param filename where to save the file. + * @param options options for graph generation that include coloring or verbose + * mode */ void GNUNET_REGEX_automaton_save_graph (struct GNUNET_REGEX_Automaton *a, - const char *filename); + const char *filename, + enum GNUNET_REGEX_GraphSavingOptions options); + /** * Evaluates the given 'string' against the given compiled regex. @@ -111,9 +163,10 @@ int GNUNET_REGEX_eval (struct GNUNET_REGEX_Automaton *a, const char *string); + /** * Get the first key for the given 'input_string'. This hashes - * the first x bits of the 'input_strings'. + * the first x bits of the 'input_string'. * * @param input_string string. * @param string_len length of the 'input_string'. @@ -122,21 +175,23 @@ GNUNET_REGEX_eval (struct GNUNET_REGEX_Automaton *a, * @return number of bits of 'input_string' that have been consumed * to construct the key */ -unsigned int -GNUNET_REGEX_get_first_key (const char *input_string, unsigned int string_len, - GNUNET_HashCode * key); +size_t +GNUNET_REGEX_get_first_key (const char *input_string, size_t string_len, + struct GNUNET_HashCode * key); + /** * Check if the given 'proof' matches the given 'key'. * - * @param proof partial regex - * @param key hash + * @param proof partial regex of a state. + * @param key hash of a state. * - * @return GNUNET_OK if the proof is valid for the given key + * @return GNUNET_OK if the proof is valid for the given key. */ int GNUNET_REGEX_check_proof (const char *proof, - const GNUNET_HashCode *key); + const struct GNUNET_HashCode *key); + /** * Iterator callback function. @@ -149,12 +204,13 @@ GNUNET_REGEX_check_proof (const char *proof, * @param edges edges leaving current state. */ typedef void (*GNUNET_REGEX_KeyIterator)(void *cls, - const GNUNET_HashCode *key, + const struct GNUNET_HashCode *key, const char *proof, int accepting, unsigned int num_edges, const struct GNUNET_REGEX_Edge *edges); + /** * Iterate over all edges starting from start state of automaton 'a'. Calling * iterator for each edge. @@ -168,6 +224,133 @@ GNUNET_REGEX_iterate_all_edges (struct GNUNET_REGEX_Automaton *a, GNUNET_REGEX_KeyIterator iterator, void *iterator_cls); + +/** + * Create a regex in 'rxstr' from the given 'ip' and 'netmask'. + * + * @param ip IPv4 representation. + * @param netmask netmask for the ip. + * @param rxstr generated regex, must be at least GNUNET_REGEX_IPV4_REGEXLEN + * bytes long. + */ +void +GNUNET_REGEX_ipv4toregex (const struct in_addr *ip, const char *netmask, + char *rxstr); + + +/** + * Create a regex in 'rxstr' from the given 'ipv6' and 'prefixlen'. + * + * @param ipv6 IPv6 representation. + * @param prefixlen length of the ipv6 prefix. + * @param rxstr generated regex, must be at least GNUNET_REGEX_IPV6_REGEXLEN + * bytes long. + */ +void +GNUNET_REGEX_ipv6toregex (const struct in6_addr *ipv6, + unsigned int prefixlen, char *rxstr); + + + +/** + * Handle to store cached data about a regex announce. + */ +struct GNUNET_REGEX_announce_handle; + +/** + * Handle to store data about a regex search. + */ +struct GNUNET_REGEX_search_handle; + +/** + * Announce a regular expression: put all states of the automaton in the DHT. + * Does not free resources, must call GNUNET_REGEX_announce_cancel for that. + * + * @param dht An existing and valid DHT service handle. + * @param id ID to announce as provider of regex. Own ID in most cases. + * @param regex Regular expression to announce. + * @param compression How many characters per edge can we squeeze? + * @param stats Optional statistics handle to report usage. Can be NULL. + * + * @return Handle to reuse o free cached resources. + * Must be freed by calling GNUNET_REGEX_announce_cancel. + */ +struct GNUNET_REGEX_announce_handle * +GNUNET_REGEX_announce (struct GNUNET_DHT_Handle *dht, + struct GNUNET_PeerIdentity *id, + const char *regex, + uint16_t compression, + struct GNUNET_STATISTICS_Handle *stats); + +/** + * Announce again a regular expression previously announced. + * Does use caching to speed up process. + * + * @param h Handle returned by a previous GNUNET_REGEX_announce call. + */ +void +GNUNET_REGEX_reannounce (struct GNUNET_REGEX_announce_handle *h); + + +/** + * Clear all cached data used by a regex announce. + * Does not close DHT connection. + * + * @param h Handle returned by a previous GNUNET_REGEX_announce call. + */ +void +GNUNET_REGEX_announce_cancel (struct GNUNET_REGEX_announce_handle *h); + + +/** + * Search callback function. + * + * @param cls Closure provided in GNUNET_REGEX_search. + * @param id Peer providing a regex that matches the string. + * @param get_path Path of the get request. + * @param get_path_length Lenght of get_path. + * @param put_path Path of the put request. + * @param put_path_length Length of the put_path. + */ +typedef void (*GNUNET_REGEX_Found)(void *cls, + const struct GNUNET_PeerIdentity *id, + const struct GNUNET_PeerIdentity *get_path, + unsigned int get_path_length, + const struct GNUNET_PeerIdentity *put_path, + unsigned int put_path_length); + + +/** + * Search for a peer offering a regex matching certain string in the DHT. + * The search runs until GNUNET_REGEX_search_cancel is called, even if results + * are returned. + * + * @param dht An existing and valid DHT service handle. + * @param string String to match against the regexes in the DHT. + * @param callback Callback for found peers. + * @param callback_cls Closure for @c callback. + * @param stats Optional statistics handle to report usage. Can be NULL. + * + * @return Handle to stop search and free resources. + * Must be freed by calling GNUNET_REGEX_search_cancel. + */ +struct GNUNET_REGEX_search_handle * +GNUNET_REGEX_search (struct GNUNET_DHT_Handle *dht, + const char *string, + GNUNET_REGEX_Found callback, + void *callback_cls, + struct GNUNET_STATISTICS_Handle *stats); + +/** + * Stop search and free all data used by a GNUNET_REGEX_search call. + * Does not close DHT connection. + * + * @param h Handle returned by a previous GNUNET_REGEX_search call. + */ +void +GNUNET_REGEX_search_cancel (struct GNUNET_REGEX_search_handle *h); + + #if 0 /* keep Emacsens' auto-indent happy */ { #endif @@ -177,4 +360,3 @@ GNUNET_REGEX_iterate_all_edges (struct GNUNET_REGEX_Automaton *a, /* end of gnunet_regex_lib.h */ #endif - diff --git a/src/include/gnunet_scheduler_lib.h b/src/include/gnunet_scheduler_lib.h index 4727534..1e2a400 100644 --- a/src/include/gnunet_scheduler_lib.h +++ b/src/include/gnunet_scheduler_lib.h @@ -212,6 +212,8 @@ typedef int (*GNUNET_SCHEDULER_select) (void *cls, struct GNUNET_NETWORK_FDSet * wfds, struct GNUNET_NETWORK_FDSet * efds, struct GNUNET_TIME_Relative timeout); + + /** * Initialize and run scheduler. This function will return when all * tasks have completed. On systems with signals, receiving a SIGTERM diff --git a/src/include/gnunet_server_lib.h b/src/include/gnunet_server_lib.h index 73fe800..f59e970 100644 --- a/src/include/gnunet_server_lib.h +++ b/src/include/gnunet_server_lib.h @@ -154,6 +154,24 @@ GNUNET_SERVER_create (GNUNET_CONNECTION_AccessCheck access, void *access_cls, int require_found); +/** + * Suspend accepting connections from the listen socket temporarily. + * + * @param server server to stop accepting connections. + */ +void +GNUNET_SERVER_suspend (struct GNUNET_SERVER_Handle *server); + + +/** + * Resume accepting connections from the listen socket. + * + * @param server server to stop accepting connections. + */ +void +GNUNET_SERVER_resume (struct GNUNET_SERVER_Handle *server); + + /** * Stop the listen socket and get ready to shutdown the server * once only 'monitor' clients are left. @@ -519,10 +537,10 @@ GNUNET_SERVER_transmit_context_destroy (struct GNUNET_SERVER_TransmitContext /** * The notification context is the key datastructure for a conveniance * API used for transmission of notifications to the client until the - * client disconnects (or the notification context is destroyed, in - * which case we disconnect these clients). Essentially, all - * (notification) messages are queued up until the client is able to - * read them. + * client disconnects or is disconnected (or the notification context + * is destroyed, in which case we disconnect these clients). + * Essentially, all (notification) messages are queued up until the + * client is able to read them. */ struct GNUNET_SERVER_NotificationContext; diff --git a/src/include/gnunet_stream_lib.h b/src/include/gnunet_stream_lib.h index e09c264..056695b 100644 --- a/src/include/gnunet_stream_lib.h +++ b/src/include/gnunet_stream_lib.h @@ -46,28 +46,23 @@ enum GNUNET_STREAM_Status /** * All previous read/write operations are successfully done */ - GNUNET_STREAM_OK = 0, + GNUNET_STREAM_OK, /** * A timeout occured while reading/writing the stream */ - GNUNET_STREAM_TIMEOUT = 1, + GNUNET_STREAM_TIMEOUT, /** * Other side has shutdown the socket for this type of operation * (reading/writing) */ - GNUNET_STREAM_SHUTDOWN = 2, + GNUNET_STREAM_SHUTDOWN, /** * A serious error occured while operating on this stream */ - GNUNET_STREAM_SYSERR = 3, - - /** - * An error resulted in an unusable stream - */ - GNUNET_STREAM_BROKEN + GNUNET_STREAM_SYSERR }; /** @@ -85,6 +80,13 @@ typedef void (*GNUNET_STREAM_OpenCallback) (void *cls, struct GNUNET_STREAM_Socket *socket); +/** + * Callback for signalling stream listen success; See + * GNUNET_STREAM_OPTION_SIGNAL_LISTEN_SUCCESS + */ +typedef void (*GNUNET_STREAM_ListenSuccessCallback) (void); + + /** * Options for the stream. */ @@ -103,7 +105,32 @@ enum GNUNET_STREAM_Option * of '0' means to use the round-trip time (plus a tiny grace period); * this is also the default. */ - GNUNET_STREAM_OPTION_INITIAL_RETRANSMIT_TIMEOUT + GNUNET_STREAM_OPTION_INITIAL_RETRANSMIT_TIMEOUT, + + /** + * Option to set the write sequence number. Takes a uint32_t as parameter + * to set the value of the write sequence number + */ + GNUNET_STREAM_OPTION_TESTING_SET_WRITE_SEQUENCE_NUMBER, + + /** + * Listen socket timeout in milliseconds given as uint32_t + */ + GNUNET_STREAM_OPTION_LISTEN_TIMEOUT, + + /** + * Option to register a callback when stream listening is successfull. Takes + * parameter of the form GNUNET_STREAM_ListenSuccessCallback. The callback + * is only called if listening is successful + */ + GNUNET_STREAM_OPTION_SIGNAL_LISTEN_SUCCESS, + + /** + * Option to set the maximum payload size in bytes of a stream data + * packets. Takes an uint16_t as argument. Note that this should be less + * than 64000 and cannot be zero. Default is 64000 bytes. + */ + GNUNET_STREAM_OPTION_MAX_PAYLOAD_SIZE }; @@ -114,7 +141,8 @@ enum GNUNET_STREAM_Option * @param target the target peer to which the stream has to be opened * @param app_port the application port number which uniquely identifies this * stream - * @param open_cb this function will be called after stream has be established + * @param open_cb this function will be called after stream has be established; + * cannot be NULL * @param open_cb_cls the closure for open_cb * @param ... options to the stream, terminated by GNUNET_STREAM_OPTION_END * @return if successful it returns the stream socket; NULL if stream cannot be @@ -164,7 +192,10 @@ GNUNET_STREAM_shutdown (struct GNUNET_STREAM_Socket *socket, /** - * Cancels a pending shutdown + * Cancels a pending shutdown. Note that the shutdown messages may already + * be sent and the stream is shutdown already for the operation given to + * GNUNET_STREAM_shutdown(). This function only clears up any retranmissions of + * shutdown messages and frees the shutdown handle. * * @param handle the shutdown handle returned from GNUNET_STREAM_shutdown */ @@ -174,7 +205,7 @@ GNUNET_STREAM_shutdown_cancel (struct GNUNET_STREAM_ShutdownHandle *handle); /** * Closes the stream and frees the associated state. The stream should be - * shutdown before closing. + * shutdown for both reading and writing before closing. * * @param socket the stream socket */ @@ -184,11 +215,13 @@ GNUNET_STREAM_close (struct GNUNET_STREAM_Socket *socket); /** * Functions of this type are called upon new stream connection from other peers + * or upon binding error which happen when the app_port given in + * GNUNET_STREAM_listen() is already taken. * * @param cls the closure from GNUNET_STREAM_listen - * @param socket the socket representing the stream + * @param socket the socket representing the stream; NULL on binding error * @param initiator the identity of the peer who wants to establish a stream - * with us + * with us; NULL on binding error * @return GNUNET_OK to keep the socket open, GNUNET_SYSERR to close the * stream (the socket will be invalid after the call) */ @@ -207,17 +240,22 @@ struct GNUNET_STREAM_ListenSocket; * Listens for stream connections for a specific application ports * * @param cfg the configuration to use - * @param app_port the application port for which new streams will be accepted + * @param app_port the application port for which new streams will be + * accepted. If another stream is listening on the same port the + * listen_cb will be called to signal binding error and the returned + * ListenSocket will be invalidated. * @param listen_cb this function will be called when a peer tries to establish * a stream with us * @param listen_cb_cls closure for listen_cb + * @param ... options to the stream, terminated by GNUNET_STREAM_OPTION_END * @return listen socket, NULL for any error */ struct GNUNET_STREAM_ListenSocket * GNUNET_STREAM_listen (const struct GNUNET_CONFIGURATION_Handle *cfg, GNUNET_MESH_ApplicationType app_port, GNUNET_STREAM_ListenCallback listen_cb, - void *listen_cb_cls); + void *listen_cb_cls, + ...); /** @@ -234,7 +272,14 @@ GNUNET_STREAM_listen_close (struct GNUNET_STREAM_ListenSocket *lsocket); * on a stream are executed * * @param cls the closure from GNUNET_STREAM_write - * @param status the status of the stream at the time this function is called + * @param status the status of the stream at the time this function is called; + * GNUNET_STREAM_OK if writing to stream was completed successfully; + * GNUNET_STREAM_TIMEOUT if the given data is not sent successfully + * (this doesn't mean that the data is never sent, the receiver may + * have read the data but its ACKs may have been lost); + * GNUNET_STREAM_SHUTDOWN if the stream is shutdown for writing in the + * mean time; GNUNET_STREAM_SYSERR if the stream is broken and cannot + * be processed. * @param size the number of bytes written */ typedef void (*GNUNET_STREAM_CompletionContinuation) (void *cls, @@ -246,17 +291,17 @@ typedef void (*GNUNET_STREAM_CompletionContinuation) (void *cls, /** * Handle to cancel IO write operations. */ -struct GNUNET_STREAM_IOWriteHandle; +struct GNUNET_STREAM_WriteHandle; /** * Handle to cancel IO read operations. */ -struct GNUNET_STREAM_IOReadHandle; +struct GNUNET_STREAM_ReadHandle; /** * Tries to write the given data to the stream. The maximum size of data that - * can be written as part of a write operation is (64 * (64000 - sizeof (struct + * can be written per a write operation is ~ 4MB (64 * (64000 - sizeof (struct * GNUNET_STREAM_DataMessage))). If size is greater than this it is not an API * violation, however only the said number of maximum bytes will be written. * @@ -268,11 +313,12 @@ struct GNUNET_STREAM_IOReadHandle; * stream * @param write_cont_cls the closure * - * @return handle to cancel the operation; if a previous write is pending or - * the stream has been shutdown for this operation then write_cont is - * immediately called and NULL is returned. + * @return handle to cancel the operation; if a previous write is pending NULL + * is returned. If the stream has been shutdown for this operation or + * is broken then write_cont is immediately called and NULL is + * returned. */ -struct GNUNET_STREAM_IOWriteHandle * +struct GNUNET_STREAM_WriteHandle * GNUNET_STREAM_write (struct GNUNET_STREAM_Socket *socket, const void *data, size_t size, @@ -299,18 +345,20 @@ typedef size_t (*GNUNET_STREAM_DataProcessor) (void *cls, /** - * Tries to read data from the stream. + * Tries to read data from the stream. Should not be called when another read + * handle is present; the existing read handle should be canceled with + * GNUNET_STREAM_read_cancel(). Only one read handle per socket is present at + * any time * * @param socket the socket representing a stream * @param timeout the timeout period * @param proc function to call with data (once only) * @param proc_cls the closure for proc - * - * @return handle to cancel the operation; if the stream has been shutdown for - * this type of opeartion then the DataProcessor is immediately - * called with GNUNET_STREAM_SHUTDOWN as status and NULL if returned + * @return handle to cancel the operation; NULL is returned if the stream has + * been shutdown for this type of opeartion (the DataProcessor is + * immediately called with GNUNET_STREAM_SHUTDOWN as status) */ -struct GNUNET_STREAM_IOReadHandle * +struct GNUNET_STREAM_ReadHandle * GNUNET_STREAM_read (struct GNUNET_STREAM_Socket *socket, struct GNUNET_TIME_Relative timeout, GNUNET_STREAM_DataProcessor proc, @@ -332,19 +380,19 @@ GNUNET_STREAM_read (struct GNUNET_STREAM_Socket *socket, * used before shutting down transmission from our side or before closing the * socket. * - * @param ioh handle to operation to cancel + * @param wh write operation handle to cancel */ void -GNUNET_STREAM_io_write_cancel (struct GNUNET_STREAM_IOWriteHandle *iowh); +GNUNET_STREAM_write_cancel (struct GNUNET_STREAM_WriteHandle *wh); /** * Cancel pending read operation. * - * @param ioh handle to operation to cancel + * @param rh read operation handle to cancel */ void -GNUNET_STREAM_io_read_cancel (struct GNUNET_STREAM_IOReadHandle *iorh); +GNUNET_STREAM_read_cancel (struct GNUNET_STREAM_ReadHandle *rh); #if 0 diff --git a/src/include/gnunet_strings_lib.h b/src/include/gnunet_strings_lib.h index 54d2e30..64dbd1e 100644 --- a/src/include/gnunet_strings_lib.h +++ b/src/include/gnunet_strings_lib.h @@ -1,6 +1,6 @@ /* This file is part of GNUnet. - (C) 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2009 Christian Grothoff (and other contributing authors) + (C) 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2009, 2012 Christian Grothoff (and other contributing authors) GNUnet is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published @@ -75,6 +75,19 @@ GNUNET_STRINGS_fancy_time_to_relative (const char *fancy_time, struct GNUNET_TIME_Relative *rtime); +/** + * Convert a given fancy human-readable time to our internal + * representation. + * + * @param fancy_time human readable string (i.e. %Y-%m-%d %H:%M:%S) + * @param atime set to the absolute time + * @return GNUNET_OK on success, GNUNET_SYSERR on error + */ +int +GNUNET_STRINGS_fancy_time_to_absolute (const char *fancy_time, + struct GNUNET_TIME_Absolute *atime); + + /** * Convert a given filesize into a fancy human-readable format. * @@ -95,7 +108,9 @@ GNUNET_STRINGS_byte_size_fancy (unsigned long long size); */ char * GNUNET_STRINGS_conv (const char *input, size_t len, - const char *input_charset, const char *output_charset); + const char *input_charset, + const char *output_charset); + /** * Convert the len characters long character sequence @@ -108,7 +123,10 @@ GNUNET_STRINGS_conv (const char *input, size_t len, * @return the converted string (0-terminated) */ char * -GNUNET_STRINGS_to_utf8 (const char *input, size_t len, const char *charset); +GNUNET_STRINGS_to_utf8 (const char *input, + size_t len, + const char *charset); + /** * Convert the len bytes-long UTF-8 string @@ -119,7 +137,10 @@ GNUNET_STRINGS_to_utf8 (const char *input, size_t len, const char *charset); * string is returned. */ char * -GNUNET_STRINGS_from_utf8 (const char *input, size_t len, const char *charset); +GNUNET_STRINGS_from_utf8 (const char *input, + size_t len, + const char *charset); + /** * Convert the utf-8 input string to lowercase @@ -129,7 +150,8 @@ GNUNET_STRINGS_from_utf8 (const char *input, size_t len, const char *charset); * @param output output buffer */ void -GNUNET_STRINGS_utf8_tolower(const char* input, char** output); +GNUNET_STRINGS_utf8_tolower (const char* input, + char** output); /** @@ -140,7 +162,8 @@ GNUNET_STRINGS_utf8_tolower(const char* input, char** output); * @param output output buffer */ void -GNUNET_STRINGS_utf8_toupper(const char* input, char** output); +GNUNET_STRINGS_utf8_toupper (const char* input, + char** output); /** @@ -156,16 +179,14 @@ GNUNET_STRINGS_filename_expand (const char *fil); /** - * Fill a buffer of the given size with - * count 0-terminated strings (given as varargs). - * If "buffer" is NULL, only compute the amount of - * space required (sum of "strlen(arg)+1"). + * Fill a buffer of the given size with count 0-terminated strings + * (given as varargs). If "buffer" is NULL, only compute the amount + * of space required (sum of "strlen(arg)+1"). * - * Unlike using "snprintf" with "%s", this function - * will add 0-terminators after each string. The - * "GNUNET_string_buffer_tokenize" function can be - * used to parse the buffer back into individual - * strings. + * Unlike using "snprintf" with "%s", this function will add + * 0-terminators after each string. The + * "GNUNET_string_buffer_tokenize" function can be used to parse the + * buffer back into individual strings. * * @param buffer the buffer to fill with strings, can * be NULL in which case only the necessary @@ -177,15 +198,16 @@ GNUNET_STRINGS_filename_expand (const char *fil); * (or number of bytes that would have been written) */ size_t -GNUNET_STRINGS_buffer_fill (char *buffer, size_t size, unsigned int count, ...); +GNUNET_STRINGS_buffer_fill (char *buffer, + size_t size, + unsigned int count, + ...); /** - * Given a buffer of a given size, find "count" - * 0-terminated strings in the buffer and assign - * the count (varargs) of type "const char**" to the - * locations of the respective strings in the - * buffer. + * Given a buffer of a given size, find "count" 0-terminated strings + * in the buffer and assign the count (varargs) of type "const char**" + * to the locations of the respective strings in the buffer. * * @param buffer the buffer to parse * @param size size of the buffer @@ -201,24 +223,30 @@ GNUNET_STRINGS_buffer_tokenize (const char *buffer, size_t size, /** - * "man ctime_r", except for GNUnet time; also, unlike ctime, the - * return value does not include the newline character. + * "asctime", except for GNUnet time. + * This is one of the very few calls in the entire API that is + * NOT reentrant! * * @param t the absolute time to convert * @return timestamp in human-readable form */ -char * +const char * GNUNET_STRINGS_absolute_time_to_string (struct GNUNET_TIME_Absolute t); /** * Give relative time in human-readable fancy format. + * This is one of the very few calls in the entire API that is + * NOT reentrant! * * @param delta time in milli seconds + * @param do_round are we allowed to round a bit? * @return string in human-readable form */ -char * -GNUNET_STRINGS_relative_time_to_string (struct GNUNET_TIME_Relative delta); +const char * +GNUNET_STRINGS_relative_time_to_string (struct GNUNET_TIME_Relative delta, + int do_round); + /** * "man basename" @@ -251,8 +279,10 @@ GNUNET_STRINGS_get_short_name (const char *filename); * @return pointer to the next byte in 'out' or NULL on error. */ char * -GNUNET_STRINGS_data_to_string (const unsigned char *data, size_t size, - char *out, size_t out_size); +GNUNET_STRINGS_data_to_string (const unsigned char *data, + size_t size, + char *out, + size_t out_size); /** @@ -266,25 +296,12 @@ GNUNET_STRINGS_data_to_string (const unsigned char *data, size_t size, * @return GNUNET_OK on success, GNUNET_SYSERR if result has the wrong encoding */ int -GNUNET_STRINGS_string_to_data (const char *enc, size_t enclen, - unsigned char *out, size_t out_size); +GNUNET_STRINGS_string_to_data (const char *enc, + size_t enclen, + unsigned char *out, + size_t out_size); -#if 0 /* keep Emacsens' auto-indent happy */ -{ -#endif -#ifdef __cplusplus -} -#endif - -enum GNUNET_STRINGS_FilenameCheck -{ - GNUNET_STRINGS_CHECK_EXISTS = 0x00000001, - GNUNET_STRINGS_CHECK_IS_DIRECTORY = 0x00000002, - GNUNET_STRINGS_CHECK_IS_LINK = 0x00000004, - GNUNET_STRINGS_CHECK_IS_ABSOLUTE = 0x00000008 -}; - /** * Parse a path that might be an URI. * @@ -302,8 +319,9 @@ enum GNUNET_STRINGS_FilenameCheck * (if they weren't NULL). */ int -GNUNET_STRINGS_parse_uri (const char *path, char **scheme_part, - const char **path_part); +GNUNET_STRINGS_parse_uri (const char *path, + char **scheme_part, + const char **path_part); /** @@ -328,7 +346,35 @@ GNUNET_STRINGS_path_is_absolute (const char *filename, /** - * Perform checks on 'filename; + * Flags for what we should check a file for. + */ +enum GNUNET_STRINGS_FilenameCheck +{ + /** + * Check that it exists. + */ + GNUNET_STRINGS_CHECK_EXISTS = 0x00000001, + + /** + * Check that it is a directory. + */ + GNUNET_STRINGS_CHECK_IS_DIRECTORY = 0x00000002, + + /** + * Check that it is a link. + */ + GNUNET_STRINGS_CHECK_IS_LINK = 0x00000004, + + /** + * Check that the path is an absolute path. + */ + GNUNET_STRINGS_CHECK_IS_ABSOLUTE = 0x00000008 +}; + + +/** + * Perform checks on 'filename'. FIXME: some duplication with + * "GNUNET_DISK_"-APIs. We should unify those. * * @param filename file to check * @param checks checks to perform @@ -390,6 +436,35 @@ GNUNET_STRINGS_to_address_ip (const char *addr, struct sockaddr_storage *r_buf); +/** + * Returns utf-8 encoded arguments. + * Does nothing (returns a copy of argc and argv) on any platform + * other than W32. + * Returned argv has u8argv[u8argc] == NULL. + * Returned argv is a single memory block, and can be freed with a single + * GNUNET_free () call. + * + * @param argc argc (as given by main()) + * @param argv argv (as given by main()) + * @param u8argc a location to store new argc in (though it's th same as argc) + * @param u8argv a location to store new argv in + * @return GNUNET_OK on success, GNUNET_SYSERR on failure + */ +int +GNUNET_STRINGS_get_utf8_args (int argc, + char *const *argv, + int *u8argc, + char *const **u8argv); + + +#if 0 /* keep Emacsens' auto-indent happy */ +{ +#endif +#ifdef __cplusplus +} +#endif + + /* ifndef GNUNET_UTIL_STRING_H */ #endif /* end of gnunet_util_string.h */ diff --git a/src/include/gnunet_testbed_service.h b/src/include/gnunet_testbed_service.h index ab8db87..3c2d932 100644 --- a/src/include/gnunet_testbed_service.h +++ b/src/include/gnunet_testbed_service.h @@ -29,6 +29,7 @@ #define GNUNET_TESTBED_SERVICE_H #include "gnunet_util_lib.h" +#include "gnunet_testing_lib.h" #ifdef __cplusplus extern "C" @@ -49,7 +50,7 @@ struct GNUNET_TESTBED_Host; /** * Opaque handle to a peer controlled by the testbed framework. A peer runs * at a particular host. - */ + */ struct GNUNET_TESTBED_Peer; /** @@ -58,45 +59,62 @@ struct GNUNET_TESTBED_Peer; struct GNUNET_TESTBED_Operation; /** - * Handle to interact with a GNUnet testbed controller. Each controller has at - * least one master handle which is created when the controller is created; this - * master handle interacts with the controller via stdin/stdout of the controller - * process. Additionally, controllers can interact with each other (in a P2P - * fashion); those links are established via TCP/IP on the controller's service - * port. + * Handle to interact with a GNUnet testbed controller. Each + * controller has at least one master handle which is created when the + * controller is created; this master handle interacts with the + * controller process, destroying it destroys the controller (by + * closing stdin of the controller process). Additionally, + * controllers can interact with each other (in a P2P fashion); those + * links are established via TCP/IP on the controller's service port. */ struct GNUNET_TESTBED_Controller; + /** - * Handle to a large-scale testbed that is managed at a high level. + * Create a host to run peers and controllers on. + * + * @param hostname name of the host, use "NULL" for localhost + * @param username username to use for the login; may be NULL + * @param port port number to use for ssh; use 0 to let ssh decide + * @return handle to the host, NULL on error */ -struct GNUNET_TESTBED_Testbed; +struct GNUNET_TESTBED_Host * +GNUNET_TESTBED_host_create (const char *hostname, + const char *username, + uint16_t port); + /** - * Create a host to run peers and controllers on. - * + * Create a host to run peers and controllers on. This function is used + * if a peer learns about a host via IPC between controllers (and thus + * some higher-level controller has already determined the unique IDs). + * + * @param id global host ID assigned to the host; 0 is + * reserved to always mean 'localhost' * @param hostname name of the host, use "NULL" for localhost * @param username username to use for the login; may be NULL * @param port port number to use for ssh; use 0 to let ssh decide * @return handle to the host, NULL on error */ struct GNUNET_TESTBED_Host * -GNUNET_TESTBED_host_create (const char *hostname, - const char *username, - uint16_t port); +GNUNET_TESTBED_host_create_with_id (uint32_t id, + const char *hostname, + const char *username, + uint16_t port); /** * Load a set of hosts from a configuration file. * * @param filename file with the host specification - * @param hosts set to the hosts found in the file + * @param hosts set to the hosts found in the file; caller must free this if + * number of hosts returned is greater than 0 * @return number of hosts returned in 'hosts', 0 on error */ unsigned int GNUNET_TESTBED_hosts_load_from_file (const char *filename, - struct GNUNET_TESTBED_Host **hosts); + struct GNUNET_TESTBED_Host ***hosts); /** @@ -109,6 +127,68 @@ void GNUNET_TESTBED_host_destroy (struct GNUNET_TESTBED_Host *host); +/** + * The handle for whether a host is habitable or not + */ +struct GNUNET_TESTBED_HostHabitableCheckHandle; + + +/** + * Callbacks of this type are called by GNUNET_TESTBED_is_host_habitable to + * inform whether the given host is habitable or not. The Handle returned by + * GNUNET_TESTBED_is_host_habitable() is invalid after this callback is called + * + * @param cls the closure given to GNUNET_TESTBED_is_host_habitable() + * @param host the host whose status is being reported; will be NULL if the host + * given to GNUNET_TESTBED_is_host_habitable() is NULL + * @param status GNUNET_YES if it is habitable; GNUNET_NO if not + */ +typedef void (*GNUNET_TESTBED_HostHabitableCallback) (void *cls, + const struct + GNUNET_TESTBED_Host + *host, + int status); + + +/** + * Checks whether a host can be used to start testbed service + * + * @param host the host to check + * @param config the configuration handle to lookup the path of the testbed + * helper + * @param cb the callback to call to inform about habitability of the given host + * @param cb_cls the closure for the callback + * @return NULL upon any error or a handle which can be passed to + * GNUNET_TESTBED_is_host_habitable_cancel() + */ +struct GNUNET_TESTBED_HostHabitableCheckHandle * +GNUNET_TESTBED_is_host_habitable (const struct GNUNET_TESTBED_Host *host, + const struct GNUNET_CONFIGURATION_Handle + *config, + GNUNET_TESTBED_HostHabitableCallback cb, + void *cb_cls); + + +/** + * Function to cancel a request started using GNUNET_TESTBED_is_host_habitable() + * + * @param handle the habitability check handle + */ +void +GNUNET_TESTBED_is_host_habitable_cancel (struct + GNUNET_TESTBED_HostHabitableCheckHandle + *handle); + +/** + * Obtain the host's hostname. + * + * @param host handle to the host, NULL means 'localhost' + * @return hostname of the host + */ +const char * +GNUNET_TESTBED_host_get_hostname (const struct GNUNET_TESTBED_Host *host); + + /** * Enumeration with (at most 64) possible event types that * can be monitored using the testbed framework. @@ -162,13 +242,6 @@ enum GNUNET_TESTBED_PeerInformationType */ GNUNET_TESTBED_PIT_GENERIC = 0, - /** - * What host is the peer running on? Returns a 'const struct - * GNUNET_TESTBED_Host *'. Valid until - * 'GNUNET_TESTBED_operation_done' is called. - */ - GNUNET_TESTBED_PIT_HOST, - /** * What configuration is the peer using? Returns a 'const struct * GNUNET_CONFIGURATION_Handle *'. Valid until @@ -194,7 +267,7 @@ enum GNUNET_TESTBED_PeerInformationType */ struct GNUNET_TESTBED_EventInformation { - + /** * Type of the event. */ @@ -205,10 +278,10 @@ struct GNUNET_TESTBED_EventInformation */ union { - + /** * Details about peer start event. - */ + */ struct { /** @@ -221,12 +294,12 @@ struct GNUNET_TESTBED_EventInformation * Handle for the peer that was started. */ struct GNUNET_TESTBED_Peer *peer; - + } peer_start; /** * Details about peer stop event. - */ + */ struct { @@ -234,12 +307,12 @@ struct GNUNET_TESTBED_EventInformation * Handle for the peer that was started. */ struct GNUNET_TESTBED_Peer *peer; - + } peer_stop; /** * Details about connect event. - */ + */ struct { /** @@ -256,7 +329,7 @@ struct GNUNET_TESTBED_EventInformation /** * Details about disconnect event. - */ + */ struct { /** @@ -268,13 +341,13 @@ struct GNUNET_TESTBED_EventInformation * Handle for one of the disconnected peers. */ struct GNUNET_TESTBED_Peer *peer2; - + } peer_disconnect; /** * Details about an operation finished event. - */ - struct + */ + struct { /** @@ -290,57 +363,26 @@ struct GNUNET_TESTBED_EventInformation /** * Error message for the operation, NULL on success. - */ - const char *emsg; - - /** - * Peer information type; captures which of the types - * in the 'op_result' is actually in use. */ - enum GNUNET_TESTBED_PeerInformationType pit; + const char *emsg; /** - * Pointer to an operation-specific return value; NULL on error; - * can be NULL for certain operations. Valid until - * 'GNUNET_TESTBED_operation_done' is called. + * No result (NULL pointer) or generic result + * (whatever the GNUNET_TESTBED_ConnectAdapter returned). */ - union - { - /** - * No result (NULL pointer) or generic result - * (whatever the GNUNET_TESTBED_ConnectAdapter returned). - */ - void *generic; - - /** - * Identity of host running the peer. - */ - struct GNUNET_TESTBED_Host *host; - - /** - * Identity of the peer. - */ - const struct GNUNET_PeerIdentity *pid; - - /** - * Configuration of the peer. - */ - const struct GNUNET_CONFIGURATION_Handle *cfg; - - } op_result; - - } operation_finished; + void *generic; + } operation_finished; /** * Details about an testbed run completed event. - */ - struct + */ + struct { /** * Error message for the operation, NULL on success. - */ + */ const char *emsg; /** @@ -355,8 +397,8 @@ struct GNUNET_TESTBED_EventInformation * Size of the 'peers' array. */ unsigned int num_peers; - - } testbed_run_finished; + + } testbed_run_finished; } details; @@ -371,15 +413,80 @@ struct GNUNET_TESTBED_EventInformation * @param event information about the event */ typedef void (*GNUNET_TESTBED_ControllerCallback)(void *cls, - const struct GNUNET_TESTBED_EventInformation *event); + const struct GNUNET_TESTBED_EventInformation *event); + + +/** + * Opaque Handle for Controller process + */ +struct GNUNET_TESTBED_ControllerProc; + + +/** + * Callback to signal successfull startup of the controller process + * + * @param cls the closure from GNUNET_TESTBED_controller_start() + * @param cfg the configuration with which the controller has been started; + * NULL if status is not GNUNET_OK + * @param status GNUNET_OK if the startup is successfull; GNUNET_SYSERR if not, + * GNUNET_TESTBED_controller_stop() shouldn't be called in this case + */ +typedef void (*GNUNET_TESTBED_ControllerStatusCallback) (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + int status); /** - * Start a controller process using the given configuration at the + * Starts a controller process at the given host. + * + * @param trusted_ip the ip address of the controller which will be set as TRUSTED + * HOST(all connections form this ip are permitted by the testbed) when + * starting testbed controller at host. This can either be a single ip + * address or a network address in CIDR notation. + * @param host the host where the controller has to be started; NULL for + * localhost + * @param cfg template configuration to use for the remote controller; the + * remote controller will be started with a slightly modified + * configuration (port numbers, unix domain sockets and service home + * values are changed as per TESTING library on the remote host) + * @param cb function called when the controller is successfully started or + * dies unexpectedly; GNUNET_TESTBED_controller_stop shouldn't be + * called if cb is called with GNUNET_SYSERR as status. Will never be + * called in the same task as 'GNUNET_TESTBED_controller_start' + * (synchronous errors will be signalled by returning NULL). This + * parameter cannot be NULL. + * @param cls closure for above callbacks + * @return the controller process handle, NULL on errors + */ +struct GNUNET_TESTBED_ControllerProc * +GNUNET_TESTBED_controller_start (const char *trusted_ip, + struct GNUNET_TESTBED_Host *host, + const struct GNUNET_CONFIGURATION_Handle *cfg, + GNUNET_TESTBED_ControllerStatusCallback cb, + void *cls); + + +/** + * Stop the controller process (also will terminate all peers and controllers + * dependent on this controller). This function blocks until the testbed has + * been fully terminated (!). The controller status cb from + * GNUNET_TESTBED_controller_start() will not be called. + * + * @param cproc the controller process handle + */ +void +GNUNET_TESTBED_controller_stop (struct GNUNET_TESTBED_ControllerProc *cproc); + + +/** + * Connect to a controller process using the given configuration at the * given host. * * @param cfg configuration to use - * @param host host to run the controller on, NULL for 'localhost' + * @param host host to run the controller on; This should be the same host if + * the controller was previously started with + * GNUNET_TESTBED_controller_start; NULL for localhost + * @param host host where this controller is being run; * @param event_mask bit mask with set of events to call 'cc' for; * or-ed values of "1LL" shifted by the * respective 'enum GNUNET_TESTBED_EventType' @@ -389,11 +496,11 @@ typedef void (*GNUNET_TESTBED_ControllerCallback)(void *cls, * @return handle to the controller */ struct GNUNET_TESTBED_Controller * -GNUNET_TESTBED_controller_start (const struct GNUNET_CONFIGURATION_Handle *cfg, - struct GNUNET_TESTBED_Host *host, - uint64_t event_mask, - GNUNET_TESTBED_ControllerCallback cc, - void *cc_cls); +GNUNET_TESTBED_controller_connect (const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTBED_Host *host, + uint64_t event_mask, + GNUNET_TESTBED_ControllerCallback cc, + void *cc_cls); /** @@ -402,7 +509,7 @@ GNUNET_TESTBED_controller_start (const struct GNUNET_CONFIGURATION_Handle *cfg, * should not be run for each peer but instead be shared * across N peers on the specified host. This function * must be called before any peers are created at the host. - * + * * @param controller controller to configure * @param service_name name of the service to share * @param num_peers number of peers that should share one instance @@ -411,49 +518,190 @@ GNUNET_TESTBED_controller_start (const struct GNUNET_CONFIGURATION_Handle *cfg, */ void GNUNET_TESTBED_controller_configure_sharing (struct GNUNET_TESTBED_Controller *controller, - const char *service_name, - uint32_t num_peers); + const char *service_name, + uint32_t num_peers); /** * Stop the given controller (also will terminate all peers and - * controllers dependent on this controller). This function + * controllers dependent on this controller). This function * blocks until the testbed has been fully terminated (!). * * @param controller handle to controller to stop */ void -GNUNET_TESTBED_controller_stop (struct GNUNET_TESTBED_Controller *controller); - - -/** - * Create a link from a 'master' controller to a slave controller. - * Whenever the master controller is asked to start a peer at the - * given 'delegated_host', it will delegate the request to the - * specified slave controller. Note that the slave controller runs at - * the 'slave_host', which may or may not be the same host as the - * 'delegated_host' (for hierarchical delegations). The configuration - * of the slave controller is given and to be used to either create - * the slave controller or to connect to an existing slave controller - * process. 'is_subordinate' specifies if the given slave controller - * should be started and managed by the master controller, or if the - * slave already has a master and this is just a secondary master that - * is also allowed to use the existing slave. +GNUNET_TESTBED_controller_disconnect (struct GNUNET_TESTBED_Controller *controller); + + +/** + * Opaque handle for host registration + */ +struct GNUNET_TESTBED_HostRegistrationHandle; + + +/** + * Callback which will be called to after a host registration succeeded or failed + * + * @param cls the closure + * @param emsg the error message; NULL if host registration is successful + */ +typedef void (* GNUNET_TESTBED_HostRegistrationCompletion) (void *cls, + const char *emsg); + + +/** + * Register a host with the controller. This makes the controller aware of the + * host. A host should be registered at the controller before starting a + * sub-controller on that host using GNUNET_TESTBED_controller_link(). + * + * @param controller the controller handle + * @param host the host to register + * @param cc the completion callback to call to inform the status of + * registration. After calling this callback the registration handle + * will be invalid. Cannot be NULL + * @param cc_cls the closure for the cc + * @return handle to the host registration which can be used to cancel the + * registration; NULL if another registration handle is present and + * is not cancelled + */ +struct GNUNET_TESTBED_HostRegistrationHandle * +GNUNET_TESTBED_register_host (struct GNUNET_TESTBED_Controller *controller, + struct GNUNET_TESTBED_Host *host, + GNUNET_TESTBED_HostRegistrationCompletion cc, + void *cc_cls); + + +/** + * Cancel the pending registration. Note that the registration message will + * already be queued to be sent to the service, cancellation has only the + * effect that the registration completion callback for the registration is + * never called and from our perspective the host is not registered until the + * completion callback is called. + * + * @param handle the registration handle to cancel + */ +void +GNUNET_TESTBED_cancel_registration (struct GNUNET_TESTBED_HostRegistrationHandle + *handle); + + +/** + * Callback to be called when an operation is completed + * + * @param cls the callback closure from functions generating an operation + * @param op the operation that has been finished + * @param emsg error message in case the operation has failed; will be NULL if + * operation has executed successfully. + */ +typedef void (*GNUNET_TESTBED_OperationCompletionCallback) (void *cls, + struct + GNUNET_TESTBED_Operation + *op, + const char *emsg); + + +/** + * Create a link from slave controller to delegated controller. Whenever the + * master controller is asked to start a peer at the delegated controller the + * request will be routed towards slave controller (if a route exists). The + * slave controller will then route it to the delegated controller. The + * configuration of the delegated controller is given and is used to either + * create the delegated controller or to connect to an existing controller. Note + * that while starting the delegated controller the configuration will be + * modified to accommodate available free ports. the 'is_subordinate' specifies + * if the given delegated controller should be started and managed by the slave + * controller, or if the delegated controller already has a master and the slave + * controller connects to it as a non master controller. The success or failure + * of this operation will be signalled through the + * GNUNET_TESTBED_ControllerCallback() with an event of type + * GNUNET_TESTBED_ET_OPERATION_FINISHED * + * @param op_cls the operation closure for the event which is generated to + * signal success or failure of this operation * @param master handle to the master controller who creates the association - * @param delegated_host requests to which host should be delegated - * @param slave_host which host is used to run the slave controller + * @param delegated_host requests to which host should be delegated; cannot be NULL + * @param slave_host which host is used to run the slave controller; use NULL to + * make the master controller connect to the delegated host * @param slave_cfg configuration to use for the slave controller - * @param is_subordinate GNUNET_YES if the slave should be started (and stopped) - * by the master controller; GNUNET_NO if we are just - * allowed to use the slave via TCP/IP + * @param is_subordinate GNUNET_YES if the controller at delegated_host should + * be started by the slave controller; GNUNET_NO if the slave + * controller has to connect to the already started delegated + * controller via TCP/IP + * @return the operation handle */ -void -GNUNET_TESTBED_controller_link (struct GNUNET_TESTBED_Controller *master, - struct GNUNET_TESTBED_Host *delegated_host, - struct GNUNET_TESTBED_Host *slave_host, - const struct GNUNET_CONFIGURATION_Handle *slave_cfg, - int is_subordinate); +struct GNUNET_TESTBED_Operation * +GNUNET_TESTBED_controller_link (void *op_cls, + struct GNUNET_TESTBED_Controller *master, + struct GNUNET_TESTBED_Host *delegated_host, + struct GNUNET_TESTBED_Host *slave_host, + const struct GNUNET_CONFIGURATION_Handle + *slave_cfg, + int is_subordinate); + + +/** + * Same as the GNUNET_TESTBED_controller_link, however expects configuration in + * serialized and compressed + * + * @param op_cls the operation closure for the event which is generated to + * signal success or failure of this operation + * @param master handle to the master controller who creates the association + * @param delegated_host requests to which host should be delegated; cannot be NULL + * @param slave_host which host is used to run the slave controller; use NULL to + * make the master controller connect to the delegated host + * @param sxcfg serialized and compressed configuration + * @param sxcfg_size the size sxcfg + * @param scfg_size the size of uncompressed serialized configuration + * @param is_subordinate GNUNET_YES if the controller at delegated_host should + * be started by the slave controller; GNUNET_NO if the slave + * controller has to connect to the already started delegated + * controller via TCP/IP + * @return the operation handle + */ +struct GNUNET_TESTBED_Operation * +GNUNET_TESTBED_controller_link_2 (void *op_cls, + struct GNUNET_TESTBED_Controller *master, + struct GNUNET_TESTBED_Host *delegated_host, + struct GNUNET_TESTBED_Host *slave_host, + const char *sxcfg, + size_t sxcfg_size, + size_t scfg_size, + int is_subordinate); + + +/** + * Function to acquire the configuration of a running slave controller. The + * completion of the operation is signalled through the controller_cb from + * GNUNET_TESTBED_controller_connect(). If the operation is successful the + * handle to the configuration is available in the generic pointer of + * operation_finished field of struct GNUNET_TESTBED_EventInformation. + * + * @param op_cls the closure for the operation + * @param master the handle to master controller + * @param slave_host the host where the slave controller is running; the handle + * to the slave_host should remain valid until this operation is + * cancelled or marked as finished + * @return the operation handle; NULL if the slave_host is not registered at + * master + */ +struct GNUNET_TESTBED_Operation * +GNUNET_TESTBED_get_slave_config (void *op_cls, + struct GNUNET_TESTBED_Controller *master, + struct GNUNET_TESTBED_Host *slave_host); + + +/** + * Functions of this signature are called when a peer has been successfully + * created + * + * @param cls the closure from GNUNET_TESTBED_peer_create() + * @param peer the handle for the created peer; NULL on any error during + * creation + * @param emsg NULL if peer is not NULL; else MAY contain the error description + */ +typedef void (*GNUNET_TESTBED_PeerCreateCallback) (void *cls, + struct GNUNET_TESTBED_Peer *peer, + const char *emsg); /** @@ -478,48 +726,131 @@ GNUNET_TESTBED_controller_link (struct GNUNET_TESTBED_Controller *master, * 'GNUNET_TESTBED_peer_get_information'. * * @param controller controller process to use - * @param host host to run the peer on - * @param cfg configuration to use for the peer - * @return handle to the peer (actual startup will happen asynchronously) + * @param host host to run the peer on; cannot be NULL + * @param cfg Template configuration to use for the peer. Should exist until + * operation is cancelled or GNUNET_TESTBED_operation_done() is called + * @param cb the callback to call when the peer has been created + * @param cls the closure to the above callback + * @return the operation handle */ -struct GNUNET_TESTBED_Peer * +struct GNUNET_TESTBED_Operation * GNUNET_TESTBED_peer_create (struct GNUNET_TESTBED_Controller *controller, - struct GNUNET_TESTBED_Host *host, - const struct GNUNET_CONFIGURATION_Handle *cfg); + struct GNUNET_TESTBED_Host *host, + const struct GNUNET_CONFIGURATION_Handle *cfg, + GNUNET_TESTBED_PeerCreateCallback cb, + void *cls); + + +/** + * Functions of this signature are called when a peer has been successfully + * started or stopped. + * + * @param cls the closure from GNUNET_TESTBED_peer_start/stop() + * @param emsg NULL on success; otherwise an error description + */ +typedef void (*GNUNET_TESTBED_PeerChurnCallback) (void *cls, + const char *emsg); /** * Start the given peer. * + * @param op_cls the closure for this operation; will be set in + * event->details.operation_finished.op_cls when this operation fails. * @param peer peer to start + * @param pcc function to call upon completion + * @param pcc_cls closure for 'pcc' * @return handle to the operation */ struct GNUNET_TESTBED_Operation * -GNUNET_TESTBED_peer_start (struct GNUNET_TESTBED_Peer *peer); +GNUNET_TESTBED_peer_start (void *op_cls, + struct GNUNET_TESTBED_Peer *peer, + GNUNET_TESTBED_PeerChurnCallback pcc, + void *pcc_cls); /** * Stop the given peer. The handle remains valid (use - * "GNUNET_TESTBED_peer_destroy" to fully clean up the + * "GNUNET_TESTBED_peer_destroy" to fully clean up the * state of the peer). * * @param peer peer to stop + * @param pcc function to call upon completion + * @param pcc_cls closure for 'pcc' * @return handle to the operation */ struct GNUNET_TESTBED_Operation * -GNUNET_TESTBED_peer_stop (struct GNUNET_TESTBED_Peer *peer); +GNUNET_TESTBED_peer_stop (struct GNUNET_TESTBED_Peer *peer, + GNUNET_TESTBED_PeerChurnCallback pcc, + void *pcc_cls); + + +/** + * Data returned from GNUNET_TESTBED_peer_get_information + */ +struct GNUNET_TESTBED_PeerInformation +{ + /** + * Peer information type; captures which of the types + * in the 'op_result' is actually in use. + */ + enum GNUNET_TESTBED_PeerInformationType pit; + + /** + * The result of the get information operation; Choose according to the pit + */ + union + { + /** + * The configuration of the peer + */ + struct GNUNET_CONFIGURATION_Handle *cfg; + + /** + * The identity of the peer + */ + struct GNUNET_PeerIdentity *id; + } result; +}; /** - * Request information about a peer. + * Callback to be called when the requested peer information is available + * + * @param cb_cls the closure from GNUNET_TETSBED_peer_get_information() + * @param op the operation this callback corresponds to + * @param pinfo the result; will be NULL if the operation has failed + * @param emsg error message if the operation has failed; will be NULL if the + * operation is successfull + */ +typedef void (*GNUNET_TESTBED_PeerInfoCallback) (void *cb_cls, + struct GNUNET_TESTBED_Operation + *op, + const struct + GNUNET_TESTBED_PeerInformation + *pinfo, + const char *emsg); + + +/** + * Request information about a peer. The controller callback will not be called + * with event type GNUNET_TESTBED_ET_OPERATION_FINISHED when result for this + * operation is available. Instead, the GNUNET_TESTBED_PeerInfoCallback() will + * be called. * * @param peer peer to request information about * @param pit desired information + * @param cb the convenience callback to be called when results for this + * operation are available + * @param cb_cls the closure for the above callback * @return handle to the operation */ struct GNUNET_TESTBED_Operation * GNUNET_TESTBED_peer_get_information (struct GNUNET_TESTBED_Peer *peer, - enum GNUNET_TESTBED_PeerInformationType pit); + enum GNUNET_TESTBED_PeerInformationType + pit, + GNUNET_TESTBED_PeerInfoCallback cb, + void *cb_cls); /** @@ -534,7 +865,7 @@ GNUNET_TESTBED_peer_get_information (struct GNUNET_TESTBED_Peer *peer, */ struct GNUNET_TESTBED_Operation * GNUNET_TESTBED_peer_update_configuration (struct GNUNET_TESTBED_Peer *peer, - const struct GNUNET_CONFIGURATION_Handle *cfg); + const struct GNUNET_CONFIGURATION_Handle *cfg); /** @@ -557,28 +888,28 @@ enum GNUNET_TESTBED_ConnectOption * No option (not valid as an argument). */ GNUNET_TESTBED_CO_NONE = 0, - + /** - * Allow or disallow a connection between the specified peers. + * Allow or disallow a connection between the specified peers. * Followed by GNUNET_NO (int) if a connection is disallowed * or GNUNET_YES if a connection is allowed. Note that the * default (all connections allowed or disallowed) is * specified in the configuration of the controller. */ GNUNET_TESTBED_CO_ALLOW = 1, - + /** * FIXME: add (and implement) options to limit connection to * particular transports, force simulation of particular latencies * or message loss rates, or set bandwidth limitations. */ - + }; /** * Manipulate the P2P underlay topology by configuring a link - * between two peers. + * between two peers. * * @param op_cls closure argument to give with the operation event * @param p1 first peer @@ -590,15 +921,15 @@ enum GNUNET_TESTBED_ConnectOption */ struct GNUNET_TESTBED_Operation * GNUNET_TESTBED_underlay_configure_link_va (void *op_cls, - struct GNUNET_TESTBED_Peer *p1, - struct GNUNET_TESTBED_Peer *p2, - enum GNUNET_TESTBED_ConnectOption co, - va_list ap); + struct GNUNET_TESTBED_Peer *p1, + struct GNUNET_TESTBED_Peer *p2, + enum GNUNET_TESTBED_ConnectOption co, + va_list ap); /** * Manipulate the P2P underlay topology by configuring a link - * between two peers. + * between two peers. * * @param op_cls closure argument to give with the operation event * @param p1 first peer @@ -610,19 +941,21 @@ GNUNET_TESTBED_underlay_configure_link_va (void *op_cls, */ struct GNUNET_TESTBED_Operation * GNUNET_TESTBED_underlay_configure_link (void *op_cls, - struct GNUNET_TESTBED_Peer *p1, - struct GNUNET_TESTBED_Peer *p2, - enum GNUNET_TESTBED_ConnectOption co, ...); + struct GNUNET_TESTBED_Peer *p1, + struct GNUNET_TESTBED_Peer *p2, + enum GNUNET_TESTBED_ConnectOption co, ...); /** - * Topologies supported for testbeds. + * Topologies and topology options supported for testbeds. Options should always + * end with GNUNET_TESTBED_TOPOLOGY_OPTION_END */ enum GNUNET_TESTBED_TopologyOption { /** - * A clique (everyone connected to everyone else). No options. + * A clique (everyone connected to everyone else). No options. If there are N + * peers this topology results in (N * (N -1)) connections. */ GNUNET_TESTBED_TOPOLOGY_CLIQUE, @@ -649,9 +982,8 @@ enum GNUNET_TESTBED_TopologyOption GNUNET_TESTBED_TOPOLOGY_2D_TORUS, /** - * Random graph. Followed by the link density, that is the - * percentage of links present in relation to a clique - * (float). + * Random graph. Followed by the number of random links to be established + * (unsigned int) */ GNUNET_TESTBED_TOPOLOGY_ERDOS_RENYI, @@ -663,7 +995,7 @@ enum GNUNET_TESTBED_TopologyOption GNUNET_TESTBED_TOPOLOGY_INTERNAT, /** - * Scale free topology. FIXME: options? + * Scale free topology. No options. */ GNUNET_TESTBED_TOPOLOGY_SCALE_FREE, @@ -672,15 +1004,34 @@ enum GNUNET_TESTBED_TopologyOption */ GNUNET_TESTBED_TOPOLOGY_LINE, + /** + * Read a topology from a given file. Followed by the name of the file (const char *). + */ + GNUNET_TESTBED_TOPOLOGY_FROM_FILE, + /** * All peers are disconnected. No options. */ GNUNET_TESTBED_TOPOLOGY_NONE, /** - * Read a topology from a given file. Followed by the name of the file (const char *). + * The options should always end with this */ - GNUNET_TESTBED_TOPOLOGY_FROM_FILE + GNUNET_TESTBED_TOPOLOGY_OPTION_END, + + /* The following are not topologies but influence how the topology has to be + setup. These options should follow the topology specific options (if + required by the chosen topology). Note that these should be given before + GNUNET_TESTBED_TOPOLOGY_OPTION_END */ + + /** + * How many times should the failed overlay connect operations be retried + * before giving up. The default if this option is not specified is to retry + * 3 times. This option takes and unsigned integer as a parameter. Use this + * option with parameter 0 to disable retrying of failed overlay connect + * operations. + */ + GNUNET_TESTBED_TOPOLOGY_RETRY_CNT }; @@ -697,10 +1048,10 @@ enum GNUNET_TESTBED_TopologyOption */ struct GNUNET_TESTBED_Operation * GNUNET_TESTBED_underlay_configure_topology_va (void *op_cls, - unsigned int num_peers, - struct GNUNET_TESTBED_Peer **peers, - enum GNUNET_TESTBED_TopologyOption topo, - va_list ap); + unsigned int num_peers, + struct GNUNET_TESTBED_Peer **peers, + enum GNUNET_TESTBED_TopologyOption topo, + va_list ap); /** @@ -716,10 +1067,10 @@ GNUNET_TESTBED_underlay_configure_topology_va (void *op_cls, */ struct GNUNET_TESTBED_Operation * GNUNET_TESTBED_underlay_configure_topology (void *op_cls, - unsigned int num_peers, - struct GNUNET_TESTBED_Peer **peers, - enum GNUNET_TESTBED_TopologyOption topo, - ...); + unsigned int num_peers, + struct GNUNET_TESTBED_Peer **peers, + enum GNUNET_TESTBED_TopologyOption topo, + ...); /** @@ -728,6 +1079,8 @@ GNUNET_TESTBED_underlay_configure_topology (void *op_cls, * and asks 'p2' to connect to 'p1'. * * @param op_cls closure argument to give with the operation event + * @param cb the callback to call when this operation has finished + * @param cb_cls the closure for the above callback * @param p1 first peer * @param p2 second peer * @return handle to the operation, NULL if connecting these two @@ -736,8 +1089,24 @@ GNUNET_TESTBED_underlay_configure_topology (void *op_cls, */ struct GNUNET_TESTBED_Operation * GNUNET_TESTBED_overlay_connect (void *op_cls, - struct GNUNET_TESTBED_Peer *p1, - struct GNUNET_TESTBED_Peer *p2); + GNUNET_TESTBED_OperationCompletionCallback cb, + void *cb_cls, + struct GNUNET_TESTBED_Peer *p1, + struct GNUNET_TESTBED_Peer *p2); + + +/** + * Callbacks of this type are called when topology configuration is completed + * + * @param cls the operation closure given to + * GNUNET_TESTBED_overlay_configure_topology_va() and + * GNUNET_TESTBED_overlay_configure() calls + * @param nsuccess the number of successful overlay connects + * @param nfailures the number of overlay connects which failed + */ +typedef void (*GNUNET_TESTBED_TopologyCompletionCallback) (void *cls, + unsigned int nsuccess, + unsigned int nfailures); /** @@ -745,21 +1114,31 @@ GNUNET_TESTBED_overlay_connect (void *op_cls, * This function then connects the given peers in the P2P overlay * using the given topology. * - * @param op_cls closure argument to give with the operation event + * @param op_cls closure argument to give with the peer connect operation events + * generated through this function * @param num_peers number of peers in 'peers' * @param peers array of 'num_peers' with the peers to configure + * @param max_connections the maximums number of overlay connections that will + * be made to achieve the given topology + * @param comp_cb the completion callback to call when the topology generation + * is completed + * @param comp_cb_cls closure for the above completion callback * @param topo desired underlay topology to use * @param va topology-specific options - * @return handle to the operation, NULL if connecting these + * @return handle to the operation, NULL if connecting these * peers is fundamentally not possible at this time (peers - * not running or underlay disallows) + * not running or underlay disallows) or if num_peers is less than 2 */ struct GNUNET_TESTBED_Operation * GNUNET_TESTBED_overlay_configure_topology_va (void *op_cls, - unsigned int num_peers, - struct GNUNET_TESTBED_Peer *peers, - enum GNUNET_TESTBED_TopologyOption topo, - va_list va); + unsigned int num_peers, + struct GNUNET_TESTBED_Peer **peers, + unsigned int *max_connections, + GNUNET_TESTBED_TopologyCompletionCallback + comp_cb, + void *comp_cb_cls, + enum GNUNET_TESTBED_TopologyOption topo, + va_list va); /** @@ -767,28 +1146,38 @@ GNUNET_TESTBED_overlay_configure_topology_va (void *op_cls, * This function then connects the given peers in the P2P overlay * using the given topology. * - * @param op_cls closure argument to give with the operation event + * @param op_cls closure argument to give with the peer connect operation events + * generated through this function * @param num_peers number of peers in 'peers' * @param peers array of 'num_peers' with the peers to configure + * @param max_connections the maximums number of overlay connections that will + * be made to achieve the given topology + * @param comp_cb the completion callback to call when the topology generation + * is completed + * @param comp_cb_cls closure for the above completion callback * @param topo desired underlay topology to use * @param ... topology-specific options - * @return handle to the operation, NULL if connecting these + * @return handle to the operation, NULL if connecting these * peers is fundamentally not possible at this time (peers - * not running or underlay disallows) + * not running or underlay disallows) or if num_peers is less than 2 */ struct GNUNET_TESTBED_Operation * GNUNET_TESTBED_overlay_configure_topology (void *op_cls, - unsigned int num_peers, - struct GNUNET_TESTBED_Peer *peers, - enum GNUNET_TESTBED_TopologyOption topo, - ...); - + unsigned int num_peers, + struct GNUNET_TESTBED_Peer **peers, + unsigned int *max_connections, + GNUNET_TESTBED_TopologyCompletionCallback + comp_cb, + void *comp_cb_cls, + enum GNUNET_TESTBED_TopologyOption topo, + ...); /** * Ask the testbed controller to write the current overlay topology to * a file. Naturally, the file will only contain a snapshot as the * topology may evolve all the time. + * FIXME: needs continuation!? * * @param controller overlay controller to inspect * @param filename name of the file the topology should @@ -796,30 +1185,51 @@ GNUNET_TESTBED_overlay_configure_topology (void *op_cls, */ void GNUNET_TESTBED_overlay_write_topology_to_file (struct GNUNET_TESTBED_Controller *controller, - const char *filename); + const char *filename); /** * Adapter function called to establish a connection to * a service. - * + * * @param cls closure - * @param cfg configuration of the peer to connect to + * @param cfg configuration of the peer to connect to; will be available until + * GNUNET_TESTBED_operation_done() is called on the operation returned + * from GNUNET_TESTBED_service_connect() * @return service handle to return in 'op_result', NULL on error */ typedef void * (*GNUNET_TESTBED_ConnectAdapter)(void *cls, - const struct GNUNET_CONFIGURATION_Handle *cfg); + const struct GNUNET_CONFIGURATION_Handle *cfg); /** * Adapter function called to destroy a connection to * a service. - * + * * @param cls closure * @param op_result service handle returned from the connect adapter */ typedef void (*GNUNET_TESTBED_DisconnectAdapter)(void *cls, - void *op_result); + void *op_result); + + +/** + * Callback to be called when a service connect operation is completed + * + * @param cls the callback closure from functions generating an operation + * @param op the operation that has been finished + * @param ca_result the service handle returned from GNUNET_TESTBED_ConnectAdapter() + * @param emsg error message in case the operation has failed; will be NULL if + * operation has executed successfully. + */ +typedef void (*GNUNET_TESTBED_ServiceConnectCompletionCallback) (void *cls, + struct + GNUNET_TESTBED_Operation + *op, + void + *ca_result, + const char + *emsg ); /** @@ -828,14 +1238,16 @@ typedef void (*GNUNET_TESTBED_DisconnectAdapter)(void *cls, * maintain connections with other systems. The actual service * handle is then returned via the 'op_result' member in the event * callback. The 'ca' callback is used to create the connection - * when the time is right; the 'da' callback will be used to + * when the time is right; the 'da' callback will be used to * destroy the connection (upon 'GNUNET_TESTBED_operation_done'). * 'GNUNET_TESTBED_operation_cancel' can be used to abort this * operation until the event callback has been called. * - * @param op_cls closure to pass in operation event + * @param op_cls closure to pass in operation event // FIXME: didn't we say we'd no longer use the global callback for these? -CG * @param peer peer that runs the service * @param service_name name of the service to connect to + * @param cb the callback to call when this operation finishes + * @param cb_cls closure for the above callback * @param ca helper function to establish the connection * @param da helper function to close the connection * @param cada_cls closure for ca and da @@ -843,100 +1255,88 @@ typedef void (*GNUNET_TESTBED_DisconnectAdapter)(void *cls, */ struct GNUNET_TESTBED_Operation * GNUNET_TESTBED_service_connect (void *op_cls, - struct GNUNET_TESTBED_Peer *peer, - const char *service_name, - GNUNET_TESTBED_ConnectAdapter ca, - GNUNET_TESTBED_DisconnectAdapter da, - void *cada_cls); - - -/** - * Cancel a pending operation. Releases all resources - * of the operation and will ensure that no event - * is generated for the operation. Does NOT guarantee - * that the operation will be fully undone (or that - * nothing ever happened). - * - * @param operation operation to cancel - */ -void -GNUNET_TESTBED_operation_cancel (struct GNUNET_TESTBED_Operation *operation); + struct GNUNET_TESTBED_Peer *peer, + const char *service_name, + GNUNET_TESTBED_ServiceConnectCompletionCallback cb, + void *cb_cls, + GNUNET_TESTBED_ConnectAdapter ca, + GNUNET_TESTBED_DisconnectAdapter da, + void *cada_cls); /** - * Signal that the information from an operation has been fully - * processed. This function MUST be called for each event - * of type 'operation_finished' to fully remove the operation - * from the operation queue. After calling this function, the - * 'op_result' becomes invalid (!). - * - * @param operation operation to signal completion for + * This function is used to signal that the event information (struct + * GNUNET_TESTBED_EventInformation) from an operation has been fully processed + * i.e. if the event callback is ever called for this operation. If the event + * callback for this operation has not yet been called, calling this function + * cancels the operation, frees its resources and ensures the no event is + * generated with respect to this operation. Note that however cancelling an + * operation does NOT guarantee that the operation will be fully undone (or that + * nothing ever happened). + * + * This function MUST be called for every operation to fully remove the + * operation from the operation queue. After calling this function, if + * operation is completed and its event information is of type + * GNUNET_TESTBED_ET_OPERATION_FINISHED, the 'op_result' becomes invalid (!). + + * If the operation is generated from GNUNET_TESTBED_service_connect() then + * calling this function on such as operation calls the disconnect adapter if + * the connect adapter was ever called. + * + * @param operation operation to signal completion or cancellation */ void GNUNET_TESTBED_operation_done (struct GNUNET_TESTBED_Operation *operation); /** - * Configure and run a testbed using the given - * master controller on 'num_hosts' starting - * 'num_peers' using the given peer configuration. + * Callback function to process statistic values from all peers. * - * @param controller master controller for the testbed - * (must not be destroyed until after the - * testbed is destroyed). - * @param num_hosts number of hosts in 'hosts', 0 to only - * use 'localhost' - * @param hosts list of hosts to use for the testbed - * @param num_peers number of peers to start - * @param peer_cfg peer configuration template to use - * @param underlay_topology underlay topology to create - * @param va topology-specific options - * @return handle to the testbed + * @param cls closure + * @param peer the peer the statistic belong to + * @param subsystem name of subsystem that created the statistic + * @param name the name of the datum + * @param value the current value + * @param is_persistent GNUNET_YES if the value is persistent, GNUNET_NO if not + * @return GNUNET_OK to continue, GNUNET_SYSERR to abort iteration */ -struct GNUNET_TESTBED_Testbed * -GNUNET_TESTBED_create_va (struct GNUNET_TESTBED_Controller *controller, - unsigned int num_hosts, - struct GNUNET_TESTBED_Host **hosts, - unsigned int num_peers, - const struct GNUNET_CONFIGURATION_Handle *peer_cfg, - enum GNUNET_TESTBED_TopologyOption underlay_topology, - va_list va); +typedef int (*GNUNET_TESTBED_StatisticsIterator) (void *cls, + const struct GNUNET_TESTBED_Peer *peer, + const char *subsystem, + const char *name, + uint64_t value, + int is_persistent); /** - * Configure and run a testbed using the given - * master controller on 'num_hosts' starting - * 'num_peers' using the given peer configuration. + * Convenience method that iterates over all (running) peers + * and retrieves all statistics from each peer. * - * @param controller master controller for the testbed - * (must not be destroyed until after the - * testbed is destroyed). - * @param num_hosts number of hosts in 'hosts', 0 to only - * use 'localhost' - * @param hosts list of hosts to use for the testbed - * @param num_peers number of peers to start - * @param peer_cfg peer configuration template to use - * @param underlay_topology underlay topology to create - * @param ... topology-specific options + * @param num_peers number of peers to iterate over + * @param peers array of peers to iterate over + * @param proc processing function for each statistic retrieved + * @param cont continuation to call once call is completed(?) + * @param cls closure to pass to proc and cont + * @return operation handle to cancel the operation */ -struct GNUNET_TESTBED_Testbed * -GNUNET_TESTBED_create (struct GNUNET_TESTBED_Controller *controller, - unsigned int num_hosts, - struct GNUNET_TESTBED_Host **hosts, - unsigned int num_peers, - const struct GNUNET_CONFIGURATION_Handle *peer_cfg, - enum GNUNET_TESTBED_TopologyOption underlay_topology, - ...); +struct GNUNET_TESTBED_Operation * +GNUNET_TESTBED_get_statistics (unsigned int num_peers, + struct GNUNET_TESTBED_Peer **peers, + GNUNET_TESTBED_StatisticsIterator proc, + GNUNET_TESTBED_OperationCompletionCallback cont, + void *cls); /** - * Destroy a testbed. Stops all running peers and then - * destroys all peers. Does NOT destroy the master controller. + * Signature of a main function for a testcase. * - * @param testbed testbed to destroy + * @param cls closure + * @param num_peers number of peers in 'peers' + * @param peers handle to peers run in the testbed */ -void -GNUNET_TESTBED_destroy (struct GNUNET_TESTBED_Testbed *testbed); +typedef void (*GNUNET_TESTBED_TestMaster)(void *cls, + unsigned int num_peers, + struct GNUNET_TESTBED_Peer **peers); /** @@ -953,39 +1353,31 @@ GNUNET_TESTBED_destroy (struct GNUNET_TESTBED_Testbed *testbed); * @param host_filename name of the file with the 'hosts', NULL * to run everything on 'localhost' * @param cfg configuration to use (for testbed, controller and peers) - * @param num_peers number of peers to start; FIXME: maybe put that ALSO into cfg? + * @param num_peers number of peers to start; FIXME: maybe put that ALSO into + * cfg?; should be greater than 0 * @param event_mask bit mask with set of events to call 'cc' for; * or-ed values of "1LL" shifted by the * respective 'enum GNUNET_TESTBED_EventType' * (i.e. "(1LL << GNUNET_TESTBED_ET_CONNECT) || ...") - * @param cc controller callback to invoke on events + * @param cc controller callback to invoke on events; This callback is called + * for all peer start events even if GNUNET_TESTBED_ET_PEER_START isn't + * set in the event_mask as this is the only way get access to the + * handle of each peer * @param cc_cls closure for cc - * @param master task to run once the testbed is ready - * @param master_cls closure for 'task'. + * @param test_master this callback will be called once the test is ready + * @param test_master_cls closure for 'test_master'. */ void GNUNET_TESTBED_run (const char *host_filename, - const struct GNUNET_CONFIGURATION_Handle *cfg, - unsigned int num_peers, - uint64_t event_mask, - GNUNET_TESTBED_ControllerCallback cc, - void *cc_cls, - GNUNET_SCHEDULER_Task master, - void *master_cls); + const struct GNUNET_CONFIGURATION_Handle *cfg, + unsigned int num_peers, + uint64_t event_mask, + GNUNET_TESTBED_ControllerCallback cc, + void *cc_cls, + GNUNET_TESTBED_TestMaster test_master, + void *test_master_cls); -/** - * Signature of a main function for a testcase. - * - * @param cls closure - * @param num_peers number of peers in 'peers' - * @param peers handle to peers run in the testbed - */ -typedef void (*GNUNET_TESTBED_TestMaster)(void *cls, - unsigned int num_peers, - struct GNUNET_TESTBED_Peer **peers); - - /** * Convenience method for running a "simple" test on the local system * with a single call from 'main'. Underlay and overlay topology are @@ -1005,16 +1397,29 @@ typedef void (*GNUNET_TESTBED_TestMaster)(void *cls, * @param testname name of the testcase (to configure logging, etc.) * @param cfg_filename configuration filename to use * (for testbed, controller and peers) - * @param num_peers number of peers to start - * @param test_master task to run once the test is ready - * @param test_master_cls closure for 'task'. + * @param num_peers number of peers to start; should be greter than 0 + * @param event_mask bit mask with set of events to call 'cc' for; + * or-ed values of "1LL" shifted by the + * respective 'enum GNUNET_TESTBED_EventType' + * (i.e. "(1LL << GNUNET_TESTBED_ET_CONNECT) || ...") + * @param cc controller callback to invoke on events; This callback is called + * for all peer start events even if GNUNET_TESTBED_ET_PEER_START isn't + * set in the event_mask as this is the only way get access to the + * handle of each peer + * @param cc_cls closure for cc + * @param test_master this callback will be called once the test is ready + * @param test_master_cls closure for 'test_master'. + * @return GNUNET_SYSERR on error, GNUNET_OK on success */ -void +int GNUNET_TESTBED_test_run (const char *testname, - const char *cfg_filename, - unsigned int num_peers, - GNUNET_TESTBED_TestMaster test_master, - void *test_master_cls); + const char *cfg_filename, + unsigned int num_peers, + uint64_t event_mask, + GNUNET_TESTBED_ControllerCallback cc, + void *cc_cls, + GNUNET_TESTBED_TestMaster test_master, + void *test_master_cls); #if 0 /* keep Emacsens' auto-indent happy */ diff --git a/src/include/gnunet_testing_lib-new.h b/src/include/gnunet_testing_lib-new.h deleted file mode 100644 index 9b5f4c2..0000000 --- a/src/include/gnunet_testing_lib-new.h +++ /dev/null @@ -1,299 +0,0 @@ -/* - This file is part of GNUnet - (C) 2008, 2009, 2012 Christian Grothoff (and other contributing authors) - - GNUnet is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published - by the Free Software Foundation; either version 3, or (at your - option) any later version. - - GNUnet is distributed in the hope that it will be useful, but - WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - General Public License for more details. - - You should have received a copy of the GNU General Public License - along with GNUnet; see the file COPYING. If not, write to the - Free Software Foundation, Inc., 59 Temple Place - Suite 330, - Boston, MA 02111-1307, USA. - */ - -/** - * @file include/gnunet_testing_lib-new.h - * @brief convenience API for writing testcases for GNUnet; - * can start/stop one or more peers on a system; - * testing is responsible for managing private keys, - * ports and paths; it is a low-level library that - * does not support higher-level functions such as - * P2P connection, topology management or distributed - * testbed maintenance (those are in gnunet_testbed_service.h) - * @author Christian Grothoff - */ - -#ifndef GNUNET_TESTING_LIB_NEW_H -#define GNUNET_TESTING_LIB_NEW_H - -#include "gnunet_util_lib.h" -#include "gnunet_statistics_service.h" - -#ifdef __cplusplus -extern "C" -{ -#if 0 /* keep Emacsens' auto-indent happy */ -} -#endif -#endif - - -/** - * Handle for a system on which GNUnet peers are executed; - * a system is used for reserving unique paths and ports. - */ -struct GNUNET_TESTING_System; - - -/** - * Handle for a GNUnet peer controlled by testing. - */ -struct GNUNET_TESTING_Peer; - - -/** - * Create a system handle. There must only be one system - * handle per operating system. - * - * @param tmppath prefix path to use for all service homes - * @param controller hostname of the controlling host, - * service configurations are modified to allow - * control connections from this host; can be NULL - * @return handle to this system, NULL on error - */ -struct GNUNET_TESTING_System * -GNUNET_TESTING_system_create (const char *tmppath, - const char *controller); - - - -/** - * Free system resources. - * - * @param system system to be freed - * @param remove_paths should the 'tmppath' and all subdirectories - * be removed (clean up on shutdown)? - */ -void -GNUNET_TESTING_system_destroy (struct GNUNET_TESTING_System *system, - int remove_paths); - - -/** - * Testing includes a number of pre-created hostkeys for faster peer - * startup. This function loads such keys into memory from a file. - * - * @param system the testing system handle - * @param filename the path of the hostkeys file - * @return GNUNET_OK on success; GNUNET_SYSERR on error - */ -int -GNUNET_TESTING_hostkeys_load (struct GNUNET_TESTING_System *system, - const char *filename); - - -/** - * Function to remove the loaded hostkeys - * - * @param system the testing system handle - */ -void -GNUNET_TESTING_hostkeys_unload (struct GNUNET_TESTING_System *system); - - -/** - * Testing includes a number of pre-created hostkeys for - * faster peer startup. This function can be used to - * access the n-th key of those pre-created hostkeys; note - * that these keys are ONLY useful for testing and not - * secure as the private keys are part of the public - * GNUnet source code. - * - * This is primarily a helper function used internally - * by 'GNUNET_TESTING_peer_configure'. - * - * @param system the testing system handle - * @param key_number desired pre-created hostkey to obtain - * @param id set to the peer's identity (hash of the public - * key; if NULL, GNUNET_SYSERR is returned immediately - * @return GNUNET_SYSERR on error (not enough keys) - */ -int -GNUNET_TESTING_hostkey_get (const struct GNUNET_TESTING_System *system, - uint32_t key_number, - struct GNUNET_PeerIdentity *id); - - -/** - * Reserve a TCP or UDP port for a peer. - * - * @param system system to use for reservation tracking - * @param is_tcp GNUNET_YES for TCP ports, GNUNET_NO for UDP - * @return 0 if no free port was available - */ -uint16_t -GNUNET_TESTING_reserve_port (struct GNUNET_TESTING_System *system, - int is_tcp); - - -/** - * Release reservation of a TCP or UDP port for a peer - * (used during GNUNET_TESTING_peer_destroy). - * - * @param system system to use for reservation tracking - * @param is_tcp GNUNET_YES for TCP ports, GNUNET_NO for UDP - * @param port reserved port to release - */ -void -GNUNET_TESTING_release_port (struct GNUNET_TESTING_System *system, - int is_tcp, - uint16_t port); - - -/** - * Create a new configuration using the given configuration - * as a template; ports and paths will be modified to select - * available ports on the local system. If we run - * out of "*port" numbers, return SYSERR. - * - * This is primarily a helper function used internally - * by 'GNUNET_TESTING_peer_configure'. - * - * @param system system to use to coordinate resource usage - * @param cfg template configuration to update - * @return GNUNET_OK on success, GNUNET_SYSERR on error - the configuration will - * be incomplete and should not be used there upon - */ -int -GNUNET_TESTING_configuration_create (struct GNUNET_TESTING_System *system, - struct GNUNET_CONFIGURATION_Handle *cfg); -// FIXME: add dual to 'release' ports again... - - -/** - * Configure a GNUnet peer. GNUnet must be installed on the local - * system and available in the PATH. - * - * @param system system to use to coordinate resource usage - * @param cfg configuration to use; will be UPDATED (to reflect needed - * changes in port numbers and paths) - * @param key_number number of the hostkey to use for the peer - * @param id identifier for the daemon, will be set, can be NULL - * @param emsg set to error message (set to NULL on success), can be NULL - * @return handle to the peer, NULL on error - */ -struct GNUNET_TESTING_Peer * -GNUNET_TESTING_peer_configure (struct GNUNET_TESTING_System *system, - struct GNUNET_CONFIGURATION_Handle *cfg, - uint32_t key_number, - struct GNUNET_PeerIdentity *id, - char **emsg); - - -/** - * Start the peer. - * - * @param peer peer to start - * @return GNUNET_OK on success, GNUNET_SYSERR on error (i.e. peer already running) - */ -int -GNUNET_TESTING_peer_start (struct GNUNET_TESTING_Peer *peer); - - -/** - * Stop the peer. - * - * @param peer peer to stop - * @return GNUNET_OK on success, GNUNET_SYSERR on error (i.e. peer not running) - */ -int -GNUNET_TESTING_peer_stop (struct GNUNET_TESTING_Peer *peer); - - -/** - * Destroy the peer. Releases resources locked during peer configuration. - * If the peer is still running, it will be stopped AND a warning will be - * printed (users of the API should stop the peer explicitly first). - * - * @param peer peer to destroy - */ -void -GNUNET_TESTING_peer_destroy (struct GNUNET_TESTING_Peer *peer); - - -/** - * Signature of the 'main' function for a (single-peer) testcase that - * is run using 'GNUNET_TESTING_peer_run'. - * - * @param cls closure - * @param cfg configuration of the peer that was started - */ -typedef void (*GNUNET_TESTING_TestMain)(void *cls, - const struct GNUNET_CONFIGURATION_Handle *cfg); - - -/** - * Start a single peer and run a test using the testing library. - * Starts a peer using the given configuration and then invokes the - * given callback. This function ALSO initializes the scheduler loop - * and should thus be called directly from "main". The testcase - * should self-terminate by invoking 'GNUNET_SCHEDULER_shutdown'. - * - * @param tmppath path for storing temporary data for the test - * @param cfgfilename name of the configuration file to use; - * use NULL to only run with defaults - * @param tm main function of the testcase - * @param tm_cls closure for 'tm' - * @return 0 on success, 1 on error - */ -int -GNUNET_TESTING_peer_run (const char *tmppath, - const char *cfgfilename, - GNUNET_TESTING_TestMain tm, - void *tm_cls); - - - -/** - * Start a single service (no ARM, except of course if the given - * service name is 'arm') and run a test using the testing library. - * Starts a service using the given configuration and then invokes the - * given callback. This function ALSO initializes the scheduler loop - * and should thus be called directly from "main". The testcase - * should self-terminate by invoking 'GNUNET_SCHEDULER_shutdown'. - * - * This function is useful if the testcase is for a single service - * and if that service doesn't itself depend on other services. - * - * @param tmppath path for storing temporary data for the test - * @param service_name name of the service to run - * @param cfgfilename name of the configuration file to use; - * use NULL to only run with defaults - * @param tm main function of the testcase - * @param tm_cls closure for 'tm' - * @return 0 on success, 1 on error - */ -int -GNUNET_TESTING_service_run (const char *tmppath, - const char *service_name, - const char *cfgfilename, - GNUNET_TESTING_TestMain tm, - void *tm_cls); - - - -#if 0 /* keep Emacsens' auto-indent happy */ -{ -#endif -#ifdef __cplusplus -} -#endif - -#endif diff --git a/src/include/gnunet_testing_lib.h b/src/include/gnunet_testing_lib.h index b170670..04a3e99 100644 --- a/src/include/gnunet_testing_lib.h +++ b/src/include/gnunet_testing_lib.h @@ -1,6 +1,6 @@ /* This file is part of GNUnet - (C) 2008, 2009 Christian Grothoff (and other contributing authors) + (C) 2008, 2009, 2012 Christian Grothoff (and other contributing authors) GNUnet is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published @@ -20,12 +20,13 @@ /** * @file include/gnunet_testing_lib.h - * @brief convenience API for writing testcases for GNUnet - * Many testcases need to start and stop gnunetd, - * and this library is supposed to make that easier - * for TESTCASES. Normal programs should always - * use functions from gnunet_{util,arm}_lib.h. This API is - * ONLY for writing testcases! + * @brief convenience API for writing testcases for GNUnet; + * can start/stop one or more peers on a system; + * testing is responsible for managing private keys, + * ports and paths; it is a low-level library that + * does not support higher-level functions such as + * P2P connection, topology management or distributed + * testbed maintenance (those are in gnunet_testbed_service.h) * @author Christian Grothoff */ @@ -43,1207 +44,319 @@ extern "C" #endif #endif -#define HOSTKEYFILESIZE 914 +#define GNUNET_TESTING_HOSTKEYFILESIZE 914 /** - * Handle for a GNUnet daemon (technically a set of - * daemons; the handle is really for the master ARM - * daemon) started by the testing library. + * Handle for a system on which GNUnet peers are executed; + * a system is used for reserving unique paths and ports. */ -struct GNUNET_TESTING_Daemon; - -/** - * Linked list of hostnames and ports to use for starting daemons. - */ -struct GNUNET_TESTING_Host -{ - /** - * Pointer to next item in the list. - */ - struct GNUNET_TESTING_Host *next; - - /** - * Hostname to connect to. - */ - char *hostname; - - /** - * Username to use when connecting (may be null). - */ - char *username; - - /** - * Port to use for SSH connection (used for ssh - * connection forwarding, 0 to let ssh decide) - */ - uint16_t port; -}; - -/** - * Prototype of a function that will be called whenever - * a daemon was started by the testing library. - * - * @param cls closure - * @param id identifier for the daemon, NULL on error - * @param d handle for the daemon - * @param emsg error message (NULL on success) - */ -typedef void (*GNUNET_TESTING_NotifyHostkeyCreated) (void *cls, - const struct - GNUNET_PeerIdentity * id, - struct - GNUNET_TESTING_Daemon * d, - const char *emsg); - -/** - * Prototype of a function that will be called whenever - * a daemon was started by the testing library. - * - * @param cls closure - * @param id identifier for the daemon, NULL on error - * @param cfg configuration used by this daemon - * @param d handle for the daemon - * @param emsg error message (NULL on success) - */ -typedef void (*GNUNET_TESTING_NotifyDaemonRunning) (void *cls, - const struct - GNUNET_PeerIdentity * id, - const struct - GNUNET_CONFIGURATION_Handle - * cfg, - struct GNUNET_TESTING_Daemon - * d, const char *emsg); - -/** - * Handle to an entire testbed of GNUnet peers. - */ -struct GNUNET_TESTING_Testbed; - -/** - * Phases of starting GNUnet on a system. - */ -enum GNUNET_TESTING_StartPhase -{ - /** - * Copy the configuration file to the target system. - */ - SP_COPYING, - - /** - * Configuration file has been copied, generate hostkey. - */ - SP_COPIED, - - /** - * Create the hostkey for the peer. - */ - SP_HOSTKEY_CREATE, - - /** - * Hostkey generated, wait for topology to be finished. - */ - SP_HOSTKEY_CREATED, - - /** - * Topology has been created, now start ARM. - */ - SP_TOPOLOGY_SETUP, - - /** - * ARM has been started, check that it has properly daemonized and - * then try to connect to the CORE service (which should be - * auto-started by ARM). - */ - SP_START_ARMING, - - /** - * We're waiting for CORE to start. - */ - SP_START_CORE, - - /** - * CORE is up, now make sure we get the HELLO for this peer. - */ - SP_GET_HELLO, - - /** - * Core has notified us that we've established a connection to the service. - * The main FSM halts here and waits to be moved to UPDATE or CLEANUP. - */ - SP_START_DONE, - - /** - * We've been asked to terminate the instance and are now waiting for - * the remote command to stop the gnunet-arm process and delete temporary - * files. - */ - SP_SHUTDOWN_START, - - /** - * We should shutdown a *single* service via gnunet-arm. Call the dead_cb - * upon notification from gnunet-arm that the service has been stopped. - */ - SP_SERVICE_SHUTDOWN_START, - - /** - * We should start a *single* service via gnunet-arm. Call the daemon cb - * upon notification from gnunet-arm that the service has been started. - */ - SP_SERVICE_START, - - /** - * We've received a configuration update and are currently waiting for - * the copy process for the update to complete. Once it is, we will - * return to "SP_START_DONE" (and rely on ARM to restart all affected - * services). - */ - SP_CONFIG_UPDATE -}; - -/** - * Prototype of a function that will be called when a - * particular operation was completed the testing library. - * - * @param cls closure - * @param emsg NULL on success - */ -typedef void (*GNUNET_TESTING_NotifyCompletion) (void *cls, const char *emsg); - -/** - * Prototype of a function that will be called with the - * number of connections created for a particular topology. - * - * @param cls closure - * @param num_connections the number of connections created - */ -typedef void (*GNUNET_TESTING_NotifyConnections) (void *cls, - unsigned int num_connections); - -/** - * Handle for a GNUnet daemon (technically a set of - * daemons; the handle is really for the master ARM - * daemon) started by the testing library. - */ -struct GNUNET_TESTING_Daemon -{ - /** - * Our configuration. - */ - struct GNUNET_CONFIGURATION_Handle *cfg; - - /** - * At what time to give up starting the peer - */ - struct GNUNET_TIME_Absolute max_timeout; - - /** - * Host to run GNUnet on. - */ - char *hostname; - - /** - * Port to use for ssh, NULL to let system choose default. - */ - char *ssh_port_str; - - /** - * Result of GNUNET_i2s of this peer, - * for printing - */ - char *shortname; - - /** - * Username we are using. - */ - char *username; - - /** - * Name of the configuration file - */ - char *cfgfile; - - /** - * Callback to inform initiator that the peer's - * hostkey has been created. - */ - GNUNET_TESTING_NotifyHostkeyCreated hostkey_callback; - - /** - * Closure for hostkey creation callback. - */ - void *hostkey_cls; - - /** - * Function to call when the peer is running. - */ - GNUNET_TESTING_NotifyDaemonRunning cb; - - /** - * Closure for cb. - */ - void *cb_cls; - - /** - * Arguments from "daemon_stop" call. - */ - GNUNET_TESTING_NotifyCompletion dead_cb; - - /** - * Closure for 'dead_cb'. - */ - void *dead_cb_cls; - - /** - * Arguments from "daemon_stop" call. - */ - GNUNET_TESTING_NotifyCompletion update_cb; - - /** - * Closure for 'update_cb'. - */ - void *update_cb_cls; - - /** - * PID of the process we used to run gnunet-arm or SSH to start the peer. - */ - struct GNUNET_OS_Process *proc_arm_start; - - /** - * PID of the process we used to run gnunet-arm or SSH to stop the peer. - */ - struct GNUNET_OS_Process *proc_arm_stop; - - /** - * PID of the process we used to run gnunet-arm or SSH to manage services at the peer. - */ - struct GNUNET_OS_Process *proc_arm_srv_start; - - /** - * PID of the process we used to run gnunet-arm or SSH to manage services at the peer. - */ - struct GNUNET_OS_Process *proc_arm_srv_stop; - - /** - * PID of the process we used to run copy files - */ - struct GNUNET_OS_Process *proc_arm_copying; - - /** - * PID of the process we used to run gnunet-peerinfo. - */ - struct GNUNET_OS_Process *proc_arm_peerinfo; - - /** - * Handle to the server. - */ - struct GNUNET_CORE_Handle *server; - - /** - * Handle to the transport service of this peer - */ - struct GNUNET_TRANSPORT_Handle *th; - - /** - * Handle for getting HELLOs from transport - */ - struct GNUNET_TRANSPORT_GetHelloHandle *ghh; - - /** - * HELLO message for this peer - */ - struct GNUNET_HELLO_Message *hello; - - /** - * Handle to a pipe for reading the hostkey. - */ - struct GNUNET_DISK_PipeHandle *pipe_stdout; - - /** - * Currently, a single char * pointing to a service - * that has been churned off. - * - * FIXME: make this a linked list of services that have been churned off!!! - */ - char *churned_services; - - /** - * ID of the current task. - */ - GNUNET_SCHEDULER_TaskIdentifier task; - - /** - * Identity of this peer (once started). - */ - struct GNUNET_PeerIdentity id; - - /** - * Flag to indicate that we've already been asked - * to terminate (but could not because some action - * was still pending). - */ - int dead; - - /** - * GNUNET_YES if the hostkey has been created - * for this peer, GNUNET_NO otherwise. - */ - int have_hostkey; - - /** - * In which phase are we during the start of - * this process? - */ - enum GNUNET_TESTING_StartPhase phase; - - /** - * Current position in 'hostkeybuf' (for reading from gnunet-peerinfo) - */ - unsigned int hostkeybufpos; - - /** - * Set to GNUNET_YES once the peer is up. - */ - int running; - - /** - * Used to tell shutdown not to remove configuration for the peer - * (if it's going to be restarted later) - */ - int churn; - - /** - * Output from gnunet-peerinfo is read into this buffer. - */ - char hostkeybuf[105]; - -}; +struct GNUNET_TESTING_System; /** - * Handle to a group of GNUnet peers. + * Handle for a GNUnet peer controlled by testing. */ -struct GNUNET_TESTING_PeerGroup; +struct GNUNET_TESTING_Peer; /** - * Prototype of a function that will be called whenever - * two daemons are connected by the testing library. + * Create a system handle. There must only be one system handle per operating + * system. Uses a default range for allowed ports. Ports are still tested for + * availability. * - * @param cls closure - * @param first peer id for first daemon - * @param second peer id for the second daemon - * @param distance distance between the connected peers - * @param first_cfg config for the first daemon - * @param second_cfg config for the second daemon - * @param first_daemon handle for the first daemon - * @param second_daemon handle for the second daemon - * @param emsg error message (NULL on success) + * @param testdir only the directory name without any path. This is used for all + * service homes; the directory will be created in a temporary location + * depending on the underlying OS + * @param trusted_ip the ip address which will be set as TRUSTED HOST in all + * service configurations generated to allow control connections from + * this ip. This can either be a single ip address or a network address + * in CIDR notation. + * @param hostname the hostname of the system we are using for testing; NULL for + * localhost + * @return handle to this system, NULL on error */ -typedef void (*GNUNET_TESTING_NotifyConnection) (void *cls, - const struct - GNUNET_PeerIdentity * first, - const struct - GNUNET_PeerIdentity * second, - uint32_t distance, - const struct - GNUNET_CONFIGURATION_Handle * - first_cfg, - const struct - GNUNET_CONFIGURATION_Handle * - second_cfg, - struct GNUNET_TESTING_Daemon * - first_daemon, - struct GNUNET_TESTING_Daemon * - second_daemon, - const char *emsg); +struct GNUNET_TESTING_System * +GNUNET_TESTING_system_create (const char *testdir, + const char *trusted_ip, + const char *hostname); /** - * Prototype of a callback function indicating that two peers - * are currently connected. + * Create a system handle. There must only be one system + * handle per operating system. Use this function directly + * if multiple system objects are created for the same host + * (only really useful when testing --- or to make the port + * range configureable). * - * @param cls closure - * @param first peer id for first daemon - * @param second peer id for the second daemon - * @param distance distance between the connected peers - * @param emsg error message (NULL on success) + * @param testdir only the directory name without any path. This is used for + * all service homes; the directory will be created in a temporary + * location depending on the underlying OS + * @param trusted_ip the ip address which will be set as TRUSTED HOST in all + * service configurations generated to allow control connections from + * this ip. This can either be a single ip address or a network address + * in CIDR notation. + * @param hostname the hostname of the system we are using for testing; NULL for + * localhost + * @param lowport lowest port number this system is allowed to allocate (inclusive) + * @param highport highest port number this system is allowed to allocate (exclusive) + * @return handle to this system, NULL on error */ -typedef void (*GNUNET_TESTING_NotifyTopology) (void *cls, - const struct GNUNET_PeerIdentity - * first, - const struct GNUNET_PeerIdentity - * second, const char *emsg); - +struct GNUNET_TESTING_System * +GNUNET_TESTING_system_create_with_portrange (const char *testdir, + const char *trusted_ip, + const char *hostname, + uint16_t lowport, + uint16_t highport); -/** - * Starts a GNUnet daemon. GNUnet must be installed on the target - * system and available in the PATH. The machine must furthermore be - * reachable via "ssh" (unless the hostname is "NULL") without the - * need to enter a password. - * - * @param cfg configuration to use - * @param timeout how long to wait starting up peers - * @param pretend GNUNET_YES to set up files but not start peer GNUNET_NO - * to really start the peer (default) - * @param hostname name of the machine where to run GNUnet - * (use NULL for localhost). - * @param ssh_username ssh username to use when connecting to hostname - * @param sshport port to pass to ssh process when connecting to hostname - * @param hostkey pointer to a hostkey to be written to disk (instead of being generated) - * @param hostkey_callback function to call once the hostkey has been - * generated for this peer, but it hasn't yet been started - * (NULL to start immediately, otherwise waits on GNUNET_TESTING_daemon_continue_start) - * @param hostkey_cls closure for hostkey callback - * @param cb function to call once peer is up, or failed to start - * @param cb_cls closure for cb - * @return handle to the daemon (actual start will be completed asynchronously) - */ -struct GNUNET_TESTING_Daemon * -GNUNET_TESTING_daemon_start (const struct GNUNET_CONFIGURATION_Handle *cfg, - struct GNUNET_TIME_Relative timeout, int pretend, - const char *hostname, const char *ssh_username, - uint16_t sshport, const char *hostkey, - GNUNET_TESTING_NotifyHostkeyCreated - hostkey_callback, void *hostkey_cls, - GNUNET_TESTING_NotifyDaemonRunning cb, - void *cb_cls); /** - * Continues GNUnet daemon startup when user wanted to be notified - * once a hostkey was generated (for creating friends files, blacklists, - * etc.). + * Free system resources. * - * @param daemon the daemon to finish starting + * @param system system to be freed + * @param remove_paths should the 'testdir' and all subdirectories + * be removed (clean up on shutdown)? */ void -GNUNET_TESTING_daemon_continue_startup (struct GNUNET_TESTING_Daemon *daemon); +GNUNET_TESTING_system_destroy (struct GNUNET_TESTING_System *system, + int remove_paths); /** - * Check whether the given daemon is running. + * Testing includes a number of pre-created hostkeys for + * faster peer startup. This function can be used to + * access the n-th key of those pre-created hostkeys; note + * that these keys are ONLY useful for testing and not + * secure as the private keys are part of the public + * GNUnet source code. * - * @param daemon the daemon to check - * @return GNUNET_YES if the daemon is up, GNUNET_NO if the - * daemon is down, GNUNET_SYSERR on error. - */ -int -GNUNET_TESTING_test_daemon_running (struct GNUNET_TESTING_Daemon *daemon); - - -/** - * Obtain the peer identity of the peer with the given configuration - * handle. This function reads the private key of the peer, obtains - * the public key and hashes it. - * - * @param cfg configuration of the peer - * @param pid where to store the peer identity - * @return GNUNET_OK on success, GNUNET_SYSERR on failure - */ -int -GNUNET_TESTING_get_peer_identity (const struct GNUNET_CONFIGURATION_Handle *cfg, - struct GNUNET_PeerIdentity *pid); - - -/** - * Restart (stop and start) a GNUnet daemon. + * This is primarily a helper function used internally + * by 'GNUNET_TESTING_peer_configure'. * - * @param d the daemon that should be restarted - * @param cb function called once the daemon is (re)started - * @param cb_cls closure for cb + * @param system the testing system handle + * @param key_number desired pre-created hostkey to obtain + * @param id set to the peer's identity (hash of the public + * key; if NULL, GNUNET_SYSERR is returned immediately + * @return NULL on error (not enough keys) */ -void -GNUNET_TESTING_daemon_restart (struct GNUNET_TESTING_Daemon *d, - GNUNET_TESTING_NotifyDaemonRunning cb, - void *cb_cls); +struct GNUNET_CRYPTO_RsaPrivateKey * +GNUNET_TESTING_hostkey_get (const struct GNUNET_TESTING_System *system, + uint32_t key_number, + struct GNUNET_PeerIdentity *id); /** - * Start a peer that has previously been stopped using the daemon_stop - * call (and files weren't deleted and the allow restart flag) + * Reserve a TCP or UDP port for a peer. * - * @param daemon the daemon to start (has been previously stopped) - * @param timeout how long to wait for restart - * @param cb the callback for notification when the peer is running - * @param cb_cls closure for the callback + * @param system system to use for reservation tracking + * @param is_tcp GNUNET_YES for TCP ports, GNUNET_NO for UDP + * @return 0 if no free port was available */ -void -GNUNET_TESTING_daemon_start_stopped (struct GNUNET_TESTING_Daemon *daemon, - struct GNUNET_TIME_Relative timeout, - GNUNET_TESTING_NotifyDaemonRunning cb, - void *cb_cls); +uint16_t +GNUNET_TESTING_reserve_port (struct GNUNET_TESTING_System *system, + int is_tcp); /** - * Starts a GNUnet daemon's service. + * Release reservation of a TCP or UDP port for a peer + * (used during GNUNET_TESTING_peer_destroy). * - * @param d the daemon for which the service should be started - * @param service the name of the service to start - * @param timeout how long to wait for process for startup - * @param cb function called once gnunet-arm returns - * @param cb_cls closure for cb + * @param system system to use for reservation tracking + * @param is_tcp GNUNET_YES for TCP ports, GNUNET_NO for UDP + * @param port reserved port to release */ void -GNUNET_TESTING_daemon_start_service (struct GNUNET_TESTING_Daemon *d, - const char *service, - struct GNUNET_TIME_Relative timeout, - GNUNET_TESTING_NotifyDaemonRunning cb, - void *cb_cls); +GNUNET_TESTING_release_port (struct GNUNET_TESTING_System *system, + int is_tcp, + uint16_t port); /** - * Starts a GNUnet daemon's service which has been previously turned off. + * Create a new configuration using the given configuration as a template; + * ports and paths will be modified to select available ports on the local + * system. The default configuration will be available in PATHS section under + * the option DEFAULTCONFIG after the call. SERVICE_HOME is also set in PATHS + * section to the temporary directory specific to this configuration. If we run + * out of "*port" numbers, return SYSERR. * - * @param d the daemon for which the service should be started - * @param service the name of the service to start - * @param timeout how long to wait for process for startup - * @param cb function called once gnunet-arm returns - * @param cb_cls closure for cb - */ -void -GNUNET_TESTING_daemon_start_stopped_service (struct GNUNET_TESTING_Daemon *d, - char *service, - struct GNUNET_TIME_Relative - timeout, - GNUNET_TESTING_NotifyDaemonRunning - cb, void *cb_cls); - - -/** - * Get a certain testing daemon handle. + * This is primarily a helper function used internally + * by 'GNUNET_TESTING_peer_configure'. * - * @param pg handle to the set of running peers - * @param position the number of the peer to return + * @param system system to use to coordinate resource usage + * @param cfg template configuration to update + * @return GNUNET_OK on success, GNUNET_SYSERR on error - the configuration will + * be incomplete and should not be used there upon */ -struct GNUNET_TESTING_Daemon * -GNUNET_TESTING_daemon_get (struct GNUNET_TESTING_PeerGroup *pg, - unsigned int position); - - -/** - * Get a daemon by peer identity, so callers can - * retrieve the daemon without knowing it's offset. - * - * @param pg the peer group to retrieve the daemon from - * @param peer_id the peer identity of the daemon to retrieve - * - * @return the daemon on success, or NULL if no such peer identity is found - */ -struct GNUNET_TESTING_Daemon * -GNUNET_TESTING_daemon_get_by_id (struct GNUNET_TESTING_PeerGroup *pg, - const struct GNUNET_PeerIdentity *peer_id); - - -/** - * Stops a GNUnet daemon. - * - * @param d the daemon that should be stopped - * @param timeout how long to wait for process for shutdown to complete - * @param cb function called once the daemon was stopped - * @param cb_cls closure for cb - * @param delete_files GNUNET_YES to remove files, GNUNET_NO - * to leave them (i.e. for restarting at a later time, - * or logfile inspection once finished) - * @param allow_restart GNUNET_YES to restart peer later (using this API) - * GNUNET_NO to kill off and clean up for good - */ -void -GNUNET_TESTING_daemon_stop (struct GNUNET_TESTING_Daemon *d, - struct GNUNET_TIME_Relative timeout, - GNUNET_TESTING_NotifyCompletion cb, void *cb_cls, - int delete_files, int allow_restart); - - - -/** - * Create a new configuration using the given configuration - * as a template; however, each PORT in the existing cfg - * must be renumbered by incrementing "*port". If we run - * out of "*port" numbers, return NULL. - * - * @param cfg template configuration - * @param off the current peer offset - * @param port port numbers to use, update to reflect - * port numbers that were used - * @param upnum number to make unix domain socket names unique - * @param hostname hostname of the controlling host, to allow control connections from - * @param fdnum number used to offset the unix domain socket for grouped processes - * (such as statistics or peerinfo, which can be shared among others) - * - * @return new configuration, NULL on error - */ -struct GNUNET_CONFIGURATION_Handle * -GNUNET_TESTING_create_cfg (const struct GNUNET_CONFIGURATION_Handle *cfg, uint32_t off, - uint16_t * port, uint32_t * upnum, const char *hostname, - uint32_t * fdnum); - -/** - * Changes the configuration of a GNUnet daemon. - * - * @param d the daemon that should be modified - * @param cfg the new configuration for the daemon - * @param cb function called once the configuration was changed - * @param cb_cls closure for cb - */ -void -GNUNET_TESTING_daemon_reconfigure (struct GNUNET_TESTING_Daemon *d, - struct GNUNET_CONFIGURATION_Handle *cfg, - GNUNET_TESTING_NotifyCompletion cb, - void *cb_cls); - - -/** - * Stops a single service of a GNUnet daemon. Used like daemon_stop, - * only doesn't stop the entire peer in any case. If the service - * is not currently running, this call is likely to fail after - * timeout! - * - * @param d the daemon that should be stopped - * @param service the name of the service to stop - * @param timeout how long to wait for process for shutdown to complete - * @param cb function called once the service was stopped - * @param cb_cls closure for cb - */ -void -GNUNET_TESTING_daemon_stop_service (struct GNUNET_TESTING_Daemon *d, - const char *service, - struct GNUNET_TIME_Relative timeout, - GNUNET_TESTING_NotifyCompletion cb, - void *cb_cls); - - -/** - * Read a testing hosts file based on a configuration. - * Returns a DLL of hosts (caller must free!) on success - * or NULL on failure. - * - * @param cfg a configuration with a testing section - * - * @return DLL of hosts on success, NULL on failure - */ -struct GNUNET_TESTING_Host * -GNUNET_TESTING_hosts_load (const struct GNUNET_CONFIGURATION_Handle *cfg); - - -/** - * Start count gnunet instances with the same set of transports and - * applications. The port numbers (any option called "PORT") will be - * adjusted to ensure that no two peers running on the same system - * have the same port(s) in their respective configurations. - * - * @param cfg configuration template to use - * @param total number of daemons to start - * @param max_concurrent_connections for testing, how many peers can -* we connect to simultaneously - * @param max_concurrent_ssh when starting with ssh, how many ssh - * connections will we allow at once (based on remote hosts allowed!) - * @param timeout total time allowed for peers to start - * @param hostkey_callback function to call on each peers hostkey generation - * if NULL, peers will be started by this call, if non-null, - * GNUNET_TESTING_daemons_continue_startup must be called after - * successful hostkey generation - * @param hostkey_cls closure for hostkey callback - * @param cb function to call on each daemon that was started - * @param cb_cls closure for cb - * @param connect_callback function to call each time two hosts are connected - * @param connect_callback_cls closure for connect_callback - * @param hostnames linked list of host structs to use to start peers on - * (NULL to run on localhost only) - * - * @return NULL on error, otherwise handle to control peer group - */ -struct GNUNET_TESTING_PeerGroup * -GNUNET_TESTING_daemons_start (const struct GNUNET_CONFIGURATION_Handle *cfg, - unsigned int total, - unsigned int max_concurrent_connections, - unsigned int max_concurrent_ssh, - struct GNUNET_TIME_Relative timeout, - GNUNET_TESTING_NotifyHostkeyCreated - hostkey_callback, void *hostkey_cls, - GNUNET_TESTING_NotifyDaemonRunning cb, - void *cb_cls, - GNUNET_TESTING_NotifyConnection connect_callback, - void *connect_callback_cls, - const struct GNUNET_TESTING_Host *hostnames); - - -/** - * Function which continues a peer group starting up - * after successfully generating hostkeys for each peer. - * - * @param pg the peer group to continue starting - */ -void -GNUNET_TESTING_daemons_continue_startup (struct GNUNET_TESTING_PeerGroup *pg); - - -/** - * Handle for an active request to connect two peers. - */ -struct GNUNET_TESTING_ConnectContext; - - -/** - * Establish a connection between two GNUnet daemons. The daemons - * must both be running and not be stopped until either the - * 'cb' callback is called OR the connection request has been - * explicitly cancelled. - * - * @param d1 handle for the first daemon - * @param d2 handle for the second daemon - * @param timeout how long is the connection attempt - * allowed to take? - * @param max_connect_attempts how many times should we try to reconnect - * (within timeout) - * @param send_hello GNUNET_YES to send the HELLO, GNUNET_NO to assume - * the HELLO has already been exchanged - * @param cb function to call at the end - * @param cb_cls closure for cb - * @return handle to cancel the request, NULL on error - */ -struct GNUNET_TESTING_ConnectContext * -GNUNET_TESTING_daemons_connect (struct GNUNET_TESTING_Daemon *d1, - struct GNUNET_TESTING_Daemon *d2, - struct GNUNET_TIME_Relative timeout, - unsigned int max_connect_attempts, - int send_hello, - GNUNET_TESTING_NotifyConnection cb, - void *cb_cls); - - - -/** - * Cancel an attempt to connect two daemons. - * - * @param cc connect context - */ -void -GNUNET_TESTING_daemons_connect_cancel (struct GNUNET_TESTING_ConnectContext - *cc); - +int +GNUNET_TESTING_configuration_create (struct GNUNET_TESTING_System *system, + struct GNUNET_CONFIGURATION_Handle *cfg); +// FIXME: add dual to 'release' ports again... /** - * Restart all peers in the given group. + * Configure a GNUnet peer. GNUnet must be installed on the local + * system and available in the PATH. * - * @param pg the handle to the peer group - * @param callback function to call on completion (or failure) - * @param callback_cls closure for the callback function + * @param system system to use to coordinate resource usage + * @param cfg configuration to use; will be UPDATED (to reflect needed + * changes in port numbers and paths) + * @param key_number number of the hostkey to use for the peer + * @param id identifier for the daemon, will be set, can be NULL + * @param emsg set to freshly allocated error message (set to NULL on success), + * can be NULL + * @return handle to the peer, NULL on error */ -void -GNUNET_TESTING_daemons_restart (struct GNUNET_TESTING_PeerGroup *pg, - GNUNET_TESTING_NotifyCompletion callback, - void *callback_cls); +struct GNUNET_TESTING_Peer * +GNUNET_TESTING_peer_configure (struct GNUNET_TESTING_System *system, + struct GNUNET_CONFIGURATION_Handle *cfg, + uint32_t key_number, + struct GNUNET_PeerIdentity *id, + char **emsg); /** - * Shutdown all peers started in the given group. + * Obtain the peer identity from a peer handle. * - * @param pg handle to the peer group - * @param timeout how long to wait for shutdown - * @param cb callback to notify upon success or failure - * @param cb_cls closure for cb + * @param peer peer handle for which we want the peer's identity + * @param id identifier for the daemon, will be set */ void -GNUNET_TESTING_daemons_stop (struct GNUNET_TESTING_PeerGroup *pg, - struct GNUNET_TIME_Relative timeout, - GNUNET_TESTING_NotifyCompletion cb, void *cb_cls); +GNUNET_TESTING_peer_get_identity (const struct GNUNET_TESTING_Peer *peer, + struct GNUNET_PeerIdentity *id); /** - * Count the number of running peers. - * - * @param pg handle for the peer group + * Start the peer. * - * @return the number of currently running peers in the peer group + * @param peer peer to start + * @return GNUNET_OK on success, GNUNET_SYSERR on error (i.e. peer already running) */ -unsigned int -GNUNET_TESTING_daemons_running (struct GNUNET_TESTING_PeerGroup *pg); - - -/** - * Simulate churn by stopping some peers (and possibly - * re-starting others if churn is called multiple times). This - * function can only be used to create leave-join churn (peers "never" - * leave for good). First "voff" random peers that are currently - * online will be taken offline; then "von" random peers that are then - * offline will be put back online. No notifications will be - * generated for any of these operations except for the callback upon - * completion. Note that the implementation is at liberty to keep - * the ARM service itself (but none of the other services or daemons) - * running even though the "peer" is being varied offline. - * - * @param pg handle for the peer group - * @param service the service to churn on/off, NULL for all - * @param voff number of peers that should go offline - * @param von number of peers that should come back online; - * must be zero on first call (since "testbed_start" - * always starts all of the peers) - * @param timeout how long to wait for operations to finish before - * giving up - * @param cb function to call at the end - * @param cb_cls closure for cb - */ -void -GNUNET_TESTING_daemons_churn (struct GNUNET_TESTING_PeerGroup *pg, - char *service, unsigned int voff, - unsigned int von, - struct GNUNET_TIME_Relative timeout, - GNUNET_TESTING_NotifyCompletion cb, void *cb_cls); - - -/** - * Start a given service for each of the peers in the peer group. - * - * @param pg handle for the peer group - * @param service the service to start - * @param timeout how long to wait for operations to finish before - * giving up - * @param cb function to call once finished - * @param cb_cls closure for cb - * - */ -void -GNUNET_TESTING_daemons_start_service (struct GNUNET_TESTING_PeerGroup *pg, - char *service, - struct GNUNET_TIME_Relative timeout, - GNUNET_TESTING_NotifyCompletion cb, - void *cb_cls); +int +GNUNET_TESTING_peer_start (struct GNUNET_TESTING_Peer *peer); /** - * Callback function to process statistic values. + * Stop the peer. * - * @param cls closure - * @param peer the peer the statistics belong to - * @param subsystem name of subsystem that created the statistic - * @param name the name of the datum - * @param value the current value - * @param is_persistent GNUNET_YES if the value is persistent, GNUNET_NO if not - * @return GNUNET_OK to continue, GNUNET_SYSERR to abort iteration + * @param peer peer to stop + * @return GNUNET_OK on success, GNUNET_SYSERR on error (i.e. peer not running) */ -typedef int (*GNUNET_TESTING_STATISTICS_Iterator) (void *cls, - const struct - GNUNET_PeerIdentity * peer, - const char *subsystem, - const char *name, - uint64_t value, - int is_persistent); +int +GNUNET_TESTING_peer_stop (struct GNUNET_TESTING_Peer *peer); /** - * Iterate over all (running) peers in the peer group, retrieve - * all statistics from each. + * Destroy the peer. Releases resources locked during peer configuration. + * If the peer is still running, it will be stopped AND a warning will be + * printed (users of the API should stop the peer explicitly first). * - * @param pg the peergroup to iterate statistics of - * @param cont continuation to call once call is completed(?) - * @param proc processing function for each statistic retrieved - * @param cls closure to pass to proc + * @param peer peer to destroy */ void -GNUNET_TESTING_get_statistics (struct GNUNET_TESTING_PeerGroup *pg, - GNUNET_STATISTICS_Callback cont, - GNUNET_TESTING_STATISTICS_Iterator proc, - void *cls); +GNUNET_TESTING_peer_destroy (struct GNUNET_TESTING_Peer *peer); /** - * Topologies supported for testbeds. - */ -enum GNUNET_TESTING_Topology -{ - /** - * A clique (everyone connected to everyone else). - */ - GNUNET_TESTING_TOPOLOGY_CLIQUE, - - /** - * Small-world network (2d torus plus random links). - */ - GNUNET_TESTING_TOPOLOGY_SMALL_WORLD, - - /** - * Small-world network (ring plus random links). - */ - GNUNET_TESTING_TOPOLOGY_SMALL_WORLD_RING, - - /** - * Ring topology. - */ - GNUNET_TESTING_TOPOLOGY_RING, - - /** - * 2-d torus. - */ - GNUNET_TESTING_TOPOLOGY_2D_TORUS, - - /** - * Random graph. - */ - GNUNET_TESTING_TOPOLOGY_ERDOS_RENYI, - - /** - * Certain percentage of peers are unable to communicate directly - * replicating NAT conditions - */ - GNUNET_TESTING_TOPOLOGY_INTERNAT, - - /** - * Scale free topology. - */ - GNUNET_TESTING_TOPOLOGY_SCALE_FREE, - - /** - * Straight line topology. - */ - GNUNET_TESTING_TOPOLOGY_LINE, - - /** - * All peers are disconnected. - */ - GNUNET_TESTING_TOPOLOGY_NONE, - - /** - * Read a topology from a given file. - */ - GNUNET_TESTING_TOPOLOGY_FROM_FILE -}; - -/** - * Options for connecting a topology. - */ -enum GNUNET_TESTING_TopologyOption -{ - /** - * Try to connect all peers specified in the topology. - */ - GNUNET_TESTING_TOPOLOGY_OPTION_ALL, - - /** - * Choose a random subset of connections to create. - */ - GNUNET_TESTING_TOPOLOGY_OPTION_RANDOM, - - /** - * Create at least X connections for each peer. - */ - GNUNET_TESTING_TOPOLOGY_OPTION_MINIMUM, - - /** - * Using a depth first search, create one connection - * per peer. If any are missed (graph disconnected) - * start over at those peers until all have at least one - * connection. - */ - GNUNET_TESTING_TOPOLOGY_OPTION_DFS, - - /** - * Find the N closest peers to each allowed peer in the - * topology and make sure a connection to those peers - * exists in the connect topology. - */ - GNUNET_TESTING_TOPOLOGY_OPTION_ADD_CLOSEST, - - /** - * No options specified. - */ - GNUNET_TESTING_TOPOLOGY_OPTION_NONE -}; - - -/** - * Get a topology from a string input. + * Sends SIGTERM to the peer's main process * - * @param topology where to write the retrieved topology - * @param topology_string The string to attempt to - * get a configuration value from - * @return GNUNET_YES if topology string matched a - * known topology, GNUNET_NO if not + * @param peer the handle to the peer + * @return GNUNET_OK if successful; GNUNET_SYSERR if the main process is NULL + * or upon any error while sending SIGTERM */ int -GNUNET_TESTING_topology_get (enum GNUNET_TESTING_Topology *topology, - const char *topology_string); +GNUNET_TESTING_peer_kill (struct GNUNET_TESTING_Peer *peer); /** - * Get connect topology option from string input. + * Waits for a peer to terminate. The peer's main process will also be destroyed. * - * @param topology_option where to write the retrieved topology - * @param topology_string The string to attempt to - * get a configuration value from - * @return GNUNET_YES if topology string matched a - * known topology, GNUNET_NO if not + * @param peer the handle to the peer + * @return GNUNET_OK if successful; GNUNET_SYSERR if the main process is NULL + * or upon any error while waiting */ int -GNUNET_TESTING_topology_option_get (enum GNUNET_TESTING_TopologyOption - *topology_option, - const char *topology_string); - - -/** - * Takes a peer group and creates a topology based on the - * one specified. Creates a topology means generates friend - * files for the peers so they can only connect to those allowed - * by the topology. This will only have an effect once peers - * are started if the FRIENDS_ONLY option is set in the base - * config. - * - * Also takes an optional restrict topology which - * disallows direct connections UNLESS they are specified in - * the restricted topology. - * - * A simple example; if the topology option is set to LINE - * peers can ONLY connect in a LINE. However, if the topology - * option is set to 2D-torus and the restrict option is set to - * line with restrict_transports equal to "tcp udp", then peers - * may connect in a 2D-torus, but will be restricted to tcp and - * udp connections only in a LINE. Generally it only makes - * sense to do this if restrict_topology is a subset of topology. - * - * For testing peer discovery, etc. it is generally better to - * leave restrict_topology as GNUNET_TESTING_TOPOLOGY_NONE and - * then use the connect_topology function to restrict the initial - * connection set. - * - * @param pg the peer group struct representing the running peers - * @param topology which topology to connect the peers in - * @param restrict_topology allow only direct connections in this topology, - * based on those listed in restrict_transports, set to - * GNUNET_TESTING_TOPOLOGY_NONE for no restrictions - * @param restrict_transports space delimited list of transports to blacklist - * to create restricted topology, NULL for none - * - * @return the maximum number of connections were all allowed peers - * connected to each other - */ -unsigned int -GNUNET_TESTING_create_topology (struct GNUNET_TESTING_PeerGroup *pg, - enum GNUNET_TESTING_Topology topology, - enum GNUNET_TESTING_Topology restrict_topology, - const char *restrict_transports); - - -/** - * Iterate over all (running) peers in the peer group, retrieve - * all connections that each currently has. - * - * @param pg the peer group we are concerned with - * @param cb callback for topology information - * @param cls closure for callback - */ -void -GNUNET_TESTING_get_topology (struct GNUNET_TESTING_PeerGroup *pg, - GNUNET_TESTING_NotifyTopology cb, void *cls); +GNUNET_TESTING_peer_wait (struct GNUNET_TESTING_Peer *peer); /** - * Stop the connection process temporarily. - * - * @param pg the peer group to stop connecting - */ -void -GNUNET_TESTING_stop_connections (struct GNUNET_TESTING_PeerGroup *pg); - - -/** - * Resume the connection process. - * - * @param pg the peer group to resume connecting + * Signature of the 'main' function for a (single-peer) testcase that + * is run using 'GNUNET_TESTING_peer_run'. + * + * @param cls closure + * @param cfg configuration of the peer that was started + * @param peer identity of the peer that was created */ -void -GNUNET_TESTING_resume_connections (struct GNUNET_TESTING_PeerGroup *pg); +typedef void (*GNUNET_TESTING_TestMain)(void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer); /** - * There are many ways to connect peers that are supported by this function. - * To connect peers in the same topology that was created via the - * GNUNET_TESTING_create_topology, the topology variable must be set to - * GNUNET_TESTING_TOPOLOGY_NONE. If the topology variable is specified, - * a new instance of that topology will be generated and attempted to be - * connected. This could result in some connections being impossible, - * because some topologies are non-deterministic. + * Start a single peer and run a test using the testing library. + * Starts a peer using the given configuration and then invokes the + * given callback. This function ALSO initializes the scheduler loop + * and should thus be called directly from "main". The testcase + * should self-terminate by invoking 'GNUNET_SCHEDULER_shutdown'. * - * @param pg the peer group struct representing the running peers - * @param topology which topology to connect the peers in - * @param options options for connecting the topology - * @param option_modifier modifier for options that take a parameter - * @param connect_timeout how long to wait before giving up on connecting - * two peers - * @param connect_attempts how many times to attempt to connect two peers - * over the connect_timeout duration - * @param notify_callback notification to be called once all connections completed - * @param notify_cls closure for notification callback - * - * @return the number of connections that will be attempted, GNUNET_SYSERR on error + * @param testdir only the directory name without any path. This is used for + * all service homes; the directory will be created in a temporary + * location depending on the underlying OS + * @param cfgfilename name of the configuration file to use; + * use NULL to only run with defaults + * @param tm main function of the testcase + * @param tm_cls closure for 'tm' + * @return 0 on success, 1 on error */ int -GNUNET_TESTING_connect_topology (struct GNUNET_TESTING_PeerGroup *pg, - enum GNUNET_TESTING_Topology topology, - enum GNUNET_TESTING_TopologyOption options, - double option_modifier, - struct GNUNET_TIME_Relative connect_timeout, - unsigned int connect_attempts, - GNUNET_TESTING_NotifyCompletion - notify_callback, void *notify_cls); +GNUNET_TESTING_peer_run (const char *testdir, + const char *cfgfilename, + GNUNET_TESTING_TestMain tm, + void *tm_cls); /** - * Start or stop an individual peer from the given group. + * Start a single service (no ARM, except of course if the given + * service name is 'arm') and run a test using the testing library. + * Starts a service using the given configuration and then invokes the + * given callback. This function ALSO initializes the scheduler loop + * and should thus be called directly from "main". The testcase + * should self-terminate by invoking 'GNUNET_SCHEDULER_shutdown'. * - * @param pg handle to the peer group - * @param offset which peer to start or stop - * @param desired_status GNUNET_YES to have it running, GNUNET_NO to stop it - * @param timeout how long to wait for shutdown - * @param cb function to call at the end - * @param cb_cls closure for cb - */ -void -GNUNET_TESTING_daemons_vary (struct GNUNET_TESTING_PeerGroup *pg, - unsigned int offset, int desired_status, - struct GNUNET_TIME_Relative timeout, - GNUNET_TESTING_NotifyCompletion cb, void *cb_cls); - - -/** - * Start a peer group with a given number of peers. Notify - * on completion of peer startup and connection based on given - * topological constraints. Optionally notify on each - * established connection. + * This function is useful if the testcase is for a single service + * and if that service doesn't itself depend on other services. * - * @param cfg configuration template to use - * @param total number of daemons to start - * @param timeout total time allowed for peers to start - * @param connect_cb function to call each time two daemons are connected - * @param peergroup_cb function to call once all peers are up and connected - * @param peergroup_cls closure for peergroup callbacks - * @param hostnames linked list of host structs to use to start peers on - * (NULL to run on localhost only) - * - * @return NULL on error, otherwise handle to control peer group + * @param testdir only the directory name without any path. This is used for + * all service homes; the directory will be created in a temporary + * location depending on the underlying OS + * @param service_name name of the service to run + * @param cfgfilename name of the configuration file to use; + * use NULL to only run with defaults + * @param tm main function of the testcase + * @param tm_cls closure for 'tm' + * @return 0 on success, 1 on error */ -struct GNUNET_TESTING_PeerGroup * -GNUNET_TESTING_peergroup_start (const struct GNUNET_CONFIGURATION_Handle *cfg, - unsigned int total, - struct GNUNET_TIME_Relative timeout, - GNUNET_TESTING_NotifyConnection connect_cb, - GNUNET_TESTING_NotifyCompletion peergroup_cb, - void *peergroup_cls, - const struct GNUNET_TESTING_Host *hostnames); +int +GNUNET_TESTING_service_run (const char *testdir, + const char *service_name, + const char *cfgfilename, + GNUNET_TESTING_TestMain tm, + void *tm_cls); /** - * Print current topology to a graphviz readable file. + * Sometimes we use the binary name to determine which specific + * test to run. In those cases, the string after the last "_" + * in 'argv[0]' specifies a string that determines the configuration + * file or plugin to use. * - * @param pg a currently running peergroup to print to file - * @param output_filename the file to write the topology to - * @param notify_cb callback to call upon completion or failure - * @param notify_cb_cls closure for notify_cb + * This function returns the respective substring, taking care + * of issues such as binaries ending in '.exe' on W32. * + * @param argv0 the name of the binary + * @return string between the last '_' and the '.exe' (or the end of the string), + * NULL if argv0 has no '_' */ -void -GNUNET_TESTING_peergroup_topology_to_file (struct GNUNET_TESTING_PeerGroup *pg, - const char *output_filename, - GNUNET_TESTING_NotifyCompletion - notify_cb, void *notify_cb_cls); +char * +GNUNET_TESTING_get_testname_from_underscore (const char *argv0); #if 0 /* keep Emacsens' auto-indent happy */ diff --git a/src/include/gnunet_time_lib.h b/src/include/gnunet_time_lib.h index 35d180c..d131e4e 100644 --- a/src/include/gnunet_time_lib.h +++ b/src/include/gnunet_time_lib.h @@ -150,6 +150,22 @@ GNUNET_NETWORK_STRUCT_END #define GNUNET_TIME_UNIT_FOREVER_ABS GNUNET_TIME_absolute_get_forever_ () + +/** + * Threshold after which exponential backoff should not increase (15 m). + */ +#define GNUNET_TIME_STD_EXPONENTIAL_BACKOFF_THRESHOLD GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MINUTES, 15) + + +/** + * Perform our standard exponential back-off calculation, starting at 1mst + * and then going by a factor of 2 up unto a maximum of 1s. + * + * @param r current backoff time, initially zero + */ +#define GNUNET_TIME_STD_BACKOFF(r) GNUNET_TIME_relative_min (GNUNET_TIME_STD_EXPONENTIAL_BACKOFF_THRESHOLD, \ + GNUNET_TIME_relative_multiply (GNUNET_TIME_relative_max (GNUNET_TIME_UNIT_MILLISECONDS, (r)), 2)); + /** * Return relative time of 0ms. */ @@ -440,18 +456,6 @@ struct GNUNET_TIME_Absolute GNUNET_TIME_absolute_ntoh (struct GNUNET_TIME_AbsoluteNBO a); -/** - * Convert a relative time to a string. - * NOT reentrant! - * - * @param time the time to print - * - * @return string form of the time (as milliseconds) - */ -const char * -GNUNET_TIME_relative_to_string (struct GNUNET_TIME_Relative time); - - /** * Set the timestamp offset for this instance. * diff --git a/src/include/gnunet_transport_plugin.h b/src/include/gnunet_transport_plugin.h index d1e03d7..d8c4ec4 100644 --- a/src/include/gnunet_transport_plugin.h +++ b/src/include/gnunet_transport_plugin.h @@ -44,6 +44,10 @@ * useful since sometimes (i.e. for inbound TCP connections) a * connection may not have an address that can be used for meaningful * distinction between sessions to the same peer. + * + * Each 'struct Session' MUST start with the 'struct GNUNET_PeerIdentity' + * of the peer the session is for (which will be used for some error + * checking by the ATS code). */ struct Session; @@ -151,10 +155,12 @@ typedef struct GNUNET_ATS_Information * @param addr one of the addresses of the host * the specific address format depends on the transport * @param addrlen length of the address + * @param dest_plugin plugin to use this address with */ typedef void (*GNUNET_TRANSPORT_AddressNotification) (void *cls, int add_remove, const void *addr, - size_t addrlen); + size_t addrlen, + const char *dest_plugin); /** @@ -185,8 +191,8 @@ typedef struct GNUNET_TIME_Relative (*GNUNET_TRANSPORT_TrafficReport) (void /** * Function that returns a HELLO message. */ -typedef const struct GNUNET_MessageHeader - *(*GNUNET_TRANSPORT_GetHelloCallback) (void); +typedef const struct GNUNET_MessageHeader * + (*GNUNET_TRANSPORT_GetHelloCallback) (void); /** @@ -277,11 +283,17 @@ struct GNUNET_TRANSPORT_PluginEnvironment * GNUNET_SYSERR if the target disconnected; * disconnect will ALSO be signalled using * the ReceiveCallback. + * @param size_payload bytes of payload from transport service in message + * @param size_on_wire bytes required on wire for transmission, + * 0 if result == GNUNET_SYSERR */ typedef void (*GNUNET_TRANSPORT_TransmitContinuation) (void *cls, const struct GNUNET_PeerIdentity * - target, int result); + target, + int result, + size_t size_payload, + size_t size_on_wire); /** * The new send function with just the session and no address @@ -434,7 +446,7 @@ typedef const char *(*GNUNET_TRANSPORT_AddressToString) (void *cls, * * @param cls closure ('struct Plugin*') * @param addr string address - * @param addrlen length of the address + * @param addrlen length of the address including \0 termination * @param buf location to store the buffer * If the function returns GNUNET_SYSERR, its contents are undefined. * @param added length of created address diff --git a/src/include/gnunet_transport_service.h b/src/include/gnunet_transport_service.h index 5c939a0..5fb46a1 100644 --- a/src/include/gnunet_transport_service.h +++ b/src/include/gnunet_transport_service.h @@ -43,6 +43,13 @@ extern "C" */ #define GNUNET_TRANSPORT_VERSION 0x00000000 +enum TRAFFIC_METRIC_DIRECTION +{ + TM_SEND = 0, + TM_RECEIVE = 1, + TM_BOTH = 2 +}; + /** * Function called by the transport for each received message. @@ -98,6 +105,18 @@ typedef void (*GNUNET_TRANSPORT_NotifyDisconnect) (void *cls, GNUNET_PeerIdentity * peer); +/** + * Function to call with result of the try connect request. + * + * + * @param cls closure + * @param result GNUNET_OK if message was transmitted to transport service + * GNUNET_SYSERR if message was not transmitted to transport service + */ +typedef void (*GNUNET_TRANSPORT_TryConnectCallback) (void *cls, + const int result); + + /** * Function to call with a textual representation of an address. * This function will be called several times with different possible @@ -158,18 +177,40 @@ void GNUNET_TRANSPORT_disconnect (struct GNUNET_TRANSPORT_Handle *handle); +/** + * Opaque handle for a transmission-ready request. + */ +struct GNUNET_TRANSPORT_TryConnectHandle; + + /** * Ask the transport service to establish a connection to * the given peer. * * @param handle connection to transport service * @param target who we should try to connect to + * @param cb callback to be called when request was transmitted to transport + * service + * @param cb_cls closure for the callback + * @return a GNUNET_TRANSPORT_TryConnectHandle handle or + * NULL on failure (cb will not be called) */ -void +struct GNUNET_TRANSPORT_TryConnectHandle * GNUNET_TRANSPORT_try_connect (struct GNUNET_TRANSPORT_Handle *handle, - const struct GNUNET_PeerIdentity *target); + const struct GNUNET_PeerIdentity *target, + GNUNET_TRANSPORT_TryConnectCallback cb, + void *cb_cls); +/** + * Cancel the request to transport to try a connect + * Callback will not be called + * + * @param tch GNUNET_TRANSPORT_TryConnectHandle handle to cancel + */ +void +GNUNET_TRANSPORT_try_connect_cancel (struct GNUNET_TRANSPORT_TryConnectHandle *tch); + /** * Opaque handle for a transmission-ready request. */ @@ -236,7 +277,54 @@ struct GNUNET_TRANSPORT_GetHelloHandle; /** - * Obtain updates on changes to the HELLO message for this peer. + * Checks if a neighbour is connected + * + * @param handle connection to transport service + * @peer the peer to check + * @return GNUNET_YES or GNUNET_NO + * + */ +int +GNUNET_TRANSPORT_check_neighbour_connected (struct GNUNET_TRANSPORT_Handle *handle, + const struct GNUNET_PeerIdentity *peer); + + +/** + * Set transport metrics for a peer and a direction + * + * @param handle transport handle + * @param peer the peer to set the metric for + * @param direction can be: TM_SEND, TM_RECV, TM_BOTH + * @param ats the metric as ATS information + * @param ats_count the number of metrics + * + * Supported ATS values: + * GNUNET_ATS_QUALITY_NET_DELAY (value in ms) + * GNUNET_ATS_QUALITY_NET_DISTANCE (value in #hops) + * + * Example + * To enforce a delay of 10 ms for peer p1 in sending direction use: + * + * struct GNUNET_ATS_Information ats; + * ats.type = ntohl (GNUNET_ATS_QUALITY_NET_DELAY); + * ats.value = ntohl (10); + * GNUNET_TRANSPORT_set_traffic_metric (th, p1, TM_SEND, &ats, 1); + * + * Note: + * Delay restrictions in receiving direction will be enforced with + * 1 message delay. + */ +void +GNUNET_TRANSPORT_set_traffic_metric (struct GNUNET_TRANSPORT_Handle *handle, + const struct GNUNET_PeerIdentity *peer, + int direction, + const struct GNUNET_ATS_Information *ats, + size_t ats_count); + + +/** + * Obtain updates on changes to the HELLO message for this peer. The callback + * given in this function is never called synchronously. * * @param handle connection to transport service * @param rec function to call with the HELLO @@ -252,7 +340,7 @@ GNUNET_TRANSPORT_get_hello (struct GNUNET_TRANSPORT_Handle *handle, /** * Stop receiving updates about changes to our HELLO message. * - * @param ghh handle returned from 'GNUNET_TRANSPORT_get_hello') + * @param ghh handle to cancel */ void GNUNET_TRANSPORT_get_hello_cancel (struct GNUNET_TRANSPORT_GetHelloHandle *ghh); @@ -265,15 +353,28 @@ GNUNET_TRANSPORT_get_hello_cancel (struct GNUNET_TRANSPORT_GetHelloHandle *ghh); * * @param handle connection to transport service * @param hello the hello message - * @param cont continuation to call when HELLO has been sent + * @param cont continuation to call when HELLO has been sent, + * tc reason GNUNET_SCHEDULER_REASON_TIMEOUT for fail + * tc reasong GNUNET_SCHEDULER_REASON_READ_READY for success * @param cls closure for continuation + * @return a GNUNET_TRANSPORT_OfferHelloHandle handle or NULL on failure, + * in case of failure cont will not be called + * */ -void +struct GNUNET_TRANSPORT_OfferHelloHandle * GNUNET_TRANSPORT_offer_hello (struct GNUNET_TRANSPORT_Handle *handle, const struct GNUNET_MessageHeader *hello, GNUNET_SCHEDULER_Task cont, void *cls); +/** + * Cancel the request to transport to offer the HELLO message + * + * @param ohh the GNUNET_TRANSPORT_OfferHelloHandle to cancel + */ +void +GNUNET_TRANSPORT_offer_hello_cancel (struct GNUNET_TRANSPORT_OfferHelloHandle *ohh); + /** * Handle to cancel a pending address lookup. */ @@ -315,7 +416,7 @@ GNUNET_TRANSPORT_address_to_string_cancel (struct /** * Return all the known addresses for a specific peer or all peers. - * Returns continously all address if one_shot is set to GNUNET_NO + * Returns continuously all address if one_shot is set to GNUNET_NO * * CHANGE: Returns the address(es) that we are currently using for this * peer. Upon completion, the 'AddressLookUpCallback' is called one more diff --git a/src/include/gnunet_vpn_service.h b/src/include/gnunet_vpn_service.h index ecf6cf5..77944c9 100644 --- a/src/include/gnunet_vpn_service.h +++ b/src/include/gnunet_vpn_service.h @@ -97,7 +97,7 @@ GNUNET_VPN_redirect_to_peer (struct GNUNET_VPN_Handle *vh, int result_af, uint8_t protocol, const struct GNUNET_PeerIdentity *peer, - const GNUNET_HashCode *serv, + const struct GNUNET_HashCode *serv, int nac, struct GNUNET_TIME_Absolute expiration_time, GNUNET_VPN_AllocationCallback cb, diff --git a/src/include/platform.h b/src/include/platform.h index 9a5d164..c44f67f 100644 --- a/src/include/platform.h +++ b/src/include/platform.h @@ -1,6 +1,6 @@ /* This file is part of GNUnet. - (C) 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2009 Christian Grothoff (and other contributing authors) + (C) 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2009, 2012 Christian Grothoff (and other contributing authors) GNUnet is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published @@ -20,14 +20,12 @@ /** * @file include/platform.h - * @brief plaform specifics - * + * @brief plaform specific includes and defines * @author Nils Durner - * + * @author Christian Grothoff * This file should never be included by installed - * header files (thos starting with "gnunet_"). + * header files (those starting with "gnunet_"). */ - #ifndef PLATFORM_H #define PLATFORM_H @@ -50,7 +48,7 @@ #include #endif -#define ALLOW_EXTRA_CHECKS GNUNET_NO +#define ALLOW_EXTRA_CHECKS GNUNET_YES /** * For strptime (glibc2 needs this). @@ -111,6 +109,9 @@ #ifdef WINDOWS #include /* for alloca(), on other OSes it's in stdlib.h */ #endif +#ifdef HAVE_MALLOC_H +#include /* for mallinfo on GNU */ +#endif #ifndef _MSC_VER #include /* KLB_FIX */ #endif @@ -138,7 +139,7 @@ #ifdef SOMEBSD #include #endif -#ifdef GNUNET_freeBSD +#ifdef FREEBSD #include #endif #ifdef DARWIN @@ -146,7 +147,7 @@ #include #include #endif -#ifdef LINUX +#if defined(LINUX) || defined(GNU) #include #endif #ifdef SOLARIS diff --git a/src/include/winproc.h b/src/include/winproc.h index 3670a74..6cbe562 100644 --- a/src/include/winproc.h +++ b/src/include/winproc.h @@ -227,6 +227,7 @@ extern "C" int GNInitWinEnv (); void GNShutdownWinEnv (); + BOOL SafeTerminateProcess (HANDLE hProcess, UINT uExitCode, DWORD dwTimeout); #ifdef __cplusplus } #endif diff --git a/src/integration-tests/Makefile.am b/src/integration-tests/Makefile.am index fb69e28..e42fb0c 100644 --- a/src/integration-tests/Makefile.am +++ b/src/integration-tests/Makefile.am @@ -21,7 +21,7 @@ noinst_SCRIPTS = \ test_integration_connection_values_tcp_udp.py \ test_integration_connection_values_tcp_udp_http.py -if HAVE_PYTHON_PEXPECT +if HAVE_PYTHON check_SCRIPTS = \ test_integration_bootstrap_and_connect.py \ test_integration_bootstrap_and_connect_and_disconnect.py \ @@ -33,14 +33,13 @@ check_SCRIPTS = \ endif # test_integration_disconnect.py -check_PROGRAMS = \ - test_connection_stability - +if HAVE_MHD if ENABLE_TEST_RUN TESTS = \ $(check_SCRIPTS) endif +endif connection_watchdog_SOURCE = \ connection_watchdog.c @@ -113,12 +112,6 @@ test_integration_connection_values_tcp_udp_http.py: test_integration_connection_ $(do_subst) < $(srcdir)/test_integration_connection_values_tcp_udp_http.py.in > test_integration_connection_values_tcp_udp_http.py chmod +x test_integration_connection_values_tcp_udp_http.py -test_connection_stability_SOURCES = \ - test_connection_stability.c -test_connection_stability_LDADD = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/util/libgnunetutil.la - EXTRA_DIST = \ gnunet_testing.py.in \ @@ -135,6 +128,7 @@ EXTRA_DIST = \ test_integration_clique.py.in \ test_integration_clique_nat.py.in \ confs/c_bootstrap_server.conf \ + confs/c_bootstrap_server_w_massif.conf \ confs/c_nat_client.conf \ confs/c_no_nat_client_2.conf \ confs/c_no_nat_client.conf \ @@ -147,7 +141,6 @@ EXTRA_DIST = \ confs/c_no_nat_client_http_2.conf \ confs/c_no_nat_client_unix.conf \ confs/c_no_nat_client_unix_2.conf \ - test_connection_stability.conf \ hostkeys/0000-hostkey \ hostkeys/0001-hostkey \ hostkeys/0002-hostkey \ diff --git a/src/integration-tests/Makefile.in b/src/integration-tests/Makefile.in index 3e5e7dc..c9e19ba 100644 --- a/src/integration-tests/Makefile.in +++ b/src/integration-tests/Makefile.in @@ -1,9 +1,9 @@ -# Makefile.in generated by automake 1.11.1 from Makefile.am. +# Makefile.in generated by automake 1.11.6 from Makefile.am. # @configure_input@ # Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, -# 2003, 2004, 2005, 2006, 2007, 2008, 2009 Free Software Foundation, -# Inc. +# 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Free Software +# Foundation, Inc. # This Makefile.in is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. @@ -17,6 +17,23 @@ VPATH = @srcdir@ +am__make_dryrun = \ + { \ + am__dry=no; \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + echo 'am--echo: ; @echo "AM" OK' | $(MAKE) -f - 2>/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } pkgdatadir = $(datadir)/@PACKAGE@ pkgincludedir = $(includedir)/@PACKAGE@ pkglibdir = $(libdir)/@PACKAGE@ @@ -37,20 +54,20 @@ build_triplet = @build@ host_triplet = @host@ target_triplet = @target@ noinst_PROGRAMS = connection_watchdog$(EXEEXT) -check_PROGRAMS = test_connection_stability$(EXEEXT) subdir = src/integration-tests DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 am__aclocal_m4_deps = $(top_srcdir)/m4/absolute-header.m4 \ $(top_srcdir)/m4/align.m4 $(top_srcdir)/m4/argz.m4 \ - $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/iconv.m4 \ - $(top_srcdir)/m4/lib-ld.m4 $(top_srcdir)/m4/lib-link.m4 \ - $(top_srcdir)/m4/lib-prefix.m4 $(top_srcdir)/m4/libcurl.m4 \ - $(top_srcdir)/m4/libgcrypt.m4 $(top_srcdir)/m4/libtool.m4 \ - $(top_srcdir)/m4/libunistring.m4 $(top_srcdir)/m4/ltdl.m4 \ - $(top_srcdir)/m4/ltoptions.m4 $(top_srcdir)/m4/ltsugar.m4 \ - $(top_srcdir)/m4/ltversion.m4 $(top_srcdir)/m4/lt~obsolete.m4 \ - $(top_srcdir)/m4/nls.m4 $(top_srcdir)/m4/po.m4 \ + $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/glib-2.0.m4 \ + $(top_srcdir)/m4/iconv.m4 $(top_srcdir)/m4/lib-ld.m4 \ + $(top_srcdir)/m4/lib-link.m4 $(top_srcdir)/m4/lib-prefix.m4 \ + $(top_srcdir)/m4/libcurl.m4 $(top_srcdir)/m4/libgcrypt.m4 \ + $(top_srcdir)/m4/libtool.m4 $(top_srcdir)/m4/libunistring.m4 \ + $(top_srcdir)/m4/ltdl.m4 $(top_srcdir)/m4/ltoptions.m4 \ + $(top_srcdir)/m4/ltsugar.m4 $(top_srcdir)/m4/ltversion.m4 \ + $(top_srcdir)/m4/lt~obsolete.m4 $(top_srcdir)/m4/nls.m4 \ + $(top_srcdir)/m4/pkg.m4 $(top_srcdir)/m4/po.m4 \ $(top_srcdir)/m4/progtest.m4 $(top_srcdir)/acinclude.m4 \ $(top_srcdir)/configure.ac am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ @@ -67,16 +84,9 @@ connection_watchdog_DEPENDENCIES = \ $(top_builddir)/src/core/libgnunetcore.la \ $(top_builddir)/src/transport/libgnunettransport.la \ $(top_builddir)/src/util/libgnunetutil.la -AM_V_lt = $(am__v_lt_$(V)) -am__v_lt_ = $(am__v_lt_$(AM_DEFAULT_VERBOSITY)) +AM_V_lt = $(am__v_lt_@AM_V@) +am__v_lt_ = $(am__v_lt_@AM_DEFAULT_V@) am__v_lt_0 = --silent -am_test_connection_stability_OBJECTS = \ - test_connection_stability.$(OBJEXT) -test_connection_stability_OBJECTS = \ - $(am_test_connection_stability_OBJECTS) -test_connection_stability_DEPENDENCIES = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/util/libgnunetutil.la SCRIPTS = $(noinst_SCRIPTS) DEFAULT_INCLUDES = -I.@am__isrc@ -I$(top_builddir) depcomp = $(SHELL) $(top_srcdir)/depcomp @@ -88,25 +98,29 @@ LTCOMPILE = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) \ $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) \ $(AM_CFLAGS) $(CFLAGS) -AM_V_CC = $(am__v_CC_$(V)) -am__v_CC_ = $(am__v_CC_$(AM_DEFAULT_VERBOSITY)) +AM_V_CC = $(am__v_CC_@AM_V@) +am__v_CC_ = $(am__v_CC_@AM_DEFAULT_V@) am__v_CC_0 = @echo " CC " $@; -AM_V_at = $(am__v_at_$(V)) -am__v_at_ = $(am__v_at_$(AM_DEFAULT_VERBOSITY)) +AM_V_at = $(am__v_at_@AM_V@) +am__v_at_ = $(am__v_at_@AM_DEFAULT_V@) am__v_at_0 = @ CCLD = $(CC) LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ $(AM_LDFLAGS) $(LDFLAGS) -o $@ -AM_V_CCLD = $(am__v_CCLD_$(V)) -am__v_CCLD_ = $(am__v_CCLD_$(AM_DEFAULT_VERBOSITY)) +AM_V_CCLD = $(am__v_CCLD_@AM_V@) +am__v_CCLD_ = $(am__v_CCLD_@AM_DEFAULT_V@) am__v_CCLD_0 = @echo " CCLD " $@; -AM_V_GEN = $(am__v_GEN_$(V)) -am__v_GEN_ = $(am__v_GEN_$(AM_DEFAULT_VERBOSITY)) +AM_V_GEN = $(am__v_GEN_@AM_V@) +am__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@) am__v_GEN_0 = @echo " GEN " $@; -SOURCES = connection_watchdog.c $(test_connection_stability_SOURCES) -DIST_SOURCES = connection_watchdog.c \ - $(test_connection_stability_SOURCES) +SOURCES = connection_watchdog.c +DIST_SOURCES = connection_watchdog.c +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac ETAGS = etags CTAGS = ctags am__tty_colors = \ @@ -147,6 +161,10 @@ EXEEXT = @EXEEXT@ EXT_LIBS = @EXT_LIBS@ EXT_LIB_PATH = @EXT_LIB_PATH@ FGREP = @FGREP@ +GLIB_CFLAGS = @GLIB_CFLAGS@ +GLIB_GENMARSHAL = @GLIB_GENMARSHAL@ +GLIB_LIBS = @GLIB_LIBS@ +GLIB_MKENUMS = @GLIB_MKENUMS@ GMSGFMT = @GMSGFMT@ GMSGFMT_015 = @GMSGFMT_015@ GNUNETDNS_GROUP = @GNUNETDNS_GROUP@ @@ -157,6 +175,7 @@ GN_LIBINTL = @GN_LIBINTL@ GN_LIB_LDFLAGS = @GN_LIB_LDFLAGS@ GN_PLUGIN_LDFLAGS = @GN_PLUGIN_LDFLAGS@ GN_USER_HOME_DIR = @GN_USER_HOME_DIR@ +GOBJECT_QUERY = @GOBJECT_QUERY@ GREP = @GREP@ HAVE_LIBUNISTRING = @HAVE_LIBUNISTRING@ INCLTDL = @INCLTDL@ @@ -179,6 +198,8 @@ LIBCURL_CPPFLAGS = @LIBCURL_CPPFLAGS@ LIBGCRYPT_CFLAGS = @LIBGCRYPT_CFLAGS@ LIBGCRYPT_CONFIG = @LIBGCRYPT_CONFIG@ LIBGCRYPT_LIBS = @LIBGCRYPT_LIBS@ +LIBGTOP_CFLAGS = @LIBGTOP_CFLAGS@ +LIBGTOP_LIBS = @LIBGTOP_LIBS@ LIBICONV = @LIBICONV@ LIBINTL = @LIBINTL@ LIBLTDL = @LIBLTDL@ @@ -200,6 +221,7 @@ LT_CONFIG_H = @LT_CONFIG_H@ LT_DLLOADERS = @LT_DLLOADERS@ LT_DLPREOPEN = @LT_DLPREOPEN@ MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ MKDIR_P = @MKDIR_P@ MONKEYPREFIX = @MONKEYPREFIX@ MSGFMT = @MSGFMT@ @@ -209,6 +231,7 @@ MYSQL_CPPFLAGS = @MYSQL_CPPFLAGS@ MYSQL_LDFLAGS = @MYSQL_LDFLAGS@ NM = @NM@ NMEDIT = @NMEDIT@ +NSS_DIR = @NSS_DIR@ OBJC = @OBJC@ OBJCDEPMODE = @OBJCDEPMODE@ OBJCFLAGS = @OBJCFLAGS@ @@ -224,6 +247,7 @@ PACKAGE_TARNAME = @PACKAGE_TARNAME@ PACKAGE_URL = @PACKAGE_URL@ PACKAGE_VERSION = @PACKAGE_VERSION@ PATH_SEPARATOR = @PATH_SEPARATOR@ +PKG_CONFIG = @PKG_CONFIG@ POSTGRES_CPPFLAGS = @POSTGRES_CPPFLAGS@ POSTGRES_LDFLAGS = @POSTGRES_LDFLAGS@ POSUB = @POSUB@ @@ -255,6 +279,7 @@ abs_builddir = @abs_builddir@ abs_srcdir = @abs_srcdir@ abs_top_builddir = @abs_top_builddir@ abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ ac_ct_CC = @ac_ct_CC@ ac_ct_CXX = @ac_ct_CXX@ ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ @@ -277,6 +302,7 @@ datarootdir = @datarootdir@ docdir = @docdir@ dvidir = @dvidir@ exec_prefix = @exec_prefix@ +gitcommand = @gitcommand@ host = @host@ host_alias = @host_alias@ host_cpu = @host_cpu@ @@ -290,7 +316,6 @@ libdir = @libdir@ libexecdir = @libexecdir@ localedir = @localedir@ localstatedir = @localstatedir@ -lt_ECHO = @lt_ECHO@ ltdl_LIBOBJS = @ltdl_LIBOBJS@ ltdl_LTLIBOBJS = @ltdl_LTLIBOBJS@ mandir = @mandir@ @@ -308,6 +333,7 @@ sbindir = @sbindir@ sharedstatedir = @sharedstatedir@ srcdir = @srcdir@ subdirs = @subdirs@ +svnversioncommand = @svnversioncommand@ sys_symbol_underscore = @sys_symbol_underscore@ sysconfdir = @sysconfdir@ target = @target@ @@ -329,17 +355,18 @@ noinst_SCRIPTS = \ test_integration_connection_values_tcp_udp.py \ test_integration_connection_values_tcp_udp_http.py -@HAVE_PYTHON_PEXPECT_TRUE@check_SCRIPTS = \ -@HAVE_PYTHON_PEXPECT_TRUE@ test_integration_bootstrap_and_connect.py \ -@HAVE_PYTHON_PEXPECT_TRUE@ test_integration_bootstrap_and_connect_and_disconnect.py \ -@HAVE_PYTHON_PEXPECT_TRUE@ test_integration_bootstrap_and_connect_and_disconnect_nat.py \ -@HAVE_PYTHON_PEXPECT_TRUE@ test_integration_restart.py \ -@HAVE_PYTHON_PEXPECT_TRUE@ test_integration_clique.py \ -@HAVE_PYTHON_PEXPECT_TRUE@ test_integration_clique_nat.py \ -@HAVE_PYTHON_PEXPECT_TRUE@ test_integration_connect_on_restart.py +@HAVE_PYTHON_TRUE@check_SCRIPTS = \ +@HAVE_PYTHON_TRUE@ test_integration_bootstrap_and_connect.py \ +@HAVE_PYTHON_TRUE@ test_integration_bootstrap_and_connect_and_disconnect.py \ +@HAVE_PYTHON_TRUE@ test_integration_bootstrap_and_connect_and_disconnect_nat.py \ +@HAVE_PYTHON_TRUE@ test_integration_restart.py \ +@HAVE_PYTHON_TRUE@ test_integration_clique.py \ +@HAVE_PYTHON_TRUE@ test_integration_clique_nat.py \ +@HAVE_PYTHON_TRUE@ test_integration_connect_on_restart.py -@ENABLE_TEST_RUN_TRUE@TESTS = \ -@ENABLE_TEST_RUN_TRUE@ $(check_SCRIPTS) +# test_integration_disconnect.py +@ENABLE_TEST_RUN_TRUE@@HAVE_MHD_TRUE@TESTS = \ +@ENABLE_TEST_RUN_TRUE@@HAVE_MHD_TRUE@ $(check_SCRIPTS) connection_watchdog_SOURCE = \ connection_watchdog.c @@ -351,13 +378,6 @@ connection_watchdog_LDADD = \ $(top_builddir)/src/util/libgnunetutil.la do_subst = $(SED) -e 's,[@]PYTHON[@],$(PYTHON),g' -test_connection_stability_SOURCES = \ - test_connection_stability.c - -test_connection_stability_LDADD = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/util/libgnunetutil.la - EXTRA_DIST = \ gnunet_testing.py.in \ gnunet_pyexpect.py.in \ @@ -373,6 +393,7 @@ EXTRA_DIST = \ test_integration_clique.py.in \ test_integration_clique_nat.py.in \ confs/c_bootstrap_server.conf \ + confs/c_bootstrap_server_w_massif.conf \ confs/c_nat_client.conf \ confs/c_no_nat_client_2.conf \ confs/c_no_nat_client.conf \ @@ -385,7 +406,6 @@ EXTRA_DIST = \ confs/c_no_nat_client_http_2.conf \ confs/c_no_nat_client_unix.conf \ confs/c_no_nat_client_unix_2.conf \ - test_connection_stability.conf \ hostkeys/0000-hostkey \ hostkeys/0001-hostkey \ hostkeys/0002-hostkey \ @@ -437,15 +457,6 @@ $(ACLOCAL_M4): $(am__aclocal_m4_deps) cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh $(am__aclocal_m4_deps): -clean-checkPROGRAMS: - @list='$(check_PROGRAMS)'; test -n "$$list" || exit 0; \ - echo " rm -f" $$list; \ - rm -f $$list || exit $$?; \ - test -n "$(EXEEXT)" || exit 0; \ - list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ - echo " rm -f" $$list; \ - rm -f $$list - clean-noinstPROGRAMS: @list='$(noinst_PROGRAMS)'; test -n "$$list" || exit 0; \ echo " rm -f" $$list; \ @@ -454,12 +465,9 @@ clean-noinstPROGRAMS: list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ echo " rm -f" $$list; \ rm -f $$list -connection_watchdog$(EXEEXT): $(connection_watchdog_OBJECTS) $(connection_watchdog_DEPENDENCIES) +connection_watchdog$(EXEEXT): $(connection_watchdog_OBJECTS) $(connection_watchdog_DEPENDENCIES) $(EXTRA_connection_watchdog_DEPENDENCIES) @rm -f connection_watchdog$(EXEEXT) $(AM_V_CCLD)$(LINK) $(connection_watchdog_OBJECTS) $(connection_watchdog_LDADD) $(LIBS) -test_connection_stability$(EXEEXT): $(test_connection_stability_OBJECTS) $(test_connection_stability_DEPENDENCIES) - @rm -f test_connection_stability$(EXEEXT) - $(AM_V_CCLD)$(LINK) $(test_connection_stability_OBJECTS) $(test_connection_stability_LDADD) $(LIBS) mostlyclean-compile: -rm -f *.$(OBJEXT) @@ -468,31 +476,27 @@ distclean-compile: -rm -f *.tab.c @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/connection_watchdog.Po@am__quote@ -@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_connection_stability.Po@am__quote@ .c.o: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c $< .c.obj: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'` @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c `$(CYGPATH_W) '$<'` +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c `$(CYGPATH_W) '$<'` .c.lo: @am__fastdepCC_TRUE@ $(AM_V_CC)$(LTCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LTCOMPILE) -c -o $@ $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LTCOMPILE) -c -o $@ $< mostlyclean-libtool: -rm -f *.lo @@ -633,14 +637,15 @@ check-TESTS: $(TESTS) fi; \ dashes=`echo "$$dashes" | sed s/./=/g`; \ if test "$$failed" -eq 0; then \ - echo "$$grn$$dashes"; \ + col="$$grn"; \ else \ - echo "$$red$$dashes"; \ + col="$$red"; \ fi; \ - echo "$$banner"; \ - test -z "$$skipped" || echo "$$skipped"; \ - test -z "$$report" || echo "$$report"; \ - echo "$$dashes$$std"; \ + echo "$${col}$$dashes$${std}"; \ + echo "$${col}$$banner$${std}"; \ + test -z "$$skipped" || echo "$${col}$$skipped$${std}"; \ + test -z "$$report" || echo "$${col}$$report$${std}"; \ + echo "$${col}$$dashes$${std}"; \ test "$$failed" -eq 0; \ else :; fi @@ -675,7 +680,7 @@ distdir: $(DISTFILES) fi; \ done check-am: all-am - $(MAKE) $(AM_MAKEFLAGS) $(check_PROGRAMS) $(check_SCRIPTS) + $(MAKE) $(AM_MAKEFLAGS) $(check_SCRIPTS) $(MAKE) $(AM_MAKEFLAGS) check-TESTS check: check-am all-am: Makefile $(PROGRAMS) $(SCRIPTS) @@ -690,10 +695,15 @@ install-am: all-am installcheck: installcheck-am install-strip: - $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ - install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ - `test -z '$(STRIP)' || \ - echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi mostlyclean-generic: clean-generic: @@ -708,8 +718,8 @@ maintainer-clean-generic: @echo "it deletes files that may require special tools to rebuild." clean: clean-am -clean-am: clean-checkPROGRAMS clean-generic clean-libtool \ - clean-noinstPROGRAMS mostlyclean-am +clean-am: clean-generic clean-libtool clean-noinstPROGRAMS \ + mostlyclean-am distclean: distclean-am -rm -rf ./$(DEPDIR) @@ -780,15 +790,15 @@ uninstall-am: .MAKE: check-am install-am install-strip .PHONY: CTAGS GTAGS all all-am check check-TESTS check-am clean \ - clean-checkPROGRAMS clean-generic clean-libtool \ - clean-noinstPROGRAMS ctags distclean distclean-compile \ - distclean-generic distclean-libtool distclean-tags distdir dvi \ - dvi-am html html-am info info-am install install-am \ - install-data install-data-am install-dvi install-dvi-am \ - install-exec install-exec-am install-html install-html-am \ - install-info install-info-am install-man install-pdf \ - install-pdf-am install-ps install-ps-am install-strip \ - installcheck installcheck-am installdirs maintainer-clean \ + clean-generic clean-libtool clean-noinstPROGRAMS ctags \ + distclean distclean-compile distclean-generic \ + distclean-libtool distclean-tags distdir dvi dvi-am html \ + html-am info info-am install install-am install-data \ + install-data-am install-dvi install-dvi-am install-exec \ + install-exec-am install-html install-html-am install-info \ + install-info-am install-man install-pdf install-pdf-am \ + install-ps install-ps-am install-strip installcheck \ + installcheck-am installdirs maintainer-clean \ maintainer-clean-generic mostlyclean mostlyclean-compile \ mostlyclean-generic mostlyclean-libtool pdf pdf-am ps ps-am \ tags uninstall uninstall-am diff --git a/src/integration-tests/confs/c_bootstrap_server.conf b/src/integration-tests/confs/c_bootstrap_server.conf index 7235fca..4ead99d 100644 --- a/src/integration-tests/confs/c_bootstrap_server.conf +++ b/src/integration-tests/confs/c_bootstrap_server.conf @@ -1,6 +1,5 @@ [PATHS] SERVICEHOME = /tmp/c_bootstrap_server/ -DEFAULTCONFIG = confs/c_bootstrap_server.conf [gnunetd] #HOSTKEY = $SERVICEHOME/.hostkey @@ -11,7 +10,6 @@ AUTOSTART = YES PORT = 0 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-dns ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -22,7 +20,6 @@ AUTOSTART = YES PORT = 20017 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-resolver ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -35,7 +32,6 @@ AUTOSTART = YES PORT = 20016 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-mesh ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -48,7 +44,6 @@ AUTOSTART = YES PORT = 20015 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-nse ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -59,7 +54,7 @@ PROOFFILE = $SERVICEHOME/.nse-proof HISTOGRAM = $SERVICEHOME/nse-history.log WORKDELAY = 5 ms INTERVAL = 1 h -WORKBITS = 26 +WORKBITS = 1 [topology] MINIMUM-FRIENDS = 0 @@ -67,7 +62,6 @@ FRIENDS-ONLY = NO AUTOCONNECT = YES TARGET-CONNECTION-COUNT = 16 FRIENDS = $SERVICEHOME/friends -CONFIG = $DEFAULTCONFIG BINARY = gnunet-daemon-topology [datastore] @@ -78,7 +72,6 @@ UNIX_MATCH_GID = YES PORT = 20014 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-datastore ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -101,7 +94,6 @@ AUTOSTART = YES PORT = 20013 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-peerinfo ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -125,15 +117,14 @@ AUTOSTART = YES PORT = 20012 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-ats ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; UNIXPATH = /tmp/test-service-ats-9 UNIX_MATCH_UID = YES UNIX_MATCH_GID = YES -WAN_QUOTA_IN = 65536 -WAN_QUOTA_OUT = 65536 +WAN_QUOTA_IN = unlimited +WAN_QUOTA_OUT = unlimited DUMP_MLP = NO DUMP_SOLUTION = NO DUMP_OVERWRITE = NO @@ -147,7 +138,6 @@ AUTOSTART = YES PORT = 20011 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-transport NEIGHBOUR_LIMIT = 50 ACCEPT_FROM = 127.0.0.1; @@ -199,7 +189,6 @@ AUTOSTART = NO PORT = 20006 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-template ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -217,7 +206,6 @@ UPDATE_DIR = $SERVICEHOME/updates/ PORT = 20005 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-fs ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -232,7 +220,6 @@ MIN_MIGRATION_DELAY = 100 ms EXPECTED_NEIGHBOUR_COUNT = 128 [vpn] -CONFIG = $DEFAULTCONFIG BINARY = gnunet-daemon-vpn IPV6ADDR = 1234::1 IPV6PREFIX = 32 @@ -243,7 +230,6 @@ VIRTDNS6 = 1234::17 IFNAME = vpn-gnunet [exit] -CONFIG = $DEFAULTCONFIG BINARY = gnunet-daemon-exit IPV6ADDR = 1234:1::1 IPV6PREFIX = 32 @@ -258,7 +244,6 @@ AUTOSTART = YES PORT = 0 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-dns ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -269,7 +254,6 @@ PROVIDE_EXIT = NO PORT = 20004 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-arm ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -282,7 +266,6 @@ UNIX_MATCH_GID = YES HTTPPORT = 8080 HOME = $SERVICEHOME HOSTLISTFILE = $SERVICEHOME/hostlist/learned.data -CONFIG = $DEFAULTCONFIG BINARY = gnunet-daemon-hostlist OPTIONS = -p #SERVERS = http://v9.gnunet.org:58080/ @@ -293,7 +276,6 @@ AUTOSTART = YES PORT = 20003 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-core ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -327,7 +309,6 @@ AUTOSTART = YES PORT = 20001 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-statistics ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -340,7 +321,6 @@ AUTOSTART = YES PORT = 20000 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-dht ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -349,6 +329,16 @@ UNIXPATH = /tmp/test-service-dht-1 UNIX_MATCH_UID = YES UNIX_MATCH_GID = YES +[chat] +UNIXPATH = /tmp/test-service-chat-b_server-1 +UNIX_MATCH_UID = YES +UNIX_MATCH_GID = YES + +[dv] +UNIXPATH = /tmp/test-service-dv-b_server-1 +UNIX_MATCH_UID = YES +UNIX_MATCH_GID = YES + [dhtcache] DATABASE = sqlite QUOTA = 1 MB @@ -360,4 +350,8 @@ AUTOSTART = NO AUTOSTART = NO [lockmanager] -AUTOSTART = NO \ No newline at end of file +AUTOSTART = NO +[consensus] +AUTOSTART = NO + + diff --git a/src/integration-tests/confs/c_bootstrap_server_w_massif.conf b/src/integration-tests/confs/c_bootstrap_server_w_massif.conf new file mode 100644 index 0000000..b6c88c4 --- /dev/null +++ b/src/integration-tests/confs/c_bootstrap_server_w_massif.conf @@ -0,0 +1,348 @@ +[PATHS] +SERVICEHOME = /tmp/c_bootstrap_server/ + +[gnunetd] +#HOSTKEY = $SERVICEHOME/.hostkey +HOSTKEY = hostkeys/0000-hostkey + +[vpn] +AUTOSTART = YES +PORT = 0 +HOSTNAME = localhost +HOME = $SERVICEHOME +BINARY = gnunet-service-dns +ACCEPT_FROM = 127.0.0.1; +ACCEPT_FROM6 = ::1; +UNIXPATH = /tmp/gnunet-service-vpn-15 + +[resolver] +AUTOSTART = YES +PORT = 20017 +HOSTNAME = localhost +HOME = $SERVICEHOME +BINARY = gnunet-service-resolver +ACCEPT_FROM = 127.0.0.1; +ACCEPT_FROM6 = ::1; +UNIXPATH = /tmp/test-service-resolver-14 +UNIX_MATCH_UID = NO +UNIX_MATCH_GID = NO + +[mesh] +AUTOSTART = YES +PORT = 20016 +HOSTNAME = localhost +HOME = $SERVICEHOME +BINARY = gnunet-service-mesh +ACCEPT_FROM = 127.0.0.1; +ACCEPT_FROM6 = ::1; +UNIXPATH = /tmp/test-service-mesh-13 +UNIX_MATCH_UID = YES +UNIX_MATCH_GID = YES + +[nse] +AUTOSTART = YES +PORT = 20015 +HOSTNAME = localhost +HOME = $SERVICEHOME +BINARY = gnunet-service-nse +ACCEPT_FROM = 127.0.0.1; +ACCEPT_FROM6 = ::1; +UNIXPATH = /tmp/test-service-nse-12 +UNIX_MATCH_UID = YES +UNIX_MATCH_GID = YES +PROOFFILE = $SERVICEHOME/.nse-proof +HISTOGRAM = $SERVICEHOME/nse-history.log +WORKDELAY = 5 ms +INTERVAL = 1 h +WORKBITS = 1 + +[topology] +MINIMUM-FRIENDS = 0 +FRIENDS-ONLY = NO +AUTOCONNECT = YES +TARGET-CONNECTION-COUNT = 16 +FRIENDS = $SERVICEHOME/friends +BINARY = gnunet-daemon-topology + +[datastore] +AUTOSTART = YES +UNIXPATH = /tmp/test-service-datastore-11 +UNIX_MATCH_UID = YES +UNIX_MATCH_GID = YES +PORT = 20014 +HOSTNAME = localhost +HOME = $SERVICEHOME +BINARY = gnunet-service-datastore +ACCEPT_FROM = 127.0.0.1; +ACCEPT_FROM6 = ::1; +QUOTA = 100 MB +BLOOMFILTER = $SERVICEHOME/fs/bloomfilter +DATABASE = sqlite + +[datastore-sqlite] +FILENAME = $SERVICEHOME/datastore/sqlite.db + +[datastore-postgres] +CONFIG = connect_timeout=10; dbname=gnunet + +[datastore-mysql] +DATABASE = gnunet +CONFIG = ~/.my.cnf + +[peerinfo] +AUTOSTART = YES +PORT = 20013 +HOSTNAME = localhost +HOME = $SERVICEHOME +BINARY = gnunet-service-peerinfo +ACCEPT_FROM = 127.0.0.1; +ACCEPT_FROM6 = ::1; +UNIXPATH = /tmp/test-service-peerinfo-10 +UNIX_MATCH_UID = NO +UNIX_MATCH_GID = YES +HOSTS = $SERVICEHOME/data/hosts/ + +[client] +HOME = $SERVICEHOME + +[TESTING] +WEAKRANDOM = YES +CONNECT_TIMEOUT = 30 s +CONNECT_ATTEMPTS = 3 +MAX_OUTSTANDING_CONNECTIONS = 50 +DELETE_FILES = YES + +[ats] +AUTOSTART = YES +PORT = 20012 +HOSTNAME = localhost +HOME = $SERVICEHOME +BINARY = gnunet-service-ats +ACCEPT_FROM = 127.0.0.1; +ACCEPT_FROM6 = ::1; +UNIXPATH = /tmp/test-service-ats-9 +UNIX_MATCH_UID = YES +UNIX_MATCH_GID = YES +WAN_QUOTA_IN = unlimited +WAN_QUOTA_OUT = unlimited +DUMP_MLP = NO +DUMP_SOLUTION = NO +DUMP_OVERWRITE = NO +DUMP_MIN_PEERS = 0 +DUMP_MIN_ADDRS = 0 +ATS_MIN_INTERVAL = 15000 +ATS_EXEC_INTERVAL = 30000 + +[transport] +#PREFIX = valgrind --alloc-fn=GNUNET_xmalloc_ --alloc-fn=GNUNET_xmalloc_unchecked_ --alloc-fn=GNUNET_xrealloc_ --alloc-fn=GNUNET_xgrow_ --massif-out-file=massif_bootstrap.out --tool=massif +AUTOSTART = YES +PORT = 20011 +HOSTNAME = localhost +HOME = $SERVICEHOME +BINARY = gnunet-service-transport +NEIGHBOUR_LIMIT = 50 +ACCEPT_FROM = 127.0.0.1; +ACCEPT_FROM6 = ::1; +PLUGINS = tcp +UNIXPATH = /tmp/test-service-transport-8 +BLACKLIST_FILE = $SERVICEHOME/blacklist +UNIX_MATCH_UID = YES +UNIX_MATCH_GID = YES + +[transport-tcp] +USE_LOCALADDR = YES +PORT = 20010 +ADVERTISED_PORT = 20010 +MAX_CONNECTIONS = 128 +TIMEOUT = 5 s + +[transport-udp] +USE_LOCALADDR = YES +PORT = 20009 +BROADCAST = YES +BROADCAST_INTERVAL = 30000 +MAX_BPS = 1000000 + +[transport-http] +PORT = 20008 +MAX_CONNECTIONS = 128 + +[transport-https] +PORT = 20007 +CRYPTO_INIT = NORMAL +KEY_FILE = https.key +CERT_FILE = https.cert +MAX_CONNECTIONS = 128 + +[transport-wlan] +INTERFACE = mon0 +TESTMODE = 0 + +[datacache-mysql] +DATABASE = gnunet +CONFIG = ~/.my.cnf + +[datacache-postgres] +CONFIG = connect_timeout=10; dbname=gnunet + +[template] +AUTOSTART = NO +PORT = 20006 +HOSTNAME = localhost +HOME = $SERVICEHOME +BINARY = gnunet-service-template +ACCEPT_FROM = 127.0.0.1; +ACCEPT_FROM6 = ::1; +UNIXPATH = /tmp/test-service-template-7 +UNIX_MATCH_UID = YES +UNIX_MATCH_GID = YES + +[fs] +AUTOSTART = YES +INDEXDB = $SERVICEHOME/idxinfo.lst +TRUST = $SERVICEHOME/data/credit/ +IDENTITY_DIR = $SERVICEHOME/identities/ +STATE_DIR = $SERVICEHOME/persistence/ +UPDATE_DIR = $SERVICEHOME/updates/ +PORT = 20005 +HOSTNAME = localhost +HOME = $SERVICEHOME +BINARY = gnunet-service-fs +ACCEPT_FROM = 127.0.0.1; +ACCEPT_FROM6 = ::1; +DELAY = YES +CONTENT_CACHING = YES +CONTENT_PUSHING = YES +UNIXPATH = /tmp/test-service-fs-6 +UNIX_MATCH_UID = NO +UNIX_MATCH_GID = YES +MAX_PENDING_REQUESTS = 65536 +MIN_MIGRATION_DELAY = 100 ms +EXPECTED_NEIGHBOUR_COUNT = 128 + +[vpn] +BINARY = gnunet-daemon-vpn +IPV6ADDR = 1234::1 +IPV6PREFIX = 32 +IPV4ADDR = 10.11.10.1 +IPV4MASK = 255.255.0.0 +VIRTDNS = 10.11.10.2 +VIRTDNS6 = 1234::17 +IFNAME = vpn-gnunet + +[exit] +BINARY = gnunet-daemon-exit +IPV6ADDR = 1234:1::1 +IPV6PREFIX = 32 +IPV4ADDR = 10.10.1.1 +IPV4MASK = 255.255.0.0 +IFNAME = exit-gnunet +ENABLE_UDP = NO +ENABLE_TCP = NO + +[dns] +AUTOSTART = YES +PORT = 0 +HOSTNAME = localhost +HOME = $SERVICEHOME +BINARY = gnunet-service-dns +ACCEPT_FROM = 127.0.0.1; +ACCEPT_FROM6 = ::1; +UNIXPATH = /tmp/test-service-dns-5 +PROVIDE_EXIT = NO + +[arm] +PORT = 20004 +HOSTNAME = localhost +HOME = $SERVICEHOME +BINARY = gnunet-service-arm +ACCEPT_FROM = 127.0.0.1; +ACCEPT_FROM6 = ::1; +DEFAULTSERVICES = topology hostlist fs dht gns +UNIXPATH = /tmp/test-service-arm-4 +UNIX_MATCH_UID = YES +UNIX_MATCH_GID = YES + +[hostlist] +HTTPPORT = 8080 +HOME = $SERVICEHOME +HOSTLISTFILE = $SERVICEHOME/hostlist/learned.data +BINARY = gnunet-daemon-hostlist +OPTIONS = -p +#SERVERS = http://v9.gnunet.org:58080/ +HTTP-PROXY = + +[core] +AUTOSTART = YES +PORT = 20003 +HOSTNAME = localhost +HOME = $SERVICEHOME +BINARY = gnunet-service-core +ACCEPT_FROM = 127.0.0.1; +ACCEPT_FROM6 = ::1; +UNIXPATH = /tmp/test-service-core-3 +UNIX_MATCH_UID = YES +UNIX_MATCH_GID = YES + +[nat] +EXTERNAL_ADDRESS = 127.0.0.1 +INTERNAL_ADDRESS = 127.0.0.1 +BINDTO = 127.0.0.1 +BEHIND_NAT = NO +PUNCHED_NAT = NO +ENABLE_UPNP = NO +USE_LOCALADDR = YES +USE_HOSTNAME = NO +ENABLE_ICMP_CLIENT = NO +ENABLE_ICMP_SERVER = NO +DISABLEV6 = YES +RETURN_LOCAL_ADDRESSES = NO +HOSTNAME_DNS_FREQUENCY = 1200000 +IFC_SCAN_FREQUENCY = 3000000 +DYNDNS_FREQUENCY = 140000 + +[gnunet-nat-server] +HOSTNAME = gnunet.org +PORT = 20002 + +[statistics] +AUTOSTART = YES +PORT = 20001 +HOSTNAME = localhost +HOME = $SERVICEHOME +BINARY = gnunet-service-statistics +ACCEPT_FROM = 127.0.0.1; +ACCEPT_FROM6 = ::1; +UNIXPATH = /tmp/test-service-statistics-2 +UNIX_MATCH_UID = NO +UNIX_MATCH_GID = YES + +[dht] +AUTOSTART = YES +PORT = 20000 +HOSTNAME = localhost +HOME = $SERVICEHOME +BINARY = gnunet-service-dht +ACCEPT_FROM = 127.0.0.1; +ACCEPT_FROM6 = ::1; +BUCKET_SIZE = 4 +UNIXPATH = /tmp/test-service-dht-1 +UNIX_MATCH_UID = YES +UNIX_MATCH_GID = YES + +[dhtcache] +DATABASE = sqlite +QUOTA = 1 MB + +[gns] +AUTOSTART = NO + +[namestore] +AUTOSTART = NO + +[lockmanager] +AUTOSTART = NO +[consensus] +AUTOSTART = NO + + diff --git a/src/integration-tests/confs/c_nat_client.conf b/src/integration-tests/confs/c_nat_client.conf index 4f6c578..130d439 100644 --- a/src/integration-tests/confs/c_nat_client.conf +++ b/src/integration-tests/confs/c_nat_client.conf @@ -1,6 +1,5 @@ [PATHS] SERVICEHOME = /tmp/c_nat_client -DEFAULTCONFIG = confs/c_nat_client.conf [gnunetd] HOSTKEY = hostkeys/0002-hostkey @@ -19,7 +18,6 @@ AUTOSTART = YES PORT = 0 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-dns ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -31,7 +29,6 @@ AUTOSTART = YES PORT = 20071 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-resolver ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -44,7 +41,6 @@ AUTOSTART = YES PORT = 20070 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-mesh ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -57,7 +53,6 @@ AUTOSTART = YES PORT = 20069 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-nse ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -68,7 +63,7 @@ PROOFFILE = $SERVICEHOME/.nse-proof HISTOGRAM = $SERVICEHOME/nse-history.log WORKDELAY = 5 ms INTERVAL = 1 h -WORKBITS = 26 +WORKBITS = 1 [topology] MINIMUM-FRIENDS = 0 @@ -76,7 +71,6 @@ FRIENDS-ONLY = NO AUTOCONNECT = YES TARGET-CONNECTION-COUNT = 16 FRIENDS = $SERVICEHOME/friends -CONFIG = $DEFAULTCONFIG BINARY = gnunet-daemon-topology [datastore] @@ -87,7 +81,6 @@ UNIX_MATCH_GID = YES PORT = 20068 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-datastore ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -110,7 +103,6 @@ AUTOSTART = YES PORT = 20067 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-peerinfo ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -131,15 +123,14 @@ AUTOSTART = YES PORT = 20066 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-ats ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; UNIXPATH = /tmp/test-service-ats-51 UNIX_MATCH_UID = YES UNIX_MATCH_GID = YES -WAN_QUOTA_IN = 65536 -WAN_QUOTA_OUT = 65536 +WAN_QUOTA_IN = unlimited +WAN_QUOTA_OUT = unlimited DUMP_MLP = NO DUMP_SOLUTION = NO DUMP_OVERWRITE = NO @@ -153,7 +144,6 @@ AUTOSTART = YES PORT = 20065 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-transport NEIGHBOUR_LIMIT = 50 ACCEPT_FROM = 127.0.0.1; @@ -205,7 +195,6 @@ AUTOSTART = NO PORT = 20060 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-template ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -223,7 +212,6 @@ UPDATE_DIR = $SERVICEHOME/updates/ PORT = 20059 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-fs ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -238,7 +226,6 @@ MIN_MIGRATION_DELAY = 100 ms EXPECTED_NEIGHBOUR_COUNT = 128 [vpn] -CONFIG = $DEFAULTCONFIG BINARY = gnunet-daemon-vpn IPV6ADDR = 1234::1 IPV6PREFIX = 32 @@ -249,7 +236,6 @@ VIRTDNS6 = 1234::17 IFNAME = vpn-gnunet [exit] -CONFIG = $DEFAULTCONFIG BINARY = gnunet-daemon-exit IPV6ADDR = 1234:1::1 IPV6PREFIX = 32 @@ -264,7 +250,6 @@ AUTOSTART = YES PORT = 0 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-dns ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -275,7 +260,6 @@ PROVIDE_EXIT = NO PORT = 20058 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-arm ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -288,7 +272,6 @@ UNIX_MATCH_GID = YES HTTPPORT = 8080 HOME = $SERVICEHOME HOSTLISTFILE = $SERVICEHOME/hostlist/learned.data -CONFIG = $DEFAULTCONFIG BINARY = gnunet-daemon-hostlist OPTIONS = -b SERVERS = http://localhost:8080/ @@ -299,7 +282,6 @@ AUTOSTART = YES PORT = 20057 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-core ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -333,7 +315,6 @@ AUTOSTART = YES PORT = 20055 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-statistics ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -346,7 +327,6 @@ AUTOSTART = YES PORT = 20054 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-dht ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -359,5 +339,19 @@ UNIX_MATCH_GID = YES DATABASE = sqlite QUOTA = 1 MB +[chat] +UNIXPATH = /tmp/test-service-chat-b_nat_c-1 +UNIX_MATCH_UID = YES +UNIX_MATCH_GID = YES + +[dv] +UNIXPATH = /tmp/test-service-dv-b_nat_c-1 +UNIX_MATCH_UID = YES +UNIX_MATCH_GID = YES + [lockmanager] -AUTOSTART = NO \ No newline at end of file +AUTOSTART = NO +[consensus] +AUTOSTART = NO + + diff --git a/src/integration-tests/confs/c_no_nat_client.conf b/src/integration-tests/confs/c_no_nat_client.conf index 0a24b5a..494e813 100644 --- a/src/integration-tests/confs/c_no_nat_client.conf +++ b/src/integration-tests/confs/c_no_nat_client.conf @@ -1,6 +1,5 @@ [PATHS] SERVICEHOME = /tmp/c_no_nat_client/ -DEFAULTCONFIG = confs/c_no_nat_client.conf [gnunetd] #HOSTKEY = $SERVICEHOME/.hostkey @@ -17,7 +16,6 @@ AUTOSTART = YES PORT = 0 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-dns ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -28,7 +26,6 @@ AUTOSTART = YES PORT = 20035 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-resolver ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -41,7 +38,6 @@ AUTOSTART = YES PORT = 20034 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-mesh ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -54,7 +50,6 @@ AUTOSTART = YES PORT = 20033 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-nse ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -65,7 +60,7 @@ PROOFFILE = $SERVICEHOME/.nse-proof HISTOGRAM = $SERVICEHOME/nse-history.log WORKDELAY = 5 ms INTERVAL = 1 h -WORKBITS = 26 +WORKBITS = 1 [topology] MINIMUM-FRIENDS = 0 @@ -73,7 +68,6 @@ FRIENDS-ONLY = NO AUTOCONNECT = YES TARGET-CONNECTION-COUNT = 16 FRIENDS = $SERVICEHOME/friends -CONFIG = $DEFAULTCONFIG BINARY = gnunet-daemon-topology [datastore] @@ -84,7 +78,6 @@ UNIX_MATCH_GID = YES PORT = 20032 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-datastore ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -107,7 +100,6 @@ AUTOSTART = YES PORT = 20031 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-peerinfo ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -131,15 +123,14 @@ AUTOSTART = YES PORT = 20030 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-ats ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; UNIXPATH = /tmp/test-service-ats-23 UNIX_MATCH_UID = YES UNIX_MATCH_GID = YES -WAN_QUOTA_IN = 65536 -WAN_QUOTA_OUT = 65536 +WAN_QUOTA_IN = unlimited +WAN_QUOTA_OUT = unlimited DUMP_MLP = NO DUMP_SOLUTION = NO DUMP_OVERWRITE = NO @@ -149,12 +140,11 @@ ATS_MIN_INTERVAL = 15000 ATS_EXEC_INTERVAL = 30000 [transport] -#DEBUG = YES +#PREFIX = valgrind --alloc-fn=GNUNET_xmalloc_ --alloc-fn=GNUNET_xmalloc_unchecked_ --alloc-fn=GNUNET_xrealloc_ --alloc-fn=GNUNET_xgrow_ --massif-out-file=massif_client.out --tool=massif AUTOSTART = YES PORT = 20029 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-transport NEIGHBOUR_LIMIT = 50 ACCEPT_FROM = 127.0.0.1; @@ -206,7 +196,6 @@ AUTOSTART = NO PORT = 20024 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-template ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -224,7 +213,6 @@ UPDATE_DIR = $SERVICEHOME/updates/ PORT = 20023 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-fs ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -239,7 +227,6 @@ MIN_MIGRATION_DELAY = 100 ms EXPECTED_NEIGHBOUR_COUNT = 128 [vpn] -CONFIG = $DEFAULTCONFIG BINARY = gnunet-daemon-vpn IPV6ADDR = 1234::1 IPV6PREFIX = 32 @@ -250,7 +237,6 @@ VIRTDNS6 = 1234::17 IFNAME = vpn-gnunet [exit] -CONFIG = $DEFAULTCONFIG BINARY = gnunet-daemon-exit IPV6ADDR = 1234:1::1 IPV6PREFIX = 32 @@ -265,7 +251,6 @@ AUTOSTART = YES PORT = 0 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-dns ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -276,7 +261,6 @@ PROVIDE_EXIT = NO PORT = 20022 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-arm ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -289,7 +273,6 @@ UNIX_MATCH_GID = YES HTTPPORT = 8080 HOME = $SERVICEHOME HOSTLISTFILE = $SERVICEHOME/hostlist/learned.data -CONFIG = $DEFAULTCONFIG BINARY = gnunet-daemon-hostlist OPTIONS = -b SERVERS = http://localhost:8080/ @@ -300,7 +283,6 @@ AUTOSTART = YES PORT = 20021 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-core ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -334,7 +316,6 @@ AUTOSTART = YES PORT = 20019 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-statistics ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -347,7 +328,6 @@ AUTOSTART = YES PORT = 20018 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-dht ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -360,5 +340,19 @@ UNIX_MATCH_GID = YES DATABASE = sqlite QUOTA = 1 MB +[chat] +UNIXPATH = /tmp/test-service-chat-b_no_nat_c-1 +UNIX_MATCH_UID = YES +UNIX_MATCH_GID = YES + +[dv] +UNIXPATH = /tmp/test-service-dv-b_no_nat_c-1 +UNIX_MATCH_UID = YES +UNIX_MATCH_GID = YES + [lockmanager] AUTOSTART = NO +[consensus] +AUTOSTART = NO + + diff --git a/src/integration-tests/confs/c_no_nat_client_2.conf b/src/integration-tests/confs/c_no_nat_client_2.conf index 61a6a3b..8cdd24f 100644 --- a/src/integration-tests/confs/c_no_nat_client_2.conf +++ b/src/integration-tests/confs/c_no_nat_client_2.conf @@ -1,6 +1,5 @@ [PATHS] SERVICEHOME = /tmp/c_no_nat_client_2/ -DEFAULTCONFIG = confs/c_no_nat_client_2.conf [gnunetd] #HOSTKEY = $SERVICEHOME/.hostkey @@ -11,7 +10,6 @@ AUTOSTART = YES PORT = 20053 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-resolver ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -24,7 +22,6 @@ AUTOSTART = YES PORT = 20052 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-mesh ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -37,7 +34,6 @@ AUTOSTART = YES PORT = 20051 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-nse ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -48,7 +44,7 @@ PROOFFILE = $SERVICEHOME/.nse-proof HISTOGRAM = $SERVICEHOME/nse-history.log WORKDELAY = 5 ms INTERVAL = 1 h -WORKBITS = 26 +WORKBITS = 1 [topology] MINIMUM-FRIENDS = 0 @@ -56,7 +52,6 @@ FRIENDS-ONLY = NO AUTOCONNECT = YES TARGET-CONNECTION-COUNT = 16 FRIENDS = $SERVICEHOME/friends -CONFIG = $DEFAULTCONFIG BINARY = gnunet-daemon-topology [datastore] @@ -67,7 +62,6 @@ UNIX_MATCH_GID = YES PORT = 20050 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-datastore ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -90,7 +84,6 @@ AUTOSTART = YES PORT = 20049 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-peerinfo ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -114,15 +107,14 @@ AUTOSTART = YES PORT = 20048 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-ats ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; UNIXPATH = /tmp/test-service-ats-37 UNIX_MATCH_UID = YES UNIX_MATCH_GID = YES -WAN_QUOTA_IN = 65536 -WAN_QUOTA_OUT = 65536 +WAN_QUOTA_IN = unlimited +WAN_QUOTA_OUT = unlimited DUMP_MLP = NO DUMP_SOLUTION = NO DUMP_OVERWRITE = NO @@ -136,7 +128,6 @@ AUTOSTART = YES PORT = 20047 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-transport NEIGHBOUR_LIMIT = 50 ACCEPT_FROM = 127.0.0.1; @@ -188,7 +179,6 @@ AUTOSTART = NO PORT = 20042 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-template ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -206,7 +196,6 @@ UPDATE_DIR = $SERVICEHOME/updates/ PORT = 20041 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-fs ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -221,7 +210,6 @@ MIN_MIGRATION_DELAY = 100 ms EXPECTED_NEIGHBOUR_COUNT = 128 [vpn] -CONFIG = $DEFAULTCONFIG BINARY = gnunet-daemon-vpn IPV6ADDR = 1234::1 IPV6PREFIX = 32 @@ -232,7 +220,6 @@ VIRTDNS6 = 1234::17 IFNAME = vpn-gnunet [exit] -CONFIG = $DEFAULTCONFIG BINARY = gnunet-daemon-exit IPV6ADDR = 1234:1::1 IPV6PREFIX = 32 @@ -247,7 +234,6 @@ AUTOSTART = YES PORT = 0 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-dns ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -258,7 +244,6 @@ PROVIDE_EXIT = NO PORT = 20040 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-arm ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -271,7 +256,6 @@ UNIX_MATCH_GID = YES HTTPPORT = 8080 HOME = $SERVICEHOME HOSTLISTFILE = $SERVICEHOME/hostlist/learned.data -CONFIG = $DEFAULTCONFIG BINARY = gnunet-daemon-hostlist OPTIONS = -b SERVERS = http://localhost:8080/ @@ -282,7 +266,6 @@ AUTOSTART = YES PORT = 20039 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-core ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -316,7 +299,6 @@ AUTOSTART = YES PORT = 20037 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-statistics ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -329,7 +311,6 @@ AUTOSTART = YES PORT = 20036 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-dht ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -342,6 +323,16 @@ UNIX_MATCH_GID = YES DATABASE = sqlite QUOTA = 1 MB +[chat] +UNIXPATH = /tmp/test-service-chat-b_no_nat_c-2 +UNIX_MATCH_UID = YES +UNIX_MATCH_GID = YES + +[dv] +UNIXPATH = /tmp/test-service-dv-b_no_nat_c-2 +UNIX_MATCH_UID = YES +UNIX_MATCH_GID = YES + [gns] AUTOSTART = NO @@ -349,3 +340,7 @@ AUTOSTART = NO AUTOSTART = NO +[consensus] +AUTOSTART = NO + + diff --git a/src/integration-tests/confs/c_no_nat_client_http.conf b/src/integration-tests/confs/c_no_nat_client_http.conf index 718794e..c0c4aa8 100644 --- a/src/integration-tests/confs/c_no_nat_client_http.conf +++ b/src/integration-tests/confs/c_no_nat_client_http.conf @@ -1,6 +1,5 @@ [PATHS] SERVICEHOME = /tmp/c_no_nat_client/ -DEFAULTCONFIG = confs/c_no_nat_client_http.conf [gnunetd] #HOSTKEY = $SERVICEHOME/.hostkey @@ -17,7 +16,6 @@ AUTOSTART = YES PORT = 0 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-dns ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -28,7 +26,6 @@ AUTOSTART = YES PORT = 20035 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-resolver ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -41,7 +38,6 @@ AUTOSTART = YES PORT = 20034 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-mesh ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -54,7 +50,6 @@ AUTOSTART = YES PORT = 20033 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-nse ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -65,7 +60,7 @@ PROOFFILE = $SERVICEHOME/.nse-proof HISTOGRAM = $SERVICEHOME/nse-history.log WORKDELAY = 5 ms INTERVAL = 1 h -WORKBITS = 26 +WORKBITS = 1 [topology] MINIMUM-FRIENDS = 0 @@ -73,7 +68,6 @@ FRIENDS-ONLY = NO AUTOCONNECT = YES TARGET-CONNECTION-COUNT = 16 FRIENDS = $SERVICEHOME/friends -CONFIG = $DEFAULTCONFIG BINARY = gnunet-daemon-topology [datastore] @@ -84,7 +78,6 @@ UNIX_MATCH_GID = YES PORT = 20032 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-datastore ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -107,7 +100,6 @@ AUTOSTART = YES PORT = 20031 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-peerinfo ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -131,15 +123,14 @@ AUTOSTART = YES PORT = 20030 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-ats ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; UNIXPATH = /tmp/test-service-ats-23 UNIX_MATCH_UID = YES UNIX_MATCH_GID = YES -WAN_QUOTA_IN = 65536 -WAN_QUOTA_OUT = 65536 +WAN_QUOTA_IN = unlimited +WAN_QUOTA_OUT = unlimited DUMP_MLP = NO DUMP_SOLUTION = NO DUMP_OVERWRITE = NO @@ -150,12 +141,10 @@ ATS_EXEC_INTERVAL = 30000 [transport] PREFIX = valgrind --leak-check=full -#DEBUG = YES AUTOSTART = YES PORT = 20029 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-transport NEIGHBOUR_LIMIT = 50 ACCEPT_FROM = 127.0.0.1; @@ -207,7 +196,6 @@ AUTOSTART = NO PORT = 20024 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-template ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -225,7 +213,6 @@ UPDATE_DIR = $SERVICEHOME/updates/ PORT = 20023 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-fs ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -240,7 +227,6 @@ MIN_MIGRATION_DELAY = 100 ms EXPECTED_NEIGHBOUR_COUNT = 128 [vpn] -CONFIG = $DEFAULTCONFIG BINARY = gnunet-daemon-vpn IPV6ADDR = 1234::1 IPV6PREFIX = 32 @@ -251,7 +237,6 @@ VIRTDNS6 = 1234::17 IFNAME = vpn-gnunet [exit] -CONFIG = $DEFAULTCONFIG BINARY = gnunet-daemon-exit IPV6ADDR = 1234:1::1 IPV6PREFIX = 32 @@ -266,7 +251,6 @@ AUTOSTART = YES PORT = 0 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-dns ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -277,7 +261,6 @@ PROVIDE_EXIT = NO PORT = 20022 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-arm ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -290,7 +273,6 @@ UNIX_MATCH_GID = YES HTTPPORT = 8080 HOME = $SERVICEHOME HOSTLISTFILE = $SERVICEHOME/hostlist/learned.data -CONFIG = $DEFAULTCONFIG BINARY = gnunet-daemon-hostlist OPTIONS = -b SERVERS = http://localhost:8080/ @@ -301,7 +283,6 @@ AUTOSTART = YES PORT = 20021 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-core ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -335,7 +316,6 @@ AUTOSTART = YES PORT = 20019 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-statistics ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -348,7 +328,6 @@ AUTOSTART = YES PORT = 20018 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-dht ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -357,7 +336,21 @@ UNIXPATH = /tmp/test-service-dht-15 UNIX_MATCH_UID = YES UNIX_MATCH_GID = YES +[chat] +UNIXPATH = /tmp/test-service-chat-b_no_nat_http_c-1 +UNIX_MATCH_UID = YES +UNIX_MATCH_GID = YES + +[dv] +UNIXPATH = /tmp/test-service-dv-b_no_nat_http_c-1 +UNIX_MATCH_UID = YES +UNIX_MATCH_GID = YES + [dhtcache] DATABASE = sqlite QUOTA = 1 MB +[consensus] +AUTOSTART = NO + + diff --git a/src/integration-tests/confs/c_no_nat_client_http_2.conf b/src/integration-tests/confs/c_no_nat_client_http_2.conf index 3acb6b1..935b0b3 100644 --- a/src/integration-tests/confs/c_no_nat_client_http_2.conf +++ b/src/integration-tests/confs/c_no_nat_client_http_2.conf @@ -1,6 +1,5 @@ [PATHS] SERVICEHOME = /tmp/c_no_nat_client_2/ -DEFAULTCONFIG = confs/c_no_nat_client_http_2.conf [gnunetd] #HOSTKEY = $SERVICEHOME/.hostkey @@ -17,7 +16,6 @@ AUTOSTART = YES PORT = 20053 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-resolver ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -30,7 +28,6 @@ AUTOSTART = YES PORT = 20052 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-mesh ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -43,7 +40,6 @@ AUTOSTART = YES PORT = 20051 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-nse ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -54,7 +50,7 @@ PROOFFILE = $SERVICEHOME/.nse-proof HISTOGRAM = $SERVICEHOME/nse-history.log WORKDELAY = 5 ms INTERVAL = 1 h -WORKBITS = 26 +WORKBITS = 1 [topology] MINIMUM-FRIENDS = 0 @@ -62,7 +58,6 @@ FRIENDS-ONLY = NO AUTOCONNECT = YES TARGET-CONNECTION-COUNT = 16 FRIENDS = $SERVICEHOME/friends -CONFIG = $DEFAULTCONFIG BINARY = gnunet-daemon-topology [datastore] @@ -73,7 +68,6 @@ UNIX_MATCH_GID = YES PORT = 20050 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-datastore ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -96,7 +90,6 @@ AUTOSTART = YES PORT = 20049 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-peerinfo ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -120,15 +113,14 @@ AUTOSTART = YES PORT = 20048 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-ats ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; UNIXPATH = /tmp/test-service-ats-37 UNIX_MATCH_UID = YES UNIX_MATCH_GID = YES -WAN_QUOTA_IN = 65536 -WAN_QUOTA_OUT = 65536 +WAN_QUOTA_IN = unlimited +WAN_QUOTA_OUT = unlimited DUMP_MLP = NO DUMP_SOLUTION = NO DUMP_OVERWRITE = NO @@ -144,7 +136,6 @@ AUTOSTART = YES PORT = 20047 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-transport NEIGHBOUR_LIMIT = 50 ACCEPT_FROM = 127.0.0.1; @@ -196,7 +187,6 @@ AUTOSTART = NO PORT = 20042 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-template ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -214,7 +204,6 @@ UPDATE_DIR = $SERVICEHOME/updates/ PORT = 20041 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-fs ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -229,7 +218,6 @@ MIN_MIGRATION_DELAY = 100 ms EXPECTED_NEIGHBOUR_COUNT = 128 [vpn] -CONFIG = $DEFAULTCONFIG BINARY = gnunet-daemon-vpn IPV6ADDR = 1234::1 IPV6PREFIX = 32 @@ -240,7 +228,6 @@ VIRTDNS6 = 1234::17 IFNAME = vpn-gnunet [exit] -CONFIG = $DEFAULTCONFIG BINARY = gnunet-daemon-exit IPV6ADDR = 1234:1::1 IPV6PREFIX = 32 @@ -255,7 +242,6 @@ AUTOSTART = YES PORT = 0 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-dns ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -266,7 +252,6 @@ PROVIDE_EXIT = NO PORT = 20040 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-arm ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -279,7 +264,6 @@ UNIX_MATCH_GID = YES HTTPPORT = 8080 HOME = $SERVICEHOME HOSTLISTFILE = $SERVICEHOME/hostlist/learned.data -CONFIG = $DEFAULTCONFIG BINARY = gnunet-daemon-hostlist OPTIONS = -b SERVERS = http://localhost:8080/ @@ -290,7 +274,6 @@ AUTOSTART = YES PORT = 20039 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-core ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -324,7 +307,6 @@ AUTOSTART = YES PORT = 20037 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-statistics ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -337,7 +319,6 @@ AUTOSTART = YES PORT = 20036 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-dht ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -350,3 +331,17 @@ UNIX_MATCH_GID = YES DATABASE = sqlite QUOTA = 1 MB +[chat] +UNIXPATH = /tmp/test-service-chat-b_no_nat_http_c-2 +UNIX_MATCH_UID = YES +UNIX_MATCH_GID = YES + +[dv] +UNIXPATH = /tmp/test-service-dv-b_no_nat_http_c-2 +UNIX_MATCH_UID = YES +UNIX_MATCH_GID = YES + +[consensus] +AUTOSTART = NO + + diff --git a/src/integration-tests/confs/c_no_nat_client_unix.conf b/src/integration-tests/confs/c_no_nat_client_unix.conf index 37c5ad6..56f55dd 100644 --- a/src/integration-tests/confs/c_no_nat_client_unix.conf +++ b/src/integration-tests/confs/c_no_nat_client_unix.conf @@ -1,6 +1,5 @@ [PATHS] SERVICEHOME = /tmp/c_no_nat_client/ -DEFAULTCONFIG = confs/c_no_nat_client_unix.conf [gnunetd] #HOSTKEY = $SERVICEHOME/.hostkey @@ -17,7 +16,6 @@ AUTOSTART = YES PORT = 0 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-dns ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -28,7 +26,6 @@ AUTOSTART = YES PORT = 20035 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-resolver ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -41,7 +38,6 @@ AUTOSTART = YES PORT = 20034 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-mesh ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -54,7 +50,6 @@ AUTOSTART = YES PORT = 20033 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-nse ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -65,7 +60,7 @@ PROOFFILE = $SERVICEHOME/.nse-proof HISTOGRAM = $SERVICEHOME/nse-history.log WORKDELAY = 5 ms INTERVAL = 1 h -WORKBITS = 26 +WORKBITS = 1 [topology] MINIMUM-FRIENDS = 0 @@ -73,7 +68,6 @@ FRIENDS-ONLY = NO AUTOCONNECT = YES TARGET-CONNECTION-COUNT = 16 FRIENDS = $SERVICEHOME/friends -CONFIG = $DEFAULTCONFIG BINARY = gnunet-daemon-topology [datastore] @@ -84,7 +78,6 @@ UNIX_MATCH_GID = YES PORT = 20032 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-datastore ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -107,7 +100,6 @@ AUTOSTART = YES PORT = 20031 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-peerinfo ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -131,15 +123,14 @@ AUTOSTART = YES PORT = 20030 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-ats ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; UNIXPATH = /tmp/test-service-ats-23 UNIX_MATCH_UID = YES UNIX_MATCH_GID = YES -WAN_QUOTA_IN = 65536 -WAN_QUOTA_OUT = 65536 +WAN_QUOTA_IN = unlimited +WAN_QUOTA_OUT = unlimited DUMP_MLP = NO DUMP_SOLUTION = NO DUMP_OVERWRITE = NO @@ -150,12 +141,10 @@ ATS_EXEC_INTERVAL = 30000 [transport] PREFIX = valgrind --leak-check=full -#DEBUG = YES AUTOSTART = YES PORT = 20029 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-transport NEIGHBOUR_LIMIT = 50 ACCEPT_FROM = 127.0.0.1; @@ -210,7 +199,6 @@ AUTOSTART = NO PORT = 20024 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-template ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -228,7 +216,6 @@ UPDATE_DIR = $SERVICEHOME/updates/ PORT = 20023 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-fs ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -243,7 +230,6 @@ MIN_MIGRATION_DELAY = 100 ms EXPECTED_NEIGHBOUR_COUNT = 128 [vpn] -CONFIG = $DEFAULTCONFIG BINARY = gnunet-daemon-vpn IPV6ADDR = 1234::1 IPV6PREFIX = 32 @@ -254,7 +240,6 @@ VIRTDNS6 = 1234::17 IFNAME = vpn-gnunet [exit] -CONFIG = $DEFAULTCONFIG BINARY = gnunet-daemon-exit IPV6ADDR = 1234:1::1 IPV6PREFIX = 32 @@ -269,7 +254,6 @@ AUTOSTART = YES PORT = 0 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-dns ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -280,7 +264,6 @@ PROVIDE_EXIT = NO PORT = 20022 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-arm ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -293,7 +276,6 @@ UNIX_MATCH_GID = YES HTTPPORT = 8080 HOME = $SERVICEHOME HOSTLISTFILE = $SERVICEHOME/hostlist/learned.data -CONFIG = $DEFAULTCONFIG BINARY = gnunet-daemon-hostlist OPTIONS = -b SERVERS = http://localhost:8080/ @@ -304,7 +286,6 @@ AUTOSTART = YES PORT = 20021 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-core ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -338,7 +319,6 @@ AUTOSTART = YES PORT = 20019 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-statistics ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -351,7 +331,6 @@ AUTOSTART = YES PORT = 20018 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-dht ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -360,7 +339,21 @@ UNIXPATH = /tmp/test-service-dht-15 UNIX_MATCH_UID = YES UNIX_MATCH_GID = YES +[chat] +UNIXPATH = /tmp/test-service-chat-b_no_nat_unix_c-1 +UNIX_MATCH_UID = YES +UNIX_MATCH_GID = YES + +[dv] +UNIXPATH = /tmp/test-service-dv-b_no_nat_unix_c-1 +UNIX_MATCH_UID = YES +UNIX_MATCH_GID = YES + [dhtcache] DATABASE = sqlite QUOTA = 1 MB +[consensus] +AUTOSTART = NO + + diff --git a/src/integration-tests/confs/c_no_nat_client_unix_2.conf b/src/integration-tests/confs/c_no_nat_client_unix_2.conf index 6bf8e8b..463bebb 100644 --- a/src/integration-tests/confs/c_no_nat_client_unix_2.conf +++ b/src/integration-tests/confs/c_no_nat_client_unix_2.conf @@ -1,6 +1,5 @@ [PATHS] SERVICEHOME = /tmp/c_no_nat_client_2/ -DEFAULTCONFIG = confs/c_no_nat_client_unix_2.conf [gnunetd] #HOSTKEY = $SERVICEHOME/.hostkey @@ -17,7 +16,6 @@ AUTOSTART = YES PORT = 20053 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-resolver ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -30,7 +28,6 @@ AUTOSTART = YES PORT = 20052 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-mesh ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -43,7 +40,6 @@ AUTOSTART = YES PORT = 20051 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-nse ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -54,7 +50,7 @@ PROOFFILE = $SERVICEHOME/.nse-proof HISTOGRAM = $SERVICEHOME/nse-history.log WORKDELAY = 5 ms INTERVAL = 1 h -WORKBITS = 26 +WORKBITS = 1 [topology] MINIMUM-FRIENDS = 0 @@ -62,7 +58,6 @@ FRIENDS-ONLY = NO AUTOCONNECT = YES TARGET-CONNECTION-COUNT = 16 FRIENDS = $SERVICEHOME/friends -CONFIG = $DEFAULTCONFIG BINARY = gnunet-daemon-topology [datastore] @@ -73,7 +68,6 @@ UNIX_MATCH_GID = YES PORT = 20050 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-datastore ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -96,7 +90,6 @@ AUTOSTART = YES PORT = 20049 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-peerinfo ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -120,15 +113,14 @@ AUTOSTART = YES PORT = 20048 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-ats ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; UNIXPATH = /tmp/test-service-ats-37 UNIX_MATCH_UID = YES UNIX_MATCH_GID = YES -WAN_QUOTA_IN = 65536 -WAN_QUOTA_OUT = 65536 +WAN_QUOTA_IN = unlimited +WAN_QUOTA_OUT = unlimited DUMP_MLP = NO DUMP_SOLUTION = NO DUMP_OVERWRITE = NO @@ -144,7 +136,6 @@ AUTOSTART = YES PORT = 20047 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-transport NEIGHBOUR_LIMIT = 50 ACCEPT_FROM = 127.0.0.1; @@ -199,7 +190,6 @@ AUTOSTART = NO PORT = 20042 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-template ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -217,7 +207,6 @@ UPDATE_DIR = $SERVICEHOME/updates/ PORT = 20041 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-fs ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -232,7 +221,6 @@ MIN_MIGRATION_DELAY = 100 ms EXPECTED_NEIGHBOUR_COUNT = 128 [vpn] -CONFIG = $DEFAULTCONFIG BINARY = gnunet-daemon-vpn IPV6ADDR = 1234::1 IPV6PREFIX = 32 @@ -243,7 +231,6 @@ VIRTDNS6 = 1234::17 IFNAME = vpn-gnunet [exit] -CONFIG = $DEFAULTCONFIG BINARY = gnunet-daemon-exit IPV6ADDR = 1234:1::1 IPV6PREFIX = 32 @@ -258,7 +245,6 @@ AUTOSTART = YES PORT = 0 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-dns ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -269,7 +255,6 @@ PROVIDE_EXIT = NO PORT = 20040 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-arm ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -282,7 +267,6 @@ UNIX_MATCH_GID = YES HTTPPORT = 8080 HOME = $SERVICEHOME HOSTLISTFILE = $SERVICEHOME/hostlist/learned.data -CONFIG = $DEFAULTCONFIG BINARY = gnunet-daemon-hostlist OPTIONS = -b SERVERS = http://localhost:8080/ @@ -293,7 +277,6 @@ AUTOSTART = YES PORT = 20039 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-core ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -327,7 +310,6 @@ AUTOSTART = YES PORT = 20037 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-statistics ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -340,7 +322,6 @@ AUTOSTART = YES PORT = 20036 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-dht ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -349,7 +330,21 @@ UNIXPATH = /tmp/test-service-dht-29 UNIX_MATCH_UID = YES UNIX_MATCH_GID = YES +[chat] +UNIXPATH = /tmp/test-service-chat-b_no_nat_unix_c-2 +UNIX_MATCH_UID = YES +UNIX_MATCH_GID = YES + +[dv] +UNIXPATH = /tmp/test-service-dv-b_no_nat_unix_c-2 +UNIX_MATCH_UID = YES +UNIX_MATCH_GID = YES + [dhtcache] DATABASE = sqlite QUOTA = 1 MB +[consensus] +AUTOSTART = NO + + diff --git a/src/integration-tests/confs/c_normal_client_tcp.conf b/src/integration-tests/confs/c_normal_client_tcp.conf index 45acdaf..ec8098c 100644 --- a/src/integration-tests/confs/c_normal_client_tcp.conf +++ b/src/integration-tests/confs/c_normal_client_tcp.conf @@ -1,6 +1,5 @@ [PATHS] SERVICEHOME = /tmp/c_normal_client -DEFAULTCONFIG = confs/c_normal_client_tcp.conf [gnunetd] HOSTKEY = hostkeys/0002-hostkey @@ -19,7 +18,6 @@ AUTOSTART = YES PORT = 0 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-dns ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -31,7 +29,6 @@ AUTOSTART = YES PORT = 20071 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-resolver ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -44,7 +41,6 @@ AUTOSTART = YES PORT = 20070 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-mesh ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -57,7 +53,6 @@ AUTOSTART = YES PORT = 20069 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-nse ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -68,7 +63,7 @@ PROOFFILE = $SERVICEHOME/.nse-proof HISTOGRAM = $SERVICEHOME/nse-history.log WORKDELAY = 5 ms INTERVAL = 1 h -WORKBITS = 26 +WORKBITS = 1 [topology] MINIMUM-FRIENDS = 0 @@ -76,7 +71,6 @@ FRIENDS-ONLY = NO AUTOCONNECT = YES TARGET-CONNECTION-COUNT = 16 FRIENDS = $SERVICEHOME/friends -CONFIG = $DEFAULTCONFIG BINARY = gnunet-daemon-topology [datastore] @@ -87,7 +81,6 @@ UNIX_MATCH_GID = YES PORT = 20068 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-datastore ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -110,7 +103,6 @@ AUTOSTART = YES PORT = 20067 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-peerinfo ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -131,15 +123,14 @@ AUTOSTART = YES PORT = 20066 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-ats ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; UNIXPATH = /tmp/test-service-ats-51 UNIX_MATCH_UID = YES UNIX_MATCH_GID = YES -WAN_QUOTA_IN = 65536 -WAN_QUOTA_OUT = 65536 +WAN_QUOTA_IN = unlimited +WAN_QUOTA_OUT = unlimited DUMP_MLP = NO DUMP_SOLUTION = NO DUMP_OVERWRITE = NO @@ -153,7 +144,6 @@ AUTOSTART = YES PORT = 20065 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-transport NEIGHBOUR_LIMIT = 50 ACCEPT_FROM = 127.0.0.1; @@ -205,7 +195,6 @@ AUTOSTART = NO PORT = 20060 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-template ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -223,7 +212,6 @@ UPDATE_DIR = $SERVICEHOME/updates/ PORT = 20059 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-fs ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -238,7 +226,6 @@ MIN_MIGRATION_DELAY = 100 ms EXPECTED_NEIGHBOUR_COUNT = 128 [vpn] -CONFIG = $DEFAULTCONFIG BINARY = gnunet-daemon-vpn IPV6ADDR = 1234::1 IPV6PREFIX = 32 @@ -249,7 +236,6 @@ VIRTDNS6 = 1234::17 IFNAME = vpn-gnunet [exit] -CONFIG = $DEFAULTCONFIG BINARY = gnunet-daemon-exit IPV6ADDR = 1234:1::1 IPV6PREFIX = 32 @@ -264,7 +250,6 @@ AUTOSTART = YES PORT = 0 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-dns ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -275,7 +260,6 @@ PROVIDE_EXIT = NO PORT = 20058 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-arm ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -288,7 +272,6 @@ UNIX_MATCH_GID = YES HTTPPORT = 8080 HOME = $SERVICEHOME HOSTLISTFILE = $SERVICEHOME/hostlist/learned.data -CONFIG = $DEFAULTCONFIG BINARY = gnunet-daemon-hostlist OPTIONS = -b SERVERS = http://v9.gnunet.org/hostlist http://ioerror.gnunet.org:65535/ @@ -299,7 +282,6 @@ AUTOSTART = YES PORT = 20057 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-core ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -333,7 +315,6 @@ AUTOSTART = YES PORT = 20055 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-statistics ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -346,7 +327,6 @@ AUTOSTART = YES PORT = 20054 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-dht ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -355,6 +335,20 @@ UNIXPATH = /tmp/test-service-dht-43 UNIX_MATCH_UID = YES UNIX_MATCH_GID = YES +[chat] +UNIXPATH = /tmp/test-service-chat-c_normal_client_tcp-1 +UNIX_MATCH_UID = YES +UNIX_MATCH_GID = YES + +[dv] +UNIXPATH = /tmp/test-service-dv-b_c_normal_client_tcp-1 +UNIX_MATCH_UID = YES +UNIX_MATCH_GID = YES + [dhtcache] DATABASE = sqlite -QUOTA = 1 MB \ No newline at end of file +QUOTA = 1 MB +[consensus] +AUTOSTART = NO + + diff --git a/src/integration-tests/confs/c_normal_client_tcp_udp.conf b/src/integration-tests/confs/c_normal_client_tcp_udp.conf index e568f12..415056f 100644 --- a/src/integration-tests/confs/c_normal_client_tcp_udp.conf +++ b/src/integration-tests/confs/c_normal_client_tcp_udp.conf @@ -1,6 +1,5 @@ [PATHS] SERVICEHOME = /tmp/c_normal_client -DEFAULTCONFIG = confs/c_normal_client_tcp_udp.conf [gnunetd] HOSTKEY = hostkeys/0002-hostkey @@ -19,7 +18,6 @@ AUTOSTART = YES PORT = 0 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-dns ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -31,7 +29,6 @@ AUTOSTART = YES PORT = 20071 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-resolver ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -44,7 +41,6 @@ AUTOSTART = YES PORT = 20070 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-mesh ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -57,7 +53,6 @@ AUTOSTART = YES PORT = 20069 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-nse ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -68,7 +63,7 @@ PROOFFILE = $SERVICEHOME/.nse-proof HISTOGRAM = $SERVICEHOME/nse-history.log WORKDELAY = 5 ms INTERVAL = 1 h -WORKBITS = 26 +WORKBITS = 1 [topology] MINIMUM-FRIENDS = 0 @@ -76,7 +71,6 @@ FRIENDS-ONLY = NO AUTOCONNECT = YES TARGET-CONNECTION-COUNT = 16 FRIENDS = $SERVICEHOME/friends -CONFIG = $DEFAULTCONFIG BINARY = gnunet-daemon-topology [datastore] @@ -87,7 +81,6 @@ UNIX_MATCH_GID = YES PORT = 20068 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-datastore ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -110,7 +103,6 @@ AUTOSTART = YES PORT = 20067 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-peerinfo ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -131,15 +123,14 @@ AUTOSTART = YES PORT = 20066 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-ats ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; UNIXPATH = /tmp/test-service-ats-51 UNIX_MATCH_UID = YES UNIX_MATCH_GID = YES -WAN_QUOTA_IN = 65536 -WAN_QUOTA_OUT = 65536 +WAN_QUOTA_IN = unlimited +WAN_QUOTA_OUT = unlimited DUMP_MLP = NO DUMP_SOLUTION = NO DUMP_OVERWRITE = NO @@ -153,7 +144,6 @@ AUTOSTART = YES PORT = 20065 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-transport NEIGHBOUR_LIMIT = 50 ACCEPT_FROM = 127.0.0.1; @@ -205,7 +195,6 @@ AUTOSTART = NO PORT = 20060 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-template ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -223,7 +212,6 @@ UPDATE_DIR = $SERVICEHOME/updates/ PORT = 20059 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-fs ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -238,7 +226,6 @@ MIN_MIGRATION_DELAY = 100 ms EXPECTED_NEIGHBOUR_COUNT = 128 [vpn] -CONFIG = $DEFAULTCONFIG BINARY = gnunet-daemon-vpn IPV6ADDR = 1234::1 IPV6PREFIX = 32 @@ -249,7 +236,6 @@ VIRTDNS6 = 1234::17 IFNAME = vpn-gnunet [exit] -CONFIG = $DEFAULTCONFIG BINARY = gnunet-daemon-exit IPV6ADDR = 1234:1::1 IPV6PREFIX = 32 @@ -264,7 +250,6 @@ AUTOSTART = YES PORT = 0 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-dns ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -275,7 +260,6 @@ PROVIDE_EXIT = NO PORT = 20058 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-arm ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -288,7 +272,6 @@ UNIX_MATCH_GID = YES HTTPPORT = 8080 HOME = $SERVICEHOME HOSTLISTFILE = $SERVICEHOME/hostlist/learned.data -CONFIG = $DEFAULTCONFIG BINARY = gnunet-daemon-hostlist OPTIONS = -b SERVERS = http://v9.gnunet.org/hostlist http://ioerror.gnunet.org:65535/ @@ -299,7 +282,6 @@ AUTOSTART = YES PORT = 20057 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-core ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -333,7 +315,6 @@ AUTOSTART = YES PORT = 20055 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-statistics ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -346,7 +327,6 @@ AUTOSTART = YES PORT = 20054 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-dht ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -355,6 +335,20 @@ UNIXPATH = /tmp/test-service-dht-43 UNIX_MATCH_UID = YES UNIX_MATCH_GID = YES +[chat] +UNIXPATH = /tmp/test-service-chat-c_normal_client_tcp_udp-1 +UNIX_MATCH_UID = YES +UNIX_MATCH_GID = YES + +[dv] +UNIXPATH = /tmp/test-service-dv-b_c_normal_client_tcp_udp-1 +UNIX_MATCH_UID = YES +UNIX_MATCH_GID = YES + [dhtcache] DATABASE = sqlite -QUOTA = 1 MB \ No newline at end of file +QUOTA = 1 MB +[consensus] +AUTOSTART = NO + + diff --git a/src/integration-tests/confs/c_normal_client_tcp_udp_http.conf b/src/integration-tests/confs/c_normal_client_tcp_udp_http.conf index 93275bf..6edd8cc 100644 --- a/src/integration-tests/confs/c_normal_client_tcp_udp_http.conf +++ b/src/integration-tests/confs/c_normal_client_tcp_udp_http.conf @@ -1,6 +1,5 @@ [PATHS] SERVICEHOME = /tmp/c_normal_client -DEFAULTCONFIG = confs/c_normal_client_tcp_udp_http.conf [gnunetd] HOSTKEY = hostkeys/0002-hostkey @@ -19,7 +18,6 @@ AUTOSTART = YES PORT = 0 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-dns ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -31,7 +29,6 @@ AUTOSTART = YES PORT = 20071 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-resolver ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -44,7 +41,6 @@ AUTOSTART = YES PORT = 20070 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-mesh ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -57,7 +53,6 @@ AUTOSTART = YES PORT = 20069 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-nse ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -68,7 +63,7 @@ PROOFFILE = $SERVICEHOME/.nse-proof HISTOGRAM = $SERVICEHOME/nse-history.log WORKDELAY = 5 ms INTERVAL = 1 h -WORKBITS = 26 +WORKBITS = 1 [topology] MINIMUM-FRIENDS = 0 @@ -76,7 +71,6 @@ FRIENDS-ONLY = NO AUTOCONNECT = YES TARGET-CONNECTION-COUNT = 16 FRIENDS = $SERVICEHOME/friends -CONFIG = $DEFAULTCONFIG BINARY = gnunet-daemon-topology [datastore] @@ -87,7 +81,6 @@ UNIX_MATCH_GID = YES PORT = 20068 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-datastore ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -110,7 +103,6 @@ AUTOSTART = YES PORT = 20067 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-peerinfo ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -131,15 +123,14 @@ AUTOSTART = YES PORT = 20066 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-ats ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; UNIXPATH = /tmp/test-service-ats-51 UNIX_MATCH_UID = YES UNIX_MATCH_GID = YES -WAN_QUOTA_IN = 65536 -WAN_QUOTA_OUT = 65536 +WAN_QUOTA_IN = unlimited +WAN_QUOTA_OUT = unlimited DUMP_MLP = NO DUMP_SOLUTION = NO DUMP_OVERWRITE = NO @@ -153,7 +144,6 @@ AUTOSTART = YES PORT = 20065 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-transport NEIGHBOUR_LIMIT = 50 ACCEPT_FROM = 127.0.0.1; @@ -205,7 +195,6 @@ AUTOSTART = NO PORT = 20060 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-template ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -223,7 +212,6 @@ UPDATE_DIR = $SERVICEHOME/updates/ PORT = 20059 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-fs ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -238,7 +226,6 @@ MIN_MIGRATION_DELAY = 100 ms EXPECTED_NEIGHBOUR_COUNT = 128 [vpn] -CONFIG = $DEFAULTCONFIG BINARY = gnunet-daemon-vpn IPV6ADDR = 1234::1 IPV6PREFIX = 32 @@ -249,7 +236,6 @@ VIRTDNS6 = 1234::17 IFNAME = vpn-gnunet [exit] -CONFIG = $DEFAULTCONFIG BINARY = gnunet-daemon-exit IPV6ADDR = 1234:1::1 IPV6PREFIX = 32 @@ -264,7 +250,6 @@ AUTOSTART = YES PORT = 0 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-dns ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -275,7 +260,6 @@ PROVIDE_EXIT = NO PORT = 20058 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-arm ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -288,7 +272,6 @@ UNIX_MATCH_GID = YES HTTPPORT = 8080 HOME = $SERVICEHOME HOSTLISTFILE = $SERVICEHOME/hostlist/learned.data -CONFIG = $DEFAULTCONFIG BINARY = gnunet-daemon-hostlist OPTIONS = -b SERVERS = http://v9.gnunet.org/hostlist http://ioerror.gnunet.org:65535/ @@ -299,7 +282,6 @@ AUTOSTART = YES PORT = 20057 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-core ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -333,7 +315,6 @@ AUTOSTART = YES PORT = 20055 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-statistics ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -346,7 +327,6 @@ AUTOSTART = YES PORT = 20054 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-dht ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -355,6 +335,20 @@ UNIXPATH = /tmp/test-service-dht-43 UNIX_MATCH_UID = YES UNIX_MATCH_GID = YES +[chat] +UNIXPATH = /tmp/test-service-chat-c_normal_client_tcp_udp_http +UNIX_MATCH_UID = YES +UNIX_MATCH_GID = YES + +[dv] +UNIXPATH = /tmp/test-service-dv-b_c_normal_client_tcp_udp_http +UNIX_MATCH_UID = YES +UNIX_MATCH_GID = YES + [dhtcache] DATABASE = sqlite -QUOTA = 1 MB \ No newline at end of file +QUOTA = 1 MB +[consensus] +AUTOSTART = NO + + diff --git a/src/integration-tests/connection_watchdog.c b/src/integration-tests/connection_watchdog.c index ac19338..0998a36 100644 --- a/src/integration-tests/connection_watchdog.c +++ b/src/integration-tests/connection_watchdog.c @@ -121,7 +121,7 @@ struct TransportPlugin *ptail; static int map_check_it (void *cls, - const GNUNET_HashCode * key, + const struct GNUNET_HashCode * key, void *value) { int *fail = cls; @@ -142,7 +142,7 @@ map_check_it (void *cls, static int map_cleanup_it (void *cls, - const GNUNET_HashCode * key, + const struct GNUNET_HashCode * key, void *value) { struct PeerContainer *pc = value; @@ -451,7 +451,7 @@ return mlen; int map_ping_it (void *cls, - const GNUNET_HashCode * key, + const struct GNUNET_HashCode * key, void *value) { struct PeerContainer *pc = value; @@ -572,6 +572,8 @@ map_connect (const struct GNUNET_PeerIdentity *peer, void * source) } pc = GNUNET_CONTAINER_multihashmap_get(peers, &peer->hashPubKey); + GNUNET_assert (NULL != pc); + if (source == th) { if (GNUNET_NO == pc->transport_connected) @@ -658,6 +660,8 @@ map_disconnect (const struct GNUNET_PeerIdentity * peer, void * source) } pc = GNUNET_CONTAINER_multihashmap_get(peers, &peer->hashPubKey); + GNUNET_assert (NULL != pc); + if (source == th) { if (NULL != pc->th_ping) @@ -1052,7 +1056,7 @@ run (void *cls, char *const *args, const char *cfgfile, init(); stats = GNUNET_STATISTICS_create ("watchdog", cfg); - peers = GNUNET_CONTAINER_multihashmap_create (20); + peers = GNUNET_CONTAINER_multihashmap_create (32, GNUNET_NO); th = GNUNET_TRANSPORT_connect(cfg, NULL, NULL, &transport_notify_receive_cb, @@ -1060,7 +1064,7 @@ run (void *cls, char *const *args, const char *cfgfile, &transport_notify_disconnect_cb); GNUNET_assert (th != NULL); GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Connected to transport service\n"); - ch = GNUNET_CORE_connect (cfg, 1, NULL, + ch = GNUNET_CORE_connect (cfg, NULL, &core_init_cb, &core_connect_cb, &core_disconnect_cb, @@ -1090,10 +1094,15 @@ main (int argc, char *const *argv) GNUNET_NO, &GNUNET_GETOPT_set_one, &ping}, GNUNET_GETOPT_OPTION_END }; - return (GNUNET_OK == - GNUNET_PROGRAM_run (argc, argv, "cn", - gettext_noop ("help text"), options, &run, - NULL)) ? ret : 1; + + if (GNUNET_OK != GNUNET_STRINGS_get_utf8_args (argc, argv, &argc, &argv)) + return 2; + ret = (GNUNET_OK == + GNUNET_PROGRAM_run (argc, argv, "cn", + gettext_noop ("help text"), options, &run, + NULL)) ? ret : 1; + GNUNET_free ((void*) argv); + return ret; } /* end of connection_watchdog.c */ diff --git a/src/integration-tests/gnunet_testing.py.in b/src/integration-tests/gnunet_testing.py.in index 41e709f..0e3cdaa 100644 --- a/src/integration-tests/gnunet_testing.py.in +++ b/src/integration-tests/gnunet_testing.py.in @@ -53,11 +53,13 @@ class Check: if ((False == res) and (execs >= timeout)): print ('Check had timeout after ' +str(timeout)+ ' seconds') neg_cont (self) - elif ((False == res) and (execs >= timeout)): - neg_cont (self) + elif ((False == res) and (execs < timeout)): + if (None != neg_cont): + neg_cont (self) else: - pos_cont (self) - return res + if (None != pos_cont): + pos_cont (self) + return res def run_once (self, pos_cont, neg_cont): execs = 0; res = False diff --git a/src/integration-tests/test_connection_stability.c b/src/integration-tests/test_connection_stability.c deleted file mode 100644 index ce6568b..0000000 --- a/src/integration-tests/test_connection_stability.c +++ /dev/null @@ -1,126 +0,0 @@ -/* - This file is part of GNUnet. - (C) 2009 Christian Grothoff (and other contributing authors) - - GNUnet is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published - by the Free Software Foundation; either version 3, or (at your - option) any later version. - - GNUnet is distributed in the hope that it will be useful, but - WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - General Public License for more details. - - You should have received a copy of the GNU General Public License - along with GNUnet; see the file COPYING. If not, write to the - Free Software Foundation, Inc., 59 Temple Place - Suite 330, - Boston, MA 02111-1307, USA. -*/ -/** - * @file integretion-tests/test_connection_stability.c - * @brief testcase for connection stability - */ -#include "platform.h" -#include "gnunet_testing_lib.h" - -#define VERBOSE GNUNET_YES - -#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 300) - -static int ok; - -static void -end_cb (void *cls, const char *emsg) -{ - if (emsg != NULL) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Ending with error: %s\n", emsg); - ok = 1; - } - else - { -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Daemon terminated, will now exit.\n"); -#endif - ok = 0; - } -} - - - -void -do_shutdown (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - struct GNUNET_TESTING_Daemon *d = cls; - - GNUNET_TESTING_daemon_stop (d, TIMEOUT, &end_cb, NULL, GNUNET_YES, GNUNET_NO); -} - - -static void -my_cb (void *cls, const struct GNUNET_PeerIdentity *id, - const struct GNUNET_CONFIGURATION_Handle *cfg, - struct GNUNET_TESTING_Daemon *d, const char *emsg) -{ - GNUNET_assert (id != NULL); -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Daemon `%s' started, will now stop it.\n", GNUNET_i2s (id)); -#endif - GNUNET_SCHEDULER_add_now (&do_shutdown, d); -} - - -static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) -{ - struct GNUNET_TESTING_Daemon *d; - - ok = 1; -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Starting daemon.\n"); -#endif - d = GNUNET_TESTING_daemon_start (cfg, TIMEOUT, GNUNET_NO, NULL, NULL, 0, NULL, - NULL, NULL, &my_cb, NULL); - GNUNET_assert (d != NULL); -} - -static int -check () -{ - char *const argv[] = { "test_connection_stability", - "-c", - "test_connection_stability.conf", -#if VERBOSE - "-L", "DEBUG", -#endif - NULL - }; - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - GNUNET_PROGRAM_run ((sizeof (argv) / sizeof (char *)) - 1, argv, - "test-testing", "nohelp", options, &run, &ok); - return ok; -} - -int -main (int argc, char *argv[]) -{ - int ret; - - GNUNET_log_setup ("test_connection_stability", -#if VERBOSE - "DEBUG", -#else - "WARNING", -#endif - NULL); - ret = check (); - - return ret; -} - -/* end of test_connection_stability.c */ diff --git a/src/integration-tests/test_connection_stability.conf b/src/integration-tests/test_connection_stability.conf deleted file mode 100644 index ba2ae05..0000000 --- a/src/integration-tests/test_connection_stability.conf +++ /dev/null @@ -1,82 +0,0 @@ -[PATHS] -SERVICEHOME = /tmp/test_connection_stability/ -DEFAULTCONFIG = test_connection_stability.conf - -[resolver] -PORT = 2564 - -[transport] -PORT = 2565 -PLUGINS = tcp - -[arm] -PORT = 2566 -DEFAULTSERVICES = - -[statistics] -PORT = 2567 - -[transport-tcp] -PORT = 2568 -BINDTO = 127.0.0.1 - -[peerinfo] -PORT = 2569 - -[core] -PORT = 2570 - -[testing] -NUM_PEERS = 5 -WEAKRANDOM = YES -F2F = YES -HOSTKEYSFILE = ../../contrib/testing_hostkeys.dat - -[dht] -AUTOSTART = NO - -[nat] -DISABLEV6 = YES -ENABLE_UPNP = NO -BEHIND_NAT = NO -ALLOW_NAT = NO -INTERNAL_ADDRESS = 127.0.0.1 -EXTERNAL_ADDRESS = 127.0.0.1 -USE_LOCALADDR = NO - -[dns] -AUTOSTART = NO - -[nse] -AUTOSTART = NO - -[mesh] -AUTOSTART = NO - -[datastore] -AUTOSTART = NO - -[fs] -AUTOSTART = NO - -[dv] -AUTOSTART = NO - -[chat] -AUTOSTART = NO - -[vpn] -AUTOSTART = NO - -[gns] -AUTOSTART = NO - -[namestore] -AUTOSTART = NO - -[lockmanager] -AUTOSTART = NO - -[arm] -DEFAULTSERVICES = core - diff --git a/src/integration-tests/test_integration_bootstrap_and_connect.py.in b/src/integration-tests/test_integration_bootstrap_and_connect.py.in index 1e71488..cd3bdbe 100755 --- a/src/integration-tests/test_integration_bootstrap_and_connect.py.in +++ b/src/integration-tests/test_integration_bootstrap_and_connect.py.in @@ -24,7 +24,6 @@ import subprocess import re import shutil import time -import pexpect from gnunet_testing import Peer from gnunet_testing import Test from gnunet_testing import Check @@ -52,14 +51,14 @@ testname = "test_integration_bootstrap_and_connect" verbose = True check_timeout = 180 +if os.name == "nt": + tmp = os.getenv ("TEMP") +else: + tmp = "/tmp" def cleanup (): - if os.name == "nt": - shutil.rmtree (os.path.join (os.getenv ("TEMP"), "gnunet-test-fs-py-ns"), True) - shutil.rmtree (os.path.join (os.getenv ("TEMP"), "c_no_nat_client"), True) - else: - shutil.rmtree ("/tmp/c_bootstrap_server/", True) - shutil.rmtree ("/tmp/c_no_nat_client/", True) + shutil.rmtree (os.path.join (tmp, "c_bootstrap_server"), True) + shutil.rmtree (os.path.join (tmp, "c_no_nat_client"), True) def success_cont (check): global success diff --git a/src/integration-tests/test_integration_bootstrap_and_connect_and_disconnect.py.in b/src/integration-tests/test_integration_bootstrap_and_connect_and_disconnect.py.in index aefb9cd..3ca0aea 100755 --- a/src/integration-tests/test_integration_bootstrap_and_connect_and_disconnect.py.in +++ b/src/integration-tests/test_integration_bootstrap_and_connect_and_disconnect.py.in @@ -24,7 +24,6 @@ import subprocess import re import shutil import time -import pexpect from gnunet_testing import Peer from gnunet_testing import Test from gnunet_testing import Check @@ -52,14 +51,14 @@ testname = "test_integration_bootstrap_and_connect" verbose = True check_timeout = 180 +if os.name == "nt": + tmp = os.getenv ("TEMP") +else: + tmp = "/tmp" def cleanup (): - if os.name == "nt": - shutil.rmtree (os.path.join (os.getenv ("TEMP"), "gnunet-test-fs-py-ns"), True) - shutil.rmtree (os.path.join (os.getenv ("TEMP"), "c_no_nat_client"), True) - else: - shutil.rmtree ("/tmp/c_bootstrap_server/", True) - shutil.rmtree ("/tmp/c_no_nat_client/", True) + shutil.rmtree (os.path.join (tmp, "c_bootstrap_server"), True) + shutil.rmtree (os.path.join (tmp, "c_no_nat_client"), True) def success_server_stop_cont (check): global success diff --git a/src/integration-tests/test_integration_bootstrap_and_connect_and_disconnect_nat.py.in b/src/integration-tests/test_integration_bootstrap_and_connect_and_disconnect_nat.py.in index 88327bf..55982c2 100755 --- a/src/integration-tests/test_integration_bootstrap_and_connect_and_disconnect_nat.py.in +++ b/src/integration-tests/test_integration_bootstrap_and_connect_and_disconnect_nat.py.in @@ -24,7 +24,6 @@ import subprocess import re import shutil import time -import pexpect from gnunet_testing import Peer from gnunet_testing import Test from gnunet_testing import Check @@ -52,14 +51,14 @@ testname = "test_integration_bootstrap_and_connect" verbose = True check_timeout = 180 +if os.name == "nt": + tmp = os.getenv ("TEMP") +else: + tmp = "/tmp" def cleanup (): - if os.name == "nt": - shutil.rmtree (os.path.join (os.getenv ("TEMP"), "gnunet-test-fs-py-ns"), True) - shutil.rmtree (os.path.join (os.getenv ("TEMP"), "c_no_nat_client"), True) - else: - shutil.rmtree ("/tmp/c_bootstrap_server/", True) - shutil.rmtree ("/tmp/c_no_nat_client/", True) + shutil.rmtree (os.path.join (tmp, "c_bootstrap_server"), True) + shutil.rmtree (os.path.join (tmp, "c_no_nat_client"), True) def success_server_stop_cont (check): global success diff --git a/src/integration-tests/test_integration_clique.py.in b/src/integration-tests/test_integration_clique.py.in index 65c9341..6c7a5d7 100755 --- a/src/integration-tests/test_integration_clique.py.in +++ b/src/integration-tests/test_integration_clique.py.in @@ -30,13 +30,16 @@ import subprocess import re import shutil import time -import pexpect from gnunet_testing import Peer from gnunet_testing import Test from gnunet_testing import Check from gnunet_testing import Condition from gnunet_testing import * +if os.name == "nt": + tmp = os.getenv ("TEMP") +else: + tmp = "/tmp" #definitions @@ -46,14 +49,9 @@ check_timeout = 180 def cleanup (): - if os.name == "nt": - shutil.rmtree (os.path.join (os.getenv ("TEMP"), "gnunet-test-fs-py-ns"), True) - shutil.rmtree (os.path.join (os.getenv ("TEMP"), "c_no_nat_client"), True) - shutil.rmtree (os.path.join (os.getenv ("TEMP"), "c_no_nat_client_2"), True) - else: - shutil.rmtree ("/tmp/c_bootstrap_server/", True) - shutil.rmtree ("/tmp/c_no_nat_client/", True) - shutil.rmtree ("/tmp/c_no_nat_client_2/", True) + shutil.rmtree (os.path.join (tmp, "c_bootstrap_server"), True) + shutil.rmtree (os.path.join (tmp, "c_no_nat_client"), True) + shutil.rmtree (os.path.join (tmp, "c_no_nat_client_2"), True) def success_cont (check): diff --git a/src/integration-tests/test_integration_clique_nat.py.in b/src/integration-tests/test_integration_clique_nat.py.in index 59d1179..a457e8d 100755 --- a/src/integration-tests/test_integration_clique_nat.py.in +++ b/src/integration-tests/test_integration_clique_nat.py.in @@ -31,13 +31,16 @@ import subprocess import re import shutil import time -import pexpect from gnunet_testing import Peer from gnunet_testing import Test from gnunet_testing import Check from gnunet_testing import Condition from gnunet_testing import * +if os.name == "nt": + tmp = os.getenv ("TEMP") +else: + tmp = "/tmp" #definitions testname = "test_integration_clique_nat" @@ -46,14 +49,9 @@ check_timeout = 180 def cleanup (): - if os.name == "nt": - shutil.rmtree (os.path.join (os.getenv ("TEMP"), "c_bootstrap_server"), True) - shutil.rmtree (os.path.join (os.getenv ("TEMP"), "c_no_nat_client"), True) - shutil.rmtree (os.path.join (os.getenv ("TEMP"), "c_nat_client"), True) - else: - shutil.rmtree ("/tmp/c_bootstrap_server/", True) - shutil.rmtree ("/tmp/c_no_nat_client/", True) - shutil.rmtree ("/tmp/c_nat_client/", True) + shutil.rmtree (os.path.join (tmp, "c_bootstrap_server"), True) + shutil.rmtree (os.path.join (tmp, "c_no_nat_client"), True) + shutil.rmtree (os.path.join (tmp, "c_nat_client"), True) def success_cont (check): diff --git a/src/integration-tests/test_integration_connect_on_restart.py.in b/src/integration-tests/test_integration_connect_on_restart.py.in index f77fd1c..0b23c8f 100755 --- a/src/integration-tests/test_integration_connect_on_restart.py.in +++ b/src/integration-tests/test_integration_connect_on_restart.py.in @@ -32,7 +32,6 @@ import subprocess import re import shutil import time -import pexpect from gnunet_testing import Peer from gnunet_testing import Test from gnunet_testing import Check @@ -46,16 +45,15 @@ testname = "test_integration_clique" verbose = True check_timeout = 180 +if os.name == "nt": + tmp = os.getenv ("TEMP") +else: + tmp = "/tmp" def cleanup (): - if os.name == "nt": - shutil.rmtree (os.path.join (os.getenv ("TEMP"), "c_bootstrap_server"), True) - shutil.rmtree (os.path.join (os.getenv ("TEMP"), "c_no_nat_client"), True) - shutil.rmtree (os.path.join (os.getenv ("TEMP"), "c_no_nat_client_2"), True) - else: - shutil.rmtree ("/tmp/c_bootstrap_server/", True) - shutil.rmtree ("/tmp/c_no_nat_client/", True) - shutil.rmtree ("/tmp/c_no_nat_client_2/", True) + shutil.rmtree (os.path.join (tmp, "c_bootstrap_server"), True) + shutil.rmtree (os.path.join (tmp, "c_no_nat_client"), True) + shutil.rmtree (os.path.join (tmp, "c_no_nat_client_2"), True) def success_cont (check): diff --git a/src/integration-tests/test_integration_connection_values_tcp.py.in b/src/integration-tests/test_integration_connection_values_tcp.py.in index d8a92ba..efcf5c7 100755 --- a/src/integration-tests/test_integration_connection_values_tcp.py.in +++ b/src/integration-tests/test_integration_connection_values_tcp.py.in @@ -30,13 +30,16 @@ import subprocess import re import shutil import time -import pexpect from gnunet_testing import Peer from gnunet_testing import Test from gnunet_testing import Check from gnunet_testing import Condition from gnunet_testing import * +if os.name == "nt": + tmp = os.getenv ("TEMP") +else: + tmp = "/tmp" #definitions @@ -46,10 +49,7 @@ check_timeout = 180 def cleanup (): - if os.name == "nt": - shutil.rmtree (os.path.join (os.getenv ("TEMP"), "c_normal_client"), True) - else: - shutil.rmtree ("/tmp/c_normal_client/", True) + shutil.rmtree (os.path.join (tmp, "c_normal_client"), True) def success_cont (check): diff --git a/src/integration-tests/test_integration_connection_values_tcp_udp.py.in b/src/integration-tests/test_integration_connection_values_tcp_udp.py.in index 11b8266..cfb1043 100755 --- a/src/integration-tests/test_integration_connection_values_tcp_udp.py.in +++ b/src/integration-tests/test_integration_connection_values_tcp_udp.py.in @@ -30,7 +30,6 @@ import subprocess import re import shutil import time -import pexpect from gnunet_testing import Peer from gnunet_testing import Test from gnunet_testing import Check @@ -44,13 +43,13 @@ testname = "test_integration_connection_value" verbose = True check_timeout = 180 +if os.name == "nt": + tmp = os.getenv ("TEMP") +else: + tmp = "/tmp" def cleanup (): - if os.name == "nt": - shutil.rmtree (os.path.join (os.getenv ("TEMP"), "c_normal_client"), True) - else: - shutil.rmtree ("/tmp/c_normal_client/", True) - + shutil.rmtree (os.path.join (tmp, "c_normal_client"), True) def success_cont (check): global success diff --git a/src/integration-tests/test_integration_connection_values_tcp_udp_http.py.in b/src/integration-tests/test_integration_connection_values_tcp_udp_http.py.in index 69184a2..4e9e72e 100755 --- a/src/integration-tests/test_integration_connection_values_tcp_udp_http.py.in +++ b/src/integration-tests/test_integration_connection_values_tcp_udp_http.py.in @@ -30,13 +30,16 @@ import subprocess import re import shutil import time -import pexpect from gnunet_testing import Peer from gnunet_testing import Test from gnunet_testing import Check from gnunet_testing import Condition from gnunet_testing import * +if os.name == "nt": + tmp = os.getenv ("TEMP") +else: + tmp = "/tmp" #definitions @@ -46,10 +49,7 @@ check_timeout = 180 def cleanup (): - if os.name == "nt": - shutil.rmtree (os.path.join (os.getenv ("TEMP"), "c_normal_client"), True) - else: - shutil.rmtree ("/tmp/c_normal_client/", True) + shutil.rmtree (os.path.join (tmp, "c_normal_client"), True) def success_cont (check): diff --git a/src/integration-tests/test_integration_disconnect.py.in b/src/integration-tests/test_integration_disconnect.py.in index 6f84f37..2a863f8 100755 --- a/src/integration-tests/test_integration_disconnect.py.in +++ b/src/integration-tests/test_integration_disconnect.py.in @@ -24,7 +24,6 @@ import subprocess import re import shutil import time -import pexpect from gnunet_testing import Peer from gnunet_testing import Test from gnunet_testing import Check @@ -46,14 +45,14 @@ testname = "test_integration_disconnect" verbose = True check_timeout = 180 +if os.name == "nt": + tmp = os.getenv ("TEMP") +else: + tmp = "/tmp" def cleanup (): - if os.name == "nt": - shutil.rmtree (os.path.join (os.getenv ("TEMP"), "c_bootstrap_server"), True) - shutil.rmtree (os.path.join (os.getenv ("TEMP"), "c_no_nat_client"), True) - else: - shutil.rmtree ("/tmp/c_bootstrap_server/", True) - shutil.rmtree ("/tmp/c_no_nat_client/", True) + shutil.rmtree (os.path.join (tmp, "c_bootstrap_server"), True) + shutil.rmtree (os.path.join (tmp, "c_no_nat_client"), True) def success_disconnect_cont (check): diff --git a/src/integration-tests/test_integration_restart.py.in b/src/integration-tests/test_integration_restart.py.in index 26917d0..b3d3ecd 100755 --- a/src/integration-tests/test_integration_restart.py.in +++ b/src/integration-tests/test_integration_restart.py.in @@ -24,7 +24,6 @@ import subprocess import re import shutil import time -import pexpect from gnunet_testing import Peer from gnunet_testing import Test from gnunet_testing import Check @@ -47,14 +46,14 @@ testname = "test_integration_restart" verbose = False check_timeout = 180 +if os.name == "nt": + tmp = os.getenv ("TEMP") +else: + tmp = "/tmp" def cleanup (): - if os.name == "nt": - shutil.rmtree (os.path.join (os.getenv ("TEMP"), "gnunet-test-fs-py-ns"), True) - shutil.rmtree (os.path.join (os.getenv ("TEMP"), "c_no_nat_client"), True) - else: - shutil.rmtree ("/tmp/c_bootstrap_server/", True) - shutil.rmtree ("/tmp/c_no_nat_client/", True) + shutil.rmtree (os.path.join (tmp, "c_bootstrap_server"), True) + shutil.rmtree (os.path.join (tmp, "c_no_nat_client"), True) def success_restart_cont (check): diff --git a/src/lockmanager/Makefile.am b/src/lockmanager/Makefile.am index 0fbc20b..6a41fe5 100644 --- a/src/lockmanager/Makefile.am +++ b/src/lockmanager/Makefile.am @@ -11,10 +11,12 @@ endif pkgcfgdir= $(pkgdatadir)/config.d/ +libexecdir= $(pkglibdir)/libexec/ + pkgcfg_DATA = \ lockmanager.conf -bin_PROGRAMS = \ +libexec_PROGRAMS = \ gnunet-service-lockmanager lib_LTLIBRARIES = \ @@ -32,37 +34,49 @@ libgnunetlockmanager_la_SOURCES = \ lockmanager_api.c lockmanager.h libgnunetlockmanager_la_LIBADD = \ $(top_builddir)/src/util/libgnunetutil.la \ - $(XLIB) + $(XLIB) \ + $(LTLIBINTL) libgnunetlockmanager_la_LDFLAGS = \ $(GN_LIB_LDFLAGS) $(WINFLAGS) \ -version-info 0:0:0 check_PROGRAMS = \ - test-lockmanager-api \ - test-lockmanager-api-lockrelease \ - test-lockmanager-api-servercrash + test_lockmanager_api \ + test_lockmanager_api_lockrelease \ + test_lockmanager_api_servercrash \ + test_lockmanager_api_acquireretry EXTRA_DIST = \ test_lockmanager_api.conf if ENABLE_TEST_RUN -TESTS = $(check_PROGRAMS) + TESTS = $(check_PROGRAMS) endif test_lockmanager_api_SOURCES = \ test_lockmanager_api.c test_lockmanager_api_LDADD = \ $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ libgnunetlockmanager.la test_lockmanager_api_lockrelease_SOURCES = \ test_lockmanager_api_lockrelease.c test_lockmanager_api_lockrelease_LDADD = \ $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ libgnunetlockmanager.la test_lockmanager_api_servercrash_SOURCES = \ test_lockmanager_api_servercrash.c test_lockmanager_api_servercrash_LDADD = \ $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + libgnunetlockmanager.la + +test_lockmanager_api_acquireretry_SOURCES = \ + test_lockmanager_api_acquireretry.c +test_lockmanager_api_acquireretry_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ libgnunetlockmanager.la \ No newline at end of file diff --git a/src/lockmanager/Makefile.in b/src/lockmanager/Makefile.in index 6a90407..0c4db3b 100644 --- a/src/lockmanager/Makefile.in +++ b/src/lockmanager/Makefile.in @@ -1,9 +1,9 @@ -# Makefile.in generated by automake 1.11.1 from Makefile.am. +# Makefile.in generated by automake 1.11.6 from Makefile.am. # @configure_input@ # Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, -# 2003, 2004, 2005, 2006, 2007, 2008, 2009 Free Software Foundation, -# Inc. +# 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Free Software +# Foundation, Inc. # This Makefile.in is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. @@ -18,6 +18,23 @@ VPATH = @srcdir@ +am__make_dryrun = \ + { \ + am__dry=no; \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + echo 'am--echo: ; @echo "AM" OK' | $(MAKE) -f - 2>/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } pkgdatadir = $(datadir)/@PACKAGE@ pkgincludedir = $(includedir)/@PACKAGE@ pkglibdir = $(libdir)/@PACKAGE@ @@ -37,24 +54,26 @@ POST_UNINSTALL = : build_triplet = @build@ host_triplet = @host@ target_triplet = @target@ -bin_PROGRAMS = gnunet-service-lockmanager$(EXEEXT) -check_PROGRAMS = test-lockmanager-api$(EXEEXT) \ - test-lockmanager-api-lockrelease$(EXEEXT) \ - test-lockmanager-api-servercrash$(EXEEXT) +libexec_PROGRAMS = gnunet-service-lockmanager$(EXEEXT) +check_PROGRAMS = test_lockmanager_api$(EXEEXT) \ + test_lockmanager_api_lockrelease$(EXEEXT) \ + test_lockmanager_api_servercrash$(EXEEXT) \ + test_lockmanager_api_acquireretry$(EXEEXT) subdir = src/lockmanager DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in \ $(srcdir)/lockmanager.conf.in ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 am__aclocal_m4_deps = $(top_srcdir)/m4/absolute-header.m4 \ $(top_srcdir)/m4/align.m4 $(top_srcdir)/m4/argz.m4 \ - $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/iconv.m4 \ - $(top_srcdir)/m4/lib-ld.m4 $(top_srcdir)/m4/lib-link.m4 \ - $(top_srcdir)/m4/lib-prefix.m4 $(top_srcdir)/m4/libcurl.m4 \ - $(top_srcdir)/m4/libgcrypt.m4 $(top_srcdir)/m4/libtool.m4 \ - $(top_srcdir)/m4/libunistring.m4 $(top_srcdir)/m4/ltdl.m4 \ - $(top_srcdir)/m4/ltoptions.m4 $(top_srcdir)/m4/ltsugar.m4 \ - $(top_srcdir)/m4/ltversion.m4 $(top_srcdir)/m4/lt~obsolete.m4 \ - $(top_srcdir)/m4/nls.m4 $(top_srcdir)/m4/po.m4 \ + $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/glib-2.0.m4 \ + $(top_srcdir)/m4/iconv.m4 $(top_srcdir)/m4/lib-ld.m4 \ + $(top_srcdir)/m4/lib-link.m4 $(top_srcdir)/m4/lib-prefix.m4 \ + $(top_srcdir)/m4/libcurl.m4 $(top_srcdir)/m4/libgcrypt.m4 \ + $(top_srcdir)/m4/libtool.m4 $(top_srcdir)/m4/libunistring.m4 \ + $(top_srcdir)/m4/ltdl.m4 $(top_srcdir)/m4/ltoptions.m4 \ + $(top_srcdir)/m4/ltsugar.m4 $(top_srcdir)/m4/ltversion.m4 \ + $(top_srcdir)/m4/lt~obsolete.m4 $(top_srcdir)/m4/nls.m4 \ + $(top_srcdir)/m4/pkg.m4 $(top_srcdir)/m4/po.m4 \ $(top_srcdir)/m4/progtest.m4 $(top_srcdir)/acinclude.m4 \ $(top_srcdir)/configure.ac am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ @@ -84,24 +103,30 @@ am__nobase_list = $(am__nobase_strip_setup); \ am__base_list = \ sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \ sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g' -am__installdirs = "$(DESTDIR)$(libdir)" "$(DESTDIR)$(bindir)" \ +am__uninstall_files_from_dir = { \ + test -z "$$files" \ + || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \ + || { echo " ( cd '$$dir' && rm -f" $$files ")"; \ + $(am__cd) "$$dir" && rm -f $$files; }; \ + } +am__installdirs = "$(DESTDIR)$(libdir)" "$(DESTDIR)$(libexecdir)" \ "$(DESTDIR)$(pkgcfgdir)" LTLIBRARIES = $(lib_LTLIBRARIES) am__DEPENDENCIES_1 = libgnunetlockmanager_la_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la \ - $(am__DEPENDENCIES_1) + $(am__DEPENDENCIES_1) $(am__DEPENDENCIES_1) am_libgnunetlockmanager_la_OBJECTS = lockmanager_api.lo libgnunetlockmanager_la_OBJECTS = \ $(am_libgnunetlockmanager_la_OBJECTS) -AM_V_lt = $(am__v_lt_$(V)) -am__v_lt_ = $(am__v_lt_$(AM_DEFAULT_VERBOSITY)) +AM_V_lt = $(am__v_lt_@AM_V@) +am__v_lt_ = $(am__v_lt_@AM_DEFAULT_V@) am__v_lt_0 = --silent libgnunetlockmanager_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ $(AM_CFLAGS) $(CFLAGS) $(libgnunetlockmanager_la_LDFLAGS) \ $(LDFLAGS) -o $@ -PROGRAMS = $(bin_PROGRAMS) +PROGRAMS = $(libexec_PROGRAMS) am_gnunet_service_lockmanager_OBJECTS = \ gnunet-service-lockmanager.$(OBJEXT) gnunet_service_lockmanager_OBJECTS = \ @@ -110,6 +135,15 @@ am_test_lockmanager_api_OBJECTS = test_lockmanager_api.$(OBJEXT) test_lockmanager_api_OBJECTS = $(am_test_lockmanager_api_OBJECTS) test_lockmanager_api_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + libgnunetlockmanager.la +am_test_lockmanager_api_acquireretry_OBJECTS = \ + test_lockmanager_api_acquireretry.$(OBJEXT) +test_lockmanager_api_acquireretry_OBJECTS = \ + $(am_test_lockmanager_api_acquireretry_OBJECTS) +test_lockmanager_api_acquireretry_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ libgnunetlockmanager.la am_test_lockmanager_api_lockrelease_OBJECTS = \ test_lockmanager_api_lockrelease.$(OBJEXT) @@ -117,6 +151,7 @@ test_lockmanager_api_lockrelease_OBJECTS = \ $(am_test_lockmanager_api_lockrelease_OBJECTS) test_lockmanager_api_lockrelease_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ libgnunetlockmanager.la am_test_lockmanager_api_servercrash_OBJECTS = \ test_lockmanager_api_servercrash.$(OBJEXT) @@ -124,6 +159,7 @@ test_lockmanager_api_servercrash_OBJECTS = \ $(am_test_lockmanager_api_servercrash_OBJECTS) test_lockmanager_api_servercrash_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ libgnunetlockmanager.la DEFAULT_INCLUDES = -I.@am__isrc@ -I$(top_builddir) depcomp = $(SHELL) $(top_srcdir)/depcomp @@ -135,32 +171,39 @@ LTCOMPILE = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) \ $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) \ $(AM_CFLAGS) $(CFLAGS) -AM_V_CC = $(am__v_CC_$(V)) -am__v_CC_ = $(am__v_CC_$(AM_DEFAULT_VERBOSITY)) +AM_V_CC = $(am__v_CC_@AM_V@) +am__v_CC_ = $(am__v_CC_@AM_DEFAULT_V@) am__v_CC_0 = @echo " CC " $@; -AM_V_at = $(am__v_at_$(V)) -am__v_at_ = $(am__v_at_$(AM_DEFAULT_VERBOSITY)) +AM_V_at = $(am__v_at_@AM_V@) +am__v_at_ = $(am__v_at_@AM_DEFAULT_V@) am__v_at_0 = @ CCLD = $(CC) LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ $(AM_LDFLAGS) $(LDFLAGS) -o $@ -AM_V_CCLD = $(am__v_CCLD_$(V)) -am__v_CCLD_ = $(am__v_CCLD_$(AM_DEFAULT_VERBOSITY)) +AM_V_CCLD = $(am__v_CCLD_@AM_V@) +am__v_CCLD_ = $(am__v_CCLD_@AM_DEFAULT_V@) am__v_CCLD_0 = @echo " CCLD " $@; -AM_V_GEN = $(am__v_GEN_$(V)) -am__v_GEN_ = $(am__v_GEN_$(AM_DEFAULT_VERBOSITY)) +AM_V_GEN = $(am__v_GEN_@AM_V@) +am__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@) am__v_GEN_0 = @echo " GEN " $@; SOURCES = $(libgnunetlockmanager_la_SOURCES) \ $(gnunet_service_lockmanager_SOURCES) \ $(test_lockmanager_api_SOURCES) \ + $(test_lockmanager_api_acquireretry_SOURCES) \ $(test_lockmanager_api_lockrelease_SOURCES) \ $(test_lockmanager_api_servercrash_SOURCES) DIST_SOURCES = $(libgnunetlockmanager_la_SOURCES) \ $(gnunet_service_lockmanager_SOURCES) \ $(test_lockmanager_api_SOURCES) \ + $(test_lockmanager_api_acquireretry_SOURCES) \ $(test_lockmanager_api_lockrelease_SOURCES) \ $(test_lockmanager_api_servercrash_SOURCES) +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac DATA = $(pkgcfg_DATA) ETAGS = etags CTAGS = ctags @@ -202,6 +245,10 @@ EXEEXT = @EXEEXT@ EXT_LIBS = @EXT_LIBS@ EXT_LIB_PATH = @EXT_LIB_PATH@ FGREP = @FGREP@ +GLIB_CFLAGS = @GLIB_CFLAGS@ +GLIB_GENMARSHAL = @GLIB_GENMARSHAL@ +GLIB_LIBS = @GLIB_LIBS@ +GLIB_MKENUMS = @GLIB_MKENUMS@ GMSGFMT = @GMSGFMT@ GMSGFMT_015 = @GMSGFMT_015@ GNUNETDNS_GROUP = @GNUNETDNS_GROUP@ @@ -212,6 +259,7 @@ GN_LIBINTL = @GN_LIBINTL@ GN_LIB_LDFLAGS = @GN_LIB_LDFLAGS@ GN_PLUGIN_LDFLAGS = @GN_PLUGIN_LDFLAGS@ GN_USER_HOME_DIR = @GN_USER_HOME_DIR@ +GOBJECT_QUERY = @GOBJECT_QUERY@ GREP = @GREP@ HAVE_LIBUNISTRING = @HAVE_LIBUNISTRING@ INCLTDL = @INCLTDL@ @@ -234,6 +282,8 @@ LIBCURL_CPPFLAGS = @LIBCURL_CPPFLAGS@ LIBGCRYPT_CFLAGS = @LIBGCRYPT_CFLAGS@ LIBGCRYPT_CONFIG = @LIBGCRYPT_CONFIG@ LIBGCRYPT_LIBS = @LIBGCRYPT_LIBS@ +LIBGTOP_CFLAGS = @LIBGTOP_CFLAGS@ +LIBGTOP_LIBS = @LIBGTOP_LIBS@ LIBICONV = @LIBICONV@ LIBINTL = @LIBINTL@ LIBLTDL = @LIBLTDL@ @@ -255,6 +305,7 @@ LT_CONFIG_H = @LT_CONFIG_H@ LT_DLLOADERS = @LT_DLLOADERS@ LT_DLPREOPEN = @LT_DLPREOPEN@ MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ MKDIR_P = @MKDIR_P@ MONKEYPREFIX = @MONKEYPREFIX@ MSGFMT = @MSGFMT@ @@ -264,6 +315,7 @@ MYSQL_CPPFLAGS = @MYSQL_CPPFLAGS@ MYSQL_LDFLAGS = @MYSQL_LDFLAGS@ NM = @NM@ NMEDIT = @NMEDIT@ +NSS_DIR = @NSS_DIR@ OBJC = @OBJC@ OBJCDEPMODE = @OBJCDEPMODE@ OBJCFLAGS = @OBJCFLAGS@ @@ -279,6 +331,7 @@ PACKAGE_TARNAME = @PACKAGE_TARNAME@ PACKAGE_URL = @PACKAGE_URL@ PACKAGE_VERSION = @PACKAGE_VERSION@ PATH_SEPARATOR = @PATH_SEPARATOR@ +PKG_CONFIG = @PKG_CONFIG@ POSTGRES_CPPFLAGS = @POSTGRES_CPPFLAGS@ POSTGRES_LDFLAGS = @POSTGRES_LDFLAGS@ POSUB = @POSUB@ @@ -310,6 +363,7 @@ abs_builddir = @abs_builddir@ abs_srcdir = @abs_srcdir@ abs_top_builddir = @abs_top_builddir@ abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ ac_ct_CC = @ac_ct_CC@ ac_ct_CXX = @ac_ct_CXX@ ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ @@ -332,6 +386,7 @@ datarootdir = @datarootdir@ docdir = @docdir@ dvidir = @dvidir@ exec_prefix = @exec_prefix@ +gitcommand = @gitcommand@ host = @host@ host_alias = @host_alias@ host_cpu = @host_cpu@ @@ -342,10 +397,9 @@ includedir = @includedir@ infodir = @infodir@ install_sh = @install_sh@ libdir = @libdir@ -libexecdir = @libexecdir@ +libexecdir = $(pkglibdir)/libexec/ localedir = @localedir@ localstatedir = @localstatedir@ -lt_ECHO = @lt_ECHO@ ltdl_LIBOBJS = @ltdl_LIBOBJS@ ltdl_LTLIBOBJS = @ltdl_LTLIBOBJS@ mandir = @mandir@ @@ -363,6 +417,7 @@ sbindir = @sbindir@ sharedstatedir = @sharedstatedir@ srcdir = @srcdir@ subdirs = @subdirs@ +svnversioncommand = @svnversioncommand@ sys_symbol_underscore = @sys_symbol_underscore@ sysconfdir = @sysconfdir@ target = @target@ @@ -399,7 +454,8 @@ libgnunetlockmanager_la_SOURCES = \ libgnunetlockmanager_la_LIBADD = \ $(top_builddir)/src/util/libgnunetutil.la \ - $(XLIB) + $(XLIB) \ + $(LTLIBINTL) libgnunetlockmanager_la_LDFLAGS = \ $(GN_LIB_LDFLAGS) $(WINFLAGS) \ @@ -414,6 +470,7 @@ test_lockmanager_api_SOURCES = \ test_lockmanager_api_LDADD = \ $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ libgnunetlockmanager.la test_lockmanager_api_lockrelease_SOURCES = \ @@ -421,6 +478,7 @@ test_lockmanager_api_lockrelease_SOURCES = \ test_lockmanager_api_lockrelease_LDADD = \ $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ libgnunetlockmanager.la test_lockmanager_api_servercrash_SOURCES = \ @@ -428,6 +486,15 @@ test_lockmanager_api_servercrash_SOURCES = \ test_lockmanager_api_servercrash_LDADD = \ $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + libgnunetlockmanager.la + +test_lockmanager_api_acquireretry_SOURCES = \ + test_lockmanager_api_acquireretry.c + +test_lockmanager_api_acquireretry_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ libgnunetlockmanager.la all: all-am @@ -468,7 +535,6 @@ lockmanager.conf: $(top_builddir)/config.status $(srcdir)/lockmanager.conf.in cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ install-libLTLIBRARIES: $(lib_LTLIBRARIES) @$(NORMAL_INSTALL) - test -z "$(libdir)" || $(MKDIR_P) "$(DESTDIR)$(libdir)" @list='$(lib_LTLIBRARIES)'; test -n "$(libdir)" || list=; \ list2=; for p in $$list; do \ if test -f $$p; then \ @@ -476,6 +542,8 @@ install-libLTLIBRARIES: $(lib_LTLIBRARIES) else :; fi; \ done; \ test -z "$$list2" || { \ + echo " $(MKDIR_P) '$(DESTDIR)$(libdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libdir)" || exit 1; \ echo " $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 '$(DESTDIR)$(libdir)'"; \ $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 "$(DESTDIR)$(libdir)"; \ } @@ -497,12 +565,24 @@ clean-libLTLIBRARIES: echo "rm -f \"$${dir}/so_locations\""; \ rm -f "$${dir}/so_locations"; \ done -libgnunetlockmanager.la: $(libgnunetlockmanager_la_OBJECTS) $(libgnunetlockmanager_la_DEPENDENCIES) +libgnunetlockmanager.la: $(libgnunetlockmanager_la_OBJECTS) $(libgnunetlockmanager_la_DEPENDENCIES) $(EXTRA_libgnunetlockmanager_la_DEPENDENCIES) $(AM_V_CCLD)$(libgnunetlockmanager_la_LINK) -rpath $(libdir) $(libgnunetlockmanager_la_OBJECTS) $(libgnunetlockmanager_la_LIBADD) $(LIBS) -install-binPROGRAMS: $(bin_PROGRAMS) + +clean-checkPROGRAMS: + @list='$(check_PROGRAMS)'; test -n "$$list" || exit 0; \ + echo " rm -f" $$list; \ + rm -f $$list || exit $$?; \ + test -n "$(EXEEXT)" || exit 0; \ + list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ + echo " rm -f" $$list; \ + rm -f $$list +install-libexecPROGRAMS: $(libexec_PROGRAMS) @$(NORMAL_INSTALL) - test -z "$(bindir)" || $(MKDIR_P) "$(DESTDIR)$(bindir)" - @list='$(bin_PROGRAMS)'; test -n "$(bindir)" || list=; \ + @list='$(libexec_PROGRAMS)'; test -n "$(libexecdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(libexecdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libexecdir)" || exit 1; \ + fi; \ for p in $$list; do echo "$$p $$p"; done | \ sed 's/$(EXEEXT)$$//' | \ while read p p1; do if test -f $$p || test -f $$p1; \ @@ -519,49 +599,43 @@ install-binPROGRAMS: $(bin_PROGRAMS) while read type dir files; do \ if test "$$dir" = .; then dir=; else dir=/$$dir; fi; \ test -z "$$files" || { \ - echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files '$(DESTDIR)$(bindir)$$dir'"; \ - $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files "$(DESTDIR)$(bindir)$$dir" || exit $$?; \ + echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files '$(DESTDIR)$(libexecdir)$$dir'"; \ + $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files "$(DESTDIR)$(libexecdir)$$dir" || exit $$?; \ } \ ; done -uninstall-binPROGRAMS: +uninstall-libexecPROGRAMS: @$(NORMAL_UNINSTALL) - @list='$(bin_PROGRAMS)'; test -n "$(bindir)" || list=; \ + @list='$(libexec_PROGRAMS)'; test -n "$(libexecdir)" || list=; \ files=`for p in $$list; do echo "$$p"; done | \ sed -e 'h;s,^.*/,,;s/$(EXEEXT)$$//;$(transform)' \ -e 's/$$/$(EXEEXT)/' `; \ test -n "$$list" || exit 0; \ - echo " ( cd '$(DESTDIR)$(bindir)' && rm -f" $$files ")"; \ - cd "$(DESTDIR)$(bindir)" && rm -f $$files - -clean-binPROGRAMS: - @list='$(bin_PROGRAMS)'; test -n "$$list" || exit 0; \ - echo " rm -f" $$list; \ - rm -f $$list || exit $$?; \ - test -n "$(EXEEXT)" || exit 0; \ - list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ - echo " rm -f" $$list; \ - rm -f $$list + echo " ( cd '$(DESTDIR)$(libexecdir)' && rm -f" $$files ")"; \ + cd "$(DESTDIR)$(libexecdir)" && rm -f $$files -clean-checkPROGRAMS: - @list='$(check_PROGRAMS)'; test -n "$$list" || exit 0; \ +clean-libexecPROGRAMS: + @list='$(libexec_PROGRAMS)'; test -n "$$list" || exit 0; \ echo " rm -f" $$list; \ rm -f $$list || exit $$?; \ test -n "$(EXEEXT)" || exit 0; \ list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ echo " rm -f" $$list; \ rm -f $$list -gnunet-service-lockmanager$(EXEEXT): $(gnunet_service_lockmanager_OBJECTS) $(gnunet_service_lockmanager_DEPENDENCIES) +gnunet-service-lockmanager$(EXEEXT): $(gnunet_service_lockmanager_OBJECTS) $(gnunet_service_lockmanager_DEPENDENCIES) $(EXTRA_gnunet_service_lockmanager_DEPENDENCIES) @rm -f gnunet-service-lockmanager$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_service_lockmanager_OBJECTS) $(gnunet_service_lockmanager_LDADD) $(LIBS) -test-lockmanager-api$(EXEEXT): $(test_lockmanager_api_OBJECTS) $(test_lockmanager_api_DEPENDENCIES) - @rm -f test-lockmanager-api$(EXEEXT) +test_lockmanager_api$(EXEEXT): $(test_lockmanager_api_OBJECTS) $(test_lockmanager_api_DEPENDENCIES) $(EXTRA_test_lockmanager_api_DEPENDENCIES) + @rm -f test_lockmanager_api$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_lockmanager_api_OBJECTS) $(test_lockmanager_api_LDADD) $(LIBS) -test-lockmanager-api-lockrelease$(EXEEXT): $(test_lockmanager_api_lockrelease_OBJECTS) $(test_lockmanager_api_lockrelease_DEPENDENCIES) - @rm -f test-lockmanager-api-lockrelease$(EXEEXT) +test_lockmanager_api_acquireretry$(EXEEXT): $(test_lockmanager_api_acquireretry_OBJECTS) $(test_lockmanager_api_acquireretry_DEPENDENCIES) $(EXTRA_test_lockmanager_api_acquireretry_DEPENDENCIES) + @rm -f test_lockmanager_api_acquireretry$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_lockmanager_api_acquireretry_OBJECTS) $(test_lockmanager_api_acquireretry_LDADD) $(LIBS) +test_lockmanager_api_lockrelease$(EXEEXT): $(test_lockmanager_api_lockrelease_OBJECTS) $(test_lockmanager_api_lockrelease_DEPENDENCIES) $(EXTRA_test_lockmanager_api_lockrelease_DEPENDENCIES) + @rm -f test_lockmanager_api_lockrelease$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_lockmanager_api_lockrelease_OBJECTS) $(test_lockmanager_api_lockrelease_LDADD) $(LIBS) -test-lockmanager-api-servercrash$(EXEEXT): $(test_lockmanager_api_servercrash_OBJECTS) $(test_lockmanager_api_servercrash_DEPENDENCIES) - @rm -f test-lockmanager-api-servercrash$(EXEEXT) +test_lockmanager_api_servercrash$(EXEEXT): $(test_lockmanager_api_servercrash_OBJECTS) $(test_lockmanager_api_servercrash_DEPENDENCIES) $(EXTRA_test_lockmanager_api_servercrash_DEPENDENCIES) + @rm -f test_lockmanager_api_servercrash$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_lockmanager_api_servercrash_OBJECTS) $(test_lockmanager_api_servercrash_LDADD) $(LIBS) mostlyclean-compile: @@ -573,32 +647,30 @@ distclean-compile: @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-service-lockmanager.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/lockmanager_api.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_lockmanager_api.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_lockmanager_api_acquireretry.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_lockmanager_api_lockrelease.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_lockmanager_api_servercrash.Po@am__quote@ .c.o: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c $< .c.obj: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'` @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c `$(CYGPATH_W) '$<'` +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c `$(CYGPATH_W) '$<'` .c.lo: @am__fastdepCC_TRUE@ $(AM_V_CC)$(LTCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LTCOMPILE) -c -o $@ $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LTCOMPILE) -c -o $@ $< mostlyclean-libtool: -rm -f *.lo @@ -607,8 +679,11 @@ clean-libtool: -rm -rf .libs _libs install-pkgcfgDATA: $(pkgcfg_DATA) @$(NORMAL_INSTALL) - test -z "$(pkgcfgdir)" || $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" @list='$(pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(pkgcfgdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" || exit 1; \ + fi; \ for p in $$list; do \ if test -f "$$p"; then d=; else d="$(srcdir)/"; fi; \ echo "$$d$$p"; \ @@ -622,9 +697,7 @@ uninstall-pkgcfgDATA: @$(NORMAL_UNINSTALL) @list='$(pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ files=`for p in $$list; do echo $$p; done | sed -e 's|^.*/||'`; \ - test -n "$$files" || exit 0; \ - echo " ( cd '$(DESTDIR)$(pkgcfgdir)' && rm -f" $$files ")"; \ - cd "$(DESTDIR)$(pkgcfgdir)" && rm -f $$files + dir='$(DESTDIR)$(pkgcfgdir)'; $(am__uninstall_files_from_dir) ID: $(HEADERS) $(SOURCES) $(LISP) $(TAGS_FILES) list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ @@ -759,14 +832,15 @@ check-TESTS: $(TESTS) fi; \ dashes=`echo "$$dashes" | sed s/./=/g`; \ if test "$$failed" -eq 0; then \ - echo "$$grn$$dashes"; \ + col="$$grn"; \ else \ - echo "$$red$$dashes"; \ + col="$$red"; \ fi; \ - echo "$$banner"; \ - test -z "$$skipped" || echo "$$skipped"; \ - test -z "$$report" || echo "$$report"; \ - echo "$$dashes$$std"; \ + echo "$${col}$$dashes$${std}"; \ + echo "$${col}$$banner$${std}"; \ + test -z "$$skipped" || echo "$${col}$$skipped$${std}"; \ + test -z "$$report" || echo "$${col}$$report$${std}"; \ + echo "$${col}$$dashes$${std}"; \ test "$$failed" -eq 0; \ else :; fi @@ -805,10 +879,8 @@ check-am: all-am $(MAKE) $(AM_MAKEFLAGS) check-TESTS check: check-am all-am: Makefile $(LTLIBRARIES) $(PROGRAMS) $(DATA) -install-binPROGRAMS: install-libLTLIBRARIES - installdirs: - for dir in "$(DESTDIR)$(libdir)" "$(DESTDIR)$(bindir)" "$(DESTDIR)$(pkgcfgdir)"; do \ + for dir in "$(DESTDIR)$(libdir)" "$(DESTDIR)$(libexecdir)" "$(DESTDIR)$(pkgcfgdir)"; do \ test -z "$$dir" || $(MKDIR_P) "$$dir"; \ done install: install-am @@ -821,10 +893,15 @@ install-am: all-am installcheck: installcheck-am install-strip: - $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ - install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ - `test -z '$(STRIP)' || \ - echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi mostlyclean-generic: clean-generic: @@ -838,8 +915,8 @@ maintainer-clean-generic: @echo "it deletes files that may require special tools to rebuild." clean: clean-am -clean-am: clean-binPROGRAMS clean-checkPROGRAMS clean-generic \ - clean-libLTLIBRARIES clean-libtool mostlyclean-am +clean-am: clean-checkPROGRAMS clean-generic clean-libLTLIBRARIES \ + clean-libexecPROGRAMS clean-libtool mostlyclean-am distclean: distclean-am -rm -rf ./$(DEPDIR) @@ -865,7 +942,7 @@ install-dvi: install-dvi-am install-dvi-am: -install-exec-am: install-binPROGRAMS install-libLTLIBRARIES +install-exec-am: install-libLTLIBRARIES install-libexecPROGRAMS install-html: install-html-am @@ -905,27 +982,27 @@ ps: ps-am ps-am: -uninstall-am: uninstall-binPROGRAMS uninstall-libLTLIBRARIES \ +uninstall-am: uninstall-libLTLIBRARIES uninstall-libexecPROGRAMS \ uninstall-pkgcfgDATA .MAKE: check-am install-am install-strip .PHONY: CTAGS GTAGS all all-am check check-TESTS check-am clean \ - clean-binPROGRAMS clean-checkPROGRAMS clean-generic \ - clean-libLTLIBRARIES clean-libtool ctags distclean \ + clean-checkPROGRAMS clean-generic clean-libLTLIBRARIES \ + clean-libexecPROGRAMS clean-libtool ctags distclean \ distclean-compile distclean-generic distclean-libtool \ distclean-tags distdir dvi dvi-am html html-am info info-am \ - install install-am install-binPROGRAMS install-data \ - install-data-am install-dvi install-dvi-am install-exec \ - install-exec-am install-html install-html-am install-info \ - install-info-am install-libLTLIBRARIES install-man install-pdf \ - install-pdf-am install-pkgcfgDATA install-ps install-ps-am \ - install-strip installcheck installcheck-am installdirs \ - maintainer-clean maintainer-clean-generic mostlyclean \ - mostlyclean-compile mostlyclean-generic mostlyclean-libtool \ - pdf pdf-am ps ps-am tags uninstall uninstall-am \ - uninstall-binPROGRAMS uninstall-libLTLIBRARIES \ - uninstall-pkgcfgDATA + install install-am install-data install-data-am install-dvi \ + install-dvi-am install-exec install-exec-am install-html \ + install-html-am install-info install-info-am \ + install-libLTLIBRARIES install-libexecPROGRAMS install-man \ + install-pdf install-pdf-am install-pkgcfgDATA install-ps \ + install-ps-am install-strip installcheck installcheck-am \ + installdirs maintainer-clean maintainer-clean-generic \ + mostlyclean mostlyclean-compile mostlyclean-generic \ + mostlyclean-libtool pdf pdf-am ps ps-am tags uninstall \ + uninstall-am uninstall-libLTLIBRARIES \ + uninstall-libexecPROGRAMS uninstall-pkgcfgDATA # Tell versions [3.59,3.63) of GNU make to not export all variables. diff --git a/src/lockmanager/gnunet-service-lockmanager.c b/src/lockmanager/gnunet-service-lockmanager.c index 8ec9889..e509fc6 100644 --- a/src/lockmanager/gnunet-service-lockmanager.c +++ b/src/lockmanager/gnunet-service-lockmanager.c @@ -58,7 +58,7 @@ struct WaitList * The next client structure */ struct WaitList *next; - + /** * The prev client structure */ @@ -204,15 +204,12 @@ static struct ClientList *cl_tail; * @param key set to the key */ static void -get_key (const char *domain_name, - uint32_t lock_number, - struct GNUNET_HashCode *key) +get_key (const char *domain_name, uint32_t lock_number, + struct GNUNET_HashCode *key) { uint32_t *last_32; - GNUNET_CRYPTO_hash (domain_name, - strlen (domain_name), - key); + GNUNET_CRYPTO_hash (domain_name, strlen (domain_name), key); last_32 = (uint32_t *) key; *last_32 ^= lock_number; } @@ -226,18 +223,18 @@ get_key (const char *domain_name, * @param value value in the hash map (struct Lock) * @return GNUNET_YES if we should continue to * iterate, - * GNUNET_NO if not. + * GNUNET_NO if not. */ static int -match_iterator (void *cls, const GNUNET_HashCode *key, void *value) +match_iterator (void *cls, const struct GNUNET_HashCode *key, void *value) { struct LockMatch *match = cls; struct Lock *lock = value; - if ( (match->lock_num == lock->lock_num) - && (0 == strcmp (match->domain_name, lock->domain_name)) ) + if ((match->lock_num == lock->lock_num) && + (0 == strcmp (match->domain_name, lock->domain_name))) { - match->matched_entry = lock; + match->matched_entry = lock; return GNUNET_NO; } return GNUNET_YES; @@ -252,9 +249,7 @@ match_iterator (void *cls, const GNUNET_HashCode *key, void *value) * @return the lock if found; NULL if not */ static struct Lock * -find_lock (const char *domain_name, - const uint32_t lock_num) - +find_lock (const char *domain_name, const uint32_t lock_num) { struct LockMatch match; struct GNUNET_HashCode key; @@ -263,9 +258,7 @@ find_lock (const char *domain_name, match.domain_name = domain_name; match.matched_entry = NULL; get_key (domain_name, lock_num, &key); - GNUNET_CONTAINER_multihashmap_get_multiple (lock_map, - &key, - &match_iterator, + GNUNET_CONTAINER_multihashmap_get_multiple (lock_map, &key, &match_iterator, &match); return match.matched_entry; } @@ -279,8 +272,7 @@ find_lock (const char *domain_name, * @return pointer to the lock structure which is added to lock map */ static struct Lock * -add_lock (const char *domain_name, - uint32_t lock_num) +add_lock (const char *domain_name, uint32_t lock_num) { struct Lock *lock; struct GNUNET_HashCode key; @@ -295,9 +287,7 @@ add_lock (const char *domain_name, LOG (GNUNET_ERROR_TYPE_DEBUG, "Adding a lock with num: %d and domain: %s to the lock map\n", lock->lock_num, lock->domain_name); - GNUNET_CONTAINER_multihashmap_put (lock_map, - &key, - lock, + GNUNET_CONTAINER_multihashmap_put (lock_map, &key, lock, GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE); return lock; } @@ -312,16 +302,14 @@ static void remove_lock (struct Lock *lock) { struct GNUNET_HashCode key; - + GNUNET_assert (NULL == lock->wl_head); - get_key (lock->domain_name, - lock->lock_num, - &key); + get_key (lock->domain_name, lock->lock_num, &key); LOG (GNUNET_ERROR_TYPE_DEBUG, - "Removing lock with num: %u, domain: %s from lock map\n", - lock->lock_num, lock->domain_name); - GNUNET_assert (GNUNET_YES == GNUNET_CONTAINER_multihashmap_remove - (lock_map, &key, lock)); + "Removing lock with num: %u, domain: %s from lock map\n", lock->lock_num, + lock->domain_name); + GNUNET_assert (GNUNET_YES == + GNUNET_CONTAINER_multihashmap_remove (lock_map, &key, lock)); GNUNET_free (lock->domain_name); GNUNET_free (lock); } @@ -336,13 +324,12 @@ remove_lock (struct Lock *lock) * @return the matching LockList entry; NULL if no match is found */ static struct LockList * -cl_ll_find_lock (struct ClientList *cl_entry, - const struct Lock *lock) +cl_ll_find_lock (struct ClientList *cl_entry, const struct Lock *lock) { struct LockList *ll_entry; - for (ll_entry = cl_entry->ll_head; - NULL != ll_entry; ll_entry = ll_entry->next) + for (ll_entry = cl_entry->ll_head; NULL != ll_entry; + ll_entry = ll_entry->next) { if (lock == ll_entry->lock) return ll_entry; @@ -358,8 +345,7 @@ cl_ll_find_lock (struct ClientList *cl_entry, * @param lock the lock to be added to the cl_entry's lock list */ static void -cl_ll_add_lock (struct ClientList *cl_entry, - struct Lock *lock) +cl_ll_add_lock (struct ClientList *cl_entry, struct Lock *lock) { struct LockList *ll_entry; @@ -368,8 +354,7 @@ cl_ll_add_lock (struct ClientList *cl_entry, LOG (GNUNET_ERROR_TYPE_DEBUG, "Adding a lock with num: %u and domain: %s to lock list\n", lock->lock_num, lock->domain_name); - GNUNET_CONTAINER_DLL_insert_tail (cl_entry->ll_head, - cl_entry->ll_tail, + GNUNET_CONTAINER_DLL_insert_tail (cl_entry->ll_head, cl_entry->ll_tail, ll_entry); } @@ -381,17 +366,13 @@ cl_ll_add_lock (struct ClientList *cl_entry, * @param ll_entry the LockList entry to be deleted */ static void -cl_ll_remove_lock (struct ClientList *cl_entry, - struct LockList *ll_entry) +cl_ll_remove_lock (struct ClientList *cl_entry, struct LockList *ll_entry) { LOG (GNUNET_ERROR_TYPE_DEBUG, "Removing lock with num: %u, domain: %s from lock list of a client\n", - ll_entry->lock->lock_num, - ll_entry->lock->domain_name); + ll_entry->lock->lock_num, ll_entry->lock->domain_name); GNUNET_assert (NULL != cl_entry->ll_head); - GNUNET_CONTAINER_DLL_remove (cl_entry->ll_head, - cl_entry->ll_tail, - ll_entry); + GNUNET_CONTAINER_DLL_remove (cl_entry->ll_head, cl_entry->ll_tail, ll_entry); GNUNET_free (ll_entry); } @@ -405,14 +386,11 @@ cl_ll_remove_lock (struct ClientList *cl_entry, * was found */ static struct WaitList * -lock_wl_find (const struct Lock *lock, - const struct ClientList *cl_entry) +lock_wl_find (const struct Lock *lock, const struct ClientList *cl_entry) { struct WaitList *wl_entry; - for (wl_entry = lock->wl_head; - NULL != wl_entry; - wl_entry = wl_entry->next) + for (wl_entry = lock->wl_head; NULL != wl_entry; wl_entry = wl_entry->next) { if (cl_entry == wl_entry->cl_entry) return wl_entry; @@ -428,20 +406,16 @@ lock_wl_find (const struct Lock *lock, * @param cl_entry the client to queue for the lock's wait list */ static void -lock_wl_add_client (struct Lock *lock, - struct ClientList *cl_entry) +lock_wl_add_client (struct Lock *lock, struct ClientList *cl_entry) { struct WaitList *wl_entry; LOG (GNUNET_ERROR_TYPE_DEBUG, "Adding a client to lock's wait list (lock num: %u, domain: %s)\n", - lock->lock_num, - lock->domain_name); + lock->lock_num, lock->domain_name); wl_entry = GNUNET_malloc (sizeof (struct WaitList)); wl_entry->cl_entry = cl_entry; - GNUNET_CONTAINER_DLL_insert_tail (lock->wl_head, - lock->wl_tail, - wl_entry); + GNUNET_CONTAINER_DLL_insert_tail (lock->wl_head, lock->wl_tail, wl_entry); } @@ -452,15 +426,12 @@ lock_wl_add_client (struct Lock *lock, * @param wl_entry the wait list entry to be removed */ static void -lock_wl_remove (struct Lock *lock, - struct WaitList *wl_entry) +lock_wl_remove (struct Lock *lock, struct WaitList *wl_entry) { LOG (GNUNET_ERROR_TYPE_DEBUG, "Removing client from wait list of lock with num: %u, domain: %s\n", lock->lock_num, lock->domain_name); - GNUNET_CONTAINER_DLL_remove (lock->wl_head, - lock->wl_tail, - wl_entry); + GNUNET_CONTAINER_DLL_remove (lock->wl_head, lock->wl_tail, wl_entry); GNUNET_free (wl_entry); } @@ -472,7 +443,7 @@ lock_wl_remove (struct Lock *lock, * @return the ClientList entry; NULL if the client is not found */ static struct ClientList * -cl_find_client (const struct GNUNET_SERVER_Client *client) +cl_find_client (const struct GNUNET_SERVER_Client *client) { struct ClientList *current; @@ -493,15 +464,12 @@ static struct ClientList * cl_add_client (struct GNUNET_SERVER_Client *client) { struct ClientList *new_client; - - LOG (GNUNET_ERROR_TYPE_DEBUG, - "Adding a client to the client list\n"); + + LOG (GNUNET_ERROR_TYPE_DEBUG, "Adding a client to the client list\n"); new_client = GNUNET_malloc (sizeof (struct ClientList)); GNUNET_SERVER_client_keep (client); new_client->client = client; - GNUNET_CONTAINER_DLL_insert_tail (cl_head, - cl_tail, - new_client); + GNUNET_CONTAINER_DLL_insert_tail (cl_head, cl_tail, new_client); return new_client; } @@ -515,12 +483,9 @@ static void cl_remove_client (struct ClientList *cl_entry) { GNUNET_assert (NULL == cl_entry->ll_head); - LOG (GNUNET_ERROR_TYPE_DEBUG, - "Removing a client from the client list\n"); + LOG (GNUNET_ERROR_TYPE_DEBUG, "Removing a client from the client list\n"); GNUNET_SERVER_client_drop (cl_entry->client); - GNUNET_CONTAINER_DLL_remove (cl_head, - cl_tail, - cl_entry); + GNUNET_CONTAINER_DLL_remove (cl_head, cl_tail, cl_entry); GNUNET_free (cl_entry); } @@ -533,7 +498,7 @@ cl_remove_client (struct ClientList *cl_entry) * @param buf where the callee should write the message * @return number of bytes written to buf */ -static size_t +static size_t transmit_notify (void *cls, size_t size, void *buf) { struct GNUNET_LOCKMANAGER_Message *msg = cls; @@ -548,8 +513,7 @@ transmit_notify (void *cls, size_t size, void *buf) GNUNET_assert (size >= msg_size); memcpy (buf, msg, msg_size); GNUNET_free (msg); - LOG (GNUNET_ERROR_TYPE_DEBUG, - "Message of size %u sent\n", msg_size); + LOG (GNUNET_ERROR_TYPE_DEBUG, "Message of size %u sent\n", msg_size); return msg_size; } @@ -562,8 +526,7 @@ transmit_notify (void *cls, size_t size, void *buf) * @param lock_num the number of the successfully acquired lock */ static void -send_success_msg (struct GNUNET_SERVER_Client *client, - const char *domain_name, +send_success_msg (struct GNUNET_SERVER_Client *client, const char *domain_name, int lock_num) { struct GNUNET_LOCKMANAGER_Message *reply; @@ -578,13 +541,10 @@ send_success_msg (struct GNUNET_SERVER_Client *client, reply->lock = htonl (lock_num); strncpy ((char *) &reply[1], domain_name, domain_name_len); LOG (GNUNET_ERROR_TYPE_DEBUG, - "Sending SUCCESS message for lock with num: %u, domain: %s\n", - lock_num, domain_name); - GNUNET_SERVER_notify_transmit_ready (client, - reply_size, - TIMEOUT, - &transmit_notify, - reply); + "Sending SUCCESS message for lock with num: %u, domain: %s\n", lock_num, + domain_name); + GNUNET_SERVER_notify_transmit_ready (client, reply_size, TIMEOUT, + &transmit_notify, reply); } @@ -596,8 +556,7 @@ send_success_msg (struct GNUNET_SERVER_Client *client, * @param message GNUNET_MESSAGE_TYPE_LOCKMANAGER_ACQUIRE message */ static void -handle_acquire (void *cls, - struct GNUNET_SERVER_Client *client, +handle_acquire (void *cls, struct GNUNET_SERVER_Client *client, const struct GNUNET_MessageHeader *message) { const struct GNUNET_LOCKMANAGER_Message *request; @@ -617,23 +576,26 @@ handle_acquire (void *cls, request = (struct GNUNET_LOCKMANAGER_Message *) message; domain_name = (const char *) &request[1]; msize -= sizeof (struct GNUNET_LOCKMANAGER_Message); - if ('\0' != domain_name[msize]) + if ('\0' != domain_name[msize - 1]) { + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Bad domain `%.*s' - byte with index %u is %X, not 0.\n", msize, + domain_name, msize - 1, (unsigned int) domain_name[msize - 1]); GNUNET_break (0); GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } lock_num = ntohl (request->lock); LOG (GNUNET_ERROR_TYPE_DEBUG, - "Received an ACQUIRE message for lock num: %u domain: %s\n", - lock_num, domain_name); - if (NULL == (cl_entry = cl_find_client (client))) - cl_entry = cl_add_client (client); /* Add client if not in client list */ - if (NULL != (lock = find_lock (domain_name,lock_num))) + "Received an ACQUIRE message for lock num: %u domain: %s\n", lock_num, + domain_name); + if (NULL == (cl_entry = cl_find_client (client))) + cl_entry = cl_add_client (client); /* Add client if not in client list */ + if (NULL != (lock = find_lock (domain_name, lock_num))) { if (lock->cl_entry == cl_entry) - { /* Client is requesting a lock it already owns */ - GNUNET_break (0); + { /* Client is requesting a lock it already owns */ + GNUNET_break_op (0); GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } @@ -669,17 +631,13 @@ process_lock_release (struct Lock *lock) wl_entry = lock->wl_head; if (NULL == wl_entry) { - remove_lock (lock); /* No clients waiting for this lock - delete */ + remove_lock (lock); /* No clients waiting for this lock - delete */ return; } - LOG (GNUNET_ERROR_TYPE_DEBUG, - "Giving lock to a client from wait list\n"); + LOG (GNUNET_ERROR_TYPE_DEBUG, "Giving lock to a client from wait list\n"); lock->cl_entry = wl_entry->cl_entry; - lock_wl_remove(lock, wl_entry); - send_success_msg (lock->cl_entry->client, - lock->domain_name, - lock->lock_num); - return; + lock_wl_remove (lock, wl_entry); + send_success_msg (lock->cl_entry->client, lock->domain_name, lock->lock_num); } @@ -691,8 +649,7 @@ process_lock_release (struct Lock *lock) * @param message the LOCKMANAGER_RELEASE message */ static void -handle_release (void *cls, - struct GNUNET_SERVER_Client *client, +handle_release (void *cls, struct GNUNET_SERVER_Client *client, const struct GNUNET_MessageHeader *message) { const struct GNUNET_LOCKMANAGER_Message *request; @@ -706,7 +663,7 @@ handle_release (void *cls, msize = ntohs (message->size); if (msize <= sizeof (struct GNUNET_LOCKMANAGER_Message)) - { + { GNUNET_break (0); GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; @@ -714,27 +671,27 @@ handle_release (void *cls, request = (const struct GNUNET_LOCKMANAGER_Message *) message; domain_name = (const char *) &request[1]; msize -= sizeof (struct GNUNET_LOCKMANAGER_Message); - if ('\0' != domain_name[msize-1]) + if ('\0' != domain_name[msize - 1]) { GNUNET_break (0); GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; - + } lock_num = ntohl (request->lock); LOG (GNUNET_ERROR_TYPE_DEBUG, - "Received RELEASE message for lock with num: %d, domain: %s\n", - lock_num, domain_name); + "Received RELEASE message for lock with num: %d, domain: %s\n", lock_num, + domain_name); if (NULL == (cl_entry = cl_find_client (client))) { - GNUNET_break(0); + GNUNET_break (0); GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } lock = find_lock (domain_name, lock_num); - if(NULL == lock) - { + if (NULL == lock) + { GNUNET_break (0); GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; @@ -773,11 +730,12 @@ client_disconnect_cb (void *cls, struct GNUNET_SERVER_Client *client) struct ClientList *cl_entry; struct LockList *ll_entry; struct Lock *lock; + struct WaitList *wl_entry; if (NULL == client) return; LOG (GNUNET_ERROR_TYPE_DEBUG, - "A client has been disconnected -- freeing its locks and resources\n"); + "A client has been disconnected -- freeing its locks and resources\n"); cl_entry = cl_find_client (client); if (NULL == cl_entry) return; @@ -785,7 +743,14 @@ client_disconnect_cb (void *cls, struct GNUNET_SERVER_Client *client) { lock = ll_entry->lock; cl_ll_remove_lock (cl_entry, ll_entry); - process_lock_release (lock); + if (lock->cl_entry == cl_entry) + process_lock_release (lock); + else + { + wl_entry = lock_wl_find (lock, cl_entry); + GNUNET_assert (NULL != wl_entry); + lock_wl_remove (lock, wl_entry); + } } cl_remove_client (cl_entry); } @@ -801,10 +766,8 @@ client_disconnect_cb (void *cls, struct GNUNET_SERVER_Client *client) * iterate, * GNUNET_NO if not. */ -static int -lock_delete_iterator (void *cls, - const GNUNET_HashCode * key, - void *value) +static int +lock_delete_iterator (void *cls, const struct GNUNET_HashCode *key, void *value) { struct Lock *lock = value; @@ -813,10 +776,8 @@ lock_delete_iterator (void *cls, { lock_wl_remove (lock, lock->wl_head); } - GNUNET_assert (GNUNET_YES == - GNUNET_CONTAINER_multihashmap_remove(lock_map, - key, - lock)); + GNUNET_assert (GNUNET_YES == + GNUNET_CONTAINER_multihashmap_remove (lock_map, key, lock)); GNUNET_free (lock->domain_name); GNUNET_free (lock); return GNUNET_YES; @@ -830,26 +791,23 @@ lock_delete_iterator (void *cls, * @param tc the TaskContext from scheduler */ static void -shutdown_task (void *cls, - const struct GNUNET_SCHEDULER_TaskContext *tc) +shutdown_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { - LOG (GNUNET_ERROR_TYPE_DEBUG, - "Shutting down lock manager\n"); + LOG (GNUNET_ERROR_TYPE_DEBUG, "Shutting down lock manager\n"); /* Clean the global ClientList */ while (NULL != cl_head) { - while (NULL != cl_head->ll_head) /* Clear the LockList */ + while (NULL != cl_head->ll_head) /* Clear the LockList */ { cl_ll_remove_lock (cl_head, cl_head->ll_head); } cl_remove_client (cl_head); } /* Clean the global hash table */ - GNUNET_CONTAINER_multihashmap_iterate (lock_map, - &lock_delete_iterator, - NULL); + GNUNET_CONTAINER_multihashmap_iterate (lock_map, &lock_delete_iterator, NULL); GNUNET_assert (0 == GNUNET_CONTAINER_multihashmap_size (lock_map)); GNUNET_CONTAINER_multihashmap_destroy (lock_map); + lock_map = NULL; } @@ -860,25 +818,19 @@ shutdown_task (void *cls, * @param server the initialized server * @param cfg configuration to use */ -static void -lockmanager_run (void *cls, - struct GNUNET_SERVER_Handle * server, +static void +lockmanager_run (void *cls, struct GNUNET_SERVER_Handle *server, const struct GNUNET_CONFIGURATION_Handle *cfg) { - static const struct GNUNET_SERVER_MessageHandler message_handlers[] = - { - {&handle_acquire, NULL, GNUNET_MESSAGE_TYPE_LOCKMANAGER_ACQUIRE, 0}, - {&handle_release, NULL, GNUNET_MESSAGE_TYPE_LOCKMANAGER_RELEASE, 0}, - {NULL} - }; - GNUNET_SERVER_add_handlers (server, - message_handlers); - GNUNET_SERVER_disconnect_notify (server, - &client_disconnect_cb, - NULL); - lock_map = GNUNET_CONTAINER_multihashmap_create (30); - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, - &shutdown_task, + static const struct GNUNET_SERVER_MessageHandler message_handlers[] = { + {&handle_acquire, NULL, GNUNET_MESSAGE_TYPE_LOCKMANAGER_ACQUIRE, 0}, + {&handle_release, NULL, GNUNET_MESSAGE_TYPE_LOCKMANAGER_RELEASE, 0}, + {NULL} + }; + GNUNET_SERVER_add_handlers (server, message_handlers); + GNUNET_SERVER_disconnect_notify (server, &client_disconnect_cb, NULL); + lock_map = GNUNET_CONTAINER_multihashmap_create (32, GNUNET_NO); + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, &shutdown_task, NULL); } @@ -886,14 +838,13 @@ lockmanager_run (void *cls, /** * The starting point of execution */ -int main (int argc, char *const *argv) +int +main (int argc, char *const *argv) { - return - (GNUNET_OK == - GNUNET_SERVICE_run (argc, - argv, - "lockmanager", - GNUNET_SERVICE_OPTION_NONE, - &lockmanager_run, - NULL)) ? 0 : 1; + return (GNUNET_OK == + GNUNET_SERVICE_run (argc, argv, "lockmanager", + GNUNET_SERVICE_OPTION_NONE, &lockmanager_run, + NULL)) ? 0 : 1; } + +/* end of gnunet-service-lockmanager.c */ diff --git a/src/lockmanager/lockmanager.conf.in b/src/lockmanager/lockmanager.conf.in index 75b9244..42d5743 100644 --- a/src/lockmanager/lockmanager.conf.in +++ b/src/lockmanager/lockmanager.conf.in @@ -3,7 +3,6 @@ AUTOSTART = YES @UNIXONLY@ PORT = 2100 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-lockmanager ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; diff --git a/src/lockmanager/lockmanager_api.c b/src/lockmanager/lockmanager_api.c index 99f5ab5..3b9e70e 100644 --- a/src/lockmanager/lockmanager_api.c +++ b/src/lockmanager/lockmanager_api.c @@ -24,11 +24,6 @@ * @author Sree Harsha Totakura */ -/** - * To be fixed: - * Should the handle be freed when the connection to service is lost? - * Should cancel_request have a call back (else simultaneous calls break) - */ #include "platform.h" #include "gnunet_common.h" @@ -63,11 +58,17 @@ struct MessageQueue * The prev pointer for doubly linked list */ struct MessageQueue *prev; - + /** * The LOCKMANAGER Message */ struct GNUNET_LOCKMANAGER_Message *msg; + + /** + * If this is a AQUIRE_LOCK message, this is the + * affiliated locking request. + */ + struct GNUNET_LOCKMANAGER_LockingRequest *lr; }; @@ -100,6 +101,11 @@ struct GNUNET_LOCKMANAGER_Handle * Double linked list tail for message queue */ struct MessageQueue *mq_tail; + + /** + * Are we currently handling replies? + */ + int in_replies; }; @@ -118,6 +124,12 @@ struct GNUNET_LOCKMANAGER_LockingRequest */ GNUNET_LOCKMANAGER_StatusCallback status_cb; + /** + * Entry in the request message queue for aquiring this + * lock; NULL after request has been sent. + */ + struct MessageQueue *mqe; + /** * Closure for the status callback */ @@ -127,7 +139,7 @@ struct GNUNET_LOCKMANAGER_LockingRequest * The locking domain of this request */ char *domain; - + /** * The lock */ @@ -137,6 +149,11 @@ struct GNUNET_LOCKMANAGER_LockingRequest * The status of the lock */ enum GNUNET_LOCKMANAGER_Status status; + + /** + * set to GNUNET_YES if acquire message for this lock is till in messga queue + */ + int acquire_sent; }; @@ -162,6 +179,16 @@ struct LockingRequestMatch }; +/** + * Handler for server replies + * + * @param cls the LOCKMANAGER_Handle + * @param msg received message, NULL on timeout or fatal error + */ +static void +handle_replies (void *cls, const struct GNUNET_MessageHeader *msg); + + /** * Transmit notify for sending message to server * @@ -170,7 +197,7 @@ struct LockingRequestMatch * @param buf where the callee should write the message * @return number of bytes written to buf */ -static size_t +static size_t transmit_notify (void *cls, size_t size, void *buf) { struct GNUNET_LOCKMANAGER_Handle *handle = cls; @@ -178,34 +205,48 @@ transmit_notify (void *cls, size_t size, void *buf) uint16_t msg_size; handle->transmit_handle = NULL; + queue_entity = handle->mq_head; + GNUNET_assert (NULL != queue_entity); if ((0 == size) || (NULL == buf)) { - /* FIXME: Timed out -- requeue? */ + handle->transmit_handle = + GNUNET_CLIENT_notify_transmit_ready (handle->conn, + ntohs (queue_entity->msg-> + header.size), + GNUNET_TIME_UNIT_FOREVER_REL, + GNUNET_YES, &transmit_notify, + handle); return 0; } - queue_entity = handle->mq_head; - GNUNET_assert (NULL != queue_entity); msg_size = ntohs (queue_entity->msg->header.size); GNUNET_assert (size >= msg_size); memcpy (buf, queue_entity->msg, msg_size); - LOG (GNUNET_ERROR_TYPE_DEBUG, - "Message of size %u sent\n", msg_size); + LOG (GNUNET_ERROR_TYPE_DEBUG, "Message of size %u sent\n", msg_size); + if (GNUNET_MESSAGE_TYPE_LOCKMANAGER_ACQUIRE == + ntohs (queue_entity->msg->header.type)) + { + GNUNET_break (GNUNET_NO == queue_entity->lr->acquire_sent); + queue_entity->lr->acquire_sent = GNUNET_YES; + queue_entity->lr->mqe = NULL; + } GNUNET_free (queue_entity->msg); - GNUNET_CONTAINER_DLL_remove (handle->mq_head, - handle->mq_tail, - queue_entity); + GNUNET_CONTAINER_DLL_remove (handle->mq_head, handle->mq_tail, queue_entity); GNUNET_free (queue_entity); queue_entity = handle->mq_head; if (NULL != queue_entity) { handle->transmit_handle = - GNUNET_CLIENT_notify_transmit_ready (handle->conn, - ntohs - (queue_entity->msg->header.size), - TIMEOUT, - GNUNET_YES, - &transmit_notify, - handle); + GNUNET_CLIENT_notify_transmit_ready (handle->conn, + ntohs (queue_entity->msg-> + header.size), TIMEOUT, + GNUNET_YES, &transmit_notify, + handle); + } + if (GNUNET_NO == handle->in_replies) + { + handle->in_replies = GNUNET_YES; + GNUNET_CLIENT_receive (handle->conn, &handle_replies, handle, + GNUNET_TIME_UNIT_FOREVER_REL); } return msg_size; } @@ -216,29 +257,31 @@ transmit_notify (void *cls, size_t size, void *buf) * * @param handle the lockmanager handle whose queue will be used * @param msg the message to be queued + * @param request the locking reqeust responsible for queueing this message + * @return the MessageQueue entity that has been queued */ -static void +static struct MessageQueue * queue_message (struct GNUNET_LOCKMANAGER_Handle *handle, - struct GNUNET_LOCKMANAGER_Message *msg) + struct GNUNET_LOCKMANAGER_Message *msg, + struct GNUNET_LOCKMANAGER_LockingRequest *request) { struct MessageQueue *queue_entity; GNUNET_assert (NULL != msg); queue_entity = GNUNET_malloc (sizeof (struct MessageQueue)); queue_entity->msg = msg; - GNUNET_CONTAINER_DLL_insert_tail (handle->mq_head, - handle->mq_tail, + queue_entity->lr = request; + GNUNET_CONTAINER_DLL_insert_tail (handle->mq_head, handle->mq_tail, queue_entity); if (NULL == handle->transmit_handle) { handle->transmit_handle = - GNUNET_CLIENT_notify_transmit_ready (handle->conn, - ntohs (msg->header.size), - TIMEOUT, - GNUNET_YES, - &transmit_notify, - handle); + GNUNET_CLIENT_notify_transmit_ready (handle->conn, + ntohs (msg->header.size), TIMEOUT, + GNUNET_YES, &transmit_notify, + handle); } + return queue_entity; } @@ -250,15 +293,12 @@ queue_message (struct GNUNET_LOCKMANAGER_Handle *handle, * @param key set to the key */ static void -get_key (const char *domain_name, - uint32_t lock_number, - struct GNUNET_HashCode *key) +get_key (const char *domain_name, uint32_t lock_number, + struct GNUNET_HashCode *key) { uint32_t *last_32; - GNUNET_CRYPTO_hash (domain_name, - strlen (domain_name), - key); + GNUNET_CRYPTO_hash (domain_name, strlen (domain_name), key); last_32 = (uint32_t *) key; *last_32 ^= lock_number; } @@ -272,17 +312,17 @@ get_key (const char *domain_name, * @param value value in the hash map (struct GNUNET_LOCKMANAGER_LockingRequest) * @return GNUNET_YES if we should continue to * iterate, - * GNUNET_NO if not. + * GNUNET_NO if not. */ static int -match_iterator (void *cls, const GNUNET_HashCode *key, void *value) +match_iterator (void *cls, const struct GNUNET_HashCode *key, void *value) { struct LockingRequestMatch *match = cls; struct GNUNET_LOCKMANAGER_LockingRequest *lr = value; - if ( (match->lock == lr->lock) && (0 == strcmp (match->domain, lr->domain)) ) + if ((match->lock == lr->lock) && (0 == strcmp (match->domain, lr->domain))) { - match->matched_entry = lr; + match->matched_entry = lr; return GNUNET_NO; } return GNUNET_YES; @@ -297,12 +337,11 @@ match_iterator (void *cls, const GNUNET_HashCode *key, void *value) * @param domain the locking domain name * @param lock the lock number * @return the found LockingRequest; NULL if a matching LockingRequest wasn't - * found + * found */ static struct GNUNET_LOCKMANAGER_LockingRequest * hashmap_find_lockingrequest (const struct GNUNET_CONTAINER_MultiHashMap *map, - const char *domain, - uint32_t lock) + const char *domain, uint32_t lock) { struct GNUNET_HashCode hash; struct LockingRequestMatch lock_match; @@ -311,9 +350,7 @@ hashmap_find_lockingrequest (const struct GNUNET_CONTAINER_MultiHashMap *map, lock_match.domain = domain; lock_match.lock = lock; get_key (domain, lock, &hash); - GNUNET_CONTAINER_multihashmap_get_multiple (map, - &hash, - &match_iterator, + GNUNET_CONTAINER_multihashmap_get_multiple (map, &hash, &match_iterator, &lock_match); return lock_match.matched_entry; } @@ -335,16 +372,40 @@ call_status_cb_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) LOG (GNUNET_ERROR_TYPE_DEBUG, "Calling status change for SUCCESS on lock num: %d, domain: %s\n", r->lock, r->domain); - r->status_cb (r->status_cb_cls, - r->domain, - r->lock, - r->status); + r->status_cb (r->status_cb_cls, r->domain, r->lock, r->status); } } /** - * Iterator to call relase and free all LockingRequest entries + * Function to generate acquire message for a lock + * + * @param domain_name the domain name of the lock + * @param lock the lock number + * @return the generated GNUNET_LOCKMANAGER_Message + */ +static struct GNUNET_LOCKMANAGER_Message * +generate_acquire_msg (const char *domain_name, uint32_t lock) +{ + struct GNUNET_LOCKMANAGER_Message *msg; + size_t domain_name_len; + uint16_t msg_size; + + domain_name_len = strlen (domain_name) + 1; + msg_size = sizeof (struct GNUNET_LOCKMANAGER_Message) + domain_name_len; + msg = GNUNET_malloc (msg_size); + msg->header.type = htons (GNUNET_MESSAGE_TYPE_LOCKMANAGER_ACQUIRE); + msg->header.size = htons (msg_size); + msg->lock = htonl (lock); + memcpy (&msg[1], domain_name, domain_name_len); + return msg; +} + + +/** + * Iterator to call relase on locks; acquire messages are sent for all + * locks. In addition, if a lock is acquired before, it is not released and its + * status callback is called to signal its release * * @param cls the lockmanager handle * @param key current key code @@ -354,29 +415,29 @@ call_status_cb_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) * GNUNET_NO if not. */ static int -release_iterator(void *cls, - const GNUNET_HashCode * key, - void *value) +release_n_retry_iterator (void *cls, const struct GNUNET_HashCode *key, + void *value) { - struct GNUNET_LOCKMANAGER_Handle *h = cls; struct GNUNET_LOCKMANAGER_LockingRequest *r = value; + struct GNUNET_LOCKMANAGER_Handle *h = cls; + struct GNUNET_LOCKMANAGER_Message *msg; + if (GNUNET_NO == r->acquire_sent) /* an acquire is still in queue */ + return GNUNET_YES; + r->acquire_sent = GNUNET_NO; + msg = generate_acquire_msg (r->domain, r->lock); + r->mqe = queue_message (h, msg, r); + if (GNUNET_LOCKMANAGER_RELEASE == r->status) + return GNUNET_YES; if (NULL != r->status_cb) { LOG (GNUNET_ERROR_TYPE_DEBUG, "Calling status change for RELEASE on lock num: %d, domain: %s\n", r->lock, r->domain); - r->status_cb (r->status_cb_cls, - r->domain, - r->lock, + r->status = GNUNET_LOCKMANAGER_RELEASE; + r->status_cb (r->status_cb_cls, r->domain, r->lock, GNUNET_LOCKMANAGER_RELEASE); } - GNUNET_assert (GNUNET_YES == - GNUNET_CONTAINER_multihashmap_remove (h->hashmap, - key, - value)); - GNUNET_free (r->domain); - GNUNET_free (r); return GNUNET_YES; } @@ -387,9 +448,8 @@ release_iterator(void *cls, * @param cls the LOCKMANAGER_Handle * @param msg received message, NULL on timeout or fatal error */ -static void -handle_replies (void *cls, - const struct GNUNET_MessageHeader *msg) +static void +handle_replies (void *cls, const struct GNUNET_MessageHeader *msg) { struct GNUNET_LOCKMANAGER_Handle *handle = cls; const struct GNUNET_LOCKMANAGER_Message *m; @@ -398,22 +458,21 @@ handle_replies (void *cls, struct GNUNET_HashCode hash; uint32_t lock; uint16_t msize; - + + handle->in_replies = GNUNET_NO; if (NULL == msg) { LOG (GNUNET_ERROR_TYPE_DEBUG, "Lockmanager service not available or went down\n"); - /* Should release all locks and free its locking requests */ + /* Should release all locks and retry to acquire them */ GNUNET_CONTAINER_multihashmap_iterate (handle->hashmap, - &release_iterator, - handle); + &release_n_retry_iterator, handle); return; } - GNUNET_CLIENT_receive (handle->conn, - &handle_replies, - handle, + handle->in_replies = GNUNET_YES; + GNUNET_CLIENT_receive (handle->conn, &handle_replies, handle, GNUNET_TIME_UNIT_FOREVER_REL); - if (GNUNET_MESSAGE_TYPE_LOCKMANAGER_SUCCESS != ntohs(msg->type)) + if (GNUNET_MESSAGE_TYPE_LOCKMANAGER_SUCCESS != ntohs (msg->type)) { GNUNET_break (0); return; @@ -427,20 +486,18 @@ handle_replies (void *cls, m = (const struct GNUNET_LOCKMANAGER_Message *) msg; domain = (const char *) &m[1]; msize -= sizeof (struct GNUNET_LOCKMANAGER_Message); - if ('\0' != domain[msize-1]) + if ('\0' != domain[msize - 1]) { GNUNET_break (0); return; } lock = ntohl (m->lock); - get_key (domain, lock, &hash); + get_key (domain, lock, &hash); LOG (GNUNET_ERROR_TYPE_DEBUG, - "Received SUCCESS message for lock: %d, domain %s\n", - lock, domain); - if (NULL == (lr = hashmap_find_lockingrequest (handle->hashmap, - domain, - lock))) + "Received SUCCESS message for lock: %d, domain %s\n", lock, domain); + if (NULL == + (lr = hashmap_find_lockingrequest (handle->hashmap, domain, lock))) { GNUNET_break (0); return; @@ -451,11 +508,10 @@ handle_replies (void *cls, return; } LOG (GNUNET_ERROR_TYPE_DEBUG, - "Changing status for lock: %d in domain: %s to SUCCESS\n", - lr->lock, lr->domain); + "Changing status for lock: %d in domain: %s to SUCCESS\n", lr->lock, + lr->domain); lr->status = GNUNET_LOCKMANAGER_SUCCESS; - GNUNET_SCHEDULER_add_continuation (&call_status_cb_task, - lr, + GNUNET_SCHEDULER_add_continuation (&call_status_cb_task, lr, GNUNET_SCHEDULER_REASON_PREREQ_DONE); } @@ -471,19 +527,14 @@ handle_replies (void *cls, * GNUNET_NO if not. */ static int -free_iterator(void *cls, - const GNUNET_HashCode * key, - void *value) +free_iterator (void *cls, const struct GNUNET_HashCode *key, void *value) { struct GNUNET_LOCKMANAGER_Handle *h = cls; struct GNUNET_LOCKMANAGER_LockingRequest *r = value; - LOG (GNUNET_ERROR_TYPE_DEBUG, - "Clearing locking request\n"); - GNUNET_assert (GNUNET_YES == - GNUNET_CONTAINER_multihashmap_remove (h->hashmap, - key, - value)); + LOG (GNUNET_ERROR_TYPE_DEBUG, "Clearing locking request\n"); + GNUNET_assert (GNUNET_YES == + GNUNET_CONTAINER_multihashmap_remove (h->hashmap, key, value)); GNUNET_free (r->domain); GNUNET_free (r); return GNUNET_YES; @@ -515,14 +566,12 @@ GNUNET_LOCKMANAGER_connect (const struct GNUNET_CONFIGURATION_Handle *cfg) GNUNET_free (h); LOG (GNUNET_ERROR_TYPE_DEBUG, "%s() END\n", __func__); return NULL; - } - h->hashmap = GNUNET_CONTAINER_multihashmap_create (15); + } + h->hashmap = GNUNET_CONTAINER_multihashmap_create (16, GNUNET_NO); GNUNET_assert (NULL != h->hashmap); - GNUNET_CLIENT_receive (h->conn, - &handle_replies, - h, + h->in_replies = GNUNET_YES; + GNUNET_CLIENT_receive (h->conn, &handle_replies, h, GNUNET_TIME_UNIT_FOREVER_REL); - LOG (GNUNET_ERROR_TYPE_DEBUG, "%s() END\n", __func__); return h; } @@ -544,8 +593,7 @@ GNUNET_LOCKMANAGER_disconnect (struct GNUNET_LOCKMANAGER_Handle *handle) LOG (GNUNET_ERROR_TYPE_WARNING, "Some locking requests are still present. Cancel them before " "calling %s\n", __func__); - GNUNET_CONTAINER_multihashmap_iterate (handle->hashmap, - &free_iterator, + GNUNET_CONTAINER_multihashmap_iterate (handle->hashmap, &free_iterator, handle); } GNUNET_CONTAINER_multihashmap_destroy (handle->hashmap); @@ -557,9 +605,7 @@ GNUNET_LOCKMANAGER_disconnect (struct GNUNET_LOCKMANAGER_Handle *handle) head = handle->mq_head; while (NULL != head) { - GNUNET_CONTAINER_DLL_remove (handle->mq_head, - handle->mq_tail, - head); + GNUNET_CONTAINER_DLL_remove (handle->mq_head, handle->mq_tail, head); GNUNET_free (head->msg); GNUNET_free (head); head = handle->mq_head; @@ -595,18 +641,15 @@ GNUNET_LOCKMANAGER_disconnect (struct GNUNET_LOCKMANAGER_Handle *handle) */ struct GNUNET_LOCKMANAGER_LockingRequest * GNUNET_LOCKMANAGER_acquire_lock (struct GNUNET_LOCKMANAGER_Handle *handle, - const char *domain_name, - uint32_t lock, - GNUNET_LOCKMANAGER_StatusCallback - status_cb, + const char *domain_name, uint32_t lock, + GNUNET_LOCKMANAGER_StatusCallback status_cb, void *status_cb_cls) { struct GNUNET_LOCKMANAGER_LockingRequest *r; struct GNUNET_LOCKMANAGER_Message *msg; struct GNUNET_HashCode hash; - uint16_t msg_size; size_t domain_name_length; - + LOG (GNUNET_ERROR_TYPE_DEBUG, "%s()\n", __func__); r = GNUNET_malloc (sizeof (struct GNUNET_LOCKMANAGER_LockingRequest)); domain_name_length = strlen (domain_name) + 1; @@ -616,30 +659,25 @@ GNUNET_LOCKMANAGER_acquire_lock (struct GNUNET_LOCKMANAGER_Handle *handle, r->status = GNUNET_LOCKMANAGER_RELEASE; r->status_cb = status_cb; r->status_cb_cls = status_cb_cls; + r->acquire_sent = GNUNET_NO; memcpy (r->domain, domain_name, domain_name_length); - msg_size = sizeof (struct GNUNET_LOCKMANAGER_Message) + domain_name_length; - msg = GNUNET_malloc (msg_size); - msg->header.type = htons (GNUNET_MESSAGE_TYPE_LOCKMANAGER_ACQUIRE); - msg->header.size = htons (msg_size); - msg->lock = htonl (lock); - memcpy (&msg[1], r->domain, domain_name_length); + msg = generate_acquire_msg (r->domain, r->lock); LOG (GNUNET_ERROR_TYPE_DEBUG, "Queueing ACQUIRE message\n"); - queue_message (handle, msg); + r->mqe = queue_message (handle, msg, r); get_key (r->domain, r->lock, &hash); - GNUNET_CONTAINER_multihashmap_put (r->handle->hashmap, - &hash, - r, - GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE); + GNUNET_assert (GNUNET_OK == + GNUNET_CONTAINER_multihashmap_put (r->handle->hashmap, &hash, + r, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE)); LOG (GNUNET_ERROR_TYPE_DEBUG, "%s() END\n", __func__); return r; } - /** * Function to cancel the locking request generated by - * GNUNET_LOCKMANAGER_acquire_lock. If the lock is acquired us then the lock is - * released. GNUNET_LOCKMANAGER_StatusCallback will not be called upon any + * GNUNET_LOCKMANAGER_acquire_lock. If the lock is acquired by us then the lock + * is released. GNUNET_LOCKMANAGER_StatusCallback will not be called upon any * status changes resulting due to this call. * * @param request the LockingRequest to cancel @@ -654,24 +692,41 @@ GNUNET_LOCKMANAGER_cancel_request (struct GNUNET_LOCKMANAGER_LockingRequest size_t domain_name_length; LOG (GNUNET_ERROR_TYPE_DEBUG, "%s()\n", __func__); - /* FIXME: Stop ACQUIRE retransmissions */ + if (GNUNET_NO == request->acquire_sent) + { + GNUNET_assert (NULL != request->mqe); + if ((NULL != request->handle->transmit_handle) && + (request->handle->mq_head == request->mqe)) + { + GNUNET_CLIENT_notify_transmit_ready_cancel (request-> + handle->transmit_handle); + request->handle->transmit_handle = NULL; + } + GNUNET_CONTAINER_DLL_remove (request->handle->mq_head, + request->handle->mq_tail, request->mqe); + GNUNET_free (request->mqe->msg); + GNUNET_free (request->mqe); + request->status = GNUNET_LOCKMANAGER_RELEASE; + } if (GNUNET_LOCKMANAGER_SUCCESS == request->status) { domain_name_length = strlen (request->domain) + 1; - msg_size = sizeof (struct GNUNET_LOCKMANAGER_Message) - + domain_name_length; + msg_size = sizeof (struct GNUNET_LOCKMANAGER_Message) + domain_name_length; msg = GNUNET_malloc (msg_size); msg->header.type = htons (GNUNET_MESSAGE_TYPE_LOCKMANAGER_RELEASE); msg->header.size = htons (msg_size); msg->lock = htonl (request->lock); memcpy (&msg[1], request->domain, domain_name_length); - queue_message (request->handle, msg); + GNUNET_assert (NULL == request->mqe); + (void) queue_message (request->handle, msg, request); } get_key (request->domain, request->lock, &hash); GNUNET_assert (GNUNET_YES == - GNUNET_CONTAINER_multihashmap_remove - (request->handle->hashmap, &hash, request)); + GNUNET_CONTAINER_multihashmap_remove (request->handle->hashmap, + &hash, request)); GNUNET_free (request->domain); GNUNET_free (request); LOG (GNUNET_ERROR_TYPE_DEBUG, "%s() END\n", __func__); } + +/* end of lockmanager_api.c */ diff --git a/src/lockmanager/test_lockmanager_api.c b/src/lockmanager/test_lockmanager_api.c index e8d0412..dd9d48f 100644 --- a/src/lockmanager/test_lockmanager_api.c +++ b/src/lockmanager/test_lockmanager_api.c @@ -27,11 +27,11 @@ #include "platform.h" #include "gnunet_util_lib.h" #include "gnunet_lockmanager_service.h" +#include "gnunet_testing_lib.h" -#define VERBOSE GNUNET_YES - -#define VERBOSE_ARM 1 - +/** + * Generic logging shortcut + */ #define LOG(kind,...) \ GNUNET_log (kind, __VA_ARGS__) @@ -43,15 +43,15 @@ * Enumeration of testing steps */ enum Test - { - TEST_FAIL, +{ + TEST_FAIL, - TEST_INIT, + TEST_INIT, - LOCK1_ACQUIRE, + LOCK1_ACQUIRE, - LOCK2_ACQUIRE - }; + LOCK2_ACQUIRE +}; /** @@ -59,15 +59,10 @@ enum Test */ static enum Test result; -/** - * The process id of the GNUNET ARM process - */ -static struct GNUNET_OS_Process *arm_pid = NULL; - /** * Configuration Handle */ -static struct GNUNET_CONFIGURATION_Handle *config; +static const struct GNUNET_CONFIGURATION_Handle *config; /** * The handle to the lockmanager service @@ -96,28 +91,19 @@ static GNUNET_SCHEDULER_TaskIdentifier abort_task_id; * @param tc the task context */ static void -do_shutdown (void *cls, const const struct GNUNET_SCHEDULER_TaskContext *tc) +do_shutdown (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { if (GNUNET_SCHEDULER_NO_TASK != abort_task_id) - { - GNUNET_SCHEDULER_cancel (abort_task_id); - abort_task_id = GNUNET_SCHEDULER_NO_TASK; - } + { + GNUNET_SCHEDULER_cancel (abort_task_id); + abort_task_id = GNUNET_SCHEDULER_NO_TASK; + } if (NULL != request) GNUNET_LOCKMANAGER_cancel_request (request); if (NULL != request2) GNUNET_LOCKMANAGER_cancel_request (request2); GNUNET_LOCKMANAGER_disconnect (handle); - if (0 != GNUNET_OS_process_kill (arm_pid, SIGTERM)) - { - LOG (GNUNET_ERROR_TYPE_DEBUG, - "Kill gnunet-service-arm manually\n"); - } - GNUNET_OS_process_wait (arm_pid); - GNUNET_OS_process_destroy (arm_pid); - - if (NULL != config) - GNUNET_CONFIGURATION_destroy (config); + GNUNET_SCHEDULER_shutdown (); } @@ -128,7 +114,7 @@ do_shutdown (void *cls, const const struct GNUNET_SCHEDULER_TaskContext *tc) * @param tc the task context */ static void -do_abort (void *cls, const const struct GNUNET_SCHEDULER_TaskContext *tc) +do_abort (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { LOG (GNUNET_ERROR_TYPE_DEBUG, "Aborting test...\n"); abort_task_id = GNUNET_SCHEDULER_NO_TASK; @@ -141,22 +127,20 @@ do_abort (void *cls, const const struct GNUNET_SCHEDULER_TaskContext *tc) * * @param cls the closure from GNUNET_LOCKMANAGER_lock call * - * @param domain_name the locking domain of the lock + * @param domain_name the locking domain of the lock * * @param lock the lock for which this status is relevant * * @param status GNUNET_LOCKMANAGER_SUCCESS if the lock has been successfully * acquired; GNUNET_LOCKMANAGER_RELEASE when the acquired lock is lost */ -static void -status_cb (void *cls, - const char *domain_name, - uint32_t lock, +static void +status_cb (void *cls, const char *domain_name, uint32_t lock, enum GNUNET_LOCKMANAGER_Status status) { LOG (GNUNET_ERROR_TYPE_DEBUG, - "Status change callback called on lock: %d of domain: %s\n", - lock, domain_name); + "Status change callback called on lock: %d of domain: %s\n", lock, + domain_name); switch (result) { case LOCK1_ACQUIRE: @@ -165,46 +149,19 @@ status_cb (void *cls, //GNUNET_LOCKMANAGER_cancel_request (request); //request = NULL; result = LOCK2_ACQUIRE; - request2 = GNUNET_LOCKMANAGER_acquire_lock (handle, - "GNUNET_LOCKMANAGER_TESTING", - 100, - &status_cb, - NULL); + request2 = + GNUNET_LOCKMANAGER_acquire_lock (handle, "GNUNET_LOCKMANAGER_TESTING", + 100, &status_cb, NULL); GNUNET_assert (NULL != request2); break; case LOCK2_ACQUIRE: GNUNET_assert (GNUNET_LOCKMANAGER_SUCCESS == status); GNUNET_assert (NULL != request); - GNUNET_SCHEDULER_add_delayed (TIME_REL_SECONDS (1), - &do_shutdown, - NULL); + GNUNET_SCHEDULER_add_delayed (TIME_REL_SECONDS (1), &do_shutdown, NULL); break; default: GNUNET_break (0); - } -} - - -/** - * Testing function - * - * @param cls NULL - * @param tc the task context - */ -static void -test (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - handle = GNUNET_LOCKMANAGER_connect (config); - GNUNET_assert (NULL != handle); - result = LOCK1_ACQUIRE; - request = GNUNET_LOCKMANAGER_acquire_lock (handle, - "GNUNET_LOCKMANAGER_TESTING", - 99, - &status_cb, - NULL); - abort_task_id = GNUNET_SCHEDULER_add_delayed (TIME_REL_SECONDS (10), - &do_abort, - NULL); + } } @@ -212,68 +169,34 @@ test (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) * Main point of test execution */ static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) +run (void *cls, const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) { LOG (GNUNET_ERROR_TYPE_DEBUG, "Starting test...\n"); - config = GNUNET_CONFIGURATION_dup (cfg); - arm_pid = - GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-arm", - "gnunet-service-arm", -#if VERBOSE_ARM - "-L", "DEBUG", -#endif - "-c", "test_lockmanager_api.conf", NULL); - - GNUNET_assert (NULL != arm_pid); - GNUNET_SCHEDULER_add_delayed (TIME_REL_SECONDS (3), - &test, - NULL); + config = cfg; + handle = GNUNET_LOCKMANAGER_connect (config); + GNUNET_assert (NULL != handle); + result = LOCK1_ACQUIRE; + request = + GNUNET_LOCKMANAGER_acquire_lock (handle, "GNUNET_LOCKMANAGER_TESTING", 99, + &status_cb, NULL); + abort_task_id = + GNUNET_SCHEDULER_add_delayed (TIME_REL_SECONDS (30), &do_abort, NULL); } /** * Main function */ -int main (int argc, char **argv) +int +main (int argc, char **argv) { - int ret; - - char *const argv2[] = { "test-lockmanager-api", - "-c", "test_lockmanager_api.conf", -#if VERBOSE - "-L", "DEBUG", -#endif - NULL - }; - - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - - GNUNET_log_setup ("test-lockmanager-api", -#if VERBOSE - "DEBUG", -#else - "WARNING", -#endif - NULL); - - ret = - GNUNET_PROGRAM_run ((sizeof (argv2) / sizeof (char *)) - 1, argv2, - "test-lockmanager-api", "nohelp", options, &run, NULL); - if (GNUNET_OK != ret) - { - LOG (GNUNET_ERROR_TYPE_WARNING, "run failed with error code %d\n", - ret); + if (0 != + GNUNET_TESTING_peer_run ("test_lockmanager_api", + "test_lockmanager_api.conf", &run, NULL)) return 1; - } - if (TEST_FAIL == result) - { - LOG (GNUNET_ERROR_TYPE_WARNING, "test failed\n"); - return 1; - } - LOG (GNUNET_ERROR_TYPE_INFO, "test OK\n"); - return 0; + return (TEST_FAIL == result) ? 1 : 0; } + +/* end of test_lockmanager_api.c */ diff --git a/src/lockmanager/test_lockmanager_api.conf b/src/lockmanager/test_lockmanager_api.conf index 894f409..4ac6b56 100644 --- a/src/lockmanager/test_lockmanager_api.conf +++ b/src/lockmanager/test_lockmanager_api.conf @@ -1,5 +1,4 @@ [lockmanager] -DEBUG = YES AUTOSTART = NO PORT = 12112 ACCEPT_FROM = 127.0.0.1; @@ -28,7 +27,6 @@ DATABASE = sqlite [transport] PLUGINS = tcp -DEBUG = NO ACCEPT_FROM6 = ::1; ACCEPT_FROM = 127.0.0.1; NEIGHBOUR_LIMIT = 50 @@ -44,7 +42,6 @@ PORT = 12092 [arm] DEFAULTSERVICES = core lockmanager PORT = 12366 -DEBUG = NO [transport-tcp] TIMEOUT = 300 s @@ -53,7 +50,6 @@ PORT = 12368 [TESTING] NUM_PEERS = 5 WEAKRANDOM = YES -DEBUG = YES HOSTKEYSFILE = ../../contrib/testing_hostkeys.dat MAX_CONCURRENT_SSH = 10 USE_PROGRESSBARS = YES @@ -63,7 +59,6 @@ PEERGROUP_TIMEOUT = 2400 s HOSTKEY = $SERVICEHOME/.hostkey [PATHS] -DEFAULTCONFIG = test_lockmanager_api.conf SERVICEHOME = /tmp/test-lockmanager/ [dns] @@ -71,3 +66,6 @@ AUTOSTART = NO [nse] AUTOSTART = NO + +[consensus] +AUTOSTART = NO diff --git a/src/lockmanager/test_lockmanager_api_acquireretry.c b/src/lockmanager/test_lockmanager_api_acquireretry.c new file mode 100644 index 0000000..d2c88e5 --- /dev/null +++ b/src/lockmanager/test_lockmanager_api_acquireretry.c @@ -0,0 +1,224 @@ +/* + This file is part of GNUnet. + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 2, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @file lockmanager/test_lockmanager_api_acquireretry.c + * @brief Test cases for lockmanager_api where the server crashes and comes + * back; the api should try to acqurie the lock again + * @author Sree Harsha Totakura + */ + +#include "platform.h" +#include "gnunet_util_lib.h" +#include "gnunet_lockmanager_service.h" +#include "gnunet_testing_lib.h" + +/** + * Generic logging shorthand + */ +#define LOG(kind,...) \ + GNUNET_log (kind, __VA_ARGS__) + +/** + * Relative seconds shorthand + */ +#define TIME_REL_SECS(sec) \ + GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, sec) + +/** + * Various stages in test + */ +enum Test +{ + /** + * Signal test failure + */ + TEST_FAIL, + + /** + * Testing just began + */ + TEST_INIT, + + /** + * Client has successfully acquired the lock + */ + TEST_CLIENT_LOCK_SUCCESS, + + /** + * Client has lost the lock + */ + TEST_CLIENT_LOCK_RELEASE, + + /** + * Client has again acquired the lock + */ + TEST_CLIENT_LOCK_AGAIN_SUCCESS +}; + +/** + * Configuration Handle + */ +static const struct GNUNET_CONFIGURATION_Handle *config; + +/** + * The handle to the lockmanager service + */ +static struct GNUNET_LOCKMANAGER_Handle *handle; + +/** + * The locking request + */ +static struct GNUNET_LOCKMANAGER_LockingRequest *request; + +/** + * Abort task identifier + */ +static GNUNET_SCHEDULER_TaskIdentifier abort_task_id; + +/** + * The test result + */ +enum Test result; + +/** + * Our peer + */ +static struct GNUNET_TESTING_Peer *self; + + +/** + * Shutdown nicely + * + * @param cls + * @param tc the task context + */ +static void +do_shutdown (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + if (GNUNET_SCHEDULER_NO_TASK != abort_task_id) + { + GNUNET_SCHEDULER_cancel (abort_task_id); + abort_task_id = GNUNET_SCHEDULER_NO_TASK; + } + if (NULL != handle) + GNUNET_LOCKMANAGER_disconnect (handle); +} + +/** + * Abort + * + * @param cls + * @param tc the task context + */ +static void +do_abort (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + LOG (GNUNET_ERROR_TYPE_DEBUG, "Aborting test...\n"); + abort_task_id = GNUNET_SCHEDULER_NO_TASK; + result = TEST_FAIL; + do_shutdown (cls, tc); +} + + +/** + * Callback for lock status changes + * + * @param cls the handle + * + * @param domain_name the locking domain of the lock + * + * @param lock the lock for which this status is relevant + * + * @param status GNUNET_LOCKMANAGER_SUCCESS if the lock has been successfully + * acquired; GNUNET_LOCKMANAGER_RELEASE when the acquired lock is lost + */ +static void +status_cb (void *cls, const char *domain_name, uint32_t lock, + enum GNUNET_LOCKMANAGER_Status status) +{ + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Status change callback called on lock: %d of domain: %s\n", lock, + domain_name); + switch (result) + { + case TEST_INIT: + GNUNET_assert (handle == cls); + GNUNET_assert (GNUNET_LOCKMANAGER_SUCCESS == status); + result = TEST_CLIENT_LOCK_SUCCESS; + /* We should kill the lockmanager process */ + GNUNET_TESTING_peer_stop (self); + break; + case TEST_CLIENT_LOCK_SUCCESS: + GNUNET_assert (handle == cls); + GNUNET_assert (GNUNET_LOCKMANAGER_RELEASE == status); + result = TEST_CLIENT_LOCK_RELEASE; + /* Now we should start again the lockmanager process */ + GNUNET_TESTING_peer_start (self); + break; + case TEST_CLIENT_LOCK_RELEASE: + GNUNET_assert (handle == cls); + GNUNET_assert (GNUNET_LOCKMANAGER_SUCCESS == status); + result = TEST_CLIENT_LOCK_AGAIN_SUCCESS; + GNUNET_LOCKMANAGER_cancel_request (request); + request = NULL; + GNUNET_SCHEDULER_add_delayed (TIME_REL_SECS (1), &do_shutdown, NULL); + break; + default: + GNUNET_assert (0); /* We should never reach here */ + } +} + + +/** + * Main point of test execution + */ +static void +run (void *cls, const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) +{ + config = cfg; + self = peer; + result = TEST_INIT; + handle = GNUNET_LOCKMANAGER_connect (config); + GNUNET_assert (NULL != handle); + request = + GNUNET_LOCKMANAGER_acquire_lock (handle, "GNUNET_LOCKMANAGER_TESTING", 99, + &status_cb, handle); + GNUNET_assert (NULL != request); + abort_task_id = + GNUNET_SCHEDULER_add_delayed (TIME_REL_SECS (30), &do_abort, NULL); +} + + +/** + * Main function + */ +int +main (int argc, char **argv) +{ + if (0 != + GNUNET_TESTING_peer_run ("test_lockmanager_api_acquireretry", + "test_lockmanager_api.conf", &run, NULL)) + return 1; + return (TEST_CLIENT_LOCK_AGAIN_SUCCESS != result) ? 1 : 0; +} + +/* end of test_lockmanager_api_acquireretry.c */ diff --git a/src/lockmanager/test_lockmanager_api_lockrelease.c b/src/lockmanager/test_lockmanager_api_lockrelease.c index 7e24d10..ba4881a 100644 --- a/src/lockmanager/test_lockmanager_api_lockrelease.c +++ b/src/lockmanager/test_lockmanager_api_lockrelease.c @@ -26,15 +26,18 @@ #include "platform.h" #include "gnunet_util_lib.h" +#include "gnunet_testing_lib.h" #include "gnunet_lockmanager_service.h" -#define VERBOSE GNUNET_YES - -#define VERBOSE_ARM 1 - +/** + * Generic Logging shorthand + */ #define LOG(kind,...) \ GNUNET_log (kind, __VA_ARGS__) +/** + * Relative seconds shorthand + */ #define TIME_REL_SECONDS(min) \ GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, min) @@ -42,43 +45,38 @@ * Various steps of the test */ enum Test - { +{ /** * Signal test failure */ - TEST_FAIL, + TEST_FAIL, /** * Testing just began */ - TEST_INIT, + TEST_INIT, /** * Client 1 has got the lock successfully; Client 2 should try to acquire * the lock now; after some time client 1 has to release the lock */ - TEST_CLIENT1_LOCK_SUCCESS, + TEST_CLIENT1_LOCK_SUCCESS, /** * Client 2 has got the lock; Should release it and call shutdown */ - TEST_CLIENT2_LOCK_SUCCESS, - }; + TEST_CLIENT2_LOCK_SUCCESS, +}; /** * The testing result */ static enum Test result; -/** - * The process id of the GNUNET ARM process - */ -static struct GNUNET_OS_Process *arm_pid = NULL; - /** * Configuration Handle */ -static struct GNUNET_CONFIGURATION_Handle *config; +static const struct GNUNET_CONFIGURATION_Handle *config; /** * The handle to the lockmanager service @@ -113,26 +111,15 @@ static GNUNET_SCHEDULER_TaskIdentifier abort_task_id; * @param tc the task context */ static void -do_shutdown (void *cls, const const struct GNUNET_SCHEDULER_TaskContext *tc) +do_shutdown (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { if (GNUNET_SCHEDULER_NO_TASK != abort_task_id) { GNUNET_SCHEDULER_cancel (abort_task_id); abort_task_id = GNUNET_SCHEDULER_NO_TASK; } - GNUNET_LOCKMANAGER_disconnect (handle); GNUNET_LOCKMANAGER_disconnect (handle2); - if (0 != GNUNET_OS_process_kill (arm_pid, SIGTERM)) - { - LOG (GNUNET_ERROR_TYPE_DEBUG, - "Kill gnunet-service-arm manually\n"); - } - GNUNET_OS_process_wait (arm_pid); - GNUNET_OS_process_destroy (arm_pid); - - if (NULL != config) - GNUNET_CONFIGURATION_destroy (config); } @@ -143,7 +130,7 @@ do_shutdown (void *cls, const const struct GNUNET_SCHEDULER_TaskContext *tc) * @param tc the task context */ static void -do_abort (void *cls, const const struct GNUNET_SCHEDULER_TaskContext *tc) +do_abort (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { LOG (GNUNET_ERROR_TYPE_DEBUG, "Aborting test...\n"); abort_task_id = GNUNET_SCHEDULER_NO_TASK; @@ -157,33 +144,29 @@ do_abort (void *cls, const const struct GNUNET_SCHEDULER_TaskContext *tc) * * @param cls the handle * - * @param domain_name the locking domain of the lock + * @param domain_name the locking domain of the lock * * @param lock the lock for which this status is relevant * * @param status GNUNET_LOCKMANAGER_SUCCESS if the lock has been successfully * acquired; GNUNET_LOCKMANAGER_RELEASE when the acquired lock is lost */ -static void -status_cb (void *cls, - const char *domain_name, - uint32_t lock, +static void +status_cb (void *cls, const char *domain_name, uint32_t lock, enum GNUNET_LOCKMANAGER_Status status) { LOG (GNUNET_ERROR_TYPE_DEBUG, - "Status change callback called on lock: %d of domain: %s\n", - lock, domain_name); + "Status change callback called on lock: %d of domain: %s\n", lock, + domain_name); GNUNET_assert (GNUNET_LOCKMANAGER_SUCCESS == status); switch (result) { case TEST_INIT: GNUNET_assert (handle == cls); result = TEST_CLIENT1_LOCK_SUCCESS; - request2 = GNUNET_LOCKMANAGER_acquire_lock (handle2, - "GNUNET_LOCKMANAGER_TESTING", - 99, - &status_cb, - handle2); + request2 = + GNUNET_LOCKMANAGER_acquire_lock (handle2, "GNUNET_LOCKMANAGER_TESTING", + 99, &status_cb, handle2); GNUNET_assert (NULL != request2); GNUNET_LOCKMANAGER_cancel_request (request); request = NULL; @@ -192,9 +175,7 @@ status_cb (void *cls, GNUNET_assert (handle2 == cls); result = TEST_CLIENT2_LOCK_SUCCESS; GNUNET_LOCKMANAGER_cancel_request (request2); - GNUNET_SCHEDULER_add_delayed (TIME_REL_SECONDS (1), - &do_shutdown, - NULL); + GNUNET_SCHEDULER_add_delayed (TIME_REL_SECONDS (1), &do_shutdown, NULL); break; default: GNUNET_assert (0); /* We should never reach here */ @@ -204,98 +185,39 @@ status_cb (void *cls, /** - * Testing function - * - * @param cls NULL - * @param tc the task context + * Main point of test execution */ static void -test (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ +run (void *cls, const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) +{ + LOG (GNUNET_ERROR_TYPE_DEBUG, "Starting test...\n"); + config = cfg; result = TEST_INIT; handle = GNUNET_LOCKMANAGER_connect (config); GNUNET_assert (NULL != handle); handle2 = GNUNET_LOCKMANAGER_connect (config); - - request = GNUNET_LOCKMANAGER_acquire_lock (handle, - "GNUNET_LOCKMANAGER_TESTING", - 99, - &status_cb, - handle); - GNUNET_assert (NULL != request); - abort_task_id = GNUNET_SCHEDULER_add_delayed (TIME_REL_SECONDS (10), - &do_abort, - NULL); -} - - -/** - * Main point of test execution - */ -static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) -{ - LOG (GNUNET_ERROR_TYPE_DEBUG, "Starting test...\n"); - config = GNUNET_CONFIGURATION_dup (cfg); - arm_pid = - GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-arm", - "gnunet-service-arm", -#if VERBOSE_ARM - "-L", "DEBUG", -#endif - "-c", "test_lockmanager_api.conf", NULL); - GNUNET_assert (NULL != arm_pid); - GNUNET_SCHEDULER_add_delayed (TIME_REL_SECONDS (3), - &test, - NULL); + request = + GNUNET_LOCKMANAGER_acquire_lock (handle, "GNUNET_LOCKMANAGER_TESTING", 99, + &status_cb, handle); + GNUNET_assert (NULL != request); + abort_task_id = + GNUNET_SCHEDULER_add_delayed (TIME_REL_SECONDS (10), &do_abort, NULL); } /** * Main function */ -int main (int argc, char **argv) +int +main (int argc, char **argv) { - int ret; - - char *const argv2[] = { "test-lockmanager-api-lockrelease", - "-c", "test_lockmanager_api.conf", -#if VERBOSE - "-L", "DEBUG", -#endif - NULL - }; - - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - - GNUNET_log_setup ("test-lockmanager-api-lockrelease", -#if VERBOSE - "DEBUG", -#else - "WARNING", -#endif - NULL); - - ret = - GNUNET_PROGRAM_run ((sizeof (argv2) / sizeof (char *)) - 1, argv2, - "test-lockmanager-api-lockrelease", - "nohelp", options, &run, NULL); - - if (GNUNET_OK != ret) - { - LOG (GNUNET_ERROR_TYPE_WARNING, "run failed with error code %d\n", - ret); + if (0 != + GNUNET_TESTING_peer_run ("test_lockmanager_api_lockrelease", + "test_lockmanager_api.conf", &run, NULL)) return 1; - } - if (TEST_CLIENT2_LOCK_SUCCESS != result) - { - LOG (GNUNET_ERROR_TYPE_WARNING, "test failed\n"); - return 1; - } - LOG (GNUNET_ERROR_TYPE_INFO, "test OK\n"); - return 0; + return (TEST_CLIENT2_LOCK_SUCCESS != result) ? 1 : 0; } + +/* end of test_lockmanager_api_lockrelease.c */ diff --git a/src/lockmanager/test_lockmanager_api_servercrash.c b/src/lockmanager/test_lockmanager_api_servercrash.c index 3fa6418..a37d614 100644 --- a/src/lockmanager/test_lockmanager_api_servercrash.c +++ b/src/lockmanager/test_lockmanager_api_servercrash.c @@ -27,14 +27,17 @@ #include "platform.h" #include "gnunet_util_lib.h" #include "gnunet_lockmanager_service.h" +#include "gnunet_testing_lib.h" -#define VERBOSE GNUNET_YES - -#define VERBOSE_ARM 1 - +/** + * Generic logging shorthand + */ #define LOG(kind,...) \ GNUNET_log (kind, __VA_ARGS__) +/** + * Relative seconds shorthand + */ #define TIME_REL_SECONDS(min) \ GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, min) @@ -42,49 +45,44 @@ * Various steps of the test */ enum Test - { +{ /** * Signal test failure */ - TEST_FAIL, + TEST_FAIL, /** * Testing just began */ - TEST_INIT, + TEST_INIT, /** * Client 1 has got the lock successfully; Client 2 should try to acquire * the lock now; after some time client 1 has to release the lock */ - TEST_CLIENT1_LOCK_SUCCESS, + TEST_CLIENT1_LOCK_SUCCESS, /** * Client 2 has got the lock; Server should crash now; */ - TEST_CLIENT2_LOCK_SUCCESS, + TEST_CLIENT2_LOCK_SUCCESS, /** * Client 2 should get lock release due to server crash; Should call * shutdown now */ - TEST_CLIENT2_SERVER_CRASH_SUCCESS - }; + TEST_CLIENT2_SERVER_CRASH_SUCCESS +}; /** * The testing result */ static enum Test result; -/** - * The process id of the GNUNET ARM process - */ -static struct GNUNET_OS_Process *arm_pid = NULL; - /** * Configuration Handle */ -static struct GNUNET_CONFIGURATION_Handle *config; +static const struct GNUNET_CONFIGURATION_Handle *config; /** * The handle to the lockmanager service @@ -111,6 +109,11 @@ static struct GNUNET_LOCKMANAGER_LockingRequest *request2; */ static GNUNET_SCHEDULER_TaskIdentifier abort_task_id; +/** + * Our peer + */ +static struct GNUNET_TESTING_Peer *self; + /** * Shutdown nicely @@ -119,7 +122,7 @@ static GNUNET_SCHEDULER_TaskIdentifier abort_task_id; * @param tc the task context */ static void -do_shutdown (void *cls, const const struct GNUNET_SCHEDULER_TaskContext *tc) +do_shutdown (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { if (GNUNET_SCHEDULER_NO_TASK != abort_task_id) { @@ -130,18 +133,6 @@ do_shutdown (void *cls, const const struct GNUNET_SCHEDULER_TaskContext *tc) GNUNET_LOCKMANAGER_disconnect (handle); if (NULL != handle2) GNUNET_LOCKMANAGER_disconnect (handle2); - if (NULL != arm_pid) - { - if (0 != GNUNET_OS_process_kill (arm_pid, SIGTERM)) - { - LOG (GNUNET_ERROR_TYPE_DEBUG, - "Kill gnunet-service-arm manually\n"); - } - GNUNET_OS_process_wait (arm_pid); - GNUNET_OS_process_destroy (arm_pid); - } - if (NULL != config) - GNUNET_CONFIGURATION_destroy (config); } @@ -152,7 +143,7 @@ do_shutdown (void *cls, const const struct GNUNET_SCHEDULER_TaskContext *tc) * @param tc the task context */ static void -do_abort (void *cls, const const struct GNUNET_SCHEDULER_TaskContext *tc) +do_abort (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { LOG (GNUNET_ERROR_TYPE_DEBUG, "Aborting test...\n"); abort_task_id = GNUNET_SCHEDULER_NO_TASK; @@ -166,33 +157,29 @@ do_abort (void *cls, const const struct GNUNET_SCHEDULER_TaskContext *tc) * * @param cls the handle * - * @param domain_name the locking domain of the lock + * @param domain_name the locking domain of the lock * * @param lock the lock for which this status is relevant * * @param status GNUNET_LOCKMANAGER_SUCCESS if the lock has been successfully * acquired; GNUNET_LOCKMANAGER_RELEASE when the acquired lock is lost */ -static void -status_cb (void *cls, - const char *domain_name, - uint32_t lock, +static void +status_cb (void *cls, const char *domain_name, uint32_t lock, enum GNUNET_LOCKMANAGER_Status status) { LOG (GNUNET_ERROR_TYPE_DEBUG, - "Status change callback called on lock: %d of domain: %s\n", - lock, domain_name); + "Status change callback called on lock: %d of domain: %s\n", lock, + domain_name); switch (result) { case TEST_INIT: GNUNET_assert (handle == cls); GNUNET_assert (GNUNET_LOCKMANAGER_SUCCESS == status); result = TEST_CLIENT1_LOCK_SUCCESS; - request2 = GNUNET_LOCKMANAGER_acquire_lock (handle2, - "GNUNET_LOCKMANAGER_TESTING", - 99, - &status_cb, - handle2); + request2 = + GNUNET_LOCKMANAGER_acquire_lock (handle2, "GNUNET_LOCKMANAGER_TESTING", + 99, &status_cb, handle2); GNUNET_assert (NULL != request2); GNUNET_LOCKMANAGER_cancel_request (request); request = NULL; @@ -201,15 +188,8 @@ status_cb (void *cls, GNUNET_assert (handle2 == cls); GNUNET_assert (GNUNET_LOCKMANAGER_SUCCESS == status); result = TEST_CLIENT2_LOCK_SUCCESS; - /* We should kill the lockmanager process */ - if (0 != GNUNET_OS_process_kill (arm_pid, SIGTERM)) - { - LOG (GNUNET_ERROR_TYPE_DEBUG, - "Kill gnunet-service-arm manually\n"); - } - GNUNET_OS_process_wait (arm_pid); - GNUNET_OS_process_destroy (arm_pid); - arm_pid =NULL; + /* We should stop our peer to simulate crash in lockmanager service */ + GNUNET_TESTING_peer_stop (self); break; case TEST_CLIENT2_LOCK_SUCCESS: GNUNET_assert (handle2 == cls); @@ -217,110 +197,50 @@ status_cb (void *cls, GNUNET_assert (99 == lock); GNUNET_assert (0 == strcmp (domain_name, "GNUNET_LOCKMANAGER_TESTING")); result = TEST_CLIENT2_SERVER_CRASH_SUCCESS; - GNUNET_SCHEDULER_add_delayed (TIME_REL_SECONDS (1), - &do_shutdown, - NULL); + GNUNET_LOCKMANAGER_cancel_request (request2); + request2 = NULL; + GNUNET_SCHEDULER_add_delayed (TIME_REL_SECONDS (1), &do_shutdown, NULL); break; default: GNUNET_assert (0); /* We should never reach here */ } - } /** - * Testing function - * - * @param cls NULL - * @param tc the task context + * Main point of test execution */ static void -test (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ +run (void *cls, const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) +{ + config = cfg; + self = peer; result = TEST_INIT; handle = GNUNET_LOCKMANAGER_connect (config); GNUNET_assert (NULL != handle); handle2 = GNUNET_LOCKMANAGER_connect (config); - - request = GNUNET_LOCKMANAGER_acquire_lock (handle, - "GNUNET_LOCKMANAGER_TESTING", - 99, - &status_cb, - handle); - GNUNET_assert (NULL != request); - abort_task_id = GNUNET_SCHEDULER_add_delayed (TIME_REL_SECONDS (10), - &do_abort, - NULL); -} - -/** - * Main point of test execution - */ -static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) -{ - LOG (GNUNET_ERROR_TYPE_DEBUG, "Starting test...\n"); - config = GNUNET_CONFIGURATION_dup (cfg); - arm_pid = - GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-arm", - "gnunet-service-arm", -#if VERBOSE_ARM - "-L", "DEBUG", -#endif - "-c", "test_lockmanager_api.conf", NULL); - - GNUNET_assert (NULL != arm_pid); - GNUNET_SCHEDULER_add_delayed (TIME_REL_SECONDS (3), - &test, - NULL); + request = + GNUNET_LOCKMANAGER_acquire_lock (handle, "GNUNET_LOCKMANAGER_TESTING", 99, + &status_cb, handle); + GNUNET_assert (NULL != request); + abort_task_id = + GNUNET_SCHEDULER_add_delayed (TIME_REL_SECONDS (10), &do_abort, NULL); } /** * Main function */ -int main (int argc, char **argv) +int +main (int argc, char **argv) { - int ret; - - char *const argv2[] = { "test-lockmanager-api-servercrash", - "-c", "test_lockmanager_api.conf", -#if VERBOSE - "-L", "DEBUG", -#endif - NULL - }; - - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - - GNUNET_log_setup ("test-lockmanager-api-servercrash", -#if VERBOSE - "DEBUG", -#else - "WARNING", -#endif - NULL); - - ret = - GNUNET_PROGRAM_run ((sizeof (argv2) / sizeof (char *)) - 1, argv2, - "test-lockmanager-api-servercrash", - "nohelp", options, &run, NULL); - - if (GNUNET_OK != ret) - { - LOG (GNUNET_ERROR_TYPE_WARNING, "run failed with error code %d\n", - ret); + if (0 != + GNUNET_TESTING_peer_run ("test_lockmanager_api_servercrash", + "test_lockmanager_api.conf", &run, NULL)) return 1; - } - if (TEST_CLIENT2_SERVER_CRASH_SUCCESS != result) - { - LOG (GNUNET_ERROR_TYPE_WARNING, "test failed\n"); - return 1; - } - LOG (GNUNET_ERROR_TYPE_INFO, "test OK\n"); - return 0; + return (TEST_CLIENT2_SERVER_CRASH_SUCCESS != result) ? 1 : 0; } + +/* end of test_lockmanager_api_servercrash.c */ diff --git a/src/mesh/Makefile.am b/src/mesh/Makefile.am index ac38b0d..7d9a4da 100644 --- a/src/mesh/Makefile.am +++ b/src/mesh/Makefile.am @@ -11,53 +11,141 @@ endif pkgcfgdir= $(pkgdatadir)/config.d/ +libexecdir= $(pkglibdir)/libexec/ + pkgcfg_DATA = \ mesh.conf +plugindir = $(libdir)/gnunet + AM_CLFAGS = -g +libexec_PROGRAMS = \ + gnunet-service-mesh gnunet-service-mesh-new + bin_PROGRAMS = \ - gnunet-service-mesh + gnunet-mesh lib_LTLIBRARIES = \ libgnunetmesh.la +plugin_LTLIBRARIES = \ + libgnunet_plugin_block_mesh.la + +libgnunet_plugin_block_mesh_la_SOURCES = \ + plugin_block_mesh.c +libgnunet_plugin_block_mesh_la_LIBADD = \ + $(top_builddir)/src/block/libgnunetblock.la \ + $(top_builddir)/src/util/libgnunetutil.la +libgnunet_plugin_block_mesh_la_LDFLAGS = \ + $(GN_PLUGIN_LDFLAGS) +libgnunet_plugin_block_mesh_la_DEPENDENCIES = \ + $(top_builddir)/src/block/libgnunetblock.la \ + $(top_builddir)/src/util/libgnunetutil.la + +libgnunetmesh_la_SOURCES = \ + mesh_api.c mesh_common.c +libgnunetmesh_la_LIBADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(XLIB) \ + $(LTLIBINTL) +libgnunetmesh_la_LDFLAGS = \ + $(GN_LIB_LDFLAGS) $(WINFLAGS) \ + -version-info 2:1:1 + gnunet_service_mesh_SOURCES = \ gnunet-service-mesh.c \ - mesh_tunnel_tree.c mesh_tunnel_tree.h + mesh_tunnel_tree.c mesh_tunnel_tree.h \ + mesh_common.c +gnunet_service_mesh_CFLAGS = $(AM_CFLAGS) gnunet_service_mesh_LDADD = \ - $(top_builddir)/src/core/libgnunetcore.la\ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/core/libgnunetcore.la \ $(top_builddir)/src/dht/libgnunetdht.la \ - $(top_builddir)/src/util/libgnunetutil.la - gnunet_service_mesh_DEPENDENCIES = \ - $(top_builddir)/src/core/libgnunetcore.la\ + $(top_builddir)/src/statistics/libgnunetstatistics.la \ + $(top_builddir)/src/block/libgnunetblock.la \ + $(top_builddir)/src/regex/libgnunetregex.la +gnunet_service_mesh_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/core/libgnunetcore.la \ $(top_builddir)/src/dht/libgnunetdht.la \ + $(top_builddir)/src/statistics/libgnunetstatistics.la \ + $(top_builddir)/src/block/libgnunetblock.la \ + $(top_builddir)/src/regex/libgnunetregex.la +if LINUX +gnunet_service_mesh_LDFLAGS = -lrt +endif + +gnunet_mesh_SOURCES = \ + gnunet-mesh.c +gnunet_mesh_LDADD = \ + $(top_builddir)/src/mesh/libgnunetmesh.la \ $(top_builddir)/src/util/libgnunetutil.la +gnunet_mesh_DEPENDENCIES = \ + libgnunetmesh.la -libgnunetmesh_la_SOURCES = \ - mesh_api.c mesh.h mesh_protocol.h -libgnunetmesh_la_LIBADD = \ +gnunet_service_mesh_new_SOURCES = \ + gnunet-service-mesh-new.c \ + mesh_tunnel_tree.c \ + mesh_common.c +gnunet_service_mesh_new_CFLAGS = $(AM_CFLAGS) +gnunet_service_mesh_new_LDADD = \ $(top_builddir)/src/util/libgnunetutil.la \ - $(XLIB) -libgnunetmesh_la_LDFLAGS = \ - $(GN_LIB_LDFLAGS) $(WINFLAGS) \ - -version-info 1:0:0 + $(top_builddir)/src/core/libgnunetcore.la \ + $(top_builddir)/src/dht/libgnunetdht.la \ + $(top_builddir)/src/statistics/libgnunetstatistics.la \ + $(top_builddir)/src/block/libgnunetblock.la \ + $(top_builddir)/src/regex/libgnunetregex.la +gnunet_service_mesh_new_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/core/libgnunetcore.la \ + $(top_builddir)/src/dht/libgnunetdht.la \ + $(top_builddir)/src/statistics/libgnunetstatistics.la \ + $(top_builddir)/src/block/libgnunetblock.la \ + $(top_builddir)/src/regex/libgnunetregex.la +if LINUX +gnunet_service_mesh_new_LDFLAGS = -lrt +endif + + +noinst_LIBRARIES = libgnunetmeshtest.a + +libgnunetmeshtest_a_SOURCES = \ + mesh_test_lib.c mesh_test_lib.h +libgnunetmeshtest_a_LIBADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la \ + $(top_builddir)/src/mesh/libgnunetmesh.la +libgnunetmeshtest_a_DEPENDENCIES = \ + libgnunetmesh.la + check_PROGRAMS = \ test_mesh_api \ test_mesh_tree_api \ test_mesh_local_1 \ test_mesh_local_2 \ + test_mesh_local_traffic_fwd \ + test_mesh_local_traffic_bck \ + test_mesh_local_traffic_both \ test_mesh_2dtorus \ + test_mesh_regex \ test_mesh_small_unicast \ test_mesh_small_multicast \ + test_mesh_small_signal \ test_mesh_small_speed \ + test_mesh_small_speed_nobuf \ + test_mesh_small_speed_min \ + test_mesh_small_speed_backwards \ + test_mesh_small_speed_nobuf_backwards \ + test_mesh_small_speed_min_backwards \ test_mesh_small_speed_ack test_mesh_api_SOURCES = \ test_mesh_api.c test_mesh_api_LDADD = \ $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/mesh/libgnunetmesh.la test_mesh_api_DEPENDENCIES = \ libgnunetmesh.la \ @@ -67,7 +155,7 @@ test_mesh_tree_api_SOURCES = \ test_mesh_tree_api.c test_mesh_tree_api_LDADD = \ $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/dht/libgnunetdht.la + $(top_builddir)/src/dht/libgnunetdht.la test_mesh_tree_api_DEPENDENCIES = \ libgnunetmesh.la \ $(top_builddir)/src/dht/libgnunetdht.la @@ -76,6 +164,7 @@ test_mesh_local_1_SOURCES = \ test_mesh_local_1.c test_mesh_local_1_LDADD = \ $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/mesh/libgnunetmesh.la test_mesh_local_1_DEPENDENCIES = \ libgnunetmesh.la @@ -84,59 +173,129 @@ test_mesh_local_2_SOURCES = \ test_mesh_local_2.c test_mesh_local_2_LDADD = \ $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/mesh/libgnunetmesh.la test_mesh_local_2_DEPENDENCIES = \ libgnunetmesh.la +test_mesh_local_traffic_fwd_SOURCES = \ + test_mesh_local_traffic.c +test_mesh_local_traffic_fwd_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/mesh/libgnunetmesh.la +test_mesh_local_traffic_fwd_DEPENDENCIES = \ + libgnunetmesh.la + +test_mesh_local_traffic_bck_SOURCES = \ + test_mesh_local_traffic.c +test_mesh_local_traffic_bck_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/mesh/libgnunetmesh.la +test_mesh_local_traffic_bck_DEPENDENCIES = \ + libgnunetmesh.la + +test_mesh_local_traffic_both_SOURCES = \ + test_mesh_local_traffic.c +test_mesh_local_traffic_both_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/mesh/libgnunetmesh.la +test_mesh_local_traffic_both_DEPENDENCIES = \ + libgnunetmesh.la + + +ld_mesh_test_lib = \ + $(top_builddir)/src/mesh/libgnunetmeshtest.a \ + $(top_builddir)/src/mesh/libgnunetmesh.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la \ + $(top_builddir)/src/util/libgnunetutil.la + +dep_mesh_test_lib = \ + libgnunetmeshtest.a \ + libgnunetmesh.la + test_mesh_2dtorus_SOURCES = \ test_mesh_2dtorus.c -test_mesh_2dtorus_LDADD = \ - $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/testing/libgnunettesting.la +test_mesh_2dtorus_LDADD = $(ld_mesh_test_lib) +test_mesh_2dtorus_DEPENDENCIES = $(dep_mesh_test_lib) + +test_mesh_regex_SOURCES = \ + test_mesh_regex.c +test_mesh_regex_LDADD = $(ld_mesh_test_lib) +test_mesh_regex_DEPENDENCIES = $(dep_mesh_test_lib) test_mesh_small_unicast_SOURCES = \ test_mesh_small.c -test_mesh_small_unicast_LDADD = \ - $(top_builddir)/src/mesh/libgnunetmesh.la \ - $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/testing/libgnunettesting.la -test_mesh_small_unicast_DEPENDENCIES = \ - libgnunetmesh.la +test_mesh_small_unicast_LDADD = $(ld_mesh_test_lib) +test_mesh_small_unicast_DEPENDENCIES = $(dep_mesh_test_lib) test_mesh_small_multicast_SOURCES = \ test_mesh_small.c -test_mesh_small_multicast_LDADD = \ - $(top_builddir)/src/mesh/libgnunetmesh.la \ - $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/testing/libgnunettesting.la -test_mesh_small_multicast_DEPENDENCIES = \ - libgnunetmesh.la +test_mesh_small_multicast_LDADD = $(ld_mesh_test_lib) +test_mesh_small_multicast_DEPENDENCIES = $(dep_mesh_test_lib) -test_mesh_small_speed_SOURCES = \ +test_mesh_small_signal_SOURCES = \ test_mesh_small.c -test_mesh_small_speed_LDADD = \ - $(top_builddir)/src/mesh/libgnunetmesh.la \ - $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/testing/libgnunettesting.la -test_mesh_small_speed_DEPENDENCIES = \ - libgnunetmesh.la +test_mesh_small_signal_LDADD = $(ld_mesh_test_lib) +test_mesh_small_signal_DEPENDENCIES = $(dep_mesh_test_lib) test_mesh_small_speed_ack_SOURCES = \ test_mesh_small.c -test_mesh_small_speed_ack_LDADD = \ - $(top_builddir)/src/mesh/libgnunetmesh.la \ - $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/testing/libgnunettesting.la -test_mesh_small_speed_ack_DEPENDENCIES = \ - libgnunetmesh.la +test_mesh_small_speed_ack_LDADD = $(ld_mesh_test_lib) +test_mesh_small_speed_ack_DEPENDENCIES = $(dep_mesh_test_lib) + +test_mesh_small_speed_SOURCES = \ + test_mesh_small.c +test_mesh_small_speed_LDADD = $(ld_mesh_test_lib) +test_mesh_small_speed_DEPENDENCIES = $(dep_mesh_test_lib) + +test_mesh_small_speed_min_SOURCES = \ + test_mesh_small.c +test_mesh_small_speed_min_LDADD = $(ld_mesh_test_lib) +test_mesh_small_speed_min_DEPENDENCIES = $(dep_mesh_test_lib) + +test_mesh_small_speed_nobuf_SOURCES = \ + test_mesh_small.c +test_mesh_small_speed_nobuf_LDADD = $(ld_mesh_test_lib) +test_mesh_small_speed_nobuf_DEPENDENCIES = $(dep_mesh_test_lib) + +test_mesh_small_speed_backwards_SOURCES = \ + test_mesh_small.c +test_mesh_small_speed_backwards_LDADD = $(ld_mesh_test_lib) +test_mesh_small_speed_backwards_DEPENDENCIES = $(dep_mesh_test_lib) + +test_mesh_small_speed_min_backwards_SOURCES = \ + test_mesh_small.c +test_mesh_small_speed_min_backwards_LDADD = $(ld_mesh_test_lib) +test_mesh_small_speed_min_backwards_DEPENDENCIES = $(dep_mesh_test_lib) + +test_mesh_small_speed_nobuf_backwards_SOURCES = \ + test_mesh_small.c +test_mesh_small_speed_nobuf_backwards_LDADD = $(ld_mesh_test_lib) +test_mesh_small_speed_nobuf_backwards_DEPENDENCIES = $(dep_mesh_test_lib) + if ENABLE_TEST_RUN -TESTS = test_mesh_api test_mesh_tree_api test_mesh_local_1 test_mesh_local_2 \ - test_mesh_2dtorus test_mesh_small_unicast test_mesh_small_multicast +TESTS = test_mesh_api \ + test_mesh_tree_api \ + test_mesh_local_1 test_mesh_local_2 \ + test_mesh_local_traffic_fwd \ + test_mesh_local_traffic_bck \ + test_mesh_local_traffic_both \ + test_mesh_2dtorus test_mesh_regex \ + test_mesh_small_unicast test_mesh_small_multicast \ + test_mesh_small_signal \ + test_mesh_small_speed \ + test_mesh_small_speed_min \ + test_mesh_small_speed_nobuf \ + test_mesh_small_speed_backwards \ + test_mesh_small_speed_min_backwards endif EXTRA_DIST = \ + mesh.h mesh_protocol.h \ test_mesh.conf \ test_mesh_2dtorus.conf \ - test_mesh_small.conf \ - test_mesh_path.conf + test_mesh_small.conf diff --git a/src/mesh/Makefile.in b/src/mesh/Makefile.in index 1504c4b..4c55099 100644 --- a/src/mesh/Makefile.in +++ b/src/mesh/Makefile.in @@ -1,9 +1,9 @@ -# Makefile.in generated by automake 1.11.1 from Makefile.am. +# Makefile.in generated by automake 1.11.6 from Makefile.am. # @configure_input@ # Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, -# 2003, 2004, 2005, 2006, 2007, 2008, 2009 Free Software Foundation, -# Inc. +# 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Free Software +# Foundation, Inc. # This Makefile.in is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. @@ -17,7 +17,25 @@ + VPATH = @srcdir@ +am__make_dryrun = \ + { \ + am__dry=no; \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + echo 'am--echo: ; @echo "AM" OK' | $(MAKE) -f - 2>/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } pkgdatadir = $(datadir)/@PACKAGE@ pkgincludedir = $(includedir)/@PACKAGE@ pkglibdir = $(libdir)/@PACKAGE@ @@ -37,34 +55,56 @@ POST_UNINSTALL = : build_triplet = @build@ host_triplet = @host@ target_triplet = @target@ -bin_PROGRAMS = gnunet-service-mesh$(EXEEXT) +libexec_PROGRAMS = gnunet-service-mesh$(EXEEXT) \ + gnunet-service-mesh-new$(EXEEXT) +bin_PROGRAMS = gnunet-mesh$(EXEEXT) check_PROGRAMS = test_mesh_api$(EXEEXT) test_mesh_tree_api$(EXEEXT) \ test_mesh_local_1$(EXEEXT) test_mesh_local_2$(EXEEXT) \ - test_mesh_2dtorus$(EXEEXT) test_mesh_small_unicast$(EXEEXT) \ + test_mesh_local_traffic_fwd$(EXEEXT) \ + test_mesh_local_traffic_bck$(EXEEXT) \ + test_mesh_local_traffic_both$(EXEEXT) \ + test_mesh_2dtorus$(EXEEXT) test_mesh_regex$(EXEEXT) \ + test_mesh_small_unicast$(EXEEXT) \ test_mesh_small_multicast$(EXEEXT) \ - test_mesh_small_speed$(EXEEXT) \ + test_mesh_small_signal$(EXEEXT) test_mesh_small_speed$(EXEEXT) \ + test_mesh_small_speed_nobuf$(EXEEXT) \ + test_mesh_small_speed_min$(EXEEXT) \ + test_mesh_small_speed_backwards$(EXEEXT) \ + test_mesh_small_speed_nobuf_backwards$(EXEEXT) \ + test_mesh_small_speed_min_backwards$(EXEEXT) \ test_mesh_small_speed_ack$(EXEEXT) @ENABLE_TEST_RUN_TRUE@TESTS = test_mesh_api$(EXEEXT) \ @ENABLE_TEST_RUN_TRUE@ test_mesh_tree_api$(EXEEXT) \ @ENABLE_TEST_RUN_TRUE@ test_mesh_local_1$(EXEEXT) \ @ENABLE_TEST_RUN_TRUE@ test_mesh_local_2$(EXEEXT) \ +@ENABLE_TEST_RUN_TRUE@ test_mesh_local_traffic_fwd$(EXEEXT) \ +@ENABLE_TEST_RUN_TRUE@ test_mesh_local_traffic_bck$(EXEEXT) \ +@ENABLE_TEST_RUN_TRUE@ test_mesh_local_traffic_both$(EXEEXT) \ @ENABLE_TEST_RUN_TRUE@ test_mesh_2dtorus$(EXEEXT) \ +@ENABLE_TEST_RUN_TRUE@ test_mesh_regex$(EXEEXT) \ @ENABLE_TEST_RUN_TRUE@ test_mesh_small_unicast$(EXEEXT) \ -@ENABLE_TEST_RUN_TRUE@ test_mesh_small_multicast$(EXEEXT) +@ENABLE_TEST_RUN_TRUE@ test_mesh_small_multicast$(EXEEXT) \ +@ENABLE_TEST_RUN_TRUE@ test_mesh_small_signal$(EXEEXT) \ +@ENABLE_TEST_RUN_TRUE@ test_mesh_small_speed$(EXEEXT) \ +@ENABLE_TEST_RUN_TRUE@ test_mesh_small_speed_min$(EXEEXT) \ +@ENABLE_TEST_RUN_TRUE@ test_mesh_small_speed_nobuf$(EXEEXT) \ +@ENABLE_TEST_RUN_TRUE@ test_mesh_small_speed_backwards$(EXEEXT) \ +@ENABLE_TEST_RUN_TRUE@ test_mesh_small_speed_min_backwards$(EXEEXT) subdir = src/mesh DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in \ $(srcdir)/mesh.conf.in ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 am__aclocal_m4_deps = $(top_srcdir)/m4/absolute-header.m4 \ $(top_srcdir)/m4/align.m4 $(top_srcdir)/m4/argz.m4 \ - $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/iconv.m4 \ - $(top_srcdir)/m4/lib-ld.m4 $(top_srcdir)/m4/lib-link.m4 \ - $(top_srcdir)/m4/lib-prefix.m4 $(top_srcdir)/m4/libcurl.m4 \ - $(top_srcdir)/m4/libgcrypt.m4 $(top_srcdir)/m4/libtool.m4 \ - $(top_srcdir)/m4/libunistring.m4 $(top_srcdir)/m4/ltdl.m4 \ - $(top_srcdir)/m4/ltoptions.m4 $(top_srcdir)/m4/ltsugar.m4 \ - $(top_srcdir)/m4/ltversion.m4 $(top_srcdir)/m4/lt~obsolete.m4 \ - $(top_srcdir)/m4/nls.m4 $(top_srcdir)/m4/po.m4 \ + $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/glib-2.0.m4 \ + $(top_srcdir)/m4/iconv.m4 $(top_srcdir)/m4/lib-ld.m4 \ + $(top_srcdir)/m4/lib-link.m4 $(top_srcdir)/m4/lib-prefix.m4 \ + $(top_srcdir)/m4/libcurl.m4 $(top_srcdir)/m4/libgcrypt.m4 \ + $(top_srcdir)/m4/libtool.m4 $(top_srcdir)/m4/libunistring.m4 \ + $(top_srcdir)/m4/ltdl.m4 $(top_srcdir)/m4/ltoptions.m4 \ + $(top_srcdir)/m4/ltsugar.m4 $(top_srcdir)/m4/ltversion.m4 \ + $(top_srcdir)/m4/lt~obsolete.m4 $(top_srcdir)/m4/nls.m4 \ + $(top_srcdir)/m4/pkg.m4 $(top_srcdir)/m4/po.m4 \ $(top_srcdir)/m4/progtest.m4 $(top_srcdir)/acinclude.m4 \ $(top_srcdir)/configure.ac am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ @@ -73,6 +113,17 @@ mkinstalldirs = $(install_sh) -d CONFIG_HEADER = $(top_builddir)/gnunet_config.h CONFIG_CLEAN_FILES = mesh.conf CONFIG_CLEAN_VPATH_FILES = +LIBRARIES = $(noinst_LIBRARIES) +ARFLAGS = cru +AM_V_AR = $(am__v_AR_@AM_V@) +am__v_AR_ = $(am__v_AR_@AM_DEFAULT_V@) +am__v_AR_0 = @echo " AR " $@; +AM_V_at = $(am__v_at_@AM_V@) +am__v_at_ = $(am__v_at_@AM_DEFAULT_V@) +am__v_at_0 = @ +libgnunetmeshtest_a_AR = $(AR) $(ARFLAGS) +am_libgnunetmeshtest_a_OBJECTS = mesh_test_lib.$(OBJEXT) +libgnunetmeshtest_a_OBJECTS = $(am_libgnunetmeshtest_a_OBJECTS) am__vpath_adj_setup = srcdirstrip=`echo "$(srcdir)" | sed 's|.|.|g'`; am__vpath_adj = case $$p in \ $(srcdir)/*) f=`echo "$$p" | sed "s|^$$srcdirstrip/||"`;; \ @@ -94,45 +145,108 @@ am__nobase_list = $(am__nobase_strip_setup); \ am__base_list = \ sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \ sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g' -am__installdirs = "$(DESTDIR)$(libdir)" "$(DESTDIR)$(bindir)" \ +am__uninstall_files_from_dir = { \ + test -z "$$files" \ + || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \ + || { echo " ( cd '$$dir' && rm -f" $$files ")"; \ + $(am__cd) "$$dir" && rm -f $$files; }; \ + } +am__installdirs = "$(DESTDIR)$(libdir)" "$(DESTDIR)$(plugindir)" \ + "$(DESTDIR)$(bindir)" "$(DESTDIR)$(libexecdir)" \ "$(DESTDIR)$(pkgcfgdir)" -LTLIBRARIES = $(lib_LTLIBRARIES) +LTLIBRARIES = $(lib_LTLIBRARIES) $(plugin_LTLIBRARIES) +am_libgnunet_plugin_block_mesh_la_OBJECTS = plugin_block_mesh.lo +libgnunet_plugin_block_mesh_la_OBJECTS = \ + $(am_libgnunet_plugin_block_mesh_la_OBJECTS) +AM_V_lt = $(am__v_lt_@AM_V@) +am__v_lt_ = $(am__v_lt_@AM_DEFAULT_V@) +am__v_lt_0 = --silent +libgnunet_plugin_block_mesh_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ + $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ + $(AM_CFLAGS) $(CFLAGS) \ + $(libgnunet_plugin_block_mesh_la_LDFLAGS) $(LDFLAGS) -o $@ am__DEPENDENCIES_1 = libgnunetmesh_la_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la \ - $(am__DEPENDENCIES_1) -am_libgnunetmesh_la_OBJECTS = mesh_api.lo + $(am__DEPENDENCIES_1) $(am__DEPENDENCIES_1) +am_libgnunetmesh_la_OBJECTS = mesh_api.lo mesh_common.lo libgnunetmesh_la_OBJECTS = $(am_libgnunetmesh_la_OBJECTS) -AM_V_lt = $(am__v_lt_$(V)) -am__v_lt_ = $(am__v_lt_$(AM_DEFAULT_VERBOSITY)) -am__v_lt_0 = --silent libgnunetmesh_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ $(AM_CFLAGS) $(CFLAGS) $(libgnunetmesh_la_LDFLAGS) $(LDFLAGS) \ -o $@ -PROGRAMS = $(bin_PROGRAMS) -am_gnunet_service_mesh_OBJECTS = gnunet-service-mesh.$(OBJEXT) \ - mesh_tunnel_tree.$(OBJEXT) +PROGRAMS = $(bin_PROGRAMS) $(libexec_PROGRAMS) +am_gnunet_mesh_OBJECTS = gnunet-mesh.$(OBJEXT) +gnunet_mesh_OBJECTS = $(am_gnunet_mesh_OBJECTS) +am_gnunet_service_mesh_OBJECTS = \ + gnunet_service_mesh-gnunet-service-mesh.$(OBJEXT) \ + gnunet_service_mesh-mesh_tunnel_tree.$(OBJEXT) \ + gnunet_service_mesh-mesh_common.$(OBJEXT) gnunet_service_mesh_OBJECTS = $(am_gnunet_service_mesh_OBJECTS) +gnunet_service_mesh_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ + $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ + $(gnunet_service_mesh_CFLAGS) $(CFLAGS) \ + $(gnunet_service_mesh_LDFLAGS) $(LDFLAGS) -o $@ +am_gnunet_service_mesh_new_OBJECTS = \ + gnunet_service_mesh_new-gnunet-service-mesh-new.$(OBJEXT) \ + gnunet_service_mesh_new-mesh_tunnel_tree.$(OBJEXT) \ + gnunet_service_mesh_new-mesh_common.$(OBJEXT) +gnunet_service_mesh_new_OBJECTS = \ + $(am_gnunet_service_mesh_new_OBJECTS) +gnunet_service_mesh_new_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ + $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ + $(gnunet_service_mesh_new_CFLAGS) $(CFLAGS) \ + $(gnunet_service_mesh_new_LDFLAGS) $(LDFLAGS) -o $@ am_test_mesh_2dtorus_OBJECTS = test_mesh_2dtorus.$(OBJEXT) test_mesh_2dtorus_OBJECTS = $(am_test_mesh_2dtorus_OBJECTS) -test_mesh_2dtorus_DEPENDENCIES = \ - $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/testing/libgnunettesting.la am_test_mesh_api_OBJECTS = test_mesh_api.$(OBJEXT) test_mesh_api_OBJECTS = $(am_test_mesh_api_OBJECTS) am_test_mesh_local_1_OBJECTS = test_mesh_local_1.$(OBJEXT) test_mesh_local_1_OBJECTS = $(am_test_mesh_local_1_OBJECTS) am_test_mesh_local_2_OBJECTS = test_mesh_local_2.$(OBJEXT) test_mesh_local_2_OBJECTS = $(am_test_mesh_local_2_OBJECTS) +am_test_mesh_local_traffic_bck_OBJECTS = \ + test_mesh_local_traffic.$(OBJEXT) +test_mesh_local_traffic_bck_OBJECTS = \ + $(am_test_mesh_local_traffic_bck_OBJECTS) +am_test_mesh_local_traffic_both_OBJECTS = \ + test_mesh_local_traffic.$(OBJEXT) +test_mesh_local_traffic_both_OBJECTS = \ + $(am_test_mesh_local_traffic_both_OBJECTS) +am_test_mesh_local_traffic_fwd_OBJECTS = \ + test_mesh_local_traffic.$(OBJEXT) +test_mesh_local_traffic_fwd_OBJECTS = \ + $(am_test_mesh_local_traffic_fwd_OBJECTS) +am_test_mesh_regex_OBJECTS = test_mesh_regex.$(OBJEXT) +test_mesh_regex_OBJECTS = $(am_test_mesh_regex_OBJECTS) am_test_mesh_small_multicast_OBJECTS = test_mesh_small.$(OBJEXT) test_mesh_small_multicast_OBJECTS = \ $(am_test_mesh_small_multicast_OBJECTS) +am_test_mesh_small_signal_OBJECTS = test_mesh_small.$(OBJEXT) +test_mesh_small_signal_OBJECTS = $(am_test_mesh_small_signal_OBJECTS) am_test_mesh_small_speed_OBJECTS = test_mesh_small.$(OBJEXT) test_mesh_small_speed_OBJECTS = $(am_test_mesh_small_speed_OBJECTS) am_test_mesh_small_speed_ack_OBJECTS = test_mesh_small.$(OBJEXT) test_mesh_small_speed_ack_OBJECTS = \ $(am_test_mesh_small_speed_ack_OBJECTS) +am_test_mesh_small_speed_backwards_OBJECTS = \ + test_mesh_small.$(OBJEXT) +test_mesh_small_speed_backwards_OBJECTS = \ + $(am_test_mesh_small_speed_backwards_OBJECTS) +am_test_mesh_small_speed_min_OBJECTS = test_mesh_small.$(OBJEXT) +test_mesh_small_speed_min_OBJECTS = \ + $(am_test_mesh_small_speed_min_OBJECTS) +am_test_mesh_small_speed_min_backwards_OBJECTS = \ + test_mesh_small.$(OBJEXT) +test_mesh_small_speed_min_backwards_OBJECTS = \ + $(am_test_mesh_small_speed_min_backwards_OBJECTS) +am_test_mesh_small_speed_nobuf_OBJECTS = test_mesh_small.$(OBJEXT) +test_mesh_small_speed_nobuf_OBJECTS = \ + $(am_test_mesh_small_speed_nobuf_OBJECTS) +am_test_mesh_small_speed_nobuf_backwards_OBJECTS = \ + test_mesh_small.$(OBJEXT) +test_mesh_small_speed_nobuf_backwards_OBJECTS = \ + $(am_test_mesh_small_speed_nobuf_backwards_OBJECTS) am_test_mesh_small_unicast_OBJECTS = test_mesh_small.$(OBJEXT) test_mesh_small_unicast_OBJECTS = \ $(am_test_mesh_small_unicast_OBJECTS) @@ -148,39 +262,68 @@ LTCOMPILE = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) \ $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) \ $(AM_CFLAGS) $(CFLAGS) -AM_V_CC = $(am__v_CC_$(V)) -am__v_CC_ = $(am__v_CC_$(AM_DEFAULT_VERBOSITY)) +AM_V_CC = $(am__v_CC_@AM_V@) +am__v_CC_ = $(am__v_CC_@AM_DEFAULT_V@) am__v_CC_0 = @echo " CC " $@; -AM_V_at = $(am__v_at_$(V)) -am__v_at_ = $(am__v_at_$(AM_DEFAULT_VERBOSITY)) -am__v_at_0 = @ CCLD = $(CC) LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ $(AM_LDFLAGS) $(LDFLAGS) -o $@ -AM_V_CCLD = $(am__v_CCLD_$(V)) -am__v_CCLD_ = $(am__v_CCLD_$(AM_DEFAULT_VERBOSITY)) +AM_V_CCLD = $(am__v_CCLD_@AM_V@) +am__v_CCLD_ = $(am__v_CCLD_@AM_DEFAULT_V@) am__v_CCLD_0 = @echo " CCLD " $@; -AM_V_GEN = $(am__v_GEN_$(V)) -am__v_GEN_ = $(am__v_GEN_$(AM_DEFAULT_VERBOSITY)) +AM_V_GEN = $(am__v_GEN_@AM_V@) +am__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@) am__v_GEN_0 = @echo " GEN " $@; -SOURCES = $(libgnunetmesh_la_SOURCES) $(gnunet_service_mesh_SOURCES) \ +SOURCES = $(libgnunetmeshtest_a_SOURCES) \ + $(libgnunet_plugin_block_mesh_la_SOURCES) \ + $(libgnunetmesh_la_SOURCES) $(gnunet_mesh_SOURCES) \ + $(gnunet_service_mesh_SOURCES) \ + $(gnunet_service_mesh_new_SOURCES) \ $(test_mesh_2dtorus_SOURCES) $(test_mesh_api_SOURCES) \ $(test_mesh_local_1_SOURCES) $(test_mesh_local_2_SOURCES) \ + $(test_mesh_local_traffic_bck_SOURCES) \ + $(test_mesh_local_traffic_both_SOURCES) \ + $(test_mesh_local_traffic_fwd_SOURCES) \ + $(test_mesh_regex_SOURCES) \ $(test_mesh_small_multicast_SOURCES) \ + $(test_mesh_small_signal_SOURCES) \ $(test_mesh_small_speed_SOURCES) \ $(test_mesh_small_speed_ack_SOURCES) \ + $(test_mesh_small_speed_backwards_SOURCES) \ + $(test_mesh_small_speed_min_SOURCES) \ + $(test_mesh_small_speed_min_backwards_SOURCES) \ + $(test_mesh_small_speed_nobuf_SOURCES) \ + $(test_mesh_small_speed_nobuf_backwards_SOURCES) \ $(test_mesh_small_unicast_SOURCES) \ $(test_mesh_tree_api_SOURCES) -DIST_SOURCES = $(libgnunetmesh_la_SOURCES) \ - $(gnunet_service_mesh_SOURCES) $(test_mesh_2dtorus_SOURCES) \ - $(test_mesh_api_SOURCES) $(test_mesh_local_1_SOURCES) \ - $(test_mesh_local_2_SOURCES) \ +DIST_SOURCES = $(libgnunetmeshtest_a_SOURCES) \ + $(libgnunet_plugin_block_mesh_la_SOURCES) \ + $(libgnunetmesh_la_SOURCES) $(gnunet_mesh_SOURCES) \ + $(gnunet_service_mesh_SOURCES) \ + $(gnunet_service_mesh_new_SOURCES) \ + $(test_mesh_2dtorus_SOURCES) $(test_mesh_api_SOURCES) \ + $(test_mesh_local_1_SOURCES) $(test_mesh_local_2_SOURCES) \ + $(test_mesh_local_traffic_bck_SOURCES) \ + $(test_mesh_local_traffic_both_SOURCES) \ + $(test_mesh_local_traffic_fwd_SOURCES) \ + $(test_mesh_regex_SOURCES) \ $(test_mesh_small_multicast_SOURCES) \ + $(test_mesh_small_signal_SOURCES) \ $(test_mesh_small_speed_SOURCES) \ $(test_mesh_small_speed_ack_SOURCES) \ + $(test_mesh_small_speed_backwards_SOURCES) \ + $(test_mesh_small_speed_min_SOURCES) \ + $(test_mesh_small_speed_min_backwards_SOURCES) \ + $(test_mesh_small_speed_nobuf_SOURCES) \ + $(test_mesh_small_speed_nobuf_backwards_SOURCES) \ $(test_mesh_small_unicast_SOURCES) \ $(test_mesh_tree_api_SOURCES) +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac DATA = $(pkgcfg_DATA) ETAGS = etags CTAGS = ctags @@ -222,6 +365,10 @@ EXEEXT = @EXEEXT@ EXT_LIBS = @EXT_LIBS@ EXT_LIB_PATH = @EXT_LIB_PATH@ FGREP = @FGREP@ +GLIB_CFLAGS = @GLIB_CFLAGS@ +GLIB_GENMARSHAL = @GLIB_GENMARSHAL@ +GLIB_LIBS = @GLIB_LIBS@ +GLIB_MKENUMS = @GLIB_MKENUMS@ GMSGFMT = @GMSGFMT@ GMSGFMT_015 = @GMSGFMT_015@ GNUNETDNS_GROUP = @GNUNETDNS_GROUP@ @@ -232,6 +379,7 @@ GN_LIBINTL = @GN_LIBINTL@ GN_LIB_LDFLAGS = @GN_LIB_LDFLAGS@ GN_PLUGIN_LDFLAGS = @GN_PLUGIN_LDFLAGS@ GN_USER_HOME_DIR = @GN_USER_HOME_DIR@ +GOBJECT_QUERY = @GOBJECT_QUERY@ GREP = @GREP@ HAVE_LIBUNISTRING = @HAVE_LIBUNISTRING@ INCLTDL = @INCLTDL@ @@ -254,6 +402,8 @@ LIBCURL_CPPFLAGS = @LIBCURL_CPPFLAGS@ LIBGCRYPT_CFLAGS = @LIBGCRYPT_CFLAGS@ LIBGCRYPT_CONFIG = @LIBGCRYPT_CONFIG@ LIBGCRYPT_LIBS = @LIBGCRYPT_LIBS@ +LIBGTOP_CFLAGS = @LIBGTOP_CFLAGS@ +LIBGTOP_LIBS = @LIBGTOP_LIBS@ LIBICONV = @LIBICONV@ LIBINTL = @LIBINTL@ LIBLTDL = @LIBLTDL@ @@ -275,6 +425,7 @@ LT_CONFIG_H = @LT_CONFIG_H@ LT_DLLOADERS = @LT_DLLOADERS@ LT_DLPREOPEN = @LT_DLPREOPEN@ MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ MKDIR_P = @MKDIR_P@ MONKEYPREFIX = @MONKEYPREFIX@ MSGFMT = @MSGFMT@ @@ -284,6 +435,7 @@ MYSQL_CPPFLAGS = @MYSQL_CPPFLAGS@ MYSQL_LDFLAGS = @MYSQL_LDFLAGS@ NM = @NM@ NMEDIT = @NMEDIT@ +NSS_DIR = @NSS_DIR@ OBJC = @OBJC@ OBJCDEPMODE = @OBJCDEPMODE@ OBJCFLAGS = @OBJCFLAGS@ @@ -299,6 +451,7 @@ PACKAGE_TARNAME = @PACKAGE_TARNAME@ PACKAGE_URL = @PACKAGE_URL@ PACKAGE_VERSION = @PACKAGE_VERSION@ PATH_SEPARATOR = @PATH_SEPARATOR@ +PKG_CONFIG = @PKG_CONFIG@ POSTGRES_CPPFLAGS = @POSTGRES_CPPFLAGS@ POSTGRES_LDFLAGS = @POSTGRES_LDFLAGS@ POSUB = @POSUB@ @@ -330,6 +483,7 @@ abs_builddir = @abs_builddir@ abs_srcdir = @abs_srcdir@ abs_top_builddir = @abs_top_builddir@ abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ ac_ct_CC = @ac_ct_CC@ ac_ct_CXX = @ac_ct_CXX@ ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ @@ -352,6 +506,7 @@ datarootdir = @datarootdir@ docdir = @docdir@ dvidir = @dvidir@ exec_prefix = @exec_prefix@ +gitcommand = @gitcommand@ host = @host@ host_alias = @host_alias@ host_cpu = @host_cpu@ @@ -362,10 +517,9 @@ includedir = @includedir@ infodir = @infodir@ install_sh = @install_sh@ libdir = @libdir@ -libexecdir = @libexecdir@ +libexecdir = $(pkglibdir)/libexec/ localedir = @localedir@ localstatedir = @localstatedir@ -lt_ECHO = @lt_ECHO@ ltdl_LIBOBJS = @ltdl_LIBOBJS@ ltdl_LTLIBOBJS = @ltdl_LTLIBOBJS@ mandir = @mandir@ @@ -383,6 +537,7 @@ sbindir = @sbindir@ sharedstatedir = @sharedstatedir@ srcdir = @srcdir@ subdirs = @subdirs@ +svnversioncommand = @svnversioncommand@ sys_symbol_underscore = @sys_symbol_underscore@ sysconfdir = @sysconfdir@ target = @target@ @@ -401,40 +556,114 @@ pkgcfgdir = $(pkgdatadir)/config.d/ pkgcfg_DATA = \ mesh.conf +plugindir = $(libdir)/gnunet AM_CLFAGS = -g lib_LTLIBRARIES = \ libgnunetmesh.la +plugin_LTLIBRARIES = \ + libgnunet_plugin_block_mesh.la + +libgnunet_plugin_block_mesh_la_SOURCES = \ + plugin_block_mesh.c + +libgnunet_plugin_block_mesh_la_LIBADD = \ + $(top_builddir)/src/block/libgnunetblock.la \ + $(top_builddir)/src/util/libgnunetutil.la + +libgnunet_plugin_block_mesh_la_LDFLAGS = \ + $(GN_PLUGIN_LDFLAGS) + +libgnunet_plugin_block_mesh_la_DEPENDENCIES = \ + $(top_builddir)/src/block/libgnunetblock.la \ + $(top_builddir)/src/util/libgnunetutil.la + +libgnunetmesh_la_SOURCES = \ + mesh_api.c mesh_common.c + +libgnunetmesh_la_LIBADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(XLIB) \ + $(LTLIBINTL) + +libgnunetmesh_la_LDFLAGS = \ + $(GN_LIB_LDFLAGS) $(WINFLAGS) \ + -version-info 2:1:1 + gnunet_service_mesh_SOURCES = \ gnunet-service-mesh.c \ - mesh_tunnel_tree.c mesh_tunnel_tree.h + mesh_tunnel_tree.c mesh_tunnel_tree.h \ + mesh_common.c +gnunet_service_mesh_CFLAGS = $(AM_CFLAGS) gnunet_service_mesh_LDADD = \ - $(top_builddir)/src/core/libgnunetcore.la\ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/core/libgnunetcore.la \ $(top_builddir)/src/dht/libgnunetdht.la \ - $(top_builddir)/src/util/libgnunetutil.la + $(top_builddir)/src/statistics/libgnunetstatistics.la \ + $(top_builddir)/src/block/libgnunetblock.la \ + $(top_builddir)/src/regex/libgnunetregex.la gnunet_service_mesh_DEPENDENCIES = \ - $(top_builddir)/src/core/libgnunetcore.la\ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/core/libgnunetcore.la \ $(top_builddir)/src/dht/libgnunetdht.la \ + $(top_builddir)/src/statistics/libgnunetstatistics.la \ + $(top_builddir)/src/block/libgnunetblock.la \ + $(top_builddir)/src/regex/libgnunetregex.la + +@LINUX_TRUE@gnunet_service_mesh_LDFLAGS = -lrt +gnunet_mesh_SOURCES = \ + gnunet-mesh.c + +gnunet_mesh_LDADD = \ + $(top_builddir)/src/mesh/libgnunetmesh.la \ $(top_builddir)/src/util/libgnunetutil.la -libgnunetmesh_la_SOURCES = \ - mesh_api.c mesh.h mesh_protocol.h +gnunet_mesh_DEPENDENCIES = \ + libgnunetmesh.la -libgnunetmesh_la_LIBADD = \ +gnunet_service_mesh_new_SOURCES = \ + gnunet-service-mesh-new.c \ + mesh_tunnel_tree.c \ + mesh_common.c + +gnunet_service_mesh_new_CFLAGS = $(AM_CFLAGS) +gnunet_service_mesh_new_LDADD = \ $(top_builddir)/src/util/libgnunetutil.la \ - $(XLIB) + $(top_builddir)/src/core/libgnunetcore.la \ + $(top_builddir)/src/dht/libgnunetdht.la \ + $(top_builddir)/src/statistics/libgnunetstatistics.la \ + $(top_builddir)/src/block/libgnunetblock.la \ + $(top_builddir)/src/regex/libgnunetregex.la -libgnunetmesh_la_LDFLAGS = \ - $(GN_LIB_LDFLAGS) $(WINFLAGS) \ - -version-info 1:0:0 +gnunet_service_mesh_new_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/core/libgnunetcore.la \ + $(top_builddir)/src/dht/libgnunetdht.la \ + $(top_builddir)/src/statistics/libgnunetstatistics.la \ + $(top_builddir)/src/block/libgnunetblock.la \ + $(top_builddir)/src/regex/libgnunetregex.la + +@LINUX_TRUE@gnunet_service_mesh_new_LDFLAGS = -lrt +noinst_LIBRARIES = libgnunetmeshtest.a +libgnunetmeshtest_a_SOURCES = \ + mesh_test_lib.c mesh_test_lib.h + +libgnunetmeshtest_a_LIBADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la \ + $(top_builddir)/src/mesh/libgnunetmesh.la + +libgnunetmeshtest_a_DEPENDENCIES = \ + libgnunetmesh.la test_mesh_api_SOURCES = \ test_mesh_api.c test_mesh_api_LDADD = \ $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/mesh/libgnunetmesh.la test_mesh_api_DEPENDENCIES = \ @@ -446,7 +675,7 @@ test_mesh_tree_api_SOURCES = \ test_mesh_tree_api_LDADD = \ $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/dht/libgnunetdht.la + $(top_builddir)/src/dht/libgnunetdht.la test_mesh_tree_api_DEPENDENCIES = \ libgnunetmesh.la \ @@ -457,6 +686,7 @@ test_mesh_local_1_SOURCES = \ test_mesh_local_1_LDADD = \ $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/mesh/libgnunetmesh.la test_mesh_local_1_DEPENDENCIES = \ @@ -467,67 +697,120 @@ test_mesh_local_2_SOURCES = \ test_mesh_local_2_LDADD = \ $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/mesh/libgnunetmesh.la test_mesh_local_2_DEPENDENCIES = \ libgnunetmesh.la -test_mesh_2dtorus_SOURCES = \ - test_mesh_2dtorus.c +test_mesh_local_traffic_fwd_SOURCES = \ + test_mesh_local_traffic.c -test_mesh_2dtorus_LDADD = \ - $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/testing/libgnunettesting.la +test_mesh_local_traffic_fwd_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/mesh/libgnunetmesh.la -test_mesh_small_unicast_SOURCES = \ - test_mesh_small.c +test_mesh_local_traffic_fwd_DEPENDENCIES = \ + libgnunetmesh.la -test_mesh_small_unicast_LDADD = \ +test_mesh_local_traffic_bck_SOURCES = \ + test_mesh_local_traffic.c + +test_mesh_local_traffic_bck_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/mesh/libgnunetmesh.la + +test_mesh_local_traffic_bck_DEPENDENCIES = \ + libgnunetmesh.la + +test_mesh_local_traffic_both_SOURCES = \ + test_mesh_local_traffic.c + +test_mesh_local_traffic_both_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/mesh/libgnunetmesh.la + +test_mesh_local_traffic_both_DEPENDENCIES = \ + libgnunetmesh.la + +ld_mesh_test_lib = \ + $(top_builddir)/src/mesh/libgnunetmeshtest.a \ $(top_builddir)/src/mesh/libgnunetmesh.la \ - $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/testing/libgnunettesting.la + $(top_builddir)/src/testbed/libgnunettestbed.la \ + $(top_builddir)/src/util/libgnunetutil.la -test_mesh_small_unicast_DEPENDENCIES = \ +dep_mesh_test_lib = \ + libgnunetmeshtest.a \ libgnunetmesh.la +test_mesh_2dtorus_SOURCES = \ + test_mesh_2dtorus.c + +test_mesh_2dtorus_LDADD = $(ld_mesh_test_lib) +test_mesh_2dtorus_DEPENDENCIES = $(dep_mesh_test_lib) +test_mesh_regex_SOURCES = \ + test_mesh_regex.c + +test_mesh_regex_LDADD = $(ld_mesh_test_lib) +test_mesh_regex_DEPENDENCIES = $(dep_mesh_test_lib) +test_mesh_small_unicast_SOURCES = \ + test_mesh_small.c + +test_mesh_small_unicast_LDADD = $(ld_mesh_test_lib) +test_mesh_small_unicast_DEPENDENCIES = $(dep_mesh_test_lib) test_mesh_small_multicast_SOURCES = \ test_mesh_small.c -test_mesh_small_multicast_LDADD = \ - $(top_builddir)/src/mesh/libgnunetmesh.la \ - $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/testing/libgnunettesting.la +test_mesh_small_multicast_LDADD = $(ld_mesh_test_lib) +test_mesh_small_multicast_DEPENDENCIES = $(dep_mesh_test_lib) +test_mesh_small_signal_SOURCES = \ + test_mesh_small.c -test_mesh_small_multicast_DEPENDENCIES = \ - libgnunetmesh.la +test_mesh_small_signal_LDADD = $(ld_mesh_test_lib) +test_mesh_small_signal_DEPENDENCIES = $(dep_mesh_test_lib) +test_mesh_small_speed_ack_SOURCES = \ + test_mesh_small.c +test_mesh_small_speed_ack_LDADD = $(ld_mesh_test_lib) +test_mesh_small_speed_ack_DEPENDENCIES = $(dep_mesh_test_lib) test_mesh_small_speed_SOURCES = \ test_mesh_small.c -test_mesh_small_speed_LDADD = \ - $(top_builddir)/src/mesh/libgnunetmesh.la \ - $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/testing/libgnunettesting.la +test_mesh_small_speed_LDADD = $(ld_mesh_test_lib) +test_mesh_small_speed_DEPENDENCIES = $(dep_mesh_test_lib) +test_mesh_small_speed_min_SOURCES = \ + test_mesh_small.c -test_mesh_small_speed_DEPENDENCIES = \ - libgnunetmesh.la +test_mesh_small_speed_min_LDADD = $(ld_mesh_test_lib) +test_mesh_small_speed_min_DEPENDENCIES = $(dep_mesh_test_lib) +test_mesh_small_speed_nobuf_SOURCES = \ + test_mesh_small.c -test_mesh_small_speed_ack_SOURCES = \ +test_mesh_small_speed_nobuf_LDADD = $(ld_mesh_test_lib) +test_mesh_small_speed_nobuf_DEPENDENCIES = $(dep_mesh_test_lib) +test_mesh_small_speed_backwards_SOURCES = \ test_mesh_small.c -test_mesh_small_speed_ack_LDADD = \ - $(top_builddir)/src/mesh/libgnunetmesh.la \ - $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/testing/libgnunettesting.la +test_mesh_small_speed_backwards_LDADD = $(ld_mesh_test_lib) +test_mesh_small_speed_backwards_DEPENDENCIES = $(dep_mesh_test_lib) +test_mesh_small_speed_min_backwards_SOURCES = \ + test_mesh_small.c -test_mesh_small_speed_ack_DEPENDENCIES = \ - libgnunetmesh.la +test_mesh_small_speed_min_backwards_LDADD = $(ld_mesh_test_lib) +test_mesh_small_speed_min_backwards_DEPENDENCIES = $(dep_mesh_test_lib) +test_mesh_small_speed_nobuf_backwards_SOURCES = \ + test_mesh_small.c +test_mesh_small_speed_nobuf_backwards_LDADD = $(ld_mesh_test_lib) +test_mesh_small_speed_nobuf_backwards_DEPENDENCIES = $(dep_mesh_test_lib) EXTRA_DIST = \ + mesh.h mesh_protocol.h \ test_mesh.conf \ test_mesh_2dtorus.conf \ - test_mesh_small.conf \ - test_mesh_path.conf + test_mesh_small.conf all: all-am @@ -565,9 +848,15 @@ $(ACLOCAL_M4): $(am__aclocal_m4_deps) $(am__aclocal_m4_deps): mesh.conf: $(top_builddir)/config.status $(srcdir)/mesh.conf.in cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ + +clean-noinstLIBRARIES: + -test -z "$(noinst_LIBRARIES)" || rm -f $(noinst_LIBRARIES) +libgnunetmeshtest.a: $(libgnunetmeshtest_a_OBJECTS) $(libgnunetmeshtest_a_DEPENDENCIES) $(EXTRA_libgnunetmeshtest_a_DEPENDENCIES) + $(AM_V_at)-rm -f libgnunetmeshtest.a + $(AM_V_AR)$(libgnunetmeshtest_a_AR) libgnunetmeshtest.a $(libgnunetmeshtest_a_OBJECTS) $(libgnunetmeshtest_a_LIBADD) + $(AM_V_at)$(RANLIB) libgnunetmeshtest.a install-libLTLIBRARIES: $(lib_LTLIBRARIES) @$(NORMAL_INSTALL) - test -z "$(libdir)" || $(MKDIR_P) "$(DESTDIR)$(libdir)" @list='$(lib_LTLIBRARIES)'; test -n "$(libdir)" || list=; \ list2=; for p in $$list; do \ if test -f $$p; then \ @@ -575,6 +864,8 @@ install-libLTLIBRARIES: $(lib_LTLIBRARIES) else :; fi; \ done; \ test -z "$$list2" || { \ + echo " $(MKDIR_P) '$(DESTDIR)$(libdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libdir)" || exit 1; \ echo " $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 '$(DESTDIR)$(libdir)'"; \ $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 "$(DESTDIR)$(libdir)"; \ } @@ -596,12 +887,49 @@ clean-libLTLIBRARIES: echo "rm -f \"$${dir}/so_locations\""; \ rm -f "$${dir}/so_locations"; \ done -libgnunetmesh.la: $(libgnunetmesh_la_OBJECTS) $(libgnunetmesh_la_DEPENDENCIES) +install-pluginLTLIBRARIES: $(plugin_LTLIBRARIES) + @$(NORMAL_INSTALL) + @list='$(plugin_LTLIBRARIES)'; test -n "$(plugindir)" || list=; \ + list2=; for p in $$list; do \ + if test -f $$p; then \ + list2="$$list2 $$p"; \ + else :; fi; \ + done; \ + test -z "$$list2" || { \ + echo " $(MKDIR_P) '$(DESTDIR)$(plugindir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(plugindir)" || exit 1; \ + echo " $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 '$(DESTDIR)$(plugindir)'"; \ + $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 "$(DESTDIR)$(plugindir)"; \ + } + +uninstall-pluginLTLIBRARIES: + @$(NORMAL_UNINSTALL) + @list='$(plugin_LTLIBRARIES)'; test -n "$(plugindir)" || list=; \ + for p in $$list; do \ + $(am__strip_dir) \ + echo " $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=uninstall rm -f '$(DESTDIR)$(plugindir)/$$f'"; \ + $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=uninstall rm -f "$(DESTDIR)$(plugindir)/$$f"; \ + done + +clean-pluginLTLIBRARIES: + -test -z "$(plugin_LTLIBRARIES)" || rm -f $(plugin_LTLIBRARIES) + @list='$(plugin_LTLIBRARIES)'; for p in $$list; do \ + dir="`echo $$p | sed -e 's|/[^/]*$$||'`"; \ + test "$$dir" != "$$p" || dir=.; \ + echo "rm -f \"$${dir}/so_locations\""; \ + rm -f "$${dir}/so_locations"; \ + done +libgnunet_plugin_block_mesh.la: $(libgnunet_plugin_block_mesh_la_OBJECTS) $(libgnunet_plugin_block_mesh_la_DEPENDENCIES) $(EXTRA_libgnunet_plugin_block_mesh_la_DEPENDENCIES) + $(AM_V_CCLD)$(libgnunet_plugin_block_mesh_la_LINK) -rpath $(plugindir) $(libgnunet_plugin_block_mesh_la_OBJECTS) $(libgnunet_plugin_block_mesh_la_LIBADD) $(LIBS) +libgnunetmesh.la: $(libgnunetmesh_la_OBJECTS) $(libgnunetmesh_la_DEPENDENCIES) $(EXTRA_libgnunetmesh_la_DEPENDENCIES) $(AM_V_CCLD)$(libgnunetmesh_la_LINK) -rpath $(libdir) $(libgnunetmesh_la_OBJECTS) $(libgnunetmesh_la_LIBADD) $(LIBS) install-binPROGRAMS: $(bin_PROGRAMS) @$(NORMAL_INSTALL) - test -z "$(bindir)" || $(MKDIR_P) "$(DESTDIR)$(bindir)" @list='$(bin_PROGRAMS)'; test -n "$(bindir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(bindir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(bindir)" || exit 1; \ + fi; \ for p in $$list; do echo "$$p $$p"; done | \ sed 's/$(EXEEXT)$$//' | \ while read p p1; do if test -f $$p || test -f $$p1; \ @@ -650,34 +978,116 @@ clean-checkPROGRAMS: list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ echo " rm -f" $$list; \ rm -f $$list -gnunet-service-mesh$(EXEEXT): $(gnunet_service_mesh_OBJECTS) $(gnunet_service_mesh_DEPENDENCIES) +install-libexecPROGRAMS: $(libexec_PROGRAMS) + @$(NORMAL_INSTALL) + @list='$(libexec_PROGRAMS)'; test -n "$(libexecdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(libexecdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libexecdir)" || exit 1; \ + fi; \ + for p in $$list; do echo "$$p $$p"; done | \ + sed 's/$(EXEEXT)$$//' | \ + while read p p1; do if test -f $$p || test -f $$p1; \ + then echo "$$p"; echo "$$p"; else :; fi; \ + done | \ + sed -e 'p;s,.*/,,;n;h' -e 's|.*|.|' \ + -e 'p;x;s,.*/,,;s/$(EXEEXT)$$//;$(transform);s/$$/$(EXEEXT)/' | \ + sed 'N;N;N;s,\n, ,g' | \ + $(AWK) 'BEGIN { files["."] = ""; dirs["."] = 1 } \ + { d=$$3; if (dirs[d] != 1) { print "d", d; dirs[d] = 1 } \ + if ($$2 == $$4) files[d] = files[d] " " $$1; \ + else { print "f", $$3 "/" $$4, $$1; } } \ + END { for (d in files) print "f", d, files[d] }' | \ + while read type dir files; do \ + if test "$$dir" = .; then dir=; else dir=/$$dir; fi; \ + test -z "$$files" || { \ + echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files '$(DESTDIR)$(libexecdir)$$dir'"; \ + $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files "$(DESTDIR)$(libexecdir)$$dir" || exit $$?; \ + } \ + ; done + +uninstall-libexecPROGRAMS: + @$(NORMAL_UNINSTALL) + @list='$(libexec_PROGRAMS)'; test -n "$(libexecdir)" || list=; \ + files=`for p in $$list; do echo "$$p"; done | \ + sed -e 'h;s,^.*/,,;s/$(EXEEXT)$$//;$(transform)' \ + -e 's/$$/$(EXEEXT)/' `; \ + test -n "$$list" || exit 0; \ + echo " ( cd '$(DESTDIR)$(libexecdir)' && rm -f" $$files ")"; \ + cd "$(DESTDIR)$(libexecdir)" && rm -f $$files + +clean-libexecPROGRAMS: + @list='$(libexec_PROGRAMS)'; test -n "$$list" || exit 0; \ + echo " rm -f" $$list; \ + rm -f $$list || exit $$?; \ + test -n "$(EXEEXT)" || exit 0; \ + list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ + echo " rm -f" $$list; \ + rm -f $$list +gnunet-mesh$(EXEEXT): $(gnunet_mesh_OBJECTS) $(gnunet_mesh_DEPENDENCIES) $(EXTRA_gnunet_mesh_DEPENDENCIES) + @rm -f gnunet-mesh$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(gnunet_mesh_OBJECTS) $(gnunet_mesh_LDADD) $(LIBS) +gnunet-service-mesh$(EXEEXT): $(gnunet_service_mesh_OBJECTS) $(gnunet_service_mesh_DEPENDENCIES) $(EXTRA_gnunet_service_mesh_DEPENDENCIES) @rm -f gnunet-service-mesh$(EXEEXT) - $(AM_V_CCLD)$(LINK) $(gnunet_service_mesh_OBJECTS) $(gnunet_service_mesh_LDADD) $(LIBS) -test_mesh_2dtorus$(EXEEXT): $(test_mesh_2dtorus_OBJECTS) $(test_mesh_2dtorus_DEPENDENCIES) + $(AM_V_CCLD)$(gnunet_service_mesh_LINK) $(gnunet_service_mesh_OBJECTS) $(gnunet_service_mesh_LDADD) $(LIBS) +gnunet-service-mesh-new$(EXEEXT): $(gnunet_service_mesh_new_OBJECTS) $(gnunet_service_mesh_new_DEPENDENCIES) $(EXTRA_gnunet_service_mesh_new_DEPENDENCIES) + @rm -f gnunet-service-mesh-new$(EXEEXT) + $(AM_V_CCLD)$(gnunet_service_mesh_new_LINK) $(gnunet_service_mesh_new_OBJECTS) $(gnunet_service_mesh_new_LDADD) $(LIBS) +test_mesh_2dtorus$(EXEEXT): $(test_mesh_2dtorus_OBJECTS) $(test_mesh_2dtorus_DEPENDENCIES) $(EXTRA_test_mesh_2dtorus_DEPENDENCIES) @rm -f test_mesh_2dtorus$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_mesh_2dtorus_OBJECTS) $(test_mesh_2dtorus_LDADD) $(LIBS) -test_mesh_api$(EXEEXT): $(test_mesh_api_OBJECTS) $(test_mesh_api_DEPENDENCIES) +test_mesh_api$(EXEEXT): $(test_mesh_api_OBJECTS) $(test_mesh_api_DEPENDENCIES) $(EXTRA_test_mesh_api_DEPENDENCIES) @rm -f test_mesh_api$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_mesh_api_OBJECTS) $(test_mesh_api_LDADD) $(LIBS) -test_mesh_local_1$(EXEEXT): $(test_mesh_local_1_OBJECTS) $(test_mesh_local_1_DEPENDENCIES) +test_mesh_local_1$(EXEEXT): $(test_mesh_local_1_OBJECTS) $(test_mesh_local_1_DEPENDENCIES) $(EXTRA_test_mesh_local_1_DEPENDENCIES) @rm -f test_mesh_local_1$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_mesh_local_1_OBJECTS) $(test_mesh_local_1_LDADD) $(LIBS) -test_mesh_local_2$(EXEEXT): $(test_mesh_local_2_OBJECTS) $(test_mesh_local_2_DEPENDENCIES) +test_mesh_local_2$(EXEEXT): $(test_mesh_local_2_OBJECTS) $(test_mesh_local_2_DEPENDENCIES) $(EXTRA_test_mesh_local_2_DEPENDENCIES) @rm -f test_mesh_local_2$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_mesh_local_2_OBJECTS) $(test_mesh_local_2_LDADD) $(LIBS) -test_mesh_small_multicast$(EXEEXT): $(test_mesh_small_multicast_OBJECTS) $(test_mesh_small_multicast_DEPENDENCIES) +test_mesh_local_traffic_bck$(EXEEXT): $(test_mesh_local_traffic_bck_OBJECTS) $(test_mesh_local_traffic_bck_DEPENDENCIES) $(EXTRA_test_mesh_local_traffic_bck_DEPENDENCIES) + @rm -f test_mesh_local_traffic_bck$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_mesh_local_traffic_bck_OBJECTS) $(test_mesh_local_traffic_bck_LDADD) $(LIBS) +test_mesh_local_traffic_both$(EXEEXT): $(test_mesh_local_traffic_both_OBJECTS) $(test_mesh_local_traffic_both_DEPENDENCIES) $(EXTRA_test_mesh_local_traffic_both_DEPENDENCIES) + @rm -f test_mesh_local_traffic_both$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_mesh_local_traffic_both_OBJECTS) $(test_mesh_local_traffic_both_LDADD) $(LIBS) +test_mesh_local_traffic_fwd$(EXEEXT): $(test_mesh_local_traffic_fwd_OBJECTS) $(test_mesh_local_traffic_fwd_DEPENDENCIES) $(EXTRA_test_mesh_local_traffic_fwd_DEPENDENCIES) + @rm -f test_mesh_local_traffic_fwd$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_mesh_local_traffic_fwd_OBJECTS) $(test_mesh_local_traffic_fwd_LDADD) $(LIBS) +test_mesh_regex$(EXEEXT): $(test_mesh_regex_OBJECTS) $(test_mesh_regex_DEPENDENCIES) $(EXTRA_test_mesh_regex_DEPENDENCIES) + @rm -f test_mesh_regex$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_mesh_regex_OBJECTS) $(test_mesh_regex_LDADD) $(LIBS) +test_mesh_small_multicast$(EXEEXT): $(test_mesh_small_multicast_OBJECTS) $(test_mesh_small_multicast_DEPENDENCIES) $(EXTRA_test_mesh_small_multicast_DEPENDENCIES) @rm -f test_mesh_small_multicast$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_mesh_small_multicast_OBJECTS) $(test_mesh_small_multicast_LDADD) $(LIBS) -test_mesh_small_speed$(EXEEXT): $(test_mesh_small_speed_OBJECTS) $(test_mesh_small_speed_DEPENDENCIES) +test_mesh_small_signal$(EXEEXT): $(test_mesh_small_signal_OBJECTS) $(test_mesh_small_signal_DEPENDENCIES) $(EXTRA_test_mesh_small_signal_DEPENDENCIES) + @rm -f test_mesh_small_signal$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_mesh_small_signal_OBJECTS) $(test_mesh_small_signal_LDADD) $(LIBS) +test_mesh_small_speed$(EXEEXT): $(test_mesh_small_speed_OBJECTS) $(test_mesh_small_speed_DEPENDENCIES) $(EXTRA_test_mesh_small_speed_DEPENDENCIES) @rm -f test_mesh_small_speed$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_mesh_small_speed_OBJECTS) $(test_mesh_small_speed_LDADD) $(LIBS) -test_mesh_small_speed_ack$(EXEEXT): $(test_mesh_small_speed_ack_OBJECTS) $(test_mesh_small_speed_ack_DEPENDENCIES) +test_mesh_small_speed_ack$(EXEEXT): $(test_mesh_small_speed_ack_OBJECTS) $(test_mesh_small_speed_ack_DEPENDENCIES) $(EXTRA_test_mesh_small_speed_ack_DEPENDENCIES) @rm -f test_mesh_small_speed_ack$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_mesh_small_speed_ack_OBJECTS) $(test_mesh_small_speed_ack_LDADD) $(LIBS) -test_mesh_small_unicast$(EXEEXT): $(test_mesh_small_unicast_OBJECTS) $(test_mesh_small_unicast_DEPENDENCIES) +test_mesh_small_speed_backwards$(EXEEXT): $(test_mesh_small_speed_backwards_OBJECTS) $(test_mesh_small_speed_backwards_DEPENDENCIES) $(EXTRA_test_mesh_small_speed_backwards_DEPENDENCIES) + @rm -f test_mesh_small_speed_backwards$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_mesh_small_speed_backwards_OBJECTS) $(test_mesh_small_speed_backwards_LDADD) $(LIBS) +test_mesh_small_speed_min$(EXEEXT): $(test_mesh_small_speed_min_OBJECTS) $(test_mesh_small_speed_min_DEPENDENCIES) $(EXTRA_test_mesh_small_speed_min_DEPENDENCIES) + @rm -f test_mesh_small_speed_min$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_mesh_small_speed_min_OBJECTS) $(test_mesh_small_speed_min_LDADD) $(LIBS) +test_mesh_small_speed_min_backwards$(EXEEXT): $(test_mesh_small_speed_min_backwards_OBJECTS) $(test_mesh_small_speed_min_backwards_DEPENDENCIES) $(EXTRA_test_mesh_small_speed_min_backwards_DEPENDENCIES) + @rm -f test_mesh_small_speed_min_backwards$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_mesh_small_speed_min_backwards_OBJECTS) $(test_mesh_small_speed_min_backwards_LDADD) $(LIBS) +test_mesh_small_speed_nobuf$(EXEEXT): $(test_mesh_small_speed_nobuf_OBJECTS) $(test_mesh_small_speed_nobuf_DEPENDENCIES) $(EXTRA_test_mesh_small_speed_nobuf_DEPENDENCIES) + @rm -f test_mesh_small_speed_nobuf$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_mesh_small_speed_nobuf_OBJECTS) $(test_mesh_small_speed_nobuf_LDADD) $(LIBS) +test_mesh_small_speed_nobuf_backwards$(EXEEXT): $(test_mesh_small_speed_nobuf_backwards_OBJECTS) $(test_mesh_small_speed_nobuf_backwards_DEPENDENCIES) $(EXTRA_test_mesh_small_speed_nobuf_backwards_DEPENDENCIES) + @rm -f test_mesh_small_speed_nobuf_backwards$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_mesh_small_speed_nobuf_backwards_OBJECTS) $(test_mesh_small_speed_nobuf_backwards_LDADD) $(LIBS) +test_mesh_small_unicast$(EXEEXT): $(test_mesh_small_unicast_OBJECTS) $(test_mesh_small_unicast_DEPENDENCIES) $(EXTRA_test_mesh_small_unicast_DEPENDENCIES) @rm -f test_mesh_small_unicast$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_mesh_small_unicast_OBJECTS) $(test_mesh_small_unicast_LDADD) $(LIBS) -test_mesh_tree_api$(EXEEXT): $(test_mesh_tree_api_OBJECTS) $(test_mesh_tree_api_DEPENDENCIES) +test_mesh_tree_api$(EXEEXT): $(test_mesh_tree_api_OBJECTS) $(test_mesh_tree_api_DEPENDENCIES) $(EXTRA_test_mesh_tree_api_DEPENDENCIES) @rm -f test_mesh_tree_api$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_mesh_tree_api_OBJECTS) $(test_mesh_tree_api_LDADD) $(LIBS) @@ -687,39 +1097,130 @@ mostlyclean-compile: distclean-compile: -rm -f *.tab.c -@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-service-mesh.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-mesh.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet_service_mesh-gnunet-service-mesh.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet_service_mesh-mesh_common.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet_service_mesh-mesh_tunnel_tree.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet_service_mesh_new-gnunet-service-mesh-new.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet_service_mesh_new-mesh_common.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet_service_mesh_new-mesh_tunnel_tree.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/mesh_api.Plo@am__quote@ -@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/mesh_tunnel_tree.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/mesh_common.Plo@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/mesh_test_lib.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/plugin_block_mesh.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_mesh_2dtorus.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_mesh_api.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_mesh_local_1.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_mesh_local_2.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_mesh_local_traffic.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_mesh_regex.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_mesh_small.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_mesh_tree_api.Po@am__quote@ .c.o: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c $< .c.obj: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'` @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c `$(CYGPATH_W) '$<'` +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c `$(CYGPATH_W) '$<'` .c.lo: @am__fastdepCC_TRUE@ $(AM_V_CC)$(LTCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LTCOMPILE) -c -o $@ $< + +gnunet_service_mesh-gnunet-service-mesh.o: gnunet-service-mesh.c +@am__fastdepCC_TRUE@ $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_mesh_CFLAGS) $(CFLAGS) -MT gnunet_service_mesh-gnunet-service-mesh.o -MD -MP -MF $(DEPDIR)/gnunet_service_mesh-gnunet-service-mesh.Tpo -c -o gnunet_service_mesh-gnunet-service-mesh.o `test -f 'gnunet-service-mesh.c' || echo '$(srcdir)/'`gnunet-service-mesh.c +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/gnunet_service_mesh-gnunet-service-mesh.Tpo $(DEPDIR)/gnunet_service_mesh-gnunet-service-mesh.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='gnunet-service-mesh.c' object='gnunet_service_mesh-gnunet-service-mesh.o' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_mesh_CFLAGS) $(CFLAGS) -c -o gnunet_service_mesh-gnunet-service-mesh.o `test -f 'gnunet-service-mesh.c' || echo '$(srcdir)/'`gnunet-service-mesh.c + +gnunet_service_mesh-gnunet-service-mesh.obj: gnunet-service-mesh.c +@am__fastdepCC_TRUE@ $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_mesh_CFLAGS) $(CFLAGS) -MT gnunet_service_mesh-gnunet-service-mesh.obj -MD -MP -MF $(DEPDIR)/gnunet_service_mesh-gnunet-service-mesh.Tpo -c -o gnunet_service_mesh-gnunet-service-mesh.obj `if test -f 'gnunet-service-mesh.c'; then $(CYGPATH_W) 'gnunet-service-mesh.c'; else $(CYGPATH_W) '$(srcdir)/gnunet-service-mesh.c'; fi` +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/gnunet_service_mesh-gnunet-service-mesh.Tpo $(DEPDIR)/gnunet_service_mesh-gnunet-service-mesh.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='gnunet-service-mesh.c' object='gnunet_service_mesh-gnunet-service-mesh.obj' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_mesh_CFLAGS) $(CFLAGS) -c -o gnunet_service_mesh-gnunet-service-mesh.obj `if test -f 'gnunet-service-mesh.c'; then $(CYGPATH_W) 'gnunet-service-mesh.c'; else $(CYGPATH_W) '$(srcdir)/gnunet-service-mesh.c'; fi` + +gnunet_service_mesh-mesh_tunnel_tree.o: mesh_tunnel_tree.c +@am__fastdepCC_TRUE@ $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_mesh_CFLAGS) $(CFLAGS) -MT gnunet_service_mesh-mesh_tunnel_tree.o -MD -MP -MF $(DEPDIR)/gnunet_service_mesh-mesh_tunnel_tree.Tpo -c -o gnunet_service_mesh-mesh_tunnel_tree.o `test -f 'mesh_tunnel_tree.c' || echo '$(srcdir)/'`mesh_tunnel_tree.c +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/gnunet_service_mesh-mesh_tunnel_tree.Tpo $(DEPDIR)/gnunet_service_mesh-mesh_tunnel_tree.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='mesh_tunnel_tree.c' object='gnunet_service_mesh-mesh_tunnel_tree.o' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_mesh_CFLAGS) $(CFLAGS) -c -o gnunet_service_mesh-mesh_tunnel_tree.o `test -f 'mesh_tunnel_tree.c' || echo '$(srcdir)/'`mesh_tunnel_tree.c + +gnunet_service_mesh-mesh_tunnel_tree.obj: mesh_tunnel_tree.c +@am__fastdepCC_TRUE@ $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_mesh_CFLAGS) $(CFLAGS) -MT gnunet_service_mesh-mesh_tunnel_tree.obj -MD -MP -MF $(DEPDIR)/gnunet_service_mesh-mesh_tunnel_tree.Tpo -c -o gnunet_service_mesh-mesh_tunnel_tree.obj `if test -f 'mesh_tunnel_tree.c'; then $(CYGPATH_W) 'mesh_tunnel_tree.c'; else $(CYGPATH_W) '$(srcdir)/mesh_tunnel_tree.c'; fi` +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/gnunet_service_mesh-mesh_tunnel_tree.Tpo $(DEPDIR)/gnunet_service_mesh-mesh_tunnel_tree.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='mesh_tunnel_tree.c' object='gnunet_service_mesh-mesh_tunnel_tree.obj' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_mesh_CFLAGS) $(CFLAGS) -c -o gnunet_service_mesh-mesh_tunnel_tree.obj `if test -f 'mesh_tunnel_tree.c'; then $(CYGPATH_W) 'mesh_tunnel_tree.c'; else $(CYGPATH_W) '$(srcdir)/mesh_tunnel_tree.c'; fi` + +gnunet_service_mesh-mesh_common.o: mesh_common.c +@am__fastdepCC_TRUE@ $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_mesh_CFLAGS) $(CFLAGS) -MT gnunet_service_mesh-mesh_common.o -MD -MP -MF $(DEPDIR)/gnunet_service_mesh-mesh_common.Tpo -c -o gnunet_service_mesh-mesh_common.o `test -f 'mesh_common.c' || echo '$(srcdir)/'`mesh_common.c +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/gnunet_service_mesh-mesh_common.Tpo $(DEPDIR)/gnunet_service_mesh-mesh_common.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='mesh_common.c' object='gnunet_service_mesh-mesh_common.o' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_mesh_CFLAGS) $(CFLAGS) -c -o gnunet_service_mesh-mesh_common.o `test -f 'mesh_common.c' || echo '$(srcdir)/'`mesh_common.c + +gnunet_service_mesh-mesh_common.obj: mesh_common.c +@am__fastdepCC_TRUE@ $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_mesh_CFLAGS) $(CFLAGS) -MT gnunet_service_mesh-mesh_common.obj -MD -MP -MF $(DEPDIR)/gnunet_service_mesh-mesh_common.Tpo -c -o gnunet_service_mesh-mesh_common.obj `if test -f 'mesh_common.c'; then $(CYGPATH_W) 'mesh_common.c'; else $(CYGPATH_W) '$(srcdir)/mesh_common.c'; fi` +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/gnunet_service_mesh-mesh_common.Tpo $(DEPDIR)/gnunet_service_mesh-mesh_common.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='mesh_common.c' object='gnunet_service_mesh-mesh_common.obj' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_mesh_CFLAGS) $(CFLAGS) -c -o gnunet_service_mesh-mesh_common.obj `if test -f 'mesh_common.c'; then $(CYGPATH_W) 'mesh_common.c'; else $(CYGPATH_W) '$(srcdir)/mesh_common.c'; fi` + +gnunet_service_mesh_new-gnunet-service-mesh-new.o: gnunet-service-mesh-new.c +@am__fastdepCC_TRUE@ $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_mesh_new_CFLAGS) $(CFLAGS) -MT gnunet_service_mesh_new-gnunet-service-mesh-new.o -MD -MP -MF $(DEPDIR)/gnunet_service_mesh_new-gnunet-service-mesh-new.Tpo -c -o gnunet_service_mesh_new-gnunet-service-mesh-new.o `test -f 'gnunet-service-mesh-new.c' || echo '$(srcdir)/'`gnunet-service-mesh-new.c +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/gnunet_service_mesh_new-gnunet-service-mesh-new.Tpo $(DEPDIR)/gnunet_service_mesh_new-gnunet-service-mesh-new.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='gnunet-service-mesh-new.c' object='gnunet_service_mesh_new-gnunet-service-mesh-new.o' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_mesh_new_CFLAGS) $(CFLAGS) -c -o gnunet_service_mesh_new-gnunet-service-mesh-new.o `test -f 'gnunet-service-mesh-new.c' || echo '$(srcdir)/'`gnunet-service-mesh-new.c + +gnunet_service_mesh_new-gnunet-service-mesh-new.obj: gnunet-service-mesh-new.c +@am__fastdepCC_TRUE@ $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_mesh_new_CFLAGS) $(CFLAGS) -MT gnunet_service_mesh_new-gnunet-service-mesh-new.obj -MD -MP -MF $(DEPDIR)/gnunet_service_mesh_new-gnunet-service-mesh-new.Tpo -c -o gnunet_service_mesh_new-gnunet-service-mesh-new.obj `if test -f 'gnunet-service-mesh-new.c'; then $(CYGPATH_W) 'gnunet-service-mesh-new.c'; else $(CYGPATH_W) '$(srcdir)/gnunet-service-mesh-new.c'; fi` +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/gnunet_service_mesh_new-gnunet-service-mesh-new.Tpo $(DEPDIR)/gnunet_service_mesh_new-gnunet-service-mesh-new.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='gnunet-service-mesh-new.c' object='gnunet_service_mesh_new-gnunet-service-mesh-new.obj' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LTCOMPILE) -c -o $@ $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_mesh_new_CFLAGS) $(CFLAGS) -c -o gnunet_service_mesh_new-gnunet-service-mesh-new.obj `if test -f 'gnunet-service-mesh-new.c'; then $(CYGPATH_W) 'gnunet-service-mesh-new.c'; else $(CYGPATH_W) '$(srcdir)/gnunet-service-mesh-new.c'; fi` + +gnunet_service_mesh_new-mesh_tunnel_tree.o: mesh_tunnel_tree.c +@am__fastdepCC_TRUE@ $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_mesh_new_CFLAGS) $(CFLAGS) -MT gnunet_service_mesh_new-mesh_tunnel_tree.o -MD -MP -MF $(DEPDIR)/gnunet_service_mesh_new-mesh_tunnel_tree.Tpo -c -o gnunet_service_mesh_new-mesh_tunnel_tree.o `test -f 'mesh_tunnel_tree.c' || echo '$(srcdir)/'`mesh_tunnel_tree.c +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/gnunet_service_mesh_new-mesh_tunnel_tree.Tpo $(DEPDIR)/gnunet_service_mesh_new-mesh_tunnel_tree.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='mesh_tunnel_tree.c' object='gnunet_service_mesh_new-mesh_tunnel_tree.o' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_mesh_new_CFLAGS) $(CFLAGS) -c -o gnunet_service_mesh_new-mesh_tunnel_tree.o `test -f 'mesh_tunnel_tree.c' || echo '$(srcdir)/'`mesh_tunnel_tree.c + +gnunet_service_mesh_new-mesh_tunnel_tree.obj: mesh_tunnel_tree.c +@am__fastdepCC_TRUE@ $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_mesh_new_CFLAGS) $(CFLAGS) -MT gnunet_service_mesh_new-mesh_tunnel_tree.obj -MD -MP -MF $(DEPDIR)/gnunet_service_mesh_new-mesh_tunnel_tree.Tpo -c -o gnunet_service_mesh_new-mesh_tunnel_tree.obj `if test -f 'mesh_tunnel_tree.c'; then $(CYGPATH_W) 'mesh_tunnel_tree.c'; else $(CYGPATH_W) '$(srcdir)/mesh_tunnel_tree.c'; fi` +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/gnunet_service_mesh_new-mesh_tunnel_tree.Tpo $(DEPDIR)/gnunet_service_mesh_new-mesh_tunnel_tree.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='mesh_tunnel_tree.c' object='gnunet_service_mesh_new-mesh_tunnel_tree.obj' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_mesh_new_CFLAGS) $(CFLAGS) -c -o gnunet_service_mesh_new-mesh_tunnel_tree.obj `if test -f 'mesh_tunnel_tree.c'; then $(CYGPATH_W) 'mesh_tunnel_tree.c'; else $(CYGPATH_W) '$(srcdir)/mesh_tunnel_tree.c'; fi` + +gnunet_service_mesh_new-mesh_common.o: mesh_common.c +@am__fastdepCC_TRUE@ $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_mesh_new_CFLAGS) $(CFLAGS) -MT gnunet_service_mesh_new-mesh_common.o -MD -MP -MF $(DEPDIR)/gnunet_service_mesh_new-mesh_common.Tpo -c -o gnunet_service_mesh_new-mesh_common.o `test -f 'mesh_common.c' || echo '$(srcdir)/'`mesh_common.c +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/gnunet_service_mesh_new-mesh_common.Tpo $(DEPDIR)/gnunet_service_mesh_new-mesh_common.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='mesh_common.c' object='gnunet_service_mesh_new-mesh_common.o' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_mesh_new_CFLAGS) $(CFLAGS) -c -o gnunet_service_mesh_new-mesh_common.o `test -f 'mesh_common.c' || echo '$(srcdir)/'`mesh_common.c + +gnunet_service_mesh_new-mesh_common.obj: mesh_common.c +@am__fastdepCC_TRUE@ $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_mesh_new_CFLAGS) $(CFLAGS) -MT gnunet_service_mesh_new-mesh_common.obj -MD -MP -MF $(DEPDIR)/gnunet_service_mesh_new-mesh_common.Tpo -c -o gnunet_service_mesh_new-mesh_common.obj `if test -f 'mesh_common.c'; then $(CYGPATH_W) 'mesh_common.c'; else $(CYGPATH_W) '$(srcdir)/mesh_common.c'; fi` +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/gnunet_service_mesh_new-mesh_common.Tpo $(DEPDIR)/gnunet_service_mesh_new-mesh_common.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='mesh_common.c' object='gnunet_service_mesh_new-mesh_common.obj' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_mesh_new_CFLAGS) $(CFLAGS) -c -o gnunet_service_mesh_new-mesh_common.obj `if test -f 'mesh_common.c'; then $(CYGPATH_W) 'mesh_common.c'; else $(CYGPATH_W) '$(srcdir)/mesh_common.c'; fi` mostlyclean-libtool: -rm -f *.lo @@ -728,8 +1229,11 @@ clean-libtool: -rm -rf .libs _libs install-pkgcfgDATA: $(pkgcfg_DATA) @$(NORMAL_INSTALL) - test -z "$(pkgcfgdir)" || $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" @list='$(pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(pkgcfgdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" || exit 1; \ + fi; \ for p in $$list; do \ if test -f "$$p"; then d=; else d="$(srcdir)/"; fi; \ echo "$$d$$p"; \ @@ -743,9 +1247,7 @@ uninstall-pkgcfgDATA: @$(NORMAL_UNINSTALL) @list='$(pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ files=`for p in $$list; do echo $$p; done | sed -e 's|^.*/||'`; \ - test -n "$$files" || exit 0; \ - echo " ( cd '$(DESTDIR)$(pkgcfgdir)' && rm -f" $$files ")"; \ - cd "$(DESTDIR)$(pkgcfgdir)" && rm -f $$files + dir='$(DESTDIR)$(pkgcfgdir)'; $(am__uninstall_files_from_dir) ID: $(HEADERS) $(SOURCES) $(LISP) $(TAGS_FILES) list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ @@ -880,14 +1382,15 @@ check-TESTS: $(TESTS) fi; \ dashes=`echo "$$dashes" | sed s/./=/g`; \ if test "$$failed" -eq 0; then \ - echo "$$grn$$dashes"; \ + col="$$grn"; \ else \ - echo "$$red$$dashes"; \ + col="$$red"; \ fi; \ - echo "$$banner"; \ - test -z "$$skipped" || echo "$$skipped"; \ - test -z "$$report" || echo "$$report"; \ - echo "$$dashes$$std"; \ + echo "$${col}$$dashes$${std}"; \ + echo "$${col}$$banner$${std}"; \ + test -z "$$skipped" || echo "$${col}$$skipped$${std}"; \ + test -z "$$report" || echo "$${col}$$report$${std}"; \ + echo "$${col}$$dashes$${std}"; \ test "$$failed" -eq 0; \ else :; fi @@ -925,11 +1428,11 @@ check-am: all-am $(MAKE) $(AM_MAKEFLAGS) $(check_PROGRAMS) $(MAKE) $(AM_MAKEFLAGS) check-TESTS check: check-am -all-am: Makefile $(LTLIBRARIES) $(PROGRAMS) $(DATA) +all-am: Makefile $(LIBRARIES) $(LTLIBRARIES) $(PROGRAMS) $(DATA) install-binPROGRAMS: install-libLTLIBRARIES installdirs: - for dir in "$(DESTDIR)$(libdir)" "$(DESTDIR)$(bindir)" "$(DESTDIR)$(pkgcfgdir)"; do \ + for dir in "$(DESTDIR)$(libdir)" "$(DESTDIR)$(plugindir)" "$(DESTDIR)$(bindir)" "$(DESTDIR)$(libexecdir)" "$(DESTDIR)$(pkgcfgdir)"; do \ test -z "$$dir" || $(MKDIR_P) "$$dir"; \ done install: install-am @@ -942,10 +1445,15 @@ install-am: all-am installcheck: installcheck-am install-strip: - $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ - install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ - `test -z '$(STRIP)' || \ - echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi mostlyclean-generic: clean-generic: @@ -960,7 +1468,8 @@ maintainer-clean-generic: clean: clean-am clean-am: clean-binPROGRAMS clean-checkPROGRAMS clean-generic \ - clean-libLTLIBRARIES clean-libtool mostlyclean-am + clean-libLTLIBRARIES clean-libexecPROGRAMS clean-libtool \ + clean-noinstLIBRARIES clean-pluginLTLIBRARIES mostlyclean-am distclean: distclean-am -rm -rf ./$(DEPDIR) @@ -980,13 +1489,14 @@ info: info-am info-am: -install-data-am: install-pkgcfgDATA +install-data-am: install-pkgcfgDATA install-pluginLTLIBRARIES install-dvi: install-dvi-am install-dvi-am: -install-exec-am: install-binPROGRAMS install-libLTLIBRARIES +install-exec-am: install-binPROGRAMS install-libLTLIBRARIES \ + install-libexecPROGRAMS install-html: install-html-am @@ -1027,26 +1537,30 @@ ps: ps-am ps-am: uninstall-am: uninstall-binPROGRAMS uninstall-libLTLIBRARIES \ - uninstall-pkgcfgDATA + uninstall-libexecPROGRAMS uninstall-pkgcfgDATA \ + uninstall-pluginLTLIBRARIES .MAKE: check-am install-am install-strip .PHONY: CTAGS GTAGS all all-am check check-TESTS check-am clean \ clean-binPROGRAMS clean-checkPROGRAMS clean-generic \ - clean-libLTLIBRARIES clean-libtool ctags distclean \ + clean-libLTLIBRARIES clean-libexecPROGRAMS clean-libtool \ + clean-noinstLIBRARIES clean-pluginLTLIBRARIES ctags distclean \ distclean-compile distclean-generic distclean-libtool \ distclean-tags distdir dvi dvi-am html html-am info info-am \ install install-am install-binPROGRAMS install-data \ install-data-am install-dvi install-dvi-am install-exec \ install-exec-am install-html install-html-am install-info \ - install-info-am install-libLTLIBRARIES install-man install-pdf \ - install-pdf-am install-pkgcfgDATA install-ps install-ps-am \ + install-info-am install-libLTLIBRARIES install-libexecPROGRAMS \ + install-man install-pdf install-pdf-am install-pkgcfgDATA \ + install-pluginLTLIBRARIES install-ps install-ps-am \ install-strip installcheck installcheck-am installdirs \ maintainer-clean maintainer-clean-generic mostlyclean \ mostlyclean-compile mostlyclean-generic mostlyclean-libtool \ pdf pdf-am ps ps-am tags uninstall uninstall-am \ uninstall-binPROGRAMS uninstall-libLTLIBRARIES \ - uninstall-pkgcfgDATA + uninstall-libexecPROGRAMS uninstall-pkgcfgDATA \ + uninstall-pluginLTLIBRARIES # Tell versions [3.59,3.63) of GNU make to not export all variables. diff --git a/src/mesh/gnunet-mesh.c b/src/mesh/gnunet-mesh.c new file mode 100644 index 0000000..21a3f7d --- /dev/null +++ b/src/mesh/gnunet-mesh.c @@ -0,0 +1,235 @@ +/* + This file is part of GNUnet. + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @file mesh/gnunet-mesh.c + * @brief Print information about mesh tunnels and peers. + * @author Bartlomiej Polot + */ +#include "platform.h" +#include "gnunet_configuration_lib.h" +#include "gnunet_getopt_lib.h" +#include "gnunet_mesh_service.h" +#include "gnunet_program_lib.h" + + +/** + * Option -m. + */ +static int monitor_connections; + +/** + * Option -t + */ +static char *tunnel_id; + +/** + * Mesh handle. + */ +static struct GNUNET_MESH_Handle *mh; + +/** + * Shutdown task handle. + */ +GNUNET_SCHEDULER_TaskIdentifier sd; + +/** + * Task run in monitor mode when the user presses CTRL-C to abort. + * Stops monitoring activity. + * + * @param cls Closure (unused). + * @param tc scheduler context + */ +static void +shutdown_task (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + if (NULL != mh) + { + GNUNET_MESH_disconnect (mh); + mh = NULL; + } +} + + +/** + * Method called to retrieve information about each tunnel the mesh peer + * is aware of. + * + * @param cls Closure (unused). + * @param initiator Peer that started the tunnel (owner). + * @param tunnel_number Tunnel number. + * @param peers Array of peer identities that participate in the tunnel. + * @param npeers Number of peers in peers. + */ +static void +tunnels_callback (void *cls, + const struct GNUNET_PeerIdentity *initiator, + unsigned int tunnel_number, + const struct GNUNET_PeerIdentity *peers, + unsigned int npeers) +{ + unsigned int i; + + fprintf (stdout, "Tunnel %s [%u]: %u peers\n", + GNUNET_i2s_full (initiator), tunnel_number, npeers); + for (i = 0; i < npeers; i++) + fprintf (stdout, " * %s\n", GNUNET_i2s_full (&peers[i])); + fprintf (stdout, "\n"); +} + + +/** + * Method called to retrieve information about each tunnel the mesh peer + * is aware of. + * + * @param cls Closure. + * @param peer Peer in the tunnel's tree. + * @param parent Parent of the current peer. All 0 when peer is root. + * + */ +static void +tunnel_callback (void *cls, + const struct GNUNET_PeerIdentity *peer, + const struct GNUNET_PeerIdentity *parent) +{ +} + + +/** + * Call MESH's monitor API, get all tunnels known to peer. + * + * @param cls Closure (unused). + * @param tc TaskContext + */ +static void +get_tunnels (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + if (0 != (tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN)) + { + return; + } + GNUNET_MESH_get_tunnels (mh, &tunnels_callback, NULL); + if (GNUNET_YES != monitor_connections) + { + GNUNET_SCHEDULER_shutdown(); + } +} + +/** + * Call MESH's monitor API, get info of one tunnel. + * + * @param cls Closure (unused). + * @param tc TaskContext + */ +static void +show_tunnel (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct GNUNET_PeerIdentity pid; + + if (GNUNET_OK != + GNUNET_CRYPTO_hash_from_string (tunnel_id, &pid.hashPubKey)) + { + GNUNET_SCHEDULER_shutdown(); + return; + } + GNUNET_MESH_show_tunnel (mh, &pid, 0, tunnel_callback, NULL); +} + + +/** + * Main function that will be run by the scheduler. + * + * @param cls closure + * @param args remaining command-line arguments + * @param cfgfile name of the configuration file used (for saving, can be NULL!) + * @param cfg configuration + */ +static void +run (void *cls, char *const *args, const char *cfgfile, + const struct GNUNET_CONFIGURATION_Handle *cfg) +{ + static const struct GNUNET_MESH_MessageHandler handlers[] = { + {NULL, 0, 0} /* FIXME add option to monitor msg types */ + }; + GNUNET_MESH_ApplicationType apps = 0; /* FIXME add option to monitor apps */ + + if (args[0] != NULL) + { + FPRINTF (stderr, _("Invalid command line argument `%s'\n"), args[0]); + return; + } + mh = GNUNET_MESH_connect (cfg, + NULL, /* cls */ + NULL, /* nt */ + NULL, /* cleaner */ + handlers, + &apps); + if (NULL == mh) + GNUNET_SCHEDULER_add_now (shutdown_task, NULL); + else + sd = GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, + shutdown_task, NULL); + + if (NULL != tunnel_id) + GNUNET_SCHEDULER_add_now (&show_tunnel, NULL); + else + GNUNET_SCHEDULER_add_now (&get_tunnels, NULL); +} + + +/** + * The main function to obtain peer information. + * + * @param argc number of arguments from the command line + * @param argv command line arguments + * @return 0 ok, 1 on error + */ +int +main (int argc, char *const *argv) +{ + int res; + static const struct GNUNET_GETOPT_CommandLineOption options[] = { + {'m', "monitor", NULL, + gettext_noop ("provide information about all tunnels (continuously) NOT IMPLEMENTED"), /* FIXME */ + GNUNET_NO, &GNUNET_GETOPT_set_one, &monitor_connections}, + {'t', "tunnel", "OWNER_ID:TUNNEL_ID", + gettext_noop ("provide information about a particular tunnel"), + GNUNET_YES, &GNUNET_GETOPT_set_string, &tunnel_id}, + GNUNET_GETOPT_OPTION_END + }; + + if (GNUNET_OK != GNUNET_STRINGS_get_utf8_args (argc, argv, &argc, &argv)) + return 2; + + res = GNUNET_PROGRAM_run (argc, argv, "gnunet-mesh", + gettext_noop + ("Print information about mesh tunnels and peers."), + options, &run, NULL); + + GNUNET_free ((void *) argv); + + if (GNUNET_OK == res) + return 0; + else + return 1; +} + +/* end of gnunet-mesh.c */ diff --git a/src/mesh/gnunet-service-mesh-new.c b/src/mesh/gnunet-service-mesh-new.c new file mode 100644 index 0000000..82bfc5e --- /dev/null +++ b/src/mesh/gnunet-service-mesh-new.c @@ -0,0 +1,8483 @@ +/* + This file is part of GNUnet. + (C) 2001-2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @file mesh/gnunet-service-mesh.c + * @brief GNUnet MESH service + * @author Bartlomiej Polot + * + * STRUCTURE: + * - DATA STRUCTURES + * - GLOBAL VARIABLES + * - GENERAL HELPERS + * - PERIODIC FUNCTIONS + * - MESH NETWORK HANDLER HELPERS + * - MESH NETWORK HANDLES + * - MESH LOCAL HANDLER HELPERS + * - MESH LOCAL HANDLES + * - MAIN FUNCTIONS (main & run) + * + * TODO: + * - error reporting (CREATE/CHANGE/ADD/DEL?) -- new message! + * - partial disconnect reporting -- same as error reporting? + * - add ping message + * - relay corking down to core + * - set ttl relative to tree depth + * - Add data ACK count in path ACK + * - Make common GNUNET_MESH_Data header for unicast, to_orig, multicast + * TODO END + */ + +#include "platform.h" +#include "mesh.h" +#include "mesh_protocol.h" +#include "mesh_tunnel_tree.h" +#include "block_mesh.h" +#include "gnunet_dht_service.h" +#include "gnunet_statistics_service.h" +#include "gnunet_regex_lib.h" + +#define MESH_BLOOM_SIZE 128 + +#define MESH_DEBUG_DHT GNUNET_NO +#define MESH_DEBUG_CONNECTION GNUNET_NO +#define MESH_DEBUG_TIMING __LINUX__ && GNUNET_NO + +#define MESH_MAX_POLL_TIME GNUNET_TIME_relative_multiply (\ + GNUNET_TIME_UNIT_MINUTES,\ + 10) + +#if MESH_DEBUG_CONNECTION +#define DEBUG_CONN(...) GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, __VA_ARGS__) +#else +#define DEBUG_CONN(...) +#endif + +#if MESH_DEBUG_DHT +#define DEBUG_DHT(...) GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, __VA_ARGS__) +#else +#define DEBUG_DHT(...) +#endif + +#if MESH_DEBUG_TIMING +#include +double __sum; +uint64_t __count; +struct timespec __mesh_start; +struct timespec __mesh_end; +#define INTERVAL_START clock_gettime(CLOCK_PROCESS_CPUTIME_ID, &(__mesh_start)) +#define INTERVAL_END \ +do {\ + clock_gettime(CLOCK_PROCESS_CPUTIME_ID, &(__mesh_end));\ + double __diff = __mesh_end.tv_nsec - __mesh_start.tv_nsec;\ + if (__diff < 0) __diff += 1000000000;\ + __sum += __diff;\ + __count++;\ +} while (0) +#define INTERVAL_SHOW \ +if (0 < __count)\ + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "AVG process time: %f ns\n", __sum/__count) +#else +#define INTERVAL_START +#define INTERVAL_END +#define INTERVAL_SHOW +#endif + +/******************************************************************************/ +/************************ DATA STRUCTURES ****************************/ +/******************************************************************************/ + +/** FWD declaration */ +struct MeshPeerInfo; +struct MeshClient; + + +/** + * Struct representing a piece of data being sent to other peers + */ +struct MeshData +{ + /** Tunnel it belongs to. */ + struct MeshTunnel *t; + + /** How many remaining neighbors still hav't got it. */ + unsigned int reference_counter; + + /** How many remaining neighbors we need to send this to. */ + unsigned int total_out; + + /** Size of the data. */ + size_t data_len; + + /** Data itself */ + void *data; +}; + + +/** + * Struct containing info about a queued transmission to this peer + */ +struct MeshPeerQueue +{ + /** + * DLL next + */ + struct MeshPeerQueue *next; + + /** + * DLL previous + */ + struct MeshPeerQueue *prev; + + /** + * Peer this transmission is directed to. + */ + struct MeshPeerInfo *peer; + + /** + * Tunnel this message belongs to. + */ + struct MeshTunnel *tunnel; + + /** + * Pointer to info stucture used as cls. + */ + void *cls; + + /** + * Type of message + */ + uint16_t type; + + /** + * Size of the message + */ + size_t size; +}; + + +/** + * Struct to store regex information announced by clients. + */ +struct MeshRegexDescriptor +{ + /** + * Regular expression itself. + */ + char *regex; + + /** + * How many characters per edge can we squeeze? + */ + uint16_t compression; + + /** + * Handle to announce the regex. + */ + struct GNUNET_REGEX_announce_handle *h; +}; + + +/** + * Struct to keep information of searches of services described by a regex + * using a user-provided string service description. + */ +struct MeshRegexSearchInfo +{ + /** + * Which tunnel is this for + */ + struct MeshTunnel *t; + + /** + * User provided description of the searched service. + */ + char *description; + + /** + * Regex search handle. + */ + struct GNUNET_REGEX_search_handle *search_handle; + + /** + * Peer that is connecting via connect_by_string. When connected, free ctx. + */ + GNUNET_PEER_Id peer; + + /** + * Other peers that are found but not yet being connected to. + */ + GNUNET_PEER_Id *peers; + + /** + * Number of elements in peers. + */ + unsigned int n_peers; + + /** + * Next peer to try to connect to. + */ + unsigned int i_peer; + + /** + * Timeout for a connect attempt. + * When reached, try to connect to a different peer, if any. If not, + * try the same peer again. + */ + GNUNET_SCHEDULER_TaskIdentifier timeout; + +}; + + +/** + * Struct containing all info possibly needed to build a package when called + * back by core. + */ +struct MeshTransmissionDescriptor +{ + /** ID of the tunnel this packet travels in */ + struct MESH_TunnelID *origin; + + /** Who was this message being sent to */ + struct MeshPeerInfo *peer; + + /** Ultimate destination of the packet */ + GNUNET_PEER_Id destination; + + /** Data descriptor */ + struct MeshData* mesh_data; +}; + + +/** + * Struct containing all information regarding a given peer + */ +struct MeshPeerInfo +{ + /** + * ID of the peer + */ + GNUNET_PEER_Id id; + + /** + * Last time we heard from this peer + */ + struct GNUNET_TIME_Absolute last_contact; + + /** + * Task handler for delayed connect task; + */ + GNUNET_SCHEDULER_TaskIdentifier connect_task; + + /** + * Number of attempts to reconnect so far + */ + int n_reconnect_attempts; + + /** + * Paths to reach the peer, ordered by ascending hop count + */ + struct MeshPeerPath *path_head; + + /** + * Paths to reach the peer, ordered by ascending hop count + */ + struct MeshPeerPath *path_tail; + + /** + * Handle to stop the DHT search for a path to this peer + */ + struct GNUNET_DHT_GetHandle *dhtget; + + /** + * Closure given to the DHT GET + */ + struct MeshPathInfo *dhtgetcls; + + /** + * Array of tunnels this peer participates in + * (most probably a small amount, therefore not a hashmap) + * When the path to the peer changes, notify these tunnels to let them + * re-adjust their path trees. + */ + struct MeshTunnel **tunnels; + + /** + * Number of tunnels this peers participates in + */ + unsigned int ntunnels; + + /** + * Transmission queue to core DLL head + */ + struct MeshPeerQueue *queue_head; + + /** + * Transmission queue to core DLL tail + */ + struct MeshPeerQueue *queue_tail; + + /** + * How many messages are in the queue to this peer. + */ + unsigned int queue_n; + + /** + * Handle to for queued transmissions + */ + struct GNUNET_CORE_TransmitHandle *core_transmit; +}; + + +/** + * Globally unique tunnel identification (owner + number) + * DO NOT USE OVER THE NETWORK + */ +struct MESH_TunnelID +{ + /** + * Node that owns the tunnel + */ + GNUNET_PEER_Id oid; + + /** + * Tunnel number to differentiate all the tunnels owned by the node oid + * ( tid < GNUNET_MESH_LOCAL_TUNNEL_ID_CLI ) + */ + MESH_TunnelNumber tid; +}; + + +/** + * Struct containing all information regarding a tunnel + * For an intermediate node the improtant info used will be: + * - id Tunnel unique identification + * - paths[0] To know where to send it next + * - metainfo: ready, speeds, accounting + */ +struct MeshTunnel +{ + /** + * Tunnel ID + */ + struct MESH_TunnelID id; + + /** + * Local tunnel number ( >= GNUNET_MESH_LOCAL_TUNNEL_ID_CLI or 0 ) + */ + MESH_TunnelNumber local_tid; + + /** + * Local tunnel number for local destination clients (incoming number) + * ( >= GNUNET_MESH_LOCAL_TUNNEL_ID_SERV or 0). All clients share the same + * number. + */ + MESH_TunnelNumber local_tid_dest; + + /** + * Is the speed on the tunnel limited to the slowest peer? + */ + int speed_min; + + /** + * Is the tunnel bufferless (minimum latency)? + */ + int nobuffer; + + /** + * Packet ID of the last fwd packet seen (sent/retransmitted/received). + */ + uint32_t fwd_pid; + + /** + * Packet ID of the last bck packet sent (unique counter per hop). + */ + uint32_t bck_pid; + + /** + * SKIP value for this tunnel. + */ + uint32_t skip; + + /** + * Force sending ACK? Flag to allow duplicate ACK on POLL. + */ + int force_ack; + + /** + * MeshTunnelChildInfo of all children, indexed by GNUNET_PEER_Id. + * Contains the Flow Control info: FWD ACK value received, + * last BCK ACK sent, PID and SKIP values. + */ + struct GNUNET_CONTAINER_MultiHashMap *children_fc; + + /** + * Last ACK sent towards the origin (for traffic towards leaf node). + */ + uint32_t last_fwd_ack; + + /** + * BCK ACK value received from the hop towards the owner of the tunnel, + * (previous node / owner): up to what message PID can we sent back to him. + */ + uint32_t bck_ack; + + /** + * How many messages are in the forward queue (towards leaves). + */ + unsigned int fwd_queue_n; + + /** + * How many messages do we accept in the forward queue. + */ + unsigned int fwd_queue_max; + + /** + * How many messages are in the backward queue (towards origin). + */ + unsigned int bck_queue_n; + + /** + * How many messages do we accept in the backward queue. + */ + unsigned int bck_queue_max; + + /** + * Task to poll peer in case of a stall. + */ + GNUNET_SCHEDULER_TaskIdentifier fc_poll_bck; + + /** + * Last time the tunnel was used + */ + struct GNUNET_TIME_Absolute timestamp; + + /** + * Peers in the tunnel, indexed by PeerIdentity -> (MeshPeerInfo) + * containing peers added by id or by type, not intermediate peers. + */ + struct GNUNET_CONTAINER_MultiHashMap *peers; + + /** + * Number of peers that are connected and potentially ready to receive data + */ + unsigned int peers_ready; + + /** + * Number of peers that have been added to the tunnel + */ + unsigned int peers_total; + + /** + * Client owner of the tunnel, if any + */ + struct MeshClient *owner; + + /** + * Clients that have been informed about and want to stay in the tunnel. + */ + struct MeshClient **clients; + + /** + * Flow control info for each client. + */ + struct MeshTunnelClientInfo *clients_fc; + + /** + * Number of elements in clients/clients_fc + */ + unsigned int nclients; + + /** + * Clients that have been informed but requested to leave the tunnel. + */ + struct MeshClient **ignore; + + /** + * Number of elements in clients + */ + unsigned int nignore; + + /** + * Blacklisted peers + */ + GNUNET_PEER_Id *blacklisted; + + /** + * Number of elements in blacklisted + */ + unsigned int nblacklisted; + + /** + * Bloomfilter (for peer identities) to stop circular routes + */ + char bloomfilter[MESH_BLOOM_SIZE]; + + /** + * Tunnel paths + */ + struct MeshTunnelTree *tree; + + /** + * Application type we are looking for in this tunnel + */ + GNUNET_MESH_ApplicationType type; + + /** + * Used to search peers offering a service + */ + struct GNUNET_DHT_GetHandle *dht_get_type; + + /** + * Handle for the regex search for a connect_by_string + */ + struct MeshRegexSearchInfo *regex_search; + + /** + * Task to keep the used paths alive + */ + GNUNET_SCHEDULER_TaskIdentifier path_refresh_task; + + /** + * Task to destroy the tunnel after timeout + * + * FIXME: merge the two? a tunnel will have either + * a path refresh OR a timeout, never both! + */ + GNUNET_SCHEDULER_TaskIdentifier timeout_task; + + /** + * Flag to signal the destruction of the tunnel. + * If this is set GNUNET_YES the tunnel will be destroyed + * when the queue is empty. + */ + int destroy; + + /** + * Total messages pending for this tunnels, payload or not. + */ + unsigned int pending_messages; + + /** + * If the tunnel is empty, destoy it. + */ + GNUNET_SCHEDULER_TaskIdentifier delayed_destroy; +}; + + +/** + * Info about a child node in a tunnel, needed to perform flow control. + */ +struct MeshTunnelChildInfo +{ + /** + * ID of the child node. + */ + GNUNET_PEER_Id id; + + /** + * SKIP value. + */ + uint32_t skip; + + /** + * Last sent PID. + */ + uint32_t fwd_pid; + + /** + * Last received PID. + */ + uint32_t bck_pid; + + /** + * Maximum PID allowed (FWD ACK received). + */ + uint32_t fwd_ack; + + /** + * Last ACK sent to that child (BCK ACK). + */ + uint32_t bck_ack; + + /** + * Circular buffer pointing to MeshPeerQueue elements for all + * payload traffic going to this child. + * Size determined by the tunnel queue size (@c t->fwd_queue_max). + */ + struct MeshPeerQueue **send_buffer; + + /** + * Index of the oldest element in the send_buffer. + */ + unsigned int send_buffer_start; + + /** + * How many elements are already in the buffer. + */ + unsigned int send_buffer_n; + + /** + * Tunnel this info is about + */ + struct MeshTunnel *t; + + /** + * Task to poll peer in case of a stall. + */ + GNUNET_SCHEDULER_TaskIdentifier fc_poll; + + /** + * Time to use for next polling call. + */ + struct GNUNET_TIME_Relative fc_poll_time; +}; + + +/** + * Info about a leaf client of a tunnel, needed to perform flow control. + */ +struct MeshTunnelClientInfo +{ + /** + * PID of the last packet sent to the client (FWD). + */ + uint32_t fwd_pid; + + /** + * PID of the last packet received from the client (BCK). + */ + uint32_t bck_pid; + + /** + * Maximum PID allowed (FWD ACK received). + */ + uint32_t fwd_ack; + + /** + * Last ACK sent to that child (BCK ACK). + */ + uint32_t bck_ack; +}; + + + +/** + * Info collected during iteration of child nodes in order to get the ACK value + * for a tunnel. + */ +struct MeshTunnelChildIteratorContext +{ + /** + * Tunnel whose info is being collected. + */ + struct MeshTunnel *t; + + /** + * Is this context initialized? Is the value in max_child_ack valid? + */ + int init; + + /** + * Maximum child ACK so far. + */ + uint32_t max_child_ack; + + /** + * Number of children nodes + */ + unsigned int nchildren; +}; + + +/** + * Info needed to work with tunnel paths and peers + */ +struct MeshPathInfo +{ + /** + * Tunnel + */ + struct MeshTunnel *t; + + /** + * Neighbouring peer to whom we send the packet to + */ + struct MeshPeerInfo *peer; + + /** + * Path itself + */ + struct MeshPeerPath *path; +}; + + +/** + * Struct containing information about a client of the service + */ +struct MeshClient +{ + /** + * Linked list next + */ + struct MeshClient *next; + + /** + * Linked list prev + */ + struct MeshClient *prev; + + /** + * Tunnels that belong to this client, indexed by local id + */ + struct GNUNET_CONTAINER_MultiHashMap *own_tunnels; + + /** + * Tunnels this client has accepted, indexed by incoming local id + */ + struct GNUNET_CONTAINER_MultiHashMap *incoming_tunnels; + + /** + * Tunnels this client has rejected, indexed by incoming local id + */ + struct GNUNET_CONTAINER_MultiHashMap *ignore_tunnels; + /** + * Handle to communicate with the client + */ + struct GNUNET_SERVER_Client *handle; + + /** + * Applications that this client has claimed to provide + */ + struct GNUNET_CONTAINER_MultiHashMap *apps; + + /** + * Messages that this client has declared interest in + */ + struct GNUNET_CONTAINER_MultiHashMap *types; + + /** + * Whether the client is active or shutting down (don't send confirmations + * to a client that is shutting down. + */ + int shutting_down; + + /** + * ID of the client, mainly for debug messages + */ + unsigned int id; + + /** + * Regular expressions describing the services offered by this client. + */ + struct MeshRegexDescriptor *regexes; // FIXME regex add timeout? API to remove a regex? + + /** + * Number of regular expressions in regexes. + */ + unsigned int n_regex; + + /** + * Task to refresh all regular expresions in the DHT. + */ + GNUNET_SCHEDULER_TaskIdentifier regex_announce_task; + + /** + * Tmp store for partially retrieved regex. + */ + char *partial_regex; + +}; + + +/******************************************************************************/ +/************************ DEBUG FUNCTIONS ****************************/ +/******************************************************************************/ + +#if MESH_DEBUG +/** + * GNUNET_SCHEDULER_Task for printing a message after some operation is done + * @param cls string to print + * @param success GNUNET_OK if the PUT was transmitted, + * GNUNET_NO on timeout, + * GNUNET_SYSERR on disconnect from service + * after the PUT message was transmitted + * (so we don't know if it was received or not) + */ + +#if 0 +static void +mesh_debug (void *cls, int success) +{ + char *s = cls; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "%s (%d)\n", s, success); +} +#endif + +unsigned int debug_fwd_ack; +unsigned int debug_bck_ack; + +#endif + +/******************************************************************************/ +/*********************** GLOBAL VARIABLES ****************************/ +/******************************************************************************/ + +/************************** Configuration parameters **************************/ + +/** + * How often to send tunnel keepalives. Tunnels timeout after 4 missed. + */ +static struct GNUNET_TIME_Relative refresh_path_time; + +/** + * How often to PUT local application numbers in the DHT. + */ +static struct GNUNET_TIME_Relative app_announce_time; + +/** + * How often to PUT own ID in the DHT. + */ +static struct GNUNET_TIME_Relative id_announce_time; + +/** + * Maximum time allowed to connect to a peer found by string. + */ +static struct GNUNET_TIME_Relative connect_timeout; + +/** + * Default TTL for payload packets. + */ +static unsigned long long default_ttl; + +/** + * DHT replication level, see DHT API: GNUNET_DHT_get_start, GNUNET_DHT_put. + */ +static unsigned long long dht_replication_level; + +/** + * How many tunnels are we willing to maintain. + * Local tunnels are always allowed, even if there are more tunnels than max. + */ +static unsigned long long max_tunnels; + +/** + * How many messages *in total* are we willing to queue, divided by number of + * tunnels to get tunnel queue size. + */ +static unsigned long long max_msgs_queue; + +/** + * How many peers do we want to remember? + */ +static unsigned long long max_peers; + + +/*************************** Static global variables **************************/ + +/** + * Hostkey generation context + */ +static struct GNUNET_CRYPTO_RsaKeyGenerationContext *keygen; + +/** + * DLL with all the clients, head. + */ +static struct MeshClient *clients; + +/** + * DLL with all the clients, tail. + */ +static struct MeshClient *clients_tail; + +/** + * Tunnels known, indexed by MESH_TunnelID (MeshTunnel). + */ +static struct GNUNET_CONTAINER_MultiHashMap *tunnels; + +/** + * Number of tunnels known. + */ +static unsigned long long n_tunnels; + +/** + * Tunnels incoming, indexed by MESH_TunnelNumber + * (which is greater than GNUNET_MESH_LOCAL_TUNNEL_ID_SERV). + */ +static struct GNUNET_CONTAINER_MultiHashMap *incoming_tunnels; + +/** + * Peers known, indexed by PeerIdentity (MeshPeerInfo). + */ +static struct GNUNET_CONTAINER_MultiHashMap *peers; + +/* + * Handle to communicate with transport + */ +// static struct GNUNET_TRANSPORT_Handle *transport_handle; + +/** + * Handle to communicate with core. + */ +static struct GNUNET_CORE_Handle *core_handle; + +/** + * Handle to use DHT. + */ +static struct GNUNET_DHT_Handle *dht_handle; + +/** + * Handle to server. + */ +static struct GNUNET_SERVER_Handle *server_handle; + +/** + * Handle to the statistics service. + */ +static struct GNUNET_STATISTICS_Handle *stats; + +/** + * Notification context, to send messages to local clients. + */ +static struct GNUNET_SERVER_NotificationContext *nc; + +/** + * Local peer own ID (memory efficient handle). + */ +static GNUNET_PEER_Id myid; + +/** + * Local peer own ID (full value). + */ +static struct GNUNET_PeerIdentity my_full_id; + +/** + * Own private key. + */ +static struct GNUNET_CRYPTO_RsaPrivateKey *my_private_key; + +/** + * Own public key. + */ +static struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded my_public_key; + +/** + * Tunnel ID for the next created tunnel (global tunnel number). + */ +static MESH_TunnelNumber next_tid; + +/** + * Tunnel ID for the next incoming tunnel (local tunnel number). + */ +static MESH_TunnelNumber next_local_tid; + +/** + * All application types provided by this peer. + */ +static struct GNUNET_CONTAINER_MultiHashMap *applications; + +/** + * All message types clients of this peer are interested in. + */ +static struct GNUNET_CONTAINER_MultiHashMap *types; + +/** + * Task to periodically announce provided applications. + */ +GNUNET_SCHEDULER_TaskIdentifier announce_applications_task; + +/** + * Task to periodically announce itself in the network. + */ +GNUNET_SCHEDULER_TaskIdentifier announce_id_task; + +/** + * Next ID to assign to a client. + */ +unsigned int next_client_id; + + +/******************************************************************************/ +/*********************** DECLARATIONS **************************/ +/******************************************************************************/ + +/** + * Function to process paths received for a new peer addition. The recorded + * paths form the initial tunnel, which can be optimized later. + * Called on each result obtained for the DHT search. + * + * @param cls closure + * @param exp when will this value expire + * @param key key of the result + * @param type type of the result + * @param size number of bytes in data + * @param data pointer to the result data + */ +static void +dht_get_id_handler (void *cls, struct GNUNET_TIME_Absolute exp, + const struct GNUNET_HashCode * key, + const struct GNUNET_PeerIdentity *get_path, + unsigned int get_path_length, + const struct GNUNET_PeerIdentity *put_path, + unsigned int put_path_length, enum GNUNET_BLOCK_Type type, + size_t size, const void *data); + + +/** + * Retrieve the MeshPeerInfo stucture associated with the peer, create one + * and insert it in the appropiate structures if the peer is not known yet. + * + * @param peer Full identity of the peer. + * + * @return Existing or newly created peer info. + */ +static struct MeshPeerInfo * +peer_info_get (const struct GNUNET_PeerIdentity *peer); + + +/** + * Retrieve the MeshPeerInfo stucture associated with the peer, create one + * and insert it in the appropiate structures if the peer is not known yet. + * + * @param peer Short identity of the peer. + * + * @return Existing or newly created peer info. + */ +static struct MeshPeerInfo * +peer_info_get_short (const GNUNET_PEER_Id peer); + + +/** + * Try to establish a new connection to this peer. + * Use the best path for the given tunnel. + * If the peer doesn't have any path to it yet, try to get one. + * If the peer already has some path, send a CREATE PATH towards it. + * + * @param peer PeerInfo of the peer. + * @param t Tunnel for which to create the path, if possible. + */ +static void +peer_info_connect (struct MeshPeerInfo *peer, struct MeshTunnel *t); + + +/** + * Build a PeerPath from the paths returned from the DHT, reversing the paths + * to obtain a local peer -> destination path and interning the peer ids. + * + * @return Newly allocated and created path + */ +static struct MeshPeerPath * +path_build_from_dht (const struct GNUNET_PeerIdentity *get_path, + unsigned int get_path_length, + const struct GNUNET_PeerIdentity *put_path, + unsigned int put_path_length); + + +/** + * Adds a path to the peer_infos of all the peers in the path + * + * @param p Path to process. + * @param confirmed Whether we know if the path works or not. + */ +static void +path_add_to_peers (struct MeshPeerPath *p, int confirmed); + + +/** + * Add a peer to a tunnel, accomodating paths accordingly and initializing all + * needed rescources. + * If peer already exists, reevaluate shortest path and change if different. + * + * @param t Tunnel we want to add a new peer to + * @param peer PeerInfo of the peer being added + * + */ +static void +tunnel_add_peer (struct MeshTunnel *t, struct MeshPeerInfo *peer); + + +/** + * Removes an explicit path from a tunnel, freeing all intermediate nodes + * that are no longer needed, as well as nodes of no longer reachable peers. + * The tunnel itself is also destoyed if results in a remote empty tunnel. + * + * @param t Tunnel from which to remove the path. + * @param peer Short id of the peer which should be removed. + */ +static void +tunnel_delete_peer (struct MeshTunnel *t, GNUNET_PEER_Id peer); + + +/** + * Search for a tunnel by global ID using full PeerIdentities. + * + * @param oid owner of the tunnel. + * @param tid global tunnel number. + * + * @return tunnel handler, NULL if doesn't exist. + */ +static struct MeshTunnel * +tunnel_get (const struct GNUNET_PeerIdentity *oid, MESH_TunnelNumber tid); + + +/** + * Delete an active client from the tunnel. + * + * @param t Tunnel. + * @param c Client. + */ +static void +tunnel_delete_active_client (struct MeshTunnel *t, const struct MeshClient *c); + +/** + * Notify a tunnel that a connection has broken that affects at least + * some of its peers. + * + * @param t Tunnel affected. + * @param p1 Peer that got disconnected from p2. + * @param p2 Peer that got disconnected from p1. + * + * @return Short ID of the peer disconnected (either p1 or p2). + * 0 if the tunnel remained unaffected. + */ +static GNUNET_PEER_Id +tunnel_notify_connection_broken (struct MeshTunnel *t, GNUNET_PEER_Id p1, + GNUNET_PEER_Id p2); + + +/** + * Get the current ack value for a tunnel, for data going from root to leaves, + * taking in account the tunnel mode and the status of all children and clients. + * + * @param t Tunnel. + * + * @return Maximum PID allowed. + */ +static uint32_t +tunnel_get_fwd_ack (struct MeshTunnel *t); + + +/** + * Add a client to a tunnel, initializing all needed data structures. + * + * @param t Tunnel to which add the client. + * @param c Client which to add to the tunnel. + */ +static void +tunnel_add_client (struct MeshTunnel *t, struct MeshClient *c); + + +/** + * @brief Queue and pass message to core when possible. + * + * If type is payload (UNICAST, TO_ORIGIN, MULTICAST) checks for queue status + * and accounts for it. In case the queue is full, the message is dropped and + * a break issued. + * + * Otherwise, message is treated as internal and allowed to go regardless of + * queue status. + * + * @param cls Closure (@c type dependant). It will be used by queue_send to + * build the message to be sent if not already prebuilt. + * @param type Type of the message, 0 for a raw message. + * @param size Size of the message. + * @param dst Neighbor to send message to. + * @param t Tunnel this message belongs to. + */ +static void +queue_add (void *cls, uint16_t type, size_t size, + struct MeshPeerInfo *dst, struct MeshTunnel *t); + + +/** + * Free a transmission that was already queued with all resources + * associated to the request. + * + * @param queue Queue handler to cancel. + * @param clear_cls Is it necessary to free associated cls? + */ +static void +queue_destroy (struct MeshPeerQueue *queue, int clear_cls); + + +/** + * @brief Get the next transmittable message from the queue. + * + * This will be the head, except in the case of being a data packet + * not allowed by the destination peer. + * + * @param peer Destination peer. + * + * @return The next viable MeshPeerQueue element to send to that peer. + * NULL when there are no transmittable messages. + */ +struct MeshPeerQueue * +queue_get_next (const struct MeshPeerInfo *peer); + + +/** + * Core callback to write a queued packet to core buffer + * + * @param cls Closure (peer info). + * @param size Number of bytes available in buf. + * @param buf Where the to write the message. + * + * @return number of bytes written to buf + */ +static size_t +queue_send (void *cls, size_t size, void *buf); + +/******************************************************************************/ +/************************ REGEX INTEGRATION ****************************/ +/******************************************************************************/ + +/** + * Cancel a mesh regex search and free resources. + */ +static void +regex_cancel_search (struct MeshRegexSearchInfo *regex_search) +{ + GNUNET_REGEX_search_cancel (regex_search->search_handle); + if (0 < regex_search->n_peers) + GNUNET_free (regex_search->peers); + if (GNUNET_SCHEDULER_NO_TASK != regex_search->timeout) + { + GNUNET_SCHEDULER_cancel(regex_search->timeout); + } + GNUNET_free (regex_search); +} + + +/** + * Function called if the connect attempt to a peer found via + * connect_by_string times out. Try to connect to another peer, if any. + * Otherwise try to reconnect to the same peer. + * + * @param cls Closure (info about regex search). + * @param tc TaskContext. + */ +static void +regex_connect_timeout (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct MeshRegexSearchInfo *info = cls; + struct MeshPeerInfo *peer_info; + GNUNET_PEER_Id id; + GNUNET_PEER_Id old; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Regex connect timeout\n"); + info->timeout = GNUNET_SCHEDULER_NO_TASK; + if (0 != (tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN)) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " due to shutdown\n"); + return; + } + + old = info->peer; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " timed out: %u\n", old); + + if (0 < info->n_peers) + { + // Select next peer, put current in that spot. + id = info->peers[info->i_peer]; + info->peers[info->i_peer] = info->peer; + info->i_peer = (info->i_peer + 1) % info->n_peers; + } + else + { + // Try to connect to same peer again. + id = info->peer; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " trying: %u\n", id); + + peer_info = peer_info_get_short(id); + tunnel_add_peer (info->t, peer_info); + if (old != id) + tunnel_delete_peer (info->t, old); + peer_info_connect (peer_info, info->t); + info->timeout = GNUNET_SCHEDULER_add_delayed (connect_timeout, + ®ex_connect_timeout, + info); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Regex connect timeout END\n"); +} + + +/** + * Function to process DHT string to regex matching. + * Called on each result obtained for the DHT search. + * + * @param cls Closure provided in GNUNET_REGEX_search. + * @param id Peer providing a regex that matches the string. + * @param get_path Path of the get request. + * @param get_path_length Lenght of get_path. + * @param put_path Path of the put request. + * @param put_path_length Length of the put_path. + */ +static void +regex_found_handler (void *cls, + const struct GNUNET_PeerIdentity *id, + const struct GNUNET_PeerIdentity *get_path, + unsigned int get_path_length, + const struct GNUNET_PeerIdentity *put_path, + unsigned int put_path_length) +{ + struct MeshRegexSearchInfo *info = cls; + struct MeshPeerPath *p; + struct MeshPeerInfo *peer_info; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Got regex results from DHT!\n"); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " for %s\n", info->description); + + peer_info = peer_info_get (id); + p = path_build_from_dht (get_path, get_path_length, + put_path, put_path_length); + path_add_to_peers (p, GNUNET_NO); + path_destroy(p); + + tunnel_add_peer (info->t, peer_info); + peer_info_connect (peer_info, info->t); + if (0 == info->peer) + { + info->peer = peer_info->id; + } + else + { + GNUNET_array_append (info->peers, info->n_peers, peer_info->id); + } + + if (GNUNET_SCHEDULER_NO_TASK != info->timeout) + return; + + info->timeout = GNUNET_SCHEDULER_add_delayed (connect_timeout, + ®ex_connect_timeout, + info); + + return; +} + + +/** + * Store the regular expression describing a local service into the DHT. + * + * @param regex The regular expresion. + */ +static void +regex_put (struct MeshRegexDescriptor *regex) +{ + DEBUG_DHT (" regex_put (%s) start\n", regex->regex); + if (NULL == regex->h) + { + DEBUG_DHT (" first put, creating DFA\n"); + regex->h = GNUNET_REGEX_announce (dht_handle, + &my_full_id, + regex->regex, + regex->compression, + stats); + } + else + { + DEBUG_DHT (" not first put, using cached data\n"); + GNUNET_REGEX_reannounce (regex->h); + } + DEBUG_DHT (" regex_put (%s) end\n", regex->regex); +} + + +/** + * Periodically announce what applications are provided by local clients + * (by regex) + * + * @param cls closure + * @param tc task context + */ +static void +regex_announce (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct MeshClient *c = cls; + unsigned int i; + + c->regex_announce_task = GNUNET_SCHEDULER_NO_TASK; + if (0 != (tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN)) + return; + DEBUG_DHT ("Starting PUT for regex\n"); + for (i = 0; i < c->n_regex; i++) + regex_put (&c->regexes[i]); + c->regex_announce_task = GNUNET_SCHEDULER_add_delayed (app_announce_time, + ®ex_announce, + cls); + DEBUG_DHT ("Finished PUT for regex\n"); +} + + +/******************************************************************************/ +/************************ PERIODIC FUNCTIONS ****************************/ +/******************************************************************************/ + +/** + * Announce iterator over for each application provided by the peer + * + * @param cls closure + * @param key current key code + * @param value value in the hash map + * @return GNUNET_YES if we should continue to + * iterate, + * GNUNET_NO if not. + */ +static int +announce_application (void *cls, const struct GNUNET_HashCode * key, void *value) +{ + struct PBlock block; + struct MeshClient *c; + + block.id = my_full_id; + c = GNUNET_CONTAINER_multihashmap_get (applications, key); + GNUNET_assert(NULL != c); + block.type = (long) GNUNET_CONTAINER_multihashmap_get (c->apps, key); + if (0 == block.type) + { + GNUNET_break(0); + return GNUNET_YES; + } + block.type = htonl (block.type); + + GNUNET_break (NULL != + GNUNET_DHT_put (dht_handle, key, + dht_replication_level, + GNUNET_DHT_RO_RECORD_ROUTE | + GNUNET_DHT_RO_DEMULTIPLEX_EVERYWHERE, + GNUNET_BLOCK_TYPE_MESH_PEER_BY_TYPE, + sizeof (block), + (const char *) &block, + GNUNET_TIME_relative_to_absolute (GNUNET_TIME_UNIT_HOURS), /* FIXME: this should be an option */ + app_announce_time, NULL, NULL)); + return GNUNET_OK; +} + + +/** + * Periodically announce what applications are provided by local clients + * (by type) + * + * @param cls closure + * @param tc task context + */ +static void +announce_applications (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + if (0 != (tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN)) + { + announce_applications_task = GNUNET_SCHEDULER_NO_TASK; + return; + } + + DEBUG_DHT ("Starting PUT for apps\n"); + + GNUNET_CONTAINER_multihashmap_iterate (applications, &announce_application, + NULL); + announce_applications_task = + GNUNET_SCHEDULER_add_delayed (app_announce_time, &announce_applications, + cls); + DEBUG_DHT ("Finished PUT for apps\n"); +} + + +/** + * Periodically announce self id in the DHT + * + * @param cls closure + * @param tc task context + */ +static void +announce_id (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct PBlock block; + + if (0 != (tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN)) + { + announce_id_task = GNUNET_SCHEDULER_NO_TASK; + return; + } + /* TODO + * - Set data expiration in function of X + * - Adapt X to churn + */ + DEBUG_DHT ("DHT_put for ID %s started.\n", GNUNET_i2s (&my_full_id)); + + block.id = my_full_id; + block.type = htonl (0); + GNUNET_DHT_put (dht_handle, /* DHT handle */ + &my_full_id.hashPubKey, /* Key to use */ + dht_replication_level, /* Replication level */ + GNUNET_DHT_RO_RECORD_ROUTE | GNUNET_DHT_RO_DEMULTIPLEX_EVERYWHERE, /* DHT options */ + GNUNET_BLOCK_TYPE_MESH_PEER, /* Block type */ + sizeof (block), /* Size of the data */ + (const char *) &block, /* Data itself */ + GNUNET_TIME_UNIT_FOREVER_ABS, /* Data expiration */ + GNUNET_TIME_UNIT_FOREVER_REL, /* Retry time */ + NULL, /* Continuation */ + NULL); /* Continuation closure */ + announce_id_task = + GNUNET_SCHEDULER_add_delayed (id_announce_time, &announce_id, cls); +} + + +/******************************************************************************/ +/****************** GENERAL HELPER FUNCTIONS ************************/ +/******************************************************************************/ + +/** + * Decrements the reference counter and frees all resources if needed + * + * @param mesh_data Data Descriptor used in a multicast message. + * Freed no longer needed (last message). + */ +static void +data_descriptor_decrement_rc (struct MeshData *mesh_data) +{ + if (0 == --(mesh_data->reference_counter)) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Last copy!\n"); + GNUNET_free (mesh_data->data); + GNUNET_free (mesh_data); + } +} + + +/** + * Check if client has registered with the service and has not disconnected + * + * @param client the client to check + * + * @return non-NULL if client exists in the global DLL + */ +static struct MeshClient * +client_get (struct GNUNET_SERVER_Client *client) +{ + struct MeshClient *c; + + c = clients; + while (NULL != c) + { + if (c->handle == client) + return c; + c = c->next; + } + return NULL; +} + + +/** + * Checks if a given client has subscribed to certain message type + * + * @param message_type Type of message to check + * @param c Client to check + * + * @return GNUNET_YES or GNUNET_NO, depending on subscription status + * + * FIXME: use of crypto_hash slows it down + * The hash function alone takes 8-10us out of the ~55us for the whole + * process of retransmitting the message from one local client to another. + * Find faster implementation! + */ +static int +client_is_subscribed (uint16_t message_type, struct MeshClient *c) +{ + struct GNUNET_HashCode hc; + + if (NULL == c->types) + return GNUNET_NO; + + GNUNET_CRYPTO_hash (&message_type, sizeof (uint16_t), &hc); + return GNUNET_CONTAINER_multihashmap_contains (c->types, &hc); +} + + +/** + * Check whether client wants traffic from a tunnel. + * + * @param c Client to check. + * @param t Tunnel to be found. + * + * @return GNUNET_YES if client knows tunnel. + * + * TODO look in client hashmap + */ +static int +client_wants_tunnel (struct MeshClient *c, struct MeshTunnel *t) +{ + unsigned int i; + + for (i = 0; i < t->nclients; i++) + if (t->clients[i] == c) + return GNUNET_YES; + return GNUNET_NO; +} + + +/** + * Check whether client has been informed about a tunnel. + * + * @param c Client to check. + * @param t Tunnel to be found. + * + * @return GNUNET_YES if client knows tunnel. + * + * TODO look in client hashmap + */ +static int +client_knows_tunnel (struct MeshClient *c, struct MeshTunnel *t) +{ + unsigned int i; + + for (i = 0; i < t->nignore; i++) + if (t->ignore[i] == c) + return GNUNET_YES; + return client_wants_tunnel(c, t); +} + + +/** + * Marks a client as uninterested in traffic from the tunnel, updating both + * client and tunnel to reflect this. + * + * @param c Client that doesn't want traffic anymore. + * @param t Tunnel which should be ignored. + * + * FIXME when to delete an incoming tunnel? + */ +static void +client_ignore_tunnel (struct MeshClient *c, struct MeshTunnel *t) +{ + struct GNUNET_HashCode hash; + + GNUNET_CRYPTO_hash (&t->local_tid_dest, sizeof (MESH_TunnelNumber), &hash); + GNUNET_break (GNUNET_YES == + GNUNET_CONTAINER_multihashmap_remove (c->incoming_tunnels, + &hash, t)); + GNUNET_break (GNUNET_YES == + GNUNET_CONTAINER_multihashmap_put (c->ignore_tunnels, &hash, t, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_FAST)); + tunnel_delete_active_client (t, c); + GNUNET_array_append (t->ignore, t->nignore, c); +} + + +/** + * Deletes a tunnel from a client (either owner or destination). To be used on + * tunnel destroy, otherwise, use client_ignore_tunnel. + * + * @param c Client whose tunnel to delete. + * @param t Tunnel which should be deleted. + */ +static void +client_delete_tunnel (struct MeshClient *c, struct MeshTunnel *t) +{ + struct GNUNET_HashCode hash; + + if (c == t->owner) + { + GNUNET_CRYPTO_hash(&t->local_tid, sizeof (MESH_TunnelNumber), &hash); + GNUNET_assert (GNUNET_YES == + GNUNET_CONTAINER_multihashmap_remove (c->own_tunnels, + &hash, + t)); + } + else + { + GNUNET_CRYPTO_hash(&t->local_tid_dest, sizeof (MESH_TunnelNumber), &hash); + // FIXME XOR? + GNUNET_assert (GNUNET_YES == + GNUNET_CONTAINER_multihashmap_remove (c->incoming_tunnels, + &hash, + t) || + GNUNET_YES == + GNUNET_CONTAINER_multihashmap_remove (c->ignore_tunnels, + &hash, + t)); + } +} + + +/** + * Notify the owner of a tunnel that a peer has disconnected. + * + * @param c Client (owner of tunnel). + * @param t Tunnel this message is about. + * @param peer_id Short ID of the disconnected peer. + */ +void +client_notify_peer_disconnected (struct MeshClient *c, + struct MeshTunnel *t, + GNUNET_PEER_Id peer_id) +{ + struct GNUNET_MESH_PeerControl msg; + + if (NULL == t->owner || NULL == nc) + return; + + msg.header.size = htons (sizeof (msg)); + msg.header.type = htons (GNUNET_MESSAGE_TYPE_MESH_LOCAL_PEER_DEL); + msg.tunnel_id = htonl (t->local_tid); + GNUNET_PEER_resolve (peer_id, &msg.peer); + GNUNET_SERVER_notification_context_unicast (nc, t->owner->handle, + &msg.header, GNUNET_NO); +} + + +/** + * Send the message to all clients that have subscribed to its type + * + * @param msg Pointer to the message itself + * @param payload Pointer to the payload of the message. + * @param t The tunnel to whose clients this message goes. + * + * @return number of clients this message was sent to + */ +static unsigned int +send_subscribed_clients (const struct GNUNET_MessageHeader *msg, + const struct GNUNET_MessageHeader *payload, + struct MeshTunnel *t) +{ + struct MeshClient *c; + MESH_TunnelNumber *tid; + unsigned int count; + uint16_t type; + char cbuf[htons (msg->size)]; + + type = ntohs (payload->type); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Sending to clients...\n"); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "message of type %s\n", + GNUNET_MESH_DEBUG_M2S (type)); + + memcpy (cbuf, msg, sizeof (cbuf)); + switch (htons (msg->type)) + { + struct GNUNET_MESH_Unicast *uc; + struct GNUNET_MESH_Multicast *mc; + struct GNUNET_MESH_ToOrigin *to; + + case GNUNET_MESSAGE_TYPE_MESH_UNICAST: + uc = (struct GNUNET_MESH_Unicast *) cbuf; + tid = &uc->tid; + break; + case GNUNET_MESSAGE_TYPE_MESH_MULTICAST: + mc = (struct GNUNET_MESH_Multicast *) cbuf; + tid = &mc->tid; + break; + case GNUNET_MESSAGE_TYPE_MESH_TO_ORIGIN: + to = (struct GNUNET_MESH_ToOrigin *) cbuf; + tid = &to->tid; + break; + default: + GNUNET_break (0); + return 0; + } + + for (count = 0, c = clients; c != NULL; c = c->next) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " client %u\n", c->id); + if (client_is_subscribed (type, c)) + { + if (htons (msg->type) == GNUNET_MESSAGE_TYPE_MESH_TO_ORIGIN) + { + if (c != t->owner) + continue; + *tid = htonl (t->local_tid); + } + else + { + if (GNUNET_NO == client_knows_tunnel (c, t)) + { + /* This client doesn't know the tunnel */ + struct GNUNET_MESH_TunnelNotification tmsg; + struct GNUNET_HashCode hash; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " sending tunnel create\n"); + tmsg.header.size = htons (sizeof (tmsg)); + tmsg.header.type = htons (GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_CREATE); + GNUNET_PEER_resolve (t->id.oid, &tmsg.peer); + tmsg.tunnel_id = htonl (t->local_tid_dest); + tmsg.opt = 0; + if (GNUNET_YES == t->speed_min) + tmsg.opt |= MESH_TUNNEL_OPT_SPEED_MIN; + if (GNUNET_YES == t->nobuffer) + tmsg.opt |= MESH_TUNNEL_OPT_NOBUFFER; + GNUNET_SERVER_notification_context_unicast (nc, c->handle, + &tmsg.header, GNUNET_NO); + tunnel_add_client (t, c); + GNUNET_CRYPTO_hash (&t->local_tid_dest, sizeof (MESH_TunnelNumber), + &hash); + GNUNET_break (GNUNET_OK == GNUNET_CONTAINER_multihashmap_put ( + c->incoming_tunnels, &hash, t, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_FAST)); + } + *tid = htonl (t->local_tid_dest); + } + + /* Check if the client wants to get traffic from the tunnel */ + if (GNUNET_NO == client_wants_tunnel(c, t)) + continue; + count++; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " sending\n"); + GNUNET_SERVER_notification_context_unicast (nc, c->handle, + (struct GNUNET_MessageHeader + *) cbuf, GNUNET_NO); + } + } + + return count; +} + + +/** + * Notify the client that owns the tunnel that a peer has connected to it + * (the requested path to it has been confirmed). + * + * @param t Tunnel whose owner to notify + * @param id Short id of the peer that has connected + */ +static void +send_client_peer_connected (const struct MeshTunnel *t, const GNUNET_PEER_Id id) +{ + struct GNUNET_MESH_PeerControl pc; + + if (NULL == t->owner || GNUNET_YES == t->destroy) + return; + + pc.header.type = htons (GNUNET_MESSAGE_TYPE_MESH_LOCAL_PEER_ADD); + pc.header.size = htons (sizeof (struct GNUNET_MESH_PeerControl)); + pc.tunnel_id = htonl (t->local_tid); + GNUNET_PEER_resolve (id, &pc.peer); + GNUNET_SERVER_notification_context_unicast (nc, t->owner->handle, &pc.header, + GNUNET_NO); +} + + +/** + * Notify all clients (not depending on registration status) that the incoming + * tunnel is no longer valid. + * + * @param t Tunnel that was destroyed. + */ +static void +send_clients_tunnel_destroy (struct MeshTunnel *t) +{ + struct GNUNET_MESH_TunnelMessage msg; + + msg.header.size = htons (sizeof (msg)); + msg.header.type = htons (GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_DESTROY); + msg.tunnel_id = htonl (t->local_tid_dest); + GNUNET_SERVER_notification_context_broadcast (nc, &msg.header, GNUNET_NO); +} + + +/** + * Notify clients of tunnel disconnections, if needed. + * In case the origin disconnects, the destination clients get a tunnel destroy + * notification. If the last destination disconnects (only one remaining client + * in tunnel), the origin gets a (local ID) peer disconnected. + * Note that the function must be called BEFORE removing the client from + * the tunnel. + * + * @param t Tunnel that was destroyed. + * @param c Client that disconnected. + */ +static void +send_client_tunnel_disconnect (struct MeshTunnel *t, struct MeshClient *c) +{ + unsigned int i; + + if (c == t->owner) + { + struct GNUNET_MESH_TunnelMessage msg; + + msg.header.size = htons (sizeof (msg)); + msg.header.type = htons (GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_DESTROY); + msg.tunnel_id = htonl (t->local_tid_dest); + for (i = 0; i < t->nclients; i++) + GNUNET_SERVER_notification_context_unicast (nc, t->clients[i]->handle, + &msg.header, GNUNET_NO); + } + // FIXME when to disconnect an incoming tunnel? + else if (1 == t->nclients && NULL != t->owner) + { + struct GNUNET_MESH_PeerControl msg; + + msg.header.size = htons (sizeof (msg)); + msg.header.type = htons (GNUNET_MESSAGE_TYPE_MESH_LOCAL_PEER_DEL); + msg.tunnel_id = htonl (t->local_tid); + msg.peer = my_full_id; + GNUNET_SERVER_notification_context_unicast (nc, t->owner->handle, + &msg.header, GNUNET_NO); + } +} + + +/** + * Iterator over all the peers to remove the oldest not-used entry. + * + * @param cls Closure (unsued). + * @param key ID of the peer. + * @param value Peer_Info of the peer. + * + * FIXME implement + */ +static int +peer_info_timeout (void *cls, + const struct GNUNET_HashCode *key, + void *value) +{ + return GNUNET_YES; +} + +/** + * Retrieve the MeshPeerInfo stucture associated with the peer, create one + * and insert it in the appropiate structures if the peer is not known yet. + * + * @param peer Full identity of the peer. + * + * @return Existing or newly created peer info. + */ +static struct MeshPeerInfo * +peer_info_get (const struct GNUNET_PeerIdentity *peer) +{ + struct MeshPeerInfo *peer_info; + + peer_info = GNUNET_CONTAINER_multihashmap_get (peers, &peer->hashPubKey); + if (NULL == peer_info) + { + peer_info = + (struct MeshPeerInfo *) GNUNET_malloc (sizeof (struct MeshPeerInfo)); + if (GNUNET_CONTAINER_multihashmap_size (peers) > max_peers) + { + GNUNET_CONTAINER_multihashmap_iterate (peers, + &peer_info_timeout, + NULL); + } + GNUNET_CONTAINER_multihashmap_put (peers, &peer->hashPubKey, peer_info, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_FAST); + peer_info->id = GNUNET_PEER_intern (peer); + } + peer_info->last_contact = GNUNET_TIME_absolute_get(); + + return peer_info; +} + + +/** + * Retrieve the MeshPeerInfo stucture associated with the peer, create one + * and insert it in the appropiate structures if the peer is not known yet. + * + * @param peer Short identity of the peer. + * + * @return Existing or newly created peer info. + */ +static struct MeshPeerInfo * +peer_info_get_short (const GNUNET_PEER_Id peer) +{ + struct GNUNET_PeerIdentity id; + + GNUNET_PEER_resolve (peer, &id); + return peer_info_get (&id); +} + + +/** + * Iterator to remove the tunnel from the list of tunnels a peer participates + * in. + * + * @param cls Closure (tunnel info) + * @param key GNUNET_PeerIdentity of the peer (unused) + * @param value PeerInfo of the peer + * + * @return always GNUNET_YES, to keep iterating + */ +static int +peer_info_delete_tunnel (void *cls, const struct GNUNET_HashCode * key, void *value) +{ + struct MeshTunnel *t = cls; + struct MeshPeerInfo *peer = value; + unsigned int i; + + for (i = 0; i < peer->ntunnels; i++) + { + if (0 == + memcmp (&peer->tunnels[i]->id, &t->id, sizeof (struct MESH_TunnelID))) + { + peer->ntunnels--; + peer->tunnels[i] = peer->tunnels[peer->ntunnels]; + peer->tunnels = GNUNET_realloc (peer->tunnels, peer->ntunnels); + return GNUNET_YES; + } + } + return GNUNET_YES; +} + + +/** + * Core callback to write a pre-constructed data packet to core buffer + * + * @param cls Closure (MeshTransmissionDescriptor with data in "data" member). + * @param size Number of bytes available in buf. + * @param buf Where the to write the message. + * + * @return number of bytes written to buf + */ +static size_t +send_core_data_raw (void *cls, size_t size, void *buf) +{ + struct MeshTransmissionDescriptor *info = cls; + struct GNUNET_MessageHeader *msg; + size_t total_size; + + GNUNET_assert (NULL != info); + GNUNET_assert (NULL != info->mesh_data); + msg = (struct GNUNET_MessageHeader *) info->mesh_data->data; + total_size = ntohs (msg->size); + + if (total_size > size) + { + GNUNET_break (0); + return 0; + } + memcpy (buf, msg, total_size); + data_descriptor_decrement_rc (info->mesh_data); + GNUNET_free (info); + return total_size; +} + + +/** + * Sends an already built non-multicast message to a peer, + * properly registrating all used resources. + * + * @param message Message to send. Function makes a copy of it. + * @param peer Short ID of the neighbor whom to send the message. + * @param t Tunnel on which this message is transmitted. + */ +static void +send_prebuilt_message (const struct GNUNET_MessageHeader *message, + const struct GNUNET_PeerIdentity *peer, + struct MeshTunnel *t) +{ + struct MeshTransmissionDescriptor *info; + struct MeshPeerInfo *neighbor; + struct MeshPeerPath *p; + size_t size; + uint16_t type; + +// GNUNET_TRANSPORT_try_connect(); FIXME use? + + size = ntohs (message->size); + info = GNUNET_malloc (sizeof (struct MeshTransmissionDescriptor)); + info->mesh_data = GNUNET_malloc (sizeof (struct MeshData)); + info->mesh_data->data = GNUNET_malloc (size); + memcpy (info->mesh_data->data, message, size); + type = ntohs(message->type); + switch (type) + { + struct GNUNET_MESH_Unicast *m; + struct GNUNET_MESH_ToOrigin *to; + + case GNUNET_MESSAGE_TYPE_MESH_UNICAST: + m = (struct GNUNET_MESH_Unicast *) info->mesh_data->data; + m->ttl = htonl (ntohl (m->ttl) - 1); + break; + case GNUNET_MESSAGE_TYPE_MESH_TO_ORIGIN: + to = (struct GNUNET_MESH_ToOrigin *) info->mesh_data->data; + t->bck_pid++; + to->pid = htonl(t->bck_pid); + } + info->mesh_data->data_len = size; + info->mesh_data->reference_counter = 1; + info->mesh_data->total_out = 1; + neighbor = peer_info_get (peer); + for (p = neighbor->path_head; NULL != p; p = p->next) + { + if (2 >= p->length) + { + break; + } + } + if (NULL == p) + { +#if MESH_DEBUG + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " %s IS NOT DIRECTLY CONNECTED\n", + GNUNET_i2s(peer)); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " PATHS TO %s:\n", + GNUNET_i2s(peer)); + for (p = neighbor->path_head; NULL != p; p = p->next) + { + struct GNUNET_PeerIdentity debug_id; + unsigned int i; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " path with %u hops through:\n", + p->length); + for (i = 0; i < p->length; i++) + { + GNUNET_PEER_resolve(p->peers[i], &debug_id); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " hop %u: %s\n", + i, GNUNET_i2s(&debug_id)); + } + } +#endif + GNUNET_break (0); // FIXME sometimes fails (testing disconnect?) + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + " no direct connection to %s\n", + GNUNET_i2s (peer)); + GNUNET_free (info->mesh_data->data); + GNUNET_free (info->mesh_data); + GNUNET_free (info); + return; + } + info->peer = neighbor; + if (GNUNET_MESSAGE_TYPE_MESH_PATH_ACK == type) + type = 0; + queue_add (info, + type, + size, + neighbor, + t); +} + + +/** + * Sends a CREATE PATH message for a path to a peer, properly registrating + * all used resources. + * + * @param peer PeerInfo of the final peer for whom this path is being created. + * @param p Path itself. + * @param t Tunnel for which the path is created. + */ +static void +send_create_path (struct MeshPeerInfo *peer, struct MeshPeerPath *p, + struct MeshTunnel *t) +{ + struct GNUNET_PeerIdentity id; + struct MeshPathInfo *path_info; + struct MeshPeerInfo *neighbor; + + unsigned int i; + + if (NULL == p) + { + p = tree_get_path_to_peer (t->tree, peer->id); + if (NULL == p) + { + GNUNET_break (0); + return; + } + } + for (i = 0; i < p->length; i++) + { + if (p->peers[i] == myid) + break; + } + if (i >= p->length - 1) + { + path_destroy (p); + GNUNET_break (0); + return; + } + GNUNET_PEER_resolve (p->peers[i + 1], &id); + + path_info = GNUNET_malloc (sizeof (struct MeshPathInfo)); + path_info->path = p; + path_info->t = t; + neighbor = peer_info_get (&id); + path_info->peer = neighbor; + queue_add (path_info, + GNUNET_MESSAGE_TYPE_MESH_PATH_CREATE, + sizeof (struct GNUNET_MESH_ManipulatePath) + + (p->length * sizeof (struct GNUNET_PeerIdentity)), + neighbor, + t); +} + + +/** + * Sends a DESTROY PATH message to free resources for a path in a tunnel + * + * @param t Tunnel whose path to destroy. + * @param destination Short ID of the peer to whom the path to destroy. + */ +static void +send_destroy_path (struct MeshTunnel *t, GNUNET_PEER_Id destination) +{ + struct MeshPeerPath *p; + size_t size; + + p = tree_get_path_to_peer (t->tree, destination); + if (NULL == p) + { + GNUNET_break (0); + return; + } + size = sizeof (struct GNUNET_MESH_ManipulatePath); + size += p->length * sizeof (struct GNUNET_PeerIdentity); + { + struct GNUNET_MESH_ManipulatePath *msg; + struct GNUNET_PeerIdentity *pi; + char cbuf[size]; + unsigned int i; + + msg = (struct GNUNET_MESH_ManipulatePath *) cbuf; + msg->header.size = htons (size); + msg->header.type = htons (GNUNET_MESSAGE_TYPE_MESH_PATH_DESTROY); + msg->tid = htonl (t->id.tid); + pi = (struct GNUNET_PeerIdentity *) &msg[1]; + for (i = 0; i < p->length; i++) + { + GNUNET_PEER_resolve (p->peers[i], &pi[i]); + } + send_prebuilt_message (&msg->header, tree_get_first_hop (t->tree, destination), t); + } + path_destroy (p); +} + + +/** + * Sends a PATH ACK message in reponse to a received PATH_CREATE directed to us. + * + * @param t Tunnel which to confirm. + */ +static void +send_path_ack (struct MeshTunnel *t) +{ + struct MeshTransmissionDescriptor *info; + struct GNUNET_PeerIdentity id; + GNUNET_PEER_Id peer; + + peer = tree_get_predecessor (t->tree); + GNUNET_PEER_resolve (peer, &id); + info = GNUNET_malloc (sizeof (struct MeshTransmissionDescriptor)); + info->origin = &t->id; + info->peer = GNUNET_CONTAINER_multihashmap_get (peers, &id.hashPubKey); + GNUNET_assert (NULL != info->peer); + + queue_add (info, + GNUNET_MESSAGE_TYPE_MESH_PATH_ACK, + sizeof (struct GNUNET_MESH_PathACK), + info->peer, + t); +} + + +/** + * Try to establish a new connection to this peer. + * Use the best path for the given tunnel. + * If the peer doesn't have any path to it yet, try to get one. + * If the peer already has some path, send a CREATE PATH towards it. + * + * @param peer PeerInfo of the peer. + * @param t Tunnel for which to create the path, if possible. + */ +static void +peer_info_connect (struct MeshPeerInfo *peer, struct MeshTunnel *t) +{ + struct MeshPeerPath *p; + struct MeshPathInfo *path_info; + + if (NULL != peer->path_head) + { + p = tree_get_path_to_peer (t->tree, peer->id); + if (NULL == p) + { + GNUNET_break (0); + return; + } + + // FIXME always send create path to self + if (p->length > 1) + { + send_create_path (peer, p, t); + } + else + { + struct GNUNET_HashCode hash; + + path_destroy (p); + send_client_peer_connected (t, myid); + t->local_tid_dest = next_local_tid++; + GNUNET_CRYPTO_hash (&t->local_tid_dest, sizeof (MESH_TunnelNumber), + &hash); + if (GNUNET_OK != + GNUNET_CONTAINER_multihashmap_put (incoming_tunnels, &hash, t, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_FAST)) + { + GNUNET_break (0); + return; + } + } + } + else if (NULL == peer->dhtget) + { + struct GNUNET_PeerIdentity id; + + GNUNET_PEER_resolve (peer->id, &id); + path_info = GNUNET_malloc (sizeof (struct MeshPathInfo)); + path_info->peer = peer; + path_info->t = t; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " Starting DHT GET for peer %s\n", GNUNET_i2s (&id)); + peer->dhtgetcls = path_info; + peer->dhtget = GNUNET_DHT_get_start (dht_handle, /* handle */ + GNUNET_BLOCK_TYPE_MESH_PEER, /* type */ + &id.hashPubKey, /* key to search */ + dht_replication_level, /* replication level */ + GNUNET_DHT_RO_RECORD_ROUTE | + GNUNET_DHT_RO_DEMULTIPLEX_EVERYWHERE, + NULL, /* xquery */ // FIXME BLOOMFILTER + 0, /* xquery bits */ // FIXME BLOOMFILTER SIZE + &dht_get_id_handler, path_info); + } + /* Otherwise, there is no path but the DHT get is already started. */ +} + + +/** + * Task to delay the connection of a peer + * + * @param cls Closure (path info with tunnel and peer to connect). + * Will be free'd on exection. + * @param tc TaskContext + */ +static void +peer_info_connect_task (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct MeshPathInfo *path_info = cls; + + path_info->peer->connect_task = GNUNET_SCHEDULER_NO_TASK; + + if (0 != (GNUNET_SCHEDULER_REASON_SHUTDOWN & tc->reason)) + { + GNUNET_free (cls); + return; + } + peer_info_connect (path_info->peer, path_info->t); + GNUNET_free (cls); +} + + +/** + * Destroy the peer_info and free any allocated resources linked to it + * + * @param pi The peer_info to destroy. + * + * @return GNUNET_OK on success + */ +static int +peer_info_destroy (struct MeshPeerInfo *pi) +{ + struct GNUNET_PeerIdentity id; + struct MeshPeerPath *p; + struct MeshPeerPath *nextp; + + GNUNET_PEER_resolve (pi->id, &id); + GNUNET_PEER_change_rc (pi->id, -1); + + if (GNUNET_YES != + GNUNET_CONTAINER_multihashmap_remove (peers, &id.hashPubKey, pi)) + { + GNUNET_break (0); + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + "removing peer %s, not in hashmap\n", GNUNET_i2s (&id)); + } + if (NULL != pi->dhtget) + { + GNUNET_DHT_get_stop (pi->dhtget); + GNUNET_free (pi->dhtgetcls); + } + p = pi->path_head; + while (NULL != p) + { + nextp = p->next; + GNUNET_CONTAINER_DLL_remove (pi->path_head, pi->path_tail, p); + path_destroy (p); + p = nextp; + } + if (GNUNET_SCHEDULER_NO_TASK != pi->connect_task) + { + GNUNET_free (GNUNET_SCHEDULER_cancel (pi->connect_task)); + } + GNUNET_free (pi); + return GNUNET_OK; +} + + +/** + * Remove all paths that rely on a direct connection between p1 and p2 + * from the peer itself and notify all tunnels about it. + * + * @param peer PeerInfo of affected peer. + * @param p1 GNUNET_PEER_Id of one peer. + * @param p2 GNUNET_PEER_Id of another peer that was connected to the first and + * no longer is. + * + * TODO: optimize (see below) + */ +static void +peer_info_remove_path (struct MeshPeerInfo *peer, GNUNET_PEER_Id p1, + GNUNET_PEER_Id p2) +{ + struct MeshPeerPath *p; + struct MeshPeerPath *aux; + struct MeshPeerInfo *peer_d; + GNUNET_PEER_Id d; + unsigned int destroyed; + unsigned int best; + unsigned int cost; + unsigned int i; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "peer_info_remove_path\n"); + destroyed = 0; + p = peer->path_head; + while (NULL != p) + { + aux = p->next; + for (i = 0; i < (p->length - 1); i++) + { + if ((p->peers[i] == p1 && p->peers[i + 1] == p2) || + (p->peers[i] == p2 && p->peers[i + 1] == p1)) + { + GNUNET_CONTAINER_DLL_remove (peer->path_head, peer->path_tail, p); + path_destroy (p); + destroyed++; + break; + } + } + p = aux; + } + if (0 == destroyed) + return; + + for (i = 0; i < peer->ntunnels; i++) + { + d = tunnel_notify_connection_broken (peer->tunnels[i], p1, p2); + if (0 == d) + continue; + /* TODO + * Problem: one or more peers have been deleted from the tunnel tree. + * We don't know who they are to try to add them again. + * We need to try to find a new path for each of the disconnected peers. + * Some of them might already have a path to reach them that does not + * involve p1 and p2. Adding all anew might render in a better tree than + * the trivial immediate fix. + * + * Trivial immiediate fix: try to reconnect to the disconnected node. All + * its children will be reachable trough him. + */ + peer_d = peer_info_get_short (d); + best = UINT_MAX; + aux = NULL; + for (p = peer_d->path_head; NULL != p; p = p->next) + { + if ((cost = tree_get_path_cost (peer->tunnels[i]->tree, p)) < best) + { + best = cost; + aux = p; + } + } + if (NULL != aux) + { + /* No callback, as peer will be already disconnected and a connection + * scheduled by tunnel_notify_connection_broken. + */ + tree_add_path (peer->tunnels[i]->tree, aux, NULL, NULL); + } + else + { + peer_info_connect (peer_d, peer->tunnels[i]); + } + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "peer_info_remove_path END\n"); +} + + +/** + * Add the path to the peer and update the path used to reach it in case this + * is the shortest. + * + * @param peer_info Destination peer to add the path to. + * @param path New path to add. Last peer must be the peer in arg 1. + * Path will be either used of freed if already known. + * @param trusted Do we trust that this path is real? + */ +void +peer_info_add_path (struct MeshPeerInfo *peer_info, struct MeshPeerPath *path, + int trusted) +{ + struct MeshPeerPath *aux; + unsigned int l; + unsigned int l2; + + if ((NULL == peer_info) || (NULL == path)) + { + GNUNET_break (0); + path_destroy (path); + return; + } + if (path->peers[path->length - 1] != peer_info->id) + { + GNUNET_break (0); + path_destroy (path); + return; + } + if (path->length <= 2 && GNUNET_NO == trusted) + { + /* Only allow CORE to tell us about direct paths */ + path_destroy (path); + return; + } + GNUNET_assert (peer_info->id == path->peers[path->length - 1]); + for (l = 1; l < path->length; l++) + { + if (path->peers[l] == myid) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "shortening path by %u\n", l); + for (l2 = 0; l2 < path->length - l; l2++) + { + path->peers[l2] = path->peers[l + l2]; + } + path->length -= l; + l = 1; + path->peers = + GNUNET_realloc (path->peers, path->length * sizeof (GNUNET_PEER_Id)); + } + } +#if MESH_DEBUG + { + struct GNUNET_PeerIdentity id; + + GNUNET_PEER_resolve (peer_info->id, &id); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "adding path [%u] to peer %s\n", + path->length, GNUNET_i2s (&id)); + } +#endif + l = path_get_length (path); + if (0 == l) + { + GNUNET_free (path); + return; + } + + GNUNET_assert (peer_info->id == path->peers[path->length - 1]); + for (aux = peer_info->path_head; aux != NULL; aux = aux->next) + { + l2 = path_get_length (aux); + if (l2 > l) + { + GNUNET_CONTAINER_DLL_insert_before (peer_info->path_head, + peer_info->path_tail, aux, path); + return; + } + else + { + if (l2 == l && memcmp (path->peers, aux->peers, l) == 0) + { + path_destroy (path); + return; + } + } + } + GNUNET_CONTAINER_DLL_insert_tail (peer_info->path_head, peer_info->path_tail, + path); + return; +} + + +/** + * Add the path to the origin peer and update the path used to reach it in case + * this is the shortest. + * The path is given in peer_info -> destination, therefore we turn the path + * upside down first. + * + * @param peer_info Peer to add the path to, being the origin of the path. + * @param path New path to add after being inversed. + * @param trusted Do we trust that this path is real? + */ +static void +peer_info_add_path_to_origin (struct MeshPeerInfo *peer_info, + struct MeshPeerPath *path, int trusted) +{ + path_invert (path); + peer_info_add_path (peer_info, path, trusted); +} + + +/** + * Function called if the connection to the peer has been stalled for a while, + * possibly due to a missed ACK. Poll the peer about its ACK status. + * + * @param cls Closure (cinfo). + * @param tc TaskContext. + */ +static void +tunnel_poll (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct MeshTunnelChildInfo *cinfo = cls; + struct GNUNET_MESH_Poll msg; + struct GNUNET_PeerIdentity id; + struct MeshTunnel *t; + + cinfo->fc_poll = GNUNET_SCHEDULER_NO_TASK; + if (0 != (tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN)) + { + return; + } + + t = cinfo->t; + msg.header.type = htons (GNUNET_MESSAGE_TYPE_MESH_POLL); + msg.header.size = htons (sizeof (msg)); + msg.tid = htonl (t->id.tid); + GNUNET_PEER_resolve (t->id.oid, &msg.oid); + msg.last_ack = htonl (cinfo->fwd_ack); + + GNUNET_PEER_resolve (cinfo->id, &id); + send_prebuilt_message (&msg.header, &id, cinfo->t); + cinfo->fc_poll_time = GNUNET_TIME_relative_min ( + MESH_MAX_POLL_TIME, + GNUNET_TIME_relative_multiply (cinfo->fc_poll_time, 2)); + cinfo->fc_poll = GNUNET_SCHEDULER_add_delayed (cinfo->fc_poll_time, + &tunnel_poll, cinfo); +} + + +/** + * Build a PeerPath from the paths returned from the DHT, reversing the paths + * to obtain a local peer -> destination path and interning the peer ids. + * + * @return Newly allocated and created path + */ +static struct MeshPeerPath * +path_build_from_dht (const struct GNUNET_PeerIdentity *get_path, + unsigned int get_path_length, + const struct GNUNET_PeerIdentity *put_path, + unsigned int put_path_length) +{ + struct MeshPeerPath *p; + GNUNET_PEER_Id id; + int i; + + p = path_new (1); + p->peers[0] = myid; + GNUNET_PEER_change_rc (myid, 1); + i = get_path_length; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " GET has %d hops.\n", i); + for (i--; i >= 0; i--) + { + id = GNUNET_PEER_intern (&get_path[i]); + if (p->length > 0 && id == p->peers[p->length - 1]) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " Optimizing 1 hop out.\n"); + GNUNET_PEER_change_rc (id, -1); + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " Adding from GET: %s.\n", + GNUNET_i2s (&get_path[i])); + p->length++; + p->peers = GNUNET_realloc (p->peers, sizeof (GNUNET_PEER_Id) * p->length); + p->peers[p->length - 1] = id; + } + } + i = put_path_length; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " PUT has %d hops.\n", i); + for (i--; i >= 0; i--) + { + id = GNUNET_PEER_intern (&put_path[i]); + if (id == myid) + { + /* PUT path went through us, so discard the path up until now and start + * from here to get a much shorter (and loop-free) path. + */ + path_destroy (p); + p = path_new (0); + } + if (p->length > 0 && id == p->peers[p->length - 1]) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " Optimizing 1 hop out.\n"); + GNUNET_PEER_change_rc (id, -1); + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " Adding from PUT: %s.\n", + GNUNET_i2s (&put_path[i])); + p->length++; + p->peers = GNUNET_realloc (p->peers, sizeof (GNUNET_PEER_Id) * p->length); + p->peers[p->length - 1] = id; + } + } +#if MESH_DEBUG + if (get_path_length > 0) + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " (first of GET: %s)\n", + GNUNET_i2s (&get_path[0])); + if (put_path_length > 0) + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " (first of PUT: %s)\n", + GNUNET_i2s (&put_path[0])); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " In total: %d hops\n", + p->length); + for (i = 0; i < p->length; i++) + { + struct GNUNET_PeerIdentity peer_id; + + GNUNET_PEER_resolve (p->peers[i], &peer_id); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " %u: %s\n", p->peers[i], + GNUNET_i2s (&peer_id)); + } +#endif + return p; +} + + +/** + * Adds a path to the peer_infos of all the peers in the path + * + * @param p Path to process. + * @param confirmed Whether we know if the path works or not. + */ +static void +path_add_to_peers (struct MeshPeerPath *p, int confirmed) +{ + unsigned int i; + + /* TODO: invert and add */ + for (i = 0; i < p->length && p->peers[i] != myid; i++) /* skip'em */ ; + for (i++; i < p->length; i++) + { + struct MeshPeerInfo *aux; + struct MeshPeerPath *copy; + + aux = peer_info_get_short (p->peers[i]); + copy = path_duplicate (p); + copy->length = i + 1; + peer_info_add_path (aux, copy, GNUNET_NO); + } +} + + +/** + * Send keepalive packets for a peer + * + * @param cls Closure (tunnel for which to send the keepalive). + * @param tc Notification context. + * + * TODO: implement explicit multicast keepalive? + */ +static void +path_refresh (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc); + + +/** + * Search for a tunnel among the incoming tunnels + * + * @param tid the local id of the tunnel + * + * @return tunnel handler, NULL if doesn't exist + */ +static struct MeshTunnel * +tunnel_get_incoming (MESH_TunnelNumber tid) +{ + struct GNUNET_HashCode hash; + + GNUNET_assert (tid >= GNUNET_MESH_LOCAL_TUNNEL_ID_SERV); + GNUNET_CRYPTO_hash (&tid, sizeof (MESH_TunnelNumber), &hash); + return GNUNET_CONTAINER_multihashmap_get (incoming_tunnels, &hash); +} + + +/** + * Search for a tunnel among the tunnels for a client + * + * @param c the client whose tunnels to search in + * @param tid the local id of the tunnel + * + * @return tunnel handler, NULL if doesn't exist + */ +static struct MeshTunnel * +tunnel_get_by_local_id (struct MeshClient *c, MESH_TunnelNumber tid) +{ + if (tid >= GNUNET_MESH_LOCAL_TUNNEL_ID_SERV) + { + return tunnel_get_incoming (tid); + } + else + { + struct GNUNET_HashCode hash; + + GNUNET_CRYPTO_hash (&tid, sizeof (MESH_TunnelNumber), &hash); + return GNUNET_CONTAINER_multihashmap_get (c->own_tunnels, &hash); + } +} + + +/** + * Search for a tunnel by global ID using PEER_ID + * + * @param pi owner of the tunnel + * @param tid global tunnel number + * + * @return tunnel handler, NULL if doesn't exist + */ +static struct MeshTunnel * +tunnel_get_by_pi (GNUNET_PEER_Id pi, MESH_TunnelNumber tid) +{ + struct MESH_TunnelID id; + struct GNUNET_HashCode hash; + + id.oid = pi; + id.tid = tid; + + GNUNET_CRYPTO_hash (&id, sizeof (struct MESH_TunnelID), &hash); + return GNUNET_CONTAINER_multihashmap_get (tunnels, &hash); +} + + +/** + * Search for a tunnel by global ID using full PeerIdentities + * + * @param oid owner of the tunnel + * @param tid global tunnel number + * + * @return tunnel handler, NULL if doesn't exist + */ +static struct MeshTunnel * +tunnel_get (const struct GNUNET_PeerIdentity *oid, MESH_TunnelNumber tid) +{ + return tunnel_get_by_pi (GNUNET_PEER_search (oid), tid); +} + + +/** + * Delete an active client from the tunnel. + * + * @param t Tunnel. + * @param c Client. + */ +static void +tunnel_delete_active_client (struct MeshTunnel *t, const struct MeshClient *c) +{ + unsigned int i; + + for (i = 0; i < t->nclients; i++) + { + if (t->clients[i] == c) + { + t->clients[i] = t->clients[t->nclients - 1]; + t->clients_fc[i] = t->clients_fc[t->nclients - 1]; + GNUNET_array_grow (t->clients, t->nclients, t->nclients - 1); + t->nclients++; + GNUNET_array_grow (t->clients_fc, t->nclients, t->nclients - 1); + break; + } + } +} + + +/** + * Delete an ignored client from the tunnel. + * + * @param t Tunnel. + * @param c Client. + */ +static void +tunnel_delete_ignored_client (struct MeshTunnel *t, const struct MeshClient *c) +{ + unsigned int i; + + for (i = 0; i < t->nignore; i++) + { + if (t->ignore[i] == c) + { + t->ignore[i] = t->ignore[t->nignore - 1]; + GNUNET_array_grow (t->ignore, t->nignore, t->nignore - 1); + break; + } + } +} + + +/** + * Delete a client from the tunnel. It should be only done on + * client disconnection, otherwise use client_ignore_tunnel. + * + * @param t Tunnel. + * @param c Client. + */ +static void +tunnel_delete_client (struct MeshTunnel *t, const struct MeshClient *c) +{ + tunnel_delete_ignored_client (t, c); + tunnel_delete_active_client (t, c); +} + + +/** + * @brief Iterator to destroy MeshTunnelChildInfo of tunnel children. + * + * Destroys queue elements of all waiting transmissions and frees all memory + * used by the struct and its elements. + * + * @param cls Closure (tunnel info). + * @param key Hash of GNUNET_PEER_Id (unused). + * @param value MeshTunnelChildInfo of the child. + * + * @return always GNUNET_YES, to keep iterating + */ +static int +tunnel_destroy_child (void *cls, + const struct GNUNET_HashCode * key, + void *value) +{ + struct MeshTunnelChildInfo *cinfo = value; + struct MeshTunnel *t = cls; + struct MeshPeerQueue *q; + unsigned int c; + unsigned int i; + + for (c = 0; c < cinfo->send_buffer_n; c++) + { + i = (cinfo->send_buffer_start + c) % t->fwd_queue_max; + q = cinfo->send_buffer[i]; + cinfo->send_buffer[i] = NULL; + if (NULL != q) + queue_destroy (q, GNUNET_YES); + else + GNUNET_break (0); + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "%u %u\n", c, cinfo->send_buffer_n); + } + GNUNET_free_non_null (cinfo->send_buffer); + if (GNUNET_SCHEDULER_NO_TASK != cinfo->fc_poll) + { + GNUNET_SCHEDULER_cancel (cinfo->fc_poll); + cinfo->fc_poll = GNUNET_SCHEDULER_NO_TASK; + } + GNUNET_free (cinfo); + return GNUNET_YES; +} + + +/** + * Callback used to notify a client owner of a tunnel that a peer has + * disconnected, most likely because of a path change. + * + * @param cls Closure (tunnel this notification is about). + * @param peer_id Short ID of disconnected peer. + */ +void +tunnel_notify_client_peer_disconnected (void *cls, GNUNET_PEER_Id peer_id) +{ + struct MeshTunnel *t = cls; + struct MeshPeerInfo *peer; + struct MeshPathInfo *path_info; + + client_notify_peer_disconnected (t->owner, t, peer_id); + + peer = peer_info_get_short (peer_id); + path_info = GNUNET_malloc (sizeof (struct MeshPathInfo)); + path_info->peer = peer; + path_info->t = t; + peer->connect_task = GNUNET_SCHEDULER_add_now (&peer_info_connect_task, + path_info); +} + + +/** + * Add a peer to a tunnel, accomodating paths accordingly and initializing all + * needed rescources. + * If peer already exists, reevaluate shortest path and change if different. + * + * @param t Tunnel we want to add a new peer to + * @param peer PeerInfo of the peer being added + * + */ +static void +tunnel_add_peer (struct MeshTunnel *t, struct MeshPeerInfo *peer) +{ + struct GNUNET_PeerIdentity id; + struct MeshPeerPath *best_p; + struct MeshPeerPath *p; + unsigned int best_cost; + unsigned int cost; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "tunnel_add_peer\n"); + GNUNET_PEER_resolve (peer->id, &id); + if (GNUNET_NO == + GNUNET_CONTAINER_multihashmap_contains (t->peers, &id.hashPubKey)) + { + t->peers_total++; + GNUNET_array_append (peer->tunnels, peer->ntunnels, t); + GNUNET_assert (GNUNET_OK == + GNUNET_CONTAINER_multihashmap_put (t->peers, &id.hashPubKey, + peer, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_FAST)); + } + + if (NULL != (p = peer->path_head)) + { + best_p = p; + best_cost = tree_get_path_cost (t->tree, p); + while (NULL != p) + { + if ((cost = tree_get_path_cost (t->tree, p)) < best_cost) + { + best_cost = cost; + best_p = p; + } + p = p->next; + } + tree_add_path (t->tree, best_p, &tunnel_notify_client_peer_disconnected, t); + if (GNUNET_SCHEDULER_NO_TASK == t->path_refresh_task) + t->path_refresh_task = + GNUNET_SCHEDULER_add_delayed (refresh_path_time, &path_refresh, t); + } + else + { + /* Start a DHT get */ + peer_info_connect (peer, t); + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "tunnel_add_peer END\n"); +} + +/** + * Add a path to a tunnel which we don't own, just to remember the next hop. + * If destination node was already in the tunnel, the first hop information + * will be replaced with the new path. + * + * @param t Tunnel we want to add a new peer to + * @param p Path to add + * @param own_pos Position of local node in path. + * + */ +static void +tunnel_add_path (struct MeshTunnel *t, struct MeshPeerPath *p, + unsigned int own_pos) +{ + struct GNUNET_PeerIdentity id; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "tunnel_add_path\n"); + GNUNET_assert (0 != own_pos); + tree_add_path (t->tree, p, NULL, NULL); + if (own_pos < p->length - 1) + { + GNUNET_PEER_resolve (p->peers[own_pos + 1], &id); + tree_update_first_hops (t->tree, myid, &id); + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "tunnel_add_path END\n"); +} + +/** + * Add a client to a tunnel, initializing all needed data structures. + * + * @param t Tunnel to which add the client. + * @param c Client which to add to the tunnel. + */ +static void +tunnel_add_client (struct MeshTunnel *t, struct MeshClient *c) +{ + struct MeshTunnelClientInfo clinfo; + + GNUNET_array_append (t->clients, t->nclients, c); + clinfo.fwd_ack = t->fwd_pid + 1; + clinfo.bck_ack = t->nobuffer ? 1 : INITIAL_WINDOW_SIZE - 1; + clinfo.fwd_pid = t->fwd_pid; + clinfo.bck_pid = (uint32_t) -1; // Expected next: 0 + t->nclients--; + GNUNET_array_append (t->clients_fc, t->nclients, clinfo); +} + + +/** + * Notifies a tunnel that a connection has broken that affects at least + * some of its peers. Sends a notification towards the root of the tree. + * In case the peer is the owner of the tree, notifies the client that owns + * the tunnel and tries to reconnect. + * + * @param t Tunnel affected. + * @param p1 Peer that got disconnected from p2. + * @param p2 Peer that got disconnected from p1. + * + * @return Short ID of the peer disconnected (either p1 or p2). + * 0 if the tunnel remained unaffected. + */ +static GNUNET_PEER_Id +tunnel_notify_connection_broken (struct MeshTunnel *t, GNUNET_PEER_Id p1, + GNUNET_PEER_Id p2) +{ + GNUNET_PEER_Id pid; + + pid = + tree_notify_connection_broken (t->tree, p1, p2, + &tunnel_notify_client_peer_disconnected, + t); + if (myid != p1 && myid != p2) + { + return pid; + } + if (pid != myid) + { + if (tree_get_predecessor (t->tree) != 0) + { + /* We are the peer still connected, notify owner of the disconnection. */ + struct GNUNET_MESH_PathBroken msg; + struct GNUNET_PeerIdentity neighbor; + + msg.header.size = htons (sizeof (msg)); + msg.header.type = htons (GNUNET_MESSAGE_TYPE_MESH_PATH_BROKEN); + GNUNET_PEER_resolve (t->id.oid, &msg.oid); + msg.tid = htonl (t->id.tid); + msg.peer1 = my_full_id; + GNUNET_PEER_resolve (pid, &msg.peer2); + GNUNET_PEER_resolve (tree_get_predecessor (t->tree), &neighbor); + send_prebuilt_message (&msg.header, &neighbor, t); + } + } + return pid; +} + + +/** + * Send a multicast packet to a neighbor. + * + * @param cls Closure (Info about the multicast packet) + * @param neighbor_id Short ID of the neighbor to send the packet to. + */ +static void +tunnel_send_multicast_iterator (void *cls, GNUNET_PEER_Id neighbor_id) +{ + struct MeshData *mdata = cls; + struct MeshTransmissionDescriptor *info; + struct GNUNET_PeerIdentity neighbor; + struct GNUNET_MessageHeader *msg; + + info = GNUNET_malloc (sizeof (struct MeshTransmissionDescriptor)); + + info->mesh_data = mdata; + (mdata->reference_counter) ++; + info->destination = neighbor_id; + GNUNET_PEER_resolve (neighbor_id, &neighbor); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " sending to %s...\n", + GNUNET_i2s (&neighbor)); + info->peer = peer_info_get (&neighbor); + GNUNET_assert (NULL != info->peer); + msg = (struct GNUNET_MessageHeader *) mdata->data; + queue_add(info, + ntohs (msg->type), + info->mesh_data->data_len, + info->peer, + mdata->t); +} + + +/** + * Queue a message in a tunnel in multicast, sending a copy to each child node + * down the local one in the tunnel tree. + * + * @param t Tunnel in which to send the data. + * @param msg Message to be sent. + */ +static void +tunnel_send_multicast (struct MeshTunnel *t, + const struct GNUNET_MessageHeader *msg) +{ + struct MeshData *mdata; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " sending a multicast packet...\n"); + + mdata = GNUNET_malloc (sizeof (struct MeshData)); + mdata->data_len = ntohs (msg->size); + mdata->t = t; + mdata->data = GNUNET_malloc (mdata->data_len); + memcpy (mdata->data, msg, mdata->data_len); + if (ntohs (msg->type) == GNUNET_MESSAGE_TYPE_MESH_MULTICAST) + { + struct GNUNET_MESH_Multicast *mcast; + + mcast = (struct GNUNET_MESH_Multicast *) mdata->data; + if (t->fwd_queue_n >= t->fwd_queue_max) + { + GNUNET_break (0); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, " queue full!\n"); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + " message from %s!\n", + GNUNET_i2s(&mcast->oid)); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + " message at %s!\n", + GNUNET_i2s(&my_full_id)); + GNUNET_free (mdata->data); + GNUNET_free (mdata); + return; + } + t->fwd_queue_n++; + mcast->ttl = htonl (ntohl (mcast->ttl) - 1); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " data packet, ttl: %u\n", + ntohl (mcast->ttl)); + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " not a data packet, no ttl\n"); + } + + tree_iterate_children (t->tree, &tunnel_send_multicast_iterator, mdata); + if (mdata->reference_counter == 0) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " no one to send data to\n"); + GNUNET_free (mdata->data); + GNUNET_free (mdata); + if (ntohs (msg->type) == GNUNET_MESSAGE_TYPE_MESH_MULTICAST) + t->fwd_queue_n--; + } + else + { + mdata->total_out = mdata->reference_counter; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " sending a multicast packet done\n"); + return; +} + + +/** + * Increase the SKIP value of all peers that + * have not received a unicast message. + * + * @param cls Closure (ID of the peer that HAS received the message). + * @param key ID of the neighbor. + * @param value Information about the neighbor. + * + * @return GNUNET_YES to keep iterating. + */ +static int +tunnel_add_skip (void *cls, + const struct GNUNET_HashCode * key, + void *value) +{ + struct GNUNET_PeerIdentity *neighbor = cls; + struct MeshTunnelChildInfo *cinfo = value; + + /* TODO compare only pointers? key == neighbor? */ + if (0 == memcmp (&neighbor->hashPubKey, key, sizeof (struct GNUNET_HashCode))) + { + return GNUNET_YES; + } + cinfo->skip++; + return GNUNET_YES; +} + + +/** + * @brief Get neighbor's Flow Control information. + * + * Retrieves the MeshTunnelChildInfo containing Flow Control data about a direct + * descendant of the local node in a certain tunnel. + * If the info is not yet there (recently created path), creates the data struct + * and inserts it into the tunnel info, initialized to the current tunnel ACK + * values. + * + * @param t Tunnel related. + * @param peer Neighbor whose Flow Control info is needed. + * + * @return Neighbor's Flow Control info. + */ +static struct MeshTunnelChildInfo * +tunnel_get_neighbor_fc (struct MeshTunnel *t, + const struct GNUNET_PeerIdentity *peer) +{ + struct MeshTunnelChildInfo *cinfo; + + if (NULL == t->children_fc) + return NULL; + + cinfo = GNUNET_CONTAINER_multihashmap_get (t->children_fc, + &peer->hashPubKey); + if (NULL == cinfo) + { + uint32_t delta; + + cinfo = GNUNET_malloc (sizeof (struct MeshTunnelChildInfo)); + cinfo->id = GNUNET_PEER_intern (peer); + cinfo->skip = t->fwd_pid; + cinfo->t = t; + + delta = t->nobuffer ? 1 : INITIAL_WINDOW_SIZE; + cinfo->fwd_ack = t->fwd_pid + delta; + cinfo->bck_ack = delta; + cinfo->bck_pid = -1; + + cinfo->fc_poll = GNUNET_SCHEDULER_NO_TASK; + cinfo->fc_poll_time = GNUNET_TIME_UNIT_SECONDS; + + cinfo->send_buffer = + GNUNET_malloc (sizeof(struct MeshPeerQueue *) * t->fwd_queue_max); + + GNUNET_assert (GNUNET_OK == + GNUNET_CONTAINER_multihashmap_put (t->children_fc, + &peer->hashPubKey, + cinfo, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_FAST)); + } + return cinfo; +} + + +/** + * Get the Flow Control info of a client. + * + * @param t Tunnel on which to look. + * @param c Client whose ACK to get. + * + * @return ACK value. + */ +static struct MeshTunnelClientInfo * +tunnel_get_client_fc (struct MeshTunnel *t, + struct MeshClient *c) +{ + unsigned int i; + + for (i = 0; i < t->nclients; i++) + { + if (t->clients[i] != c) + continue; + return &t->clients_fc[i]; + } + GNUNET_assert (0); + return NULL; // avoid compiler / coverity complaints +} + + +/** + * Iterator to get the appropiate ACK value from all children nodes. + * + * @param cls Closue (tunnel). + * @param id Id of the child node. + */ +static void +tunnel_get_child_fwd_ack (void *cls, + GNUNET_PEER_Id id) +{ + struct GNUNET_PeerIdentity peer_id; + struct MeshTunnelChildInfo *cinfo; + struct MeshTunnelChildIteratorContext *ctx = cls; + struct MeshTunnel *t = ctx->t; + uint32_t ack; + + GNUNET_PEER_resolve (id, &peer_id); + cinfo = tunnel_get_neighbor_fc (t, &peer_id); + ack = cinfo->fwd_ack; + + ctx->nchildren++; + if (GNUNET_NO == ctx->init) + { + ctx->max_child_ack = ack; + ctx->init = GNUNET_YES; + } + + if (GNUNET_YES == t->speed_min) + { + ctx->max_child_ack = ctx->max_child_ack > ack ? ack : ctx->max_child_ack; + } + else + { + ctx->max_child_ack = ctx->max_child_ack > ack ? ctx->max_child_ack : ack; + } + +} + + +/** + * Get the maximum PID allowed to transmit to any + * tunnel child of the local peer, depending on the tunnel + * buffering/speed settings. + * + * @param t Tunnel. + * + * @return Maximum PID allowed (uint32 MAX), -1LL if node has no children. + */ +static int64_t +tunnel_get_children_fwd_ack (struct MeshTunnel *t) +{ + struct MeshTunnelChildIteratorContext ctx; + ctx.t = t; + ctx.max_child_ack = 0; + ctx.nchildren = 0; + ctx.init = GNUNET_NO; + tree_iterate_children (t->tree, tunnel_get_child_fwd_ack, &ctx); + + if (0 == ctx.nchildren) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " tunnel has no children, no FWD ACK\n"); + return -1LL; + } + + if (GNUNET_YES == t->nobuffer && GMC_is_pid_bigger(ctx.max_child_ack, t->fwd_pid)) + ctx.max_child_ack = t->fwd_pid + 1; // Might overflow, it's ok. + + return (int64_t) ctx.max_child_ack; +} + + +/** + * Set the FWD ACK value of a client in a particular tunnel. + * + * @param t Tunnel affected. + * @param c Client whose ACK to set. + * @param ack ACK value. + */ +static void +tunnel_set_client_fwd_ack (struct MeshTunnel *t, + struct MeshClient *c, + uint32_t ack) +{ + unsigned int i; + + for (i = 0; i < t->nclients; i++) + { + if (t->clients[i] != c) + continue; + t->clients_fc[i].fwd_ack = ack; + return; + } + GNUNET_break (0); +} + + +/** + * Get the highest ACK value of all clients in a particular tunnel, + * according to the buffering/speed settings. + * + * @param t Tunnel on which to look. + * + * @return Corresponding ACK value (max uint32_t). + * If no clients are suscribed, -1LL. + */ +static int64_t +tunnel_get_clients_fwd_ack (struct MeshTunnel *t) +{ + unsigned int i; + int64_t ack; + + if (0 == t->nclients) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " tunnel has no clients, no FWD ACK\n"); + return -1LL; + } + + for (ack = -1LL, i = 0; i < t->nclients; i++) + { + if (-1LL == ack || + (GNUNET_YES == t->speed_min && + GNUNET_YES == GMC_is_pid_bigger (ack, t->clients_fc[i].fwd_ack)) || + (GNUNET_NO == t->speed_min && + GNUNET_YES == GMC_is_pid_bigger (t->clients_fc[i].fwd_ack, ack))) + { + ack = t->clients_fc[i].fwd_ack; + } + } + + if (GNUNET_YES == t->nobuffer && GMC_is_pid_bigger(ack, t->fwd_pid)) + ack = (uint32_t) t->fwd_pid + 1; // Might overflow, it's ok. + + return (uint32_t) ack; +} + + +/** + * Get the current fwd ack value for a tunnel, taking in account the tunnel + * mode and the status of all children nodes. + * + * @param t Tunnel. + * + * @return Maximum PID allowed. + */ +static uint32_t +tunnel_get_fwd_ack (struct MeshTunnel *t) +{ + uint32_t ack; + uint32_t count; + uint32_t buffer_free; + int64_t child_ack; + int64_t client_ack; + + count = t->fwd_pid - t->skip; + buffer_free = t->fwd_queue_max - t->fwd_queue_n; + child_ack = tunnel_get_children_fwd_ack (t); + client_ack = tunnel_get_clients_fwd_ack (t); + if (GNUNET_YES == t->nobuffer) + { + ack = count; + if (-1LL == child_ack) + child_ack = client_ack; + if (-1LL == child_ack) + { + GNUNET_break (0); + client_ack = child_ack = ack; + } + } + else + { + ack = count + buffer_free; // Overflow? OK! + } + if (-1LL == child_ack) + { + // Node has no children, child_ack AND core buffer are irrelevant. + if (-1LL == client_ack) // No children AND no clients? Not good! + { + GNUNET_STATISTICS_update (stats, "# mesh acks with no target", + 1, GNUNET_NO); + + } + return (uint32_t) client_ack; + } + if (-1LL == client_ack) + { + client_ack = ack; + } + if (GNUNET_YES == t->speed_min) + { + ack = GMC_min_pid ((uint32_t) child_ack, ack); + ack = GMC_min_pid ((uint32_t) client_ack, ack); + } + else + { + ack = GMC_max_pid ((uint32_t) child_ack, ack); + ack = GMC_max_pid ((uint32_t) client_ack, ack); + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "c %u, bf %u, ch %lld, cl %lld, ACK: %u\n", + count, buffer_free, child_ack, client_ack, ack); + return ack; +} + + +/** + * Build a local ACK message and send it to a local client. + * + * @param t Tunnel on which to send the ACK. + * @param c Client to whom send the ACK. + * @param ack Value of the ACK. + */ +static void +send_local_ack (struct MeshTunnel *t, struct MeshClient *c, uint32_t ack) +{ + struct GNUNET_MESH_LocalAck msg; + + msg.header.size = htons (sizeof (msg)); + msg.header.type = htons (GNUNET_MESSAGE_TYPE_MESH_LOCAL_ACK); + msg.tunnel_id = htonl (t->owner == c ? t->local_tid : t->local_tid_dest); + msg.max_pid = htonl (ack); + GNUNET_SERVER_notification_context_unicast(nc, + c->handle, + &msg.header, + GNUNET_NO); +} + +/** + * Build an ACK message and queue it to send to the given peer. + * + * @param t Tunnel on which to send the ACK. + * @param peer Peer to whom send the ACK. + * @param ack Value of the ACK. + */ +static void +send_ack (struct MeshTunnel *t, struct GNUNET_PeerIdentity *peer, uint32_t ack) +{ + struct GNUNET_MESH_ACK msg; + + GNUNET_PEER_resolve (t->id.oid, &msg.oid); + msg.header.size = htons (sizeof (msg)); + msg.header.type = htons (GNUNET_MESSAGE_TYPE_MESH_ACK); + msg.pid = htonl (ack); + msg.tid = htonl (t->id.tid); + + send_prebuilt_message (&msg.header, peer, t); +} + + +/** + * Notify a the owner of a tunnel about how many more + * payload packages will we accept on a given tunnel. + * + * @param t Tunnel on which to send the ACK. + */ +static void +tunnel_send_client_fwd_ack (struct MeshTunnel *t) +{ + uint32_t ack; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Sending client FWD ACK on tunnel %X\n", + t->local_tid); + + ack = tunnel_get_fwd_ack (t); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " ack %u\n", ack); + if (t->last_fwd_ack == ack) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " same as last, not sending!\n"); + return; + } + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " sending!\n"); + t->last_fwd_ack = ack; + send_local_ack (t, t->owner, ack); +} + + +/** + * Send an ACK informing the predecessor about the available buffer space. + * In case there is no predecessor, inform the owning client. + * If buffering is off, send only on behalf of children or self if endpoint. + * If buffering is on, send when sent to children and buffer space is free. + * Note that although the name is fwd_ack, the FWD mean forward *traffic*, + * the ACK itself goes "back" (towards root). + * + * @param t Tunnel on which to send the ACK. + * @param type Type of message that triggered the ACK transmission. + */ +static void +tunnel_send_fwd_ack (struct MeshTunnel *t, uint16_t type) +{ + struct GNUNET_PeerIdentity id; + uint32_t ack; + + if (NULL != t->owner) + { + tunnel_send_client_fwd_ack (t); + return; + } + /* Is it after unicast / multicast retransmission? */ + switch (type) + { + case GNUNET_MESSAGE_TYPE_MESH_UNICAST: + case GNUNET_MESSAGE_TYPE_MESH_MULTICAST: + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "ACK due to FWD DATA retransmission\n"); + if (GNUNET_YES == t->nobuffer) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Not sending ACK, nobuffer\n"); + return; + } + break; + case GNUNET_MESSAGE_TYPE_MESH_ACK: + case GNUNET_MESSAGE_TYPE_MESH_LOCAL_ACK: + break; + case GNUNET_MESSAGE_TYPE_MESH_POLL: + t->force_ack = GNUNET_YES; + break; + default: + GNUNET_break (0); + } + + /* Check if we need to transmit the ACK */ + if (t->fwd_queue_max > t->fwd_queue_n * 4 && + GMC_is_pid_bigger(t->last_fwd_ack, t->fwd_pid) && + GNUNET_NO == t->force_ack) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Not sending ACK, buffer free\n"); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " t->qmax: %u, t->qn: %u\n", + t->fwd_queue_max, t->fwd_queue_n); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " t->pid: %u, t->ack: %u\n", + t->fwd_pid, t->last_fwd_ack); + return; + } + + /* Ok, ACK might be necessary, what PID to ACK? */ + ack = tunnel_get_fwd_ack (t); + + /* If speed_min and not all children have ack'd, dont send yet */ + if (ack == t->last_fwd_ack && GNUNET_NO == t->force_ack) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Not sending FWD ACK, not ready\n"); + return; + } + + t->last_fwd_ack = ack; + GNUNET_PEER_resolve (tree_get_predecessor (t->tree), &id); + send_ack (t, &id, ack); + debug_fwd_ack++; + t->force_ack = GNUNET_NO; +} + + +/** + * Iterator to send a child node a BCK ACK to allow him to send more + * to_origin data. + * + * @param cls Closure (tunnel). + * @param id Id of the child node. + */ +static void +tunnel_send_child_bck_ack (void *cls, + GNUNET_PEER_Id id) +{ + struct MeshTunnel *t = cls; + struct MeshTunnelChildInfo *cinfo; + struct GNUNET_PeerIdentity peer; + uint32_t ack; + + GNUNET_PEER_resolve (id, &peer); + cinfo = tunnel_get_neighbor_fc (t, &peer); + ack = cinfo->bck_pid + t->bck_queue_max - t->bck_queue_n; + + if (cinfo->bck_ack == ack && GNUNET_NO == t->force_ack) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " Not sending ACK, not needed\n"); + return; + } + cinfo->bck_ack = ack; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " Sending BCK ACK %u (last sent: %u)\n", + ack, cinfo->bck_ack); + send_ack (t, &peer, ack); +} + + +/** + * @brief Send BCK ACKs to clients to allow them more to_origin traffic + * + * Iterates over all clients and sends BCK ACKs to the ones that need it. + * + * FIXME fc: what happens if we have 2 clients but q_size is 1? + * - implement a size 1 buffer in each client_fc AND children_fc + * to hold at least 1 message per "child". + * problem: violates no buffer policy + * - ack 0 and make "children" poll for transmission slots + * problem: big overhead, extra latency even in low traffic + * settings + * + * @param t Tunnel on which to send the BCK ACKs. + */ +static void +tunnel_send_clients_bck_ack (struct MeshTunnel *t) +{ + unsigned int i; + unsigned int tunnel_delta; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " Sending BCK ACK to clients\n"); + + tunnel_delta = t->bck_queue_max - t->bck_queue_n; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " tunnel delta: %u\n", tunnel_delta); + + /* Find client whom to allow to send to origin (with lowest buffer space) */ + for (i = 0; i < t->nclients; i++) + { + struct MeshTunnelClientInfo *clinfo; + unsigned int delta; + + clinfo = &t->clients_fc[i]; + delta = clinfo->bck_ack - clinfo->bck_pid; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " client %u delta: %u\n", + t->clients[i]->id, delta); + + if ((GNUNET_NO == t->nobuffer && tunnel_delta > delta) || + (GNUNET_YES == t->nobuffer && 0 == delta)) + { + uint32_t ack; + + ack = clinfo->bck_pid; + ack += t->nobuffer ? 1 : tunnel_delta; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " sending ack to client %u: %u\n", + t->clients[i]->id, ack); + send_local_ack (t, t->clients[i], ack); + clinfo->bck_ack = ack; + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " not sending ack to client %u (td %u, d %u)\n", + t->clients[i]->id, tunnel_delta, delta); + } + } +} + + +/** + * Send an ACK informing the children nodes and destination clients about + * the available buffer space. + * If buffering is off, send only on behalf of root (can be self). + * If buffering is on, send when sent to predecessor and buffer space is free. + * Note that although the name is bck_ack, the BCK mean backwards *traffic*, + * the ACK itself goes "forward" (towards children/clients). + * + * @param t Tunnel on which to send the ACK. + * @param type Type of message that triggered the ACK transmission. + */ +static void +tunnel_send_bck_ack (struct MeshTunnel *t, uint16_t type) +{ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Sending BCK ACK on tunnel %u [%u] due to %s\n", + t->id.oid, t->id.tid, GNUNET_MESH_DEBUG_M2S(type)); + /* Is it after data to_origin retransmission? */ + switch (type) + { + case GNUNET_MESSAGE_TYPE_MESH_TO_ORIGIN: + if (GNUNET_YES == t->nobuffer) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " Not sending ACK, nobuffer\n"); + return; + } + break; + case GNUNET_MESSAGE_TYPE_MESH_ACK: + case GNUNET_MESSAGE_TYPE_MESH_LOCAL_ACK: + break; + case GNUNET_MESSAGE_TYPE_MESH_POLL: + t->force_ack = GNUNET_YES; + break; + default: + GNUNET_break (0); + } + + tunnel_send_clients_bck_ack (t); + tree_iterate_children (t->tree, &tunnel_send_child_bck_ack, t); + t->force_ack = GNUNET_NO; +} + + +/** + * @brief Re-initiate traffic to this peer if necessary. + * + * Check if there is traffic queued towards this peer + * and the core transmit handle is NULL (traffic was stalled). + * If so, call core tmt rdy. + * + * @param cls Closure (unused) + * @param peer_id Short ID of peer to which initiate traffic. + */ +static void +peer_unlock_queue(void *cls, GNUNET_PEER_Id peer_id) +{ + struct MeshPeerInfo *peer; + struct GNUNET_PeerIdentity id; + struct MeshPeerQueue *q; + size_t size; + + peer = peer_info_get_short(peer_id); + if (NULL != peer->core_transmit) + return; + + q = queue_get_next(peer); + if (NULL == q) + { + /* Might br multicast traffic already sent to this particular peer but + * not to other children in this tunnel. + * This way t->queue_n would be > 0 but the queue of this particular peer + * would be empty. + */ + return; + } + size = q->size; + GNUNET_PEER_resolve (peer->id, &id); + peer->core_transmit = + GNUNET_CORE_notify_transmit_ready(core_handle, + 0, + 0, + GNUNET_TIME_UNIT_FOREVER_REL, + &id, + size, + &queue_send, + peer); + return; +} + + +/** + * @brief Allow transmission of FWD traffic on this tunnel + * + * Check if there is traffic queued towards any children + * and the core transmit handle is NULL, and if so, call core tmt rdy. + * + * @param t Tunnel on which to unlock FWD traffic. + */ +static void +tunnel_unlock_fwd_queues (struct MeshTunnel *t) +{ + if (0 == t->fwd_queue_n) + return; + + tree_iterate_children (t->tree, &peer_unlock_queue, NULL); +} + + +/** + * @brief Allow transmission of BCK traffic on this tunnel + * + * Check if there is traffic queued towards the root of the tree + * and the core transmit handle is NULL, and if so, call core tmt rdy. + * + * @param t Tunnel on which to unlock BCK traffic. + */ +static void +tunnel_unlock_bck_queue (struct MeshTunnel *t) +{ + if (0 == t->bck_queue_n) + return; + + peer_unlock_queue(NULL, tree_get_predecessor(t->tree)); +} + + +/** + * Send a message to all peers in this tunnel that the tunnel is no longer + * valid. + * + * @param t The tunnel whose peers to notify. + * @param parent ID of the parent, in case the tree is already destroyed. + */ +static void +tunnel_send_destroy (struct MeshTunnel *t, GNUNET_PEER_Id parent) +{ + struct GNUNET_MESH_TunnelDestroy msg; + struct GNUNET_PeerIdentity id; + + msg.header.size = htons (sizeof (msg)); + msg.header.type = htons (GNUNET_MESSAGE_TYPE_MESH_TUNNEL_DESTROY); + GNUNET_PEER_resolve (t->id.oid, &msg.oid); + msg.tid = htonl (t->id.tid); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " sending tunnel destroy for tunnel: %s [%X]\n", + GNUNET_i2s (&msg.oid), t->id.tid); + if (tree_count_children(t->tree) > 0) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " sending multicast to children\n"); + tunnel_send_multicast (t, &msg.header); + } + if (0 == parent) + parent = tree_get_predecessor (t->tree); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " parent: %u\n", parent); + if (0 == parent) + return; + + GNUNET_PEER_resolve (parent, &id); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " sending back to %s\n", + GNUNET_i2s (&id)); + send_prebuilt_message (&msg.header, &id, t); +} + + +/** + * Cancel all transmissions towards a neighbor that belong to a certain tunnel. + * + * @param cls Closure (Tunnel which to cancel). + * @param neighbor_id Short ID of the neighbor to whom cancel the transmissions. + */ +static void +tunnel_cancel_queues (void *cls, GNUNET_PEER_Id neighbor_id) +{ + struct MeshTunnel *t = cls; + struct MeshPeerInfo *peer_info; + struct MeshPeerQueue *pq; + struct MeshPeerQueue *next; + + peer_info = peer_info_get_short (neighbor_id); + for (pq = peer_info->queue_head; NULL != pq; pq = next) + { + next = pq->next; + if (pq->tunnel == t) + { + if (GNUNET_MESSAGE_TYPE_MESH_MULTICAST == pq->type || + GNUNET_MESSAGE_TYPE_MESH_UNICAST == pq->type || + GNUNET_MESSAGE_TYPE_MESH_TO_ORIGIN == pq->type) + { + // Should have been removed on destroy children + GNUNET_break (0); + } + queue_destroy (pq, GNUNET_YES); + } + } + if (NULL == peer_info->queue_head && NULL != peer_info->core_transmit) + { + GNUNET_CORE_notify_transmit_ready_cancel(peer_info->core_transmit); + peer_info->core_transmit = NULL; + } +} + +/** + * Destroy the tunnel and free any allocated resources linked to it. + * + * @param t the tunnel to destroy + * + * @return GNUNET_OK on success + */ +static int +tunnel_destroy (struct MeshTunnel *t) +{ + struct MeshClient *c; + struct GNUNET_HashCode hash; + unsigned int i; + int r; + + if (NULL == t) + return GNUNET_OK; + + r = GNUNET_OK; + c = t->owner; +#if MESH_DEBUG + { + struct GNUNET_PeerIdentity id; + + GNUNET_PEER_resolve (t->id.oid, &id); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "destroying tunnel %s [%x]\n", + GNUNET_i2s (&id), t->id.tid); + if (NULL != c) + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " by client %u\n", c->id); + } +#endif + + GNUNET_CRYPTO_hash (&t->id, sizeof (struct MESH_TunnelID), &hash); + if (GNUNET_YES != GNUNET_CONTAINER_multihashmap_remove (tunnels, &hash, t)) + { + GNUNET_break (0); + r = GNUNET_SYSERR; + } + + if (NULL != c) + { + GNUNET_CRYPTO_hash (&t->local_tid, sizeof (MESH_TunnelNumber), &hash); + if (GNUNET_YES != + GNUNET_CONTAINER_multihashmap_remove (c->own_tunnels, &hash, t)) + { + GNUNET_break (0); + r = GNUNET_SYSERR; + } + } + + GNUNET_CRYPTO_hash (&t->local_tid_dest, sizeof (MESH_TunnelNumber), &hash); + for (i = 0; i < t->nclients; i++) + { + c = t->clients[i]; + if (GNUNET_YES != + GNUNET_CONTAINER_multihashmap_remove (c->incoming_tunnels, &hash, t)) + { + GNUNET_break (0); + r = GNUNET_SYSERR; + } + } + for (i = 0; i < t->nignore; i++) + { + c = t->ignore[i]; + if (GNUNET_YES != + GNUNET_CONTAINER_multihashmap_remove (c->ignore_tunnels, &hash, t)) + { + GNUNET_break (0); + r = GNUNET_SYSERR; + } + } + + (void) GNUNET_CONTAINER_multihashmap_remove (incoming_tunnels, &hash, t); + GNUNET_free_non_null (t->clients); + GNUNET_free_non_null (t->ignore); + GNUNET_free_non_null (t->clients_fc); + + if (NULL != t->peers) + { + GNUNET_CONTAINER_multihashmap_iterate (t->peers, &peer_info_delete_tunnel, + t); + GNUNET_CONTAINER_multihashmap_destroy (t->peers); + } + + GNUNET_CONTAINER_multihashmap_iterate (t->children_fc, + &tunnel_destroy_child, + t); + GNUNET_CONTAINER_multihashmap_destroy (t->children_fc); + t->children_fc = NULL; + + tree_iterate_children (t->tree, &tunnel_cancel_queues, t); + tree_destroy (t->tree); + + if (NULL != t->regex_search) + GNUNET_REGEX_search_cancel (t->regex_search->search_handle); + if (NULL != t->dht_get_type) + GNUNET_DHT_get_stop (t->dht_get_type); + if (GNUNET_SCHEDULER_NO_TASK != t->timeout_task) + GNUNET_SCHEDULER_cancel (t->timeout_task); + if (GNUNET_SCHEDULER_NO_TASK != t->path_refresh_task) + GNUNET_SCHEDULER_cancel (t->path_refresh_task); + + n_tunnels--; + GNUNET_STATISTICS_update (stats, "# tunnels", -1, GNUNET_NO); + GNUNET_free (t); + return r; +} + +#define TUNNEL_DESTROY_EMPTY_TIME GNUNET_TIME_UNIT_MILLISECONDS + +/** + * Tunnel is empty: destroy it. + * + * @param cls Closure (Tunnel). + * @param tc TaskContext. + */ +static void +tunnel_destroy_empty_delayed (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct MeshTunnel *t = cls; + + t->delayed_destroy = GNUNET_SCHEDULER_NO_TASK; + if (0 != (tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN)) + return; + + if (0 != t->nclients || + 0 != tree_count_children (t->tree)) + return; + + #if MESH_DEBUG + { + struct GNUNET_PeerIdentity id; + + GNUNET_PEER_resolve (t->id.oid, &id); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "executing destruction of empty tunnel %s [%X]\n", + GNUNET_i2s (&id), t->id.tid); + } + #endif + + tunnel_send_destroy (t, 0); + if (0 == t->pending_messages) + tunnel_destroy (t); + else + t->destroy = GNUNET_YES; +} + + +/** + * Schedule tunnel destruction if is empty and no new traffic comes in a time. + * + * @param t Tunnel to destroy if empty. + */ +static void +tunnel_destroy_empty (struct MeshTunnel *t) +{ + if (GNUNET_SCHEDULER_NO_TASK != t->delayed_destroy || + 0 != t->nclients || + 0 != tree_count_children (t->tree)) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "%u %u %u\n", + t->delayed_destroy, t->nclients, tree_count_children(t->tree)); + return; + } + + #if MESH_DEBUG + { + struct GNUNET_PeerIdentity id; + + GNUNET_PEER_resolve (t->id.oid, &id); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "scheduling destruction of empty tunnel %s [%X]\n", + GNUNET_i2s (&id), t->id.tid); + } + #endif + + t->delayed_destroy = + GNUNET_SCHEDULER_add_delayed (TUNNEL_DESTROY_EMPTY_TIME, + &tunnel_destroy_empty_delayed, + t); +} + + +/** + * Create a new tunnel + * + * @param owner Who is the owner of the tunnel (short ID). + * @param tid Tunnel Number of the tunnel. + * @param client Clients that owns the tunnel, NULL for foreign tunnels. + * @param local Tunnel Number for the tunnel, for the client point of view. + * + * @return A new initialized tunnel. NULL on error. + */ +static struct MeshTunnel * +tunnel_new (GNUNET_PEER_Id owner, + MESH_TunnelNumber tid, + struct MeshClient *client, + MESH_TunnelNumber local) +{ + struct MeshTunnel *t; + struct GNUNET_HashCode hash; + + if (n_tunnels >= max_tunnels && NULL == client) + return NULL; + + t = GNUNET_malloc (sizeof (struct MeshTunnel)); + t->id.oid = owner; + t->id.tid = tid; + t->fwd_queue_max = (max_msgs_queue / max_tunnels) + 1; + t->bck_queue_max = t->fwd_queue_max; + t->tree = tree_new (owner); + t->owner = client; + t->fwd_pid = (uint32_t) -1; // Next (expected) = 0 + t->bck_pid = (uint32_t) -1; // Next (expected) = 0 + t->bck_ack = INITIAL_WINDOW_SIZE - 1; + t->last_fwd_ack = INITIAL_WINDOW_SIZE - 1; + t->local_tid = local; + t->children_fc = GNUNET_CONTAINER_multihashmap_create (8, GNUNET_NO); + n_tunnels++; + GNUNET_STATISTICS_update (stats, "# tunnels", 1, GNUNET_NO); + + GNUNET_CRYPTO_hash (&t->id, sizeof (struct MESH_TunnelID), &hash); + if (GNUNET_OK != + GNUNET_CONTAINER_multihashmap_put (tunnels, &hash, t, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY)) + { + GNUNET_break (0); + tunnel_destroy (t); + if (NULL != client) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client->handle, GNUNET_SYSERR); + } + return NULL; + } + + if (NULL != client) + { + GNUNET_CRYPTO_hash (&t->local_tid, sizeof (MESH_TunnelNumber), &hash); + if (GNUNET_OK != + GNUNET_CONTAINER_multihashmap_put (client->own_tunnels, &hash, t, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY)) + { + tunnel_destroy (t); + GNUNET_break (0); + GNUNET_SERVER_receive_done (client->handle, GNUNET_SYSERR); + return NULL; + } + } + + return t; +} + +/** + * Callback when removing children from a tunnel tree. Notify owner. + * + * @param cls Closure (tunnel). + * @param peer_id Short ID of the peer deleted. + */ +void +tunnel_child_removed (void *cls, GNUNET_PEER_Id peer_id) +{ + struct MeshTunnel *t = cls; + + client_notify_peer_disconnected (t->owner, t, peer_id); +} + +/** + * Removes an explicit path from a tunnel, freeing all intermediate nodes + * that are no longer needed, as well as nodes of no longer reachable peers. + * The tunnel itself is also destoyed if results in a remote empty tunnel. + * + * @param t Tunnel from which to remove the path. + * @param peer Short id of the peer which should be removed. + */ +static void +tunnel_delete_peer (struct MeshTunnel *t, GNUNET_PEER_Id peer) +{ + int r; + + r = tree_del_peer (t->tree, peer, &tunnel_child_removed, t); + if (GNUNET_NO == r) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Tunnel %u [%u] has no more nodes\n", + t->id.oid, t->id.tid); + } +} + + +/** + * tunnel_destroy_iterator: iterator for deleting each tunnel that belongs to a + * client when the client disconnects. If the client is not the owner, the + * owner will get notified if no more clients are in the tunnel and the client + * get removed from the tunnel's list. + * + * @param cls closure (client that is disconnecting) + * @param key the hash of the local tunnel id (used to access the hashmap) + * @param value the value stored at the key (tunnel to destroy) + * + * @return GNUNET_OK, keep iterating. + */ +static int +tunnel_destroy_iterator (void *cls, + const struct GNUNET_HashCode * key, + void *value) +{ + struct MeshTunnel *t = value; + struct MeshClient *c = cls; + + send_client_tunnel_disconnect (t, c); + if (c != t->owner) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Client %u is destination.\n", c->id); + tunnel_delete_client (t, c); + client_delete_tunnel (c, t); + tunnel_destroy_empty (t); + return GNUNET_OK; + } + tunnel_send_destroy (t, 0); + t->owner = NULL; + t->destroy = GNUNET_YES; + + return GNUNET_OK; +} + + +/** + * Timeout function, destroys tunnel if called + * + * @param cls Closure (tunnel to destroy). + * @param tc TaskContext + */ +static void +tunnel_timeout (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct MeshTunnel *t = cls; + struct GNUNET_PeerIdentity id; + + t->timeout_task = GNUNET_SCHEDULER_NO_TASK; + if (0 != (tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN)) + return; + GNUNET_PEER_resolve(t->id.oid, &id); + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + "Tunnel %s [%X] timed out. Destroying.\n", + GNUNET_i2s(&id), t->id.tid); + send_clients_tunnel_destroy (t); + tunnel_destroy (t); +} + +/** + * Resets the tunnel timeout. Starts it if no timeout was running. + * + * @param t Tunnel whose timeout to reset. + * + * TODO use heap to improve efficiency of scheduler. + */ +static void +tunnel_reset_timeout (struct MeshTunnel *t) +{ + if (GNUNET_SCHEDULER_NO_TASK != t->timeout_task) + GNUNET_SCHEDULER_cancel (t->timeout_task); + t->timeout_task = + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply + (refresh_path_time, 4), &tunnel_timeout, t); +} + + +/******************************************************************************/ +/**************** MESH NETWORK HANDLER HELPERS ***********************/ +/******************************************************************************/ + +/** + * Function to send a create path packet to a peer. + * + * @param cls closure + * @param size number of bytes available in buf + * @param buf where the callee should write the message + * @return number of bytes written to buf + */ +static size_t +send_core_path_create (void *cls, size_t size, void *buf) +{ + struct MeshPathInfo *info = cls; + struct GNUNET_MESH_ManipulatePath *msg; + struct GNUNET_PeerIdentity *peer_ptr; + struct MeshTunnel *t = info->t; + struct MeshPeerPath *p = info->path; + size_t size_needed; + uint32_t opt; + int i; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "CREATE PATH sending...\n"); + size_needed = + sizeof (struct GNUNET_MESH_ManipulatePath) + + p->length * sizeof (struct GNUNET_PeerIdentity); + + if (size < size_needed || NULL == buf) + { + GNUNET_break (0); + return 0; + } + msg = (struct GNUNET_MESH_ManipulatePath *) buf; + msg->header.size = htons (size_needed); + msg->header.type = htons (GNUNET_MESSAGE_TYPE_MESH_PATH_CREATE); + msg->tid = ntohl (t->id.tid); + + opt = 0; + if (GNUNET_YES == t->speed_min) + opt |= MESH_TUNNEL_OPT_SPEED_MIN; + if (GNUNET_YES == t->nobuffer) + opt |= MESH_TUNNEL_OPT_NOBUFFER; + msg->opt = htonl(opt); + msg->reserved = 0; + + peer_ptr = (struct GNUNET_PeerIdentity *) &msg[1]; + for (i = 0; i < p->length; i++) + { + GNUNET_PEER_resolve (p->peers[i], peer_ptr++); + } + + path_destroy (p); + GNUNET_free (info); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "CREATE PATH (%u bytes long) sent!\n", size_needed); + return size_needed; +} + + +/** + * Fill the core buffer + * + * @param cls closure (data itself) + * @param size number of bytes available in buf + * @param buf where the callee should write the message + * + * @return number of bytes written to buf + */ +static size_t +send_core_data_multicast (void *cls, size_t size, void *buf) +{ + struct MeshTransmissionDescriptor *info = cls; + size_t total_size; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Multicast callback.\n"); + GNUNET_assert (NULL != info); + GNUNET_assert (NULL != info->peer); + total_size = info->mesh_data->data_len; + GNUNET_assert (total_size < GNUNET_SERVER_MAX_MESSAGE_SIZE); + + if (total_size > size) + { + GNUNET_break (0); + return 0; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " copying data...\n"); + memcpy (buf, info->mesh_data->data, total_size); +#if MESH_DEBUG + { + struct GNUNET_MESH_Multicast *mc; + struct GNUNET_MessageHeader *mh; + + mh = buf; + if (ntohs (mh->type) == GNUNET_MESSAGE_TYPE_MESH_MULTICAST) + { + mc = (struct GNUNET_MESH_Multicast *) mh; + mh = (struct GNUNET_MessageHeader *) &mc[1]; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " multicast, payload type %s\n", + GNUNET_MESH_DEBUG_M2S (ntohs (mh->type))); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " multicast, payload size %u\n", ntohs (mh->size)); + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " type %s\n", + GNUNET_MESH_DEBUG_M2S (ntohs (mh->type))); + } + } +#endif + data_descriptor_decrement_rc (info->mesh_data); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "freeing info...\n"); + GNUNET_free (info); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "return %u\n", total_size); + return total_size; +} + + +/** + * Creates a path ack message in buf and frees all unused resources. + * + * @param cls closure (MeshTransmissionDescriptor) + * @param size number of bytes available in buf + * @param buf where the callee should write the message + * @return number of bytes written to buf + */ +static size_t +send_core_path_ack (void *cls, size_t size, void *buf) +{ + struct MeshTransmissionDescriptor *info = cls; + struct GNUNET_MESH_PathACK *msg = buf; + + GNUNET_assert (NULL != info); + if (sizeof (struct GNUNET_MESH_PathACK) > size) + { + GNUNET_break (0); + return 0; + } + msg->header.size = htons (sizeof (struct GNUNET_MESH_PathACK)); + msg->header.type = htons (GNUNET_MESSAGE_TYPE_MESH_PATH_ACK); + GNUNET_PEER_resolve (info->origin->oid, &msg->oid); + msg->tid = htonl (info->origin->tid); + msg->peer_id = my_full_id; + + GNUNET_free (info); + /* TODO add signature */ + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "PATH ACK sent!\n"); + return sizeof (struct GNUNET_MESH_PathACK); +} + + +/** + * Free a transmission that was already queued with all resources + * associated to the request. + * + * @param queue Queue handler to cancel. + * @param clear_cls Is it necessary to free associated cls? + */ +static void +queue_destroy (struct MeshPeerQueue *queue, int clear_cls) +{ + struct MeshTransmissionDescriptor *dd; + struct MeshPathInfo *path_info; + struct MeshTunnelChildInfo *cinfo; + struct GNUNET_PeerIdentity id; + unsigned int i; + unsigned int max; + + if (GNUNET_YES == clear_cls) + { + switch (queue->type) + { + case GNUNET_MESSAGE_TYPE_MESH_TUNNEL_DESTROY: + GNUNET_log (GNUNET_ERROR_TYPE_INFO, " cancelling TUNNEL_DESTROY\n"); + GNUNET_break (GNUNET_YES == queue->tunnel->destroy); + /* fall through */ + case GNUNET_MESSAGE_TYPE_MESH_UNICAST: + case GNUNET_MESSAGE_TYPE_MESH_MULTICAST: + case GNUNET_MESSAGE_TYPE_MESH_TO_ORIGIN: + case GNUNET_MESSAGE_TYPE_MESH_ACK: + case GNUNET_MESSAGE_TYPE_MESH_POLL: + case GNUNET_MESSAGE_TYPE_MESH_PATH_KEEPALIVE: + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " prebuilt message\n"); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " type %s\n", + GNUNET_MESH_DEBUG_M2S(queue->type)); + dd = queue->cls; + data_descriptor_decrement_rc (dd->mesh_data); + break; + case GNUNET_MESSAGE_TYPE_MESH_PATH_CREATE: + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " type create path\n"); + path_info = queue->cls; + path_destroy (path_info->path); + break; + default: + GNUNET_break (0); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + " type %s unknown!\n", + GNUNET_MESH_DEBUG_M2S(queue->type)); + } + GNUNET_free_non_null (queue->cls); + } + GNUNET_CONTAINER_DLL_remove (queue->peer->queue_head, + queue->peer->queue_tail, + queue); + + /* Delete from child_fc in the appropiate tunnel */ + max = queue->tunnel->fwd_queue_max; + GNUNET_PEER_resolve (queue->peer->id, &id); + cinfo = tunnel_get_neighbor_fc (queue->tunnel, &id); + if (NULL != cinfo) + { + for (i = 0; i < cinfo->send_buffer_n; i++) + { + unsigned int i2; + i2 = (cinfo->send_buffer_start + i) % max; + if (cinfo->send_buffer[i2] == queue) + { + /* Found corresponding entry in the send_buffer. Move all others back. */ + unsigned int j; + unsigned int j2; + unsigned int j3; + + for (j = i, j2 = 0, j3 = 0; j < cinfo->send_buffer_n - 1; j++) + { + j2 = (cinfo->send_buffer_start + j) % max; + j3 = (cinfo->send_buffer_start + j + 1) % max; + cinfo->send_buffer[j2] = cinfo->send_buffer[j3]; + } + + cinfo->send_buffer[j3] = NULL; + cinfo->send_buffer_n--; + } + } + } + + GNUNET_free (queue); +} + + +/** + * @brief Get the next transmittable message from the queue. + * + * This will be the head, except in the case of being a data packet + * not allowed by the destination peer. + * + * @param peer Destination peer. + * + * @return The next viable MeshPeerQueue element to send to that peer. + * NULL when there are no transmittable messages. + */ +struct MeshPeerQueue * +queue_get_next (const struct MeshPeerInfo *peer) +{ + struct MeshPeerQueue *q; + struct MeshTunnel *t; + struct MeshTransmissionDescriptor *info; + struct MeshTunnelChildInfo *cinfo; + struct GNUNET_MESH_Unicast *ucast; + struct GNUNET_MESH_ToOrigin *to_orig; + struct GNUNET_MESH_Multicast *mcast; + struct GNUNET_PeerIdentity id; + uint32_t pid; + uint32_t ack; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "********* selecting message\n"); + for (q = peer->queue_head; NULL != q; q = q->next) + { + t = q->tunnel; + info = q->cls; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "********* %s\n", + GNUNET_MESH_DEBUG_M2S(q->type)); + switch (q->type) + { + case GNUNET_MESSAGE_TYPE_MESH_UNICAST: + ucast = (struct GNUNET_MESH_Unicast *) info->mesh_data->data; + pid = ntohl (ucast->pid); + GNUNET_PEER_resolve (info->peer->id, &id); + cinfo = tunnel_get_neighbor_fc(t, &id); + ack = cinfo->fwd_ack; + break; + case GNUNET_MESSAGE_TYPE_MESH_TO_ORIGIN: + to_orig = (struct GNUNET_MESH_ToOrigin *) info->mesh_data->data; + pid = ntohl (to_orig->pid); + ack = t->bck_ack; + break; + case GNUNET_MESSAGE_TYPE_MESH_MULTICAST: + mcast = (struct GNUNET_MESH_Multicast *) info->mesh_data->data; + if (GNUNET_MESSAGE_TYPE_MESH_MULTICAST != ntohs(mcast->header.type)) + { + // Not a multicast payload: multicast control traffic (destroy, etc) + return q; + } + pid = ntohl (mcast->pid); + GNUNET_PEER_resolve (info->peer->id, &id); + cinfo = tunnel_get_neighbor_fc(t, &id); + ack = cinfo->fwd_ack; + break; + default: + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "********* OK!\n"); + return q; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "********* ACK: %u, PID: %u\n", + ack, pid); + if (GNUNET_NO == GMC_is_pid_bigger(pid, ack)) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "********* OK!\n"); + return q; + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "********* NEXT!\n"); + } + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "********* nothing found\n"); + return NULL; +} + + +/** + * Core callback to write a queued packet to core buffer + * + * @param cls Closure (peer info). + * @param size Number of bytes available in buf. + * @param buf Where the to write the message. + * + * @return number of bytes written to buf + */ +static size_t +queue_send (void *cls, size_t size, void *buf) +{ + struct MeshPeerInfo *peer = cls; + struct GNUNET_MessageHeader *msg; + struct MeshPeerQueue *queue; + struct MeshTunnel *t; + struct MeshTunnelChildInfo *cinfo; + struct GNUNET_PeerIdentity dst_id; + size_t data_size; + + peer->core_transmit = NULL; + cinfo = NULL; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "********* Queue send\n"); + queue = queue_get_next (peer); + + /* Queue has no internal mesh traffic nor sendable payload */ + if (NULL == queue) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "********* not ready, return\n"); + if (NULL == peer->queue_head) + GNUNET_break (0); // Should've been canceled + return 0; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "********* not empty\n"); + + GNUNET_PEER_resolve (peer->id, &dst_id); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "********* towards %s\n", + GNUNET_i2s(&dst_id)); + /* Check if buffer size is enough for the message */ + if (queue->size > size) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "********* not enough room, reissue\n"); + peer->core_transmit = + GNUNET_CORE_notify_transmit_ready (core_handle, + 0, + 0, + GNUNET_TIME_UNIT_FOREVER_REL, + &dst_id, + queue->size, + &queue_send, + peer); + return 0; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "********* size ok\n"); + + t = queue->tunnel; + GNUNET_assert (0 < t->pending_messages); + t->pending_messages--; + if (GNUNET_MESSAGE_TYPE_MESH_UNICAST == queue->type) + { + t->fwd_queue_n--; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "********* unicast: t->q (%u/%u)\n", + t->fwd_queue_n, t->fwd_queue_max); + } + else if (GNUNET_MESSAGE_TYPE_MESH_TO_ORIGIN == queue->type) + { + t->bck_queue_n--; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "********* to origin\n"); + } + + /* Fill buf */ + switch (queue->type) + { + case 0: + case GNUNET_MESSAGE_TYPE_MESH_ACK: + case GNUNET_MESSAGE_TYPE_MESH_POLL: + case GNUNET_MESSAGE_TYPE_MESH_PATH_BROKEN: + case GNUNET_MESSAGE_TYPE_MESH_PATH_DESTROY: + case GNUNET_MESSAGE_TYPE_MESH_TUNNEL_DESTROY: + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "********* raw: %s\n", + GNUNET_MESH_DEBUG_M2S (queue->type)); + /* Fall through */ + case GNUNET_MESSAGE_TYPE_MESH_UNICAST: + case GNUNET_MESSAGE_TYPE_MESH_TO_ORIGIN: + data_size = send_core_data_raw (queue->cls, size, buf); + msg = (struct GNUNET_MessageHeader *) buf; + switch (ntohs (msg->type)) // Type of preconstructed message + { + case GNUNET_MESSAGE_TYPE_MESH_UNICAST: + tunnel_send_fwd_ack (t, GNUNET_MESSAGE_TYPE_MESH_UNICAST); + break; + case GNUNET_MESSAGE_TYPE_MESH_TO_ORIGIN: + tunnel_send_bck_ack (t, GNUNET_MESSAGE_TYPE_MESH_TO_ORIGIN); + break; + default: + break; + } + break; + case GNUNET_MESSAGE_TYPE_MESH_MULTICAST: + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "********* multicast\n"); + { + struct MeshTransmissionDescriptor *info = queue->cls; + + if ((1 == info->mesh_data->reference_counter + && GNUNET_YES == t->speed_min) + || + (info->mesh_data->total_out == info->mesh_data->reference_counter + && GNUNET_NO == t->speed_min)) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "********* considered sent\n"); + t->fwd_queue_n--; + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "********* NOT considered sent yet\n"); + t->pending_messages++; + } + } + data_size = send_core_data_multicast(queue->cls, size, buf); + tunnel_send_fwd_ack (t, GNUNET_MESSAGE_TYPE_MESH_MULTICAST); + break; + case GNUNET_MESSAGE_TYPE_MESH_PATH_CREATE: + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "********* path create\n"); + data_size = send_core_path_create (queue->cls, size, buf); + break; + case GNUNET_MESSAGE_TYPE_MESH_PATH_ACK: + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "********* path ack\n"); + data_size = send_core_path_ack (queue->cls, size, buf); + break; + case GNUNET_MESSAGE_TYPE_MESH_PATH_KEEPALIVE: + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "********* path keepalive\n"); + data_size = send_core_data_multicast (queue->cls, size, buf); + break; + default: + GNUNET_break (0); + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + "********* type unknown: %u\n", + queue->type); + data_size = 0; + } + switch (queue->type) + { + case GNUNET_MESSAGE_TYPE_MESH_UNICAST: + case GNUNET_MESSAGE_TYPE_MESH_TO_ORIGIN: + case GNUNET_MESSAGE_TYPE_MESH_MULTICAST: + cinfo = tunnel_get_neighbor_fc (t, &dst_id); + if (cinfo->send_buffer[cinfo->send_buffer_start] != queue) + { + GNUNET_break (0); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "at pos %u (%p) != %p\n", + cinfo->send_buffer_start, + cinfo->send_buffer[cinfo->send_buffer_start], + queue); + } + if (cinfo->send_buffer_n > 0) + { + cinfo->send_buffer[cinfo->send_buffer_start] = NULL; + cinfo->send_buffer_n--; + cinfo->send_buffer_start++; + cinfo->send_buffer_start %= t->fwd_queue_max; + } + else + { + GNUNET_break (0); + } + break; + default: + break; + } + + /* Free queue, but cls was freed by send_core_* */ + queue_destroy (queue, GNUNET_NO); + + if (GNUNET_YES == t->destroy && 0 == t->pending_messages) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "********* destroying tunnel!\n"); + tunnel_destroy (t); + } + + /* If more data in queue, send next */ + queue = queue_get_next(peer); + if (NULL != queue) + { + struct GNUNET_PeerIdentity id; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "********* more data!\n"); + GNUNET_PEER_resolve (peer->id, &id); + peer->core_transmit = + GNUNET_CORE_notify_transmit_ready(core_handle, + 0, + 0, + GNUNET_TIME_UNIT_FOREVER_REL, + &id, + queue->size, + &queue_send, + peer); + } + else + { + if (NULL != peer->queue_head) + { + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + "********* %s stalled\n", + GNUNET_i2s(&my_full_id)); + if (NULL == cinfo) + cinfo = tunnel_get_neighbor_fc (t, &dst_id); + // FIXME unify bck/fwd structures, bck does not have cinfo right now + if (NULL != cinfo && GNUNET_SCHEDULER_NO_TASK == cinfo->fc_poll) + { + cinfo->fc_poll = GNUNET_SCHEDULER_add_delayed (cinfo->fc_poll_time, + &tunnel_poll, cinfo); + } + } + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "********* return %d\n", data_size); + return data_size; +} + + +/** + * @brief Queue and pass message to core when possible. + * + * If type is payload (UNICAST, TO_ORIGIN, MULTICAST) checks for queue status + * and accounts for it. In case the queue is full, the message is dropped and + * a break issued. + * + * Otherwise, message is treated as internal and allowed to go regardless of + * queue status. + * + * @param cls Closure (@c type dependant). It will be used by queue_send to + * build the message to be sent if not already prebuilt. + * @param type Type of the message, 0 for a raw message. + * @param size Size of the message. + * @param dst Neighbor to send message to. + * @param t Tunnel this message belongs to. + */ +static void +queue_add (void *cls, uint16_t type, size_t size, + struct MeshPeerInfo *dst, struct MeshTunnel *t) +{ + struct MeshPeerQueue *queue; + struct MeshTunnelChildInfo *cinfo; + struct GNUNET_PeerIdentity id; + unsigned int *max; + unsigned int *n; + unsigned int i; + + n = NULL; + if (GNUNET_MESSAGE_TYPE_MESH_UNICAST == type || + GNUNET_MESSAGE_TYPE_MESH_MULTICAST == type) + { + n = &t->fwd_queue_n; + max = &t->fwd_queue_max; + } + else if (GNUNET_MESSAGE_TYPE_MESH_TO_ORIGIN == type) + { + n = &t->bck_queue_n; + max = &t->bck_queue_max; + } + if (NULL != n) + { + if (*n >= *max) + { + GNUNET_break(0); + GNUNET_STATISTICS_update(stats, + "# messages dropped (buffer full)", + 1, GNUNET_NO); + return; // Drop message + } + (*n)++; + } + queue = GNUNET_malloc (sizeof (struct MeshPeerQueue)); + queue->cls = cls; + queue->type = type; + queue->size = size; + queue->peer = dst; + queue->tunnel = t; + GNUNET_CONTAINER_DLL_insert_tail (dst->queue_head, dst->queue_tail, queue); + GNUNET_PEER_resolve (dst->id, &id); + if (NULL == dst->core_transmit) + { + dst->core_transmit = + GNUNET_CORE_notify_transmit_ready (core_handle, + 0, + 0, + GNUNET_TIME_UNIT_FOREVER_REL, + &id, + size, + &queue_send, + dst); + } + t->pending_messages++; + if (NULL == n) // Is this internal mesh traffic? + return; + + // It's payload, keep track of buffer per peer. + cinfo = tunnel_get_neighbor_fc(t, &id); + i = (cinfo->send_buffer_start + cinfo->send_buffer_n) % t->fwd_queue_max; + if (NULL != cinfo->send_buffer[i]) + { + GNUNET_break (cinfo->send_buffer_n == t->fwd_queue_max); // aka i == start + queue_destroy (cinfo->send_buffer[cinfo->send_buffer_start], GNUNET_YES); + cinfo->send_buffer_start++; + cinfo->send_buffer_start %= t->fwd_queue_max; + } + else + { + cinfo->send_buffer_n++; + } + cinfo->send_buffer[i] = queue; + if (cinfo->send_buffer_n > t->fwd_queue_max) + { + GNUNET_break (0); + cinfo->send_buffer_n = t->fwd_queue_max; + } +} + + +/******************************************************************************/ +/******************** MESH NETWORK HANDLERS **************************/ +/******************************************************************************/ + + +/** + * Core handler for path creation + * + * @param cls closure + * @param message message + * @param peer peer identity this notification is about + * @param atsi performance data + * @param atsi_count number of records in 'atsi' + * + * @return GNUNET_OK to keep the connection open, + * GNUNET_SYSERR to close it (signal serious error) + */ +static int +handle_mesh_path_create (void *cls, const struct GNUNET_PeerIdentity *peer, + const struct GNUNET_MessageHeader *message, + const struct GNUNET_ATS_Information *atsi, + unsigned int atsi_count) +{ + unsigned int own_pos; + uint16_t size; + uint16_t i; + MESH_TunnelNumber tid; + struct GNUNET_MESH_ManipulatePath *msg; + struct GNUNET_PeerIdentity *pi; + struct GNUNET_HashCode hash; + struct MeshPeerPath *path; + struct MeshPeerInfo *dest_peer_info; + struct MeshPeerInfo *orig_peer_info; + struct MeshTunnel *t; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Received a path create msg [%s]\n", + GNUNET_i2s (&my_full_id)); + size = ntohs (message->size); + if (size < sizeof (struct GNUNET_MESH_ManipulatePath)) + { + GNUNET_break_op (0); + return GNUNET_OK; + } + + size -= sizeof (struct GNUNET_MESH_ManipulatePath); + if (size % sizeof (struct GNUNET_PeerIdentity)) + { + GNUNET_break_op (0); + return GNUNET_OK; + } + size /= sizeof (struct GNUNET_PeerIdentity); + if (size < 2) + { + GNUNET_break_op (0); + return GNUNET_OK; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " path has %u hops.\n", size); + msg = (struct GNUNET_MESH_ManipulatePath *) message; + + tid = ntohl (msg->tid); + pi = (struct GNUNET_PeerIdentity *) &msg[1]; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " path is for tunnel %s [%X].\n", GNUNET_i2s (pi), tid); + t = tunnel_get (pi, tid); + if (NULL == t) // FIXME only for INCOMING tunnels? + { + uint32_t opt; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " Creating tunnel\n"); + t = tunnel_new (GNUNET_PEER_intern (pi), tid, NULL, 0); + if (NULL == t) + { + // FIXME notify failure + return GNUNET_OK; + } + opt = ntohl (msg->opt); + t->speed_min = (0 != (opt & MESH_TUNNEL_OPT_SPEED_MIN)) ? + GNUNET_YES : GNUNET_NO; + if (0 != (opt & MESH_TUNNEL_OPT_NOBUFFER)) + { + t->nobuffer = GNUNET_YES; + t->last_fwd_ack = t->fwd_pid + 1; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " speed_min: %d, nobuffer:%d\n", + t->speed_min, t->nobuffer); + + if (GNUNET_YES == t->nobuffer) + { + t->bck_queue_max = 1; + t->fwd_queue_max = 1; + } + + // FIXME only assign a local tid if a local client is interested (on demand) + while (NULL != tunnel_get_incoming (next_local_tid)) + next_local_tid = (next_local_tid + 1) | GNUNET_MESH_LOCAL_TUNNEL_ID_SERV; + t->local_tid_dest = next_local_tid++; + next_local_tid = next_local_tid | GNUNET_MESH_LOCAL_TUNNEL_ID_SERV; + // FIXME end + + tunnel_reset_timeout (t); + GNUNET_CRYPTO_hash (&t->local_tid_dest, sizeof (MESH_TunnelNumber), &hash); + if (GNUNET_OK != + GNUNET_CONTAINER_multihashmap_put (incoming_tunnels, &hash, t, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_FAST)) + { + tunnel_destroy (t); + GNUNET_break (0); + return GNUNET_OK; + } + } + dest_peer_info = + GNUNET_CONTAINER_multihashmap_get (peers, &pi[size - 1].hashPubKey); + if (NULL == dest_peer_info) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " Creating PeerInfo for destination.\n"); + dest_peer_info = GNUNET_malloc (sizeof (struct MeshPeerInfo)); + dest_peer_info->id = GNUNET_PEER_intern (&pi[size - 1]); + GNUNET_CONTAINER_multihashmap_put (peers, &pi[size - 1].hashPubKey, + dest_peer_info, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY); + } + orig_peer_info = GNUNET_CONTAINER_multihashmap_get (peers, &pi->hashPubKey); + if (NULL == orig_peer_info) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " Creating PeerInfo for origin.\n"); + orig_peer_info = GNUNET_malloc (sizeof (struct MeshPeerInfo)); + orig_peer_info->id = GNUNET_PEER_intern (pi); + GNUNET_CONTAINER_multihashmap_put (peers, &pi->hashPubKey, orig_peer_info, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY); + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " Creating path...\n"); + path = path_new (size); + own_pos = 0; + for (i = 0; i < size; i++) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " ... adding %s\n", + GNUNET_i2s (&pi[i])); + path->peers[i] = GNUNET_PEER_intern (&pi[i]); + if (path->peers[i] == myid) + own_pos = i; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " Own position: %u\n", own_pos); + if (own_pos == 0) + { + /* cannot be self, must be 'not found' */ + /* create path: self not found in path through self */ + GNUNET_break_op (0); + path_destroy (path); + tunnel_destroy (t); + return GNUNET_OK; + } + path_add_to_peers (path, GNUNET_NO); + tunnel_add_path (t, path, own_pos); + if (own_pos == size - 1) + { + /* It is for us! Send ack. */ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " It's for us!\n"); + peer_info_add_path_to_origin (orig_peer_info, path, GNUNET_NO); + if (NULL == t->peers) + { + /* New tunnel! Notify clients on first payload message. */ + t->peers = GNUNET_CONTAINER_multihashmap_create (4, GNUNET_NO); + } + GNUNET_break (GNUNET_SYSERR != + GNUNET_CONTAINER_multihashmap_put (t->peers, + &my_full_id.hashPubKey, + peer_info_get + (&my_full_id), + GNUNET_CONTAINER_MULTIHASHMAPOPTION_REPLACE)); + send_path_ack (t); + } + else + { + struct MeshPeerPath *path2; + + /* It's for somebody else! Retransmit. */ + path2 = path_duplicate (path); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " Retransmitting.\n"); + peer_info_add_path (dest_peer_info, path2, GNUNET_NO); + path2 = path_duplicate (path); + peer_info_add_path_to_origin (orig_peer_info, path2, GNUNET_NO); + send_create_path (dest_peer_info, path, t); + } + return GNUNET_OK; +} + + +/** + * Core handler for path destruction + * + * @param cls closure + * @param message message + * @param peer peer identity this notification is about + * @param atsi performance data + * @param atsi_count number of records in 'atsi' + * + * @return GNUNET_OK to keep the connection open, + * GNUNET_SYSERR to close it (signal serious error) + */ +static int +handle_mesh_path_destroy (void *cls, const struct GNUNET_PeerIdentity *peer, + const struct GNUNET_MessageHeader *message, + const struct GNUNET_ATS_Information *atsi, + unsigned int atsi_count) +{ + struct GNUNET_MESH_ManipulatePath *msg; + struct GNUNET_PeerIdentity *pi; + struct MeshPeerPath *path; + struct MeshTunnel *t; + unsigned int own_pos; + unsigned int i; + size_t size; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Received a PATH DESTROY msg from %s\n", GNUNET_i2s (peer)); + size = ntohs (message->size); + if (size < sizeof (struct GNUNET_MESH_ManipulatePath)) + { + GNUNET_break_op (0); + return GNUNET_OK; + } + + size -= sizeof (struct GNUNET_MESH_ManipulatePath); + if (size % sizeof (struct GNUNET_PeerIdentity)) + { + GNUNET_break_op (0); + return GNUNET_OK; + } + size /= sizeof (struct GNUNET_PeerIdentity); + if (size < 2) + { + GNUNET_break_op (0); + return GNUNET_OK; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " path has %u hops.\n", size); + + msg = (struct GNUNET_MESH_ManipulatePath *) message; + pi = (struct GNUNET_PeerIdentity *) &msg[1]; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " path is for tunnel %s [%X].\n", GNUNET_i2s (pi), + msg->tid); + t = tunnel_get (pi, ntohl (msg->tid)); + if (NULL == t) + { + /* TODO notify back: we don't know this tunnel */ + GNUNET_break_op (0); + return GNUNET_OK; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " Creating path...\n"); + path = path_new (size); + own_pos = 0; + for (i = 0; i < size; i++) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " ... adding %s\n", + GNUNET_i2s (&pi[i])); + path->peers[i] = GNUNET_PEER_intern (&pi[i]); + if (path->peers[i] == myid) + own_pos = i; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " Own position: %u\n", own_pos); + if (own_pos < path->length - 1) + send_prebuilt_message (message, &pi[own_pos + 1], t); + else + send_client_tunnel_disconnect(t, NULL); + + tunnel_delete_peer (t, path->peers[path->length - 1]); + path_destroy (path); + return GNUNET_OK; +} + + +/** + * Core handler for notifications of broken paths + * + * @param cls closure + * @param message message + * @param peer peer identity this notification is about + * @param atsi performance data + * @param atsi_count number of records in 'atsi' + * + * @return GNUNET_OK to keep the connection open, + * GNUNET_SYSERR to close it (signal serious error) + */ +static int +handle_mesh_path_broken (void *cls, const struct GNUNET_PeerIdentity *peer, + const struct GNUNET_MessageHeader *message, + const struct GNUNET_ATS_Information *atsi, + unsigned int atsi_count) +{ + struct GNUNET_MESH_PathBroken *msg; + struct MeshTunnel *t; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Received a PATH BROKEN msg from %s\n", GNUNET_i2s (peer)); + msg = (struct GNUNET_MESH_PathBroken *) message; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " regarding %s\n", + GNUNET_i2s (&msg->peer1)); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " regarding %s\n", + GNUNET_i2s (&msg->peer2)); + t = tunnel_get (&msg->oid, ntohl (msg->tid)); + if (NULL == t) + { + GNUNET_break_op (0); + return GNUNET_OK; + } + tunnel_notify_connection_broken (t, GNUNET_PEER_search (&msg->peer1), + GNUNET_PEER_search (&msg->peer2)); + return GNUNET_OK; + +} + + +/** + * Core handler for tunnel destruction + * + * @param cls closure + * @param message message + * @param peer peer identity this notification is about + * @param atsi performance data + * @param atsi_count number of records in 'atsi' + * + * @return GNUNET_OK to keep the connection open, + * GNUNET_SYSERR to close it (signal serious error) + */ +static int +handle_mesh_tunnel_destroy (void *cls, const struct GNUNET_PeerIdentity *peer, + const struct GNUNET_MessageHeader *message, + const struct GNUNET_ATS_Information *atsi, + unsigned int atsi_count) +{ + struct GNUNET_MESH_TunnelDestroy *msg; + struct MeshTunnel *t; + GNUNET_PEER_Id parent; + GNUNET_PEER_Id pid; + + msg = (struct GNUNET_MESH_TunnelDestroy *) message; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Got a TUNNEL DESTROY packet from %s\n", + GNUNET_i2s (peer)); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " for tunnel %s [%u]\n", + GNUNET_i2s (&msg->oid), ntohl (msg->tid)); + t = tunnel_get (&msg->oid, ntohl (msg->tid)); + /* Check signature */ + if (NULL == t) + { + /* Probably already got the message from another path, + * destroyed the tunnel and retransmitted to children. + * Safe to ignore. + */ + GNUNET_STATISTICS_update (stats, "# control on unknown tunnel", + 1, GNUNET_NO); + return GNUNET_OK; + } + parent = tree_get_predecessor (t->tree); + pid = GNUNET_PEER_search (peer); + if (pid != parent) + { + unsigned int nc; + + tree_del_peer (t->tree, pid, &tunnel_child_removed, t); + nc = tree_count_children (t->tree); + if (nc > 0 || NULL != t->owner || t->nclients > 0) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "still in use: %u cl, %u ch\n", + t->nclients, nc); + return GNUNET_OK; + } + } + if (t->local_tid_dest >= GNUNET_MESH_LOCAL_TUNNEL_ID_SERV) + { + /* Tunnel was incoming, notify clients */ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "INCOMING TUNNEL %X %X\n", + t->local_tid, t->local_tid_dest); + send_clients_tunnel_destroy (t); + } + tunnel_send_destroy (t, parent); + t->destroy = GNUNET_YES; + // TODO: add timeout to destroy the tunnel anyway + return GNUNET_OK; +} + + +/** + * Core handler for mesh network traffic going from the origin to a peer + * + * @param cls closure + * @param peer peer identity this notification is about + * @param message message + * @param atsi performance data + * @param atsi_count number of records in 'atsi' + * @return GNUNET_OK to keep the connection open, + * GNUNET_SYSERR to close it (signal serious error) + */ +static int +handle_mesh_data_unicast (void *cls, const struct GNUNET_PeerIdentity *peer, + const struct GNUNET_MessageHeader *message, + const struct GNUNET_ATS_Information *atsi, + unsigned int atsi_count) +{ + struct GNUNET_MESH_Unicast *msg; + struct GNUNET_PeerIdentity *neighbor; + struct MeshTunnelChildInfo *cinfo; + struct MeshTunnel *t; + GNUNET_PEER_Id dest_id; + uint32_t pid; + uint32_t ttl; + size_t size; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "got a unicast packet from %s\n", + GNUNET_i2s (peer)); + /* Check size */ + size = ntohs (message->size); + if (size < + sizeof (struct GNUNET_MESH_Unicast) + + sizeof (struct GNUNET_MessageHeader)) + { + GNUNET_break (0); + return GNUNET_OK; + } + msg = (struct GNUNET_MESH_Unicast *) message; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " of type %s\n", + GNUNET_MESH_DEBUG_M2S (ntohs (msg[1].header.type))); + /* Check tunnel */ + t = tunnel_get (&msg->oid, ntohl (msg->tid)); + if (NULL == t) + { + /* TODO notify back: we don't know this tunnel */ + GNUNET_STATISTICS_update (stats, "# data on unknown tunnel", 1, GNUNET_NO); + GNUNET_break_op (0); + return GNUNET_OK; + } + pid = ntohl (msg->pid); + if (t->fwd_pid == pid) + { + GNUNET_STATISTICS_update (stats, "# duplicate PID drops", 1, GNUNET_NO); + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + " Already seen pid %u, DROPPING!\n", pid); + return GNUNET_OK; + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " pid %u not seen yet, forwarding\n", pid); + } + + t->skip += (pid - t->fwd_pid) - 1; + t->fwd_pid = pid; + + if (GMC_is_pid_bigger (pid, t->last_fwd_ack)) + { + GNUNET_STATISTICS_update (stats, "# unsolicited unicast", 1, GNUNET_NO); + GNUNET_break_op (0); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Received PID %u, ACK %u\n", + pid, t->last_fwd_ack); + return GNUNET_OK; + } + + tunnel_reset_timeout (t); + dest_id = GNUNET_PEER_search (&msg->destination); + if (dest_id == myid) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " it's for us! sending to clients...\n"); + GNUNET_STATISTICS_update (stats, "# unicast received", 1, GNUNET_NO); + send_subscribed_clients (message, &msg[1].header, t); + tunnel_send_fwd_ack (t, GNUNET_MESSAGE_TYPE_MESH_UNICAST); + return GNUNET_OK; + } + ttl = ntohl (msg->ttl); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " ttl: %u\n", ttl); + if (ttl == 0) + { + GNUNET_STATISTICS_update (stats, "# TTL drops", 1, GNUNET_NO); + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, " TTL is 0, DROPPING!\n"); + tunnel_send_fwd_ack (t, GNUNET_MESSAGE_TYPE_MESH_ACK); + return GNUNET_OK; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " not for us, retransmitting...\n"); + + neighbor = tree_get_first_hop (t->tree, dest_id); + cinfo = tunnel_get_neighbor_fc (t, neighbor); + cinfo->fwd_pid = pid; + GNUNET_CONTAINER_multihashmap_iterate (t->children_fc, + &tunnel_add_skip, + &neighbor); + if (GNUNET_YES == t->nobuffer && + GNUNET_YES == GMC_is_pid_bigger (pid, cinfo->fwd_ack)) + { + GNUNET_STATISTICS_update (stats, "# unsolicited unicast", 1, GNUNET_NO); + GNUNET_log (GNUNET_ERROR_TYPE_INFO, " %u > %u\n", pid, cinfo->fwd_ack); + GNUNET_break_op (0); + return GNUNET_OK; + } + send_prebuilt_message (message, neighbor, t); + GNUNET_STATISTICS_update (stats, "# unicast forwarded", 1, GNUNET_NO); + return GNUNET_OK; +} + + +/** + * Core handler for mesh network traffic going from the origin to all peers + * + * @param cls closure + * @param message message + * @param peer peer identity this notification is about + * @param atsi performance data + * @param atsi_count number of records in 'atsi' + * @return GNUNET_OK to keep the connection open, + * GNUNET_SYSERR to close it (signal serious error) + * + * TODO: Check who we got this from, to validate route. + */ +static int +handle_mesh_data_multicast (void *cls, const struct GNUNET_PeerIdentity *peer, + const struct GNUNET_MessageHeader *message, + const struct GNUNET_ATS_Information *atsi, + unsigned int atsi_count) +{ + struct GNUNET_MESH_Multicast *msg; + struct MeshTunnel *t; + size_t size; + uint32_t pid; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "got a multicast packet from %s\n", + GNUNET_i2s (peer)); + size = ntohs (message->size); + if (sizeof (struct GNUNET_MESH_Multicast) + + sizeof (struct GNUNET_MessageHeader) > size) + { + GNUNET_break_op (0); + return GNUNET_OK; + } + msg = (struct GNUNET_MESH_Multicast *) message; + t = tunnel_get (&msg->oid, ntohl (msg->tid)); + + if (NULL == t) + { + /* TODO notify that we dont know that tunnel */ + GNUNET_STATISTICS_update (stats, "# data on unknown tunnel", 1, GNUNET_NO); + GNUNET_break_op (0); + return GNUNET_OK; + } + pid = ntohl (msg->pid); + if (t->fwd_pid == pid) + { + /* already seen this packet, drop */ + GNUNET_STATISTICS_update (stats, "# duplicate PID drops", 1, GNUNET_NO); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " Already seen pid %u, DROPPING!\n", pid); + tunnel_send_fwd_ack (t, GNUNET_MESSAGE_TYPE_MESH_ACK); + return GNUNET_OK; + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " pid %u not seen yet, forwarding\n", pid); + } + t->skip += (pid - t->fwd_pid) - 1; + t->fwd_pid = pid; + tunnel_reset_timeout (t); + + /* Transmit to locally interested clients */ + if (NULL != t->peers && + GNUNET_CONTAINER_multihashmap_contains (t->peers, &my_full_id.hashPubKey)) + { + GNUNET_STATISTICS_update (stats, "# multicast received", 1, GNUNET_NO); + send_subscribed_clients (message, &msg[1].header, t); + tunnel_send_fwd_ack(t, GNUNET_MESSAGE_TYPE_MESH_MULTICAST); + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " ttl: %u\n", ntohl (msg->ttl)); + if (ntohl (msg->ttl) == 0) + { + GNUNET_STATISTICS_update (stats, "# TTL drops", 1, GNUNET_NO); + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, " TTL is 0, DROPPING!\n"); + tunnel_send_fwd_ack (t, GNUNET_MESSAGE_TYPE_MESH_ACK); + return GNUNET_OK; + } + GNUNET_STATISTICS_update (stats, "# multicast forwarded", 1, GNUNET_NO); + tunnel_send_multicast (t, message); + return GNUNET_OK; +} + + +/** + * Core handler for mesh network traffic toward the owner of a tunnel + * + * @param cls closure + * @param message message + * @param peer peer identity this notification is about + * @param atsi performance data + * @param atsi_count number of records in 'atsi' + * + * @return GNUNET_OK to keep the connection open, + * GNUNET_SYSERR to close it (signal serious error) + */ +static int +handle_mesh_data_to_orig (void *cls, const struct GNUNET_PeerIdentity *peer, + const struct GNUNET_MessageHeader *message, + const struct GNUNET_ATS_Information *atsi, + unsigned int atsi_count) +{ + struct GNUNET_MESH_ToOrigin *msg; + struct GNUNET_PeerIdentity id; + struct MeshPeerInfo *peer_info; + struct MeshTunnel *t; + struct MeshTunnelChildInfo *cinfo; + GNUNET_PEER_Id predecessor; + size_t size; + uint32_t pid; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "got a ToOrigin packet from %s\n", + GNUNET_i2s (peer)); + size = ntohs (message->size); + if (size < sizeof (struct GNUNET_MESH_ToOrigin) + /* Payload must be */ + sizeof (struct GNUNET_MessageHeader)) /* at least a header */ + { + GNUNET_break_op (0); + return GNUNET_OK; + } + msg = (struct GNUNET_MESH_ToOrigin *) message; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " of type %s\n", + GNUNET_MESH_DEBUG_M2S (ntohs (msg[1].header.type))); + t = tunnel_get (&msg->oid, ntohl (msg->tid)); + pid = ntohl (msg->pid); + + if (NULL == t) + { + /* TODO notify that we dont know this tunnel (whom)? */ + GNUNET_STATISTICS_update (stats, "# data on unknown tunnel", 1, GNUNET_NO); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Received to_origin with PID %u on unknown tunnel %s [%u]\n", + pid, GNUNET_i2s (&msg->oid), ntohl (msg->tid)); + return GNUNET_OK; + } + + cinfo = tunnel_get_neighbor_fc(t, peer); + if (NULL == cinfo) + { + GNUNET_break (0); + return GNUNET_OK; + } + + if (cinfo->bck_pid == pid) + { + /* already seen this packet, drop */ + GNUNET_STATISTICS_update (stats, "# duplicate PID drops BCK", 1, GNUNET_NO); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " Already seen pid %u, DROPPING!\n", pid); + tunnel_send_bck_ack (t, GNUNET_MESSAGE_TYPE_MESH_ACK); + return GNUNET_OK; + } + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " pid %u not seen yet, forwarding\n", pid); + cinfo->bck_pid = pid; + + if (NULL != t->owner) + { + char cbuf[size]; + struct GNUNET_MESH_ToOrigin *copy; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " it's for us! sending to clients...\n"); + /* TODO signature verification */ + memcpy (cbuf, message, size); + copy = (struct GNUNET_MESH_ToOrigin *) cbuf; + copy->tid = htonl (t->local_tid); + t->bck_pid++; + copy->pid = htonl (t->bck_pid); + GNUNET_STATISTICS_update (stats, "# to origin received", 1, GNUNET_NO); + GNUNET_SERVER_notification_context_unicast (nc, t->owner->handle, + ©->header, GNUNET_NO); + tunnel_send_bck_ack (t, GNUNET_MESSAGE_TYPE_MESH_TO_ORIGIN); + return GNUNET_OK; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " not for us, retransmitting...\n"); + + peer_info = peer_info_get (&msg->oid); + if (NULL == peer_info) + { + /* unknown origin of tunnel */ + GNUNET_break (0); + return GNUNET_OK; + } + predecessor = tree_get_predecessor (t->tree); + if (0 == predecessor) + { + if (GNUNET_YES == t->destroy) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "to orig received on a dying tunnel %s [%X]\n", + GNUNET_i2s (&msg->oid), ntohl(msg->tid)); + return GNUNET_OK; + } + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "unknown to origin at %s\n", + GNUNET_i2s (&my_full_id)); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "from peer %s\n", + GNUNET_i2s (peer)); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "for tunnel %s [%X]\n", + GNUNET_i2s (&msg->oid), ntohl(msg->tid)); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "current tree:\n"); + tree_debug (t->tree); + return GNUNET_OK; + } + GNUNET_PEER_resolve (predecessor, &id); + send_prebuilt_message (message, &id, t); + GNUNET_STATISTICS_update (stats, "# to origin forwarded", 1, GNUNET_NO); + + return GNUNET_OK; +} + + +/** + * Core handler for mesh network traffic point-to-point acks. + * + * @param cls closure + * @param message message + * @param peer peer identity this notification is about + * @param atsi performance data + * @param atsi_count number of records in 'atsi' + * + * @return GNUNET_OK to keep the connection open, + * GNUNET_SYSERR to close it (signal serious error) + */ +static int +handle_mesh_ack (void *cls, const struct GNUNET_PeerIdentity *peer, + const struct GNUNET_MessageHeader *message, + const struct GNUNET_ATS_Information *atsi, + unsigned int atsi_count) +{ + struct GNUNET_MESH_ACK *msg; + struct MeshTunnel *t; + uint32_t ack; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Got an ACK packet from %s!\n", + GNUNET_i2s (peer)); + msg = (struct GNUNET_MESH_ACK *) message; + + t = tunnel_get (&msg->oid, ntohl (msg->tid)); + + if (NULL == t) + { + /* TODO notify that we dont know this tunnel (whom)? */ + GNUNET_STATISTICS_update (stats, "# ack on unknown tunnel", 1, GNUNET_NO); + return GNUNET_OK; + } + ack = ntohl (msg->pid); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " ACK %u\n", ack); + + /* Is this a forward or backward ACK? */ + if (tree_get_predecessor(t->tree) != GNUNET_PEER_search(peer)) + { + struct MeshTunnelChildInfo *cinfo; + + debug_bck_ack++; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " FWD ACK\n"); + cinfo = tunnel_get_neighbor_fc (t, peer); + cinfo->fwd_ack = ack; + tunnel_send_fwd_ack (t, GNUNET_MESSAGE_TYPE_MESH_ACK); + tunnel_unlock_fwd_queues (t); + if (GNUNET_SCHEDULER_NO_TASK != cinfo->fc_poll) + { + GNUNET_SCHEDULER_cancel (cinfo->fc_poll); + cinfo->fc_poll = GNUNET_SCHEDULER_NO_TASK; + cinfo->fc_poll_time = GNUNET_TIME_UNIT_SECONDS; + } + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " BCK ACK\n"); + t->bck_ack = ack; + tunnel_send_bck_ack (t, GNUNET_MESSAGE_TYPE_MESH_ACK); + tunnel_unlock_bck_queue (t); + } + return GNUNET_OK; +} + + +/** + * Core handler for mesh network traffic point-to-point ack polls. + * + * @param cls closure + * @param message message + * @param peer peer identity this notification is about + * @param atsi performance data + * @param atsi_count number of records in 'atsi' + * + * @return GNUNET_OK to keep the connection open, + * GNUNET_SYSERR to close it (signal serious error) + */ +static int +handle_mesh_poll (void *cls, const struct GNUNET_PeerIdentity *peer, + const struct GNUNET_MessageHeader *message, + const struct GNUNET_ATS_Information *atsi, + unsigned int atsi_count) +{ + struct GNUNET_MESH_Poll *msg; + struct MeshTunnel *t; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Got an POLL packet from %s!\n", + GNUNET_i2s (peer)); + + msg = (struct GNUNET_MESH_Poll *) message; + + t = tunnel_get (&msg->oid, ntohl (msg->tid)); + + if (NULL == t) + { + /* TODO notify that we dont know this tunnel (whom)? */ + GNUNET_STATISTICS_update (stats, "# poll on unknown tunnel", 1, GNUNET_NO); + GNUNET_break_op (0); + return GNUNET_OK; + } + + /* Is this a forward or backward ACK? */ + if (tree_get_predecessor(t->tree) != GNUNET_PEER_search(peer)) + { + struct MeshTunnelChildInfo *cinfo; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " from FWD\n"); + cinfo = tunnel_get_neighbor_fc (t, peer); + cinfo->bck_ack = cinfo->fwd_pid; // mark as ready to send + tunnel_send_bck_ack (t, GNUNET_MESSAGE_TYPE_MESH_POLL); + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " from BCK\n"); + tunnel_send_fwd_ack (t, GNUNET_MESSAGE_TYPE_MESH_POLL); + } + + return GNUNET_OK; +} + +/** + * Core handler for path ACKs + * + * @param cls closure + * @param message message + * @param peer peer identity this notification is about + * @param atsi performance data + * @param atsi_count number of records in 'atsi' + * + * @return GNUNET_OK to keep the connection open, + * GNUNET_SYSERR to close it (signal serious error) + */ +static int +handle_mesh_path_ack (void *cls, const struct GNUNET_PeerIdentity *peer, + const struct GNUNET_MessageHeader *message, + const struct GNUNET_ATS_Information *atsi, + unsigned int atsi_count) +{ + struct GNUNET_MESH_PathACK *msg; + struct GNUNET_PeerIdentity id; + struct MeshPeerInfo *peer_info; + struct MeshPeerPath *p; + struct MeshTunnel *t; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received a path ACK msg [%s]\n", + GNUNET_i2s (&my_full_id)); + msg = (struct GNUNET_MESH_PathACK *) message; + t = tunnel_get (&msg->oid, ntohl(msg->tid)); + if (NULL == t) + { + /* TODO notify that we don't know the tunnel */ + GNUNET_STATISTICS_update (stats, "# control on unknown tunnel", 1, GNUNET_NO); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " don't know the tunnel %s [%X]!\n", + GNUNET_i2s (&msg->oid), ntohl(msg->tid)); + return GNUNET_OK; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " on tunnel %s [%X]\n", + GNUNET_i2s (&msg->oid), ntohl(msg->tid)); + + peer_info = peer_info_get (&msg->peer_id); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " by peer %s\n", + GNUNET_i2s (&msg->peer_id)); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " via peer %s\n", + GNUNET_i2s (peer)); + + if (NULL != t->regex_search && t->regex_search->peer == peer_info->id) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "connect_by_string completed, stopping search\n"); + regex_cancel_search (t->regex_search); + t->regex_search = NULL; + } + + /* Add paths to peers? */ + p = tree_get_path_to_peer (t->tree, peer_info->id); + if (NULL != p) + { + path_add_to_peers (p, GNUNET_YES); + path_destroy (p); + } + else + { + GNUNET_break (0); + } + + /* Message for us? */ + if (0 == memcmp (&msg->oid, &my_full_id, sizeof (struct GNUNET_PeerIdentity))) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " It's for us!\n"); + if (NULL == t->owner) + { + GNUNET_break_op (0); + return GNUNET_OK; + } + if (NULL != t->dht_get_type) + { + GNUNET_DHT_get_stop (t->dht_get_type); + t->dht_get_type = NULL; + } + if (tree_get_status (t->tree, peer_info->id) != MESH_PEER_READY) + { + tree_set_status (t->tree, peer_info->id, MESH_PEER_READY); + send_client_peer_connected (t, peer_info->id); + } + return GNUNET_OK; + } + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " not for us, retransmitting...\n"); + GNUNET_PEER_resolve (tree_get_predecessor (t->tree), &id); + peer_info = peer_info_get (&msg->oid); + if (NULL == peer_info) + { + /* If we know the tunnel, we should DEFINITELY know the peer */ + GNUNET_break (0); + return GNUNET_OK; + } + send_prebuilt_message (message, &id, t); + return GNUNET_OK; +} + + +/** + * Core handler for mesh keepalives. + * + * @param cls closure + * @param message message + * @param peer peer identity this notification is about + * @param atsi performance data + * @param atsi_count number of records in 'atsi' + * @return GNUNET_OK to keep the connection open, + * GNUNET_SYSERR to close it (signal serious error) + * + * TODO: Check who we got this from, to validate route. + */ +static int +handle_mesh_keepalive (void *cls, const struct GNUNET_PeerIdentity *peer, + const struct GNUNET_MessageHeader *message, + const struct GNUNET_ATS_Information *atsi, + unsigned int atsi_count) +{ + struct GNUNET_MESH_TunnelKeepAlive *msg; + struct MeshTunnel *t; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "got a keepalive packet from %s\n", + GNUNET_i2s (peer)); + + msg = (struct GNUNET_MESH_TunnelKeepAlive *) message; + t = tunnel_get (&msg->oid, ntohl (msg->tid)); + + if (NULL == t) + { + /* TODO notify that we dont know that tunnel */ + GNUNET_STATISTICS_update (stats, "# keepalive on unknown tunnel", 1, + GNUNET_NO); + return GNUNET_OK; + } + + tunnel_reset_timeout (t); + + GNUNET_STATISTICS_update (stats, "# keepalives forwarded", 1, GNUNET_NO); + tunnel_send_multicast (t, message); + return GNUNET_OK; + } + + + +/** + * Functions to handle messages from core + */ +static struct GNUNET_CORE_MessageHandler core_handlers[] = { + {&handle_mesh_path_create, GNUNET_MESSAGE_TYPE_MESH_PATH_CREATE, 0}, + {&handle_mesh_path_destroy, GNUNET_MESSAGE_TYPE_MESH_PATH_DESTROY, 0}, + {&handle_mesh_path_broken, GNUNET_MESSAGE_TYPE_MESH_PATH_BROKEN, + sizeof (struct GNUNET_MESH_PathBroken)}, + {&handle_mesh_tunnel_destroy, GNUNET_MESSAGE_TYPE_MESH_TUNNEL_DESTROY, + sizeof (struct GNUNET_MESH_TunnelDestroy)}, + {&handle_mesh_data_unicast, GNUNET_MESSAGE_TYPE_MESH_UNICAST, 0}, + {&handle_mesh_data_multicast, GNUNET_MESSAGE_TYPE_MESH_MULTICAST, 0}, + {&handle_mesh_keepalive, GNUNET_MESSAGE_TYPE_MESH_PATH_KEEPALIVE, + sizeof (struct GNUNET_MESH_TunnelKeepAlive)}, + {&handle_mesh_data_to_orig, GNUNET_MESSAGE_TYPE_MESH_TO_ORIGIN, 0}, + {&handle_mesh_ack, GNUNET_MESSAGE_TYPE_MESH_ACK, + sizeof (struct GNUNET_MESH_ACK)}, + {&handle_mesh_poll, GNUNET_MESSAGE_TYPE_MESH_POLL, + sizeof (struct GNUNET_MESH_Poll)}, + {&handle_mesh_path_ack, GNUNET_MESSAGE_TYPE_MESH_PATH_ACK, + sizeof (struct GNUNET_MESH_PathACK)}, + {NULL, 0, 0} +}; + + + +/******************************************************************************/ +/**************** MESH LOCAL HANDLER HELPERS ***********************/ +/******************************************************************************/ + +/** + * deregister_app: iterator for removing each application registered by a client + * + * @param cls closure + * @param key the hash of the application id (used to access the hashmap) + * @param value the value stored at the key (client) + * + * @return GNUNET_OK on success + */ +static int +deregister_app (void *cls, const struct GNUNET_HashCode * key, void *value) +{ + struct GNUNET_CONTAINER_MultiHashMap *h = cls; + GNUNET_break (GNUNET_YES == + GNUNET_CONTAINER_multihashmap_remove (h, key, value)); + return GNUNET_OK; +} + +#if LATER +/** + * notify_client_connection_failure: notify a client that the connection to the + * requested remote peer is not possible (for instance, no route found) + * Function called when the socket is ready to queue more data. "buf" will be + * NULL and "size" zero if the socket was closed for writing in the meantime. + * + * @param cls closure + * @param size number of bytes available in buf + * @param buf where the callee should write the message + * @return number of bytes written to buf + */ +static size_t +notify_client_connection_failure (void *cls, size_t size, void *buf) +{ + int size_needed; + struct MeshPeerInfo *peer_info; + struct GNUNET_MESH_PeerControl *msg; + struct GNUNET_PeerIdentity id; + + if (0 == size && NULL == buf) + { + // TODO retry? cancel? + return 0; + } + + size_needed = sizeof (struct GNUNET_MESH_PeerControl); + peer_info = (struct MeshPeerInfo *) cls; + msg = (struct GNUNET_MESH_PeerControl *) buf; + msg->header.size = htons (sizeof (struct GNUNET_MESH_PeerControl)); + msg->header.type = htons (GNUNET_MESSAGE_TYPE_MESH_LOCAL_PEER_DISCONNECTED); +// msg->tunnel_id = htonl(peer_info->t->tid); + GNUNET_PEER_resolve (peer_info->id, &id); + memcpy (&msg->peer, &id, sizeof (struct GNUNET_PeerIdentity)); + + return size_needed; +} +#endif + + +/** + * Send keepalive packets for a peer + * + * @param cls Closure (tunnel for which to send the keepalive). + * @param tc Notification context. + */ +static void +path_refresh (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct MeshTunnel *t = cls; + struct GNUNET_MESH_TunnelKeepAlive *msg; + size_t size = sizeof (struct GNUNET_MESH_TunnelKeepAlive); + char cbuf[size]; + + t->path_refresh_task = GNUNET_SCHEDULER_NO_TASK; + if (0 != (tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN)) + { + return; + } + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "sending keepalive for tunnel %d\n", t->id.tid); + + msg = (struct GNUNET_MESH_TunnelKeepAlive *) cbuf; + msg->header.size = htons (size); + msg->header.type = htons (GNUNET_MESSAGE_TYPE_MESH_PATH_KEEPALIVE); + msg->oid = my_full_id; + msg->tid = htonl (t->id.tid); + tunnel_send_multicast (t, &msg->header); + + t->path_refresh_task = + GNUNET_SCHEDULER_add_delayed (refresh_path_time, &path_refresh, t); + tunnel_reset_timeout(t); +} + + +/** + * Function to process paths received for a new peer addition. The recorded + * paths form the initial tunnel, which can be optimized later. + * Called on each result obtained for the DHT search. + * + * @param cls closure + * @param exp when will this value expire + * @param key key of the result + * @param get_path path of the get request + * @param get_path_length lenght of get_path + * @param put_path path of the put request + * @param put_path_length length of the put_path + * @param type type of the result + * @param size number of bytes in data + * @param data pointer to the result data + * + * TODO: re-issue the request after certain time? cancel after X results? + */ +static void +dht_get_id_handler (void *cls, struct GNUNET_TIME_Absolute exp, + const struct GNUNET_HashCode * key, + const struct GNUNET_PeerIdentity *get_path, + unsigned int get_path_length, + const struct GNUNET_PeerIdentity *put_path, + unsigned int put_path_length, enum GNUNET_BLOCK_Type type, + size_t size, const void *data) +{ + struct MeshPathInfo *path_info = cls; + struct MeshPeerPath *p; + struct GNUNET_PeerIdentity pi; + int i; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Got results from DHT!\n"); + GNUNET_PEER_resolve (path_info->peer->id, &pi); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " for %s\n", GNUNET_i2s (&pi)); + + p = path_build_from_dht (get_path, get_path_length, put_path, + put_path_length); + path_add_to_peers (p, GNUNET_NO); + path_destroy(p); + for (i = 0; i < path_info->peer->ntunnels; i++) + { + tunnel_add_peer (path_info->peer->tunnels[i], path_info->peer); + peer_info_connect (path_info->peer, path_info->t); + } + + return; +} + + +/** + * Function to process paths received for a new peer addition. The recorded + * paths form the initial tunnel, which can be optimized later. + * Called on each result obtained for the DHT search. + * + * @param cls closure + * @param exp when will this value expire + * @param key key of the result + * @param get_path path of the get request + * @param get_path_length lenght of get_path + * @param put_path path of the put request + * @param put_path_length length of the put_path + * @param type type of the result + * @param size number of bytes in data + * @param data pointer to the result data + */ +static void +dht_get_type_handler (void *cls, struct GNUNET_TIME_Absolute exp, + const struct GNUNET_HashCode * key, + const struct GNUNET_PeerIdentity *get_path, + unsigned int get_path_length, + const struct GNUNET_PeerIdentity *put_path, + unsigned int put_path_length, enum GNUNET_BLOCK_Type type, + size_t size, const void *data) +{ + const struct PBlock *pb = data; + const struct GNUNET_PeerIdentity *pi = &pb->id; + struct MeshTunnel *t = cls; + struct MeshPeerInfo *peer_info; + struct MeshPeerPath *p; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "got type DHT result!\n"); + if (size != sizeof (struct PBlock)) + { + GNUNET_break_op (0); + return; + } + if (ntohl(pb->type) != t->type) + { + GNUNET_break_op (0); + return; + } + GNUNET_assert (NULL != t->owner); + peer_info = peer_info_get (pi); + (void) GNUNET_CONTAINER_multihashmap_put (t->peers, &pi->hashPubKey, + peer_info, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_REPLACE); + + p = path_build_from_dht (get_path, get_path_length, put_path, + put_path_length); + path_add_to_peers (p, GNUNET_NO); + path_destroy(p); + tunnel_add_peer (t, peer_info); + peer_info_connect (peer_info, t); +} + + +/******************************************************************************/ +/********************* MESH LOCAL HANDLES **************************/ +/******************************************************************************/ + + +/** + * Handler for client disconnection + * + * @param cls closure + * @param client identification of the client; NULL + * for the last call when the server is destroyed + */ +static void +handle_local_client_disconnect (void *cls, struct GNUNET_SERVER_Client *client) +{ + struct MeshClient *c; + struct MeshClient *next; + unsigned int i; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "client disconnected\n"); + if (client == NULL) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " (SERVER DOWN)\n"); + return; + } + + c = clients; + while (NULL != c) + { + if (c->handle != client) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " ... searching\n"); + c = c->next; + continue; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "matching client found (%u)\n", + c->id); + GNUNET_SERVER_client_drop (c->handle); + c->shutting_down = GNUNET_YES; + GNUNET_assert (NULL != c->own_tunnels); + GNUNET_assert (NULL != c->incoming_tunnels); + GNUNET_CONTAINER_multihashmap_iterate (c->own_tunnels, + &tunnel_destroy_iterator, c); + GNUNET_CONTAINER_multihashmap_iterate (c->incoming_tunnels, + &tunnel_destroy_iterator, c); + GNUNET_CONTAINER_multihashmap_iterate (c->ignore_tunnels, + &tunnel_destroy_iterator, c); + GNUNET_CONTAINER_multihashmap_destroy (c->own_tunnels); + GNUNET_CONTAINER_multihashmap_destroy (c->incoming_tunnels); + GNUNET_CONTAINER_multihashmap_destroy (c->ignore_tunnels); + + /* deregister clients applications */ + if (NULL != c->apps) + { + GNUNET_CONTAINER_multihashmap_iterate (c->apps, &deregister_app, c->apps); + GNUNET_CONTAINER_multihashmap_destroy (c->apps); + } + if (0 == GNUNET_CONTAINER_multihashmap_size (applications) && + GNUNET_SCHEDULER_NO_TASK != announce_applications_task) + { + GNUNET_SCHEDULER_cancel (announce_applications_task); + announce_applications_task = GNUNET_SCHEDULER_NO_TASK; + } + if (NULL != c->types) + GNUNET_CONTAINER_multihashmap_destroy (c->types); + for (i = 0; i < c->n_regex; i++) + { + GNUNET_free (c->regexes[i].regex); + if (NULL != c->regexes[i].h) + GNUNET_REGEX_announce_cancel (c->regexes[i].h); + } + GNUNET_free_non_null (c->regexes); + if (GNUNET_SCHEDULER_NO_TASK != c->regex_announce_task) + GNUNET_SCHEDULER_cancel (c->regex_announce_task); + next = c->next; + GNUNET_CONTAINER_DLL_remove (clients, clients_tail, c); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " CLIENT FREE at %p\n", c); + GNUNET_free (c); + GNUNET_STATISTICS_update (stats, "# clients", -1, GNUNET_NO); + c = next; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " done!\n"); + return; +} + + +/** + * Handler for new clients + * + * @param cls closure + * @param client identification of the client + * @param message the actual message, which includes messages the client wants + */ +static void +handle_local_new_client (void *cls, struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) +{ + struct GNUNET_MESH_ClientConnect *cc_msg; + struct MeshClient *c; + GNUNET_MESH_ApplicationType *a; + unsigned int size; + uint16_t ntypes; + uint16_t *t; + uint16_t napps; + uint16_t i; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "new client connected\n"); + /* Check data sanity */ + size = ntohs (message->size) - sizeof (struct GNUNET_MESH_ClientConnect); + cc_msg = (struct GNUNET_MESH_ClientConnect *) message; + ntypes = ntohs (cc_msg->types); + napps = ntohs (cc_msg->applications); + if (size != + ntypes * sizeof (uint16_t) + napps * sizeof (GNUNET_MESH_ApplicationType)) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + + /* Create new client structure */ + c = GNUNET_malloc (sizeof (struct MeshClient)); + c->id = next_client_id++; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " CLIENT NEW %u\n", c->id); + c->handle = client; + GNUNET_SERVER_client_keep (client); + a = (GNUNET_MESH_ApplicationType *) &cc_msg[1]; + if (napps > 0) + { + GNUNET_MESH_ApplicationType at; + struct GNUNET_HashCode hc; + + c->apps = GNUNET_CONTAINER_multihashmap_create (napps, GNUNET_NO); + for (i = 0; i < napps; i++) + { + at = ntohl (a[i]); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " app type: %u\n", at); + GNUNET_CRYPTO_hash (&at, sizeof (at), &hc); + /* store in clients hashmap */ + GNUNET_CONTAINER_multihashmap_put (c->apps, &hc, (void *) (long) at, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE); + /* store in global hashmap, for announcements */ + GNUNET_CONTAINER_multihashmap_put (applications, &hc, c, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE); + } + if (GNUNET_SCHEDULER_NO_TASK == announce_applications_task) + announce_applications_task = + GNUNET_SCHEDULER_add_now (&announce_applications, NULL); + + } + if (ntypes > 0) + { + uint16_t u16; + struct GNUNET_HashCode hc; + + t = (uint16_t *) & a[napps]; + c->types = GNUNET_CONTAINER_multihashmap_create (ntypes, GNUNET_NO); + for (i = 0; i < ntypes; i++) + { + u16 = ntohs (t[i]); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " msg type: %u\n", u16); + GNUNET_CRYPTO_hash (&u16, sizeof (u16), &hc); + + /* store in clients hashmap */ + GNUNET_CONTAINER_multihashmap_put (c->types, &hc, c, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE); + /* store in global hashmap */ + GNUNET_CONTAINER_multihashmap_put (types, &hc, c, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE); + } + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " client has %u+%u subscriptions\n", napps, ntypes); + + GNUNET_CONTAINER_DLL_insert (clients, clients_tail, c); + c->own_tunnels = GNUNET_CONTAINER_multihashmap_create (32, GNUNET_NO); + c->incoming_tunnels = GNUNET_CONTAINER_multihashmap_create (32, GNUNET_NO); + c->ignore_tunnels = GNUNET_CONTAINER_multihashmap_create (32, GNUNET_NO); + GNUNET_SERVER_notification_context_add (nc, client); + GNUNET_STATISTICS_update (stats, "# clients", 1, GNUNET_NO); + + GNUNET_SERVER_receive_done (client, GNUNET_OK); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "new client processed\n"); +} + + +/** + * Handler for clients announcing available services by a regular expression. + * + * @param cls closure + * @param client identification of the client + * @param message the actual message, which includes messages the client wants + */ +static void +handle_local_announce_regex (void *cls, struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) +{ + const struct GNUNET_MESH_RegexAnnounce *msg; + struct MeshRegexDescriptor rd; + struct MeshClient *c; + char *regex; + size_t len; + size_t offset; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "announce regex started\n"); + + /* Sanity check for client registration */ + if (NULL == (c = client_get (client))) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " by client %u\n", c->id); + + msg = (const struct GNUNET_MESH_RegexAnnounce *) message; + + len = ntohs (message->size) - sizeof(struct GNUNET_MESH_RegexAnnounce); + if (NULL != c->partial_regex) + { + regex = c->partial_regex; + offset = strlen (c->partial_regex); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " continuation, already have %u bytes\n", + offset); + } + else + { + regex = NULL; + offset = 0; + } + + regex = GNUNET_realloc (regex, offset + len + 1); + memcpy (®ex[offset], &msg[1], len); + regex[offset + len] = '\0'; + if (0 == ntohs (msg->last)) + { + c->partial_regex = regex; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " not ended, stored %u bytes for later\n", + len); + GNUNET_SERVER_receive_done (client, GNUNET_OK); + return; + } + rd.regex = regex; + rd.compression = ntohs (msg->compression_characters); + rd.h = NULL; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " length %u\n", len); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " regex %s\n", regex); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " cm %u\n", ntohs(rd.compression)); + GNUNET_array_append (c->regexes, c->n_regex, rd); + c->partial_regex = NULL; + if (GNUNET_SCHEDULER_NO_TASK == c->regex_announce_task) + { + c->regex_announce_task = GNUNET_SCHEDULER_add_now(®ex_announce, c); + } + else + { + regex_put(&rd); + } + GNUNET_SERVER_receive_done (client, GNUNET_OK); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "announce regex processed\n"); +} + + +/** + * Handler for requests of new tunnels + * + * @param cls closure + * @param client identification of the client + * @param message the actual message + */ +static void +handle_local_tunnel_create (void *cls, struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) +{ + struct GNUNET_MESH_TunnelMessage *t_msg; + struct MeshTunnel *t; + struct MeshClient *c; + MESH_TunnelNumber tid; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "new tunnel requested\n"); + + /* Sanity check for client registration */ + if (NULL == (c = client_get (client))) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " by client %u\n", c->id); + + /* Message sanity check */ + if (sizeof (struct GNUNET_MESH_TunnelMessage) != ntohs (message->size)) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + + t_msg = (struct GNUNET_MESH_TunnelMessage *) message; + /* Sanity check for tunnel numbering */ + tid = ntohl (t_msg->tunnel_id); + if (0 == (tid & GNUNET_MESH_LOCAL_TUNNEL_ID_CLI)) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + /* Sanity check for duplicate tunnel IDs */ + if (NULL != tunnel_get_by_local_id (c, tid)) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + + while (NULL != tunnel_get_by_pi (myid, next_tid)) + next_tid = (next_tid + 1) & ~GNUNET_MESH_LOCAL_TUNNEL_ID_CLI; + t = tunnel_new (myid, next_tid++, c, tid); + if (NULL == t) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Tunnel creation failed.\n"); + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + next_tid = next_tid & ~GNUNET_MESH_LOCAL_TUNNEL_ID_CLI; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "CREATED TUNNEL %s [%x] (%x)\n", + GNUNET_i2s (&my_full_id), t->id.tid, t->local_tid); + t->peers = GNUNET_CONTAINER_multihashmap_create (32, GNUNET_NO); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "new tunnel created\n"); + GNUNET_SERVER_receive_done (client, GNUNET_OK); + return; +} + + +/** + * Handler for requests of deleting tunnels + * + * @param cls closure + * @param client identification of the client + * @param message the actual message + */ +static void +handle_local_tunnel_destroy (void *cls, struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) +{ + struct GNUNET_MESH_TunnelMessage *tunnel_msg; + struct MeshClient *c; + struct MeshTunnel *t; + MESH_TunnelNumber tid; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Got a DESTROY TUNNEL from client!\n"); + + /* Sanity check for client registration */ + if (NULL == (c = client_get (client))) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " by client %u\n", c->id); + + /* Message sanity check */ + if (sizeof (struct GNUNET_MESH_TunnelMessage) != ntohs (message->size)) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + + tunnel_msg = (struct GNUNET_MESH_TunnelMessage *) message; + + /* Retrieve tunnel */ + tid = ntohl (tunnel_msg->tunnel_id); + t = tunnel_get_by_local_id(c, tid); + if (NULL == t) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, " tunnel %X not found\n", tid); + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + if (c != t->owner || tid >= GNUNET_MESH_LOCAL_TUNNEL_ID_SERV) + { + client_ignore_tunnel (c, t); + tunnel_destroy_empty (t); + GNUNET_SERVER_receive_done (client, GNUNET_OK); + return; + } + send_client_tunnel_disconnect (t, c); + client_delete_tunnel (c, t); + + /* Don't try to ACK the client about the tunnel_destroy multicast packet */ + t->owner = NULL; + tunnel_send_destroy (t, 0); + t->destroy = GNUNET_YES; + /* The tunnel will be destroyed when the last message is transmitted. */ + GNUNET_SERVER_receive_done (client, GNUNET_OK); + return; +} + + +/** + * Handler for requests of seeting tunnel's speed. + * + * @param cls Closure (unused). + * @param client Identification of the client. + * @param message The actual message. + */ +static void +handle_local_tunnel_speed (void *cls, struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) +{ + struct GNUNET_MESH_TunnelMessage *tunnel_msg; + struct MeshClient *c; + struct MeshTunnel *t; + MESH_TunnelNumber tid; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Got a SPEED request from client!\n"); + + /* Sanity check for client registration */ + if (NULL == (c = client_get (client))) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " by client %u\n", c->id); + + tunnel_msg = (struct GNUNET_MESH_TunnelMessage *) message; + + /* Retrieve tunnel */ + tid = ntohl (tunnel_msg->tunnel_id); + t = tunnel_get_by_local_id(c, tid); + if (NULL == t) + { + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, " tunnel %X not found\n", tid); + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + + switch (ntohs(message->type)) + { + case GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_MIN: + t->speed_min = GNUNET_YES; + break; + case GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_MAX: + t->speed_min = GNUNET_NO; + break; + default: + GNUNET_break (0); + } + GNUNET_SERVER_receive_done (client, GNUNET_OK); +} + + +/** + * Handler for requests of seeting tunnel's buffering policy. + * + * @param cls Closure (unused). + * @param client Identification of the client. + * @param message The actual message. + */ +static void +handle_local_tunnel_buffer (void *cls, struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) +{ + struct GNUNET_MESH_TunnelMessage *tunnel_msg; + struct MeshClient *c; + struct MeshTunnel *t; + MESH_TunnelNumber tid; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Got a BUFFER request from client!\n"); + + /* Sanity check for client registration */ + if (NULL == (c = client_get (client))) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " by client %u\n", c->id); + + tunnel_msg = (struct GNUNET_MESH_TunnelMessage *) message; + + /* Retrieve tunnel */ + tid = ntohl (tunnel_msg->tunnel_id); + t = tunnel_get_by_local_id(c, tid); + if (NULL == t) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, " tunnel %X not found\n", tid); + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + + switch (ntohs(message->type)) + { + case GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_BUFFER: + t->nobuffer = GNUNET_NO; + break; + case GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_NOBUFFER: + t->nobuffer = GNUNET_YES; + break; + default: + GNUNET_break (0); + } + + GNUNET_SERVER_receive_done (client, GNUNET_OK); +} + + +/** + * Handler for connection requests to new peers + * + * @param cls closure + * @param client identification of the client + * @param message the actual message (PeerControl) + */ +static void +handle_local_connect_add (void *cls, struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) +{ + struct GNUNET_MESH_PeerControl *peer_msg; + struct MeshPeerInfo *peer_info; + struct MeshClient *c; + struct MeshTunnel *t; + MESH_TunnelNumber tid; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Got connection request\n"); + /* Sanity check for client registration */ + if (NULL == (c = client_get (client))) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " by client %u\n", c->id); + + peer_msg = (struct GNUNET_MESH_PeerControl *) message; + + /* Sanity check for message size */ + if (sizeof (struct GNUNET_MESH_PeerControl) != ntohs (peer_msg->header.size)) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + + /* Tunnel exists? */ + tid = ntohl (peer_msg->tunnel_id); + t = tunnel_get_by_local_id (c, tid); + if (NULL == t) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + + /* Does client own tunnel? */ + if (t->owner->handle != client) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " for %s\n", + GNUNET_i2s (&peer_msg->peer)); + peer_info = peer_info_get (&peer_msg->peer); + + tunnel_add_peer (t, peer_info); + peer_info_connect (peer_info, t); + + GNUNET_SERVER_receive_done (client, GNUNET_OK); + return; +} + + +/** + * Handler for disconnection requests of peers in a tunnel + * + * @param cls closure + * @param client identification of the client + * @param message the actual message (PeerControl) + */ +static void +handle_local_connect_del (void *cls, struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) +{ + struct GNUNET_MESH_PeerControl *peer_msg; + struct MeshPeerInfo *peer_info; + struct MeshClient *c; + struct MeshTunnel *t; + MESH_TunnelNumber tid; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Got a PEER DEL request\n"); + /* Sanity check for client registration */ + if (NULL == (c = client_get (client))) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " by client %u\n", c->id); + + peer_msg = (struct GNUNET_MESH_PeerControl *) message; + + /* Sanity check for message size */ + if (sizeof (struct GNUNET_MESH_PeerControl) != ntohs (peer_msg->header.size)) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + + /* Tunnel exists? */ + tid = ntohl (peer_msg->tunnel_id); + t = tunnel_get_by_local_id (c, tid); + if (NULL == t) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " on tunnel %X\n", t->id.tid); + + /* Does client own tunnel? */ + if (t->owner->handle != client) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " for peer %s\n", + GNUNET_i2s (&peer_msg->peer)); + /* Is the peer in the tunnel? */ + peer_info = + GNUNET_CONTAINER_multihashmap_get (t->peers, &peer_msg->peer.hashPubKey); + if (NULL == peer_info) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + + /* Ok, delete peer from tunnel */ + GNUNET_CONTAINER_multihashmap_remove_all (t->peers, + &peer_msg->peer.hashPubKey); + + send_destroy_path (t, peer_info->id); + tunnel_delete_peer (t, peer_info->id); + GNUNET_SERVER_receive_done (client, GNUNET_OK); + return; +} + +/** + * Handler for blacklist requests of peers in a tunnel + * + * @param cls closure + * @param client identification of the client + * @param message the actual message (PeerControl) + * + * FIXME implement DHT block bloomfilter + */ +static void +handle_local_blacklist (void *cls, struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) +{ + struct GNUNET_MESH_PeerControl *peer_msg; + struct MeshClient *c; + struct MeshTunnel *t; + MESH_TunnelNumber tid; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Got a PEER BLACKLIST request\n"); + /* Sanity check for client registration */ + if (NULL == (c = client_get (client))) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " by client %u\n", c->id); + + peer_msg = (struct GNUNET_MESH_PeerControl *) message; + + /* Sanity check for message size */ + if (sizeof (struct GNUNET_MESH_PeerControl) != ntohs (peer_msg->header.size)) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + + /* Tunnel exists? */ + tid = ntohl (peer_msg->tunnel_id); + t = tunnel_get_by_local_id (c, tid); + if (NULL == t) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " on tunnel %X\n", t->id.tid); + + GNUNET_array_append(t->blacklisted, t->nblacklisted, + GNUNET_PEER_intern(&peer_msg->peer)); +} + + +/** + * Handler for unblacklist requests of peers in a tunnel + * + * @param cls closure + * @param client identification of the client + * @param message the actual message (PeerControl) + */ +static void +handle_local_unblacklist (void *cls, struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) +{ + struct GNUNET_MESH_PeerControl *peer_msg; + struct MeshClient *c; + struct MeshTunnel *t; + MESH_TunnelNumber tid; + GNUNET_PEER_Id pid; + unsigned int i; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Got a PEER UNBLACKLIST request\n"); + /* Sanity check for client registration */ + if (NULL == (c = client_get (client))) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " by client %u\n", c->id); + + peer_msg = (struct GNUNET_MESH_PeerControl *) message; + + /* Sanity check for message size */ + if (sizeof (struct GNUNET_MESH_PeerControl) != ntohs (peer_msg->header.size)) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + + /* Tunnel exists? */ + tid = ntohl (peer_msg->tunnel_id); + t = tunnel_get_by_local_id (c, tid); + if (NULL == t) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " on tunnel %X\n", t->id.tid); + + /* if peer is not known, complain */ + pid = GNUNET_PEER_search (&peer_msg->peer); + if (0 == pid) + { + GNUNET_break (0); + return; + } + + /* search and remove from list */ + for (i = 0; i < t->nblacklisted; i++) + { + if (t->blacklisted[i] == pid) + { + t->blacklisted[i] = t->blacklisted[t->nblacklisted - 1]; + GNUNET_array_grow (t->blacklisted, t->nblacklisted, t->nblacklisted - 1); + return; + } + } + + /* if peer hasn't been blacklisted, complain */ + GNUNET_break (0); +} + + +/** + * Handler for connection requests to new peers by type + * + * @param cls closure + * @param client identification of the client + * @param message the actual message (ConnectPeerByType) + */ +static void +handle_local_connect_by_type (void *cls, struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) +{ + struct GNUNET_MESH_ConnectPeerByType *connect_msg; + struct MeshClient *c; + struct MeshTunnel *t; + struct GNUNET_HashCode hash; + MESH_TunnelNumber tid; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "got connect by type request\n"); + /* Sanity check for client registration */ + if (NULL == (c = client_get (client))) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " by client %u\n", c->id); + + connect_msg = (struct GNUNET_MESH_ConnectPeerByType *) message; + + /* Sanity check for message size */ + if (sizeof (struct GNUNET_MESH_ConnectPeerByType) != + ntohs (connect_msg->header.size)) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + + /* Tunnel exists? */ + tid = ntohl (connect_msg->tunnel_id); + t = tunnel_get_by_local_id (c, tid); + if (NULL == t) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + + /* Does client own tunnel? */ + if (t->owner->handle != client) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + + /* Do WE have the service? */ + t->type = ntohl (connect_msg->type); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " type requested: %u\n", t->type); + GNUNET_CRYPTO_hash (&t->type, sizeof (GNUNET_MESH_ApplicationType), &hash); + if (GNUNET_CONTAINER_multihashmap_contains (applications, &hash) == + GNUNET_YES) + { + /* Yes! Fast forward, add ourselves to the tunnel and send the + * good news to the client, and alert the destination client of + * an incoming tunnel. + * + * FIXME send a path create to self, avoid code duplication + */ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " available locally\n"); + GNUNET_CONTAINER_multihashmap_put (t->peers, &my_full_id.hashPubKey, + peer_info_get (&my_full_id), + GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_FAST); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " notifying client\n"); + send_client_peer_connected (t, myid); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " Done\n"); + GNUNET_SERVER_receive_done (client, GNUNET_OK); + + t->local_tid_dest = next_local_tid++; + GNUNET_CRYPTO_hash (&t->local_tid_dest, sizeof (MESH_TunnelNumber), &hash); + GNUNET_CONTAINER_multihashmap_put (incoming_tunnels, &hash, t, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_FAST); + + return; + } + /* Ok, lets find a peer offering the service */ + if (NULL != t->dht_get_type) + { + GNUNET_DHT_get_stop (t->dht_get_type); + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " looking in DHT for %s\n", + GNUNET_h2s (&hash)); + t->dht_get_type = + GNUNET_DHT_get_start (dht_handle, + GNUNET_BLOCK_TYPE_MESH_PEER_BY_TYPE, + &hash, + dht_replication_level, + GNUNET_DHT_RO_RECORD_ROUTE | + GNUNET_DHT_RO_DEMULTIPLEX_EVERYWHERE, + NULL, 0, + &dht_get_type_handler, t); + + GNUNET_SERVER_receive_done (client, GNUNET_OK); + return; +} + + +/** + * Handler for connection requests to new peers by a string service description. + * + * @param cls closure + * @param client identification of the client + * @param message the actual message, which includes messages the client wants + */ +static void +handle_local_connect_by_string (void *cls, struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) +{ + struct GNUNET_MESH_ConnectPeerByString *msg; + struct MeshRegexSearchInfo *info; + struct GNUNET_HashCode key; + struct MeshTunnel *t; + struct MeshClient *c; + MESH_TunnelNumber tid; + const char *string; + size_t size; + size_t len; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Connect by string started\n"); + msg = (struct GNUNET_MESH_ConnectPeerByString *) message; + size = htons (message->size); + + /* Sanity check for client registration */ + if (NULL == (c = client_get (client))) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " by client %u\n", c->id); + + /* Message size sanity check */ + if (sizeof(struct GNUNET_MESH_ConnectPeerByString) >= size) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + + /* Tunnel exists? */ + tid = ntohl (msg->tunnel_id); + t = tunnel_get_by_local_id (c, tid); + if (NULL == t) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + + /* Does client own tunnel? */ + if (t->owner->handle != client) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " on tunnel %s [%u]\n", + GNUNET_i2s(&my_full_id), + t->id.tid); + + /* Only one connect_by_string allowed at the same time! */ + /* FIXME: allow more, return handle at api level to cancel, document */ + if (NULL != t->regex_search) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + + /* Find string itself */ + len = size - sizeof(struct GNUNET_MESH_ConnectPeerByString); + string = (const char *) &msg[1]; + + /* Initialize context */ + size = GNUNET_REGEX_get_first_key (string, len, &key); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " consumed %u bits out of %u\n", size, len); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " looking for %s\n", GNUNET_h2s (&key)); + + info = GNUNET_malloc (sizeof (struct MeshRegexSearchInfo)); + info->t = t; + info->description = GNUNET_strndup (string, len); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " string: %s\n", info->description); + + t->regex_search = info; + + info->search_handle = GNUNET_REGEX_search (dht_handle, + info->description, + ®ex_found_handler, info, + stats); + + GNUNET_SERVER_receive_done (client, GNUNET_OK); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "connect by string processed\n"); +} + + +/** + * Handler for client traffic directed to one peer + * + * @param cls closure + * @param client identification of the client + * @param message the actual message + */ +static void +handle_local_unicast (void *cls, struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) +{ + struct MeshClient *c; + struct MeshTunnel *t; + struct MeshPeerInfo *pi; + struct GNUNET_MESH_Unicast *data_msg; + MESH_TunnelNumber tid; + size_t size; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Got a unicast request from a client!\n"); + + /* Sanity check for client registration */ + if (NULL == (c = client_get (client))) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " by client %u\n", c->id); + + data_msg = (struct GNUNET_MESH_Unicast *) message; + + /* Sanity check for message size */ + size = ntohs (message->size); + if (sizeof (struct GNUNET_MESH_Unicast) + + sizeof (struct GNUNET_MessageHeader) > size) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + + /* Tunnel exists? */ + tid = ntohl (data_msg->tid); + t = tunnel_get_by_local_id (c, tid); + if (NULL == t) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + + /* Is it a local tunnel? Then, does client own the tunnel? */ + if (t->owner->handle != client) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + + pi = GNUNET_CONTAINER_multihashmap_get (t->peers, + &data_msg->destination.hashPubKey); + /* Is the selected peer in the tunnel? */ + if (NULL == pi) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + + /* PID should be as expected */ + if (ntohl (data_msg->pid) != t->fwd_pid + 1) + { + GNUNET_break (0); + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + "Unicast PID, expected %u, got %u\n", + t->fwd_pid + 1, ntohl (data_msg->pid)); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + + /* Ok, everything is correct, send the message + * (pretend we got it from a mesh peer) + */ + { + /* Work around const limitation */ + char buf[ntohs (message->size)] GNUNET_ALIGN; + struct GNUNET_MESH_Unicast *copy; + + copy = (struct GNUNET_MESH_Unicast *) buf; + memcpy (buf, data_msg, size); + copy->oid = my_full_id; + copy->tid = htonl (t->id.tid); + copy->ttl = htonl (default_ttl); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " calling generic handler...\n"); + handle_mesh_data_unicast (NULL, &my_full_id, ©->header, NULL, 0); + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "receive done OK\n"); + GNUNET_SERVER_receive_done (client, GNUNET_OK); + + return; +} + + +/** + * Handler for client traffic directed to the origin + * + * @param cls closure + * @param client identification of the client + * @param message the actual message + */ +static void +handle_local_to_origin (void *cls, struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) +{ + struct GNUNET_MESH_ToOrigin *data_msg; + struct MeshTunnelClientInfo *clinfo; + struct MeshClient *c; + struct MeshTunnel *t; + MESH_TunnelNumber tid; + size_t size; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Got a ToOrigin request from a client!\n"); + /* Sanity check for client registration */ + if (NULL == (c = client_get (client))) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " by client %u\n", c->id); + + data_msg = (struct GNUNET_MESH_ToOrigin *) message; + + /* Sanity check for message size */ + size = ntohs (message->size); + if (sizeof (struct GNUNET_MESH_ToOrigin) + + sizeof (struct GNUNET_MessageHeader) > size) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + + /* Tunnel exists? */ + tid = ntohl (data_msg->tid); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " on tunnel %X\n", tid); + if (tid < GNUNET_MESH_LOCAL_TUNNEL_ID_SERV) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + t = tunnel_get_by_local_id (c, tid); + if (NULL == t) + { + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Tunnel %X unknown.\n", tid); + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, " for client %u.\n", c->id); + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + + /* It should be sent by someone who has this as incoming tunnel. */ + if (GNUNET_NO == client_knows_tunnel (c, t)) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + + /* PID should be as expected */ + clinfo = tunnel_get_client_fc (t, c); + if (ntohl (data_msg->pid) != clinfo->bck_pid + 1) + { + GNUNET_break (0); + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + "To Origin PID, expected %u, got %u\n", + clinfo->bck_pid + 1, + ntohl (data_msg->pid)); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + clinfo->bck_pid++; + + /* Ok, everything is correct, send the message + * (pretend we got it from a mesh peer) + */ + { + char buf[ntohs (message->size)] GNUNET_ALIGN; + struct GNUNET_MESH_ToOrigin *copy; + + /* Work around const limitation */ + copy = (struct GNUNET_MESH_ToOrigin *) buf; + memcpy (buf, data_msg, size); + GNUNET_PEER_resolve (t->id.oid, ©->oid); + copy->tid = htonl (t->id.tid); + copy->ttl = htonl (default_ttl); + copy->pid = htonl (t->bck_pid + 1); + + copy->sender = my_full_id; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " calling generic handler...\n"); + handle_mesh_data_to_orig (NULL, &my_full_id, ©->header, NULL, 0); + } + GNUNET_SERVER_receive_done (client, GNUNET_OK); + + return; +} + + +/** + * Handler for client traffic directed to all peers in a tunnel + * + * @param cls closure + * @param client identification of the client + * @param message the actual message + */ +static void +handle_local_multicast (void *cls, struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) +{ + struct MeshClient *c; + struct MeshTunnel *t; + struct GNUNET_MESH_Multicast *data_msg; + MESH_TunnelNumber tid; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Got a multicast request from a client!\n"); + + /* Sanity check for client registration */ + if (NULL == (c = client_get (client))) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " by client %u\n", c->id); + + data_msg = (struct GNUNET_MESH_Multicast *) message; + + /* Sanity check for message size */ + if (sizeof (struct GNUNET_MESH_Multicast) + + sizeof (struct GNUNET_MessageHeader) > ntohs (data_msg->header.size)) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + + /* Tunnel exists? */ + tid = ntohl (data_msg->tid); + t = tunnel_get_by_local_id (c, tid); + if (NULL == t) + { + GNUNET_break (0); + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Tunnel %X unknown.\n", tid); + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, " for client %u.\n", c->id); + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + + /* Does client own tunnel? */ + if (t->owner->handle != client) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + + /* PID should be as expected */ + if (ntohl (data_msg->pid) != t->fwd_pid + 1) + { + GNUNET_break (0); + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + "Multicast PID, expected %u, got %u\n", + t->fwd_pid + 1, ntohl (data_msg->pid)); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + + { + char buf[ntohs (message->size)] GNUNET_ALIGN; + struct GNUNET_MESH_Multicast *copy; + + copy = (struct GNUNET_MESH_Multicast *) buf; + memcpy (buf, message, ntohs (message->size)); + copy->oid = my_full_id; + copy->tid = htonl (t->id.tid); + copy->ttl = htonl (default_ttl); + GNUNET_assert (ntohl (copy->pid) == (t->fwd_pid + 1)); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " calling generic handler...\n"); + handle_mesh_data_multicast (client, &my_full_id, ©->header, NULL, 0); + } + + GNUNET_SERVER_receive_done (t->owner->handle, GNUNET_OK); + return; +} + + +/** + * Handler for client's ACKs for payload traffic. + * + * @param cls Closure (unused). + * @param client Identification of the client. + * @param message The actual message. + */ +static void +handle_local_ack (void *cls, struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) +{ + struct GNUNET_MESH_LocalAck *msg; + struct MeshTunnel *t; + struct MeshClient *c; + MESH_TunnelNumber tid; + uint32_t ack; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Got a local ACK\n"); + /* Sanity check for client registration */ + if (NULL == (c = client_get (client))) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " by client %u\n", c->id); + + msg = (struct GNUNET_MESH_LocalAck *) message; + + /* Tunnel exists? */ + tid = ntohl (msg->tunnel_id); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " on tunnel %X\n", tid); + t = tunnel_get_by_local_id (c, tid); + if (NULL == t) + { + GNUNET_break (0); + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Tunnel %X unknown.\n", tid); + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, " for client %u.\n", c->id); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + + ack = ntohl (msg->max_pid); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " ack %u\n", ack); + + /* Does client own tunnel? I.E: Is this an ACK for BCK traffic? */ + if (NULL != t->owner && t->owner->handle == client) + { + /* The client owns the tunnel, ACK is for data to_origin, send BCK ACK. */ + t->bck_ack = ack; + tunnel_send_bck_ack(t, GNUNET_MESSAGE_TYPE_MESH_LOCAL_ACK); + } + else + { + /* The client doesn't own the tunnel, this ACK is for FWD traffic. */ + tunnel_set_client_fwd_ack (t, c, ack); + tunnel_send_fwd_ack (t, GNUNET_MESSAGE_TYPE_MESH_LOCAL_ACK); + } + + GNUNET_SERVER_receive_done (client, GNUNET_OK); + + return; +} + + +/** + * Iterator over all peers to send a monitoring client info about a tunnel. + * + * @param cls Closure (message being built). + * @param key Key (hashed tunnel ID, unused). + * @param value Peer info. + * + * @return GNUNET_YES, to keep iterating. + */ +static int +monitor_peers_iterator (void *cls, + const struct GNUNET_HashCode * key, + void *value) +{ + struct GNUNET_MESH_LocalMonitor *msg = cls; + struct GNUNET_PeerIdentity *id; + struct MeshPeerInfo *info = value; + + id = (struct GNUNET_PeerIdentity *) &msg[1]; + GNUNET_PEER_resolve (info->id, &id[msg->npeers]); + msg->npeers++; + + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + "* sending info about peer %s [%u]\n", + GNUNET_i2s (&id[msg->npeers - 1]), msg->npeers); + + return GNUNET_YES; +} + + + +/** + * Iterator over all tunnels to send a monitoring client info about each tunnel. + * + * @param cls Closure (client handle). + * @param key Key (hashed tunnel ID, unused). + * @param value Tunnel info. + * + * @return GNUNET_YES, to keep iterating. + */ +static int +monitor_all_tunnels_iterator (void *cls, + const struct GNUNET_HashCode * key, + void *value) +{ + struct GNUNET_SERVER_Client *client = cls; + struct MeshTunnel *t = value; + struct GNUNET_MESH_LocalMonitor *msg; + uint32_t npeers; + + npeers = GNUNET_CONTAINER_multihashmap_size (t->peers); + msg = GNUNET_malloc (sizeof(struct GNUNET_MESH_LocalMonitor) + + npeers * sizeof (struct GNUNET_PeerIdentity)); + GNUNET_PEER_resolve(t->id.oid, &msg->owner); + msg->tunnel_id = htonl (t->id.tid); + msg->header.size = htons (sizeof (struct GNUNET_MESH_LocalMonitor) + + npeers * sizeof (struct GNUNET_PeerIdentity)); + msg->header.type = htons (GNUNET_MESSAGE_TYPE_MESH_LOCAL_INFO_TUNNELS); + msg->npeers = 0; + (void) GNUNET_CONTAINER_multihashmap_iterate (t->peers, + monitor_peers_iterator, + msg); + + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + "* sending info about tunnel %s [%u] (%u peers)\n", + GNUNET_i2s (&msg->owner), t->id.tid, npeers); + + if (msg->npeers != npeers) + { + GNUNET_break (0); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Get tunnels fail: size %u - iter %u\n", + npeers, msg->npeers); + } + + msg->npeers = htonl (npeers); + GNUNET_SERVER_notification_context_unicast (nc, client, + &msg->header, GNUNET_NO); + return GNUNET_YES; +} + + +/** + * Handler for client's MONITOR request. + * + * @param cls Closure (unused). + * @param client Identification of the client. + * @param message The actual message. + */ +static void +handle_local_get_tunnels (void *cls, struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) +{ + struct MeshClient *c; + + /* Sanity check for client registration */ + if (NULL == (c = client_get (client))) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + "Received get tunnels request from client %u\n", + c->id); + GNUNET_CONTAINER_multihashmap_iterate (tunnels, + monitor_all_tunnels_iterator, + client); + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + "Get tunnels request from client %u completed\n", + c->id); + GNUNET_SERVER_receive_done (client, GNUNET_OK); +} + + +/** + * Data needed to build a Monitor_Tunnel message. + */ +struct MeshMonitorTunnelContext +{ + /** + * Partial message, including peer count. + */ + struct GNUNET_MESH_LocalMonitor *msg; + + /** + * Hashmap with positions: peer->position. + */ + struct GNUNET_CONTAINER_MultiHashMap *lookup; + + /** + * Index of the parent of each peer in the message, realtive to the absolute + * order in the array (can be in a previous message). + */ + uint32_t parents[1024]; + + /** + * Peers visited so far in the tree, aka position of the current peer. + */ + unsigned int npeers; + + /** + * Client requesting the info. + */ + struct MeshClient *c; +}; + + +/** + * Send a client a message about the structure of a tunnel. + * + * @param ctx Context of the tunnel iteration, with info regarding the state + * of the execution and the number of peers visited for this message. + */ +static void +send_client_tunnel_info (struct MeshMonitorTunnelContext *ctx) +{ + struct GNUNET_MESH_LocalMonitor *resp = ctx->msg; + struct GNUNET_PeerIdentity *pid; + unsigned int *parent; + size_t size; + + size = sizeof (struct GNUNET_MESH_LocalMonitor); + size += (sizeof (struct GNUNET_PeerIdentity) + sizeof (int)) * resp->npeers; + resp->header.size = htons (size); + pid = (struct GNUNET_PeerIdentity *) &resp[1]; + parent = (unsigned int *) &pid[resp->npeers]; + memcpy (parent, ctx->parents, sizeof(uint32_t) * resp->npeers); + GNUNET_SERVER_notification_context_unicast (nc, ctx->c->handle, + &resp->header, GNUNET_NO); +} + +/** + * Iterator over a tunnel tree to build a message containing all peers + * the in the tunnel, including relay nodes. + * + * @param cls Closure (pointer to pointer of message being built). + * @param peer Short ID of a peer. + * @param parent Short ID of the @c peer 's parent. + */ +static void +tunnel_tree_iterator (void *cls, + GNUNET_PEER_Id peer, + GNUNET_PEER_Id parent) +{ + struct MeshMonitorTunnelContext *ctx = cls; + struct GNUNET_MESH_LocalMonitor *msg; + struct GNUNET_PeerIdentity *pid; + struct GNUNET_PeerIdentity ppid; + + msg = ctx->msg; + pid = (struct GNUNET_PeerIdentity *) &msg[1]; + GNUNET_PEER_resolve (peer, &pid[msg->npeers]); + GNUNET_CONTAINER_multihashmap_put (ctx->lookup, + &pid[msg->npeers].hashPubKey, + (void *) (long) ctx->npeers, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_FAST); + GNUNET_PEER_resolve (parent, &ppid); + ctx->parents[msg->npeers] = + htonl ((long) GNUNET_CONTAINER_multihashmap_get (ctx->lookup, + &ppid.hashPubKey)); + + ctx->npeers++; + msg->npeers++; + + if (sizeof (struct GNUNET_MESH_LocalMonitor) + + (msg->npeers + 1) * + (sizeof (struct GNUNET_PeerIdentity) + sizeof (uint32_t)) + > USHRT_MAX) + { + send_client_tunnel_info (ctx); + msg->npeers = 0; + } +} + + +/** + * Handler for client's MONITOR_TUNNEL request. + * + * @param cls Closure (unused). + * @param client Identification of the client. + * @param message The actual message. + */ +static void +handle_local_show_tunnel (void *cls, struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) +{ + const struct GNUNET_MESH_LocalMonitor *msg; + struct GNUNET_MESH_LocalMonitor *resp; + struct MeshMonitorTunnelContext ctx; + struct MeshClient *c; + struct MeshTunnel *t; + + /* Sanity check for client registration */ + if (NULL == (c = client_get (client))) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + + msg = (struct GNUNET_MESH_LocalMonitor *) message; + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + "Received tunnel info request from client %u for tunnel %s[%X]\n", + c->id, + &msg->owner, + ntohl (msg->tunnel_id)); + t = tunnel_get (&msg->owner, ntohl (msg->tunnel_id)); + if (NULL == t) + { + /* We don't know the tunnel */ + struct GNUNET_MESH_LocalMonitor warn; + + warn = *msg; + warn.npeers = htonl (UINT_MAX); + GNUNET_SERVER_notification_context_unicast (nc, client, + &warn.header, + GNUNET_NO); + GNUNET_SERVER_receive_done (client, GNUNET_OK); + return; + } + + /* Initialize context */ + resp = GNUNET_malloc (USHRT_MAX); /* avoid realloc'ing on each step */ + *resp = *msg; + resp->npeers = 0; + ctx.msg = resp; + ctx.lookup = GNUNET_CONTAINER_multihashmap_create (4 * t->peers_total, + GNUNET_YES); + ctx.c = c; + + /* Collect and send information */ + tree_iterate_all (t->tree, &tunnel_tree_iterator, &ctx); + send_client_tunnel_info (&ctx); + + /* Free context */ + GNUNET_CONTAINER_multihashmap_destroy (ctx.lookup); + GNUNET_free (resp); + + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + "Monitor tunnel request from client %u completed\n", + c->id); + GNUNET_SERVER_receive_done (client, GNUNET_OK); +} + + +/** + * Functions to handle messages from clients + */ +static struct GNUNET_SERVER_MessageHandler client_handlers[] = { + {&handle_local_new_client, NULL, + GNUNET_MESSAGE_TYPE_MESH_LOCAL_CONNECT, 0}, + {&handle_local_announce_regex, NULL, + GNUNET_MESSAGE_TYPE_MESH_LOCAL_ANNOUNCE_REGEX, 0}, + {&handle_local_tunnel_create, NULL, + GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_CREATE, + sizeof (struct GNUNET_MESH_TunnelMessage)}, + {&handle_local_tunnel_destroy, NULL, + GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_DESTROY, + sizeof (struct GNUNET_MESH_TunnelMessage)}, + {&handle_local_tunnel_speed, NULL, + GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_MIN, + sizeof (struct GNUNET_MESH_TunnelMessage)}, + {&handle_local_tunnel_speed, NULL, + GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_MAX, + sizeof (struct GNUNET_MESH_TunnelMessage)}, + {&handle_local_tunnel_buffer, NULL, + GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_BUFFER, + sizeof (struct GNUNET_MESH_TunnelMessage)}, + {&handle_local_tunnel_buffer, NULL, + GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_NOBUFFER, + sizeof (struct GNUNET_MESH_TunnelMessage)}, + {&handle_local_connect_add, NULL, + GNUNET_MESSAGE_TYPE_MESH_LOCAL_PEER_ADD, + sizeof (struct GNUNET_MESH_PeerControl)}, + {&handle_local_connect_del, NULL, + GNUNET_MESSAGE_TYPE_MESH_LOCAL_PEER_DEL, + sizeof (struct GNUNET_MESH_PeerControl)}, + {&handle_local_blacklist, NULL, + GNUNET_MESSAGE_TYPE_MESH_LOCAL_PEER_BLACKLIST, + sizeof (struct GNUNET_MESH_PeerControl)}, + {&handle_local_unblacklist, NULL, + GNUNET_MESSAGE_TYPE_MESH_LOCAL_PEER_UNBLACKLIST, + sizeof (struct GNUNET_MESH_PeerControl)}, + {&handle_local_connect_by_type, NULL, + GNUNET_MESSAGE_TYPE_MESH_LOCAL_PEER_ADD_BY_TYPE, + sizeof (struct GNUNET_MESH_ConnectPeerByType)}, + {&handle_local_connect_by_string, NULL, + GNUNET_MESSAGE_TYPE_MESH_LOCAL_PEER_ADD_BY_STRING, 0}, + {&handle_local_unicast, NULL, + GNUNET_MESSAGE_TYPE_MESH_UNICAST, 0}, + {&handle_local_to_origin, NULL, + GNUNET_MESSAGE_TYPE_MESH_TO_ORIGIN, 0}, + {&handle_local_multicast, NULL, + GNUNET_MESSAGE_TYPE_MESH_MULTICAST, 0}, + {&handle_local_ack, NULL, + GNUNET_MESSAGE_TYPE_MESH_LOCAL_ACK, + sizeof (struct GNUNET_MESH_LocalAck)}, + {&handle_local_get_tunnels, NULL, + GNUNET_MESSAGE_TYPE_MESH_LOCAL_INFO_TUNNELS, + sizeof (struct GNUNET_MessageHeader)}, + {&handle_local_show_tunnel, NULL, + GNUNET_MESSAGE_TYPE_MESH_LOCAL_INFO_TUNNEL, + sizeof (struct GNUNET_MESH_LocalMonitor)}, + {NULL, NULL, 0, 0} +}; + + +/** + * To be called on core init/fail. + * + * @param cls service closure + * @param server handle to the server for this service + * @param identity the public identity of this peer + */ +static void +core_init (void *cls, struct GNUNET_CORE_Handle *server, + const struct GNUNET_PeerIdentity *identity) +{ + static int i = 0; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Core init\n"); + core_handle = server; + if (0 != memcmp (identity, &my_full_id, sizeof (my_full_id)) || + NULL == server) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("Wrong CORE service\n")); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + " core id %s\n", + GNUNET_i2s (identity)); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + " my id %s\n", + GNUNET_i2s (&my_full_id)); + GNUNET_SCHEDULER_shutdown (); // Try gracefully + if (10 < i++) + GNUNET_abort(); // Try harder + } + return; +} + + +/** + * Method called whenever a given peer connects. + * + * @param cls closure + * @param peer peer identity this notification is about + * @param atsi performance data for the connection + * @param atsi_count number of records in 'atsi' + */ +static void +core_connect (void *cls, const struct GNUNET_PeerIdentity *peer, + const struct GNUNET_ATS_Information *atsi, + unsigned int atsi_count) +{ + struct MeshPeerInfo *peer_info; + struct MeshPeerPath *path; + + DEBUG_CONN ("Peer connected\n"); + DEBUG_CONN (" %s\n", GNUNET_i2s (&my_full_id)); + peer_info = peer_info_get (peer); + if (myid == peer_info->id) + { + DEBUG_CONN (" (self)\n"); + return; + } + else + { + DEBUG_CONN (" %s\n", GNUNET_i2s (peer)); + } + path = path_new (2); + path->peers[0] = myid; + path->peers[1] = peer_info->id; + GNUNET_PEER_change_rc (myid, 1); + GNUNET_PEER_change_rc (peer_info->id, 1); + peer_info_add_path (peer_info, path, GNUNET_YES); + GNUNET_STATISTICS_update (stats, "# peers", 1, GNUNET_NO); + return; +} + + +/** + * Method called whenever a peer disconnects. + * + * @param cls closure + * @param peer peer identity this notification is about + */ +static void +core_disconnect (void *cls, const struct GNUNET_PeerIdentity *peer) +{ + struct MeshPeerInfo *pi; + struct MeshPeerQueue *q; + struct MeshPeerQueue *n; + + DEBUG_CONN ("Peer disconnected\n"); + pi = GNUNET_CONTAINER_multihashmap_get (peers, &peer->hashPubKey); + if (NULL == pi) + { + GNUNET_break (0); + return; + } + q = pi->queue_head; + while (NULL != q) + { + n = q->next; + /* TODO try to reroute this traffic instead */ + queue_destroy(q, GNUNET_YES); + q = n; + } + if (NULL != pi->core_transmit) + { + GNUNET_CORE_notify_transmit_ready_cancel(pi->core_transmit); + pi->core_transmit = NULL; + } + peer_info_remove_path (pi, pi->id, myid); + if (myid == pi->id) + { + DEBUG_CONN (" (self)\n"); + } + GNUNET_STATISTICS_update (stats, "# peers", -1, GNUNET_NO); + return; +} + + +/******************************************************************************/ +/************************ MAIN FUNCTIONS ****************************/ +/******************************************************************************/ + +/** + * Iterator over tunnel hash map entries to destroy the tunnel during shutdown. + * + * @param cls closure + * @param key current key code + * @param value value in the hash map + * @return GNUNET_YES if we should continue to iterate, + * GNUNET_NO if not. + */ +static int +shutdown_tunnel (void *cls, const struct GNUNET_HashCode * key, void *value) +{ + struct MeshTunnel *t = value; + + tunnel_destroy (t); + return GNUNET_YES; +} + +/** + * Iterator over peer hash map entries to destroy the tunnel during shutdown. + * + * @param cls closure + * @param key current key code + * @param value value in the hash map + * @return GNUNET_YES if we should continue to iterate, + * GNUNET_NO if not. + */ +static int +shutdown_peer (void *cls, const struct GNUNET_HashCode * key, void *value) +{ + struct MeshPeerInfo *p = value; + struct MeshPeerQueue *q; + struct MeshPeerQueue *n; + + q = p->queue_head; + while (NULL != q) + { + n = q->next; + if (q->peer == p) + { + queue_destroy(q, GNUNET_YES); + } + q = n; + } + peer_info_destroy (p); + return GNUNET_YES; +} + + +/** + * Task run during shutdown. + * + * @param cls unused + * @param tc unused + */ +static void +shutdown_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "shutting down\n"); + + if (core_handle != NULL) + { + GNUNET_CORE_disconnect (core_handle); + core_handle = NULL; + } + if (NULL != keygen) + { + GNUNET_CRYPTO_rsa_key_create_stop (keygen); + keygen = NULL; + } + GNUNET_CONTAINER_multihashmap_iterate (tunnels, &shutdown_tunnel, NULL); + GNUNET_CONTAINER_multihashmap_iterate (peers, &shutdown_peer, NULL); + if (dht_handle != NULL) + { + GNUNET_DHT_disconnect (dht_handle); + dht_handle = NULL; + } + if (nc != NULL) + { + GNUNET_SERVER_notification_context_destroy (nc); + nc = NULL; + } + if (GNUNET_SCHEDULER_NO_TASK != announce_id_task) + { + GNUNET_SCHEDULER_cancel (announce_id_task); + announce_id_task = GNUNET_SCHEDULER_NO_TASK; + } + if (GNUNET_SCHEDULER_NO_TASK != announce_applications_task) + { + GNUNET_SCHEDULER_cancel (announce_applications_task); + announce_applications_task = GNUNET_SCHEDULER_NO_TASK; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "shut down\n"); +} + + +/** + * Callback for hostkey read/generation + * + * @param cls Closure (Configuration handle). + * @param pk the private key + * @param emsg error message + */ +static void +key_generation_cb (void *cls, + struct GNUNET_CRYPTO_RsaPrivateKey *pk, + const char *emsg) +{ + const struct GNUNET_CONFIGURATION_Handle *c = cls; + struct MeshPeerInfo *peer; + struct MeshPeerPath *p; + + keygen = NULL; + if (NULL == pk) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Mesh service could not access hostkey: %s. Exiting.\n"), + emsg); + GNUNET_SCHEDULER_shutdown (); + return; + } + my_private_key = pk; + GNUNET_CRYPTO_rsa_key_get_public (my_private_key, &my_public_key); + GNUNET_CRYPTO_hash (&my_public_key, sizeof (my_public_key), + &my_full_id.hashPubKey); + myid = GNUNET_PEER_intern (&my_full_id); + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + "Mesh for peer [%s] starting\n", + GNUNET_i2s(&my_full_id)); + +// transport_handle = GNUNET_TRANSPORT_connect(c, +// &my_full_id, +// NULL, +// NULL, +// NULL, +// NULL); + + core_handle = GNUNET_CORE_connect (c, /* Main configuration */ + NULL, /* Closure passed to MESH functions */ + &core_init, /* Call core_init once connected */ + &core_connect, /* Handle connects */ + &core_disconnect, /* remove peers on disconnects */ + NULL, /* Don't notify about all incoming messages */ + GNUNET_NO, /* For header only in notification */ + NULL, /* Don't notify about all outbound messages */ + GNUNET_NO, /* For header-only out notification */ + core_handlers); /* Register these handlers */ + + if (core_handle == NULL) + { + GNUNET_break (0); + GNUNET_SCHEDULER_shutdown (); + return; + } + + next_tid = 0; + next_local_tid = GNUNET_MESH_LOCAL_TUNNEL_ID_SERV; + + + GNUNET_SERVER_add_handlers (server_handle, client_handlers); + nc = GNUNET_SERVER_notification_context_create (server_handle, 1); + GNUNET_SERVER_disconnect_notify (server_handle, + &handle_local_client_disconnect, NULL); + + + clients = NULL; + clients_tail = NULL; + next_client_id = 0; + + announce_applications_task = GNUNET_SCHEDULER_NO_TASK; + announce_id_task = GNUNET_SCHEDULER_add_now (&announce_id, cls); + + /* Create a peer_info for the local peer */ + peer = peer_info_get (&my_full_id); + p = path_new (1); + p->peers[0] = myid; + GNUNET_PEER_change_rc (myid, 1); + peer_info_add_path (peer, p, GNUNET_YES); + GNUNET_SERVER_resume (server_handle); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Mesh service running\n"); +} + + +/** + * Process mesh requests. + * + * @param cls closure + * @param server the initialized server + * @param c configuration to use + */ +static void +run (void *cls, struct GNUNET_SERVER_Handle *server, + const struct GNUNET_CONFIGURATION_Handle *c) +{ + char *keyfile; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "starting to run\n"); + server_handle = server; + + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_filename (c, "GNUNETD", "HOSTKEY", + &keyfile)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _ + ("%s service is lacking key configuration settings (%s). Exiting.\n"), + "mesh", "hostkey"); + GNUNET_SCHEDULER_shutdown (); + return; + } + + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_time (c, "MESH", "REFRESH_PATH_TIME", + &refresh_path_time)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _ + ("%s service is lacking key configuration settings (%s). Exiting.\n"), + "mesh", "refresh path time"); + GNUNET_SCHEDULER_shutdown (); + return; + } + + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_time (c, "MESH", "APP_ANNOUNCE_TIME", + &app_announce_time)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _ + ("%s service is lacking key configuration settings (%s). Exiting.\n"), + "mesh", "app announce time"); + GNUNET_SCHEDULER_shutdown (); + return; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "APP_ANNOUNCE_TIME %llu ms\n", + app_announce_time.rel_value); + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_time (c, "MESH", "ID_ANNOUNCE_TIME", + &id_announce_time)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _ + ("%s service is lacking key configuration settings (%s). Exiting.\n"), + "mesh", "id announce time"); + GNUNET_SCHEDULER_shutdown (); + return; + } + + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_time (c, "MESH", "CONNECT_TIMEOUT", + &connect_timeout)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _ + ("%s service is lacking key configuration settings (%s). Exiting.\n"), + "mesh", "connect timeout"); + GNUNET_SCHEDULER_shutdown (); + return; + } + + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_number (c, "MESH", "MAX_MSGS_QUEUE", + &max_msgs_queue)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _ + ("%s service is lacking key configuration settings (%s). Exiting.\n"), + "mesh", "max msgs queue"); + GNUNET_SCHEDULER_shutdown (); + return; + } + + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_number (c, "MESH", "MAX_TUNNELS", + &max_tunnels)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _ + ("%s service is lacking key configuration settings (%s). Exiting.\n"), + "mesh", "max tunnels"); + GNUNET_SCHEDULER_shutdown (); + return; + } + + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_number (c, "MESH", "DEFAULT_TTL", + &default_ttl)) + { + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + _ + ("%s service is lacking key configuration settings (%s). Using default (%u).\n"), + "mesh", "default ttl", 64); + default_ttl = 64; + } + + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_number (c, "MESH", "MAX_PEERS", + &max_peers)) + { + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + _("%s service is lacking key configuration settings (%s). Using default (%u).\n"), + "mesh", "max peers", 1000); + max_peers = 1000; + } + + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_number (c, "MESH", "DHT_REPLICATION_LEVEL", + &dht_replication_level)) + { + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + _ + ("%s service is lacking key configuration settings (%s). Using default (%u).\n"), + "mesh", "dht replication level", 3); + dht_replication_level = 3; + } + + tunnels = GNUNET_CONTAINER_multihashmap_create (32, GNUNET_NO); + incoming_tunnels = GNUNET_CONTAINER_multihashmap_create (32, GNUNET_NO); + peers = GNUNET_CONTAINER_multihashmap_create (32, GNUNET_NO); + applications = GNUNET_CONTAINER_multihashmap_create (32, GNUNET_NO); + types = GNUNET_CONTAINER_multihashmap_create (32, GNUNET_NO); + + dht_handle = GNUNET_DHT_connect (c, 64); + if (NULL == dht_handle) + { + GNUNET_break (0); + } + stats = GNUNET_STATISTICS_create ("mesh", c); + + GNUNET_SERVER_suspend (server_handle); + /* Scheduled the task to clean up when shutdown is called */ + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, &shutdown_task, + NULL); + keygen = GNUNET_CRYPTO_rsa_key_create_start (keyfile, + &key_generation_cb, + (void *) c); + GNUNET_free (keyfile); +} + + +/** + * The main function for the mesh service. + * + * @param argc number of arguments from the command line + * @param argv command line arguments + * @return 0 ok, 1 on error + */ +int +main (int argc, char *const *argv) +{ + int ret; + int r; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "main()\n"); + r = GNUNET_SERVICE_run (argc, argv, "mesh", GNUNET_SERVICE_OPTION_NONE, &run, + NULL); + ret = (GNUNET_OK == r) ? 0 : 1; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "main() END\n"); + + INTERVAL_SHOW; + + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + "Mesh for peer [%s] FWD ACKs %u, BCK ACKs %u\n", + GNUNET_i2s(&my_full_id), debug_fwd_ack, debug_bck_ack); + + return ret; +} diff --git a/src/mesh/gnunet-service-mesh.c b/src/mesh/gnunet-service-mesh.c index 36c6115..2ee5b9d 100644 --- a/src/mesh/gnunet-service-mesh.c +++ b/src/mesh/gnunet-service-mesh.c @@ -1,6 +1,6 @@ /* This file is part of GNUnet. - (C) 2001 - 2011 Christian Grothoff (and other contributing authors) + (C) 2001-2012 Christian Grothoff (and other contributing authors) GNUnet is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published @@ -37,41 +37,33 @@ * TODO: * - error reporting (CREATE/CHANGE/ADD/DEL?) -- new message! * - partial disconnect reporting -- same as error reporting? - * - add vs create? change vs. keep-alive? same msg or different ones? -- thinking... - * - speed requirement specification (change?) in mesh API -- API call * - add ping message * - relay corking down to core * - set ttl relative to tree depth + * - Add data ACK count in path ACK + * - Make common GNUNET_MESH_Data header for unicast, to_orig, multicast * TODO END */ #include "platform.h" #include "mesh.h" #include "mesh_protocol.h" -#include "gnunet_dht_service.h" #include "mesh_tunnel_tree.h" +#include "block_mesh.h" +#include "gnunet_dht_service.h" +#include "gnunet_statistics_service.h" +#include "gnunet_regex_lib.h" -/* TODO: move into configuration file */ -#define REFRESH_PATH_TIME GNUNET_TIME_relative_multiply(\ - GNUNET_TIME_UNIT_SECONDS,\ - 300) -#define APP_ANNOUNCE_TIME GNUNET_TIME_relative_multiply(\ - GNUNET_TIME_UNIT_SECONDS,\ - 5) - -#define ID_ANNOUNCE_TIME GNUNET_TIME_relative_multiply(\ - GNUNET_TIME_UNIT_SECONDS,\ - 5) - -#define UNACKNOWLEDGED_WAIT GNUNET_TIME_relative_multiply(\ - GNUNET_TIME_UNIT_SECONDS,\ - 2) -#define DEFAULT_TTL 64 +#define MESH_BLOOM_SIZE 128 -/* TODO END */ +#define MESH_DEBUG_REGEX GNUNET_YES +#define MESH_DEBUG_DHT GNUNET_NO +#define MESH_DEBUG_CONNECTION GNUNET_NO +#define MESH_DEBUG_TIMING __LINUX__ && GNUNET_NO -#define MESH_DEBUG_DHT GNUNET_YES -#define MESH_DEBUG_CONNECTION GNUNET_NO +#define MESH_MAX_POLL_TIME GNUNET_TIME_relative_multiply (\ + GNUNET_TIME_UNIT_MINUTES,\ + 10) #if MESH_DEBUG_CONNECTION #define DEBUG_CONN(...) GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, __VA_ARGS__) @@ -85,12 +77,43 @@ #define DEBUG_DHT(...) #endif +#if MESH_DEBUG_REGEX +#define DEBUG_REGEX(...) GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, __VA_ARGS__) +#else +#define DEBUG_REGEX(...) +#endif + +#if MESH_DEBUG_TIMING +#include +double __sum; +uint64_t __count; +struct timespec __mesh_start; +struct timespec __mesh_end; +#define INTERVAL_START clock_gettime(CLOCK_PROCESS_CPUTIME_ID, &(__mesh_start)) +#define INTERVAL_END \ +do {\ + clock_gettime(CLOCK_PROCESS_CPUTIME_ID, &(__mesh_end));\ + double __diff = __mesh_end.tv_nsec - __mesh_start.tv_nsec;\ + if (__diff < 0) __diff += 1000000000;\ + __sum += __diff;\ + __count++;\ +} while (0) +#define INTERVAL_SHOW \ +if (0 < __count)\ + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "AVG process time: %f ns\n", __sum/__count) +#else +#define INTERVAL_START +#define INTERVAL_END +#define INTERVAL_SHOW +#endif + /******************************************************************************/ /************************ DATA STRUCTURES ****************************/ /******************************************************************************/ /** FWD declaration */ struct MeshPeerInfo; +struct MeshClient; /** @@ -101,12 +124,11 @@ struct MeshData /** Tunnel it belongs to. */ struct MeshTunnel *t; - /** In case of a multicast, task to allow a client to send more data if - * some neighbor is too slow. */ - GNUNET_SCHEDULER_TaskIdentifier *task; + /** How many remaining neighbors still hav't got it. */ + unsigned int reference_counter; /** How many remaining neighbors we need to send this to. */ - unsigned int *reference_counter; + unsigned int total_out; /** Size of the data. */ size_t data_len; @@ -116,6 +138,121 @@ struct MeshData }; +/** + * Struct containing info about a queued transmission to this peer + */ +struct MeshPeerQueue +{ + /** + * DLL next + */ + struct MeshPeerQueue *next; + + /** + * DLL previous + */ + struct MeshPeerQueue *prev; + + /** + * Peer this transmission is directed to. + */ + struct MeshPeerInfo *peer; + + /** + * Tunnel this message belongs to. + */ + struct MeshTunnel *tunnel; + + /** + * Pointer to info stucture used as cls. + */ + void *cls; + + /** + * Type of message + */ + uint16_t type; + + /** + * Size of the message + */ + size_t size; +}; + + +/** + * Struct to store regex information announced by clients. + */ +struct MeshRegexDescriptor +{ + /** + * Regular expression itself. + */ + char *regex; + + /** + * How many characters per edge can we squeeze? + */ + uint16_t compression; + + /** + * Handle to announce the regex. + */ + struct GNUNET_REGEX_announce_handle *h; +}; + + +/** + * Struct to keep information of searches of services described by a regex + * using a user-provided string service description. + */ +struct MeshRegexSearchInfo +{ + /** + * Which tunnel is this for + */ + struct MeshTunnel *t; + + /** + * User provided description of the searched service. + */ + char *description; + + /** + * Regex search handle. + */ + struct GNUNET_REGEX_search_handle *search_handle; + + /** + * Peer that is connecting via connect_by_string. When connected, free ctx. + */ + GNUNET_PEER_Id peer; + + /** + * Other peers that are found but not yet being connected to. + */ + GNUNET_PEER_Id *peers; + + /** + * Number of elements in peers. + */ + unsigned int n_peers; + + /** + * Next peer to try to connect to. + */ + unsigned int i_peer; + + /** + * Timeout for a connect attempt. + * When reached, try to connect to a different peer, if any. If not, + * try the same peer again. + */ + GNUNET_SCHEDULER_TaskIdentifier timeout; + +}; + + /** * Struct containing all info possibly needed to build a package when called * back by core. @@ -131,9 +268,6 @@ struct MeshTransmissionDescriptor /** Ultimate destination of the packet */ GNUNET_PEER_Id destination; - /** Which handler was used to request the transmission */ - unsigned int handler_n; - /** Data descriptor */ struct MeshData* mesh_data; }; @@ -154,6 +288,11 @@ struct MeshPeerInfo */ struct GNUNET_TIME_Absolute last_contact; + /** + * Task handler for delayed connect task; + */ + GNUNET_SCHEDULER_TaskIdentifier connect_task; + /** * Number of attempts to reconnect so far */ @@ -179,21 +318,6 @@ struct MeshPeerInfo */ struct MeshPathInfo *dhtgetcls; - /** - * Handles to stop queued transmissions for this peer - */ - struct GNUNET_CORE_TransmitHandle *core_transmit[CORE_QUEUE_SIZE]; - - /** - * Pointer to info stuctures used as cls for queued transmissions - */ - void *infos[CORE_QUEUE_SIZE]; - - /** - * Type of message being in each transmission - */ - uint16_t types[CORE_QUEUE_SIZE]; - /** * Array of tunnels this peer participates in * (most probably a small amount, therefore not a hashmap) @@ -206,46 +330,29 @@ struct MeshPeerInfo * Number of tunnels this peers participates in */ unsigned int ntunnels; -}; + /** + * Transmission queue to core DLL head + */ + struct MeshPeerQueue *queue_head; -/** - * Data scheduled to transmit (to local client or remote peer) - */ -struct MeshQueue -{ - /** - * Double linked list - */ - struct MeshQueue *next; - struct MeshQueue *prev; - - /** - * Target of the data (NULL if target is client) - */ - struct MeshPeerInfo *peer; - - /** - * Client to send the data to (NULL if target is peer) - */ - struct MeshClient *client; - - /** - * Size of the message to transmit - */ - unsigned int size; + /** + * Transmission queue to core DLL tail + */ + struct MeshPeerQueue *queue_tail; - /** - * How old is the data? - */ - struct GNUNET_TIME_Absolute timestamp; + /** + * How many messages are in the queue to this peer. + */ + unsigned int queue_n; - /** - * Data itself - */ - struct GNUNET_MessageHeader *data; + /** + * Handle to for queued transmissions + */ + struct GNUNET_CORE_TransmitHandle *core_transmit; }; + /** * Globally unique tunnel identification (owner + number) * DO NOT USE OVER THE NETWORK @@ -265,8 +372,6 @@ struct MESH_TunnelID }; -struct MeshClient; /* FWD declaration */ - /** * Struct containing all information regarding a tunnel * For an intermediate node the improtant info used will be: @@ -294,9 +399,77 @@ struct MeshTunnel MESH_TunnelNumber local_tid_dest; /** - * ID of the last multicast packet seen/sent. + * Is the speed on the tunnel limited to the slowest peer? + */ + int speed_min; + + /** + * Is the tunnel bufferless (minimum latency)? + */ + int nobuffer; + + /** + * Packet ID of the last fwd packet seen (sent/retransmitted/received). + */ + uint32_t fwd_pid; + + /** + * Packet ID of the last bck packet sent (unique counter per hop). + */ + uint32_t bck_pid; + + /** + * SKIP value for this tunnel. + */ + uint32_t skip; + + /** + * Force sending ACK? Flag to allow duplicate ACK on POLL. + */ + int force_ack; + + /** + * MeshTunnelChildInfo of all children, indexed by GNUNET_PEER_Id. + * Contains the Flow Control info: FWD ACK value received, + * last BCK ACK sent, PID and SKIP values. + */ + struct GNUNET_CONTAINER_MultiHashMap *children_fc; + + /** + * Last ACK sent towards the origin (for traffic towards leaf node). + */ + uint32_t last_fwd_ack; + + /** + * BCK ACK value received from the hop towards the owner of the tunnel, + * (previous node / owner): up to what message PID can we sent back to him. + */ + uint32_t bck_ack; + + /** + * How many messages are in the forward queue (towards leaves). + */ + unsigned int fwd_queue_n; + + /** + * How many messages do we accept in the forward queue. + */ + unsigned int fwd_queue_max; + + /** + * How many messages are in the backward queue (towards origin). + */ + unsigned int bck_queue_n; + + /** + * How many messages do we accept in the backward queue. + */ + unsigned int bck_queue_max; + + /** + * Task to poll peer in case of a stall. */ - uint32_t mid; + GNUNET_SCHEDULER_TaskIdentifier fc_poll_bck; /** * Last time the tunnel was used @@ -325,17 +498,22 @@ struct MeshTunnel struct MeshClient *owner; /** - * Clients that have been informed about the tunnel, if any + * Clients that have been informed about and want to stay in the tunnel. */ struct MeshClient **clients; /** - * Number of elements in clients + * Flow control info for each client. + */ + struct MeshTunnelClientInfo *clients_fc; + + /** + * Number of elements in clients/clients_fc */ unsigned int nclients; /** - * Clients that have requested to leave the tunnel + * Clients that have been informed but requested to leave the tunnel. */ struct MeshClient **ignore; @@ -345,10 +523,19 @@ struct MeshTunnel unsigned int nignore; /** - * Messages ready to transmit + * Blacklisted peers + */ + GNUNET_PEER_Id *blacklisted; + + /** + * Number of elements in blacklisted */ - struct MeshQueue *queue_head; - struct MeshQueue *queue_tail; + unsigned int nblacklisted; + + /** + * Bloomfilter (for peer identities) to stop circular routes + */ + char bloomfilter[MESH_BLOOM_SIZE]; /** * Tunnel paths @@ -365,120 +552,281 @@ struct MeshTunnel */ struct GNUNET_DHT_GetHandle *dht_get_type; - /** - * Task to keep the used paths alive - */ + /** + * Handle for the regex search for a connect_by_string + */ + struct MeshRegexSearchInfo *regex_search; + + /** + * Task to keep the used paths alive + */ GNUNET_SCHEDULER_TaskIdentifier path_refresh_task; - /** - * Task to destroy the tunnel after timeout - * - * FIXME: merge the two? a tunnel will have either - * a path refresh OR a timeout, never both! - */ + /** + * Task to destroy the tunnel after timeout + * + * FIXME: merge the two? a tunnel will have either + * a path refresh OR a timeout, never both! + */ GNUNET_SCHEDULER_TaskIdentifier timeout_task; -}; - - -/** - * Info needed to work with tunnel paths and peers - */ -struct MeshPathInfo -{ - /** - * Tunnel - */ - struct MeshTunnel *t; - /** - * Neighbouring peer to whom we send the packet to - */ - struct MeshPeerInfo *peer; + /** + * Flag to signal the destruction of the tunnel. + * If this is set GNUNET_YES the tunnel will be destroyed + * when the queue is empty. + */ + int destroy; - /** - * Path itself - */ - struct MeshPeerPath *path; + /** + * Total messages pending for this tunnels, payload or not. + */ + unsigned int pending_messages; /** - * Position in peer's transmit queue + * If the tunnel is empty, destoy it. */ - unsigned int pos; + GNUNET_SCHEDULER_TaskIdentifier delayed_destroy; }; /** - * Struct containing information about a client of the service + * Info about a child node in a tunnel, needed to perform flow control. */ -struct MeshClient +struct MeshTunnelChildInfo { /** - * Linked list next + * ID of the child node. */ - struct MeshClient *next; + GNUNET_PEER_Id id; /** - * Linked list prev + * SKIP value. */ - struct MeshClient *prev; + uint32_t skip; /** - * Tunnels that belong to this client, indexed by local id + * Last sent PID. */ - struct GNUNET_CONTAINER_MultiHashMap *own_tunnels; + uint32_t fwd_pid; - /** - * Tunnels this client has accepted, indexed by incoming local id + /** + * Last received PID. */ - struct GNUNET_CONTAINER_MultiHashMap *incoming_tunnels; + uint32_t bck_pid; - /** - * Tunnels this client has rejected, indexed by incoming local id - */ - struct GNUNET_CONTAINER_MultiHashMap *ignore_tunnels; /** - * Handle to communicate with the client + * Maximum PID allowed (FWD ACK received). */ - struct GNUNET_SERVER_Client *handle; + uint32_t fwd_ack; /** - * Applications that this client has claimed to provide + * Last ACK sent to that child (BCK ACK). */ - struct GNUNET_CONTAINER_MultiHashMap *apps; + uint32_t bck_ack; /** - * Messages that this client has declared interest in + * Circular buffer pointing to MeshPeerQueue elements for all + * payload traffic going to this child. + * Size determined by the tunnel queue size (@c t->fwd_queue_max). */ - struct GNUNET_CONTAINER_MultiHashMap *types; + struct MeshPeerQueue **send_buffer; /** - * Whether the client is active or shutting down (don't send confirmations - * to a client that is shutting down. + * Index of the oldest element in the send_buffer. */ - int shutting_down; + unsigned int send_buffer_start; /** - * ID of the client, mainly for debug messages + * How many elements are already in the buffer. */ - unsigned int id; + unsigned int send_buffer_n; -}; + /** + * Tunnel this info is about + */ + struct MeshTunnel *t; + /** + * Task to poll peer in case of a stall. + */ + GNUNET_SCHEDULER_TaskIdentifier fc_poll; + /** + * Time to use for next polling call. + */ + struct GNUNET_TIME_Relative fc_poll_time; +}; -/******************************************************************************/ -/************************ DEBUG FUNCTIONS ****************************/ -/******************************************************************************/ -#if MESH_DEBUG /** - * GNUNET_SCHEDULER_Task for printing a message after some operation is done - * @param cls string to print - * @param success GNUNET_OK if the PUT was transmitted, - * GNUNET_NO on timeout, - * GNUNET_SYSERR on disconnect from service - * after the PUT message was transmitted - * (so we don't know if it was received or not) + * Info about a leaf client of a tunnel, needed to perform flow control. + */ +struct MeshTunnelClientInfo +{ + /** + * PID of the last packet sent to the client (FWD). + */ + uint32_t fwd_pid; + + /** + * PID of the last packet received from the client (BCK). + */ + uint32_t bck_pid; + + /** + * Maximum PID allowed (FWD ACK received). + */ + uint32_t fwd_ack; + + /** + * Last ACK sent to that child (BCK ACK). + */ + uint32_t bck_ack; +}; + + + +/** + * Info collected during iteration of child nodes in order to get the ACK value + * for a tunnel. + */ +struct MeshTunnelChildIteratorContext +{ + /** + * Tunnel whose info is being collected. + */ + struct MeshTunnel *t; + + /** + * Is this context initialized? Is the value in max_child_ack valid? + */ + int init; + + /** + * Maximum child ACK so far. + */ + uint32_t max_child_ack; + + /** + * Number of children nodes + */ + unsigned int nchildren; +}; + + +/** + * Info needed to work with tunnel paths and peers + */ +struct MeshPathInfo +{ + /** + * Tunnel + */ + struct MeshTunnel *t; + + /** + * Neighbouring peer to whom we send the packet to + */ + struct MeshPeerInfo *peer; + + /** + * Path itself + */ + struct MeshPeerPath *path; +}; + + +/** + * Struct containing information about a client of the service + */ +struct MeshClient +{ + /** + * Linked list next + */ + struct MeshClient *next; + + /** + * Linked list prev + */ + struct MeshClient *prev; + + /** + * Tunnels that belong to this client, indexed by local id + */ + struct GNUNET_CONTAINER_MultiHashMap *own_tunnels; + + /** + * Tunnels this client has accepted, indexed by incoming local id + */ + struct GNUNET_CONTAINER_MultiHashMap *incoming_tunnels; + + /** + * Tunnels this client has rejected, indexed by incoming local id + */ + struct GNUNET_CONTAINER_MultiHashMap *ignore_tunnels; + /** + * Handle to communicate with the client + */ + struct GNUNET_SERVER_Client *handle; + + /** + * Applications that this client has claimed to provide + */ + struct GNUNET_CONTAINER_MultiHashMap *apps; + + /** + * Messages that this client has declared interest in + */ + struct GNUNET_CONTAINER_MultiHashMap *types; + + /** + * Whether the client is active or shutting down (don't send confirmations + * to a client that is shutting down. + */ + int shutting_down; + + /** + * ID of the client, mainly for debug messages + */ + unsigned int id; + + /** + * Regular expressions describing the services offered by this client. + */ + struct MeshRegexDescriptor *regexes; // FIXME regex add timeout? API to remove a regex? + + /** + * Number of regular expressions in regexes. + */ + unsigned int n_regex; + + /** + * Task to refresh all regular expresions in the DHT. + */ + GNUNET_SCHEDULER_TaskIdentifier regex_announce_task; + + /** + * Tmp store for partially retrieved regex. + */ + char *partial_regex; + +}; + + +/******************************************************************************/ +/************************ DEBUG FUNCTIONS ****************************/ +/******************************************************************************/ + +#if MESH_DEBUG +/** + * GNUNET_SCHEDULER_Task for printing a message after some operation is done + * @param cls string to print + * @param success GNUNET_OK if the PUT was transmitted, + * GNUNET_NO on timeout, + * GNUNET_SYSERR on disconnect from service + * after the PUT message was transmitted + * (so we don't know if it was received or not) */ #if 0 @@ -491,71 +839,145 @@ mesh_debug (void *cls, int success) } #endif +unsigned int debug_fwd_ack; +unsigned int debug_bck_ack; + #endif /******************************************************************************/ /*********************** GLOBAL VARIABLES ****************************/ /******************************************************************************/ +/************************** Configuration parameters **************************/ + +/** + * How often to send tunnel keepalives. Tunnels timeout after 4 missed. + */ +static struct GNUNET_TIME_Relative refresh_path_time; + +/** + * How often to PUT local application numbers in the DHT. + */ +static struct GNUNET_TIME_Relative app_announce_time; + +/** + * How often to PUT own ID in the DHT. + */ +static struct GNUNET_TIME_Relative id_announce_time; + +/** + * Maximum time allowed to connect to a peer found by string. + */ +static struct GNUNET_TIME_Relative connect_timeout; + +/** + * Default TTL for payload packets. + */ +static unsigned long long default_ttl; + +/** + * DHT replication level, see DHT API: GNUNET_DHT_get_start, GNUNET_DHT_put. + */ +static unsigned long long dht_replication_level; + +/** + * How many tunnels are we willing to maintain. + * Local tunnels are always allowed, even if there are more tunnels than max. + */ +static unsigned long long max_tunnels; + +/** + * How many messages *in total* are we willing to queue, divided by number of + * tunnels to get tunnel queue size. + */ +static unsigned long long max_msgs_queue; + +/** + * How many peers do we want to remember? + */ +static unsigned long long max_peers; + + +/*************************** Static global variables **************************/ + +/** + * Hostkey generation context + */ +static struct GNUNET_CRYPTO_RsaKeyGenerationContext *keygen; + /** - * All the clients + * DLL with all the clients, head. */ static struct MeshClient *clients; + +/** + * DLL with all the clients, tail. + */ static struct MeshClient *clients_tail; /** - * Tunnels known, indexed by MESH_TunnelID (MeshTunnel) + * Tunnels known, indexed by MESH_TunnelID (MeshTunnel). */ static struct GNUNET_CONTAINER_MultiHashMap *tunnels; +/** + * Number of tunnels known. + */ +static unsigned long long n_tunnels; + /** * Tunnels incoming, indexed by MESH_TunnelNumber - * (which is greater than GNUNET_MESH_LOCAL_TUNNEL_ID_SERV) + * (which is greater than GNUNET_MESH_LOCAL_TUNNEL_ID_SERV). */ static struct GNUNET_CONTAINER_MultiHashMap *incoming_tunnels; /** - * Peers known, indexed by PeerIdentity (MeshPeerInfo) + * Peers known, indexed by PeerIdentity (MeshPeerInfo). */ static struct GNUNET_CONTAINER_MultiHashMap *peers; -/** - * Handle to communicate with core +/* + * Handle to communicate with transport */ -static struct GNUNET_CORE_Handle *core_handle; +// static struct GNUNET_TRANSPORT_Handle *transport_handle; /** - * Handle to communicate with transport + * Handle to communicate with core. */ -// static struct GNUNET_TRANSPORT_Handle *transport_handle; +static struct GNUNET_CORE_Handle *core_handle; /** - * Handle to use DHT + * Handle to use DHT. */ static struct GNUNET_DHT_Handle *dht_handle; /** - * Handle to server + * Handle to server. */ static struct GNUNET_SERVER_Handle *server_handle; /** - * Notification context, to send messages to local clients + * Handle to the statistics service. + */ +static struct GNUNET_STATISTICS_Handle *stats; + +/** + * Notification context, to send messages to local clients. */ static struct GNUNET_SERVER_NotificationContext *nc; /** - * Local peer own ID (memory efficient handle) + * Local peer own ID (memory efficient handle). */ static GNUNET_PEER_Id myid; /** - * Local peer own ID (full value) + * Local peer own ID (full value). */ static struct GNUNET_PeerIdentity my_full_id; /** - * Own private key + * Own private key. */ static struct GNUNET_CRYPTO_RsaPrivateKey *my_private_key; @@ -565,185 +987,167 @@ static struct GNUNET_CRYPTO_RsaPrivateKey *my_private_key; static struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded my_public_key; /** - * Tunnel ID for the next created tunnel (global tunnel number) + * Tunnel ID for the next created tunnel (global tunnel number). */ static MESH_TunnelNumber next_tid; /** - * Tunnel ID for the next incoming tunnel (local tunnel number) + * Tunnel ID for the next incoming tunnel (local tunnel number). */ static MESH_TunnelNumber next_local_tid; /** - * All application types provided by this peer + * All application types provided by this peer. */ static struct GNUNET_CONTAINER_MultiHashMap *applications; /** - * All message types clients of this peer are interested in + * All message types clients of this peer are interested in. */ static struct GNUNET_CONTAINER_MultiHashMap *types; /** - * Task to periodically announce provided applications + * Task to periodically announce provided applications. */ GNUNET_SCHEDULER_TaskIdentifier announce_applications_task; /** - * Task to periodically announce itself in the network + * Task to periodically announce itself in the network. */ GNUNET_SCHEDULER_TaskIdentifier announce_id_task; /** - * Next ID to assign to a client + * Next ID to assign to a client. */ unsigned int next_client_id; - -/******************************************************************************/ -/************************ ITERATORS ****************************/ -/******************************************************************************/ - -/* FIXME move iterators here */ - - /******************************************************************************/ -/************************ PERIODIC FUNCTIONS ****************************/ +/*********************** DECLARATIONS **************************/ /******************************************************************************/ /** - * Announce iterator over for each application provided by the peer + * Function to process paths received for a new peer addition. The recorded + * paths form the initial tunnel, which can be optimized later. + * Called on each result obtained for the DHT search. * * @param cls closure - * @param key current key code - * @param value value in the hash map - * @return GNUNET_YES if we should continue to - * iterate, - * GNUNET_NO if not. + * @param exp when will this value expire + * @param key key of the result + * @param type type of the result + * @param size number of bytes in data + * @param data pointer to the result data */ -static int -announce_application (void *cls, const GNUNET_HashCode * key, void *value) -{ - /* FIXME are hashes in multihash map equal on all aquitectures? */ - /* FIXME: keep return value of 'put' to possibly cancel!? */ - GNUNET_DHT_put (dht_handle, key, 10, - GNUNET_DHT_RO_RECORD_ROUTE | - GNUNET_DHT_RO_DEMULTIPLEX_EVERYWHERE, GNUNET_BLOCK_TYPE_TEST, - sizeof (struct GNUNET_PeerIdentity), - (const char *) &my_full_id, - GNUNET_TIME_absolute_add (GNUNET_TIME_absolute_get (), - APP_ANNOUNCE_TIME), - APP_ANNOUNCE_TIME, NULL, NULL); - return GNUNET_OK; -} +static void +dht_get_id_handler (void *cls, struct GNUNET_TIME_Absolute exp, + const struct GNUNET_HashCode * key, + const struct GNUNET_PeerIdentity *get_path, + unsigned int get_path_length, + const struct GNUNET_PeerIdentity *put_path, + unsigned int put_path_length, enum GNUNET_BLOCK_Type type, + size_t size, const void *data); /** - * Periodically announce what applications are provided by local clients + * Retrieve the MeshPeerInfo stucture associated with the peer, create one + * and insert it in the appropiate structures if the peer is not known yet. * - * @param cls closure - * @param tc task context + * @param peer Full identity of the peer. + * + * @return Existing or newly created peer info. */ -static void -announce_applications (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - if (tc->reason == GNUNET_SCHEDULER_REASON_SHUTDOWN) - { - announce_applications_task = GNUNET_SCHEDULER_NO_TASK; - return; - } - - DEBUG_DHT ("Starting PUT for apps\n"); +static struct MeshPeerInfo * +peer_info_get (const struct GNUNET_PeerIdentity *peer); - GNUNET_CONTAINER_multihashmap_iterate (applications, &announce_application, - NULL); - announce_applications_task = - GNUNET_SCHEDULER_add_delayed (APP_ANNOUNCE_TIME, &announce_applications, - cls); - DEBUG_DHT ("Finished PUT for apps\n"); - return; -} +/** + * Retrieve the MeshPeerInfo stucture associated with the peer, create one + * and insert it in the appropiate structures if the peer is not known yet. + * + * @param peer Short identity of the peer. + * + * @return Existing or newly created peer info. + */ +static struct MeshPeerInfo * +peer_info_get_short (const GNUNET_PEER_Id peer); /** - * Periodically announce self id in the DHT + * Try to establish a new connection to this peer. + * Use the best path for the given tunnel. + * If the peer doesn't have any path to it yet, try to get one. + * If the peer already has some path, send a CREATE PATH towards it. * - * @param cls closure - * @param tc task context + * @param peer PeerInfo of the peer. + * @param t Tunnel for which to create the path, if possible. */ static void -announce_id (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - if (tc->reason == GNUNET_SCHEDULER_REASON_SHUTDOWN) - { - announce_id_task = GNUNET_SCHEDULER_NO_TASK; - return; - } - /* TODO - * - Set data expiration in function of X - * - Adapt X to churn - */ - DEBUG_DHT ("DHT_put for ID %s started.\n", GNUNET_i2s (&my_full_id)); +peer_info_connect (struct MeshPeerInfo *peer, struct MeshTunnel *t); - GNUNET_DHT_put (dht_handle, /* DHT handle */ - &my_full_id.hashPubKey, /* Key to use */ - 10, /* Replication level */ - GNUNET_DHT_RO_RECORD_ROUTE | GNUNET_DHT_RO_DEMULTIPLEX_EVERYWHERE, /* DHT options */ - GNUNET_BLOCK_TYPE_TEST, /* Block type */ - sizeof (my_full_id), /* Size of the data */ - (char *) &my_full_id, /* Data itself */ - GNUNET_TIME_UNIT_FOREVER_ABS, /* Data expiration */ - GNUNET_TIME_UNIT_FOREVER_REL, /* Retry time */ - NULL, /* Continuation */ - NULL); /* Continuation closure */ - announce_id_task = - GNUNET_SCHEDULER_add_delayed (ID_ANNOUNCE_TIME, &announce_id, cls); -} + +/** + * Build a PeerPath from the paths returned from the DHT, reversing the paths + * to obtain a local peer -> destination path and interning the peer ids. + * + * @return Newly allocated and created path + */ +static struct MeshPeerPath * +path_build_from_dht (const struct GNUNET_PeerIdentity *get_path, + unsigned int get_path_length, + const struct GNUNET_PeerIdentity *put_path, + unsigned int put_path_length); /** - * Function to process paths received for a new peer addition. The recorded - * paths form the initial tunnel, which can be optimized later. - * Called on each result obtained for the DHT search. + * Adds a path to the peer_infos of all the peers in the path * - * @param cls closure - * @param exp when will this value expire - * @param key key of the result - * @param type type of the result - * @param size number of bytes in data - * @param data pointer to the result data + * @param p Path to process. + * @param confirmed Whether we know if the path works or not. */ static void -dht_get_id_handler (void *cls, struct GNUNET_TIME_Absolute exp, - const GNUNET_HashCode * key, - const struct GNUNET_PeerIdentity *get_path, - unsigned int get_path_length, - const struct GNUNET_PeerIdentity *put_path, - unsigned int put_path_length, enum GNUNET_BLOCK_Type type, - size_t size, const void *data); +path_add_to_peers (struct MeshPeerPath *p, int confirmed); -/******************************************************************************/ -/****************** GENERAL HELPER FUNCTIONS ************************/ -/******************************************************************************/ +/** + * Add a peer to a tunnel, accomodating paths accordingly and initializing all + * needed rescources. + * If peer already exists, reevaluate shortest path and change if different. + * + * @param t Tunnel we want to add a new peer to + * @param peer PeerInfo of the peer being added + * + */ +static void +tunnel_add_peer (struct MeshTunnel *t, struct MeshPeerInfo *peer); + /** - * Search for a tunnel by global ID using full PeerIdentities + * Removes an explicit path from a tunnel, freeing all intermediate nodes + * that are no longer needed, as well as nodes of no longer reachable peers. + * The tunnel itself is also destoyed if results in a remote empty tunnel. * - * @param oid owner of the tunnel - * @param tid global tunnel number + * @param t Tunnel from which to remove the path. + * @param peer Short id of the peer which should be removed. + */ +static void +tunnel_delete_peer (struct MeshTunnel *t, GNUNET_PEER_Id peer); + + +/** + * Search for a tunnel by global ID using full PeerIdentities. * - * @return tunnel handler, NULL if doesn't exist + * @param oid owner of the tunnel. + * @param tid global tunnel number. + * + * @return tunnel handler, NULL if doesn't exist. */ static struct MeshTunnel * -tunnel_get (struct GNUNET_PeerIdentity *oid, MESH_TunnelNumber tid); +tunnel_get (const struct GNUNET_PeerIdentity *oid, MESH_TunnelNumber tid); /** * Delete an active client from the tunnel. - * + * * @param t Tunnel. * @param c Client. */ @@ -767,2057 +1171,4487 @@ tunnel_notify_connection_broken (struct MeshTunnel *t, GNUNET_PEER_Id p1, /** - * Check if client has registered with the service and has not disconnected + * Get the current ack value for a tunnel, for data going from root to leaves, + * taking in account the tunnel mode and the status of all children and clients. * - * @param client the client to check + * @param t Tunnel. * - * @return non-NULL if client exists in the global DLL + * @return Maximum PID allowed. */ -static struct MeshClient * -client_get (struct GNUNET_SERVER_Client *client) -{ - struct MeshClient *c; +static uint32_t +tunnel_get_fwd_ack (struct MeshTunnel *t); - c = clients; - while (NULL != c) - { - if (c->handle == client) - return c; - c = c->next; - } - return NULL; -} + +/** + * Add a client to a tunnel, initializing all needed data structures. + * + * @param t Tunnel to which add the client. + * @param c Client which to add to the tunnel. + */ +static void +tunnel_add_client (struct MeshTunnel *t, struct MeshClient *c); /** - * Checks if a given client has subscribed to certain message type - * - * @param message_type Type of message to check - * @param c Client to check - * - * @return GNUNET_YES or GNUNET_NO, depending on subscription status + * @brief Queue and pass message to core when possible. + * + * If type is payload (UNICAST, TO_ORIGIN, MULTICAST) checks for queue status + * and accounts for it. In case the queue is full, the message is dropped and + * a break issued. + * + * Otherwise, message is treated as internal and allowed to go regardless of + * queue status. * - * TODO inline? + * @param cls Closure (@c type dependant). It will be used by queue_send to + * build the message to be sent if not already prebuilt. + * @param type Type of the message, 0 for a raw message. + * @param size Size of the message. + * @param dst Neighbor to send message to. + * @param t Tunnel this message belongs to. */ -static int -client_is_subscribed (uint16_t message_type, struct MeshClient *c) -{ - GNUNET_HashCode hc; - - GNUNET_CRYPTO_hash (&message_type, sizeof (uint16_t), &hc); - return GNUNET_CONTAINER_multihashmap_contains (c->types, &hc); -} +static void +queue_add (void *cls, uint16_t type, size_t size, + struct MeshPeerInfo *dst, struct MeshTunnel *t); /** - * Allow a client to send more data after transmitting a multicast message - * which some neighbor has not yet accepted altough a reasonable time has - * passed. + * Free a transmission that was already queued with all resources + * associated to the request. * - * @param cls Closure (DataDescriptor containing the task identifier) - * @param tc Task Context - * - * FIXME reference counter cshould be just int + * @param queue Queue handler to cancel. + * @param clear_cls Is it necessary to free associated cls? */ static void -client_allow_send (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - struct MeshData *mdata = cls; - - if (GNUNET_SCHEDULER_REASON_SHUTDOWN == tc->reason) - return; - GNUNET_assert (NULL != mdata->reference_counter); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "CLIENT ALLOW SEND DESPITE %u COPIES PENDING\n", - *(mdata->reference_counter)); - *(mdata->task) = GNUNET_SCHEDULER_NO_TASK; - GNUNET_SERVER_receive_done (mdata->t->owner->handle, GNUNET_OK); -} +queue_destroy (struct MeshPeerQueue *queue, int clear_cls); /** - * Check whether client wants traffic from a tunnel. + * @brief Get the next transmittable message from the queue. * - * @param c Client to check. - * @param t Tunnel to be found. + * This will be the head, except in the case of being a data packet + * not allowed by the destination peer. * - * @return GNUNET_YES if client knows tunnel. - * - * TODO look in client hashmap + * @param peer Destination peer. + * + * @return The next viable MeshPeerQueue element to send to that peer. + * NULL when there are no transmittable messages. */ -static int -client_wants_tunnel (struct MeshClient *c, struct MeshTunnel *t) -{ - unsigned int i; - - for (i = 0; i < t->nclients; i++) - if (t->clients[i] == c) - return GNUNET_YES; - return GNUNET_NO; -} +struct MeshPeerQueue * +queue_get_next (const struct MeshPeerInfo *peer); /** - * Check whether client has been informed about a tunnel. + * Core callback to write a queued packet to core buffer * - * @param c Client to check. - * @param t Tunnel to be found. + * @param cls Closure (peer info). + * @param size Number of bytes available in buf. + * @param buf Where the to write the message. * - * @return GNUNET_YES if client knows tunnel. - * - * TODO look in client hashmap + * @return number of bytes written to buf */ -static int -client_knows_tunnel (struct MeshClient *c, struct MeshTunnel *t) -{ - unsigned int i; - - for (i = 0; i < t->nignore; i++) - if (t->ignore[i] == c) - return GNUNET_YES; - return client_wants_tunnel(c, t); -} +static size_t +queue_send (void *cls, size_t size, void *buf); +/******************************************************************************/ +/************************ REGEX INTEGRATION ****************************/ +/******************************************************************************/ /** - * Marks a client as uninterested in traffic from the tunnel, updating both - * client and tunnel to reflect this. - * - * @param c Client that doesn't want traffic anymore. - * @param t Tunnel which should be ignored. - * - * FIXME when to delete an incoming tunnel? + * Cancel a mesh regex search and free resources. */ static void -client_ignore_tunnel (struct MeshClient *c, struct MeshTunnel *t) +regex_cancel_search (struct MeshRegexSearchInfo *regex_search) { - GNUNET_HashCode hash; - - GNUNET_CRYPTO_hash(&t->local_tid_dest, sizeof (MESH_TunnelNumber), &hash); - GNUNET_break (GNUNET_YES == - GNUNET_CONTAINER_multihashmap_remove (c->incoming_tunnels, - &hash, t)); - GNUNET_break (GNUNET_YES == - GNUNET_CONTAINER_multihashmap_put (c->ignore_tunnels, &hash, t, - GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_FAST)); - tunnel_delete_active_client (t, c); - GNUNET_array_append (t->ignore, t->nignore, c); + DEBUG_REGEX ("Search for %s canelled.\n", regex_search->description); + GNUNET_REGEX_search_cancel (regex_search->search_handle); + if (0 < regex_search->n_peers) + GNUNET_free (regex_search->peers); + if (GNUNET_SCHEDULER_NO_TASK != regex_search->timeout) + { + GNUNET_SCHEDULER_cancel(regex_search->timeout); + } + GNUNET_free (regex_search); } /** - * Deletes a tunnel from a client (either owner or destination). To be used on - * tunnel destroy, otherwise, use client_ignore_tunnel. + * Function called if the connect attempt to a peer found via + * connect_by_string times out. Try to connect to another peer, if any. + * Otherwise try to reconnect to the same peer. * - * @param c Client whose tunnel to delete. - * @param t Tunnel which should be deleted. + * @param cls Closure (info about regex search). + * @param tc TaskContext. */ static void -client_delete_tunnel (struct MeshClient *c, struct MeshTunnel *t) +regex_connect_timeout (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { - GNUNET_HashCode hash; + struct MeshRegexSearchInfo *info = cls; + struct MeshPeerInfo *peer_info; + GNUNET_PEER_Id id; + GNUNET_PEER_Id old; - if (c == t->owner) + DEBUG_REGEX ("Regex connect timeout\n"); + info->timeout = GNUNET_SCHEDULER_NO_TASK; + if (0 != (tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN)) { - GNUNET_CRYPTO_hash(&t->local_tid, sizeof (MESH_TunnelNumber), &hash); - GNUNET_assert (GNUNET_YES == - GNUNET_CONTAINER_multihashmap_remove (c->own_tunnels, - &hash, - t)); + DEBUG_REGEX (" due to shutdown\n"); + return; + } + + old = info->peer; + DEBUG_REGEX (" timed out: %u\n", old); + + if (0 < info->n_peers) + { + // Select next peer, put current in that spot. + id = info->peers[info->i_peer]; + info->peers[info->i_peer] = info->peer; + info->i_peer = (info->i_peer + 1) % info->n_peers; } else { - GNUNET_CRYPTO_hash(&t->local_tid_dest, sizeof (MESH_TunnelNumber), &hash); - // FIXME XOR? - GNUNET_assert (GNUNET_YES == - GNUNET_CONTAINER_multihashmap_remove (c->incoming_tunnels, - &hash, - t) || - GNUNET_YES == - GNUNET_CONTAINER_multihashmap_remove (c->ignore_tunnels, - &hash, - t)); + // Try to connect to same peer again. + id = info->peer; } - + DEBUG_REGEX (" trying: %u\n", id); + + peer_info = peer_info_get_short(id); + tunnel_add_peer (info->t, peer_info); + if (old != id) + tunnel_delete_peer (info->t, old); + peer_info_connect (peer_info, info->t); + info->timeout = GNUNET_SCHEDULER_add_delayed (connect_timeout, + ®ex_connect_timeout, + info); + DEBUG_REGEX ("Regex connect timeout END\n"); } /** - * Send the message to all clients that have subscribed to its type + * Function to process DHT string to regex matching. + * Called on each result obtained for the DHT search. * - * @param msg Pointer to the message itself - * @param payload Pointer to the payload of the message. - * @return number of clients this message was sent to + * @param cls Closure provided in GNUNET_REGEX_search. + * @param id Peer providing a regex that matches the string. + * @param get_path Path of the get request. + * @param get_path_length Lenght of get_path. + * @param put_path Path of the put request. + * @param put_path_length Length of the put_path. */ -static unsigned int -send_subscribed_clients (const struct GNUNET_MessageHeader *msg, - const struct GNUNET_MessageHeader *payload) +static void +regex_found_handler (void *cls, + const struct GNUNET_PeerIdentity *id, + const struct GNUNET_PeerIdentity *get_path, + unsigned int get_path_length, + const struct GNUNET_PeerIdentity *put_path, + unsigned int put_path_length) { - struct GNUNET_PeerIdentity *oid; - struct MeshClient *c; - struct MeshTunnel *t; - MESH_TunnelNumber *tid; - unsigned int count; - uint16_t type; - char cbuf[htons (msg->size)]; + struct MeshRegexSearchInfo *info = cls; + struct MeshPeerPath *p; + struct MeshPeerInfo *peer_info; - type = ntohs (payload->type); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Sending to clients...\n"); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "message of type %u\n", type); + DEBUG_REGEX ("Got regex results from DHT!\n"); + DEBUG_REGEX (" for %s\n", info->description); - memcpy (cbuf, msg, sizeof (cbuf)); - switch (htons (msg->type)) - { - struct GNUNET_MESH_Unicast *uc; - struct GNUNET_MESH_Multicast *mc; - struct GNUNET_MESH_ToOrigin *to; + peer_info = peer_info_get (id); + p = path_build_from_dht (get_path, get_path_length, + put_path, put_path_length); + path_add_to_peers (p, GNUNET_NO); + path_destroy(p); - case GNUNET_MESSAGE_TYPE_MESH_UNICAST: - uc = (struct GNUNET_MESH_Unicast *) cbuf; - tid = &uc->tid; - oid = &uc->oid; - break; - case GNUNET_MESSAGE_TYPE_MESH_MULTICAST: - mc = (struct GNUNET_MESH_Multicast *) cbuf; - tid = &mc->tid; - oid = &mc->oid; - break; - case GNUNET_MESSAGE_TYPE_MESH_TO_ORIGIN: - to = (struct GNUNET_MESH_ToOrigin *) cbuf; - tid = &to->tid; - oid = &to->oid; - break; - default: - GNUNET_break (0); - return 0; + tunnel_add_peer (info->t, peer_info); + peer_info_connect (peer_info, info->t); + if (0 == info->peer) + { + info->peer = peer_info->id; } - t = tunnel_get (oid, ntohl (*tid)); - if (NULL == t) + else { - GNUNET_break (0); - return 0; + GNUNET_array_append (info->peers, info->n_peers, peer_info->id); } - for (count = 0, c = clients; c != NULL; c = c->next) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " client %u\n", c->id); - if (client_is_subscribed (type, c)) - { - if (htons (msg->type) == GNUNET_MESSAGE_TYPE_MESH_TO_ORIGIN) - { - if (c != t->owner) - continue; - *tid = htonl (t->local_tid); - } - else - { - if (GNUNET_NO == client_knows_tunnel (c, t)) - { - /* This client doesn't know the tunnel */ - struct GNUNET_MESH_TunnelNotification tmsg; - GNUNET_HashCode hash; + if (GNUNET_SCHEDULER_NO_TASK != info->timeout) + return; - tmsg.header.size = htons (sizeof (tmsg)); - tmsg.header.type = htons (GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_CREATE); - GNUNET_PEER_resolve (t->id.oid, &tmsg.peer); - tmsg.tunnel_id = htonl (t->local_tid_dest); - GNUNET_SERVER_notification_context_unicast (nc, c->handle, - &tmsg.header, GNUNET_NO); - GNUNET_array_append (t->clients, t->nclients, c); - GNUNET_CRYPTO_hash (&t->local_tid_dest, sizeof (MESH_TunnelNumber), - &hash); - GNUNET_break (GNUNET_OK == GNUNET_CONTAINER_multihashmap_put ( - c->incoming_tunnels, &hash, t, - GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_FAST)); - } - *tid = htonl (t->local_tid_dest); - } + info->timeout = GNUNET_SCHEDULER_add_delayed (connect_timeout, + ®ex_connect_timeout, + info); - /* Check if the client wants to get traffic from the tunnel */ - if (GNUNET_NO == client_wants_tunnel(c, t)) - continue; - count++; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " sending\n"); - GNUNET_SERVER_notification_context_unicast (nc, c->handle, - (struct GNUNET_MessageHeader - *) cbuf, GNUNET_YES); - } - } - return count; + return; } /** - * Notify the client that owns the tunnel that a peer has connected to it - * (the requested path to it has been confirmed). + * Store the regular expression describing a local service into the DHT. * - * @param t Tunnel whose owner to notify - * @param id Short id of the peer that has connected + * @param regex The regular expresion. */ static void -send_client_peer_connected (const struct MeshTunnel *t, const GNUNET_PEER_Id id) +regex_put (struct MeshRegexDescriptor *regex) { - struct GNUNET_MESH_PeerControl pc; - - pc.header.type = htons (GNUNET_MESSAGE_TYPE_MESH_LOCAL_PEER_ADD); - pc.header.size = htons (sizeof (struct GNUNET_MESH_PeerControl)); - pc.tunnel_id = htonl (t->local_tid); - GNUNET_PEER_resolve (id, &pc.peer); - GNUNET_SERVER_notification_context_unicast (nc, t->owner->handle, &pc.header, - GNUNET_NO); + DEBUG_REGEX (" regex_put (%s) start\n", regex->regex); + if (NULL == regex->h) + { + DEBUG_REGEX (" first put, creating DFA\n"); + regex->h = GNUNET_REGEX_announce (dht_handle, + &my_full_id, + regex->regex, + regex->compression, + stats); + } + else + { + DEBUG_REGEX (" not first put, using cached data\n"); + GNUNET_REGEX_reannounce (regex->h); + } + DEBUG_REGEX (" regex_put (%s) end\n", regex->regex); } /** - * Notify all clients (not depending on registration status) that the incoming - * tunnel is no longer valid. + * Periodically announce what applications are provided by local clients + * (by regex) * - * @param t Tunnel that was destroyed. + * @param cls closure + * @param tc task context */ static void -send_clients_tunnel_destroy (struct MeshTunnel *t) +regex_announce (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { - struct GNUNET_MESH_TunnelMessage msg; + struct MeshClient *c = cls; + unsigned int i; - msg.header.size = htons (sizeof (msg)); - msg.header.type = htons (GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_DESTROY); - msg.tunnel_id = htonl (t->local_tid_dest); - GNUNET_SERVER_notification_context_broadcast (nc, &msg.header, GNUNET_NO); + c->regex_announce_task = GNUNET_SCHEDULER_NO_TASK; + if (0 != (tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN)) + return; + DEBUG_REGEX ("Starting announce for regex\n"); + for (i = 0; i < c->n_regex; i++) + regex_put (&c->regexes[i]); + c->regex_announce_task = GNUNET_SCHEDULER_add_delayed (app_announce_time, + ®ex_announce, + cls); + DEBUG_REGEX ("Finished announce for regex\n"); } +/******************************************************************************/ +/************************ PERIODIC FUNCTIONS ****************************/ +/******************************************************************************/ + /** - * Notify clients of tunnel disconnections, if needed. - * In case the origin disconnects, the destination clients get a tunnel destroy - * notification. If the last destination disconnects (only one remaining client - * in tunnel), the origin gets a (local ID) peer disconnected. - * Note that the function must be called BEFORE removing the client from - * the tunnel. + * Announce iterator over for each application provided by the peer * - * @param t Tunnel that was destroyed. - * @param c Client that disconnected. + * @param cls closure + * @param key current key code + * @param value value in the hash map + * @return GNUNET_YES if we should continue to + * iterate, + * GNUNET_NO if not. */ -static void -send_client_tunnel_disconnect (struct MeshTunnel *t, struct MeshClient *c) +static int +announce_application (void *cls, const struct GNUNET_HashCode * key, void *value) { - unsigned int i; - - if (c == t->owner) - { - struct GNUNET_MESH_TunnelMessage msg; - - msg.header.size = htons (sizeof (msg)); - msg.header.type = htons (GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_DESTROY); - msg.tunnel_id = htonl (t->local_tid_dest); - for (i = 0; i < t->nclients; i++) - GNUNET_SERVER_notification_context_unicast (nc, t->clients[i]->handle, - &msg.header, GNUNET_NO); - } - // FIXME when to disconnect an incoming tunnel? - else if (1 == t->nclients && NULL != t->owner) - { - struct GNUNET_MESH_PeerControl msg; + struct PBlock block; + struct MeshClient *c; - msg.header.size = htons (sizeof (msg)); - msg.header.type = htons (GNUNET_MESSAGE_TYPE_MESH_LOCAL_PEER_DEL); - msg.tunnel_id = htonl (t->local_tid); - msg.peer = my_full_id; - GNUNET_SERVER_notification_context_unicast (nc, t->owner->handle, - &msg.header, GNUNET_NO); - } + block.id = my_full_id; + c = GNUNET_CONTAINER_multihashmap_get (applications, key); + GNUNET_assert(NULL != c); + block.type = (long) GNUNET_CONTAINER_multihashmap_get (c->apps, key); + if (0 == block.type) + { + GNUNET_break(0); + return GNUNET_YES; + } + block.type = htonl (block.type); + + GNUNET_break (NULL != + GNUNET_DHT_put (dht_handle, key, + dht_replication_level, + GNUNET_DHT_RO_RECORD_ROUTE | + GNUNET_DHT_RO_DEMULTIPLEX_EVERYWHERE, + GNUNET_BLOCK_TYPE_MESH_PEER_BY_TYPE, + sizeof (block), + (const char *) &block, + GNUNET_TIME_relative_to_absolute (GNUNET_TIME_UNIT_HOURS), /* FIXME: this should be an option */ + app_announce_time, NULL, NULL)); + return GNUNET_OK; } /** - * Function called to notify a client about the socket - * being ready to queue more data. "buf" will be - * NULL and "size" zero if the socket was closed for - * writing in the meantime. + * Periodically announce what applications are provided by local clients + * (by type) * * @param cls closure - * @param size number of bytes available in buf - * @param buf where the callee should write the message - * @return number of bytes written to buf + * @param tc task context */ -static size_t -send_core_create_path (void *cls, size_t size, void *buf); - +static void +announce_applications (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + if (0 != (tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN)) + { + announce_applications_task = GNUNET_SCHEDULER_NO_TASK; + return; + } + + DEBUG_DHT ("Starting PUT for apps\n"); -/** - * Function called to notify a client about the socket - * being ready to queue more data. "buf" will be - * NULL and "size" zero if the socket was closed for - * writing in the meantime. - * - * @param cls closure (data itself) - * @param size number of bytes available in buf - * @param buf where the callee should write the message - * - * @return number of bytes written to buf - */ -static size_t -send_core_data_multicast (void *cls, size_t size, void *buf); + GNUNET_CONTAINER_multihashmap_iterate (applications, &announce_application, + NULL); + announce_applications_task = + GNUNET_SCHEDULER_add_delayed (app_announce_time, &announce_applications, + cls); + DEBUG_DHT ("Finished PUT for apps\n"); +} /** - * Decrements the reference counter and frees all resources if needed + * Periodically announce self id in the DHT * - * @param mesh_data Data Descriptor used in a multicast message. - * Freed no longer needed (last message). + * @param cls closure + * @param tc task context */ static void -data_descriptor_decrement_multicast (struct MeshData *mesh_data) +announce_id (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { - /* Make sure it's a multicast packet */ - GNUNET_assert (NULL != mesh_data->reference_counter); + struct PBlock block; - if (0 == --(*(mesh_data->reference_counter))) + if (0 != (tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN)) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Last copy!\n"); - if (NULL != mesh_data->task) - { - if (GNUNET_SCHEDULER_NO_TASK != *(mesh_data->task)) - { - GNUNET_SCHEDULER_cancel (*(mesh_data->task)); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " notifying client...\n"); - GNUNET_SERVER_receive_done (mesh_data->t->owner->handle, GNUNET_OK); - } - GNUNET_free (mesh_data->task); - } - GNUNET_free (mesh_data->reference_counter); - GNUNET_free (mesh_data->data); - GNUNET_free (mesh_data); + announce_id_task = GNUNET_SCHEDULER_NO_TASK; + return; } + /* TODO + * - Set data expiration in function of X + * - Adapt X to churn + */ + DEBUG_DHT ("DHT_put for ID %s started.\n", GNUNET_i2s (&my_full_id)); + + block.id = my_full_id; + block.type = htonl (0); + GNUNET_DHT_put (dht_handle, /* DHT handle */ + &my_full_id.hashPubKey, /* Key to use */ + dht_replication_level, /* Replication level */ + GNUNET_DHT_RO_RECORD_ROUTE | GNUNET_DHT_RO_DEMULTIPLEX_EVERYWHERE, /* DHT options */ + GNUNET_BLOCK_TYPE_MESH_PEER, /* Block type */ + sizeof (block), /* Size of the data */ + (const char *) &block, /* Data itself */ + GNUNET_TIME_UNIT_FOREVER_ABS, /* Data expiration */ + GNUNET_TIME_UNIT_FOREVER_REL, /* Retry time */ + NULL, /* Continuation */ + NULL); /* Continuation closure */ + announce_id_task = + GNUNET_SCHEDULER_add_delayed (id_announce_time, &announce_id, cls); } +/******************************************************************************/ +/****************** GENERAL HELPER FUNCTIONS ************************/ +/******************************************************************************/ + /** - * Cancel a core transmission that was already requested and free all resources - * associated to the request. + * Decrements the reference counter and frees all resources if needed * - * @param peer PeeInfo of the peer whose transmission is cancelled. - * @param i Position of the transmission to be cancelled. + * @param mesh_data Data Descriptor used in a multicast message. + * Freed no longer needed (last message). */ static void -peer_info_cancel_transmission (struct MeshPeerInfo *peer, unsigned int i) +data_descriptor_decrement_rc (struct MeshData *mesh_data) { - if (NULL != peer->core_transmit[i]) + if (0 == --(mesh_data->reference_counter)) { - struct MeshTransmissionDescriptor *dd; - struct MeshPathInfo *path_info; - -#if MESH_DEBUG - { - struct GNUNET_PeerIdentity id; - - GNUNET_PEER_resolve (peer->id, &id); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - " Cancelling data transmission at %s [%u]\n", - GNUNET_i2s (&id), i); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " message type %u\n", - peer->types[i]); - } -#endif - /* TODO: notify that tranmission has failed */ - switch (peer->types[i]) - { - case GNUNET_MESSAGE_TYPE_MESH_MULTICAST: - case GNUNET_MESSAGE_TYPE_MESH_UNICAST: - case GNUNET_MESSAGE_TYPE_MESH_TO_ORIGIN: - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " type payload\n"); - dd = peer->infos[i]; - data_descriptor_decrement_multicast (dd->mesh_data); - break; - case GNUNET_MESSAGE_TYPE_MESH_PATH_CREATE: - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " type create path\n"); - path_info = peer->infos[i]; - path_destroy (path_info->path); - break; - default: - GNUNET_break (0); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " type unknown!\n"); - } - GNUNET_CORE_notify_transmit_ready_cancel (peer->core_transmit[i]); - peer->core_transmit[i] = NULL; - GNUNET_free (peer->infos[i]); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Last copy!\n"); + GNUNET_free (mesh_data->data); + GNUNET_free (mesh_data); } } /** - * Get a unused CORE slot to transmit a message to a peer. If all the slots - * are used, cancel one and return it's position. + * Check if client has registered with the service and has not disconnected * - * @param peer PeerInfo of the neighbor we want to transmit to. + * @param client the client to check * - * @return The index of an available slot to transmit to the neighbor. + * @return non-NULL if client exists in the global DLL */ -static unsigned int -peer_info_transmit_slot (struct MeshPeerInfo *peer) +static struct MeshClient * +client_get (struct GNUNET_SERVER_Client *client) { - unsigned int i; + struct MeshClient *c; - for (i = 0; peer->core_transmit[i]; i++) + c = clients; + while (NULL != c) { - if (i == (CORE_QUEUE_SIZE - 1)) - { - /* All positions are taken! Overwriting! */ - GNUNET_break (0); - peer_info_cancel_transmission (peer, 0); - return 0; - } + if (c->handle == client) + return c; + c = c->next; } - return i; + return NULL; } /** - * Retrieve the MeshPeerInfo stucture associated with the peer, create one - * and insert it in the appropiate structures if the peer is not known yet. + * Checks if a given client has subscribed to certain message type * - * @param peer Full identity of the peer. + * @param message_type Type of message to check + * @param c Client to check * - * @return Existing or newly created peer info. + * @return GNUNET_YES or GNUNET_NO, depending on subscription status + * + * FIXME: use of crypto_hash slows it down + * The hash function alone takes 8-10us out of the ~55us for the whole + * process of retransmitting the message from one local client to another. + * Find faster implementation! */ -static struct MeshPeerInfo * -peer_info_get (const struct GNUNET_PeerIdentity *peer) +static int +client_is_subscribed (uint16_t message_type, struct MeshClient *c) { - struct MeshPeerInfo *peer_info; + struct GNUNET_HashCode hc; - peer_info = GNUNET_CONTAINER_multihashmap_get (peers, &peer->hashPubKey); - if (NULL == peer_info) - { - peer_info = - (struct MeshPeerInfo *) GNUNET_malloc (sizeof (struct MeshPeerInfo)); - GNUNET_CONTAINER_multihashmap_put (peers, &peer->hashPubKey, peer_info, - GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY); - peer_info->id = GNUNET_PEER_intern (peer); - } + if (NULL == c->types) + return GNUNET_NO; - return peer_info; + GNUNET_CRYPTO_hash (&message_type, sizeof (uint16_t), &hc); + return GNUNET_CONTAINER_multihashmap_contains (c->types, &hc); } /** - * Retrieve the MeshPeerInfo stucture associated with the peer, create one - * and insert it in the appropiate structures if the peer is not known yet. + * Check whether client wants traffic from a tunnel. * - * @param peer Short identity of the peer. + * @param c Client to check. + * @param t Tunnel to be found. * - * @return Existing or newly created peer info. + * @return GNUNET_YES if client knows tunnel. + * + * TODO look in client hashmap */ -static struct MeshPeerInfo * -peer_info_get_short (const GNUNET_PEER_Id peer) +static int +client_wants_tunnel (struct MeshClient *c, struct MeshTunnel *t) { - struct GNUNET_PeerIdentity id; + unsigned int i; - GNUNET_PEER_resolve (peer, &id); - return peer_info_get (&id); + for (i = 0; i < t->nclients; i++) + if (t->clients[i] == c) + return GNUNET_YES; + return GNUNET_NO; } /** - * Iterator to remove the tunnel from the list of tunnels a peer participates - * in. + * Check whether client has been informed about a tunnel. * - * @param cls Closure (tunnel info) - * @param key GNUNET_PeerIdentity of the peer (unused) - * @param value PeerInfo of the peer + * @param c Client to check. + * @param t Tunnel to be found. * - * @return always GNUNET_YES, to keep iterating + * @return GNUNET_YES if client knows tunnel. + * + * TODO look in client hashmap */ static int -peer_info_delete_tunnel (void *cls, const GNUNET_HashCode * key, void *value) +client_knows_tunnel (struct MeshClient *c, struct MeshTunnel *t) { - struct MeshTunnel *t = cls; - struct MeshPeerInfo *peer = value; unsigned int i; - for (i = 0; i < peer->ntunnels; i++) - { - if (0 == - memcmp (&peer->tunnels[i]->id, &t->id, sizeof (struct MESH_TunnelID))) - { - peer->ntunnels--; - peer->tunnels[i] = peer->tunnels[peer->ntunnels]; - peer->tunnels = GNUNET_realloc (peer->tunnels, peer->ntunnels); + for (i = 0; i < t->nignore; i++) + if (t->ignore[i] == c) return GNUNET_YES; - } - } - return GNUNET_YES; -} - - -/** - * Core callback to write a - * - * @param cls Closure (MeshTransmissionDescriptor with data in "data" member). - * @param size Number of bytes available in buf. - * @param buf Where the to write the message. - * - * @return number of bytes written to buf - */ -static size_t -send_core_data_raw (void *cls, size_t size, void *buf) -{ - struct MeshTransmissionDescriptor *info = cls; - struct GNUNET_MessageHeader *msg; - size_t total_size; - - GNUNET_assert (NULL != info); - GNUNET_assert (NULL != info->mesh_data); - msg = (struct GNUNET_MessageHeader *) info->mesh_data->data; - total_size = ntohs (msg->size); - - if (total_size > size) - { - struct GNUNET_PeerIdentity id; - - GNUNET_PEER_resolve (info->peer->id, &id); - info->peer->core_transmit[info->handler_n] = - GNUNET_CORE_notify_transmit_ready (core_handle, 0, 100, - GNUNET_TIME_UNIT_FOREVER_REL, &id, - size, &send_core_data_raw, info); - return 0; - } - info->peer->core_transmit[info->handler_n] = NULL; - memcpy (buf, msg, total_size); - GNUNET_free (info->mesh_data); - GNUNET_free (info); - return total_size; + return client_wants_tunnel(c, t); } /** - * Sends an already built message to a peer, properly registrating - * all used resources. + * Marks a client as uninterested in traffic from the tunnel, updating both + * client and tunnel to reflect this. * - * @param message Message to send. Fucntion makes a copy of it. - * @param peer Short ID of the neighbor whom to send the message. + * @param c Client that doesn't want traffic anymore. + * @param t Tunnel which should be ignored. * - * FIXME tunnel? + * FIXME when to delete an incoming tunnel? */ static void -send_message (const struct GNUNET_MessageHeader *message, - const struct GNUNET_PeerIdentity *peer) +client_ignore_tunnel (struct MeshClient *c, struct MeshTunnel *t) { - struct MeshTransmissionDescriptor *info; - struct MeshPeerInfo *neighbor; - struct MeshPeerPath *p; - unsigned int i; - size_t size; - -// GNUNET_TRANSPORT_try_connect(); - - size = ntohs (message->size); - info = GNUNET_malloc (sizeof (struct MeshTransmissionDescriptor)); - info->mesh_data = GNUNET_malloc (sizeof (struct MeshData)); - info->mesh_data->data = GNUNET_malloc (size); - memcpy (info->mesh_data->data, message, size); - info->mesh_data->data_len = size; - neighbor = peer_info_get (peer); - for (p = neighbor->path_head; NULL != p; p = p->next) - { - if (2 == p->length) - { - break; - } - } - if (NULL == p) - { - GNUNET_break (0); - GNUNET_free (info->mesh_data->data); - GNUNET_free (info->mesh_data); - GNUNET_free (info); - return; - } - i = peer_info_transmit_slot (neighbor); - info->handler_n = i; - info->peer = neighbor; - neighbor->types[i] = GNUNET_MESSAGE_TYPE_MESH_UNICAST; - neighbor->infos[i] = info; - neighbor->core_transmit[i] = - GNUNET_CORE_notify_transmit_ready (core_handle, 0, 100, - GNUNET_TIME_UNIT_FOREVER_REL, peer, - size, &send_core_data_raw, info); + struct GNUNET_HashCode hash; + GNUNET_CRYPTO_hash (&t->local_tid_dest, sizeof (MESH_TunnelNumber), &hash); + GNUNET_break (GNUNET_YES == + GNUNET_CONTAINER_multihashmap_remove (c->incoming_tunnels, + &hash, t)); + GNUNET_break (GNUNET_YES == + GNUNET_CONTAINER_multihashmap_put (c->ignore_tunnels, &hash, t, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_FAST)); + tunnel_delete_active_client (t, c); + GNUNET_array_append (t->ignore, t->nignore, c); } /** - * Sends a CREATE PATH message for a path to a peer, properly registrating - * all used resources. + * Deletes a tunnel from a client (either owner or destination). To be used on + * tunnel destroy, otherwise, use client_ignore_tunnel. * - * @param peer PeerInfo of the final peer for whom this path is being created. - * @param p Path itself. - * @param t Tunnel for which the path is created. + * @param c Client whose tunnel to delete. + * @param t Tunnel which should be deleted. */ static void -send_create_path (struct MeshPeerInfo *peer, struct MeshPeerPath *p, - struct MeshTunnel *t) +client_delete_tunnel (struct MeshClient *c, struct MeshTunnel *t) { - struct GNUNET_PeerIdentity id; - struct MeshPathInfo *path_info; - struct MeshPeerInfo *neighbor; - unsigned int i; + struct GNUNET_HashCode hash; - if (NULL == p) - { - p = tree_get_path_to_peer (t->tree, peer->id); - if (NULL == p) - { - GNUNET_break (0); - return; - } - } - for (i = 0; i < p->length; i++) + if (c == t->owner) { - if (p->peers[i] == myid) - break; + GNUNET_CRYPTO_hash(&t->local_tid, sizeof (MESH_TunnelNumber), &hash); + GNUNET_assert (GNUNET_YES == + GNUNET_CONTAINER_multihashmap_remove (c->own_tunnels, + &hash, + t)); } - if (i >= p->length - 1) + else { - path_destroy (p); - GNUNET_break (0); - return; + GNUNET_CRYPTO_hash(&t->local_tid_dest, sizeof (MESH_TunnelNumber), &hash); + // FIXME XOR? + GNUNET_assert (GNUNET_YES == + GNUNET_CONTAINER_multihashmap_remove (c->incoming_tunnels, + &hash, + t) || + GNUNET_YES == + GNUNET_CONTAINER_multihashmap_remove (c->ignore_tunnels, + &hash, + t)); } - GNUNET_PEER_resolve (p->peers[i + 1], &id); - - path_info = GNUNET_malloc (sizeof (struct MeshPathInfo)); - path_info->path = p; - path_info->t = t; - neighbor = peer_info_get (&id); - path_info->peer = neighbor; - path_info->pos = peer_info_transmit_slot (neighbor); - neighbor->types[path_info->pos] = GNUNET_MESSAGE_TYPE_MESH_PATH_CREATE; - neighbor->infos[path_info->pos] = path_info; - neighbor->core_transmit[path_info->pos] = - GNUNET_CORE_notify_transmit_ready (core_handle, /* handle */ - 0, /* cork */ - 0, /* priority */ - GNUNET_TIME_UNIT_FOREVER_REL, /* timeout */ - &id, /* target */ - sizeof (struct GNUNET_MESH_ManipulatePath) + - (p->length * sizeof (struct GNUNET_PeerIdentity)), /*size */ - &send_core_create_path, /* callback */ - path_info); /* cls */ } /** - * Sends a DESTROY PATH message to free resources for a path in a tunnel - * - * @param t Tunnel whose path to destroy. - * @param destination Short ID of the peer to whom the path to destroy. + * Notify the owner of a tunnel that a peer has disconnected. + * + * @param c Client (owner of tunnel). + * @param t Tunnel this message is about. + * @param peer_id Short ID of the disconnected peer. */ -static void -send_destroy_path (struct MeshTunnel *t, GNUNET_PEER_Id destination) +void +client_notify_peer_disconnected (struct MeshClient *c, + struct MeshTunnel *t, + GNUNET_PEER_Id peer_id) { - struct MeshPeerPath *p; - size_t size; + struct GNUNET_MESH_PeerControl msg; - p = tree_get_path_to_peer (t->tree, destination); - if (NULL == p) - { - GNUNET_break (0); + if (NULL == t->owner || NULL == nc) return; - } - size = sizeof (struct GNUNET_MESH_ManipulatePath); - size += p->length * sizeof (struct GNUNET_PeerIdentity); - { - struct GNUNET_MESH_ManipulatePath *msg; - struct GNUNET_PeerIdentity *pi; - char cbuf[size]; - unsigned int i; - msg = (struct GNUNET_MESH_ManipulatePath *) cbuf; - msg->header.size = htons (size); - msg->header.type = htons (GNUNET_MESSAGE_TYPE_MESH_PATH_DESTROY); - msg->tid = htonl (t->id.tid); - pi = (struct GNUNET_PeerIdentity *) &msg[1]; - for (i = 0; i < p->length; i++) - { - GNUNET_PEER_resolve (p->peers[i], &pi[i]); - } - send_message (&msg->header, tree_get_first_hop (t->tree, destination)); - } - path_destroy (p); + msg.header.size = htons (sizeof (msg)); + msg.header.type = htons (GNUNET_MESSAGE_TYPE_MESH_LOCAL_PEER_DEL); + msg.tunnel_id = htonl (t->local_tid); + GNUNET_PEER_resolve (peer_id, &msg.peer); + GNUNET_SERVER_notification_context_unicast (nc, t->owner->handle, + &msg.header, GNUNET_NO); } /** - * Try to establish a new connection to this peer. - * Use the best path for the given tunnel. - * If the peer doesn't have any path to it yet, try to get one. - * If the peer already has some path, send a CREATE PATH towards it. + * Send the message to all clients that have subscribed to its type * - * @param peer PeerInfo of the peer. - * @param t Tunnel for which to create the path, if possible. + * @param msg Pointer to the message itself + * @param payload Pointer to the payload of the message. + * @param t The tunnel to whose clients this message goes. + * + * @return number of clients this message was sent to */ -static void -peer_info_connect (struct MeshPeerInfo *peer, struct MeshTunnel *t) +static unsigned int +send_subscribed_clients (const struct GNUNET_MessageHeader *msg, + const struct GNUNET_MessageHeader *payload, + struct MeshTunnel *t) { - struct MeshPeerPath *p; - struct MeshPathInfo *path_info; + struct MeshClient *c; + MESH_TunnelNumber *tid; + unsigned int count; + uint16_t type; + char cbuf[htons (msg->size)]; - if (NULL != peer->path_head) + type = ntohs (payload->type); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Sending to clients...\n"); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "message of type %s\n", + GNUNET_MESH_DEBUG_M2S (type)); + + memcpy (cbuf, msg, sizeof (cbuf)); + switch (htons (msg->type)) { - p = tree_get_path_to_peer (t->tree, peer->id); - if (NULL == p) - { - GNUNET_break (0); - return; - } + struct GNUNET_MESH_Unicast *uc; + struct GNUNET_MESH_Multicast *mc; + struct GNUNET_MESH_ToOrigin *to; - // FIXME always send create path to self - if (p->length > 1) - { - send_create_path (peer, p, t); - } - else - { - GNUNET_HashCode hash; + case GNUNET_MESSAGE_TYPE_MESH_UNICAST: + uc = (struct GNUNET_MESH_Unicast *) cbuf; + tid = &uc->tid; + break; + case GNUNET_MESSAGE_TYPE_MESH_MULTICAST: + mc = (struct GNUNET_MESH_Multicast *) cbuf; + tid = &mc->tid; + break; + case GNUNET_MESSAGE_TYPE_MESH_TO_ORIGIN: + to = (struct GNUNET_MESH_ToOrigin *) cbuf; + tid = &to->tid; + break; + default: + GNUNET_break (0); + return 0; + } - path_destroy (p); - send_client_peer_connected (t, myid); - t->local_tid_dest = next_local_tid++; - GNUNET_CRYPTO_hash (&t->local_tid_dest, sizeof (MESH_TunnelNumber), - &hash); - if (GNUNET_OK != - GNUNET_CONTAINER_multihashmap_put (incoming_tunnels, &hash, t, - GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_FAST)) + for (count = 0, c = clients; c != NULL; c = c->next) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " client %u\n", c->id); + if (client_is_subscribed (type, c)) + { + if (htons (msg->type) == GNUNET_MESSAGE_TYPE_MESH_TO_ORIGIN) { - GNUNET_break (0); - return; + if (c != t->owner) + continue; + *tid = htonl (t->local_tid); + } + else + { + if (GNUNET_NO == client_knows_tunnel (c, t)) + { + /* This client doesn't know the tunnel */ + struct GNUNET_MESH_TunnelNotification tmsg; + struct GNUNET_HashCode hash; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " sending tunnel create\n"); + tmsg.header.size = htons (sizeof (tmsg)); + tmsg.header.type = htons (GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_CREATE); + GNUNET_PEER_resolve (t->id.oid, &tmsg.peer); + tmsg.tunnel_id = htonl (t->local_tid_dest); + tmsg.opt = 0; + if (GNUNET_YES == t->speed_min) + tmsg.opt |= MESH_TUNNEL_OPT_SPEED_MIN; + if (GNUNET_YES == t->nobuffer) + tmsg.opt |= MESH_TUNNEL_OPT_NOBUFFER; + GNUNET_SERVER_notification_context_unicast (nc, c->handle, + &tmsg.header, GNUNET_NO); + tunnel_add_client (t, c); + GNUNET_CRYPTO_hash (&t->local_tid_dest, sizeof (MESH_TunnelNumber), + &hash); + GNUNET_break (GNUNET_OK == GNUNET_CONTAINER_multihashmap_put ( + c->incoming_tunnels, &hash, t, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_FAST)); + } + *tid = htonl (t->local_tid_dest); } + + /* Check if the client wants to get traffic from the tunnel */ + if (GNUNET_NO == client_wants_tunnel(c, t)) + continue; + count++; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " sending\n"); + GNUNET_SERVER_notification_context_unicast (nc, c->handle, + (struct GNUNET_MessageHeader + *) cbuf, GNUNET_NO); } } - else if (NULL == peer->dhtget) - { - struct GNUNET_PeerIdentity id; - GNUNET_PEER_resolve (peer->id, &id); - path_info = GNUNET_malloc (sizeof (struct MeshPathInfo)); - path_info->peer = peer; - path_info->t = t; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - " Starting DHT GET for peer %s\n", GNUNET_i2s (&id)); - peer->dhtgetcls = path_info; - peer->dhtget = GNUNET_DHT_get_start (dht_handle, /* handle */ - GNUNET_BLOCK_TYPE_TEST, /* type */ - &id.hashPubKey, /* key to search */ - 10, /* replication level */ - GNUNET_DHT_RO_RECORD_ROUTE | GNUNET_DHT_RO_DEMULTIPLEX_EVERYWHERE, NULL, /* xquery */ - 0, /* xquery bits */ - &dht_get_id_handler, path_info); - } - /* Otherwise, there is no path but the DHT get is already started. */ + return count; } /** - * Task to delay the connection of a peer + * Notify the client that owns the tunnel that a peer has connected to it + * (the requested path to it has been confirmed). * - * @param cls Closure (path info with tunnel and peer to connect). - * Will be free'd on exection. - * @param tc TaskContext + * @param t Tunnel whose owner to notify + * @param id Short id of the peer that has connected */ static void -peer_info_connect_task (void *cls, - const struct GNUNET_SCHEDULER_TaskContext *tc) +send_client_peer_connected (const struct MeshTunnel *t, const GNUNET_PEER_Id id) { - struct MeshPathInfo *path_info = cls; + struct GNUNET_MESH_PeerControl pc; - if (0 != (GNUNET_SCHEDULER_REASON_SHUTDOWN & tc->reason)) - { - GNUNET_free (cls); + if (NULL == t->owner || GNUNET_YES == t->destroy) return; - } - peer_info_connect (path_info->peer, path_info->t); - GNUNET_free (cls); + + pc.header.type = htons (GNUNET_MESSAGE_TYPE_MESH_LOCAL_PEER_ADD); + pc.header.size = htons (sizeof (struct GNUNET_MESH_PeerControl)); + pc.tunnel_id = htonl (t->local_tid); + GNUNET_PEER_resolve (id, &pc.peer); + GNUNET_SERVER_notification_context_unicast (nc, t->owner->handle, &pc.header, + GNUNET_NO); } /** - * Destroy the peer_info and free any allocated resources linked to it - * - * @param pi The peer_info to destroy. + * Notify all clients (not depending on registration status) that the incoming + * tunnel is no longer valid. * - * @return GNUNET_OK on success + * @param t Tunnel that was destroyed. */ -static int -peer_info_destroy (struct MeshPeerInfo *pi) +static void +send_clients_tunnel_destroy (struct MeshTunnel *t) { - struct GNUNET_PeerIdentity id; - struct MeshPeerPath *p; - struct MeshPeerPath *nextp; - unsigned int i; - - GNUNET_PEER_resolve (pi->id, &id); - GNUNET_PEER_change_rc (pi->id, -1); + struct GNUNET_MESH_TunnelMessage msg; - if (GNUNET_YES != - GNUNET_CONTAINER_multihashmap_remove (peers, &id.hashPubKey, pi)) - { - GNUNET_break (0); - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "removing peer %s, not in hashmap\n", GNUNET_i2s (&id)); - } - if (NULL != pi->dhtget) - { - GNUNET_DHT_get_stop (pi->dhtget); - GNUNET_free (pi->dhtgetcls); - } - for (i = 0; i < CORE_QUEUE_SIZE; i++) - { - peer_info_cancel_transmission (pi, i); - } - p = pi->path_head; - while (NULL != p) - { - nextp = p->next; - GNUNET_CONTAINER_DLL_remove (pi->path_head, pi->path_tail, p); - path_destroy (p); - p = nextp; - } - GNUNET_free (pi); - return GNUNET_OK; + msg.header.size = htons (sizeof (msg)); + msg.header.type = htons (GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_DESTROY); + msg.tunnel_id = htonl (t->local_tid_dest); + GNUNET_SERVER_notification_context_broadcast (nc, &msg.header, GNUNET_NO); } /** - * Remove all paths that rely on a direct connection between p1 and p2 - * from the peer itself and notify all tunnels about it. - * - * @param peer PeerInfo of affected peer. - * @param p1 GNUNET_PEER_Id of one peer. - * @param p2 GNUNET_PEER_Id of another peer that was connected to the first and - * no longer is. + * Notify clients of tunnel disconnections, if needed. + * In case the origin disconnects, the destination clients get a tunnel destroy + * notification. If the last destination disconnects (only one remaining client + * in tunnel), the origin gets a (local ID) peer disconnected. + * Note that the function must be called BEFORE removing the client from + * the tunnel. * - * TODO: optimize (see below) + * @param t Tunnel that was destroyed. + * @param c Client that disconnected. */ static void -peer_info_remove_path (struct MeshPeerInfo *peer, GNUNET_PEER_Id p1, - GNUNET_PEER_Id p2) +send_client_tunnel_disconnect (struct MeshTunnel *t, struct MeshClient *c) { - struct MeshPeerPath *p; - struct MeshPeerPath *aux; - struct MeshPeerInfo *peer_d; - GNUNET_PEER_Id d; - unsigned int destroyed; - unsigned int best; - unsigned int cost; unsigned int i; - destroyed = 0; - p = peer->path_head; - while (NULL != p) + if (c == t->owner) { - aux = p->next; - for (i = 0; i < (p->length - 1); i++) - { - if ((p->peers[i] == p1 && p->peers[i + 1] == p2) || - (p->peers[i] == p2 && p->peers[i + 1] == p1)) - { - GNUNET_CONTAINER_DLL_remove (peer->path_head, peer->path_tail, p); - path_destroy (p); - destroyed++; - break; - } - } - p = aux; - } - if (0 == destroyed) - return; + struct GNUNET_MESH_TunnelMessage msg; - for (i = 0; i < peer->ntunnels; i++) + msg.header.size = htons (sizeof (msg)); + msg.header.type = htons (GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_DESTROY); + msg.tunnel_id = htonl (t->local_tid_dest); + for (i = 0; i < t->nclients; i++) + GNUNET_SERVER_notification_context_unicast (nc, t->clients[i]->handle, + &msg.header, GNUNET_NO); + } + // FIXME when to disconnect an incoming tunnel? + else if (1 == t->nclients && NULL != t->owner) { - d = tunnel_notify_connection_broken (peer->tunnels[i], p1, p2); - if (0 == d) - continue; - /* TODO - * Problem: one or more peers have been deleted from the tunnel tree. - * We don't know who they are to try to add them again. - * We need to try to find a new path for each of the disconnected peers. - * Some of them might already have a path to reach them that does not - * involve p1 and p2. Adding all anew might render in a better tree than - * the trivial immediate fix. - * - * Trivial immiediate fix: try to reconnect to the disconnected node. All - * its children will be reachable trough him. - */ - peer_d = peer_info_get_short (d); - best = UINT_MAX; - aux = NULL; - for (p = peer_d->path_head; NULL != p; p = p->next) - { - if ((cost = tree_get_path_cost (peer->tunnels[i]->tree, p)) < best) - { - best = cost; - aux = p; - } - } - if (NULL != aux) - { - /* No callback, as peer will be already disconnected and a connection - * scheduled by tunnel_notify_connection_broken. - */ - tree_add_path (peer->tunnels[i]->tree, aux, NULL, NULL); - } - else - { - peer_info_connect (peer_d, peer->tunnels[i]); - } + struct GNUNET_MESH_PeerControl msg; + + msg.header.size = htons (sizeof (msg)); + msg.header.type = htons (GNUNET_MESSAGE_TYPE_MESH_LOCAL_PEER_DEL); + msg.tunnel_id = htonl (t->local_tid); + msg.peer = my_full_id; + GNUNET_SERVER_notification_context_unicast (nc, t->owner->handle, + &msg.header, GNUNET_NO); } } /** - * Add the path to the peer and update the path used to reach it in case this - * is the shortest. + * Iterator over all the peers to remove the oldest not-used entry. * - * @param peer_info Destination peer to add the path to. - * @param path New path to add. Last peer must be the peer in arg 1. - * Path will be either used of freed if already known. - * @param trusted Do we trust that this path is real? + * @param cls Closure (unsued). + * @param key ID of the peer. + * @param value Peer_Info of the peer. + * + * FIXME implement */ -void -peer_info_add_path (struct MeshPeerInfo *peer_info, struct MeshPeerPath *path, - int trusted) +static int +peer_info_timeout (void *cls, + const struct GNUNET_HashCode *key, + void *value) { - struct MeshPeerPath *aux; - unsigned int l; - unsigned int l2; - - if ((NULL == peer_info) || (NULL == path)) - { - GNUNET_break (0); - path_destroy (path); - return; - } - if (path->peers[path->length - 1] != peer_info->id) - { - GNUNET_break (0); - path_destroy (path); - return; - } - if (path->length <= 2 && GNUNET_NO == trusted) - { - /* Only allow CORE to tell us about direct paths */ - path_destroy (path); - return; - } - GNUNET_assert (peer_info->id == path->peers[path->length - 1]); - for (l = 1; l < path->length; l++) - { - if (path->peers[l] == myid) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "shortening path by %u\n", l); - for (l2 = 0; l2 < path->length - l; l2++) - { - path->peers[l2] = path->peers[l + l2]; - } - path->length -= l; - l = 1; - path->peers = - GNUNET_realloc (path->peers, path->length * sizeof (GNUNET_PEER_Id)); - } - } -#if MESH_DEBUG - { - struct GNUNET_PeerIdentity id; + return GNUNET_YES; +} - GNUNET_PEER_resolve (peer_info->id, &id); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "adding path [%u] to peer %s\n", - path->length, GNUNET_i2s (&id)); - } -#endif - l = path_get_length (path); - if (0 == l) - { - GNUNET_free (path); - return; - } +/** + * Retrieve the MeshPeerInfo stucture associated with the peer, create one + * and insert it in the appropiate structures if the peer is not known yet. + * + * @param peer Full identity of the peer. + * + * @return Existing or newly created peer info. + */ +static struct MeshPeerInfo * +peer_info_get (const struct GNUNET_PeerIdentity *peer) +{ + struct MeshPeerInfo *peer_info; - GNUNET_assert (peer_info->id == path->peers[path->length - 1]); - for (aux = peer_info->path_head; aux != NULL; aux = aux->next) + peer_info = GNUNET_CONTAINER_multihashmap_get (peers, &peer->hashPubKey); + if (NULL == peer_info) { - l2 = path_get_length (aux); - if (l2 > l) - { - GNUNET_CONTAINER_DLL_insert_before (peer_info->path_head, - peer_info->path_tail, aux, path); - return; - } - else + peer_info = + (struct MeshPeerInfo *) GNUNET_malloc (sizeof (struct MeshPeerInfo)); + if (GNUNET_CONTAINER_multihashmap_size (peers) > max_peers) { - if (l2 == l && memcmp (path->peers, aux->peers, l) == 0) - { - path_destroy (path); - return; - } + GNUNET_CONTAINER_multihashmap_iterate (peers, + &peer_info_timeout, + NULL); } + GNUNET_CONTAINER_multihashmap_put (peers, &peer->hashPubKey, peer_info, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_FAST); + peer_info->id = GNUNET_PEER_intern (peer); } - GNUNET_CONTAINER_DLL_insert_tail (peer_info->path_head, peer_info->path_tail, - path); - return; + peer_info->last_contact = GNUNET_TIME_absolute_get(); + + return peer_info; } /** - * Add the path to the origin peer and update the path used to reach it in case - * this is the shortest. - * The path is given in peer_info -> destination, therefore we turn the path - * upside down first. + * Retrieve the MeshPeerInfo stucture associated with the peer, create one + * and insert it in the appropiate structures if the peer is not known yet. * - * @param peer_info Peer to add the path to, being the origin of the path. - * @param path New path to add after being inversed. - * @param trusted Do we trust that this path is real? + * @param peer Short identity of the peer. + * + * @return Existing or newly created peer info. */ -static void -peer_info_add_path_to_origin (struct MeshPeerInfo *peer_info, - struct MeshPeerPath *path, int trusted) +static struct MeshPeerInfo * +peer_info_get_short (const GNUNET_PEER_Id peer) { - path_invert (path); - peer_info_add_path (peer_info, path, trusted); + struct GNUNET_PeerIdentity id; + + GNUNET_PEER_resolve (peer, &id); + return peer_info_get (&id); } /** - * Build a PeerPath from the paths returned from the DHT, reversing the paths - * to obtain a local peer -> destination path and interning the peer ids. + * Iterator to remove the tunnel from the list of tunnels a peer participates + * in. * - * @return Newly allocated and created path + * @param cls Closure (tunnel info) + * @param key GNUNET_PeerIdentity of the peer (unused) + * @param value PeerInfo of the peer + * + * @return always GNUNET_YES, to keep iterating */ -static struct MeshPeerPath * -path_build_from_dht (const struct GNUNET_PeerIdentity *get_path, - unsigned int get_path_length, - const struct GNUNET_PeerIdentity *put_path, - unsigned int put_path_length) +static int +peer_info_delete_tunnel (void *cls, const struct GNUNET_HashCode * key, void *value) { - struct MeshPeerPath *p; - GNUNET_PEER_Id id; - int i; + struct MeshTunnel *t = cls; + struct MeshPeerInfo *peer = value; + unsigned int i; - p = path_new (1); - p->peers[0] = myid; - GNUNET_PEER_change_rc (myid, 1); - i = get_path_length; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " GET has %d hops.\n", i); - for (i--; i >= 0; i--) - { - id = GNUNET_PEER_intern (&get_path[i]); - if (p->length > 0 && id == p->peers[p->length - 1]) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " Optimizing 1 hop out.\n"); - GNUNET_PEER_change_rc (id, -1); - } - else - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " Adding from GET: %s.\n", - GNUNET_i2s (&get_path[i])); - p->length++; - p->peers = GNUNET_realloc (p->peers, sizeof (GNUNET_PEER_Id) * p->length); - p->peers[p->length - 1] = id; - } - } - i = put_path_length; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " PUT has %d hops.\n", i); - for (i--; i >= 0; i--) + for (i = 0; i < peer->ntunnels; i++) { - id = GNUNET_PEER_intern (&put_path[i]); - if (id == myid) - { - /* PUT path went through us, so discard the path up until now and start - * from here to get a much shorter (and loop-free) path. - */ - path_destroy (p); - p = path_new (0); - } - if (p->length > 0 && id == p->peers[p->length - 1]) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " Optimizing 1 hop out.\n"); - GNUNET_PEER_change_rc (id, -1); - } - else + if (0 == + memcmp (&peer->tunnels[i]->id, &t->id, sizeof (struct MESH_TunnelID))) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " Adding from PUT: %s.\n", - GNUNET_i2s (&put_path[i])); - p->length++; - p->peers = GNUNET_realloc (p->peers, sizeof (GNUNET_PEER_Id) * p->length); - p->peers[p->length - 1] = id; + peer->ntunnels--; + peer->tunnels[i] = peer->tunnels[peer->ntunnels]; + peer->tunnels = GNUNET_realloc (peer->tunnels, peer->ntunnels); + return GNUNET_YES; } } -#if MESH_DEBUG - if (get_path_length > 0) - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " (first of GET: %s)\n", - GNUNET_i2s (&get_path[0])); - if (put_path_length > 0) - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " (first of PUT: %s)\n", - GNUNET_i2s (&put_path[0])); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " In total: %d hops\n", - p->length); - for (i = 0; i < p->length; i++) - { - struct GNUNET_PeerIdentity peer_id; - - GNUNET_PEER_resolve (p->peers[i], &peer_id); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " %u: %s\n", p->peers[i], - GNUNET_i2s (&peer_id)); - } -#endif - return p; + return GNUNET_YES; } /** - * Adds a path to the peer_infos of all the peers in the path - * - * @param p Path to process. - * @param confirmed Whether we know if the path works or not. FIXME use - */ -static void -path_add_to_peers (struct MeshPeerPath *p, int confirmed) + * Core callback to write a pre-constructed data packet to core buffer + * + * @param cls Closure (MeshTransmissionDescriptor with data in "data" member). + * @param size Number of bytes available in buf. + * @param buf Where the to write the message. + * + * @return number of bytes written to buf + */ +static size_t +send_core_data_raw (void *cls, size_t size, void *buf) { - unsigned int i; + struct MeshTransmissionDescriptor *info = cls; + struct GNUNET_MessageHeader *msg; + size_t total_size; - /* TODO: invert and add */ - for (i = 0; i < p->length && p->peers[i] != myid; i++) /* skip'em */ ; - for (i++; i < p->length; i++) - { - struct MeshPeerInfo *aux; - struct MeshPeerPath *copy; + GNUNET_assert (NULL != info); + GNUNET_assert (NULL != info->mesh_data); + msg = (struct GNUNET_MessageHeader *) info->mesh_data->data; + total_size = ntohs (msg->size); - aux = peer_info_get_short (p->peers[i]); - copy = path_duplicate (p); - copy->length = i + 1; - peer_info_add_path (aux, copy, GNUNET_NO); + if (total_size > size) + { + GNUNET_break (0); + return 0; } + memcpy (buf, msg, total_size); + data_descriptor_decrement_rc (info->mesh_data); + GNUNET_free (info); + return total_size; } /** - * Send keepalive packets for a peer + * Sends an already built non-multicast message to a peer, + * properly registrating all used resources. * - * @param cls Closure (tunnel for which to send the keepalive). - * @param tc Notification context. - * - * TODO: implement explicit multicast keepalive? + * @param message Message to send. Function makes a copy of it. + * @param peer Short ID of the neighbor whom to send the message. + * @param t Tunnel on which this message is transmitted. */ static void -path_refresh (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc); - - -/** - * Search for a tunnel among the incoming tunnels - * - * @param tid the local id of the tunnel - * - * @return tunnel handler, NULL if doesn't exist - */ -static struct MeshTunnel * -tunnel_get_incoming (MESH_TunnelNumber tid) +send_prebuilt_message (const struct GNUNET_MessageHeader *message, + const struct GNUNET_PeerIdentity *peer, + struct MeshTunnel *t) { - GNUNET_HashCode hash; + struct MeshTransmissionDescriptor *info; + struct MeshPeerInfo *neighbor; + struct MeshPeerPath *p; + size_t size; + uint16_t type; - GNUNET_assert (tid >= GNUNET_MESH_LOCAL_TUNNEL_ID_SERV); - GNUNET_CRYPTO_hash (&tid, sizeof (MESH_TunnelNumber), &hash); - return GNUNET_CONTAINER_multihashmap_get (incoming_tunnels, &hash); -} +// GNUNET_TRANSPORT_try_connect(); FIXME use? + size = ntohs (message->size); + info = GNUNET_malloc (sizeof (struct MeshTransmissionDescriptor)); + info->mesh_data = GNUNET_malloc (sizeof (struct MeshData)); + info->mesh_data->data = GNUNET_malloc (size); + memcpy (info->mesh_data->data, message, size); + type = ntohs(message->type); + switch (type) + { + struct GNUNET_MESH_Unicast *m; + struct GNUNET_MESH_ToOrigin *to; -/** - * Search for a tunnel among the tunnels for a client - * - * @param c the client whose tunnels to search in - * @param tid the local id of the tunnel - * - * @return tunnel handler, NULL if doesn't exist - */ -static struct MeshTunnel * -tunnel_get_by_local_id (struct MeshClient *c, MESH_TunnelNumber tid) -{ - if (tid >= GNUNET_MESH_LOCAL_TUNNEL_ID_SERV) + case GNUNET_MESSAGE_TYPE_MESH_UNICAST: + m = (struct GNUNET_MESH_Unicast *) info->mesh_data->data; + m->ttl = htonl (ntohl (m->ttl) - 1); + break; + case GNUNET_MESSAGE_TYPE_MESH_TO_ORIGIN: + to = (struct GNUNET_MESH_ToOrigin *) info->mesh_data->data; + t->bck_pid++; + to->pid = htonl(t->bck_pid); + } + info->mesh_data->data_len = size; + info->mesh_data->reference_counter = 1; + info->mesh_data->total_out = 1; + neighbor = peer_info_get (peer); + for (p = neighbor->path_head; NULL != p; p = p->next) { - return tunnel_get_incoming (tid); + if (2 >= p->length) + { + break; + } } - else + if (NULL == p) { - GNUNET_HashCode hash; +#if MESH_DEBUG + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " %s IS NOT DIRECTLY CONNECTED\n", + GNUNET_i2s(peer)); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " PATHS TO %s:\n", + GNUNET_i2s(peer)); + for (p = neighbor->path_head; NULL != p; p = p->next) + { + struct GNUNET_PeerIdentity debug_id; + unsigned int i; - GNUNET_CRYPTO_hash (&tid, sizeof (MESH_TunnelNumber), &hash); - return GNUNET_CONTAINER_multihashmap_get (c->own_tunnels, &hash); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " path with %u hops through:\n", + p->length); + for (i = 0; i < p->length; i++) + { + GNUNET_PEER_resolve(p->peers[i], &debug_id); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " hop %u: %s\n", + i, GNUNET_i2s(&debug_id)); + } + } +#endif + GNUNET_break (0); // FIXME sometimes fails (testing disconnect?) + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + " no direct connection to %s\n", + GNUNET_i2s (peer)); + GNUNET_free (info->mesh_data->data); + GNUNET_free (info->mesh_data); + GNUNET_free (info); + return; } + info->peer = neighbor; + if (GNUNET_MESSAGE_TYPE_MESH_PATH_ACK == type) + type = 0; + queue_add (info, + type, + size, + neighbor, + t); } /** - * Search for a tunnel by global ID using PEER_ID - * - * @param pi owner of the tunnel - * @param tid global tunnel number - * - * @return tunnel handler, NULL if doesn't exist - */ -static struct MeshTunnel * -tunnel_get_by_pi (GNUNET_PEER_Id pi, MESH_TunnelNumber tid) -{ - struct MESH_TunnelID id; - GNUNET_HashCode hash; - - id.oid = pi; - id.tid = tid; - - GNUNET_CRYPTO_hash (&id, sizeof (struct MESH_TunnelID), &hash); - return GNUNET_CONTAINER_multihashmap_get (tunnels, &hash); -} - - -/** - * Search for a tunnel by global ID using full PeerIdentities - * - * @param oid owner of the tunnel - * @param tid global tunnel number + * Sends a CREATE PATH message for a path to a peer, properly registrating + * all used resources. * - * @return tunnel handler, NULL if doesn't exist - */ -static struct MeshTunnel * -tunnel_get (struct GNUNET_PeerIdentity *oid, MESH_TunnelNumber tid) -{ - return tunnel_get_by_pi (GNUNET_PEER_search (oid), tid); -} - - -/** - * Delete an active client from the tunnel. - * - * @param t Tunnel. - * @param c Client. + * @param peer PeerInfo of the final peer for whom this path is being created. + * @param p Path itself. + * @param t Tunnel for which the path is created. */ static void -tunnel_delete_active_client (struct MeshTunnel *t, const struct MeshClient *c) +send_create_path (struct MeshPeerInfo *peer, struct MeshPeerPath *p, + struct MeshTunnel *t) { + struct GNUNET_PeerIdentity id; + struct MeshPathInfo *path_info; + struct MeshPeerInfo *neighbor; + unsigned int i; - for (i = 0; i < t->nclients; i++) + if (NULL == p) { - if (t->clients[i] == c) + p = tree_get_path_to_peer (t->tree, peer->id); + if (NULL == p) { - t->clients[i] = t->clients[t->nclients - 1]; - GNUNET_array_grow (t->clients, t->nclients, t->nclients - 1); - break; + GNUNET_break (0); + return; } } + for (i = 0; i < p->length; i++) + { + if (p->peers[i] == myid) + break; + } + if (i >= p->length - 1) + { + path_destroy (p); + GNUNET_break (0); + return; + } + GNUNET_PEER_resolve (p->peers[i + 1], &id); + + path_info = GNUNET_malloc (sizeof (struct MeshPathInfo)); + path_info->path = p; + path_info->t = t; + neighbor = peer_info_get (&id); + path_info->peer = neighbor; + queue_add (path_info, + GNUNET_MESSAGE_TYPE_MESH_PATH_CREATE, + sizeof (struct GNUNET_MESH_ManipulatePath) + + (p->length * sizeof (struct GNUNET_PeerIdentity)), + neighbor, + t); } /** - * Delete an ignored client from the tunnel. - * - * @param t Tunnel. - * @param c Client. + * Sends a DESTROY PATH message to free resources for a path in a tunnel + * + * @param t Tunnel whose path to destroy. + * @param destination Short ID of the peer to whom the path to destroy. */ static void -tunnel_delete_ignored_client (struct MeshTunnel *t, const struct MeshClient *c) +send_destroy_path (struct MeshTunnel *t, GNUNET_PEER_Id destination) { - unsigned int i; + struct MeshPeerPath *p; + size_t size; - for (i = 0; i < t->nignore; i++) + p = tree_get_path_to_peer (t->tree, destination); + if (NULL == p) { - if (t->ignore[i] == c) + GNUNET_break (0); + return; + } + size = sizeof (struct GNUNET_MESH_ManipulatePath); + size += p->length * sizeof (struct GNUNET_PeerIdentity); + { + struct GNUNET_MESH_ManipulatePath *msg; + struct GNUNET_PeerIdentity *pi; + char cbuf[size]; + unsigned int i; + + msg = (struct GNUNET_MESH_ManipulatePath *) cbuf; + msg->header.size = htons (size); + msg->header.type = htons (GNUNET_MESSAGE_TYPE_MESH_PATH_DESTROY); + msg->tid = htonl (t->id.tid); + pi = (struct GNUNET_PeerIdentity *) &msg[1]; + for (i = 0; i < p->length; i++) { - t->ignore[i] = t->ignore[t->nignore - 1]; - GNUNET_array_grow (t->ignore, t->nignore, t->nignore - 1); - break; + GNUNET_PEER_resolve (p->peers[i], &pi[i]); } + send_prebuilt_message (&msg->header, tree_get_first_hop (t->tree, destination), t); } + path_destroy (p); } /** - * Delete a client from the tunnel. It should be only done on - * client disconnection, otherwise use client_ignore_tunnel. - * - * @param t Tunnel. - * @param c Client. - */ -static void -tunnel_delete_client (struct MeshTunnel *t, const struct MeshClient *c) -{ - tunnel_delete_ignored_client (t, c); - tunnel_delete_active_client (t, c); -} - - -/** - * Callback used to notify a client owner of a tunnel that a peer has - * disconnected, most likely because of a path change. + * Sends a PATH ACK message in reponse to a received PATH_CREATE directed to us. * - * @param cls Closure (tunnel this notification is about). - * @param peer_id Short ID of disconnected peer. + * @param t Tunnel which to confirm. */ -void -notify_peer_disconnected (void *cls, GNUNET_PEER_Id peer_id) +static void +send_path_ack (struct MeshTunnel *t) { - struct MeshTunnel *t = cls; - struct MeshPeerInfo *peer; - struct MeshPathInfo *path_info; + struct MeshTransmissionDescriptor *info; + struct GNUNET_PeerIdentity id; + GNUNET_PEER_Id peer; - if (NULL != t->owner && NULL != nc) - { - struct GNUNET_MESH_PeerControl msg; + peer = tree_get_predecessor (t->tree); + GNUNET_PEER_resolve (peer, &id); + info = GNUNET_malloc (sizeof (struct MeshTransmissionDescriptor)); + info->origin = &t->id; + info->peer = GNUNET_CONTAINER_multihashmap_get (peers, &id.hashPubKey); + GNUNET_assert (NULL != info->peer); - msg.header.size = htons (sizeof (msg)); - msg.header.type = htons (GNUNET_MESSAGE_TYPE_MESH_LOCAL_PEER_DEL); - msg.tunnel_id = htonl (t->local_tid); - GNUNET_PEER_resolve (peer_id, &msg.peer); - GNUNET_SERVER_notification_context_unicast (nc, t->owner->handle, - &msg.header, GNUNET_NO); - } - peer = peer_info_get_short (peer_id); - path_info = GNUNET_malloc (sizeof (struct MeshPathInfo)); - path_info->peer = peer; - path_info->t = t; - GNUNET_SCHEDULER_add_now (&peer_info_connect_task, path_info); + queue_add (info, + GNUNET_MESSAGE_TYPE_MESH_PATH_ACK, + sizeof (struct GNUNET_MESH_PathACK), + info->peer, + t); } /** - * Add a peer to a tunnel, accomodating paths accordingly and initializing all - * needed rescources. - * If peer already exists, reevaluate shortest path and change if different. - * - * @param t Tunnel we want to add a new peer to - * @param peer PeerInfo of the peer being added + * Try to establish a new connection to this peer. + * Use the best path for the given tunnel. + * If the peer doesn't have any path to it yet, try to get one. + * If the peer already has some path, send a CREATE PATH towards it. * + * @param peer PeerInfo of the peer. + * @param t Tunnel for which to create the path, if possible. */ static void -tunnel_add_peer (struct MeshTunnel *t, struct MeshPeerInfo *peer) +peer_info_connect (struct MeshPeerInfo *peer, struct MeshTunnel *t) { - struct GNUNET_PeerIdentity id; - struct MeshPeerPath *best_p; struct MeshPeerPath *p; - unsigned int best_cost; - unsigned int cost; + struct MeshPathInfo *path_info; - GNUNET_PEER_resolve (peer->id, &id); - if (GNUNET_NO == - GNUNET_CONTAINER_multihashmap_contains (t->peers, &id.hashPubKey)) + if (NULL != peer->path_head) { - t->peers_total++; - GNUNET_array_append (peer->tunnels, peer->ntunnels, t); - GNUNET_assert (GNUNET_OK == - GNUNET_CONTAINER_multihashmap_put (t->peers, &id.hashPubKey, - peer, - GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_FAST)); - } + p = tree_get_path_to_peer (t->tree, peer->id); + if (NULL == p) + { + GNUNET_break (0); + return; + } - if (NULL != (p = peer->path_head)) - { - best_p = p; - best_cost = tree_get_path_cost (t->tree, p); - while (NULL != p) + // FIXME always send create path to self + if (p->length > 1) { - if ((cost = tree_get_path_cost (t->tree, p)) < best_cost) + send_create_path (peer, p, t); + } + else + { + struct GNUNET_HashCode hash; + + path_destroy (p); + send_client_peer_connected (t, myid); + t->local_tid_dest = next_local_tid++; + GNUNET_CRYPTO_hash (&t->local_tid_dest, sizeof (MESH_TunnelNumber), + &hash); + if (GNUNET_OK != + GNUNET_CONTAINER_multihashmap_put (incoming_tunnels, &hash, t, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_FAST)) { - best_cost = cost; - best_p = p; + GNUNET_break (0); + return; } - p = p->next; } - tree_add_path (t->tree, best_p, ¬ify_peer_disconnected, t); - if (GNUNET_SCHEDULER_NO_TASK == t->path_refresh_task) - t->path_refresh_task = - GNUNET_SCHEDULER_add_delayed (REFRESH_PATH_TIME, &path_refresh, t); } - else + else if (NULL == peer->dhtget) { - /* Start a DHT get */ - peer_info_connect (peer, t); + struct GNUNET_PeerIdentity id; + + GNUNET_PEER_resolve (peer->id, &id); + path_info = GNUNET_malloc (sizeof (struct MeshPathInfo)); + path_info->peer = peer; + path_info->t = t; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " Starting DHT GET for peer %s\n", GNUNET_i2s (&id)); + peer->dhtgetcls = path_info; + peer->dhtget = GNUNET_DHT_get_start (dht_handle, /* handle */ + GNUNET_BLOCK_TYPE_MESH_PEER, /* type */ + &id.hashPubKey, /* key to search */ + dht_replication_level, /* replication level */ + GNUNET_DHT_RO_RECORD_ROUTE | + GNUNET_DHT_RO_DEMULTIPLEX_EVERYWHERE, + NULL, /* xquery */ // FIXME BLOOMFILTER + 0, /* xquery bits */ // FIXME BLOOMFILTER SIZE + &dht_get_id_handler, path_info); } + /* Otherwise, there is no path but the DHT get is already started. */ } + /** - * Add a path to a tunnel which we don't own, just to remember the next hop. - * If destination node was already in the tunnel, the first hop information - * will be replaced with the new path. - * - * @param t Tunnel we want to add a new peer to - * @param p Path to add - * @param own_pos Position of local node in path. + * Task to delay the connection of a peer * + * @param cls Closure (path info with tunnel and peer to connect). + * Will be free'd on exection. + * @param tc TaskContext */ static void -tunnel_add_path (struct MeshTunnel *t, struct MeshPeerPath *p, - unsigned int own_pos) +peer_info_connect_task (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) { - struct GNUNET_PeerIdentity id; + struct MeshPathInfo *path_info = cls; - GNUNET_assert (0 != own_pos); - tree_add_path (t->tree, p, NULL, NULL); - if (own_pos < p->length - 1) + path_info->peer->connect_task = GNUNET_SCHEDULER_NO_TASK; + + if (0 != (GNUNET_SCHEDULER_REASON_SHUTDOWN & tc->reason)) { - GNUNET_PEER_resolve (p->peers[own_pos + 1], &id); - tree_update_first_hops (t->tree, myid, &id); + GNUNET_free (cls); + return; } + peer_info_connect (path_info->peer, path_info->t); + GNUNET_free (cls); } /** - * Notifies a tunnel that a connection has broken that affects at least - * some of its peers. Sends a notification towards the root of the tree. - * In case the peer is the owner of the tree, notifies the client that owns - * the tunnel and tries to reconnect. + * Destroy the peer_info and free any allocated resources linked to it * - * @param t Tunnel affected. - * @param p1 Peer that got disconnected from p2. - * @param p2 Peer that got disconnected from p1. + * @param pi The peer_info to destroy. * - * @return Short ID of the peer disconnected (either p1 or p2). - * 0 if the tunnel remained unaffected. + * @return GNUNET_OK on success */ -static GNUNET_PEER_Id -tunnel_notify_connection_broken (struct MeshTunnel *t, GNUNET_PEER_Id p1, - GNUNET_PEER_Id p2) +static int +peer_info_destroy (struct MeshPeerInfo *pi) { - GNUNET_PEER_Id pid; + struct GNUNET_PeerIdentity id; + struct MeshPeerPath *p; + struct MeshPeerPath *nextp; - pid = - tree_notify_connection_broken (t->tree, p1, p2, ¬ify_peer_disconnected, - t); - if (myid != p1 && myid != p2) + GNUNET_PEER_resolve (pi->id, &id); + GNUNET_PEER_change_rc (pi->id, -1); + + if (GNUNET_YES != + GNUNET_CONTAINER_multihashmap_remove (peers, &id.hashPubKey, pi)) { - return pid; + GNUNET_break (0); + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + "removing peer %s, not in hashmap\n", GNUNET_i2s (&id)); } - if (pid != myid) + if (NULL != pi->dhtget) { - if (tree_get_predecessor (t->tree) != 0) - { - /* We are the peer still connected, notify owner of the disconnection. */ - struct GNUNET_MESH_PathBroken msg; - struct GNUNET_PeerIdentity neighbor; - - msg.header.size = htons (sizeof (msg)); - msg.header.type = htons (GNUNET_MESSAGE_TYPE_MESH_PATH_BROKEN); - GNUNET_PEER_resolve (t->id.oid, &msg.oid); - msg.tid = htonl (t->id.tid); - msg.peer1 = my_full_id; - GNUNET_PEER_resolve (pid, &msg.peer2); - GNUNET_PEER_resolve (tree_get_predecessor (t->tree), &neighbor); - send_message (&msg.header, &neighbor); - } + GNUNET_DHT_get_stop (pi->dhtget); + GNUNET_free (pi->dhtgetcls); } - return pid; + p = pi->path_head; + while (NULL != p) + { + nextp = p->next; + GNUNET_CONTAINER_DLL_remove (pi->path_head, pi->path_tail, p); + path_destroy (p); + p = nextp; + } + if (GNUNET_SCHEDULER_NO_TASK != pi->connect_task) + { + GNUNET_free (GNUNET_SCHEDULER_cancel (pi->connect_task)); + } + GNUNET_free (pi); + return GNUNET_OK; } /** - * Send a multicast packet to a neighbor. + * Remove all paths that rely on a direct connection between p1 and p2 + * from the peer itself and notify all tunnels about it. * - * @param cls Closure (Info about the multicast packet) - * @param neighbor_id Short ID of the neighbor to send the packet to. + * @param peer PeerInfo of affected peer. + * @param p1 GNUNET_PEER_Id of one peer. + * @param p2 GNUNET_PEER_Id of another peer that was connected to the first and + * no longer is. + * + * TODO: optimize (see below) */ static void -tunnel_send_multicast_iterator (void *cls, GNUNET_PEER_Id neighbor_id) +peer_info_remove_path (struct MeshPeerInfo *peer, GNUNET_PEER_Id p1, + GNUNET_PEER_Id p2) { - struct MeshData *mdata = cls; - struct MeshTransmissionDescriptor *info; - struct GNUNET_PeerIdentity neighbor; + struct MeshPeerPath *p; + struct MeshPeerPath *aux; + struct MeshPeerInfo *peer_d; + GNUNET_PEER_Id d; + unsigned int destroyed; + unsigned int best; + unsigned int cost; unsigned int i; - info = GNUNET_malloc (sizeof (struct MeshTransmissionDescriptor)); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "peer_info_remove_path\n"); + destroyed = 0; + p = peer->path_head; + while (NULL != p) + { + aux = p->next; + for (i = 0; i < (p->length - 1); i++) + { + if ((p->peers[i] == p1 && p->peers[i + 1] == p2) || + (p->peers[i] == p2 && p->peers[i + 1] == p1)) + { + GNUNET_CONTAINER_DLL_remove (peer->path_head, peer->path_tail, p); + path_destroy (p); + destroyed++; + break; + } + } + p = aux; + } + if (0 == destroyed) + return; - info->mesh_data = mdata; - (*(mdata->reference_counter)) ++; - info->destination = neighbor_id; - GNUNET_PEER_resolve (neighbor_id, &neighbor); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " sending to %s...\n", - GNUNET_i2s (&neighbor)); - info->peer = peer_info_get (&neighbor); - GNUNET_assert (NULL != info->peer); - i = peer_info_transmit_slot (info->peer); - info->handler_n = i; - info->peer->infos[i] = info; - info->peer->types[i] = GNUNET_MESSAGE_TYPE_MESH_MULTICAST; - info->peer->core_transmit[i] = - GNUNET_CORE_notify_transmit_ready (core_handle, 0, 0, - GNUNET_TIME_UNIT_FOREVER_REL, - &neighbor, info->mesh_data->data_len, - &send_core_data_multicast, info); + for (i = 0; i < peer->ntunnels; i++) + { + d = tunnel_notify_connection_broken (peer->tunnels[i], p1, p2); + if (0 == d) + continue; + /* TODO + * Problem: one or more peers have been deleted from the tunnel tree. + * We don't know who they are to try to add them again. + * We need to try to find a new path for each of the disconnected peers. + * Some of them might already have a path to reach them that does not + * involve p1 and p2. Adding all anew might render in a better tree than + * the trivial immediate fix. + * + * Trivial immiediate fix: try to reconnect to the disconnected node. All + * its children will be reachable trough him. + */ + peer_d = peer_info_get_short (d); + best = UINT_MAX; + aux = NULL; + for (p = peer_d->path_head; NULL != p; p = p->next) + { + if ((cost = tree_get_path_cost (peer->tunnels[i]->tree, p)) < best) + { + best = cost; + aux = p; + } + } + if (NULL != aux) + { + /* No callback, as peer will be already disconnected and a connection + * scheduled by tunnel_notify_connection_broken. + */ + tree_add_path (peer->tunnels[i]->tree, aux, NULL, NULL); + } + else + { + peer_info_connect (peer_d, peer->tunnels[i]); + } + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "peer_info_remove_path END\n"); } + /** - * Send a message in a tunnel in multicast, sending a copy to each child node - * down the local one in the tunnel tree. + * Add the path to the peer and update the path used to reach it in case this + * is the shortest. * - * @param t Tunnel in which to send the data. - * @param msg Message to be sent. - * @param internal Has the service generated this message? + * @param peer_info Destination peer to add the path to. + * @param path New path to add. Last peer must be the peer in arg 1. + * Path will be either used of freed if already known. + * @param trusted Do we trust that this path is real? */ -static void -tunnel_send_multicast (struct MeshTunnel *t, - const struct GNUNET_MessageHeader *msg, - int internal) +void +peer_info_add_path (struct MeshPeerInfo *peer_info, struct MeshPeerPath *path, + int trusted) { - struct MeshData *mdata; - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - " sending a multicast packet...\n"); - mdata = GNUNET_malloc (sizeof (struct MeshData)); - mdata->data_len = ntohs (msg->size); - mdata->reference_counter = GNUNET_malloc (sizeof (unsigned int)); - mdata->t = t; - mdata->data = GNUNET_malloc (mdata->data_len); - memcpy (mdata->data, msg, mdata->data_len); - if (ntohs (msg->type) == GNUNET_MESSAGE_TYPE_MESH_MULTICAST) - { - struct GNUNET_MESH_Multicast *mcast; + struct MeshPeerPath *aux; + unsigned int l; + unsigned int l2; - mcast = (struct GNUNET_MESH_Multicast *) mdata->data; - mcast->ttl = htonl (ntohl (mcast->ttl) - 1); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " data packet, ttl: %u\n", - ntohl (mcast->ttl)); + if ((NULL == peer_info) || (NULL == path)) + { + GNUNET_break (0); + path_destroy (path); + return; } - else + if (path->peers[path->length - 1] != peer_info->id) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " not a data packet, no ttl\n"); + GNUNET_break (0); + path_destroy (path); + return; + } + if (path->length <= 2 && GNUNET_NO == trusted) + { + /* Only allow CORE to tell us about direct paths */ + path_destroy (path); + return; } - if (NULL != t->owner && GNUNET_YES != t->owner->shutting_down - && GNUNET_NO == internal) + GNUNET_assert (peer_info->id == path->peers[path->length - 1]); + for (l = 1; l < path->length; l++) { - mdata->task = GNUNET_malloc (sizeof (GNUNET_SCHEDULER_TaskIdentifier)); - (*(mdata->task)) = - GNUNET_SCHEDULER_add_delayed (UNACKNOWLEDGED_WAIT, &client_allow_send, - mdata); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "timeout task %u\n", - *(mdata->task)); + if (path->peers[l] == myid) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "shortening path by %u\n", l); + for (l2 = 0; l2 < path->length - l; l2++) + { + path->peers[l2] = path->peers[l + l2]; + } + path->length -= l; + l = 1; + path->peers = + GNUNET_realloc (path->peers, path->length * sizeof (GNUNET_PEER_Id)); + } } +#if MESH_DEBUG + { + struct GNUNET_PeerIdentity id; - tree_iterate_children (t->tree, &tunnel_send_multicast_iterator, mdata); - if (*(mdata->reference_counter) == 0) + GNUNET_PEER_resolve (peer_info->id, &id); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "adding path [%u] to peer %s\n", + path->length, GNUNET_i2s (&id)); + } +#endif + l = path_get_length (path); + if (0 == l) { - GNUNET_free (mdata->data); - GNUNET_free (mdata->reference_counter); - if (NULL != mdata->task) + GNUNET_free (path); + return; + } + + GNUNET_assert (peer_info->id == path->peers[path->length - 1]); + for (aux = peer_info->path_head; aux != NULL; aux = aux->next) + { + l2 = path_get_length (aux); + if (l2 > l) { - GNUNET_SCHEDULER_cancel(*(mdata->task)); - GNUNET_free (mdata->task); - GNUNET_SERVER_receive_done(t->owner->handle, GNUNET_OK); + GNUNET_CONTAINER_DLL_insert_before (peer_info->path_head, + peer_info->path_tail, aux, path); + return; + } + else + { + if (l2 == l && memcmp (path->peers, aux->peers, l) == 0) + { + path_destroy (path); + return; + } } - // FIXME change order? - GNUNET_free (mdata); } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - " sending a multicast packet done\n"); + GNUNET_CONTAINER_DLL_insert_tail (peer_info->path_head, peer_info->path_tail, + path); return; } /** - * Send a message to all peers in this tunnel that the tunnel is no longer - * valid. + * Add the path to the origin peer and update the path used to reach it in case + * this is the shortest. + * The path is given in peer_info -> destination, therefore we turn the path + * upside down first. * - * @param t The tunnel whose peers to notify. + * @param peer_info Peer to add the path to, being the origin of the path. + * @param path New path to add after being inversed. + * @param trusted Do we trust that this path is real? */ static void -tunnel_send_destroy (struct MeshTunnel *t) +peer_info_add_path_to_origin (struct MeshPeerInfo *peer_info, + struct MeshPeerPath *path, int trusted) { - struct GNUNET_MESH_TunnelDestroy msg; - - msg.header.size = htons (sizeof (msg)); - msg.header.type = htons (GNUNET_MESSAGE_TYPE_MESH_TUNNEL_DESTROY); - GNUNET_PEER_resolve (t->id.oid, &msg.oid); - msg.tid = htonl (t->id.tid); - tunnel_send_multicast (t, &msg.header, GNUNET_NO); + path_invert (path); + peer_info_add_path (peer_info, path, trusted); } - /** - * Destroy the tunnel and free any allocated resources linked to it. - * - * @param t the tunnel to destroy + * Function called if the connection to the peer has been stalled for a while, + * possibly due to a missed ACK. Poll the peer about its ACK status. * - * @return GNUNET_OK on success + * @param cls Closure (cinfo). + * @param tc TaskContext. */ -static int -tunnel_destroy (struct MeshTunnel *t) +static void +tunnel_poll (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { - struct MeshClient *c; - struct MeshQueue *q; - struct MeshQueue *qn; - GNUNET_HashCode hash; - unsigned int i; - int r; - - if (NULL == t) - return GNUNET_OK; + struct MeshTunnelChildInfo *cinfo = cls; + struct GNUNET_MESH_Poll msg; + struct GNUNET_PeerIdentity id; + struct MeshTunnel *t; - r = GNUNET_OK; - c = t->owner; -#if MESH_DEBUG + cinfo->fc_poll = GNUNET_SCHEDULER_NO_TASK; + if (0 != (tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN)) { - struct GNUNET_PeerIdentity id; - - GNUNET_PEER_resolve (t->id.oid, &id); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "destroying tunnel %s [%x]\n", - GNUNET_i2s (&id), t->id.tid); - if (NULL != c) - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " by client %u\n", c->id); + return; } -#endif - GNUNET_CRYPTO_hash (&t->id, sizeof (struct MESH_TunnelID), &hash); - if (GNUNET_YES != GNUNET_CONTAINER_multihashmap_remove (tunnels, &hash, t)) - { - r = GNUNET_SYSERR; - } + t = cinfo->t; + msg.header.type = htons (GNUNET_MESSAGE_TYPE_MESH_POLL); + msg.header.size = htons (sizeof (msg)); + msg.tid = htonl (t->id.tid); + GNUNET_PEER_resolve (t->id.oid, &msg.oid); + msg.last_ack = htonl (cinfo->fwd_ack); + + GNUNET_PEER_resolve (cinfo->id, &id); + send_prebuilt_message (&msg.header, &id, cinfo->t); + cinfo->fc_poll_time = GNUNET_TIME_relative_min ( + MESH_MAX_POLL_TIME, + GNUNET_TIME_relative_multiply (cinfo->fc_poll_time, 2)); + cinfo->fc_poll = GNUNET_SCHEDULER_add_delayed (cinfo->fc_poll_time, + &tunnel_poll, cinfo); +} - GNUNET_CRYPTO_hash (&t->local_tid, sizeof (MESH_TunnelNumber), &hash); - if (NULL != c && - GNUNET_YES != - GNUNET_CONTAINER_multihashmap_remove (c->own_tunnels, &hash, t)) - { - r = GNUNET_SYSERR; - } - GNUNET_CRYPTO_hash (&t->local_tid_dest, sizeof (MESH_TunnelNumber), &hash); - for (i = 0; i < t->nclients; i++) + +/** + * Build a PeerPath from the paths returned from the DHT, reversing the paths + * to obtain a local peer -> destination path and interning the peer ids. + * + * @return Newly allocated and created path + */ +static struct MeshPeerPath * +path_build_from_dht (const struct GNUNET_PeerIdentity *get_path, + unsigned int get_path_length, + const struct GNUNET_PeerIdentity *put_path, + unsigned int put_path_length) +{ + struct MeshPeerPath *p; + GNUNET_PEER_Id id; + int i; + + p = path_new (1); + p->peers[0] = myid; + GNUNET_PEER_change_rc (myid, 1); + i = get_path_length; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " GET has %d hops.\n", i); + for (i--; i >= 0; i--) { - c = t->clients[i]; - if (GNUNET_YES != - GNUNET_CONTAINER_multihashmap_remove (c->incoming_tunnels, &hash, t)) + id = GNUNET_PEER_intern (&get_path[i]); + if (p->length > 0 && id == p->peers[p->length - 1]) { - r = GNUNET_SYSERR; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " Optimizing 1 hop out.\n"); + GNUNET_PEER_change_rc (id, -1); } - } - for (i = 0; i < t->nignore; i++) - { - c = t->ignore[i]; - if (GNUNET_YES != - GNUNET_CONTAINER_multihashmap_remove (c->ignore_tunnels, &hash, t)) + else { - r = GNUNET_SYSERR; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " Adding from GET: %s.\n", + GNUNET_i2s (&get_path[i])); + p->length++; + p->peers = GNUNET_realloc (p->peers, sizeof (GNUNET_PEER_Id) * p->length); + p->peers[p->length - 1] = id; } } - if (t->nclients > 0) + i = put_path_length; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " PUT has %d hops.\n", i); + for (i--; i >= 0; i--) { - if (GNUNET_YES != - GNUNET_CONTAINER_multihashmap_remove (incoming_tunnels, &hash, t)) + id = GNUNET_PEER_intern (&put_path[i]); + if (id == myid) { - r = GNUNET_SYSERR; + /* PUT path went through us, so discard the path up until now and start + * from here to get a much shorter (and loop-free) path. + */ + path_destroy (p); + p = path_new (0); + } + if (p->length > 0 && id == p->peers[p->length - 1]) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " Optimizing 1 hop out.\n"); + GNUNET_PEER_change_rc (id, -1); + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " Adding from PUT: %s.\n", + GNUNET_i2s (&put_path[i])); + p->length++; + p->peers = GNUNET_realloc (p->peers, sizeof (GNUNET_PEER_Id) * p->length); + p->peers[p->length - 1] = id; } - GNUNET_free (t->clients); - } - if (NULL != t->peers) - { - GNUNET_CONTAINER_multihashmap_iterate (t->peers, &peer_info_delete_tunnel, - t); - GNUNET_CONTAINER_multihashmap_destroy (t->peers); } - q = t->queue_head; - while (NULL != q) +#if MESH_DEBUG + if (get_path_length > 0) + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " (first of GET: %s)\n", + GNUNET_i2s (&get_path[0])); + if (put_path_length > 0) + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " (first of PUT: %s)\n", + GNUNET_i2s (&put_path[0])); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " In total: %d hops\n", + p->length); + for (i = 0; i < p->length; i++) { - if (NULL != q->data) - GNUNET_free (q->data); - qn = q->next; - GNUNET_free (q); - q = qn; - /* TODO cancel core transmit ready in case it was active */ + struct GNUNET_PeerIdentity peer_id; + + GNUNET_PEER_resolve (p->peers[i], &peer_id); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " %u: %s\n", p->peers[i], + GNUNET_i2s (&peer_id)); } - tree_destroy (t->tree); - if (NULL != t->dht_get_type) - GNUNET_DHT_get_stop (t->dht_get_type); - if (GNUNET_SCHEDULER_NO_TASK != t->timeout_task) - GNUNET_SCHEDULER_cancel (t->timeout_task); - if (GNUNET_SCHEDULER_NO_TASK != t->path_refresh_task) - GNUNET_SCHEDULER_cancel (t->path_refresh_task); - GNUNET_free (t); - return r; +#endif + return p; } /** - * Removes an explicit path from a tunnel, freeing all intermediate nodes - * that are no longer needed, as well as nodes of no longer reachable peers. - * The tunnel itself is also destoyed if results in a remote empty tunnel. + * Adds a path to the peer_infos of all the peers in the path * - * @param t Tunnel from which to remove the path. - * @param peer Short id of the peer which should be removed. + * @param p Path to process. + * @param confirmed Whether we know if the path works or not. + */ +static void +path_add_to_peers (struct MeshPeerPath *p, int confirmed) +{ + unsigned int i; + + /* TODO: invert and add */ + for (i = 0; i < p->length && p->peers[i] != myid; i++) /* skip'em */ ; + for (i++; i < p->length; i++) + { + struct MeshPeerInfo *aux; + struct MeshPeerPath *copy; + + aux = peer_info_get_short (p->peers[i]); + copy = path_duplicate (p); + copy->length = i + 1; + peer_info_add_path (aux, copy, GNUNET_NO); + } +} + + +/** + * Send keepalive packets for a peer + * + * @param cls Closure (tunnel for which to send the keepalive). + * @param tc Notification context. + * + * TODO: implement explicit multicast keepalive? + */ +static void +path_refresh (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc); + + +/** + * Search for a tunnel among the incoming tunnels + * + * @param tid the local id of the tunnel + * + * @return tunnel handler, NULL if doesn't exist + */ +static struct MeshTunnel * +tunnel_get_incoming (MESH_TunnelNumber tid) +{ + struct GNUNET_HashCode hash; + + GNUNET_assert (tid >= GNUNET_MESH_LOCAL_TUNNEL_ID_SERV); + GNUNET_CRYPTO_hash (&tid, sizeof (MESH_TunnelNumber), &hash); + return GNUNET_CONTAINER_multihashmap_get (incoming_tunnels, &hash); +} + + +/** + * Search for a tunnel among the tunnels for a client + * + * @param c the client whose tunnels to search in + * @param tid the local id of the tunnel + * + * @return tunnel handler, NULL if doesn't exist + */ +static struct MeshTunnel * +tunnel_get_by_local_id (struct MeshClient *c, MESH_TunnelNumber tid) +{ + if (tid >= GNUNET_MESH_LOCAL_TUNNEL_ID_SERV) + { + return tunnel_get_incoming (tid); + } + else + { + struct GNUNET_HashCode hash; + + GNUNET_CRYPTO_hash (&tid, sizeof (MESH_TunnelNumber), &hash); + return GNUNET_CONTAINER_multihashmap_get (c->own_tunnels, &hash); + } +} + + +/** + * Search for a tunnel by global ID using PEER_ID + * + * @param pi owner of the tunnel + * @param tid global tunnel number + * + * @return tunnel handler, NULL if doesn't exist + */ +static struct MeshTunnel * +tunnel_get_by_pi (GNUNET_PEER_Id pi, MESH_TunnelNumber tid) +{ + struct MESH_TunnelID id; + struct GNUNET_HashCode hash; + + id.oid = pi; + id.tid = tid; + + GNUNET_CRYPTO_hash (&id, sizeof (struct MESH_TunnelID), &hash); + return GNUNET_CONTAINER_multihashmap_get (tunnels, &hash); +} + + +/** + * Search for a tunnel by global ID using full PeerIdentities + * + * @param oid owner of the tunnel + * @param tid global tunnel number + * + * @return tunnel handler, NULL if doesn't exist + */ +static struct MeshTunnel * +tunnel_get (const struct GNUNET_PeerIdentity *oid, MESH_TunnelNumber tid) +{ + return tunnel_get_by_pi (GNUNET_PEER_search (oid), tid); +} + + +/** + * Delete an active client from the tunnel. + * + * @param t Tunnel. + * @param c Client. + */ +static void +tunnel_delete_active_client (struct MeshTunnel *t, const struct MeshClient *c) +{ + unsigned int i; + + for (i = 0; i < t->nclients; i++) + { + if (t->clients[i] == c) + { + t->clients[i] = t->clients[t->nclients - 1]; + t->clients_fc[i] = t->clients_fc[t->nclients - 1]; + GNUNET_array_grow (t->clients, t->nclients, t->nclients - 1); + t->nclients++; + GNUNET_array_grow (t->clients_fc, t->nclients, t->nclients - 1); + break; + } + } +} + + +/** + * Delete an ignored client from the tunnel. + * + * @param t Tunnel. + * @param c Client. + */ +static void +tunnel_delete_ignored_client (struct MeshTunnel *t, const struct MeshClient *c) +{ + unsigned int i; + + for (i = 0; i < t->nignore; i++) + { + if (t->ignore[i] == c) + { + t->ignore[i] = t->ignore[t->nignore - 1]; + GNUNET_array_grow (t->ignore, t->nignore, t->nignore - 1); + break; + } + } +} + + +/** + * Delete a client from the tunnel. It should be only done on + * client disconnection, otherwise use client_ignore_tunnel. + * + * @param t Tunnel. + * @param c Client. + */ +static void +tunnel_delete_client (struct MeshTunnel *t, const struct MeshClient *c) +{ + tunnel_delete_ignored_client (t, c); + tunnel_delete_active_client (t, c); +} + + +/** + * @brief Iterator to destroy MeshTunnelChildInfo of tunnel children. + * + * Destroys queue elements of all waiting transmissions and frees all memory + * used by the struct and its elements. + * + * @param cls Closure (tunnel info). + * @param key Hash of GNUNET_PEER_Id (unused). + * @param value MeshTunnelChildInfo of the child. + * + * @return always GNUNET_YES, to keep iterating + */ +static int +tunnel_destroy_child (void *cls, + const struct GNUNET_HashCode * key, + void *value) +{ + struct MeshTunnelChildInfo *cinfo = value; + struct MeshTunnel *t = cls; + struct MeshPeerQueue *q; + unsigned int c; + unsigned int i; + + for (c = 0; c < cinfo->send_buffer_n; c++) + { + i = (cinfo->send_buffer_start + c) % t->fwd_queue_max; + q = cinfo->send_buffer[i]; + cinfo->send_buffer[i] = NULL; + if (NULL != q) + queue_destroy (q, GNUNET_YES); + else + GNUNET_break (0); + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "%u %u\n", c, cinfo->send_buffer_n); + } + GNUNET_free_non_null (cinfo->send_buffer); + if (GNUNET_SCHEDULER_NO_TASK != cinfo->fc_poll) + { + GNUNET_SCHEDULER_cancel (cinfo->fc_poll); + cinfo->fc_poll = GNUNET_SCHEDULER_NO_TASK; + } + GNUNET_free (cinfo); + return GNUNET_YES; +} + + +/** + * Callback used to notify a client owner of a tunnel that a peer has + * disconnected, most likely because of a path change. + * + * @param cls Closure (tunnel this notification is about). + * @param peer_id Short ID of disconnected peer. + */ +void +tunnel_notify_client_peer_disconnected (void *cls, GNUNET_PEER_Id peer_id) +{ + struct MeshTunnel *t = cls; + struct MeshPeerInfo *peer; + struct MeshPathInfo *path_info; + + client_notify_peer_disconnected (t->owner, t, peer_id); + + peer = peer_info_get_short (peer_id); + path_info = GNUNET_malloc (sizeof (struct MeshPathInfo)); + path_info->peer = peer; + path_info->t = t; + peer->connect_task = GNUNET_SCHEDULER_add_now (&peer_info_connect_task, + path_info); +} + + +/** + * Add a peer to a tunnel, accomodating paths accordingly and initializing all + * needed rescources. + * If peer already exists, reevaluate shortest path and change if different. + * + * @param t Tunnel we want to add a new peer to + * @param peer PeerInfo of the peer being added + * + */ +static void +tunnel_add_peer (struct MeshTunnel *t, struct MeshPeerInfo *peer) +{ + struct GNUNET_PeerIdentity id; + struct MeshPeerPath *best_p; + struct MeshPeerPath *p; + unsigned int best_cost; + unsigned int cost; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "tunnel_add_peer\n"); + GNUNET_PEER_resolve (peer->id, &id); + if (GNUNET_NO == + GNUNET_CONTAINER_multihashmap_contains (t->peers, &id.hashPubKey)) + { + t->peers_total++; + GNUNET_array_append (peer->tunnels, peer->ntunnels, t); + GNUNET_assert (GNUNET_OK == + GNUNET_CONTAINER_multihashmap_put (t->peers, &id.hashPubKey, + peer, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_FAST)); + } + + if (NULL != (p = peer->path_head)) + { + best_p = p; + best_cost = tree_get_path_cost (t->tree, p); + while (NULL != p) + { + if ((cost = tree_get_path_cost (t->tree, p)) < best_cost) + { + best_cost = cost; + best_p = p; + } + p = p->next; + } + tree_add_path (t->tree, best_p, &tunnel_notify_client_peer_disconnected, t); + if (GNUNET_SCHEDULER_NO_TASK == t->path_refresh_task) + t->path_refresh_task = + GNUNET_SCHEDULER_add_delayed (refresh_path_time, &path_refresh, t); + } + else + { + /* Start a DHT get */ + peer_info_connect (peer, t); + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "tunnel_add_peer END\n"); +} + +/** + * Add a path to a tunnel which we don't own, just to remember the next hop. + * If destination node was already in the tunnel, the first hop information + * will be replaced with the new path. + * + * @param t Tunnel we want to add a new peer to + * @param p Path to add + * @param own_pos Position of local node in path. + * + */ +static void +tunnel_add_path (struct MeshTunnel *t, struct MeshPeerPath *p, + unsigned int own_pos) +{ + struct GNUNET_PeerIdentity id; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "tunnel_add_path\n"); + GNUNET_assert (0 != own_pos); + tree_add_path (t->tree, p, NULL, NULL); + if (own_pos < p->length - 1) + { + GNUNET_PEER_resolve (p->peers[own_pos + 1], &id); + tree_update_first_hops (t->tree, myid, &id); + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "tunnel_add_path END\n"); +} + +/** + * Add a client to a tunnel, initializing all needed data structures. + * + * @param t Tunnel to which add the client. + * @param c Client which to add to the tunnel. + */ +static void +tunnel_add_client (struct MeshTunnel *t, struct MeshClient *c) +{ + struct MeshTunnelClientInfo clinfo; + + GNUNET_array_append (t->clients, t->nclients, c); + clinfo.fwd_ack = t->fwd_pid + 1; + clinfo.bck_ack = t->nobuffer ? 1 : INITIAL_WINDOW_SIZE - 1; + clinfo.fwd_pid = t->fwd_pid; + clinfo.bck_pid = (uint32_t) -1; // Expected next: 0 + t->nclients--; + GNUNET_array_append (t->clients_fc, t->nclients, clinfo); +} + + +/** + * Notifies a tunnel that a connection has broken that affects at least + * some of its peers. Sends a notification towards the root of the tree. + * In case the peer is the owner of the tree, notifies the client that owns + * the tunnel and tries to reconnect. + * + * @param t Tunnel affected. + * @param p1 Peer that got disconnected from p2. + * @param p2 Peer that got disconnected from p1. + * + * @return Short ID of the peer disconnected (either p1 or p2). + * 0 if the tunnel remained unaffected. + */ +static GNUNET_PEER_Id +tunnel_notify_connection_broken (struct MeshTunnel *t, GNUNET_PEER_Id p1, + GNUNET_PEER_Id p2) +{ + GNUNET_PEER_Id pid; + + pid = + tree_notify_connection_broken (t->tree, p1, p2, + &tunnel_notify_client_peer_disconnected, + t); + if (myid != p1 && myid != p2) + { + return pid; + } + if (pid != myid) + { + if (tree_get_predecessor (t->tree) != 0) + { + /* We are the peer still connected, notify owner of the disconnection. */ + struct GNUNET_MESH_PathBroken msg; + struct GNUNET_PeerIdentity neighbor; + + msg.header.size = htons (sizeof (msg)); + msg.header.type = htons (GNUNET_MESSAGE_TYPE_MESH_PATH_BROKEN); + GNUNET_PEER_resolve (t->id.oid, &msg.oid); + msg.tid = htonl (t->id.tid); + msg.peer1 = my_full_id; + GNUNET_PEER_resolve (pid, &msg.peer2); + GNUNET_PEER_resolve (tree_get_predecessor (t->tree), &neighbor); + send_prebuilt_message (&msg.header, &neighbor, t); + } + } + return pid; +} + + +/** + * Send a multicast packet to a neighbor. + * + * @param cls Closure (Info about the multicast packet) + * @param neighbor_id Short ID of the neighbor to send the packet to. + */ +static void +tunnel_send_multicast_iterator (void *cls, GNUNET_PEER_Id neighbor_id) +{ + struct MeshData *mdata = cls; + struct MeshTransmissionDescriptor *info; + struct GNUNET_PeerIdentity neighbor; + struct GNUNET_MessageHeader *msg; + + info = GNUNET_malloc (sizeof (struct MeshTransmissionDescriptor)); + + info->mesh_data = mdata; + (mdata->reference_counter) ++; + info->destination = neighbor_id; + GNUNET_PEER_resolve (neighbor_id, &neighbor); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " sending to %s...\n", + GNUNET_i2s (&neighbor)); + info->peer = peer_info_get (&neighbor); + GNUNET_assert (NULL != info->peer); + msg = (struct GNUNET_MessageHeader *) mdata->data; + queue_add(info, + ntohs (msg->type), + info->mesh_data->data_len, + info->peer, + mdata->t); +} + + +/** + * Queue a message in a tunnel in multicast, sending a copy to each child node + * down the local one in the tunnel tree. + * + * @param t Tunnel in which to send the data. + * @param msg Message to be sent. + */ +static void +tunnel_send_multicast (struct MeshTunnel *t, + const struct GNUNET_MessageHeader *msg) +{ + struct MeshData *mdata; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " sending a multicast packet...\n"); + + mdata = GNUNET_malloc (sizeof (struct MeshData)); + mdata->data_len = ntohs (msg->size); + mdata->t = t; + mdata->data = GNUNET_malloc (mdata->data_len); + memcpy (mdata->data, msg, mdata->data_len); + if (ntohs (msg->type) == GNUNET_MESSAGE_TYPE_MESH_MULTICAST) + { + struct GNUNET_MESH_Multicast *mcast; + + mcast = (struct GNUNET_MESH_Multicast *) mdata->data; + if (t->fwd_queue_n >= t->fwd_queue_max) + { + GNUNET_break (0); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, " queue full!\n"); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + " message from %s!\n", + GNUNET_i2s(&mcast->oid)); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + " message at %s!\n", + GNUNET_i2s(&my_full_id)); + GNUNET_free (mdata->data); + GNUNET_free (mdata); + return; + } + t->fwd_queue_n++; + mcast->ttl = htonl (ntohl (mcast->ttl) - 1); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " data packet, ttl: %u\n", + ntohl (mcast->ttl)); + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " not a data packet, no ttl\n"); + } + + tree_iterate_children (t->tree, &tunnel_send_multicast_iterator, mdata); + if (mdata->reference_counter == 0) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " no one to send data to\n"); + GNUNET_free (mdata->data); + GNUNET_free (mdata); + if (ntohs (msg->type) == GNUNET_MESSAGE_TYPE_MESH_MULTICAST) + t->fwd_queue_n--; + } + else + { + mdata->total_out = mdata->reference_counter; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " sending a multicast packet done\n"); + return; +} + + +/** + * Increase the SKIP value of all peers that + * have not received a unicast message. + * + * @param cls Closure (ID of the peer that HAS received the message). + * @param key ID of the neighbor. + * @param value Information about the neighbor. + * + * @return GNUNET_YES to keep iterating. + */ +static int +tunnel_add_skip (void *cls, + const struct GNUNET_HashCode * key, + void *value) +{ + struct GNUNET_PeerIdentity *neighbor = cls; + struct MeshTunnelChildInfo *cinfo = value; + + /* TODO compare only pointers? key == neighbor? */ + if (0 == memcmp (&neighbor->hashPubKey, key, sizeof (struct GNUNET_HashCode))) + { + return GNUNET_YES; + } + cinfo->skip++; + return GNUNET_YES; +} + + +/** + * @brief Get neighbor's Flow Control information. + * + * Retrieves the MeshTunnelChildInfo containing Flow Control data about a direct + * descendant of the local node in a certain tunnel. + * If the info is not yet there (recently created path), creates the data struct + * and inserts it into the tunnel info, initialized to the current tunnel ACK + * values. + * + * @param t Tunnel related. + * @param peer Neighbor whose Flow Control info is needed. + * + * @return Neighbor's Flow Control info. + */ +static struct MeshTunnelChildInfo * +tunnel_get_neighbor_fc (struct MeshTunnel *t, + const struct GNUNET_PeerIdentity *peer) +{ + struct MeshTunnelChildInfo *cinfo; + + if (NULL == t->children_fc) + return NULL; + + cinfo = GNUNET_CONTAINER_multihashmap_get (t->children_fc, + &peer->hashPubKey); + if (NULL == cinfo) + { + uint32_t delta; + + cinfo = GNUNET_malloc (sizeof (struct MeshTunnelChildInfo)); + cinfo->id = GNUNET_PEER_intern (peer); + cinfo->skip = t->fwd_pid; + cinfo->t = t; + + delta = t->nobuffer ? 1 : INITIAL_WINDOW_SIZE; + cinfo->fwd_ack = t->fwd_pid + delta; + cinfo->bck_ack = delta; + cinfo->bck_pid = -1; + + cinfo->fc_poll = GNUNET_SCHEDULER_NO_TASK; + cinfo->fc_poll_time = GNUNET_TIME_UNIT_SECONDS; + + cinfo->send_buffer = + GNUNET_malloc (sizeof(struct MeshPeerQueue *) * t->fwd_queue_max); + + GNUNET_assert (GNUNET_OK == + GNUNET_CONTAINER_multihashmap_put (t->children_fc, + &peer->hashPubKey, + cinfo, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_FAST)); + } + return cinfo; +} + + +/** + * Get the Flow Control info of a client. + * + * @param t Tunnel on which to look. + * @param c Client whose ACK to get. + * + * @return ACK value. + */ +static struct MeshTunnelClientInfo * +tunnel_get_client_fc (struct MeshTunnel *t, + struct MeshClient *c) +{ + unsigned int i; + + for (i = 0; i < t->nclients; i++) + { + if (t->clients[i] != c) + continue; + return &t->clients_fc[i]; + } + GNUNET_assert (0); + return NULL; // avoid compiler / coverity complaints +} + + +/** + * Iterator to get the appropiate ACK value from all children nodes. + * + * @param cls Closue (tunnel). + * @param id Id of the child node. + */ +static void +tunnel_get_child_fwd_ack (void *cls, + GNUNET_PEER_Id id) +{ + struct GNUNET_PeerIdentity peer_id; + struct MeshTunnelChildInfo *cinfo; + struct MeshTunnelChildIteratorContext *ctx = cls; + struct MeshTunnel *t = ctx->t; + uint32_t ack; + + GNUNET_PEER_resolve (id, &peer_id); + cinfo = tunnel_get_neighbor_fc (t, &peer_id); + ack = cinfo->fwd_ack; + + ctx->nchildren++; + if (GNUNET_NO == ctx->init) + { + ctx->max_child_ack = ack; + ctx->init = GNUNET_YES; + } + + if (GNUNET_YES == t->speed_min) + { + ctx->max_child_ack = ctx->max_child_ack > ack ? ack : ctx->max_child_ack; + } + else + { + ctx->max_child_ack = ctx->max_child_ack > ack ? ctx->max_child_ack : ack; + } + +} + + +/** + * Get the maximum PID allowed to transmit to any + * tunnel child of the local peer, depending on the tunnel + * buffering/speed settings. + * + * @param t Tunnel. + * + * @return Maximum PID allowed (uint32 MAX), -1LL if node has no children. + */ +static int64_t +tunnel_get_children_fwd_ack (struct MeshTunnel *t) +{ + struct MeshTunnelChildIteratorContext ctx; + ctx.t = t; + ctx.max_child_ack = 0; + ctx.nchildren = 0; + ctx.init = GNUNET_NO; + tree_iterate_children (t->tree, tunnel_get_child_fwd_ack, &ctx); + + if (0 == ctx.nchildren) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " tunnel has no children, no FWD ACK\n"); + return -1LL; + } + + if (GNUNET_YES == t->nobuffer && GMC_is_pid_bigger(ctx.max_child_ack, t->fwd_pid)) + ctx.max_child_ack = t->fwd_pid + 1; // Might overflow, it's ok. + + return (int64_t) ctx.max_child_ack; +} + + +/** + * Set the FWD ACK value of a client in a particular tunnel. + * + * @param t Tunnel affected. + * @param c Client whose ACK to set. + * @param ack ACK value. + */ +static void +tunnel_set_client_fwd_ack (struct MeshTunnel *t, + struct MeshClient *c, + uint32_t ack) +{ + unsigned int i; + + for (i = 0; i < t->nclients; i++) + { + if (t->clients[i] != c) + continue; + t->clients_fc[i].fwd_ack = ack; + return; + } + GNUNET_break (0); +} + + +/** + * Get the highest ACK value of all clients in a particular tunnel, + * according to the buffering/speed settings. + * + * @param t Tunnel on which to look. + * + * @return Corresponding ACK value (max uint32_t). + * If no clients are suscribed, -1LL. + */ +static int64_t +tunnel_get_clients_fwd_ack (struct MeshTunnel *t) +{ + unsigned int i; + int64_t ack; + + if (0 == t->nclients) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " tunnel has no clients, no FWD ACK\n"); + return -1LL; + } + + for (ack = -1LL, i = 0; i < t->nclients; i++) + { + if (-1LL == ack || + (GNUNET_YES == t->speed_min && + GNUNET_YES == GMC_is_pid_bigger (ack, t->clients_fc[i].fwd_ack)) || + (GNUNET_NO == t->speed_min && + GNUNET_YES == GMC_is_pid_bigger (t->clients_fc[i].fwd_ack, ack))) + { + ack = t->clients_fc[i].fwd_ack; + } + } + + if (GNUNET_YES == t->nobuffer && GMC_is_pid_bigger(ack, t->fwd_pid)) + ack = (uint32_t) t->fwd_pid + 1; // Might overflow, it's ok. + + return (uint32_t) ack; +} + + +/** + * Get the current fwd ack value for a tunnel, taking in account the tunnel + * mode and the status of all children nodes. + * + * @param t Tunnel. + * + * @return Maximum PID allowed. + */ +static uint32_t +tunnel_get_fwd_ack (struct MeshTunnel *t) +{ + uint32_t ack; + uint32_t count; + uint32_t buffer_free; + int64_t child_ack; + int64_t client_ack; + + count = t->fwd_pid - t->skip; + buffer_free = t->fwd_queue_max - t->fwd_queue_n; + child_ack = tunnel_get_children_fwd_ack (t); + client_ack = tunnel_get_clients_fwd_ack (t); + if (GNUNET_YES == t->nobuffer) + { + ack = count; + if (-1LL == child_ack) + child_ack = client_ack; + if (-1LL == child_ack) + { + GNUNET_break (0); + client_ack = child_ack = ack; + } + } + else + { + ack = count + buffer_free; // Overflow? OK! + } + if (-1LL == child_ack) + { + // Node has no children, child_ack AND core buffer are irrelevant. + if (-1LL == client_ack) // No children AND no clients? Not good! + { + GNUNET_STATISTICS_update (stats, "# mesh acks with no target", + 1, GNUNET_NO); + + } + return (uint32_t) client_ack; + } + if (-1LL == client_ack) + { + client_ack = ack; + } + if (GNUNET_YES == t->speed_min) + { + ack = GMC_min_pid ((uint32_t) child_ack, ack); + ack = GMC_min_pid ((uint32_t) client_ack, ack); + } + else + { + ack = GMC_max_pid ((uint32_t) child_ack, ack); + ack = GMC_max_pid ((uint32_t) client_ack, ack); + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "c %u, bf %u, ch %lld, cl %lld, ACK: %u\n", + count, buffer_free, child_ack, client_ack, ack); + return ack; +} + + +/** + * Build a local ACK message and send it to a local client. + * + * @param t Tunnel on which to send the ACK. + * @param c Client to whom send the ACK. + * @param ack Value of the ACK. + */ +static void +send_local_ack (struct MeshTunnel *t, struct MeshClient *c, uint32_t ack) +{ + struct GNUNET_MESH_LocalAck msg; + + msg.header.size = htons (sizeof (msg)); + msg.header.type = htons (GNUNET_MESSAGE_TYPE_MESH_LOCAL_ACK); + msg.tunnel_id = htonl (t->owner == c ? t->local_tid : t->local_tid_dest); + msg.max_pid = htonl (ack); + GNUNET_SERVER_notification_context_unicast(nc, + c->handle, + &msg.header, + GNUNET_NO); +} + +/** + * Build an ACK message and queue it to send to the given peer. + * + * @param t Tunnel on which to send the ACK. + * @param peer Peer to whom send the ACK. + * @param ack Value of the ACK. + */ +static void +send_ack (struct MeshTunnel *t, struct GNUNET_PeerIdentity *peer, uint32_t ack) +{ + struct GNUNET_MESH_ACK msg; + + GNUNET_PEER_resolve (t->id.oid, &msg.oid); + msg.header.size = htons (sizeof (msg)); + msg.header.type = htons (GNUNET_MESSAGE_TYPE_MESH_ACK); + msg.pid = htonl (ack); + msg.tid = htonl (t->id.tid); + + send_prebuilt_message (&msg.header, peer, t); +} + + +/** + * Notify a the owner of a tunnel about how many more + * payload packages will we accept on a given tunnel. + * + * @param t Tunnel on which to send the ACK. + */ +static void +tunnel_send_client_fwd_ack (struct MeshTunnel *t) +{ + uint32_t ack; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Sending client FWD ACK on tunnel %X\n", + t->local_tid); + + ack = tunnel_get_fwd_ack (t); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " ack %u\n", ack); + if (t->last_fwd_ack == ack) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " same as last, not sending!\n"); + return; + } + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " sending!\n"); + t->last_fwd_ack = ack; + send_local_ack (t, t->owner, ack); +} + + +/** + * Send an ACK informing the predecessor about the available buffer space. + * In case there is no predecessor, inform the owning client. + * If buffering is off, send only on behalf of children or self if endpoint. + * If buffering is on, send when sent to children and buffer space is free. + * Note that although the name is fwd_ack, the FWD mean forward *traffic*, + * the ACK itself goes "back" (towards root). + * + * @param t Tunnel on which to send the ACK. + * @param type Type of message that triggered the ACK transmission. + */ +static void +tunnel_send_fwd_ack (struct MeshTunnel *t, uint16_t type) +{ + struct GNUNET_PeerIdentity id; + uint32_t ack; + + if (NULL != t->owner) + { + tunnel_send_client_fwd_ack (t); + return; + } + /* Is it after unicast / multicast retransmission? */ + switch (type) + { + case GNUNET_MESSAGE_TYPE_MESH_UNICAST: + case GNUNET_MESSAGE_TYPE_MESH_MULTICAST: + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "ACK due to FWD DATA retransmission\n"); + if (GNUNET_YES == t->nobuffer) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Not sending ACK, nobuffer\n"); + return; + } + break; + case GNUNET_MESSAGE_TYPE_MESH_ACK: + case GNUNET_MESSAGE_TYPE_MESH_LOCAL_ACK: + break; + case GNUNET_MESSAGE_TYPE_MESH_POLL: + t->force_ack = GNUNET_YES; + break; + default: + GNUNET_break (0); + } + + /* Check if we need to transmit the ACK */ + if (t->fwd_queue_max > t->fwd_queue_n * 4 && + GMC_is_pid_bigger(t->last_fwd_ack, t->fwd_pid) && + GNUNET_NO == t->force_ack) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Not sending ACK, buffer free\n"); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " t->qmax: %u, t->qn: %u\n", + t->fwd_queue_max, t->fwd_queue_n); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " t->pid: %u, t->ack: %u\n", + t->fwd_pid, t->last_fwd_ack); + return; + } + + /* Ok, ACK might be necessary, what PID to ACK? */ + ack = tunnel_get_fwd_ack (t); + + /* If speed_min and not all children have ack'd, dont send yet */ + if (ack == t->last_fwd_ack && GNUNET_NO == t->force_ack) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Not sending FWD ACK, not ready\n"); + return; + } + + t->last_fwd_ack = ack; + GNUNET_PEER_resolve (tree_get_predecessor (t->tree), &id); + send_ack (t, &id, ack); + debug_fwd_ack++; + t->force_ack = GNUNET_NO; +} + + +/** + * Iterator to send a child node a BCK ACK to allow him to send more + * to_origin data. + * + * @param cls Closure (tunnel). + * @param id Id of the child node. + */ +static void +tunnel_send_child_bck_ack (void *cls, + GNUNET_PEER_Id id) +{ + struct MeshTunnel *t = cls; + struct MeshTunnelChildInfo *cinfo; + struct GNUNET_PeerIdentity peer; + uint32_t ack; + + GNUNET_PEER_resolve (id, &peer); + cinfo = tunnel_get_neighbor_fc (t, &peer); + ack = cinfo->bck_pid + t->bck_queue_max - t->bck_queue_n; + + if (cinfo->bck_ack == ack && GNUNET_NO == t->force_ack) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " Not sending ACK, not needed\n"); + return; + } + cinfo->bck_ack = ack; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " Sending BCK ACK %u (last sent: %u)\n", + ack, cinfo->bck_ack); + send_ack (t, &peer, ack); +} + + +/** + * @brief Send BCK ACKs to clients to allow them more to_origin traffic + * + * Iterates over all clients and sends BCK ACKs to the ones that need it. + * + * FIXME fc: what happens if we have 2 clients but q_size is 1? + * - implement a size 1 buffer in each client_fc AND children_fc + * to hold at least 1 message per "child". + * problem: violates no buffer policy + * - ack 0 and make "children" poll for transmission slots + * problem: big overhead, extra latency even in low traffic + * settings + * + * @param t Tunnel on which to send the BCK ACKs. + */ +static void +tunnel_send_clients_bck_ack (struct MeshTunnel *t) +{ + unsigned int i; + unsigned int tunnel_delta; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " Sending BCK ACK to clients\n"); + + tunnel_delta = t->bck_queue_max - t->bck_queue_n; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " tunnel delta: %u\n", tunnel_delta); + + /* Find client whom to allow to send to origin (with lowest buffer space) */ + for (i = 0; i < t->nclients; i++) + { + struct MeshTunnelClientInfo *clinfo; + unsigned int delta; + + clinfo = &t->clients_fc[i]; + delta = clinfo->bck_ack - clinfo->bck_pid; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " client %u delta: %u\n", + t->clients[i]->id, delta); + + if ((GNUNET_NO == t->nobuffer && tunnel_delta > delta) || + (GNUNET_YES == t->nobuffer && 0 == delta)) + { + uint32_t ack; + + ack = clinfo->bck_pid; + ack += t->nobuffer ? 1 : tunnel_delta; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " sending ack to client %u: %u\n", + t->clients[i]->id, ack); + send_local_ack (t, t->clients[i], ack); + clinfo->bck_ack = ack; + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " not sending ack to client %u (td %u, d %u)\n", + t->clients[i]->id, tunnel_delta, delta); + } + } +} + + +/** + * Send an ACK informing the children nodes and destination clients about + * the available buffer space. + * If buffering is off, send only on behalf of root (can be self). + * If buffering is on, send when sent to predecessor and buffer space is free. + * Note that although the name is bck_ack, the BCK mean backwards *traffic*, + * the ACK itself goes "forward" (towards children/clients). + * + * @param t Tunnel on which to send the ACK. + * @param type Type of message that triggered the ACK transmission. + */ +static void +tunnel_send_bck_ack (struct MeshTunnel *t, uint16_t type) +{ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Sending BCK ACK on tunnel %u [%u] due to %s\n", + t->id.oid, t->id.tid, GNUNET_MESH_DEBUG_M2S(type)); + /* Is it after data to_origin retransmission? */ + switch (type) + { + case GNUNET_MESSAGE_TYPE_MESH_TO_ORIGIN: + if (GNUNET_YES == t->nobuffer) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " Not sending ACK, nobuffer\n"); + return; + } + break; + case GNUNET_MESSAGE_TYPE_MESH_ACK: + case GNUNET_MESSAGE_TYPE_MESH_LOCAL_ACK: + break; + case GNUNET_MESSAGE_TYPE_MESH_POLL: + t->force_ack = GNUNET_YES; + break; + default: + GNUNET_break (0); + } + + tunnel_send_clients_bck_ack (t); + tree_iterate_children (t->tree, &tunnel_send_child_bck_ack, t); + t->force_ack = GNUNET_NO; +} + + +/** + * @brief Re-initiate traffic to this peer if necessary. + * + * Check if there is traffic queued towards this peer + * and the core transmit handle is NULL (traffic was stalled). + * If so, call core tmt rdy. + * + * @param cls Closure (unused) + * @param peer_id Short ID of peer to which initiate traffic. + */ +static void +peer_unlock_queue(void *cls, GNUNET_PEER_Id peer_id) +{ + struct MeshPeerInfo *peer; + struct GNUNET_PeerIdentity id; + struct MeshPeerQueue *q; + size_t size; + + peer = peer_info_get_short(peer_id); + if (NULL != peer->core_transmit) + return; + + q = queue_get_next(peer); + if (NULL == q) + { + /* Might br multicast traffic already sent to this particular peer but + * not to other children in this tunnel. + * This way t->queue_n would be > 0 but the queue of this particular peer + * would be empty. + */ + return; + } + size = q->size; + GNUNET_PEER_resolve (peer->id, &id); + peer->core_transmit = + GNUNET_CORE_notify_transmit_ready(core_handle, + 0, + 0, + GNUNET_TIME_UNIT_FOREVER_REL, + &id, + size, + &queue_send, + peer); + return; +} + + +/** + * @brief Allow transmission of FWD traffic on this tunnel + * + * Check if there is traffic queued towards any children + * and the core transmit handle is NULL, and if so, call core tmt rdy. + * + * @param t Tunnel on which to unlock FWD traffic. + */ +static void +tunnel_unlock_fwd_queues (struct MeshTunnel *t) +{ + if (0 == t->fwd_queue_n) + return; + + tree_iterate_children (t->tree, &peer_unlock_queue, NULL); +} + + +/** + * @brief Allow transmission of BCK traffic on this tunnel + * + * Check if there is traffic queued towards the root of the tree + * and the core transmit handle is NULL, and if so, call core tmt rdy. + * + * @param t Tunnel on which to unlock BCK traffic. + */ +static void +tunnel_unlock_bck_queue (struct MeshTunnel *t) +{ + if (0 == t->bck_queue_n) + return; + + peer_unlock_queue(NULL, tree_get_predecessor(t->tree)); +} + + +/** + * Send a message to all peers in this tunnel that the tunnel is no longer + * valid. + * + * @param t The tunnel whose peers to notify. + * @param parent ID of the parent, in case the tree is already destroyed. + */ +static void +tunnel_send_destroy (struct MeshTunnel *t, GNUNET_PEER_Id parent) +{ + struct GNUNET_MESH_TunnelDestroy msg; + struct GNUNET_PeerIdentity id; + + msg.header.size = htons (sizeof (msg)); + msg.header.type = htons (GNUNET_MESSAGE_TYPE_MESH_TUNNEL_DESTROY); + GNUNET_PEER_resolve (t->id.oid, &msg.oid); + msg.tid = htonl (t->id.tid); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " sending tunnel destroy for tunnel: %s [%X]\n", + GNUNET_i2s (&msg.oid), t->id.tid); + if (tree_count_children(t->tree) > 0) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " sending multicast to children\n"); + tunnel_send_multicast (t, &msg.header); + } + if (0 == parent) + parent = tree_get_predecessor (t->tree); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " parent: %u\n", parent); + if (0 == parent) + return; + + GNUNET_PEER_resolve (parent, &id); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " sending back to %s\n", + GNUNET_i2s (&id)); + send_prebuilt_message (&msg.header, &id, t); +} + + +/** + * Cancel all transmissions towards a neighbor that belong to a certain tunnel. + * + * @param cls Closure (Tunnel which to cancel). + * @param neighbor_id Short ID of the neighbor to whom cancel the transmissions. + */ +static void +tunnel_cancel_queues (void *cls, GNUNET_PEER_Id neighbor_id) +{ + struct MeshTunnel *t = cls; + struct MeshPeerInfo *peer_info; + struct MeshPeerQueue *pq; + struct MeshPeerQueue *next; + + peer_info = peer_info_get_short (neighbor_id); + for (pq = peer_info->queue_head; NULL != pq; pq = next) + { + next = pq->next; + if (pq->tunnel == t) + { + if (GNUNET_MESSAGE_TYPE_MESH_MULTICAST == pq->type || + GNUNET_MESSAGE_TYPE_MESH_UNICAST == pq->type || + GNUNET_MESSAGE_TYPE_MESH_TO_ORIGIN == pq->type) + { + // Should have been removed on destroy children + GNUNET_break (0); + } + queue_destroy (pq, GNUNET_YES); + } + } + if (NULL == peer_info->queue_head && NULL != peer_info->core_transmit) + { + GNUNET_CORE_notify_transmit_ready_cancel(peer_info->core_transmit); + peer_info->core_transmit = NULL; + } +} + +/** + * Destroy the tunnel and free any allocated resources linked to it. + * + * @param t the tunnel to destroy + * + * @return GNUNET_OK on success + */ +static int +tunnel_destroy (struct MeshTunnel *t) +{ + struct MeshClient *c; + struct GNUNET_HashCode hash; + unsigned int i; + int r; + + if (NULL == t) + return GNUNET_OK; + + r = GNUNET_OK; + c = t->owner; +#if MESH_DEBUG + { + struct GNUNET_PeerIdentity id; + + GNUNET_PEER_resolve (t->id.oid, &id); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "destroying tunnel %s [%x]\n", + GNUNET_i2s (&id), t->id.tid); + if (NULL != c) + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " by client %u\n", c->id); + } +#endif + + GNUNET_CRYPTO_hash (&t->id, sizeof (struct MESH_TunnelID), &hash); + if (GNUNET_YES != GNUNET_CONTAINER_multihashmap_remove (tunnels, &hash, t)) + { + GNUNET_break (0); + r = GNUNET_SYSERR; + } + + if (NULL != c) + { + GNUNET_CRYPTO_hash (&t->local_tid, sizeof (MESH_TunnelNumber), &hash); + if (GNUNET_YES != + GNUNET_CONTAINER_multihashmap_remove (c->own_tunnels, &hash, t)) + { + GNUNET_break (0); + r = GNUNET_SYSERR; + } + } + + GNUNET_CRYPTO_hash (&t->local_tid_dest, sizeof (MESH_TunnelNumber), &hash); + for (i = 0; i < t->nclients; i++) + { + c = t->clients[i]; + if (GNUNET_YES != + GNUNET_CONTAINER_multihashmap_remove (c->incoming_tunnels, &hash, t)) + { + GNUNET_break (0); + r = GNUNET_SYSERR; + } + } + for (i = 0; i < t->nignore; i++) + { + c = t->ignore[i]; + if (GNUNET_YES != + GNUNET_CONTAINER_multihashmap_remove (c->ignore_tunnels, &hash, t)) + { + GNUNET_break (0); + r = GNUNET_SYSERR; + } + } + + (void) GNUNET_CONTAINER_multihashmap_remove (incoming_tunnels, &hash, t); + GNUNET_free_non_null (t->clients); + GNUNET_free_non_null (t->ignore); + GNUNET_free_non_null (t->clients_fc); + + if (NULL != t->peers) + { + GNUNET_CONTAINER_multihashmap_iterate (t->peers, &peer_info_delete_tunnel, + t); + GNUNET_CONTAINER_multihashmap_destroy (t->peers); + } + + GNUNET_CONTAINER_multihashmap_iterate (t->children_fc, + &tunnel_destroy_child, + t); + GNUNET_CONTAINER_multihashmap_destroy (t->children_fc); + t->children_fc = NULL; + + tree_iterate_children (t->tree, &tunnel_cancel_queues, t); + tree_destroy (t->tree); + + if (NULL != t->regex_search) + GNUNET_REGEX_search_cancel (t->regex_search->search_handle); + if (NULL != t->dht_get_type) + GNUNET_DHT_get_stop (t->dht_get_type); + if (GNUNET_SCHEDULER_NO_TASK != t->timeout_task) + GNUNET_SCHEDULER_cancel (t->timeout_task); + if (GNUNET_SCHEDULER_NO_TASK != t->path_refresh_task) + GNUNET_SCHEDULER_cancel (t->path_refresh_task); + + n_tunnels--; + GNUNET_STATISTICS_update (stats, "# tunnels", -1, GNUNET_NO); + GNUNET_free (t); + return r; +} + +#define TUNNEL_DESTROY_EMPTY_TIME GNUNET_TIME_UNIT_MILLISECONDS + +/** + * Tunnel is empty: destroy it. + * + * @param cls Closure (Tunnel). + * @param tc TaskContext. + */ +static void +tunnel_destroy_empty_delayed (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct MeshTunnel *t = cls; + + t->delayed_destroy = GNUNET_SCHEDULER_NO_TASK; + if (0 != (tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN)) + return; + + if (0 != t->nclients || + 0 != tree_count_children (t->tree)) + return; + + #if MESH_DEBUG + { + struct GNUNET_PeerIdentity id; + + GNUNET_PEER_resolve (t->id.oid, &id); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "executing destruction of empty tunnel %s [%X]\n", + GNUNET_i2s (&id), t->id.tid); + } + #endif + + tunnel_send_destroy (t, 0); + if (0 == t->pending_messages) + tunnel_destroy (t); + else + t->destroy = GNUNET_YES; +} + + +/** + * Schedule tunnel destruction if is empty and no new traffic comes in a time. + * + * @param t Tunnel to destroy if empty. + */ +static void +tunnel_destroy_empty (struct MeshTunnel *t) +{ + if (GNUNET_SCHEDULER_NO_TASK != t->delayed_destroy || + 0 != t->nclients || + 0 != tree_count_children (t->tree)) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "%u %u %u\n", + t->delayed_destroy, t->nclients, tree_count_children(t->tree)); + return; + } + + #if MESH_DEBUG + { + struct GNUNET_PeerIdentity id; + + GNUNET_PEER_resolve (t->id.oid, &id); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "scheduling destruction of empty tunnel %s [%X]\n", + GNUNET_i2s (&id), t->id.tid); + } + #endif + + t->delayed_destroy = + GNUNET_SCHEDULER_add_delayed (TUNNEL_DESTROY_EMPTY_TIME, + &tunnel_destroy_empty_delayed, + t); +} + + +/** + * Create a new tunnel + * + * @param owner Who is the owner of the tunnel (short ID). + * @param tid Tunnel Number of the tunnel. + * @param client Clients that owns the tunnel, NULL for foreign tunnels. + * @param local Tunnel Number for the tunnel, for the client point of view. + * + * @return A new initialized tunnel. NULL on error. + */ +static struct MeshTunnel * +tunnel_new (GNUNET_PEER_Id owner, + MESH_TunnelNumber tid, + struct MeshClient *client, + MESH_TunnelNumber local) +{ + struct MeshTunnel *t; + struct GNUNET_HashCode hash; + + if (n_tunnels >= max_tunnels && NULL == client) + return NULL; + + t = GNUNET_malloc (sizeof (struct MeshTunnel)); + t->id.oid = owner; + t->id.tid = tid; + t->fwd_queue_max = (max_msgs_queue / max_tunnels) + 1; + t->bck_queue_max = t->fwd_queue_max; + t->tree = tree_new (owner); + t->owner = client; + t->fwd_pid = (uint32_t) -1; // Next (expected) = 0 + t->bck_pid = (uint32_t) -1; // Next (expected) = 0 + t->bck_ack = INITIAL_WINDOW_SIZE - 1; + t->last_fwd_ack = INITIAL_WINDOW_SIZE - 1; + t->local_tid = local; + t->children_fc = GNUNET_CONTAINER_multihashmap_create (8, GNUNET_NO); + n_tunnels++; + GNUNET_STATISTICS_update (stats, "# tunnels", 1, GNUNET_NO); + + GNUNET_CRYPTO_hash (&t->id, sizeof (struct MESH_TunnelID), &hash); + if (GNUNET_OK != + GNUNET_CONTAINER_multihashmap_put (tunnels, &hash, t, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY)) + { + GNUNET_break (0); + tunnel_destroy (t); + if (NULL != client) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client->handle, GNUNET_SYSERR); + } + return NULL; + } + + if (NULL != client) + { + GNUNET_CRYPTO_hash (&t->local_tid, sizeof (MESH_TunnelNumber), &hash); + if (GNUNET_OK != + GNUNET_CONTAINER_multihashmap_put (client->own_tunnels, &hash, t, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY)) + { + tunnel_destroy (t); + GNUNET_break (0); + GNUNET_SERVER_receive_done (client->handle, GNUNET_SYSERR); + return NULL; + } + } + + return t; +} + +/** + * Callback when removing children from a tunnel tree. Notify owner. + * + * @param cls Closure (tunnel). + * @param peer_id Short ID of the peer deleted. + */ +void +tunnel_child_removed (void *cls, GNUNET_PEER_Id peer_id) +{ + struct MeshTunnel *t = cls; + + client_notify_peer_disconnected (t->owner, t, peer_id); +} + +/** + * Removes an explicit path from a tunnel, freeing all intermediate nodes + * that are no longer needed, as well as nodes of no longer reachable peers. + * The tunnel itself is also destoyed if results in a remote empty tunnel. + * + * @param t Tunnel from which to remove the path. + * @param peer Short id of the peer which should be removed. */ static void tunnel_delete_peer (struct MeshTunnel *t, GNUNET_PEER_Id peer) { - if (GNUNET_NO == tree_del_peer (t->tree, peer, NULL, NULL)) + int r; + + r = tree_del_peer (t->tree, peer, &tunnel_child_removed, t); + if (GNUNET_NO == r) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Tunnel %u [%u] has no more nodes\n", + t->id.oid, t->id.tid); + } +} + + +/** + * tunnel_destroy_iterator: iterator for deleting each tunnel that belongs to a + * client when the client disconnects. If the client is not the owner, the + * owner will get notified if no more clients are in the tunnel and the client + * get removed from the tunnel's list. + * + * @param cls closure (client that is disconnecting) + * @param key the hash of the local tunnel id (used to access the hashmap) + * @param value the value stored at the key (tunnel to destroy) + * + * @return GNUNET_OK, keep iterating. + */ +static int +tunnel_destroy_iterator (void *cls, + const struct GNUNET_HashCode * key, + void *value) +{ + struct MeshTunnel *t = value; + struct MeshClient *c = cls; + + send_client_tunnel_disconnect (t, c); + if (c != t->owner) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Client %u is destination.\n", c->id); + tunnel_delete_client (t, c); + client_delete_tunnel (c, t); + tunnel_destroy_empty (t); + return GNUNET_OK; + } + tunnel_send_destroy (t, 0); + t->owner = NULL; + t->destroy = GNUNET_YES; + + return GNUNET_OK; +} + + +/** + * Timeout function, destroys tunnel if called + * + * @param cls Closure (tunnel to destroy). + * @param tc TaskContext + */ +static void +tunnel_timeout (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct MeshTunnel *t = cls; + struct GNUNET_PeerIdentity id; + + t->timeout_task = GNUNET_SCHEDULER_NO_TASK; + if (0 != (tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN)) + return; + GNUNET_PEER_resolve(t->id.oid, &id); + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + "Tunnel %s [%X] timed out. Destroying.\n", + GNUNET_i2s(&id), t->id.tid); + send_clients_tunnel_destroy (t); + tunnel_destroy (t); +} + +/** + * Resets the tunnel timeout. Starts it if no timeout was running. + * + * @param t Tunnel whose timeout to reset. + * + * TODO use heap to improve efficiency of scheduler. + */ +static void +tunnel_reset_timeout (struct MeshTunnel *t) +{ + if (GNUNET_SCHEDULER_NO_TASK != t->timeout_task) + GNUNET_SCHEDULER_cancel (t->timeout_task); + t->timeout_task = + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply + (refresh_path_time, 4), &tunnel_timeout, t); +} + + +/******************************************************************************/ +/**************** MESH NETWORK HANDLER HELPERS ***********************/ +/******************************************************************************/ + +/** + * Function to send a create path packet to a peer. + * + * @param cls closure + * @param size number of bytes available in buf + * @param buf where the callee should write the message + * @return number of bytes written to buf + */ +static size_t +send_core_path_create (void *cls, size_t size, void *buf) +{ + struct MeshPathInfo *info = cls; + struct GNUNET_MESH_ManipulatePath *msg; + struct GNUNET_PeerIdentity *peer_ptr; + struct MeshTunnel *t = info->t; + struct MeshPeerPath *p = info->path; + size_t size_needed; + uint32_t opt; + int i; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "CREATE PATH sending...\n"); + size_needed = + sizeof (struct GNUNET_MESH_ManipulatePath) + + p->length * sizeof (struct GNUNET_PeerIdentity); + + if (size < size_needed || NULL == buf) + { + GNUNET_break (0); + return 0; + } + msg = (struct GNUNET_MESH_ManipulatePath *) buf; + msg->header.size = htons (size_needed); + msg->header.type = htons (GNUNET_MESSAGE_TYPE_MESH_PATH_CREATE); + msg->tid = ntohl (t->id.tid); + + opt = 0; + if (GNUNET_YES == t->speed_min) + opt |= MESH_TUNNEL_OPT_SPEED_MIN; + if (GNUNET_YES == t->nobuffer) + opt |= MESH_TUNNEL_OPT_NOBUFFER; + msg->opt = htonl(opt); + msg->reserved = 0; + + peer_ptr = (struct GNUNET_PeerIdentity *) &msg[1]; + for (i = 0; i < p->length; i++) + { + GNUNET_PEER_resolve (p->peers[i], peer_ptr++); + } + + path_destroy (p); + GNUNET_free (info); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "CREATE PATH (%u bytes long) sent!\n", size_needed); + return size_needed; +} + + +/** + * Fill the core buffer + * + * @param cls closure (data itself) + * @param size number of bytes available in buf + * @param buf where the callee should write the message + * + * @return number of bytes written to buf + */ +static size_t +send_core_data_multicast (void *cls, size_t size, void *buf) +{ + struct MeshTransmissionDescriptor *info = cls; + size_t total_size; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Multicast callback.\n"); + GNUNET_assert (NULL != info); + GNUNET_assert (NULL != info->peer); + total_size = info->mesh_data->data_len; + GNUNET_assert (total_size < GNUNET_SERVER_MAX_MESSAGE_SIZE); + + if (total_size > size) + { + GNUNET_break (0); + return 0; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " copying data...\n"); + memcpy (buf, info->mesh_data->data, total_size); +#if MESH_DEBUG + { + struct GNUNET_MESH_Multicast *mc; + struct GNUNET_MessageHeader *mh; + + mh = buf; + if (ntohs (mh->type) == GNUNET_MESSAGE_TYPE_MESH_MULTICAST) + { + mc = (struct GNUNET_MESH_Multicast *) mh; + mh = (struct GNUNET_MessageHeader *) &mc[1]; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " multicast, payload type %s\n", + GNUNET_MESH_DEBUG_M2S (ntohs (mh->type))); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " multicast, payload size %u\n", ntohs (mh->size)); + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " type %s\n", + GNUNET_MESH_DEBUG_M2S (ntohs (mh->type))); + } + } +#endif + data_descriptor_decrement_rc (info->mesh_data); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "freeing info...\n"); + GNUNET_free (info); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "return %u\n", total_size); + return total_size; +} + + +/** + * Creates a path ack message in buf and frees all unused resources. + * + * @param cls closure (MeshTransmissionDescriptor) + * @param size number of bytes available in buf + * @param buf where the callee should write the message + * @return number of bytes written to buf + */ +static size_t +send_core_path_ack (void *cls, size_t size, void *buf) +{ + struct MeshTransmissionDescriptor *info = cls; + struct GNUNET_MESH_PathACK *msg = buf; + + GNUNET_assert (NULL != info); + if (sizeof (struct GNUNET_MESH_PathACK) > size) + { + GNUNET_break (0); + return 0; + } + msg->header.size = htons (sizeof (struct GNUNET_MESH_PathACK)); + msg->header.type = htons (GNUNET_MESSAGE_TYPE_MESH_PATH_ACK); + GNUNET_PEER_resolve (info->origin->oid, &msg->oid); + msg->tid = htonl (info->origin->tid); + msg->peer_id = my_full_id; + + GNUNET_free (info); + /* TODO add signature */ + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "PATH ACK sent!\n"); + return sizeof (struct GNUNET_MESH_PathACK); +} + + +/** + * Free a transmission that was already queued with all resources + * associated to the request. + * + * @param queue Queue handler to cancel. + * @param clear_cls Is it necessary to free associated cls? + */ +static void +queue_destroy (struct MeshPeerQueue *queue, int clear_cls) +{ + struct MeshTransmissionDescriptor *dd; + struct MeshPathInfo *path_info; + struct MeshTunnelChildInfo *cinfo; + struct GNUNET_PeerIdentity id; + unsigned int i; + unsigned int max; + + if (GNUNET_YES == clear_cls) + { + switch (queue->type) + { + case GNUNET_MESSAGE_TYPE_MESH_TUNNEL_DESTROY: + GNUNET_log (GNUNET_ERROR_TYPE_INFO, " cancelling TUNNEL_DESTROY\n"); + GNUNET_break (GNUNET_YES == queue->tunnel->destroy); + /* fall through */ + case GNUNET_MESSAGE_TYPE_MESH_UNICAST: + case GNUNET_MESSAGE_TYPE_MESH_MULTICAST: + case GNUNET_MESSAGE_TYPE_MESH_TO_ORIGIN: + case GNUNET_MESSAGE_TYPE_MESH_ACK: + case GNUNET_MESSAGE_TYPE_MESH_POLL: + case GNUNET_MESSAGE_TYPE_MESH_PATH_KEEPALIVE: + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " prebuilt message\n"); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " type %s\n", + GNUNET_MESH_DEBUG_M2S(queue->type)); + dd = queue->cls; + data_descriptor_decrement_rc (dd->mesh_data); + break; + case GNUNET_MESSAGE_TYPE_MESH_PATH_CREATE: + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " type create path\n"); + path_info = queue->cls; + path_destroy (path_info->path); + break; + default: + GNUNET_break (0); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + " type %s unknown!\n", + GNUNET_MESH_DEBUG_M2S(queue->type)); + } + GNUNET_free_non_null (queue->cls); + } + GNUNET_CONTAINER_DLL_remove (queue->peer->queue_head, + queue->peer->queue_tail, + queue); + + /* Delete from child_fc in the appropiate tunnel */ + max = queue->tunnel->fwd_queue_max; + GNUNET_PEER_resolve (queue->peer->id, &id); + cinfo = tunnel_get_neighbor_fc (queue->tunnel, &id); + if (NULL != cinfo) + { + for (i = 0; i < cinfo->send_buffer_n; i++) + { + unsigned int i2; + i2 = (cinfo->send_buffer_start + i) % max; + if (cinfo->send_buffer[i2] == queue) + { + /* Found corresponding entry in the send_buffer. Move all others back. */ + unsigned int j; + unsigned int j2; + unsigned int j3; + + for (j = i, j2 = 0, j3 = 0; j < cinfo->send_buffer_n - 1; j++) + { + j2 = (cinfo->send_buffer_start + j) % max; + j3 = (cinfo->send_buffer_start + j + 1) % max; + cinfo->send_buffer[j2] = cinfo->send_buffer[j3]; + } + + cinfo->send_buffer[j3] = NULL; + cinfo->send_buffer_n--; + } + } + } + + GNUNET_free (queue); +} + + +/** + * @brief Get the next transmittable message from the queue. + * + * This will be the head, except in the case of being a data packet + * not allowed by the destination peer. + * + * @param peer Destination peer. + * + * @return The next viable MeshPeerQueue element to send to that peer. + * NULL when there are no transmittable messages. + */ +struct MeshPeerQueue * +queue_get_next (const struct MeshPeerInfo *peer) +{ + struct MeshPeerQueue *q; + struct MeshTunnel *t; + struct MeshTransmissionDescriptor *info; + struct MeshTunnelChildInfo *cinfo; + struct GNUNET_MESH_Unicast *ucast; + struct GNUNET_MESH_ToOrigin *to_orig; + struct GNUNET_MESH_Multicast *mcast; + struct GNUNET_PeerIdentity id; + uint32_t pid; + uint32_t ack; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "********* selecting message\n"); + for (q = peer->queue_head; NULL != q; q = q->next) + { + t = q->tunnel; + info = q->cls; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "********* %s\n", + GNUNET_MESH_DEBUG_M2S(q->type)); + switch (q->type) + { + case GNUNET_MESSAGE_TYPE_MESH_UNICAST: + ucast = (struct GNUNET_MESH_Unicast *) info->mesh_data->data; + pid = ntohl (ucast->pid); + GNUNET_PEER_resolve (info->peer->id, &id); + cinfo = tunnel_get_neighbor_fc(t, &id); + ack = cinfo->fwd_ack; + break; + case GNUNET_MESSAGE_TYPE_MESH_TO_ORIGIN: + to_orig = (struct GNUNET_MESH_ToOrigin *) info->mesh_data->data; + pid = ntohl (to_orig->pid); + ack = t->bck_ack; + break; + case GNUNET_MESSAGE_TYPE_MESH_MULTICAST: + mcast = (struct GNUNET_MESH_Multicast *) info->mesh_data->data; + if (GNUNET_MESSAGE_TYPE_MESH_MULTICAST != ntohs(mcast->header.type)) + { + // Not a multicast payload: multicast control traffic (destroy, etc) + return q; + } + pid = ntohl (mcast->pid); + GNUNET_PEER_resolve (info->peer->id, &id); + cinfo = tunnel_get_neighbor_fc(t, &id); + ack = cinfo->fwd_ack; + break; + default: + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "********* OK!\n"); + return q; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "********* ACK: %u, PID: %u\n", + ack, pid); + if (GNUNET_NO == GMC_is_pid_bigger(pid, ack)) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "********* OK!\n"); + return q; + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "********* NEXT!\n"); + } + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "********* nothing found\n"); + return NULL; +} + + +/** + * Core callback to write a queued packet to core buffer + * + * @param cls Closure (peer info). + * @param size Number of bytes available in buf. + * @param buf Where the to write the message. + * + * @return number of bytes written to buf + */ +static size_t +queue_send (void *cls, size_t size, void *buf) +{ + struct MeshPeerInfo *peer = cls; + struct GNUNET_MessageHeader *msg; + struct MeshPeerQueue *queue; + struct MeshTunnel *t; + struct MeshTunnelChildInfo *cinfo; + struct GNUNET_PeerIdentity dst_id; + size_t data_size; + + peer->core_transmit = NULL; + cinfo = NULL; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "********* Queue send\n"); + queue = queue_get_next (peer); + + /* Queue has no internal mesh traffic nor sendable payload */ + if (NULL == queue) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "********* not ready, return\n"); + if (NULL == peer->queue_head) + GNUNET_break (0); // Should've been canceled + return 0; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "********* not empty\n"); + + GNUNET_PEER_resolve (peer->id, &dst_id); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "********* towards %s\n", + GNUNET_i2s(&dst_id)); + /* Check if buffer size is enough for the message */ + if (queue->size > size) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "********* not enough room, reissue\n"); + peer->core_transmit = + GNUNET_CORE_notify_transmit_ready (core_handle, + 0, + 0, + GNUNET_TIME_UNIT_FOREVER_REL, + &dst_id, + queue->size, + &queue_send, + peer); + return 0; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "********* size ok\n"); + + t = queue->tunnel; + GNUNET_assert (0 < t->pending_messages); + t->pending_messages--; + if (GNUNET_MESSAGE_TYPE_MESH_UNICAST == queue->type) + { + t->fwd_queue_n--; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "********* unicast: t->q (%u/%u)\n", + t->fwd_queue_n, t->fwd_queue_max); + } + else if (GNUNET_MESSAGE_TYPE_MESH_TO_ORIGIN == queue->type) + { + t->bck_queue_n--; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "********* to origin\n"); + } + + /* Fill buf */ + switch (queue->type) + { + case 0: + case GNUNET_MESSAGE_TYPE_MESH_ACK: + case GNUNET_MESSAGE_TYPE_MESH_POLL: + case GNUNET_MESSAGE_TYPE_MESH_PATH_BROKEN: + case GNUNET_MESSAGE_TYPE_MESH_PATH_DESTROY: + case GNUNET_MESSAGE_TYPE_MESH_TUNNEL_DESTROY: + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "********* raw: %s\n", + GNUNET_MESH_DEBUG_M2S (queue->type)); + /* Fall through */ + case GNUNET_MESSAGE_TYPE_MESH_UNICAST: + case GNUNET_MESSAGE_TYPE_MESH_TO_ORIGIN: + data_size = send_core_data_raw (queue->cls, size, buf); + msg = (struct GNUNET_MessageHeader *) buf; + switch (ntohs (msg->type)) // Type of preconstructed message + { + case GNUNET_MESSAGE_TYPE_MESH_UNICAST: + tunnel_send_fwd_ack (t, GNUNET_MESSAGE_TYPE_MESH_UNICAST); + break; + case GNUNET_MESSAGE_TYPE_MESH_TO_ORIGIN: + tunnel_send_bck_ack (t, GNUNET_MESSAGE_TYPE_MESH_TO_ORIGIN); + break; + default: + break; + } + break; + case GNUNET_MESSAGE_TYPE_MESH_MULTICAST: + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "********* multicast\n"); + { + struct MeshTransmissionDescriptor *info = queue->cls; + + if ((1 == info->mesh_data->reference_counter + && GNUNET_YES == t->speed_min) + || + (info->mesh_data->total_out == info->mesh_data->reference_counter + && GNUNET_NO == t->speed_min)) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "********* considered sent\n"); + t->fwd_queue_n--; + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "********* NOT considered sent yet\n"); + t->pending_messages++; + } + } + data_size = send_core_data_multicast(queue->cls, size, buf); + tunnel_send_fwd_ack (t, GNUNET_MESSAGE_TYPE_MESH_MULTICAST); + break; + case GNUNET_MESSAGE_TYPE_MESH_PATH_CREATE: + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "********* path create\n"); + data_size = send_core_path_create (queue->cls, size, buf); + break; + case GNUNET_MESSAGE_TYPE_MESH_PATH_ACK: + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "********* path ack\n"); + data_size = send_core_path_ack (queue->cls, size, buf); + break; + case GNUNET_MESSAGE_TYPE_MESH_PATH_KEEPALIVE: + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "********* path keepalive\n"); + data_size = send_core_data_multicast (queue->cls, size, buf); + break; + default: + GNUNET_break (0); + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + "********* type unknown: %u\n", + queue->type); + data_size = 0; + } + switch (queue->type) + { + case GNUNET_MESSAGE_TYPE_MESH_UNICAST: + case GNUNET_MESSAGE_TYPE_MESH_TO_ORIGIN: + case GNUNET_MESSAGE_TYPE_MESH_MULTICAST: + cinfo = tunnel_get_neighbor_fc (t, &dst_id); + if (cinfo->send_buffer[cinfo->send_buffer_start] != queue) + { + GNUNET_break (0); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "at pos %u (%p) != %p\n", + cinfo->send_buffer_start, + cinfo->send_buffer[cinfo->send_buffer_start], + queue); + } + if (cinfo->send_buffer_n > 0) + { + cinfo->send_buffer[cinfo->send_buffer_start] = NULL; + cinfo->send_buffer_n--; + cinfo->send_buffer_start++; + cinfo->send_buffer_start %= t->fwd_queue_max; + } + else + { + GNUNET_break (0); + } + break; + default: + break; + } + + /* Free queue, but cls was freed by send_core_* */ + queue_destroy (queue, GNUNET_NO); + + if (GNUNET_YES == t->destroy && 0 == t->pending_messages) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "********* destroying tunnel!\n"); + tunnel_destroy (t); + } + + /* If more data in queue, send next */ + queue = queue_get_next(peer); + if (NULL != queue) + { + struct GNUNET_PeerIdentity id; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "********* more data!\n"); + GNUNET_PEER_resolve (peer->id, &id); + peer->core_transmit = + GNUNET_CORE_notify_transmit_ready(core_handle, + 0, + 0, + GNUNET_TIME_UNIT_FOREVER_REL, + &id, + queue->size, + &queue_send, + peer); + } + else + { + if (NULL != peer->queue_head) + { + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + "********* %s stalled\n", + GNUNET_i2s(&my_full_id)); + if (NULL == cinfo) + cinfo = tunnel_get_neighbor_fc (t, &dst_id); + // FIXME unify bck/fwd structures, bck does not have cinfo right now + if (NULL != cinfo && GNUNET_SCHEDULER_NO_TASK == cinfo->fc_poll) + { + cinfo->fc_poll = GNUNET_SCHEDULER_add_delayed (cinfo->fc_poll_time, + &tunnel_poll, cinfo); + } + } + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "********* return %d\n", data_size); + return data_size; +} + + +/** + * @brief Queue and pass message to core when possible. + * + * If type is payload (UNICAST, TO_ORIGIN, MULTICAST) checks for queue status + * and accounts for it. In case the queue is full, the message is dropped and + * a break issued. + * + * Otherwise, message is treated as internal and allowed to go regardless of + * queue status. + * + * @param cls Closure (@c type dependant). It will be used by queue_send to + * build the message to be sent if not already prebuilt. + * @param type Type of the message, 0 for a raw message. + * @param size Size of the message. + * @param dst Neighbor to send message to. + * @param t Tunnel this message belongs to. + */ +static void +queue_add (void *cls, uint16_t type, size_t size, + struct MeshPeerInfo *dst, struct MeshTunnel *t) +{ + struct MeshPeerQueue *queue; + struct MeshTunnelChildInfo *cinfo; + struct GNUNET_PeerIdentity id; + unsigned int *max; + unsigned int *n; + unsigned int i; + + n = NULL; + if (GNUNET_MESSAGE_TYPE_MESH_UNICAST == type || + GNUNET_MESSAGE_TYPE_MESH_MULTICAST == type) + { + n = &t->fwd_queue_n; + max = &t->fwd_queue_max; + } + else if (GNUNET_MESSAGE_TYPE_MESH_TO_ORIGIN == type) + { + n = &t->bck_queue_n; + max = &t->bck_queue_max; + } + if (NULL != n) + { + if (*n >= *max) + { + GNUNET_break(0); + GNUNET_STATISTICS_update(stats, + "# messages dropped (buffer full)", + 1, GNUNET_NO); + return; // Drop message + } + (*n)++; + } + queue = GNUNET_malloc (sizeof (struct MeshPeerQueue)); + queue->cls = cls; + queue->type = type; + queue->size = size; + queue->peer = dst; + queue->tunnel = t; + GNUNET_CONTAINER_DLL_insert_tail (dst->queue_head, dst->queue_tail, queue); + GNUNET_PEER_resolve (dst->id, &id); + if (NULL == dst->core_transmit) + { + dst->core_transmit = + GNUNET_CORE_notify_transmit_ready (core_handle, + 0, + 0, + GNUNET_TIME_UNIT_FOREVER_REL, + &id, + size, + &queue_send, + dst); + } + t->pending_messages++; + if (NULL == n) // Is this internal mesh traffic? + return; + + // It's payload, keep track of buffer per peer. + cinfo = tunnel_get_neighbor_fc(t, &id); + i = (cinfo->send_buffer_start + cinfo->send_buffer_n) % t->fwd_queue_max; + if (NULL != cinfo->send_buffer[i]) + { + GNUNET_break (cinfo->send_buffer_n == t->fwd_queue_max); // aka i == start + queue_destroy (cinfo->send_buffer[cinfo->send_buffer_start], GNUNET_YES); + cinfo->send_buffer_start++; + cinfo->send_buffer_start %= t->fwd_queue_max; + } + else + { + cinfo->send_buffer_n++; + } + cinfo->send_buffer[i] = queue; + if (cinfo->send_buffer_n > t->fwd_queue_max) + { + GNUNET_break (0); + cinfo->send_buffer_n = t->fwd_queue_max; + } +} + + +/******************************************************************************/ +/******************** MESH NETWORK HANDLERS **************************/ +/******************************************************************************/ + + +/** + * Core handler for path creation + * + * @param cls closure + * @param message message + * @param peer peer identity this notification is about + * @param atsi performance data + * @param atsi_count number of records in 'atsi' + * + * @return GNUNET_OK to keep the connection open, + * GNUNET_SYSERR to close it (signal serious error) + */ +static int +handle_mesh_path_create (void *cls, const struct GNUNET_PeerIdentity *peer, + const struct GNUNET_MessageHeader *message, + const struct GNUNET_ATS_Information *atsi, + unsigned int atsi_count) +{ + unsigned int own_pos; + uint16_t size; + uint16_t i; + MESH_TunnelNumber tid; + struct GNUNET_MESH_ManipulatePath *msg; + struct GNUNET_PeerIdentity *pi; + struct GNUNET_HashCode hash; + struct MeshPeerPath *path; + struct MeshPeerInfo *dest_peer_info; + struct MeshPeerInfo *orig_peer_info; + struct MeshTunnel *t; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Received a path create msg [%s]\n", + GNUNET_i2s (&my_full_id)); + size = ntohs (message->size); + if (size < sizeof (struct GNUNET_MESH_ManipulatePath)) + { + GNUNET_break_op (0); + return GNUNET_OK; + } + + size -= sizeof (struct GNUNET_MESH_ManipulatePath); + if (size % sizeof (struct GNUNET_PeerIdentity)) + { + GNUNET_break_op (0); + return GNUNET_OK; + } + size /= sizeof (struct GNUNET_PeerIdentity); + if (size < 2) + { + GNUNET_break_op (0); + return GNUNET_OK; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " path has %u hops.\n", size); + msg = (struct GNUNET_MESH_ManipulatePath *) message; + + tid = ntohl (msg->tid); + pi = (struct GNUNET_PeerIdentity *) &msg[1]; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " path is for tunnel %s [%X].\n", GNUNET_i2s (pi), tid); + t = tunnel_get (pi, tid); + if (NULL == t) // FIXME only for INCOMING tunnels? + { + uint32_t opt; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " Creating tunnel\n"); + t = tunnel_new (GNUNET_PEER_intern (pi), tid, NULL, 0); + if (NULL == t) + { + // FIXME notify failure + return GNUNET_OK; + } + opt = ntohl (msg->opt); + t->speed_min = (0 != (opt & MESH_TUNNEL_OPT_SPEED_MIN)) ? + GNUNET_YES : GNUNET_NO; + if (0 != (opt & MESH_TUNNEL_OPT_NOBUFFER)) + { + t->nobuffer = GNUNET_YES; + t->last_fwd_ack = t->fwd_pid + 1; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " speed_min: %d, nobuffer:%d\n", + t->speed_min, t->nobuffer); + + if (GNUNET_YES == t->nobuffer) + { + t->bck_queue_max = 1; + t->fwd_queue_max = 1; + } + + // FIXME only assign a local tid if a local client is interested (on demand) + while (NULL != tunnel_get_incoming (next_local_tid)) + next_local_tid = (next_local_tid + 1) | GNUNET_MESH_LOCAL_TUNNEL_ID_SERV; + t->local_tid_dest = next_local_tid++; + next_local_tid = next_local_tid | GNUNET_MESH_LOCAL_TUNNEL_ID_SERV; + // FIXME end + + tunnel_reset_timeout (t); + GNUNET_CRYPTO_hash (&t->local_tid_dest, sizeof (MESH_TunnelNumber), &hash); + if (GNUNET_OK != + GNUNET_CONTAINER_multihashmap_put (incoming_tunnels, &hash, t, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_FAST)) + { + tunnel_destroy (t); + GNUNET_break (0); + return GNUNET_OK; + } + } + dest_peer_info = + GNUNET_CONTAINER_multihashmap_get (peers, &pi[size - 1].hashPubKey); + if (NULL == dest_peer_info) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " Creating PeerInfo for destination.\n"); + dest_peer_info = GNUNET_malloc (sizeof (struct MeshPeerInfo)); + dest_peer_info->id = GNUNET_PEER_intern (&pi[size - 1]); + GNUNET_CONTAINER_multihashmap_put (peers, &pi[size - 1].hashPubKey, + dest_peer_info, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY); + } + orig_peer_info = GNUNET_CONTAINER_multihashmap_get (peers, &pi->hashPubKey); + if (NULL == orig_peer_info) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " Creating PeerInfo for origin.\n"); + orig_peer_info = GNUNET_malloc (sizeof (struct MeshPeerInfo)); + orig_peer_info->id = GNUNET_PEER_intern (pi); + GNUNET_CONTAINER_multihashmap_put (peers, &pi->hashPubKey, orig_peer_info, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY); + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " Creating path...\n"); + path = path_new (size); + own_pos = 0; + for (i = 0; i < size; i++) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " ... adding %s\n", + GNUNET_i2s (&pi[i])); + path->peers[i] = GNUNET_PEER_intern (&pi[i]); + if (path->peers[i] == myid) + own_pos = i; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " Own position: %u\n", own_pos); + if (own_pos == 0) + { + /* cannot be self, must be 'not found' */ + /* create path: self not found in path through self */ + GNUNET_break_op (0); + path_destroy (path); tunnel_destroy (t); + return GNUNET_OK; + } + path_add_to_peers (path, GNUNET_NO); + tunnel_add_path (t, path, own_pos); + if (own_pos == size - 1) + { + /* It is for us! Send ack. */ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " It's for us!\n"); + peer_info_add_path_to_origin (orig_peer_info, path, GNUNET_NO); + if (NULL == t->peers) + { + /* New tunnel! Notify clients on first payload message. */ + t->peers = GNUNET_CONTAINER_multihashmap_create (4, GNUNET_NO); + } + GNUNET_break (GNUNET_SYSERR != + GNUNET_CONTAINER_multihashmap_put (t->peers, + &my_full_id.hashPubKey, + peer_info_get + (&my_full_id), + GNUNET_CONTAINER_MULTIHASHMAPOPTION_REPLACE)); + send_path_ack (t); + } + else + { + struct MeshPeerPath *path2; + + /* It's for somebody else! Retransmit. */ + path2 = path_duplicate (path); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " Retransmitting.\n"); + peer_info_add_path (dest_peer_info, path2, GNUNET_NO); + path2 = path_duplicate (path); + peer_info_add_path_to_origin (orig_peer_info, path2, GNUNET_NO); + send_create_path (dest_peer_info, path, t); + } + return GNUNET_OK; +} + + +/** + * Core handler for path destruction + * + * @param cls closure + * @param message message + * @param peer peer identity this notification is about + * @param atsi performance data + * @param atsi_count number of records in 'atsi' + * + * @return GNUNET_OK to keep the connection open, + * GNUNET_SYSERR to close it (signal serious error) + */ +static int +handle_mesh_path_destroy (void *cls, const struct GNUNET_PeerIdentity *peer, + const struct GNUNET_MessageHeader *message, + const struct GNUNET_ATS_Information *atsi, + unsigned int atsi_count) +{ + struct GNUNET_MESH_ManipulatePath *msg; + struct GNUNET_PeerIdentity *pi; + struct MeshPeerPath *path; + struct MeshTunnel *t; + unsigned int own_pos; + unsigned int i; + size_t size; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Received a PATH DESTROY msg from %s\n", GNUNET_i2s (peer)); + size = ntohs (message->size); + if (size < sizeof (struct GNUNET_MESH_ManipulatePath)) + { + GNUNET_break_op (0); + return GNUNET_OK; + } + + size -= sizeof (struct GNUNET_MESH_ManipulatePath); + if (size % sizeof (struct GNUNET_PeerIdentity)) + { + GNUNET_break_op (0); + return GNUNET_OK; + } + size /= sizeof (struct GNUNET_PeerIdentity); + if (size < 2) + { + GNUNET_break_op (0); + return GNUNET_OK; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " path has %u hops.\n", size); + + msg = (struct GNUNET_MESH_ManipulatePath *) message; + pi = (struct GNUNET_PeerIdentity *) &msg[1]; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " path is for tunnel %s [%X].\n", GNUNET_i2s (pi), + msg->tid); + t = tunnel_get (pi, ntohl (msg->tid)); + if (NULL == t) + { + /* TODO notify back: we don't know this tunnel */ + GNUNET_break_op (0); + return GNUNET_OK; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " Creating path...\n"); + path = path_new (size); + own_pos = 0; + for (i = 0; i < size; i++) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " ... adding %s\n", + GNUNET_i2s (&pi[i])); + path->peers[i] = GNUNET_PEER_intern (&pi[i]); + if (path->peers[i] == myid) + own_pos = i; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " Own position: %u\n", own_pos); + if (own_pos < path->length - 1) + send_prebuilt_message (message, &pi[own_pos + 1], t); + else + send_client_tunnel_disconnect(t, NULL); + + tunnel_delete_peer (t, path->peers[path->length - 1]); + path_destroy (path); + return GNUNET_OK; } /** - * tunnel_destroy_iterator: iterator for deleting each tunnel that belongs to a - * client when the client disconnects. If the client is not the owner, the - * owner will get notified if no more clients are in the tunnel and the client - * get removed from the tunnel's list. + * Core handler for notifications of broken paths * - * @param cls closure (client that is disconnecting) - * @param key the hash of the local tunnel id (used to access the hashmap) - * @param value the value stored at the key (tunnel to destroy) + * @param cls closure + * @param message message + * @param peer peer identity this notification is about + * @param atsi performance data + * @param atsi_count number of records in 'atsi' * - * @return GNUNET_OK on success + * @return GNUNET_OK to keep the connection open, + * GNUNET_SYSERR to close it (signal serious error) */ static int -tunnel_destroy_iterator (void *cls, const GNUNET_HashCode * key, void *value) +handle_mesh_path_broken (void *cls, const struct GNUNET_PeerIdentity *peer, + const struct GNUNET_MessageHeader *message, + const struct GNUNET_ATS_Information *atsi, + unsigned int atsi_count) { - struct MeshTunnel *t = value; - struct MeshClient *c = cls; - int r; + struct GNUNET_MESH_PathBroken *msg; + struct MeshTunnel *t; - send_client_tunnel_disconnect(t, c); - if (c != t->owner) + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Received a PATH BROKEN msg from %s\n", GNUNET_i2s (peer)); + msg = (struct GNUNET_MESH_PathBroken *) message; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " regarding %s\n", + GNUNET_i2s (&msg->peer1)); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " regarding %s\n", + GNUNET_i2s (&msg->peer2)); + t = tunnel_get (&msg->oid, ntohl (msg->tid)); + if (NULL == t) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Client %u is destination, keeping the tunnel alive.\n", c->id); - tunnel_delete_client(t, c); - client_delete_tunnel(c, t); + GNUNET_break_op (0); return GNUNET_OK; } - tunnel_send_destroy(t); - r = tunnel_destroy (t); - return r; -} - - -/** - * Timeout function, destroys tunnel if called - * - * @param cls Closure (tunnel to destroy). - * @param tc TaskContext - */ -static void -tunnel_timeout (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - struct MeshTunnel *t = cls; - - if (GNUNET_SCHEDULER_REASON_SHUTDOWN == tc->reason) - return; - t->timeout_task = GNUNET_SCHEDULER_NO_TASK; - tunnel_destroy (t); -} + tunnel_notify_connection_broken (t, GNUNET_PEER_search (&msg->peer1), + GNUNET_PEER_search (&msg->peer2)); + return GNUNET_OK; -/** - * Resets the tunnel timeout. Starts it if no timeout was running. - * - * @param t Tunnel whose timeout to reset. - */ -static void -tunnel_reset_timeout (struct MeshTunnel *t) -{ - if (GNUNET_SCHEDULER_NO_TASK != t->timeout_task) - GNUNET_SCHEDULER_cancel (t->timeout_task); - t->timeout_task = - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply - (REFRESH_PATH_TIME, 4), &tunnel_timeout, t); } -/******************************************************************************/ -/**************** MESH NETWORK HANDLER HELPERS ***********************/ -/******************************************************************************/ - /** - * Function called to notify a client about the socket - * being ready to queue more data. "buf" will be - * NULL and "size" zero if the socket was closed for - * writing in the meantime. + * Core handler for tunnel destruction * * @param cls closure - * @param size number of bytes available in buf - * @param buf where the callee should write the message - * @return number of bytes written to buf + * @param message message + * @param peer peer identity this notification is about + * @param atsi performance data + * @param atsi_count number of records in 'atsi' + * + * @return GNUNET_OK to keep the connection open, + * GNUNET_SYSERR to close it (signal serious error) */ -static size_t -send_core_create_path (void *cls, size_t size, void *buf) +static int +handle_mesh_tunnel_destroy (void *cls, const struct GNUNET_PeerIdentity *peer, + const struct GNUNET_MessageHeader *message, + const struct GNUNET_ATS_Information *atsi, + unsigned int atsi_count) { - struct MeshPathInfo *info = cls; - struct GNUNET_MESH_ManipulatePath *msg; - struct GNUNET_PeerIdentity *peer_ptr; - struct MeshPeerInfo *peer = info->peer; - struct MeshTunnel *t = info->t; - struct MeshPeerPath *p = info->path; - size_t size_needed; - int i; - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "CREATE PATH sending...\n"); - size_needed = - sizeof (struct GNUNET_MESH_ManipulatePath) + - p->length * sizeof (struct GNUNET_PeerIdentity); + struct GNUNET_MESH_TunnelDestroy *msg; + struct MeshTunnel *t; + GNUNET_PEER_Id parent; + GNUNET_PEER_Id pid; - if (size < size_needed || NULL == buf) + msg = (struct GNUNET_MESH_TunnelDestroy *) message; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Got a TUNNEL DESTROY packet from %s\n", + GNUNET_i2s (peer)); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " for tunnel %s [%u]\n", + GNUNET_i2s (&msg->oid), ntohl (msg->tid)); + t = tunnel_get (&msg->oid, ntohl (msg->tid)); + /* Check signature */ + if (NULL == t) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "create path retransmit!\n"); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " buf: %p\n", buf); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " size: (%u/%u)\n", size, - size_needed); - info->peer->core_transmit[info->pos] = - GNUNET_CORE_notify_transmit_ready (core_handle, 0, 0, - GNUNET_TIME_UNIT_FOREVER_REL, - tree_get_first_hop (t->tree, - peer->id), - size_needed, &send_core_create_path, - info); - return 0; + /* Probably already got the message from another path, + * destroyed the tunnel and retransmitted to children. + * Safe to ignore. + */ + GNUNET_STATISTICS_update (stats, "# control on unknown tunnel", + 1, GNUNET_NO); + return GNUNET_OK; } - info->peer->core_transmit[info->pos] = NULL; -#if MESH_DEBUG + parent = tree_get_predecessor (t->tree); + pid = GNUNET_PEER_search (peer); + if (pid != parent) { - struct GNUNET_PeerIdentity id; + unsigned int nc; - GNUNET_PEER_resolve (peer->id, &id); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - " setting core_transmit %s [%u] to NULL\n", - GNUNET_i2s (&id), info->pos); + tree_del_peer (t->tree, pid, &tunnel_child_removed, t); + nc = tree_count_children (t->tree); + if (nc > 0 || NULL != t->owner || t->nclients > 0) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "still in use: %u cl, %u ch\n", + t->nclients, nc); + return GNUNET_OK; + } } -#endif - msg = (struct GNUNET_MESH_ManipulatePath *) buf; - msg->header.size = htons (size_needed); - msg->header.type = htons (GNUNET_MESSAGE_TYPE_MESH_PATH_CREATE); - msg->tid = ntohl (t->id.tid); - - peer_ptr = (struct GNUNET_PeerIdentity *) &msg[1]; - for (i = 0; i < p->length; i++) + if (t->local_tid_dest >= GNUNET_MESH_LOCAL_TUNNEL_ID_SERV) { - GNUNET_PEER_resolve (p->peers[i], peer_ptr++); + /* Tunnel was incoming, notify clients */ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "INCOMING TUNNEL %X %X\n", + t->local_tid, t->local_tid_dest); + send_clients_tunnel_destroy (t); } - - path_destroy (p); - GNUNET_free (info); - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "CREATE PATH (%u bytes long) sent!\n", size_needed); - return size_needed; + tunnel_send_destroy (t, parent); + t->destroy = GNUNET_YES; + // TODO: add timeout to destroy the tunnel anyway + return GNUNET_OK; } /** - * Function called to notify a client about the socket - * being ready to queue more data. "buf" will be - * NULL and "size" zero if the socket was closed for - * writing in the meantime. - * - * @param cls closure (data itself) - * @param size number of bytes available in buf - * @param buf where the callee should write the message + * Core handler for mesh network traffic going from the origin to a peer * - * @return number of bytes written to buf + * @param cls closure + * @param peer peer identity this notification is about + * @param message message + * @param atsi performance data + * @param atsi_count number of records in 'atsi' + * @return GNUNET_OK to keep the connection open, + * GNUNET_SYSERR to close it (signal serious error) */ -static size_t -send_core_data_multicast (void *cls, size_t size, void *buf) +static int +handle_mesh_data_unicast (void *cls, const struct GNUNET_PeerIdentity *peer, + const struct GNUNET_MessageHeader *message, + const struct GNUNET_ATS_Information *atsi, + unsigned int atsi_count) { - struct MeshTransmissionDescriptor *info = cls; - size_t total_size; + struct GNUNET_MESH_Unicast *msg; + struct GNUNET_PeerIdentity *neighbor; + struct MeshTunnelChildInfo *cinfo; + struct MeshTunnel *t; + GNUNET_PEER_Id dest_id; + uint32_t pid; + uint32_t ttl; + size_t size; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Multicast callback.\n"); - GNUNET_assert (NULL != info); - GNUNET_assert (NULL != info->peer); - total_size = info->mesh_data->data_len; - GNUNET_assert (total_size < GNUNET_SERVER_MAX_MESSAGE_SIZE); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "got a unicast packet from %s\n", + GNUNET_i2s (peer)); + /* Check size */ + size = ntohs (message->size); + if (size < + sizeof (struct GNUNET_MESH_Unicast) + + sizeof (struct GNUNET_MessageHeader)) + { + GNUNET_break (0); + return GNUNET_OK; + } + msg = (struct GNUNET_MESH_Unicast *) message; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " of type %s\n", + GNUNET_MESH_DEBUG_M2S (ntohs (msg[1].header.type))); + /* Check tunnel */ + t = tunnel_get (&msg->oid, ntohl (msg->tid)); + if (NULL == t) + { + /* TODO notify back: we don't know this tunnel */ + GNUNET_STATISTICS_update (stats, "# data on unknown tunnel", 1, GNUNET_NO); + GNUNET_break_op (0); + return GNUNET_OK; + } + pid = ntohl (msg->pid); + if (t->fwd_pid == pid) + { + GNUNET_STATISTICS_update (stats, "# duplicate PID drops", 1, GNUNET_NO); + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + " Already seen pid %u, DROPPING!\n", pid); + return GNUNET_OK; + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " pid %u not seen yet, forwarding\n", pid); + } - if (total_size > size) + t->skip += (pid - t->fwd_pid) - 1; + t->fwd_pid = pid; + + if (GMC_is_pid_bigger (pid, t->last_fwd_ack)) { - /* Retry */ - struct GNUNET_PeerIdentity id; + GNUNET_STATISTICS_update (stats, "# unsolicited unicast", 1, GNUNET_NO); + GNUNET_break_op (0); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Received PID %u, ACK %u\n", + pid, t->last_fwd_ack); + return GNUNET_OK; + } + tunnel_reset_timeout (t); + dest_id = GNUNET_PEER_search (&msg->destination); + if (dest_id == myid) + { GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Multicast: retransmitting... (%u/%u)\n", size, - total_size); - GNUNET_PEER_resolve (info->peer->id, &id); - info->peer->core_transmit[info->handler_n] = - GNUNET_CORE_notify_transmit_ready (core_handle, 0, 0, - GNUNET_TIME_UNIT_FOREVER_REL, &id, - total_size, - &send_core_data_multicast, info); - return 0; + " it's for us! sending to clients...\n"); + GNUNET_STATISTICS_update (stats, "# unicast received", 1, GNUNET_NO); + send_subscribed_clients (message, &msg[1].header, t); + tunnel_send_fwd_ack (t, GNUNET_MESSAGE_TYPE_MESH_UNICAST); + return GNUNET_OK; } - info->peer->core_transmit[info->handler_n] = NULL; - info->peer->infos[info->handler_n] = NULL; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " copying data...\n"); - memcpy (buf, info->mesh_data->data, total_size); -#if MESH_DEBUG + ttl = ntohl (msg->ttl); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " ttl: %u\n", ttl); + if (ttl == 0) { - struct GNUNET_MESH_Multicast *mc; - struct GNUNET_MessageHeader *mh; + GNUNET_STATISTICS_update (stats, "# TTL drops", 1, GNUNET_NO); + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, " TTL is 0, DROPPING!\n"); + tunnel_send_fwd_ack (t, GNUNET_MESSAGE_TYPE_MESH_ACK); + return GNUNET_OK; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " not for us, retransmitting...\n"); - mh = buf; - if (ntohs (mh->type) == GNUNET_MESSAGE_TYPE_MESH_MULTICAST) - { - mc = (struct GNUNET_MESH_Multicast *) mh; - mh = (struct GNUNET_MessageHeader *) &mc[1]; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - " multicast, payload type %u\n", ntohs (mh->type)); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - " multicast, payload size %u\n", ntohs (mh->size)); - } - else - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " type %u\n", - ntohs (mh->type)); - } + neighbor = tree_get_first_hop (t->tree, dest_id); + cinfo = tunnel_get_neighbor_fc (t, neighbor); + cinfo->fwd_pid = pid; + GNUNET_CONTAINER_multihashmap_iterate (t->children_fc, + &tunnel_add_skip, + &neighbor); + if (GNUNET_YES == t->nobuffer && + GNUNET_YES == GMC_is_pid_bigger (pid, cinfo->fwd_ack)) + { + GNUNET_STATISTICS_update (stats, "# unsolicited unicast", 1, GNUNET_NO); + GNUNET_log (GNUNET_ERROR_TYPE_INFO, " %u > %u\n", pid, cinfo->fwd_ack); + GNUNET_break_op (0); + return GNUNET_OK; } -#endif - data_descriptor_decrement_multicast (info->mesh_data); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "freeing info...\n"); - GNUNET_free (info); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "return %u\n", total_size); - return total_size; + send_prebuilt_message (message, neighbor, t); + GNUNET_STATISTICS_update (stats, "# unicast forwarded", 1, GNUNET_NO); + return GNUNET_OK; } /** - * Function called to notify a client about the socket - * being ready to queue more data. "buf" will be - * NULL and "size" zero if the socket was closed for - * writing in the meantime. + * Core handler for mesh network traffic going from the origin to all peers * - * @param cls closure (MeshTransmissionDescriptor) - * @param size number of bytes available in buf - * @param buf where the callee should write the message - * @return number of bytes written to buf + * @param cls closure + * @param message message + * @param peer peer identity this notification is about + * @param atsi performance data + * @param atsi_count number of records in 'atsi' + * @return GNUNET_OK to keep the connection open, + * GNUNET_SYSERR to close it (signal serious error) + * + * TODO: Check who we got this from, to validate route. */ -static size_t -send_core_path_ack (void *cls, size_t size, void *buf) +static int +handle_mesh_data_multicast (void *cls, const struct GNUNET_PeerIdentity *peer, + const struct GNUNET_MessageHeader *message, + const struct GNUNET_ATS_Information *atsi, + unsigned int atsi_count) { - struct MeshTransmissionDescriptor *info = cls; - struct GNUNET_MESH_PathACK *msg = buf; + struct GNUNET_MESH_Multicast *msg; + struct MeshTunnel *t; + size_t size; + uint32_t pid; - GNUNET_assert (NULL != info); - if (info->peer) + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "got a multicast packet from %s\n", + GNUNET_i2s (peer)); + size = ntohs (message->size); + if (sizeof (struct GNUNET_MESH_Multicast) + + sizeof (struct GNUNET_MessageHeader) > size) { - info->peer->core_transmit[info->handler_n] = NULL; + GNUNET_break_op (0); + return GNUNET_OK; } - if (sizeof (struct GNUNET_MESH_PathACK) > size) + msg = (struct GNUNET_MESH_Multicast *) message; + t = tunnel_get (&msg->oid, ntohl (msg->tid)); + + if (NULL == t) { - GNUNET_break (0); - return 0; + /* TODO notify that we dont know that tunnel */ + GNUNET_STATISTICS_update (stats, "# data on unknown tunnel", 1, GNUNET_NO); + GNUNET_break_op (0); + return GNUNET_OK; } - msg->header.size = htons (sizeof (struct GNUNET_MESH_PathACK)); - msg->header.type = htons (GNUNET_MESSAGE_TYPE_MESH_PATH_ACK); - GNUNET_PEER_resolve (info->origin->oid, &msg->oid); - msg->tid = htonl (info->origin->tid); - msg->peer_id = my_full_id; - GNUNET_free (info); - /* TODO add signature */ + pid = ntohl (msg->pid); + if (t->fwd_pid == pid) + { + /* already seen this packet, drop */ + GNUNET_STATISTICS_update (stats, "# duplicate PID drops", 1, GNUNET_NO); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " Already seen pid %u, DROPPING!\n", pid); + tunnel_send_fwd_ack (t, GNUNET_MESSAGE_TYPE_MESH_ACK); + return GNUNET_OK; + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " pid %u not seen yet, forwarding\n", pid); + } + t->skip += (pid - t->fwd_pid) - 1; + t->fwd_pid = pid; + tunnel_reset_timeout (t); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "PATH ACK sent!\n"); - return sizeof (struct GNUNET_MESH_PathACK); + /* Transmit to locally interested clients */ + if (NULL != t->peers && + GNUNET_CONTAINER_multihashmap_contains (t->peers, &my_full_id.hashPubKey)) + { + GNUNET_STATISTICS_update (stats, "# multicast received", 1, GNUNET_NO); + send_subscribed_clients (message, &msg[1].header, t); + tunnel_send_fwd_ack(t, GNUNET_MESSAGE_TYPE_MESH_MULTICAST); + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " ttl: %u\n", ntohl (msg->ttl)); + if (ntohl (msg->ttl) == 0) + { + GNUNET_STATISTICS_update (stats, "# TTL drops", 1, GNUNET_NO); + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, " TTL is 0, DROPPING!\n"); + tunnel_send_fwd_ack (t, GNUNET_MESSAGE_TYPE_MESH_ACK); + return GNUNET_OK; + } + GNUNET_STATISTICS_update (stats, "# multicast forwarded", 1, GNUNET_NO); + tunnel_send_multicast (t, message); + return GNUNET_OK; } -/******************************************************************************/ -/******************** MESH NETWORK HANDLERS **************************/ -/******************************************************************************/ - - /** - * Core handler for path creation + * Core handler for mesh network traffic toward the owner of a tunnel * * @param cls closure * @param message message @@ -2829,182 +5663,195 @@ send_core_path_ack (void *cls, size_t size, void *buf) * GNUNET_SYSERR to close it (signal serious error) */ static int -handle_mesh_path_create (void *cls, const struct GNUNET_PeerIdentity *peer, - const struct GNUNET_MessageHeader *message, - const struct GNUNET_ATS_Information *atsi, - unsigned int atsi_count) +handle_mesh_data_to_orig (void *cls, const struct GNUNET_PeerIdentity *peer, + const struct GNUNET_MessageHeader *message, + const struct GNUNET_ATS_Information *atsi, + unsigned int atsi_count) { - unsigned int own_pos; - uint16_t size; - uint16_t i; - MESH_TunnelNumber tid; - struct GNUNET_MESH_ManipulatePath *msg; - struct GNUNET_PeerIdentity *pi; - GNUNET_HashCode hash; - struct MeshPeerPath *path; - struct MeshPeerInfo *dest_peer_info; - struct MeshPeerInfo *orig_peer_info; + struct GNUNET_MESH_ToOrigin *msg; + struct GNUNET_PeerIdentity id; + struct MeshPeerInfo *peer_info; struct MeshTunnel *t; + struct MeshTunnelChildInfo *cinfo; + GNUNET_PEER_Id predecessor; + size_t size; + uint32_t pid; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Received a path create msg [%s]\n", - GNUNET_i2s (&my_full_id)); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "got a ToOrigin packet from %s\n", + GNUNET_i2s (peer)); size = ntohs (message->size); - if (size < sizeof (struct GNUNET_MESH_ManipulatePath)) + if (size < sizeof (struct GNUNET_MESH_ToOrigin) + /* Payload must be */ + sizeof (struct GNUNET_MessageHeader)) /* at least a header */ { GNUNET_break_op (0); return GNUNET_OK; } + msg = (struct GNUNET_MESH_ToOrigin *) message; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " of type %s\n", + GNUNET_MESH_DEBUG_M2S (ntohs (msg[1].header.type))); + t = tunnel_get (&msg->oid, ntohl (msg->tid)); + pid = ntohl (msg->pid); - size -= sizeof (struct GNUNET_MESH_ManipulatePath); - if (size % sizeof (struct GNUNET_PeerIdentity)) + if (NULL == t) { - GNUNET_break_op (0); + /* TODO notify that we dont know this tunnel (whom)? */ + GNUNET_STATISTICS_update (stats, "# data on unknown tunnel", 1, GNUNET_NO); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Received to_origin with PID %u on unknown tunnel %s [%u]\n", + pid, GNUNET_i2s (&msg->oid), ntohl (msg->tid)); return GNUNET_OK; } - size /= sizeof (struct GNUNET_PeerIdentity); - if (size < 2) + + cinfo = tunnel_get_neighbor_fc(t, peer); + if (NULL == cinfo) { - GNUNET_break_op (0); + GNUNET_break (0); return GNUNET_OK; } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " path has %u hops.\n", size); - msg = (struct GNUNET_MESH_ManipulatePath *) message; - tid = ntohl (msg->tid); - pi = (struct GNUNET_PeerIdentity *) &msg[1]; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - " path is for tunnel %s [%X].\n", GNUNET_i2s (pi), tid); - t = tunnel_get (pi, tid); - if (NULL == t) + if (cinfo->bck_pid == pid) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " Creating tunnel\n"); - t = GNUNET_malloc (sizeof (struct MeshTunnel)); - t->id.oid = GNUNET_PEER_intern (pi); - t->id.tid = tid; - while (NULL != tunnel_get_incoming (next_local_tid)) - next_local_tid = (next_local_tid + 1) | GNUNET_MESH_LOCAL_TUNNEL_ID_SERV; - t->local_tid_dest = next_local_tid++; - next_local_tid = next_local_tid | GNUNET_MESH_LOCAL_TUNNEL_ID_SERV; - t->tree = tree_new (t->id.oid); - - GNUNET_CRYPTO_hash (&t->id, sizeof (struct MESH_TunnelID), &hash); - if (GNUNET_OK != - GNUNET_CONTAINER_multihashmap_put (tunnels, &hash, t, - GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_FAST)) - { - tunnel_destroy (t); - GNUNET_break (0); - return GNUNET_OK; - } - tunnel_reset_timeout (t); - GNUNET_CRYPTO_hash (&t->local_tid_dest, sizeof (MESH_TunnelNumber), &hash); - if (GNUNET_OK != - GNUNET_CONTAINER_multihashmap_put (incoming_tunnels, &hash, t, - GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_FAST)) - { - tunnel_destroy (t); - GNUNET_break (0); - return GNUNET_OK; - } + /* already seen this packet, drop */ + GNUNET_STATISTICS_update (stats, "# duplicate PID drops BCK", 1, GNUNET_NO); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " Already seen pid %u, DROPPING!\n", pid); + tunnel_send_bck_ack (t, GNUNET_MESSAGE_TYPE_MESH_ACK); + return GNUNET_OK; } - dest_peer_info = - GNUNET_CONTAINER_multihashmap_get (peers, &pi[size - 1].hashPubKey); - if (NULL == dest_peer_info) + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " pid %u not seen yet, forwarding\n", pid); + cinfo->bck_pid = pid; + + if (NULL != t->owner) { + char cbuf[size]; + struct GNUNET_MESH_ToOrigin *copy; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - " Creating PeerInfo for destination.\n"); - dest_peer_info = GNUNET_malloc (sizeof (struct MeshPeerInfo)); - dest_peer_info->id = GNUNET_PEER_intern (&pi[size - 1]); - GNUNET_CONTAINER_multihashmap_put (peers, &pi[size - 1].hashPubKey, - dest_peer_info, - GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY); + " it's for us! sending to clients...\n"); + /* TODO signature verification */ + memcpy (cbuf, message, size); + copy = (struct GNUNET_MESH_ToOrigin *) cbuf; + copy->tid = htonl (t->local_tid); + t->bck_pid++; + copy->pid = htonl (t->bck_pid); + GNUNET_STATISTICS_update (stats, "# to origin received", 1, GNUNET_NO); + GNUNET_SERVER_notification_context_unicast (nc, t->owner->handle, + ©->header, GNUNET_NO); + tunnel_send_bck_ack (t, GNUNET_MESSAGE_TYPE_MESH_TO_ORIGIN); + return GNUNET_OK; } - orig_peer_info = GNUNET_CONTAINER_multihashmap_get (peers, &pi->hashPubKey); - if (NULL == orig_peer_info) + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " not for us, retransmitting...\n"); + + peer_info = peer_info_get (&msg->oid); + if (NULL == peer_info) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - " Creating PeerInfo for origin.\n"); - orig_peer_info = GNUNET_malloc (sizeof (struct MeshPeerInfo)); - orig_peer_info->id = GNUNET_PEER_intern (pi); - GNUNET_CONTAINER_multihashmap_put (peers, &pi->hashPubKey, orig_peer_info, - GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY); + /* unknown origin of tunnel */ + GNUNET_break (0); + return GNUNET_OK; } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " Creating path...\n"); - path = path_new (size); - own_pos = 0; - for (i = 0; i < size; i++) + predecessor = tree_get_predecessor (t->tree); + if (0 == predecessor) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " ... adding %s\n", - GNUNET_i2s (&pi[i])); - path->peers[i] = GNUNET_PEER_intern (&pi[i]); - if (path->peers[i] == myid) - own_pos = i; + if (GNUNET_YES == t->destroy) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "to orig received on a dying tunnel %s [%X]\n", + GNUNET_i2s (&msg->oid), ntohl(msg->tid)); + return GNUNET_OK; + } + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "unknown to origin at %s\n", + GNUNET_i2s (&my_full_id)); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "from peer %s\n", + GNUNET_i2s (peer)); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "for tunnel %s [%X]\n", + GNUNET_i2s (&msg->oid), ntohl(msg->tid)); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "current tree:\n"); + tree_debug (t->tree); + return GNUNET_OK; } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " Own position: %u\n", own_pos); - if (own_pos == 0) + GNUNET_PEER_resolve (predecessor, &id); + send_prebuilt_message (message, &id, t); + GNUNET_STATISTICS_update (stats, "# to origin forwarded", 1, GNUNET_NO); + + return GNUNET_OK; +} + + +/** + * Core handler for mesh network traffic point-to-point acks. + * + * @param cls closure + * @param message message + * @param peer peer identity this notification is about + * @param atsi performance data + * @param atsi_count number of records in 'atsi' + * + * @return GNUNET_OK to keep the connection open, + * GNUNET_SYSERR to close it (signal serious error) + */ +static int +handle_mesh_ack (void *cls, const struct GNUNET_PeerIdentity *peer, + const struct GNUNET_MessageHeader *message, + const struct GNUNET_ATS_Information *atsi, + unsigned int atsi_count) +{ + struct GNUNET_MESH_ACK *msg; + struct MeshTunnel *t; + uint32_t ack; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Got an ACK packet from %s!\n", + GNUNET_i2s (peer)); + msg = (struct GNUNET_MESH_ACK *) message; + + t = tunnel_get (&msg->oid, ntohl (msg->tid)); + + if (NULL == t) { - /* cannot be self, must be 'not found' */ - /* create path: self not found in path through self */ - GNUNET_break_op (0); - path_destroy (path); - /* FIXME error. destroy tunnel? leave for timeout? */ - return 0; + /* TODO notify that we dont know this tunnel (whom)? */ + GNUNET_STATISTICS_update (stats, "# ack on unknown tunnel", 1, GNUNET_NO); + return GNUNET_OK; } - path_add_to_peers (path, GNUNET_NO); - tunnel_add_path (t, path, own_pos); - if (own_pos == size - 1) + ack = ntohl (msg->pid); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " ACK %u\n", ack); + + /* Is this a forward or backward ACK? */ + if (tree_get_predecessor(t->tree) != GNUNET_PEER_search(peer)) { - /* It is for us! Send ack. */ - struct MeshTransmissionDescriptor *info; - unsigned int j; + struct MeshTunnelChildInfo *cinfo; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " It's for us!\n"); - peer_info_add_path_to_origin (orig_peer_info, path, GNUNET_NO); - if (NULL == t->peers) + debug_bck_ack++; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " FWD ACK\n"); + cinfo = tunnel_get_neighbor_fc (t, peer); + cinfo->fwd_ack = ack; + tunnel_send_fwd_ack (t, GNUNET_MESSAGE_TYPE_MESH_ACK); + tunnel_unlock_fwd_queues (t); + if (GNUNET_SCHEDULER_NO_TASK != cinfo->fc_poll) { - /* New tunnel! Notify clients on data. */ - t->peers = GNUNET_CONTAINER_multihashmap_create (4); - } - GNUNET_break (GNUNET_OK == - GNUNET_CONTAINER_multihashmap_put (t->peers, - &my_full_id.hashPubKey, - peer_info_get - (&my_full_id), - GNUNET_CONTAINER_MULTIHASHMAPOPTION_REPLACE)); - /* FIXME use send_message */ - info = GNUNET_malloc (sizeof (struct MeshTransmissionDescriptor)); - info->origin = &t->id; - info->peer = GNUNET_CONTAINER_multihashmap_get (peers, &peer->hashPubKey); - GNUNET_assert (NULL != info->peer); - j = peer_info_transmit_slot (info->peer); - info->handler_n = j; - info->peer->types[j] = GNUNET_MESSAGE_TYPE_MESH_PATH_ACK; - info->peer->infos[j] = info; - info->peer->core_transmit[j] = - GNUNET_CORE_notify_transmit_ready (core_handle, 0, 10, - GNUNET_TIME_UNIT_FOREVER_REL, peer, - sizeof (struct GNUNET_MESH_PathACK), - &send_core_path_ack, info); + GNUNET_SCHEDULER_cancel (cinfo->fc_poll); + cinfo->fc_poll = GNUNET_SCHEDULER_NO_TASK; + cinfo->fc_poll_time = GNUNET_TIME_UNIT_SECONDS; + } } else { - struct MeshPeerPath *path2; - - /* It's for somebody else! Retransmit. */ - path2 = path_duplicate (path); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " Retransmitting.\n"); - peer_info_add_path (dest_peer_info, path2, GNUNET_NO); - path2 = path_duplicate (path); - peer_info_add_path_to_origin (orig_peer_info, path2, GNUNET_NO); - send_create_path (dest_peer_info, path, t); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " BCK ACK\n"); + t->bck_ack = ack; + tunnel_send_bck_ack (t, GNUNET_MESSAGE_TYPE_MESH_ACK); + tunnel_unlock_bck_queue (t); } return GNUNET_OK; } /** - * Core handler for path destruction + * Core handler for mesh network traffic point-to-point ack polls. * * @param cls closure * @param message message @@ -3016,892 +5863,1109 @@ handle_mesh_path_create (void *cls, const struct GNUNET_PeerIdentity *peer, * GNUNET_SYSERR to close it (signal serious error) */ static int -handle_mesh_path_destroy (void *cls, const struct GNUNET_PeerIdentity *peer, - const struct GNUNET_MessageHeader *message, - const struct GNUNET_ATS_Information *atsi, - unsigned int atsi_count) +handle_mesh_poll (void *cls, const struct GNUNET_PeerIdentity *peer, + const struct GNUNET_MessageHeader *message, + const struct GNUNET_ATS_Information *atsi, + unsigned int atsi_count) { - struct GNUNET_MESH_ManipulatePath *msg; - struct GNUNET_PeerIdentity *pi; - struct MeshPeerPath *path; + struct GNUNET_MESH_Poll *msg; struct MeshTunnel *t; - unsigned int own_pos; - unsigned int i; - size_t size; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Received a PATH DESTROY msg from %s\n", GNUNET_i2s (peer)); - size = ntohs (message->size); - if (size < sizeof (struct GNUNET_MESH_ManipulatePath)) + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Got an POLL packet from %s!\n", + GNUNET_i2s (peer)); + + msg = (struct GNUNET_MESH_Poll *) message; + + t = tunnel_get (&msg->oid, ntohl (msg->tid)); + + if (NULL == t) { + /* TODO notify that we dont know this tunnel (whom)? */ + GNUNET_STATISTICS_update (stats, "# poll on unknown tunnel", 1, GNUNET_NO); GNUNET_break_op (0); return GNUNET_OK; } - size -= sizeof (struct GNUNET_MESH_ManipulatePath); - if (size % sizeof (struct GNUNET_PeerIdentity)) + /* Is this a forward or backward ACK? */ + if (tree_get_predecessor(t->tree) != GNUNET_PEER_search(peer)) { - GNUNET_break_op (0); - return GNUNET_OK; + struct MeshTunnelChildInfo *cinfo; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " from FWD\n"); + cinfo = tunnel_get_neighbor_fc (t, peer); + cinfo->bck_ack = cinfo->fwd_pid; // mark as ready to send + tunnel_send_bck_ack (t, GNUNET_MESSAGE_TYPE_MESH_POLL); } - size /= sizeof (struct GNUNET_PeerIdentity); - if (size < 2) + else { - GNUNET_break_op (0); - return GNUNET_OK; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " from BCK\n"); + tunnel_send_fwd_ack (t, GNUNET_MESSAGE_TYPE_MESH_POLL); } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " path has %u hops.\n", size); - msg = (struct GNUNET_MESH_ManipulatePath *) message; - pi = (struct GNUNET_PeerIdentity *) &msg[1]; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - " path is for tunnel %s [%X].\n", GNUNET_i2s (pi), - msg->tid); - t = tunnel_get (pi, ntohl (msg->tid)); + return GNUNET_OK; +} + +/** + * Core handler for path ACKs + * + * @param cls closure + * @param message message + * @param peer peer identity this notification is about + * @param atsi performance data + * @param atsi_count number of records in 'atsi' + * + * @return GNUNET_OK to keep the connection open, + * GNUNET_SYSERR to close it (signal serious error) + */ +static int +handle_mesh_path_ack (void *cls, const struct GNUNET_PeerIdentity *peer, + const struct GNUNET_MessageHeader *message, + const struct GNUNET_ATS_Information *atsi, + unsigned int atsi_count) +{ + struct GNUNET_MESH_PathACK *msg; + struct GNUNET_PeerIdentity id; + struct MeshPeerInfo *peer_info; + struct MeshPeerPath *p; + struct MeshTunnel *t; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received a path ACK msg [%s]\n", + GNUNET_i2s (&my_full_id)); + msg = (struct GNUNET_MESH_PathACK *) message; + t = tunnel_get (&msg->oid, ntohl(msg->tid)); if (NULL == t) { - /* TODO notify back: we don't know this tunnel */ - GNUNET_break_op (0); + /* TODO notify that we don't know the tunnel */ + GNUNET_STATISTICS_update (stats, "# control on unknown tunnel", 1, GNUNET_NO); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " don't know the tunnel %s [%X]!\n", + GNUNET_i2s (&msg->oid), ntohl(msg->tid)); return GNUNET_OK; } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " Creating path...\n"); - path = path_new (size); - own_pos = 0; - for (i = 0; i < size; i++) + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " on tunnel %s [%X]\n", + GNUNET_i2s (&msg->oid), ntohl(msg->tid)); + + peer_info = peer_info_get (&msg->peer_id); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " by peer %s\n", + GNUNET_i2s (&msg->peer_id)); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " via peer %s\n", + GNUNET_i2s (peer)); + + if (NULL != t->regex_search && t->regex_search->peer == peer_info->id) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " ... adding %s\n", - GNUNET_i2s (&pi[i])); - path->peers[i] = GNUNET_PEER_intern (&pi[i]); - if (path->peers[i] == myid) - own_pos = i; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "connect_by_string completed, stopping search\n"); + regex_cancel_search (t->regex_search); + t->regex_search = NULL; + } + + /* Add paths to peers? */ + p = tree_get_path_to_peer (t->tree, peer_info->id); + if (NULL != p) + { + path_add_to_peers (p, GNUNET_YES); + path_destroy (p); } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " Own position: %u\n", own_pos); - if (own_pos < path->length - 1) - send_message (message, &pi[own_pos + 1]); else - send_client_tunnel_disconnect(t, NULL); + { + GNUNET_break (0); + } - tunnel_delete_peer (t, path->peers[path->length - 1]); - path_destroy (path); + /* Message for us? */ + if (0 == memcmp (&msg->oid, &my_full_id, sizeof (struct GNUNET_PeerIdentity))) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " It's for us!\n"); + if (NULL == t->owner) + { + GNUNET_break_op (0); + return GNUNET_OK; + } + if (NULL != t->dht_get_type) + { + GNUNET_DHT_get_stop (t->dht_get_type); + t->dht_get_type = NULL; + } + if (tree_get_status (t->tree, peer_info->id) != MESH_PEER_READY) + { + tree_set_status (t->tree, peer_info->id, MESH_PEER_READY); + send_client_peer_connected (t, peer_info->id); + } + return GNUNET_OK; + } + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " not for us, retransmitting...\n"); + GNUNET_PEER_resolve (tree_get_predecessor (t->tree), &id); + peer_info = peer_info_get (&msg->oid); + if (NULL == peer_info) + { + /* If we know the tunnel, we should DEFINITELY know the peer */ + GNUNET_break (0); + return GNUNET_OK; + } + send_prebuilt_message (message, &id, t); return GNUNET_OK; } /** - * Core handler for notifications of broken paths + * Core handler for mesh keepalives. * * @param cls closure * @param message message * @param peer peer identity this notification is about * @param atsi performance data * @param atsi_count number of records in 'atsi' - * * @return GNUNET_OK to keep the connection open, * GNUNET_SYSERR to close it (signal serious error) + * + * TODO: Check who we got this from, to validate route. */ static int -handle_mesh_path_broken (void *cls, const struct GNUNET_PeerIdentity *peer, - const struct GNUNET_MessageHeader *message, - const struct GNUNET_ATS_Information *atsi, - unsigned int atsi_count) +handle_mesh_keepalive (void *cls, const struct GNUNET_PeerIdentity *peer, + const struct GNUNET_MessageHeader *message, + const struct GNUNET_ATS_Information *atsi, + unsigned int atsi_count) { - struct GNUNET_MESH_PathBroken *msg; + struct GNUNET_MESH_TunnelKeepAlive *msg; struct MeshTunnel *t; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Received a PATH BROKEN msg from %s\n", GNUNET_i2s (peer)); - msg = (struct GNUNET_MESH_PathBroken *) message; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " regarding %s\n", - GNUNET_i2s (&msg->peer1)); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " regarding %s\n", - GNUNET_i2s (&msg->peer2)); - t = tunnel_get (&msg->oid, ntohl (msg->tid)); - if (NULL == t) + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "got a keepalive packet from %s\n", + GNUNET_i2s (peer)); + + msg = (struct GNUNET_MESH_TunnelKeepAlive *) message; + t = tunnel_get (&msg->oid, ntohl (msg->tid)); + + if (NULL == t) + { + /* TODO notify that we dont know that tunnel */ + GNUNET_STATISTICS_update (stats, "# keepalive on unknown tunnel", 1, + GNUNET_NO); + return GNUNET_OK; + } + + tunnel_reset_timeout (t); + + GNUNET_STATISTICS_update (stats, "# keepalives forwarded", 1, GNUNET_NO); + tunnel_send_multicast (t, message); + return GNUNET_OK; + } + + + +/** + * Functions to handle messages from core + */ +static struct GNUNET_CORE_MessageHandler core_handlers[] = { + {&handle_mesh_path_create, GNUNET_MESSAGE_TYPE_MESH_PATH_CREATE, 0}, + {&handle_mesh_path_destroy, GNUNET_MESSAGE_TYPE_MESH_PATH_DESTROY, 0}, + {&handle_mesh_path_broken, GNUNET_MESSAGE_TYPE_MESH_PATH_BROKEN, + sizeof (struct GNUNET_MESH_PathBroken)}, + {&handle_mesh_tunnel_destroy, GNUNET_MESSAGE_TYPE_MESH_TUNNEL_DESTROY, + sizeof (struct GNUNET_MESH_TunnelDestroy)}, + {&handle_mesh_data_unicast, GNUNET_MESSAGE_TYPE_MESH_UNICAST, 0}, + {&handle_mesh_data_multicast, GNUNET_MESSAGE_TYPE_MESH_MULTICAST, 0}, + {&handle_mesh_keepalive, GNUNET_MESSAGE_TYPE_MESH_PATH_KEEPALIVE, + sizeof (struct GNUNET_MESH_TunnelKeepAlive)}, + {&handle_mesh_data_to_orig, GNUNET_MESSAGE_TYPE_MESH_TO_ORIGIN, 0}, + {&handle_mesh_ack, GNUNET_MESSAGE_TYPE_MESH_ACK, + sizeof (struct GNUNET_MESH_ACK)}, + {&handle_mesh_poll, GNUNET_MESSAGE_TYPE_MESH_POLL, + sizeof (struct GNUNET_MESH_Poll)}, + {&handle_mesh_path_ack, GNUNET_MESSAGE_TYPE_MESH_PATH_ACK, + sizeof (struct GNUNET_MESH_PathACK)}, + {NULL, 0, 0} +}; + + + +/******************************************************************************/ +/**************** MESH LOCAL HANDLER HELPERS ***********************/ +/******************************************************************************/ + +/** + * deregister_app: iterator for removing each application registered by a client + * + * @param cls closure + * @param key the hash of the application id (used to access the hashmap) + * @param value the value stored at the key (client) + * + * @return GNUNET_OK on success + */ +static int +deregister_app (void *cls, const struct GNUNET_HashCode * key, void *value) +{ + struct GNUNET_CONTAINER_MultiHashMap *h = cls; + GNUNET_break (GNUNET_YES == + GNUNET_CONTAINER_multihashmap_remove (h, key, value)); + return GNUNET_OK; +} + +#if LATER +/** + * notify_client_connection_failure: notify a client that the connection to the + * requested remote peer is not possible (for instance, no route found) + * Function called when the socket is ready to queue more data. "buf" will be + * NULL and "size" zero if the socket was closed for writing in the meantime. + * + * @param cls closure + * @param size number of bytes available in buf + * @param buf where the callee should write the message + * @return number of bytes written to buf + */ +static size_t +notify_client_connection_failure (void *cls, size_t size, void *buf) +{ + int size_needed; + struct MeshPeerInfo *peer_info; + struct GNUNET_MESH_PeerControl *msg; + struct GNUNET_PeerIdentity id; + + if (0 == size && NULL == buf) + { + // TODO retry? cancel? + return 0; + } + + size_needed = sizeof (struct GNUNET_MESH_PeerControl); + peer_info = (struct MeshPeerInfo *) cls; + msg = (struct GNUNET_MESH_PeerControl *) buf; + msg->header.size = htons (sizeof (struct GNUNET_MESH_PeerControl)); + msg->header.type = htons (GNUNET_MESSAGE_TYPE_MESH_LOCAL_PEER_DISCONNECTED); +// msg->tunnel_id = htonl(peer_info->t->tid); + GNUNET_PEER_resolve (peer_info->id, &id); + memcpy (&msg->peer, &id, sizeof (struct GNUNET_PeerIdentity)); + + return size_needed; +} +#endif + + +/** + * Send keepalive packets for a peer + * + * @param cls Closure (tunnel for which to send the keepalive). + * @param tc Notification context. + */ +static void +path_refresh (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct MeshTunnel *t = cls; + struct GNUNET_MESH_TunnelKeepAlive *msg; + size_t size = sizeof (struct GNUNET_MESH_TunnelKeepAlive); + char cbuf[size]; + + t->path_refresh_task = GNUNET_SCHEDULER_NO_TASK; + if (0 != (tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN)) { - GNUNET_break_op (0); - return GNUNET_OK; + return; } - tunnel_notify_connection_broken (t, GNUNET_PEER_search (&msg->peer1), - GNUNET_PEER_search (&msg->peer2)); - return GNUNET_OK; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "sending keepalive for tunnel %d\n", t->id.tid); + + msg = (struct GNUNET_MESH_TunnelKeepAlive *) cbuf; + msg->header.size = htons (size); + msg->header.type = htons (GNUNET_MESSAGE_TYPE_MESH_PATH_KEEPALIVE); + msg->oid = my_full_id; + msg->tid = htonl (t->id.tid); + tunnel_send_multicast (t, &msg->header); + + t->path_refresh_task = + GNUNET_SCHEDULER_add_delayed (refresh_path_time, &path_refresh, t); + tunnel_reset_timeout(t); } /** - * Core handler for tunnel destruction + * Function to process paths received for a new peer addition. The recorded + * paths form the initial tunnel, which can be optimized later. + * Called on each result obtained for the DHT search. * * @param cls closure - * @param message message - * @param peer peer identity this notification is about - * @param atsi performance data - * @param atsi_count number of records in 'atsi' + * @param exp when will this value expire + * @param key key of the result + * @param get_path path of the get request + * @param get_path_length lenght of get_path + * @param put_path path of the put request + * @param put_path_length length of the put_path + * @param type type of the result + * @param size number of bytes in data + * @param data pointer to the result data * - * @return GNUNET_OK to keep the connection open, - * GNUNET_SYSERR to close it (signal serious error) + * TODO: re-issue the request after certain time? cancel after X results? */ -static int -handle_mesh_tunnel_destroy (void *cls, const struct GNUNET_PeerIdentity *peer, - const struct GNUNET_MessageHeader *message, - const struct GNUNET_ATS_Information *atsi, - unsigned int atsi_count) +static void +dht_get_id_handler (void *cls, struct GNUNET_TIME_Absolute exp, + const struct GNUNET_HashCode * key, + const struct GNUNET_PeerIdentity *get_path, + unsigned int get_path_length, + const struct GNUNET_PeerIdentity *put_path, + unsigned int put_path_length, enum GNUNET_BLOCK_Type type, + size_t size, const void *data) { - struct GNUNET_MESH_TunnelDestroy *msg; - struct MeshTunnel *t; + struct MeshPathInfo *path_info = cls; + struct MeshPeerPath *p; + struct GNUNET_PeerIdentity pi; + int i; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Got a TUNNEL DESTROY packet from %s\n", GNUNET_i2s (peer)); - msg = (struct GNUNET_MESH_TunnelDestroy *) message; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " for tunnel %s [%u]\n", - GNUNET_i2s (&msg->oid), ntohl (msg->tid)); - t = tunnel_get (&msg->oid, ntohl (msg->tid)); - if (NULL == t) - { - /* Probably already got the message from another path, - * destroyed the tunnel and retransmitted to children. - * Safe to ignore. - */ - return GNUNET_OK; - } - if (t->id.oid == myid) - { - GNUNET_break_op (0); - return GNUNET_OK; - } - if (t->local_tid_dest >= GNUNET_MESH_LOCAL_TUNNEL_ID_SERV) + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Got results from DHT!\n"); + GNUNET_PEER_resolve (path_info->peer->id, &pi); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " for %s\n", GNUNET_i2s (&pi)); + + p = path_build_from_dht (get_path, get_path_length, put_path, + put_path_length); + path_add_to_peers (p, GNUNET_NO); + path_destroy(p); + for (i = 0; i < path_info->peer->ntunnels; i++) { - /* Tunnel was incoming, notify clients */ - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "INCOMING TUNNEL %X %X\n", - t->local_tid, t->local_tid_dest); - send_clients_tunnel_destroy (t); + tunnel_add_peer (path_info->peer->tunnels[i], path_info->peer); + peer_info_connect (path_info->peer, path_info->t); } - tunnel_send_destroy (t); - tunnel_destroy (t); - return GNUNET_OK; + + return; } /** - * Core handler for mesh network traffic going from the origin to a peer + * Function to process paths received for a new peer addition. The recorded + * paths form the initial tunnel, which can be optimized later. + * Called on each result obtained for the DHT search. * * @param cls closure - * @param peer peer identity this notification is about - * @param message message - * @param atsi performance data - * @param atsi_count number of records in 'atsi' - * @return GNUNET_OK to keep the connection open, - * GNUNET_SYSERR to close it (signal serious error) + * @param exp when will this value expire + * @param key key of the result + * @param get_path path of the get request + * @param get_path_length lenght of get_path + * @param put_path path of the put request + * @param put_path_length length of the put_path + * @param type type of the result + * @param size number of bytes in data + * @param data pointer to the result data */ -static int -handle_mesh_data_unicast (void *cls, const struct GNUNET_PeerIdentity *peer, - const struct GNUNET_MessageHeader *message, - const struct GNUNET_ATS_Information *atsi, - unsigned int atsi_count) +static void +dht_get_type_handler (void *cls, struct GNUNET_TIME_Absolute exp, + const struct GNUNET_HashCode * key, + const struct GNUNET_PeerIdentity *get_path, + unsigned int get_path_length, + const struct GNUNET_PeerIdentity *put_path, + unsigned int put_path_length, enum GNUNET_BLOCK_Type type, + size_t size, const void *data) { - struct GNUNET_MESH_Unicast *msg; - struct MeshTunnel *t; - GNUNET_PEER_Id pid; - size_t size; + const struct PBlock *pb = data; + const struct GNUNET_PeerIdentity *pi = &pb->id; + struct MeshTunnel *t = cls; + struct MeshPeerInfo *peer_info; + struct MeshPeerPath *p; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "got a unicast packet from %s\n", - GNUNET_i2s (peer)); - size = ntohs (message->size); - if (size < - sizeof (struct GNUNET_MESH_Unicast) + - sizeof (struct GNUNET_MessageHeader)) - { - GNUNET_break (0); - return GNUNET_OK; - } - msg = (struct GNUNET_MESH_Unicast *) message; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " of type %u\n", - ntohs (msg[1].header.type)); - t = tunnel_get (&msg->oid, ntohl (msg->tid)); - if (NULL == t) + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "got type DHT result!\n"); + if (size != sizeof (struct PBlock)) { - /* TODO notify back: we don't know this tunnel */ GNUNET_break_op (0); - return GNUNET_OK; + return; } - tunnel_reset_timeout (t); - pid = GNUNET_PEER_search (&msg->destination); - if (pid == myid) + if (ntohl(pb->type) != t->type) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - " it's for us! sending to clients...\n"); - send_subscribed_clients (message, (struct GNUNET_MessageHeader *) &msg[1]); - return GNUNET_OK; + GNUNET_break_op (0); + return; } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - " not for us, retransmitting...\n"); - send_message (message, tree_get_first_hop (t->tree, pid)); - return GNUNET_OK; + GNUNET_assert (NULL != t->owner); + peer_info = peer_info_get (pi); + (void) GNUNET_CONTAINER_multihashmap_put (t->peers, &pi->hashPubKey, + peer_info, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_REPLACE); + + p = path_build_from_dht (get_path, get_path_length, put_path, + put_path_length); + path_add_to_peers (p, GNUNET_NO); + path_destroy(p); + tunnel_add_peer (t, peer_info); + peer_info_connect (peer_info, t); } +/******************************************************************************/ +/********************* MESH LOCAL HANDLES **************************/ +/******************************************************************************/ + + /** - * Core handler for mesh network traffic going from the origin to all peers + * Handler for client disconnection * * @param cls closure - * @param message message - * @param peer peer identity this notification is about - * @param atsi performance data - * @param atsi_count number of records in 'atsi' - * @return GNUNET_OK to keep the connection open, - * GNUNET_SYSERR to close it (signal serious error) - * - * TODO: Check who we got this from, to validate route. + * @param client identification of the client; NULL + * for the last call when the server is destroyed */ -static int -handle_mesh_data_multicast (void *cls, const struct GNUNET_PeerIdentity *peer, - const struct GNUNET_MessageHeader *message, - const struct GNUNET_ATS_Information *atsi, - unsigned int atsi_count) +static void +handle_local_client_disconnect (void *cls, struct GNUNET_SERVER_Client *client) { - struct GNUNET_MESH_Multicast *msg; - struct MeshTunnel *t; - size_t size; + struct MeshClient *c; + struct MeshClient *next; + unsigned int i; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "got a multicast packet from %s\n", - GNUNET_i2s (peer)); - size = ntohs (message->size); - if (sizeof (struct GNUNET_MESH_Multicast) + - sizeof (struct GNUNET_MessageHeader) > size) + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "client disconnected\n"); + if (client == NULL) { - GNUNET_break_op (0); - return GNUNET_OK; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " (SERVER DOWN)\n"); + return; } - msg = (struct GNUNET_MESH_Multicast *) message; - t = tunnel_get (&msg->oid, ntohl (msg->tid)); - if (NULL == t) - { - /* TODO notify that we dont know that tunnel */ - GNUNET_break_op (0); - return GNUNET_OK; - } - if (t->mid == ntohl (msg->mid)) - { - /* FIXME: already seen this packet, log dropping */ - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - " Already seen mid %u, DROPPING!\n", t->mid); - return GNUNET_OK; - } - else + c = clients; + while (NULL != c) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - " mid %u not seen yet, forwarding\n", ntohl (msg->mid)); - } - t->mid = ntohl (msg->mid); - tunnel_reset_timeout (t); + if (c->handle != client) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " ... searching\n"); + c = c->next; + continue; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "matching client found (%u)\n", + c->id); + GNUNET_SERVER_client_drop (c->handle); + c->shutting_down = GNUNET_YES; + GNUNET_assert (NULL != c->own_tunnels); + GNUNET_assert (NULL != c->incoming_tunnels); + GNUNET_CONTAINER_multihashmap_iterate (c->own_tunnels, + &tunnel_destroy_iterator, c); + GNUNET_CONTAINER_multihashmap_iterate (c->incoming_tunnels, + &tunnel_destroy_iterator, c); + GNUNET_CONTAINER_multihashmap_iterate (c->ignore_tunnels, + &tunnel_destroy_iterator, c); + GNUNET_CONTAINER_multihashmap_destroy (c->own_tunnels); + GNUNET_CONTAINER_multihashmap_destroy (c->incoming_tunnels); + GNUNET_CONTAINER_multihashmap_destroy (c->ignore_tunnels); - /* Transmit to locally interested clients */ - if (NULL != t->peers && - GNUNET_CONTAINER_multihashmap_contains (t->peers, &my_full_id.hashPubKey)) - { - send_subscribed_clients (message, &msg[1].header); - } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " ttl: %u\n", ntohl (msg->ttl)); - if (ntohl (msg->ttl) == 0) - { - /* FIXME: ttl is 0, log dropping */ - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, " TTL is 0, DROPPING!\n"); - return GNUNET_OK; + /* deregister clients applications */ + if (NULL != c->apps) + { + GNUNET_CONTAINER_multihashmap_iterate (c->apps, &deregister_app, c->apps); + GNUNET_CONTAINER_multihashmap_destroy (c->apps); + } + if (0 == GNUNET_CONTAINER_multihashmap_size (applications) && + GNUNET_SCHEDULER_NO_TASK != announce_applications_task) + { + GNUNET_SCHEDULER_cancel (announce_applications_task); + announce_applications_task = GNUNET_SCHEDULER_NO_TASK; + } + if (NULL != c->types) + GNUNET_CONTAINER_multihashmap_destroy (c->types); + for (i = 0; i < c->n_regex; i++) + { + GNUNET_free (c->regexes[i].regex); + if (NULL != c->regexes[i].h) + GNUNET_REGEX_announce_cancel (c->regexes[i].h); + } + GNUNET_free_non_null (c->regexes); + if (GNUNET_SCHEDULER_NO_TASK != c->regex_announce_task) + GNUNET_SCHEDULER_cancel (c->regex_announce_task); + next = c->next; + GNUNET_CONTAINER_DLL_remove (clients, clients_tail, c); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " CLIENT FREE at %p\n", c); + GNUNET_free (c); + GNUNET_STATISTICS_update (stats, "# clients", -1, GNUNET_NO); + c = next; } - tunnel_send_multicast (t, message, GNUNET_NO); - return GNUNET_OK; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " done!\n"); + return; } /** - * Core handler for mesh network traffic toward the owner of a tunnel + * Handler for new clients * * @param cls closure - * @param message message - * @param peer peer identity this notification is about - * @param atsi performance data - * @param atsi_count number of records in 'atsi' - * - * @return GNUNET_OK to keep the connection open, - * GNUNET_SYSERR to close it (signal serious error) + * @param client identification of the client + * @param message the actual message, which includes messages the client wants */ -static int -handle_mesh_data_to_orig (void *cls, const struct GNUNET_PeerIdentity *peer, - const struct GNUNET_MessageHeader *message, - const struct GNUNET_ATS_Information *atsi, - unsigned int atsi_count) +static void +handle_local_new_client (void *cls, struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) { - struct GNUNET_MESH_ToOrigin *msg; - struct GNUNET_PeerIdentity id; - struct MeshPeerInfo *peer_info; - struct MeshTunnel *t; - size_t size; + struct GNUNET_MESH_ClientConnect *cc_msg; + struct MeshClient *c; + GNUNET_MESH_ApplicationType *a; + unsigned int size; + uint16_t ntypes; + uint16_t *t; + uint16_t napps; + uint16_t i; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "got a ToOrigin packet from %s\n", - GNUNET_i2s (peer)); - size = ntohs (message->size); - if (size < sizeof (struct GNUNET_MESH_ToOrigin) + /* Payload must be */ - sizeof (struct GNUNET_MessageHeader)) /* at least a header */ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "new client connected\n"); + /* Check data sanity */ + size = ntohs (message->size) - sizeof (struct GNUNET_MESH_ClientConnect); + cc_msg = (struct GNUNET_MESH_ClientConnect *) message; + ntypes = ntohs (cc_msg->types); + napps = ntohs (cc_msg->applications); + if (size != + ntypes * sizeof (uint16_t) + napps * sizeof (GNUNET_MESH_ApplicationType)) { - GNUNET_break_op (0); - return GNUNET_OK; + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; } - msg = (struct GNUNET_MESH_ToOrigin *) message; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " of type %u\n", - ntohs (msg[1].header.type)); - t = tunnel_get (&msg->oid, ntohl (msg->tid)); - if (NULL == t) + /* Create new client structure */ + c = GNUNET_malloc (sizeof (struct MeshClient)); + c->id = next_client_id++; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " CLIENT NEW %u\n", c->id); + c->handle = client; + GNUNET_SERVER_client_keep (client); + a = (GNUNET_MESH_ApplicationType *) &cc_msg[1]; + if (napps > 0) { - /* TODO notify that we dont know this tunnel (whom)? */ - GNUNET_break_op (0); - return GNUNET_OK; - } + GNUNET_MESH_ApplicationType at; + struct GNUNET_HashCode hc; + + c->apps = GNUNET_CONTAINER_multihashmap_create (napps, GNUNET_NO); + for (i = 0; i < napps; i++) + { + at = ntohl (a[i]); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " app type: %u\n", at); + GNUNET_CRYPTO_hash (&at, sizeof (at), &hc); + /* store in clients hashmap */ + GNUNET_CONTAINER_multihashmap_put (c->apps, &hc, (void *) (long) at, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE); + /* store in global hashmap, for announcements */ + GNUNET_CONTAINER_multihashmap_put (applications, &hc, c, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE); + } + if (GNUNET_SCHEDULER_NO_TASK == announce_applications_task) + announce_applications_task = + GNUNET_SCHEDULER_add_now (&announce_applications, NULL); - if (t->id.oid == myid) + } + if (ntypes > 0) { - char cbuf[size]; - struct GNUNET_MESH_ToOrigin *copy; + uint16_t u16; + struct GNUNET_HashCode hc; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - " it's for us! sending to clients...\n"); - if (NULL == t->owner) + t = (uint16_t *) & a[napps]; + c->types = GNUNET_CONTAINER_multihashmap_create (ntypes, GNUNET_NO); + for (i = 0; i < ntypes; i++) { - /* got data packet for ownerless tunnel */ - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " no clients!\n"); - GNUNET_break_op (0); - return GNUNET_OK; + u16 = ntohs (t[i]); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " msg type: %u\n", u16); + GNUNET_CRYPTO_hash (&u16, sizeof (u16), &hc); + + /* store in clients hashmap */ + GNUNET_CONTAINER_multihashmap_put (c->types, &hc, c, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE); + /* store in global hashmap */ + GNUNET_CONTAINER_multihashmap_put (types, &hc, c, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE); } - /* TODO signature verification */ - memcpy (cbuf, message, size); - copy = (struct GNUNET_MESH_ToOrigin *) cbuf; - copy->tid = htonl (t->local_tid); - GNUNET_SERVER_notification_context_unicast (nc, t->owner->handle, - ©->header, GNUNET_YES); - return GNUNET_OK; } GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - " not for us, retransmitting...\n"); + " client has %u+%u subscriptions\n", napps, ntypes); - peer_info = peer_info_get (&msg->oid); - if (NULL == peer_info) - { - /* unknown origin of tunnel */ - GNUNET_break (0); - return GNUNET_OK; - } - GNUNET_PEER_resolve (tree_get_predecessor (t->tree), &id); - send_message (message, &id); + GNUNET_CONTAINER_DLL_insert (clients, clients_tail, c); + c->own_tunnels = GNUNET_CONTAINER_multihashmap_create (32, GNUNET_NO); + c->incoming_tunnels = GNUNET_CONTAINER_multihashmap_create (32, GNUNET_NO); + c->ignore_tunnels = GNUNET_CONTAINER_multihashmap_create (32, GNUNET_NO); + GNUNET_SERVER_notification_context_add (nc, client); + GNUNET_STATISTICS_update (stats, "# clients", 1, GNUNET_NO); - return GNUNET_OK; + GNUNET_SERVER_receive_done (client, GNUNET_OK); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "new client processed\n"); } /** - * Core handler for path ACKs + * Handler for clients announcing available services by a regular expression. * * @param cls closure - * @param message message - * @param peer peer identity this notification is about - * @param atsi performance data - * @param atsi_count number of records in 'atsi' - * - * @return GNUNET_OK to keep the connection open, - * GNUNET_SYSERR to close it (signal serious error) + * @param client identification of the client + * @param message the actual message, which includes messages the client wants */ -static int -handle_mesh_path_ack (void *cls, const struct GNUNET_PeerIdentity *peer, - const struct GNUNET_MessageHeader *message, - const struct GNUNET_ATS_Information *atsi, - unsigned int atsi_count) +static void +handle_local_announce_regex (void *cls, struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) { - struct GNUNET_MESH_PathACK *msg; - struct GNUNET_PeerIdentity id; - struct MeshPeerInfo *peer_info; - struct MeshPeerPath *p; - struct MeshTunnel *t; + const struct GNUNET_MESH_RegexAnnounce *msg; + struct MeshRegexDescriptor rd; + struct MeshClient *c; + char *regex; + size_t len; + size_t offset; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received a path ACK msg [%s]\n", - GNUNET_i2s (&my_full_id)); - msg = (struct GNUNET_MESH_PathACK *) message; - t = tunnel_get (&msg->oid, msg->tid); - if (NULL == t) + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "announce regex started\n"); + + /* Sanity check for client registration */ + if (NULL == (c = client_get (client))) { - /* TODO notify that we don't know the tunnel */ - return GNUNET_OK; + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " by client %u\n", c->id); - peer_info = peer_info_get (&msg->peer_id); + msg = (const struct GNUNET_MESH_RegexAnnounce *) message; - /* Add paths to peers? */ - p = tree_get_path_to_peer (t->tree, peer_info->id); - if (NULL != p) + len = ntohs (message->size) - sizeof(struct GNUNET_MESH_RegexAnnounce); + if (NULL != c->partial_regex) { - path_add_to_peers (p, GNUNET_YES); - path_destroy (p); + regex = c->partial_regex; + offset = strlen (c->partial_regex); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " continuation, already have %u bytes\n", + offset); } else { - GNUNET_break (0); + regex = NULL; + offset = 0; } - /* Message for us? */ - if (0 == memcmp (&msg->oid, &my_full_id, sizeof (struct GNUNET_PeerIdentity))) + regex = GNUNET_realloc (regex, offset + len + 1); + memcpy (®ex[offset], &msg[1], len); + regex[offset + len] = '\0'; + if (0 == ntohs (msg->last)) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " It's for us!\n"); - if (NULL == t->owner) - { - GNUNET_break_op (0); - return GNUNET_OK; - } - if (NULL != t->dht_get_type) - { - GNUNET_DHT_get_stop (t->dht_get_type); - t->dht_get_type = NULL; - } - if (tree_get_status (t->tree, peer_info->id) != MESH_PEER_READY) - { - tree_set_status (t->tree, peer_info->id, MESH_PEER_READY); - send_client_peer_connected (t, peer_info->id); - } - return GNUNET_OK; + c->partial_regex = regex; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " not ended, stored %u bytes for later\n", + len); + GNUNET_SERVER_receive_done (client, GNUNET_OK); + return; + } + rd.regex = regex; + rd.compression = ntohs (msg->compression_characters); + rd.h = NULL; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " length %u\n", len); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " regex %s\n", regex); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " compr %u\n", ntohs (rd.compression)); + GNUNET_array_append (c->regexes, c->n_regex, rd); + c->partial_regex = NULL; + if (GNUNET_SCHEDULER_NO_TASK == c->regex_announce_task) + { + c->regex_announce_task = GNUNET_SCHEDULER_add_now (®ex_announce, c); + } + else + { + regex_put (&rd); + } + GNUNET_SERVER_receive_done (client, GNUNET_OK); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "announce regex processed\n"); +} + + +/** + * Handler for requests of new tunnels + * + * @param cls closure + * @param client identification of the client + * @param message the actual message + */ +static void +handle_local_tunnel_create (void *cls, struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) +{ + struct GNUNET_MESH_TunnelMessage *t_msg; + struct MeshTunnel *t; + struct MeshClient *c; + MESH_TunnelNumber tid; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "new tunnel requested\n"); + + /* Sanity check for client registration */ + if (NULL == (c = client_get (client))) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " by client %u\n", c->id); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - " not for us, retransmitting...\n"); - GNUNET_PEER_resolve (tree_get_predecessor (t->tree), &id); - peer_info = peer_info_get (&msg->oid); - if (NULL == peer_info) + /* Message sanity check */ + if (sizeof (struct GNUNET_MESH_TunnelMessage) != ntohs (message->size)) { - /* If we know the tunnel, we should DEFINITELY know the peer */ GNUNET_break (0); - return GNUNET_OK; + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; } - send_message (message, &id); - return GNUNET_OK; -} + t_msg = (struct GNUNET_MESH_TunnelMessage *) message; + /* Sanity check for tunnel numbering */ + tid = ntohl (t_msg->tunnel_id); + if (0 == (tid & GNUNET_MESH_LOCAL_TUNNEL_ID_CLI)) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + /* Sanity check for duplicate tunnel IDs */ + if (NULL != tunnel_get_by_local_id (c, tid)) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } -/** - * Functions to handle messages from core - */ -static struct GNUNET_CORE_MessageHandler core_handlers[] = { - {&handle_mesh_path_create, GNUNET_MESSAGE_TYPE_MESH_PATH_CREATE, 0}, - {&handle_mesh_path_destroy, GNUNET_MESSAGE_TYPE_MESH_PATH_DESTROY, 0}, - {&handle_mesh_path_broken, GNUNET_MESSAGE_TYPE_MESH_PATH_BROKEN, - sizeof (struct GNUNET_MESH_PathBroken)}, - {&handle_mesh_tunnel_destroy, GNUNET_MESSAGE_TYPE_MESH_TUNNEL_DESTROY, 0}, - {&handle_mesh_data_unicast, GNUNET_MESSAGE_TYPE_MESH_UNICAST, 0}, - {&handle_mesh_data_multicast, GNUNET_MESSAGE_TYPE_MESH_MULTICAST, 0}, - {&handle_mesh_data_to_orig, GNUNET_MESSAGE_TYPE_MESH_TO_ORIGIN, 0}, - {&handle_mesh_path_ack, GNUNET_MESSAGE_TYPE_MESH_PATH_ACK, - sizeof (struct GNUNET_MESH_PathACK)}, - {NULL, 0, 0} -}; - + while (NULL != tunnel_get_by_pi (myid, next_tid)) + next_tid = (next_tid + 1) & ~GNUNET_MESH_LOCAL_TUNNEL_ID_CLI; + t = tunnel_new (myid, next_tid++, c, tid); + if (NULL == t) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Tunnel creation failed.\n"); + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + next_tid = next_tid & ~GNUNET_MESH_LOCAL_TUNNEL_ID_CLI; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "CREATED TUNNEL %s [%x] (%x)\n", + GNUNET_i2s (&my_full_id), t->id.tid, t->local_tid); + t->peers = GNUNET_CONTAINER_multihashmap_create (32, GNUNET_NO); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "new tunnel created\n"); + GNUNET_SERVER_receive_done (client, GNUNET_OK); + return; +} -/******************************************************************************/ -/**************** MESH LOCAL HANDLER HELPERS ***********************/ -/******************************************************************************/ /** - * deregister_app: iterator for removing each application registered by a client + * Handler for requests of deleting tunnels * * @param cls closure - * @param key the hash of the application id (used to access the hashmap) - * @param value the value stored at the key (client) - * - * @return GNUNET_OK on success + * @param client identification of the client + * @param message the actual message */ -static int -deregister_app (void *cls, const GNUNET_HashCode * key, void *value) +static void +handle_local_tunnel_destroy (void *cls, struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) { - GNUNET_break (GNUNET_YES == - GNUNET_CONTAINER_multihashmap_remove (applications, key, - value)); - return GNUNET_OK; -} + struct GNUNET_MESH_TunnelMessage *tunnel_msg; + struct MeshClient *c; + struct MeshTunnel *t; + MESH_TunnelNumber tid; -#if LATER -/** - * notify_client_connection_failure: notify a client that the connection to the - * requested remote peer is not possible (for instance, no route found) - * Function called when the socket is ready to queue more data. "buf" will be - * NULL and "size" zero if the socket was closed for writing in the meantime. - * - * @param cls closure - * @param size number of bytes available in buf - * @param buf where the callee should write the message - * @return number of bytes written to buf - */ -static size_t -notify_client_connection_failure (void *cls, size_t size, void *buf) -{ - int size_needed; - struct MeshPeerInfo *peer_info; - struct GNUNET_MESH_PeerControl *msg; - struct GNUNET_PeerIdentity id; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Got a DESTROY TUNNEL from client!\n"); - if (0 == size && NULL == buf) + /* Sanity check for client registration */ + if (NULL == (c = client_get (client))) { - // TODO retry? cancel? - return 0; + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " by client %u\n", c->id); - size_needed = sizeof (struct GNUNET_MESH_PeerControl); - peer_info = (struct MeshPeerInfo *) cls; - msg = (struct GNUNET_MESH_PeerControl *) buf; - msg->header.size = htons (sizeof (struct GNUNET_MESH_PeerControl)); - msg->header.type = htons (GNUNET_MESSAGE_TYPE_MESH_LOCAL_PEER_DISCONNECTED); -// msg->tunnel_id = htonl(peer_info->t->tid); - GNUNET_PEER_resolve (peer_info->id, &id); - memcpy (&msg->peer, &id, sizeof (struct GNUNET_PeerIdentity)); + /* Message sanity check */ + if (sizeof (struct GNUNET_MESH_TunnelMessage) != ntohs (message->size)) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } - return size_needed; + tunnel_msg = (struct GNUNET_MESH_TunnelMessage *) message; + + /* Retrieve tunnel */ + tid = ntohl (tunnel_msg->tunnel_id); + t = tunnel_get_by_local_id(c, tid); + if (NULL == t) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, " tunnel %X not found\n", tid); + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + if (c != t->owner || tid >= GNUNET_MESH_LOCAL_TUNNEL_ID_SERV) + { + client_ignore_tunnel (c, t); + tunnel_destroy_empty (t); + GNUNET_SERVER_receive_done (client, GNUNET_OK); + return; + } + send_client_tunnel_disconnect (t, c); + client_delete_tunnel (c, t); + + /* Don't try to ACK the client about the tunnel_destroy multicast packet */ + t->owner = NULL; + tunnel_send_destroy (t, 0); + t->destroy = GNUNET_YES; + /* The tunnel will be destroyed when the last message is transmitted. */ + GNUNET_SERVER_receive_done (client, GNUNET_OK); + return; } -#endif /** - * Send keepalive packets for a peer - * - * @param cls Closure (tunnel for which to send the keepalive). - * @param tc Notification context. + * Handler for requests of seeting tunnel's speed. * - * TODO: implement explicit multicast keepalive? + * @param cls Closure (unused). + * @param client Identification of the client. + * @param message The actual message. */ static void -path_refresh (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +handle_local_tunnel_speed (void *cls, struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) { - struct MeshTunnel *t = cls; - struct GNUNET_MessageHeader *payload; - struct GNUNET_MESH_Multicast *msg; - size_t size = - sizeof (struct GNUNET_MESH_Multicast) + - sizeof (struct GNUNET_MessageHeader); - char cbuf[size]; + struct GNUNET_MESH_TunnelMessage *tunnel_msg; + struct MeshClient *c; + struct MeshTunnel *t; + MESH_TunnelNumber tid; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Got a SPEED request from client!\n"); - if (tc->reason == GNUNET_SCHEDULER_REASON_SHUTDOWN) + /* Sanity check for client registration */ + if (NULL == (c = client_get (client))) { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } - t->path_refresh_task = GNUNET_SCHEDULER_NO_TASK; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "sending keepalive for tunnel %d\n", t->id.tid); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " by client %u\n", c->id); - msg = (struct GNUNET_MESH_Multicast *) cbuf; - msg->header.size = htons (size); - msg->header.type = htons (GNUNET_MESSAGE_TYPE_MESH_MULTICAST); - msg->oid = my_full_id; - msg->tid = htonl (t->id.tid); - msg->ttl = htonl (DEFAULT_TTL); - msg->mid = htonl (t->mid + 1); - t->mid++; - payload = (struct GNUNET_MessageHeader *) &msg[1]; - payload->size = htons (sizeof (struct GNUNET_MessageHeader)); - payload->type = htons (GNUNET_MESSAGE_TYPE_MESH_PATH_KEEPALIVE); - tunnel_send_multicast (t, &msg->header, GNUNET_YES); + tunnel_msg = (struct GNUNET_MESH_TunnelMessage *) message; - t->path_refresh_task = - GNUNET_SCHEDULER_add_delayed (REFRESH_PATH_TIME, &path_refresh, t); - return; + /* Retrieve tunnel */ + tid = ntohl (tunnel_msg->tunnel_id); + t = tunnel_get_by_local_id(c, tid); + if (NULL == t) + { + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, " tunnel %X not found\n", tid); + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + + switch (ntohs(message->type)) + { + case GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_MIN: + t->speed_min = GNUNET_YES; + break; + case GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_MAX: + t->speed_min = GNUNET_NO; + break; + default: + GNUNET_break (0); + } + GNUNET_SERVER_receive_done (client, GNUNET_OK); } /** - * Function to process paths received for a new peer addition. The recorded - * paths form the initial tunnel, which can be optimized later. - * Called on each result obtained for the DHT search. - * - * @param cls closure - * @param exp when will this value expire - * @param key key of the result - * @param get_path path of the get request - * @param get_path_length lenght of get_path - * @param put_path path of the put request - * @param put_path_length length of the put_path - * @param type type of the result - * @param size number of bytes in data - * @param data pointer to the result data + * Handler for requests of seeting tunnel's buffering policy. * - * TODO: re-issue the request after certain time? cancel after X results? + * @param cls Closure (unused). + * @param client Identification of the client. + * @param message The actual message. */ static void -dht_get_id_handler (void *cls, struct GNUNET_TIME_Absolute exp, - const GNUNET_HashCode * key, - const struct GNUNET_PeerIdentity *get_path, - unsigned int get_path_length, - const struct GNUNET_PeerIdentity *put_path, - unsigned int put_path_length, enum GNUNET_BLOCK_Type type, - size_t size, const void *data) +handle_local_tunnel_buffer (void *cls, struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) { - struct MeshPathInfo *path_info = cls; - struct MeshPeerPath *p; - struct GNUNET_PeerIdentity pi; - int i; + struct GNUNET_MESH_TunnelMessage *tunnel_msg; + struct MeshClient *c; + struct MeshTunnel *t; + MESH_TunnelNumber tid; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Got results from DHT!\n"); - GNUNET_PEER_resolve (path_info->peer->id, &pi); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " for %s\n", GNUNET_i2s (&pi)); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Got a BUFFER request from client!\n"); - p = path_build_from_dht (get_path, get_path_length, put_path, - put_path_length); - path_add_to_peers (p, GNUNET_NO); - path_destroy(p); - for (i = 0; i < path_info->peer->ntunnels; i++) + /* Sanity check for client registration */ + if (NULL == (c = client_get (client))) { - tunnel_add_peer (path_info->peer->tunnels[i], path_info->peer); - peer_info_connect (path_info->peer, path_info->t); + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " by client %u\n", c->id); + + tunnel_msg = (struct GNUNET_MESH_TunnelMessage *) message; + + /* Retrieve tunnel */ + tid = ntohl (tunnel_msg->tunnel_id); + t = tunnel_get_by_local_id(c, tid); + if (NULL == t) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, " tunnel %X not found\n", tid); + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + + switch (ntohs(message->type)) + { + case GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_BUFFER: + t->nobuffer = GNUNET_NO; + break; + case GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_NOBUFFER: + t->nobuffer = GNUNET_YES; + break; + default: + GNUNET_break (0); } - return; + GNUNET_SERVER_receive_done (client, GNUNET_OK); } /** - * Function to process paths received for a new peer addition. The recorded - * paths form the initial tunnel, which can be optimized later. - * Called on each result obtained for the DHT search. + * Handler for connection requests to new peers * * @param cls closure - * @param exp when will this value expire - * @param key key of the result - * @param get_path path of the get request - * @param get_path_length lenght of get_path - * @param put_path path of the put request - * @param put_path_length length of the put_path - * @param type type of the result - * @param size number of bytes in data - * @param data pointer to the result data + * @param client identification of the client + * @param message the actual message (PeerControl) */ static void -dht_get_type_handler (void *cls, struct GNUNET_TIME_Absolute exp, - const GNUNET_HashCode * key, - const struct GNUNET_PeerIdentity *get_path, - unsigned int get_path_length, - const struct GNUNET_PeerIdentity *put_path, - unsigned int put_path_length, enum GNUNET_BLOCK_Type type, - size_t size, const void *data) +handle_local_connect_add (void *cls, struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) { - const struct GNUNET_PeerIdentity *pi = data; - struct MeshTunnel *t = cls; + struct GNUNET_MESH_PeerControl *peer_msg; struct MeshPeerInfo *peer_info; - struct MeshPeerPath *p; + struct MeshClient *c; + struct MeshTunnel *t; + MESH_TunnelNumber tid; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "got type DHT result!\n"); - if (size != sizeof (struct GNUNET_PeerIdentity)) + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Got connection request\n"); + /* Sanity check for client registration */ + if (NULL == (c = client_get (client))) { - GNUNET_break_op (0); + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } - GNUNET_assert (NULL != t->owner); - peer_info = peer_info_get (pi); - (void) GNUNET_CONTAINER_multihashmap_put (t->peers, &pi->hashPubKey, - peer_info, - GNUNET_CONTAINER_MULTIHASHMAPOPTION_REPLACE); - - p = path_build_from_dht (get_path, get_path_length, put_path, - put_path_length); - path_add_to_peers (p, GNUNET_NO); - path_destroy(p); - tunnel_add_peer (t, peer_info); - peer_info_connect (peer_info, t); -} - - -/******************************************************************************/ -/********************* MESH LOCAL HANDLES **************************/ -/******************************************************************************/ - + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " by client %u\n", c->id); -/** - * Handler for client disconnection - * - * @param cls closure - * @param client identification of the client; NULL - * for the last call when the server is destroyed - */ -static void -handle_local_client_disconnect (void *cls, struct GNUNET_SERVER_Client *client) -{ - struct MeshClient *c; - struct MeshClient *next; + peer_msg = (struct GNUNET_MESH_PeerControl *) message; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "client disconnected\n"); - if (client == NULL) + /* Sanity check for message size */ + if (sizeof (struct GNUNET_MESH_PeerControl) != ntohs (peer_msg->header.size)) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " (SERVER DOWN)\n"); + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } - c = clients; - while (NULL != c) + + /* Tunnel exists? */ + tid = ntohl (peer_msg->tunnel_id); + t = tunnel_get_by_local_id (c, tid); + if (NULL == t) { - if (c->handle != client) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " ... searching\n"); - c = c->next; - continue; - } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "matching client found (%u)\n", - c->id); - GNUNET_SERVER_client_drop (c->handle); - c->shutting_down = GNUNET_YES; - GNUNET_assert (NULL != c->own_tunnels); - GNUNET_assert (NULL != c->incoming_tunnels); - GNUNET_CONTAINER_multihashmap_iterate (c->own_tunnels, - &tunnel_destroy_iterator, c); - GNUNET_CONTAINER_multihashmap_iterate (c->incoming_tunnels, - &tunnel_destroy_iterator, c); - GNUNET_CONTAINER_multihashmap_iterate (c->ignore_tunnels, - &tunnel_destroy_iterator, c); - GNUNET_CONTAINER_multihashmap_destroy (c->own_tunnels); - GNUNET_CONTAINER_multihashmap_destroy (c->incoming_tunnels); - GNUNET_CONTAINER_multihashmap_destroy (c->ignore_tunnels); + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } - /* deregister clients applications */ - if (NULL != c->apps) - { - GNUNET_CONTAINER_multihashmap_iterate (c->apps, &deregister_app, NULL); - GNUNET_CONTAINER_multihashmap_destroy (c->apps); - } - if (0 == GNUNET_CONTAINER_multihashmap_size (applications) && - GNUNET_SCHEDULER_NO_TASK != announce_applications_task) - { - GNUNET_SCHEDULER_cancel (announce_applications_task); - announce_applications_task = GNUNET_SCHEDULER_NO_TASK; - } - if (NULL != c->types) - GNUNET_CONTAINER_multihashmap_destroy (c->types); - next = c->next; - GNUNET_CONTAINER_DLL_remove (clients, clients_tail, c); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " CLIENT FREE at %p\n", c); - GNUNET_free (c); - c = next; + /* Does client own tunnel? */ + if (t->owner->handle != client) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " done!\n"); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " for %s\n", + GNUNET_i2s (&peer_msg->peer)); + peer_info = peer_info_get (&peer_msg->peer); + + tunnel_add_peer (t, peer_info); + peer_info_connect (peer_info, t); + + GNUNET_SERVER_receive_done (client, GNUNET_OK); return; } /** - * Handler for new clients + * Handler for disconnection requests of peers in a tunnel * * @param cls closure * @param client identification of the client - * @param message the actual message, which includes messages the client wants + * @param message the actual message (PeerControl) */ static void -handle_local_new_client (void *cls, struct GNUNET_SERVER_Client *client, - const struct GNUNET_MessageHeader *message) +handle_local_connect_del (void *cls, struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) { - struct GNUNET_MESH_ClientConnect *cc_msg; + struct GNUNET_MESH_PeerControl *peer_msg; + struct MeshPeerInfo *peer_info; struct MeshClient *c; - GNUNET_MESH_ApplicationType *a; - unsigned int size; - uint16_t ntypes; - uint16_t *t; - uint16_t napps; - uint16_t i; + struct MeshTunnel *t; + MESH_TunnelNumber tid; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "new client connected\n"); - /* Check data sanity */ - size = ntohs (message->size) - sizeof (struct GNUNET_MESH_ClientConnect); - cc_msg = (struct GNUNET_MESH_ClientConnect *) message; - ntypes = ntohs (cc_msg->types); - napps = ntohs (cc_msg->applications); - if (size != - ntypes * sizeof (uint16_t) + napps * sizeof (GNUNET_MESH_ApplicationType)) + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Got a PEER DEL request\n"); + /* Sanity check for client registration */ + if (NULL == (c = client_get (client))) { GNUNET_break (0); GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " by client %u\n", c->id); - /* Create new client structure */ - c = GNUNET_malloc (sizeof (struct MeshClient)); - c->id = next_client_id++; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " CLIENT NEW %u\n", c->id); - c->handle = client; - GNUNET_SERVER_client_keep (client); - a = (GNUNET_MESH_ApplicationType *) &cc_msg[1]; - if (napps > 0) - { - GNUNET_MESH_ApplicationType at; - GNUNET_HashCode hc; - - c->apps = GNUNET_CONTAINER_multihashmap_create (napps); - for (i = 0; i < napps; i++) - { - at = ntohl (a[i]); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " app type: %u\n", at); - GNUNET_CRYPTO_hash (&at, sizeof (at), &hc); - /* store in clients hashmap */ - GNUNET_CONTAINER_multihashmap_put (c->apps, &hc, c, - GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE); - /* store in global hashmap, for announcements */ - GNUNET_CONTAINER_multihashmap_put (applications, &hc, c, - GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE); - } - if (GNUNET_SCHEDULER_NO_TASK == announce_applications_task) - announce_applications_task = - GNUNET_SCHEDULER_add_now (&announce_applications, NULL); + peer_msg = (struct GNUNET_MESH_PeerControl *) message; + /* Sanity check for message size */ + if (sizeof (struct GNUNET_MESH_PeerControl) != ntohs (peer_msg->header.size)) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; } - if (ntypes > 0) + + /* Tunnel exists? */ + tid = ntohl (peer_msg->tunnel_id); + t = tunnel_get_by_local_id (c, tid); + if (NULL == t) { - uint16_t u16; - GNUNET_HashCode hc; + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " on tunnel %X\n", t->id.tid); - t = (uint16_t *) & a[napps]; - c->types = GNUNET_CONTAINER_multihashmap_create (ntypes); - for (i = 0; i < ntypes; i++) - { - u16 = ntohs (t[i]); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " msg type: %u\n", u16); - GNUNET_CRYPTO_hash (&u16, sizeof (u16), &hc); + /* Does client own tunnel? */ + if (t->owner->handle != client) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } - /* store in clients hashmap */ - GNUNET_CONTAINER_multihashmap_put (c->types, &hc, c, - GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE); - /* store in global hashmap */ - GNUNET_CONTAINER_multihashmap_put (types, &hc, c, - GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE); - } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " for peer %s\n", + GNUNET_i2s (&peer_msg->peer)); + /* Is the peer in the tunnel? */ + peer_info = + GNUNET_CONTAINER_multihashmap_get (t->peers, &peer_msg->peer.hashPubKey); + if (NULL == peer_info) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - " client has %u+%u subscriptions\n", napps, ntypes); - GNUNET_CONTAINER_DLL_insert (clients, clients_tail, c); - c->own_tunnels = GNUNET_CONTAINER_multihashmap_create (32); - c->incoming_tunnels = GNUNET_CONTAINER_multihashmap_create (32); - c->ignore_tunnels = GNUNET_CONTAINER_multihashmap_create (32); - GNUNET_SERVER_notification_context_add (nc, client); + /* Ok, delete peer from tunnel */ + GNUNET_CONTAINER_multihashmap_remove_all (t->peers, + &peer_msg->peer.hashPubKey); + send_destroy_path (t, peer_info->id); + tunnel_delete_peer (t, peer_info->id); GNUNET_SERVER_receive_done (client, GNUNET_OK); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "new client processed\n"); + return; } - /** - * Handler for requests of new tunnels + * Handler for blacklist requests of peers in a tunnel * * @param cls closure * @param client identification of the client - * @param message the actual message + * @param message the actual message (PeerControl) + * + * FIXME implement DHT block bloomfilter */ static void -handle_local_tunnel_create (void *cls, struct GNUNET_SERVER_Client *client, - const struct GNUNET_MessageHeader *message) +handle_local_blacklist (void *cls, struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) { - struct GNUNET_MESH_TunnelMessage *t_msg; - struct MeshTunnel *t; + struct GNUNET_MESH_PeerControl *peer_msg; struct MeshClient *c; - GNUNET_HashCode hash; - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "new tunnel requested\n"); + struct MeshTunnel *t; + MESH_TunnelNumber tid; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Got a PEER BLACKLIST request\n"); /* Sanity check for client registration */ if (NULL == (c = client_get (client))) { @@ -3911,88 +6975,123 @@ handle_local_tunnel_create (void *cls, struct GNUNET_SERVER_Client *client, } GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " by client %u\n", c->id); - /* Message sanity check */ - if (sizeof (struct GNUNET_MESH_TunnelMessage) != ntohs (message->size)) + peer_msg = (struct GNUNET_MESH_PeerControl *) message; + + /* Sanity check for message size */ + if (sizeof (struct GNUNET_MESH_PeerControl) != ntohs (peer_msg->header.size)) { GNUNET_break (0); GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } - t_msg = (struct GNUNET_MESH_TunnelMessage *) message; - /* Sanity check for tunnel numbering */ - if (0 == (ntohl (t_msg->tunnel_id) & GNUNET_MESH_LOCAL_TUNNEL_ID_CLI)) + /* Tunnel exists? */ + tid = ntohl (peer_msg->tunnel_id); + t = tunnel_get_by_local_id (c, tid); + if (NULL == t) { GNUNET_break (0); GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } - /* Sanity check for duplicate tunnel IDs */ - if (NULL != tunnel_get_by_local_id (c, ntohl (t_msg->tunnel_id))) + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " on tunnel %X\n", t->id.tid); + + GNUNET_array_append(t->blacklisted, t->nblacklisted, + GNUNET_PEER_intern(&peer_msg->peer)); +} + + +/** + * Handler for unblacklist requests of peers in a tunnel + * + * @param cls closure + * @param client identification of the client + * @param message the actual message (PeerControl) + */ +static void +handle_local_unblacklist (void *cls, struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) +{ + struct GNUNET_MESH_PeerControl *peer_msg; + struct MeshClient *c; + struct MeshTunnel *t; + MESH_TunnelNumber tid; + GNUNET_PEER_Id pid; + unsigned int i; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Got a PEER UNBLACKLIST request\n"); + /* Sanity check for client registration */ + if (NULL == (c = client_get (client))) { GNUNET_break (0); GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " by client %u\n", c->id); - t = GNUNET_malloc (sizeof (struct MeshTunnel)); - while (NULL != tunnel_get_by_pi (myid, next_tid)) - next_tid = (next_tid + 1) & ~GNUNET_MESH_LOCAL_TUNNEL_ID_CLI; - t->id.tid = next_tid++; - next_tid = next_tid & ~GNUNET_MESH_LOCAL_TUNNEL_ID_CLI; - t->id.oid = myid; - t->local_tid = ntohl (t_msg->tunnel_id); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "CREATED TUNNEL %s [%x] (%x)\n", - GNUNET_i2s (&my_full_id), t->id.tid, t->local_tid); - t->owner = c; - t->peers = GNUNET_CONTAINER_multihashmap_create (32); + peer_msg = (struct GNUNET_MESH_PeerControl *) message; - GNUNET_CRYPTO_hash (&t->local_tid, sizeof (MESH_TunnelNumber), &hash); - if (GNUNET_OK != - GNUNET_CONTAINER_multihashmap_put (c->own_tunnels, &hash, t, - GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY)) + /* Sanity check for message size */ + if (sizeof (struct GNUNET_MESH_PeerControl) != ntohs (peer_msg->header.size)) { GNUNET_break (0); GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } - GNUNET_CRYPTO_hash (&t->id, sizeof (struct MESH_TunnelID), &hash); - if (GNUNET_OK != - GNUNET_CONTAINER_multihashmap_put (tunnels, &hash, t, - GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY)) + /* Tunnel exists? */ + tid = ntohl (peer_msg->tunnel_id); + t = tunnel_get_by_local_id (c, tid); + if (NULL == t) { GNUNET_break (0); GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } - t->tree = tree_new (myid); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " on tunnel %X\n", t->id.tid); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "new tunnel created\n"); - GNUNET_SERVER_receive_done (client, GNUNET_OK); - return; + /* if peer is not known, complain */ + pid = GNUNET_PEER_search (&peer_msg->peer); + if (0 == pid) + { + GNUNET_break (0); + return; + } + + /* search and remove from list */ + for (i = 0; i < t->nblacklisted; i++) + { + if (t->blacklisted[i] == pid) + { + t->blacklisted[i] = t->blacklisted[t->nblacklisted - 1]; + GNUNET_array_grow (t->blacklisted, t->nblacklisted, t->nblacklisted - 1); + return; + } + } + + /* if peer hasn't been blacklisted, complain */ + GNUNET_break (0); } /** - * Handler for requests of deleting tunnels + * Handler for connection requests to new peers by type * * @param cls closure * @param client identification of the client - * @param message the actual message + * @param message the actual message (ConnectPeerByType) */ static void -handle_local_tunnel_destroy (void *cls, struct GNUNET_SERVER_Client *client, - const struct GNUNET_MessageHeader *message) +handle_local_connect_by_type (void *cls, struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) { - struct GNUNET_MESH_TunnelMessage *tunnel_msg; + struct GNUNET_MESH_ConnectPeerByType *connect_msg; struct MeshClient *c; struct MeshTunnel *t; + struct GNUNET_HashCode hash; MESH_TunnelNumber tid; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Got a DESTROY TUNNEL from client!\n"); - + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "got connect by type request\n"); /* Sanity check for client registration */ if (NULL == (c = client_get (client))) { @@ -4000,75 +7099,114 @@ handle_local_tunnel_destroy (void *cls, struct GNUNET_SERVER_Client *client, GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } - /* Message sanity check */ - if (sizeof (struct GNUNET_MESH_TunnelMessage) != ntohs (message->size)) + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " by client %u\n", c->id); + + connect_msg = (struct GNUNET_MESH_ConnectPeerByType *) message; + + /* Sanity check for message size */ + if (sizeof (struct GNUNET_MESH_ConnectPeerByType) != + ntohs (connect_msg->header.size)) { GNUNET_break (0); GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " by client %u\n", c->id); - tunnel_msg = (struct GNUNET_MESH_TunnelMessage *) message; - /* Retrieve tunnel */ - tid = ntohl (tunnel_msg->tunnel_id); - t = tunnel_get_by_local_id(c, tid); + /* Tunnel exists? */ + tid = ntohl (connect_msg->tunnel_id); + t = tunnel_get_by_local_id (c, tid); if (NULL == t) { GNUNET_break (0); - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, " tunnel %X not found\n", tid); GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } - if (c != t->owner || tid >= GNUNET_MESH_LOCAL_TUNNEL_ID_SERV) + + /* Does client own tunnel? */ + if (t->owner->handle != client) { - client_ignore_tunnel (c, t); -#if 0 - // TODO: when to destroy incoming tunnel? - if (t->nclients == 0) - { - GNUNET_assert (GNUNET_YES == - GNUNET_CONTAINER_multihashmap_remove (incoming_tunnels, - &hash, t)); - GNUNET_assert (GNUNET_YES == - GNUNET_CONTAINER_multihashmap_remove (t->peers, - &my_full_id.hashPubKey, - t)); - } -#endif + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + + /* Do WE have the service? */ + t->type = ntohl (connect_msg->type); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " type requested: %u\n", t->type); + GNUNET_CRYPTO_hash (&t->type, sizeof (GNUNET_MESH_ApplicationType), &hash); + if (GNUNET_CONTAINER_multihashmap_contains (applications, &hash) == + GNUNET_YES) + { + /* Yes! Fast forward, add ourselves to the tunnel and send the + * good news to the client, and alert the destination client of + * an incoming tunnel. + * + * FIXME send a path create to self, avoid code duplication + */ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " available locally\n"); + GNUNET_CONTAINER_multihashmap_put (t->peers, &my_full_id.hashPubKey, + peer_info_get (&my_full_id), + GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_FAST); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " notifying client\n"); + send_client_peer_connected (t, myid); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " Done\n"); GNUNET_SERVER_receive_done (client, GNUNET_OK); + + t->local_tid_dest = next_local_tid++; + GNUNET_CRYPTO_hash (&t->local_tid_dest, sizeof (MESH_TunnelNumber), &hash); + GNUNET_CONTAINER_multihashmap_put (incoming_tunnels, &hash, t, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_FAST); + return; } - send_client_tunnel_disconnect(t, c); - client_delete_tunnel(c, t); + /* Ok, lets find a peer offering the service */ + if (NULL != t->dht_get_type) + { + GNUNET_DHT_get_stop (t->dht_get_type); + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " looking in DHT for %s\n", + GNUNET_h2s (&hash)); + t->dht_get_type = + GNUNET_DHT_get_start (dht_handle, + GNUNET_BLOCK_TYPE_MESH_PEER_BY_TYPE, + &hash, + dht_replication_level, + GNUNET_DHT_RO_RECORD_ROUTE | + GNUNET_DHT_RO_DEMULTIPLEX_EVERYWHERE, + NULL, 0, + &dht_get_type_handler, t); - /* Don't try to ACK the client about the tunnel_destroy multicast packet */ - t->owner = NULL; - tunnel_send_destroy (t); - tunnel_destroy (t); GNUNET_SERVER_receive_done (client, GNUNET_OK); return; } /** - * Handler for connection requests to new peers + * Handler for connection requests to new peers by a string service description. * * @param cls closure * @param client identification of the client - * @param message the actual message (PeerControl) + * @param message the actual message, which includes messages the client wants */ static void -handle_local_connect_add (void *cls, struct GNUNET_SERVER_Client *client, - const struct GNUNET_MessageHeader *message) +handle_local_connect_by_string (void *cls, struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) { - struct GNUNET_MESH_PeerControl *peer_msg; - struct MeshPeerInfo *peer_info; - struct MeshClient *c; + struct GNUNET_MESH_ConnectPeerByString *msg; + struct MeshRegexSearchInfo *info; struct MeshTunnel *t; + struct MeshClient *c; MESH_TunnelNumber tid; + const char *string; + size_t size; + size_t len; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Connect by string started\n"); + msg = (struct GNUNET_MESH_ConnectPeerByString *) message; + size = htons (message->size); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Got connection request\n"); /* Sanity check for client registration */ if (NULL == (c = client_get (client))) { @@ -4076,10 +7214,10 @@ handle_local_connect_add (void *cls, struct GNUNET_SERVER_Client *client, GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " by client %u\n", c->id); - peer_msg = (struct GNUNET_MESH_PeerControl *) message; - /* Sanity check for message size */ - if (sizeof (struct GNUNET_MESH_PeerControl) != ntohs (peer_msg->header.size)) + /* Message size sanity check */ + if (sizeof(struct GNUNET_MESH_ConnectPeerByString) >= size) { GNUNET_break (0); GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); @@ -4087,7 +7225,7 @@ handle_local_connect_add (void *cls, struct GNUNET_SERVER_Client *client, } /* Tunnel exists? */ - tid = ntohl (peer_msg->tunnel_id); + tid = ntohl (msg->tunnel_id); t = tunnel_get_by_local_id (c, tid); if (NULL == t) { @@ -4103,36 +7241,63 @@ handle_local_connect_add (void *cls, struct GNUNET_SERVER_Client *client, GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " for %s\n", - GNUNET_i2s (&peer_msg->peer)); - peer_info = peer_info_get (&peer_msg->peer); - tunnel_add_peer (t, peer_info); - peer_info_connect (peer_info, t); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " on tunnel %s [%u]\n", + GNUNET_i2s(&my_full_id), + t->id.tid); + + /* Only one connect_by_string allowed at the same time! */ + /* FIXME: allow more, return handle at api level to cancel, document */ + if (NULL != t->regex_search) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + + /* Find string itself */ + len = size - sizeof(struct GNUNET_MESH_ConnectPeerByString); + string = (const char *) &msg[1]; + + info = GNUNET_malloc (sizeof (struct MeshRegexSearchInfo)); + info->t = t; + info->description = GNUNET_strndup (string, len); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " string: %s\n", info->description); + + t->regex_search = info; + + info->search_handle = GNUNET_REGEX_search (dht_handle, + info->description, + ®ex_found_handler, info, + stats); GNUNET_SERVER_receive_done (client, GNUNET_OK); - return; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "connect by string processed\n"); } /** - * Handler for disconnection requests of peers in a tunnel + * Handler for client traffic directed to one peer * * @param cls closure * @param client identification of the client - * @param message the actual message (PeerControl) + * @param message the actual message */ static void -handle_local_connect_del (void *cls, struct GNUNET_SERVER_Client *client, - const struct GNUNET_MessageHeader *message) +handle_local_unicast (void *cls, struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) { - struct GNUNET_MESH_PeerControl *peer_msg; - struct MeshPeerInfo *peer_info; struct MeshClient *c; struct MeshTunnel *t; + struct MeshPeerInfo *pi; + struct GNUNET_MESH_Unicast *data_msg; MESH_TunnelNumber tid; + size_t size; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Got a unicast request from a client!\n"); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Got a PEER DEL request\n"); /* Sanity check for client registration */ if (NULL == (c = client_get (client))) { @@ -4140,9 +7305,14 @@ handle_local_connect_del (void *cls, struct GNUNET_SERVER_Client *client, GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } - peer_msg = (struct GNUNET_MESH_PeerControl *) message; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " by client %u\n", c->id); + + data_msg = (struct GNUNET_MESH_Unicast *) message; + /* Sanity check for message size */ - if (sizeof (struct GNUNET_MESH_PeerControl) != ntohs (peer_msg->header.size)) + size = ntohs (message->size); + if (sizeof (struct GNUNET_MESH_Unicast) + + sizeof (struct GNUNET_MessageHeader) > size) { GNUNET_break (0); GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); @@ -4150,7 +7320,7 @@ handle_local_connect_del (void *cls, struct GNUNET_SERVER_Client *client, } /* Tunnel exists? */ - tid = ntohl (peer_msg->tunnel_id); + tid = ntohl (data_msg->tid); t = tunnel_get_by_local_id (c, tid); if (NULL == t) { @@ -4158,9 +7328,8 @@ handle_local_connect_del (void *cls, struct GNUNET_SERVER_Client *client, GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " on tunnel %X\n", t->id.tid); - /* Does client own tunnel? */ + /* Is it a local tunnel? Then, does client own the tunnel? */ if (t->owner->handle != client) { GNUNET_break (0); @@ -4168,47 +7337,71 @@ handle_local_connect_del (void *cls, struct GNUNET_SERVER_Client *client, return; } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " for peer %s\n", - GNUNET_i2s (&peer_msg->peer)); - /* Is the peer in the tunnel? */ - peer_info = - GNUNET_CONTAINER_multihashmap_get (t->peers, &peer_msg->peer.hashPubKey); - if (NULL == peer_info) + pi = GNUNET_CONTAINER_multihashmap_get (t->peers, + &data_msg->destination.hashPubKey); + /* Is the selected peer in the tunnel? */ + if (NULL == pi) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + + /* PID should be as expected */ + if (ntohl (data_msg->pid) != t->fwd_pid + 1) { GNUNET_break (0); + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + "Unicast PID, expected %u, got %u\n", + t->fwd_pid + 1, ntohl (data_msg->pid)); GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } - /* Ok, delete peer from tunnel */ - GNUNET_CONTAINER_multihashmap_remove_all (t->peers, - &peer_msg->peer.hashPubKey); + /* Ok, everything is correct, send the message + * (pretend we got it from a mesh peer) + */ + { + /* Work around const limitation */ + char buf[ntohs (message->size)] GNUNET_ALIGN; + struct GNUNET_MESH_Unicast *copy; - send_destroy_path (t, peer_info->id); - tunnel_delete_peer (t, peer_info->id); + copy = (struct GNUNET_MESH_Unicast *) buf; + memcpy (buf, data_msg, size); + copy->oid = my_full_id; + copy->tid = htonl (t->id.tid); + copy->ttl = htonl (default_ttl); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " calling generic handler...\n"); + handle_mesh_data_unicast (NULL, &my_full_id, ©->header, NULL, 0); + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "receive done OK\n"); GNUNET_SERVER_receive_done (client, GNUNET_OK); + return; } /** - * Handler for connection requests to new peers by type + * Handler for client traffic directed to the origin * * @param cls closure * @param client identification of the client - * @param message the actual message (ConnectPeerByType) + * @param message the actual message */ static void -handle_local_connect_by_type (void *cls, struct GNUNET_SERVER_Client *client, - const struct GNUNET_MessageHeader *message) +handle_local_to_origin (void *cls, struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) { - struct GNUNET_MESH_ConnectPeerByType *connect_msg; + struct GNUNET_MESH_ToOrigin *data_msg; + struct MeshTunnelClientInfo *clinfo; struct MeshClient *c; struct MeshTunnel *t; - GNUNET_HashCode hash; MESH_TunnelNumber tid; + size_t size; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "got connect by type request\n"); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Got a ToOrigin request from a client!\n"); /* Sanity check for client registration */ if (NULL == (c = client_get (client))) { @@ -4216,11 +7409,14 @@ handle_local_connect_by_type (void *cls, struct GNUNET_SERVER_Client *client, GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " by client %u\n", c->id); + + data_msg = (struct GNUNET_MESH_ToOrigin *) message; - connect_msg = (struct GNUNET_MESH_ConnectPeerByType *) message; /* Sanity check for message size */ - if (sizeof (struct GNUNET_MESH_ConnectPeerByType) != - ntohs (connect_msg->header.size)) + size = ntohs (message->size); + if (sizeof (struct GNUNET_MESH_ToOrigin) + + sizeof (struct GNUNET_MessageHeader) > size) { GNUNET_break (0); GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); @@ -4228,92 +7424,90 @@ handle_local_connect_by_type (void *cls, struct GNUNET_SERVER_Client *client, } /* Tunnel exists? */ - tid = ntohl (connect_msg->tunnel_id); + tid = ntohl (data_msg->tid); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " on tunnel %X\n", tid); + if (tid < GNUNET_MESH_LOCAL_TUNNEL_ID_SERV) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } t = tunnel_get_by_local_id (c, tid); if (NULL == t) { + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Tunnel %X unknown.\n", tid); + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, " for client %u.\n", c->id); GNUNET_break (0); GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } - /* Does client own tunnel? */ - if (t->owner->handle != client) + /* It should be sent by someone who has this as incoming tunnel. */ + if (GNUNET_NO == client_knows_tunnel (c, t)) { GNUNET_break (0); GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } - /* Do WE have the service? */ - t->type = ntohl (connect_msg->type); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " type requested: %u\n", t->type); - GNUNET_CRYPTO_hash (&t->type, sizeof (GNUNET_MESH_ApplicationType), &hash); - if (GNUNET_CONTAINER_multihashmap_contains (applications, &hash) == - GNUNET_YES) + /* PID should be as expected */ + clinfo = tunnel_get_client_fc (t, c); + if (ntohl (data_msg->pid) != clinfo->bck_pid + 1) { - /* Yes! Fast forward, add ourselves to the tunnel and send the - * good news to the client, and alert the destination client of - * an incoming tunnel. - * - * FIXME send a path create to self, avoid code duplication - */ - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " available locally\n"); - GNUNET_CONTAINER_multihashmap_put (t->peers, &my_full_id.hashPubKey, - peer_info_get (&my_full_id), - GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_FAST); - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " notifying client\n"); - send_client_peer_connected (t, myid); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " Done\n"); - GNUNET_SERVER_receive_done (client, GNUNET_OK); - - t->local_tid_dest = next_local_tid++; - GNUNET_CRYPTO_hash (&t->local_tid_dest, sizeof (MESH_TunnelNumber), &hash); - GNUNET_CONTAINER_multihashmap_put (incoming_tunnels, &hash, t, - GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_FAST); - + GNUNET_break (0); + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + "To Origin PID, expected %u, got %u\n", + clinfo->bck_pid + 1, + ntohl (data_msg->pid)); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } - /* Ok, lets find a peer offering the service */ - if (NULL != t->dht_get_type) + clinfo->bck_pid++; + + /* Ok, everything is correct, send the message + * (pretend we got it from a mesh peer) + */ { - GNUNET_DHT_get_stop (t->dht_get_type); - } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " looking in DHT for %s\n", - GNUNET_h2s (&hash)); - t->dht_get_type = - GNUNET_DHT_get_start (dht_handle, - GNUNET_BLOCK_TYPE_TEST, &hash, 10, - GNUNET_DHT_RO_RECORD_ROUTE | - GNUNET_DHT_RO_DEMULTIPLEX_EVERYWHERE, NULL, 0, - &dht_get_type_handler, t); + char buf[ntohs (message->size)] GNUNET_ALIGN; + struct GNUNET_MESH_ToOrigin *copy; + /* Work around const limitation */ + copy = (struct GNUNET_MESH_ToOrigin *) buf; + memcpy (buf, data_msg, size); + GNUNET_PEER_resolve (t->id.oid, ©->oid); + copy->tid = htonl (t->id.tid); + copy->ttl = htonl (default_ttl); + copy->pid = htonl (t->bck_pid + 1); + + copy->sender = my_full_id; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " calling generic handler...\n"); + handle_mesh_data_to_orig (NULL, &my_full_id, ©->header, NULL, 0); + } GNUNET_SERVER_receive_done (client, GNUNET_OK); + return; } /** - * Handler for client traffic directed to one peer + * Handler for client traffic directed to all peers in a tunnel * * @param cls closure * @param client identification of the client * @param message the actual message */ static void -handle_local_unicast (void *cls, struct GNUNET_SERVER_Client *client, - const struct GNUNET_MessageHeader *message) +handle_local_multicast (void *cls, struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) { struct MeshClient *c; struct MeshTunnel *t; - struct MeshPeerInfo *pi; - struct GNUNET_MESH_Unicast *data_msg; + struct GNUNET_MESH_Multicast *data_msg; MESH_TunnelNumber tid; - size_t size; GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Got a unicast request from a client!\n"); + "Got a multicast request from a client!\n"); /* Sanity check for client registration */ if (NULL == (c = client_get (client))) @@ -4322,11 +7516,13 @@ handle_local_unicast (void *cls, struct GNUNET_SERVER_Client *client, GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } - data_msg = (struct GNUNET_MESH_Unicast *) message; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " by client %u\n", c->id); + + data_msg = (struct GNUNET_MESH_Multicast *) message; + /* Sanity check for message size */ - size = ntohs (message->size); - if (sizeof (struct GNUNET_MESH_Unicast) + - sizeof (struct GNUNET_MessageHeader) > size) + if (sizeof (struct GNUNET_MESH_Multicast) + + sizeof (struct GNUNET_MessageHeader) > ntohs (data_msg->header.size)) { GNUNET_break (0); GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); @@ -4338,12 +7534,15 @@ handle_local_unicast (void *cls, struct GNUNET_SERVER_Client *client, t = tunnel_get_by_local_id (c, tid); if (NULL == t) { + GNUNET_break (0); + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Tunnel %X unknown.\n", tid); + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, " for client %u.\n", c->id); GNUNET_break (0); GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } - /* Is it a local tunnel? Then, does client own the tunnel? */ + /* Does client own tunnel? */ if (t->owner->handle != client) { GNUNET_break (0); @@ -4351,55 +7550,55 @@ handle_local_unicast (void *cls, struct GNUNET_SERVER_Client *client, return; } - pi = GNUNET_CONTAINER_multihashmap_get (t->peers, - &data_msg->destination.hashPubKey); - /* Is the selected peer in the tunnel? */ - if (NULL == pi) + /* PID should be as expected */ + if (ntohl (data_msg->pid) != t->fwd_pid + 1) { GNUNET_break (0); + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + "Multicast PID, expected %u, got %u\n", + t->fwd_pid + 1, ntohl (data_msg->pid)); GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } - /* Ok, everything is correct, send the message - * (pretend we got it from a mesh peer) - */ { char buf[ntohs (message->size)] GNUNET_ALIGN; - struct GNUNET_MESH_Unicast *copy; + struct GNUNET_MESH_Multicast *copy; - /* Work around const limitation */ - copy = (struct GNUNET_MESH_Unicast *) buf; - memcpy (buf, data_msg, size); + copy = (struct GNUNET_MESH_Multicast *) buf; + memcpy (buf, message, ntohs (message->size)); copy->oid = my_full_id; copy->tid = htonl (t->id.tid); + copy->ttl = htonl (default_ttl); + GNUNET_assert (ntohl (copy->pid) == (t->fwd_pid + 1)); GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " calling generic handler...\n"); - handle_mesh_data_unicast (NULL, &my_full_id, ©->header, NULL, 0); + handle_mesh_data_multicast (client, &my_full_id, ©->header, NULL, 0); } - GNUNET_SERVER_receive_done (client, GNUNET_OK); + + GNUNET_SERVER_receive_done (t->owner->handle, GNUNET_OK); return; } /** - * Handler for client traffic directed to the origin + * Handler for client's ACKs for payload traffic. * - * @param cls closure - * @param client identification of the client - * @param message the actual message + * @param cls Closure (unused). + * @param client Identification of the client. + * @param message The actual message. */ static void -handle_local_to_origin (void *cls, struct GNUNET_SERVER_Client *client, - const struct GNUNET_MessageHeader *message) +handle_local_ack (void *cls, struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) { - struct GNUNET_MESH_ToOrigin *data_msg; - struct GNUNET_PeerIdentity id; - struct MeshClient *c; + struct GNUNET_MESH_LocalAck *msg; struct MeshTunnel *t; + struct MeshClient *c; MESH_TunnelNumber tid; - size_t size; + uint32_t ack; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Got a local ACK\n"); /* Sanity check for client registration */ if (NULL == (c = client_get (client))) { @@ -4407,84 +7606,279 @@ handle_local_to_origin (void *cls, struct GNUNET_SERVER_Client *client, GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } - data_msg = (struct GNUNET_MESH_ToOrigin *) message; - /* Sanity check for message size */ - size = ntohs (message->size); - if (sizeof (struct GNUNET_MESH_ToOrigin) + - sizeof (struct GNUNET_MessageHeader) > size) + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " by client %u\n", c->id); + + msg = (struct GNUNET_MESH_LocalAck *) message; + + /* Tunnel exists? */ + tid = ntohl (msg->tunnel_id); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " on tunnel %X\n", tid); + t = tunnel_get_by_local_id (c, tid); + if (NULL == t) { GNUNET_break (0); + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Tunnel %X unknown.\n", tid); + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, " for client %u.\n", c->id); GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } - /* Tunnel exists? */ - tid = ntohl (data_msg->tid); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Got a ToOrigin request from a client! Tunnel %X\n", tid); - if (tid < GNUNET_MESH_LOCAL_TUNNEL_ID_SERV) + ack = ntohl (msg->max_pid); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " ack %u\n", ack); + + /* Does client own tunnel? I.E: Is this an ACK for BCK traffic? */ + if (NULL != t->owner && t->owner->handle == client) { - GNUNET_break (0); - GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); - return; + /* The client owns the tunnel, ACK is for data to_origin, send BCK ACK. */ + t->bck_ack = ack; + tunnel_send_bck_ack(t, GNUNET_MESSAGE_TYPE_MESH_LOCAL_ACK); } - t = tunnel_get_by_local_id (c, tid); - if (NULL == t) + else { - GNUNET_break (0); - GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); - return; + /* The client doesn't own the tunnel, this ACK is for FWD traffic. */ + tunnel_set_client_fwd_ack (t, c, ack); + tunnel_send_fwd_ack (t, GNUNET_MESSAGE_TYPE_MESH_LOCAL_ACK); } - /* It should be sent by someone who has this as incoming tunnel. */ - if (-1 == client_knows_tunnel (c, t)) + GNUNET_SERVER_receive_done (client, GNUNET_OK); + + return; +} + + +/** + * Iterator over all peers to send a monitoring client info about a tunnel. + * + * @param cls Closure (message being built). + * @param key Key (hashed tunnel ID, unused). + * @param value Peer info. + * + * @return GNUNET_YES, to keep iterating. + */ +static int +monitor_peers_iterator (void *cls, + const struct GNUNET_HashCode * key, + void *value) +{ + struct GNUNET_MESH_LocalMonitor *msg = cls; + struct GNUNET_PeerIdentity *id; + struct MeshPeerInfo *info = value; + + id = (struct GNUNET_PeerIdentity *) &msg[1]; + GNUNET_PEER_resolve (info->id, &id[msg->npeers]); + msg->npeers++; + + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + "* sending info about peer %s [%u]\n", + GNUNET_i2s (&id[msg->npeers - 1]), msg->npeers); + + return GNUNET_YES; +} + + + +/** + * Iterator over all tunnels to send a monitoring client info about each tunnel. + * + * @param cls Closure (client handle). + * @param key Key (hashed tunnel ID, unused). + * @param value Tunnel info. + * + * @return GNUNET_YES, to keep iterating. + */ +static int +monitor_all_tunnels_iterator (void *cls, + const struct GNUNET_HashCode * key, + void *value) +{ + struct GNUNET_SERVER_Client *client = cls; + struct MeshTunnel *t = value; + struct GNUNET_MESH_LocalMonitor *msg; + uint32_t npeers; + + npeers = GNUNET_CONTAINER_multihashmap_size (t->peers); + msg = GNUNET_malloc (sizeof(struct GNUNET_MESH_LocalMonitor) + + npeers * sizeof (struct GNUNET_PeerIdentity)); + GNUNET_PEER_resolve(t->id.oid, &msg->owner); + msg->tunnel_id = htonl (t->id.tid); + msg->header.size = htons (sizeof (struct GNUNET_MESH_LocalMonitor) + + npeers * sizeof (struct GNUNET_PeerIdentity)); + msg->header.type = htons (GNUNET_MESSAGE_TYPE_MESH_LOCAL_INFO_TUNNELS); + msg->npeers = 0; + (void) GNUNET_CONTAINER_multihashmap_iterate (t->peers, + monitor_peers_iterator, + msg); + + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + "* sending info about tunnel %s [%u] (%u peers)\n", + GNUNET_i2s (&msg->owner), t->id.tid, npeers); + + if (msg->npeers != npeers) + { + GNUNET_break (0); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Get tunnels fail: size %u - iter %u\n", + npeers, msg->npeers); + } + + msg->npeers = htonl (npeers); + GNUNET_SERVER_notification_context_unicast (nc, client, + &msg->header, GNUNET_NO); + return GNUNET_YES; +} + + +/** + * Handler for client's MONITOR request. + * + * @param cls Closure (unused). + * @param client Identification of the client. + * @param message The actual message. + */ +static void +handle_local_get_tunnels (void *cls, struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) +{ + struct MeshClient *c; + + /* Sanity check for client registration */ + if (NULL == (c = client_get (client))) { GNUNET_break (0); GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } - GNUNET_PEER_resolve (t->id.oid, &id); - /* Ok, everything is correct, send the message - * (pretend we got it from a mesh peer) + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + "Received get tunnels request from client %u\n", + c->id); + GNUNET_CONTAINER_multihashmap_iterate (tunnels, + monitor_all_tunnels_iterator, + client); + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + "Get tunnels request from client %u completed\n", + c->id); + GNUNET_SERVER_receive_done (client, GNUNET_OK); +} + + +/** + * Data needed to build a Monitor_Tunnel message. + */ +struct MeshMonitorTunnelContext +{ + /** + * Partial message, including peer count. + */ + struct GNUNET_MESH_LocalMonitor *msg; + + /** + * Hashmap with positions: peer->position. + */ + struct GNUNET_CONTAINER_MultiHashMap *lookup; + + /** + * Index of the parent of each peer in the message, realtive to the absolute + * order in the array (can be in a previous message). + */ + uint32_t parents[1024]; + + /** + * Peers visited so far in the tree, aka position of the current peer. + */ + unsigned int npeers; + + /** + * Client requesting the info. */ - { - char buf[ntohs (message->size)] GNUNET_ALIGN; - struct GNUNET_MESH_ToOrigin *copy; + struct MeshClient *c; +}; - /* Work around const limitation */ - copy = (struct GNUNET_MESH_ToOrigin *) buf; - memcpy (buf, data_msg, size); - copy->oid = id; - copy->tid = htonl (t->id.tid); - copy->sender = my_full_id; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - " calling generic handler...\n"); - handle_mesh_data_to_orig (NULL, &my_full_id, ©->header, NULL, 0); + +/** + * Send a client a message about the structure of a tunnel. + * + * @param ctx Context of the tunnel iteration, with info regarding the state + * of the execution and the number of peers visited for this message. + */ +static void +send_client_tunnel_info (struct MeshMonitorTunnelContext *ctx) +{ + struct GNUNET_MESH_LocalMonitor *resp = ctx->msg; + struct GNUNET_PeerIdentity *pid; + unsigned int *parent; + size_t size; + + size = sizeof (struct GNUNET_MESH_LocalMonitor); + size += (sizeof (struct GNUNET_PeerIdentity) + sizeof (int)) * resp->npeers; + resp->header.size = htons (size); + pid = (struct GNUNET_PeerIdentity *) &resp[1]; + parent = (unsigned int *) &pid[resp->npeers]; + memcpy (parent, ctx->parents, sizeof(uint32_t) * resp->npeers); + GNUNET_SERVER_notification_context_unicast (nc, ctx->c->handle, + &resp->header, GNUNET_NO); +} + +/** + * Iterator over a tunnel tree to build a message containing all peers + * the in the tunnel, including relay nodes. + * + * @param cls Closure (pointer to pointer of message being built). + * @param peer Short ID of a peer. + * @param parent Short ID of the @c peer 's parent. + */ +static void +tunnel_tree_iterator (void *cls, + GNUNET_PEER_Id peer, + GNUNET_PEER_Id parent) +{ + struct MeshMonitorTunnelContext *ctx = cls; + struct GNUNET_MESH_LocalMonitor *msg; + struct GNUNET_PeerIdentity *pid; + struct GNUNET_PeerIdentity ppid; + + msg = ctx->msg; + pid = (struct GNUNET_PeerIdentity *) &msg[1]; + GNUNET_PEER_resolve (peer, &pid[msg->npeers]); + GNUNET_CONTAINER_multihashmap_put (ctx->lookup, + &pid[msg->npeers].hashPubKey, + (void *) (long) ctx->npeers, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_FAST); + GNUNET_PEER_resolve (parent, &ppid); + ctx->parents[msg->npeers] = + htonl ((long) GNUNET_CONTAINER_multihashmap_get (ctx->lookup, + &ppid.hashPubKey)); + + ctx->npeers++; + msg->npeers++; + + if (sizeof (struct GNUNET_MESH_LocalMonitor) + + (msg->npeers + 1) * + (sizeof (struct GNUNET_PeerIdentity) + sizeof (uint32_t)) + > USHRT_MAX) + { + send_client_tunnel_info (ctx); + msg->npeers = 0; } - GNUNET_SERVER_receive_done (client, GNUNET_OK); - return; } /** - * Handler for client traffic directed to all peers in a tunnel + * Handler for client's MONITOR_TUNNEL request. * - * @param cls closure - * @param client identification of the client - * @param message the actual message + * @param cls Closure (unused). + * @param client Identification of the client. + * @param message The actual message. */ static void -handle_local_multicast (void *cls, struct GNUNET_SERVER_Client *client, - const struct GNUNET_MessageHeader *message) +handle_local_show_tunnel (void *cls, struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) { + const struct GNUNET_MESH_LocalMonitor *msg; + struct GNUNET_MESH_LocalMonitor *resp; + struct MeshMonitorTunnelContext ctx; struct MeshClient *c; struct MeshTunnel *t; - struct GNUNET_MESH_Multicast *data_msg; - MESH_TunnelNumber tid; - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Got a multicast request from a client!\n"); /* Sanity check for client registration */ if (NULL == (c = client_get (client))) @@ -4493,80 +7887,110 @@ handle_local_multicast (void *cls, struct GNUNET_SERVER_Client *client, GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } - data_msg = (struct GNUNET_MESH_Multicast *) message; - /* Sanity check for message size */ - if (sizeof (struct GNUNET_MESH_Multicast) + - sizeof (struct GNUNET_MessageHeader) > ntohs (data_msg->header.size)) - { - GNUNET_break (0); - GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); - return; - } - /* Tunnel exists? */ - tid = ntohl (data_msg->tid); - t = tunnel_get_by_local_id (c, tid); + msg = (struct GNUNET_MESH_LocalMonitor *) message; + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + "Received tunnel info request from client %u for tunnel %s[%X]\n", + c->id, + &msg->owner, + ntohl (msg->tunnel_id)); + t = tunnel_get (&msg->owner, ntohl (msg->tunnel_id)); if (NULL == t) { - GNUNET_break (0); - GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); - return; - } + /* We don't know the tunnel */ + struct GNUNET_MESH_LocalMonitor warn; - /* Does client own tunnel? */ - if (t->owner->handle != client) - { - GNUNET_break (0); - GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + warn = *msg; + warn.npeers = htonl (UINT_MAX); + GNUNET_SERVER_notification_context_unicast (nc, client, + &warn.header, + GNUNET_NO); + GNUNET_SERVER_receive_done (client, GNUNET_OK); return; } - { - char buf[ntohs (message->size)] GNUNET_ALIGN; - struct GNUNET_MESH_Multicast *copy; + /* Initialize context */ + resp = GNUNET_malloc (USHRT_MAX); /* avoid realloc'ing on each step */ + *resp = *msg; + resp->npeers = 0; + ctx.msg = resp; + ctx.lookup = GNUNET_CONTAINER_multihashmap_create (4 * t->peers_total, + GNUNET_YES); + ctx.c = c; - copy = (struct GNUNET_MESH_Multicast *) buf; - memcpy (buf, message, ntohs (message->size)); - copy->oid = my_full_id; - copy->tid = htonl (t->id.tid); - copy->ttl = htonl (DEFAULT_TTL); - copy->mid = htonl (t->mid + 1); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - " calling generic handler...\n"); - handle_mesh_data_multicast (client, &my_full_id, ©->header, NULL, 0); - } + /* Collect and send information */ + tree_iterate_all (t->tree, &tunnel_tree_iterator, &ctx); + send_client_tunnel_info (&ctx); - /* receive done gets called when last copy is sent to a neighbor */ - return; + /* Free context */ + GNUNET_CONTAINER_multihashmap_destroy (ctx.lookup); + GNUNET_free (resp); + + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + "Monitor tunnel request from client %u completed\n", + c->id); + GNUNET_SERVER_receive_done (client, GNUNET_OK); } + /** * Functions to handle messages from clients */ static struct GNUNET_SERVER_MessageHandler client_handlers[] = { {&handle_local_new_client, NULL, GNUNET_MESSAGE_TYPE_MESH_LOCAL_CONNECT, 0}, + {&handle_local_announce_regex, NULL, + GNUNET_MESSAGE_TYPE_MESH_LOCAL_ANNOUNCE_REGEX, 0}, {&handle_local_tunnel_create, NULL, GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_CREATE, sizeof (struct GNUNET_MESH_TunnelMessage)}, {&handle_local_tunnel_destroy, NULL, GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_DESTROY, sizeof (struct GNUNET_MESH_TunnelMessage)}, + {&handle_local_tunnel_speed, NULL, + GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_MIN, + sizeof (struct GNUNET_MESH_TunnelMessage)}, + {&handle_local_tunnel_speed, NULL, + GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_MAX, + sizeof (struct GNUNET_MESH_TunnelMessage)}, + {&handle_local_tunnel_buffer, NULL, + GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_BUFFER, + sizeof (struct GNUNET_MESH_TunnelMessage)}, + {&handle_local_tunnel_buffer, NULL, + GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_NOBUFFER, + sizeof (struct GNUNET_MESH_TunnelMessage)}, {&handle_local_connect_add, NULL, GNUNET_MESSAGE_TYPE_MESH_LOCAL_PEER_ADD, sizeof (struct GNUNET_MESH_PeerControl)}, {&handle_local_connect_del, NULL, GNUNET_MESSAGE_TYPE_MESH_LOCAL_PEER_DEL, sizeof (struct GNUNET_MESH_PeerControl)}, + {&handle_local_blacklist, NULL, + GNUNET_MESSAGE_TYPE_MESH_LOCAL_PEER_BLACKLIST, + sizeof (struct GNUNET_MESH_PeerControl)}, + {&handle_local_unblacklist, NULL, + GNUNET_MESSAGE_TYPE_MESH_LOCAL_PEER_UNBLACKLIST, + sizeof (struct GNUNET_MESH_PeerControl)}, {&handle_local_connect_by_type, NULL, GNUNET_MESSAGE_TYPE_MESH_LOCAL_PEER_ADD_BY_TYPE, sizeof (struct GNUNET_MESH_ConnectPeerByType)}, + {&handle_local_connect_by_string, NULL, + GNUNET_MESSAGE_TYPE_MESH_LOCAL_PEER_ADD_BY_STRING, 0}, {&handle_local_unicast, NULL, GNUNET_MESSAGE_TYPE_MESH_UNICAST, 0}, {&handle_local_to_origin, NULL, GNUNET_MESSAGE_TYPE_MESH_TO_ORIGIN, 0}, {&handle_local_multicast, NULL, GNUNET_MESSAGE_TYPE_MESH_MULTICAST, 0}, + {&handle_local_ack, NULL, + GNUNET_MESSAGE_TYPE_MESH_LOCAL_ACK, + sizeof (struct GNUNET_MESH_LocalAck)}, + {&handle_local_get_tunnels, NULL, + GNUNET_MESSAGE_TYPE_MESH_LOCAL_INFO_TUNNELS, + sizeof (struct GNUNET_MessageHeader)}, + {&handle_local_show_tunnel, NULL, + GNUNET_MESSAGE_TYPE_MESH_LOCAL_INFO_TUNNEL, + sizeof (struct GNUNET_MESH_LocalMonitor)}, {NULL, NULL, 0, 0} }; @@ -4582,17 +8006,27 @@ static void core_init (void *cls, struct GNUNET_CORE_Handle *server, const struct GNUNET_PeerIdentity *identity) { + static int i = 0; GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Core init\n"); core_handle = server; if (0 != memcmp (identity, &my_full_id, sizeof (my_full_id)) || NULL == server) { GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("Wrong CORE service\n")); - GNUNET_SCHEDULER_shutdown (); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + " core id %s\n", + GNUNET_i2s (identity)); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + " my id %s\n", + GNUNET_i2s (&my_full_id)); + GNUNET_SCHEDULER_shutdown (); // Try gracefully + if (10 < i++) + GNUNET_abort(); // Try harder } return; } + /** * Method called whenever a given peer connects. * @@ -4627,9 +8061,11 @@ core_connect (void *cls, const struct GNUNET_PeerIdentity *peer, GNUNET_PEER_change_rc (myid, 1); GNUNET_PEER_change_rc (peer_info->id, 1); peer_info_add_path (peer_info, path, GNUNET_YES); + GNUNET_STATISTICS_update (stats, "# peers", 1, GNUNET_NO); return; } + /** * Method called whenever a peer disconnects. * @@ -4640,7 +8076,8 @@ static void core_disconnect (void *cls, const struct GNUNET_PeerIdentity *peer) { struct MeshPeerInfo *pi; - unsigned int i; + struct MeshPeerQueue *q; + struct MeshPeerQueue *n; DEBUG_CONN ("Peer disconnected\n"); pi = GNUNET_CONTAINER_multihashmap_get (peers, &peer->hashPubKey); @@ -4649,16 +8086,25 @@ core_disconnect (void *cls, const struct GNUNET_PeerIdentity *peer) GNUNET_break (0); return; } - for (i = 0; i < CORE_QUEUE_SIZE; i++) + q = pi->queue_head; + while (NULL != q) + { + n = q->next; + /* TODO try to reroute this traffic instead */ + queue_destroy(q, GNUNET_YES); + q = n; + } + if (NULL != pi->core_transmit) { - /* TODO: notify that the transmission failed */ - peer_info_cancel_transmission (pi, i); + GNUNET_CORE_notify_transmit_ready_cancel(pi->core_transmit); + pi->core_transmit = NULL; } peer_info_remove_path (pi, pi->id, myid); if (myid == pi->id) { DEBUG_CONN (" (self)\n"); } + GNUNET_STATISTICS_update (stats, "# peers", -1, GNUNET_NO); return; } @@ -4677,7 +8123,7 @@ core_disconnect (void *cls, const struct GNUNET_PeerIdentity *peer) * GNUNET_NO if not. */ static int -shutdown_tunnel (void *cls, const GNUNET_HashCode * key, void *value) +shutdown_tunnel (void *cls, const struct GNUNET_HashCode * key, void *value) { struct MeshTunnel *t = value; @@ -4695,14 +8141,27 @@ shutdown_tunnel (void *cls, const GNUNET_HashCode * key, void *value) * GNUNET_NO if not. */ static int -shutdown_peer (void *cls, const GNUNET_HashCode * key, void *value) +shutdown_peer (void *cls, const struct GNUNET_HashCode * key, void *value) { struct MeshPeerInfo *p = value; + struct MeshPeerQueue *q; + struct MeshPeerQueue *n; + q = p->queue_head; + while (NULL != q) + { + n = q->next; + if (q->peer == p) + { + queue_destroy(q, GNUNET_YES); + } + q = n; + } peer_info_destroy (p); return GNUNET_YES; } + /** * Task run during shutdown. * @@ -4719,6 +8178,11 @@ shutdown_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) GNUNET_CORE_disconnect (core_handle); core_handle = NULL; } + if (NULL != keygen) + { + GNUNET_CRYPTO_rsa_key_create_stop (keygen); + keygen = NULL; + } GNUNET_CONTAINER_multihashmap_iterate (tunnels, &shutdown_tunnel, NULL); GNUNET_CONTAINER_multihashmap_iterate (peers, &shutdown_peer, NULL); if (dht_handle != NULL) @@ -4736,28 +8200,50 @@ shutdown_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) GNUNET_SCHEDULER_cancel (announce_id_task); announce_id_task = GNUNET_SCHEDULER_NO_TASK; } + if (GNUNET_SCHEDULER_NO_TASK != announce_applications_task) + { + GNUNET_SCHEDULER_cancel (announce_applications_task); + announce_applications_task = GNUNET_SCHEDULER_NO_TASK; + } GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "shut down\n"); } + /** - * Process mesh requests. + * Callback for hostkey read/generation * - * @param cls closure - * @param server the initialized server - * @param c configuration to use + * @param cls Closure (Configuration handle). + * @param pk the private key + * @param emsg error message */ static void -run (void *cls, struct GNUNET_SERVER_Handle *server, - const struct GNUNET_CONFIGURATION_Handle *c) +key_generation_cb (void *cls, + struct GNUNET_CRYPTO_RsaPrivateKey *pk, + const char *emsg) { + const struct GNUNET_CONFIGURATION_Handle *c = cls; struct MeshPeerInfo *peer; struct MeshPeerPath *p; - char *keyfile; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "starting to run\n"); - server_handle = server; + keygen = NULL; + if (NULL == pk) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Mesh service could not access hostkey: %s. Exiting.\n"), + emsg); + GNUNET_SCHEDULER_shutdown (); + return; + } + my_private_key = pk; + GNUNET_CRYPTO_rsa_key_get_public (my_private_key, &my_public_key); + GNUNET_CRYPTO_hash (&my_public_key, sizeof (my_public_key), + &my_full_id.hashPubKey); + myid = GNUNET_PEER_intern (&my_full_id); + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + "Mesh for peer [%s] starting\n", + GNUNET_i2s(&my_full_id)); + core_handle = GNUNET_CORE_connect (c, /* Main configuration */ - CORE_QUEUE_SIZE, /* queue size */ NULL, /* Closure passed to MESH functions */ &core_init, /* Call core_init once connected */ &core_connect, /* Handle connects */ @@ -4767,7 +8253,7 @@ run (void *cls, struct GNUNET_SERVER_Handle *server, NULL, /* Don't notify about all outbound messages */ GNUNET_NO, /* For header-only out notification */ core_handlers); /* Register these handlers */ - + if (core_handle == NULL) { GNUNET_break (0); @@ -4775,80 +8261,192 @@ run (void *cls, struct GNUNET_SERVER_Handle *server, return; } + next_tid = 0; + next_local_tid = GNUNET_MESH_LOCAL_TUNNEL_ID_SERV; + + + GNUNET_SERVER_add_handlers (server_handle, client_handlers); + nc = GNUNET_SERVER_notification_context_create (server_handle, 1); + GNUNET_SERVER_disconnect_notify (server_handle, + &handle_local_client_disconnect, NULL); + + + clients = NULL; + clients_tail = NULL; + next_client_id = 0; + + announce_applications_task = GNUNET_SCHEDULER_NO_TASK; + announce_id_task = GNUNET_SCHEDULER_add_now (&announce_id, cls); + + /* Create a peer_info for the local peer */ + peer = peer_info_get (&my_full_id); + p = path_new (1); + p->peers[0] = myid; + GNUNET_PEER_change_rc (myid, 1); + peer_info_add_path (peer, p, GNUNET_YES); + GNUNET_SERVER_resume (server_handle); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Mesh service running\n"); +} + + +/** + * Process mesh requests. + * + * @param cls closure + * @param server the initialized server + * @param c configuration to use + */ +static void +run (void *cls, struct GNUNET_SERVER_Handle *server, + const struct GNUNET_CONFIGURATION_Handle *c) +{ + char *keyfile; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "starting to run\n"); + server_handle = server; + if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_filename (c, "GNUNETD", "HOSTKEY", &keyfile)) { GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _ - ("Mesh service is lacking key configuration settings. Exiting.\n")); + ("%s service is lacking key configuration settings (%s). Exiting.\n"), + "mesh", "hostkey"); GNUNET_SCHEDULER_shutdown (); return; } - my_private_key = GNUNET_CRYPTO_rsa_key_create_from_file (keyfile); - GNUNET_free (keyfile); - if (my_private_key == NULL) + + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_time (c, "MESH", "REFRESH_PATH_TIME", + &refresh_path_time)) { GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - _("Mesh service could not access hostkey. Exiting.\n")); + _ + ("%s service is lacking key configuration settings (%s). Exiting.\n"), + "mesh", "refresh path time"); GNUNET_SCHEDULER_shutdown (); return; } - GNUNET_CRYPTO_rsa_key_get_public (my_private_key, &my_public_key); - GNUNET_CRYPTO_hash (&my_public_key, sizeof (my_public_key), - &my_full_id.hashPubKey); - myid = GNUNET_PEER_intern (&my_full_id); -// // transport_handle = GNUNET_TRANSPORT_connect(c, -// // &my_full_id, -// // NULL, -// // NULL, -// // NULL, -// // NULL); + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_time (c, "MESH", "APP_ANNOUNCE_TIME", + &app_announce_time)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _ + ("%s service is lacking key configuration settings (%s). Exiting.\n"), + "mesh", "app announce time"); + GNUNET_SCHEDULER_shutdown (); + return; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "APP_ANNOUNCE_TIME %llu ms\n", + app_announce_time.rel_value); + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_time (c, "MESH", "ID_ANNOUNCE_TIME", + &id_announce_time)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _ + ("%s service is lacking key configuration settings (%s). Exiting.\n"), + "mesh", "id announce time"); + GNUNET_SCHEDULER_shutdown (); + return; + } - dht_handle = GNUNET_DHT_connect (c, 64); - if (dht_handle == NULL) + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_time (c, "MESH", "CONNECT_TIMEOUT", + &connect_timeout)) { - GNUNET_break (0); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _ + ("%s service is lacking key configuration settings (%s). Exiting.\n"), + "mesh", "connect timeout"); + GNUNET_SCHEDULER_shutdown (); + return; } - next_tid = 0; - next_local_tid = GNUNET_MESH_LOCAL_TUNNEL_ID_SERV; + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_number (c, "MESH", "MAX_MSGS_QUEUE", + &max_msgs_queue)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _ + ("%s service is lacking key configuration settings (%s). Exiting.\n"), + "mesh", "max msgs queue"); + GNUNET_SCHEDULER_shutdown (); + return; + } - tunnels = GNUNET_CONTAINER_multihashmap_create (32); - incoming_tunnels = GNUNET_CONTAINER_multihashmap_create (32); - peers = GNUNET_CONTAINER_multihashmap_create (32); - applications = GNUNET_CONTAINER_multihashmap_create (32); - types = GNUNET_CONTAINER_multihashmap_create (32); + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_number (c, "MESH", "MAX_TUNNELS", + &max_tunnels)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _ + ("%s service is lacking key configuration settings (%s). Exiting.\n"), + "mesh", "max tunnels"); + GNUNET_SCHEDULER_shutdown (); + return; + } - GNUNET_SERVER_add_handlers (server_handle, client_handlers); - nc = GNUNET_SERVER_notification_context_create (server_handle, - LOCAL_QUEUE_SIZE); - GNUNET_SERVER_disconnect_notify (server_handle, - &handle_local_client_disconnect, NULL); + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_number (c, "MESH", "DEFAULT_TTL", + &default_ttl)) + { + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + _ + ("%s service is lacking key configuration settings (%s). Using default (%u).\n"), + "mesh", "default ttl", 64); + default_ttl = 64; + } + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_number (c, "MESH", "MAX_PEERS", + &max_peers)) + { + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + _("%s service is lacking key configuration settings (%s). Using default (%u).\n"), + "mesh", "max peers", 1000); + max_peers = 1000; + } - clients = NULL; - clients_tail = NULL; - next_client_id = 0; + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_number (c, "MESH", "DHT_REPLICATION_LEVEL", + &dht_replication_level)) + { + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + _ + ("%s service is lacking key configuration settings (%s). Using default (%u).\n"), + "mesh", "dht replication level", 3); + dht_replication_level = 3; + } - announce_applications_task = GNUNET_SCHEDULER_NO_TASK; - announce_id_task = GNUNET_SCHEDULER_add_now (&announce_id, cls); + tunnels = GNUNET_CONTAINER_multihashmap_create (32, GNUNET_NO); + incoming_tunnels = GNUNET_CONTAINER_multihashmap_create (32, GNUNET_NO); + peers = GNUNET_CONTAINER_multihashmap_create (32, GNUNET_NO); + applications = GNUNET_CONTAINER_multihashmap_create (32, GNUNET_NO); + types = GNUNET_CONTAINER_multihashmap_create (32, GNUNET_NO); - /* Create a peer_info for the local peer */ - peer = peer_info_get (&my_full_id); - p = path_new (1); - p->peers[0] = myid; - GNUNET_PEER_change_rc (myid, 1); - peer_info_add_path (peer, p, GNUNET_YES); + dht_handle = GNUNET_DHT_connect (c, 64); + if (NULL == dht_handle) + { + GNUNET_break (0); + } + stats = GNUNET_STATISTICS_create ("mesh", c); + GNUNET_SERVER_suspend (server_handle); /* Scheduled the task to clean up when shutdown is called */ GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, &shutdown_task, NULL); - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "end of run()\n"); + keygen = GNUNET_CRYPTO_rsa_key_create_start (keyfile, + &key_generation_cb, + (void *) c); + GNUNET_free (keyfile); } + /** * The main function for the mesh service. * @@ -4860,13 +8458,19 @@ int main (int argc, char *const *argv) { int ret; + int r; GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "main()\n"); - ret = - (GNUNET_OK == - GNUNET_SERVICE_run (argc, argv, "mesh", GNUNET_SERVICE_OPTION_NONE, &run, - NULL)) ? 0 : 1; + r = GNUNET_SERVICE_run (argc, argv, "mesh", GNUNET_SERVICE_OPTION_NONE, &run, + NULL); + ret = (GNUNET_OK == r) ? 0 : 1; GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "main() END\n"); + INTERVAL_SHOW; + + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + "Mesh for peer [%s] FWD ACKs %u, BCK ACKs %u\n", + GNUNET_i2s(&my_full_id), debug_fwd_ack, debug_bck_ack); + return ret; } diff --git a/src/mesh/mesh.conf.in b/src/mesh/mesh.conf.in index 83a8938..9aa8b89 100644 --- a/src/mesh/mesh.conf.in +++ b/src/mesh/mesh.conf.in @@ -1,13 +1,20 @@ [mesh] AUTOSTART = YES -@UNIXONLY@ PORT = 2096 +@JAVAPORT@PORT = 2096 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-mesh ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; UNIXPATH = /tmp/gnunet-service-mesh.sock UNIX_MATCH_UID = YES UNIX_MATCH_GID = YES - +REFRESH_PATH_TIME = 30 min +APP_ANNOUNCE_TIME = 1 h +ID_ANNOUNCE_TIME = 1 h +CONNECT_TIMEOUT = 30 s +DEFAULT_TTL = 64 +DHT_REPLICATION_LEVEL = 3 +MAX_TUNNELS = 1000 +MAX_MSGS_QUEUE = 10000 +MAX_PEERS=1000 \ No newline at end of file diff --git a/src/mesh/mesh.h b/src/mesh/mesh.h index d8fc404..a5a817c 100644 --- a/src/mesh/mesh.h +++ b/src/mesh/mesh.h @@ -25,10 +25,21 @@ #ifndef MESH_H_ #define MESH_H_ + +#ifdef __cplusplus +extern "C" +{ +#if 0 /* keep Emacsens' auto-indent happy */ +} +#endif +#endif + #include #define MESH_DEBUG GNUNET_YES +#define INITIAL_WINDOW_SIZE 8 +#define ACK_THRESHOLD INITIAL_WINDOW_SIZE / 2 #include "platform.h" #include "gnunet_common.h" @@ -52,20 +63,29 @@ * * tunnel_create GNUNET_MESH_TunnelMessage * tunnel_destroy GNUNET_MESH_TunnelMessage + * tunnel_speed_max GNUNET_MESH_TunnelMessage + * tunnel_speed_min GNUNET_MESH_TunnelMessage + * tunnel_buffer GNUNET_MESH_TunnelMessage * * peer_request_connect_add GNUNET_MESH_PeerControl * peer_request_connect_del GNUNET_MESH_PeerControl * peer_request_connect_by_type GNUNET_MESH_ConnectPeerByType + * peer_request_connect_by_string GNUNET_MESH_ConnectPeerByString + * + * peer_blacklist GNUNET_MESH_PeerControl + * peer_unblacklist GNUNET_MESH_PeerControl * - * notify_transmit_ready *GNUNET_MESH_TransmitReady?* + * notify_transmit_ready None (queue / GNUNET_CLIENT_ntf_tmt_rdy) * notify_transmit_ready_cancel None (clear of internal data structures) * - * - * + * * EVENT MESSAGE USED * ----- ------------ - * data GNUNET_MESH_Data OR - * GNUNET_MESH_DataBroadcast + * data GNUNET_MESH_Unicast OR + * GNUNET_MESH_Multicast OR + * GNUNET_MESH_ToOrigin + * data ack GNUNET_MESH_LocalAck + * * new incoming tunnel GNUNET_MESH_PeerControl * peer connects to a tunnel GNUNET_MESH_PeerControl * peer disconnects from a tunnel GNUNET_MESH_PeerControl @@ -75,11 +95,13 @@ /************************** CONSTANTS ******************************/ /******************************************************************************/ -#define GNUNET_MESH_LOCAL_TUNNEL_ID_CLI 0x80000000 -#define GNUNET_MESH_LOCAL_TUNNEL_ID_SERV 0xB0000000 +#define GNUNET_MESH_LOCAL_TUNNEL_ID_CLI 0x80000000 +#define GNUNET_MESH_LOCAL_TUNNEL_ID_SERV 0xB0000000 + +#define HIGH_PID 0xFFFF0000 +#define LOW_PID 0x0000FFFF -#define CORE_QUEUE_SIZE 10 -#define LOCAL_QUEUE_SIZE 100 +#define PID_OVERFLOW(pid, max) (pid > HIGH_PID && max < LOW_PID) /******************************************************************************/ /************************** MESSAGES ******************************/ @@ -102,7 +124,7 @@ struct GNUNET_MESH_ClientConnect struct GNUNET_MessageHeader header; uint16_t applications GNUNET_PACKED; uint16_t types GNUNET_PACKED; - /* uint16_t list_apps[applications] */ + /* uint32_t list_apps[applications] */ /* uint16_t list_types[types] */ }; @@ -122,6 +144,7 @@ struct GNUNET_MESH_TunnelMessage { /** * Type: GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_[CREATE|DESTROY] + * GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_[MAX|MIN] * * Size: sizeof(struct GNUNET_MESH_TunnelMessage) */ @@ -155,8 +178,39 @@ struct GNUNET_MESH_TunnelNotification * Peer at the other end, if any */ struct GNUNET_PeerIdentity peer; + + /** + * Tunnel options (speed, buffering) + */ + uint32_t opt; +}; + +/** + * Message for announce of regular expressions. + */ +struct GNUNET_MESH_RegexAnnounce +{ + /** + * Type: GNUNET_MESSAGE_TYPE_MESH_LOCAL_ANNOUNCE_REGEX + * + * Size: sizeof(struct GNUNET_MESH_RegexAnnounce) + strlen (regex) + */ + struct GNUNET_MessageHeader header; + + /** + * How many characters do we want to put in an edge label. + */ + uint16_t compression_characters; + + /** + * Is this the last message for this regex? (for regex > 65k) + */ + int16_t last; + + /* regex payload */ }; + /** * Message for: * - request adding and deleting peers from a tunnel @@ -168,49 +222,131 @@ struct GNUNET_MESH_TunnelNotification struct GNUNET_MESH_PeerControl { - /** - * Type: GNUNET_MESSAGE_TYPE_MESH_LOCAL_CONNECT_PEER_[ADD|DEL] - * (client to service, client created tunnel) - * GNUNET_MESSAGE_TYPE_MESH_LOCAL_PEER_[CONNECTED|DISCONNECTED] - * (service to client) - * - * Size: sizeof(struct GNUNET_MESH_PeerControl) - */ + /** + * Type: GNUNET_MESSAGE_TYPE_MESH_LOCAL_CONNECT_PEER_[ADD|DEL|[UN]BLACKLIST] + * (client to service, client created tunnel) + * GNUNET_MESSAGE_TYPE_MESH_LOCAL_PEER_[CONNECTED|DISCONNECTED] + * (service to client) + * + * Size: sizeof(struct GNUNET_MESH_PeerControl) + */ struct GNUNET_MessageHeader header; - /** - * ID of a tunnel controlled by this client. - */ + /** + * ID of a tunnel controlled by this client. + */ MESH_TunnelNumber tunnel_id GNUNET_PACKED; - /** - * Peer to connect/disconnect. - */ + /** + * Peer to connect/disconnect. + */ struct GNUNET_PeerIdentity peer; }; /** - * Message for connecting to peers offering a certain service. + * Message for connecting to peers offering a service, by service number. */ struct GNUNET_MESH_ConnectPeerByType { /** * Type: GNUNET_MESSAGE_TYPE_MESH_LOCAL_CONNECT_PEER_BY_TYPE | * GNUNET_MESSAGE_TYPE_MESH_LOCAL_DISCONNECT_PEER_BY_TYPE + * + * Size: sizeof(struct GNUNET_MESH_ConnectPeerByType) */ struct GNUNET_MessageHeader header; + /** + * ID of a tunnel controlled by this client. + */ + MESH_TunnelNumber tunnel_id GNUNET_PACKED; + + /** + * Type specification + */ + GNUNET_MESH_ApplicationType type GNUNET_PACKED; +}; + + +/** + * Message for connecting to peers offering a service, by service string. + */ +struct GNUNET_MESH_ConnectPeerByString +{ + /** + * Type: GNUNET_MESSAGE_TYPE_MESH_LOCAL_PEER_ADD_BY_STRING + * + * Size: sizeof(struct GNUNET_MESH_ConnectPeerByString) + strlen (string) + */ + struct GNUNET_MessageHeader header; + + /** + * ID of a tunnel controlled by this client. + */ + MESH_TunnelNumber tunnel_id GNUNET_PACKED; + + /* String describing the service */ +}; + + +/** + * Message to allow the client send more data to the service + * (always service -> client). + */ +struct GNUNET_MESH_LocalAck +{ + /** + * Type: GNUNET_MESSAGE_TYPE_MESH_LOCAL_ACK + */ + struct GNUNET_MessageHeader header; + + /** + * ID of the tunnel allowed to send more data. + */ + MESH_TunnelNumber tunnel_id GNUNET_PACKED; + + /** + * ID of the last packet allowed. + */ + uint32_t max_pid GNUNET_PACKED; +}; + + +/** + * Message to inform the client about tunnels in the service. + */ +struct GNUNET_MESH_LocalMonitor +{ /** - * ID of a tunnel controlled by this client. + * Type: GNUNET_MESSAGE_TYPE_MESH_LOCAL_MONITOR[_TUNNEL] + */ + struct GNUNET_MessageHeader header; + + /** + * ID of the tunnel allowed to send more data. */ MESH_TunnelNumber tunnel_id GNUNET_PACKED; /** - * Type specification + * Number of peers in the tunnel. */ - GNUNET_MESH_ApplicationType type GNUNET_PACKED; + uint32_t npeers GNUNET_PACKED; + + /** + * Alignment. + */ + uint32_t reserved GNUNET_PACKED; + + /** + * ID of the owner of the tunnel (can be local peer). + */ + struct GNUNET_PeerIdentity owner; + + /* struct GNUNET_PeerIdentity peers[npeers] */ }; + + GNUNET_NETWORK_STRUCT_END /******************************************************************************/ @@ -259,5 +395,60 @@ enum MeshPeerState }; +/** + * Check if one pid is bigger than other, accounting for overflow. + * + * @param bigger Argument that should be bigger. + * @param smaller Argument that should be smaller. + * + * @return True if bigger (arg1) has a higher value than smaller (arg 2). + */ +int +GMC_is_pid_bigger (uint32_t bigger, uint32_t smaller); + + +/** + * Get the higher ACK value out of two values, taking in account overflow. + * + * @param a First ACK value. + * @param b Second ACK value. + * + * @return Highest ACK value from the two. + */ +uint32_t +GMC_max_pid (uint32_t a, uint32_t b); + + +/** + * Get the lower ACK value out of two values, taking in account overflow. + * + * @param a First ACK value. + * @param b Second ACK value. + * + * @return Lowest ACK value from the two. + */ +uint32_t +GMC_min_pid (uint32_t a, uint32_t b); + + +/** + * Convert a message type into a string to help debug + * Generated with: + * FIND: "#define ([^ ]+)[ ]*([0-9]+)" + * REPLACE: " case \2: return "\1"; break;" + * + * @param m Message type. + * + * @return Human readable string description. + */ +const char * +GNUNET_MESH_DEBUG_M2S (uint16_t m); + +#if 0 /* keep Emacsens' auto-indent happy */ +{ +#endif +#ifdef __cplusplus +} +#endif #endif diff --git a/src/mesh/mesh_api.c b/src/mesh/mesh_api.c index de931db..be2ec27 100644 --- a/src/mesh/mesh_api.c +++ b/src/mesh/mesh_api.c @@ -21,12 +21,14 @@ * @author Bartlomiej Polot * * STRUCTURE: - * - CONSTANTS * - DATA STRUCTURES + * - DECLARATIONS * - AUXILIARY FUNCTIONS * - RECEIVE HANDLERS * - SEND FUNCTIONS * - API CALL DEFINITIONS + * + * TODO: add regex to reconnect */ #include "platform.h" #include "gnunet_common.h" @@ -39,6 +41,7 @@ #define LOG(kind,...) GNUNET_log_from (kind, "mesh-api",__VA_ARGS__) +#define DEBUG_ACK GNUNET_YES /******************************************************************************/ /************************ DATA STRUCTURES ****************************/ @@ -91,12 +94,6 @@ struct GNUNET_MESH_TransmitHandle */ GNUNET_SCHEDULER_TaskIdentifier timeout_task; - /** - * Priority of the message. The queue is sorted by priority, - * control messages have the maximum priority (UINT32_MAX). - */ - uint32_t priority; - /** * Target of the message, 0 for multicast. This field * is only valid if 'notify' is non-NULL. @@ -135,9 +132,13 @@ struct GNUNET_MESH_Handle const GNUNET_MESH_ApplicationType *applications; /** - * Double linked list of the tunnels this client is connected to. + * Double linked list of the tunnels this client is connected to, head. */ struct GNUNET_MESH_Tunnel *tunnels_head; + + /** + * Double linked list of the tunnels this client is connected to, tail. + */ struct GNUNET_MESH_Tunnel *tunnels_tail; /** @@ -161,18 +162,29 @@ struct GNUNET_MESH_Handle void *cls; /** - * Messages to send to the service + * Messages to send to the service, head. */ struct GNUNET_MESH_TransmitHandle *th_head; + + /** + * Messages to send to the service, tail. + */ struct GNUNET_MESH_TransmitHandle *th_tail; /** * tid of the next tunnel to create (to avoid reusing IDs often) */ MESH_TunnelNumber next_tid; + + /** + * Number of handlers in the handlers array. + */ unsigned int n_handlers; + + /** + * Number of applications in the applications array. + */ unsigned int n_applications; - unsigned int max_queue_size; /** * Have we started the task to receive messages from the service @@ -180,11 +192,6 @@ struct GNUNET_MESH_Handle */ int in_receive; - /** - * Number of packets queued - */ - unsigned int npackets; - /** * Configuration given by the client, in case of reconnection */ @@ -199,6 +206,41 @@ struct GNUNET_MESH_Handle * Task for trying to reconnect. */ GNUNET_SCHEDULER_TaskIdentifier reconnect_task; + + /** + * Monitor callback + */ + GNUNET_MESH_TunnelsCB tunnels_cb; + + /** + * Monitor callback closure. + */ + void *tunnels_cls; + + /** + * Tunnel callback. + */ + GNUNET_MESH_TunnelCB tunnel_cb; + + /** + * Tunnel callback closure. + */ + void *tunnel_cls; + + /** + * All the peer in the tunnel so far. + */ + struct GNUNET_PeerIdentity *peers; + + /** + * How many peers we have in this tunnel so far. + */ + unsigned int tunnel_npeers; + +#if DEBUG_ACK + unsigned int acks_sent; + unsigned int acks_recv; +#endif }; @@ -232,9 +274,13 @@ struct GNUNET_MESH_Tunnel { /** - * DLL + * DLL next */ struct GNUNET_MESH_Tunnel *next; + + /** + * DLL prev + */ struct GNUNET_MESH_Tunnel *prev; /** @@ -288,22 +334,117 @@ struct GNUNET_MESH_Tunnel unsigned int npeers; /** - * Number of packets queued in this tunnel + * Size of packet queued in this tunnel */ - unsigned int npackets; + unsigned int packet_size; /** * Number of applications requested this tunnel */ unsigned int napps; + /** + * Is the tunnel throttled to the slowest peer? + */ + int speed_min; + + /** + * Is the tunnel allowed to buffer? + */ + int buffering; + + /** + * Next packet ID to send. + */ + uint32_t next_send_pid; + + /** + * Maximum allowed PID to send (ACK recevied). + */ + uint32_t max_send_pid; + + /** + * Last pid received from the service. + */ + uint32_t last_recv_pid; + + /** + * Which ACK value have we last sent to the service? + */ + uint32_t max_recv_pid; }; +/******************************************************************************/ +/*********************** DECLARATIONS *************************/ +/******************************************************************************/ + +/** + * Function called to send a message to the service. + * "buf" will be NULL and "size" zero if the socket was closed for writing in + * the meantime. + * + * @param cls closure, the mesh handle + * @param size number of bytes available in buf + * @param buf where the callee should write the connect message + * @return number of bytes written to buf + */ +static size_t +send_callback (void *cls, size_t size, void *buf); + + /******************************************************************************/ /*********************** AUXILIARY FUNCTIONS *************************/ /******************************************************************************/ +/** + * Check if transmission is a payload packet. + * + * @param th Transmission handle. + * + * @return GNUNET_YES if it is a payload packet, + * GNUNET_NO if it is a mesh management packet. + */ +static int +th_is_payload (struct GNUNET_MESH_TransmitHandle *th) +{ + return (th->notify != NULL) ? GNUNET_YES : GNUNET_NO; +} + + +/** + * Check whether there is any message ready in the queue and find the size. + * + * @param h Mesh handle. + * + * @return The size of the first ready message in the queue, + * 0 if there is none. + */ +static size_t +message_ready_size (struct GNUNET_MESH_Handle *h) +{ + struct GNUNET_MESH_TransmitHandle *th; + struct GNUNET_MESH_Tunnel *t; + + for (th = h->th_head; NULL != th; th = th->next) + { + t = th->tunnel; + if (GNUNET_NO == th_is_payload (th)) + { + LOG (GNUNET_ERROR_TYPE_DEBUG, " message internal\n"); + return th->size; + } + if (GNUNET_NO == GMC_is_pid_bigger(t->next_send_pid, t->max_send_pid)) + { + LOG (GNUNET_ERROR_TYPE_DEBUG, " message payload ok (%u <= %u)\n", + t->next_send_pid, t->max_send_pid); + return th->size; + } + } + return 0; +} + + /** * Get the tunnel handler for the tunnel specified by id from the given handle * @param h Mesh handle @@ -354,6 +495,9 @@ create_tunnel (struct GNUNET_MESH_Handle *h, MESH_TunnelNumber tid) { t->tid = tid; } + t->max_send_pid = INITIAL_WINDOW_SIZE - 1; + t->last_recv_pid = (uint32_t) -1; + t->buffering = GNUNET_YES; return t; } @@ -379,6 +523,8 @@ destroy_tunnel (struct GNUNET_MESH_Tunnel *t, int call_cleaner) struct GNUNET_MESH_TransmitHandle *next; unsigned int i; + LOG (GNUNET_ERROR_TYPE_DEBUG, "destroy_tunnel %X\n", t->tid); + if (NULL == t) { GNUNET_break (0); @@ -411,7 +557,7 @@ destroy_tunnel (struct GNUNET_MESH_Tunnel *t, int call_cleaner) continue; /* Clients should have aborted their requests already. * Management traffic should be ok, as clients can't cancel that */ - GNUNET_break (NULL == th->notify); + GNUNET_break (GNUNET_NO == th_is_payload(th)); GNUNET_CONTAINER_DLL_remove (h->th_head, h->th_tail, th); /* clean up request */ @@ -422,7 +568,7 @@ destroy_tunnel (struct GNUNET_MESH_Tunnel *t, int call_cleaner) /* if there are no more pending requests with mesh service, cancel active request */ /* Note: this should be unnecessary... */ - if ( (NULL == h->th_head) && (NULL != h->th)) + if ((0 == message_ready_size (h)) && (NULL != h->th)) { GNUNET_CLIENT_notify_transmit_ready_cancel (h->th); h->th = NULL; @@ -512,6 +658,7 @@ remove_peer_from_tunnel (struct GNUNET_MESH_Peer *p) /** * Notify client that the transmission has timed out + * * @param cls closure * @param tc task context */ @@ -523,12 +670,13 @@ timeout_transmission (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) mesh = th->tunnel->mesh; GNUNET_CONTAINER_DLL_remove (mesh->th_head, mesh->th_tail, th); - if (th->notify != NULL) + th->tunnel->packet_size = 0; + if (GNUNET_YES == th_is_payload (th)) th->notify (th->notify_cls, 0, NULL); GNUNET_free (th); - if ((NULL == mesh->th_head) && (NULL != mesh->th)) + if ((0 == message_ready_size (mesh)) && (NULL != mesh->th)) { - /* queue empty, no point in asking for transmission */ + /* nothing ready to transmit, no point in asking for transmission */ GNUNET_CLIENT_notify_transmit_ready_cancel (mesh->th); mesh->th = NULL; } @@ -536,7 +684,7 @@ timeout_transmission (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) /** - * Add a transmit handle to the transmission queue by priority and set the + * Add a transmit handle to the transmission queue and set the * timeout if needed. * * @param h mesh handle with the queue head and tail @@ -546,16 +694,7 @@ static void add_to_queue (struct GNUNET_MESH_Handle *h, struct GNUNET_MESH_TransmitHandle *th) { - struct GNUNET_MESH_TransmitHandle *p; - - p = h->th_head; - while ((NULL != p) && (th->priority <= p->priority)) - p = p->next; - if (NULL == p) - p = h->th_tail; - else - p = p->prev; - GNUNET_CONTAINER_DLL_insert_after (h->th_head, h->th_tail, p, th); + GNUNET_CONTAINER_DLL_insert_tail (h->th_head, h->th_tail, th); if (GNUNET_TIME_UNIT_FOREVER_ABS.abs_value == th->timeout.abs_value) return; th->timeout_task = @@ -579,6 +718,48 @@ send_packet (struct GNUNET_MESH_Handle *h, struct GNUNET_MESH_Tunnel *tunnel); +/** + * Send an ack on the tunnel to confirm the processing of a message. + * + * @param h Mesh handle. + * @param t Tunnel on which to send the ACK. + */ +static void +send_ack (struct GNUNET_MESH_Handle *h, struct GNUNET_MESH_Tunnel *t) +{ + struct GNUNET_MESH_LocalAck msg; + uint32_t delta; + + delta = t->max_recv_pid - t->last_recv_pid; + if (delta > ACK_THRESHOLD) + { + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Not sending ACK on tunnel %X: ACK: %u, PID: %u, buffer %u\n", + t->tid, t->max_recv_pid, t->last_recv_pid, delta); + return; + } + if (GNUNET_YES == t->buffering) + t->max_recv_pid = t->last_recv_pid + INITIAL_WINDOW_SIZE; + else + t->max_recv_pid = t->last_recv_pid + 1; + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Sending ACK on tunnel %X: %u\n", + t->tid, t->max_recv_pid); + msg.header.type = htons (GNUNET_MESSAGE_TYPE_MESH_LOCAL_ACK); + msg.header.size = htons (sizeof (msg)); + msg.tunnel_id = htonl (t->tid); + msg.max_pid = htonl (t->max_recv_pid); + +#if DEBUG_ACK + t->mesh->acks_sent++; +#endif + + send_packet (h, &msg.header, t); + return; +} + + + /** * Reconnect callback: tries to reconnect again after a failer previous * reconnecttion @@ -620,11 +801,16 @@ send_connect (struct GNUNET_MESH_Handle *h) for (napps = 0; napps < h->n_applications; napps++) { apps[napps] = htonl (h->applications[napps]); - LOG (GNUNET_ERROR_TYPE_DEBUG, " app %u\n", h->applications[napps]); + LOG (GNUNET_ERROR_TYPE_DEBUG, " app %u\n", + h->applications[napps]); } types = (uint16_t *) & apps[napps]; for (ntypes = 0; ntypes < h->n_handlers; ntypes++) + { types[ntypes] = htons (h->message_handlers[ntypes].type); + LOG (GNUNET_ERROR_TYPE_DEBUG, " type %u\n", + h->message_handlers[ntypes].type); + } msg->applications = htons (napps); msg->types = htons (ntypes); LOG (GNUNET_ERROR_TYPE_DEBUG, @@ -652,8 +838,9 @@ do_reconnect (struct GNUNET_MESH_Handle *h) LOG (GNUNET_ERROR_TYPE_DEBUG, "*****************************\n"); LOG (GNUNET_ERROR_TYPE_DEBUG, "******* RECONNECT *******\n"); LOG (GNUNET_ERROR_TYPE_DEBUG, "*****************************\n"); + LOG (GNUNET_ERROR_TYPE_DEBUG, "******** on %p *******\n", h); + LOG (GNUNET_ERROR_TYPE_DEBUG, "*****************************\n"); - h->in_receive = GNUNET_NO; /* disconnect */ if (NULL != h->th) { @@ -675,8 +862,10 @@ do_reconnect (struct GNUNET_MESH_Handle *h) GNUNET_TIME_relative_min (GNUNET_TIME_UNIT_SECONDS, GNUNET_TIME_relative_multiply (h->reconnect_time, 2)); - LOG (GNUNET_ERROR_TYPE_DEBUG, " Next retry in %sms\n", - GNUNET_TIME_relative_to_string (h->reconnect_time)); + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Next retry in %s\n", + GNUNET_STRINGS_relative_time_to_string (h->reconnect_time, + GNUNET_NO)); GNUNET_break (0); return GNUNET_NO; } @@ -699,6 +888,9 @@ do_reconnect (struct GNUNET_MESH_Handle *h) */ continue; } + t->next_send_pid = 0; + t->max_send_pid = INITIAL_WINDOW_SIZE - 1; + t->last_recv_pid = (uint32_t) -1; tmsg.header.type = htons (GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_CREATE); tmsg.header.size = htons (sizeof (struct GNUNET_MESH_TunnelMessage)); tmsg.tunnel_id = htonl (t->tid); @@ -709,14 +901,13 @@ do_reconnect (struct GNUNET_MESH_Handle *h) pmsg.tunnel_id = htonl (t->tid); /* Reconnect all peers */ - for (i = 0; i < t->npeers; i++) + /* If the tunnel was "by type", dont connect individual peers */ + for (i = 0; i < t->npeers && 0 == t->napps; i++) { GNUNET_PEER_resolve (t->peers[i]->id, &pmsg.peer); if (NULL != t->disconnect_handler && t->peers[i]->connected) t->disconnect_handler (t->cls, &pmsg.peer); - /* If the tunnel was "by type", dont connect individual peers */ - if (0 == t->napps) - send_packet (t->mesh, &pmsg.header, t); + send_packet (t->mesh, &pmsg.header, t); } /* Reconnect all types, if any */ for (i = 0; i < t->napps; i++) @@ -729,6 +920,10 @@ do_reconnect (struct GNUNET_MESH_Handle *h) msg.type = htonl (t->apps[i]); send_packet (t->mesh, &msg.header, t); } + if (GNUNET_NO == t->buffering) + GNUNET_MESH_tunnel_buffer (t, GNUNET_NO); + if (GNUNET_YES == t->speed_min) + GNUNET_MESH_tunnel_speed_min (t); } return GNUNET_YES; } @@ -763,6 +958,7 @@ static void reconnect (struct GNUNET_MESH_Handle *h) { LOG (GNUNET_ERROR_TYPE_DEBUG, "Requested RECONNECT\n"); + h->in_receive = GNUNET_NO; if (GNUNET_SCHEDULER_NO_TASK == h->reconnect_task) h->reconnect_task = GNUNET_SCHEDULER_add_delayed (h->reconnect_time, &reconnect_cbk, h); @@ -787,6 +983,7 @@ process_tunnel_created (struct GNUNET_MESH_Handle *h, MESH_TunnelNumber tid; tid = ntohl (msg->tunnel_id); + LOG (GNUNET_ERROR_TYPE_DEBUG, "Creating incoming tunnel %X\n", tid); if (tid < GNUNET_MESH_LOCAL_TUNNEL_ID_SERV) { GNUNET_break (0); @@ -807,10 +1004,17 @@ process_tunnel_created (struct GNUNET_MESH_Handle *h, GNUNET_PEER_change_rc (t->owner, 1); t->mesh = h; t->tid = tid; + if ((msg->opt & MESH_TUNNEL_OPT_NOBUFFER) != 0) + t->buffering = GNUNET_NO; + else + t->buffering = GNUNET_YES; + if ((msg->opt & MESH_TUNNEL_OPT_SPEED_MIN) != 0) + t->speed_min = GNUNET_YES; atsi.type = 0; atsi.value = 0; + LOG (GNUNET_ERROR_TYPE_DEBUG, " created tunnel %p\n", t); t->ctx = h->new_tunnel (h->cls, t, &msg->peer, &atsi); - LOG (GNUNET_ERROR_TYPE_DEBUG, "new incoming tunnel %X\n", t->tid); + LOG (GNUNET_ERROR_TYPE_DEBUG, "User notified\n"); } else { @@ -936,6 +1140,7 @@ process_incoming_data (struct GNUNET_MESH_Handle *h, struct GNUNET_MESH_ToOrigin *to_orig; struct GNUNET_MESH_Tunnel *t; unsigned int i; + uint32_t pid; uint16_t type; LOG (GNUNET_ERROR_TYPE_DEBUG, "Got a data message!\n"); @@ -948,7 +1153,8 @@ process_incoming_data (struct GNUNET_MESH_Handle *h, t = retrieve_tunnel (h, ntohl (ucast->tid)); payload = (struct GNUNET_MessageHeader *) &ucast[1]; peer = &ucast->oid; - LOG (GNUNET_ERROR_TYPE_DEBUG, " ucast on tunnel %s [%x]\n", + pid = ntohl (ucast->pid); + LOG (GNUNET_ERROR_TYPE_DEBUG, " ucast on tunnel %s [%X]\n", GNUNET_i2s (peer), ntohl (ucast->tid)); break; case GNUNET_MESSAGE_TYPE_MESH_MULTICAST: @@ -956,7 +1162,8 @@ process_incoming_data (struct GNUNET_MESH_Handle *h, t = retrieve_tunnel (h, ntohl (mcast->tid)); payload = (struct GNUNET_MessageHeader *) &mcast[1]; peer = &mcast->oid; - LOG (GNUNET_ERROR_TYPE_DEBUG, " mcast on tunnel %s [%x]\n", + pid = ntohl (mcast->pid); + LOG (GNUNET_ERROR_TYPE_DEBUG, " mcast on tunnel %s [%X]\n", GNUNET_i2s (peer), ntohl (mcast->tid)); break; case GNUNET_MESSAGE_TYPE_MESH_TO_ORIGIN: @@ -964,19 +1171,34 @@ process_incoming_data (struct GNUNET_MESH_Handle *h, t = retrieve_tunnel (h, ntohl (to_orig->tid)); payload = (struct GNUNET_MessageHeader *) &to_orig[1]; peer = &to_orig->sender; - LOG (GNUNET_ERROR_TYPE_DEBUG, " torig on tunnel %s [%x]\n", + pid = ntohl (to_orig->pid); + LOG (GNUNET_ERROR_TYPE_DEBUG, " torig on tunnel %s [%X]\n", GNUNET_i2s (peer), ntohl (to_orig->tid)); break; default: GNUNET_break (0); return GNUNET_YES; } + LOG (GNUNET_ERROR_TYPE_DEBUG, " pid %u\n", pid); if (NULL == t) { - /* Tunnel was ignored, probably service didn't get it yet */ + /* Tunnel was ignored/destroyed, probably service didn't get it yet */ + LOG (GNUNET_ERROR_TYPE_DEBUG, " ignored!\n"); return GNUNET_YES; } + if (GNUNET_YES == + GMC_is_pid_bigger(pid, t->max_recv_pid)) + { + GNUNET_break (0); + LOG (GNUNET_ERROR_TYPE_WARNING, + " unauthorized message! (%u, max %u)\n", + pid, t->max_recv_pid); + // FIXME fc what now? accept? reject? + return GNUNET_YES; + } + t->last_recv_pid = pid; type = ntohs (payload->type); + send_ack (h, t); for (i = 0; i < h->n_handlers; i++) { handler = &h->message_handlers[i]; @@ -989,15 +1211,14 @@ process_incoming_data (struct GNUNET_MESH_Handle *h, if (GNUNET_OK != handler->callback (h->cls, t, &t->ctx, peer, payload, &atsi)) { - LOG (GNUNET_ERROR_TYPE_DEBUG, "MESH: callback caused disconnection\n"); + LOG (GNUNET_ERROR_TYPE_DEBUG, "callback caused disconnection\n"); GNUNET_MESH_disconnect (h); return GNUNET_NO; } else { LOG (GNUNET_ERROR_TYPE_DEBUG, - "MESH: callback completed successfully\n"); - + "callback completed successfully\n"); } } } @@ -1005,6 +1226,160 @@ process_incoming_data (struct GNUNET_MESH_Handle *h, } +/** + * Process a local ACK message, enabling the client to send + * more data to the service. + * + * @param h Mesh handle. + * @param message Message itself. + */ +static void +process_ack (struct GNUNET_MESH_Handle *h, + const struct GNUNET_MessageHeader *message) +{ + struct GNUNET_MESH_LocalAck *msg; + struct GNUNET_MESH_Tunnel *t; + uint32_t ack; + + LOG (GNUNET_ERROR_TYPE_DEBUG, "Got an ACK!\n"); + h->acks_recv++; + msg = (struct GNUNET_MESH_LocalAck *) message; + + t = retrieve_tunnel (h, ntohl (msg->tunnel_id)); + + if (NULL == t) + { + LOG (GNUNET_ERROR_TYPE_WARNING, + "ACK on unknown tunnel %X\n", + ntohl (msg->tunnel_id)); + return; + } + ack = ntohl (msg->max_pid); + LOG (GNUNET_ERROR_TYPE_DEBUG, " on tunnel %X, ack %u!\n", t->tid, ack); + if (GNUNET_YES == GMC_is_pid_bigger(ack, t->max_send_pid)) + t->max_send_pid = ack; + else + return; + if (NULL == h->th && 0 < t->packet_size) + { + LOG (GNUNET_ERROR_TYPE_DEBUG, " tmt rdy was NULL, requesting!\n", t->tid, ack); + h->th = + GNUNET_CLIENT_notify_transmit_ready (h->client, t->packet_size, + GNUNET_TIME_UNIT_FOREVER_REL, + GNUNET_YES, &send_callback, h); + } +} + + +/** + * Process a local reply about info on all tunnels, pass info to the user. + * + * @param h Mesh handle. + * @param message Message itself. + */ +static void +process_get_tunnels (struct GNUNET_MESH_Handle *h, + const struct GNUNET_MessageHeader *message) +{ + struct GNUNET_MESH_LocalMonitor *msg; + uint32_t npeers; + + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Get Tunnels messasge received\n"); + + if (NULL == h->tunnels_cb) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, " ignored\n"); + return; + } + + msg = (struct GNUNET_MESH_LocalMonitor *) message; + npeers = ntohl (msg->npeers); + if (ntohs (message->size) != + (sizeof (struct GNUNET_MESH_LocalMonitor) + + npeers * sizeof (struct GNUNET_PeerIdentity))) + { + GNUNET_break_op (0); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Get tunnels message: size %hu - expected %u (%u peers)\n", + ntohs (message->size), + sizeof (struct GNUNET_MESH_LocalMonitor) + + npeers * sizeof (struct GNUNET_PeerIdentity), + npeers); + return; + } + h->tunnels_cb (h->tunnels_cls, + &msg->owner, + ntohl (msg->tunnel_id), + (struct GNUNET_PeerIdentity *) &msg[1], + npeers); +} + + + +/** + * Process a local monitor_tunnel reply, pass info to the user. + * + * @param h Mesh handle. + * @param message Message itself. + */ +static void +process_show_tunnel (struct GNUNET_MESH_Handle *h, + const struct GNUNET_MessageHeader *message) +{ + struct GNUNET_MESH_LocalMonitor *msg; + struct GNUNET_PeerIdentity *new_peers; + uint32_t *new_parents; + size_t esize; + uint32_t npeers; + unsigned int i; + + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Show Tunnel messasge received\n"); + + if (NULL == h->tunnel_cb) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, " ignored\n"); + return; + } + + /* Verify message sanity */ + msg = (struct GNUNET_MESH_LocalMonitor *) message; + npeers = ntohl (msg->npeers); + esize = sizeof (struct GNUNET_MESH_LocalMonitor); + esize += npeers * (sizeof (struct GNUNET_PeerIdentity) + sizeof (uint32_t)); + if (ntohs (message->size) != esize) + { + GNUNET_break_op (0); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Show tunnel message: size %hu - expected %u (%u peers)\n", + ntohs (message->size), + esize, + npeers); + + h->tunnel_cb (h->tunnel_cls, NULL, NULL); + h->tunnel_cb = NULL; + h->tunnel_cls = NULL; + h->tunnel_npeers = 0; + GNUNET_free_non_null (h->peers); + h->peers = NULL; + + return; + } + + new_peers = (struct GNUNET_PeerIdentity *) &msg[1]; + new_parents = (uint32_t *) &new_peers[npeers]; + + h->peers = GNUNET_realloc (h->peers, h->tunnel_npeers + npeers); + memcpy (&h->peers[h->tunnel_npeers], + new_peers, + npeers * sizeof (struct GNUNET_PeerIdentity)); + h->tunnel_npeers += npeers; + for (i = 0; i < npeers; i++) + h->tunnel_cb (h->tunnel_cls, + &new_peers[i], + &h->peers[new_parents[i]]); +} + + /** * Function to process all messages received from the service * @@ -1018,12 +1393,15 @@ msg_received (void *cls, const struct GNUNET_MessageHeader *msg) if (msg == NULL) { - LOG (GNUNET_ERROR_TYPE_DEBUG, "Received NULL msg\n"); + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Mesh service disconnected, reconnecting\n", h); reconnect (h); return; } - LOG (GNUNET_ERROR_TYPE_DEBUG, "received a message type %hu from MESH\n", - ntohs (msg->type)); + LOG (GNUNET_ERROR_TYPE_DEBUG, "\n", + GNUNET_MESH_DEBUG_M2S (ntohs (msg->type))); + LOG (GNUNET_ERROR_TYPE_DEBUG, "Received a message: %s\n", + GNUNET_MESH_DEBUG_M2S (ntohs (msg->type))); switch (ntohs (msg->type)) { /* Notify of a new incoming tunnel */ @@ -1046,15 +1424,32 @@ msg_received (void *cls, const struct GNUNET_MessageHeader *msg) if (GNUNET_NO == process_incoming_data (h, msg)) return; break; - /* We shouldn't get any other packages, log and ignore */ + case GNUNET_MESSAGE_TYPE_MESH_LOCAL_ACK: + process_ack (h, msg); + break; + case GNUNET_MESSAGE_TYPE_MESH_LOCAL_INFO_TUNNELS: + process_get_tunnels (h, msg); + break; + case GNUNET_MESSAGE_TYPE_MESH_LOCAL_INFO_TUNNEL: + process_show_tunnel (h, msg); + break; default: + /* We shouldn't get any other packages, log and ignore */ LOG (GNUNET_ERROR_TYPE_WARNING, - "MESH: unsolicited message form service (type %d)\n", - ntohs (msg->type)); + "unsolicited message form service (type %s)\n", + GNUNET_MESH_DEBUG_M2S (ntohs (msg->type))); } LOG (GNUNET_ERROR_TYPE_DEBUG, "message processed\n"); - GNUNET_CLIENT_receive (h->client, &msg_received, h, - GNUNET_TIME_UNIT_FOREVER_REL); + if (GNUNET_YES == h->in_receive) + { + GNUNET_CLIENT_receive (h->client, &msg_received, h, + GNUNET_TIME_UNIT_FOREVER_REL); + } + else + { + LOG (GNUNET_ERROR_TYPE_DEBUG, + "in receive off, not calling CLIENT_receive\n"); + } } @@ -1077,24 +1472,39 @@ send_callback (void *cls, size_t size, void *buf) { struct GNUNET_MESH_Handle *h = cls; struct GNUNET_MESH_TransmitHandle *th; + struct GNUNET_MESH_TransmitHandle *next; + struct GNUNET_MESH_Tunnel *t; char *cbuf = buf; size_t tsize; size_t psize; + size_t nsize; + LOG (GNUNET_ERROR_TYPE_DEBUG, "\n"); LOG (GNUNET_ERROR_TYPE_DEBUG, "Send packet() Buffer %u\n", size); - h->th = NULL; if ((0 == size) || (NULL == buf)) { - LOG (GNUNET_ERROR_TYPE_DEBUG, "Received NULL callback\n"); + LOG (GNUNET_ERROR_TYPE_DEBUG, "Received NULL send callback on %p\n", h); reconnect (h); + h->th = NULL; return 0; } tsize = 0; - while ((NULL != (th = h->th_head)) && (size >= th->size)) + next = h->th_head; + nsize = message_ready_size (h); + while ((NULL != (th = next)) && (0 < nsize) && (size >= nsize)) { - if (NULL != th->notify) + t = th->tunnel; + if (GNUNET_YES == th_is_payload (th)) { - if (th->tunnel->tid >= GNUNET_MESH_LOCAL_TUNNEL_ID_SERV) + LOG (GNUNET_ERROR_TYPE_DEBUG, " payload\n"); + if (GNUNET_YES == GMC_is_pid_bigger(t->next_send_pid, t->max_send_pid)) + { + /* This tunnel is not ready to transmit yet, try next message */ + next = th->next; + continue; + } + t->packet_size = 0; + if (t->tid >= GNUNET_MESH_LOCAL_TUNNEL_ID_SERV) { /* traffic to origin */ struct GNUNET_MESH_ToOrigin to; @@ -1103,15 +1513,17 @@ send_callback (void *cls, size_t size, void *buf) GNUNET_assert (size >= th->size); mh = (struct GNUNET_MessageHeader *) &cbuf[sizeof (to)]; psize = th->notify (th->notify_cls, size - sizeof (to), mh); - LOG (GNUNET_ERROR_TYPE_DEBUG, " to origin, type %u\n", - ntohs (mh->type)); + LOG (GNUNET_ERROR_TYPE_DEBUG, " to origin, type %s\n", + GNUNET_MESH_DEBUG_M2S (ntohs (mh->type))); if (psize > 0) { psize += sizeof (to); GNUNET_assert (size >= psize); to.header.size = htons (psize); to.header.type = htons (GNUNET_MESSAGE_TYPE_MESH_TO_ORIGIN); - to.tid = htonl (th->tunnel->tid); + to.tid = htonl (t->tid); + to.pid = htonl (t->next_send_pid); + to.ttl = 0; memset (&to.oid, 0, sizeof (struct GNUNET_PeerIdentity)); memset (&to.sender, 0, sizeof (struct GNUNET_PeerIdentity)); memcpy (cbuf, &to, sizeof (to)); @@ -1126,16 +1538,16 @@ send_callback (void *cls, size_t size, void *buf) GNUNET_assert (size >= th->size); mh = (struct GNUNET_MessageHeader *) &cbuf[sizeof (mc)]; psize = th->notify (th->notify_cls, size - sizeof (mc), mh); - LOG (GNUNET_ERROR_TYPE_DEBUG, " multicast, type %u\n", - ntohs (mh->type)); + LOG (GNUNET_ERROR_TYPE_DEBUG, " multicast, type %s\n", + GNUNET_MESH_DEBUG_M2S (ntohs (mh->type))); if (psize > 0) { psize += sizeof (mc); GNUNET_assert (size >= psize); mc.header.size = htons (psize); mc.header.type = htons (GNUNET_MESSAGE_TYPE_MESH_MULTICAST); - mc.tid = htonl (th->tunnel->tid); - mc.mid = 0; + mc.tid = htonl (t->tid); + mc.pid = htonl (t->next_send_pid); mc.ttl = 0; memset (&mc.oid, 0, sizeof (struct GNUNET_PeerIdentity)); memcpy (cbuf, &mc, sizeof (mc)); @@ -1150,56 +1562,69 @@ send_callback (void *cls, size_t size, void *buf) GNUNET_assert (size >= th->size); mh = (struct GNUNET_MessageHeader *) &cbuf[sizeof (uc)]; psize = th->notify (th->notify_cls, size - sizeof (uc), mh); - LOG (GNUNET_ERROR_TYPE_DEBUG, " unicast, type %u\n", - ntohs (mh->type)); + LOG (GNUNET_ERROR_TYPE_DEBUG, " unicast, type %s\n", + GNUNET_MESH_DEBUG_M2S (ntohs (mh->type))); if (psize > 0) { psize += sizeof (uc); GNUNET_assert (size >= psize); uc.header.size = htons (psize); uc.header.type = htons (GNUNET_MESSAGE_TYPE_MESH_UNICAST); - uc.tid = htonl (th->tunnel->tid); + uc.tid = htonl (t->tid); + uc.pid = htonl (t->next_send_pid); + uc.ttl = 0; memset (&uc.oid, 0, sizeof (struct GNUNET_PeerIdentity)); GNUNET_PEER_resolve (th->target, &uc.destination); memcpy (cbuf, &uc, sizeof (uc)); } } + t->next_send_pid++; } else { + struct GNUNET_MessageHeader *mh = (struct GNUNET_MessageHeader *) &th[1]; + + LOG (GNUNET_ERROR_TYPE_DEBUG, " mesh traffic, type %s\n", + GNUNET_MESH_DEBUG_M2S (ntohs (mh->type))); memcpy (cbuf, &th[1], th->size); psize = th->size; } if (th->timeout_task != GNUNET_SCHEDULER_NO_TASK) GNUNET_SCHEDULER_cancel (th->timeout_task); - if (NULL != th->notify) - { - th->tunnel->mesh->npackets--; - th->tunnel->npackets--; - } GNUNET_CONTAINER_DLL_remove (h->th_head, h->th_tail, th); GNUNET_free (th); + next = h->th_head; + nsize = message_ready_size (h); cbuf += psize; size -= psize; tsize += psize; } LOG (GNUNET_ERROR_TYPE_DEBUG, " total size: %u\n", tsize); - if (NULL != (th = h->th_head)) + h->th = NULL; + size = message_ready_size (h); + if (0 != size) { - LOG (GNUNET_ERROR_TYPE_DEBUG, " next size: %u\n", th->size); - if (NULL == h->th) - h->th = - GNUNET_CLIENT_notify_transmit_ready (h->client, th->size, - GNUNET_TIME_UNIT_FOREVER_REL, - GNUNET_YES, &send_callback, h); + LOG (GNUNET_ERROR_TYPE_DEBUG, " next size: %u\n", size); + h->th = + GNUNET_CLIENT_notify_transmit_ready (h->client, size, + GNUNET_TIME_UNIT_FOREVER_REL, + GNUNET_YES, &send_callback, h); + } + else + { + if (NULL != h->th_head) + LOG (GNUNET_ERROR_TYPE_DEBUG, " can't transmit any more\n"); + else + LOG (GNUNET_ERROR_TYPE_DEBUG, " nothing left to transmit\n"); } - LOG (GNUNET_ERROR_TYPE_DEBUG, "Send packet() END\n"); if (GNUNET_NO == h->in_receive) { + LOG (GNUNET_ERROR_TYPE_DEBUG, " start receiving from service\n"); h->in_receive = GNUNET_YES; GNUNET_CLIENT_receive (h->client, &msg_received, h, GNUNET_TIME_UNIT_FOREVER_REL); } + LOG (GNUNET_ERROR_TYPE_DEBUG, "Send packet() END\n"); return tsize; } @@ -1221,16 +1646,19 @@ send_packet (struct GNUNET_MESH_Handle *h, struct GNUNET_MESH_TransmitHandle *th; size_t msize; + LOG (GNUNET_ERROR_TYPE_DEBUG, " Sending message to service: %s\n", + GNUNET_MESH_DEBUG_M2S(ntohs(msg->type))); msize = ntohs (msg->size); th = GNUNET_malloc (sizeof (struct GNUNET_MESH_TransmitHandle) + msize); - th->priority = UINT32_MAX; th->timeout = GNUNET_TIME_UNIT_FOREVER_ABS; th->size = msize; th->tunnel = tunnel; memcpy (&th[1], msg, msize); add_to_queue (h, th); + LOG (GNUNET_ERROR_TYPE_DEBUG, " queued\n"); if (NULL != h->th) return; + LOG (GNUNET_ERROR_TYPE_DEBUG, " calling ntfy tmt rdy for %u bytes\n", msize); h->th = GNUNET_CLIENT_notify_transmit_ready (h->client, msize, GNUNET_TIME_UNIT_FOREVER_REL, @@ -1246,9 +1674,6 @@ send_packet (struct GNUNET_MESH_Handle *h, * Connect to the mesh service. * * @param cfg configuration to use - * @param queue_size size of the data message queue, shared among all tunnels - * (each tunnel is guaranteed to accept at least one message, - * no matter what is the status of other tunnels) * @param cls closure for the various callbacks that follow * (including handlers in the handlers array) * @param new_tunnel function called when an *inbound* tunnel is created @@ -1264,8 +1689,7 @@ send_packet (struct GNUNET_MESH_Handle *h, * (in this case, init is never called) */ struct GNUNET_MESH_Handle * -GNUNET_MESH_connect (const struct GNUNET_CONFIGURATION_Handle *cfg, - unsigned int queue_size, void *cls, +GNUNET_MESH_connect (const struct GNUNET_CONFIGURATION_Handle *cfg, void *cls, GNUNET_MESH_InboundTunnelNotificationHandler new_tunnel, GNUNET_MESH_TunnelEndHandler cleaner, const struct GNUNET_MESH_MessageHandler *handlers, @@ -1275,8 +1699,8 @@ GNUNET_MESH_connect (const struct GNUNET_CONFIGURATION_Handle *cfg, LOG (GNUNET_ERROR_TYPE_DEBUG, "GNUNET_MESH_connect()\n"); h = GNUNET_malloc (sizeof (struct GNUNET_MESH_Handle)); + LOG (GNUNET_ERROR_TYPE_DEBUG, " addr %p\n", h); h->cfg = cfg; - h->max_queue_size = queue_size; h->new_tunnel = new_tunnel; h->cleaner = cleaner; h->client = GNUNET_CLIENT_connect ("mesh", cfg); @@ -1295,8 +1719,12 @@ GNUNET_MESH_connect (const struct GNUNET_CONFIGURATION_Handle *cfg, h->reconnect_task = GNUNET_SCHEDULER_NO_TASK; /* count handlers and apps, calculate size */ - for (h->n_applications = 0; stypes[h->n_applications]; h->n_applications++) ; - for (h->n_handlers = 0; handlers[h->n_handlers].type; h->n_handlers++) ; + for (h->n_applications = 0; + stypes && stypes[h->n_applications]; + h->n_applications++) ; + for (h->n_handlers = 0; + handlers && handlers[h->n_handlers].type; + h->n_handlers++) ; send_connect (h); LOG (GNUNET_ERROR_TYPE_DEBUG, "GNUNET_MESH_connect() END\n"); return h; @@ -1318,6 +1746,13 @@ GNUNET_MESH_disconnect (struct GNUNET_MESH_Handle *handle) struct GNUNET_MESH_Tunnel *aux; struct GNUNET_MESH_TransmitHandle *th; + LOG (GNUNET_ERROR_TYPE_DEBUG, "MESH DISCONNECT\n"); + +#if DEBUG_ACK + LOG (GNUNET_ERROR_TYPE_INFO, "Sent %d ACKs\n", handle->acks_sent); + LOG (GNUNET_ERROR_TYPE_INFO, "Recv %d ACKs\n\n", handle->acks_recv); +#endif + t = handle->tunnels_head; while (NULL != t) { @@ -1337,17 +1772,18 @@ GNUNET_MESH_disconnect (struct GNUNET_MESH_Handle *handle) /* Make sure it is an allowed packet (everything else should have been * already canceled). */ - GNUNET_break (UINT32_MAX == th->priority); - GNUNET_break (NULL == th->notify); + GNUNET_break (GNUNET_NO == th_is_payload (th)); msg = (struct GNUNET_MessageHeader *) &th[1]; switch (ntohs(msg->type)) { case GNUNET_MESSAGE_TYPE_MESH_LOCAL_CONNECT: case GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_DESTROY: + case GNUNET_MESSAGE_TYPE_MESH_LOCAL_INFO_TUNNELS: + case GNUNET_MESSAGE_TYPE_MESH_LOCAL_INFO_TUNNEL: break; default: GNUNET_break (0); - LOG (GNUNET_ERROR_TYPE_DEBUG, "unexpected msg %u\n", + LOG (GNUNET_ERROR_TYPE_ERROR, "unexpected msg %u\n", ntohs(msg->type)); } @@ -1374,6 +1810,55 @@ GNUNET_MESH_disconnect (struct GNUNET_MESH_Handle *handle) } +/** + * Announce to ther peer the availability of services described by the regex, + * in order to be reachable to other peers via connect_by_string. + * + * Note that the first 8 characters are considered to be part of a prefix, + * (for instance 'gnunet://'). If you put a variable part in there (*, +. ()), + * all matching strings will be stored in the DHT. + * + * @param h Handle to mesh. + * @param regex String with the regular expression describing local services. + * @param compression_characters How many characters can be assigned to one + * edge of the graph. The bigger the variability + * of the data, the smaller this parameter should + * be (down to 1). + * For maximum compression, use strlen (regex) + * or 0 (special value). Use with care! + */ +void +GNUNET_MESH_announce_regex (struct GNUNET_MESH_Handle *h, + const char *regex, + unsigned int compression_characters) +{ + struct GNUNET_MESH_RegexAnnounce *msg; + size_t payload; + size_t len; + size_t msgsize; + size_t offset; + char buffer[UINT16_MAX]; + + len = strlen (regex); + payload = UINT16_MAX - sizeof(struct GNUNET_MESH_RegexAnnounce); + msg = (struct GNUNET_MESH_RegexAnnounce *) buffer; + msg->header.type = htons (GNUNET_MESSAGE_TYPE_MESH_LOCAL_ANNOUNCE_REGEX); + msg->compression_characters = htons (compression_characters); + offset = 0; + do + { + msgsize = (len - offset > payload) ? payload : len - offset; + memcpy (&msg[1], ®ex[offset], msgsize); + offset += msgsize; + msgsize += sizeof(struct GNUNET_MESH_RegexAnnounce); + + msg->header.size = htons (msgsize); + msg->last = htons (offset >= len); + + send_packet (h, &msg->header, NULL); + } while (len > offset); +} + /** * Create a new tunnel (we're initiator and will be allowed to add/remove peers * and to broadcast). @@ -1395,6 +1880,8 @@ GNUNET_MESH_tunnel_create (struct GNUNET_MESH_Handle *h, void *tunnel_ctx, LOG (GNUNET_ERROR_TYPE_DEBUG, "Creating new tunnel\n"); t = create_tunnel (h, 0); + LOG (GNUNET_ERROR_TYPE_DEBUG, " at %p\n", t); + LOG (GNUNET_ERROR_TYPE_DEBUG, " number %X\n", t->tid); t->connect_handler = connect_handler; t->disconnect_handler = disconnect_handler; t->cls = handler_cls; @@ -1434,7 +1921,7 @@ GNUNET_MESH_tunnel_destroy (struct GNUNET_MESH_Tunnel *tunnel) { aux = th->next; /* FIXME call the handler? */ - if (NULL != th->notify) + if (GNUNET_YES == th_is_payload (th)) th->notify (th->notify_cls, 0, NULL); GNUNET_CONTAINER_DLL_remove (h->th_head, h->th_tail, th); GNUNET_free (th); @@ -1448,12 +1935,90 @@ GNUNET_MESH_tunnel_destroy (struct GNUNET_MESH_Tunnel *tunnel) send_packet (h, &msg.header, NULL); } +/** + * Request that the tunnel data rate is limited to the speed of the slowest + * receiver. + * + * @param tunnel Tunnel affected. + */ +void +GNUNET_MESH_tunnel_speed_min (struct GNUNET_MESH_Tunnel *tunnel) +{ + struct GNUNET_MESH_TunnelMessage msg; + struct GNUNET_MESH_Handle *h; + + h = tunnel->mesh; + tunnel->speed_min = GNUNET_YES; + + msg.header.type = htons (GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_MIN); + msg.header.size = htons (sizeof (struct GNUNET_MESH_TunnelMessage)); + msg.tunnel_id = htonl (tunnel->tid); + + send_packet (h, &msg.header, NULL); +} + + +/** + * Request that the tunnel data rate is limited to the speed of the fastest + * receiver. This is the default behavior. + * + * @param tunnel Tunnel affected. + */ +void +GNUNET_MESH_tunnel_speed_max (struct GNUNET_MESH_Tunnel *tunnel) +{ + struct GNUNET_MESH_TunnelMessage msg; + struct GNUNET_MESH_Handle *h; + + h = tunnel->mesh; + tunnel->speed_min = GNUNET_NO; + + msg.header.type = htons (GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_MAX); + msg.header.size = htons (sizeof (struct GNUNET_MESH_TunnelMessage)); + msg.tunnel_id = htonl (tunnel->tid); + + send_packet (h, &msg.header, NULL); +} + +/** + * Turn on/off the buffering status of the tunnel. + * + * @param tunnel Tunnel affected. + * @param buffer GNUNET_YES to turn buffering on (default), + * GNUNET_NO otherwise. + */ +void +GNUNET_MESH_tunnel_buffer (struct GNUNET_MESH_Tunnel *tunnel, int buffer) +{ + struct GNUNET_MESH_TunnelMessage msg; + struct GNUNET_MESH_Handle *h; + + h = tunnel->mesh; + tunnel->buffering = buffer; + tunnel->max_send_pid = tunnel->next_send_pid; + + if (GNUNET_YES == buffer) + msg.header.type = htons (GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_BUFFER); + else + msg.header.type = htons (GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_NOBUFFER); + msg.header.size = htons (sizeof (struct GNUNET_MESH_TunnelMessage)); + msg.tunnel_id = htonl (tunnel->tid); + + send_packet (h, &msg.header, NULL); +} + /** * Request that a peer should be added to the tunnel. The existing * connect handler will be called ONCE with either success or failure. * This function should NOT be called again with the same peer before the * connect handler is called. + * FIXME: I think the above documentation is false. I think it should + * read: "The connect handler will be called once the peer was actually + * successfully added to the multicast group. This function should + * not be called twice for the same peer (unless, of course, + * the peer was removed using GNUNET_MESH_peer_Request_connect_del in + * the meantime). * * @param tunnel handle to existing tunnel * @param peer peer to add @@ -1485,8 +2050,6 @@ GNUNET_MESH_peer_request_connect_add (struct GNUNET_MESH_Tunnel *tunnel, msg.tunnel_id = htonl (tunnel->tid); msg.peer = *peer; send_packet (tunnel->mesh, &msg.header, tunnel); - - return; } @@ -1559,17 +2122,99 @@ GNUNET_MESH_peer_request_connect_by_type (struct GNUNET_MESH_Tunnel *tunnel, } +/** + * Request that the mesh should try to connect to a peer matching the + * description given in the service string. + * + * FIXME: allow multiple? how to deal with reconnect? + * + * @param tunnel handle to existing tunnel + * @param description string describing the destination node requirements + */ +void +GNUNET_MESH_peer_request_connect_by_string (struct GNUNET_MESH_Tunnel *tunnel, + const char *description) +{ + struct GNUNET_MESH_ConnectPeerByString *m; + size_t len; + size_t msgsize; + + len = strlen (description); + msgsize = sizeof(struct GNUNET_MESH_ConnectPeerByString) + len; + GNUNET_assert (UINT16_MAX > msgsize); + { + char buffer[msgsize]; + + m = (struct GNUNET_MESH_ConnectPeerByString *) buffer; + m->header.size = htons (msgsize); + m->header.type = htons (GNUNET_MESSAGE_TYPE_MESH_LOCAL_PEER_ADD_BY_STRING); + m->tunnel_id = htonl (tunnel->tid); + memcpy(&m[1], description, len); + + send_packet (tunnel->mesh, &m->header, tunnel); + } +} + + +/** + * Request that the given peer isn't added to this tunnel in calls to + * connect_by_* calls, (due to misbehaviour, bad performance, ...). + * + * @param tunnel handle to existing tunnel. + * @param peer peer identity of the peer which should be blacklisted + * for the tunnel. + */ +void +GNUNET_MESH_peer_blacklist (struct GNUNET_MESH_Tunnel *tunnel, + const struct GNUNET_PeerIdentity *peer) +{ + struct GNUNET_MESH_PeerControl msg; + + msg.header.size = htons (sizeof (struct GNUNET_MESH_PeerControl)); + msg.header.type = htons (GNUNET_MESSAGE_TYPE_MESH_LOCAL_PEER_BLACKLIST); + msg.tunnel_id = htonl (tunnel->tid); + msg.peer = *peer; + send_packet (tunnel->mesh, &msg.header, tunnel); + + return; +} + + +/** + * Request that the given peer isn't blacklisted anymore from this tunnel, + * and therefore can be added in future calls to connect_by_*. + * The peer must have been previously blacklisted for this tunnel. + * + * @param tunnel handle to existing tunnel. + * @param peer peer identity of the peer which shouldn't be blacklisted + * for the tunnel anymore. + */ +void +GNUNET_MESH_peer_unblacklist (struct GNUNET_MESH_Tunnel *tunnel, + const struct GNUNET_PeerIdentity *peer) +{ + struct GNUNET_MESH_PeerControl msg; + + msg.header.size = htons (sizeof (struct GNUNET_MESH_PeerControl)); + msg.header.type = htons (GNUNET_MESSAGE_TYPE_MESH_LOCAL_PEER_UNBLACKLIST); + msg.tunnel_id = htonl (tunnel->tid); + msg.peer = *peer; + send_packet (tunnel->mesh, &msg.header, tunnel); + + return; +} + + /** * Ask the mesh to call "notify" once it is ready to transmit the - * given number of bytes to the specified "target". If we are not yet - * connected to the specified peer, a call to this function will cause - * us to try to establish a connection. + * given number of bytes to the specified tunnel or target. + * Only one call can be active at any time, to issue another request, + * wait for the callback or cancel the current request. * * @param tunnel tunnel to use for transmission * @param cork is corking allowed for this transmission? - * @param priority how important is the message? * @param maxdelay how long can the message wait? - * @param target destination for the message, + * @param target destination for the message * NULL for multicast to all tunnel targets * @param notify_size how many bytes of buffer space does notify want? * @param notify function to call when buffer space is available; @@ -1583,7 +2228,6 @@ GNUNET_MESH_peer_request_connect_by_type (struct GNUNET_MESH_Tunnel *tunnel, */ struct GNUNET_MESH_TransmitHandle * GNUNET_MESH_notify_transmit_ready (struct GNUNET_MESH_Tunnel *tunnel, int cork, - uint32_t priority, struct GNUNET_TIME_Relative maxdelay, const struct GNUNET_PeerIdentity *target, size_t notify_size, @@ -1591,53 +2235,22 @@ GNUNET_MESH_notify_transmit_ready (struct GNUNET_MESH_Tunnel *tunnel, int cork, void *notify_cls) { struct GNUNET_MESH_TransmitHandle *th; - struct GNUNET_MESH_TransmitHandle *least_priority_th; - uint32_t least_priority; size_t overhead; GNUNET_assert (NULL != tunnel); - LOG (GNUNET_ERROR_TYPE_DEBUG, "mesh notify transmit ready called\n"); - if (NULL != target) + LOG (GNUNET_ERROR_TYPE_DEBUG, "MESH NOTIFY TRANSMIT READY\n"); + LOG (GNUNET_ERROR_TYPE_DEBUG, " on tunnel %X\n", tunnel->tid); + if (tunnel->tid >= GNUNET_MESH_LOCAL_TUNNEL_ID_SERV) + LOG (GNUNET_ERROR_TYPE_DEBUG, " to origin\n"); + else if (NULL != target) LOG (GNUNET_ERROR_TYPE_DEBUG, " target %s\n", GNUNET_i2s (target)); else LOG (GNUNET_ERROR_TYPE_DEBUG, " target multicast\n"); + LOG (GNUNET_ERROR_TYPE_DEBUG, " payload size %u\n", notify_size); GNUNET_assert (NULL != notify); - if (tunnel->mesh->npackets >= tunnel->mesh->max_queue_size && - tunnel->npackets > 0) - { - /* queue full */ - if (0 == priority) - return NULL; - th = tunnel->mesh->th_tail; - least_priority = priority; - least_priority_th = NULL; - while (NULL != th) - { - if (th->priority < least_priority && th->tunnel->npackets > 1) - { - least_priority_th = th; - least_priority = th->priority; - } - th = th->prev; - } - if (NULL == least_priority_th) - return NULL; - /* Can't be a control message */ - GNUNET_assert (NULL != least_priority_th->notify); - least_priority_th->notify (notify_cls, 0, NULL); - least_priority_th->tunnel->npackets--; - tunnel->mesh->npackets--; - GNUNET_CONTAINER_DLL_remove (tunnel->mesh->th_head, tunnel->mesh->th_tail, - least_priority_th); - if (GNUNET_SCHEDULER_NO_TASK != least_priority_th->timeout_task) - GNUNET_SCHEDULER_cancel (least_priority_th->timeout_task); - GNUNET_free (least_priority_th); - } - tunnel->npackets++; - tunnel->mesh->npackets++; + GNUNET_assert (0 == tunnel->packet_size); // Only one data packet allowed th = GNUNET_malloc (sizeof (struct GNUNET_MESH_TransmitHandle)); th->tunnel = tunnel; - th->priority = priority; th->timeout = GNUNET_TIME_relative_to_absolute (maxdelay); th->target = GNUNET_PEER_intern (target); if (tunnel->tid >= GNUNET_MESH_LOCAL_TUNNEL_ID_SERV) @@ -1646,17 +2259,22 @@ GNUNET_MESH_notify_transmit_ready (struct GNUNET_MESH_Tunnel *tunnel, int cork, overhead = sizeof (struct GNUNET_MESH_Multicast); else overhead = sizeof (struct GNUNET_MESH_Unicast); - th->size = notify_size + overhead; + tunnel->packet_size = th->size = notify_size + overhead; + LOG (GNUNET_ERROR_TYPE_DEBUG, " total size %u\n", th->size); th->notify = notify; th->notify_cls = notify_cls; add_to_queue (tunnel->mesh, th); if (NULL != tunnel->mesh->th) return th; + if (GMC_is_pid_bigger(tunnel->next_send_pid, tunnel->max_send_pid)) + return th; + LOG (GNUNET_ERROR_TYPE_DEBUG, " call notify tmt rdy\n"); tunnel->mesh->th = GNUNET_CLIENT_notify_transmit_ready (tunnel->mesh->client, th->size, GNUNET_TIME_UNIT_FOREVER_REL, GNUNET_YES, &send_callback, tunnel->mesh); + LOG (GNUNET_ERROR_TYPE_DEBUG, "MESH NOTIFY TRANSMIT READY END\n"); return th; } @@ -1671,12 +2289,13 @@ GNUNET_MESH_notify_transmit_ready_cancel (struct GNUNET_MESH_TransmitHandle *th) { struct GNUNET_MESH_Handle *mesh; + th->tunnel->packet_size = 0; mesh = th->tunnel->mesh; if (th->timeout_task != GNUNET_SCHEDULER_NO_TASK) GNUNET_SCHEDULER_cancel (th->timeout_task); GNUNET_CONTAINER_DLL_remove (mesh->th_head, mesh->th_tail, th); GNUNET_free (th); - if ((NULL == mesh->th_head) && (NULL != mesh->th)) + if ((0 == message_ready_size (mesh)) && (NULL != mesh->th)) { /* queue empty, no point in asking for transmission */ GNUNET_CLIENT_notify_transmit_ready_cancel (mesh->th); @@ -1685,6 +2304,91 @@ GNUNET_MESH_notify_transmit_ready_cancel (struct GNUNET_MESH_TransmitHandle *th) } +/** + * Request information about the running mesh peer. + * The callback will be called for every tunnel known to the service, + * listing all active peers that blong to the tunnel. + * + * If called again on the same handle, it will overwrite the previous + * callback and cls. To retrieve the cls, monitor_cancel must be + * called first. + * + * WARNING: unstable API, likely to change in the future! + * + * @param h Handle to the mesh peer. + * @param callback Function to call with the requested data. + * @param callback_cls Closure for @c callback. + */ +void +GNUNET_MESH_get_tunnels (struct GNUNET_MESH_Handle *h, + GNUNET_MESH_TunnelsCB callback, + void *callback_cls) +{ + struct GNUNET_MessageHeader msg; + + msg.size = htons (sizeof (msg)); + msg.type = htons (GNUNET_MESSAGE_TYPE_MESH_LOCAL_INFO_TUNNELS); + send_packet (h, &msg, NULL); + h->tunnels_cb = callback; + h->tunnels_cls = callback_cls; + + return; +} + + +/** + * Cancel a monitor request. The monitor callback will not be called. + * + * @param h Mesh handle. + * + * @return Closure given to GNUNET_MESH_monitor, if any. + */ +void * +GNUNET_MESH_get_tunnels_cancel (struct GNUNET_MESH_Handle *h) +{ + void *cls; + + cls = h->tunnels_cls; + h->tunnels_cb = NULL; + h->tunnels_cls = NULL; + return cls; +} + + +/** + * Request information about a specific tunnel of the running mesh peer. + * + * WARNING: unstable API, likely to change in the future! + * + * @param h Handle to the mesh peer. + * @param initiator ID of the owner of the tunnel. + * @param tunnel_number Tunnel number. + * @param callback Function to call with the requested data. + * @param callback_cls Closure for @c callback. + */ +void +GNUNET_MESH_show_tunnel (struct GNUNET_MESH_Handle *h, + struct GNUNET_PeerIdentity *initiator, + unsigned int tunnel_number, + GNUNET_MESH_TunnelCB callback, + void *callback_cls) +{ + struct GNUNET_MESH_LocalMonitor msg; + + msg.header.size = htons (sizeof (msg)); + msg.header.type = htons (GNUNET_MESSAGE_TYPE_MESH_LOCAL_INFO_TUNNEL); + msg.npeers = htonl (0); + msg.owner = *initiator; + msg.tunnel_id = htonl (tunnel_number); + msg.reserved = 0; + send_packet (h, &msg.header, NULL); + h->tunnel_cb = callback; + h->tunnel_cls = callback_cls; + + return; +} + + /** * Transition API for tunnel ctx management */ diff --git a/src/mesh/mesh_common.c b/src/mesh/mesh_common.c new file mode 100644 index 0000000..c9af35c --- /dev/null +++ b/src/mesh/mesh_common.c @@ -0,0 +1,250 @@ +/* + This file is part of GNUnet. + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @file mesh/mesh_common.c + * @brief MESH helper functions + * @author Bartlomiej Polot + */ + +#include "mesh.h" + + +/** + * Check if one pid is bigger than other, accounting for overflow. + * + * @param bigger Argument that should be bigger. + * @param smaller Argument that should be smaller. + * + * @return True if bigger (arg1) has a higher value than smaller (arg 2). + */ +int +GMC_is_pid_bigger (uint32_t bigger, uint32_t smaller) +{ + return (GNUNET_YES == PID_OVERFLOW(smaller, bigger) || + (bigger > smaller && GNUNET_NO == PID_OVERFLOW(bigger, smaller))); +} + +/** + * Get the higher ACK value out of two values, taking in account overflow. + * + * @param a First ACK value. + * @param b Second ACK value. + * + * @return Highest ACK value from the two. + */ +uint32_t +GMC_max_pid (uint32_t a, uint32_t b) +{ + if (GMC_is_pid_bigger(a, b)) + return a; + return b; +} + + +/** + * Get the lower ACK value out of two values, taking in account overflow. + * + * @param a First ACK value. + * @param b Second ACK value. + * + * @return Lowest ACK value from the two. + */ +uint32_t +GMC_min_pid (uint32_t a, uint32_t b) +{ + if (GMC_is_pid_bigger(a, b)) + return b; + return a; +} + + +#if !defined(GNUNET_CULL_LOGGING) +const char * +GNUNET_MESH_DEBUG_M2S (uint16_t m) +{ + static char buf[32]; + switch (m) + { + /** + * Request the creation of a path + */ + case 256: return "GNUNET_MESSAGE_TYPE_MESH_PATH_CREATE"; + + /** + * Request the modification of an existing path + */ + case 257: return "GNUNET_MESSAGE_TYPE_MESH_PATH_CHANGE"; + + /** + * Notify that a connection of a path is no longer valid + */ + case 258: return "GNUNET_MESSAGE_TYPE_MESH_PATH_BROKEN"; + + /** + * At some point, the route will spontaneously change + */ + case 259: return "GNUNET_MESSAGE_TYPE_MESH_PATH_CHANGED"; + + /** + * Transport data in the mesh (origin->end) unicast + */ + case 260: return "GNUNET_MESSAGE_TYPE_MESH_UNICAST"; + + /** + * Transport data to all peers in a tunnel + */ + case 261: return "GNUNET_MESSAGE_TYPE_MESH_MULTICAST"; + + /** + * Transport data back in the mesh (end->origin) + */ + case 262: return "GNUNET_MESSAGE_TYPE_MESH_TO_ORIGIN"; + + /** + * Send origin an ACK that the path is complete + */ + case 263: return "GNUNET_MESSAGE_TYPE_MESH_PATH_ACK"; + + /** + * Avoid path timeouts + */ + case 264: return "GNUNET_MESSAGE_TYPE_MESH_PATH_KEEPALIVE"; + + /** + * Request the destuction of a path + */ + case 265: return "GNUNET_MESSAGE_TYPE_MESH_PATH_DESTROY"; + + /** + * Request the destruction of a whole tunnel + */ + case 266: return "GNUNET_MESSAGE_TYPE_MESH_TUNNEL_DESTROY"; + + /** + * ACK for a data packet. + */ + case 267: return "GNUNET_MESSAGE_TYPE_MESH_ACK"; + + /** + * POLL for ACK. + */ + case 268: return "GNUNET_MESSAGE_TYPE_MESH_POLL"; + + /** + * Connect to the mesh service, specifying subscriptions + */ + case 272: return "GNUNET_MESSAGE_TYPE_MESH_LOCAL_CONNECT"; + + /** + * Ask the mesh service to create a new tunnel + */ + case 273: return "GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_CREATE"; + + /** + * Ask the mesh service to destroy a tunnel + */ + case 274: return "GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_DESTROY"; + + /** + * Ask the mesh service to add a peer to an existing tunnel + */ + case 275: return "GNUNET_MESSAGE_TYPE_MESH_LOCAL_PEER_ADD"; + + /** + * Ask the mesh service to remove a peer from a tunnel + */ + case 276: return "GNUNET_MESSAGE_TYPE_MESH_LOCAL_PEER_DEL"; + + /** + * Ask the mesh service to add a peer offering a service to an existing tunnel + */ + case 277: return "GNUNET_MESSAGE_TYPE_MESH_LOCAL_PEER_ADD_BY_TYPE"; + + /** + * Ask the mesh service to add a peer described by a service string + */ + case 278: return "GNUNET_MESSAGE_TYPE_MESH_LOCAL_ANNOUNCE_REGEX"; + + /** + * Ask the mesh service to add a peer described by a service string + */ + case 279: return "GNUNET_MESSAGE_TYPE_MESH_LOCAL_PEER_ADD_BY_STRING"; + + /** + * Ask the mesh service to add a peer to the blacklist of an existing tunnel + */ + case 280: return "GNUNET_MESSAGE_TYPE_MESH_LOCAL_PEER_BLACKLIST"; + + /** + * Ask the mesh service to remove a peer from the blacklist of a tunnel + */ + case 281: return "GNUNET_MESSAGE_TYPE_MESH_LOCAL_PEER_UNBLACKLIST"; + + /** + * Set tunnel speed to slowest peer + */ + case 282: return "GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_MIN"; + + /** + * Set tunnel speed to fastest peer + */ + case 283: return "GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_MAX"; + + /** + * Set tunnel buffering on. + */ + case 284: return "GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_BUFFER"; + + /** + * Set tunnel buffering off. + */ + case 285: return "GNUNET_MESSAGE_TYPE_MESH_LOCAL_TUNNEL_NOBUFFER"; + + /** + * Local ACK for data. + */ + case 286: return "GNUNET_MESSAGE_TYPE_MESH_LOCAL_ACK"; + + /** + * Local monitoring of service. + */ + case 287: return "GNUNET_MESSAGE_TYPE_MESH_LOCAL_MONITOR"; + + /** + * Local monitoring of service of a specific tunnel. + */ + case 288: return "GNUNET_MESSAGE_TYPE_MESH_LOCAL_MONITOR_TUNNEL"; + + /** + * 640kb should be enough for everybody + */ + case 299: return "GNUNET_MESSAGE_TYPE_MESH_RESERVE_END"; + } + sprintf(buf, "%u (UNKNOWN TYPE)", m); + return buf; +} +#else +const char * +GNUNET_MESH_DEBUG_M2S (uint16_t m) +{ + return ""; +} +#endif diff --git a/src/mesh/mesh_protocol.h b/src/mesh/mesh_protocol.h index 885f1f3..01f7f34 100644 --- a/src/mesh/mesh_protocol.h +++ b/src/mesh/mesh_protocol.h @@ -35,6 +35,10 @@ extern "C" #endif #endif +#define MESH_TUNNEL_OPT_SPEED_MIN 0x1 +#define MESH_TUNNEL_OPT_NOBUFFER 0x2 + + /******************************************************************************/ /******************** MESH NETWORK MESSAGES **************************/ /******************************************************************************/ @@ -47,7 +51,7 @@ GNUNET_NETWORK_STRUCT_BEGIN struct GNUNET_MESH_ManipulatePath { /** - * Type: GNUNET_MESSAGE_TYPE_MESH_PATH_[CREATE|CHANGE|ADD|DEL] + * Type: GNUNET_MESSAGE_TYPE_MESH_PATH_[CREATE|CHANGE|ADD|DESTROY] * * Size: sizeof(struct GNUNET_MESH_ManipulatePath) + * path_length * sizeof (struct GNUNET_PeerIdentity) @@ -60,6 +64,16 @@ struct GNUNET_MESH_ManipulatePath */ uint32_t tid GNUNET_PACKED; + /** + * Tunnel options (MESH_TUNNEL_OPT_*). + */ + uint32_t opt GNUNET_PACKED; + + /** + * 64 bit alignment padding. + */ + uint32_t reserved GNUNET_PACKED; + /** * path_length structs defining the *whole* path from the origin [0] to the * final destination [path_length-1]. @@ -90,7 +104,7 @@ struct GNUNET_MESH_Multicast /** * Unique ID of the packet */ - uint32_t mid GNUNET_PACKED; + uint32_t pid GNUNET_PACKED; /** * OID of the tunnel @@ -118,6 +132,16 @@ struct GNUNET_MESH_Unicast */ uint32_t tid GNUNET_PACKED; + /** + * Number of hops to live + */ + uint32_t ttl GNUNET_PACKED; + + /** + * Unique ID of the packet + */ + uint32_t pid GNUNET_PACKED; + /** * OID of the tunnel */ @@ -149,6 +173,16 @@ struct GNUNET_MESH_ToOrigin */ uint32_t tid GNUNET_PACKED; + /** + * Number of hops to live + */ + uint32_t ttl GNUNET_PACKED; + + /** + * Unique ID of the packet + */ + uint32_t pid GNUNET_PACKED; + /** * OID of the tunnel */ @@ -165,6 +199,59 @@ struct GNUNET_MESH_ToOrigin }; +/** + * Message to acknowledge mesh data traffic. + */ +struct GNUNET_MESH_ACK +{ + /** + * Type: GNUNET_MESSAGE_TYPE_MESH_ACK + */ + struct GNUNET_MessageHeader header; + + /** + * TID of the tunnel + */ + uint32_t tid GNUNET_PACKED; + + /** + * OID of the tunnel + */ + struct GNUNET_PeerIdentity oid; + + /** + * Maximum packet ID authorized. + */ + uint32_t pid; + +}; + +/** + * Message to query a peer about its Flow Control status regarding a tunnel. + */ +struct GNUNET_MESH_Poll +{ + /** + * Type: GNUNET_MESSAGE_TYPE_MESH_POLL + */ + struct GNUNET_MessageHeader header; + + /** + * TID of the tunnel + */ + uint32_t tid GNUNET_PACKED; + + /** + * OID of the tunnel + */ + struct GNUNET_PeerIdentity oid; + + /** + * Last ACK received. + */ + uint32_t last_ack; +}; + /** * Message for ack'ing a path */ @@ -253,31 +340,28 @@ struct GNUNET_MESH_TunnelDestroy /** - * Message for mesh flow control + * Message to destroy a tunnel */ -struct GNUNET_MESH_SpeedNotify +struct GNUNET_MESH_TunnelKeepAlive { - /** - * Type: GNUNET_MESSAGE_TYPE_DATA_SPEED_NOTIFY - */ + /** + * Type: GNUNET_MESSAGE_TYPE_MESH_PATH_KEEPALIVE + */ struct GNUNET_MessageHeader header; - - /** - * TID of the tunnel - */ + + /** + * TID of the tunnel + */ uint32_t tid GNUNET_PACKED; - - /** - * OID of the tunnel - */ + + /** + * OID of the tunnel + */ struct GNUNET_PeerIdentity oid; +}; + - /** - * Slowest link down the path (above minimum speed requirement). - */ - uint32_t speed_min; -}; GNUNET_NETWORK_STRUCT_END #if 0 /* keep Emacsens' auto-indent happy */ @@ -287,6 +371,6 @@ GNUNET_NETWORK_STRUCT_END } #endif -/* ifndef MES_PROTOCOL_H */ +/* ifndef MESH_PROTOCOL_H */ #endif /* end of mesh_protocol.h */ diff --git a/src/mesh/mesh_test_lib.c b/src/mesh/mesh_test_lib.c new file mode 100644 index 0000000..cec74f2 --- /dev/null +++ b/src/mesh/mesh_test_lib.c @@ -0,0 +1,297 @@ +/* + This file is part of GNUnet. + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ +/** + * @file mesh/mesh_test_lib.c + * @author Bartlomiej Polot + * @brief library for writing MESH tests + */ +#include "platform.h" +#include "gnunet_util_lib.h" +#include "mesh_test_lib.h" +#include "gnunet_mesh_service.h" + +/** + * Test context for a MESH Test. + */ +struct GNUNET_MESH_TEST_Context +{ + /** + * Array of running peers. + */ + struct GNUNET_TESTBED_Peer **peers; + + /** + * Array of handles to the MESH for each peer. + */ + struct GNUNET_MESH_Handle **meshes; + + /** + * Operation associated with the connection to the MESH. + */ + struct GNUNET_TESTBED_Operation **ops; + + /** + * Main function of the test to run once all MESHs are available. + */ + GNUNET_MESH_TEST_AppMain app_main; + + /** + * Closure for 'app_main'. + */ + void *app_main_cls; + + /** + * Number of peers running, size of the arrays above. + */ + unsigned int num_peers; + + /** + * Handler for incoming tunnels. + */ + GNUNET_MESH_InboundTunnelNotificationHandler *new_tunnel; + + /** + * Cleaner for destroyed incoming tunnels. + */ + GNUNET_MESH_TunnelEndHandler *cleaner; + + /** + * Message handlers. + */ + struct GNUNET_MESH_MessageHandler* handlers; + + /** + * Application types. + */ + const GNUNET_MESH_ApplicationType* stypes; + +}; + + +/** + * Context for a mesh adapter callback. + */ +struct GNUNET_MESH_TEST_AdapterContext +{ + /** + * Peer number for the particular peer. + */ + unsigned int peer; + + /** + * General context. + */ + struct GNUNET_MESH_TEST_Context *ctx; +}; + + +/** + * Adapter function called to establish a connection to + * the MESH service. + * + * @param cls closure + * @param cfg configuration of the peer to connect to; will be available until + * GNUNET_TESTBED_operation_done() is called on the operation returned + * from GNUNET_TESTBED_service_connect() + * @return service handle to return in 'op_result', NULL on error + */ +static void * +mesh_connect_adapter (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg) +{ + struct GNUNET_MESH_TEST_AdapterContext *actx = cls; + struct GNUNET_MESH_TEST_Context *ctx = actx->ctx; + struct GNUNET_MESH_Handle *h; + + h = GNUNET_MESH_connect (cfg, + (void *) (long) actx->peer, + ctx->new_tunnel, + ctx->cleaner, + ctx->handlers, + ctx->stypes); + return h; +} + + +/** + * Adapter function called to destroy a connection to + * the MESH service. + * + * @param cls closure + * @param op_result service handle returned from the connect adapter + */ +static void +mesh_disconnect_adapter (void *cls, + void *op_result) +{ + struct GNUNET_MESH_Handle *mesh = op_result; + struct GNUNET_MESH_TEST_AdapterContext *actx = cls; + + GNUNET_free (actx); + GNUNET_MESH_disconnect (mesh); +} + + +/** + * Callback to be called when a service connect operation is completed. + * + * @param cls The callback closure from functions generating an operation. + * @param op The operation that has been finished. + * @param ca_result The service handle returned from + * GNUNET_TESTBED_ConnectAdapter() (mesh handle). + * @param emsg Error message in case the operation has failed. + * NULL if operation has executed successfully. + */ +static void +mesh_connect_cb (void *cls, + struct GNUNET_TESTBED_Operation *op, + void *ca_result, + const char *emsg) +{ + struct GNUNET_MESH_TEST_Context *ctx = cls; + unsigned int i; + + if (NULL != emsg) + { + fprintf (stderr, "Failed to connect to MESH service: %s\n", + emsg); + GNUNET_SCHEDULER_shutdown (); + return; + } + for (i = 0; i < ctx->num_peers; i++) + if (op == ctx->ops[i]) + ctx->meshes[i] = ca_result; + for (i = 0; i < ctx->num_peers; i++) + if (NULL == ctx->meshes[i]) + return; /* still some MESH connections missing */ + /* all MESH connections ready! */ + ctx->app_main (ctx->app_main_cls, + ctx, + ctx->num_peers, + ctx->peers, + ctx->meshes); +} + + +/** + * Clean up the testbed. + * + * @param ctx handle for the testbed + */ +void +GNUNET_MESH_TEST_cleanup (struct GNUNET_MESH_TEST_Context *ctx) +{ + unsigned int i; + + for (i = 0; i < ctx->num_peers; i++) + { + GNUNET_assert (NULL != ctx->ops[i]); + GNUNET_TESTBED_operation_done (ctx->ops[i]); + ctx->ops[i] = NULL; + } + GNUNET_free (ctx->ops); + GNUNET_free (ctx->meshes); + GNUNET_free (ctx); + GNUNET_SCHEDULER_shutdown (); +} + + +/** + * Callback run when the testbed is ready (peers running and connected to + * each other) + * + * @param cls Closure (context). + * @param num_peers Number of peers that are running. + * @param peers Handles to each one of the @c num_peers peers. + */ +static void +mesh_test_run (void *cls, + unsigned int num_peers, + struct GNUNET_TESTBED_Peer **peers) +{ + struct GNUNET_MESH_TEST_Context *ctx = cls; + unsigned int i; + + GNUNET_assert (num_peers == ctx->num_peers); + ctx->peers = peers; + for (i = 0; i < num_peers; i++) + { + struct GNUNET_MESH_TEST_AdapterContext *newctx; + newctx = GNUNET_malloc (sizeof (struct GNUNET_MESH_TEST_AdapterContext)); + newctx->peer = i; + newctx->ctx = ctx; + ctx->ops[i] = GNUNET_TESTBED_service_connect (ctx, + peers[i], + "mesh", + &mesh_connect_cb, + ctx, + &mesh_connect_adapter, + &mesh_disconnect_adapter, + newctx); + } +} + + +/** + * Run a test using the given name, configuration file and number of + * peers. + * All mesh callbacks will receive the peer number as the closure. + * + * @param testname Name of the test (for logging). + * @param cfgname Name of the configuration file. + * @param num_peers Number of peers to start. + * @param tmain Main function to run once the testbed is ready. + * @param tmain_cls Closure for 'tmain'. + * @param new_tunnel Handler for incoming tunnels. + * @param cleaner Cleaner for destroyed incoming tunnels. + * @param handlers Message handlers. + * @param stypes Application types. + */ +void +GNUNET_MESH_TEST_run (const char *testname, + const char *cfgname, + unsigned int num_peers, + GNUNET_MESH_TEST_AppMain tmain, + void *tmain_cls, + GNUNET_MESH_InboundTunnelNotificationHandler new_tunnel, + GNUNET_MESH_TunnelEndHandler cleaner, + struct GNUNET_MESH_MessageHandler* handlers, + const GNUNET_MESH_ApplicationType* stypes) +{ + struct GNUNET_MESH_TEST_Context *ctx; + + ctx = GNUNET_malloc (sizeof (struct GNUNET_MESH_TEST_Context)); + ctx->num_peers = num_peers; + ctx->ops = GNUNET_malloc (num_peers * sizeof (struct GNUNET_TESTBED_Operation *)); + ctx->meshes = GNUNET_malloc (num_peers * sizeof (struct GNUNET_MESH_Handle *)); + ctx->app_main = tmain; + ctx->app_main_cls = tmain_cls; + ctx->new_tunnel = new_tunnel; + ctx->cleaner = cleaner; + ctx->handlers = handlers; + ctx->stypes = stypes; + GNUNET_TESTBED_test_run (testname, + cfgname, + num_peers, + 0LL, NULL, NULL, + &mesh_test_run, ctx); +} + +/* end of mesh_test_lib.c */ diff --git a/src/mesh/mesh_test_lib.h b/src/mesh/mesh_test_lib.h new file mode 100644 index 0000000..554d065 --- /dev/null +++ b/src/mesh/mesh_test_lib.h @@ -0,0 +1,106 @@ +/* + This file is part of GNUnet. + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ +/** + * @file mesh/mesh_test_lib.h + * @author Bartlomiej Polot + * @brief library for writing MESH tests + */ +#ifndef MESH_TEST_LIB_H +#define MESH_TEST_LIB_H + +#ifdef __cplusplus +extern "C" +{ +#if 0 /* keep Emacsens' auto-indent happy */ +} +#endif +#endif + +#include "gnunet_testbed_service.h" +#include "gnunet_mesh_service.h" + +/** + * Test context for a MESH Test. + */ +struct GNUNET_MESH_TEST_Context; + + +/** + * Main function of a MESH test. + * + * @param cls Closure. + * @param ctx Argument to give to GNUNET_MESH_TEST_cleanup on test end. + * @param num_peers Number of peers that are running. + * @param peers Array of peers. + * @param meshes Handle to each of the MESHs of the peers. + */ +typedef void (*GNUNET_MESH_TEST_AppMain) (void *cls, + struct GNUNET_MESH_TEST_Context *ctx, + unsigned int num_peers, + struct GNUNET_TESTBED_Peer **peers, + struct GNUNET_MESH_Handle **meshes); + + +/** + * Run a test using the given name, configuration file and number of + * peers. + * All mesh callbacks will receive the peer number as the closure. + * + * @param testname Name of the test (for logging). + * @param cfgname Name of the configuration file. + * @param num_peers Number of peers to start. + * @param tmain Main function to run once the testbed is ready. + * @param tmain_cls Closure for 'tmain'. + * @param new_tunnel Handler for incoming tunnels. + * @param cleaner Cleaner for destroyed incoming tunnels. + * @param handlers Message handlers. + * @param stypes Application types. + */ +void +GNUNET_MESH_TEST_run (const char *testname, + const char *cfgname, + unsigned int num_peers, + GNUNET_MESH_TEST_AppMain tmain, + void *tmain_cls, + GNUNET_MESH_InboundTunnelNotificationHandler new_tunnel, + GNUNET_MESH_TunnelEndHandler cleaner, + struct GNUNET_MESH_MessageHandler* handlers, + const GNUNET_MESH_ApplicationType* stypes); + + +/** + * Clean up the testbed. + * + * @param ctx handle for the testbed + */ +void +GNUNET_MESH_TEST_cleanup (struct GNUNET_MESH_TEST_Context *ctx); + + +#if 0 /* keep Emacsens' auto-indent happy */ +{ +#endif +#ifdef __cplusplus +} +#endif + + +/* ifndef MESH_TEST_LIB_H */ +#endif diff --git a/src/mesh/mesh_tunnel_tree.c b/src/mesh/mesh_tunnel_tree.c index 287eefc..41b25c3 100644 --- a/src/mesh/mesh_tunnel_tree.c +++ b/src/mesh/mesh_tunnel_tree.c @@ -379,6 +379,8 @@ tree_node_destroy (struct MeshTunnelTreeNode *parent) struct MeshTunnelTreeNode *n; struct MeshTunnelTreeNode *next; + if (NULL == parent) + return; #if MESH_TREE_DEBUG struct GNUNET_PeerIdentity id; @@ -416,7 +418,7 @@ tree_new (GNUNET_PEER_Id peer) struct MeshTunnelTree *tree; tree = GNUNET_malloc (sizeof (struct MeshTunnelTree)); - tree->first_hops = GNUNET_CONTAINER_multihashmap_create (32); + tree->first_hops = GNUNET_CONTAINER_multihashmap_create (32, GNUNET_NO); tree->root = tree_node_new (NULL, peer); tree->root->status = MESH_PEER_ROOT; @@ -494,6 +496,8 @@ tree_get_predecessor (struct MeshTunnelTree *tree) * * @return peerinfo of the peer who is the first hop in the tunnel * NULL on error + * + * FIXME use PEER_Id */ struct GNUNET_PeerIdentity * tree_get_first_hop (struct MeshTunnelTree *t, GNUNET_PEER_Id peer) @@ -583,26 +587,117 @@ tree_mark_peers_disconnected (struct MeshTunnelTree *tree, * * @param tree Tree to use. Must have "me" set. * @param cb Callback to call over each child. - * @param cls Closure. + * @param cb_cls Closure for @c cb. */ void tree_iterate_children (struct MeshTunnelTree *tree, MeshTreeCallback cb, - void *cls) + void *cb_cls) { struct MeshTunnelTreeNode *n; if (NULL == tree->me) - { - GNUNET_break (0); return; - } for (n = tree->me->children_head; NULL != n; n = n->next) { - cb (cls, n->peer); + cb (cb_cls, n->peer); + } +} + + +/** + * Struct to contain a list of pending nodes when iterating a tree. + */ +struct MeshTreePendingNode { + + /** + * DLL next. + */ + struct MeshTreePendingNode *next; + + /** + * DLL prev. + */ + struct MeshTreePendingNode *prev; + + /** + * Pending node. + */ + struct MeshTunnelTreeNode *node; +}; + + +/** + * Iterate over all nodes in the tree. + * + * @param tree Tree to use.. + * @param cb Callback to call over each child. + * @param cb_cls Closure for @c cb. + * + * TODO: recursive implementation? (s/heap/stack/g) + */ +void +tree_iterate_all (struct MeshTunnelTree *tree, + MeshWholeTreeCallback cb, + void *cb_cls) +{ + struct MeshTunnelTreeNode *parent; + struct MeshTunnelTreeNode *n; + struct MeshTreePendingNode *head; + struct MeshTreePendingNode *tail; + struct MeshTreePendingNode *pending; + + cb (cb_cls, tree->root->peer, 0); + pending = GNUNET_malloc (sizeof (struct MeshTreePendingNode)); + pending->node = tree->root; + head = tail = NULL; + GNUNET_CONTAINER_DLL_insert (head, tail, pending); + + while (NULL != head) + { + pending = head; + parent = pending->node; + GNUNET_CONTAINER_DLL_remove (head, tail, pending); + GNUNET_free (pending); + for (n = parent->children_head; NULL != n; n = n->next) + { + cb (cb_cls, n->peer, parent->peer); + pending = GNUNET_malloc (sizeof (struct MeshTreePendingNode)); + pending->node = n; + /* Insert_tail: breadth first, Insert: depth first */ + GNUNET_CONTAINER_DLL_insert (head, tail, pending); + } } } +/** + * Iterator to count the children in a tree. + */ +static void +count_children_cb (void *cls, GNUNET_PEER_Id peer) +{ + unsigned int *i = cls; + + (*i)++; +} + + +/** + * Count how many children does the local node have in the tree. + * + * @param tree Tree to use. Must have "me" set. + */ +unsigned int +tree_count_children (struct MeshTunnelTree *tree) +{ + unsigned int i; + + i = 0; + tree_iterate_children(tree, &count_children_cb, &i); + return i; +} + + /** * Recusively update the info about what is the first hop to reach the node * @@ -647,7 +742,7 @@ tree_del_path (struct MeshTunnelTree *t, GNUNET_PEER_Id peer_id, GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "tree: Deleting path to %s.\n", GNUNET_i2s (&id)); #endif - if (peer_id == t->root->peer) + if (NULL == t->root || peer_id == t->root->peer) return NULL; for (n = t->disconnected_head; NULL != n; n = n->next) @@ -669,7 +764,8 @@ tree_del_path (struct MeshTunnelTree *t, GNUNET_PEER_Id peer_id, GNUNET_CONTAINER_DLL_remove (parent->children_head, parent->children_tail, n); n->parent = NULL; - while (MESH_PEER_RELAY == parent->status && NULL == parent->children_head) + while (MESH_PEER_RELAY == parent->status && + NULL == parent->children_head) { #if MESH_TREE_DEBUG GNUNET_PEER_resolve (parent->peer, &id); @@ -677,6 +773,8 @@ tree_del_path (struct MeshTunnelTree *t, GNUNET_PEER_Id peer_id, GNUNET_i2s (&id)); #endif n = parent->parent; + if (parent == t->me) + t->me = NULL; tree_node_destroy (parent); parent = n; } @@ -970,7 +1068,6 @@ tree_del_peer (struct MeshTunnelTree *t, GNUNET_PEER_Id peer, GNUNET_break (0); return GNUNET_YES; } - GNUNET_break_op (NULL == n->children_head); tree_node_destroy (n); if (NULL == t->root->children_head && t->me != t->root) { @@ -1037,6 +1134,8 @@ void tree_debug (struct MeshTunnelTree *t) { tree_node_debug (t->root, 0); + FPRINTF (stderr, "root: %p\n", t->root); + FPRINTF (stderr, "me: %p\n", t->me); } @@ -1050,7 +1149,7 @@ tree_debug (struct MeshTunnelTree *t) * @return GNUNET_YES if we should continue to iterate, GNUNET_NO if not. */ static int -iterate_free (void *cls, const GNUNET_HashCode * key, void *value) +iterate_free (void *cls, const struct GNUNET_HashCode * key, void *value) { GNUNET_free (value); return GNUNET_YES; diff --git a/src/mesh/mesh_tunnel_tree.h b/src/mesh/mesh_tunnel_tree.h index 84fd0ac..e5d6592 100644 --- a/src/mesh/mesh_tunnel_tree.h +++ b/src/mesh/mesh_tunnel_tree.h @@ -126,14 +126,25 @@ path_destroy (struct MeshPeerPath *p); /******************************************************************************/ /** - * Method called whenever a node has been marked as disconnected. + * Iterator over all children of a node. * * @param cls Closure. - * @param peer_id short ID of peer that is no longer reachable. + * @param peer_id Short ID of the peer. */ typedef void (*MeshTreeCallback) (void *cls, GNUNET_PEER_Id peer_id); +/** + * Iterator over all nodes in a tree. + * + * @param cls Closure. + * @param peer_id Short ID of the peer. + * @param peer_id Short ID of the parent of the peer. + */ +typedef void (*MeshWholeTreeCallback) (void *cls, + GNUNET_PEER_Id peer_id, + GNUNET_PEER_Id parent_id); + /** * Create a new tunnel tree associated to a tunnel * @@ -210,11 +221,35 @@ tree_find_peer (struct MeshTunnelTree *tree, GNUNET_PEER_Id peer_id); * * @param tree Tree to use. Must have "me" set. * @param cb Callback to call over each child. - * @param cls Closure. + * @param cb_cls Closure for @c cb. */ void -tree_iterate_children (struct MeshTunnelTree *tree, MeshTreeCallback cb, - void *cls); +tree_iterate_children (struct MeshTunnelTree *tree, + MeshTreeCallback cb, + void *cb_cls); + + +/** + * Iterate over all nodes in the tree. + * + * @param tree Tree to use.. + * @param cb Callback to call over each child. + * @param cb_cls Closure for @c cb. + * + * TODO: recursive implementation? (s/heap/stack/g) + */ +void +tree_iterate_all (struct MeshTunnelTree *tree, + MeshWholeTreeCallback cb, + void *cb_cls); + +/** + * Count how many children does the local node have in the tree. + * + * @param tree Tree to use. Must have "me" set. + */ +unsigned int +tree_count_children (struct MeshTunnelTree *tree); /** @@ -302,6 +337,8 @@ tree_notify_connection_broken (struct MeshTunnelTree *t, GNUNET_PEER_Id p1, * If the tree is not local and no longer has any paths, the root node will be * destroyed and marked as NULL. * + * FIXME: dont destroy the root + * * @param t Tunnel tree to use. * @param peer Short ID of the peer to remove from the tunnel tree. * @param cb Callback to notify client of disconnected peers. diff --git a/src/mesh/plugin_block_mesh.c b/src/mesh/plugin_block_mesh.c new file mode 100644 index 0000000..f0dae71 --- /dev/null +++ b/src/mesh/plugin_block_mesh.c @@ -0,0 +1,205 @@ +/* + This file is part of GNUnet + (C) 2012,2013 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @file mesh/plugin_block_mesh.c + * @brief blocks used for mesh peer discovery + * @author Bartlomiej Polot + */ + +#include "platform.h" +#include "gnunet_block_plugin.h" +#include "block_mesh.h" + +/** + * Number of bits we set per entry in the bloomfilter. + * Do not change! + */ +#define BLOOMFILTER_K 16 + + +/** + * Function called to validate a reply or a request. For + * request evaluation, simply pass "NULL" for the reply_block. + * Note that it is assumed that the reply has already been + * matched to the key (and signatures checked) as it would + * be done with the "get_key" function. + * + * @param cls closure + * @param type block type + * @param query original query (hash) + * @param bf pointer to bloom filter associated with query; possibly updated (!) + * @param bf_mutator mutation value for bf + * @param xquery extrended query data (can be NULL, depending on type) + * @param xquery_size number of bytes in xquery + * @param reply_block response to validate + * @param reply_block_size number of bytes in reply block + * @return characterization of result + */ +static enum GNUNET_BLOCK_EvaluationResult +block_plugin_mesh_evaluate (void *cls, enum GNUNET_BLOCK_Type type, + const struct GNUNET_HashCode * query, + struct GNUNET_CONTAINER_BloomFilter **bf, + int32_t bf_mutator, const void *xquery, + size_t xquery_size, const void *reply_block, + size_t reply_block_size) +{ + struct GNUNET_HashCode chash; + struct GNUNET_HashCode mhash; + + switch (type) + { + case GNUNET_BLOCK_TYPE_MESH_PEER: + if (0 != xquery_size) + { + GNUNET_break_op (0); + return GNUNET_BLOCK_EVALUATION_REQUEST_INVALID; + } + if (NULL == reply_block) + return GNUNET_BLOCK_EVALUATION_REQUEST_VALID; + if (sizeof (struct PBlock) != reply_block_size) + return GNUNET_BLOCK_EVALUATION_RESULT_INVALID; + if (NULL != bf) + { + GNUNET_CRYPTO_hash (reply_block, reply_block_size, &chash); + GNUNET_BLOCK_mingle_hash (&chash, bf_mutator, &mhash); + if (NULL != *bf) + { + if (GNUNET_YES == GNUNET_CONTAINER_bloomfilter_test (*bf, &mhash)) + return GNUNET_BLOCK_EVALUATION_OK_DUPLICATE; + } + else + { + *bf = GNUNET_CONTAINER_bloomfilter_init (NULL, 8, BLOOMFILTER_K); + } + GNUNET_CONTAINER_bloomfilter_add (*bf, &mhash); + } + + return GNUNET_BLOCK_EVALUATION_OK_LAST; + + + case GNUNET_BLOCK_TYPE_MESH_PEER_BY_TYPE: + /* FIXME: have an xquery? not sure */ + if (0 != xquery_size) + { + GNUNET_break_op (0); + return GNUNET_BLOCK_EVALUATION_REQUEST_INVALID; + } + if (NULL == reply_block) + return GNUNET_BLOCK_EVALUATION_REQUEST_VALID; + if (sizeof (struct PBlock) != reply_block_size) + { + GNUNET_break_op(0); + return GNUNET_BLOCK_EVALUATION_RESULT_INVALID; + } + if (NULL != bf) + { + GNUNET_CRYPTO_hash (reply_block, reply_block_size, &chash); + GNUNET_BLOCK_mingle_hash (&chash, bf_mutator, &mhash); + if (NULL != *bf) + { + if (GNUNET_YES == GNUNET_CONTAINER_bloomfilter_test (*bf, &mhash)) + return GNUNET_BLOCK_EVALUATION_OK_DUPLICATE; + } + else + { + *bf = GNUNET_CONTAINER_bloomfilter_init (NULL, 8, BLOOMFILTER_K); + } + GNUNET_CONTAINER_bloomfilter_add (*bf, &mhash); + } + return GNUNET_BLOCK_EVALUATION_OK_MORE; + + default: + return GNUNET_BLOCK_EVALUATION_TYPE_NOT_SUPPORTED; + } +} + + +/** + * Function called to obtain the key for a block. + * + * @param cls closure + * @param type block type + * @param block block to get the key for + * @param block_size number of bytes in block + * @param key set to the key (query) for the given block + * @return GNUNET_OK on success, GNUNET_SYSERR if type not supported + * (or if extracting a key from a block of this type does not work) + */ +static int +block_plugin_mesh_get_key (void *cls, enum GNUNET_BLOCK_Type type, + const void *block, size_t block_size, + struct GNUNET_HashCode * key) +{ + const struct PBlock *pb; + pb = block; + + switch (type) + { + case GNUNET_BLOCK_TYPE_MESH_PEER: + if (sizeof (struct PBlock) != block_size) + return GNUNET_SYSERR; + *key = pb->id.hashPubKey; + return GNUNET_OK; + case GNUNET_BLOCK_TYPE_MESH_PEER_BY_TYPE: + GNUNET_CRYPTO_hash (&pb->type, sizeof(GNUNET_MESH_ApplicationType), key); + return GNUNET_OK; + default: + GNUNET_break (0); + return GNUNET_SYSERR; + } +} + + +/** + * Entry point for the plugin. + */ +void * +libgnunet_plugin_block_mesh_init (void *cls) +{ + static enum GNUNET_BLOCK_Type types[] = + { + GNUNET_BLOCK_TYPE_MESH_PEER, + GNUNET_BLOCK_TYPE_MESH_PEER_BY_TYPE, + GNUNET_BLOCK_TYPE_ANY /* end of list */ + }; + struct GNUNET_BLOCK_PluginFunctions *api; + + api = GNUNET_malloc (sizeof (struct GNUNET_BLOCK_PluginFunctions)); + api->evaluate = &block_plugin_mesh_evaluate; + api->get_key = &block_plugin_mesh_get_key; + api->types = types; + return api; +} + + +/** + * Exit point from the plugin. + */ +void * +libgnunet_plugin_block_mesh_done (void *cls) +{ + struct GNUNET_TRANSPORT_PluginFunctions *api = cls; + + GNUNET_free (api); + return NULL; +} + +/* end of plugin_block_mesh.c */ diff --git a/src/mesh/test_mesh.conf b/src/mesh/test_mesh.conf index f2e51e4..3b35a16 100644 --- a/src/mesh/test_mesh.conf +++ b/src/mesh/test_mesh.conf @@ -5,16 +5,26 @@ AUTOSTART = NO AUTOSTART = NO [mesh] -DEBUG = YES AUTOSTART = YES ACCEPT_FROM = 127.0.0.1; HOSTNAME = localhost PORT = 10511 # PREFIX = valgrind --leak-check=full # PREFIX = xterm -geometry 100x85 -T peer1 -e gdb --args +REFRESH_PATH_TIME = 3 s +APP_ANNOUNCE_TIME = 5 s +ID_ANNOUNCE_TIME = 5 s +CONNECT_TIMEOUT = 30 s +DEFAULT_TTL = 16 +DHT_REPLICATION_LEVEL = 3 +MAX_TUNNELS = 10 +MAX_MSGS_QUEUE = 20 + +[vpn] +AUTOSTART = NO +PORT = 10012 [dht] -DEBUG = NO AUTOSTART = YES ACCEPT_FROM6 = ::1; ACCEPT_FROM = 127.0.0.1; @@ -30,7 +40,6 @@ DATABASE = sqlite [transport] PLUGINS = tcp -DEBUG = NO ACCEPT_FROM6 = ::1; ACCEPT_FROM = 127.0.0.1; NEIGHBOUR_LIMIT = 50 @@ -46,7 +55,6 @@ PORT = 12092 [arm] DEFAULTSERVICES = core PORT = 12366 -DEBUG = NO [transport-tcp] TIMEOUT = 300 s @@ -59,7 +67,6 @@ WEAKRANDOM = YES HOSTKEY = $SERVICEHOME/.hostkey [PATHS] -DEFAULTCONFIG = test_mesh.conf SERVICEHOME = /tmp/test-mesh/ [dns] @@ -70,3 +77,6 @@ AUTOSTART = NO [namestore] AUTOSTART = NO + +[consensus] +AUTOSTART = NO diff --git a/src/mesh/test_mesh_2dtorus.c b/src/mesh/test_mesh_2dtorus.c index c708e8f..4b6affc 100644 --- a/src/mesh/test_mesh_2dtorus.c +++ b/src/mesh/test_mesh_2dtorus.c @@ -23,9 +23,9 @@ * @brief Test for creating a 2dtorus. */ #include "platform.h" -#include "gnunet_testing_lib.h" +#include "mesh_test_lib.h" +#include "gnunet_mesh_service.h" -#define VERBOSE GNUNET_YES #define REMOVE_DIR GNUNET_YES /** @@ -44,326 +44,84 @@ */ static int ok; -/** - * Be verbose - */ -static int verbose; - -/** - * Total number of peers in the test. - */ -static unsigned long long num_peers; - -/** - * Global configuration file - */ -static struct GNUNET_CONFIGURATION_Handle *testing_cfg; - /** * Total number of currently running peers. */ static unsigned long long peers_running; /** - * Total number of successful connections in the whole network. - */ -static unsigned int total_connections; - -/** - * Total number of counted topo connections - */ -static unsigned int topo_connections; - -/** - * Total number of failed connections in the whole network. - */ -static unsigned int failed_connections; - -/** - * The currently running peer group. - */ -static struct GNUNET_TESTING_PeerGroup *pg; - -/** - * Task called to disconnect peers - */ -static GNUNET_SCHEDULER_TaskIdentifier disconnect_task; - -/** - * Task called to shutdown test. - */ -static GNUNET_SCHEDULER_TaskIdentifier shutdown_handle; - - -/** - * Check whether peers successfully shut down. + * Task to time out. */ -static void -shutdown_callback (void *cls, const char *emsg) -{ - if (emsg != NULL) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "test: Shutdown of peers failed! (%s)\n", emsg); - ok--; - } -#if VERBOSE - else - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "test: All peers successfully shut down!\n"); - } -#endif - GNUNET_CONFIGURATION_destroy (testing_cfg); -} +static GNUNET_SCHEDULER_TaskIdentifier timeout_task; static void shutdown_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: Ending test.\n"); -#endif - - GNUNET_TESTING_daemons_stop (pg, TIMEOUT, &shutdown_callback, NULL); -} - - -static void -disconnect_peers (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: disconnecting peers\n"); - - if (GNUNET_SCHEDULER_NO_TASK != shutdown_handle) - { - GNUNET_SCHEDULER_cancel (shutdown_handle); - shutdown_handle = GNUNET_SCHEDULER_add_now (&shutdown_task, NULL); - } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "shutting down test\n"); } /** - * Prototype of a callback function indicating that two peers - * are currently connected. + * test main: start test when all peers are connected * - * @param cls closure - * @param first peer id for first daemon - * @param second peer id for the second daemon - * @param distance distance between the connected peers - * @param emsg error message (NULL on success) - */ -void -topo_cb (void *cls, const struct GNUNET_PeerIdentity *first, - const struct GNUNET_PeerIdentity *second, const char *emsg) -{ - topo_connections++; - if (NULL != emsg) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "test: Error by topo %u: %s\n", - topo_connections, emsg); - } - else - { - if (first == NULL || second == NULL) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: Connection %u NULL\n", - topo_connections); - if (disconnect_task != GNUNET_SCHEDULER_NO_TASK) - { - GNUNET_SCHEDULER_cancel (disconnect_task); - disconnect_task = GNUNET_SCHEDULER_add_now (&disconnect_peers, NULL); - } - return; - } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: Connection %u ok\n", - topo_connections); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: %s\n", GNUNET_i2s (first)); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: %s\n", GNUNET_i2s (second)); - } -} - - -/** - * peergroup_ready: start test when all peers are connected - * @param cls closure - * @param emsg error message + * @param cls Closure. + * @param ctx Argument to give to GNUNET_MESH_TEST_cleanup on test end. + * @param num_peers Number of peers that are running. + * @param peers Array of peers. + * @param meshes Handle to each of the MESHs of the peers. */ static void -peergroup_ready (void *cls, const char *emsg) +tmain (void *cls, + struct GNUNET_MESH_TEST_Context *ctx, + unsigned int num_peers, + struct GNUNET_TESTBED_Peer **peers, + struct GNUNET_MESH_Handle **meshes) { - if (emsg != NULL) + if (16 != num_peers) { GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "test: Peergroup callback called with error, aborting test!\n"); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: Error from testing: `%s'\n", - emsg); + "running peers mismatch, aborting test!\n"); ok--; - GNUNET_TESTING_daemons_stop (pg, TIMEOUT, &shutdown_callback, NULL); + GNUNET_MESH_TEST_cleanup (ctx); return; } -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "************************************************************\n"); GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "test: Peer Group started successfully!\n"); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: Have %u connections\n", - total_connections); -#endif - - peers_running = GNUNET_TESTING_daemons_running (pg); - if (0 < failed_connections) - { - ok = GNUNET_SYSERR; - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "test: %u connections have FAILED!\n", - failed_connections); - disconnect_task = GNUNET_SCHEDULER_add_now (&disconnect_peers, NULL); - - } - else - { - GNUNET_TESTING_get_topology (pg, &topo_cb, NULL); - disconnect_task = - GNUNET_SCHEDULER_add_delayed (SHORT_TIME, &disconnect_peers, NULL); - ok = GNUNET_OK; - } - -} - - -/** - * Function that will be called whenever two daemons are connected by - * the testing library. - * - * @param cls closure - * @param first peer id for first daemon - * @param second peer id for the second daemon - * @param distance distance between the connected peers - * @param first_cfg config for the first daemon - * @param second_cfg config for the second daemon - * @param first_daemon handle for the first daemon - * @param second_daemon handle for the second daemon - * @param emsg error message (NULL on success) - */ -static void -connect_cb (void *cls, const struct GNUNET_PeerIdentity *first, - const struct GNUNET_PeerIdentity *second, uint32_t distance, - const struct GNUNET_CONFIGURATION_Handle *first_cfg, - const struct GNUNET_CONFIGURATION_Handle *second_cfg, - struct GNUNET_TESTING_Daemon *first_daemon, - struct GNUNET_TESTING_Daemon *second_daemon, const char *emsg) -{ - if (emsg == NULL) - { - total_connections++; - } - else - { - failed_connections++; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "test: Problem with new connection (%s)\n", emsg); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: (%s)\n", GNUNET_i2s (first)); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: (%s)\n", GNUNET_i2s (second)); - } - + "testbed started successfully with ?? connections\n"); + peers_running = num_peers; + timeout_task = GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_MINUTES, + &shutdown_task, ctx); + ok = GNUNET_OK; + GNUNET_MESH_TEST_cleanup (ctx); } -/** - * run: load configuration options and schedule test to run (start peergroup) - * @param cls closure - * @param args argv - * @param cfgfile configuration file name (can be NULL) - * @param cfg configuration handle - */ -static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) -{ - struct GNUNET_TESTING_Host *hosts; - - ok = GNUNET_NO; - total_connections = 0; - failed_connections = 0; - testing_cfg = GNUNET_CONFIGURATION_dup (cfg); - - GNUNET_log_setup ("test_mesh_2dtorus", -#if VERBOSE - "DEBUG", -#else - "WARNING", -#endif - NULL); - -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: Starting daemons.\n"); - GNUNET_CONFIGURATION_set_value_string (testing_cfg, "testing", - "use_progressbars", "YES"); -#endif - - if (GNUNET_OK != - GNUNET_CONFIGURATION_get_value_number (testing_cfg, "testing", - "num_peers", &num_peers)) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "Option TESTING:NUM_PEERS is required!\n"); - return; - } - - hosts = GNUNET_TESTING_hosts_load (testing_cfg); - - pg = GNUNET_TESTING_peergroup_start (testing_cfg, num_peers, TIMEOUT, - &connect_cb, &peergroup_ready, NULL, - hosts); - GNUNET_assert (pg != NULL); - shutdown_handle = - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, - &shutdown_task, NULL); -} - - -/** - * test_mesh_2dtorus command line options - */ -static struct GNUNET_GETOPT_CommandLineOption options[] = { - {'V', "verbose", NULL, - gettext_noop ("be verbose (print progress information)"), - 0, &GNUNET_GETOPT_set_one, &verbose}, - GNUNET_GETOPT_OPTION_END -}; - - /** * Main: start test */ int main (int argc, char *argv[]) { - char *const argv2[] = { - argv[0], - "-c", - "test_mesh_2dtorus.conf", -#if VERBOSE - "-L", - "DEBUG", -#endif - NULL - }; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: Start\n"); + ok = GNUNET_SYSERR; + + GNUNET_MESH_TEST_run ("test_mesh_2dtorus", + "test_mesh_2dtorus.conf", + 16, + &tmain, + NULL, + NULL, + NULL, + NULL, + NULL + ); - - GNUNET_PROGRAM_run ((sizeof (argv2) / sizeof (char *)) - 1, argv2, - "test_mesh_2dtorus", gettext_noop ("Test mesh 2d torus."), - options, &run, NULL); -#if REMOVE_DIR - GNUNET_DISK_directory_remove ("/tmp/test_mesh_2dtorus"); -#endif if (GNUNET_OK != ok) { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "test: FAILED!\n"); + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "FAILED!\n"); return 1; } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: success\n"); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "success\n"); return 0; } diff --git a/src/mesh/test_mesh_2dtorus.conf b/src/mesh/test_mesh_2dtorus.conf index 9a2227b..fb235fe 100644 --- a/src/mesh/test_mesh_2dtorus.conf +++ b/src/mesh/test_mesh_2dtorus.conf @@ -1,23 +1,38 @@ [PATHS] SERVICEHOME = /tmp/test_mesh_small/ -DEFAULTCONFIG = test_mesh_small.conf + +[mesh] +PORT = 10005 +ACCEPT_FROM = 127.0.0.1; +HOSTNAME = localhost +DHT_REPLICATION_LEVEL = 10 +# PREFIX = valgrind --leak-check=full +# PREFIX = xterm -geometry 100x85 -T peer1 -e gdb --args + +[testing] +WEAKRANDOM = YES + +[testbed] +NUM_PEERS = 16 +OVERLAY_TOPOLOGY = 2D_TORUS + + [arm] PORT = 10010 DEFAULTSERVICES = core dht mesh -#DEBUG = YES [statistics] AUTOSTART = YES PORT = 10000 [dht] -DEBUG = NO AUTOSTART = YES ACCEPT_FROM6 = ::1; ACCEPT_FROM = 127.0.0.1; HOSTNAME = localhost PORT = 10001 +DISABLE_TRY_CONNECT = YES [nse] WORKBITS = 0 @@ -26,6 +41,10 @@ WORKBITS = 0 AUTOSTART = NO PORT = 10011 +[vpn] +AUTOSTART = NO +PORT = 10012 + [transport] PORT = 10002 AUTOSTART = YES @@ -38,6 +57,8 @@ BEHIND_NAT = NO ALLOW_NAT = NO INTERNAL_ADDRESS = 127.0.0.1 EXTERNAL_ADDRESS = 127.0.0.1 +RETURN_LOCAL_ADDRESSES = YES +USE_LOCALADDR = YES [ats] WAN_QUOTA_IN = 1 GB @@ -50,38 +71,3 @@ PORT = 10003 [peerinfo] AUTOSTART = YES PORT = 10004 - -[mesh] -PORT = 10005 -DEBUG=YES -ACCEPT_FROM = 127.0.0.1; -HOSTNAME = localhost -# PREFIX = valgrind --leak-check=full -# PREFIX = xterm -geometry 100x85 -T peer1 -e gdb --args - -[testing] -NUM_PEERS = 16 -WEAKRANDOM = YES -TOPOLOGY = 2D_TORUS -CONNECT_TOPOLOGY = 2D_TORUS -#TOPOLOGY_FILE = small.dat -CONNECT_TOPOLOGY = 2D_TORUS -#CONNECT_TOPOLOGY_OPTION = CONNECT_MINIMUM -#CONNECT_TOPOLOGY_OPTION_MODIFIER = 25 -#PERCENTAGE = 3 -#PROBABILITY = .1 -F2F = NO -CONNECT_TIMEOUT = 600 s -CONNECT_ATTEMPTS = 2 -DEBUG = YES -HOSTKEYSFILE = ../../contrib/testing_hostkeys.dat -MAX_CONCURRENT_SSH = 10 -USE_PROGRESSBARS = YES -PEERGROUP_TIMEOUT = 2400 s -TOPOLOGY_OUTPUT_FILE = mesh_topo_initial -MAX_OUTSTANDING_CONNECTIONS = 75 -#SINGLE_PEERINFO_PER_HOST = YES -#NUM_PEERINFO_PER_HOST = 10 -#SINGLE_STATISTICS_PER_HOST = YES -#NUM_STATISTICS_PER_HOST = 10 -DELETE_FILES = YES diff --git a/src/mesh/test_mesh_api.c b/src/mesh/test_mesh_api.c index 1e12e9b..349ec80 100644 --- a/src/mesh/test_mesh_api.c +++ b/src/mesh/test_mesh_api.c @@ -23,21 +23,20 @@ * @brief test mesh api: dummy test of callbacks * @author Bartlomiej Polot */ - #include "platform.h" #include "gnunet_util_lib.h" +#include "gnunet_testing_lib.h" #include "gnunet_dht_service.h" #include "gnunet_mesh_service.h" -#define VERBOSE 1 -#define VERBOSE_ARM 0 - -static struct GNUNET_OS_Process *arm_pid; static struct GNUNET_MESH_Handle *mesh; + static struct GNUNET_MESH_Tunnel *t; + static int result; + static GNUNET_SCHEDULER_TaskIdentifier abort_task; -static GNUNET_SCHEDULER_TaskIdentifier test_task; + /** * Function is called whenever a message is received. @@ -60,8 +59,10 @@ callback (void *cls, struct GNUNET_MESH_Tunnel *tunnel, void **tunnel_ctx, return GNUNET_OK; } -static struct GNUNET_MESH_MessageHandler handlers[] = { {&callback, 1, 0}, -{NULL, 0, 0} + +static struct GNUNET_MESH_MessageHandler handlers[] = { + { &callback, 1, 0 }, + { NULL, 0, 0 } }; @@ -80,113 +81,58 @@ do_shutdown (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { GNUNET_MESH_disconnect (mesh); } - if (0 != GNUNET_OS_process_kill (arm_pid, SIGTERM)) - { - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); - } - GNUNET_assert (GNUNET_OK == GNUNET_OS_process_wait (arm_pid)); - GNUNET_OS_process_destroy (arm_pid); } + static void do_abort (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { - if (0 != test_task) - { - GNUNET_SCHEDULER_cancel (test_task); - } result = GNUNET_SYSERR; abort_task = 0; do_shutdown (cls, tc); } + static void -test (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) { - struct GNUNET_CONFIGURATION_Handle *cfg = cls; static const GNUNET_MESH_ApplicationType app[] = - { 1, 2, 3, 4, 5, 6, 7, 8, 0 }; + { 1, 2, 3, 4, 5, 6, 7, 8, 0 }; - test_task = (GNUNET_SCHEDULER_TaskIdentifier) 0; - mesh = GNUNET_MESH_connect (cfg, 10, NULL, NULL, NULL, handlers, app); + mesh = GNUNET_MESH_connect (cfg, NULL, NULL, NULL, handlers, app); if (NULL == mesh) { GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "test: Couldn't connect to mesh :(\n"); + result = GNUNET_SYSERR; return; } else { GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: YAY! CONNECTED TO MESH :D\n"); } - t = GNUNET_MESH_tunnel_create (mesh, NULL, NULL, NULL, NULL); - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 5), &do_shutdown, NULL); -} - - -static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) -{ - GNUNET_log_setup ("test_mesh_api", -#if VERBOSE - "DEBUG", -#else - "WARNING", -#endif - NULL); - arm_pid = - GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-arm", - "gnunet-service-arm", -#if VERBOSE_ARM - "-L", "DEBUG", -#endif - "-c", "test_mesh.conf", NULL); - abort_task = GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 20), &do_abort, NULL); - - test_task = GNUNET_SCHEDULER_add_now (&test, (void *) cfg); - } int main (int argc, char *argv[]) { - int ret; - - char *const argv2[] = { "test-mesh-api", - "-c", "test_mesh.conf", -#if VERBOSE - "-L", "DEBUG", -#endif - NULL - }; - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - - ret = - GNUNET_PROGRAM_run ((sizeof (argv2) / sizeof (char *)) - 1, argv2, - "test-mesh-api", "nohelp", options, &run, NULL); - - if (GNUNET_OK != ret) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "run failed with error code %d\n", - ret); - return 1; - } - if (GNUNET_SYSERR == result) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "test failed\n"); + result = GNUNET_OK; + if (0 != GNUNET_TESTING_peer_run ("test-mesh-api", + "test_mesh.conf", + &run, NULL)) return 1; - } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test ok\n"); - return 0; + return (result == GNUNET_OK) ? 0 : 1; } + +/* end of test_mesh_api.c */ + diff --git a/src/mesh/test_mesh_local_1.c b/src/mesh/test_mesh_local_1.c index d80bee8..4f40688 100644 --- a/src/mesh/test_mesh_local_1.c +++ b/src/mesh/test_mesh_local_1.c @@ -19,7 +19,7 @@ */ /** - * @file mesh/test_mesh_local.c + * @file mesh/test_mesh_local_1.c * @brief test mesh local: test of tunnels with just one peer * @author Bartlomiej Polot */ @@ -27,21 +27,24 @@ #include "platform.h" #include "gnunet_util_lib.h" #include "gnunet_dht_service.h" +#include "gnunet_testing_lib.h" #include "gnunet_mesh_service.h" -#define VERBOSE 1 -#define VERBOSE_ARM 0 -static struct GNUNET_OS_Process *arm_pid; static struct GNUNET_MESH_Handle *mesh_peer_1; + static struct GNUNET_MESH_Handle *mesh_peer_2; + static struct GNUNET_MESH_Tunnel *t; + static unsigned int one = 1; + static unsigned int two = 2; -static int result; +static int result = GNUNET_OK; + static GNUNET_SCHEDULER_TaskIdentifier abort_task; -static GNUNET_SCHEDULER_TaskIdentifier test_task; + static GNUNET_SCHEDULER_TaskIdentifier shutdown_task; @@ -70,14 +73,6 @@ do_shutdown (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { GNUNET_MESH_disconnect (mesh_peer_2); } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: arm\n"); - if (0 != GNUNET_OS_process_kill (arm_pid, SIGTERM)) - { - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); - } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: Wait\n"); - GNUNET_assert (GNUNET_OK == GNUNET_OS_process_wait (arm_pid)); - GNUNET_OS_process_destroy (arm_pid); } @@ -88,10 +83,6 @@ static void do_abort (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: ABORT\n"); - if (0 != test_task) - { - GNUNET_SCHEDULER_cancel (test_task); - } result = GNUNET_SYSERR; abort_task = 0; if (GNUNET_SCHEDULER_NO_TASK != shutdown_task) @@ -244,18 +235,21 @@ do_find (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) /** - * Main test function + * Initialize framework and start test */ static void -test (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) { - struct GNUNET_CONFIGURATION_Handle *cfg = cls; static const GNUNET_MESH_ApplicationType app1[] = { 1, 0 }; static const GNUNET_MESH_ApplicationType app2[] = { 0 }; - test_task = GNUNET_SCHEDULER_NO_TASK; + abort_task = + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply + (GNUNET_TIME_UNIT_SECONDS, 20), &do_abort, + NULL); mesh_peer_1 = GNUNET_MESH_connect (cfg, /* configuration */ - 10, /* queue size */ (void *) &one, /* cls */ &inbound_tunnel, /* inbound new hndlr */ &inbound_end, /* inbound end hndlr */ @@ -263,7 +257,6 @@ test (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) app1); /* apps offered */ mesh_peer_2 = GNUNET_MESH_connect (cfg, /* configuration */ - 10, /* queue size */ (void *) &two, /* cls */ &inbound_tunnel, /* inbound new hndlr */ &inbound_end, /* inbound end hndlr */ @@ -272,86 +265,30 @@ test (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) if (NULL == mesh_peer_1 || NULL == mesh_peer_2) { GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "test: Couldn't connect to mesh :(\n"); + result = GNUNET_SYSERR; return; } else { GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: YAY! CONNECTED TO MESH :D\n"); } - t = GNUNET_MESH_tunnel_create (mesh_peer_2, NULL, &peer_conected, &peer_disconnected, (void *) &two); GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_SECONDS, &do_find, NULL); } -/** - * Initialize framework and start test - */ -static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) -{ - GNUNET_log_setup ("test_mesh_local", -#if VERBOSE - "DEBUG", -#else - "WARNING", -#endif - NULL); - arm_pid = - GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-arm", - "gnunet-service-arm", -#if VERBOSE_ARM - "-L", "DEBUG", -#endif - "-c", "test_mesh.conf", NULL); - - abort_task = - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply - (GNUNET_TIME_UNIT_SECONDS, 20), &do_abort, - NULL); - - test_task = GNUNET_SCHEDULER_add_now (&test, (void *) cfg); - -} - - /** * Main */ int main (int argc, char *argv[]) { - int ret; - - char *const argv2[] = { "test-mesh-local", - "-c", "test_mesh.conf", -#if VERBOSE - "-L", "DEBUG", -#endif - NULL - }; - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - - result = GNUNET_OK; - ret = - GNUNET_PROGRAM_run ((sizeof (argv2) / sizeof (char *)) - 1, argv2, - "test-mesh-local", "nohelp", options, &run, NULL); - - if (GNUNET_OK != ret) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "run failed with error code %d\n", - ret); + if (0 != GNUNET_TESTING_peer_run ("test-mesh-local-1", + "test_mesh.conf", + &run, NULL)) return 1; - } - if (GNUNET_SYSERR == result) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "test failed\n"); - return 1; - } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test ok\n"); - return 0; + return (result == GNUNET_OK) ? 0 : 1; } + +/* end of test_mesh_local_1.c */ diff --git a/src/mesh/test_mesh_local_2.c b/src/mesh/test_mesh_local_2.c index d495b71..935c3b2 100644 --- a/src/mesh/test_mesh_local_2.c +++ b/src/mesh/test_mesh_local_2.c @@ -26,21 +26,24 @@ #include "platform.h" #include "gnunet_util_lib.h" +#include "gnunet_testing_lib.h" #include "gnunet_dht_service.h" #include "gnunet_mesh_service.h" -#define VERBOSE 1 -#define VERBOSE_ARM 0 - -static struct GNUNET_OS_Process *arm_pid; static struct GNUNET_MESH_Handle *mesh_peer_1; + static struct GNUNET_MESH_Handle *mesh_peer_2; + static struct GNUNET_MESH_Tunnel *t; + static unsigned int one = 1; + static unsigned int two = 2; -static int result; +static int result = GNUNET_OK; + static GNUNET_SCHEDULER_TaskIdentifier abort_task; + static GNUNET_SCHEDULER_TaskIdentifier test_task; @@ -69,14 +72,6 @@ do_shutdown (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { GNUNET_MESH_disconnect (mesh_peer_2); } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: arm\n"); - if (0 != GNUNET_OS_process_kill (arm_pid, SIGTERM)) - { - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); - } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: Wait\n"); - GNUNET_assert (GNUNET_OK == GNUNET_OS_process_wait (arm_pid)); - GNUNET_OS_process_destroy (arm_pid); } @@ -226,12 +221,11 @@ static struct GNUNET_MESH_MessageHandler handlers2[] = { {NULL, 0, 0} }; static void do_connect_peer_1 (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { - struct GNUNET_CONFIGURATION_Handle *cfg = cls; + const struct GNUNET_CONFIGURATION_Handle *cfg = cls; static const GNUNET_MESH_ApplicationType app1[] = { 1, 0 }; test_task = GNUNET_SCHEDULER_NO_TASK; mesh_peer_1 = GNUNET_MESH_connect (cfg, /* configuration */ - 10, /* queue size */ (void *) &one, /* cls */ &inbound_tunnel, /* inbound new hndlr */ &inbound_end, /* inbound end hndlr */ @@ -241,18 +235,20 @@ do_connect_peer_1 (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) /** - * Main test function + * Initialize framework and start test */ static void -test (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) { - struct GNUNET_CONFIGURATION_Handle *cfg = cls; static const GNUNET_MESH_ApplicationType app2[] = { 0 }; - test_task = GNUNET_SCHEDULER_NO_TASK; - + abort_task = + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply + (GNUNET_TIME_UNIT_SECONDS, 20), &do_abort, + NULL); mesh_peer_2 = GNUNET_MESH_connect (cfg, /* configuration */ - 10, /* queue size */ (void *) &two, /* cls */ &inbound_tunnel, /* inbound new hndlr */ &inbound_end, /* inbound end hndlr */ @@ -261,52 +257,20 @@ test (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) if (NULL == mesh_peer_2) { GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "test: Couldn't connect to mesh :(\n"); + result = GNUNET_SYSERR; return; } else { GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: YAY! CONNECTED TO MESH :D\n"); } - t = GNUNET_MESH_tunnel_create (mesh_peer_2, NULL, &peer_conected, &peer_disconnected, (void *) &two); GNUNET_MESH_peer_request_connect_by_type (t, 1); test_task = GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 5), - &do_connect_peer_1, cfg); -} - - -/** - * Initialize framework and start test - */ -static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) -{ - GNUNET_log_setup ("test_mesh_local", -#if VERBOSE - "DEBUG", -#else - "WARNING", -#endif - NULL); - arm_pid = - GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-arm", - "gnunet-service-arm", -#if VERBOSE_ARM - "-L", "DEBUG", -#endif - "-c", "test_mesh.conf", NULL); - - abort_task = - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply - (GNUNET_TIME_UNIT_SECONDS, 20), &do_abort, - NULL); - - test_task = GNUNET_SCHEDULER_add_now (&test, (void *) cfg); - + &do_connect_peer_1, (void*) cfg); } @@ -316,34 +280,11 @@ run (void *cls, char *const *args, const char *cfgfile, int main (int argc, char *argv[]) { - int ret; - - char *const argv2[] = { "test-mesh-local", - "-c", "test_mesh.conf", -#if VERBOSE - "-L", "DEBUG", -#endif - NULL - }; - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - - ret = - GNUNET_PROGRAM_run ((sizeof (argv2) / sizeof (char *)) - 1, argv2, - "test-mesh-local", "nohelp", options, &run, NULL); - - if (GNUNET_OK != ret) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "run failed with error code %d\n", - ret); + if (0 != GNUNET_TESTING_peer_run ("test-mesh-local-2", + "test_mesh.conf", + &run, NULL)) return 1; - } - if (GNUNET_SYSERR == result) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "test failed\n"); - return 1; - } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test ok\n"); - return 0; + return (result == GNUNET_OK) ? 0 : 1; } + +/* end of test_mesh_local_2.c */ diff --git a/src/mesh/test_mesh_local_traffic.c b/src/mesh/test_mesh_local_traffic.c new file mode 100644 index 0000000..cd54ea8 --- /dev/null +++ b/src/mesh/test_mesh_local_traffic.c @@ -0,0 +1,526 @@ +/* + This file is part of GNUnet. + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @file mesh/test_mesh_local_traffic.c + * @brief test mesh local traffic: test of tunnels with just one peer + * @author Bartlomiej Polot + */ + +#include "platform.h" +#include "gnunet_util_lib.h" +#include "gnunet_mesh_service.h" +#include "gnunet_testing_lib.h" +#include + +#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 5) + +#define TARGET 1000 + +/** + * DIFFERENT TESTS TO RUN + */ +#define FWD 0 +#define BCK 1 +#define BOTH 2 + + +GNUNET_NETWORK_STRUCT_BEGIN + +struct test_traffic_message +{ + struct GNUNET_MessageHeader header; + uint32_t data GNUNET_PACKED; +}; + +GNUNET_NETWORK_STRUCT_END + + +/** Which test to run, based on executable name */ +static int test; + +static int started; + +/** How many packets to send from root to leaf */ +static unsigned int to_send_fwd; + +/** How many packets to send from leaf to root */ +static unsigned int to_send_bck; + +static unsigned int sent_fwd = 0; + +static unsigned int got_fwd = 0; + +static unsigned int sent_bck = 0; + +static unsigned int got_bck = 0; + +static struct GNUNET_MESH_Handle *mesh_peer_1; + +static struct GNUNET_MESH_Handle *mesh_peer_2; + +static struct GNUNET_MESH_Tunnel *t_fwd; + +static struct GNUNET_MESH_Tunnel *t_bck; + +static unsigned int one = 1; + +static unsigned int two = 2; + +static int result = GNUNET_SYSERR; + +static GNUNET_SCHEDULER_TaskIdentifier abort_task; + +static GNUNET_SCHEDULER_TaskIdentifier shutdown_task; + +static struct GNUNET_TIME_Absolute start_time; + +static struct GNUNET_TIME_Absolute end_time; + +static struct GNUNET_PeerIdentity peer_id; + + +/** + * Shutdown nicely + */ +static void +do_shutdown (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "shutdown\n"); + if (0 != abort_task) + { + GNUNET_SCHEDULER_cancel (abort_task); + } + if (NULL != t_fwd) + { + GNUNET_MESH_tunnel_destroy(t_fwd); + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "D1\n"); + if (NULL != mesh_peer_1) + { + GNUNET_MESH_disconnect (mesh_peer_1); + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "D2\n"); + if (NULL != mesh_peer_2) + { + GNUNET_MESH_disconnect (mesh_peer_2); + } +} + + +/** + * Something went wrong and timed out. Kill everything and set error flag + */ +static void +do_abort (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "ABORT\n"); + result = GNUNET_SYSERR; + abort_task = 0; + if (GNUNET_SCHEDULER_NO_TASK != shutdown_task) + { + GNUNET_SCHEDULER_cancel (shutdown_task); + shutdown_task = GNUNET_SCHEDULER_NO_TASK; + } + do_shutdown (cls, tc); +} + +static void +finish(void) +{ + if (GNUNET_SCHEDULER_NO_TASK != shutdown_task) + GNUNET_SCHEDULER_cancel(shutdown_task); + shutdown_task = GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_SECONDS, + &do_shutdown, NULL); +} + + +/** + * Transmit ready callback. + * + * @param cls Closure (peer number of peer sending the data). + * @param size Buffer size. + * @param buf Buffer. + */ +static size_t +tmt_rdy (void *cls, size_t size, void *buf) +{ + unsigned int peer_number = *(unsigned int *) cls; + struct GNUNET_MessageHeader *m = buf; + struct GNUNET_MESH_Tunnel *t; + struct test_traffic_message *msg = buf; + size_t msize = sizeof (struct test_traffic_message); + unsigned int *sent; + unsigned int target; + char *s; + + if (0 == size || NULL == buf) + return 0; + + if (1 == peer_number) + { + sent = &sent_fwd; + target = to_send_fwd; + t = t_fwd; + s = "FWD"; + } + else if (2 == peer_number) + { + sent = &sent_bck; + target = to_send_bck; + t = t_bck; + s = "BCK"; + } + else + GNUNET_abort(); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Sending %s data packet # %4u\n", + s, *sent); + GNUNET_assert (size >= msize); + if (GNUNET_YES == started) + { + (*sent)++; + if (target > *sent) { + GNUNET_MESH_notify_transmit_ready (t, GNUNET_NO, + GNUNET_TIME_UNIT_FOREVER_REL, + &peer_id, msize, &tmt_rdy, cls); + } + } + m->size = htons (msize); + m->type = htons (1); + msg->data = htonl (*sent - 1); + return msize; +} + + +/** + * Function is called whenever a message is received. + * + * @param cls closure (set from GNUNET_MESH_connect) + * @param tunnel connection to the other end + * @param tunnel_ctx place to store local state associated with the tunnel + * @param sender who sent the message + * @param message the actual message + * @param atsi performance data for the connection + * @return GNUNET_OK to keep the connection open, + * GNUNET_SYSERR to close it (signal serious error) + */ +static int +data_callback (void *cls, struct GNUNET_MESH_Tunnel *tunnel, void **tunnel_ctx, + const struct GNUNET_PeerIdentity *sender, + const struct GNUNET_MessageHeader *message, + const struct GNUNET_ATS_Information *atsi) +{ + struct test_traffic_message *msg; + unsigned int *peer_number = cls; + unsigned int *got; + unsigned int target; + + if (GNUNET_NO == started) + { + GNUNET_break (2 == *peer_number); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Got initial data packet\n"); + started = GNUNET_YES; + start_time = GNUNET_TIME_absolute_get(); + if (FWD != test) // Send leaf -> root + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " sending first BCK data\n"); + GNUNET_MESH_notify_transmit_ready (t_bck, GNUNET_NO, + GNUNET_TIME_UNIT_FOREVER_REL, + NULL, + sizeof (struct test_traffic_message), + &tmt_rdy, &two); + } + if (BCK != test) // Send root -> leaf + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " sending first FWD data\n"); + GNUNET_MESH_notify_transmit_ready (t_fwd, GNUNET_NO, + GNUNET_TIME_UNIT_FOREVER_REL, + &peer_id, + sizeof (struct test_traffic_message), + &tmt_rdy, &one); + } + return GNUNET_OK; + } + + if (*peer_number == 1) + { + got = &got_bck; + target = to_send_bck; + } + else if (*peer_number == 2) + { + got = &got_fwd; + target = to_send_fwd; + } + else + { + GNUNET_abort(); + } + msg = (struct test_traffic_message *) message; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Got data packet # %u [%u]\n", + ntohl (msg->data), *got + 1); + (*got)++; + if (target == *got) + { + if (to_send_bck == sent_bck && to_send_fwd == sent_fwd) { + end_time = GNUNET_TIME_absolute_get(); + result = GNUNET_OK; + finish(); + } + return GNUNET_OK; + } + if (GNUNET_SCHEDULER_NO_TASK != shutdown_task) + GNUNET_SCHEDULER_cancel (shutdown_task); + shutdown_task = + GNUNET_SCHEDULER_add_delayed (TIMEOUT, &do_shutdown, + NULL); + return GNUNET_OK; +} + + +/** + * Method called whenever another peer has added us to a tunnel + * the other peer initiated. + * + * @param cls closure + * @param tunnel new handle to the tunnel + * @param initiator peer that started the tunnel + * @param atsi performance information for the tunnel + * @return initial tunnel context for the tunnel (can be NULL -- that's not an error) + */ +static void * +inbound_tunnel (void *cls, struct GNUNET_MESH_Tunnel *tunnel, + const struct GNUNET_PeerIdentity *initiator, + const struct GNUNET_ATS_Information *atsi) +{ + unsigned int id = *(unsigned int *) cls; + + t_bck = tunnel; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "received incoming tunnel %p\n", tunnel); + if (id != 2) + { + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + "received incoming tunnel on peer 1\n"); + result = GNUNET_SYSERR; + } + return NULL; +} + + +/** + * Function called whenever an inbound tunnel is destroyed. Should clean up + * any associated state. + * + * @param cls closure (set from GNUNET_MESH_connect) + * @param tunnel connection to the other end (henceforth invalid) + * @param tunnel_ctx place where local state associated + * with the tunnel is stored + */ +static void +inbound_end (void *cls, const struct GNUNET_MESH_Tunnel *tunnel, + void *tunnel_ctx) +{ + unsigned int id = *(unsigned int *) cls; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "incoming tunnel closed\n"); + if (id != 2) + { + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + "received closing tunnel on peer 1\n"); + result = GNUNET_SYSERR; + } +} + + +/** + * Method called whenever a peer has connected to the tunnel. + * + * @param cls Closure. + * @param peer Peer identity of connected peer. + */ +static void +peer_connected (void *cls, const struct GNUNET_PeerIdentity *peer, + const struct GNUNET_ATS_Information *atsi) +{ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "peer connected\n"); + peer_id = *peer; + /* Force an inbound tunnel notification on peer 2 */ + GNUNET_MESH_notify_transmit_ready (t_fwd, GNUNET_NO, GNUNET_TIME_UNIT_FOREVER_REL, + peer, sizeof (struct test_traffic_message), + &tmt_rdy, &one); +} + + +/** + * Method called whenever a peer has connected to the tunnel. + * + * @param cls closure + * @param peer peer identity the tunnel was created to, NULL on timeout + * @param atsi performance data for the connection + */ +static void +peer_disconnected (void *cls, const struct GNUNET_PeerIdentity *peer) +{ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "peer disconnected\n"); +} + + +/** + * Handler array for traffic received on peer1 + */ +static struct GNUNET_MESH_MessageHandler handlers[] = { + {&data_callback, 1, sizeof (struct test_traffic_message)}, + {NULL, 0, 0} +}; + + +/** + * Handler array for traffic received on peer2 (none expected) + */ +static struct GNUNET_MESH_MessageHandler handlers_null[] = { {NULL, 0, 0} }; + + +/** + * Initialize framework and start test + */ +static void +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) +{ + static const GNUNET_MESH_ApplicationType app1[] = { 0 }; + static const GNUNET_MESH_ApplicationType app2[] = { 1, 0 }; + + abort_task = + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply + (GNUNET_TIME_UNIT_SECONDS, 20), &do_abort, + NULL); + mesh_peer_1 = GNUNET_MESH_connect (cfg, /* configuration */ + (void *) &one, /* cls */ + NULL, /* inbound new hndlr */ + NULL, /* inbound end hndlr */ + /* traffic handlers */ + test == FWD ? handlers_null : handlers, + app1); /* apps offered */ + + mesh_peer_2 = GNUNET_MESH_connect (cfg, /* configuration */ + (void *) &two, /* cls */ + &inbound_tunnel, /* inbound new hndlr */ + &inbound_end, /* inbound end hndlr */ + handlers, /* traffic handlers */ + app2); /* apps offered */ + if (NULL == mesh_peer_1 || NULL == mesh_peer_2) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Couldn't connect to mesh\n"); + result = GNUNET_SYSERR; + return; + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Connected to mesh\n"); + } + t_fwd = GNUNET_MESH_tunnel_create (mesh_peer_1, NULL, &peer_connected, + &peer_disconnected, (void *) &two); + GNUNET_MESH_peer_request_connect_by_type (t_fwd, 1); +} + + +/** + * Main + */ +int +main (int argc, char *argv[]) +{ + if (strstr (argv[0], "test_mesh_local_traffic_fwd") != NULL) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "FWD\n"); + test = FWD; + to_send_fwd = TARGET; + } + else if (strstr (argv[0], "test_mesh_local_traffic_bck") != NULL) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "BCK\n"); + test = BCK; + to_send_bck = TARGET; + } + else if (strstr (argv[0], "test_mesh_local_traffic_both") != NULL) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "BOTH\n"); + test = BOTH; + to_send_bck = to_send_fwd = TARGET; + } + else + { + return 1; + } + + if (0 != GNUNET_TESTING_peer_run ("test-mesh-local-traffic", + "test_mesh.conf", + &run, NULL)) + return 1; + if (result != GNUNET_OK) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Failed.\nFWD expected: %u, Sent: %u, Got: %u\n", + to_send_fwd, sent_fwd, got_fwd); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "BCK expected: %u, Sent: %u, Got: %u\n", + to_send_bck, sent_bck, got_bck); + return 1; + } + else + { + struct GNUNET_TIME_Relative total_time; + unsigned int total_traffic; + char *name; + + total_traffic = BOTH == test ? 2 * TARGET : TARGET; + switch (test) + { + case FWD: + name = "Local traffic Root to Leaf"; + break; + case BCK: + name = "Local traffic Leaf to Root"; + break; + case BOTH: + name = "Local traffic bidirectional"; + break; + default: + GNUNET_assert (0); + } + + total_time = GNUNET_TIME_absolute_get_difference(start_time, end_time); + FPRINTF (stderr, "\nTest time %llu ms\n", + (unsigned long long) total_time.rel_value); + FPRINTF (stderr, "Test payload bandwidth: %f kb/s\n", + total_traffic * 4.0 / total_time.rel_value); // 4bytes * kb/ms + FPRINTF (stderr, "Test throughput: %f packets/s\n\n", + total_traffic * 1000.0 / total_time.rel_value); // 1000 packets * ms + GAUGER ("MESH", + name, + total_traffic * 1000.0 / total_time.rel_value, + "packets/s"); + } + return 0; +} + +/* end of test_mesh_local_traffic.c */ diff --git a/src/mesh/test_mesh_path.conf b/src/mesh/test_mesh_path.conf deleted file mode 100644 index c3d8a2c..0000000 --- a/src/mesh/test_mesh_path.conf +++ /dev/null @@ -1,69 +0,0 @@ -[fs] -AUTOSTART = NO - -[resolver] -AUTOSTART = NO - -[mesh] -DEBUG = YES -AUTOSTART = YES -ACCEPT_FROM = 127.0.0.1; -HOSTNAME = localhost -PORT = 10511 -# PREFIX = valgrind --leak-check=full -# PREFIX = xterm -geometry 100x85 -T peer1 -e gdb --args - -[dht] -DEBUG = NO -AUTOSTART = YES -ACCEPT_FROM6 = ::1; -ACCEPT_FROM = 127.0.0.1; -HOSTNAME = localhost -PORT = 12100 - -[block] -plugins = dht test - -[dhtcache] -QUOTA = 1 MB -DATABASE = sqlite - -[transport] -PLUGINS = tcp -DEBUG = NO -ACCEPT_FROM6 = ::1; -ACCEPT_FROM = 127.0.0.1; -NEIGHBOUR_LIMIT = 50 -PORT = 12365 - -[ats] -WAN_QUOTA_OUT = 3932160 -WAN_QUOTA_IN = 3932160 - -[core] -PORT = 12092 - -[arm] -DEFAULTSERVICES = core -PORT = 12366 -DEBUG = NO - -[transport-tcp] -TIMEOUT = 300 s -PORT = 12368 - -[TESTING] -WEAKRANDOM = YES - -[gnunetd] -HOSTKEY = $SERVICEHOME/.hostkey - -[PATHS] -DEFAULTCONFIG = test_mesh.conf -SERVICEHOME = /tmp/test-mesh/ - -[dns] -AUTOSTART = NO - -[nse] -AUTOSTART = NO diff --git a/src/mesh/test_mesh_regex.c b/src/mesh/test_mesh_regex.c new file mode 100644 index 0000000..d7089da --- /dev/null +++ b/src/mesh/test_mesh_regex.c @@ -0,0 +1,444 @@ +/* + This file is part of GNUnet. + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ +/** + * @file mesh/test_mesh_regex.c + * + * @brief Test for regex announce / by_string connect. + * based on the 2dtorus testcase + */ +#include "platform.h" +#include "mesh_test_lib.h" +#include "gnunet_mesh_service.h" + +#define REMOVE_DIR GNUNET_YES +#define MESH_REGEX_PEERS 4 + +/** + * How long until we give up on connecting the peers? + */ +#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 300) + +/** + * Time to wait for stuff that should be rather fast + */ +#define SHORT_TIME GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 60) + +/** + * Which strings have been found & connected. + */ +static int ok[MESH_REGEX_PEERS]; + +/** + * How many connects have happened. + */ +static int regex_peers; + +/** + * Total number of currently running peers. + */ +static unsigned long long peers_running; + +/** + * Task called to disconnect peers + */ +static GNUNET_SCHEDULER_TaskIdentifier disconnect_task; + +/** + * Task called to shutdown test. + */ +static GNUNET_SCHEDULER_TaskIdentifier shutdown_handle; + +/** + * Mesh handle for connecting peer. + */ +static struct GNUNET_MESH_Handle *h1; + +/** + * Mesh handle for announcing peers. + */ +static struct GNUNET_MESH_Handle *h2[MESH_REGEX_PEERS]; + +/** + * Tunnel handles for announcing peer. + */ +static struct GNUNET_MESH_Tunnel *t[MESH_REGEX_PEERS]; + +/** + * Incoming tunnels for announcing peers. + */ +static struct GNUNET_MESH_Tunnel *incoming_t[MESH_REGEX_PEERS]; + +/** + * Test context (to shut down). + */ +struct GNUNET_MESH_TEST_Context *test_ctx; + +/** + * Regular expressions for the announces. + */ +static char *regexes[MESH_REGEX_PEERS] = {"(0|1)" + "(0|1)" + "23456789ABC", + + "0123456789A*BC", + + "1234567890123456789012340*123456789ABC*", + + "GNUNETVPN0001000IPEX401110011101100100000111(0|1)*"}; + + +/** + * Service strings to look for. + */ +static char *strings[MESH_REGEX_PEERS] = {"1123456789ABC", + + "0123456789AABC", + + "12345678901234567890123400123456789ABCCCC", + + "GNUNETVPN0001000IPEX401110011101100100000111"}; + + + +/** + * Task to run for shutdown: stops peers, ends test. + * + * @param cls Closure (not used). + * @param tc TaskContext. + * + */ +static void +shutdown_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: Ending test.\n"); + shutdown_handle = GNUNET_SCHEDULER_NO_TASK; +} + + +/** + * Ends test: Disconnects peers and calls shutdown. + * @param cls Closure (not used). + * @param tc TaskContext. + */ +static void +disconnect_peers (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + unsigned int i; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: disconnecting peers\n"); + + for (i = 0; i < MESH_REGEX_PEERS; i++) + { + GNUNET_MESH_tunnel_destroy (t[i]); + } + if (GNUNET_SCHEDULER_NO_TASK != shutdown_handle) + { + GNUNET_SCHEDULER_cancel (shutdown_handle); + } + GNUNET_MESH_TEST_cleanup (test_ctx); + shutdown_handle = GNUNET_SCHEDULER_add_now (&shutdown_task, NULL); +} + +/** + * Function called whenever an inbound tunnel is destroyed. Should clean up + * any associated state. + * + * @param cls closure (set from GNUNET_MESH_connect) + * @param tunnel connection to the other end (henceforth invalid) + * @param tunnel_ctx place where local state associated + * with the tunnel is stored + */ +static void +tunnel_cleaner (void *cls, const struct GNUNET_MESH_Tunnel *tunnel, + void *tunnel_ctx) +{ + long i = (long) cls; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Incoming tunnel disconnected at peer %d\n", + i); + return; +} + + +/** + * Method called whenever a tunnel falls apart. + * + * @param cls closure + * @param peer peer identity the tunnel stopped working with + */ +static void +dh (void *cls, const struct GNUNET_PeerIdentity *peer) +{ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "peer %s disconnected\n", + GNUNET_i2s (peer)); + return; +} + +/** + * Function called to notify a client about the connection + * begin ready to queue more data. "buf" will be + * NULL and "size" zero if the connection was closed for + * writing in the meantime. + * + * @param cls closure + * @param size number of bytes available in buf + * @param buf where the callee should write the message + * @return number of bytes written to buf + */ +static size_t +data_ready (void *cls, size_t size, void *buf) +{ + struct GNUNET_MessageHeader *m = buf; + + if (NULL == buf || size < sizeof(struct GNUNET_MessageHeader)) + return 0; + m->type = htons (1); + m->size = htons (sizeof(struct GNUNET_MessageHeader)); + return sizeof(struct GNUNET_MessageHeader); +} + +/** + * Method called whenever a peer connects to a tunnel. + * + * @param cls closure + * @param peer peer identity the tunnel was created to, NULL on timeout + * @param atsi performance data for the connection + */ +static void +ch (void *cls, const struct GNUNET_PeerIdentity *peer, + const struct GNUNET_ATS_Information *atsi) +{ + long i = (long) cls; + + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + "Peer connected: %s\n", + GNUNET_i2s (peer)); + regex_peers++; + + GNUNET_MESH_notify_transmit_ready(t[i], GNUNET_NO, + GNUNET_TIME_UNIT_FOREVER_REL, + peer, + sizeof(struct GNUNET_MessageHeader), + &data_ready, NULL); +} + +/** + * Method called whenever another peer has added us to a tunnel + * the other peer initiated. + * + * @param cls closure + * @param tunnel new handle to the tunnel + * @param initiator peer that started the tunnel + * @param atsi performance information for the tunnel + * @return initial tunnel context for the tunnel + * (can be NULL -- that's not an error) + */ +static void * +incoming_tunnel (void *cls, struct GNUNET_MESH_Tunnel *tunnel, + const struct GNUNET_PeerIdentity *initiator, + const struct GNUNET_ATS_Information *atsi) +{ + long i = (long) cls; + + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + "Incoming tunnel from %s to peer %d\n", + GNUNET_i2s (initiator), i); + if ( (i >= 10L) && (i < 10L + MESH_REGEX_PEERS)) + { + incoming_t[i - 10L] = tunnel; + ok[i - 10L] = GNUNET_OK; + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + "Incoming tunnel for unknown client %lu\n", (long) cls); + } + if (GNUNET_SCHEDULER_NO_TASK != disconnect_task) + { + GNUNET_SCHEDULER_cancel (disconnect_task); + disconnect_task = + GNUNET_SCHEDULER_add_delayed (SHORT_TIME, &disconnect_peers, NULL); + } + return NULL; +} + +/** + * Function is called whenever a message is received. + * + * @param cls closure (set from GNUNET_MESH_connect) + * @param tunnel connection to the other end + * @param tunnel_ctx place to store local state associated with the tunnel + * @param sender who sent the message + * @param message the actual message + * @param atsi performance data for the connection + * @return GNUNET_OK to keep the connection open, + * GNUNET_SYSERR to close it (signal serious error) + */ +int +data_callback (void *cls, struct GNUNET_MESH_Tunnel *tunnel, void **tunnel_ctx, + const struct GNUNET_PeerIdentity *sender, + const struct GNUNET_MessageHeader *message, + const struct GNUNET_ATS_Information *atsi) +{ + unsigned int i; + long peer_number = (long) cls; + + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "got data on peer %ld!\n", peer_number); + for (i = 0; i < MESH_REGEX_PEERS; i++) + { + if (GNUNET_OK != ok[i]) { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "data from peer %u still missing!\n", i + 10); + return GNUNET_OK; + } + } + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + "test: EVERYONE GOT DATA, FINISHING!\n"); + if (GNUNET_SCHEDULER_NO_TASK != disconnect_task) + { + GNUNET_SCHEDULER_cancel (disconnect_task); + } + disconnect_task = + GNUNET_SCHEDULER_add_now (&disconnect_peers, NULL); + return GNUNET_OK; +} + +/** + * Handlers, for diverse services + */ +static struct GNUNET_MESH_MessageHandler handlers[] = { + {&data_callback, 1, sizeof (struct GNUNET_MessageHeader)}, + {NULL, 0, 0} +}; + + +/** + * test main: start test when all peers are connected + * + * @param cls Closure. + * @param ctx Argument to give to GNUNET_MESH_TEST_cleanup on test end. + * @param num_peers Number of peers that are running. + * @param peers Array of peers. + * @param meshes Handle to each of the MESHs of the peers. + */ +static void +tmain (void *cls, + struct GNUNET_MESH_TEST_Context *ctx, + unsigned int num_peers, + struct GNUNET_TESTBED_Peer **peers, + struct GNUNET_MESH_Handle **meshes) +{ + unsigned int i; + + shutdown_handle = GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, + &shutdown_task, NULL); + test_ctx = ctx; + if (16 != num_peers) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "running peers mismatch, aborting test!\n"); + GNUNET_MESH_TEST_cleanup (ctx); + return; + } + peers_running = num_peers; + disconnect_task = + GNUNET_SCHEDULER_add_delayed (TIMEOUT, &disconnect_peers, NULL); + +// h1 = GNUNET_MESH_connect (d->cfg, (void *) 1L, +// NULL, +// NULL, +// handlers, +// &app); + h1 = meshes[0]; + regex_peers = 0; + for (i = 0; i < MESH_REGEX_PEERS; i++) + { + ok[i] = GNUNET_NO; +// h2[i] = GNUNET_MESH_connect (d->cfg, (void *) (long) (i + 2), +// &incoming_tunnel, +// &tunnel_cleaner, +// handlers, +// &app); + h2[i] = meshes[10 + i]; + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + "Announce REGEX %u: %s\n", i, regexes[i]); + GNUNET_MESH_announce_regex (h2[i], regexes[i], 1); + } + + for (i = 0; i < MESH_REGEX_PEERS; i++) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Create tunnel\n"); + t[i] = GNUNET_MESH_tunnel_create (h1, NULL, &ch, &dh, (void *) (long) i); + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + "Connect by string %s\n", strings[i]); + GNUNET_MESH_peer_request_connect_by_string (t[i], strings[i]); + } + /* connect handler = success, timeout = error */ + +} + + +/** + * Main: start test + */ +int +main (int argc, char *argv[]) +{ + int result; + unsigned int i; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: Start\n"); + + GNUNET_MESH_TEST_run ("test_mesh_regex", + "test_mesh_2dtorus.conf", + 16, + &tmain, + NULL, + &incoming_tunnel, + &tunnel_cleaner, + handlers, + NULL); + + result = GNUNET_OK; + for (i = 0; i < MESH_REGEX_PEERS; i++) + { + if (GNUNET_OK != ok[i]) + { + result = GNUNET_SYSERR; + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "COULD NOT CONNECT TO %u: %s!\n", + i, strings[i]); + } + } + if (GNUNET_OK != result || regex_peers != MESH_REGEX_PEERS) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "FAILED! %u connected peers\n", + regex_peers); + return 1; + } + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "success :)\n"); + return 0; +} + +/* end of test_mesh_regex.c */ diff --git a/src/mesh/test_mesh_small.c b/src/mesh/test_mesh_small.c index 974b635..efe9398 100644 --- a/src/mesh/test_mesh_small.c +++ b/src/mesh/test_mesh_small.c @@ -24,35 +24,25 @@ */ #include #include "platform.h" -#include "gnunet_testing_lib.h" +#include "mesh_test_lib.h" #include "gnunet_mesh_service.h" #include -#define VERBOSE GNUNET_YES -#define REMOVE_DIR GNUNET_YES - -struct MeshPeer -{ - struct MeshPeer *prev; - - struct MeshPeer *next; - - struct GNUNET_TESTING_Daemon *daemon; - - struct GNUNET_MESH_Handle *mesh_handle; -}; - +/** + * How namy messages to send + */ +#define TOTAL_PACKETS 1000 /** * How long until we give up on connecting the peers? */ -#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 1500) +#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 120) /** * Time to wait for stuff that should be rather fast */ -#define SHORT_TIME GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 300) +#define SHORT_TIME GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 20) /** * DIFFERENT TESTS TO RUN @@ -62,71 +52,102 @@ struct MeshPeer #define MULTICAST 2 #define SPEED 3 #define SPEED_ACK 4 +#define SPEED_MIN 5 +#define SPEED_NOBUF 6 +#define P2P_SIGNAL 10 /** * Which test are we running? */ static int test; +/** + * String with test name + */ +char *test_name; + +/** + * Flag to send traffic leaf->root in speed tests to test BCK_ACK logic. + */ +static int test_backwards = GNUNET_NO; + /** * How many events have happened */ static int ok; -static int peers_in_tunnel; + /** + * Each peer is supposed to generate the following callbacks: + * 1 incoming tunnel (@dest) + * 1 connected peer (@orig) + * 1 received data packet (@dest) + * 1 received data packet (@orig) + * 1 received tunnel destroy (@dest) + * _________________________________ + * 5 x ok expected per peer + */ +int ok_goal; -static int peers_responded; -static int data_sent; +/** + * Size of each test packet + */ +size_t size_payload = sizeof (struct GNUNET_MessageHeader) + sizeof (uint32_t); -static int data_received; +/** + * Operation to get peer ids. + */ +struct GNUNET_TESTBED_Operation *t_op[3]; -static int data_ack; +/** + * Peer ids. + */ +struct GNUNET_PeerIdentity *p_id[3]; /** - * Be verbose + * Peer ids counter. */ -static int verbose; +unsigned int p_ids; /** - * Total number of peers in the test. + * Is the setup initialized? */ -static unsigned long long num_peers; +static int initialized; /** - * Global configuration file + * Peers that have been connected */ -static struct GNUNET_CONFIGURATION_Handle *testing_cfg; +static int peers_in_tunnel; /** - * Total number of currently running peers. + * Peers that have responded */ -static unsigned long long peers_running; +static int peers_responded; /** - * Total number of connections in the whole network. + * Number of payload packes sent */ -static unsigned int total_connections; +static int data_sent; /** - * The currently running peer group. + * Number of payload packets received */ -static struct GNUNET_TESTING_PeerGroup *pg; +static int data_received; /** - * File to report results to. + * Number of payload packed explicitly (app level) acknowledged */ -static struct GNUNET_DISK_FileHandle *output_file; +static int data_ack; /** - * File to log connection info, statistics to. + * Total number of currently running peers. */ -static struct GNUNET_DISK_FileHandle *data_file; +static unsigned long long peers_running; /** - * How many data points to capture before triggering next round? + * Test context (to shut down). */ -static struct GNUNET_TIME_Relative wait_time; +struct GNUNET_MESH_TEST_Context *test_ctx; /** * Task called to disconnect peers. @@ -143,151 +164,189 @@ static GNUNET_SCHEDULER_TaskIdentifier test_task; */ static GNUNET_SCHEDULER_TaskIdentifier shutdown_handle; -static char *topology_file; - -static struct GNUNET_TESTING_Daemon *d1; - -static GNUNET_PEER_Id pid1; - -static struct GNUNET_TESTING_Daemon *d2; - -static struct GNUNET_TESTING_Daemon *d3; - +/** + * Mesh handle for the root peer + */ static struct GNUNET_MESH_Handle *h1; +/** + * Mesh handle for the first leaf peer + */ static struct GNUNET_MESH_Handle *h2; +/** + * Mesh handle for the second leaf peer + */ static struct GNUNET_MESH_Handle *h3; +/** + * Tunnel handle for the root peer + */ static struct GNUNET_MESH_Tunnel *t; +/** + * Tunnel handle for the first leaf peer + */ static struct GNUNET_MESH_Tunnel *incoming_t; +/** + * Tunnel handle for the second leaf peer + */ static struct GNUNET_MESH_Tunnel *incoming_t2; +/** + * Time we started the data transmission (after tunnel has been established + * and initilized). + */ static struct GNUNET_TIME_Absolute start_time; -static struct GNUNET_TIME_Absolute end_time; - -static struct GNUNET_TIME_Relative total_time; - /** - * Check whether peers successfully shut down. + * Show the results of the test (banwidth acheived) and log them to GAUGER */ static void -shutdown_callback (void *cls, const char *emsg) +show_end_data (void) { - if (emsg != NULL) - { -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Shutdown of peers failed!\n"); -#endif - ok--; - } - else - { -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "All peers successfully shut down!\n"); -#endif - } - GNUNET_CONFIGURATION_destroy (testing_cfg); + static struct GNUNET_TIME_Absolute end_time; + static struct GNUNET_TIME_Relative total_time; + + end_time = GNUNET_TIME_absolute_get(); + total_time = GNUNET_TIME_absolute_get_difference(start_time, end_time); + FPRINTF (stderr, "\nResults of test \"%s\"\n", test_name); + FPRINTF (stderr, "Test time %llu ms\n", + (unsigned long long) total_time.rel_value); + FPRINTF (stderr, "Test bandwidth: %f kb/s\n", + 4 * TOTAL_PACKETS * 1.0 / total_time.rel_value); // 4bytes * ms + FPRINTF (stderr, "Test throughput: %f packets/s\n\n", + TOTAL_PACKETS * 1000.0 / total_time.rel_value); // packets * ms + GAUGER ("MESH", test_name, + TOTAL_PACKETS * 1000.0 / total_time.rel_value, + "packets/s"); } /** * Shut down peergroup, clean up. + * + * @param cls Closure (unused). + * @param tc Task Context. */ static void shutdown_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Ending test.\n"); -#endif - - if (disconnect_task != GNUNET_SCHEDULER_NO_TASK) - { - GNUNET_SCHEDULER_cancel (disconnect_task); - disconnect_task = GNUNET_SCHEDULER_NO_TASK; - } - - if (NULL != h1) - { - GNUNET_MESH_disconnect (h1); - h1 = NULL; - } - if (NULL != h2) - { - GNUNET_MESH_disconnect (h2); - h2 = NULL; - } - if (test == MULTICAST && NULL != h3) - { - GNUNET_MESH_disconnect (h3); - h3 = NULL; - } - - if (data_file != NULL) - GNUNET_DISK_file_close (data_file); - GNUNET_TESTING_daemons_stop (pg, TIMEOUT, &shutdown_callback, NULL); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Ending test.\n"); + shutdown_handle = GNUNET_SCHEDULER_NO_TASK; } /** * Disconnect from mesh services af all peers, call shutdown. + * + * @param cls Closure (unused). + * @param tc Task Context. */ static void disconnect_mesh_peers (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { + long line = (long) cls; + unsigned int i; + + for (i = 0; i < 3; i++) + if (NULL != t_op[i]) + { + GNUNET_TESTBED_operation_done (t_op[i]); + t_op[i] = NULL; + } GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "disconnecting mesh service of peers\n"); + "disconnecting mesh service of peers, called from line %ld\n", + line); disconnect_task = GNUNET_SCHEDULER_NO_TASK; if (NULL != t) { - GNUNET_MESH_tunnel_destroy(t); + GNUNET_MESH_tunnel_destroy (t); t = NULL; } if (NULL != incoming_t) { - GNUNET_MESH_tunnel_destroy(incoming_t); + GNUNET_MESH_tunnel_destroy (incoming_t); incoming_t = NULL; } if (NULL != incoming_t2) { - GNUNET_MESH_tunnel_destroy(incoming_t2); + GNUNET_MESH_tunnel_destroy (incoming_t2); incoming_t2 = NULL; } - GNUNET_MESH_disconnect (h1); - GNUNET_MESH_disconnect (h2); - h1 = h2 = NULL; - if (test == MULTICAST) - { - GNUNET_MESH_disconnect (h3); - h3 = NULL; - } + GNUNET_MESH_TEST_cleanup (test_ctx); if (GNUNET_SCHEDULER_NO_TASK != shutdown_handle) { GNUNET_SCHEDULER_cancel (shutdown_handle); - shutdown_handle = GNUNET_SCHEDULER_add_now (&shutdown_task, NULL); } + shutdown_handle = GNUNET_SCHEDULER_add_now (&shutdown_task, NULL); } -size_t + +/** + * Abort test: schedule disconnect and shutdown immediately + * + * @param line Line in the code the abort is requested from (__LINE__). + */ +void +abort_test (long line) +{ + if (disconnect_task != GNUNET_SCHEDULER_NO_TASK) + { + GNUNET_SCHEDULER_cancel (disconnect_task); + } + disconnect_task = GNUNET_SCHEDULER_add_delayed (SHORT_TIME, + &disconnect_mesh_peers, + (void *) line); +} + +/** + * Transmit ready callback. + * + * @param cls Closure (message type). + * @param size Size of the tranmist buffer. + * @param buf Pointer to the beginning of the buffer. + * + * @return Number of bytes written to buf. + */ +static size_t tmt_rdy (void *cls, size_t size, void *buf); + +/** + * Task to schedule a new data transmission. + * + * @param cls Closure (peer #). + * @param tc Task Context. + */ static void data_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { struct GNUNET_MESH_TransmitHandle *th; + struct GNUNET_MESH_Tunnel *tunnel; + struct GNUNET_PeerIdentity *destination; + if ((GNUNET_SCHEDULER_REASON_SHUTDOWN & tc->reason) != 0) return; - th = GNUNET_MESH_notify_transmit_ready (t, GNUNET_NO, 0, - GNUNET_TIME_UNIT_FOREVER_REL, &d2->id, - sizeof (struct GNUNET_MessageHeader), - &tmt_rdy, (void *) 1L); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Data task\n"); + if (GNUNET_YES == test_backwards) + { + tunnel = incoming_t; + destination = p_id[0]; + } + else + { + tunnel = t; + destination = p_id[2]; + } + th = GNUNET_MESH_notify_transmit_ready (tunnel, GNUNET_NO, + GNUNET_TIME_UNIT_FOREVER_REL, + destination, + size_payload, + &tmt_rdy, (void *) 1L); if (NULL == th) { unsigned long i = (unsigned long) cls; @@ -311,10 +370,11 @@ data_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) } } + /** * Transmit ready callback * - * @param cls Closure. + * @param cls Closure (message type). * @param size Size of the buffer we have. * @param buf Buffer to copy data to. */ @@ -322,24 +382,38 @@ size_t tmt_rdy (void *cls, size_t size, void *buf) { struct GNUNET_MessageHeader *msg = buf; + uint32_t *data; GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " tmt_rdy called\n"); - if (size < sizeof (struct GNUNET_MessageHeader) || NULL == buf) + if (size < size_payload || NULL == buf) + { + GNUNET_break (0); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "size %u, buf %p, data_sent %u, data_received %u\n", + size, + buf, + data_sent, + data_received); return 0; - msg->size = htons (sizeof (struct GNUNET_MessageHeader)); + } + msg->size = htons (size); msg->type = htons ((long) cls); - if (test == SPEED) + data = (uint32_t *) &msg[1]; + *data = htonl (data_sent); + if (SPEED == test && GNUNET_YES == initialized) { data_sent++; - if (data_sent < 1000) + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + " Sent packet %d\n", data_sent); + if (data_sent < TOTAL_PACKETS) { GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - " Scheduling %d packet\n", data_sent); + " Scheduling packet %d\n", data_sent + 1); GNUNET_SCHEDULER_add_now(&data_task, NULL); } } - return sizeof (struct GNUNET_MessageHeader); + return size_payload; } @@ -362,82 +436,121 @@ data_callback (void *cls, struct GNUNET_MESH_Tunnel *tunnel, void **tunnel_ctx, const struct GNUNET_ATS_Information *atsi) { long client = (long) cls; + long expected_target_client; + uint32_t *data; - switch (client) + ok++; + + if ((ok % 20) == 0) { - case 1L: - GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Origin client got a response!\n"); - ok++; - GNUNET_log (GNUNET_ERROR_TYPE_INFO, " ok: %d\n", ok); - peers_responded++; - data_ack++; if (GNUNET_SCHEDULER_NO_TASK != disconnect_task) { GNUNET_SCHEDULER_cancel (disconnect_task); - disconnect_task = - GNUNET_SCHEDULER_add_delayed (SHORT_TIME, &disconnect_mesh_peers, - NULL); } + disconnect_task = + GNUNET_SCHEDULER_add_delayed (SHORT_TIME, &disconnect_mesh_peers, + (void *) __LINE__); + } + + switch (client) + { + case 0L: + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Root client got a message!\n"); + peers_responded++; if (test == MULTICAST && peers_responded < 2) return GNUNET_OK; - if (test == SPEED_ACK) - { - GNUNET_log (GNUNET_ERROR_TYPE_INFO, - " received ack %u\n", data_ack); - GNUNET_MESH_notify_transmit_ready (tunnel, GNUNET_NO, 0, - GNUNET_TIME_UNIT_FOREVER_REL, sender, - sizeof (struct GNUNET_MessageHeader), - &tmt_rdy, (void *) 1L); - if (data_ack < 1000) - return GNUNET_OK; - end_time = GNUNET_TIME_absolute_get(); - total_time = GNUNET_TIME_absolute_get_difference(start_time, end_time); - FPRINTF (stderr, "\nTest time %llu ms\n", - (unsigned long long) total_time.rel_value); - FPRINTF (stderr, "Test bandwidth: %f kb/s\n", - 4000.0 / total_time.rel_value); - FPRINTF (stderr, "Test throughput: %f packets/s\n", - 1000000.0 / total_time.rel_value); - GAUGER ("MESH", "Tunnel 5 peers", 1000000.0 / total_time.rel_value, - "packets/s"); - } - GNUNET_assert (tunnel == t); - GNUNET_MESH_tunnel_destroy (t); - t = NULL; break; - case 2L: case 3L: + case 4L: GNUNET_log (GNUNET_ERROR_TYPE_INFO, - "Destination client %u got a message.\n", + "Leaf client %li got a message.\n", client); - ok++; - GNUNET_log (GNUNET_ERROR_TYPE_INFO, " ok: %d\n", ok); - if (SPEED != test) + client = 4L; + break; + default: + GNUNET_assert (0); + break; + } + GNUNET_log (GNUNET_ERROR_TYPE_INFO, " ok: (%d/%d)\n", ok, ok_goal); + data = (uint32_t *) &message[1]; + GNUNET_log (GNUNET_ERROR_TYPE_INFO, " payload: (%u)\n", ntohl (*data)); + if (SPEED == test && GNUNET_YES == test_backwards) + { + expected_target_client = 0L; + } + else + { + expected_target_client = 4L; + } + + if (GNUNET_NO == initialized) + { + initialized = GNUNET_YES; + start_time = GNUNET_TIME_absolute_get (); + if (SPEED == test) { - GNUNET_MESH_notify_transmit_ready (tunnel, GNUNET_NO, 0, + GNUNET_assert (4L == client); + GNUNET_SCHEDULER_add_now (&data_task, NULL); + return GNUNET_OK; + } + } + + if (client == expected_target_client) // Normally 3 or 4 + { + data_received++; + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + " received data %u\n", data_received); + if (SPEED != test || (ok_goal - 2) == ok) + { + GNUNET_MESH_notify_transmit_ready (tunnel, GNUNET_NO, GNUNET_TIME_UNIT_FOREVER_REL, sender, - sizeof (struct GNUNET_MessageHeader), + size_payload, &tmt_rdy, (void *) 1L); + return GNUNET_OK; } else { - data_received++; + if (data_received < TOTAL_PACKETS) + return GNUNET_OK; + } + } + else // Normally 0 + { + if (test == SPEED_ACK || test == SPEED) + { + data_ack++; GNUNET_log (GNUNET_ERROR_TYPE_INFO, - " received data %u\n", data_received); - if (data_received < 1000) + " received ack %u\n", data_ack); + GNUNET_MESH_notify_transmit_ready (tunnel, GNUNET_NO, + GNUNET_TIME_UNIT_FOREVER_REL, sender, + size_payload, + &tmt_rdy, (void *) 1L); + if (data_ack < TOTAL_PACKETS && SPEED != test) return GNUNET_OK; + if (ok == 2 && SPEED == test) + return GNUNET_OK; + show_end_data(); } - if (GNUNET_SCHEDULER_NO_TASK != disconnect_task) + if (test == P2P_SIGNAL) { - GNUNET_SCHEDULER_cancel (disconnect_task); - disconnect_task = - GNUNET_SCHEDULER_add_delayed (SHORT_TIME, &disconnect_mesh_peers, - NULL); + GNUNET_MESH_tunnel_destroy (incoming_t); + incoming_t = NULL; } - break; - default: - break; + else + { + GNUNET_MESH_tunnel_destroy (t); + t = NULL; + } + } + + if (GNUNET_SCHEDULER_NO_TASK != disconnect_task) + { + GNUNET_SCHEDULER_cancel (disconnect_task); } + disconnect_task = + GNUNET_SCHEDULER_add_delayed (SHORT_TIME, &disconnect_mesh_peers, + (void *) __LINE__); + return GNUNET_OK; } @@ -472,7 +585,7 @@ incoming_tunnel (void *cls, struct GNUNET_MESH_Tunnel *tunnel, GNUNET_i2s (initiator), (long) cls); ok++; GNUNET_log (GNUNET_ERROR_TYPE_INFO, " ok: %d\n", ok); - if ((long) cls == 2L) + if ((long) cls == 4L) incoming_t = tunnel; else if ((long) cls == 3L) incoming_t2 = tunnel; @@ -480,13 +593,16 @@ incoming_tunnel (void *cls, struct GNUNET_MESH_Tunnel *tunnel, { GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Incoming tunnel for unknown client %lu\n", (long) cls); + GNUNET_break(0); } if (GNUNET_SCHEDULER_NO_TASK != disconnect_task) { GNUNET_SCHEDULER_cancel (disconnect_task); - disconnect_task = - GNUNET_SCHEDULER_add_delayed (SHORT_TIME, &disconnect_mesh_peers, NULL); } + disconnect_task = + GNUNET_SCHEDULER_add_delayed (SHORT_TIME, &disconnect_mesh_peers, + (void *) __LINE__); + return NULL; } @@ -508,7 +624,7 @@ tunnel_cleaner (void *cls, const struct GNUNET_MESH_Tunnel *tunnel, GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Incoming tunnel disconnected at peer %d\n", i); - if (2L == i) + if (4L == i) { ok++; incoming_t = NULL; @@ -529,8 +645,9 @@ tunnel_cleaner (void *cls, const struct GNUNET_MESH_Tunnel *tunnel, if (GNUNET_SCHEDULER_NO_TASK != disconnect_task) { GNUNET_SCHEDULER_cancel (disconnect_task); - disconnect_task = GNUNET_SCHEDULER_add_now (&disconnect_mesh_peers, NULL); } + disconnect_task = GNUNET_SCHEDULER_add_now (&disconnect_mesh_peers, + (void *) __LINE__); return; } @@ -548,6 +665,16 @@ dh (void *cls, const struct GNUNET_PeerIdentity *peer) GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "peer %s disconnected\n", GNUNET_i2s (peer)); + if (P2P_SIGNAL == test) + { + ok ++; + if (GNUNET_SCHEDULER_NO_TASK != disconnect_task) + { + GNUNET_SCHEDULER_cancel (disconnect_task); + } + disconnect_task = GNUNET_SCHEDULER_add_now (&disconnect_mesh_peers, + (void *) __LINE__); + } return; } @@ -563,52 +690,59 @@ static void ch (void *cls, const struct GNUNET_PeerIdentity *peer, const struct GNUNET_ATS_Information *atsi) { + long i = (long) cls; + struct GNUNET_PeerIdentity *dest; GNUNET_log (GNUNET_ERROR_TYPE_INFO, - "peer %s connected\n", GNUNET_i2s (peer)); + "%ld peer %s connected\n", i, GNUNET_i2s (peer)); - if (0 == memcmp (&d2->id, peer, sizeof (d2->id)) && (long) cls == 1L) + if (0 == memcmp (p_id[2], peer, sizeof (struct GNUNET_PeerIdentity)) && + i == 0L) { ok++; } - if (test == MULTICAST && 0 == memcmp (&d3->id, peer, sizeof (d3->id)) && - (long) cls == 1L) + if (test == MULTICAST && + 0 == memcmp (p_id[1], peer, sizeof (struct GNUNET_PeerIdentity)) && + i == 0L) { ok++; } GNUNET_log (GNUNET_ERROR_TYPE_INFO, " ok: %d\n", ok); switch (test) { - case UNICAST: - case SPEED: - case SPEED_ACK: - dest = &d2->id; - break; - case MULTICAST: - peers_in_tunnel++; - if (peers_in_tunnel < 2) + case UNICAST: + case P2P_SIGNAL: + case SPEED: + case SPEED_ACK: + // incoming_t is NULL unless we send a relevant data packet + dest = p_id[2]; + break; + case MULTICAST: + peers_in_tunnel++; + if (peers_in_tunnel < 2) + return; + dest = NULL; + break; + default: + GNUNET_assert (0); return; - dest = NULL; - break; - default: - return; } if (GNUNET_SCHEDULER_NO_TASK != disconnect_task) { GNUNET_SCHEDULER_cancel (disconnect_task); disconnect_task = - GNUNET_SCHEDULER_add_delayed (SHORT_TIME, &disconnect_mesh_peers, NULL); + GNUNET_SCHEDULER_add_delayed (SHORT_TIME, &disconnect_mesh_peers, + (void *) __LINE__); GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Sending data...\n"); + "Sending data initializer...\n"); peers_responded = 0; data_ack = 0; data_received = 0; data_sent = 0; - start_time = GNUNET_TIME_absolute_get(); - GNUNET_MESH_notify_transmit_ready (t, GNUNET_NO, 0, + GNUNET_MESH_notify_transmit_ready (t, GNUNET_NO, GNUNET_TIME_UNIT_FOREVER_REL, dest, - sizeof (struct GNUNET_MessageHeader), + size_payload, &tmt_rdy, (void *) 1L); } else @@ -622,376 +756,210 @@ ch (void *cls, const struct GNUNET_PeerIdentity *peer, } +/** + * START THE TESTCASE ITSELF, AS WE ARE CONNECTED TO THE MESH SERVICES. + * + * Testcase continues when the root receives confirmation of connected peers, + * on callback funtion ch. + * + * @param cls Closure (unsued). + * @param tc Task Context. + */ static void do_test (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test_task\n"); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "add peer 2\n"); + GNUNET_MESH_peer_request_connect_add (t, p_id[2]); + if (test == MULTICAST) { GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "add peer 3\n"); - GNUNET_MESH_peer_request_connect_add (t, &d3->id); + GNUNET_MESH_peer_request_connect_add (t, p_id[1]); } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "add peer 2\n"); - GNUNET_MESH_peer_request_connect_add (t, &d2->id); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "schedule timeout in 90s\n"); + "schedule timeout in TIMEOUT\n"); if (GNUNET_SCHEDULER_NO_TASK != disconnect_task) { GNUNET_SCHEDULER_cancel (disconnect_task); - disconnect_task = - GNUNET_SCHEDULER_add_delayed (SHORT_TIME, &disconnect_mesh_peers, NULL); } + disconnect_task = GNUNET_SCHEDULER_add_delayed (TIMEOUT, + &disconnect_mesh_peers, + (void *) __LINE__); } - /** - * connect_mesh_service: connect to the mesh service of one of the peers + * Callback to be called when the requested peer information is available * - */ -static void -connect_mesh_service (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) + * @param cls the closure from GNUNET_TETSBED_peer_get_information() + * @param op the operation this callback corresponds to + * @param pinfo the result; will be NULL if the operation has failed + * @param emsg error message if the operation has failed; + * NULL if the operation is successfull + */ +void +pi_cb (void *cls, + struct GNUNET_TESTBED_Operation *op, + const struct GNUNET_TESTBED_PeerInformation *pinfo, + const char *emsg) { - GNUNET_MESH_ApplicationType app; - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "connect_mesh_service\n"); - - d2 = GNUNET_TESTING_daemon_get (pg, 4); - if (test == MULTICAST) - { - d3 = GNUNET_TESTING_daemon_get (pg, 3); - } - app = (GNUNET_MESH_ApplicationType) 0; - -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "connecting to mesh service of peer %s\n", - GNUNET_i2s (&d1->id)); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "connecting to mesh service of peer %s\n", - GNUNET_i2s (&d2->id)); - if (test == MULTICAST) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "connecting to mesh service of peer %s\n", - GNUNET_i2s (&d3->id)); - } -#endif - h1 = GNUNET_MESH_connect (d1->cfg, 5, (void *) 1L, NULL, &tunnel_cleaner, - handlers, &app); - h2 = GNUNET_MESH_connect (d2->cfg, 5, (void *) 2L, &incoming_tunnel, - &tunnel_cleaner, handlers, &app); - if (test == MULTICAST) - { - h3 = GNUNET_MESH_connect (d3->cfg, 5, (void *) 3L, &incoming_tunnel, - &tunnel_cleaner, handlers, &app); - } - t = GNUNET_MESH_tunnel_create (h1, NULL, &ch, &dh, (void *) 1L); - peers_in_tunnel = 0; - test_task = - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply - (GNUNET_TIME_UNIT_SECONDS, 1), &do_test, - NULL); -} - - - -/** - * peergroup_ready: start test when all peers are connected - * @param cls closure - * @param emsg error message - */ -static void -peergroup_ready (void *cls, const char *emsg) -{ - char *buf; - int buf_len; - unsigned int i; + long i = (long) cls; - if (emsg != NULL) + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "id callback for %ld\n", i); + if (NULL == pinfo || NULL != emsg) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Peergroup callback called with error, aborting test!\n"); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Error from testing: `%s'\n", emsg); - ok--; - GNUNET_TESTING_daemons_stop (pg, TIMEOUT, &shutdown_callback, NULL); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "pi_cb: %s\n", emsg); + abort_test (__LINE__); return; } -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "************************************************************\n"); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Peer Group started successfully!\n"); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Have %u connections\n", - total_connections); -#endif - - if (data_file != NULL) - { - buf = NULL; - buf_len = GNUNET_asprintf (&buf, "CONNECTIONS_0: %u\n", total_connections); - if (buf_len > 0) - GNUNET_DISK_file_write (data_file, buf, buf_len); - GNUNET_free (buf); - } - peers_running = GNUNET_TESTING_daemons_running (pg); - for (i = 0; i < num_peers; i++) - { - GNUNET_PEER_Id peer_id; - - d1 = GNUNET_TESTING_daemon_get (pg, i); - peer_id = GNUNET_PEER_intern (&d1->id); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " %u: %s\n", - peer_id, GNUNET_i2s (&d1->id)); - } - d1 = GNUNET_TESTING_daemon_get (pg, 0); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Peer looking: %s\n", - GNUNET_i2s (&d1->id)); - pid1 = GNUNET_PEER_intern (&d1->id); - - GNUNET_SCHEDULER_add_now (&connect_mesh_service, NULL); - disconnect_task = - GNUNET_SCHEDULER_add_delayed (wait_time, &disconnect_mesh_peers, NULL); - + p_id[i] = pinfo->result.id; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " id: %s\n", GNUNET_i2s (p_id[i])); + p_ids++; + if ((MULTICAST == test && p_ids < 3) || p_ids < 2) + return; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Got all IDs, starting test\n"); + test_task = GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_SECONDS, + &do_test, NULL); } - /** - * Function that will be called whenever two daemons are connected by - * the testing library. + * test main: start test when all peers are connected * - * @param cls closure - * @param first peer id for first daemon - * @param second peer id for the second daemon - * @param distance distance between the connected peers - * @param first_cfg config for the first daemon - * @param second_cfg config for the second daemon - * @param first_daemon handle for the first daemon - * @param second_daemon handle for the second daemon - * @param emsg error message (NULL on success) - */ -static void -connect_cb (void *cls, const struct GNUNET_PeerIdentity *first, - const struct GNUNET_PeerIdentity *second, uint32_t distance, - const struct GNUNET_CONFIGURATION_Handle *first_cfg, - const struct GNUNET_CONFIGURATION_Handle *second_cfg, - struct GNUNET_TESTING_Daemon *first_daemon, - struct GNUNET_TESTING_Daemon *second_daemon, const char *emsg) -{ - if (emsg == NULL) - { - total_connections++; - } - else - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Problem with new connection (%s)\n", - emsg); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " (%s)\n", GNUNET_i2s (first)); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " (%s)\n", GNUNET_i2s (second)); - } - -} - - -/** - * run: load configuration options and schedule test to run (start peergroup) - * @param cls closure - * @param args argv - * @param cfgfile configuration file name (can be NULL) - * @param cfg configuration handle + * @param cls Closure. + * @param ctx Argument to give to GNUNET_MESH_TEST_cleanup on test end. + * @param num_peers Number of peers that are running. + * @param peers Array of peers. + * @param meshes Handle to each of the MESHs of the peers. */ static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) +tmain (void *cls, + struct GNUNET_MESH_TEST_Context *ctx, + unsigned int num_peers, + struct GNUNET_TESTBED_Peer **peers, + struct GNUNET_MESH_Handle **meshes) { - char *temp_str; - struct GNUNET_TESTING_Host *hosts; - char *data_filename; - + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test main\n"); ok = 0; - testing_cfg = GNUNET_CONFIGURATION_dup (cfg); - - GNUNET_log_setup ("test_mesh_small", -#if VERBOSE - "DEBUG", -#else - "WARNING", -#endif - NULL); - -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Starting daemons.\n"); - GNUNET_CONFIGURATION_set_value_string (testing_cfg, "testing", - "use_progressbars", "YES"); -#endif - - if (GNUNET_OK != - GNUNET_CONFIGURATION_get_value_number (testing_cfg, "testing", - "num_peers", &num_peers)) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "Option TESTING:NUM_PEERS is required!\n"); - return; + test_ctx = ctx; + peers_running = num_peers; + h1 = meshes[0]; + h2 = meshes[num_peers - 1]; + t = GNUNET_MESH_tunnel_create (h1, NULL, &ch, &dh, (void *) 0L); + if (SPEED_MIN == test) + { + GNUNET_MESH_tunnel_speed_min(t); + test = SPEED; } - - if (GNUNET_OK != - GNUNET_CONFIGURATION_get_value_time (testing_cfg, "test_mesh_small", - "WAIT_TIME", &wait_time)) + if (SPEED_NOBUF == test) { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "Option test_mesh_small:wait_time is required!\n"); - return; - } - - if (GNUNET_OK != - GNUNET_CONFIGURATION_get_value_string (testing_cfg, "testing", - "topology_output_file", - &topology_file)) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "Option test_mesh_small:topology_output_file is required!\n"); - return; + GNUNET_MESH_tunnel_buffer(t, GNUNET_NO); + test = SPEED; } - - if (GNUNET_OK == - GNUNET_CONFIGURATION_get_value_string (testing_cfg, "test_mesh_small", - "data_output_file", - &data_filename)) - { - data_file = - GNUNET_DISK_file_open (data_filename, - GNUNET_DISK_OPEN_READWRITE | - GNUNET_DISK_OPEN_CREATE, - GNUNET_DISK_PERM_USER_READ | - GNUNET_DISK_PERM_USER_WRITE); - if (data_file == NULL) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Failed to open %s for output!\n", - data_filename); - GNUNET_free (data_filename); - } + peers_in_tunnel = 0; + disconnect_task = GNUNET_SCHEDULER_add_delayed (SHORT_TIME, + &disconnect_mesh_peers, + (void *) __LINE__); + shutdown_handle = GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, + &shutdown_task, NULL); + t_op[0] = GNUNET_TESTBED_peer_get_information (peers[0], + GNUNET_TESTBED_PIT_IDENTITY, + &pi_cb, (void *) 0L); + t_op[2] = GNUNET_TESTBED_peer_get_information (peers[num_peers - 1], + GNUNET_TESTBED_PIT_IDENTITY, + &pi_cb, (void *) 2L); + if (MULTICAST == test) + { + h3 = meshes[num_peers - 2]; + t_op[1] = GNUNET_TESTBED_peer_get_information (peers[num_peers - 2], + GNUNET_TESTBED_PIT_IDENTITY, + &pi_cb, (void *) 1L); } - - if (GNUNET_YES == - GNUNET_CONFIGURATION_get_value_string (cfg, "test_mesh_small", - "output_file", &temp_str)) + else { - output_file = - GNUNET_DISK_file_open (temp_str, - GNUNET_DISK_OPEN_READWRITE | - GNUNET_DISK_OPEN_CREATE, - GNUNET_DISK_PERM_USER_READ | - GNUNET_DISK_PERM_USER_WRITE); - if (output_file == NULL) - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Failed to open %s for output!\n", - temp_str); + t_op[1] = NULL; } - GNUNET_free_non_null (temp_str); - - hosts = GNUNET_TESTING_hosts_load (testing_cfg); - - pg = GNUNET_TESTING_peergroup_start (testing_cfg, num_peers, TIMEOUT, - &connect_cb, &peergroup_ready, NULL, - hosts); - GNUNET_assert (pg != NULL); - shutdown_handle = - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, - &shutdown_task, NULL); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "requested peer ids\n"); } - -/** - * test_mesh_small command line options - */ -static struct GNUNET_GETOPT_CommandLineOption options[] = { - {'V', "verbose", NULL, - gettext_noop ("be verbose (print progress information)"), - 0, &GNUNET_GETOPT_set_one, &verbose}, - GNUNET_GETOPT_OPTION_END -}; - - /** * Main: start test */ int main (int argc, char *argv[]) { - char * argv2[] = { - argv[0], - "-c", - "test_mesh_small.conf", -#if VERBOSE - "-L", - "DEBUG", -#endif - NULL - }; - int argc2 = (sizeof (argv2) / sizeof (char *)) - 1; - - /* Each peer is supposed to generate the following callbacks: - * 1 incoming tunnel (@dest) - * 1 connected peer (@orig) - * 1 received data packet (@dest) - * 1 received data packet (@orig) - * 1 received tunnel destroy (@dest) - * _________________________________ - * 5 x ok expected per peer - */ - int ok_goal; + initialized = GNUNET_NO; + GNUNET_log_setup ("test", "DEBUG", NULL); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Start\n"); if (strstr (argv[0], "test_mesh_small_unicast") != NULL) { GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "UNICAST\n"); test = UNICAST; + test_name = "unicast"; ok_goal = 5; } else if (strstr (argv[0], "test_mesh_small_multicast") != NULL) { GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "MULTICAST\n"); test = MULTICAST; + test_name = "multicast"; ok_goal = 10; } + else if (strstr (argv[0], "test_mesh_small_signal") != NULL) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "SIGNAL\n"); + test = P2P_SIGNAL; + test_name = "signal"; + ok_goal = 5; + } else if (strstr (argv[0], "test_mesh_small_speed_ack") != NULL) { /* Each peer is supposed to generate the following callbacks: * 1 incoming tunnel (@dest) * 1 connected peer (@orig) - * 1000 received data packet (@dest) - * 1000 received data packet (@orig) + * TOTAL_PACKETS received data packet (@dest) + * TOTAL_PACKETS received data packet (@orig) * 1 received tunnel destroy (@dest) * _________________________________ * 5 x ok expected per peer */ GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "SPEED_ACK\n"); test = SPEED_ACK; - ok_goal = 2003; - argv2 [3] = NULL; // remove -L DEBUG -#if VERBOSE - argc2 -= 2; -#endif + test_name = "speed ack"; + ok_goal = TOTAL_PACKETS * 2 + 3; } else if (strstr (argv[0], "test_mesh_small_speed") != NULL) { /* Each peer is supposed to generate the following callbacks: * 1 incoming tunnel (@dest) * 1 connected peer (@orig) - * 1000 received data packet (@dest) + * 1 initial packet (@dest) + * TOTAL_PACKETS received data packet (@dest) + * 1 received data packet (@orig) * 1 received tunnel destroy (@dest) * _________________________________ - * 5 x ok expected per peer */ GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "SPEED\n"); - test = SPEED; - ok_goal = 1003; + ok_goal = TOTAL_PACKETS + 5; + if (strstr (argv[0], "_min") != NULL) + { + test = SPEED_MIN; + test_name = "speed min"; + } + else if (strstr (argv[0], "_nobuf") != NULL) + { + test = SPEED_NOBUF; + test_name = "speed nobuf"; + } + else + { + test = SPEED; + test_name = "speed"; + } } else { @@ -1000,16 +968,31 @@ main (int argc, char *argv[]) ok_goal = 0; } - GNUNET_PROGRAM_run (argc2, argv2, - "test_mesh_small", - gettext_noop ("Test mesh in a small network."), options, - &run, NULL); -#if REMOVE_DIR - GNUNET_DISK_directory_remove ("/tmp/test_mesh_small"); -#endif + if (strstr (argv[0], "backwards") != NULL) + { + char *aux; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "BACKWARDS (LEAF TO ROOT)\n"); + test_backwards = GNUNET_YES; + aux = GNUNET_malloc (32); + sprintf (aux, "backwards %s", test_name); + test_name = aux; + } + + p_ids = 0; + GNUNET_MESH_TEST_run ("test_mesh_small", + "test_mesh_small.conf", + 5, + &tmain, + NULL, + &incoming_tunnel, + &tunnel_cleaner, + handlers, + NULL); + if (ok_goal > ok) { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "FAILED! (%d/%d)\n", ok, ok_goal); return 1; } diff --git a/src/mesh/test_mesh_small.conf b/src/mesh/test_mesh_small.conf index 005c490..943ef36 100644 --- a/src/mesh/test_mesh_small.conf +++ b/src/mesh/test_mesh_small.conf @@ -1,18 +1,32 @@ [PATHS] SERVICEHOME = /tmp/test_mesh_small/ -DEFAULTCONFIG = test_mesh_small.conf + +[mesh] +PORT = 10005 +ACCEPT_FROM = 127.0.0.1; +HOSTNAME = localhost +REFRESH_PATH_TIME = 5 s +APP_ANNOUNCE_TIME = 2 s +ID_ANNOUNCE_TIME = 2 s +CONNECT_TIMEOUT = 30 s +DEFAULT_TTL = 64 +DHT_REPLICAITON_LEVEL = 3 +# PREFIX = valgrind --leak-check=full --suppressions=valgrind-mesh.supp +# PREFIX = xterm -geometry 100x85 -T peer1 -e gdb --args + +[testbed] +NUM_PEERS = 5 +OVERLAY_TOPOLOGY = LINE [arm] PORT = 10010 DEFAULTSERVICES = core dht mesh -#DEBUG = YES [statistics] AUTOSTART = YES PORT = 10000 [dht] -DEBUG = NO AUTOSTART = YES ACCEPT_FROM6 = ::1; ACCEPT_FROM = 127.0.0.1; @@ -28,6 +42,10 @@ WORKDELAY = 500 ms AUTOSTART = NO PORT = 10011 +[vpn] +AUTOSTART = NO +PORT = 10012 + [transport] PORT = 10002 AUTOSTART = YES @@ -40,6 +58,8 @@ BEHIND_NAT = NO ALLOW_NAT = NO INTERNAL_ADDRESS = 127.0.0.1 EXTERNAL_ADDRESS = 127.0.0.1 +RETURN_LOCAL_ADDRESSES = YES +USE_LOCALADDR = YES [ats] WAN_QUOTA_IN = 1 GB @@ -53,43 +73,6 @@ PORT = 10003 AUTOSTART = YES PORT = 10004 -[mesh] -PORT = 10005 -DEBUG = YES -ACCEPT_FROM = 127.0.0.1; -HOSTNAME = localhost -# PREFIX = valgrind --leak-check=full --suppressions=valgrind-mesh.supp -# PREFIX = xterm -geometry 100x85 -T peer1 -e gdb --args - [testing] -NUM_PEERS = 5 WEAKRANDOM = YES -TOPOLOGY = NONE -CONNECT_TOPOLOGY = LINE -BLACKLIST_TOPOLOGY = LINE -BLACKLIST_TRANSPORTS = tcp udp http unix -#TOPOLOGY_FILE = small.dat -#CONNECT_TOPOLOGY_OPTION = CONNECT_MINIMUM -#CONNECT_TOPOLOGY_OPTION_MODIFIER = 25 -#PERCENTAGE = 3 -#PROBABILITY = .1 -F2F = NO -CONNECT_TIMEOUT = 660 s -CONNECT_ATTEMPTS = 2 -DEBUG = YES -HOSTKEYSFILE = ../../contrib/testing_hostkeys.dat -MAX_CONCURRENT_SSH = 10 -USE_PROGRESSBARS = YES -PEERGROUP_TIMEOUT = 2400 s -TOPOLOGY_OUTPUT_FILE = mesh_topo_initial -MAX_OUTSTANDING_CONNECTIONS = 75 -#SINGLE_PEERINFO_PER_HOST = YES -#NUM_PEERINFO_PER_HOST = 10 -#SINGLE_STATISTICS_PER_HOST = YES -#NUM_STATISTICS_PER_HOST = 10 -DELETE_FILES = YES -[test_mesh_small] -WAIT_TIME = 300 s -CONNECTION_LIMIT = 16 -#DATA_OUTPUT_FILE=data_output diff --git a/src/mesh/test_mesh_tree_api.c b/src/mesh/test_mesh_tree_api.c index 1d43135..3bdb82e 100644 --- a/src/mesh/test_mesh_tree_api.c +++ b/src/mesh/test_mesh_tree_api.c @@ -35,13 +35,32 @@ #define MESH_TUNNEL_TREE_C #endif -#define VERBOSE 1 +static int failed; +static int cb_call; +static struct GNUNET_PeerIdentity *pi[10]; +static struct MeshTunnelTree *tree; -int failed; -int cb_call; -struct GNUNET_PeerIdentity *pi[10]; -struct MeshTunnelTree *tree; +/** + * Whole tree iterator. + * + * @param cls Closure (unused). + * @param peer_id Short ID of the node. + * @param parent_id Short ID of the parent node. + */ +static void +tree_cb (void *cls, GNUNET_PEER_Id peer_id, GNUNET_PEER_Id parent_id) +{ + fprintf (stdout, "%u -> %u\n", peer_id, parent_id);; +} + + +/** + * Node children iterator. + * + * @param cls Closure (unused). + * @param peer_idShort ID of the child. + */ static void cb (void *cls, GNUNET_PEER_Id peer_id) { @@ -55,6 +74,19 @@ cb (void *cls, GNUNET_PEER_Id peer_id) } +/** + * Print debug information about the state of the tree. + * + * @param tree Tree to debug-print. + */ +static void +test_debug (struct MeshTunnelTree *tree) +{ + tree_debug (tree); + tree_iterate_all (tree, &tree_cb, NULL); +} + + /** * Check if a node has all expected properties. * @@ -118,6 +150,9 @@ test_assert (GNUNET_PEER_Id peer_id, enum MeshPeerState status, } +/** + * Clean up and free all memory. + */ static void finish (void) { @@ -155,11 +190,7 @@ main (int argc, char *argv[]) failed = 0; cb_call = 0; GNUNET_log_setup ("test_mesh_api_tree", -#if VERBOSE - "DEBUG", -#else "WARNING", -#endif NULL); for (i = 0; i < 10; i++) { @@ -179,7 +210,7 @@ main (int argc, char *argv[]) GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: Adding first path: 1 2 3 4\n"); tree_add_path (tree, path, &cb, NULL); - tree_debug (tree); + test_debug (tree); path1 = tree_get_path_to_peer (tree, 4); if (NULL == path1 || path->length != path1->length || memcmp (path->peers, path1->peers, path->length) != 0) @@ -196,7 +227,7 @@ main (int argc, char *argv[]) GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: Adding second path: 1 2 3\n"); path->length--; tree_add_path (tree, path, &cb, NULL); - tree_debug (tree); + test_debug (tree); test_assert (4, MESH_PEER_SEARCHING, 0, 2); test_assert (3, MESH_PEER_SEARCHING, 1, 2); @@ -207,7 +238,7 @@ main (int argc, char *argv[]) path->length++; path->peers[3] = 5; tree_add_path (tree, path, &cb, NULL); - tree_debug (tree); + test_debug (tree); test_assert (5, MESH_PEER_SEARCHING, 0, 2); test_assert (4, MESH_PEER_SEARCHING, 0, 2); @@ -249,7 +280,7 @@ main (int argc, char *argv[]) tree_set_status (tree, 5, MESH_PEER_READY); cb_call = 1; node = tree_del_path (tree, 5, &cb, NULL); - tree_debug (tree); + test_debug (tree); if (cb_call != 0) { GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "%u callbacks missed!\n", cb_call); @@ -276,7 +307,7 @@ main (int argc, char *argv[]) cb_call = 1; tree_find_peer (tree, 4)->status = MESH_PEER_READY; tree_add_path (tree, path, &cb, NULL); - tree_debug (tree); + test_debug (tree); if (cb_call != 0) { GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "%u callbacks missed!\n", cb_call); @@ -309,7 +340,7 @@ main (int argc, char *argv[]) GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: Adding first path: 2 1 3\n"); tree_add_path (tree, path, &cb, NULL); - tree_debug (tree); + test_debug (tree); test_assert (3, MESH_PEER_SEARCHING, 0, 3); test_assert (1, MESH_PEER_RELAY, 1, 0); @@ -321,7 +352,7 @@ main (int argc, char *argv[]) path->peers[4] = 3; path->length = 5; tree_add_path (tree, path, &cb, NULL); - tree_debug (tree); + test_debug (tree); test_assert (3, MESH_PEER_SEARCHING, 0, 4); test_assert (5, MESH_PEER_RELAY, 1, 4); @@ -341,7 +372,7 @@ main (int argc, char *argv[]) path->peers[7] = 3; path->length = 8; tree_add_path (tree, path, &cb, NULL); - tree_debug (tree); + test_debug (tree); test_assert (3, MESH_PEER_SEARCHING, 0, 7); test_assert (5, MESH_PEER_RELAY, 1, 7); @@ -357,7 +388,7 @@ main (int argc, char *argv[]) path->peers[2] = 3; path->length = 3; tree_add_path (tree, path, &cb, NULL); - tree_debug (tree); + test_debug (tree); test_assert (3, MESH_PEER_SEARCHING, 0, 3); test_assert (1, MESH_PEER_RELAY, 1, 0); diff --git a/src/mysql/Makefile.am b/src/mysql/Makefile.am index 1711e75..c98c71b 100644 --- a/src/mysql/Makefile.am +++ b/src/mysql/Makefile.am @@ -12,7 +12,7 @@ lib_LTLIBRARIES = libgnunetmysql.la libgnunetmysql_la_SOURCES = \ mysql.c -libgnunetmysql_la_LIBADD = -lmysqlclient \ +libgnunetmysql_la_LIBADD = $(MYSQL_LDFLAGS) -lmysqlclient \ $(top_builddir)/src/util/libgnunetutil.la libgnunetmysql_la_LDFLAGS = \ $(GN_LIB_LDFLAGS) \ diff --git a/src/mysql/Makefile.in b/src/mysql/Makefile.in index f058135..918f29a 100644 --- a/src/mysql/Makefile.in +++ b/src/mysql/Makefile.in @@ -1,9 +1,9 @@ -# Makefile.in generated by automake 1.11.1 from Makefile.am. +# Makefile.in generated by automake 1.11.6 from Makefile.am. # @configure_input@ # Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, -# 2003, 2004, 2005, 2006, 2007, 2008, 2009 Free Software Foundation, -# Inc. +# 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Free Software +# Foundation, Inc. # This Makefile.in is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. @@ -16,6 +16,23 @@ @SET_MAKE@ VPATH = @srcdir@ +am__make_dryrun = \ + { \ + am__dry=no; \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + echo 'am--echo: ; @echo "AM" OK' | $(MAKE) -f - 2>/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } pkgdatadir = $(datadir)/@PACKAGE@ pkgincludedir = $(includedir)/@PACKAGE@ pkglibdir = $(libdir)/@PACKAGE@ @@ -40,14 +57,15 @@ DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 am__aclocal_m4_deps = $(top_srcdir)/m4/absolute-header.m4 \ $(top_srcdir)/m4/align.m4 $(top_srcdir)/m4/argz.m4 \ - $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/iconv.m4 \ - $(top_srcdir)/m4/lib-ld.m4 $(top_srcdir)/m4/lib-link.m4 \ - $(top_srcdir)/m4/lib-prefix.m4 $(top_srcdir)/m4/libcurl.m4 \ - $(top_srcdir)/m4/libgcrypt.m4 $(top_srcdir)/m4/libtool.m4 \ - $(top_srcdir)/m4/libunistring.m4 $(top_srcdir)/m4/ltdl.m4 \ - $(top_srcdir)/m4/ltoptions.m4 $(top_srcdir)/m4/ltsugar.m4 \ - $(top_srcdir)/m4/ltversion.m4 $(top_srcdir)/m4/lt~obsolete.m4 \ - $(top_srcdir)/m4/nls.m4 $(top_srcdir)/m4/po.m4 \ + $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/glib-2.0.m4 \ + $(top_srcdir)/m4/iconv.m4 $(top_srcdir)/m4/lib-ld.m4 \ + $(top_srcdir)/m4/lib-link.m4 $(top_srcdir)/m4/lib-prefix.m4 \ + $(top_srcdir)/m4/libcurl.m4 $(top_srcdir)/m4/libgcrypt.m4 \ + $(top_srcdir)/m4/libtool.m4 $(top_srcdir)/m4/libunistring.m4 \ + $(top_srcdir)/m4/ltdl.m4 $(top_srcdir)/m4/ltoptions.m4 \ + $(top_srcdir)/m4/ltsugar.m4 $(top_srcdir)/m4/ltversion.m4 \ + $(top_srcdir)/m4/lt~obsolete.m4 $(top_srcdir)/m4/nls.m4 \ + $(top_srcdir)/m4/pkg.m4 $(top_srcdir)/m4/po.m4 \ $(top_srcdir)/m4/progtest.m4 $(top_srcdir)/acinclude.m4 \ $(top_srcdir)/configure.ac am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ @@ -77,14 +95,21 @@ am__nobase_list = $(am__nobase_strip_setup); \ am__base_list = \ sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \ sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g' +am__uninstall_files_from_dir = { \ + test -z "$$files" \ + || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \ + || { echo " ( cd '$$dir' && rm -f" $$files ")"; \ + $(am__cd) "$$dir" && rm -f $$files; }; \ + } am__installdirs = "$(DESTDIR)$(libdir)" LTLIBRARIES = $(lib_LTLIBRARIES) -libgnunetmysql_la_DEPENDENCIES = \ +am__DEPENDENCIES_1 = +libgnunetmysql_la_DEPENDENCIES = $(am__DEPENDENCIES_1) \ $(top_builddir)/src/util/libgnunetutil.la am_libgnunetmysql_la_OBJECTS = mysql.lo libgnunetmysql_la_OBJECTS = $(am_libgnunetmysql_la_OBJECTS) -AM_V_lt = $(am__v_lt_$(V)) -am__v_lt_ = $(am__v_lt_$(AM_DEFAULT_VERBOSITY)) +AM_V_lt = $(am__v_lt_@AM_V@) +am__v_lt_ = $(am__v_lt_@AM_DEFAULT_V@) am__v_lt_0 = --silent libgnunetmysql_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ @@ -100,24 +125,29 @@ LTCOMPILE = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) \ $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) \ $(AM_CFLAGS) $(CFLAGS) -AM_V_CC = $(am__v_CC_$(V)) -am__v_CC_ = $(am__v_CC_$(AM_DEFAULT_VERBOSITY)) +AM_V_CC = $(am__v_CC_@AM_V@) +am__v_CC_ = $(am__v_CC_@AM_DEFAULT_V@) am__v_CC_0 = @echo " CC " $@; -AM_V_at = $(am__v_at_$(V)) -am__v_at_ = $(am__v_at_$(AM_DEFAULT_VERBOSITY)) +AM_V_at = $(am__v_at_@AM_V@) +am__v_at_ = $(am__v_at_@AM_DEFAULT_V@) am__v_at_0 = @ CCLD = $(CC) LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ $(AM_LDFLAGS) $(LDFLAGS) -o $@ -AM_V_CCLD = $(am__v_CCLD_$(V)) -am__v_CCLD_ = $(am__v_CCLD_$(AM_DEFAULT_VERBOSITY)) +AM_V_CCLD = $(am__v_CCLD_@AM_V@) +am__v_CCLD_ = $(am__v_CCLD_@AM_DEFAULT_V@) am__v_CCLD_0 = @echo " CCLD " $@; -AM_V_GEN = $(am__v_GEN_$(V)) -am__v_GEN_ = $(am__v_GEN_$(AM_DEFAULT_VERBOSITY)) +AM_V_GEN = $(am__v_GEN_@AM_V@) +am__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@) am__v_GEN_0 = @echo " GEN " $@; SOURCES = $(libgnunetmysql_la_SOURCES) DIST_SOURCES = $(libgnunetmysql_la_SOURCES) +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac ETAGS = etags CTAGS = ctags DISTFILES = $(DIST_COMMON) $(DIST_SOURCES) $(TEXINFOS) $(EXTRA_DIST) @@ -156,6 +186,10 @@ EXEEXT = @EXEEXT@ EXT_LIBS = @EXT_LIBS@ EXT_LIB_PATH = @EXT_LIB_PATH@ FGREP = @FGREP@ +GLIB_CFLAGS = @GLIB_CFLAGS@ +GLIB_GENMARSHAL = @GLIB_GENMARSHAL@ +GLIB_LIBS = @GLIB_LIBS@ +GLIB_MKENUMS = @GLIB_MKENUMS@ GMSGFMT = @GMSGFMT@ GMSGFMT_015 = @GMSGFMT_015@ GNUNETDNS_GROUP = @GNUNETDNS_GROUP@ @@ -166,6 +200,7 @@ GN_LIBINTL = @GN_LIBINTL@ GN_LIB_LDFLAGS = @GN_LIB_LDFLAGS@ GN_PLUGIN_LDFLAGS = @GN_PLUGIN_LDFLAGS@ GN_USER_HOME_DIR = @GN_USER_HOME_DIR@ +GOBJECT_QUERY = @GOBJECT_QUERY@ GREP = @GREP@ HAVE_LIBUNISTRING = @HAVE_LIBUNISTRING@ INCLTDL = @INCLTDL@ @@ -188,6 +223,8 @@ LIBCURL_CPPFLAGS = @LIBCURL_CPPFLAGS@ LIBGCRYPT_CFLAGS = @LIBGCRYPT_CFLAGS@ LIBGCRYPT_CONFIG = @LIBGCRYPT_CONFIG@ LIBGCRYPT_LIBS = @LIBGCRYPT_LIBS@ +LIBGTOP_CFLAGS = @LIBGTOP_CFLAGS@ +LIBGTOP_LIBS = @LIBGTOP_LIBS@ LIBICONV = @LIBICONV@ LIBINTL = @LIBINTL@ LIBLTDL = @LIBLTDL@ @@ -209,6 +246,7 @@ LT_CONFIG_H = @LT_CONFIG_H@ LT_DLLOADERS = @LT_DLLOADERS@ LT_DLPREOPEN = @LT_DLPREOPEN@ MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ MKDIR_P = @MKDIR_P@ MONKEYPREFIX = @MONKEYPREFIX@ MSGFMT = @MSGFMT@ @@ -218,6 +256,7 @@ MYSQL_CPPFLAGS = @MYSQL_CPPFLAGS@ MYSQL_LDFLAGS = @MYSQL_LDFLAGS@ NM = @NM@ NMEDIT = @NMEDIT@ +NSS_DIR = @NSS_DIR@ OBJC = @OBJC@ OBJCDEPMODE = @OBJCDEPMODE@ OBJCFLAGS = @OBJCFLAGS@ @@ -233,6 +272,7 @@ PACKAGE_TARNAME = @PACKAGE_TARNAME@ PACKAGE_URL = @PACKAGE_URL@ PACKAGE_VERSION = @PACKAGE_VERSION@ PATH_SEPARATOR = @PATH_SEPARATOR@ +PKG_CONFIG = @PKG_CONFIG@ POSTGRES_CPPFLAGS = @POSTGRES_CPPFLAGS@ POSTGRES_LDFLAGS = @POSTGRES_LDFLAGS@ POSUB = @POSUB@ @@ -264,6 +304,7 @@ abs_builddir = @abs_builddir@ abs_srcdir = @abs_srcdir@ abs_top_builddir = @abs_top_builddir@ abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ ac_ct_CC = @ac_ct_CC@ ac_ct_CXX = @ac_ct_CXX@ ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ @@ -286,6 +327,7 @@ datarootdir = @datarootdir@ docdir = @docdir@ dvidir = @dvidir@ exec_prefix = @exec_prefix@ +gitcommand = @gitcommand@ host = @host@ host_alias = @host_alias@ host_cpu = @host_cpu@ @@ -299,7 +341,6 @@ libdir = @libdir@ libexecdir = @libexecdir@ localedir = @localedir@ localstatedir = @localstatedir@ -lt_ECHO = @lt_ECHO@ ltdl_LIBOBJS = @ltdl_LIBOBJS@ ltdl_LTLIBOBJS = @ltdl_LTLIBOBJS@ mandir = @mandir@ @@ -317,6 +358,7 @@ sbindir = @sbindir@ sharedstatedir = @sharedstatedir@ srcdir = @srcdir@ subdirs = @subdirs@ +svnversioncommand = @svnversioncommand@ sys_symbol_underscore = @sys_symbol_underscore@ sysconfdir = @sysconfdir@ target = @target@ @@ -334,7 +376,7 @@ lib_LTLIBRARIES = libgnunetmysql.la libgnunetmysql_la_SOURCES = \ mysql.c -libgnunetmysql_la_LIBADD = -lmysqlclient \ +libgnunetmysql_la_LIBADD = $(MYSQL_LDFLAGS) -lmysqlclient \ $(top_builddir)/src/util/libgnunetutil.la libgnunetmysql_la_LDFLAGS = \ @@ -377,7 +419,6 @@ $(ACLOCAL_M4): $(am__aclocal_m4_deps) $(am__aclocal_m4_deps): install-libLTLIBRARIES: $(lib_LTLIBRARIES) @$(NORMAL_INSTALL) - test -z "$(libdir)" || $(MKDIR_P) "$(DESTDIR)$(libdir)" @list='$(lib_LTLIBRARIES)'; test -n "$(libdir)" || list=; \ list2=; for p in $$list; do \ if test -f $$p; then \ @@ -385,6 +426,8 @@ install-libLTLIBRARIES: $(lib_LTLIBRARIES) else :; fi; \ done; \ test -z "$$list2" || { \ + echo " $(MKDIR_P) '$(DESTDIR)$(libdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libdir)" || exit 1; \ echo " $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 '$(DESTDIR)$(libdir)'"; \ $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 "$(DESTDIR)$(libdir)"; \ } @@ -406,7 +449,7 @@ clean-libLTLIBRARIES: echo "rm -f \"$${dir}/so_locations\""; \ rm -f "$${dir}/so_locations"; \ done -libgnunetmysql.la: $(libgnunetmysql_la_OBJECTS) $(libgnunetmysql_la_DEPENDENCIES) +libgnunetmysql.la: $(libgnunetmysql_la_OBJECTS) $(libgnunetmysql_la_DEPENDENCIES) $(EXTRA_libgnunetmysql_la_DEPENDENCIES) $(AM_V_CCLD)$(libgnunetmysql_la_LINK) -rpath $(libdir) $(libgnunetmysql_la_OBJECTS) $(libgnunetmysql_la_LIBADD) $(LIBS) mostlyclean-compile: @@ -420,26 +463,23 @@ distclean-compile: .c.o: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c $< .c.obj: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'` @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c `$(CYGPATH_W) '$<'` +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c `$(CYGPATH_W) '$<'` .c.lo: @am__fastdepCC_TRUE@ $(AM_V_CC)$(LTCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LTCOMPILE) -c -o $@ $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LTCOMPILE) -c -o $@ $< mostlyclean-libtool: -rm -f *.lo @@ -546,10 +586,15 @@ install-am: all-am installcheck: installcheck-am install-strip: - $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ - install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ - `test -z '$(STRIP)' || \ - echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi mostlyclean-generic: clean-generic: diff --git a/src/namestore/Makefile.am b/src/namestore/Makefile.am index 7783506..1d36fe7 100644 --- a/src/namestore/Makefile.am +++ b/src/namestore/Makefile.am @@ -4,6 +4,8 @@ plugindir = $(libdir)/gnunet pkgcfgdir= $(pkgdatadir)/config.d/ +libexecdir= $(pkglibdir)/libexec/ + pkgcfg_DATA = \ namestore.conf @@ -18,13 +20,18 @@ if USE_COVERAGE endif if HAVE_SQLITE -SQLITE_TESTS = \ - test_plugin_namestore_sqlite +SQLITE_PLUGIN = libgnunet_plugin_namestore_sqlite.la +SQLITE_TESTS = test_plugin_namestore_sqlite +endif +if HAVE_POSTGRES +POSTGRES_TESTS = test_plugin_namestore_postgres +POSTGRES_PLUGIN = libgnunet_plugin_namestore_postgres.la endif - +if HAVE_SQLITE check_PROGRAMS = \ $(SQLITE_TESTS) \ + $(POSTGRES_TESTS) \ test_namestore_record_serialization \ test_namestore_api_sign_verify \ test_namestore_api \ @@ -39,6 +46,7 @@ check_PROGRAMS = \ test_namestore_api_zone_iteration \ test_namestore_api_zone_iteration_specific_zone \ test_namestore_api_zone_iteration_stop +endif if ENABLE_TEST_RUN TESTS = $(check_PROGRAMS) @@ -55,10 +63,12 @@ libgnunetnamestore_la_LIBADD = \ $(GN_LIBINTL) libgnunetnamestore_la_LDFLAGS = \ $(GN_LIB_LDFLAGS) $(WINFLAGS) \ - -version-info 0:0:0 + -version-info 0:1:0 + +libexec_PROGRAMS = \ + gnunet-service-namestore bin_PROGRAMS = \ - gnunet-service-namestore \ gnunet-namestore @@ -87,19 +97,18 @@ gnunet_service_namestore_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la \ libgnunetnamestore.la -if HAVE_SQLITE - SQLITE_PLUGIN = libgnunet_plugin_namestore_sqlite.la -endif plugin_LTLIBRARIES = \ - $(SQLITE_PLUGIN) + $(SQLITE_PLUGIN) \ + $(POSTGRES_PLUGIN) libgnunet_plugin_namestore_sqlite_la_SOURCES = \ plugin_namestore_sqlite.c namestore_common.c libgnunet_plugin_namestore_sqlite_la_LIBADD = \ $(top_builddir)/src/namestore/libgnunetnamestore.la \ $(top_builddir)/src/statistics/libgnunetstatistics.la \ - $(top_builddir)/src/util/libgnunetutil.la $(XLIBS) -lsqlite3 + $(top_builddir)/src/util/libgnunetutil.la $(XLIBS) -lsqlite3 \ + $(LTLIBINTL) libgnunet_plugin_namestore_sqlite_la_LDFLAGS = \ $(GN_PLUGIN_LDFLAGS) libgnunet_plugin_namestore_sqlite_la_DEPENDENCIES = \ @@ -107,33 +116,55 @@ libgnunet_plugin_namestore_sqlite_la_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la \ libgnunetnamestore.la + +libgnunet_plugin_namestore_postgres_la_SOURCES = \ + plugin_namestore_postgres.c namestore_common.c +libgnunet_plugin_namestore_postgres_la_LIBADD = \ + $(top_builddir)/src/namestore/libgnunetnamestore.la \ + $(top_builddir)/src/postgres/libgnunetpostgres.la \ + $(top_builddir)/src/statistics/libgnunetstatistics.la \ + $(top_builddir)/src/util/libgnunetutil.la $(XLIBS) -lpq \ + $(LTLIBINTL) +libgnunet_plugin_namestore_postgres_la_LDFLAGS = \ + $(GN_PLUGIN_LDFLAGS) +libgnunet_plugin_namestore_postgres_la_DEPENDENCIES = \ + $(top_builddir)/src/postgres/libgnunetpostgres.la \ + $(top_builddir)/src/statistics/libgnunetstatistics.la \ + $(top_builddir)/src/util/libgnunetutil.la \ + libgnunetnamestore.la + test_namestore_api_sign_verify_SOURCES = \ test_namestore_api_sign_verify.c test_namestore_api_sign_verify_LDADD = \ $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la test_namestore_api_SOURCES = \ test_namestore_api.c test_namestore_api_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la test_namestore_api_put_SOURCES = \ test_namestore_api_put.c test_namestore_api_put_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la test_namestore_api_lookup_SOURCES = \ test_namestore_api_lookup.c test_namestore_api_lookup_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la test_namestore_api_lookup_specific_type_SOURCES = \ test_namestore_api_lookup_specific_type.c test_namestore_api_lookup_specific_type_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la @@ -141,12 +172,14 @@ test_namestore_api_lookup_specific_type_LDADD = \ test_namestore_api_create_SOURCES = \ test_namestore_api_create.c test_namestore_api_create_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la test_namestore_api_create_update_SOURCES = \ test_namestore_api_create_update.c test_namestore_api_create_update_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la @@ -154,48 +187,56 @@ test_namestore_api_create_update_LDADD = \ test_namestore_api_remove_SOURCES = \ test_namestore_api_remove.c test_namestore_api_remove_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la test_namestore_api_remove_not_existing_record_SOURCES = \ test_namestore_api_remove_not_existing_record.c test_namestore_api_remove_not_existing_record_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la test_namestore_api_zone_to_name_SOURCES = \ test_namestore_api_zone_to_name.c test_namestore_api_zone_to_name_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la test_namestore_api_zone_iteration_SOURCES = \ test_namestore_api_zone_iteration.c test_namestore_api_zone_iteration_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la - + test_namestore_api_zone_iteration_specific_zone_SOURCES = \ test_namestore_api_zone_iteration_specific_zone.c test_namestore_api_zone_iteration_specific_zone_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la - + test_namestore_api_zone_iteration_stop_SOURCES = \ test_namestore_api_zone_iteration_stop.c test_namestore_api_zone_iteration_stop_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la test_namestore_record_serialization_SOURCES = \ test_namestore_record_serialization.c test_namestore_record_serialization_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la EXTRA_DIST = \ test_namestore_api.conf \ test_plugin_namestore_sqlite.conf\ + test_plugin_namestore_postgres.conf\ test_hostkey \ zonefiles/HGU0A0VCU334DN7F2I9UIUMVQMM7JMSD142LIMNUGTTV9R0CF4EG.zkey \ zonefiles/N0UJMP015AFUNR2BTNM3FKPBLG38913BL8IDMCO2H0A1LIB81960.zkey @@ -204,4 +245,11 @@ EXTRA_DIST = \ test_plugin_namestore_sqlite_SOURCES = \ test_plugin_namestore.c test_plugin_namestore_sqlite_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/util/libgnunetutil.la + +test_plugin_namestore_postgres_SOURCES = \ + test_plugin_namestore.c +test_plugin_namestore_postgres_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la diff --git a/src/namestore/Makefile.in b/src/namestore/Makefile.in index 180232d..4512eac 100644 --- a/src/namestore/Makefile.in +++ b/src/namestore/Makefile.in @@ -1,9 +1,9 @@ -# Makefile.in generated by automake 1.11.1 from Makefile.am. +# Makefile.in generated by automake 1.11.6 from Makefile.am. # @configure_input@ # Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, -# 2003, 2004, 2005, 2006, 2007, 2008, 2009 Free Software Foundation, -# Inc. +# 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Free Software +# Foundation, Inc. # This Makefile.in is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. @@ -18,6 +18,23 @@ VPATH = @srcdir@ +am__make_dryrun = \ + { \ + am__dry=no; \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + echo 'am--echo: ; @echo "AM" OK' | $(MAKE) -f - 2>/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } pkgdatadir = $(datadir)/@PACKAGE@ pkgincludedir = $(includedir)/@PACKAGE@ pkglibdir = $(libdir)/@PACKAGE@ @@ -37,36 +54,38 @@ POST_UNINSTALL = : build_triplet = @build@ host_triplet = @host@ target_triplet = @target@ -check_PROGRAMS = $(am__EXEEXT_1) \ - test_namestore_record_serialization$(EXEEXT) \ - test_namestore_api_sign_verify$(EXEEXT) \ - test_namestore_api$(EXEEXT) test_namestore_api_put$(EXEEXT) \ - test_namestore_api_lookup$(EXEEXT) \ - test_namestore_api_lookup_specific_type$(EXEEXT) \ - test_namestore_api_create$(EXEEXT) \ - test_namestore_api_create_update$(EXEEXT) \ - test_namestore_api_remove$(EXEEXT) \ - test_namestore_api_remove_not_existing_record$(EXEEXT) \ - test_namestore_api_zone_to_name$(EXEEXT) \ - test_namestore_api_zone_iteration$(EXEEXT) \ - test_namestore_api_zone_iteration_specific_zone$(EXEEXT) \ - test_namestore_api_zone_iteration_stop$(EXEEXT) -bin_PROGRAMS = gnunet-service-namestore$(EXEEXT) \ - gnunet-namestore$(EXEEXT) +@HAVE_SQLITE_TRUE@check_PROGRAMS = $(am__EXEEXT_1) $(am__EXEEXT_2) \ +@HAVE_SQLITE_TRUE@ test_namestore_record_serialization$(EXEEXT) \ +@HAVE_SQLITE_TRUE@ test_namestore_api_sign_verify$(EXEEXT) \ +@HAVE_SQLITE_TRUE@ test_namestore_api$(EXEEXT) \ +@HAVE_SQLITE_TRUE@ test_namestore_api_put$(EXEEXT) \ +@HAVE_SQLITE_TRUE@ test_namestore_api_lookup$(EXEEXT) \ +@HAVE_SQLITE_TRUE@ test_namestore_api_lookup_specific_type$(EXEEXT) \ +@HAVE_SQLITE_TRUE@ test_namestore_api_create$(EXEEXT) \ +@HAVE_SQLITE_TRUE@ test_namestore_api_create_update$(EXEEXT) \ +@HAVE_SQLITE_TRUE@ test_namestore_api_remove$(EXEEXT) \ +@HAVE_SQLITE_TRUE@ test_namestore_api_remove_not_existing_record$(EXEEXT) \ +@HAVE_SQLITE_TRUE@ test_namestore_api_zone_to_name$(EXEEXT) \ +@HAVE_SQLITE_TRUE@ test_namestore_api_zone_iteration$(EXEEXT) \ +@HAVE_SQLITE_TRUE@ test_namestore_api_zone_iteration_specific_zone$(EXEEXT) \ +@HAVE_SQLITE_TRUE@ test_namestore_api_zone_iteration_stop$(EXEEXT) +libexec_PROGRAMS = gnunet-service-namestore$(EXEEXT) +bin_PROGRAMS = gnunet-namestore$(EXEEXT) subdir = src/namestore DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in \ $(srcdir)/namestore.conf.in ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 am__aclocal_m4_deps = $(top_srcdir)/m4/absolute-header.m4 \ $(top_srcdir)/m4/align.m4 $(top_srcdir)/m4/argz.m4 \ - $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/iconv.m4 \ - $(top_srcdir)/m4/lib-ld.m4 $(top_srcdir)/m4/lib-link.m4 \ - $(top_srcdir)/m4/lib-prefix.m4 $(top_srcdir)/m4/libcurl.m4 \ - $(top_srcdir)/m4/libgcrypt.m4 $(top_srcdir)/m4/libtool.m4 \ - $(top_srcdir)/m4/libunistring.m4 $(top_srcdir)/m4/ltdl.m4 \ - $(top_srcdir)/m4/ltoptions.m4 $(top_srcdir)/m4/ltsugar.m4 \ - $(top_srcdir)/m4/ltversion.m4 $(top_srcdir)/m4/lt~obsolete.m4 \ - $(top_srcdir)/m4/nls.m4 $(top_srcdir)/m4/po.m4 \ + $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/glib-2.0.m4 \ + $(top_srcdir)/m4/iconv.m4 $(top_srcdir)/m4/lib-ld.m4 \ + $(top_srcdir)/m4/lib-link.m4 $(top_srcdir)/m4/lib-prefix.m4 \ + $(top_srcdir)/m4/libcurl.m4 $(top_srcdir)/m4/libgcrypt.m4 \ + $(top_srcdir)/m4/libtool.m4 $(top_srcdir)/m4/libunistring.m4 \ + $(top_srcdir)/m4/ltdl.m4 $(top_srcdir)/m4/ltoptions.m4 \ + $(top_srcdir)/m4/ltsugar.m4 $(top_srcdir)/m4/ltversion.m4 \ + $(top_srcdir)/m4/lt~obsolete.m4 $(top_srcdir)/m4/nls.m4 \ + $(top_srcdir)/m4/pkg.m4 $(top_srcdir)/m4/po.m4 \ $(top_srcdir)/m4/progtest.m4 $(top_srcdir)/acinclude.m4 \ $(top_srcdir)/configure.ac am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ @@ -96,17 +115,35 @@ am__nobase_list = $(am__nobase_strip_setup); \ am__base_list = \ sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \ sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g' +am__uninstall_files_from_dir = { \ + test -z "$$files" \ + || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \ + || { echo " ( cd '$$dir' && rm -f" $$files ")"; \ + $(am__cd) "$$dir" && rm -f $$files; }; \ + } am__installdirs = "$(DESTDIR)$(libdir)" "$(DESTDIR)$(plugindir)" \ - "$(DESTDIR)$(bindir)" "$(DESTDIR)$(pkgcfgdir)" + "$(DESTDIR)$(bindir)" "$(DESTDIR)$(libexecdir)" \ + "$(DESTDIR)$(pkgcfgdir)" LTLIBRARIES = $(lib_LTLIBRARIES) $(plugin_LTLIBRARIES) am__DEPENDENCIES_1 = +am_libgnunet_plugin_namestore_postgres_la_OBJECTS = \ + plugin_namestore_postgres.lo namestore_common.lo +libgnunet_plugin_namestore_postgres_la_OBJECTS = \ + $(am_libgnunet_plugin_namestore_postgres_la_OBJECTS) +AM_V_lt = $(am__v_lt_@AM_V@) +am__v_lt_ = $(am__v_lt_@AM_DEFAULT_V@) +am__v_lt_0 = --silent +libgnunet_plugin_namestore_postgres_la_LINK = $(LIBTOOL) $(AM_V_lt) \ + --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link \ + $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ + $(libgnunet_plugin_namestore_postgres_la_LDFLAGS) $(LDFLAGS) \ + -o $@ +@HAVE_POSTGRES_TRUE@am_libgnunet_plugin_namestore_postgres_la_rpath = \ +@HAVE_POSTGRES_TRUE@ -rpath $(plugindir) am_libgnunet_plugin_namestore_sqlite_la_OBJECTS = \ plugin_namestore_sqlite.lo namestore_common.lo libgnunet_plugin_namestore_sqlite_la_OBJECTS = \ $(am_libgnunet_plugin_namestore_sqlite_la_OBJECTS) -AM_V_lt = $(am__v_lt_$(V)) -am__v_lt_ = $(am__v_lt_$(AM_DEFAULT_VERBOSITY)) -am__v_lt_0 = --silent libgnunet_plugin_namestore_sqlite_la_LINK = $(LIBTOOL) $(AM_V_lt) \ --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link \ $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ @@ -127,7 +164,9 @@ libgnunetnamestore_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ $(LDFLAGS) -o $@ @HAVE_SQLITE_TRUE@am__EXEEXT_1 = \ @HAVE_SQLITE_TRUE@ test_plugin_namestore_sqlite$(EXEEXT) -PROGRAMS = $(bin_PROGRAMS) +@HAVE_POSTGRES_TRUE@am__EXEEXT_2 = \ +@HAVE_POSTGRES_TRUE@ test_plugin_namestore_postgres$(EXEEXT) +PROGRAMS = $(bin_PROGRAMS) $(libexec_PROGRAMS) am_gnunet_namestore_OBJECTS = gnunet-namestore.$(OBJEXT) gnunet_namestore_OBJECTS = $(am_gnunet_namestore_OBJECTS) am_gnunet_service_namestore_OBJECTS = \ @@ -137,6 +176,7 @@ gnunet_service_namestore_OBJECTS = \ am_test_namestore_api_OBJECTS = test_namestore_api.$(OBJEXT) test_namestore_api_OBJECTS = $(am_test_namestore_api_OBJECTS) test_namestore_api_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la am_test_namestore_api_create_OBJECTS = \ @@ -144,6 +184,7 @@ am_test_namestore_api_create_OBJECTS = \ test_namestore_api_create_OBJECTS = \ $(am_test_namestore_api_create_OBJECTS) test_namestore_api_create_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la am_test_namestore_api_create_update_OBJECTS = \ @@ -151,6 +192,7 @@ am_test_namestore_api_create_update_OBJECTS = \ test_namestore_api_create_update_OBJECTS = \ $(am_test_namestore_api_create_update_OBJECTS) test_namestore_api_create_update_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la am_test_namestore_api_lookup_OBJECTS = \ @@ -158,6 +200,7 @@ am_test_namestore_api_lookup_OBJECTS = \ test_namestore_api_lookup_OBJECTS = \ $(am_test_namestore_api_lookup_OBJECTS) test_namestore_api_lookup_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la am_test_namestore_api_lookup_specific_type_OBJECTS = \ @@ -165,11 +208,13 @@ am_test_namestore_api_lookup_specific_type_OBJECTS = \ test_namestore_api_lookup_specific_type_OBJECTS = \ $(am_test_namestore_api_lookup_specific_type_OBJECTS) test_namestore_api_lookup_specific_type_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la am_test_namestore_api_put_OBJECTS = test_namestore_api_put.$(OBJEXT) test_namestore_api_put_OBJECTS = $(am_test_namestore_api_put_OBJECTS) test_namestore_api_put_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la am_test_namestore_api_remove_OBJECTS = \ @@ -177,6 +222,7 @@ am_test_namestore_api_remove_OBJECTS = \ test_namestore_api_remove_OBJECTS = \ $(am_test_namestore_api_remove_OBJECTS) test_namestore_api_remove_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la am_test_namestore_api_remove_not_existing_record_OBJECTS = \ @@ -184,6 +230,7 @@ am_test_namestore_api_remove_not_existing_record_OBJECTS = \ test_namestore_api_remove_not_existing_record_OBJECTS = \ $(am_test_namestore_api_remove_not_existing_record_OBJECTS) test_namestore_api_remove_not_existing_record_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la am_test_namestore_api_sign_verify_OBJECTS = \ @@ -192,12 +239,14 @@ test_namestore_api_sign_verify_OBJECTS = \ $(am_test_namestore_api_sign_verify_OBJECTS) test_namestore_api_sign_verify_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la am_test_namestore_api_zone_iteration_OBJECTS = \ test_namestore_api_zone_iteration.$(OBJEXT) test_namestore_api_zone_iteration_OBJECTS = \ $(am_test_namestore_api_zone_iteration_OBJECTS) test_namestore_api_zone_iteration_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la am_test_namestore_api_zone_iteration_specific_zone_OBJECTS = \ @@ -205,6 +254,7 @@ am_test_namestore_api_zone_iteration_specific_zone_OBJECTS = \ test_namestore_api_zone_iteration_specific_zone_OBJECTS = \ $(am_test_namestore_api_zone_iteration_specific_zone_OBJECTS) test_namestore_api_zone_iteration_specific_zone_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la am_test_namestore_api_zone_iteration_stop_OBJECTS = \ @@ -212,6 +262,7 @@ am_test_namestore_api_zone_iteration_stop_OBJECTS = \ test_namestore_api_zone_iteration_stop_OBJECTS = \ $(am_test_namestore_api_zone_iteration_stop_OBJECTS) test_namestore_api_zone_iteration_stop_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la am_test_namestore_api_zone_to_name_OBJECTS = \ @@ -219,6 +270,7 @@ am_test_namestore_api_zone_to_name_OBJECTS = \ test_namestore_api_zone_to_name_OBJECTS = \ $(am_test_namestore_api_zone_to_name_OBJECTS) test_namestore_api_zone_to_name_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la am_test_namestore_record_serialization_OBJECTS = \ @@ -226,13 +278,22 @@ am_test_namestore_record_serialization_OBJECTS = \ test_namestore_record_serialization_OBJECTS = \ $(am_test_namestore_record_serialization_OBJECTS) test_namestore_record_serialization_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la +am_test_plugin_namestore_postgres_OBJECTS = \ + test_plugin_namestore.$(OBJEXT) +test_plugin_namestore_postgres_OBJECTS = \ + $(am_test_plugin_namestore_postgres_OBJECTS) +test_plugin_namestore_postgres_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/util/libgnunetutil.la am_test_plugin_namestore_sqlite_OBJECTS = \ test_plugin_namestore.$(OBJEXT) test_plugin_namestore_sqlite_OBJECTS = \ $(am_test_plugin_namestore_sqlite_OBJECTS) test_plugin_namestore_sqlite_DEPENDENCIES = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la DEFAULT_INCLUDES = -I.@am__isrc@ -I$(top_builddir) depcomp = $(SHELL) $(top_srcdir)/depcomp @@ -244,23 +305,24 @@ LTCOMPILE = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) \ $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) \ $(AM_CFLAGS) $(CFLAGS) -AM_V_CC = $(am__v_CC_$(V)) -am__v_CC_ = $(am__v_CC_$(AM_DEFAULT_VERBOSITY)) +AM_V_CC = $(am__v_CC_@AM_V@) +am__v_CC_ = $(am__v_CC_@AM_DEFAULT_V@) am__v_CC_0 = @echo " CC " $@; -AM_V_at = $(am__v_at_$(V)) -am__v_at_ = $(am__v_at_$(AM_DEFAULT_VERBOSITY)) +AM_V_at = $(am__v_at_@AM_V@) +am__v_at_ = $(am__v_at_@AM_DEFAULT_V@) am__v_at_0 = @ CCLD = $(CC) LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ $(AM_LDFLAGS) $(LDFLAGS) -o $@ -AM_V_CCLD = $(am__v_CCLD_$(V)) -am__v_CCLD_ = $(am__v_CCLD_$(AM_DEFAULT_VERBOSITY)) +AM_V_CCLD = $(am__v_CCLD_@AM_V@) +am__v_CCLD_ = $(am__v_CCLD_@AM_DEFAULT_V@) am__v_CCLD_0 = @echo " CCLD " $@; -AM_V_GEN = $(am__v_GEN_$(V)) -am__v_GEN_ = $(am__v_GEN_$(AM_DEFAULT_VERBOSITY)) +AM_V_GEN = $(am__v_GEN_@AM_V@) +am__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@) am__v_GEN_0 = @echo " GEN " $@; -SOURCES = $(libgnunet_plugin_namestore_sqlite_la_SOURCES) \ +SOURCES = $(libgnunet_plugin_namestore_postgres_la_SOURCES) \ + $(libgnunet_plugin_namestore_sqlite_la_SOURCES) \ $(libgnunetnamestore_la_SOURCES) $(gnunet_namestore_SOURCES) \ $(gnunet_service_namestore_SOURCES) \ $(test_namestore_api_SOURCES) \ @@ -277,8 +339,10 @@ SOURCES = $(libgnunet_plugin_namestore_sqlite_la_SOURCES) \ $(test_namestore_api_zone_iteration_stop_SOURCES) \ $(test_namestore_api_zone_to_name_SOURCES) \ $(test_namestore_record_serialization_SOURCES) \ + $(test_plugin_namestore_postgres_SOURCES) \ $(test_plugin_namestore_sqlite_SOURCES) -DIST_SOURCES = $(libgnunet_plugin_namestore_sqlite_la_SOURCES) \ +DIST_SOURCES = $(libgnunet_plugin_namestore_postgres_la_SOURCES) \ + $(libgnunet_plugin_namestore_sqlite_la_SOURCES) \ $(libgnunetnamestore_la_SOURCES) $(gnunet_namestore_SOURCES) \ $(gnunet_service_namestore_SOURCES) \ $(test_namestore_api_SOURCES) \ @@ -295,7 +359,13 @@ DIST_SOURCES = $(libgnunet_plugin_namestore_sqlite_la_SOURCES) \ $(test_namestore_api_zone_iteration_stop_SOURCES) \ $(test_namestore_api_zone_to_name_SOURCES) \ $(test_namestore_record_serialization_SOURCES) \ + $(test_plugin_namestore_postgres_SOURCES) \ $(test_plugin_namestore_sqlite_SOURCES) +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac DATA = $(pkgcfg_DATA) ETAGS = etags CTAGS = ctags @@ -337,6 +407,10 @@ EXEEXT = @EXEEXT@ EXT_LIBS = @EXT_LIBS@ EXT_LIB_PATH = @EXT_LIB_PATH@ FGREP = @FGREP@ +GLIB_CFLAGS = @GLIB_CFLAGS@ +GLIB_GENMARSHAL = @GLIB_GENMARSHAL@ +GLIB_LIBS = @GLIB_LIBS@ +GLIB_MKENUMS = @GLIB_MKENUMS@ GMSGFMT = @GMSGFMT@ GMSGFMT_015 = @GMSGFMT_015@ GNUNETDNS_GROUP = @GNUNETDNS_GROUP@ @@ -347,6 +421,7 @@ GN_LIBINTL = @GN_LIBINTL@ GN_LIB_LDFLAGS = @GN_LIB_LDFLAGS@ GN_PLUGIN_LDFLAGS = @GN_PLUGIN_LDFLAGS@ GN_USER_HOME_DIR = @GN_USER_HOME_DIR@ +GOBJECT_QUERY = @GOBJECT_QUERY@ GREP = @GREP@ HAVE_LIBUNISTRING = @HAVE_LIBUNISTRING@ INCLTDL = @INCLTDL@ @@ -369,6 +444,8 @@ LIBCURL_CPPFLAGS = @LIBCURL_CPPFLAGS@ LIBGCRYPT_CFLAGS = @LIBGCRYPT_CFLAGS@ LIBGCRYPT_CONFIG = @LIBGCRYPT_CONFIG@ LIBGCRYPT_LIBS = @LIBGCRYPT_LIBS@ +LIBGTOP_CFLAGS = @LIBGTOP_CFLAGS@ +LIBGTOP_LIBS = @LIBGTOP_LIBS@ LIBICONV = @LIBICONV@ LIBINTL = @LIBINTL@ LIBLTDL = @LIBLTDL@ @@ -390,6 +467,7 @@ LT_CONFIG_H = @LT_CONFIG_H@ LT_DLLOADERS = @LT_DLLOADERS@ LT_DLPREOPEN = @LT_DLPREOPEN@ MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ MKDIR_P = @MKDIR_P@ MONKEYPREFIX = @MONKEYPREFIX@ MSGFMT = @MSGFMT@ @@ -399,6 +477,7 @@ MYSQL_CPPFLAGS = @MYSQL_CPPFLAGS@ MYSQL_LDFLAGS = @MYSQL_LDFLAGS@ NM = @NM@ NMEDIT = @NMEDIT@ +NSS_DIR = @NSS_DIR@ OBJC = @OBJC@ OBJCDEPMODE = @OBJCDEPMODE@ OBJCFLAGS = @OBJCFLAGS@ @@ -414,6 +493,7 @@ PACKAGE_TARNAME = @PACKAGE_TARNAME@ PACKAGE_URL = @PACKAGE_URL@ PACKAGE_VERSION = @PACKAGE_VERSION@ PATH_SEPARATOR = @PATH_SEPARATOR@ +PKG_CONFIG = @PKG_CONFIG@ POSTGRES_CPPFLAGS = @POSTGRES_CPPFLAGS@ POSTGRES_LDFLAGS = @POSTGRES_LDFLAGS@ POSUB = @POSUB@ @@ -445,6 +525,7 @@ abs_builddir = @abs_builddir@ abs_srcdir = @abs_srcdir@ abs_top_builddir = @abs_top_builddir@ abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ ac_ct_CC = @ac_ct_CC@ ac_ct_CXX = @ac_ct_CXX@ ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ @@ -467,6 +548,7 @@ datarootdir = @datarootdir@ docdir = @docdir@ dvidir = @dvidir@ exec_prefix = @exec_prefix@ +gitcommand = @gitcommand@ host = @host@ host_alias = @host_alias@ host_cpu = @host_cpu@ @@ -477,10 +559,9 @@ includedir = @includedir@ infodir = @infodir@ install_sh = @install_sh@ libdir = @libdir@ -libexecdir = @libexecdir@ +libexecdir = $(pkglibdir)/libexec/ localedir = @localedir@ localstatedir = @localstatedir@ -lt_ECHO = @lt_ECHO@ ltdl_LIBOBJS = @ltdl_LIBOBJS@ ltdl_LTLIBOBJS = @ltdl_LTLIBOBJS@ mandir = @mandir@ @@ -498,6 +579,7 @@ sbindir = @sbindir@ sharedstatedir = @sharedstatedir@ srcdir = @srcdir@ subdirs = @subdirs@ +svnversioncommand = @svnversioncommand@ sys_symbol_underscore = @sys_symbol_underscore@ sysconfdir = @sysconfdir@ target = @target@ @@ -517,9 +599,10 @@ pkgcfg_DATA = \ @MINGW_TRUE@WINFLAGS = -Wl,--no-undefined -Wl,--export-all-symbols @USE_COVERAGE_TRUE@AM_CFLAGS = --coverage -O0 @USE_COVERAGE_TRUE@XLIBS = -lgcov -@HAVE_SQLITE_TRUE@SQLITE_TESTS = \ -@HAVE_SQLITE_TRUE@ test_plugin_namestore_sqlite - +@HAVE_SQLITE_TRUE@SQLITE_PLUGIN = libgnunet_plugin_namestore_sqlite.la +@HAVE_SQLITE_TRUE@SQLITE_TESTS = test_plugin_namestore_sqlite +@HAVE_POSTGRES_TRUE@POSTGRES_TESTS = test_plugin_namestore_postgres +@HAVE_POSTGRES_TRUE@POSTGRES_PLUGIN = libgnunet_plugin_namestore_postgres.la @ENABLE_TEST_RUN_TRUE@TESTS = $(check_PROGRAMS) lib_LTLIBRARIES = \ libgnunetnamestore.la @@ -534,7 +617,7 @@ libgnunetnamestore_la_LIBADD = \ libgnunetnamestore_la_LDFLAGS = \ $(GN_LIB_LDFLAGS) $(WINFLAGS) \ - -version-info 0:0:0 + -version-info 0:1:0 gnunet_namestore_SOURCES = \ gnunet-namestore.c @@ -562,9 +645,9 @@ gnunet_service_namestore_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la \ libgnunetnamestore.la -@HAVE_SQLITE_TRUE@SQLITE_PLUGIN = libgnunet_plugin_namestore_sqlite.la plugin_LTLIBRARIES = \ - $(SQLITE_PLUGIN) + $(SQLITE_PLUGIN) \ + $(POSTGRES_PLUGIN) libgnunet_plugin_namestore_sqlite_la_SOURCES = \ plugin_namestore_sqlite.c namestore_common.c @@ -572,7 +655,8 @@ libgnunet_plugin_namestore_sqlite_la_SOURCES = \ libgnunet_plugin_namestore_sqlite_la_LIBADD = \ $(top_builddir)/src/namestore/libgnunetnamestore.la \ $(top_builddir)/src/statistics/libgnunetstatistics.la \ - $(top_builddir)/src/util/libgnunetutil.la $(XLIBS) -lsqlite3 + $(top_builddir)/src/util/libgnunetutil.la $(XLIBS) -lsqlite3 \ + $(LTLIBINTL) libgnunet_plugin_namestore_sqlite_la_LDFLAGS = \ $(GN_PLUGIN_LDFLAGS) @@ -582,17 +666,38 @@ libgnunet_plugin_namestore_sqlite_la_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la \ libgnunetnamestore.la +libgnunet_plugin_namestore_postgres_la_SOURCES = \ + plugin_namestore_postgres.c namestore_common.c + +libgnunet_plugin_namestore_postgres_la_LIBADD = \ + $(top_builddir)/src/namestore/libgnunetnamestore.la \ + $(top_builddir)/src/postgres/libgnunetpostgres.la \ + $(top_builddir)/src/statistics/libgnunetstatistics.la \ + $(top_builddir)/src/util/libgnunetutil.la $(XLIBS) -lpq \ + $(LTLIBINTL) + +libgnunet_plugin_namestore_postgres_la_LDFLAGS = \ + $(GN_PLUGIN_LDFLAGS) + +libgnunet_plugin_namestore_postgres_la_DEPENDENCIES = \ + $(top_builddir)/src/postgres/libgnunetpostgres.la \ + $(top_builddir)/src/statistics/libgnunetstatistics.la \ + $(top_builddir)/src/util/libgnunetutil.la \ + libgnunetnamestore.la + test_namestore_api_sign_verify_SOURCES = \ test_namestore_api_sign_verify.c test_namestore_api_sign_verify_LDADD = \ $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la test_namestore_api_SOURCES = \ test_namestore_api.c test_namestore_api_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la @@ -600,6 +705,7 @@ test_namestore_api_put_SOURCES = \ test_namestore_api_put.c test_namestore_api_put_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la @@ -607,6 +713,7 @@ test_namestore_api_lookup_SOURCES = \ test_namestore_api_lookup.c test_namestore_api_lookup_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la @@ -614,6 +721,7 @@ test_namestore_api_lookup_specific_type_SOURCES = \ test_namestore_api_lookup_specific_type.c test_namestore_api_lookup_specific_type_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la @@ -621,6 +729,7 @@ test_namestore_api_create_SOURCES = \ test_namestore_api_create.c test_namestore_api_create_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la @@ -628,6 +737,7 @@ test_namestore_api_create_update_SOURCES = \ test_namestore_api_create_update.c test_namestore_api_create_update_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la @@ -635,6 +745,7 @@ test_namestore_api_remove_SOURCES = \ test_namestore_api_remove.c test_namestore_api_remove_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la @@ -642,6 +753,7 @@ test_namestore_api_remove_not_existing_record_SOURCES = \ test_namestore_api_remove_not_existing_record.c test_namestore_api_remove_not_existing_record_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la @@ -649,6 +761,7 @@ test_namestore_api_zone_to_name_SOURCES = \ test_namestore_api_zone_to_name.c test_namestore_api_zone_to_name_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la @@ -656,6 +769,7 @@ test_namestore_api_zone_iteration_SOURCES = \ test_namestore_api_zone_iteration.c test_namestore_api_zone_iteration_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la @@ -663,6 +777,7 @@ test_namestore_api_zone_iteration_specific_zone_SOURCES = \ test_namestore_api_zone_iteration_specific_zone.c test_namestore_api_zone_iteration_specific_zone_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la @@ -670,6 +785,7 @@ test_namestore_api_zone_iteration_stop_SOURCES = \ test_namestore_api_zone_iteration_stop.c test_namestore_api_zone_iteration_stop_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la @@ -677,12 +793,14 @@ test_namestore_record_serialization_SOURCES = \ test_namestore_record_serialization.c test_namestore_record_serialization_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/namestore/libgnunetnamestore.la EXTRA_DIST = \ test_namestore_api.conf \ test_plugin_namestore_sqlite.conf\ + test_plugin_namestore_postgres.conf\ test_hostkey \ zonefiles/HGU0A0VCU334DN7F2I9UIUMVQMM7JMSD142LIMNUGTTV9R0CF4EG.zkey \ zonefiles/N0UJMP015AFUNR2BTNM3FKPBLG38913BL8IDMCO2H0A1LIB81960.zkey @@ -691,6 +809,14 @@ test_plugin_namestore_sqlite_SOURCES = \ test_plugin_namestore.c test_plugin_namestore_sqlite_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/util/libgnunetutil.la + +test_plugin_namestore_postgres_SOURCES = \ + test_plugin_namestore.c + +test_plugin_namestore_postgres_LDADD = \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la all: all-am @@ -731,7 +857,6 @@ namestore.conf: $(top_builddir)/config.status $(srcdir)/namestore.conf.in cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ install-libLTLIBRARIES: $(lib_LTLIBRARIES) @$(NORMAL_INSTALL) - test -z "$(libdir)" || $(MKDIR_P) "$(DESTDIR)$(libdir)" @list='$(lib_LTLIBRARIES)'; test -n "$(libdir)" || list=; \ list2=; for p in $$list; do \ if test -f $$p; then \ @@ -739,6 +864,8 @@ install-libLTLIBRARIES: $(lib_LTLIBRARIES) else :; fi; \ done; \ test -z "$$list2" || { \ + echo " $(MKDIR_P) '$(DESTDIR)$(libdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libdir)" || exit 1; \ echo " $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 '$(DESTDIR)$(libdir)'"; \ $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 "$(DESTDIR)$(libdir)"; \ } @@ -762,7 +889,6 @@ clean-libLTLIBRARIES: done install-pluginLTLIBRARIES: $(plugin_LTLIBRARIES) @$(NORMAL_INSTALL) - test -z "$(plugindir)" || $(MKDIR_P) "$(DESTDIR)$(plugindir)" @list='$(plugin_LTLIBRARIES)'; test -n "$(plugindir)" || list=; \ list2=; for p in $$list; do \ if test -f $$p; then \ @@ -770,6 +896,8 @@ install-pluginLTLIBRARIES: $(plugin_LTLIBRARIES) else :; fi; \ done; \ test -z "$$list2" || { \ + echo " $(MKDIR_P) '$(DESTDIR)$(plugindir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(plugindir)" || exit 1; \ echo " $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 '$(DESTDIR)$(plugindir)'"; \ $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 "$(DESTDIR)$(plugindir)"; \ } @@ -791,14 +919,19 @@ clean-pluginLTLIBRARIES: echo "rm -f \"$${dir}/so_locations\""; \ rm -f "$${dir}/so_locations"; \ done -libgnunet_plugin_namestore_sqlite.la: $(libgnunet_plugin_namestore_sqlite_la_OBJECTS) $(libgnunet_plugin_namestore_sqlite_la_DEPENDENCIES) +libgnunet_plugin_namestore_postgres.la: $(libgnunet_plugin_namestore_postgres_la_OBJECTS) $(libgnunet_plugin_namestore_postgres_la_DEPENDENCIES) $(EXTRA_libgnunet_plugin_namestore_postgres_la_DEPENDENCIES) + $(AM_V_CCLD)$(libgnunet_plugin_namestore_postgres_la_LINK) $(am_libgnunet_plugin_namestore_postgres_la_rpath) $(libgnunet_plugin_namestore_postgres_la_OBJECTS) $(libgnunet_plugin_namestore_postgres_la_LIBADD) $(LIBS) +libgnunet_plugin_namestore_sqlite.la: $(libgnunet_plugin_namestore_sqlite_la_OBJECTS) $(libgnunet_plugin_namestore_sqlite_la_DEPENDENCIES) $(EXTRA_libgnunet_plugin_namestore_sqlite_la_DEPENDENCIES) $(AM_V_CCLD)$(libgnunet_plugin_namestore_sqlite_la_LINK) $(am_libgnunet_plugin_namestore_sqlite_la_rpath) $(libgnunet_plugin_namestore_sqlite_la_OBJECTS) $(libgnunet_plugin_namestore_sqlite_la_LIBADD) $(LIBS) -libgnunetnamestore.la: $(libgnunetnamestore_la_OBJECTS) $(libgnunetnamestore_la_DEPENDENCIES) +libgnunetnamestore.la: $(libgnunetnamestore_la_OBJECTS) $(libgnunetnamestore_la_DEPENDENCIES) $(EXTRA_libgnunetnamestore_la_DEPENDENCIES) $(AM_V_CCLD)$(libgnunetnamestore_la_LINK) -rpath $(libdir) $(libgnunetnamestore_la_OBJECTS) $(libgnunetnamestore_la_LIBADD) $(LIBS) install-binPROGRAMS: $(bin_PROGRAMS) @$(NORMAL_INSTALL) - test -z "$(bindir)" || $(MKDIR_P) "$(DESTDIR)$(bindir)" @list='$(bin_PROGRAMS)'; test -n "$(bindir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(bindir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(bindir)" || exit 1; \ + fi; \ for p in $$list; do echo "$$p $$p"; done | \ sed 's/$(EXEEXT)$$//' | \ while read p p1; do if test -f $$p || test -f $$p1; \ @@ -847,55 +980,104 @@ clean-checkPROGRAMS: list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ echo " rm -f" $$list; \ rm -f $$list -gnunet-namestore$(EXEEXT): $(gnunet_namestore_OBJECTS) $(gnunet_namestore_DEPENDENCIES) +install-libexecPROGRAMS: $(libexec_PROGRAMS) + @$(NORMAL_INSTALL) + @list='$(libexec_PROGRAMS)'; test -n "$(libexecdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(libexecdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libexecdir)" || exit 1; \ + fi; \ + for p in $$list; do echo "$$p $$p"; done | \ + sed 's/$(EXEEXT)$$//' | \ + while read p p1; do if test -f $$p || test -f $$p1; \ + then echo "$$p"; echo "$$p"; else :; fi; \ + done | \ + sed -e 'p;s,.*/,,;n;h' -e 's|.*|.|' \ + -e 'p;x;s,.*/,,;s/$(EXEEXT)$$//;$(transform);s/$$/$(EXEEXT)/' | \ + sed 'N;N;N;s,\n, ,g' | \ + $(AWK) 'BEGIN { files["."] = ""; dirs["."] = 1 } \ + { d=$$3; if (dirs[d] != 1) { print "d", d; dirs[d] = 1 } \ + if ($$2 == $$4) files[d] = files[d] " " $$1; \ + else { print "f", $$3 "/" $$4, $$1; } } \ + END { for (d in files) print "f", d, files[d] }' | \ + while read type dir files; do \ + if test "$$dir" = .; then dir=; else dir=/$$dir; fi; \ + test -z "$$files" || { \ + echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files '$(DESTDIR)$(libexecdir)$$dir'"; \ + $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files "$(DESTDIR)$(libexecdir)$$dir" || exit $$?; \ + } \ + ; done + +uninstall-libexecPROGRAMS: + @$(NORMAL_UNINSTALL) + @list='$(libexec_PROGRAMS)'; test -n "$(libexecdir)" || list=; \ + files=`for p in $$list; do echo "$$p"; done | \ + sed -e 'h;s,^.*/,,;s/$(EXEEXT)$$//;$(transform)' \ + -e 's/$$/$(EXEEXT)/' `; \ + test -n "$$list" || exit 0; \ + echo " ( cd '$(DESTDIR)$(libexecdir)' && rm -f" $$files ")"; \ + cd "$(DESTDIR)$(libexecdir)" && rm -f $$files + +clean-libexecPROGRAMS: + @list='$(libexec_PROGRAMS)'; test -n "$$list" || exit 0; \ + echo " rm -f" $$list; \ + rm -f $$list || exit $$?; \ + test -n "$(EXEEXT)" || exit 0; \ + list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ + echo " rm -f" $$list; \ + rm -f $$list +gnunet-namestore$(EXEEXT): $(gnunet_namestore_OBJECTS) $(gnunet_namestore_DEPENDENCIES) $(EXTRA_gnunet_namestore_DEPENDENCIES) @rm -f gnunet-namestore$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_namestore_OBJECTS) $(gnunet_namestore_LDADD) $(LIBS) -gnunet-service-namestore$(EXEEXT): $(gnunet_service_namestore_OBJECTS) $(gnunet_service_namestore_DEPENDENCIES) +gnunet-service-namestore$(EXEEXT): $(gnunet_service_namestore_OBJECTS) $(gnunet_service_namestore_DEPENDENCIES) $(EXTRA_gnunet_service_namestore_DEPENDENCIES) @rm -f gnunet-service-namestore$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_service_namestore_OBJECTS) $(gnunet_service_namestore_LDADD) $(LIBS) -test_namestore_api$(EXEEXT): $(test_namestore_api_OBJECTS) $(test_namestore_api_DEPENDENCIES) +test_namestore_api$(EXEEXT): $(test_namestore_api_OBJECTS) $(test_namestore_api_DEPENDENCIES) $(EXTRA_test_namestore_api_DEPENDENCIES) @rm -f test_namestore_api$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_namestore_api_OBJECTS) $(test_namestore_api_LDADD) $(LIBS) -test_namestore_api_create$(EXEEXT): $(test_namestore_api_create_OBJECTS) $(test_namestore_api_create_DEPENDENCIES) +test_namestore_api_create$(EXEEXT): $(test_namestore_api_create_OBJECTS) $(test_namestore_api_create_DEPENDENCIES) $(EXTRA_test_namestore_api_create_DEPENDENCIES) @rm -f test_namestore_api_create$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_namestore_api_create_OBJECTS) $(test_namestore_api_create_LDADD) $(LIBS) -test_namestore_api_create_update$(EXEEXT): $(test_namestore_api_create_update_OBJECTS) $(test_namestore_api_create_update_DEPENDENCIES) +test_namestore_api_create_update$(EXEEXT): $(test_namestore_api_create_update_OBJECTS) $(test_namestore_api_create_update_DEPENDENCIES) $(EXTRA_test_namestore_api_create_update_DEPENDENCIES) @rm -f test_namestore_api_create_update$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_namestore_api_create_update_OBJECTS) $(test_namestore_api_create_update_LDADD) $(LIBS) -test_namestore_api_lookup$(EXEEXT): $(test_namestore_api_lookup_OBJECTS) $(test_namestore_api_lookup_DEPENDENCIES) +test_namestore_api_lookup$(EXEEXT): $(test_namestore_api_lookup_OBJECTS) $(test_namestore_api_lookup_DEPENDENCIES) $(EXTRA_test_namestore_api_lookup_DEPENDENCIES) @rm -f test_namestore_api_lookup$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_namestore_api_lookup_OBJECTS) $(test_namestore_api_lookup_LDADD) $(LIBS) -test_namestore_api_lookup_specific_type$(EXEEXT): $(test_namestore_api_lookup_specific_type_OBJECTS) $(test_namestore_api_lookup_specific_type_DEPENDENCIES) +test_namestore_api_lookup_specific_type$(EXEEXT): $(test_namestore_api_lookup_specific_type_OBJECTS) $(test_namestore_api_lookup_specific_type_DEPENDENCIES) $(EXTRA_test_namestore_api_lookup_specific_type_DEPENDENCIES) @rm -f test_namestore_api_lookup_specific_type$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_namestore_api_lookup_specific_type_OBJECTS) $(test_namestore_api_lookup_specific_type_LDADD) $(LIBS) -test_namestore_api_put$(EXEEXT): $(test_namestore_api_put_OBJECTS) $(test_namestore_api_put_DEPENDENCIES) +test_namestore_api_put$(EXEEXT): $(test_namestore_api_put_OBJECTS) $(test_namestore_api_put_DEPENDENCIES) $(EXTRA_test_namestore_api_put_DEPENDENCIES) @rm -f test_namestore_api_put$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_namestore_api_put_OBJECTS) $(test_namestore_api_put_LDADD) $(LIBS) -test_namestore_api_remove$(EXEEXT): $(test_namestore_api_remove_OBJECTS) $(test_namestore_api_remove_DEPENDENCIES) +test_namestore_api_remove$(EXEEXT): $(test_namestore_api_remove_OBJECTS) $(test_namestore_api_remove_DEPENDENCIES) $(EXTRA_test_namestore_api_remove_DEPENDENCIES) @rm -f test_namestore_api_remove$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_namestore_api_remove_OBJECTS) $(test_namestore_api_remove_LDADD) $(LIBS) -test_namestore_api_remove_not_existing_record$(EXEEXT): $(test_namestore_api_remove_not_existing_record_OBJECTS) $(test_namestore_api_remove_not_existing_record_DEPENDENCIES) +test_namestore_api_remove_not_existing_record$(EXEEXT): $(test_namestore_api_remove_not_existing_record_OBJECTS) $(test_namestore_api_remove_not_existing_record_DEPENDENCIES) $(EXTRA_test_namestore_api_remove_not_existing_record_DEPENDENCIES) @rm -f test_namestore_api_remove_not_existing_record$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_namestore_api_remove_not_existing_record_OBJECTS) $(test_namestore_api_remove_not_existing_record_LDADD) $(LIBS) -test_namestore_api_sign_verify$(EXEEXT): $(test_namestore_api_sign_verify_OBJECTS) $(test_namestore_api_sign_verify_DEPENDENCIES) +test_namestore_api_sign_verify$(EXEEXT): $(test_namestore_api_sign_verify_OBJECTS) $(test_namestore_api_sign_verify_DEPENDENCIES) $(EXTRA_test_namestore_api_sign_verify_DEPENDENCIES) @rm -f test_namestore_api_sign_verify$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_namestore_api_sign_verify_OBJECTS) $(test_namestore_api_sign_verify_LDADD) $(LIBS) -test_namestore_api_zone_iteration$(EXEEXT): $(test_namestore_api_zone_iteration_OBJECTS) $(test_namestore_api_zone_iteration_DEPENDENCIES) +test_namestore_api_zone_iteration$(EXEEXT): $(test_namestore_api_zone_iteration_OBJECTS) $(test_namestore_api_zone_iteration_DEPENDENCIES) $(EXTRA_test_namestore_api_zone_iteration_DEPENDENCIES) @rm -f test_namestore_api_zone_iteration$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_namestore_api_zone_iteration_OBJECTS) $(test_namestore_api_zone_iteration_LDADD) $(LIBS) -test_namestore_api_zone_iteration_specific_zone$(EXEEXT): $(test_namestore_api_zone_iteration_specific_zone_OBJECTS) $(test_namestore_api_zone_iteration_specific_zone_DEPENDENCIES) +test_namestore_api_zone_iteration_specific_zone$(EXEEXT): $(test_namestore_api_zone_iteration_specific_zone_OBJECTS) $(test_namestore_api_zone_iteration_specific_zone_DEPENDENCIES) $(EXTRA_test_namestore_api_zone_iteration_specific_zone_DEPENDENCIES) @rm -f test_namestore_api_zone_iteration_specific_zone$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_namestore_api_zone_iteration_specific_zone_OBJECTS) $(test_namestore_api_zone_iteration_specific_zone_LDADD) $(LIBS) -test_namestore_api_zone_iteration_stop$(EXEEXT): $(test_namestore_api_zone_iteration_stop_OBJECTS) $(test_namestore_api_zone_iteration_stop_DEPENDENCIES) +test_namestore_api_zone_iteration_stop$(EXEEXT): $(test_namestore_api_zone_iteration_stop_OBJECTS) $(test_namestore_api_zone_iteration_stop_DEPENDENCIES) $(EXTRA_test_namestore_api_zone_iteration_stop_DEPENDENCIES) @rm -f test_namestore_api_zone_iteration_stop$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_namestore_api_zone_iteration_stop_OBJECTS) $(test_namestore_api_zone_iteration_stop_LDADD) $(LIBS) -test_namestore_api_zone_to_name$(EXEEXT): $(test_namestore_api_zone_to_name_OBJECTS) $(test_namestore_api_zone_to_name_DEPENDENCIES) +test_namestore_api_zone_to_name$(EXEEXT): $(test_namestore_api_zone_to_name_OBJECTS) $(test_namestore_api_zone_to_name_DEPENDENCIES) $(EXTRA_test_namestore_api_zone_to_name_DEPENDENCIES) @rm -f test_namestore_api_zone_to_name$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_namestore_api_zone_to_name_OBJECTS) $(test_namestore_api_zone_to_name_LDADD) $(LIBS) -test_namestore_record_serialization$(EXEEXT): $(test_namestore_record_serialization_OBJECTS) $(test_namestore_record_serialization_DEPENDENCIES) +test_namestore_record_serialization$(EXEEXT): $(test_namestore_record_serialization_OBJECTS) $(test_namestore_record_serialization_DEPENDENCIES) $(EXTRA_test_namestore_record_serialization_DEPENDENCIES) @rm -f test_namestore_record_serialization$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_namestore_record_serialization_OBJECTS) $(test_namestore_record_serialization_LDADD) $(LIBS) -test_plugin_namestore_sqlite$(EXEEXT): $(test_plugin_namestore_sqlite_OBJECTS) $(test_plugin_namestore_sqlite_DEPENDENCIES) +test_plugin_namestore_postgres$(EXEEXT): $(test_plugin_namestore_postgres_OBJECTS) $(test_plugin_namestore_postgres_DEPENDENCIES) $(EXTRA_test_plugin_namestore_postgres_DEPENDENCIES) + @rm -f test_plugin_namestore_postgres$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_plugin_namestore_postgres_OBJECTS) $(test_plugin_namestore_postgres_LDADD) $(LIBS) +test_plugin_namestore_sqlite$(EXEEXT): $(test_plugin_namestore_sqlite_OBJECTS) $(test_plugin_namestore_sqlite_DEPENDENCIES) $(EXTRA_test_plugin_namestore_sqlite_DEPENDENCIES) @rm -f test_plugin_namestore_sqlite$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_plugin_namestore_sqlite_OBJECTS) $(test_plugin_namestore_sqlite_LDADD) $(LIBS) @@ -909,6 +1091,7 @@ distclean-compile: @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-service-namestore.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/namestore_api.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/namestore_common.Plo@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/plugin_namestore_postgres.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/plugin_namestore_sqlite.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_namestore_api.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_namestore_api_create.Po@am__quote@ @@ -929,26 +1112,23 @@ distclean-compile: .c.o: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c $< .c.obj: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'` @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c `$(CYGPATH_W) '$<'` +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c `$(CYGPATH_W) '$<'` .c.lo: @am__fastdepCC_TRUE@ $(AM_V_CC)$(LTCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LTCOMPILE) -c -o $@ $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LTCOMPILE) -c -o $@ $< mostlyclean-libtool: -rm -f *.lo @@ -957,8 +1137,11 @@ clean-libtool: -rm -rf .libs _libs install-pkgcfgDATA: $(pkgcfg_DATA) @$(NORMAL_INSTALL) - test -z "$(pkgcfgdir)" || $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" @list='$(pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(pkgcfgdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" || exit 1; \ + fi; \ for p in $$list; do \ if test -f "$$p"; then d=; else d="$(srcdir)/"; fi; \ echo "$$d$$p"; \ @@ -972,9 +1155,7 @@ uninstall-pkgcfgDATA: @$(NORMAL_UNINSTALL) @list='$(pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ files=`for p in $$list; do echo $$p; done | sed -e 's|^.*/||'`; \ - test -n "$$files" || exit 0; \ - echo " ( cd '$(DESTDIR)$(pkgcfgdir)' && rm -f" $$files ")"; \ - cd "$(DESTDIR)$(pkgcfgdir)" && rm -f $$files + dir='$(DESTDIR)$(pkgcfgdir)'; $(am__uninstall_files_from_dir) ID: $(HEADERS) $(SOURCES) $(LISP) $(TAGS_FILES) list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ @@ -1109,14 +1290,15 @@ check-TESTS: $(TESTS) fi; \ dashes=`echo "$$dashes" | sed s/./=/g`; \ if test "$$failed" -eq 0; then \ - echo "$$grn$$dashes"; \ + col="$$grn"; \ else \ - echo "$$red$$dashes"; \ + col="$$red"; \ fi; \ - echo "$$banner"; \ - test -z "$$skipped" || echo "$$skipped"; \ - test -z "$$report" || echo "$$report"; \ - echo "$$dashes$$std"; \ + echo "$${col}$$dashes$${std}"; \ + echo "$${col}$$banner$${std}"; \ + test -z "$$skipped" || echo "$${col}$$skipped$${std}"; \ + test -z "$$report" || echo "$${col}$$report$${std}"; \ + echo "$${col}$$dashes$${std}"; \ test "$$failed" -eq 0; \ else :; fi @@ -1158,7 +1340,7 @@ all-am: Makefile $(LTLIBRARIES) $(PROGRAMS) $(DATA) install-binPROGRAMS: install-libLTLIBRARIES installdirs: - for dir in "$(DESTDIR)$(libdir)" "$(DESTDIR)$(plugindir)" "$(DESTDIR)$(bindir)" "$(DESTDIR)$(pkgcfgdir)"; do \ + for dir in "$(DESTDIR)$(libdir)" "$(DESTDIR)$(plugindir)" "$(DESTDIR)$(bindir)" "$(DESTDIR)$(libexecdir)" "$(DESTDIR)$(pkgcfgdir)"; do \ test -z "$$dir" || $(MKDIR_P) "$$dir"; \ done install: install-am @@ -1171,10 +1353,15 @@ install-am: all-am installcheck: installcheck-am install-strip: - $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ - install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ - `test -z '$(STRIP)' || \ - echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi mostlyclean-generic: clean-generic: @@ -1189,8 +1376,8 @@ maintainer-clean-generic: clean: clean-am clean-am: clean-binPROGRAMS clean-checkPROGRAMS clean-generic \ - clean-libLTLIBRARIES clean-libtool clean-pluginLTLIBRARIES \ - mostlyclean-am + clean-libLTLIBRARIES clean-libexecPROGRAMS clean-libtool \ + clean-pluginLTLIBRARIES mostlyclean-am distclean: distclean-am -rm -rf ./$(DEPDIR) @@ -1216,7 +1403,8 @@ install-dvi: install-dvi-am install-dvi-am: -install-exec-am: install-binPROGRAMS install-libLTLIBRARIES +install-exec-am: install-binPROGRAMS install-libLTLIBRARIES \ + install-libexecPROGRAMS install-html: install-html-am @@ -1257,27 +1445,30 @@ ps: ps-am ps-am: uninstall-am: uninstall-binPROGRAMS uninstall-libLTLIBRARIES \ - uninstall-pkgcfgDATA uninstall-pluginLTLIBRARIES + uninstall-libexecPROGRAMS uninstall-pkgcfgDATA \ + uninstall-pluginLTLIBRARIES .MAKE: check-am install-am install-strip .PHONY: CTAGS GTAGS all all-am check check-TESTS check-am clean \ clean-binPROGRAMS clean-checkPROGRAMS clean-generic \ - clean-libLTLIBRARIES clean-libtool clean-pluginLTLIBRARIES \ - ctags distclean distclean-compile distclean-generic \ - distclean-libtool distclean-tags distdir dvi dvi-am html \ - html-am info info-am install install-am install-binPROGRAMS \ - install-data install-data-am install-dvi install-dvi-am \ - install-exec install-exec-am install-html install-html-am \ - install-info install-info-am install-libLTLIBRARIES \ - install-man install-pdf install-pdf-am install-pkgcfgDATA \ + clean-libLTLIBRARIES clean-libexecPROGRAMS clean-libtool \ + clean-pluginLTLIBRARIES ctags distclean distclean-compile \ + distclean-generic distclean-libtool distclean-tags distdir dvi \ + dvi-am html html-am info info-am install install-am \ + install-binPROGRAMS install-data install-data-am install-dvi \ + install-dvi-am install-exec install-exec-am install-html \ + install-html-am install-info install-info-am \ + install-libLTLIBRARIES install-libexecPROGRAMS install-man \ + install-pdf install-pdf-am install-pkgcfgDATA \ install-pluginLTLIBRARIES install-ps install-ps-am \ install-strip installcheck installcheck-am installdirs \ maintainer-clean maintainer-clean-generic mostlyclean \ mostlyclean-compile mostlyclean-generic mostlyclean-libtool \ pdf pdf-am ps ps-am tags uninstall uninstall-am \ uninstall-binPROGRAMS uninstall-libLTLIBRARIES \ - uninstall-pkgcfgDATA uninstall-pluginLTLIBRARIES + uninstall-libexecPROGRAMS uninstall-pkgcfgDATA \ + uninstall-pluginLTLIBRARIES # Tell versions [3.59,3.63) of GNU make to not export all variables. diff --git a/src/namestore/gnunet-namestore.c b/src/namestore/gnunet-namestore.c index a0d1de1..a79ec5e 100644 --- a/src/namestore/gnunet-namestore.c +++ b/src/namestore/gnunet-namestore.c @@ -32,6 +32,12 @@ #include #include + +/** + * Hostkey generation context + */ +struct GNUNET_CRYPTO_RsaKeyGenerationContext * keygen; + /** * Handle to the namestore. */ @@ -62,6 +68,11 @@ static int add; */ static struct GNUNET_NAMESTORE_QueueEntry *add_qe; +/** + * Queue entry for the 'add-uri' operation. + */ +static struct GNUNET_NAMESTORE_QueueEntry *add_qe_uri; + /** * Desired action is to list records. */ @@ -102,6 +113,11 @@ static char *name; */ static char *value; +/** + * URI to import. + */ +static char *uri; + /** * Type of the record to add/remove, NULL to remove all. */ @@ -112,6 +128,11 @@ static char *typestring; */ static char *expirationstring; +/** + * Global return value + */ +static int ret; + /** * Task run on shutdown. Cleans up everything. @@ -123,9 +144,35 @@ static void do_shutdown (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { + if (NULL != keygen) + { + GNUNET_CRYPTO_rsa_key_create_stop (keygen); + keygen = NULL; + } + + if (NULL != list_it) + { + GNUNET_NAMESTORE_zone_iteration_stop (list_it); + list_it = NULL; + } + if (NULL != add_qe) + { + GNUNET_NAMESTORE_cancel (add_qe); + add_qe = NULL; + } + if (NULL != add_qe_uri) + { + GNUNET_NAMESTORE_cancel (add_qe_uri); + add_qe_uri = NULL; + } + if (NULL != del_qe) + { + GNUNET_NAMESTORE_cancel (del_qe); + del_qe = NULL; + } if (NULL != ns) { - GNUNET_NAMESTORE_disconnect (ns, GNUNET_NO); + GNUNET_NAMESTORE_disconnect (ns); ns = NULL; } if (NULL != zone_pkey) @@ -133,6 +180,11 @@ do_shutdown (void *cls, GNUNET_CRYPTO_rsa_key_free (zone_pkey); zone_pkey = NULL; } + if (NULL != uri) + { + GNUNET_free (uri); + uri = NULL; + } } @@ -140,7 +192,7 @@ do_shutdown (void *cls, * Continuation called to notify client about result of the * operation. * - * @param cls closure, unused + * @param cls closure, location of the QueueEntry pointer to NULL out * @param success GNUNET_SYSERR on failure (including timeout/queue drop/failure to validate) * GNUNET_NO if content was already there * GNUNET_YES (or other positive value) on success @@ -151,12 +203,20 @@ add_continuation (void *cls, int32_t success, const char *emsg) { - add_qe = NULL; - if (success != GNUNET_YES) + struct GNUNET_NAMESTORE_QueueEntry **qe = cls; + + *qe = NULL; + if (GNUNET_YES != success) + { fprintf (stderr, _("Adding record failed: %s\n"), - (success == GNUNET_NO) ? "record exists" : emsg); - if ( (NULL == del_qe) && + (GNUNET_NO == success) ? "record exists" : emsg); + if (GNUNET_NO != success) + ret = 1; + } + if ( (NULL == add_qe) && + (NULL == add_qe_uri) && + (NULL == del_qe) && (NULL == list_it) ) GNUNET_SCHEDULER_shutdown (); } @@ -183,6 +243,7 @@ del_continuation (void *cls, _("Deleting record failed: %s\n"), emsg); if ( (NULL == add_qe) && + (NULL == add_qe_uri) && (NULL == list_it) ) GNUNET_SCHEDULER_shutdown (); } @@ -216,11 +277,15 @@ display_record (void *cls, const char *typestring; char *s; unsigned int i; + const char *etime; + struct GNUNET_TIME_Absolute aex; + struct GNUNET_TIME_Relative rex; if (NULL == name) { list_it = NULL; if ( (NULL == del_qe) && + (NULL == add_qe_uri) && (NULL == add_qe) ) GNUNET_SCHEDULER_shutdown (); return; @@ -240,51 +305,51 @@ display_record (void *cls, (unsigned int) rd[i].record_type); continue; } - FPRINTF (stdout, "\t%s: %s\n", typestring, s); + if (0 != (rd[i].flags & GNUNET_NAMESTORE_RF_RELATIVE_EXPIRATION)) + { + rex.rel_value = rd[i].expiration_time; + etime = GNUNET_STRINGS_relative_time_to_string (rex, GNUNET_YES); + } + else + { + aex.abs_value = rd[i].expiration_time; + etime = GNUNET_STRINGS_absolute_time_to_string (aex); + } + FPRINTF (stdout, "\t%s: %s (%s %s)\n", typestring, s, + (0 != (rd[i].flags & GNUNET_NAMESTORE_RF_RELATIVE_EXPIRATION)) + ? _(/* what follows is relative expiration */ "for at least") + : _(/* what follows is absolute expiration */ "until"), + etime); GNUNET_free (s); } FPRINTF (stdout, "%s", "\n"); GNUNET_NAMESTORE_zone_iterator_next (list_it); } - -/** - * Main function that will be run. - * - * @param cls closure - * @param args remaining command-line arguments - * @param cfgfile name of the configuration file used (for saving, can be NULL!) - * @param cfg configuration - */ static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) +key_generation_cb (void *cls, + struct GNUNET_CRYPTO_RsaPrivateKey *pk, + const char *emsg) { + struct GNUNET_CONFIGURATION_Handle *cfg = cls; struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded pub; uint32_t type; void *data = NULL; size_t data_size = 0; - struct GNUNET_TIME_Relative etime; + struct GNUNET_TIME_Relative etime_rel; + struct GNUNET_TIME_Absolute etime_abs; + int etime_is_rel = GNUNET_SYSERR; struct GNUNET_NAMESTORE_RecordData rd; - if (NULL == keyfile) + keygen = NULL; + if (NULL == pk) { - if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_filename (cfg, "gns", - "ZONEKEY", &keyfile)) - { - fprintf (stderr, - _("Option `%s' not given, but I need a zone key file!\n"), - "z"); - return; - } - fprintf (stderr, - _("Using default zone file `%s'\n"), - keyfile); + GNUNET_SCHEDULER_shutdown (); + return; } - zone_pkey = GNUNET_CRYPTO_rsa_key_create_from_file (keyfile); - GNUNET_free (keyfile); - keyfile = NULL; - if (! (add|del|list)) + zone_pkey = pk; + + if (! (add|del|list|(NULL != uri))) { /* nothing more to be done */ fprintf (stderr, @@ -296,22 +361,22 @@ run (void *cls, char *const *args, const char *cfgfile, if (NULL == zone_pkey) { GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - _("Failed to read or create private zone key\n")); + _("Failed to read or create private zone key\n")); return; } GNUNET_CRYPTO_rsa_key_get_public (zone_pkey, - &pub); + &pub); GNUNET_CRYPTO_short_hash (&pub, sizeof (pub), &zone); ns = GNUNET_NAMESTORE_connect (cfg); if (NULL == ns) { GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - _("Failed to connect to namestore\n")); + _("Failed to connect to namestore\n")); return; } GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, - &do_shutdown, NULL); + &do_shutdown, NULL); if (NULL == typestring) type = 0; else @@ -320,35 +385,39 @@ run (void *cls, char *const *args, const char *cfgfile, { fprintf (stderr, _("Unsupported type `%s'\n"), typestring); GNUNET_SCHEDULER_shutdown (); + ret = 1; return; } if ((NULL == typestring) && (add | del)) { fprintf (stderr, - _("Missing option `%s' for operation `%s'\n"), - "-t", _("add/del")); + _("Missing option `%s' for operation `%s'\n"), + "-t", _("add/del")); GNUNET_SCHEDULER_shutdown (); + ret = 1; return; } if (NULL != value) { if (GNUNET_OK != - GNUNET_NAMESTORE_string_to_value (type, - value, - &data, - &data_size)) + GNUNET_NAMESTORE_string_to_value (type, + value, + &data, + &data_size)) { - fprintf (stderr, _("Value `%s' invalid for record type `%s'\n"), - value, - typestring); - GNUNET_SCHEDULER_shutdown (); - return; + fprintf (stderr, _("Value `%s' invalid for record type `%s'\n"), + value, + typestring); + GNUNET_SCHEDULER_shutdown (); + ret = 1; + return; } } else if (add | del) { fprintf (stderr, - _("Missing option `%s' for operation `%s'\n"), - "-V", _("add/del")); + _("Missing option `%s' for operation `%s'\n"), + "-V", _("add/del")); + ret = 1; GNUNET_SCHEDULER_shutdown (); return; } @@ -356,72 +425,115 @@ run (void *cls, char *const *args, const char *cfgfile, { if (0 == strcmp (expirationstring, "never")) { - etime = GNUNET_TIME_UNIT_FOREVER_REL; + etime_abs = GNUNET_TIME_UNIT_FOREVER_ABS; + etime_is_rel = GNUNET_NO; + } + else if (GNUNET_OK == + GNUNET_STRINGS_fancy_time_to_relative (expirationstring, + &etime_rel)) + { + etime_is_rel = GNUNET_YES; + } + else if (GNUNET_OK == + GNUNET_STRINGS_fancy_time_to_absolute (expirationstring, + &etime_abs)) + { + etime_is_rel = GNUNET_NO; } - else if (GNUNET_OK != - GNUNET_STRINGS_fancy_time_to_relative (expirationstring, - &etime)) + else { fprintf (stderr, - _("Invalid time format `%s'\n"), - expirationstring); + _("Invalid time format `%s'\n"), + expirationstring); GNUNET_SCHEDULER_shutdown (); + ret = 1; return; } - } else if (add) + if (etime_is_rel && del) + { + fprintf (stderr, + _("Deletion requires either absolute time, or no time at all. Got relative time `%s' instead.\n"), + expirationstring); + GNUNET_SCHEDULER_shutdown (); + ret = 1; + return; + } + } + else if (add) { fprintf (stderr, - _("Missing option `%s' for operation `%s'\n"), - "-e", _("add")); + _("Missing option `%s' for operation `%s'\n"), + "-e", _("add")); GNUNET_SCHEDULER_shutdown (); + ret = 1; return; } + memset (&rd, 0, sizeof (rd)); if (add) { if (NULL == name) { fprintf (stderr, - _("Missing option `%s' for operation `%s'\n"), - "-n", _("add")); + _("Missing option `%s' for operation `%s'\n"), + "-n", _("add")); GNUNET_SCHEDULER_shutdown (); + ret = 1; return; } rd.data = data; rd.data_size = data_size; rd.record_type = type; - rd.expiration = GNUNET_TIME_relative_to_absolute (etime); + if (GNUNET_YES == etime_is_rel) + { + rd.expiration_time = etime_rel.rel_value; + rd.flags |= GNUNET_NAMESTORE_RF_RELATIVE_EXPIRATION; + } + else if (GNUNET_NO == etime_is_rel) + rd.expiration_time = etime_abs.abs_value; + else + { + fprintf (stderr, + _("No valid expiration time for operation `%s'\n"), + _("add")); + GNUNET_SCHEDULER_shutdown (); + ret = 1; + return; + } if (1 != nonauthority) rd.flags |= GNUNET_NAMESTORE_RF_AUTHORITY; if (1 != public) rd.flags |= GNUNET_NAMESTORE_RF_PRIVATE; add_qe = GNUNET_NAMESTORE_record_create (ns, - zone_pkey, - name, - &rd, - &add_continuation, - NULL); + zone_pkey, + name, + &rd, + &add_continuation, + &add_qe); } if (del) { if (NULL == name) { fprintf (stderr, - _("Missing option `%s' for operation `%s'\n"), - "-n", _("del")); + _("Missing option `%s' for operation `%s'\n"), + "-n", _("del")); GNUNET_SCHEDULER_shutdown (); + ret = 1; return; } rd.data = data; rd.data_size = data_size; rd.record_type = type; - rd.expiration.abs_value = 0; + rd.expiration_time = 0; + if (!etime_is_rel) + rd.expiration_time = etime_abs.abs_value; rd.flags = GNUNET_NAMESTORE_RF_AUTHORITY; del_qe = GNUNET_NAMESTORE_record_remove (ns, - zone_pkey, - name, - &rd, - &del_continuation, - NULL); + zone_pkey, + name, + &rd, + &del_continuation, + NULL); } if (list) { @@ -434,13 +546,116 @@ run (void *cls, char *const *args, const char *cfgfile, must_not_flags |= GNUNET_NAMESTORE_RF_PRIVATE; list_it = GNUNET_NAMESTORE_zone_iteration_start (ns, - &zone, - 0, - must_not_flags, - &display_record, - NULL); + &zone, + GNUNET_NAMESTORE_RF_RELATIVE_EXPIRATION, + must_not_flags, + &display_record, + NULL); + } + if (NULL != uri) + { + char sh[53]; + char name[64]; + struct GNUNET_CRYPTO_ShortHashCode sc; + + if ( (2 != (sscanf (uri, + "gnunet://gns/%52s/%63s", + sh, + name)) ) || + (GNUNET_OK != + GNUNET_CRYPTO_short_hash_from_string (sh, &sc)) ) + { + fprintf (stderr, + _("Invalid URI `%s'\n"), + uri); + GNUNET_SCHEDULER_shutdown (); + ret = 1; + return; + } + rd.data = ≻ + rd.data_size = sizeof (struct GNUNET_CRYPTO_ShortHashCode); + rd.record_type = GNUNET_NAMESTORE_TYPE_PKEY; + if (GNUNET_YES == etime_is_rel) + { + rd.expiration_time = etime_rel.rel_value; + rd.flags |= GNUNET_NAMESTORE_RF_RELATIVE_EXPIRATION; + } + else if (GNUNET_NO == etime_is_rel) + rd.expiration_time = etime_abs.abs_value; + else + rd.expiration_time = GNUNET_TIME_UNIT_FOREVER_ABS.abs_value; + if (1 != nonauthority) + rd.flags |= GNUNET_NAMESTORE_RF_AUTHORITY; + + add_qe_uri = GNUNET_NAMESTORE_record_create (ns, + zone_pkey, + name, + &rd, + &add_continuation, + &add_qe_uri); } GNUNET_free_non_null (data); + +} + + +static void +testservice_task (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct GNUNET_CONFIGURATION_Handle *cfg = cls; + + if (0 != (tc->reason & GNUNET_SCHEDULER_REASON_TIMEOUT)) + { + FPRINTF (stderr, _("Service `%s' is not running\n"), "namestore"); + return; + } + + + if (NULL == keyfile) + { + if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_filename (cfg, "gns", + "ZONEKEY", &keyfile)) + { + GNUNET_log_config_missing (GNUNET_ERROR_TYPE_ERROR, + "gns", "ZONEKEY"); + return; + } + fprintf (stderr, + _("Using default zone file `%s'\n"), + keyfile); + } + keygen = GNUNET_CRYPTO_rsa_key_create_start (keyfile, key_generation_cb, cfg); + GNUNET_free (keyfile); + keyfile = NULL; + if (NULL == keygen) + { + GNUNET_SCHEDULER_shutdown (); + ret = 1; + } +} + + +/** + * Main function that will be run. + * + * @param cls closure + * @param args remaining command-line arguments + * @param cfgfile name of the configuration file used (for saving, can be NULL!) + * @param cfg configuration + */ +static void +run (void *cls, char *const *args, const char *cfgfile, + const struct GNUNET_CONFIGURATION_Handle *cfg) +{ + + if ( (NULL != args[0]) && (NULL == uri) ) + uri = GNUNET_strdup (args[0]); + + GNUNET_CLIENT_service_test ("namestore", cfg, + GNUNET_TIME_UNIT_SECONDS, + &testservice_task, + (void *) cfg); } @@ -476,6 +691,9 @@ main (int argc, char *const *argv) {'t', "type", "TYPE", gettext_noop ("type of the record to add/delete/display"), 1, &GNUNET_GETOPT_set_string, &typestring}, + {'u', "uri", "URI", + gettext_noop ("URI to import into our zone"), 1, + &GNUNET_GETOPT_set_string, &uri}, {'V', "value", "VALUE", gettext_noop ("value of the record to add/delete"), 1, &GNUNET_GETOPT_set_string, &value}, @@ -491,16 +709,20 @@ main (int argc, char *const *argv) GNUNET_GETOPT_OPTION_END }; - int ret; + if (GNUNET_OK != GNUNET_STRINGS_get_utf8_args (argc, argv, &argc, &argv)) + return 2; GNUNET_log_setup ("gnunet-namestore", "WARNING", NULL); - ret = - (GNUNET_OK == - GNUNET_PROGRAM_run (argc, argv, "gnunet-namestore", - _("GNUnet zone manipulation tool"), - options, - &run, NULL)) ? 0 : 1; - + if (GNUNET_OK != + GNUNET_PROGRAM_run (argc, argv, "gnunet-namestore", + _("GNUnet zone manipulation tool"), + options, + &run, NULL)) + { + GNUNET_free ((void*) argv); + return 1; + } + GNUNET_free ((void*) argv); return ret; } diff --git a/src/namestore/gnunet-service-namestore.c b/src/namestore/gnunet-service-namestore.c index d6c2998..a14ad92 100644 --- a/src/namestore/gnunet-service-namestore.c +++ b/src/namestore/gnunet-service-namestore.c @@ -1,6 +1,6 @@ /* This file is part of GNUnet. - (C) 2009 Christian Grothoff (and other contributing authors) + (C) 2012 Christian Grothoff (and other contributing authors) GNUnet is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published @@ -24,8 +24,8 @@ * @author Matthias Wachs */ #include "platform.h" -#include "gnunet_getopt_lib.h" -#include "gnunet_service_lib.h" +#include "gnunet_util_lib.h" +#include "gnunet_dnsparser_lib.h" #include "gnunet_namestore_service.h" #include "gnunet_namestore_plugin.h" #include "gnunet_signatures.h" @@ -38,16 +38,45 @@ */ struct GNUNET_NAMESTORE_ZoneIteration { + /** + * Next element in the DLL + */ struct GNUNET_NAMESTORE_ZoneIteration *next; + + /** + * Previous element in the DLL + */ struct GNUNET_NAMESTORE_ZoneIteration *prev; - struct GNUNET_NAMESTORE_Client * client; + /** + * Namestore client which intiated this zone iteration + */ + struct GNUNET_NAMESTORE_Client *client; + /** + * GNUNET_YES if we iterate over a specific zone + * GNUNET_NO if we iterate over all zones + */ int has_zone; + /** + * Hash of the specific zone if 'has_zone' is GNUNET_YES, + * othwerwise set to '\0' + */ struct GNUNET_CRYPTO_ShortHashCode zone; + /** + * The operation id fot the zone iteration in the response for the client + */ uint64_t request_id; + + /** + * Offset of the zone iteration used to address next result of the zone + * iteration in the store + * + * Initialy set to 0 in handle_iteration_start + * Incremented with by every call to handle_iteration_next + */ uint32_t offset; /** @@ -67,175 +96,300 @@ struct GNUNET_NAMESTORE_ZoneIteration */ struct GNUNET_NAMESTORE_Client { + /** + * Next element in the DLL + */ struct GNUNET_NAMESTORE_Client *next; + + /** + * Previous element in the DLL + */ struct GNUNET_NAMESTORE_Client *prev; - struct GNUNET_SERVER_Client * client; + /** + * The client + */ + struct GNUNET_SERVER_Client *client; + /** + * Head of the DLL of + * Zone iteration operations in progress initiated by this client + */ struct GNUNET_NAMESTORE_ZoneIteration *op_head; + + /** + * Tail of the DLL of + * Zone iteration operations in progress initiated by this client + */ struct GNUNET_NAMESTORE_ZoneIteration *op_tail; }; + +/** + * A container struct to store information belonging to a zone crypto key pair + */ struct GNUNET_NAMESTORE_CryptoContainer { - char * filename; + /** + * Filename where to store the container + */ + char *filename; + /** + * Short hash of the zone's public key + */ struct GNUNET_CRYPTO_ShortHashCode zone; + + /** + * Zone's private key + */ struct GNUNET_CRYPTO_RsaPrivateKey *privkey; - struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *pubkey; + }; /** -* Configuration handle. -*/ -const struct GNUNET_CONFIGURATION_Handle *GSN_cfg; + * Configuration handle. + */ +static const struct GNUNET_CONFIGURATION_Handle *GSN_cfg; /** -* Database handle -*/ -struct GNUNET_NAMESTORE_PluginFunctions *GSN_database; + * Database handle + */ +static struct GNUNET_NAMESTORE_PluginFunctions *GSN_database; /** -* Zonefile directory -*/ + * Zonefile directory + */ static char *zonefile_directory; +/** + * Name of the database plugin + */ static char *db_lib_name; - /** * Our notification context. */ static struct GNUNET_SERVER_NotificationContext *snc; +/** + * Head of the Client DLL + */ static struct GNUNET_NAMESTORE_Client *client_head; + +/** + * Tail of the Client DLL + */ static struct GNUNET_NAMESTORE_Client *client_tail; -struct GNUNET_CONTAINER_MultiHashMap *zonekeys; +/** + * Hashmap containing the zone keys this namestore has is authoritative for + * + * Keys are the GNUNET_CRYPTO_HashCode of the GNUNET_CRYPTO_ShortHashCode + * The values are 'struct GNUNET_NAMESTORE_CryptoContainer *' + */ +static struct GNUNET_CONTAINER_MultiHashMap *zonekeys; +/** + * DLL head for key loading contexts + */ +static struct KeyLoadContext *kl_head; /** - * Write zonefile to disk - * @param filename where to write - * @param c the crypto container - * - * @return GNUNET_OK on success, GNUNET_SYSERR on fail + * DLL tail for key loading contexts */ +static struct KeyLoadContext *kl_tail; -int -write_key_to_file (const char *filename, struct GNUNET_NAMESTORE_CryptoContainer *c) +struct KeyLoadContext +{ + struct KeyLoadContext *next; + struct KeyLoadContext *prev; + struct GNUNET_CRYPTO_RsaKeyGenerationContext *keygen; + char *filename; + unsigned int *counter; +}; + + +/** + * Writes the encrypted private key of a zone in a file + * + * @param filename where to store the zone + * @param c the crypto container containing private key of the zone + * @return GNUNET_OK on success, GNUNET_SYSERR on failure + */ +static int +write_key_to_file (const char *filename, + struct GNUNET_NAMESTORE_CryptoContainer *c) { struct GNUNET_CRYPTO_RsaPrivateKey *ret = c->privkey; struct GNUNET_CRYPTO_RsaPrivateKeyBinaryEncoded *enc; struct GNUNET_DISK_FileHandle *fd; + struct GNUNET_CRYPTO_ShortHashCode zone; + struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded pubkey; + struct GNUNET_CRYPTO_RsaPrivateKey *privkey; - if (GNUNET_YES == GNUNET_DISK_file_test (filename)) + fd = GNUNET_DISK_file_open (filename, + GNUNET_DISK_OPEN_WRITE | GNUNET_DISK_OPEN_CREATE | GNUNET_DISK_OPEN_FAILIFEXISTS, + GNUNET_DISK_PERM_USER_READ | GNUNET_DISK_PERM_USER_WRITE); + if ( (NULL == fd) && (EEXIST == errno) ) { - struct GNUNET_CRYPTO_ShortHashCode zone; - struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded pubkey; - struct GNUNET_CRYPTO_RsaPrivateKey * privkey; - - privkey = GNUNET_CRYPTO_rsa_key_create_from_file(filename); - if (privkey == NULL) + privkey = GNUNET_CRYPTO_rsa_key_create_from_file (filename); + if (NULL == privkey) { GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - _("File zone `%s' but corrupt content already exists, failed to write! \n"), GNUNET_short_h2s (&zone)); + _("Failed to write zone key to file `%s': %s\n"), + filename, + _("file exists but reading key failed")); return GNUNET_SYSERR; } - GNUNET_CRYPTO_rsa_key_get_public (privkey, &pubkey); GNUNET_CRYPTO_short_hash (&pubkey, sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded), &zone); GNUNET_CRYPTO_rsa_key_free (privkey); - if (0 == memcmp (&zone, &c->zone, sizeof(zone))) { - GNUNET_log (GNUNET_ERROR_TYPE_INFO, - _("File zone `%s' containing this key already exists\n"), GNUNET_short_h2s (&zone)); - return GNUNET_OK; - } - else - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - _("File zone `%s' but different zone key already exists, failed to write! \n"), GNUNET_short_h2s (&zone)); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "File zone `%s' containing this key already exists\n", + GNUNET_short_h2s (&zone)); return GNUNET_OK; } + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Failed to write zone key to file `%s': %s\n"), + filename, + _("file exists with different key")); + return GNUNET_OK; } - fd = GNUNET_DISK_file_open (filename, GNUNET_DISK_OPEN_WRITE | GNUNET_DISK_OPEN_CREATE | GNUNET_DISK_OPEN_FAILIFEXISTS, GNUNET_DISK_PERM_USER_READ | GNUNET_DISK_PERM_USER_WRITE); if (NULL == fd) { - if (errno == EEXIST) - { - if (GNUNET_YES != GNUNET_DISK_file_test (filename)) - { - /* must exist but not be accessible, fail for good! */ - if (0 != ACCESS (filename, R_OK)) - LOG_STRERROR_FILE (GNUNET_ERROR_TYPE_ERROR, "access", filename); - else - GNUNET_break (0); /* what is going on!? */ - return GNUNET_SYSERR; - } - } LOG_STRERROR_FILE (GNUNET_ERROR_TYPE_ERROR, "open", filename); return GNUNET_SYSERR; } - if (GNUNET_YES != GNUNET_DISK_file_lock (fd, 0, sizeof (struct GNUNET_CRYPTO_RsaPrivateKeyBinaryEncoded), GNUNET_YES)) { - GNUNET_assert (GNUNET_YES == GNUNET_DISK_file_close (fd)); + GNUNET_break (GNUNET_YES == GNUNET_DISK_file_close (fd)); return GNUNET_SYSERR; } enc = GNUNET_CRYPTO_rsa_encode_key (ret); - GNUNET_assert (enc != NULL); + GNUNET_assert (NULL != enc); GNUNET_assert (ntohs (enc->len) == GNUNET_DISK_file_write (fd, enc, ntohs (enc->len))); GNUNET_free (enc); GNUNET_DISK_file_sync (fd); if (GNUNET_YES != GNUNET_DISK_file_unlock (fd, 0, sizeof (struct GNUNET_CRYPTO_RsaPrivateKeyBinaryEncoded))) LOG_STRERROR_FILE (GNUNET_ERROR_TYPE_WARNING, "fcntl", filename); GNUNET_assert (GNUNET_YES == GNUNET_DISK_file_close (fd)); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - _("Stored zonekey for zone `%s' in file `%s'\n"), GNUNET_short_h2s(&c->zone), c->filename); + "Stored zonekey for zone `%s' in file `%s'\n", + GNUNET_short_h2s(&c->zone), c->filename); return GNUNET_OK; } -int zone_to_disk_it (void *cls, - const GNUNET_HashCode *key, - void *value) -{ - struct GNUNET_NAMESTORE_CryptoContainer * c = value; - if (c->filename != NULL) - write_key_to_file(c->filename, c); - else - { - GNUNET_asprintf(&c->filename, "%s/%s.zkey", zonefile_directory, GNUNET_short_h2s (&c->zone)); - write_key_to_file(c->filename, c); - } - +/** + * Write allthe given zone key to disk and then removes the entry from the + * 'zonekeys' hash map. + * + * @param cls unused + * @param key zone key + * @param value 'struct GNUNET_NAMESTORE_CryptoContainer' containing the private + * key + * @return GNUNET_OK to continue iteration + */ +static int +zone_to_disk_it (void *cls, + const struct GNUNET_HashCode *key, + void *value) +{ + struct GNUNET_NAMESTORE_CryptoContainer *c = value; + + if (NULL == c->filename) + GNUNET_asprintf(&c->filename, + "%s/%s.zkey", + zonefile_directory, + GNUNET_short_h2s (&c->zone)); + (void) write_key_to_file(c->filename, c); GNUNET_assert (GNUNET_OK == GNUNET_CONTAINER_multihashmap_remove (zonekeys, key, value)); GNUNET_CRYPTO_rsa_key_free (c->privkey); - GNUNET_free (c->pubkey); GNUNET_free (c->filename); GNUNET_free (c); - return GNUNET_OK; } -struct GNUNET_TIME_Absolute +/** + * Add the given private key to the set of private keys + * this namestore can use to sign records when needed. + * + * @param pkey private key to add to our list (reference will + * be taken over or freed and should not be used afterwards) + */ +static void +learn_private_key (struct GNUNET_CRYPTO_RsaPrivateKey *pkey) +{ + struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded pub; + struct GNUNET_HashCode long_hash; + struct GNUNET_CRYPTO_ShortHashCode pubkey_hash; + struct GNUNET_NAMESTORE_CryptoContainer *cc; + + GNUNET_CRYPTO_rsa_key_get_public (pkey, &pub); + GNUNET_CRYPTO_short_hash (&pub, + sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded), + &pubkey_hash); + GNUNET_CRYPTO_short_hash_double (&pubkey_hash, &long_hash); + + if (GNUNET_NO != GNUNET_CONTAINER_multihashmap_contains(zonekeys, &long_hash)) + { + GNUNET_CRYPTO_rsa_key_free (pkey); + return; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Received new private key for zone `%s'\n", + GNUNET_short_h2s(&pubkey_hash)); + cc = GNUNET_malloc (sizeof (struct GNUNET_NAMESTORE_CryptoContainer)); + cc->privkey = pkey; + cc->zone = pubkey_hash; + GNUNET_assert (GNUNET_YES == + GNUNET_CONTAINER_multihashmap_put(zonekeys, &long_hash, cc, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY)); +} + + +/** + * Returns the expiration time of the given block of records. The block + * expiration time is the expiration time of the block with smallest + * expiration time. + * + * @param rd_count number of records given in 'rd' + * @param rd array of records + * @return absolute expiration time + */ +static struct GNUNET_TIME_Absolute get_block_expiration_time (unsigned int rd_count, const struct GNUNET_NAMESTORE_RecordData *rd) { unsigned int c; - struct GNUNET_TIME_Absolute expire = GNUNET_TIME_UNIT_FOREVER_ABS; + struct GNUNET_TIME_Absolute expire; + struct GNUNET_TIME_Absolute at; + struct GNUNET_TIME_Relative rt; if (NULL == rd) return GNUNET_TIME_UNIT_ZERO_ABS; + expire = GNUNET_TIME_UNIT_FOREVER_ABS; for (c = 0; c < rd_count; c++) - expire = GNUNET_TIME_absolute_min (rd[c].expiration, expire); + { + if (0 != (rd[c].flags & GNUNET_NAMESTORE_RF_RELATIVE_EXPIRATION)) + { + rt.rel_value = rd[c].expiration_time; + at = GNUNET_TIME_relative_to_absolute (rt); + } + else + { + at.abs_value = rd[c].expiration_time; + } + expire = GNUNET_TIME_absolute_min (at, expire); + } return expire; } + /** * Task run during shutdown. * @@ -245,240 +399,341 @@ get_block_expiration_time (unsigned int rd_count, const struct GNUNET_NAMESTORE_ static void cleanup_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { + struct GNUNET_NAMESTORE_ZoneIteration *no; + struct GNUNET_NAMESTORE_Client *nc; + struct KeyLoadContext *kl; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stopping namestore service\n"); - struct GNUNET_NAMESTORE_ZoneIteration * no; - struct GNUNET_NAMESTORE_ZoneIteration * tmp; - struct GNUNET_NAMESTORE_Client * nc; - struct GNUNET_NAMESTORE_Client * next; + if (NULL != snc) + { + GNUNET_SERVER_notification_context_destroy (snc); + snc = NULL; + } - GNUNET_SERVER_notification_context_destroy (snc); - snc = NULL; - GNUNET_CONTAINER_multihashmap_iterate(zonekeys, &zone_to_disk_it, NULL); - GNUNET_CONTAINER_multihashmap_destroy(zonekeys); + while (NULL != (kl = kl_head)) + { + GNUNET_CONTAINER_DLL_remove (kl_head, kl_tail, kl); + if (NULL != kl->keygen) + GNUNET_CRYPTO_rsa_key_create_stop (kl->keygen); + GNUNET_free (kl->filename); + GNUNET_free (kl); + } - for (nc = client_head; nc != NULL; nc = next) + GNUNET_CONTAINER_multihashmap_iterate (zonekeys, &zone_to_disk_it, NULL); + GNUNET_CONTAINER_multihashmap_destroy (zonekeys); + zonekeys = NULL; + while (NULL != (nc = client_head)) { - next = nc->next; - for (no = nc->op_head; no != NULL; no = tmp) + while (NULL != (no = nc->op_head)) { GNUNET_CONTAINER_DLL_remove (nc->op_head, nc->op_tail, no); - tmp = no->next; GNUNET_free (no); } GNUNET_SERVER_client_drop(nc->client); GNUNET_CONTAINER_DLL_remove (client_head, client_tail, nc); GNUNET_free (nc); } - GNUNET_break (NULL == GNUNET_PLUGIN_unload (db_lib_name, GSN_database)); GNUNET_free (db_lib_name); - GNUNET_free_non_null(zonefile_directory); + db_lib_name = NULL; + GNUNET_free_non_null (zonefile_directory); + zonefile_directory = NULL; } + +/** + * Lookup our internal data structure for a given client. + * + * @param client server client handle to use for the lookup + * @return our internal structure for the client, NULL if + * we do not have any yet + */ static struct GNUNET_NAMESTORE_Client * client_lookup (struct GNUNET_SERVER_Client *client) { - struct GNUNET_NAMESTORE_Client * nc; + struct GNUNET_NAMESTORE_Client *nc; GNUNET_assert (NULL != client); - - for (nc = client_head; nc != NULL; nc = nc->next) - { + for (nc = client_head; NULL != nc; nc = nc->next) if (client == nc->client) - break; - } - return nc; + return nc; + return NULL; } + /** - * Called whenever a client is disconnected. Frees our - * resources associated with that client. + * Called whenever a client is disconnected. + * Frees our resources associated with that client. * * @param cls closure * @param client identification of the client */ static void -client_disconnect_notification (void *cls, struct GNUNET_SERVER_Client *client) +client_disconnect_notification (void *cls, + struct GNUNET_SERVER_Client *client) { - struct GNUNET_NAMESTORE_ZoneIteration * no; - struct GNUNET_NAMESTORE_Client * nc; + struct GNUNET_NAMESTORE_ZoneIteration *no; + struct GNUNET_NAMESTORE_Client *nc; + if (NULL == client) return; - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Client %p disconnected \n", client); - - nc = client_lookup (client); - - if ((NULL == client) || (NULL == nc)) + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Client %p disconnected\n", + client); + if (NULL == (nc = client_lookup (client))) return; - - no = nc->op_head; - while (NULL != no) + while (NULL != (no = nc->op_head)) { GNUNET_CONTAINER_DLL_remove (nc->op_head, nc->op_tail, no); GNUNET_free (no); - no = nc->op_head; } - - GNUNET_SERVER_client_drop(nc->client); + GNUNET_SERVER_client_drop (nc->client); GNUNET_CONTAINER_DLL_remove (client_head, client_tail, nc); GNUNET_free (nc); - nc = NULL; } - -static void handle_start (void *cls, - struct GNUNET_SERVER_Client * client, - const struct GNUNET_MessageHeader * message) +/** + * Handles a 'GNUNET_MESSAGE_TYPE_NAMESTORE_START' message + * + * @param cls unused + * @param client GNUNET_SERVER_Client sending the message + * @param message unused + */ +static void +handle_start (void *cls, + struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Client %p connected\n", client); + struct GNUNET_NAMESTORE_Client *nc; - struct GNUNET_NAMESTORE_Client * nc = GNUNET_malloc (sizeof (struct GNUNET_NAMESTORE_Client)); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Client %p connected\n", client); + if (NULL != client_lookup (client)) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + nc = GNUNET_malloc (sizeof (struct GNUNET_NAMESTORE_Client)); nc->client = client; GNUNET_SERVER_notification_context_add (snc, client); - GNUNET_CONTAINER_DLL_insert(client_head, client_tail, nc); + GNUNET_CONTAINER_DLL_insert (client_head, client_tail, nc); GNUNET_SERVER_client_keep (client); GNUNET_SERVER_receive_done (client, GNUNET_OK); } + +/** + * Context for name lookups passed from 'handle_lookup_name' to + * 'handle_lookup_name_it' as closure + */ struct LookupNameContext { + /** + * The client to send the response to + */ struct GNUNET_NAMESTORE_Client *nc; + + /** + * Requested zone + */ + const struct GNUNET_CRYPTO_ShortHashCode *zone; + + /** + * Requested name + */ + const char *name; + + /** + * Operation id for the name lookup + */ uint32_t request_id; + + /** + * Requested specific record type + */ uint32_t record_type; - struct GNUNET_CRYPTO_ShortHashCode *zone; - char * name; }; -void drop_iterator (void *cls, - const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *zone_key, - struct GNUNET_TIME_Absolute expire, - const char *name, - unsigned int rd_len, - const struct GNUNET_NAMESTORE_RecordData *rd, - const struct GNUNET_CRYPTO_RsaSignature *signature) -{ - struct GNUNET_CRYPTO_ShortHashCode zone_hash; - int * stop = cls; - if (NULL != zone_key) - { - GNUNET_CRYPTO_short_hash(zone_key, sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded), &zone_hash); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Deleting zone `%s'\n", GNUNET_short_h2s (&zone_hash)); - GSN_database->delete_zone (GSN_database->cls, &zone_hash); - } - else - { - (*stop) = GNUNET_YES; - } -} - +/** + * A 'GNUNET_NAMESTORE_RecordIterator' for name lookups in handle_lookup_name + * + * @param cls a 'struct LookupNameContext *' with information about the request + * @param zone_key zone key of the zone + * @param expire expiration time + * @param name name + * @param rd_count number of records + * @param rd array of records + * @param signature signature + */ static void handle_lookup_name_it (void *cls, - const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *zone_key, - struct GNUNET_TIME_Absolute expire, - const char *name, - unsigned int rd_count, - const struct GNUNET_NAMESTORE_RecordData *rd, - const struct GNUNET_CRYPTO_RsaSignature *signature) + const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *zone_key, + struct GNUNET_TIME_Absolute expire, + const char *name, + unsigned int rd_count, + const struct GNUNET_NAMESTORE_RecordData *rd, + const struct GNUNET_CRYPTO_RsaSignature *signature) { - /* send response */ struct LookupNameContext *lnc = cls; struct LookupNameResponseMessage *lnr_msg; - struct GNUNET_NAMESTORE_RecordData *rd_selected = NULL; + struct GNUNET_NAMESTORE_RecordData *rd_selected; struct GNUNET_NAMESTORE_CryptoContainer *cc; - struct GNUNET_CRYPTO_RsaSignature *signature_new = NULL; + struct GNUNET_CRYPTO_RsaSignature *signature_new; struct GNUNET_TIME_Absolute e; + struct GNUNET_TIME_Relative re; struct GNUNET_CRYPTO_ShortHashCode zone_key_hash; - GNUNET_HashCode long_hash; + struct GNUNET_HashCode long_hash; char *rd_tmp; char *name_tmp; size_t rd_ser_len; - size_t r_size = 0; - size_t name_len = 0; - - int copied_elements = 0; - int contains_signature = GNUNET_NO; - int authoritative = GNUNET_NO; - int c; + size_t r_size; + size_t name_len; + int copied_elements; + int contains_signature; + int authoritative; + int rd_modified; + unsigned int c; - if (NULL != name) - name_len = strlen(name) + 1; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Found %u records under name `%s'\n", + rd_count, + name); + authoritative = GNUNET_NO; + signature_new = NULL; + cc = NULL; + if (NULL != zone_key) + { + GNUNET_CRYPTO_short_hash (zone_key, + sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded), + &zone_key_hash); + GNUNET_CRYPTO_short_hash_double (&zone_key_hash, &long_hash); + if (NULL != (cc = GNUNET_CONTAINER_multihashmap_get (zonekeys, &long_hash))) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Am authoritative for zone `%s'\n", + GNUNET_short_h2s (&zone_key_hash)); + authoritative = GNUNET_YES; + } + } + copied_elements = 0; + rd_modified = GNUNET_NO; + rd_selected = NULL; /* count records to copy */ - if (rd_count != 0) + for (c = 0; c < rd_count; c++) { - if (lnc->record_type != 0) + if ( (GNUNET_YES == authoritative) && + (GNUNET_YES == + GNUNET_NAMESTORE_is_expired (&rd[c]) ) ) { - /* special record type needed */ - for (c = 0; c < rd_count; c ++) - if (rd[c].record_type == lnc->record_type) - copied_elements++; /* found matching record */ - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Found %u records with type %u for name `%s' in zone `%s'\n", - copied_elements, lnc->record_type, lnc->name, GNUNET_short_h2s(lnc->zone)); - rd_selected = GNUNET_malloc (copied_elements * sizeof (struct GNUNET_NAMESTORE_RecordData)); - copied_elements = 0; - for (c = 0; c < rd_count; c ++) - { - if (rd[c].record_type == lnc->record_type) - { - /* found matching record */ - memcpy (&rd_selected[copied_elements], &rd[c], sizeof (struct GNUNET_NAMESTORE_RecordData)); - copied_elements++; - } - } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Skipping expired record\n"); + continue; } + if ( (GNUNET_NAMESTORE_TYPE_ANY == lnc->record_type) || + (rd[c].record_type == lnc->record_type) ) + copied_elements++; /* found matching record */ else { - copied_elements = rd_count; - rd_selected = (struct GNUNET_NAMESTORE_RecordData *) rd; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Skipping non-mtaching record\n"); + rd_modified = GNUNET_YES; } } - else + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Found %u records with type %u for name `%s' in zone `%s'\n", + copied_elements, + lnc->record_type, + lnc->name, + GNUNET_short_h2s(lnc->zone)); + if (copied_elements > 0) { - /* No results */ + rd_selected = GNUNET_malloc (copied_elements * sizeof (struct GNUNET_NAMESTORE_RecordData)); copied_elements = 0; - rd_selected = NULL; - expire = GNUNET_TIME_UNIT_ZERO_ABS; + for (c = 0; c < rd_count; c++) + { + if ( (GNUNET_YES == authoritative) && + (GNUNET_YES == + GNUNET_NAMESTORE_is_expired (&rd[c])) ) + continue; + if ( (GNUNET_NAMESTORE_TYPE_ANY == lnc->record_type) || + (rd[c].record_type == lnc->record_type) ) + { + if (0 != (rd[c].flags & GNUNET_NAMESTORE_RF_RELATIVE_EXPIRATION)) + { + GNUNET_break (GNUNET_YES == authoritative); + rd_modified = GNUNET_YES; + re.rel_value = rd[c].expiration_time; + e = GNUNET_TIME_relative_to_absolute (re); + } + else + { + e.abs_value = rd[c].expiration_time; + } + /* found matching record, copy and convert flags to public format */ + rd_selected[copied_elements] = rd[c]; /* shallow copy! */ + rd_selected[copied_elements].expiration_time = e.abs_value; + if (0 != (rd_selected[copied_elements].flags & + (GNUNET_NAMESTORE_RF_RELATIVE_EXPIRATION | GNUNET_NAMESTORE_RF_AUTHORITY))) + { + rd_selected[copied_elements].flags &= ~ (GNUNET_NAMESTORE_RF_RELATIVE_EXPIRATION | + GNUNET_NAMESTORE_RF_AUTHORITY); + rd_modified = GNUNET_YES; + } + copied_elements++; + } + else + { + rd_modified = GNUNET_YES; + } + } } - - rd_ser_len = GNUNET_NAMESTORE_records_get_size(copied_elements, rd_selected); - char rd_ser[rd_ser_len]; - GNUNET_NAMESTORE_records_serialize(copied_elements, rd_selected, rd_ser_len, rd_ser); - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Found %u records for name `%s' in zone `%s'\n", - copied_elements, lnc->name, GNUNET_short_h2s(lnc->zone)); - - if ((copied_elements == rd_count) && (NULL != signature)) - contains_signature = GNUNET_YES; /* returning all records, so include signature */ else - contains_signature = GNUNET_NO; /* returning not all records, so do not include signature */ - + rd_selected = NULL; - if ((NULL != zone_key) && (copied_elements == rd_count)) + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Found %u matching records for name `%s' in zone `%s'\n", + copied_elements, + lnc->name, + GNUNET_short_h2s (lnc->zone)); + contains_signature = GNUNET_NO; + if (copied_elements > 0) { - GNUNET_CRYPTO_short_hash(zone_key, sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded), &zone_key_hash); - GNUNET_CRYPTO_short_hash_double (&zone_key_hash, &long_hash); - if (GNUNET_CONTAINER_multihashmap_contains(zonekeys, &long_hash)) + if (GNUNET_YES == authoritative) { - cc = GNUNET_CONTAINER_multihashmap_get(zonekeys, &long_hash); - e = get_block_expiration_time(rd_count, rd); - signature_new = GNUNET_NAMESTORE_create_signature(cc->privkey, e, name, rd, rd_count); - GNUNET_assert (signature_new != NULL); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Creating signature for name `%s' with %u records in zone `%s'\n",name, copied_elements, GNUNET_short_h2s(&zone_key_hash)); - authoritative = GNUNET_YES; + GNUNET_assert (NULL != cc); + e = get_block_expiration_time (rd_count, rd); + signature_new = GNUNET_NAMESTORE_create_signature (cc->privkey, e, name, rd_selected, copied_elements); + GNUNET_assert (NULL != signature_new); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Creating signature for name `%s' with %u records in zone `%s'\n", + name, + copied_elements, + GNUNET_short_h2s(&zone_key_hash)); } else - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "I am not authoritative for name `%s' in zone `%s'\n",name, GNUNET_short_h2s(&zone_key_hash)); + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Not authoritative, records modified is %d, have sig is %d\n", + rd_modified, + NULL != signature); + if ((GNUNET_NO == rd_modified) && (NULL != signature)) + contains_signature = GNUNET_YES; /* returning all records, so include signature */ + } } + rd_ser_len = GNUNET_NAMESTORE_records_get_size (copied_elements, rd_selected); + name_len = (NULL == name) ? 0 : strlen(name) + 1; r_size = sizeof (struct LookupNameResponseMessage) + sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded) + name_len + rd_ser_len; - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Sending `%s' message\n", "NAMESTORE_LOOKUP_NAME_RESPONSE"); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Sending `%s' message\n", + "NAMESTORE_LOOKUP_NAME_RESPONSE"); lnr_msg = GNUNET_malloc (r_size); lnr_msg->gns_header.header.type = ntohs (GNUNET_MESSAGE_TYPE_NAMESTORE_LOOKUP_NAME_RESPONSE); lnr_msg->gns_header.header.size = ntohs (r_size); @@ -486,20 +741,22 @@ handle_lookup_name_it (void *cls, lnr_msg->rd_count = htons (copied_elements); lnr_msg->rd_len = htons (rd_ser_len); lnr_msg->name_len = htons (name_len); - lnr_msg->expire = GNUNET_TIME_absolute_hton(get_block_expiration_time(copied_elements, rd_selected)); - + lnr_msg->expire = GNUNET_TIME_absolute_hton (get_block_expiration_time (copied_elements, + rd_selected)); + name_tmp = (char *) &lnr_msg[1]; + memcpy (name_tmp, name, name_len); + rd_tmp = &name_tmp[name_len]; + GNUNET_NAMESTORE_records_serialize (copied_elements, rd_selected, rd_ser_len, rd_tmp); if (rd_selected != rd) - GNUNET_free (rd_selected); - - if (zone_key != NULL) - lnr_msg->public_key = (*zone_key); - else - memset(&lnr_msg->public_key, '\0', sizeof (lnr_msg->public_key)); - - if (GNUNET_YES == authoritative) - { /* use new created signature */ + GNUNET_free_non_null (rd_selected); + if (NULL != zone_key) + lnr_msg->public_key = *zone_key; + if ( (GNUNET_YES == authoritative) && + (copied_elements > 0) ) + { + /* use new created signature */ lnr_msg->contains_sig = htons (GNUNET_YES); - GNUNET_assert (signature_new != NULL); + GNUNET_assert (NULL != signature_new); lnr_msg->signature = *signature_new; GNUNET_free (signature_new); } @@ -507,392 +764,433 @@ handle_lookup_name_it (void *cls, { /* use existing signature */ lnr_msg->contains_sig = htons (GNUNET_YES); - GNUNET_assert (signature != NULL); + GNUNET_assert (NULL != signature); lnr_msg->signature = *signature; } - else - { - /* use no signature */ - memset (&lnr_msg->signature, '\0', sizeof (lnr_msg->signature)); - } - - name_tmp = (char *) &lnr_msg[1]; - rd_tmp = &name_tmp[name_len]; - - memcpy (name_tmp, name, name_len); - memcpy (rd_tmp, rd_ser, rd_ser_len); - - GNUNET_SERVER_notification_context_unicast (snc, lnc->nc->client, (const struct GNUNET_MessageHeader *) lnr_msg, GNUNET_NO); + GNUNET_SERVER_notification_context_unicast (snc, lnc->nc->client, + &lnr_msg->gns_header.header, + GNUNET_NO); GNUNET_free (lnr_msg); } -static void handle_lookup_name (void *cls, - struct GNUNET_SERVER_Client * client, - const struct GNUNET_MessageHeader * message) + +/** + * Handles a 'GNUNET_MESSAGE_TYPE_NAMESTORE_LOOKUP_NAME' message + * + * @param cls unused + * @param client GNUNET_SERVER_Client sending the message + * @param message message of type 'struct LookupNameMessage' + */ +static void +handle_lookup_name (void *cls, + struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received `%s' message\n", "NAMESTORE_LOOKUP_NAME"); + const struct LookupNameMessage *ln_msg; struct LookupNameContext lnc; struct GNUNET_NAMESTORE_Client *nc; size_t name_len; - char * name; - uint32_t rid = 0; - uint32_t type = 0; + const char *name; + uint32_t rid; + uint32_t type; + char *conv_name; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Received `%s' message\n", + "NAMESTORE_LOOKUP_NAME"); if (ntohs (message->size) < sizeof (struct LookupNameMessage)) { - GNUNET_break_op (0); - GNUNET_SERVER_receive_done (client, GNUNET_OK); + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } - - nc = client_lookup(client); - if (nc == NULL) + if (NULL == (nc = client_lookup(client))) { - GNUNET_break_op (0); - GNUNET_SERVER_receive_done (client, GNUNET_OK); + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } - - struct LookupNameMessage * ln_msg = (struct LookupNameMessage *) message; + ln_msg = (const struct LookupNameMessage *) message; rid = ntohl (ln_msg->gns_header.r_id); name_len = ntohl (ln_msg->name_len); type = ntohl (ln_msg->record_type); - - if ((name_len == 0) || (name_len > 256)) + if ((0 == name_len) || (name_len > MAX_NAME_LEN)) { - GNUNET_break_op (0); - GNUNET_SERVER_receive_done (client, GNUNET_OK); + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } - - name = (char *) &ln_msg[1]; - if (name[name_len -1] != '\0') + name = (const char *) &ln_msg[1]; + if ('\0' != name[name_len -1]) { - GNUNET_break_op (0); - GNUNET_SERVER_receive_done (client, GNUNET_OK); + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } - - if (0 == type) - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Looking up all records for name `%s' in zone `%s'\n", name, GNUNET_short_h2s(&ln_msg->zone)); + if (GNUNET_NAMESTORE_TYPE_ANY == type) + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Looking up all records for name `%s' in zone `%s'\n", + name, + GNUNET_short_h2s(&ln_msg->zone)); else - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Looking up records with type %u for name `%s' in zone `%s'\n", type, name, GNUNET_short_h2s(&ln_msg->zone)); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Looking up records with type %u for name `%s' in zone `%s'\n", + type, name, + GNUNET_short_h2s(&ln_msg->zone)); - /* do the actual lookup */ - lnc.request_id = rid; - lnc.nc = nc; + conv_name = GNUNET_NAMESTORE_normalize_string (name); + if (NULL == conv_name) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Error converting name `%s'\n", name); + return; + } + + /* do the actual lookup */ + lnc.request_id = rid; + lnc.nc = nc; lnc.record_type = type; - lnc.name = name; + lnc.name = conv_name; lnc.zone = &ln_msg->zone; - GSN_database->iterate_records(GSN_database->cls, &ln_msg->zone, name, 0, &handle_lookup_name_it, &lnc); - + if (GNUNET_SYSERR == + GSN_database->iterate_records (GSN_database->cls, + &ln_msg->zone, conv_name, 0 /* offset */, + &handle_lookup_name_it, &lnc)) + { + /* internal error (in database plugin); might be best to just hang up on + plugin rather than to signal that there are 'no' results, which + might also be false... */ + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + GNUNET_free (conv_name); + return; + } + GNUNET_free (conv_name); GNUNET_SERVER_receive_done (client, GNUNET_OK); } -static void handle_record_put (void *cls, - struct GNUNET_SERVER_Client * client, - const struct GNUNET_MessageHeader * message) + +/** + * Handles a 'GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_PUT' message + * + * @param cls unused + * @param client GNUNET_SERVER_Client sending the message + * @param message message of type 'struct RecordPutMessage' + */ +static void +handle_record_put (void *cls, + struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received `%s' message\n", "NAMESTORE_RECORD_PUT"); struct GNUNET_NAMESTORE_Client *nc; + const struct RecordPutMessage *rp_msg; struct GNUNET_TIME_Absolute expire; - struct GNUNET_CRYPTO_RsaSignature *signature; + const struct GNUNET_CRYPTO_RsaSignature *signature; struct RecordPutResponseMessage rpr_msg; + struct GNUNET_CRYPTO_ShortHashCode zone_hash; size_t name_len; size_t msg_size; size_t msg_size_exp; - char * name; - char * rd_ser; - uint32_t rid = 0; + const char *name; + const char *rd_ser; + char * conv_name; + uint32_t rid; uint32_t rd_ser_len; uint32_t rd_count; - int res = GNUNET_SYSERR; + int res; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Received `%s' message\n", + "NAMESTORE_RECORD_PUT"); if (ntohs (message->size) < sizeof (struct RecordPutMessage)) { - GNUNET_break_op (0); - GNUNET_SERVER_receive_done (client, GNUNET_OK); + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } - - nc = client_lookup (client); - if (nc == NULL) + if (NULL == (nc = client_lookup (client))) { - GNUNET_break_op (0); - GNUNET_SERVER_receive_done (client, GNUNET_OK); + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } - - struct RecordPutMessage * rp_msg = (struct RecordPutMessage *) message; - + rp_msg = (const struct RecordPutMessage *) message; rid = ntohl (rp_msg->gns_header.r_id); msg_size = ntohs (rp_msg->gns_header.header.size); name_len = ntohs (rp_msg->name_len); rd_count = ntohs (rp_msg->rd_count); - rd_ser_len = ntohs(rp_msg->rd_len); - - if (msg_size > GNUNET_SERVER_MAX_MESSAGE_SIZE) - { - GNUNET_break_op (0); - GNUNET_SERVER_receive_done (client, GNUNET_OK); - return; - } - - if ((rd_count < 1) || (rd_ser_len < 1) || (name_len >=256) || (name_len == 0)) + rd_ser_len = ntohs (rp_msg->rd_len); + if ((rd_count < 1) || (rd_ser_len < 1) || (name_len >= MAX_NAME_LEN) || (0 == name_len)) { - GNUNET_break_op (0); - GNUNET_SERVER_receive_done (client, GNUNET_OK); + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } - - msg_size_exp = sizeof (struct RecordPutMessage) + name_len + rd_ser_len; + msg_size_exp = sizeof (struct RecordPutMessage) + name_len + rd_ser_len; if (msg_size != msg_size_exp) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Expected message %u size but message size is %u \n", msg_size_exp, msg_size); - GNUNET_break_op (0); - GNUNET_SERVER_receive_done (client, GNUNET_OK); + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } - if ((name_len == 0) || (name_len > 256)) + name = (const char *) &rp_msg[1]; + if ('\0' != name[name_len -1]) { - GNUNET_break_op (0); - GNUNET_SERVER_receive_done (client, GNUNET_OK); + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } + expire = GNUNET_TIME_absolute_ntoh (rp_msg->expire); + signature = &rp_msg->signature; + rd_ser = &name[name_len]; + struct GNUNET_NAMESTORE_RecordData rd[rd_count]; - name = (char *) &rp_msg[1]; - - if (name[name_len -1] != '\0') + if (GNUNET_OK != + GNUNET_NAMESTORE_records_deserialize (rd_ser_len, rd_ser, rd_count, rd)) { - GNUNET_break_op (0); - GNUNET_SERVER_receive_done (client, GNUNET_OK); + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } + GNUNET_CRYPTO_short_hash (&rp_msg->public_key, + sizeof (rp_msg->public_key), + &zone_hash); - expire = GNUNET_TIME_absolute_ntoh(rp_msg->expire); - signature = (struct GNUNET_CRYPTO_RsaSignature *) &rp_msg->signature; - - rd_ser = &name[name_len]; - struct GNUNET_NAMESTORE_RecordData rd[rd_count]; - res = GNUNET_NAMESTORE_records_deserialize(rd_ser_len, rd_ser, rd_count, rd); - if (res != GNUNET_OK) + conv_name = GNUNET_NAMESTORE_normalize_string (name); + if (NULL == conv_name) { - GNUNET_break_op (0); - goto send; + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Error converting name `%s'\n", name); + return; } - struct GNUNET_CRYPTO_ShortHashCode zone_hash; - GNUNET_CRYPTO_short_hash (&rp_msg->public_key, sizeof (rp_msg->public_key), &zone_hash); - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Putting %u record for name `%s' in zone `%s'\n", rd_count, name, GNUNET_short_h2s(&zone_hash)); - - /* Database operation */ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Putting %u records under name `%s' in zone `%s'\n", + rd_count, conv_name, + GNUNET_short_h2s (&zone_hash)); res = GSN_database->put_records(GSN_database->cls, - &rp_msg->public_key, - expire, - name, - rd_count, rd, - signature); - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Putting record for name `%s': %s\n", - name, (res == GNUNET_OK) ? "OK" : "FAIL"); - - /* Send response */ -send: - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Sending `%s' message\n", "RECORD_PUT_RESPONSE"); + &rp_msg->public_key, + expire, + conv_name, + rd_count, rd, + signature); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Putting record for name `%s': %s\n", + conv_name, + (GNUNET_OK == res) ? "OK" : "FAILED"); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Sending `%s' message\n", + "RECORD_PUT_RESPONSE"); + GNUNET_free (conv_name); rpr_msg.gns_header.header.type = htons (GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_PUT_RESPONSE); rpr_msg.gns_header.header.size = htons (sizeof (struct RecordPutResponseMessage)); rpr_msg.gns_header.r_id = htonl (rid); rpr_msg.op_result = htonl (res); - GNUNET_SERVER_notification_context_unicast (snc, nc->client, (const struct GNUNET_MessageHeader *) &rpr_msg, GNUNET_NO); - + GNUNET_SERVER_notification_context_unicast (snc, + nc->client, + &rpr_msg.gns_header.header, + GNUNET_NO); GNUNET_SERVER_receive_done (client, GNUNET_OK); } + +/** + * Context for record create operations passed from 'handle_record_create' to + * 'handle_create_record_it' as closure + */ struct CreateRecordContext { - struct GNUNET_NAMESTORE_RecordData *rd; - struct GNUNET_CRYPTO_RsaPrivateKey *pkey; - struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *pubkey; + /** + * Record data + */ + const struct GNUNET_NAMESTORE_RecordData *rd; + + /** + * Zone's public key + */ + struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded pubkey; + + /** + * Name for the record to create + */ + const char *name; + + /** + * Record expiration time + */ struct GNUNET_TIME_Absolute expire; - char *name; + + /** + * result returned from 'handle_create_record_it' + * GNUNET_SYSERR: failed to create the record + * GNUNET_NO: we updated an existing record or identical entry existed + * GNUNET_YES : we created a new record + */ int res; }; +/** + * A 'GNUNET_NAMESTORE_RecordIterator' for record create operations + * in handle_record_create + * + * @param cls a 'struct CreateRecordContext *' with information about the request + * @param pubkey zone key of the zone + * @param expire expiration time + * @param name name + * @param rd_count number of records + * @param rd array of records + * @param signature signature + */ static void handle_create_record_it (void *cls, - const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *pubkey, - struct GNUNET_TIME_Absolute expire, - const char *name, - unsigned int rd_count, - const struct GNUNET_NAMESTORE_RecordData *rd, - const struct GNUNET_CRYPTO_RsaSignature *signature) + const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *pubkey, + struct GNUNET_TIME_Absolute expire, + const char *name, + unsigned int rd_count, + const struct GNUNET_NAMESTORE_RecordData *rd, + const struct GNUNET_CRYPTO_RsaSignature *signature) { - struct CreateRecordContext * crc = cls; - struct GNUNET_NAMESTORE_RecordData *rd_new = NULL; - struct GNUNET_CRYPTO_RsaSignature dummy_signature; + static struct GNUNET_CRYPTO_RsaSignature dummy_signature; + struct CreateRecordContext *crc = cls; + struct GNUNET_NAMESTORE_RecordData *rd_new; struct GNUNET_TIME_Absolute block_expiration; - int res; - int exist = GNUNET_SYSERR; - int update = GNUNET_NO; - int c; - int rd_count_new = 0; + int exist; + int update; + unsigned int c; + unsigned int rd_count_new; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Found %u existing records for `%s'\n", rd_count, crc->name); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Found %u existing records for `%s'\n", + rd_count, crc->name); + exist = -1; + update = GNUNET_NO; for (c = 0; c < rd_count; c++) { - if ((crc->rd->record_type == GNUNET_NAMESTORE_TYPE_PKEY) && (rd[c].record_type == GNUNET_NAMESTORE_TYPE_PKEY)) + if ( (crc->rd->record_type != rd[c].record_type) || + ((crc->rd->flags & GNUNET_NAMESTORE_RF_RELATIVE_EXPIRATION) + != (rd[c].flags & GNUNET_NAMESTORE_RF_RELATIVE_EXPIRATION)) ) + continue; /* no match */ + if ( (GNUNET_NAMESTORE_TYPE_PKEY == crc->rd->record_type) || + (GNUNET_NAMESTORE_TYPE_PSEU == crc->rd->record_type) || + (GNUNET_DNSPARSER_TYPE_CNAME == crc->rd->record_type) ) { - /* Update unique PKEY */ + /* Update unique PKEY, PSEU or CNAME record; for these + record types, only one can be active at any time */ exist = c; - update = GNUNET_YES; - break; - } - else if ((crc->rd->record_type == GNUNET_NAMESTORE_TYPE_PSEU) && (rd[c].record_type == GNUNET_NAMESTORE_TYPE_PSEU)) - { - /* Update unique PSEU */ - exist = c; - update = GNUNET_YES; - break; + if ( (crc->rd->data_size != rd[c].data_size) || + (0 != memcmp (crc->rd->data, rd[c].data, rd[c].data_size)) || + (crc->rd->expiration_time != rd[c].expiration_time) ) + update = GNUNET_YES; + break; } - else if ((crc->rd->record_type == rd[c].record_type) && - (crc->rd->data_size == rd[c].data_size) && - (0 == memcmp (crc->rd->data, rd[c].data, rd[c].data_size))) + if ( (crc->rd->data_size == rd[c].data_size) && + (0 == memcmp (crc->rd->data, rd[c].data, rd[c].data_size))) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Found existing records for `%s' to update expiration date!\n", crc->name); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Found matching existing record for `%s'; only updating expiration date!\n", + crc->name); exist = c; - if (crc->rd->expiration.abs_value != rd[c].expiration.abs_value) + if (crc->rd->expiration_time != rd[c].expiration_time) update = GNUNET_YES; - break; + break; } } - if (exist == GNUNET_SYSERR) - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "New record does not exist for name `%s'!\n", crc->name); - - if (exist == GNUNET_SYSERR) - { - rd_new = GNUNET_malloc ((rd_count+1) * sizeof (struct GNUNET_NAMESTORE_RecordData)); - memcpy (rd_new, rd, rd_count * sizeof (struct GNUNET_NAMESTORE_RecordData)); - rd_count_new = rd_count + 1; - rd_new[rd_count] = *(crc->rd); - } - else if (update == GNUNET_NO) + if ( (-1 != exist) && + (GNUNET_NO == update) ) { /* Exact same record already exists */ - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "No update for %s' record required!\n", crc->name); - res = GNUNET_NO; - goto end; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Matching record for %s' exists, no change required!\n", + crc->name); + crc->res = GNUNET_NO; /* identical record existed */ + return; } - else if (update == GNUNET_YES) + if (-1 == exist) { - /* Update record */ - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Updating existing records for `%s'!\n", crc->name); - rd_new = GNUNET_malloc ((rd_count) * sizeof (struct GNUNET_NAMESTORE_RecordData)); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "No existing record for name `%s'!\n", + crc->name); + rd_count_new = rd_count + 1; + rd_new = GNUNET_malloc (rd_count_new * sizeof (struct GNUNET_NAMESTORE_RecordData)); memcpy (rd_new, rd, rd_count * sizeof (struct GNUNET_NAMESTORE_RecordData)); + rd_new[rd_count] = *(crc->rd); + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Updating existing records for `%s'!\n", + crc->name); rd_count_new = rd_count; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Updating expiration from %llu to %llu!\n", rd_new[exist].expiration.abs_value, crc->rd->expiration.abs_value); + rd_new = GNUNET_malloc (rd_count_new * sizeof (struct GNUNET_NAMESTORE_RecordData)); + memcpy (rd_new, rd, rd_count * sizeof (struct GNUNET_NAMESTORE_RecordData)); rd_new[exist] = *(crc->rd); } - - block_expiration = GNUNET_TIME_absolute_max(crc->expire, expire); - if (block_expiration.abs_value != expire.abs_value) - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Updated block expiration time\n"); - - memset (&dummy_signature, '\0', sizeof (dummy_signature)); - - /* Database operation */ - GNUNET_assert ((rd_new != NULL) && (rd_count_new > 0)); - res = GSN_database->put_records(GSN_database->cls, - (const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *) crc->pubkey, - block_expiration, - crc->name, - rd_count_new, rd_new, - &dummy_signature); - GNUNET_break (GNUNET_OK == res); - if (res == GNUNET_OK) - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Successfully put record for `%s' in database \n", crc->name); + block_expiration = GNUNET_TIME_absolute_max (crc->expire, expire); + if (GNUNET_OK != + GSN_database->put_records (GSN_database->cls, + &crc->pubkey, + block_expiration, + crc->name, + rd_count_new, rd_new, + &dummy_signature)) + crc->res = GNUNET_SYSERR; /* error */ + else if (GNUNET_YES == update) + crc->res = GNUNET_NO; /* update */ else - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Failed to put record for `%s' in database \n", crc->name); - res = GNUNET_YES; - -end: - GNUNET_free_non_null (rd_new); - - switch (res) { - case GNUNET_SYSERR: - /* failed to create the record */ - crc->res = GNUNET_SYSERR; - break; - case GNUNET_YES: - /* database operations OK */ - if (GNUNET_YES == update) - { - /* we updated an existing record */ - crc->res = GNUNET_NO; - } - else - { - /* we created a new record */ - crc->res = GNUNET_YES; - } - break; - case GNUNET_NO: - /* identical entry existed, so we did nothing */ - crc->res = GNUNET_NO; - break; - default: - break; - } - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Update result for name `%s' %u\n", crc->name, res); - + crc->res = GNUNET_YES; /* created new record */ + GNUNET_free (rd_new); } -static void handle_record_create (void *cls, - struct GNUNET_SERVER_Client * client, - const struct GNUNET_MessageHeader * message) + +/** + * Handles a 'GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_CREATE' message + * + * @param cls unused + * @param client GNUNET_SERVER_Client sending the message + * @param message message of type 'struct RecordCreateMessage' + */ +static void +handle_record_create (void *cls, + struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received `%s' message\n", "NAMESTORE_RECORD_CREATE"); struct GNUNET_NAMESTORE_Client *nc; - struct GNUNET_NAMESTORE_CryptoContainer *cc; + const struct RecordCreateMessage *rp_msg; struct CreateRecordContext crc; struct GNUNET_CRYPTO_RsaPrivateKey *pkey; - struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded pub; struct RecordCreateResponseMessage rcr_msg; - struct GNUNET_CRYPTO_ShortHashCode pubkey_hash; - GNUNET_HashCode long_hash; size_t name_len; size_t msg_size; size_t msg_size_exp; size_t rd_ser_len; size_t key_len; - uint32_t rid = 0; - char *pkey_tmp; - char *name_tmp; - char *rd_ser; - int rd_count; - - int res = GNUNET_SYSERR; - crc.res = GNUNET_SYSERR; + uint32_t rid; + const char *pkey_tmp; + const char *name_tmp; + char *conv_name; + const char *rd_ser; + unsigned int rd_count; + int res; + struct GNUNET_NAMESTORE_RecordData rd; + struct GNUNET_CRYPTO_ShortHashCode pubkey_hash; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Received `%s' message\n", "NAMESTORE_RECORD_CREATE"); if (ntohs (message->size) < sizeof (struct RecordCreateMessage)) { - GNUNET_break_op (0); - GNUNET_SERVER_receive_done (client, GNUNET_OK); + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } - - nc = client_lookup(client); - if (nc == NULL) + if (NULL == (nc = client_lookup (client))) { - GNUNET_break_op (0); - GNUNET_SERVER_receive_done (client, GNUNET_OK); + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } - - struct RecordCreateMessage * rp_msg = (struct RecordCreateMessage *) message; + rp_msg = (const struct RecordCreateMessage *) message; rid = ntohl (rp_msg->gns_header.r_id); name_len = ntohs (rp_msg->name_len); msg_size = ntohs (message->size); @@ -900,79 +1198,74 @@ static void handle_record_create (void *cls, rd_ser_len = ntohs (rp_msg->rd_len); key_len = ntohs (rp_msg->pkey_len); msg_size_exp = sizeof (struct RecordCreateMessage) + key_len + name_len + rd_ser_len; - - if (msg_size != msg_size_exp) + if ( (msg_size != msg_size_exp) || (1 != rd_count) ) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Expected message %u size but message size is %u \n", msg_size_exp, msg_size); - GNUNET_break_op (0); - GNUNET_SERVER_receive_done (client, GNUNET_OK); + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } - - if ((name_len == 0) || (name_len > 256)) + if ((0 == name_len) || (name_len > MAX_NAME_LEN)) { - GNUNET_break_op (0); - GNUNET_SERVER_receive_done (client, GNUNET_OK); + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } - - pkey_tmp = (char *) &rp_msg[1]; + pkey_tmp = (const char *) &rp_msg[1]; name_tmp = &pkey_tmp[key_len]; rd_ser = &name_tmp[name_len]; - - if (name_tmp[name_len -1] != '\0') + if ('\0' != name_tmp[name_len -1]) { - GNUNET_break_op (0); - GNUNET_SERVER_receive_done (client, GNUNET_OK); + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } - - struct GNUNET_NAMESTORE_RecordData rd[rd_count]; - - res = GNUNET_NAMESTORE_records_deserialize(rd_ser_len, rd_ser, rd_count, rd); - if ((res != GNUNET_OK) || (rd_count != 1)) + if (NULL == (pkey = GNUNET_CRYPTO_rsa_decode_key (pkey_tmp, key_len))) { - GNUNET_break_op (0); - goto send; + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + if (GNUNET_OK != + GNUNET_NAMESTORE_records_deserialize (rd_ser_len, rd_ser, rd_count, &rd)) + { + GNUNET_break (0); + GNUNET_CRYPTO_rsa_key_free (pkey); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; } + /* Extracting and converting private key */ - pkey = GNUNET_CRYPTO_rsa_decode_key((char *) pkey_tmp, key_len); - GNUNET_assert (pkey != NULL); - GNUNET_CRYPTO_rsa_key_get_public(pkey, &pub); - GNUNET_CRYPTO_short_hash (&pub, sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded), &pubkey_hash); - GNUNET_CRYPTO_short_hash_double (&pubkey_hash, &long_hash); + GNUNET_CRYPTO_rsa_key_get_public (pkey, &crc.pubkey); + GNUNET_CRYPTO_short_hash (&crc.pubkey, + sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded), + &pubkey_hash); + learn_private_key (pkey); - if (GNUNET_NO == GNUNET_CONTAINER_multihashmap_contains(zonekeys, &long_hash)) + conv_name = GNUNET_NAMESTORE_normalize_string(name_tmp); + if (NULL == conv_name) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received new private key for zone `%s'\n",GNUNET_short_h2s(&pubkey_hash)); - - cc = GNUNET_malloc (sizeof (struct GNUNET_NAMESTORE_CryptoContainer)); - cc->privkey = GNUNET_CRYPTO_rsa_decode_key((char *) pkey_tmp, key_len); - cc->pubkey = GNUNET_malloc(sizeof (pub)); - memcpy (cc->pubkey, &pub, sizeof(pub)); - cc->zone = pubkey_hash; - GNUNET_CONTAINER_multihashmap_put(zonekeys, &long_hash, cc, GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Error converting name `%s'\n", name_tmp); + return; } - + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Creating record for name `%s' in zone `%s'\n", + conv_name, GNUNET_short_h2s(&pubkey_hash)); crc.expire = GNUNET_TIME_absolute_ntoh(rp_msg->expire); crc.res = GNUNET_SYSERR; - crc.pkey = pkey; - crc.pubkey = &pub; - crc.rd = rd; - crc.name = name_tmp; - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Creating record for name `%s' in zone `%s'\n", name_tmp, GNUNET_short_h2s(&pubkey_hash)); + crc.rd = &rd; + crc.name = conv_name; /* Get existing records for name */ - res = GSN_database->iterate_records(GSN_database->cls, &pubkey_hash, name_tmp, 0, &handle_create_record_it, &crc); + res = GSN_database->iterate_records (GSN_database->cls, &pubkey_hash, conv_name, 0, + &handle_create_record_it, &crc); + GNUNET_free (conv_name); if (res != GNUNET_SYSERR) res = GNUNET_OK; - GNUNET_CRYPTO_rsa_key_free(pkey); - pkey = NULL; /* Send response */ -send: - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Sending `%s' message\n", "RECORD_CREATE_RESPONSE"); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Sending `%s' message\n", "RECORD_CREATE_RESPONSE"); rcr_msg.gns_header.header.type = htons (GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_CREATE_RESPONSE); rcr_msg.gns_header.header.size = htons (sizeof (struct RecordCreateResponseMessage)); rcr_msg.gns_header.r_id = htonl (rid); @@ -982,365 +1275,397 @@ send: rcr_msg.op_result = htonl (GNUNET_NO); else rcr_msg.op_result = htonl (GNUNET_SYSERR); - GNUNET_SERVER_notification_context_unicast (snc, nc->client, (const struct GNUNET_MessageHeader *) &rcr_msg, GNUNET_NO); - + GNUNET_SERVER_notification_context_unicast (snc, nc->client, + &rcr_msg.gns_header.header, + GNUNET_NO); GNUNET_SERVER_receive_done (client, GNUNET_OK); } +/** + * Context for record remove operations passed from 'handle_record_remove' to + * 'handle_record_remove_it' as closure + */ struct RemoveRecordContext { - struct GNUNET_NAMESTORE_RecordData *rd; - struct GNUNET_CRYPTO_RsaPrivateKey *pkey; - int remove_name; - uint16_t op_res; + /** + * Record to remove + */ + const struct GNUNET_NAMESTORE_RecordData *rd; + + /** + * See RECORD_REMOVE_RESULT_*-codes. Set by 'handle_record_remove_it' + * to the result of the operation. + */ + int32_t op_res; }; + +/** + * We are to remove a record (or all records for a given name). This function + * will be called with the existing records (if there are any) and is to then + * compute what to keep and trigger the necessary changes. + * + * @param cls the 'struct RecordRemoveContext' with information about what to remove + * @param zone_key public key of the zone + * @param expire when does the corresponding block in the DHT expire (until + * when should we never do a DHT lookup for the same name again)? + * @param name name that is being mapped (at most 255 characters long) + * @param rd_count number of entries in 'rd' array + * @param rd array of records with data to store + * @param signature signature of the record block, NULL if signature is unavailable (i.e. + * because the user queried for a particular record type only) + */ static void handle_record_remove_it (void *cls, - const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *zone_key, - struct GNUNET_TIME_Absolute expire, - const char *name, - unsigned int rd_count, - const struct GNUNET_NAMESTORE_RecordData *rd, - const struct GNUNET_CRYPTO_RsaSignature *signature) + const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *zone_key, + struct GNUNET_TIME_Absolute expire, + const char *name, + unsigned int rd_count, + const struct GNUNET_NAMESTORE_RecordData *rd, + const struct GNUNET_CRYPTO_RsaSignature *signature) { + static struct GNUNET_CRYPTO_RsaSignature dummy_signature; struct RemoveRecordContext *rrc = cls; unsigned int c; - int res; int found; - unsigned int rd_count_new; - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Name `%s 'currently has %u records\n", name, rd_count); + struct GNUNET_CRYPTO_ShortHashCode pubkey_hash; - if (rd_count == 0) + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Name `%s 'currently has %u records\n", + name, rd_count); + if (0 == rd_count) { /* Could not find record to remove */ - rrc->op_res = 1; + rrc->op_res = RECORD_REMOVE_RESULT_NO_RECORDS; return; } - /* Find record to remove */ - found = GNUNET_SYSERR; + found = -1; for (c = 0; c < rd_count; c++) { - /* - if (rd[c].flags != rrc->rd->flags) - continue;*/ - if (rd[c].record_type != rrc->rd->record_type) - continue; - /* - if (rd[c].data_size != rrc->rd->data_size) - continue; - GNUNET_break(0); - if (0 != memcmp (rd[c].data, rrc->rd->data, rrc->rd->data_size)) - continue; - GNUNET_break(0); */ + if (GNUNET_YES != + GNUNET_NAMESTORE_records_cmp (&rd[c], + rrc->rd)) + continue; GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Found record to remove!\n", rd_count); found = c; break; } - if (GNUNET_SYSERR == found) + if (-1 == found) { /* Could not find record to remove */ - rrc->op_res = 2; + rrc->op_res = RECORD_REMOVE_RESULT_RECORD_NOT_FOUND; return; } - - if (rd_count-1 == 0) + if (1 == rd_count) { - struct GNUNET_CRYPTO_ShortHashCode pubkey_hash; - GNUNET_CRYPTO_short_hash (zone_key, sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded), &pubkey_hash); - res = GSN_database->remove_records (GSN_database->cls, - &pubkey_hash, - name); GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "No records left for name `%s', removing name\n", - name, res); - if (GNUNET_OK != res) + name); + GNUNET_CRYPTO_short_hash (zone_key, + sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded), + &pubkey_hash); + if (GNUNET_OK != + GSN_database->remove_records (GSN_database->cls, + &pubkey_hash, + name)) { - /* Could put records into database */ - rrc->op_res = 4; + /* Could not remove records from database */ + rrc->op_res = RECORD_REMOVE_RESULT_FAILED_TO_REMOVE; return; } - rrc->op_res = 0; + rrc->op_res = RECORD_REMOVE_RESULT_SUCCESS; return; } - rd_count_new = rd_count -1; - struct GNUNET_NAMESTORE_RecordData rd_new[rd_count_new]; - - unsigned int c2 = 0; - for (c = 0; c < rd_count; c++) { - if (c != found) + struct GNUNET_NAMESTORE_RecordData rd_new[rd_count - 1]; + unsigned int c2 = 0; + + for (c = 0; c < rd_count; c++) { - GNUNET_assert (c2 < rd_count_new); - rd_new[c2] = rd[c]; - c2++; + if (c == found) + continue; + rd_new[c2++] = rd[c]; + } + if (GNUNET_OK != + GSN_database->put_records(GSN_database->cls, + zone_key, + expire, + name, + rd_count - 1, rd_new, + &dummy_signature)) + { + /* Could not put records into database */ + rrc->op_res = RECORD_REMOVE_RESULT_FAILED_TO_PUT_UPDATE; + return; } } - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Name `%s' now has %u records\n", name, rd_count_new); - - /* Create dummy signature */ - struct GNUNET_CRYPTO_RsaSignature dummy_signature; - memset (&dummy_signature, '\0', sizeof (dummy_signature)); - - - /* Put records */ - res = GSN_database->put_records(GSN_database->cls, - zone_key, - expire, - name, - rd_count_new, rd_new, - &dummy_signature); - if (GNUNET_OK != res) - { - /* Could put records into database */ - rrc->op_res = 4; - return; - } - - rrc->op_res = 0; + rrc->op_res = RECORD_REMOVE_RESULT_SUCCESS; } -static void handle_record_remove (void *cls, - struct GNUNET_SERVER_Client * client, - const struct GNUNET_MessageHeader * message) + +/** + * Handles a 'GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_REMOVE' message + * + * @param cls unused + * @param client GNUNET_SERVER_Client sending the message + * @param message message of type 'struct RecordRemoveMessage' + */ +static void +handle_record_remove (void *cls, + struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received `%s' message\n", "NAMESTORE_RECORD_REMOVE"); struct GNUNET_NAMESTORE_Client *nc; + const struct RecordRemoveMessage *rr_msg; struct RecordRemoveResponseMessage rrr_msg; struct GNUNET_CRYPTO_RsaPrivateKey *pkey; - struct GNUNET_NAMESTORE_CryptoContainer *cc = NULL; struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded pub; struct GNUNET_CRYPTO_ShortHashCode pubkey_hash; - GNUNET_HashCode long_hash; - char * pkey_tmp = NULL; - char * name_tmp = NULL; - char * rd_ser = NULL; - size_t key_len = 0; - size_t name_len = 0; - size_t rd_ser_len = 0; - size_t msg_size = 0; - size_t msg_size_exp = 0; + struct GNUNET_NAMESTORE_RecordData rd; + const char *pkey_tmp; + const char *name_tmp; + const char *rd_ser; + char * conv_name; + size_t key_len; + size_t name_len; + size_t rd_ser_len; + size_t msg_size; + size_t msg_size_exp; uint32_t rd_count; - uint32_t rid = 0; - - int res = GNUNET_SYSERR; + uint32_t rid; + struct RemoveRecordContext rrc; + int res; + uint64_t off; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Received `%s' message\n", + "NAMESTORE_RECORD_REMOVE"); if (ntohs (message->size) < sizeof (struct RecordRemoveMessage)) { - GNUNET_break_op (0); - GNUNET_SERVER_receive_done (client, GNUNET_OK); + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } - - nc = client_lookup(client); - if (nc == NULL) + if (NULL == (nc = client_lookup(client))) { - GNUNET_break_op (0); - GNUNET_SERVER_receive_done (client, GNUNET_OK); + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } - - struct RecordRemoveMessage * rr_msg = (struct RecordRemoveMessage *) message; + rr_msg = (const struct RecordRemoveMessage *) message; rid = ntohl (rr_msg->gns_header.r_id); name_len = ntohs (rr_msg->name_len); rd_ser_len = ntohs (rr_msg->rd_len); rd_count = ntohs (rr_msg->rd_count); key_len = ntohs (rr_msg->pkey_len); msg_size = ntohs (message->size); - - if (msg_size > GNUNET_SERVER_MAX_MESSAGE_SIZE) - { - GNUNET_break_op (0); - GNUNET_SERVER_receive_done (client, GNUNET_OK); - return; - } - - if ((name_len >=256) || (name_len == 0)) + if ((name_len >= MAX_NAME_LEN) || (0 == name_len) || (1 < rd_count) ) { - GNUNET_break_op (0); - GNUNET_SERVER_receive_done (client, GNUNET_OK); + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } - msg_size_exp = sizeof (struct RecordRemoveMessage) + key_len + name_len + rd_ser_len; if (msg_size != msg_size_exp) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Expected message %u size but message size is %u \n", msg_size_exp, msg_size); - GNUNET_break_op (0); - GNUNET_SERVER_receive_done (client, GNUNET_OK); + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } - - pkey_tmp = (char *) &rr_msg[1]; + pkey_tmp = (const char *) &rr_msg[1]; name_tmp = &pkey_tmp[key_len]; rd_ser = &name_tmp[name_len]; - - - if ((name_len == 0) || (name_len > 256)) + if ('\0' != name_tmp[name_len -1]) { - GNUNET_break_op (0); - GNUNET_SERVER_receive_done (client, GNUNET_OK); + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } - - if (name_tmp[name_len -1] != '\0') + if (NULL == (pkey = GNUNET_CRYPTO_rsa_decode_key (pkey_tmp, key_len))) { - GNUNET_break_op (0); - GNUNET_SERVER_receive_done (client, GNUNET_OK); + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } - - /* Extracting and converting private key */ - pkey = GNUNET_CRYPTO_rsa_decode_key((char *) pkey_tmp, key_len); - GNUNET_assert (pkey != NULL); - GNUNET_CRYPTO_rsa_key_get_public(pkey, &pub); - GNUNET_CRYPTO_short_hash (&pub, sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded), &pubkey_hash); - GNUNET_CRYPTO_short_hash_double (&pubkey_hash, &long_hash); - - if (GNUNET_NO == GNUNET_CONTAINER_multihashmap_contains(zonekeys, &long_hash)) + GNUNET_CRYPTO_rsa_key_get_public (pkey, &pub); + GNUNET_CRYPTO_short_hash (&pub, + sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded), + &pubkey_hash); + learn_private_key (pkey); + if (GNUNET_OK != + GNUNET_NAMESTORE_records_deserialize (rd_ser_len, rd_ser, rd_count, &rd)) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received new private key for zone `%s'\n",GNUNET_short_h2s(&pubkey_hash)); - cc = GNUNET_malloc (sizeof (struct GNUNET_NAMESTORE_CryptoContainer)); - cc->privkey = GNUNET_CRYPTO_rsa_decode_key((char *) pkey_tmp, key_len); - cc->pubkey = GNUNET_malloc(sizeof (pub)); - memcpy (cc->pubkey, &pub, sizeof(pub)); - cc->zone = pubkey_hash; - - GNUNET_CONTAINER_multihashmap_put(zonekeys, &long_hash, cc, GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY); + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; } - - struct GNUNET_NAMESTORE_RecordData rd[rd_count]; - res = GNUNET_NAMESTORE_records_deserialize(rd_ser_len, rd_ser, rd_count, rd); - if ((res != GNUNET_OK) || (rd_count > 1)) + conv_name = GNUNET_NAMESTORE_normalize_string(name_tmp); + if (NULL == conv_name) { - GNUNET_break_op (0); - goto send; + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Error converting name `%s'\n", name_tmp); + return; } if (0 == rd_count) { /* remove the whole name and all records */ - /* Database operation */ res = GSN_database->remove_records (GSN_database->cls, - &pubkey_hash, - name_tmp); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Removing name `%s': %s\n", - name_tmp, (GNUNET_OK == res) ? "OK" : "FAIL"); - + &pubkey_hash, + conv_name); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Removing name `%s': %s\n", + conv_name, (GNUNET_OK == res) ? "OK" : "FAILED"); if (GNUNET_OK != res) /* Could not remove entry from database */ - res = 4; + res = RECORD_REMOVE_RESULT_FAILED_TO_PUT_UPDATE; else - res = 0; + res = RECORD_REMOVE_RESULT_SUCCESS; } else { /* remove a single record */ - struct RemoveRecordContext rrc; - rrc.rd = rd; - rrc.pkey = pkey; - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Removing record for name `%s' in zone `%s'\n", name_tmp, GNUNET_short_h2s(&pubkey_hash)); - - /* Database operation */ - res = GSN_database->iterate_records (GSN_database->cls, - &pubkey_hash, - name_tmp, - 0, - handle_record_remove_it, &rrc); - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Removing record for name `%s': %s\n", - name_tmp, (rrc.op_res == 0) ? "OK" : "FAIL"); - res = rrc.op_res; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Removing record for name `%s' in zone `%s'\n", conv_name, + GNUNET_short_h2s (&pubkey_hash)); + rrc.rd = &rd; + rrc.op_res = RECORD_REMOVE_RESULT_RECORD_NOT_FOUND; + off = 0; + res = GNUNET_OK; + while ( (RECORD_REMOVE_RESULT_RECORD_NOT_FOUND == rrc.op_res) && + (GNUNET_OK == res) ) + { + res = GSN_database->iterate_records (GSN_database->cls, + &pubkey_hash, + conv_name, + off++, + &handle_record_remove_it, &rrc); + } + switch (res) + { + case GNUNET_OK: + res = rrc.op_res; + break; + case GNUNET_NO: + GNUNET_break (RECORD_REMOVE_RESULT_NO_RECORDS == rrc.op_res); + res = RECORD_REMOVE_RESULT_NO_RECORDS; + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + _("Failed to find record to remove\n")); + break; + case GNUNET_SYSERR: + res = RECORD_REMOVE_RESULT_FAILED_ACCESS_DATABASE; + break; + default: + GNUNET_break (0); + res = RECORD_REMOVE_RESULT_FAILED_INTERNAL_ERROR; + break; + } } - /* Send response */ -send: - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Sending `%s' message\n", "RECORD_REMOVE_RESPONSE"); + GNUNET_free (conv_name); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Sending `%s' message\n", + "RECORD_REMOVE_RESPONSE"); rrr_msg.gns_header.header.type = htons (GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_REMOVE_RESPONSE); rrr_msg.gns_header.header.size = htons (sizeof (struct RecordRemoveResponseMessage)); rrr_msg.gns_header.r_id = htonl (rid); rrr_msg.op_result = htonl (res); - GNUNET_SERVER_notification_context_unicast (snc, nc->client, (const struct GNUNET_MessageHeader *) &rrr_msg, GNUNET_NO); - - GNUNET_CRYPTO_rsa_key_free (pkey); - + GNUNET_SERVER_notification_context_unicast (snc, nc->client, + &rrr_msg.gns_header.header, + GNUNET_NO); GNUNET_SERVER_receive_done (client, GNUNET_OK); } +/** + * Context for record remove operations passed from 'handle_zone_to_name' to + * 'handle_zone_to_name_it' as closure + */ struct ZoneToNameCtx { + /** + * Namestore client + */ struct GNUNET_NAMESTORE_Client *nc; + + /** + * Request id (to be used in the response to the client). + */ uint32_t rid; + + /** + * Set to GNUNET_OK on success, GNUNET_SYSERR on error. Note that + * not finding a name for the zone still counts as a 'success' here, + * as this field is about the success of executing the IPC protocol. + */ + int success; }; + +/** + * Zone to name iterator + * + * @param cls struct ZoneToNameCtx * + * @param zone_key the zone key + * @param expire expiration date + * @param name name + * @param rd_count number of records + * @param rd record data + * @param signature signature + */ static void handle_zone_to_name_it (void *cls, - const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *zone_key, - struct GNUNET_TIME_Absolute expire, - const char *name, - unsigned int rd_count, - const struct GNUNET_NAMESTORE_RecordData *rd, - const struct GNUNET_CRYPTO_RsaSignature *signature) + const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *zone_key, + struct GNUNET_TIME_Absolute expire, + const char *name, + unsigned int rd_count, + const struct GNUNET_NAMESTORE_RecordData *rd, + const struct GNUNET_CRYPTO_RsaSignature *signature) { - struct ZoneToNameCtx * ztn_ctx = cls; + struct ZoneToNameCtx *ztn_ctx = cls; struct ZoneToNameResponseMessage *ztnr_msg; - int16_t res = GNUNET_SYSERR; - uint16_t name_len = 0; - uint16_t rd_ser_len = 0 ; - int32_t contains_sig = 0; - size_t msg_size = 0; - - char *rd_ser = NULL; + int16_t res; + size_t name_len; + size_t rd_ser_len; + size_t msg_size; char *name_tmp; char *rd_tmp; char *sig_tmp; - if ((zone_key != NULL) && (name != NULL)) + if ((NULL != zone_key) && (NULL != name)) { /* found result */ - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Found results: name is `%s', has %u records\n", name, rd_count); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Found result: name `%s' has %u records\n", + name, rd_count); res = GNUNET_YES; - name_len = strlen (name) +1; + name_len = strlen (name) + 1; } else { /* no result found */ - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Found no results\n"); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Found no results\n"); res = GNUNET_NO; name_len = 0; } - - if (rd_count > 0) + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Sending `%s' message\n", + "ZONE_TO_NAME_RESPONSE"); + rd_ser_len = GNUNET_NAMESTORE_records_get_size (rd_count, rd); + msg_size = sizeof (struct ZoneToNameResponseMessage) + name_len + rd_ser_len; + if (NULL != signature) + msg_size += sizeof (struct GNUNET_CRYPTO_RsaSignature); + if (msg_size >= GNUNET_SERVER_MAX_MESSAGE_SIZE) { - rd_ser_len = GNUNET_NAMESTORE_records_get_size (rd_count, rd); - rd_ser = GNUNET_malloc (rd_ser_len); - GNUNET_NAMESTORE_records_serialize(rd_count, rd, rd_ser_len, rd_ser); + GNUNET_break (0); + ztn_ctx->success = GNUNET_SYSERR; + return; } - else - rd_ser_len = 0; - - if (signature != NULL) - contains_sig = GNUNET_YES; - else - contains_sig = GNUNET_NO; - - - - msg_size = sizeof (struct ZoneToNameResponseMessage) + name_len + rd_ser_len + contains_sig * sizeof (struct GNUNET_CRYPTO_RsaSignature); ztnr_msg = GNUNET_malloc (msg_size); - - name_tmp = (char *) &ztnr_msg[1]; - rd_tmp = &name_tmp[name_len]; - sig_tmp = &rd_tmp[rd_ser_len]; - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Sending `%s' message\n", "ZONE_TO_NAME_RESPONSE"); ztnr_msg->gns_header.header.type = htons (GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_TO_NAME_RESPONSE); ztnr_msg->gns_header.header.size = htons (msg_size); ztnr_msg->gns_header.r_id = htonl (ztn_ctx->rid); @@ -1348,369 +1673,384 @@ handle_zone_to_name_it (void *cls, ztnr_msg->rd_len = htons (rd_ser_len); ztnr_msg->rd_count = htons (rd_count); ztnr_msg->name_len = htons (name_len); - ztnr_msg->expire = GNUNET_TIME_absolute_hton(expire); - if (zone_key != NULL) + ztnr_msg->expire = GNUNET_TIME_absolute_hton (expire); + if (NULL != zone_key) ztnr_msg->zone_key = *zone_key; - else - memset (&ztnr_msg->zone_key, '\0', sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded)); - - if ((name_len > 0) && (name != NULL)) + name_tmp = (char *) &ztnr_msg[1]; + if (NULL != name) memcpy (name_tmp, name, name_len); - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Name is `%s', has %u records, rd ser len %u msg_size %u\n", name, rd_count, rd_ser_len, msg_size); - if ((rd_ser_len > 0) && (rd_ser != NULL)) - memcpy (rd_tmp, rd_ser, rd_ser_len); - if ((GNUNET_YES == contains_sig) && (signature != NULL)) - memcpy (sig_tmp, signature, contains_sig * sizeof (struct GNUNET_CRYPTO_RsaSignature)); - - GNUNET_SERVER_notification_context_unicast (snc, ztn_ctx->nc->client, (const struct GNUNET_MessageHeader *) ztnr_msg, GNUNET_NO); + rd_tmp = &name_tmp[name_len]; + GNUNET_NAMESTORE_records_serialize (rd_count, rd, rd_ser_len, rd_tmp); + sig_tmp = &rd_tmp[rd_ser_len]; + if (NULL != signature) + memcpy (sig_tmp, signature, sizeof (struct GNUNET_CRYPTO_RsaSignature)); + ztn_ctx->success = GNUNET_OK; + GNUNET_SERVER_notification_context_unicast (snc, ztn_ctx->nc->client, + &ztnr_msg->gns_header.header, + GNUNET_NO); GNUNET_free (ztnr_msg); - GNUNET_free_non_null (rd_ser); } -static void handle_zone_to_name (void *cls, - struct GNUNET_SERVER_Client * client, - const struct GNUNET_MessageHeader * message) +/** + * Handles a 'GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_TO_NAME' message + * + * @param cls unused + * @param client GNUNET_SERVER_Client sending the message + * @param message message of type 'struct ZoneToNameMessage' + */ +static void +handle_zone_to_name (void *cls, + struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received `%s' message\n", "ZONE_TO_NAME"); struct GNUNET_NAMESTORE_Client *nc; + const struct ZoneToNameMessage *ztn_msg; struct ZoneToNameCtx ztn_ctx; - size_t msg_size = 0; - uint32_t rid = 0; - - if (ntohs (message->size) != sizeof (struct ZoneToNameMessage)) - { - GNUNET_break_op (0); - GNUNET_SERVER_receive_done (client, GNUNET_OK); - return; - } - - nc = client_lookup(client); - if (nc == NULL) - { - GNUNET_break_op (0); - GNUNET_SERVER_receive_done (client, GNUNET_OK); - return; - } - - struct ZoneToNameMessage *ztn_msg = (struct ZoneToNameMessage *) message; - if (msg_size > GNUNET_SERVER_MAX_MESSAGE_SIZE) + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Received `%s' message\n", + "ZONE_TO_NAME"); + ztn_msg = (const struct ZoneToNameMessage *) message; + if (NULL == (nc = client_lookup(client))) { - GNUNET_break_op (0); - GNUNET_SERVER_receive_done (client, GNUNET_OK); + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } - - rid = ntohl (ztn_msg->gns_header.r_id); - - ztn_ctx.rid = rid; + ztn_ctx.rid = ntohl (ztn_msg->gns_header.r_id); ztn_ctx.nc = nc; - - struct GNUNET_CRYPTO_ShortHashAsciiEncoded z_tmp; - GNUNET_CRYPTO_short_hash_to_enc(&ztn_msg->zone, &z_tmp); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Looking up name for zone `%s' in zone `%s'\n", - (char *) &z_tmp, - GNUNET_short_h2s (&ztn_msg->value_zone)); - - GSN_database->zone_to_name (GSN_database->cls, &ztn_msg->zone, &ztn_msg->value_zone, &handle_zone_to_name_it, &ztn_ctx); - - GNUNET_SERVER_receive_done (client, GNUNET_OK); + ztn_ctx.success = GNUNET_SYSERR; + if (GNUNET_SYSERR == + GSN_database->zone_to_name (GSN_database->cls, + &ztn_msg->zone, + &ztn_msg->value_zone, + &handle_zone_to_name_it, &ztn_ctx)) + { + /* internal error, hang up instead of signalling something + that might be wrong */ + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + GNUNET_SERVER_receive_done (client, ztn_ctx.success); } /** - * Copy record, data has to be free separetely + * Zone iteration processor result */ -void -copy_record (const struct GNUNET_NAMESTORE_RecordData *src, struct GNUNET_NAMESTORE_RecordData *dest) +enum ZoneIterationResult { + /** + * Found records, but all records were filtered + * Continue to iterate + */ + IT_ALL_RECORDS_FILTERED = -1, - memcpy (dest, src, sizeof (struct GNUNET_NAMESTORE_RecordData)); - dest->data = GNUNET_malloc (src->data_size); - memcpy ((void *) dest->data, src->data, src->data_size); -} + /** + * Found records, + * Continue to iterate with next iteration_next call + */ + IT_SUCCESS_MORE_AVAILABLE = 0, + + /** + * Iteration complete + */ + IT_SUCCESS_NOT_MORE_RESULTS_AVAILABLE = 1 +}; + +/** + * Context for record remove operations passed from + * 'run_zone_iteration_round' to 'zone_iteraterate_proc' as closure + */ struct ZoneIterationProcResult { + /** + * The zone iteration handle + */ struct GNUNET_NAMESTORE_ZoneIteration *zi; + /** + * Iteration result: iteration done? + * IT_SUCCESS_MORE_AVAILABLE: if there may be more results overall but + * we got one for now and have sent it to the client + * IT_SUCCESS_NOT_MORE_RESULTS_AVAILABLE: if there are no further results, + * IT_ALL_RECORDS_FILTERED: if all results were filtered so far. + */ int res_iteration_finished; - int records_included; - int has_signature; - char *name; - struct GNUNET_CRYPTO_ShortHashCode zone_hash; - struct GNUNET_NAMESTORE_RecordData *rd; - struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded zone_key; - struct GNUNET_CRYPTO_RsaSignature signature; - struct GNUNET_TIME_Absolute expire; }; -void zone_iteraterate_proc (void *cls, - const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *zone_key, - struct GNUNET_TIME_Absolute expire, - const char *name, - unsigned int rd_count, - const struct GNUNET_NAMESTORE_RecordData *rd, - const struct GNUNET_CRYPTO_RsaSignature *signature) +/** + * Process results for zone iteration from database + * + * @param cls struct ZoneIterationProcResult *proc + * @param zone_key the zone key + * @param expire expiration time + * @param name name + * @param rd_count number of records for this name + * @param rd record data + * @param signature block signature + */ +static void +zone_iteraterate_proc (void *cls, + const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *zone_key, + struct GNUNET_TIME_Absolute expire, + const char *name, + unsigned int rd_count, + const struct GNUNET_NAMESTORE_RecordData *rd, + const struct GNUNET_CRYPTO_RsaSignature *signature) { struct ZoneIterationProcResult *proc = cls; - struct GNUNET_NAMESTORE_RecordData *rd_filtered; - struct GNUNET_CRYPTO_RsaSignature * new_signature; + struct GNUNET_NAMESTORE_RecordData rd_filtered[rd_count]; + struct GNUNET_CRYPTO_RsaSignature *new_signature = NULL; struct GNUNET_NAMESTORE_CryptoContainer *cc; - struct GNUNET_CRYPTO_ShortHashCode hash; - GNUNET_HashCode long_hash; - struct GNUNET_TIME_Absolute e; - unsigned int rd_count_filtered = 0; - int include; - int c; - - proc->res_iteration_finished = GNUNET_NO; - proc->records_included = 0; + struct GNUNET_HashCode long_hash; + struct GNUNET_CRYPTO_ShortHashCode zone_hash; + struct ZoneIterationResponseMessage *zir_msg; + struct GNUNET_TIME_Relative rt; + unsigned int rd_count_filtered; + unsigned int c; + size_t name_len; + size_t rd_ser_len; + size_t msg_size; + char *name_tmp; + char *rd_ser; - if ((zone_key == NULL) && (name == NULL)) + proc->res_iteration_finished = IT_SUCCESS_MORE_AVAILABLE; + if ((NULL == zone_key) && (NULL == name)) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Iteration done\n"); - proc->res_iteration_finished = GNUNET_YES; - proc->rd = NULL; - proc->name = NULL; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Iteration done\n"); + proc->res_iteration_finished = IT_SUCCESS_NOT_MORE_RESULTS_AVAILABLE; + return; } - else if ((zone_key != NULL) && (name != NULL)) /* just a safety check */ + if ((NULL == zone_key) || (NULL == name)) { - rd_filtered = GNUNET_malloc (rd_count * sizeof (struct GNUNET_NAMESTORE_RecordData)); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received result for zone iteration: `%s'\n", name); - for (c = 0; c < rd_count; c++) + /* what is this!? should never happen */ + GNUNET_break (0); + return; + } + rd_count_filtered = 0; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Received result for zone iteration: `%s'\n", + name); + for (c = 0; c < rd_count; c++) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Record %u has flags: %x must have flags are %x, must not have flags are %x\n", + c, rd[c].flags, + proc->zi->must_have_flags, + proc->zi->must_not_have_flags); + /* Checking must have flags, except 'relative-expiration' which is a special flag */ + if ((rd[c].flags & proc->zi->must_have_flags & (~GNUNET_NAMESTORE_RF_RELATIVE_EXPIRATION)) + != (proc->zi->must_have_flags & (~ GNUNET_NAMESTORE_RF_RELATIVE_EXPIRATION))) { - include = GNUNET_YES; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Record %i has flags: 0x%x must have 0x%x \n", - c, rd[c].flags, proc->zi->must_have_flags); - /* Checking must have flags */ - if ((rd[c].flags & proc->zi->must_have_flags) == proc->zi->must_have_flags) - { - /* Include */ - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Record %i has flags: Include \n", c); - } - else - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Record %i has flags: Not include \n", c); - include = GNUNET_NO; - } - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Record %i has flags: 0x%x must not have 0x%x\n", - c, rd[c].flags, proc->zi->must_not_have_flags); - if ((rd[c].flags & proc->zi->must_not_have_flags) != 0) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Record %i has flags: Not include \n", c); - include = GNUNET_NO; - } - else - { - /* Include */ - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Record %i has flags: Include \n", c); - } - if (GNUNET_YES == include) - { - copy_record (&rd[c], &rd_filtered[rd_count_filtered]); - rd_count_filtered++; - } - + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Record %u lacks 'must-have' flags: Not included\n", c); + continue; } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Included %i of %i records \n", rd_count_filtered, rd_count); - - proc->records_included = rd_count_filtered; - if (0 == rd_count_filtered) + /* Checking must-not-have flags */ + if (0 != (rd[c].flags & proc->zi->must_not_have_flags)) { - GNUNET_free (rd_filtered); - rd_filtered = NULL; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Record %u has 'must-not-have' flags: Not included\n", c); + continue; } - proc->rd = rd_filtered; - proc->name = GNUNET_strdup(name); - memcpy (&proc->zone_key, zone_key, sizeof (proc->zone_key)); - - /* Signature */ - proc->has_signature = GNUNET_NO; - GNUNET_CRYPTO_short_hash (zone_key, sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded), &hash); - GNUNET_CRYPTO_short_hash_double(&hash, &long_hash); - proc->zone_hash = hash; - - if (GNUNET_CONTAINER_multihashmap_contains(zonekeys, &long_hash)) + rd_filtered[rd_count_filtered] = rd[c]; + /* convert relative to absolute expiration time unless explicitly requested otherwise */ + if ( (0 == (proc->zi->must_have_flags & GNUNET_NAMESTORE_RF_RELATIVE_EXPIRATION)) && + (0 != (rd[c].flags & GNUNET_NAMESTORE_RF_RELATIVE_EXPIRATION)) ) + { + /* should convert relative-to-absolute expiration time */ + rt.rel_value = rd[c].expiration_time; + rd_filtered[c].expiration_time = GNUNET_TIME_relative_to_absolute (rt).abs_value; + rd_filtered[c].flags &= ~ GNUNET_NAMESTORE_RF_RELATIVE_EXPIRATION; + } + /* we NEVER keep the 'authority' flag */ + rd_filtered[c].flags &= ~ GNUNET_NAMESTORE_RF_AUTHORITY; + rd_count_filtered++; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Included %u of %u records\n", + rd_count_filtered, rd_count); + + signature = NULL; + if ( (rd_count_filtered > 0) && + (0 == (proc->zi->must_have_flags & GNUNET_NAMESTORE_RF_RELATIVE_EXPIRATION)) ) + { + /* compute / obtain signature, but only if we (a) have records and (b) expiration times were + converted to absolute expiration times */ + GNUNET_CRYPTO_short_hash (zone_key, + sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded), + &zone_hash); + GNUNET_CRYPTO_short_hash_double (&zone_hash, &long_hash); + if (NULL != (cc = GNUNET_CONTAINER_multihashmap_get(zonekeys, &long_hash))) { - cc = GNUNET_CONTAINER_multihashmap_get(zonekeys, &long_hash); - e = get_block_expiration_time(rd_count_filtered, rd_filtered); - proc->expire = e; - new_signature = GNUNET_NAMESTORE_create_signature(cc->privkey, e, name, rd_filtered, rd_count_filtered); - GNUNET_assert (signature != NULL); - proc->signature = (*new_signature); - GNUNET_free (new_signature); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Creating signature for `%s' in zone `%s' with %u records and expiration %llu\n", - name, GNUNET_short_h2s(&hash), rd_count_filtered, e.abs_value); - proc->has_signature = GNUNET_YES; + expire = get_block_expiration_time (rd_count_filtered, rd_filtered); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Creating signature for `%s' in zone `%s' with %u records and expiration %llu\n", + name, GNUNET_short_h2s(&zone_hash), + rd_count_filtered, + (unsigned long long) expire.abs_value); + new_signature = GNUNET_NAMESTORE_create_signature (cc->privkey, expire, name, + rd_filtered, rd_count_filtered); + GNUNET_assert (NULL != new_signature); + signature = new_signature; } else if (rd_count_filtered == rd_count) { - proc->expire = expire; if (NULL != signature) - { - proc->signature = (*signature); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Using provided signature for `%s' in zone `%s' with %u records and expiration %llu\n", - name, GNUNET_short_h2s(&hash), rd_count_filtered, expire.abs_value); - proc->has_signature = GNUNET_YES; - } - else - { - memset (&proc->signature, '\0', sizeof (proc->signature)); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "No signature provided for `%s'\n", name); - } + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Using provided signature for `%s' in zone `%s' with %u records and expiration %llu\n", + name, GNUNET_short_h2s (&zone_hash), rd_count_filtered, + (unsigned long long) expire.abs_value); + return; + } } } - else + if (rd_count_filtered == 0) { - GNUNET_break (0); + /* After filtering records there are no records left to return */ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "No records to transmit\n"); + proc->res_iteration_finished = IT_ALL_RECORDS_FILTERED; return; } + if (GNUNET_YES == proc->zi->has_zone) + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Sending name `%s' for iteration over zone `%s'\n", + name, GNUNET_short_h2s(&proc->zi->zone)); + else + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Sending name `%s' for iteration over all zones\n", + name); + name_len = strlen (name) + 1; + rd_ser_len = GNUNET_NAMESTORE_records_get_size (rd_count_filtered, rd_filtered); + msg_size = sizeof (struct ZoneIterationResponseMessage) + name_len + rd_ser_len; + + zir_msg = GNUNET_malloc (msg_size); + zir_msg->gns_header.header.type = htons (GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_ITERATION_RESPONSE); + zir_msg->gns_header.header.size = htons (msg_size); + zir_msg->gns_header.r_id = htonl (proc->zi->request_id); + zir_msg->expire = GNUNET_TIME_absolute_hton (expire); + zir_msg->reserved = htons (0); + zir_msg->name_len = htons (name_len); + zir_msg->rd_count = htons (rd_count_filtered); + zir_msg->rd_len = htons (rd_ser_len); + if (NULL != signature) + zir_msg->signature = *signature; + zir_msg->public_key = *zone_key; + name_tmp = (char *) &zir_msg[1]; + memcpy (name_tmp, name, name_len); + rd_ser = &name_tmp[name_len]; + GNUNET_NAMESTORE_records_serialize (rd_count_filtered, rd_filtered, rd_ser_len, rd_ser); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Sending `%s' message with size %u\n", + "ZONE_ITERATION_RESPONSE", + msg_size); + GNUNET_SERVER_notification_context_unicast (snc, proc->zi->client->client, + (const struct GNUNET_MessageHeader *) zir_msg, + GNUNET_NO); + proc->res_iteration_finished = IT_SUCCESS_MORE_AVAILABLE; + GNUNET_free (zir_msg); + GNUNET_free_non_null (new_signature); } -void find_next_zone_iteration_result (struct ZoneIterationProcResult *proc) -{ +/** + * Perform the next round of the zone iteration. + * + * @param zi zone iterator to process + */ +static void +run_zone_iteration_round (struct GNUNET_NAMESTORE_ZoneIteration *zi) +{ + struct ZoneIterationProcResult proc; + struct ZoneIterationResponseMessage zir_end; struct GNUNET_CRYPTO_ShortHashCode *zone; - if (GNUNET_YES == proc->zi->has_zone) - zone = &proc->zi->zone; + memset (&proc, 0, sizeof (proc)); + proc.zi = zi; + if (GNUNET_YES == zi->has_zone) + zone = &zi->zone; else zone = NULL; - - do + proc.res_iteration_finished = IT_ALL_RECORDS_FILTERED; + while (IT_ALL_RECORDS_FILTERED == proc.res_iteration_finished) { - GSN_database->iterate_records (GSN_database->cls, zone , NULL, proc->zi->offset, &zone_iteraterate_proc, proc); - proc->zi->offset++; + if (GNUNET_SYSERR == + GSN_database->iterate_records (GSN_database->cls, zone, NULL, + zi->offset, + &zone_iteraterate_proc, &proc)) + { + GNUNET_break (0); + break; + } + zi->offset++; } - while ((proc->records_included == 0) && (GNUNET_NO == proc->res_iteration_finished)); -} - - -void send_zone_iteration_result (struct ZoneIterationProcResult *proc) -{ - struct GNUNET_NAMESTORE_ZoneIteration *zi = proc->zi; - - if (GNUNET_YES == proc->res_iteration_finished) + if (IT_SUCCESS_MORE_AVAILABLE == proc.res_iteration_finished) { - struct ZoneIterationResponseMessage zir_msg; - if (zi->has_zone == GNUNET_YES) - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "No more results for zone `%s'\n", GNUNET_short_h2s(&zi->zone)); - else - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "No more results for all zones\n"); - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Sending empty `%s' message\n", "ZONE_ITERATION_RESPONSE"); - zir_msg.gns_header.header.type = htons (GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_ITERATION_RESPONSE); - zir_msg.gns_header.header.size = htons (sizeof (struct ZoneIterationResponseMessage)); - zir_msg.gns_header.r_id = htonl(zi->request_id); - zir_msg.expire = GNUNET_TIME_absolute_hton(GNUNET_TIME_UNIT_ZERO_ABS); - zir_msg.name_len = htons (0); - zir_msg.reserved = htons (0); - zir_msg.rd_count = htons (0); - zir_msg.rd_len = htons (0); - memset (&zir_msg.public_key, '\0', sizeof (zir_msg.public_key)); - memset (&zir_msg.signature, '\0', sizeof (zir_msg.signature)); - GNUNET_SERVER_notification_context_unicast (snc, zi->client->client, (const struct GNUNET_MessageHeader *) &zir_msg, GNUNET_NO); - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Removing zone iterator\n"); - GNUNET_CONTAINER_DLL_remove (zi->client->op_head, zi->client->op_tail, zi); - GNUNET_free (zi); - return; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "More results available\n"); + return; /* more results later */ } + if (GNUNET_YES == zi->has_zone) + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "No more results for zone `%s'\n", + GNUNET_short_h2s(&zi->zone)); else - { - GNUNET_assert (proc->records_included > 0); - - struct ZoneIterationResponseMessage *zir_msg; - if (zi->has_zone == GNUNET_YES) - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Sending name `%s' for iteration over zone `%s'\n", - proc->name, GNUNET_short_h2s(&zi->zone)); - if (zi->has_zone == GNUNET_NO) - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Sending name `%s' for iteration over all zones\n", - proc->name); - - size_t name_len; - size_t rd_ser_len; - size_t msg_size; - char *name_tmp; - char *rd_tmp; - name_len = strlen (proc->name) +1; - - rd_ser_len = GNUNET_NAMESTORE_records_get_size(proc->records_included, proc->rd); - char rd_ser[rd_ser_len]; - GNUNET_NAMESTORE_records_serialize(proc->records_included, proc->rd, rd_ser_len, rd_ser); - msg_size = sizeof (struct ZoneIterationResponseMessage) + name_len + rd_ser_len; - zir_msg = GNUNET_malloc(msg_size); - - name_tmp = (char *) &zir_msg[1]; - rd_tmp = &name_tmp[name_len]; - - zir_msg->gns_header.header.type = htons (GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_ITERATION_RESPONSE); - zir_msg->gns_header.header.size = htons (msg_size); - zir_msg->gns_header.r_id = htonl(zi->request_id); - zir_msg->expire = GNUNET_TIME_absolute_hton(proc->expire); - zir_msg->reserved = htons (0); - zir_msg->name_len = htons (name_len); - zir_msg->rd_count = htons (proc->records_included); - zir_msg->rd_len = htons (rd_ser_len); - zir_msg->signature = proc->signature; - zir_msg->public_key = proc->zone_key; - memcpy (name_tmp, proc->name, name_len); - memcpy (rd_tmp, rd_ser, rd_ser_len); - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Sending `%s' message with size %u\n", "ZONE_ITERATION_RESPONSE", msg_size); - GNUNET_SERVER_notification_context_unicast (snc, zi->client->client, (const struct GNUNET_MessageHeader *) zir_msg, GNUNET_NO); - GNUNET_free (zir_msg); - } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "No more results for all zones\n"); + memset (&zir_end, 0, sizeof (zir_end)); + zir_end.gns_header.header.type = htons (GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_ITERATION_RESPONSE); + zir_end.gns_header.header.size = htons (sizeof (struct ZoneIterationResponseMessage)); + zir_end.gns_header.r_id = htonl(zi->request_id); + GNUNET_SERVER_notification_context_unicast (snc, + zi->client->client, + &zir_end.gns_header.header, GNUNET_NO); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Removing zone iterator\n"); + GNUNET_CONTAINER_DLL_remove (zi->client->op_head, zi->client->op_tail, zi); + GNUNET_free (zi); } -void clean_up_zone_iteration_result (struct ZoneIterationProcResult *proc) -{ - int c; - GNUNET_free_non_null (proc->name); - for (c = 0; c < proc->records_included; c++) - { - GNUNET_free ((void *) proc->rd[c].data); - } - GNUNET_free_non_null (proc->rd); - proc->name = NULL; - proc->rd = NULL; -} -static void handle_iteration_start (void *cls, - struct GNUNET_SERVER_Client * client, - const struct GNUNET_MessageHeader * message) +/** + * Handles a 'GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_ITERATION_START' message + * + * @param cls unused + * @param client GNUNET_SERVER_Client sending the message + * @param message message of type 'struct ZoneIterationStartMessage' + */ +static void +handle_iteration_start (void *cls, + struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received `%s' message\n", "ZONE_ITERATION_START"); - - struct ZoneIterationStartMessage * zis_msg = (struct ZoneIterationStartMessage *) message; + static struct GNUNET_CRYPTO_ShortHashCode zeros; + const struct ZoneIterationStartMessage *zis_msg; struct GNUNET_NAMESTORE_Client *nc; struct GNUNET_NAMESTORE_ZoneIteration *zi; - nc = client_lookup(client); - if (nc == NULL) + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received `%s' message\n", "ZONE_ITERATION_START"); + if (NULL == (nc = client_lookup (client))) { - GNUNET_break_op (0); - GNUNET_SERVER_receive_done (client, GNUNET_OK); + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } - + zis_msg = (const struct ZoneIterationStartMessage *) message; zi = GNUNET_malloc (sizeof (struct GNUNET_NAMESTORE_ZoneIteration)); zi->request_id = ntohl (zis_msg->gns_header.r_id); zi->offset = 0; zi->client = nc; zi->must_have_flags = ntohs (zis_msg->must_have_flags); zi->must_not_have_flags = ntohs (zis_msg->must_not_have_flags); - - struct GNUNET_CRYPTO_ShortHashCode dummy; - memset (&dummy, '\0', sizeof (dummy)); - if (0 == memcmp (&dummy, &zis_msg->zone, sizeof (dummy))) + if (0 == memcmp (&zeros, &zis_msg->zone, sizeof (zeros))) { GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Starting to iterate over all zones\n"); zi->zone = zis_msg->zone; @@ -1718,152 +2058,164 @@ static void handle_iteration_start (void *cls, } else { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Starting to iterate over zone `%s'\n", GNUNET_short_h2s (&zis_msg->zone)); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Starting to iterate over zone `%s'\n", GNUNET_short_h2s (&zis_msg->zone)); zi->zone = zis_msg->zone; zi->has_zone = GNUNET_YES; } - GNUNET_CONTAINER_DLL_insert (nc->op_head, nc->op_tail, zi); - - struct ZoneIterationProcResult proc; - proc.zi = zi; - - find_next_zone_iteration_result (&proc); - if (GNUNET_YES == proc.res_iteration_finished) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Zone iteration done\n"); - } - else if (proc.records_included != 0) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Zone iteration return %u records\n", proc.records_included); - } - send_zone_iteration_result (&proc); - clean_up_zone_iteration_result (&proc); - + run_zone_iteration_round (zi); GNUNET_SERVER_receive_done (client, GNUNET_OK); } -static void handle_iteration_stop (void *cls, - struct GNUNET_SERVER_Client * client, - const struct GNUNET_MessageHeader * message) -{ - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received `%s' message\n", "ZONE_ITERATION_STOP"); +/** + * Handles a 'GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_ITERATION_STOP' message + * + * @param cls unused + * @param client GNUNET_SERVER_Client sending the message + * @param message message of type 'struct ZoneIterationStopMessage' + */ +static void +handle_iteration_stop (void *cls, + struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) +{ struct GNUNET_NAMESTORE_Client *nc; struct GNUNET_NAMESTORE_ZoneIteration *zi; - struct ZoneIterationStopMessage * zis_msg = (struct ZoneIterationStopMessage *) message; + const struct ZoneIterationStopMessage *zis_msg; uint32_t rid; - nc = client_lookup(client); - if (nc == NULL) + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Received `%s' message\n", + "ZONE_ITERATION_STOP"); + if (NULL == (nc = client_lookup(client))) { - GNUNET_break_op (0); - GNUNET_SERVER_receive_done (client, GNUNET_OK); + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } - + zis_msg = (const struct ZoneIterationStopMessage *) message; rid = ntohl (zis_msg->gns_header.r_id); - for (zi = nc->op_head; zi != NULL; zi = zi->next) - { + for (zi = nc->op_head; NULL != zi; zi = zi->next) if (zi->request_id == rid) break; - } - if (zi == NULL) + if (NULL == zi) { - GNUNET_break_op (0); - GNUNET_SERVER_receive_done (client, GNUNET_OK); + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } - - GNUNET_CONTAINER_DLL_remove(nc->op_head, nc->op_tail, zi); + GNUNET_CONTAINER_DLL_remove (nc->op_head, nc->op_tail, zi); if (GNUNET_YES == zi->has_zone) - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stopped zone iteration for zone `%s'\n", GNUNET_short_h2s (&zi->zone)); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Stopped zone iteration for zone `%s'\n", + GNUNET_short_h2s (&zi->zone)); else - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stopped zone iteration all zones\n"); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Stopped zone iteration over all zones\n"); GNUNET_free (zi); - GNUNET_SERVER_receive_done (client, GNUNET_OK); } -static void handle_iteration_next (void *cls, - struct GNUNET_SERVER_Client * client, - const struct GNUNET_MessageHeader * message) -{ - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received `%s' message\n", "ZONE_ITERATION_NEXT"); +/** + * Handles a 'GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_ITERATION_NEXT' message + * + * @param cls unused + * @param client GNUNET_SERVER_Client sending the message + * @param message message of type 'struct ZoneIterationNextMessage' + */ +static void +handle_iteration_next (void *cls, + struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) +{ struct GNUNET_NAMESTORE_Client *nc; struct GNUNET_NAMESTORE_ZoneIteration *zi; - struct ZoneIterationStopMessage * zis_msg = (struct ZoneIterationStopMessage *) message; + const struct ZoneIterationNextMessage *zis_msg; uint32_t rid; - nc = client_lookup(client); - if (nc == NULL) + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received `%s' message\n", "ZONE_ITERATION_NEXT"); + if (NULL == (nc = client_lookup(client))) { - GNUNET_break_op (0); - GNUNET_SERVER_receive_done (client, GNUNET_OK); + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } - + zis_msg = (const struct ZoneIterationNextMessage *) message; rid = ntohl (zis_msg->gns_header.r_id); - for (zi = nc->op_head; zi != NULL; zi = zi->next) - { + for (zi = nc->op_head; NULL != zi; zi = zi->next) if (zi->request_id == rid) break; - } - if (zi == NULL) + if (NULL == zi) { - GNUNET_break_op (0); - GNUNET_SERVER_receive_done (client, GNUNET_OK); + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); return; } + run_zone_iteration_round (zi); + GNUNET_SERVER_receive_done (client, GNUNET_OK); +} - struct ZoneIterationProcResult proc; - proc.zi = zi; +static void +zonekey_it_key_cb (void *cls, + struct GNUNET_CRYPTO_RsaPrivateKey *pk, + const char *emsg) +{ + struct KeyLoadContext *kl = cls; - find_next_zone_iteration_result (&proc); - if (GNUNET_YES == proc.res_iteration_finished) + kl->keygen = NULL; + if (NULL == pk) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Zone iteration done\n"); - } - else if (proc.records_included != 0) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Zone iteration return %u records\n", proc.records_included); + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + _("Could not parse zone key file `%s'\n"), + kl->filename); + return; } - send_zone_iteration_result (&proc); - clean_up_zone_iteration_result (&proc); + learn_private_key (pk); + (*kl->counter) ++; - GNUNET_SERVER_receive_done (client, GNUNET_OK); + GNUNET_CONTAINER_DLL_remove (kl_head, kl_tail, kl); + GNUNET_free (kl->filename); + GNUNET_free (kl); } -int zonekey_file_it (void *cls, const char *filename) + +/** + * Load zone keys from directory by reading all .zkey files in this directory + * + * @param cls int * 'counter' to store the number of files found + * @param filename directory to scan + * @return GNUNET_OK to continue + */ +static int +zonekey_file_it (void *cls, const char *filename) { - GNUNET_HashCode long_hash; - int *counter = cls; - if ((filename != NULL) && (NULL != strstr(filename, ".zkey"))) - { - struct GNUNET_CRYPTO_RsaPrivateKey * privkey; - struct GNUNET_NAMESTORE_CryptoContainer *c; - privkey = GNUNET_CRYPTO_rsa_key_create_from_file(filename); - if (privkey == NULL) - return GNUNET_OK; - - c = GNUNET_malloc (sizeof (struct GNUNET_NAMESTORE_CryptoContainer)); - c->pubkey = GNUNET_malloc(sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded)); - c->privkey = privkey; - GNUNET_CRYPTO_rsa_key_get_public(privkey, c->pubkey); - GNUNET_CRYPTO_short_hash(c->pubkey, sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded), &c->zone); - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Found zonefile for zone `%s'\n", GNUNET_short_h2s (&c->zone)); - GNUNET_CRYPTO_short_hash_double (&c->zone, &long_hash); - GNUNET_CONTAINER_multihashmap_put(zonekeys, &long_hash, c, GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY); - (*counter) ++; - } - return GNUNET_OK; + struct KeyLoadContext *kl; + + if ((NULL == filename) || + (NULL == strstr(filename, ".zkey"))) + return GNUNET_OK; + + kl = GNUNET_malloc (sizeof (struct KeyLoadContext)); + kl->filename = strdup (filename); + kl->counter = cls; + kl->keygen = GNUNET_CRYPTO_rsa_key_create_start (filename, zonekey_it_key_cb, kl); + if (NULL == kl->keygen) + { + GNUNET_free (kl->filename); + GNUNET_free (kl); + return GNUNET_OK; + } + + GNUNET_CONTAINER_DLL_insert (kl_head, kl_tail, kl); + return GNUNET_OK; } /** - * Process template requests. + * Process namestore requests. * * @param cls closure * @param server the initialized server @@ -1873,10 +2225,6 @@ static void run (void *cls, struct GNUNET_SERVER_Handle *server, const struct GNUNET_CONFIGURATION_Handle *cfg) { - char * database; - int counter = 0; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Starting namestore service\n"); - static const struct GNUNET_SERVER_MessageHandler handlers[] = { {&handle_start, NULL, GNUNET_MESSAGE_TYPE_NAMESTORE_START, sizeof (struct StartMessage)}, @@ -1889,24 +2237,29 @@ run (void *cls, struct GNUNET_SERVER_Handle *server, {&handle_record_remove, NULL, GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_REMOVE, 0}, {&handle_zone_to_name, NULL, - GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_TO_NAME, 0}, + GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_TO_NAME, sizeof (struct ZoneToNameMessage) }, {&handle_iteration_start, NULL, - GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_ITERATION_START, sizeof (struct ZoneIterationStartMessage)}, + GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_ITERATION_START, sizeof (struct ZoneIterationStartMessage) }, {&handle_iteration_next, NULL, - GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_ITERATION_NEXT, 0}, + GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_ITERATION_NEXT, sizeof (struct ZoneIterationNextMessage) }, {&handle_iteration_stop, NULL, - GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_ITERATION_STOP, 0}, + GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_ITERATION_STOP, sizeof (struct ZoneIterationStopMessage) }, {NULL, NULL, 0, 0} }; + char *database; + unsigned int counter; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Starting namestore service\n"); GSN_cfg = cfg; /* Load private keys from disk */ if (GNUNET_OK != - GNUNET_CONFIGURATION_get_value_filename (cfg, "namestore", "zonefile_directory", - &zonefile_directory)) + GNUNET_CONFIGURATION_get_value_filename (cfg, "namestore", + "zonefile_directory", + &zonefile_directory)) { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("No directory to load zonefiles specified in configuration\n")); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("No directory to load zonefiles specified in configuration\n")); GNUNET_SCHEDULER_add_now (&cleanup_task, NULL); return; } @@ -1915,17 +2268,25 @@ run (void *cls, struct GNUNET_SERVER_Handle *server, { if (GNUNET_SYSERR == GNUNET_DISK_directory_create (zonefile_directory)) { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("Creating directory `%s' for zone files failed!\n"), zonefile_directory); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Creating directory `%s' for zone files failed!\n"), + zonefile_directory); GNUNET_SCHEDULER_add_now (&cleanup_task, NULL); return; } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Created directory `%s' for zone files\n", zonefile_directory); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Created directory `%s' for zone files\n", + zonefile_directory); } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Scanning directory `%s' for zone files\n", zonefile_directory); - zonekeys = GNUNET_CONTAINER_multihashmap_create (10); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Scanning directory `%s' for zone files\n", zonefile_directory); + zonekeys = GNUNET_CONTAINER_multihashmap_create (16, GNUNET_NO); + counter = 0; GNUNET_DISK_directory_scan (zonefile_directory, zonekey_file_it, &counter); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Found %u zone files\n", counter); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Found %u zone files\n", + counter); /* Loading database plugin */ if (GNUNET_OK != @@ -1936,10 +2297,11 @@ run (void *cls, struct GNUNET_SERVER_Handle *server, GNUNET_asprintf (&db_lib_name, "libgnunet_plugin_namestore_%s", database); GSN_database = GNUNET_PLUGIN_load (db_lib_name, (void *) GSN_cfg); GNUNET_free (database); - if (GSN_database == NULL) + if (NULL == GSN_database) { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Could not load database backend `%s'\n", - db_lib_name); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Could not load database backend `%s'\n", + db_lib_name); GNUNET_SCHEDULER_add_now (&cleanup_task, NULL); return; } @@ -1950,10 +2312,8 @@ run (void *cls, struct GNUNET_SERVER_Handle *server, GNUNET_SERVER_disconnect_notify (server, &client_disconnect_notification, NULL); - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, &cleanup_task, NULL); - } diff --git a/src/namestore/namestore.conf.in b/src/namestore/namestore.conf.in index d93aea6..d7c372d 100644 --- a/src/namestore/namestore.conf.in +++ b/src/namestore/namestore.conf.in @@ -1,12 +1,11 @@ [namestore] AUTOSTART = YES UNIXPATH = /tmp/gnunet-service-namestore.sock -UNIX_MATCH_UID = YES +UNIX_MATCH_UID = NO UNIX_MATCH_GID = YES @UNIXONLY@ PORT = 2099 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-namestore ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -18,14 +17,7 @@ FILENAME = $SERVICEHOME/namestore/sqlite.db [namestore-postgres] CONFIG = connect_timeout=10; dbname=gnunet +TEMPORARY_TABLE = NO -[namestore-mysql] -DATABASE = gnunet -CONFIG = ~/.my.cnf -# USER = gnunet -# PASSWORD = -# HOST = localhost -# PORT = 3306 - - - +[uri] +gns = gnunet-namestore diff --git a/src/namestore/namestore.h b/src/namestore/namestore.h index 5a42c14..0e7ecfd 100644 --- a/src/namestore/namestore.h +++ b/src/namestore/namestore.h @@ -26,26 +26,18 @@ #ifndef NAMESTORE_H #define NAMESTORE_H -/* - * Collect message types here, move to protocols later +/** + * Maximum length of any name, including 0-termination. */ -#define GNUNET_MESSAGE_TYPE_NAMESTORE_START 430 -#define GNUNET_MESSAGE_TYPE_NAMESTORE_LOOKUP_NAME 431 -#define GNUNET_MESSAGE_TYPE_NAMESTORE_LOOKUP_NAME_RESPONSE 432 -#define GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_PUT 433 -#define GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_PUT_RESPONSE 434 -#define GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_CREATE 435 -#define GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_CREATE_RESPONSE 436 -#define GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_REMOVE 437 -#define GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_REMOVE_RESPONSE 438 -#define GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_TO_NAME 439 -#define GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_TO_NAME_RESPONSE 440 - -#define GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_ITERATION_START 445 -#define GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_ITERATION_RESPONSE 446 -#define GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_ITERATION_NEXT 447 -#define GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_ITERATION_STOP 448 +#define MAX_NAME_LEN 256 +/** + * Convert a UTF-8 string to UTF-8 lowercase + * @param src source string + * @return converted result + */ +char * +GNUNET_NAMESTORE_normalize_string (const char *src); /** * Convert a short hash to a string (for printing debug messages). @@ -398,6 +390,49 @@ struct RecordRemoveMessage }; +/** + * Removal of the record succeeded. + */ +#define RECORD_REMOVE_RESULT_SUCCESS 0 + +/** + * There are NO records for the given name. + */ +#define RECORD_REMOVE_RESULT_NO_RECORDS 1 + +/** + * The specific record that was to be removed was + * not found. + */ +#define RECORD_REMOVE_RESULT_RECORD_NOT_FOUND 2 + +/** + * Internal error, failed to sign the remaining records. + * (Note: not used?) + */ +#define RECORD_REMOVE_RESULT_FAILED_TO_SIGN 3 + +/** + * Internal error, failed to store the updated record set + */ +#define RECORD_REMOVE_RESULT_FAILED_TO_PUT_UPDATE 4 + +/** + * Internal error, failed to remove records from database + */ +#define RECORD_REMOVE_RESULT_FAILED_TO_REMOVE 5 + +/** + * Internal error, failed to access database + */ +#define RECORD_REMOVE_RESULT_FAILED_ACCESS_DATABASE 6 + +/** + * Internal error, failed to access database + */ +#define RECORD_REMOVE_RESULT_FAILED_INTERNAL_ERROR 7 + + /** * Remove a record from the namestore response */ @@ -409,12 +444,7 @@ struct RecordRemoveResponseMessage struct GNUNET_NAMESTORE_Header gns_header; /** - * result: - * 0 : successful - * 1 : no records for entry - * 2 : Could not find record to remove - * 3 : Failed to create new signature - * 4 : Failed to put new set of records in database + * Result code (see RECORD_REMOVE_RESULT_*). In network byte order. */ int32_t op_result; }; diff --git a/src/namestore/namestore_api.c b/src/namestore/namestore_api.c index 151fb97..5e82e08 100644 --- a/src/namestore/namestore_api.c +++ b/src/namestore/namestore_api.c @@ -1,6 +1,6 @@ /* This file is part of GNUnet. - (C) 2009, 2010 Christian Grothoff (and other contributing authors) + (C) 2010, 2011, 2012 Christian Grothoff (and other contributing authors) GNUnet is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published @@ -23,6 +23,7 @@ * @brief API to access the NAMESTORE service * @author Martin Schanzenbach * @author Matthias Wachs + * @author Christian Grothoff */ #include "platform.h" @@ -36,10 +37,12 @@ #include "namestore.h" -#define LOG(kind,...) GNUNET_log_from (kind, "gns-api",__VA_ARGS__) +#define LOG(kind,...) GNUNET_log_from (kind, "namestore-api",__VA_ARGS__) + /** - * A QueueEntry. + * An QueueEntry used to store information for a pending + * NAMESTORE record operation */ struct GNUNET_NAMESTORE_QueueEntry { @@ -54,22 +57,41 @@ struct GNUNET_NAMESTORE_QueueEntry */ struct GNUNET_NAMESTORE_QueueEntry *prev; + /** + * Main handle to access the namestore. + */ struct GNUNET_NAMESTORE_Handle *nsh; - uint32_t op_id; - + /** + * Continuation to call + */ GNUNET_NAMESTORE_ContinuationWithStatus cont; + + /** + * Closure for 'cont'. + */ void *cont_cls; + /** + * Function to call with the records we get back; or NULL. + */ GNUNET_NAMESTORE_RecordProcessor proc; + + /** + * Closure for 'proc'. + */ void *proc_cls; - char *data; /*stub data pointer*/ + /** + * The operation id this zone iteration operation has + */ + uint32_t op_id; + }; /** - * Zone iterator + * Handle for a zone iterator operation */ struct GNUNET_NAMESTORE_ZoneIterator { @@ -84,14 +106,38 @@ struct GNUNET_NAMESTORE_ZoneIterator */ struct GNUNET_NAMESTORE_ZoneIterator *prev; - uint32_t op_id; - + /** + * Main handle to access the namestore. + */ struct GNUNET_NAMESTORE_Handle *h; + + /** + * The continuation to call with the results + */ GNUNET_NAMESTORE_RecordProcessor proc; + + /** + * Closure for 'proc'. + */ void* proc_cls; + + /** + * If this iterator iterates over a specific zone this value contains the + * short hash of the zone + */ struct GNUNET_CRYPTO_ShortHashCode zone; - uint32_t no_flags; - uint32_t flags; + + /** + * The operation id this zone iteration operation has + */ + uint32_t op_id; + + /** + * GNUNET_YES if this iterator iterates over a specific zone + * GNUNET_NO if this iterator iterates over all zones + * + * Zone is stored GNUNET_CRYPTO_ShortHashCode 'zone'; + */ int has_zone; }; @@ -147,59 +193,51 @@ struct GNUNET_NAMESTORE_Handle struct GNUNET_CLIENT_TransmitHandle *th; /** - * Reconnect task + * Head of linked list of pending messages to send to the service */ - GNUNET_SCHEDULER_TaskIdentifier reconnect_task; + struct PendingMessage * pending_head; /** - * Pending messages to send to the service + * Tail of linked list of pending messages to send to the service */ - - struct PendingMessage * pending_head; struct PendingMessage * pending_tail; /** - * Should we reconnect to service due to some serious error? + * Head of pending namestore queue entries */ - int reconnect; - + struct GNUNET_NAMESTORE_QueueEntry * op_head; /** - * Pending namestore queue entries + * Tail of pending namestore queue entries */ - struct GNUNET_NAMESTORE_QueueEntry * op_head; struct GNUNET_NAMESTORE_QueueEntry * op_tail; - uint32_t op_id; - /** - * Pending namestore zone iterator entries + * Head of pending namestore zone iterator entries */ struct GNUNET_NAMESTORE_ZoneIterator * z_head; + + /** + * Tail of pending namestore zone iterator entries + */ struct GNUNET_NAMESTORE_ZoneIterator * z_tail; -}; -struct GNUNET_NAMESTORE_SimpleRecord -{ /** - * DLL + * Reconnect task */ - struct GNUNET_NAMESTORE_SimpleRecord *next; + GNUNET_SCHEDULER_TaskIdentifier reconnect_task; /** - * DLL + * Should we reconnect to service due to some serious error? */ - struct GNUNET_NAMESTORE_SimpleRecord *prev; - - const char *name; - const struct GNUNET_CRYPTO_ShortHashCode *zone; - uint32_t record_type; - struct GNUNET_TIME_Absolute expiration; - enum GNUNET_NAMESTORE_RecordFlags flags; - size_t data_size; - const void *data; -}; + int reconnect; + + /** + * The last operation id used for a NAMESTORE operation + */ + uint32_t last_op_id_used; +}; /** @@ -210,449 +248,433 @@ struct GNUNET_NAMESTORE_SimpleRecord static void force_reconnect (struct GNUNET_NAMESTORE_Handle *h); -static void + +/** + * Handle an incoming message of type 'GNUNET_MESSAGE_TYPE_NAMESTORE_LOOKUP_NAME_RESPONSE' + * + * @param qe the respective entry in the message queue + * @param msg the message we received + * @param size the message size + * @return GNUNET_OK on success, GNUNET_SYSERR on error and we did NOT notify the client + */ +static int handle_lookup_name_response (struct GNUNET_NAMESTORE_QueueEntry *qe, - struct LookupNameResponseMessage * msg, + const struct LookupNameResponseMessage * msg, size_t size) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received `%s' \n", - "LOOKUP_NAME_RESPONSE"); - - struct GNUNET_NAMESTORE_Handle *h = qe->nsh; - - /* Operation done, remove */ - GNUNET_CONTAINER_DLL_remove(h->op_head, h->op_tail, qe); - - - char *name; - char * rd_tmp; - - struct GNUNET_CRYPTO_RsaSignature *signature = NULL; + const char *name; + const char * rd_tmp; + const struct GNUNET_CRYPTO_RsaSignature *signature; struct GNUNET_TIME_Absolute expire; - struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *public_key_tmp; + const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *public_key_tmp; size_t exp_msg_len; - size_t msg_len = 0; - size_t name_len = 0; - size_t rd_len = 0; - int contains_sig = GNUNET_NO; - int rd_count = 0; + size_t msg_len; + size_t name_len; + size_t rd_len; + int contains_sig; + int rd_count; + LOG (GNUNET_ERROR_TYPE_DEBUG, "Received `%s'\n", "LOOKUP_NAME_RESPONSE"); rd_len = ntohs (msg->rd_len); rd_count = ntohs (msg->rd_count); msg_len = ntohs (msg->gns_header.header.size); name_len = ntohs (msg->name_len); contains_sig = ntohs (msg->contains_sig); - expire = GNUNET_TIME_absolute_ntoh(msg->expire); - + expire = GNUNET_TIME_absolute_ntoh (msg->expire); exp_msg_len = sizeof (struct LookupNameResponseMessage) + sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded) + name_len + rd_len; - if (msg_len != exp_msg_len) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Message size describes with `%u' bytes but calculated size is %u bytes \n", - msg_len, exp_msg_len); - GNUNET_break_op (0); - return; + GNUNET_break (0); + return GNUNET_SYSERR; } - - name = (char *) &msg[1]; - if (name_len > 0) + name = (const char *) &msg[1]; + if ( (name_len > 0) && + ('\0' != name[name_len -1]) ) { - GNUNET_assert ('\0' == name[name_len -1]); - GNUNET_assert ((name_len - 1) == strlen(name)); + GNUNET_break (0); + return GNUNET_SYSERR; } rd_tmp = &name[name_len]; - - /* deserialize records */ - struct GNUNET_NAMESTORE_RecordData rd[rd_count]; - if (GNUNET_OK != GNUNET_NAMESTORE_records_deserialize(rd_len, rd_tmp, rd_count, rd)) { - GNUNET_break_op (0); - return; - } - - - /* reset values if values not contained */ - if (contains_sig == GNUNET_NO) - signature = NULL; - else - signature = &msg->signature; - if (name_len == 0) - name = NULL; - - if (name != NULL) - public_key_tmp = &msg->public_key; - else - public_key_tmp = NULL; + struct GNUNET_NAMESTORE_RecordData rd[rd_count]; - if (qe->proc != NULL) - { - qe->proc (qe->proc_cls, public_key_tmp, expire, name, rd_count, (rd_count > 0) ? rd : NULL, signature); + if (GNUNET_OK != GNUNET_NAMESTORE_records_deserialize(rd_len, rd_tmp, rd_count, rd)) + { + GNUNET_break (0); + return GNUNET_SYSERR; + } + if (GNUNET_NO == contains_sig) + signature = NULL; + else + signature = &msg->signature; + if (0 == name_len) + name = NULL; + if (NULL != name) + public_key_tmp = &msg->public_key; + else + public_key_tmp = NULL; + if (NULL != qe->proc) + qe->proc (qe->proc_cls, public_key_tmp, expire, name, rd_count, (rd_count > 0) ? rd : NULL, signature); } - GNUNET_free (qe); + return GNUNET_OK; } -static void +/** + * Handle an incoming message of type 'GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_PUT_RESPONSE' + * + * @param qe the respective entry in the message queue + * @param msg the message we received + * @param size the message size + * @return GNUNET_OK on success, GNUNET_SYSERR on error and we did NOT notify the client + */ +static int handle_record_put_response (struct GNUNET_NAMESTORE_QueueEntry *qe, - struct RecordPutResponseMessage* msg, - size_t size) + const struct RecordPutResponseMessage* msg, + size_t size) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received `%s' \n", - "RECORD_PUT_RESPONSE"); - - struct GNUNET_NAMESTORE_Handle *h = qe->nsh; - /* Operation done, remove */ - GNUNET_CONTAINER_DLL_remove(h->op_head, h->op_tail, qe); - - int res = ntohl (msg->op_result); - - if (res == GNUNET_OK) - { - if (qe->cont != NULL) - { - qe->cont (qe->cont_cls, res, _("Namestore added record successfully")); - } - - } - else if (res == GNUNET_SYSERR) - { - if (qe->cont != NULL) - { - qe->cont (qe->cont_cls, res, _("Namestore failed to add record")); - } - } - else - { - GNUNET_break_op (0); - return; - } - - GNUNET_free (qe); + int res; + + LOG (GNUNET_ERROR_TYPE_DEBUG, "Received `%s'\n", + "RECORD_PUT_RESPONSE"); + res = ntohl (msg->op_result); + /* TODO: add actual error message from namestore to response... */ + if (NULL != qe->cont) + qe->cont (qe->cont_cls, res, (GNUNET_OK == res) ? NULL : _("Namestore failed to add record")); + return GNUNET_OK; } -static void +/** + * Handle an incoming message of type 'GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_CREATE_RESPONSE' + * + * @param qe the respective entry in the message queue + * @param msg the message we received + * @param size the message size + * @return GNUNET_OK on success, GNUNET_SYSERR on error and we did NOT notify the client + */ +static int handle_record_create_response (struct GNUNET_NAMESTORE_QueueEntry *qe, - struct RecordCreateResponseMessage* msg, - size_t size) + const struct RecordCreateResponseMessage* msg, + size_t size) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received `%s' \n", - "RECORD_CREATE_RESPONSE"); - - struct GNUNET_NAMESTORE_Handle *h = qe->nsh; - /* Operation done, remove */ - GNUNET_CONTAINER_DLL_remove(h->op_head, h->op_tail, qe); - - int res = ntohl (msg->op_result); - if (res == GNUNET_YES) - { - if (qe->cont != NULL) - { - qe->cont (qe->cont_cls, res, _("Namestore added record successfully")); - } - - } - else if (res == GNUNET_NO) - { - if (qe->cont != NULL) - { - qe->cont (qe->cont_cls, res, _("Namestore record already existed")); - } - } + int res; + const char *emsg; + + LOG (GNUNET_ERROR_TYPE_DEBUG, "Received `%s'\n", + "RECORD_CREATE_RESPONSE"); + /* TODO: add actual error message from namestore to response... */ + res = ntohl (msg->op_result); + if (GNUNET_SYSERR == res) + emsg = _("Namestore failed to add record\n"); else - { - if (qe->cont != NULL) - { - qe->cont (qe->cont_cls, GNUNET_SYSERR, _("Namestore failed to add record\n")); - } - } - - GNUNET_free (qe); + emsg = NULL; + if (NULL != qe->cont) + qe->cont (qe->cont_cls, res, emsg); + return GNUNET_OK; } -static void +/** + * Handle an incoming message of type 'GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_REMOVE_RESPONSE' + * + * @param qe the respective entry in the message queue + * @param msg the message we received + * @param size the message size + * @return GNUNET_OK on success, GNUNET_SYSERR on error and we did NOT notify the client + */ +static int handle_record_remove_response (struct GNUNET_NAMESTORE_QueueEntry *qe, - struct RecordRemoveResponseMessage* msg, - size_t size) + const struct RecordRemoveResponseMessage* msg, + size_t size) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received `%s' \n", - "RECORD_REMOVE_RESPONSE"); + int ret; + const char *emsg; - struct GNUNET_NAMESTORE_Handle *h = qe->nsh; /* Operation done, remove */ - GNUNET_CONTAINER_DLL_remove(h->op_head, h->op_tail, qe); - - int res = ntohl (msg->op_result); - /** - * result: - * 0 : successful - * 1 : No records for entry - * 2 : Could not find record to remove - * 3 : Failed to create new signature - * 4 : Failed to put new set of records in database - */ - switch (res) { - case 0: - if (qe->cont != NULL) - { - qe->cont (qe->cont_cls, GNUNET_YES, _("Namestore removed record successfully")); - } - - break; - case 1: - if (qe->cont != NULL) - { - qe->cont (qe->cont_cls, GNUNET_NO, _("No records for entry")); - } - - break; - case 2: - if (qe->cont != NULL) - { - qe->cont (qe->cont_cls, GNUNET_NO, _("Could not find record to remove")); - } - - break; - case 3: - if (qe->cont != NULL) - { - qe->cont (qe->cont_cls, GNUNET_SYSERR, _("Failed to create new signature")); - } - - break; - case 4: - if (qe->cont != NULL) - { - qe->cont (qe->cont_cls, GNUNET_SYSERR, _("Failed to put new set of records in database")); - } - break; - default: - GNUNET_break_op (0); - break; + LOG (GNUNET_ERROR_TYPE_DEBUG, "Received `%s'\n", + "RECORD_REMOVE_RESPONSE"); + switch (ntohl (msg->op_result)) + { + case RECORD_REMOVE_RESULT_SUCCESS: + ret = GNUNET_OK; + emsg = NULL; + break; + case RECORD_REMOVE_RESULT_NO_RECORDS: + ret = GNUNET_NO; + emsg = NULL; + break; + case RECORD_REMOVE_RESULT_RECORD_NOT_FOUND: + ret = GNUNET_NO; + emsg = NULL; + break; + case RECORD_REMOVE_RESULT_FAILED_TO_SIGN: + ret = GNUNET_SYSERR; + emsg = _("Failed to create new signature"); + break; + case RECORD_REMOVE_RESULT_FAILED_TO_PUT_UPDATE: + ret = GNUNET_SYSERR; + emsg = _("Failed to put new set of records in database"); + break; + case RECORD_REMOVE_RESULT_FAILED_TO_REMOVE: + ret = GNUNET_SYSERR; + emsg = _("Failed to remove records from database"); + break; + case RECORD_REMOVE_RESULT_FAILED_ACCESS_DATABASE: + ret = GNUNET_SYSERR; + emsg = _("Failed to access database"); + break; + case RECORD_REMOVE_RESULT_FAILED_INTERNAL_ERROR: + ret = GNUNET_SYSERR; + emsg = _("unknown internal error in namestore"); + break; + default: + GNUNET_break (0); + if (NULL != qe->cont) + qe->cont (qe->cont_cls, GNUNET_SYSERR, _("Protocol error")); + return GNUNET_NO; } - - GNUNET_free (qe); + if (NULL != qe->cont) + qe->cont (qe->cont_cls, ret, emsg); + return GNUNET_OK; } -static void + +/** + * Handle an incoming message of type 'GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_TO_NAME_RESPONSE' + * + * @param qe the respective entry in the message queue + * @param msg the message we received + * @param size the message size + * @return GNUNET_OK on success, GNUNET_NO if we notified the client about + * the error, GNUNET_SYSERR on error and we did NOT notify the client + */ +static int handle_zone_to_name_response (struct GNUNET_NAMESTORE_QueueEntry *qe, - struct ZoneToNameResponseMessage* msg, - size_t size) + const struct ZoneToNameResponseMessage* msg, + size_t size) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received `%s' \n", - "ZONE_TO_NAME_RESPONSE"); - - struct GNUNET_NAMESTORE_Handle *h = qe->nsh; - /* Operation done, remove */ - GNUNET_CONTAINER_DLL_remove(h->op_head, h->op_tail, qe); - - int res = ntohs (msg->res); - + int res; struct GNUNET_TIME_Absolute expire; size_t name_len; size_t rd_ser_len; unsigned int rd_count; - - char * name_tmp; - char * rd_tmp; - - if (res == GNUNET_SYSERR) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "An error occured during zone to name operation\n"); - if (qe->proc != NULL) - qe->proc (qe->proc_cls, NULL, GNUNET_TIME_UNIT_ZERO_ABS, NULL, 0, NULL, NULL); - } - else if (res == GNUNET_NO) + const char * name_tmp; + const char * rd_tmp; + + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Received `%s'\n", + "ZONE_TO_NAME_RESPONSE"); + res = ntohs (msg->res); + switch (res) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Namestore has no result for zone to name mapping \n"); - if (qe->proc != NULL) - qe->proc (qe->proc_cls, NULL, GNUNET_TIME_UNIT_ZERO_ABS, NULL, 0, NULL, NULL); - } - else if (res == GNUNET_YES) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Namestore has result for zone to name mapping \n"); - + case GNUNET_SYSERR: + LOG (GNUNET_ERROR_TYPE_DEBUG, "An error occured during zone to name operation\n"); + break; + case GNUNET_NO: + LOG (GNUNET_ERROR_TYPE_DEBUG, "Namestore has no result for zone to name mapping \n"); + break; + case GNUNET_YES: + LOG (GNUNET_ERROR_TYPE_DEBUG, "Namestore has result for zone to name mapping \n"); name_len = ntohs (msg->name_len); rd_count = ntohs (msg->rd_count); rd_ser_len = ntohs (msg->rd_len); expire = GNUNET_TIME_absolute_ntoh(msg->expire); - - name_tmp = (char *) &msg[1]; - if (name_len > 0) + name_tmp = (const char *) &msg[1]; + if ( (name_len > 0) && + ('\0' != name_tmp[name_len -1]) ) { - GNUNET_assert ('\0' == name_tmp[name_len -1]); - GNUNET_assert (name_len -1 == strlen(name_tmp)); + GNUNET_break (0); + return GNUNET_SYSERR; } rd_tmp = &name_tmp[name_len]; - - struct GNUNET_NAMESTORE_RecordData rd[rd_count]; - if (GNUNET_OK != GNUNET_NAMESTORE_records_deserialize(rd_ser_len, rd_tmp, rd_count, rd)) { - GNUNET_break_op (0); - return; + struct GNUNET_NAMESTORE_RecordData rd[rd_count]; + if (GNUNET_OK != GNUNET_NAMESTORE_records_deserialize(rd_ser_len, rd_tmp, rd_count, rd)) + { + GNUNET_break (0); + return GNUNET_SYSERR; + } + /* normal end, call continuation with result */ + if (NULL != qe->proc) + qe->proc (qe->proc_cls, &msg->zone_key, expire, name_tmp, rd_count, rd, &msg->signature); + /* return is important here: break would call continuation with error! */ + return GNUNET_OK; } - - if (qe->proc != NULL) - qe->proc (qe->proc_cls, &msg->zone_key, expire, name_tmp, rd_count, rd, &msg->signature); + default: + GNUNET_break (0); + return GNUNET_SYSERR; } - else - GNUNET_break_op (0); - - GNUNET_free (qe); + /* error case, call continuation with error */ + if (NULL != qe->proc) + qe->proc (qe->proc_cls, NULL, GNUNET_TIME_UNIT_ZERO_ABS, NULL, 0, NULL, NULL); + return GNUNET_OK; } -static void +/** + * Handle incoming messages for record operations + * + * @param qe the respective zone iteration handle + * @param msg the message we received + * @param type the message type in HBO + * @param size the message size + * @return GNUNET_OK on success, GNUNET_NO if we notified the client about + * the error, GNUNET_SYSERR on error and we did NOT notify the client + */ +static int manage_record_operations (struct GNUNET_NAMESTORE_QueueEntry *qe, const struct GNUNET_MessageHeader *msg, - int type, size_t size) + uint16_t type, + size_t size) { - /* handle different message type */ - switch (type) { - case GNUNET_MESSAGE_TYPE_NAMESTORE_LOOKUP_NAME_RESPONSE: - if (size < sizeof (struct LookupNameResponseMessage)) - { - GNUNET_break_op (0); - break; - } - handle_lookup_name_response (qe, (struct LookupNameResponseMessage *) msg, size); - break; - case GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_PUT_RESPONSE: - if (size != sizeof (struct RecordPutResponseMessage)) - { - GNUNET_break_op (0); - break; - } - handle_record_put_response (qe, (struct RecordPutResponseMessage *) msg, size); - break; - case GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_CREATE_RESPONSE: - if (size != sizeof (struct RecordCreateResponseMessage)) - { - GNUNET_break_op (0); - break; - } - handle_record_create_response (qe, (struct RecordCreateResponseMessage *) msg, size); - break; - case GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_REMOVE_RESPONSE: - if (size != sizeof (struct RecordRemoveResponseMessage)) - { - GNUNET_break_op (0); - break; - } - handle_record_remove_response (qe, (struct RecordRemoveResponseMessage *) msg, size); - break; - case GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_TO_NAME_RESPONSE: - if (size < sizeof (struct ZoneToNameResponseMessage)) - { - GNUNET_break_op (0); - break; - } - handle_zone_to_name_response (qe, (struct ZoneToNameResponseMessage *) msg, size); - break; - default: - GNUNET_break_op (0); - break; + switch (type) + { + case GNUNET_MESSAGE_TYPE_NAMESTORE_LOOKUP_NAME_RESPONSE: + if (size < sizeof (struct LookupNameResponseMessage)) + { + GNUNET_break (0); + return GNUNET_SYSERR; + } + return handle_lookup_name_response (qe, (const struct LookupNameResponseMessage *) msg, size); + case GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_PUT_RESPONSE: + if (size != sizeof (struct RecordPutResponseMessage)) + { + GNUNET_break (0); + return GNUNET_SYSERR; + } + return handle_record_put_response (qe, (const struct RecordPutResponseMessage *) msg, size); + case GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_CREATE_RESPONSE: + if (size != sizeof (struct RecordCreateResponseMessage)) + { + GNUNET_break (0); + return GNUNET_SYSERR; + } + return handle_record_create_response (qe, (const struct RecordCreateResponseMessage *) msg, size); + case GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_REMOVE_RESPONSE: + if (size != sizeof (struct RecordRemoveResponseMessage)) + { + GNUNET_break (0); + return GNUNET_SYSERR; + } + return handle_record_remove_response (qe, (const struct RecordRemoveResponseMessage *) msg, size); + case GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_TO_NAME_RESPONSE: + if (size < sizeof (struct ZoneToNameResponseMessage)) + { + GNUNET_break (0); + return GNUNET_SYSERR; + } + return handle_zone_to_name_response (qe, (const struct ZoneToNameResponseMessage *) msg, size); + default: + GNUNET_break (0); + return GNUNET_SYSERR; } } -static void + +/** + * Handle a response from NAMESTORE service for a zone iteration request + * + * @param ze the respective iterator for this operation + * @param msg the message containing the respoonse + * @param size the message size + * @return GNUNET_YES on success, 'ze' should be kept, GNUNET_NO on success if 'ze' should + * not be kept any longer, GNUNET_SYSERR on error (disconnect) and 'ze' should be kept + */ +static int handle_zone_iteration_response (struct GNUNET_NAMESTORE_ZoneIterator *ze, - struct ZoneIterationResponseMessage *msg, + const struct ZoneIterationResponseMessage *msg, size_t size) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received `%s' \n", - "ZONE_ITERATION_RESPONSE"); - struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded pubdummy; - size_t msg_len = 0; - size_t exp_msg_len = 0; - size_t name_len = 0; - size_t rd_len = 0; - unsigned rd_count = 0; - - char *name_tmp; - char *rd_ser_tmp; + size_t msg_len; + size_t exp_msg_len; + size_t name_len; + size_t rd_len; + unsigned rd_count; + const char *name_tmp; + const char *rd_ser_tmp; struct GNUNET_TIME_Absolute expire; + LOG (GNUNET_ERROR_TYPE_DEBUG, "Received `%s'\n", + "ZONE_ITERATION_RESPONSE"); msg_len = ntohs (msg->gns_header.header.size); rd_len = ntohs (msg->rd_len); rd_count = ntohs (msg->rd_count); name_len = ntohs (msg->name_len); expire = GNUNET_TIME_absolute_ntoh (msg->expire); - exp_msg_len = sizeof (struct ZoneIterationResponseMessage) + name_len + rd_len; if (msg_len != exp_msg_len) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Message size describes with `%u' bytes but calculated size is %u bytes \n", - msg_len, exp_msg_len); - GNUNET_break_op (0); - return; - } - if (0 != ntohs (msg->reserved)) - { - GNUNET_break_op (0); - return; + GNUNET_break (0); + return GNUNET_SYSERR; } - + GNUNET_break (0 == ntohs (msg->reserved)); memset (&pubdummy, '\0', sizeof (pubdummy)); if ((0 == name_len) && (0 == (memcmp (&msg->public_key, &pubdummy, sizeof (pubdummy))))) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Zone iteration is completed!\n"); - - GNUNET_CONTAINER_DLL_remove(ze->h->z_head, ze->h->z_tail, ze); - - if (ze->proc != NULL) + LOG (GNUNET_ERROR_TYPE_DEBUG, "Zone iteration is completed!\n"); + if (NULL != ze->proc) ze->proc(ze->proc_cls, NULL, GNUNET_TIME_UNIT_ZERO_ABS, NULL , 0, NULL, NULL); - - GNUNET_free (ze); - return; + return GNUNET_NO; } - - name_tmp = (char *) &msg[1]; - if ((name_tmp[name_len -1] != '\0') || (name_len > 256)) + name_tmp = (const char *) &msg[1]; + if ((name_tmp[name_len -1] != '\0') || (name_len > MAX_NAME_LEN)) { - GNUNET_break_op (0); - return; + GNUNET_break (0); + return GNUNET_SYSERR; } - rd_ser_tmp = (char *) &name_tmp[name_len]; - struct GNUNET_NAMESTORE_RecordData rd[rd_count]; - if (GNUNET_OK != GNUNET_NAMESTORE_records_deserialize (rd_len, rd_ser_tmp, rd_count, rd)) + rd_ser_tmp = (const char *) &name_tmp[name_len]; { - GNUNET_break_op (0); - return; - } + struct GNUNET_NAMESTORE_RecordData rd[rd_count]; - if (ze->proc != NULL) - ze->proc(ze->proc_cls, &msg->public_key, expire, name_tmp, rd_count, rd, &msg->signature); + if (GNUNET_OK != GNUNET_NAMESTORE_records_deserialize (rd_len, rd_ser_tmp, rd_count, rd)) + { + GNUNET_break (0); + return GNUNET_SYSERR; + } + if (NULL != ze->proc) + ze->proc(ze->proc_cls, &msg->public_key, expire, name_tmp, rd_count, rd, &msg->signature); + return GNUNET_YES; + } } -static void +/** + * Handle incoming messages for zone iterations + * + * @param ze the respective zone iteration handle + * @param msg the message we received + * @param type the message type in HBO + * @param size the message size + * @return GNUNET_YES on success, 'ze' should be kept, GNUNET_NO on success if 'ze' should + * not be kept any longer, GNUNET_SYSERR on error (disconnect) and 'ze' should be kept + */ +static int manage_zone_operations (struct GNUNET_NAMESTORE_ZoneIterator *ze, const struct GNUNET_MessageHeader *msg, int type, size_t size) { - /* handle different message type */ - switch (type) { - case GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_ITERATION_RESPONSE: - if (size < sizeof (struct ZoneIterationResponseMessage)) - { - GNUNET_break_op (0); - break; - } - handle_zone_iteration_response (ze, (struct ZoneIterationResponseMessage *) msg, size); - break; - default: - GNUNET_break_op (0); - break; + switch (type) + { + case GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_ITERATION_RESPONSE: + if (size < sizeof (struct ZoneIterationResponseMessage)) + { + GNUNET_break (0); + return GNUNET_SYSERR; + } + return handle_zone_iteration_response (ze, (const struct ZoneIterationResponseMessage *) msg, size); + default: + GNUNET_break (0); + return GNUNET_SYSERR; } } + /** * Type of a function to call when we receive a message * from the service. @@ -664,22 +686,21 @@ static void process_namestore_message (void *cls, const struct GNUNET_MessageHeader *msg) { struct GNUNET_NAMESTORE_Handle *h = cls; - struct GNUNET_NAMESTORE_Header * gm; + const struct GNUNET_NAMESTORE_Header *gm; struct GNUNET_NAMESTORE_QueueEntry *qe; struct GNUNET_NAMESTORE_ZoneIterator *ze; uint16_t size; uint16_t type; - uint32_t r_id = UINT32_MAX; + uint32_t r_id; + int ret; if (NULL == msg) { force_reconnect (h); return; } - size = ntohs (msg->size); type = ntohs (msg->type); - if (size < sizeof (struct GNUNET_NAMESTORE_Header)) { GNUNET_break_op (0); @@ -687,50 +708,64 @@ process_namestore_message (void *cls, const struct GNUNET_MessageHeader *msg) GNUNET_TIME_UNIT_FOREVER_REL); return; } - - gm = (struct GNUNET_NAMESTORE_Header *) msg; + gm = (const struct GNUNET_NAMESTORE_Header *) msg; r_id = ntohl (gm->r_id); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received message type %i size %i op %u\n", type, size, r_id); - - /* Find matching operation */ - if (r_id > h->op_id) - { - /* No matching pending operation found */ - GNUNET_break_op (0); - GNUNET_CLIENT_receive (h->client, &process_namestore_message, h, - GNUNET_TIME_UNIT_FOREVER_REL); - return; - } + LOG (GNUNET_ERROR_TYPE_DEBUG, "Received message type %u size %u op %u\n", + (unsigned int) type, + (unsigned int) size, + (unsigned int) r_id); /* Is it a record related operation ? */ for (qe = h->op_head; qe != NULL; qe = qe->next) - { if (qe->op_id == r_id) break; - } - if (qe != NULL) + if (NULL != qe) { - manage_record_operations (qe, msg, type, size); + ret = manage_record_operations (qe, msg, type, size); + if (GNUNET_OK != ret) + { + /* protocol error, need to reconnect */ + h->reconnect = GNUNET_YES; + } + if (GNUNET_SYSERR != ret) + { + /* client was notified about success or failure, clean up 'qe' */ + GNUNET_CONTAINER_DLL_remove (h->op_head, + h->op_tail, + qe); + GNUNET_free (qe); + } } /* Is it a zone iteration operation ? */ for (ze = h->z_head; ze != NULL; ze = ze->next) - { if (ze->op_id == r_id) break; + if (NULL != ze) + { + ret = manage_zone_operations (ze, msg, type, size); + if (GNUNET_NO == ret) + { + /* end of iteration, clean up 'ze' */ + GNUNET_CONTAINER_DLL_remove (h->z_head, + h->z_tail, + ze); + GNUNET_free (ze); + } + if (GNUNET_SYSERR == ret) + { + /* protocol error, need to reconnect */ + h->reconnect = GNUNET_YES; + } } - if (ze != NULL) + if (GNUNET_YES == h->reconnect) { - manage_zone_operations (ze, msg, type, size); + force_reconnect (h); + return; } - GNUNET_CLIENT_receive (h->client, &process_namestore_message, h, GNUNET_TIME_UNIT_FOREVER_REL); - - if (GNUNET_YES == h->reconnect) - force_reconnect (h); - } @@ -761,7 +796,7 @@ transmit_message_to_namestore (void *cls, size_t size, void *buf) char *cbuf; h->th = NULL; - if ((size == 0) || (buf == NULL)) + if ((0 == size) || (NULL == buf)) { force_reconnect (h); return 0; @@ -796,12 +831,11 @@ do_transmit (struct GNUNET_NAMESTORE_Handle *h) struct PendingMessage *p; if (NULL != h->th) - return; + return; /* transmission request already pending */ if (NULL == (p = h->pending_head)) - return; + return; /* transmission queue empty */ if (NULL == h->client) return; /* currently reconnecting */ - h->th = GNUNET_CLIENT_notify_transmit_ready (h->client, p->size, GNUNET_TIME_UNIT_FOREVER_REL, GNUNET_NO, &transmit_message_to_namestore, @@ -812,7 +846,7 @@ do_transmit (struct GNUNET_NAMESTORE_Handle *h) /** * Reconnect to namestore service. * - * @param h the handle to the namestore service + * @param h the handle to the NAMESTORE service */ static void reconnect (struct GNUNET_NAMESTORE_Handle *h) @@ -823,7 +857,6 @@ reconnect (struct GNUNET_NAMESTORE_Handle *h) GNUNET_assert (NULL == h->client); h->client = GNUNET_CLIENT_connect ("namestore", h->cfg); GNUNET_assert (NULL != h->client); - if ((NULL == (p = h->pending_head)) || (GNUNET_YES != p->is_init)) { p = GNUNET_malloc (sizeof (struct PendingMessage) + @@ -838,6 +871,7 @@ reconnect (struct GNUNET_NAMESTORE_Handle *h) do_transmit (h); } + /** * Re-establish the connection to the service. * @@ -866,18 +900,24 @@ force_reconnect (struct GNUNET_NAMESTORE_Handle *h) GNUNET_CLIENT_disconnect (h->client); h->client = NULL; h->reconnect_task = GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_SECONDS, - &reconnect_task, - h); + &reconnect_task, + h); } + +/** + * Get a fresh operation id to distinguish between namestore requests + * + * @param h the namestore handle + * @return next operation id to use + */ static uint32_t get_op_id (struct GNUNET_NAMESTORE_Handle *h) { - uint32_t op_id = h->op_id; - h->op_id ++; - return op_id; + return h->last_op_id_used++; } + /** * Initialize the connection with the NAMESTORE service. * @@ -892,37 +932,43 @@ GNUNET_NAMESTORE_connect (const struct GNUNET_CONFIGURATION_Handle *cfg) h = GNUNET_malloc (sizeof (struct GNUNET_NAMESTORE_Handle)); h->cfg = cfg; h->reconnect_task = GNUNET_SCHEDULER_add_now (&reconnect_task, h); - h->op_id = 0; + h->last_op_id_used = 0; return h; } -static void -clean_up_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) + +/** + * Disconnect from the namestore service (and free associated + * resources). + * + * @param h handle to the namestore + */ +void +GNUNET_NAMESTORE_disconnect (struct GNUNET_NAMESTORE_Handle *h) { struct PendingMessage *p; struct GNUNET_NAMESTORE_QueueEntry *q; struct GNUNET_NAMESTORE_ZoneIterator *z; - struct GNUNET_NAMESTORE_Handle *h = cls; - GNUNET_assert (h != NULL); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Cleaning up\n"); + + LOG (GNUNET_ERROR_TYPE_DEBUG, "Cleaning up\n"); + GNUNET_assert (NULL != h); while (NULL != (p = h->pending_head)) { GNUNET_CONTAINER_DLL_remove (h->pending_head, h->pending_tail, p); GNUNET_free (p); } - + GNUNET_break (NULL == h->op_head); while (NULL != (q = h->op_head)) { GNUNET_CONTAINER_DLL_remove (h->op_head, h->op_tail, q); GNUNET_free (q); } - + GNUNET_break (NULL == h->z_head); while (NULL != (z = h->z_head)) { GNUNET_CONTAINER_DLL_remove (h->z_head, h->z_tail, z); GNUNET_free (z); } - if (NULL != h->client) { GNUNET_CLIENT_disconnect (h->client); @@ -933,23 +979,7 @@ clean_up_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) GNUNET_SCHEDULER_cancel (h->reconnect_task); h->reconnect_task = GNUNET_SCHEDULER_NO_TASK; } - GNUNET_free(h); - h = NULL; -} - - -/** - * Disconnect from the namestore service (and free associated - * resources). - * - * @param h handle to the namestore - * @param drop set to GNUNET_YES to delete all data in namestore (!) - */ -void -GNUNET_NAMESTORE_disconnect (struct GNUNET_NAMESTORE_Handle *h, int drop) -{ - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Disconnecting from namestore service\n"); - GNUNET_SCHEDULER_add_now (&clean_up_task, h); + GNUNET_free (h); } @@ -984,53 +1014,44 @@ GNUNET_NAMESTORE_record_put (struct GNUNET_NAMESTORE_Handle *h, { struct GNUNET_NAMESTORE_QueueEntry *qe; struct PendingMessage *pe; - - /* pointer to elements */ - char * rd_tmp; + struct RecordPutMessage * msg; + char * rd_ser; char * name_tmp; - - size_t msg_size = 0; - size_t name_len = 0; - size_t rd_ser_len = 0; - uint32_t rid = 0; + size_t msg_size; + size_t name_len; + size_t rd_ser_len; + uint32_t rid; GNUNET_assert (NULL != h); GNUNET_assert (NULL != zone_key); GNUNET_assert (NULL != name); GNUNET_assert (NULL != rd); GNUNET_assert (NULL != signature); - + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Storing %u records under name `%s'\n", + rd_count, + name); name_len = strlen(name) + 1; - if (name_len > 256) + if (name_len > MAX_NAME_LEN) { GNUNET_break (0); return NULL; } - - rid = get_op_id(h); + rid = get_op_id (h); qe = GNUNET_malloc(sizeof (struct GNUNET_NAMESTORE_QueueEntry)); qe->nsh = h; qe->cont = cont; qe->cont_cls = cont_cls; qe->op_id = rid; - GNUNET_CONTAINER_DLL_insert_tail(h->op_head, h->op_tail, qe); + GNUNET_CONTAINER_DLL_insert_tail (h->op_head, h->op_tail, qe); - /* set msg_size*/ + /* setup msg */ rd_ser_len = GNUNET_NAMESTORE_records_get_size(rd_count, rd); - char rd_ser[rd_ser_len]; - GNUNET_NAMESTORE_records_serialize(rd_count, rd, rd_ser_len, rd_ser); - - struct RecordPutMessage * msg; msg_size = sizeof (struct RecordPutMessage) + name_len + rd_ser_len; - - /* create msg here */ pe = GNUNET_malloc(sizeof (struct PendingMessage) + msg_size); pe->size = msg_size; pe->is_init = GNUNET_NO; msg = (struct RecordPutMessage *) &pe[1]; - name_tmp = (char *) &msg[1]; - rd_tmp = &name_tmp[name_len]; - msg->gns_header.header.type = htons (GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_PUT); msg->gns_header.header.size = htons (msg_size); msg->gns_header.r_id = htonl (rid); @@ -1039,16 +1060,17 @@ GNUNET_NAMESTORE_record_put (struct GNUNET_NAMESTORE_Handle *h, msg->expire = GNUNET_TIME_absolute_hton (freshness); msg->rd_len = htons (rd_ser_len); msg->rd_count = htons (rd_count); - msg->public_key = *zone_key; + name_tmp = (char *) &msg[1]; memcpy (name_tmp, name, name_len); - memcpy (rd_tmp, rd_ser, rd_ser_len); - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Sending `%s' message for name `%s' with size %u\n", "NAMESTORE_RECORD_PUT", name, msg_size); - + rd_ser = &name_tmp[name_len]; + GNUNET_NAMESTORE_records_serialize(rd_count, rd, rd_ser_len, rd_ser); + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Sending `%s' message for name `%s' with size %u\n", + "NAMESTORE_RECORD_PUT", + name, msg_size); GNUNET_CONTAINER_DLL_insert_tail (h->pending_head, h->pending_tail, pe); do_transmit(h); - return qe; } @@ -1058,7 +1080,7 @@ GNUNET_NAMESTORE_record_put (struct GNUNET_NAMESTORE_Handle *h, * to validate signatures received from the network. * * @param public_key public key of the zone - * @param expire block expiration + * @param freshness block expiration * @param name name that is being mapped (at most 255 characters long) * @param rd_count number of entries in 'rd' array * @param rd array of records with data to store @@ -1067,55 +1089,51 @@ GNUNET_NAMESTORE_record_put (struct GNUNET_NAMESTORE_Handle *h, */ int GNUNET_NAMESTORE_verify_signature (const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *public_key, - const struct GNUNET_TIME_Absolute expire, + const struct GNUNET_TIME_Absolute freshness, const char *name, unsigned int rd_count, const struct GNUNET_NAMESTORE_RecordData *rd, const struct GNUNET_CRYPTO_RsaSignature *signature) { - int res = GNUNET_SYSERR; - size_t rd_ser_len = 0; - size_t name_len = 0; - char * name_tmp; - char * rd_tmp; + size_t rd_ser_len; + size_t name_len; + char *name_tmp; + char *rd_ser; struct GNUNET_CRYPTO_RsaSignaturePurpose *sig_purpose; struct GNUNET_TIME_AbsoluteNBO *expire_tmp; - struct GNUNET_TIME_AbsoluteNBO expire_nbo = GNUNET_TIME_absolute_hton(expire); - - GNUNET_assert (public_key != NULL); - GNUNET_assert (name != NULL); - GNUNET_assert (rd != NULL); - GNUNET_assert (signature != NULL); - - - rd_ser_len = GNUNET_NAMESTORE_records_get_size(rd_count, rd); - char rd_ser[rd_ser_len]; - GNUNET_NAMESTORE_records_serialize(rd_count, rd, rd_ser_len, rd_ser); + struct GNUNET_TIME_AbsoluteNBO expire_nbo = GNUNET_TIME_absolute_hton (freshness); + uint32_t sig_len; + GNUNET_assert (NULL != public_key); + GNUNET_assert (NULL != name); + GNUNET_assert (NULL != rd); + GNUNET_assert (NULL != signature); name_len = strlen (name) + 1; - if (name_len > 256) + if (name_len > MAX_NAME_LEN) { GNUNET_break (0); return GNUNET_SYSERR; } - - sig_purpose = GNUNET_malloc(sizeof (struct GNUNET_CRYPTO_RsaSignaturePurpose) + sizeof (struct GNUNET_TIME_AbsoluteNBO) + rd_ser_len + name_len); - sig_purpose->size = htonl (sizeof (struct GNUNET_CRYPTO_RsaSignaturePurpose)+ rd_ser_len + name_len); - sig_purpose->purpose = htonl (GNUNET_SIGNATURE_PURPOSE_GNS_RECORD_SIGN); - expire_tmp = (struct GNUNET_TIME_AbsoluteNBO *) &sig_purpose[1]; - name_tmp = (char *) &expire_tmp[1]; - rd_tmp = &name_tmp[name_len]; - memcpy (expire_tmp, &expire_nbo, sizeof (struct GNUNET_TIME_AbsoluteNBO)); - memcpy (name_tmp, name, name_len); - memcpy (rd_tmp, rd_ser, rd_ser_len); - - res = GNUNET_CRYPTO_rsa_verify(GNUNET_SIGNATURE_PURPOSE_GNS_RECORD_SIGN, sig_purpose, signature, public_key); - - GNUNET_free (sig_purpose); - - return res; + rd_ser_len = GNUNET_NAMESTORE_records_get_size (rd_count, rd); + sig_len = sizeof (struct GNUNET_CRYPTO_RsaSignaturePurpose) + sizeof (struct GNUNET_TIME_AbsoluteNBO) + rd_ser_len + name_len; + { + char sig_buf[sig_len] GNUNET_ALIGN; + + sig_purpose = (struct GNUNET_CRYPTO_RsaSignaturePurpose *) sig_buf; + sig_purpose->size = htonl (sig_len); + sig_purpose->purpose = htonl (GNUNET_SIGNATURE_PURPOSE_GNS_RECORD_SIGN); + expire_tmp = (struct GNUNET_TIME_AbsoluteNBO *) &sig_purpose[1]; + memcpy (expire_tmp, &expire_nbo, sizeof (struct GNUNET_TIME_AbsoluteNBO)); + name_tmp = (char *) &expire_tmp[1]; + memcpy (name_tmp, name, name_len); + rd_ser = &name_tmp[name_len]; + GNUNET_assert (rd_ser_len == + GNUNET_NAMESTORE_records_serialize (rd_count, rd, rd_ser_len, rd_ser)); + return GNUNET_CRYPTO_rsa_verify (GNUNET_SIGNATURE_PURPOSE_GNS_RECORD_SIGN, sig_purpose, signature, public_key); + } } + /** * Store an item in the namestore. If the item is already present, * the expiration time is updated to the max of the existing time and @@ -1141,55 +1159,48 @@ GNUNET_NAMESTORE_record_create (struct GNUNET_NAMESTORE_Handle *h, struct PendingMessage *pe; char * name_tmp; char * pkey_tmp; - char * rd_tmp; - size_t rd_ser_len = 0; - size_t msg_size = 0; - size_t name_len = 0; - size_t key_len = 0; - uint32_t rid = 0; + char * rd_ser; + size_t rd_ser_len; + size_t msg_size; + size_t name_len; + size_t key_len; + uint32_t rid; + struct RecordCreateMessage * msg; + struct GNUNET_CRYPTO_RsaPrivateKeyBinaryEncoded * pkey_enc; GNUNET_assert (NULL != h); GNUNET_assert (NULL != pkey); GNUNET_assert (NULL != name); GNUNET_assert (NULL != rd); - + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Creating record of type %u under name `%s'\n", + rd->record_type, + name); name_len = strlen(name) + 1; - if (name_len > 256) + if (name_len > MAX_NAME_LEN) { GNUNET_break (0); return NULL; } - rid = get_op_id(h); qe = GNUNET_malloc(sizeof (struct GNUNET_NAMESTORE_QueueEntry)); qe->nsh = h; qe->cont = cont; qe->cont_cls = cont_cls; qe->op_id = rid; - GNUNET_CONTAINER_DLL_insert_tail(h->op_head, h->op_tail, qe); + GNUNET_CONTAINER_DLL_insert_tail (h->op_head, h->op_tail, qe); - /* set msg_size*/ - struct GNUNET_CRYPTO_RsaPrivateKeyBinaryEncoded * pkey_enc = GNUNET_CRYPTO_rsa_encode_key (pkey); - GNUNET_assert (pkey_enc != NULL); - key_len = ntohs (pkey_enc->len); + pkey_enc = GNUNET_CRYPTO_rsa_encode_key (pkey); + GNUNET_assert (NULL != pkey_enc); + /* setup msg */ + key_len = ntohs (pkey_enc->len); rd_ser_len = GNUNET_NAMESTORE_records_get_size(1, rd); - char rd_ser[rd_ser_len]; - GNUNET_NAMESTORE_records_serialize(1, rd, rd_ser_len, rd_ser); - - struct RecordCreateMessage * msg; msg_size = sizeof (struct RecordCreateMessage) + key_len + name_len + rd_ser_len; - - /* create msg here */ pe = GNUNET_malloc(sizeof (struct PendingMessage) + msg_size); pe->size = msg_size; pe->is_init = GNUNET_NO; msg = (struct RecordCreateMessage *) &pe[1]; - - pkey_tmp = (char *) &msg[1]; - name_tmp = &pkey_tmp[key_len]; - rd_tmp = &name_tmp[name_len]; - msg->gns_header.header.type = htons (GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_CREATE); msg->gns_header.header.size = htons (msg_size); msg->gns_header.r_id = htonl (rid); @@ -1198,13 +1209,18 @@ GNUNET_NAMESTORE_record_create (struct GNUNET_NAMESTORE_Handle *h, msg->rd_len = htons (rd_ser_len); msg->pkey_len = htons (key_len); msg->expire = GNUNET_TIME_absolute_hton(GNUNET_TIME_UNIT_FOREVER_ABS); + pkey_tmp = (char *) &msg[1]; memcpy (pkey_tmp, pkey_enc, key_len); + name_tmp = &pkey_tmp[key_len]; memcpy (name_tmp, name, name_len); - memcpy (rd_tmp, rd_ser, rd_ser_len); - GNUNET_free (pkey_enc); + rd_ser = &name_tmp[name_len]; + GNUNET_NAMESTORE_records_serialize(1, rd, rd_ser_len, rd_ser); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Sending `%s' message for name `%s' with size %u\n", "NAMESTORE_RECORD_CREATE", name, msg_size); + GNUNET_free (pkey_enc); + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Sending `%s' message for name `%s' with size %u\n", + "NAMESTORE_RECORD_CREATE", name, msg_size); GNUNET_CONTAINER_DLL_insert_tail (h->pending_head, h->pending_tail, pe); do_transmit(h); return qe; @@ -1235,55 +1251,49 @@ GNUNET_NAMESTORE_record_remove (struct GNUNET_NAMESTORE_Handle *h, void *cont_cls) { struct GNUNET_NAMESTORE_QueueEntry *qe; + struct GNUNET_CRYPTO_RsaPrivateKeyBinaryEncoded * pkey_enc; struct PendingMessage *pe; + struct RecordRemoveMessage * msg; char *pkey_tmp; - char *rd_tmp; + char *rd_ser; char *name_tmp; - size_t rd_ser_len = 0; - size_t msg_size = 0; - size_t name_len = 0; - size_t key_len = 0; - uint32_t rid = 0; - uint16_t rd_count = 1; + size_t rd_ser_len; + size_t msg_size; + size_t name_len; + size_t key_len; + uint32_t rid; + uint16_t rd_count; GNUNET_assert (NULL != h); - + if (NULL != rd) + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Removing record of type %u under name `%s'\n", + rd->record_type, + name); + else + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Removing all records under name `%s'\n", + name); rid = get_op_id(h); qe = GNUNET_malloc(sizeof (struct GNUNET_NAMESTORE_QueueEntry)); qe->nsh = h; qe->cont = cont; qe->cont_cls = cont_cls; qe->op_id = rid; - GNUNET_CONTAINER_DLL_insert_tail(h->op_head, h->op_tail, qe); + GNUNET_CONTAINER_DLL_insert_tail (h->op_head, h->op_tail, qe); - /* set msg_size*/ - struct GNUNET_CRYPTO_RsaPrivateKeyBinaryEncoded * pkey_enc = GNUNET_CRYPTO_rsa_encode_key (pkey); - GNUNET_assert (pkey_enc != NULL); + pkey_enc = GNUNET_CRYPTO_rsa_encode_key (pkey); + GNUNET_assert (NULL != pkey_enc); key_len = ntohs (pkey_enc->len); - if (NULL == rd) - rd_count = 0; - else - rd_count = 1; + rd_count = (NULL == rd) ? 0 : 1; rd_ser_len = GNUNET_NAMESTORE_records_get_size (rd_count, rd); - char rd_ser[rd_ser_len]; - GNUNET_NAMESTORE_records_serialize (rd_count, rd, rd_ser_len, rd_ser); - name_len = strlen (name) + 1; - - struct RecordRemoveMessage * msg; msg_size = sizeof (struct RecordRemoveMessage) + key_len + name_len + rd_ser_len; - - /* create msg here */ pe = GNUNET_malloc(sizeof (struct PendingMessage) + msg_size); pe->size = msg_size; pe->is_init = GNUNET_NO; msg = (struct RecordRemoveMessage *) &pe[1]; - - pkey_tmp = (char *) &msg[1]; - name_tmp = &pkey_tmp[key_len]; - rd_tmp = &name_tmp[name_len]; - msg->gns_header.header.type = htons (GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_REMOVE); msg->gns_header.header.size = htons (msg_size); msg->gns_header.r_id = htonl (rid); @@ -1291,14 +1301,18 @@ GNUNET_NAMESTORE_record_remove (struct GNUNET_NAMESTORE_Handle *h, msg->rd_len = htons (rd_ser_len); msg->rd_count = htons (rd_count); msg->pkey_len = htons (key_len); + pkey_tmp = (char *) &msg[1]; memcpy (pkey_tmp, pkey_enc, key_len); + name_tmp = &pkey_tmp[key_len]; memcpy (name_tmp, name, name_len); - memcpy (rd_tmp, rd_ser, rd_ser_len); + rd_ser = &name_tmp[name_len]; + GNUNET_NAMESTORE_records_serialize (rd_count, rd, rd_ser_len, rd_ser); GNUNET_free (pkey_enc); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Sending `%s' message for name `%s' with size %u\n", "NAMESTORE_RECORD_REMOVE", name, msg_size); - + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Sending `%s' message for name `%s' with size %u\n", + "NAMESTORE_RECORD_REMOVE", name, msg_size); GNUNET_CONTAINER_DLL_insert_tail (h->pending_head, h->pending_tail, pe); do_transmit(h); return qe; @@ -1328,16 +1342,20 @@ GNUNET_NAMESTORE_lookup_record (struct GNUNET_NAMESTORE_Handle *h, { struct GNUNET_NAMESTORE_QueueEntry *qe; struct PendingMessage *pe; - size_t msg_size = 0; - size_t name_len = 0; - uint32_t rid = 0; + struct LookupNameMessage * msg; + size_t msg_size; + size_t name_len; + uint32_t rid; GNUNET_assert (NULL != h); GNUNET_assert (NULL != zone); GNUNET_assert (NULL != name); - + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Looking for record of type %u under name `%s'\n", + record_type, + name); name_len = strlen (name) + 1; - if ((name_len == 0) || (name_len > 256)) + if ((name_len == 0) || (name_len > MAX_NAME_LEN)) { GNUNET_break (0); return NULL; @@ -1349,14 +1367,10 @@ GNUNET_NAMESTORE_lookup_record (struct GNUNET_NAMESTORE_Handle *h, qe->proc = proc; qe->proc_cls = proc_cls; qe->op_id = rid; - GNUNET_CONTAINER_DLL_insert_tail(h->op_head, h->op_tail, qe); + GNUNET_CONTAINER_DLL_insert_tail (h->op_head, h->op_tail, qe); - /* set msg_size*/ msg_size = sizeof (struct LookupNameMessage) + name_len; pe = GNUNET_malloc(sizeof (struct PendingMessage) + msg_size); - - /* create msg here */ - struct LookupNameMessage * msg; pe->size = msg_size; pe->is_init = GNUNET_NO; msg = (struct LookupNameMessage *) &pe[1]; @@ -1368,12 +1382,10 @@ GNUNET_NAMESTORE_lookup_record (struct GNUNET_NAMESTORE_Handle *h, msg->zone = *zone; memcpy (&msg[1], name, name_len); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Sending `%s' message for name `%s'\n", "NAMESTORE_LOOKUP_NAME", name); - - /* transmit message */ + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Sending `%s' message for name `%s'\n", "NAMESTORE_LOOKUP_NAME", name); GNUNET_CONTAINER_DLL_insert_tail (h->pending_head, h->pending_tail, pe); do_transmit(h); - return qe; } @@ -1399,27 +1411,23 @@ GNUNET_NAMESTORE_zone_to_name (struct GNUNET_NAMESTORE_Handle *h, { struct GNUNET_NAMESTORE_QueueEntry *qe; struct PendingMessage *pe; - size_t msg_size = 0; - uint32_t rid = 0; + struct ZoneToNameMessage * msg; + size_t msg_size; + uint32_t rid; GNUNET_assert (NULL != h); GNUNET_assert (NULL != zone); GNUNET_assert (NULL != value_zone); - rid = get_op_id(h); qe = GNUNET_malloc(sizeof (struct GNUNET_NAMESTORE_QueueEntry)); qe->nsh = h; qe->proc = proc; qe->proc_cls = proc_cls; qe->op_id = rid; - GNUNET_CONTAINER_DLL_insert_tail(h->op_head, h->op_tail, qe); + GNUNET_CONTAINER_DLL_insert_tail (h->op_head, h->op_tail, qe); - /* set msg_size*/ msg_size = sizeof (struct ZoneToNameMessage); pe = GNUNET_malloc(sizeof (struct PendingMessage) + msg_size); - - /* create msg here */ - struct ZoneToNameMessage * msg; pe->size = msg_size; pe->is_init = GNUNET_NO; msg = (struct ZoneToNameMessage *) &pe[1]; @@ -1429,22 +1437,13 @@ GNUNET_NAMESTORE_zone_to_name (struct GNUNET_NAMESTORE_Handle *h, msg->zone = *zone; msg->value_zone = *value_zone; - char * z_tmp = GNUNET_strdup (GNUNET_short_h2s (zone)); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Sending `%s' message for zone `%s' in zone `%s'\n", - "NAMESTORE_ZONE_TO_NAME", - z_tmp, - GNUNET_short_h2s (value_zone)); - GNUNET_free (z_tmp); - /* transmit message */ GNUNET_CONTAINER_DLL_insert_tail (h->pending_head, h->pending_tail, pe); do_transmit(h); - return qe; } - /** * Starts a new zone iteration (used to periodically PUT all of our * records into our DHT). This MUST lock the GNUNET_NAMESTORE_Handle @@ -1473,19 +1472,17 @@ GNUNET_NAMESTORE_zone_iteration_start (struct GNUNET_NAMESTORE_Handle *h, { struct GNUNET_NAMESTORE_ZoneIterator *it; struct PendingMessage *pe; - size_t msg_size = 0; - uint32_t rid = 0; + struct ZoneIterationStartMessage * msg; + size_t msg_size; + uint32_t rid; GNUNET_assert (NULL != h); - - rid = get_op_id(h); it = GNUNET_malloc (sizeof (struct GNUNET_NAMESTORE_ZoneIterator)); it->h = h; it->proc = proc; it->proc_cls = proc_cls; it->op_id = rid; - if (NULL != zone) { it->zone = *zone; @@ -1496,14 +1493,10 @@ GNUNET_NAMESTORE_zone_iteration_start (struct GNUNET_NAMESTORE_Handle *h, memset (&it->zone, '\0', sizeof (it->zone)); it->has_zone = GNUNET_NO; } - GNUNET_CONTAINER_DLL_insert_tail(h->z_head, h->z_tail, it); + GNUNET_CONTAINER_DLL_insert_tail (h->z_head, h->z_tail, it); - /* set msg_size*/ msg_size = sizeof (struct ZoneIterationStartMessage); - pe = GNUNET_malloc(sizeof (struct PendingMessage) + msg_size); - - /* create msg here */ - struct ZoneIterationStartMessage * msg; + pe = GNUNET_malloc (sizeof (struct PendingMessage) + msg_size); pe->size = msg_size; pe->is_init = GNUNET_NO; msg = (struct ZoneIterationStartMessage *) &pe[1]; @@ -1512,23 +1505,21 @@ GNUNET_NAMESTORE_zone_iteration_start (struct GNUNET_NAMESTORE_Handle *h, msg->gns_header.r_id = htonl (rid); if (NULL != zone) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Sending `%s' message for zone `%s'\n", "ZONE_ITERATION_START", GNUNET_short_h2s(zone)); + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Sending `%s' message for zone `%s'\n", + "ZONE_ITERATION_START", GNUNET_short_h2s(zone)); msg->zone = *zone; } else { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Sending `%s' message for all zones\n", "ZONE_ITERATION_START"); + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Sending `%s' message for all zones\n", "ZONE_ITERATION_START"); memset (&msg->zone, '\0', sizeof (msg->zone)); } msg->must_have_flags = ntohs (must_have_flags); msg->must_not_have_flags = ntohs (must_not_have_flags); - - - - /* transmit message */ GNUNET_CONTAINER_DLL_insert_tail (h->pending_head, h->pending_tail, pe); do_transmit(h); - return it; } @@ -1543,37 +1534,21 @@ void GNUNET_NAMESTORE_zone_iterator_next (struct GNUNET_NAMESTORE_ZoneIterator *it) { struct GNUNET_NAMESTORE_Handle *h; + struct ZoneIterationNextMessage * msg; struct PendingMessage *pe; - size_t msg_size = 0; + size_t msg_size; GNUNET_assert (NULL != it); h = it->h; - struct GNUNET_NAMESTORE_ZoneIterator *tmp = it->h->z_head; - - while (tmp != NULL) - { - if (tmp == it) - break; - tmp = tmp->next; - } - GNUNET_assert (NULL != tmp); - - /* set msg_size*/ msg_size = sizeof (struct ZoneIterationNextMessage); pe = GNUNET_malloc(sizeof (struct PendingMessage) + msg_size); - - /* create msg here */ - struct ZoneIterationNextMessage * msg; pe->size = msg_size; pe->is_init = GNUNET_NO; msg = (struct ZoneIterationNextMessage *) &pe[1]; msg->gns_header.header.type = htons (GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_ITERATION_NEXT); msg->gns_header.header.size = htons (msg_size); msg->gns_header.r_id = htonl (it->op_id); - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Sending `%s' message\n", "ZONE_ITERATION_NEXT"); - - /* transmit message */ + LOG (GNUNET_ERROR_TYPE_DEBUG, "Sending `%s' message\n", "ZONE_ITERATION_NEXT"); GNUNET_CONTAINER_DLL_insert_tail (h->pending_head, h->pending_tail, pe); do_transmit(h); } @@ -1587,41 +1562,33 @@ GNUNET_NAMESTORE_zone_iterator_next (struct GNUNET_NAMESTORE_ZoneIterator *it) void GNUNET_NAMESTORE_zone_iteration_stop (struct GNUNET_NAMESTORE_ZoneIterator *it) { - GNUNET_assert (NULL != it); + struct GNUNET_NAMESTORE_Handle *h; struct PendingMessage *pe; - size_t msg_size = 0; - struct GNUNET_NAMESTORE_Handle *h = it->h; - struct GNUNET_NAMESTORE_ZoneIterator *tmp = it->h->z_head; - - while (tmp != NULL) - { - if (tmp == it) - break; - tmp = tmp->next; - } - GNUNET_assert (NULL != tmp); + size_t msg_size; + struct ZoneIterationStopMessage * msg; - /* set msg_size*/ + GNUNET_assert (NULL != it); + h = it->h; + GNUNET_CONTAINER_DLL_remove (h->z_head, + h->z_tail, + it); msg_size = sizeof (struct ZoneIterationStopMessage); pe = GNUNET_malloc(sizeof (struct PendingMessage) + msg_size); - - /* create msg here */ - struct ZoneIterationStopMessage * msg; pe->size = msg_size; pe->is_init = GNUNET_NO; msg = (struct ZoneIterationStopMessage *) &pe[1]; msg->gns_header.header.type = htons (GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_ITERATION_STOP); msg->gns_header.header.size = htons (msg_size); msg->gns_header.r_id = htonl (it->op_id); - if (GNUNET_YES == it->has_zone) - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Sending `%s' message for zone `%s'\n", "ZONE_ITERATION_STOP", GNUNET_short_h2s(&it->zone)); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Sending `%s' message for zone `%s'\n", "ZONE_ITERATION_STOP", GNUNET_short_h2s(&it->zone)); else - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Sending `%s' message for all zones\n", "ZONE_ITERATION_STOP"); - - /* transmit message */ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Sending `%s' message for all zones\n", "ZONE_ITERATION_STOP"); GNUNET_CONTAINER_DLL_insert_tail (h->pending_head, h->pending_tail, pe); do_transmit(h); + GNUNET_free (it); } @@ -1636,11 +1603,9 @@ GNUNET_NAMESTORE_cancel (struct GNUNET_NAMESTORE_QueueEntry *qe) { struct GNUNET_NAMESTORE_Handle *h = qe->nsh; - GNUNET_assert (qe != NULL); - + GNUNET_assert (NULL != qe); GNUNET_CONTAINER_DLL_remove(h->op_head, h->op_tail, qe); GNUNET_free(qe); - } /* end of namestore_api.c */ diff --git a/src/namestore/namestore_common.c b/src/namestore/namestore_common.c index 95f6364..71e89f4 100644 --- a/src/namestore/namestore_common.c +++ b/src/namestore/namestore_common.c @@ -32,11 +32,13 @@ #include "gnunet_arm_service.h" #include "gnunet_namestore_service.h" #include "gnunet_dnsparser_lib.h" +#include "gns_protocol.h" #include "namestore.h" #define LOG(kind,...) GNUNET_log_from (kind, "gns-api",__VA_ARGS__) +GNUNET_NETWORK_STRUCT_BEGIN /** * Internal format of a record in the serialized form. @@ -45,27 +47,45 @@ struct NetworkRecord { /** - * Expiration time for the DNS record. + * Expiration time for the DNS record; relative or absolute depends + * on 'flags', network byte order. */ - struct GNUNET_TIME_AbsoluteNBO expiration; + uint64_t expiration_time GNUNET_PACKED; /** * Number of bytes in 'data', network byte order. */ - uint32_t data_size; + uint32_t data_size GNUNET_PACKED; /** * Type of the GNS/DNS record, network byte order. */ - uint32_t record_type; + uint32_t record_type GNUNET_PACKED; /** * Flags for the record, network byte order. */ - uint32_t flags; + uint32_t flags GNUNET_PACKED; }; +GNUNET_NETWORK_STRUCT_END + +/** + * Convert a UTF-8 string to UTF-8 lowercase + * @param src source string + * @return converted result + */ +char * +GNUNET_NAMESTORE_normalize_string (const char *src) +{ + GNUNET_assert (NULL != src); + char *res = strdup (src); + /* normalize */ + GNUNET_STRINGS_utf8_tolower(src, &res); + return res; +} + /** * Convert a short hash to a string (for printing debug messages). @@ -120,7 +140,7 @@ GNUNET_NAMESTORE_records_get_size (unsigned int rd_count, * @param dest_size size of the destination array * @param dest where to write the result * - * @return the size of serialized records + * @return the size of serialized records, -1 if records do not fit */ ssize_t GNUNET_NAMESTORE_records_serialize (unsigned int rd_count, @@ -135,7 +155,7 @@ GNUNET_NAMESTORE_records_serialize (unsigned int rd_count, off = 0; for (i=0;irecord_type == b->record_type) && - (a->expiration.abs_value == b->expiration.abs_value) && - (a->data_size == b->data_size) && - (0 == memcmp (a->data, b->data, a->data_size))) - return GNUNET_YES; - else + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Comparing records\n"); + if (a->record_type != b->record_type) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Record type %lu != %lu\n", a->record_type, b->record_type); + return GNUNET_NO; + } + if ((a->expiration_time != b->expiration_time) && + ((a->expiration_time != 0) && (b->expiration_time != 0))) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Expiration time %llu != %llu\n", a->expiration_time, b->expiration_time); + return GNUNET_NO; + } + if ((a->flags & GNUNET_NAMESTORE_RF_RCMP_FLAGS) + != (b->flags & GNUNET_NAMESTORE_RF_RCMP_FLAGS)) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Flags %lu (%lu) != %lu (%lu)\n", a->flags, + a->flags & GNUNET_NAMESTORE_RF_RCMP_FLAGS, b->flags, + b->flags & GNUNET_NAMESTORE_RF_RCMP_FLAGS); + return GNUNET_NO; + } + if (a->data_size != b->data_size) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Data size %lu != %lu\n", a->data_size, b->data_size); return GNUNET_NO; + } + if (0 != memcmp (a->data, b->data, a->data_size)) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Data contents do not match\n"); + return GNUNET_NO; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Records are equal\n"); + return GNUNET_YES; } @@ -199,7 +253,7 @@ GNUNET_NAMESTORE_records_deserialize (size_t len, if (off + sizeof (rec) > len) return GNUNET_SYSERR; memcpy (&rec, &src[off], sizeof (rec)); - dest[i].expiration = GNUNET_TIME_absolute_ntoh (rec.expiration); + dest[i].expiration_time = GNUNET_ntohll (rec.expiration_time); dest[i].data_size = ntohl ((uint32_t) rec.data_size); dest[i].record_type = ntohl (rec.record_type); dest[i].flags = ntohl (rec.flags); @@ -213,6 +267,7 @@ GNUNET_NAMESTORE_records_deserialize (size_t len, return GNUNET_OK; } + /** * Sign name and records * @@ -226,48 +281,49 @@ GNUNET_NAMESTORE_records_deserialize (size_t len, */ struct GNUNET_CRYPTO_RsaSignature * GNUNET_NAMESTORE_create_signature (const struct GNUNET_CRYPTO_RsaPrivateKey *key, - struct GNUNET_TIME_Absolute expire, - const char *name, - const struct GNUNET_NAMESTORE_RecordData *rd, - unsigned int rd_count) + struct GNUNET_TIME_Absolute expire, + const char *name, + const struct GNUNET_NAMESTORE_RecordData *rd, + unsigned int rd_count) { - struct GNUNET_CRYPTO_RsaSignature *sig = GNUNET_malloc(sizeof (struct GNUNET_CRYPTO_RsaSignature)); + struct GNUNET_CRYPTO_RsaSignature *sig; struct GNUNET_CRYPTO_RsaSignaturePurpose *sig_purpose; - struct GNUNET_TIME_AbsoluteNBO expire_nbo = GNUNET_TIME_absolute_hton(expire); + struct GNUNET_TIME_AbsoluteNBO expire_nbo; size_t rd_ser_len; size_t name_len; - struct GNUNET_TIME_AbsoluteNBO *expire_tmp; char * name_tmp; char * rd_tmp; int res; + uint32_t sig_len; - if (name == NULL) + if (NULL == name) { GNUNET_break (0); - GNUNET_free (sig); return NULL; } + sig = GNUNET_malloc (sizeof (struct GNUNET_CRYPTO_RsaSignature)); name_len = strlen (name) + 1; - - rd_ser_len = GNUNET_NAMESTORE_records_get_size(rd_count, rd); - char rd_ser[rd_ser_len]; - GNUNET_NAMESTORE_records_serialize(rd_count, rd, rd_ser_len, rd_ser); - - sig_purpose = GNUNET_malloc(sizeof (struct GNUNET_CRYPTO_RsaSignaturePurpose) + sizeof (struct GNUNET_TIME_AbsoluteNBO) + rd_ser_len + name_len); - sig_purpose->size = htonl (sizeof (struct GNUNET_CRYPTO_RsaSignaturePurpose)+ rd_ser_len + name_len); - sig_purpose->purpose = htonl (GNUNET_SIGNATURE_PURPOSE_GNS_RECORD_SIGN); - expire_tmp = (struct GNUNET_TIME_AbsoluteNBO *) &sig_purpose[1]; - name_tmp = (char *) &expire_tmp[1]; - rd_tmp = &name_tmp[name_len]; - memcpy (expire_tmp, &expire_nbo, sizeof (struct GNUNET_TIME_AbsoluteNBO)); - memcpy (name_tmp, name, name_len); - memcpy (rd_tmp, rd_ser, rd_ser_len); - - res = GNUNET_CRYPTO_rsa_sign (key, sig_purpose, sig); - - GNUNET_free (sig_purpose); - + expire_nbo = GNUNET_TIME_absolute_hton (expire); + rd_ser_len = GNUNET_NAMESTORE_records_get_size (rd_count, rd); + { + char rd_ser[rd_ser_len]; + + GNUNET_assert (rd_ser_len == + GNUNET_NAMESTORE_records_serialize (rd_count, rd, rd_ser_len, rd_ser)); + sig_len = sizeof (struct GNUNET_CRYPTO_RsaSignaturePurpose) + sizeof (struct GNUNET_TIME_AbsoluteNBO) + rd_ser_len + name_len; + sig_purpose = GNUNET_malloc (sig_len); + sig_purpose->size = htonl (sig_len); + sig_purpose->purpose = htonl (GNUNET_SIGNATURE_PURPOSE_GNS_RECORD_SIGN); + expire_tmp = (struct GNUNET_TIME_AbsoluteNBO *) &sig_purpose[1]; + memcpy (expire_tmp, &expire_nbo, sizeof (struct GNUNET_TIME_AbsoluteNBO)); + name_tmp = (char *) &expire_tmp[1]; + memcpy (name_tmp, name, name_len); + rd_tmp = &name_tmp[name_len]; + memcpy (rd_tmp, rd_ser, rd_ser_len); + res = GNUNET_CRYPTO_rsa_sign (key, sig_purpose, sig); + GNUNET_free (sig_purpose); + } if (GNUNET_OK != res) { GNUNET_break (0); @@ -277,22 +333,6 @@ GNUNET_NAMESTORE_create_signature (const struct GNUNET_CRYPTO_RsaPrivateKey *key return sig; } -/** - * Checks if a name is wellformed - * - * @param name the name to check - * @return GNUNET_OK on success, GNUNET_SYSERR on error - */ -int -GNUNET_NAMESTORE_check_name (const char * name) -{ - if (name == NULL) - return GNUNET_SYSERR; - if (strlen (name) > 63) - return GNUNET_SYSERR; - return GNUNET_OK; -} - /** * Convert the 'value' of a record to a string. @@ -307,18 +347,21 @@ GNUNET_NAMESTORE_value_to_string (uint32_t type, const void *data, size_t data_size) { - char tmp[INET6_ADDRSTRLEN]; - struct GNUNET_CRYPTO_ShortHashAsciiEncoded enc; uint16_t mx_pref; + const struct soa_data *soa; + const struct vpn_data *vpn; + const struct srv_data *srv; + const struct tlsa_data *tlsa; + struct GNUNET_CRYPTO_ShortHashAsciiEncoded enc; + struct GNUNET_CRYPTO_HashAsciiEncoded s_peer; + const char *cdata; + char* vpn_str; + char* srv_str; + char* tlsa_str; char* result; - char* soa_rname; - char* soa_mname; - uint32_t* soa_data; - uint32_t soa_serial; - uint32_t soa_refresh; - uint32_t soa_retry; - uint32_t soa_expire; - uint32_t soa_min; + const char* soa_rname; + const char* soa_mname; + char tmp[INET6_ADDRSTRLEN]; switch (type) { @@ -335,20 +378,26 @@ GNUNET_NAMESTORE_value_to_string (uint32_t type, case GNUNET_DNSPARSER_TYPE_CNAME: return GNUNET_strndup (data, data_size); case GNUNET_DNSPARSER_TYPE_SOA: - soa_rname = (char*)data; - soa_mname = (char*)data+strlen(soa_rname)+1; - soa_data = (uint32_t*)(soa_mname+strlen(soa_mname)+1); - soa_serial = ntohl(soa_data[0]); - soa_refresh = ntohl(soa_data[1]); - soa_retry = ntohl(soa_data[2]); - soa_expire = ntohl(soa_data[3]); - soa_min = ntohl(soa_data[4]); - if (GNUNET_asprintf(&result, "rname=%s mname=%s %lu,%lu,%lu,%lu,%lu", - soa_rname, soa_mname, - soa_serial, soa_refresh, soa_retry, soa_expire, soa_min)) - return result; - else + if (data_size <= sizeof (struct soa_data)) + return NULL; + soa = data; + soa_rname = (const char*) &soa[1]; + soa_mname = memchr (soa_rname, 0, data_size - sizeof (struct soa_data) - 1); + if (NULL == soa_mname) return NULL; + soa_mname++; + if (NULL == memchr (soa_mname, 0, + data_size - (sizeof (struct soa_data) + strlen (soa_rname) + 1))) + return NULL; + GNUNET_asprintf (&result, + "rname=%s mname=%s %lu,%lu,%lu,%lu,%lu", + soa_rname, soa_mname, + ntohl (soa->serial), + ntohl (soa->refresh), + ntohl (soa->retry), + ntohl (soa->expire), + ntohl (soa->minimum)); + return result; case GNUNET_DNSPARSER_TYPE_PTR: return GNUNET_strndup (data, data_size); case GNUNET_DNSPARSER_TYPE_MX: @@ -357,7 +406,10 @@ GNUNET_NAMESTORE_value_to_string (uint32_t type, != 0) return result; else + { + GNUNET_free (result); return NULL; + } case GNUNET_DNSPARSER_TYPE_TXT: return GNUNET_strndup (data, data_size); case GNUNET_DNSPARSER_TYPE_AAAA: @@ -376,6 +428,57 @@ GNUNET_NAMESTORE_value_to_string (uint32_t type, return GNUNET_strndup (data, data_size); case GNUNET_NAMESTORE_TYPE_LEHO: return GNUNET_strndup (data, data_size); + case GNUNET_NAMESTORE_TYPE_VPN: + cdata = data; + if ( (data_size <= sizeof (struct vpn_data)) || + ('\0' != cdata[data_size - 1]) ) + return NULL; /* malformed */ + vpn = data; + GNUNET_CRYPTO_hash_to_enc (&vpn->peer, &s_peer); + if (0 == GNUNET_asprintf (&vpn_str, "%u %s %s", + (unsigned int) ntohs (vpn->proto), + (const char*) &s_peer, + (const char*) &vpn[1])) + { + GNUNET_free (vpn_str); + return NULL; + } + return vpn_str; + case GNUNET_DNSPARSER_TYPE_SRV: + cdata = data; + if ( (data_size <= sizeof (struct srv_data)) || + ('\0' != cdata[data_size - 1]) ) + return NULL; /* malformed */ + srv = data; + + if (0 == GNUNET_asprintf (&srv_str, + "%d %d %d %s", + ntohs (srv->prio), + ntohs (srv->weight), + ntohs (srv->port), + (const char *)&srv[1])) + { + GNUNET_free (srv_str); + return NULL; + } + return srv_str; + case GNUNET_DNSPARSER_TYPE_TLSA: + cdata = data; + if ( (data_size <= sizeof (struct tlsa_data)) || + ('\0' != cdata[data_size - 1]) ) + return NULL; /* malformed */ + tlsa = data; + if (0 == GNUNET_asprintf (&tlsa_str, + "%c %c %c %s", + tlsa->usage, + tlsa->selector, + tlsa->matching_type, + (const char *) &tlsa[1])) + { + GNUNET_free (tlsa_str); + return NULL; + } + return tlsa_str; default: GNUNET_break (0); } @@ -403,65 +506,84 @@ GNUNET_NAMESTORE_string_to_value (uint32_t type, struct in_addr value_a; struct in6_addr value_aaaa; struct GNUNET_CRYPTO_ShortHashCode pkey; + struct soa_data *soa; + struct vpn_data *vpn; + struct tlsa_data *tlsa; + char result[253 + 1]; + char soa_rname[253 + 1]; + char soa_mname[253 + 1]; + char s_peer[103 + 1]; + char s_serv[253 + 1]; + unsigned int soa_serial; + unsigned int soa_refresh; + unsigned int soa_retry; + unsigned int soa_expire; + unsigned int soa_min; uint16_t mx_pref; uint16_t mx_pref_n; - uint32_t soa_data[5]; - char result[253]; - char soa_rname[63]; - char soa_mname[63]; - uint32_t soa_serial; - uint32_t soa_refresh; - uint32_t soa_retry; - uint32_t soa_expire; - uint32_t soa_min; + unsigned int proto; switch (type) { case 0: + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Unsupported record type %d\n"), + (int) type); return GNUNET_SYSERR; case GNUNET_DNSPARSER_TYPE_A: if (1 != inet_pton (AF_INET, s, &value_a)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Unable to parse IPv4 address `%s'\n"), + s); return GNUNET_SYSERR; + } *data = GNUNET_malloc (sizeof (struct in_addr)); memcpy (*data, &value_a, sizeof (value_a)); *data_size = sizeof (value_a); return GNUNET_OK; case GNUNET_DNSPARSER_TYPE_NS: *data = GNUNET_strdup (s); - *data_size = strlen (s); + *data_size = strlen (s) + 1; return GNUNET_OK; case GNUNET_DNSPARSER_TYPE_CNAME: *data = GNUNET_strdup (s); - *data_size = strlen (s); + *data_size = strlen (s) + 1; return GNUNET_OK; case GNUNET_DNSPARSER_TYPE_SOA: - - if (SSCANF(s, "rname=%s mname=%s %u,%u,%u,%u,%u", - soa_rname, soa_mname, - &soa_serial, &soa_refresh, &soa_retry, &soa_expire, &soa_min) - != 7) + if (7 != SSCANF (s, + "rname=%253s mname=%253s %u,%u,%u,%u,%u", + soa_rname, soa_mname, + &soa_serial, &soa_refresh, &soa_retry, &soa_expire, &soa_min)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Unable to parse SOA record `%s'\n"), + s); return GNUNET_SYSERR; - - *data_size = sizeof (soa_data)+strlen(soa_rname)+strlen(soa_mname)+2; + } + *data_size = sizeof (struct soa_data)+strlen(soa_rname)+strlen(soa_mname)+2; *data = GNUNET_malloc (*data_size); - soa_data[0] = htonl(soa_serial); - soa_data[1] = htonl(soa_refresh); - soa_data[2] = htonl(soa_retry); - soa_data[3] = htonl(soa_expire); - soa_data[4] = htonl(soa_min); - strcpy(*data, soa_rname); - strcpy(*data+strlen(*data)+1, soa_mname); - memcpy(*data+strlen(*data)+1+strlen(soa_mname)+1, - soa_data, sizeof(soa_data)); + soa = (struct soa_data*)*data; + soa->serial = htonl(soa_serial); + soa->refresh = htonl(soa_refresh); + soa->retry = htonl(soa_retry); + soa->expire = htonl(soa_expire); + soa->minimum = htonl(soa_min); + strcpy((char*)&soa[1], soa_rname); + strcpy((char*)&soa[1]+strlen(*data)+1, soa_mname); return GNUNET_OK; - case GNUNET_DNSPARSER_TYPE_PTR: *data = GNUNET_strdup (s); *data_size = strlen (s); return GNUNET_OK; case GNUNET_DNSPARSER_TYPE_MX: - if (SSCANF(s, "%hu,%s", &mx_pref, result) != 2) + if (2 != SSCANF(s, "%hu,%253s", &mx_pref, result)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Unable to parse MX record `%s'\n"), + s); return GNUNET_SYSERR; + } *data_size = sizeof (uint16_t)+strlen(result)+1; *data = GNUNET_malloc (*data_size); mx_pref_n = htons(mx_pref); @@ -474,7 +596,12 @@ GNUNET_NAMESTORE_string_to_value (uint32_t type, return GNUNET_OK; case GNUNET_DNSPARSER_TYPE_AAAA: if (1 != inet_pton (AF_INET6, s, &value_aaaa)) - return GNUNET_SYSERR; + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Unable to parse IPv6 address `%s'\n"), + s); + return GNUNET_SYSERR; + } *data = GNUNET_malloc (sizeof (struct in6_addr)); *data_size = sizeof (struct in6_addr); memcpy (*data, &value_aaaa, sizeof (value_aaaa)); @@ -482,7 +609,12 @@ GNUNET_NAMESTORE_string_to_value (uint32_t type, case GNUNET_NAMESTORE_TYPE_PKEY: if (GNUNET_OK != GNUNET_CRYPTO_short_hash_from_string (s, &pkey)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Unable to parse PKEY record `%s'\n"), + s); return GNUNET_SYSERR; + } *data = GNUNET_malloc (sizeof (struct GNUNET_CRYPTO_ShortHashCode)); memcpy (*data, &pkey, sizeof (pkey)); *data_size = sizeof (struct GNUNET_CRYPTO_ShortHashCode); @@ -495,10 +627,50 @@ GNUNET_NAMESTORE_string_to_value (uint32_t type, *data = GNUNET_strdup (s); *data_size = strlen (s); return GNUNET_OK; + case GNUNET_NAMESTORE_TYPE_VPN: + if (3 != SSCANF (s,"%u %103s %253s", + &proto, s_peer, s_serv)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Unable to parse VPN record string `%s'\n"), + s); + return GNUNET_SYSERR; + } + *data_size = sizeof (struct vpn_data) + strlen (s_serv) + 1; + *data = vpn = GNUNET_malloc (*data_size); + if (GNUNET_OK != GNUNET_CRYPTO_hash_from_string ((char*)&s_peer, + &vpn->peer)) + { + GNUNET_free (vpn); + *data_size = 0; + return GNUNET_SYSERR; + } + vpn->proto = htons ((uint16_t) proto); + strcpy ((char*)&vpn[1], s_serv); + return GNUNET_OK; + case GNUNET_DNSPARSER_TYPE_TLSA: + *data_size = sizeof (struct tlsa_data) + strlen (s) - 6; + *data = tlsa = GNUNET_malloc (*data_size); + if (4 != SSCANF (s, "%c %c %c %s", + &tlsa->usage, + &tlsa->selector, + &tlsa->matching_type, + (char*)&tlsa[1])) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Unable to parse TLSA record string `%s'\n"), + s); + *data_size = 0; + GNUNET_free (tlsa); + return GNUNET_SYSERR; + } + return GNUNET_OK; default: - GNUNET_break (0); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Unsupported record type %d\n"), + (int) type); + return GNUNET_SYSERR; } - return GNUNET_SYSERR; } @@ -517,6 +689,8 @@ static struct { { "PKEY", GNUNET_NAMESTORE_TYPE_PKEY }, { "PSEU", GNUNET_NAMESTORE_TYPE_PSEU }, { "LEHO", GNUNET_NAMESTORE_TYPE_LEHO }, + { "VPN", GNUNET_NAMESTORE_TYPE_VPN }, + { "TLSA", GNUNET_DNSPARSER_TYPE_TLSA }, { NULL, UINT32_MAX } }; @@ -558,6 +732,22 @@ GNUNET_NAMESTORE_number_to_typename (uint32_t type) return name_map[i].name; } +/** + * Test if a given record is expired. + * + * @return GNUNET_YES if the record is expired, + * GNUNET_NO if not + */ +int +GNUNET_NAMESTORE_is_expired (const struct GNUNET_NAMESTORE_RecordData *rd) +{ + struct GNUNET_TIME_Absolute at; + + if (0 != (rd->flags & GNUNET_NAMESTORE_RF_RELATIVE_EXPIRATION)) + return GNUNET_NO; + at.abs_value = rd->expiration_time; + return (0 == GNUNET_TIME_absolute_get_remaining (at).rel_value) ? GNUNET_YES : GNUNET_NO; +} /* end of namestore_common.c */ diff --git a/src/namestore/plugin_namestore_postgres.c b/src/namestore/plugin_namestore_postgres.c new file mode 100644 index 0000000..3cddc95 --- /dev/null +++ b/src/namestore/plugin_namestore_postgres.c @@ -0,0 +1,677 @@ + /* + * This file is part of GNUnet + * (C) 2009, 2011, 2012 Christian Grothoff (and other contributing authors) + * + * GNUnet is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published + * by the Free Software Foundation; either version 3, or (at your + * option) any later version. + * + * GNUnet is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with GNUnet; see the file COPYING. If not, write to the + * Free Software Foundation, Inc., 59 Temple Place - Suite 330, + * Boston, MA 02111-1307, USA. + */ + +/** + * @file namestore/plugin_namestore_postgres.c + * @brief postgres-based namestore backend + * @author Christian Grothoff + */ + +#include "platform.h" +#include "gnunet_namestore_plugin.h" +#include "gnunet_namestore_service.h" +#include "gnunet_postgres_lib.h" +#include "namestore.h" + + +/** + * After how many ms "busy" should a DB operation fail for good? + * A low value makes sure that we are more responsive to requests + * (especially PUTs). A high value guarantees a higher success + * rate (SELECTs in iterate can take several seconds despite LIMIT=1). + * + * The default value of 1s should ensure that users do not experience + * huge latencies while at the same time allowing operations to succeed + * with reasonable probability. + */ +#define BUSY_TIMEOUT_MS 1000 + + +/** + * Log an error message at log-level 'level' that indicates + * a failure of the command 'cmd' on file 'filename' + * with the message given by strerror(errno). + */ +#define LOG_POSTGRES(db, level, cmd) do { GNUNET_log_from (level, "namestore-postgres", _("`%s' failed at %s:%d with error: %s\n"), cmd, __FILE__, __LINE__, sqlite3_errmsg(db->dbh)); } while(0) + +#define LOG(kind,...) GNUNET_log_from (kind, "namestore-postgres", __VA_ARGS__) + + +/** + * Context for all functions in this plugin. + */ +struct Plugin +{ + + const struct GNUNET_CONFIGURATION_Handle *cfg; + + /** + * Native Postgres database handle. + */ + PGconn *dbh; + +}; + + +/** + * Create our database indices. + * + * @param dbh handle to the database + */ +static void +create_indices (PGconn * dbh) +{ + /* create indices */ + if ( (GNUNET_OK != + GNUNET_POSTGRES_exec (dbh, "CREATE INDEX ir_zone_name_rv ON ns091records (zone_hash,record_name_hash,rvalue)")) || + (GNUNET_OK != + GNUNET_POSTGRES_exec (dbh, "CREATE INDEX ir_zone_delegation ON ns091records (zone_hash,zone_delegation)")) || + (GNUNET_OK != + GNUNET_POSTGRES_exec (dbh, "CREATE INDEX ir_zone_rv ON ns091records (zone_hash,rvalue)")) || + (GNUNET_OK != + GNUNET_POSTGRES_exec (dbh, "CREATE INDEX ir_zone ON ns091records (zone_hash)")) || + (GNUNET_OK != + GNUNET_POSTGRES_exec (dbh, "CREATE INDEX ir_name_rv ON ns091records (record_name_hash,rvalue)")) || + (GNUNET_OK != + GNUNET_POSTGRES_exec (dbh, "CREATE INDEX ir_rv ON ns091records (rvalue)")) ) + LOG (GNUNET_ERROR_TYPE_ERROR, + _("Failed to create indices\n")); +} + + +/** + * Initialize the database connections and associated + * data structures (create tables and indices + * as needed as well). + * + * @param plugin the plugin context (state for this module) + * @return GNUNET_OK on success + */ +static int +database_setup (struct Plugin *plugin) +{ + PGresult *res; + + plugin->dbh = GNUNET_POSTGRES_connect (plugin->cfg, + "namestore-postgres"); + if (NULL == plugin->dbh) + return GNUNET_SYSERR; + if (GNUNET_YES == + GNUNET_CONFIGURATION_get_value_yesno (plugin->cfg, + "namestore-postgres", + "TEMPORARY_TABLE")) + { + res = + PQexec (plugin->dbh, + "CREATE TEMPORARY TABLE ns091records (" + " zone_key BYTEA NOT NULL DEFAULT ''," + " zone_delegation BYTEA NOT NULL DEFAULT ''," + " zone_hash BYTEA NOT NULL DEFAULT ''," + " record_count INTEGER NOT NULL DEFAULT 0," + " record_data BYTEA NOT NULL DEFAULT ''," + " block_expiration_time BIGINT NOT NULL DEFAULT 0," + " signature BYTEA NOT NULL DEFAULT ''," + " record_name TEXT NOT NULL DEFAULT ''," + " record_name_hash BYTEA NOT NULL DEFAULT ''," + " rvalue BIGINT NOT NULL DEFAULT 0" + ")" "WITH OIDS"); + } + else + res = + PQexec (plugin->dbh, + "CREATE TABLE ns091records (" + " zone_key BYTEA NOT NULL DEFAULT ''," + " zone_delegation BYTEA NOT NULL DEFAULT ''," + " zone_hash BYTEA NOT NULL DEFAULT ''," + " record_count INTEGER NOT NULL DEFAULT 0," + " record_data BYTEA NOT NULL DEFAULT ''," + " block_expiration_time BIGINT NOT NULL DEFAULT 0," + " signature BYTEA NOT NULL DEFAULT ''," + " record_name TEXT NOT NULL DEFAULT ''," + " record_name_hash BYTEA NOT NULL DEFAULT ''," + " rvalue BIGINT NOT NULL DEFAULT 0" + ")" "WITH OIDS"); + + if ((NULL == res) || ((PQresultStatus (res) != PGRES_COMMAND_OK) && (0 != strcmp ("42P07", /* duplicate table */ + PQresultErrorField + (res, + PG_DIAG_SQLSTATE))))) + { + (void) GNUNET_POSTGRES_check_result (plugin->dbh, res, PGRES_COMMAND_OK, "CREATE TABLE", + "ns091records"); + PQfinish (plugin->dbh); + plugin->dbh = NULL; + return GNUNET_SYSERR; + } + if (PQresultStatus (res) == PGRES_COMMAND_OK) + create_indices (plugin->dbh); + PQclear (res); + + if ((GNUNET_OK != + GNUNET_POSTGRES_prepare (plugin->dbh, + "put_records", + "INSERT INTO ns091records (zone_key, record_name, record_count, record_data, block_expiration_time, signature" + ", zone_delegation, zone_hash, record_name_hash, rvalue) VALUES " + "($1, $2, $3, $4, $5, $6, $7, $8, $9, $10)", 10)) || + (GNUNET_OK != + GNUNET_POSTGRES_prepare (plugin->dbh, + "remove_records", + "DELETE FROM ns091records WHERE zone_hash=$1 AND record_name_hash=$2", 2)) || + (GNUNET_OK != + GNUNET_POSTGRES_prepare (plugin->dbh, + "iterate_records", + "SELECT zone_key, record_name, record_count, record_data, block_expiration_time, signature" + " FROM ns091records WHERE zone_hash=$1 AND record_name_hash=$2 ORDER BY rvalue LIMIT 1 OFFSET $3", 3)) || + (GNUNET_OK != + GNUNET_POSTGRES_prepare (plugin->dbh, + "iterate_by_zone", + "SELECT zone_key, record_name, record_count, record_data, block_expiration_time, signature" + " FROM ns091records WHERE zone_hash=$1 ORDER BY rvalue LIMIT 1 OFFSET $2", 2)) || + (GNUNET_OK != + GNUNET_POSTGRES_prepare (plugin->dbh, + "iterate_by_name", + "SELECT zone_key, record_name, record_count, record_data, block_expiration_time, signature" + " FROM ns091records WHERE record_name_hash=$1 ORDER BY rvalue LIMIT 1 OFFSET $2", 2)) || + (GNUNET_OK != + GNUNET_POSTGRES_prepare (plugin->dbh, + "iterate_all", + "SELECT zone_key, record_name, record_count, record_data, block_expiration_time, signature" + " FROM ns091records ORDER BY rvalue LIMIT 1 OFFSET $1", 1)) || + (GNUNET_OK != + GNUNET_POSTGRES_prepare (plugin->dbh, + "zone_to_name", + "SELECT zone_key, record_name, record_count, record_data, block_expiration_time, signature" + " FROM ns091records WHERE zone_hash=$1 AND zone_delegation=$2", 2)) || + (GNUNET_OK != + GNUNET_POSTGRES_prepare (plugin->dbh, + "delete_zone", + "DELETE FROM ns091records WHERE zone_hash=$1", 1))) + { + PQfinish (plugin->dbh); + plugin->dbh = NULL; + return GNUNET_SYSERR; + } + return GNUNET_OK; +} + + +/** + * Removes any existing record in the given zone with the same name. + * + * @param cls closure (internal context for the plugin) + * @param zone hash of the public key of the zone + * @param name name to remove (at most 255 characters long) + * @return GNUNET_OK on success + */ +static int +namestore_postgres_remove_records (void *cls, + const struct GNUNET_CRYPTO_ShortHashCode *zone, + const char *name) +{ + struct Plugin *plugin = cls; + PGresult *ret; + struct GNUNET_CRYPTO_ShortHashCode nh; + const char *paramValues[] = { + (const char *) zone, + (const char *) &nh + }; + int paramLengths[] = { + sizeof (struct GNUNET_CRYPTO_ShortHashCode), + sizeof (struct GNUNET_CRYPTO_ShortHashCode) + }; + const int paramFormats[] = { 1, 1 }; + size_t name_len; + + name_len = strlen (name); + GNUNET_CRYPTO_short_hash (name, name_len, &nh); + ret = + PQexecPrepared (plugin->dbh, "remove_records", 2, paramValues, paramLengths, + paramFormats, 1); + if (GNUNET_OK != + GNUNET_POSTGRES_check_result (plugin->dbh, ret, PGRES_COMMAND_OK, "PQexecPrepared", "remove_records")) + return GNUNET_SYSERR; + PQclear (ret); + return GNUNET_OK; +} + + +/** + * Store a record in the datastore. Removes any existing record in the + * same zone with the same name. + * + * @param cls closure (internal context for the plugin) + * @param zone_key public key of the zone + * @param expire when does the corresponding block in the DHT expire (until + * when should we never do a DHT lookup for the same name again)? + * @param name name that is being mapped (at most 255 characters long) + * @param rd_count number of entries in 'rd' array + * @param rd array of records with data to store + * @param signature signature of the record block, NULL if signature is unavailable (i.e. + * because the user queried for a particular record type only) + * @return GNUNET_OK on success, else GNUNET_SYSERR + */ +static int +namestore_postgres_put_records (void *cls, + const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *zone_key, + struct GNUNET_TIME_Absolute expire, + const char *name, + unsigned int rd_count, + const struct GNUNET_NAMESTORE_RecordData *rd, + const struct GNUNET_CRYPTO_RsaSignature *signature) +{ + struct Plugin *plugin = cls; + PGresult *ret; + struct GNUNET_CRYPTO_ShortHashCode zone; + struct GNUNET_CRYPTO_ShortHashCode zone_delegation; + struct GNUNET_CRYPTO_ShortHashCode nh; + size_t name_len; + uint64_t rvalue; + size_t data_size; + unsigned int i; + + GNUNET_CRYPTO_short_hash (zone_key, + sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded), + &zone); + (void) namestore_postgres_remove_records (plugin, &zone, name); + name_len = strlen (name); + GNUNET_CRYPTO_short_hash (name, name_len, &nh); + memset (&zone_delegation, 0, sizeof (zone_delegation)); + for (i=0;i 64 * 65536) + { + GNUNET_break (0); + return GNUNET_SYSERR; + } + { + char data[data_size]; + uint64_t expire_be = GNUNET_htonll (expire.abs_value); + uint64_t rvalue_be = GNUNET_htonll (rvalue); + uint32_t rd_count_be = htonl ((uint32_t) rd_count); + const char *paramValues[] = { + (const char *) zone_key, + (const char *) name, + (const char *) &rd_count_be, + (const char *) data, + (const char *) &expire_be, + (const char *) signature, + (const char *) &zone_delegation, + (const char *) &zone, + (const char *) &nh, + (const char *) &rvalue_be + }; + int paramLengths[] = { + sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded), + name_len, + sizeof (uint32_t), + data_size, + sizeof (uint64_t), + sizeof (struct GNUNET_CRYPTO_RsaSignature), + sizeof (struct GNUNET_CRYPTO_ShortHashCode), + sizeof (struct GNUNET_CRYPTO_ShortHashCode), + sizeof (struct GNUNET_CRYPTO_ShortHashCode), + sizeof (uint64_t) + }; + const int paramFormats[] = { 1, 1, 1, 1, 1, 1, 1, 1, 1, 1 }; + + if (data_size != GNUNET_NAMESTORE_records_serialize (rd_count, rd, + data_size, data)) + { + GNUNET_break (0); + return GNUNET_SYSERR; + } + ret = + PQexecPrepared (plugin->dbh, "put_records", 10, paramValues, paramLengths, + paramFormats, 1); + if (GNUNET_OK != + GNUNET_POSTGRES_check_result (plugin->dbh, ret, PGRES_COMMAND_OK, "PQexecPrepared", "put_records")) + return GNUNET_SYSERR; + PQclear (ret); + } + return GNUNET_OK; +} + + +/** + * The given 'postgres' result was obtained from the database. + * Parse the record and give it to the iterator. + * + * @param plugin plugin context + * @param stmt_name name of the prepared statement that was executed + * @param res result from postgres to interpret (and then clean up) + * @param iter iterator to call with the result + * @param iter_cls closure for 'iter' + * @return GNUNET_OK on success, GNUNET_NO if there were no results, GNUNET_SYSERR on error + * 'iter' will have been called unless the return value is 'GNUNET_SYSERR' + */ +static int +get_record_and_call_iterator (struct Plugin *plugin, + const char *stmt_name, + PGresult *res, + GNUNET_NAMESTORE_RecordIterator iter, void *iter_cls) +{ + unsigned int record_count; + size_t data_size; + const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *zone_key; + const struct GNUNET_CRYPTO_RsaSignature *sig; + struct GNUNET_TIME_Absolute expiration; + const char *data; + const char *name; + unsigned int cnt; + size_t name_len; + + if (GNUNET_OK != + GNUNET_POSTGRES_check_result (plugin->dbh, res, PGRES_TUPLES_OK, "PQexecPrepared", + stmt_name)) + { + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Ending iteration (postgres error)\n"); + return GNUNET_SYSERR; + } + + if (0 == (cnt = PQntuples (res))) + { + /* no result */ + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Ending iteration (no more results)\n"); + PQclear (res); + iter (iter_cls, NULL, GNUNET_TIME_UNIT_ZERO_ABS, NULL, 0, NULL, NULL); + return GNUNET_NO; + } + GNUNET_assert (1 == cnt); + if ((6 != PQnfields (res)) || + (sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded) != PQgetlength (res, 0, 0)) || + (sizeof (uint32_t) != PQfsize (res, 2)) || + (sizeof (uint64_t) != PQfsize (res, 4)) || + (sizeof (struct GNUNET_CRYPTO_RsaSignature) != PQgetlength (res, 0, 5))) + { + GNUNET_break (0); + PQclear (res); + return GNUNET_SYSERR; + } + zone_key = (const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *) PQgetvalue (res, 0, 0); + name = PQgetvalue (res, 0, 1); + name_len = PQgetlength (res, 0, 1); + record_count = ntohl (*(uint32_t *) PQgetvalue (res, 0, 2)); + data_size = PQgetlength (res, 0, 3); + data = PQgetvalue (res, 0, 3); + expiration.abs_value = + GNUNET_ntohll (*(uint64_t *) PQgetvalue (res, 0, 4)); + sig = (const struct GNUNET_CRYPTO_RsaSignature*) PQgetvalue (res, 0, 5); + if (record_count > 64 * 1024) + { + /* sanity check, don't stack allocate far too much just + because database might contain a large value here */ + GNUNET_break (0); + PQclear (res); + return GNUNET_SYSERR; + } + { + struct GNUNET_NAMESTORE_RecordData rd[record_count]; + char buf[name_len + 1]; + + memcpy (buf, name, name_len); + buf[name_len] = '\0'; + if (GNUNET_OK != + GNUNET_NAMESTORE_records_deserialize (data_size, data, + record_count, rd)) + { + GNUNET_break (0); + PQclear (res); + return GNUNET_SYSERR; + } + iter (iter_cls, zone_key, expiration, buf, + record_count, rd, sig); + } + PQclear (res); + return GNUNET_OK; +} + + +/** + * Iterate over the results for a particular key and zone in the + * datastore. Will return at most one result to the iterator. + * + * @param cls closure (internal context for the plugin) + * @param zone hash of public key of the zone, NULL to iterate over all zones + * @param name name as string, NULL to iterate over all records of the zone + * @param offset offset in the list of all matching records + * @param iter function to call with the result + * @param iter_cls closure for iter + * @return GNUNET_OK on success, GNUNET_NO if there were no results, GNUNET_SYSERR on error + * 'iter' will have been called unless the return value is 'GNUNET_SYSERR' + */ +static int +namestore_postgres_iterate_records (void *cls, + const struct GNUNET_CRYPTO_ShortHashCode *zone, + const char *name, + uint64_t offset, + GNUNET_NAMESTORE_RecordIterator iter, void *iter_cls) +{ + struct Plugin *plugin = cls; + const char *stmt_name; + struct GNUNET_CRYPTO_ShortHashCode name_hase; + uint64_t offset_be = GNUNET_htonll (offset); + const char *paramValues[] = { + (const char *) zone, + (const char *) &name_hase, + (const char *) &offset_be, + (const char *) zone, + (const char *) &offset_be, + }; + int paramLengths[] = { + sizeof (struct GNUNET_CRYPTO_ShortHashCode), + sizeof (struct GNUNET_CRYPTO_ShortHashCode), + sizeof (uint64_t), + sizeof (struct GNUNET_CRYPTO_ShortHashCode), + sizeof (uint64_t) + }; + const int paramFormats[] = { 1, 1, 1, 1, 1 }; + unsigned int num_params; + unsigned int first_param; + PGresult *res; + + if (NULL == zone) + if (NULL == name) + { + stmt_name = "iterate_all"; + num_params = 1; + first_param = 2; + } + else + { + GNUNET_CRYPTO_short_hash (name, strlen(name), &name_hase); + stmt_name = "iterate_by_name"; + num_params = 2; + first_param = 1; + } + else + if (NULL == name) + { + stmt_name = "iterate_by_zone"; + num_params = 2; + first_param = 3; + } + else + { + GNUNET_CRYPTO_short_hash (name, strlen(name), &name_hase); + stmt_name = "iterate_records"; + num_params = 3; + first_param = 0; + } + res = + PQexecPrepared (plugin->dbh, stmt_name, num_params, + ¶mValues[first_param], + ¶mLengths[first_param], + ¶mFormats[first_param], 1); + return get_record_and_call_iterator (plugin, stmt_name, res, iter, iter_cls); +} + + +/** + * Look for an existing PKEY delegation record for a given public key. + * Returns at most one result to the iterator. + * + * @param cls closure (internal context for the plugin) + * @param zone hash of public key of the zone to look up in, never NULL + * @param value_zone hash of the public key of the target zone (value), never NULL + * @param iter function to call with the result + * @param iter_cls closure for iter + * @return GNUNET_OK on success, GNUNET_NO if there were no results, GNUNET_SYSERR on error + * 'iter' will have been called unless the return value is 'GNUNET_SYSERR' + */ +static int +namestore_postgres_zone_to_name (void *cls, + const struct GNUNET_CRYPTO_ShortHashCode *zone, + const struct GNUNET_CRYPTO_ShortHashCode *value_zone, + GNUNET_NAMESTORE_RecordIterator iter, void *iter_cls) +{ + struct Plugin *plugin = cls; + const char *paramValues[] = { + (const char *) zone, + (const char *) value_zone + }; + int paramLengths[] = { + sizeof (struct GNUNET_CRYPTO_ShortHashCode), + sizeof (struct GNUNET_CRYPTO_ShortHashCode) + }; + const int paramFormats[] = { 1, 1 }; + PGresult *res; + + res = + PQexecPrepared (plugin->dbh, "zone_to_name", 2, + paramValues, paramLengths, paramFormats, 1); + return get_record_and_call_iterator (plugin, "zone_to_name", res, iter, iter_cls); +} + + +/** + * Delete an entire zone (all records). Not used in normal operation. + * + * @param cls closure (internal context for the plugin) + * @param zone zone to delete + */ +static void +namestore_postgres_delete_zone (void *cls, + const struct GNUNET_CRYPTO_ShortHashCode *zone) +{ + struct Plugin *plugin = cls; + PGresult *ret; + const char *paramValues[] = { + (const char *) zone, + }; + int paramLengths[] = { + sizeof (struct GNUNET_CRYPTO_ShortHashCode) + }; + const int paramFormats[] = { 1 }; + + ret = + PQexecPrepared (plugin->dbh, "delete_zone", 1, paramValues, paramLengths, + paramFormats, 1); + if (GNUNET_OK != + GNUNET_POSTGRES_check_result (plugin->dbh, ret, PGRES_COMMAND_OK, "PQexecPrepared", "delete_zone")) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Deleting zone failed!\n"); + return; + } + PQclear (ret); +} + + +/** + * Shutdown database connection and associate data + * structures. + * + * @param plugin the plugin context (state for this module) + */ +static void +database_shutdown (struct Plugin *plugin) +{ + PQfinish (plugin->dbh); + plugin->dbh = NULL; +} + + +/** + * Entry point for the plugin. + * + * @param cls the "struct GNUNET_NAMESTORE_PluginEnvironment*" + * @return NULL on error, othrewise the plugin context + */ +void * +libgnunet_plugin_namestore_postgres_init (void *cls) +{ + static struct Plugin plugin; + const struct GNUNET_CONFIGURATION_Handle *cfg = cls; + struct GNUNET_NAMESTORE_PluginFunctions *api; + + if (NULL != plugin.cfg) + return NULL; /* can only initialize once! */ + memset (&plugin, 0, sizeof (struct Plugin)); + plugin.cfg = cfg; + if (GNUNET_OK != database_setup (&plugin)) + { + database_shutdown (&plugin); + return NULL; + } + api = GNUNET_malloc (sizeof (struct GNUNET_NAMESTORE_PluginFunctions)); + api->cls = &plugin; + api->put_records = &namestore_postgres_put_records; + api->remove_records = &namestore_postgres_remove_records; + api->iterate_records = &namestore_postgres_iterate_records; + api->zone_to_name = &namestore_postgres_zone_to_name; + api->delete_zone = &namestore_postgres_delete_zone; + LOG (GNUNET_ERROR_TYPE_INFO, + _("Postgres database running\n")); + return api; +} + + +/** + * Exit point from the plugin. + * + * @param cls the plugin context (as returned by "init") + * @return always NULL + */ +void * +libgnunet_plugin_namestore_postgres_done (void *cls) +{ + struct GNUNET_NAMESTORE_PluginFunctions *api = cls; + struct Plugin *plugin = api->cls; + + database_shutdown (plugin); + plugin->cfg = NULL; + GNUNET_free (api); + LOG (GNUNET_ERROR_TYPE_DEBUG, + "postgres plugin is finished\n"); + return NULL; +} + +/* end of plugin_namestore_postgres.c */ diff --git a/src/namestore/plugin_namestore_sqlite.c b/src/namestore/plugin_namestore_sqlite.c index f685887..f0deb7f 100644 --- a/src/namestore/plugin_namestore_sqlite.c +++ b/src/namestore/plugin_namestore_sqlite.c @@ -199,10 +199,9 @@ database_setup (struct Plugin *plugin) if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_filename (plugin->cfg, "namestore-sqlite", "FILENAME", &afsdir)) - { - LOG (GNUNET_ERROR_TYPE_ERROR, - _ ("Option `%s' in section `%s' missing in configuration!\n"), - "FILENAME", "namestore-sqlite"); + { + GNUNET_log_config_missing (GNUNET_ERROR_TYPE_ERROR, + "namestore-sqlite", "FILENAME"); return GNUNET_SYSERR; } if (GNUNET_OK != GNUNET_DISK_file_test (afsdir)) @@ -214,13 +213,8 @@ database_setup (struct Plugin *plugin) return GNUNET_SYSERR; } } -#ifdef ENABLE_NLS - plugin->fn = - GNUNET_STRINGS_to_utf8 (afsdir, strlen (afsdir), nl_langinfo (CODESET)); -#else - plugin->fn = GNUNET_STRINGS_to_utf8 (afsdir, strlen (afsdir), "UTF-8"); /* good luck */ -#endif - GNUNET_free (afsdir); + /* afsdir should be UTF-8-encoded. If it isn't, it's a bug */ + plugin->fn = afsdir; /* Open database and precompile statements */ if (sqlite3_open (plugin->fn, &plugin->dbh) != SQLITE_OK) @@ -288,10 +282,9 @@ database_setup (struct Plugin *plugin) create_indices (plugin->dbh); -#define ALL "zone_key, record_name, record_count, record_data, block_expiration_time, signature" if ((sq_prepare (plugin->dbh, - "INSERT INTO ns091records (" ALL ", zone_delegation, zone_hash, record_name_hash, rvalue) VALUES " + "INSERT INTO ns091records (zone_key, record_name, record_count, record_data, block_expiration_time, signature, zone_delegation, zone_hash, record_name_hash, rvalue) VALUES " "(?, ?, ?, ?, ?, ?, ?, ?, ?, ?)", &plugin->put_records) != SQLITE_OK) || (sq_prepare @@ -300,27 +293,27 @@ database_setup (struct Plugin *plugin) &plugin->remove_records) != SQLITE_OK) || (sq_prepare (plugin->dbh, - "SELECT " ALL + "SELECT zone_key, record_name, record_count, record_data, block_expiration_time, signature" " FROM ns091records WHERE zone_hash=? AND record_name_hash=? ORDER BY rvalue LIMIT 1 OFFSET ?", &plugin->iterate_records) != SQLITE_OK) || (sq_prepare (plugin->dbh, - "SELECT " ALL + "SELECT zone_key, record_name, record_count, record_data, block_expiration_time, signature" " FROM ns091records WHERE zone_hash=? ORDER BY rvalue LIMIT 1 OFFSET ?", &plugin->iterate_by_zone) != SQLITE_OK) || (sq_prepare (plugin->dbh, - "SELECT " ALL + "SELECT zone_key, record_name, record_count, record_data, block_expiration_time, signature" " FROM ns091records WHERE record_name_hash=? ORDER BY rvalue LIMIT 1 OFFSET ?", &plugin->iterate_by_name) != SQLITE_OK) || (sq_prepare (plugin->dbh, - "SELECT " ALL + "SELECT zone_key, record_name, record_count, record_data, block_expiration_time, signature" " FROM ns091records ORDER BY rvalue LIMIT 1 OFFSET ?", &plugin->iterate_all) != SQLITE_OK) || (sq_prepare (plugin->dbh, - "SELECT " ALL + "SELECT zone_key, record_name, record_count, record_data, block_expiration_time, signature" " FROM ns091records WHERE zone_hash=? AND zone_delegation=?", &plugin->zone_to_name) != SQLITE_OK) || (sq_prepare @@ -331,7 +324,6 @@ database_setup (struct Plugin *plugin) LOG_SQLITE (plugin,GNUNET_ERROR_TYPE_ERROR, "precompiling"); return GNUNET_SYSERR; } -#undef ALL return GNUNET_OK; } @@ -405,6 +397,7 @@ namestore_sqlite_remove_records (void *cls, struct GNUNET_CRYPTO_ShortHashCode nh; size_t name_len; int n; + name_len = strlen (name); GNUNET_CRYPTO_short_hash (name, name_len, &nh); @@ -591,6 +584,13 @@ get_record_and_call_iterator (struct Plugin *plugin, GNUNET_break (0); ret = GNUNET_SYSERR; } + else if (record_count > 64 * 1024) + { + /* sanity check, don't stack allocate far too much just + because database might contain a large value here */ + GNUNET_break (0); + ret = GNUNET_SYSERR; + } else { struct GNUNET_NAMESTORE_RecordData rd[record_count]; @@ -601,7 +601,6 @@ get_record_and_call_iterator (struct Plugin *plugin, { GNUNET_break (0); ret = GNUNET_SYSERR; - record_count = 0; } else { @@ -746,7 +745,6 @@ namestore_sqlite_zone_to_name (void *cls, "sqlite3_reset"); return GNUNET_SYSERR; } - return get_record_and_call_iterator (plugin, stmt, iter, iter_cls); } diff --git a/src/namestore/test_namestore_api.c b/src/namestore/test_namestore_api.c index 039f1b9..c290673 100644 --- a/src/namestore/test_namestore_api.c +++ b/src/namestore/test_namestore_api.c @@ -1,6 +1,6 @@ /* This file is part of GNUnet. - (C) 2009 Christian Grothoff (and other contributing authors) + (C) 2012 Christian Grothoff (and other contributing authors) GNUnet is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published @@ -24,53 +24,49 @@ #include "platform.h" #include "gnunet_common.h" #include "gnunet_namestore_service.h" +#include "gnunet_testing_lib.h" -#define VERBOSE GNUNET_NO +#define TEST_RECORD_TYPE 1234 + +#define TEST_RECORD_DATALEN 123 + +#define TEST_RECORD_DATA 'a' -#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 10) +#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 100) -static struct GNUNET_NAMESTORE_Handle * nsh; + +static struct GNUNET_NAMESTORE_Handle *nsh; static GNUNET_SCHEDULER_TaskIdentifier endbadly_task; -static struct GNUNET_OS_Process *arm; -static struct GNUNET_CRYPTO_RsaPrivateKey * privkey; +static struct GNUNET_CRYPTO_RsaPrivateKey *privkey; + static struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded pubkey; + static struct GNUNET_CRYPTO_ShortHashCode zone; static int res; -#define TEST_RECORD_TYPE 1234 -#define TEST_RECORD_DATALEN 123 -#define TEST_RECORD_DATA 'a' - +static struct GNUNET_NAMESTORE_QueueEntry *nsqe; -static void -start_arm (const char *cfgname) -{ - arm = GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-arm", - "gnunet-service-arm", "-c", cfgname, -#if VERBOSE_PEERS - "-L", "DEBUG", -#else - "-L", "ERROR", -#endif - NULL); -} static void -stop_arm () +cleanup () { - if (NULL != arm) + if (NULL != nsh) { - if (0 != GNUNET_OS_process_kill (arm, SIGTERM)) - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); - GNUNET_OS_process_wait (arm); - GNUNET_OS_process_destroy (arm); - arm = NULL; + GNUNET_NAMESTORE_disconnect (nsh); + nsh = NULL; } + if (NULL != privkey) + { + GNUNET_CRYPTO_rsa_key_free (privkey); + privkey = NULL; + } + GNUNET_SCHEDULER_shutdown (); } + /** * Re-establish the connection to the service. * @@ -80,17 +76,12 @@ stop_arm () static void endbadly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { - if (nsh != NULL) - GNUNET_NAMESTORE_disconnect (nsh, GNUNET_YES); - nsh = NULL; - - if (privkey != NULL) - GNUNET_CRYPTO_rsa_key_free (privkey); - privkey = NULL; - - if (NULL != arm) - stop_arm(); - + if (NULL != nsqe) + { + GNUNET_NAMESTORE_cancel (nsqe); + nsqe = NULL; + } + cleanup (); res = 1; } @@ -98,141 +89,97 @@ endbadly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) static void end (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { + cleanup (); + res = 0; +} + + +static void +name_lookup_proc (void *cls, + const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *zone_key, + struct GNUNET_TIME_Absolute expire, + const char *name, + unsigned int rd_count, + const struct GNUNET_NAMESTORE_RecordData *rd, + const struct GNUNET_CRYPTO_RsaSignature *signature) +{ + nsqe = NULL; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Namestore lookup result %p `%s' %i %p %p\n", + zone_key, name, rd_count, rd, signature); if (endbadly_task != GNUNET_SCHEDULER_NO_TASK) { GNUNET_SCHEDULER_cancel (endbadly_task); endbadly_task = GNUNET_SCHEDULER_NO_TASK; } - - if (privkey != NULL) - GNUNET_CRYPTO_rsa_key_free (privkey); - privkey = NULL; - - if (nsh != NULL) - GNUNET_NAMESTORE_disconnect (nsh, GNUNET_YES); - nsh = NULL; - - - if (NULL != arm) - stop_arm(); - - res = 0; + GNUNET_SCHEDULER_add_now (&end, NULL); } -void name_lookup_proc (void *cls, - const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *zone_key, - struct GNUNET_TIME_Absolute expire, - const char *name, - unsigned int rd_count, - const struct GNUNET_NAMESTORE_RecordData *rd, - const struct GNUNET_CRYPTO_RsaSignature *signature) -{ - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Namestore lookup result %p `%s' %i %p %p\n", zone_key, name, rd_count, rd, signature); - res = 0; - GNUNET_SCHEDULER_add_now(&end, NULL); -} - -void put_cont (void *cls, int32_t success, const char *emsg) +static void +put_cont (void *cls, int32_t success, const char *emsg) { - char * name = cls; - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Name store added record for `%s': %s\n", name, (success == GNUNET_OK) ? "SUCCESS" : "FAIL"); - - GNUNET_NAMESTORE_lookup_record (nsh, &zone, name, 0, &name_lookup_proc, NULL); + const char *name = cls; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Name store added record for `%s': %s\n", + name, + (success == GNUNET_OK) ? "SUCCESS" : "FAIL"); + nsqe = GNUNET_NAMESTORE_lookup_record (nsh, &zone, name, 0, + &name_lookup_proc, NULL); } -void -delete_existing_db (const struct GNUNET_CONFIGURATION_Handle *cfg) -{ - char *afsdir; - - if (GNUNET_OK == - GNUNET_CONFIGURATION_get_value_filename (cfg, "namestore-sqlite", - "FILENAME", &afsdir)) - { - if (GNUNET_OK == GNUNET_DISK_file_test (afsdir)) - if (GNUNET_OK == GNUNET_DISK_file_test (afsdir)) - if (GNUNET_OK == GNUNET_DISK_directory_remove(afsdir)) - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Deleted existing database `%s' \n", afsdir); - GNUNET_free (afsdir); - } - -} static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) { - delete_existing_db(cfg); - endbadly_task = GNUNET_SCHEDULER_add_delayed(TIMEOUT,endbadly, NULL); - + struct GNUNET_CRYPTO_RsaSignature signature; + struct GNUNET_NAMESTORE_RecordData rd; char *hostkey_file; - GNUNET_asprintf(&hostkey_file,"zonefiles%s%s",DIR_SEPARATOR_STR, - "N0UJMP015AFUNR2BTNM3FKPBLG38913BL8IDMCO2H0A1LIB81960.zkey"); + const char * name = "dummy.dummy.gnunet"; + + endbadly_task = GNUNET_SCHEDULER_add_delayed (TIMEOUT, + &endbadly, NULL); + GNUNET_asprintf (&hostkey_file, + "zonefiles%s%s", + DIR_SEPARATOR_STR, + "N0UJMP015AFUNR2BTNM3FKPBLG38913BL8IDMCO2H0A1LIB81960.zkey"); GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Using zonekey file `%s' \n", hostkey_file); - privkey = GNUNET_CRYPTO_rsa_key_create_from_file(hostkey_file); + privkey = GNUNET_CRYPTO_rsa_key_create_from_file (hostkey_file); GNUNET_free (hostkey_file); GNUNET_assert (privkey != NULL); - GNUNET_CRYPTO_rsa_key_get_public(privkey, &pubkey); - + GNUNET_CRYPTO_rsa_key_get_public (privkey, &pubkey); GNUNET_CRYPTO_short_hash (&pubkey, sizeof (pubkey), &zone); - - - struct GNUNET_CRYPTO_RsaSignature signature; memset (&signature, '\0', sizeof (signature)); - struct GNUNET_NAMESTORE_RecordData rd; - - rd.expiration = GNUNET_TIME_absolute_get(); + rd.expiration_time = GNUNET_TIME_absolute_get().abs_value; rd.record_type = TEST_RECORD_TYPE; rd.data_size = TEST_RECORD_DATALEN; - rd.data = GNUNET_malloc(TEST_RECORD_DATALEN); + rd.data = GNUNET_malloc (TEST_RECORD_DATALEN); memset ((char *) rd.data, 'a', TEST_RECORD_DATALEN); - char * name = "dummy.dummy.gnunet"; - - start_arm (cfgfile); - GNUNET_assert (arm != NULL); - nsh = GNUNET_NAMESTORE_connect (cfg); GNUNET_break (NULL != nsh); - - GNUNET_NAMESTORE_record_put (nsh, &pubkey, name, - GNUNET_TIME_UNIT_FOREVER_ABS, - 1, &rd, &signature, put_cont, name); - + nsqe = GNUNET_NAMESTORE_record_put (nsh, &pubkey, name, + GNUNET_TIME_UNIT_FOREVER_ABS, + 1, &rd, &signature, &put_cont, (void*) name); GNUNET_free ((void *)rd.data); - } -static int -check () -{ - static char *const argv[] = { "test-namestore-api", - "-c", - "test_namestore_api.conf", -#if VERBOSE - "-L", "DEBUG", -#endif - NULL - }; - static struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - - res = 1; - GNUNET_PROGRAM_run ((sizeof (argv) / sizeof (char *)) - 1, argv, "test-namestore-api", - "nohelp", options, &run, &res); - return res; -} int main (int argc, char *argv[]) { - int ret; - - ret = check (); - - return ret; + res = 1; + if (0 != + GNUNET_TESTING_service_run ("test-namestore-api", + "namestore", + "test_namestore_api.conf", + &run, + NULL)) + return 1; + return res; } + /* end of test_namestore_api.c */ diff --git a/src/namestore/test_namestore_api.conf b/src/namestore/test_namestore_api.conf index 33e07a4..a685ab4 100644 --- a/src/namestore/test_namestore_api.conf +++ b/src/namestore/test_namestore_api.conf @@ -4,7 +4,7 @@ DEFAULTSERVICES = namestore UNIXPATH = /tmp/gnunet-p1-service-arm.sock [namestore] -#PREFIX = valgrind --leak-check=full --track-origins=yes +#PREFIX = valgrind AUTOSTART = YES UNIXPATH = /tmp/gnunet-service-namestore.sock UNIX_MATCH_UID = YES @@ -12,8 +12,7 @@ UNIX_MATCH_GID = YES PORT = 2099 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG -BINARY = gnunet-service-namestore +BINARY = gnunet-service-namestore2 ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; DATABASE = sqlite @@ -23,13 +22,6 @@ ZONEFILE_DIRECTORY = zonefiles FILENAME = $SERVICEHOME/namestore/sqlite_test.db [namestore-postgres] -CONFIG = connect_timeout=10; dbname=gnunet - -[namestore-mysql] -DATABASE = gnunet -CONFIG = ~/.my.cnf -# USER = gnunet -# PASSWORD = -# HOST = localhost -# PORT = 3306 +CONFIG = connect_timeout=10; dbname=gnunetcheck +TEMPORARY_TABLE = YES diff --git a/src/namestore/test_namestore_api_create.c b/src/namestore/test_namestore_api_create.c index 131c934..8bdf133 100644 --- a/src/namestore/test_namestore_api_create.c +++ b/src/namestore/test_namestore_api_create.c @@ -24,65 +24,50 @@ #include "platform.h" #include "gnunet_common.h" #include "gnunet_namestore_service.h" +#include "gnunet_testing_lib.h" #include "namestore.h" #include "gnunet_signatures.h" -#define VERBOSE GNUNET_NO #define RECORDS 1 + #define TEST_RECORD_TYPE 1234 + #define TEST_RECORD_DATALEN 123 + #define TEST_RECORD_DATA 'a' #define TEST_CREATE_RECORD_TYPE 4321 + #define TEST_CREATE_RECORD_DATALEN 255 + #define TEST_CREATE_RECORD_DATA 'b' -#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 10) +#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 100) + static struct GNUNET_NAMESTORE_Handle * nsh; static GNUNET_SCHEDULER_TaskIdentifier endbadly_task; -static struct GNUNET_OS_Process *arm; static struct GNUNET_CRYPTO_RsaPrivateKey * privkey; + static struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded pubkey; -struct GNUNET_CRYPTO_RsaSignature *s_signature; -struct GNUNET_CRYPTO_RsaSignature *s_signature_updated; + +static struct GNUNET_CRYPTO_RsaSignature *s_signature; + +static struct GNUNET_CRYPTO_RsaSignature *s_signature_updated; + static struct GNUNET_CRYPTO_ShortHashCode s_zone; -struct GNUNET_NAMESTORE_RecordData *s_first_record; -struct GNUNET_NAMESTORE_RecordData *s_second_record; -static char *s_name; +static struct GNUNET_NAMESTORE_RecordData *s_first_record; +static struct GNUNET_NAMESTORE_RecordData *s_second_record; -static int res; +static char *s_name; -static void -start_arm (const char *cfgname) -{ - arm = GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-arm", - "gnunet-service-arm", "-c", cfgname, -#if VERBOSE_PEERS - "-L", "DEBUG", -#else - "-L", "ERROR", -#endif - NULL); -} +static int res; -static void -stop_arm () -{ - if (NULL != arm) - { - if (0 != GNUNET_OS_process_kill (arm, SIGTERM)) - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); - GNUNET_OS_process_wait (arm); - GNUNET_OS_process_destroy (arm); - arm = NULL; - } -} /** * Re-establish the connection to the service. @@ -94,16 +79,12 @@ static void endbadly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { if (nsh != NULL) - GNUNET_NAMESTORE_disconnect (nsh, GNUNET_YES); + GNUNET_NAMESTORE_disconnect (nsh); nsh = NULL; - if (privkey != NULL) GNUNET_CRYPTO_rsa_key_free (privkey); privkey = NULL; - - if (NULL != arm) - stop_arm(); - + GNUNET_free_non_null (s_name); res = 1; } @@ -116,30 +97,27 @@ end (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) GNUNET_SCHEDULER_cancel (endbadly_task); endbadly_task = GNUNET_SCHEDULER_NO_TASK; } - GNUNET_free ((void *) s_first_record->data); GNUNET_free (s_first_record); GNUNET_free_non_null (s_second_record); - + GNUNET_free_non_null (s_name); if (privkey != NULL) GNUNET_CRYPTO_rsa_key_free (privkey); privkey = NULL; - if (nsh != NULL) - GNUNET_NAMESTORE_disconnect (nsh, GNUNET_YES); + GNUNET_NAMESTORE_disconnect (nsh); nsh = NULL; - - if (NULL != arm) - stop_arm(); } -void name_lookup_second_proc (void *cls, - const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *zone_key, - struct GNUNET_TIME_Absolute expire, - const char *n, - unsigned int rd_count, - const struct GNUNET_NAMESTORE_RecordData *rd, - const struct GNUNET_CRYPTO_RsaSignature *signature) + +static void +name_lookup_second_proc (void *cls, + const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *zone_key, + struct GNUNET_TIME_Absolute expire, + const char *n, + unsigned int rd_count, + const struct GNUNET_NAMESTORE_RecordData *rd, + const struct GNUNET_CRYPTO_RsaSignature *signature) { static int found = GNUNET_NO; int failed = GNUNET_NO; @@ -176,14 +154,13 @@ void name_lookup_second_proc (void *cls, } } - if (GNUNET_OK != GNUNET_NAMESTORE_verify_signature(zone_key, expire, n, rd_count, rd, signature)) + if (GNUNET_OK != GNUNET_NAMESTORE_verify_signature (zone_key, expire, n, rd_count, rd, signature)) { GNUNET_break (0); failed = GNUNET_YES; } - - if (GNUNET_OK != GNUNET_NAMESTORE_verify_signature(&pubkey, expire, n, rd_count, rd, signature)) + if (GNUNET_OK != GNUNET_NAMESTORE_verify_signature (&pubkey, expire, n, rd_count, rd, signature)) { GNUNET_break (0); failed = GNUNET_YES; @@ -192,7 +169,8 @@ void name_lookup_second_proc (void *cls, struct GNUNET_NAMESTORE_RecordData rd_new[2]; rd_new[0] = *s_first_record; rd_new[1] = *s_second_record; - s_signature_updated = GNUNET_NAMESTORE_create_signature(privkey, expire, s_name, rd_new, 2); + rd_new[1].flags = 0; /* unset GNUNET_NAMESTORE_RF_AUTHORITY */ + s_signature_updated = GNUNET_NAMESTORE_create_signature (privkey, expire, s_name, rd_new, 2); if (0 != memcmp (s_signature_updated, signature, sizeof (struct GNUNET_CRYPTO_RsaSignature))) { @@ -219,10 +197,11 @@ void name_lookup_second_proc (void *cls, } -void +static void create_second_cont (void *cls, int32_t success, const char *emsg) { char *name = cls; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Create second record for `%s': %s\n", name, (success == GNUNET_OK) ? "SUCCESS" : "FAIL"); if (success == GNUNET_OK) { @@ -235,16 +214,17 @@ create_second_cont (void *cls, int32_t success, const char *emsg) GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Failed to put records for name `%s'\n", name); GNUNET_SCHEDULER_add_now(&end, NULL); } - } -void name_lookup_initial_proc (void *cls, - const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *zone_key, - struct GNUNET_TIME_Absolute expire, - const char *n, - unsigned int rd_count, - const struct GNUNET_NAMESTORE_RecordData *rd, - const struct GNUNET_CRYPTO_RsaSignature *signature) + +static void +name_lookup_initial_proc (void *cls, + const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *zone_key, + struct GNUNET_TIME_Absolute expire, + const char *n, + unsigned int rd_count, + const struct GNUNET_NAMESTORE_RecordData *rd, + const struct GNUNET_CRYPTO_RsaSignature *signature) { char * name = cls; static int found = GNUNET_NO; @@ -281,7 +261,7 @@ void name_lookup_initial_proc (void *cls, } } - if (GNUNET_OK != GNUNET_NAMESTORE_verify_signature(&pubkey, expire,n, rd_count, rd, signature)) + if (GNUNET_OK != GNUNET_NAMESTORE_verify_signature (&pubkey, expire, n, rd_count, rd, signature)) { GNUNET_break (0); failed = GNUNET_YES; @@ -301,7 +281,7 @@ void name_lookup_initial_proc (void *cls, /* create a second record */ s_second_record = GNUNET_malloc(sizeof (struct GNUNET_NAMESTORE_RecordData) + TEST_CREATE_RECORD_DATALEN); - s_second_record->expiration = GNUNET_TIME_UNIT_FOREVER_ABS; + s_second_record->expiration_time = UINT64_MAX; s_second_record->record_type = TEST_CREATE_RECORD_TYPE; s_second_record->flags = GNUNET_NAMESTORE_RF_AUTHORITY; s_second_record->data = &s_second_record[1]; @@ -323,7 +303,8 @@ void name_lookup_initial_proc (void *cls, } } -void + +static void create_first_cont (void *cls, int32_t success, const char *emsg) { char *name = cls; @@ -340,74 +321,39 @@ create_first_cont (void *cls, int32_t success, const char *emsg) GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Failed to put records for name `%s'\n", name); GNUNET_SCHEDULER_add_now(&end, NULL); } - } -void -put_cont (void *cls, int32_t success, const char *emsg) -{ - char *name = cls; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Name store added record for `%s': %s\n", name, (success == GNUNET_OK) ? "SUCCESS" : "FAIL"); - if (success == GNUNET_OK) - { - - } - else - { - res = 1; - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Failed to put records for name `%s'\n", name); - GNUNET_SCHEDULER_add_now(&end, NULL); - } -} static struct GNUNET_NAMESTORE_RecordData * -create_record (int count) +create_record (unsigned int count) { - int c; + unsigned int c; struct GNUNET_NAMESTORE_RecordData * rd; - rd = GNUNET_malloc (count * sizeof (struct GNUNET_NAMESTORE_RecordData)); + rd = GNUNET_malloc (count * sizeof (struct GNUNET_NAMESTORE_RecordData)); for (c = 0; c < count; c++) { - rd[c].expiration = GNUNET_TIME_absolute_get(); - rd[c].record_type = TEST_RECORD_TYPE; - rd[c].data_size = TEST_RECORD_DATALEN; - rd[c].data = GNUNET_malloc(TEST_RECORD_DATALEN); - memset ((char *) rd[c].data, TEST_RECORD_DATA, TEST_RECORD_DATALEN); + rd[c].expiration_time = GNUNET_TIME_relative_to_absolute (GNUNET_TIME_UNIT_HOURS).abs_value; + rd[c].record_type = TEST_RECORD_TYPE; + rd[c].data_size = TEST_RECORD_DATALEN; + rd[c].data = GNUNET_malloc(TEST_RECORD_DATALEN); + memset ((char *) rd[c].data, TEST_RECORD_DATA, TEST_RECORD_DATALEN); } - return rd; } -void -delete_existing_db (const struct GNUNET_CONFIGURATION_Handle *cfg) -{ - char *afsdir; - - if (GNUNET_OK == - GNUNET_CONFIGURATION_get_value_filename (cfg, "namestore-sqlite", - "FILENAME", &afsdir)) - { - if (GNUNET_OK == GNUNET_DISK_file_test (afsdir)) - if (GNUNET_OK == GNUNET_DISK_file_test (afsdir)) - if (GNUNET_OK == GNUNET_DISK_directory_remove(afsdir)) - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Deleted existing database `%s' \n", afsdir); - GNUNET_free (afsdir); - } - -} static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) { - delete_existing_db(cfg); - - endbadly_task = GNUNET_SCHEDULER_add_delayed(TIMEOUT,endbadly, NULL); size_t rd_ser_len; + char *hostkey_file; + struct GNUNET_TIME_Absolute et; + endbadly_task = GNUNET_SCHEDULER_add_delayed (TIMEOUT,endbadly, NULL); /* load privat key */ - char *hostkey_file; GNUNET_asprintf(&hostkey_file,"zonefiles%s%s",DIR_SEPARATOR_STR, "N0UJMP015AFUNR2BTNM3FKPBLG38913BL8IDMCO2H0A1LIB81960.zkey"); GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Using zonekey file `%s' \n", hostkey_file); @@ -417,23 +363,19 @@ run (void *cls, char *const *args, const char *cfgfile, GNUNET_CRYPTO_rsa_key_get_public(privkey, &pubkey); /* create record */ - s_name = "dummy.dummy.gnunet"; + s_name = GNUNET_NAMESTORE_normalize_string ("DUMMY.dummy.gnunet"); s_first_record = create_record (1); rd_ser_len = GNUNET_NAMESTORE_records_get_size(1, s_first_record); char rd_ser[rd_ser_len]; GNUNET_NAMESTORE_records_serialize(1, s_first_record, rd_ser_len, rd_ser); - - s_signature = GNUNET_NAMESTORE_create_signature(privkey, s_first_record->expiration, s_name, s_first_record, 1); + et.abs_value = s_first_record->expiration_time; + s_signature = GNUNET_NAMESTORE_create_signature(privkey, et, s_name, s_first_record, 1); /* create random zone hash */ GNUNET_CRYPTO_short_hash (&pubkey, sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded), &s_zone); GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Name: `%s' Zone: `%s' \n", s_name, GNUNET_short_h2s (&s_zone)); - - start_arm (cfgfile); - GNUNET_assert (arm != NULL); - nsh = GNUNET_NAMESTORE_connect (cfg); GNUNET_break (NULL != nsh); @@ -444,35 +386,20 @@ run (void *cls, char *const *args, const char *cfgfile, GNUNET_NAMESTORE_record_create (nsh, privkey, s_name, s_first_record, &create_first_cont, s_name); } -static int -check () -{ - static char *const argv[] = { "test-namestore-api", - "-c", - "test_namestore_api.conf", -#if VERBOSE - "-L", "DEBUG", -#endif - NULL - }; - static struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - - res = 1; - GNUNET_PROGRAM_run ((sizeof (argv) / sizeof (char *)) - 1, argv, "test-namestore-api", - "nohelp", options, &run, &res); - return res; -} int main (int argc, char *argv[]) { - int ret; - - ret = check (); + res = 1; + if (0 != + GNUNET_TESTING_service_run ("test-namestore-api-create", + "namestore", + "test_namestore_api.conf", + &run, + NULL)) + return 1; GNUNET_free (s_signature); - return ret; + return res; } -/* end of test_namestore_api.c */ +/* end of test_namestore_api_create.c */ diff --git a/src/namestore/test_namestore_api_create_update.c b/src/namestore/test_namestore_api_create_update.c index 93570e4..2a5c45e 100644 --- a/src/namestore/test_namestore_api_create_update.c +++ b/src/namestore/test_namestore_api_create_update.c @@ -24,65 +24,48 @@ #include "platform.h" #include "gnunet_common.h" #include "gnunet_namestore_service.h" +#include "gnunet_testing_lib.h" #include "namestore.h" #include "gnunet_signatures.h" -#define VERBOSE GNUNET_NO #define RECORDS 1 + #define TEST_RECORD_TYPE 1234 + #define TEST_RECORD_DATALEN 123 + #define TEST_RECORD_DATA 'a' #define TEST_CREATE_RECORD_TYPE 4321 + #define TEST_CREATE_RECORD_DATALEN 255 + #define TEST_CREATE_RECORD_DATA 'b' -#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 10) +#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 100) + static struct GNUNET_NAMESTORE_Handle * nsh; static GNUNET_SCHEDULER_TaskIdentifier endbadly_task; -static struct GNUNET_OS_Process *arm; static struct GNUNET_CRYPTO_RsaPrivateKey * privkey; + static struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded pubkey; -struct GNUNET_CRYPTO_RsaSignature *s_signature; -struct GNUNET_CRYPTO_RsaSignature *s_signature_updated; + +static struct GNUNET_CRYPTO_RsaSignature *s_signature; + static struct GNUNET_CRYPTO_ShortHashCode s_zone; -struct GNUNET_NAMESTORE_RecordData *s_first_record; -struct GNUNET_NAMESTORE_RecordData *s_second_record; -static char *s_name; +static struct GNUNET_NAMESTORE_RecordData *s_first_record; +static struct GNUNET_NAMESTORE_RecordData *s_second_record; -static int res; +static char *s_name; -static void -start_arm (const char *cfgname) -{ - arm = GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-arm", - "gnunet-service-arm", "-c", cfgname, -#if VERBOSE_PEERS - "-L", "DEBUG", -#else - "-L", "ERROR", -#endif - NULL); -} +static int res; -static void -stop_arm () -{ - if (NULL != arm) - { - if (0 != GNUNET_OS_process_kill (arm, SIGTERM)) - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); - GNUNET_OS_process_wait (arm); - GNUNET_OS_process_destroy (arm); - arm = NULL; - } -} /** * Re-establish the connection to the service. @@ -94,16 +77,12 @@ static void endbadly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { if (nsh != NULL) - GNUNET_NAMESTORE_disconnect (nsh, GNUNET_YES); + GNUNET_NAMESTORE_disconnect (nsh); nsh = NULL; - if (privkey != NULL) GNUNET_CRYPTO_rsa_key_free (privkey); privkey = NULL; - - if (NULL != arm) - stop_arm(); - + GNUNET_free_non_null (s_name); res = 1; } @@ -116,208 +95,20 @@ end (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) GNUNET_SCHEDULER_cancel (endbadly_task); endbadly_task = GNUNET_SCHEDULER_NO_TASK; } - GNUNET_free ((void *) s_first_record->data); GNUNET_free (s_first_record); GNUNET_free_non_null (s_second_record); - if (privkey != NULL) GNUNET_CRYPTO_rsa_key_free (privkey); privkey = NULL; - if (nsh != NULL) - GNUNET_NAMESTORE_disconnect (nsh, GNUNET_YES); + GNUNET_NAMESTORE_disconnect (nsh); nsh = NULL; - - if (NULL != arm) - stop_arm(); -} - -void name_lookup_second_proc (void *cls, - const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *zone_key, - struct GNUNET_TIME_Absolute expire, - const char *n, - unsigned int rd_count, - const struct GNUNET_NAMESTORE_RecordData *rd, - const struct GNUNET_CRYPTO_RsaSignature *signature) -{ - static int found = GNUNET_NO; - int failed = GNUNET_NO; - int c; - - if (n != NULL) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Checking returned results\n"); - if (0 != memcmp (zone_key, &pubkey, sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded))) - { - GNUNET_break (0); - failed = GNUNET_YES; - } - - if (0 != strcmp(n, s_name)) - { - GNUNET_break (0); - failed = GNUNET_YES; - } - - if (2 != rd_count) - { - GNUNET_break (0); - failed = GNUNET_YES; - } - - for (c = 0; c < rd_count; c++) - { - if ((GNUNET_NO == GNUNET_NAMESTORE_records_cmp(&rd[c], s_first_record)) && - (GNUNET_NO == GNUNET_NAMESTORE_records_cmp(&rd[c], s_second_record))) - { - GNUNET_break (0); - failed = GNUNET_YES; - } - } - - if (GNUNET_OK != GNUNET_NAMESTORE_verify_signature(&pubkey, expire, n, rd_count, rd, signature)) - { - GNUNET_break (0); - failed = GNUNET_YES; - } - - struct GNUNET_NAMESTORE_RecordData rd_new[2]; - rd_new[0] = *s_first_record; - rd_new[1] = *s_second_record; - s_signature_updated = GNUNET_NAMESTORE_create_signature(privkey, expire, s_name, rd_new, 2); - - if (0 != memcmp (s_signature_updated, signature, sizeof (struct GNUNET_CRYPTO_RsaSignature))) - { - GNUNET_break (0); - failed = GNUNET_YES; - } - - found = GNUNET_YES; - if (failed == GNUNET_NO) - res = 0; - else - res = 1; - } - else - { - if (found != GNUNET_YES) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Failed to lookup records for name `%s'\n", s_name); - res = 1; - } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Lookup done for name %s'\n", s_name); - } - GNUNET_SCHEDULER_add_now(&end, NULL); -} - - -void -create_second_cont (void *cls, int32_t success, const char *emsg) -{ - char *name = cls; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Create second record for `%s': %s\n", name, (success == GNUNET_OK) ? "SUCCESS" : "FAIL"); - if (success == GNUNET_OK) - { - res = 0; - GNUNET_NAMESTORE_lookup_record (nsh, &s_zone, name, 0, &name_lookup_second_proc, name); - } - else - { - res = 1; - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Failed to put records for name `%s'\n", name); - GNUNET_SCHEDULER_add_now(&end, NULL); - } - -} - -void name_lookup_initial_proc (void *cls, - const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *zone_key, - struct GNUNET_TIME_Absolute expire, - const char *n, - unsigned int rd_count, - const struct GNUNET_NAMESTORE_RecordData *rd, - const struct GNUNET_CRYPTO_RsaSignature *signature) -{ - char * name = cls; - static int found = GNUNET_NO; - int failed = GNUNET_NO; - int c; - - if (n != NULL) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Checking returned results\n"); - if (0 != memcmp (zone_key, &pubkey, sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded))) - { - GNUNET_break (0); - failed = GNUNET_YES; - } - - if (0 != strcmp(n, s_name)) - { - GNUNET_break (0); - failed = GNUNET_YES; - } - - if (RECORDS != rd_count) - { - GNUNET_break (0); - failed = GNUNET_YES; - } - - for (c = 0; c < RECORDS; c++) - { - if (GNUNET_NO == GNUNET_NAMESTORE_records_cmp(&rd[c], &s_first_record[c])) - { - GNUNET_break (0); - failed = GNUNET_YES; - } - } - - if (GNUNET_OK != GNUNET_NAMESTORE_verify_signature(&pubkey, expire, n, rd_count, rd, signature)) - { - GNUNET_break (0); - failed = GNUNET_YES; - } - - if (0 != memcmp (s_signature, signature, sizeof (struct GNUNET_CRYPTO_RsaSignature))) - { - GNUNET_break (0); - failed = GNUNET_YES; - } - - found = GNUNET_YES; - if (failed == GNUNET_NO) - res = 0; - else - res = 1; - - /* create a second record */ - s_second_record = GNUNET_malloc(sizeof (struct GNUNET_NAMESTORE_RecordData) + TEST_CREATE_RECORD_DATALEN); - s_second_record->expiration = GNUNET_TIME_UNIT_FOREVER_ABS; - s_second_record->record_type = TEST_CREATE_RECORD_TYPE; - s_second_record->flags = GNUNET_NAMESTORE_RF_AUTHORITY; - s_second_record->data = &s_second_record[1]; - s_second_record->data_size = TEST_CREATE_RECORD_DATALEN; - memset ((char *) s_second_record->data, TEST_CREATE_RECORD_DATA, TEST_CREATE_RECORD_DATALEN); - - GNUNET_NAMESTORE_record_create (nsh, privkey, name, s_second_record, &create_second_cont, name); - - } - else - { - if (found != GNUNET_YES) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Failed to lookup records for name `%s'\n", s_name); - res = 1; - } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Lookup done for name %s'\n", s_name); - GNUNET_SCHEDULER_add_now (&end, NULL); - } + GNUNET_free_non_null (s_name); } -void +static void create_updated_cont (void *cls, int32_t success, const char *emsg) { char *name = cls; @@ -340,7 +131,8 @@ create_updated_cont (void *cls, int32_t success, const char *emsg) GNUNET_SCHEDULER_add_now(&end, NULL); } -void + +static void create_identical_cont (void *cls, int32_t success, const char *emsg) { char *name = cls; @@ -348,7 +140,7 @@ create_identical_cont (void *cls, int32_t success, const char *emsg) if (success == GNUNET_NO) { res = 0; - s_first_record->expiration = GNUNET_TIME_absolute_get (); + s_first_record->expiration_time = GNUNET_TIME_absolute_get ().abs_value; GNUNET_NAMESTORE_record_create (nsh, privkey, s_name, s_first_record, &create_updated_cont, s_name); } else @@ -360,7 +152,8 @@ create_identical_cont (void *cls, int32_t success, const char *emsg) } -void + +static void create_first_cont (void *cls, int32_t success, const char *emsg) { char *name = cls; @@ -380,99 +173,62 @@ create_first_cont (void *cls, int32_t success, const char *emsg) } -void -put_cont (void *cls, int32_t success, const char *emsg) -{ - char *name = cls; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Name store added record for `%s': %s `%s'\n", name, (success == GNUNET_OK) ? "SUCCESS" : "FAIL", emsg); - if (success == GNUNET_OK) - { - - } - else - { - res = 1; - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Failed to put records for name `%s'\n", name); - GNUNET_SCHEDULER_add_now(&end, NULL); - } -} static struct GNUNET_NAMESTORE_RecordData * -create_record (int count) +create_record (unsigned int count) { - int c; + unsigned int c; struct GNUNET_NAMESTORE_RecordData * rd; - rd = GNUNET_malloc (count * sizeof (struct GNUNET_NAMESTORE_RecordData)); + rd = GNUNET_malloc (count * sizeof (struct GNUNET_NAMESTORE_RecordData)); for (c = 0; c < count; c++) { - rd[c].expiration = GNUNET_TIME_UNIT_ZERO_ABS; + rd[c].expiration_time = 0; rd[c].record_type = TEST_RECORD_TYPE; rd[c].data_size = TEST_RECORD_DATALEN; rd[c].data = GNUNET_malloc(TEST_RECORD_DATALEN); memset ((char *) rd[c].data, TEST_RECORD_DATA, TEST_RECORD_DATALEN); } - return rd; } -void -delete_existing_db (const struct GNUNET_CONFIGURATION_Handle *cfg) -{ - char *afsdir; - - if (GNUNET_OK == - GNUNET_CONFIGURATION_get_value_filename (cfg, "namestore-sqlite", - "FILENAME", &afsdir)) - { - if (GNUNET_OK == GNUNET_DISK_file_test (afsdir)) - if (GNUNET_OK == GNUNET_DISK_file_test (afsdir)) - if (GNUNET_OK == GNUNET_DISK_directory_remove(afsdir)) - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Deleted existing database `%s' \n", afsdir); - GNUNET_free (afsdir); - } - -} static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) { - delete_existing_db(cfg); + size_t rd_ser_len; + char *hostkey_file; + struct GNUNET_TIME_Absolute et; endbadly_task = GNUNET_SCHEDULER_add_delayed(TIMEOUT,endbadly, NULL); - size_t rd_ser_len; /* load privat key */ - char *hostkey_file; GNUNET_asprintf(&hostkey_file,"zonefiles%s%s",DIR_SEPARATOR_STR, "N0UJMP015AFUNR2BTNM3FKPBLG38913BL8IDMCO2H0A1LIB81960.zkey"); GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Using zonekey file `%s' \n", hostkey_file); privkey = GNUNET_CRYPTO_rsa_key_create_from_file(hostkey_file); GNUNET_free (hostkey_file); - GNUNET_assert (privkey != NULL); /* get public key */ GNUNET_CRYPTO_rsa_key_get_public(privkey, &pubkey); /* create record */ - s_name = "dummy.dummy.gnunet"; + s_name = GNUNET_NAMESTORE_normalize_string ("DUMMY.dummy.gnunet"); s_first_record = create_record (1); rd_ser_len = GNUNET_NAMESTORE_records_get_size(1, s_first_record); char rd_ser[rd_ser_len]; GNUNET_NAMESTORE_records_serialize(1, s_first_record, rd_ser_len, rd_ser); - s_signature = GNUNET_NAMESTORE_create_signature(privkey, s_first_record->expiration, s_name, s_first_record, 1); + et.abs_value = s_first_record->expiration_time; + s_signature = GNUNET_NAMESTORE_create_signature(privkey, et, s_name, s_first_record, 1); /* create random zone hash */ GNUNET_CRYPTO_short_hash (&pubkey, sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded), &s_zone); GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Name: `%s' Zone: `%s' \n", s_name, GNUNET_short_h2s (&s_zone)); - - start_arm (cfgfile); - GNUNET_assert (arm != NULL); - nsh = GNUNET_NAMESTORE_connect (cfg); GNUNET_break (NULL != nsh); @@ -483,35 +239,20 @@ run (void *cls, char *const *args, const char *cfgfile, GNUNET_NAMESTORE_record_create (nsh, privkey, s_name, s_first_record, &create_first_cont, s_name); } -static int -check () -{ - static char *const argv[] = { "test-namestore-api", - "-c", - "test_namestore_api.conf", -#if VERBOSE - "-L", "DEBUG", -#endif - NULL - }; - static struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - - res = 1; - GNUNET_PROGRAM_run ((sizeof (argv) / sizeof (char *)) - 1, argv, "test-namestore-api", - "nohelp", options, &run, &res); - return res; -} int main (int argc, char *argv[]) { - int ret; - - ret = check (); - GNUNET_free (s_signature); - return ret; + res = 1; + if (0 != + GNUNET_TESTING_service_run ("test-namestore-api-create-update", + "namestore", + "test_namestore_api.conf", + &run, + NULL)) + return 1; + GNUNET_free_non_null (s_signature); + return res; } -/* end of test_namestore_api.c */ +/* end of test_namestore_api_create_update.c */ diff --git a/src/namestore/test_namestore_api_lookup.c b/src/namestore/test_namestore_api_lookup.c index 818e710..7d2f86e 100644 --- a/src/namestore/test_namestore_api_lookup.c +++ b/src/namestore/test_namestore_api_lookup.c @@ -1,6 +1,6 @@ /* This file is part of GNUnet. - (C) 2009 Christian Grothoff (and other contributing authors) + (C) 2012 Christian Grothoff (and other contributing authors) GNUnet is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published @@ -18,66 +18,65 @@ Boston, MA 02111-1307, USA. */ /** - * @file namestore/test_namestore_api.c + * @file namestore/test_namestore_api_lookup.c * @brief testcase for namestore_api.c */ #include "platform.h" #include "gnunet_common.h" #include "gnunet_namestore_service.h" +#include "gnunet_testing_lib.h" #include "namestore.h" #include "gnunet_signatures.h" -#define VERBOSE GNUNET_NO - #define RECORDS 5 + #define TEST_RECORD_TYPE 1234 + #define TEST_RECORD_DATALEN 123 + #define TEST_RECORD_DATA 'a' -#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 10) +#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 100) + static struct GNUNET_NAMESTORE_Handle * nsh; static GNUNET_SCHEDULER_TaskIdentifier endbadly_task; -static struct GNUNET_OS_Process *arm; static struct GNUNET_CRYPTO_RsaPrivateKey * privkey; + static struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded pubkey; -struct GNUNET_CRYPTO_RsaSignature *s_signature; + +static struct GNUNET_CRYPTO_RsaSignature *s_signature; + static struct GNUNET_CRYPTO_ShortHashCode s_zone; -struct GNUNET_NAMESTORE_RecordData *s_rd; -static char *s_name; +static struct GNUNET_NAMESTORE_RecordData *s_rd; +static struct GNUNET_NAMESTORE_QueueEntry *nsqe; + +static char *s_name; static int res; -static void -start_arm (const char *cfgname) -{ - arm = GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-arm", - "gnunet-service-arm", "-c", cfgname, -#if VERBOSE_PEERS - "-L", "DEBUG", -#else - "-L", "ERROR", -#endif - NULL); -} static void -stop_arm () +cleanup () { - if (NULL != arm) + if (NULL != nsh) { - if (0 != GNUNET_OS_process_kill (arm, SIGTERM)) - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); - GNUNET_OS_process_wait (arm); - GNUNET_OS_process_destroy (arm); - arm = NULL; + GNUNET_NAMESTORE_disconnect (nsh); + nsh = NULL; } + if (NULL != privkey) + { + GNUNET_CRYPTO_rsa_key_free (privkey); + privkey = NULL; + } + GNUNET_SCHEDULER_shutdown (); } + /** * Re-establish the connection to the service. * @@ -87,17 +86,7 @@ stop_arm () static void endbadly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { - if (nsh != NULL) - GNUNET_NAMESTORE_disconnect (nsh, GNUNET_YES); - nsh = NULL; - - if (privkey != NULL) - GNUNET_CRYPTO_rsa_key_free (privkey); - privkey = NULL; - - if (NULL != arm) - stop_arm(); - + cleanup (); res = 1; } @@ -105,63 +94,49 @@ endbadly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) static void end (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { - if (endbadly_task != GNUNET_SCHEDULER_NO_TASK) - { - GNUNET_SCHEDULER_cancel (endbadly_task); - endbadly_task = GNUNET_SCHEDULER_NO_TASK; - } + unsigned int c; - int c; for (c = 0; c < RECORDS; c++) GNUNET_free_non_null((void *) s_rd[c].data); GNUNET_free (s_rd); - - if (privkey != NULL) - GNUNET_CRYPTO_rsa_key_free (privkey); - privkey = NULL; - - if (nsh != NULL) - GNUNET_NAMESTORE_disconnect (nsh, GNUNET_YES); - nsh = NULL; - - if (NULL != arm) - stop_arm(); + cleanup (); } -void name_lookup_proc (void *cls, - const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *zone_key, - struct GNUNET_TIME_Absolute expire, - const char *n, - unsigned int rd_count, - const struct GNUNET_NAMESTORE_RecordData *rd, - const struct GNUNET_CRYPTO_RsaSignature *signature) + +static void +name_lookup_proc (void *cls, + const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *zone_key, + struct GNUNET_TIME_Absolute expire, + const char *n, + unsigned int rd_count, + const struct GNUNET_NAMESTORE_RecordData *rd, + const struct GNUNET_CRYPTO_RsaSignature *signature) { static int found = GNUNET_NO; int c; - if (n != NULL) + if (NULL != n) { GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Checking returned results\n"); - if (0 != memcmp (zone_key, &pubkey, sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded))) + if (0 != memcmp (zone_key, &pubkey, + sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded))) { GNUNET_break (0); } - - if (0 != memcmp (signature, s_signature, sizeof (struct GNUNET_CRYPTO_RsaSignature))) + GNUNET_assert (NULL != signature); + if (0 != memcmp (signature, s_signature, + sizeof (struct GNUNET_CRYPTO_RsaSignature))) { GNUNET_break (0); } - - if (0 != strcmp(n, s_name)) + if (0 != strcmp (n, s_name)) { GNUNET_break (0); } - if (RECORDS != rd_count) { GNUNET_break (0); } - for (c = 0; c < RECORDS; c++) { if (GNUNET_NO == GNUNET_NAMESTORE_records_cmp (&rd[c], &s_rd[c])) @@ -174,144 +149,126 @@ void name_lookup_proc (void *cls, } else { - if (found != GNUNET_YES) + if (GNUNET_YES != found) { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Failed to lookup records for name `%s'\n", s_name); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Failed to lookup records for name `%s'\n", s_name); res = 1; } GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Lookup done for name %s'\n", s_name); } - GNUNET_SCHEDULER_add_now(&end, NULL); + if (GNUNET_SCHEDULER_NO_TASK != endbadly_task) + { + GNUNET_SCHEDULER_cancel (endbadly_task); + endbadly_task = GNUNET_SCHEDULER_NO_TASK; + } + GNUNET_SCHEDULER_add_now (&end, NULL); } -void + +static void put_cont (void *cls, int32_t success, const char *emsg) { char * name = cls; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Name store added record for `%s': %s\n", name, (success == GNUNET_OK) ? "SUCCESS" : "FAIL"); - if (success == GNUNET_OK) + nsqe = NULL; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Name store added record for `%s': %s\n", name, + (GNUNET_OK == success) ? "SUCCESS" : "FAIL"); + if (GNUNET_OK == success) { res = 0; - GNUNET_NAMESTORE_lookup_record (nsh, &s_zone, name, 0, &name_lookup_proc, NULL); + GNUNET_NAMESTORE_lookup_record (nsh, &s_zone, name, 0, + &name_lookup_proc, NULL); } else { res = 1; - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Failed to put records for name `%s'\n", name); - GNUNET_SCHEDULER_add_now(&end, NULL); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Failed to put records for name `%s'\n", name); + GNUNET_SCHEDULER_shutdown (); } } + static struct GNUNET_NAMESTORE_RecordData * -create_record (int count) +create_record (unsigned int count) { - int c; + unsigned int c; struct GNUNET_NAMESTORE_RecordData * rd; - rd = GNUNET_malloc (count * sizeof (struct GNUNET_NAMESTORE_RecordData)); - for (c = 0; c < RECORDS; c++) + rd = GNUNET_malloc (count * sizeof (struct GNUNET_NAMESTORE_RecordData)); + for (c = 0; c < count; c++) { - rd[c].expiration = GNUNET_TIME_absolute_get(); - rd[c].record_type = TEST_RECORD_TYPE; - rd[c].data_size = TEST_RECORD_DATALEN; - rd[c].data = GNUNET_malloc(TEST_RECORD_DATALEN); - memset ((char *) rd[c].data, TEST_RECORD_DATA, TEST_RECORD_DATALEN); + rd[c].expiration_time = GNUNET_TIME_relative_to_absolute (GNUNET_TIME_UNIT_HOURS).abs_value; + rd[c].record_type = TEST_RECORD_TYPE; + rd[c].data_size = TEST_RECORD_DATALEN; + rd[c].data = GNUNET_malloc(TEST_RECORD_DATALEN); + memset ((char *) rd[c].data, TEST_RECORD_DATA, TEST_RECORD_DATALEN); } - return rd; } -void -delete_existing_db (const struct GNUNET_CONFIGURATION_Handle *cfg) -{ - char *afsdir; - - if (GNUNET_OK == - GNUNET_CONFIGURATION_get_value_filename (cfg, "namestore-sqlite", - "FILENAME", &afsdir)) - { - if (GNUNET_OK == GNUNET_DISK_file_test (afsdir)) - if (GNUNET_OK == GNUNET_DISK_file_test (afsdir)) - if (GNUNET_OK == GNUNET_DISK_directory_remove(afsdir)) - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Deleted existing database `%s' \n", afsdir); - GNUNET_free (afsdir); - } - -} static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) { - delete_existing_db(cfg); - endbadly_task = GNUNET_SCHEDULER_add_delayed(TIMEOUT,endbadly, NULL); - size_t rd_ser_len; + struct GNUNET_TIME_Absolute et; + + endbadly_task = GNUNET_SCHEDULER_add_delayed (TIMEOUT, + &endbadly, NULL); /* load privat key from file not included in zonekey dir */ privkey = GNUNET_CRYPTO_rsa_key_create_from_file("test_hostkey"); - GNUNET_assert (privkey != NULL); + GNUNET_assert (NULL != privkey); /* get public key */ GNUNET_CRYPTO_rsa_key_get_public(privkey, &pubkey); /* create record */ - s_name = "dummy.dummy.gnunet"; + s_name = GNUNET_NAMESTORE_normalize_string ("DUMMY.dummy.gnunet"); s_rd = create_record (RECORDS); rd_ser_len = GNUNET_NAMESTORE_records_get_size(RECORDS, s_rd); - char rd_ser[rd_ser_len]; - GNUNET_NAMESTORE_records_serialize(RECORDS, s_rd, rd_ser_len, rd_ser); - - /* sign */ - s_signature = GNUNET_NAMESTORE_create_signature(privkey, s_rd[0].expiration, s_name, s_rd, RECORDS); - - /* create random zone hash */ - GNUNET_CRYPTO_short_hash (&pubkey, sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded), &s_zone); - start_arm (cfgfile); - GNUNET_assert (arm != NULL); - - nsh = GNUNET_NAMESTORE_connect (cfg); - GNUNET_break (NULL != nsh); - - GNUNET_break (s_rd != NULL); - GNUNET_break (s_name != NULL); - - GNUNET_NAMESTORE_record_put (nsh, &pubkey, s_name, - GNUNET_TIME_UNIT_FOREVER_ABS, - RECORDS, s_rd, s_signature, put_cont, s_name); + { + char rd_ser[rd_ser_len]; + GNUNET_NAMESTORE_records_serialize(RECORDS, s_rd, rd_ser_len, rd_ser); + + /* sign */ + et.abs_value = s_rd[0].expiration_time; + s_signature = GNUNET_NAMESTORE_create_signature (privkey, et, s_name, + s_rd, RECORDS); + + /* create random zone hash */ + GNUNET_CRYPTO_short_hash (&pubkey, + sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded), + &s_zone); + nsh = GNUNET_NAMESTORE_connect (cfg); + GNUNET_break (NULL != nsh); + nsqe = GNUNET_NAMESTORE_record_put (nsh, &pubkey, s_name, + GNUNET_TIME_UNIT_FOREVER_ABS, + RECORDS, s_rd, s_signature, + &put_cont, s_name); + } } -static int -check () +int +main (int argc, char *argv[]) { - static char *const argv[] = { "test-namestore-api", - "-c", - "test_namestore_api.conf", -#if VERBOSE - "-L", "DEBUG", -#endif - NULL - }; - static struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - res = 1; - GNUNET_PROGRAM_run ((sizeof (argv) / sizeof (char *)) - 1, argv, "test-namestore-api", - "nohelp", options, &run, &res); + if (0 != + GNUNET_TESTING_service_run ("test-namestore-api-lookup", + "namestore", + "test_namestore_api.conf", + &run, + NULL)) + return 1; + GNUNET_free_non_null (s_signature); return res; } -int -main (int argc, char *argv[]) -{ - int ret; - - ret = check (); - GNUNET_free (s_signature); - return ret; -} -/* end of test_namestore_api.c */ +/* end of test_namestore_api_lookup.c */ diff --git a/src/namestore/test_namestore_api_lookup_specific_type.c b/src/namestore/test_namestore_api_lookup_specific_type.c index 981e252..4d2aa1c 100644 --- a/src/namestore/test_namestore_api_lookup_specific_type.c +++ b/src/namestore/test_namestore_api_lookup_specific_type.c @@ -18,68 +18,50 @@ Boston, MA 02111-1307, USA. */ /** - * @file namestore/test_namestore_api.c + * @file namestore/test_namestore_api_lookup_sepecific_type.c * @brief testcase for namestore_api.c */ #include "platform.h" #include "gnunet_common.h" #include "gnunet_namestore_service.h" +#include "gnunet_testing_lib.h" #include "namestore.h" #include "gnunet_signatures.h" -#define VERBOSE GNUNET_NO #define RECORDS 5 + #define TEST_RECORD_TYPE 1234 + #define TEST_RECORD_DATALEN 123 + #define TEST_RECORD_DATA 'a' #define TEST_RECORD_LOOKUP_TYPE_NOT_EXISTING 11111 + #define TEST_RECORD_LOOKUP_TYPE_EXISTING 22222 -#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 10) +#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 100) + static struct GNUNET_NAMESTORE_Handle * nsh; static GNUNET_SCHEDULER_TaskIdentifier endbadly_task; -static struct GNUNET_OS_Process *arm; static struct GNUNET_CRYPTO_RsaPrivateKey * privkey; + static struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded pubkey; -struct GNUNET_CRYPTO_RsaSignature *s_signature; + +static struct GNUNET_CRYPTO_RsaSignature *s_signature; + static struct GNUNET_CRYPTO_ShortHashCode s_zone; -struct GNUNET_NAMESTORE_RecordData *s_rd; -static char *s_name; +static struct GNUNET_NAMESTORE_RecordData *s_rd; +static char *s_name; static int res; -static void -start_arm (const char *cfgname) -{ - arm = GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-arm", - "gnunet-service-arm", "-c", cfgname, -#if VERBOSE_PEERS - "-L", "DEBUG", -#else - "-L", "ERROR", -#endif - NULL); -} - -static void -stop_arm () -{ - if (NULL != arm) - { - if (0 != GNUNET_OS_process_kill (arm, SIGTERM)) - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); - GNUNET_OS_process_wait (arm); - GNUNET_OS_process_destroy (arm); - arm = NULL; - } -} /** * Re-establish the connection to the service. @@ -91,16 +73,12 @@ static void endbadly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { if (nsh != NULL) - GNUNET_NAMESTORE_disconnect (nsh, GNUNET_YES); + GNUNET_NAMESTORE_disconnect (nsh); nsh = NULL; - if (privkey != NULL) GNUNET_CRYPTO_rsa_key_free (privkey); privkey = NULL; - - if (NULL != arm) - stop_arm(); - + GNUNET_free_non_null (s_name); res = 1; } @@ -108,39 +86,36 @@ endbadly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) static void end (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { + int c; + if (endbadly_task != GNUNET_SCHEDULER_NO_TASK) { GNUNET_SCHEDULER_cancel (endbadly_task); endbadly_task = GNUNET_SCHEDULER_NO_TASK; } - - int c; for (c = 0; c < RECORDS; c++) { GNUNET_free_non_null((void *) s_rd[c].data); } GNUNET_free (s_rd); - + GNUNET_free_non_null (s_name); if (privkey != NULL) GNUNET_CRYPTO_rsa_key_free (privkey); privkey = NULL; - if (nsh != NULL) - GNUNET_NAMESTORE_disconnect (nsh, GNUNET_YES); + GNUNET_NAMESTORE_disconnect (nsh); nsh = NULL; - - if (NULL != arm) - stop_arm(); } -void name_lookup_existing_record_type (void *cls, - const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *zone_key, - struct GNUNET_TIME_Absolute expire, - const char *n, - unsigned int rd_count, - const struct GNUNET_NAMESTORE_RecordData *rd, - const struct GNUNET_CRYPTO_RsaSignature *signature) +static void +name_lookup_existing_record_type (void *cls, + const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *zone_key, + struct GNUNET_TIME_Absolute expire, + const char *n, + unsigned int rd_count, + const struct GNUNET_NAMESTORE_RecordData *rd, + const struct GNUNET_CRYPTO_RsaSignature *signature) { int failed = GNUNET_NO; @@ -166,12 +141,6 @@ void name_lookup_existing_record_type (void *cls, GNUNET_break(0); failed = GNUNET_YES; } - if (NULL != signature) - { - GNUNET_break(0); - failed = GNUNET_YES; - } - if (failed == GNUNET_YES) { GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Namestore returned invalid response\n"); @@ -181,18 +150,18 @@ void name_lookup_existing_record_type (void *cls, { res = 0; } - GNUNET_SCHEDULER_add_now(&end, NULL); } -void name_lookup_non_existing_record_type (void *cls, - const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *zone_key, - struct GNUNET_TIME_Absolute expire, - const char *n, - unsigned int rd_count, - const struct GNUNET_NAMESTORE_RecordData *rd, - const struct GNUNET_CRYPTO_RsaSignature *signature) +static void +name_lookup_non_existing_record_type (void *cls, + const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *zone_key, + struct GNUNET_TIME_Absolute expire, + const char *n, + unsigned int rd_count, + const struct GNUNET_NAMESTORE_RecordData *rd, + const struct GNUNET_CRYPTO_RsaSignature *signature) { int failed = GNUNET_NO; /* We expect zone key != NULL, name != NULL, rd_count 0, rd NULL, signature NULL */ @@ -250,7 +219,8 @@ void name_lookup_non_existing_record_type (void *cls, } } -void + +static void put_cont (void *cls, int32_t success, const char *emsg) { char * name = cls; @@ -270,61 +240,43 @@ put_cont (void *cls, int32_t success, const char *emsg) } } + static struct GNUNET_NAMESTORE_RecordData * -create_record (int count) +create_record (unsigned int count) { - int c; + unsigned int c; struct GNUNET_NAMESTORE_RecordData * rd; - rd = GNUNET_malloc (count * sizeof (struct GNUNET_NAMESTORE_RecordData)); - for (c = 0; c < RECORDS-1; c++) + rd = GNUNET_malloc (count * sizeof (struct GNUNET_NAMESTORE_RecordData)); + for (c = 0; c < count-1; c++) { - rd[c].expiration = GNUNET_TIME_UNIT_ZERO_ABS; + rd[c].expiration_time = GNUNET_TIME_relative_to_absolute (GNUNET_TIME_UNIT_HOURS).abs_value; rd[c].record_type = 1; rd[c].data_size = TEST_RECORD_DATALEN; rd[c].data = GNUNET_malloc(TEST_RECORD_DATALEN); memset ((char *) rd[c].data, TEST_RECORD_DATA, TEST_RECORD_DATALEN); } - - rd[c].expiration = GNUNET_TIME_absolute_get(); + rd[c].expiration_time = GNUNET_TIME_relative_to_absolute (GNUNET_TIME_UNIT_HOURS).abs_value; rd[c].record_type = TEST_RECORD_LOOKUP_TYPE_EXISTING; rd[c].data_size = TEST_RECORD_DATALEN; rd[c].data = GNUNET_malloc(TEST_RECORD_DATALEN); memset ((char *) rd[c].data, TEST_RECORD_DATA, TEST_RECORD_DATALEN); - return rd; } -void -delete_existing_db (const struct GNUNET_CONFIGURATION_Handle *cfg) -{ - char *afsdir; - - if (GNUNET_OK == - GNUNET_CONFIGURATION_get_value_filename (cfg, "namestore-sqlite", - "FILENAME", &afsdir)) - { - if (GNUNET_OK == GNUNET_DISK_file_test (afsdir)) - if (GNUNET_OK == GNUNET_DISK_file_test (afsdir)) - if (GNUNET_OK == GNUNET_DISK_directory_remove(afsdir)) - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Deleted existing database `%s' \n", afsdir); - GNUNET_free (afsdir); - } - -} static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) { - delete_existing_db(cfg); - endbadly_task = GNUNET_SCHEDULER_add_delayed(TIMEOUT,endbadly, NULL); - size_t rd_ser_len; + char *hostkey_file; + struct GNUNET_TIME_Absolute et; + endbadly_task = GNUNET_SCHEDULER_add_delayed(TIMEOUT,endbadly, NULL); /* load privat key */ - char *hostkey_file; GNUNET_asprintf(&hostkey_file,"zonefiles%s%s",DIR_SEPARATOR_STR, "N0UJMP015AFUNR2BTNM3FKPBLG38913BL8IDMCO2H0A1LIB81960.zkey"); GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Using zonekey file `%s' \n", hostkey_file); @@ -335,65 +287,44 @@ run (void *cls, char *const *args, const char *cfgfile, GNUNET_CRYPTO_rsa_key_get_public(privkey, &pubkey); /* create record */ - s_name = "dummy.dummy.gnunet"; + s_name = GNUNET_NAMESTORE_normalize_string ("DUMMY.dummy.gnunet"); s_rd = create_record (RECORDS); rd_ser_len = GNUNET_NAMESTORE_records_get_size(RECORDS, s_rd); - char rd_ser[rd_ser_len]; - GNUNET_NAMESTORE_records_serialize(RECORDS, s_rd, rd_ser_len, rd_ser); - - /* sign */ - s_signature = GNUNET_NAMESTORE_create_signature(privkey, s_rd[RECORDS -1].expiration, s_name, s_rd, RECORDS); - - /* create random zone hash */ - GNUNET_CRYPTO_short_hash (&pubkey, sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded), &s_zone); - - start_arm (cfgfile); - GNUNET_assert (arm != NULL); - - nsh = GNUNET_NAMESTORE_connect (cfg); - GNUNET_break (NULL != nsh); - - GNUNET_break (s_rd != NULL); - GNUNET_break (s_name != NULL); - - GNUNET_NAMESTORE_record_put (nsh, &pubkey, s_name, - GNUNET_TIME_UNIT_FOREVER_ABS, - RECORDS, s_rd, s_signature, put_cont, s_name); - - - + { + char rd_ser[rd_ser_len]; + GNUNET_NAMESTORE_records_serialize(RECORDS, s_rd, rd_ser_len, rd_ser); + + /* sign */ + et.abs_value = s_rd[RECORDS - 1].expiration_time; + s_signature = GNUNET_NAMESTORE_create_signature(privkey, et, s_name, s_rd, RECORDS); + + /* create random zone hash */ + GNUNET_CRYPTO_short_hash (&pubkey, sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded), &s_zone); + nsh = GNUNET_NAMESTORE_connect (cfg); + GNUNET_break (NULL != nsh); + GNUNET_break (s_rd != NULL); + GNUNET_break (s_name != NULL); + GNUNET_NAMESTORE_record_put (nsh, &pubkey, s_name, + GNUNET_TIME_UNIT_FOREVER_ABS, + RECORDS, s_rd, s_signature, put_cont, s_name); + } } -static int -check () -{ - static char *const argv[] = { "test-namestore-api", - "-c", - "test_namestore_api.conf", -#if VERBOSE - "-L", "DEBUG", -#endif - NULL - }; - static struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - - res = 1; - GNUNET_PROGRAM_run ((sizeof (argv) / sizeof (char *)) - 1, argv, "test-namestore-api", - "nohelp", options, &run, &res); - return res; -} int main (int argc, char *argv[]) { - int ret; - - ret = check (); - GNUNET_free (s_signature); - return ret; + res = 1; + if (0 != + GNUNET_TESTING_service_run ("test-namestore-api-lookup-specific-type", + "namestore", + "test_namestore_api.conf", + &run, + NULL)) + return 1; + GNUNET_free_non_null (s_signature); + return res; } -/* end of test_namestore_api.c */ +/* end of test_namestore_api_lookup_specific_type.c */ diff --git a/src/namestore/test_namestore_api_put.c b/src/namestore/test_namestore_api_put.c index 9315fd3..e4bc5e4 100644 --- a/src/namestore/test_namestore_api_put.c +++ b/src/namestore/test_namestore_api_put.c @@ -1,6 +1,6 @@ /* This file is part of GNUnet. - (C) 2009 Christian Grothoff (and other contributing authors) + (C) 2009, 2012 Christian Grothoff (and other contributing authors) GNUnet is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published @@ -24,54 +24,32 @@ #include "platform.h" #include "gnunet_common.h" #include "gnunet_namestore_service.h" +#include "gnunet_testing_lib.h" #include "namestore.h" -#define VERBOSE GNUNET_NO - #define RECORDS 5 + #define TEST_RECORD_TYPE 1234 + #define TEST_RECORD_DATALEN 123 + #define TEST_RECORD_DATA 'a' -#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 10) +#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 100) + static struct GNUNET_NAMESTORE_Handle * nsh; static GNUNET_SCHEDULER_TaskIdentifier endbadly_task; -static struct GNUNET_OS_Process *arm; static struct GNUNET_CRYPTO_RsaPrivateKey * privkey; + static struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded pubkey; -struct GNUNET_NAMESTORE_RecordData *s_rd; +static struct GNUNET_NAMESTORE_RecordData *s_rd; static int res; -static void -start_arm (const char *cfgname) -{ - arm = GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-arm", - "gnunet-service-arm", "-c", cfgname, -#if VERBOSE_PEERS - "-L", "DEBUG", -#else - "-L", "ERROR", -#endif - NULL); -} - -static void -stop_arm () -{ - if (NULL != arm) - { - if (0 != GNUNET_OS_process_kill (arm, SIGTERM)) - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); - GNUNET_OS_process_wait (arm); - GNUNET_OS_process_destroy (arm); - arm = NULL; - } -} /** * Re-establish the connection to the service. @@ -83,15 +61,15 @@ static void endbadly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { if (nsh != NULL) - GNUNET_NAMESTORE_disconnect (nsh, GNUNET_YES); + GNUNET_NAMESTORE_disconnect (nsh); nsh = NULL; if (privkey != NULL) + { GNUNET_CRYPTO_rsa_key_free (privkey); - privkey = NULL; - - if (NULL != arm) - stop_arm(); + privkey = NULL; + } + GNUNET_SCHEDULER_shutdown (); res = 1; } @@ -106,144 +84,105 @@ end (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) } if (privkey != NULL) + { GNUNET_CRYPTO_rsa_key_free (privkey); - privkey = NULL; - + privkey = NULL; + } if (nsh != NULL) - GNUNET_NAMESTORE_disconnect (nsh, GNUNET_YES); - nsh = NULL; - - if (NULL != arm) - stop_arm(); + { + GNUNET_NAMESTORE_disconnect (nsh); + nsh = NULL; + } } -void + +static void put_cont (void *cls, int32_t success, const char *emsg) { - char * name = cls; + const char * name = cls; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Name store added record for `%s': %s\n", name, (success == GNUNET_OK) ? "SUCCESS" : "FAIL"); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Name store added record for `%s': %s\n", + name, (success == GNUNET_OK) ? "SUCCESS" : "FAIL"); if (success == GNUNET_OK) res = 0; else res = 1; - - GNUNET_SCHEDULER_add_now(&end, NULL); + GNUNET_SCHEDULER_add_now (&end, NULL); } + static struct GNUNET_NAMESTORE_RecordData * -create_record (int count) +create_record (unsigned int count) { - int c; + unsigned int c; struct GNUNET_NAMESTORE_RecordData * rd; - rd = GNUNET_malloc (count * sizeof (struct GNUNET_NAMESTORE_RecordData)); - for (c = 0; c < RECORDS; c++) + rd = GNUNET_malloc (count * sizeof (struct GNUNET_NAMESTORE_RecordData)); + for (c = 0; c < count; c++) { - rd[c].expiration = GNUNET_TIME_absolute_get(); - rd[c].record_type = TEST_RECORD_TYPE; - rd[c].data_size = TEST_RECORD_DATALEN; - rd[c].data = GNUNET_malloc(TEST_RECORD_DATALEN); - memset ((char *) rd[c].data, TEST_RECORD_DATA, TEST_RECORD_DATALEN); + rd[c].expiration_time = GNUNET_TIME_absolute_get().abs_value; + rd[c].record_type = TEST_RECORD_TYPE; + rd[c].data_size = TEST_RECORD_DATALEN; + rd[c].data = GNUNET_malloc(TEST_RECORD_DATALEN); + memset ((char *) rd[c].data, TEST_RECORD_DATA, TEST_RECORD_DATALEN); } return rd; } -void -delete_existing_db (const struct GNUNET_CONFIGURATION_Handle *cfg) -{ - char *afsdir; - - if (GNUNET_OK == - GNUNET_CONFIGURATION_get_value_filename (cfg, "namestore-sqlite", - "FILENAME", &afsdir)) - { - if (GNUNET_OK == GNUNET_DISK_file_test (afsdir)) - if (GNUNET_OK == GNUNET_DISK_file_test (afsdir)) - if (GNUNET_OK == GNUNET_DISK_directory_remove(afsdir)) - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Deleted existing database `%s' \n", afsdir); - GNUNET_free (afsdir); - } -} static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) { - delete_existing_db(cfg); - endbadly_task = GNUNET_SCHEDULER_add_delayed(TIMEOUT,endbadly, NULL); + struct GNUNET_CRYPTO_RsaSignature *signature; + char * s_name; + int c; + char *hostkey_file; + struct GNUNET_TIME_Absolute et; + endbadly_task = GNUNET_SCHEDULER_add_delayed(TIMEOUT,endbadly, NULL); /* load privat key */ - char *hostkey_file; GNUNET_asprintf(&hostkey_file,"zonefiles%s%s",DIR_SEPARATOR_STR, "N0UJMP015AFUNR2BTNM3FKPBLG38913BL8IDMCO2H0A1LIB81960.zkey"); GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Using zonekey file `%s' \n", hostkey_file); privkey = GNUNET_CRYPTO_rsa_key_create_from_file(hostkey_file); - GNUNET_free (hostkey_file); - GNUNET_assert (privkey != NULL); + GNUNET_free (hostkey_file); /* get public key */ GNUNET_CRYPTO_rsa_key_get_public(privkey, &pubkey); - - struct GNUNET_CRYPTO_RsaSignature *signature; - - start_arm (cfgfile); - GNUNET_assert (arm != NULL); - nsh = GNUNET_NAMESTORE_connect (cfg); GNUNET_break (NULL != nsh); - /* create record */ - char * s_name = "dummy.dummy.gnunet"; + s_name = GNUNET_NAMESTORE_normalize_string ("DUMMY.dummy.gnunet"); s_rd = create_record (RECORDS); - - signature = GNUNET_NAMESTORE_create_signature(privkey, s_rd[0].expiration, s_name, s_rd, RECORDS); - + et.abs_value = s_rd[0].expiration_time; + signature = GNUNET_NAMESTORE_create_signature(privkey, et, s_name, s_rd, RECORDS); GNUNET_break (s_rd != NULL); GNUNET_break (s_name != NULL); - GNUNET_NAMESTORE_record_put (nsh, &pubkey, s_name, - GNUNET_TIME_UNIT_FOREVER_ABS, - RECORDS, s_rd, signature, put_cont, s_name); - + GNUNET_TIME_UNIT_FOREVER_ABS, + RECORDS, s_rd, signature, &put_cont, (void*) s_name); GNUNET_free (signature); - - int c; for (c = 0; c < RECORDS; c++) GNUNET_free_non_null((void *) s_rd[c].data); GNUNET_free (s_rd); - + GNUNET_free (s_name); } -static int -check () -{ - static char *const argv[] = { "test-namestore-api", - "-c", - "test_namestore_api.conf", -#if VERBOSE - "-L", "DEBUG", -#endif - NULL - }; - static struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - - res = 1; - GNUNET_PROGRAM_run ((sizeof (argv) / sizeof (char *)) - 1, argv, "test-namestore-api", - "nohelp", options, &run, &res); - return res; -} int main (int argc, char *argv[]) { - int ret; - - ret = check (); - - return ret; + res = 1; + if (0 != GNUNET_TESTING_service_run ("test-namestore-api-put", + "namestore", + "test_namestore_api.conf", + &run, + NULL)) + return 1; + return res; } -/* end of test_namestore_api.c */ +/* end of test_namestore_api_put.c */ diff --git a/src/namestore/test_namestore_api_remove.c b/src/namestore/test_namestore_api_remove.c index 57bb4a8..8583e69 100644 --- a/src/namestore/test_namestore_api_remove.c +++ b/src/namestore/test_namestore_api_remove.c @@ -24,63 +24,45 @@ #include "platform.h" #include "gnunet_common.h" #include "gnunet_namestore_service.h" +#include "gnunet_testing_lib.h" #include "namestore.h" #include "gnunet_signatures.h" -#define VERBOSE GNUNET_NO - #define RECORDS 5 + #define TEST_RECORD_TYPE 1234 + #define TEST_RECORD_DATALEN 123 + #define TEST_RECORD_DATA 'a' #define TEST_REMOVE_RECORD_TYPE 4321 + #define TEST_REMOVE_RECORD_DATALEN 255 + #define TEST_REMOVE_RECORD_DATA 'b' -#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 10) +#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 100) + static struct GNUNET_NAMESTORE_Handle * nsh; static GNUNET_SCHEDULER_TaskIdentifier endbadly_task; -static struct GNUNET_OS_Process *arm; static struct GNUNET_CRYPTO_RsaPrivateKey * privkey; + static struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded pubkey; -struct GNUNET_CRYPTO_RsaSignature *s_signature; + +static struct GNUNET_CRYPTO_RsaSignature *s_signature; + static struct GNUNET_CRYPTO_ShortHashCode s_zone; -struct GNUNET_NAMESTORE_RecordData *s_rd; -static char *s_name; +static struct GNUNET_NAMESTORE_RecordData *s_rd; +static char *s_name; static int res; -static void -start_arm (const char *cfgname) -{ - arm = GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-arm", - "gnunet-service-arm", "-c", cfgname, -#if VERBOSE_PEERS - "-L", "DEBUG", -#else - "-L", "ERROR", -#endif - NULL); -} - -static void -stop_arm () -{ - if (NULL != arm) - { - if (0 != GNUNET_OS_process_kill (arm, SIGTERM)) - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); - GNUNET_OS_process_wait (arm); - GNUNET_OS_process_destroy (arm); - arm = NULL; - } -} /** * Re-establish the connection to the service. @@ -92,16 +74,12 @@ static void endbadly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { if (nsh != NULL) - GNUNET_NAMESTORE_disconnect (nsh, GNUNET_YES); + GNUNET_NAMESTORE_disconnect (nsh); nsh = NULL; - if (privkey != NULL) GNUNET_CRYPTO_rsa_key_free (privkey); privkey = NULL; - - if (NULL != arm) - stop_arm(); - + GNUNET_free_non_null (s_name); res = 1; } @@ -109,36 +87,34 @@ endbadly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) static void end (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { + int c; + if (endbadly_task != GNUNET_SCHEDULER_NO_TASK) { GNUNET_SCHEDULER_cancel (endbadly_task); endbadly_task = GNUNET_SCHEDULER_NO_TASK; } - - int c; for (c = 0; c < RECORDS; c++) GNUNET_free_non_null((void *) s_rd[c].data); GNUNET_free (s_rd); - if (privkey != NULL) GNUNET_CRYPTO_rsa_key_free (privkey); privkey = NULL; - if (nsh != NULL) - GNUNET_NAMESTORE_disconnect (nsh, GNUNET_YES); + GNUNET_NAMESTORE_disconnect (nsh); nsh = NULL; - - if (NULL != arm) - stop_arm(); + GNUNET_free_non_null (s_name); } -void name_lookup_proc (void *cls, - const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *zone_key, - struct GNUNET_TIME_Absolute expire, - const char *n, - unsigned int rd_count, - const struct GNUNET_NAMESTORE_RecordData *rd, - const struct GNUNET_CRYPTO_RsaSignature *signature) + +static void +name_lookup_proc (void *cls, + const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *zone_key, + struct GNUNET_TIME_Absolute expire, + const char *n, + unsigned int rd_count, + const struct GNUNET_NAMESTORE_RecordData *rd, + const struct GNUNET_CRYPTO_RsaSignature *signature) { static int found = GNUNET_NO; int failed = GNUNET_NO; @@ -197,7 +173,8 @@ void name_lookup_proc (void *cls, GNUNET_SCHEDULER_add_now(&end, NULL); } -void + +static void remove_cont (void *cls, int32_t success, const char *emsg) { char *name = cls; @@ -216,7 +193,8 @@ remove_cont (void *cls, int32_t success, const char *emsg) } -void + +static void put_cont (void *cls, int32_t success, const char *emsg) { char *name = cls; @@ -236,22 +214,22 @@ put_cont (void *cls, int32_t success, const char *emsg) } } + static struct GNUNET_NAMESTORE_RecordData * -create_record (int count) +create_record (unsigned int count) { - int c; + unsigned int c; struct GNUNET_NAMESTORE_RecordData * rd; - rd = GNUNET_malloc (count * sizeof (struct GNUNET_NAMESTORE_RecordData)); - rd[0].expiration = GNUNET_TIME_absolute_get(); + rd = GNUNET_malloc (count * sizeof (struct GNUNET_NAMESTORE_RecordData)); + rd[0].expiration_time = GNUNET_TIME_relative_to_absolute (GNUNET_TIME_UNIT_HOURS).abs_value; rd[0].record_type = 0; rd[0].data_size = TEST_REMOVE_RECORD_DATALEN; rd[0].data = GNUNET_malloc(TEST_REMOVE_RECORD_DATALEN); memset ((char *) rd[0].data, TEST_RECORD_DATA, TEST_RECORD_DATALEN); - - for (c = 1; c < RECORDS; c++) + for (c = 1; c < count; c++) { - rd[c].expiration = GNUNET_TIME_UNIT_ZERO_ABS; + rd[c].expiration_time = GNUNET_TIME_relative_to_absolute (GNUNET_TIME_UNIT_HOURS).abs_value; rd[c].record_type = TEST_RECORD_TYPE; rd[c].data_size = TEST_RECORD_DATALEN; rd[c].data = GNUNET_malloc(TEST_RECORD_DATALEN); @@ -261,34 +239,18 @@ create_record (int count) return rd; } -void -delete_existing_db (const struct GNUNET_CONFIGURATION_Handle *cfg) -{ - char *afsdir; - - if (GNUNET_OK == - GNUNET_CONFIGURATION_get_value_filename (cfg, "namestore-sqlite", - "FILENAME", &afsdir)) - { - if (GNUNET_OK == GNUNET_DISK_file_test (afsdir)) - if (GNUNET_OK == GNUNET_DISK_file_test (afsdir)) - if (GNUNET_OK == GNUNET_DISK_directory_remove(afsdir)) - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Deleted existing database `%s' \n", afsdir); - GNUNET_free (afsdir); - } - -} static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) { - delete_existing_db(cfg); - endbadly_task = GNUNET_SCHEDULER_add_delayed(TIMEOUT,endbadly, NULL); size_t rd_ser_len; + char *hostkey_file; + struct GNUNET_TIME_Absolute et; + endbadly_task = GNUNET_SCHEDULER_add_delayed(TIMEOUT,endbadly, NULL); /* load privat key */ - char *hostkey_file; GNUNET_asprintf(&hostkey_file,"zonefiles%s%s",DIR_SEPARATOR_STR, "N0UJMP015AFUNR2BTNM3FKPBLG38913BL8IDMCO2H0A1LIB81960.zkey"); GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Using zonekey file `%s' \n", hostkey_file); @@ -299,7 +261,7 @@ run (void *cls, char *const *args, const char *cfgfile, GNUNET_CRYPTO_rsa_key_get_public(privkey, &pubkey); /* create record */ - s_name = "dummy.dummy.gnunet"; + s_name = GNUNET_NAMESTORE_normalize_string ("DUMMY.dummy.gnunet"); s_rd = create_record (RECORDS); rd_ser_len = GNUNET_NAMESTORE_records_get_size(RECORDS, s_rd); @@ -307,60 +269,36 @@ run (void *cls, char *const *args, const char *cfgfile, GNUNET_NAMESTORE_records_serialize(RECORDS, s_rd, rd_ser_len, rd_ser); /* sign */ - s_signature = GNUNET_NAMESTORE_create_signature(privkey, s_rd[0].expiration, s_name, s_rd, RECORDS); + et.abs_value = s_rd[0].expiration_time; + s_signature = GNUNET_NAMESTORE_create_signature(privkey, et, s_name, s_rd, RECORDS); /* create random zone hash */ GNUNET_CRYPTO_short_hash (&pubkey, sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded), &s_zone); GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Name: `%s' Zone: `%s' \n", s_name, GNUNET_short_h2s (&s_zone)); - - - start_arm (cfgfile); - GNUNET_assert (arm != NULL); - nsh = GNUNET_NAMESTORE_connect (cfg); GNUNET_break (NULL != nsh); - GNUNET_break (s_rd != NULL); GNUNET_break (s_name != NULL); - GNUNET_NAMESTORE_record_put (nsh, &pubkey, s_name, GNUNET_TIME_UNIT_FOREVER_ABS, RECORDS, s_rd, s_signature, put_cont, s_name); - - - } -static int -check () -{ - static char *const argv[] = { "test-namestore-api", - "-c", - "test_namestore_api.conf", -#if VERBOSE - "-L", "DEBUG", -#endif - NULL - }; - static struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - - res = 1; - GNUNET_PROGRAM_run ((sizeof (argv) / sizeof (char *)) - 1, argv, "test-namestore-api", - "nohelp", options, &run, &res); - return res; -} int main (int argc, char *argv[]) { - int ret; - - ret = check (); - GNUNET_free (s_signature); - return ret; + res = 1; + if (0 != + GNUNET_TESTING_service_run ("test-namestore-api-remove", + "namestore", + "test_namestore_api.conf", + &run, + NULL)) + return 1; + GNUNET_free_non_null (s_signature); + return res; } /* end of test_namestore_api.c */ diff --git a/src/namestore/test_namestore_api_remove_not_existing_record.c b/src/namestore/test_namestore_api_remove_not_existing_record.c index 8c32278..973cf94 100644 --- a/src/namestore/test_namestore_api_remove_not_existing_record.c +++ b/src/namestore/test_namestore_api_remove_not_existing_record.c @@ -18,69 +18,51 @@ Boston, MA 02111-1307, USA. */ /** - * @file namestore/test_namestore_api.c + * @file namestore/test_namestore_api_remove_not_existing_record.c * @brief testcase for namestore_api.c */ #include "platform.h" #include "gnunet_common.h" #include "gnunet_namestore_service.h" +#include "gnunet_testing_lib.h" #include "namestore.h" #include "gnunet_signatures.h" -#define VERBOSE GNUNET_NO - #define RECORDS 5 + #define TEST_RECORD_TYPE 1234 + #define TEST_RECORD_DATALEN 123 + #define TEST_RECORD_DATA 'a' #define TEST_REMOVE_RECORD_TYPE 4321 + #define TEST_REMOVE_RECORD_DATALEN 255 + #define TEST_REMOVE_RECORD_DATA 'b' -#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 10) +#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 100) + static struct GNUNET_NAMESTORE_Handle * nsh; static GNUNET_SCHEDULER_TaskIdentifier endbadly_task; -static struct GNUNET_OS_Process *arm; static struct GNUNET_CRYPTO_RsaPrivateKey * privkey; + static struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded pubkey; -struct GNUNET_CRYPTO_RsaSignature *s_signature; -static GNUNET_HashCode s_zone; -struct GNUNET_NAMESTORE_RecordData *s_rd; -static char *s_name; +static struct GNUNET_CRYPTO_RsaSignature *s_signature; +static struct GNUNET_HashCode s_zone; -static int res; +static struct GNUNET_NAMESTORE_RecordData *s_rd; -static void -start_arm (const char *cfgname) -{ - arm = GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-arm", - "gnunet-service-arm", "-c", cfgname, -#if VERBOSE_PEERS - "-L", "DEBUG", -#else - "-L", "ERROR", -#endif - NULL); -} +static char *s_name; + +static int res; -static void -stop_arm () -{ - if (NULL != arm) - { - if (0 != GNUNET_OS_process_kill (arm, SIGTERM)) - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); - GNUNET_OS_process_wait (arm); - GNUNET_OS_process_destroy (arm); - arm = NULL; - } -} /** * Re-establish the connection to the service. @@ -92,16 +74,12 @@ static void endbadly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { if (nsh != NULL) - GNUNET_NAMESTORE_disconnect (nsh, GNUNET_YES); + GNUNET_NAMESTORE_disconnect (nsh); nsh = NULL; - if (privkey != NULL) GNUNET_CRYPTO_rsa_key_free (privkey); privkey = NULL; - - if (NULL != arm) - stop_arm(); - + GNUNET_free_non_null (s_name); res = 1; } @@ -109,13 +87,13 @@ endbadly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) static void end (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { + int c; + if (endbadly_task != GNUNET_SCHEDULER_NO_TASK) { GNUNET_SCHEDULER_cancel (endbadly_task); endbadly_task = GNUNET_SCHEDULER_NO_TASK; } - - int c; for (c = 0; c < RECORDS; c++) GNUNET_free_non_null((void *) s_rd[c].data); GNUNET_free (s_rd); @@ -123,19 +101,18 @@ end (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) if (privkey != NULL) GNUNET_CRYPTO_rsa_key_free (privkey); privkey = NULL; - if (nsh != NULL) - GNUNET_NAMESTORE_disconnect (nsh, GNUNET_YES); + GNUNET_NAMESTORE_disconnect (nsh); nsh = NULL; - - if (NULL != arm) - stop_arm(); + GNUNET_free_non_null (s_name); } -void + +static void remove_cont (void *cls, int32_t success, const char *emsg) { char *name = cls; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Remove record for `%s': %s `%s'\n", name, (success == GNUNET_YES) ? "SUCCESS" : "FAIL", emsg); if (GNUNET_NO == success) { @@ -149,7 +126,8 @@ remove_cont (void *cls, int32_t success, const char *emsg) GNUNET_SCHEDULER_add_now(&end, NULL); } -void + +static void put_cont (void *cls, int32_t success, const char *emsg) { char *name = cls; @@ -161,7 +139,8 @@ put_cont (void *cls, int32_t success, const char *emsg) struct GNUNET_NAMESTORE_RecordData rd; char data[TEST_REMOVE_RECORD_DATALEN]; - rd.expiration = GNUNET_TIME_absolute_get(); + + rd.expiration_time = GNUNET_TIME_absolute_get().abs_value; rd.record_type = TEST_REMOVE_RECORD_TYPE; rd.data_size = TEST_REMOVE_RECORD_DATALEN; rd.data = &data; @@ -176,53 +155,38 @@ put_cont (void *cls, int32_t success, const char *emsg) } } + static struct GNUNET_NAMESTORE_RecordData * -create_record (int count) +create_record (unsigned int count) { - int c; + unsigned int c; struct GNUNET_NAMESTORE_RecordData * rd; - rd = GNUNET_malloc (count * sizeof (struct GNUNET_NAMESTORE_RecordData)); - for (c = 0; c < RECORDS; c++) + rd = GNUNET_malloc (count * sizeof (struct GNUNET_NAMESTORE_RecordData)); + for (c = 0; c < count; c++) { - rd[c].expiration = GNUNET_TIME_absolute_get(); - rd[c].record_type = TEST_RECORD_TYPE; - rd[c].data_size = TEST_RECORD_DATALEN; - rd[c].data = GNUNET_malloc(TEST_RECORD_DATALEN); - memset ((char *) rd[c].data, TEST_RECORD_DATA, TEST_RECORD_DATALEN); + rd[c].expiration_time = GNUNET_TIME_absolute_get().abs_value; + rd[c].record_type = TEST_RECORD_TYPE; + rd[c].data_size = TEST_RECORD_DATALEN; + rd[c].data = GNUNET_malloc(TEST_RECORD_DATALEN); + memset ((char *) rd[c].data, TEST_RECORD_DATA, TEST_RECORD_DATALEN); } - return rd; } -void -delete_existing_db (const struct GNUNET_CONFIGURATION_Handle *cfg) -{ - char *afsdir; - - if (GNUNET_OK == - GNUNET_CONFIGURATION_get_value_filename (cfg, "namestore-sqlite", - "FILENAME", &afsdir)) - { - if (GNUNET_OK == GNUNET_DISK_file_test (afsdir)) - if (GNUNET_OK == GNUNET_DISK_file_test (afsdir)) - if (GNUNET_OK == GNUNET_DISK_directory_remove(afsdir)) - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Deleted existing database `%s' \n", afsdir); - GNUNET_free (afsdir); - } - -} static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) { - delete_existing_db(cfg); - endbadly_task = GNUNET_SCHEDULER_add_delayed(TIMEOUT,endbadly, NULL); + char *hostkey_file; size_t rd_ser_len; + struct GNUNET_TIME_Absolute et; + + endbadly_task = GNUNET_SCHEDULER_add_delayed(TIMEOUT,endbadly, NULL); /* load privat key */ - char *hostkey_file; GNUNET_asprintf(&hostkey_file,"zonefiles%s%s",DIR_SEPARATOR_STR, "N0UJMP015AFUNR2BTNM3FKPBLG38913BL8IDMCO2H0A1LIB81960.zkey"); GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Using zonekey file `%s' \n", hostkey_file); @@ -233,7 +197,7 @@ run (void *cls, char *const *args, const char *cfgfile, GNUNET_CRYPTO_rsa_key_get_public(privkey, &pubkey); /* create record */ - s_name = "dummy.dummy.gnunet"; + s_name = GNUNET_NAMESTORE_normalize_string ("DUMMY.dummy.gnunet"); s_rd = create_record (RECORDS); rd_ser_len = GNUNET_NAMESTORE_records_get_size(RECORDS, s_rd); @@ -241,59 +205,36 @@ run (void *cls, char *const *args, const char *cfgfile, GNUNET_NAMESTORE_records_serialize(RECORDS, s_rd, rd_ser_len, rd_ser); /* sign */ - s_signature = GNUNET_NAMESTORE_create_signature(privkey, s_rd[0].expiration, s_name, s_rd, RECORDS); + et.abs_value = s_rd[0].expiration_time; + s_signature = GNUNET_NAMESTORE_create_signature(privkey, et, s_name, s_rd, RECORDS); /* create random zone hash */ GNUNET_CRYPTO_hash (&pubkey, sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded), &s_zone); GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Name: `%s' Zone: `%s' \n", s_name, GNUNET_h2s_full(&s_zone)); - - - start_arm (cfgfile); - GNUNET_assert (arm != NULL); - nsh = GNUNET_NAMESTORE_connect (cfg); GNUNET_break (NULL != nsh); - GNUNET_break (s_rd != NULL); GNUNET_break (s_name != NULL); - GNUNET_NAMESTORE_record_put (nsh, &pubkey, s_name, GNUNET_TIME_UNIT_FOREVER_ABS, RECORDS, s_rd, s_signature, put_cont, s_name); - - } -static int -check () -{ - static char *const argv[] = { "test-namestore-api", - "-c", - "test_namestore_api.conf", -#if VERBOSE - "-L", "DEBUG", -#endif - NULL - }; - static struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - - res = 1; - GNUNET_PROGRAM_run ((sizeof (argv) / sizeof (char *)) - 1, argv, "test-namestore-api", - "nohelp", options, &run, &res); - return res; -} int main (int argc, char *argv[]) { - int ret; - - ret = check (); - GNUNET_free (s_signature); - return ret; + res = 1; + if (0 != + GNUNET_TESTING_service_run ("test-namestore-api-remove-not-existing-record", + "namestore", + "test_namestore_api.conf", + &run, + NULL)) + return 1; + GNUNET_free_non_null (s_signature); + return res; } -/* end of test_namestore_api.c */ +/* end of test_namestore_api_remove_not_existing_record.c */ diff --git a/src/namestore/test_namestore_api_sign_verify.c b/src/namestore/test_namestore_api_sign_verify.c index 17bfb1e..10be25b 100644 --- a/src/namestore/test_namestore_api_sign_verify.c +++ b/src/namestore/test_namestore_api_sign_verify.c @@ -27,46 +27,51 @@ #include "namestore.h" #include "gnunet_signatures.h" -#define VERBOSE GNUNET_NO - #define RECORDS 5 + #define TEST_RECORD_TYPE 1234 + #define TEST_RECORD_DATALEN 123 + #define TEST_RECORD_DATA 'a' #define TEST_REMOVE_RECORD_TYPE 4321 + #define TEST_REMOVE_RECORD_DATALEN 255 + #define TEST_REMOVE_RECORD_DATA 'b' + static struct GNUNET_CRYPTO_RsaPrivateKey * privkey; + static struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded pubkey; -struct GNUNET_CRYPTO_RsaSignature s_signature; -struct GNUNET_NAMESTORE_RecordData *s_rd; + +static struct GNUNET_NAMESTORE_RecordData *s_rd; + static char *s_name; static int res; + static struct GNUNET_NAMESTORE_RecordData * create_record (int count) { - int c; + unsigned int c; struct GNUNET_NAMESTORE_RecordData * rd; - rd = GNUNET_malloc (count * sizeof (struct GNUNET_NAMESTORE_RecordData)); - for (c = 0; c < RECORDS; c++) + rd = GNUNET_malloc (count * sizeof (struct GNUNET_NAMESTORE_RecordData)); + for (c = 0; c < count; c++) { - rd[c].expiration = GNUNET_TIME_absolute_get(); - rd[c].record_type = TEST_RECORD_TYPE; - rd[c].data_size = TEST_RECORD_DATALEN; - rd[c].data = GNUNET_malloc(TEST_RECORD_DATALEN); - memset ((char *) rd[c].data, TEST_RECORD_DATA, TEST_RECORD_DATALEN); + rd[c].expiration_time = GNUNET_TIME_absolute_get().abs_value; + rd[c].record_type = TEST_RECORD_TYPE; + rd[c].data_size = TEST_RECORD_DATALEN; + rd[c].data = GNUNET_malloc(TEST_RECORD_DATALEN); + memset ((char *) rd[c].data, TEST_RECORD_DATA, TEST_RECORD_DATALEN); } - return rd; } - static void run (void *cls, char *const *args, const char *cfgfile, const struct GNUNET_CONFIGURATION_Handle *cfg) @@ -89,7 +94,7 @@ run (void *cls, char *const *args, const char *cfgfile, int res_w; /* create record */ - s_name = "dummy.dummy.gnunet"; + s_name = "DUMMY.dummy.gnunet"; s_rd = create_record (RECORDS); signature = GNUNET_NAMESTORE_create_signature (privkey, expire, s_name, s_rd, RECORDS); @@ -116,15 +121,13 @@ run (void *cls, char *const *args, const char *cfgfile, } -static int -check () + +int +main (int argc, char *argv[]) { - static char *const argv[] = { "test-namestore-api", + static char *const argvx[] = { "test-namestore-api", "-c", "test_namestore_api.conf", -#if VERBOSE - "-L", "DEBUG", -#endif NULL }; static struct GNUNET_GETOPT_CommandLineOption options[] = { @@ -132,19 +135,9 @@ check () }; res = 1; - GNUNET_PROGRAM_run ((sizeof (argv) / sizeof (char *)) - 1, argv, "test-namestore-api", + GNUNET_PROGRAM_run ((sizeof (argvx) / sizeof (char *)) - 1, argvx, "test-namestore-api", "nohelp", options, &run, &res); return res; } -int -main (int argc, char *argv[]) -{ - int ret; - - ret = check (); - - return ret; -} - /* end of test_namestore_api_sign_verify.c */ diff --git a/src/namestore/test_namestore_api_zone_iteration.c b/src/namestore/test_namestore_api_zone_iteration.c index 0665541..e61fb67 100644 --- a/src/namestore/test_namestore_api_zone_iteration.c +++ b/src/namestore/test_namestore_api_zone_iteration.c @@ -24,67 +24,55 @@ #include "platform.h" #include "gnunet_common.h" #include "gnunet_namestore_service.h" +#include "gnunet_testing_lib.h" #include "namestore.h" -#define VERBOSE GNUNET_NO -#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 10) +#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 100) + static struct GNUNET_NAMESTORE_Handle * nsh; static GNUNET_SCHEDULER_TaskIdentifier endbadly_task; + static GNUNET_SCHEDULER_TaskIdentifier stopiteration_task; -static struct GNUNET_OS_Process *arm; static struct GNUNET_CRYPTO_RsaPrivateKey * privkey; + static struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded pubkey; -static GNUNET_HashCode zone; + +static struct GNUNET_HashCode zone; static struct GNUNET_CRYPTO_RsaPrivateKey * privkey2; + static struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded pubkey2; -static GNUNET_HashCode zone2; + +static struct GNUNET_HashCode zone2; static struct GNUNET_NAMESTORE_ZoneIterator *zi; + static int res; + static int returned_records; -struct GNUNET_CRYPTO_RsaSignature *sig_1; -char * s_name_1; -struct GNUNET_NAMESTORE_RecordData *s_rd_1; +static struct GNUNET_CRYPTO_RsaSignature *sig_1; -struct GNUNET_CRYPTO_RsaSignature *sig_2; -char * s_name_2; -struct GNUNET_NAMESTORE_RecordData *s_rd_2; +static char * s_name_1; -struct GNUNET_CRYPTO_RsaSignature *sig_3; -char * s_name_3; -struct GNUNET_NAMESTORE_RecordData *s_rd_3; +static struct GNUNET_NAMESTORE_RecordData *s_rd_1; -static void -start_arm (const char *cfgname) -{ - arm = GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-arm", - "gnunet-service-arm", "-c", cfgname, -#if VERBOSE_PEERS - "-L", "DEBUG", -#else - "-L", "ERROR", -#endif - NULL); -} +static struct GNUNET_CRYPTO_RsaSignature *sig_2; + +static char * s_name_2; + +static struct GNUNET_NAMESTORE_RecordData *s_rd_2; + +static struct GNUNET_CRYPTO_RsaSignature *sig_3; + +static char * s_name_3; + +static struct GNUNET_NAMESTORE_RecordData *s_rd_3; -static void -stop_arm () -{ - if (NULL != arm) - { - if (0 != GNUNET_OS_process_kill (arm, SIGTERM)) - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); - GNUNET_OS_process_wait (arm); - GNUNET_OS_process_destroy (arm); - arm = NULL; - } -} /** * Re-establish the connection to the service. @@ -102,7 +90,7 @@ endbadly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) } if (nsh != NULL) - GNUNET_NAMESTORE_disconnect (nsh, GNUNET_YES); + GNUNET_NAMESTORE_disconnect (nsh); nsh = NULL; GNUNET_free_non_null(sig_1); @@ -135,10 +123,6 @@ endbadly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) if (privkey2 != NULL) GNUNET_CRYPTO_rsa_key_free (privkey2); privkey2 = NULL; - - if (NULL != arm) - stop_arm(); - res = 1; } @@ -187,26 +171,23 @@ end (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) GNUNET_free ((void *)s_rd_3->data); GNUNET_free (s_rd_3); } - if (nsh != NULL) - GNUNET_NAMESTORE_disconnect (nsh, GNUNET_YES); + GNUNET_NAMESTORE_disconnect (nsh); nsh = NULL; - - - if (NULL != arm) - stop_arm(); } -void zone_proc (void *cls, - const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *zone_key, - struct GNUNET_TIME_Absolute expire, - const char *name, - unsigned int rd_count, - const struct GNUNET_NAMESTORE_RecordData *rd, - const struct GNUNET_CRYPTO_RsaSignature *signature) + +static void +zone_proc (void *cls, + const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *zone_key, + struct GNUNET_TIME_Absolute expire, + const char *name, + unsigned int rd_count, + const struct GNUNET_NAMESTORE_RecordData *rd, + const struct GNUNET_CRYPTO_RsaSignature *signature) { int failed = GNUNET_NO; - if ((zone_key == NULL) && (name == NULL)) + if ((zone_key == NULL) && (name == NULL)) { GNUNET_break (3 == returned_records); if (3 == returned_records) @@ -222,7 +203,7 @@ void zone_proc (void *cls, /* verify signature returned from name store */ if (GNUNET_OK != GNUNET_NAMESTORE_verify_signature (zone_key, expire, name, rd_count, rd, signature)) { - GNUNET_HashCode zone_key_hash; + struct GNUNET_HashCode zone_key_hash; GNUNET_CRYPTO_hash (zone_key, sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded), &zone_key_hash); GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Verifying signature for `%s' in zone `%s' with %u records and expiration %llu failed\n", name, GNUNET_h2s(&zone_key_hash), rd_count, expire.abs_value); @@ -322,25 +303,8 @@ void zone_proc (void *cls, } } -void -delete_existing_db (const struct GNUNET_CONFIGURATION_Handle *cfg) -{ - char *afsdir; - - if (GNUNET_OK == - GNUNET_CONFIGURATION_get_value_filename (cfg, "namestore-sqlite", - "FILENAME", &afsdir)) - { - if (GNUNET_OK == GNUNET_DISK_file_test (afsdir)) - if (GNUNET_OK == GNUNET_DISK_file_test (afsdir)) - if (GNUNET_OK == GNUNET_DISK_directory_remove(afsdir)) - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Deleted existing database `%s' \n", afsdir); - GNUNET_free (afsdir); - } - -} -void +static void put_cont (void *cls, int32_t success, const char *emsg) { static int c = 0; @@ -364,11 +328,11 @@ put_cont (void *cls, int32_t success, const char *emsg) returned_records = 0; GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "All records created, starting iteration over all zones \n"); zi = GNUNET_NAMESTORE_zone_iteration_start(nsh, - NULL, - GNUNET_NAMESTORE_RF_NONE, - GNUNET_NAMESTORE_RF_NONE, - zone_proc, - &zone); + NULL, + GNUNET_NAMESTORE_RF_NONE, + GNUNET_NAMESTORE_RF_NONE, + &zone_proc, + &zone); if (zi == NULL) { GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Failed to create zone iterator\n"); @@ -379,16 +343,17 @@ put_cont (void *cls, int32_t success, const char *emsg) } } + static struct GNUNET_NAMESTORE_RecordData * -create_record (int count) +create_record (unsigned int count) { - int c; + unsigned int c; struct GNUNET_NAMESTORE_RecordData * rd; - rd = GNUNET_malloc (count * sizeof (struct GNUNET_NAMESTORE_RecordData)); + rd = GNUNET_malloc (count * sizeof (struct GNUNET_NAMESTORE_RecordData)); for (c = 0; c < count; c++) { - rd[c].expiration = GNUNET_TIME_absolute_get(); + rd[c].expiration_time = GNUNET_TIME_relative_to_absolute (GNUNET_TIME_UNIT_HOURS).abs_value; rd[c].record_type = 1111; rd[c].data_size = 50; rd[c].data = GNUNET_malloc(50); @@ -397,14 +362,28 @@ create_record (int count) return rd; } + +/** + * Callback called from the zone iterator when we iterate over + * the empty zone. Check that we got no records and then + * start the actual tests by filling the zone. + */ static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) +empty_zone_proc (void *cls, + const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *zone_key, + struct GNUNET_TIME_Absolute expire, + const char *name, + unsigned int rd_count, + const struct GNUNET_NAMESTORE_RecordData *rd, + const struct GNUNET_CRYPTO_RsaSignature *signature) { - delete_existing_db(cfg); - endbadly_task = GNUNET_SCHEDULER_add_delayed(TIMEOUT,&endbadly, NULL); - char *hostkey_file; + struct GNUNET_TIME_Absolute et; + + GNUNET_assert (nsh == cls); + GNUNET_assert (NULL == name); + GNUNET_assert (NULL == zone_key); + zi = NULL; GNUNET_asprintf(&hostkey_file,"zonefiles%s%s",DIR_SEPARATOR_STR, "N0UJMP015AFUNR2BTNM3FKPBLG38913BL8IDMCO2H0A1LIB81960.zkey"); GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Using zonekey file `%s' \n", hostkey_file); @@ -425,18 +404,12 @@ run (void *cls, char *const *args, const char *cfgfile, GNUNET_CRYPTO_rsa_key_get_public(privkey2, &pubkey2); GNUNET_CRYPTO_hash(&pubkey2, sizeof (pubkey), &zone2); - - start_arm (cfgfile); - GNUNET_assert (arm != NULL); - - nsh = GNUNET_NAMESTORE_connect (cfg); - GNUNET_break (NULL != nsh); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Created record 1\n"); GNUNET_asprintf(&s_name_1, "dummy1"); s_rd_1 = create_record(1); - sig_1 = GNUNET_NAMESTORE_create_signature(privkey, s_rd_1->expiration, s_name_1, s_rd_1, 1); + et.abs_value = s_rd_1->expiration_time; + sig_1 = GNUNET_NAMESTORE_create_signature(privkey, et, s_name_1, s_rd_1, 1); GNUNET_NAMESTORE_record_create(nsh, privkey, s_name_1, s_rd_1, &put_cont, NULL); @@ -444,46 +417,58 @@ run (void *cls, char *const *args, const char *cfgfile, GNUNET_asprintf(&s_name_2, "dummy2"); s_rd_2 = create_record(1); - sig_2 = GNUNET_NAMESTORE_create_signature(privkey, s_rd_2->expiration, s_name_2, s_rd_2, 1); + et.abs_value = s_rd_2->expiration_time; + sig_2 = GNUNET_NAMESTORE_create_signature(privkey, et, s_name_2, s_rd_2, 1); GNUNET_NAMESTORE_record_create(nsh, privkey, s_name_2, s_rd_2, &put_cont, NULL); GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Created record 3\n"); /* name in different zone */ GNUNET_asprintf(&s_name_3, "dummy3"); s_rd_3 = create_record(1); - sig_3 = GNUNET_NAMESTORE_create_signature(privkey2, s_rd_3->expiration, s_name_3, s_rd_3, 1); + et.abs_value = s_rd_3->expiration_time; + sig_3 = GNUNET_NAMESTORE_create_signature(privkey2, et, s_name_3, s_rd_3, 1); GNUNET_NAMESTORE_record_put (nsh, &pubkey2, s_name_3, GNUNET_TIME_UNIT_FOREVER_ABS, 1, s_rd_3, sig_3, &put_cont, NULL); } -static int -check () -{ - static char *const argv[] = { "test_namestore_api_zone_iteration", - "-c", - "test_namestore_api.conf", -#if VERBOSE - "-L", "DEBUG", -#endif - NULL - }; - static struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - res = 1; - GNUNET_PROGRAM_run ((sizeof (argv) / sizeof (char *)) - 1, argv, "test_namestore_api_zone_iteration", - "nohelp", options, &run, &res); - return res; +static void +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) +{ + endbadly_task = GNUNET_SCHEDULER_add_delayed(TIMEOUT, &endbadly, NULL); + nsh = GNUNET_NAMESTORE_connect (cfg); + GNUNET_break (NULL != nsh); + /* first, iterate over empty namestore */ + zi = GNUNET_NAMESTORE_zone_iteration_start(nsh, + NULL, + GNUNET_NAMESTORE_RF_NONE, + GNUNET_NAMESTORE_RF_NONE, + &empty_zone_proc, + nsh); + if (NULL == zi) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Failed to create zone iterator\n"); + GNUNET_break (0); + GNUNET_SCHEDULER_cancel (endbadly_task); + endbadly_task = GNUNET_SCHEDULER_add_now (&endbadly, NULL); + } } + int main (int argc, char *argv[]) { - int ret; - - ret = check (); - - return ret; + res = 1; + if (0 != + GNUNET_TESTING_service_run ("test-namestore-api-zone-iteration", + "namestore", + "test_namestore_api.conf", + &run, + NULL)) + return 1; + return res; } + /* end of test_namestore_api_zone_iteration.c */ diff --git a/src/namestore/test_namestore_api_zone_iteration_specific_zone.c b/src/namestore/test_namestore_api_zone_iteration_specific_zone.c index b21c860..7adf3fe 100644 --- a/src/namestore/test_namestore_api_zone_iteration_specific_zone.c +++ b/src/namestore/test_namestore_api_zone_iteration_specific_zone.c @@ -23,68 +23,56 @@ */ #include "platform.h" #include "gnunet_common.h" +#include "gnunet_testing_lib.h" #include "gnunet_namestore_service.h" #include "namestore.h" -#define VERBOSE GNUNET_NO -#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 10) +#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 100) + static struct GNUNET_NAMESTORE_Handle * nsh; static GNUNET_SCHEDULER_TaskIdentifier endbadly_task; + static GNUNET_SCHEDULER_TaskIdentifier stopiteration_task; -static struct GNUNET_OS_Process *arm; static struct GNUNET_CRYPTO_RsaPrivateKey * privkey; + static struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded pubkey; + static struct GNUNET_CRYPTO_ShortHashCode zone; static struct GNUNET_CRYPTO_RsaPrivateKey * privkey2; + static struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded pubkey2; + static struct GNUNET_CRYPTO_ShortHashCode zone2; static struct GNUNET_NAMESTORE_ZoneIterator *zi; + static int res; + static int returned_records; -struct GNUNET_CRYPTO_RsaSignature *sig_1; -char * s_name_1; -struct GNUNET_NAMESTORE_RecordData *s_rd_1; +static struct GNUNET_CRYPTO_RsaSignature *sig_1; -struct GNUNET_CRYPTO_RsaSignature *sig_2; -char * s_name_2; -struct GNUNET_NAMESTORE_RecordData *s_rd_2; +static char * s_name_1; -struct GNUNET_CRYPTO_RsaSignature *sig_3; -char * s_name_3; -struct GNUNET_NAMESTORE_RecordData *s_rd_3; +static struct GNUNET_NAMESTORE_RecordData *s_rd_1; -static void -start_arm (const char *cfgname) -{ - arm = GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-arm", - "gnunet-service-arm", "-c", cfgname, -#if VERBOSE_PEERS - "-L", "DEBUG", -#else - "-L", "ERROR", -#endif - NULL); -} +static struct GNUNET_CRYPTO_RsaSignature *sig_2; + +static char * s_name_2; + +static struct GNUNET_NAMESTORE_RecordData *s_rd_2; + +static struct GNUNET_CRYPTO_RsaSignature *sig_3; + +static char * s_name_3; + +static struct GNUNET_NAMESTORE_RecordData *s_rd_3; -static void -stop_arm () -{ - if (NULL != arm) - { - if (0 != GNUNET_OS_process_kill (arm, SIGTERM)) - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); - GNUNET_OS_process_wait (arm); - GNUNET_OS_process_destroy (arm); - arm = NULL; - } -} /** * Re-establish the connection to the service. @@ -102,16 +90,14 @@ endbadly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) } if (nsh != NULL) - GNUNET_NAMESTORE_disconnect (nsh, GNUNET_YES); + GNUNET_NAMESTORE_disconnect (nsh); nsh = NULL; - GNUNET_free_non_null(sig_1); GNUNET_free_non_null(sig_2); GNUNET_free_non_null(sig_3); GNUNET_free_non_null(s_name_1); GNUNET_free_non_null(s_name_2); GNUNET_free_non_null(s_name_3); - if (s_rd_1 != NULL) { GNUNET_free ((void *)s_rd_1->data); @@ -135,10 +121,6 @@ endbadly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) if (privkey2 != NULL) GNUNET_CRYPTO_rsa_key_free (privkey2); privkey2 = NULL; - - if (NULL != arm) - stop_arm(); - res = 1; } @@ -151,17 +133,14 @@ end (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) GNUNET_SCHEDULER_cancel (stopiteration_task); stopiteration_task = GNUNET_SCHEDULER_NO_TASK; } - if (endbadly_task != GNUNET_SCHEDULER_NO_TASK) { GNUNET_SCHEDULER_cancel (endbadly_task); endbadly_task = GNUNET_SCHEDULER_NO_TASK; } - if (privkey != NULL) GNUNET_CRYPTO_rsa_key_free (privkey); privkey = NULL; - if (privkey2 != NULL) GNUNET_CRYPTO_rsa_key_free (privkey2); privkey2 = NULL; @@ -187,23 +166,20 @@ end (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) GNUNET_free ((void *)s_rd_3->data); GNUNET_free (s_rd_3); } - if (nsh != NULL) - GNUNET_NAMESTORE_disconnect (nsh, GNUNET_YES); + GNUNET_NAMESTORE_disconnect (nsh); nsh = NULL; - - - if (NULL != arm) - stop_arm(); } -void zone_proc (void *cls, - const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *zone_key, - struct GNUNET_TIME_Absolute expire, - const char *name, - unsigned int rd_count, - const struct GNUNET_NAMESTORE_RecordData *rd, - const struct GNUNET_CRYPTO_RsaSignature *signature) + +static void +zone_proc (void *cls, + const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *zone_key, + struct GNUNET_TIME_Absolute expire, + const char *name, + unsigned int rd_count, + const struct GNUNET_NAMESTORE_RecordData *rd, + const struct GNUNET_CRYPTO_RsaSignature *signature) { int failed = GNUNET_NO; GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Callback for zone `%s'\n", GNUNET_short_h2s (&zone)); @@ -285,25 +261,8 @@ void zone_proc (void *cls, } } -void -delete_existing_db (const struct GNUNET_CONFIGURATION_Handle *cfg) -{ - char *afsdir; - - if (GNUNET_OK == - GNUNET_CONFIGURATION_get_value_filename (cfg, "namestore-sqlite", - "FILENAME", &afsdir)) - { - if (GNUNET_OK == GNUNET_DISK_file_test (afsdir)) - if (GNUNET_OK == GNUNET_DISK_file_test (afsdir)) - if (GNUNET_OK == GNUNET_DISK_directory_remove(afsdir)) - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Deleted existing database `%s' \n", afsdir); - GNUNET_free (afsdir); - } - -} -void +static void put_cont (void *cls, int32_t success, const char *emsg) { static int c = 0; @@ -343,16 +302,17 @@ put_cont (void *cls, int32_t success, const char *emsg) } } + static struct GNUNET_NAMESTORE_RecordData * -create_record (int count) +create_record (unsigned int count) { - int c; + unsigned int c; struct GNUNET_NAMESTORE_RecordData * rd; - rd = GNUNET_malloc (count * sizeof (struct GNUNET_NAMESTORE_RecordData)); + rd = GNUNET_malloc (count * sizeof (struct GNUNET_NAMESTORE_RecordData)); for (c = 0; c < count; c++) { - rd[c].expiration = GNUNET_TIME_absolute_get(); + rd[c].expiration_time = GNUNET_TIME_relative_to_absolute (GNUNET_TIME_UNIT_HOURS).abs_value; rd[c].record_type = 1111; rd[c].data_size = 50; rd[c].data = GNUNET_malloc(50); @@ -361,14 +321,16 @@ create_record (int count) return rd; } + static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) { - delete_existing_db(cfg); - endbadly_task = GNUNET_SCHEDULER_add_delayed(TIMEOUT,&endbadly, NULL); - char *hostkey_file; + struct GNUNET_TIME_Absolute et; + + endbadly_task = GNUNET_SCHEDULER_add_delayed(TIMEOUT,&endbadly, NULL); GNUNET_asprintf(&hostkey_file,"zonefiles%s%s",DIR_SEPARATOR_STR, "N0UJMP015AFUNR2BTNM3FKPBLG38913BL8IDMCO2H0A1LIB81960.zkey"); GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Using zonekey file `%s' \n", hostkey_file); @@ -386,66 +348,45 @@ run (void *cls, char *const *args, const char *cfgfile, GNUNET_assert (privkey2 != NULL); GNUNET_CRYPTO_rsa_key_get_public(privkey2, &pubkey2); GNUNET_CRYPTO_short_hash (&pubkey2, sizeof (pubkey), &zone2); - - - start_arm (cfgfile); - GNUNET_assert (arm != NULL); - nsh = GNUNET_NAMESTORE_connect (cfg); GNUNET_break (NULL != nsh); GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Created record 1\n"); - GNUNET_asprintf(&s_name_1, "dummy1"); s_rd_1 = create_record(1); - sig_1 = GNUNET_NAMESTORE_create_signature(privkey, s_rd_1[0].expiration ,s_name_1, s_rd_1, 1); + et.abs_value = s_rd_1[0].expiration_time; + sig_1 = GNUNET_NAMESTORE_create_signature(privkey, et, s_name_1, s_rd_1, 1); GNUNET_NAMESTORE_record_create(nsh, privkey, s_name_1, s_rd_1, &put_cont, NULL); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Created record 2 \n"); GNUNET_asprintf(&s_name_2, "dummy2"); s_rd_2 = create_record(1); - - sig_2 = GNUNET_NAMESTORE_create_signature(privkey, s_rd_2[0].expiration, s_name_2, s_rd_2, 1); + et.abs_value = s_rd_2[0].expiration_time; + sig_2 = GNUNET_NAMESTORE_create_signature(privkey, et, s_name_2, s_rd_2, 1); GNUNET_NAMESTORE_record_create(nsh, privkey, s_name_2, s_rd_2, &put_cont, NULL); GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Created record 3\n"); /* name in different zone */ GNUNET_asprintf(&s_name_3, "dummy3"); s_rd_3 = create_record(1); - sig_3 = GNUNET_NAMESTORE_create_signature(privkey, s_rd_3[0].expiration, s_name_3, s_rd_3, 1); + et.abs_value = s_rd_3[0].expiration_time; + sig_3 = GNUNET_NAMESTORE_create_signature(privkey, et, s_name_3, s_rd_3, 1); GNUNET_NAMESTORE_record_put (nsh, &pubkey2, s_name_3, GNUNET_TIME_UNIT_FOREVER_ABS, 1, s_rd_3, sig_3, &put_cont, NULL); } -static int -check () -{ - static char *const argv[] = { "test_namestore_api_zone_iteration", - "-c", - "test_namestore_api.conf", -#if VERBOSE - "-L", "DEBUG", -#endif - NULL - }; - static struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - - res = 1; - GNUNET_PROGRAM_run ((sizeof (argv) / sizeof (char *)) - 1, argv, "test_namestore_api_zone_iteration", - "nohelp", options, &run, &res); - return res; -} int main (int argc, char *argv[]) { - int ret; - - ret = check (); - - return ret; + res = 1; + if (0 != + GNUNET_TESTING_service_run ("test-namestore-api-zone-iteration-specific-zone", + "namestore", + "test_namestore_api.conf", + &run, + NULL)) + return 1; + return res; } /* end of test_namestore_api_zone_iteration_specific_zone.c */ diff --git a/src/namestore/test_namestore_api_zone_iteration_stop.c b/src/namestore/test_namestore_api_zone_iteration_stop.c index 9f62c73..dcb6f8c 100644 --- a/src/namestore/test_namestore_api_zone_iteration_stop.c +++ b/src/namestore/test_namestore_api_zone_iteration_stop.c @@ -23,68 +23,55 @@ */ #include "platform.h" #include "gnunet_common.h" +#include "gnunet_testing_lib.h" #include "gnunet_namestore_service.h" #include "namestore.h" -#define VERBOSE GNUNET_NO -#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 15) +#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 150) static struct GNUNET_NAMESTORE_Handle * nsh; static GNUNET_SCHEDULER_TaskIdentifier endbadly_task; + static GNUNET_SCHEDULER_TaskIdentifier stopiteration_task; -static struct GNUNET_OS_Process *arm; static struct GNUNET_CRYPTO_RsaPrivateKey * privkey; + static struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded pubkey; -static GNUNET_HashCode zone; + +static struct GNUNET_HashCode zone; static struct GNUNET_CRYPTO_RsaPrivateKey * privkey2; + static struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded pubkey2; -static GNUNET_HashCode zone2; + +static struct GNUNET_HashCode zone2; static struct GNUNET_NAMESTORE_ZoneIterator *zi; + static int res; + static int returned_records; -struct GNUNET_CRYPTO_RsaSignature *sig_1; -char * s_name_1; -struct GNUNET_NAMESTORE_RecordData *s_rd_1; +static struct GNUNET_CRYPTO_RsaSignature *sig_1; -struct GNUNET_CRYPTO_RsaSignature *sig_2; -char * s_name_2; -struct GNUNET_NAMESTORE_RecordData *s_rd_2; +static char * s_name_1; -struct GNUNET_CRYPTO_RsaSignature *sig_3; -char * s_name_3; -struct GNUNET_NAMESTORE_RecordData *s_rd_3; +static struct GNUNET_NAMESTORE_RecordData *s_rd_1; -static void -start_arm (const char *cfgname) -{ - arm = GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-arm", - "gnunet-service-arm", "-c", cfgname, -#if VERBOSE_PEERS - "-L", "DEBUG", -#else - "-L", "ERROR", -#endif - NULL); -} +static struct GNUNET_CRYPTO_RsaSignature *sig_2; + +static char * s_name_2; + +static struct GNUNET_NAMESTORE_RecordData *s_rd_2; + +static struct GNUNET_CRYPTO_RsaSignature *sig_3; + +static char * s_name_3; + +static struct GNUNET_NAMESTORE_RecordData *s_rd_3; -static void -stop_arm () -{ - if (NULL != arm) - { - if (0 != GNUNET_OS_process_kill (arm, SIGTERM)) - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); - GNUNET_OS_process_wait (arm); - GNUNET_OS_process_destroy (arm); - arm = NULL; - } -} /** * Re-establish the connection to the service. @@ -100,18 +87,15 @@ endbadly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) GNUNET_SCHEDULER_cancel (stopiteration_task); stopiteration_task = GNUNET_SCHEDULER_NO_TASK; } - if (nsh != NULL) - GNUNET_NAMESTORE_disconnect (nsh, GNUNET_YES); + GNUNET_NAMESTORE_disconnect (nsh); nsh = NULL; - GNUNET_free_non_null(sig_1); GNUNET_free_non_null(sig_2); GNUNET_free_non_null(sig_3); GNUNET_free_non_null(s_name_1); GNUNET_free_non_null(s_name_2); GNUNET_free_non_null(s_name_3); - if (s_rd_1 != NULL) { GNUNET_free ((void *)s_rd_1->data); @@ -127,7 +111,6 @@ endbadly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) GNUNET_free ((void *)s_rd_3->data); GNUNET_free (s_rd_3); } - if (privkey != NULL) GNUNET_CRYPTO_rsa_key_free (privkey); privkey = NULL; @@ -135,10 +118,6 @@ endbadly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) if (privkey2 != NULL) GNUNET_CRYPTO_rsa_key_free (privkey2); privkey2 = NULL; - - if (NULL != arm) - stop_arm(); - res = 1; } @@ -157,11 +136,9 @@ end (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) GNUNET_SCHEDULER_cancel (endbadly_task); endbadly_task = GNUNET_SCHEDULER_NO_TASK; } - if (privkey != NULL) GNUNET_CRYPTO_rsa_key_free (privkey); privkey = NULL; - if (privkey2 != NULL) GNUNET_CRYPTO_rsa_key_free (privkey2); privkey2 = NULL; @@ -187,13 +164,9 @@ end (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) GNUNET_free ((void *)s_rd_3->data); GNUNET_free (s_rd_3); } - if (nsh != NULL) - GNUNET_NAMESTORE_disconnect (nsh, GNUNET_YES); + GNUNET_NAMESTORE_disconnect (nsh); nsh = NULL; - - if (NULL != arm) - stop_arm(); if (returned_records == 1) res = 0; else @@ -201,13 +174,15 @@ end (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) } -void zone_proc (void *cls, - const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *zone_key, - struct GNUNET_TIME_Absolute expire, - const char *name, - unsigned int rd_count, - const struct GNUNET_NAMESTORE_RecordData *rd, - const struct GNUNET_CRYPTO_RsaSignature *signature) + +static void +zone_proc (void *cls, + const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *zone_key, + struct GNUNET_TIME_Absolute expire, + const char *name, + unsigned int rd_count, + const struct GNUNET_NAMESTORE_RecordData *rd, + const struct GNUNET_CRYPTO_RsaSignature *signature) { int failed = GNUNET_NO; @@ -336,25 +311,8 @@ void zone_proc (void *cls, } } -void -delete_existing_db (const struct GNUNET_CONFIGURATION_Handle *cfg) -{ - char *afsdir; - - if (GNUNET_OK == - GNUNET_CONFIGURATION_get_value_filename (cfg, "namestore-sqlite", - "FILENAME", &afsdir)) - { - if (GNUNET_OK == GNUNET_DISK_file_test (afsdir)) - if (GNUNET_OK == GNUNET_DISK_file_test (afsdir)) - if (GNUNET_OK == GNUNET_DISK_directory_remove(afsdir)) - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Deleted existing database `%s' \n", afsdir); - GNUNET_free (afsdir); - } - -} -void +static void put_cont (void *cls, int32_t success, const char *emsg) { static int c = 0; @@ -393,16 +351,17 @@ put_cont (void *cls, int32_t success, const char *emsg) } } + static struct GNUNET_NAMESTORE_RecordData * -create_record (int count) +create_record (unsigned int count) { - int c; + unsigned int c; struct GNUNET_NAMESTORE_RecordData * rd; - rd = GNUNET_malloc (count * sizeof (struct GNUNET_NAMESTORE_RecordData)); + rd = GNUNET_malloc (count * sizeof (struct GNUNET_NAMESTORE_RecordData)); for (c = 0; c < count; c++) { - rd[c].expiration = GNUNET_TIME_absolute_get(); + rd[c].expiration_time = GNUNET_TIME_relative_to_absolute (GNUNET_TIME_UNIT_HOURS).abs_value; rd[c].record_type = 1111; rd[c].data_size = 50; rd[c].data = GNUNET_malloc(50); @@ -411,14 +370,16 @@ create_record (int count) return rd; } + static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) { - delete_existing_db(cfg); - endbadly_task = GNUNET_SCHEDULER_add_delayed(TIMEOUT,&endbadly, NULL); - char *hostkey_file; + struct GNUNET_TIME_Absolute et; + + endbadly_task = GNUNET_SCHEDULER_add_delayed(TIMEOUT,&endbadly, NULL); GNUNET_asprintf(&hostkey_file,"zonefiles%s%s",DIR_SEPARATOR_STR, "N0UJMP015AFUNR2BTNM3FKPBLG38913BL8IDMCO2H0A1LIB81960.zkey"); GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Using zonekey file `%s' \n", hostkey_file); @@ -437,10 +398,6 @@ run (void *cls, char *const *args, const char *cfgfile, GNUNET_CRYPTO_rsa_key_get_public(privkey2, &pubkey2); GNUNET_CRYPTO_hash(&pubkey2, sizeof (pubkey), &zone2); - - start_arm (cfgfile); - GNUNET_assert (arm != NULL); - nsh = GNUNET_NAMESTORE_connect (cfg); GNUNET_break (NULL != nsh); @@ -448,7 +405,8 @@ run (void *cls, char *const *args, const char *cfgfile, GNUNET_asprintf(&s_name_1, "dummy1"); s_rd_1 = create_record(1); - sig_1 = GNUNET_NAMESTORE_create_signature(privkey, s_rd_1[0].expiration, s_name_1, s_rd_1, 1); + et.abs_value = s_rd_1[0].expiration_time; + sig_1 = GNUNET_NAMESTORE_create_signature(privkey, et, s_name_1, s_rd_1, 1); GNUNET_NAMESTORE_record_create(nsh, privkey, s_name_1, s_rd_1, &put_cont, NULL); @@ -456,46 +414,33 @@ run (void *cls, char *const *args, const char *cfgfile, GNUNET_asprintf(&s_name_2, "dummy2"); s_rd_2 = create_record(1); - sig_2 = GNUNET_NAMESTORE_create_signature(privkey, s_rd_2[0].expiration, s_name_2, s_rd_2, 1); + et.abs_value = s_rd_2[0].expiration_time; + sig_2 = GNUNET_NAMESTORE_create_signature(privkey, et, s_name_2, s_rd_2, 1); GNUNET_NAMESTORE_record_create(nsh, privkey, s_name_2, s_rd_2, &put_cont, NULL); GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Created record 3\n"); /* name in different zone */ GNUNET_asprintf(&s_name_3, "dummy3"); s_rd_3 = create_record(1); - sig_3 = GNUNET_NAMESTORE_create_signature(privkey2, s_rd_3[0].expiration, s_name_3, s_rd_3, 1); + et.abs_value = s_rd_3[0].expiration_time; + sig_3 = GNUNET_NAMESTORE_create_signature(privkey2, et, s_name_3, s_rd_3, 1); GNUNET_NAMESTORE_record_put (nsh, &pubkey2, s_name_3, GNUNET_TIME_UNIT_FOREVER_ABS, 1, s_rd_3, sig_3, &put_cont, NULL); } -static int -check () -{ - static char *const argv[] = { "test_namestore_api_zone_iteration", - "-c", - "test_namestore_api.conf", -#if VERBOSE - "-L", "DEBUG", -#endif - NULL - }; - static struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - - res = 1; - GNUNET_PROGRAM_run ((sizeof (argv) / sizeof (char *)) - 1, argv, "test_namestore_api_zone_iteration", - "nohelp", options, &run, &res); - return res; -} int main (int argc, char *argv[]) { - int ret; - - ret = check (); - - return ret; + res = 1; + if (0 != + GNUNET_TESTING_service_run ("test-namestore-api-zone-iteration-stop", + "namestore", + "test_namestore_api.conf", + &run, + NULL)) + return 1; + return res; } -/* end of test_namestore_api_zone_iteration.c */ + +/* end of test_namestore_api_zone_iteration_stop.c */ diff --git a/src/namestore/test_namestore_api_zone_to_name.c b/src/namestore/test_namestore_api_zone_to_name.c index 6efbaf5..8562071 100644 --- a/src/namestore/test_namestore_api_zone_to_name.c +++ b/src/namestore/test_namestore_api_zone_to_name.c @@ -24,63 +24,41 @@ #include "platform.h" #include "gnunet_common.h" #include "gnunet_namestore_service.h" +#include "gnunet_testing_lib.h" #include "namestore.h" #include "gnunet_signatures.h" -#define VERBOSE GNUNET_NO - #define RECORDS 5 + #define TEST_RECORD_TYPE 1234 + #define TEST_RECORD_DATALEN 123 + #define TEST_RECORD_DATA 'a' -#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 10) +#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 100) + static struct GNUNET_NAMESTORE_Handle * nsh; static GNUNET_SCHEDULER_TaskIdentifier endbadly_task; -static struct GNUNET_OS_Process *arm; static struct GNUNET_CRYPTO_RsaPrivateKey * privkey; + static struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded pubkey; -struct GNUNET_TIME_Absolute expire; +static struct GNUNET_TIME_Absolute expire; static struct GNUNET_CRYPTO_ShortHashCode s_zone; + static struct GNUNET_CRYPTO_ShortHashCode s_zone_value; -char * s_name; +static char * s_name; -struct GNUNET_NAMESTORE_RecordData *s_rd; -struct GNUNET_CRYPTO_RsaSignature *s_signature; +static struct GNUNET_CRYPTO_RsaSignature *s_signature; static int res; -static void -start_arm (const char *cfgname) -{ - arm = GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-arm", - "gnunet-service-arm", "-c", cfgname, -#if VERBOSE_PEERS - "-L", "DEBUG", -#else - "-L", "ERROR", -#endif - NULL); -} - -static void -stop_arm () -{ - if (NULL != arm) - { - if (0 != GNUNET_OS_process_kill (arm, SIGTERM)) - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); - GNUNET_OS_process_wait (arm); - GNUNET_OS_process_destroy (arm); - arm = NULL; - } -} /** * Re-establish the connection to the service. @@ -92,16 +70,11 @@ static void endbadly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { if (nsh != NULL) - GNUNET_NAMESTORE_disconnect (nsh, GNUNET_YES); + GNUNET_NAMESTORE_disconnect (nsh); nsh = NULL; - if (privkey != NULL) GNUNET_CRYPTO_rsa_key_free (privkey); privkey = NULL; - - if (NULL != arm) - stop_arm(); - res = 1; } @@ -114,26 +87,23 @@ end (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) GNUNET_SCHEDULER_cancel (endbadly_task); endbadly_task = GNUNET_SCHEDULER_NO_TASK; } - if (privkey != NULL) GNUNET_CRYPTO_rsa_key_free (privkey); privkey = NULL; - if (nsh != NULL) - GNUNET_NAMESTORE_disconnect (nsh, GNUNET_YES); + GNUNET_NAMESTORE_disconnect (nsh); nsh = NULL; - - if (NULL != arm) - stop_arm(); } -void zone_to_name_proc (void *cls, - const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *zone_key, - struct GNUNET_TIME_Absolute expire, - const char *n, - unsigned int rd_count, - const struct GNUNET_NAMESTORE_RecordData *rd, - const struct GNUNET_CRYPTO_RsaSignature *signature) + +static void +zone_to_name_proc (void *cls, + const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *zone_key, + struct GNUNET_TIME_Absolute expire, + const char *n, + unsigned int rd_count, + const struct GNUNET_NAMESTORE_RecordData *rd, + const struct GNUNET_CRYPTO_RsaSignature *signature) { int fail = GNUNET_NO; @@ -169,26 +139,7 @@ void zone_to_name_proc (void *cls, } -void -delete_existing_db (const struct GNUNET_CONFIGURATION_Handle *cfg) -{ - char *afsdir; - - if (GNUNET_OK == - GNUNET_CONFIGURATION_get_value_filename (cfg, "namestore-sqlite", - "FILENAME", &afsdir)) - { - if (GNUNET_OK == GNUNET_DISK_file_test (afsdir)) - if (GNUNET_OK == GNUNET_DISK_file_test (afsdir)) - if (GNUNET_OK == GNUNET_DISK_directory_remove(afsdir)) - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Deleted existing database `%s' \n", afsdir); - GNUNET_free (afsdir); - } - -} - - -void +static void put_cont (void *cls, int32_t success, const char *emsg) { char *name = cls; @@ -209,16 +160,16 @@ put_cont (void *cls, int32_t success, const char *emsg) } } + static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) { - delete_existing_db(cfg); + struct GNUNET_TIME_Absolute et; endbadly_task = GNUNET_SCHEDULER_add_delayed(TIMEOUT,endbadly, NULL); GNUNET_asprintf(&s_name, "dummy"); - - /* load privat key */ char *hostkey_file; GNUNET_asprintf(&hostkey_file,"zonefiles%s%s",DIR_SEPARATOR_STR, @@ -236,53 +187,36 @@ run (void *cls, char *const *args, const char *cfgfile, GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Using PKEY `%s' \n", GNUNET_short_h2s (&s_zone_value)); struct GNUNET_NAMESTORE_RecordData rd; - rd.expiration = GNUNET_TIME_absolute_get(); + rd.expiration_time = GNUNET_TIME_absolute_get().abs_value; rd.record_type = GNUNET_NAMESTORE_TYPE_PKEY; rd.data_size = sizeof (struct GNUNET_CRYPTO_ShortHashCode); rd.data = GNUNET_malloc(sizeof (struct GNUNET_CRYPTO_ShortHashCode)); memcpy ((char *) rd.data, &s_zone_value, sizeof (struct GNUNET_CRYPTO_ShortHashCode)); - - start_arm (cfgfile); - GNUNET_assert (arm != NULL); - nsh = GNUNET_NAMESTORE_connect (cfg); GNUNET_break (NULL != nsh); expire = GNUNET_TIME_absolute_get (); - s_signature = GNUNET_NAMESTORE_create_signature(privkey, rd.expiration, s_name, &rd, 1); + et.abs_value = rd.expiration_time; + s_signature = GNUNET_NAMESTORE_create_signature(privkey, et, s_name, &rd, 1); GNUNET_NAMESTORE_record_put(nsh, &pubkey, s_name, expire, 1, &rd, s_signature, put_cont, NULL); GNUNET_free ((void *) rd.data); } -static int -check () -{ - static char *const argv[] = { "test-namestore-api", - "-c", - "test_namestore_api.conf", -#if VERBOSE - "-L", "DEBUG", -#endif - NULL - }; - static struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - res = 1; - GNUNET_PROGRAM_run ((sizeof (argv) / sizeof (char *)) - 1, argv, "test-namestore-api", - "nohelp", options, &run, &res); - return res; -} int main (int argc, char *argv[]) { - int ret; - - ret = check (); - return ret; + res = 1; + if (0 != + GNUNET_TESTING_service_run ("test-namestore-api-zone-to-name", + "namestore", + "test_namestore_api.conf", + &run, + NULL)) + return 1; + return res; } -/* end of test_namestore_api.c */ +/* end of test_namestore_api_zone_to_name.c */ diff --git a/src/namestore/test_namestore_record_serialization.c b/src/namestore/test_namestore_record_serialization.c index 5e95253..7b7cc8b 100644 --- a/src/namestore/test_namestore_record_serialization.c +++ b/src/namestore/test_namestore_record_serialization.c @@ -26,12 +26,11 @@ #include "gnunet_namestore_service.h" #include "namestore.h" -#define VERBOSE GNUNET_NO - -#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 10) +#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 100) static int res; + static void run (void *cls, char *const *args, const char *cfgfile, const struct GNUNET_CONFIGURATION_Handle *cfg) @@ -78,7 +77,7 @@ run (void *cls, char *const *args, const char *cfgfile, GNUNET_break (0); res = 1; } - if (0 != GNUNET_TIME_absolute_get_difference(src[c].expiration, dst[c].expiration).rel_value) + if (src[c].expiration_time != dst[c].expiration_time) { GNUNET_break (0); res = 1; @@ -128,9 +127,6 @@ check () static char *const argv[] = { "test_namestore_record_serialization", "-c", "test_namestore_api.conf", -#if VERBOSE - "-L", "DEBUG", -#endif NULL }; static struct GNUNET_GETOPT_CommandLineOption options[] = { diff --git a/src/namestore/test_plugin_namestore.c b/src/namestore/test_plugin_namestore.c index 3e93d73..ea0bc78 100644 --- a/src/namestore/test_plugin_namestore.c +++ b/src/namestore/test_plugin_namestore.c @@ -25,8 +25,8 @@ #include "platform.h" #include "gnunet_util_lib.h" #include "gnunet_namestore_plugin.h" +#include "gnunet_testing_lib.h" -#define VERBOSE GNUNET_NO #define ASSERT(x) do { if (! (x)) { printf("Error at %s:%d\n", __FILE__, __LINE__); goto FAILURE;} } while (0) @@ -154,7 +154,7 @@ put_record (struct GNUNET_NAMESTORE_PluginFunctions *nsp, int id) { rd[i].data = "Hello World"; rd[i].data_size = id % 10; - rd[i].expiration = GNUNET_TIME_relative_to_absolute (GNUNET_TIME_UNIT_MINUTES); + rd[i].expiration_time = GNUNET_TIME_relative_to_absolute (GNUNET_TIME_UNIT_MINUTES).abs_value; rd[i].record_type = 1 + (id % 13); rd[i].flags = (id % 7); } @@ -187,32 +187,24 @@ run (void *cls, char *const *args, const char *cfgfile, "Failed to initialize namestore. Database likely not setup, skipping test.\n"); return; } - put_record (nsp, 1); - get_record (nsp, 1); memset (&zone_key, 1, sizeof (zone_key)); GNUNET_CRYPTO_short_hash (&zone_key, sizeof (zone_key), &zone); nsp->delete_zone (nsp->cls, &zone); unload_plugin (nsp); - } int main (int argc, char *argv[]) { - char *pos; char cfg_name[128]; - char *const xargv[] = { "test-plugin-namestore", "-c", cfg_name, -#if VERBOSE - "-L", "DEBUG", -#endif NULL }; struct GNUNET_GETOPT_CommandLineOption options[] = { @@ -221,21 +213,9 @@ main (int argc, char *argv[]) GNUNET_DISK_directory_remove ("/tmp/gnunet-test-plugin-namestore-sqlite"); GNUNET_log_setup ("test-plugin-namestore", -#if VERBOSE - "DEBUG", -#else "WARNING", -#endif NULL); - /* determine name of plugin to use */ - plugin_name = argv[0]; - while (NULL != (pos = strstr (plugin_name, "_"))) - plugin_name = pos + 1; - if (NULL != (pos = strstr (plugin_name, "."))) - pos[0] = 0; - else - pos = (char *) plugin_name; - + plugin_name = GNUNET_TESTING_get_testname_from_underscore (argv[0]); GNUNET_snprintf (cfg_name, sizeof (cfg_name), "test_plugin_namestore_%s.conf", plugin_name); GNUNET_PROGRAM_run ((sizeof (xargv) / sizeof (char *)) - 1, xargv, diff --git a/src/namestore/test_plugin_namestore_postgres.conf b/src/namestore/test_plugin_namestore_postgres.conf new file mode 100644 index 0000000..8473857 --- /dev/null +++ b/src/namestore/test_plugin_namestore_postgres.conf @@ -0,0 +1,3 @@ +[namestore-postgres] +CONFIG = connect_timeout=10; dbname=gnunetcheck +TEMPORARY_TABLE = YES diff --git a/src/nat/Makefile.am b/src/nat/Makefile.am index ed3a154..1b57ab6 100644 --- a/src/nat/Makefile.am +++ b/src/nat/Makefile.am @@ -7,30 +7,27 @@ if MINGW NATCLIENT = gnunet-helper-nat-client-windows.c endif +libexecdir= $(pkglibdir)/libexec/ + pkgcfgdir= $(pkgdatadir)/config.d/ dist_pkgcfg_DATA = \ nat.conf - -if ENABLE_TEST_RUN - nattest = $(bindir)/gnunet-nat-server -endif - - if LINUX NATBIN = gnunet-helper-nat-server gnunet-helper-nat-client NATSERVER = gnunet-helper-nat-server.c NATCLIENT = gnunet-helper-nat-client.c install-exec-hook: - $(SUDO_BINARY) chown root:root $(bindir)/gnunet-helper-nat-server $(bindir)/gnunet-helper-nat-client $(nattest) || true - $(SUDO_BINARY) chmod u+s $(bindir)/gnunet-helper-nat-server $(bindir)/gnunet-helper-nat-client $(nattest) || true + $(top_srcdir)/src/nat/install-nat-helper.sh $(libexecdir) $(SUDO_BINARY) || true else install-exec-hook: endif bin_PROGRAMS = \ - gnunet-nat-server \ + gnunet-nat-server + +libexec_PROGRAMS = \ $(NATBIN) gnunet_nat_server_SOURCES = \ @@ -57,8 +54,9 @@ lib_LTLIBRARIES = libgnunetnat.la libgnunetnat_la_SOURCES = \ nat.c nat.h \ + nat_auto.c \ nat_test.c \ - nat_mini.c + nat_mini.c libgnunetnat_la_LIBADD = \ $(top_builddir)/src/util/libgnunetutil.la \ @@ -66,7 +64,7 @@ libgnunetnat_la_LIBADD = \ libgnunetnat_la_LDFLAGS = \ $(GN_LIB_LDFLAGS) $(WINFLAGS) \ - -version-info 0:0:0 + -version-info 1:0:1 check_PROGRAMS = \ test_nat \ diff --git a/src/nat/Makefile.in b/src/nat/Makefile.in index 1387216..2736a21 100644 --- a/src/nat/Makefile.in +++ b/src/nat/Makefile.in @@ -1,9 +1,9 @@ -# Makefile.in generated by automake 1.11.1 from Makefile.am. +# Makefile.in generated by automake 1.11.6 from Makefile.am. # @configure_input@ # Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, -# 2003, 2004, 2005, 2006, 2007, 2008, 2009 Free Software Foundation, -# Inc. +# 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Free Software +# Foundation, Inc. # This Makefile.in is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. @@ -18,6 +18,23 @@ VPATH = @srcdir@ +am__make_dryrun = \ + { \ + am__dry=no; \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + echo 'am--echo: ; @echo "AM" OK' | $(MAKE) -f - 2>/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } pkgdatadir = $(datadir)/@PACKAGE@ pkgincludedir = $(includedir)/@PACKAGE@ pkglibdir = $(libdir)/@PACKAGE@ @@ -37,7 +54,8 @@ POST_UNINSTALL = : build_triplet = @build@ host_triplet = @host@ target_triplet = @target@ -bin_PROGRAMS = gnunet-nat-server$(EXEEXT) $(am__EXEEXT_1) +bin_PROGRAMS = gnunet-nat-server$(EXEEXT) +libexec_PROGRAMS = $(am__EXEEXT_1) check_PROGRAMS = test_nat$(EXEEXT) test_nat_mini$(EXEEXT) \ test_nat_test$(EXEEXT) subdir = src/nat @@ -46,14 +64,15 @@ DIST_COMMON = $(dist_pkgcfg_DATA) $(srcdir)/Makefile.am \ ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 am__aclocal_m4_deps = $(top_srcdir)/m4/absolute-header.m4 \ $(top_srcdir)/m4/align.m4 $(top_srcdir)/m4/argz.m4 \ - $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/iconv.m4 \ - $(top_srcdir)/m4/lib-ld.m4 $(top_srcdir)/m4/lib-link.m4 \ - $(top_srcdir)/m4/lib-prefix.m4 $(top_srcdir)/m4/libcurl.m4 \ - $(top_srcdir)/m4/libgcrypt.m4 $(top_srcdir)/m4/libtool.m4 \ - $(top_srcdir)/m4/libunistring.m4 $(top_srcdir)/m4/ltdl.m4 \ - $(top_srcdir)/m4/ltoptions.m4 $(top_srcdir)/m4/ltsugar.m4 \ - $(top_srcdir)/m4/ltversion.m4 $(top_srcdir)/m4/lt~obsolete.m4 \ - $(top_srcdir)/m4/nls.m4 $(top_srcdir)/m4/po.m4 \ + $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/glib-2.0.m4 \ + $(top_srcdir)/m4/iconv.m4 $(top_srcdir)/m4/lib-ld.m4 \ + $(top_srcdir)/m4/lib-link.m4 $(top_srcdir)/m4/lib-prefix.m4 \ + $(top_srcdir)/m4/libcurl.m4 $(top_srcdir)/m4/libgcrypt.m4 \ + $(top_srcdir)/m4/libtool.m4 $(top_srcdir)/m4/libunistring.m4 \ + $(top_srcdir)/m4/ltdl.m4 $(top_srcdir)/m4/ltoptions.m4 \ + $(top_srcdir)/m4/ltsugar.m4 $(top_srcdir)/m4/ltversion.m4 \ + $(top_srcdir)/m4/lt~obsolete.m4 $(top_srcdir)/m4/nls.m4 \ + $(top_srcdir)/m4/pkg.m4 $(top_srcdir)/m4/po.m4 \ $(top_srcdir)/m4/progtest.m4 $(top_srcdir)/acinclude.m4 \ $(top_srcdir)/configure.ac am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ @@ -83,17 +102,24 @@ am__nobase_list = $(am__nobase_strip_setup); \ am__base_list = \ sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \ sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g' +am__uninstall_files_from_dir = { \ + test -z "$$files" \ + || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \ + || { echo " ( cd '$$dir' && rm -f" $$files ")"; \ + $(am__cd) "$$dir" && rm -f $$files; }; \ + } am__installdirs = "$(DESTDIR)$(libdir)" "$(DESTDIR)$(bindir)" \ - "$(DESTDIR)$(pkgcfgdir)" + "$(DESTDIR)$(libexecdir)" "$(DESTDIR)$(pkgcfgdir)" LTLIBRARIES = $(lib_LTLIBRARIES) am__DEPENDENCIES_1 = libgnunetnat_la_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la \ $(am__DEPENDENCIES_1) -am_libgnunetnat_la_OBJECTS = nat.lo nat_test.lo nat_mini.lo +am_libgnunetnat_la_OBJECTS = nat.lo nat_auto.lo nat_test.lo \ + nat_mini.lo libgnunetnat_la_OBJECTS = $(am_libgnunetnat_la_OBJECTS) -AM_V_lt = $(am__v_lt_$(V)) -am__v_lt_ = $(am__v_lt_$(AM_DEFAULT_VERBOSITY)) +AM_V_lt = $(am__v_lt_@AM_V@) +am__v_lt_ = $(am__v_lt_@AM_DEFAULT_V@) am__v_lt_0 = --silent libgnunetnat_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ @@ -104,7 +130,7 @@ libgnunetnat_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ @LINUX_FALSE@@MINGW_TRUE@ gnunet-helper-nat-client$(EXEEXT) @LINUX_TRUE@am__EXEEXT_1 = gnunet-helper-nat-server$(EXEEXT) \ @LINUX_TRUE@ gnunet-helper-nat-client$(EXEEXT) -PROGRAMS = $(bin_PROGRAMS) +PROGRAMS = $(bin_PROGRAMS) $(libexec_PROGRAMS) am__gnunet_helper_nat_client_SOURCES_DIST = \ gnunet-helper-nat-client.c gnunet-helper-nat-client-windows.c @LINUX_FALSE@@MINGW_TRUE@am__objects_1 = gnunet-helper-nat-client-windows.$(OBJEXT) @@ -145,21 +171,21 @@ LTCOMPILE = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) \ $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) \ $(AM_CFLAGS) $(CFLAGS) -AM_V_CC = $(am__v_CC_$(V)) -am__v_CC_ = $(am__v_CC_$(AM_DEFAULT_VERBOSITY)) +AM_V_CC = $(am__v_CC_@AM_V@) +am__v_CC_ = $(am__v_CC_@AM_DEFAULT_V@) am__v_CC_0 = @echo " CC " $@; -AM_V_at = $(am__v_at_$(V)) -am__v_at_ = $(am__v_at_$(AM_DEFAULT_VERBOSITY)) +AM_V_at = $(am__v_at_@AM_V@) +am__v_at_ = $(am__v_at_@AM_DEFAULT_V@) am__v_at_0 = @ CCLD = $(CC) LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ $(AM_LDFLAGS) $(LDFLAGS) -o $@ -AM_V_CCLD = $(am__v_CCLD_$(V)) -am__v_CCLD_ = $(am__v_CCLD_$(AM_DEFAULT_VERBOSITY)) +AM_V_CCLD = $(am__v_CCLD_@AM_V@) +am__v_CCLD_ = $(am__v_CCLD_@AM_DEFAULT_V@) am__v_CCLD_0 = @echo " CCLD " $@; -AM_V_GEN = $(am__v_GEN_$(V)) -am__v_GEN_ = $(am__v_GEN_$(AM_DEFAULT_VERBOSITY)) +AM_V_GEN = $(am__v_GEN_@AM_V@) +am__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@) am__v_GEN_0 = @echo " GEN " $@; SOURCES = $(libgnunetnat_la_SOURCES) \ $(gnunet_helper_nat_client_SOURCES) \ @@ -171,6 +197,11 @@ DIST_SOURCES = $(libgnunetnat_la_SOURCES) \ $(am__gnunet_helper_nat_server_SOURCES_DIST) \ $(gnunet_nat_server_SOURCES) $(test_nat_SOURCES) \ $(test_nat_mini_SOURCES) $(test_nat_test_SOURCES) +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac DATA = $(dist_pkgcfg_DATA) ETAGS = etags CTAGS = ctags @@ -212,6 +243,10 @@ EXEEXT = @EXEEXT@ EXT_LIBS = @EXT_LIBS@ EXT_LIB_PATH = @EXT_LIB_PATH@ FGREP = @FGREP@ +GLIB_CFLAGS = @GLIB_CFLAGS@ +GLIB_GENMARSHAL = @GLIB_GENMARSHAL@ +GLIB_LIBS = @GLIB_LIBS@ +GLIB_MKENUMS = @GLIB_MKENUMS@ GMSGFMT = @GMSGFMT@ GMSGFMT_015 = @GMSGFMT_015@ GNUNETDNS_GROUP = @GNUNETDNS_GROUP@ @@ -222,6 +257,7 @@ GN_LIBINTL = @GN_LIBINTL@ GN_LIB_LDFLAGS = @GN_LIB_LDFLAGS@ GN_PLUGIN_LDFLAGS = @GN_PLUGIN_LDFLAGS@ GN_USER_HOME_DIR = @GN_USER_HOME_DIR@ +GOBJECT_QUERY = @GOBJECT_QUERY@ GREP = @GREP@ HAVE_LIBUNISTRING = @HAVE_LIBUNISTRING@ INCLTDL = @INCLTDL@ @@ -244,6 +280,8 @@ LIBCURL_CPPFLAGS = @LIBCURL_CPPFLAGS@ LIBGCRYPT_CFLAGS = @LIBGCRYPT_CFLAGS@ LIBGCRYPT_CONFIG = @LIBGCRYPT_CONFIG@ LIBGCRYPT_LIBS = @LIBGCRYPT_LIBS@ +LIBGTOP_CFLAGS = @LIBGTOP_CFLAGS@ +LIBGTOP_LIBS = @LIBGTOP_LIBS@ LIBICONV = @LIBICONV@ LIBINTL = @LIBINTL@ LIBLTDL = @LIBLTDL@ @@ -265,6 +303,7 @@ LT_CONFIG_H = @LT_CONFIG_H@ LT_DLLOADERS = @LT_DLLOADERS@ LT_DLPREOPEN = @LT_DLPREOPEN@ MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ MKDIR_P = @MKDIR_P@ MONKEYPREFIX = @MONKEYPREFIX@ MSGFMT = @MSGFMT@ @@ -274,6 +313,7 @@ MYSQL_CPPFLAGS = @MYSQL_CPPFLAGS@ MYSQL_LDFLAGS = @MYSQL_LDFLAGS@ NM = @NM@ NMEDIT = @NMEDIT@ +NSS_DIR = @NSS_DIR@ OBJC = @OBJC@ OBJCDEPMODE = @OBJCDEPMODE@ OBJCFLAGS = @OBJCFLAGS@ @@ -289,6 +329,7 @@ PACKAGE_TARNAME = @PACKAGE_TARNAME@ PACKAGE_URL = @PACKAGE_URL@ PACKAGE_VERSION = @PACKAGE_VERSION@ PATH_SEPARATOR = @PATH_SEPARATOR@ +PKG_CONFIG = @PKG_CONFIG@ POSTGRES_CPPFLAGS = @POSTGRES_CPPFLAGS@ POSTGRES_LDFLAGS = @POSTGRES_LDFLAGS@ POSUB = @POSUB@ @@ -320,6 +361,7 @@ abs_builddir = @abs_builddir@ abs_srcdir = @abs_srcdir@ abs_top_builddir = @abs_top_builddir@ abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ ac_ct_CC = @ac_ct_CC@ ac_ct_CXX = @ac_ct_CXX@ ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ @@ -342,6 +384,7 @@ datarootdir = @datarootdir@ docdir = @docdir@ dvidir = @dvidir@ exec_prefix = @exec_prefix@ +gitcommand = @gitcommand@ host = @host@ host_alias = @host_alias@ host_cpu = @host_cpu@ @@ -352,10 +395,9 @@ includedir = @includedir@ infodir = @infodir@ install_sh = @install_sh@ libdir = @libdir@ -libexecdir = @libexecdir@ +libexecdir = $(pkglibdir)/libexec/ localedir = @localedir@ localstatedir = @localstatedir@ -lt_ECHO = @lt_ECHO@ ltdl_LIBOBJS = @ltdl_LIBOBJS@ ltdl_LTLIBOBJS = @ltdl_LTLIBOBJS@ mandir = @mandir@ @@ -373,6 +415,7 @@ sbindir = @sbindir@ sharedstatedir = @sharedstatedir@ srcdir = @srcdir@ subdirs = @subdirs@ +svnversioncommand = @svnversioncommand@ sys_symbol_underscore = @sys_symbol_underscore@ sysconfdir = @sysconfdir@ target = @target@ @@ -395,7 +438,6 @@ pkgcfgdir = $(pkgdatadir)/config.d/ dist_pkgcfg_DATA = \ nat.conf -@ENABLE_TEST_RUN_TRUE@nattest = $(bindir)/gnunet-nat-server gnunet_nat_server_SOURCES = \ gnunet-nat-server.c nat.h @@ -416,8 +458,9 @@ gnunet_helper_nat_client_SOURCES = \ lib_LTLIBRARIES = libgnunetnat.la libgnunetnat_la_SOURCES = \ nat.c nat.h \ + nat_auto.c \ nat_test.c \ - nat_mini.c + nat_mini.c libgnunetnat_la_LIBADD = \ $(top_builddir)/src/util/libgnunetutil.la \ @@ -425,7 +468,7 @@ libgnunetnat_la_LIBADD = \ libgnunetnat_la_LDFLAGS = \ $(GN_LIB_LDFLAGS) $(WINFLAGS) \ - -version-info 0:0:0 + -version-info 1:0:1 @ENABLE_TEST_RUN_TRUE@TESTS = $(check_PROGRAMS) test_nat_SOURCES = \ @@ -489,7 +532,6 @@ $(ACLOCAL_M4): $(am__aclocal_m4_deps) $(am__aclocal_m4_deps): install-libLTLIBRARIES: $(lib_LTLIBRARIES) @$(NORMAL_INSTALL) - test -z "$(libdir)" || $(MKDIR_P) "$(DESTDIR)$(libdir)" @list='$(lib_LTLIBRARIES)'; test -n "$(libdir)" || list=; \ list2=; for p in $$list; do \ if test -f $$p; then \ @@ -497,6 +539,8 @@ install-libLTLIBRARIES: $(lib_LTLIBRARIES) else :; fi; \ done; \ test -z "$$list2" || { \ + echo " $(MKDIR_P) '$(DESTDIR)$(libdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libdir)" || exit 1; \ echo " $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 '$(DESTDIR)$(libdir)'"; \ $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 "$(DESTDIR)$(libdir)"; \ } @@ -518,12 +562,15 @@ clean-libLTLIBRARIES: echo "rm -f \"$${dir}/so_locations\""; \ rm -f "$${dir}/so_locations"; \ done -libgnunetnat.la: $(libgnunetnat_la_OBJECTS) $(libgnunetnat_la_DEPENDENCIES) +libgnunetnat.la: $(libgnunetnat_la_OBJECTS) $(libgnunetnat_la_DEPENDENCIES) $(EXTRA_libgnunetnat_la_DEPENDENCIES) $(AM_V_CCLD)$(libgnunetnat_la_LINK) -rpath $(libdir) $(libgnunetnat_la_OBJECTS) $(libgnunetnat_la_LIBADD) $(LIBS) install-binPROGRAMS: $(bin_PROGRAMS) @$(NORMAL_INSTALL) - test -z "$(bindir)" || $(MKDIR_P) "$(DESTDIR)$(bindir)" @list='$(bin_PROGRAMS)'; test -n "$(bindir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(bindir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(bindir)" || exit 1; \ + fi; \ for p in $$list; do echo "$$p $$p"; done | \ sed 's/$(EXEEXT)$$//' | \ while read p p1; do if test -f $$p || test -f $$p1; \ @@ -572,22 +619,68 @@ clean-checkPROGRAMS: list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ echo " rm -f" $$list; \ rm -f $$list -gnunet-helper-nat-client$(EXEEXT): $(gnunet_helper_nat_client_OBJECTS) $(gnunet_helper_nat_client_DEPENDENCIES) +install-libexecPROGRAMS: $(libexec_PROGRAMS) + @$(NORMAL_INSTALL) + @list='$(libexec_PROGRAMS)'; test -n "$(libexecdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(libexecdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libexecdir)" || exit 1; \ + fi; \ + for p in $$list; do echo "$$p $$p"; done | \ + sed 's/$(EXEEXT)$$//' | \ + while read p p1; do if test -f $$p || test -f $$p1; \ + then echo "$$p"; echo "$$p"; else :; fi; \ + done | \ + sed -e 'p;s,.*/,,;n;h' -e 's|.*|.|' \ + -e 'p;x;s,.*/,,;s/$(EXEEXT)$$//;$(transform);s/$$/$(EXEEXT)/' | \ + sed 'N;N;N;s,\n, ,g' | \ + $(AWK) 'BEGIN { files["."] = ""; dirs["."] = 1 } \ + { d=$$3; if (dirs[d] != 1) { print "d", d; dirs[d] = 1 } \ + if ($$2 == $$4) files[d] = files[d] " " $$1; \ + else { print "f", $$3 "/" $$4, $$1; } } \ + END { for (d in files) print "f", d, files[d] }' | \ + while read type dir files; do \ + if test "$$dir" = .; then dir=; else dir=/$$dir; fi; \ + test -z "$$files" || { \ + echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files '$(DESTDIR)$(libexecdir)$$dir'"; \ + $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files "$(DESTDIR)$(libexecdir)$$dir" || exit $$?; \ + } \ + ; done + +uninstall-libexecPROGRAMS: + @$(NORMAL_UNINSTALL) + @list='$(libexec_PROGRAMS)'; test -n "$(libexecdir)" || list=; \ + files=`for p in $$list; do echo "$$p"; done | \ + sed -e 'h;s,^.*/,,;s/$(EXEEXT)$$//;$(transform)' \ + -e 's/$$/$(EXEEXT)/' `; \ + test -n "$$list" || exit 0; \ + echo " ( cd '$(DESTDIR)$(libexecdir)' && rm -f" $$files ")"; \ + cd "$(DESTDIR)$(libexecdir)" && rm -f $$files + +clean-libexecPROGRAMS: + @list='$(libexec_PROGRAMS)'; test -n "$$list" || exit 0; \ + echo " rm -f" $$list; \ + rm -f $$list || exit $$?; \ + test -n "$(EXEEXT)" || exit 0; \ + list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ + echo " rm -f" $$list; \ + rm -f $$list +gnunet-helper-nat-client$(EXEEXT): $(gnunet_helper_nat_client_OBJECTS) $(gnunet_helper_nat_client_DEPENDENCIES) $(EXTRA_gnunet_helper_nat_client_DEPENDENCIES) @rm -f gnunet-helper-nat-client$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_helper_nat_client_OBJECTS) $(gnunet_helper_nat_client_LDADD) $(LIBS) -gnunet-helper-nat-server$(EXEEXT): $(gnunet_helper_nat_server_OBJECTS) $(gnunet_helper_nat_server_DEPENDENCIES) +gnunet-helper-nat-server$(EXEEXT): $(gnunet_helper_nat_server_OBJECTS) $(gnunet_helper_nat_server_DEPENDENCIES) $(EXTRA_gnunet_helper_nat_server_DEPENDENCIES) @rm -f gnunet-helper-nat-server$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_helper_nat_server_OBJECTS) $(gnunet_helper_nat_server_LDADD) $(LIBS) -gnunet-nat-server$(EXEEXT): $(gnunet_nat_server_OBJECTS) $(gnunet_nat_server_DEPENDENCIES) +gnunet-nat-server$(EXEEXT): $(gnunet_nat_server_OBJECTS) $(gnunet_nat_server_DEPENDENCIES) $(EXTRA_gnunet_nat_server_DEPENDENCIES) @rm -f gnunet-nat-server$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_nat_server_OBJECTS) $(gnunet_nat_server_LDADD) $(LIBS) -test_nat$(EXEEXT): $(test_nat_OBJECTS) $(test_nat_DEPENDENCIES) +test_nat$(EXEEXT): $(test_nat_OBJECTS) $(test_nat_DEPENDENCIES) $(EXTRA_test_nat_DEPENDENCIES) @rm -f test_nat$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_nat_OBJECTS) $(test_nat_LDADD) $(LIBS) -test_nat_mini$(EXEEXT): $(test_nat_mini_OBJECTS) $(test_nat_mini_DEPENDENCIES) +test_nat_mini$(EXEEXT): $(test_nat_mini_OBJECTS) $(test_nat_mini_DEPENDENCIES) $(EXTRA_test_nat_mini_DEPENDENCIES) @rm -f test_nat_mini$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_nat_mini_OBJECTS) $(test_nat_mini_LDADD) $(LIBS) -test_nat_test$(EXEEXT): $(test_nat_test_OBJECTS) $(test_nat_test_DEPENDENCIES) +test_nat_test$(EXEEXT): $(test_nat_test_OBJECTS) $(test_nat_test_DEPENDENCIES) $(EXTRA_test_nat_test_DEPENDENCIES) @rm -f test_nat_test$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_nat_test_OBJECTS) $(test_nat_test_LDADD) $(LIBS) @@ -603,6 +696,7 @@ distclean-compile: @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-helper-nat-server.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-nat-server.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/nat.Plo@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/nat_auto.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/nat_mini.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/nat_test.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_nat.Po@am__quote@ @@ -612,26 +706,23 @@ distclean-compile: .c.o: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c $< .c.obj: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'` @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c `$(CYGPATH_W) '$<'` +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c `$(CYGPATH_W) '$<'` .c.lo: @am__fastdepCC_TRUE@ $(AM_V_CC)$(LTCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LTCOMPILE) -c -o $@ $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LTCOMPILE) -c -o $@ $< mostlyclean-libtool: -rm -f *.lo @@ -640,8 +731,11 @@ clean-libtool: -rm -rf .libs _libs install-dist_pkgcfgDATA: $(dist_pkgcfg_DATA) @$(NORMAL_INSTALL) - test -z "$(pkgcfgdir)" || $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" @list='$(dist_pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(pkgcfgdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" || exit 1; \ + fi; \ for p in $$list; do \ if test -f "$$p"; then d=; else d="$(srcdir)/"; fi; \ echo "$$d$$p"; \ @@ -655,9 +749,7 @@ uninstall-dist_pkgcfgDATA: @$(NORMAL_UNINSTALL) @list='$(dist_pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ files=`for p in $$list; do echo $$p; done | sed -e 's|^.*/||'`; \ - test -n "$$files" || exit 0; \ - echo " ( cd '$(DESTDIR)$(pkgcfgdir)' && rm -f" $$files ")"; \ - cd "$(DESTDIR)$(pkgcfgdir)" && rm -f $$files + dir='$(DESTDIR)$(pkgcfgdir)'; $(am__uninstall_files_from_dir) ID: $(HEADERS) $(SOURCES) $(LISP) $(TAGS_FILES) list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ @@ -792,14 +884,15 @@ check-TESTS: $(TESTS) fi; \ dashes=`echo "$$dashes" | sed s/./=/g`; \ if test "$$failed" -eq 0; then \ - echo "$$grn$$dashes"; \ + col="$$grn"; \ else \ - echo "$$red$$dashes"; \ + col="$$red"; \ fi; \ - echo "$$banner"; \ - test -z "$$skipped" || echo "$$skipped"; \ - test -z "$$report" || echo "$$report"; \ - echo "$$dashes$$std"; \ + echo "$${col}$$dashes$${std}"; \ + echo "$${col}$$banner$${std}"; \ + test -z "$$skipped" || echo "$${col}$$skipped$${std}"; \ + test -z "$$report" || echo "$${col}$$report$${std}"; \ + echo "$${col}$$dashes$${std}"; \ test "$$failed" -eq 0; \ else :; fi @@ -841,7 +934,7 @@ all-am: Makefile $(LTLIBRARIES) $(PROGRAMS) $(DATA) install-binPROGRAMS: install-libLTLIBRARIES installdirs: - for dir in "$(DESTDIR)$(libdir)" "$(DESTDIR)$(bindir)" "$(DESTDIR)$(pkgcfgdir)"; do \ + for dir in "$(DESTDIR)$(libdir)" "$(DESTDIR)$(bindir)" "$(DESTDIR)$(libexecdir)" "$(DESTDIR)$(pkgcfgdir)"; do \ test -z "$$dir" || $(MKDIR_P) "$$dir"; \ done install: install-am @@ -854,10 +947,15 @@ install-am: all-am installcheck: installcheck-am install-strip: - $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ - install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ - `test -z '$(STRIP)' || \ - echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi mostlyclean-generic: clean-generic: @@ -872,7 +970,8 @@ maintainer-clean-generic: clean: clean-am clean-am: clean-binPROGRAMS clean-checkPROGRAMS clean-generic \ - clean-libLTLIBRARIES clean-libtool mostlyclean-am + clean-libLTLIBRARIES clean-libexecPROGRAMS clean-libtool \ + mostlyclean-am distclean: distclean-am -rm -rf ./$(DEPDIR) @@ -898,7 +997,8 @@ install-dvi: install-dvi-am install-dvi-am: -install-exec-am: install-binPROGRAMS install-libLTLIBRARIES +install-exec-am: install-binPROGRAMS install-libLTLIBRARIES \ + install-libexecPROGRAMS @$(NORMAL_INSTALL) $(MAKE) $(AM_MAKEFLAGS) install-exec-hook install-html: install-html-am @@ -940,30 +1040,30 @@ ps: ps-am ps-am: uninstall-am: uninstall-binPROGRAMS uninstall-dist_pkgcfgDATA \ - uninstall-libLTLIBRARIES + uninstall-libLTLIBRARIES uninstall-libexecPROGRAMS .MAKE: check-am install-am install-exec-am install-strip .PHONY: CTAGS GTAGS all all-am check check-TESTS check-am clean \ clean-binPROGRAMS clean-checkPROGRAMS clean-generic \ - clean-libLTLIBRARIES clean-libtool ctags distclean \ - distclean-compile distclean-generic distclean-libtool \ - distclean-tags distdir dvi dvi-am html html-am info info-am \ - install install-am install-binPROGRAMS install-data \ - install-data-am install-dist_pkgcfgDATA install-dvi \ - install-dvi-am install-exec install-exec-am install-exec-hook \ - install-html install-html-am install-info install-info-am \ - install-libLTLIBRARIES install-man install-pdf install-pdf-am \ - install-ps install-ps-am install-strip installcheck \ - installcheck-am installdirs maintainer-clean \ - maintainer-clean-generic mostlyclean mostlyclean-compile \ - mostlyclean-generic mostlyclean-libtool pdf pdf-am ps ps-am \ - tags uninstall uninstall-am uninstall-binPROGRAMS \ - uninstall-dist_pkgcfgDATA uninstall-libLTLIBRARIES + clean-libLTLIBRARIES clean-libexecPROGRAMS clean-libtool ctags \ + distclean distclean-compile distclean-generic \ + distclean-libtool distclean-tags distdir dvi dvi-am html \ + html-am info info-am install install-am install-binPROGRAMS \ + install-data install-data-am install-dist_pkgcfgDATA \ + install-dvi install-dvi-am install-exec install-exec-am \ + install-exec-hook install-html install-html-am install-info \ + install-info-am install-libLTLIBRARIES install-libexecPROGRAMS \ + install-man install-pdf install-pdf-am install-ps \ + install-ps-am install-strip installcheck installcheck-am \ + installdirs maintainer-clean maintainer-clean-generic \ + mostlyclean mostlyclean-compile mostlyclean-generic \ + mostlyclean-libtool pdf pdf-am ps ps-am tags uninstall \ + uninstall-am uninstall-binPROGRAMS uninstall-dist_pkgcfgDATA \ + uninstall-libLTLIBRARIES uninstall-libexecPROGRAMS @LINUX_TRUE@install-exec-hook: -@LINUX_TRUE@ $(SUDO_BINARY) chown root:root $(bindir)/gnunet-helper-nat-server $(bindir)/gnunet-helper-nat-client $(nattest) || true -@LINUX_TRUE@ $(SUDO_BINARY) chmod u+s $(bindir)/gnunet-helper-nat-server $(bindir)/gnunet-helper-nat-client $(nattest) || true +@LINUX_TRUE@ $(top_srcdir)/src/nat/install-nat-helper.sh $(libexecdir) $(SUDO_BINARY) || true @LINUX_FALSE@install-exec-hook: # Tell versions [3.59,3.63) of GNU make to not export all variables. diff --git a/src/nat/gnunet-nat-server.c b/src/nat/gnunet-nat-server.c index 9b6846c..1a98cdc 100644 --- a/src/nat/gnunet-nat-server.c +++ b/src/nat/gnunet-nat-server.c @@ -313,11 +313,18 @@ main (int argc, char *const argv[]) GNUNET_GETOPT_OPTION_END }; + if (GNUNET_OK != GNUNET_STRINGS_get_utf8_args (argc, argv, &argc, &argv)) + return 2; + if (GNUNET_OK != GNUNET_PROGRAM_run (argc, argv, "gnunet-nat-server [options] PORT", _("GNUnet NAT traversal test helper daemon"), options, &run, NULL)) + { + GNUNET_free ((void*) argv); return 1; + } + GNUNET_free ((void*) argv); return 0; } diff --git a/src/nat/nat.c b/src/nat/nat.c index 79604da..dd63224 100644 --- a/src/nat/nat.c +++ b/src/nat/nat.c @@ -759,11 +759,7 @@ nat_server_read (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) h->server_stdout = NULL; h->server_stdout_handle = NULL; /* now try to restart it */ - h->server_retry_delay = - GNUNET_TIME_relative_multiply (h->server_retry_delay, 2); - h->server_retry_delay = - GNUNET_TIME_relative_max (GNUNET_TIME_UNIT_HOURS, - h->server_retry_delay); + h->server_retry_delay = GNUNET_TIME_STD_BACKOFF (h->server_retry_delay); h->server_read_task = GNUNET_SCHEDULER_add_delayed (h->server_retry_delay, &restart_nat_server, h); @@ -825,6 +821,8 @@ nat_server_read (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) static void start_gnunet_nat_server (struct GNUNET_NAT_Handle *h) { + char *binary; + if ((h->behind_nat == GNUNET_YES) && (h->enable_nat_server == GNUNET_YES) && (h->internal_address != NULL) && (NULL != @@ -834,11 +832,13 @@ start_gnunet_nat_server (struct GNUNET_NAT_Handle *h) LOG (GNUNET_ERROR_TYPE_DEBUG, "Starting `%s' at `%s'\n", "gnunet-helper-nat-server", h->internal_address); /* Start the server process */ + binary = GNUNET_OS_get_libexec_binary_path ("gnunet-helper-nat-server"); h->server_proc = - GNUNET_OS_start_process (GNUNET_NO, NULL, h->server_stdout, - "gnunet-helper-nat-server", + GNUNET_OS_start_process (GNUNET_NO, 0, NULL, h->server_stdout, + binary, "gnunet-helper-nat-server", h->internal_address, NULL); + GNUNET_free (binary); if (h->server_proc == NULL) { LOG (GNUNET_ERROR_TYPE_WARNING, "nat", _("Failed to start %s\n"), @@ -1070,6 +1070,7 @@ GNUNET_NAT_register (const struct GNUNET_CONFIGURATION_Handle *cfg, int is_tcp, struct GNUNET_NAT_Handle *h; struct in_addr in_addr; unsigned int i; + char *binary; LOG (GNUNET_ERROR_TYPE_DEBUG, "Registered with NAT service at port %u with %u IP bound local addresses\n", @@ -1107,9 +1108,9 @@ GNUNET_NAT_register (const struct GNUNET_CONFIGURATION_Handle *cfg, int is_tcp, if ((h->internal_address != NULL) && (inet_pton (AF_INET, h->internal_address, &in_addr) != 1)) { - LOG (GNUNET_ERROR_TYPE_WARNING, "nat", - _("Malformed %s `%s' given in configuration!\n"), "INTERNAL_ADDRESS", - h->internal_address); + GNUNET_log_config_invalid (GNUNET_ERROR_TYPE_WARNING, + "nat", "INTERNAL_ADDRESS", + _("malformed")); GNUNET_free (h->internal_address); h->internal_address = NULL; } @@ -1167,9 +1168,10 @@ GNUNET_NAT_register (const struct GNUNET_CONFIGURATION_Handle *cfg, int is_tcp, } /* Test for SUID binaries */ + binary = GNUNET_OS_get_libexec_binary_path ("gnunet-helper-nat-server"); if ((h->behind_nat == GNUNET_YES) && (GNUNET_YES == h->enable_nat_server) && (GNUNET_YES != - GNUNET_OS_check_helper_binary ("gnunet-helper-nat-server"))) + GNUNET_OS_check_helper_binary (binary))) { h->enable_nat_server = GNUNET_NO; LOG (GNUNET_ERROR_TYPE_WARNING, @@ -1177,9 +1179,11 @@ GNUNET_NAT_register (const struct GNUNET_CONFIGURATION_Handle *cfg, int is_tcp, ("Configuration requires `%s', but binary is not installed properly (SUID bit not set). Option disabled.\n"), "gnunet-helper-nat-server"); } + GNUNET_free (binary); + binary = GNUNET_OS_get_libexec_binary_path ("gnunet-helper-nat-client"); if ((GNUNET_YES == h->enable_nat_client) && (GNUNET_YES != - GNUNET_OS_check_helper_binary ("gnunet-helper-nat-client"))) + GNUNET_OS_check_helper_binary (binary))) { h->enable_nat_client = GNUNET_NO; LOG (GNUNET_ERROR_TYPE_WARNING, @@ -1187,7 +1191,7 @@ GNUNET_NAT_register (const struct GNUNET_CONFIGURATION_Handle *cfg, int is_tcp, ("Configuration requires `%s', but binary is not installed properly (SUID bit not set). Option disabled.\n"), "gnunet-helper-nat-client"); } - + GNUNET_free (binary); start_gnunet_nat_server (h); /* FIXME: add support for UPnP, etc */ @@ -1310,6 +1314,7 @@ GNUNET_NAT_run_client (struct GNUNET_NAT_Handle *h, char inet4[INET_ADDRSTRLEN]; char port_as_string[6]; struct GNUNET_OS_Process *proc; + char *binary; if (GNUNET_YES != h->enable_nat_client) return GNUNET_NO; /* not permitted / possible */ @@ -1331,11 +1336,13 @@ GNUNET_NAT_run_client (struct GNUNET_NAT_Handle *h, LOG (GNUNET_ERROR_TYPE_DEBUG, _("Running gnunet-helper-nat-client %s %s %u\n"), h->internal_address, inet4, (unsigned int) h->adv_port); + binary = GNUNET_OS_get_libexec_binary_path ("gnunet-helper-nat-client"); proc = - GNUNET_OS_start_process (GNUNET_NO, - NULL, NULL, "gnunet-helper-nat-client", + GNUNET_OS_start_process (GNUNET_NO, 0, NULL, NULL, + binary, "gnunet-helper-nat-client", h->internal_address, inet4, port_as_string, NULL); + GNUNET_free (binary); if (NULL == proc) return GNUNET_SYSERR; /* we know that the gnunet-helper-nat-client will terminate virtually diff --git a/src/nat/nat_auto.c b/src/nat/nat_auto.c new file mode 100644 index 0000000..baa1cc7 --- /dev/null +++ b/src/nat/nat_auto.c @@ -0,0 +1,584 @@ +/* + This file is part of GNUnet. + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @file nat/nat_auto.c + * @brief functions for auto-configuration of the network + * @author Christian Grothoff + */ +#include "platform.h" +#include "gnunet_util_lib.h" +#include "gnunet_resolver_service.h" +#include "gnunet_nat_lib.h" +#include "nat.h" + +#define LOG(kind,...) GNUNET_log_from (kind, "nat", __VA_ARGS__) + + +/** + * How long do we wait for the NAT test to report success? + */ +#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 15) + +/** + * Phases of the auto configuration. + */ +enum AutoPhase +{ + /** + * Initial start value. + */ + AUTO_INIT = 0, + + /** + * Test if we are online. + */ + AUTO_ONLINE, + + /** + * Test our external IP. + */ + AUTO_EXTERNAL_IP, + + /** + * Test our internal IP. + */ + AUTO_LOCAL_IP, + + /** + * Test if NAT was punched. + */ + AUTO_NAT_PUNCHED, + + /** + * Test if UPnP is working. + */ + AUTO_UPNPC, + + /** + * Test if ICMP server works. + */ + AUTO_ICMP_SERVER, + + /** + * Test if ICMP client works. + */ + AUTO_ICMP_CLIENT, + + /** + * Last phase, we're done. + */ + AUTO_DONE + +}; + + +/** + * Handle to auto-configuration in progress. + */ +struct GNUNET_NAT_AutoHandle +{ + + /** + * Handle to the active NAT test. + */ + struct GNUNET_NAT_Test *tst; + + /** + * Function to call when done. + */ + GNUNET_NAT_AutoResultCallback fin_cb; + + /** + * Closure for 'fin_cb'. + */ + void *fin_cb_cls; + + /** + * Handle for active 'GNUNET_NAT_mini_get_external_ipv4'-operation. + */ + struct GNUNET_NAT_ExternalHandle *eh; + + /** + * Current configuration (with updates from previous phases) + */ + struct GNUNET_CONFIGURATION_Handle *cfg; + + /** + * Original configuration (used to calculate differences) + */ + struct GNUNET_CONFIGURATION_Handle *initial_cfg; + + /** + * Task identifier for the timeout. + */ + GNUNET_SCHEDULER_TaskIdentifier task; + + /** + * Where are we in the test? + */ + enum AutoPhase phase; + + /** + * Do we have IPv6? + */ + int have_v6; + +}; + + +/** + * Run the next phase of the auto test. + * + * @param ah auto test handle + */ +static void +next_phase (struct GNUNET_NAT_AutoHandle *ah); + + +/** + * Function called if NAT failed to confirm success. + * Clean up and update GUI (with failure). + * + * @param cls closure with setup context + * @param tc scheduler callback + */ +static void +fail_timeout (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct GNUNET_NAT_AutoHandle *ah = cls; + + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + _("NAT traversal with ICMP Server timed out.\n")); + GNUNET_assert (NULL != ah->tst); + ah->task = GNUNET_SCHEDULER_NO_TASK; + GNUNET_NAT_test_stop (ah->tst); + ah->tst = NULL; + GNUNET_CONFIGURATION_set_value_string (ah->cfg, "nat", + "ENABLE_ICMP_SERVER", + "NO"); + next_phase (ah); +} + + +/** + * Function called by NAT on success. + * Clean up and update GUI (with success). + * + * @param cls the auto handle + * @param success currently always GNUNET_OK + */ +static void +result_callback (void *cls, int success) +{ + struct GNUNET_NAT_AutoHandle *ah = cls; + + GNUNET_SCHEDULER_cancel (ah->task); + ah->task = GNUNET_SCHEDULER_NO_TASK; + GNUNET_NAT_test_stop (ah->tst); + ah->tst = NULL; + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + success + ? _("NAT traversal with ICMP Server succeeded.\n") + : _("NAT traversal with ICMP Server failed.\n")); + GNUNET_CONFIGURATION_set_value_string (ah->cfg, "nat", "ENABLE_ICMP_SERVER", + success ? "YES": "NO"); + next_phase (ah); +} + +/** + * Main function for the connection reversal test. + * + * @param cls the 'int*' for the result + * @param tc scheduler context + */ +static void +reversal_test (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct GNUNET_NAT_AutoHandle *ah = cls; + + ah->task = GNUNET_SCHEDULER_NO_TASK; + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + _("Testing connection reversal with ICMP server.\n")); + GNUNET_RESOLVER_connect (ah->cfg); + ah->tst = GNUNET_NAT_test_start (ah->cfg, GNUNET_YES, 0, 0, + &result_callback, ah); + if (NULL == ah->tst) + { + next_phase (ah); + return; + } + ah->task = GNUNET_SCHEDULER_add_delayed (TIMEOUT, &fail_timeout, ah); +} + + +/** + * Test if we are online at all. + * + * @param ah auto setup context + */ +static void +test_online (struct GNUNET_NAT_AutoHandle *ah) +{ + // FIXME: not implemented + next_phase (ah); +} + + +/** + * Set our external IPv4 address. + * + * @param cls closure with our setup context + * @param addr the address, NULL on errors + */ +static void +set_external_ipv4 (void *cls, const struct in_addr *addr) +{ + struct GNUNET_NAT_AutoHandle *ah = cls; + char buf[INET_ADDRSTRLEN]; + + ah->eh = NULL; + if (NULL == addr) + { + next_phase (ah); + return; + } + /* enable 'behind nat' */ + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + _("Detected external IP `%s'\n"), + inet_ntop (AF_INET, + addr, + buf, + sizeof (buf))); + GNUNET_CONFIGURATION_set_value_string (ah->cfg, "nat", "BEHIND_NAT", "YES"); + + /* set external IP address */ + if (NULL == inet_ntop (AF_INET, addr, buf, sizeof (buf))) + { + GNUNET_break (0); + next_phase (ah); + return; + } + GNUNET_CONFIGURATION_set_value_string (ah->cfg, "nat", "EXTERNAL_ADDRESS", + buf); + next_phase (ah); +} + + +/** + * Determine our external IPv4 address. + * + * @param ah auto setup context + */ +static void +test_external_ip (struct GNUNET_NAT_AutoHandle *ah) +{ + // FIXME: CPS? + /* try to detect external IP */ + ah->eh = GNUNET_NAT_mini_get_external_ipv4 (TIMEOUT, + &set_external_ipv4, ah); +} + + +/** + * Process list of local IP addresses. Find and set the + * one of the default interface. + * + * @param cls our NAT auto handle + * @param name name of the interface (can be NULL for unknown) + * @param isDefault is this presumably the default interface + * @param addr address of this interface (can be NULL for unknown or unassigned) + * @param broadcast_addr the broadcast address (can be NULL for unknown or unassigned) + * @param netmask the network mask (can be NULL for unknown or unassigned)) + * @param addrlen length of the address + * @return GNUNET_OK to continue iteration, GNUNET_SYSERR to abort + */ +static int +nipo (void *cls, const char *name, int isDefault, const struct sockaddr *addr, + const struct sockaddr *broadcast_addr, const struct sockaddr *netmask, + socklen_t addrlen) +{ + struct GNUNET_NAT_AutoHandle *ah = cls; + const struct sockaddr_in *in; + char buf[INET_ADDRSTRLEN]; + + if (!isDefault) + return GNUNET_OK; + if ( (sizeof (struct sockaddr_in6) == addrlen) && + (0 != memcmp (&in6addr_loopback, &((const struct sockaddr_in6 *) addr)->sin6_addr, + sizeof (struct in6_addr))) && + (! IN6_IS_ADDR_LINKLOCAL(&((const struct sockaddr_in6 *) addr)->sin6_addr)) ) + { + ah->have_v6 = GNUNET_YES; + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + _("This system has a global IPv6 address, setting IPv6 to supported.\n")); + return GNUNET_OK; + } + if (addrlen != sizeof (struct sockaddr_in)) + return GNUNET_OK; + in = (const struct sockaddr_in *) addr; + + /* set internal IP address */ + if (NULL == inet_ntop (AF_INET, &in->sin_addr, buf, sizeof (buf))) + { + GNUNET_break (0); + return GNUNET_OK; + } + GNUNET_CONFIGURATION_set_value_string (ah->cfg, "nat", "INTERNAL_ADDRESS", + buf); + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + _("Detected internal network address `%s'.\n"), + buf); + /* no need to continue iteration */ + return GNUNET_SYSERR; +} + + +/** + * Determine our local IP addresses; detect internal IP & IPv6-support + * + * @param ah auto setup context + */ +static void +test_local_ip (struct GNUNET_NAT_AutoHandle *ah) +{ + ah->have_v6 = GNUNET_NO; + GNUNET_OS_network_interfaces_list (&nipo, ah); + GNUNET_CONFIGURATION_set_value_string (ah->cfg, "nat", "DISABLEV6", + (GNUNET_YES == ah->have_v6) ? "NO" : "YES"); + next_phase (ah); +} + + +/** + * Test if NAT has been punched + * + * @param ah auto setup context + */ +static void +test_nat_punched (struct GNUNET_NAT_AutoHandle *ah) +{ + // FIXME: not implemented + next_phase (ah); +} + + +/** + * Test if UPnPC works. + * + * @param ah auto setup context + */ +static void +test_upnpc (struct GNUNET_NAT_AutoHandle *ah) +{ + int have_upnpc; + + /* test if upnpc is available */ + have_upnpc = (GNUNET_SYSERR != + GNUNET_OS_check_helper_binary ("upnpc")); + /* FIXME: test if upnpc is actually working, that is, if transports + start to work once we use UPnP */ + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + (have_upnpc) + ? _("upnpc found, enabling its use\n") + : _("upnpc not found\n")); + GNUNET_CONFIGURATION_set_value_string (ah->cfg, "nat", "ENABLE_UPNP", + (GNUNET_YES == have_upnpc) ? "YES" : "NO"); + next_phase (ah); +} + + +/** + * Test if ICMP server is working + * + * @param ah auto setup context + */ +static void +test_icmp_server (struct GNUNET_NAT_AutoHandle *ah) +{ + int hns; + char *tmp; + char *binary; + + tmp = NULL; + binary = GNUNET_OS_get_libexec_binary_path ("gnunet-helper-nat-server"); + hns = + ((GNUNET_OK == + GNUNET_CONFIGURATION_get_value_string (ah->cfg, "nat", "EXTERNAL_ADDRESS", + &tmp)) && (0 < strlen (tmp)) && + (GNUNET_YES == + GNUNET_CONFIGURATION_get_value_yesno (ah->cfg, "nat", "BEHIND_NAT")) && + (GNUNET_YES == + GNUNET_OS_check_helper_binary (binary))); + GNUNET_free_non_null (tmp); + GNUNET_free (binary); + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + (hns) + ? _("gnunet-helper-nat-server found, testing it\n") + : _("No working gnunet-helper-nat-server found\n")); + if (hns) + ah->task = GNUNET_SCHEDULER_add_now (&reversal_test, ah); + else + next_phase (ah); +} + + +/** + * Test if ICMP client is working + * + * @param ah auto setup context + */ +static void +test_icmp_client (struct GNUNET_NAT_AutoHandle *ah) +{ + int hnc; + char *tmp; + char *binary; + + tmp = NULL; + binary = GNUNET_OS_get_libexec_binary_path ("gnunet-helper-nat-client"); + hnc = + ((GNUNET_OK == + GNUNET_CONFIGURATION_get_value_string (ah->cfg, "nat", "INTERNAL_ADDRESS", + &tmp)) && (0 < strlen (tmp)) && + (GNUNET_YES != + GNUNET_CONFIGURATION_get_value_yesno (ah->cfg, "nat", "BEHIND_NAT")) && + (GNUNET_YES == + GNUNET_OS_check_helper_binary (binary))); + GNUNET_free_non_null (tmp); + GNUNET_free (binary); + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + (hnc) + ? _("gnunet-helper-nat-client found, enabling it\n") + : _("gnunet-helper-nat-client not found or behind NAT, disabling it\n")); + next_phase (ah); +} + + +/** + * Run the next phase of the auto test. + */ +static void +next_phase (struct GNUNET_NAT_AutoHandle *ah) +{ + struct GNUNET_CONFIGURATION_Handle *diff; + + ah->phase++; + switch (ah->phase) + { + case AUTO_INIT: + GNUNET_assert (0); + break; + case AUTO_ONLINE: + test_online (ah); + break; + case AUTO_EXTERNAL_IP: + test_external_ip (ah); + break; + case AUTO_LOCAL_IP: + test_local_ip (ah); + break; + case AUTO_NAT_PUNCHED: + test_nat_punched (ah); + break; + case AUTO_UPNPC: + test_upnpc (ah); + break; + case AUTO_ICMP_SERVER: + test_icmp_server (ah); + break; + case AUTO_ICMP_CLIENT: + test_icmp_client (ah); + break; + case AUTO_DONE: + diff = GNUNET_CONFIGURATION_get_diff (ah->initial_cfg, + ah->cfg); + ah->fin_cb (ah->fin_cb_cls, + diff); + GNUNET_CONFIGURATION_destroy (diff); + GNUNET_NAT_autoconfig_cancel (ah); + return; + } +} + + + +/** + * Start auto-configuration routine. The resolver service should + * be available when this function is called. + * + * @param cfg initial configuration + * @param cb function to call with autoconfiguration result + * @param cb_cls closure for cb + * @return handle to cancel operation + */ +struct GNUNET_NAT_AutoHandle * +GNUNET_NAT_autoconfig_start (const struct GNUNET_CONFIGURATION_Handle *cfg, + GNUNET_NAT_AutoResultCallback cb, + void *cb_cls) +{ + struct GNUNET_NAT_AutoHandle *ah; + + ah = GNUNET_malloc (sizeof (struct GNUNET_NAT_AutoHandle)); + ah->fin_cb = cb; + ah->fin_cb_cls = cb_cls; + ah->cfg = GNUNET_CONFIGURATION_dup (cfg); + ah->initial_cfg = GNUNET_CONFIGURATION_dup (cfg); + + /* never use loopback addresses if user wanted autoconfiguration */ + GNUNET_CONFIGURATION_set_value_string (ah->cfg, "nat", + "USE_LOCALADDR", + "NO"); + next_phase (ah); + return ah; +} + + +/** + * Abort autoconfiguration. + * + * @param ah handle for operation to abort + */ +void +GNUNET_NAT_autoconfig_cancel (struct GNUNET_NAT_AutoHandle *ah) +{ + if (NULL != ah->tst) + { + GNUNET_NAT_test_stop (ah->tst); + ah->tst = NULL; + } + if (NULL != ah->eh) + { + GNUNET_NAT_mini_get_external_ipv4_cancel (ah->eh); + ah->eh = NULL; + } + if (GNUNET_SCHEDULER_NO_TASK != ah->task) + { + GNUNET_SCHEDULER_cancel (ah->task); + ah->task = GNUNET_SCHEDULER_NO_TASK; + } + GNUNET_CONFIGURATION_destroy (ah->cfg); + GNUNET_CONFIGURATION_destroy (ah->initial_cfg); + GNUNET_free (ah); +} + + + +/* end of nat_auto.c */ diff --git a/src/nat/nat_mini.c b/src/nat/nat_mini.c index 82697a9..fbb6e76 100644 --- a/src/nat/nat_mini.c +++ b/src/nat/nat_mini.c @@ -165,7 +165,13 @@ GNUNET_NAT_mini_get_external_ipv4 (struct GNUNET_TIME_Relative timeout, struct GNUNET_NAT_ExternalHandle *eh; if (GNUNET_SYSERR == GNUNET_OS_check_helper_binary ("external-ip")) + { + LOG (GNUNET_ERROR_TYPE_INFO, + _("`external-ip' command not found\n")); return NULL; + } + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Running `external-ip' to determine our external IP\n"); eh = GNUNET_malloc (sizeof (struct GNUNET_NAT_ExternalHandle)); eh->cb = cb; eh->cb_cls = cb_cls; @@ -176,7 +182,7 @@ GNUNET_NAT_mini_get_external_ipv4 (struct GNUNET_TIME_Relative timeout, return NULL; } eh->eip = - GNUNET_OS_start_process (GNUNET_NO, NULL, eh->opipe, "external-ip", "external-ip", + GNUNET_OS_start_process (GNUNET_NO, 0, NULL, eh->opipe, "external-ip", "external-ip", NULL); if (NULL == eh->eip) { @@ -408,6 +414,8 @@ do_refresh (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { struct GNUNET_NAT_MiniHandle *mini = cls; + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Running `upnpc' to check if our mapping still exists\n"); mini->refresh_task = GNUNET_SCHEDULER_NO_TASK; mini->found = GNUNET_NO; mini->refresh_cmd = @@ -492,7 +500,13 @@ GNUNET_NAT_mini_map_start (uint16_t port, int is_tcp, char pstr[6]; if (GNUNET_SYSERR == GNUNET_OS_check_helper_binary ("upnpc")) + { + LOG (GNUNET_ERROR_TYPE_INFO, + _("`upnpc' command not found\n")); return NULL; + } + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Running `upnpc' to install mapping\n"); ret = GNUNET_malloc (sizeof (struct GNUNET_NAT_MiniHandle)); ret->ac = ac; ret->ac_cls = ac_cls; diff --git a/src/nat/test_nat_data.conf b/src/nat/test_nat_data.conf index 7ad00a0..9314e06 100644 --- a/src/nat/test_nat_data.conf +++ b/src/nat/test_nat_data.conf @@ -1,8 +1,6 @@ [PATHS] SERVICEHOME = /tmp/nat-test # SERVICEHOME = /var/lib/gnunet/ -# DEFAULTCONFIG = /etc/gnunet.conf -# If 'DEFAULTCONFIG' is not defined, the current # configuration file is assumed to be the default, # which is what we want by default... @@ -51,7 +49,6 @@ DISABLEV6 = NO PORT = 2087 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-arm ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -75,7 +72,6 @@ AUTOSTART = YES PORT = 2088 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-statistics ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -97,7 +93,6 @@ AUTOSTART = YES PORT = 2089 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-resolver ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -139,3 +134,5 @@ AUTOSTART = NO AUTOSTART = NO +[consensus] +AUTOSTART = NO diff --git a/src/nat/test_nat_mini.c b/src/nat/test_nat_mini.c index 2c6da3b..f2e1ee9 100644 --- a/src/nat/test_nat_mini.c +++ b/src/nat/test_nat_mini.c @@ -35,9 +35,6 @@ #include "gnunet_scheduler_lib.h" #include "gnunet_nat_lib.h" - -#define VERBOSE GNUNET_NO - /* Time to wait before stopping NAT, in seconds */ #define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 5) @@ -104,20 +101,12 @@ main (int argc, char *const argv[]) "-c", "test_nat_data.conf", "-L", -#if VERBOSE - "DEBUG", -#else "WARNING", -#endif NULL }; GNUNET_log_setup ("test-nat-mini", -#if VERBOSE - "DEBUG", -#else "WARNING", -#endif NULL); GNUNET_log (GNUNET_ERROR_TYPE_INFO, diff --git a/src/nat/test_nat_test.c b/src/nat/test_nat_test.c index 891a763..c213ffa 100644 --- a/src/nat/test_nat_test.c +++ b/src/nat/test_nat_test.c @@ -102,7 +102,7 @@ main (int argc, char *const argv[]) } gns = - GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-nat-server", + GNUNET_OS_start_process (GNUNET_YES, GNUNET_OS_INHERIT_STD_OUT_AND_ERR, NULL, NULL, "gnunet-nat-server", "gnunet-nat-server", "-c", "test_nat_test_data.conf", "12345", NULL); GNUNET_assert (NULL != gns); diff --git a/src/nat/test_nat_test_data.conf b/src/nat/test_nat_test_data.conf index 1128b37..b30240c 100644 --- a/src/nat/test_nat_test_data.conf +++ b/src/nat/test_nat_test_data.conf @@ -1,8 +1,6 @@ [PATHS] SERVICEHOME = /tmp/nat-test # SERVICEHOME = /var/lib/gnunet/ -# DEFAULTCONFIG = /etc/gnunet.conf -# If 'DEFAULTCONFIG' is not defined, the current # configuration file is assumed to be the default, # which is what we want by default... diff --git a/src/nse/Makefile.am b/src/nse/Makefile.am index 054a776..a67ffea 100644 --- a/src/nse/Makefile.am +++ b/src/nse/Makefile.am @@ -11,6 +11,8 @@ endif pkgcfgdir= $(pkgdatadir)/config.d/ +libexecdir= $(pkglibdir)/libexec/ + pkgcfg_DATA = \ nse.conf @@ -27,19 +29,19 @@ libgnunetnse_la_LDFLAGS = \ -version-info 0:0:0 -bin_PROGRAMS = \ +libexec_PROGRAMS = \ gnunet-service-nse noinst_PROGRAMS = \ gnunet-nse-profiler gnunet_nse_profiler_SOURCES = \ - gnunet-nse-profiler.c + gnunet-nse-profiler.c gnunet_nse_profiler_LDADD = -lm \ $(top_builddir)/src/nse/libgnunetnse.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/statistics/libgnunetstatistics.la \ - $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la \ $(GN_LIBINTL) gnunet_nse_profiler_DEPENDENCIES = \ libgnunetnse.la @@ -73,6 +75,7 @@ test_nse_api_SOURCES = \ test_nse_api.c test_nse_api_LDADD = \ $(top_builddir)/src/nse/libgnunetnse.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la test_nse_multipeer_SOURCES = \ @@ -80,7 +83,7 @@ test_nse_multipeer_SOURCES = \ test_nse_multipeer_LDADD = \ $(top_builddir)/src/nse/libgnunetnse.la \ $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la \ -lm EXTRA_DIST = \ diff --git a/src/nse/Makefile.in b/src/nse/Makefile.in index 43d533b..7cdf53d 100644 --- a/src/nse/Makefile.in +++ b/src/nse/Makefile.in @@ -1,9 +1,9 @@ -# Makefile.in generated by automake 1.11.1 from Makefile.am. +# Makefile.in generated by automake 1.11.6 from Makefile.am. # @configure_input@ # Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, -# 2003, 2004, 2005, 2006, 2007, 2008, 2009 Free Software Foundation, -# Inc. +# 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Free Software +# Foundation, Inc. # This Makefile.in is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. @@ -18,6 +18,23 @@ VPATH = @srcdir@ +am__make_dryrun = \ + { \ + am__dry=no; \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + echo 'am--echo: ; @echo "AM" OK' | $(MAKE) -f - 2>/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } pkgdatadir = $(datadir)/@PACKAGE@ pkgincludedir = $(includedir)/@PACKAGE@ pkglibdir = $(libdir)/@PACKAGE@ @@ -37,7 +54,7 @@ POST_UNINSTALL = : build_triplet = @build@ host_triplet = @host@ target_triplet = @target@ -bin_PROGRAMS = gnunet-service-nse$(EXEEXT) +libexec_PROGRAMS = gnunet-service-nse$(EXEEXT) noinst_PROGRAMS = gnunet-nse-profiler$(EXEEXT) check_PROGRAMS = test_nse_api$(EXEEXT) $(am__EXEEXT_1) subdir = src/nse @@ -46,14 +63,15 @@ DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in \ ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 am__aclocal_m4_deps = $(top_srcdir)/m4/absolute-header.m4 \ $(top_srcdir)/m4/align.m4 $(top_srcdir)/m4/argz.m4 \ - $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/iconv.m4 \ - $(top_srcdir)/m4/lib-ld.m4 $(top_srcdir)/m4/lib-link.m4 \ - $(top_srcdir)/m4/lib-prefix.m4 $(top_srcdir)/m4/libcurl.m4 \ - $(top_srcdir)/m4/libgcrypt.m4 $(top_srcdir)/m4/libtool.m4 \ - $(top_srcdir)/m4/libunistring.m4 $(top_srcdir)/m4/ltdl.m4 \ - $(top_srcdir)/m4/ltoptions.m4 $(top_srcdir)/m4/ltsugar.m4 \ - $(top_srcdir)/m4/ltversion.m4 $(top_srcdir)/m4/lt~obsolete.m4 \ - $(top_srcdir)/m4/nls.m4 $(top_srcdir)/m4/po.m4 \ + $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/glib-2.0.m4 \ + $(top_srcdir)/m4/iconv.m4 $(top_srcdir)/m4/lib-ld.m4 \ + $(top_srcdir)/m4/lib-link.m4 $(top_srcdir)/m4/lib-prefix.m4 \ + $(top_srcdir)/m4/libcurl.m4 $(top_srcdir)/m4/libgcrypt.m4 \ + $(top_srcdir)/m4/libtool.m4 $(top_srcdir)/m4/libunistring.m4 \ + $(top_srcdir)/m4/ltdl.m4 $(top_srcdir)/m4/ltoptions.m4 \ + $(top_srcdir)/m4/ltsugar.m4 $(top_srcdir)/m4/ltversion.m4 \ + $(top_srcdir)/m4/lt~obsolete.m4 $(top_srcdir)/m4/nls.m4 \ + $(top_srcdir)/m4/pkg.m4 $(top_srcdir)/m4/po.m4 \ $(top_srcdir)/m4/progtest.m4 $(top_srcdir)/acinclude.m4 \ $(top_srcdir)/configure.ac am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ @@ -83,7 +101,13 @@ am__nobase_list = $(am__nobase_strip_setup); \ am__base_list = \ sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \ sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g' -am__installdirs = "$(DESTDIR)$(libdir)" "$(DESTDIR)$(bindir)" \ +am__uninstall_files_from_dir = { \ + test -z "$$files" \ + || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \ + || { echo " ( cd '$$dir' && rm -f" $$files ")"; \ + $(am__cd) "$$dir" && rm -f $$files; }; \ + } +am__installdirs = "$(DESTDIR)$(libdir)" "$(DESTDIR)$(libexecdir)" \ "$(DESTDIR)$(pkgcfgdir)" LTLIBRARIES = $(lib_LTLIBRARIES) am__DEPENDENCIES_1 = @@ -92,15 +116,15 @@ libgnunetnse_la_DEPENDENCIES = \ $(am__DEPENDENCIES_1) $(am__DEPENDENCIES_1) am_libgnunetnse_la_OBJECTS = nse_api.lo libgnunetnse_la_OBJECTS = $(am_libgnunetnse_la_OBJECTS) -AM_V_lt = $(am__v_lt_$(V)) -am__v_lt_ = $(am__v_lt_$(AM_DEFAULT_VERBOSITY)) +AM_V_lt = $(am__v_lt_@AM_V@) +am__v_lt_ = $(am__v_lt_@AM_DEFAULT_V@) am__v_lt_0 = --silent libgnunetnse_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ $(AM_CFLAGS) $(CFLAGS) $(libgnunetnse_la_LDFLAGS) $(LDFLAGS) \ -o $@ @HAVE_BENCHMARKS_TRUE@am__EXEEXT_1 = test_nse_multipeer$(EXEEXT) -PROGRAMS = $(bin_PROGRAMS) $(noinst_PROGRAMS) +PROGRAMS = $(libexec_PROGRAMS) $(noinst_PROGRAMS) am_gnunet_nse_profiler_OBJECTS = gnunet-nse-profiler.$(OBJEXT) gnunet_nse_profiler_OBJECTS = $(am_gnunet_nse_profiler_OBJECTS) am_gnunet_service_nse_OBJECTS = gnunet-service-nse.$(OBJEXT) @@ -108,13 +132,14 @@ gnunet_service_nse_OBJECTS = $(am_gnunet_service_nse_OBJECTS) am_test_nse_api_OBJECTS = test_nse_api.$(OBJEXT) test_nse_api_OBJECTS = $(am_test_nse_api_OBJECTS) test_nse_api_DEPENDENCIES = $(top_builddir)/src/nse/libgnunetnse.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la am_test_nse_multipeer_OBJECTS = test_nse_multipeer.$(OBJEXT) test_nse_multipeer_OBJECTS = $(am_test_nse_multipeer_OBJECTS) test_nse_multipeer_DEPENDENCIES = \ $(top_builddir)/src/nse/libgnunetnse.la \ $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/testing/libgnunettesting.la + $(top_builddir)/src/testbed/libgnunettestbed.la DEFAULT_INCLUDES = -I.@am__isrc@ -I$(top_builddir) depcomp = $(SHELL) $(top_srcdir)/depcomp am__depfiles_maybe = depfiles @@ -125,21 +150,21 @@ LTCOMPILE = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) \ $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) \ $(AM_CFLAGS) $(CFLAGS) -AM_V_CC = $(am__v_CC_$(V)) -am__v_CC_ = $(am__v_CC_$(AM_DEFAULT_VERBOSITY)) +AM_V_CC = $(am__v_CC_@AM_V@) +am__v_CC_ = $(am__v_CC_@AM_DEFAULT_V@) am__v_CC_0 = @echo " CC " $@; -AM_V_at = $(am__v_at_$(V)) -am__v_at_ = $(am__v_at_$(AM_DEFAULT_VERBOSITY)) +AM_V_at = $(am__v_at_@AM_V@) +am__v_at_ = $(am__v_at_@AM_DEFAULT_V@) am__v_at_0 = @ CCLD = $(CC) LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ $(AM_LDFLAGS) $(LDFLAGS) -o $@ -AM_V_CCLD = $(am__v_CCLD_$(V)) -am__v_CCLD_ = $(am__v_CCLD_$(AM_DEFAULT_VERBOSITY)) +AM_V_CCLD = $(am__v_CCLD_@AM_V@) +am__v_CCLD_ = $(am__v_CCLD_@AM_DEFAULT_V@) am__v_CCLD_0 = @echo " CCLD " $@; -AM_V_GEN = $(am__v_GEN_$(V)) -am__v_GEN_ = $(am__v_GEN_$(AM_DEFAULT_VERBOSITY)) +AM_V_GEN = $(am__v_GEN_@AM_V@) +am__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@) am__v_GEN_0 = @echo " GEN " $@; SOURCES = $(libgnunetnse_la_SOURCES) $(gnunet_nse_profiler_SOURCES) \ $(gnunet_service_nse_SOURCES) $(test_nse_api_SOURCES) \ @@ -147,6 +172,11 @@ SOURCES = $(libgnunetnse_la_SOURCES) $(gnunet_nse_profiler_SOURCES) \ DIST_SOURCES = $(libgnunetnse_la_SOURCES) \ $(gnunet_nse_profiler_SOURCES) $(gnunet_service_nse_SOURCES) \ $(test_nse_api_SOURCES) $(test_nse_multipeer_SOURCES) +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac DATA = $(pkgcfg_DATA) ETAGS = etags CTAGS = ctags @@ -188,6 +218,10 @@ EXEEXT = @EXEEXT@ EXT_LIBS = @EXT_LIBS@ EXT_LIB_PATH = @EXT_LIB_PATH@ FGREP = @FGREP@ +GLIB_CFLAGS = @GLIB_CFLAGS@ +GLIB_GENMARSHAL = @GLIB_GENMARSHAL@ +GLIB_LIBS = @GLIB_LIBS@ +GLIB_MKENUMS = @GLIB_MKENUMS@ GMSGFMT = @GMSGFMT@ GMSGFMT_015 = @GMSGFMT_015@ GNUNETDNS_GROUP = @GNUNETDNS_GROUP@ @@ -198,6 +232,7 @@ GN_LIBINTL = @GN_LIBINTL@ GN_LIB_LDFLAGS = @GN_LIB_LDFLAGS@ GN_PLUGIN_LDFLAGS = @GN_PLUGIN_LDFLAGS@ GN_USER_HOME_DIR = @GN_USER_HOME_DIR@ +GOBJECT_QUERY = @GOBJECT_QUERY@ GREP = @GREP@ HAVE_LIBUNISTRING = @HAVE_LIBUNISTRING@ INCLTDL = @INCLTDL@ @@ -220,6 +255,8 @@ LIBCURL_CPPFLAGS = @LIBCURL_CPPFLAGS@ LIBGCRYPT_CFLAGS = @LIBGCRYPT_CFLAGS@ LIBGCRYPT_CONFIG = @LIBGCRYPT_CONFIG@ LIBGCRYPT_LIBS = @LIBGCRYPT_LIBS@ +LIBGTOP_CFLAGS = @LIBGTOP_CFLAGS@ +LIBGTOP_LIBS = @LIBGTOP_LIBS@ LIBICONV = @LIBICONV@ LIBINTL = @LIBINTL@ LIBLTDL = @LIBLTDL@ @@ -241,6 +278,7 @@ LT_CONFIG_H = @LT_CONFIG_H@ LT_DLLOADERS = @LT_DLLOADERS@ LT_DLPREOPEN = @LT_DLPREOPEN@ MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ MKDIR_P = @MKDIR_P@ MONKEYPREFIX = @MONKEYPREFIX@ MSGFMT = @MSGFMT@ @@ -250,6 +288,7 @@ MYSQL_CPPFLAGS = @MYSQL_CPPFLAGS@ MYSQL_LDFLAGS = @MYSQL_LDFLAGS@ NM = @NM@ NMEDIT = @NMEDIT@ +NSS_DIR = @NSS_DIR@ OBJC = @OBJC@ OBJCDEPMODE = @OBJCDEPMODE@ OBJCFLAGS = @OBJCFLAGS@ @@ -265,6 +304,7 @@ PACKAGE_TARNAME = @PACKAGE_TARNAME@ PACKAGE_URL = @PACKAGE_URL@ PACKAGE_VERSION = @PACKAGE_VERSION@ PATH_SEPARATOR = @PATH_SEPARATOR@ +PKG_CONFIG = @PKG_CONFIG@ POSTGRES_CPPFLAGS = @POSTGRES_CPPFLAGS@ POSTGRES_LDFLAGS = @POSTGRES_LDFLAGS@ POSUB = @POSUB@ @@ -296,6 +336,7 @@ abs_builddir = @abs_builddir@ abs_srcdir = @abs_srcdir@ abs_top_builddir = @abs_top_builddir@ abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ ac_ct_CC = @ac_ct_CC@ ac_ct_CXX = @ac_ct_CXX@ ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ @@ -318,6 +359,7 @@ datarootdir = @datarootdir@ docdir = @docdir@ dvidir = @dvidir@ exec_prefix = @exec_prefix@ +gitcommand = @gitcommand@ host = @host@ host_alias = @host_alias@ host_cpu = @host_cpu@ @@ -328,10 +370,9 @@ includedir = @includedir@ infodir = @infodir@ install_sh = @install_sh@ libdir = @libdir@ -libexecdir = @libexecdir@ +libexecdir = $(pkglibdir)/libexec/ localedir = @localedir@ localstatedir = @localstatedir@ -lt_ECHO = @lt_ECHO@ ltdl_LIBOBJS = @ltdl_LIBOBJS@ ltdl_LTLIBOBJS = @ltdl_LTLIBOBJS@ mandir = @mandir@ @@ -349,6 +390,7 @@ sbindir = @sbindir@ sharedstatedir = @sharedstatedir@ srcdir = @srcdir@ subdirs = @subdirs@ +svnversioncommand = @svnversioncommand@ sys_symbol_underscore = @sys_symbol_underscore@ sysconfdir = @sysconfdir@ target = @target@ @@ -380,13 +422,13 @@ libgnunetnse_la_LDFLAGS = \ -version-info 0:0:0 gnunet_nse_profiler_SOURCES = \ - gnunet-nse-profiler.c + gnunet-nse-profiler.c gnunet_nse_profiler_LDADD = -lm \ $(top_builddir)/src/nse/libgnunetnse.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/statistics/libgnunetstatistics.la \ - $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la \ $(GN_LIBINTL) gnunet_nse_profiler_DEPENDENCIES = \ @@ -413,6 +455,7 @@ test_nse_api_SOURCES = \ test_nse_api_LDADD = \ $(top_builddir)/src/nse/libgnunetnse.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la test_nse_multipeer_SOURCES = \ @@ -421,7 +464,7 @@ test_nse_multipeer_SOURCES = \ test_nse_multipeer_LDADD = \ $(top_builddir)/src/nse/libgnunetnse.la \ $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la \ -lm EXTRA_DIST = \ @@ -466,7 +509,6 @@ nse.conf: $(top_builddir)/config.status $(srcdir)/nse.conf.in cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ install-libLTLIBRARIES: $(lib_LTLIBRARIES) @$(NORMAL_INSTALL) - test -z "$(libdir)" || $(MKDIR_P) "$(DESTDIR)$(libdir)" @list='$(lib_LTLIBRARIES)'; test -n "$(libdir)" || list=; \ list2=; for p in $$list; do \ if test -f $$p; then \ @@ -474,6 +516,8 @@ install-libLTLIBRARIES: $(lib_LTLIBRARIES) else :; fi; \ done; \ test -z "$$list2" || { \ + echo " $(MKDIR_P) '$(DESTDIR)$(libdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libdir)" || exit 1; \ echo " $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 '$(DESTDIR)$(libdir)'"; \ $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 "$(DESTDIR)$(libdir)"; \ } @@ -495,12 +539,24 @@ clean-libLTLIBRARIES: echo "rm -f \"$${dir}/so_locations\""; \ rm -f "$${dir}/so_locations"; \ done -libgnunetnse.la: $(libgnunetnse_la_OBJECTS) $(libgnunetnse_la_DEPENDENCIES) +libgnunetnse.la: $(libgnunetnse_la_OBJECTS) $(libgnunetnse_la_DEPENDENCIES) $(EXTRA_libgnunetnse_la_DEPENDENCIES) $(AM_V_CCLD)$(libgnunetnse_la_LINK) -rpath $(libdir) $(libgnunetnse_la_OBJECTS) $(libgnunetnse_la_LIBADD) $(LIBS) -install-binPROGRAMS: $(bin_PROGRAMS) + +clean-checkPROGRAMS: + @list='$(check_PROGRAMS)'; test -n "$$list" || exit 0; \ + echo " rm -f" $$list; \ + rm -f $$list || exit $$?; \ + test -n "$(EXEEXT)" || exit 0; \ + list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ + echo " rm -f" $$list; \ + rm -f $$list +install-libexecPROGRAMS: $(libexec_PROGRAMS) @$(NORMAL_INSTALL) - test -z "$(bindir)" || $(MKDIR_P) "$(DESTDIR)$(bindir)" - @list='$(bin_PROGRAMS)'; test -n "$(bindir)" || list=; \ + @list='$(libexec_PROGRAMS)'; test -n "$(libexecdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(libexecdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libexecdir)" || exit 1; \ + fi; \ for p in $$list; do echo "$$p $$p"; done | \ sed 's/$(EXEEXT)$$//' | \ while read p p1; do if test -f $$p || test -f $$p1; \ @@ -517,32 +573,23 @@ install-binPROGRAMS: $(bin_PROGRAMS) while read type dir files; do \ if test "$$dir" = .; then dir=; else dir=/$$dir; fi; \ test -z "$$files" || { \ - echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files '$(DESTDIR)$(bindir)$$dir'"; \ - $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files "$(DESTDIR)$(bindir)$$dir" || exit $$?; \ + echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files '$(DESTDIR)$(libexecdir)$$dir'"; \ + $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files "$(DESTDIR)$(libexecdir)$$dir" || exit $$?; \ } \ ; done -uninstall-binPROGRAMS: +uninstall-libexecPROGRAMS: @$(NORMAL_UNINSTALL) - @list='$(bin_PROGRAMS)'; test -n "$(bindir)" || list=; \ + @list='$(libexec_PROGRAMS)'; test -n "$(libexecdir)" || list=; \ files=`for p in $$list; do echo "$$p"; done | \ sed -e 'h;s,^.*/,,;s/$(EXEEXT)$$//;$(transform)' \ -e 's/$$/$(EXEEXT)/' `; \ test -n "$$list" || exit 0; \ - echo " ( cd '$(DESTDIR)$(bindir)' && rm -f" $$files ")"; \ - cd "$(DESTDIR)$(bindir)" && rm -f $$files + echo " ( cd '$(DESTDIR)$(libexecdir)' && rm -f" $$files ")"; \ + cd "$(DESTDIR)$(libexecdir)" && rm -f $$files -clean-binPROGRAMS: - @list='$(bin_PROGRAMS)'; test -n "$$list" || exit 0; \ - echo " rm -f" $$list; \ - rm -f $$list || exit $$?; \ - test -n "$(EXEEXT)" || exit 0; \ - list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ - echo " rm -f" $$list; \ - rm -f $$list - -clean-checkPROGRAMS: - @list='$(check_PROGRAMS)'; test -n "$$list" || exit 0; \ +clean-libexecPROGRAMS: + @list='$(libexec_PROGRAMS)'; test -n "$$list" || exit 0; \ echo " rm -f" $$list; \ rm -f $$list || exit $$?; \ test -n "$(EXEEXT)" || exit 0; \ @@ -558,16 +605,16 @@ clean-noinstPROGRAMS: list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ echo " rm -f" $$list; \ rm -f $$list -gnunet-nse-profiler$(EXEEXT): $(gnunet_nse_profiler_OBJECTS) $(gnunet_nse_profiler_DEPENDENCIES) +gnunet-nse-profiler$(EXEEXT): $(gnunet_nse_profiler_OBJECTS) $(gnunet_nse_profiler_DEPENDENCIES) $(EXTRA_gnunet_nse_profiler_DEPENDENCIES) @rm -f gnunet-nse-profiler$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_nse_profiler_OBJECTS) $(gnunet_nse_profiler_LDADD) $(LIBS) -gnunet-service-nse$(EXEEXT): $(gnunet_service_nse_OBJECTS) $(gnunet_service_nse_DEPENDENCIES) +gnunet-service-nse$(EXEEXT): $(gnunet_service_nse_OBJECTS) $(gnunet_service_nse_DEPENDENCIES) $(EXTRA_gnunet_service_nse_DEPENDENCIES) @rm -f gnunet-service-nse$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_service_nse_OBJECTS) $(gnunet_service_nse_LDADD) $(LIBS) -test_nse_api$(EXEEXT): $(test_nse_api_OBJECTS) $(test_nse_api_DEPENDENCIES) +test_nse_api$(EXEEXT): $(test_nse_api_OBJECTS) $(test_nse_api_DEPENDENCIES) $(EXTRA_test_nse_api_DEPENDENCIES) @rm -f test_nse_api$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_nse_api_OBJECTS) $(test_nse_api_LDADD) $(LIBS) -test_nse_multipeer$(EXEEXT): $(test_nse_multipeer_OBJECTS) $(test_nse_multipeer_DEPENDENCIES) +test_nse_multipeer$(EXEEXT): $(test_nse_multipeer_OBJECTS) $(test_nse_multipeer_DEPENDENCIES) $(EXTRA_test_nse_multipeer_DEPENDENCIES) @rm -f test_nse_multipeer$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_nse_multipeer_OBJECTS) $(test_nse_multipeer_LDADD) $(LIBS) @@ -586,26 +633,23 @@ distclean-compile: .c.o: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c $< .c.obj: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'` @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c `$(CYGPATH_W) '$<'` +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c `$(CYGPATH_W) '$<'` .c.lo: @am__fastdepCC_TRUE@ $(AM_V_CC)$(LTCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LTCOMPILE) -c -o $@ $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LTCOMPILE) -c -o $@ $< mostlyclean-libtool: -rm -f *.lo @@ -614,8 +658,11 @@ clean-libtool: -rm -rf .libs _libs install-pkgcfgDATA: $(pkgcfg_DATA) @$(NORMAL_INSTALL) - test -z "$(pkgcfgdir)" || $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" @list='$(pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(pkgcfgdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" || exit 1; \ + fi; \ for p in $$list; do \ if test -f "$$p"; then d=; else d="$(srcdir)/"; fi; \ echo "$$d$$p"; \ @@ -629,9 +676,7 @@ uninstall-pkgcfgDATA: @$(NORMAL_UNINSTALL) @list='$(pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ files=`for p in $$list; do echo $$p; done | sed -e 's|^.*/||'`; \ - test -n "$$files" || exit 0; \ - echo " ( cd '$(DESTDIR)$(pkgcfgdir)' && rm -f" $$files ")"; \ - cd "$(DESTDIR)$(pkgcfgdir)" && rm -f $$files + dir='$(DESTDIR)$(pkgcfgdir)'; $(am__uninstall_files_from_dir) ID: $(HEADERS) $(SOURCES) $(LISP) $(TAGS_FILES) list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ @@ -766,14 +811,15 @@ check-TESTS: $(TESTS) fi; \ dashes=`echo "$$dashes" | sed s/./=/g`; \ if test "$$failed" -eq 0; then \ - echo "$$grn$$dashes"; \ + col="$$grn"; \ else \ - echo "$$red$$dashes"; \ + col="$$red"; \ fi; \ - echo "$$banner"; \ - test -z "$$skipped" || echo "$$skipped"; \ - test -z "$$report" || echo "$$report"; \ - echo "$$dashes$$std"; \ + echo "$${col}$$dashes$${std}"; \ + echo "$${col}$$banner$${std}"; \ + test -z "$$skipped" || echo "$${col}$$skipped$${std}"; \ + test -z "$$report" || echo "$${col}$$report$${std}"; \ + echo "$${col}$$dashes$${std}"; \ test "$$failed" -eq 0; \ else :; fi @@ -812,10 +858,8 @@ check-am: all-am $(MAKE) $(AM_MAKEFLAGS) check-TESTS check: check-am all-am: Makefile $(LTLIBRARIES) $(PROGRAMS) $(DATA) -install-binPROGRAMS: install-libLTLIBRARIES - installdirs: - for dir in "$(DESTDIR)$(libdir)" "$(DESTDIR)$(bindir)" "$(DESTDIR)$(pkgcfgdir)"; do \ + for dir in "$(DESTDIR)$(libdir)" "$(DESTDIR)$(libexecdir)" "$(DESTDIR)$(pkgcfgdir)"; do \ test -z "$$dir" || $(MKDIR_P) "$$dir"; \ done install: install-am @@ -828,10 +872,15 @@ install-am: all-am installcheck: installcheck-am install-strip: - $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ - install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ - `test -z '$(STRIP)' || \ - echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi mostlyclean-generic: clean-generic: @@ -845,8 +894,8 @@ maintainer-clean-generic: @echo "it deletes files that may require special tools to rebuild." clean: clean-am -clean-am: clean-binPROGRAMS clean-checkPROGRAMS clean-generic \ - clean-libLTLIBRARIES clean-libtool clean-noinstPROGRAMS \ +clean-am: clean-checkPROGRAMS clean-generic clean-libLTLIBRARIES \ + clean-libexecPROGRAMS clean-libtool clean-noinstPROGRAMS \ mostlyclean-am distclean: distclean-am @@ -873,7 +922,7 @@ install-dvi: install-dvi-am install-dvi-am: -install-exec-am: install-binPROGRAMS install-libLTLIBRARIES +install-exec-am: install-libLTLIBRARIES install-libexecPROGRAMS install-html: install-html-am @@ -913,27 +962,27 @@ ps: ps-am ps-am: -uninstall-am: uninstall-binPROGRAMS uninstall-libLTLIBRARIES \ +uninstall-am: uninstall-libLTLIBRARIES uninstall-libexecPROGRAMS \ uninstall-pkgcfgDATA .MAKE: check-am install-am install-strip .PHONY: CTAGS GTAGS all all-am check check-TESTS check-am clean \ - clean-binPROGRAMS clean-checkPROGRAMS clean-generic \ - clean-libLTLIBRARIES clean-libtool clean-noinstPROGRAMS ctags \ + clean-checkPROGRAMS clean-generic clean-libLTLIBRARIES \ + clean-libexecPROGRAMS clean-libtool clean-noinstPROGRAMS ctags \ distclean distclean-compile distclean-generic \ distclean-libtool distclean-tags distdir dvi dvi-am html \ - html-am info info-am install install-am install-binPROGRAMS \ - install-data install-data-am install-dvi install-dvi-am \ - install-exec install-exec-am install-html install-html-am \ - install-info install-info-am install-libLTLIBRARIES \ + html-am info info-am install install-am install-data \ + install-data-am install-dvi install-dvi-am install-exec \ + install-exec-am install-html install-html-am install-info \ + install-info-am install-libLTLIBRARIES install-libexecPROGRAMS \ install-man install-pdf install-pdf-am install-pkgcfgDATA \ install-ps install-ps-am install-strip installcheck \ installcheck-am installdirs maintainer-clean \ maintainer-clean-generic mostlyclean mostlyclean-compile \ mostlyclean-generic mostlyclean-libtool pdf pdf-am ps ps-am \ - tags uninstall uninstall-am uninstall-binPROGRAMS \ - uninstall-libLTLIBRARIES uninstall-pkgcfgDATA + tags uninstall uninstall-am uninstall-libLTLIBRARIES \ + uninstall-libexecPROGRAMS uninstall-pkgcfgDATA # Tell versions [3.59,3.63) of GNU make to not export all variables. diff --git a/src/nse/gnunet-nse-profiler.c b/src/nse/gnunet-nse-profiler.c index 4a4bea5..225a420 100644 --- a/src/nse/gnunet-nse-profiler.c +++ b/src/nse/gnunet-nse-profiler.c @@ -1,6 +1,6 @@ /* This file is part of GNUnet. - (C) 2011 Christian Grothoff (and other contributing authors) + (C) 2011, 2012 Christian Grothoff (and other contributing authors) GNUnet is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published @@ -24,35 +24,64 @@ * Generally, the profiler starts a given number of peers, * then churns some off, waits a certain amount of time, then * churns again, and repeats. + * + * TODO: + * - need to enable user to specify topology options + * - need to check for leaks (especially FD leaks) + * - need to TEST */ #include "platform.h" -#include "gnunet_testing_lib.h" +#include "gnunet_testbed_service.h" #include "gnunet_nse_service.h" -#define VERBOSE 3 +/** + * Information we track for a peer in the testbed. + */ struct NSEPeer { + /** + * Prev reference in DLL. + */ struct NSEPeer *prev; + /** + * Next reference in DLL. + */ struct NSEPeer *next; - struct GNUNET_TESTING_Daemon *daemon; + /** + * Handle with testbed. + */ + struct GNUNET_TESTBED_Peer *daemon; - struct GNUNET_NSE_Handle *nse_handle; + /** + * Testbed operation to connect to NSE service. + */ + struct GNUNET_TESTBED_Operation *nse_op; + /** + * Handle to statistics service of the peer. + */ struct GNUNET_STATISTICS_Handle *stats; + + /** + * Testbed operation to connect to statistics service. + */ + struct GNUNET_TESTBED_Operation *stats_op; + /** + * Task scheduled to get statistics from this peer. + */ GNUNET_SCHEDULER_TaskIdentifier stats_task; }; +/** + * Context for the stats task? + */ struct StatsContext { - /** - * Whether or not shoutdown after finishing. - */ - int shutdown; /** * How many messages have peers received during the test. @@ -81,51 +110,80 @@ struct StatsContext }; +/** + * Head of DLL of peers we monitor closely. + */ static struct NSEPeer *peer_head; +/** + * Tail of DLL of peers we monitor closely. + */ static struct NSEPeer *peer_tail; /** - * How long until we give up on connecting the peers? + * Return value from 'main' (0 == success) */ -#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 1500) - static int ok; /** - * Be verbose + * Be verbose (configuration option) */ static int verbose; /** - * Total number of peers in the test. + * Name of the file with the hosts to run the test over (configuration option) + */ +static char *hosts_file; + +/** + * IP address of this system, as seen by the rest of the system (configuration option) */ -static unsigned long long num_peers; +static char *controller_ip; /** - * Global configuration file + * Maximum number of peers in the test. */ -static struct GNUNET_CONFIGURATION_Handle *testing_cfg; +static unsigned int num_peers; /** - * Total number of currently running peers. + * Total number of rounds to execute. */ -static unsigned long long peers_running; +static unsigned int num_rounds; /** * Current round we are in. */ -static unsigned long long current_round; +static unsigned int current_round; + +/** + * Array of size 'num_rounds' with the requested number of peers in the given round. + */ +static unsigned int *num_peers_in_round; + +/** + * How many peers are running right now? + */ +static unsigned int peers_running; + +/** + * Specification for the numbers of peers to have in each round. + */ +static char *num_peer_spec; + +/** + * Handles to all of the running peers. + */ +static struct GNUNET_TESTBED_Peer **daemons; /** - * Peers desired in the next round. + * Global configuration file */ -static unsigned long long peers_next_round; +static struct GNUNET_CONFIGURATION_Handle *testing_cfg; /** * Maximum number of connections to NSE services. */ -static unsigned long long connection_limit; +static unsigned int connection_limit; /** * Total number of connections in the whole network. @@ -133,14 +191,14 @@ static unsigned long long connection_limit; static unsigned int total_connections; /** - * The currently running peer group. + * File to report results to. */ -static struct GNUNET_TESTING_PeerGroup *pg; +static struct GNUNET_DISK_FileHandle *output_file; /** - * File to report results to. + * Filename to log results to. */ -static struct GNUNET_DISK_FileHandle *output_file; +static char *output_filename; /** * File to log connection info, statistics to. @@ -148,94 +206,106 @@ static struct GNUNET_DISK_FileHandle *output_file; static struct GNUNET_DISK_FileHandle *data_file; /** - * How many data points to capture before triggering next round? + * Filename to log connection info, statistics to. */ -static struct GNUNET_TIME_Relative wait_time; +static char *data_filename; /** - * NSE interval. + * How long to wait before triggering next round? + * Default: 60 s. */ -static struct GNUNET_TIME_Relative interval; +static struct GNUNET_TIME_Relative wait_time = { 60 * 1000 }; /** - * Task called to disconnect peers. + * How often do we query for statistics during a round? + * Default: 1 s. */ -static GNUNET_SCHEDULER_TaskIdentifier disconnect_task; +static struct GNUNET_TIME_Relative interval = { 1000 }; /** - * Task called to shutdown test. + * Name of the file where we write the topology for each round; NULL for + * none. */ -static GNUNET_SCHEDULER_TaskIdentifier shutdown_handle; +static char *topology_file; /** - * Task used to churn the network. + * List of hosts we use for the testbed. */ -static GNUNET_SCHEDULER_TaskIdentifier churn_task; +static struct GNUNET_TESTBED_Host **hosts; -static char *topology_file; +/** + * Size of the 'hosts' array. + */ +static unsigned int num_hosts; /** - * Check whether peers successfully shut down. + * Handle to the master controller. */ -static void -shutdown_callback (void *cls, const char *emsg) -{ - if (emsg != NULL) - { -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Shutdown of peers failed!\n"); -#endif - if (ok == 0) - ok = 666; - } - else - { -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "All peers successfully shut down!\n"); -#endif - ok = 0; - } -} +static struct GNUNET_TESTBED_Controller *controller; + +/** + * Controller start handle. + */ +static struct GNUNET_TESTBED_ControllerProc *copro; + +/* /\** */ +/* * Testbed handle. */ +/* *\/ */ +/* static struct GNUNET_TESTBED_Testbed *testbed; */ +/** + * Clean up all of the monitoring connections to NSE and + * STATISTICS that we keep to selected peers. + */ static void -shutdown_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +close_monitor_connections () { struct NSEPeer *pos; -#if VERBOSE - FPRINTF (stderr, "%s", "Ending test.\n"); -#endif - - if (disconnect_task != GNUNET_SCHEDULER_NO_TASK) - { - GNUNET_SCHEDULER_cancel (disconnect_task); - disconnect_task = GNUNET_SCHEDULER_NO_TASK; - } while (NULL != (pos = peer_head)) { - if (pos->nse_handle != NULL) - GNUNET_NSE_disconnect (pos->nse_handle); + if (NULL != pos->nse_op) + GNUNET_TESTBED_operation_done (pos->nse_op); + if (NULL != pos->stats_op) + GNUNET_TESTBED_operation_done (pos->stats_op); GNUNET_CONTAINER_DLL_remove (peer_head, peer_tail, pos); if (GNUNET_SCHEDULER_NO_TASK != pos->stats_task) - { GNUNET_SCHEDULER_cancel (pos->stats_task); - if (NULL != pos->stats) - GNUNET_STATISTICS_destroy(pos->stats, GNUNET_NO); - } GNUNET_free (pos); } +} + - if (data_file != NULL) +/** + * Task run on shutdown; cleans up everything. + * + * @param cls unused + * @param tc unused + */ +static void +shutdown_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Ending test.\n"); + close_monitor_connections (); + /* if (NULL != testbed) */ + /* GNUNET_TESTBED_destroy (testbed); */ + if (NULL != controller) + GNUNET_TESTBED_controller_disconnect (controller); + if (NULL != copro) + GNUNET_TESTBED_controller_stop (copro); + while (0 < num_hosts) + GNUNET_TESTBED_host_destroy (hosts[--num_hosts]); + // FIXME: what about closing other files!? + if (NULL != data_file) GNUNET_DISK_file_close (data_file); - GNUNET_TESTING_daemons_stop (pg, TIMEOUT, &shutdown_callback, NULL); } /** * Callback to call when network size estimate is updated. * - * @param cls closure + * @param cls closure with the 'struct NSEPeer' providing the update * @param timestamp server timestamp * @param estimate the value of the current network size estimate * @param std_dev standard deviation (rounded down to nearest integer) @@ -243,32 +313,34 @@ shutdown_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) * */ static void -handle_estimate (void *cls, struct GNUNET_TIME_Absolute timestamp, +handle_estimate (void *cls, + struct GNUNET_TIME_Absolute timestamp, double estimate, double std_dev) { struct NSEPeer *peer = cls; - char *output_buffer; + char output_buffer[512]; size_t size; - if (output_file != NULL) - { - size = - GNUNET_asprintf (&output_buffer, "%s %llu %llu %f %f %f\n", - GNUNET_i2s (&peer->daemon->id), peers_running, - timestamp.abs_value, - GNUNET_NSE_log_estimate_to_n (estimate), estimate, - std_dev); - if (size != GNUNET_DISK_file_write (output_file, output_buffer, size)) - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Unable to write to file!\n"); - GNUNET_free (output_buffer); - } - else - FPRINTF (stderr, - "Received network size estimate from peer %s. Size: %f std.dev. %f\n", - GNUNET_i2s (&peer->daemon->id), estimate, std_dev); - + if (NULL == output_file) + { + FPRINTF (stderr, + "Received network size estimate from peer %p. Size: %f std.dev. %f\n", + peer, estimate, std_dev); + return; + } + size = GNUNET_snprintf (output_buffer, + sizeof (output_buffer), + "%p %llu %llu %f %f %f\n", + peer, peers_running, + timestamp.abs_value, + GNUNET_NSE_log_estimate_to_n (estimate), estimate, + std_dev); + if (size != GNUNET_DISK_file_write (output_file, output_buffer, size)) + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + "Unable to write to file!\n"); } + /** * Process core statistic values. * @@ -284,29 +356,30 @@ core_stats_iterator (void *cls, const char *subsystem, const char *name, uint64_t value, int is_persistent) { struct NSEPeer *peer = cls; - char *output_buffer; + char output_buffer[512]; size_t size; - if (output_file != NULL) - { - size = - GNUNET_asprintf (&output_buffer, "%s [%s] %s %llu\n", - GNUNET_i2s (&peer->daemon->id), - subsystem, name, value); - if (size != GNUNET_DISK_file_write (output_file, output_buffer, size)) - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Unable to write to file!\n"); - GNUNET_free (output_buffer); - } - else - GNUNET_log (GNUNET_ERROR_TYPE_INFO, - "%s -> %s [%s]: %llu\n", - GNUNET_i2s (&peer->daemon->id), subsystem, name, value); - + if (NULL == output_file) + { + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + "%p -> %s [%s]: %llu\n", + peer, subsystem, name, value); + return GNUNET_OK; + } + size = + GNUNET_snprintf (output_buffer, + sizeof (output_buffer), + "%p [%s] %s %llu\n", + peer, + subsystem, name, value); + if (size != GNUNET_DISK_file_write (output_file, output_buffer, size)) + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Unable to write to file!\n"); return GNUNET_OK; } + /** - * Continuation called by "get_stats" function. + * Continuation called by "get_stats" function once we are done. * * @param cls closure * @param success GNUNET_OK if statistics were @@ -315,32 +388,43 @@ core_stats_iterator (void *cls, const char *subsystem, const char *name, static void core_stats_cont (void *cls, int success); + +/** + * Function invoked periodically to get the statistics. + * + * @param cls 'struct NSEPeer' to get stats from + * @param tc scheduler context + */ static void -core_get_stats (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +core_get_stats (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) { struct NSEPeer *peer = cls; - if ((tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN) != 0) + if (0 != (tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN)) { - GNUNET_STATISTICS_destroy(peer->stats, GNUNET_NO); + GNUNET_TESTBED_operation_done (peer->stats_op); peer->stats = NULL; + peer->stats_op = NULL; return; } - else - { - GNUNET_STATISTICS_get(peer->stats, "core", NULL, - GNUNET_TIME_UNIT_FOREVER_REL, - &core_stats_cont, &core_stats_iterator, peer); - GNUNET_STATISTICS_get(peer->stats, "transport", NULL, - GNUNET_TIME_UNIT_FOREVER_REL, - NULL, &core_stats_iterator, peer); - GNUNET_STATISTICS_get(peer->stats, "nse", NULL, - GNUNET_TIME_UNIT_FOREVER_REL, - NULL, &core_stats_iterator, peer); - } + /* FIXME: code duplication! */ + GNUNET_STATISTICS_get (peer->stats, "core", NULL, + GNUNET_TIME_UNIT_FOREVER_REL, + &core_stats_cont, + &core_stats_iterator, peer); + GNUNET_STATISTICS_get (peer->stats, "transport", NULL, + GNUNET_TIME_UNIT_FOREVER_REL, + NULL, + &core_stats_iterator, peer); + GNUNET_STATISTICS_get (peer->stats, "nse", NULL, + GNUNET_TIME_UNIT_FOREVER_REL, + NULL, + &core_stats_iterator, peer); peer->stats_task = GNUNET_SCHEDULER_NO_TASK; } + /** * Continuation called by "get_stats" function. * @@ -349,149 +433,243 @@ core_get_stats (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) * successfully obtained, GNUNET_SYSERR if not. */ static void -core_stats_cont (void *cls, int success) +core_stats_cont (void *cls, + int success) { struct NSEPeer *peer = cls; - peer->stats_task = GNUNET_SCHEDULER_add_delayed (interval, &core_get_stats, - peer); + + if (GNUNET_OK != success) + return; + peer->stats_task = GNUNET_SCHEDULER_add_delayed (interval, + &core_get_stats, peer); } /** + * Adapter function called to establish a connection to + * statistics service. + * + * @param cls closure + * @param cfg configuration of the peer to connect to; will be available until + * GNUNET_TESTBED_operation_done() is called on the operation returned + * from GNUNET_TESTBED_service_connect() + * @return service handle to return in 'op_result', NULL on error + */ +static void * +statistics_connect_adapter (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg) +{ + return GNUNET_STATISTICS_create ("", + cfg); +} + + +/** + * Adapter function called to destroy a connection to + * statistics service. + * + * @param cls closure + * @param op_result service handle returned from the connect adapter + */ +static void +statistics_disconnect_adapter (void *cls, + void *op_result) +{ + GNUNET_STATISTICS_destroy (op_result, GNUNET_NO); +} + + +/** + * Function called by testbed once we are connected to stats service. * + * @param cls the 'struct NSEPeer' for which we connected to stats + * @param op connect operation handle + * @param ca_result handle to stats service + * @param emsg error message on failure */ static void -connect_nse_service (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +stat_run (void *cls, + struct GNUNET_TESTBED_Operation *op, + void *ca_result, + const char *emsg) +{ + struct NSEPeer *current_peer = cls; + + if (NULL == ca_result) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Failed to connect to statistics service: %s\n", + emsg); + GNUNET_SCHEDULER_shutdown (); + return; + } + current_peer->stats = ca_result; + GNUNET_STATISTICS_get (current_peer->stats, "core", NULL, + GNUNET_TIME_UNIT_FOREVER_REL, + &core_stats_cont, + &core_stats_iterator, current_peer); + GNUNET_STATISTICS_get (current_peer->stats, "transport", NULL, + GNUNET_TIME_UNIT_FOREVER_REL, + NULL, + &core_stats_iterator, current_peer); + GNUNET_STATISTICS_get (current_peer->stats, "nse", NULL, + GNUNET_TIME_UNIT_FOREVER_REL, + NULL, + &core_stats_iterator, current_peer); +} + + +/** + * Adapter function called to establish a connection to + * NSE service. + * + * @param cls closure (the 'struct NSEPeer') + * @param cfg configuration of the peer to connect to; will be available until + * GNUNET_TESTBED_operation_done() is called on the operation returned + * from GNUNET_TESTBED_service_connect() + * @return service handle to return in 'op_result', NULL on error + */ +static void * +nse_connect_adapter (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg) +{ + struct NSEPeer *current_peer = cls; + + return GNUNET_NSE_connect (cfg, &handle_estimate, current_peer); +} + + +/** + * Adapter function called to destroy a connection to + * NSE service. + * + * @param cls closure + * @param op_result service handle returned from the connect adapter + */ +static void +nse_disconnect_adapter (void *cls, + void *op_result) +{ + GNUNET_NSE_disconnect (op_result); +} + + +/** + * Task run to connect to the NSE and statistics services to a subset of + * all of the running peers. + */ +static void +connect_nse_service () { struct NSEPeer *current_peer; unsigned int i; -#if VERBOSE GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Connecting to nse service of peers\n"); -#endif for (i = 0; i < num_peers; i++) { if ((connection_limit > 0) && (num_peers > connection_limit) && - (i % (num_peers / connection_limit) != 0)) + (0 != (i % (num_peers / connection_limit)))) continue; -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "nse-profiler: connecting to nse service of peer %d\n", i); -#endif current_peer = GNUNET_malloc (sizeof (struct NSEPeer)); - current_peer->daemon = GNUNET_TESTING_daemon_get (pg, i); - if (GNUNET_YES == - GNUNET_TESTING_test_daemon_running (GNUNET_TESTING_daemon_get (pg, i))) - { - current_peer->nse_handle = - GNUNET_NSE_connect (current_peer->daemon->cfg, &handle_estimate, - current_peer); - GNUNET_assert (current_peer->nse_handle != NULL); - } - current_peer->stats = GNUNET_STATISTICS_create("profiler", current_peer->daemon->cfg); - GNUNET_STATISTICS_get(current_peer->stats, "core", NULL, - GNUNET_TIME_UNIT_FOREVER_REL, - &core_stats_cont, &core_stats_iterator, current_peer); - GNUNET_STATISTICS_get(current_peer->stats, "transport", NULL, - GNUNET_TIME_UNIT_FOREVER_REL, - NULL, &core_stats_iterator, current_peer); - GNUNET_STATISTICS_get(current_peer->stats, "nse", NULL, - GNUNET_TIME_UNIT_FOREVER_REL, - NULL, &core_stats_iterator, current_peer); + current_peer->daemon = daemons[i]; + current_peer->nse_op + = GNUNET_TESTBED_service_connect (NULL, + current_peer->daemon, + "nse", + NULL, NULL, + &nse_connect_adapter, + &nse_disconnect_adapter, + current_peer); + current_peer->stats_op + = GNUNET_TESTBED_service_connect (NULL, + current_peer->daemon, + "statistics", + &stat_run, current_peer, + &statistics_connect_adapter, + &statistics_disconnect_adapter, + NULL); GNUNET_CONTAINER_DLL_insert (peer_head, peer_tail, current_peer); } } +/** + * Task that starts/stops peers to move to the next round. + * + * @param cls NULL, unused + * @param tc scheduler context (unused) + */ static void -churn_peers (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc); +next_round (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc); /** - * Continuation called by the "get_all" and "get" functions. + * Continuation called by the "get_all" and "get" functions at the + * end of a round. Obtains the final statistics and writes them to + * the file, then either starts the next round, or, if this was the + * last round, terminates the run. * * @param cls struct StatsContext - * @param success GNUNET_OK if statistics were - * successfully obtained, GNUNET_SYSERR if not. + * @param op operation handle + * @param emsg error message, NULL on success */ static void -stats_finished_callback (void *cls, int success) +stats_finished_callback (void *cls, + struct GNUNET_TESTBED_Operation *op, + const char *emsg) { struct StatsContext *stats_context = cls; - char *buf; - int buf_len; + char buf[512]; + size_t buf_len; - if ((GNUNET_OK == success) && (data_file != NULL)) - { - /* Stats lookup successful, write out data */ - buf = NULL; - buf_len = - GNUNET_asprintf (&buf, "TOTAL_NSE_RECEIVED_MESSAGES_%d: %u \n", - stats_context->shutdown, - stats_context->total_nse_received_messages); - if (buf_len > 0) + if (NULL != emsg) { - GNUNET_DISK_file_write (data_file, buf, buf_len); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Failed to get statistics: %s\n", + emsg); + GNUNET_SCHEDULER_shutdown (); + GNUNET_free (stats_context); + return; } - GNUNET_free_non_null (buf); - - buf = NULL; - buf_len = - GNUNET_asprintf (&buf, "TOTAL_NSE_TRANSMITTED_MESSAGES_%d: %u\n", - stats_context->shutdown, - stats_context->total_nse_transmitted_messages); - if (buf_len > 0) + if (NULL != data_file) { + /* Stats lookup successful, write out data */ + buf_len = + GNUNET_snprintf (buf, sizeof (buf), + "TOTAL_NSE_RECEIVED_MESSAGES_%u: %u \n", + current_round, + stats_context->total_nse_received_messages); GNUNET_DISK_file_write (data_file, buf, buf_len); - } - GNUNET_free_non_null (buf); - - buf = NULL; - buf_len = - GNUNET_asprintf (&buf, "TOTAL_NSE_CROSS_%d: %u \n", - stats_context->shutdown, - stats_context->total_nse_cross); - if (buf_len > 0) - { + buf_len = + GNUNET_snprintf (buf, sizeof (buf), + "TOTAL_NSE_TRANSMITTED_MESSAGES_%u: %u\n", + current_round, + stats_context->total_nse_transmitted_messages); + GNUNET_DISK_file_write (data_file, buf, buf_len); + buf_len = + GNUNET_snprintf (buf, sizeof (buf), + "TOTAL_NSE_CROSS_%u: %u \n", + current_round, + stats_context->total_nse_cross); GNUNET_DISK_file_write (data_file, buf, buf_len); - } - GNUNET_free_non_null (buf); - - buf = NULL; - buf_len = - GNUNET_asprintf (&buf, "TOTAL_NSE_EXTRA_%d: %u \n", - stats_context->shutdown, - stats_context->total_nse_extra); - if (buf_len > 0) - { + buf_len = + GNUNET_snprintf (buf, sizeof (buf), + "TOTAL_NSE_EXTRA_%u: %u \n", + current_round, + stats_context->total_nse_extra); GNUNET_DISK_file_write (data_file, buf, buf_len); - } - GNUNET_free_non_null (buf); - - buf = NULL; - buf_len = - GNUNET_asprintf (&buf, "TOTAL_NSE_DISCARDED_%d: %u \n", - stats_context->shutdown, - stats_context->total_discarded); - if (buf_len > 0) - { - GNUNET_DISK_file_write (data_file, buf, buf_len); - } - GNUNET_free_non_null (buf); - - } - - if (GNUNET_YES == stats_context->shutdown) - { - GNUNET_assert (GNUNET_SCHEDULER_NO_TASK == shutdown_handle); - shutdown_handle = GNUNET_SCHEDULER_add_now (&shutdown_task, NULL); - } - else - { - GNUNET_assert (churn_task == GNUNET_SCHEDULER_NO_TASK); - churn_task = GNUNET_SCHEDULER_add_now (&churn_peers, NULL); - } + buf_len = + GNUNET_snprintf (buf, sizeof (buf), + "TOTAL_NSE_DISCARDED_%u: %u \n", + current_round, + stats_context->total_discarded); + GNUNET_DISK_file_write (data_file, buf, buf_len); + } + GNUNET_SCHEDULER_add_now (&next_round, NULL); GNUNET_free (stats_context); } @@ -508,428 +686,366 @@ stats_finished_callback (void *cls, int success) * @return GNUNET_OK to continue, GNUNET_SYSERR to abort iteration */ static int -statistics_iterator (void *cls, const struct GNUNET_PeerIdentity *peer, +statistics_iterator (void *cls, + const struct GNUNET_TESTBED_Peer *peer, const char *subsystem, const char *name, uint64_t value, int is_persistent) { struct StatsContext *stats_context = cls; + char buf[512]; + size_t buf_len; - if (0 == strcmp (subsystem, "nse")) - { - if (0 == strcmp (name, "# flood messages received")) + if (0 != strcmp (subsystem, "nse")) + return GNUNET_OK; + if (0 == strcmp (name, "# flood messages received")) { stats_context->total_nse_received_messages += value; -#if VERBOSE - if (data_file != NULL) - { - char *buf; - int buf_len; - - buf = NULL; - buf_len = - GNUNET_asprintf (&buf, "%s %u RECEIVED\n", GNUNET_i2s(peer), value); - if (buf_len > 0) - { - GNUNET_DISK_file_write (data_file, buf, buf_len); - } - GNUNET_free_non_null (buf); - } -#endif + if ( (verbose > 1) && + (NULL != data_file) ) + { + buf_len = + GNUNET_snprintf (buf, sizeof (buf), + "%p %u RECEIVED\n", + peer, value); + GNUNET_DISK_file_write (data_file, buf, buf_len); + } } - if (0 == strcmp (name, "# flood messages transmitted")) + if (0 == strcmp (name, "# flood messages transmitted")) { stats_context->total_nse_transmitted_messages += value; -#if VERBOSE - if (data_file != NULL) - { - char *buf; - int buf_len; - - buf = NULL; - buf_len = - GNUNET_asprintf (&buf, "%s %u TRANSMITTED\n", - GNUNET_i2s(peer), value); - if (buf_len > 0) - { - GNUNET_DISK_file_write (data_file, buf, buf_len); - } - GNUNET_free_non_null (buf); - } -#endif - } - if (0 == strcmp (name, "# cross messages")) - { - stats_context->total_nse_cross += value; - } - if (0 == strcmp (name, "# extra messages")) - { - stats_context->total_nse_extra += value; - } - if (0 == strcmp (name, "# flood messages discarded (clock skew too large)")) - { - stats_context->total_discarded += value; + if ( (verbose > 1) && + (NULL != data_file) ) + { + buf_len = + GNUNET_snprintf (buf, sizeof (buf), + "%p %u TRANSMITTED\n", + peer, value); + GNUNET_DISK_file_write (data_file, buf, buf_len); + } } - } + if (0 == strcmp (name, "# cross messages")) + stats_context->total_nse_cross += value; + if (0 == strcmp (name, "# extra messages")) + stats_context->total_nse_extra += value; + if (0 == strcmp (name, "# flood messages discarded (clock skew too large)")) + stats_context->total_discarded += value; return GNUNET_OK; } +/** + * Function called upon completion of the node start/stop operations + * for the current round. Writes the new topology to disk. + */ static void -disconnect_nse_peers (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +write_topology () { - struct NSEPeer *pos; - char *buf; - struct StatsContext *stats_context; - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "disconnecting nse service of peers\n"); - disconnect_task = GNUNET_SCHEDULER_NO_TASK; - while (NULL != (pos = peer_head)) - { - if (pos->nse_handle != NULL) - { - GNUNET_NSE_disconnect (pos->nse_handle); - pos->nse_handle = NULL; - } - GNUNET_CONTAINER_DLL_remove (peer_head, peer_tail, pos); - if (NULL != pos->stats) - GNUNET_STATISTICS_destroy(pos->stats, GNUNET_NO); - if (GNUNET_SCHEDULER_NO_TASK != pos->stats_task) - GNUNET_SCHEDULER_cancel (pos->stats_task); - GNUNET_free (pos); - } + char temp_output_file[1024]; - GNUNET_asprintf (&buf, "round%llu", current_round); - if (GNUNET_OK == - GNUNET_CONFIGURATION_get_value_number (testing_cfg, "nse-profiler", buf, - &peers_next_round)) - { - current_round++; - if (current_round == 1) - { - stats_context = GNUNET_malloc (sizeof (struct StatsContext)); - stats_context->shutdown = GNUNET_NO; - GNUNET_TESTING_get_statistics (pg, &stats_finished_callback, - &statistics_iterator, stats_context); - } - else + if (NULL != topology_file) { - GNUNET_assert (churn_task == GNUNET_SCHEDULER_NO_TASK); - churn_task = GNUNET_SCHEDULER_add_now (&churn_peers, NULL); + GNUNET_snprintf (temp_output_file, sizeof (temp_output_file), + "%s_%llu.dot", + topology_file, current_round); + GNUNET_TESTBED_overlay_write_topology_to_file (controller, + temp_output_file); } - } - else /* No more rounds, let's shut it down! */ - { - stats_context = GNUNET_malloc (sizeof (struct StatsContext)); - stats_context->shutdown = GNUNET_YES; - GNUNET_SCHEDULER_cancel (shutdown_handle); - shutdown_handle = GNUNET_SCHEDULER_NO_TASK; - GNUNET_TESTING_get_statistics (pg, &stats_finished_callback, - &statistics_iterator, stats_context); - } - GNUNET_free (buf); } /** - * FIXME. + * We're at the end of a round. Stop monitoring, write total + * number of connections to log and get full stats. Then trigger + * the next round. * - * @param cls unused - * @param emsg NULL on success + * @param cls unused, NULL + * @param tc unused */ static void -topology_output_callback (void *cls, const char *emsg) +finish_round (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) { - disconnect_task = - GNUNET_SCHEDULER_add_delayed (wait_time, &disconnect_nse_peers, NULL); - GNUNET_SCHEDULER_add_now (&connect_nse_service, NULL); + struct StatsContext *stats_context; + char buf[1024]; + size_t buf_len; + + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + "Have %u connections\n", + total_connections); + if (NULL != data_file) + { + buf_len = GNUNET_snprintf (buf, sizeof (buf), + "CONNECTIONS_0: %u\n", + total_connections); + GNUNET_DISK_file_write (data_file, buf, buf_len); + } + close_monitor_connections (); + stats_context = GNUNET_malloc (sizeof (struct StatsContext)); + GNUNET_TESTBED_get_statistics (num_peers_in_round[current_round], + daemons, + &statistics_iterator, + &stats_finished_callback, + stats_context); } /** - * FIXME. - * - * @param cls closure - * @param emsg NULL on success + * We have reached the desired number of peers for the current round. + * Run it (by connecting and monitoring a few peers and waiting the + * specified delay before finishing the round). */ static void -churn_callback (void *cls, const char *emsg) +run_round () { - char *temp_output_file; - - if (emsg == NULL) /* Everything is okay! */ - { - peers_running = peers_next_round; - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Round %llu, churn finished successfully.\n", current_round); - GNUNET_assert (disconnect_task == GNUNET_SCHEDULER_NO_TASK); - GNUNET_asprintf (&temp_output_file, "%s_%llu.dot", topology_file, - current_round); - GNUNET_TESTING_peergroup_topology_to_file (pg, temp_output_file, - &topology_output_callback, NULL); - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Writing topology to file %s\n", - temp_output_file); - GNUNET_free (temp_output_file); - } - else - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Round %llu, churn FAILED!!\n", - current_round); - GNUNET_SCHEDULER_cancel (shutdown_handle); - shutdown_handle = GNUNET_SCHEDULER_add_now (&shutdown_task, NULL); - } + write_topology (); + connect_nse_service (); + GNUNET_SCHEDULER_add_delayed (wait_time, + &finish_round, + NULL); } +/** + * Task run at the end of a round. Disconnect from all monitored + * peers; then get statistics from *all* peers. + * + * @param cls NULL, unused + * @param tc unused + */ static void -churn_peers (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +next_round (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) { - /* peers_running = GNUNET_TESTING_daemons_running(pg); */ - churn_task = GNUNET_SCHEDULER_NO_TASK; - if (peers_next_round == peers_running) - { - /* Nothing to do... */ - GNUNET_SCHEDULER_add_now (&connect_nse_service, NULL); - GNUNET_assert (disconnect_task == GNUNET_SCHEDULER_NO_TASK); - disconnect_task = - GNUNET_SCHEDULER_add_delayed (wait_time, &disconnect_nse_peers, NULL); - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Round %lu, doing nothing!\n", - current_round); - } - else - { - if (peers_next_round > num_peers) + unsigned int i; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "disconnecting nse service of peers\n"); + current_round++; + + if (current_round == num_rounds) { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "Asked to turn on more peers than we have!!\n"); - GNUNET_SCHEDULER_cancel (shutdown_handle); - GNUNET_SCHEDULER_add_now (&shutdown_task, NULL); + /* this was the last round, terminate */ + GNUNET_SCHEDULER_shutdown (); + return; } - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Round %llu, turning off %llu peers, turning on %llu peers!\n", - current_round, - (peers_running > - peers_next_round) ? peers_running - peers_next_round : 0, - (peers_next_round > - peers_running) ? peers_next_round - peers_running : 0); - GNUNET_TESTING_daemons_churn (pg, "nse", - (peers_running > - peers_next_round) ? peers_running - - peers_next_round : 0, - (peers_next_round > - peers_running) ? peers_next_round - - peers_running : 0, wait_time, &churn_callback, - NULL); - } + if (num_peers_in_round[current_round] == peers_running) + { + /* no need to churn, just run next round */ + run_round (); + return; + } + + /* start peers if we have too few */ + for (i=peers_running;itype) + { + case GNUNET_TESTBED_ET_PEER_START: + peers_running++; + if (num_peers_in_round[current_round] == peers_running) + run_round (); + break; + case GNUNET_TESTBED_ET_PEER_STOP: + peers_running--; + if (num_peers_in_round[current_round] == peers_running) + run_round (); + break; + case GNUNET_TESTBED_ET_CONNECT: + total_connections++; + break; + case GNUNET_TESTBED_ET_DISCONNECT: + total_connections--; + break; + default: + break; + } } static void -my_cb (void *cls, const char *emsg) +controller_start_cb (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + int status) { - char *buf; - int buf_len; - - if (emsg != NULL) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Peergroup callback called with error, aborting test!\n"); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Error from testing: `%s'\n"); - ok = 1; - GNUNET_TESTING_daemons_stop (pg, TIMEOUT, &shutdown_callback, NULL); - return; - } -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Peer Group started successfully, connecting to NSE service for each peer!\n"); -#endif - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Have %u connections\n", - total_connections); - if (data_file != NULL) - { - buf = NULL; - buf_len = GNUNET_asprintf (&buf, "CONNECTIONS_0: %u\n", total_connections); - if (buf_len > 0) - GNUNET_DISK_file_write (data_file, buf, buf_len); - GNUNET_free (buf); - } - peers_running = GNUNET_TESTING_daemons_running (pg); - GNUNET_TESTING_daemons_start_service (pg, "nse", wait_time, &nse_started_cb, - NULL); - + if (GNUNET_OK != status) + { + copro = NULL; + GNUNET_SCHEDULER_shutdown (); + return; + } + num_hosts = GNUNET_TESTBED_hosts_load_from_file (hosts_file, + &hosts); + if (0 == num_hosts) + { + fprintf (stderr, + "Failed to read host information from `%s'\n", + hosts_file); + return; + } + controller = GNUNET_TESTBED_controller_connect (cfg, + NULL, + 0 /* mask */, + &master_controller_cb, NULL); + + /* testbed = GNUNET_TESTBED_create (controller, */ + /* num_hosts, hosts, */ + /* num_peers, */ + /* cfg, */ + /* 0 /\* FIXME: topology *\/, */ + /* NULL /\* FIXME: topology options *\/); */ } /** - * Function that will be called whenever two daemons are connected by - * the testing library. + * Actual main function that runs the emulation. * - * @param cls closure - * @param first peer id for first daemon - * @param second peer id for the second daemon - * @param distance distance between the connected peers - * @param first_cfg config for the first daemon - * @param second_cfg config for the second daemon - * @param first_daemon handle for the first daemon - * @param second_daemon handle for the second daemon - * @param emsg error message (NULL on success) + * @param cls unused + * @param args remaining args, unused + * @param cfgfile name of the configuration + * @param cfg configuration handle */ -static void -connect_cb (void *cls, const struct GNUNET_PeerIdentity *first, - const struct GNUNET_PeerIdentity *second, uint32_t distance, - const struct GNUNET_CONFIGURATION_Handle *first_cfg, - const struct GNUNET_CONFIGURATION_Handle *second_cfg, - struct GNUNET_TESTING_Daemon *first_daemon, - struct GNUNET_TESTING_Daemon *second_daemon, const char *emsg) -{ - if (emsg == NULL) - total_connections++; -} - - static void run (void *cls, char *const *args, const char *cfgfile, const struct GNUNET_CONFIGURATION_Handle *cfg) { - char *temp_str; - struct GNUNET_TESTING_Host *hosts; - char *data_filename; + char *tok; + unsigned int num; ok = 1; - //testing_cfg = GNUNET_CONFIGURATION_create (); testing_cfg = GNUNET_CONFIGURATION_dup (cfg); -#if VERBOSE GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Starting daemons.\n"); - GNUNET_CONFIGURATION_set_value_string (testing_cfg, "testing", - "use_progressbars", "YES"); -#endif - if (GNUNET_OK != - GNUNET_CONFIGURATION_get_value_number (testing_cfg, "testing", - "num_peers", &num_peers)) + if (verbose) + GNUNET_CONFIGURATION_set_value_string (testing_cfg, "testing", + "use_progressbars", "YES"); + if (NULL == num_peer_spec) { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "Option TESTING:NUM_PEERS is required!\n"); + fprintf (stderr, "You need to specify the number of peers to run\n"); return; } - - if (GNUNET_OK != - GNUNET_CONFIGURATION_get_value_time (testing_cfg, "nse-profiler", - "WAIT_TIME", &wait_time)) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "Option nse-profiler:wait_time is required!\n"); - return; - } - - if (GNUNET_OK != - GNUNET_CONFIGURATION_get_value_time (testing_cfg, "nse", - "INTERVAL", &interval)) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "Option nse:interval is required!\n"); - return; - } - - if (GNUNET_OK != - GNUNET_CONFIGURATION_get_value_number (testing_cfg, "nse-profiler", - "connection_limit", - &connection_limit)) - { - connection_limit = 0; - } - - if (GNUNET_OK != - GNUNET_CONFIGURATION_get_value_string (testing_cfg, "nse-profiler", - "topology_output_file", - &topology_file)) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "Option nse-profiler:topology_output_file is required!\n"); - return; - } - - if (GNUNET_OK == - GNUNET_CONFIGURATION_get_value_string (testing_cfg, "nse-profiler", - "data_output_file", - &data_filename)) - { - data_file = - GNUNET_DISK_file_open (data_filename, - GNUNET_DISK_OPEN_READWRITE | - GNUNET_DISK_OPEN_TRUNCATE | - GNUNET_DISK_OPEN_CREATE, - GNUNET_DISK_PERM_USER_READ | - GNUNET_DISK_PERM_USER_WRITE); - if (data_file == NULL) - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Failed to open %s for output!\n", - data_filename); - GNUNET_free (data_filename); - } - - if (GNUNET_YES == - GNUNET_CONFIGURATION_get_value_string (cfg, "nse-profiler", "output_file", - &temp_str)) - { - output_file = - GNUNET_DISK_file_open (temp_str, - GNUNET_DISK_OPEN_READWRITE | - GNUNET_DISK_OPEN_CREATE, - GNUNET_DISK_PERM_USER_READ | - GNUNET_DISK_PERM_USER_WRITE); - if (output_file == NULL) - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Failed to open %s for output!\n", - temp_str); - } - GNUNET_free_non_null (temp_str); - - hosts = GNUNET_TESTING_hosts_load (testing_cfg); - - pg = GNUNET_TESTING_peergroup_start (testing_cfg, num_peers, TIMEOUT, - &connect_cb, &my_cb, NULL, hosts); - GNUNET_assert (pg != NULL); - shutdown_handle = - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, - &shutdown_task, NULL); + for (tok = strtok (num_peer_spec, ","); NULL != tok; tok = strtok (NULL, ",")) + { + if (1 != sscanf (tok, "%u", &num)) + { + fprintf (stderr, "You need to specify numbers, not `%s'\n", tok); + return; + } + if (0 == num) + { + fprintf (stderr, "Refusing to run a round with 0 peers\n"); + return; + } + GNUNET_array_grow (num_peers_in_round, num_rounds, num); + num_peers = GNUNET_MAX (num_peers, num); + } + if (0 == num_peers) + { + fprintf (stderr, "Refusing to run a testbed with no rounds\n"); + return; + } + daemons = GNUNET_malloc (sizeof (struct GNUNET_TESTBED_Peer*) * num_peers); + if ( (NULL != data_filename) && + (NULL == (data_file = + GNUNET_DISK_file_open (data_filename, + GNUNET_DISK_OPEN_READWRITE | + GNUNET_DISK_OPEN_TRUNCATE | + GNUNET_DISK_OPEN_CREATE, + GNUNET_DISK_PERM_USER_READ | + GNUNET_DISK_PERM_USER_WRITE))) ) + GNUNET_log_strerror_file (GNUNET_ERROR_TYPE_ERROR, + "open", + data_filename); + + if ( (NULL != output_filename) && + (NULL == (output_file = + GNUNET_DISK_file_open (output_filename, + GNUNET_DISK_OPEN_READWRITE | + GNUNET_DISK_OPEN_CREATE, + GNUNET_DISK_PERM_USER_READ | + GNUNET_DISK_PERM_USER_WRITE))) ) + GNUNET_log_strerror_file (GNUNET_ERROR_TYPE_ERROR, "open", + output_filename); + + if (NULL == + (copro = GNUNET_TESTBED_controller_start (controller_ip, NULL, + cfg, + &controller_start_cb, NULL))) + { + fprintf (stderr, + "Failed to start controller\n"); + return; + } + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, + &shutdown_task, NULL); } - /** - * nse-profiler command line options + * Main function. + * + * @return 0 on success */ -static struct GNUNET_GETOPT_CommandLineOption options[] = { - {'V', "verbose", NULL, - gettext_noop ("be verbose (print progress information)"), - 0, &GNUNET_GETOPT_set_one, &verbose}, - GNUNET_GETOPT_OPTION_END -}; - - int -main (int argc, char *argv[]) +main (int argc, char *const *argv) { - GNUNET_log_setup ("nse-profiler", -#if VERBOSE - "DEBUG", -#else - "WARNING", -#endif - NULL); - GNUNET_PROGRAM_run (argc, argv, "nse-profiler", - gettext_noop - ("Measure quality and performance of the NSE service."), - options, &run, NULL); -#if REMOVE_DIR - GNUNET_DISK_directory_remove ("/tmp/nse-profiler"); -#endif + static struct GNUNET_GETOPT_CommandLineOption options[] = { + {'C', "connections", "COUNT", + gettext_noop ("limit to the number of connections to NSE services, 0 for none"), + 1, &GNUNET_GETOPT_set_string, &num_peer_spec}, + {'d', "details", "FILENAME", + gettext_noop ("name of the file for writing connection information and statistics"), + 1, &GNUNET_GETOPT_set_string, &data_filename}, + {'H', "hosts", "FILENAME", + gettext_noop ("name of the file with the login information for the testbed"), + 1, &GNUNET_GETOPT_set_string, &hosts_file}, + {'i', "ip", "CONTROLLER_IP", + gettext_noop ("IP address of this system as seen by the rest of the testbed"), + 1, &GNUNET_GETOPT_set_string, &controller_ip}, + {'I', "interval", "DELAY", + gettext_noop ("delay between queries to statistics during a round"), + 1, &GNUNET_GETOPT_set_relative_time, &interval}, + {'t', "topology", "FILENAME", + gettext_noop ("prefix of the filenames we use for writing the topology for each round"), + 1, &GNUNET_GETOPT_set_string, &topology_file}, + {'o', "output", "FILENAME", + gettext_noop ("name of the file for writing the main results"), + 1, &GNUNET_GETOPT_set_string, &output_filename}, + {'p', "peers", "NETWORKSIZESPEC", + gettext_noop ("Number of peers to run in each round, separated by commas"), + 1, &GNUNET_GETOPT_set_string, &num_peer_spec}, + {'V', "verbose", NULL, + gettext_noop ("be verbose (print progress information)"), + 0, &GNUNET_GETOPT_increment_value, &verbose}, + {'w', "wait", "DELAY", + gettext_noop ("delay between rounds"), + 1, &GNUNET_GETOPT_set_relative_time, &wait_time}, + GNUNET_GETOPT_OPTION_END + }; + if (GNUNET_OK != GNUNET_STRINGS_get_utf8_args (argc, argv, &argc, &argv)) + return 2; + GNUNET_log_setup ("nse-profiler", "WARNING", NULL); + if (GNUNET_OK != + GNUNET_PROGRAM_run (argc, argv, "nse-profiler", + gettext_noop + ("Measure quality and performance of the NSE service."), + options, &run, NULL)) + ok = 1; return ok; } diff --git a/src/nse/gnunet-service-nse.c b/src/nse/gnunet-service-nse.c index 9c31ab8..f7352f0 100644 --- a/src/nse/gnunet-service-nse.c +++ b/src/nse/gnunet-service-nse.c @@ -1,6 +1,6 @@ /* This file is part of GNUnet. - (C) 2009, 2010, 2011 Christian Grothoff (and other contributing authors) + (C) 2009, 2010, 2011, 2012 Christian Grothoff (and other contributing authors) GNUnet is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published @@ -304,6 +304,16 @@ static struct GNUNET_PeerIdentity my_identity; */ static uint64_t my_proof; +/** + * Handle to this serivce's server. + */ +static struct GNUNET_SERVER_Handle *srv; + +/** + * Hostkey generation context + */ +static struct GNUNET_CRYPTO_RsaKeyGenerationContext *keygen; + /** * Initialize a message to clients with the current network @@ -477,7 +487,7 @@ static uint32_t get_matching_bits (struct GNUNET_TIME_Absolute timestamp, const struct GNUNET_PeerIdentity *id) { - GNUNET_HashCode timestamp_hash; + struct GNUNET_HashCode timestamp_hash; GNUNET_CRYPTO_hash (×tamp.abs_value, sizeof (timestamp.abs_value), ×tamp_hash); @@ -576,7 +586,7 @@ transmit_ready (void *cls, size_t size, void *buf) GNUNET_SCHEDULER_add_delayed (get_transmit_delay (0), &transmit_task_cb, peer_entry); } - if ((ntohl (size_estimate_messages[idx].hop_count) == 0) && + if ((0 == ntohl (size_estimate_messages[idx].hop_count)) && (GNUNET_SCHEDULER_NO_TASK != proof_task)) { GNUNET_STATISTICS_update (stats, @@ -584,7 +594,7 @@ transmit_ready (void *cls, size_t size, void *buf) 1, GNUNET_NO); return 0; } - if (ntohs (size_estimate_messages[idx].header.size) == 0) + if (0 == ntohs (size_estimate_messages[idx].header.size)) { GNUNET_STATISTICS_update (stats, "# flood messages not generated (lack of history)", @@ -661,7 +671,8 @@ update_network_size_estimate () * @param ts timestamp to use */ static void -setup_flood_message (unsigned int slot, struct GNUNET_TIME_Absolute ts) +setup_flood_message (unsigned int slot, + struct GNUNET_TIME_Absolute ts) { struct GNUNET_NSE_FloodMessage *fm; uint32_t matching_bits; @@ -699,7 +710,9 @@ setup_flood_message (unsigned int slot, struct GNUNET_TIME_Absolute ts) * @return GNUNET_OK (continue to iterate) */ static int -schedule_current_round (void *cls, const GNUNET_HashCode * key, void *value) +schedule_current_round (void *cls, + const struct GNUNET_HashCode * key, + void *value) { struct NSEPeerEntry *peer_entry = value; struct GNUNET_TIME_Relative delay; @@ -791,7 +804,7 @@ update_flood_message (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) * @return the number of leading zero bits. */ static unsigned int -count_leading_zeroes (const GNUNET_HashCode * hash) +count_leading_zeroes (const struct GNUNET_HashCode * hash) { unsigned int hash_count; @@ -817,7 +830,7 @@ check_proof_of_work (const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *pkey, { char buf[sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded) + sizeof (val)] GNUNET_ALIGN; - GNUNET_HashCode result; + struct GNUNET_HashCode result; memcpy (buf, &val, sizeof (val)); memcpy (&buf[sizeof (val)], pkey, @@ -862,7 +875,7 @@ find_proof (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) uint64_t counter; char buf[sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded) + sizeof (uint64_t)] GNUNET_ALIGN; - GNUNET_HashCode result; + struct GNUNET_HashCode result; unsigned int i; proof_task = GNUNET_SCHEDULER_NO_TASK; @@ -922,7 +935,7 @@ verify_message_crypto (const struct GNUNET_NSE_FloodMessage *incoming_flood) check_proof_of_work (&incoming_flood->pkey, incoming_flood->proof_of_work)) { - GNUNET_log (GNUNET_ERROR_TYPE_INFO, _("Proof of work invalid: %llu!\n"), + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Proof of work invalid: %llu!\n", (unsigned long long) GNUNET_ntohll (incoming_flood->proof_of_work)); GNUNET_break_op (0); @@ -952,13 +965,13 @@ verify_message_crypto (const struct GNUNET_NSE_FloodMessage *incoming_flood) * @return GNUNET_OK (continue to iterate) */ static int -update_flood_times (void *cls, const GNUNET_HashCode * key, void *value) +update_flood_times (void *cls, const struct GNUNET_HashCode * key, void *value) { struct NSEPeerEntry *exclude = cls; struct NSEPeerEntry *peer_entry = value; struct GNUNET_TIME_Relative delay; - if (peer_entry->th != NULL) + if (NULL != peer_entry->th) return GNUNET_OK; /* already active */ if (peer_entry == exclude) return GNUNET_OK; /* trigger of the update */ @@ -966,14 +979,14 @@ update_flood_times (void *cls, const GNUNET_HashCode * key, void *value) { /* still stuck in previous round, no point to update, check that * we are active here though... */ - if (GNUNET_SCHEDULER_NO_TASK == peer_entry->transmit_task && - NULL == peer_entry->th) + if ( (GNUNET_SCHEDULER_NO_TASK == peer_entry->transmit_task) && + (NULL == peer_entry->th) ) { GNUNET_break (0); } return GNUNET_OK; } - if (peer_entry->transmit_task != GNUNET_SCHEDULER_NO_TASK) + if (GNUNET_SCHEDULER_NO_TASK != peer_entry->transmit_task) { GNUNET_SCHEDULER_cancel (peer_entry->transmit_task); peer_entry->transmit_task = GNUNET_SCHEDULER_NO_TASK; @@ -1099,7 +1112,7 @@ handle_p2p_size_estimate (void *cls, const struct GNUNET_PeerIdentity *peer, GNUNET_SCHEDULER_cancel (peer_entry->transmit_task); peer_entry->transmit_task = GNUNET_SCHEDULER_NO_TASK; } - if (peer_entry->th != NULL) + if (NULL != peer_entry->th) { GNUNET_CORE_notify_transmit_ready_cancel (peer_entry->th); peer_entry->th = NULL; @@ -1228,7 +1241,7 @@ handle_core_disconnect (void *cls, const struct GNUNET_PeerIdentity *peer) GNUNET_SCHEDULER_cancel (pos->transmit_task); pos->transmit_task = GNUNET_SCHEDULER_NO_TASK; } - if (pos->th != NULL) + if (NULL != pos->th) { GNUNET_CORE_notify_transmit_ready_cancel (pos->th); pos->th = NULL; @@ -1247,44 +1260,49 @@ handle_core_disconnect (void *cls, const struct GNUNET_PeerIdentity *peer) static void shutdown_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { - if (flood_task != GNUNET_SCHEDULER_NO_TASK) + if (GNUNET_SCHEDULER_NO_TASK != flood_task) { GNUNET_SCHEDULER_cancel (flood_task); flood_task = GNUNET_SCHEDULER_NO_TASK; } - if (proof_task != GNUNET_SCHEDULER_NO_TASK) + if (GNUNET_SCHEDULER_NO_TASK != proof_task) { GNUNET_SCHEDULER_cancel (proof_task); proof_task = GNUNET_SCHEDULER_NO_TASK; write_proof (); /* remember progress */ } - if (nc != NULL) + if (NULL != keygen) + { + GNUNET_CRYPTO_rsa_key_create_stop (keygen); + keygen = NULL; + } + if (NULL != nc) { GNUNET_SERVER_notification_context_destroy (nc); nc = NULL; } - if (coreAPI != NULL) + if (NULL != coreAPI) { GNUNET_CORE_disconnect (coreAPI); coreAPI = NULL; } - if (stats != NULL) + if (NULL != stats) { GNUNET_STATISTICS_destroy (stats, GNUNET_NO); stats = NULL; } - if (peers != NULL) + if (NULL != peers) { GNUNET_CONTAINER_multihashmap_destroy (peers); peers = NULL; } - if (my_private_key != NULL) + if (NULL != my_private_key) { GNUNET_CRYPTO_rsa_key_free (my_private_key); my_private_key = NULL; } #if ENABLE_HISTOGRAM - if (wh != NULL) + if (NULL != wh) { GNUNET_break (GNUNET_OK == GNUNET_BIO_write_close (wh)); wh = NULL; @@ -1341,19 +1359,17 @@ core_init (void *cls, struct GNUNET_CORE_Handle *server, /** - * Handle network size estimate clients. + * Callback for hostkey read/generation * - * @param cls closure - * @param server the initialized server - * @param c configuration to use + * @param cls NULL + * @param pk the private key + * @param emsg error message */ static void -run (void *cls, struct GNUNET_SERVER_Handle *server, - const struct GNUNET_CONFIGURATION_Handle *c) +key_generation_cb (void *cls, + struct GNUNET_CRYPTO_RsaPrivateKey *pk, + const char *emsg) { - char *keyfile; - char *proof; - static const struct GNUNET_SERVER_MessageHandler handlers[] = { {&handle_start_message, NULL, GNUNET_MESSAGE_TYPE_NSE_START, sizeof (struct GNUNET_MessageHeader)}, @@ -1364,52 +1380,18 @@ run (void *cls, struct GNUNET_SERVER_Handle *server, sizeof (struct GNUNET_NSE_FloodMessage)}, {NULL, 0, 0} }; - cfg = c; - - if ((GNUNET_OK != - GNUNET_CONFIGURATION_get_value_time (cfg, "NSE", "INTERVAL", - &gnunet_nse_interval)) || - (GNUNET_OK != - GNUNET_CONFIGURATION_get_value_time (cfg, "NSE", "WORKDELAY", - &proof_find_delay)) || - (GNUNET_OK != - GNUNET_CONFIGURATION_get_value_number (cfg, "NSE", "WORKBITS", - &nse_work_required))) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - _ - ("NSE service is lacking key configuration settings. Exiting.\n")); - GNUNET_SCHEDULER_shutdown (); - return; - } - if (nse_work_required >= sizeof (GNUNET_HashCode) * 8) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - _("Invalid work requirement for NSE service. Exiting.\n")); - GNUNET_SCHEDULER_shutdown (); - return; - } - + char *proof; - if (GNUNET_OK != - GNUNET_CONFIGURATION_get_value_filename (cfg, "GNUNETD", "HOSTKEY", - &keyfile)) + keygen = NULL; + if (NULL == pk) { GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - _ - ("NSE service is lacking key configuration settings. Exiting.\n")); - GNUNET_SCHEDULER_shutdown (); - return; - } - my_private_key = GNUNET_CRYPTO_rsa_key_create_from_file (keyfile); - GNUNET_free (keyfile); - if (my_private_key == NULL) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - _("NSE service could not access hostkey. Exiting.\n")); + _("NSE service could not access hostkey: %s\n"), + emsg); GNUNET_SCHEDULER_shutdown (); return; } + my_private_key = pk; GNUNET_CRYPTO_rsa_key_get_public (my_private_key, &my_public_key); GNUNET_CRYPTO_hash (&my_public_key, sizeof (my_public_key), &my_identity.hashPubKey); @@ -1419,11 +1401,8 @@ run (void *cls, struct GNUNET_SERVER_Handle *server, GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _ ("NSE service is lacking key configuration settings. Exiting.\n")); - if (my_private_key != NULL) - { - GNUNET_CRYPTO_rsa_key_free (my_private_key); - my_private_key = NULL; - } + GNUNET_CRYPTO_rsa_key_free (my_private_key); + my_private_key = NULL; GNUNET_SCHEDULER_shutdown (); return; } @@ -1436,12 +1415,12 @@ run (void *cls, struct GNUNET_SERVER_Handle *server, GNUNET_SCHEDULER_add_with_priority (GNUNET_SCHEDULER_PRIORITY_IDLE, &find_proof, NULL); - peers = GNUNET_CONTAINER_multihashmap_create (128); - GNUNET_SERVER_add_handlers (server, handlers); - nc = GNUNET_SERVER_notification_context_create (server, 1); + peers = GNUNET_CONTAINER_multihashmap_create (128, GNUNET_NO); + GNUNET_SERVER_add_handlers (srv, handlers); + nc = GNUNET_SERVER_notification_context_create (srv, 1); /* Connect to core service and register core handlers */ coreAPI = GNUNET_CORE_connect (cfg, /* Main configuration */ - 1, NULL, /* Closure passed to functions */ + NULL, /* Closure passed to functions */ &core_init, /* Call core_init once connected */ &handle_core_connect, /* Handle connects */ &handle_core_disconnect, /* Handle disconnects */ @@ -1450,8 +1429,11 @@ run (void *cls, struct GNUNET_SERVER_Handle *server, NULL, /* Don't want notified about all outbound messages */ GNUNET_NO, /* For header only outbound notification */ core_handlers); /* Register these handlers */ - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, &shutdown_task, - NULL); + if (NULL == coreAPI) + { + GNUNET_SCHEDULER_shutdown (); + return; + } #if ENABLE_HISTOGRAM if (GNUNET_OK == GNUNET_CONFIGURATION_get_value_filename (cfg, "NSE", "HISTOGRAM", &proof)) @@ -1460,17 +1442,70 @@ run (void *cls, struct GNUNET_SERVER_Handle *server, GNUNET_free (proof); } #endif - if (coreAPI == NULL) + stats = GNUNET_STATISTICS_create ("nse", cfg); + GNUNET_SERVER_resume (srv); +} + + +/** + * Handle network size estimate clients. + * + * @param cls closure + * @param server the initialized server + * @param c configuration to use + */ +static void +run (void *cls, + struct GNUNET_SERVER_Handle *server, + const struct GNUNET_CONFIGURATION_Handle *c) +{ + char *keyfile; + + cfg = c; + srv = server; + if ((GNUNET_OK != + GNUNET_CONFIGURATION_get_value_time (cfg, "NSE", "INTERVAL", + &gnunet_nse_interval)) || + (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_time (cfg, "NSE", "WORKDELAY", + &proof_find_delay)) || + (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_number (cfg, "NSE", "WORKBITS", + &nse_work_required))) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _ + ("NSE service is lacking key configuration settings. Exiting.\n")); + GNUNET_SCHEDULER_shutdown (); + return; + } + if (nse_work_required >= sizeof (struct GNUNET_HashCode) * 8) { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Invalid work requirement for NSE service. Exiting.\n")); GNUNET_SCHEDULER_shutdown (); return; } - stats = GNUNET_STATISTICS_create ("nse", cfg); + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_filename (cfg, "GNUNETD", "HOSTKEY", + &keyfile)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _ + ("NSE service is lacking key configuration settings. Exiting.\n")); + GNUNET_SCHEDULER_shutdown (); + return; + } + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, &shutdown_task, + NULL); + GNUNET_SERVER_suspend (srv); + keygen = GNUNET_CRYPTO_rsa_key_create_start (keyfile, &key_generation_cb, NULL); + GNUNET_free (keyfile); } /** - * The main function for the statistics service. + * The main function for the network size estimation service. * * @param argc number of arguments from the command line * @param argv command line arguments @@ -1484,4 +1519,21 @@ main (int argc, char *const *argv) &run, NULL)) ? 0 : 1; } + +#ifdef LINUX +#include + +/** + * MINIMIZE heap size (way below 128k) since this process doesn't need much. + */ +void __attribute__ ((constructor)) GNUNET_ARM_memory_init () +{ + mallopt (M_TRIM_THRESHOLD, 4 * 1024); + mallopt (M_TOP_PAD, 1 * 1024); + malloc_trim (0); +} +#endif + + + /* end of gnunet-service-nse.c */ diff --git a/src/nse/nse.conf.in b/src/nse/nse.conf.in index bc49e05..84f1f6c 100644 --- a/src/nse/nse.conf.in +++ b/src/nse/nse.conf.in @@ -3,7 +3,6 @@ AUTOSTART = YES @JAVAPORT@PORT = 2097 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-nse ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; diff --git a/src/nse/nse_api.c b/src/nse/nse_api.c index 9a44197..136f4b6 100644 --- a/src/nse/nse_api.c +++ b/src/nse/nse_api.c @@ -154,16 +154,7 @@ reschedule_connect (struct GNUNET_NSE_Handle *h) h->reconnect_delay.rel_value); h->reconnect_task = GNUNET_SCHEDULER_add_delayed (h->reconnect_delay, &reconnect, h); - if (h->reconnect_delay.rel_value == 0) - { - h->reconnect_delay = GNUNET_TIME_UNIT_MILLISECONDS; - } - else - { - h->reconnect_delay = GNUNET_TIME_relative_multiply (h->reconnect_delay, 2); - h->reconnect_delay = - GNUNET_TIME_relative_min (GNUNET_TIME_UNIT_SECONDS, h->reconnect_delay); - } + h->reconnect_delay = GNUNET_TIME_STD_BACKOFF (h->reconnect_delay); } diff --git a/src/nse/nse_profiler_test.conf b/src/nse/nse_profiler_test.conf index 3a3217d..398eb27 100644 --- a/src/nse/nse_profiler_test.conf +++ b/src/nse/nse_profiler_test.conf @@ -1,6 +1,5 @@ [PATHS] SERVICEHOME = /tmp/nse-profiler/ -DEFAULTCONFIG = nse_profiler_test.conf [nse] PORT = 0 @@ -9,8 +8,6 @@ BINARY = gnunet-service-nse #BINARY = /home/mrwiggles/documents/research/gnunet/gnunet-ng/src/nse/.libs/gnunet-service-nse #PREFIX = valgrind --leak-check=full --log-file=valgrind_nse.%p AUTOSTART = NO -DEBUG = YES -CONFIG = $DEFAULTCONFIG # Overriding network settings for faster testing (do NOT use # these values in production just because they are here) WORKDELAY = 60 s @@ -22,7 +19,6 @@ PROOFFILE = $SERVICEHOME/nse.proof PORT = 0 DEFAULTSERVICES = core UNIXPATH = /tmp/test-nse-service-arm.unix -#DEBUG = YES [statistics] AUTOSTART = YES @@ -104,8 +100,10 @@ AUTOSTART = NO AUTOSTART = NO [testing] -NUM_PEERS = 2000 WEAKRANDOM = YES + +[testing_old] +NUM_PEERS = 2000 TOPOLOGY = NONE #CONNECT_TOPOLOGY = SMALL_WORLD_RING CONNECT_TOPOLOGY = ERDOS_RENYI @@ -116,7 +114,6 @@ PROBABILITY = .1 F2F = NO CONNECT_TIMEOUT = 360 s CONNECT_ATTEMPTS = 3 -DEBUG = YES #HOSTKEYSFILE = ../../contrib/testing_hostkeys.dat HOSTKEYSFILE = hostkeys.dat MAX_CONCURRENT_SSH = 20 diff --git a/src/nse/test_nse.conf b/src/nse/test_nse.conf index 48944c1..5652fa4 100644 --- a/src/nse/test_nse.conf +++ b/src/nse/test_nse.conf @@ -1,6 +1,5 @@ [PATHS] SERVICEHOME = /tmp/test-nse-multipeer/ -DEFAULTCONFIG = test_nse.conf [nse] PORT = 22353 @@ -9,8 +8,6 @@ BINARY = gnunet-service-nse #BINARY = /home/mrwiggles/documents/research/gnunet/gnunet-ng/src/nse/.libs/gnunet-service-nse #PREFIX = valgrind --leak-check=full --log-file=valgrind_nse.%p AUTOSTART = YES -DEBUG = NO -CONFIG = $DEFAULTCONFIG PROOFFILE = $SERVICEHOME/proof.nse # Overriding network settings for faster testing (do NOT use # these values in production just because they are here) @@ -25,7 +22,6 @@ HISTOGRAM = $SERVICEHOME/nse-histogram PORT = 22354 DEFAULTSERVICES = nse core UNIXPATH = /tmp/test-nse-service-arm.unix -#DEBUG = YES [fs] AUTOSTART = NO @@ -58,16 +54,17 @@ EXTERNAL_ADDRESS = 127.0.0.1 AUTOSTART = NO [testing] -NUM_PEERS = 10 WEAKRANDOM = YES + +[testing_old] +NUM_PEERS = 10 TOPOLOGY = NONE CONNECT_TOPOLOGY = SMALL_WORLD_RING PERCENTAGE = 3 F2F = NO CONNECT_TIMEOUT = 60 s CONNECT_ATTEMPTS = 3 -#DEBUG = YES -HOSTKEYSFILE = ../../contrib/testing_hostkeys.dat +HOSTKEYSFILE = ${DATADIR}/testing_hostkeys.dat MAX_CONCURRENT_SSH = 20 USE_PROGRESSBARS = YES PEERGROUP_TIMEOUT = 1000 s @@ -75,3 +72,5 @@ PEERGROUP_TIMEOUT = 1000 s DELETE_FILES = NO +[consensus] +AUTOSTART = NO diff --git a/src/nse/test_nse_api.c b/src/nse/test_nse_api.c index f99cb3b..171595b 100644 --- a/src/nse/test_nse_api.c +++ b/src/nse/test_nse_api.c @@ -22,42 +22,15 @@ * @brief testcase for nse_api.c */ #include "platform.h" -#include "gnunet_common.h" -#include "gnunet_getopt_lib.h" -#include "gnunet_os_lib.h" -#include "gnunet_program_lib.h" -#include "gnunet_scheduler_lib.h" +#include "gnunet_util_lib.h" #include "gnunet_nse_service.h" +#include "gnunet_testing_lib.h" -#define START_ARM GNUNET_YES static struct GNUNET_NSE_Handle *h; static GNUNET_SCHEDULER_TaskIdentifier die_task; -struct PeerContext -{ - struct GNUNET_CONFIGURATION_Handle *cfg; -#if START_ARM - struct GNUNET_OS_Process *arm_proc; -#endif -}; - -static struct PeerContext p1; - - -static void -stop_arm (struct PeerContext *p) -{ -#if START_ARM - if (0 != GNUNET_OS_process_kill (p->arm_proc, SIGTERM)) - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); - GNUNET_OS_process_wait (p->arm_proc); - GNUNET_OS_process_destroy (p->arm_proc); - p->arm_proc = NULL; -#endif - GNUNET_CONFIGURATION_destroy (p->cfg); -} /** * Signature of the main function of a task. @@ -103,74 +76,31 @@ check_nse_message (void *cls, struct GNUNET_TIME_Absolute timestamp, static void -setup_peer (struct PeerContext *p, const char *cfgname) -{ - p->cfg = GNUNET_CONFIGURATION_create (); -#if START_ARM - p->arm_proc = - GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-arm", - "gnunet-service-arm", -#if VERBOSE_ARM - "-L", "DEBUG", -#endif - "-c", cfgname, NULL); -#endif - GNUNET_assert (GNUNET_OK == GNUNET_CONFIGURATION_load (p->cfg, cfgname)); - -} - - - -static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) { die_task = GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MINUTES, 1), &end_test, NULL); - setup_peer (&p1, cfgfile); h = GNUNET_NSE_connect (cfg, &check_nse_message, cls); GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Connecting to NSE service.\n"); GNUNET_assert (h != NULL); } -static int -check () -{ - int ok = 1; - - char *const argv[] = { "test-nse-api", - "-c", - "test_nse.conf", - "-L", "WARNING", - NULL - }; - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - - GNUNET_PROGRAM_run (5, argv, "test-nse-api", "nohelp", options, &run, &ok); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stopping arm.\n"); - stop_arm (&p1); - if (0 != ok) - FPRINTF (stderr, "%s", "No information received from NSE service!\n"); - return ok; -} - - int main (int argc, char *argv[]) { - int ret; + int ok = 1; - GNUNET_log_setup ("test_nse_api", - "WARNING", - NULL); - ret = check (); - return ret; + if (0 != GNUNET_TESTING_peer_run ("test_nse_api", + "test_nse.conf", + &run, &ok)) + return 1; + return ok; } /* end of test_nse_api.c */ diff --git a/src/nse/test_nse_multipeer.c b/src/nse/test_nse_multipeer.c index 28d066b..2b8c367 100644 --- a/src/nse/test_nse_multipeer.c +++ b/src/nse/test_nse_multipeer.c @@ -1,6 +1,6 @@ /* This file is part of GNUnet. - (C) 2009 Christian Grothoff (and other contributing authors) + (C) 2009, 2012 Christian Grothoff (and other contributing authors) GNUnet is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published @@ -19,93 +19,69 @@ */ /** * @file nse/test_nse_multipeer.c - * * @brief Testcase for the network size estimation service. Starts * a peergroup with a given number of peers, then waits to * receive size estimates from each peer. Expects to wait * for one message from each peer. */ #include "platform.h" -#include "gnunet_testing_lib.h" +#include "gnunet_testbed_service.h" #include "gnunet_nse_service.h" -#define VERBOSE GNUNET_NO +/** + * How many peers do we start? + */ #define NUM_PEERS 4 -struct NSEPeer -{ - struct NSEPeer *prev; - - struct NSEPeer *next; +/** + * How long do we run the test? + */ +#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 300) - struct GNUNET_TESTING_Daemon *daemon; +/** + * Information we track for each peer. + */ +struct NSEPeer +{ + /** + * Handle for NSE connect operation. + */ + struct GNUNET_TESTBED_Operation *op; + + /** + * Handle to NSE service. + */ struct GNUNET_NSE_Handle *nse_handle; }; -struct NSEPeer *peer_head; - -struct NSEPeer *peer_tail; /** - * How long do we run the test? + * Information for all the peers. */ -#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 300) +static struct NSEPeer nse_peers[NUM_PEERS]; +/** + * Return value from 'main'. + */ static int ok; -static int peers_left; - -static unsigned int num_peers; - -static unsigned int total_connections; - -static struct GNUNET_TESTING_PeerGroup *pg; /** - * Check whether peers successfully shut down. + * Task run on timeout to shut everything down. */ -static void -shutdown_callback (void *cls, const char *emsg) -{ - if (emsg != NULL) - { -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Shutdown of peers failed: %s!\n", - emsg); -#endif - if (ok == 0) - ok = 666; - } - else - { -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "All peers successfully shut down!\n"); -#endif - ok = 0; - } -} - static void shutdown_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { - struct NSEPeer *pos; - -#if VERBOSE - FPRINTF (stderr, "%s", "Ending test.\n"); -#endif - - while (NULL != (pos = peer_head)) - { - GNUNET_NSE_disconnect (pos->nse_handle); - GNUNET_CONTAINER_DLL_remove (peer_head, peer_tail, pos); - GNUNET_free (pos); - } + unsigned int i; - GNUNET_TESTING_daemons_stop (pg, TIMEOUT, &shutdown_callback, NULL); + for (i=0;idaemon->id), estimate, std_dev, - GNUNET_NSE_log_estimate_to_n (estimate), num_peers); + "Received network size estimate from peer %u. logSize: %f std.dev. %f (%f/%u)\n", + (unsigned int) (peer - nse_peers), + estimate, std_dev, + GNUNET_NSE_log_estimate_to_n (estimate), + NUM_PEERS); + ok = 0; } +/** + * Callback to be called when NSE service connect operation is completed + * + * @param cls the callback closure from functions generating an operation + * @param op the operation that has been finished + * @param ca_result the NSE service handle returned from nse_connect_adapter + * @param emsg error message in case the operation has failed; will be NULL if + * operation has executed successfully. + */ static void -connect_nse_service (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +nse_connect_complete_cb (void *cls, + struct GNUNET_TESTBED_Operation *op, + void *ca_result, + const char *emsg) { - struct NSEPeer *current_peer; - unsigned int i; - -#if VERBOSE - FPRINTF (stderr, "%s", "TEST_NSE_MULTIPEER: connecting to nse service of peers\n"); -#endif - for (i = 0; i < num_peers; i++) - { - current_peer = GNUNET_malloc (sizeof (struct NSEPeer)); - current_peer->daemon = GNUNET_TESTING_daemon_get (pg, i); - current_peer->nse_handle = - GNUNET_NSE_connect (current_peer->daemon->cfg, &handle_estimate, - current_peer); - GNUNET_assert (current_peer->nse_handle != NULL); - GNUNET_CONTAINER_DLL_insert (peer_head, peer_tail, current_peer); - } + struct NSEPeer *peer = cls; + struct GNUNET_NSE_Handle *nse = ca_result; + + GNUNET_assert (op == peer->op); + if (NULL != emsg) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Failed to connect to NSE service: %s\n", + emsg); + ok = 1; + GNUNET_SCHEDULER_shutdown (); + return; + } + peer->nse_handle = nse; } -static void -my_cb (void *cls, const char *emsg) +/** + * Adapter function called to establish a connection to + * the NSE service. + * + * @param cls closure + * @param cfg configuration of the peer to connect to; will be available until + * GNUNET_TESTBED_operation_done() is called on the operation returned + * from GNUNET_TESTBED_service_connect() + * @return service handle to return in 'op_result', NULL on error + */ +static void * +nse_connect_adapter (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg) { - if (emsg != NULL) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Peergroup callback called with error, aborting test!\n"); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Error from testing: `%s'\n"); - ok = 1; - GNUNET_TESTING_daemons_stop (pg, TIMEOUT, &shutdown_callback, NULL); - return; - } -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Peer Group started successfully, connecting to NSE service for each peer!\n"); -#endif - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Have %u connections\n", - total_connections); - - GNUNET_SCHEDULER_add_now (&connect_nse_service, NULL); + return GNUNET_NSE_connect (cfg, + &handle_estimate, + cls); } /** - * Function that will be called whenever - * two daemons are connected by the testing library. - * + * Adapter function called to destroy connection to + * NSE service. + * * @param cls closure - * @param first peer id for first daemon - * @param second peer id for the second daemon - * @param distance distance between the connected peers - * @param first_cfg config for the first daemon - * @param second_cfg config for the second daemon - * @param first_daemon handle for the first daemon - * @param second_daemon handle for the second daemon - * @param emsg error message (NULL on success) + * @param op_result service handle returned from the connect adapter */ static void -connect_cb (void *cls, const struct GNUNET_PeerIdentity *first, - const struct GNUNET_PeerIdentity *second, uint32_t distance, - const struct GNUNET_CONFIGURATION_Handle *first_cfg, - const struct GNUNET_CONFIGURATION_Handle *second_cfg, - struct GNUNET_TESTING_Daemon *first_daemon, - struct GNUNET_TESTING_Daemon *second_daemon, const char *emsg) +nse_disconnect_adapter (void *cls, + void *op_result) { - if (emsg == NULL) - { - //fprintf(stderr, "Connected %s -> %s\n", GNUNET_i2s(first), second_id); - total_connections++; - } + GNUNET_NSE_disconnect (op_result); } - +/** + * Actual "main" function for the testcase. + * + * @param cls closure + * @param num_peers number of peers in 'peers' + * @param peers handle to peers run in the testbed + */ static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) +run (void *cls, + unsigned int num_peers, + struct GNUNET_TESTBED_Peer **peers) { - struct GNUNET_CONFIGURATION_Handle *testing_cfg; - unsigned long long total_peers; - - ok = 1; - testing_cfg = GNUNET_CONFIGURATION_create (); - GNUNET_assert (GNUNET_OK == GNUNET_CONFIGURATION_load (testing_cfg, cfgfile)); - -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Starting daemons.\n"); - GNUNET_CONFIGURATION_set_value_string (testing_cfg, "testing", - "use_progressbars", "YES"); -#endif - if (GNUNET_OK != - GNUNET_CONFIGURATION_get_value_number (testing_cfg, "testing", - "num_peers", &total_peers)) - total_peers = NUM_PEERS; + unsigned int i; - peers_left = total_peers; - num_peers = peers_left; - pg = GNUNET_TESTING_peergroup_start (testing_cfg, peers_left, TIMEOUT, - &connect_cb, &my_cb, NULL, NULL); - GNUNET_assert (pg != NULL); + GNUNET_assert (NUM_PEERS == num_peers); + for (i=0;i/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } pkgdatadir = $(datadir)/@PACKAGE@ pkgincludedir = $(includedir)/@PACKAGE@ pkglibdir = $(libdir)/@PACKAGE@ @@ -41,14 +58,15 @@ DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 am__aclocal_m4_deps = $(top_srcdir)/m4/absolute-header.m4 \ $(top_srcdir)/m4/align.m4 $(top_srcdir)/m4/argz.m4 \ - $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/iconv.m4 \ - $(top_srcdir)/m4/lib-ld.m4 $(top_srcdir)/m4/lib-link.m4 \ - $(top_srcdir)/m4/lib-prefix.m4 $(top_srcdir)/m4/libcurl.m4 \ - $(top_srcdir)/m4/libgcrypt.m4 $(top_srcdir)/m4/libtool.m4 \ - $(top_srcdir)/m4/libunistring.m4 $(top_srcdir)/m4/ltdl.m4 \ - $(top_srcdir)/m4/ltoptions.m4 $(top_srcdir)/m4/ltsugar.m4 \ - $(top_srcdir)/m4/ltversion.m4 $(top_srcdir)/m4/lt~obsolete.m4 \ - $(top_srcdir)/m4/nls.m4 $(top_srcdir)/m4/po.m4 \ + $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/glib-2.0.m4 \ + $(top_srcdir)/m4/iconv.m4 $(top_srcdir)/m4/lib-ld.m4 \ + $(top_srcdir)/m4/lib-link.m4 $(top_srcdir)/m4/lib-prefix.m4 \ + $(top_srcdir)/m4/libcurl.m4 $(top_srcdir)/m4/libgcrypt.m4 \ + $(top_srcdir)/m4/libtool.m4 $(top_srcdir)/m4/libunistring.m4 \ + $(top_srcdir)/m4/ltdl.m4 $(top_srcdir)/m4/ltoptions.m4 \ + $(top_srcdir)/m4/ltsugar.m4 $(top_srcdir)/m4/ltversion.m4 \ + $(top_srcdir)/m4/lt~obsolete.m4 $(top_srcdir)/m4/nls.m4 \ + $(top_srcdir)/m4/pkg.m4 $(top_srcdir)/m4/po.m4 \ $(top_srcdir)/m4/progtest.m4 $(top_srcdir)/acinclude.m4 \ $(top_srcdir)/configure.ac am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ @@ -68,8 +86,8 @@ gnunet_peerinfo_DEPENDENCIES = \ $(top_builddir)/src/hello/libgnunethello.la \ $(top_builddir)/src/statistics/libgnunetstatistics.la \ $(top_builddir)/src/util/libgnunetutil.la -AM_V_lt = $(am__v_lt_$(V)) -am__v_lt_ = $(am__v_lt_$(AM_DEFAULT_VERBOSITY)) +AM_V_lt = $(am__v_lt_@AM_V@) +am__v_lt_ = $(am__v_lt_@AM_DEFAULT_V@) am__v_lt_0 = --silent DEFAULT_INCLUDES = -I.@am__isrc@ -I$(top_builddir) depcomp = $(SHELL) $(top_srcdir)/depcomp @@ -81,24 +99,29 @@ LTCOMPILE = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) \ $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) \ $(AM_CFLAGS) $(CFLAGS) -AM_V_CC = $(am__v_CC_$(V)) -am__v_CC_ = $(am__v_CC_$(AM_DEFAULT_VERBOSITY)) +AM_V_CC = $(am__v_CC_@AM_V@) +am__v_CC_ = $(am__v_CC_@AM_DEFAULT_V@) am__v_CC_0 = @echo " CC " $@; -AM_V_at = $(am__v_at_$(V)) -am__v_at_ = $(am__v_at_$(AM_DEFAULT_VERBOSITY)) +AM_V_at = $(am__v_at_@AM_V@) +am__v_at_ = $(am__v_at_@AM_DEFAULT_V@) am__v_at_0 = @ CCLD = $(CC) LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ $(AM_LDFLAGS) $(LDFLAGS) -o $@ -AM_V_CCLD = $(am__v_CCLD_$(V)) -am__v_CCLD_ = $(am__v_CCLD_$(AM_DEFAULT_VERBOSITY)) +AM_V_CCLD = $(am__v_CCLD_@AM_V@) +am__v_CCLD_ = $(am__v_CCLD_@AM_DEFAULT_V@) am__v_CCLD_0 = @echo " CCLD " $@; -AM_V_GEN = $(am__v_GEN_$(V)) -am__v_GEN_ = $(am__v_GEN_$(AM_DEFAULT_VERBOSITY)) +AM_V_GEN = $(am__v_GEN_@AM_V@) +am__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@) am__v_GEN_0 = @echo " GEN " $@; SOURCES = $(gnunet_peerinfo_SOURCES) DIST_SOURCES = $(gnunet_peerinfo_SOURCES) +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac ETAGS = etags CTAGS = ctags am__tty_colors = \ @@ -139,6 +162,10 @@ EXEEXT = @EXEEXT@ EXT_LIBS = @EXT_LIBS@ EXT_LIB_PATH = @EXT_LIB_PATH@ FGREP = @FGREP@ +GLIB_CFLAGS = @GLIB_CFLAGS@ +GLIB_GENMARSHAL = @GLIB_GENMARSHAL@ +GLIB_LIBS = @GLIB_LIBS@ +GLIB_MKENUMS = @GLIB_MKENUMS@ GMSGFMT = @GMSGFMT@ GMSGFMT_015 = @GMSGFMT_015@ GNUNETDNS_GROUP = @GNUNETDNS_GROUP@ @@ -149,6 +176,7 @@ GN_LIBINTL = @GN_LIBINTL@ GN_LIB_LDFLAGS = @GN_LIB_LDFLAGS@ GN_PLUGIN_LDFLAGS = @GN_PLUGIN_LDFLAGS@ GN_USER_HOME_DIR = @GN_USER_HOME_DIR@ +GOBJECT_QUERY = @GOBJECT_QUERY@ GREP = @GREP@ HAVE_LIBUNISTRING = @HAVE_LIBUNISTRING@ INCLTDL = @INCLTDL@ @@ -171,6 +199,8 @@ LIBCURL_CPPFLAGS = @LIBCURL_CPPFLAGS@ LIBGCRYPT_CFLAGS = @LIBGCRYPT_CFLAGS@ LIBGCRYPT_CONFIG = @LIBGCRYPT_CONFIG@ LIBGCRYPT_LIBS = @LIBGCRYPT_LIBS@ +LIBGTOP_CFLAGS = @LIBGTOP_CFLAGS@ +LIBGTOP_LIBS = @LIBGTOP_LIBS@ LIBICONV = @LIBICONV@ LIBINTL = @LIBINTL@ LIBLTDL = @LIBLTDL@ @@ -192,6 +222,7 @@ LT_CONFIG_H = @LT_CONFIG_H@ LT_DLLOADERS = @LT_DLLOADERS@ LT_DLPREOPEN = @LT_DLPREOPEN@ MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ MKDIR_P = @MKDIR_P@ MONKEYPREFIX = @MONKEYPREFIX@ MSGFMT = @MSGFMT@ @@ -201,6 +232,7 @@ MYSQL_CPPFLAGS = @MYSQL_CPPFLAGS@ MYSQL_LDFLAGS = @MYSQL_LDFLAGS@ NM = @NM@ NMEDIT = @NMEDIT@ +NSS_DIR = @NSS_DIR@ OBJC = @OBJC@ OBJCDEPMODE = @OBJCDEPMODE@ OBJCFLAGS = @OBJCFLAGS@ @@ -216,6 +248,7 @@ PACKAGE_TARNAME = @PACKAGE_TARNAME@ PACKAGE_URL = @PACKAGE_URL@ PACKAGE_VERSION = @PACKAGE_VERSION@ PATH_SEPARATOR = @PATH_SEPARATOR@ +PKG_CONFIG = @PKG_CONFIG@ POSTGRES_CPPFLAGS = @POSTGRES_CPPFLAGS@ POSTGRES_LDFLAGS = @POSTGRES_LDFLAGS@ POSUB = @POSUB@ @@ -247,6 +280,7 @@ abs_builddir = @abs_builddir@ abs_srcdir = @abs_srcdir@ abs_top_builddir = @abs_top_builddir@ abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ ac_ct_CC = @ac_ct_CC@ ac_ct_CXX = @ac_ct_CXX@ ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ @@ -269,6 +303,7 @@ datarootdir = @datarootdir@ docdir = @docdir@ dvidir = @dvidir@ exec_prefix = @exec_prefix@ +gitcommand = @gitcommand@ host = @host@ host_alias = @host_alias@ host_cpu = @host_cpu@ @@ -282,7 +317,6 @@ libdir = @libdir@ libexecdir = @libexecdir@ localedir = @localedir@ localstatedir = @localstatedir@ -lt_ECHO = @lt_ECHO@ ltdl_LIBOBJS = @ltdl_LIBOBJS@ ltdl_LTLIBOBJS = @ltdl_LTLIBOBJS@ mandir = @mandir@ @@ -300,6 +334,7 @@ sbindir = @sbindir@ sharedstatedir = @sharedstatedir@ srcdir = @srcdir@ subdirs = @subdirs@ +svnversioncommand = @svnversioncommand@ sys_symbol_underscore = @sys_symbol_underscore@ sysconfdir = @sysconfdir@ target = @target@ @@ -325,8 +360,8 @@ gnunet_peerinfo_LDADD = \ $(top_builddir)/src/statistics/libgnunetstatistics.la \ $(top_builddir)/src/util/libgnunetutil.la -@HAVE_PYTHON_PEXPECT_TRUE@check_SCRIPTS = \ -@HAVE_PYTHON_PEXPECT_TRUE@ test_gnunet_peerinfo.py +@HAVE_PYTHON_TRUE@check_SCRIPTS = \ +@HAVE_PYTHON_TRUE@ test_gnunet_peerinfo.py @ENABLE_TEST_RUN_TRUE@TESTS = $(check_SCRIPTS) do_subst = $(SED) -e 's,[@]PYTHON[@],$(PYTHON),g' @@ -371,8 +406,11 @@ $(ACLOCAL_M4): $(am__aclocal_m4_deps) $(am__aclocal_m4_deps): install-binPROGRAMS: $(bin_PROGRAMS) @$(NORMAL_INSTALL) - test -z "$(bindir)" || $(MKDIR_P) "$(DESTDIR)$(bindir)" @list='$(bin_PROGRAMS)'; test -n "$(bindir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(bindir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(bindir)" || exit 1; \ + fi; \ for p in $$list; do echo "$$p $$p"; done | \ sed 's/$(EXEEXT)$$//' | \ while read p p1; do if test -f $$p || test -f $$p1; \ @@ -412,7 +450,7 @@ clean-binPROGRAMS: list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ echo " rm -f" $$list; \ rm -f $$list -gnunet-peerinfo$(EXEEXT): $(gnunet_peerinfo_OBJECTS) $(gnunet_peerinfo_DEPENDENCIES) +gnunet-peerinfo$(EXEEXT): $(gnunet_peerinfo_OBJECTS) $(gnunet_peerinfo_DEPENDENCIES) $(EXTRA_gnunet_peerinfo_DEPENDENCIES) @rm -f gnunet-peerinfo$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_peerinfo_OBJECTS) $(gnunet_peerinfo_LDADD) $(LIBS) @@ -428,26 +466,23 @@ distclean-compile: .c.o: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c $< .c.obj: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'` @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c `$(CYGPATH_W) '$<'` +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c `$(CYGPATH_W) '$<'` .c.lo: @am__fastdepCC_TRUE@ $(AM_V_CC)$(LTCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LTCOMPILE) -c -o $@ $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LTCOMPILE) -c -o $@ $< mostlyclean-libtool: -rm -f *.lo @@ -588,14 +623,15 @@ check-TESTS: $(TESTS) fi; \ dashes=`echo "$$dashes" | sed s/./=/g`; \ if test "$$failed" -eq 0; then \ - echo "$$grn$$dashes"; \ + col="$$grn"; \ else \ - echo "$$red$$dashes"; \ + col="$$red"; \ fi; \ - echo "$$banner"; \ - test -z "$$skipped" || echo "$$skipped"; \ - test -z "$$report" || echo "$$report"; \ - echo "$$dashes$$std"; \ + echo "$${col}$$dashes$${std}"; \ + echo "$${col}$$banner$${std}"; \ + test -z "$$skipped" || echo "$${col}$$skipped$${std}"; \ + test -z "$$report" || echo "$${col}$$report$${std}"; \ + echo "$${col}$$dashes$${std}"; \ test "$$failed" -eq 0; \ else :; fi @@ -648,10 +684,15 @@ install-am: all-am installcheck: installcheck-am install-strip: - $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ - install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ - `test -z '$(STRIP)' || \ - echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi mostlyclean-generic: clean-generic: diff --git a/src/peerinfo-tool/gnunet-peerinfo.c b/src/peerinfo-tool/gnunet-peerinfo.c index de27cd2..61185bc 100644 --- a/src/peerinfo-tool/gnunet-peerinfo.c +++ b/src/peerinfo-tool/gnunet-peerinfo.c @@ -27,17 +27,12 @@ #include "gnunet_crypto_lib.h" #include "gnunet_configuration_lib.h" #include "gnunet_getopt_lib.h" -#include "gnunet_peerinfo_service.h" -#include "gnunet_transport_service.h" #include "gnunet_program_lib.h" -#include "gnunet_transport_plugin.h" +#include "gnunet_hello_lib.h" +#include "gnunet_transport_service.h" +#include "gnunet_peerinfo_service.h" #include "gnunet-peerinfo_plugins.h" -/** - * Prefix that every HELLO URI must start with. - */ -#define HELLO_URI_PREFIX "gnunet://hello/" - /** * How long until we time out during peerinfo iterations? */ @@ -114,37 +109,6 @@ struct PrintContext }; -/** - * Context used for building our own URI. - */ -struct GetUriContext -{ - /** - * Final URI. - */ - char *uri; - -}; - - -/** - * Context for 'add_address_to_hello'. - */ -struct GNUNET_PEERINFO_HelloAddressParsingContext -{ - /** - * Position in the URI with the next address to parse. - */ - const char *pos; - - /** - * Set to GNUNET_SYSERR to indicate parse errors. - */ - int ret; - -}; - - /** * Option '-n' */ @@ -233,42 +197,6 @@ state_machine (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc); - -/** - * Replace all characters in the input 'in' according - * to the mapping. The mapping says to map each character - * in 'oldchars' to the corresponding character (by offset) - * in 'newchars'. - * - * @param in input string to remap - * @param oldchars characters to replace - * @param newchars replacement characters, must have same length as 'oldchars' - * @return copy of string with replacement applied. - */ -static char * -map_characters (const char *in, - const char *oldchars, - const char *newchars) -{ - char *ret; - const char *off; - size_t i; - - GNUNET_assert (strlen (oldchars) == strlen (newchars)); - ret = GNUNET_strdup (in); - i = 0; - while (ret[i] != '\0') - { - off = strchr (oldchars, ret[i]); - if (NULL != off) - ret[i] = newchars[off - oldchars]; - i++; - } - return ret; -} - - - /* ********************* 'get_info' ******************* */ /** @@ -394,10 +322,10 @@ print_peer_info (void *cls, const struct GNUNET_PeerIdentity *peer, struct GNUNET_CRYPTO_HashAsciiEncoded enc; struct PrintContext *pc; - if (peer == NULL) + if (NULL == peer) { pic = NULL; /* end of iteration */ - if (err_msg != NULL) + if (NULL != err_msg) { FPRINTF (stderr, _("Error in communication with PEERINFO service: %s\n"), @@ -437,65 +365,6 @@ print_peer_info (void *cls, const struct GNUNET_PeerIdentity *peer, /* ************************* GET URI ************************** */ -/** - * Function that is called on each address of this peer. - * Expands the corresponding URI string. - * - * @param cls the 'GetUriContext' - * @param address address to add - * @param expiration expiration time for the address - * @return GNUNET_OK (continue iteration). - */ -static int -compose_uri (void *cls, const struct GNUNET_HELLO_Address *address, - struct GNUNET_TIME_Absolute expiration) -{ - struct GetUriContext *guc = cls; - struct GNUNET_TRANSPORT_PluginFunctions *papi; - const char *addr; - char *uri_addr; - char *ret; - char tbuf[16]; - struct tm *t; - time_t seconds; - - papi = GPI_plugins_find (address->transport_name); - if (papi == NULL) - { - /* Not an error - we might just not have the right plugin. */ - return GNUNET_OK; - } - if (NULL == papi->address_to_string) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "URI conversion not implemented for plugin `%s'\n", - address->transport_name); - return GNUNET_OK; - } - addr = papi->address_to_string (papi->cls, address->address, address->address_length); - if ( (addr == NULL) || (strlen(addr) == 0) ) - return GNUNET_OK; - /* For URIs we use '(' and ')' instead of '[' and ']' as brackets are reserved - characters in URIs */ - uri_addr = map_characters (addr, "[]", "()"); - seconds = expiration.abs_value / 1000; - t = gmtime (&seconds); - GNUNET_assert (0 != strftime (tbuf, sizeof (tbuf), - "%Y%m%d%H%M%S", - t)); - GNUNET_asprintf (&ret, - "%s!%s!%s!%s", - guc->uri, - tbuf, - address->transport_name, - uri_addr); - GNUNET_free (uri_addr); - GNUNET_free (guc->uri); - guc->uri = ret; - return GNUNET_OK; -} - - /** * Print URI of the peer. * @@ -509,8 +378,6 @@ print_my_uri (void *cls, const struct GNUNET_PeerIdentity *peer, const struct GNUNET_HELLO_Message *hello, const char *err_msg) { - struct GetUriContext *guc = cls; - if (peer == NULL) { pic = NULL; @@ -518,157 +385,24 @@ print_my_uri (void *cls, const struct GNUNET_PeerIdentity *peer, FPRINTF (stderr, _("Error in communication with PEERINFO service: %s\n"), err_msg); - GNUNET_free_non_null (guc->uri); - GNUNET_free (guc); tt = GNUNET_SCHEDULER_add_now (&state_machine, NULL); return; - } - if (NULL != hello) - GNUNET_HELLO_iterate_addresses (hello, GNUNET_NO, &compose_uri, guc); - printf ("%s\n", (const char *) guc->uri); -} - - -/* ************************* import HELLO by URI ********************* */ - - -/** - * We're building a HELLO. Parse the next address from the - * parsing context and append it. - * - * @param cls the 'struct GNUNET_PEERINFO_HelloAddressParsingContext' - * @param max number of bytes available for HELLO construction - * @param buffer where to copy the next address (in binary format) - * @return number of bytes added to buffer - */ -static size_t -add_address_to_hello (void *cls, size_t max, void *buffer) -{ - struct GNUNET_PEERINFO_HelloAddressParsingContext *ctx = cls; - const char *tname; - const char *address; - char *uri_address; - char *plugin_address; - const char *end; - char *plugin_name; - struct tm expiration_time; - time_t expiration_seconds; - struct GNUNET_TIME_Absolute expire; - struct GNUNET_TRANSPORT_PluginFunctions *papi; - void *addr; - size_t addr_len; - struct GNUNET_HELLO_Address haddr; - size_t ret; - - if (NULL == ctx->pos) - return 0; - if ('!' != ctx->pos[0]) - { - ctx->ret = GNUNET_SYSERR; - GNUNET_break (0); - return 0; } - ctx->pos++; - memset (&expiration_time, 0, sizeof (expiration_time)); - tname = strptime (ctx->pos, - "%Y%m%d%H%M%S", - &expiration_time); - if (NULL == tname) - { - ctx->ret = GNUNET_SYSERR; - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - _("Failed to parse HELLO message: missing expiration time\n")); - GNUNET_break (0); - return 0; - } - expiration_seconds = mktime (&expiration_time); - if (expiration_seconds == (time_t) -1) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - _("Failed to parse HELLO message: invalid expiration time\n")); - ctx->ret = GNUNET_SYSERR; - GNUNET_break (0); - return 0; - } - expire.abs_value = expiration_seconds * 1000; - if ('!' != tname[0]) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - _("Failed to parse HELLO message: malformed\n")); - ctx->ret = GNUNET_SYSERR; - GNUNET_break (0); - return 0; - } - tname++; - address = strchr (tname, (int) '!'); - if (NULL == address) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - _("Failed to parse HELLO message: missing transport plugin\n")); - ctx->ret = GNUNET_SYSERR; - GNUNET_break (0); - return 0; - } - address++; - end = strchr (address, (int) '!'); - ctx->pos = end; - plugin_name = GNUNET_strndup (tname, address - (tname+1)); - papi = GPI_plugins_find (plugin_name); - if (NULL == papi) - { - /* Not an error - we might just not have the right plugin. - * Skip this part, advance to the next one and recurse. - * But only if this is not the end of string. - */ - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - _("Plugin `%s' not found\n"), - plugin_name); - GNUNET_free (plugin_name); - GNUNET_break (0); - return 0; - } - if (NULL == papi->string_to_address) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - _("Plugin `%s' does not support URIs yet\n"), - plugin_name); - GNUNET_free (plugin_name); - GNUNET_break (0); - return 0; - } - uri_address = GNUNET_strndup (address, end - address); - /* For URIs we use '(' and ')' instead of '[' and ']' as brackets are reserved - characters in URIs; need to convert back to '[]' for the plugin */ - plugin_address = map_characters (uri_address, "()", "[]"); - GNUNET_free (uri_address); - if (GNUNET_OK != - papi->string_to_address (papi->cls, - plugin_address, - strlen (plugin_address) + 1, - &addr, - &addr_len)) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - _("Failed to parse `%s' as an address for plugin `%s'\n"), - plugin_address, - plugin_name); - GNUNET_free (plugin_name); - GNUNET_free (plugin_address); - return 0; + if (NULL == hello) + return; + + char *uri = GNUNET_HELLO_compose_uri(hello, &GPI_plugins_find); + if (NULL != uri) { + printf ("%s\n", (const char *) uri); + GNUNET_free (uri); } - GNUNET_free (plugin_address); - /* address.peer is unset - not used by add_address() */ - haddr.address_length = addr_len; - haddr.address = addr; - haddr.transport_name = plugin_name; - ret = GNUNET_HELLO_add_address (&haddr, expire, buffer, max); - GNUNET_free (addr); - GNUNET_free (plugin_name); - return ret; } +/* ************************* import HELLO by URI ********************* */ + + /** * Continuation called from 'GNUNET_PEERINFO_add_peer' * @@ -698,31 +432,13 @@ add_continuation (void *cls, static int parse_hello_uri (const char *put_uri) { - const char *pks; - const char *exc; struct GNUNET_HELLO_Message *hello; - struct GNUNET_PEERINFO_HelloAddressParsingContext ctx; - - if (0 != strncmp (put_uri, - HELLO_URI_PREFIX, - strlen (HELLO_URI_PREFIX))) - return GNUNET_SYSERR; - pks = &put_uri[strlen (HELLO_URI_PREFIX)]; - exc = strstr (pks, "!"); - - if (GNUNET_OK != GNUNET_STRINGS_string_to_data (pks, - (NULL == exc) ? strlen (pks) : (exc - pks), - (unsigned char *) &my_public_key, - sizeof (my_public_key))) - return GNUNET_SYSERR; - ctx.pos = exc; - ctx.ret = GNUNET_OK; - hello = GNUNET_HELLO_create (&my_public_key, &add_address_to_hello, &ctx); - - if (NULL != hello) - { + + int ret = GNUNET_HELLO_parse_uri(put_uri, &my_public_key, &hello, &GPI_plugins_find); + + if (NULL != hello) { /* WARNING: this adds the address from URI WITHOUT verification! */ - if (GNUNET_OK == ctx.ret) + if (GNUNET_OK == ret) ac = GNUNET_PEERINFO_add_peer (peerinfo, hello, &add_continuation, NULL); else tt = GNUNET_SCHEDULER_add_now (&state_machine, NULL); @@ -732,7 +448,7 @@ parse_hello_uri (const char *put_uri) /* wait 1s to give peerinfo operation a chance to succeed */ /* FIXME: current peerinfo API sucks to require this; not to mention that we get no feedback to determine if the operation actually succeeded */ - return ctx.ret; + return ret; } @@ -812,13 +528,21 @@ run (void *cls, char *const *args, const char *cfgfile, char *fn; cfg = c; - if (args[0] != NULL) + if ( (NULL != args[0]) && + (NULL == put_uri) && + (args[0] == strcasestr (args[0], "gnunet://hello/")) ) + { + put_uri = GNUNET_strdup (args[0]); + args++; + } + if (NULL != args[0]) { - FPRINTF (stderr, _("Invalid command line argument `%s'\n"), args[0]); + FPRINTF (stderr, + _("Invalid command line argument `%s'\n"), + args[0]); return; } - peerinfo = GNUNET_PEERINFO_connect (cfg); - if (peerinfo == NULL) + if (NULL == (peerinfo = GNUNET_PEERINFO_connect (cfg))) { FPRINTF (stderr, "%s", _("Could not access PEERINFO service. Exiting.\n")); return; @@ -834,7 +558,6 @@ run (void *cls, char *const *args, const char *cfgfile, "GNUNETD", "HOSTKEYFILE"); return; } - if (NULL == (priv = GNUNET_CRYPTO_rsa_key_create_from_file (fn))) { FPRINTF (stderr, _("Loading hostkey from `%s' failed.\n"), fn); @@ -900,20 +623,9 @@ state_machine (void *cls, } if (GNUNET_YES == get_uri) { - struct GetUriContext *guc; - char *pkey; - - guc = GNUNET_malloc (sizeof (struct GetUriContext)); - pkey = GNUNET_CRYPTO_rsa_public_key_to_string (&my_public_key); - GNUNET_asprintf (&guc->uri, - "%s%s", - HELLO_URI_PREFIX, - pkey); - GNUNET_free (pkey); GPI_plugins_load (cfg); pic = GNUNET_PEERINFO_iterate (peerinfo, &my_peer_identity, - TIMEOUT, - &print_my_uri, guc); + TIMEOUT, &print_my_uri, NULL); get_uri = GNUNET_NO; return; } @@ -952,10 +664,17 @@ main (int argc, char *const *argv) 1, &GNUNET_GETOPT_set_string, &put_uri}, GNUNET_GETOPT_OPTION_END }; - return (GNUNET_OK == - GNUNET_PROGRAM_run (argc, argv, "gnunet-peerinfo", - gettext_noop ("Print information about peers."), - options, &run, NULL)) ? 0 : 1; + int ret; + + if (GNUNET_OK != GNUNET_STRINGS_get_utf8_args (argc, argv, &argc, &argv)) + return 2; + + ret = (GNUNET_OK == + GNUNET_PROGRAM_run (argc, argv, "gnunet-peerinfo", + gettext_noop ("Print information about peers."), + options, &run, NULL)) ? 0 : 1; + GNUNET_free ((void*) argv); + return ret; } /* end of gnunet-peerinfo.c */ diff --git a/src/peerinfo-tool/gnunet-peerinfo_plugins.c b/src/peerinfo-tool/gnunet-peerinfo_plugins.c index ba7c1d3..3bca9fe 100644 --- a/src/peerinfo-tool/gnunet-peerinfo_plugins.c +++ b/src/peerinfo-tool/gnunet-peerinfo_plugins.c @@ -167,8 +167,18 @@ GPI_plugins_find (const char *name) { struct TransportPlugin *head = plugins_head; - while ((head != NULL) && (0 != strcmp (name, head->short_name))) + char *stripped = GNUNET_strdup (name); + char *sep = strchr (stripped, '_'); + if (NULL != sep) + sep[0] = '\0'; + + while (head != NULL) + { + if (head->short_name == strstr (head->short_name, stripped)) + break; head = head->next; + } + GNUNET_free (stripped); if (NULL == head) return NULL; return head->api; diff --git a/src/peerinfo-tool/test_gnunet_peerinfo.py.in b/src/peerinfo-tool/test_gnunet_peerinfo.py.in old mode 100644 new mode 100755 index bff673e..81acb3c --- a/src/peerinfo-tool/test_gnunet_peerinfo.py.in +++ b/src/peerinfo-tool/test_gnunet_peerinfo.py.in @@ -35,21 +35,27 @@ from gnunet_pyexpect import pexpect if os.name == 'posix': peerinfo = 'gnunet-peerinfo' gnunetarm = 'gnunet-arm' + gnunettesting = 'gnunet-testing' elif os.name == 'nt': peerinfo = 'gnunet-peerinfo.exe' gnunetarm = 'gnunet-arm.exe' - - + gnunettesting = 'gnunet-testing.exe' pinfo = pexpect () pinfo.spawn (None, [peerinfo, '-i', '-c', 'test_gnunet_peerinfo_data.conf', '-L', 'ERROR'], stdout=subprocess.PIPE, stderr=subprocess.STDOUT) pinfo.expect ("stdout", re.compile (r'Error in communication with PEERINFO service: Timeout transmitting iteration request to `PEERINFO\' service.\r?\n')) pinfo.expect ("stdout", "EOF") + if os.name == "nt": shutil.rmtree (os.path.join (os.getenv ("TEMP"), "gnunet-test-peerinfo"), True) else: shutil.rmtree ("/tmp/gnunet-test-peerinfo", True) + +# create hostkey via testing lib +hkk = subprocess.Popen ([gnunettesting, '-n 1', '-k', '/tmp/gnunet-test-peerinfo/.hostkey']) +hkk.communicate () + arm = subprocess.Popen ([gnunetarm, '-sq', '-c', 'test_gnunet_peerinfo_data.conf']) arm.communicate () diff --git a/src/peerinfo-tool/test_gnunet_peerinfo_data.conf b/src/peerinfo-tool/test_gnunet_peerinfo_data.conf index 90da74f..a4c16ac 100644 --- a/src/peerinfo-tool/test_gnunet_peerinfo_data.conf +++ b/src/peerinfo-tool/test_gnunet_peerinfo_data.conf @@ -1,6 +1,9 @@ [PATHS] SERVICEHOME = /tmp/gnunet-test-peerinfo/ +[gnunetd] +#HOSTKEY = test_gnunet_peerinfo.hostkey + [peerinfo] PORT = 24354 @@ -29,4 +32,8 @@ AUTOSTART = NO [nse] AUTOSTART = NO +[nat] +RETURN_LOCAL_ADDRESSES = YES + + diff --git a/src/peerinfo/Makefile.am b/src/peerinfo/Makefile.am index 468fab5..8387c4f 100644 --- a/src/peerinfo/Makefile.am +++ b/src/peerinfo/Makefile.am @@ -2,6 +2,8 @@ INCLUDES = -I$(top_srcdir)/src/include pkgcfgdir= $(pkgdatadir)/config.d/ +libexecdir= $(pkglibdir)/libexec/ + pkgcfg_DATA = \ peerinfo.conf @@ -22,13 +24,14 @@ libgnunetpeerinfo_la_SOURCES = \ libgnunetpeerinfo_la_LIBADD = \ $(top_builddir)/src/hello/libgnunethello.la \ $(top_builddir)/src/util/libgnunetutil.la \ - $(XLIB) + $(XLIB) \ + $(LTLIBINTL) libgnunetpeerinfo_la_LDFLAGS = \ $(GN_LIB_LDFLAGS) $(WINFLAGS) \ -version-info 0:0:0 -bin_PROGRAMS = \ +libexec_PROGRAMS = \ gnunet-service-peerinfo gnunet_service_peerinfo_SOURCES = \ @@ -56,6 +59,7 @@ test_peerinfo_api_SOURCES = \ test_peerinfo_api_LDADD = \ $(top_builddir)/src/hello/libgnunethello.la \ $(top_builddir)/src/peerinfo/libgnunetpeerinfo.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la perf_peerinfo_api_SOURCES = \ @@ -63,6 +67,7 @@ perf_peerinfo_api_SOURCES = \ perf_peerinfo_api_LDADD = \ $(top_builddir)/src/hello/libgnunethello.la \ $(top_builddir)/src/peerinfo/libgnunetpeerinfo.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la EXTRA_DIST = \ diff --git a/src/peerinfo/Makefile.in b/src/peerinfo/Makefile.in index dc407f5..1362dcc 100644 --- a/src/peerinfo/Makefile.in +++ b/src/peerinfo/Makefile.in @@ -1,9 +1,9 @@ -# Makefile.in generated by automake 1.11.1 from Makefile.am. +# Makefile.in generated by automake 1.11.6 from Makefile.am. # @configure_input@ # Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, -# 2003, 2004, 2005, 2006, 2007, 2008, 2009 Free Software Foundation, -# Inc. +# 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Free Software +# Foundation, Inc. # This Makefile.in is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. @@ -18,6 +18,23 @@ VPATH = @srcdir@ +am__make_dryrun = \ + { \ + am__dry=no; \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + echo 'am--echo: ; @echo "AM" OK' | $(MAKE) -f - 2>/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } pkgdatadir = $(datadir)/@PACKAGE@ pkgincludedir = $(includedir)/@PACKAGE@ pkglibdir = $(libdir)/@PACKAGE@ @@ -37,7 +54,7 @@ POST_UNINSTALL = : build_triplet = @build@ host_triplet = @host@ target_triplet = @target@ -bin_PROGRAMS = gnunet-service-peerinfo$(EXEEXT) +libexec_PROGRAMS = gnunet-service-peerinfo$(EXEEXT) check_PROGRAMS = test_peerinfo_api$(EXEEXT) $(am__EXEEXT_1) subdir = src/peerinfo DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in \ @@ -45,14 +62,15 @@ DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in \ ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 am__aclocal_m4_deps = $(top_srcdir)/m4/absolute-header.m4 \ $(top_srcdir)/m4/align.m4 $(top_srcdir)/m4/argz.m4 \ - $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/iconv.m4 \ - $(top_srcdir)/m4/lib-ld.m4 $(top_srcdir)/m4/lib-link.m4 \ - $(top_srcdir)/m4/lib-prefix.m4 $(top_srcdir)/m4/libcurl.m4 \ - $(top_srcdir)/m4/libgcrypt.m4 $(top_srcdir)/m4/libtool.m4 \ - $(top_srcdir)/m4/libunistring.m4 $(top_srcdir)/m4/ltdl.m4 \ - $(top_srcdir)/m4/ltoptions.m4 $(top_srcdir)/m4/ltsugar.m4 \ - $(top_srcdir)/m4/ltversion.m4 $(top_srcdir)/m4/lt~obsolete.m4 \ - $(top_srcdir)/m4/nls.m4 $(top_srcdir)/m4/po.m4 \ + $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/glib-2.0.m4 \ + $(top_srcdir)/m4/iconv.m4 $(top_srcdir)/m4/lib-ld.m4 \ + $(top_srcdir)/m4/lib-link.m4 $(top_srcdir)/m4/lib-prefix.m4 \ + $(top_srcdir)/m4/libcurl.m4 $(top_srcdir)/m4/libgcrypt.m4 \ + $(top_srcdir)/m4/libtool.m4 $(top_srcdir)/m4/libunistring.m4 \ + $(top_srcdir)/m4/ltdl.m4 $(top_srcdir)/m4/ltoptions.m4 \ + $(top_srcdir)/m4/ltsugar.m4 $(top_srcdir)/m4/ltversion.m4 \ + $(top_srcdir)/m4/lt~obsolete.m4 $(top_srcdir)/m4/nls.m4 \ + $(top_srcdir)/m4/pkg.m4 $(top_srcdir)/m4/po.m4 \ $(top_srcdir)/m4/progtest.m4 $(top_srcdir)/acinclude.m4 \ $(top_srcdir)/configure.ac am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ @@ -82,26 +100,32 @@ am__nobase_list = $(am__nobase_strip_setup); \ am__base_list = \ sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \ sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g' -am__installdirs = "$(DESTDIR)$(libdir)" "$(DESTDIR)$(bindir)" \ +am__uninstall_files_from_dir = { \ + test -z "$$files" \ + || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \ + || { echo " ( cd '$$dir' && rm -f" $$files ")"; \ + $(am__cd) "$$dir" && rm -f $$files; }; \ + } +am__installdirs = "$(DESTDIR)$(libdir)" "$(DESTDIR)$(libexecdir)" \ "$(DESTDIR)$(pkgcfgdir)" LTLIBRARIES = $(lib_LTLIBRARIES) am__DEPENDENCIES_1 = libgnunetpeerinfo_la_DEPENDENCIES = \ $(top_builddir)/src/hello/libgnunethello.la \ $(top_builddir)/src/util/libgnunetutil.la \ - $(am__DEPENDENCIES_1) + $(am__DEPENDENCIES_1) $(am__DEPENDENCIES_1) am_libgnunetpeerinfo_la_OBJECTS = peerinfo_api.lo \ peerinfo_api_notify.lo libgnunetpeerinfo_la_OBJECTS = $(am_libgnunetpeerinfo_la_OBJECTS) -AM_V_lt = $(am__v_lt_$(V)) -am__v_lt_ = $(am__v_lt_$(AM_DEFAULT_VERBOSITY)) +AM_V_lt = $(am__v_lt_@AM_V@) +am__v_lt_ = $(am__v_lt_@AM_DEFAULT_V@) am__v_lt_0 = --silent libgnunetpeerinfo_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ $(AM_CFLAGS) $(CFLAGS) $(libgnunetpeerinfo_la_LDFLAGS) \ $(LDFLAGS) -o $@ @HAVE_BENCHMARKS_TRUE@am__EXEEXT_1 = perf_peerinfo_api$(EXEEXT) -PROGRAMS = $(bin_PROGRAMS) +PROGRAMS = $(libexec_PROGRAMS) am_gnunet_service_peerinfo_OBJECTS = \ gnunet-service-peerinfo.$(OBJEXT) gnunet_service_peerinfo_OBJECTS = \ @@ -115,12 +139,14 @@ perf_peerinfo_api_OBJECTS = $(am_perf_peerinfo_api_OBJECTS) perf_peerinfo_api_DEPENDENCIES = \ $(top_builddir)/src/hello/libgnunethello.la \ $(top_builddir)/src/peerinfo/libgnunetpeerinfo.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la am_test_peerinfo_api_OBJECTS = test_peerinfo_api.$(OBJEXT) test_peerinfo_api_OBJECTS = $(am_test_peerinfo_api_OBJECTS) test_peerinfo_api_DEPENDENCIES = \ $(top_builddir)/src/hello/libgnunethello.la \ $(top_builddir)/src/peerinfo/libgnunetpeerinfo.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la DEFAULT_INCLUDES = -I.@am__isrc@ -I$(top_builddir) depcomp = $(SHELL) $(top_srcdir)/depcomp @@ -132,21 +158,21 @@ LTCOMPILE = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) \ $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) \ $(AM_CFLAGS) $(CFLAGS) -AM_V_CC = $(am__v_CC_$(V)) -am__v_CC_ = $(am__v_CC_$(AM_DEFAULT_VERBOSITY)) +AM_V_CC = $(am__v_CC_@AM_V@) +am__v_CC_ = $(am__v_CC_@AM_DEFAULT_V@) am__v_CC_0 = @echo " CC " $@; -AM_V_at = $(am__v_at_$(V)) -am__v_at_ = $(am__v_at_$(AM_DEFAULT_VERBOSITY)) +AM_V_at = $(am__v_at_@AM_V@) +am__v_at_ = $(am__v_at_@AM_DEFAULT_V@) am__v_at_0 = @ CCLD = $(CC) LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ $(AM_LDFLAGS) $(LDFLAGS) -o $@ -AM_V_CCLD = $(am__v_CCLD_$(V)) -am__v_CCLD_ = $(am__v_CCLD_$(AM_DEFAULT_VERBOSITY)) +AM_V_CCLD = $(am__v_CCLD_@AM_V@) +am__v_CCLD_ = $(am__v_CCLD_@AM_DEFAULT_V@) am__v_CCLD_0 = @echo " CCLD " $@; -AM_V_GEN = $(am__v_GEN_$(V)) -am__v_GEN_ = $(am__v_GEN_$(AM_DEFAULT_VERBOSITY)) +AM_V_GEN = $(am__v_GEN_@AM_V@) +am__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@) am__v_GEN_0 = @echo " GEN " $@; SOURCES = $(libgnunetpeerinfo_la_SOURCES) \ $(gnunet_service_peerinfo_SOURCES) \ @@ -154,6 +180,11 @@ SOURCES = $(libgnunetpeerinfo_la_SOURCES) \ DIST_SOURCES = $(libgnunetpeerinfo_la_SOURCES) \ $(gnunet_service_peerinfo_SOURCES) \ $(perf_peerinfo_api_SOURCES) $(test_peerinfo_api_SOURCES) +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac DATA = $(pkgcfg_DATA) ETAGS = etags CTAGS = ctags @@ -195,6 +226,10 @@ EXEEXT = @EXEEXT@ EXT_LIBS = @EXT_LIBS@ EXT_LIB_PATH = @EXT_LIB_PATH@ FGREP = @FGREP@ +GLIB_CFLAGS = @GLIB_CFLAGS@ +GLIB_GENMARSHAL = @GLIB_GENMARSHAL@ +GLIB_LIBS = @GLIB_LIBS@ +GLIB_MKENUMS = @GLIB_MKENUMS@ GMSGFMT = @GMSGFMT@ GMSGFMT_015 = @GMSGFMT_015@ GNUNETDNS_GROUP = @GNUNETDNS_GROUP@ @@ -205,6 +240,7 @@ GN_LIBINTL = @GN_LIBINTL@ GN_LIB_LDFLAGS = @GN_LIB_LDFLAGS@ GN_PLUGIN_LDFLAGS = @GN_PLUGIN_LDFLAGS@ GN_USER_HOME_DIR = @GN_USER_HOME_DIR@ +GOBJECT_QUERY = @GOBJECT_QUERY@ GREP = @GREP@ HAVE_LIBUNISTRING = @HAVE_LIBUNISTRING@ INCLTDL = @INCLTDL@ @@ -227,6 +263,8 @@ LIBCURL_CPPFLAGS = @LIBCURL_CPPFLAGS@ LIBGCRYPT_CFLAGS = @LIBGCRYPT_CFLAGS@ LIBGCRYPT_CONFIG = @LIBGCRYPT_CONFIG@ LIBGCRYPT_LIBS = @LIBGCRYPT_LIBS@ +LIBGTOP_CFLAGS = @LIBGTOP_CFLAGS@ +LIBGTOP_LIBS = @LIBGTOP_LIBS@ LIBICONV = @LIBICONV@ LIBINTL = @LIBINTL@ LIBLTDL = @LIBLTDL@ @@ -248,6 +286,7 @@ LT_CONFIG_H = @LT_CONFIG_H@ LT_DLLOADERS = @LT_DLLOADERS@ LT_DLPREOPEN = @LT_DLPREOPEN@ MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ MKDIR_P = @MKDIR_P@ MONKEYPREFIX = @MONKEYPREFIX@ MSGFMT = @MSGFMT@ @@ -257,6 +296,7 @@ MYSQL_CPPFLAGS = @MYSQL_CPPFLAGS@ MYSQL_LDFLAGS = @MYSQL_LDFLAGS@ NM = @NM@ NMEDIT = @NMEDIT@ +NSS_DIR = @NSS_DIR@ OBJC = @OBJC@ OBJCDEPMODE = @OBJCDEPMODE@ OBJCFLAGS = @OBJCFLAGS@ @@ -272,6 +312,7 @@ PACKAGE_TARNAME = @PACKAGE_TARNAME@ PACKAGE_URL = @PACKAGE_URL@ PACKAGE_VERSION = @PACKAGE_VERSION@ PATH_SEPARATOR = @PATH_SEPARATOR@ +PKG_CONFIG = @PKG_CONFIG@ POSTGRES_CPPFLAGS = @POSTGRES_CPPFLAGS@ POSTGRES_LDFLAGS = @POSTGRES_LDFLAGS@ POSUB = @POSUB@ @@ -303,6 +344,7 @@ abs_builddir = @abs_builddir@ abs_srcdir = @abs_srcdir@ abs_top_builddir = @abs_top_builddir@ abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ ac_ct_CC = @ac_ct_CC@ ac_ct_CXX = @ac_ct_CXX@ ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ @@ -325,6 +367,7 @@ datarootdir = @datarootdir@ docdir = @docdir@ dvidir = @dvidir@ exec_prefix = @exec_prefix@ +gitcommand = @gitcommand@ host = @host@ host_alias = @host_alias@ host_cpu = @host_cpu@ @@ -335,10 +378,9 @@ includedir = @includedir@ infodir = @infodir@ install_sh = @install_sh@ libdir = @libdir@ -libexecdir = @libexecdir@ +libexecdir = $(pkglibdir)/libexec/ localedir = @localedir@ localstatedir = @localstatedir@ -lt_ECHO = @lt_ECHO@ ltdl_LIBOBJS = @ltdl_LIBOBJS@ ltdl_LTLIBOBJS = @ltdl_LTLIBOBJS@ mandir = @mandir@ @@ -356,6 +398,7 @@ sbindir = @sbindir@ sharedstatedir = @sharedstatedir@ srcdir = @srcdir@ subdirs = @subdirs@ +svnversioncommand = @svnversioncommand@ sys_symbol_underscore = @sys_symbol_underscore@ sysconfdir = @sysconfdir@ target = @target@ @@ -382,7 +425,8 @@ libgnunetpeerinfo_la_SOURCES = \ libgnunetpeerinfo_la_LIBADD = \ $(top_builddir)/src/hello/libgnunethello.la \ $(top_builddir)/src/util/libgnunetutil.la \ - $(XLIB) + $(XLIB) \ + $(LTLIBINTL) libgnunetpeerinfo_la_LDFLAGS = \ $(GN_LIB_LDFLAGS) $(WINFLAGS) \ @@ -406,6 +450,7 @@ test_peerinfo_api_SOURCES = \ test_peerinfo_api_LDADD = \ $(top_builddir)/src/hello/libgnunethello.la \ $(top_builddir)/src/peerinfo/libgnunetpeerinfo.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la perf_peerinfo_api_SOURCES = \ @@ -414,6 +459,7 @@ perf_peerinfo_api_SOURCES = \ perf_peerinfo_api_LDADD = \ $(top_builddir)/src/hello/libgnunethello.la \ $(top_builddir)/src/peerinfo/libgnunetpeerinfo.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(top_builddir)/src/util/libgnunetutil.la EXTRA_DIST = \ @@ -457,7 +503,6 @@ peerinfo.conf: $(top_builddir)/config.status $(srcdir)/peerinfo.conf.in cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ install-libLTLIBRARIES: $(lib_LTLIBRARIES) @$(NORMAL_INSTALL) - test -z "$(libdir)" || $(MKDIR_P) "$(DESTDIR)$(libdir)" @list='$(lib_LTLIBRARIES)'; test -n "$(libdir)" || list=; \ list2=; for p in $$list; do \ if test -f $$p; then \ @@ -465,6 +510,8 @@ install-libLTLIBRARIES: $(lib_LTLIBRARIES) else :; fi; \ done; \ test -z "$$list2" || { \ + echo " $(MKDIR_P) '$(DESTDIR)$(libdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libdir)" || exit 1; \ echo " $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 '$(DESTDIR)$(libdir)'"; \ $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 "$(DESTDIR)$(libdir)"; \ } @@ -486,12 +533,24 @@ clean-libLTLIBRARIES: echo "rm -f \"$${dir}/so_locations\""; \ rm -f "$${dir}/so_locations"; \ done -libgnunetpeerinfo.la: $(libgnunetpeerinfo_la_OBJECTS) $(libgnunetpeerinfo_la_DEPENDENCIES) +libgnunetpeerinfo.la: $(libgnunetpeerinfo_la_OBJECTS) $(libgnunetpeerinfo_la_DEPENDENCIES) $(EXTRA_libgnunetpeerinfo_la_DEPENDENCIES) $(AM_V_CCLD)$(libgnunetpeerinfo_la_LINK) -rpath $(libdir) $(libgnunetpeerinfo_la_OBJECTS) $(libgnunetpeerinfo_la_LIBADD) $(LIBS) -install-binPROGRAMS: $(bin_PROGRAMS) + +clean-checkPROGRAMS: + @list='$(check_PROGRAMS)'; test -n "$$list" || exit 0; \ + echo " rm -f" $$list; \ + rm -f $$list || exit $$?; \ + test -n "$(EXEEXT)" || exit 0; \ + list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ + echo " rm -f" $$list; \ + rm -f $$list +install-libexecPROGRAMS: $(libexec_PROGRAMS) @$(NORMAL_INSTALL) - test -z "$(bindir)" || $(MKDIR_P) "$(DESTDIR)$(bindir)" - @list='$(bin_PROGRAMS)'; test -n "$(bindir)" || list=; \ + @list='$(libexec_PROGRAMS)'; test -n "$(libexecdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(libexecdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libexecdir)" || exit 1; \ + fi; \ for p in $$list; do echo "$$p $$p"; done | \ sed 's/$(EXEEXT)$$//' | \ while read p p1; do if test -f $$p || test -f $$p1; \ @@ -508,45 +567,36 @@ install-binPROGRAMS: $(bin_PROGRAMS) while read type dir files; do \ if test "$$dir" = .; then dir=; else dir=/$$dir; fi; \ test -z "$$files" || { \ - echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files '$(DESTDIR)$(bindir)$$dir'"; \ - $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files "$(DESTDIR)$(bindir)$$dir" || exit $$?; \ + echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files '$(DESTDIR)$(libexecdir)$$dir'"; \ + $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files "$(DESTDIR)$(libexecdir)$$dir" || exit $$?; \ } \ ; done -uninstall-binPROGRAMS: +uninstall-libexecPROGRAMS: @$(NORMAL_UNINSTALL) - @list='$(bin_PROGRAMS)'; test -n "$(bindir)" || list=; \ + @list='$(libexec_PROGRAMS)'; test -n "$(libexecdir)" || list=; \ files=`for p in $$list; do echo "$$p"; done | \ sed -e 'h;s,^.*/,,;s/$(EXEEXT)$$//;$(transform)' \ -e 's/$$/$(EXEEXT)/' `; \ test -n "$$list" || exit 0; \ - echo " ( cd '$(DESTDIR)$(bindir)' && rm -f" $$files ")"; \ - cd "$(DESTDIR)$(bindir)" && rm -f $$files + echo " ( cd '$(DESTDIR)$(libexecdir)' && rm -f" $$files ")"; \ + cd "$(DESTDIR)$(libexecdir)" && rm -f $$files -clean-binPROGRAMS: - @list='$(bin_PROGRAMS)'; test -n "$$list" || exit 0; \ +clean-libexecPROGRAMS: + @list='$(libexec_PROGRAMS)'; test -n "$$list" || exit 0; \ echo " rm -f" $$list; \ rm -f $$list || exit $$?; \ test -n "$(EXEEXT)" || exit 0; \ list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ echo " rm -f" $$list; \ rm -f $$list - -clean-checkPROGRAMS: - @list='$(check_PROGRAMS)'; test -n "$$list" || exit 0; \ - echo " rm -f" $$list; \ - rm -f $$list || exit $$?; \ - test -n "$(EXEEXT)" || exit 0; \ - list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ - echo " rm -f" $$list; \ - rm -f $$list -gnunet-service-peerinfo$(EXEEXT): $(gnunet_service_peerinfo_OBJECTS) $(gnunet_service_peerinfo_DEPENDENCIES) +gnunet-service-peerinfo$(EXEEXT): $(gnunet_service_peerinfo_OBJECTS) $(gnunet_service_peerinfo_DEPENDENCIES) $(EXTRA_gnunet_service_peerinfo_DEPENDENCIES) @rm -f gnunet-service-peerinfo$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_service_peerinfo_OBJECTS) $(gnunet_service_peerinfo_LDADD) $(LIBS) -perf_peerinfo_api$(EXEEXT): $(perf_peerinfo_api_OBJECTS) $(perf_peerinfo_api_DEPENDENCIES) +perf_peerinfo_api$(EXEEXT): $(perf_peerinfo_api_OBJECTS) $(perf_peerinfo_api_DEPENDENCIES) $(EXTRA_perf_peerinfo_api_DEPENDENCIES) @rm -f perf_peerinfo_api$(EXEEXT) $(AM_V_CCLD)$(LINK) $(perf_peerinfo_api_OBJECTS) $(perf_peerinfo_api_LDADD) $(LIBS) -test_peerinfo_api$(EXEEXT): $(test_peerinfo_api_OBJECTS) $(test_peerinfo_api_DEPENDENCIES) +test_peerinfo_api$(EXEEXT): $(test_peerinfo_api_OBJECTS) $(test_peerinfo_api_DEPENDENCIES) $(EXTRA_test_peerinfo_api_DEPENDENCIES) @rm -f test_peerinfo_api$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_peerinfo_api_OBJECTS) $(test_peerinfo_api_LDADD) $(LIBS) @@ -565,26 +615,23 @@ distclean-compile: .c.o: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c $< .c.obj: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'` @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c `$(CYGPATH_W) '$<'` +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c `$(CYGPATH_W) '$<'` .c.lo: @am__fastdepCC_TRUE@ $(AM_V_CC)$(LTCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LTCOMPILE) -c -o $@ $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LTCOMPILE) -c -o $@ $< mostlyclean-libtool: -rm -f *.lo @@ -593,8 +640,11 @@ clean-libtool: -rm -rf .libs _libs install-pkgcfgDATA: $(pkgcfg_DATA) @$(NORMAL_INSTALL) - test -z "$(pkgcfgdir)" || $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" @list='$(pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(pkgcfgdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" || exit 1; \ + fi; \ for p in $$list; do \ if test -f "$$p"; then d=; else d="$(srcdir)/"; fi; \ echo "$$d$$p"; \ @@ -608,9 +658,7 @@ uninstall-pkgcfgDATA: @$(NORMAL_UNINSTALL) @list='$(pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ files=`for p in $$list; do echo $$p; done | sed -e 's|^.*/||'`; \ - test -n "$$files" || exit 0; \ - echo " ( cd '$(DESTDIR)$(pkgcfgdir)' && rm -f" $$files ")"; \ - cd "$(DESTDIR)$(pkgcfgdir)" && rm -f $$files + dir='$(DESTDIR)$(pkgcfgdir)'; $(am__uninstall_files_from_dir) ID: $(HEADERS) $(SOURCES) $(LISP) $(TAGS_FILES) list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ @@ -745,14 +793,15 @@ check-TESTS: $(TESTS) fi; \ dashes=`echo "$$dashes" | sed s/./=/g`; \ if test "$$failed" -eq 0; then \ - echo "$$grn$$dashes"; \ + col="$$grn"; \ else \ - echo "$$red$$dashes"; \ + col="$$red"; \ fi; \ - echo "$$banner"; \ - test -z "$$skipped" || echo "$$skipped"; \ - test -z "$$report" || echo "$$report"; \ - echo "$$dashes$$std"; \ + echo "$${col}$$dashes$${std}"; \ + echo "$${col}$$banner$${std}"; \ + test -z "$$skipped" || echo "$${col}$$skipped$${std}"; \ + test -z "$$report" || echo "$${col}$$report$${std}"; \ + echo "$${col}$$dashes$${std}"; \ test "$$failed" -eq 0; \ else :; fi @@ -791,10 +840,8 @@ check-am: all-am $(MAKE) $(AM_MAKEFLAGS) check-TESTS check: check-am all-am: Makefile $(LTLIBRARIES) $(PROGRAMS) $(DATA) -install-binPROGRAMS: install-libLTLIBRARIES - installdirs: - for dir in "$(DESTDIR)$(libdir)" "$(DESTDIR)$(bindir)" "$(DESTDIR)$(pkgcfgdir)"; do \ + for dir in "$(DESTDIR)$(libdir)" "$(DESTDIR)$(libexecdir)" "$(DESTDIR)$(pkgcfgdir)"; do \ test -z "$$dir" || $(MKDIR_P) "$$dir"; \ done install: install-am @@ -807,10 +854,15 @@ install-am: all-am installcheck: installcheck-am install-strip: - $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ - install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ - `test -z '$(STRIP)' || \ - echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi mostlyclean-generic: clean-generic: @@ -824,8 +876,8 @@ maintainer-clean-generic: @echo "it deletes files that may require special tools to rebuild." clean: clean-am -clean-am: clean-binPROGRAMS clean-checkPROGRAMS clean-generic \ - clean-libLTLIBRARIES clean-libtool mostlyclean-am +clean-am: clean-checkPROGRAMS clean-generic clean-libLTLIBRARIES \ + clean-libexecPROGRAMS clean-libtool mostlyclean-am distclean: distclean-am -rm -rf ./$(DEPDIR) @@ -851,7 +903,7 @@ install-dvi: install-dvi-am install-dvi-am: -install-exec-am: install-binPROGRAMS install-libLTLIBRARIES +install-exec-am: install-libLTLIBRARIES install-libexecPROGRAMS install-html: install-html-am @@ -891,27 +943,27 @@ ps: ps-am ps-am: -uninstall-am: uninstall-binPROGRAMS uninstall-libLTLIBRARIES \ +uninstall-am: uninstall-libLTLIBRARIES uninstall-libexecPROGRAMS \ uninstall-pkgcfgDATA .MAKE: check-am install-am install-strip .PHONY: CTAGS GTAGS all all-am check check-TESTS check-am clean \ - clean-binPROGRAMS clean-checkPROGRAMS clean-generic \ - clean-libLTLIBRARIES clean-libtool ctags distclean \ + clean-checkPROGRAMS clean-generic clean-libLTLIBRARIES \ + clean-libexecPROGRAMS clean-libtool ctags distclean \ distclean-compile distclean-generic distclean-libtool \ distclean-tags distdir dvi dvi-am html html-am info info-am \ - install install-am install-binPROGRAMS install-data \ - install-data-am install-dvi install-dvi-am install-exec \ - install-exec-am install-html install-html-am install-info \ - install-info-am install-libLTLIBRARIES install-man install-pdf \ - install-pdf-am install-pkgcfgDATA install-ps install-ps-am \ - install-strip installcheck installcheck-am installdirs \ - maintainer-clean maintainer-clean-generic mostlyclean \ - mostlyclean-compile mostlyclean-generic mostlyclean-libtool \ - pdf pdf-am ps ps-am tags uninstall uninstall-am \ - uninstall-binPROGRAMS uninstall-libLTLIBRARIES \ - uninstall-pkgcfgDATA + install install-am install-data install-data-am install-dvi \ + install-dvi-am install-exec install-exec-am install-html \ + install-html-am install-info install-info-am \ + install-libLTLIBRARIES install-libexecPROGRAMS install-man \ + install-pdf install-pdf-am install-pkgcfgDATA install-ps \ + install-ps-am install-strip installcheck installcheck-am \ + installdirs maintainer-clean maintainer-clean-generic \ + mostlyclean mostlyclean-compile mostlyclean-generic \ + mostlyclean-libtool pdf pdf-am ps ps-am tags uninstall \ + uninstall-am uninstall-libLTLIBRARIES \ + uninstall-libexecPROGRAMS uninstall-pkgcfgDATA # Tell versions [3.59,3.63) of GNU make to not export all variables. diff --git a/src/peerinfo/gnunet-service-peerinfo.c b/src/peerinfo/gnunet-service-peerinfo.c index df3486e..68024a9 100644 --- a/src/peerinfo/gnunet-service-peerinfo.c +++ b/src/peerinfo/gnunet-service-peerinfo.c @@ -1,6 +1,6 @@ /* This file is part of GNUnet. - (C) 2001, 2002, 2004, 2005, 2007, 2009, 2010 Christian Grothoff (and other contributing authors) + (C) 2001, 2002, 2004, 2005, 2007, 2009, 2010, 2012 Christian Grothoff (and other contributing authors) GNUnet is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published @@ -28,7 +28,7 @@ * @author Christian Grothoff * * TODO: - * - HostEntries are never 'free'd (add expiration, upper bound?) + * - notify clients when addresses in HELLO expire (#1933) */ #include "platform.h" @@ -103,7 +103,7 @@ make_info_message (const struct HostEntry *he) struct InfoMessage *im; size_t hs; - hs = (he->hello == NULL) ? 0 : GNUNET_HELLO_size (he->hello); + hs = (NULL == he->hello) ? 0 : GNUNET_HELLO_size (he->hello); im = GNUNET_malloc (sizeof (struct InfoMessage) + hs); im->header.size = htons (hs + sizeof (struct InfoMessage)); im->header.type = htons (GNUNET_MESSAGE_TYPE_PEERINFO_INFO); @@ -139,6 +139,25 @@ discard_expired (void *cls, const struct GNUNET_HELLO_Address *address, } +/** + * Address iterator that counts the remaining addresses. + * + * @param cls pointer to the counter + * @param address the address + * @param expiration expiration time for the address + * @return GNUNET_OK (always) + */ +static int +count_addresses (void *cls, const struct GNUNET_HELLO_Address *address, + struct GNUNET_TIME_Absolute expiration) +{ + unsigned int *cnt = cls; + + (*cnt)++; + return GNUNET_OK; +} + + /** * Get the filename under which we would store the GNUNET_HELLO_Message * for the given host and protocol. @@ -152,6 +171,8 @@ get_host_filename (const struct GNUNET_PeerIdentity *id) struct GNUNET_CRYPTO_HashAsciiEncoded fil; char *fn; + if (NULL == networkIdDirectory) + return NULL; GNUNET_CRYPTO_hash_to_enc (&id->hashPubKey, &fil); GNUNET_asprintf (&fn, "%s%s%s", networkIdDirectory, DIR_SEPARATOR_STR, &fil); return fn; @@ -177,19 +198,25 @@ notify_all (struct HostEntry *entry) /** - * Try to read the HELLO in the given filename and discard expired addresses. + * Try to read the HELLO in the given filename and discard expired + * addresses. Removes the file if the HELLO is mal-formed. If all + * addresses are expired, the HELLO is also removed (but the HELLO + * with the public key is still returned if it was found and valid). * * @param fn name of the file + * @param unlink_garbage if GNUNET_YES, try to remove useless files * @return HELLO of the file, NULL on error */ static struct GNUNET_HELLO_Message * -read_host_file (const char *fn) +read_host_file (const char *fn, + int unlink_garbage) { char buffer[GNUNET_SERVER_MAX_MESSAGE_SIZE - 1] GNUNET_ALIGN; const struct GNUNET_HELLO_Message *hello; struct GNUNET_HELLO_Message *hello_clean; int size; struct GNUNET_TIME_Absolute now; + unsigned int left; if (GNUNET_YES != GNUNET_DISK_file_test (fn)) return NULL; @@ -202,12 +229,25 @@ read_host_file (const char *fn) GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("Failed to parse HELLO in file `%s'\n"), fn); + if ( (GNUNET_YES == unlink_garbage) && + (0 != UNLINK (fn)) ) + GNUNET_log_strerror_file (GNUNET_ERROR_TYPE_WARNING, "unlink", fn); return NULL; } now = GNUNET_TIME_absolute_get (); hello_clean = GNUNET_HELLO_iterate_addresses (hello, GNUNET_YES, &discard_expired, &now); + left = 0; + (void) GNUNET_HELLO_iterate_addresses (hello, GNUNET_NO, &count_addresses, + &left); + if (0 == left) + { + /* no addresses left, remove from disk */ + if ( (GNUNET_YES == unlink_garbage) && + (0 != UNLINK (fn)) ) + GNUNET_log_strerror_file (GNUNET_ERROR_TYPE_WARNING, "unlink", fn); + } return hello_clean; } @@ -224,17 +264,20 @@ add_host_to_known_hosts (const struct GNUNET_PeerIdentity *identity) char *fn; entry = GNUNET_CONTAINER_multihashmap_get (hostmap, &identity->hashPubKey); - if (entry != NULL) + if (NULL != entry) return; GNUNET_STATISTICS_update (stats, gettext_noop ("# peers known"), 1, GNUNET_NO); entry = GNUNET_malloc (sizeof (struct HostEntry)); entry->identity = *identity; - GNUNET_CONTAINER_multihashmap_put (hostmap, &identity->hashPubKey, entry, + GNUNET_CONTAINER_multihashmap_put (hostmap, &entry->identity.hashPubKey, entry, GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY); fn = get_host_filename (identity); - entry->hello = read_host_file (fn); - GNUNET_free (fn); + if (NULL != fn) + { + entry->hello = read_host_file (fn, GNUNET_YES); + GNUNET_free (fn); + } notify_all (entry); } @@ -259,6 +302,26 @@ remove_garbage (const char *fullname) } +/** + * Closure for 'hosts_directory_scan_callback'. + */ +struct DirScanContext +{ + /** + * GNUNET_YES if we should remove files that are broken, + * GNUNET_NO if the directory we are iterating over should + * be treated as read-only by us. + */ + int remove_files; + + /** + * Counter for the number of (valid) entries found, incremented + * by one for each match. + */ + unsigned int matched; +}; + + /** * Function that is called on each HELLO file in a particular directory. * Try to parse the file and add the HELLO to our list. @@ -271,53 +334,55 @@ remove_garbage (const char *fullname) static int hosts_directory_scan_callback (void *cls, const char *fullname) { - unsigned int *matched = cls; + struct DirScanContext *dsc = cls; struct GNUNET_PeerIdentity identity; const char *filename; struct HostEntry *entry; struct GNUNET_HELLO_Message *hello; + struct GNUNET_PeerIdentity id; - if (GNUNET_DISK_file_test (fullname) != GNUNET_YES) + if (GNUNET_YES != GNUNET_DISK_file_test (fullname)) return GNUNET_OK; /* ignore non-files */ if (strlen (fullname) < sizeof (struct GNUNET_CRYPTO_HashAsciiEncoded)) { - if (NULL != matched) + if (GNUNET_YES == dsc->remove_files) remove_garbage (fullname); return GNUNET_OK; } filename = &fullname[strlen (fullname) - sizeof (struct GNUNET_CRYPTO_HashAsciiEncoded) + 1]; - if (filename[-1] != DIR_SEPARATOR) + if (DIR_SEPARATOR != filename[-1]) { - if (NULL != matched) + if (GNUNET_YES == dsc->remove_files) remove_garbage (fullname); return GNUNET_OK; } if (GNUNET_OK != GNUNET_CRYPTO_hash_from_string (filename, &identity.hashPubKey)) { - if (NULL != (hello = read_host_file (filename))) + /* odd filename, but might still be valid, try getting identity from HELLO */ + if ( (NULL != (hello = read_host_file (filename, + dsc->remove_files))) && + (GNUNET_OK == + GNUNET_HELLO_get_id (hello, + &id)) ) { + /* ok, found something valid, remember HELLO */ entry = GNUNET_malloc (sizeof (struct HostEntry)); - if (GNUNET_OK == - GNUNET_HELLO_get_id (hello, - &entry->identity)) - { - GNUNET_CONTAINER_multihashmap_put (hostmap, &entry->identity.hashPubKey, entry, - GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY); - entry->hello = hello; - notify_all (entry); - return GNUNET_OK; - } - GNUNET_free (entry); + entry->identity = id; + GNUNET_CONTAINER_multihashmap_put (hostmap, &entry->identity.hashPubKey, entry, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY); + entry->hello = hello; + notify_all (entry); + dsc->matched++; + return GNUNET_OK; } - if (NULL != matched) + if (GNUNET_YES == dsc->remove_files) remove_garbage (fullname); return GNUNET_OK; } - if (NULL != matched) - (*matched)++; + dsc->matched++; add_host_to_known_hosts (&identity); return GNUNET_OK; } @@ -334,11 +399,10 @@ cron_scan_directory_data_hosts (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { static unsigned int retries; - unsigned int count; + struct DirScanContext dsc; if (0 != (tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN)) return; - count = 0; if (GNUNET_SYSERR == GNUNET_DISK_directory_create (networkIdDirectory)) { GNUNET_SCHEDULER_add_delayed_with_priority (DATA_HOST_FREQ, @@ -346,9 +410,11 @@ cron_scan_directory_data_hosts (void *cls, &cron_scan_directory_data_hosts, NULL); return; } + dsc.matched = 0; + dsc.remove_files = GNUNET_YES; GNUNET_DISK_directory_scan (networkIdDirectory, - &hosts_directory_scan_callback, &count); - if ((0 == count) && (0 == (++retries & 31))) + &hosts_directory_scan_callback, &dsc); + if ((0 == dsc.matched) && (0 == (++retries & 31))) GNUNET_log (GNUNET_ERROR_TYPE_WARNING | GNUNET_ERROR_TYPE_BULK, _("Still no peers found in `%s'!\n"), networkIdDirectory); GNUNET_SCHEDULER_add_delayed_with_priority (DATA_HOST_FREQ, @@ -372,11 +438,12 @@ bind_address (const struct GNUNET_PeerIdentity *peer, struct HostEntry *host; struct GNUNET_HELLO_Message *mrg; struct GNUNET_TIME_Absolute delta; + unsigned int cnt; add_host_to_known_hosts (peer); host = GNUNET_CONTAINER_multihashmap_get (hostmap, &peer->hashPubKey); - GNUNET_assert (host != NULL); - if (host->hello == NULL) + GNUNET_assert (NULL != host); + if (NULL == host->hello) { host->hello = GNUNET_malloc (GNUNET_HELLO_size (hello)); memcpy (host->hello, hello, GNUNET_HELLO_size (hello)); @@ -387,6 +454,7 @@ bind_address (const struct GNUNET_PeerIdentity *peer, delta = GNUNET_HELLO_equals (mrg, host->hello, GNUNET_TIME_absolute_get ()); if (delta.abs_value == GNUNET_TIME_UNIT_FOREVER_ABS.abs_value) { + /* no differences, just ignore the update */ GNUNET_free (mrg); return; } @@ -394,18 +462,30 @@ bind_address (const struct GNUNET_PeerIdentity *peer, host->hello = mrg; } fn = get_host_filename (peer); - if (GNUNET_OK == GNUNET_DISK_directory_create_for_file (fn)) + if ( (NULL != fn) && + (GNUNET_OK == GNUNET_DISK_directory_create_for_file (fn)) ) { - if (GNUNET_SYSERR == - GNUNET_DISK_fn_write (fn, host->hello, GNUNET_HELLO_size (host->hello), - GNUNET_DISK_PERM_USER_READ | - GNUNET_DISK_PERM_USER_WRITE | - GNUNET_DISK_PERM_GROUP_READ | - GNUNET_DISK_PERM_OTHER_READ)) - GNUNET_log_strerror_file (GNUNET_ERROR_TYPE_WARNING, "write", fn); - + cnt = 0; + (void) GNUNET_HELLO_iterate_addresses (hello, GNUNET_NO, &count_addresses, + &cnt); + if (0 == cnt) + { + /* no valid addresses, don't put HELLO on disk; in fact, + if one exists on disk, remove it */ + (void) UNLINK (fn); + } + else + { + if (GNUNET_SYSERR == + GNUNET_DISK_fn_write (fn, host->hello, GNUNET_HELLO_size (host->hello), + GNUNET_DISK_PERM_USER_READ | + GNUNET_DISK_PERM_USER_WRITE | + GNUNET_DISK_PERM_GROUP_READ | + GNUNET_DISK_PERM_OTHER_READ)) + GNUNET_log_strerror_file (GNUNET_ERROR_TYPE_WARNING, "write", fn); + } } - GNUNET_free (fn); + GNUNET_free_non_null (fn); notify_all (host); } @@ -419,7 +499,7 @@ bind_address (const struct GNUNET_PeerIdentity *peer, * @return GNUNET_YES (continue to iterate) */ static int -add_to_tc (void *cls, const GNUNET_HashCode * key, void *value) +add_to_tc (void *cls, const struct GNUNET_HashCode * key, void *value) { struct GNUNET_SERVER_TransmitContext *tc = cls; struct HostEntry *pos = value; @@ -461,6 +541,7 @@ discard_hosts_helper (void *cls, const char *fn) const struct GNUNET_HELLO_Message *hello; struct GNUNET_HELLO_Message *new_hello; int size; + unsigned int cnt; size = GNUNET_DISK_fn_read (fn, buffer, sizeof (buffer)); if (size < sizeof (struct GNUNET_MessageHeader)) @@ -472,15 +553,17 @@ discard_hosts_helper (void *cls, const char *fn) } hello = (const struct GNUNET_HELLO_Message *) buffer; new_hello = - GNUNET_HELLO_iterate_addresses (hello, GNUNET_YES, &discard_expired, now); - if (new_hello != NULL) + GNUNET_HELLO_iterate_addresses (hello, GNUNET_YES, &discard_expired, now); + cnt = 0; + if (NULL != new_hello) + (void) GNUNET_HELLO_iterate_addresses (hello, GNUNET_NO, &count_addresses, &cnt); + if ( (NULL != new_hello) && (0 < cnt) ) { GNUNET_DISK_fn_write (fn, new_hello, GNUNET_HELLO_size (new_hello), GNUNET_DISK_PERM_USER_READ | GNUNET_DISK_PERM_USER_WRITE | GNUNET_DISK_PERM_GROUP_READ | GNUNET_DISK_PERM_OTHER_READ); - GNUNET_free (new_hello); } else { @@ -488,6 +571,7 @@ discard_hosts_helper (void *cls, const char *fn) GNUNET_log_strerror_file (GNUNET_ERROR_TYPE_WARNING | GNUNET_ERROR_TYPE_BULK, "unlink", fn); } + GNUNET_free_non_null (new_hello); return GNUNET_OK; } @@ -591,10 +675,16 @@ handle_get_all (void *cls, struct GNUNET_SERVER_Client *client, /** - * FIXME. + * Pass the given client the information we have in the respective + * host entry; the client is already in the notification context. + * + * @param cls the 'struct GNUNET_SERVER_Client' to notify + * @param key key for the value (unused) + * @param value the 'struct HostEntry' to notify the client about + * @return GNUNET_YES (always, continue to iterate) */ static int -do_notify_entry (void *cls, const GNUNET_HashCode * key, void *value) +do_notify_entry (void *cls, const struct GNUNET_HashCode * key, void *value) { struct GNUNET_SERVER_Client *client = cls; struct HostEntry *he = value; @@ -628,10 +718,15 @@ handle_notify (void *cls, struct GNUNET_SERVER_Client *client, /** - * FIXME. + * Release memory taken by a host entry. + * + * @param cls NULL + * @param key key of the host entry + * @param value the 'struct HostEntry' to free + * @return GNUNET_YES (continue to iterate) */ static int -free_host_entry (void *cls, const GNUNET_HashCode * key, void *value) +free_host_entry (void *cls, const struct GNUNET_HashCode * key, void *value) { struct HostEntry *he = value; @@ -654,7 +749,7 @@ shutdown_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) notify_list = NULL; GNUNET_CONTAINER_multihashmap_iterate (hostmap, &free_host_entry, NULL); GNUNET_CONTAINER_multihashmap_destroy (hostmap); - if (stats != NULL) + if (NULL != stats) { GNUNET_STATISTICS_destroy (stats, GNUNET_NO); stats = NULL; @@ -685,33 +780,42 @@ run (void *cls, struct GNUNET_SERVER_Handle *server, }; char *peerdir; char *ip; + struct DirScanContext dsc; + int noio; - hostmap = GNUNET_CONTAINER_multihashmap_create (1024); + hostmap = GNUNET_CONTAINER_multihashmap_create (1024, GNUNET_YES); stats = GNUNET_STATISTICS_create ("peerinfo", cfg); notify_list = GNUNET_SERVER_notification_context_create (server, 0); - GNUNET_assert (GNUNET_OK == - GNUNET_CONFIGURATION_get_value_filename (cfg, "peerinfo", - "HOSTS", - &networkIdDirectory)); - GNUNET_DISK_directory_create (networkIdDirectory); - GNUNET_SCHEDULER_add_with_priority (GNUNET_SCHEDULER_PRIORITY_IDLE, - &cron_scan_directory_data_hosts, NULL); - GNUNET_SCHEDULER_add_with_priority (GNUNET_SCHEDULER_PRIORITY_IDLE, - &cron_clean_data_hosts, NULL); + noio = GNUNET_CONFIGURATION_get_value_yesno (cfg, "peerinfo", "NO_IO"); + if (GNUNET_YES != noio) + { + GNUNET_assert (GNUNET_OK == + GNUNET_CONFIGURATION_get_value_filename (cfg, "peerinfo", + "HOSTS", + &networkIdDirectory)); + GNUNET_DISK_directory_create (networkIdDirectory); + GNUNET_SCHEDULER_add_with_priority (GNUNET_SCHEDULER_PRIORITY_IDLE, + &cron_scan_directory_data_hosts, NULL); + GNUNET_SCHEDULER_add_with_priority (GNUNET_SCHEDULER_PRIORITY_IDLE, + &cron_clean_data_hosts, NULL); + ip = GNUNET_OS_installation_get_path (GNUNET_OS_IPK_DATADIR); + GNUNET_asprintf (&peerdir, + "%shellos", + ip); + GNUNET_free (ip); + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + _("Importing HELLOs from `%s'\n"), + peerdir); + dsc.matched = 0; + dsc.remove_files = GNUNET_NO; + GNUNET_DISK_directory_scan (peerdir, + &hosts_directory_scan_callback, &dsc); + GNUNET_free (peerdir); + } + GNUNET_SERVER_add_handlers (server, handlers); GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, &shutdown_task, NULL); - GNUNET_SERVER_add_handlers (server, handlers); - ip = GNUNET_OS_installation_get_path (GNUNET_OS_IPK_DATADIR); - GNUNET_asprintf (&peerdir, - "%shellos", - ip); - GNUNET_free (ip); - GNUNET_log (GNUNET_ERROR_TYPE_INFO, - _("Importing HELLOs from `%s'\n"), - peerdir); - GNUNET_DISK_directory_scan (peerdir, - &hosts_directory_scan_callback, NULL); - GNUNET_free (peerdir); + } diff --git a/src/peerinfo/peerinfo.conf.in b/src/peerinfo/peerinfo.conf.in index a40cc4f..1420da8 100644 --- a/src/peerinfo/peerinfo.conf.in +++ b/src/peerinfo/peerinfo.conf.in @@ -1,9 +1,8 @@ [peerinfo] AUTOSTART = YES -@UNIXONLY@ PORT = 2090 +@JAVAPORT@PORT = 2090 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-peerinfo ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; @@ -21,4 +20,9 @@ UNIX_MATCH_GID = YES # PREFIX = HOSTS = $SERVICEHOME/data/hosts/ +# Option to disable all disk IO; only useful for testbed runs +# (large-scale experiments); disables persistence of HELLOs! +NO_IO = NO +[uri] +hello = gnunet-peerinfo diff --git a/src/peerinfo/peerinfo.h b/src/peerinfo/peerinfo.h index 919645e..e618487 100644 --- a/src/peerinfo/peerinfo.h +++ b/src/peerinfo/peerinfo.h @@ -38,7 +38,8 @@ struct ListPeerMessage { /** - * Type will be GNUNET_MESSAGE_TYPE_PEERINFO_GET + * Type will be GNUNET_MESSAGE_TYPE_PEERINFO_GET or + * GNUNET_MESSAGE_TYPE_PEERINFO_GET_ALL. */ struct GNUNET_MessageHeader header; diff --git a/src/peerinfo/peerinfo_api.c b/src/peerinfo/peerinfo_api.c index c13224e..175397c 100644 --- a/src/peerinfo/peerinfo_api.c +++ b/src/peerinfo/peerinfo_api.c @@ -131,9 +131,11 @@ struct GNUNET_PEERINFO_IteratorContext int have_peer; /** - * Are we now receiving? + * Set to GNUNET_YES if we are currently receiving replies from the + * service. */ - int in_receive; + int request_transmitted; + }; @@ -183,8 +185,7 @@ struct GNUNET_PEERINFO_Handle GNUNET_SCHEDULER_TaskIdentifier r_task; /** - * Set to GNUNET_YES if we are currently receiving replies from the - * service. + * Are we now receiving? */ int in_receive; @@ -227,8 +228,8 @@ GNUNET_PEERINFO_disconnect (struct GNUNET_PEERINFO_Handle *h) while (NULL != (ic = h->ic_head)) { - GNUNET_break (GNUNET_YES == ic->in_receive); - ic->in_receive = GNUNET_NO; + GNUNET_break (GNUNET_YES == ic->request_transmitted); + ic->request_transmitted = GNUNET_NO; GNUNET_PEERINFO_iterate_cancel (ic); } while (NULL != (ac = h->ac_head)) @@ -393,8 +394,6 @@ trigger_transmit (struct GNUNET_PEERINFO_Handle *h) return; /* no requests queued */ if (NULL != h->th) return; /* request already pending */ - if (GNUNET_YES == h->in_receive) - return; /* still reading replies from last request */ if (NULL == h->client) { /* disconnected, try to reconnect */ @@ -490,29 +489,49 @@ peerinfo_handler (void *cls, const struct GNUNET_MessageHeader *msg) void *cb_cls; uint16_t ms; - GNUNET_assert (NULL != ic); h->in_receive = GNUNET_NO; - ic->in_receive = GNUNET_NO; - cb = ic->callback; - cb_cls = ic->callback_cls; if (NULL == msg) { /* peerinfo service died, signal error */ - GNUNET_PEERINFO_iterate_cancel (ic); + if (NULL != ic) + { + cb = ic->callback; + cb_cls = ic->callback_cls; + GNUNET_PEERINFO_iterate_cancel (ic); + } + else + { + cb = NULL; + } reconnect (h); if (NULL != cb) cb (cb_cls, NULL, NULL, _("Failed to receive response from `PEERINFO' service.")); return; } - + if (NULL == ic) + { + /* didn't expect a response, reconnect */ + reconnect (h); + return; + } + ic->request_transmitted = GNUNET_NO; + cb = ic->callback; + cb_cls = ic->callback_cls; if (GNUNET_MESSAGE_TYPE_PEERINFO_INFO_END == ntohs (msg->type)) { /* normal end of list of peers, signal end, process next pending request */ LOG (GNUNET_ERROR_TYPE_DEBUG, "Received end of list of peers from `%s' service\n", "PEERINFO"); - GNUNET_PEERINFO_iterate_cancel (ic); + GNUNET_PEERINFO_iterate_cancel (ic); trigger_transmit (h); + if ( (GNUNET_NO == h->in_receive) && + (NULL != h->ic_head) ) + { + h->in_receive = GNUNET_YES; + GNUNET_CLIENT_receive (h->client, &peerinfo_handler, h, + GNUNET_TIME_absolute_get_remaining (h->ic_head->timeout)); + } if (NULL != cb) cb (cb_cls, NULL, NULL, NULL); return; @@ -595,7 +614,6 @@ peerinfo_handler (void *cls, const struct GNUNET_MessageHeader *msg) (hello == NULL) ? 0 : (unsigned int) GNUNET_HELLO_size (hello), "HELLO", GNUNET_i2s (&im->peer), "PEERINFO"); h->in_receive = GNUNET_YES; - ic->in_receive = GNUNET_YES; GNUNET_CLIENT_receive (h->client, &peerinfo_handler, h, GNUNET_TIME_absolute_get_remaining (ic->timeout)); if (NULL != cb) @@ -631,7 +649,7 @@ iterator_start_receive (void *cls, const char *emsg) } LOG (GNUNET_ERROR_TYPE_DEBUG, "Waiting for response from `%s' service.\n", "PEERINFO"); - ic->in_receive = GNUNET_YES; + ic->request_transmitted = GNUNET_YES; if (GNUNET_NO == h->in_receive) { h->in_receive = GNUNET_YES; @@ -665,10 +683,10 @@ signal_timeout (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) /** - * Call a method for each known matching host and change its trust - * value. The callback method will be invoked once for each matching - * host and then finally once with a NULL pointer. After that final - * invocation, the iterator context must no longer be used. + * Call a method for each known matching host. The callback method + * will be invoked once for each matching host and then finally once + * with a NULL pointer. After that final invocation, the iterator + * context must no longer be used. * * Instead of calling this function with 'peer == NULL' it is often * better to use 'GNUNET_PEERINFO_notify'. @@ -755,7 +773,7 @@ GNUNET_PEERINFO_iterate_cancel (struct GNUNET_PEERINFO_IteratorContext *ic) ic->timeout_task = GNUNET_SCHEDULER_NO_TASK; } ic->callback = NULL; - if (GNUNET_YES == ic->in_receive) + if (GNUNET_YES == ic->request_transmitted) return; /* need to finish processing */ GNUNET_CONTAINER_DLL_remove (h->ic_head, h->ic_tail, diff --git a/src/peerinfo/perf_peerinfo_api.c b/src/peerinfo/perf_peerinfo_api.c old mode 100644 new mode 100755 index 34888fa..991773c --- a/src/peerinfo/perf_peerinfo_api.c +++ b/src/peerinfo/perf_peerinfo_api.c @@ -19,18 +19,16 @@ */ /** - * @file peerinfo/test_peerinfo_hammer.c + * @file peerinfo/perf_peerinfo_api.c * @brief testcase for peerinfo_api.c, hopefully hammer the peerinfo service * @author Nathan Evans */ #include "platform.h" #include "gnunet_hello_lib.h" -#include "gnunet_getopt_lib.h" -#include "gnunet_os_lib.h" +#include "gnunet_util_lib.h" +#include "gnunet_testing_lib.h" #include "gnunet_peerinfo_service.h" -#include "gnunet_program_lib.h" -#include "gnunet_time_lib.h" #include "peerinfo.h" #include @@ -38,8 +36,6 @@ #define NUM_REQUESTS 5000 -static const struct GNUNET_CONFIGURATION_Handle *cfg; - static struct GNUNET_PEERINFO_IteratorContext *ic[NUM_REQUESTS]; static struct GNUNET_PEERINFO_Handle *h; @@ -112,12 +108,12 @@ process (void *cls, const struct GNUNET_PeerIdentity *peer, static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *c) +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) { size_t i; - cfg = c; h = GNUNET_PEERINFO_connect (cfg); GNUNET_assert (h != NULL); for (i = 0; i < NUM_REQUESTS; i++) @@ -130,61 +126,19 @@ run (void *cls, char *const *args, const char *cfgfile, } } -static int -check () -{ - int ok = 0; - - char *const argv[] = { "perf-peerinfo-api", - "-c", - "test_peerinfo_api_data.conf", - "-L", "ERROR", - NULL - }; -#if START_SERVICE - struct GNUNET_OS_Process *proc; - - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - proc = - GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-peerinfo", - "gnunet-service-peerinfo", - "-L", "ERROR", - "-c", "test_peerinfo_api_data.conf", NULL); -#endif - GNUNET_assert (NULL != proc); - GNUNET_PROGRAM_run ((sizeof (argv) / sizeof (char *)) - 1, argv, - "perf-peerinfo-api", "nohelp", options, &run, &ok); - FPRINTF (stderr, "Received %u/%u calls before timeout\n", numpeers, - NUM_REQUESTS * NUM_REQUESTS / 2); - GAUGER ("PEERINFO", "Peerinfo lookups", numpeers / 30, "peers/s"); -#if START_SERVICE - if (0 != GNUNET_OS_process_kill (proc, SIGTERM)) - { - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); - ok = 1; - } - GNUNET_OS_process_wait (proc); - GNUNET_OS_process_destroy (proc); - proc = NULL; -#endif - return ok; -} - int main (int argc, char *argv[]) { - int ret = 0; - - GNUNET_DISK_directory_remove ("/tmp/test-gnunet-peerinfo"); - GNUNET_log_setup ("perf_peerinfo_api", - "ERROR", - NULL); - ret = check (); - GNUNET_DISK_directory_remove ("/tmp/test-gnunet-peerinfo"); - return ret; + if (0 != GNUNET_TESTING_service_run ("perf-gnunet-peerinfo", + "peerinfo", + "test_peerinfo_api_data.conf", + &run, NULL)) + return 1; + FPRINTF (stderr, "Received %u/%u calls before timeout\n", numpeers, + NUM_REQUESTS * NUM_REQUESTS / 2); + GAUGER ("PEERINFO", "Peerinfo lookups", numpeers / 30, "peers/s"); + return 0; } /* end of perf_peerinfo_api.c */ diff --git a/src/peerinfo/test_peerinfo_api.c b/src/peerinfo/test_peerinfo_api.c index e66878e..f3ab731 100644 --- a/src/peerinfo/test_peerinfo_api.c +++ b/src/peerinfo/test_peerinfo_api.c @@ -26,24 +26,22 @@ * TODO: * - test merging of HELLOs (add same peer twice...) */ - #include "platform.h" #include "gnunet_hello_lib.h" -#include "gnunet_getopt_lib.h" -#include "gnunet_os_lib.h" +#include "gnunet_util_lib.h" #include "gnunet_peerinfo_service.h" -#include "gnunet_program_lib.h" -#include "gnunet_time_lib.h" +#include "gnunet_testing_lib.h" #include "peerinfo.h" -static const struct GNUNET_CONFIGURATION_Handle *cfg; - static struct GNUNET_PEERINFO_IteratorContext *ic; static struct GNUNET_PEERINFO_Handle *h; static unsigned int retries; +static int global_ret; + + static int check_it (void *cls, const struct GNUNET_HELLO_Address *address, struct GNUNET_TIME_Absolute expiration) @@ -106,7 +104,6 @@ static void process (void *cls, const struct GNUNET_PeerIdentity *peer, const struct GNUNET_HELLO_Message *hello, const char *err_msg) { - int *ok = cls; unsigned int agc; if (err_msg != NULL) @@ -118,7 +115,7 @@ process (void *cls, const struct GNUNET_PeerIdentity *peer, if (peer == NULL) { ic = NULL; - if ((3 == *ok) && (retries < 50)) + if ((3 == global_ret) && (retries < 50)) { /* try again */ retries++; @@ -130,30 +127,30 @@ process (void *cls, const struct GNUNET_PeerIdentity *peer, return; } GNUNET_assert (peer == NULL); - GNUNET_assert (2 == *ok); + GNUNET_assert (2 == global_ret); GNUNET_PEERINFO_disconnect (h); h = NULL; - *ok = 0; + global_ret = 0; return; } if (hello != NULL) { - GNUNET_assert (3 == *ok); + GNUNET_assert (3 == global_ret); agc = 3; GNUNET_HELLO_iterate_addresses (hello, GNUNET_NO, &check_it, &agc); GNUNET_assert (agc == 0); - *ok = 2; + global_ret = 2; } } static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *c) +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) { - cfg = c; h = GNUNET_PEERINFO_connect (cfg); - GNUNET_assert (h != NULL); + GNUNET_assert (NULL != h); add_peer (); ic = GNUNET_PEERINFO_iterate (h, NULL, GNUNET_TIME_relative_multiply @@ -161,51 +158,16 @@ run (void *cls, char *const *args, const char *cfgfile, } -static int -check () -{ - int ok = 3; - struct GNUNET_OS_Process *proc; - - char *const argv[] = { "test-peerinfo-api", - "-c", - "test_peerinfo_api_data.conf", - NULL - }; - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - proc = - GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-peerinfo", - "gnunet-service-peerinfo", - "-c", "test_peerinfo_api_data.conf", NULL); - GNUNET_assert (NULL != proc); - GNUNET_PROGRAM_run ((sizeof (argv) / sizeof (char *)) - 1, argv, - "test-peerinfo-api", "nohelp", options, &run, &ok); - if (0 != GNUNET_OS_process_kill (proc, SIGTERM)) - { - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); - ok = 1; - } - GNUNET_OS_process_wait (proc); - GNUNET_OS_process_destroy (proc); - proc = NULL; - return ok; -} - - int main (int argc, char *argv[]) { - int ret = 0; - - GNUNET_DISK_directory_remove ("/tmp/test-gnunet-peerinfo"); - GNUNET_log_setup ("test_peerinfo_api", - "WARNING", - NULL); - ret = check (); - GNUNET_DISK_directory_remove ("/tmp/test-gnunet-peerinfo"); - return ret; + global_ret = 3; + if (0 != GNUNET_TESTING_service_run ("test-gnunet-peerinfo", + "peerinfo", + "test_peerinfo_api_data.conf", + &run, NULL)) + return 1; + return global_ret; } /* end of test_peerinfo_api.c */ diff --git a/src/peerinfo/test_peerinfo_api_data.conf b/src/peerinfo/test_peerinfo_api_data.conf index 6caa1e4..ddbd02b 100644 --- a/src/peerinfo/test_peerinfo_api_data.conf +++ b/src/peerinfo/test_peerinfo_api_data.conf @@ -3,7 +3,6 @@ SERVICEHOME = /tmp/test-gnunet-peerinfo/ [peerinfo] PORT = 22354 -DEBUG = NO [dns] AUTOSTART = NO diff --git a/src/postgres/Makefile.in b/src/postgres/Makefile.in index 36d0f66..598c4df 100644 --- a/src/postgres/Makefile.in +++ b/src/postgres/Makefile.in @@ -1,9 +1,9 @@ -# Makefile.in generated by automake 1.11.1 from Makefile.am. +# Makefile.in generated by automake 1.11.6 from Makefile.am. # @configure_input@ # Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, -# 2003, 2004, 2005, 2006, 2007, 2008, 2009 Free Software Foundation, -# Inc. +# 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Free Software +# Foundation, Inc. # This Makefile.in is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. @@ -16,6 +16,23 @@ @SET_MAKE@ VPATH = @srcdir@ +am__make_dryrun = \ + { \ + am__dry=no; \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + echo 'am--echo: ; @echo "AM" OK' | $(MAKE) -f - 2>/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } pkgdatadir = $(datadir)/@PACKAGE@ pkgincludedir = $(includedir)/@PACKAGE@ pkglibdir = $(libdir)/@PACKAGE@ @@ -40,14 +57,15 @@ DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 am__aclocal_m4_deps = $(top_srcdir)/m4/absolute-header.m4 \ $(top_srcdir)/m4/align.m4 $(top_srcdir)/m4/argz.m4 \ - $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/iconv.m4 \ - $(top_srcdir)/m4/lib-ld.m4 $(top_srcdir)/m4/lib-link.m4 \ - $(top_srcdir)/m4/lib-prefix.m4 $(top_srcdir)/m4/libcurl.m4 \ - $(top_srcdir)/m4/libgcrypt.m4 $(top_srcdir)/m4/libtool.m4 \ - $(top_srcdir)/m4/libunistring.m4 $(top_srcdir)/m4/ltdl.m4 \ - $(top_srcdir)/m4/ltoptions.m4 $(top_srcdir)/m4/ltsugar.m4 \ - $(top_srcdir)/m4/ltversion.m4 $(top_srcdir)/m4/lt~obsolete.m4 \ - $(top_srcdir)/m4/nls.m4 $(top_srcdir)/m4/po.m4 \ + $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/glib-2.0.m4 \ + $(top_srcdir)/m4/iconv.m4 $(top_srcdir)/m4/lib-ld.m4 \ + $(top_srcdir)/m4/lib-link.m4 $(top_srcdir)/m4/lib-prefix.m4 \ + $(top_srcdir)/m4/libcurl.m4 $(top_srcdir)/m4/libgcrypt.m4 \ + $(top_srcdir)/m4/libtool.m4 $(top_srcdir)/m4/libunistring.m4 \ + $(top_srcdir)/m4/ltdl.m4 $(top_srcdir)/m4/ltoptions.m4 \ + $(top_srcdir)/m4/ltsugar.m4 $(top_srcdir)/m4/ltversion.m4 \ + $(top_srcdir)/m4/lt~obsolete.m4 $(top_srcdir)/m4/nls.m4 \ + $(top_srcdir)/m4/pkg.m4 $(top_srcdir)/m4/po.m4 \ $(top_srcdir)/m4/progtest.m4 $(top_srcdir)/acinclude.m4 \ $(top_srcdir)/configure.ac am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ @@ -77,14 +95,20 @@ am__nobase_list = $(am__nobase_strip_setup); \ am__base_list = \ sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \ sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g' +am__uninstall_files_from_dir = { \ + test -z "$$files" \ + || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \ + || { echo " ( cd '$$dir' && rm -f" $$files ")"; \ + $(am__cd) "$$dir" && rm -f $$files; }; \ + } am__installdirs = "$(DESTDIR)$(libdir)" LTLIBRARIES = $(lib_LTLIBRARIES) libgnunetpostgres_la_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la am_libgnunetpostgres_la_OBJECTS = postgres.lo libgnunetpostgres_la_OBJECTS = $(am_libgnunetpostgres_la_OBJECTS) -AM_V_lt = $(am__v_lt_$(V)) -am__v_lt_ = $(am__v_lt_$(AM_DEFAULT_VERBOSITY)) +AM_V_lt = $(am__v_lt_@AM_V@) +am__v_lt_ = $(am__v_lt_@AM_DEFAULT_V@) am__v_lt_0 = --silent libgnunetpostgres_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ @@ -100,24 +124,29 @@ LTCOMPILE = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) \ $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) \ $(AM_CFLAGS) $(CFLAGS) -AM_V_CC = $(am__v_CC_$(V)) -am__v_CC_ = $(am__v_CC_$(AM_DEFAULT_VERBOSITY)) +AM_V_CC = $(am__v_CC_@AM_V@) +am__v_CC_ = $(am__v_CC_@AM_DEFAULT_V@) am__v_CC_0 = @echo " CC " $@; -AM_V_at = $(am__v_at_$(V)) -am__v_at_ = $(am__v_at_$(AM_DEFAULT_VERBOSITY)) +AM_V_at = $(am__v_at_@AM_V@) +am__v_at_ = $(am__v_at_@AM_DEFAULT_V@) am__v_at_0 = @ CCLD = $(CC) LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ $(AM_LDFLAGS) $(LDFLAGS) -o $@ -AM_V_CCLD = $(am__v_CCLD_$(V)) -am__v_CCLD_ = $(am__v_CCLD_$(AM_DEFAULT_VERBOSITY)) +AM_V_CCLD = $(am__v_CCLD_@AM_V@) +am__v_CCLD_ = $(am__v_CCLD_@AM_DEFAULT_V@) am__v_CCLD_0 = @echo " CCLD " $@; -AM_V_GEN = $(am__v_GEN_$(V)) -am__v_GEN_ = $(am__v_GEN_$(AM_DEFAULT_VERBOSITY)) +AM_V_GEN = $(am__v_GEN_@AM_V@) +am__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@) am__v_GEN_0 = @echo " GEN " $@; SOURCES = $(libgnunetpostgres_la_SOURCES) DIST_SOURCES = $(libgnunetpostgres_la_SOURCES) +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac ETAGS = etags CTAGS = ctags DISTFILES = $(DIST_COMMON) $(DIST_SOURCES) $(TEXINFOS) $(EXTRA_DIST) @@ -156,6 +185,10 @@ EXEEXT = @EXEEXT@ EXT_LIBS = @EXT_LIBS@ EXT_LIB_PATH = @EXT_LIB_PATH@ FGREP = @FGREP@ +GLIB_CFLAGS = @GLIB_CFLAGS@ +GLIB_GENMARSHAL = @GLIB_GENMARSHAL@ +GLIB_LIBS = @GLIB_LIBS@ +GLIB_MKENUMS = @GLIB_MKENUMS@ GMSGFMT = @GMSGFMT@ GMSGFMT_015 = @GMSGFMT_015@ GNUNETDNS_GROUP = @GNUNETDNS_GROUP@ @@ -166,6 +199,7 @@ GN_LIBINTL = @GN_LIBINTL@ GN_LIB_LDFLAGS = @GN_LIB_LDFLAGS@ GN_PLUGIN_LDFLAGS = @GN_PLUGIN_LDFLAGS@ GN_USER_HOME_DIR = @GN_USER_HOME_DIR@ +GOBJECT_QUERY = @GOBJECT_QUERY@ GREP = @GREP@ HAVE_LIBUNISTRING = @HAVE_LIBUNISTRING@ INCLTDL = @INCLTDL@ @@ -188,6 +222,8 @@ LIBCURL_CPPFLAGS = @LIBCURL_CPPFLAGS@ LIBGCRYPT_CFLAGS = @LIBGCRYPT_CFLAGS@ LIBGCRYPT_CONFIG = @LIBGCRYPT_CONFIG@ LIBGCRYPT_LIBS = @LIBGCRYPT_LIBS@ +LIBGTOP_CFLAGS = @LIBGTOP_CFLAGS@ +LIBGTOP_LIBS = @LIBGTOP_LIBS@ LIBICONV = @LIBICONV@ LIBINTL = @LIBINTL@ LIBLTDL = @LIBLTDL@ @@ -209,6 +245,7 @@ LT_CONFIG_H = @LT_CONFIG_H@ LT_DLLOADERS = @LT_DLLOADERS@ LT_DLPREOPEN = @LT_DLPREOPEN@ MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ MKDIR_P = @MKDIR_P@ MONKEYPREFIX = @MONKEYPREFIX@ MSGFMT = @MSGFMT@ @@ -218,6 +255,7 @@ MYSQL_CPPFLAGS = @MYSQL_CPPFLAGS@ MYSQL_LDFLAGS = @MYSQL_LDFLAGS@ NM = @NM@ NMEDIT = @NMEDIT@ +NSS_DIR = @NSS_DIR@ OBJC = @OBJC@ OBJCDEPMODE = @OBJCDEPMODE@ OBJCFLAGS = @OBJCFLAGS@ @@ -233,6 +271,7 @@ PACKAGE_TARNAME = @PACKAGE_TARNAME@ PACKAGE_URL = @PACKAGE_URL@ PACKAGE_VERSION = @PACKAGE_VERSION@ PATH_SEPARATOR = @PATH_SEPARATOR@ +PKG_CONFIG = @PKG_CONFIG@ POSTGRES_CPPFLAGS = @POSTGRES_CPPFLAGS@ POSTGRES_LDFLAGS = @POSTGRES_LDFLAGS@ POSUB = @POSUB@ @@ -264,6 +303,7 @@ abs_builddir = @abs_builddir@ abs_srcdir = @abs_srcdir@ abs_top_builddir = @abs_top_builddir@ abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ ac_ct_CC = @ac_ct_CC@ ac_ct_CXX = @ac_ct_CXX@ ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ @@ -286,6 +326,7 @@ datarootdir = @datarootdir@ docdir = @docdir@ dvidir = @dvidir@ exec_prefix = @exec_prefix@ +gitcommand = @gitcommand@ host = @host@ host_alias = @host_alias@ host_cpu = @host_cpu@ @@ -299,7 +340,6 @@ libdir = @libdir@ libexecdir = @libexecdir@ localedir = @localedir@ localstatedir = @localstatedir@ -lt_ECHO = @lt_ECHO@ ltdl_LIBOBJS = @ltdl_LIBOBJS@ ltdl_LTLIBOBJS = @ltdl_LTLIBOBJS@ mandir = @mandir@ @@ -317,6 +357,7 @@ sbindir = @sbindir@ sharedstatedir = @sharedstatedir@ srcdir = @srcdir@ subdirs = @subdirs@ +svnversioncommand = @svnversioncommand@ sys_symbol_underscore = @sys_symbol_underscore@ sysconfdir = @sysconfdir@ target = @target@ @@ -377,7 +418,6 @@ $(ACLOCAL_M4): $(am__aclocal_m4_deps) $(am__aclocal_m4_deps): install-libLTLIBRARIES: $(lib_LTLIBRARIES) @$(NORMAL_INSTALL) - test -z "$(libdir)" || $(MKDIR_P) "$(DESTDIR)$(libdir)" @list='$(lib_LTLIBRARIES)'; test -n "$(libdir)" || list=; \ list2=; for p in $$list; do \ if test -f $$p; then \ @@ -385,6 +425,8 @@ install-libLTLIBRARIES: $(lib_LTLIBRARIES) else :; fi; \ done; \ test -z "$$list2" || { \ + echo " $(MKDIR_P) '$(DESTDIR)$(libdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libdir)" || exit 1; \ echo " $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 '$(DESTDIR)$(libdir)'"; \ $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 "$(DESTDIR)$(libdir)"; \ } @@ -406,7 +448,7 @@ clean-libLTLIBRARIES: echo "rm -f \"$${dir}/so_locations\""; \ rm -f "$${dir}/so_locations"; \ done -libgnunetpostgres.la: $(libgnunetpostgres_la_OBJECTS) $(libgnunetpostgres_la_DEPENDENCIES) +libgnunetpostgres.la: $(libgnunetpostgres_la_OBJECTS) $(libgnunetpostgres_la_DEPENDENCIES) $(EXTRA_libgnunetpostgres_la_DEPENDENCIES) $(AM_V_CCLD)$(libgnunetpostgres_la_LINK) -rpath $(libdir) $(libgnunetpostgres_la_OBJECTS) $(libgnunetpostgres_la_LIBADD) $(LIBS) mostlyclean-compile: @@ -420,26 +462,23 @@ distclean-compile: .c.o: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c $< .c.obj: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'` @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c `$(CYGPATH_W) '$<'` +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c `$(CYGPATH_W) '$<'` .c.lo: @am__fastdepCC_TRUE@ $(AM_V_CC)$(LTCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LTCOMPILE) -c -o $@ $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LTCOMPILE) -c -o $@ $< mostlyclean-libtool: -rm -f *.lo @@ -546,10 +585,15 @@ install-am: all-am installcheck: installcheck-am install-strip: - $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ - install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ - `test -z '$(STRIP)' || \ - echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi mostlyclean-generic: clean-generic: diff --git a/src/pt/Makefile.am b/src/pt/Makefile.am index 385bff6..b9a8e49 100644 --- a/src/pt/Makefile.am +++ b/src/pt/Makefile.am @@ -10,13 +10,15 @@ endif pkgcfgdir= $(pkgdatadir)/config.d/ +libexecdir= $(pkglibdir)/libexec/ + plugindir = $(libdir)/gnunet dist_pkgcfg_DATA = \ pt.conf -bin_PROGRAMS = \ - gnunet-daemon-pt $(PTBIN) +libexec_PROGRAMS = \ + gnunet-daemon-pt gnunet_daemon_pt_SOURCES = \ gnunet-daemon-pt.c @@ -29,3 +31,72 @@ gnunet_daemon_pt_LDADD = \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/mesh/libgnunetmesh.la \ $(GN_LIBINTL) + +if HAVE_MHD +if LINUX + VPN_TEST = \ + test_gnunet_vpn-4_to_6 \ + test_gnunet_vpn-6_to_4 \ + test_gnunet_vpn-6_over \ + test_gnunet_vpn-4_over \ + test_gns_vpn +endif +endif + +check_PROGRAMS = $(VPN_TEST) + +if ENABLE_TEST_RUN +TESTS = $(check_PROGRAMS) +endif + +EXTRA_DIST = \ + test_gnunet_vpn.conf \ + test_gns_vpn.conf + + + +test_gns_vpn_SOURCES = \ + test_gns_vpn.c +test_gns_vpn_LDADD = -lmicrohttpd @LIBCURL@ \ + $(top_builddir)/src/namestore/libgnunetnamestore.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/util/libgnunetutil.la +test_gns_vpn_CPPFLAGS = \ + @LIBCURL_CPPFLAGS@ + +test_gnunet_vpn_4_over_SOURCES = \ + test_gnunet_vpn.c +test_gnunet_vpn_4_over_LDADD = -lmicrohttpd @LIBCURL@ \ + $(top_builddir)/src/vpn/libgnunetvpn.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/util/libgnunetutil.la +test_gnunet_vpn_4_over_CPPFLAGS = \ + @LIBCURL_CPPFLAGS@ + +test_gnunet_vpn_6_over_SOURCES = \ + test_gnunet_vpn.c +test_gnunet_vpn_6_over_LDADD = -lmicrohttpd @LIBCURL@ \ + $(top_builddir)/src/vpn/libgnunetvpn.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/util/libgnunetutil.la +test_gnunet_vpn_6_over_CPPFLAGS = \ + @LIBCURL_CPPFLAGS@ + +test_gnunet_vpn_4_to_6_SOURCES = \ + test_gnunet_vpn.c +test_gnunet_vpn_4_to_6_LDADD = -lmicrohttpd @LIBCURL@ \ + $(top_builddir)/src/vpn/libgnunetvpn.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/util/libgnunetutil.la +test_gnunet_vpn_4_to_6_CPPFLAGS = \ + @LIBCURL_CPPFLAGS@ + +test_gnunet_vpn_6_to_4_SOURCES = \ + test_gnunet_vpn.c +test_gnunet_vpn_6_to_4_LDADD = -lmicrohttpd @LIBCURL@ \ + $(top_builddir)/src/vpn/libgnunetvpn.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/util/libgnunetutil.la +test_gnunet_vpn_6_to_4_CPPFLAGS = \ + @LIBCURL_CPPFLAGS@ + diff --git a/src/pt/Makefile.in b/src/pt/Makefile.in index ca3fee5..ced1f77 100644 --- a/src/pt/Makefile.in +++ b/src/pt/Makefile.in @@ -1,9 +1,9 @@ -# Makefile.in generated by automake 1.11.1 from Makefile.am. +# Makefile.in generated by automake 1.11.6 from Makefile.am. # @configure_input@ # Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, -# 2003, 2004, 2005, 2006, 2007, 2008, 2009 Free Software Foundation, -# Inc. +# 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Free Software +# Foundation, Inc. # This Makefile.in is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. @@ -17,6 +17,23 @@ VPATH = @srcdir@ +am__make_dryrun = \ + { \ + am__dry=no; \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + echo 'am--echo: ; @echo "AM" OK' | $(MAKE) -f - 2>/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } pkgdatadir = $(datadir)/@PACKAGE@ pkgincludedir = $(includedir)/@PACKAGE@ pkglibdir = $(libdir)/@PACKAGE@ @@ -36,21 +53,23 @@ POST_UNINSTALL = : build_triplet = @build@ host_triplet = @host@ target_triplet = @target@ -bin_PROGRAMS = gnunet-daemon-pt$(EXEEXT) +libexec_PROGRAMS = gnunet-daemon-pt$(EXEEXT) +check_PROGRAMS = $(am__EXEEXT_1) subdir = src/pt DIST_COMMON = $(dist_pkgcfg_DATA) $(srcdir)/Makefile.am \ $(srcdir)/Makefile.in ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 am__aclocal_m4_deps = $(top_srcdir)/m4/absolute-header.m4 \ $(top_srcdir)/m4/align.m4 $(top_srcdir)/m4/argz.m4 \ - $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/iconv.m4 \ - $(top_srcdir)/m4/lib-ld.m4 $(top_srcdir)/m4/lib-link.m4 \ - $(top_srcdir)/m4/lib-prefix.m4 $(top_srcdir)/m4/libcurl.m4 \ - $(top_srcdir)/m4/libgcrypt.m4 $(top_srcdir)/m4/libtool.m4 \ - $(top_srcdir)/m4/libunistring.m4 $(top_srcdir)/m4/ltdl.m4 \ - $(top_srcdir)/m4/ltoptions.m4 $(top_srcdir)/m4/ltsugar.m4 \ - $(top_srcdir)/m4/ltversion.m4 $(top_srcdir)/m4/lt~obsolete.m4 \ - $(top_srcdir)/m4/nls.m4 $(top_srcdir)/m4/po.m4 \ + $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/glib-2.0.m4 \ + $(top_srcdir)/m4/iconv.m4 $(top_srcdir)/m4/lib-ld.m4 \ + $(top_srcdir)/m4/lib-link.m4 $(top_srcdir)/m4/lib-prefix.m4 \ + $(top_srcdir)/m4/libcurl.m4 $(top_srcdir)/m4/libgcrypt.m4 \ + $(top_srcdir)/m4/libtool.m4 $(top_srcdir)/m4/libunistring.m4 \ + $(top_srcdir)/m4/ltdl.m4 $(top_srcdir)/m4/ltoptions.m4 \ + $(top_srcdir)/m4/ltsugar.m4 $(top_srcdir)/m4/ltversion.m4 \ + $(top_srcdir)/m4/lt~obsolete.m4 $(top_srcdir)/m4/nls.m4 \ + $(top_srcdir)/m4/pkg.m4 $(top_srcdir)/m4/po.m4 \ $(top_srcdir)/m4/progtest.m4 $(top_srcdir)/acinclude.m4 \ $(top_srcdir)/configure.ac am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ @@ -59,8 +78,14 @@ mkinstalldirs = $(install_sh) -d CONFIG_HEADER = $(top_builddir)/gnunet_config.h CONFIG_CLEAN_FILES = CONFIG_CLEAN_VPATH_FILES = -am__installdirs = "$(DESTDIR)$(bindir)" "$(DESTDIR)$(pkgcfgdir)" -PROGRAMS = $(bin_PROGRAMS) +@HAVE_MHD_TRUE@@LINUX_TRUE@am__EXEEXT_1 = \ +@HAVE_MHD_TRUE@@LINUX_TRUE@ test_gnunet_vpn-4_to_6$(EXEEXT) \ +@HAVE_MHD_TRUE@@LINUX_TRUE@ test_gnunet_vpn-6_to_4$(EXEEXT) \ +@HAVE_MHD_TRUE@@LINUX_TRUE@ test_gnunet_vpn-6_over$(EXEEXT) \ +@HAVE_MHD_TRUE@@LINUX_TRUE@ test_gnunet_vpn-4_over$(EXEEXT) \ +@HAVE_MHD_TRUE@@LINUX_TRUE@ test_gns_vpn$(EXEEXT) +am__installdirs = "$(DESTDIR)$(libexecdir)" "$(DESTDIR)$(pkgcfgdir)" +PROGRAMS = $(libexec_PROGRAMS) am_gnunet_daemon_pt_OBJECTS = gnunet-daemon-pt.$(OBJEXT) gnunet_daemon_pt_OBJECTS = $(am_gnunet_daemon_pt_OBJECTS) am__DEPENDENCIES_1 = @@ -73,9 +98,43 @@ gnunet_daemon_pt_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/mesh/libgnunetmesh.la \ $(am__DEPENDENCIES_1) -AM_V_lt = $(am__v_lt_$(V)) -am__v_lt_ = $(am__v_lt_$(AM_DEFAULT_VERBOSITY)) +AM_V_lt = $(am__v_lt_@AM_V@) +am__v_lt_ = $(am__v_lt_@AM_DEFAULT_V@) am__v_lt_0 = --silent +am_test_gns_vpn_OBJECTS = test_gns_vpn-test_gns_vpn.$(OBJEXT) +test_gns_vpn_OBJECTS = $(am_test_gns_vpn_OBJECTS) +test_gns_vpn_DEPENDENCIES = \ + $(top_builddir)/src/namestore/libgnunetnamestore.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/util/libgnunetutil.la +am_test_gnunet_vpn_4_over_OBJECTS = \ + test_gnunet_vpn_4_over-test_gnunet_vpn.$(OBJEXT) +test_gnunet_vpn_4_over_OBJECTS = $(am_test_gnunet_vpn_4_over_OBJECTS) +test_gnunet_vpn_4_over_DEPENDENCIES = \ + $(top_builddir)/src/vpn/libgnunetvpn.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/util/libgnunetutil.la +am_test_gnunet_vpn_4_to_6_OBJECTS = \ + test_gnunet_vpn_4_to_6-test_gnunet_vpn.$(OBJEXT) +test_gnunet_vpn_4_to_6_OBJECTS = $(am_test_gnunet_vpn_4_to_6_OBJECTS) +test_gnunet_vpn_4_to_6_DEPENDENCIES = \ + $(top_builddir)/src/vpn/libgnunetvpn.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/util/libgnunetutil.la +am_test_gnunet_vpn_6_over_OBJECTS = \ + test_gnunet_vpn_6_over-test_gnunet_vpn.$(OBJEXT) +test_gnunet_vpn_6_over_OBJECTS = $(am_test_gnunet_vpn_6_over_OBJECTS) +test_gnunet_vpn_6_over_DEPENDENCIES = \ + $(top_builddir)/src/vpn/libgnunetvpn.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/util/libgnunetutil.la +am_test_gnunet_vpn_6_to_4_OBJECTS = \ + test_gnunet_vpn_6_to_4-test_gnunet_vpn.$(OBJEXT) +test_gnunet_vpn_6_to_4_OBJECTS = $(am_test_gnunet_vpn_6_to_4_OBJECTS) +test_gnunet_vpn_6_to_4_DEPENDENCIES = \ + $(top_builddir)/src/vpn/libgnunetvpn.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/util/libgnunetutil.la DEFAULT_INCLUDES = -I.@am__isrc@ -I$(top_builddir) depcomp = $(SHELL) $(top_srcdir)/depcomp am__depfiles_maybe = depfiles @@ -86,24 +145,37 @@ LTCOMPILE = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) \ $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) \ $(AM_CFLAGS) $(CFLAGS) -AM_V_CC = $(am__v_CC_$(V)) -am__v_CC_ = $(am__v_CC_$(AM_DEFAULT_VERBOSITY)) +AM_V_CC = $(am__v_CC_@AM_V@) +am__v_CC_ = $(am__v_CC_@AM_DEFAULT_V@) am__v_CC_0 = @echo " CC " $@; -AM_V_at = $(am__v_at_$(V)) -am__v_at_ = $(am__v_at_$(AM_DEFAULT_VERBOSITY)) +AM_V_at = $(am__v_at_@AM_V@) +am__v_at_ = $(am__v_at_@AM_DEFAULT_V@) am__v_at_0 = @ CCLD = $(CC) LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ $(AM_LDFLAGS) $(LDFLAGS) -o $@ -AM_V_CCLD = $(am__v_CCLD_$(V)) -am__v_CCLD_ = $(am__v_CCLD_$(AM_DEFAULT_VERBOSITY)) +AM_V_CCLD = $(am__v_CCLD_@AM_V@) +am__v_CCLD_ = $(am__v_CCLD_@AM_DEFAULT_V@) am__v_CCLD_0 = @echo " CCLD " $@; -AM_V_GEN = $(am__v_GEN_$(V)) -am__v_GEN_ = $(am__v_GEN_$(AM_DEFAULT_VERBOSITY)) +AM_V_GEN = $(am__v_GEN_@AM_V@) +am__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@) am__v_GEN_0 = @echo " GEN " $@; -SOURCES = $(gnunet_daemon_pt_SOURCES) -DIST_SOURCES = $(gnunet_daemon_pt_SOURCES) +SOURCES = $(gnunet_daemon_pt_SOURCES) $(test_gns_vpn_SOURCES) \ + $(test_gnunet_vpn_4_over_SOURCES) \ + $(test_gnunet_vpn_4_to_6_SOURCES) \ + $(test_gnunet_vpn_6_over_SOURCES) \ + $(test_gnunet_vpn_6_to_4_SOURCES) +DIST_SOURCES = $(gnunet_daemon_pt_SOURCES) $(test_gns_vpn_SOURCES) \ + $(test_gnunet_vpn_4_over_SOURCES) \ + $(test_gnunet_vpn_4_to_6_SOURCES) \ + $(test_gnunet_vpn_6_over_SOURCES) \ + $(test_gnunet_vpn_6_to_4_SOURCES) +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac am__vpath_adj_setup = srcdirstrip=`echo "$(srcdir)" | sed 's|.|.|g'`; am__vpath_adj = case $$p in \ $(srcdir)/*) f=`echo "$$p" | sed "s|^$$srcdirstrip/||"`;; \ @@ -125,9 +197,17 @@ am__nobase_list = $(am__nobase_strip_setup); \ am__base_list = \ sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \ sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g' +am__uninstall_files_from_dir = { \ + test -z "$$files" \ + || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \ + || { echo " ( cd '$$dir' && rm -f" $$files ")"; \ + $(am__cd) "$$dir" && rm -f $$files; }; \ + } DATA = $(dist_pkgcfg_DATA) ETAGS = etags CTAGS = ctags +am__tty_colors = \ +red=; grn=; lgn=; blu=; std= DISTFILES = $(DIST_COMMON) $(DIST_SOURCES) $(TEXINFOS) $(EXTRA_DIST) ACLOCAL = @ACLOCAL@ AMTAR = @AMTAR@ @@ -164,6 +244,10 @@ EXEEXT = @EXEEXT@ EXT_LIBS = @EXT_LIBS@ EXT_LIB_PATH = @EXT_LIB_PATH@ FGREP = @FGREP@ +GLIB_CFLAGS = @GLIB_CFLAGS@ +GLIB_GENMARSHAL = @GLIB_GENMARSHAL@ +GLIB_LIBS = @GLIB_LIBS@ +GLIB_MKENUMS = @GLIB_MKENUMS@ GMSGFMT = @GMSGFMT@ GMSGFMT_015 = @GMSGFMT_015@ GNUNETDNS_GROUP = @GNUNETDNS_GROUP@ @@ -174,6 +258,7 @@ GN_LIBINTL = @GN_LIBINTL@ GN_LIB_LDFLAGS = @GN_LIB_LDFLAGS@ GN_PLUGIN_LDFLAGS = @GN_PLUGIN_LDFLAGS@ GN_USER_HOME_DIR = @GN_USER_HOME_DIR@ +GOBJECT_QUERY = @GOBJECT_QUERY@ GREP = @GREP@ HAVE_LIBUNISTRING = @HAVE_LIBUNISTRING@ INCLTDL = @INCLTDL@ @@ -196,6 +281,8 @@ LIBCURL_CPPFLAGS = @LIBCURL_CPPFLAGS@ LIBGCRYPT_CFLAGS = @LIBGCRYPT_CFLAGS@ LIBGCRYPT_CONFIG = @LIBGCRYPT_CONFIG@ LIBGCRYPT_LIBS = @LIBGCRYPT_LIBS@ +LIBGTOP_CFLAGS = @LIBGTOP_CFLAGS@ +LIBGTOP_LIBS = @LIBGTOP_LIBS@ LIBICONV = @LIBICONV@ LIBINTL = @LIBINTL@ LIBLTDL = @LIBLTDL@ @@ -217,6 +304,7 @@ LT_CONFIG_H = @LT_CONFIG_H@ LT_DLLOADERS = @LT_DLLOADERS@ LT_DLPREOPEN = @LT_DLPREOPEN@ MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ MKDIR_P = @MKDIR_P@ MONKEYPREFIX = @MONKEYPREFIX@ MSGFMT = @MSGFMT@ @@ -226,6 +314,7 @@ MYSQL_CPPFLAGS = @MYSQL_CPPFLAGS@ MYSQL_LDFLAGS = @MYSQL_LDFLAGS@ NM = @NM@ NMEDIT = @NMEDIT@ +NSS_DIR = @NSS_DIR@ OBJC = @OBJC@ OBJCDEPMODE = @OBJCDEPMODE@ OBJCFLAGS = @OBJCFLAGS@ @@ -241,6 +330,7 @@ PACKAGE_TARNAME = @PACKAGE_TARNAME@ PACKAGE_URL = @PACKAGE_URL@ PACKAGE_VERSION = @PACKAGE_VERSION@ PATH_SEPARATOR = @PATH_SEPARATOR@ +PKG_CONFIG = @PKG_CONFIG@ POSTGRES_CPPFLAGS = @POSTGRES_CPPFLAGS@ POSTGRES_LDFLAGS = @POSTGRES_LDFLAGS@ POSUB = @POSUB@ @@ -272,6 +362,7 @@ abs_builddir = @abs_builddir@ abs_srcdir = @abs_srcdir@ abs_top_builddir = @abs_top_builddir@ abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ ac_ct_CC = @ac_ct_CC@ ac_ct_CXX = @ac_ct_CXX@ ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ @@ -294,6 +385,7 @@ datarootdir = @datarootdir@ docdir = @docdir@ dvidir = @dvidir@ exec_prefix = @exec_prefix@ +gitcommand = @gitcommand@ host = @host@ host_alias = @host_alias@ host_cpu = @host_cpu@ @@ -304,10 +396,9 @@ includedir = @includedir@ infodir = @infodir@ install_sh = @install_sh@ libdir = @libdir@ -libexecdir = @libexecdir@ +libexecdir = $(pkglibdir)/libexec/ localedir = @localedir@ localstatedir = @localstatedir@ -lt_ECHO = @lt_ECHO@ ltdl_LIBOBJS = @ltdl_LIBOBJS@ ltdl_LTLIBOBJS = @ltdl_LTLIBOBJS@ mandir = @mandir@ @@ -325,6 +416,7 @@ sbindir = @sbindir@ sharedstatedir = @sharedstatedir@ srcdir = @srcdir@ subdirs = @subdirs@ +svnversioncommand = @svnversioncommand@ sys_symbol_underscore = @sys_symbol_underscore@ sysconfdir = @sysconfdir@ target = @target@ @@ -356,6 +448,73 @@ gnunet_daemon_pt_LDADD = \ $(top_builddir)/src/mesh/libgnunetmesh.la \ $(GN_LIBINTL) +@HAVE_MHD_TRUE@@LINUX_TRUE@VPN_TEST = \ +@HAVE_MHD_TRUE@@LINUX_TRUE@ test_gnunet_vpn-4_to_6 \ +@HAVE_MHD_TRUE@@LINUX_TRUE@ test_gnunet_vpn-6_to_4 \ +@HAVE_MHD_TRUE@@LINUX_TRUE@ test_gnunet_vpn-6_over \ +@HAVE_MHD_TRUE@@LINUX_TRUE@ test_gnunet_vpn-4_over \ +@HAVE_MHD_TRUE@@LINUX_TRUE@ test_gns_vpn + +@ENABLE_TEST_RUN_TRUE@TESTS = $(check_PROGRAMS) +EXTRA_DIST = \ + test_gnunet_vpn.conf \ + test_gns_vpn.conf + +test_gns_vpn_SOURCES = \ + test_gns_vpn.c + +test_gns_vpn_LDADD = -lmicrohttpd @LIBCURL@ \ + $(top_builddir)/src/namestore/libgnunetnamestore.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/util/libgnunetutil.la + +test_gns_vpn_CPPFLAGS = \ + @LIBCURL_CPPFLAGS@ + +test_gnunet_vpn_4_over_SOURCES = \ + test_gnunet_vpn.c + +test_gnunet_vpn_4_over_LDADD = -lmicrohttpd @LIBCURL@ \ + $(top_builddir)/src/vpn/libgnunetvpn.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/util/libgnunetutil.la + +test_gnunet_vpn_4_over_CPPFLAGS = \ + @LIBCURL_CPPFLAGS@ + +test_gnunet_vpn_6_over_SOURCES = \ + test_gnunet_vpn.c + +test_gnunet_vpn_6_over_LDADD = -lmicrohttpd @LIBCURL@ \ + $(top_builddir)/src/vpn/libgnunetvpn.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/util/libgnunetutil.la + +test_gnunet_vpn_6_over_CPPFLAGS = \ + @LIBCURL_CPPFLAGS@ + +test_gnunet_vpn_4_to_6_SOURCES = \ + test_gnunet_vpn.c + +test_gnunet_vpn_4_to_6_LDADD = -lmicrohttpd @LIBCURL@ \ + $(top_builddir)/src/vpn/libgnunetvpn.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/util/libgnunetutil.la + +test_gnunet_vpn_4_to_6_CPPFLAGS = \ + @LIBCURL_CPPFLAGS@ + +test_gnunet_vpn_6_to_4_SOURCES = \ + test_gnunet_vpn.c + +test_gnunet_vpn_6_to_4_LDADD = -lmicrohttpd @LIBCURL@ \ + $(top_builddir)/src/vpn/libgnunetvpn.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/util/libgnunetutil.la + +test_gnunet_vpn_6_to_4_CPPFLAGS = \ + @LIBCURL_CPPFLAGS@ + all: all-am .SUFFIXES: @@ -390,10 +549,22 @@ $(top_srcdir)/configure: $(am__configure_deps) $(ACLOCAL_M4): $(am__aclocal_m4_deps) cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh $(am__aclocal_m4_deps): -install-binPROGRAMS: $(bin_PROGRAMS) + +clean-checkPROGRAMS: + @list='$(check_PROGRAMS)'; test -n "$$list" || exit 0; \ + echo " rm -f" $$list; \ + rm -f $$list || exit $$?; \ + test -n "$(EXEEXT)" || exit 0; \ + list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ + echo " rm -f" $$list; \ + rm -f $$list +install-libexecPROGRAMS: $(libexec_PROGRAMS) @$(NORMAL_INSTALL) - test -z "$(bindir)" || $(MKDIR_P) "$(DESTDIR)$(bindir)" - @list='$(bin_PROGRAMS)'; test -n "$(bindir)" || list=; \ + @list='$(libexec_PROGRAMS)'; test -n "$(libexecdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(libexecdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libexecdir)" || exit 1; \ + fi; \ for p in $$list; do echo "$$p $$p"; done | \ sed 's/$(EXEEXT)$$//' | \ while read p p1; do if test -f $$p || test -f $$p1; \ @@ -410,32 +581,47 @@ install-binPROGRAMS: $(bin_PROGRAMS) while read type dir files; do \ if test "$$dir" = .; then dir=; else dir=/$$dir; fi; \ test -z "$$files" || { \ - echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files '$(DESTDIR)$(bindir)$$dir'"; \ - $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files "$(DESTDIR)$(bindir)$$dir" || exit $$?; \ + echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files '$(DESTDIR)$(libexecdir)$$dir'"; \ + $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files "$(DESTDIR)$(libexecdir)$$dir" || exit $$?; \ } \ ; done -uninstall-binPROGRAMS: +uninstall-libexecPROGRAMS: @$(NORMAL_UNINSTALL) - @list='$(bin_PROGRAMS)'; test -n "$(bindir)" || list=; \ + @list='$(libexec_PROGRAMS)'; test -n "$(libexecdir)" || list=; \ files=`for p in $$list; do echo "$$p"; done | \ sed -e 'h;s,^.*/,,;s/$(EXEEXT)$$//;$(transform)' \ -e 's/$$/$(EXEEXT)/' `; \ test -n "$$list" || exit 0; \ - echo " ( cd '$(DESTDIR)$(bindir)' && rm -f" $$files ")"; \ - cd "$(DESTDIR)$(bindir)" && rm -f $$files + echo " ( cd '$(DESTDIR)$(libexecdir)' && rm -f" $$files ")"; \ + cd "$(DESTDIR)$(libexecdir)" && rm -f $$files -clean-binPROGRAMS: - @list='$(bin_PROGRAMS)'; test -n "$$list" || exit 0; \ +clean-libexecPROGRAMS: + @list='$(libexec_PROGRAMS)'; test -n "$$list" || exit 0; \ echo " rm -f" $$list; \ rm -f $$list || exit $$?; \ test -n "$(EXEEXT)" || exit 0; \ list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ echo " rm -f" $$list; \ rm -f $$list -gnunet-daemon-pt$(EXEEXT): $(gnunet_daemon_pt_OBJECTS) $(gnunet_daemon_pt_DEPENDENCIES) +gnunet-daemon-pt$(EXEEXT): $(gnunet_daemon_pt_OBJECTS) $(gnunet_daemon_pt_DEPENDENCIES) $(EXTRA_gnunet_daemon_pt_DEPENDENCIES) @rm -f gnunet-daemon-pt$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_daemon_pt_OBJECTS) $(gnunet_daemon_pt_LDADD) $(LIBS) +test_gns_vpn$(EXEEXT): $(test_gns_vpn_OBJECTS) $(test_gns_vpn_DEPENDENCIES) $(EXTRA_test_gns_vpn_DEPENDENCIES) + @rm -f test_gns_vpn$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_gns_vpn_OBJECTS) $(test_gns_vpn_LDADD) $(LIBS) +test_gnunet_vpn-4_over$(EXEEXT): $(test_gnunet_vpn_4_over_OBJECTS) $(test_gnunet_vpn_4_over_DEPENDENCIES) $(EXTRA_test_gnunet_vpn_4_over_DEPENDENCIES) + @rm -f test_gnunet_vpn-4_over$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_gnunet_vpn_4_over_OBJECTS) $(test_gnunet_vpn_4_over_LDADD) $(LIBS) +test_gnunet_vpn-4_to_6$(EXEEXT): $(test_gnunet_vpn_4_to_6_OBJECTS) $(test_gnunet_vpn_4_to_6_DEPENDENCIES) $(EXTRA_test_gnunet_vpn_4_to_6_DEPENDENCIES) + @rm -f test_gnunet_vpn-4_to_6$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_gnunet_vpn_4_to_6_OBJECTS) $(test_gnunet_vpn_4_to_6_LDADD) $(LIBS) +test_gnunet_vpn-6_over$(EXEEXT): $(test_gnunet_vpn_6_over_OBJECTS) $(test_gnunet_vpn_6_over_DEPENDENCIES) $(EXTRA_test_gnunet_vpn_6_over_DEPENDENCIES) + @rm -f test_gnunet_vpn-6_over$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_gnunet_vpn_6_over_OBJECTS) $(test_gnunet_vpn_6_over_LDADD) $(LIBS) +test_gnunet_vpn-6_to_4$(EXEEXT): $(test_gnunet_vpn_6_to_4_OBJECTS) $(test_gnunet_vpn_6_to_4_DEPENDENCIES) $(EXTRA_test_gnunet_vpn_6_to_4_DEPENDENCIES) + @rm -f test_gnunet_vpn-6_to_4$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_gnunet_vpn_6_to_4_OBJECTS) $(test_gnunet_vpn_6_to_4_LDADD) $(LIBS) mostlyclean-compile: -rm -f *.$(OBJEXT) @@ -444,30 +630,102 @@ distclean-compile: -rm -f *.tab.c @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-daemon-pt.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_gns_vpn-test_gns_vpn.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_gnunet_vpn_4_over-test_gnunet_vpn.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_gnunet_vpn_4_to_6-test_gnunet_vpn.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_gnunet_vpn_6_over-test_gnunet_vpn.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_gnunet_vpn_6_to_4-test_gnunet_vpn.Po@am__quote@ .c.o: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c $< .c.obj: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'` @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c `$(CYGPATH_W) '$<'` +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c `$(CYGPATH_W) '$<'` .c.lo: @am__fastdepCC_TRUE@ $(AM_V_CC)$(LTCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LTCOMPILE) -c -o $@ $< + +test_gns_vpn-test_gns_vpn.o: test_gns_vpn.c +@am__fastdepCC_TRUE@ $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(test_gns_vpn_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT test_gns_vpn-test_gns_vpn.o -MD -MP -MF $(DEPDIR)/test_gns_vpn-test_gns_vpn.Tpo -c -o test_gns_vpn-test_gns_vpn.o `test -f 'test_gns_vpn.c' || echo '$(srcdir)/'`test_gns_vpn.c +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/test_gns_vpn-test_gns_vpn.Tpo $(DEPDIR)/test_gns_vpn-test_gns_vpn.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='test_gns_vpn.c' object='test_gns_vpn-test_gns_vpn.o' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(test_gns_vpn_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o test_gns_vpn-test_gns_vpn.o `test -f 'test_gns_vpn.c' || echo '$(srcdir)/'`test_gns_vpn.c + +test_gns_vpn-test_gns_vpn.obj: test_gns_vpn.c +@am__fastdepCC_TRUE@ $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(test_gns_vpn_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT test_gns_vpn-test_gns_vpn.obj -MD -MP -MF $(DEPDIR)/test_gns_vpn-test_gns_vpn.Tpo -c -o test_gns_vpn-test_gns_vpn.obj `if test -f 'test_gns_vpn.c'; then $(CYGPATH_W) 'test_gns_vpn.c'; else $(CYGPATH_W) '$(srcdir)/test_gns_vpn.c'; fi` +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/test_gns_vpn-test_gns_vpn.Tpo $(DEPDIR)/test_gns_vpn-test_gns_vpn.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='test_gns_vpn.c' object='test_gns_vpn-test_gns_vpn.obj' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(test_gns_vpn_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o test_gns_vpn-test_gns_vpn.obj `if test -f 'test_gns_vpn.c'; then $(CYGPATH_W) 'test_gns_vpn.c'; else $(CYGPATH_W) '$(srcdir)/test_gns_vpn.c'; fi` + +test_gnunet_vpn_4_over-test_gnunet_vpn.o: test_gnunet_vpn.c +@am__fastdepCC_TRUE@ $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(test_gnunet_vpn_4_over_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT test_gnunet_vpn_4_over-test_gnunet_vpn.o -MD -MP -MF $(DEPDIR)/test_gnunet_vpn_4_over-test_gnunet_vpn.Tpo -c -o test_gnunet_vpn_4_over-test_gnunet_vpn.o `test -f 'test_gnunet_vpn.c' || echo '$(srcdir)/'`test_gnunet_vpn.c +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/test_gnunet_vpn_4_over-test_gnunet_vpn.Tpo $(DEPDIR)/test_gnunet_vpn_4_over-test_gnunet_vpn.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='test_gnunet_vpn.c' object='test_gnunet_vpn_4_over-test_gnunet_vpn.o' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(test_gnunet_vpn_4_over_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o test_gnunet_vpn_4_over-test_gnunet_vpn.o `test -f 'test_gnunet_vpn.c' || echo '$(srcdir)/'`test_gnunet_vpn.c + +test_gnunet_vpn_4_over-test_gnunet_vpn.obj: test_gnunet_vpn.c +@am__fastdepCC_TRUE@ $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(test_gnunet_vpn_4_over_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT test_gnunet_vpn_4_over-test_gnunet_vpn.obj -MD -MP -MF $(DEPDIR)/test_gnunet_vpn_4_over-test_gnunet_vpn.Tpo -c -o test_gnunet_vpn_4_over-test_gnunet_vpn.obj `if test -f 'test_gnunet_vpn.c'; then $(CYGPATH_W) 'test_gnunet_vpn.c'; else $(CYGPATH_W) '$(srcdir)/test_gnunet_vpn.c'; fi` +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/test_gnunet_vpn_4_over-test_gnunet_vpn.Tpo $(DEPDIR)/test_gnunet_vpn_4_over-test_gnunet_vpn.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='test_gnunet_vpn.c' object='test_gnunet_vpn_4_over-test_gnunet_vpn.obj' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(test_gnunet_vpn_4_over_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o test_gnunet_vpn_4_over-test_gnunet_vpn.obj `if test -f 'test_gnunet_vpn.c'; then $(CYGPATH_W) 'test_gnunet_vpn.c'; else $(CYGPATH_W) '$(srcdir)/test_gnunet_vpn.c'; fi` + +test_gnunet_vpn_4_to_6-test_gnunet_vpn.o: test_gnunet_vpn.c +@am__fastdepCC_TRUE@ $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(test_gnunet_vpn_4_to_6_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT test_gnunet_vpn_4_to_6-test_gnunet_vpn.o -MD -MP -MF $(DEPDIR)/test_gnunet_vpn_4_to_6-test_gnunet_vpn.Tpo -c -o test_gnunet_vpn_4_to_6-test_gnunet_vpn.o `test -f 'test_gnunet_vpn.c' || echo '$(srcdir)/'`test_gnunet_vpn.c +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/test_gnunet_vpn_4_to_6-test_gnunet_vpn.Tpo $(DEPDIR)/test_gnunet_vpn_4_to_6-test_gnunet_vpn.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='test_gnunet_vpn.c' object='test_gnunet_vpn_4_to_6-test_gnunet_vpn.o' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(test_gnunet_vpn_4_to_6_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o test_gnunet_vpn_4_to_6-test_gnunet_vpn.o `test -f 'test_gnunet_vpn.c' || echo '$(srcdir)/'`test_gnunet_vpn.c + +test_gnunet_vpn_4_to_6-test_gnunet_vpn.obj: test_gnunet_vpn.c +@am__fastdepCC_TRUE@ $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(test_gnunet_vpn_4_to_6_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT test_gnunet_vpn_4_to_6-test_gnunet_vpn.obj -MD -MP -MF $(DEPDIR)/test_gnunet_vpn_4_to_6-test_gnunet_vpn.Tpo -c -o test_gnunet_vpn_4_to_6-test_gnunet_vpn.obj `if test -f 'test_gnunet_vpn.c'; then $(CYGPATH_W) 'test_gnunet_vpn.c'; else $(CYGPATH_W) '$(srcdir)/test_gnunet_vpn.c'; fi` +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/test_gnunet_vpn_4_to_6-test_gnunet_vpn.Tpo $(DEPDIR)/test_gnunet_vpn_4_to_6-test_gnunet_vpn.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='test_gnunet_vpn.c' object='test_gnunet_vpn_4_to_6-test_gnunet_vpn.obj' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(test_gnunet_vpn_4_to_6_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o test_gnunet_vpn_4_to_6-test_gnunet_vpn.obj `if test -f 'test_gnunet_vpn.c'; then $(CYGPATH_W) 'test_gnunet_vpn.c'; else $(CYGPATH_W) '$(srcdir)/test_gnunet_vpn.c'; fi` + +test_gnunet_vpn_6_over-test_gnunet_vpn.o: test_gnunet_vpn.c +@am__fastdepCC_TRUE@ $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(test_gnunet_vpn_6_over_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT test_gnunet_vpn_6_over-test_gnunet_vpn.o -MD -MP -MF $(DEPDIR)/test_gnunet_vpn_6_over-test_gnunet_vpn.Tpo -c -o test_gnunet_vpn_6_over-test_gnunet_vpn.o `test -f 'test_gnunet_vpn.c' || echo '$(srcdir)/'`test_gnunet_vpn.c +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/test_gnunet_vpn_6_over-test_gnunet_vpn.Tpo $(DEPDIR)/test_gnunet_vpn_6_over-test_gnunet_vpn.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='test_gnunet_vpn.c' object='test_gnunet_vpn_6_over-test_gnunet_vpn.o' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(test_gnunet_vpn_6_over_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o test_gnunet_vpn_6_over-test_gnunet_vpn.o `test -f 'test_gnunet_vpn.c' || echo '$(srcdir)/'`test_gnunet_vpn.c + +test_gnunet_vpn_6_over-test_gnunet_vpn.obj: test_gnunet_vpn.c +@am__fastdepCC_TRUE@ $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(test_gnunet_vpn_6_over_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT test_gnunet_vpn_6_over-test_gnunet_vpn.obj -MD -MP -MF $(DEPDIR)/test_gnunet_vpn_6_over-test_gnunet_vpn.Tpo -c -o test_gnunet_vpn_6_over-test_gnunet_vpn.obj `if test -f 'test_gnunet_vpn.c'; then $(CYGPATH_W) 'test_gnunet_vpn.c'; else $(CYGPATH_W) '$(srcdir)/test_gnunet_vpn.c'; fi` +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/test_gnunet_vpn_6_over-test_gnunet_vpn.Tpo $(DEPDIR)/test_gnunet_vpn_6_over-test_gnunet_vpn.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='test_gnunet_vpn.c' object='test_gnunet_vpn_6_over-test_gnunet_vpn.obj' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(test_gnunet_vpn_6_over_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o test_gnunet_vpn_6_over-test_gnunet_vpn.obj `if test -f 'test_gnunet_vpn.c'; then $(CYGPATH_W) 'test_gnunet_vpn.c'; else $(CYGPATH_W) '$(srcdir)/test_gnunet_vpn.c'; fi` + +test_gnunet_vpn_6_to_4-test_gnunet_vpn.o: test_gnunet_vpn.c +@am__fastdepCC_TRUE@ $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(test_gnunet_vpn_6_to_4_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT test_gnunet_vpn_6_to_4-test_gnunet_vpn.o -MD -MP -MF $(DEPDIR)/test_gnunet_vpn_6_to_4-test_gnunet_vpn.Tpo -c -o test_gnunet_vpn_6_to_4-test_gnunet_vpn.o `test -f 'test_gnunet_vpn.c' || echo '$(srcdir)/'`test_gnunet_vpn.c +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/test_gnunet_vpn_6_to_4-test_gnunet_vpn.Tpo $(DEPDIR)/test_gnunet_vpn_6_to_4-test_gnunet_vpn.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='test_gnunet_vpn.c' object='test_gnunet_vpn_6_to_4-test_gnunet_vpn.o' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LTCOMPILE) -c -o $@ $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(test_gnunet_vpn_6_to_4_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o test_gnunet_vpn_6_to_4-test_gnunet_vpn.o `test -f 'test_gnunet_vpn.c' || echo '$(srcdir)/'`test_gnunet_vpn.c + +test_gnunet_vpn_6_to_4-test_gnunet_vpn.obj: test_gnunet_vpn.c +@am__fastdepCC_TRUE@ $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(test_gnunet_vpn_6_to_4_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT test_gnunet_vpn_6_to_4-test_gnunet_vpn.obj -MD -MP -MF $(DEPDIR)/test_gnunet_vpn_6_to_4-test_gnunet_vpn.Tpo -c -o test_gnunet_vpn_6_to_4-test_gnunet_vpn.obj `if test -f 'test_gnunet_vpn.c'; then $(CYGPATH_W) 'test_gnunet_vpn.c'; else $(CYGPATH_W) '$(srcdir)/test_gnunet_vpn.c'; fi` +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/test_gnunet_vpn_6_to_4-test_gnunet_vpn.Tpo $(DEPDIR)/test_gnunet_vpn_6_to_4-test_gnunet_vpn.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='test_gnunet_vpn.c' object='test_gnunet_vpn_6_to_4-test_gnunet_vpn.obj' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(test_gnunet_vpn_6_to_4_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o test_gnunet_vpn_6_to_4-test_gnunet_vpn.obj `if test -f 'test_gnunet_vpn.c'; then $(CYGPATH_W) 'test_gnunet_vpn.c'; else $(CYGPATH_W) '$(srcdir)/test_gnunet_vpn.c'; fi` mostlyclean-libtool: -rm -f *.lo @@ -476,8 +734,11 @@ clean-libtool: -rm -rf .libs _libs install-dist_pkgcfgDATA: $(dist_pkgcfg_DATA) @$(NORMAL_INSTALL) - test -z "$(pkgcfgdir)" || $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" @list='$(dist_pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(pkgcfgdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" || exit 1; \ + fi; \ for p in $$list; do \ if test -f "$$p"; then d=; else d="$(srcdir)/"; fi; \ echo "$$d$$p"; \ @@ -491,9 +752,7 @@ uninstall-dist_pkgcfgDATA: @$(NORMAL_UNINSTALL) @list='$(dist_pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ files=`for p in $$list; do echo $$p; done | sed -e 's|^.*/||'`; \ - test -n "$$files" || exit 0; \ - echo " ( cd '$(DESTDIR)$(pkgcfgdir)' && rm -f" $$files ")"; \ - cd "$(DESTDIR)$(pkgcfgdir)" && rm -f $$files + dir='$(DESTDIR)$(pkgcfgdir)'; $(am__uninstall_files_from_dir) ID: $(HEADERS) $(SOURCES) $(LISP) $(TAGS_FILES) list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ @@ -547,6 +806,99 @@ GTAGS: distclean-tags: -rm -f TAGS ID GTAGS GRTAGS GSYMS GPATH tags +check-TESTS: $(TESTS) + @failed=0; all=0; xfail=0; xpass=0; skip=0; \ + srcdir=$(srcdir); export srcdir; \ + list=' $(TESTS) '; \ + $(am__tty_colors); \ + if test -n "$$list"; then \ + for tst in $$list; do \ + if test -f ./$$tst; then dir=./; \ + elif test -f $$tst; then dir=; \ + else dir="$(srcdir)/"; fi; \ + if $(TESTS_ENVIRONMENT) $${dir}$$tst; then \ + all=`expr $$all + 1`; \ + case " $(XFAIL_TESTS) " in \ + *[\ \ ]$$tst[\ \ ]*) \ + xpass=`expr $$xpass + 1`; \ + failed=`expr $$failed + 1`; \ + col=$$red; res=XPASS; \ + ;; \ + *) \ + col=$$grn; res=PASS; \ + ;; \ + esac; \ + elif test $$? -ne 77; then \ + all=`expr $$all + 1`; \ + case " $(XFAIL_TESTS) " in \ + *[\ \ ]$$tst[\ \ ]*) \ + xfail=`expr $$xfail + 1`; \ + col=$$lgn; res=XFAIL; \ + ;; \ + *) \ + failed=`expr $$failed + 1`; \ + col=$$red; res=FAIL; \ + ;; \ + esac; \ + else \ + skip=`expr $$skip + 1`; \ + col=$$blu; res=SKIP; \ + fi; \ + echo "$${col}$$res$${std}: $$tst"; \ + done; \ + if test "$$all" -eq 1; then \ + tests="test"; \ + All=""; \ + else \ + tests="tests"; \ + All="All "; \ + fi; \ + if test "$$failed" -eq 0; then \ + if test "$$xfail" -eq 0; then \ + banner="$$All$$all $$tests passed"; \ + else \ + if test "$$xfail" -eq 1; then failures=failure; else failures=failures; fi; \ + banner="$$All$$all $$tests behaved as expected ($$xfail expected $$failures)"; \ + fi; \ + else \ + if test "$$xpass" -eq 0; then \ + banner="$$failed of $$all $$tests failed"; \ + else \ + if test "$$xpass" -eq 1; then passes=pass; else passes=passes; fi; \ + banner="$$failed of $$all $$tests did not behave as expected ($$xpass unexpected $$passes)"; \ + fi; \ + fi; \ + dashes="$$banner"; \ + skipped=""; \ + if test "$$skip" -ne 0; then \ + if test "$$skip" -eq 1; then \ + skipped="($$skip test was not run)"; \ + else \ + skipped="($$skip tests were not run)"; \ + fi; \ + test `echo "$$skipped" | wc -c` -le `echo "$$banner" | wc -c` || \ + dashes="$$skipped"; \ + fi; \ + report=""; \ + if test "$$failed" -ne 0 && test -n "$(PACKAGE_BUGREPORT)"; then \ + report="Please report to $(PACKAGE_BUGREPORT)"; \ + test `echo "$$report" | wc -c` -le `echo "$$banner" | wc -c` || \ + dashes="$$report"; \ + fi; \ + dashes=`echo "$$dashes" | sed s/./=/g`; \ + if test "$$failed" -eq 0; then \ + col="$$grn"; \ + else \ + col="$$red"; \ + fi; \ + echo "$${col}$$dashes$${std}"; \ + echo "$${col}$$banner$${std}"; \ + test -z "$$skipped" || echo "$${col}$$skipped$${std}"; \ + test -z "$$report" || echo "$${col}$$report$${std}"; \ + echo "$${col}$$dashes$${std}"; \ + test "$$failed" -eq 0; \ + else :; fi + distdir: $(DISTFILES) @srcdirstrip=`echo "$(srcdir)" | sed 's/[].[^$$\\*]/\\\\&/g'`; \ topsrcdirstrip=`echo "$(top_srcdir)" | sed 's/[].[^$$\\*]/\\\\&/g'`; \ @@ -578,10 +930,12 @@ distdir: $(DISTFILES) fi; \ done check-am: all-am + $(MAKE) $(AM_MAKEFLAGS) $(check_PROGRAMS) + $(MAKE) $(AM_MAKEFLAGS) check-TESTS check: check-am all-am: Makefile $(PROGRAMS) $(DATA) installdirs: - for dir in "$(DESTDIR)$(bindir)" "$(DESTDIR)$(pkgcfgdir)"; do \ + for dir in "$(DESTDIR)$(libexecdir)" "$(DESTDIR)$(pkgcfgdir)"; do \ test -z "$$dir" || $(MKDIR_P) "$$dir"; \ done install: install-am @@ -594,10 +948,15 @@ install-am: all-am installcheck: installcheck-am install-strip: - $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ - install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ - `test -z '$(STRIP)' || \ - echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi mostlyclean-generic: clean-generic: @@ -611,7 +970,8 @@ maintainer-clean-generic: @echo "it deletes files that may require special tools to rebuild." clean: clean-am -clean-am: clean-binPROGRAMS clean-generic clean-libtool mostlyclean-am +clean-am: clean-checkPROGRAMS clean-generic clean-libexecPROGRAMS \ + clean-libtool mostlyclean-am distclean: distclean-am -rm -rf ./$(DEPDIR) @@ -637,7 +997,7 @@ install-dvi: install-dvi-am install-dvi-am: -install-exec-am: install-binPROGRAMS +install-exec-am: install-libexecPROGRAMS install-html: install-html-am @@ -677,24 +1037,25 @@ ps: ps-am ps-am: -uninstall-am: uninstall-binPROGRAMS uninstall-dist_pkgcfgDATA +uninstall-am: uninstall-dist_pkgcfgDATA uninstall-libexecPROGRAMS -.MAKE: install-am install-strip +.MAKE: check-am install-am install-strip -.PHONY: CTAGS GTAGS all all-am check check-am clean clean-binPROGRAMS \ - clean-generic clean-libtool ctags distclean distclean-compile \ +.PHONY: CTAGS GTAGS all all-am check check-TESTS check-am clean \ + clean-checkPROGRAMS clean-generic clean-libexecPROGRAMS \ + clean-libtool ctags distclean distclean-compile \ distclean-generic distclean-libtool distclean-tags distdir dvi \ dvi-am html html-am info info-am install install-am \ - install-binPROGRAMS install-data install-data-am \ - install-dist_pkgcfgDATA install-dvi install-dvi-am \ - install-exec install-exec-am install-html install-html-am \ - install-info install-info-am install-man install-pdf \ - install-pdf-am install-ps install-ps-am install-strip \ - installcheck installcheck-am installdirs maintainer-clean \ + install-data install-data-am install-dist_pkgcfgDATA \ + install-dvi install-dvi-am install-exec install-exec-am \ + install-html install-html-am install-info install-info-am \ + install-libexecPROGRAMS install-man install-pdf install-pdf-am \ + install-ps install-ps-am install-strip installcheck \ + installcheck-am installdirs maintainer-clean \ maintainer-clean-generic mostlyclean mostlyclean-compile \ mostlyclean-generic mostlyclean-libtool pdf pdf-am ps ps-am \ - tags uninstall uninstall-am uninstall-binPROGRAMS \ - uninstall-dist_pkgcfgDATA + tags uninstall uninstall-am uninstall-dist_pkgcfgDATA \ + uninstall-libexecPROGRAMS # Tell versions [3.59,3.63) of GNU make to not export all variables. diff --git a/src/pt/gnunet-daemon-pt.c b/src/pt/gnunet-daemon-pt.c index 2ad8468..8044f93 100644 --- a/src/pt/gnunet-daemon-pt.c +++ b/src/pt/gnunet-daemon-pt.c @@ -550,7 +550,7 @@ transmit_dns_request_to_mesh (void *cls, if (mlen > size) { mesh_th = GNUNET_MESH_notify_transmit_ready (mesh_tunnel, - GNUNET_NO, 0, + GNUNET_NO, TIMEOUT, NULL, mlen, &transmit_dns_request_to_mesh, @@ -569,7 +569,7 @@ transmit_dns_request_to_mesh (void *cls, rc = transmit_queue_head; if (NULL != rc) mesh_th = GNUNET_MESH_notify_transmit_ready (mesh_tunnel, - GNUNET_NO, 0, + GNUNET_NO, TIMEOUT, NULL, ntohs (rc->mesh_message->size), &transmit_dns_request_to_mesh, @@ -668,7 +668,7 @@ dns_pre_request_handler (void *cls, rc); if (NULL == mesh_th) mesh_th = GNUNET_MESH_notify_transmit_ready (mesh_tunnel, - GNUNET_NO, 0, + GNUNET_NO, TIMEOUT, NULL, mlen, &transmit_dns_request_to_mesh, @@ -932,7 +932,7 @@ run (void *cls, char *const *args GNUNET_UNUSED, GNUNET_SCHEDULER_shutdown (); return; } - mesh_handle = GNUNET_MESH_connect (cfg, 1, NULL, NULL, NULL, + mesh_handle = GNUNET_MESH_connect (cfg, NULL, NULL, NULL, mesh_handlers, mesh_types); if (NULL == mesh_handle) { @@ -966,12 +966,17 @@ main (int argc, char *const *argv) static const struct GNUNET_GETOPT_CommandLineOption options[] = { GNUNET_GETOPT_OPTION_END }; - - return (GNUNET_OK == - GNUNET_PROGRAM_run (argc, argv, "gnunet-daemon-pt", - gettext_noop - ("Daemon to run to perform IP protocol translation to GNUnet"), - options, &run, NULL)) ? 0 : 1; + int ret; + + if (GNUNET_OK != GNUNET_STRINGS_get_utf8_args (argc, argv, &argc, &argv)) + return 2; + ret = (GNUNET_OK == + GNUNET_PROGRAM_run (argc, argv, "gnunet-daemon-pt", + gettext_noop + ("Daemon to run to perform IP protocol translation to GNUnet"), + options, &run, NULL)) ? 0 : 1; + GNUNET_free ((void*) argv); + return ret; } diff --git a/src/pt/pt.conf b/src/pt/pt.conf index 39c1fb6..a1eea33 100644 --- a/src/pt/pt.conf +++ b/src/pt/pt.conf @@ -1,5 +1,4 @@ [pt] -CONFIG = $DEFAULTCONFIG BINARY = gnunet-daemon-pt # Set this to YES to tunnel IPv4 traffic over GNUnet diff --git a/src/pt/test_gns_vpn.c b/src/pt/test_gns_vpn.c new file mode 100644 index 0000000..6fe1e63 --- /dev/null +++ b/src/pt/test_gns_vpn.c @@ -0,0 +1,596 @@ +/* + This file is part of GNUnet + (C) 2007, 2009, 2011, 2012 Christian Grothoff + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 2, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @file test_gns_vpn.c + * @brief testcase for accessing VPN services via GNS + * @author Martin Schanzenbach + */ +#include "platform.h" +#include +#include +#include "gnunet_namestore_service.h" +#include "gnunet_gns_service.h" +#include "gnunet_testing_lib.h" + +#define PORT 8080 +#define TEST_DOMAIN "www.gads" + +#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 300) + +/** + * Return value for 'main'. + */ +static int global_ret; + +static struct GNUNET_NAMESTORE_Handle *namestore; + +static struct MHD_Daemon *mhd; + +static GNUNET_SCHEDULER_TaskIdentifier mhd_task_id; + +static GNUNET_SCHEDULER_TaskIdentifier curl_task_id; + +static CURL *curl; + +static CURLM *multi; + +static char *url; + +/** + * IP address of the ultimate destination. + */ +static const char *dest_ip; + +/** + * Address family of the dest_ip. + */ +static int dest_af; + +/** + * Address family to use by the curl client. + */ +static int src_af; + +static int use_v6; + + +struct CBC +{ + char buf[1024]; + size_t pos; +}; + +static struct CBC cbc; + + +static size_t +copy_buffer (void *ptr, size_t size, size_t nmemb, void *ctx) +{ + struct CBC *cbc = ctx; + + if (cbc->pos + size * nmemb > sizeof(cbc->buf)) + return 0; /* overflow */ + memcpy (&cbc->buf[cbc->pos], ptr, size * nmemb); + cbc->pos += size * nmemb; + return size * nmemb; +} + + +static int +mhd_ahc (void *cls, + struct MHD_Connection *connection, + const char *url, + const char *method, + const char *version, + const char *upload_data, size_t *upload_data_size, + void **unused) +{ + static int ptr; + struct MHD_Response *response; + int ret; + + if (0 != strcmp ("GET", method)) + return MHD_NO; /* unexpected method */ + if (&ptr != *unused) + { + *unused = &ptr; + return MHD_YES; + } + *unused = NULL; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "MHD sends respose for request to URL `%s'\n", url); + response = MHD_create_response_from_buffer (strlen (url), + (void *) url, + MHD_RESPMEM_MUST_COPY); + ret = MHD_queue_response (connection, MHD_HTTP_OK, response); + MHD_destroy_response (response); + if (ret == MHD_NO) + abort (); + return ret; +} + + +static void +do_shutdown () +{ + if (mhd_task_id != GNUNET_SCHEDULER_NO_TASK) + { + GNUNET_SCHEDULER_cancel (mhd_task_id); + mhd_task_id = GNUNET_SCHEDULER_NO_TASK; + } + if (curl_task_id != GNUNET_SCHEDULER_NO_TASK) + { + GNUNET_SCHEDULER_cancel (curl_task_id); + curl_task_id = GNUNET_SCHEDULER_NO_TASK; + } + if (NULL != mhd) + { + MHD_stop_daemon (mhd); + mhd = NULL; + } + GNUNET_free_non_null (url); + url = NULL; +} + + +/** + * Function to run the HTTP client. + */ +static void +curl_main (void); + + +static void +curl_task (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + curl_task_id = GNUNET_SCHEDULER_NO_TASK; + curl_main (); +} + + +static void +curl_main () +{ + fd_set rs; + fd_set ws; + fd_set es; + int max; + struct GNUNET_NETWORK_FDSet nrs; + struct GNUNET_NETWORK_FDSet nws; + struct GNUNET_TIME_Relative delay; + long timeout; + int running; + struct CURLMsg *msg; + + max = 0; + FD_ZERO (&rs); + FD_ZERO (&ws); + FD_ZERO (&es); + curl_multi_perform (multi, &running); + if (running == 0) + { + GNUNET_assert (NULL != (msg = curl_multi_info_read (multi, &running))); + if (msg->msg == CURLMSG_DONE) + { + if (msg->data.result != CURLE_OK) + { + fprintf (stderr, + "%s failed at %s:%d: `%s'\n", + "curl_multi_perform", + __FILE__, + __LINE__, curl_easy_strerror (msg->data.result)); + global_ret = 1; + } + } + curl_multi_remove_handle (multi, curl); + curl_multi_cleanup (multi); + curl_easy_cleanup (curl); + curl = NULL; + multi = NULL; + if (cbc.pos != strlen ("/hello_world")) + { + GNUNET_break (0); + global_ret = 2; + } + if (0 != strncmp ("/hello_world", cbc.buf, strlen ("/hello_world"))) + { + GNUNET_break (0); + global_ret = 3; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Download complete, shutting down!\n"); + do_shutdown (); + return; + } + GNUNET_assert (CURLM_OK == curl_multi_fdset (multi, &rs, &ws, &es, &max)); + if ( (CURLM_OK != curl_multi_timeout (multi, &timeout)) || + (-1 == timeout) ) + delay = GNUNET_TIME_UNIT_SECONDS; + else + delay = GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MILLISECONDS, (unsigned int) timeout); + GNUNET_NETWORK_fdset_copy_native (&nrs, + &rs, + max + 1); + GNUNET_NETWORK_fdset_copy_native (&nws, + &ws, + max + 1); + curl_task_id = GNUNET_SCHEDULER_add_select (GNUNET_SCHEDULER_PRIORITY_DEFAULT, + delay, + &nrs, + &nws, + &curl_task, + NULL); +} + + +static void +start_curl (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + GNUNET_asprintf (&url, + "http://%s/hello_world", + TEST_DOMAIN); + curl = curl_easy_init (); + curl_easy_setopt (curl, CURLOPT_URL, url); + curl_easy_setopt (curl, CURLOPT_WRITEFUNCTION, ©_buffer); + curl_easy_setopt (curl, CURLOPT_WRITEDATA, &cbc); + curl_easy_setopt (curl, CURLOPT_FAILONERROR, 1); + curl_easy_setopt (curl, CURLOPT_TIMEOUT, 150L); + curl_easy_setopt (curl, CURLOPT_CONNECTTIMEOUT, 15L); + curl_easy_setopt (curl, CURLOPT_NOSIGNAL, 1); + + multi = curl_multi_init (); + GNUNET_assert (multi != NULL); + GNUNET_assert (CURLM_OK == curl_multi_add_handle (multi, curl)); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Beginning HTTP download from `%s'\n", url); + curl_main (); +} + + +static void +disco_ns (void* cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + GNUNET_NAMESTORE_disconnect (namestore); + namestore = NULL; +} + + +/** + * Callback invoked from the namestore service once record is + * created. + * + * @param cls closure + * @param af address family, AF_INET or AF_INET6; AF_UNSPEC on error; + * will match 'result_af' from the request + * @param address IP address (struct in_addr or struct in_addr6, depending on 'af') + * that the VPN allocated for the redirection; + * traffic to this IP will now be redirected to the + * specified target peer; NULL on error + */ +static void +commence_testing (void *cls, int32_t success, const char *emsg) +{ + GNUNET_SCHEDULER_add_now (&disco_ns, NULL); + + if ((emsg != NULL) && (GNUNET_YES != success)) + { + fprintf (stderr, + "NS failed to create record %s\n", emsg); + GNUNET_SCHEDULER_shutdown (); + return; + } + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 10), &start_curl, NULL); +} + + +/** + * Function to keep the HTTP server running. + */ +static void +mhd_main (void); + + +static void +mhd_task (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + mhd_task_id = GNUNET_SCHEDULER_NO_TASK; + MHD_run (mhd); + mhd_main (); +} + + +static void +mhd_main () +{ + struct GNUNET_NETWORK_FDSet nrs; + struct GNUNET_NETWORK_FDSet nws; + fd_set rs; + fd_set ws; + fd_set es; + int max_fd; + unsigned MHD_LONG_LONG timeout; + struct GNUNET_TIME_Relative delay; + + GNUNET_assert (GNUNET_SCHEDULER_NO_TASK == mhd_task_id); + FD_ZERO (&rs); + FD_ZERO (&ws); + FD_ZERO (&es); + max_fd = -1; + GNUNET_assert (MHD_YES == + MHD_get_fdset (mhd, &rs, &ws, &es, &max_fd)); + if (MHD_YES == MHD_get_timeout (mhd, &timeout)) + delay = GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MILLISECONDS, + (unsigned int) timeout); + else + delay = GNUNET_TIME_UNIT_FOREVER_REL; + GNUNET_NETWORK_fdset_copy_native (&nrs, + &rs, + max_fd + 1); + GNUNET_NETWORK_fdset_copy_native (&nws, + &ws, + max_fd + 1); + mhd_task_id = GNUNET_SCHEDULER_add_select (GNUNET_SCHEDULER_PRIORITY_DEFAULT, + delay, + &nrs, + &nws, + &mhd_task, + NULL); +} + + +static void +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) +{ + enum MHD_FLAG flags; + struct GNUNET_PeerIdentity id; + struct GNUNET_CRYPTO_HashAsciiEncoded peername; + struct GNUNET_CRYPTO_RsaPrivateKey *host_key; + struct GNUNET_NAMESTORE_RecordData rd; + char *rd_string; + char *zone_keyfile; + + GNUNET_TESTING_peer_get_identity (peer, &id); + GNUNET_CRYPTO_hash_to_enc ((struct GNUNET_HashCode*)&id, &peername); + + namestore = GNUNET_NAMESTORE_connect (cfg); + GNUNET_assert (NULL != namestore); + flags = MHD_USE_DEBUG; + //if (GNUNET_YES == use_v6) + // flags |= MHD_USE_IPv6; + mhd = MHD_start_daemon (flags, + PORT, + NULL, NULL, + &mhd_ahc, NULL, + MHD_OPTION_END); + GNUNET_assert (NULL != mhd); + mhd_main (); + + if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_filename (cfg, "gns", + "ZONEKEY", + &zone_keyfile)) + { + GNUNET_log(GNUNET_ERROR_TYPE_ERROR, "Failed to get key from cfg\n"); + return; + } + + host_key = GNUNET_CRYPTO_rsa_key_create_from_file (zone_keyfile); + rd.expiration_time = GNUNET_TIME_UNIT_FOREVER_ABS.abs_value; + GNUNET_asprintf (&rd_string, "6 %s %s", (char*)&peername, "www.gads."); + GNUNET_assert (GNUNET_OK == GNUNET_NAMESTORE_string_to_value (GNUNET_GNS_RECORD_VPN, + rd_string, + (void**)&rd.data, + &rd.data_size)); + rd.record_type = GNUNET_GNS_RECORD_VPN; + + GNUNET_NAMESTORE_record_create (namestore, + host_key, + "www", + &rd, + &commence_testing, + NULL); + GNUNET_free ((void**)rd.data); + GNUNET_free (rd_string); + GNUNET_free (zone_keyfile); + GNUNET_CRYPTO_rsa_key_free (host_key); +} + + +/** + * Open '/dev/null' and make the result the given + * file descriptor. + * + * @param target_fd desired FD to point to /dev/null + * @param flags open flags (O_RDONLY, O_WRONLY) + */ +static void +open_dev_null (int target_fd, + int flags) +{ + int fd; + + fd = open ("/dev/null", flags); + if (-1 == fd) + abort (); + if (fd == target_fd) + return; + if (-1 == dup2 (fd, target_fd)) + { + (void) close (fd); + abort (); + } + (void) close (fd); +} + + +/** + * Run the given command and wait for it to complete. + * + * @param file name of the binary to run + * @param cmd command line arguments (as given to 'execv') + * @return 0 on success, 1 on any error + */ +static int +fork_and_exec (const char *file, + char *const cmd[]) +{ + int status; + pid_t pid; + pid_t ret; + + pid = fork (); + if (-1 == pid) + { + fprintf (stderr, + "fork failed: %s\n", + strerror (errno)); + return 1; + } + if (0 == pid) + { + /* we are the child process */ + /* close stdin/stdout to not cause interference + with the helper's main protocol! */ + (void) close (0); + open_dev_null (0, O_RDONLY); + (void) close (1); + open_dev_null (1, O_WRONLY); + (void) execv (file, cmd); + /* can only get here on error */ + fprintf (stderr, + "exec `%s' failed: %s\n", + file, + strerror (errno)); + _exit (1); + } + /* keep running waitpid as long as the only error we get is 'EINTR' */ + while ( (-1 == (ret = waitpid (pid, &status, 0))) && + (errno == EINTR) ); + if (-1 == ret) + { + fprintf (stderr, + "waitpid failed: %s\n", + strerror (errno)); + return 1; + } + if (! (WIFEXITED (status) && (0 == WEXITSTATUS (status)))) + return 1; + /* child process completed and returned success, we're happy */ + return 0; +} + +int +main (int argc, char *const *argv) +{ + char *sbin_iptables; + char *bin_vpn; + char *bin_exit; + char *bin_dns; + char *const iptables_args[] = + { + "iptables", "-t", "mangle", "-L", "-v", NULL + }; + + if (0 == access ("/sbin/iptables", X_OK)) + sbin_iptables = "/sbin/iptables"; + else if (0 == access ("/usr/sbin/iptables", X_OK)) + sbin_iptables = "/usr/sbin/iptables"; + else + { + fprintf (stderr, + "Executable iptables not found in approved directories: %s, skipping\n", + strerror (errno)); + return 0; + } + + if (0 != fork_and_exec (sbin_iptables, iptables_args)) + { + fprintf (stderr, + "Failed to run `iptables -t mangle -L -v'. Skipping test.\n"); + return 0; + } + + if (0 != ACCESS ("/dev/net/tun", R_OK)) + { + GNUNET_log_strerror_file (GNUNET_ERROR_TYPE_ERROR, + "access", + "/dev/net/tun"); + fprintf (stderr, + "WARNING: System unable to run test, skipping.\n"); + return 0; + } + + bin_vpn = GNUNET_OS_get_libexec_binary_path ("gnunet-helper-vpn"); + bin_exit = GNUNET_OS_get_libexec_binary_path ("gnunet-helper-exit"); + bin_dns = GNUNET_OS_get_libexec_binary_path ("gnunet-helper-dns"); + if ( (0 != geteuid ()) && + ( (GNUNET_YES != + GNUNET_OS_check_helper_binary (bin_vpn)) || + (GNUNET_YES != + GNUNET_OS_check_helper_binary (bin_exit)) || + (GNUNET_YES != + GNUNET_OS_check_helper_binary (bin_dns))) ) + { + fprintf (stderr, + "WARNING: gnunet-helper-{exit,vpn,dns} binaries in $PATH are not SUID, refusing to run test (as it would have to fail).\n"); + fprintf (stderr, + "Change $PATH ('.' in $PATH before $GNUNET_PREFIX/bin is problematic) or permissions (run 'make install' as root) to fix this!\n"); + GNUNET_free (bin_vpn); + GNUNET_free (bin_exit); + GNUNET_free (bin_dns); + return 0; + } + GNUNET_free (bin_vpn); + GNUNET_free (bin_exit); + GNUNET_free (bin_dns); + GNUNET_CRYPTO_rsa_setup_hostkey ("test_gns_vpn.conf"); + + dest_ip = "169.254.86.1"; + dest_af = AF_INET; + src_af = AF_INET; + + if (GNUNET_OK == GNUNET_NETWORK_test_pf (PF_INET6)) + use_v6 = GNUNET_YES; + else + use_v6 = GNUNET_NO; + + if ( (GNUNET_OK != GNUNET_NETWORK_test_pf (src_af)) || + (GNUNET_OK != GNUNET_NETWORK_test_pf (dest_af)) ) + { + fprintf (stderr, + "Required address families not supported by this system, skipping test.\n"); + return 0; + } + if (0 != curl_global_init (CURL_GLOBAL_WIN32)) + { + fprintf (stderr, "failed to initialize curl\n"); + return 2; + } + if (0 != GNUNET_TESTING_peer_run ("test-gnunet-vpn", + "test_gns_vpn.conf", + &run, NULL)) + return 1; + GNUNET_DISK_directory_remove ("/tmp/gnunet-test-vpn"); + return global_ret; +} + +/* end of test_gns_vpn.c */ + diff --git a/src/pt/test_gns_vpn.conf b/src/pt/test_gns_vpn.conf new file mode 100644 index 0000000..269def8 --- /dev/null +++ b/src/pt/test_gns_vpn.conf @@ -0,0 +1,58 @@ +[PATHS] +SERVICEHOME = /tmp/gnunet-test-gns-vpn/ + +[transport] +PLUGINS = tcp + +[arm] +DEFAULTSERVICES = statistics exit mesh vpn namestore gns +PORT = 0 +ALLOW_SHUTDOWN = YES + +[exit] +EXIT_IPV4 = YES +EXIT_IPV6 = YES + +# FIXME: can we use 'lo'? +EXIT_IFNAME = eth1 + +[dns] +DNS_EXIT = 8.8.8.8 + +[testing] +WEAKRANDOM = YES +HOSTKEYSFILE = ../../contrib/testing_hostkeys.dat + +[nse] +WORKBITS = 1 + +# repeating some values from the default configurations +# here as the respective network addresses are also +# hard-wired in the tests and the MUST match (!) +[vpn] +IPV6ADDR = FC2D:FDAA:6A26::1 +IPV6PREFIX = 64 +IPV4ADDR = 169.254.20.1 +IPV4MASK = 255.255.255.0 + +[exit] +IPV6ADDR = FC5A:04E1:C2BA::1 +IPV6PREFIX = 96 +IPV4ADDR = 169.254.86.1 +IPV4MASK = 255.255.255.0 + +[www.gads.] +TCP_REDIRECTS = 80:localhost4:8080 +TTL = 3600000 + +[gns] +AUTOSTART = YES +ZONEKEY = $SERVICEHOME/.hostkey +HIJACK_DNS = YES + +[namestore] +AUTOSTART = YES + +[nat] +USE_LOCALADDR = YES +RETURN_LOCAL_ADDRESSES = YES diff --git a/src/pt/test_gnunet_vpn.c b/src/pt/test_gnunet_vpn.c new file mode 100644 index 0000000..d938f79 --- /dev/null +++ b/src/pt/test_gnunet_vpn.c @@ -0,0 +1,481 @@ +/* + This file is part of GNUnet + (C) 2007, 2009, 2011, 2012 Christian Grothoff + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 2, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @file test_gnunet_vpn.c + * @brief testcase for tunneling HTTP over the GNUnet VPN + * @author Christian Grothoff + */ +#include "platform.h" +#include +#include +#include "gnunet_vpn_service.h" +#include "gnunet_testing_lib.h" + +#define PORT 48080 + +#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 300) + + +/** + * Return value for 'main'. + */ +static int global_ret; + +static struct GNUNET_VPN_Handle *vpn; + +static struct MHD_Daemon *mhd; + +static GNUNET_SCHEDULER_TaskIdentifier mhd_task_id; + +static GNUNET_SCHEDULER_TaskIdentifier curl_task_id; + +static GNUNET_SCHEDULER_TaskIdentifier ctrl_c_task_id; + +static struct GNUNET_VPN_RedirectionRequest *rr; + +static CURL *curl; + +static CURLM *multi; + +static char *url; + +/** + * IP address of the ultimate destination. + */ +static const char *dest_ip; + +/** + * Address family of the dest_ip. + */ +static int dest_af; + +/** + * Address family to use by the curl client. + */ +static int src_af; + + +struct CBC +{ + char buf[1024]; + size_t pos; +}; + +static struct CBC cbc; + + +static size_t +copy_buffer (void *ptr, size_t size, size_t nmemb, void *ctx) +{ + struct CBC *cbc = ctx; + + if (cbc->pos + size * nmemb > sizeof (cbc->buf)) + return 0; /* overflow */ + memcpy (&cbc->buf[cbc->pos], ptr, size * nmemb); + cbc->pos += size * nmemb; + return size * nmemb; +} + + +static int +mhd_ahc (void *cls, struct MHD_Connection *connection, const char *url, + const char *method, const char *version, const char *upload_data, + size_t * upload_data_size, void **unused) +{ + static int ptr; + struct MHD_Response *response; + int ret; + + if (0 != strcmp ("GET", method)) + return MHD_NO; /* unexpected method */ + if (&ptr != *unused) + { + *unused = &ptr; + return MHD_YES; + } + *unused = NULL; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "MHD sends respose for request to URL `%s'\n", url); + response = + MHD_create_response_from_buffer (strlen (url), (void *) url, + MHD_RESPMEM_MUST_COPY); + ret = MHD_queue_response (connection, MHD_HTTP_OK, response); + MHD_destroy_response (response); + if (ret == MHD_NO) + abort (); + return ret; +} + + +static void +do_shutdown () +{ + if (mhd_task_id != GNUNET_SCHEDULER_NO_TASK) + { + GNUNET_SCHEDULER_cancel (mhd_task_id); + mhd_task_id = GNUNET_SCHEDULER_NO_TASK; + } + if (curl_task_id != GNUNET_SCHEDULER_NO_TASK) + { + GNUNET_SCHEDULER_cancel (curl_task_id); + curl_task_id = GNUNET_SCHEDULER_NO_TASK; + } + if (ctrl_c_task_id != GNUNET_SCHEDULER_NO_TASK) + { + GNUNET_SCHEDULER_cancel (ctrl_c_task_id); + ctrl_c_task_id = GNUNET_SCHEDULER_NO_TASK; + } + if (NULL != mhd) + { + MHD_stop_daemon (mhd); + mhd = NULL; + } + if (NULL != rr) + { + GNUNET_VPN_cancel_request (rr); + rr = NULL; + } + if (NULL != vpn) + { + GNUNET_VPN_disconnect (vpn); + vpn = NULL; + } + GNUNET_free_non_null (url); + url = NULL; +} + + +/** + * Function to run the HTTP client. + */ +static void +curl_main (void); + + +static void +curl_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + curl_task_id = GNUNET_SCHEDULER_NO_TASK; + curl_main (); +} + + +static void +curl_main () +{ + fd_set rs; + fd_set ws; + fd_set es; + int max; + struct GNUNET_NETWORK_FDSet nrs; + struct GNUNET_NETWORK_FDSet nws; + struct GNUNET_TIME_Relative delay; + long timeout; + int running; + struct CURLMsg *msg; + + max = 0; + FD_ZERO (&rs); + FD_ZERO (&ws); + FD_ZERO (&es); + curl_multi_perform (multi, &running); + if (running == 0) + { + GNUNET_assert (NULL != (msg = curl_multi_info_read (multi, &running))); + if (msg->msg == CURLMSG_DONE) + { + if (msg->data.result != CURLE_OK) + { + fprintf (stderr, "%s failed at %s:%d: `%s'\n", "curl_multi_perform", + __FILE__, __LINE__, curl_easy_strerror (msg->data.result)); + global_ret = 1; + } + } + curl_multi_remove_handle (multi, curl); + curl_multi_cleanup (multi); + curl_easy_cleanup (curl); + curl = NULL; + multi = NULL; + if (cbc.pos != strlen ("/hello_world")) + { + GNUNET_break (0); + global_ret = 2; + } + if (0 != strncmp ("/hello_world", cbc.buf, strlen ("/hello_world"))) + { + GNUNET_break (0); + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + "You might want to check if your host-based firewall is blocking the connections.\n"); + global_ret = 3; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Download complete, shutting down!\n"); + do_shutdown (); + return; + } + GNUNET_assert (CURLM_OK == curl_multi_fdset (multi, &rs, &ws, &es, &max)); + if ((CURLM_OK != curl_multi_timeout (multi, &timeout)) || (-1 == timeout)) + delay = GNUNET_TIME_UNIT_SECONDS; + else + delay = + GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MILLISECONDS, + (unsigned int) timeout); + GNUNET_NETWORK_fdset_copy_native (&nrs, &rs, max + 1); + GNUNET_NETWORK_fdset_copy_native (&nws, &ws, max + 1); + curl_task_id = + GNUNET_SCHEDULER_add_select (GNUNET_SCHEDULER_PRIORITY_DEFAULT, delay, + &nrs, &nws, &curl_task, NULL); +} + + +/** + * Callback invoked from the VPN service once a redirection is + * available. Provides the IP address that can now be used to + * reach the requested destination (in our case, the MHD server) + * + * @param cls closure + * @param af address family, AF_INET or AF_INET6; AF_UNSPEC on error; + * will match 'result_af' from the request + * @param address IP address (struct in_addr or struct in_addr6, depending on 'af') + * that the VPN allocated for the redirection; + * traffic to this IP will now be redirected to the + * specified target peer; NULL on error + */ +static void +allocation_cb (void *cls, int af, const void *address) +{ + char ips[INET6_ADDRSTRLEN]; + + rr = NULL; + if (src_af != af) + { + fprintf (stderr, "VPN failed to allocate appropriate address\n"); + GNUNET_SCHEDULER_shutdown (); + return; + } + GNUNET_asprintf (&url, "http://%s:%u/hello_world", + inet_ntop (af, address, ips, sizeof (ips)), + (unsigned int) PORT); + curl = curl_easy_init (); + curl_easy_setopt (curl, CURLOPT_URL, url); + curl_easy_setopt (curl, CURLOPT_WRITEFUNCTION, ©_buffer); + curl_easy_setopt (curl, CURLOPT_WRITEDATA, &cbc); + curl_easy_setopt (curl, CURLOPT_FAILONERROR, 1); + curl_easy_setopt (curl, CURLOPT_TIMEOUT, 150L); + curl_easy_setopt (curl, CURLOPT_CONNECTTIMEOUT, 15L); + curl_easy_setopt (curl, CURLOPT_NOSIGNAL, 1); + + multi = curl_multi_init (); + GNUNET_assert (multi != NULL); + GNUNET_assert (CURLM_OK == curl_multi_add_handle (multi, curl)); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Beginning HTTP download from `%s'\n", + url); + curl_main (); +} + + +/** + * Function to keep the HTTP server running. + */ +static void +mhd_main (void); + + +static void +mhd_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + mhd_task_id = GNUNET_SCHEDULER_NO_TASK; + MHD_run (mhd); + mhd_main (); +} + + +static void +ctrl_c_shutdown (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + ctrl_c_task_id = GNUNET_SCHEDULER_NO_TASK; + do_shutdown (); + GNUNET_break (0); + global_ret = 1; +} + + +static void +mhd_main () +{ + struct GNUNET_NETWORK_FDSet nrs; + struct GNUNET_NETWORK_FDSet nws; + fd_set rs; + fd_set ws; + fd_set es; + int max_fd; + unsigned MHD_LONG_LONG timeout; + struct GNUNET_TIME_Relative delay; + + GNUNET_assert (GNUNET_SCHEDULER_NO_TASK == mhd_task_id); + FD_ZERO (&rs); + FD_ZERO (&ws); + FD_ZERO (&es); + max_fd = -1; + GNUNET_assert (MHD_YES == MHD_get_fdset (mhd, &rs, &ws, &es, &max_fd)); + if (MHD_YES == MHD_get_timeout (mhd, &timeout)) + delay = + GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MILLISECONDS, + (unsigned int) timeout); + else + delay = GNUNET_TIME_UNIT_FOREVER_REL; + GNUNET_NETWORK_fdset_copy_native (&nrs, &rs, max_fd + 1); + GNUNET_NETWORK_fdset_copy_native (&nws, &ws, max_fd + 1); + mhd_task_id = + GNUNET_SCHEDULER_add_select (GNUNET_SCHEDULER_PRIORITY_DEFAULT, delay, + &nrs, &nws, &mhd_task, NULL); +} + + +static void +run (void *cls, const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) +{ + struct in_addr v4; + struct in6_addr v6; + void *addr; + enum MHD_FLAG flags; + + vpn = GNUNET_VPN_connect (cfg); + GNUNET_assert (NULL != vpn); + flags = MHD_USE_DEBUG; + if (AF_INET6 == dest_af) + flags |= MHD_USE_IPv6; + mhd = + MHD_start_daemon (flags, PORT, NULL, NULL, &mhd_ahc, NULL, + MHD_OPTION_END); + GNUNET_assert (NULL != mhd); + mhd_main (); + addr = NULL; + switch (dest_af) + { + case AF_INET: + GNUNET_assert (1 == inet_pton (dest_af, dest_ip, &v4)); + addr = &v4; + break; + case AF_INET6: + GNUNET_assert (1 == inet_pton (dest_af, dest_ip, &v6)); + addr = &v6; + break; + default: + GNUNET_assert (0); + } + rr = GNUNET_VPN_redirect_to_ip (vpn, src_af, dest_af, addr, GNUNET_YES, + GNUNET_TIME_UNIT_FOREVER_ABS, &allocation_cb, + NULL); + ctrl_c_task_id = + GNUNET_SCHEDULER_add_delayed (TIMEOUT, &ctrl_c_shutdown, NULL); +} + + +int +main (int argc, char *const *argv) +{ + const char *type; + const char *bin; + char *vpn_binary; + char *exit_binary; + + if (0 != ACCESS ("/dev/net/tun", R_OK)) + { + GNUNET_log_strerror_file (GNUNET_ERROR_TYPE_ERROR, "access", + "/dev/net/tun"); + fprintf (stderr, "WARNING: System unable to run test, skipping.\n"); + return 0; + } + vpn_binary = GNUNET_OS_get_libexec_binary_path ("gnunet-helper-vpn"); + exit_binary = GNUNET_OS_get_libexec_binary_path ("gnunet-helper-exit"); + if ((GNUNET_YES != GNUNET_OS_check_helper_binary (vpn_binary)) || + (GNUNET_YES != GNUNET_OS_check_helper_binary (exit_binary))) + { + GNUNET_free (vpn_binary); + GNUNET_free (exit_binary); + fprintf (stderr, + "WARNING: gnunet-helper-{exit,vpn} binaries are not SUID, refusing to run test (as it would have to fail).\n"); + return 0; + } + GNUNET_free (vpn_binary); + GNUNET_free (exit_binary); + GNUNET_CRYPTO_rsa_setup_hostkey ("test_gnunet_vpn.conf"); + bin = argv[0]; + if (NULL != strstr (bin, "lt-")) + bin = strstr (bin, "lt-") + 4; + type = strstr (bin, "-"); + if (NULL == type) + { + fprintf (stderr, "invalid binary name\n"); + return 1; + } + type++; + if (0 == strcmp (type, "4_to_6")) + { + dest_ip = "FC5A:04E1:C2BA::1"; + dest_af = AF_INET6; + src_af = AF_INET; + } + else if (0 == strcmp (type, "6_to_4")) + { + dest_ip = "169.254.86.1"; + dest_af = AF_INET; + src_af = AF_INET6; + } + else if (0 == strcmp (type, "4_over")) + { + dest_ip = "169.254.86.1"; + dest_af = AF_INET; + src_af = AF_INET; + } + else if (0 == strcmp (type, "6_over")) + { + dest_ip = "FC5A:04E1:C2BA::1"; + dest_af = AF_INET6; + src_af = AF_INET6; + } + else + { + fprintf (stderr, "invalid binary suffix `%s'\n", type); + return 1; + } + if ((GNUNET_OK != GNUNET_NETWORK_test_pf (src_af)) || + (GNUNET_OK != GNUNET_NETWORK_test_pf (dest_af))) + { + fprintf (stderr, + "Required address families not supported by this system, skipping test.\n"); + return 0; + } + if (0 != curl_global_init (CURL_GLOBAL_WIN32)) + { + fprintf (stderr, "failed to initialize curl\n"); + return 2; + } + if (0 != + GNUNET_TESTING_peer_run ("test-gnunet-vpn", "test_gnunet_vpn.conf", &run, + NULL)) + return 1; + GNUNET_DISK_directory_remove ("/tmp/gnunet-test-vpn"); + return global_ret; +} + +/* end of test_gnunet_vpn.c */ diff --git a/src/pt/test_gnunet_vpn.conf b/src/pt/test_gnunet_vpn.conf new file mode 100644 index 0000000..c0cdd5b --- /dev/null +++ b/src/pt/test_gnunet_vpn.conf @@ -0,0 +1,49 @@ +[PATHS] +SERVICEHOME = /tmp/gnunet-test-vpn/ + +[transport] +PLUGINS = tcp + +[arm] +DEFAULTSERVICES = statistics exit vpn +PORT = 0 +ALLOW_SHUTDOWN = YES + +[exit] +EXIT_IPV4 = YES +EXIT_IPV6 = YES + +# FIXME: can we use 'lo'? +EXIT_IFNAME = eth1 + +[testing] +WEAKRANDOM = YES +HOSTKEYSFILE = ../../contrib/testing_hostkeys.dat + +[nse] +WORKBITS = 1 + +# repeating some values from the default configurations +# here as the respective network addresses are also +# hard-wired in the tests and the MUST match (!) +[vpn] +IPV6ADDR = FC2D:FDAA:6A26::1 +IPV6PREFIX = 64 +IPV4ADDR = 169.254.20.1 +IPV4MASK = 255.255.255.0 + +[exit] +IPV6ADDR = FC5A:04E1:C2BA::1 +IPV6PREFIX = 96 +IPV4ADDR = 169.254.86.1 +IPV4MASK = 255.255.255.0 + +[gns] +AUTOSTART = NO + +[nat] +USE_LOCALADDR = YES +RETURN_LOCAL_ADDRESSES = YES + +[consensus] +AUTOSTART = NO diff --git a/src/regex/Makefile.am b/src/regex/Makefile.am index 8c73c60..1203897 100644 --- a/src/regex/Makefile.am +++ b/src/regex/Makefile.am @@ -8,35 +8,158 @@ if USE_COVERAGE AM_CFLAGS = --coverage endif -lib_LTLIBRARIES = libgnunetregex.la +lib_LTLIBRARIES = libgnunetregexblock.la \ + libgnunetregex.la + + +libgnunetregexblock_la_SOURCES = \ + regex_block_lib.c regex_block_lib.h +libgnunetregexblock_la_LIBADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(XLIB) \ + $(LTLIBINTL) +libgnunetregexblock_la_LDFLAGS = \ + $(GN_LIB_LDFLAGS) $(WINFLAGS) \ + -version-info 1:0:0 libgnunetregex_la_SOURCES = \ - regex.c + regex_internal.h regex.c \ + regex_graph.c regex_random.c \ + regex_dht.c libgnunetregex_la_LIBADD = -lm \ - $(top_builddir)/src/util/libgnunetutil.la + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/dht/libgnunetdht.la \ + $(top_builddir)/src/statistics/libgnunetstatistics.la \ + $(top_builddir)/src/regex/libgnunetregexblock.la +libgnunetregex_la_DEPENDENCIES = \ + libgnunetregexblock.la libgnunetregex_la_LDFLAGS = \ - $(GN_LIB_LDFLAGS) \ - -version-info 0:0:0 + $(GN_LIB_LDFLAGS) \ + -version-info 2:0:1 + + +plugindir = $(libdir)/gnunet + +plugin_LTLIBRARIES = \ + libgnunet_plugin_block_regex.la + +libgnunet_plugin_block_regex_la_SOURCES = \ + plugin_block_regex.c +libgnunet_plugin_block_regex_la_LIBADD = \ + $(top_builddir)/src/regex/libgnunetregexblock.la \ + $(top_builddir)/src/block/libgnunetblock.la \ + $(top_builddir)/src/util/libgnunetutil.la +libgnunet_plugin_block_regex_la_LDFLAGS = \ + $(GN_PLUGIN_LDFLAGS) +libgnunet_plugin_block_regex_la_DEPENDENCIES = \ + libgnunetregexblock.la + +if HAVE_MYSQL +noinst_mysql_progs = \ +gnunet-regex-simulation-profiler + +gnunet_regex_simulation_profiler_SOURCES = \ + gnunet-regex-simulation-profiler.c +gnunet_regex_simulation_profiler_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/regex/libgnunetregex.la \ + $(top_builddir)/src/mysql/libgnunetmysql.la +gnunet_regex_simulation_profiler_DEPENDENCIES = \ + libgnunetregex.la +endif + +noinst_LTLIBRARIES = libgnunetregextest.la + +libgnunetregextest_la_SOURCES = \ + regex_test_lib.c regex_test_lib.h +libgnunetregextest_la_LIBADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/regex/libgnunetregex.la +libgnunetregextest_la_DEPENDENCIES = \ + libgnunetregex.la + + +noinst_PROGRAMS = $(noinst_mysql_progs) \ + perf-regex \ + gnunet-regex-profiler \ + gnunet-daemon-regexprofiler + +perf_regex_SOURCES = \ + perf-regex.c +perf_regex_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/regex/libgnunetregex.la \ + $(top_builddir)/src/regex/libgnunetregextest.la +perf_regex_DEPENDENCIES = \ + libgnunetregex.la \ + libgnunetregextest.la + +gnunet_regex_profiler_SOURCES = \ + gnunet-regex-profiler.c +gnunet_regex_profiler_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/dht/libgnunetdht.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la \ + $(top_builddir)/src/regex/libgnunetregex.la \ + $(top_builddir)/src/statistics/libgnunetstatistics.la +gnunet_regex_profiler_DEPENDENCIES = \ + $(top_builddir)/src/dht/libgnunetdht.la \ + libgnunetregex.la + +gnunet_daemon_regexprofiler_SOURCES = \ + gnunet-daemon-regexprofiler.c +gnunet_daemon_regexprofiler_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/dht/libgnunetdht.la \ + $(top_builddir)/src/regex/libgnunetregex.la \ + $(top_builddir)/src/statistics/libgnunetstatistics.la +gnunet_daemon_regexprofiler_DEPENDENCIES = \ + $(top_builddir)/src/dht/libgnunetdht.la \ + libgnunetregex.la + + check_PROGRAMS = \ - test_regex_eval_api \ - test_regex_iterate_api + test_regex_eval_api \ + test_regex_iterate_api \ + test_regex_proofs \ + test_regex_graph_api \ + test_regex_iptoregex if ENABLE_TEST_RUN -TESTS = $(check_PROGRAMS) + TESTS = $(check_PROGRAMS) endif test_regex_eval_api_SOURCES = \ - test_regex_eval_api.c + test_regex_eval_api.c test_regex_eval_api_LDADD = \ - $(top_builddir)/src/regex/libgnunetregex.la \ - $(top_builddir)/src/util/libgnunetutil.la + $(top_builddir)/src/regex/libgnunetregex.la \ + $(top_builddir)/src/util/libgnunetutil.la test_regex_iterate_api_SOURCES = \ - test_regex_iterate_api.c + test_regex_iterate_api.c test_regex_iterate_api_LDADD = \ - $(top_builddir)/src/regex/libgnunetregex.la \ - $(top_builddir)/src/util/libgnunetutil.la + $(top_builddir)/src/regex/libgnunetregex.la \ + $(top_builddir)/src/util/libgnunetutil.la + +test_regex_proofs_SOURCES = \ + test_regex_proofs.c +test_regex_proofs_LDADD = \ + $(top_builddir)/src/regex/libgnunetregex.la \ + $(top_builddir)/src/util/libgnunetutil.la + +test_regex_graph_api_SOURCES = \ + test_regex_graph_api.c +test_regex_graph_api_LDADD = \ + $(top_builddir)/src/regex/libgnunetregex.la \ + $(top_builddir)/src/util/libgnunetutil.la + +test_regex_iptoregex_SOURCES = \ + test_regex_iptoregex.c +test_regex_iptoregex_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/regex/libgnunetregex.la + -EXTRA_DIST = -# test_regex_data.conf +EXTRA_DIST = \ + regex_simulation_profiler_test.conf diff --git a/src/regex/Makefile.in b/src/regex/Makefile.in index c0c0704..fffad51 100644 --- a/src/regex/Makefile.in +++ b/src/regex/Makefile.in @@ -1,9 +1,9 @@ -# Makefile.in generated by automake 1.11.1 from Makefile.am. +# Makefile.in generated by automake 1.11.6 from Makefile.am. # @configure_input@ # Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, -# 2003, 2004, 2005, 2006, 2007, 2008, 2009 Free Software Foundation, -# Inc. +# 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Free Software +# Foundation, Inc. # This Makefile.in is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. @@ -15,7 +15,25 @@ @SET_MAKE@ + VPATH = @srcdir@ +am__make_dryrun = \ + { \ + am__dry=no; \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + echo 'am--echo: ; @echo "AM" OK' | $(MAKE) -f - 2>/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } pkgdatadir = $(datadir)/@PACKAGE@ pkgincludedir = $(includedir)/@PACKAGE@ pkglibdir = $(libdir)/@PACKAGE@ @@ -35,21 +53,26 @@ POST_UNINSTALL = : build_triplet = @build@ host_triplet = @host@ target_triplet = @target@ +noinst_PROGRAMS = $(am__EXEEXT_1) perf-regex$(EXEEXT) \ + gnunet-regex-profiler$(EXEEXT) \ + gnunet-daemon-regexprofiler$(EXEEXT) check_PROGRAMS = test_regex_eval_api$(EXEEXT) \ - test_regex_iterate_api$(EXEEXT) + test_regex_iterate_api$(EXEEXT) test_regex_proofs$(EXEEXT) \ + test_regex_graph_api$(EXEEXT) test_regex_iptoregex$(EXEEXT) subdir = src/regex DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 am__aclocal_m4_deps = $(top_srcdir)/m4/absolute-header.m4 \ $(top_srcdir)/m4/align.m4 $(top_srcdir)/m4/argz.m4 \ - $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/iconv.m4 \ - $(top_srcdir)/m4/lib-ld.m4 $(top_srcdir)/m4/lib-link.m4 \ - $(top_srcdir)/m4/lib-prefix.m4 $(top_srcdir)/m4/libcurl.m4 \ - $(top_srcdir)/m4/libgcrypt.m4 $(top_srcdir)/m4/libtool.m4 \ - $(top_srcdir)/m4/libunistring.m4 $(top_srcdir)/m4/ltdl.m4 \ - $(top_srcdir)/m4/ltoptions.m4 $(top_srcdir)/m4/ltsugar.m4 \ - $(top_srcdir)/m4/ltversion.m4 $(top_srcdir)/m4/lt~obsolete.m4 \ - $(top_srcdir)/m4/nls.m4 $(top_srcdir)/m4/po.m4 \ + $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/glib-2.0.m4 \ + $(top_srcdir)/m4/iconv.m4 $(top_srcdir)/m4/lib-ld.m4 \ + $(top_srcdir)/m4/lib-link.m4 $(top_srcdir)/m4/lib-prefix.m4 \ + $(top_srcdir)/m4/libcurl.m4 $(top_srcdir)/m4/libgcrypt.m4 \ + $(top_srcdir)/m4/libtool.m4 $(top_srcdir)/m4/libunistring.m4 \ + $(top_srcdir)/m4/ltdl.m4 $(top_srcdir)/m4/ltoptions.m4 \ + $(top_srcdir)/m4/ltsugar.m4 $(top_srcdir)/m4/ltversion.m4 \ + $(top_srcdir)/m4/lt~obsolete.m4 $(top_srcdir)/m4/nls.m4 \ + $(top_srcdir)/m4/pkg.m4 $(top_srcdir)/m4/po.m4 \ $(top_srcdir)/m4/progtest.m4 $(top_srcdir)/acinclude.m4 \ $(top_srcdir)/configure.ac am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ @@ -79,29 +102,86 @@ am__nobase_list = $(am__nobase_strip_setup); \ am__base_list = \ sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \ sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g' -am__installdirs = "$(DESTDIR)$(libdir)" -LTLIBRARIES = $(lib_LTLIBRARIES) -libgnunetregex_la_DEPENDENCIES = \ - $(top_builddir)/src/util/libgnunetutil.la -am_libgnunetregex_la_OBJECTS = regex.lo -libgnunetregex_la_OBJECTS = $(am_libgnunetregex_la_OBJECTS) -AM_V_lt = $(am__v_lt_$(V)) -am__v_lt_ = $(am__v_lt_$(AM_DEFAULT_VERBOSITY)) +am__uninstall_files_from_dir = { \ + test -z "$$files" \ + || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \ + || { echo " ( cd '$$dir' && rm -f" $$files ")"; \ + $(am__cd) "$$dir" && rm -f $$files; }; \ + } +am__installdirs = "$(DESTDIR)$(libdir)" "$(DESTDIR)$(plugindir)" +LTLIBRARIES = $(lib_LTLIBRARIES) $(noinst_LTLIBRARIES) \ + $(plugin_LTLIBRARIES) +am_libgnunet_plugin_block_regex_la_OBJECTS = plugin_block_regex.lo +libgnunet_plugin_block_regex_la_OBJECTS = \ + $(am_libgnunet_plugin_block_regex_la_OBJECTS) +AM_V_lt = $(am__v_lt_@AM_V@) +am__v_lt_ = $(am__v_lt_@AM_DEFAULT_V@) am__v_lt_0 = --silent +libgnunet_plugin_block_regex_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ + $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ + $(AM_CFLAGS) $(CFLAGS) \ + $(libgnunet_plugin_block_regex_la_LDFLAGS) $(LDFLAGS) -o $@ +am_libgnunetregex_la_OBJECTS = regex.lo regex_graph.lo regex_random.lo \ + regex_dht.lo +libgnunetregex_la_OBJECTS = $(am_libgnunetregex_la_OBJECTS) libgnunetregex_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ $(AM_CFLAGS) $(CFLAGS) $(libgnunetregex_la_LDFLAGS) $(LDFLAGS) \ -o $@ +am__DEPENDENCIES_1 = +libgnunetregexblock_la_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(am__DEPENDENCIES_1) +am_libgnunetregexblock_la_OBJECTS = regex_block_lib.lo +libgnunetregexblock_la_OBJECTS = $(am_libgnunetregexblock_la_OBJECTS) +libgnunetregexblock_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ + $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ + $(AM_CFLAGS) $(CFLAGS) $(libgnunetregexblock_la_LDFLAGS) \ + $(LDFLAGS) -o $@ +am_libgnunetregextest_la_OBJECTS = regex_test_lib.lo +libgnunetregextest_la_OBJECTS = $(am_libgnunetregextest_la_OBJECTS) +@HAVE_MYSQL_TRUE@am__EXEEXT_1 = \ +@HAVE_MYSQL_TRUE@ gnunet-regex-simulation-profiler$(EXEEXT) +PROGRAMS = $(noinst_PROGRAMS) +am_gnunet_daemon_regexprofiler_OBJECTS = \ + gnunet-daemon-regexprofiler.$(OBJEXT) +gnunet_daemon_regexprofiler_OBJECTS = \ + $(am_gnunet_daemon_regexprofiler_OBJECTS) +am_gnunet_regex_profiler_OBJECTS = gnunet-regex-profiler.$(OBJEXT) +gnunet_regex_profiler_OBJECTS = $(am_gnunet_regex_profiler_OBJECTS) +am__gnunet_regex_simulation_profiler_SOURCES_DIST = \ + gnunet-regex-simulation-profiler.c +@HAVE_MYSQL_TRUE@am_gnunet_regex_simulation_profiler_OBJECTS = \ +@HAVE_MYSQL_TRUE@ gnunet-regex-simulation-profiler.$(OBJEXT) +gnunet_regex_simulation_profiler_OBJECTS = \ + $(am_gnunet_regex_simulation_profiler_OBJECTS) +am_perf_regex_OBJECTS = perf-regex.$(OBJEXT) +perf_regex_OBJECTS = $(am_perf_regex_OBJECTS) am_test_regex_eval_api_OBJECTS = test_regex_eval_api.$(OBJEXT) test_regex_eval_api_OBJECTS = $(am_test_regex_eval_api_OBJECTS) test_regex_eval_api_DEPENDENCIES = \ $(top_builddir)/src/regex/libgnunetregex.la \ $(top_builddir)/src/util/libgnunetutil.la +am_test_regex_graph_api_OBJECTS = test_regex_graph_api.$(OBJEXT) +test_regex_graph_api_OBJECTS = $(am_test_regex_graph_api_OBJECTS) +test_regex_graph_api_DEPENDENCIES = \ + $(top_builddir)/src/regex/libgnunetregex.la \ + $(top_builddir)/src/util/libgnunetutil.la +am_test_regex_iptoregex_OBJECTS = test_regex_iptoregex.$(OBJEXT) +test_regex_iptoregex_OBJECTS = $(am_test_regex_iptoregex_OBJECTS) +test_regex_iptoregex_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/regex/libgnunetregex.la am_test_regex_iterate_api_OBJECTS = test_regex_iterate_api.$(OBJEXT) test_regex_iterate_api_OBJECTS = $(am_test_regex_iterate_api_OBJECTS) test_regex_iterate_api_DEPENDENCIES = \ $(top_builddir)/src/regex/libgnunetregex.la \ $(top_builddir)/src/util/libgnunetutil.la +am_test_regex_proofs_OBJECTS = test_regex_proofs.$(OBJEXT) +test_regex_proofs_OBJECTS = $(am_test_regex_proofs_OBJECTS) +test_regex_proofs_DEPENDENCIES = \ + $(top_builddir)/src/regex/libgnunetregex.la \ + $(top_builddir)/src/util/libgnunetutil.la DEFAULT_INCLUDES = -I.@am__isrc@ -I$(top_builddir) depcomp = $(SHELL) $(top_srcdir)/depcomp am__depfiles_maybe = depfiles @@ -112,27 +192,47 @@ LTCOMPILE = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) \ $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) \ $(AM_CFLAGS) $(CFLAGS) -AM_V_CC = $(am__v_CC_$(V)) -am__v_CC_ = $(am__v_CC_$(AM_DEFAULT_VERBOSITY)) +AM_V_CC = $(am__v_CC_@AM_V@) +am__v_CC_ = $(am__v_CC_@AM_DEFAULT_V@) am__v_CC_0 = @echo " CC " $@; -AM_V_at = $(am__v_at_$(V)) -am__v_at_ = $(am__v_at_$(AM_DEFAULT_VERBOSITY)) +AM_V_at = $(am__v_at_@AM_V@) +am__v_at_ = $(am__v_at_@AM_DEFAULT_V@) am__v_at_0 = @ CCLD = $(CC) LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ $(AM_LDFLAGS) $(LDFLAGS) -o $@ -AM_V_CCLD = $(am__v_CCLD_$(V)) -am__v_CCLD_ = $(am__v_CCLD_$(AM_DEFAULT_VERBOSITY)) +AM_V_CCLD = $(am__v_CCLD_@AM_V@) +am__v_CCLD_ = $(am__v_CCLD_@AM_DEFAULT_V@) am__v_CCLD_0 = @echo " CCLD " $@; -AM_V_GEN = $(am__v_GEN_$(V)) -am__v_GEN_ = $(am__v_GEN_$(AM_DEFAULT_VERBOSITY)) +AM_V_GEN = $(am__v_GEN_@AM_V@) +am__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@) am__v_GEN_0 = @echo " GEN " $@; -SOURCES = $(libgnunetregex_la_SOURCES) $(test_regex_eval_api_SOURCES) \ - $(test_regex_iterate_api_SOURCES) -DIST_SOURCES = $(libgnunetregex_la_SOURCES) \ - $(test_regex_eval_api_SOURCES) \ - $(test_regex_iterate_api_SOURCES) +SOURCES = $(libgnunet_plugin_block_regex_la_SOURCES) \ + $(libgnunetregex_la_SOURCES) $(libgnunetregexblock_la_SOURCES) \ + $(libgnunetregextest_la_SOURCES) \ + $(gnunet_daemon_regexprofiler_SOURCES) \ + $(gnunet_regex_profiler_SOURCES) \ + $(gnunet_regex_simulation_profiler_SOURCES) \ + $(perf_regex_SOURCES) $(test_regex_eval_api_SOURCES) \ + $(test_regex_graph_api_SOURCES) \ + $(test_regex_iptoregex_SOURCES) \ + $(test_regex_iterate_api_SOURCES) $(test_regex_proofs_SOURCES) +DIST_SOURCES = $(libgnunet_plugin_block_regex_la_SOURCES) \ + $(libgnunetregex_la_SOURCES) $(libgnunetregexblock_la_SOURCES) \ + $(libgnunetregextest_la_SOURCES) \ + $(gnunet_daemon_regexprofiler_SOURCES) \ + $(gnunet_regex_profiler_SOURCES) \ + $(am__gnunet_regex_simulation_profiler_SOURCES_DIST) \ + $(perf_regex_SOURCES) $(test_regex_eval_api_SOURCES) \ + $(test_regex_graph_api_SOURCES) \ + $(test_regex_iptoregex_SOURCES) \ + $(test_regex_iterate_api_SOURCES) $(test_regex_proofs_SOURCES) +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac ETAGS = etags CTAGS = ctags am__tty_colors = \ @@ -173,6 +273,10 @@ EXEEXT = @EXEEXT@ EXT_LIBS = @EXT_LIBS@ EXT_LIB_PATH = @EXT_LIB_PATH@ FGREP = @FGREP@ +GLIB_CFLAGS = @GLIB_CFLAGS@ +GLIB_GENMARSHAL = @GLIB_GENMARSHAL@ +GLIB_LIBS = @GLIB_LIBS@ +GLIB_MKENUMS = @GLIB_MKENUMS@ GMSGFMT = @GMSGFMT@ GMSGFMT_015 = @GMSGFMT_015@ GNUNETDNS_GROUP = @GNUNETDNS_GROUP@ @@ -183,6 +287,7 @@ GN_LIBINTL = @GN_LIBINTL@ GN_LIB_LDFLAGS = @GN_LIB_LDFLAGS@ GN_PLUGIN_LDFLAGS = @GN_PLUGIN_LDFLAGS@ GN_USER_HOME_DIR = @GN_USER_HOME_DIR@ +GOBJECT_QUERY = @GOBJECT_QUERY@ GREP = @GREP@ HAVE_LIBUNISTRING = @HAVE_LIBUNISTRING@ INCLTDL = @INCLTDL@ @@ -205,6 +310,8 @@ LIBCURL_CPPFLAGS = @LIBCURL_CPPFLAGS@ LIBGCRYPT_CFLAGS = @LIBGCRYPT_CFLAGS@ LIBGCRYPT_CONFIG = @LIBGCRYPT_CONFIG@ LIBGCRYPT_LIBS = @LIBGCRYPT_LIBS@ +LIBGTOP_CFLAGS = @LIBGTOP_CFLAGS@ +LIBGTOP_LIBS = @LIBGTOP_LIBS@ LIBICONV = @LIBICONV@ LIBINTL = @LIBINTL@ LIBLTDL = @LIBLTDL@ @@ -226,6 +333,7 @@ LT_CONFIG_H = @LT_CONFIG_H@ LT_DLLOADERS = @LT_DLLOADERS@ LT_DLPREOPEN = @LT_DLPREOPEN@ MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ MKDIR_P = @MKDIR_P@ MONKEYPREFIX = @MONKEYPREFIX@ MSGFMT = @MSGFMT@ @@ -235,6 +343,7 @@ MYSQL_CPPFLAGS = @MYSQL_CPPFLAGS@ MYSQL_LDFLAGS = @MYSQL_LDFLAGS@ NM = @NM@ NMEDIT = @NMEDIT@ +NSS_DIR = @NSS_DIR@ OBJC = @OBJC@ OBJCDEPMODE = @OBJCDEPMODE@ OBJCFLAGS = @OBJCFLAGS@ @@ -250,6 +359,7 @@ PACKAGE_TARNAME = @PACKAGE_TARNAME@ PACKAGE_URL = @PACKAGE_URL@ PACKAGE_VERSION = @PACKAGE_VERSION@ PATH_SEPARATOR = @PATH_SEPARATOR@ +PKG_CONFIG = @PKG_CONFIG@ POSTGRES_CPPFLAGS = @POSTGRES_CPPFLAGS@ POSTGRES_LDFLAGS = @POSTGRES_LDFLAGS@ POSUB = @POSUB@ @@ -281,6 +391,7 @@ abs_builddir = @abs_builddir@ abs_srcdir = @abs_srcdir@ abs_top_builddir = @abs_top_builddir@ abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ ac_ct_CC = @ac_ct_CC@ ac_ct_CXX = @ac_ct_CXX@ ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ @@ -303,6 +414,7 @@ datarootdir = @datarootdir@ docdir = @docdir@ dvidir = @dvidir@ exec_prefix = @exec_prefix@ +gitcommand = @gitcommand@ host = @host@ host_alias = @host_alias@ host_cpu = @host_cpu@ @@ -316,7 +428,6 @@ libdir = @libdir@ libexecdir = @libexecdir@ localedir = @localedir@ localstatedir = @localstatedir@ -lt_ECHO = @lt_ECHO@ ltdl_LIBOBJS = @ltdl_LIBOBJS@ ltdl_LTLIBOBJS = @ltdl_LTLIBOBJS@ mandir = @mandir@ @@ -334,6 +445,7 @@ sbindir = @sbindir@ sharedstatedir = @sharedstatedir@ srcdir = @srcdir@ subdirs = @subdirs@ +svnversioncommand = @svnversioncommand@ sys_symbol_underscore = @sys_symbol_underscore@ sysconfdir = @sysconfdir@ target = @target@ @@ -347,33 +459,160 @@ top_srcdir = @top_srcdir@ INCLUDES = -I$(top_srcdir)/src/include @MINGW_TRUE@WINFLAGS = -Wl,--no-undefined -Wl,--export-all-symbols @USE_COVERAGE_TRUE@AM_CFLAGS = --coverage -lib_LTLIBRARIES = libgnunetregex.la +lib_LTLIBRARIES = libgnunetregexblock.la \ + libgnunetregex.la + +libgnunetregexblock_la_SOURCES = \ + regex_block_lib.c regex_block_lib.h + +libgnunetregexblock_la_LIBADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(XLIB) \ + $(LTLIBINTL) + +libgnunetregexblock_la_LDFLAGS = \ + $(GN_LIB_LDFLAGS) $(WINFLAGS) \ + -version-info 1:0:0 + libgnunetregex_la_SOURCES = \ - regex.c + regex_internal.h regex.c \ + regex_graph.c regex_random.c \ + regex_dht.c libgnunetregex_la_LIBADD = -lm \ - $(top_builddir)/src/util/libgnunetutil.la + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/dht/libgnunetdht.la \ + $(top_builddir)/src/statistics/libgnunetstatistics.la \ + $(top_builddir)/src/regex/libgnunetregexblock.la + +libgnunetregex_la_DEPENDENCIES = \ + libgnunetregexblock.la libgnunetregex_la_LDFLAGS = \ - $(GN_LIB_LDFLAGS) \ - -version-info 0:0:0 + $(GN_LIB_LDFLAGS) \ + -version-info 2:0:1 + +plugindir = $(libdir)/gnunet +plugin_LTLIBRARIES = \ + libgnunet_plugin_block_regex.la + +libgnunet_plugin_block_regex_la_SOURCES = \ + plugin_block_regex.c + +libgnunet_plugin_block_regex_la_LIBADD = \ + $(top_builddir)/src/regex/libgnunetregexblock.la \ + $(top_builddir)/src/block/libgnunetblock.la \ + $(top_builddir)/src/util/libgnunetutil.la + +libgnunet_plugin_block_regex_la_LDFLAGS = \ + $(GN_PLUGIN_LDFLAGS) + +libgnunet_plugin_block_regex_la_DEPENDENCIES = \ + libgnunetregexblock.la + +@HAVE_MYSQL_TRUE@noinst_mysql_progs = \ +@HAVE_MYSQL_TRUE@gnunet-regex-simulation-profiler + +@HAVE_MYSQL_TRUE@gnunet_regex_simulation_profiler_SOURCES = \ +@HAVE_MYSQL_TRUE@ gnunet-regex-simulation-profiler.c + +@HAVE_MYSQL_TRUE@gnunet_regex_simulation_profiler_LDADD = \ +@HAVE_MYSQL_TRUE@ $(top_builddir)/src/util/libgnunetutil.la \ +@HAVE_MYSQL_TRUE@ $(top_builddir)/src/regex/libgnunetregex.la \ +@HAVE_MYSQL_TRUE@ $(top_builddir)/src/mysql/libgnunetmysql.la + +@HAVE_MYSQL_TRUE@gnunet_regex_simulation_profiler_DEPENDENCIES = \ +@HAVE_MYSQL_TRUE@ libgnunetregex.la + +noinst_LTLIBRARIES = libgnunetregextest.la +libgnunetregextest_la_SOURCES = \ + regex_test_lib.c regex_test_lib.h + +libgnunetregextest_la_LIBADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/regex/libgnunetregex.la + +libgnunetregextest_la_DEPENDENCIES = \ + libgnunetregex.la + +perf_regex_SOURCES = \ + perf-regex.c + +perf_regex_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/regex/libgnunetregex.la \ + $(top_builddir)/src/regex/libgnunetregextest.la + +perf_regex_DEPENDENCIES = \ + libgnunetregex.la \ + libgnunetregextest.la + +gnunet_regex_profiler_SOURCES = \ + gnunet-regex-profiler.c + +gnunet_regex_profiler_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/dht/libgnunetdht.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la \ + $(top_builddir)/src/regex/libgnunetregex.la \ + $(top_builddir)/src/statistics/libgnunetstatistics.la + +gnunet_regex_profiler_DEPENDENCIES = \ + $(top_builddir)/src/dht/libgnunetdht.la \ + libgnunetregex.la + +gnunet_daemon_regexprofiler_SOURCES = \ + gnunet-daemon-regexprofiler.c + +gnunet_daemon_regexprofiler_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/dht/libgnunetdht.la \ + $(top_builddir)/src/regex/libgnunetregex.la \ + $(top_builddir)/src/statistics/libgnunetstatistics.la + +gnunet_daemon_regexprofiler_DEPENDENCIES = \ + $(top_builddir)/src/dht/libgnunetdht.la \ + libgnunetregex.la @ENABLE_TEST_RUN_TRUE@TESTS = $(check_PROGRAMS) test_regex_eval_api_SOURCES = \ - test_regex_eval_api.c + test_regex_eval_api.c test_regex_eval_api_LDADD = \ - $(top_builddir)/src/regex/libgnunetregex.la \ - $(top_builddir)/src/util/libgnunetutil.la + $(top_builddir)/src/regex/libgnunetregex.la \ + $(top_builddir)/src/util/libgnunetutil.la test_regex_iterate_api_SOURCES = \ - test_regex_iterate_api.c + test_regex_iterate_api.c test_regex_iterate_api_LDADD = \ - $(top_builddir)/src/regex/libgnunetregex.la \ - $(top_builddir)/src/util/libgnunetutil.la + $(top_builddir)/src/regex/libgnunetregex.la \ + $(top_builddir)/src/util/libgnunetutil.la + +test_regex_proofs_SOURCES = \ + test_regex_proofs.c + +test_regex_proofs_LDADD = \ + $(top_builddir)/src/regex/libgnunetregex.la \ + $(top_builddir)/src/util/libgnunetutil.la + +test_regex_graph_api_SOURCES = \ + test_regex_graph_api.c + +test_regex_graph_api_LDADD = \ + $(top_builddir)/src/regex/libgnunetregex.la \ + $(top_builddir)/src/util/libgnunetutil.la + +test_regex_iptoregex_SOURCES = \ + test_regex_iptoregex.c + +test_regex_iptoregex_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/regex/libgnunetregex.la + +EXTRA_DIST = \ + regex_simulation_profiler_test.conf -EXTRA_DIST = all: all-am .SUFFIXES: @@ -410,7 +649,6 @@ $(ACLOCAL_M4): $(am__aclocal_m4_deps) $(am__aclocal_m4_deps): install-libLTLIBRARIES: $(lib_LTLIBRARIES) @$(NORMAL_INSTALL) - test -z "$(libdir)" || $(MKDIR_P) "$(DESTDIR)$(libdir)" @list='$(lib_LTLIBRARIES)'; test -n "$(libdir)" || list=; \ list2=; for p in $$list; do \ if test -f $$p; then \ @@ -418,6 +656,8 @@ install-libLTLIBRARIES: $(lib_LTLIBRARIES) else :; fi; \ done; \ test -z "$$list2" || { \ + echo " $(MKDIR_P) '$(DESTDIR)$(libdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libdir)" || exit 1; \ echo " $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 '$(DESTDIR)$(libdir)'"; \ $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 "$(DESTDIR)$(libdir)"; \ } @@ -439,8 +679,55 @@ clean-libLTLIBRARIES: echo "rm -f \"$${dir}/so_locations\""; \ rm -f "$${dir}/so_locations"; \ done -libgnunetregex.la: $(libgnunetregex_la_OBJECTS) $(libgnunetregex_la_DEPENDENCIES) + +clean-noinstLTLIBRARIES: + -test -z "$(noinst_LTLIBRARIES)" || rm -f $(noinst_LTLIBRARIES) + @list='$(noinst_LTLIBRARIES)'; for p in $$list; do \ + dir="`echo $$p | sed -e 's|/[^/]*$$||'`"; \ + test "$$dir" != "$$p" || dir=.; \ + echo "rm -f \"$${dir}/so_locations\""; \ + rm -f "$${dir}/so_locations"; \ + done +install-pluginLTLIBRARIES: $(plugin_LTLIBRARIES) + @$(NORMAL_INSTALL) + @list='$(plugin_LTLIBRARIES)'; test -n "$(plugindir)" || list=; \ + list2=; for p in $$list; do \ + if test -f $$p; then \ + list2="$$list2 $$p"; \ + else :; fi; \ + done; \ + test -z "$$list2" || { \ + echo " $(MKDIR_P) '$(DESTDIR)$(plugindir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(plugindir)" || exit 1; \ + echo " $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 '$(DESTDIR)$(plugindir)'"; \ + $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 "$(DESTDIR)$(plugindir)"; \ + } + +uninstall-pluginLTLIBRARIES: + @$(NORMAL_UNINSTALL) + @list='$(plugin_LTLIBRARIES)'; test -n "$(plugindir)" || list=; \ + for p in $$list; do \ + $(am__strip_dir) \ + echo " $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=uninstall rm -f '$(DESTDIR)$(plugindir)/$$f'"; \ + $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=uninstall rm -f "$(DESTDIR)$(plugindir)/$$f"; \ + done + +clean-pluginLTLIBRARIES: + -test -z "$(plugin_LTLIBRARIES)" || rm -f $(plugin_LTLIBRARIES) + @list='$(plugin_LTLIBRARIES)'; for p in $$list; do \ + dir="`echo $$p | sed -e 's|/[^/]*$$||'`"; \ + test "$$dir" != "$$p" || dir=.; \ + echo "rm -f \"$${dir}/so_locations\""; \ + rm -f "$${dir}/so_locations"; \ + done +libgnunet_plugin_block_regex.la: $(libgnunet_plugin_block_regex_la_OBJECTS) $(libgnunet_plugin_block_regex_la_DEPENDENCIES) $(EXTRA_libgnunet_plugin_block_regex_la_DEPENDENCIES) + $(AM_V_CCLD)$(libgnunet_plugin_block_regex_la_LINK) -rpath $(plugindir) $(libgnunet_plugin_block_regex_la_OBJECTS) $(libgnunet_plugin_block_regex_la_LIBADD) $(LIBS) +libgnunetregex.la: $(libgnunetregex_la_OBJECTS) $(libgnunetregex_la_DEPENDENCIES) $(EXTRA_libgnunetregex_la_DEPENDENCIES) $(AM_V_CCLD)$(libgnunetregex_la_LINK) -rpath $(libdir) $(libgnunetregex_la_OBJECTS) $(libgnunetregex_la_LIBADD) $(LIBS) +libgnunetregexblock.la: $(libgnunetregexblock_la_OBJECTS) $(libgnunetregexblock_la_DEPENDENCIES) $(EXTRA_libgnunetregexblock_la_DEPENDENCIES) + $(AM_V_CCLD)$(libgnunetregexblock_la_LINK) -rpath $(libdir) $(libgnunetregexblock_la_OBJECTS) $(libgnunetregexblock_la_LIBADD) $(LIBS) +libgnunetregextest.la: $(libgnunetregextest_la_OBJECTS) $(libgnunetregextest_la_DEPENDENCIES) $(EXTRA_libgnunetregextest_la_DEPENDENCIES) + $(AM_V_CCLD)$(LINK) $(libgnunetregextest_la_OBJECTS) $(libgnunetregextest_la_LIBADD) $(LIBS) clean-checkPROGRAMS: @list='$(check_PROGRAMS)'; test -n "$$list" || exit 0; \ @@ -450,12 +737,42 @@ clean-checkPROGRAMS: list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ echo " rm -f" $$list; \ rm -f $$list -test_regex_eval_api$(EXEEXT): $(test_regex_eval_api_OBJECTS) $(test_regex_eval_api_DEPENDENCIES) + +clean-noinstPROGRAMS: + @list='$(noinst_PROGRAMS)'; test -n "$$list" || exit 0; \ + echo " rm -f" $$list; \ + rm -f $$list || exit $$?; \ + test -n "$(EXEEXT)" || exit 0; \ + list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ + echo " rm -f" $$list; \ + rm -f $$list +gnunet-daemon-regexprofiler$(EXEEXT): $(gnunet_daemon_regexprofiler_OBJECTS) $(gnunet_daemon_regexprofiler_DEPENDENCIES) $(EXTRA_gnunet_daemon_regexprofiler_DEPENDENCIES) + @rm -f gnunet-daemon-regexprofiler$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(gnunet_daemon_regexprofiler_OBJECTS) $(gnunet_daemon_regexprofiler_LDADD) $(LIBS) +gnunet-regex-profiler$(EXEEXT): $(gnunet_regex_profiler_OBJECTS) $(gnunet_regex_profiler_DEPENDENCIES) $(EXTRA_gnunet_regex_profiler_DEPENDENCIES) + @rm -f gnunet-regex-profiler$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(gnunet_regex_profiler_OBJECTS) $(gnunet_regex_profiler_LDADD) $(LIBS) +gnunet-regex-simulation-profiler$(EXEEXT): $(gnunet_regex_simulation_profiler_OBJECTS) $(gnunet_regex_simulation_profiler_DEPENDENCIES) $(EXTRA_gnunet_regex_simulation_profiler_DEPENDENCIES) + @rm -f gnunet-regex-simulation-profiler$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(gnunet_regex_simulation_profiler_OBJECTS) $(gnunet_regex_simulation_profiler_LDADD) $(LIBS) +perf-regex$(EXEEXT): $(perf_regex_OBJECTS) $(perf_regex_DEPENDENCIES) $(EXTRA_perf_regex_DEPENDENCIES) + @rm -f perf-regex$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(perf_regex_OBJECTS) $(perf_regex_LDADD) $(LIBS) +test_regex_eval_api$(EXEEXT): $(test_regex_eval_api_OBJECTS) $(test_regex_eval_api_DEPENDENCIES) $(EXTRA_test_regex_eval_api_DEPENDENCIES) @rm -f test_regex_eval_api$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_regex_eval_api_OBJECTS) $(test_regex_eval_api_LDADD) $(LIBS) -test_regex_iterate_api$(EXEEXT): $(test_regex_iterate_api_OBJECTS) $(test_regex_iterate_api_DEPENDENCIES) +test_regex_graph_api$(EXEEXT): $(test_regex_graph_api_OBJECTS) $(test_regex_graph_api_DEPENDENCIES) $(EXTRA_test_regex_graph_api_DEPENDENCIES) + @rm -f test_regex_graph_api$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_regex_graph_api_OBJECTS) $(test_regex_graph_api_LDADD) $(LIBS) +test_regex_iptoregex$(EXEEXT): $(test_regex_iptoregex_OBJECTS) $(test_regex_iptoregex_DEPENDENCIES) $(EXTRA_test_regex_iptoregex_DEPENDENCIES) + @rm -f test_regex_iptoregex$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_regex_iptoregex_OBJECTS) $(test_regex_iptoregex_LDADD) $(LIBS) +test_regex_iterate_api$(EXEEXT): $(test_regex_iterate_api_OBJECTS) $(test_regex_iterate_api_DEPENDENCIES) $(EXTRA_test_regex_iterate_api_DEPENDENCIES) @rm -f test_regex_iterate_api$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_regex_iterate_api_OBJECTS) $(test_regex_iterate_api_LDADD) $(LIBS) +test_regex_proofs$(EXEEXT): $(test_regex_proofs_OBJECTS) $(test_regex_proofs_DEPENDENCIES) $(EXTRA_test_regex_proofs_DEPENDENCIES) + @rm -f test_regex_proofs$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_regex_proofs_OBJECTS) $(test_regex_proofs_LDADD) $(LIBS) mostlyclean-compile: -rm -f *.$(OBJEXT) @@ -463,33 +780,43 @@ mostlyclean-compile: distclean-compile: -rm -f *.tab.c +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-daemon-regexprofiler.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-regex-profiler.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-regex-simulation-profiler.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/perf-regex.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/plugin_block_regex.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/regex.Plo@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/regex_block_lib.Plo@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/regex_dht.Plo@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/regex_graph.Plo@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/regex_random.Plo@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/regex_test_lib.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_regex_eval_api.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_regex_graph_api.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_regex_iptoregex.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_regex_iterate_api.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_regex_proofs.Po@am__quote@ .c.o: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c $< .c.obj: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'` @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c `$(CYGPATH_W) '$<'` +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c `$(CYGPATH_W) '$<'` .c.lo: @am__fastdepCC_TRUE@ $(AM_V_CC)$(LTCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LTCOMPILE) -c -o $@ $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LTCOMPILE) -c -o $@ $< mostlyclean-libtool: -rm -f *.lo @@ -630,14 +957,15 @@ check-TESTS: $(TESTS) fi; \ dashes=`echo "$$dashes" | sed s/./=/g`; \ if test "$$failed" -eq 0; then \ - echo "$$grn$$dashes"; \ + col="$$grn"; \ else \ - echo "$$red$$dashes"; \ + col="$$red"; \ fi; \ - echo "$$banner"; \ - test -z "$$skipped" || echo "$$skipped"; \ - test -z "$$report" || echo "$$report"; \ - echo "$$dashes$$std"; \ + echo "$${col}$$dashes$${std}"; \ + echo "$${col}$$banner$${std}"; \ + test -z "$$skipped" || echo "$${col}$$skipped$${std}"; \ + test -z "$$report" || echo "$${col}$$report$${std}"; \ + echo "$${col}$$dashes$${std}"; \ test "$$failed" -eq 0; \ else :; fi @@ -675,9 +1003,9 @@ check-am: all-am $(MAKE) $(AM_MAKEFLAGS) $(check_PROGRAMS) $(MAKE) $(AM_MAKEFLAGS) check-TESTS check: check-am -all-am: Makefile $(LTLIBRARIES) +all-am: Makefile $(LTLIBRARIES) $(PROGRAMS) installdirs: - for dir in "$(DESTDIR)$(libdir)"; do \ + for dir in "$(DESTDIR)$(libdir)" "$(DESTDIR)$(plugindir)"; do \ test -z "$$dir" || $(MKDIR_P) "$$dir"; \ done install: install-am @@ -690,10 +1018,15 @@ install-am: all-am installcheck: installcheck-am install-strip: - $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ - install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ - `test -z '$(STRIP)' || \ - echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi mostlyclean-generic: clean-generic: @@ -708,7 +1041,8 @@ maintainer-clean-generic: clean: clean-am clean-am: clean-checkPROGRAMS clean-generic clean-libLTLIBRARIES \ - clean-libtool mostlyclean-am + clean-libtool clean-noinstLTLIBRARIES clean-noinstPROGRAMS \ + clean-pluginLTLIBRARIES mostlyclean-am distclean: distclean-am -rm -rf ./$(DEPDIR) @@ -728,7 +1062,7 @@ info: info-am info-am: -install-data-am: +install-data-am: install-pluginLTLIBRARIES install-dvi: install-dvi-am @@ -774,26 +1108,27 @@ ps: ps-am ps-am: -uninstall-am: uninstall-libLTLIBRARIES +uninstall-am: uninstall-libLTLIBRARIES uninstall-pluginLTLIBRARIES .MAKE: check-am install-am install-strip .PHONY: CTAGS GTAGS all all-am check check-TESTS check-am clean \ clean-checkPROGRAMS clean-generic clean-libLTLIBRARIES \ - clean-libtool ctags distclean distclean-compile \ + clean-libtool clean-noinstLTLIBRARIES clean-noinstPROGRAMS \ + clean-pluginLTLIBRARIES ctags distclean distclean-compile \ distclean-generic distclean-libtool distclean-tags distdir dvi \ dvi-am html html-am info info-am install install-am \ install-data install-data-am install-dvi install-dvi-am \ install-exec install-exec-am install-html install-html-am \ install-info install-info-am install-libLTLIBRARIES \ - install-man install-pdf install-pdf-am install-ps \ - install-ps-am install-strip installcheck installcheck-am \ - installdirs maintainer-clean maintainer-clean-generic \ - mostlyclean mostlyclean-compile mostlyclean-generic \ - mostlyclean-libtool pdf pdf-am ps ps-am tags uninstall \ - uninstall-am uninstall-libLTLIBRARIES - -# test_regex_data.conf + install-man install-pdf install-pdf-am \ + install-pluginLTLIBRARIES install-ps install-ps-am \ + install-strip installcheck installcheck-am installdirs \ + maintainer-clean maintainer-clean-generic mostlyclean \ + mostlyclean-compile mostlyclean-generic mostlyclean-libtool \ + pdf pdf-am ps ps-am tags uninstall uninstall-am \ + uninstall-libLTLIBRARIES uninstall-pluginLTLIBRARIES + # Tell versions [3.59,3.63) of GNU make to not export all variables. # Otherwise a system limit (for SysV at least) may be exceeded. diff --git a/src/regex/gnunet-daemon-regexprofiler.c b/src/regex/gnunet-daemon-regexprofiler.c new file mode 100644 index 0000000..591cda3 --- /dev/null +++ b/src/regex/gnunet-daemon-regexprofiler.c @@ -0,0 +1,472 @@ +/* + This file is part of GNUnet. + (C) 2012, 2013 Christian Grothoff + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @file regex/gnunet-daemon-regexprofiler.c + * @brief daemon that uses mesh to announce a regular expression. Used in + * conjunction with gnunet-regex-profiler to announce regexes on serveral peers + * without the need to explicitly connect to the mesh service running on the + * peer from within the profiler. + * @author Maximilian Szengel + * @author Bartlomiej Polot + */ +#include "platform.h" +#include "gnunet_util_lib.h" +#include "gnunet_regex_lib.h" +#include "gnunet_dht_service.h" +#include "gnunet_statistics_service.h" + +/** + * Return value from 'main'. + */ +static int global_ret; + +/** + * Configuration we use. + */ +static const struct GNUNET_CONFIGURATION_Handle *cfg; + +/** + * Handle to the statistics service. + */ +static struct GNUNET_STATISTICS_Handle *stats_handle; + +/** + * Peer's dht handle. + */ +static struct GNUNET_DHT_Handle *dht_handle; + +/** + * Peer's regex announce handle. + */ +static struct GNUNET_REGEX_announce_handle *announce_handle; + +/** + * Hostkey generation context + */ +static struct GNUNET_CRYPTO_RsaKeyGenerationContext *keygen; + +/** + * Periodically reannounce regex. + */ +static GNUNET_SCHEDULER_TaskIdentifier reannounce_task; + +/** + * How often reannounce regex. + */ +static struct GNUNET_TIME_Relative reannounce_freq; + +/** + * Random delay to spread out load on the DHT. + */ +static struct GNUNET_TIME_Relative announce_delay; + +/** + * Local peer's PeerID. + */ +static struct GNUNET_PeerIdentity my_full_id; + +/** + * Maximal path compression length for regex announcing. + */ +static unsigned long long max_path_compression; + +/** + * Name of the file containing policies that this peer should announce. One + * policy per line. + */ +static char * policy_filename; + +/** + * Prefix to add before every regex we're announcing. + */ +static char * regex_prefix; + +/** + * Regex with prefix. + */ +static char *rx_with_pfx; + + +/** + * Task run during shutdown. + * + * @param cls unused + * @param tc unused + */ +static void +shutdown_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "shutting down\n"); + + if (NULL != keygen) + { + GNUNET_CRYPTO_rsa_key_create_stop (keygen); + keygen = NULL; + } + if (NULL != announce_handle) + { + GNUNET_REGEX_announce_cancel (announce_handle); + announce_handle = NULL; + } + + if (NULL != dht_handle) + { + GNUNET_DHT_disconnect (dht_handle); + dht_handle = NULL; + } + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "shut down\n"); +} + + +/** + * Announce a previously announced regex re-using cached data. + * + * @param cls Closure (regex to announce if needed). + * @param tc TaskContext. + */ +static void +reannounce_regex (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + char *regex = cls; + reannounce_task = GNUNET_SCHEDULER_NO_TASK; + if (0 != (tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN)) + { + GNUNET_free (regex); + return; + } + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Announcing regex: %s\n", regex); + GNUNET_STATISTICS_update (stats_handle, "# regexes announced", 1, GNUNET_NO); + if (NULL == announce_handle && NULL != regex) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "First time, creating regex: %s\n", + regex); + announce_handle = GNUNET_REGEX_announce (dht_handle, + &my_full_id, + regex, + (unsigned int) max_path_compression, + stats_handle); + } + else + { + GNUNET_assert (NULL != announce_handle); + GNUNET_REGEX_reannounce (announce_handle); + } + + reannounce_task = + GNUNET_SCHEDULER_add_delayed ( + GNUNET_TIME_relative_add (reannounce_freq, + GNUNET_TIME_relative_multiply ( + GNUNET_TIME_UNIT_SECONDS, + GNUNET_CRYPTO_random_u32 ( + GNUNET_CRYPTO_QUALITY_WEAK, + 600))), + &reannounce_regex, + cls); +} + + +/** + * Announce the given regular expression using Mesh and the path compression + * length read from config. + * + * @param regex regular expression to announce on this peer's mesh. + */ +static void +announce_regex (const char * regex) +{ + char *copy; + + if (NULL == regex || 0 == strlen (regex)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Cannot announce empty regex\n"); + return; + } + + GNUNET_assert (GNUNET_SCHEDULER_NO_TASK == reannounce_task); + copy = GNUNET_strdup (regex); + reannounce_task = GNUNET_SCHEDULER_add_delayed (announce_delay, + reannounce_regex, + (void *) copy); +} + + +/** + * Load regular expressions from filename into 'rxes' array. Array needs to be freed. + * + * @param filename filename of the file containing the regexes, one per line. + * @param rx string with the union of all regular expressions. + * + * @return number of regular expressions read from filename and in rxes array. + * FIXME use load regex lib function + */ +static unsigned int +load_regexes (const char *filename, char **rx) +{ + char *data; + char *buf; + uint64_t filesize; + unsigned int offset; + unsigned int rx_cnt; + + if (GNUNET_YES != GNUNET_DISK_file_test (policy_filename)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Could not find policy file %s\n", policy_filename); + return 0; + } + if (GNUNET_OK != GNUNET_DISK_file_size (policy_filename, &filesize, GNUNET_YES, GNUNET_YES)) + filesize = 0; + if (0 == filesize) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Policy file %s is empty.\n", policy_filename); + return 0; + } + data = GNUNET_malloc (filesize); + if (filesize != GNUNET_DISK_fn_read (policy_filename, data, filesize)) + { + GNUNET_free (data); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Could not read policy file %s.\n", + policy_filename); + return 0; + } + buf = data; + offset = 0; + rx_cnt = 0; + while (offset < (filesize - 1)) + { + offset++; + if ((data[offset] == '\n') && (buf != &data[offset])) + { + data[offset] = '|'; + buf = &data[offset + 1]; + rx_cnt++; + } + else if ((data[offset] == '\n') || (data[offset] == '\0')) + buf = &data[offset + 1]; + } + data[offset] = '\0'; + *rx = data; + + return rx_cnt; +} + + +/** + * Callback for hostkey read/generation + * + * @param cls Closure (not used). + * @param pk The private key of the local peer. + * @param emsg Error message if applicable. + */ +static void +key_generation_cb (void *cls, + struct GNUNET_CRYPTO_RsaPrivateKey *pk, + const char *emsg) +{ + struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded my_public_key; + + keygen = NULL; + if (NULL == pk) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Regexprofiler could not access hostkey: %s. Exiting.\n"), + emsg); + GNUNET_SCHEDULER_shutdown (); + return; + } + + GNUNET_CRYPTO_rsa_key_get_public (pk, &my_public_key); + GNUNET_CRYPTO_hash (&my_public_key, sizeof (my_public_key), + &my_full_id.hashPubKey); + + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + "Regexprofiler for peer [%s] starting\n", + GNUNET_i2s(&my_full_id)); + announce_regex (rx_with_pfx); + GNUNET_free (rx_with_pfx); +} + + +/** + * @brief Main function that will be run by the scheduler. + * + * @param cls closure + * @param args remaining command-line arguments + * @param cfgfile name of the configuration file used (for saving, can be NULL!) + * @param cfg_ configuration + */ +static void +run (void *cls, char *const *args GNUNET_UNUSED, + const char *cfgfile GNUNET_UNUSED, + const struct GNUNET_CONFIGURATION_Handle *cfg_) +{ + char *regex = NULL; + char *keyfile; + + cfg = cfg_; + + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_filename (cfg, "GNUNETD", "HOSTKEY", + &keyfile)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _ + ("%s service is lacking key configuration settings (%s). Exiting.\n"), + "regexprofiler", "hostkey"); + GNUNET_SCHEDULER_shutdown (); + return; + } + + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_number (cfg, "REGEXPROFILER", "MAX_PATH_COMPRESSION", + &max_path_compression)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _ + ("%s service is lacking key configuration settings (%s). Exiting.\n"), + "regexprofiler", "max_path_compression"); + global_ret = GNUNET_SYSERR; + GNUNET_SCHEDULER_shutdown (); + return; + } + + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_filename (cfg, "REGEXPROFILER", + "POLICY_FILE", &policy_filename)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _ + ("%s service is lacking key configuration settings (%s). Exiting.\n"), + "regexprofiler", "policy_file"); + global_ret = GNUNET_SYSERR; + GNUNET_SCHEDULER_shutdown (); + return; + } + + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_string (cfg, "REGEXPROFILER", + "REGEX_PREFIX", ®ex_prefix)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _ + ("%s service is lacking key configuration settings (%s). Exiting.\n"), + "regexprofiler", "regex_prefix"); + global_ret = GNUNET_SYSERR; + GNUNET_SCHEDULER_shutdown (); + return; + } + + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_time (cfg, "REGEXPROFILER", + "REANNOUNCE_FREQ", &reannounce_freq)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "reannounce_freq not given. Using 10 minutes.\n"); + reannounce_freq = + GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MINUTES, 10); + + } + announce_delay = + GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, + GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK, 600)); + + stats_handle = GNUNET_STATISTICS_create ("regexprofiler", cfg); + + dht_handle = GNUNET_DHT_connect (cfg, 1); + + if (NULL == dht_handle) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Could not acquire dht handle. Exiting.\n"); + global_ret = GNUNET_SYSERR; + GNUNET_SCHEDULER_shutdown (); + return; + } + + /* Read regexes from policy files */ + if (0 == load_regexes (policy_filename, ®ex)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Policy file %s contains no policies. Exiting.\n", + policy_filename); + global_ret = GNUNET_SYSERR; + GNUNET_SCHEDULER_shutdown (); + return; + } + + /* Announcing regexes from policy_filename */ + GNUNET_asprintf (&rx_with_pfx, "%s(%s)", regex_prefix, regex); + GNUNET_free (regex); + + keygen = GNUNET_CRYPTO_rsa_key_create_start (keyfile, + &key_generation_cb, + NULL); + GNUNET_free (keyfile); + + /* Scheduled the task to clean up when shutdown is called */ + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, &shutdown_task, + NULL); +} + + +/** + * The main function of the regexprofiler service. + * + * @param argc number of arguments from the command line + * @param argv command line arguments + * @return 0 ok, 1 on error + */ +int +main (int argc, char *const *argv) +{ + static const struct GNUNET_GETOPT_CommandLineOption options[] = { + GNUNET_GETOPT_OPTION_END + }; + + if (GNUNET_OK != GNUNET_STRINGS_get_utf8_args (argc, argv, &argc, &argv)) + return 2; + return (GNUNET_OK == + GNUNET_PROGRAM_run (argc, argv, "regexprofiler", + gettext_noop + ("Daemon to announce regular expressions for the peer using mesh."), + options, &run, NULL)) ? global_ret : 1; +} + + +#ifdef LINUX +#include + +/** + * MINIMIZE heap size (way below 128k) since this process doesn't need much. + */ +void __attribute__ ((constructor)) GNUNET_ARM_memory_init () +{ + mallopt (M_TRIM_THRESHOLD, 4 * 1024); + mallopt (M_TOP_PAD, 1 * 1024); + malloc_trim (0); +} +#endif + + +/* end of gnunet-daemon-regexprofiler.c */ diff --git a/src/regex/gnunet-regex-profiler.c b/src/regex/gnunet-regex-profiler.c new file mode 100644 index 0000000..f0a05c4 --- /dev/null +++ b/src/regex/gnunet-regex-profiler.c @@ -0,0 +1,1889 @@ +/* + This file is part of GNUnet. + (C) 2011 - 2013 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @file regex/gnunet-regex-profiler.c + * @brief Regex profiler for testing distributed regex use. + * @author Bartlomiej Polot + * @author Maximilian Szengel + * + */ + +#include + +#include "platform.h" +#include "gnunet_applications.h" +#include "gnunet_util_lib.h" +#include "gnunet_regex_lib.h" +#include "gnunet_dht_service.h" +#include "gnunet_testbed_service.h" + +/** + * DLL of operations + */ +struct DLLOperation +{ + /** + * The testbed operation handle + */ + struct GNUNET_TESTBED_Operation *op; + + /** + * Closure + */ + void *cls; + + /** + * The next pointer for DLL + */ + struct DLLOperation *next; + + /** + * The prev pointer for DLL + */ + struct DLLOperation *prev; +}; + + +/** + * Available states during profiling + */ +enum State +{ + /** + * Initial state + */ + STATE_INIT = 0, + + /** + * Starting slaves + */ + STATE_SLAVES_STARTING, + + /** + * Creating peers + */ + STATE_PEERS_CREATING, + + /** + * Starting peers + */ + STATE_PEERS_STARTING, + + /** + * Linking peers + */ + STATE_PEERS_LINKING, + + /** + * Matching strings against announced regexes + */ + STATE_SEARCH_REGEX, + + /** + * Destroying peers; we can do this as the controller takes care of stopping a + * peer if it is running + */ + STATE_PEERS_DESTROYING +}; + + +/** + * Peer handles. + */ +struct RegexPeer +{ + /** + * Peer id. + */ + unsigned int id; + + /** + * Peer configuration handle. + */ + struct GNUNET_CONFIGURATION_Handle *cfg; + + /** + * The actual testbed peer handle. + */ + struct GNUNET_TESTBED_Peer *peer_handle; + + /** + * Host on which the peer is running. + */ + struct GNUNET_TESTBED_Host *host_handle; + + /** + * Filename of the peer's policy file. + */ + char *policy_file; + + /** + * Peers search string. + */ + const char *search_str; + + /** + * Set to GNUNET_YES if the peer successfully matched the above + * search string. GNUNET_NO if the string could not be matched + * during the profiler run. GNUNET_SYSERR if the string matching + * timed out. Undefined if search_str is NULL + */ + int search_str_matched; + + /** + * Peer's dht handle. + */ + struct GNUNET_DHT_Handle *dht_handle; + + /** + * Handle to a running regex search. + */ + struct GNUNET_REGEX_search_handle *search_handle; + + /** + * Testbed operation handle for the dht service. + */ + struct GNUNET_TESTBED_Operation *dht_op_handle; + + /** + * Peers's statistics handle. + */ + struct GNUNET_STATISTICS_Handle *stats_handle; + + /** + * Testbed operation handle for the statistics service. + */ + struct GNUNET_TESTBED_Operation *stats_op_handle; + + /** + * The starting time of a profiling step. + */ + struct GNUNET_TIME_Absolute prof_start_time; +}; + + +/** + * An array of hosts loaded from the hostkeys file + */ +static struct GNUNET_TESTBED_Host **hosts; + +/** + * Array of peer handles used to pass to + * GNUNET_TESTBED_overlay_configure_topology + */ +static struct GNUNET_TESTBED_Peer **peer_handles; + +/** + * The array of peers; we fill this as the peers are given to us by the testbed + */ +static struct RegexPeer *peers; + +/** + * Host registration handle + */ +static struct GNUNET_TESTBED_HostRegistrationHandle *reg_handle; + +/** + * Handle to the master controller process + */ +static struct GNUNET_TESTBED_ControllerProc *mc_proc; + +/** + * Handle to the master controller + */ +static struct GNUNET_TESTBED_Controller *mc; + +/** + * Handle to global configuration + */ +static struct GNUNET_CONFIGURATION_Handle *cfg; + +/** + * Head of the operations list + */ +static struct DLLOperation *dll_op_head; + +/** + * Tail of the operations list + */ +static struct DLLOperation *dll_op_tail; + +/** + * Peer linking - topology operation + */ +static struct GNUNET_TESTBED_Operation *topology_op; + +/** + * The handle for whether a host is habitable or not + */ +struct GNUNET_TESTBED_HostHabitableCheckHandle **hc_handles; + +/** + * Abort task identifier + */ +static GNUNET_SCHEDULER_TaskIdentifier abort_task; + +/** + * Shutdown task identifier + */ +static GNUNET_SCHEDULER_TaskIdentifier shutdown_task; + +/** + * Host registration task identifier + */ +static GNUNET_SCHEDULER_TaskIdentifier register_hosts_task; + +/** + * Global event mask for all testbed events + */ +static uint64_t event_mask; + +/** + * The starting time of a profiling step + */ +static struct GNUNET_TIME_Absolute prof_start_time; + +/** + * Duration profiling step has taken + */ +static struct GNUNET_TIME_Relative prof_time; + +/** + * Number of peers to be started by the profiler + */ +static unsigned int num_peers; + +/** + * Number of hosts in the hosts array + */ +static unsigned int num_hosts; + +/** + * Factor of number of links. num_links = num_peers * linking_factor. + */ +static unsigned int linking_factor; + +/** + * Number of random links to be established between peers + */ +static unsigned int num_links; + +/** + * Number of times we try overlay connect operations + */ +static unsigned int retry_links; + +/** + * Continuous failures during overlay connect operations + */ +static unsigned int cont_fails; + +/** + * Global testing status + */ +static int result; + +/** + * current state of profiling + */ +enum State state; + +/** + * Folder where policy files are stored. + */ +static char * policy_dir; + +/** + * Search strings. + */ +static char **search_strings; + +/** + * Number of search strings. + */ +static int num_search_strings; + +/** + * Number of peers found with search strings. + */ +static unsigned int peers_found; + +/** + * Search task identifier + */ +static GNUNET_SCHEDULER_TaskIdentifier search_task; + +/** + * Search timeout task identifier. + */ +static GNUNET_SCHEDULER_TaskIdentifier search_timeout_task; + +/** + * Search timeout in seconds. + */ +static struct GNUNET_TIME_Relative search_timeout = { 60000 }; + +/** + * How long do we wait before starting the search? + * Default: 1 m. + */ +static struct GNUNET_TIME_Relative search_delay = { 60000 }; + +/** + * File to log statistics to. + */ +static struct GNUNET_DISK_FileHandle *data_file; + +/** + * Filename to log statistics to. + */ +static char *data_filename; + +/** + * Maximal path compression length. + */ +static unsigned int max_path_compression; + +/** + * If we should distribute the search evenly throught all peers (each + * peer searches for a string) or if only one peer should search for + * all strings. + */ +static int no_distributed_search; + +/** + * Prefix used for regex announcing. We need to prefix the search + * strings with it, in order to find something. + */ +static char * regex_prefix; + + +/******************************************************************************/ +/****************************** DECLARATIONS ********************************/ +/******************************************************************************/ + + +/** + * Search callback function. + * + * @param cls Closure provided in GNUNET_REGEX_search. + * @param id Peer providing a regex that matches the string. + * @param get_path Path of the get request. + * @param get_path_length Lenght of get_path. + * @param put_path Path of the put request. + * @param put_path_length Length of the put_path. + */ +static void +regex_found_handler (void *cls, + const struct GNUNET_PeerIdentity *id, + const struct GNUNET_PeerIdentity *get_path, + unsigned int get_path_length, + const struct GNUNET_PeerIdentity *put_path, + unsigned int put_path_length); + + +/** + * DHT connect callback. + * + * @param cls internal peer id. + * @param op operation handle. + * @param ca_result connect adapter result. + * @param emsg error message. + */ +static void +dht_connect_cb (void *cls, struct GNUNET_TESTBED_Operation *op, + void *ca_result, const char *emsg); + +/** + * DHT connect adapter. + * + * @param cls not used. + * @param cfg configuration handle. + * + * @return + */ +static void * +dht_ca (void *cls, const struct GNUNET_CONFIGURATION_Handle *cfg); + + +/** + * Adapter function called to destroy a connection to + * the DHT service + * + * @param cls closure + * @param op_result service handle returned from the connect adapter + */ +static void +dht_da (void *cls, void *op_result); + + +/** + * Function called by testbed once we are connected to stats + * service. Get the statistics for the services of interest. + * + * @param cls the 'struct RegexPeer' for which we connected to stats + * @param op connect operation handle + * @param ca_result handle to stats service + * @param emsg error message on failure + */ +static void +stats_connect_cb (void *cls, + struct GNUNET_TESTBED_Operation *op, + void *ca_result, + const char *emsg); + + +/** + * Task to collect all statistics from all peers, will shutdown the + * profiler, when done. + * + * @param cls NULL + * @param tc the task context + */ +static void +do_collect_stats (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc); + + +/******************************************************************************/ +/******************************** SHUTDOWN **********************************/ +/******************************************************************************/ + + +/** + * Shutdown nicely + * + * @param cls NULL + * @param tc the task context + */ +static void +do_shutdown (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct DLLOperation *dll_op; + struct RegexPeer *peer; + unsigned int nhost; + unsigned int peer_cnt; + unsigned int search_str_cnt; + char output_buffer[512]; + size_t size; + + shutdown_task = GNUNET_SCHEDULER_NO_TASK; + if (GNUNET_SCHEDULER_NO_TASK != abort_task) + GNUNET_SCHEDULER_cancel (abort_task); + if (NULL != hc_handles) + { + for (nhost = 0; nhost < num_hosts; nhost++) + if (NULL != hc_handles[nhost]) + GNUNET_TESTBED_is_host_habitable_cancel (hc_handles[nhost]); + GNUNET_free (hc_handles); + hc_handles = NULL; + } + if (GNUNET_SCHEDULER_NO_TASK != register_hosts_task) + GNUNET_SCHEDULER_cancel (register_hosts_task); + + for (peer_cnt = 0; peer_cnt < num_peers; peer_cnt++) + { + peer = &peers[peer_cnt]; + + if (GNUNET_YES != peer->search_str_matched && NULL != data_file) + { + prof_time = GNUNET_TIME_absolute_get_duration (peer->prof_start_time); + size = + GNUNET_snprintf (output_buffer, + sizeof (output_buffer), + "%p Search string not found: %s (%d)\n%p On peer: %u (%p)\n%p With policy file: %s\n%p After: %s\n", + peer, peer->search_str, peer->search_str_matched, + peer, peer->id, peer, + peer, peer->policy_file, + peer, + GNUNET_STRINGS_relative_time_to_string (prof_time, + GNUNET_NO)); + if (size != GNUNET_DISK_file_write (data_file, output_buffer, size)) + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Unable to write to file!\n"); + } + + if (NULL != peers[peer_cnt].dht_op_handle) + GNUNET_TESTBED_operation_done (peers[peer_cnt].dht_op_handle); + if (NULL != peers[peer_cnt].stats_op_handle) + GNUNET_TESTBED_operation_done (peers[peer_cnt].stats_op_handle); + } + + if (NULL != data_file) + GNUNET_DISK_file_close (data_file); + + for (search_str_cnt = 0; + search_str_cnt < num_search_strings && NULL != search_strings; + search_str_cnt++) + { + GNUNET_free_non_null (search_strings[search_str_cnt]); + } + GNUNET_free_non_null (search_strings); + + if (NULL != reg_handle) + GNUNET_TESTBED_cancel_registration (reg_handle); + if (NULL != topology_op) + GNUNET_TESTBED_operation_done (topology_op); + for (nhost = 0; nhost < num_hosts; nhost++) + if (NULL != hosts[nhost]) + GNUNET_TESTBED_host_destroy (hosts[nhost]); + GNUNET_free_non_null (hosts); + + while (NULL != (dll_op = dll_op_head)) + { + GNUNET_TESTBED_operation_done (dll_op->op); + GNUNET_CONTAINER_DLL_remove (dll_op_head, dll_op_tail, dll_op); + GNUNET_free (dll_op); + } + if (NULL != mc) + GNUNET_TESTBED_controller_disconnect (mc); + if (NULL != mc_proc) + GNUNET_TESTBED_controller_stop (mc_proc); + if (NULL != cfg) + GNUNET_CONFIGURATION_destroy (cfg); + + GNUNET_SCHEDULER_shutdown (); /* Stop scheduler to shutdown testbed run */ +} + + +/** + * abort task to run on test timed out + * + * @param cls NULL + * @param tc the task context + */ +static void +do_abort (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + unsigned long i = (unsigned long) cls; + + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Aborting %lu...\n", i); + abort_task = GNUNET_SCHEDULER_NO_TASK; + result = GNUNET_SYSERR; + if (GNUNET_SCHEDULER_NO_TASK != shutdown_task) + GNUNET_SCHEDULER_cancel (shutdown_task); + shutdown_task = GNUNET_SCHEDULER_add_now (&do_shutdown, NULL); +} + + +/******************************************************************************/ +/********************* STATISTICS SERVICE CONNECTIONS ***********************/ +/******************************************************************************/ + +/** + * Adapter function called to establish a connection to + * statistics service. + * + * @param cls closure + * @param cfg configuration of the peer to connect to; will be available until + * GNUNET_TESTBED_operation_done() is called on the operation returned + * from GNUNET_TESTBED_service_connect() + * @return service handle to return in 'op_result', NULL on error + */ +static void * +stats_ca (void *cls, const struct GNUNET_CONFIGURATION_Handle *cfg) +{ + return GNUNET_STATISTICS_create ("", cfg); +} + + +/** + * Adapter function called to destroy a connection to + * statistics service. + * + * @param cls closure + * @param op_result service handle returned from the connect adapter + */ +static void +stats_da (void *cls, void *op_result) +{ + struct RegexPeer *peer = cls; + + GNUNET_assert (op_result == peer->stats_handle); + + GNUNET_STATISTICS_destroy (peer->stats_handle, GNUNET_NO); + peer->stats_handle = NULL; +} + + +/** + * Process statistic values. Write all values to global 'data_file', if present. + * + * @param cls closure + * @param subsystem name of subsystem that created the statistic + * @param name the name of the datum + * @param value the current value + * @param is_persistent GNUNET_YES if the value is persistent, GNUNET_NO if not + * @return GNUNET_OK to continue, GNUNET_SYSERR to abort iteration + */ +static int +stats_iterator (void *cls, const char *subsystem, const char *name, + uint64_t value, int is_persistent) +{ + struct RegexPeer *peer = cls; + char output_buffer[512]; + size_t size; + + if (NULL == data_file) + { + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + "%p -> %s [%s]: %llu\n", + peer, subsystem, name, value); + return GNUNET_OK; + } + size = + GNUNET_snprintf (output_buffer, + sizeof (output_buffer), + "%p [%s] %llu %s\n", + peer, + subsystem, value, name); + if (size != GNUNET_DISK_file_write (data_file, output_buffer, size)) + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Unable to write to file!\n"); + + return GNUNET_OK; +} + + +/** + * Stats callback. Finish the stats testbed operation and when all stats have + * been iterated, shutdown the profiler. + * + * @param cls closure + * @param success GNUNET_OK if statistics were + * successfully obtained, GNUNET_SYSERR if not. + */ +static void +stats_cb (void *cls, + int success) +{ + static unsigned int peer_cnt; + struct RegexPeer *peer = cls; + + if (GNUNET_OK != success) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Getting statistics for peer %u failed!\n", + peer->id); + return; + } + + GNUNET_assert (NULL != peer->stats_op_handle); + + GNUNET_TESTBED_operation_done (peer->stats_op_handle); + peer->stats_op_handle = NULL; + + peer_cnt++; + peer = &peers[peer_cnt]; + + if (peer_cnt == num_peers) + { + struct GNUNET_TIME_Relative delay = { 100 }; + shutdown_task = GNUNET_SCHEDULER_add_delayed (delay, &do_shutdown, NULL); + } + else + { + peer->stats_op_handle = + GNUNET_TESTBED_service_connect (NULL, + peer->peer_handle, + "statistics", + &stats_connect_cb, + peer, + &stats_ca, + &stats_da, + peer); + } +} + + +/** + * Function called by testbed once we are connected to stats + * service. Get the statistics for the services of interest. + * + * @param cls the 'struct RegexPeer' for which we connected to stats + * @param op connect operation handle + * @param ca_result handle to stats service + * @param emsg error message on failure + */ +static void +stats_connect_cb (void *cls, + struct GNUNET_TESTBED_Operation *op, + void *ca_result, + const char *emsg) +{ + struct RegexPeer *peer = cls; + + if (NULL == ca_result || NULL != emsg) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Failed to connect to statistics service on peer %u: %s\n", + peer->id, emsg); + + peer->stats_handle = NULL; + return; + } + + peer->stats_handle = ca_result; + + if (NULL == GNUNET_STATISTICS_get (peer->stats_handle, NULL, NULL, + GNUNET_TIME_UNIT_FOREVER_REL, + &stats_cb, + &stats_iterator, peer)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Could not get statistics of peer %u!\n", peer->id); + } +} + + +/** + * Task to collect all statistics from all peers, will shutdown the + * profiler, when done. + * + * @param cls NULL + * @param tc the task context + */ +static void +do_collect_stats (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct RegexPeer *peer = &peers[0]; + + GNUNET_assert (NULL != peer->peer_handle); + + peer->stats_op_handle = + GNUNET_TESTBED_service_connect (NULL, + peer->peer_handle, + "statistics", + &stats_connect_cb, + peer, + &stats_ca, + &stats_da, + peer); +} + + +/******************************************************************************/ +/************************ MESH SERVICE CONNECTIONS **************************/ +/******************************************************************************/ + +/** + * Method called when we've found a peer that announced a regex + * that matches our search string. Now get the statistics. + * + * @param cls Closure provided in GNUNET_REGEX_search. + * @param id Peer providing a regex that matches the string. + * @param get_path Path of the get request. + * @param get_path_length Lenght of get_path. + * @param put_path Path of the put request. + * @param put_path_length Length of the put_path. + */ +static void +regex_found_handler (void *cls, + const struct GNUNET_PeerIdentity *id, + const struct GNUNET_PeerIdentity *get_path, + unsigned int get_path_length, + const struct GNUNET_PeerIdentity *put_path, + unsigned int put_path_length) +{ + struct RegexPeer *peer = cls; + char output_buffer[512]; + size_t size; + + if (GNUNET_YES == peer->search_str_matched) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "String %s on peer %u already matched!\n", + peer->search_str, peer->id); + return; + } + + peers_found++; + + if (NULL == id) + { + // FIXME not possible right now + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + "String matching timed out for string %s on peer %u (%i/%i)\n", + peer->search_str, peer->id, peers_found, num_search_strings); + + printf ("String matching timed out for string %s on peer %u (%i/%i)\n", + peer->search_str, peer->id, peers_found, num_search_strings); + + peer->search_str_matched = GNUNET_SYSERR; + } + else + { + prof_time = GNUNET_TIME_absolute_get_duration (peer->prof_start_time); + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + "String %s successfully matched on peer %u after %s (%i/%i)\n", + peer->search_str, peer->id, GNUNET_STRINGS_relative_time_to_string (prof_time, GNUNET_NO), + peers_found, num_search_strings); + + printf ("String %s successfully matched on peer %u after %s (%i/%i)\n", + peer->search_str, peer->id, GNUNET_STRINGS_relative_time_to_string (prof_time, GNUNET_NO), + peers_found, num_search_strings); + fflush (stdout); + + peer->search_str_matched = GNUNET_YES; + + if (NULL != data_file) + { + size = + GNUNET_snprintf (output_buffer, + sizeof (output_buffer), + "%p Peer: %u\n%p Host: %s\n%p Policy file: %s\n" + "%p Search string: %s\n%p Search duration: %s\n\n", + peer, peer->id, + peer, + GNUNET_TESTBED_host_get_hostname (peer->host_handle), + peer, peer->policy_file, + peer, peer->search_str, + peer, + GNUNET_STRINGS_relative_time_to_string (prof_time, + GNUNET_NO)); + + if (size != GNUNET_DISK_file_write (data_file, output_buffer, size)) + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Unable to write to file!\n"); + } + } + + GNUNET_TESTBED_operation_done (peer->dht_op_handle); + peer->dht_op_handle = NULL; + + if (peers_found == num_search_strings) + { + prof_time = GNUNET_TIME_absolute_get_duration (prof_start_time); + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + "All strings successfully matched in %s\n", + GNUNET_STRINGS_relative_time_to_string (prof_time, GNUNET_NO)); + printf ("All strings successfully matched.\n"); + fflush (stdout); + + if (GNUNET_SCHEDULER_NO_TASK != search_timeout_task) + GNUNET_SCHEDULER_cancel (search_timeout_task); + + printf ("Collecting stats and shutting down.\n"); + GNUNET_SCHEDULER_add_now (&do_collect_stats, NULL); + } +} + + +/** + * Connect by string timeout task. This will cancel the profiler after the + * specified timeout 'search_timeout'. + * + * @param cls NULL + * @param tc the task context + */ +static void +do_connect_by_string_timeout (void *cls, + const struct GNUNET_SCHEDULER_TaskContext * tc) +{ + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + "Finding matches to all strings did not succeed after %s.\n", + GNUNET_STRINGS_relative_time_to_string (search_timeout, GNUNET_NO)); + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + "Found %i of %i strings\n", peers_found, num_search_strings); + + printf ("Search timed out after %s. Collecting stats and shutting down.\n", + GNUNET_STRINGS_relative_time_to_string (search_timeout, GNUNET_NO)); + fflush (stdout); + + GNUNET_SCHEDULER_add_now (&do_collect_stats, NULL); +} + + +/** + * Connect by string task that is run to search for a string in the + * NFA. It first connects to the mesh service and when a connection is + * established it starts to search for the string. + * + * @param cls NULL + * @param tc the task context + */ +static void +do_connect_by_string (void *cls, + const struct GNUNET_SCHEDULER_TaskContext * tc) +{ + printf ("Starting string search.\n"); + fflush (stdout); + + peers[0].search_str = search_strings[0]; + peers[0].search_str_matched = GNUNET_NO; + + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + "Searching for string \"%s\" on peer %d with file %s\n", + peers[0].search_str, 0, peers[0].policy_file); + + /* First connect to mesh service, then search for string. Next + connect will be in mesh_connect_cb */ + peers[0].dht_op_handle = + GNUNET_TESTBED_service_connect (NULL, + peers[0].peer_handle, + "dht", + &dht_connect_cb, + &peers[0], + &dht_ca, + &dht_da, + &peers[0]); + + search_timeout_task = GNUNET_SCHEDULER_add_delayed (search_timeout, + &do_connect_by_string_timeout, NULL); +} + +/** + * Start searching for the next string in the DHT. + * + * @param cls Index of the next peer in the peers array. + * @param tc TaskContext. + */ +void +find_next_string (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + long next_p = (long) cls; + + if (0 != (tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN)) + return; + + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + "Searching for string \"%s\" on peer %d with file %s\n", + peers[next_p].search_str, next_p, peers[next_p].policy_file); + + /* FIXME + * dont connect to a new dht for each peer, we might want to seach for n + * strings on m peers where n > m + */ + peers[next_p].dht_op_handle = + GNUNET_TESTBED_service_connect (NULL, + peers[next_p].peer_handle, + "dht", + &dht_connect_cb, + &peers[next_p], + &dht_ca, + &dht_da, + &peers[next_p]); +} + +/** + * DHT connect callback. Called when we are connected to the dht service for + * the peer in 'cls'. If successfull we connect to the stats service of this + * peer and then try to match the search string of this peer. + * + * @param cls internal peer id. + * @param op operation handle. + * @param ca_result connect adapter result. + * @param emsg error message. + */ +static void +dht_connect_cb (void *cls, struct GNUNET_TESTBED_Operation *op, + void *ca_result, const char *emsg) +{ + struct RegexPeer *peer = (struct RegexPeer *) cls; + static unsigned int peer_cnt; + unsigned int next_p; + + if (NULL != emsg || NULL == op || NULL == ca_result) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "DHT connect failed: %s\n", emsg); + GNUNET_abort (); + } + + GNUNET_assert (NULL != peer->dht_handle); + GNUNET_assert (peer->dht_op_handle == op); + GNUNET_assert (peer->dht_handle == ca_result); + + peer->search_str_matched = GNUNET_NO; + peer->search_handle = GNUNET_REGEX_search (peer->dht_handle, + peer->search_str, + ®ex_found_handler, peer, + NULL); + peer->prof_start_time = GNUNET_TIME_absolute_get (); + + if (peer_cnt < (num_search_strings - 1)) + { + if (GNUNET_YES == no_distributed_search) + next_p = 0; + else + next_p = (++peer_cnt % num_peers); + + peers[next_p].search_str = search_strings[next_p]; + peers[next_p].search_str_matched = GNUNET_NO; + + /* Don't start all searches at once */ + /* TODO add some intelligence to the timeout */ + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_SECONDS, + &find_next_string, + (void *) (long) next_p); + } +} + + +/** + * DHT connect adapter. Opens a connection to the dht service. + * + * @param cls Closure (peer). + * @param cfg Configuration handle. + * + * @return + */ +static void * +dht_ca (void *cls, const struct GNUNET_CONFIGURATION_Handle *cfg) +{ + struct RegexPeer *peer = cls; + + peer->dht_handle = GNUNET_DHT_connect (cfg, 32); + + return peer->dht_handle; +} + + +/** + * Adapter function called to destroy a connection to the dht service. + * + * @param cls Closure (peer). + * @param op_result Service handle returned from the connect adapter. + */ +static void +dht_da (void *cls, void *op_result) +{ + struct RegexPeer *peer = (struct RegexPeer *) cls; + + GNUNET_assert (peer->dht_handle == op_result); + + if (NULL != peer->search_handle) + { + GNUNET_REGEX_search_cancel (peer->search_handle); + peer->search_handle = NULL; + } + + if (NULL != peer->dht_handle) + { + GNUNET_DHT_disconnect (peer->dht_handle); + peer->dht_handle = NULL; + } +} + + +/******************************************************************************/ +/*************************** TESTBED PEER SETUP *****************************/ +/******************************************************************************/ + + +/** + * Configure the peer overlay topology. + * + * @param cls NULL + * @param tc the task context + */ +static void +do_configure_topology (void *cls, + const struct GNUNET_SCHEDULER_TaskContext * tc) +{ + /* + if (0 == linking_factor) + linking_factor = 1; + num_links = linking_factor * num_peers; + */ + /* num_links = num_peers - 1; */ + num_links = linking_factor; + + /* Do overlay connect */ + prof_start_time = GNUNET_TIME_absolute_get (); + topology_op = + GNUNET_TESTBED_overlay_configure_topology (NULL, num_peers, peer_handles, + NULL, + NULL, + NULL, + GNUNET_TESTBED_TOPOLOGY_ERDOS_RENYI, + num_links, + GNUNET_TESTBED_TOPOLOGY_RETRY_CNT, + (unsigned int) 0, + GNUNET_TESTBED_TOPOLOGY_OPTION_END); + if (NULL == topology_op) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Cannot create topology, op handle was NULL\n"); + GNUNET_assert (0); + } +} + + +/** + * Functions of this signature are called when a peer has been successfully + * started or stopped. + * + * @param cls the closure from GNUNET_TESTBED_peer_start/stop() + * @param emsg NULL on success; otherwise an error description + */ +static void +peer_churn_cb (void *cls, const char *emsg) +{ + struct DLLOperation *dll_op = cls; + struct GNUNET_TESTBED_Operation *op; + static unsigned int started_peers; + unsigned int peer_cnt; + + op = dll_op->op; + GNUNET_CONTAINER_DLL_remove (dll_op_head, dll_op_tail, dll_op); + GNUNET_free (dll_op); + if (NULL != emsg) + { + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + _("An operation has failed while starting peers\n")); + GNUNET_TESTBED_operation_done (op); + if (GNUNET_SCHEDULER_NO_TASK != abort_task) + GNUNET_SCHEDULER_cancel (abort_task); + abort_task = GNUNET_SCHEDULER_add_now (&do_abort, (void*) __LINE__); + return; + } + GNUNET_TESTBED_operation_done (op); + if (++started_peers == num_peers) + { + prof_time = GNUNET_TIME_absolute_get_duration (prof_start_time); + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + "All peers started successfully in %s\n", + GNUNET_STRINGS_relative_time_to_string (prof_time, GNUNET_NO)); + result = GNUNET_OK; + + peer_handles = GNUNET_malloc (sizeof (struct GNUNET_TESTBED_Peer *) * num_peers); + for (peer_cnt = 0; peer_cnt < num_peers; peer_cnt++) + peer_handles[peer_cnt] = peers[peer_cnt].peer_handle; + + state = STATE_PEERS_LINKING; + GNUNET_SCHEDULER_add_now (&do_configure_topology, NULL); + } +} + + +/** + * Functions of this signature are called when a peer has been successfully + * created + * + * @param cls the closure from GNUNET_TESTBED_peer_create() + * @param peer the handle for the created peer; NULL on any error during + * creation + * @param emsg NULL if peer is not NULL; else MAY contain the error description + */ +static void +peer_create_cb (void *cls, struct GNUNET_TESTBED_Peer *peer, const char *emsg) +{ + struct DLLOperation *dll_op = cls; + struct RegexPeer *peer_ptr; + static unsigned int created_peers; + unsigned int peer_cnt; + + if (NULL != emsg) + { + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + _("Creating a peer failed. Error: %s\n"), emsg); + GNUNET_TESTBED_operation_done (dll_op->op); + GNUNET_CONTAINER_DLL_remove (dll_op_head, dll_op_tail, dll_op); + GNUNET_free (dll_op); + if (GNUNET_SCHEDULER_NO_TASK != abort_task) + GNUNET_SCHEDULER_cancel (abort_task); + abort_task = GNUNET_SCHEDULER_add_now (&do_abort, (void*) __LINE__); + return; + } + + peer_ptr = dll_op->cls; + GNUNET_assert (NULL == peer_ptr->peer_handle); + GNUNET_CONFIGURATION_destroy (peer_ptr->cfg); + peer_ptr->cfg = NULL; + peer_ptr->peer_handle = peer; + GNUNET_TESTBED_operation_done (dll_op->op); + GNUNET_CONTAINER_DLL_remove (dll_op_head, dll_op_tail, dll_op); + GNUNET_free (dll_op); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Peer %i created on host %s\n", + peer_ptr->id, + GNUNET_TESTBED_host_get_hostname (peer_ptr->host_handle)); + + if (++created_peers == num_peers) + { + prof_time = GNUNET_TIME_absolute_get_duration (prof_start_time); + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + "All peers created successfully in %s\n", + GNUNET_STRINGS_relative_time_to_string (prof_time, GNUNET_NO)); + /* Now peers are to be started */ + state = STATE_PEERS_STARTING; + prof_start_time = GNUNET_TIME_absolute_get (); + for (peer_cnt = 0; peer_cnt < num_peers; peer_cnt++) + { + dll_op = GNUNET_malloc (sizeof (struct DLLOperation)); + dll_op->op = GNUNET_TESTBED_peer_start (dll_op, peers[peer_cnt].peer_handle, + &peer_churn_cb, dll_op); + GNUNET_CONTAINER_DLL_insert_tail (dll_op_head, dll_op_tail, dll_op); + } + } +} + + +/** + * Function called with a filename for each file in the policy directory. Create + * a peer for each filename and update the peer's configuration to include the + * max_path_compression specified as a command line argument as well as the + * policy_file for this peer. The gnunet-service-regexprofiler service is + * automatically started on this peer. The service reads the configurration and + * announces the regexes stored in the policy file 'filename'. + * + * @param cls closure + * @param filename complete filename (absolute path) + * @return GNUNET_OK to continue to iterate, + * GNUNET_SYSERR to abort iteration with error! + */ +static int +policy_filename_cb (void *cls, const char *filename) +{ + static unsigned int peer_cnt; + struct DLLOperation *dll_op; + struct RegexPeer *peer = &peers[peer_cnt]; + + GNUNET_assert (NULL != peer); + + peer->policy_file = GNUNET_strdup (filename); + + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Creating peer %i on host %s for policy file %s\n", + peer->id, + GNUNET_TESTBED_host_get_hostname (peer->host_handle), + filename); + + /* Set configuration options specific for this peer + (max_path_compression and policy_file */ + peer->cfg = GNUNET_CONFIGURATION_dup (cfg); + GNUNET_CONFIGURATION_set_value_number (peer->cfg, "REGEXPROFILER", + "MAX_PATH_COMPRESSION", + (unsigned long long)max_path_compression); + GNUNET_CONFIGURATION_set_value_string (peer->cfg, "REGEXPROFILER", + "POLICY_FILE", filename); + + dll_op = GNUNET_malloc (sizeof (struct DLLOperation)); + dll_op->cls = &peers[peer_cnt]; + dll_op->op = GNUNET_TESTBED_peer_create (mc, + peer->host_handle, + peer->cfg, + &peer_create_cb, + dll_op); + GNUNET_CONTAINER_DLL_insert_tail (dll_op_head, dll_op_tail, dll_op); + + peer_cnt++; + + return GNUNET_OK; +} + + +/** + * Controller event callback. + * + * @param cls NULL + * @param event the controller event + */ +static void +controller_event_cb (void *cls, + const struct GNUNET_TESTBED_EventInformation *event) +{ + struct DLLOperation *dll_op; + struct GNUNET_TESTBED_Operation *op; + int ret; + + switch (state) + { + case STATE_SLAVES_STARTING: + switch (event->type) + { + case GNUNET_TESTBED_ET_OPERATION_FINISHED: + { + static unsigned int slaves_started; + unsigned int peer_cnt; + + dll_op = event->details.operation_finished.op_cls; + GNUNET_CONTAINER_DLL_remove (dll_op_head, dll_op_tail, dll_op); + GNUNET_free (dll_op); + op = event->details.operation_finished.operation; + if (NULL != event->details.operation_finished.emsg) + { + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + _("An operation has failed while starting slaves\n")); + GNUNET_TESTBED_operation_done (op); + if (GNUNET_SCHEDULER_NO_TASK != abort_task) + GNUNET_SCHEDULER_cancel (abort_task); + abort_task = GNUNET_SCHEDULER_add_now (&do_abort, (void*) __LINE__); + return; + } + GNUNET_TESTBED_operation_done (op); + /* Proceed to start peers */ + if (++slaves_started == num_hosts - 1) + { + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + "All slaves started successfully\n"); + + state = STATE_PEERS_CREATING; + prof_start_time = GNUNET_TIME_absolute_get (); + + if (-1 == (ret = GNUNET_DISK_directory_scan (policy_dir, + NULL, + NULL))) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("No files found in `%s'\n"), + policy_dir); + GNUNET_SCHEDULER_shutdown (); + return; + } + num_peers = (unsigned int) ret; + peers = GNUNET_malloc (sizeof (struct RegexPeer) * num_peers); + + /* Initialize peers */ + for (peer_cnt = 0; peer_cnt < num_peers; peer_cnt++) + { + struct RegexPeer *peer = &peers[peer_cnt]; + peer->id = peer_cnt; + peer->policy_file = NULL; + /* Do not start peers on hosts[0] (master controller) */ + peer->host_handle = hosts[1 + (peer_cnt % (num_hosts -1))]; + peer->dht_handle = NULL; + peer->search_handle = NULL; + peer->stats_handle = NULL; + peer->stats_op_handle = NULL; + peer->search_str = NULL; + peer->search_str_matched = GNUNET_NO; + } + + GNUNET_DISK_directory_scan (policy_dir, + &policy_filename_cb, + NULL); + } + } + break; + default: + GNUNET_assert (0); + } + break; + case STATE_PEERS_STARTING: + switch (event->type) + { + case GNUNET_TESTBED_ET_OPERATION_FINISHED: + /* Control reaches here when peer start fails */ + case GNUNET_TESTBED_ET_PEER_START: + /* we handle peer starts in peer_churn_cb */ + break; + default: + GNUNET_assert (0); + } + break; + case STATE_PEERS_LINKING: + switch (event->type) + { + static unsigned int established_links; + case GNUNET_TESTBED_ET_OPERATION_FINISHED: + /* Control reaches here when a peer linking operation fails */ + if (NULL != event->details.operation_finished.emsg) + { + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + _("An operation has failed while linking\n")); + printf ("F"); + fflush (stdout); + retry_links++; + } + /* We do no retries, consider this link as established */ + /* break; */ + case GNUNET_TESTBED_ET_CONNECT: + { + char output_buffer[512]; + size_t size; + + if (0 == established_links) + printf ("Establishing links ."); + else + { + printf ("."); + fflush (stdout); + } + if (++established_links == num_links) + { + fflush (stdout); + prof_time = GNUNET_TIME_absolute_get_duration (prof_start_time); + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + "%u links established in %s\n", + num_links, + GNUNET_STRINGS_relative_time_to_string (prof_time, GNUNET_NO)); + result = GNUNET_OK; + GNUNET_free (peer_handles); + + if (NULL != data_file) + { + size = + GNUNET_snprintf (output_buffer, + sizeof (output_buffer), + "# of peers: %u\n# of links established: %u\n" + "Time to establish links: %s\nLinking failures: %u\n" + "path compression length: %u\n# of search strings: %u\n", + num_peers, + (established_links - cont_fails), + GNUNET_STRINGS_relative_time_to_string (prof_time, GNUNET_NO), + cont_fails, + max_path_compression, + num_search_strings); + + if (size != GNUNET_DISK_file_write (data_file, output_buffer, size)) + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Unable to write to file!\n"); + } + + printf ("\nWaiting %s before starting to search.\n", + GNUNET_STRINGS_relative_time_to_string (search_delay, GNUNET_YES)); + fflush (stdout); + + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + "Waiting %s before starting to search.\n", + GNUNET_STRINGS_relative_time_to_string (search_delay, GNUNET_NO)); + + state = STATE_SEARCH_REGEX; + + search_task = GNUNET_SCHEDULER_add_delayed (search_delay, + &do_connect_by_string, NULL); + } + } + break; + default: + GNUNET_assert (0); + } + break; + case STATE_SEARCH_REGEX: + { + /* Handled in service connect callback */ + break; + } + default: + switch (state) + { + case STATE_PEERS_CREATING: + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Failed to create peer\n"); + break; + default: + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Unexpected controller_cb with state %i!\n", state); + } + GNUNET_assert (0); + } +} + + +/** + * Task to register all hosts available in the global host list. + * + * @param cls NULL + * @param tc the scheduler task context + */ +static void +register_hosts (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc); + + +/** + * Callback which will be called to after a host registration succeeded or failed + * + * @param cls the closure + * @param emsg the error message; NULL if host registration is successful + */ +static void +host_registration_completion (void *cls, const char *emsg) +{ + reg_handle = NULL; + if (NULL != emsg) + { + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + _("Host registration failed for a host. Error: %s\n"), emsg); + if (GNUNET_SCHEDULER_NO_TASK != abort_task) + GNUNET_SCHEDULER_cancel (abort_task); + abort_task = GNUNET_SCHEDULER_add_now (&do_abort, (void*) __LINE__); + return; + } + register_hosts_task = GNUNET_SCHEDULER_add_now (®ister_hosts, NULL); +} + + +/** + * Task to register all hosts available in the global host list. + * + * @param cls NULL + * @param tc the scheduler task context + */ +static void +register_hosts (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct DLLOperation *dll_op; + static unsigned int reg_host; + unsigned int slave; + + register_hosts_task = GNUNET_SCHEDULER_NO_TASK; + if (reg_host == num_hosts - 1) + { + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + "All hosts successfully registered\n"); + /* Start slaves */ + state = STATE_SLAVES_STARTING; + for (slave = 1; slave < num_hosts; slave++) + { + dll_op = GNUNET_malloc (sizeof (struct DLLOperation)); + dll_op->op = GNUNET_TESTBED_controller_link (dll_op, + mc, + hosts[slave], + hosts[0], + cfg, + GNUNET_YES); + GNUNET_CONTAINER_DLL_insert_tail (dll_op_head, dll_op_tail, dll_op); + } + return; + } + reg_handle = GNUNET_TESTBED_register_host (mc, hosts[++reg_host], + host_registration_completion, + NULL); +} + + +/** + * Callback to signal successfull startup of the controller process. + * + * @param cls the closure from GNUNET_TESTBED_controller_start() + * @param config the configuration with which the controller has been started; + * NULL if status is not GNUNET_OK + * @param status GNUNET_OK if the startup is successfull; GNUNET_SYSERR if not, + * GNUNET_TESTBED_controller_stop() shouldn't be called in this case + */ +static void +status_cb (void *cls, const struct GNUNET_CONFIGURATION_Handle *config, int status) +{ + if (GNUNET_SCHEDULER_NO_TASK != abort_task) + GNUNET_SCHEDULER_cancel (abort_task); + if (GNUNET_OK != status) + { + mc_proc = NULL; + printf("CRAPPP\n"); + abort_task = GNUNET_SCHEDULER_add_now (&do_abort, (void*) __LINE__); + return; + } + event_mask = 0; + event_mask |= (1LL << GNUNET_TESTBED_ET_PEER_START); + event_mask |= (1LL << GNUNET_TESTBED_ET_PEER_STOP); + event_mask |= (1LL << GNUNET_TESTBED_ET_CONNECT); + event_mask |= (1LL << GNUNET_TESTBED_ET_DISCONNECT); + event_mask |= (1LL << GNUNET_TESTBED_ET_OPERATION_FINISHED); + mc = GNUNET_TESTBED_controller_connect (config, hosts[0], event_mask, + &controller_event_cb, NULL); + if (NULL == mc) + { + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + _("Unable to connect to master controller -- Check config\n")); + abort_task = GNUNET_SCHEDULER_add_now (&do_abort, (void*) __LINE__); + return; + } + register_hosts_task = GNUNET_SCHEDULER_add_now (®ister_hosts, NULL); + abort_task = GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, + &do_abort, (void*) __LINE__); +} + + +/** + * Load search strings from given filename. One search string per line. + * + * @param filename filename of the file containing the search strings. + * @param strings set of strings loaded from file. Caller needs to free this + * if number returned is greater than zero. + * @param limit upper limit on the number of strings read from the file + * @return number of strings found in the file. GNUNET_SYSERR on error. + */ +static int +load_search_strings (const char *filename, char ***strings, unsigned int limit) +{ + char *data; + char *buf; + uint64_t filesize; + unsigned int offset; + int str_cnt; + unsigned int i; + + if (NULL == filename) + { + return GNUNET_SYSERR; + } + + if (GNUNET_YES != GNUNET_DISK_file_test (filename)) + { + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + "Could not find search strings file %s\n", filename); + return GNUNET_SYSERR; + } + if (GNUNET_OK != GNUNET_DISK_file_size (filename, &filesize, GNUNET_YES, GNUNET_YES)) + filesize = 0; + if (0 == filesize) + { + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Search strings file %s is empty.\n", filename); + return GNUNET_SYSERR; + } + data = GNUNET_malloc (filesize); + if (filesize != GNUNET_DISK_fn_read (filename, data, filesize)) + { + GNUNET_free (data); + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Could not read search strings file %s.\n", + filename); + return GNUNET_SYSERR; + } + buf = data; + offset = 0; + str_cnt = 0; + while (offset < (filesize - 1) && str_cnt < limit) + { + offset++; + if (((data[offset] == '\n')) && (buf != &data[offset])) + { + data[offset] = '\0'; + str_cnt++; + buf = &data[offset + 1]; + } + else if ((data[offset] == '\n') || (data[offset] == '\0')) + buf = &data[offset + 1]; + } + *strings = GNUNET_malloc (sizeof (char *) * str_cnt); + offset = 0; + for (i = 0; i < str_cnt; i++) + { + GNUNET_asprintf (&(*strings)[i], "%s%s", regex_prefix, &data[offset]); + offset += strlen (&data[offset]) + 1; + } + GNUNET_free (data); + return str_cnt; +} + + +/** + * Callbacks of this type are called by GNUNET_TESTBED_is_host_habitable to + * inform whether the given host is habitable or not. The Handle returned by + * GNUNET_TESTBED_is_host_habitable() is invalid after this callback is called + * + * @param cls NULL + * @param host the host whose status is being reported; will be NULL if the host + * given to GNUNET_TESTBED_is_host_habitable() is NULL + * @param status GNUNET_YES if it is habitable; GNUNET_NO if not + */ +static void +host_habitable_cb (void *cls, const struct GNUNET_TESTBED_Host *host, int status) +{ + struct GNUNET_TESTBED_HostHabitableCheckHandle **hc_handle = cls; + static unsigned int hosts_checked; + + *hc_handle = NULL; + if (GNUNET_NO == status) + { + if ((NULL != host) && (NULL != GNUNET_TESTBED_host_get_hostname (host))) + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("Host %s cannot start testbed\n"), + GNUNET_TESTBED_host_get_hostname (host)); + else + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("Testbed cannot be started on localhost\n")); + GNUNET_SCHEDULER_cancel (abort_task); + abort_task = GNUNET_SCHEDULER_add_now (&do_abort, (void*) __LINE__); + return; + } + hosts_checked++; + /* printf (_("\rChecked %u hosts"), hosts_checked); */ + /* fflush (stdout); */ + if (hosts_checked < num_hosts) + return; + /* printf (_("\nAll hosts can start testbed. Creating peers\n")); */ + GNUNET_free (hc_handles); + hc_handles = NULL; + mc_proc = + GNUNET_TESTBED_controller_start (GNUNET_TESTBED_host_get_hostname + (hosts[0]), + hosts[0], + cfg, + status_cb, + NULL); +} + + +/** + * Main function that will be run by the scheduler. + * + * @param cls closure + * @param args remaining command-line arguments + * @param cfgfile name of the configuration file used (for saving, can be NULL!) + * @param config configuration + */ +static void +run (void *cls, char *const *args, const char *cfgfile, + const struct GNUNET_CONFIGURATION_Handle *config) +{ + unsigned int nhost; + unsigned int nsearchstrs; + + if (NULL == args[0]) + { + fprintf (stderr, _("No hosts-file specified on command line. Exiting.\n")); + return; + } + if (NULL == args[1]) + { + fprintf (stderr, _("No policy directory specified on command line. Exiting.\n")); + return; + } + num_hosts = GNUNET_TESTBED_hosts_load_from_file (args[0], &hosts); + if (0 == num_hosts) + { + fprintf (stderr, _("No hosts loaded. Need at least one host\n")); + return; + } + printf (_("Checking whether given hosts can start testbed. Please wait\n")); + hc_handles = GNUNET_malloc (sizeof (struct + GNUNET_TESTBED_HostHabitableCheckHandle *) + * num_hosts); + for (nhost = 0; nhost < num_hosts; nhost++) + { + if (NULL == (hc_handles[nhost] = GNUNET_TESTBED_is_host_habitable (hosts[nhost], config, + &host_habitable_cb, + &hc_handles[nhost]))) + { + GNUNET_break (0); + for (nhost = 0; nhost < num_hosts; nhost++) + if (NULL != hc_handles[nhost]) + GNUNET_TESTBED_is_host_habitable_cancel (hc_handles[nhost]); + GNUNET_free (hc_handles); + hc_handles = NULL; + break; + } + } + if (num_hosts != nhost) + { + fprintf (stderr, _("Exiting\n")); + shutdown_task = GNUNET_SCHEDULER_add_now (&do_shutdown, NULL); + return; + } + if (NULL == config) + { + fprintf (stderr, _("No configuration file given. Exiting\n")); + shutdown_task = GNUNET_SCHEDULER_add_now (&do_shutdown, NULL); + return; + } + + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_string (config, "REGEXPROFILER", "REGEX_PREFIX", + ®ex_prefix)) + { + fprintf (stderr, _("Configuration option (regex_prefix) missing. Exiting\n")); + shutdown_task = GNUNET_SCHEDULER_add_now (&do_shutdown, NULL); + return; + } + + if ( (NULL != data_filename) && + (NULL == (data_file = + GNUNET_DISK_file_open (data_filename, + GNUNET_DISK_OPEN_READWRITE | + GNUNET_DISK_OPEN_TRUNCATE | + GNUNET_DISK_OPEN_CREATE, + GNUNET_DISK_PERM_USER_READ | + GNUNET_DISK_PERM_USER_WRITE))) ) + GNUNET_log_strerror_file (GNUNET_ERROR_TYPE_ERROR, + "open", + data_filename); + if (GNUNET_YES != GNUNET_DISK_directory_test (args[1], GNUNET_YES)) + { + fprintf (stderr, _("Specified policies directory does not exist. Exiting.\n")); + shutdown_task = GNUNET_SCHEDULER_add_now (&do_shutdown, NULL); + return; + } + policy_dir = args[1]; + if (GNUNET_YES != GNUNET_DISK_file_test (args[2])) + { + fprintf (stderr, _("No search strings file given. Exiting.\n")); + shutdown_task = GNUNET_SCHEDULER_add_now (&do_shutdown, NULL); + return; + } + nsearchstrs = load_search_strings (args[2], &search_strings, num_search_strings); + if (num_search_strings != nsearchstrs) + { + num_search_strings = nsearchstrs; + fprintf (stderr, _("Error loading search strings. Given file does not contain enough strings. Exiting.\n")); + shutdown_task = GNUNET_SCHEDULER_add_now (&do_shutdown, NULL); + return; + } + if (0 >= num_search_strings || NULL == search_strings) + { + fprintf (stderr, _("Error loading search strings. Exiting.\n")); + shutdown_task = GNUNET_SCHEDULER_add_now (&do_shutdown, NULL); + return; + } + unsigned int i; + for (i = 0; i < num_search_strings; i++) + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "search string: %s\n", search_strings[i]); + cfg = GNUNET_CONFIGURATION_dup (config); + abort_task = + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply + (GNUNET_TIME_UNIT_SECONDS, 5), &do_abort, + (void*) __LINE__); +} + + +/** + * Main function. + * + * @param argc argument count + * @param argv argument values + * @return 0 on success + */ +int +main (int argc, char *const *argv) +{ + static const struct GNUNET_GETOPT_CommandLineOption options[] = { + {'d', "details", "FILENAME", + gettext_noop ("name of the file for writing statistics"), + 1, &GNUNET_GETOPT_set_string, &data_filename}, + {'n', "num-links", "COUNT", + gettext_noop ("create COUNT number of random links between peers"), + GNUNET_YES, &GNUNET_GETOPT_set_uint, &linking_factor }, + {'t', "matching-timeout", "TIMEOUT", + gettext_noop ("wait TIMEOUT before considering a string match as failed"), + GNUNET_YES, &GNUNET_GETOPT_set_relative_time, &search_timeout }, + {'s', "search-delay", "DELAY", + gettext_noop ("wait DELAY before starting string search"), + GNUNET_YES, &GNUNET_GETOPT_set_relative_time, &search_delay }, + {'a', "num-search-strings", "COUNT", + gettext_noop ("number of search strings to read from search strings file"), + GNUNET_YES, &GNUNET_GETOPT_set_uint, &num_search_strings }, + {'p', "max-path-compression", "MAX_PATH_COMPRESSION", + gettext_noop ("maximum path compression length"), + 1, &GNUNET_GETOPT_set_uint, &max_path_compression}, + {'i', "no-distributed-search", "", + gettext_noop ("if this option is set, only one peer is responsible for searching all strings"), + 0, &GNUNET_GETOPT_set_one, &no_distributed_search}, + GNUNET_GETOPT_OPTION_END + }; + int ret; + + if (GNUNET_OK != GNUNET_STRINGS_get_utf8_args (argc, argv, &argc, &argv)) + return 2; + + result = GNUNET_SYSERR; + ret = + GNUNET_PROGRAM_run (argc, argv, + "gnunet-regex-profiler [OPTIONS] hosts-file policy-dir search-strings-file", + _("Profiler for regex"), + options, &run, NULL); + + if (GNUNET_OK != ret) + return ret; + if (GNUNET_OK != result) + return 1; + return 0; +} diff --git a/src/regex/gnunet-regex-simulation-profiler.c b/src/regex/gnunet-regex-simulation-profiler.c new file mode 100644 index 0000000..32b09ea --- /dev/null +++ b/src/regex/gnunet-regex-simulation-profiler.c @@ -0,0 +1,711 @@ +/* + This file is part of GNUnet. + (C) 2011, 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @file regex/gnunet-regex-simulation-profiler.c + * @brief Regex profiler that dumps all DFAs into a database instead of + * using the DHT (with mesh). + * @author Maximilian Szengel + * + */ + +#include "platform.h" +#include "gnunet_util_lib.h" +#include "gnunet_regex_lib.h" +#include "gnunet_mysql_lib.h" +#include + +/** + * MySQL statement to insert an edge. + */ +#define INSERT_EDGE_STMT "INSERT IGNORE INTO `%s` "\ + "(`key`, `label`, `to_key`, `accepting`) "\ + "VALUES (?, ?, ?, ?);" + +/** + * MySQL statement to select a key count. + */ +#define SELECT_KEY_STMT "SELECT COUNT(*) FROM `%s` "\ + "WHERE `key` = ? AND `label` = ?;" + +/** + * Simple struct to keep track of progress, and print a + * nice little percentage meter for long running tasks. + */ +struct ProgressMeter +{ + /** + * Total number of elements. + */ + unsigned int total; + + /** + * Intervall for printing percentage. + */ + unsigned int modnum; + + /** + * Number of dots to print. + */ + unsigned int dotnum; + + /** + * Completed number. + */ + unsigned int completed; + + /** + * Should the meter be printed? + */ + int print; + + /** + * String to print on startup. + */ + char *startup_string; +}; + + +/** + * Handle for the progress meter + */ +static struct ProgressMeter *meter; + +/** + * Abort task identifier. + */ +static GNUNET_SCHEDULER_TaskIdentifier abort_task; + +/** + * Shutdown task identifier. + */ +static GNUNET_SCHEDULER_TaskIdentifier shutdown_task; + +/** + * Scan task identifier; + */ +static GNUNET_SCHEDULER_TaskIdentifier scan_task; + +/** + * Global testing status. + */ +static int result; + +/** + * MySQL context. + */ +static struct GNUNET_MYSQL_Context *mysql_ctx; + +/** + * MySQL prepared statement handle. + */ +static struct GNUNET_MYSQL_StatementHandle *stmt_handle; + +/** + * MySQL prepared statement handle for `key` select. + */ +static struct GNUNET_MYSQL_StatementHandle *select_stmt_handle; + +/** + * MySQL table name. + */ +static char *table_name; + +/** + * Policy dir containing files that contain policies. + */ +static char *policy_dir; + +/** + * Number of policy files. + */ +static unsigned int num_policy_files; + +/** + * Number of policies. + */ +static unsigned int num_policies; + +/** + * Maximal path compression length. + */ +static unsigned int max_path_compression; + +/** + * Number of merged transitions. + */ +static unsigned long long num_merged_transitions; + +/** + * Number of merged states from different policies. + */ +static unsigned long long num_merged_states; + +/** + * Prefix to add before every regex we're announcing. + */ +static char *regex_prefix; + + +/** + * Create a meter to keep track of the progress of some task. + * + * @param total the total number of items to complete + * @param start_string a string to prefix the meter with (if printing) + * @param print GNUNET_YES to print the meter, GNUNET_NO to count + * internally only + * + * @return the progress meter + */ +static struct ProgressMeter * +create_meter (unsigned int total, char *start_string, int print) +{ + struct ProgressMeter *ret; + + ret = GNUNET_malloc (sizeof (struct ProgressMeter)); + ret->print = print; + ret->total = total; + ret->modnum = total / 4; + if (ret->modnum == 0) /* Divide by zero check */ + ret->modnum = 1; + ret->dotnum = (total / 50) + 1; + if (start_string != NULL) + ret->startup_string = GNUNET_strdup (start_string); + else + ret->startup_string = GNUNET_strdup (""); + + return ret; +} + + +/** + * Update progress meter (increment by one). + * + * @param meter the meter to update and print info for + * + * @return GNUNET_YES if called the total requested, + * GNUNET_NO if more items expected + */ +static int +update_meter (struct ProgressMeter *meter) +{ + if (meter->print == GNUNET_YES) + { + if (meter->completed % meter->modnum == 0) + { + if (meter->completed == 0) + { + FPRINTF (stdout, "%sProgress: [0%%", meter->startup_string); + } + else + FPRINTF (stdout, "%d%%", + (int) (((float) meter->completed / meter->total) * 100)); + } + else if (meter->completed % meter->dotnum == 0) + FPRINTF (stdout, "%s", "."); + + if (meter->completed + 1 == meter->total) + FPRINTF (stdout, "%d%%]\n", 100); + fflush (stdout); + } + meter->completed++; + + if (meter->completed == meter->total) + return GNUNET_YES; + if (meter->completed > meter->total) + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Progress meter overflow!!\n"); + return GNUNET_NO; +} + + +/** + * Reset progress meter. + * + * @param meter the meter to reset + * + * @return GNUNET_YES if meter reset, + * GNUNET_SYSERR on error + */ +static int +reset_meter (struct ProgressMeter *meter) +{ + if (meter == NULL) + return GNUNET_SYSERR; + + meter->completed = 0; + return GNUNET_YES; +} + + +/** + * Release resources for meter + * + * @param meter the meter to free + */ +static void +free_meter (struct ProgressMeter *meter) +{ + GNUNET_free_non_null (meter->startup_string); + GNUNET_free (meter); +} + + +/** + * Shutdown task. + * + * @param cls NULL + * @param tc the task context + */ +static void +do_shutdown (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + shutdown_task = GNUNET_SCHEDULER_NO_TASK; + if (GNUNET_SCHEDULER_NO_TASK != abort_task) + GNUNET_SCHEDULER_cancel (abort_task); + if (NULL != mysql_ctx) + GNUNET_MYSQL_context_destroy (mysql_ctx); + if (NULL != meter) + free_meter (meter); + + GNUNET_SCHEDULER_shutdown (); /* Stop scheduler to shutdown testbed run */ +} + + +/** + * abort task to run on test timed out + * + * @param cls NULL + * @param tc the task context + */ +static void +do_abort (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Aborting\n"); + abort_task = GNUNET_SCHEDULER_NO_TASK; + GNUNET_SCHEDULER_cancel (scan_task); + scan_task = GNUNET_SCHEDULER_NO_TASK; + result = GNUNET_SYSERR; + GNUNET_SCHEDULER_add_now (&do_shutdown, NULL); +} + + +/** + * Dummy function for prepared select. Always return GNUNET_OK. + * + * @param cls closure + * @param num_values number of values. + * @param values returned values from select stmt. + * + * @return GNUNET_OK + */ +static int +return_ok (void *cls, unsigned int num_values, MYSQL_BIND * values) +{ + return GNUNET_OK; +} + + +/** + * Iterator over all states that inserts each state into the MySQL db. + * + * @param cls closure. + * @param key hash for current state. + * @param proof proof for current state. + * @param accepting GNUNET_YES if this is an accepting state, GNUNET_NO if not. + * @param num_edges number of edges leaving current state. + * @param edges edges leaving current state. + */ +static void +regex_iterator (void *cls, const struct GNUNET_HashCode *key, const char *proof, + int accepting, unsigned int num_edges, + const struct GNUNET_REGEX_Edge *edges) +{ + unsigned int i; + int result; + unsigned long k_length; + unsigned long e_length; + unsigned long d_length; + MYSQL_BIND rbind[1]; + unsigned long long total; + + GNUNET_assert (NULL != mysql_ctx); + + for (i = 0; i < num_edges; i++) + { + k_length = sizeof (struct GNUNET_HashCode); + e_length = strlen (edges[i].label); + d_length = sizeof (struct GNUNET_HashCode); + memset (rbind, 0, sizeof (rbind)); + total = -1; + rbind[0].buffer_type = MYSQL_TYPE_LONGLONG; + rbind[0].buffer = &total; + rbind[0].is_unsigned = GNUNET_YES; + + result = + GNUNET_MYSQL_statement_run_prepared_select (mysql_ctx, + select_stmt_handle, 1, + rbind, &return_ok, NULL, + MYSQL_TYPE_BLOB, key, + sizeof (struct + GNUNET_HashCode), + &k_length, + MYSQL_TYPE_STRING, + edges[i].label, + strlen (edges[i].label), + &e_length, -1); + + if (GNUNET_SYSERR == result) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Error executing prepared mysql select statement\n"); + GNUNET_SCHEDULER_add_now (&do_abort, NULL); + return; + } + + if (-1 != total && total > 0) + { + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Total: %llu (%s, %s)\n", total, + GNUNET_h2s (key), edges[i].label); + } + + result = + GNUNET_MYSQL_statement_run_prepared (mysql_ctx, stmt_handle, NULL, + MYSQL_TYPE_BLOB, key, + sizeof (struct GNUNET_HashCode), + &k_length, MYSQL_TYPE_STRING, + edges[i].label, + strlen (edges[i].label), &e_length, + MYSQL_TYPE_BLOB, + &edges[i].destination, + sizeof (struct GNUNET_HashCode), + &d_length, MYSQL_TYPE_LONG, + &accepting, GNUNET_YES, -1); + + if (0 == result) + { + char *key_str = GNUNET_strdup (GNUNET_h2s (key)); + char *to_key_str = GNUNET_strdup (GNUNET_h2s (&edges[i].destination)); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Merged (%s, %s, %s, %i)\n", key_str, + edges[i].label, to_key_str, accepting); + GNUNET_free (key_str); + GNUNET_free (to_key_str); + num_merged_transitions++; + } + else if (-1 != total) + { + num_merged_states++; + } + + if (GNUNET_SYSERR == result || (1 != result && 0 != result)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Error executing prepared mysql statement for edge: Affected rows: %i, expected 0 or 1!\n", + result); + GNUNET_SCHEDULER_add_now (&do_abort, NULL); + } + } + + if (0 == num_edges) + { + k_length = sizeof (struct GNUNET_HashCode); + e_length = 0; + d_length = 0; + + result = + GNUNET_MYSQL_statement_run_prepared (mysql_ctx, stmt_handle, NULL, + MYSQL_TYPE_BLOB, key, + sizeof (struct GNUNET_HashCode), + &k_length, MYSQL_TYPE_STRING, NULL, + 0, &e_length, MYSQL_TYPE_BLOB, + NULL, 0, &d_length, + MYSQL_TYPE_LONG, &accepting, + GNUNET_YES, -1); + + if (1 != result && 0 != result) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Error executing prepared mysql statement for edge: Affected rows: %i, expected 0 or 1!\n", + result); + GNUNET_SCHEDULER_add_now (&do_abort, NULL); + } + } +} + + +/** + * Announce a regex by creating the DFA and iterating over each state, inserting + * each state into a MySQL database. + * + * @param regex regular expression. + * @return GNUNET_OK on success, GNUNET_SYSERR on failure. + */ +static int +announce_regex (const char *regex) +{ + struct GNUNET_REGEX_Automaton *dfa; + + dfa = + GNUNET_REGEX_construct_dfa (regex, strlen (regex), max_path_compression); + + if (NULL == dfa) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Failed to create DFA for regex %s\n", + regex); + abort_task = GNUNET_SCHEDULER_add_now (&do_abort, NULL); + return GNUNET_SYSERR; + } + + GNUNET_REGEX_iterate_all_edges (dfa, ®ex_iterator, NULL); + + GNUNET_REGEX_automaton_destroy (dfa); + + return GNUNET_OK; +} + + +/** + * Function called with a filename. + * + * @param cls closure + * @param filename complete filename (absolute path) + * @return GNUNET_OK to continue to iterate, + * GNUNET_SYSERR to abort iteration with error! + */ +int +policy_filename_cb (void *cls, const char *filename) +{ + char *regex; + char *data; + char *buf; + uint64_t filesize; + unsigned int offset; + + GNUNET_assert (NULL != filename); + + GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Announcing regexes from file %s\n", + filename); + + if (GNUNET_YES != GNUNET_DISK_file_test (filename)) + { + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Could not find policy file %s\n", + filename); + return GNUNET_OK; + } + if (GNUNET_OK != + GNUNET_DISK_file_size (filename, &filesize, GNUNET_YES, GNUNET_YES)) + filesize = 0; + if (0 == filesize) + { + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Policy file %s is empty.\n", + filename); + return GNUNET_OK; + } + data = GNUNET_malloc (filesize); + if (filesize != GNUNET_DISK_fn_read (filename, data, filesize)) + { + GNUNET_free (data); + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Could not read policy file %s.\n", + filename); + return GNUNET_OK; + } + + update_meter (meter); + + buf = data; + offset = 0; + regex = NULL; + while (offset < (filesize - 1)) + { + offset++; + if (((data[offset] == '\n')) && (buf != &data[offset])) + { + data[offset] = '|'; + num_policies++; + buf = &data[offset + 1]; + } + else if ((data[offset] == '\n') || (data[offset] == '\0')) + buf = &data[offset + 1]; + } + data[offset] = '\0'; + GNUNET_asprintf (®ex, "%s(%s)", regex_prefix, data); + GNUNET_assert (NULL != regex); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Announcing regex: %s\n", regex); + + if (GNUNET_OK != announce_regex (regex)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Could not announce regex %s\n", + regex); + } + GNUNET_free (regex); + GNUNET_free (data); + return GNUNET_OK; +} + + +/** + * Iterate over files contained in policy_dir. + * + * @param cls NULL + * @param tc the task context + */ +static void +do_directory_scan (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct GNUNET_TIME_Absolute start_time; + struct GNUNET_TIME_Relative duration; + char *stmt; + + /* Create an MySQL prepared statement for the inserts */ + GNUNET_asprintf (&stmt, INSERT_EDGE_STMT, table_name); + stmt_handle = GNUNET_MYSQL_statement_prepare (mysql_ctx, stmt); + GNUNET_free (stmt); + + GNUNET_asprintf (&stmt, SELECT_KEY_STMT, table_name); + select_stmt_handle = GNUNET_MYSQL_statement_prepare (mysql_ctx, stmt); + GNUNET_free (stmt); + + GNUNET_assert (NULL != stmt_handle); + + meter = + create_meter (num_policy_files, "Announcing policy files\n", GNUNET_YES); + start_time = GNUNET_TIME_absolute_get (); + GNUNET_DISK_directory_scan (policy_dir, &policy_filename_cb, stmt_handle); + duration = GNUNET_TIME_absolute_get_duration (start_time); + reset_meter (meter); + free_meter (meter); + meter = NULL; + + printf ("Announced %u files containing %u policies in %s\n" + "Duplicate transitions: %llu\nMerged states: %llu\n", + num_policy_files, num_policies, + GNUNET_STRINGS_relative_time_to_string (duration, GNUNET_NO), + num_merged_transitions, num_merged_states); + + result = GNUNET_OK; + shutdown_task = GNUNET_SCHEDULER_add_now (&do_shutdown, NULL); +} + + +/** + * Main function that will be run by the scheduler. + * + * @param cls closure + * @param args remaining command-line arguments + * @param cfgfile name of the configuration file used (for saving, can be NULL!) + * @param config configuration + */ +static void +run (void *cls, char *const *args, const char *cfgfile, + const struct GNUNET_CONFIGURATION_Handle *config) +{ + if (NULL == args[0]) + { + fprintf (stderr, + _("No policy directory specified on command line. Exiting.\n")); + result = GNUNET_SYSERR; + return; + } + if (GNUNET_YES != GNUNET_DISK_directory_test (args[0], GNUNET_YES)) + { + fprintf (stderr, + _("Specified policies directory does not exist. Exiting.\n")); + result = GNUNET_SYSERR; + return; + } + policy_dir = args[0]; + + num_policy_files = GNUNET_DISK_directory_scan (policy_dir, NULL, NULL); + meter = NULL; + + if (NULL == table_name) + { + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + "No table name specified, using default \"NFA\".\n"); + table_name = "NFA"; + } + + mysql_ctx = GNUNET_MYSQL_context_create (config, "regex-mysql"); + if (NULL == mysql_ctx) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Failed to create mysql context\n"); + result = GNUNET_SYSERR; + return; + } + + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_string (config, "regex-mysql", + "REGEX_PREFIX", ®ex_prefix)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _ + ("%s service is lacking key configuration settings (%s). Exiting.\n"), + "regexprofiler", "regex_prefix"); + result = GNUNET_SYSERR; + return; + } + + + result = GNUNET_OK; + + scan_task = GNUNET_SCHEDULER_add_now (&do_directory_scan, NULL); + + /* Scheduled the task to clean up when shutdown is called */ + shutdown_task = + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, &do_shutdown, + NULL); +} + + +/** + * Main function. + * + * @param argc argument count + * @param argv argument values + * @return 0 on success + */ +int +main (int argc, char *const *argv) +{ + static const struct GNUNET_GETOPT_CommandLineOption options[] = { + {'t', "table", "TABLENAME", + gettext_noop ("name of the table to write DFAs"), + 1, &GNUNET_GETOPT_set_string, &table_name}, + {'p', "max-path-compression", "MAX_PATH_COMPRESSION", + gettext_noop ("maximum path compression length"), + 1, &GNUNET_GETOPT_set_uint, &max_path_compression}, + GNUNET_GETOPT_OPTION_END + }; + int ret; + + if (GNUNET_OK != GNUNET_STRINGS_get_utf8_args (argc, argv, &argc, &argv)) + return 2; + + result = GNUNET_SYSERR; + ret = + GNUNET_PROGRAM_run (argc, argv, + "gnunet-regex-simulationprofiler [OPTIONS] policy-dir", + _("Profiler for regex library"), options, &run, NULL); + if (GNUNET_OK != ret) + return ret; + if (GNUNET_OK != result) + return 1; + return 0; +} diff --git a/src/regex/perf-regex.c b/src/regex/perf-regex.c new file mode 100644 index 0000000..45642db --- /dev/null +++ b/src/regex/perf-regex.c @@ -0,0 +1,87 @@ +/* + This file is part of GNUnet. + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @file src/regex/prof-regex.c + * @brief Test how long it takes to create a automaton from a string regex. + * @author Bartlomiej Polot + */ +#include +#include +#include "platform.h" +#include "gnunet_regex_lib.h" +#include "regex_test_lib.h" + +static const char *exe; + +static void +usage(void) +{ + fprintf (stderr, "Usage: %s REGEX_FILE COMPRESSION\n", exe); +} + +/** + * The main function to obtain peer information. + * + * @param argc number of arguments from the command line + * @param argv command line arguments + * @return 0 ok, 1 on error + */ +int +main (int argc, char *const *argv) +{ + struct GNUNET_REGEX_Automaton* dfa; + char **regexes; + char *buffer; + char *regex; + int compression; + long size; + + GNUNET_log_setup ("perf-regex", "DEBUG", NULL); + exe = argv[0]; + if (3 != argc) + { + usage(); + return 1; + } + regexes = GNUNET_REGEX_read_from_file (argv[1]); + + if (NULL == regexes) + { + usage(); + return 2; + } + buffer = GNUNET_REGEX_combine (regexes); + + GNUNET_asprintf (®ex, "GNVPN-0001-PAD(%s)(0|1)*", buffer); + size = strlen (regex); + + // fprintf (stderr, "Combined regex (%ld bytes):\n%s\n", size, regex); + // return 0; + + compression = atoi (argv[2]); + dfa = GNUNET_REGEX_construct_dfa (regex, size, compression); + GNUNET_REGEX_automaton_destroy (dfa); + GNUNET_free (buffer); + GNUNET_REGEX_free_from_file (regexes); + return 0; +} + +/* end of prof-regex.c */ diff --git a/src/regex/plugin_block_regex.c b/src/regex/plugin_block_regex.c new file mode 100644 index 0000000..d3c9735 --- /dev/null +++ b/src/regex/plugin_block_regex.c @@ -0,0 +1,256 @@ +/* + This file is part of GNUnet + (C) 2013 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @file regex/plugin_block_regex.c + * @brief blocks used for regex storage and search + * @author Bartlomiej Polot + */ + +#include "platform.h" +#include "gnunet_block_plugin.h" +#include "block_regex.h" +#include "regex_block_lib.h" + +/** + * Number of bits we set per entry in the bloomfilter. + * Do not change! + */ +#define BLOOMFILTER_K 16 + + +/** + * Show debug info about outgoing edges from a block. + * + * @param cls Closure (uunsed). + * @param token Edge label. + * @param len Length of @c token. + * @param key Block the edge point to. + * + * @return GNUNET_YES to keep iterating. + */ +static int +rdebug (void *cls, + const char *token, + size_t len, + const struct GNUNET_HashCode *key) +{ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " %s: %.*s\n", + GNUNET_h2s (key), len, token); + return GNUNET_YES; +} + + +/** + * Function called to validate a reply or a request. For + * request evaluation, simply pass "NULL" for the reply_block. + * Note that it is assumed that the reply has already been + * matched to the key (and signatures checked) as it would + * be done with the "get_key" function. + * + * @param cls closure + * @param type block type + * @param query original query (hash) + * @param bf pointer to bloom filter associated with query; possibly updated (!) + * @param bf_mutator mutation value for bf + * @param xquery extrended query data (can be NULL, depending on type) + * @param xquery_size number of bytes in xquery + * @param reply_block response to validate + * @param reply_block_size number of bytes in reply block + * @return characterization of result + */ +static enum GNUNET_BLOCK_EvaluationResult +block_plugin_regex_evaluate (void *cls, enum GNUNET_BLOCK_Type type, + const struct GNUNET_HashCode * query, + struct GNUNET_CONTAINER_BloomFilter **bf, + int32_t bf_mutator, const void *xquery, + size_t xquery_size, const void *reply_block, + size_t reply_block_size) +{ + struct GNUNET_HashCode chash; + struct GNUNET_HashCode mhash; + + switch (type) + { + case GNUNET_BLOCK_TYPE_REGEX: + if (NULL == reply_block) + return GNUNET_BLOCK_EVALUATION_REQUEST_VALID; + if (0 != xquery_size) + { + const char *query; + + query = (const char *) xquery; + if ('\0' != query[xquery_size - 1]) /* must be valid string */ + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Block xquery not a valid string\n"); + return GNUNET_BLOCK_EVALUATION_RESULT_INVALID; + } + } + else + { + const struct RegexBlock *rblock = reply_block; + + GNUNET_break_op (0); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Block with no xquery\n"); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " key: %s, %u edges\n", + GNUNET_h2s (&rblock->key), ntohl (rblock->n_edges)); + GNUNET_REGEX_block_iterate (rblock, reply_block_size, &rdebug, NULL); + return GNUNET_BLOCK_EVALUATION_RESULT_INVALID; + } + switch (GNUNET_REGEX_block_check (reply_block, + reply_block_size, + xquery)) + { + case GNUNET_SYSERR: + GNUNET_break_op(0); + return GNUNET_BLOCK_EVALUATION_RESULT_INVALID; + case GNUNET_NO: + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "BLOCK XQUERY %s not accepted\n", xquery); + return GNUNET_BLOCK_EVALUATION_RESULT_IRRELEVANT; + default: + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "BLOCK XQUERY %s accepted\n", xquery); + break; + } + if (NULL != bf) + { + GNUNET_CRYPTO_hash (reply_block, reply_block_size, &chash); + GNUNET_BLOCK_mingle_hash (&chash, bf_mutator, &mhash); + if (NULL != *bf) + { + if (GNUNET_YES == GNUNET_CONTAINER_bloomfilter_test (*bf, &mhash)) + return GNUNET_BLOCK_EVALUATION_OK_DUPLICATE; + } + else + { + *bf = GNUNET_CONTAINER_bloomfilter_init (NULL, 8, BLOOMFILTER_K); + } + GNUNET_CONTAINER_bloomfilter_add (*bf, &mhash); + } + return GNUNET_BLOCK_EVALUATION_OK_MORE; + + + case GNUNET_BLOCK_TYPE_REGEX_ACCEPT: + if (0 != xquery_size) + { + GNUNET_break_op (0); + return GNUNET_BLOCK_EVALUATION_REQUEST_INVALID; + } + if (NULL == reply_block) + return GNUNET_BLOCK_EVALUATION_REQUEST_VALID; + if (sizeof (struct RegexAccept) != reply_block_size) + { + GNUNET_break_op(0); + return GNUNET_BLOCK_EVALUATION_RESULT_INVALID; + } + if (NULL != bf) + { + GNUNET_CRYPTO_hash (reply_block, reply_block_size, &chash); + GNUNET_BLOCK_mingle_hash (&chash, bf_mutator, &mhash); + if (NULL != *bf) + { + if (GNUNET_YES == GNUNET_CONTAINER_bloomfilter_test (*bf, &mhash)) + return GNUNET_BLOCK_EVALUATION_OK_DUPLICATE; + } + else + { + *bf = GNUNET_CONTAINER_bloomfilter_init (NULL, 8, BLOOMFILTER_K); + } + GNUNET_CONTAINER_bloomfilter_add (*bf, &mhash); + } + return GNUNET_BLOCK_EVALUATION_OK_MORE; + + + default: + return GNUNET_BLOCK_EVALUATION_TYPE_NOT_SUPPORTED; + } +} + + +/** + * Function called to obtain the key for a block. + * + * @param cls closure + * @param type block type + * @param block block to get the key for + * @param block_size number of bytes in block + * @param key set to the key (query) for the given block + * @return GNUNET_OK on success, GNUNET_SYSERR if type not supported + * (or if extracting a key from a block of this type does not work) + */ +static int +block_plugin_regex_get_key (void *cls, enum GNUNET_BLOCK_Type type, + const void *block, size_t block_size, + struct GNUNET_HashCode * key) +{ + switch (type) + { + case GNUNET_BLOCK_TYPE_REGEX: + GNUNET_assert (sizeof (struct RegexBlock) <= block_size); + *key = ((struct RegexBlock *) block)->key; + return GNUNET_OK; + case GNUNET_BLOCK_TYPE_REGEX_ACCEPT: + GNUNET_assert (sizeof (struct RegexAccept) <= block_size); + *key = ((struct RegexAccept *) block)->key; + return GNUNET_OK; + default: + GNUNET_break (0); + return GNUNET_SYSERR; + } +} + + +/** + * Entry point for the plugin. + */ +void * +libgnunet_plugin_block_regex_init (void *cls) +{ + static enum GNUNET_BLOCK_Type types[] = + { + GNUNET_BLOCK_TYPE_REGEX, + GNUNET_BLOCK_TYPE_REGEX_ACCEPT, + GNUNET_BLOCK_TYPE_ANY /* end of list */ + }; + struct GNUNET_BLOCK_PluginFunctions *api; + + api = GNUNET_malloc (sizeof (struct GNUNET_BLOCK_PluginFunctions)); + api->evaluate = &block_plugin_regex_evaluate; + api->get_key = &block_plugin_regex_get_key; + api->types = types; + return api; +} + + +/** + * Exit point from the plugin. + */ +void * +libgnunet_plugin_block_regex_done (void *cls) +{ + struct GNUNET_TRANSPORT_PluginFunctions *api = cls; + + GNUNET_free (api); + return NULL; +} + +/* end of plugin_block_regex.c */ diff --git a/src/regex/regex.c b/src/regex/regex.c index 5244c26..ad8e56b 100644 --- a/src/regex/regex.c +++ b/src/regex/regex.c @@ -19,417 +19,80 @@ */ /** * @file src/regex/regex.c - * @brief library to create automatons from regular expressions + * @brief library to create Deterministic Finite Automatons (DFAs) from regular + * expressions (regexes). * @author Maximilian Szengel */ #include "platform.h" #include "gnunet_container_lib.h" #include "gnunet_crypto_lib.h" #include "gnunet_regex_lib.h" -#include "regex.h" - -#define initial_bits 10 - -/** - * Context that contains an id counter for states and transitions as well as a - * DLL of automatons used as a stack for NFA construction. - */ -struct GNUNET_REGEX_Context -{ - /** - * Unique state id. - */ - unsigned int state_id; - - /** - * Unique transition id. - */ - unsigned int transition_id; - - /** - * Unique SCC (Strongly Connected Component) id. - */ - unsigned int scc_id; - - /** - * DLL of GNUNET_REGEX_Automaton's used as a stack. - */ - struct GNUNET_REGEX_Automaton *stack_head; - - /** - * DLL of GNUNET_REGEX_Automaton's used as a stack. - */ - struct GNUNET_REGEX_Automaton *stack_tail; -}; - -/** - * Type of an automaton. - */ -enum GNUNET_REGEX_automaton_type -{ - NFA, - DFA -}; - -/** - * Automaton representation. - */ -struct GNUNET_REGEX_Automaton -{ - /** - * This is a linked list. - */ - struct GNUNET_REGEX_Automaton *prev; - - /** - * This is a linked list. - */ - struct GNUNET_REGEX_Automaton *next; - - /** - * First state of the automaton. This is mainly used for constructing an NFA, - * where each NFA itself consists of one or more NFAs linked together. - */ - struct GNUNET_REGEX_State *start; - - /** - * End state of the automaton. - */ - struct GNUNET_REGEX_State *end; - - /** - * Number of states in the automaton. - */ - unsigned int state_count; - - /** - * DLL of states. - */ - struct GNUNET_REGEX_State *states_head; - - /** - * DLL of states - */ - struct GNUNET_REGEX_State *states_tail; - - /** - * Type of the automaton. - */ - enum GNUNET_REGEX_automaton_type type; -}; +#include "regex_internal.h" /** - * A state. Can be used in DFA and NFA automatons. + * Set this to GNUNET_YES to enable state naming. Used to debug NFA->DFA + * creation. Disabled by default for better performance. */ -struct GNUNET_REGEX_State -{ - /** - * This is a linked list. - */ - struct GNUNET_REGEX_State *prev; - - /** - * This is a linked list. - */ - struct GNUNET_REGEX_State *next; - - /** - * Unique state id. - */ - unsigned int id; - - /** - * If this is an accepting state or not. - */ - int accepting; - - /** - * Marking of the state. This is used for marking all visited states when - * traversing all states of an automaton and for cases where the state id - * cannot be used (dfa minimization). - */ - int marked; - - /** - * Marking the state as contained. This is used for checking, if the state is - * contained in a set in constant time - */ - int contained; - - /** - * Marking the state as part of an SCC (Strongly Connected Component). All - * states with the same scc_id are part of the same SCC. scc_id is 0, if state - * is not a part of any SCC. - */ - unsigned int scc_id; - - /** - * Used for SCC detection. - */ - int index; - - /** - * Used for SCC detection. - */ - int lowlink; - - /** - * Human readable name of the automaton. Used for debugging and graph - * creation. - */ - char *name; - - /** - * Hash of the state. - */ - GNUNET_HashCode hash; - - /** - * Proof for this state. - */ - char *proof; - - /** - * Number of transitions from this state to other states. - */ - unsigned int transition_count; - - /** - * DLL of transitions. - */ - struct Transition *transitions_head; - - /** - * DLL of transitions. - */ - struct Transition *transitions_tail; - - /** - * Set of states on which this state is based on. Used when creating a DFA out - * of several NFA states. - */ - struct GNUNET_REGEX_StateSet *nfa_set; -}; +#define REGEX_DEBUG_DFA GNUNET_NO /** - * Transition between two states. Each state can have 0-n transitions. If label - * is 0, this is considered to be an epsilon transition. + * Set of states using MDLL API. */ -struct Transition +struct GNUNET_REGEX_StateSet_MDLL { /** - * This is a linked list. - */ - struct Transition *prev; - - /** - * This is a linked list. - */ - struct Transition *next; - - /** - * Unique id of this transition. - */ - unsigned int id; - - /** - * Label for this transition. This is basically the edge label for the graph. - */ - char label; - - /** - * State to which this transition leads. - */ - struct GNUNET_REGEX_State *to_state; - - /** - * State from which this transition origins. - */ - struct GNUNET_REGEX_State *from_state; - - /** - * Mark this transition. For example when reversing the automaton. + * MDLL of states. */ - int mark; -}; + struct GNUNET_REGEX_State *head; -/** - * Set of states. - */ -struct GNUNET_REGEX_StateSet -{ /** - * Array of states. + * MDLL of states. */ - struct GNUNET_REGEX_State **states; + struct GNUNET_REGEX_State *tail; /** - * Length of the 'states' array. + * Length of the MDLL. */ unsigned int len; }; -/* - * Debug helper functions - */ -void -debug_print_transitions (struct GNUNET_REGEX_State *); - -void -debug_print_state (struct GNUNET_REGEX_State *s) -{ - char *proof; - - if (NULL == s->proof) - proof = "NULL"; - else - proof = s->proof; - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "State %i: %s marked: %i accepting: %i scc_id: %i transitions: %i proof: %s\n", - s->id, s->name, s->marked, s->accepting, s->scc_id, - s->transition_count, proof); - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Transitions:\n"); - debug_print_transitions (s); -} - -void -debug_print_states (struct GNUNET_REGEX_Automaton *a) -{ - struct GNUNET_REGEX_State *s; - - for (s = a->states_head; NULL != s; s = s->next) - debug_print_state (s); -} - -void -debug_print_transition (struct Transition *t) -{ - char *to_state; - char *from_state; - char label; - - if (NULL == t) - return; - - if (0 == t->label) - label = '0'; - else - label = t->label; - - if (NULL == t->to_state) - to_state = "NULL"; - else - to_state = t->to_state->name; - - if (NULL == t->from_state) - from_state = "NULL"; - else - from_state = t->from_state->name; - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Transition %i: From %s on %c to %s\n", - t->id, from_state, label, to_state); -} - -void -debug_print_transitions (struct GNUNET_REGEX_State *s) -{ - struct Transition *t; - - for (t = s->transitions_head; NULL != t; t = t->next) - debug_print_transition (t); -} /** - * Recursive function doing DFS with 'v' as a start, detecting all SCCs inside - * the subgraph reachable from 'v'. Used with scc_tarjan function to detect all - * SCCs inside an automaton. + * Append state to the given StateSet ' * - * @param ctx context - * @param v start vertex - * @param index current index - * @param stack stack for saving all SCCs - * @param stack_size current size of the stack + * @param set set to be modified + * @param state state to be appended */ static void -scc_tarjan_strongconnect (struct GNUNET_REGEX_Context *ctx, - struct GNUNET_REGEX_State *v, int *index, - struct GNUNET_REGEX_State **stack, - unsigned int *stack_size) +state_set_append (struct GNUNET_REGEX_StateSet *set, + struct GNUNET_REGEX_State *state) { - struct GNUNET_REGEX_State *w; - struct Transition *t; - - v->index = *index; - v->lowlink = *index; - (*index)++; - stack[(*stack_size)++] = v; - v->contained = 1; - - for (t = v->transitions_head; NULL != t; t = t->next) - { - w = t->to_state; - if (NULL != w && w->index < 0) - { - scc_tarjan_strongconnect (ctx, w, index, stack, stack_size); - v->lowlink = (v->lowlink > w->lowlink) ? w->lowlink : v->lowlink; - } - else if (0 != w->contained) - v->lowlink = (v->lowlink > w->index) ? w->index : v->lowlink; - } - - if (v->lowlink == v->index) - { - w = stack[--(*stack_size)]; - w->contained = 0; - - if (v != w) - { - ctx->scc_id++; - while (v != w) - { - w->scc_id = ctx->scc_id; - w = stack[--(*stack_size)]; - w->contained = 0; - } - w->scc_id = ctx->scc_id; - } - } + if (set->off == set->size) + GNUNET_array_grow (set->states, set->size, set->size * 2 + 4); + set->states[set->off++] = state; } + /** - * Detect all SCCs (Strongly Connected Components) inside the given automaton. - * SCCs will be marked using the scc_id on each state. + * Compare two strings for equality. If either is NULL they are not equal. * - * @param ctx context - * @param a automaton + * @param str1 first string for comparison. + * @param str2 second string for comparison. + * + * @return 0 if the strings are the same or both NULL, 1 or -1 if not. */ -static void -scc_tarjan (struct GNUNET_REGEX_Context *ctx, struct GNUNET_REGEX_Automaton *a) +static int +nullstrcmp (const char *str1, const char *str2) { - int index; - struct GNUNET_REGEX_State *v; - struct GNUNET_REGEX_State *stack[a->state_count]; - unsigned int stack_size; - - for (v = a->states_head; NULL != v; v = v->next) - { - v->contained = 0; - v->index = -1; - v->lowlink = -1; - } - - stack_size = 0; - index = 0; + if ((NULL == str1) != (NULL == str2)) + return -1; + if ((NULL == str1) && (NULL == str2)) + return 0; - for (v = a->states_head; NULL != v; v = v->next) - { - if (v->index < 0) - scc_tarjan_strongconnect (ctx, v, &index, stack, &stack_size); - } + return strcmp (str1, str2); } + /** * Adds a transition from one state to another on 'label'. Does not add * duplicate states. @@ -441,11 +104,11 @@ scc_tarjan (struct GNUNET_REGEX_Context *ctx, struct GNUNET_REGEX_Automaton *a) */ static void state_add_transition (struct GNUNET_REGEX_Context *ctx, - struct GNUNET_REGEX_State *from_state, const char label, + struct GNUNET_REGEX_State *from_state, const char *label, struct GNUNET_REGEX_State *to_state) { - int is_dup; - struct Transition *t; + struct GNUNET_REGEX_Transition *t; + struct GNUNET_REGEX_Transition *oth; if (NULL == from_state) { @@ -453,33 +116,64 @@ state_add_transition (struct GNUNET_REGEX_Context *ctx, return; } - // Do not add duplicate state transitions - is_dup = GNUNET_NO; + /* Do not add duplicate state transitions */ for (t = from_state->transitions_head; NULL != t; t = t->next) { - if (t->to_state == to_state && t->label == label && + if (t->to_state == to_state && 0 == nullstrcmp (t->label, label) && t->from_state == from_state) - { - is_dup = GNUNET_YES; - break; - } + return; } - if (is_dup) - return; + /* sort transitions by label */ + for (oth = from_state->transitions_head; NULL != oth; oth = oth->next) + { + if (0 < nullstrcmp (oth->label, label)) + break; + } - t = GNUNET_malloc (sizeof (struct Transition)); - t->id = ctx->transition_id++; - t->label = label; + t = GNUNET_malloc (sizeof (struct GNUNET_REGEX_Transition)); + if (NULL != ctx) + t->id = ctx->transition_id++; + if (NULL != label) + t->label = GNUNET_strdup (label); + else + t->label = NULL; t->to_state = to_state; t->from_state = from_state; - // Add outgoing transition to 'from_state' + /* Add outgoing transition to 'from_state' */ from_state->transition_count++; - GNUNET_CONTAINER_DLL_insert (from_state->transitions_head, - from_state->transitions_tail, t); + GNUNET_CONTAINER_DLL_insert_before (from_state->transitions_head, + from_state->transitions_tail, oth, t); +} + + +/** + * Remove a 'transition' from 'state'. + * + * @param state state from which the to-be-removed transition originates. + * @param transition transition that should be removed from state 'state'. + */ +static void +state_remove_transition (struct GNUNET_REGEX_State *state, + struct GNUNET_REGEX_Transition *transition) +{ + if (NULL == state || NULL == transition) + return; + + if (transition->from_state != state) + return; + + GNUNET_free_non_null (transition->label); + + state->transition_count--; + GNUNET_CONTAINER_DLL_remove (state->transitions_head, state->transitions_tail, + transition); + + GNUNET_free (transition); } + /** * Compare two states. Used for sorting. * @@ -493,27 +187,26 @@ state_add_transition (struct GNUNET_REGEX_Context *ctx, static int state_compare (const void *a, const void *b) { - struct GNUNET_REGEX_State **s1; - struct GNUNET_REGEX_State **s2; - - s1 = (struct GNUNET_REGEX_State **) a; - s2 = (struct GNUNET_REGEX_State **) b; + struct GNUNET_REGEX_State **s1 = (struct GNUNET_REGEX_State **) a; + struct GNUNET_REGEX_State **s2 = (struct GNUNET_REGEX_State **) b; return (*s1)->id - (*s2)->id; } + /** * Get all edges leaving state 's'. * * @param s state. - * @param edges all edges leaving 's'. + * @param edges all edges leaving 's', expected to be allocated and have enough + * space for s->transitions_count elements. * * @return number of edges. */ static unsigned int state_get_edges (struct GNUNET_REGEX_State *s, struct GNUNET_REGEX_Edge *edges) { - struct Transition *t; + struct GNUNET_REGEX_Transition *t; unsigned int count; if (NULL == s) @@ -525,7 +218,7 @@ state_get_edges (struct GNUNET_REGEX_State *s, struct GNUNET_REGEX_Edge *edges) { if (NULL != t->to_state) { - edges[count].label = &t->label; + edges[count].label = t->label; edges[count].destination = t->to_state->hash; count++; } @@ -533,39 +226,37 @@ state_get_edges (struct GNUNET_REGEX_State *s, struct GNUNET_REGEX_Edge *edges) return count; } + /** * Compare to state sets by comparing the id's of the states that are contained * in each set. Both sets are expected to be sorted by id! * * @param sset1 first state set * @param sset2 second state set - * - * @return an integer less than, equal to, or greater than zero - * if the first argument is considered to be respectively - * less than, equal to, or greater than the second. + * @return 0 if the sets are equal, otherwise non-zero */ static int state_set_compare (struct GNUNET_REGEX_StateSet *sset1, struct GNUNET_REGEX_StateSet *sset2) { int result; - int i; + unsigned int i; if (NULL == sset1 || NULL == sset2) return 1; - result = sset1->len - sset2->len; - - for (i = 0; i < sset1->len; i++) - { - if (0 != result) + result = sset1->off - sset2->off; + if (result < 0) + return -1; + if (result > 0) + return 1; + for (i = 0; i < sset1->off; i++) + if (0 != (result = state_compare (&sset1->states[i], &sset2->states[i]))) break; - - result = state_compare (&sset1->states[i], &sset2->states[i]); - } return result; } + /** * Clears the given StateSet 'set' * @@ -574,14 +265,11 @@ state_set_compare (struct GNUNET_REGEX_StateSet *sset1, static void state_set_clear (struct GNUNET_REGEX_StateSet *set) { - if (NULL != set) - { - if (NULL != set->states) - GNUNET_free (set->states); - GNUNET_free (set); - } + GNUNET_array_grow (set->states, set->size, 0); + set->off = 0; } + /** * Clears an automaton fragment. Does not destroy the states inside the * automaton. @@ -602,6 +290,7 @@ automaton_fragment_clear (struct GNUNET_REGEX_Automaton *a) GNUNET_free (a); } + /** * Frees the memory used by State 's' * @@ -610,30 +299,25 @@ automaton_fragment_clear (struct GNUNET_REGEX_Automaton *a) static void automaton_destroy_state (struct GNUNET_REGEX_State *s) { - struct Transition *t; - struct Transition *next_t; + struct GNUNET_REGEX_Transition *t; + struct GNUNET_REGEX_Transition *next_t; if (NULL == s) return; - if (NULL != s->name) - GNUNET_free (s->name); - - if (NULL != s->proof) - GNUNET_free (s->proof); - + GNUNET_free_non_null (s->name); + GNUNET_free_non_null (s->proof); + state_set_clear (&s->nfa_set); for (t = s->transitions_head; NULL != t; t = next_t) { next_t = t->next; - GNUNET_CONTAINER_DLL_remove (s->transitions_head, s->transitions_tail, t); - GNUNET_free (t); + state_remove_transition (s, t); } - state_set_clear (s->nfa_set); - GNUNET_free (s); } + /** * Remove a state from the given automaton 'a'. Always use this function when * altering the states of an automaton. Will also remove all transitions leading @@ -646,39 +330,36 @@ static void automaton_remove_state (struct GNUNET_REGEX_Automaton *a, struct GNUNET_REGEX_State *s) { - struct GNUNET_REGEX_State *ss; struct GNUNET_REGEX_State *s_check; - struct Transition *t_check; + struct GNUNET_REGEX_Transition *t_check; + struct GNUNET_REGEX_Transition *t_check_next; if (NULL == a || NULL == s) return; - // remove state - ss = s; - GNUNET_CONTAINER_DLL_remove (a->states_head, a->states_tail, s); - a->state_count--; - - // remove all transitions leading to this state + /* remove all transitions leading to this state */ for (s_check = a->states_head; NULL != s_check; s_check = s_check->next) { for (t_check = s_check->transitions_head; NULL != t_check; - t_check = t_check->next) + t_check = t_check_next) { - if (t_check->to_state == ss) - { - GNUNET_CONTAINER_DLL_remove (s_check->transitions_head, - s_check->transitions_tail, t_check); - s_check->transition_count--; - } + t_check_next = t_check->next; + if (t_check->to_state == s) + state_remove_transition (s_check, t_check); } } - automaton_destroy_state (ss); + /* remove state */ + GNUNET_CONTAINER_DLL_remove (a->states_head, a->states_tail, s); + a->state_count--; + + automaton_destroy_state (s); } + /** * Merge two states into one. Will merge 's1' and 's2' into 's1' and destroy - * 's2'. + * 's2'. 's1' will contain all (non-duplicate) outgoing transitions of 's2'. * * @param ctx context * @param a automaton @@ -692,48 +373,61 @@ automaton_merge_states (struct GNUNET_REGEX_Context *ctx, struct GNUNET_REGEX_State *s2) { struct GNUNET_REGEX_State *s_check; - struct Transition *t_check; - char *new_name; - - GNUNET_assert (NULL != ctx && NULL != a && NULL != s1 && NULL != s2); + struct GNUNET_REGEX_Transition *t_check; + struct GNUNET_REGEX_Transition *t; + struct GNUNET_REGEX_Transition *t_next; + int is_dup; if (s1 == s2) return; - // 1. Make all transitions pointing to s2 point to s1 + /* 1. Make all transitions pointing to s2 point to s1, unless this transition + * does not already exists, if it already exists remove transition. */ for (s_check = a->states_head; NULL != s_check; s_check = s_check->next) { - for (t_check = s_check->transitions_head; NULL != t_check; - t_check = t_check->next) + for (t_check = s_check->transitions_head; NULL != t_check; t_check = t_next) { + t_next = t_check->next; + if (s2 == t_check->to_state) - t_check->to_state = s1; + { + is_dup = GNUNET_NO; + for (t = t_check->from_state->transitions_head; NULL != t; t = t->next) + { + if (t->to_state == s1 && 0 == strcmp (t_check->label, t->label)) + is_dup = GNUNET_YES; + } + if (GNUNET_NO == is_dup) + t_check->to_state = s1; + else + state_remove_transition (t_check->from_state, t_check); + } } } - // 2. Add all transitions from s2 to sX to s1 + /* 2. Add all transitions from s2 to sX to s1 */ for (t_check = s2->transitions_head; NULL != t_check; t_check = t_check->next) { if (t_check->to_state != s1) state_add_transition (ctx, s1, t_check->label, t_check->to_state); } - // 3. Rename s1 to {s1,s2} - new_name = GNUNET_strdup (s1->name); - if (NULL != s1->name) - { - GNUNET_free (s1->name); - s1->name = NULL; - } + /* 3. Rename s1 to {s1,s2} */ +#if REGEX_DEBUG_DFA + char *new_name; + + new_name = s1->name; GNUNET_asprintf (&s1->name, "{%s,%s}", new_name, s2->name); GNUNET_free (new_name); +#endif - // remove state + /* remove state */ GNUNET_CONTAINER_DLL_remove (a->states_head, a->states_tail, s2); a->state_count--; automaton_destroy_state (s2); } + /** * Add a state to the automaton 'a', always use this function to alter the * states DLL of the automaton. @@ -749,154 +443,1316 @@ automaton_add_state (struct GNUNET_REGEX_Automaton *a, a->state_count++; } -/** - * Function that is called with each state, when traversing an automaton. - * - * @param cls closure - * @param s state - */ -typedef void (*GNUNET_REGEX_traverse_action) (void *cls, - struct GNUNET_REGEX_State * s); /** - * Traverses all states that are reachable from state 's'. Expects the states to - * be unmarked (s->marked == GNUNET_NO). Performs 'action' on each visited - * state. + * Depth-first traversal (DFS) of all states that are reachable from state + * 's'. Performs 'action' on each visited state. * - * @param cls closure. * @param s start state. + * @param marks an array of size a->state_count to remember which state was + * already visited. + * @param count current count of the state. + * @param check function that is checked before advancing on each transition + * in the DFS. + * @param check_cls closure for check. * @param action action to be performed on each state. + * @param action_cls closure for action. */ static void -automaton_state_traverse (void *cls, struct GNUNET_REGEX_State *s, - GNUNET_REGEX_traverse_action action) +automaton_state_traverse (struct GNUNET_REGEX_State *s, int *marks, + unsigned int *count, + GNUNET_REGEX_traverse_check check, void *check_cls, + GNUNET_REGEX_traverse_action action, void *action_cls) { - struct Transition *t; + struct GNUNET_REGEX_Transition *t; - if (GNUNET_NO == s->marked) + if (GNUNET_YES == marks[s->traversal_id]) + return; + + marks[s->traversal_id] = GNUNET_YES; + + if (NULL != action) + action (action_cls, *count, s); + + (*count)++; + + for (t = s->transitions_head; NULL != t; t = t->next) { - s->marked = GNUNET_YES; + if (NULL == check || + (NULL != check && GNUNET_YES == check (check_cls, s, t))) + { + automaton_state_traverse (t->to_state, marks, count, check, check_cls, + action, action_cls); + } + } +} - if (action > 0) - action (cls, s); - for (t = s->transitions_head; NULL != t; t = t->next) - automaton_state_traverse (cls, t->to_state, action); +/** + * Traverses the given automaton using depth-first-search (DFS) from it's start + * state, visiting all reachable states and calling 'action' on each one of + * them. + * + * @param a automaton to be traversed. + * @param start start state, pass a->start or NULL to traverse the whole automaton. + * @param check function that is checked before advancing on each transition + * in the DFS. + * @param check_cls closure for check. + * @param action action to be performed on each state. + * @param action_cls closure for action + */ +void +GNUNET_REGEX_automaton_traverse (const struct GNUNET_REGEX_Automaton *a, + struct GNUNET_REGEX_State *start, + GNUNET_REGEX_traverse_check check, + void *check_cls, + GNUNET_REGEX_traverse_action action, + void *action_cls) +{ + unsigned int count; + struct GNUNET_REGEX_State *s; + + if (NULL == a || 0 == a->state_count) + return; + + int marks[a->state_count]; + + for (count = 0, s = a->states_head; NULL != s && count < a->state_count; + s = s->next, count++) + { + s->traversal_id = count; + marks[s->traversal_id] = GNUNET_NO; } + + count = 0; + + if (NULL == start) + s = a->start; + else + s = start; + + automaton_state_traverse (s, marks, &count, check, check_cls, action, + action_cls); +} + + +/** + * String container for faster string operations. + */ +struct StringBuffer +{ + /** + * Buffer holding the string (may start in the middle!); + * NOT 0-terminated! + */ + char *sbuf; + + /** + * Allocated buffer. + */ + char *abuf; + + /** + * Length of the string in the buffer. + */ + size_t slen; + + /** + * Number of bytes allocated for 'sbuf' + */ + unsigned int blen; + + /** + * Buffer currently represents "NULL" (not the empty string!) + */ + int16_t null_flag; + + /** + * If this entry is part of the last/current generation array, + * this flag is GNUNET_YES if the last and current generation are + * identical (and thus copying is unnecessary if the value didn't + * change). This is used in an optimization that improves + * performance by about 1% --- if we use int16_t here. With just + * "int" for both flags, performance drops (on my system) significantly, + * most likely due to increased cache misses. + */ + int16_t synced; + +}; + + +/** + * Compare two strings for equality. If either is NULL they are not equal. + * + * @param s1 first string for comparison. + * @param s2 second string for comparison. + * + * @return 0 if the strings are the same or both NULL, 1 or -1 if not. + */ +static int +sb_nullstrcmp (const struct StringBuffer *s1, + const struct StringBuffer *s2) +{ + if ( (GNUNET_YES == s1->null_flag) && + (GNUNET_YES == s2->null_flag) ) + return 0; + if ( (GNUNET_YES == s1->null_flag) || + (GNUNET_YES == s2->null_flag) ) + return -1; + if (s1->slen != s2->slen) + return -1; + return memcmp (s1->sbuf, s2->sbuf, s1->slen); } + /** - * Traverses the given automaton from it's start state, visiting all reachable - * states and calling 'action' on each one of them. + * Compare two strings for equality. * - * @param cls closure. - * @param a automaton. - * @param action action to be performed on each state. + * @param s1 first string for comparison. + * @param s2 second string for comparison. + * + * @return 0 if the strings are the same, 1 or -1 if not. + */ +static int +sb_strcmp (const struct StringBuffer *s1, + const struct StringBuffer *s2) +{ + if (s1->slen != s2->slen) + return -1; + return memcmp (s1->sbuf, s2->sbuf, s1->slen); +} + + +/** + * Reallocate the buffer of 'ret' to fit 'nlen' characters; + * move the existing string to the beginning of the new buffer. + * + * @param ret current buffer, to be updated + * @param nlen target length for the buffer, must be at least ret->slen */ static void -automaton_traverse (void *cls, struct GNUNET_REGEX_Automaton *a, - GNUNET_REGEX_traverse_action action) +sb_realloc (struct StringBuffer *ret, + size_t nlen) { - struct GNUNET_REGEX_State *s; + char *old; + + GNUNET_assert (nlen >= ret->slen); + old = ret->abuf; + ret->abuf = GNUNET_malloc (nlen); + ret->blen = nlen; + memcpy (ret->abuf, + ret->sbuf, + ret->slen); + ret->sbuf = ret->abuf; + GNUNET_free_non_null (old); +} + - for (s = a->states_head; NULL != s; s = s->next) - s->marked = GNUNET_NO; +/** + * Append a string. + * + * @param ret where to write the result + * @param sarg string to append + */ +static void +sb_append (struct StringBuffer *ret, + const struct StringBuffer *sarg) +{ + if (GNUNET_YES == ret->null_flag) + ret->slen = 0; + ret->null_flag = GNUNET_NO; + if (ret->blen < sarg->slen + ret->slen) + sb_realloc (ret, ret->blen + sarg->slen + 128); + memcpy (&ret->sbuf[ret->slen], + sarg->sbuf, + sarg->slen); + ret->slen += sarg->slen; +} + + +/** + * Append a C string. + * + * @param ret where to write the result + * @param cstr string to append + */ +static void +sb_append_cstr (struct StringBuffer *ret, + const char *cstr) +{ + size_t cstr_len = strlen (cstr); + + if (GNUNET_YES == ret->null_flag) + ret->slen = 0; + ret->null_flag = GNUNET_NO; + if (ret->blen < cstr_len + ret->slen) + sb_realloc (ret, ret->blen + cstr_len + 128); + memcpy (&ret->sbuf[ret->slen], + cstr, + cstr_len); + ret->slen += cstr_len; +} + - automaton_state_traverse (cls, a->start, action); +/** + * Wrap a string buffer, that is, set ret to the format string + * which contains an "%s" which is to be replaced with the original + * content of 'ret'. Note that optimizing this function is not + * really worth it, it is rarely called. + * + * @param ret where to write the result and take the input for %.*s from + * @param format format string, fprintf-style, with exactly one "%.*s" + * @param extra_chars how long will the result be, in addition to 'sarg' length + */ +static void +sb_wrap (struct StringBuffer *ret, + const char *format, + size_t extra_chars) +{ + char *temp; + + if (GNUNET_YES == ret->null_flag) + ret->slen = 0; + ret->null_flag = GNUNET_NO; + temp = GNUNET_malloc (ret->slen + extra_chars + 1); + GNUNET_snprintf (temp, + ret->slen + extra_chars + 1, + format, + (int) ret->slen, + ret->sbuf); + GNUNET_free_non_null (ret->abuf); + ret->abuf = temp; + ret->sbuf = temp; + ret->blen = ret->slen + extra_chars + 1; + ret->slen = ret->slen + extra_chars; } + /** - * Reverses all transitions of the given automaton. + * Format a string buffer. Note that optimizing this function is not + * really worth it, it is rarely called. * - * @param a automaton. + * @param ret where to write the result + * @param format format string, fprintf-style, with exactly one "%.*s" + * @param extra_chars how long will the result be, in addition to 'sarg' length + * @param sarg string to print into the format */ static void -automaton_reverse (struct GNUNET_REGEX_Automaton *a) +sb_printf1 (struct StringBuffer *ret, + const char *format, + size_t extra_chars, + const struct StringBuffer *sarg) { - struct GNUNET_REGEX_State *s; - struct Transition *t; - struct Transition *t_next; - struct GNUNET_REGEX_State *s_swp; + if (ret->blen < sarg->slen + extra_chars + 1) + sb_realloc (ret, + sarg->slen + extra_chars + 1); + ret->null_flag = GNUNET_NO; + ret->sbuf = ret->abuf; + ret->slen = sarg->slen + extra_chars; + GNUNET_snprintf (ret->sbuf, + ret->blen, + format, + (int) sarg->slen, + sarg->sbuf); +} - for (s = a->states_head; NULL != s; s = s->next) - for (t = s->transitions_head; NULL != t; t = t->next) - t->mark = GNUNET_NO; - for (s = a->states_head; NULL != s; s = s->next) +/** + * Format a string buffer. + * + * @param ret where to write the result + * @param format format string, fprintf-style, with exactly two "%.*s" + * @param extra_chars how long will the result be, in addition to 'sarg1/2' length + * @param sarg1 first string to print into the format + * @param sarg2 second string to print into the format + */ +static void +sb_printf2 (struct StringBuffer *ret, + const char *format, + size_t extra_chars, + const struct StringBuffer *sarg1, + const struct StringBuffer *sarg2) +{ + if (ret->blen < sarg1->slen + sarg2->slen + extra_chars + 1) + sb_realloc (ret, + sarg1->slen + sarg2->slen + extra_chars + 1); + ret->null_flag = GNUNET_NO; + ret->slen = sarg1->slen + sarg2->slen + extra_chars; + ret->sbuf = ret->abuf; + GNUNET_snprintf (ret->sbuf, + ret->blen, + format, + (int) sarg1->slen, + sarg1->sbuf, + (int) sarg2->slen, + sarg2->sbuf); +} + + +/** + * Format a string buffer. Note that optimizing this function is not + * really worth it, it is rarely called. + * + * @param ret where to write the result + * @param format format string, fprintf-style, with exactly three "%.*s" + * @param extra_chars how long will the result be, in addition to 'sarg1/2/3' length + * @param sarg1 first string to print into the format + * @param sarg2 second string to print into the format + * @param sarg3 third string to print into the format + */ +static void +sb_printf3 (struct StringBuffer *ret, + const char *format, + size_t extra_chars, + const struct StringBuffer *sarg1, + const struct StringBuffer *sarg2, + const struct StringBuffer *sarg3) +{ + if (ret->blen < sarg1->slen + sarg2->slen + sarg3->slen + extra_chars + 1) + sb_realloc (ret, + sarg1->slen + sarg2->slen + sarg3->slen + extra_chars + 1); + ret->null_flag = GNUNET_NO; + ret->slen = sarg1->slen + sarg2->slen + sarg3->slen + extra_chars; + ret->sbuf = ret->abuf; + GNUNET_snprintf (ret->sbuf, + ret->blen, + format, + (int) sarg1->slen, + sarg1->sbuf, + (int) sarg2->slen, + sarg2->sbuf, + (int) sarg3->slen, + sarg3->sbuf); +} + + +/** + * Free resources of the given string buffer. + * + * @param sb buffer to free (actual pointer is not freed, as they + * should not be individually allocated) + */ +static void +sb_free (struct StringBuffer *sb) +{ + GNUNET_array_grow (sb->abuf, + sb->blen, + 0); + sb->slen = 0; + sb->sbuf = NULL; + sb->null_flag= GNUNET_YES; +} + + +/** + * Copy the given string buffer from 'in' to 'out'. + * + * @param in input string + * @param out output string + */ +static void +sb_strdup (struct StringBuffer *out, + const struct StringBuffer *in) + +{ + out->null_flag = in->null_flag; + if (GNUNET_YES == out->null_flag) + return; + if (out->blen < in->slen) + { + GNUNET_array_grow (out->abuf, + out->blen, + in->slen); + } + out->sbuf = out->abuf; + out->slen = in->slen; + memcpy (out->sbuf, in->sbuf, out->slen); +} + + +/** + * Copy the given string buffer from 'in' to 'out'. + * + * @param cstr input string + * @param out output string + */ +static void +sb_strdup_cstr (struct StringBuffer *out, + const char *cstr) +{ + if (NULL == cstr) { - for (t = s->transitions_head; NULL != t; t = t_next) + out->null_flag = GNUNET_YES; + return; + } + out->null_flag = GNUNET_NO; + out->slen = strlen (cstr); + if (out->blen < out->slen) + { + GNUNET_array_grow (out->abuf, + out->blen, + out->slen); + } + out->sbuf = out->abuf; + memcpy (out->sbuf, cstr, out->slen); +} + + +/** + * Check if the given string 'str' needs parentheses around it when + * using it to generate a regex. + * + * @param str string + * + * @return GNUNET_YES if parentheses are needed, GNUNET_NO otherwise + */ +static int +needs_parentheses (const struct StringBuffer *str) +{ + size_t slen; + const char *op; + const char *cl; + const char *pos; + const char *end; + unsigned int cnt; + + if ((GNUNET_YES == str->null_flag) || ((slen = str->slen) < 2)) + return GNUNET_NO; + pos = str->sbuf; + if ('(' != pos[0]) + return GNUNET_YES; + end = str->sbuf + slen; + cnt = 1; + pos++; + while (cnt > 0) + { + cl = memchr (pos, ')', end - pos); + if (NULL == cl) { - t_next = t->next; + GNUNET_break (0); + return GNUNET_YES; + } + /* while '(' before ')', count opening parens */ + while ( (NULL != (op = memchr (pos, '(', end - pos))) && + (op < cl) ) + { + cnt++; + pos = op + 1; + } + /* got ')' first */ + cnt--; + pos = cl + 1; + } + return (*pos == '\0') ? GNUNET_NO : GNUNET_YES; +} - if (GNUNET_YES == t->mark || t->from_state == t->to_state) - continue; - t->mark = GNUNET_YES; +/** + * Remove parentheses surrounding string 'str'. + * Example: "(a)" becomes "a", "(a|b)|(a|c)" stays the same. + * You need to GNUNET_free the returned string. + * + * @param str string, modified to contain a + * @return string without surrounding parentheses, string 'str' if no preceding + * epsilon could be found, NULL if 'str' was NULL + */ +static void +remove_parentheses (struct StringBuffer *str) +{ + size_t slen; + const char *pos; + const char *end; + const char *sbuf; + const char *op; + const char *cp; + unsigned int cnt; + + if (0) + return; + sbuf = str->sbuf; + if ( (GNUNET_YES == str->null_flag) || + (1 >= (slen = str->slen)) || + ('(' != str->sbuf[0]) || + (')' != str->sbuf[slen - 1]) ) + return; + cnt = 0; + pos = &sbuf[1]; + end = &sbuf[slen - 1]; + op = memchr (pos, '(', end - pos); + cp = memchr (pos, ')', end - pos); + while (NULL != cp) + { + while ( (NULL != op) && + (op < cp) ) + { + cnt++; + pos = op + 1; + op = memchr (pos, '(', end - pos); + } + while ( (NULL != cp) && + ( (NULL == op) || + (cp < op) ) ) + { + if (0 == cnt) + return; /* can't strip parens */ + cnt--; + pos = cp + 1; + cp = memchr (pos, ')', end - pos); + } + } + if (0 != cnt) + { + GNUNET_break (0); + return; + } + str->sbuf++; + str->slen -= 2; +} + + +/** + * Check if the string 'str' starts with an epsilon (empty string). + * Example: "(|a)" is starting with an epsilon. + * + * @param str string to test + * + * @return 0 if str has no epsilon, 1 if str starts with '(|' and ends with ')' + */ +static int +has_epsilon (const struct StringBuffer *str) +{ + return + (GNUNET_YES != str->null_flag) && + (0 < str->slen) && + ('(' == str->sbuf[0]) && + ('|' == str->sbuf[1]) && + (')' == str->sbuf[str->slen - 1]); +} - GNUNET_CONTAINER_DLL_remove (t->from_state->transitions_head, - t->from_state->transitions_tail, t); - t->from_state->transition_count--; - GNUNET_CONTAINER_DLL_insert (t->to_state->transitions_head, - t->to_state->transitions_tail, t); - t->to_state->transition_count++; - s_swp = t->from_state; - t->from_state = t->to_state; - t->to_state = s_swp; +/** + * Remove an epsilon from the string str. Where epsilon is an empty string + * Example: str = "(|a|b|c)", result: "a|b|c" + * The returned string needs to be freed. + * + * @param str original string + * @param ret where to return string without preceding epsilon, string 'str' if no preceding + * epsilon could be found, NULL if 'str' was NULL + */ +static void +remove_epsilon (const struct StringBuffer *str, + struct StringBuffer *ret) +{ + if (GNUNET_YES == str->null_flag) + { + ret->null_flag = GNUNET_YES; + return; + } + if ( (str->slen > 1) && + ('(' == str->sbuf[0]) && + ('|' == str->sbuf[1]) && + (')' == str->sbuf[str->slen - 1]) ) + { + /* remove epsilon */ + if (ret->blen < str->slen - 3) + { + GNUNET_array_grow (ret->abuf, + ret->blen, + str->slen - 3); } + ret->sbuf = ret->abuf; + ret->slen = str->slen - 3; + memcpy (ret->sbuf, &str->sbuf[2], ret->slen); + return; } + sb_strdup (ret, str); } + /** - * Create proof for the given state. + * Compare n bytes of 'str1' and 'str2' * - * @param cls closure. - * @param s state. + * @param str1 first string to compare + * @param str2 second string for comparison + * @param n number of bytes to compare + * + * @return -1 if any of the strings is NULL, 0 if equal, non 0 otherwise + */ +static int +sb_strncmp (const struct StringBuffer *str1, + const struct StringBuffer *str2, size_t n) +{ + size_t max; + + if ( (str1->slen != str2->slen) && + ( (str1->slen < n) || + (str2->slen < n) ) ) + return -1; + max = GNUNET_MAX (str1->slen, str2->slen); + if (max > n) + max = n; + return memcmp (str1->sbuf, str2->sbuf, max); +} + + +/** + * Compare n bytes of 'str1' and 'str2' + * + * @param str1 first string to compare + * @param str2 second C string for comparison + * @param n number of bytes to compare (and length of str2) + * + * @return -1 if any of the strings is NULL, 0 if equal, non 0 otherwise + */ +static int +sb_strncmp_cstr (const struct StringBuffer *str1, + const char *str2, size_t n) +{ + if (str1->slen < n) + return -1; + return memcmp (str1->sbuf, str2, n); +} + + +/** + * Initialize string buffer for storing strings of up to n + * characters. + * + * @param sb buffer to initialize + * @param n desired target length */ static void -automaton_create_proofs_step (void *cls, struct GNUNET_REGEX_State *s) +sb_init (struct StringBuffer *sb, + size_t n) { - struct Transition *t; - int i; - char *tmp; + sb->null_flag = GNUNET_NO; + sb->abuf = sb->sbuf = (0 == n) ? NULL : GNUNET_malloc (n); + sb->blen = n; + sb->slen = 0; +} + + +/** + * Compare 'str1', starting from position 'k', with whole 'str2' + * + * @param str1 first string to compare, starting from position 'k' + * @param str2 second string for comparison + * @param k starting position in 'str1' + * + * @return -1 if any of the strings is NULL, 0 if equal, non 0 otherwise + */ +static int +sb_strkcmp (const struct StringBuffer *str1, + const struct StringBuffer *str2, size_t k) +{ + if ( (GNUNET_YES == str1->null_flag) || + (GNUNET_YES == str2->null_flag) || + (k > str1->slen) || + (str1->slen - k != str2->slen) ) + return -1; + return memcmp (&str1->sbuf[k], str2->sbuf, str2->slen); +} + + +/** + * Helper function used as 'action' in 'GNUNET_REGEX_automaton_traverse' + * function to create the depth-first numbering of the states. + * + * @param cls states array. + * @param count current state counter. + * @param s current state. + */ +static void +number_states (void *cls, const unsigned int count, + struct GNUNET_REGEX_State *s) +{ + struct GNUNET_REGEX_State **states = cls; + + s->dfs_id = count; + if (NULL != states) + states[count] = s; +} + - for (i = 0, t = s->transitions_head; NULL != t; t = t->next, i++) + +#define PRIS(a) \ + ((GNUNET_YES == a.null_flag) ? 6 : (int) a.slen), \ + ((GNUNET_YES == a.null_flag) ? "(null)" : a.sbuf) + + +/** + * Construct the regular expression given the inductive step, + * $R^{(k)}_{ij} = R^{(k-1)}_{ij} | R^{(k-1)}_{ik} ( R^{(k-1)}_{kk} )^* + * R^{(k-1)}_{kj}, and simplify the resulting expression saved in R_cur_ij. + * + * @param R_last_ij value of $R^{(k-1)_{ij}. + * @param R_last_ik value of $R^{(k-1)_{ik}. + * @param R_last_kk value of $R^{(k-1)_{kk}. + * @param R_last_kj value of $R^{(k-1)_{kj}. + * @param R_cur_ij result for this inductive step is saved in R_cur_ij, R_cur_ij + * is expected to be NULL when called! + * @param R_cur_l optimization -- kept between iterations to avoid realloc + * @param R_cur_r optimization -- kept between iterations to avoid realloc + */ +static void +automaton_create_proofs_simplify (const struct StringBuffer *R_last_ij, + const struct StringBuffer *R_last_ik, + const struct StringBuffer *R_last_kk, + const struct StringBuffer *R_last_kj, + struct StringBuffer *R_cur_ij, + struct StringBuffer *R_cur_l, + struct StringBuffer *R_cur_r) +{ + struct StringBuffer R_temp_ij; + struct StringBuffer R_temp_ik; + struct StringBuffer R_temp_kj; + struct StringBuffer R_temp_kk; + int eps_check; + int ij_ik_cmp; + int ij_kj_cmp; + int ik_kk_cmp; + int kk_kj_cmp; + int clean_ik_kk_cmp; + int clean_kk_kj_cmp; + size_t length; + size_t length_l; + size_t length_r; + + /* + * $R^{(k)}_{ij} = R^{(k-1)}_{ij} | R^{(k-1)}_{ik} ( R^{(k-1)}_{kk} )^* R^{(k-1)}_{kj} + * R_last == R^{(k-1)}, R_cur == R^{(k)} + * R_cur_ij = R_cur_l | R_cur_r + * R_cur_l == R^{(k-1)}_{ij} + * R_cur_r == R^{(k-1)}_{ik} ( R^{(k-1)}_{kk} )^* R^{(k-1)}_{kj} + */ + + if ( (GNUNET_YES == R_last_ij->null_flag) && + ( (GNUNET_YES == R_last_ik->null_flag) || + (GNUNET_YES == R_last_kj->null_flag))) + { + /* R^{(k)}_{ij} = N | N */ + R_cur_ij->null_flag = GNUNET_YES; + R_cur_ij->synced = GNUNET_NO; + return; + } + + if ( (GNUNET_YES == R_last_ik->null_flag) || + (GNUNET_YES == R_last_kj->null_flag) ) { - if (t->to_state == s) - GNUNET_asprintf (&tmp, "%c*", t->label); - else if (i != s->transition_count - 1) - GNUNET_asprintf (&tmp, "%c|", t->label); + /* R^{(k)}_{ij} = R^{(k-1)}_{ij} | N */ + if (GNUNET_YES == R_last_ij->synced) + { + R_cur_ij->synced = GNUNET_YES; + R_cur_ij->null_flag = GNUNET_NO; + return; + } + R_cur_ij->synced = GNUNET_YES; + sb_strdup (R_cur_ij, R_last_ij); + return; + } + R_cur_ij->synced = GNUNET_NO; + + /* $R^{(k)}_{ij} = N | R^{(k-1)}_{ik} ( R^{(k-1)}_{kk} )^* R^{(k-1)}_{kj} OR + * $R^{(k)}_{ij} = R^{(k-1)}_{ij} | R^{(k-1)}_{ik} ( R^{(k-1)}_{kk} )^* R^{(k-1)}_{kj} */ + + R_cur_r->null_flag = GNUNET_YES; + R_cur_r->slen = 0; + R_cur_l->null_flag = GNUNET_YES; + R_cur_l->slen = 0; + + /* cache results from strcmp, we might need these many times */ + ij_kj_cmp = sb_nullstrcmp (R_last_ij, R_last_kj); + ij_ik_cmp = sb_nullstrcmp (R_last_ij, R_last_ik); + ik_kk_cmp = sb_nullstrcmp (R_last_ik, R_last_kk); + kk_kj_cmp = sb_nullstrcmp (R_last_kk, R_last_kj); + + /* Assign R_temp_(ik|kk|kj) to R_last[][] and remove epsilon as well + * as parentheses, so we can better compare the contents */ + + memset (&R_temp_ij, 0, sizeof (struct StringBuffer)); + memset (&R_temp_ik, 0, sizeof (struct StringBuffer)); + memset (&R_temp_kk, 0, sizeof (struct StringBuffer)); + memset (&R_temp_kj, 0, sizeof (struct StringBuffer)); + remove_epsilon (R_last_ik, &R_temp_ik); + remove_epsilon (R_last_kk, &R_temp_kk); + remove_epsilon (R_last_kj, &R_temp_kj); + remove_parentheses (&R_temp_ik); + remove_parentheses (&R_temp_kk); + remove_parentheses (&R_temp_kj); + clean_ik_kk_cmp = sb_nullstrcmp (R_last_ik, &R_temp_kk); + clean_kk_kj_cmp = sb_nullstrcmp (&R_temp_kk, R_last_kj); + + /* construct R_cur_l (and, if necessary R_cur_r) */ + if (GNUNET_YES != R_last_ij->null_flag) + { + /* Assign R_temp_ij to R_last_ij and remove epsilon as well + * as parentheses, so we can better compare the contents */ + remove_epsilon (R_last_ij, &R_temp_ij); + remove_parentheses (&R_temp_ij); + + if ( (0 == sb_strcmp (&R_temp_ij, &R_temp_ik)) && + (0 == sb_strcmp (&R_temp_ik, &R_temp_kk)) && + (0 == sb_strcmp (&R_temp_kk, &R_temp_kj)) ) + { + if (0 == R_temp_ij.slen) + { + R_cur_r->null_flag = GNUNET_NO; + } + else if ((0 == sb_strncmp_cstr (R_last_ij, "(|", 2)) || + (0 == sb_strncmp_cstr (R_last_ik, "(|", 2) && + 0 == sb_strncmp_cstr (R_last_kj, "(|", 2))) + { + /* + * a|(e|a)a*(e|a) = a* + * a|(e|a)(e|a)*(e|a) = a* + * (e|a)|aa*a = a* + * (e|a)|aa*(e|a) = a* + * (e|a)|(e|a)a*a = a* + * (e|a)|(e|a)a*(e|a) = a* + * (e|a)|(e|a)(e|a)*(e|a) = a* + */ + if (GNUNET_YES == needs_parentheses (&R_temp_ij)) + sb_printf1 (R_cur_r, "(%.*s)*", 3, &R_temp_ij); + else + sb_printf1 (R_cur_r, "%.*s*", 1, &R_temp_ij); + } + else + { + /* + * a|aa*a = a+ + * a|(e|a)a*a = a+ + * a|aa*(e|a) = a+ + * a|(e|a)(e|a)*a = a+ + * a|a(e|a)*(e|a) = a+ + */ + if (GNUNET_YES == needs_parentheses (&R_temp_ij)) + sb_printf1 (R_cur_r, "(%.*s)+", 3, &R_temp_ij); + else + sb_printf1 (R_cur_r, "%.*s+", 1, &R_temp_ij); + } + } + else if ( (0 == ij_ik_cmp) && (0 == clean_kk_kj_cmp) && (0 != clean_ik_kk_cmp) ) + { + /* a|ab*b = ab* */ + if (0 == R_last_kk->slen) + sb_strdup (R_cur_r, R_last_ij); + else if (GNUNET_YES == needs_parentheses (&R_temp_kk)) + sb_printf2 (R_cur_r, "%.*s(%.*s)*", 3, R_last_ij, &R_temp_kk); + else + sb_printf2 (R_cur_r, "%.*s%.*s*", 1, R_last_ij, R_last_kk); + R_cur_l->null_flag = GNUNET_YES; + } + else if ( (0 == ij_kj_cmp) && (0 == clean_ik_kk_cmp) && (0 != clean_kk_kj_cmp)) + { + /* a|bb*a = b*a */ + if (R_last_kk->slen < 1) + { + sb_strdup (R_cur_r, R_last_kj); + } + else if (GNUNET_YES == needs_parentheses (&R_temp_kk)) + sb_printf2 (R_cur_r, "(%.*s)*%.*s", 3, &R_temp_kk, R_last_kj); + else + sb_printf2 (R_cur_r, "%.*s*%.*s", 1, &R_temp_kk, R_last_kj); + + R_cur_l->null_flag = GNUNET_YES; + } + else if ( (0 == ij_ik_cmp) && (0 == kk_kj_cmp) && (! has_epsilon (R_last_ij)) && + has_epsilon (R_last_kk)) + { + /* a|a(e|b)*(e|b) = a|ab* = a|a|ab|abb|abbb|... = ab* */ + if (needs_parentheses (&R_temp_kk)) + sb_printf2 (R_cur_r, "%.*s(%.*s)*", 3, R_last_ij, &R_temp_kk); + else + sb_printf2 (R_cur_r, "%.*s%.*s*", 1, R_last_ij, &R_temp_kk); + R_cur_l->null_flag = GNUNET_YES; + } + else if ( (0 == ij_kj_cmp) && (0 == ik_kk_cmp) && (! has_epsilon (R_last_ij)) && + has_epsilon (R_last_kk)) + { + /* a|(e|b)(e|b)*a = a|b*a = a|a|ba|bba|bbba|... = b*a */ + if (needs_parentheses (&R_temp_kk)) + sb_printf2 (R_cur_r, "(%.*s)*%.*s", 3, &R_temp_kk, R_last_ij); + else + sb_printf2 (R_cur_r, "%.*s*%.*s", 1, &R_temp_kk, R_last_ij); + R_cur_l->null_flag = GNUNET_YES; + } else - GNUNET_asprintf (&tmp, "%c", t->label); + { + sb_strdup (R_cur_l, R_last_ij); + remove_parentheses (R_cur_l); + } + } + else + { + /* we have no left side */ + R_cur_l->null_flag = GNUNET_YES; + } - if (NULL != s->proof) - s->proof = - GNUNET_realloc (s->proof, strlen (s->proof) + strlen (tmp) + 1); + /* construct R_cur_r, if not already constructed */ + if (GNUNET_YES == R_cur_r->null_flag) + { + length = R_temp_kk.slen - R_last_ik->slen; + + /* a(ba)*bx = (ab)+x */ + if ( (length > 0) && + (GNUNET_YES != R_last_kk->null_flag) && + (0 < R_last_kk->slen) && + (GNUNET_YES != R_last_kj->null_flag) && + (0 < R_last_kj->slen) && + (GNUNET_YES != R_last_ik->null_flag) && + (0 < R_last_ik->slen) && + (0 == sb_strkcmp (&R_temp_kk, R_last_ik, length)) && + (0 == sb_strncmp (&R_temp_kk, R_last_kj, length)) ) + { + struct StringBuffer temp_a; + struct StringBuffer temp_b; + + sb_init (&temp_a, length); + sb_init (&temp_b, R_last_kj->slen - length); + + length_l = length; + temp_a.sbuf = temp_a.abuf; + memcpy (temp_a.sbuf, R_last_kj->sbuf, length_l); + temp_a.slen = length_l; + + length_r = R_last_kj->slen - length; + temp_b.sbuf = temp_b.abuf; + memcpy (temp_b.sbuf, &R_last_kj->sbuf[length], length_r); + temp_b.slen = length_r; + + /* e|(ab)+ = (ab)* */ + if ( (GNUNET_YES != R_cur_l->null_flag) && + (0 == R_cur_l->slen) && + (0 == temp_b.slen) ) + { + sb_printf2 (R_cur_r, "(%.*s%.*s)*", 3, R_last_ik, &temp_a); + sb_free (R_cur_l); + R_cur_l->null_flag = GNUNET_YES; + } + else + { + sb_printf3 (R_cur_r, "(%.*s%.*s)+%.*s", 3, R_last_ik, &temp_a, &temp_b); + } + sb_free (&temp_a); + sb_free (&temp_b); + } + else if (0 == sb_strcmp (&R_temp_ik, &R_temp_kk) && + 0 == sb_strcmp (&R_temp_kk, &R_temp_kj)) + { + /* + * (e|a)a*(e|a) = a* + * (e|a)(e|a)*(e|a) = a* + */ + if (has_epsilon (R_last_ik) && has_epsilon (R_last_kj)) + { + if (needs_parentheses (&R_temp_kk)) + sb_printf1 (R_cur_r, "(%.*s)*", 3, &R_temp_kk); + else + sb_printf1 (R_cur_r, "%.*s*", 1, &R_temp_kk); + } + /* aa*a = a+a */ + else if ( (0 == clean_ik_kk_cmp) && + (0 == clean_kk_kj_cmp) && + (! has_epsilon (R_last_ik)) ) + { + if (needs_parentheses (&R_temp_kk)) + sb_printf2 (R_cur_r, "(%.*s)+%.*s", 3, &R_temp_kk, &R_temp_kk); + else + sb_printf2 (R_cur_r, "%.*s+%.*s", 1, &R_temp_kk, &R_temp_kk); + } + /* + * (e|a)a*a = a+ + * aa*(e|a) = a+ + * a(e|a)*(e|a) = a+ + * (e|a)a*a = a+ + */ + else + { + eps_check = + (has_epsilon (R_last_ik) + has_epsilon (R_last_kk) + + has_epsilon (R_last_kj)); + + if (1 == eps_check) + { + if (needs_parentheses (&R_temp_kk)) + sb_printf1 (R_cur_r, "(%.*s)+", 3, &R_temp_kk); + else + sb_printf1 (R_cur_r, "%.*s+", 1, &R_temp_kk); + } + } + } + /* + * aa*b = a+b + * (e|a)(e|a)*b = a*b + */ + else if (0 == sb_strcmp (&R_temp_ik, &R_temp_kk)) + { + if (has_epsilon (R_last_ik)) + { + if (needs_parentheses (&R_temp_kk)) + sb_printf2 (R_cur_r, "(%.*s)*%.*s", 3, &R_temp_kk, R_last_kj); + else + sb_printf2 (R_cur_r, "%.*s*%.*s", 1, &R_temp_kk, R_last_kj); + } + else + { + if (needs_parentheses (&R_temp_kk)) + sb_printf2 (R_cur_r, "(%.*s)+%.*s", 3, &R_temp_kk, R_last_kj); + else + sb_printf2 (R_cur_r, "%.*s+%.*s", 1, &R_temp_kk, R_last_kj); + } + } + /* + * ba*a = ba+ + * b(e|a)*(e|a) = ba* + */ + else if (0 == sb_strcmp (&R_temp_kk, &R_temp_kj)) + { + if (has_epsilon (R_last_kj)) + { + if (needs_parentheses (&R_temp_kk)) + sb_printf2 (R_cur_r, "%.*s(%.*s)*", 3, R_last_ik, &R_temp_kk); + else + sb_printf2 (R_cur_r, "%.*s%.*s*", 1, R_last_ik, &R_temp_kk); + } + else + { + if (needs_parentheses (&R_temp_kk)) + sb_printf2 (R_cur_r, "(%.*s)+%.*s", 3, R_last_ik, &R_temp_kk); + else + sb_printf2 (R_cur_r, "%.*s+%.*s", 1, R_last_ik, &R_temp_kk); + } + } else - s->proof = GNUNET_malloc (strlen (tmp) + 1); - strcat (s->proof, tmp); - GNUNET_free (tmp); + { + if (0 < R_temp_kk.slen) + { + if (needs_parentheses (&R_temp_kk)) + { + sb_printf3 (R_cur_r, "%.*s(%.*s)*%.*s", 3, R_last_ik, &R_temp_kk, + R_last_kj); + } + else + { + sb_printf3 (R_cur_r, "%.*s%.*s*%.*s", 1, R_last_ik, &R_temp_kk, + R_last_kj); + } + } + else + { + sb_printf2 (R_cur_r, "%.*s%.*s", 0, R_last_ik, R_last_kj); + } + } } + sb_free (&R_temp_ij); + sb_free (&R_temp_ik); + sb_free (&R_temp_kk); + sb_free (&R_temp_kj); + + if ( (GNUNET_YES == R_cur_l->null_flag) && + (GNUNET_YES == R_cur_r->null_flag) ) + { + R_cur_ij->null_flag = GNUNET_YES; + return; + } + + if ( (GNUNET_YES != R_cur_l->null_flag) && + (GNUNET_YES == R_cur_r->null_flag) ) + { + struct StringBuffer tmp; + + tmp = *R_cur_ij; + *R_cur_ij = *R_cur_l; + *R_cur_l = tmp; + return; + } + + if ( (GNUNET_YES == R_cur_l->null_flag) && + (GNUNET_YES != R_cur_r->null_flag) ) + { + struct StringBuffer tmp; + + tmp = *R_cur_ij; + *R_cur_ij = *R_cur_r; + *R_cur_r = tmp; + return; + } + + if (0 == sb_nullstrcmp (R_cur_l, R_cur_r)) + { + struct StringBuffer tmp; + + tmp = *R_cur_ij; + *R_cur_ij = *R_cur_l; + *R_cur_l = tmp; + return; + } + sb_printf2 (R_cur_ij, "(%.*s|%.*s)", 3, R_cur_l, R_cur_r); } + /** - * Create proofs for all states in the given automaton. + * Create proofs for all states in the given automaton. Implementation of the + * algorithm descriped in chapter 3.2.1 of "Automata Theory, Languages, and + * Computation 3rd Edition" by Hopcroft, Motwani and Ullman. * - * @param a automaton. + * Each state in the automaton gets assigned 'proof' and 'hash' (hash of the + * proof) fields. The starting state will only have a valid proof/hash if it has + * any incoming transitions. + * + * @param a automaton for which to assign proofs and hashes, must not be NULL */ -static void +static int automaton_create_proofs (struct GNUNET_REGEX_Automaton *a) { - struct GNUNET_REGEX_State *s; + unsigned int n = a->state_count; + struct GNUNET_REGEX_State *states[n]; + struct StringBuffer *R_last; + struct StringBuffer *R_cur; + struct StringBuffer R_cur_r; + struct StringBuffer R_cur_l; + struct StringBuffer *R_swap; + struct GNUNET_REGEX_Transition *t; + struct StringBuffer complete_regex; + unsigned int i; + unsigned int j; + unsigned int k; + + R_last = GNUNET_malloc_large (sizeof (struct StringBuffer) * n * n); + R_cur = GNUNET_malloc_large (sizeof (struct StringBuffer) * n * n); + if ( (NULL == R_last) || + (NULL == R_cur) ) + { + GNUNET_log_strerror (GNUNET_ERROR_TYPE_ERROR, "malloc"); + GNUNET_free_non_null (R_cur); + GNUNET_free_non_null (R_last); + return GNUNET_SYSERR; + } + + /* create depth-first numbering of the states, initializes 'state' */ + GNUNET_REGEX_automaton_traverse (a, a->start, NULL, NULL, &number_states, + states); + + for (i = 0; i < n; i++) + GNUNET_assert (NULL != states[i]); + for (i = 0; i < n; i++) + for (j = 0; j < n; j++) + R_last[i *n + j].null_flag = GNUNET_YES; - automaton_reverse (a); + /* Compute regular expressions of length "1" between each pair of states */ + for (i = 0; i < n; i++) + { + for (t = states[i]->transitions_head; NULL != t; t = t->next) + { + j = t->to_state->dfs_id; + if (GNUNET_YES == R_last[i * n + j].null_flag) + { + sb_strdup_cstr (&R_last[i * n + j], t->label); + } + else + { + sb_append_cstr (&R_last[i * n + j], "|"); + sb_append_cstr (&R_last[i * n + j], t->label); + } + } + /* add self-loop: i is reachable from i via epsilon-transition */ + if (GNUNET_YES == R_last[i * n + i].null_flag) + { + R_last[i * n + i].slen = 0; + R_last[i * n + i].null_flag = GNUNET_NO; + } + else + { + sb_wrap (&R_last[i * n + i], "(|%.*s)", 3); + } + } + for (i = 0; i < n; i++) + for (j = 0; j < n; j++) + if (needs_parentheses (&R_last[i * n + j])) + sb_wrap (&R_last[i * n + j], "(%.*s)", 2); + /* Compute regular expressions of length "k" between each pair of states per + * induction */ + memset (&R_cur_l, 0, sizeof (struct StringBuffer)); + memset (&R_cur_r, 0, sizeof (struct StringBuffer)); + for (k = 0; k < n; k++) + { + for (i = 0; i < n; i++) + { + for (j = 0; j < n; j++) + { + /* Basis for the recursion: + * $R^{(k)}_{ij} = R^{(k-1)}_{ij} | R^{(k-1)}_{ik} ( R^{(k-1)}_{kk} )^* R^{(k-1)}_{kj} + * R_last == R^{(k-1)}, R_cur == R^{(k)} + */ + + /* Create R_cur[i][j] and simplify the expression */ + automaton_create_proofs_simplify (&R_last[i * n + j], &R_last[i * n + k], + &R_last[k * n + k], &R_last[k * n + j], + &R_cur[i * n + j], + &R_cur_l, &R_cur_r); + } + } + /* set R_last = R_cur */ + R_swap = R_last; + R_last = R_cur; + R_cur = R_swap; + /* clear 'R_cur' for next iteration */ + for (i = 0; i < n; i++) + for (j = 0; j < n; j++) + R_cur[i * n + j].null_flag = GNUNET_YES; + } + sb_free (&R_cur_l); + sb_free (&R_cur_r); + /* assign proofs and hashes */ + for (i = 0; i < n; i++) + { + if (GNUNET_YES != R_last[a->start->dfs_id * n + i].null_flag) + { + states[i]->proof = GNUNET_strndup (R_last[a->start->dfs_id * n + i].sbuf, + R_last[a->start->dfs_id * n + i].slen); + GNUNET_CRYPTO_hash (states[i]->proof, strlen (states[i]->proof), + &states[i]->hash); + } + } - for (s = a->states_head; NULL != s; s = s->next) - automaton_create_proofs_step (NULL, s); + /* complete regex for whole DFA: union of all pairs (start state/accepting + * state(s)). */ + sb_init (&complete_regex, 16 * n); + for (i = 0; i < n; i++) + { + if (states[i]->accepting) + { + if ( (0 == complete_regex.slen) && + (0 < R_last[a->start->dfs_id * n + i].slen) ) + { + sb_append (&complete_regex, + &R_last[a->start->dfs_id * n + i]); + } + else if ( (GNUNET_YES != R_last[a->start->dfs_id * n + i].null_flag) && + (0 < R_last[a->start->dfs_id * n + i].slen) ) + { + sb_append_cstr (&complete_regex, "|"); + sb_append (&complete_regex, + &R_last[a->start->dfs_id * n + i]); + } + } + } + a->canonical_regex = GNUNET_strndup (complete_regex.sbuf, complete_regex.slen); - automaton_reverse (a); + /* cleanup */ + sb_free (&complete_regex); + for (i = 0; i < n; i++) + for (j = 0; j < n; j++) + { + sb_free (&R_cur[i * n + j]); + sb_free (&R_last[i * n + j]); + } + GNUNET_free (R_cur); + GNUNET_free (R_last); + return GNUNET_OK; } + /** * Creates a new DFA state based on a set of NFA states. Needs to be freed using * automaton_destroy_state. @@ -911,24 +1767,16 @@ dfa_state_create (struct GNUNET_REGEX_Context *ctx, struct GNUNET_REGEX_StateSet *nfa_states) { struct GNUNET_REGEX_State *s; - char *name; - int len = 0; + char *pos; + size_t len; struct GNUNET_REGEX_State *cstate; - struct Transition *ctran; - int insert = 1; - struct Transition *t; - int i; + struct GNUNET_REGEX_Transition *ctran; + unsigned int i; s = GNUNET_malloc (sizeof (struct GNUNET_REGEX_State)); s->id = ctx->state_id++; - s->accepting = 0; - s->marked = 0; - s->name = NULL; - s->scc_id = 0; s->index = -1; s->lowlink = -1; - s->contained = 0; - s->proof = NULL; if (NULL == nfa_states) { @@ -936,93 +1784,103 @@ dfa_state_create (struct GNUNET_REGEX_Context *ctx, return s; } - s->nfa_set = nfa_states; + s->nfa_set = *nfa_states; - if (nfa_states->len < 1) + if (nfa_states->off < 1) return s; - // Create a name based on 'sset' - s->name = GNUNET_malloc (sizeof (char) * 2); + /* Create a name based on 'nfa_states' */ + len = nfa_states->off * 14 + 4; + s->name = GNUNET_malloc (len); strcat (s->name, "{"); - name = NULL; + pos = s->name + 1; - for (i = 0; i < nfa_states->len; i++) + for (i = 0; i < nfa_states->off; i++) { cstate = nfa_states->states[i]; - GNUNET_asprintf (&name, "%i,", cstate->id); - - if (NULL != name) - { - len = strlen (s->name) + strlen (name) + 1; - s->name = GNUNET_realloc (s->name, len); - strcat (s->name, name); - GNUNET_free (name); - name = NULL; - } - - // Add a transition for each distinct label to NULL state - for (ctran = cstate->transitions_head; NULL != ctran; ctran = ctran->next) - { - if (0 != ctran->label) - { - insert = 1; - - for (t = s->transitions_head; NULL != t; t = t->next) - { - if (t->label == ctran->label) - { - insert = 0; - break; - } - } + GNUNET_snprintf (pos, pos - s->name + len, + "%i,", cstate->id); + pos += strlen (pos); - if (insert) - state_add_transition (ctx, s, ctran->label, NULL); - } - } + /* Add a transition for each distinct label to NULL state */ + for (ctran = cstate->transitions_head; NULL != ctran; ctran = ctran->next) + if (NULL != ctran->label) + state_add_transition (ctx, s, ctran->label, NULL); - // If the nfa_states contain an accepting state, the new dfa state is also - // accepting + /* If the nfa_states contain an accepting state, the new dfa state is also + * accepting. */ if (cstate->accepting) s->accepting = 1; - } - - s->name[strlen (s->name) - 1] = '}'; + } + pos[-1] = '}'; + s->name = GNUNET_realloc (s->name, strlen (s->name) + 1); + memset (nfa_states, 0, sizeof (struct GNUNET_REGEX_StateSet)); return s; } + /** - * Move from the given state 's' to the next state on transition 'label' + * Move from the given state 's' to the next state on transition 'str'. Consumes + * as much of the given 'str' as possible (usefull for strided DFAs). On return + * 's' will point to the next state, and the length of the substring used for + * this transition will be returned. If no transition possible 0 is returned and + * 's' points to NULL. * - * @param s starting state - * @param label edge label to follow + * @param s starting state, will point to the next state or NULL (if no + * transition possible) + * @param str edge label to follow (will match longest common prefix) * - * @return new state or NULL, if transition on label not possible + * @return length of the substring comsumed from 'str' */ -static struct GNUNET_REGEX_State * -dfa_move (struct GNUNET_REGEX_State *s, const char label) +static unsigned int +dfa_move (struct GNUNET_REGEX_State **s, const char *str) { - struct Transition *t; + struct GNUNET_REGEX_Transition *t; struct GNUNET_REGEX_State *new_s; + unsigned int len; + unsigned int max_len; if (NULL == s) - return NULL; + return 0; new_s = NULL; - - for (t = s->transitions_head; NULL != t; t = t->next) + max_len = 0; + for (t = (*s)->transitions_head; NULL != t; t = t->next) { - if (label == t->label) + len = strlen (t->label); + + if (0 == strncmp (t->label, str, len)) { - new_s = t->to_state; - break; + if (len >= max_len) + { + max_len = len; + new_s = t->to_state; + } } } - return new_s; + *s = new_s; + return max_len; +} + + +/** + * Set the given state 'marked' to GNUNET_YES. Used by the + * 'dfa_remove_unreachable_states' function to detect unreachable states in the + * automaton. + * + * @param cls closure, not used. + * @param count count, not used. + * @param s state where the marked attribute will be set to GNUNET_YES. + */ +static void +mark_states (void *cls, const unsigned int count, struct GNUNET_REGEX_State *s) +{ + s->marked = GNUNET_YES; } + /** * Remove all unreachable states from DFA 'a'. Unreachable states are those * states that are not reachable from the starting state. @@ -1035,14 +1893,14 @@ dfa_remove_unreachable_states (struct GNUNET_REGEX_Automaton *a) struct GNUNET_REGEX_State *s; struct GNUNET_REGEX_State *s_next; - // 1. unmark all states + /* 1. unmark all states */ for (s = a->states_head; NULL != s; s = s->next) s->marked = GNUNET_NO; - // 2. traverse dfa from start state and mark all visited states - automaton_traverse (NULL, a, NULL); + /* 2. traverse dfa from start state and mark all visited states */ + GNUNET_REGEX_automaton_traverse (a, a->start, NULL, NULL, &mark_states, NULL); - // 3. delete all states that were not visited + /* 3. delete all states that were not visited */ for (s = a->states_head; NULL != s; s = s_next) { s_next = s->next; @@ -1051,9 +1909,10 @@ dfa_remove_unreachable_states (struct GNUNET_REGEX_Automaton *a) } } + /** * Remove all dead states from the DFA 'a'. Dead states are those states that do - * not transition to any other state but themselfes. + * not transition to any other state but themselves. * * @param a DFA automaton */ @@ -1061,13 +1920,16 @@ static void dfa_remove_dead_states (struct GNUNET_REGEX_Automaton *a) { struct GNUNET_REGEX_State *s; - struct Transition *t; + struct GNUNET_REGEX_State *s_next; + struct GNUNET_REGEX_Transition *t; int dead; GNUNET_assert (DFA == a->type); - for (s = a->states_head; NULL != s; s = s->next) + for (s = a->states_head; NULL != s; s = s_next) { + s_next = s->next; + if (s->accepting) continue; @@ -1084,54 +1946,66 @@ dfa_remove_dead_states (struct GNUNET_REGEX_Automaton *a) if (0 == dead) continue; - // state s is dead, remove it + /* state s is dead, remove it */ automaton_remove_state (a, s); } } + /** * Merge all non distinguishable states in the DFA 'a' * * @param ctx context * @param a DFA automaton + * @return GNUNET_OK on success */ -static void +static int dfa_merge_nondistinguishable_states (struct GNUNET_REGEX_Context *ctx, struct GNUNET_REGEX_Automaton *a) { - int i; - int table[a->state_count][a->state_count]; + uint32_t *table; struct GNUNET_REGEX_State *s1; struct GNUNET_REGEX_State *s2; - struct Transition *t1; - struct Transition *t2; + struct GNUNET_REGEX_Transition *t1; + struct GNUNET_REGEX_Transition *t2; struct GNUNET_REGEX_State *s1_next; struct GNUNET_REGEX_State *s2_next; int change; - int num_equal_edges; + unsigned int num_equal_edges; + unsigned int i; + unsigned int state_cnt; + unsigned long long idx; + unsigned long long idx1; - for (i = 0, s1 = a->states_head; i < a->state_count && NULL != s1; - i++, s1 = s1->next) + if ( (NULL == a) || (0 == a->state_count) ) { - s1->marked = i; + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Could not merge nondistinguishable states, automaton was NULL.\n"); + return GNUNET_SYSERR; } - // Mark all pairs of accepting/!accepting states - for (s1 = a->states_head; NULL != s1; s1 = s1->next) + state_cnt = a->state_count; + table = GNUNET_malloc_large ((sizeof (uint32_t) * state_cnt * state_cnt / 32) + sizeof (uint32_t)); + if (NULL == table) { - for (s2 = a->states_head; NULL != s2; s2 = s2->next) - { - table[s1->marked][s2->marked] = 0; + GNUNET_log_strerror (GNUNET_ERROR_TYPE_ERROR, "malloc"); + return GNUNET_SYSERR; + } + + for (i = 0, s1 = a->states_head; NULL != s1; s1 = s1->next) + s1->marked = i++; - if ((s1->accepting && !s2->accepting) || - (!s1->accepting && s2->accepting)) + /* Mark all pairs of accepting/!accepting states */ + for (s1 = a->states_head; NULL != s1; s1 = s1->next) + for (s2 = a->states_head; NULL != s2; s2 = s2->next) + if ( (s1->accepting && !s2->accepting) || + (!s1->accepting && s2->accepting) ) { - table[s1->marked][s2->marked] = 1; + idx = s1->marked * state_cnt + s2->marked; + table[idx / 32] |= (1 << (idx % 32)); } - } - } - // Find all equal states + /* Find all equal states */ change = 1; while (0 != change) { @@ -1140,75 +2014,351 @@ dfa_merge_nondistinguishable_states (struct GNUNET_REGEX_Context *ctx, { for (s2 = a->states_head; NULL != s2 && s1 != s2; s2 = s2->next) { - if (0 != table[s1->marked][s2->marked]) + idx = s1->marked * state_cnt + s2->marked; + if (0 != (table[idx / 32] & (1 << (idx % 32)))) continue; - num_equal_edges = 0; for (t1 = s1->transitions_head; NULL != t1; t1 = t1->next) { for (t2 = s2->transitions_head; NULL != t2; t2 = t2->next) { - if (t1->label == t2->label) - { - num_equal_edges++; - if (0 != table[t1->to_state->marked][t2->to_state->marked] || - 0 != table[t2->to_state->marked][t1->to_state->marked]) - { - table[s1->marked][s2->marked] = t1->label != 0 ? t1->label : 1; - change = 1; - } - } - } + if (0 == strcmp (t1->label, t2->label)) + { + num_equal_edges++; + /* same edge, but targets definitively different, so we're different + as well */ + if (t1->to_state->marked > t2->to_state->marked) + idx1 = t1->to_state->marked * state_cnt + t2->to_state->marked; + else + idx1 = t2->to_state->marked * state_cnt + t1->to_state->marked; + if (0 != (table[idx1 / 32] & (1 << (idx1 % 32)))) + { + table[idx / 32] |= (1 << (idx % 32)); + change = 1; /* changed a marker, need to run again */ + } + } + } } - if (num_equal_edges != s1->transition_count || - num_equal_edges != s2->transition_count) + if ( (num_equal_edges != s1->transition_count) || + (num_equal_edges != s2->transition_count) ) { - // Make sure ALL edges of possible equal states are the same - table[s1->marked][s2->marked] = -2; + /* Make sure ALL edges of possible equal states are the same */ + table[idx / 32] |= (1 << (idx % 32)); + change = 1; /* changed a marker, need to run again */ } } } } - // Merge states that are equal + /* Merge states that are equal */ for (s1 = a->states_head; NULL != s1; s1 = s1_next) { s1_next = s1->next; for (s2 = a->states_head; NULL != s2 && s1 != s2; s2 = s2_next) { s2_next = s2->next; - if (table[s1->marked][s2->marked] == 0) + idx = s1->marked * state_cnt + s2->marked; + if (0 == (table[idx / 32] & (1 << (idx % 32)))) automaton_merge_states (ctx, a, s1, s2); } } + + GNUNET_free (table); + return GNUNET_OK; } + /** * Minimize the given DFA 'a' by removing all unreachable states, removing all * dead states and merging all non distinguishable states * * @param ctx context * @param a DFA automaton + * @return GNUNET_OK on success */ -static void +static int dfa_minimize (struct GNUNET_REGEX_Context *ctx, struct GNUNET_REGEX_Automaton *a) { if (NULL == a) - return; + return GNUNET_SYSERR; GNUNET_assert (DFA == a->type); - // 1. remove unreachable states + /* 1. remove unreachable states */ dfa_remove_unreachable_states (a); - // 2. remove dead states + /* 2. remove dead states */ dfa_remove_dead_states (a); - // 3. Merge nondistinguishable states - dfa_merge_nondistinguishable_states (ctx, a); + /* 3. Merge nondistinguishable states */ + if (GNUNET_OK != dfa_merge_nondistinguishable_states (ctx, a)) + return GNUNET_SYSERR; + return GNUNET_OK; +} + + +/** + * Context for adding strided transitions to a DFA. + */ +struct GNUNET_REGEX_Strided_Context +{ + /** + * Length of the strides. + */ + const unsigned int stride; + + /** + * Strided transitions DLL. New strided transitions will be stored in this DLL + * and afterwards added to the DFA. + */ + struct GNUNET_REGEX_Transition *transitions_head; + + /** + * Strided transitions DLL. + */ + struct GNUNET_REGEX_Transition *transitions_tail; +}; + + +/** + * Recursive helper function to add strides to a DFA. + * + * @param cls context, contains stride length and strided transitions DLL. + * @param depth current depth of the depth-first traversal of the graph. + * @param label current label, string that contains all labels on the path from + * 'start' to 's'. + * @param start start state for the depth-first traversal of the graph. + * @param s current state in the depth-first traversal + */ +void +dfa_add_multi_strides_helper (void *cls, const unsigned int depth, char *label, + struct GNUNET_REGEX_State *start, + struct GNUNET_REGEX_State *s) +{ + struct GNUNET_REGEX_Strided_Context *ctx = cls; + struct GNUNET_REGEX_Transition *t; + char *new_label; + + if (depth == ctx->stride) + { + t = GNUNET_malloc (sizeof (struct GNUNET_REGEX_Transition)); + t->label = GNUNET_strdup (label); + t->to_state = s; + t->from_state = start; + GNUNET_CONTAINER_DLL_insert (ctx->transitions_head, ctx->transitions_tail, + t); + } + else + { + for (t = s->transitions_head; NULL != t; t = t->next) + { + /* Do not consider self-loops, because it end's up in too many + * transitions */ + if (t->to_state == t->from_state) + continue; + + if (NULL != label) + { + GNUNET_asprintf (&new_label, "%s%s", label, t->label); + } + else + new_label = GNUNET_strdup (t->label); + + dfa_add_multi_strides_helper (cls, (depth + 1), new_label, start, + t->to_state); + } + } + GNUNET_free_non_null (label); +} + + +/** + * Function called for each state in the DFA. Starts a traversal of depth set in + * context starting from state 's'. + * + * @param cls context. + * @param count not used. + * @param s current state. + */ +void +dfa_add_multi_strides (void *cls, const unsigned int count, + struct GNUNET_REGEX_State *s) +{ + dfa_add_multi_strides_helper (cls, 0, NULL, s, s); +} + + +/** + * Adds multi-strided transitions to the given 'dfa'. + * + * @param regex_ctx regex context needed to add transitions to the automaton. + * @param dfa DFA to which the multi strided transitions should be added. + * @param stride_len length of the strides. + */ +void +GNUNET_REGEX_dfa_add_multi_strides (struct GNUNET_REGEX_Context *regex_ctx, + struct GNUNET_REGEX_Automaton *dfa, + const unsigned int stride_len) +{ + struct GNUNET_REGEX_Strided_Context ctx = { stride_len, NULL, NULL }; + struct GNUNET_REGEX_Transition *t; + struct GNUNET_REGEX_Transition *t_next; + + if (1 > stride_len || GNUNET_YES == dfa->is_multistrided) + return; + + /* Compute the new transitions of given stride_len */ + GNUNET_REGEX_automaton_traverse (dfa, dfa->start, NULL, NULL, + &dfa_add_multi_strides, &ctx); + + /* Add all the new transitions to the automaton. */ + for (t = ctx.transitions_head; NULL != t; t = t_next) + { + t_next = t->next; + state_add_transition (regex_ctx, t->from_state, t->label, t->to_state); + GNUNET_CONTAINER_DLL_remove (ctx.transitions_head, ctx.transitions_tail, t); + GNUNET_free_non_null (t->label); + GNUNET_free (t); + } + + /* Mark this automaton as multistrided */ + dfa->is_multistrided = GNUNET_YES; +} + +/** + * Recursive Helper function for DFA path compression. Does DFS on the DFA graph + * and adds new transitions to the given transitions DLL and marks states that + * should be removed by setting state->contained to GNUNET_YES. + * + * @param dfa DFA for which the paths should be compressed. + * @param start starting state for linear path search. + * @param cur current state in the recursive DFS. + * @param label current label (string of traversed labels). + * @param max_len maximal path compression length. + * @param transitions_head transitions DLL. + * @param transitions_tail transitions DLL. + */ +void +dfa_compress_paths_helper (struct GNUNET_REGEX_Automaton *dfa, + struct GNUNET_REGEX_State *start, + struct GNUNET_REGEX_State *cur, char *label, + unsigned int max_len, + struct GNUNET_REGEX_Transition **transitions_head, + struct GNUNET_REGEX_Transition **transitions_tail) +{ + struct GNUNET_REGEX_Transition *t; + char *new_label; + + + if (NULL != label && + ((cur->incoming_transition_count > 1 || GNUNET_YES == cur->accepting || + GNUNET_YES == cur->marked) || (start != dfa->start && max_len > 0 && + max_len == strlen (label)) || + (start == dfa->start && GNUNET_REGEX_INITIAL_BYTES == strlen (label)))) + { + t = GNUNET_malloc (sizeof (struct GNUNET_REGEX_Transition)); + t->label = GNUNET_strdup (label); + t->to_state = cur; + t->from_state = start; + GNUNET_CONTAINER_DLL_insert (*transitions_head, *transitions_tail, t); + + if (GNUNET_NO == cur->marked) + { + dfa_compress_paths_helper (dfa, cur, cur, NULL, max_len, transitions_head, + transitions_tail); + } + return; + } + else if (cur != start) + cur->contained = GNUNET_YES; + + if (GNUNET_YES == cur->marked && cur != start) + return; + + cur->marked = GNUNET_YES; + + + for (t = cur->transitions_head; NULL != t; t = t->next) + { + if (NULL != label) + GNUNET_asprintf (&new_label, "%s%s", label, t->label); + else + new_label = GNUNET_strdup (t->label); + + if (t->to_state != cur) + { + dfa_compress_paths_helper (dfa, start, t->to_state, new_label, max_len, + transitions_head, transitions_tail); + } + GNUNET_free (new_label); + } +} + + +/** + * Compress paths in the given 'dfa'. Linear paths like 0->1->2->3 will be + * compressed to 0->3 by combining transitions. + * + * @param regex_ctx context for adding new transitions. + * @param dfa DFA representation, will directly modify the given DFA. + * @param max_len maximal length of the compressed paths. + */ +static void +dfa_compress_paths (struct GNUNET_REGEX_Context *regex_ctx, + struct GNUNET_REGEX_Automaton *dfa, unsigned int max_len) +{ + struct GNUNET_REGEX_State *s; + struct GNUNET_REGEX_State *s_next; + struct GNUNET_REGEX_Transition *t; + struct GNUNET_REGEX_Transition *t_next; + struct GNUNET_REGEX_Transition *transitions_head = NULL; + struct GNUNET_REGEX_Transition *transitions_tail = NULL; + + if (NULL == dfa) + return; + + /* Count the incoming transitions on each state. */ + for (s = dfa->states_head; NULL != s; s = s->next) + { + for (t = s->transitions_head; NULL != t; t = t->next) + { + if (NULL != t->to_state) + t->to_state->incoming_transition_count++; + } + } + + /* Unmark all states. */ + for (s = dfa->states_head; NULL != s; s = s->next) + { + s->marked = GNUNET_NO; + s->contained = GNUNET_NO; + } + + /* Add strides and mark states that can be deleted. */ + dfa_compress_paths_helper (dfa, dfa->start, dfa->start, NULL, max_len, + &transitions_head, &transitions_tail); + + /* Add all the new transitions to the automaton. */ + for (t = transitions_head; NULL != t; t = t_next) + { + t_next = t->next; + state_add_transition (regex_ctx, t->from_state, t->label, t->to_state); + GNUNET_CONTAINER_DLL_remove (transitions_head, transitions_tail, t); + GNUNET_free_non_null (t->label); + GNUNET_free (t); + } + + /* Remove marked states (including their incoming and outgoing transitions). */ + for (s = dfa->states_head; NULL != s; s = s_next) + { + s_next = s->next; + if (GNUNET_YES == s->contained) + automaton_remove_state (dfa, s); + } } + /** * Creates a new NFA fragment. Needs to be cleared using * automaton_fragment_clear. @@ -1229,19 +2379,23 @@ nfa_fragment_create (struct GNUNET_REGEX_State *start, n->type = NFA; n->start = NULL; n->end = NULL; + n->state_count = 0; - if (NULL == start && NULL == end) + if (NULL == start || NULL == end) return n; automaton_add_state (n, end); automaton_add_state (n, start); + n->state_count = 2; + n->start = start; n->end = end; return n; } + /** * Adds a list of states to the given automaton 'n'. * @@ -1279,154 +2433,105 @@ nfa_add_states (struct GNUNET_REGEX_Automaton *n, n->state_count++; } + /** * Creates a new NFA state. Needs to be freed using automaton_destroy_state. * * @param ctx context * @param accepting is it an accepting state or not * - * @return new NFA state - */ -static struct GNUNET_REGEX_State * -nfa_state_create (struct GNUNET_REGEX_Context *ctx, int accepting) -{ - struct GNUNET_REGEX_State *s; - - s = GNUNET_malloc (sizeof (struct GNUNET_REGEX_State)); - s->id = ctx->state_id++; - s->accepting = accepting; - s->marked = 0; - s->contained = 0; - s->index = -1; - s->lowlink = -1; - s->scc_id = 0; - s->name = NULL; - GNUNET_asprintf (&s->name, "s%i", s->id); - - return s; -} - -/** - * Calculates the NFA closure set for the given state. - * - * @param nfa the NFA containing 's' - * @param s starting point state - * @param label transitioning label on which to base the closure on, - * pass 0 for epsilon transition - * - * @return sorted nfa closure on 'label' (epsilon closure if 'label' is 0) - */ -static struct GNUNET_REGEX_StateSet * -nfa_closure_create (struct GNUNET_REGEX_Automaton *nfa, - struct GNUNET_REGEX_State *s, const char label) -{ - struct GNUNET_REGEX_StateSet *cls; - struct GNUNET_REGEX_StateSet *cls_check; - struct GNUNET_REGEX_State *clsstate; - struct GNUNET_REGEX_State *currentstate; - struct Transition *ctran; - - if (NULL == s) - return NULL; - - cls = GNUNET_malloc (sizeof (struct GNUNET_REGEX_StateSet)); - cls_check = GNUNET_malloc (sizeof (struct GNUNET_REGEX_StateSet)); - - for (clsstate = nfa->states_head; NULL != clsstate; clsstate = clsstate->next) - clsstate->contained = 0; - - // Add start state to closure only for epsilon closure - if (0 == label) - GNUNET_array_append (cls->states, cls->len, s); - - GNUNET_array_append (cls_check->states, cls_check->len, s); - while (cls_check->len > 0) - { - currentstate = cls_check->states[cls_check->len - 1]; - GNUNET_array_grow (cls_check->states, cls_check->len, cls_check->len - 1); - - for (ctran = currentstate->transitions_head; NULL != ctran; - ctran = ctran->next) - { - if (NULL != ctran->to_state && label == ctran->label) - { - clsstate = ctran->to_state; - - if (NULL != clsstate && 0 == clsstate->contained) - { - GNUNET_array_append (cls->states, cls->len, clsstate); - GNUNET_array_append (cls_check->states, cls_check->len, clsstate); - clsstate->contained = 1; - } - } - } - } - GNUNET_assert (0 == cls_check->len); - GNUNET_free (cls_check); + * @return new NFA state + */ +static struct GNUNET_REGEX_State * +nfa_state_create (struct GNUNET_REGEX_Context *ctx, int accepting) +{ + struct GNUNET_REGEX_State *s; - if (cls->len > 1) - qsort (cls->states, cls->len, sizeof (struct GNUNET_REGEX_State *), - state_compare); + s = GNUNET_malloc (sizeof (struct GNUNET_REGEX_State)); + s->id = ctx->state_id++; + s->accepting = accepting; + s->marked = GNUNET_NO; + s->contained = 0; + s->index = -1; + s->lowlink = -1; + s->scc_id = 0; + s->name = NULL; + GNUNET_asprintf (&s->name, "s%i", s->id); - return cls; + return s; } + /** * Calculates the closure set for the given set of states. * + * @param ret set to sorted nfa closure on 'label' (epsilon closure if 'label' is NULL) * @param nfa the NFA containing 's' * @param states list of states on which to base the closure on * @param label transitioning label for which to base the closure on, - * pass 0 for epsilon transition - * - * @return sorted nfa closure on 'label' (epsilon closure if 'label' is 0) + * pass NULL for epsilon transition */ -static struct GNUNET_REGEX_StateSet * -nfa_closure_set_create (struct GNUNET_REGEX_Automaton *nfa, - struct GNUNET_REGEX_StateSet *states, const char label) +static void +nfa_closure_set_create (struct GNUNET_REGEX_StateSet *ret, + struct GNUNET_REGEX_Automaton *nfa, + struct GNUNET_REGEX_StateSet *states, const char *label) { struct GNUNET_REGEX_State *s; - struct GNUNET_REGEX_StateSet *sset; - struct GNUNET_REGEX_StateSet *cls; - int i; - int j; - int k; - int contains; + unsigned int i; + struct GNUNET_REGEX_StateSet_MDLL cls_stack; + struct GNUNET_REGEX_State *clsstate; + struct GNUNET_REGEX_State *currentstate; + struct GNUNET_REGEX_Transition *ctran; + memset (ret, 0, sizeof (struct GNUNET_REGEX_StateSet)); if (NULL == states) - return NULL; - - cls = GNUNET_malloc (sizeof (struct GNUNET_REGEX_StateSet)); + return; - for (i = 0; i < states->len; i++) + for (i = 0; i < states->off; i++) { s = states->states[i]; - sset = nfa_closure_create (nfa, s, label); - for (j = 0; j < sset->len; j++) + /* Add start state to closure only for epsilon closure */ + if (NULL == label) + state_set_append (ret, s); + + /* initialize work stack */ + cls_stack.head = NULL; + cls_stack.tail = NULL; + GNUNET_CONTAINER_MDLL_insert (ST, cls_stack.head, cls_stack.tail, s); + cls_stack.len = 1; + + while (NULL != (currentstate = cls_stack.tail)) { - contains = 0; - for (k = 0; k < cls->len; k++) + GNUNET_CONTAINER_MDLL_remove (ST, cls_stack.head, cls_stack.tail, + currentstate); + cls_stack.len--; + for (ctran = currentstate->transitions_head; NULL != ctran; + ctran = ctran->next) { - if (sset->states[j]->id == cls->states[k]->id) - { - contains = 1; - break; - } - } - if (!contains) - GNUNET_array_append (cls->states, cls->len, sset->states[j]); + if (NULL == (clsstate = ctran->to_state)) + continue; + if (0 != clsstate->contained) + continue; + if (0 != nullstrcmp (label, ctran->label)) + continue; + state_set_append (ret, clsstate); + GNUNET_CONTAINER_MDLL_insert_tail (ST, cls_stack.head, cls_stack.tail, + clsstate); + cls_stack.len++; + clsstate->contained = 1; + } } - state_set_clear (sset); } + for (i = 0; i < ret->off; i++) + ret->states[i]->contained = 0; - if (cls->len > 1) - qsort (cls->states, cls->len, sizeof (struct GNUNET_REGEX_State *), - state_compare); - - return cls; + if (ret->off > 1) + qsort (ret->states, ret->off, sizeof (struct GNUNET_REGEX_State *), + &state_compare); } + /** * Pops two NFA fragments (a, b) from the stack and concatenates them (ab) * @@ -1437,28 +2542,32 @@ nfa_add_concatenation (struct GNUNET_REGEX_Context *ctx) { struct GNUNET_REGEX_Automaton *a; struct GNUNET_REGEX_Automaton *b; - struct GNUNET_REGEX_Automaton *new; + struct GNUNET_REGEX_Automaton *new_nfa; b = ctx->stack_tail; + GNUNET_assert (NULL != b); GNUNET_CONTAINER_DLL_remove (ctx->stack_head, ctx->stack_tail, b); a = ctx->stack_tail; + GNUNET_assert (NULL != a); GNUNET_CONTAINER_DLL_remove (ctx->stack_head, ctx->stack_tail, a); - state_add_transition (ctx, a->end, 0, b->start); + state_add_transition (ctx, a->end, NULL, b->start); a->end->accepting = 0; b->end->accepting = 1; - new = nfa_fragment_create (NULL, NULL); - nfa_add_states (new, a->states_head, a->states_tail); - nfa_add_states (new, b->states_head, b->states_tail); - new->start = a->start; - new->end = b->end; + new_nfa = nfa_fragment_create (NULL, NULL); + nfa_add_states (new_nfa, a->states_head, a->states_tail); + nfa_add_states (new_nfa, b->states_head, b->states_tail); + new_nfa->start = a->start; + new_nfa->end = b->end; + new_nfa->state_count += a->state_count + b->state_count; automaton_fragment_clear (a); automaton_fragment_clear (b); - GNUNET_CONTAINER_DLL_insert_tail (ctx->stack_head, ctx->stack_tail, new); + GNUNET_CONTAINER_DLL_insert_tail (ctx->stack_head, ctx->stack_tail, new_nfa); } + /** * Pops a NFA fragment from the stack (a) and adds a new fragment (a*) * @@ -1468,12 +2577,11 @@ static void nfa_add_star_op (struct GNUNET_REGEX_Context *ctx) { struct GNUNET_REGEX_Automaton *a; - struct GNUNET_REGEX_Automaton *new; + struct GNUNET_REGEX_Automaton *new_nfa; struct GNUNET_REGEX_State *start; struct GNUNET_REGEX_State *end; a = ctx->stack_tail; - GNUNET_CONTAINER_DLL_remove (ctx->stack_head, ctx->stack_tail, a); if (NULL == a) { @@ -1482,24 +2590,27 @@ nfa_add_star_op (struct GNUNET_REGEX_Context *ctx) return; } + GNUNET_CONTAINER_DLL_remove (ctx->stack_head, ctx->stack_tail, a); + start = nfa_state_create (ctx, 0); end = nfa_state_create (ctx, 1); - state_add_transition (ctx, start, 0, a->start); - state_add_transition (ctx, start, 0, end); - state_add_transition (ctx, a->end, 0, a->start); - state_add_transition (ctx, a->end, 0, end); + state_add_transition (ctx, start, NULL, a->start); + state_add_transition (ctx, start, NULL, end); + state_add_transition (ctx, a->end, NULL, a->start); + state_add_transition (ctx, a->end, NULL, end); a->end->accepting = 0; end->accepting = 1; - new = nfa_fragment_create (start, end); - nfa_add_states (new, a->states_head, a->states_tail); + new_nfa = nfa_fragment_create (start, end); + nfa_add_states (new_nfa, a->states_head, a->states_tail); automaton_fragment_clear (a); - GNUNET_CONTAINER_DLL_insert_tail (ctx->stack_head, ctx->stack_tail, new); + GNUNET_CONTAINER_DLL_insert_tail (ctx->stack_head, ctx->stack_tail, new_nfa); } + /** * Pops an NFA fragment (a) from the stack and adds a new fragment (a+) * @@ -1511,13 +2622,22 @@ nfa_add_plus_op (struct GNUNET_REGEX_Context *ctx) struct GNUNET_REGEX_Automaton *a; a = ctx->stack_tail; + + if (NULL == a) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "nfa_add_plus_op failed, because there was no element on the stack"); + return; + } + GNUNET_CONTAINER_DLL_remove (ctx->stack_head, ctx->stack_tail, a); - state_add_transition (ctx, a->end, 0, a->start); + state_add_transition (ctx, a->end, NULL, a->start); GNUNET_CONTAINER_DLL_insert_tail (ctx->stack_head, ctx->stack_tail, a); } + /** * Pops an NFA fragment (a) from the stack and adds a new fragment (a?) * @@ -1527,12 +2647,11 @@ static void nfa_add_question_op (struct GNUNET_REGEX_Context *ctx) { struct GNUNET_REGEX_Automaton *a; - struct GNUNET_REGEX_Automaton *new; + struct GNUNET_REGEX_Automaton *new_nfa; struct GNUNET_REGEX_State *start; struct GNUNET_REGEX_State *end; a = ctx->stack_tail; - GNUNET_CONTAINER_DLL_remove (ctx->stack_head, ctx->stack_tail, a); if (NULL == a) { @@ -1541,22 +2660,24 @@ nfa_add_question_op (struct GNUNET_REGEX_Context *ctx) return; } + GNUNET_CONTAINER_DLL_remove (ctx->stack_head, ctx->stack_tail, a); + start = nfa_state_create (ctx, 0); end = nfa_state_create (ctx, 1); - state_add_transition (ctx, start, 0, a->start); - state_add_transition (ctx, start, 0, end); - state_add_transition (ctx, a->end, 0, end); + state_add_transition (ctx, start, NULL, a->start); + state_add_transition (ctx, start, NULL, end); + state_add_transition (ctx, a->end, NULL, end); a->end->accepting = 0; - new = nfa_fragment_create (start, end); - nfa_add_states (new, a->states_head, a->states_tail); + new_nfa = nfa_fragment_create (start, end); + nfa_add_states (new_nfa, a->states_head, a->states_tail); + GNUNET_CONTAINER_DLL_insert_tail (ctx->stack_head, ctx->stack_tail, new_nfa); automaton_fragment_clear (a); - - GNUNET_CONTAINER_DLL_insert_tail (ctx->stack_head, ctx->stack_tail, new); } + /** * Pops two NFA fragments (a, b) from the stack and adds a new NFA fragment that * alternates between a and b (a|b) @@ -1568,44 +2689,47 @@ nfa_add_alternation (struct GNUNET_REGEX_Context *ctx) { struct GNUNET_REGEX_Automaton *a; struct GNUNET_REGEX_Automaton *b; - struct GNUNET_REGEX_Automaton *new; + struct GNUNET_REGEX_Automaton *new_nfa; struct GNUNET_REGEX_State *start; struct GNUNET_REGEX_State *end; b = ctx->stack_tail; + GNUNET_assert (NULL != b); GNUNET_CONTAINER_DLL_remove (ctx->stack_head, ctx->stack_tail, b); a = ctx->stack_tail; + GNUNET_assert (NULL != a); GNUNET_CONTAINER_DLL_remove (ctx->stack_head, ctx->stack_tail, a); start = nfa_state_create (ctx, 0); end = nfa_state_create (ctx, 1); - state_add_transition (ctx, start, 0, a->start); - state_add_transition (ctx, start, 0, b->start); + state_add_transition (ctx, start, NULL, a->start); + state_add_transition (ctx, start, NULL, b->start); - state_add_transition (ctx, a->end, 0, end); - state_add_transition (ctx, b->end, 0, end); + state_add_transition (ctx, a->end, NULL, end); + state_add_transition (ctx, b->end, NULL, end); a->end->accepting = 0; b->end->accepting = 0; end->accepting = 1; - new = nfa_fragment_create (start, end); - nfa_add_states (new, a->states_head, a->states_tail); - nfa_add_states (new, b->states_head, b->states_tail); + new_nfa = nfa_fragment_create (start, end); + nfa_add_states (new_nfa, a->states_head, a->states_tail); + nfa_add_states (new_nfa, b->states_head, b->states_tail); automaton_fragment_clear (a); automaton_fragment_clear (b); - GNUNET_CONTAINER_DLL_insert_tail (ctx->stack_head, ctx->stack_tail, new); + GNUNET_CONTAINER_DLL_insert_tail (ctx->stack_head, ctx->stack_tail, new_nfa); } + /** * Adds a new nfa fragment to the stack * * @param ctx context - * @param lit label for nfa transition + * @param label label for nfa transition */ static void -nfa_add_label (struct GNUNET_REGEX_Context *ctx, const char lit) +nfa_add_label (struct GNUNET_REGEX_Context *ctx, const char *label) { struct GNUNET_REGEX_Automaton *n; struct GNUNET_REGEX_State *start; @@ -1615,12 +2739,13 @@ nfa_add_label (struct GNUNET_REGEX_Context *ctx, const char lit) start = nfa_state_create (ctx, 0); end = nfa_state_create (ctx, 1); - state_add_transition (ctx, start, lit, end); + state_add_transition (ctx, start, label, end); n = nfa_fragment_create (start, end); GNUNET_assert (NULL != n); GNUNET_CONTAINER_DLL_insert_tail (ctx->stack_head, ctx->stack_tail, n); } + /** * Initialize a new context * @@ -1636,11 +2761,11 @@ GNUNET_REGEX_context_init (struct GNUNET_REGEX_Context *ctx) } ctx->state_id = 0; ctx->transition_id = 0; - ctx->scc_id = 0; ctx->stack_head = NULL; ctx->stack_tail = NULL; } + /** * Construct an NFA by parsing the regex string of length 'len'. * @@ -1655,25 +2780,36 @@ GNUNET_REGEX_construct_nfa (const char *regex, const size_t len) struct GNUNET_REGEX_Context ctx; struct GNUNET_REGEX_Automaton *nfa; const char *regexp; + char curlabel[2]; char *error_msg; unsigned int count; unsigned int altcount; unsigned int atomcount; - unsigned int pcount; + unsigned int poff; + unsigned int psize; struct { int altcount; int atomcount; } *p; + if (NULL == regex || 0 == strlen (regex) || 0 == len) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Could not parse regex. Empty regex string provided.\n"); + + return NULL; + } GNUNET_REGEX_context_init (&ctx); regexp = regex; + curlabel[1] = '\0'; p = NULL; error_msg = NULL; altcount = 0; atomcount = 0; - pcount = 0; + poff = 0; + psize = 0; for (count = 0; count < len && *regexp; count++, regexp++) { @@ -1685,9 +2821,11 @@ GNUNET_REGEX_construct_nfa (const char *regex, const size_t len) --atomcount; nfa_add_concatenation (&ctx); } - GNUNET_array_grow (p, pcount, pcount + 1); - p[pcount - 1].altcount = altcount; - p[pcount - 1].atomcount = atomcount; + if (poff == psize) + GNUNET_array_grow (p, psize, psize * 2 + 4); + p[poff].altcount = altcount; + p[poff].atomcount = atomcount; + poff++; altcount = 0; atomcount = 0; break; @@ -1702,26 +2840,26 @@ GNUNET_REGEX_construct_nfa (const char *regex, const size_t len) altcount++; break; case ')': - if (0 == pcount) + if (0 == poff) { error_msg = "Missing opening '('"; goto error; } if (0 == atomcount) { - // Ignore this: "()" - pcount--; - altcount = p[pcount].altcount; - atomcount = p[pcount].atomcount; + /* Ignore this: "()" */ + poff--; + altcount = p[poff].altcount; + atomcount = p[poff].atomcount; break; } while (--atomcount > 0) nfa_add_concatenation (&ctx); for (; altcount > 0; altcount--) nfa_add_alternation (&ctx); - pcount--; - altcount = p[pcount].altcount; - atomcount = p[pcount].atomcount; + poff--; + altcount = p[poff].altcount; + atomcount = p[poff].atomcount; atomcount++; break; case '*': @@ -1748,21 +2886,19 @@ GNUNET_REGEX_construct_nfa (const char *regex, const size_t len) } nfa_add_question_op (&ctx); break; - case 92: /* escape: \ */ - regexp++; - count++; default: if (atomcount > 1) { --atomcount; nfa_add_concatenation (&ctx); } - nfa_add_label (&ctx, *regexp); + curlabel[0] = *regexp; + nfa_add_label (&ctx, curlabel); atomcount++; break; } } - if (0 != pcount) + if (0 != poff) { error_msg = "Unbalanced parenthesis"; goto error; @@ -1772,8 +2908,7 @@ GNUNET_REGEX_construct_nfa (const char *regex, const size_t len) for (; altcount > 0; altcount--) nfa_add_alternation (&ctx); - if (NULL != p) - GNUNET_free (p); + GNUNET_array_grow (p, psize, 0); nfa = ctx.stack_tail; GNUNET_CONTAINER_DLL_remove (ctx.stack_head, ctx.stack_tail, nfa); @@ -1784,23 +2919,34 @@ GNUNET_REGEX_construct_nfa (const char *regex, const size_t len) goto error; } + /* Remember the regex that was used to generate this NFA */ + nfa->regex = GNUNET_strdup (regex); + + /* create depth-first numbering of the states for pretty printing */ + GNUNET_REGEX_automaton_traverse (nfa, NULL, NULL, NULL, &number_states, NULL); + + /* No multistriding added so far */ + nfa->is_multistrided = GNUNET_NO; + return nfa; error: - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Could not parse regex\n"); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Could not parse regex: `%s'\n", regex); if (NULL != error_msg) GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "%s\n", error_msg); - if (NULL != p) - GNUNET_free (p); - while (NULL != ctx.stack_tail) + + GNUNET_free_non_null (p); + + while (NULL != (nfa = ctx.stack_head)) { - GNUNET_REGEX_automaton_destroy (ctx.stack_tail); - GNUNET_CONTAINER_DLL_remove (ctx.stack_head, ctx.stack_tail, - ctx.stack_tail); + GNUNET_CONTAINER_DLL_remove (ctx.stack_head, ctx.stack_tail, nfa); + GNUNET_REGEX_automaton_destroy (nfa); } + return NULL; } + /** * Create DFA states based on given 'nfa' and starting with 'dfa_state'. * @@ -1816,32 +2962,35 @@ construct_dfa_states (struct GNUNET_REGEX_Context *ctx, struct GNUNET_REGEX_Automaton *dfa, struct GNUNET_REGEX_State *dfa_state) { - struct Transition *ctran; - struct GNUNET_REGEX_State *state_iter; + struct GNUNET_REGEX_Transition *ctran; struct GNUNET_REGEX_State *new_dfa_state; struct GNUNET_REGEX_State *state_contains; - struct GNUNET_REGEX_StateSet *tmp; - struct GNUNET_REGEX_StateSet *nfa_set; + struct GNUNET_REGEX_State *state_iter; + struct GNUNET_REGEX_StateSet tmp; + struct GNUNET_REGEX_StateSet nfa_set; for (ctran = dfa_state->transitions_head; NULL != ctran; ctran = ctran->next) { - if (0 == ctran->label || NULL != ctran->to_state) + if (NULL == ctran->label || NULL != ctran->to_state) continue; - tmp = nfa_closure_set_create (nfa, dfa_state->nfa_set, ctran->label); - nfa_set = nfa_closure_set_create (nfa, tmp, 0); - state_set_clear (tmp); - new_dfa_state = dfa_state_create (ctx, nfa_set); + nfa_closure_set_create (&tmp, nfa, &dfa_state->nfa_set, ctran->label); + nfa_closure_set_create (&nfa_set, nfa, &tmp, NULL); + state_set_clear (&tmp); + state_contains = NULL; for (state_iter = dfa->states_head; NULL != state_iter; state_iter = state_iter->next) { - if (0 == state_set_compare (state_iter->nfa_set, new_dfa_state->nfa_set)) + if (0 == state_set_compare (&state_iter->nfa_set, &nfa_set)) + { state_contains = state_iter; + break; + } } - if (NULL == state_contains) { + new_dfa_state = dfa_state_create (ctx, &nfa_set); automaton_add_state (dfa, new_dfa_state); ctran->to_state = new_dfa_state; construct_dfa_states (ctx, nfa, dfa, new_dfa_state); @@ -1849,30 +2998,43 @@ construct_dfa_states (struct GNUNET_REGEX_Context *ctx, else { ctran->to_state = state_contains; - automaton_destroy_state (new_dfa_state); + state_set_clear (&nfa_set); } } } + /** - * Construct DFA for the given 'regex' of length 'len' - * - * @param regex regular expression string - * @param len length of the regular expression - * - * @return DFA, needs to be freed using GNUNET_REGEX_destroy_automaton + * Construct DFA for the given 'regex' of length 'len'. + * + * Path compression means, that for example a DFA o -> a -> b -> c -> o will be + * compressed to o -> abc -> o. Note that this parameter influences the + * non-determinism of states of the resulting NFA in the DHT (number of outgoing + * edges with the same label). For example for an application that stores IPv4 + * addresses as bitstrings it could make sense to limit the path compression to + * 4 or 8. + * + * @param regex regular expression string. + * @param len length of the regular expression. + * @param max_path_len limit the path compression length to the + * given value. If set to 1, no path compression is applied. Set to 0 for + * maximal possible path compression (generally not desireable). + * @return DFA, needs to be freed using GNUNET_REGEX_automaton_destroy. */ struct GNUNET_REGEX_Automaton * -GNUNET_REGEX_construct_dfa (const char *regex, const size_t len) +GNUNET_REGEX_construct_dfa (const char *regex, const size_t len, + unsigned int max_path_len) { struct GNUNET_REGEX_Context ctx; struct GNUNET_REGEX_Automaton *dfa; struct GNUNET_REGEX_Automaton *nfa; - struct GNUNET_REGEX_StateSet *nfa_set; + struct GNUNET_REGEX_StateSet nfa_start_eps_cls; + struct GNUNET_REGEX_StateSet singleton_set; GNUNET_REGEX_context_init (&ctx); - // Create NFA + /* Create NFA */ + // fprintf (stderr, "N"); nfa = GNUNET_REGEX_construct_nfa (regex, len); if (NULL == nfa) @@ -1884,28 +3046,43 @@ GNUNET_REGEX_construct_dfa (const char *regex, const size_t len) dfa = GNUNET_malloc (sizeof (struct GNUNET_REGEX_Automaton)); dfa->type = DFA; - - // Create DFA start state from epsilon closure - nfa_set = nfa_closure_create (nfa, nfa->start, 0); - dfa->start = dfa_state_create (&ctx, nfa_set); + dfa->regex = GNUNET_strdup (regex); + + /* Create DFA start state from epsilon closure */ + memset (&singleton_set, 0, sizeof (struct GNUNET_REGEX_StateSet)); + state_set_append (&singleton_set, nfa->start); + nfa_closure_set_create (&nfa_start_eps_cls, nfa, &singleton_set, NULL); + state_set_clear (&singleton_set); + dfa->start = dfa_state_create (&ctx, &nfa_start_eps_cls); automaton_add_state (dfa, dfa->start); + // fprintf (stderr, "D"); construct_dfa_states (&ctx, nfa, dfa, dfa->start); - GNUNET_REGEX_automaton_destroy (nfa); - // Minimize DFA - dfa_minimize (&ctx, dfa); + /* Minimize DFA */ + // fprintf (stderr, "M"); + if (GNUNET_OK != dfa_minimize (&ctx, dfa)) + { + GNUNET_REGEX_automaton_destroy (dfa); + return NULL; + } - // Calculate SCCs - scc_tarjan (&ctx, dfa); + /* Create proofs and hashes for all states */ + if (GNUNET_OK != automaton_create_proofs (dfa)) + { + GNUNET_REGEX_automaton_destroy (dfa); + return NULL; + } - // Create proofs for all states - automaton_create_proofs (dfa); + /* Compress linear DFA paths */ + if (1 != max_path_len) + dfa_compress_paths (&ctx, dfa, max_path_len); return dfa; } + /** * Free the memory allocated by constructing the GNUNET_REGEX_Automaton data * structure. @@ -1921,123 +3098,19 @@ GNUNET_REGEX_automaton_destroy (struct GNUNET_REGEX_Automaton *a) if (NULL == a) return; - for (s = a->states_head; NULL != s;) + GNUNET_free_non_null (a->regex); + GNUNET_free_non_null (a->canonical_regex); + + for (s = a->states_head; NULL != s; s = next_state) { next_state = s->next; + GNUNET_CONTAINER_DLL_remove (a->states_head, a->states_tail, s); automaton_destroy_state (s); - s = next_state; } GNUNET_free (a); } -/** - * Save the given automaton as a GraphViz dot file - * - * @param a the automaton to be saved - * @param filename where to save the file - */ -void -GNUNET_REGEX_automaton_save_graph (struct GNUNET_REGEX_Automaton *a, - const char *filename) -{ - struct GNUNET_REGEX_State *s; - struct Transition *ctran; - char *s_acc = NULL; - char *s_tran = NULL; - char *start; - char *end; - FILE *p; - - if (NULL == a) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Could not print NFA, was NULL!"); - return; - } - - if (NULL == filename || strlen (filename) < 1) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "No Filename given!"); - return; - } - - p = fopen (filename, "w"); - - if (NULL == p) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Could not open file for writing: %s", - filename); - return; - } - - start = "digraph G {\nrankdir=LR\n"; - fwrite (start, strlen (start), 1, p); - - for (s = a->states_head; NULL != s; s = s->next) - { - if (s->accepting) - { - GNUNET_asprintf (&s_acc, - "\"%s\" [shape=doublecircle, color=\"0.%i 0.8 0.95\"];\n", - s->name, s->scc_id); - } - else - { - GNUNET_asprintf (&s_acc, "\"%s\" [color=\"0.%i 0.8 0.95\"];\n", s->name, - s->scc_id); - } - - if (NULL == s_acc) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Could not print state %s\n", - s->name); - return; - } - fwrite (s_acc, strlen (s_acc), 1, p); - GNUNET_free (s_acc); - s_acc = NULL; - - for (ctran = s->transitions_head; NULL != ctran; ctran = ctran->next) - { - if (NULL == ctran->to_state) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "Transition from State %i has has no state for transitioning\n", - s->id); - continue; - } - - if (ctran->label == 0) - { - GNUNET_asprintf (&s_tran, - "\"%s\" -> \"%s\" [label = \"epsilon\", color=\"0.%i 0.8 0.95\"];\n", - s->name, ctran->to_state->name, s->scc_id); - } - else - { - GNUNET_asprintf (&s_tran, - "\"%s\" -> \"%s\" [label = \"%c\", color=\"0.%i 0.8 0.95\"];\n", - s->name, ctran->to_state->name, ctran->label, - s->scc_id); - } - - if (NULL == s_tran) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Could not print state %s\n", - s->name); - return; - } - - fwrite (s_tran, strlen (s_tran), 1, p); - GNUNET_free (s_tran); - s_tran = NULL; - } - } - - end = "\n}\n"; - fwrite (end, strlen (end), 1, p); - fclose (p); -} /** * Evaluates the given string using the given DFA automaton @@ -2052,6 +3125,7 @@ evaluate_dfa (struct GNUNET_REGEX_Automaton *a, const char *string) { const char *strp; struct GNUNET_REGEX_State *s; + unsigned int step_len; if (DFA != a->type) { @@ -2062,9 +3136,14 @@ evaluate_dfa (struct GNUNET_REGEX_Automaton *a, const char *string) s = a->start; - for (strp = string; NULL != strp && *strp; strp++) + /* If the string is empty but the starting state is accepting, we accept. */ + if ((NULL == string || 0 == strlen (string)) && s->accepting) + return 0; + + for (strp = string; NULL != strp && *strp; strp += step_len) { - s = dfa_move (s, *strp); + step_len = dfa_move (&s, strp); + if (NULL == s) break; } @@ -2075,6 +3154,7 @@ evaluate_dfa (struct GNUNET_REGEX_Automaton *a, const char *string) return 1; } + /** * Evaluates the given string using the given NFA automaton * @@ -2087,10 +3167,12 @@ static int evaluate_nfa (struct GNUNET_REGEX_Automaton *a, const char *string) { const char *strp; + char str[2]; struct GNUNET_REGEX_State *s; - struct GNUNET_REGEX_StateSet *sset; - struct GNUNET_REGEX_StateSet *new_sset; - int i; + struct GNUNET_REGEX_StateSet sset; + struct GNUNET_REGEX_StateSet new_sset; + struct GNUNET_REGEX_StateSet singleton_set; + unsigned int i; int result; if (NFA != a->type) @@ -2100,32 +3182,41 @@ evaluate_nfa (struct GNUNET_REGEX_Automaton *a, const char *string) return -1; } + /* If the string is empty but the starting state is accepting, we accept. */ + if ((NULL == string || 0 == strlen (string)) && a->start->accepting) + return 0; + result = 1; - strp = string; - sset = nfa_closure_create (a, a->start, 0); + memset (&singleton_set, 0, sizeof (struct GNUNET_REGEX_StateSet)); + state_set_append (&singleton_set, a->start); + nfa_closure_set_create (&sset, a, &singleton_set, NULL); + state_set_clear (&singleton_set); + str[1] = '\0'; for (strp = string; NULL != strp && *strp; strp++) { - new_sset = nfa_closure_set_create (a, sset, *strp); - state_set_clear (sset); - sset = nfa_closure_set_create (a, new_sset, 0); - state_set_clear (new_sset); + str[0] = *strp; + nfa_closure_set_create (&new_sset, a, &sset, str); + state_set_clear (&sset); + nfa_closure_set_create (&sset, a, &new_sset, 0); + state_set_clear (&new_sset); } - for (i = 0; i < sset->len; i++) + for (i = 0; i < sset.off; i++) { - s = sset->states[i]; - if (NULL != s && s->accepting) + s = sset.states[i]; + if ( (NULL != s) && (s->accepting) ) { result = 0; break; } } - state_set_clear (sset); + state_set_clear (&sset); return result; } + /** * Evaluates the given 'string' against the given compiled regex * @@ -2157,9 +3248,55 @@ GNUNET_REGEX_eval (struct GNUNET_REGEX_Automaton *a, const char *string) return result; } + +/** + * Get the canonical regex of the given automaton. + * When constructing the automaton a proof is computed for each state, + * consisting of the regular expression leading to this state. A complete + * regex for the automaton can be computed by combining these proofs. + * As of now this function is only useful for testing. + * + * @param a automaton for which the canonical regex should be returned. + * + * @return + */ +const char * +GNUNET_REGEX_get_canonical_regex (struct GNUNET_REGEX_Automaton *a) +{ + if (NULL == a) + return NULL; + + return a->canonical_regex; +} + + +/** + * Get the number of transitions that are contained in the given automaton. + * + * @param a automaton for which the number of transitions should be returned. + * + * @return number of transitions in the given automaton. + */ +unsigned int +GNUNET_REGEX_get_transition_count (struct GNUNET_REGEX_Automaton *a) +{ + unsigned int t_count; + struct GNUNET_REGEX_State *s; + + if (NULL == a) + return 0; + + t_count = 0; + for (s = a->states_head; NULL != s; s = s->next) + t_count += s->transition_count; + + return t_count; +} + + /** * Get the first key for the given 'input_string'. This hashes the first x bits - * of the 'input_strings'. + * of the 'input_string'. * * @param input_string string. * @param string_len length of the 'input_string'. @@ -2168,13 +3305,15 @@ GNUNET_REGEX_eval (struct GNUNET_REGEX_Automaton *a, const char *string) * @return number of bits of 'input_string' that have been consumed * to construct the key */ -unsigned int -GNUNET_REGEX_get_first_key (const char *input_string, unsigned int string_len, - GNUNET_HashCode * key) +size_t +GNUNET_REGEX_get_first_key (const char *input_string, size_t string_len, + struct GNUNET_HashCode * key) { unsigned int size; - size = string_len < initial_bits ? string_len : initial_bits; + size = + string_len < + GNUNET_REGEX_INITIAL_BYTES ? string_len : GNUNET_REGEX_INITIAL_BYTES; if (NULL == input_string) { @@ -2187,49 +3326,125 @@ GNUNET_REGEX_get_first_key (const char *input_string, unsigned int string_len, return size; } + /** * Check if the given 'proof' matches the given 'key'. * - * @param proof partial regex - * @param key hash + * @param proof partial regex of a state. + * @param key hash of a state. * - * @return GNUNET_OK if the proof is valid for the given key + * @return GNUNET_OK if the proof is valid for the given key. */ int -GNUNET_REGEX_check_proof (const char *proof, const GNUNET_HashCode * key) +GNUNET_REGEX_check_proof (const char *proof, const struct GNUNET_HashCode *key) { - return GNUNET_OK; + struct GNUNET_HashCode key_check; + + if (NULL == proof || NULL == key) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Proof check failed, was NULL.\n"); + return GNUNET_NO; + } + + GNUNET_CRYPTO_hash (proof, strlen (proof), &key_check); + return (0 == + GNUNET_CRYPTO_hash_cmp (key, &key_check)) ? GNUNET_OK : GNUNET_NO; } + /** - * Iterate over all edges helper function starting from state 's', calling - * iterator on for each edge. + * Recursive function that calls the iterator for each synthetic start state. * - * @param s state. + * @param min_len minimum length of the path in the graph. + * @param max_len maximum length of the path in the graph. + * @param consumed_string string consumed by traversing the graph till this state. + * @param state current state of the automaton. * @param iterator iterator function called for each edge. - * @param iterator_cls closure. + * @param iterator_cls closure for the iterator function. */ static void -iterate_edge (struct GNUNET_REGEX_State *s, GNUNET_REGEX_KeyIterator iterator, - void *iterator_cls) +iterate_initial_edge (const unsigned int min_len, const unsigned int max_len, + char *consumed_string, struct GNUNET_REGEX_State *state, + GNUNET_REGEX_KeyIterator iterator, void *iterator_cls) { - struct Transition *t; - struct GNUNET_REGEX_Edge edges[s->transition_count]; - unsigned int num_edges; + unsigned int i; + char *temp; + struct GNUNET_REGEX_Transition *t; + unsigned int num_edges = state->transition_count; + struct GNUNET_REGEX_Edge edges[num_edges]; + struct GNUNET_REGEX_Edge edge[1]; + struct GNUNET_HashCode hash; + struct GNUNET_HashCode hash_new; + + unsigned int cur_len; + + if (NULL != consumed_string) + cur_len = strlen (consumed_string); + else + cur_len = 0; - if (GNUNET_YES != s->marked) + if ((cur_len >= min_len || GNUNET_YES == state->accepting) && cur_len > 0 && + NULL != consumed_string) { - s->marked = GNUNET_YES; + if (cur_len <= max_len) + { + if (state->proof != NULL && 0 != strcmp (consumed_string, state->proof)) + { + for (i = 0, t = state->transitions_head; NULL != t && i < num_edges; + t = t->next, i++) + { + edges[i].label = t->label; + edges[i].destination = t->to_state->hash; + } + GNUNET_CRYPTO_hash (consumed_string, strlen (consumed_string), &hash); + iterator (iterator_cls, &hash, consumed_string, state->accepting, + num_edges, edges); + } - num_edges = state_get_edges (s, edges); + if (GNUNET_YES == state->accepting && cur_len > 1 && + state->transition_count < 1 && cur_len < max_len) + { + /* Special case for regex consisting of just a string that is shorter than + * max_len */ + edge[0].label = &consumed_string[cur_len - 1]; + edge[0].destination = state->hash; + temp = GNUNET_strdup (consumed_string); + temp[cur_len - 1] = '\0'; + GNUNET_CRYPTO_hash (temp, cur_len - 1, &hash_new); + iterator (iterator_cls, &hash_new, temp, GNUNET_NO, 1, edge); + GNUNET_free (temp); + } + } + else if (max_len < cur_len) + { + /* Case where the concatenated labels are longer than max_len, then split. */ + edge[0].label = &consumed_string[max_len]; + edge[0].destination = state->hash; + temp = GNUNET_strdup (consumed_string); + temp[max_len] = '\0'; + GNUNET_CRYPTO_hash (temp, max_len, &hash); + iterator (iterator_cls, &hash, temp, GNUNET_NO, 1, edge); + GNUNET_free (temp); + } + } - iterator (iterator_cls, &s->hash, s->proof, s->accepting, num_edges, edges); + if (cur_len < max_len) + { + for (t = state->transitions_head; NULL != t; t = t->next) + { + if (NULL != consumed_string) + GNUNET_asprintf (&temp, "%s%s", consumed_string, t->label); + else + GNUNET_asprintf (&temp, "%s", t->label); - for (t = s->transitions_head; NULL != t; t = t->next) - iterate_edge (t->to_state, iterator, iterator_cls); + iterate_initial_edge (min_len, max_len, temp, t->to_state, iterator, + iterator_cls); + GNUNET_free (temp); + } } } + /** * Iterate over all edges starting from start state of automaton 'a'. Calling * iterator for each edge. @@ -2246,7 +3461,133 @@ GNUNET_REGEX_iterate_all_edges (struct GNUNET_REGEX_Automaton *a, struct GNUNET_REGEX_State *s; for (s = a->states_head; NULL != s; s = s->next) + { + struct GNUNET_REGEX_Edge edges[s->transition_count]; + unsigned int num_edges; + + num_edges = state_get_edges (s, edges); + + if ((NULL != s->proof && 0 < strlen (s->proof)) || s->accepting) + iterator (iterator_cls, &s->hash, s->proof, s->accepting, num_edges, + edges); + s->marked = GNUNET_NO; + } + + iterate_initial_edge (GNUNET_REGEX_INITIAL_BYTES, GNUNET_REGEX_INITIAL_BYTES, + NULL, a->start, iterator, iterator_cls); +} + +/** + * Create a string with binary IP notation for the given 'addr' in 'str'. + * + * @param af address family of the given 'addr'. + * @param addr address that should be converted to a string. + * struct in_addr * for IPv4 and struct in6_addr * for IPv6. + * @param str string that will contain binary notation of 'addr'. Expected + * to be at least 33 bytes long for IPv4 and 129 bytes long for IPv6. + */ +static void +iptobinstr (const int af, const void *addr, char *str) +{ + int i; + + switch (af) + { + case AF_INET: + { + uint32_t b = htonl (((struct in_addr *) addr)->s_addr); + + str[32] = '\0'; + str += 31; + for (i = 31; i >= 0; i--) + { + *str = (b & 1) + '0'; + str--; + b >>= 1; + } + break; + } + case AF_INET6: + { + struct in6_addr b = *(const struct in6_addr *) addr; + + str[128] = '\0'; + str += 127; + for (i = 127; i >= 0; i--) + { + *str = (b.s6_addr[i / 8] & 1) + '0'; + str--; + b.s6_addr[i / 8] >>= 1; + } + break; + } + } +} + + +/** + * Get the ipv4 network prefix from the given 'netmask'. + * + * @param netmask netmask for which to get the prefix len. + * + * @return length of ipv4 prefix for 'netmask'. + */ +static unsigned int +ipv4netmasktoprefixlen (const char *netmask) +{ + struct in_addr a; + unsigned int len; + uint32_t t; + + if (1 != inet_pton (AF_INET, netmask, &a)) + return 0; + len = 32; + for (t = htonl (~a.s_addr); 0 != t; t >>= 1) + len--; + return len; +} - iterate_edge (a->start, iterator, iterator_cls); + +/** + * Create a regex in 'rxstr' from the given 'ip' and 'netmask'. + * + * @param ip IPv4 representation. + * @param netmask netmask for the ip. + * @param rxstr generated regex, must be at least GNUNET_REGEX_IPV4_REGEXLEN + * bytes long. + */ +void +GNUNET_REGEX_ipv4toregex (const struct in_addr *ip, const char *netmask, + char *rxstr) +{ + unsigned int pfxlen; + + pfxlen = ipv4netmasktoprefixlen (netmask); + iptobinstr (AF_INET, ip, rxstr); + rxstr[pfxlen] = '\0'; + if (pfxlen < 32) + strcat (rxstr, "(0|1)+"); +} + + +/** + * Create a regex in 'rxstr' from the given 'ipv6' and 'prefixlen'. + * + * @param ipv6 IPv6 representation. + * @param prefixlen length of the ipv6 prefix. + * @param rxstr generated regex, must be at least GNUNET_REGEX_IPV6_REGEXLEN + * bytes long. + */ +void +GNUNET_REGEX_ipv6toregex (const struct in6_addr *ipv6, unsigned int prefixlen, + char *rxstr) +{ + iptobinstr (AF_INET6, ipv6, rxstr); + rxstr[prefixlen] = '\0'; + if (prefixlen < 128) + strcat (rxstr, "(0|1)+"); } + + +/* end of regex.c */ diff --git a/src/regex/regex_block_lib.c b/src/regex/regex_block_lib.c new file mode 100644 index 0000000..95361ca --- /dev/null +++ b/src/regex/regex_block_lib.c @@ -0,0 +1,210 @@ +/* + This file is part of GNUnet. + (C) 2012,2013 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ +/** + * @author Bartlomiej Polot + * @file regex/regex_block_lib.c + */ +#include "platform.h" +#include "regex_block_lib.h" + + +/** + * Struct to keep track of the xquery while iterating all the edges in a block. + */ +struct regex_block_xquery_ctx +{ + /** + * Xquery: string we are looking for. + */ + const char *xquery; + + /** + * Has any edge matched the xquery so far? (GNUNET_OK / GNUNET_NO) + */ + int found; +}; + + +/** + * Iterator over all edges in a block, checking for a presence of a given query. + * + * @param cls Closure, (xquery context). + * @param token Token that follows to next state. + * @param len Lenght of token. + * @param key Hash of next state. + * + * @return GNUNET_YES, to keep iterating + */ +static int +check_edge (void *cls, + const char *token, + size_t len, + const struct GNUNET_HashCode *key) +{ + struct regex_block_xquery_ctx *ctx = cls; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " edge %.*s [%u]\n", + (int) len, token, len); + if (strlen (ctx->xquery) < len) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " too long!\n"); + return GNUNET_YES; + } + if (0 == strncmp (ctx->xquery, token, len)) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " OK!\n"); + ctx->found = GNUNET_OK; + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " KO!\n"); + } + + return GNUNET_YES; /* keep checking for malformed data! */ +} + + +/** + * Check if the regex block is well formed, including all edges + * + * @param block The start of the block. + * @param size The size of the block. + * @param xquery String describing the edge we are looking for. + * + * @return GNUNET_OK in case it's fine. + * GNUNET_NO in case the xquery is not found. + * GNUNET_SYSERR if the block is invalid. + */ +int +GNUNET_REGEX_block_check (const struct RegexBlock *block, + size_t size, + const char *xquery) +{ + int res; + struct regex_block_xquery_ctx ctx; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "* Checking block with xquery \"%s\"\n", + xquery); + if ( (GNUNET_YES == ntohl(block->accepting)) && ('\0' == xquery[0]) ) + return GNUNET_OK; + ctx.xquery = xquery; + ctx.found = GNUNET_NO; + res = GNUNET_REGEX_block_iterate (block, size, &check_edge, &ctx); + if (GNUNET_SYSERR == res) + return GNUNET_SYSERR; + return ctx.found; +} + + +/** + * Iterate over all edges of a block of a regex state. + * + * @param block Block to iterate over. + * @param size Size of block. + * @param iterator Function to call on each edge in the block. + * @param iter_cls Closure for the iterator. + * + * @return How many bytes of block have been processed + */ +int +GNUNET_REGEX_block_iterate (const struct RegexBlock *block, + size_t size, + GNUNET_REGEX_EgdeIterator iterator, + void *iter_cls) +{ + struct RegexEdge *edge; + unsigned int n; + unsigned int n_token; + unsigned int i; + size_t offset; + char *aux; + + offset = sizeof (struct RegexBlock); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "* Start iterating block of size %u, off %u\n", + size, offset); + if (offset > size) // Is it safe to access the regex block? + { + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + "* Block is smaller than struct RegexBlock, END\n"); + GNUNET_break_op (0); + return GNUNET_SYSERR; + } + n = ntohl (block->n_proof); + offset += n; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "* Proof length: %u, off %u\n", n, offset); + if (offset > size) // Is it safe to access the regex proof? + { + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + "* Block is smaller than Block + proof, END\n"); + GNUNET_break_op (0); + return GNUNET_SYSERR; + } + aux = (char *) &block[1]; // Skip regex block + aux = &aux[n]; // Skip regex proof + n = ntohl (block->n_edges); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "* Edges: %u\n", n); + for (i = 0; i < n; i++) // aux always points at the end of the previous block + { + offset += sizeof (struct RegexEdge); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "* Edge %u, off %u\n", i, offset); + if (offset > size) // Is it safe to access the next edge block? + { + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + "* Size not enough for RegexEdge, END\n"); + GNUNET_break_op (0); + return GNUNET_SYSERR; + } + edge = (struct RegexEdge *) aux; + n_token = ntohl (edge->n_token); + offset += n_token; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "* Token lenght %u, off %u\n", n_token, offset); + if (offset > size) // Is it safe to access the edge token? + { + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + "* Size not enough for edge token, END\n"); + GNUNET_break_op (0); + return GNUNET_SYSERR; + } + aux = (char *) &edge[1]; // Skip edge block + if (NULL != iterator) + if (GNUNET_NO == iterator (iter_cls, aux, n_token, &edge->key)) + return GNUNET_OK; + aux = &aux[n_token]; // Skip edge token + } + // The total size should be exactly the size of (regex + all edges) blocks + // If size == -1, block is from cache and therefore previously checked and + // assumed correct. + if (offset == size || SIZE_MAX == size) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "* Block processed, END OK\n"); + return GNUNET_OK; + } + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + "* Size %u (%d), read %u END KO\n", size, size, offset); + GNUNET_break_op (0); + return GNUNET_SYSERR; +} + +/* end of regex_block_lib.c */ diff --git a/src/regex/regex_block_lib.h b/src/regex/regex_block_lib.h new file mode 100644 index 0000000..f591f5f --- /dev/null +++ b/src/regex/regex_block_lib.h @@ -0,0 +1,98 @@ +/* + This file is part of GNUnet. + (C) 2012,2013 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @author Bartlomiej Polot + * @file regex/regex_block_lib.h + */ + +#ifndef REGEX_BLOCK_LIB_H_ +#define REGEX_BLOCK_LIB_H_ + +#ifdef __cplusplus +extern "C" +{ +#if 0 + /* keep Emacsens' auto-indent happy */ +} +#endif +#endif + +#include "platform.h" +#include "block_regex.h" + +/** + * Check if the regex block is well formed, including all edges + * + * @param block The start of the block. + * @param size The size of the block. + * @param xquery String describing the edge we are looking for. + * + * @return GNUNET_OK in case it's fine. + * GNUNET_NO in case the xquery is not found. + * GNUNET_SYSERR if the block is invalid. + */ +int +GNUNET_REGEX_block_check (const struct RegexBlock *block, + size_t size, + const char *xquery); + +/** + * Iterator over edges in a block. + * + * @param cls Closure. + * @param token Token that follows to next state. + * @param len Length of token. + * @param key Hash of next state. + * + * @return GNUNET_YES if should keep iterating, GNUNET_NO otherwise. + */ +typedef int (*GNUNET_REGEX_EgdeIterator)(void *cls, + const char *token, + size_t len, + const struct GNUNET_HashCode *key); + + +/** + * Iterate over all edges of a block of a regex state. + * + * @param block Block to iterate over. + * @param size Size of block. + * @param iterator Function to call on each edge in the block. + * @param iter_cls Closure for the iterator. + * + * @return GNUNET_SYSERR if an error has been encountered, GNUNET_OK otherwise + */ +int +GNUNET_REGEX_block_iterate (const struct RegexBlock *block, + size_t size, + GNUNET_REGEX_EgdeIterator iterator, + void *iter_cls); + +#if 0 /* keep Emacsens' auto-indent happy */ +{ +#endif +#ifdef __cplusplus +} +#endif + +/* ifndef REGEX_BLOCK_LIB_H */ +#endif +/* end of regex_block_lib.h */ diff --git a/src/regex/regex_dht.c b/src/regex/regex_dht.c new file mode 100644 index 0000000..52e8d48 --- /dev/null +++ b/src/regex/regex_dht.c @@ -0,0 +1,790 @@ +/* + This file is part of GNUnet + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ +/** + * @file src/regex/regex_dht.c + * @brief library to announce regexes in the network and match strings + * against published regexes. + * @author Bartlomiej Polot + */ +#include "platform.h" +#include "gnunet_regex_lib.h" +#include "regex_block_lib.h" +#include "gnunet_dht_service.h" +#include "gnunet_statistics_service.h" + +#define LOG(kind,...) GNUNET_log_from (kind,"regex-dht",__VA_ARGS__) + +#define DHT_REPLICATION 5 +#define DHT_TTL GNUNET_TIME_UNIT_HOURS + +struct GNUNET_REGEX_announce_handle +{ + /** + * DHT handle to use, must be initialized externally. + */ + struct GNUNET_DHT_Handle *dht; + + /** + * Regular expression. + */ + const char *regex; + + /** + * Automaton representation of the regex (expensive to build). + */ + struct GNUNET_REGEX_Automaton* dfa; + + /** + * Identity under which to announce the regex. + */ + struct GNUNET_PeerIdentity *id; + + /** + * Optional statistics handle to report usage. Can be NULL. + */ + struct GNUNET_STATISTICS_Handle *stats; +}; + + +/** + * Regex callback iterator to store own service description in the DHT. + * + * @param cls closure. + * @param key hash for current state. + * @param proof proof for current state. + * @param accepting GNUNET_YES if this is an accepting state, GNUNET_NO if not. + * @param num_edges number of edges leaving current state. + * @param edges edges leaving current state. + */ +static void +regex_iterator (void *cls, + const struct GNUNET_HashCode *key, + const char *proof, + int accepting, + unsigned int num_edges, + const struct GNUNET_REGEX_Edge *edges) +{ + struct GNUNET_REGEX_announce_handle *h = cls; + struct RegexBlock *block; + struct RegexEdge *block_edge; + enum GNUNET_DHT_RouteOption opt; + size_t size; + size_t len; + unsigned int i; + unsigned int offset; + char *aux; + + LOG (GNUNET_ERROR_TYPE_DEBUG, + " regex dht put for state %s\n", + GNUNET_h2s (key)); + LOG (GNUNET_ERROR_TYPE_DEBUG, " proof: %s\n", proof); + LOG (GNUNET_ERROR_TYPE_DEBUG, " num edges: %u\n", num_edges); + + opt = GNUNET_DHT_RO_DEMULTIPLEX_EVERYWHERE; + if (GNUNET_YES == accepting) + { + struct RegexAccept block; + + LOG (GNUNET_ERROR_TYPE_DEBUG, + " state %s is accepting, putting own id\n", + GNUNET_h2s(key)); + size = sizeof (block); + block.key = *key; + block.id = *(h->id); + GNUNET_STATISTICS_update (h->stats, "# regex accepting blocks stored", + 1, GNUNET_NO); + GNUNET_STATISTICS_update (h->stats, "# regex accepting block bytes stored", + sizeof (block), GNUNET_NO); + (void) + GNUNET_DHT_put (h->dht, key, + 2, /* FIXME option */ + opt /* | GNUNET_DHT_RO_RECORD_ROUTE*/, + GNUNET_BLOCK_TYPE_REGEX_ACCEPT, + size, + (char *) &block, + GNUNET_TIME_relative_to_absolute (GNUNET_TIME_UNIT_HOURS), /* FIXME: expiration time should be option */ + GNUNET_TIME_UNIT_HOURS, /* FIXME option */ + NULL, NULL); + } + len = strlen(proof); + size = sizeof (struct RegexBlock) + len; + block = GNUNET_malloc (size); + + block->key = *key; + block->n_proof = htonl (len); + block->n_edges = htonl (num_edges); + block->accepting = htonl (accepting); + + /* Store the proof at the end of the block. */ + aux = (char *) &block[1]; + memcpy (aux, proof, len); + aux = &aux[len]; + + /* Store each edge in a variable length MeshEdge struct at the + * very end of the MeshRegexBlock structure. + */ + for (i = 0; i < num_edges; i++) + { + LOG (GNUNET_ERROR_TYPE_DEBUG, " edge %s towards %s\n", + edges[i].label, GNUNET_h2s(&edges[i].destination)); + + /* aux points at the end of the last block */ + len = strlen (edges[i].label); + size += sizeof (struct RegexEdge) + len; + // Calculate offset FIXME is this ok? use size instead? + offset = aux - (char *) block; + block = GNUNET_realloc (block, size); + aux = &((char *) block)[offset]; + block_edge = (struct RegexEdge *) aux; + block_edge->key = edges[i].destination; + block_edge->n_token = htonl (len); + aux = (char *) &block_edge[1]; + memcpy (aux, edges[i].label, len); + aux = &aux[len]; + } + (void) + GNUNET_DHT_put(h->dht, key, + DHT_REPLICATION, /* FIXME OPTION */ + opt, + GNUNET_BLOCK_TYPE_REGEX, size, + (char *) block, + GNUNET_TIME_relative_to_absolute (DHT_TTL), /* FIXME: this should be an option */ + DHT_TTL, + NULL, NULL); + GNUNET_STATISTICS_update (h->stats, "# regex blocks stored", + 1, GNUNET_NO); + GNUNET_STATISTICS_update (h->stats, "# regex block bytes stored", + size, GNUNET_NO); + + GNUNET_free (block); +} + + +struct GNUNET_REGEX_announce_handle * +GNUNET_REGEX_announce (struct GNUNET_DHT_Handle *dht, + struct GNUNET_PeerIdentity *id, + const char *regex, + uint16_t compression, + struct GNUNET_STATISTICS_Handle *stats) +{ + struct GNUNET_REGEX_announce_handle *h; + + GNUNET_assert (NULL != dht); + h = GNUNET_malloc (sizeof (struct GNUNET_REGEX_announce_handle)); + h->regex = regex; + h->dht = dht; + h->stats = stats; + h->id = id; + h->dfa = GNUNET_REGEX_construct_dfa (regex, + strlen (regex), + compression); + GNUNET_REGEX_reannounce (h); + return h; +} + +void +GNUNET_REGEX_reannounce (struct GNUNET_REGEX_announce_handle *h) +{ + GNUNET_REGEX_iterate_all_edges (h->dfa, ®ex_iterator, h); +} + +void +GNUNET_REGEX_announce_cancel (struct GNUNET_REGEX_announce_handle *h) +{ + GNUNET_REGEX_automaton_destroy (h->dfa); + GNUNET_free (h); +} + + +/******************************************************************************/ + + +/** + * Struct to keep state of running searches that have consumed a part of + * the inital string. + */ +struct RegexSearchContext +{ + /** + * Part of the description already consumed by + * this particular search branch. + */ + size_t position; + + /** + * Information about the search. + */ + struct GNUNET_REGEX_search_handle *info; + + /** + * We just want to look for one edge, the longer the better. + * Keep its length. + */ + unsigned int longest_match; + + /** + * Destination hash of the longest match. + */ + struct GNUNET_HashCode hash; +}; + + +/** + * Struct to keep information of searches of services described by a regex + * using a user-provided string service description. + */ +struct GNUNET_REGEX_search_handle +{ + /** + * DHT handle to use, must be initialized externally. + */ + struct GNUNET_DHT_Handle *dht; + + /** + * Optional statistics handle to report usage. Can be NULL. + */ + struct GNUNET_STATISTICS_Handle *stats; + + /** + * User provided description of the searched service. + */ + char *description; + + /** + * Running DHT GETs. + */ + struct GNUNET_CONTAINER_MultiHashMap *dht_get_handles; + + /** + * Results from running DHT GETs. + */ + struct GNUNET_CONTAINER_MultiHashMap *dht_get_results; + + /** + * Contexts, for each running DHT GET. Free all on end of search. + */ + struct RegexSearchContext **contexts; + + /** + * Number of contexts (branches/steps in search). + */ + unsigned int n_contexts; + + /** + * @param callback Callback for found peers. + */ + GNUNET_REGEX_Found callback; + + /** + * @param callback_cls Closure for @c callback. + */ + void *callback_cls; +}; + + + +/** + * Jump to the next edge, with the longest matching token. + * + * @param block Block found in the DHT. + * @param size Size of the block. + * @param ctx Context of the search. + * + * @return GNUNET_YES if should keep iterating, GNUNET_NO otherwise. + */ +static void +regex_next_edge (const struct RegexBlock *block, + size_t size, + struct RegexSearchContext *ctx); + + +/** + * Function to process DHT string to regex matching. + * Called on each result obtained for the DHT search. + * + * @param cls Closure (search context). + * @param exp When will this value expire. + * @param key Key of the result. + * @param get_path Path of the get request. + * @param get_path_length Lenght of get_path. + * @param put_path Path of the put request. + * @param put_path_length Length of the put_path. + * @param type Type of the result. + * @param size Number of bytes in data. + * @param data Pointer to the result data. + */ +static void +dht_get_string_accept_handler (void *cls, struct GNUNET_TIME_Absolute exp, + const struct GNUNET_HashCode * key, + const struct GNUNET_PeerIdentity *get_path, + unsigned int get_path_length, + const struct GNUNET_PeerIdentity *put_path, + unsigned int put_path_length, + enum GNUNET_BLOCK_Type type, + size_t size, const void *data) +{ + const struct RegexAccept *block = data; + struct RegexSearchContext *ctx = cls; + struct GNUNET_REGEX_search_handle *info = ctx->info; + + LOG (GNUNET_ERROR_TYPE_DEBUG, "Got regex results from DHT!\n"); + LOG (GNUNET_ERROR_TYPE_DEBUG, " for %s\n", info->description); + + GNUNET_STATISTICS_update (info->stats, "# regex accepting blocks found", + 1, GNUNET_NO); + GNUNET_STATISTICS_update (info->stats, "# regex accepting block bytes found", + size, GNUNET_NO); + + info->callback (info->callback_cls, + &block->id, + get_path, get_path_length, + put_path, put_path_length); + + return; +} + +/** + * Find a path to a peer that offers a regex servcie compatible + * with a given string. + * + * @param key The key of the accepting state. + * @param ctx Context containing info about the string, tunnel, etc. + */ +static void +regex_find_path (const struct GNUNET_HashCode *key, + struct RegexSearchContext *ctx) +{ + struct GNUNET_DHT_GetHandle *get_h; + + LOG (GNUNET_ERROR_TYPE_DEBUG, "Found peer by service\n"); + get_h = GNUNET_DHT_get_start (ctx->info->dht, /* handle */ + GNUNET_BLOCK_TYPE_REGEX_ACCEPT, /* type */ + key, /* key to search */ + DHT_REPLICATION, /* replication level */ + GNUNET_DHT_RO_DEMULTIPLEX_EVERYWHERE | + GNUNET_DHT_RO_RECORD_ROUTE, + NULL, /* xquery */ // FIXME BLOOMFILTER + 0, /* xquery bits */ // FIXME BLOOMFILTER SIZE + &dht_get_string_accept_handler, ctx); + GNUNET_break (GNUNET_OK == + GNUNET_CONTAINER_multihashmap_put(ctx->info->dht_get_handles, + key, + get_h, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE)); +} + + +/** + * Function to process DHT string to regex matching. + * Called on each result obtained for the DHT search. + * + * @param cls closure (search context) + * @param exp when will this value expire + * @param key key of the result + * @param get_path path of the get request (not used) + * @param get_path_length lenght of get_path (not used) + * @param put_path path of the put request (not used) + * @param put_path_length length of the put_path (not used) + * @param type type of the result + * @param size number of bytes in data + * @param data pointer to the result data + * + * TODO: re-issue the request after certain time? cancel after X results? + */ +static void +dht_get_string_handler (void *cls, struct GNUNET_TIME_Absolute exp, + const struct GNUNET_HashCode * key, + const struct GNUNET_PeerIdentity *get_path, + unsigned int get_path_length, + const struct GNUNET_PeerIdentity *put_path, + unsigned int put_path_length, + enum GNUNET_BLOCK_Type type, + size_t size, const void *data) +{ + const struct RegexBlock *block = data; + struct RegexSearchContext *ctx = cls; + struct GNUNET_REGEX_search_handle *info = ctx->info; + void *copy; + size_t len; + + LOG (GNUNET_ERROR_TYPE_DEBUG, "DHT GET STRING RETURNED RESULTS\n"); + LOG (GNUNET_ERROR_TYPE_DEBUG, " for: %s\n", ctx->info->description); + LOG (GNUNET_ERROR_TYPE_DEBUG, " key: %s\n", GNUNET_h2s (key)); + + copy = GNUNET_malloc (size); + memcpy (copy, data, size); + GNUNET_break ( + GNUNET_OK == + GNUNET_CONTAINER_multihashmap_put (info->dht_get_results, key, copy, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE) + ); + len = ntohl (block->n_proof); + { + char proof[len + 1]; + + memcpy (proof, &block[1], len); + proof[len] = '\0'; + if (GNUNET_OK != GNUNET_REGEX_check_proof (proof, key)) + { + GNUNET_break_op (0); + return; + } + } + len = strlen (info->description); + if (len == ctx->position) // String processed + { + if (GNUNET_YES == ntohl (block->accepting)) + { + regex_find_path (key, ctx); + } + else + { + LOG (GNUNET_ERROR_TYPE_DEBUG, " block not accepting!\n"); + // FIXME REGEX this block not successful, wait for more? start timeout? + } + return; + } + + regex_next_edge (block, size, ctx); + + return; +} + + +/** + * Iterator over found existing mesh regex blocks that match an ongoing search. + * + * @param cls closure + * @param key current key code + * @param value value in the hash map + * @return GNUNET_YES if we should continue to iterate, + * GNUNET_NO if not. + */ +static int +regex_result_iterator (void *cls, + const struct GNUNET_HashCode * key, + void *value) +{ + struct RegexBlock *block = value; + struct RegexSearchContext *ctx = cls; + + if (GNUNET_YES == ntohl(block->accepting) && + ctx->position == strlen (ctx->info->description)) + { + LOG (GNUNET_ERROR_TYPE_DEBUG, "* Found accepting known block\n"); + regex_find_path (key, ctx); + return GNUNET_YES; // We found an accept state! + } + else + { + LOG (GNUNET_ERROR_TYPE_DEBUG, "* %u, %u, [%u]\n", + ctx->position, strlen(ctx->info->description), + ntohl(block->accepting)); + + } + regex_next_edge(block, SIZE_MAX, ctx); + + GNUNET_STATISTICS_update (ctx->info->stats, "# regex mesh blocks iterated", + 1, GNUNET_NO); + + return GNUNET_YES; +} + + +/** + * Iterator over edges in a regex block retrieved from the DHT. + * + * @param cls Closure (context of the search). + * @param token Token that follows to next state. + * @param len Lenght of token. + * @param key Hash of next state. + * + * @return GNUNET_YES if should keep iterating, GNUNET_NO otherwise. + */ +static int +regex_edge_iterator (void *cls, + const char *token, + size_t len, + const struct GNUNET_HashCode *key) +{ + struct RegexSearchContext *ctx = cls; + struct GNUNET_REGEX_search_handle *info = ctx->info; + const char *current; + size_t current_len; + + GNUNET_STATISTICS_update (info->stats, "# regex edges iterated", + 1, GNUNET_NO); + + LOG (GNUNET_ERROR_TYPE_DEBUG, "* Start of regex edge iterator\n"); + LOG (GNUNET_ERROR_TYPE_DEBUG, "* descr : %s\n", info->description); + LOG (GNUNET_ERROR_TYPE_DEBUG, "* posit : %u\n", ctx->position); + current = &info->description[ctx->position]; + LOG (GNUNET_ERROR_TYPE_DEBUG, "* currt : %s\n", current); + current_len = strlen (info->description) - ctx->position; + LOG (GNUNET_ERROR_TYPE_DEBUG, "* ctlen : %u\n", current_len); + LOG (GNUNET_ERROR_TYPE_DEBUG, "* tklen : %u\n", len); + LOG (GNUNET_ERROR_TYPE_DEBUG, "* token : %.*s\n", len, token); + LOG (GNUNET_ERROR_TYPE_DEBUG, "* nextk : %s\n", GNUNET_h2s(key)); + if (len > current_len) + { + LOG (GNUNET_ERROR_TYPE_DEBUG, "* Token too long, END\n"); + return GNUNET_YES; // Token too long, wont match + } + if (0 != strncmp (current, token, len)) + { + LOG (GNUNET_ERROR_TYPE_DEBUG, "* Token doesn't match, END\n"); + return GNUNET_YES; // Token doesn't match + } + + if (len > ctx->longest_match) + { + LOG (GNUNET_ERROR_TYPE_DEBUG, "* Token is longer, KEEP\n"); + ctx->longest_match = len; + ctx->hash = *key; + } + else + { + LOG (GNUNET_ERROR_TYPE_DEBUG, "* Token is not longer, IGNORE\n"); + } + + LOG (GNUNET_ERROR_TYPE_DEBUG, "* End of regex edge iterator\n"); + return GNUNET_YES; +} + + +/** + * Jump to the next edge, with the longest matching token. + * + * @param block Block found in the DHT. + * @param size Size of the block. + * @param ctx Context of the search. + * + * @return GNUNET_YES if should keep iterating, GNUNET_NO otherwise. + */ +static void +regex_next_edge (const struct RegexBlock *block, + size_t size, + struct RegexSearchContext *ctx) +{ + struct RegexSearchContext *new_ctx; + struct GNUNET_REGEX_search_handle *info = ctx->info; + struct GNUNET_DHT_GetHandle *get_h; + const char *rest; + int result; + + /* Find the longest match for the current string position, + * among tokens in the given block */ + ctx->longest_match = 0; + result = GNUNET_REGEX_block_iterate (block, size, + ®ex_edge_iterator, ctx); + GNUNET_break (GNUNET_OK == result); + + /* Did anything match? */ + if (0 == ctx->longest_match) + return; + + new_ctx = GNUNET_malloc (sizeof (struct RegexSearchContext)); + new_ctx->info = info; + new_ctx->position = ctx->position + ctx->longest_match; + GNUNET_array_append (info->contexts, info->n_contexts, new_ctx); + + /* Check whether we already have a DHT GET running for it */ + if (GNUNET_YES == + GNUNET_CONTAINER_multihashmap_contains(info->dht_get_handles, &ctx->hash)) + { + LOG (GNUNET_ERROR_TYPE_DEBUG, "* GET running, END\n"); + GNUNET_CONTAINER_multihashmap_get_multiple (info->dht_get_results, + &ctx->hash, + ®ex_result_iterator, + new_ctx); + // FIXME: "leaks" new_ctx? avoid keeping it around? + return; // We are already looking for it + } + + GNUNET_STATISTICS_update (info->stats, "# regex nodes traversed", + 1, GNUNET_NO); + + /* Start search in DHT */ + rest = &new_ctx->info->description[new_ctx->position]; + get_h = + GNUNET_DHT_get_start (info->dht, /* handle */ + GNUNET_BLOCK_TYPE_REGEX, /* type */ + &ctx->hash, /* key to search */ + DHT_REPLICATION, /* replication level */ + GNUNET_DHT_RO_DEMULTIPLEX_EVERYWHERE, + rest, /* xquery */ + // FIXME add BLOOMFILTER to exclude filtered peers + strlen(rest) + 1, /* xquery bits */ + // FIXME add BLOOMFILTER SIZE + &dht_get_string_handler, new_ctx); + if (GNUNET_OK != + GNUNET_CONTAINER_multihashmap_put(info->dht_get_handles, + &ctx->hash, + get_h, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_FAST)) + { + GNUNET_break (0); + return; + } +} + + +struct GNUNET_REGEX_search_handle * +GNUNET_REGEX_search (struct GNUNET_DHT_Handle *dht, + const char *string, + GNUNET_REGEX_Found callback, + void *callback_cls, + struct GNUNET_STATISTICS_Handle *stats) +{ + struct GNUNET_REGEX_search_handle *h; + struct GNUNET_DHT_GetHandle *get_h; + struct RegexSearchContext *ctx; + struct GNUNET_HashCode key; + size_t size; + size_t len; + + /* Initialize handle */ + LOG (GNUNET_ERROR_TYPE_DEBUG, "GNUNET_REGEX_search: %s\n", string); + GNUNET_assert (NULL != dht); + GNUNET_assert (NULL != callback); + h = GNUNET_malloc (sizeof (struct GNUNET_REGEX_search_handle)); + h->dht = dht; + h->description = GNUNET_strdup (string); + h->callback = callback; + h->callback_cls = callback_cls; + h->stats = stats; + h->dht_get_handles = GNUNET_CONTAINER_multihashmap_create (32, GNUNET_YES); + h->dht_get_results = GNUNET_CONTAINER_multihashmap_create (32, GNUNET_YES); + + /* Initialize context */ + len = strlen (string); + size = GNUNET_REGEX_get_first_key (string, len, &key); + ctx = GNUNET_malloc (sizeof (struct RegexSearchContext)); + ctx->position = size; + ctx->info = h; + GNUNET_array_append (h->contexts, h->n_contexts, ctx); + LOG (GNUNET_ERROR_TYPE_DEBUG, + " consumed %u bits out of %u\n", size, len); + LOG (GNUNET_ERROR_TYPE_DEBUG, + " looking for %s\n", GNUNET_h2s (&key)); + + /* Start search in DHT */ + get_h = GNUNET_DHT_get_start (h->dht, /* handle */ + GNUNET_BLOCK_TYPE_REGEX, /* type */ + &key, /* key to search */ + DHT_REPLICATION, /* replication level */ + GNUNET_DHT_RO_DEMULTIPLEX_EVERYWHERE, + &h->description[size], /* xquery */ + // FIXME add BLOOMFILTER to exclude filtered peers + len + 1 - size, /* xquery bits */ + // FIXME add BLOOMFILTER SIZE + &dht_get_string_handler, ctx); + GNUNET_break ( + GNUNET_OK == + GNUNET_CONTAINER_multihashmap_put (h->dht_get_handles, + &key, + get_h, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_FAST) + ); + + return h; +} + + +/** + * Iterator over hash map entries to cancel DHT GET requests after a + * successful connect_by_string. + * + * @param cls Closure (unused). + * @param key Current key code (unused). + * @param value Value in the hash map (get handle). + * @return GNUNET_YES if we should continue to iterate, + * GNUNET_NO if not. + */ +static int +regex_cancel_dht_get (void *cls, + const struct GNUNET_HashCode * key, + void *value) +{ + struct GNUNET_DHT_GetHandle *h = value; + + GNUNET_DHT_get_stop (h); + return GNUNET_YES; +} + + +/** + * Iterator over hash map entries to free MeshRegexBlocks stored during the + * search for connect_by_string. + * + * @param cls Closure (unused). + * @param key Current key code (unused). + * @param value MeshRegexBlock in the hash map. + * @return GNUNET_YES if we should continue to iterate, + * GNUNET_NO if not. + */ +static int +regex_free_result (void *cls, + const struct GNUNET_HashCode * key, + void *value) +{ + + GNUNET_free (value); + return GNUNET_YES; +} + + +/** + * Cancel an ongoing regex search in the DHT and free all resources. + * + * @param ctx The search context. + */ +static void +regex_cancel_search (struct GNUNET_REGEX_search_handle *ctx) +{ + GNUNET_free (ctx->description); + GNUNET_CONTAINER_multihashmap_iterate (ctx->dht_get_handles, + ®ex_cancel_dht_get, NULL); + GNUNET_CONTAINER_multihashmap_iterate (ctx->dht_get_results, + ®ex_free_result, NULL); + GNUNET_CONTAINER_multihashmap_destroy (ctx->dht_get_results); + GNUNET_CONTAINER_multihashmap_destroy (ctx->dht_get_handles); + if (0 < ctx->n_contexts) + { + int i; + + for (i = 0; i < ctx->n_contexts; i++) + { + GNUNET_free (ctx->contexts[i]); + } + GNUNET_free (ctx->contexts); + } +} + +void +GNUNET_REGEX_search_cancel (struct GNUNET_REGEX_search_handle *h) +{ + regex_cancel_search (h); + GNUNET_free (h); +} + + + +/* end of regex_dht.c */ \ No newline at end of file diff --git a/src/regex/regex_graph.c b/src/regex/regex_graph.c new file mode 100644 index 0000000..0b5c571 --- /dev/null +++ b/src/regex/regex_graph.c @@ -0,0 +1,317 @@ +/* + This file is part of GNUnet + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ +/** + * @file src/regex/regex_graph.c + * @brief functions for creating .dot graphs from regexes + * @author Maximilian Szengel + */ +#include "platform.h" +#include "gnunet_regex_lib.h" +#include "regex_internal.h" + +/** + * Context for graph creation. Passed as the cls to + * GNUNET_REGEX_automaton_save_graph_step. + */ +struct GNUNET_REGEX_Graph_Context +{ + /** + * File pointer to the dot file used for output. + */ + FILE *filep; + + /** + * Verbose flag, if it's set to GNUNET_YES additional info will be printed in + * the graph. + */ + int verbose; + + /** + * Coloring flag, if set to GNUNET_YES SCCs will be colored. + */ + int coloring; +}; + + +/** + * Recursive function doing DFS with 'v' as a start, detecting all SCCs inside + * the subgraph reachable from 'v'. Used with scc_tarjan function to detect all + * SCCs inside an automaton. + * + * @param scc_counter counter for numbering the sccs + * @param v start vertex + * @param index current index + * @param stack stack for saving all SCCs + * @param stack_size current size of the stack + */ +static void +scc_tarjan_strongconnect (unsigned int *scc_counter, + struct GNUNET_REGEX_State *v, unsigned int *index, + struct GNUNET_REGEX_State **stack, + unsigned int *stack_size) +{ + struct GNUNET_REGEX_State *w; + struct GNUNET_REGEX_Transition *t; + + v->index = *index; + v->lowlink = *index; + (*index)++; + stack[(*stack_size)++] = v; + v->contained = 1; + + for (t = v->transitions_head; NULL != t; t = t->next) + { + w = t->to_state; + + if (NULL == w) + continue; + + if (w->index < 0) + { + scc_tarjan_strongconnect (scc_counter, w, index, stack, stack_size); + v->lowlink = (v->lowlink > w->lowlink) ? w->lowlink : v->lowlink; + } + else if (1 == w->contained) + v->lowlink = (v->lowlink > w->index) ? w->index : v->lowlink; + } + + if (v->lowlink == v->index) + { + (*scc_counter)++; + do + { + w = stack[--(*stack_size)]; + w->contained = 0; + w->scc_id = *scc_counter; + } + while (w != v); + } +} + + +/** + * Detect all SCCs (Strongly Connected Components) inside the given automaton. + * SCCs will be marked using the scc_id on each state. + * + * @param a the automaton for which SCCs should be computed and assigned. + */ +static void +scc_tarjan (struct GNUNET_REGEX_Automaton *a) +{ + unsigned int index; + unsigned int scc_counter; + struct GNUNET_REGEX_State *v; + struct GNUNET_REGEX_State *stack[a->state_count]; + unsigned int stack_size; + + for (v = a->states_head; NULL != v; v = v->next) + { + v->contained = 0; + v->index = -1; + v->lowlink = -1; + } + + stack_size = 0; + index = 0; + scc_counter = 0; + + for (v = a->states_head; NULL != v; v = v->next) + { + if (v->index < 0) + scc_tarjan_strongconnect (&scc_counter, v, &index, stack, &stack_size); + } +} + + +/** + * Save a state to an open file pointer. cls is expected to be a file pointer to + * an open file. Used only in conjunction with + * GNUNET_REGEX_automaton_save_graph. + * + * @param cls file pointer. + * @param count current count of the state, not used. + * @param s state. + */ +void +GNUNET_REGEX_automaton_save_graph_step (void *cls, unsigned int count, + struct GNUNET_REGEX_State *s) +{ + struct GNUNET_REGEX_Graph_Context *ctx = cls; + struct GNUNET_REGEX_Transition *ctran; + char *s_acc = NULL; + char *s_tran = NULL; + char *name; + char *to_name; + + if (GNUNET_YES == ctx->verbose) + GNUNET_asprintf (&name, "%i (%s) (%s) (%s)", s->dfs_id, s->name, s->proof, + GNUNET_h2s (&s->hash)); + else + GNUNET_asprintf (&name, "%i", s->dfs_id); + + if (s->accepting) + { + if (GNUNET_YES == ctx->coloring) + { + GNUNET_asprintf (&s_acc, + "\"%s\" [shape=doublecircle, color=\"0.%i 0.8 0.95\"];\n", + name, s->scc_id * s->scc_id); + } + else + { + GNUNET_asprintf (&s_acc, "\"%s\" [shape=doublecircle];\n", name, + s->scc_id); + } + } + else if (GNUNET_YES == ctx->coloring) + { + GNUNET_asprintf (&s_acc, + "\"%s\" [shape=circle, color=\"0.%i 0.8 0.95\"];\n", name, + s->scc_id * s->scc_id); + } + else + { + GNUNET_asprintf (&s_acc, "\"%s\" [shape=circle];\n", name, s->scc_id); + } + + GNUNET_assert (NULL != s_acc); + + fwrite (s_acc, strlen (s_acc), 1, ctx->filep); + GNUNET_free (s_acc); + s_acc = NULL; + + for (ctran = s->transitions_head; NULL != ctran; ctran = ctran->next) + { + if (NULL == ctran->to_state) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Transition from State %i has no state for transitioning\n", + s->id); + continue; + } + + if (GNUNET_YES == ctx->verbose) + { + GNUNET_asprintf (&to_name, "%i (%s) (%s) (%s)", ctran->to_state->dfs_id, + ctran->to_state->name, ctran->to_state->proof, + GNUNET_h2s (&ctran->to_state->hash)); + } + else + GNUNET_asprintf (&to_name, "%i", ctran->to_state->dfs_id); + + if (NULL == ctran->label) + { + if (GNUNET_YES == ctx->coloring) + { + GNUNET_asprintf (&s_tran, + "\"%s\" -> \"%s\" [label = \"ε\", color=\"0.%i 0.8 0.95\"];\n", + name, to_name, s->scc_id * s->scc_id); + } + else + { + GNUNET_asprintf (&s_tran, "\"%s\" -> \"%s\" [label = \"ε\"];\n", name, + to_name, s->scc_id); + } + } + else + { + if (GNUNET_YES == ctx->coloring) + { + GNUNET_asprintf (&s_tran, + "\"%s\" -> \"%s\" [label = \"%s\", color=\"0.%i 0.8 0.95\"];\n", + name, to_name, ctran->label, s->scc_id * s->scc_id); + } + else + { + GNUNET_asprintf (&s_tran, "\"%s\" -> \"%s\" [label = \"%s\"];\n", name, + to_name, ctran->label, s->scc_id); + } + } + + GNUNET_free (to_name); + + GNUNET_assert (NULL != s_tran); + + fwrite (s_tran, strlen (s_tran), 1, ctx->filep); + GNUNET_free (s_tran); + s_tran = NULL; + } + + GNUNET_free (name); +} + + +/** + * Save the given automaton as a GraphViz dot file. + * + * @param a the automaton to be saved. + * @param filename where to save the file. + * @param options options for graph generation that include coloring or verbose + * mode + */ +void +GNUNET_REGEX_automaton_save_graph (struct GNUNET_REGEX_Automaton *a, + const char *filename, + enum GNUNET_REGEX_GraphSavingOptions options) +{ + char *start; + char *end; + struct GNUNET_REGEX_Graph_Context ctx; + + if (NULL == a) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Could not print NFA, was NULL!"); + return; + } + + if (NULL == filename || strlen (filename) < 1) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "No Filename given!"); + return; + } + + ctx.filep = fopen (filename, "w"); + ctx.verbose = + (0 == (options & GNUNET_REGEX_GRAPH_VERBOSE)) ? GNUNET_NO : GNUNET_YES; + ctx.coloring = + (0 == (options & GNUNET_REGEX_GRAPH_COLORING)) ? GNUNET_NO : GNUNET_YES; + + if (NULL == ctx.filep) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Could not open file for writing: %s", + filename); + return; + } + + /* First add the SCCs to the automaton, so we can color them nicely */ + if (GNUNET_YES == ctx.coloring) + scc_tarjan (a); + + start = "digraph G {\nrankdir=LR\n"; + fwrite (start, strlen (start), 1, ctx.filep); + + GNUNET_REGEX_automaton_traverse (a, a->start, NULL, NULL, + &GNUNET_REGEX_automaton_save_graph_step, + &ctx); + + end = "\n}\n"; + fwrite (end, strlen (end), 1, ctx.filep); + fclose (ctx.filep); +} diff --git a/src/regex/regex_internal.h b/src/regex/regex_internal.h new file mode 100644 index 0000000..00badc5 --- /dev/null +++ b/src/regex/regex_internal.h @@ -0,0 +1,484 @@ +/* + This file is part of GNUnet + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ +/** + * @file src/regex/regex_internal.h + * @brief common internal definitions for regex library. + * @author Maximilian Szengel + */ +#ifndef REGEX_INTERNAL_H +#define REGEX_INTERNAL_H + +#include "gnunet_regex_lib.h" + +#ifdef __cplusplus +extern "C" +{ +#if 0 /* keep Emacsens' auto-indent happy */ +} +#endif +#endif + +/** + * char array of literals that are allowed inside a regex (apart from the + * operators) + */ +#define ALLOWED_LITERALS "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz" + + +/** + * Transition between two states. Transitions are stored at the states from + * which they origin ('from_state'). Each state can have 0-n transitions. + * If label is NULL, this is considered to be an epsilon transition. + */ +struct GNUNET_REGEX_Transition +{ + /** + * This is a linked list. + */ + struct GNUNET_REGEX_Transition *prev; + + /** + * This is a linked list. + */ + struct GNUNET_REGEX_Transition *next; + + /** + * Unique id of this transition. + */ + unsigned int id; + + /** + * Label for this transition. This is basically the edge label for the graph. + */ + char *label; + + /** + * State to which this transition leads. + */ + struct GNUNET_REGEX_State *to_state; + + /** + * State from which this transition origins. + */ + struct GNUNET_REGEX_State *from_state; +}; + + +/** + * A state. Can be used in DFA and NFA automatons. + */ +struct GNUNET_REGEX_State; + + +/** + * Set of states. + */ +struct GNUNET_REGEX_StateSet +{ + /** + * Array of states. + */ + struct GNUNET_REGEX_State **states; + + /** + * Number of entries in *use* in the 'states' array. + */ + unsigned int off; + + /** + * Length of the 'states' array. + */ + unsigned int size; +}; + + +/** + * A state. Can be used in DFA and NFA automatons. + */ +struct GNUNET_REGEX_State +{ + /** + * This is a linked list to keep states in an automaton. + */ + struct GNUNET_REGEX_State *prev; + + /** + * This is a linked list to keep states in an automaton. + */ + struct GNUNET_REGEX_State *next; + + /** + * This is a multi DLL for StateSet_MDLL. + */ + struct GNUNET_REGEX_State *prev_SS; + + /** + * This is a multi DLL for StateSet_MDLL. + */ + struct GNUNET_REGEX_State *next_SS; + + /** + * This is a multi DLL for StateSet_MDLL Stack. + */ + struct GNUNET_REGEX_State *prev_ST; + + /** + * This is a multi DLL for StateSet_MDLL Stack. + */ + struct GNUNET_REGEX_State *next_ST; + + /** + * Unique state id. + */ + unsigned int id; + + /** + * Unique state id that is used for traversing the automaton. It is guaranteed + * to be > 0 and < state_count. + */ + unsigned int traversal_id; + + /** + * If this is an accepting state or not. + */ + int accepting; + + /** + * Marking of the state. This is used for marking all visited states when + * traversing all states of an automaton and for cases where the state id + * cannot be used (dfa minimization). + */ + int marked; + + /** + * Marking the state as contained. This is used for checking, if the state is + * contained in a set in constant time. + */ + int contained; + + /** + * Marking the state as part of an SCC (Strongly Connected Component). All + * states with the same scc_id are part of the same SCC. scc_id is 0, if state + * is not a part of any SCC. + */ + unsigned int scc_id; + + /** + * Used for SCC detection. + */ + int index; + + /** + * Used for SCC detection. + */ + int lowlink; + + /** + * Human readable name of the state. Used for debugging and graph + * creation. + */ + char *name; + + /** + * Hash of the state. + */ + struct GNUNET_HashCode hash; + + /** + * Linear state ID accquired by depth-first-search. This ID should be used for + * storing information about the state in an array, because the 'id' of the + * state is not guaranteed to be linear. The 'dfs_id' is guaranteed to be > 0 + * and < 'state_count'. + */ + unsigned int dfs_id; + + /** + * Proof for this state. + */ + char *proof; + + /** + * Number of transitions from this state to other states. + */ + unsigned int transition_count; + + /** + * DLL of transitions. + */ + struct GNUNET_REGEX_Transition *transitions_head; + + /** + * DLL of transitions. + */ + struct GNUNET_REGEX_Transition *transitions_tail; + + /** + * Number of incoming transitions. Used for compressing DFA paths. + */ + unsigned int incoming_transition_count; + + /** + * Set of states on which this state is based on. Used when creating a DFA out + * of several NFA states. + */ + struct GNUNET_REGEX_StateSet nfa_set; +}; + + +/** + * Type of an automaton. + */ +enum GNUNET_REGEX_AutomatonType +{ + NFA, + DFA +}; + + +/** + * Automaton representation. + */ +struct GNUNET_REGEX_Automaton +{ + /** + * Linked list of NFAs used for partial NFA creation. + */ + struct GNUNET_REGEX_Automaton *prev; + + /** + * Linked list of NFAs used for partial NFA creation. + */ + struct GNUNET_REGEX_Automaton *next; + + /** + * First state of the automaton. This is mainly used for constructing an NFA, + * where each NFA itself consists of one or more NFAs linked together. + */ + struct GNUNET_REGEX_State *start; + + /** + * End state of the partial NFA. This is undefined for DFAs + */ + struct GNUNET_REGEX_State *end; + + /** + * Number of states in the automaton. + */ + unsigned int state_count; + + /** + * DLL of states. + */ + struct GNUNET_REGEX_State *states_head; + + /** + * DLL of states + */ + struct GNUNET_REGEX_State *states_tail; + + /** + * Type of the automaton. + */ + enum GNUNET_REGEX_AutomatonType type; + + /** + * Regex + */ + char *regex; + + /** + * Canonical regex (result of RX->NFA->DFA->RX) + */ + char *canonical_regex; + + /** + * GNUNET_YES, if multi strides have been added to the Automaton. + */ + int is_multistrided; +}; + + +/** + * Construct an NFA by parsing the regex string of length 'len'. + * + * @param regex regular expression string. + * @param len length of the string. + * + * @return NFA, needs to be freed using GNUNET_REGEX_automaton_destroy. + */ +struct GNUNET_REGEX_Automaton * +GNUNET_REGEX_construct_nfa (const char *regex, const size_t len); + + +/** + * Function that get's passed to automaton traversal and is called before each + * next traversal from state 's' using transition 't' to check if traversal + * should proceed. Return GNUNET_NO to stop traversal or GNUNET_YES to continue. + * + * @param cls closure for the check. + * @param s current state in the traversal. + * @param t current transition from state 's' that will be used for the next + * step. + * + * @return GNUNET_YES to proceed traversal, GNUNET_NO to stop. + */ +typedef int (*GNUNET_REGEX_traverse_check) (void *cls, + struct GNUNET_REGEX_State * s, + struct GNUNET_REGEX_Transition * t); + + +/** + * Function that is called with each state, when traversing an automaton. + * + * @param cls closure. + * @param count current count of the state, from 0 to a->state_count -1. + * @param s state. + */ +typedef void (*GNUNET_REGEX_traverse_action) (void *cls, + const unsigned int count, + struct GNUNET_REGEX_State * s); + + +/** + * Traverses the given automaton using depth-first-search (DFS) from it's start + * state, visiting all reachable states and calling 'action' on each one of + * them. + * + * @param a automaton to be traversed. + * @param start start state, pass a->start or NULL to traverse the whole automaton. + * @param check function that is checked before advancing on each transition + * in the DFS. + * @param check_cls closure for check. + * @param action action to be performed on each state. + * @param action_cls closure for action + */ +void +GNUNET_REGEX_automaton_traverse (const struct GNUNET_REGEX_Automaton *a, + struct GNUNET_REGEX_State *start, + GNUNET_REGEX_traverse_check check, + void *check_cls, + GNUNET_REGEX_traverse_action action, + void *action_cls); + +/** + * Get the canonical regex of the given automaton. + * When constructing the automaton a proof is computed for each state, + * consisting of the regular expression leading to this state. A complete + * regex for the automaton can be computed by combining these proofs. + * As of now this function is only useful for testing. + * + * @param a automaton for which the canonical regex should be returned. + * + * @return canonical regex string. + */ +const char * +GNUNET_REGEX_get_canonical_regex (struct GNUNET_REGEX_Automaton *a); + + +/** + * Get the number of transitions that are contained in the given automaton. + * + * @param a automaton for which the number of transitions should be returned. + * + * @return number of transitions in the given automaton. + */ +unsigned int +GNUNET_REGEX_get_transition_count (struct GNUNET_REGEX_Automaton *a); + + +/** + * Context that contains an id counter for states and transitions as well as a + * DLL of automatons used as a stack for NFA construction. + */ +struct GNUNET_REGEX_Context +{ + /** + * Unique state id. + */ + unsigned int state_id; + + /** + * Unique transition id. + */ + unsigned int transition_id; + + /** + * DLL of GNUNET_REGEX_Automaton's used as a stack. + */ + struct GNUNET_REGEX_Automaton *stack_head; + + /** + * DLL of GNUNET_REGEX_Automaton's used as a stack. + */ + struct GNUNET_REGEX_Automaton *stack_tail; +}; + + +/** + * Adds multi-strided transitions to the given 'dfa'. + * + * @param regex_ctx regex context needed to add transitions to the automaton. + * @param dfa DFA to which the multi strided transitions should be added. + * @param stride_len length of the strides. + */ +void +GNUNET_REGEX_dfa_add_multi_strides (struct GNUNET_REGEX_Context *regex_ctx, + struct GNUNET_REGEX_Automaton *dfa, + const unsigned int stride_len); + + +/** + * Generate a (pseudo) random regular expression of length 'rx_length', as well + * as a (optional) string that will be matched by the generated regex. The + * returned regex needs to be freed. + * + * @param rx_length length of the random regex. + * @param matching_str (optional) pointer to a string that will contain a string + * that will be matched by the generated regex, if + * 'matching_str' pointer was not NULL. + * + * @return NULL if 'rx_length' is 0, a random regex of length 'rx_length', which + * needs to be freed, otherwise. + */ +char * +GNUNET_REGEX_generate_random_regex (size_t rx_length, char *matching_str); + + +/** + * Generate a random string of maximum length 'max_len' that only contains literals allowed + * in a regular expression. The string might be 0 chars long but is garantueed + * to be shorter or equal to 'max_len'. + * + * @param max_len maximum length of the string that should be generated. + * + * @return random string that needs to be freed. + */ +char * +GNUNET_REGEX_generate_random_string (size_t max_len); + + +#if 0 /* keep Emacsens' auto-indent happy */ +{ +#endif +#ifdef __cplusplus +} +#endif + +#endif diff --git a/src/regex/regex_random.c b/src/regex/regex_random.c new file mode 100644 index 0000000..eee0c73 --- /dev/null +++ b/src/regex/regex_random.c @@ -0,0 +1,170 @@ +/* + This file is part of GNUnet + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ +/** + * @file src/regex/regex_random.c + * @brief functions for creating random regular expressions and strings + * @author Maximilian Szengel + */ +#include "platform.h" +#include "gnunet_regex_lib.h" +#include "gnunet_crypto_lib.h" +#include "regex_internal.h" + + +/** + * Get a (pseudo) random valid literal for building a regular expression. + * + * @return random valid literal + */ +char +get_random_literal () +{ + uint32_t ridx; + + ridx = + GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK, + (uint32_t) strlen (ALLOWED_LITERALS)); + + return ALLOWED_LITERALS[ridx]; +} + + +/** + * Generate a (pseudo) random regular expression of length 'rx_length', as well + * as a (optional) string that will be matched by the generated regex. The + * returned regex needs to be freed. + * + * @param rx_length length of the random regex. + * @param matching_str (optional) pointer to a string that will contain a string + * that will be matched by the generated regex, if + * 'matching_str' pointer was not NULL. Make sure you + * allocated at least rx_length+1 bytes for this sting. + * + * @return NULL if 'rx_length' is 0, a random regex of length 'rx_length', which + * needs to be freed, otherwise. + */ +char * +GNUNET_REGEX_generate_random_regex (size_t rx_length, char *matching_str) +{ + char *rx; + char *rx_p; + char *matching_strp; + unsigned int i; + unsigned int char_op_switch; + unsigned int last_was_op; + int rx_op; + char current_char; + + if (0 == rx_length) + return NULL; + + if (NULL != matching_str) + matching_strp = matching_str; + else + matching_strp = NULL; + + rx = GNUNET_malloc (rx_length + 1); + rx_p = rx; + current_char = 0; + last_was_op = 1; + + for (i = 0; i < rx_length; i++) + { + char_op_switch = GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK, 2); + + if (0 == char_op_switch && !last_was_op) + { + last_was_op = 1; + rx_op = GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK, 4); + + switch (rx_op) + { + case 0: + current_char = '+'; + break; + case 1: + current_char = '*'; + break; + case 2: + current_char = '?'; + break; + case 3: + if (i < rx_length - 1) /* '|' cannot be at the end */ + current_char = '|'; + else + current_char = get_random_literal (); + break; + } + } + else + { + current_char = get_random_literal (); + last_was_op = 0; + } + + if (NULL != matching_strp && + (current_char != '+' && current_char != '*' && current_char != '?' && + current_char != '|')) + { + *matching_strp = current_char; + matching_strp++; + } + + *rx_p = current_char; + rx_p++; + } + *rx_p = '\0'; + if (NULL != matching_strp) + *matching_strp = '\0'; + + return rx; +} + +/** + * Generate a random string of maximum length 'max_len' that only contains literals allowed + * in a regular expression. The string might be 0 chars long but is garantueed + * to be shorter or equal to 'max_len'. + * + * @param max_len maximum length of the string that should be generated. + * + * @return random string that needs to be freed. + */ +char * +GNUNET_REGEX_generate_random_string (size_t max_len) +{ + unsigned int i; + char *str; + size_t len; + + if (1 > max_len) + return GNUNET_strdup (""); + + len = (size_t) GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK, max_len); + str = GNUNET_malloc (len + 1); + + for (i = 0; i < len; i++) + { + str[i] = get_random_literal (); + } + + str[i] = '\0'; + + return str; +} diff --git a/src/regex/regex_simulation_profiler_test.conf b/src/regex/regex_simulation_profiler_test.conf new file mode 100644 index 0000000..9384aa2 --- /dev/null +++ b/src/regex/regex_simulation_profiler_test.conf @@ -0,0 +1,7 @@ +[regex-mysql] +DATABASE = regex +USER = gnunet +PASSWORD = +HOST = localhost +PORT = 3306 +REGEX_PREFIX = GNVPN-0001-PAD diff --git a/src/regex/regex_test_lib.c b/src/regex/regex_test_lib.c new file mode 100644 index 0000000..7a11fe0 --- /dev/null +++ b/src/regex/regex_test_lib.c @@ -0,0 +1,291 @@ +/* + * This file is part of GNUnet + * (C) 2012 Christian Grothoff (and other contributing authors) + * + * GNUnet is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published + * by the Free Software Foundation; either version 3, or (at your + * option) any later version. + * + * GNUnet is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with GNUnet; see the file COPYING. If not, write to the + * Free Software Foundation, Inc., 59 Temple Place - Suite 330, + * Boston, MA 02111-1307, USA. + */ +/** + * @file src/regex/regex_test_lib.c + * @brief library to read regexes representing IP networks from a file. + * and simplyfinying the into one big regex, in order to run + * tests (regex performance, mesh profiler). + * @author Bartlomiej Polot + */ + +#include "platform.h" +#include "gnunet_util_lib.h" + +struct RegexCombineCtx { + struct RegexCombineCtx *next; + struct RegexCombineCtx *prev; + + struct RegexCombineCtx *head; + struct RegexCombineCtx *tail; + + char *s; +}; + + +/** + * Extract a string from all prefix-combined regexes. + * + * @param ctx Context with 0 or more regexes. + * + * @return Regex that matches any of the added regexes. + */ +static char * +regex_combine (struct RegexCombineCtx *ctx) +{ + struct RegexCombineCtx *p; + size_t len; + char *regex; + char *tmp; + char *s; + + if (NULL != ctx->s) + GNUNET_asprintf (®ex, "%s(", ctx->s); + else + regex = GNUNET_strdup ("("); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "prefix: %s\n", regex); + + for (p = ctx->head; NULL != p; p = p->next) + { + s = regex_combine (p); + GNUNET_asprintf (&tmp, "%s%s|", regex, s); + GNUNET_free_non_null (s); + GNUNET_free_non_null (regex); + regex = tmp; + } + len = strlen (regex); + if (1 == len) + { + GNUNET_free (regex); + return GNUNET_strdup (""); + } + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "pre-partial: %s\n", regex); + if ('|' == regex[len - 1]) + regex[len - 1] = ')'; + if ('(' == regex[len - 1]) + regex[len - 1] = '\0'; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "partial: %s\n", regex); + return regex; +} + + +/** + * Add a single regex to a context, combining with exisiting regex by-prefix. + * + * @param ctx Context with 0 or more regexes. + * @param regex Regex to add. + */ +static void +regex_add (struct RegexCombineCtx *ctx, const char *regex) +{ + struct RegexCombineCtx *p; + const char *rest; + + rest = ®ex[1]; + for (p = ctx->head; NULL != p; p = p->next) + { + if (p->s[0] == regex[0]) + { + if (1 == strlen(p->s)) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "common char %s\n", p->s); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "adding %s\n", rest); + regex_add (p, rest); + } + else + { + struct RegexCombineCtx *new; + new = GNUNET_malloc (sizeof (struct RegexCombineCtx)); + new->s = GNUNET_strdup (&p->s[1]); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " p has now %s\n", p->s); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " p will have %.1s\n", p->s); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " regex is %s\n", regex); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " new has now %s\n", new->s); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " rest is now %s\n", rest); + p->s[1] = '\0'; /* dont realloc */ + GNUNET_CONTAINER_DLL_insert (p->head, p->tail, new); + regex_add (p, rest); + } + return; + } + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " no match\n"); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " new state %s\n", regex); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " under %s\n", ctx->s); + p = GNUNET_malloc (sizeof (struct RegexCombineCtx)); + p->s = GNUNET_strdup (regex); + GNUNET_CONTAINER_DLL_insert (ctx->head, ctx->tail, p); +} + + +/** + * Free all resources used by the context node and all its children. + * + * @param ctx Context to free. + */ +static void +regex_ctx_destroy (struct RegexCombineCtx *ctx) +{ + struct RegexCombineCtx *p; + struct RegexCombineCtx *next; + + for (p = ctx->head; NULL != p; p = next) + { + next = p->next; + regex_ctx_destroy (p); + } + GNUNET_free (ctx->s); + GNUNET_free (ctx); +} + + +/** + * Return a prefix-combine regex that matches the same strings as + * any of the original regexes. + * + * WARNING: only useful for reading specific regexes for specific applications, + * namely the gnunet-regex-profiler / gnunet-regex-daemon. + * This function DOES NOT support arbitrary regex combining. + */ +char * +GNUNET_REGEX_combine (char * const regexes[]) +{ + unsigned int i; + char *combined; + const char *current; + struct RegexCombineCtx *ctx; + + ctx = GNUNET_malloc (sizeof (struct RegexCombineCtx)); + for (i = 0; regexes[i]; i++) + { + current = regexes[i]; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Regex %u: %s\n", i, current); + regex_add (ctx, current); + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "\nCombining...\n"); + + combined = regex_combine (ctx); + + regex_ctx_destroy (ctx); + + return combined; +} + + +/** + * Read a set of regexes from a file, one per line and return them in an array + * suitable for GNUNET_REGEX_combine. + * The array must be free'd using GNUNET_REGEX_free_from_file. + * + * @param filename Name of the file containing the regexes. + * + * @return A newly allocated, NULL terminated array of regexes. + */ +char ** +GNUNET_REGEX_read_from_file (const char *filename) +{ + struct GNUNET_DISK_FileHandle *f; + unsigned int nr; + unsigned int offset; + off_t size; + size_t len; + char *buffer; + char *regex; + char **regexes; + + f = GNUNET_DISK_file_open (filename, + GNUNET_DISK_OPEN_READ, + GNUNET_DISK_PERM_NONE); + if (NULL == f) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Can't open file %s for reading\n", filename); + return NULL; + } + if (GNUNET_OK != GNUNET_DISK_file_handle_size (f, &size)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Can't get size of file %s\n", filename); + GNUNET_DISK_file_close (f); + return NULL; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "using file %s, size %llu\n", + filename, (unsigned long long) size); + + buffer = GNUNET_malloc (size + 1); + GNUNET_DISK_file_read (f, buffer, size); + GNUNET_DISK_file_close (f); + regexes = GNUNET_malloc (sizeof (char *)); + nr = 1; + offset = 0; + regex = NULL; + do + { + if (NULL == regex) + regex = GNUNET_malloc (size + 1); + len = (size_t) sscanf (&buffer[offset], "%s", regex); + if (0 == len) + break; + len = strlen (regex); + offset += len + 1; + if (len < 1) + continue; + if (len < 6 || strncmp (®ex[len - 6], "(0|1)*", 6) != 0) + { + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + "%s (line %u) does not end in \"(0|1)*\"\n", + buffer, nr); + } + else + { + len -= 6; + buffer[len] = '\0'; + } + regex = GNUNET_realloc (regex, len + 1); + GNUNET_array_grow (regexes, nr, nr + 1); + regexes[nr - 2] = regex; + regexes[nr - 1] = NULL; + regex = NULL; + } while (offset < size); + GNUNET_free_non_null (regex); + GNUNET_free (buffer); + + return regexes; +} + + +/** + * Free all memory reserved for a set of regexes created by read_from_file. + * + * @param regexes NULL-terminated array of regexes. + */ +void +GNUNET_REGEX_free_from_file (char **regexes) +{ + unsigned int i; + + for (i = 0; regexes[i]; i++) + GNUNET_free (regexes[i]); + GNUNET_free (regexes); +} + +/* end of regex_test_lib.c */ \ No newline at end of file diff --git a/src/regex/regex_test_lib.h b/src/regex/regex_test_lib.h new file mode 100644 index 0000000..b21af2e --- /dev/null +++ b/src/regex/regex_test_lib.h @@ -0,0 +1,80 @@ +/* + * This file is part of GNUnet + * (C) 2012 Christian Grothoff (and other contributing authors) + * + * GNUnet is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published + * by the Free Software Foundation; either version 3, or (at your + * option) any later version. + * + * GNUnet is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with GNUnet; see the file COPYING. If not, write to the + * Free Software Foundation, Inc., 59 Temple Place - Suite 330, + * Boston, MA 02111-1307, USA. + */ +/** + * @file src/regex/regex_test_lib.h + * @brief library to read regexes representing IP networks from a file. + * and simplyfinying the into one big regex, in order to run + * tests (regex performance, mesh profiler). + * @author Bertlomiej Polot + * + */ + +#ifndef GNUNET_REGEX_TEST_LIB_H +#define GNUNET_REGEX_TEST_LIB_H + + +#ifdef __cplusplus +extern "C" +{ + #if 0 /* keep Emacsens' auto-indent happy */ +} +#endif +#endif + +/** + * Combine an array of regexes into a single prefix-shared regex. + * + * @param regexes A NULL-terminated array of regexes. + * + * @retrun A string with a single regex that matches any of the original regexes + */ +char * +GNUNET_REGEX_combine(char * const regexes[]); + +/** + * Read a set of regexes from a file, one per line and return them in an array + * suitable for GNUNET_REGEX_combine. + * The array must be free'd using GNUNET_REGEX_free_from_file. + * + * @param filename Name of the file containing the regexes. + * + * @return A newly allocated, NULL terminated array of regexes. + */ +char ** +GNUNET_REGEX_read_from_file (const char *filename); + + +/** + * Free all memory reserved for a set of regexes created by read_from_file. + * + * @param regexes NULL-terminated array of regexes. + */ +void +GNUNET_REGEX_free_from_file (char **regexes); + +#if 0 /* keep Emacsens' auto-indent happy */ +{ + #endif + #ifdef __cplusplus +} +#endif + +/* end of gnunet_regex_lib.h */ +#endif \ No newline at end of file diff --git a/src/regex/test_regex_eval_api.c b/src/regex/test_regex_eval_api.c index c63e97c..ce6f923 100644 --- a/src/regex/test_regex_eval_api.c +++ b/src/regex/test_regex_eval_api.c @@ -26,6 +26,7 @@ #include #include "platform.h" #include "gnunet_regex_lib.h" +#include "regex_internal.h" enum Match_Result { @@ -41,148 +42,155 @@ struct Regex_String_Pair enum Match_Result expected_results[20]; }; -static const char allowed_literals[] = - "0123456789" "ABCDEFGHIJKLMNOPQRSTUVWXYZ" "abcdefghijklmnopqrstuvwxyz"; +/** + * Random regex test. Generate a random regex as well as 'str_count' strings to + * match it against. Will match using GNUNET_REGEX implementation and compare + * the result to glibc regex result. 'rx_length' has to be smaller then + * 'max_str_len'. + * + * @param rx_length length of the regular expression. + * @param max_str_len maximum length of the random strings. + * @param str_count number of generated random strings. + * + * @return 0 on success, non 0 otherwise. + */ int test_random (unsigned int rx_length, unsigned int max_str_len, unsigned int str_count) { - int i; - int j; - int rx_exp; - char rand_rx[rx_length + 1]; - char matching_str[str_count][max_str_len + 1]; - char *rand_rxp; - char *matching_strp; - int char_op_switch; - int last_was_op; - char current_char; + unsigned int i; + char *rand_rx; + char *matching_str; int eval; int eval_check; + int eval_canonical; + int eval_canonical_check; struct GNUNET_REGEX_Automaton *dfa; regex_t rx; regmatch_t matchptr[1]; char error[200]; int result; - unsigned int str_len; + char *canonical_regex = NULL; - // At least one string is needed for matching + /* At least one string is needed for matching */ GNUNET_assert (str_count > 0); - // The string should be at least as long as the regex itself + /* The string should be at least as long as the regex itself */ GNUNET_assert (max_str_len >= rx_length); - rand_rxp = rand_rx; - matching_strp = matching_str[0]; - current_char = 0; - last_was_op = 1; + /* Generate random regex and a string that matches the regex */ + matching_str = GNUNET_malloc (rx_length + 1); + rand_rx = GNUNET_REGEX_generate_random_regex (rx_length, matching_str); - // Generate random regex and a string that matches the regex - for (i = 0; i < rx_length; i++) + /* Now match */ + result = 0; + for (i = 0; i < str_count; i++) { - char_op_switch = 0 + (int) (1.0 * rand () / (RAND_MAX + 1.0)); - - if (0 == char_op_switch && !last_was_op) + if (0 < i) { - last_was_op = 1; - rx_exp = rand () % 4; - - switch (rx_exp) - { - case 0: - current_char = '+'; - break; - case 1: - current_char = '*'; - break; - case 2: - current_char = '?'; - break; - case 3: - if (i < rx_length - 1) // '|' cannot be at the end - current_char = '|'; - else - current_char = - allowed_literals[rand () % (sizeof (allowed_literals) - 1)]; - break; - } + matching_str = GNUNET_REGEX_generate_random_string (max_str_len); } - else + + /* Match string using DFA */ + dfa = GNUNET_REGEX_construct_dfa (rand_rx, strlen (rand_rx), 0); + if (NULL == dfa) { - current_char = - allowed_literals[rand () % (sizeof (allowed_literals) - 1)]; - last_was_op = 0; + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Constructing DFA failed\n"); + goto error; } - if (current_char != '+' && current_char != '*' && current_char != '?' && - current_char != '|') + eval = GNUNET_REGEX_eval (dfa, matching_str); + /* save the canonical regex for later comparison */ + canonical_regex = GNUNET_strdup (GNUNET_REGEX_get_canonical_regex (dfa)); + GNUNET_REGEX_automaton_destroy (dfa); + + /* Match string using glibc regex */ + if (0 != regcomp (&rx, rand_rx, REG_EXTENDED)) { - *matching_strp = current_char; - matching_strp++; + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Could not compile regex using regcomp: %s\n", rand_rx); + goto error; } - *rand_rxp = current_char; - rand_rxp++; - } - *rand_rxp = '\0'; - *matching_strp = '\0'; + eval_check = regexec (&rx, matching_str, 1, matchptr, 0); + regfree (&rx); - // Generate some random strings for matching... - // Start at 1, because the first string is generated above during regex generation - for (i = 1; i < str_count; i++) - { - str_len = rand () % max_str_len; - for (j = 0; j < str_len; j++) - matching_str[i][j] = - allowed_literals[rand () % (sizeof (allowed_literals) - 1)]; - matching_str[i][str_len] = '\0'; - } + /* We only want to match the whole string, because that's what our DFA does, + * too. */ + if (eval_check == 0 && + (matchptr[0].rm_so != 0 || matchptr[0].rm_eo != strlen (matching_str))) + eval_check = 1; - // Now match - result = 0; - for (i = 0; i < str_count; i++) - { - // Match string using DFA - dfa = GNUNET_REGEX_construct_dfa (rand_rx, strlen (rand_rx)); + /* Match canonical regex */ + dfa = + GNUNET_REGEX_construct_dfa (canonical_regex, strlen (canonical_regex), + 0); if (NULL == dfa) { GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Constructing DFA failed\n"); - return -1; + goto error; } - eval = GNUNET_REGEX_eval (dfa, matching_str[i]); + eval_canonical = GNUNET_REGEX_eval (dfa, matching_str); GNUNET_REGEX_automaton_destroy (dfa); - // Match string using glibc regex - if (0 != regcomp (&rx, rand_rx, REG_EXTENDED)) + if (0 != regcomp (&rx, canonical_regex, REG_EXTENDED)) { GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "Could not compile regex using regcomp\n"); - return -1; + "Could not compile regex using regcomp: %s\n", + canonical_regex); + goto error; } - eval_check = regexec (&rx, matching_str[i], 1, matchptr, 0); + eval_canonical_check = regexec (&rx, matching_str, 1, matchptr, 0); regfree (&rx); - // We only want to match the whole string, because that's what our DFA does, too. - if (eval_check == 0 && - (matchptr[0].rm_so != 0 || - matchptr[0].rm_eo != strlen (matching_str[i]))) - eval_check = 1; + /* We only want to match the whole string, because that's what our DFA does, + * too. */ + if (eval_canonical_check == 0 && + (matchptr[0].rm_so != 0 || matchptr[0].rm_eo != strlen (matching_str))) + eval_canonical_check = 1; - // compare result - if (eval_check != eval) + /* compare results */ + if (eval_check != eval || eval_canonical != eval_canonical_check) { regerror (eval_check, &rx, error, sizeof error); - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "Unexpected result:\nregex: %s\nstring: %s\ngnunet regex: %i\nglibc regex: %i\nglibc error: %s\n\n", - rand_rx, matching_str, eval, eval_check, error); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Unexpected result:\nregex: %s\ncanonical_regex: %s\n\ + string: %s\ngnunet regex: %i\nglibc regex: %i\n\ + canonical regex: %i\ncanonical regex glibc: %i\n\ + glibc error: %s\n\n", rand_rx, canonical_regex, matching_str, + eval, eval_check, eval_canonical, eval_canonical_check, error); result += 1; } + GNUNET_free (canonical_regex); + GNUNET_free (matching_str); + canonical_regex = NULL; + matching_str = NULL; } + + GNUNET_free (rand_rx); + return result; + +error: + GNUNET_free_non_null (matching_str); + GNUNET_free_non_null (rand_rx); + GNUNET_free_non_null (canonical_regex); + return -1; } +/** + * Automaton test that compares the result of matching regular expression 'rx' + * with the strings and expected results in 'rxstr' with the result of matching + * the same strings with glibc regex. + * + * @param a automaton. + * @param rx compiled glibc regex. + * @param rxstr regular expression and strings with expected results to + * match against. + * + * @return 0 on successfull, non 0 otherwise + */ int test_automaton (struct GNUNET_REGEX_Automaton *a, regex_t * rx, struct Regex_String_Pair *rxstr) @@ -207,7 +215,8 @@ test_automaton (struct GNUNET_REGEX_Automaton *a, regex_t * rx, eval = GNUNET_REGEX_eval (a, rxstr->strings[i]); eval_check = regexec (rx, rxstr->strings[i], 1, matchptr, 0); - // We only want to match the whole string, because that's what our DFA does, too. + /* We only want to match the whole string, because that's what our DFA does, + * too. */ if (eval_check == 0 && (matchptr[0].rm_so != 0 || matchptr[0].rm_eo != strlen (rxstr->strings[i]))) @@ -220,11 +229,13 @@ test_automaton (struct GNUNET_REGEX_Automaton *a, regex_t * rx, result = 1; regerror (eval_check, rx, error, sizeof error); GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "Unexpected result:\nregex: %s\nstring: %s\nexpected result: %i\n" - "gnunet regex: %i\nglibc regex: %i\nglibc error: %s\nrm_so: %i\nrm_eo: %i\n\n", - rxstr->regex, rxstr->strings[i], rxstr->expected_results[i], - eval, eval_check, error, matchptr[0].rm_so, - matchptr[0].rm_eo); + "Unexpected result:\nregex: %s\ncanonical_regex: %s\n" + "string: %s\nexpected result: %i\n" + "gnunet regex: %i\nglibc regex: %i\nglibc error: %s\n" + "rm_so: %i\nrm_eo: %i\n\n", rxstr->regex, + GNUNET_REGEX_get_canonical_regex (a), rxstr->strings[i], + rxstr->expected_results[i], eval, eval_check, error, + matchptr[0].rm_so, matchptr[0].rm_eo); } } return result; @@ -233,13 +244,7 @@ test_automaton (struct GNUNET_REGEX_Automaton *a, regex_t * rx, int main (int argc, char *argv[]) { - GNUNET_log_setup ("test-regex", -#if VERBOSE - "DEBUG", -#else - "WARNING", -#endif - NULL); + GNUNET_log_setup ("test-regex", "WARNING", NULL); struct GNUNET_REGEX_Automaton *a; regex_t rx; @@ -247,17 +252,20 @@ main (int argc, char *argv[]) int check_nfa; int check_dfa; int check_rand; + char *check_proof; - struct Regex_String_Pair rxstr[8] = { + struct Regex_String_Pair rxstr[19] = { {"ab?(abcd)?", 5, {"ababcd", "abab", "aabcd", "a", "abb"}, {match, nomatch, match, match, nomatch}}, {"ab(c|d)+c*(a(b|c)d)+", 5, - {"abcdcdcdcdddddabd", "abcd", "abcddddddccccccccccccccccccccccccabdacdabd", + {"abcdcdcdcdddddabd", "abcd", + "abcddddddccccccccccccccccccccccccabdacdabd", "abccccca", "abcdcdcdccdabdabd"}, {match, nomatch, match, nomatch, match}}, {"ab+c*(a(bx|c)d)+", 5, - {"abcdcdcdcdddddabd", "abcd", "abcddddddccccccccccccccccccccccccabdacdabd", + {"abcdcdcdcdddddabd", "abcd", + "abcddddddccccccccccccccccccccccccabdacdabd", "abccccca", "abcdcdcdccdabdabd"}, {nomatch, nomatch, nomatch, nomatch, nomatch}}, {"a+X*y+c|p|R|Z*K*y*R+w|Y*6+n+h*k*w+V*F|W*B*e*", 1, @@ -272,16 +280,53 @@ main (int argc, char *argv[]) {"V|M*o?x*p*d+h+b|E*m?h?Y*E*O?W*W*P+o?Z+H*M|I*q+C*a+5?5*9|b?z|G*y*k?R|p+u|8*h?B+l*H|e|L*O|1|F?v*0?5|C+", 1, {"VMoxpdhbEmhYEOWWPoZHMIqCa559bzGykRpu8hBlHeLO1Fv05C"}, {nomatch}}, + {"(bla)*", 8, + {"", "bla", "blabla", "bl", "la", "b", "l", "a"}, + {match, match, match, nomatch, nomatch, nomatch, nomatch, nomatch}}, + {"ab(c|d)+c*(a(b|c)+d)+(bla)(bla)*", 8, + {"ab", "abcabdbla", "abdcccccccccccabcbccdblablabla", "bl", "la", "b", + "l", + "a"}, + {nomatch, match, match, nomatch, nomatch, nomatch, nomatch, nomatch}}, + {"a|aa*a", 6, + {"", "a", "aa", "aaa", "aaaa", "aaaaa"}, + {nomatch, match, match, match, match, match}}, + {"ab(c|d)+c*(a(b|c)+d)+(bla)+", 1, + {"abcabdblaacdbla"}, + {nomatch}}, + {"(ac|b)+", 8, + {"b", "bb", "ac", "", "acb", "bacbacac", "acacac", "abc"}, + {match, match, match, nomatch, match, match, match, nomatch}}, + {"(ab|c)+", 7, + {"", "ab", "c", "abc", "ababcc", "acc", "abac"}, + {nomatch, match, match, match, match, nomatch, nomatch}}, + {"((j|2j)K|(j|2j)AK|(j|2j)(D|e|(j|2j)A(D|e))D*K)", 1, + {"", "2j2jADK", "j2jADK"}, + {nomatch, match, match}}, + {"((j|2j)K|(j|2j)(D|e|((j|2j)j|(j|2j)2j)A(D|e))D*K|(j|2j)AK)", 2, + {"", "2j2jjADK", "j2jADK"}, + {nomatch, match, match}}, {"ab(c|d)+c*(a(b|c)d)+", 1, {"abacd"}, - {nomatch}} + {nomatch}}, + {"d|5kl", 1, + {"d5kl"}, + {nomatch}}, + {"a()b", 1, + {"ab"}, + {match}}, + {"GNVPN-0001-PAD(001110101001001010(0|1)*|001110101001001010000(0|1)*|001110101001001010001(0|1)*|001110101001001010010(0|1)*|001110101001001010011(0|1)*|001110101001001010100(0|1)*|001110101001001010101(0|1)*|001110101001001010110(0|1)*|001110101001001010111(0|1)*|0011101010110110(0|1)*|001110101011011000000(0|1)*|001110101011011000001(0|1)*|001110101011011000010(0|1)*|001110101011011000011(0|1)*|001110101011011000100(0|1)*|001110101011011000101(0|1)*|001110101011011000110(0|1)*|001110101011011000111(0|1)*|001110101011011001000(0|1)*|001110101011011001001(0|1)*|001110101011011001010(0|1)*|001110101011011001011(0|1)*|001110101011011001100(0|1)*|001110101011011001101(0|1)*|001110101011011001110(0|1)*|001110101011011001111(0|1)*|001110101011011010000(0|1)*|001110101011011010001(0|1)*|001110101011011010010(0|1)*|001110101011011010011(0|1)*|001110101011011010100(0|1)*|001110101011011010101(0|1)*|001110101011011010110(0|1)*|001110101011011010111(0|1)*|001110101011011011000(0|1)*|001110101011011011001(0|1)*|001110101011011011010(0|1)*|001110101011011011011(0|1)*|001110101011011011100(0|1)*|001110101011011011101(0|1)*|001110101011011011110(0|1)*|001110101011011011111(0|1)*|0011101110111101(0|1)*|001110111011110100000(0|1)*|001110111011110100001(0|1)*|001110111011110100010(0|1)*|001110111011110100011(0|1)*|001110111011110100100(0|1)*|001110111011110100101(0|1)*|001110111011110100110(0|1)*|001110111011110100111(0|1)*|001110111011110101000(0|1)*|001110111011110101001(0|1)*|001110111011110101010(0|1)*|001110111011110101011(0|1)*|001110111011110101100(0|1)*|001110111011110101101(0|1)*|001110111011110101110(0|1)*|001110111011110101111(0|1)*|001110111011110110000(0|1)*|001110111011110110001(0|1)*|001110111011110110010(0|1)*|001110111011110110011(0|1)*|001110111011110110100(0|1)*|001110111011110110101(0|1)*|001110111011110110110(0|1)*|001110111011110110111(0|1)*|001110111011110111000(0|1)*|001110111011110111001(0|1)*|001110111011110111010(0|1)*|001110111011110111011(0|1)*|001110111011110111100(0|1)*|001110111011110111101(0|1)*|001110111011110111110(0|1)*|0111010001010110(0|1)*|011101000101011000000(0|1)*|011101000101011000001(0|1)*|011101000101011000010(0|1)*|011101000101011000011(0|1)*|011101000101011000100(0|1)*|011101000101011000101(0|1)*|011101000101011000110(0|1)*|011101000101011000111(0|1)*|011101000101011001000(0|1)*|011101000101011001001(0|1)*|011101000101011001010(0|1)*|011101000101011001011(0|1)*|011101000101011001100(0|1)*|011101000101011001101(0|1)*|011101000101011001110(0|1)*|011101000101011001111(0|1)*|011101000101011010000(0|1)*|011101000101011010001(0|1)*|011101000101011010010(0|1)*|011101000101011010011(0|1)*|011101000101011010100(0|1)*|011101000101011010101(0|1)*|011101000101011010110(0|1)*|011101000101011010111(0|1)*|011101000101011011000(0|1)*|011101000101011011001(0|1)*|011101000101011011010(0|1)*|011101000101011011011(0|1)*|011101000101011011100(0|1)*|011101000101011011101(0|1)*|011101000101011011110(0|1)*|011101000101011011111(0|1)*|0111010001010111(0|1)*|011101000101011100000(0|1)*|011101000101011100001(0|1)*|011101000101011100010(0|1)*|011101000101011100011(0|1)*|011101000101011100100(0|1)*|011101000101011100101(0|1)*|011101000101011100110(0|1)*|011101000101011100111(0|1)*|011101000101011101000(0|1)*|011101000101011101001(0|1)*|011101000101011101010(0|1)*|011101000101011101011(0|1)*|011101000101011101100(0|1)*|011101000101011101101(0|1)*|011101000101011101110(0|1)*|011101000101011101111(0|1)*|011101000101011110000(0|1)*|011101000101011110001(0|1)*|011101000101011110010(0|1)*|011101000101011110011(0|1)*|011101000101011110100(0|1)*|011101000101011110101(0|1)*|011101000101011110110(0|1)*|011101000101011110111(0|1)*|011101000101011111000(0|1)*|011101000101011111001(0|1)*|011101000101011111010(0|1)*|011101000101011111011(0|1)*|011101000101011111100(0|1)*|011101000101011111101(0|1)*|011101000101011111110(0|1)*|011101000101011111111(0|1)*|0111010001011000(0|1)*|011101000101100000000(0|1)*|011101000101100000001(0|1)*|011101000101100000010(0|1)*|011101000101100000011(0|1)*|011101000101100000100(0|1)*|011101000101100000101(0|1)*|011101000101100000110(0|1)*|011101000101100000111(0|1)*|011101000101100001000(0|1)*|011101000101100001001(0|1)*|011101000101100001010(0|1)*|011101000101100001011(0|1)*|011101000101100001100(0|1)*|011101000101100001101(0|1)*|011101000101100001110(0|1)*|011101000101100001111(0|1)*|011101000101100010000(0|1)*|011101000101100010001(0|1)*|011101000101100010010(0|1)*|011101000101100010011(0|1)*|011101000101100010100(0|1)*|011101000101100010101(0|1)*|011101000101100010110(0|1)*|011101000101100010111(0|1)*|011101000101100011000(0|1)*|011101000101100011001(0|1)*|011101000101100011010(0|1)*|011101000101100011011(0|1)*|011101000101100011100(0|1)*|011101000101100011101(0|1)*|011101000101100011110(0|1)*|011101000101100011111(0|1)*|01110100010110010(0|1)*|011101000101100100000(0|1)*|011101000101100100001(0|1)*|011101000101100100010(0|1)*|011101000101100100011(0|1)*|011101000101100100100(0|1)*|011101000101100100101(0|1)*|011101000101100100110(0|1)*|011101000101100100111(0|1)*|011101000101100101000(0|1)*|011101000101100101001(0|1)*|011101000101100101010(0|1)*|011101000101100101011(0|1)*|011101000101100101100(0|1)*|011101000101100101101(0|1)*|011101000101100101110(0|1)*|011101000101100101111(0|1)*|011101000101100101111000(0|1)*|1100101010011100(0|1)*|110010101001110000000(0|1)*|110010101001110000000001(0|1)*|110010101001110000000010(0|1)*|110010101001110000000110(0|1)*|110010101001110000001(0|1)*|110010101001110000001000(0|1)*|110010101001110000001001(0|1)*|110010101001110000001010(0|1)*|110010101001110000001011(0|1)*|110010101001110000001101(0|1)*|110010101001110000001110(0|1)*|110010101001110000010(0|1)*|110010101001110000011(0|1)*|110010101001110000100(0|1)*|110010101001110000101(0|1)*|110010101001110000110(0|1)*|110010101001110000111(0|1)*|110010101001110001000(0|1)*|110010101001110001001(0|1)*|110010101001110001010(0|1)*|110010101001110001011(0|1)*|110010101001110001100(0|1)*|110010101001110001101(0|1)*|110010101001110001110(0|1)*|110010101001110001111(0|1)*|110010101001110010000(0|1)*|110010101001110010001(0|1)*|110010101001110010010(0|1)*|110010101001110010011(0|1)*|110010101001110010100(0|1)*|110010101001110010101(0|1)*|110010101001110010110(0|1)*|110010101001110010111(0|1)*|110010101001110011000(0|1)*|110010101001110011001(0|1)*|110010101001110011010(0|1)*|110010101001110011011(0|1)*|110010101001110011100(0|1)*|110010101001110011101(0|1)*|110010101001110011110(0|1)*|110010101001110011111(0|1)*|1101101010111010(0|1)*|110110101011101000000(0|1)*|110110101011101000000001(0|1)*|110110101011101000001000(0|1)*|110110101011101000001001(0|1)*|110110101011101000001010(0|1)*|110110101011101000001011(0|1)*|110110101011101000001100(0|1)*|110110101011101000001110(0|1)*|110110101011101000001111(0|1)*|110110101011101000010(0|1)*|110110101011101000010000(0|1)*|110110101011101000010001(0|1)*|110110101011101000010010(0|1)*|110110101011101000010011(0|1)*|110110101011101000011(0|1)*|110110101011101000100(0|1)*|110110101011101000101(0|1)*|110110101011101000110(0|1)*|110110101011101000111(0|1)*|110110101011101001000(0|1)*|110110101011101001001(0|1)*|110110101011101001010(0|1)*|110110101011101001011(0|1)*|110110101011101001100(0|1)*|110110101011101001101(0|1)*|110110101011101001110(0|1)*|110110101011101001111(0|1)*|110110101011101010000(0|1)*|110110101011101010001(0|1)*|110110101011101010010(0|1)*|110110101011101010011(0|1)*|110110101011101010100(0|1)*|110110101011101010101(0|1)*|110110101011101010110(0|1)*|110110101011101010111(0|1)*|110110101011101011000(0|1)*|110110101011101011001(0|1)*|110110101011101011010(0|1)*|110110101011101011011(0|1)*|110110101011101011100(0|1)*|110110101011101011101(0|1)*|110110101011101011110(0|1)*|110110101011101011111(0|1)*|1101101011010100(0|1)*|110110101101010000000(0|1)*|110110101101010000001(0|1)*|110110101101010000010(0|1)*|110110101101010000011(0|1)*|110110101101010000100(0|1)*|110110101101010000101(0|1)*|110110101101010000110(0|1)*|110110101101010000111(0|1)*|110110101101010001000(0|1)*|110110101101010001001(0|1)*|110110101101010001010(0|1)*|110110101101010001011(0|1)*|110110101101010001100(0|1)*|110110101101010001101(0|1)*|110110101101010001110(0|1)*|110110101101010001111(0|1)*|110110101101010010000(0|1)*|110110101101010010001(0|1)*|110110101101010010010(0|1)*|110110101101010010011(0|1)*|110110101101010010100(0|1)*|1101101011010100101000(0|1)*|110110101101010010101(0|1)*|110110101101010010110(0|1)*|110110101101010010111(0|1)*|110110101101010011000(0|1)*|110110101101010011010(0|1)*|110110101101010011011(0|1)*|110110101101010011100(0|1)*|110110101101010011101(0|1)*|110110101101010011110(0|1)*|110110101101010011111(0|1)*|1101111010100100(0|1)*|110111101010010000000(0|1)*|110111101010010000001(0|1)*|110111101010010000010(0|1)*|110111101010010000011(0|1)*|110111101010010000100(0|1)*|110111101010010000101(0|1)*|110111101010010000110(0|1)*|110111101010010000111(0|1)*|110111101010010001000(0|1)*|110111101010010001001(0|1)*|110111101010010001010(0|1)*|110111101010010001011(0|1)*|110111101010010001100(0|1)*|110111101010010001101(0|1)*|110111101010010001110(0|1)*|110111101010010001111(0|1)*|110111101010010010000(0|1)*|110111101010010010001(0|1)*|110111101010010010010(0|1)*|110111101010010010011(0|1)*|110111101010010010100(0|1)*|110111101010010010101(0|1)*|110111101010010010110(0|1)*|110111101010010010111(0|1)*|110111101010010011000(0|1)*|110111101010010011001(0|1)*|110111101010010011010(0|1)*|110111101010010011011(0|1)*|110111101010010011100(0|1)*|110111101010010011101(0|1)*|110111101010010011110(0|1)*|110111101010010011111(0|1)*|11011110101001010(0|1)*|110111101010010100000(0|1)*|110111101010010100001(0|1)*|110111101010010100010(0|1)*|110111101010010100011(0|1)*|110111101010010100100(0|1)*|110111101010010100101(0|1)*|110111101010010100110(0|1)*|110111101010010100111(0|1)*|110111101010010101000(0|1)*|110111101010010101001(0|1)*|110111101010010101010(0|1)*|110111101010010101011(0|1)*|110111101010010101100(0|1)*|110111101010010101101(0|1)*|110111101010010101110(0|1)*|110111101010010101111(0|1)*)", + 2, + {"GNVPN-0001-PAD1101111010100101011101010101010101", + "GNVPN-0001-PAD11001010100111000101101010101"}, + {match, match}} }; check_nfa = 0; check_dfa = 0; check_rand = 0; - for (i = 0; i < 8; i++) + for (i = 0; i < 19; i++) { if (0 != regcomp (&rx, rxstr[i].regex, REG_EXTENDED)) { @@ -290,22 +335,31 @@ main (int argc, char *argv[]) return 1; } - // NFA test + /* NFA test */ a = GNUNET_REGEX_construct_nfa (rxstr[i].regex, strlen (rxstr[i].regex)); check_nfa += test_automaton (a, &rx, &rxstr[i]); GNUNET_REGEX_automaton_destroy (a); - // DFA test - a = GNUNET_REGEX_construct_dfa (rxstr[i].regex, strlen (rxstr[i].regex)); + /* DFA test */ + a = GNUNET_REGEX_construct_dfa (rxstr[i].regex, strlen (rxstr[i].regex), 0); + check_dfa += test_automaton (a, &rx, &rxstr[i]); + check_proof = GNUNET_strdup (GNUNET_REGEX_get_canonical_regex (a)); + GNUNET_REGEX_automaton_destroy (a); + + a = GNUNET_REGEX_construct_dfa (check_proof, strlen (check_proof), 0); check_dfa += test_automaton (a, &rx, &rxstr[i]); GNUNET_REGEX_automaton_destroy (a); + if (0 != check_dfa) + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "check_proof: %s\n", check_proof); + GNUNET_free_non_null (check_proof); regfree (&rx); } + /* Random tests */ srand (time (NULL)); - for (i = 0; i < 150; i++) - check_rand += test_random (150, 200, 25); + for (i = 0; i < 20; i++) + check_rand += test_random (50, 60, 10); return check_nfa + check_dfa + check_rand; } diff --git a/src/regex/test_regex_graph_api.c b/src/regex/test_regex_graph_api.c new file mode 100644 index 0000000..3ae6073 --- /dev/null +++ b/src/regex/test_regex_graph_api.c @@ -0,0 +1,157 @@ +/* + This file is part of GNUnet + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ +/** + * @file regex/test_regex_graph_api.c + * @brief test for regex_graph.c + * @author Maximilian Szengel + */ +#include +#include +#include "platform.h" +#include "gnunet_regex_lib.h" +#include "regex_internal.h" + +#define KEEP_FILES 1 + +/** + * Check if 'filename' exists and is not empty. + * + * @param filename name of the file that should be checked + * + * @return 0 if ok, non 0 on error. + */ +static int +filecheck (const char *filename) +{ + int error = 0; + FILE *fp; + + /* Check if file was created and delete it again */ + if (NULL == (fp = fopen (filename, "r"))) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Could not find graph %s\n", filename); + return 1; + } + + GNUNET_break (0 == fseek (fp, 0L, SEEK_END)); + if (1 > ftell (fp)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Graph writing failed, got empty file (%s)!\n", filename); + error = 2; + } + + GNUNET_assert (0 == fclose (fp)); + + if (!KEEP_FILES) + { + if (0 != unlink (filename)) + GNUNET_log_strerror_file (GNUNET_ERROR_TYPE_ERROR, "unlink", filename); + } + return error; +} + + +int +main (int argc, char *argv[]) +{ + int error; + struct GNUNET_REGEX_Automaton *a; + unsigned int i; + const char *filename = "test_graph.dot"; + + const char *regex[12] = { + "ab(c|d)+c*(a(b|c)+d)+(bla)+", + "(bla)*", + "b(lab)*la", + "(ab)*", + "ab(c|d)+c*(a(b|c)+d)+(bla)(bla)*", + "z(abc|def)?xyz", + "1*0(0|1)*", + "a*b*", + "a+X*y+c|p|R|Z*K*y*R+w|Y*6+n+h*k*w+V*F|W*B*e*", + "a", + "a|b", + "PADPADPADPADPADPabcdefghixxxxxxxxxxxxxjklmnop*qstoisdjfguisdfguihsdfgbdsuivggsd" + }; + + GNUNET_log_setup ("test-regex", "WARNING", NULL); + error = 0; + for (i = 0; i < 12; i++) + { + /* Check NFA graph creation */ + a = GNUNET_REGEX_construct_nfa (regex[i], strlen (regex[i])); + GNUNET_REGEX_automaton_save_graph (a, filename, GNUNET_REGEX_GRAPH_DEFAULT); + GNUNET_REGEX_automaton_destroy (a); + error += filecheck (filename); + + a = GNUNET_REGEX_construct_nfa (regex[i], strlen (regex[i])); + GNUNET_REGEX_automaton_save_graph (a, filename, + GNUNET_REGEX_GRAPH_DEFAULT | + GNUNET_REGEX_GRAPH_VERBOSE); + GNUNET_REGEX_automaton_destroy (a); + error += filecheck (filename); + + a = GNUNET_REGEX_construct_nfa (regex[i], strlen (regex[i])); + GNUNET_REGEX_automaton_save_graph (a, filename, + GNUNET_REGEX_GRAPH_DEFAULT | + GNUNET_REGEX_GRAPH_COLORING); + GNUNET_REGEX_automaton_destroy (a); + error += filecheck (filename); + + a = GNUNET_REGEX_construct_nfa (regex[i], strlen (regex[i])); + GNUNET_REGEX_automaton_save_graph (a, filename, + GNUNET_REGEX_GRAPH_DEFAULT | + GNUNET_REGEX_GRAPH_VERBOSE | + GNUNET_REGEX_GRAPH_COLORING); + GNUNET_REGEX_automaton_destroy (a); + error += filecheck (filename); + + + /* Check DFA graph creation */ + a = GNUNET_REGEX_construct_dfa (regex[i], strlen (regex[i]), 0); + GNUNET_REGEX_automaton_save_graph (a, filename, GNUNET_REGEX_GRAPH_DEFAULT); + GNUNET_REGEX_automaton_destroy (a); + error += filecheck (filename); + + a = GNUNET_REGEX_construct_dfa (regex[i], strlen (regex[i]), 0); + GNUNET_REGEX_automaton_save_graph (a, filename, + GNUNET_REGEX_GRAPH_DEFAULT | + GNUNET_REGEX_GRAPH_VERBOSE); + GNUNET_REGEX_automaton_destroy (a); + error += filecheck (filename); + + a = GNUNET_REGEX_construct_dfa (regex[i], strlen (regex[i]), 0); + GNUNET_REGEX_automaton_save_graph (a, filename, + GNUNET_REGEX_GRAPH_DEFAULT | + GNUNET_REGEX_GRAPH_COLORING); + GNUNET_REGEX_automaton_destroy (a); + error += filecheck (filename); + + + a = GNUNET_REGEX_construct_dfa (regex[i], strlen (regex[i]), 4); + GNUNET_REGEX_automaton_save_graph (a, filename, GNUNET_REGEX_GRAPH_DEFAULT); + GNUNET_REGEX_automaton_destroy (a); + error += filecheck (filename); + + } + + return error; +} diff --git a/src/regex/test_regex_iptoregex.c b/src/regex/test_regex_iptoregex.c new file mode 100644 index 0000000..e33e792 --- /dev/null +++ b/src/regex/test_regex_iptoregex.c @@ -0,0 +1,103 @@ +/* + This file is part of GNUnet + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ +/** + * @file regex/test_regex_iptoregex.c + * @brief simple test for regex.c iptoregex functions + * @author Maximilian Szengel + */ +#include "platform.h" +#include "gnunet_regex_lib.h" + + +static int +test_iptoregex (const char *ipv4, const char *netmask, const char *expectedv4, + const char *ipv6, unsigned int prefixlen, + const char *expectedv6) +{ + int error = 0; + + struct in_addr a; + struct in6_addr b; + char rxv4[GNUNET_REGEX_IPV4_REGEXLEN]; + char rxv6[GNUNET_REGEX_IPV6_REGEXLEN]; + + GNUNET_assert (1 == inet_pton (AF_INET, ipv4, &a)); + GNUNET_REGEX_ipv4toregex (&a, netmask, rxv4); + + + if (0 != strcmp (rxv4, expectedv4)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Expected: %s but got: %s\n", + expectedv4, rxv4); + error++; + } + + GNUNET_assert (1 == inet_pton (AF_INET6, ipv6, &b)); + GNUNET_REGEX_ipv6toregex (&b, prefixlen, rxv6); + + if (0 != strcmp (rxv6, expectedv6)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Expected: %s but got: %s\n", + expectedv6, rxv6); + error++; + } + + return error; +} + +int +main (int argc, char *argv[]) +{ + GNUNET_log_setup ("test-regex", "WARNING", NULL); + + int error; + + error = 0; + + error += + test_iptoregex ("192.0.0.0", "255.255.255.0", + "110000000000000000000000(0|1)+", "FFFF::0", 16, + "1111111111111111(0|1)+"); + + error += + test_iptoregex ("187.238.225.0", "255.255.255.128", + "1011101111101110111000010(0|1)+", "E1E1:73F9:51BE::0", + 49, + "1110000111100001011100111111100101010001101111100(0|1)+"); + + error += + test_iptoregex ("255.255.255.255", "255.255.255.255", + "11111111111111111111111111111111", + "FFFF:FFFF:FFFF:FFFF:FFFF:FFFF:FFFF:FFFF", 128, + "11111111111111111111111111111111" + "11111111111111111111111111111111" + "11111111111111111111111111111111" + "11111111111111111111111111111111"); + + error += + test_iptoregex ("0.0.0.0", "255.255.255.255", + "00000000000000000000000000000000", "0::0", 128, + "00000000000000000000000000000000" + "00000000000000000000000000000000" + "00000000000000000000000000000000" + "00000000000000000000000000000000"); + + return error; +} diff --git a/src/regex/test_regex_iterate_api.c b/src/regex/test_regex_iterate_api.c index b214d6a..695bc30 100644 --- a/src/regex/test_regex_iterate_api.c +++ b/src/regex/test_regex_iterate_api.c @@ -26,46 +26,233 @@ #include #include "platform.h" #include "gnunet_regex_lib.h" +#include "regex_internal.h" -void -key_iterator (void *cls, const GNUNET_HashCode * key, const char *proof, +/** + * Regex initial padding. + */ +#define INITIAL_PADDING "PADPADPADPADPADP" + +/** + * Set to GNUNET_YES to save a debug graph. + */ +#define GNUNET_REGEX_ITERATE_SAVE_DEBUG_GRAPH GNUNET_NO + +static unsigned int transition_counter; + +struct IteratorContext +{ + int error; + int should_save_graph; + FILE *graph_filep; + unsigned int string_count; + char *const *strings; + unsigned int match_count; +}; + +struct RegexStringPair +{ + char *regex; + unsigned int string_count; + char *strings[20]; +}; + + +static void +key_iterator (void *cls, const struct GNUNET_HashCode *key, const char *proof, int accepting, unsigned int num_edges, const struct GNUNET_REGEX_Edge *edges) { - int i; + unsigned int i; + struct IteratorContext *ctx = cls; + char *out_str; + char *state_id = GNUNET_strdup (GNUNET_h2s (key)); + + GNUNET_assert (NULL != proof); + if (GNUNET_YES == ctx->should_save_graph) + { + if (GNUNET_YES == accepting) + GNUNET_asprintf (&out_str, "\"%s\" [shape=doublecircle]\n", state_id); + else + GNUNET_asprintf (&out_str, "\"%s\" [shape=circle]\n", state_id); + fwrite (out_str, strlen (out_str), 1, ctx->graph_filep); + GNUNET_free (out_str); + + for (i = 0; i < num_edges; i++) + { + transition_counter++; + GNUNET_asprintf (&out_str, "\"%s\" -> \"%s\" [label = \"%s (%s)\"]\n", + state_id, GNUNET_h2s (&edges[i].destination), + edges[i].label, proof); + fwrite (out_str, strlen (out_str), 1, ctx->graph_filep); + + GNUNET_free (out_str); + } + } + else + { + for (i = 0; i < num_edges; i++) + transition_counter++; + } + + for (i = 0; i < ctx->string_count; i++) + { + if (0 == strcmp (proof, ctx->strings[i])) + ctx->match_count++; + } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Iterating...\n"); - for (i = 0; i < num_edges; i++) + if (GNUNET_OK != GNUNET_REGEX_check_proof (proof, key)) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Edge %i: %s\n", i, edges[i].label); + ctx->error++; + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Proof check failed: proof: %s key: %s\n", proof, state_id); } - if (NULL != proof) - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Proof: %s\n", proof); + GNUNET_free (state_id); } int main (int argc, char *argv[]) { - GNUNET_log_setup ("test-regex", -#if VERBOSE - "DEBUG", -#else - "WARNING", -#endif - NULL); + GNUNET_log_setup ("test-regex", "WARNING", NULL); int error; - const char *regex; struct GNUNET_REGEX_Automaton *dfa; + unsigned int i; + unsigned int num_transitions; + char *filename = NULL; + struct IteratorContext ctx = { 0, 0, NULL, 0, NULL, 0 }; error = 0; - regex = "ab(c|d)+c*(a(b|c)d)+"; - dfa = GNUNET_REGEX_construct_dfa (regex, strlen (regex)); - GNUNET_REGEX_automaton_save_graph (dfa, "dfa.dot"); - GNUNET_REGEX_iterate_all_edges (dfa, key_iterator, NULL); - GNUNET_REGEX_automaton_destroy (dfa); + const struct RegexStringPair rxstr[13] = { + {INITIAL_PADDING "ab(c|d)+c*(a(b|c)+d)+(bla)+", 2, + {INITIAL_PADDING "abcdcdca", INITIAL_PADDING "abcabdbl"}}, + {INITIAL_PADDING + "abcdefghixxxxxxxxxxxxxjklmnop*qstoisdjfguisdfguihsdfgbdsuivggsd", 1, + {INITIAL_PADDING "abcdefgh"}}, + {INITIAL_PADDING "VPN-4-1(0|1)*", 2, + {INITIAL_PADDING "VPN-4-10", INITIAL_PADDING "VPN-4-11"}}, + {INITIAL_PADDING "(a+X*y+c|p|R|Z*K*y*R+w|Y*6+n+h*k*w+V*F|W*B*e*)", 2, + {INITIAL_PADDING "aaaaaaaa", INITIAL_PADDING "aaXXyyyc"}}, + {INITIAL_PADDING "a*", 1, {INITIAL_PADDING "aaaaaaaa"}}, + {INITIAL_PADDING "xzxzxzxzxz", 1, {INITIAL_PADDING "xzxzxzxz"}}, + {INITIAL_PADDING "xyz*", 1, {INITIAL_PADDING "xyzzzzzz"}}, + {INITIAL_PADDING + "abcd:(0|1)(0|1)(0|1)(0|1)(0|1)(0|1)(0|1)(0|1)(0|1)(0|1)(0|1)(0|1)(0|1)(0|1)(0|1)(0|1)(0|1)(0|1)(0|1)(0|1):(0|1)(0|1)(0|1)(0|1)(0|1)(0|1)(0|1)(0|1)(0|1)(0|1)(0|1)(0|1)(0|1)(0|1)(0|1)(0|1)(0|1)(0|1)(0|1)(0|1)(0|1)(0|1)(0|1)(0|1)(0|1)(0|1)(0|1)(0|1)(0|1)(0|1)(0|1)(0|1)(0|1)(0|1)(0|1)(0|1)(0|1)(0|1)(0|1)(0|1)(0|1)(0|1)(0|1)(0|1)", + 2, {INITIAL_PADDING "abcd:000", INITIAL_PADDING "abcd:101"}}, + {INITIAL_PADDING "(x*|(0|1|2)(a|b|c|d)+)", 2, + {INITIAL_PADDING "xxxxxxxx", INITIAL_PADDING "0abcdbad"}}, + {INITIAL_PADDING "(0|1)(0|1)23456789ABC", 1, {INITIAL_PADDING "11234567"}}, + {INITIAL_PADDING "0*123456789ABC*", 3, + {INITIAL_PADDING "00123456", INITIAL_PADDING "00000000", + INITIAL_PADDING "12345678"}}, + {INITIAL_PADDING "0123456789A*BC", 1, {INITIAL_PADDING "01234567"}}, + {"GNUNETVPN000100000IPEX6-fc5a:4e1:c2ba::1", 1, {"GNUNETVPN000100000IPEX6-"}} + }; + + const char *graph_start_str = "digraph G {\nrankdir=LR\n"; + const char *graph_end_str = "\n}\n"; + + for (i = 0; i < 13; i++) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Iterating DFA for regex %s\n", + rxstr[i].regex); + + + /* Create graph */ + if (GNUNET_YES == GNUNET_REGEX_ITERATE_SAVE_DEBUG_GRAPH) + { + GNUNET_asprintf (&filename, "iteration_graph_%u.dot", i); + ctx.graph_filep = fopen (filename, "w"); + if (NULL == ctx.graph_filep) + { + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + "Could not open file %s for saving iteration graph.\n", + filename); + ctx.should_save_graph = GNUNET_NO; + } + else + { + ctx.should_save_graph = GNUNET_YES; + fwrite (graph_start_str, strlen (graph_start_str), 1, ctx.graph_filep); + } + GNUNET_free (filename); + } + else + { + ctx.should_save_graph = GNUNET_NO; + ctx.graph_filep = NULL; + } + + /* Iterate over DFA edges */ + transition_counter = 0; + ctx.string_count = rxstr[i].string_count; + ctx.strings = rxstr[i].strings; + ctx.match_count = 0; + dfa = + GNUNET_REGEX_construct_dfa (rxstr[i].regex, strlen (rxstr[i].regex), 0); + GNUNET_REGEX_iterate_all_edges (dfa, key_iterator, &ctx); + num_transitions = + GNUNET_REGEX_get_transition_count (dfa) - dfa->start->transition_count; + + if (transition_counter < num_transitions) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Automaton has %d transitions, iterated over %d transitions\n", + num_transitions, transition_counter); + error += 1; + } + + if (ctx.match_count < ctx.string_count) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Missing initial states for regex %s\n", rxstr[i].regex); + error += (ctx.string_count - ctx.match_count); + } + else if (ctx.match_count > ctx.string_count) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Duplicate initial transitions for regex %s\n", + rxstr[i].regex); + error += (ctx.string_count - ctx.match_count); + } + + GNUNET_REGEX_automaton_destroy (dfa); + + /* Finish graph */ + if (GNUNET_YES == ctx.should_save_graph) + { + fwrite (graph_end_str, strlen (graph_end_str), 1, ctx.graph_filep); + fclose (ctx.graph_filep); + ctx.graph_filep = NULL; + ctx.should_save_graph = GNUNET_NO; + } + } + + + for (i = 0; i < 13; i++) + { + ctx.string_count = rxstr[i].string_count; + ctx.strings = rxstr[i].strings; + ctx.match_count = 0; + + dfa = + GNUNET_REGEX_construct_dfa (rxstr[i].regex, strlen (rxstr[i].regex), 0); + GNUNET_REGEX_dfa_add_multi_strides (NULL, dfa, 2); + GNUNET_REGEX_iterate_all_edges (dfa, key_iterator, &ctx); + + if (ctx.match_count < ctx.string_count) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Missing initial states for regex %s\n", rxstr[i].regex); + error += (ctx.string_count - ctx.match_count); + } + + GNUNET_REGEX_automaton_destroy (dfa); + } + + error += ctx.error; return error; } diff --git a/src/regex/test_regex_proofs.c b/src/regex/test_regex_proofs.c new file mode 100644 index 0000000..92a3a41 --- /dev/null +++ b/src/regex/test_regex_proofs.c @@ -0,0 +1,171 @@ +/* + This file is part of GNUnet + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ +/** + * @file regex/test_regex_proofs.c + * @brief test for regex.c + * @author Maximilian Szengel + */ +#include "platform.h" +#include "gnunet_regex_lib.h" +#include "regex_internal.h" + + +/** + * Test if the given regex's canonical regex is the same as this canonical + * regex's canonical regex. Confused? Ok, then: 1. construct a dfa A from the + * given 'regex' 2. get the canonical regex of dfa A 3. construct a dfa B from + * this canonical regex 3. compare the canonical regex of dfa A with the + * canonical regex of dfa B. + * + * @param regex regular expression used for this test (see above). + * + * @return 0 on success, 1 on failure + */ +static unsigned int +test_proof (const char *regex) +{ + unsigned int error; + struct GNUNET_REGEX_Automaton *dfa; + char *c_rx1; + const char *c_rx2; + + dfa = GNUNET_REGEX_construct_dfa (regex, strlen (regex), 1); + GNUNET_assert (NULL != dfa); + c_rx1 = GNUNET_strdup (GNUNET_REGEX_get_canonical_regex (dfa)); + GNUNET_REGEX_automaton_destroy (dfa); + dfa = GNUNET_REGEX_construct_dfa (c_rx1, strlen (c_rx1), 1); + GNUNET_assert (NULL != dfa); + c_rx2 = GNUNET_REGEX_get_canonical_regex (dfa); + + error = (0 == strcmp (c_rx1, c_rx2)) ? 0 : 1; + + if (error > 0) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Comparing canonical regex of\n%s\nfailed:\n%s\nvs.\n%s\n", + regex, c_rx1, c_rx2); + } + + GNUNET_free (c_rx1); + GNUNET_REGEX_automaton_destroy (dfa); + + return error; +} + + +/** + * Use 'test_proof' function to randomly test the canonical regexes of 'count' + * random expressions of length 'rx_length'. + * + * @param count number of random regular expressions to test. + * @param rx_length length of the random regular expressions. + * + * @return 0 on succes, number of failures otherwise. + */ +static unsigned int +test_proofs_random (unsigned int count, size_t rx_length) +{ + unsigned int i; + char *rand_rx; + unsigned int failures; + + failures = 0; + + for (i = 0; i < count; i++) + { + rand_rx = GNUNET_REGEX_generate_random_regex (rx_length, NULL); + failures += test_proof (rand_rx); + GNUNET_free (rand_rx); + } + + return failures; +} + + +/** + * Test a number of known examples of regexes for proper canonicalization. + * + * @return 0 on success, number of failures otherwise. + */ +static unsigned int +test_proofs_static () +{ + unsigned int i; + unsigned int error; + + const char *regex[8] = { + "a|aa*a", + "a+", + "a*", + "a*a*", + "(F*C|WfPf|y+F*C)", + "y*F*C|WfPf", + "((a|b)c|(a|b)(d|(a|b)e))", + "((a|b)(c|d)|(a|b)(a|b)e)" + }; + + const char *canon_rx1; + const char *canon_rx2; + struct GNUNET_REGEX_Automaton *dfa1; + struct GNUNET_REGEX_Automaton *dfa2; + + error = 0; + + for (i = 0; i < 8; i += 2) + { + dfa1 = GNUNET_REGEX_construct_dfa (regex[i], strlen (regex[i]), 1); + dfa2 = GNUNET_REGEX_construct_dfa (regex[i + 1], strlen (regex[i + 1]), 1); + GNUNET_assert (NULL != dfa1); + GNUNET_assert (NULL != dfa2); + + canon_rx1 = GNUNET_REGEX_get_canonical_regex (dfa1); + canon_rx2 = GNUNET_REGEX_get_canonical_regex (dfa2); + + error += (0 == strcmp (canon_rx1, canon_rx2)) ? 0 : 1; + + if (error > 0) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Comparing canonical regex failed:\nrx1:\t%s\ncrx1:\t%s\nrx2:\t%s\ncrx2:\t%s\n", + regex[i], canon_rx1, regex[i + 1], canon_rx2); + } + + GNUNET_REGEX_automaton_destroy (dfa1); + GNUNET_REGEX_automaton_destroy (dfa2); + } + + return error; +} + + +int +main (int argc, char *argv[]) +{ + GNUNET_log_setup ("test-regex", "WARNING", NULL); + + int error; + + error = 0; + + error += test_proofs_static (); + error += test_proofs_random (100, 30); + + return error; +} diff --git a/src/statistics/Makefile.am b/src/statistics/Makefile.am index ddf5fda..fe79212 100644 --- a/src/statistics/Makefile.am +++ b/src/statistics/Makefile.am @@ -11,6 +11,8 @@ endif pkgcfgdir= $(pkgdatadir)/config.d/ +libexecdir= $(pkglibdir)/libexec/ + pkgcfg_DATA = \ statistics.conf @@ -23,12 +25,13 @@ libgnunetstatistics_la_LIBADD = \ $(GN_LIBINTL) $(XLIB) libgnunetstatistics_la_LDFLAGS = \ $(GN_LIB_LDFLAGS) $(WINFLAGS) \ - -version-info 1:1:1 + -version-info 1:2:1 +libexec_PROGRAMS = \ + gnunet-service-statistics bin_PROGRAMS = \ - gnunet-statistics \ - gnunet-service-statistics + gnunet-statistics gnunet_statistics_SOURCES = \ gnunet-statistics.c @@ -83,10 +86,20 @@ test_statistics_api_watch_zero_value_LDADD = \ $(top_builddir)/src/util/libgnunetutil.la check_SCRIPTS = \ - test_gnunet_statistics.sh + test_gnunet_statistics.py + +do_subst = $(SED) -e 's,[@]PYTHON[@],$(PYTHON),g' + +%.py: %.py.in Makefile + $(do_subst) < $(srcdir)/$< > $@ + chmod +x $@ + +test_gnunet_statistics.py: test_gnunet_statistics.py.in Makefile + $(do_subst) < $(srcdir)/test_gnunet_statistics.py.in > test_gnunet_statistics.py + chmod +x test_gnunet_statistics.py EXTRA_DIST = \ test_statistics_api_data.conf \ - $(check_SCRIPTS) + test_gnunet_statistics.py.in diff --git a/src/statistics/Makefile.in b/src/statistics/Makefile.in index a81ae4a..e3ae1e9 100644 --- a/src/statistics/Makefile.in +++ b/src/statistics/Makefile.in @@ -1,9 +1,9 @@ -# Makefile.in generated by automake 1.11.1 from Makefile.am. +# Makefile.in generated by automake 1.11.6 from Makefile.am. # @configure_input@ # Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, -# 2003, 2004, 2005, 2006, 2007, 2008, 2009 Free Software Foundation, -# Inc. +# 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Free Software +# Foundation, Inc. # This Makefile.in is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. @@ -18,6 +18,23 @@ VPATH = @srcdir@ +am__make_dryrun = \ + { \ + am__dry=no; \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + echo 'am--echo: ; @echo "AM" OK' | $(MAKE) -f - 2>/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } pkgdatadir = $(datadir)/@PACKAGE@ pkgincludedir = $(includedir)/@PACKAGE@ pkglibdir = $(libdir)/@PACKAGE@ @@ -37,8 +54,8 @@ POST_UNINSTALL = : build_triplet = @build@ host_triplet = @host@ target_triplet = @target@ -bin_PROGRAMS = gnunet-statistics$(EXEEXT) \ - gnunet-service-statistics$(EXEEXT) +libexec_PROGRAMS = gnunet-service-statistics$(EXEEXT) +bin_PROGRAMS = gnunet-statistics$(EXEEXT) check_PROGRAMS = test_statistics_api$(EXEEXT) \ test_statistics_api_loop$(EXEEXT) \ test_statistics_api_watch$(EXEEXT) \ @@ -49,14 +66,15 @@ DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in \ ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 am__aclocal_m4_deps = $(top_srcdir)/m4/absolute-header.m4 \ $(top_srcdir)/m4/align.m4 $(top_srcdir)/m4/argz.m4 \ - $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/iconv.m4 \ - $(top_srcdir)/m4/lib-ld.m4 $(top_srcdir)/m4/lib-link.m4 \ - $(top_srcdir)/m4/lib-prefix.m4 $(top_srcdir)/m4/libcurl.m4 \ - $(top_srcdir)/m4/libgcrypt.m4 $(top_srcdir)/m4/libtool.m4 \ - $(top_srcdir)/m4/libunistring.m4 $(top_srcdir)/m4/ltdl.m4 \ - $(top_srcdir)/m4/ltoptions.m4 $(top_srcdir)/m4/ltsugar.m4 \ - $(top_srcdir)/m4/ltversion.m4 $(top_srcdir)/m4/lt~obsolete.m4 \ - $(top_srcdir)/m4/nls.m4 $(top_srcdir)/m4/po.m4 \ + $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/glib-2.0.m4 \ + $(top_srcdir)/m4/iconv.m4 $(top_srcdir)/m4/lib-ld.m4 \ + $(top_srcdir)/m4/lib-link.m4 $(top_srcdir)/m4/lib-prefix.m4 \ + $(top_srcdir)/m4/libcurl.m4 $(top_srcdir)/m4/libgcrypt.m4 \ + $(top_srcdir)/m4/libtool.m4 $(top_srcdir)/m4/libunistring.m4 \ + $(top_srcdir)/m4/ltdl.m4 $(top_srcdir)/m4/ltoptions.m4 \ + $(top_srcdir)/m4/ltsugar.m4 $(top_srcdir)/m4/ltversion.m4 \ + $(top_srcdir)/m4/lt~obsolete.m4 $(top_srcdir)/m4/nls.m4 \ + $(top_srcdir)/m4/pkg.m4 $(top_srcdir)/m4/po.m4 \ $(top_srcdir)/m4/progtest.m4 $(top_srcdir)/acinclude.m4 \ $(top_srcdir)/configure.ac am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ @@ -86,8 +104,14 @@ am__nobase_list = $(am__nobase_strip_setup); \ am__base_list = \ sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \ sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g' +am__uninstall_files_from_dir = { \ + test -z "$$files" \ + || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \ + || { echo " ( cd '$$dir' && rm -f" $$files ")"; \ + $(am__cd) "$$dir" && rm -f $$files; }; \ + } am__installdirs = "$(DESTDIR)$(libdir)" "$(DESTDIR)$(bindir)" \ - "$(DESTDIR)$(pkgcfgdir)" + "$(DESTDIR)$(libexecdir)" "$(DESTDIR)$(pkgcfgdir)" LTLIBRARIES = $(lib_LTLIBRARIES) am__DEPENDENCIES_1 = libgnunetstatistics_la_DEPENDENCIES = \ @@ -95,14 +119,14 @@ libgnunetstatistics_la_DEPENDENCIES = \ $(am__DEPENDENCIES_1) $(am__DEPENDENCIES_1) am_libgnunetstatistics_la_OBJECTS = statistics_api.lo libgnunetstatistics_la_OBJECTS = $(am_libgnunetstatistics_la_OBJECTS) -AM_V_lt = $(am__v_lt_$(V)) -am__v_lt_ = $(am__v_lt_$(AM_DEFAULT_VERBOSITY)) +AM_V_lt = $(am__v_lt_@AM_V@) +am__v_lt_ = $(am__v_lt_@AM_DEFAULT_V@) am__v_lt_0 = --silent libgnunetstatistics_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ $(AM_CFLAGS) $(CFLAGS) $(libgnunetstatistics_la_LDFLAGS) \ $(LDFLAGS) -o $@ -PROGRAMS = $(bin_PROGRAMS) +PROGRAMS = $(bin_PROGRAMS) $(libexec_PROGRAMS) am_gnunet_service_statistics_OBJECTS = \ gnunet-service-statistics.$(OBJEXT) gnunet_service_statistics_OBJECTS = \ @@ -145,21 +169,21 @@ LTCOMPILE = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) \ $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) \ $(AM_CFLAGS) $(CFLAGS) -AM_V_CC = $(am__v_CC_$(V)) -am__v_CC_ = $(am__v_CC_$(AM_DEFAULT_VERBOSITY)) +AM_V_CC = $(am__v_CC_@AM_V@) +am__v_CC_ = $(am__v_CC_@AM_DEFAULT_V@) am__v_CC_0 = @echo " CC " $@; -AM_V_at = $(am__v_at_$(V)) -am__v_at_ = $(am__v_at_$(AM_DEFAULT_VERBOSITY)) +AM_V_at = $(am__v_at_@AM_V@) +am__v_at_ = $(am__v_at_@AM_DEFAULT_V@) am__v_at_0 = @ CCLD = $(CC) LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ $(AM_LDFLAGS) $(LDFLAGS) -o $@ -AM_V_CCLD = $(am__v_CCLD_$(V)) -am__v_CCLD_ = $(am__v_CCLD_$(AM_DEFAULT_VERBOSITY)) +AM_V_CCLD = $(am__v_CCLD_@AM_V@) +am__v_CCLD_ = $(am__v_CCLD_@AM_DEFAULT_V@) am__v_CCLD_0 = @echo " CCLD " $@; -AM_V_GEN = $(am__v_GEN_$(V)) -am__v_GEN_ = $(am__v_GEN_$(AM_DEFAULT_VERBOSITY)) +AM_V_GEN = $(am__v_GEN_@AM_V@) +am__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@) am__v_GEN_0 = @echo " GEN " $@; SOURCES = $(libgnunetstatistics_la_SOURCES) \ $(gnunet_service_statistics_SOURCES) \ @@ -173,6 +197,11 @@ DIST_SOURCES = $(libgnunetstatistics_la_SOURCES) \ $(test_statistics_api_loop_SOURCES) \ $(test_statistics_api_watch_SOURCES) \ $(test_statistics_api_watch_zero_value_SOURCES) +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac DATA = $(pkgcfg_DATA) ETAGS = etags CTAGS = ctags @@ -214,6 +243,10 @@ EXEEXT = @EXEEXT@ EXT_LIBS = @EXT_LIBS@ EXT_LIB_PATH = @EXT_LIB_PATH@ FGREP = @FGREP@ +GLIB_CFLAGS = @GLIB_CFLAGS@ +GLIB_GENMARSHAL = @GLIB_GENMARSHAL@ +GLIB_LIBS = @GLIB_LIBS@ +GLIB_MKENUMS = @GLIB_MKENUMS@ GMSGFMT = @GMSGFMT@ GMSGFMT_015 = @GMSGFMT_015@ GNUNETDNS_GROUP = @GNUNETDNS_GROUP@ @@ -224,6 +257,7 @@ GN_LIBINTL = @GN_LIBINTL@ GN_LIB_LDFLAGS = @GN_LIB_LDFLAGS@ GN_PLUGIN_LDFLAGS = @GN_PLUGIN_LDFLAGS@ GN_USER_HOME_DIR = @GN_USER_HOME_DIR@ +GOBJECT_QUERY = @GOBJECT_QUERY@ GREP = @GREP@ HAVE_LIBUNISTRING = @HAVE_LIBUNISTRING@ INCLTDL = @INCLTDL@ @@ -246,6 +280,8 @@ LIBCURL_CPPFLAGS = @LIBCURL_CPPFLAGS@ LIBGCRYPT_CFLAGS = @LIBGCRYPT_CFLAGS@ LIBGCRYPT_CONFIG = @LIBGCRYPT_CONFIG@ LIBGCRYPT_LIBS = @LIBGCRYPT_LIBS@ +LIBGTOP_CFLAGS = @LIBGTOP_CFLAGS@ +LIBGTOP_LIBS = @LIBGTOP_LIBS@ LIBICONV = @LIBICONV@ LIBINTL = @LIBINTL@ LIBLTDL = @LIBLTDL@ @@ -267,6 +303,7 @@ LT_CONFIG_H = @LT_CONFIG_H@ LT_DLLOADERS = @LT_DLLOADERS@ LT_DLPREOPEN = @LT_DLPREOPEN@ MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ MKDIR_P = @MKDIR_P@ MONKEYPREFIX = @MONKEYPREFIX@ MSGFMT = @MSGFMT@ @@ -276,6 +313,7 @@ MYSQL_CPPFLAGS = @MYSQL_CPPFLAGS@ MYSQL_LDFLAGS = @MYSQL_LDFLAGS@ NM = @NM@ NMEDIT = @NMEDIT@ +NSS_DIR = @NSS_DIR@ OBJC = @OBJC@ OBJCDEPMODE = @OBJCDEPMODE@ OBJCFLAGS = @OBJCFLAGS@ @@ -291,6 +329,7 @@ PACKAGE_TARNAME = @PACKAGE_TARNAME@ PACKAGE_URL = @PACKAGE_URL@ PACKAGE_VERSION = @PACKAGE_VERSION@ PATH_SEPARATOR = @PATH_SEPARATOR@ +PKG_CONFIG = @PKG_CONFIG@ POSTGRES_CPPFLAGS = @POSTGRES_CPPFLAGS@ POSTGRES_LDFLAGS = @POSTGRES_LDFLAGS@ POSUB = @POSUB@ @@ -322,6 +361,7 @@ abs_builddir = @abs_builddir@ abs_srcdir = @abs_srcdir@ abs_top_builddir = @abs_top_builddir@ abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ ac_ct_CC = @ac_ct_CC@ ac_ct_CXX = @ac_ct_CXX@ ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ @@ -344,6 +384,7 @@ datarootdir = @datarootdir@ docdir = @docdir@ dvidir = @dvidir@ exec_prefix = @exec_prefix@ +gitcommand = @gitcommand@ host = @host@ host_alias = @host_alias@ host_cpu = @host_cpu@ @@ -354,10 +395,9 @@ includedir = @includedir@ infodir = @infodir@ install_sh = @install_sh@ libdir = @libdir@ -libexecdir = @libexecdir@ +libexecdir = $(pkglibdir)/libexec/ localedir = @localedir@ localstatedir = @localstatedir@ -lt_ECHO = @lt_ECHO@ ltdl_LIBOBJS = @ltdl_LIBOBJS@ ltdl_LTLIBOBJS = @ltdl_LTLIBOBJS@ mandir = @mandir@ @@ -375,6 +415,7 @@ sbindir = @sbindir@ sharedstatedir = @sharedstatedir@ srcdir = @srcdir@ subdirs = @subdirs@ +svnversioncommand = @svnversioncommand@ sys_symbol_underscore = @sys_symbol_underscore@ sysconfdir = @sysconfdir@ target = @target@ @@ -403,7 +444,7 @@ libgnunetstatistics_la_LIBADD = \ libgnunetstatistics_la_LDFLAGS = \ $(GN_LIB_LDFLAGS) $(WINFLAGS) \ - -version-info 1:1:1 + -version-info 1:2:1 gnunet_statistics_SOURCES = \ gnunet-statistics.c @@ -457,11 +498,12 @@ test_statistics_api_watch_zero_value_LDADD = \ $(top_builddir)/src/util/libgnunetutil.la check_SCRIPTS = \ - test_gnunet_statistics.sh + test_gnunet_statistics.py +do_subst = $(SED) -e 's,[@]PYTHON[@],$(PYTHON),g' EXTRA_DIST = \ test_statistics_api_data.conf \ - $(check_SCRIPTS) + test_gnunet_statistics.py.in all: all-am @@ -501,7 +543,6 @@ statistics.conf: $(top_builddir)/config.status $(srcdir)/statistics.conf.in cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ install-libLTLIBRARIES: $(lib_LTLIBRARIES) @$(NORMAL_INSTALL) - test -z "$(libdir)" || $(MKDIR_P) "$(DESTDIR)$(libdir)" @list='$(lib_LTLIBRARIES)'; test -n "$(libdir)" || list=; \ list2=; for p in $$list; do \ if test -f $$p; then \ @@ -509,6 +550,8 @@ install-libLTLIBRARIES: $(lib_LTLIBRARIES) else :; fi; \ done; \ test -z "$$list2" || { \ + echo " $(MKDIR_P) '$(DESTDIR)$(libdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libdir)" || exit 1; \ echo " $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 '$(DESTDIR)$(libdir)'"; \ $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 "$(DESTDIR)$(libdir)"; \ } @@ -530,12 +573,15 @@ clean-libLTLIBRARIES: echo "rm -f \"$${dir}/so_locations\""; \ rm -f "$${dir}/so_locations"; \ done -libgnunetstatistics.la: $(libgnunetstatistics_la_OBJECTS) $(libgnunetstatistics_la_DEPENDENCIES) +libgnunetstatistics.la: $(libgnunetstatistics_la_OBJECTS) $(libgnunetstatistics_la_DEPENDENCIES) $(EXTRA_libgnunetstatistics_la_DEPENDENCIES) $(AM_V_CCLD)$(libgnunetstatistics_la_LINK) -rpath $(libdir) $(libgnunetstatistics_la_OBJECTS) $(libgnunetstatistics_la_LIBADD) $(LIBS) install-binPROGRAMS: $(bin_PROGRAMS) @$(NORMAL_INSTALL) - test -z "$(bindir)" || $(MKDIR_P) "$(DESTDIR)$(bindir)" @list='$(bin_PROGRAMS)'; test -n "$(bindir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(bindir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(bindir)" || exit 1; \ + fi; \ for p in $$list; do echo "$$p $$p"; done | \ sed 's/$(EXEEXT)$$//' | \ while read p p1; do if test -f $$p || test -f $$p1; \ @@ -584,22 +630,68 @@ clean-checkPROGRAMS: list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ echo " rm -f" $$list; \ rm -f $$list -gnunet-service-statistics$(EXEEXT): $(gnunet_service_statistics_OBJECTS) $(gnunet_service_statistics_DEPENDENCIES) +install-libexecPROGRAMS: $(libexec_PROGRAMS) + @$(NORMAL_INSTALL) + @list='$(libexec_PROGRAMS)'; test -n "$(libexecdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(libexecdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libexecdir)" || exit 1; \ + fi; \ + for p in $$list; do echo "$$p $$p"; done | \ + sed 's/$(EXEEXT)$$//' | \ + while read p p1; do if test -f $$p || test -f $$p1; \ + then echo "$$p"; echo "$$p"; else :; fi; \ + done | \ + sed -e 'p;s,.*/,,;n;h' -e 's|.*|.|' \ + -e 'p;x;s,.*/,,;s/$(EXEEXT)$$//;$(transform);s/$$/$(EXEEXT)/' | \ + sed 'N;N;N;s,\n, ,g' | \ + $(AWK) 'BEGIN { files["."] = ""; dirs["."] = 1 } \ + { d=$$3; if (dirs[d] != 1) { print "d", d; dirs[d] = 1 } \ + if ($$2 == $$4) files[d] = files[d] " " $$1; \ + else { print "f", $$3 "/" $$4, $$1; } } \ + END { for (d in files) print "f", d, files[d] }' | \ + while read type dir files; do \ + if test "$$dir" = .; then dir=; else dir=/$$dir; fi; \ + test -z "$$files" || { \ + echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files '$(DESTDIR)$(libexecdir)$$dir'"; \ + $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files "$(DESTDIR)$(libexecdir)$$dir" || exit $$?; \ + } \ + ; done + +uninstall-libexecPROGRAMS: + @$(NORMAL_UNINSTALL) + @list='$(libexec_PROGRAMS)'; test -n "$(libexecdir)" || list=; \ + files=`for p in $$list; do echo "$$p"; done | \ + sed -e 'h;s,^.*/,,;s/$(EXEEXT)$$//;$(transform)' \ + -e 's/$$/$(EXEEXT)/' `; \ + test -n "$$list" || exit 0; \ + echo " ( cd '$(DESTDIR)$(libexecdir)' && rm -f" $$files ")"; \ + cd "$(DESTDIR)$(libexecdir)" && rm -f $$files + +clean-libexecPROGRAMS: + @list='$(libexec_PROGRAMS)'; test -n "$$list" || exit 0; \ + echo " rm -f" $$list; \ + rm -f $$list || exit $$?; \ + test -n "$(EXEEXT)" || exit 0; \ + list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ + echo " rm -f" $$list; \ + rm -f $$list +gnunet-service-statistics$(EXEEXT): $(gnunet_service_statistics_OBJECTS) $(gnunet_service_statistics_DEPENDENCIES) $(EXTRA_gnunet_service_statistics_DEPENDENCIES) @rm -f gnunet-service-statistics$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_service_statistics_OBJECTS) $(gnunet_service_statistics_LDADD) $(LIBS) -gnunet-statistics$(EXEEXT): $(gnunet_statistics_OBJECTS) $(gnunet_statistics_DEPENDENCIES) +gnunet-statistics$(EXEEXT): $(gnunet_statistics_OBJECTS) $(gnunet_statistics_DEPENDENCIES) $(EXTRA_gnunet_statistics_DEPENDENCIES) @rm -f gnunet-statistics$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_statistics_OBJECTS) $(gnunet_statistics_LDADD) $(LIBS) -test_statistics_api$(EXEEXT): $(test_statistics_api_OBJECTS) $(test_statistics_api_DEPENDENCIES) +test_statistics_api$(EXEEXT): $(test_statistics_api_OBJECTS) $(test_statistics_api_DEPENDENCIES) $(EXTRA_test_statistics_api_DEPENDENCIES) @rm -f test_statistics_api$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_statistics_api_OBJECTS) $(test_statistics_api_LDADD) $(LIBS) -test_statistics_api_loop$(EXEEXT): $(test_statistics_api_loop_OBJECTS) $(test_statistics_api_loop_DEPENDENCIES) +test_statistics_api_loop$(EXEEXT): $(test_statistics_api_loop_OBJECTS) $(test_statistics_api_loop_DEPENDENCIES) $(EXTRA_test_statistics_api_loop_DEPENDENCIES) @rm -f test_statistics_api_loop$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_statistics_api_loop_OBJECTS) $(test_statistics_api_loop_LDADD) $(LIBS) -test_statistics_api_watch$(EXEEXT): $(test_statistics_api_watch_OBJECTS) $(test_statistics_api_watch_DEPENDENCIES) +test_statistics_api_watch$(EXEEXT): $(test_statistics_api_watch_OBJECTS) $(test_statistics_api_watch_DEPENDENCIES) $(EXTRA_test_statistics_api_watch_DEPENDENCIES) @rm -f test_statistics_api_watch$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_statistics_api_watch_OBJECTS) $(test_statistics_api_watch_LDADD) $(LIBS) -test_statistics_api_watch_zero_value$(EXEEXT): $(test_statistics_api_watch_zero_value_OBJECTS) $(test_statistics_api_watch_zero_value_DEPENDENCIES) +test_statistics_api_watch_zero_value$(EXEEXT): $(test_statistics_api_watch_zero_value_OBJECTS) $(test_statistics_api_watch_zero_value_DEPENDENCIES) $(EXTRA_test_statistics_api_watch_zero_value_DEPENDENCIES) @rm -f test_statistics_api_watch_zero_value$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_statistics_api_watch_zero_value_OBJECTS) $(test_statistics_api_watch_zero_value_LDADD) $(LIBS) @@ -620,26 +712,23 @@ distclean-compile: .c.o: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c $< .c.obj: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'` @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c `$(CYGPATH_W) '$<'` +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c `$(CYGPATH_W) '$<'` .c.lo: @am__fastdepCC_TRUE@ $(AM_V_CC)$(LTCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LTCOMPILE) -c -o $@ $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LTCOMPILE) -c -o $@ $< mostlyclean-libtool: -rm -f *.lo @@ -648,8 +737,11 @@ clean-libtool: -rm -rf .libs _libs install-pkgcfgDATA: $(pkgcfg_DATA) @$(NORMAL_INSTALL) - test -z "$(pkgcfgdir)" || $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" @list='$(pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(pkgcfgdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" || exit 1; \ + fi; \ for p in $$list; do \ if test -f "$$p"; then d=; else d="$(srcdir)/"; fi; \ echo "$$d$$p"; \ @@ -663,9 +755,7 @@ uninstall-pkgcfgDATA: @$(NORMAL_UNINSTALL) @list='$(pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ files=`for p in $$list; do echo $$p; done | sed -e 's|^.*/||'`; \ - test -n "$$files" || exit 0; \ - echo " ( cd '$(DESTDIR)$(pkgcfgdir)' && rm -f" $$files ")"; \ - cd "$(DESTDIR)$(pkgcfgdir)" && rm -f $$files + dir='$(DESTDIR)$(pkgcfgdir)'; $(am__uninstall_files_from_dir) ID: $(HEADERS) $(SOURCES) $(LISP) $(TAGS_FILES) list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ @@ -800,14 +890,15 @@ check-TESTS: $(TESTS) fi; \ dashes=`echo "$$dashes" | sed s/./=/g`; \ if test "$$failed" -eq 0; then \ - echo "$$grn$$dashes"; \ + col="$$grn"; \ else \ - echo "$$red$$dashes"; \ + col="$$red"; \ fi; \ - echo "$$banner"; \ - test -z "$$skipped" || echo "$$skipped"; \ - test -z "$$report" || echo "$$report"; \ - echo "$$dashes$$std"; \ + echo "$${col}$$dashes$${std}"; \ + echo "$${col}$$banner$${std}"; \ + test -z "$$skipped" || echo "$${col}$$skipped$${std}"; \ + test -z "$$report" || echo "$${col}$$report$${std}"; \ + echo "$${col}$$dashes$${std}"; \ test "$$failed" -eq 0; \ else :; fi @@ -849,7 +940,7 @@ all-am: Makefile $(LTLIBRARIES) $(PROGRAMS) $(DATA) install-binPROGRAMS: install-libLTLIBRARIES installdirs: - for dir in "$(DESTDIR)$(libdir)" "$(DESTDIR)$(bindir)" "$(DESTDIR)$(pkgcfgdir)"; do \ + for dir in "$(DESTDIR)$(libdir)" "$(DESTDIR)$(bindir)" "$(DESTDIR)$(libexecdir)" "$(DESTDIR)$(pkgcfgdir)"; do \ test -z "$$dir" || $(MKDIR_P) "$$dir"; \ done install: install-am @@ -862,10 +953,15 @@ install-am: all-am installcheck: installcheck-am install-strip: - $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ - install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ - `test -z '$(STRIP)' || \ - echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi mostlyclean-generic: clean-generic: @@ -880,7 +976,8 @@ maintainer-clean-generic: clean: clean-am clean-am: clean-binPROGRAMS clean-checkPROGRAMS clean-generic \ - clean-libLTLIBRARIES clean-libtool mostlyclean-am + clean-libLTLIBRARIES clean-libexecPROGRAMS clean-libtool \ + mostlyclean-am distclean: distclean-am -rm -rf ./$(DEPDIR) @@ -906,7 +1003,8 @@ install-dvi: install-dvi-am install-dvi-am: -install-exec-am: install-binPROGRAMS install-libLTLIBRARIES +install-exec-am: install-binPROGRAMS install-libLTLIBRARIES \ + install-libexecPROGRAMS install-html: install-html-am @@ -947,28 +1045,37 @@ ps: ps-am ps-am: uninstall-am: uninstall-binPROGRAMS uninstall-libLTLIBRARIES \ - uninstall-pkgcfgDATA + uninstall-libexecPROGRAMS uninstall-pkgcfgDATA .MAKE: check-am install-am install-strip .PHONY: CTAGS GTAGS all all-am check check-TESTS check-am clean \ clean-binPROGRAMS clean-checkPROGRAMS clean-generic \ - clean-libLTLIBRARIES clean-libtool ctags distclean \ - distclean-compile distclean-generic distclean-libtool \ - distclean-tags distdir dvi dvi-am html html-am info info-am \ - install install-am install-binPROGRAMS install-data \ - install-data-am install-dvi install-dvi-am install-exec \ - install-exec-am install-html install-html-am install-info \ - install-info-am install-libLTLIBRARIES install-man install-pdf \ - install-pdf-am install-pkgcfgDATA install-ps install-ps-am \ - install-strip installcheck installcheck-am installdirs \ - maintainer-clean maintainer-clean-generic mostlyclean \ - mostlyclean-compile mostlyclean-generic mostlyclean-libtool \ - pdf pdf-am ps ps-am tags uninstall uninstall-am \ - uninstall-binPROGRAMS uninstall-libLTLIBRARIES \ + clean-libLTLIBRARIES clean-libexecPROGRAMS clean-libtool ctags \ + distclean distclean-compile distclean-generic \ + distclean-libtool distclean-tags distdir dvi dvi-am html \ + html-am info info-am install install-am install-binPROGRAMS \ + install-data install-data-am install-dvi install-dvi-am \ + install-exec install-exec-am install-html install-html-am \ + install-info install-info-am install-libLTLIBRARIES \ + install-libexecPROGRAMS install-man install-pdf install-pdf-am \ + install-pkgcfgDATA install-ps install-ps-am install-strip \ + installcheck installcheck-am installdirs maintainer-clean \ + maintainer-clean-generic mostlyclean mostlyclean-compile \ + mostlyclean-generic mostlyclean-libtool pdf pdf-am ps ps-am \ + tags uninstall uninstall-am uninstall-binPROGRAMS \ + uninstall-libLTLIBRARIES uninstall-libexecPROGRAMS \ uninstall-pkgcfgDATA +%.py: %.py.in Makefile + $(do_subst) < $(srcdir)/$< > $@ + chmod +x $@ + +test_gnunet_statistics.py: test_gnunet_statistics.py.in Makefile + $(do_subst) < $(srcdir)/test_gnunet_statistics.py.in > test_gnunet_statistics.py + chmod +x test_gnunet_statistics.py + # Tell versions [3.59,3.63) of GNU make to not export all variables. # Otherwise a system limit (for SysV at least) may be exceeded. .NOEXPORT: diff --git a/src/statistics/gnunet-service-statistics.c b/src/statistics/gnunet-service-statistics.c index efd8346..beb3d51 100644 --- a/src/statistics/gnunet-service-statistics.c +++ b/src/statistics/gnunet-service-statistics.c @@ -849,4 +849,19 @@ main (int argc, char *const *argv) GNUNET_SERVICE_OPTION_SOFT_SHUTDOWN, &run, NULL)) ? 0 : 1; } +#ifdef LINUX +#include + +/** + * MINIMIZE heap size (way below 128k) since this process doesn't need much. + */ +void __attribute__ ((constructor)) GNUNET_ARM_memory_init () +{ + mallopt (M_TRIM_THRESHOLD, 4 * 1024); + mallopt (M_TOP_PAD, 1 * 1024); + malloc_trim (0); +} +#endif + + /* end of gnunet-service-statistics.c */ diff --git a/src/statistics/gnunet-statistics.c b/src/statistics/gnunet-statistics.c index 3eef887..2747f7a 100644 --- a/src/statistics/gnunet-statistics.c +++ b/src/statistics/gnunet-statistics.c @@ -63,6 +63,25 @@ static int watch; */ static int quiet; +/** + * Remote host + */ +static char *remote_host; + +/** + * Remote host's port + */ +static unsigned long long remote_port; + +/** + * Value to set + */ +static unsigned long long set_val; + +/** + * Set operation + */ +static int set_value; /** * Callback function to process statistic values. @@ -79,7 +98,8 @@ printer (void *cls, const char *subsystem, const char *name, uint64_t value, int is_persistent) { struct GNUNET_TIME_Absolute now = GNUNET_TIME_absolute_get(); - char * now_str; + const char * now_str; + if (quiet == GNUNET_NO) { if (GNUNET_YES == watch) @@ -89,7 +109,6 @@ printer (void *cls, const char *subsystem, const char *name, uint64_t value, now_str, is_persistent ? "!" : " ", subsystem, _(name), (unsigned long long) value); - GNUNET_free (now_str); } else { @@ -115,56 +134,86 @@ printer (void *cls, const char *subsystem, const char *name, uint64_t value, static void cleanup (void *cls, int success) { - struct GNUNET_STATISTICS_Handle *h = cls; if (success != GNUNET_OK) { - FPRINTF (stderr, "%s", _("Failed to obtain statistics.\n")); + if (NULL == remote_host) + FPRINTF (stderr, "%s", _("Failed to obtain statistics.\n")); + else + FPRINTF (stderr, _("Failed to obtain statistics from host `%s:%llu'\n"), + remote_host, remote_port); ret = 1; } - if (NULL != h) - { - GNUNET_STATISTICS_destroy (h, GNUNET_NO); - h = NULL; - } + GNUNET_SCHEDULER_shutdown (); } +/** + * Function run on shutdown to clean up. + * + * @param cls the statistics handle + * @param tc scheduler context + */ static void shutdown_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { struct GNUNET_STATISTICS_Handle *h = cls; + if (NULL == h) + return; GNUNET_STATISTICS_watch_cancel (h, subsystem, name, &printer, h); - if (NULL != h) - { - GNUNET_STATISTICS_destroy (h, GNUNET_NO); - h = NULL; - } + GNUNET_STATISTICS_destroy (h, GNUNET_NO); + h = NULL; } -/** - * Main function that will be run by the scheduler. - * - * @param cls closure - * @param args remaining command-line arguments - * @param cfgfile name of the configuration file used (for saving, can be NULL!) - * @param cfg configuration - */ + static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) +resolver_test_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { + struct GNUNET_CONFIGURATION_Handle *cfg = cls; struct GNUNET_STATISTICS_Handle *h; - unsigned long long val; - if (args[0] != NULL) + if (NULL != remote_host) { - if ((1 != SSCANF (args[0], "%llu", &val)) || (subsystem == NULL) || - (name == NULL)) + if (0 != (tc->reason & GNUNET_SCHEDULER_REASON_TIMEOUT)) + { + FPRINTF (stderr, _("Trying to connect to remote host, but service `%s' is not running\n"), "resolver"); + return; + } + + /* connect to a remote host */ + if (0 == remote_port) + { + if (GNUNET_SYSERR == GNUNET_CONFIGURATION_get_value_number (cfg, "statistics", "PORT", &remote_port)) + { + FPRINTF (stderr, _("A port is required to connect to host `%s'\n"), remote_host); + return; + } + } + else if (65535 <= remote_port) + { + FPRINTF (stderr, _("A port has to be between 1 and 65535 to connect to host `%s'\n"), remote_host); + return; + } + + /* Manipulate configuration */ + GNUNET_CONFIGURATION_set_value_string ((struct GNUNET_CONFIGURATION_Handle *) cfg, "statistics", "UNIXPATH", ""); + GNUNET_CONFIGURATION_set_value_string ((struct GNUNET_CONFIGURATION_Handle *) cfg, "statistics", "HOSTNAME", remote_host); + GNUNET_CONFIGURATION_set_value_number ((struct GNUNET_CONFIGURATION_Handle *) cfg, "statistics", "PORT", remote_port); + } + + if (set_value) + { + if (subsystem == NULL) { - FPRINTF (stderr, _("Invalid argument `%s'\n"), args[0]); + FPRINTF (stderr, "%s", _("Missing argument: subsystem \n")); + ret = 1; + return; + } + if (name == NULL) + { + FPRINTF (stderr, "%s", _("Missing argument: name\n")); ret = 1; return; } @@ -174,13 +223,12 @@ run (void *cls, char *const *args, const char *cfgfile, ret = 1; return; } - GNUNET_STATISTICS_set (h, name, (uint64_t) val, persistent); + GNUNET_STATISTICS_set (h, name, (uint64_t) set_val, persistent); GNUNET_STATISTICS_destroy (h, GNUNET_YES); h = NULL; return; } - h = GNUNET_STATISTICS_create ("gnunet-statistics", cfg); - if (NULL == h) + if (NULL == (h = GNUNET_STATISTICS_create ("gnunet-statistics", cfg))) { ret = 1; return; @@ -197,8 +245,8 @@ run (void *cls, char *const *args, const char *cfgfile, if ((NULL == subsystem) || (NULL == name)) { printf (_("No subsystem or name given\n")); - if (h != NULL) - GNUNET_STATISTICS_destroy (h, GNUNET_NO); + GNUNET_STATISTICS_destroy (h, GNUNET_NO); + h = NULL; ret = 1; return; } @@ -208,10 +256,45 @@ run (void *cls, char *const *args, const char *cfgfile, GNUNET_SCHEDULER_add_now (&shutdown_task, h); return; } - GNUNET_SCHEDULER_add_delayed(GNUNET_TIME_UNIT_FOREVER_REL, &shutdown_task, h); } + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, + &shutdown_task, h); + +} + + +/** + * Main function that will be run by the scheduler. + * + * @param cls closure + * @param args remaining command-line arguments + * @param cfgfile name of the configuration file used (for saving, can be NULL!) + * @param cfg configuration + */ +static void +run (void *cls, char *const *args, const char *cfgfile, + const struct GNUNET_CONFIGURATION_Handle *cfg) +{ + set_value = GNUNET_NO; + if (NULL != args[0]) + { + if (1 != SSCANF (args[0], "%llu", &set_val)) + { + FPRINTF (stderr, _("Invalid argument `%s'\n"), args[0]); + ret = 1; + return; + } + set_value = GNUNET_YES; + } + + if (NULL != remote_host) + GNUNET_CLIENT_service_test ("resolver", cfg, GNUNET_TIME_UNIT_SECONDS, &resolver_test_task, (void *) cfg); + else + GNUNET_SCHEDULER_add_now (&resolver_test_task, (void *) cfg); + } + /** * The main function to obtain statistics in GNUnet. * @@ -236,15 +319,29 @@ main (int argc, char *const *argv) gettext_noop ("just print the statistics value"), 0, &GNUNET_GETOPT_set_one, &quiet}, {'w', "watch", NULL, - gettext_noop ("watch value continously"), 0, + gettext_noop ("watch value continuously"), 0, &GNUNET_GETOPT_set_one, &watch}, + {'r', "remote", NULL, + gettext_noop ("connect to remote host"), 1, + &GNUNET_GETOPT_set_string, &remote_host}, + {'o', "port", NULL, + gettext_noop ("port for remote host"), 1, + &GNUNET_GETOPT_set_uint, &remote_port}, GNUNET_GETOPT_OPTION_END }; - return (GNUNET_OK == - GNUNET_PROGRAM_run (argc, argv, "gnunet-statistics [options [value]]", - gettext_noop - ("Print statistics about GNUnet operations."), - options, &run, NULL)) ? ret : 1; + remote_port = 0; + remote_host = NULL; + if (GNUNET_OK != GNUNET_STRINGS_get_utf8_args (argc, argv, &argc, &argv)) + return 2; + + ret = (GNUNET_OK == + GNUNET_PROGRAM_run (argc, argv, "gnunet-statistics [options [value]]", + gettext_noop + ("Print statistics about GNUnet operations."), + options, &run, NULL)) ? ret : 1; + GNUNET_free_non_null (remote_host); + GNUNET_free ((void*) argv); + return ret; } /* end of gnunet-statistics.c */ diff --git a/src/statistics/statistics.conf.in b/src/statistics/statistics.conf.in index 5de9ded..669e89b 100644 --- a/src/statistics/statistics.conf.in +++ b/src/statistics/statistics.conf.in @@ -3,7 +3,6 @@ AUTOSTART = YES @JAVAPORT@PORT = 2088 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-statistics ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; diff --git a/src/statistics/statistics_api.c b/src/statistics/statistics_api.c index e1b3698..7bdd6a5 100644 --- a/src/statistics/statistics_api.c +++ b/src/statistics/statistics_api.c @@ -235,6 +235,16 @@ struct GNUNET_STATISTICS_Handle */ struct GNUNET_TIME_Relative backoff; + /** + * Maximum heap size observed so far (if available). + */ + uint64_t peak_heap_size; + + /** + * Maximum resident set side observed so far (if available). + */ + uint64_t peak_rss; + /** * Size of the 'watches' array. */ @@ -254,6 +264,51 @@ struct GNUNET_STATISTICS_Handle }; +/** + * Obtain statistics about this process's memory consumption and + * report those as well (if they changed). + */ +static void +update_memory_statistics (struct GNUNET_STATISTICS_Handle *h) +{ +#if ENABLE_HEAP_STATISTICS + uint64_t current_heap_size = 0; + uint64_t current_rss = 0; + + if (GNUNET_NO != h->do_destroy) + return; +#if HAVE_MALLINFO + { + struct mallinfo mi; + + mi = mallinfo(); + current_heap_size = mi.uordblks + mi.fordblks; + } +#endif +#if HAVE_GETRUSAGE + { + struct rusage ru; + + if (0 == getrusage (RUSAGE_SELF, &ru)) + { + current_rss = 1024LL * ru.ru_maxrss; + } + } +#endif + if (current_heap_size > h->peak_heap_size) + { + h->peak_heap_size = current_heap_size; + GNUNET_STATISTICS_set (h, "# peak heap size", current_heap_size, GNUNET_NO); + } + if (current_rss > h->peak_rss) + { + h->peak_rss = current_rss; + GNUNET_STATISTICS_set (h, "# peak resident set size", current_rss, GNUNET_NO); + } +#endif +} + + /** * Schedule the next action to be performed. * @@ -461,9 +516,7 @@ reconnect_later (struct GNUNET_STATISTICS_Handle *h) } h->backoff_task = GNUNET_SCHEDULER_add_delayed (h->backoff, &reconnect_task, h); - h->backoff = GNUNET_TIME_relative_multiply (h->backoff, 2); - h->backoff = - GNUNET_TIME_relative_min (h->backoff, GNUNET_CONSTANTS_SERVICE_TIMEOUT); + h->backoff = GNUNET_TIME_STD_BACKOFF (h->backoff); } @@ -820,6 +873,7 @@ transmit_set (struct GNUNET_STATISTICS_Handle *handle, size_t size, void *buf) GNUNET_assert (NULL == handle->current->cont); free_action_item (handle->current); handle->current = NULL; + update_memory_statistics (handle); return nsize; } @@ -875,6 +929,9 @@ GNUNET_STATISTICS_create (const char *subsystem, { struct GNUNET_STATISTICS_Handle *ret; + if (GNUNET_YES == + GNUNET_CONFIGURATION_get_value_yesno (cfg, "statistics", "DISABLE")) + return NULL; GNUNET_assert (NULL != subsystem); GNUNET_assert (NULL != cfg); ret = GNUNET_malloc (sizeof (struct GNUNET_STATISTICS_Handle)); diff --git a/src/statistics/test_gnunet_statistics.py.in b/src/statistics/test_gnunet_statistics.py.in new file mode 100644 index 0000000..0d3c984 --- /dev/null +++ b/src/statistics/test_gnunet_statistics.py.in @@ -0,0 +1,148 @@ +#!@PYTHON@ +from __future__ import print_function +import os +import sys +import shutil +import re +import subprocess +import time + +if os.name == "nt": + tmp = os.getenv ("TEMP") +else: + tmp = "/tmp" + +if os.name == 'nt': + st = 'gnunet-statistics.exe' + arm = 'gnunet-arm.exe' +else: + st = 'gnunet-statistics' + arm = 'gnunet-arm' + +run_st = [st, '-c', 'test_statistics_api_data.conf'] +run_arm = [arm, '-c', 'test_statistics_api_data.conf'] +debug = os.getenv ('DEBUG') +if debug: + run_arm += [debug.split (' ')] + +def cleanup (): + shutil.rmtree (os.path.join (tmp, "test-gnunetd-statistics"), True) + +def sub_run (args, want_stdo = True, want_stde = False, nofail = False): + if want_stdo: + stdo = subprocess.PIPE + else: + stdo = None + if want_stde: + stde = subprocess.PIPE + else: + stde = None + p = subprocess.Popen (args, stdout = stdo, stderr = stde) + stdo, stde = p.communicate () + if not nofail: + if p.returncode != 0: + sys.exit (p.returncode) + return (p.returncode, stdo, stde) + +def fail (result): + print (result) + r_arm (['-e'], want_stdo = False) + sys.exit (1) + +def r_arm (extra_args, **kw): + rc, stdo, stde = sub_run (run_arm + extra_args, **kw) + if rc != 0: + fail ("FAIL: error running {}".format (run_arm)) + return (rc, stdo, stde) + +def r_st (extra_args, normal = True, **kw): + rc, stdo, stde = sub_run (run_st + extra_args, **kw) + if normal: + if rc != 0: + fail ("FAIL: error running {}".format (run_st)) + else: + if rc == 0: + fail ("FAIL: expected error while running {}".format (run_st)) + return (rc, stdo, stde) + +def restart (): + print ("Restarting service...") + t = r_arm (['-k', 'statistics']) + time.sleep (1) + t = r_arm (['-i', 'statistics']) + time.sleep (1) + + +cleanup () + +print ("Preparing: Starting service...") +t = r_arm (['-s'], want_stdo = False) +time.sleep (1) +t = r_arm (['-i', 'statistics'], want_stdo = False) +time.sleep (1) + +print ("TEST: Bad argument checking...", end='') +r_st (['-x'], normal = False, nofail = True, want_stdo = False, want_stde = True) +print ("PASS") + +print ("TEST: Set value...", end='') +r_st (['-n', 'test', '-s', 'subsystem', '42'], nofail = True, want_stdo = False) +print ("PASS") + +print ("TEST: Set another value...", end='') +r_st (['-n', 'other', '-s', 'osystem', '43'], nofail = True, want_stdo = False) +print ("PASS") + +print ("TEST: Viewing all stats...", end='') +rc, stdo, stde = r_st ([], nofail = True, want_stdo = True) +if len (stdo.splitlines ()) != 2: + fail ("FAIL: unexpected output:\n{}".format (stdo)) +print ("PASS") + +print ("TEST: Viewing stats by name...", end='') +rc, stdo, stde = r_st (['-n', 'other'], nofail = True, want_stdo = True) +if len ([x for x in stdo.splitlines () if re.search ('43', x)]) != 1: + fail ("FAIL: unexpected output:\n{}".format (stdo)) +print ("PASS") + +print ("TEST: Viewing stats by subsystem...", end='') +rc, stdo, stde = r_st (['-s', 'subsystem'], nofail = True, want_stdo = True) +if len ([x for x in stdo.splitlines () if re.search ('42', x)]) != 1: + fail ("FAIL: unexpected output:\n{}".format (stdo)) +print ("PASS") + +print ("TEST: Set persistent value...", end='') +rc, stdo, stde = r_st (['-n', 'lasting', '-s', 'subsystem', '40', '-p'], nofail = True, want_stdo = False) +rc, stdo, stde = r_st ([], nofail = True, want_stdo = True) +if len ([x for x in stdo.splitlines () if re.search ('40', x)]) != 1: + fail ("FAIL: unexpected output:\n{}".format (stdo)) +print ("PASS") + +restart () + +print ("TEST: Checking persistence...", end='') +rc, stdo, stde = r_st ([], nofail = True, want_stdo = True) +if len ([x for x in stdo.splitlines () if re.search ('40', x)]) != 1: + fail ("FAIL: unexpected output:\n{}".format (stdo)) +print ("PASS") + +print ("TEST: Removing persistence...", end='') +rc, stdo, stde = r_st (['-n', 'lasting', '-s', 'subsystem', '40'], nofail = True, want_stdo = False) +rc, stdo, stde = r_st ([], nofail = True, want_stdo = True) +if len ([x for x in stdo.splitlines () if re.search ('!', x)]) != 0: + fail ("FAIL: unexpected output:\n{}".format (stdo)) +print ("PASS") + +restart () + +print ("TEST: Checking removed persistence...", end='') +rc, stdo, stde = r_st ([], nofail = True, want_stdo = True) +if len ([x for x in stdo.splitlines () if re.search ('40', x)]) != 0: + fail ("FAIL: unexpected output:\n{}".format (stdo)) +print ("PASS") + +print ("Stopping service...") +t = r_arm (['-e'], want_stdo = False) +time.sleep (1) + +cleanup () diff --git a/src/statistics/test_gnunet_statistics.sh b/src/statistics/test_gnunet_statistics.sh deleted file mode 100755 index eb2d618..0000000 --- a/src/statistics/test_gnunet_statistics.sh +++ /dev/null @@ -1,199 +0,0 @@ -#!/bin/sh - -rm -rf /tmp/test-gnunetd-statistics/ -exe="./gnunet-statistics -c test_statistics_api_data.conf" -out=`mktemp /tmp/test-gnunet-statistics-logXXXXXXXX` -arm="gnunet-arm -c test_statistics_api_data.conf $DEBUG" -#DEBUG="-L DEBUG" -# ----------------------------------- -echo -n "Preparing: Starting service..." - -$arm -s > /dev/null -sleep 1 -$arm -i statistics > /dev/null -sleep 1 -echo "DONE" - -# ---------------------------------------------------------------------------------- -echo -n "TEST: Bad argument checking..." - -if $exe -x 2> /dev/null; then - echo "FAIL: error running $exe" - $arm -e - exit 1 -fi -echo "PASS" - -# ---------------------------------------------------------------------------------- -echo -n "TEST: Set value..." - -if ! $exe $DEBUG -n test -s subsystem 42 ; then - echo "FAIL: error running $exe" - $arm -e - exit 1 -fi -echo "PASS" - -# ---------------------------------------------------------------------------------- -echo -n "TEST: Set another value..." - -if ! $exe $DEBUG -n other -s osystem 43 ; then - echo "FAIL: error running $exe" - $arm -e - exit 1 -fi -echo "PASS" - -# ---------------------------------------------------------------------------------- -echo -n "TEST: viewing all stats..." - -if ! $exe $DEBUG > $out; then - echo "FAIL: error running $exe" - $arm -e - exit 1 -fi -LINES=`cat $out | wc -l` -if test $LINES -ne 2; then - echo "FAIL: unexpected output" - $arm -e - exit 1 -fi -echo "PASS" - -# ---------------------------------------------------------------------------------- -echo -n "TEST: viewing stats by name..." - -if ! $exe $DEBUG -n other > $out; then - echo "FAIL: error running $exe" - $arm -e - exit 1 -fi -LINES=`cat $out | grep 43 | wc -l` -if test $LINES -ne 1; then - echo "FAIL: unexpected output" - $arm -e - exit 1 -fi -echo "PASS" - -# ---------------------------------------------------------------------------------- -echo -n "TEST: viewing stats by subsystem..." - -if ! $exe $DEBUG -s subsystem > $out; then - echo "FAIL: error running $exe" - $arm -e - exit 1 -fi -LINES=`cat $out | grep 42 | wc -l` -if test $LINES -ne 1; then - echo "FAIL: unexpected output" - $arm -e - exit 1 -fi -echo "PASS" - - -# ---------------------------------------------------------------------------------- -echo -n "TEST: Set persistent value..." - -if ! $exe $DEBUG -n lasting -s subsystem 40 -p; then - echo "FAIL: error running $exe" - $arm -e - exit 1 -fi -if ! $exe $DEBUG > $out; then - echo "FAIL: error running $exe" - $arm -e - exit 1 -fi -LINES=`cat $out | grep 40 | wc -l` -if test $LINES -ne 1; then - echo "FAIL: unexpected output" - cat $out - $arm -e - exit 1 -fi -echo "PASS" - -# ----------------------------------- -echo -n "Restarting service..." -$arm -k statistics > /dev/null -sleep 1 -$arm -i statistics > /dev/null -sleep 1 -echo "DONE" - -# ---------------------------------------------------------------------------------- -echo -n "TEST: checking persistence..." - -if ! $exe $DEBUG > $out; then - echo "FAIL: error running $exe" - $arm -e - exit 1 -fi -LINES=`cat $out | grep 40 | wc -l` -if test $LINES -ne 1; then - echo "FAIL: unexpected output" - cat $out - $arm -e - exit 1 -fi -echo "PASS" - - - -# ---------------------------------------------------------------------------------- -echo -n "TEST: Removing persistence..." - -if ! $exe $DEBUG -n lasting -s subsystem 40; then - echo "FAIL: error running $exe" - $arm -e - exit 1 -fi -if ! $exe $DEBUG > $out; then - echo "FAIL: error running $exe" - $arm -e - exit 1 -fi -LINES=`cat $out | grep \! | wc -l` -if test $LINES -ne 0; then - echo "FAIL: unexpected output" - cat $out - $arm -e - exit 1 -fi -echo "PASS" - - -# ----------------------------------- -echo -n "Restarting service..." -$arm -k statistics > /dev/null -sleep 1 -$arm -i statistics > /dev/null -sleep 1 -echo "DONE" - -# ---------------------------------------------------------------------------------- -echo -n "TEST: checking removed persistence..." - -if ! $exe $DEBUG > $out; then - echo "FAIL: error running $exe" - $arm -e - exit 1 -fi -LINES=`cat $out | grep 40 | wc -l` -if test $LINES -ne 0; then - echo "FAIL: unexpected output" - cat $out - $arm -e - exit 1 -fi -echo "PASS" - -# ----------------------------------- -echo -n "Stopping service..." -$arm -e > /dev/null -sleep 1 -echo "DONE" -rm -f $out -rm -rf /tmp/test-gnunetd-statistics/ diff --git a/src/statistics/test_statistics_api.c b/src/statistics/test_statistics_api.c index 11f02b8..5fb506f 100644 --- a/src/statistics/test_statistics_api.c +++ b/src/statistics/test_statistics_api.c @@ -1,6 +1,6 @@ /* This file is part of GNUnet. - (C) 2009 Christian Grothoff (and other contributing authors) + (C) 2009, 2012 Christian Grothoff (and other contributing authors) GNUnet is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published @@ -20,17 +20,15 @@ /** * @file statistics/test_statistics_api.c * @brief testcase for statistics_api.c + * @author Christian Grothoff */ #include "platform.h" -#include "gnunet_common.h" -#include "gnunet_getopt_lib.h" -#include "gnunet_os_lib.h" -#include "gnunet_program_lib.h" -#include "gnunet_scheduler_lib.h" +#include "gnunet_util_lib.h" #include "gnunet_statistics_service.h" -#define START_SERVICE GNUNET_YES +static struct GNUNET_STATISTICS_Handle *h; + static int check_1 (void *cls, const char *subsystem, const char *name, uint64_t value, @@ -45,6 +43,7 @@ check_1 (void *cls, const char *subsystem, const char *name, uint64_t value, return GNUNET_OK; } + static int check_2 (void *cls, const char *subsystem, const char *name, uint64_t value, int is_persistent) @@ -58,6 +57,7 @@ check_2 (void *cls, const char *subsystem, const char *name, uint64_t value, return GNUNET_OK; } + static int check_3 (void *cls, const char *subsystem, const char *name, uint64_t value, int is_persistent) @@ -71,7 +71,6 @@ check_3 (void *cls, const char *subsystem, const char *name, uint64_t value, return GNUNET_OK; } -static struct GNUNET_STATISTICS_Handle *h; static void next_fin (void *cls, int success) @@ -83,6 +82,7 @@ next_fin (void *cls, int success) *ok = 0; } + static void next (void *cls, int success) { @@ -94,6 +94,7 @@ next (void *cls, int success) &check_2, cls)); } + static void run (void *cls, char *const *args, const char *cfgfile, const struct GNUNET_CONFIGURATION_Handle *cfg) @@ -110,6 +111,7 @@ run (void *cls, char *const *args, const char *cfgfile, &check_1, cls)); } + static void run_more (void *cls, char *const *args, const char *cfgfile, const struct GNUNET_CONFIGURATION_Handle *cfg) @@ -121,8 +123,9 @@ run_more (void *cls, char *const *args, const char *cfgfile, &check_3, cls)); } -static int -check () + +int +main (int argc, char *argv_ign[]) { int ok = 1; @@ -135,18 +138,21 @@ check () struct GNUNET_GETOPT_CommandLineOption options[] = { GNUNET_GETOPT_OPTION_END }; -#if START_SERVICE struct GNUNET_OS_Process *proc; + char *binary; + GNUNET_log_setup ("test_statistics_api", + "WARNING", + NULL); + binary = GNUNET_OS_get_libexec_binary_path ("gnunet-service-statistics"); proc = - GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-statistics", + GNUNET_OS_start_process (GNUNET_YES, GNUNET_OS_INHERIT_STD_OUT_AND_ERR, NULL, NULL, + binary, "gnunet-service-statistics", "-c", "test_statistics_api_data.conf", NULL); -#endif GNUNET_assert (NULL != proc); GNUNET_PROGRAM_run (5, argv, "test-statistics-api", "nohelp", options, &run, &ok); -#if START_SERVICE if (0 != GNUNET_OS_process_kill (proc, SIGTERM)) { GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); @@ -155,20 +161,20 @@ check () GNUNET_OS_process_wait (proc); GNUNET_OS_process_destroy (proc); proc = NULL; -#endif if (ok != 0) + { + GNUNET_free (binary); return ok; + } ok = 1; -#if START_SERVICE /* restart to check persistence! */ proc = - GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-statistics", + GNUNET_OS_start_process (GNUNET_YES, GNUNET_OS_INHERIT_STD_OUT_AND_ERR, NULL, NULL, + binary, "gnunet-service-statistics", "-c", "test_statistics_api_data.conf", NULL); -#endif GNUNET_PROGRAM_run (5, argv, "test-statistics-api", "nohelp", options, &run_more, &ok); -#if START_SERVICE if (0 != GNUNET_OS_process_kill (proc, SIGTERM)) { GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); @@ -177,21 +183,8 @@ check () GNUNET_OS_process_wait (proc); GNUNET_OS_process_destroy (proc); proc = NULL; -#endif + GNUNET_free (binary); return ok; } -int -main (int argc, char *argv[]) -{ - int ret; - - GNUNET_log_setup ("test_statistics_api", - "WARNING", - NULL); - ret = check (); - - return ret; -} - /* end of test_statistics_api.c */ diff --git a/src/statistics/test_statistics_api_data.conf b/src/statistics/test_statistics_api_data.conf index 4e229e9..1ef8f95 100644 --- a/src/statistics/test_statistics_api_data.conf +++ b/src/statistics/test_statistics_api_data.conf @@ -1,17 +1,14 @@ [PATHS] SERVICEHOME = /tmp/test-gnunetd-statistics/ -DEFAULTCONFIG = test_statistics_api_data.conf [statistics] PORT = 22353 UNIXPATH = /tmp/test-statistics-service-statistics.unix -#DEBUG = YES [arm] PORT = 22354 DEFAULTSERVICES = UNIXPATH = /tmp/test-statistics-service-arm.unix -# DEBUG = YES [fs] AUTOSTART = NO @@ -52,3 +49,5 @@ AUTOSTART = NO [vpn] AUTOSTART = NO +[consensus] +AUTOSTART = NO diff --git a/src/statistics/test_statistics_api_loop.c b/src/statistics/test_statistics_api_loop.c index 58114f2..f9a3a3b 100644 --- a/src/statistics/test_statistics_api_loop.c +++ b/src/statistics/test_statistics_api_loop.c @@ -22,18 +22,13 @@ * @brief testcase for statistics_api.c */ #include "platform.h" -#include "gnunet_common.h" -#include "gnunet_getopt_lib.h" -#include "gnunet_os_lib.h" -#include "gnunet_program_lib.h" -#include "gnunet_scheduler_lib.h" +#include "gnunet_util_lib.h" #include "gnunet_statistics_service.h" -#define VERBOSE GNUNET_NO +#define ROUNDS (1024 * 1024) -#define START_SERVICE GNUNET_YES +static struct GNUNET_STATISTICS_Handle *h; -#define ROUNDS (1024 * 1024) static int check_1 (void *cls, const char *subsystem, const char *name, uint64_t value, @@ -45,7 +40,6 @@ check_1 (void *cls, const char *subsystem, const char *name, uint64_t value, return GNUNET_OK; } -static struct GNUNET_STATISTICS_Handle *h; static void next (void *cls, int success) @@ -57,11 +51,12 @@ next (void *cls, int success) *ok = 0; } + static void run (void *cls, char *const *args, const char *cfgfile, const struct GNUNET_CONFIGURATION_Handle *cfg) { - int i; + unsigned int i; char name[128]; h = GNUNET_STATISTICS_create ("test-statistics-api-loop", cfg); @@ -80,8 +75,8 @@ run (void *cls, char *const *args, const char *cfgfile, } -static int -check () +int +main (int argc, char *argv_ign[]) { int ok = 1; @@ -93,21 +88,19 @@ check () struct GNUNET_GETOPT_CommandLineOption options[] = { GNUNET_GETOPT_OPTION_END }; -#if START_SERVICE struct GNUNET_OS_Process *proc; + char *binary; + binary = GNUNET_OS_get_libexec_binary_path ("gnunet-service-statistics"); proc = - GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-statistics", - "gnunet-service-statistics", -#if DEBUG_STATISTICS - "-L", "DEBUG", -#endif - "-c", "test_statistics_api_data.conf", NULL); -#endif + GNUNET_OS_start_process (GNUNET_YES, GNUNET_OS_INHERIT_STD_OUT_AND_ERR, + NULL, NULL, + binary, + "gnunet-service-statistics", + "-c", "test_statistics_api_data.conf", NULL); GNUNET_assert (NULL != proc); GNUNET_PROGRAM_run (3, argv, "test-statistics-api", "nohelp", options, &run, &ok); -#if START_SERVICE if (0 != GNUNET_OS_process_kill (proc, SIGTERM)) { GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); @@ -116,18 +109,8 @@ check () GNUNET_OS_process_wait (proc); GNUNET_OS_process_destroy (proc); proc = NULL; -#endif + GNUNET_free (binary); return ok; } -int -main (int argc, char *argv[]) -{ - int ret; - - ret = check (); - - return ret; -} - /* end of test_statistics_api_loop.c */ diff --git a/src/statistics/test_statistics_api_watch.c b/src/statistics/test_statistics_api_watch.c index e976bd4..1e7f27b 100644 --- a/src/statistics/test_statistics_api_watch.c +++ b/src/statistics/test_statistics_api_watch.c @@ -1,6 +1,6 @@ /* This file is part of GNUnet. - (C) 2009, 2011 Christian Grothoff (and other contributing authors) + (C) 2009, 2011, 2012 Christian Grothoff (and other contributing authors) GNUnet is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published @@ -20,6 +20,7 @@ /** * @file statistics/test_statistics_api_watch.c * @brief testcase for statistics_api.c watch functions + * @author Christian Grothoff */ #include "platform.h" #include "gnunet_common.h" @@ -29,9 +30,6 @@ #include "gnunet_scheduler_lib.h" #include "gnunet_statistics_service.h" -#define VERBOSE GNUNET_NO - -#define START_SERVICE GNUNET_YES static int ok; @@ -112,8 +110,8 @@ run (void *cls, char *const *args, const char *cfgfile, } -static int -check () +int +main (int argc, char *argv_ign[]) { char *const argv[] = { "test-statistics-api", "-c", @@ -123,22 +121,19 @@ check () struct GNUNET_GETOPT_CommandLineOption options[] = { GNUNET_GETOPT_OPTION_END }; -#if START_SERVICE struct GNUNET_OS_Process *proc; - + char *binary; + + binary = GNUNET_OS_get_libexec_binary_path ("gnunet-service-statistics"); proc = - GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-statistics", - "gnunet-service-statistics", -#if VERBOSE - "-L", "DEBUG", -#endif - "-c", "test_statistics_api_data.conf", NULL); -#endif + GNUNET_OS_start_process (GNUNET_YES, GNUNET_OS_INHERIT_STD_OUT_AND_ERR, NULL, NULL, + binary, + "gnunet-service-statistics", + "-c", "test_statistics_api_data.conf", NULL); GNUNET_assert (NULL != proc); ok = 3; GNUNET_PROGRAM_run (3, argv, "test-statistics-api", "nohelp", options, &run, NULL); -#if START_SERVICE if (0 != GNUNET_OS_process_kill (proc, SIGTERM)) { GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); @@ -147,18 +142,9 @@ check () GNUNET_OS_process_wait (proc); GNUNET_OS_process_destroy (proc); proc = NULL; -#endif + GNUNET_free (binary); return ok; } -int -main (int argc, char *argv[]) -{ - int ret; - - ret = check (); - - return ret; -} /* end of test_statistics_api_watch.c */ diff --git a/src/statistics/test_statistics_api_watch_zero_value.c b/src/statistics/test_statistics_api_watch_zero_value.c index 9fadf6a..d78de9a 100644 --- a/src/statistics/test_statistics_api_watch_zero_value.c +++ b/src/statistics/test_statistics_api_watch_zero_value.c @@ -1,6 +1,6 @@ /* This file is part of GNUnet. - (C) 2009, 2011 Christian Grothoff (and other contributing authors) + (C) 2009, 2011, 2012 Christian Grothoff (and other contributing authors) GNUnet is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published @@ -22,21 +22,15 @@ * @brief testcase for statistics_api.c watch functions with initial 0 value */ #include "platform.h" -#include "gnunet_common.h" -#include "gnunet_getopt_lib.h" -#include "gnunet_os_lib.h" -#include "gnunet_program_lib.h" -#include "gnunet_scheduler_lib.h" +#include "gnunet_util_lib.h" #include "gnunet_statistics_service.h" -#define VERBOSE GNUNET_NO - -#define START_SERVICE GNUNET_YES - static int ok; + static int ok2; static struct GNUNET_STATISTICS_Handle *h; + static struct GNUNET_STATISTICS_Handle *h2; static GNUNET_SCHEDULER_TaskIdentifier shutdown_task; @@ -92,6 +86,7 @@ watch_1 (void *cls, const char *subsystem, const char *name, uint64_t value, return GNUNET_OK; } + static int watch_2 (void *cls, const char *subsystem, const char *name, uint64_t value, int is_persistent) @@ -121,6 +116,7 @@ watch_2 (void *cls, const char *subsystem, const char *name, uint64_t value, return GNUNET_OK; } + static void run (void *cls, char *const *args, const char *cfgfile, const struct GNUNET_CONFIGURATION_Handle *cfg) @@ -145,8 +141,8 @@ run (void *cls, char *const *args, const char *cfgfile, } -static int -check () +int +main (int argc, char *argv_ign[]) { char *const argv[] = { "test-statistics-api", "-c", @@ -156,23 +152,20 @@ check () struct GNUNET_GETOPT_CommandLineOption options[] = { GNUNET_GETOPT_OPTION_END }; -#if START_SERVICE struct GNUNET_OS_Process *proc; + char *binary; + binary = GNUNET_OS_get_libexec_binary_path ("gnunet-service-statistics"); proc = - GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-statistics", - "gnunet-service-statistics", -#if VERBOSE - "-L", "DEBUG", -#endif - "-c", "test_statistics_api_data.conf", NULL); -#endif + GNUNET_OS_start_process (GNUNET_YES, GNUNET_OS_INHERIT_STD_OUT_AND_ERR, NULL, NULL, + binary, + "gnunet-service-statistics", + "-c", "test_statistics_api_data.conf", NULL); GNUNET_assert (NULL != proc); ok = 3; ok2 = 1; GNUNET_PROGRAM_run (3, argv, "test-statistics-api", "nohelp", options, &run, NULL); -#if START_SERVICE if (0 != GNUNET_OS_process_kill (proc, SIGTERM)) { GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); @@ -181,21 +174,10 @@ check () GNUNET_OS_process_wait (proc); GNUNET_OS_process_destroy (proc); proc = NULL; -#endif + GNUNET_free (binary); if ((0 == ok) && (0 == ok2)) return 0; - else - return 1; -} - -int -main (int argc, char *argv[]) -{ - int ret; - - ret = check (); - - return ret; + return 1; } /* end of test_statistics_api_watch_zero_value.c */ diff --git a/src/stream/Makefile.am b/src/stream/Makefile.am index 8d74417..0994697 100644 --- a/src/stream/Makefile.am +++ b/src/stream/Makefile.am @@ -12,22 +12,39 @@ endif lib_LTLIBRARIES = libgnunetstream.la libgnunetstream_la_SOURCES = \ - stream_api.c stream_protocol.h + stream_api.c stream.h libgnunetstream_la_LIBADD = \ $(top_builddir)/src/mesh/libgnunetmesh.la \ + $(top_builddir)/src/lockmanager/libgnunetlockmanager.la \ + $(top_builddir)/src/statistics/libgnunetstatistics.la \ $(top_builddir)/src/util/libgnunetutil.la $(XLIB) libgnunetstream_la_LDFLAGS = \ - $(GN_LIB_LDFLAGS) + $(GN_LIB_LDFLAGS) \ + -version-info 1:0:0 + +if HAVE_BENCHMARKS + STREAM_BENCHMARKS = \ + perf_stream_api +endif check_PROGRAMS = \ - test-stream-2peers \ - test-stream-2peers_halfclose \ - test-stream-local + test_stream_2peers \ + test_stream_2peers_halfclose \ + test_stream_local \ + test_stream_big \ + test_stream_sequence_wraparound \ + $(STREAM_BENCHMARKS) EXTRA_DIST = test_stream_local.conf if ENABLE_TEST_RUN -TESTS = $(check_PROGRAMS) +TESTS = \ + test_stream_2peers \ + test_stream_2peers_halfclose \ + test_stream_local \ + test_stream_big \ + test_stream_sequence_wraparound \ + $(STREAM_BENCHMARKS) endif test_stream_2peers_SOURCES = \ @@ -35,18 +52,41 @@ test_stream_2peers_SOURCES = \ test_stream_2peers_LDADD = \ $(top_builddir)/src/stream/libgnunetstream.la \ $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/testing/libgnunettesting.la + $(top_builddir)/src/testbed/libgnunettestbed.la + test_stream_2peers_halfclose_SOURCES = \ test_stream_2peers_halfclose.c test_stream_2peers_halfclose_LDADD = \ $(top_builddir)/src/stream/libgnunetstream.la \ $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/testing/libgnunettesting.la + $(top_builddir)/src/testbed/libgnunettestbed.la test_stream_local_SOURCES = \ test_stream_local.c test_stream_local_LDADD = \ $(top_builddir)/src/stream/libgnunetstream.la \ $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/testing/libgnunettesting.la \ No newline at end of file + $(top_builddir)/src/testing/libgnunettesting.la + +test_stream_big_SOURCES = \ + test_stream_big.c +test_stream_big_LDADD = \ + $(top_builddir)/src/stream/libgnunetstream.la \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la + +test_stream_sequence_wraparound_SOURCES = \ + test_stream_sequence_wraparound.c +test_stream_sequence_wraparound_LDADD = \ + $(top_builddir)/src/stream/libgnunetstream.la \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la + +perf_stream_api_SOURCES = \ + perf_stream_api.c +perf_stream_api_LDADD = \ + $(top_builddir)/src/stream/libgnunetstream.la \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la \ No newline at end of file diff --git a/src/stream/Makefile.in b/src/stream/Makefile.in index 9f1c278..2422602 100644 --- a/src/stream/Makefile.in +++ b/src/stream/Makefile.in @@ -1,9 +1,9 @@ -# Makefile.in generated by automake 1.11.1 from Makefile.am. +# Makefile.in generated by automake 1.11.6 from Makefile.am. # @configure_input@ # Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, -# 2003, 2004, 2005, 2006, 2007, 2008, 2009 Free Software Foundation, -# Inc. +# 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Free Software +# Foundation, Inc. # This Makefile.in is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. @@ -16,6 +16,23 @@ @SET_MAKE@ VPATH = @srcdir@ +am__make_dryrun = \ + { \ + am__dry=no; \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + echo 'am--echo: ; @echo "AM" OK' | $(MAKE) -f - 2>/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } pkgdatadir = $(datadir)/@PACKAGE@ pkgincludedir = $(includedir)/@PACKAGE@ pkglibdir = $(libdir)/@PACKAGE@ @@ -35,22 +52,30 @@ POST_UNINSTALL = : build_triplet = @build@ host_triplet = @host@ target_triplet = @target@ -check_PROGRAMS = test-stream-2peers$(EXEEXT) \ - test-stream-2peers_halfclose$(EXEEXT) \ - test-stream-local$(EXEEXT) +check_PROGRAMS = test_stream_2peers$(EXEEXT) \ + test_stream_2peers_halfclose$(EXEEXT) \ + test_stream_local$(EXEEXT) test_stream_big$(EXEEXT) \ + test_stream_sequence_wraparound$(EXEEXT) $(am__EXEEXT_1) +@ENABLE_TEST_RUN_TRUE@TESTS = test_stream_2peers$(EXEEXT) \ +@ENABLE_TEST_RUN_TRUE@ test_stream_2peers_halfclose$(EXEEXT) \ +@ENABLE_TEST_RUN_TRUE@ test_stream_local$(EXEEXT) \ +@ENABLE_TEST_RUN_TRUE@ test_stream_big$(EXEEXT) \ +@ENABLE_TEST_RUN_TRUE@ test_stream_sequence_wraparound$(EXEEXT) \ +@ENABLE_TEST_RUN_TRUE@ $(am__EXEEXT_1) subdir = src/stream DIST_COMMON = README $(srcdir)/Makefile.am $(srcdir)/Makefile.in ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 am__aclocal_m4_deps = $(top_srcdir)/m4/absolute-header.m4 \ $(top_srcdir)/m4/align.m4 $(top_srcdir)/m4/argz.m4 \ - $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/iconv.m4 \ - $(top_srcdir)/m4/lib-ld.m4 $(top_srcdir)/m4/lib-link.m4 \ - $(top_srcdir)/m4/lib-prefix.m4 $(top_srcdir)/m4/libcurl.m4 \ - $(top_srcdir)/m4/libgcrypt.m4 $(top_srcdir)/m4/libtool.m4 \ - $(top_srcdir)/m4/libunistring.m4 $(top_srcdir)/m4/ltdl.m4 \ - $(top_srcdir)/m4/ltoptions.m4 $(top_srcdir)/m4/ltsugar.m4 \ - $(top_srcdir)/m4/ltversion.m4 $(top_srcdir)/m4/lt~obsolete.m4 \ - $(top_srcdir)/m4/nls.m4 $(top_srcdir)/m4/po.m4 \ + $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/glib-2.0.m4 \ + $(top_srcdir)/m4/iconv.m4 $(top_srcdir)/m4/lib-ld.m4 \ + $(top_srcdir)/m4/lib-link.m4 $(top_srcdir)/m4/lib-prefix.m4 \ + $(top_srcdir)/m4/libcurl.m4 $(top_srcdir)/m4/libgcrypt.m4 \ + $(top_srcdir)/m4/libtool.m4 $(top_srcdir)/m4/libunistring.m4 \ + $(top_srcdir)/m4/ltdl.m4 $(top_srcdir)/m4/ltoptions.m4 \ + $(top_srcdir)/m4/ltsugar.m4 $(top_srcdir)/m4/ltversion.m4 \ + $(top_srcdir)/m4/lt~obsolete.m4 $(top_srcdir)/m4/nls.m4 \ + $(top_srcdir)/m4/pkg.m4 $(top_srcdir)/m4/po.m4 \ $(top_srcdir)/m4/progtest.m4 $(top_srcdir)/acinclude.m4 \ $(top_srcdir)/configure.ac am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ @@ -80,33 +105,55 @@ am__nobase_list = $(am__nobase_strip_setup); \ am__base_list = \ sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \ sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g' +am__uninstall_files_from_dir = { \ + test -z "$$files" \ + || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \ + || { echo " ( cd '$$dir' && rm -f" $$files ")"; \ + $(am__cd) "$$dir" && rm -f $$files; }; \ + } am__installdirs = "$(DESTDIR)$(libdir)" LTLIBRARIES = $(lib_LTLIBRARIES) am__DEPENDENCIES_1 = libgnunetstream_la_DEPENDENCIES = \ $(top_builddir)/src/mesh/libgnunetmesh.la \ + $(top_builddir)/src/lockmanager/libgnunetlockmanager.la \ + $(top_builddir)/src/statistics/libgnunetstatistics.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(am__DEPENDENCIES_1) am_libgnunetstream_la_OBJECTS = stream_api.lo libgnunetstream_la_OBJECTS = $(am_libgnunetstream_la_OBJECTS) -AM_V_lt = $(am__v_lt_$(V)) -am__v_lt_ = $(am__v_lt_$(AM_DEFAULT_VERBOSITY)) +AM_V_lt = $(am__v_lt_@AM_V@) +am__v_lt_ = $(am__v_lt_@AM_DEFAULT_V@) am__v_lt_0 = --silent libgnunetstream_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ $(AM_CFLAGS) $(CFLAGS) $(libgnunetstream_la_LDFLAGS) \ $(LDFLAGS) -o $@ +@HAVE_BENCHMARKS_TRUE@am__EXEEXT_1 = perf_stream_api$(EXEEXT) +am_perf_stream_api_OBJECTS = perf_stream_api.$(OBJEXT) +perf_stream_api_OBJECTS = $(am_perf_stream_api_OBJECTS) +perf_stream_api_DEPENDENCIES = \ + $(top_builddir)/src/stream/libgnunetstream.la \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la am_test_stream_2peers_OBJECTS = test_stream_2peers.$(OBJEXT) test_stream_2peers_OBJECTS = $(am_test_stream_2peers_OBJECTS) test_stream_2peers_DEPENDENCIES = \ $(top_builddir)/src/stream/libgnunetstream.la \ $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/testing/libgnunettesting.la + $(top_builddir)/src/testbed/libgnunettestbed.la am_test_stream_2peers_halfclose_OBJECTS = \ test_stream_2peers_halfclose.$(OBJEXT) test_stream_2peers_halfclose_OBJECTS = \ $(am_test_stream_2peers_halfclose_OBJECTS) test_stream_2peers_halfclose_DEPENDENCIES = \ + $(top_builddir)/src/stream/libgnunetstream.la \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la +am_test_stream_big_OBJECTS = test_stream_big.$(OBJEXT) +test_stream_big_OBJECTS = $(am_test_stream_big_OBJECTS) +test_stream_big_DEPENDENCIES = \ $(top_builddir)/src/stream/libgnunetstream.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/testing/libgnunettesting.la @@ -116,6 +163,14 @@ test_stream_local_DEPENDENCIES = \ $(top_builddir)/src/stream/libgnunetstream.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/testing/libgnunettesting.la +am_test_stream_sequence_wraparound_OBJECTS = \ + test_stream_sequence_wraparound.$(OBJEXT) +test_stream_sequence_wraparound_OBJECTS = \ + $(am_test_stream_sequence_wraparound_OBJECTS) +test_stream_sequence_wraparound_DEPENDENCIES = \ + $(top_builddir)/src/stream/libgnunetstream.la \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la DEFAULT_INCLUDES = -I.@am__isrc@ -I$(top_builddir) depcomp = $(SHELL) $(top_srcdir)/depcomp am__depfiles_maybe = depfiles @@ -126,29 +181,37 @@ LTCOMPILE = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) \ $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) \ $(AM_CFLAGS) $(CFLAGS) -AM_V_CC = $(am__v_CC_$(V)) -am__v_CC_ = $(am__v_CC_$(AM_DEFAULT_VERBOSITY)) +AM_V_CC = $(am__v_CC_@AM_V@) +am__v_CC_ = $(am__v_CC_@AM_DEFAULT_V@) am__v_CC_0 = @echo " CC " $@; -AM_V_at = $(am__v_at_$(V)) -am__v_at_ = $(am__v_at_$(AM_DEFAULT_VERBOSITY)) +AM_V_at = $(am__v_at_@AM_V@) +am__v_at_ = $(am__v_at_@AM_DEFAULT_V@) am__v_at_0 = @ CCLD = $(CC) LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ $(AM_LDFLAGS) $(LDFLAGS) -o $@ -AM_V_CCLD = $(am__v_CCLD_$(V)) -am__v_CCLD_ = $(am__v_CCLD_$(AM_DEFAULT_VERBOSITY)) +AM_V_CCLD = $(am__v_CCLD_@AM_V@) +am__v_CCLD_ = $(am__v_CCLD_@AM_DEFAULT_V@) am__v_CCLD_0 = @echo " CCLD " $@; -AM_V_GEN = $(am__v_GEN_$(V)) -am__v_GEN_ = $(am__v_GEN_$(AM_DEFAULT_VERBOSITY)) +AM_V_GEN = $(am__v_GEN_@AM_V@) +am__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@) am__v_GEN_0 = @echo " GEN " $@; -SOURCES = $(libgnunetstream_la_SOURCES) $(test_stream_2peers_SOURCES) \ +SOURCES = $(libgnunetstream_la_SOURCES) $(perf_stream_api_SOURCES) \ + $(test_stream_2peers_SOURCES) \ $(test_stream_2peers_halfclose_SOURCES) \ - $(test_stream_local_SOURCES) + $(test_stream_big_SOURCES) $(test_stream_local_SOURCES) \ + $(test_stream_sequence_wraparound_SOURCES) DIST_SOURCES = $(libgnunetstream_la_SOURCES) \ - $(test_stream_2peers_SOURCES) \ + $(perf_stream_api_SOURCES) $(test_stream_2peers_SOURCES) \ $(test_stream_2peers_halfclose_SOURCES) \ - $(test_stream_local_SOURCES) + $(test_stream_big_SOURCES) $(test_stream_local_SOURCES) \ + $(test_stream_sequence_wraparound_SOURCES) +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac ETAGS = etags CTAGS = ctags am__tty_colors = \ @@ -189,6 +252,10 @@ EXEEXT = @EXEEXT@ EXT_LIBS = @EXT_LIBS@ EXT_LIB_PATH = @EXT_LIB_PATH@ FGREP = @FGREP@ +GLIB_CFLAGS = @GLIB_CFLAGS@ +GLIB_GENMARSHAL = @GLIB_GENMARSHAL@ +GLIB_LIBS = @GLIB_LIBS@ +GLIB_MKENUMS = @GLIB_MKENUMS@ GMSGFMT = @GMSGFMT@ GMSGFMT_015 = @GMSGFMT_015@ GNUNETDNS_GROUP = @GNUNETDNS_GROUP@ @@ -199,6 +266,7 @@ GN_LIBINTL = @GN_LIBINTL@ GN_LIB_LDFLAGS = @GN_LIB_LDFLAGS@ GN_PLUGIN_LDFLAGS = @GN_PLUGIN_LDFLAGS@ GN_USER_HOME_DIR = @GN_USER_HOME_DIR@ +GOBJECT_QUERY = @GOBJECT_QUERY@ GREP = @GREP@ HAVE_LIBUNISTRING = @HAVE_LIBUNISTRING@ INCLTDL = @INCLTDL@ @@ -221,6 +289,8 @@ LIBCURL_CPPFLAGS = @LIBCURL_CPPFLAGS@ LIBGCRYPT_CFLAGS = @LIBGCRYPT_CFLAGS@ LIBGCRYPT_CONFIG = @LIBGCRYPT_CONFIG@ LIBGCRYPT_LIBS = @LIBGCRYPT_LIBS@ +LIBGTOP_CFLAGS = @LIBGTOP_CFLAGS@ +LIBGTOP_LIBS = @LIBGTOP_LIBS@ LIBICONV = @LIBICONV@ LIBINTL = @LIBINTL@ LIBLTDL = @LIBLTDL@ @@ -242,6 +312,7 @@ LT_CONFIG_H = @LT_CONFIG_H@ LT_DLLOADERS = @LT_DLLOADERS@ LT_DLPREOPEN = @LT_DLPREOPEN@ MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ MKDIR_P = @MKDIR_P@ MONKEYPREFIX = @MONKEYPREFIX@ MSGFMT = @MSGFMT@ @@ -251,6 +322,7 @@ MYSQL_CPPFLAGS = @MYSQL_CPPFLAGS@ MYSQL_LDFLAGS = @MYSQL_LDFLAGS@ NM = @NM@ NMEDIT = @NMEDIT@ +NSS_DIR = @NSS_DIR@ OBJC = @OBJC@ OBJCDEPMODE = @OBJCDEPMODE@ OBJCFLAGS = @OBJCFLAGS@ @@ -266,6 +338,7 @@ PACKAGE_TARNAME = @PACKAGE_TARNAME@ PACKAGE_URL = @PACKAGE_URL@ PACKAGE_VERSION = @PACKAGE_VERSION@ PATH_SEPARATOR = @PATH_SEPARATOR@ +PKG_CONFIG = @PKG_CONFIG@ POSTGRES_CPPFLAGS = @POSTGRES_CPPFLAGS@ POSTGRES_LDFLAGS = @POSTGRES_LDFLAGS@ POSUB = @POSUB@ @@ -297,6 +370,7 @@ abs_builddir = @abs_builddir@ abs_srcdir = @abs_srcdir@ abs_top_builddir = @abs_top_builddir@ abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ ac_ct_CC = @ac_ct_CC@ ac_ct_CXX = @ac_ct_CXX@ ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ @@ -319,6 +393,7 @@ datarootdir = @datarootdir@ docdir = @docdir@ dvidir = @dvidir@ exec_prefix = @exec_prefix@ +gitcommand = @gitcommand@ host = @host@ host_alias = @host_alias@ host_cpu = @host_cpu@ @@ -332,7 +407,6 @@ libdir = @libdir@ libexecdir = @libexecdir@ localedir = @localedir@ localstatedir = @localstatedir@ -lt_ECHO = @lt_ECHO@ ltdl_LIBOBJS = @ltdl_LIBOBJS@ ltdl_LTLIBOBJS = @ltdl_LTLIBOBJS@ mandir = @mandir@ @@ -350,6 +424,7 @@ sbindir = @sbindir@ sharedstatedir = @sharedstatedir@ srcdir = @srcdir@ subdirs = @subdirs@ +svnversioncommand = @svnversioncommand@ sys_symbol_underscore = @sys_symbol_underscore@ sysconfdir = @sysconfdir@ target = @target@ @@ -366,24 +441,29 @@ INCLUDES = -I$(top_srcdir)/src/include @USE_COVERAGE_TRUE@XLIB = -lgcov lib_LTLIBRARIES = libgnunetstream.la libgnunetstream_la_SOURCES = \ - stream_api.c stream_protocol.h + stream_api.c stream.h libgnunetstream_la_LIBADD = \ $(top_builddir)/src/mesh/libgnunetmesh.la \ + $(top_builddir)/src/lockmanager/libgnunetlockmanager.la \ + $(top_builddir)/src/statistics/libgnunetstatistics.la \ $(top_builddir)/src/util/libgnunetutil.la $(XLIB) libgnunetstream_la_LDFLAGS = \ - $(GN_LIB_LDFLAGS) + $(GN_LIB_LDFLAGS) \ + -version-info 1:0:0 + +@HAVE_BENCHMARKS_TRUE@STREAM_BENCHMARKS = \ +@HAVE_BENCHMARKS_TRUE@ perf_stream_api EXTRA_DIST = test_stream_local.conf -@ENABLE_TEST_RUN_TRUE@TESTS = $(check_PROGRAMS) test_stream_2peers_SOURCES = \ test_stream_2peers.c test_stream_2peers_LDADD = \ $(top_builddir)/src/stream/libgnunetstream.la \ $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/testing/libgnunettesting.la + $(top_builddir)/src/testbed/libgnunettestbed.la test_stream_2peers_halfclose_SOURCES = \ test_stream_2peers_halfclose.c @@ -391,7 +471,7 @@ test_stream_2peers_halfclose_SOURCES = \ test_stream_2peers_halfclose_LDADD = \ $(top_builddir)/src/stream/libgnunetstream.la \ $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/testing/libgnunettesting.la + $(top_builddir)/src/testbed/libgnunettestbed.la test_stream_local_SOURCES = \ test_stream_local.c @@ -401,6 +481,31 @@ test_stream_local_LDADD = \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/testing/libgnunettesting.la +test_stream_big_SOURCES = \ + test_stream_big.c + +test_stream_big_LDADD = \ + $(top_builddir)/src/stream/libgnunetstream.la \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la + +test_stream_sequence_wraparound_SOURCES = \ + test_stream_sequence_wraparound.c + +test_stream_sequence_wraparound_LDADD = \ + $(top_builddir)/src/stream/libgnunetstream.la \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la + +perf_stream_api_SOURCES = \ + perf_stream_api.c + +perf_stream_api_LDADD = \ + $(top_builddir)/src/stream/libgnunetstream.la \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la + all: all-am .SUFFIXES: @@ -437,7 +542,6 @@ $(ACLOCAL_M4): $(am__aclocal_m4_deps) $(am__aclocal_m4_deps): install-libLTLIBRARIES: $(lib_LTLIBRARIES) @$(NORMAL_INSTALL) - test -z "$(libdir)" || $(MKDIR_P) "$(DESTDIR)$(libdir)" @list='$(lib_LTLIBRARIES)'; test -n "$(libdir)" || list=; \ list2=; for p in $$list; do \ if test -f $$p; then \ @@ -445,6 +549,8 @@ install-libLTLIBRARIES: $(lib_LTLIBRARIES) else :; fi; \ done; \ test -z "$$list2" || { \ + echo " $(MKDIR_P) '$(DESTDIR)$(libdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libdir)" || exit 1; \ echo " $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 '$(DESTDIR)$(libdir)'"; \ $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 "$(DESTDIR)$(libdir)"; \ } @@ -466,7 +572,7 @@ clean-libLTLIBRARIES: echo "rm -f \"$${dir}/so_locations\""; \ rm -f "$${dir}/so_locations"; \ done -libgnunetstream.la: $(libgnunetstream_la_OBJECTS) $(libgnunetstream_la_DEPENDENCIES) +libgnunetstream.la: $(libgnunetstream_la_OBJECTS) $(libgnunetstream_la_DEPENDENCIES) $(EXTRA_libgnunetstream_la_DEPENDENCIES) $(AM_V_CCLD)$(libgnunetstream_la_LINK) -rpath $(libdir) $(libgnunetstream_la_OBJECTS) $(libgnunetstream_la_LIBADD) $(LIBS) clean-checkPROGRAMS: @@ -477,15 +583,24 @@ clean-checkPROGRAMS: list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ echo " rm -f" $$list; \ rm -f $$list -test-stream-2peers$(EXEEXT): $(test_stream_2peers_OBJECTS) $(test_stream_2peers_DEPENDENCIES) - @rm -f test-stream-2peers$(EXEEXT) +perf_stream_api$(EXEEXT): $(perf_stream_api_OBJECTS) $(perf_stream_api_DEPENDENCIES) $(EXTRA_perf_stream_api_DEPENDENCIES) + @rm -f perf_stream_api$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(perf_stream_api_OBJECTS) $(perf_stream_api_LDADD) $(LIBS) +test_stream_2peers$(EXEEXT): $(test_stream_2peers_OBJECTS) $(test_stream_2peers_DEPENDENCIES) $(EXTRA_test_stream_2peers_DEPENDENCIES) + @rm -f test_stream_2peers$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_stream_2peers_OBJECTS) $(test_stream_2peers_LDADD) $(LIBS) -test-stream-2peers_halfclose$(EXEEXT): $(test_stream_2peers_halfclose_OBJECTS) $(test_stream_2peers_halfclose_DEPENDENCIES) - @rm -f test-stream-2peers_halfclose$(EXEEXT) +test_stream_2peers_halfclose$(EXEEXT): $(test_stream_2peers_halfclose_OBJECTS) $(test_stream_2peers_halfclose_DEPENDENCIES) $(EXTRA_test_stream_2peers_halfclose_DEPENDENCIES) + @rm -f test_stream_2peers_halfclose$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_stream_2peers_halfclose_OBJECTS) $(test_stream_2peers_halfclose_LDADD) $(LIBS) -test-stream-local$(EXEEXT): $(test_stream_local_OBJECTS) $(test_stream_local_DEPENDENCIES) - @rm -f test-stream-local$(EXEEXT) +test_stream_big$(EXEEXT): $(test_stream_big_OBJECTS) $(test_stream_big_DEPENDENCIES) $(EXTRA_test_stream_big_DEPENDENCIES) + @rm -f test_stream_big$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_stream_big_OBJECTS) $(test_stream_big_LDADD) $(LIBS) +test_stream_local$(EXEEXT): $(test_stream_local_OBJECTS) $(test_stream_local_DEPENDENCIES) $(EXTRA_test_stream_local_DEPENDENCIES) + @rm -f test_stream_local$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_stream_local_OBJECTS) $(test_stream_local_LDADD) $(LIBS) +test_stream_sequence_wraparound$(EXEEXT): $(test_stream_sequence_wraparound_OBJECTS) $(test_stream_sequence_wraparound_DEPENDENCIES) $(EXTRA_test_stream_sequence_wraparound_DEPENDENCIES) + @rm -f test_stream_sequence_wraparound$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_stream_sequence_wraparound_OBJECTS) $(test_stream_sequence_wraparound_LDADD) $(LIBS) mostlyclean-compile: -rm -f *.$(OBJEXT) @@ -493,34 +608,34 @@ mostlyclean-compile: distclean-compile: -rm -f *.tab.c +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/perf_stream_api.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/stream_api.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_stream_2peers.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_stream_2peers_halfclose.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_stream_big.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_stream_local.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_stream_sequence_wraparound.Po@am__quote@ .c.o: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c $< .c.obj: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'` @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c `$(CYGPATH_W) '$<'` +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c `$(CYGPATH_W) '$<'` .c.lo: @am__fastdepCC_TRUE@ $(AM_V_CC)$(LTCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LTCOMPILE) -c -o $@ $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LTCOMPILE) -c -o $@ $< mostlyclean-libtool: -rm -f *.lo @@ -661,14 +776,15 @@ check-TESTS: $(TESTS) fi; \ dashes=`echo "$$dashes" | sed s/./=/g`; \ if test "$$failed" -eq 0; then \ - echo "$$grn$$dashes"; \ + col="$$grn"; \ else \ - echo "$$red$$dashes"; \ + col="$$red"; \ fi; \ - echo "$$banner"; \ - test -z "$$skipped" || echo "$$skipped"; \ - test -z "$$report" || echo "$$report"; \ - echo "$$dashes$$std"; \ + echo "$${col}$$dashes$${std}"; \ + echo "$${col}$$banner$${std}"; \ + test -z "$$skipped" || echo "$${col}$$skipped$${std}"; \ + test -z "$$report" || echo "$${col}$$report$${std}"; \ + echo "$${col}$$dashes$${std}"; \ test "$$failed" -eq 0; \ else :; fi @@ -721,10 +837,15 @@ install-am: all-am installcheck: installcheck-am install-strip: - $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ - install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ - `test -z '$(STRIP)' || \ - echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi mostlyclean-generic: clean-generic: diff --git a/src/stream/perf_stream_api.c b/src/stream/perf_stream_api.c new file mode 100644 index 0000000..aa534ce --- /dev/null +++ b/src/stream/perf_stream_api.c @@ -0,0 +1,1047 @@ + /* + This file is part of GNUnet. + (C) 2011, 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @file stream/perf_stream_api.c + * @brief performance benchmarks for stream api + * @author Sree Harsha Totakura + */ + +#define LOG(kind, ...) \ + GNUNET_log (kind, __VA_ARGS__); + +/****************************************************************************************/ +/* Test is setup into the following major steps: */ +/* 1. Measurements over loopback (1 hop). i.e. we use only one peer and open */ +/* stream connections over loopback. Messages will go through */ +/* STREAM_API->MESH_API->MESH_SERVICE->MESH_API->STREAM_API. */ +/* 2. Measurements over 2 peers (2 hops). We use testbed to create 2 peers, */ +/* connect them and then create stream connections. Messages will go through */ +/* STREAM_API->MESH_API->MESH_SERVICE->CORE1.....CORE2->MESH_API->STREAM_API */ +/* 3. Measurements over 3 peers (3 hops). We use testbed to create 3 peers, */ +/* connect them in a line topology: peer1->peer2->peer3. Messages will go */ +/* through */ +/* STREAM_API->MESH_API->MESH_SERVICE->CORE1..CORE2..CORE3->MESH_API->STREAM_API. */ +/****************************************************************************************/ + +#include "platform.h" +#include "gnunet_common.h" +#include "gnunet_util_lib.h" +#include "gnunet_testbed_service.h" +#include "gnunet_stream_lib.h" + +/** + * Simple struct to keep track of progress, and print a + * nice little percentage meter for long running tasks. + */ +struct ProgressMeter +{ + unsigned int total; + + unsigned int modnum; + + unsigned int dotnum; + + unsigned int completed; + + int print; + + char *startup_string; +}; + + +/** + * Steps in testing + */ +enum TestStep +{ + /** + * Single hop loopback testing + */ + TEST_STEP_1_HOP, + + /** + * Testing with 2 peers + */ + TEST_STEP_2_HOP, + + /** + * Testing with 3 peers + */ + TEST_STEP_3_HOP +}; + + +/** + * Structure for holding peer's sockets and IO Handles + */ +struct PeerData +{ + /** + * Peer's stream socket + */ + struct GNUNET_STREAM_Socket *socket; + + /** + * Peer's io write handle + */ + struct GNUNET_STREAM_WriteHandle *io_write_handle; + + /** + * Peer's io read handle + */ + struct GNUNET_STREAM_ReadHandle *io_read_handle; + + /** + * The peer handle when we use the testbed servie + */ + struct GNUNET_TESTBED_Peer *peer; + + /** + * Handle to peer specific opearations while using testbed service + */ + struct GNUNET_TESTBED_Operation *op; + + /** + * The identity of this peer + */ + struct GNUNET_PeerIdentity id; + + /** + * Peer's shutdown handle + */ + struct GNUNET_STREAM_ShutdownHandle *shutdown_handle; + + /** + * Bytes the peer has written + */ + size_t bytes_wrote; + + /** + * Byte the peer has read + */ + size_t bytes_read; + + /** + * number of packets sent + */ + unsigned int packets_wrote; + + /** + * number of packets read + */ + unsigned int packets_read; +}; + + +/** + * Enumeration of stages in this testing + */ +enum TestStage +{ + /** + * The initial stage + */ + INIT, + + /** + * Uplink testing stage + */ + UPLINK_OK, + + /** + * Downlink testing stage + */ + DOWNLINK_OK +}; + + +/** + * Maximum size of the data which we will transfer during tests + */ +#define DATA_SIZE 5000000 /* 5mB */ + +/** + * Fixed number of packets we send in each direction during each subtest + */ +#define MAX_PACKETS 1000 + +/** + * Listen socket of peer2 + */ +struct GNUNET_STREAM_ListenSocket *peer2_listen_socket; + +/** + * Handle to configuration during TEST_STEP_1_HOP + */ +const struct GNUNET_CONFIGURATION_Handle *config; + +/** + * Handle for the progress meter + */ +static struct ProgressMeter *meter; + +/** + * Placeholder for peer data + */ +static struct PeerData peer_data[3]; + +/** + * Handle to common operations while using testbed + */ +static struct GNUNET_TESTBED_Operation *common_op; + +/** + * Task ID for abort task + */ +static GNUNET_SCHEDULER_TaskIdentifier abort_task; + +/** + * Task ID for write task + */ +static GNUNET_SCHEDULER_TaskIdentifier write_task; + +/** + * Task ID for read task + */ +static GNUNET_SCHEDULER_TaskIdentifier read_task; + +/** + * Absolute time when profiling starts + */ +static struct GNUNET_TIME_Absolute prof_start_time; + +/** + * Test time taken for sending the data + */ +static struct GNUNET_TIME_Relative prof_time; + +/** + * Random data block. Should generate data first + */ +static uint32_t data[DATA_SIZE / 4]; + +/** + * Payload sizes to test each major test with + */ +static uint16_t payload_size[] = +{ 20, 500, 2000, 7000, 13000, 25000, 30000};//, 50000, 60000, 63000, 64000 }; + +/** + * Current step of testing + */ +static enum TestStep test_step; + +/** + * Index for choosing payload size + */ +static unsigned int payload_size_index; + +/** + * Number of peers we want to create while using the testbed service + */ +static int num_peers; + +/** + * Flag to indicate that the other peer should reset its data read source index + */ +static int reset_read; + +/** + * Testing result of a major test + */ +static enum TestStage result; + +/** + * Create a meter to keep track of the progress of some task. + * + * @param total the total number of items to complete + * @param start_string a string to prefix the meter with (if printing) + * @param print GNUNET_YES to print the meter, GNUNET_NO to count + * internally only + * + * @return the progress meter + */ +static struct ProgressMeter * +create_meter (unsigned int total, char *start_string, int print) +{ + struct ProgressMeter *ret; + + ret = GNUNET_malloc (sizeof (struct ProgressMeter)); + ret->print = print; + ret->total = total; + ret->modnum = total / 4; + if (ret->modnum == 0) /* Divide by zero check */ + ret->modnum = 1; + ret->dotnum = (total / 50) + 1; + if (start_string != NULL) + ret->startup_string = GNUNET_strdup (start_string); + else + ret->startup_string = GNUNET_strdup (""); + + return ret; +} + + +/** + * Update progress meter (increment by one). + * + * @param meter the meter to update and print info for + * + * @return GNUNET_YES if called the total requested, + * GNUNET_NO if more items expected + */ +static int +update_meter (struct ProgressMeter *meter) +{ + if (meter->print == GNUNET_YES) + { + if (meter->completed % meter->modnum == 0) + { + if (meter->completed == 0) + { + FPRINTF (stdout, "%sProgress: [0%%", meter->startup_string); + } + else + FPRINTF (stdout, "%d%%", + (int) (((float) meter->completed / meter->total) * 100)); + } + else if (meter->completed % meter->dotnum == 0) + FPRINTF (stdout, "%s", "."); + + if (meter->completed + 1 == meter->total) + FPRINTF (stdout, "%d%%]\n", 100); + fflush (stdout); + } + meter->completed++; + + if (meter->completed == meter->total) + return GNUNET_YES; + if (meter->completed > meter->total) + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Progress meter overflow!!\n"); + return GNUNET_NO; +} + + +/** + * Reset progress meter. + * + * @param meter the meter to reset + * + * @return GNUNET_YES if meter reset, + * GNUNET_SYSERR on error + */ +static int +reset_meter (struct ProgressMeter *meter) +{ + if (meter == NULL) + return GNUNET_SYSERR; + + meter->completed = 0; + return GNUNET_YES; +} + + +/** + * Release resources for meter + * + * @param meter the meter to free + */ +static void +free_meter (struct ProgressMeter *meter) +{ + GNUNET_free_non_null (meter->startup_string); + GNUNET_free (meter); +} + + +/** + * Shutdown nicely + */ +static void +do_close (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + switch (test_step) + { + case TEST_STEP_1_HOP: + if (NULL != peer_data[0].socket) + GNUNET_STREAM_close (peer_data[0].socket); + if (NULL != peer_data[1].socket) + GNUNET_STREAM_close (peer_data[1].socket); + if (NULL != peer2_listen_socket) + GNUNET_STREAM_listen_close (peer2_listen_socket); /* Close listen socket */ + break; + case TEST_STEP_2_HOP: + if (NULL != peer_data[1].socket) + GNUNET_STREAM_close (peer_data[1].socket); + if (NULL != peer_data[0].op) + GNUNET_TESTBED_operation_done (peer_data[0].op); + if (NULL != peer_data[1].op) + GNUNET_TESTBED_operation_done (peer_data[1].op); + break; + case TEST_STEP_3_HOP: + GNUNET_break (0); + } + if (GNUNET_SCHEDULER_NO_TASK != abort_task) + GNUNET_SCHEDULER_cancel (abort_task); + if (GNUNET_SCHEDULER_NO_TASK != write_task) + GNUNET_SCHEDULER_cancel (write_task); + GNUNET_SCHEDULER_shutdown (); /* Shutdown this testcase */ + if (NULL != meter) + { + free_meter (meter); + meter = NULL; + } +} + + +/** + * Something went wrong and timed out. Kill everything and set error flag + */ +static void +do_abort (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + abort_task = GNUNET_SCHEDULER_NO_TASK; + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "test: ABORT\n"); + if (GNUNET_SCHEDULER_NO_TASK != read_task) + GNUNET_SCHEDULER_cancel (read_task); + result = GNUNET_SYSERR; + do_close (cls, tc); +} + + +/** + * Completion callback for shutdown + * + * @param cls the closure from GNUNET_STREAM_shutdown call + * @param operation the operation that was shutdown (SHUT_RD, SHUT_WR, + * SHUT_RDWR) + */ +static void +shutdown_completion (void *cls, + int operation) +{ + static int shutdowns; + + if (++shutdowns == 1) + { + peer_data[0].shutdown_handle = NULL; + peer_data[1].shutdown_handle = GNUNET_STREAM_shutdown (peer_data[1].socket, SHUT_RDWR, + &shutdown_completion, cls); + return; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "STREAM shutdown successful\n"); + GNUNET_SCHEDULER_add_now (&do_close, cls); +} + + +/** + * Shutdown sockets gracefully + */ +static void +do_shutdown (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + peer_data[0].shutdown_handle = GNUNET_STREAM_shutdown (peer_data[0].socket, SHUT_RDWR, + &shutdown_completion, cls); +} + + +/** + * Scheduler call back; to be executed when a new stream is connected + * Called from listen connect for peer2 + */ +static void +stream_read_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc); + + +/** + * Task for calling STREAM_write with a chunk of random data + * + * @param cls the peer data entity + * @param tc the task context + */ +static void +stream_write_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc); + + +/** + * The write completion function; called upon writing some data to stream or + * upon error + * + * @param cls the closure from GNUNET_STREAM_write/read + * @param status the status of the stream at the time this function is called + * @param size the number of bytes written + */ +static void +write_completion (void *cls, enum GNUNET_STREAM_Status status, size_t size) +{ + struct PeerData *pdata = cls; + double throughput; + double prof_time_sec; + unsigned int packets_wrote; + + if (GNUNET_STREAM_OK != status) + { + GNUNET_SCHEDULER_cancel (abort_task); + abort_task = GNUNET_SCHEDULER_add_now (&do_abort, NULL); + return; + } + GNUNET_assert (size <= DATA_SIZE); + packets_wrote = (size + payload_size[payload_size_index] - 1) + / payload_size[payload_size_index]; + pdata->bytes_wrote += size; + for (;packets_wrote > 0; packets_wrote--) + { + update_meter (meter); + pdata->packets_wrote++; + } + if (pdata->packets_wrote < MAX_PACKETS) /* Have more data to send */ + { + size_t write_amount; + + if (GNUNET_SCHEDULER_NO_TASK != abort_task) + { + GNUNET_SCHEDULER_cancel (abort_task); + abort_task = + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply + (GNUNET_TIME_UNIT_SECONDS, 300), &do_abort, + NULL); + } + write_amount = (MAX_PACKETS - pdata->packets_wrote) * + payload_size[payload_size_index]; + if (write_amount > DATA_SIZE) + write_amount = DATA_SIZE; + reset_read = GNUNET_YES; + pdata->io_write_handle = GNUNET_STREAM_write (pdata->socket, data, + write_amount, + GNUNET_TIME_UNIT_FOREVER_REL, + &write_completion, pdata); + GNUNET_assert (NULL != pdata->io_write_handle); + } + else + { + free_meter (meter); + meter = NULL; + prof_time = GNUNET_TIME_absolute_get_duration (prof_start_time); + prof_time_sec = (((double) prof_time.rel_value)/ ((double) 1000)); + throughput = ((float) pdata->bytes_wrote) / prof_time_sec; + PRINTF ("Throughput %.2f kB/sec\n", throughput / 1000.00); + switch (result) + { + case INIT: + result = UPLINK_OK; + GNUNET_assert (GNUNET_SCHEDULER_NO_TASK == read_task); + GNUNET_assert (GNUNET_SCHEDULER_NO_TASK == write_task); + pdata->bytes_read = 0; + pdata->packets_read = 0; + meter = create_meter (MAX_PACKETS, "Testing Downlink\n", GNUNET_YES); + read_task = GNUNET_SCHEDULER_add_now (&stream_read_task, &peer_data[0]); + write_task = GNUNET_SCHEDULER_add_now (&stream_write_task, &peer_data[1]); + break; + case UPLINK_OK: + result = DOWNLINK_OK; + GNUNET_SCHEDULER_add_now (&do_shutdown, NULL); + break; + case DOWNLINK_OK: + GNUNET_assert (0); + } + } +} + + +/** + * Task for calling STREAM_write with a chunk of random data + * + * @param cls the peer data entity + * @param tc the task context + */ +static void +stream_write_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct PeerData *pdata = cls; + size_t write_amount; + + if (GNUNET_SCHEDULER_NO_TASK != abort_task) + { + GNUNET_SCHEDULER_cancel (abort_task); + abort_task = + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply + (GNUNET_TIME_UNIT_SECONDS, 300), &do_abort, + NULL); + } + write_task = GNUNET_SCHEDULER_NO_TASK; + prof_start_time = GNUNET_TIME_absolute_get (); + pdata->bytes_wrote = 0; + pdata->packets_wrote = 0; + write_amount = MAX_PACKETS * payload_size[payload_size_index]; + if (write_amount > DATA_SIZE) + write_amount = DATA_SIZE; + reset_read = GNUNET_YES; + pdata->io_write_handle = GNUNET_STREAM_write (pdata->socket, data, + write_amount, + GNUNET_TIME_UNIT_FOREVER_REL, + &write_completion, pdata); + GNUNET_assert (NULL != pdata->io_write_handle); +} + + +/** + * Scheduler call back; to be executed when a new stream is connected + * Called from listen connect for peer2 + */ +static void +stream_read_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc); + + +/** + * Input processor + * + * @param cls peer2 + * @param status the status of the stream at the time this function is called + * @param data traffic from the other side + * @param size the number of bytes available in data read + * @return number of bytes of processed from 'data' (any data remaining should be + * given to the next time the read processor is called). + */ +static size_t +input_processor (void *cls, enum GNUNET_STREAM_Status status, + const void *input_data, size_t size) +{ + struct PeerData *pdata = cls; + + if (GNUNET_STREAM_OK != status) + { + GNUNET_SCHEDULER_cancel (abort_task); + abort_task = GNUNET_SCHEDULER_add_now (&do_abort, NULL); + return 0; + } + GNUNET_assert (size <= DATA_SIZE); + if (GNUNET_YES == reset_read) + { + pdata->bytes_read = 0; + reset_read = GNUNET_NO; + } + GNUNET_assert ((pdata->bytes_read + size) <= DATA_SIZE); + GNUNET_assert (0 == memcmp (((void *)data ) + pdata->bytes_read, + input_data, size)); + pdata->bytes_read += size; + pdata->packets_read += (size + payload_size[payload_size_index] - 1) + / payload_size[payload_size_index]; + if (pdata->packets_read < MAX_PACKETS) + { + GNUNET_assert (GNUNET_SCHEDULER_NO_TASK == read_task); + read_task = GNUNET_SCHEDULER_add_now (&stream_read_task, pdata); + } + else + { + LOG (GNUNET_ERROR_TYPE_DEBUG, "Reading finished successfully\n"); + } + return size; +} + + +/** + * Scheduler call back; to be executed when a new stream is connected + * Called from listen connect for peer2 + */ +static void +stream_read_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct PeerData *pdata = cls; + + read_task = GNUNET_SCHEDULER_NO_TASK; + pdata->io_read_handle = + GNUNET_STREAM_read (pdata->socket, GNUNET_TIME_UNIT_FOREVER_REL, + &input_processor, pdata); + GNUNET_assert (NULL != pdata->io_read_handle); +} + + +/** + * Functions of this type are called upon new stream connection from other peers + * + * @param cls the closure from GNUNET_STREAM_listen + * @param socket the socket representing the stream + * @param initiator the identity of the peer who wants to establish a stream + * with us + * @return GNUNET_OK to keep the socket open, GNUNET_SYSERR to close the + * stream (the socket will be invalid after the call) + */ +static int +stream_listen_cb (void *cls, struct GNUNET_STREAM_Socket *socket, + const struct GNUNET_PeerIdentity *initiator) +{ + struct PeerData *pdata = cls; + + + if ((NULL == socket) || (NULL == initiator)) + { + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Binding error\n"); + if (GNUNET_SCHEDULER_NO_TASK != abort_task) + GNUNET_SCHEDULER_cancel (abort_task); + abort_task = GNUNET_SCHEDULER_add_now (&do_abort, NULL); + return GNUNET_OK; + } + GNUNET_assert (NULL != socket); + GNUNET_assert (pdata == &peer_data[1]); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Peer connected: %s\n", + GNUNET_i2s(initiator)); + pdata->socket = socket; + pdata->bytes_read = 0; + read_task = GNUNET_SCHEDULER_add_now (&stream_read_task, pdata); + return GNUNET_OK; +} + + +/** + * Function executed after stream has been established + * + * @param cls the closure from GNUNET_STREAM_open + * @param socket socket to use to communicate with the other side (read/write) + */ +static void +stream_open_cb (void *cls, + struct GNUNET_STREAM_Socket *socket) +{ + struct PeerData *pdata = cls; + + GNUNET_assert (socket == pdata->socket); + meter = create_meter (MAX_PACKETS, "Testing Uplink\n", GNUNET_YES); + write_task = GNUNET_SCHEDULER_add_now (&stream_write_task, pdata); +} + + +/** + * Listen success callback; connects a peer to stream as client + */ +static void +stream_connect (void) +{ + peer_data[0].socket = + GNUNET_STREAM_open (config, &peer_data[1].id, 10, &stream_open_cb, + &peer_data[0], + GNUNET_STREAM_OPTION_MAX_PAYLOAD_SIZE, + payload_size[payload_size_index], + GNUNET_STREAM_OPTION_END); + GNUNET_assert (NULL != peer_data[0].socket); +} + + +/** + * Initialize framework and start test + * + * @param cls closure + * @param cfg configuration of the peer that was started + * @param peer identity of the peer that was created + */ +static void +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) +{ + struct GNUNET_PeerIdentity id; + + GNUNET_TESTING_peer_get_identity (peer, &id); + config = cfg; + peer2_listen_socket = + GNUNET_STREAM_listen (config, 10, &stream_listen_cb, &peer_data[1], + GNUNET_STREAM_OPTION_SIGNAL_LISTEN_SUCCESS, + &stream_connect, + GNUNET_STREAM_OPTION_MAX_PAYLOAD_SIZE, + payload_size[payload_size_index], + GNUNET_STREAM_OPTION_END); + GNUNET_assert (NULL != peer2_listen_socket); + peer_data[0].id = id; + peer_data[1].id = id; + abort_task = + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply + (GNUNET_TIME_UNIT_SECONDS, 300), &do_abort, + NULL); +} + + +/** + * Adapter function called to establish a connection to + * a service. + * + * @param cls closure + * @param cfg configuration of the peer to connect to; will be available until + * GNUNET_TESTBED_operation_done() is called on the operation returned + * from GNUNET_TESTBED_service_connect() + * @return service handle to return in 'op_result', NULL on error + */ +static void * +stream_ca (void *cls, const struct GNUNET_CONFIGURATION_Handle *cfg); + + +/** + * Adapter function called to destroy a connection to + * a service. + * + * @param cls closure + * @param op_result service handle returned from the connect adapter + */ +static void +stream_da (void *cls, void *op_result) +{ + if (&peer_data[1] == cls) + { + GNUNET_STREAM_listen_close (op_result); + return; + } + else if (&peer_data[0] == cls) + { + GNUNET_STREAM_close (op_result); + return; + } + GNUNET_assert (0); +} + + +/** + * Listen success callback; connects a peer to stream as client. Called from + * testbed stream_ca + */ +static void +stream_connect2 (void) +{ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stream listen open successful\n"); + peer_data[0].op = + GNUNET_TESTBED_service_connect (&peer_data[0], peer_data[0].peer, + "stream", NULL, NULL, stream_ca, + stream_da, &peer_data[0]); +} + + +/** + * Adapter function called to establish a connection to + * a service. + * + * @param cls closure + * @param cfg configuration of the peer to connect to; will be available until + * GNUNET_TESTBED_operation_done() is called on the operation returned + * from GNUNET_TESTBED_service_connect() + * @return service handle to return in 'op_result', NULL on error + */ +static void * +stream_ca (void *cls, const struct GNUNET_CONFIGURATION_Handle *cfg) +{ + struct PeerData *pdata = cls; + + if (&peer_data[1] == pdata) + { + peer2_listen_socket = NULL; + peer2_listen_socket = + GNUNET_STREAM_listen (cfg, 10, &stream_listen_cb, &peer_data[1], + GNUNET_STREAM_OPTION_SIGNAL_LISTEN_SUCCESS, + &stream_connect2, + GNUNET_STREAM_OPTION_MAX_PAYLOAD_SIZE, + payload_size[payload_size_index], + GNUNET_STREAM_OPTION_END); + GNUNET_assert (NULL != peer2_listen_socket); + return peer2_listen_socket; + } + if (&peer_data[0] == pdata) + { + pdata->socket = + GNUNET_STREAM_open (cfg, &peer_data[1].id, 10, &stream_open_cb, + &peer_data[0], + GNUNET_STREAM_OPTION_MAX_PAYLOAD_SIZE, + payload_size[payload_size_index], + GNUNET_STREAM_OPTION_END); + GNUNET_assert (NULL != pdata->socket); + return pdata->socket; + } + GNUNET_assert (0); + return NULL; +} + + +/** + * Callback to be called when the requested peer information is available + * + * @param cb_cls the closure from GNUNET_TETSBED_peer_get_information() + * @param op the operation this callback corresponds to + * @param pinfo the result; will be NULL if the operation has failed + * @param emsg error message if the operation has failed; will be NULL if the + * operation is successfull + */ +static void +peerinfo_cb (void *cb_cls, struct GNUNET_TESTBED_Operation *op, + const struct GNUNET_TESTBED_PeerInformation *pinfo, + const char *emsg) +{ + struct PeerData *pdata = cb_cls; + + GNUNET_assert (NULL == emsg); + GNUNET_assert (common_op == op); + GNUNET_assert (NULL != pdata); + memcpy (&pdata->id, pinfo->result.id, sizeof (struct GNUNET_PeerIdentity)); + GNUNET_TESTBED_operation_done (op); + if (pdata == &peer_data[0]) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Peer 1 id: %s\n", + GNUNET_i2s (&pdata->id)); + common_op = GNUNET_TESTBED_peer_get_information (peer_data[1].peer, + GNUNET_TESTBED_PIT_IDENTITY, + &peerinfo_cb, &peer_data[1]); + } + else if (pdata == &peer_data[1]) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Peer 2 id: %s\n", + GNUNET_i2s (&pdata->id)); + if (TEST_STEP_2_HOP == test_step) + peer_data[1].op = + GNUNET_TESTBED_service_connect (&peer_data[1], peer_data[1].peer, + "stream", NULL, NULL, stream_ca, + stream_da, &peer_data[1]); + else + GNUNET_break (0); /* FIXME: 3 hop test case here... */ + } +} + + +/** + * Controller event callback + * + * @param cls NULL + * @param event the controller event + */ +static void +controller_event_cb (void *cls, + const struct GNUNET_TESTBED_EventInformation *event) +{ + switch (event->type) + { + case GNUNET_TESTBED_ET_OPERATION_FINISHED: + if (NULL != event->details.operation_finished.emsg) + { + FPRINTF (stderr, "Error while expecting an operation to succeed:%s \n", + event->details.operation_finished.emsg); + GNUNET_assert (0); + } + break; + default: + GNUNET_assert (0); + } +} + + +/** + * Signature of a main function for a testcase. + * + * @param cls closure + * @param num_peers number of peers in 'peers' + * @param peers handle to peers run in the testbed + */ +static void +test_master (void *cls, unsigned int num_peers_, + struct GNUNET_TESTBED_Peer **peers) +{ + GNUNET_assert (NULL != peers); + GNUNET_assert (NULL != peers[0]); + GNUNET_assert (NULL != peers[1]); + GNUNET_assert (num_peers_ == num_peers); + peer_data[0].peer = peers[0]; + peer_data[1].peer = peers[1]; + if (2 == num_peers) + /* Get the peer identity and configuration of peers */ + common_op = + GNUNET_TESTBED_peer_get_information (peer_data[0].peer, + GNUNET_TESTBED_PIT_IDENTITY, + &peerinfo_cb, &peer_data[0]); + else + GNUNET_break (0); + abort_task = + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply + (GNUNET_TIME_UNIT_SECONDS, 120), &do_abort, + NULL); +} + + +/** + * Main function + */ +int main (int argc, char **argv) +{ + char *test_name = "perf_stream_api"; + char *cfg_file = "test_stream_local.conf"; + uint64_t event_mask; + unsigned int count; + int ret; + + meter = create_meter ((sizeof (data) / 4), "Generating random data\n", GNUNET_YES); + for (count=0; count < (sizeof (data) / 4); count++) + { + data[count] = GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK, + UINT32_MAX); + update_meter (meter); + } + reset_meter (meter); + free_meter (meter); + meter = NULL; + test_step = TEST_STEP_1_HOP; + for (payload_size_index = 0; + payload_size_index < (sizeof (payload_size) / sizeof (uint16_t)); + payload_size_index++) + { + PRINTF ("\nTesting over loopback with payload size %hu\n", + payload_size[payload_size_index]); + (void) memset (peer_data, 0, sizeof (peer_data)); + result = INIT; + reset_read = GNUNET_NO; + ret = GNUNET_TESTING_peer_run (test_name, cfg_file, &run, NULL); + if ((0 != ret) || (DOWNLINK_OK != result)) + goto return_fail; + } + test_step = TEST_STEP_2_HOP; + num_peers = 2; + event_mask = 0; + event_mask |= (1LL << GNUNET_TESTBED_ET_OPERATION_FINISHED); + for (payload_size_index = 0; + payload_size_index < (sizeof (payload_size) / sizeof (uint16_t)); + payload_size_index++) + { + PRINTF ("\nTesting over 1 hop with payload size %hu\n", + payload_size[payload_size_index]); + (void) memset (peer_data, 0, sizeof (peer_data)); + result = INIT; + reset_read = GNUNET_NO; + (void) GNUNET_TESTBED_test_run (test_name, cfg_file, num_peers, event_mask, + &controller_event_cb, NULL, &test_master, + NULL); + if (DOWNLINK_OK != result) + goto return_fail; + } + test_step = TEST_STEP_3_HOP; + for (payload_size_index = 0; + payload_size_index < (sizeof (payload_size) / sizeof (uint16_t)); + payload_size_index++) + { + /* Initialize testbed here */ + } + return 0; + + return_fail: + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Test failed\n"); + return 1; +} + +/* end of perf_stream_api.c */ diff --git a/src/stream/stream.h b/src/stream/stream.h new file mode 100644 index 0000000..9b92a28 --- /dev/null +++ b/src/stream/stream.h @@ -0,0 +1,190 @@ +/* + This file is part of GNUnet. + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @file stream/stream.h + * @brief P2P protocol for the stream connections + * @author Sree Harsha Totakura + */ + +#ifndef STREAM_H +#define STREAM_H + +#ifdef __cplusplus +extern "C" +{ +#if 0 /* keep Emacsens' auto-indent happy */ +} +#endif +#endif + +#include "gnunet_util_lib.h" + +GNUNET_NETWORK_STRUCT_BEGIN + + +/** + * The stream message header + * All messages of STREAM should commonly have this as header + */ +struct GNUNET_STREAM_MessageHeader +{ + /** + * The GNUNET message header, types are from GNUNET_MESSAGE_TYPE_STREAM_*-range. + */ + struct GNUNET_MessageHeader header; +}; + + +/** + * The Data message, should be prefixed with stream header with its type set to + * GNUNET_STREAM_Data + */ +struct GNUNET_STREAM_DataMessage +{ + + /** + * Type is GNUNET_MESSAGE_TYPE_STREAM_DATA + */ + struct GNUNET_STREAM_MessageHeader header; + + /** + * Sequence number; starts with a random value. (Just in case + * someone breaks mesh and is able to try to do a Sequence + * Prediction Attack on us.) + */ + uint32_t sequence_number GNUNET_PACKED; + + /** + * number of milliseconds to the soft deadline for sending acknowledgement + * measured from the time this message is received. It is optimal for the + * communication to send the ack within the soft deadline + */ + struct GNUNET_TIME_RelativeNBO ack_deadline; + + /** + * Offset of the packet in the overall stream, modulo 2^32; allows + * the receiver to calculate where in the destination buffer the + * message should be placed. In network byte order. + */ + uint32_t offset GNUNET_PACKED; + + /** + * The data should be appended here + */ +}; + + +/** + * Number of bits in GNUNET_STREAM_AckBitmap + */ +#define GNUNET_STREAM_ACK_BITMAP_BIT_LENGTH 64 + +/** + * The Selective Acknowledgement Bitmap + */ +typedef uint64_t GNUNET_STREAM_AckBitmap; + + +/** + * The Acknowledgment Message to confirm receipt of DATA. + */ +struct GNUNET_STREAM_AckMessage +{ + + /** + * Type is GNUNET_MESSAGE_TYPE_STREAM_ACK + */ + struct GNUNET_STREAM_MessageHeader header; + + /** + * The sequence number of the next Data Message receiver is + * anticipating. Data messages less than this number are received by receiver + */ + uint32_t base_sequence_number GNUNET_PACKED; + + /** + * The Selective Acknowledgement Bitmap. Computed relative to the base_seq + * (bit n corresponds to the Data message with sequence number base_seq+n) + */ + GNUNET_STREAM_AckBitmap bitmap GNUNET_PACKED; + + /** + * Available buffer space past the last acknowledged buffer (for flow control), + * in bytes. + */ + uint32_t receive_window_remaining GNUNET_PACKED; +}; + + +/** + * Message for Acknowledging HELLO + */ +struct GNUNET_STREAM_HelloAckMessage +{ + /** + * The stream message header + */ + struct GNUNET_STREAM_MessageHeader header; + + /** + * The selected sequence number. Following data tranmissions from the sender + * start with this sequence + */ + uint32_t sequence_number GNUNET_PACKED; + + /** + * The size(in bytes) of the receive window on the peer sending this message + * + * FIXME: Remove if not needed + */ + uint32_t receiver_window_size GNUNET_PACKED; +}; + + +/** + * The Transmit close message(used to signal transmission is closed) + * FIXME: dead struct? + */ +struct GNUNET_STREAM_TransmitCloseMessage +{ + /** + * The stream message header + */ + struct GNUNET_STREAM_MessageHeader header; + + /** + * The last sequence number of the packet after which the transmission has + * ended + */ + uint32_t final_sequence_number GNUNET_PACKED; +}; + +GNUNET_NETWORK_STRUCT_END + + +#if 0 /** keep Emacsens' auto-indent happy */ +{ +#endif +#ifdef __cplusplus +} +#endif + +#endif /* STREAM.H */ diff --git a/src/stream/stream_api.c b/src/stream/stream_api.c index dadba33..20df4aa 100644 --- a/src/stream/stream_api.c +++ b/src/stream/stream_api.c @@ -34,31 +34,41 @@ * @author Sree Harsha Totakura */ - #include "platform.h" #include "gnunet_common.h" -#include "gnunet_crypto_lib.h" +#include "gnunet_util_lib.h" +#include "gnunet_lockmanager_service.h" +#include "gnunet_statistics_service.h" #include "gnunet_stream_lib.h" -#include "stream_protocol.h" +#include "stream.h" +/** + * Generic logging shorthand + */ #define LOG(kind,...) \ GNUNET_log_from (kind, "stream-api", __VA_ARGS__) /** - * The maximum packet size of a stream packet + * Debug logging shorthand */ -#define MAX_PACKET_SIZE 64000 +#define LOG_DEBUG(...) \ + LOG (GNUNET_ERROR_TYPE_DEBUG, __VA_ARGS__) /** - * Receive buffer + * Time in relative seconds shorthand */ -#define RECEIVE_BUFFER_SIZE 4096000 +#define TIME_REL_SECS(sec) \ + GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, sec) /** - * The maximum payload a data message packet can carry + * The maximum packet size of a stream packet */ -static size_t max_payload_size = - MAX_PACKET_SIZE - sizeof (struct GNUNET_STREAM_DataMessage); +#define DEFAULT_MAX_PAYLOAD_SIZE 64000 + +/** + * Receive buffer + */ +#define RECEIVE_BUFFER_SIZE 4096000 /** * states in the Protocol @@ -165,29 +175,14 @@ struct MessageQueue struct GNUNET_STREAM_Socket { /** - * Retransmission timeout - */ - struct GNUNET_TIME_Relative retransmit_timeout; - - /** - * The Acknowledgement Bitmap - */ - GNUNET_STREAM_AckBitmap ack_bitmap; - - /** - * Time when the Acknowledgement was queued - */ - struct GNUNET_TIME_Absolute ack_time_registered; - - /** - * Queued Acknowledgement deadline + * The mesh handle */ - struct GNUNET_TIME_Relative ack_time_deadline; + struct GNUNET_MESH_Handle *mesh; /** - * The mesh handle + * Handle to statistics */ - struct GNUNET_MESH_Handle *mesh; + struct GNUNET_STATISTICS_Handle *stat_handle; /** * The mesh tunnel handle @@ -209,16 +204,6 @@ struct GNUNET_STREAM_Socket */ struct GNUNET_MESH_TransmitHandle *transmit_handle; - /** - * The current act transmit handle (if a pending ack transmit request exists) - */ - struct GNUNET_MESH_TransmitHandle *ack_transmit_handle; - - /** - * Pointer to the current ack message using in ack_task - */ - struct GNUNET_STREAM_AckMessage *ack_msg; - /** * The current message associated with the transmit handle */ @@ -232,12 +217,12 @@ struct GNUNET_STREAM_Socket /** * The write IO_handle associated with this socket */ - struct GNUNET_STREAM_IOWriteHandle *write_handle; + struct GNUNET_STREAM_WriteHandle *write_handle; /** * The read IO_handle associated with this socket */ - struct GNUNET_STREAM_IOReadHandle *read_handle; + struct GNUNET_STREAM_ReadHandle *read_handle; /** * The shutdown handle associated with this socket @@ -261,14 +246,19 @@ struct GNUNET_STREAM_Socket struct GNUNET_PeerIdentity other_peer; /** - * Task identifier for the read io timeout task + * The Acknowledgement Bitmap */ - GNUNET_SCHEDULER_TaskIdentifier read_io_timeout_task_id; + GNUNET_STREAM_AckBitmap ack_bitmap; /** * Task identifier for retransmission task after timeout */ - GNUNET_SCHEDULER_TaskIdentifier retransmission_timeout_task_id; + GNUNET_SCHEDULER_TaskIdentifier data_retransmission_task_id; + + /** + * Task identifier for retransmission of control messages + */ + GNUNET_SCHEDULER_TaskIdentifier control_retransmission_task_id; /** * The task for sending timely Acks @@ -276,9 +266,29 @@ struct GNUNET_STREAM_Socket GNUNET_SCHEDULER_TaskIdentifier ack_task_id; /** - * Task scheduled to continue a read operation. + * Retransmission timeout */ - GNUNET_SCHEDULER_TaskIdentifier read_task_id; + struct GNUNET_TIME_Relative retransmit_timeout; + + /** + * Time when the Acknowledgement was queued + */ + struct GNUNET_TIME_Absolute ack_time_registered; + + /** + * Queued Acknowledgement deadline + */ + struct GNUNET_TIME_Relative ack_time_deadline; + + /** + * Mesh transmit timeout + */ + struct GNUNET_TIME_Relative mesh_retry_timeout; + + /** + * Data retransmission timeout + */ + struct GNUNET_TIME_Relative data_retransmit_timeout; /** * The state of the protocol associated with this socket @@ -286,14 +296,19 @@ struct GNUNET_STREAM_Socket enum State state; /** - * The status of the socket + * Whether testing mode is active or not + */ + int testing_active; + + /** + * Is receive closed */ - enum GNUNET_STREAM_Status status; + int receive_closed; /** - * The number of previous timeouts; FIXME: currently not used + * Is transmission closed */ - unsigned int retries; + int transmit_closed; /** * The application port number (type: uint32_t) @@ -301,10 +316,9 @@ struct GNUNET_STREAM_Socket GNUNET_MESH_ApplicationType app_port; /** - * The session id associated with this stream connection - * FIXME: Not used currently, may be removed + * The write sequence number to be set incase of testing */ - uint32_t session_id; + uint32_t testing_set_write_sequence_number_value; /** * Write sequence number. Set to random when sending HELLO(client) and @@ -346,6 +360,11 @@ struct GNUNET_STREAM_Socket * The offset upto which user has read from the received buffer */ uint32_t copy_offset; + + /** + * The maximum size of the data message payload this stream handle can send + */ + uint16_t max_payload_size; }; @@ -359,6 +378,31 @@ struct GNUNET_STREAM_ListenSocket */ struct GNUNET_MESH_Handle *mesh; + /** + * Handle to statistics + */ + struct GNUNET_STATISTICS_Handle *stat_handle; + + /** + * Our configuration + */ + struct GNUNET_CONFIGURATION_Handle *cfg; + + /** + * Handle to the lock manager service + */ + struct GNUNET_LOCKMANAGER_Handle *lockmanager; + + /** + * The active LockingRequest from lockmanager + */ + struct GNUNET_LOCKMANAGER_LockingRequest *locking_request; + + /** + * Callback to call after acquring a lock and listening + */ + GNUNET_STREAM_ListenSuccessCallback listen_ok_cb; + /** * The callback function which is called after successful opening socket */ @@ -371,27 +415,52 @@ struct GNUNET_STREAM_ListenSocket /** * The service port - * FIXME: Remove if not required! */ GNUNET_MESH_ApplicationType port; + + /** + * The id of the lockmanager timeout task + */ + GNUNET_SCHEDULER_TaskIdentifier lockmanager_acquire_timeout_task; + + /** + * The retransmit timeout + */ + struct GNUNET_TIME_Relative retransmit_timeout; + + /** + * Listen enabled? + */ + int listening; + + /** + * Whether testing mode is active or not + */ + int testing_active; + + /** + * The write sequence number to be set incase of testing + */ + uint32_t testing_set_write_sequence_number_value; + + /** + * The maximum size of the data message payload this stream handle can send + */ + uint16_t max_payload_size; + }; /** * The IO Write Handle */ -struct GNUNET_STREAM_IOWriteHandle +struct GNUNET_STREAM_WriteHandle { /** * The socket to which this write handle is associated */ struct GNUNET_STREAM_Socket *socket; - /** - * The packet_buffers associated with this Handle - */ - struct GNUNET_STREAM_DataMessage *messages[GNUNET_STREAM_ACK_BITMAP_BIT_LENGTH]; - /** * The write continuation callback */ @@ -402,6 +471,11 @@ struct GNUNET_STREAM_IOWriteHandle */ void *write_cont_cls; + /** + * The packet_buffers associated with this Handle + */ + struct GNUNET_STREAM_DataMessage *messages[GNUNET_STREAM_ACK_BITMAP_BIT_LENGTH]; + /** * The bitmap of this IOHandle; Corresponding bit for a message is set when * it has been acknowledged by the receiver @@ -412,14 +486,33 @@ struct GNUNET_STREAM_IOWriteHandle * Number of bytes in this write handle */ size_t size; + + /** + * Number of packets already transmitted from this IO handle. Retransmitted + * packets are not taken into account here. This is used to determine which + * packets account for retransmission and which packets occupy buffer space at + * the receiver. + */ + unsigned int packets_sent; + + /** + * The maximum of the base numbers of the received acks + */ + uint32_t max_ack_base_num; + }; /** * The IO Read Handle */ -struct GNUNET_STREAM_IOReadHandle +struct GNUNET_STREAM_ReadHandle { + /** + * The socket to which this read handle is associated + */ + struct GNUNET_STREAM_Socket *socket; + /** * Callback for the read processor */ @@ -429,6 +522,22 @@ struct GNUNET_STREAM_IOReadHandle * The closure pointer for the read processor callback */ void *proc_cls; + + /** + * Task identifier for the read io timeout task + */ + GNUNET_SCHEDULER_TaskIdentifier read_io_timeout_task_id; + + /** + * Task scheduled to continue a read operation. + */ + GNUNET_SCHEDULER_TaskIdentifier read_task_id; + + /** + * Task scheduled from GNUNET_STREAM_read() to lookup the ACK bitmap and call + * the read processor task + */ + GNUNET_SCHEDULER_TaskIdentifier probe_data_availability_task_id; }; @@ -457,6 +566,11 @@ struct GNUNET_STREAM_ShutdownHandle */ GNUNET_SCHEDULER_TaskIdentifier close_msg_retransmission_task_id; + /** + * Task scheduled to call the shutdown continuation callback + */ + GNUNET_SCHEDULER_TaskIdentifier call_cont_task_id; + /** * Which operation to shutdown? SHUT_RD, SHUT_WR or SHUT_RDWR */ @@ -467,8 +581,12 @@ struct GNUNET_STREAM_ShutdownHandle /** * Default value in seconds for various timeouts */ -static unsigned int default_timeout = 10; +static const unsigned int default_timeout = 10; +/** + * The domain name for locks we use here + */ +static const char *locking_domain = "GNUNET_STREAM_APPLOCK"; /** * Callback function for sending queued message @@ -491,24 +609,23 @@ send_message_notify (void *cls, size_t size, void *buf) return 0; /* just to be safe */ if (0 == size) /* request timed out */ { - socket->retries++; + socket->mesh_retry_timeout = GNUNET_TIME_STD_BACKOFF + (socket->mesh_retry_timeout); LOG (GNUNET_ERROR_TYPE_DEBUG, - "%s: Message sending timed out. Retry %d \n", + "%s: Message sending to MESH timed out. Retrying in %s \n", GNUNET_i2s (&socket->other_peer), - socket->retries); + GNUNET_STRINGS_relative_time_to_string (socket->mesh_retry_timeout, + GNUNET_YES)); socket->transmit_handle = - GNUNET_MESH_notify_transmit_ready (socket->tunnel, - 0, /* Corking */ - 1, /* Priority */ - /* FIXME: exponential backoff */ - socket->retransmit_timeout, - &socket->other_peer, - ntohs (head->message->header.size), - &send_message_notify, - socket); + GNUNET_MESH_notify_transmit_ready (socket->tunnel, + GNUNET_NO, /* Corking */ + socket->mesh_retry_timeout, + &socket->other_peer, + ntohs (head->message->header.size), + &send_message_notify, + socket); return 0; } - ret = ntohs (head->message->header.size); GNUNET_assert (size >= ret); memcpy (buf, head->message, ret); @@ -521,20 +638,20 @@ send_message_notify (void *cls, size_t size, void *buf) head); GNUNET_free (head->message); GNUNET_free (head); + if (NULL != socket->transmit_handle) + return ret; /* 'finish_cb' might have triggered message already! */ head = socket->queue_head; if (NULL != head) /* more pending messages to send */ { - socket->retries = 0; + socket->mesh_retry_timeout = GNUNET_TIME_UNIT_ZERO; socket->transmit_handle = - GNUNET_MESH_notify_transmit_ready (socket->tunnel, - 0, /* Corking */ - 1, /* Priority */ - /* FIXME: exponential backoff */ - socket->retransmit_timeout, - &socket->other_peer, - ntohs (head->message->header.size), - &send_message_notify, - socket); + GNUNET_MESH_notify_transmit_ready (socket->tunnel, + GNUNET_NO, /* Corking */ + socket->mesh_retry_timeout, + &socket->other_peer, + ntohs (head->message->header.size), + &send_message_notify, + socket); } return ret; } @@ -547,19 +664,21 @@ send_message_notify (void *cls, size_t size, void *buf) * @param message the message to be sent * @param finish_cb the callback to be called when the message is sent * @param finish_cb_cls the closure for the callback + * @param urgent set to GNUNET_YES to add the message to the beginning of the + * queue; GNUNET_NO to add at the tail */ static void queue_message (struct GNUNET_STREAM_Socket *socket, struct GNUNET_STREAM_MessageHeader *message, SendFinishCallback finish_cb, - void *finish_cb_cls) + void *finish_cb_cls, + int urgent) { struct MessageQueue *queue_entity; GNUNET_assert ((ntohs (message->header.type) >= GNUNET_MESSAGE_TYPE_STREAM_DATA) && (ntohs (message->header.type) <= GNUNET_MESSAGE_TYPE_STREAM_CLOSE_ACK)); - LOG (GNUNET_ERROR_TYPE_DEBUG, "%s: Queueing message of type %d and size %d\n", GNUNET_i2s (&socket->other_peer), @@ -570,21 +689,31 @@ queue_message (struct GNUNET_STREAM_Socket *socket, queue_entity->message = message; queue_entity->finish_cb = finish_cb; queue_entity->finish_cb_cls = finish_cb_cls; - GNUNET_CONTAINER_DLL_insert_tail (socket->queue_head, - socket->queue_tail, - queue_entity); + if (GNUNET_YES == urgent) + { + GNUNET_CONTAINER_DLL_insert (socket->queue_head, socket->queue_tail, + queue_entity); + if (NULL != socket->transmit_handle) + { + GNUNET_MESH_notify_transmit_ready_cancel (socket->transmit_handle); + socket->transmit_handle = NULL; + } + } + else + GNUNET_CONTAINER_DLL_insert_tail (socket->queue_head, + socket->queue_tail, + queue_entity); if (NULL == socket->transmit_handle) { - socket->retries = 0; + socket->mesh_retry_timeout = GNUNET_TIME_UNIT_ZERO; socket->transmit_handle = - GNUNET_MESH_notify_transmit_ready (socket->tunnel, - 0, /* Corking */ - 1, /* Priority */ - socket->retransmit_timeout, - &socket->other_peer, - ntohs (message->header.size), - &send_message_notify, - socket); + GNUNET_MESH_notify_transmit_ready (socket->tunnel, + GNUNET_NO, /* Corking */ + socket->mesh_retry_timeout, + &socket->other_peer, + ntohs (message->header.size), + &send_message_notify, + socket); } } @@ -610,40 +739,10 @@ copy_and_queue_message (struct GNUNET_STREAM_Socket *socket, size = ntohs (message->header.size); msg_copy = GNUNET_malloc (size); memcpy (msg_copy, message, size); - queue_message (socket, msg_copy, finish_cb, finish_cb_cls); + queue_message (socket, msg_copy, finish_cb, finish_cb_cls, GNUNET_NO); } -/** - * Callback function for sending ack message - * - * @param cls closure the ACK message created in ack_task - * @param size number of bytes available in buffer - * @param buf where the callee should write the message - * @return number of bytes written to buf - */ -static size_t -send_ack_notify (void *cls, size_t size, void *buf) -{ - struct GNUNET_STREAM_Socket *socket = cls; - - if (0 == size) - { - LOG (GNUNET_ERROR_TYPE_DEBUG, - "%s called with size 0\n", __func__); - return 0; - } - GNUNET_assert (ntohs (socket->ack_msg->header.header.size) <= size); - - size = ntohs (socket->ack_msg->header.header.size); - memcpy (buf, socket->ack_msg, size); - - GNUNET_free (socket->ack_msg); - socket->ack_msg = NULL; - socket->ack_transmit_handle = NULL; - return size; -} - /** * Writes data using the given socket. The amount of data written is limited by * the receiver_window_size @@ -653,6 +752,7 @@ send_ack_notify (void *cls, size_t size, void *buf) static void write_data (struct GNUNET_STREAM_Socket *socket); + /** * Task for retransmitting data messages if they aren't ACK before their ack * deadline @@ -661,17 +761,16 @@ write_data (struct GNUNET_STREAM_Socket *socket); * @param tc the Task context */ static void -retransmission_timeout_task (void *cls, - const struct GNUNET_SCHEDULER_TaskContext *tc) +data_retransmission_task (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) { struct GNUNET_STREAM_Socket *socket = cls; - if (GNUNET_SCHEDULER_REASON_SHUTDOWN == tc->reason) + socket->data_retransmission_task_id = GNUNET_SCHEDULER_NO_TASK; + if (0 != (GNUNET_SCHEDULER_REASON_SHUTDOWN & tc->reason)) return; - LOG (GNUNET_ERROR_TYPE_DEBUG, "%s: Retransmitting DATA...\n", GNUNET_i2s (&socket->other_peer)); - socket->retransmission_timeout_task_id = GNUNET_SCHEDULER_NO_TASK; write_data (socket); } @@ -689,11 +788,9 @@ ack_task (void *cls, struct GNUNET_STREAM_Socket *socket = cls; struct GNUNET_STREAM_AckMessage *ack_msg; - if (GNUNET_SCHEDULER_REASON_SHUTDOWN == tc->reason) - { - return; - } socket->ack_task_id = GNUNET_SCHEDULER_NO_TASK; + if (0 != (GNUNET_SCHEDULER_REASON_SHUTDOWN & tc->reason)) + return; /* Create the ACK Message */ ack_msg = GNUNET_malloc (sizeof (struct GNUNET_STREAM_AckMessage)); ack_msg->header.header.size = htons (sizeof (struct @@ -703,17 +800,8 @@ ack_task (void *cls, ack_msg->base_sequence_number = htonl (socket->read_sequence_number); ack_msg->receive_window_remaining = htonl (RECEIVE_BUFFER_SIZE - socket->receive_buffer_size); - socket->ack_msg = ack_msg; - /* Request MESH for sending ACK */ - socket->ack_transmit_handle = - GNUNET_MESH_notify_transmit_ready (socket->tunnel, - 0, /* Corking */ - 1, /* Priority */ - socket->retransmit_timeout, - &socket->other_peer, - ntohs (ack_msg->header.header.size), - &send_ack_notify, - socket); + /* Queue up ACK for immediate sending */ + queue_message (socket, &ack_msg->header, NULL, NULL, GNUNET_YES); } @@ -731,9 +819,11 @@ close_msg_retransmission_task (void *cls, struct GNUNET_STREAM_MessageHeader *msg; struct GNUNET_STREAM_Socket *socket; + shutdown_handle->close_msg_retransmission_task_id = GNUNET_SCHEDULER_NO_TASK; GNUNET_assert (NULL != shutdown_handle); + if (0 != (GNUNET_SCHEDULER_REASON_SHUTDOWN & tc->reason)) + return; socket = shutdown_handle->socket; - msg = GNUNET_malloc (sizeof (struct GNUNET_STREAM_MessageHeader)); msg->header.size = htons (sizeof (struct GNUNET_STREAM_MessageHeader)); switch (shutdown_handle->operation) @@ -753,7 +843,7 @@ close_msg_retransmission_task (void *cls, GNUNET_SCHEDULER_NO_TASK; return; } - queue_message (socket, msg, NULL, NULL); + queue_message (socket, msg, NULL, NULL, GNUNET_NO); shutdown_handle->close_msg_retransmission_task_id = GNUNET_SCHEDULER_add_delayed (socket->retransmit_timeout, &close_msg_retransmission_task, @@ -806,41 +896,29 @@ ackbitmap_is_bit_set (const GNUNET_STREAM_AckBitmap *bitmap, static void write_data (struct GNUNET_STREAM_Socket *socket) { - struct GNUNET_STREAM_IOWriteHandle *io_handle = socket->write_handle; - int packet; /* Although an int, should never be negative */ - int ack_packet; - - ack_packet = -1; - /* Find the last acknowledged packet */ - for (packet=0; packet < GNUNET_STREAM_ACK_BITMAP_BIT_LENGTH; packet++) - { - if (GNUNET_YES == ackbitmap_is_bit_set (&io_handle->ack_bitmap, - packet)) - ack_packet = packet; - else if (NULL == io_handle->messages[packet]) - break; - } - /* Resend packets which weren't ack'ed */ - for (packet=0; packet < ack_packet; packet++) + struct GNUNET_STREAM_WriteHandle *io_handle = socket->write_handle; + unsigned int packet; + + for (packet=0; packet < io_handle->packets_sent; packet++) { if (GNUNET_NO == ackbitmap_is_bit_set (&io_handle->ack_bitmap, - packet)) + packet)) { LOG (GNUNET_ERROR_TYPE_DEBUG, - "%s: Placing DATA message with sequence %u in send queue\n", - GNUNET_i2s (&socket->other_peer), - ntohl (io_handle->messages[packet]->sequence_number)); + "%s: Retransmitting DATA message with sequence %u\n", + GNUNET_i2s (&socket->other_peer), + ntohl (io_handle->messages[packet]->sequence_number)); copy_and_queue_message (socket, - &io_handle->messages[packet]->header, - NULL, - NULL); + &io_handle->messages[packet]->header, + NULL, + NULL); } } - packet = ack_packet + 1; /* Now send new packets if there is enough buffer space */ - while ( (NULL != io_handle->messages[packet]) && - (socket->receiver_window_available - >= ntohs (io_handle->messages[packet]->header.header.size)) ) + while ((packet < GNUNET_STREAM_ACK_BITMAP_BIT_LENGTH) && + (NULL != io_handle->messages[packet]) && + (socket->receiver_window_available + >= ntohs (io_handle->messages[packet]->header.header.size))) { socket->receiver_window_available -= ntohs (io_handle->messages[packet]->header.header.size); @@ -854,12 +932,42 @@ write_data (struct GNUNET_STREAM_Socket *socket) NULL); packet++; } - if (GNUNET_SCHEDULER_NO_TASK == socket->retransmission_timeout_task_id) - socket->retransmission_timeout_task_id = - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply - (GNUNET_TIME_UNIT_SECONDS, 8), - &retransmission_timeout_task, - socket); + io_handle->packets_sent = packet; + if (GNUNET_SCHEDULER_NO_TASK == socket->data_retransmission_task_id) + { + socket->data_retransmit_timeout = GNUNET_TIME_STD_BACKOFF + (socket->data_retransmit_timeout); + socket->data_retransmission_task_id = + GNUNET_SCHEDULER_add_delayed (socket->data_retransmit_timeout, + &data_retransmission_task, + socket); + } +} + + +/** + * Cleansup the sockets read handle + * + * @param socket the socket whose read handle has to be cleanedup + */ +static void +cleanup_read_handle (struct GNUNET_STREAM_Socket *socket) +{ + struct GNUNET_STREAM_ReadHandle *read_handle; + + read_handle = socket->read_handle; + /* Read io time task should be there; if it is already executed then this + read handle is not valid; However upon scheduler shutdown the read io task + may be executed before */ + if (GNUNET_SCHEDULER_NO_TASK != read_handle->read_io_timeout_task_id) + GNUNET_SCHEDULER_cancel (read_handle->read_io_timeout_task_id); + /* reading task may be present; if so we have to stop it */ + if (GNUNET_SCHEDULER_NO_TASK != read_handle->read_task_id) + GNUNET_SCHEDULER_cancel (read_handle->read_task_id); + if (GNUNET_SCHEDULER_NO_TASK != read_handle->probe_data_availability_task_id) + GNUNET_SCHEDULER_cancel (read_handle->probe_data_availability_task_id); + GNUNET_free (read_handle); + socket->read_handle = NULL; } @@ -874,22 +982,23 @@ call_read_processor (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { struct GNUNET_STREAM_Socket *socket = cls; + struct GNUNET_STREAM_ReadHandle *read_handle; + GNUNET_STREAM_DataProcessor proc; + void *proc_cls; size_t read_size; size_t valid_read_size; unsigned int packet; uint32_t sequence_increase; uint32_t offset_increase; - socket->read_task_id = GNUNET_SCHEDULER_NO_TASK; + read_handle = socket->read_handle; + GNUNET_assert (NULL != read_handle); + read_handle->read_task_id = GNUNET_SCHEDULER_NO_TASK; if (0 != (tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN)) return; - if (NULL == socket->receive_buffer) return; - - GNUNET_assert (NULL != socket->read_handle); - GNUNET_assert (NULL != socket->read_handle->proc); - + GNUNET_assert (NULL != read_handle->proc); /* Check the bitmap for any holes */ for (packet=0; packet < GNUNET_STREAM_ACK_BITMAP_BIT_LENGTH; packet++) { @@ -902,51 +1011,46 @@ call_read_processor (void *cls, valid_read_size = socket->receive_buffer_boundaries[packet-1] - socket->copy_offset; GNUNET_assert (0 != valid_read_size); - /* Cancel the read_io_timeout_task */ - GNUNET_SCHEDULER_cancel (socket->read_io_timeout_task_id); - socket->read_io_timeout_task_id = GNUNET_SCHEDULER_NO_TASK; + proc = read_handle->proc; + proc_cls = read_handle->proc_cls; + cleanup_read_handle (socket); /* Call the data processor */ - LOG (GNUNET_ERROR_TYPE_DEBUG, - "%s: Calling read processor\n", + LOG (GNUNET_ERROR_TYPE_DEBUG, "%s: Calling read processor\n", GNUNET_i2s (&socket->other_peer)); - read_size = - socket->read_handle->proc (socket->read_handle->proc_cls, - socket->status, - socket->receive_buffer + socket->copy_offset, - valid_read_size); - LOG (GNUNET_ERROR_TYPE_DEBUG, - "%s: Read processor read %d bytes\n", + read_size = proc (proc_cls, GNUNET_STREAM_OK, + socket->receive_buffer + socket->copy_offset, + valid_read_size); + LOG (GNUNET_ERROR_TYPE_DEBUG, "%s: Read processor read %d bytes\n", GNUNET_i2s (&socket->other_peer), read_size); - LOG (GNUNET_ERROR_TYPE_DEBUG, - "%s: Read processor completed successfully\n", + LOG (GNUNET_ERROR_TYPE_DEBUG, "%s: Read processor completed successfully\n", GNUNET_i2s (&socket->other_peer)); - /* Free the read handle */ - GNUNET_free (socket->read_handle); - socket->read_handle = NULL; GNUNET_assert (read_size <= valid_read_size); socket->copy_offset += read_size; /* Determine upto which packet we can remove from the buffer */ for (packet = 0; packet < GNUNET_STREAM_ACK_BITMAP_BIT_LENGTH; packet++) { if (socket->copy_offset == socket->receive_buffer_boundaries[packet]) - { packet++; break; } + { + packet++; + break; + } if (socket->copy_offset < socket->receive_buffer_boundaries[packet]) break; } - /* If no packets can be removed we can't move the buffer */ - if (0 == packet) return; + if (0 == packet) + return; sequence_increase = packet; LOG (GNUNET_ERROR_TYPE_DEBUG, "%s: Sequence increase after read processor completion: %u\n", GNUNET_i2s (&socket->other_peer), sequence_increase); - /* Shift the data in the receive buffer */ - memmove (socket->receive_buffer, - socket->receive_buffer - + socket->receive_buffer_boundaries[sequence_increase-1], - socket->receive_buffer_size - - socket->receive_buffer_boundaries[sequence_increase-1]); + socket->receive_buffer = + memmove (socket->receive_buffer, + socket->receive_buffer + + socket->receive_buffer_boundaries[sequence_increase-1], + socket->receive_buffer_size + - socket->receive_buffer_boundaries[sequence_increase-1]); /* Shift the bitmap */ socket->ack_bitmap = socket->ack_bitmap >> sequence_increase; /* Set read_sequence_number */ @@ -960,11 +1064,20 @@ call_read_processor (void *cls, /* Fix relative boundaries */ for (packet=0; packet < GNUNET_STREAM_ACK_BITMAP_BIT_LENGTH; packet++) { - if (packet < GNUNET_STREAM_ACK_BITMAP_BIT_LENGTH - sequence_increase) + if (packet < (GNUNET_STREAM_ACK_BITMAP_BIT_LENGTH - sequence_increase)) { - socket->receive_buffer_boundaries[packet] = - socket->receive_buffer_boundaries[packet + sequence_increase] - - offset_increase; + uint32_t ahead_buffer_boundary; + + ahead_buffer_boundary = + socket->receive_buffer_boundaries[packet + sequence_increase]; + if (0 == ahead_buffer_boundary) + socket->receive_buffer_boundaries[packet] = 0; + else + { + GNUNET_assert (offset_increase < ahead_buffer_boundary); + socket->receive_buffer_boundaries[packet] = + ahead_buffer_boundary - offset_increase; + } } else socket->receive_buffer_boundaries[packet] = 0; @@ -979,27 +1092,30 @@ call_read_processor (void *cls, * @param tc the task context */ static void -read_io_timeout (void *cls, +read_io_timeout (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { struct GNUNET_STREAM_Socket *socket = cls; + struct GNUNET_STREAM_ReadHandle *read_handle; GNUNET_STREAM_DataProcessor proc; void *proc_cls; - socket->read_io_timeout_task_id = GNUNET_SCHEDULER_NO_TASK; - if (socket->read_task_id != GNUNET_SCHEDULER_NO_TASK) + read_handle = socket->read_handle; + GNUNET_assert (NULL != read_handle); + read_handle->read_io_timeout_task_id = GNUNET_SCHEDULER_NO_TASK; + if (0 != (GNUNET_SCHEDULER_REASON_SHUTDOWN & tc->reason)) + return; + if (read_handle->read_task_id != GNUNET_SCHEDULER_NO_TASK) { LOG (GNUNET_ERROR_TYPE_DEBUG, "%s: Read task timedout - Cancelling it\n", GNUNET_i2s (&socket->other_peer)); - GNUNET_SCHEDULER_cancel (socket->read_task_id); - socket->read_task_id = GNUNET_SCHEDULER_NO_TASK; + GNUNET_SCHEDULER_cancel (read_handle->read_task_id); + read_handle->read_task_id = GNUNET_SCHEDULER_NO_TASK; } - GNUNET_assert (NULL != socket->read_handle); - proc = socket->read_handle->proc; - proc_cls = socket->read_handle->proc_cls; - - GNUNET_free (socket->read_handle); + proc = read_handle->proc; + proc_cls = read_handle->proc_cls; + GNUNET_free (read_handle); socket->read_handle = NULL; /* Call the read processor to signal timeout */ proc (proc_cls, @@ -1028,6 +1144,7 @@ handle_data (struct GNUNET_STREAM_Socket *socket, const struct GNUNET_ATS_Information*atsi) { const void *payload; + struct GNUNET_TIME_Relative ack_deadline_rel; uint32_t bytes_needed; uint32_t relative_offset; uint32_t relative_sequence_number; @@ -1039,28 +1156,24 @@ handle_data (struct GNUNET_STREAM_Socket *socket, GNUNET_break_op (0); return GNUNET_SYSERR; } - - if (0 != memcmp (sender, - &socket->other_peer, - sizeof (struct GNUNET_PeerIdentity))) + if (0 != memcmp (sender, &socket->other_peer, + sizeof (struct GNUNET_PeerIdentity))) { LOG (GNUNET_ERROR_TYPE_DEBUG, - "%s: Received DATA from non-confirming peer\n", - GNUNET_i2s (&socket->other_peer)); + "%s: Received DATA from non-confirming peer\n", + GNUNET_i2s (&socket->other_peer)); return GNUNET_YES; } - switch (socket->state) { case STATE_ESTABLISHED: case STATE_TRANSMIT_CLOSED: - case STATE_TRANSMIT_CLOSE_WAIT: - + case STATE_TRANSMIT_CLOSE_WAIT: /* check if the message's sequence number is in the range we are expecting */ relative_sequence_number = ntohl (msg->sequence_number) - socket->read_sequence_number; - if ( relative_sequence_number > GNUNET_STREAM_ACK_BITMAP_BIT_LENGTH) + if ( relative_sequence_number >= GNUNET_STREAM_ACK_BITMAP_BIT_LENGTH) { LOG (GNUNET_ERROR_TYPE_DEBUG, "%s: Ignoring received message with sequence number %u\n", @@ -1076,8 +1189,7 @@ handle_data (struct GNUNET_STREAM_Socket *socket, socket); } return GNUNET_YES; - } - + } /* Check if we have already seen this message */ if (GNUNET_YES == ackbitmap_is_bit_set (&socket->ack_bitmap, relative_sequence_number)) @@ -1091,20 +1203,14 @@ handle_data (struct GNUNET_STREAM_Socket *socket, { socket->ack_task_id = GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_ntoh - (msg->ack_deadline), - &ack_task, - socket); + (msg->ack_deadline), &ack_task, socket); } return GNUNET_YES; } - LOG (GNUNET_ERROR_TYPE_DEBUG, "%s: Receiving DATA with sequence number: %u and size: %d from %s\n", - GNUNET_i2s (&socket->other_peer), - ntohl (msg->sequence_number), - ntohs (msg->header.header.size), - GNUNET_i2s (&socket->other_peer)); - + GNUNET_i2s (&socket->other_peer), ntohl (msg->sequence_number), + ntohs (msg->header.header.size), GNUNET_i2s (&socket->other_peer)); /* Check if we have to allocate the buffer */ size -= sizeof (struct GNUNET_STREAM_DataMessage); relative_offset = ntohl (msg->offset) - socket->read_offset; @@ -1121,54 +1227,67 @@ handle_data (struct GNUNET_STREAM_Socket *socket, { LOG (GNUNET_ERROR_TYPE_DEBUG, "%s: Cannot accommodate packet %d as buffer is full\n", - GNUNET_i2s (&socket->other_peer), - ntohl (msg->sequence_number)); + GNUNET_i2s (&socket->other_peer), ntohl (msg->sequence_number)); return GNUNET_YES; } } - /* Copy Data to buffer */ payload = &msg[1]; GNUNET_assert (relative_offset + size <= socket->receive_buffer_size); - memcpy (socket->receive_buffer + relative_offset, - payload, - size); + memcpy (socket->receive_buffer + relative_offset, payload, size); socket->receive_buffer_boundaries[relative_sequence_number] = - relative_offset + size; - + relative_offset + size; /* Modify the ACK bitmap */ - ackbitmap_modify_bit (&socket->ack_bitmap, - relative_sequence_number, - GNUNET_YES); - + ackbitmap_modify_bit (&socket->ack_bitmap, relative_sequence_number, + GNUNET_YES); /* Start ACK sending task if one is not already present */ + ack_deadline_rel = GNUNET_TIME_relative_ntoh (msg->ack_deadline); if (GNUNET_SCHEDULER_NO_TASK == socket->ack_task_id) { + ack_deadline_rel = + GNUNET_TIME_relative_min (ack_deadline_rel, + GNUNET_TIME_relative_multiply + (GNUNET_TIME_UNIT_SECONDS, 300)); socket->ack_task_id = - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_ntoh - (msg->ack_deadline), - &ack_task, - socket); + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_ntoh + (msg->ack_deadline), &ack_task, socket); + socket->ack_time_registered = GNUNET_TIME_absolute_get (); + socket->ack_time_deadline = ack_deadline_rel; + } + else + { + struct GNUNET_TIME_Relative ack_time_past; + struct GNUNET_TIME_Relative ack_time_remaining; + struct GNUNET_TIME_Relative ack_time_min; + ack_time_past = + GNUNET_TIME_absolute_get_duration (socket->ack_time_registered); + ack_time_remaining = GNUNET_TIME_relative_subtract + (socket->ack_time_deadline, ack_time_past); + ack_time_min = GNUNET_TIME_relative_min (ack_time_remaining, + ack_deadline_rel); + if (0 == memcmp(&ack_deadline_rel, &ack_time_min, + sizeof (struct GNUNET_TIME_Relative))) + { + ack_deadline_rel = ack_time_min; + GNUNET_SCHEDULER_cancel (socket->ack_task_id); + socket->ack_task_id = GNUNET_SCHEDULER_add_delayed (ack_deadline_rel, + &ack_task, socket); + socket->ack_time_registered = GNUNET_TIME_absolute_get (); + socket->ack_time_deadline = ack_deadline_rel; + } } - if ((NULL != socket->read_handle) /* A read handle is waiting */ /* There is no current read task */ - && (GNUNET_SCHEDULER_NO_TASK == socket->read_task_id) + && (GNUNET_SCHEDULER_NO_TASK == socket->read_handle->read_task_id) /* We have the first packet */ - && (GNUNET_YES == ackbitmap_is_bit_set(&socket->ack_bitmap, - 0))) + && (GNUNET_YES == ackbitmap_is_bit_set(&socket->ack_bitmap, 0))) { - LOG (GNUNET_ERROR_TYPE_DEBUG, - "%s: Scheduling read processor\n", - GNUNET_i2s (&socket->other_peer)); - - socket->read_task_id = - GNUNET_SCHEDULER_add_now (&call_read_processor, - socket); + LOG (GNUNET_ERROR_TYPE_DEBUG, "%s: Scheduling read processor\n", + GNUNET_i2s (&socket->other_peer)); + socket->read_handle->read_task_id = + GNUNET_SCHEDULER_add_now (&call_read_processor, socket); } - break; - default: LOG (GNUNET_ERROR_TYPE_DEBUG, "%s: Received data message when it cannot be handled\n", @@ -1201,18 +1320,15 @@ client_handle_data (void *cls, { struct GNUNET_STREAM_Socket *socket = cls; - return handle_data (socket, - tunnel, - sender, - (const struct GNUNET_STREAM_DataMessage *) message, - atsi); + return handle_data (socket, tunnel, sender, + (const struct GNUNET_STREAM_DataMessage *) message, atsi); } /** * Callback to set state to ESTABLISHED * - * @param cls the closure from queue_message FIXME: document + * @param cls the closure NULL; * @param socket the socket to requiring state change */ static void @@ -1225,7 +1341,10 @@ set_state_established (void *cls, socket->write_offset = 0; socket->read_offset = 0; socket->state = STATE_ESTABLISHED; - /* FIXME: What if listen_cb is NULL */ + GNUNET_assert (GNUNET_SCHEDULER_NO_TASK != + socket->control_retransmission_task_id); + GNUNET_SCHEDULER_cancel (socket->control_retransmission_task_id); + socket->control_retransmission_task_id = GNUNET_SCHEDULER_NO_TASK; if (NULL != socket->lsocket) { LOG (GNUNET_ERROR_TYPE_DEBUG, @@ -1237,12 +1356,12 @@ set_state_established (void *cls, &socket->other_peer)) { socket->state = STATE_CLOSED; - /* FIXME: We should close in a decent way */ + /* FIXME: We should close in a decent way (send RST) */ GNUNET_MESH_tunnel_destroy (socket->tunnel); /* Destroy the tunnel */ GNUNET_free (socket); } } - else if (socket->open_cb) + else socket->open_cb (socket->open_cls, socket); } @@ -1258,7 +1377,7 @@ set_state_hello_wait (void *cls, struct GNUNET_STREAM_Socket *socket) { GNUNET_assert (STATE_INIT == socket->state); - LOG (GNUNET_ERROR_TYPE_DEBUG, + LOG (GNUNET_ERROR_TYPE_DEBUG, "%s: Attaining HELLO_WAIT state\n", GNUNET_i2s (&socket->other_peer)); socket->state = STATE_HELLO_WAIT; @@ -1335,37 +1454,114 @@ set_state_closed (void *cls, socket->state = STATE_CLOSED; } + +/** + * Returns GNUNET_MESSAGE_TYPE_STREAM_HELLO + * + * @return the generate hello message + */ +static struct GNUNET_STREAM_MessageHeader * +generate_hello (void) +{ + struct GNUNET_STREAM_MessageHeader *msg; + + msg = GNUNET_malloc (sizeof (struct GNUNET_STREAM_MessageHeader)); + msg->header.type = htons (GNUNET_MESSAGE_TYPE_STREAM_HELLO); + msg->header.size = htons (sizeof (struct GNUNET_STREAM_MessageHeader)); + return msg; +} + + /** * Returns a new HelloAckMessage. Also sets the write sequence number for the * socket * * @param socket the socket for which this HelloAckMessage has to be generated + * @param generate_seq GNUNET_YES to generate the write sequence number, + * GNUNET_NO to use the existing sequence number * @return the HelloAckMessage */ static struct GNUNET_STREAM_HelloAckMessage * -generate_hello_ack_msg (struct GNUNET_STREAM_Socket *socket) +generate_hello_ack (struct GNUNET_STREAM_Socket *socket, + int generate_seq) { struct GNUNET_STREAM_HelloAckMessage *msg; - /* Get the random sequence number */ - socket->write_sequence_number = - GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_NONCE, UINT32_MAX); - LOG (GNUNET_ERROR_TYPE_DEBUG, - "%s: Generated write sequence number %u\n", - GNUNET_i2s (&socket->other_peer), - (unsigned int) socket->write_sequence_number); - + if (GNUNET_YES == generate_seq) + { + if (GNUNET_YES == socket->testing_active) + socket->write_sequence_number = + socket->testing_set_write_sequence_number_value; + else + socket->write_sequence_number = + GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_NONCE, UINT32_MAX); + LOG_DEBUG ("%s: write sequence number %u\n", + GNUNET_i2s (&socket->other_peer), + (unsigned int) socket->write_sequence_number); + } msg = GNUNET_malloc (sizeof (struct GNUNET_STREAM_HelloAckMessage)); msg->header.header.size = htons (sizeof (struct GNUNET_STREAM_HelloAckMessage)); msg->header.header.type = htons (GNUNET_MESSAGE_TYPE_STREAM_HELLO_ACK); msg->sequence_number = htonl (socket->write_sequence_number); msg->receiver_window_size = htonl (RECEIVE_BUFFER_SIZE); - return msg; } +/** + * Task for retransmitting control messages if they aren't ACK'ed before a + * deadline + * + * @param cls the socket + * @param tc the Task context + */ +static void +control_retransmission_task (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct GNUNET_STREAM_Socket *socket = cls; + + socket->control_retransmission_task_id = GNUNET_SCHEDULER_NO_TASK; + if (GNUNET_SCHEDULER_REASON_SHUTDOWN == tc->reason) + return; + LOG_DEBUG ("%s: Retransmitting a control message\n", + GNUNET_i2s (&socket->other_peer)); + switch (socket->state) + { + case STATE_INIT: + GNUNET_break (0); + break; + case STATE_LISTEN: + GNUNET_break (0); + break; + case STATE_HELLO_WAIT: + if (NULL == socket->lsocket) /* We are client */ + queue_message (socket, generate_hello (), NULL, NULL, GNUNET_NO); + else + queue_message (socket, + (struct GNUNET_STREAM_MessageHeader *) + generate_hello_ack (socket, GNUNET_NO), NULL, NULL, + GNUNET_NO); + socket->control_retransmission_task_id = + GNUNET_SCHEDULER_add_delayed (socket->retransmit_timeout, + &control_retransmission_task, socket); + break; + case STATE_ESTABLISHED: + if (NULL == socket->lsocket) + queue_message (socket, + (struct GNUNET_STREAM_MessageHeader *) + generate_hello_ack (socket, GNUNET_NO), NULL, NULL, + GNUNET_NO); + else + GNUNET_break (0); + break; + default: + GNUNET_break (0); + } +} + + /** * Client's message handler for GNUNET_MESSAGE_TYPE_STREAM_HELLO_ACK * @@ -1390,9 +1586,8 @@ client_handle_hello_ack (void *cls, const struct GNUNET_STREAM_HelloAckMessage *ack_msg; struct GNUNET_STREAM_HelloAckMessage *reply; - if (0 != memcmp (sender, - &socket->other_peer, - sizeof (struct GNUNET_PeerIdentity))) + if (0 != memcmp (sender, &socket->other_peer, + sizeof (struct GNUNET_PeerIdentity))) { LOG (GNUNET_ERROR_TYPE_DEBUG, "%s: Received HELLO_ACK from non-confirming peer\n", @@ -1400,11 +1595,8 @@ client_handle_hello_ack (void *cls, return GNUNET_YES; } ack_msg = (const struct GNUNET_STREAM_HelloAckMessage *) message; - LOG (GNUNET_ERROR_TYPE_DEBUG, - "%s: Received HELLO_ACK from %s\n", - GNUNET_i2s (&socket->other_peer), - GNUNET_i2s (&socket->other_peer)); - + LOG (GNUNET_ERROR_TYPE_DEBUG, "%s: Received HELLO_ACK from %s\n", + GNUNET_i2s (&socket->other_peer), GNUNET_i2s (&socket->other_peer)); GNUNET_assert (socket->tunnel == tunnel); switch (socket->state) { @@ -1415,27 +1607,24 @@ client_handle_hello_ack (void *cls, GNUNET_i2s (&socket->other_peer), (unsigned int) socket->read_sequence_number); socket->receiver_window_available = ntohl (ack_msg->receiver_window_size); - reply = generate_hello_ack_msg (socket); - queue_message (socket, - &reply->header, - &set_state_established, - NULL); + reply = generate_hello_ack (socket, GNUNET_YES); + queue_message (socket, &reply->header, &set_state_established, + NULL, GNUNET_NO); return GNUNET_OK; case STATE_ESTABLISHED: - case STATE_RECEIVE_CLOSE_WAIT: // call statistics (# ACKs ignored++) + GNUNET_assert (GNUNET_SCHEDULER_NO_TASK == + socket->control_retransmission_task_id); + socket->control_retransmission_task_id = + GNUNET_SCHEDULER_add_now (&control_retransmission_task, socket); return GNUNET_OK; - case STATE_INIT: default: - LOG (GNUNET_ERROR_TYPE_DEBUG, - "%s: Server %s sent HELLO_ACK when in state %d\n", - GNUNET_i2s (&socket->other_peer), - GNUNET_i2s (&socket->other_peer), - socket->state); + LOG_DEBUG ("%s: Server %s sent HELLO_ACK when in state %d\n", + GNUNET_i2s (&socket->other_peer), + GNUNET_i2s (&socket->other_peer), socket->state); socket->state = STATE_CLOSED; // introduce STATE_ERROR? return GNUNET_SYSERR; } - } @@ -1465,6 +1654,63 @@ client_handle_reset (void *cls, } +/** + * Frees the socket's receive buffers, marks the socket as receive closed and + * calls the DataProcessor with GNUNET_STREAM_SHUTDOWN status if a read handle + * is present + * + * @param socket the socket + */ +static void +do_receive_shutdown (struct GNUNET_STREAM_Socket *socket) +{ + socket->receive_closed = GNUNET_YES; + GNUNET_free_non_null (socket->receive_buffer); /* Free the receive buffer */ + socket->receive_buffer = NULL; + socket->receive_buffer_size = 0; + if (NULL != socket->read_handle) + { + GNUNET_STREAM_DataProcessor proc; + void *proc_cls; + + proc = socket->read_handle->proc; + proc_cls = socket->read_handle->proc_cls; + GNUNET_STREAM_read_cancel (socket->read_handle); + socket->read_handle = NULL; + if (NULL != proc) + proc (proc_cls, GNUNET_STREAM_SHUTDOWN, NULL, 0); + } +} + + +/** + * Marks the socket as transmit closed and calls the CompletionContinuation with + * GNUNET_STREAM_SHUTDOWN status if a write handle is present + * + * @param socket the socket + */ +static void +do_transmit_shutdown (struct GNUNET_STREAM_Socket *socket) +{ + socket->transmit_closed = GNUNET_YES; + /* If write handle is present call it with GNUNET_STREAM_SHUTDOWN to signal + that that stream has been shutdown */ + if (NULL != socket->write_handle) + { + GNUNET_STREAM_CompletionContinuation wc; + void *wc_cls; + + wc = socket->write_handle->write_cont; + wc_cls = socket->write_handle->write_cont_cls; + GNUNET_STREAM_write_cancel (socket->write_handle); + socket->write_handle = NULL; + if (NULL != wc) + wc (wc_cls, + GNUNET_STREAM_SHUTDOWN, 0); + } +} + + /** * Common message handler for handling TRANSMIT_CLOSE messages * @@ -1487,22 +1733,40 @@ handle_transmit_close (struct GNUNET_STREAM_Socket *socket, switch (socket->state) { - case STATE_ESTABLISHED: - socket->state = STATE_RECEIVE_CLOSED; - - /* Send TRANSMIT_CLOSE_ACK */ - reply = GNUNET_malloc (sizeof (struct GNUNET_STREAM_MessageHeader)); - reply->header.type = - htons (GNUNET_MESSAGE_TYPE_STREAM_TRANSMIT_CLOSE_ACK); - reply->header.size = htons (sizeof (struct GNUNET_STREAM_MessageHeader)); - queue_message (socket, reply, NULL, NULL); + case STATE_INIT: + case STATE_LISTEN: + case STATE_HELLO_WAIT: + LOG (GNUNET_ERROR_TYPE_DEBUG, + "%s: Ignoring RECEIVE_CLOSE as it cannot be handled now\n", + GNUNET_i2s (&socket->other_peer)); + return GNUNET_OK; + default: break; - + } + /* Send TRANSMIT_CLOSE_ACK */ + reply = GNUNET_malloc (sizeof (struct GNUNET_STREAM_MessageHeader)); + reply->header.type = + htons (GNUNET_MESSAGE_TYPE_STREAM_TRANSMIT_CLOSE_ACK); + reply->header.size = htons (sizeof (struct GNUNET_STREAM_MessageHeader)); + queue_message (socket, reply, NULL, NULL, GNUNET_NO); + LOG (GNUNET_ERROR_TYPE_DEBUG, "%s: Received TRANSMIT_CLOSE from %s\n", + GNUNET_i2s (&socket->other_peer), GNUNET_i2s (&socket->other_peer)); + switch(socket->state) + { + case STATE_RECEIVE_CLOSED: + case STATE_RECEIVE_CLOSE_WAIT: + case STATE_CLOSE_WAIT: + case STATE_CLOSED: + return GNUNET_OK; default: - /* FIXME: Call statistics? */ break; } - return GNUNET_YES; + do_receive_shutdown (socket); + if (GNUNET_YES == socket->transmit_closed) + socket->state = STATE_CLOSED; + else + socket->state = STATE_RECEIVE_CLOSED; + return GNUNET_OK; } @@ -1536,6 +1800,28 @@ client_handle_transmit_close (void *cls, } +/** + * Task for calling the shutdown continuation callback + * + * @param cls the socket + * @param tc the scheduler task context + */ +static void +call_cont_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct GNUNET_STREAM_Socket *socket = cls; + + GNUNET_assert (NULL != socket->shutdown_handle); + socket->shutdown_handle->call_cont_task_id = GNUNET_SCHEDULER_NO_TASK; + if (NULL != socket->shutdown_handle->completion_cb) + socket->shutdown_handle->completion_cb + (socket->shutdown_handle->completion_cls, + socket->shutdown_handle->operation); + GNUNET_free (socket->shutdown_handle); + socket->shutdown_handle = NULL; +} + + /** * Generic handler for GNUNET_MESSAGE_TYPE_STREAM_*_CLOSE_ACK messages * @@ -1561,12 +1847,12 @@ handle_generic_close_ack (struct GNUNET_STREAM_Socket *socket, shutdown_handle = socket->shutdown_handle; if (NULL == shutdown_handle) { + /* This may happen when the shudown handle is cancelled */ LOG (GNUNET_ERROR_TYPE_DEBUG, "%s: Received CLOSE_ACK when shutdown handle is NULL\n", GNUNET_i2s (&socket->other_peer)); return GNUNET_OK; } - switch (operation) { case SHUT_RDWR: @@ -1577,25 +1863,20 @@ handle_generic_close_ack (struct GNUNET_STREAM_Socket *socket, { LOG (GNUNET_ERROR_TYPE_DEBUG, "%s: Received CLOSE_ACK when shutdown handle is not for " - "SHUT_RDWR\n", - GNUNET_i2s (&socket->other_peer)); + "SHUT_RDWR\n", GNUNET_i2s (&socket->other_peer)); return GNUNET_OK; } - - LOG (GNUNET_ERROR_TYPE_DEBUG, - "%s: Received CLOSE_ACK from %s\n", - GNUNET_i2s (&socket->other_peer), - GNUNET_i2s (&socket->other_peer)); + LOG (GNUNET_ERROR_TYPE_DEBUG, "%s: Received CLOSE_ACK from %s\n", + GNUNET_i2s (&socket->other_peer), GNUNET_i2s (&socket->other_peer)); socket->state = STATE_CLOSED; break; default: LOG (GNUNET_ERROR_TYPE_DEBUG, - "%s: Received CLOSE_ACK when in it not expected\n", + "%s: Received CLOSE_ACK when it is not expected\n", GNUNET_i2s (&socket->other_peer)); return GNUNET_OK; } break; - case SHUT_RD: switch (socket->state) { @@ -1604,24 +1885,19 @@ handle_generic_close_ack (struct GNUNET_STREAM_Socket *socket, { LOG (GNUNET_ERROR_TYPE_DEBUG, "%s: Received RECEIVE_CLOSE_ACK when shutdown handle " - "is not for SHUT_RD\n", - GNUNET_i2s (&socket->other_peer)); + "is not for SHUT_RD\n", GNUNET_i2s (&socket->other_peer)); return GNUNET_OK; } - - LOG (GNUNET_ERROR_TYPE_DEBUG, - "%s: Received RECEIVE_CLOSE_ACK from %s\n", - GNUNET_i2s (&socket->other_peer), - GNUNET_i2s (&socket->other_peer)); + LOG (GNUNET_ERROR_TYPE_DEBUG, "%s: Received RECEIVE_CLOSE_ACK from %s\n", + GNUNET_i2s (&socket->other_peer), GNUNET_i2s (&socket->other_peer)); socket->state = STATE_RECEIVE_CLOSED; break; default: LOG (GNUNET_ERROR_TYPE_DEBUG, - "%s: Received RECEIVE_CLOSE_ACK when in it not expected\n", + "%s: Received RECEIVE_CLOSE_ACK when it is not expected\n", GNUNET_i2s (&socket->other_peer)); return GNUNET_OK; } - break; case SHUT_WR: switch (socket->state) @@ -1635,37 +1911,29 @@ handle_generic_close_ack (struct GNUNET_STREAM_Socket *socket, GNUNET_i2s (&socket->other_peer)); return GNUNET_OK; } - - LOG (GNUNET_ERROR_TYPE_DEBUG, - "%s: Received TRANSMIT_CLOSE_ACK from %s\n", - GNUNET_i2s (&socket->other_peer), - GNUNET_i2s (&socket->other_peer)); + LOG (GNUNET_ERROR_TYPE_DEBUG, "%s: Received TRANSMIT_CLOSE_ACK from %s\n", + GNUNET_i2s (&socket->other_peer), GNUNET_i2s (&socket->other_peer)); socket->state = STATE_TRANSMIT_CLOSED; break; default: LOG (GNUNET_ERROR_TYPE_DEBUG, - "%s: Received TRANSMIT_CLOSE_ACK when in it not expected\n", - GNUNET_i2s (&socket->other_peer)); - + "%s: Received TRANSMIT_CLOSE_ACK when it is not expected\n", + GNUNET_i2s (&socket->other_peer)); return GNUNET_OK; } break; default: GNUNET_assert (0); } - - if (NULL != shutdown_handle->completion_cb) /* Shutdown completion */ - shutdown_handle->completion_cb(shutdown_handle->completion_cls, - operation); - GNUNET_free (shutdown_handle); /* Free shutdown handle */ - socket->shutdown_handle = NULL; + shutdown_handle->call_cont_task_id = GNUNET_SCHEDULER_add_now + (&call_cont_task, socket); if (GNUNET_SCHEDULER_NO_TASK != shutdown_handle->close_msg_retransmission_task_id) { GNUNET_SCHEDULER_cancel (shutdown_handle->close_msg_retransmission_task_id); shutdown_handle->close_msg_retransmission_task_id = - GNUNET_SCHEDULER_NO_TASK; + GNUNET_SCHEDULER_NO_TASK; } return GNUNET_OK; } @@ -1734,26 +2002,31 @@ handle_receive_close (struct GNUNET_STREAM_Socket *socket, return GNUNET_OK; default: break; - } - - LOG (GNUNET_ERROR_TYPE_DEBUG, - "%s: Received RECEIVE_CLOSE from %s\n", - GNUNET_i2s (&socket->other_peer), - GNUNET_i2s (&socket->other_peer)); + } + LOG (GNUNET_ERROR_TYPE_DEBUG, "%s: Received RECEIVE_CLOSE from %s\n", + GNUNET_i2s (&socket->other_peer), GNUNET_i2s (&socket->other_peer)); receive_close_ack = GNUNET_malloc (sizeof (struct GNUNET_STREAM_MessageHeader)); receive_close_ack->header.size = htons (sizeof (struct GNUNET_STREAM_MessageHeader)); receive_close_ack->header.type = htons (GNUNET_MESSAGE_TYPE_STREAM_RECEIVE_CLOSE_ACK); - queue_message (socket, - receive_close_ack, - &set_state_closed, - NULL); - - /* FIXME: Handle the case where write handle is present; the write operation - should be deemed as finised and the write continuation callback - has to be called with the stream status GNUNET_STREAM_SHUTDOWN */ + queue_message (socket, receive_close_ack, NULL, NULL, GNUNET_NO); + switch (socket->state) + { + case STATE_TRANSMIT_CLOSED: + case STATE_TRANSMIT_CLOSE_WAIT: + case STATE_CLOSED: + case STATE_CLOSE_WAIT: + return GNUNET_OK; + default: + break; + } + do_transmit_shutdown (socket); + if (GNUNET_YES == socket->receive_closed) + socket->state = STATE_CLOSED; + else + socket->state = STATE_TRANSMIT_CLOSED; return GNUNET_OK; } @@ -1853,24 +2126,18 @@ handle_close (struct GNUNET_STREAM_Socket *socket, default: break; } - - LOG (GNUNET_ERROR_TYPE_DEBUG, - "%s: Received CLOSE from %s\n", - GNUNET_i2s (&socket->other_peer), - GNUNET_i2s (&socket->other_peer)); + LOG (GNUNET_ERROR_TYPE_DEBUG, "%s: Received CLOSE from %s\n", + GNUNET_i2s (&socket->other_peer), GNUNET_i2s (&socket->other_peer)); close_ack = GNUNET_malloc (sizeof (struct GNUNET_STREAM_MessageHeader)); close_ack->header.size = htons (sizeof (struct GNUNET_STREAM_MessageHeader)); close_ack->header.type = htons (GNUNET_MESSAGE_TYPE_STREAM_CLOSE_ACK); - queue_message (socket, - close_ack, - &set_state_closed, - NULL); - if (socket->state == STATE_CLOSED) + queue_message (socket, close_ack, &set_state_closed, NULL, GNUNET_NO); + if ((STATE_CLOSED == socket->state) || (STATE_CLOSE_WAIT == socket->state)) return GNUNET_OK; - - GNUNET_free_non_null (socket->receive_buffer); /* Free the receive buffer */ - socket->receive_buffer = NULL; - socket->receive_buffer_size = 0; + if (GNUNET_NO == socket->transmit_closed) + do_transmit_shutdown (socket); + if (GNUNET_NO == socket->receive_closed) + do_receive_shutdown (socket); return GNUNET_OK; } @@ -1997,34 +2264,38 @@ server_handle_hello (void *cls, &socket->other_peer, sizeof (struct GNUNET_PeerIdentity))) { - LOG (GNUNET_ERROR_TYPE_DEBUG, - "%s: Received HELLO from non-confirming peer\n", - GNUNET_i2s (&socket->other_peer)); + LOG_DEBUG ("%s: Received HELLO from non-confirming peer\n", + GNUNET_i2s (&socket->other_peer)); return GNUNET_YES; } - - GNUNET_assert (GNUNET_MESSAGE_TYPE_STREAM_HELLO == - ntohs (message->type)); + GNUNET_assert (GNUNET_MESSAGE_TYPE_STREAM_HELLO == ntohs (message->type)); GNUNET_assert (socket->tunnel == tunnel); - LOG (GNUNET_ERROR_TYPE_DEBUG, - "%s: Received HELLO from %s\n", - GNUNET_i2s (&socket->other_peer), - GNUNET_i2s (&socket->other_peer)); - - if (STATE_INIT == socket->state) - { - reply = generate_hello_ack_msg (socket); - queue_message (socket, - &reply->header, - &set_state_hello_wait, - NULL); - } - else + LOG_DEBUG ("%s: Received HELLO from %s\n", GNUNET_i2s (&socket->other_peer), + GNUNET_i2s (&socket->other_peer)); + switch (socket->state) { - LOG (GNUNET_ERROR_TYPE_DEBUG, - "Client sent HELLO when in state %d\n", socket->state); + case STATE_INIT: + reply = generate_hello_ack (socket, GNUNET_YES); + queue_message (socket, &reply->header, &set_state_hello_wait, NULL, + GNUNET_NO); + GNUNET_assert (GNUNET_SCHEDULER_NO_TASK == + socket->control_retransmission_task_id); + socket->control_retransmission_task_id = + GNUNET_SCHEDULER_add_delayed (socket->retransmit_timeout, + &control_retransmission_task, socket); + break; + case STATE_HELLO_WAIT: + /* Perhaps our HELLO_ACK was lost */ + GNUNET_assert (GNUNET_SCHEDULER_NO_TASK != + socket->control_retransmission_task_id); + GNUNET_SCHEDULER_cancel (socket->control_retransmission_task_id); + socket->control_retransmission_task_id = + GNUNET_SCHEDULER_add_now (&control_retransmission_task, socket); + break; + default: + LOG_DEBUG( "%s: Client sent HELLO when in state %d\n", + GNUNET_i2s (&socket->other_peer), socket->state); /* FIXME: Send RESET? */ - } return GNUNET_OK; } @@ -2057,8 +2328,9 @@ server_handle_hello_ack (void *cls, ntohs (message->type)); GNUNET_assert (socket->tunnel == tunnel); ack_message = (struct GNUNET_STREAM_HelloAckMessage *) message; - if (STATE_HELLO_WAIT == socket->state) + switch (socket->state) { + case STATE_HELLO_WAIT: LOG (GNUNET_ERROR_TYPE_DEBUG, "%s: Received HELLO_ACK from %s\n", GNUNET_i2s (&socket->other_peer), @@ -2070,15 +2342,11 @@ server_handle_hello_ack (void *cls, (unsigned int) socket->read_sequence_number); socket->receiver_window_available = ntohl (ack_message->receiver_window_size); - /* Attain ESTABLISHED state */ set_state_established (NULL, socket); - } - else - { + break; + default: LOG (GNUNET_ERROR_TYPE_DEBUG, - "Client sent HELLO_ACK when in state %d\n", socket->state); - /* FIXME: Send RESET? */ - + "Client sent HELLO_ACK when in state %d\n", socket->state); } return GNUNET_OK; } @@ -2316,9 +2584,11 @@ handle_ack (struct GNUNET_STREAM_Socket *socket, const struct GNUNET_STREAM_AckMessage *ack, const struct GNUNET_ATS_Information*atsi) { + struct GNUNET_STREAM_WriteHandle *write_handle; + uint64_t ack_bitmap; unsigned int packet; int need_retransmission; - + uint32_t sequence_difference; if (0 != memcmp (sender, &socket->other_peer, @@ -2329,7 +2599,6 @@ handle_ack (struct GNUNET_STREAM_Socket *socket, GNUNET_i2s (&socket->other_peer)); return GNUNET_YES; } - switch (socket->state) { case (STATE_ESTABLISHED): @@ -2342,10 +2611,9 @@ handle_ack (struct GNUNET_STREAM_Socket *socket, GNUNET_i2s (&socket->other_peer)); return GNUNET_OK; } - /* FIXME: increment in the base sequence number is breaking current flow - */ - if (!((socket->write_sequence_number - - ntohl (ack->base_sequence_number)) < GNUNET_STREAM_ACK_BITMAP_BIT_LENGTH)) + sequence_difference = + socket->write_sequence_number - ntohl (ack->base_sequence_number); + if (!(sequence_difference <= GNUNET_STREAM_ACK_BITMAP_BIT_LENGTH)) { LOG (GNUNET_ERROR_TYPE_DEBUG, "%s: Received DATA_ACK with unexpected base sequence number\n", @@ -2357,46 +2625,59 @@ handle_ack (struct GNUNET_STREAM_Socket *socket, ntohl (ack->base_sequence_number)); return GNUNET_OK; } - /* FIXME: include the case when write_handle is cancelled - ignore the - acks */ - - LOG (GNUNET_ERROR_TYPE_DEBUG, - "%s: Received DATA_ACK from %s\n", - GNUNET_i2s (&socket->other_peer), - GNUNET_i2s (&socket->other_peer)); - + LOG (GNUNET_ERROR_TYPE_DEBUG, "%s: Received DATA_ACK from %s\n", + GNUNET_i2s (&socket->other_peer), GNUNET_i2s (&socket->other_peer)); /* Cancel the retransmission task */ - if (GNUNET_SCHEDULER_NO_TASK != socket->retransmission_timeout_task_id) + if (GNUNET_SCHEDULER_NO_TASK != socket->data_retransmission_task_id) { - GNUNET_SCHEDULER_cancel (socket->retransmission_timeout_task_id); - socket->retransmission_timeout_task_id = - GNUNET_SCHEDULER_NO_TASK; + GNUNET_SCHEDULER_cancel (socket->data_retransmission_task_id); + socket->data_retransmission_task_id = GNUNET_SCHEDULER_NO_TASK; + socket->data_retransmit_timeout = GNUNET_TIME_UNIT_SECONDS; } - for (packet=0; packet < GNUNET_STREAM_ACK_BITMAP_BIT_LENGTH; packet++) + { + if (NULL == socket->write_handle->messages[packet]) + break; + /* BS: Base sequence from ack; PS: sequence num of current packet */ + sequence_difference = ntohl (ack->base_sequence_number) + - ntohl (socket->write_handle->messages[packet]->sequence_number); + if (0 == sequence_difference) + break; /* The message in our handle is not yet received */ + /* case where BS = PS + GNUNET_STREAM_ACK_BITMAP_BIT_LENGTH */ + /* sequence_difference <= GNUNET_STREAM_ACK_BITMAP_BIT_LENGTH */ + ackbitmap_modify_bit (&socket->write_handle->ack_bitmap, + packet, GNUNET_YES); + } + if (((ntohl (ack->base_sequence_number) + - (socket->write_handle->max_ack_base_num)) + <= GNUNET_STREAM_ACK_BITMAP_BIT_LENGTH)) + { + socket->write_handle->max_ack_base_num = ntohl (ack->base_sequence_number); + socket->receiver_window_available = + ntohl (ack->receive_window_remaining); + } + else + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Ignoring to modify receive window available as base: %u, max_ack_base: %u\n", + ntohl (ack->base_sequence_number), + socket->write_handle->max_ack_base_num); + if ((packet == GNUNET_STREAM_ACK_BITMAP_BIT_LENGTH) + || ((packet < GNUNET_STREAM_ACK_BITMAP_BIT_LENGTH) + && (NULL == socket->write_handle->messages[packet]))) + goto call_write_cont_cb; + GNUNET_assert (ntohl + (socket->write_handle->messages[packet]->sequence_number) + == ntohl (ack->base_sequence_number)); + /* Update our bitmap */ + ack_bitmap = GNUNET_ntohll (ack->bitmap); + for (; packet < GNUNET_STREAM_ACK_BITMAP_BIT_LENGTH; packet++) { if (NULL == socket->write_handle->messages[packet]) break; - if (ntohl (ack->base_sequence_number) - >= ntohl (socket->write_handle->messages[packet]->sequence_number)) - ackbitmap_modify_bit (&socket->write_handle->ack_bitmap, - packet, - GNUNET_YES); - else - if (GNUNET_YES == - ackbitmap_is_bit_set (&socket->write_handle->ack_bitmap, - ntohl (socket->write_handle->messages[packet]->sequence_number) - - ntohl (ack->base_sequence_number))) - ackbitmap_modify_bit (&socket->write_handle->ack_bitmap, - packet, - GNUNET_YES); + if (ackbitmap_is_bit_set (&ack_bitmap, ntohl + (socket->write_handle->messages[packet]->sequence_number) + - ntohl (ack->base_sequence_number))) + ackbitmap_modify_bit (&socket->write_handle->ack_bitmap, packet, GNUNET_YES); } - - /* Update the receive window remaining - FIXME : Should update with the value from a data ack with greater - sequence number */ - socket->receiver_window_available = - ntohl (ack->receive_window_remaining); - /* Check if we have received all acknowledgements */ need_retransmission = GNUNET_NO; for (packet=0; packet < GNUNET_STREAM_ACK_BITMAP_BIT_LENGTH; packet++) @@ -2412,26 +2693,26 @@ handle_ack (struct GNUNET_STREAM_Socket *socket, if (GNUNET_YES == need_retransmission) { write_data (socket); + return GNUNET_OK; } - else /* We have to call the write continuation callback now */ + + call_write_cont_cb: + /* Free the packets */ + for (packet=0; packet < GNUNET_STREAM_ACK_BITMAP_BIT_LENGTH; packet++) { - /* Free the packets */ - for (packet=0; packet < GNUNET_STREAM_ACK_BITMAP_BIT_LENGTH; packet++) - { - GNUNET_free_non_null (socket->write_handle->messages[packet]); - } - if (NULL != socket->write_handle->write_cont) - socket->write_handle->write_cont - (socket->write_handle->write_cont_cls, - socket->status, - socket->write_handle->size); - LOG (GNUNET_ERROR_TYPE_DEBUG, - "%s: Write completion callback completed\n", - GNUNET_i2s (&socket->other_peer)); - /* We are done with the write handle - Freeing it */ - GNUNET_free (socket->write_handle); - socket->write_handle = NULL; + GNUNET_free_non_null (socket->write_handle->messages[packet]); } + write_handle = socket->write_handle; + socket->write_handle = NULL; + if (NULL != write_handle->write_cont) + write_handle->write_cont (write_handle->write_cont_cls, + GNUNET_STREAM_OK, + write_handle->size); + /* We are done with the write handle - Freeing it */ + GNUNET_free (write_handle); + LOG (GNUNET_ERROR_TYPE_DEBUG, + "%s: Write completion callback completed\n", + GNUNET_i2s (&socket->other_peer)); break; default: break; @@ -2576,30 +2857,20 @@ mesh_peer_connect_callback (void *cls, GNUNET_i2s(peer)); return; } - LOG (GNUNET_ERROR_TYPE_DEBUG, "%s: Target peer %s connected\n", GNUNET_i2s (&socket->other_peer), GNUNET_i2s (&socket->other_peer)); - /* Set state to INIT */ socket->state = STATE_INIT; - /* Send HELLO message */ - message = GNUNET_malloc (sizeof (struct GNUNET_STREAM_MessageHeader)); - message->header.type = htons (GNUNET_MESSAGE_TYPE_STREAM_HELLO); - message->header.size = htons (sizeof (struct GNUNET_STREAM_MessageHeader)); - queue_message (socket, - message, - &set_state_hello_wait, - NULL); - - /* Call open callback */ - if (NULL == socket->open_cb) - { - LOG (GNUNET_ERROR_TYPE_DEBUG, - "STREAM_open callback is NULL\n"); - } + message = generate_hello (); + queue_message (socket, message, &set_state_hello_wait, NULL, GNUNET_NO); + GNUNET_assert (GNUNET_SCHEDULER_NO_TASK == + socket->control_retransmission_task_id); + socket->control_retransmission_task_id = + GNUNET_SCHEDULER_add_delayed (socket->retransmit_timeout, + &control_retransmission_task, socket); } @@ -2645,19 +2916,34 @@ new_tunnel_notify (void *cls, /* FIXME: If a tunnel is already created, we should not accept new tunnels from the same peer again until the socket is closed */ + if (GNUNET_NO == lsocket->listening) + { + GNUNET_MESH_tunnel_destroy (tunnel); + return NULL; + } socket = GNUNET_malloc (sizeof (struct GNUNET_STREAM_Socket)); socket->other_peer = *initiator; socket->tunnel = tunnel; - socket->session_id = 0; /* FIXME */ socket->state = STATE_INIT; socket->lsocket = lsocket; - + socket->stat_handle = lsocket->stat_handle; + socket->retransmit_timeout = lsocket->retransmit_timeout; + socket->testing_active = lsocket->testing_active; + socket->testing_set_write_sequence_number_value = + lsocket->testing_set_write_sequence_number_value; + socket->max_payload_size = lsocket->max_payload_size; LOG (GNUNET_ERROR_TYPE_DEBUG, "%s: Peer %s initiated tunnel to us\n", GNUNET_i2s (&socket->other_peer), GNUNET_i2s (&socket->other_peer)); - - /* FIXME: Copy MESH handle from lsocket to socket */ + if (NULL != socket->stat_handle) + { + GNUNET_STATISTICS_update (socket->stat_handle, + "total inbound connections received", + 1, GNUNET_NO); + GNUNET_STATISTICS_update (socket->stat_handle, + "inbound connections", 1, GNUNET_NO); + } return socket; } @@ -2681,47 +2967,123 @@ tunnel_cleaner (void *cls, void *tunnel_ctx) { struct GNUNET_STREAM_Socket *socket = tunnel_ctx; + struct MessageQueue *head; - if (tunnel != socket->tunnel) - return; - + GNUNET_assert (tunnel == socket->tunnel); GNUNET_break_op(0); LOG (GNUNET_ERROR_TYPE_DEBUG, "%s: Peer %s has terminated connection abruptly\n", GNUNET_i2s (&socket->other_peer), GNUNET_i2s (&socket->other_peer)); - - socket->status = GNUNET_STREAM_SHUTDOWN; - + if (NULL != socket->stat_handle) + { + GNUNET_STATISTICS_update (socket->stat_handle, + "connections terminated abruptly", 1, GNUNET_NO); + GNUNET_STATISTICS_update (socket->stat_handle, + "inbound connections", -1, GNUNET_NO); + } /* Clear Transmit handles */ if (NULL != socket->transmit_handle) { GNUNET_MESH_notify_transmit_ready_cancel (socket->transmit_handle); socket->transmit_handle = NULL; } - if (NULL != socket->ack_transmit_handle) - { - GNUNET_MESH_notify_transmit_ready_cancel (socket->ack_transmit_handle); - GNUNET_free (socket->ack_msg); - socket->ack_msg = NULL; - socket->ack_transmit_handle = NULL; - } /* Stop Tasks using socket->tunnel */ if (GNUNET_SCHEDULER_NO_TASK != socket->ack_task_id) { GNUNET_SCHEDULER_cancel (socket->ack_task_id); socket->ack_task_id = GNUNET_SCHEDULER_NO_TASK; } - if (GNUNET_SCHEDULER_NO_TASK != socket->retransmission_timeout_task_id) + if (GNUNET_SCHEDULER_NO_TASK != socket->data_retransmission_task_id) + { + GNUNET_SCHEDULER_cancel (socket->data_retransmission_task_id); + socket->data_retransmission_task_id = GNUNET_SCHEDULER_NO_TASK; + } + /* Terminate the control retransmission tasks */ + if (GNUNET_SCHEDULER_NO_TASK != socket->control_retransmission_task_id) { - GNUNET_SCHEDULER_cancel (socket->retransmission_timeout_task_id); - socket->retransmission_timeout_task_id = GNUNET_SCHEDULER_NO_TASK; + GNUNET_SCHEDULER_cancel (socket->control_retransmission_task_id); + socket->control_retransmission_task_id = GNUNET_SCHEDULER_NO_TASK; + } + /* Clear existing message queue */ + while (NULL != (head = socket->queue_head)) { + GNUNET_CONTAINER_DLL_remove (socket->queue_head, + socket->queue_tail, + head); + GNUNET_free (head->message); + GNUNET_free (head); } - /* FIXME: Cancel all other tasks using socket->tunnel */ socket->tunnel = NULL; } +/** + * Callback to signal timeout on lockmanager lock acquire + * + * @param cls the ListenSocket + * @param tc the scheduler task context + */ +static void +lockmanager_acquire_timeout (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct GNUNET_STREAM_ListenSocket *lsocket = cls; + GNUNET_STREAM_ListenCallback listen_cb; + void *listen_cb_cls; + + lsocket->lockmanager_acquire_timeout_task = GNUNET_SCHEDULER_NO_TASK; + listen_cb = lsocket->listen_cb; + listen_cb_cls = lsocket->listen_cb_cls; + if (NULL != listen_cb) + listen_cb (listen_cb_cls, NULL, NULL); +} + + +/** + * Callback to notify us on the status changes on app_port lock + * + * @param cls the ListenSocket + * @param domain the domain name of the lock + * @param lock the app_port + * @param status the current status of the lock + */ +static void +lock_status_change_cb (void *cls, const char *domain, uint32_t lock, + enum GNUNET_LOCKMANAGER_Status status) +{ + struct GNUNET_STREAM_ListenSocket *lsocket = cls; + + GNUNET_assert (lock == (uint32_t) lsocket->port); + if (GNUNET_LOCKMANAGER_SUCCESS == status) + { + lsocket->listening = GNUNET_YES; + if (GNUNET_SCHEDULER_NO_TASK != lsocket->lockmanager_acquire_timeout_task) + { + GNUNET_SCHEDULER_cancel (lsocket->lockmanager_acquire_timeout_task); + lsocket->lockmanager_acquire_timeout_task = GNUNET_SCHEDULER_NO_TASK; + } + if (NULL == lsocket->mesh) + { + GNUNET_MESH_ApplicationType ports[] = {lsocket->port, 0}; + + lsocket->mesh = GNUNET_MESH_connect (lsocket->cfg, + lsocket, /* Closure */ + &new_tunnel_notify, + &tunnel_cleaner, + server_message_handlers, + ports); + GNUNET_assert (NULL != lsocket->mesh); + if (NULL != lsocket->listen_ok_cb) + { + (void) lsocket->listen_ok_cb (); + } + } + } + if (GNUNET_LOCKMANAGER_RELEASE == status) + lsocket->listening = GNUNET_NO; +} + + /*****************/ /* API functions */ /*****************/ @@ -2734,7 +3096,8 @@ tunnel_cleaner (void *cls, * @param target the target peer to which the stream has to be opened * @param app_port the application port number which uniquely identifies this * stream - * @param open_cb this function will be called after stream has be established + * @param open_cb this function will be called after stream has be established; + * cannot be NULL * @param open_cb_cls the closure for open_cb * @param ... options to the stream, terminated by GNUNET_STREAM_OPTION_END * @return if successful it returns the stream socket; NULL if stream cannot be @@ -2751,17 +3114,20 @@ GNUNET_STREAM_open (const struct GNUNET_CONFIGURATION_Handle *cfg, struct GNUNET_STREAM_Socket *socket; enum GNUNET_STREAM_Option option; GNUNET_MESH_ApplicationType ports[] = {app_port, 0}; - va_list vargs; /* Variable arguments */ + va_list vargs; + uint16_t payload_size; LOG (GNUNET_ERROR_TYPE_DEBUG, "%s\n", __func__); + GNUNET_assert (NULL != open_cb); socket = GNUNET_malloc (sizeof (struct GNUNET_STREAM_Socket)); socket->other_peer = *target; socket->open_cb = open_cb; socket->open_cls = open_cb_cls; /* Set defaults */ - socket->retransmit_timeout = - GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, default_timeout); + socket->retransmit_timeout = TIME_REL_SECS (default_timeout); + socket->testing_active = GNUNET_NO; + socket->max_payload_size = DEFAULT_MAX_PAYLOAD_SIZE; va_start (vargs, open_cb_cls); /* Parse variable args */ do { option = va_arg (vargs, enum GNUNET_STREAM_Option); @@ -2772,13 +3138,29 @@ GNUNET_STREAM_open (const struct GNUNET_CONFIGURATION_Handle *cfg, socket->retransmit_timeout = va_arg (vargs, struct GNUNET_TIME_Relative); break; + case GNUNET_STREAM_OPTION_TESTING_SET_WRITE_SEQUENCE_NUMBER: + socket->testing_active = GNUNET_YES; + socket->testing_set_write_sequence_number_value = va_arg (vargs, + uint32_t); + break; + case GNUNET_STREAM_OPTION_LISTEN_TIMEOUT: + GNUNET_break (0); /* Option irrelevant in STREAM_open */ + break; + case GNUNET_STREAM_OPTION_SIGNAL_LISTEN_SUCCESS: + GNUNET_break (0); /* Option irrelevant in STREAM_open */ + break; + case GNUNET_STREAM_OPTION_MAX_PAYLOAD_SIZE: + payload_size = (uint16_t) va_arg (vargs, unsigned int); + GNUNET_assert (0 != payload_size); + if (payload_size < socket->max_payload_size) + socket->max_payload_size = payload_size; + break; case GNUNET_STREAM_OPTION_END: break; } } while (GNUNET_STREAM_OPTION_END != option); va_end (vargs); /* End of variable args parsing */ socket->mesh = GNUNET_MESH_connect (cfg, /* the configuration handle */ - 10, /* QUEUE size as parameter? */ socket, /* cls */ NULL, /* No inbound tunnel handler */ NULL, /* No in-tunnel cleaner */ @@ -2789,10 +3171,8 @@ GNUNET_STREAM_open (const struct GNUNET_CONFIGURATION_Handle *cfg, GNUNET_free (socket); return NULL; } - /* Now create the mesh tunnel to target */ - LOG (GNUNET_ERROR_TYPE_DEBUG, - "Creating MESH Tunnel\n"); + LOG (GNUNET_ERROR_TYPE_DEBUG, "Creating MESH Tunnel\n"); socket->tunnel = GNUNET_MESH_tunnel_create (socket->mesh, NULL, /* Tunnel context */ &mesh_peer_connect_callback, @@ -2801,9 +3181,8 @@ GNUNET_STREAM_open (const struct GNUNET_CONFIGURATION_Handle *cfg, GNUNET_assert (NULL != socket->tunnel); GNUNET_MESH_peer_request_connect_add (socket->tunnel, &socket->other_peer); - - LOG (GNUNET_ERROR_TYPE_DEBUG, - "%s() END\n", __func__); + socket->stat_handle = GNUNET_STATISTICS_create ("stream", cfg); + LOG (GNUNET_ERROR_TYPE_DEBUG, "%s() END\n", __func__); return socket; } @@ -2828,13 +3207,22 @@ GNUNET_STREAM_shutdown (struct GNUNET_STREAM_Socket *socket, struct GNUNET_STREAM_MessageHeader *msg; GNUNET_assert (NULL == socket->shutdown_handle); - handle = GNUNET_malloc (sizeof (struct GNUNET_STREAM_ShutdownHandle)); handle->socket = socket; handle->completion_cb = completion_cb; handle->completion_cls = completion_cls; socket->shutdown_handle = handle; - + if ( ((GNUNET_YES == socket->receive_closed) && (SHUT_RD == operation)) + || ((GNUNET_YES == socket->transmit_closed) && (SHUT_WR == operation)) + || ((GNUNET_YES == socket->transmit_closed) + && (GNUNET_YES == socket->receive_closed) + && (SHUT_RDWR == operation)) ) + { + handle->operation = operation; + handle->call_cont_task_id = GNUNET_SCHEDULER_add_now (&call_cont_task, + socket); + return handle; + } msg = GNUNET_malloc (sizeof (struct GNUNET_STREAM_MessageHeader)); msg->header.size = htons (sizeof (struct GNUNET_STREAM_MessageHeader)); switch (operation) @@ -2846,10 +3234,9 @@ GNUNET_STREAM_shutdown (struct GNUNET_STREAM_Socket *socket, "Existing read handle should be cancelled before shutting" " down reading\n"); msg->header.type = htons (GNUNET_MESSAGE_TYPE_STREAM_RECEIVE_CLOSE); - queue_message (socket, - msg, - &set_state_receive_close_wait, - NULL); + queue_message (socket, msg, &set_state_receive_close_wait, NULL, + GNUNET_NO); + socket->receive_closed = GNUNET_YES; break; case SHUT_WR: handle->operation = SHUT_WR; @@ -2858,10 +3245,9 @@ GNUNET_STREAM_shutdown (struct GNUNET_STREAM_Socket *socket, "Existing write handle should be cancelled before shutting" " down writing\n"); msg->header.type = htons (GNUNET_MESSAGE_TYPE_STREAM_TRANSMIT_CLOSE); - queue_message (socket, - msg, - &set_state_transmit_close_wait, - NULL); + queue_message (socket, msg, &set_state_transmit_close_wait, NULL, + GNUNET_NO); + socket->transmit_closed = GNUNET_YES; break; case SHUT_RDWR: handle->operation = SHUT_RDWR; @@ -2874,10 +3260,9 @@ GNUNET_STREAM_shutdown (struct GNUNET_STREAM_Socket *socket, "Existing read handle should be cancelled before shutting" " down reading\n"); msg->header.type = htons (GNUNET_MESSAGE_TYPE_STREAM_CLOSE); - queue_message (socket, - msg, - &set_state_close_wait, - NULL); + queue_message (socket, msg, &set_state_close_wait, NULL, GNUNET_NO); + socket->transmit_closed = GNUNET_YES; + socket->receive_closed = GNUNET_YES; break; default: LOG (GNUNET_ERROR_TYPE_WARNING, @@ -2896,7 +3281,10 @@ GNUNET_STREAM_shutdown (struct GNUNET_STREAM_Socket *socket, /** - * Cancels a pending shutdown + * Cancels a pending shutdown. Note that the shutdown messages may already be + * sent and the stream is shutdown already for the operation given to + * GNUNET_STREAM_shutdown(). This function only clears up any retranmissions of + * shutdown messages and frees the shutdown handle. * * @param handle the shutdown handle returned from GNUNET_STREAM_shutdown */ @@ -2905,8 +3293,10 @@ GNUNET_STREAM_shutdown_cancel (struct GNUNET_STREAM_ShutdownHandle *handle) { if (GNUNET_SCHEDULER_NO_TASK != handle->close_msg_retransmission_task_id) GNUNET_SCHEDULER_cancel (handle->close_msg_retransmission_task_id); + if (GNUNET_SCHEDULER_NO_TASK != handle->call_cont_task_id) + GNUNET_SCHEDULER_cancel (handle->call_cont_task_id); + handle->socket->shutdown_handle = NULL; GNUNET_free (handle); - return; } @@ -2924,42 +3314,32 @@ GNUNET_STREAM_close (struct GNUNET_STREAM_Socket *socket) { LOG (GNUNET_ERROR_TYPE_WARNING, "Closing STREAM socket when a read handle is pending\n"); + GNUNET_STREAM_read_cancel (socket->read_handle); } if (NULL != socket->write_handle) { LOG (GNUNET_ERROR_TYPE_WARNING, "Closing STREAM socket when a write handle is pending\n"); + GNUNET_STREAM_write_cancel (socket->write_handle); + //socket->write_handle = NULL; } - - if (socket->read_task_id != GNUNET_SCHEDULER_NO_TASK) - { - /* socket closed with read task pending!? */ - GNUNET_break (0); - GNUNET_SCHEDULER_cancel (socket->read_task_id); - socket->read_task_id = GNUNET_SCHEDULER_NO_TASK; - } - - /* Terminate the ack'ing tasks if they are still present */ + /* Terminate the ack'ing task if they are still present */ if (socket->ack_task_id != GNUNET_SCHEDULER_NO_TASK) { GNUNET_SCHEDULER_cancel (socket->ack_task_id); socket->ack_task_id = GNUNET_SCHEDULER_NO_TASK; } - + /* Terminate the control retransmission tasks */ + if (GNUNET_SCHEDULER_NO_TASK != socket->control_retransmission_task_id) + { + GNUNET_SCHEDULER_cancel (socket->control_retransmission_task_id); + } /* Clear Transmit handles */ if (NULL != socket->transmit_handle) { GNUNET_MESH_notify_transmit_ready_cancel (socket->transmit_handle); socket->transmit_handle = NULL; } - if (NULL != socket->ack_transmit_handle) - { - GNUNET_MESH_notify_transmit_ready_cancel (socket->ack_transmit_handle); - GNUNET_free (socket->ack_msg); - socket->ack_msg = NULL; - socket->ack_transmit_handle = NULL; - } - /* Clear existing message queue */ while (NULL != (head = socket->queue_head)) { GNUNET_CONTAINER_DLL_remove (socket->queue_head, @@ -2968,27 +3348,26 @@ GNUNET_STREAM_close (struct GNUNET_STREAM_Socket *socket) GNUNET_free (head->message); GNUNET_free (head); } - /* Close associated tunnel */ if (NULL != socket->tunnel) { GNUNET_MESH_tunnel_destroy (socket->tunnel); socket->tunnel = NULL; } - /* Close mesh connection */ - if (NULL != socket->mesh && NULL == socket->lsocket) + if ((NULL != socket->mesh) && (NULL == socket->lsocket)) { GNUNET_MESH_disconnect (socket->mesh); socket->mesh = NULL; } - + /* Close statistics connection */ + if ( (NULL != socket->stat_handle) && (NULL == socket->lsocket) ) + GNUNET_STATISTICS_destroy (socket->stat_handle, GNUNET_YES); /* Release receive buffer */ if (NULL != socket->receive_buffer) { GNUNET_free (socket->receive_buffer); } - GNUNET_free (socket); } @@ -3001,30 +3380,84 @@ GNUNET_STREAM_close (struct GNUNET_STREAM_Socket *socket) * @param listen_cb this function will be called when a peer tries to establish * a stream with us * @param listen_cb_cls closure for listen_cb + * @param ... options to the stream, terminated by GNUNET_STREAM_OPTION_END * @return listen socket, NULL for any error */ struct GNUNET_STREAM_ListenSocket * GNUNET_STREAM_listen (const struct GNUNET_CONFIGURATION_Handle *cfg, GNUNET_MESH_ApplicationType app_port, GNUNET_STREAM_ListenCallback listen_cb, - void *listen_cb_cls) + void *listen_cb_cls, + ...) { - /* FIXME: Add variable args for passing configration options? */ struct GNUNET_STREAM_ListenSocket *lsocket; - GNUNET_MESH_ApplicationType ports[] = {app_port, 0}; + struct GNUNET_TIME_Relative listen_timeout; + enum GNUNET_STREAM_Option option; + va_list vargs; + uint16_t payload_size; + GNUNET_assert (NULL != listen_cb); lsocket = GNUNET_malloc (sizeof (struct GNUNET_STREAM_ListenSocket)); + lsocket->cfg = GNUNET_CONFIGURATION_dup (cfg); + lsocket->lockmanager = GNUNET_LOCKMANAGER_connect (lsocket->cfg); + if (NULL == lsocket->lockmanager) + { + GNUNET_CONFIGURATION_destroy (lsocket->cfg); + GNUNET_free (lsocket); + return NULL; + } + lsocket->listening = GNUNET_NO;/* We listen when we get a lock on app_port */ + /* Set defaults */ + lsocket->retransmit_timeout = TIME_REL_SECS (default_timeout); + lsocket->testing_active = GNUNET_NO; + lsocket->listen_ok_cb = NULL; + lsocket->max_payload_size = DEFAULT_MAX_PAYLOAD_SIZE; + listen_timeout = TIME_REL_SECS (60); /* A minute for listen timeout */ + va_start (vargs, listen_cb_cls); + do { + option = va_arg (vargs, enum GNUNET_STREAM_Option); + switch (option) + { + case GNUNET_STREAM_OPTION_INITIAL_RETRANSMIT_TIMEOUT: + lsocket->retransmit_timeout = va_arg (vargs, + struct GNUNET_TIME_Relative); + break; + case GNUNET_STREAM_OPTION_TESTING_SET_WRITE_SEQUENCE_NUMBER: + lsocket->testing_active = GNUNET_YES; + lsocket->testing_set_write_sequence_number_value = va_arg (vargs, + uint32_t); + break; + case GNUNET_STREAM_OPTION_LISTEN_TIMEOUT: + listen_timeout = GNUNET_TIME_relative_multiply + (GNUNET_TIME_UNIT_MILLISECONDS, va_arg (vargs, uint32_t)); + break; + case GNUNET_STREAM_OPTION_SIGNAL_LISTEN_SUCCESS: + lsocket->listen_ok_cb = va_arg (vargs, + GNUNET_STREAM_ListenSuccessCallback); + break; + case GNUNET_STREAM_OPTION_MAX_PAYLOAD_SIZE: + payload_size = (uint16_t) va_arg (vargs, unsigned int); + GNUNET_assert (0 != payload_size); + if (payload_size < lsocket->max_payload_size) + lsocket->max_payload_size = payload_size; + break; + case GNUNET_STREAM_OPTION_END: + break; + } + } while (GNUNET_STREAM_OPTION_END != option); + va_end (vargs); lsocket->port = app_port; lsocket->listen_cb = listen_cb; lsocket->listen_cb_cls = listen_cb_cls; - lsocket->mesh = GNUNET_MESH_connect (cfg, - 10, /* FIXME: QUEUE size as parameter? */ - lsocket, /* Closure */ - &new_tunnel_notify, - &tunnel_cleaner, - server_message_handlers, - ports); - GNUNET_assert (NULL != lsocket->mesh); + lsocket->locking_request = + GNUNET_LOCKMANAGER_acquire_lock (lsocket->lockmanager, locking_domain, + (uint32_t) lsocket->port, + &lock_status_change_cb, lsocket); + lsocket->lockmanager_acquire_timeout_task = + GNUNET_SCHEDULER_add_delayed (listen_timeout, + &lockmanager_acquire_timeout, lsocket); + lsocket->stat_handle = GNUNET_STATISTICS_create ("stream", + lsocket->cfg); return lsocket; } @@ -3038,16 +3471,24 @@ void GNUNET_STREAM_listen_close (struct GNUNET_STREAM_ListenSocket *lsocket) { /* Close MESH connection */ - GNUNET_assert (NULL != lsocket->mesh); - GNUNET_MESH_disconnect (lsocket->mesh); - + if (NULL != lsocket->mesh) + GNUNET_MESH_disconnect (lsocket->mesh); + if (NULL != lsocket->stat_handle) + GNUNET_STATISTICS_destroy (lsocket->stat_handle, GNUNET_YES); + GNUNET_CONFIGURATION_destroy (lsocket->cfg); + if (GNUNET_SCHEDULER_NO_TASK != lsocket->lockmanager_acquire_timeout_task) + GNUNET_SCHEDULER_cancel (lsocket->lockmanager_acquire_timeout_task); + if (NULL != lsocket->locking_request) + GNUNET_LOCKMANAGER_cancel_request (lsocket->locking_request); + if (NULL != lsocket->lockmanager) + GNUNET_LOCKMANAGER_disconnect (lsocket->lockmanager); GNUNET_free (lsocket); } /** * Tries to write the given data to the stream. The maximum size of data that - * can be written as part of a write operation is (64 * (64000 - sizeof (struct + * can be written per a write operation is ~ 4MB (64 * (64000 - sizeof (struct * GNUNET_STREAM_DataMessage))). If size is greater than this it is not an API * violation, however only the said number of maximum bytes will be written. * @@ -3059,11 +3500,12 @@ GNUNET_STREAM_listen_close (struct GNUNET_STREAM_ListenSocket *lsocket) * stream * @param write_cont_cls the closure * - * @return handle to cancel the operation; if a previous write is pending or - * the stream has been shutdown for this operation then write_cont is - * immediately called and NULL is returned. + * @return handle to cancel the operation; if a previous write is pending NULL + * is returned. If the stream has been shutdown for this operation or + * is broken then write_cont is immediately called and NULL is + * returned. */ -struct GNUNET_STREAM_IOWriteHandle * +struct GNUNET_STREAM_WriteHandle * GNUNET_STREAM_write (struct GNUNET_STREAM_Socket *socket, const void *data, size_t size, @@ -3071,25 +3513,29 @@ GNUNET_STREAM_write (struct GNUNET_STREAM_Socket *socket, GNUNET_STREAM_CompletionContinuation write_cont, void *write_cont_cls) { + struct GNUNET_STREAM_WriteHandle *io_handle; + struct GNUNET_STREAM_DataMessage *data_msg; + const void *sweep; + struct GNUNET_TIME_Relative ack_deadline; unsigned int num_needed_packets; unsigned int packet; - struct GNUNET_STREAM_IOWriteHandle *io_handle; uint32_t packet_size; uint32_t payload_size; - struct GNUNET_STREAM_DataMessage *data_msg; - const void *sweep; - struct GNUNET_TIME_Relative ack_deadline; + uint16_t max_data_packet_size; LOG (GNUNET_ERROR_TYPE_DEBUG, "%s\n", __func__); - - /* Return NULL if there is already a write request pending */ if (NULL != socket->write_handle) { GNUNET_break (0); return NULL; } - + if (NULL == socket->tunnel) + { + if (NULL != write_cont) + write_cont (write_cont_cls, GNUNET_STREAM_SYSERR, 0); + return NULL; + } switch (socket->state) { case STATE_TRANSMIT_CLOSED: @@ -3105,7 +3551,6 @@ GNUNET_STREAM_write (struct GNUNET_STREAM_Socket *socket, case STATE_LISTEN: case STATE_HELLO_WAIT: if (NULL != write_cont) - /* FIXME: GNUNET_STREAM_SYSERR?? */ write_cont (write_cont_cls, GNUNET_STREAM_SYSERR, 0); LOG (GNUNET_ERROR_TYPE_DEBUG, "%s() END\n", __func__); @@ -3115,32 +3560,36 @@ GNUNET_STREAM_write (struct GNUNET_STREAM_Socket *socket, case STATE_RECEIVE_CLOSE_WAIT: break; } - - if (GNUNET_STREAM_ACK_BITMAP_BIT_LENGTH * max_payload_size < size) - size = GNUNET_STREAM_ACK_BITMAP_BIT_LENGTH * max_payload_size; - num_needed_packets = (size + (max_payload_size - 1)) / max_payload_size; - io_handle = GNUNET_malloc (sizeof (struct GNUNET_STREAM_IOWriteHandle)); + if (GNUNET_STREAM_ACK_BITMAP_BIT_LENGTH * socket->max_payload_size < size) + size = GNUNET_STREAM_ACK_BITMAP_BIT_LENGTH * socket->max_payload_size; + num_needed_packets = + (size + (socket->max_payload_size - 1)) / socket->max_payload_size; + io_handle = GNUNET_malloc (sizeof (struct GNUNET_STREAM_WriteHandle)); io_handle->socket = socket; io_handle->write_cont = write_cont; io_handle->write_cont_cls = write_cont_cls; io_handle->size = size; + io_handle->packets_sent = 0; sweep = data; /* FIXME: Remove the fixed delay for ack deadline; Set it to the value determined from RTT */ ack_deadline = GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 5); /* Divide the given buffer into packets for sending */ + max_data_packet_size = + socket->max_payload_size + sizeof (struct GNUNET_STREAM_DataMessage); + io_handle->max_ack_base_num = socket->write_sequence_number; for (packet=0; packet < num_needed_packets; packet++) { - if ((packet + 1) * max_payload_size < size) + if ((packet + 1) * socket->max_payload_size < size) { - payload_size = max_payload_size; - packet_size = MAX_PACKET_SIZE; + payload_size = socket->max_payload_size; + packet_size = max_data_packet_size; } else { - payload_size = size - packet * max_payload_size; - packet_size = payload_size + sizeof (struct - GNUNET_STREAM_DataMessage); + payload_size = size - packet * socket->max_payload_size; + packet_size = + payload_size + sizeof (struct GNUNET_STREAM_DataMessage); } io_handle->messages[packet] = GNUNET_malloc (packet_size); io_handle->messages[packet]->header.header.size = htons (packet_size); @@ -3149,143 +3598,170 @@ GNUNET_STREAM_write (struct GNUNET_STREAM_Socket *socket, io_handle->messages[packet]->sequence_number = htonl (socket->write_sequence_number++); io_handle->messages[packet]->offset = htonl (socket->write_offset); - /* FIXME: Remove the fixed delay for ack deadline; Set it to the value determined from RTT */ io_handle->messages[packet]->ack_deadline = GNUNET_TIME_relative_hton (ack_deadline); data_msg = io_handle->messages[packet]; /* Copy data from given buffer to the packet */ - memcpy (&data_msg[1], - sweep, - payload_size); + memcpy (&data_msg[1], sweep, payload_size); sweep += payload_size; socket->write_offset += payload_size; } + /* ack the last data message. FIXME: remove when we figure out how to do this + using RTT */ + io_handle->messages[num_needed_packets - 1]->ack_deadline = + GNUNET_TIME_relative_hton (GNUNET_TIME_UNIT_ZERO); + socket->data_retransmit_timeout = GNUNET_TIME_UNIT_SECONDS; socket->write_handle = io_handle; write_data (socket); - LOG (GNUNET_ERROR_TYPE_DEBUG, "%s() END\n", __func__); - return io_handle; } +/** + * Function to check the ACK bitmap for any received messages and call the data processor + * + * @param cls the socket + * @param tc the scheduler task context + */ +static void +probe_data_availability (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct GNUNET_STREAM_Socket *socket = cls; + + GNUNET_assert (NULL != socket->read_handle); + socket->read_handle->probe_data_availability_task_id = + GNUNET_SCHEDULER_NO_TASK; + if (GNUNET_SCHEDULER_NO_TASK != socket->read_handle->read_task_id) + return; /* A task to call read processor is present */ + if (GNUNET_YES == ackbitmap_is_bit_set (&socket->ack_bitmap, + 0)) + socket->read_handle->read_task_id + = GNUNET_SCHEDULER_add_now (&call_read_processor, socket); +} + + /** - * Tries to read data from the stream. + * Tries to read data from the stream. Should not be called when another read + * handle is present; the existing read handle should be canceled with + * GNUNET_STREAM_read_cancel(). Only one read handle per socket is present at + * any time * * @param socket the socket representing a stream * @param timeout the timeout period * @param proc function to call with data (once only) * @param proc_cls the closure for proc - * - * @return handle to cancel the operation; if the stream has been shutdown for - * this type of opeartion then the DataProcessor is immediately - * called with GNUNET_STREAM_SHUTDOWN as status and NULL if returned + * @return handle to cancel the operation; NULL is returned if the stream has + * been shutdown for this type of opeartion (the DataProcessor is + * immediately called with GNUNET_STREAM_SHUTDOWN as status) */ -struct GNUNET_STREAM_IOReadHandle * +struct GNUNET_STREAM_ReadHandle * GNUNET_STREAM_read (struct GNUNET_STREAM_Socket *socket, struct GNUNET_TIME_Relative timeout, GNUNET_STREAM_DataProcessor proc, void *proc_cls) { - struct GNUNET_STREAM_IOReadHandle *read_handle; + struct GNUNET_STREAM_ReadHandle *read_handle; LOG (GNUNET_ERROR_TYPE_DEBUG, "%s: %s()\n", GNUNET_i2s (&socket->other_peer), __func__); - - /* Return NULL if there is already a read handle; the user has to cancel that - first before continuing or has to wait until it is completed */ - if (NULL != socket->read_handle) return NULL; - + /* Only one read handle is permitted at any time; cancel the existing or wait + for it to complete */ + GNUNET_assert (NULL == socket->read_handle); GNUNET_assert (NULL != proc); - + if (GNUNET_YES == socket->receive_closed) + return NULL; switch (socket->state) { case STATE_RECEIVE_CLOSED: case STATE_RECEIVE_CLOSE_WAIT: case STATE_CLOSED: case STATE_CLOSE_WAIT: - proc (proc_cls, GNUNET_STREAM_SHUTDOWN, NULL, 0); LOG (GNUNET_ERROR_TYPE_DEBUG, "%s: %s() END\n", GNUNET_i2s (&socket->other_peer), __func__); + proc (proc_cls, GNUNET_STREAM_SHUTDOWN, NULL, 0); return NULL; default: break; } - - read_handle = GNUNET_malloc (sizeof (struct GNUNET_STREAM_IOReadHandle)); + read_handle = GNUNET_malloc (sizeof (struct GNUNET_STREAM_ReadHandle)); read_handle->proc = proc; read_handle->proc_cls = proc_cls; + read_handle->socket = socket; socket->read_handle = read_handle; - - /* Check if we have a packet at bitmap 0 */ - if (GNUNET_YES == ackbitmap_is_bit_set (&socket->ack_bitmap, - 0)) - { - socket->read_task_id = GNUNET_SCHEDULER_add_now (&call_read_processor, - socket); - - } - - /* Setup the read timeout task */ - socket->read_io_timeout_task_id = - GNUNET_SCHEDULER_add_delayed (timeout, - &read_io_timeout, - socket); - LOG (GNUNET_ERROR_TYPE_DEBUG, - "%s: %s() END\n", - GNUNET_i2s (&socket->other_peer), - __func__); + read_handle->probe_data_availability_task_id = + GNUNET_SCHEDULER_add_now (&probe_data_availability, socket); + read_handle->read_io_timeout_task_id = + GNUNET_SCHEDULER_add_delayed (timeout, &read_io_timeout, socket); + LOG (GNUNET_ERROR_TYPE_DEBUG, "%s: %s() END\n", + GNUNET_i2s (&socket->other_peer), __func__); return read_handle; } /** - * Cancel pending write operation. + * Cancels pending write operation. Also cancels packet retransmissions which + * may have resulted otherwise. * - * @param ioh handle to operation to cancel + * CAUTION: Normally a write operation is considered successful if the data + * given to it is sent and acknowledged by the receiver. As data is divided + * into packets, it is possible that not all packets are received by the + * receiver. Any missing packets are then retransmitted till the receiver + * acknowledges all packets or until a timeout . During this scenario if the + * write operation is cancelled all such retransmissions are also + * cancelled. This may leave the receiver's receive buffer incompletely filled + * as some missing packets are never retransmitted. So this operation should be + * used before shutting down transmission from our side or before closing the + * socket. + * + * @param wh write operation handle to cancel */ void -GNUNET_STREAM_io_write_cancel (struct GNUNET_STREAM_IOWriteHandle *ioh) +GNUNET_STREAM_write_cancel (struct GNUNET_STREAM_WriteHandle *wh) { - struct GNUNET_STREAM_Socket *socket = ioh->socket; + struct GNUNET_STREAM_Socket *socket = wh->socket; unsigned int packet; GNUNET_assert (NULL != socket->write_handle); - GNUNET_assert (socket->write_handle == ioh); - - if (GNUNET_SCHEDULER_NO_TASK != socket->retransmission_timeout_task_id) + GNUNET_assert (socket->write_handle == wh); + if (GNUNET_SCHEDULER_NO_TASK != socket->data_retransmission_task_id) { - GNUNET_SCHEDULER_cancel (socket->retransmission_timeout_task_id); - socket->retransmission_timeout_task_id = GNUNET_SCHEDULER_NO_TASK; + GNUNET_SCHEDULER_cancel (socket->data_retransmission_task_id); + socket->data_retransmission_task_id = GNUNET_SCHEDULER_NO_TASK; } - for (packet=0; packet < GNUNET_STREAM_ACK_BITMAP_BIT_LENGTH; packet++) { - if (NULL == ioh->messages[packet]) break; - GNUNET_free (ioh->messages[packet]); - } - + if (NULL == wh->messages[packet]) break; + GNUNET_free (wh->messages[packet]); + } GNUNET_free (socket->write_handle); socket->write_handle = NULL; - return; } /** * Cancel pending read operation. * - * @param ioh handle to operation to cancel + * @param rh read operation handle to cancel */ void -GNUNET_STREAM_io_read_cancel (struct GNUNET_STREAM_IOReadHandle *ioh) +GNUNET_STREAM_read_cancel (struct GNUNET_STREAM_ReadHandle *rh) { - return; + struct GNUNET_STREAM_Socket *socket; + + socket = rh->socket; + GNUNET_assert (NULL != socket->read_handle); + GNUNET_assert (rh == socket->read_handle); + cleanup_read_handle (socket); } + +/* end of stream_api.c */ diff --git a/src/stream/stream_protocol.h b/src/stream/stream_protocol.h deleted file mode 100644 index 0c5376f..0000000 --- a/src/stream/stream_protocol.h +++ /dev/null @@ -1,195 +0,0 @@ -/* - This file is part of GNUnet. - (C) 2012 Christian Grothoff (and other contributing authors) - - GNUnet is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published - by the Free Software Foundation; either version 3, or (at your - option) any later version. - - GNUnet is distributed in the hope that it will be useful, but - WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - General Public License for more details. - - You should have received a copy of the GNU General Public License - along with GNUnet; see the file COPYING. If not, write to the - Free Software Foundation, Inc., 59 Temple Place - Suite 330, - Boston, MA 02111-1307, USA. -*/ - -/** - * @file stream/stream_protocol.h - * @brief P2P protocol for the stream connections - * @author Sree Harsha Totakura - */ - -#ifndef STREAM_PROTOCOL_H -#define STREAM_PROTOCOL_H - -#ifdef __cplusplus -extern "C" -{ -#if 0 /* keep Emacsens' auto-indent happy */ -} -#endif -#endif - -#include "gnunet_util_lib.h" - -GNUNET_NETWORK_STRUCT_BEGIN - - -/** - * The stream message header - * All messages of STREAM should commonly have this as header - */ -struct GNUNET_STREAM_MessageHeader -{ - /** - * The GNUNET message header, types are from GNUNET_MESSAGE_TYPE_STREAM_*-range. - */ - struct GNUNET_MessageHeader header; - - /** - * A number which identifies a session between the two peers. FIXME: not needed - */ - uint32_t session_id GNUNET_PACKED; - -}; - - -/** - * The Data message, should be prefixed with stream header with its type set to - * GNUNET_STREAM_Data - */ -struct GNUNET_STREAM_DataMessage -{ - - /** - * Type is GNUNET_MESSAGE_TYPE_STREAM_DATA - */ - struct GNUNET_STREAM_MessageHeader header; - - /** - * Sequence number; starts with a random value. (Just in case - * someone breaks mesh and is able to try to do a Sequence - * Prediction Attack on us.) - */ - uint32_t sequence_number GNUNET_PACKED; - - /** - * number of milliseconds to the soft deadline for sending acknowledgement - * measured from the time this message is received. It is optimal for the - * communication to send the ack within the soft deadline - */ - struct GNUNET_TIME_RelativeNBO ack_deadline; - - /** - * Offset of the packet in the overall stream, modulo 2^32; allows - * the receiver to calculate where in the destination buffer the - * message should be placed. In network byte order. - */ - uint32_t offset GNUNET_PACKED; - - /** - * The data should be appended here - */ -}; - - -/** - * Number of bits in GNUNET_STREAM_AckBitmap - */ -#define GNUNET_STREAM_ACK_BITMAP_BIT_LENGTH 64 - -/** - * The Selective Acknowledgement Bitmap - */ -typedef uint64_t GNUNET_STREAM_AckBitmap; - - -/** - * The Acknowledgment Message to confirm receipt of DATA. - */ -struct GNUNET_STREAM_AckMessage -{ - - /** - * Type is GNUNET_MESSAGE_TYPE_STREAM_ACK - */ - struct GNUNET_STREAM_MessageHeader header; - - /** - * The Selective Acknowledgement Bitmap. Computed relative to the base_seq - * (bit n corresponds to the Data message with sequence number base_seq+n) - */ - GNUNET_STREAM_AckBitmap bitmap GNUNET_PACKED; - - /** - * The sequence number of the next Data Message receiver is - * anticipating. Data messages less than this number are received by receiver - */ - uint32_t base_sequence_number GNUNET_PACKED; - - /** - * Available buffer space past the last acknowledged buffer (for flow control), - * in bytes. - */ - uint32_t receive_window_remaining GNUNET_PACKED; -}; - - -/** - * Message for Acknowledging HELLO - */ -struct GNUNET_STREAM_HelloAckMessage -{ - /** - * The stream message header - */ - struct GNUNET_STREAM_MessageHeader header; - - /** - * The selected sequence number. Following data tranmissions from the sender - * start with this sequence - */ - uint32_t sequence_number; - - /** - * The size(in bytes) of the receive window on the peer sending this message - * - * FIXME: Remove if not needed - */ - uint32_t receiver_window_size; -}; - - -/** - * The Transmit close message(used to signal transmission is closed) - */ -struct GNUNET_STREAM_TransmitCloseMessage -{ - /** - * The stream message header - */ - struct GNUNET_STREAM_MessageHeader header; - - /** - * The last sequence number of the packet after which the transmission has - * ended - */ - uint32_t final_sequence_number GNUNET_PACKED; -}; - -GNUNET_NETWORK_STRUCT_END - - -#if 0 /** keep Emacsens' auto-indent happy */ -{ -#endif -#ifdef __cplusplus -} -#endif - -#endif /* STREAM_PROTOCOL_H */ diff --git a/src/stream/test_stream_2peers.c b/src/stream/test_stream_2peers.c index 1fdc0ee..0126439 100644 --- a/src/stream/test_stream_2peers.c +++ b/src/stream/test_stream_2peers.c @@ -30,20 +30,29 @@ #include "gnunet_util_lib.h" #include "gnunet_mesh_service.h" #include "gnunet_stream_lib.h" -#include "gnunet_testing_lib.h" - -#define VERBOSE 1 +#include "gnunet_testbed_service.h" /** - * Number of peers + * Number of peers; Do NOT change this */ #define NUM_PEERS 2 +/** + * Shorthand for Relative time in seconds + */ +#define TIME_REL_SECS(sec) \ + GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, sec) + /** * Structure for holding peer's sockets and IO Handles */ struct PeerData { + /** + * Handle to testbed peer + */ + struct GNUNET_TESTBED_Peer *peer; + /** * Peer's stream socket */ @@ -52,18 +61,23 @@ struct PeerData /** * Peer's io write handle */ - struct GNUNET_STREAM_IOWriteHandle *io_write_handle; + struct GNUNET_STREAM_WriteHandle *io_write_handle; /** * Peer's io read handle */ - struct GNUNET_STREAM_IOReadHandle *io_read_handle; + struct GNUNET_STREAM_ReadHandle *io_read_handle; /** * Peer's shutdown handle */ struct GNUNET_STREAM_ShutdownHandle *shutdown_handle; + /** + * The service connect operation to stream + */ + struct GNUNET_TESTBED_Operation *op; + /** * Our Peer id */ @@ -80,25 +94,53 @@ struct PeerData unsigned int bytes_read; }; + /** - * The current peer group + * Different states in test setup */ -static struct GNUNET_TESTING_PeerGroup *pg; +enum SetupState +{ + /** + * Get the identity of peer 1 + */ + PEER1_GET_IDENTITY, + + /** + * Get the identity of peer 2 + */ + PEER2_GET_IDENTITY, + + /** + * Connect to stream service of peer 1 + */ + PEER1_STREAM_CONNECT, + + /** + * Connect to stream service of peer 2 + */ + PEER2_STREAM_CONNECT + +}; /** - * Peer 1 daemon + * Various states during test setup */ -static struct GNUNET_TESTING_Daemon *d1; +static enum SetupState setup_state; /** - * Peer 2 daemon + * Data context for peer 1 */ -static struct GNUNET_TESTING_Daemon *d2; - static struct PeerData peer1; + +/** + * Data context for peer 2 + */ static struct PeerData peer2; -static struct GNUNET_STREAM_ListenSocket *peer2_listen_socket; -static struct GNUNET_CONFIGURATION_Handle *config; + +/** + * Testbed operation handle + */ +static struct GNUNET_TESTBED_Operation *op; static GNUNET_SCHEDULER_TaskIdentifier abort_task; @@ -184,52 +226,20 @@ stream_write_task (void *cls, } -/** - * Check whether peers successfully shut down. - */ -static void -peergroup_shutdown_callback (void *cls, const char *emsg) -{ - if (emsg != NULL) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Shutdown of peers failed!\n"); - } - else - { - GNUNET_log (GNUNET_ERROR_TYPE_INFO, - "All peers successfully shut down!\n"); - } - GNUNET_CONFIGURATION_destroy (config); -} - - /** * Close sockets and stop testing deamons nicely */ static void do_close (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { + if (GNUNET_SCHEDULER_NO_TASK != abort_task) + GNUNET_SCHEDULER_cancel (abort_task); if (NULL != peer1.socket) GNUNET_STREAM_close (peer1.socket); - if (NULL != peer2.socket) - GNUNET_STREAM_close (peer2.socket); - if (NULL != peer2_listen_socket) - GNUNET_STREAM_listen_close (peer2_listen_socket); - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: shutdown\n"); - if (0 != abort_task) - { - GNUNET_SCHEDULER_cancel (abort_task); - } - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: Wait\n"); - - GNUNET_TESTING_daemons_stop (pg, - GNUNET_TIME_relative_multiply - (GNUNET_TIME_UNIT_SECONDS, 5), - &peergroup_shutdown_callback, - NULL); + if (NULL != peer1.op) + GNUNET_TESTBED_operation_done (peer1.op); + else + GNUNET_SCHEDULER_shutdown (); /* For shutting down testbed */ } @@ -244,12 +254,18 @@ static void shutdown_completion (void *cls, int operation) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "STREAM shutdown successful\n"); - GNUNET_SCHEDULER_add_now (&do_close, - cls); -} + static int shutdowns; + if (++shutdowns == 1) + { + peer1.shutdown_handle = NULL; + peer2.shutdown_handle = GNUNET_STREAM_shutdown (peer2.socket, SHUT_RDWR, + &shutdown_completion, cls); + return; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "STREAM shutdown successful\n"); + GNUNET_SCHEDULER_add_now (&do_close, cls); +} /** @@ -258,10 +274,9 @@ shutdown_completion (void *cls, static void do_shutdown (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { - peer1.shutdown_handle = GNUNET_STREAM_shutdown (peer1.socket, - SHUT_RDWR, - &shutdown_completion, - cls); + result = GNUNET_OK; + peer1.shutdown_handle = GNUNET_STREAM_shutdown (peer1.socket, SHUT_RDWR, + &shutdown_completion, cls); } @@ -306,7 +321,7 @@ write_completion (void *cls, GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Writing completed\n"); - if (&peer1 == peer) /* Peer1 has finished writing; should read now */ + if (&peer2 == peer) /* Peer1 has finished writing; should read now */ { peer->bytes_read = 0; GNUNET_SCHEDULER_add_now (&stream_read_task, peer); @@ -333,10 +348,9 @@ stream_open_cb (void *cls, { struct PeerData *peer=cls; - GNUNET_assert (&peer1 == peer); - GNUNET_assert (socket == peer1.socket); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "%s: Stream established from peer1\n", + GNUNET_assert (&peer2 == peer); + GNUNET_assert (socket == peer2.socket); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "%s: Stream established from peer2\n", GNUNET_i2s (&peer1.our_id)); peer->bytes_wrote = 0; GNUNET_SCHEDULER_add_now (&stream_write_task, peer); @@ -385,7 +399,7 @@ input_processor (void *cls, } else { - if (&peer2 == peer) /* Peer2 has completed reading; should write */ + if (&peer1 == peer) /* Peer2 has completed reading; should write */ { peer->bytes_wrote = 0; GNUNET_SCHEDULER_add_now (&stream_write_task, peer); @@ -416,145 +430,232 @@ stream_listen_cb (void *cls, struct GNUNET_STREAM_Socket *socket, const struct GNUNET_PeerIdentity *initiator) { - GNUNET_assert (NULL != socket); + if ((NULL == socket) || (NULL == initiator)) + { + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Binding error\n"); + if (GNUNET_SCHEDULER_NO_TASK != abort_task) + GNUNET_SCHEDULER_cancel (abort_task); + abort_task = GNUNET_SCHEDULER_add_now (&do_abort, NULL); + return GNUNET_OK; + } GNUNET_assert (NULL != initiator); - GNUNET_assert (socket != peer1.socket); + GNUNET_assert (socket != peer2.socket); + GNUNET_assert (0 == memcmp (initiator, &peer2.our_id, + sizeof (struct GNUNET_PeerIdentity))); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "%s: Peer connected: %s\n", + GNUNET_i2s (&peer1.our_id), GNUNET_i2s (initiator)); + peer1.socket = socket; + peer1.bytes_read = 0; + GNUNET_SCHEDULER_add_now (&stream_read_task, &peer1); + return GNUNET_OK; +} - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "%s: Peer connected: %s\n", - GNUNET_i2s (&peer2.our_id), - GNUNET_i2s(initiator)); - peer2.socket = socket; - peer2.bytes_read = 0; - GNUNET_SCHEDULER_add_now (&stream_read_task, &peer2); - return GNUNET_OK; +/** + * Listen success callback; connects a peer to stream as client + */ +static void stream_connect (void); + + +/** + * Adapter function called to destroy a connection to + * a service. + * + * @param cls closure + * @param op_result service handle returned from the connect adapter + */ +static void +stream_da (void *cls, void *op_result) +{ + struct GNUNET_STREAM_ListenSocket *lsocket; + struct GNUNET_STREAM_Socket *socket; + + if (&peer1 == cls) + { + lsocket = op_result; + GNUNET_STREAM_listen_close (lsocket); + if (NULL != peer2.op) + GNUNET_TESTBED_operation_done (peer2.op); + else + GNUNET_SCHEDULER_shutdown (); + return; + } + if (&peer2 == cls) + { + socket = op_result; + GNUNET_STREAM_close (socket); + GNUNET_SCHEDULER_shutdown (); /* Exit point of the test */ + return; + } + GNUNET_assert (0); +} + + +/** + * Adapter function called to establish a connection to + * a service. + * + * @param cls closure + * @param cfg configuration of the peer to connect to; will be available until + * GNUNET_TESTBED_operation_done() is called on the operation returned + * from GNUNET_TESTBED_service_connect() + * @return service handle to return in 'op_result', NULL on error + */ +static void * +stream_ca (void *cls, const struct GNUNET_CONFIGURATION_Handle *cfg) +{ + struct GNUNET_STREAM_ListenSocket *lsocket; + + switch (setup_state) + { + case PEER1_STREAM_CONNECT: + lsocket = GNUNET_STREAM_listen (cfg, 10, &stream_listen_cb, NULL, + GNUNET_STREAM_OPTION_SIGNAL_LISTEN_SUCCESS, + &stream_connect, GNUNET_STREAM_OPTION_END); + return lsocket; + case PEER2_STREAM_CONNECT: + peer2.socket = GNUNET_STREAM_open (cfg, &peer1.our_id, 10, &stream_open_cb, + &peer2, GNUNET_STREAM_OPTION_END); + return peer2.socket; + default: + GNUNET_assert (0); + } +} + + +/** + * Listen success callback; connects a peer to stream as client + */ +static void +stream_connect (void) +{ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stream listen open successful\n"); + peer2.op = GNUNET_TESTBED_service_connect (&peer2, peer2.peer, "stream", + NULL, NULL, + stream_ca, stream_da, &peer2); + setup_state = PEER2_STREAM_CONNECT; } /** - * Callback to be called when testing peer group is ready + * Callback to be called when the requested peer information is available * - * @param cls NULL - * @param emsg NULL on success + * @param cb_cls the closure from GNUNET_TETSBED_peer_get_information() + * @param op the operation this callback corresponds to + * @param pinfo the result; will be NULL if the operation has failed + * @param emsg error message if the operation has failed; will be NULL if the + * operation is successfull */ -void -peergroup_ready (void *cls, const char *emsg) +static void +peerinfo_cb (void *cb_cls, struct GNUNET_TESTBED_Operation *op_, + const struct GNUNET_TESTBED_PeerInformation *pinfo, + const char *emsg) { - if (NULL != emsg) + GNUNET_assert (NULL == emsg); + GNUNET_assert (op == op_); + switch (setup_state) { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "Starting peer group failed: %s\n", emsg); - return; + case PEER1_GET_IDENTITY: + memcpy (&peer1.our_id, pinfo->result.id, + sizeof (struct GNUNET_PeerIdentity)); + GNUNET_TESTBED_operation_done (op); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Peer 1 id: %s\n", GNUNET_i2s + (&peer1.our_id)); + op = GNUNET_TESTBED_peer_get_information (peer2.peer, + GNUNET_TESTBED_PIT_IDENTITY, + &peerinfo_cb, NULL); + setup_state = PEER2_GET_IDENTITY; + break; + case PEER2_GET_IDENTITY: + memcpy (&peer2.our_id, pinfo->result.id, + sizeof (struct GNUNET_PeerIdentity)); + GNUNET_TESTBED_operation_done (op); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Peer 2 id: %s\n", GNUNET_i2s + (&peer2.our_id)); + peer1.op = GNUNET_TESTBED_service_connect (&peer1, peer1.peer, "stream", + NULL, NULL, stream_ca, + stream_da, &peer1); + setup_state = PEER1_STREAM_CONNECT; + break; + default: + GNUNET_assert (0); } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Peer group is now ready\n"); - - GNUNET_assert (2 == GNUNET_TESTING_daemons_running (pg)); - - d1 = GNUNET_TESTING_daemon_get (pg, 0); - GNUNET_assert (NULL != d1); - - d2 = GNUNET_TESTING_daemon_get (pg, 1); - GNUNET_assert (NULL != d2); - - GNUNET_TESTING_get_peer_identity (d1->cfg, - &peer1.our_id); - GNUNET_TESTING_get_peer_identity (d2->cfg, - &peer2.our_id); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "%s : %s\n", - GNUNET_i2s (&peer1.our_id), - GNUNET_i2s (&d1->id)); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "%s : %s\n", - GNUNET_i2s (&peer2.our_id), - GNUNET_i2s (&d2->id)); - - peer2_listen_socket = GNUNET_STREAM_listen (d2->cfg, - 10, /* App port */ - &stream_listen_cb, - NULL); - GNUNET_assert (NULL != peer2_listen_socket); - - /* Connect to stream library */ - peer1.socket = GNUNET_STREAM_open (d1->cfg, - &d2->id, /* Null for local peer? */ - 10, /* App port */ - &stream_open_cb, - &peer1, - GNUNET_STREAM_OPTION_END); - GNUNET_assert (NULL != peer1.socket); } /** - * Initialize framework and start test + * Controller event callback + * + * @param cls NULL + * @param event the controller event */ static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) +controller_event_cb (void *cls, + const struct GNUNET_TESTBED_EventInformation *event) { - struct GNUNET_TESTING_Host *hosts; /* FIXME: free hosts (DLL) */ - - GNUNET_log_setup ("test_stream_2peers", - "DEBUG", - NULL); + switch (event->type) + { + case GNUNET_TESTBED_ET_OPERATION_FINISHED: + switch (setup_state) + { + case PEER1_STREAM_CONNECT: + case PEER2_STREAM_CONNECT: + GNUNET_assert (NULL == event->details.operation_finished.emsg); + break; + default: + GNUNET_assert (0); + } + break; + default: + GNUNET_assert (0); + } +} - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Starting test\n"); - /* Duplicate the configuration */ - config = GNUNET_CONFIGURATION_dup (cfg); - hosts = GNUNET_TESTING_hosts_load (config); - - pg = GNUNET_TESTING_peergroup_start (config, - 2, - GNUNET_TIME_relative_multiply - (GNUNET_TIME_UNIT_SECONDS, 3), - NULL, - &peergroup_ready, - NULL, - hosts); - GNUNET_assert (NULL != pg); - +/** + * Signature of a main function for a testcase. + * + * @param cls closure + * @param num_peers number of peers in 'peers' + * @param peers handle to peers run in the testbed + */ +static void +test_master (void *cls, unsigned int num_peers, + struct GNUNET_TESTBED_Peer **peers) +{ + GNUNET_assert (NULL != peers); + GNUNET_assert (NULL != peers[0]); + GNUNET_assert (NULL != peers[1]); + peer1.peer = peers[0]; + peer2.peer = peers[1]; + /* Get the peer identity and configuration of peers */ + op = GNUNET_TESTBED_peer_get_information (peer1.peer, + GNUNET_TESTBED_PIT_IDENTITY, + &peerinfo_cb, NULL); + setup_state = PEER1_GET_IDENTITY; abort_task = GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 40), &do_abort, NULL); } + /** * Main function */ int main (int argc, char **argv) { - int ret; - - char *argv2[] = { "test-stream-2peers", - "-L", "DEBUG", - "-c", "test_stream_local.conf", - NULL}; - - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - - ret = - GNUNET_PROGRAM_run ((sizeof (argv2) / sizeof (char *)) - 1, argv2, - "test-stream-2peers", "nohelp", options, &run, NULL); - - if (GNUNET_OK != ret) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "run failed with error code %d\n", - ret); - return 1; - } + uint64_t event_mask; + + result = GNUNET_NO; + event_mask = 0; + event_mask |= (1LL << GNUNET_TESTBED_ET_OPERATION_FINISHED); + (void) GNUNET_TESTBED_test_run ("test_stream_2peers", + "test_stream_local.conf", + NUM_PEERS, event_mask, &controller_event_cb, + NULL, + &test_master, NULL); if (GNUNET_SYSERR == result) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "test failed\n"); return 1; - } - GNUNET_log (GNUNET_ERROR_TYPE_INFO, "test ok\n"); return 0; } diff --git a/src/stream/test_stream_2peers_halfclose.c b/src/stream/test_stream_2peers_halfclose.c index 7997c20..95f5aa9 100644 --- a/src/stream/test_stream_2peers_halfclose.c +++ b/src/stream/test_stream_2peers_halfclose.c @@ -23,28 +23,30 @@ * @brief Testcases for Stream API halfclosed connections between 2 peers * @author Sree Harsha Totakura */ - -#include - #include "platform.h" #include "gnunet_util_lib.h" +#include "gnunet_testbed_service.h" #include "gnunet_mesh_service.h" #include "gnunet_stream_lib.h" -#include "gnunet_testing_lib.h" -#include "gnunet_scheduler_lib.h" - -#define VERBOSE 1 /** * Number of peers */ #define NUM_PEERS 2 +#define TIME_REL_SECS(sec) \ + GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, sec) + /** * Structure for holding peer's sockets and IO Handles */ struct PeerData { + /** + * The testbed peer handle corresponding to this peer + */ + struct GNUNET_TESTBED_Peer *peer; + /** * Peer's stream socket */ @@ -53,18 +55,23 @@ struct PeerData /** * Peer's io write handle */ - struct GNUNET_STREAM_IOWriteHandle *io_write_handle; + struct GNUNET_STREAM_WriteHandle *io_write_handle; /** * Peer's io read handle */ - struct GNUNET_STREAM_IOReadHandle *io_read_handle; + struct GNUNET_STREAM_ReadHandle *io_read_handle; /** * Peer's shutdown handle */ struct GNUNET_STREAM_ShutdownHandle *shutdown_handle; + /** + * Testbed operation handle specific for this peer + */ + struct GNUNET_TESTBED_Operation *op; + /** * Our Peer id */ @@ -91,20 +98,71 @@ struct PeerData int shutdown_operation; }; -/** - * The current peer group - */ -static struct GNUNET_TESTING_PeerGroup *pg; /** - * Peer 1 daemon + * Enumeration for various tests that are to be passed in the same order as + * below */ -static struct GNUNET_TESTING_Daemon *d1; +enum Test +{ + /** + * Peer1 writing; Peer2 reading + */ + PEER1_WRITE, + + /** + * Peer1 write shutdown; Peer2 should get an error when it tries to read; + */ + PEER1_WRITE_SHUTDOWN, + + /** + * Peer1 reads; Peer2 writes (connection is halfclosed) + */ + PEER1_HALFCLOSE_READ, + + /** + * Peer1 attempts to write; Should fail with stream already shutdown error + */ + PEER1_HALFCLOSE_WRITE_FAIL, + + /** + * Peer1 read shutdown; Peer2 should get stream shutdown error during write + */ + PEER1_READ_SHUTDOWN, + + /** + * All tests successfully finished + */ + SUCCESS +}; + /** - * Peer 2 daemon + * Different states in test setup */ -static struct GNUNET_TESTING_Daemon *d2; +enum SetupState +{ + /** + * Get the identity of peer 1 + */ + PEER1_GET_IDENTITY, + + /** + * Get the identity of peer 2 + */ + PEER2_GET_IDENTITY, + + /** + * Connect to stream service of peer 2 + */ + PEER2_STREAM_CONNECT, + + /** + * Connect to stream service of peer 1 + */ + PEER1_STREAM_CONNECT + +}; /** @@ -116,57 +174,40 @@ static struct GNUNET_TESTING_Daemon *d2; */ static struct PeerData peer1; static struct PeerData peer2; -static struct GNUNET_STREAM_ListenSocket *peer2_listen_socket; -static struct GNUNET_CONFIGURATION_Handle *config; +/** + * Task for aborting the test case if it takes too long + */ static GNUNET_SCHEDULER_TaskIdentifier abort_task; + +/** + * Task for reading from stream + */ static GNUNET_SCHEDULER_TaskIdentifier read_task; static char *data = "ABCD"; -static int result; /** - * Enumeration for various tests that are to be passed in the same order as - * below + * Handle to testbed operation */ -enum Test - { - /** - * Peer1 writing; Peer2 reading - */ - PEER1_WRITE, - - /** - * Peer1 write shutdown; Peer2 should get an error when it tries to read; - */ - PEER1_WRITE_SHUTDOWN, - - /** - * Peer1 reads; Peer2 writes (connection is halfclosed) - */ - PEER1_HALFCLOSE_READ, - - /** - * Peer1 attempts to write; Should fail with stream already shutdown error - */ - PEER1_HALFCLOSE_WRITE_FAIL, - - /** - * Peer1 read shutdown; Peer2 should get stream shutdown error during write - */ - PEER1_READ_SHUTDOWN, - - /** - * All tests successfully finished - */ - SUCCESS - }; +struct GNUNET_TESTBED_Operation *op; + +/** + * Final testing result + */ +static int result; /** * Current running test */ enum Test current_test; +/** + * State is test setup + */ +enum SetupState setup_state; + + /** * Input processor * @@ -213,6 +254,7 @@ stream_read_task (void *cls, case PEER1_WRITE_SHUTDOWN: GNUNET_assert (&peer2 == peer); GNUNET_assert (NULL == peer->io_read_handle); + peer2.test_ok = GNUNET_YES; transition (); /* to PEER1_HALFCLOSE_READ */ break; default: @@ -273,52 +315,20 @@ stream_write_task (void *cls, } -/** - * Check whether peers successfully shut down. - */ -static void -peergroup_shutdown_callback (void *cls, const char *emsg) -{ - if (emsg != NULL) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Shutdown of peers failed!\n"); - } - else - { - GNUNET_log (GNUNET_ERROR_TYPE_INFO, - "All peers successfully shut down!\n"); - } - GNUNET_CONFIGURATION_destroy (config); -} - - /** * Close sockets and stop testing deamons nicely */ static void do_close (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { - if (NULL != peer1.socket) - GNUNET_STREAM_close (peer1.socket); if (NULL != peer2.socket) GNUNET_STREAM_close (peer2.socket); - if (NULL != peer2_listen_socket) - GNUNET_STREAM_listen_close (peer2_listen_socket); - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: shutdown\n"); - if (0 != abort_task) - { + if (GNUNET_SCHEDULER_NO_TASK != abort_task) GNUNET_SCHEDULER_cancel (abort_task); - } - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: Wait\n"); - - GNUNET_TESTING_daemons_stop (pg, - GNUNET_TIME_relative_multiply - (GNUNET_TIME_UNIT_SECONDS, 5), - &peergroup_shutdown_callback, - NULL); + if (NULL != peer2.op) + GNUNET_TESTBED_operation_done (peer2.op); + else + GNUNET_SCHEDULER_shutdown (); /* For shutting down testbed */ } @@ -600,8 +610,8 @@ input_processor (void *cls, } break; case PEER1_WRITE_SHUTDOWN: - GNUNET_assert (GNUNET_STREAM_SHUTDOWN == status); - peer2.test_ok = GNUNET_YES; + GNUNET_assert (0); /* This callback will not be called when stream + is shutdown */ break; case PEER1_HALFCLOSE_WRITE_FAIL: case PEER1_READ_SHUTDOWN: @@ -642,15 +652,19 @@ stream_listen_cb (void *cls, struct GNUNET_STREAM_Socket *socket, const struct GNUNET_PeerIdentity *initiator) { - GNUNET_assert (NULL != socket); - GNUNET_assert (NULL != initiator); + if ((NULL == socket) || (NULL == initiator)) + { + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Binding error\n"); + if (GNUNET_SCHEDULER_NO_TASK != abort_task) + GNUNET_SCHEDULER_cancel (abort_task); + abort_task = GNUNET_SCHEDULER_add_now (&do_abort, NULL); + return GNUNET_OK; + } GNUNET_assert (socket != peer1.socket); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "%s: Peer connected: %s\n", GNUNET_i2s (&peer2.our_id), GNUNET_i2s(initiator)); - peer2.socket = socket; /* FIXME: reading should be done right now instead of a scheduled call */ read_task = GNUNET_SCHEDULER_add_now (&stream_read, (void *) socket); @@ -659,128 +673,212 @@ stream_listen_cb (void *cls, /** - * Callback to be called when testing peer group is ready - * - * @param cls NULL - * @param emsg NULL on success + * Listen success callback; connects a peer to stream as client + */ +static void +stream_connect (void); + + +/** + * Adapter function called to destroy a connection to + * a service. + * + * @param cls closure + * @param op_result service handle returned from the connect adapter */ -void -peergroup_ready (void *cls, const char *emsg) +static void +stream_da (void *cls, void *op_result) { - if (NULL != emsg) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "Starting peer group failed: %s\n", emsg); - return; - } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Peer group is now ready\n"); - - GNUNET_assert (2 == GNUNET_TESTING_daemons_running (pg)); - - d1 = GNUNET_TESTING_daemon_get (pg, 0); - GNUNET_assert (NULL != d1); - - d2 = GNUNET_TESTING_daemon_get (pg, 1); - GNUNET_assert (NULL != d2); + struct GNUNET_STREAM_ListenSocket *lsocket; - GNUNET_TESTING_get_peer_identity (d1->cfg, - &peer1.our_id); - GNUNET_TESTING_get_peer_identity (d2->cfg, - &peer2.our_id); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "%s : %s\n", - GNUNET_i2s (&peer1.our_id), - GNUNET_i2s (&d1->id)); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "%s : %s\n", - GNUNET_i2s (&peer2.our_id), - GNUNET_i2s (&d2->id)); - - peer2_listen_socket = GNUNET_STREAM_listen (d2->cfg, - 10, /* App port */ - &stream_listen_cb, - NULL); - GNUNET_assert (NULL != peer2_listen_socket); - - /* Connect to stream library */ - peer1.socket = GNUNET_STREAM_open (d1->cfg, - &d2->id, /* Null for local peer? */ - 10, /* App port */ - &stream_open_cb, - &peer1, - GNUNET_STREAM_OPTION_END); - GNUNET_assert (NULL != peer1.socket); + if (&peer2 == cls) + { + lsocket = op_result; + GNUNET_STREAM_listen_close (lsocket); + if (NULL != peer1.op) + GNUNET_TESTBED_operation_done (peer1.op); + else + GNUNET_SCHEDULER_shutdown (); + return; + } + if (&peer1 == cls) + { + GNUNET_assert (op_result == peer1.socket); + GNUNET_STREAM_close (peer1.socket); + GNUNET_SCHEDULER_shutdown (); /* Exit point of the test */ + return; + } + GNUNET_assert (0); } /** - * Initialize framework and start test + * Adapter function called to establish a connection to + * a service. + * + * @param cls closure + * @param cfg configuration of the peer to connect to; will be available until + * GNUNET_TESTBED_operation_done() is called on the operation returned + * from GNUNET_TESTBED_service_connect() + * @return service handle to return in 'op_result', NULL on error + */ +static void * +stream_ca (void *cls, const struct GNUNET_CONFIGURATION_Handle *cfg) +{ + struct GNUNET_STREAM_ListenSocket *lsocket; + + switch (setup_state) + { + case PEER2_STREAM_CONNECT: + lsocket = GNUNET_STREAM_listen (cfg, 10, &stream_listen_cb, NULL, + GNUNET_STREAM_OPTION_SIGNAL_LISTEN_SUCCESS, + &stream_connect, GNUNET_STREAM_OPTION_END); + GNUNET_assert (NULL != lsocket); + return lsocket; + case PEER1_STREAM_CONNECT: + peer1.socket = GNUNET_STREAM_open (cfg, &peer2.our_id, 10, &stream_open_cb, + &peer1, GNUNET_STREAM_OPTION_END); + GNUNET_assert (NULL != peer1.socket); + return peer1.socket; + default: + GNUNET_assert (0); + } +} + + +/** + * Listen success callback; connects a peer to stream as client */ static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) +stream_connect (void) +{ + GNUNET_assert (PEER2_STREAM_CONNECT == setup_state); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stream listen open successful\n"); + peer1.op = GNUNET_TESTBED_service_connect (&peer1, peer1.peer, "stream", + NULL, NULL, + stream_ca, stream_da, &peer1); + setup_state = PEER1_STREAM_CONNECT; +} + + +/** + * Callback to be called when the requested peer information is available + * + * @param cb_cls the closure from GNUNET_TETSBED_peer_get_information() + * @param op the operation this callback corresponds to + * @param pinfo the result; will be NULL if the operation has failed + * @param emsg error message if the operation has failed; will be NULL if the + * operation is successfull + */ +static void +peerinfo_cb (void *cb_cls, struct GNUNET_TESTBED_Operation *op_, + const struct GNUNET_TESTBED_PeerInformation *pinfo, + const char *emsg) { - struct GNUNET_TESTING_Host *hosts; /* FIXME: free hosts (DLL) */ + GNUNET_assert (NULL == emsg); + GNUNET_assert (op == op_); + switch (setup_state) + { + case PEER1_GET_IDENTITY: + memcpy (&peer1.our_id, pinfo->result.id, + sizeof (struct GNUNET_PeerIdentity)); + GNUNET_TESTBED_operation_done (op); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Peer 1 id: %s\n", GNUNET_i2s + (&peer1.our_id)); + op = GNUNET_TESTBED_peer_get_information (peer2.peer, + GNUNET_TESTBED_PIT_IDENTITY, + &peerinfo_cb, NULL); + setup_state = PEER2_GET_IDENTITY; + break; + case PEER2_GET_IDENTITY: + memcpy (&peer2.our_id, pinfo->result.id, + sizeof (struct GNUNET_PeerIdentity)); + GNUNET_TESTBED_operation_done (op); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Peer 2 id: %s\n", GNUNET_i2s + (&peer2.our_id)); + peer2.op = GNUNET_TESTBED_service_connect (&peer2, peer2.peer, "stream", + NULL, NULL, + stream_ca, stream_da, &peer2); + setup_state = PEER2_STREAM_CONNECT; + break; + default: + GNUNET_assert (0); + } +} - /* GNUNET_log_setup ("test_stream_local", */ - /* "DEBUG", */ - /* NULL); */ - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Starting test\n"); - /* Duplicate the configuration */ - config = GNUNET_CONFIGURATION_dup (cfg); +/** + * Controller event callback + * + * @param cls NULL + * @param event the controller event + */ +static void +controller_event_cb (void *cls, + const struct GNUNET_TESTBED_EventInformation *event) +{ + switch (event->type) + { + case GNUNET_TESTBED_ET_OPERATION_FINISHED: + switch (setup_state) + { + case PEER1_STREAM_CONNECT: + case PEER2_STREAM_CONNECT: + GNUNET_assert (NULL == event->details.operation_finished.emsg); + break; + default: + GNUNET_assert (0); + } + break; + default: + GNUNET_assert (0); + } +} - hosts = GNUNET_TESTING_hosts_load (config); - - pg = GNUNET_TESTING_peergroup_start (config, - 2, - GNUNET_TIME_relative_multiply - (GNUNET_TIME_UNIT_SECONDS, 3), - NULL, - &peergroup_ready, - NULL, - hosts); - GNUNET_assert (NULL != pg); - + +/** + * Signature of a main function for a testcase. + * + * @param cls closure + * @param num_peers number of peers in 'peers' + * @param peers handle to peers run in the testbed + */ +static void +test_master (void *cls, unsigned int num_peers, + struct GNUNET_TESTBED_Peer **peers) +{ + GNUNET_assert (NULL != peers); + GNUNET_assert (NULL != peers[0]); + GNUNET_assert (NULL != peers[1]); + peer1.peer = peers[0]; + peer2.peer = peers[1]; + op = GNUNET_TESTBED_peer_get_information (peer1.peer, + GNUNET_TESTBED_PIT_IDENTITY, + &peerinfo_cb, NULL); + setup_state = PEER1_GET_IDENTITY; abort_task = GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply - (GNUNET_TIME_UNIT_SECONDS, 40), &do_abort, + (GNUNET_TIME_UNIT_SECONDS, 1000), &do_abort, NULL); } + /** * Main function */ int main (int argc, char **argv) { - int ret; - - char *argv2[] = { "test-stream-2peers-halfclose", - "-L", "DEBUG", - "-c", "test_stream_local.conf", - NULL}; - - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - - ret = - GNUNET_PROGRAM_run ((sizeof (argv2) / sizeof (char *)) - 1, argv2, - "test-stream-2peers-halfclose", "nohelp", options, &run, NULL); - - if (GNUNET_OK != ret) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "run failed with error code %d\n", - ret); - return 1; - } + uint64_t event_mask; + + result = GNUNET_NO; + event_mask = 0; + event_mask |= (1LL << GNUNET_TESTBED_ET_OPERATION_FINISHED); + (void) GNUNET_TESTBED_test_run ("test_stream_2peers_halfclose", + "test_stream_local.conf", NUM_PEERS, + event_mask, + &controller_event_cb, NULL, &test_master, + NULL); if (GNUNET_SYSERR == result) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "test failed\n"); return 1; - } - GNUNET_log (GNUNET_ERROR_TYPE_INFO, "test ok\n"); return 0; } diff --git a/src/stream/test_stream_big.c b/src/stream/test_stream_big.c new file mode 100644 index 0000000..06d2a49 --- /dev/null +++ b/src/stream/test_stream_big.c @@ -0,0 +1,429 @@ +/* + This file is part of GNUnet. + (C) 2011, 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @file stream/test_stream_big.c + * @brief large data transfer using stream API between local peers + * @author Sree Harsha Totakura + */ + +#include + +#include "platform.h" +#include "gnunet_util_lib.h" +#include "gnunet_stream_lib.h" +#include "gnunet_testing_lib.h" + +#define LOG(kind, ...) \ + GNUNET_log (kind, __VA_ARGS__); + +#define TIME_REL_SECS(sec) \ + GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, sec) + + +/** + * Structure for holding peer's sockets and IO Handles + */ +struct PeerData +{ + /** + * Peer's stream socket + */ + struct GNUNET_STREAM_Socket *socket; + + struct GNUNET_PeerIdentity self; + + /** + * Peer's io write handle + */ + struct GNUNET_STREAM_WriteHandle *io_write_handle; + + /** + * Peer's io read handle + */ + struct GNUNET_STREAM_ReadHandle *io_read_handle; + + /** + * Peer's shutdown handle + */ + struct GNUNET_STREAM_ShutdownHandle *shutdown_handle; + + /** + * Bytes the peer has written + */ + unsigned int bytes_wrote; + + /** + * Byte the peer has read + */ + unsigned int bytes_read; +}; + +static struct PeerData peer1; +static struct PeerData peer2; +static struct GNUNET_STREAM_ListenSocket *peer2_listen_socket; +static const struct GNUNET_CONFIGURATION_Handle *config; + +static GNUNET_SCHEDULER_TaskIdentifier abort_task; +static GNUNET_SCHEDULER_TaskIdentifier read_task; +static GNUNET_SCHEDULER_TaskIdentifier write_task; + +#define DATA_SIZE 65536 /* 64KB */ +static uint32_t data[DATA_SIZE / 4]; /* 64KB array */ +static int result; + +/** + * Shutdown nicely + */ +static void +do_close (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + if (GNUNET_SCHEDULER_NO_TASK != abort_task) + GNUNET_SCHEDULER_cancel (abort_task); + if (NULL != peer1.socket) + GNUNET_STREAM_close (peer1.socket); + if (NULL != peer2.socket) + GNUNET_STREAM_close (peer2.socket); + if (NULL != peer2_listen_socket) + GNUNET_STREAM_listen_close (peer2_listen_socket); /* Close listen socket */ +} + + +/** + * Something went wrong and timed out. Kill everything and set error flag + */ +static void +do_abort (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: ABORT\n"); + if (GNUNET_SCHEDULER_NO_TASK != read_task) + GNUNET_SCHEDULER_cancel (read_task); + result = GNUNET_SYSERR; + abort_task = GNUNET_SCHEDULER_NO_TASK; + do_close (cls, tc); +} + + +/** + * Completion callback for shutdown + * + * @param cls the closure from GNUNET_STREAM_shutdown call + * @param operation the operation that was shutdown (SHUT_RD, SHUT_WR, + * SHUT_RDWR) + */ +static void +shutdown_completion (void *cls, + int operation) +{ + static int shutdowns; + + if (++shutdowns == 1) + { + peer1.shutdown_handle = NULL; + peer2.shutdown_handle = GNUNET_STREAM_shutdown (peer2.socket, SHUT_RDWR, + &shutdown_completion, cls); + return; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "STREAM shutdown successful\n"); + GNUNET_SCHEDULER_add_now (&do_close, cls); +} + + +/** + * Shutdown sockets gracefully + */ +static void +do_shutdown (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + result = GNUNET_OK; + peer1.shutdown_handle = GNUNET_STREAM_shutdown (peer1.socket, SHUT_RDWR, + &shutdown_completion, cls); +} + + +/** + * The write completion function; called upon writing some data to stream or + * upon error + * + * @param cls the closure from GNUNET_STREAM_write/read + * @param status the status of the stream at the time this function is called + * @param size the number of bytes read or written + */ +static void +write_completion (void *cls, + enum GNUNET_STREAM_Status status, + size_t size) +{ + struct PeerData *peer; + + peer = (struct PeerData *) cls; + GNUNET_assert (GNUNET_STREAM_OK == status); + GNUNET_assert (size <= DATA_SIZE); + peer->bytes_wrote += size; + + if (peer->bytes_wrote < DATA_SIZE) /* Have more data to send */ + { + peer->io_write_handle = + GNUNET_STREAM_write (peer->socket, + ((void *) data) + peer->bytes_wrote, + sizeof (data) - peer->bytes_wrote, + GNUNET_TIME_relative_multiply + (GNUNET_TIME_UNIT_SECONDS, 5), + &write_completion, + cls); + GNUNET_assert (NULL != peer->io_write_handle); + } + else + { + LOG (GNUNET_ERROR_TYPE_DEBUG, "Writing successfully finished\n"); + result = GNUNET_OK; + GNUNET_SCHEDULER_add_now (&do_shutdown, NULL); + } +} + + +/** + * Task for calling STREAM_write with a chunk of random data + * + * @param cls the peer data entity + * @param tc the task context + */ +static void +stream_write_task (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct PeerData *peer=cls; + unsigned int count; + + write_task = GNUNET_SCHEDULER_NO_TASK; + for (count=0; count < DATA_SIZE / 4; count++) + { + data[count]=GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK, + UINT32_MAX); + } + LOG (GNUNET_ERROR_TYPE_DEBUG, "Generation of random data complete\n"); + peer->io_write_handle = GNUNET_STREAM_write (peer->socket, + data, + sizeof (data), + GNUNET_TIME_relative_multiply + (GNUNET_TIME_UNIT_SECONDS, 10), + &write_completion, + peer); + GNUNET_assert (NULL != peer->io_write_handle); +} + + +/** + * Function executed after stream has been established + * + * @param cls the closure from GNUNET_STREAM_open + * @param socket socket to use to communicate with the other side (read/write) + */ +static void +stream_open_cb (void *cls, + struct GNUNET_STREAM_Socket *socket) +{ + struct PeerData *peer; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stream established from peer1\n"); + peer = (struct PeerData *) cls; + peer->bytes_wrote = 0; + GNUNET_assert (socket == peer1.socket); + GNUNET_assert (socket == peer->socket); + write_task = GNUNET_SCHEDULER_add_now (&stream_write_task, peer); +} + + +/** + * Scheduler call back; to be executed when a new stream is connected + * Called from listen connect for peer2 + */ +static void +stream_read_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc); + + +/** + * Input processor + * + * @param cls peer2 + * @param status the status of the stream at the time this function is called + * @param data traffic from the other side + * @param size the number of bytes available in data read + * @return number of bytes of processed from 'data' (any data remaining should be + * given to the next time the read processor is called). + */ +static size_t +input_processor (void *cls, + enum GNUNET_STREAM_Status status, + const void *input_data, + size_t size) +{ + struct PeerData *peer = cls; + + GNUNET_assert (GNUNET_STREAM_OK == status); + GNUNET_assert (&peer2 == peer); + GNUNET_assert (size < DATA_SIZE); + GNUNET_assert (0 == memcmp (((void *)data ) + peer->bytes_read, + input_data, size)); + peer->bytes_read += size; + + if (peer->bytes_read < DATA_SIZE) + { + GNUNET_assert (GNUNET_SCHEDULER_NO_TASK == read_task); + read_task = GNUNET_SCHEDULER_add_now (&stream_read_task, &peer2); + /* peer->io_read_handle = GNUNET_STREAM_read ((struct GNUNET_STREAM_Socket *) */ + /* peer->socket, */ + /* GNUNET_TIME_relative_multiply */ + /* (GNUNET_TIME_UNIT_SECONDS, 5), */ + /* &input_processor, */ + /* cls); */ + /* GNUNET_assert (NULL != peer->io_read_handle); */ + } + else + { + /* Peer2 has completed reading*/ + LOG (GNUNET_ERROR_TYPE_DEBUG, "Reading finished successfully\n"); + } + return size; +} + + +/** + * Scheduler call back; to be executed when a new stream is connected + * Called from listen connect for peer2 + */ +static void +stream_read_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct PeerData *peer = cls; + + read_task = GNUNET_SCHEDULER_NO_TASK; + GNUNET_assert (&peer2 == peer); + peer->io_read_handle = + GNUNET_STREAM_read (peer->socket, + GNUNET_TIME_relative_multiply + (GNUNET_TIME_UNIT_SECONDS, 10), + &input_processor, + peer); + GNUNET_assert (NULL != peer->io_read_handle); +} + + +/** + * Functions of this type are called upon new stream connection from other peers + * + * @param cls the closure from GNUNET_STREAM_listen + * @param socket the socket representing the stream + * @param initiator the identity of the peer who wants to establish a stream + * with us + * @return GNUNET_OK to keep the socket open, GNUNET_SYSERR to close the + * stream (the socket will be invalid after the call) + */ +static int +stream_listen_cb (void *cls, + struct GNUNET_STREAM_Socket *socket, + const struct GNUNET_PeerIdentity *initiator) +{ + if ((NULL == socket) || (NULL == initiator)) + { + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Binding error\n"); + if (GNUNET_SCHEDULER_NO_TASK != abort_task) + GNUNET_SCHEDULER_cancel (abort_task); + abort_task = GNUNET_SCHEDULER_add_now (&do_abort, NULL); + return GNUNET_OK; + } + GNUNET_assert (NULL != socket); + GNUNET_assert (socket != peer1.socket); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Peer connected: %s\n", GNUNET_i2s(initiator)); + + peer2.socket = socket; + peer2.bytes_read = 0; + read_task = GNUNET_SCHEDULER_add_now (&stream_read_task, &peer2); + return GNUNET_OK; +} + + +/** + * Listen success callback; connects a peer to stream as client + */ +static void +stream_connect (void) +{ + struct PeerData *peer = &peer1; + + /* Connect to stream */ + peer->socket = GNUNET_STREAM_open (config, + &peer2.self, /* Null for local peer? */ + 10, /* App port */ + &stream_open_cb, &peer1, + GNUNET_STREAM_OPTION_MAX_PAYLOAD_SIZE, 500, + GNUNET_STREAM_OPTION_END); + GNUNET_assert (NULL != peer->socket); +} + + +/** + * Initialize framework and start test + * + * @param cls closure + * @param cfg configuration of the peer that was started + * @param peer identity of the peer that was created + */ +static void +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) +{ + struct GNUNET_PeerIdentity self; + + GNUNET_TESTING_peer_get_identity (peer, &self); + config = cfg; + peer2_listen_socket = + GNUNET_STREAM_listen (config, + 10, /* App port */ + &stream_listen_cb, + NULL, + GNUNET_STREAM_OPTION_SIGNAL_LISTEN_SUCCESS, + &stream_connect, + GNUNET_STREAM_OPTION_END); + GNUNET_assert (NULL != peer2_listen_socket); + peer1.self = self; + peer2.self = self; + abort_task = + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply + (GNUNET_TIME_UNIT_SECONDS, 60), &do_abort, + NULL); +} + +/** + * Main function + */ +int main (int argc, char **argv) +{ + if (0 != GNUNET_TESTING_peer_run ("test_stream_big", + "test_stream_local.conf", + &run, NULL)) + return 1; + return (GNUNET_SYSERR == result) ? 1 : 0; +} + +/* end of test_stream_big.c */ diff --git a/src/stream/test_stream_local.c b/src/stream/test_stream_local.c index c9fab84..f3c8aae 100644 --- a/src/stream/test_stream_local.c +++ b/src/stream/test_stream_local.c @@ -32,7 +32,12 @@ #include "gnunet_stream_lib.h" #include "gnunet_testing_lib.h" -#define VERBOSE 1 +/** + * Relative seconds shorthand + */ +#define TIME_REL_SECS(sec) \ + GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, sec) + /** * Structure for holding peer's sockets and IO Handles @@ -47,12 +52,17 @@ struct PeerData /** * Peer's io write handle */ - struct GNUNET_STREAM_IOWriteHandle *io_write_handle; + struct GNUNET_STREAM_WriteHandle *io_write_handle; /** * Peer's io read handle */ - struct GNUNET_STREAM_IOReadHandle *io_read_handle; + struct GNUNET_STREAM_ReadHandle *io_read_handle; + + /** + * Peer's shutdown handle + */ + struct GNUNET_STREAM_ShutdownHandle *shutdown_handle; /** * Bytes the peer has written @@ -65,15 +75,14 @@ struct PeerData unsigned int bytes_read; }; -static struct GNUNET_OS_Process *arm_pid; static struct PeerData peer1; static struct PeerData peer2; static struct GNUNET_STREAM_ListenSocket *peer2_listen_socket; -static struct GNUNET_CONFIGURATION_Handle *config_peer1; -static struct GNUNET_CONFIGURATION_Handle *config_peer2; +static const struct GNUNET_CONFIGURATION_Handle *config; +static struct GNUNET_TESTING_Peer *self; +static struct GNUNET_PeerIdentity self_id; static GNUNET_SCHEDULER_TaskIdentifier abort_task; -static GNUNET_SCHEDULER_TaskIdentifier test_task; static char *data = "ABCD"; static int result; @@ -81,6 +90,7 @@ static int result; static int writing_success; static int reading_success; + /** * Input processor * @@ -117,6 +127,7 @@ stream_read_task (void *cls, GNUNET_assert (NULL != peer->io_read_handle); } + /** * The write completion function; called upon writing some data to stream or * upon error @@ -155,33 +166,21 @@ stream_write_task (void *cls, GNUNET_assert (NULL != peer->io_write_handle); } + /** * Shutdown nicely */ static void -do_shutdown (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +do_close (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { - GNUNET_STREAM_close (peer1.socket); + if (GNUNET_SCHEDULER_NO_TASK != abort_task) + GNUNET_SCHEDULER_cancel (abort_task); + if (NULL != peer1.socket) + GNUNET_STREAM_close (peer1.socket); if (NULL != peer2.socket) GNUNET_STREAM_close (peer2.socket); if (NULL != peer2_listen_socket) GNUNET_STREAM_listen_close (peer2_listen_socket); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: shutdown\n"); - if (0 != abort_task) - { - GNUNET_SCHEDULER_cancel (abort_task); - } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: arm\n"); - if (0 != GNUNET_OS_process_kill (arm_pid, SIGTERM)) - { - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); - } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: Wait\n"); - /* Free the duplicated configuration */ - GNUNET_CONFIGURATION_destroy (config_peer1); - GNUNET_CONFIGURATION_destroy (config_peer2); - GNUNET_assert (GNUNET_OK == GNUNET_OS_process_wait (arm_pid)); - GNUNET_OS_process_destroy (arm_pid); } @@ -192,14 +191,46 @@ static void do_abort (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: ABORT\n"); - if (0 != test_task) + result = GNUNET_SYSERR; + abort_task = GNUNET_SCHEDULER_NO_TASK; + do_close (cls, tc); +} + + +/** + * Completion callback for shutdown + * + * @param cls the closure from GNUNET_STREAM_shutdown call + * @param operation the operation that was shutdown (SHUT_RD, SHUT_WR, + * SHUT_RDWR) + */ +static void +shutdown_completion (void *cls, + int operation) +{ + static int shutdowns; + + if (++shutdowns == 1) { - GNUNET_SCHEDULER_cancel (test_task); - } + peer1.shutdown_handle = NULL; + peer2.shutdown_handle = GNUNET_STREAM_shutdown (peer2.socket, SHUT_RDWR, + &shutdown_completion, cls); + return; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "STREAM shutdown successful\n"); + GNUNET_SCHEDULER_add_now (&do_close, cls); +} - result = GNUNET_SYSERR; - abort_task = 0; - do_shutdown (cls, tc); + +/** + * Shutdown sockets gracefully + */ +static void +do_shutdown (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + result = GNUNET_OK; + peer1.shutdown_handle = GNUNET_STREAM_shutdown (peer1.socket, SHUT_RDWR, + &shutdown_completion, cls); } @@ -221,7 +252,6 @@ write_completion (void *cls, GNUNET_assert (GNUNET_STREAM_OK == status); GNUNET_assert (size <= strlen (data)); peer->bytes_wrote += size; - if (peer->bytes_wrote < strlen(data)) /* Have more data to send */ { GNUNET_SCHEDULER_add_now (&stream_write_task, peer); @@ -230,8 +260,7 @@ write_completion (void *cls, { GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Writing completed\n"); - - if (&peer1 == peer) /* Peer1 has finished writing; should read now */ + if (&peer1 == peer) /* Peer1 has finished writing; should read now */ { peer->bytes_read = 0; GNUNET_SCHEDULER_add_now (&stream_read_task, peer); @@ -261,7 +290,6 @@ stream_open_cb (void *cls, GNUNET_assert (&peer1 == peer); GNUNET_assert (socket == peer1.socket); GNUNET_assert (socket == peer->socket); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stream established from peer1\n"); peer->bytes_wrote = 0; GNUNET_SCHEDULER_add_now (&stream_write_task, peer); @@ -291,8 +319,7 @@ input_processor (void *cls, GNUNET_assert (0 == strncmp ((const char *) data + peer->bytes_read, (const char *) input_data, size)); - peer->bytes_read += size; - + peer->bytes_read += size; if (peer->bytes_read < strlen (data)) { GNUNET_SCHEDULER_add_now (&stream_read_task, peer); @@ -331,22 +358,23 @@ stream_listen_cb (void *cls, const struct GNUNET_PeerIdentity *initiator) { struct PeerData *peer=cls; - struct GNUNET_PeerIdentity self; + if ((NULL == socket) || (NULL == initiator)) + { + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Binding error\n"); + if (GNUNET_SCHEDULER_NO_TASK != abort_task) + GNUNET_SCHEDULER_cancel (abort_task); + abort_task = GNUNET_SCHEDULER_add_now (&do_abort, NULL); + return GNUNET_OK; + } GNUNET_assert (NULL != socket); GNUNET_assert (socket != peer1.socket); GNUNET_assert (&peer2 == peer); - - /* Get our identity */ - GNUNET_assert (GNUNET_OK == GNUNET_TESTING_get_peer_identity (config_peer1, - &self)); - GNUNET_assert (0 == memcmp (&self, + GNUNET_assert (0 == memcmp (&self_id, initiator, sizeof (struct GNUNET_PeerIdentity))); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Peer connected: %s\n", GNUNET_i2s(initiator)); - peer->socket = socket; peer->bytes_read = 0; GNUNET_SCHEDULER_add_now (&stream_read_task, &peer2); @@ -355,30 +383,13 @@ stream_listen_cb (void *cls, /** - * Testing function - * - * @param cls NULL - * @param tc the task context + * Listen success callback; connects a peer to stream as client */ static void -test (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +stream_connect (void) { - struct GNUNET_PeerIdentity self; - - test_task = GNUNET_SCHEDULER_NO_TASK; - /* Get our identity */ - GNUNET_assert (GNUNET_OK == GNUNET_TESTING_get_peer_identity (config_peer1, - &self)); - - peer2_listen_socket = GNUNET_STREAM_listen (config_peer2, - 10, /* App port */ - &stream_listen_cb, - &peer2); - GNUNET_assert (NULL != peer2_listen_socket); - - /* Connect to stream library */ - peer1.socket = GNUNET_STREAM_open (config_peer1, - &self, /* Null for local peer? */ + peer1.socket = GNUNET_STREAM_open (config, + &self_id, 10, /* App port */ &stream_open_cb, &peer1, @@ -386,37 +397,31 @@ test (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) GNUNET_assert (NULL != peer1.socket); } + /** * Initialize framework and start test */ static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) { - GNUNET_log_setup ("test_stream_local", -#if VERBOSE - "DEBUG", -#else - "WARNING", -#endif - NULL); - /* Duplicate the configuration */ - config_peer1 = GNUNET_CONFIGURATION_dup (cfg); - config_peer2 = GNUNET_CONFIGURATION_dup (cfg); - arm_pid = - GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-arm", - "gnunet-service-arm", -#if VERBOSE_ARM - "-L", "DEBUG", -#endif - "-c", "test_stream_local.conf", NULL); - - abort_task = - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply - (GNUNET_TIME_UNIT_SECONDS, 60), &do_abort, - NULL); - - test_task = GNUNET_SCHEDULER_add_now (&test, NULL); + config = cfg; + self = peer; + GNUNET_TESTING_peer_get_identity (peer, &self_id); + peer2_listen_socket = + GNUNET_STREAM_listen (config, + 10, /* App port */ + &stream_listen_cb, + &peer2, + GNUNET_STREAM_OPTION_SIGNAL_LISTEN_SUCCESS, + &stream_connect, + GNUNET_STREAM_OPTION_END); + GNUNET_assert (NULL != peer2_listen_socket); + abort_task = + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply + (GNUNET_TIME_UNIT_SECONDS, 30), &do_abort, + NULL); } /** @@ -424,35 +429,11 @@ run (void *cls, char *const *args, const char *cfgfile, */ int main (int argc, char **argv) { - int ret; - - char *const argv2[] = { "test-stream-local", - "-c", "test_stream_local.conf", -#if VERBOSE - "-L", "DEBUG", -#endif - NULL - }; - - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - - ret = - GNUNET_PROGRAM_run ((sizeof (argv2) / sizeof (char *)) - 1, argv2, - "test-stream-local", "nohelp", options, &run, NULL); - - if (GNUNET_OK != ret) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "run failed with error code %d\n", - ret); + if (0 != GNUNET_TESTING_peer_run ("test_stream_local", + "test_stream_local.conf", + &run, NULL)) return 1; - } - if (GNUNET_SYSERR == result) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "test failed\n"); - return 1; - } - GNUNET_log (GNUNET_ERROR_TYPE_INFO, "test ok\n"); - return 0; + return (GNUNET_SYSERR == result) ? 1 : 0; } + +/* end of test_stream_local.c */ diff --git a/src/stream/test_stream_local.conf b/src/stream/test_stream_local.conf index 884ecbc..35da4b4 100644 --- a/src/stream/test_stream_local.conf +++ b/src/stream/test_stream_local.conf @@ -1,3 +1,14 @@ +[lockmanager] +AUTOSTART = NO +ACCEPT_FROM = 127.0.0.1; +HOSTNAME = localhost +PORT = 12101 + +[statistics] +AUTOSTART = YES +ACCEPT_FROM = 127.0.0.1; +PORT = 12102 + [fs] AUTOSTART = NO @@ -5,7 +16,6 @@ AUTOSTART = NO AUTOSTART = NO [mesh] -DEBUG = YES AUTOSTART = YES ACCEPT_FROM = 127.0.0.1; HOSTNAME = localhost @@ -14,7 +24,6 @@ PORT = 10700 # PREFIX = xterm -geometry 100x85 -T peer1 -e gdb --args [dht] -DEBUG = NO AUTOSTART = YES ACCEPT_FROM6 = ::1; ACCEPT_FROM = 127.0.0.1; @@ -30,7 +39,6 @@ DATABASE = sqlite [transport] PLUGINS = tcp -DEBUG = NO ACCEPT_FROM6 = ::1; ACCEPT_FROM = 127.0.0.1; NEIGHBOUR_LIMIT = 50 @@ -44,28 +52,23 @@ WAN_QUOTA_IN = 3932160 PORT = 12092 [arm] -DEFAULTSERVICES = core +DEFAULTSERVICES = core lockmanager PORT = 12366 -DEBUG = NO [transport-tcp] TIMEOUT = 300 s PORT = 12368 [TESTING] -NUM_PEERS = 5 WEAKRANDOM = YES -DEBUG = YES -HOSTKEYSFILE = ../../contrib/testing_hostkeys.dat -MAX_CONCURRENT_SSH = 10 -USE_PROGRESSBARS = YES -PEERGROUP_TIMEOUT = 2400 s + +[testbed] +OVERLAY_TOPOLOGY = LINE [gnunetd] HOSTKEY = $SERVICEHOME/.hostkey [PATHS] -DEFAULTCONFIG = test_stream_local.conf SERVICEHOME = /tmp/test-stream/ [dns] @@ -73,3 +76,13 @@ AUTOSTART = NO [nse] AUTOSTART = NO + +[vpn] +AUTOSTART = NO + +[nat] +RETURN_LOCAL_ADDRESSES = YES + +[consensus] +AUTOSTART = NO + diff --git a/src/stream/test_stream_sequence_wraparound.c b/src/stream/test_stream_sequence_wraparound.c new file mode 100644 index 0000000..bbe9f1a --- /dev/null +++ b/src/stream/test_stream_sequence_wraparound.c @@ -0,0 +1,425 @@ +/* + This file is part of GNUnet. + (C) 2011, 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @file stream/test_stream_sequence_wraparound.c + * @brief test cases for sequence wrap around situations during data transfer + * @author Sree Harsha Totakura + */ + +#include + +#include "platform.h" +#include "gnunet_util_lib.h" +#include "gnunet_stream_lib.h" +#include "gnunet_testing_lib.h" + +/** + * Generic logging shorthand + */ +#define LOG(kind, ...) \ + GNUNET_log (kind, __VA_ARGS__); + +/** + * Relative seconds shorthand + */ +#define TIME_REL_SECS(sec) \ + GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, sec) + +/** + * Structure for holding peer's sockets and IO Handles + */ +struct PeerData +{ + /** + * Peer's stream socket + */ + struct GNUNET_STREAM_Socket *socket; + + /** + * Peer's io write handle + */ + struct GNUNET_STREAM_WriteHandle *io_write_handle; + + /** + * Peer's io read handle + */ + struct GNUNET_STREAM_ReadHandle *io_read_handle; + + /** + * Peer's shutdown handle + */ + struct GNUNET_STREAM_ShutdownHandle *shutdown_handle; + + /** + * Bytes the peer has written + */ + unsigned int bytes_wrote; + + /** + * Byte the peer has read + */ + unsigned int bytes_read; +}; + +static struct PeerData peer1; +static struct PeerData peer2; +static struct GNUNET_STREAM_ListenSocket *peer2_listen_socket; +static const struct GNUNET_CONFIGURATION_Handle *config; +static struct GNUNET_TESTING_Peer *self; +static struct GNUNET_PeerIdentity self_id; + +static GNUNET_SCHEDULER_TaskIdentifier abort_task; +static GNUNET_SCHEDULER_TaskIdentifier read_task; +static GNUNET_SCHEDULER_TaskIdentifier write_task; + +#define DATA_SIZE 65536 /* 64KB */ +static uint32_t data[DATA_SIZE / 4]; /* 64KB array */ +static int result; + +/** + * Shutdown nicely + */ +static void +do_close (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + if (GNUNET_SCHEDULER_NO_TASK != abort_task) + GNUNET_SCHEDULER_cancel (abort_task); + if (NULL != peer1.socket) + GNUNET_STREAM_close (peer1.socket); + if (NULL != peer2.socket) + GNUNET_STREAM_close (peer2.socket); + if (NULL != peer2_listen_socket) + GNUNET_STREAM_listen_close (peer2_listen_socket); /* Close listen socket */ +} + + +/** + * Something went wrong and timed out. Kill everything and set error flag + */ +static void +do_abort (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: ABORT\n"); + if (GNUNET_SCHEDULER_NO_TASK != read_task) + { + GNUNET_SCHEDULER_cancel (read_task); + } + result = GNUNET_SYSERR; + abort_task = GNUNET_SCHEDULER_NO_TASK; + do_close (cls, tc); +} + + +/** + * Completion callback for shutdown + * + * @param cls the closure from GNUNET_STREAM_shutdown call + * @param operation the operation that was shutdown (SHUT_RD, SHUT_WR, + * SHUT_RDWR) + */ +static void +shutdown_completion (void *cls, + int operation) +{ + static int shutdowns; + + if (++shutdowns == 1) + { + peer1.shutdown_handle = NULL; + peer2.shutdown_handle = GNUNET_STREAM_shutdown (peer2.socket, SHUT_RDWR, + &shutdown_completion, cls); + return; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "STREAM shutdown successful\n"); + GNUNET_SCHEDULER_add_now (&do_close, cls); +} + + +/** + * Shutdown sockets gracefully + */ +static void +do_shutdown (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + result = GNUNET_OK; + peer1.shutdown_handle = GNUNET_STREAM_shutdown (peer1.socket, SHUT_RDWR, + &shutdown_completion, cls); +} + + +/** + * The write completion function; called upon writing some data to stream or + * upon error + * + * @param cls the closure from GNUNET_STREAM_write/read + * @param status the status of the stream at the time this function is called + * @param size the number of bytes read or written + */ +static void +write_completion (void *cls, + enum GNUNET_STREAM_Status status, + size_t size) +{ + struct PeerData *peer; + + peer = (struct PeerData *) cls; + GNUNET_assert (GNUNET_STREAM_OK == status); + GNUNET_assert (size <= DATA_SIZE); + peer->bytes_wrote += size; + + if (peer->bytes_wrote < DATA_SIZE) /* Have more data to send */ + { + peer->io_write_handle = + GNUNET_STREAM_write (peer->socket, + ((void *) data) + peer->bytes_wrote, + DATA_SIZE - peer->bytes_wrote, + GNUNET_TIME_relative_multiply + (GNUNET_TIME_UNIT_SECONDS, 5), + &write_completion, + cls); + GNUNET_assert (NULL != peer->io_write_handle); + } + else + { + LOG (GNUNET_ERROR_TYPE_DEBUG, "Writing successfully finished\n"); + result = GNUNET_OK; + GNUNET_SCHEDULER_add_now (&do_shutdown, NULL); + } +} + + +/** + * Task for calling STREAM_write with a chunk of random data + * + * @param cls the peer data entity + * @param tc the task context + */ +static void +stream_write_task (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct PeerData *peer=cls; + unsigned int count; + + write_task = GNUNET_SCHEDULER_NO_TASK; + for (count=0; count < DATA_SIZE / 4; count++) + { + data[count]=GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK, + UINT32_MAX); + } + LOG (GNUNET_ERROR_TYPE_DEBUG, "Generation of random data complete\n"); + peer->io_write_handle = GNUNET_STREAM_write (peer->socket, + data, + DATA_SIZE, + GNUNET_TIME_relative_multiply + (GNUNET_TIME_UNIT_SECONDS, 10), + &write_completion, + peer); + GNUNET_assert (NULL != peer->io_write_handle); +} + + +/** + * Function executed after stream has been established + * + * @param cls the closure from GNUNET_STREAM_open + * @param socket socket to use to communicate with the other side (read/write) + */ +static void +stream_open_cb (void *cls, + struct GNUNET_STREAM_Socket *socket) +{ + struct PeerData *peer; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stream established from peer1\n"); + peer = (struct PeerData *) cls; + peer->bytes_wrote = 0; + GNUNET_assert (socket == peer1.socket); + GNUNET_assert (socket == peer->socket); + write_task = GNUNET_SCHEDULER_add_now (&stream_write_task, peer); +} + + +/** + * Scheduler call back; to be executed when a new stream is connected + * Called from listen connect for peer2 + */ +static void +stream_read_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc); + + +/** + * Input processor + * + * @param cls peer2 + * @param status the status of the stream at the time this function is called + * @param data traffic from the other side + * @param size the number of bytes available in data read + * @return number of bytes of processed from 'data' (any data remaining should be + * given to the next time the read processor is called). + */ +static size_t +input_processor (void *cls, + enum GNUNET_STREAM_Status status, + const void *input_data, + size_t size) +{ + struct PeerData *peer = cls; + + GNUNET_assert (GNUNET_STREAM_OK == status); + GNUNET_assert (&peer2 == peer); + GNUNET_assert (size < DATA_SIZE); + GNUNET_assert (0 == memcmp (((void *)data ) + peer->bytes_read, + input_data, size)); + peer->bytes_read += size; + + if (peer->bytes_read < DATA_SIZE) + { + GNUNET_assert (GNUNET_SCHEDULER_NO_TASK == read_task); + read_task = GNUNET_SCHEDULER_add_now (&stream_read_task, &peer2); + } + else + { + /* Peer2 has completed reading*/ + LOG (GNUNET_ERROR_TYPE_DEBUG, "Reading finished successfully\n"); + } + return size; +} + + +/** + * Scheduler call back; to be executed when a new stream is connected + * Called from listen connect for peer2 + */ +static void +stream_read_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct PeerData *peer = cls; + + read_task = GNUNET_SCHEDULER_NO_TASK; + GNUNET_assert (&peer2 == peer); + peer->io_read_handle = + GNUNET_STREAM_read (peer->socket, + GNUNET_TIME_relative_multiply + (GNUNET_TIME_UNIT_SECONDS, 10), + &input_processor, + peer); + GNUNET_assert (NULL != peer->io_read_handle); +} + + +/** + * Functions of this type are called upon new stream connection from other peers + * + * @param cls the closure from GNUNET_STREAM_listen + * @param socket the socket representing the stream + * @param initiator the identity of the peer who wants to establish a stream + * with us + * @return GNUNET_OK to keep the socket open, GNUNET_SYSERR to close the + * stream (the socket will be invalid after the call) + */ +static int +stream_listen_cb (void *cls, + struct GNUNET_STREAM_Socket *socket, + const struct GNUNET_PeerIdentity *initiator) +{ + if ((NULL == socket) || (NULL == initiator)) + { + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Binding error\n"); + if (GNUNET_SCHEDULER_NO_TASK != abort_task) + GNUNET_SCHEDULER_cancel (abort_task); + abort_task = GNUNET_SCHEDULER_add_now (&do_abort, NULL); + return GNUNET_OK; + } + GNUNET_assert (NULL != socket); + GNUNET_assert (socket != peer1.socket); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Peer connected: %s\n", GNUNET_i2s(initiator)); + peer2.socket = socket; + peer2.bytes_read = 0; + read_task = GNUNET_SCHEDULER_add_now (&stream_read_task, &peer2); + return GNUNET_OK; +} + + +/** + * Listen success callback; connects a peer to stream as client + */ +static void +stream_connect (void) +{ + peer1.socket = + GNUNET_STREAM_open (config, + &self_id, /* Null for local peer? */ + 10, /* App port */ + &stream_open_cb, + &peer1, + GNUNET_STREAM_OPTION_TESTING_SET_WRITE_SEQUENCE_NUMBER, + UINT32_MAX - GNUNET_CRYPTO_random_u32 + (GNUNET_CRYPTO_QUALITY_WEAK, 64), + GNUNET_STREAM_OPTION_MAX_PAYLOAD_SIZE, 500, + GNUNET_STREAM_OPTION_END); + GNUNET_assert (NULL != peer1.socket); +} + + +/** + * Initialize framework and start test + */ +static void +run (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) +{ + config = cfg; + self = peer; + (void) GNUNET_TESTING_peer_get_identity (peer, &self_id); + peer2_listen_socket = + GNUNET_STREAM_listen (config, + 10, /* App port */ + &stream_listen_cb, + NULL, + GNUNET_STREAM_OPTION_LISTEN_TIMEOUT, + 60 * 1000, + GNUNET_STREAM_OPTION_SIGNAL_LISTEN_SUCCESS, + &stream_connect, + GNUNET_STREAM_OPTION_END); + GNUNET_assert (NULL != peer2_listen_socket); + abort_task = + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply + (GNUNET_TIME_UNIT_SECONDS, 100), &do_abort, + NULL); +} + + +/** + * Main function + */ +int main (int argc, char **argv) +{ + if (0 != GNUNET_TESTING_peer_run ("test_stream_sequence_wraparound", + "test_stream_local.conf", + &run, NULL)) + return 1; + return (GNUNET_SYSERR == result) ? 1 : 0; +} + +/* end of test_stream_sequence_wraparound.c */ diff --git a/src/sysmon/Makefile.am b/src/sysmon/Makefile.am new file mode 100644 index 0000000..16fed20 --- /dev/null +++ b/src/sysmon/Makefile.am @@ -0,0 +1,73 @@ +INCLUDES = -I$(top_srcdir)/src/include + +pkgcfgdir= $(pkgdatadir)/config.d/ + +libexecdir= $(pkglibdir)/libexec/ + +if HAVE_LIBGTOP + GN_LIBTOP = -lgtop-2.0 -lglib-2.0 + GN_SYSMON_TEST_INIT = test_glibtop + GN_SYSMON_TEST_PROCESS = test_glibtop_process + GN_SYSMON_TEST_NETWORK = test_glibtop_network +endif + +pkgcfg_DATA = \ + sysmon.conf + +if MINGW + WINFLAGS = -Wl,--no-undefined -Wl,--export-all-symbols +endif + +if USE_COVERAGE + AM_CFLAGS = -fprofile-arcs -ftest-coverage +endif + +libexec_PROGRAMS = \ + gnunet_service_sysmon + +check_PROGRAMS = \ + $(GN_SYSMON_TEST_INIT) \ + $(GN_SYSMON_TEST_PROCESS) \ + $(GN_SYSMON_TEST_NETWORK) + +gnunet_service_sysmon_SOURCES = \ + gnunet-service-sysmon.c +gnunet_service_sysmon_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/statistics/libgnunetstatistics.la \ + $(GN_LIBTOP) \ + $(GN_LIBINTL) + +if HAVE_GLIB2 +test_glibtop_SOURCES = \ + test_glibtop.c +test_glibtop_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/statistics/libgnunetstatistics.la \ + $(GN_LIBTOP) \ + $(GN_LIBINTL) + +test_glibtop_process_SOURCES = \ + test_glibtop_process.c +test_glibtop_process_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/statistics/libgnunetstatistics.la \ + $(GN_LIBTOP) \ + $(GN_LIBINTL) + +test_glibtop_network_SOURCES = \ + test_glibtop_network.c +test_glibtop_network_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/statistics/libgnunetstatistics.la \ + $(GN_LIBTOP) \ + $(GN_LIBINTL) +endif + + +if ENABLE_TEST_RUN +TESTS = $(check_PROGRAMS) +endif + +EXTRA_DIST = \ +sysmon-properties.conf diff --git a/src/sysmon/Makefile.in b/src/sysmon/Makefile.in new file mode 100644 index 0000000..4a92546 --- /dev/null +++ b/src/sysmon/Makefile.in @@ -0,0 +1,928 @@ +# Makefile.in generated by automake 1.11.6 from Makefile.am. +# @configure_input@ + +# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, +# 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Free Software +# Foundation, Inc. +# This Makefile.in is free software; the Free Software Foundation +# gives unlimited permission to copy and/or distribute it, +# with or without modifications, as long as this notice is preserved. + +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY, to the extent permitted by law; without +# even the implied warranty of MERCHANTABILITY or FITNESS FOR A +# PARTICULAR PURPOSE. + +@SET_MAKE@ + + +VPATH = @srcdir@ +am__make_dryrun = \ + { \ + am__dry=no; \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + echo 'am--echo: ; @echo "AM" OK' | $(MAKE) -f - 2>/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } +pkgdatadir = $(datadir)/@PACKAGE@ +pkgincludedir = $(includedir)/@PACKAGE@ +pkglibdir = $(libdir)/@PACKAGE@ +pkglibexecdir = $(libexecdir)/@PACKAGE@ +am__cd = CDPATH="$${ZSH_VERSION+.}$(PATH_SEPARATOR)" && cd +install_sh_DATA = $(install_sh) -c -m 644 +install_sh_PROGRAM = $(install_sh) -c +install_sh_SCRIPT = $(install_sh) -c +INSTALL_HEADER = $(INSTALL_DATA) +transform = $(program_transform_name) +NORMAL_INSTALL = : +PRE_INSTALL = : +POST_INSTALL = : +NORMAL_UNINSTALL = : +PRE_UNINSTALL = : +POST_UNINSTALL = : +build_triplet = @build@ +host_triplet = @host@ +target_triplet = @target@ +libexec_PROGRAMS = gnunet_service_sysmon$(EXEEXT) +check_PROGRAMS = $(am__EXEEXT_1) $(am__EXEEXT_2) $(am__EXEEXT_3) +subdir = src/sysmon +DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in \ + $(srcdir)/sysmon.conf.in +ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 +am__aclocal_m4_deps = $(top_srcdir)/m4/absolute-header.m4 \ + $(top_srcdir)/m4/align.m4 $(top_srcdir)/m4/argz.m4 \ + $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/glib-2.0.m4 \ + $(top_srcdir)/m4/iconv.m4 $(top_srcdir)/m4/lib-ld.m4 \ + $(top_srcdir)/m4/lib-link.m4 $(top_srcdir)/m4/lib-prefix.m4 \ + $(top_srcdir)/m4/libcurl.m4 $(top_srcdir)/m4/libgcrypt.m4 \ + $(top_srcdir)/m4/libtool.m4 $(top_srcdir)/m4/libunistring.m4 \ + $(top_srcdir)/m4/ltdl.m4 $(top_srcdir)/m4/ltoptions.m4 \ + $(top_srcdir)/m4/ltsugar.m4 $(top_srcdir)/m4/ltversion.m4 \ + $(top_srcdir)/m4/lt~obsolete.m4 $(top_srcdir)/m4/nls.m4 \ + $(top_srcdir)/m4/pkg.m4 $(top_srcdir)/m4/po.m4 \ + $(top_srcdir)/m4/progtest.m4 $(top_srcdir)/acinclude.m4 \ + $(top_srcdir)/configure.ac +am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ + $(ACLOCAL_M4) +mkinstalldirs = $(install_sh) -d +CONFIG_HEADER = $(top_builddir)/gnunet_config.h +CONFIG_CLEAN_FILES = sysmon.conf +CONFIG_CLEAN_VPATH_FILES = +@HAVE_LIBGTOP_TRUE@am__EXEEXT_1 = test_glibtop$(EXEEXT) +@HAVE_LIBGTOP_TRUE@am__EXEEXT_2 = test_glibtop_process$(EXEEXT) +@HAVE_LIBGTOP_TRUE@am__EXEEXT_3 = test_glibtop_network$(EXEEXT) +am__installdirs = "$(DESTDIR)$(libexecdir)" "$(DESTDIR)$(pkgcfgdir)" +PROGRAMS = $(libexec_PROGRAMS) +am_gnunet_service_sysmon_OBJECTS = gnunet-service-sysmon.$(OBJEXT) +gnunet_service_sysmon_OBJECTS = $(am_gnunet_service_sysmon_OBJECTS) +am__DEPENDENCIES_1 = +gnunet_service_sysmon_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/statistics/libgnunetstatistics.la \ + $(am__DEPENDENCIES_1) $(am__DEPENDENCIES_1) +AM_V_lt = $(am__v_lt_@AM_V@) +am__v_lt_ = $(am__v_lt_@AM_DEFAULT_V@) +am__v_lt_0 = --silent +am__test_glibtop_SOURCES_DIST = test_glibtop.c +@HAVE_GLIB2_TRUE@am_test_glibtop_OBJECTS = test_glibtop.$(OBJEXT) +test_glibtop_OBJECTS = $(am_test_glibtop_OBJECTS) +@HAVE_GLIB2_TRUE@test_glibtop_DEPENDENCIES = \ +@HAVE_GLIB2_TRUE@ $(top_builddir)/src/util/libgnunetutil.la \ +@HAVE_GLIB2_TRUE@ $(top_builddir)/src/statistics/libgnunetstatistics.la \ +@HAVE_GLIB2_TRUE@ $(am__DEPENDENCIES_1) $(am__DEPENDENCIES_1) +am__test_glibtop_network_SOURCES_DIST = test_glibtop_network.c +@HAVE_GLIB2_TRUE@am_test_glibtop_network_OBJECTS = \ +@HAVE_GLIB2_TRUE@ test_glibtop_network.$(OBJEXT) +test_glibtop_network_OBJECTS = $(am_test_glibtop_network_OBJECTS) +@HAVE_GLIB2_TRUE@test_glibtop_network_DEPENDENCIES = \ +@HAVE_GLIB2_TRUE@ $(top_builddir)/src/util/libgnunetutil.la \ +@HAVE_GLIB2_TRUE@ $(top_builddir)/src/statistics/libgnunetstatistics.la \ +@HAVE_GLIB2_TRUE@ $(am__DEPENDENCIES_1) $(am__DEPENDENCIES_1) +am__test_glibtop_process_SOURCES_DIST = test_glibtop_process.c +@HAVE_GLIB2_TRUE@am_test_glibtop_process_OBJECTS = \ +@HAVE_GLIB2_TRUE@ test_glibtop_process.$(OBJEXT) +test_glibtop_process_OBJECTS = $(am_test_glibtop_process_OBJECTS) +@HAVE_GLIB2_TRUE@test_glibtop_process_DEPENDENCIES = \ +@HAVE_GLIB2_TRUE@ $(top_builddir)/src/util/libgnunetutil.la \ +@HAVE_GLIB2_TRUE@ $(top_builddir)/src/statistics/libgnunetstatistics.la \ +@HAVE_GLIB2_TRUE@ $(am__DEPENDENCIES_1) $(am__DEPENDENCIES_1) +DEFAULT_INCLUDES = -I.@am__isrc@ -I$(top_builddir) +depcomp = $(SHELL) $(top_srcdir)/depcomp +am__depfiles_maybe = depfiles +am__mv = mv -f +COMPILE = $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) \ + $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) +LTCOMPILE = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ + $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) \ + $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) \ + $(AM_CFLAGS) $(CFLAGS) +AM_V_CC = $(am__v_CC_@AM_V@) +am__v_CC_ = $(am__v_CC_@AM_DEFAULT_V@) +am__v_CC_0 = @echo " CC " $@; +AM_V_at = $(am__v_at_@AM_V@) +am__v_at_ = $(am__v_at_@AM_DEFAULT_V@) +am__v_at_0 = @ +CCLD = $(CC) +LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ + $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ + $(AM_LDFLAGS) $(LDFLAGS) -o $@ +AM_V_CCLD = $(am__v_CCLD_@AM_V@) +am__v_CCLD_ = $(am__v_CCLD_@AM_DEFAULT_V@) +am__v_CCLD_0 = @echo " CCLD " $@; +AM_V_GEN = $(am__v_GEN_@AM_V@) +am__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@) +am__v_GEN_0 = @echo " GEN " $@; +SOURCES = $(gnunet_service_sysmon_SOURCES) $(test_glibtop_SOURCES) \ + $(test_glibtop_network_SOURCES) \ + $(test_glibtop_process_SOURCES) +DIST_SOURCES = $(gnunet_service_sysmon_SOURCES) \ + $(am__test_glibtop_SOURCES_DIST) \ + $(am__test_glibtop_network_SOURCES_DIST) \ + $(am__test_glibtop_process_SOURCES_DIST) +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac +am__vpath_adj_setup = srcdirstrip=`echo "$(srcdir)" | sed 's|.|.|g'`; +am__vpath_adj = case $$p in \ + $(srcdir)/*) f=`echo "$$p" | sed "s|^$$srcdirstrip/||"`;; \ + *) f=$$p;; \ + esac; +am__strip_dir = f=`echo $$p | sed -e 's|^.*/||'`; +am__install_max = 40 +am__nobase_strip_setup = \ + srcdirstrip=`echo "$(srcdir)" | sed 's/[].[^$$\\*|]/\\\\&/g'` +am__nobase_strip = \ + for p in $$list; do echo "$$p"; done | sed -e "s|$$srcdirstrip/||" +am__nobase_list = $(am__nobase_strip_setup); \ + for p in $$list; do echo "$$p $$p"; done | \ + sed "s| $$srcdirstrip/| |;"' / .*\//!s/ .*/ ./; s,\( .*\)/[^/]*$$,\1,' | \ + $(AWK) 'BEGIN { files["."] = "" } { files[$$2] = files[$$2] " " $$1; \ + if (++n[$$2] == $(am__install_max)) \ + { print $$2, files[$$2]; n[$$2] = 0; files[$$2] = "" } } \ + END { for (dir in files) print dir, files[dir] }' +am__base_list = \ + sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \ + sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g' +am__uninstall_files_from_dir = { \ + test -z "$$files" \ + || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \ + || { echo " ( cd '$$dir' && rm -f" $$files ")"; \ + $(am__cd) "$$dir" && rm -f $$files; }; \ + } +DATA = $(pkgcfg_DATA) +ETAGS = etags +CTAGS = ctags +am__tty_colors = \ +red=; grn=; lgn=; blu=; std= +DISTFILES = $(DIST_COMMON) $(DIST_SOURCES) $(TEXINFOS) $(EXTRA_DIST) +ACLOCAL = @ACLOCAL@ +AMTAR = @AMTAR@ +AM_DEFAULT_VERBOSITY = @AM_DEFAULT_VERBOSITY@ +AR = @AR@ +ARGZ_H = @ARGZ_H@ +AS = @AS@ +AUTOCONF = @AUTOCONF@ +AUTOHEADER = @AUTOHEADER@ +AUTOMAKE = @AUTOMAKE@ +AWK = @AWK@ +CC = @CC@ +CCDEPMODE = @CCDEPMODE@ +CFLAGS = @CFLAGS@ +CPP = @CPP@ +CPPFLAGS = @CPPFLAGS@ +CXX = @CXX@ +CXXCPP = @CXXCPP@ +CXXDEPMODE = @CXXDEPMODE@ +CXXFLAGS = @CXXFLAGS@ +CYGPATH_W = @CYGPATH_W@ +DEFAULT_INTERFACE = @DEFAULT_INTERFACE@ +DEFS = @DEFS@ +DEPDIR = @DEPDIR@ +DLLDIR = @DLLDIR@ +DLLTOOL = @DLLTOOL@ +DSYMUTIL = @DSYMUTIL@ +DUMPBIN = @DUMPBIN@ +ECHO_C = @ECHO_C@ +ECHO_N = @ECHO_N@ +ECHO_T = @ECHO_T@ +EGREP = @EGREP@ +EXEEXT = @EXEEXT@ +EXT_LIBS = @EXT_LIBS@ +EXT_LIB_PATH = @EXT_LIB_PATH@ +FGREP = @FGREP@ +GLIB_CFLAGS = @GLIB_CFLAGS@ +GLIB_GENMARSHAL = @GLIB_GENMARSHAL@ +GLIB_LIBS = @GLIB_LIBS@ +GLIB_MKENUMS = @GLIB_MKENUMS@ +GMSGFMT = @GMSGFMT@ +GMSGFMT_015 = @GMSGFMT_015@ +GNUNETDNS_GROUP = @GNUNETDNS_GROUP@ +GN_DAEMON_CONFIG_DIR = @GN_DAEMON_CONFIG_DIR@ +GN_DAEMON_HOME_DIR = @GN_DAEMON_HOME_DIR@ +GN_INTLINCL = @GN_INTLINCL@ +GN_LIBINTL = @GN_LIBINTL@ +GN_LIB_LDFLAGS = @GN_LIB_LDFLAGS@ +GN_PLUGIN_LDFLAGS = @GN_PLUGIN_LDFLAGS@ +GN_USER_HOME_DIR = @GN_USER_HOME_DIR@ +GOBJECT_QUERY = @GOBJECT_QUERY@ +GREP = @GREP@ +HAVE_LIBUNISTRING = @HAVE_LIBUNISTRING@ +INCLTDL = @INCLTDL@ +INSTALL = @INSTALL@ +INSTALL_DATA = @INSTALL_DATA@ +INSTALL_PROGRAM = @INSTALL_PROGRAM@ +INSTALL_SCRIPT = @INSTALL_SCRIPT@ +INSTALL_STRIP_PROGRAM = @INSTALL_STRIP_PROGRAM@ +INTLLIBS = @INTLLIBS@ +INTL_MACOSX_LIBS = @INTL_MACOSX_LIBS@ +JAVAPORT = @JAVAPORT@ +LD = @LD@ +LDFLAGS = @LDFLAGS@ +LIBADD_DL = @LIBADD_DL@ +LIBADD_DLD_LINK = @LIBADD_DLD_LINK@ +LIBADD_DLOPEN = @LIBADD_DLOPEN@ +LIBADD_SHL_LOAD = @LIBADD_SHL_LOAD@ +LIBCURL = @LIBCURL@ +LIBCURL_CPPFLAGS = @LIBCURL_CPPFLAGS@ +LIBGCRYPT_CFLAGS = @LIBGCRYPT_CFLAGS@ +LIBGCRYPT_CONFIG = @LIBGCRYPT_CONFIG@ +LIBGCRYPT_LIBS = @LIBGCRYPT_LIBS@ +LIBGTOP_CFLAGS = @LIBGTOP_CFLAGS@ +LIBGTOP_LIBS = @LIBGTOP_LIBS@ +LIBICONV = @LIBICONV@ +LIBINTL = @LIBINTL@ +LIBLTDL = @LIBLTDL@ +LIBOBJS = @LIBOBJS@ +LIBPREFIX = @LIBPREFIX@ +LIBS = @LIBS@ +LIBTOOL = @LIBTOOL@ +LIBUNISTRING = @LIBUNISTRING@ +LIPO = @LIPO@ +LN_S = @LN_S@ +LTDLDEPS = @LTDLDEPS@ +LTDLINCL = @LTDLINCL@ +LTDLOPEN = @LTDLOPEN@ +LTLIBICONV = @LTLIBICONV@ +LTLIBINTL = @LTLIBINTL@ +LTLIBOBJS = @LTLIBOBJS@ +LTLIBUNISTRING = @LTLIBUNISTRING@ +LT_CONFIG_H = @LT_CONFIG_H@ +LT_DLLOADERS = @LT_DLLOADERS@ +LT_DLPREOPEN = @LT_DLPREOPEN@ +MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ +MKDIR_P = @MKDIR_P@ +MONKEYPREFIX = @MONKEYPREFIX@ +MSGFMT = @MSGFMT@ +MSGFMT_015 = @MSGFMT_015@ +MSGMERGE = @MSGMERGE@ +MYSQL_CPPFLAGS = @MYSQL_CPPFLAGS@ +MYSQL_LDFLAGS = @MYSQL_LDFLAGS@ +NM = @NM@ +NMEDIT = @NMEDIT@ +NSS_DIR = @NSS_DIR@ +OBJC = @OBJC@ +OBJCDEPMODE = @OBJCDEPMODE@ +OBJCFLAGS = @OBJCFLAGS@ +OBJDUMP = @OBJDUMP@ +OBJEXT = @OBJEXT@ +OTOOL = @OTOOL@ +OTOOL64 = @OTOOL64@ +PACKAGE = @PACKAGE@ +PACKAGE_BUGREPORT = @PACKAGE_BUGREPORT@ +PACKAGE_NAME = @PACKAGE_NAME@ +PACKAGE_STRING = @PACKAGE_STRING@ +PACKAGE_TARNAME = @PACKAGE_TARNAME@ +PACKAGE_URL = @PACKAGE_URL@ +PACKAGE_VERSION = @PACKAGE_VERSION@ +PATH_SEPARATOR = @PATH_SEPARATOR@ +PKG_CONFIG = @PKG_CONFIG@ +POSTGRES_CPPFLAGS = @POSTGRES_CPPFLAGS@ +POSTGRES_LDFLAGS = @POSTGRES_LDFLAGS@ +POSUB = @POSUB@ +PYTHON = @PYTHON@ +PYTHON_EXEC_PREFIX = @PYTHON_EXEC_PREFIX@ +PYTHON_PLATFORM = @PYTHON_PLATFORM@ +PYTHON_PREFIX = @PYTHON_PREFIX@ +PYTHON_VERSION = @PYTHON_VERSION@ +RANLIB = @RANLIB@ +SED = @SED@ +SET_MAKE = @SET_MAKE@ +SHELL = @SHELL@ +SQLITE_CPPFLAGS = @SQLITE_CPPFLAGS@ +SQLITE_LDFLAGS = @SQLITE_LDFLAGS@ +STRIP = @STRIP@ +SUDO_BINARY = @SUDO_BINARY@ +UNIXONLY = @UNIXONLY@ +USE_NLS = @USE_NLS@ +VERSION = @VERSION@ +XGETTEXT = @XGETTEXT@ +XGETTEXT_015 = @XGETTEXT_015@ +XMKMF = @XMKMF@ +X_CFLAGS = @X_CFLAGS@ +X_EXTRA_LIBS = @X_EXTRA_LIBS@ +X_LIBS = @X_LIBS@ +X_PRE_LIBS = @X_PRE_LIBS@ +_libcurl_config = @_libcurl_config@ +abs_builddir = @abs_builddir@ +abs_srcdir = @abs_srcdir@ +abs_top_builddir = @abs_top_builddir@ +abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ +ac_ct_CC = @ac_ct_CC@ +ac_ct_CXX = @ac_ct_CXX@ +ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ +ac_ct_OBJC = @ac_ct_OBJC@ +am__include = @am__include@ +am__leading_dot = @am__leading_dot@ +am__quote = @am__quote@ +am__tar = @am__tar@ +am__untar = @am__untar@ +bindir = @bindir@ +build = @build@ +build_alias = @build_alias@ +build_cpu = @build_cpu@ +build_os = @build_os@ +build_target = @build_target@ +build_vendor = @build_vendor@ +builddir = @builddir@ +datadir = @datadir@ +datarootdir = @datarootdir@ +docdir = @docdir@ +dvidir = @dvidir@ +exec_prefix = @exec_prefix@ +gitcommand = @gitcommand@ +host = @host@ +host_alias = @host_alias@ +host_cpu = @host_cpu@ +host_os = @host_os@ +host_vendor = @host_vendor@ +htmldir = @htmldir@ +includedir = @includedir@ +infodir = @infodir@ +install_sh = @install_sh@ +libdir = @libdir@ +libexecdir = $(pkglibdir)/libexec/ +localedir = @localedir@ +localstatedir = @localstatedir@ +ltdl_LIBOBJS = @ltdl_LIBOBJS@ +ltdl_LTLIBOBJS = @ltdl_LTLIBOBJS@ +mandir = @mandir@ +mkdir_p = @mkdir_p@ +oldincludedir = @oldincludedir@ +pdfdir = @pdfdir@ +pkgpyexecdir = @pkgpyexecdir@ +pkgpythondir = @pkgpythondir@ +prefix = @prefix@ +program_transform_name = @program_transform_name@ +psdir = @psdir@ +pyexecdir = @pyexecdir@ +pythondir = @pythondir@ +sbindir = @sbindir@ +sharedstatedir = @sharedstatedir@ +srcdir = @srcdir@ +subdirs = @subdirs@ +svnversioncommand = @svnversioncommand@ +sys_symbol_underscore = @sys_symbol_underscore@ +sysconfdir = @sysconfdir@ +target = @target@ +target_alias = @target_alias@ +target_cpu = @target_cpu@ +target_os = @target_os@ +target_vendor = @target_vendor@ +top_build_prefix = @top_build_prefix@ +top_builddir = @top_builddir@ +top_srcdir = @top_srcdir@ +INCLUDES = -I$(top_srcdir)/src/include +pkgcfgdir = $(pkgdatadir)/config.d/ +@HAVE_LIBGTOP_TRUE@GN_LIBTOP = -lgtop-2.0 -lglib-2.0 +@HAVE_LIBGTOP_TRUE@GN_SYSMON_TEST_INIT = test_glibtop +@HAVE_LIBGTOP_TRUE@GN_SYSMON_TEST_PROCESS = test_glibtop_process +@HAVE_LIBGTOP_TRUE@GN_SYSMON_TEST_NETWORK = test_glibtop_network +pkgcfg_DATA = \ + sysmon.conf + +@MINGW_TRUE@WINFLAGS = -Wl,--no-undefined -Wl,--export-all-symbols +@USE_COVERAGE_TRUE@AM_CFLAGS = -fprofile-arcs -ftest-coverage +gnunet_service_sysmon_SOURCES = \ + gnunet-service-sysmon.c + +gnunet_service_sysmon_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/statistics/libgnunetstatistics.la \ + $(GN_LIBTOP) \ + $(GN_LIBINTL) + +@HAVE_GLIB2_TRUE@test_glibtop_SOURCES = \ +@HAVE_GLIB2_TRUE@ test_glibtop.c + +@HAVE_GLIB2_TRUE@test_glibtop_LDADD = \ +@HAVE_GLIB2_TRUE@ $(top_builddir)/src/util/libgnunetutil.la \ +@HAVE_GLIB2_TRUE@ $(top_builddir)/src/statistics/libgnunetstatistics.la \ +@HAVE_GLIB2_TRUE@ $(GN_LIBTOP) \ +@HAVE_GLIB2_TRUE@ $(GN_LIBINTL) + +@HAVE_GLIB2_TRUE@test_glibtop_process_SOURCES = \ +@HAVE_GLIB2_TRUE@ test_glibtop_process.c + +@HAVE_GLIB2_TRUE@test_glibtop_process_LDADD = \ +@HAVE_GLIB2_TRUE@ $(top_builddir)/src/util/libgnunetutil.la \ +@HAVE_GLIB2_TRUE@ $(top_builddir)/src/statistics/libgnunetstatistics.la \ +@HAVE_GLIB2_TRUE@ $(GN_LIBTOP) \ +@HAVE_GLIB2_TRUE@ $(GN_LIBINTL) + +@HAVE_GLIB2_TRUE@test_glibtop_network_SOURCES = \ +@HAVE_GLIB2_TRUE@ test_glibtop_network.c + +@HAVE_GLIB2_TRUE@test_glibtop_network_LDADD = \ +@HAVE_GLIB2_TRUE@ $(top_builddir)/src/util/libgnunetutil.la \ +@HAVE_GLIB2_TRUE@ $(top_builddir)/src/statistics/libgnunetstatistics.la \ +@HAVE_GLIB2_TRUE@ $(GN_LIBTOP) \ +@HAVE_GLIB2_TRUE@ $(GN_LIBINTL) + +@ENABLE_TEST_RUN_TRUE@TESTS = $(check_PROGRAMS) +EXTRA_DIST = \ +sysmon-properties.conf + +all: all-am + +.SUFFIXES: +.SUFFIXES: .c .lo .o .obj +$(srcdir)/Makefile.in: $(srcdir)/Makefile.am $(am__configure_deps) + @for dep in $?; do \ + case '$(am__configure_deps)' in \ + *$$dep*) \ + ( cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh ) \ + && { if test -f $@; then exit 0; else break; fi; }; \ + exit 1;; \ + esac; \ + done; \ + echo ' cd $(top_srcdir) && $(AUTOMAKE) --gnu src/sysmon/Makefile'; \ + $(am__cd) $(top_srcdir) && \ + $(AUTOMAKE) --gnu src/sysmon/Makefile +.PRECIOUS: Makefile +Makefile: $(srcdir)/Makefile.in $(top_builddir)/config.status + @case '$?' in \ + *config.status*) \ + cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh;; \ + *) \ + echo ' cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ $(am__depfiles_maybe)'; \ + cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ $(am__depfiles_maybe);; \ + esac; + +$(top_builddir)/config.status: $(top_srcdir)/configure $(CONFIG_STATUS_DEPENDENCIES) + cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh + +$(top_srcdir)/configure: $(am__configure_deps) + cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh +$(ACLOCAL_M4): $(am__aclocal_m4_deps) + cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh +$(am__aclocal_m4_deps): +sysmon.conf: $(top_builddir)/config.status $(srcdir)/sysmon.conf.in + cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ + +clean-checkPROGRAMS: + @list='$(check_PROGRAMS)'; test -n "$$list" || exit 0; \ + echo " rm -f" $$list; \ + rm -f $$list || exit $$?; \ + test -n "$(EXEEXT)" || exit 0; \ + list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ + echo " rm -f" $$list; \ + rm -f $$list +install-libexecPROGRAMS: $(libexec_PROGRAMS) + @$(NORMAL_INSTALL) + @list='$(libexec_PROGRAMS)'; test -n "$(libexecdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(libexecdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libexecdir)" || exit 1; \ + fi; \ + for p in $$list; do echo "$$p $$p"; done | \ + sed 's/$(EXEEXT)$$//' | \ + while read p p1; do if test -f $$p || test -f $$p1; \ + then echo "$$p"; echo "$$p"; else :; fi; \ + done | \ + sed -e 'p;s,.*/,,;n;h' -e 's|.*|.|' \ + -e 'p;x;s,.*/,,;s/$(EXEEXT)$$//;$(transform);s/$$/$(EXEEXT)/' | \ + sed 'N;N;N;s,\n, ,g' | \ + $(AWK) 'BEGIN { files["."] = ""; dirs["."] = 1 } \ + { d=$$3; if (dirs[d] != 1) { print "d", d; dirs[d] = 1 } \ + if ($$2 == $$4) files[d] = files[d] " " $$1; \ + else { print "f", $$3 "/" $$4, $$1; } } \ + END { for (d in files) print "f", d, files[d] }' | \ + while read type dir files; do \ + if test "$$dir" = .; then dir=; else dir=/$$dir; fi; \ + test -z "$$files" || { \ + echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files '$(DESTDIR)$(libexecdir)$$dir'"; \ + $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files "$(DESTDIR)$(libexecdir)$$dir" || exit $$?; \ + } \ + ; done + +uninstall-libexecPROGRAMS: + @$(NORMAL_UNINSTALL) + @list='$(libexec_PROGRAMS)'; test -n "$(libexecdir)" || list=; \ + files=`for p in $$list; do echo "$$p"; done | \ + sed -e 'h;s,^.*/,,;s/$(EXEEXT)$$//;$(transform)' \ + -e 's/$$/$(EXEEXT)/' `; \ + test -n "$$list" || exit 0; \ + echo " ( cd '$(DESTDIR)$(libexecdir)' && rm -f" $$files ")"; \ + cd "$(DESTDIR)$(libexecdir)" && rm -f $$files + +clean-libexecPROGRAMS: + @list='$(libexec_PROGRAMS)'; test -n "$$list" || exit 0; \ + echo " rm -f" $$list; \ + rm -f $$list || exit $$?; \ + test -n "$(EXEEXT)" || exit 0; \ + list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ + echo " rm -f" $$list; \ + rm -f $$list +gnunet_service_sysmon$(EXEEXT): $(gnunet_service_sysmon_OBJECTS) $(gnunet_service_sysmon_DEPENDENCIES) $(EXTRA_gnunet_service_sysmon_DEPENDENCIES) + @rm -f gnunet_service_sysmon$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(gnunet_service_sysmon_OBJECTS) $(gnunet_service_sysmon_LDADD) $(LIBS) +test_glibtop$(EXEEXT): $(test_glibtop_OBJECTS) $(test_glibtop_DEPENDENCIES) $(EXTRA_test_glibtop_DEPENDENCIES) + @rm -f test_glibtop$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_glibtop_OBJECTS) $(test_glibtop_LDADD) $(LIBS) +test_glibtop_network$(EXEEXT): $(test_glibtop_network_OBJECTS) $(test_glibtop_network_DEPENDENCIES) $(EXTRA_test_glibtop_network_DEPENDENCIES) + @rm -f test_glibtop_network$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_glibtop_network_OBJECTS) $(test_glibtop_network_LDADD) $(LIBS) +test_glibtop_process$(EXEEXT): $(test_glibtop_process_OBJECTS) $(test_glibtop_process_DEPENDENCIES) $(EXTRA_test_glibtop_process_DEPENDENCIES) + @rm -f test_glibtop_process$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_glibtop_process_OBJECTS) $(test_glibtop_process_LDADD) $(LIBS) + +mostlyclean-compile: + -rm -f *.$(OBJEXT) + +distclean-compile: + -rm -f *.tab.c + +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-service-sysmon.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_glibtop.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_glibtop_network.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_glibtop_process.Po@am__quote@ + +.c.o: +@am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c $< + +.c.obj: +@am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'` +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c `$(CYGPATH_W) '$<'` + +.c.lo: +@am__fastdepCC_TRUE@ $(AM_V_CC)$(LTCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LTCOMPILE) -c -o $@ $< + +mostlyclean-libtool: + -rm -f *.lo + +clean-libtool: + -rm -rf .libs _libs +install-pkgcfgDATA: $(pkgcfg_DATA) + @$(NORMAL_INSTALL) + @list='$(pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(pkgcfgdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" || exit 1; \ + fi; \ + for p in $$list; do \ + if test -f "$$p"; then d=; else d="$(srcdir)/"; fi; \ + echo "$$d$$p"; \ + done | $(am__base_list) | \ + while read files; do \ + echo " $(INSTALL_DATA) $$files '$(DESTDIR)$(pkgcfgdir)'"; \ + $(INSTALL_DATA) $$files "$(DESTDIR)$(pkgcfgdir)" || exit $$?; \ + done + +uninstall-pkgcfgDATA: + @$(NORMAL_UNINSTALL) + @list='$(pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ + files=`for p in $$list; do echo $$p; done | sed -e 's|^.*/||'`; \ + dir='$(DESTDIR)$(pkgcfgdir)'; $(am__uninstall_files_from_dir) + +ID: $(HEADERS) $(SOURCES) $(LISP) $(TAGS_FILES) + list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ + unique=`for i in $$list; do \ + if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \ + done | \ + $(AWK) '{ files[$$0] = 1; nonempty = 1; } \ + END { if (nonempty) { for (i in files) print i; }; }'`; \ + mkid -fID $$unique +tags: TAGS + +TAGS: $(HEADERS) $(SOURCES) $(TAGS_DEPENDENCIES) \ + $(TAGS_FILES) $(LISP) + set x; \ + here=`pwd`; \ + list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ + unique=`for i in $$list; do \ + if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \ + done | \ + $(AWK) '{ files[$$0] = 1; nonempty = 1; } \ + END { if (nonempty) { for (i in files) print i; }; }'`; \ + shift; \ + if test -z "$(ETAGS_ARGS)$$*$$unique"; then :; else \ + test -n "$$unique" || unique=$$empty_fix; \ + if test $$# -gt 0; then \ + $(ETAGS) $(ETAGSFLAGS) $(AM_ETAGSFLAGS) $(ETAGS_ARGS) \ + "$$@" $$unique; \ + else \ + $(ETAGS) $(ETAGSFLAGS) $(AM_ETAGSFLAGS) $(ETAGS_ARGS) \ + $$unique; \ + fi; \ + fi +ctags: CTAGS +CTAGS: $(HEADERS) $(SOURCES) $(TAGS_DEPENDENCIES) \ + $(TAGS_FILES) $(LISP) + list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ + unique=`for i in $$list; do \ + if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \ + done | \ + $(AWK) '{ files[$$0] = 1; nonempty = 1; } \ + END { if (nonempty) { for (i in files) print i; }; }'`; \ + test -z "$(CTAGS_ARGS)$$unique" \ + || $(CTAGS) $(CTAGSFLAGS) $(AM_CTAGSFLAGS) $(CTAGS_ARGS) \ + $$unique + +GTAGS: + here=`$(am__cd) $(top_builddir) && pwd` \ + && $(am__cd) $(top_srcdir) \ + && gtags -i $(GTAGS_ARGS) "$$here" + +distclean-tags: + -rm -f TAGS ID GTAGS GRTAGS GSYMS GPATH tags + +check-TESTS: $(TESTS) + @failed=0; all=0; xfail=0; xpass=0; skip=0; \ + srcdir=$(srcdir); export srcdir; \ + list=' $(TESTS) '; \ + $(am__tty_colors); \ + if test -n "$$list"; then \ + for tst in $$list; do \ + if test -f ./$$tst; then dir=./; \ + elif test -f $$tst; then dir=; \ + else dir="$(srcdir)/"; fi; \ + if $(TESTS_ENVIRONMENT) $${dir}$$tst; then \ + all=`expr $$all + 1`; \ + case " $(XFAIL_TESTS) " in \ + *[\ \ ]$$tst[\ \ ]*) \ + xpass=`expr $$xpass + 1`; \ + failed=`expr $$failed + 1`; \ + col=$$red; res=XPASS; \ + ;; \ + *) \ + col=$$grn; res=PASS; \ + ;; \ + esac; \ + elif test $$? -ne 77; then \ + all=`expr $$all + 1`; \ + case " $(XFAIL_TESTS) " in \ + *[\ \ ]$$tst[\ \ ]*) \ + xfail=`expr $$xfail + 1`; \ + col=$$lgn; res=XFAIL; \ + ;; \ + *) \ + failed=`expr $$failed + 1`; \ + col=$$red; res=FAIL; \ + ;; \ + esac; \ + else \ + skip=`expr $$skip + 1`; \ + col=$$blu; res=SKIP; \ + fi; \ + echo "$${col}$$res$${std}: $$tst"; \ + done; \ + if test "$$all" -eq 1; then \ + tests="test"; \ + All=""; \ + else \ + tests="tests"; \ + All="All "; \ + fi; \ + if test "$$failed" -eq 0; then \ + if test "$$xfail" -eq 0; then \ + banner="$$All$$all $$tests passed"; \ + else \ + if test "$$xfail" -eq 1; then failures=failure; else failures=failures; fi; \ + banner="$$All$$all $$tests behaved as expected ($$xfail expected $$failures)"; \ + fi; \ + else \ + if test "$$xpass" -eq 0; then \ + banner="$$failed of $$all $$tests failed"; \ + else \ + if test "$$xpass" -eq 1; then passes=pass; else passes=passes; fi; \ + banner="$$failed of $$all $$tests did not behave as expected ($$xpass unexpected $$passes)"; \ + fi; \ + fi; \ + dashes="$$banner"; \ + skipped=""; \ + if test "$$skip" -ne 0; then \ + if test "$$skip" -eq 1; then \ + skipped="($$skip test was not run)"; \ + else \ + skipped="($$skip tests were not run)"; \ + fi; \ + test `echo "$$skipped" | wc -c` -le `echo "$$banner" | wc -c` || \ + dashes="$$skipped"; \ + fi; \ + report=""; \ + if test "$$failed" -ne 0 && test -n "$(PACKAGE_BUGREPORT)"; then \ + report="Please report to $(PACKAGE_BUGREPORT)"; \ + test `echo "$$report" | wc -c` -le `echo "$$banner" | wc -c` || \ + dashes="$$report"; \ + fi; \ + dashes=`echo "$$dashes" | sed s/./=/g`; \ + if test "$$failed" -eq 0; then \ + col="$$grn"; \ + else \ + col="$$red"; \ + fi; \ + echo "$${col}$$dashes$${std}"; \ + echo "$${col}$$banner$${std}"; \ + test -z "$$skipped" || echo "$${col}$$skipped$${std}"; \ + test -z "$$report" || echo "$${col}$$report$${std}"; \ + echo "$${col}$$dashes$${std}"; \ + test "$$failed" -eq 0; \ + else :; fi + +distdir: $(DISTFILES) + @srcdirstrip=`echo "$(srcdir)" | sed 's/[].[^$$\\*]/\\\\&/g'`; \ + topsrcdirstrip=`echo "$(top_srcdir)" | sed 's/[].[^$$\\*]/\\\\&/g'`; \ + list='$(DISTFILES)'; \ + dist_files=`for file in $$list; do echo $$file; done | \ + sed -e "s|^$$srcdirstrip/||;t" \ + -e "s|^$$topsrcdirstrip/|$(top_builddir)/|;t"`; \ + case $$dist_files in \ + */*) $(MKDIR_P) `echo "$$dist_files" | \ + sed '/\//!d;s|^|$(distdir)/|;s,/[^/]*$$,,' | \ + sort -u` ;; \ + esac; \ + for file in $$dist_files; do \ + if test -f $$file || test -d $$file; then d=.; else d=$(srcdir); fi; \ + if test -d $$d/$$file; then \ + dir=`echo "/$$file" | sed -e 's,/[^/]*$$,,'`; \ + if test -d "$(distdir)/$$file"; then \ + find "$(distdir)/$$file" -type d ! -perm -700 -exec chmod u+rwx {} \;; \ + fi; \ + if test -d $(srcdir)/$$file && test $$d != $(srcdir); then \ + cp -fpR $(srcdir)/$$file "$(distdir)$$dir" || exit 1; \ + find "$(distdir)/$$file" -type d ! -perm -700 -exec chmod u+rwx {} \;; \ + fi; \ + cp -fpR $$d/$$file "$(distdir)$$dir" || exit 1; \ + else \ + test -f "$(distdir)/$$file" \ + || cp -p $$d/$$file "$(distdir)/$$file" \ + || exit 1; \ + fi; \ + done +check-am: all-am + $(MAKE) $(AM_MAKEFLAGS) $(check_PROGRAMS) + $(MAKE) $(AM_MAKEFLAGS) check-TESTS +check: check-am +all-am: Makefile $(PROGRAMS) $(DATA) +installdirs: + for dir in "$(DESTDIR)$(libexecdir)" "$(DESTDIR)$(pkgcfgdir)"; do \ + test -z "$$dir" || $(MKDIR_P) "$$dir"; \ + done +install: install-am +install-exec: install-exec-am +install-data: install-data-am +uninstall: uninstall-am + +install-am: all-am + @$(MAKE) $(AM_MAKEFLAGS) install-exec-am install-data-am + +installcheck: installcheck-am +install-strip: + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi +mostlyclean-generic: + +clean-generic: + +distclean-generic: + -test -z "$(CONFIG_CLEAN_FILES)" || rm -f $(CONFIG_CLEAN_FILES) + -test . = "$(srcdir)" || test -z "$(CONFIG_CLEAN_VPATH_FILES)" || rm -f $(CONFIG_CLEAN_VPATH_FILES) + +maintainer-clean-generic: + @echo "This command is intended for maintainers to use" + @echo "it deletes files that may require special tools to rebuild." +clean: clean-am + +clean-am: clean-checkPROGRAMS clean-generic clean-libexecPROGRAMS \ + clean-libtool mostlyclean-am + +distclean: distclean-am + -rm -rf ./$(DEPDIR) + -rm -f Makefile +distclean-am: clean-am distclean-compile distclean-generic \ + distclean-tags + +dvi: dvi-am + +dvi-am: + +html: html-am + +html-am: + +info: info-am + +info-am: + +install-data-am: install-pkgcfgDATA + +install-dvi: install-dvi-am + +install-dvi-am: + +install-exec-am: install-libexecPROGRAMS + +install-html: install-html-am + +install-html-am: + +install-info: install-info-am + +install-info-am: + +install-man: + +install-pdf: install-pdf-am + +install-pdf-am: + +install-ps: install-ps-am + +install-ps-am: + +installcheck-am: + +maintainer-clean: maintainer-clean-am + -rm -rf ./$(DEPDIR) + -rm -f Makefile +maintainer-clean-am: distclean-am maintainer-clean-generic + +mostlyclean: mostlyclean-am + +mostlyclean-am: mostlyclean-compile mostlyclean-generic \ + mostlyclean-libtool + +pdf: pdf-am + +pdf-am: + +ps: ps-am + +ps-am: + +uninstall-am: uninstall-libexecPROGRAMS uninstall-pkgcfgDATA + +.MAKE: check-am install-am install-strip + +.PHONY: CTAGS GTAGS all all-am check check-TESTS check-am clean \ + clean-checkPROGRAMS clean-generic clean-libexecPROGRAMS \ + clean-libtool ctags distclean distclean-compile \ + distclean-generic distclean-libtool distclean-tags distdir dvi \ + dvi-am html html-am info info-am install install-am \ + install-data install-data-am install-dvi install-dvi-am \ + install-exec install-exec-am install-html install-html-am \ + install-info install-info-am install-libexecPROGRAMS \ + install-man install-pdf install-pdf-am install-pkgcfgDATA \ + install-ps install-ps-am install-strip installcheck \ + installcheck-am installdirs maintainer-clean \ + maintainer-clean-generic mostlyclean mostlyclean-compile \ + mostlyclean-generic mostlyclean-libtool pdf pdf-am ps ps-am \ + tags uninstall uninstall-am uninstall-libexecPROGRAMS \ + uninstall-pkgcfgDATA + + +# Tell versions [3.59,3.63) of GNU make to not export all variables. +# Otherwise a system limit (for SysV at least) may be exceeded. +.NOEXPORT: diff --git a/src/sysmon/gnunet-service-sysmon.c b/src/sysmon/gnunet-service-sysmon.c new file mode 100644 index 0000000..b5fc46a --- /dev/null +++ b/src/sysmon/gnunet-service-sysmon.c @@ -0,0 +1,838 @@ +/* + This file is part of GNUnet. + (C) 2001, 2002, 2004, 2005, 2006, 2007, 2009 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @file sysmon/gnunet-service-sysmon.c + * @brief system monitoring service, can use libgtop to retrieve system information + * in a plattform independent way + * @author Matthias Wachs + */ +#include "platform.h" +#include "gnunet_util_lib.h" +#include "gnunet_statistics_service.h" +#if HAVE_LIBGTOP +#include +#include +#include +#include +#include +#include +#include +#include +#endif + + +enum operation +{ + o_internal, + o_ligbtop, + o_command +}; + + +enum type +{ + t_static, + t_continous +}; + +#define V_NUMERIC_STR "numeric" +#define V_STRING_STR "string" + +enum value +{ + v_numeric, + v_string +}; + +/** + * A system property to monitor + */ +struct SysmonProperty +{ + /** + * Next element in in the DLL + */ + struct SysmonProperty *next; + + /** + * Previous element in in the DLL + */ + struct SysmonProperty *prev; + + struct SysmonGtopProcProperty *gtop_proc_head; + struct SysmonGtopProcProperty *gtop_proc_tail; + + /** + * Description used for statistics valuesd + */ + char * desc; + + /** + * Type + */ + int type; + + /** + * Value type + */ + int value_type; + + /** + * Execution interval + */ + struct GNUNET_TIME_Relative interval; + + /** + * Command + */ + char * cmd; + + /** + * Command arguments + */ + char * cmd_args; + + /** + * Command execution handle + */ + void * cmd_exec_handle; + + /** + * Numerical value + */ + uint64_t num_val; + + /** + * String value + */ + char * str_val; + + /** + * Task id + */ + GNUNET_SCHEDULER_TaskIdentifier task_id; + + /** + * Task handle + */ + GNUNET_SCHEDULER_Task task; + + /** + * Task closure + */ + void *task_cls; +}; + +/** + * A system property to monitor + */ +struct SysmonGtopProcProperty +{ + struct SysmonGtopProcProperty *prev; + struct SysmonGtopProcProperty *next; + char * srv; + char * binary; +}; + + +/** + * Final status code. + */ +static int ret; + +/** + * Configuration handle + */ +const struct GNUNET_CONFIGURATION_Handle *cfg; + + +/** + * Statistics handle + */ +struct GNUNET_STATISTICS_Handle *stats; + +/** + * Shutdown task + */ +GNUNET_SCHEDULER_TaskIdentifier end_task; + +struct SysmonProperty *sp_head; +struct SysmonProperty *sp_tail; + +struct SysmonGtopProcProperty *pp_head; +struct SysmonGtopProcProperty *pp_tail; + +static void +shutdown_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct SysmonProperty *sp; + struct SysmonProperty *next; + struct SysmonGtopProcProperty *gt_cur; + struct SysmonGtopProcProperty *gt_next; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "sysdaemon stopping ... \n"); + end_task = GNUNET_SCHEDULER_NO_TASK; + + if (NULL != stats) + { + GNUNET_STATISTICS_destroy (stats, GNUNET_YES); + stats = NULL; + } + + next = sp_head; + while (NULL != (sp = next)) + { + next = sp->next; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stopping `%s' \n", sp->desc); + GNUNET_CONTAINER_DLL_remove (sp_head, sp_tail, sp); + if (GNUNET_SCHEDULER_NO_TASK != sp->task_id) + { + GNUNET_SCHEDULER_cancel (sp->task_id); + sp->task_id = GNUNET_SCHEDULER_NO_TASK; + } + GNUNET_free_non_null (sp->cmd); + GNUNET_free_non_null (sp->cmd_args); + GNUNET_free (sp->desc); + GNUNET_free (sp); + } + + gt_next = pp_head; + while (NULL != (gt_cur = gt_next)) + { + gt_next = gt_cur->next; + GNUNET_CONTAINER_DLL_remove (pp_head, pp_tail, gt_cur); + GNUNET_free (gt_cur->srv); + GNUNET_free (gt_cur->binary); + GNUNET_free (gt_cur); + } + +#if HAVE_LIBGTOP + glibtop_close(); +#endif +} + +static void +shutdown_now (void) +{ + if (GNUNET_SCHEDULER_NO_TASK != end_task) + GNUNET_SCHEDULER_cancel (end_task); + GNUNET_SCHEDULER_add_now (&shutdown_task, NULL); +} + +static void +to_lower_str (char * str) +{ + int c; + for (c = 0; c <= strlen (str); c++) + str[c] = tolower(str[c]); +} + +static int +put_property (struct SysmonProperty *sp) +{ + if (v_numeric ==sp->value_type) + { + fprintf (stderr, "%s : %s : %llu\n", + GNUNET_STRINGS_absolute_time_to_string(GNUNET_TIME_absolute_get()), + sp->desc, (unsigned long long) sp->num_val); + } + else if (v_string ==sp->value_type) + { + fprintf (stderr, "%s : %s : %s\n", + GNUNET_STRINGS_absolute_time_to_string(GNUNET_TIME_absolute_get()), + sp->desc, sp->str_val); + } + else + { + GNUNET_break (0); + return GNUNET_SYSERR; + } + return GNUNET_OK; +} + +static void +update_uptime (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct SysmonProperty *sp = cls; + static int first_run = GNUNET_YES; + + if (GNUNET_YES == first_run) + first_run = GNUNET_NO; + else + sp->num_val += sp->interval.rel_value / 1000; + + put_property (sp); +} + +static void +exec_cmd_proc (void *cls, const char *line) +{ + struct SysmonProperty *sp = cls; + unsigned long long tmp; + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Property output: `%s'\n", line); + if (NULL == line) + { + GNUNET_OS_command_stop (sp->cmd_exec_handle); + sp->cmd_exec_handle = NULL; + return; + } + + switch (sp->value_type) { + case v_numeric: + if (1 != sscanf (line, "%llu", &tmp)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Command output was not a numerical value: `%s'\n", line); + return; + } + break; + case v_string: + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "NOT IMPLEMENTED\n"); + break; + default: + break; + + } + sp->num_val = tmp; + + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Property output: `%s'\n", line); + put_property (sp); + + +} + +static void +exec_cmd (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct SysmonProperty *sp = cls; + GNUNET_assert (NULL != sp->cmd); + + if (NULL != sp->cmd_exec_handle) + { + GNUNET_OS_command_stop (sp->cmd_exec_handle); + sp->cmd_exec_handle = NULL; + GNUNET_break (0); + } + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Property `%s': command `%s' `%s'\n", sp->desc, sp->cmd, sp->cmd_args); + if (NULL == (sp->cmd_exec_handle = GNUNET_OS_command_run (&exec_cmd_proc, sp, + GNUNET_TIME_UNIT_SECONDS, + sp->cmd, sp->cmd, + sp->cmd_args, + NULL))) + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Property `%s': command `%s' failed\n", sp->desc, sp->cmd); +} + +#if HAVE_LIBGTOP +static void +exec_gtop_proc_mon (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct SysmonGtopProcProperty *sp = cls; + glibtop_proclist proc_list; + glibtop_proc_args proc_args; + glibtop_proc_mem proc_mem; + glibtop_proc_time proc_time; + pid_t *pids = NULL; + unsigned i; + char *argss; + + /* get process list */ + pids = glibtop_get_proclist(&proc_list, GLIBTOP_KERN_PROC_ALL, 0); + if (NULL == pids) + { + fprintf (stderr, "Could not retrieve process list!\n"); + ret = 1; + return; + } + for (i = 0; i < proc_list.number; ++i) + { + //printf("PID %u:\n", pids[i]); + + /* get process args */ + argss = glibtop_get_proc_args (&proc_args, pids[i], 1024); + if (NULL == argss) + { + fprintf (stderr, "Could not retrieve process args!\n"); + ret = 1; + return; + } + //printf ("\targument string: %s\n", argss); + if (NULL != strstr (argss, sp->binary)) + { + /* get memory info */ + glibtop_get_proc_mem (&proc_mem, pids[i]); + fprintf (stderr, "%s : %s process information\n", + GNUNET_STRINGS_absolute_time_to_string(GNUNET_TIME_absolute_get()), + sp->srv); + fprintf (stderr, "\t%s memory information:\n", sp->binary); + fprintf (stderr, "\t%-50s: %llu\n", "total # of pages of memory", (long long unsigned int) proc_mem.size); + fprintf (stderr, "\t%-50s: %llu\n", "number of pages of virtual memory", (long long unsigned int) proc_mem.vsize); + fprintf (stderr, "\t%-50s: %llu\n", "number of resident set", (long long unsigned int) proc_mem.resident); + fprintf (stderr, "\t%-50s: %llu\n", "number of pages of shared (mmap'd) memory", (long long unsigned int) proc_mem.share); + fprintf (stderr, "\t%-50s: %llu\n", "resident set size", (long long unsigned int) proc_mem.rss); + + /* get time info */ + glibtop_get_proc_time (&proc_time, pids[i]); + fprintf (stderr, "\t%s time information:\n", sp->binary); + fprintf (stderr, "\t%-50s: %llu\n", "real time accumulated by process", (long long unsigned int) proc_time.rtime); + fprintf (stderr, "\t%-50s: %llu\n", "user-mode CPU time accumulated by process", (long long unsigned int) proc_time.utime); + fprintf (stderr, "\t%-50s: %llu\n", "kernel-mode CPU time accumulated by process", (long long unsigned int) proc_time.stime); + } + g_free (argss); + } + g_free(pids); + pids = NULL; +} +#endif + +#if HAVE_LIBGTOP +static void +exec_gtop_net_mon (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + glibtop_netlist netlist; + glibtop_netload netload; + int i; + char ** tmp; + uint8_t *address; + uint8_t *netmask; + char address6_string[INET6_ADDRSTRLEN]; + char prefix6_string[INET6_ADDRSTRLEN]; + + tmp = glibtop_get_netlist (&netlist); + + fprintf (stderr, "%s : Network information: %u devices\n", + GNUNET_STRINGS_absolute_time_to_string(GNUNET_TIME_absolute_get()), + netlist.number); + for (i = 0; i < netlist.number; ++i) + { + fprintf (stderr, "Device %i: %s\n", i, tmp[i]); + glibtop_get_netload (&netload, tmp[i]); + address = (uint8_t *) &netload.address; + netmask = (uint8_t *) &netload.subnet; + inet_ntop (AF_INET6, netload.address6, address6_string, INET6_ADDRSTRLEN); + inet_ntop (AF_INET6, netload.prefix6, prefix6_string, INET6_ADDRSTRLEN); + fprintf (stderr, "\t%-50s: %u.%u.%u.%u\n", "IPv4 subnet", netmask[0], netmask[1], netmask[2],netmask[3]); + fprintf (stderr, "\t%-50s: %u.%u.%u.%u\n", "IPv4 address", address[0], address[1], address[2],address[3]); + fprintf (stderr, "\t%-50s: %s\n", "IPv6 prefix", prefix6_string); + fprintf (stderr, "\t%-50s: %s\n", "IPv6 address", address6_string); + + + fprintf (stderr, "\t%-50s: %llu\n", "bytes in", (long long unsigned int) netload.bytes_in); + fprintf (stderr, "\t%-50s: %llu\n", "bytes out", (long long unsigned int) netload.bytes_out); + fprintf (stderr, "\t%-50s: %llu\n", "bytes total", (long long unsigned int) netload.bytes_total); + } + fprintf (stderr, "\n"); +} +#endif + +static void +load_property (void *cls, + const char *section) +{ + struct GNUNET_CONFIGURATION_Handle *properties = cls; + struct SysmonProperty *sp; + char *tmp; + + if (NULL == strstr (section, "sysmon-")) + return; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Loading section `%s'\n", section); + + if (GNUNET_NO == GNUNET_CONFIGURATION_have_value (properties, section, "TYPE")) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Missing value %s in section `%s'\n", + "TYPE", section); + return; + } + if (GNUNET_NO == GNUNET_CONFIGURATION_have_value (properties, section,"VALUE")) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Missing value %s in section `%s'\n", + "VALUE", section); + return; + } + if (GNUNET_NO == GNUNET_CONFIGURATION_have_value (properties, section,"DESCRIPTION")) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Missing value %s in section `%s'\n", + "DESCRIPTION", section); + return; + } + if (GNUNET_NO == GNUNET_CONFIGURATION_have_value (properties, section,"CMD")) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Missing value %s in section `%s'\n", + "CMD", section); + return; + } + sp = GNUNET_malloc (sizeof (struct SysmonProperty)); + + /* description */ + GNUNET_CONFIGURATION_get_value_string (properties, section, "DESCRIPTION", &sp->desc); + + /* cmd */ + GNUNET_CONFIGURATION_get_value_string (properties, section, "CMD", &tmp); + char *args = ""; + if (NULL != strchr (tmp, ' ')) + { + args = strchr (tmp, ' '); + if (strlen (args) > 1) + { + args[0] = '\0'; + args++; + } + } + sp->task_cls = sp; + sp->cmd = GNUNET_strdup (tmp); + sp->cmd_args = GNUNET_strdup (args); + GNUNET_free (tmp); + sp->task = &exec_cmd; + + /* type */ + GNUNET_CONFIGURATION_get_value_string (properties, section, "TYPE", &tmp); + to_lower_str (tmp); + if (0 == strcasecmp(tmp, "static")) + sp->type = t_static; + else if (0 == strcasecmp(tmp, "continous")) + sp->type = t_continous; + else + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Invalid value %s for %s in section `%s'\n", + tmp, "TYPE", section); + GNUNET_free (tmp); + GNUNET_free (sp); + return; + } + GNUNET_free (tmp); + + /* value */ + GNUNET_CONFIGURATION_get_value_string (properties, section, "VALUE", &tmp); + to_lower_str (tmp); + if (0 == strcasecmp(tmp, V_NUMERIC_STR)) + sp->value_type = v_numeric; + else if (0 == strcasecmp(tmp, V_STRING_STR)) + sp->value_type = v_string; + else + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Invalid value %s for %s in section `%s'\n", + tmp, "VALUE", section); + GNUNET_free (tmp); + GNUNET_free (sp); + return; + } + GNUNET_free (tmp); + + /* interval */ + if (GNUNET_NO == GNUNET_CONFIGURATION_have_value (properties, section,"INTERVAL")) + sp->interval = GNUNET_TIME_UNIT_MINUTES; + else + { + if (GNUNET_SYSERR == GNUNET_CONFIGURATION_get_value_time (properties, section, "INTERVAL", &sp->interval)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Could not parse execution interval for `%s', set to default 60 sec.\n"), section); + sp->interval = GNUNET_TIME_UNIT_MINUTES; + } + } + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Loaded property `%s': %s, %s, interval %llu\n", + (NULL != sp->desc) ? sp->desc: "", + (t_continous == sp->type) ? "continious" : "static", + (v_numeric == sp->value_type) ? "numeric" : "string", + sp->interval.rel_value); + + GNUNET_CONTAINER_DLL_insert (sp_head, sp_tail, sp); + +} + +static int +load_default_properties (void) +{ + struct SysmonProperty *sp; + /* GNUnet version array */ + unsigned int ver[3]; + + /* GNUnet vcs revision */ + unsigned int revision; + /* version */ +#ifdef VERSION + if (3 != sscanf (VERSION, "%u.%u.%u", &ver[0], &ver[1], &ver[2])) + { + ver[0] = 0; + ver[1] = 0; + ver[2] = 0; + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Could not parse version string `%s'\n", VERSION); + } +#else + ver[0] = 0; + ver[1] = 0; + ver[2] = 0; + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Version string is undefined \n"); +#endif + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Version: %u.%u.%u\n", ver[0], ver[1], ver[2]); + + sp = GNUNET_malloc (sizeof (struct SysmonProperty)); + sp->desc = GNUNET_strdup ("GNUnet version"); + sp->type = t_static; + sp->value_type = v_numeric; + sp->num_val = 100 * ver[0] + 10 * ver[1] + ver[2]; + GNUNET_CONTAINER_DLL_insert (sp_head, sp_tail, sp); + /* revision */ +#ifdef VCS_VERSION + if (1 != sscanf (VCS_VERSION, "svn-%uM", &revision)) + { + revision = 0; + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Could not parse revision string `%s'\n", VCS_VERSION); + } +#else + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "VCS revision string is undefined \n"); + revision = 0; +#endif + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Revision: %u\n", revision); + sp = GNUNET_malloc (sizeof (struct SysmonProperty)); + sp->desc = GNUNET_strdup ("GNUnet vcs revision"); + sp->type = t_static; + sp->value_type = v_numeric; + sp->num_val = (uint64_t) revision; + GNUNET_CONTAINER_DLL_insert (sp_head, sp_tail, sp); + + + /* GNUnet startup time */ + sp = GNUNET_malloc (sizeof (struct SysmonProperty)); + sp->desc = GNUNET_strdup ("GNUnet startup time"); + sp->type = t_static; + sp->value_type = v_numeric; + sp->num_val = (uint64_t) GNUNET_TIME_absolute_get().abs_value; + GNUNET_CONTAINER_DLL_insert (sp_head, sp_tail, sp); + + + /* GNUnet sysmon daemon uptime in seconds */ + sp = GNUNET_malloc (sizeof (struct SysmonProperty)); + sp->desc = GNUNET_strdup ("GNUnet uptime"); + sp->type = t_continous; + sp->value_type = v_numeric; + sp->num_val = (uint64_t) 0; + sp->interval = GNUNET_TIME_UNIT_MINUTES; + sp->task_id = GNUNET_SCHEDULER_NO_TASK; + sp->task = update_uptime; + sp->task_cls = sp; + GNUNET_CONTAINER_DLL_insert (sp_head, sp_tail, sp); + return GNUNET_OK; +} + +#if HAVE_LIBGTOP +static int +load_gtop_properties (void) +{ + char *services; + char *s; + char *binary; + struct SysmonGtopProcProperty *pp; + struct SysmonProperty *sp; + struct GNUNET_TIME_Relative interval; + + /* Load service memory monitoring tasks */ + if (GNUNET_NO == GNUNET_CONFIGURATION_have_value (cfg, "sysmon", "MONITOR_SERVICES")) + return GNUNET_OK; + + if (GNUNET_SYSERR == GNUNET_CONFIGURATION_get_value_string(cfg, "sysmon", "MONITOR_SERVICES", &services)) + return GNUNET_SYSERR; + + if (GNUNET_SYSERR == GNUNET_CONFIGURATION_get_value_time (cfg,"sysmon", "MONITOR_SERVICES_INTERVAL", &interval)) + interval = GNUNET_TIME_UNIT_MINUTES; + + s = strtok (services, " "); + while (NULL != s) + { + if (GNUNET_OK == GNUNET_CONFIGURATION_get_value_string(cfg, s, "BINARY", &binary)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Monitoring service `%s' with binary `%s'\n", s, binary); + pp = GNUNET_malloc (sizeof (struct SysmonGtopProcProperty)); + pp->srv = GNUNET_strdup (s); + pp->binary = binary; + GNUNET_CONTAINER_DLL_insert (pp_head, pp_tail, pp); + + sp = GNUNET_malloc (sizeof (struct SysmonProperty)); + GNUNET_asprintf(&sp->desc, "Process Monitoring for service %s", s); + sp->type = t_continous; + sp->value_type = v_numeric; + sp->num_val = (uint64_t) 0; + sp->interval = interval; + sp->task_id = GNUNET_SCHEDULER_NO_TASK; + sp->task = exec_gtop_proc_mon; + sp->task_cls = pp; + GNUNET_CONTAINER_DLL_insert (sp_head, sp_tail, sp); + } + s = strtok (NULL, " "); + } + GNUNET_free (services); + + /* Load network monitoring tasks */ + + if (GNUNET_SYSERR == GNUNET_CONFIGURATION_get_value_time (cfg,"sysmon", "MONITOR_NETWORK_INTERVAL", &interval)) + interval = GNUNET_TIME_UNIT_MINUTES; + + sp = GNUNET_malloc (sizeof (struct SysmonProperty)); + GNUNET_asprintf(&sp->desc, "Network interface monitoring"); + sp->type = t_continous; + sp->value_type = v_numeric; + sp->num_val = (uint64_t) 0; + sp->interval = interval; + sp->task_id = GNUNET_SCHEDULER_NO_TASK; + sp->task = exec_gtop_net_mon; + sp->task_cls = sp; + GNUNET_CONTAINER_DLL_insert (sp_head, sp_tail, sp); + + return GNUNET_OK; +} +#endif + + +static void +run_property (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct SysmonProperty *sp = cls; + sp->task_id = GNUNET_SCHEDULER_NO_TASK; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Running continous property `%s' \n", sp->desc); + sp->task (sp->task_cls, tc); + sp->task_id = GNUNET_SCHEDULER_add_delayed (sp->interval, &run_property, sp); +} + + +static int +run_properties (void) +{ + struct SysmonProperty *sp; + + for (sp = sp_head; NULL != sp; sp = sp->next) + { + if (t_static == sp->type) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Running static property `%s' \n", sp->desc); + put_property (sp); + } + else + { + if (NULL == sp->task) + { + GNUNET_break (0); + continue; + } + sp->task_id = GNUNET_SCHEDULER_add_now (&run_property, sp); + } + } + return GNUNET_OK; +} + + +/** + * Process template requests. + * + * @param cls closure + * @param server the initialized server + * @param mycfg configuration to use + */ +static void +run (void *cls, struct GNUNET_SERVER_Handle *server, + const struct GNUNET_CONFIGURATION_Handle *mycfg) +{ + static const struct GNUNET_SERVER_MessageHandler handlers[] = { + /* FIXME: add handlers here! */ + {NULL, NULL, 0, 0} + }; + /* FIXME: do setup here */ + GNUNET_SERVER_add_handlers (server, handlers); + + struct GNUNET_CONFIGURATION_Handle *properties; + char *file; + + end_task = GNUNET_SCHEDULER_add_delayed(GNUNET_TIME_UNIT_FOREVER_REL, &shutdown_task, NULL); + cfg = mycfg; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "sysmon starting ... \n"); + + if (GNUNET_OK == GNUNET_CONFIGURATION_get_value_filename (mycfg, "sysmon", "CFGFILE", &file)) + { + properties = GNUNET_CONFIGURATION_create(); + if (NULL == properties) + { + GNUNET_break (0); + shutdown_now(); + ret = 1; + return; + } + if ((GNUNET_YES == GNUNET_DISK_file_test(file)) && + (GNUNET_OK == GNUNET_CONFIGURATION_load (properties, file))) + GNUNET_CONFIGURATION_iterate_sections (properties, &load_property, properties); + + GNUNET_CONFIGURATION_destroy (properties); + GNUNET_free (file); + + /* Creating statistics */ + stats = GNUNET_STATISTICS_create ("sysmon", mycfg); + if (NULL == stats) + { + GNUNET_break (0); + shutdown_now(); + ret = 1; + return; + } + } + + /* load properties */ + if (GNUNET_SYSERR == load_default_properties ()) + { + GNUNET_break (0); + shutdown_now(); + ret = 1; + return; + } + +#if HAVE_LIBGTOP + if (NULL != glibtop_init()) + if ( GNUNET_SYSERR == load_gtop_properties ()) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Failed to load gtop properties \n"); + } +#endif + + /* run properties */ + if (GNUNET_SYSERR == run_properties ()) + { + GNUNET_break (0); + shutdown_now(); + ret = 1; + return; + } +} + + +/** + * The main function for the sysmon service. + * + * @param argc number of arguments from the command line + * @param argv command line arguments + * @return 0 ok, 1 on error + */ +int +main (int argc, char *const *argv) +{ + return (GNUNET_OK == + GNUNET_SERVICE_run (argc, argv, "sysmon", + GNUNET_SERVICE_OPTION_NONE, &run, NULL)) ? 0 : 1; +} + +/* end of gnunet-service-sysmon.c */ diff --git a/src/sysmon/sysmon-properties.conf b/src/sysmon/sysmon-properties.conf new file mode 100644 index 0000000..114404e --- /dev/null +++ b/src/sysmon/sysmon-properties.conf @@ -0,0 +1,14 @@ +#[sysmon-memory_transport] +#DESCRIPTION = memory transport +#VALUE = numeric +#TYPE = continous +#INTERVAL = 10 s +#CMD = ps axo c,pcpu | awk {'print $1 $0'} +#CMD = echo "TEST" + +[sysmon-test_b] +DESCRIPTION = test b +VALUE = string +TYPE = continous +INTERVAL = 1 s +CMD = echo "TEST" diff --git a/src/sysmon/sysmon.conf.in b/src/sysmon/sysmon.conf.in new file mode 100644 index 0000000..1e502d1 --- /dev/null +++ b/src/sysmon/sysmon.conf.in @@ -0,0 +1,11 @@ +[sysmon] +AUTOSTART = YES +@UNIXONLY@ PORT = 2104 +HOSTNAME = localhost +HOME = $SERVICEHOME +BINARY = gnunet_service_sysmon +#CFGFILE = sysmon-properties.conf +UNIXPATH = /tmp/gnunet-service-sysmon.sock +MONITOR_SERVICES = transport core topology hostlist dht nse mesh fs gns +MONITOR_SERVICES_INTERVAL = 60 s +MONITOR_NETWORK_INTERVAL = 60 s \ No newline at end of file diff --git a/src/sysmon/test_glibtop.c b/src/sysmon/test_glibtop.c new file mode 100644 index 0000000..e05a46b --- /dev/null +++ b/src/sysmon/test_glibtop.c @@ -0,0 +1,53 @@ +/* + This file is part of GNUnet. + (C) 2001, 2002, 2004, 2005, 2006, 2007, 2009 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @file sysmon/test_glibtop_process.c + * @brief a brief test for glibtop + * @author Matthias Wachs + */ + +#include "platform.h" +#include + +static int ret; + +/** + * The main function. + * + * @param argc number of arguments from the command line + * @param argv command line arguments + * @return 0 ok, 1 on error + */ +int +main (int argc, char *const *argv) +{ + if (NULL == glibtop_init()) + { + fprintf (stderr, "Could not init gliptop!\n"); + return 1; + } + + glibtop_close(); + return ret; +} + +/* end of test_glibtop_process.c */ + diff --git a/src/sysmon/test_glibtop_network.c b/src/sysmon/test_glibtop_network.c new file mode 100644 index 0000000..5cc41c6 --- /dev/null +++ b/src/sysmon/test_glibtop_network.c @@ -0,0 +1,88 @@ +/* + This file is part of GNUnet. + (C) 2001, 2002, 2004, 2005, 2006, 2007, 2009 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @file sysmon/test_glibtop_process.c + * @brief a brief test for glibtop + * @author Matthias Wachs + */ + +#include "platform.h" + +#include +#include +#include + +static int ret; + + +static void +print_netlist () +{ + glibtop_netlist netlist; + glibtop_netload netload; + int i; + char ** tmp; + uint8_t *address; + uint8_t *netmask; + + tmp = glibtop_get_netlist (&netlist); + + printf ("Network information: %u devices\n", netlist.number); + for (i = 0; i < netlist.number; ++i) + { + printf ("Device %i: %s\n", i, tmp[i]); + glibtop_get_netload (&netload, tmp[i]); + address = (uint8_t *) &netload.address; + netmask = (uint8_t *) &netload.subnet; + printf ("\t%-50s: %u.%u.%u.%u\n", "IPv4 subnet", netmask[0], netmask[1], netmask[2],netmask[3]); + printf ("\t%-50s: %u.%u.%u.%u\n", "IPv4 address", address[0], address[1], address[2],address[3]); + + printf ("\t%-50s: %llu\n", "bytes in", (long long unsigned int) netload.bytes_in); + printf ("\t%-50s: %llu\n", "bytes out", (long long unsigned int) netload.bytes_out); + printf ("\t%-50s: %llu\n", "packets total", (long long unsigned int) netload.packets_total); + } +} + +/** + * The main function. + * + * @param argc number of arguments from the command line + * @param argv command line arguments + * @return 0 ok, 1 on error + */ +int +main (int argc, char *const *argv) +{ + if (NULL == glibtop_init()) + { + fprintf (stderr, "Could not init gliptop!\n"); + return 1; + } + + /* Network information */ + print_netlist (); + + glibtop_close(); + return ret; +} + +/* end of ttest_glibtop_process.c */ + diff --git a/src/sysmon/test_glibtop_process.c b/src/sysmon/test_glibtop_process.c new file mode 100644 index 0000000..8af9941 --- /dev/null +++ b/src/sysmon/test_glibtop_process.c @@ -0,0 +1,122 @@ +/* + This file is part of GNUnet. + (C) 2001, 2002, 2004, 2005, 2006, 2007, 2009 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @file sysmon/test_glibtop_process.c + * @brief a brief test for glibtop + * @author Matthias Wachs + */ + +#include "platform.h" + +#include +#include +#include +#include +#include +#include + +static int ret; + +static void print_pids(guint64 which, guint64 arg) +{ + pid_t *pids = NULL; + unsigned i; + glibtop_proclist proc_list; + glibtop_proc_args proc_args; + glibtop_proc_mem proc_mem; + glibtop_proc_time proc_time; + char *argss; + + /* get process list */ + pids = glibtop_get_proclist(&proc_list, which, arg); + if (NULL == pids) + { + fprintf (stderr, "Could not retrieve process list!\n"); + ret = 1; + return; + } + + printf("Found %lu processes\n", (unsigned long) proc_list.number); + for (i = 0; i < proc_list.number; ++i) + { + printf("PID %u:\n", pids[i]); + + /* get process args */ + argss = glibtop_get_proc_args (&proc_args, pids[i], 1024); + if (NULL == argss) + { + fprintf (stderr, "Could not retrieve process args!\n"); + ret = 1; + return; + } + printf ("\targument string: %s\n", argss); + g_free (argss); + + /* get memory info */ + glibtop_get_proc_mem (&proc_mem, pids[i]); + printf ("\tMemory information:\n"); + printf ("\t%-50s: %llu\n", "total # of pages of memory", (long long unsigned int) proc_mem.size); + printf ("\t%-50s: %llu\n", "number of pages of virtual memory", (long long unsigned int) proc_mem.vsize); + printf ("\t%-50s: %llu\n", "number of resident set", (long long unsigned int) proc_mem.resident); + printf ("\t%-50s: %llu\n", "number of pages of shared (mmap'd) memory", (long long unsigned int) proc_mem.share); + printf ("\t%-50s: %llu\n", "resident set size", (long long unsigned int) proc_mem.rss); + + /* get time info */ + glibtop_get_proc_time (&proc_time, pids[i]); + printf ("\tTime information:\n"); + printf ("\t%-50s: %llu\n", "real time accumulated by process", (long long unsigned int) proc_time.rtime); + printf ("\t%-50s: %llu\n", "user-mode CPU time accumulated by process", (long long unsigned int) proc_time.utime); + printf ("\t%-50s: %llu\n", "kernel-mode CPU time accumulated by process", (long long unsigned int) proc_time.stime); + } + + if (NULL != pids) + { + g_free(pids); + pids = NULL; + } +} + + +/** + * The main function. + * + * @param argc number of arguments from the command line + * @param argv command line arguments + * @return 0 ok, 1 on error + */ +int +main (int argc, char *const *argv) +{ + if (NULL == glibtop_init()) + { + fprintf (stderr, "Could not init gliptop!\n"); + return 1; + } + + /* Print all processes */ + print_pids(GLIBTOP_KERN_PROC_ALL, 0); + + glibtop_close(); + return ret; +} + +/* end of test_glibtop_process.c */ + diff --git a/src/template/Makefile.am b/src/template/Makefile.am index 1769191..d1f87c8 100644 --- a/src/template/Makefile.am +++ b/src/template/Makefile.am @@ -2,6 +2,8 @@ INCLUDES = -I$(top_srcdir)/src/include pkgcfgdir= $(pkgdatadir)/config.d/ +libexecdir= $(pkglibdir)/libexec/ + dist_pkgcfg_DATA = \ template.conf @@ -14,7 +16,9 @@ if USE_COVERAGE endif bin_PROGRAMS = \ - gnunet-template \ + gnunet-template + +libexec_PROGRAMS = \ gnunet-service-template gnunet_template_SOURCES = \ diff --git a/src/template/Makefile.in b/src/template/Makefile.in index 8f8c858..ef48d67 100644 --- a/src/template/Makefile.in +++ b/src/template/Makefile.in @@ -1,9 +1,9 @@ -# Makefile.in generated by automake 1.11.1 from Makefile.am. +# Makefile.in generated by automake 1.11.6 from Makefile.am. # @configure_input@ # Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, -# 2003, 2004, 2005, 2006, 2007, 2008, 2009 Free Software Foundation, -# Inc. +# 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Free Software +# Foundation, Inc. # This Makefile.in is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. @@ -17,6 +17,23 @@ VPATH = @srcdir@ +am__make_dryrun = \ + { \ + am__dry=no; \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + echo 'am--echo: ; @echo "AM" OK' | $(MAKE) -f - 2>/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } pkgdatadir = $(datadir)/@PACKAGE@ pkgincludedir = $(includedir)/@PACKAGE@ pkglibdir = $(libdir)/@PACKAGE@ @@ -36,8 +53,8 @@ POST_UNINSTALL = : build_triplet = @build@ host_triplet = @host@ target_triplet = @target@ -bin_PROGRAMS = gnunet-template$(EXEEXT) \ - gnunet-service-template$(EXEEXT) +bin_PROGRAMS = gnunet-template$(EXEEXT) +libexec_PROGRAMS = gnunet-service-template$(EXEEXT) check_PROGRAMS = test_template_api$(EXEEXT) subdir = src/template DIST_COMMON = $(dist_pkgcfg_DATA) $(srcdir)/Makefile.am \ @@ -45,14 +62,15 @@ DIST_COMMON = $(dist_pkgcfg_DATA) $(srcdir)/Makefile.am \ ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 am__aclocal_m4_deps = $(top_srcdir)/m4/absolute-header.m4 \ $(top_srcdir)/m4/align.m4 $(top_srcdir)/m4/argz.m4 \ - $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/iconv.m4 \ - $(top_srcdir)/m4/lib-ld.m4 $(top_srcdir)/m4/lib-link.m4 \ - $(top_srcdir)/m4/lib-prefix.m4 $(top_srcdir)/m4/libcurl.m4 \ - $(top_srcdir)/m4/libgcrypt.m4 $(top_srcdir)/m4/libtool.m4 \ - $(top_srcdir)/m4/libunistring.m4 $(top_srcdir)/m4/ltdl.m4 \ - $(top_srcdir)/m4/ltoptions.m4 $(top_srcdir)/m4/ltsugar.m4 \ - $(top_srcdir)/m4/ltversion.m4 $(top_srcdir)/m4/lt~obsolete.m4 \ - $(top_srcdir)/m4/nls.m4 $(top_srcdir)/m4/po.m4 \ + $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/glib-2.0.m4 \ + $(top_srcdir)/m4/iconv.m4 $(top_srcdir)/m4/lib-ld.m4 \ + $(top_srcdir)/m4/lib-link.m4 $(top_srcdir)/m4/lib-prefix.m4 \ + $(top_srcdir)/m4/libcurl.m4 $(top_srcdir)/m4/libgcrypt.m4 \ + $(top_srcdir)/m4/libtool.m4 $(top_srcdir)/m4/libunistring.m4 \ + $(top_srcdir)/m4/ltdl.m4 $(top_srcdir)/m4/ltoptions.m4 \ + $(top_srcdir)/m4/ltsugar.m4 $(top_srcdir)/m4/ltversion.m4 \ + $(top_srcdir)/m4/lt~obsolete.m4 $(top_srcdir)/m4/nls.m4 \ + $(top_srcdir)/m4/pkg.m4 $(top_srcdir)/m4/po.m4 \ $(top_srcdir)/m4/progtest.m4 $(top_srcdir)/acinclude.m4 \ $(top_srcdir)/configure.ac am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ @@ -61,8 +79,9 @@ mkinstalldirs = $(install_sh) -d CONFIG_HEADER = $(top_builddir)/gnunet_config.h CONFIG_CLEAN_FILES = CONFIG_CLEAN_VPATH_FILES = -am__installdirs = "$(DESTDIR)$(bindir)" "$(DESTDIR)$(pkgcfgdir)" -PROGRAMS = $(bin_PROGRAMS) +am__installdirs = "$(DESTDIR)$(bindir)" "$(DESTDIR)$(libexecdir)" \ + "$(DESTDIR)$(pkgcfgdir)" +PROGRAMS = $(bin_PROGRAMS) $(libexec_PROGRAMS) am_gnunet_service_template_OBJECTS = \ gnunet-service-template.$(OBJEXT) gnunet_service_template_OBJECTS = \ @@ -71,8 +90,8 @@ am__DEPENDENCIES_1 = gnunet_service_template_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la \ $(am__DEPENDENCIES_1) -AM_V_lt = $(am__v_lt_$(V)) -am__v_lt_ = $(am__v_lt_$(AM_DEFAULT_VERBOSITY)) +AM_V_lt = $(am__v_lt_@AM_V@) +am__v_lt_ = $(am__v_lt_@AM_DEFAULT_V@) am__v_lt_0 = --silent am_gnunet_template_OBJECTS = gnunet-template.$(OBJEXT) gnunet_template_OBJECTS = $(am_gnunet_template_OBJECTS) @@ -93,26 +112,31 @@ LTCOMPILE = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) \ $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) \ $(AM_CFLAGS) $(CFLAGS) -AM_V_CC = $(am__v_CC_$(V)) -am__v_CC_ = $(am__v_CC_$(AM_DEFAULT_VERBOSITY)) +AM_V_CC = $(am__v_CC_@AM_V@) +am__v_CC_ = $(am__v_CC_@AM_DEFAULT_V@) am__v_CC_0 = @echo " CC " $@; -AM_V_at = $(am__v_at_$(V)) -am__v_at_ = $(am__v_at_$(AM_DEFAULT_VERBOSITY)) +AM_V_at = $(am__v_at_@AM_V@) +am__v_at_ = $(am__v_at_@AM_DEFAULT_V@) am__v_at_0 = @ CCLD = $(CC) LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ $(AM_LDFLAGS) $(LDFLAGS) -o $@ -AM_V_CCLD = $(am__v_CCLD_$(V)) -am__v_CCLD_ = $(am__v_CCLD_$(AM_DEFAULT_VERBOSITY)) +AM_V_CCLD = $(am__v_CCLD_@AM_V@) +am__v_CCLD_ = $(am__v_CCLD_@AM_DEFAULT_V@) am__v_CCLD_0 = @echo " CCLD " $@; -AM_V_GEN = $(am__v_GEN_$(V)) -am__v_GEN_ = $(am__v_GEN_$(AM_DEFAULT_VERBOSITY)) +AM_V_GEN = $(am__v_GEN_@AM_V@) +am__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@) am__v_GEN_0 = @echo " GEN " $@; SOURCES = $(gnunet_service_template_SOURCES) \ $(gnunet_template_SOURCES) $(test_template_api_SOURCES) DIST_SOURCES = $(gnunet_service_template_SOURCES) \ $(gnunet_template_SOURCES) $(test_template_api_SOURCES) +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac am__vpath_adj_setup = srcdirstrip=`echo "$(srcdir)" | sed 's|.|.|g'`; am__vpath_adj = case $$p in \ $(srcdir)/*) f=`echo "$$p" | sed "s|^$$srcdirstrip/||"`;; \ @@ -134,6 +158,12 @@ am__nobase_list = $(am__nobase_strip_setup); \ am__base_list = \ sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \ sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g' +am__uninstall_files_from_dir = { \ + test -z "$$files" \ + || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \ + || { echo " ( cd '$$dir' && rm -f" $$files ")"; \ + $(am__cd) "$$dir" && rm -f $$files; }; \ + } DATA = $(dist_pkgcfg_DATA) ETAGS = etags CTAGS = ctags @@ -175,6 +205,10 @@ EXEEXT = @EXEEXT@ EXT_LIBS = @EXT_LIBS@ EXT_LIB_PATH = @EXT_LIB_PATH@ FGREP = @FGREP@ +GLIB_CFLAGS = @GLIB_CFLAGS@ +GLIB_GENMARSHAL = @GLIB_GENMARSHAL@ +GLIB_LIBS = @GLIB_LIBS@ +GLIB_MKENUMS = @GLIB_MKENUMS@ GMSGFMT = @GMSGFMT@ GMSGFMT_015 = @GMSGFMT_015@ GNUNETDNS_GROUP = @GNUNETDNS_GROUP@ @@ -185,6 +219,7 @@ GN_LIBINTL = @GN_LIBINTL@ GN_LIB_LDFLAGS = @GN_LIB_LDFLAGS@ GN_PLUGIN_LDFLAGS = @GN_PLUGIN_LDFLAGS@ GN_USER_HOME_DIR = @GN_USER_HOME_DIR@ +GOBJECT_QUERY = @GOBJECT_QUERY@ GREP = @GREP@ HAVE_LIBUNISTRING = @HAVE_LIBUNISTRING@ INCLTDL = @INCLTDL@ @@ -207,6 +242,8 @@ LIBCURL_CPPFLAGS = @LIBCURL_CPPFLAGS@ LIBGCRYPT_CFLAGS = @LIBGCRYPT_CFLAGS@ LIBGCRYPT_CONFIG = @LIBGCRYPT_CONFIG@ LIBGCRYPT_LIBS = @LIBGCRYPT_LIBS@ +LIBGTOP_CFLAGS = @LIBGTOP_CFLAGS@ +LIBGTOP_LIBS = @LIBGTOP_LIBS@ LIBICONV = @LIBICONV@ LIBINTL = @LIBINTL@ LIBLTDL = @LIBLTDL@ @@ -228,6 +265,7 @@ LT_CONFIG_H = @LT_CONFIG_H@ LT_DLLOADERS = @LT_DLLOADERS@ LT_DLPREOPEN = @LT_DLPREOPEN@ MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ MKDIR_P = @MKDIR_P@ MONKEYPREFIX = @MONKEYPREFIX@ MSGFMT = @MSGFMT@ @@ -237,6 +275,7 @@ MYSQL_CPPFLAGS = @MYSQL_CPPFLAGS@ MYSQL_LDFLAGS = @MYSQL_LDFLAGS@ NM = @NM@ NMEDIT = @NMEDIT@ +NSS_DIR = @NSS_DIR@ OBJC = @OBJC@ OBJCDEPMODE = @OBJCDEPMODE@ OBJCFLAGS = @OBJCFLAGS@ @@ -252,6 +291,7 @@ PACKAGE_TARNAME = @PACKAGE_TARNAME@ PACKAGE_URL = @PACKAGE_URL@ PACKAGE_VERSION = @PACKAGE_VERSION@ PATH_SEPARATOR = @PATH_SEPARATOR@ +PKG_CONFIG = @PKG_CONFIG@ POSTGRES_CPPFLAGS = @POSTGRES_CPPFLAGS@ POSTGRES_LDFLAGS = @POSTGRES_LDFLAGS@ POSUB = @POSUB@ @@ -283,6 +323,7 @@ abs_builddir = @abs_builddir@ abs_srcdir = @abs_srcdir@ abs_top_builddir = @abs_top_builddir@ abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ ac_ct_CC = @ac_ct_CC@ ac_ct_CXX = @ac_ct_CXX@ ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ @@ -305,6 +346,7 @@ datarootdir = @datarootdir@ docdir = @docdir@ dvidir = @dvidir@ exec_prefix = @exec_prefix@ +gitcommand = @gitcommand@ host = @host@ host_alias = @host_alias@ host_cpu = @host_cpu@ @@ -315,10 +357,9 @@ includedir = @includedir@ infodir = @infodir@ install_sh = @install_sh@ libdir = @libdir@ -libexecdir = @libexecdir@ +libexecdir = $(pkglibdir)/libexec/ localedir = @localedir@ localstatedir = @localstatedir@ -lt_ECHO = @lt_ECHO@ ltdl_LIBOBJS = @ltdl_LIBOBJS@ ltdl_LTLIBOBJS = @ltdl_LTLIBOBJS@ mandir = @mandir@ @@ -336,6 +377,7 @@ sbindir = @sbindir@ sharedstatedir = @sharedstatedir@ srcdir = @srcdir@ subdirs = @subdirs@ +svnversioncommand = @svnversioncommand@ sys_symbol_underscore = @sys_symbol_underscore@ sysconfdir = @sysconfdir@ target = @target@ @@ -410,8 +452,11 @@ $(ACLOCAL_M4): $(am__aclocal_m4_deps) $(am__aclocal_m4_deps): install-binPROGRAMS: $(bin_PROGRAMS) @$(NORMAL_INSTALL) - test -z "$(bindir)" || $(MKDIR_P) "$(DESTDIR)$(bindir)" @list='$(bin_PROGRAMS)'; test -n "$(bindir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(bindir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(bindir)" || exit 1; \ + fi; \ for p in $$list; do echo "$$p $$p"; done | \ sed 's/$(EXEEXT)$$//' | \ while read p p1; do if test -f $$p || test -f $$p1; \ @@ -460,13 +505,59 @@ clean-checkPROGRAMS: list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ echo " rm -f" $$list; \ rm -f $$list -gnunet-service-template$(EXEEXT): $(gnunet_service_template_OBJECTS) $(gnunet_service_template_DEPENDENCIES) +install-libexecPROGRAMS: $(libexec_PROGRAMS) + @$(NORMAL_INSTALL) + @list='$(libexec_PROGRAMS)'; test -n "$(libexecdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(libexecdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libexecdir)" || exit 1; \ + fi; \ + for p in $$list; do echo "$$p $$p"; done | \ + sed 's/$(EXEEXT)$$//' | \ + while read p p1; do if test -f $$p || test -f $$p1; \ + then echo "$$p"; echo "$$p"; else :; fi; \ + done | \ + sed -e 'p;s,.*/,,;n;h' -e 's|.*|.|' \ + -e 'p;x;s,.*/,,;s/$(EXEEXT)$$//;$(transform);s/$$/$(EXEEXT)/' | \ + sed 'N;N;N;s,\n, ,g' | \ + $(AWK) 'BEGIN { files["."] = ""; dirs["."] = 1 } \ + { d=$$3; if (dirs[d] != 1) { print "d", d; dirs[d] = 1 } \ + if ($$2 == $$4) files[d] = files[d] " " $$1; \ + else { print "f", $$3 "/" $$4, $$1; } } \ + END { for (d in files) print "f", d, files[d] }' | \ + while read type dir files; do \ + if test "$$dir" = .; then dir=; else dir=/$$dir; fi; \ + test -z "$$files" || { \ + echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files '$(DESTDIR)$(libexecdir)$$dir'"; \ + $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files "$(DESTDIR)$(libexecdir)$$dir" || exit $$?; \ + } \ + ; done + +uninstall-libexecPROGRAMS: + @$(NORMAL_UNINSTALL) + @list='$(libexec_PROGRAMS)'; test -n "$(libexecdir)" || list=; \ + files=`for p in $$list; do echo "$$p"; done | \ + sed -e 'h;s,^.*/,,;s/$(EXEEXT)$$//;$(transform)' \ + -e 's/$$/$(EXEEXT)/' `; \ + test -n "$$list" || exit 0; \ + echo " ( cd '$(DESTDIR)$(libexecdir)' && rm -f" $$files ")"; \ + cd "$(DESTDIR)$(libexecdir)" && rm -f $$files + +clean-libexecPROGRAMS: + @list='$(libexec_PROGRAMS)'; test -n "$$list" || exit 0; \ + echo " rm -f" $$list; \ + rm -f $$list || exit $$?; \ + test -n "$(EXEEXT)" || exit 0; \ + list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ + echo " rm -f" $$list; \ + rm -f $$list +gnunet-service-template$(EXEEXT): $(gnunet_service_template_OBJECTS) $(gnunet_service_template_DEPENDENCIES) $(EXTRA_gnunet_service_template_DEPENDENCIES) @rm -f gnunet-service-template$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_service_template_OBJECTS) $(gnunet_service_template_LDADD) $(LIBS) -gnunet-template$(EXEEXT): $(gnunet_template_OBJECTS) $(gnunet_template_DEPENDENCIES) +gnunet-template$(EXEEXT): $(gnunet_template_OBJECTS) $(gnunet_template_DEPENDENCIES) $(EXTRA_gnunet_template_DEPENDENCIES) @rm -f gnunet-template$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_template_OBJECTS) $(gnunet_template_LDADD) $(LIBS) -test_template_api$(EXEEXT): $(test_template_api_OBJECTS) $(test_template_api_DEPENDENCIES) +test_template_api$(EXEEXT): $(test_template_api_OBJECTS) $(test_template_api_DEPENDENCIES) $(EXTRA_test_template_api_DEPENDENCIES) @rm -f test_template_api$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_template_api_OBJECTS) $(test_template_api_LDADD) $(LIBS) @@ -483,26 +574,23 @@ distclean-compile: .c.o: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c $< .c.obj: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'` @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c `$(CYGPATH_W) '$<'` +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c `$(CYGPATH_W) '$<'` .c.lo: @am__fastdepCC_TRUE@ $(AM_V_CC)$(LTCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LTCOMPILE) -c -o $@ $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LTCOMPILE) -c -o $@ $< mostlyclean-libtool: -rm -f *.lo @@ -511,8 +599,11 @@ clean-libtool: -rm -rf .libs _libs install-dist_pkgcfgDATA: $(dist_pkgcfg_DATA) @$(NORMAL_INSTALL) - test -z "$(pkgcfgdir)" || $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" @list='$(dist_pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(pkgcfgdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" || exit 1; \ + fi; \ for p in $$list; do \ if test -f "$$p"; then d=; else d="$(srcdir)/"; fi; \ echo "$$d$$p"; \ @@ -526,9 +617,7 @@ uninstall-dist_pkgcfgDATA: @$(NORMAL_UNINSTALL) @list='$(dist_pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ files=`for p in $$list; do echo $$p; done | sed -e 's|^.*/||'`; \ - test -n "$$files" || exit 0; \ - echo " ( cd '$(DESTDIR)$(pkgcfgdir)' && rm -f" $$files ")"; \ - cd "$(DESTDIR)$(pkgcfgdir)" && rm -f $$files + dir='$(DESTDIR)$(pkgcfgdir)'; $(am__uninstall_files_from_dir) ID: $(HEADERS) $(SOURCES) $(LISP) $(TAGS_FILES) list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ @@ -663,14 +752,15 @@ check-TESTS: $(TESTS) fi; \ dashes=`echo "$$dashes" | sed s/./=/g`; \ if test "$$failed" -eq 0; then \ - echo "$$grn$$dashes"; \ + col="$$grn"; \ else \ - echo "$$red$$dashes"; \ + col="$$red"; \ fi; \ - echo "$$banner"; \ - test -z "$$skipped" || echo "$$skipped"; \ - test -z "$$report" || echo "$$report"; \ - echo "$$dashes$$std"; \ + echo "$${col}$$dashes$${std}"; \ + echo "$${col}$$banner$${std}"; \ + test -z "$$skipped" || echo "$${col}$$skipped$${std}"; \ + test -z "$$report" || echo "$${col}$$report$${std}"; \ + echo "$${col}$$dashes$${std}"; \ test "$$failed" -eq 0; \ else :; fi @@ -710,7 +800,7 @@ check-am: all-am check: check-am all-am: Makefile $(PROGRAMS) $(DATA) installdirs: - for dir in "$(DESTDIR)$(bindir)" "$(DESTDIR)$(pkgcfgdir)"; do \ + for dir in "$(DESTDIR)$(bindir)" "$(DESTDIR)$(libexecdir)" "$(DESTDIR)$(pkgcfgdir)"; do \ test -z "$$dir" || $(MKDIR_P) "$$dir"; \ done install: install-am @@ -723,10 +813,15 @@ install-am: all-am installcheck: installcheck-am install-strip: - $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ - install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ - `test -z '$(STRIP)' || \ - echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi mostlyclean-generic: clean-generic: @@ -741,7 +836,7 @@ maintainer-clean-generic: clean: clean-am clean-am: clean-binPROGRAMS clean-checkPROGRAMS clean-generic \ - clean-libtool mostlyclean-am + clean-libexecPROGRAMS clean-libtool mostlyclean-am distclean: distclean-am -rm -rf ./$(DEPDIR) @@ -767,7 +862,7 @@ install-dvi: install-dvi-am install-dvi-am: -install-exec-am: install-binPROGRAMS +install-exec-am: install-binPROGRAMS install-libexecPROGRAMS install-html: install-html-am @@ -807,25 +902,27 @@ ps: ps-am ps-am: -uninstall-am: uninstall-binPROGRAMS uninstall-dist_pkgcfgDATA +uninstall-am: uninstall-binPROGRAMS uninstall-dist_pkgcfgDATA \ + uninstall-libexecPROGRAMS .MAKE: check-am install-am install-strip .PHONY: CTAGS GTAGS all all-am check check-TESTS check-am clean \ clean-binPROGRAMS clean-checkPROGRAMS clean-generic \ - clean-libtool ctags distclean distclean-compile \ - distclean-generic distclean-libtool distclean-tags distdir dvi \ - dvi-am html html-am info info-am install install-am \ - install-binPROGRAMS install-data install-data-am \ - install-dist_pkgcfgDATA install-dvi install-dvi-am \ - install-exec install-exec-am install-html install-html-am \ - install-info install-info-am install-man install-pdf \ - install-pdf-am install-ps install-ps-am install-strip \ - installcheck installcheck-am installdirs maintainer-clean \ + clean-libexecPROGRAMS clean-libtool ctags distclean \ + distclean-compile distclean-generic distclean-libtool \ + distclean-tags distdir dvi dvi-am html html-am info info-am \ + install install-am install-binPROGRAMS install-data \ + install-data-am install-dist_pkgcfgDATA install-dvi \ + install-dvi-am install-exec install-exec-am install-html \ + install-html-am install-info install-info-am \ + install-libexecPROGRAMS install-man install-pdf install-pdf-am \ + install-ps install-ps-am install-strip installcheck \ + installcheck-am installdirs maintainer-clean \ maintainer-clean-generic mostlyclean mostlyclean-compile \ mostlyclean-generic mostlyclean-libtool pdf pdf-am ps ps-am \ tags uninstall uninstall-am uninstall-binPROGRAMS \ - uninstall-dist_pkgcfgDATA + uninstall-dist_pkgcfgDATA uninstall-libexecPROGRAMS # Tell versions [3.59,3.63) of GNU make to not export all variables. diff --git a/src/template/gnunet-template.c b/src/template/gnunet-template.c index 7b1d9df..b0d25dc 100644 --- a/src/template/gnunet-template.c +++ b/src/template/gnunet-template.c @@ -24,8 +24,7 @@ * @author Christian Grothoff */ #include "platform.h" -#include "gnunet_getopt_lib.h" -#include "gnunet_program_lib.h" +#include "gnunet_util_lib.h" /* #include "gnunet_template_service.h" */ /** @@ -63,10 +62,15 @@ main (int argc, char *const *argv) /* FIMXE: add options here */ GNUNET_GETOPT_OPTION_END }; - return (GNUNET_OK == - GNUNET_PROGRAM_run (argc, argv, "gnunet-template", - gettext_noop ("help text"), options, &run, - NULL)) ? ret : 1; + if (GNUNET_OK != GNUNET_STRINGS_get_utf8_args (argc, argv, &argc, &argv)) + return 2; + + ret = (GNUNET_OK == + GNUNET_PROGRAM_run (argc, argv, "gnunet-template", + gettext_noop ("help text"), options, &run, + NULL)) ? ret : 1; + GNUNET_free ((void*) argv); + return ret; } /* end of gnunet-template.c */ diff --git a/src/template/template.conf b/src/template/template.conf index 522721f..439bbd2 100644 --- a/src/template/template.conf +++ b/src/template/template.conf @@ -3,7 +3,6 @@ AUTOSTART = NO PORT = 9999 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-template ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; diff --git a/src/template/test_template_api.c b/src/template/test_template_api.c index b987851..a08a6d8 100644 --- a/src/template/test_template_api.c +++ b/src/template/test_template_api.c @@ -18,13 +18,12 @@ Boston, MA 02111-1307, USA. */ /** - * @file template/test_template.c + * @file template/test_template_api.c * @brief testcase for template.c */ #include "platform.h" #include "gnunet_common.h" -#define VERBOSE GNUNET_NO static int check () @@ -42,4 +41,4 @@ main (int argc, char *argv[]) return ret; } -/* end of test_template.c */ +/* end of test_template_api.c */ diff --git a/src/testbed/Makefile.am b/src/testbed/Makefile.am index b7b9360..5977740 100644 --- a/src/testbed/Makefile.am +++ b/src/testbed/Makefile.am @@ -9,31 +9,289 @@ if USE_COVERAGE XLIB = -lgcov endif +if WITH_LL + CC = mpcc + ll_noinst_binaries = \ + ll-master \ + ll-monitor + ll_binaries = \ + gnunet-mpi-test +endif + +libexecdir= $(pkglibdir)/libexec/ + pkgcfgdir= $(pkgdatadir)/config.d/ -dist_pkgcfg_DATA = \ +pkgcfg_DATA = \ testbed.conf +libexec_PROGRAMS = \ + gnunet-service-testbed \ + gnunet-helper-testbed + +bin_PROGRAMS = \ + $(ll_binaries) + +noinst_PROGRAMS = \ + gnunet-testbed-profiler \ + $(ll_noinst_binaries) + +gnunet_service_testbed_SOURCES = \ + gnunet-service-testbed.c \ + gnunet-service-testbed.h \ + gnunet-service-testbed_cache.c \ + gnunet-service-testbed_oc.c +gnunet_service_testbed_LDADD = $(XLIB) \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/core/libgnunetcore.la \ + $(top_builddir)/src/hello/libgnunethello.la \ + $(top_builddir)/src/transport/libgnunettransport.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la \ + $(LTLIBINTL) -lz +gnunet_service_testbed_DEPENDENCIES = \ + libgnunettestbed.la + +gnunet_testbed_profiler_SOURCES = \ + gnunet-testbed-profiler.c +gnunet_testbed_profiler_LDADD = $(XLIB) \ + $(top_builddir)/src/util/libgnunetutil.la \ + libgnunettestbed.la + +gnunet_helper_testbed_SOURCES = \ + gnunet-helper-testbed.c +gnunet_helper_testbed_LDADD = $(XLIB) \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + libgnunettestbed.la \ + $(LTLIBINTL) -lz +gnunet_helper_testbed_DEPENDENCIES = \ + gnunet-service-testbed.$(OBJEXT) \ + libgnunettestbed.la + +ll_master_SOURCES = \ + ll_master.c +ll_master_LDADD = $(XLIB) \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(LTLIBINTL) -lz -lllapi + +ll_monitor_SOURCES = \ + ll_monitor.c +ll_monitor_LDADD = $(XLIB) \ + $(LTLIBINTL) -lz -lllapi + +gnunet_mpi_test_SOURCES = gnunet_mpi_test.c +gnunet_mpi_test_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la + lib_LTLIBRARIES = \ libgnunettestbed.la libgnunettestbed_la_SOURCES = \ - testbed_api.c testbed.h \ - testbed_api_hosts.c testbed_api_hosts.h \ + testbed_api.c testbed_api.h testbed.h \ + testbed_api_hosts.c testbed_api_hosts.h testbed_helper.h \ testbed_api_operations.c testbed_api_operations.h \ testbed_api_peers.c testbed_api_peers.h \ testbed_api_services.c \ + testbed_api_statistics.c \ testbed_api_testbed.c \ testbed_api_test.c \ - testbed_api_topology.c + testbed_api_topology.c testbed_api_topology.h libgnunettestbed_la_LIBADD = $(XLIB) \ $(top_builddir)/src/core/libgnunetcore.la \ $(top_builddir)/src/statistics/libgnunetstatistics.la \ $(top_builddir)/src/transport/libgnunettransport.la \ $(top_builddir)/src/hello/libgnunethello.la \ -lm \ - $(top_builddir)/src/util/libgnunetutil.la + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(LTLIBINTL) libgnunettestbed_la_LDFLAGS = \ $(GN_LIB_LDFLAGS) \ -version-info 0:0:0 +check_PROGRAMS = \ + test_testbed_api_hosts \ + test_testbed_api_controllerlink \ + test_testbed_api_2peers_1controller \ + test_testbed_api_3peers_3controllers \ + test_testbed_api \ + test_testbed_api_operations \ + test_testbed_api_testbed_run \ + test_testbed_api_test \ + test_gnunet_helper_testbed \ + test_testbed_api_topology \ + test_testbed_api_topology_clique \ + test_testbed_api_testbed_run_topologyrandom \ + test_testbed_api_testbed_run_topologyline \ + test_testbed_api_testbed_run_topologyclique \ + test_testbed_api_testbed_run_topologyring \ + test_testbed_api_testbed_run_topologysmallworldring \ + test_testbed_api_testbed_run_topology2dtorus \ + test_testbed_api_testbed_run_topologysmallworld \ + test_testbed_api_testbed_run_topologyfromfile \ + test_testbed_api_testbed_run_topologyscalefree + +if ENABLE_TEST_RUN + TESTS = \ + test_testbed_api \ + test_testbed_api_hosts \ + test_testbed_api_2peers_1controller \ + test_testbed_api_3peers_3controllers \ + test_testbed_api_operations \ + test_gnunet_helper_testbed \ + test_testbed_api_controllerlink \ + test_testbed_api_testbed_run \ + test_testbed_api_test \ + test_testbed_api_topology \ + test_testbed_api_topology_clique \ + test_testbed_api_testbed_run_topologyrandom \ + test_testbed_api_testbed_run_topologyline \ + test_testbed_api_testbed_run_topologyclique \ + test_testbed_api_testbed_run_topologyring \ + test_testbed_api_testbed_run_topologysmallworldring \ + test_testbed_api_testbed_run_topology2dtorus \ + test_testbed_api_testbed_run_topologysmallworld \ + test_testbed_api_testbed_run_topologyfromfile \ + test_testbed_api_testbed_run_topologyscalefree +endif + +test_testbed_api_hosts_SOURCES = \ + test_testbed_api_hosts.c +test_testbed_api_hosts_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + libgnunettestbed.la + +test_testbed_api_SOURCES = \ + test_testbed_api.c +test_testbed_api_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/dht/libgnunetdht.la \ + libgnunettestbed.la + +test_testbed_api_2peers_1controller_SOURCES = \ + test_testbed_api_2peers_1controller.c +test_testbed_api_2peers_1controller_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + libgnunettestbed.la + +test_testbed_api_3peers_3controllers_SOURCES = \ + test_testbed_api_3peers_3controllers.c +test_testbed_api_3peers_3controllers_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + libgnunettestbed.la + +test_testbed_api_operations_SOURCES = \ + test_testbed_api_operations.c +test_testbed_api_operations_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + libgnunettestbed.la + +test_testbed_api_controllerlink_SOURCES = \ + test_testbed_api_controllerlink.c +test_testbed_api_controllerlink_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + libgnunettestbed.la + +test_testbed_api_testbed_run_SOURCES = \ + test_testbed_api_testbed_run.c +test_testbed_api_testbed_run_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + libgnunettestbed.la + +test_testbed_api_test_SOURCES = \ + test_testbed_api_test.c +test_testbed_api_test_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + libgnunettestbed.la + +test_testbed_api_topology_SOURCES = \ + test_testbed_api_topology.c +test_testbed_api_topology_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + libgnunettestbed.la + +test_testbed_api_topology_clique_SOURCES = \ + test_testbed_api_topology_clique.c +test_testbed_api_topology_clique_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + libgnunettestbed.la + +test_gnunet_helper_testbed_SOURCES = \ + test_gnunet_helper_testbed.c +test_gnunet_helper_testbed_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + libgnunettestbed.la \ + -lz + +test_testbed_api_testbed_run_topologyrandom_SOURCES = \ + test_testbed_api_testbed_run.c +test_testbed_api_testbed_run_topologyrandom_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + libgnunettestbed.la + +test_testbed_api_testbed_run_topologyline_SOURCES = \ + test_testbed_api_testbed_run.c +test_testbed_api_testbed_run_topologyline_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + libgnunettestbed.la + +test_testbed_api_testbed_run_topologyclique_SOURCES = \ + test_testbed_api_testbed_run.c +test_testbed_api_testbed_run_topologyclique_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + libgnunettestbed.la + +test_testbed_api_testbed_run_topologyring_SOURCES = \ + test_testbed_api_testbed_run.c +test_testbed_api_testbed_run_topologyring_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + libgnunettestbed.la + +test_testbed_api_testbed_run_topologysmallworldring_SOURCES = \ + test_testbed_api_testbed_run.c +test_testbed_api_testbed_run_topologysmallworldring_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + libgnunettestbed.la + +test_testbed_api_testbed_run_topology2dtorus_SOURCES = \ + test_testbed_api_testbed_run.c +test_testbed_api_testbed_run_topology2dtorus_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + libgnunettestbed.la + +test_testbed_api_testbed_run_topologysmallworld_SOURCES = \ + test_testbed_api_testbed_run.c +test_testbed_api_testbed_run_topologysmallworld_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + libgnunettestbed.la + +test_testbed_api_testbed_run_topologyfromfile_SOURCES = \ + test_testbed_api_testbed_run.c +test_testbed_api_testbed_run_topologyfromfile_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + libgnunettestbed.la + +test_testbed_api_testbed_run_topologyscalefree_SOURCES = \ + test_testbed_api_testbed_run.c +test_testbed_api_testbed_run_topologyscalefree_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + libgnunettestbed.la + +EXTRA_DIST = \ + test_testbed_api.conf \ + test_testbed_api_testbed_run_topologyring.conf \ + test_testbed_api_testbed_run_topologyclique.conf \ + test_testbed_api_testbed_run_topologyline.conf \ + test_testbed_api_testbed_run_topologyrandom.conf \ + test_testbed_api_testbed_run_topologysmallworldring.conf \ + test_testbed_api_testbed_run_topology2dtorus.conf \ + test_testbed_api_testbed_run_topologysmallworld.conf \ + test_testbed_api_testbed_run_topologyfromfile.conf \ + test_testbed_api_testbed_run_topologyscalefree.conf \ + overlay_topology.txt \ + sample_hosts.txt \ + sample.job diff --git a/src/testbed/Makefile.in b/src/testbed/Makefile.in index 3b08315..1b3c3e2 100644 --- a/src/testbed/Makefile.in +++ b/src/testbed/Makefile.in @@ -1,9 +1,9 @@ -# Makefile.in generated by automake 1.11.1 from Makefile.am. +# Makefile.in generated by automake 1.11.6 from Makefile.am. # @configure_input@ # Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, -# 2003, 2004, 2005, 2006, 2007, 2008, 2009 Free Software Foundation, -# Inc. +# 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Free Software +# Foundation, Inc. # This Makefile.in is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. @@ -16,7 +16,25 @@ @SET_MAKE@ + VPATH = @srcdir@ +am__make_dryrun = \ + { \ + am__dry=no; \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + echo 'am--echo: ; @echo "AM" OK' | $(MAKE) -f - 2>/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } pkgdatadir = $(datadir)/@PACKAGE@ pkgincludedir = $(includedir)/@PACKAGE@ pkglibdir = $(libdir)/@PACKAGE@ @@ -36,27 +54,71 @@ POST_UNINSTALL = : build_triplet = @build@ host_triplet = @host@ target_triplet = @target@ +libexec_PROGRAMS = gnunet-service-testbed$(EXEEXT) \ + gnunet-helper-testbed$(EXEEXT) +bin_PROGRAMS = $(am__EXEEXT_1) +noinst_PROGRAMS = gnunet-testbed-profiler$(EXEEXT) $(am__EXEEXT_2) +check_PROGRAMS = test_testbed_api_hosts$(EXEEXT) \ + test_testbed_api_controllerlink$(EXEEXT) \ + test_testbed_api_2peers_1controller$(EXEEXT) \ + test_testbed_api_3peers_3controllers$(EXEEXT) \ + test_testbed_api$(EXEEXT) test_testbed_api_operations$(EXEEXT) \ + test_testbed_api_testbed_run$(EXEEXT) \ + test_testbed_api_test$(EXEEXT) \ + test_gnunet_helper_testbed$(EXEEXT) \ + test_testbed_api_topology$(EXEEXT) \ + test_testbed_api_topology_clique$(EXEEXT) \ + test_testbed_api_testbed_run_topologyrandom$(EXEEXT) \ + test_testbed_api_testbed_run_topologyline$(EXEEXT) \ + test_testbed_api_testbed_run_topologyclique$(EXEEXT) \ + test_testbed_api_testbed_run_topologyring$(EXEEXT) \ + test_testbed_api_testbed_run_topologysmallworldring$(EXEEXT) \ + test_testbed_api_testbed_run_topology2dtorus$(EXEEXT) \ + test_testbed_api_testbed_run_topologysmallworld$(EXEEXT) \ + test_testbed_api_testbed_run_topologyfromfile$(EXEEXT) \ + test_testbed_api_testbed_run_topologyscalefree$(EXEEXT) +@ENABLE_TEST_RUN_TRUE@TESTS = test_testbed_api$(EXEEXT) \ +@ENABLE_TEST_RUN_TRUE@ test_testbed_api_hosts$(EXEEXT) \ +@ENABLE_TEST_RUN_TRUE@ test_testbed_api_2peers_1controller$(EXEEXT) \ +@ENABLE_TEST_RUN_TRUE@ test_testbed_api_3peers_3controllers$(EXEEXT) \ +@ENABLE_TEST_RUN_TRUE@ test_testbed_api_operations$(EXEEXT) \ +@ENABLE_TEST_RUN_TRUE@ test_gnunet_helper_testbed$(EXEEXT) \ +@ENABLE_TEST_RUN_TRUE@ test_testbed_api_controllerlink$(EXEEXT) \ +@ENABLE_TEST_RUN_TRUE@ test_testbed_api_testbed_run$(EXEEXT) \ +@ENABLE_TEST_RUN_TRUE@ test_testbed_api_test$(EXEEXT) \ +@ENABLE_TEST_RUN_TRUE@ test_testbed_api_topology$(EXEEXT) \ +@ENABLE_TEST_RUN_TRUE@ test_testbed_api_topology_clique$(EXEEXT) \ +@ENABLE_TEST_RUN_TRUE@ test_testbed_api_testbed_run_topologyrandom$(EXEEXT) \ +@ENABLE_TEST_RUN_TRUE@ test_testbed_api_testbed_run_topologyline$(EXEEXT) \ +@ENABLE_TEST_RUN_TRUE@ test_testbed_api_testbed_run_topologyclique$(EXEEXT) \ +@ENABLE_TEST_RUN_TRUE@ test_testbed_api_testbed_run_topologyring$(EXEEXT) \ +@ENABLE_TEST_RUN_TRUE@ test_testbed_api_testbed_run_topologysmallworldring$(EXEEXT) \ +@ENABLE_TEST_RUN_TRUE@ test_testbed_api_testbed_run_topology2dtorus$(EXEEXT) \ +@ENABLE_TEST_RUN_TRUE@ test_testbed_api_testbed_run_topologysmallworld$(EXEEXT) \ +@ENABLE_TEST_RUN_TRUE@ test_testbed_api_testbed_run_topologyfromfile$(EXEEXT) \ +@ENABLE_TEST_RUN_TRUE@ test_testbed_api_testbed_run_topologyscalefree$(EXEEXT) subdir = src/testbed -DIST_COMMON = $(dist_pkgcfg_DATA) $(srcdir)/Makefile.am \ - $(srcdir)/Makefile.in +DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in \ + $(srcdir)/testbed.conf.in ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 am__aclocal_m4_deps = $(top_srcdir)/m4/absolute-header.m4 \ $(top_srcdir)/m4/align.m4 $(top_srcdir)/m4/argz.m4 \ - $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/iconv.m4 \ - $(top_srcdir)/m4/lib-ld.m4 $(top_srcdir)/m4/lib-link.m4 \ - $(top_srcdir)/m4/lib-prefix.m4 $(top_srcdir)/m4/libcurl.m4 \ - $(top_srcdir)/m4/libgcrypt.m4 $(top_srcdir)/m4/libtool.m4 \ - $(top_srcdir)/m4/libunistring.m4 $(top_srcdir)/m4/ltdl.m4 \ - $(top_srcdir)/m4/ltoptions.m4 $(top_srcdir)/m4/ltsugar.m4 \ - $(top_srcdir)/m4/ltversion.m4 $(top_srcdir)/m4/lt~obsolete.m4 \ - $(top_srcdir)/m4/nls.m4 $(top_srcdir)/m4/po.m4 \ + $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/glib-2.0.m4 \ + $(top_srcdir)/m4/iconv.m4 $(top_srcdir)/m4/lib-ld.m4 \ + $(top_srcdir)/m4/lib-link.m4 $(top_srcdir)/m4/lib-prefix.m4 \ + $(top_srcdir)/m4/libcurl.m4 $(top_srcdir)/m4/libgcrypt.m4 \ + $(top_srcdir)/m4/libtool.m4 $(top_srcdir)/m4/libunistring.m4 \ + $(top_srcdir)/m4/ltdl.m4 $(top_srcdir)/m4/ltoptions.m4 \ + $(top_srcdir)/m4/ltsugar.m4 $(top_srcdir)/m4/ltversion.m4 \ + $(top_srcdir)/m4/lt~obsolete.m4 $(top_srcdir)/m4/nls.m4 \ + $(top_srcdir)/m4/pkg.m4 $(top_srcdir)/m4/po.m4 \ $(top_srcdir)/m4/progtest.m4 $(top_srcdir)/acinclude.m4 \ $(top_srcdir)/configure.ac am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ $(ACLOCAL_M4) mkinstalldirs = $(install_sh) -d CONFIG_HEADER = $(top_builddir)/gnunet_config.h -CONFIG_CLEAN_FILES = +CONFIG_CLEAN_FILES = testbed.conf CONFIG_CLEAN_VPATH_FILES = am__vpath_adj_setup = srcdirstrip=`echo "$(srcdir)" | sed 's|.|.|g'`; am__vpath_adj = case $$p in \ @@ -79,7 +141,14 @@ am__nobase_list = $(am__nobase_strip_setup); \ am__base_list = \ sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \ sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g' -am__installdirs = "$(DESTDIR)$(libdir)" "$(DESTDIR)$(pkgcfgdir)" +am__uninstall_files_from_dir = { \ + test -z "$$files" \ + || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \ + || { echo " ( cd '$$dir' && rm -f" $$files ")"; \ + $(am__cd) "$$dir" && rm -f $$files; }; \ + } +am__installdirs = "$(DESTDIR)$(libdir)" "$(DESTDIR)$(bindir)" \ + "$(DESTDIR)$(libexecdir)" "$(DESTDIR)$(pkgcfgdir)" LTLIBRARIES = $(lib_LTLIBRARIES) am__DEPENDENCIES_1 = libgnunettestbed_la_DEPENDENCIES = $(am__DEPENDENCIES_1) \ @@ -87,19 +156,168 @@ libgnunettestbed_la_DEPENDENCIES = $(am__DEPENDENCIES_1) \ $(top_builddir)/src/statistics/libgnunetstatistics.la \ $(top_builddir)/src/transport/libgnunettransport.la \ $(top_builddir)/src/hello/libgnunethello.la \ - $(top_builddir)/src/util/libgnunetutil.la + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(am__DEPENDENCIES_1) am_libgnunettestbed_la_OBJECTS = testbed_api.lo testbed_api_hosts.lo \ testbed_api_operations.lo testbed_api_peers.lo \ - testbed_api_services.lo testbed_api_testbed.lo \ - testbed_api_test.lo testbed_api_topology.lo + testbed_api_services.lo testbed_api_statistics.lo \ + testbed_api_testbed.lo testbed_api_test.lo \ + testbed_api_topology.lo libgnunettestbed_la_OBJECTS = $(am_libgnunettestbed_la_OBJECTS) -AM_V_lt = $(am__v_lt_$(V)) -am__v_lt_ = $(am__v_lt_$(AM_DEFAULT_VERBOSITY)) +AM_V_lt = $(am__v_lt_@AM_V@) +am__v_lt_ = $(am__v_lt_@AM_DEFAULT_V@) am__v_lt_0 = --silent libgnunettestbed_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ $(AM_CFLAGS) $(CFLAGS) $(libgnunettestbed_la_LDFLAGS) \ $(LDFLAGS) -o $@ +@WITH_LL_TRUE@am__EXEEXT_1 = gnunet-mpi-test$(EXEEXT) +@WITH_LL_TRUE@am__EXEEXT_2 = ll-master$(EXEEXT) ll-monitor$(EXEEXT) +PROGRAMS = $(bin_PROGRAMS) $(libexec_PROGRAMS) $(noinst_PROGRAMS) +am_gnunet_helper_testbed_OBJECTS = gnunet-helper-testbed.$(OBJEXT) +gnunet_helper_testbed_OBJECTS = $(am_gnunet_helper_testbed_OBJECTS) +am_gnunet_mpi_test_OBJECTS = gnunet_mpi_test.$(OBJEXT) +gnunet_mpi_test_OBJECTS = $(am_gnunet_mpi_test_OBJECTS) +gnunet_mpi_test_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la +am_gnunet_service_testbed_OBJECTS = gnunet-service-testbed.$(OBJEXT) \ + gnunet-service-testbed_cache.$(OBJEXT) \ + gnunet-service-testbed_oc.$(OBJEXT) +gnunet_service_testbed_OBJECTS = $(am_gnunet_service_testbed_OBJECTS) +am_gnunet_testbed_profiler_OBJECTS = \ + gnunet-testbed-profiler.$(OBJEXT) +gnunet_testbed_profiler_OBJECTS = \ + $(am_gnunet_testbed_profiler_OBJECTS) +gnunet_testbed_profiler_DEPENDENCIES = $(am__DEPENDENCIES_1) \ + $(top_builddir)/src/util/libgnunetutil.la libgnunettestbed.la +am_ll_master_OBJECTS = ll_master.$(OBJEXT) +ll_master_OBJECTS = $(am_ll_master_OBJECTS) +ll_master_DEPENDENCIES = $(am__DEPENDENCIES_1) \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(am__DEPENDENCIES_1) +am_ll_monitor_OBJECTS = ll_monitor.$(OBJEXT) +ll_monitor_OBJECTS = $(am_ll_monitor_OBJECTS) +ll_monitor_DEPENDENCIES = $(am__DEPENDENCIES_1) $(am__DEPENDENCIES_1) +am_test_gnunet_helper_testbed_OBJECTS = \ + test_gnunet_helper_testbed.$(OBJEXT) +test_gnunet_helper_testbed_OBJECTS = \ + $(am_test_gnunet_helper_testbed_OBJECTS) +test_gnunet_helper_testbed_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la libgnunettestbed.la +am_test_testbed_api_OBJECTS = test_testbed_api.$(OBJEXT) +test_testbed_api_OBJECTS = $(am_test_testbed_api_OBJECTS) +test_testbed_api_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/dht/libgnunetdht.la libgnunettestbed.la +am_test_testbed_api_2peers_1controller_OBJECTS = \ + test_testbed_api_2peers_1controller.$(OBJEXT) +test_testbed_api_2peers_1controller_OBJECTS = \ + $(am_test_testbed_api_2peers_1controller_OBJECTS) +test_testbed_api_2peers_1controller_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + libgnunettestbed.la +am_test_testbed_api_3peers_3controllers_OBJECTS = \ + test_testbed_api_3peers_3controllers.$(OBJEXT) +test_testbed_api_3peers_3controllers_OBJECTS = \ + $(am_test_testbed_api_3peers_3controllers_OBJECTS) +test_testbed_api_3peers_3controllers_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + libgnunettestbed.la +am_test_testbed_api_controllerlink_OBJECTS = \ + test_testbed_api_controllerlink.$(OBJEXT) +test_testbed_api_controllerlink_OBJECTS = \ + $(am_test_testbed_api_controllerlink_OBJECTS) +test_testbed_api_controllerlink_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la libgnunettestbed.la +am_test_testbed_api_hosts_OBJECTS = test_testbed_api_hosts.$(OBJEXT) +test_testbed_api_hosts_OBJECTS = $(am_test_testbed_api_hosts_OBJECTS) +test_testbed_api_hosts_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la libgnunettestbed.la +am_test_testbed_api_operations_OBJECTS = \ + test_testbed_api_operations.$(OBJEXT) +test_testbed_api_operations_OBJECTS = \ + $(am_test_testbed_api_operations_OBJECTS) +test_testbed_api_operations_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la libgnunettestbed.la +am_test_testbed_api_test_OBJECTS = test_testbed_api_test.$(OBJEXT) +test_testbed_api_test_OBJECTS = $(am_test_testbed_api_test_OBJECTS) +test_testbed_api_test_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la libgnunettestbed.la +am_test_testbed_api_testbed_run_OBJECTS = \ + test_testbed_api_testbed_run.$(OBJEXT) +test_testbed_api_testbed_run_OBJECTS = \ + $(am_test_testbed_api_testbed_run_OBJECTS) +test_testbed_api_testbed_run_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la libgnunettestbed.la +am_test_testbed_api_testbed_run_topology2dtorus_OBJECTS = \ + test_testbed_api_testbed_run.$(OBJEXT) +test_testbed_api_testbed_run_topology2dtorus_OBJECTS = \ + $(am_test_testbed_api_testbed_run_topology2dtorus_OBJECTS) +test_testbed_api_testbed_run_topology2dtorus_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la libgnunettestbed.la +am_test_testbed_api_testbed_run_topologyclique_OBJECTS = \ + test_testbed_api_testbed_run.$(OBJEXT) +test_testbed_api_testbed_run_topologyclique_OBJECTS = \ + $(am_test_testbed_api_testbed_run_topologyclique_OBJECTS) +test_testbed_api_testbed_run_topologyclique_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la libgnunettestbed.la +am_test_testbed_api_testbed_run_topologyfromfile_OBJECTS = \ + test_testbed_api_testbed_run.$(OBJEXT) +test_testbed_api_testbed_run_topologyfromfile_OBJECTS = \ + $(am_test_testbed_api_testbed_run_topologyfromfile_OBJECTS) +test_testbed_api_testbed_run_topologyfromfile_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la libgnunettestbed.la +am_test_testbed_api_testbed_run_topologyline_OBJECTS = \ + test_testbed_api_testbed_run.$(OBJEXT) +test_testbed_api_testbed_run_topologyline_OBJECTS = \ + $(am_test_testbed_api_testbed_run_topologyline_OBJECTS) +test_testbed_api_testbed_run_topologyline_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la libgnunettestbed.la +am_test_testbed_api_testbed_run_topologyrandom_OBJECTS = \ + test_testbed_api_testbed_run.$(OBJEXT) +test_testbed_api_testbed_run_topologyrandom_OBJECTS = \ + $(am_test_testbed_api_testbed_run_topologyrandom_OBJECTS) +test_testbed_api_testbed_run_topologyrandom_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la libgnunettestbed.la +am_test_testbed_api_testbed_run_topologyring_OBJECTS = \ + test_testbed_api_testbed_run.$(OBJEXT) +test_testbed_api_testbed_run_topologyring_OBJECTS = \ + $(am_test_testbed_api_testbed_run_topologyring_OBJECTS) +test_testbed_api_testbed_run_topologyring_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la libgnunettestbed.la +am_test_testbed_api_testbed_run_topologyscalefree_OBJECTS = \ + test_testbed_api_testbed_run.$(OBJEXT) +test_testbed_api_testbed_run_topologyscalefree_OBJECTS = \ + $(am_test_testbed_api_testbed_run_topologyscalefree_OBJECTS) +test_testbed_api_testbed_run_topologyscalefree_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la libgnunettestbed.la +am_test_testbed_api_testbed_run_topologysmallworld_OBJECTS = \ + test_testbed_api_testbed_run.$(OBJEXT) +test_testbed_api_testbed_run_topologysmallworld_OBJECTS = \ + $(am_test_testbed_api_testbed_run_topologysmallworld_OBJECTS) +test_testbed_api_testbed_run_topologysmallworld_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la libgnunettestbed.la +am_test_testbed_api_testbed_run_topologysmallworldring_OBJECTS = \ + test_testbed_api_testbed_run.$(OBJEXT) +test_testbed_api_testbed_run_topologysmallworldring_OBJECTS = $(am_test_testbed_api_testbed_run_topologysmallworldring_OBJECTS) +test_testbed_api_testbed_run_topologysmallworldring_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la libgnunettestbed.la +am_test_testbed_api_topology_OBJECTS = \ + test_testbed_api_topology.$(OBJEXT) +test_testbed_api_topology_OBJECTS = \ + $(am_test_testbed_api_topology_OBJECTS) +test_testbed_api_topology_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la libgnunettestbed.la +am_test_testbed_api_topology_clique_OBJECTS = \ + test_testbed_api_topology_clique.$(OBJEXT) +test_testbed_api_topology_clique_OBJECTS = \ + $(am_test_testbed_api_topology_clique_OBJECTS) +test_testbed_api_topology_clique_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la libgnunettestbed.la DEFAULT_INCLUDES = -I.@am__isrc@ -I$(top_builddir) depcomp = $(SHELL) $(top_srcdir)/depcomp am__depfiles_maybe = depfiles @@ -110,27 +328,80 @@ LTCOMPILE = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) \ $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) \ $(AM_CFLAGS) $(CFLAGS) -AM_V_CC = $(am__v_CC_$(V)) -am__v_CC_ = $(am__v_CC_$(AM_DEFAULT_VERBOSITY)) +AM_V_CC = $(am__v_CC_@AM_V@) +am__v_CC_ = $(am__v_CC_@AM_DEFAULT_V@) am__v_CC_0 = @echo " CC " $@; -AM_V_at = $(am__v_at_$(V)) -am__v_at_ = $(am__v_at_$(AM_DEFAULT_VERBOSITY)) +AM_V_at = $(am__v_at_@AM_V@) +am__v_at_ = $(am__v_at_@AM_DEFAULT_V@) am__v_at_0 = @ CCLD = $(CC) LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ $(AM_LDFLAGS) $(LDFLAGS) -o $@ -AM_V_CCLD = $(am__v_CCLD_$(V)) -am__v_CCLD_ = $(am__v_CCLD_$(AM_DEFAULT_VERBOSITY)) +AM_V_CCLD = $(am__v_CCLD_@AM_V@) +am__v_CCLD_ = $(am__v_CCLD_@AM_DEFAULT_V@) am__v_CCLD_0 = @echo " CCLD " $@; -AM_V_GEN = $(am__v_GEN_$(V)) -am__v_GEN_ = $(am__v_GEN_$(AM_DEFAULT_VERBOSITY)) +AM_V_GEN = $(am__v_GEN_@AM_V@) +am__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@) am__v_GEN_0 = @echo " GEN " $@; -SOURCES = $(libgnunettestbed_la_SOURCES) -DIST_SOURCES = $(libgnunettestbed_la_SOURCES) -DATA = $(dist_pkgcfg_DATA) +SOURCES = $(libgnunettestbed_la_SOURCES) \ + $(gnunet_helper_testbed_SOURCES) $(gnunet_mpi_test_SOURCES) \ + $(gnunet_service_testbed_SOURCES) \ + $(gnunet_testbed_profiler_SOURCES) $(ll_master_SOURCES) \ + $(ll_monitor_SOURCES) $(test_gnunet_helper_testbed_SOURCES) \ + $(test_testbed_api_SOURCES) \ + $(test_testbed_api_2peers_1controller_SOURCES) \ + $(test_testbed_api_3peers_3controllers_SOURCES) \ + $(test_testbed_api_controllerlink_SOURCES) \ + $(test_testbed_api_hosts_SOURCES) \ + $(test_testbed_api_operations_SOURCES) \ + $(test_testbed_api_test_SOURCES) \ + $(test_testbed_api_testbed_run_SOURCES) \ + $(test_testbed_api_testbed_run_topology2dtorus_SOURCES) \ + $(test_testbed_api_testbed_run_topologyclique_SOURCES) \ + $(test_testbed_api_testbed_run_topologyfromfile_SOURCES) \ + $(test_testbed_api_testbed_run_topologyline_SOURCES) \ + $(test_testbed_api_testbed_run_topologyrandom_SOURCES) \ + $(test_testbed_api_testbed_run_topologyring_SOURCES) \ + $(test_testbed_api_testbed_run_topologyscalefree_SOURCES) \ + $(test_testbed_api_testbed_run_topologysmallworld_SOURCES) \ + $(test_testbed_api_testbed_run_topologysmallworldring_SOURCES) \ + $(test_testbed_api_topology_SOURCES) \ + $(test_testbed_api_topology_clique_SOURCES) +DIST_SOURCES = $(libgnunettestbed_la_SOURCES) \ + $(gnunet_helper_testbed_SOURCES) $(gnunet_mpi_test_SOURCES) \ + $(gnunet_service_testbed_SOURCES) \ + $(gnunet_testbed_profiler_SOURCES) $(ll_master_SOURCES) \ + $(ll_monitor_SOURCES) $(test_gnunet_helper_testbed_SOURCES) \ + $(test_testbed_api_SOURCES) \ + $(test_testbed_api_2peers_1controller_SOURCES) \ + $(test_testbed_api_3peers_3controllers_SOURCES) \ + $(test_testbed_api_controllerlink_SOURCES) \ + $(test_testbed_api_hosts_SOURCES) \ + $(test_testbed_api_operations_SOURCES) \ + $(test_testbed_api_test_SOURCES) \ + $(test_testbed_api_testbed_run_SOURCES) \ + $(test_testbed_api_testbed_run_topology2dtorus_SOURCES) \ + $(test_testbed_api_testbed_run_topologyclique_SOURCES) \ + $(test_testbed_api_testbed_run_topologyfromfile_SOURCES) \ + $(test_testbed_api_testbed_run_topologyline_SOURCES) \ + $(test_testbed_api_testbed_run_topologyrandom_SOURCES) \ + $(test_testbed_api_testbed_run_topologyring_SOURCES) \ + $(test_testbed_api_testbed_run_topologyscalefree_SOURCES) \ + $(test_testbed_api_testbed_run_topologysmallworld_SOURCES) \ + $(test_testbed_api_testbed_run_topologysmallworldring_SOURCES) \ + $(test_testbed_api_topology_SOURCES) \ + $(test_testbed_api_topology_clique_SOURCES) +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac +DATA = $(pkgcfg_DATA) ETAGS = etags CTAGS = ctags +am__tty_colors = \ +red=; grn=; lgn=; blu=; std= DISTFILES = $(DIST_COMMON) $(DIST_SOURCES) $(TEXINFOS) $(EXTRA_DIST) ACLOCAL = @ACLOCAL@ AMTAR = @AMTAR@ @@ -143,6 +414,7 @@ AUTOHEADER = @AUTOHEADER@ AUTOMAKE = @AUTOMAKE@ AWK = @AWK@ CC = @CC@ +@WITH_LL_TRUE@CC = mpcc CCDEPMODE = @CCDEPMODE@ CFLAGS = @CFLAGS@ CPP = @CPP@ @@ -167,6 +439,10 @@ EXEEXT = @EXEEXT@ EXT_LIBS = @EXT_LIBS@ EXT_LIB_PATH = @EXT_LIB_PATH@ FGREP = @FGREP@ +GLIB_CFLAGS = @GLIB_CFLAGS@ +GLIB_GENMARSHAL = @GLIB_GENMARSHAL@ +GLIB_LIBS = @GLIB_LIBS@ +GLIB_MKENUMS = @GLIB_MKENUMS@ GMSGFMT = @GMSGFMT@ GMSGFMT_015 = @GMSGFMT_015@ GNUNETDNS_GROUP = @GNUNETDNS_GROUP@ @@ -177,6 +453,7 @@ GN_LIBINTL = @GN_LIBINTL@ GN_LIB_LDFLAGS = @GN_LIB_LDFLAGS@ GN_PLUGIN_LDFLAGS = @GN_PLUGIN_LDFLAGS@ GN_USER_HOME_DIR = @GN_USER_HOME_DIR@ +GOBJECT_QUERY = @GOBJECT_QUERY@ GREP = @GREP@ HAVE_LIBUNISTRING = @HAVE_LIBUNISTRING@ INCLTDL = @INCLTDL@ @@ -199,6 +476,8 @@ LIBCURL_CPPFLAGS = @LIBCURL_CPPFLAGS@ LIBGCRYPT_CFLAGS = @LIBGCRYPT_CFLAGS@ LIBGCRYPT_CONFIG = @LIBGCRYPT_CONFIG@ LIBGCRYPT_LIBS = @LIBGCRYPT_LIBS@ +LIBGTOP_CFLAGS = @LIBGTOP_CFLAGS@ +LIBGTOP_LIBS = @LIBGTOP_LIBS@ LIBICONV = @LIBICONV@ LIBINTL = @LIBINTL@ LIBLTDL = @LIBLTDL@ @@ -220,6 +499,7 @@ LT_CONFIG_H = @LT_CONFIG_H@ LT_DLLOADERS = @LT_DLLOADERS@ LT_DLPREOPEN = @LT_DLPREOPEN@ MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ MKDIR_P = @MKDIR_P@ MONKEYPREFIX = @MONKEYPREFIX@ MSGFMT = @MSGFMT@ @@ -229,6 +509,7 @@ MYSQL_CPPFLAGS = @MYSQL_CPPFLAGS@ MYSQL_LDFLAGS = @MYSQL_LDFLAGS@ NM = @NM@ NMEDIT = @NMEDIT@ +NSS_DIR = @NSS_DIR@ OBJC = @OBJC@ OBJCDEPMODE = @OBJCDEPMODE@ OBJCFLAGS = @OBJCFLAGS@ @@ -244,6 +525,7 @@ PACKAGE_TARNAME = @PACKAGE_TARNAME@ PACKAGE_URL = @PACKAGE_URL@ PACKAGE_VERSION = @PACKAGE_VERSION@ PATH_SEPARATOR = @PATH_SEPARATOR@ +PKG_CONFIG = @PKG_CONFIG@ POSTGRES_CPPFLAGS = @POSTGRES_CPPFLAGS@ POSTGRES_LDFLAGS = @POSTGRES_LDFLAGS@ POSUB = @POSUB@ @@ -275,6 +557,7 @@ abs_builddir = @abs_builddir@ abs_srcdir = @abs_srcdir@ abs_top_builddir = @abs_top_builddir@ abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ ac_ct_CC = @ac_ct_CC@ ac_ct_CXX = @ac_ct_CXX@ ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ @@ -297,6 +580,7 @@ datarootdir = @datarootdir@ docdir = @docdir@ dvidir = @dvidir@ exec_prefix = @exec_prefix@ +gitcommand = @gitcommand@ host = @host@ host_alias = @host_alias@ host_cpu = @host_cpu@ @@ -307,10 +591,9 @@ includedir = @includedir@ infodir = @infodir@ install_sh = @install_sh@ libdir = @libdir@ -libexecdir = @libexecdir@ +libexecdir = $(pkglibdir)/libexec/ localedir = @localedir@ localstatedir = @localstatedir@ -lt_ECHO = @lt_ECHO@ ltdl_LIBOBJS = @ltdl_LIBOBJS@ ltdl_LTLIBOBJS = @ltdl_LTLIBOBJS@ mandir = @mandir@ @@ -328,6 +611,7 @@ sbindir = @sbindir@ sharedstatedir = @sharedstatedir@ srcdir = @srcdir@ subdirs = @subdirs@ +svnversioncommand = @svnversioncommand@ sys_symbol_underscore = @sys_symbol_underscore@ sysconfdir = @sysconfdir@ target = @target@ @@ -342,22 +626,85 @@ INCLUDES = -I$(top_srcdir)/src/include @MINGW_TRUE@WINFLAGS = -Wl,--no-undefined -Wl,--export-all-symbols @USE_COVERAGE_TRUE@AM_CFLAGS = --coverage -O0 @USE_COVERAGE_TRUE@XLIB = -lgcov +@WITH_LL_TRUE@ll_noinst_binaries = \ +@WITH_LL_TRUE@ ll-master \ +@WITH_LL_TRUE@ ll-monitor + +@WITH_LL_TRUE@ll_binaries = \ +@WITH_LL_TRUE@ gnunet-mpi-test + pkgcfgdir = $(pkgdatadir)/config.d/ -dist_pkgcfg_DATA = \ +pkgcfg_DATA = \ testbed.conf +gnunet_service_testbed_SOURCES = \ + gnunet-service-testbed.c \ + gnunet-service-testbed.h \ + gnunet-service-testbed_cache.c \ + gnunet-service-testbed_oc.c + +gnunet_service_testbed_LDADD = $(XLIB) \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/core/libgnunetcore.la \ + $(top_builddir)/src/hello/libgnunethello.la \ + $(top_builddir)/src/transport/libgnunettransport.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la \ + $(LTLIBINTL) -lz + +gnunet_service_testbed_DEPENDENCIES = \ + libgnunettestbed.la + +gnunet_testbed_profiler_SOURCES = \ + gnunet-testbed-profiler.c + +gnunet_testbed_profiler_LDADD = $(XLIB) \ + $(top_builddir)/src/util/libgnunetutil.la \ + libgnunettestbed.la + +gnunet_helper_testbed_SOURCES = \ + gnunet-helper-testbed.c + +gnunet_helper_testbed_LDADD = $(XLIB) \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + libgnunettestbed.la \ + $(LTLIBINTL) -lz + +gnunet_helper_testbed_DEPENDENCIES = \ + gnunet-service-testbed.$(OBJEXT) \ + libgnunettestbed.la + +ll_master_SOURCES = \ + ll_master.c + +ll_master_LDADD = $(XLIB) \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(LTLIBINTL) -lz -lllapi + +ll_monitor_SOURCES = \ + ll_monitor.c + +ll_monitor_LDADD = $(XLIB) \ + $(LTLIBINTL) -lz -lllapi + +gnunet_mpi_test_SOURCES = gnunet_mpi_test.c +gnunet_mpi_test_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la + lib_LTLIBRARIES = \ libgnunettestbed.la libgnunettestbed_la_SOURCES = \ - testbed_api.c testbed.h \ - testbed_api_hosts.c testbed_api_hosts.h \ + testbed_api.c testbed_api.h testbed.h \ + testbed_api_hosts.c testbed_api_hosts.h testbed_helper.h \ testbed_api_operations.c testbed_api_operations.h \ testbed_api_peers.c testbed_api_peers.h \ testbed_api_services.c \ + testbed_api_statistics.c \ testbed_api_testbed.c \ testbed_api_test.c \ - testbed_api_topology.c + testbed_api_topology.c testbed_api_topology.h libgnunettestbed_la_LIBADD = $(XLIB) \ $(top_builddir)/src/core/libgnunetcore.la \ @@ -365,12 +712,174 @@ libgnunettestbed_la_LIBADD = $(XLIB) \ $(top_builddir)/src/transport/libgnunettransport.la \ $(top_builddir)/src/hello/libgnunethello.la \ -lm \ - $(top_builddir)/src/util/libgnunetutil.la + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(LTLIBINTL) libgnunettestbed_la_LDFLAGS = \ $(GN_LIB_LDFLAGS) \ -version-info 0:0:0 +test_testbed_api_hosts_SOURCES = \ + test_testbed_api_hosts.c + +test_testbed_api_hosts_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + libgnunettestbed.la + +test_testbed_api_SOURCES = \ + test_testbed_api.c + +test_testbed_api_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/dht/libgnunetdht.la \ + libgnunettestbed.la + +test_testbed_api_2peers_1controller_SOURCES = \ + test_testbed_api_2peers_1controller.c + +test_testbed_api_2peers_1controller_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + libgnunettestbed.la + +test_testbed_api_3peers_3controllers_SOURCES = \ + test_testbed_api_3peers_3controllers.c + +test_testbed_api_3peers_3controllers_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + libgnunettestbed.la + +test_testbed_api_operations_SOURCES = \ + test_testbed_api_operations.c + +test_testbed_api_operations_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + libgnunettestbed.la + +test_testbed_api_controllerlink_SOURCES = \ + test_testbed_api_controllerlink.c + +test_testbed_api_controllerlink_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + libgnunettestbed.la + +test_testbed_api_testbed_run_SOURCES = \ + test_testbed_api_testbed_run.c + +test_testbed_api_testbed_run_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + libgnunettestbed.la + +test_testbed_api_test_SOURCES = \ + test_testbed_api_test.c + +test_testbed_api_test_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + libgnunettestbed.la + +test_testbed_api_topology_SOURCES = \ + test_testbed_api_topology.c + +test_testbed_api_topology_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + libgnunettestbed.la + +test_testbed_api_topology_clique_SOURCES = \ + test_testbed_api_topology_clique.c + +test_testbed_api_topology_clique_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + libgnunettestbed.la + +test_gnunet_helper_testbed_SOURCES = \ + test_gnunet_helper_testbed.c + +test_gnunet_helper_testbed_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + libgnunettestbed.la \ + -lz + +test_testbed_api_testbed_run_topologyrandom_SOURCES = \ + test_testbed_api_testbed_run.c + +test_testbed_api_testbed_run_topologyrandom_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + libgnunettestbed.la + +test_testbed_api_testbed_run_topologyline_SOURCES = \ + test_testbed_api_testbed_run.c + +test_testbed_api_testbed_run_topologyline_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + libgnunettestbed.la + +test_testbed_api_testbed_run_topologyclique_SOURCES = \ + test_testbed_api_testbed_run.c + +test_testbed_api_testbed_run_topologyclique_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + libgnunettestbed.la + +test_testbed_api_testbed_run_topologyring_SOURCES = \ + test_testbed_api_testbed_run.c + +test_testbed_api_testbed_run_topologyring_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + libgnunettestbed.la + +test_testbed_api_testbed_run_topologysmallworldring_SOURCES = \ + test_testbed_api_testbed_run.c + +test_testbed_api_testbed_run_topologysmallworldring_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + libgnunettestbed.la + +test_testbed_api_testbed_run_topology2dtorus_SOURCES = \ + test_testbed_api_testbed_run.c + +test_testbed_api_testbed_run_topology2dtorus_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + libgnunettestbed.la + +test_testbed_api_testbed_run_topologysmallworld_SOURCES = \ + test_testbed_api_testbed_run.c + +test_testbed_api_testbed_run_topologysmallworld_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + libgnunettestbed.la + +test_testbed_api_testbed_run_topologyfromfile_SOURCES = \ + test_testbed_api_testbed_run.c + +test_testbed_api_testbed_run_topologyfromfile_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + libgnunettestbed.la + +test_testbed_api_testbed_run_topologyscalefree_SOURCES = \ + test_testbed_api_testbed_run.c + +test_testbed_api_testbed_run_topologyscalefree_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + libgnunettestbed.la + +EXTRA_DIST = \ + test_testbed_api.conf \ + test_testbed_api_testbed_run_topologyring.conf \ + test_testbed_api_testbed_run_topologyclique.conf \ + test_testbed_api_testbed_run_topologyline.conf \ + test_testbed_api_testbed_run_topologyrandom.conf \ + test_testbed_api_testbed_run_topologysmallworldring.conf \ + test_testbed_api_testbed_run_topology2dtorus.conf \ + test_testbed_api_testbed_run_topologysmallworld.conf \ + test_testbed_api_testbed_run_topologyfromfile.conf \ + test_testbed_api_testbed_run_topologyscalefree.conf \ + overlay_topology.txt \ + sample_hosts.txt \ + sample.job + all: all-am .SUFFIXES: @@ -405,9 +914,10 @@ $(top_srcdir)/configure: $(am__configure_deps) $(ACLOCAL_M4): $(am__aclocal_m4_deps) cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh $(am__aclocal_m4_deps): +testbed.conf: $(top_builddir)/config.status $(srcdir)/testbed.conf.in + cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ install-libLTLIBRARIES: $(lib_LTLIBRARIES) @$(NORMAL_INSTALL) - test -z "$(libdir)" || $(MKDIR_P) "$(DESTDIR)$(libdir)" @list='$(lib_LTLIBRARIES)'; test -n "$(libdir)" || list=; \ list2=; for p in $$list; do \ if test -f $$p; then \ @@ -415,6 +925,8 @@ install-libLTLIBRARIES: $(lib_LTLIBRARIES) else :; fi; \ done; \ test -z "$$list2" || { \ + echo " $(MKDIR_P) '$(DESTDIR)$(libdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libdir)" || exit 1; \ echo " $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 '$(DESTDIR)$(libdir)'"; \ $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 "$(DESTDIR)$(libdir)"; \ } @@ -436,8 +948,196 @@ clean-libLTLIBRARIES: echo "rm -f \"$${dir}/so_locations\""; \ rm -f "$${dir}/so_locations"; \ done -libgnunettestbed.la: $(libgnunettestbed_la_OBJECTS) $(libgnunettestbed_la_DEPENDENCIES) +libgnunettestbed.la: $(libgnunettestbed_la_OBJECTS) $(libgnunettestbed_la_DEPENDENCIES) $(EXTRA_libgnunettestbed_la_DEPENDENCIES) $(AM_V_CCLD)$(libgnunettestbed_la_LINK) -rpath $(libdir) $(libgnunettestbed_la_OBJECTS) $(libgnunettestbed_la_LIBADD) $(LIBS) +install-binPROGRAMS: $(bin_PROGRAMS) + @$(NORMAL_INSTALL) + @list='$(bin_PROGRAMS)'; test -n "$(bindir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(bindir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(bindir)" || exit 1; \ + fi; \ + for p in $$list; do echo "$$p $$p"; done | \ + sed 's/$(EXEEXT)$$//' | \ + while read p p1; do if test -f $$p || test -f $$p1; \ + then echo "$$p"; echo "$$p"; else :; fi; \ + done | \ + sed -e 'p;s,.*/,,;n;h' -e 's|.*|.|' \ + -e 'p;x;s,.*/,,;s/$(EXEEXT)$$//;$(transform);s/$$/$(EXEEXT)/' | \ + sed 'N;N;N;s,\n, ,g' | \ + $(AWK) 'BEGIN { files["."] = ""; dirs["."] = 1 } \ + { d=$$3; if (dirs[d] != 1) { print "d", d; dirs[d] = 1 } \ + if ($$2 == $$4) files[d] = files[d] " " $$1; \ + else { print "f", $$3 "/" $$4, $$1; } } \ + END { for (d in files) print "f", d, files[d] }' | \ + while read type dir files; do \ + if test "$$dir" = .; then dir=; else dir=/$$dir; fi; \ + test -z "$$files" || { \ + echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files '$(DESTDIR)$(bindir)$$dir'"; \ + $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files "$(DESTDIR)$(bindir)$$dir" || exit $$?; \ + } \ + ; done + +uninstall-binPROGRAMS: + @$(NORMAL_UNINSTALL) + @list='$(bin_PROGRAMS)'; test -n "$(bindir)" || list=; \ + files=`for p in $$list; do echo "$$p"; done | \ + sed -e 'h;s,^.*/,,;s/$(EXEEXT)$$//;$(transform)' \ + -e 's/$$/$(EXEEXT)/' `; \ + test -n "$$list" || exit 0; \ + echo " ( cd '$(DESTDIR)$(bindir)' && rm -f" $$files ")"; \ + cd "$(DESTDIR)$(bindir)" && rm -f $$files + +clean-binPROGRAMS: + @list='$(bin_PROGRAMS)'; test -n "$$list" || exit 0; \ + echo " rm -f" $$list; \ + rm -f $$list || exit $$?; \ + test -n "$(EXEEXT)" || exit 0; \ + list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ + echo " rm -f" $$list; \ + rm -f $$list + +clean-checkPROGRAMS: + @list='$(check_PROGRAMS)'; test -n "$$list" || exit 0; \ + echo " rm -f" $$list; \ + rm -f $$list || exit $$?; \ + test -n "$(EXEEXT)" || exit 0; \ + list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ + echo " rm -f" $$list; \ + rm -f $$list +install-libexecPROGRAMS: $(libexec_PROGRAMS) + @$(NORMAL_INSTALL) + @list='$(libexec_PROGRAMS)'; test -n "$(libexecdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(libexecdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libexecdir)" || exit 1; \ + fi; \ + for p in $$list; do echo "$$p $$p"; done | \ + sed 's/$(EXEEXT)$$//' | \ + while read p p1; do if test -f $$p || test -f $$p1; \ + then echo "$$p"; echo "$$p"; else :; fi; \ + done | \ + sed -e 'p;s,.*/,,;n;h' -e 's|.*|.|' \ + -e 'p;x;s,.*/,,;s/$(EXEEXT)$$//;$(transform);s/$$/$(EXEEXT)/' | \ + sed 'N;N;N;s,\n, ,g' | \ + $(AWK) 'BEGIN { files["."] = ""; dirs["."] = 1 } \ + { d=$$3; if (dirs[d] != 1) { print "d", d; dirs[d] = 1 } \ + if ($$2 == $$4) files[d] = files[d] " " $$1; \ + else { print "f", $$3 "/" $$4, $$1; } } \ + END { for (d in files) print "f", d, files[d] }' | \ + while read type dir files; do \ + if test "$$dir" = .; then dir=; else dir=/$$dir; fi; \ + test -z "$$files" || { \ + echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files '$(DESTDIR)$(libexecdir)$$dir'"; \ + $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files "$(DESTDIR)$(libexecdir)$$dir" || exit $$?; \ + } \ + ; done + +uninstall-libexecPROGRAMS: + @$(NORMAL_UNINSTALL) + @list='$(libexec_PROGRAMS)'; test -n "$(libexecdir)" || list=; \ + files=`for p in $$list; do echo "$$p"; done | \ + sed -e 'h;s,^.*/,,;s/$(EXEEXT)$$//;$(transform)' \ + -e 's/$$/$(EXEEXT)/' `; \ + test -n "$$list" || exit 0; \ + echo " ( cd '$(DESTDIR)$(libexecdir)' && rm -f" $$files ")"; \ + cd "$(DESTDIR)$(libexecdir)" && rm -f $$files + +clean-libexecPROGRAMS: + @list='$(libexec_PROGRAMS)'; test -n "$$list" || exit 0; \ + echo " rm -f" $$list; \ + rm -f $$list || exit $$?; \ + test -n "$(EXEEXT)" || exit 0; \ + list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ + echo " rm -f" $$list; \ + rm -f $$list + +clean-noinstPROGRAMS: + @list='$(noinst_PROGRAMS)'; test -n "$$list" || exit 0; \ + echo " rm -f" $$list; \ + rm -f $$list || exit $$?; \ + test -n "$(EXEEXT)" || exit 0; \ + list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ + echo " rm -f" $$list; \ + rm -f $$list +gnunet-helper-testbed$(EXEEXT): $(gnunet_helper_testbed_OBJECTS) $(gnunet_helper_testbed_DEPENDENCIES) $(EXTRA_gnunet_helper_testbed_DEPENDENCIES) + @rm -f gnunet-helper-testbed$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(gnunet_helper_testbed_OBJECTS) $(gnunet_helper_testbed_LDADD) $(LIBS) +gnunet-mpi-test$(EXEEXT): $(gnunet_mpi_test_OBJECTS) $(gnunet_mpi_test_DEPENDENCIES) $(EXTRA_gnunet_mpi_test_DEPENDENCIES) + @rm -f gnunet-mpi-test$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(gnunet_mpi_test_OBJECTS) $(gnunet_mpi_test_LDADD) $(LIBS) +gnunet-service-testbed$(EXEEXT): $(gnunet_service_testbed_OBJECTS) $(gnunet_service_testbed_DEPENDENCIES) $(EXTRA_gnunet_service_testbed_DEPENDENCIES) + @rm -f gnunet-service-testbed$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(gnunet_service_testbed_OBJECTS) $(gnunet_service_testbed_LDADD) $(LIBS) +gnunet-testbed-profiler$(EXEEXT): $(gnunet_testbed_profiler_OBJECTS) $(gnunet_testbed_profiler_DEPENDENCIES) $(EXTRA_gnunet_testbed_profiler_DEPENDENCIES) + @rm -f gnunet-testbed-profiler$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(gnunet_testbed_profiler_OBJECTS) $(gnunet_testbed_profiler_LDADD) $(LIBS) +ll-master$(EXEEXT): $(ll_master_OBJECTS) $(ll_master_DEPENDENCIES) $(EXTRA_ll_master_DEPENDENCIES) + @rm -f ll-master$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(ll_master_OBJECTS) $(ll_master_LDADD) $(LIBS) +ll-monitor$(EXEEXT): $(ll_monitor_OBJECTS) $(ll_monitor_DEPENDENCIES) $(EXTRA_ll_monitor_DEPENDENCIES) + @rm -f ll-monitor$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(ll_monitor_OBJECTS) $(ll_monitor_LDADD) $(LIBS) +test_gnunet_helper_testbed$(EXEEXT): $(test_gnunet_helper_testbed_OBJECTS) $(test_gnunet_helper_testbed_DEPENDENCIES) $(EXTRA_test_gnunet_helper_testbed_DEPENDENCIES) + @rm -f test_gnunet_helper_testbed$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_gnunet_helper_testbed_OBJECTS) $(test_gnunet_helper_testbed_LDADD) $(LIBS) +test_testbed_api$(EXEEXT): $(test_testbed_api_OBJECTS) $(test_testbed_api_DEPENDENCIES) $(EXTRA_test_testbed_api_DEPENDENCIES) + @rm -f test_testbed_api$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_testbed_api_OBJECTS) $(test_testbed_api_LDADD) $(LIBS) +test_testbed_api_2peers_1controller$(EXEEXT): $(test_testbed_api_2peers_1controller_OBJECTS) $(test_testbed_api_2peers_1controller_DEPENDENCIES) $(EXTRA_test_testbed_api_2peers_1controller_DEPENDENCIES) + @rm -f test_testbed_api_2peers_1controller$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_testbed_api_2peers_1controller_OBJECTS) $(test_testbed_api_2peers_1controller_LDADD) $(LIBS) +test_testbed_api_3peers_3controllers$(EXEEXT): $(test_testbed_api_3peers_3controllers_OBJECTS) $(test_testbed_api_3peers_3controllers_DEPENDENCIES) $(EXTRA_test_testbed_api_3peers_3controllers_DEPENDENCIES) + @rm -f test_testbed_api_3peers_3controllers$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_testbed_api_3peers_3controllers_OBJECTS) $(test_testbed_api_3peers_3controllers_LDADD) $(LIBS) +test_testbed_api_controllerlink$(EXEEXT): $(test_testbed_api_controllerlink_OBJECTS) $(test_testbed_api_controllerlink_DEPENDENCIES) $(EXTRA_test_testbed_api_controllerlink_DEPENDENCIES) + @rm -f test_testbed_api_controllerlink$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_testbed_api_controllerlink_OBJECTS) $(test_testbed_api_controllerlink_LDADD) $(LIBS) +test_testbed_api_hosts$(EXEEXT): $(test_testbed_api_hosts_OBJECTS) $(test_testbed_api_hosts_DEPENDENCIES) $(EXTRA_test_testbed_api_hosts_DEPENDENCIES) + @rm -f test_testbed_api_hosts$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_testbed_api_hosts_OBJECTS) $(test_testbed_api_hosts_LDADD) $(LIBS) +test_testbed_api_operations$(EXEEXT): $(test_testbed_api_operations_OBJECTS) $(test_testbed_api_operations_DEPENDENCIES) $(EXTRA_test_testbed_api_operations_DEPENDENCIES) + @rm -f test_testbed_api_operations$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_testbed_api_operations_OBJECTS) $(test_testbed_api_operations_LDADD) $(LIBS) +test_testbed_api_test$(EXEEXT): $(test_testbed_api_test_OBJECTS) $(test_testbed_api_test_DEPENDENCIES) $(EXTRA_test_testbed_api_test_DEPENDENCIES) + @rm -f test_testbed_api_test$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_testbed_api_test_OBJECTS) $(test_testbed_api_test_LDADD) $(LIBS) +test_testbed_api_testbed_run$(EXEEXT): $(test_testbed_api_testbed_run_OBJECTS) $(test_testbed_api_testbed_run_DEPENDENCIES) $(EXTRA_test_testbed_api_testbed_run_DEPENDENCIES) + @rm -f test_testbed_api_testbed_run$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_testbed_api_testbed_run_OBJECTS) $(test_testbed_api_testbed_run_LDADD) $(LIBS) +test_testbed_api_testbed_run_topology2dtorus$(EXEEXT): $(test_testbed_api_testbed_run_topology2dtorus_OBJECTS) $(test_testbed_api_testbed_run_topology2dtorus_DEPENDENCIES) $(EXTRA_test_testbed_api_testbed_run_topology2dtorus_DEPENDENCIES) + @rm -f test_testbed_api_testbed_run_topology2dtorus$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_testbed_api_testbed_run_topology2dtorus_OBJECTS) $(test_testbed_api_testbed_run_topology2dtorus_LDADD) $(LIBS) +test_testbed_api_testbed_run_topologyclique$(EXEEXT): $(test_testbed_api_testbed_run_topologyclique_OBJECTS) $(test_testbed_api_testbed_run_topologyclique_DEPENDENCIES) $(EXTRA_test_testbed_api_testbed_run_topologyclique_DEPENDENCIES) + @rm -f test_testbed_api_testbed_run_topologyclique$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_testbed_api_testbed_run_topologyclique_OBJECTS) $(test_testbed_api_testbed_run_topologyclique_LDADD) $(LIBS) +test_testbed_api_testbed_run_topologyfromfile$(EXEEXT): $(test_testbed_api_testbed_run_topologyfromfile_OBJECTS) $(test_testbed_api_testbed_run_topologyfromfile_DEPENDENCIES) $(EXTRA_test_testbed_api_testbed_run_topologyfromfile_DEPENDENCIES) + @rm -f test_testbed_api_testbed_run_topologyfromfile$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_testbed_api_testbed_run_topologyfromfile_OBJECTS) $(test_testbed_api_testbed_run_topologyfromfile_LDADD) $(LIBS) +test_testbed_api_testbed_run_topologyline$(EXEEXT): $(test_testbed_api_testbed_run_topologyline_OBJECTS) $(test_testbed_api_testbed_run_topologyline_DEPENDENCIES) $(EXTRA_test_testbed_api_testbed_run_topologyline_DEPENDENCIES) + @rm -f test_testbed_api_testbed_run_topologyline$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_testbed_api_testbed_run_topologyline_OBJECTS) $(test_testbed_api_testbed_run_topologyline_LDADD) $(LIBS) +test_testbed_api_testbed_run_topologyrandom$(EXEEXT): $(test_testbed_api_testbed_run_topologyrandom_OBJECTS) $(test_testbed_api_testbed_run_topologyrandom_DEPENDENCIES) $(EXTRA_test_testbed_api_testbed_run_topologyrandom_DEPENDENCIES) + @rm -f test_testbed_api_testbed_run_topologyrandom$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_testbed_api_testbed_run_topologyrandom_OBJECTS) $(test_testbed_api_testbed_run_topologyrandom_LDADD) $(LIBS) +test_testbed_api_testbed_run_topologyring$(EXEEXT): $(test_testbed_api_testbed_run_topologyring_OBJECTS) $(test_testbed_api_testbed_run_topologyring_DEPENDENCIES) $(EXTRA_test_testbed_api_testbed_run_topologyring_DEPENDENCIES) + @rm -f test_testbed_api_testbed_run_topologyring$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_testbed_api_testbed_run_topologyring_OBJECTS) $(test_testbed_api_testbed_run_topologyring_LDADD) $(LIBS) +test_testbed_api_testbed_run_topologyscalefree$(EXEEXT): $(test_testbed_api_testbed_run_topologyscalefree_OBJECTS) $(test_testbed_api_testbed_run_topologyscalefree_DEPENDENCIES) $(EXTRA_test_testbed_api_testbed_run_topologyscalefree_DEPENDENCIES) + @rm -f test_testbed_api_testbed_run_topologyscalefree$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_testbed_api_testbed_run_topologyscalefree_OBJECTS) $(test_testbed_api_testbed_run_topologyscalefree_LDADD) $(LIBS) +test_testbed_api_testbed_run_topologysmallworld$(EXEEXT): $(test_testbed_api_testbed_run_topologysmallworld_OBJECTS) $(test_testbed_api_testbed_run_topologysmallworld_DEPENDENCIES) $(EXTRA_test_testbed_api_testbed_run_topologysmallworld_DEPENDENCIES) + @rm -f test_testbed_api_testbed_run_topologysmallworld$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_testbed_api_testbed_run_topologysmallworld_OBJECTS) $(test_testbed_api_testbed_run_topologysmallworld_LDADD) $(LIBS) +test_testbed_api_testbed_run_topologysmallworldring$(EXEEXT): $(test_testbed_api_testbed_run_topologysmallworldring_OBJECTS) $(test_testbed_api_testbed_run_topologysmallworldring_DEPENDENCIES) $(EXTRA_test_testbed_api_testbed_run_topologysmallworldring_DEPENDENCIES) + @rm -f test_testbed_api_testbed_run_topologysmallworldring$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_testbed_api_testbed_run_topologysmallworldring_OBJECTS) $(test_testbed_api_testbed_run_topologysmallworldring_LDADD) $(LIBS) +test_testbed_api_topology$(EXEEXT): $(test_testbed_api_topology_OBJECTS) $(test_testbed_api_topology_DEPENDENCIES) $(EXTRA_test_testbed_api_topology_DEPENDENCIES) + @rm -f test_testbed_api_topology$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_testbed_api_topology_OBJECTS) $(test_testbed_api_topology_LDADD) $(LIBS) +test_testbed_api_topology_clique$(EXEEXT): $(test_testbed_api_topology_clique_OBJECTS) $(test_testbed_api_topology_clique_DEPENDENCIES) $(EXTRA_test_testbed_api_topology_clique_DEPENDENCIES) + @rm -f test_testbed_api_topology_clique$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_testbed_api_topology_clique_OBJECTS) $(test_testbed_api_topology_clique_LDADD) $(LIBS) mostlyclean-compile: -rm -f *.$(OBJEXT) @@ -445,11 +1145,31 @@ mostlyclean-compile: distclean-compile: -rm -f *.tab.c +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-helper-testbed.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-service-testbed.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-service-testbed_cache.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-service-testbed_oc.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-testbed-profiler.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet_mpi_test.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/ll_master.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/ll_monitor.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_gnunet_helper_testbed.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_testbed_api.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_testbed_api_2peers_1controller.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_testbed_api_3peers_3controllers.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_testbed_api_controllerlink.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_testbed_api_hosts.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_testbed_api_operations.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_testbed_api_test.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_testbed_api_testbed_run.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_testbed_api_topology.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_testbed_api_topology_clique.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/testbed_api.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/testbed_api_hosts.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/testbed_api_operations.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/testbed_api_peers.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/testbed_api_services.Plo@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/testbed_api_statistics.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/testbed_api_test.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/testbed_api_testbed.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/testbed_api_topology.Plo@am__quote@ @@ -457,36 +1177,36 @@ distclean-compile: .c.o: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c $< .c.obj: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'` @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c `$(CYGPATH_W) '$<'` +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c `$(CYGPATH_W) '$<'` .c.lo: @am__fastdepCC_TRUE@ $(AM_V_CC)$(LTCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LTCOMPILE) -c -o $@ $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LTCOMPILE) -c -o $@ $< mostlyclean-libtool: -rm -f *.lo clean-libtool: -rm -rf .libs _libs -install-dist_pkgcfgDATA: $(dist_pkgcfg_DATA) +install-pkgcfgDATA: $(pkgcfg_DATA) @$(NORMAL_INSTALL) - test -z "$(pkgcfgdir)" || $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" - @list='$(dist_pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ + @list='$(pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(pkgcfgdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" || exit 1; \ + fi; \ for p in $$list; do \ if test -f "$$p"; then d=; else d="$(srcdir)/"; fi; \ echo "$$d$$p"; \ @@ -496,13 +1216,11 @@ install-dist_pkgcfgDATA: $(dist_pkgcfg_DATA) $(INSTALL_DATA) $$files "$(DESTDIR)$(pkgcfgdir)" || exit $$?; \ done -uninstall-dist_pkgcfgDATA: +uninstall-pkgcfgDATA: @$(NORMAL_UNINSTALL) - @list='$(dist_pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ + @list='$(pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ files=`for p in $$list; do echo $$p; done | sed -e 's|^.*/||'`; \ - test -n "$$files" || exit 0; \ - echo " ( cd '$(DESTDIR)$(pkgcfgdir)' && rm -f" $$files ")"; \ - cd "$(DESTDIR)$(pkgcfgdir)" && rm -f $$files + dir='$(DESTDIR)$(pkgcfgdir)'; $(am__uninstall_files_from_dir) ID: $(HEADERS) $(SOURCES) $(LISP) $(TAGS_FILES) list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ @@ -556,6 +1274,99 @@ GTAGS: distclean-tags: -rm -f TAGS ID GTAGS GRTAGS GSYMS GPATH tags +check-TESTS: $(TESTS) + @failed=0; all=0; xfail=0; xpass=0; skip=0; \ + srcdir=$(srcdir); export srcdir; \ + list=' $(TESTS) '; \ + $(am__tty_colors); \ + if test -n "$$list"; then \ + for tst in $$list; do \ + if test -f ./$$tst; then dir=./; \ + elif test -f $$tst; then dir=; \ + else dir="$(srcdir)/"; fi; \ + if $(TESTS_ENVIRONMENT) $${dir}$$tst; then \ + all=`expr $$all + 1`; \ + case " $(XFAIL_TESTS) " in \ + *[\ \ ]$$tst[\ \ ]*) \ + xpass=`expr $$xpass + 1`; \ + failed=`expr $$failed + 1`; \ + col=$$red; res=XPASS; \ + ;; \ + *) \ + col=$$grn; res=PASS; \ + ;; \ + esac; \ + elif test $$? -ne 77; then \ + all=`expr $$all + 1`; \ + case " $(XFAIL_TESTS) " in \ + *[\ \ ]$$tst[\ \ ]*) \ + xfail=`expr $$xfail + 1`; \ + col=$$lgn; res=XFAIL; \ + ;; \ + *) \ + failed=`expr $$failed + 1`; \ + col=$$red; res=FAIL; \ + ;; \ + esac; \ + else \ + skip=`expr $$skip + 1`; \ + col=$$blu; res=SKIP; \ + fi; \ + echo "$${col}$$res$${std}: $$tst"; \ + done; \ + if test "$$all" -eq 1; then \ + tests="test"; \ + All=""; \ + else \ + tests="tests"; \ + All="All "; \ + fi; \ + if test "$$failed" -eq 0; then \ + if test "$$xfail" -eq 0; then \ + banner="$$All$$all $$tests passed"; \ + else \ + if test "$$xfail" -eq 1; then failures=failure; else failures=failures; fi; \ + banner="$$All$$all $$tests behaved as expected ($$xfail expected $$failures)"; \ + fi; \ + else \ + if test "$$xpass" -eq 0; then \ + banner="$$failed of $$all $$tests failed"; \ + else \ + if test "$$xpass" -eq 1; then passes=pass; else passes=passes; fi; \ + banner="$$failed of $$all $$tests did not behave as expected ($$xpass unexpected $$passes)"; \ + fi; \ + fi; \ + dashes="$$banner"; \ + skipped=""; \ + if test "$$skip" -ne 0; then \ + if test "$$skip" -eq 1; then \ + skipped="($$skip test was not run)"; \ + else \ + skipped="($$skip tests were not run)"; \ + fi; \ + test `echo "$$skipped" | wc -c` -le `echo "$$banner" | wc -c` || \ + dashes="$$skipped"; \ + fi; \ + report=""; \ + if test "$$failed" -ne 0 && test -n "$(PACKAGE_BUGREPORT)"; then \ + report="Please report to $(PACKAGE_BUGREPORT)"; \ + test `echo "$$report" | wc -c` -le `echo "$$banner" | wc -c` || \ + dashes="$$report"; \ + fi; \ + dashes=`echo "$$dashes" | sed s/./=/g`; \ + if test "$$failed" -eq 0; then \ + col="$$grn"; \ + else \ + col="$$red"; \ + fi; \ + echo "$${col}$$dashes$${std}"; \ + echo "$${col}$$banner$${std}"; \ + test -z "$$skipped" || echo "$${col}$$skipped$${std}"; \ + test -z "$$report" || echo "$${col}$$report$${std}"; \ + echo "$${col}$$dashes$${std}"; \ + test "$$failed" -eq 0; \ + else :; fi + distdir: $(DISTFILES) @srcdirstrip=`echo "$(srcdir)" | sed 's/[].[^$$\\*]/\\\\&/g'`; \ topsrcdirstrip=`echo "$(top_srcdir)" | sed 's/[].[^$$\\*]/\\\\&/g'`; \ @@ -587,10 +1398,14 @@ distdir: $(DISTFILES) fi; \ done check-am: all-am + $(MAKE) $(AM_MAKEFLAGS) $(check_PROGRAMS) + $(MAKE) $(AM_MAKEFLAGS) check-TESTS check: check-am -all-am: Makefile $(LTLIBRARIES) $(DATA) +all-am: Makefile $(LTLIBRARIES) $(PROGRAMS) $(DATA) +install-binPROGRAMS: install-libLTLIBRARIES + installdirs: - for dir in "$(DESTDIR)$(libdir)" "$(DESTDIR)$(pkgcfgdir)"; do \ + for dir in "$(DESTDIR)$(libdir)" "$(DESTDIR)$(bindir)" "$(DESTDIR)$(libexecdir)" "$(DESTDIR)$(pkgcfgdir)"; do \ test -z "$$dir" || $(MKDIR_P) "$$dir"; \ done install: install-am @@ -603,10 +1418,15 @@ install-am: all-am installcheck: installcheck-am install-strip: - $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ - install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ - `test -z '$(STRIP)' || \ - echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi mostlyclean-generic: clean-generic: @@ -620,8 +1440,9 @@ maintainer-clean-generic: @echo "it deletes files that may require special tools to rebuild." clean: clean-am -clean-am: clean-generic clean-libLTLIBRARIES clean-libtool \ - mostlyclean-am +clean-am: clean-binPROGRAMS clean-checkPROGRAMS clean-generic \ + clean-libLTLIBRARIES clean-libexecPROGRAMS clean-libtool \ + clean-noinstPROGRAMS mostlyclean-am distclean: distclean-am -rm -rf ./$(DEPDIR) @@ -641,13 +1462,14 @@ info: info-am info-am: -install-data-am: install-dist_pkgcfgDATA +install-data-am: install-pkgcfgDATA install-dvi: install-dvi-am install-dvi-am: -install-exec-am: install-libLTLIBRARIES +install-exec-am: install-binPROGRAMS install-libLTLIBRARIES \ + install-libexecPROGRAMS install-html: install-html-am @@ -687,25 +1509,28 @@ ps: ps-am ps-am: -uninstall-am: uninstall-dist_pkgcfgDATA uninstall-libLTLIBRARIES - -.MAKE: install-am install-strip - -.PHONY: CTAGS GTAGS all all-am check check-am clean clean-generic \ - clean-libLTLIBRARIES clean-libtool ctags distclean \ - distclean-compile distclean-generic distclean-libtool \ - distclean-tags distdir dvi dvi-am html html-am info info-am \ - install install-am install-data install-data-am \ - install-dist_pkgcfgDATA install-dvi install-dvi-am \ - install-exec install-exec-am install-html install-html-am \ - install-info install-info-am install-libLTLIBRARIES \ - install-man install-pdf install-pdf-am install-ps \ +uninstall-am: uninstall-binPROGRAMS uninstall-libLTLIBRARIES \ + uninstall-libexecPROGRAMS uninstall-pkgcfgDATA + +.MAKE: check-am install-am install-strip + +.PHONY: CTAGS GTAGS all all-am check check-TESTS check-am clean \ + clean-binPROGRAMS clean-checkPROGRAMS clean-generic \ + clean-libLTLIBRARIES clean-libexecPROGRAMS clean-libtool \ + clean-noinstPROGRAMS ctags distclean distclean-compile \ + distclean-generic distclean-libtool distclean-tags distdir dvi \ + dvi-am html html-am info info-am install install-am \ + install-binPROGRAMS install-data install-data-am install-dvi \ + install-dvi-am install-exec install-exec-am install-html \ + install-html-am install-info install-info-am \ + install-libLTLIBRARIES install-libexecPROGRAMS install-man \ + install-pdf install-pdf-am install-pkgcfgDATA install-ps \ install-ps-am install-strip installcheck installcheck-am \ installdirs maintainer-clean maintainer-clean-generic \ mostlyclean mostlyclean-compile mostlyclean-generic \ mostlyclean-libtool pdf pdf-am ps ps-am tags uninstall \ - uninstall-am uninstall-dist_pkgcfgDATA \ - uninstall-libLTLIBRARIES + uninstall-am uninstall-binPROGRAMS uninstall-libLTLIBRARIES \ + uninstall-libexecPROGRAMS uninstall-pkgcfgDATA # Tell versions [3.59,3.63) of GNU make to not export all variables. diff --git a/src/testbed/gnunet-helper-testbed.c b/src/testbed/gnunet-helper-testbed.c new file mode 100644 index 0000000..7d0bf87 --- /dev/null +++ b/src/testbed/gnunet-helper-testbed.c @@ -0,0 +1,489 @@ +/* + This file is part of GNUnet + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. + */ + +/** + * @file testbed/gnunet-helper-testbed.c + * @brief Helper binary that is started from a remote controller to start + * gnunet-service-testbed. This binary also receives configuration + * from the remove controller which is put in a temporary location + * with ports and paths fixed so that gnunet-service-testbed runs + * without any hurdles. This binary also kills the testbed service + * should the connection from the remote controller is dropped + * @author Sree Harsha Totakura + */ + + +#include "platform.h" +#include "gnunet_util_lib.h" +#include "gnunet_testing_lib.h" +#include "gnunet_testbed_service.h" +#include "testbed_helper.h" +#include "testbed_api.h" +#include + +/** + * Generic logging shortcut + */ +#define LOG(kind, ...) \ + GNUNET_log (kind, __VA_ARGS__) + +/** + * Debug logging shorthand + */ +#define LOG_DEBUG(...) \ + LOG (GNUNET_ERROR_TYPE_DEBUG, __VA_ARGS__) + + +/** + * We need pipe control only on WINDOWS + */ +#if WINDOWS +#define PIPE_CONTROL GNUNET_YES +#else +#define PIPE_CONTROL GNUNET_NO +#endif + + +/** + * Context for a single write on a chunk of memory + */ +struct WriteContext +{ + /** + * The data to write + */ + void *data; + + /** + * The length of the data + */ + size_t length; + + /** + * The current position from where the write operation should begin + */ + size_t pos; +}; + + +/** + * Handle to the testing system + */ +static struct GNUNET_TESTING_System *test_system; + +/** + * Our message stream tokenizer + */ +struct GNUNET_SERVER_MessageStreamTokenizer *tokenizer; + +/** + * Disk handle from stdin + */ +static struct GNUNET_DISK_FileHandle *stdin_fd; + +/** + * Disk handle for stdout + */ +static struct GNUNET_DISK_FileHandle *stdout_fd; + +/** + * The process handle to the testbed service + */ +static struct GNUNET_OS_Process *testbed; + +/** + * Task identifier for the read task + */ +static GNUNET_SCHEDULER_TaskIdentifier read_task_id; + +/** + * Task identifier for the write task + */ +static GNUNET_SCHEDULER_TaskIdentifier write_task_id; + +/** + * Are we done reading messages from stdin? + */ +static int done_reading; + +/** + * Result to return in case we fail + */ +static int status; + + +/** + * Are we shutting down + */ +static int in_shutdown; + + +/** + * Task to shutting down nicely + * + * @param cls NULL + * @param tc the task context + */ +static void +shutdown_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + LOG_DEBUG ("Shutting down\n"); + in_shutdown = GNUNET_YES; + if (GNUNET_SCHEDULER_NO_TASK != read_task_id) + { + GNUNET_SCHEDULER_cancel (read_task_id); + read_task_id = GNUNET_SCHEDULER_NO_TASK; + } + if (GNUNET_SCHEDULER_NO_TASK != write_task_id) + { + GNUNET_SCHEDULER_cancel (write_task_id); + write_task_id = GNUNET_SCHEDULER_NO_TASK; + } + if (NULL != stdin_fd) + (void) GNUNET_DISK_file_close (stdin_fd); + if (NULL != stdout_fd) + (void) GNUNET_DISK_file_close (stdout_fd); + GNUNET_SERVER_mst_destroy (tokenizer); + tokenizer = NULL; + if (NULL != testbed) + { + LOG_DEBUG ("Killing testbed\n"); + GNUNET_break (0 == GNUNET_OS_process_kill (testbed, SIGTERM)); + GNUNET_assert (GNUNET_OK == GNUNET_OS_process_wait (testbed)); + GNUNET_OS_process_destroy (testbed); + testbed = NULL; + } + if (NULL != test_system) + { + GNUNET_TESTING_system_destroy (test_system, GNUNET_YES); + test_system = NULL; + } +} + + +/** + * Task to write to the standard out + * + * @param cls the WriteContext + * @param tc the TaskContext + */ +static void +write_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct WriteContext *wc = cls; + ssize_t bytes_wrote; + + GNUNET_assert (NULL != wc); + write_task_id = GNUNET_SCHEDULER_NO_TASK; + if (0 != (GNUNET_SCHEDULER_REASON_SHUTDOWN & tc->reason)) + { + GNUNET_free (wc->data); + GNUNET_free (wc); + return; + } + bytes_wrote = + GNUNET_DISK_file_write (stdout_fd, wc->data + wc->pos, + wc->length - wc->pos); + if (GNUNET_SYSERR == bytes_wrote) + { + LOG (GNUNET_ERROR_TYPE_WARNING, "Cannot reply back configuration\n"); + GNUNET_free (wc->data); + GNUNET_free (wc); + return; + } + wc->pos += bytes_wrote; + if (wc->pos == wc->length) + { + GNUNET_free (wc->data); + GNUNET_free (wc); + return; + } + write_task_id = + GNUNET_SCHEDULER_add_write_file (GNUNET_TIME_UNIT_FOREVER_REL, stdout_fd, + &write_task, wc); +} + + +/** + * Functions with this signature are called whenever a + * complete message is received by the tokenizer. + * + * Do not call GNUNET_SERVER_mst_destroy in callback + * + * @param cls closure + * @param client identification of the client + * @param message the actual message + * + * @return GNUNET_OK on success, GNUNET_SYSERR to stop further processing + */ +static int +tokenizer_cb (void *cls, void *client, + const struct GNUNET_MessageHeader *message) +{ + const struct GNUNET_TESTBED_HelperInit *msg; + struct GNUNET_TESTBED_HelperReply *reply; + struct GNUNET_CONFIGURATION_Handle *cfg; + struct WriteContext *wc; + char *binary; + char *trusted_ip; + char *hostname; + char *config; + char *xconfig; + size_t config_size; + uLongf ul_config_size; + size_t xconfig_size; + uint16_t trusted_ip_size; + uint16_t hostname_size; + uint16_t msize; + + msize = ntohs (message->size); + if ((sizeof (struct GNUNET_TESTBED_HelperInit) >= msize) || + (GNUNET_MESSAGE_TYPE_TESTBED_HELPER_INIT != ntohs (message->type))) + { + LOG (GNUNET_ERROR_TYPE_WARNING, "Received unexpected message -- exiting\n"); + goto error; + } + msg = (const struct GNUNET_TESTBED_HelperInit *) message; + trusted_ip_size = ntohs (msg->trusted_ip_size); + trusted_ip = (char *) &msg[1]; + if ('\0' != trusted_ip[trusted_ip_size]) + { + LOG (GNUNET_ERROR_TYPE_WARNING, "Trusted IP cannot be empty -- exiting\n"); + goto error; + } + hostname_size = ntohs (msg->hostname_size); + if ((sizeof (struct GNUNET_TESTBED_HelperInit) + trusted_ip_size + 1 + + hostname_size) >= msize) + { + GNUNET_break (0); + LOG (GNUNET_ERROR_TYPE_WARNING, "Received unexpected message -- exiting\n"); + goto error; + } + ul_config_size = (uLongf) ntohs (msg->config_size); + config = GNUNET_malloc (ul_config_size); + xconfig_size = + ntohs (message->size) - (trusted_ip_size + 1 + + sizeof (struct GNUNET_TESTBED_HelperInit)); + if (Z_OK != + uncompress ((Bytef *) config, &ul_config_size, + (const Bytef *) (trusted_ip + trusted_ip_size + 1 + + hostname_size), (uLongf) xconfig_size)) + { + LOG (GNUNET_ERROR_TYPE_WARNING, + "Error while uncompressing config -- exiting\n"); + GNUNET_free (config); + goto error; + } + cfg = GNUNET_CONFIGURATION_create (); + if (GNUNET_OK != + GNUNET_CONFIGURATION_deserialize (cfg, config, ul_config_size, GNUNET_NO)) + { + LOG (GNUNET_ERROR_TYPE_WARNING, + "Unable to deserialize config -- exiting\n"); + GNUNET_free (config); + goto error; + } + GNUNET_free (config); + hostname = NULL; + if (0 != hostname_size) + { + hostname = GNUNET_malloc (hostname_size + 1); + (void) strncpy (hostname, ((char *) &msg[1]) + trusted_ip_size + 1, + hostname_size); + hostname[hostname_size] = '\0'; + } + test_system = + GNUNET_TESTING_system_create ("testbed-helper", trusted_ip, hostname); + GNUNET_free_non_null (hostname); + hostname = NULL; + GNUNET_assert (NULL != test_system); + GNUNET_assert (GNUNET_OK == + GNUNET_TESTING_configuration_create (test_system, cfg)); + GNUNET_assert (GNUNET_OK == + GNUNET_CONFIGURATION_get_value_string (cfg, "PATHS", + "DEFAULTCONFIG", + &config)); + if (GNUNET_OK != GNUNET_CONFIGURATION_write (cfg, config)) + { + LOG (GNUNET_ERROR_TYPE_WARNING, + "Unable to write config file: %s -- exiting\n", config); + GNUNET_CONFIGURATION_destroy (cfg); + GNUNET_free (config); + goto error; + } + LOG_DEBUG ("Staring testbed with config: %s\n", config); + binary = GNUNET_OS_get_libexec_binary_path ("gnunet-service-testbed"); + testbed = + GNUNET_OS_start_process (PIPE_CONTROL, + GNUNET_OS_INHERIT_STD_ERR /*verbose? */ , NULL, + NULL, binary, "gnunet-service-testbed", "-c", + config, NULL); + GNUNET_free (binary); + GNUNET_free (config); + if (NULL == testbed) + { + LOG (GNUNET_ERROR_TYPE_WARNING, + "Error starting gnunet-service-testbed -- exiting\n"); + GNUNET_CONFIGURATION_destroy (cfg); + goto error; + } + done_reading = GNUNET_YES; + config = GNUNET_CONFIGURATION_serialize (cfg, &config_size); + GNUNET_CONFIGURATION_destroy (cfg); + cfg = NULL; + xconfig_size = + GNUNET_TESTBED_compress_config_ (config, config_size, &xconfig); + GNUNET_free (config); + wc = GNUNET_malloc (sizeof (struct WriteContext)); + wc->length = xconfig_size + sizeof (struct GNUNET_TESTBED_HelperReply); + reply = GNUNET_realloc (xconfig, wc->length); + memmove (&reply[1], reply, xconfig_size); + reply->header.type = htons (GNUNET_MESSAGE_TYPE_TESTBED_HELPER_REPLY); + reply->header.size = htons ((uint16_t) wc->length); + reply->config_size = htons ((uint16_t) config_size); + wc->data = reply; + write_task_id = + GNUNET_SCHEDULER_add_write_file (GNUNET_TIME_UNIT_FOREVER_REL, stdout_fd, + &write_task, wc); + return GNUNET_OK; + +error: + status = GNUNET_SYSERR; + GNUNET_SCHEDULER_shutdown (); + return GNUNET_SYSERR; +} + + +/** + * Task to read from stdin + * + * @param cls NULL + * @param tc the task context + */ +static void +read_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + char buf[GNUNET_SERVER_MAX_MESSAGE_SIZE]; + ssize_t sread; + + read_task_id = GNUNET_SCHEDULER_NO_TASK; + if (0 != (GNUNET_SCHEDULER_REASON_SHUTDOWN & tc->reason)) + return; + sread = GNUNET_DISK_file_read (stdin_fd, buf, sizeof (buf)); + if ((GNUNET_SYSERR == sread) || (0 == sread)) + { + GNUNET_SCHEDULER_shutdown (); + return; + } + if (GNUNET_YES == done_reading) + { + /* didn't expect any more data! */ + GNUNET_SCHEDULER_shutdown (); + return; + } + LOG_DEBUG ("Read %u bytes\n", sread); + if (GNUNET_OK != + GNUNET_SERVER_mst_receive (tokenizer, NULL, buf, sread, GNUNET_NO, + GNUNET_NO)) + { + GNUNET_break (0); + GNUNET_SCHEDULER_shutdown (); + return; + } + read_task_id = /* No timeout while reading */ + GNUNET_SCHEDULER_add_read_file (GNUNET_TIME_UNIT_FOREVER_REL, stdin_fd, + &read_task, NULL); +} + + +/** + * Main function that will be run. + * + * @param cls closure + * @param args remaining command-line arguments + * @param cfgfile name of the configuration file used (for saving, can be NULL!) + * @param cfg configuration + */ +static void +run (void *cls, char *const *args, const char *cfgfile, + const struct GNUNET_CONFIGURATION_Handle *cfg) +{ + LOG_DEBUG ("Starting testbed helper...\n"); + tokenizer = GNUNET_SERVER_mst_create (&tokenizer_cb, NULL); + stdin_fd = GNUNET_DISK_get_handle_from_native (stdin); + stdout_fd = GNUNET_DISK_get_handle_from_native (stdout); + read_task_id = + GNUNET_SCHEDULER_add_read_file (GNUNET_TIME_UNIT_FOREVER_REL, stdin_fd, + &read_task, NULL); + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, &shutdown_task, + NULL); +} + + +/** + * Signal handler called for SIGCHLD. + */ +static void +sighandler_child_death () +{ + if ((NULL != testbed) && (GNUNET_NO == in_shutdown)) + { + LOG_DEBUG ("Child died\n"); + GNUNET_assert (GNUNET_OK == GNUNET_OS_process_wait (testbed)); + GNUNET_OS_process_destroy (testbed); + testbed = NULL; + GNUNET_SCHEDULER_shutdown (); /* We are done too! */ + } +} + + +/** + * Main function + * + * @param argc the number of command line arguments + * @param argv command line arg array + * @return return code + */ +int +main (int argc, char **argv) +{ + struct GNUNET_SIGNAL_Context *shc_chld; + + struct GNUNET_GETOPT_CommandLineOption options[] = { + GNUNET_GETOPT_OPTION_END + }; + int ret; + + status = GNUNET_OK; + in_shutdown = GNUNET_NO; + shc_chld = + GNUNET_SIGNAL_handler_install (GNUNET_SIGCHLD, &sighandler_child_death); + ret = + GNUNET_PROGRAM_run (argc, argv, "gnunet-helper-testbed", + "Helper for starting gnunet-service-testbed", options, + &run, NULL); + GNUNET_SIGNAL_handler_uninstall (shc_chld); + shc_chld = NULL; + if (GNUNET_OK != ret) + return 1; + return (GNUNET_OK == status) ? 0 : 1; +} + +/* end of gnunet-helper-testbed.c */ diff --git a/src/testbed/gnunet-service-testbed.c b/src/testbed/gnunet-service-testbed.c new file mode 100644 index 0000000..f1dc3fa --- /dev/null +++ b/src/testbed/gnunet-service-testbed.c @@ -0,0 +1,2227 @@ +/* + This file is part of GNUnet. + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 2, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @file testbed/gnunet-service-testbed.c + * @brief implementation of the TESTBED service + * @author Sree Harsha Totakura + */ + +#include "gnunet-service-testbed.h" + +#include + + +/***********/ +/* Globals */ +/***********/ + +/** + * Our configuration + */ +struct GNUNET_CONFIGURATION_Handle *our_config; + +/** + * The master context; generated with the first INIT message + */ +struct Context *GST_context; + +/** + * A list of directly linked neighbours + */ +struct Slave **GST_slave_list; + +/** + * A list of peers we know about + */ +struct Peer **GST_peer_list; + +/** + * Array of hosts + */ +struct GNUNET_TESTBED_Host **GST_host_list; + +/** + * DLL head for forwarded operation contexts + */ +struct ForwardedOperationContext *fopcq_head; + +/** + * DLL tail for forwarded operation contexts + */ +struct ForwardedOperationContext *fopcq_tail; + +/** + * Operation queue for open file descriptors + */ +struct OperationQueue *GST_opq_openfds; + +/** + * The size of the host list + */ +unsigned int GST_host_list_size; + +/** + * The size of directly linked neighbours list + */ +unsigned int GST_slave_list_size; + +/** + * The size of the peer list + */ +unsigned int GST_peer_list_size; + + +/***********************************/ +/* Local definitions and variables */ +/***********************************/ + +/** + * The message queue for sending messages to clients + */ +struct MessageQueue +{ + /** + * The message to be sent + */ + struct GNUNET_MessageHeader *msg; + + /** + * The client to send the message to + */ + struct GNUNET_SERVER_Client *client; + + /** + * next pointer for DLL + */ + struct MessageQueue *next; + + /** + * prev pointer for DLL + */ + struct MessageQueue *prev; +}; + +/** + * Our hostname; we give this to all the peers we start + */ +static char *hostname; + +/** + * Current Transmit Handle; NULL if no notify transmit exists currently + */ +static struct GNUNET_SERVER_TransmitHandle *transmit_handle; + +/** + * The head for the LCF queue + */ +static struct LCFContextQueue *lcfq_head; + +/** + * The tail for the LCF queue + */ +static struct LCFContextQueue *lcfq_tail; + +/** + * The message queue head + */ +static struct MessageQueue *mq_head; + +/** + * The message queue tail + */ +static struct MessageQueue *mq_tail; + +/** + * The hashmap of shared services + */ +static struct GNUNET_CONTAINER_MultiHashMap *ss_map; + +/** + * A list of routes + */ +static struct Route **route_list; + +/** + * The event mask for the events we listen from sub-controllers + */ +static uint64_t event_mask; + +/** + * The size of the route list + */ +static unsigned int route_list_size; + +/** + * The lcf_task handle + */ +static GNUNET_SCHEDULER_TaskIdentifier lcf_proc_task_id; + +/** + * The shutdown task handle + */ +static GNUNET_SCHEDULER_TaskIdentifier shutdown_task_id; + + +/** + * Function called to notify a client about the connection begin ready to queue + * more data. "buf" will be NULL and "size" zero if the connection was closed + * for writing in the meantime. + * + * @param cls NULL + * @param size number of bytes available in buf + * @param buf where the callee should write the message + * @return number of bytes written to buf + */ +static size_t +transmit_ready_notify (void *cls, size_t size, void *buf) +{ + struct MessageQueue *mq_entry; + + transmit_handle = NULL; + mq_entry = mq_head; + GNUNET_assert (NULL != mq_entry); + if (0 == size) + return 0; + GNUNET_assert (ntohs (mq_entry->msg->size) <= size); + size = ntohs (mq_entry->msg->size); + memcpy (buf, mq_entry->msg, size); + GNUNET_free (mq_entry->msg); + GNUNET_SERVER_client_drop (mq_entry->client); + GNUNET_CONTAINER_DLL_remove (mq_head, mq_tail, mq_entry); + GNUNET_free (mq_entry); + mq_entry = mq_head; + if (NULL != mq_entry) + transmit_handle = + GNUNET_SERVER_notify_transmit_ready (mq_entry->client, + ntohs (mq_entry->msg->size), + GNUNET_TIME_UNIT_FOREVER_REL, + &transmit_ready_notify, NULL); + return size; +} + + +/** + * Queues a message in send queue for sending to the service + * + * @param client the client to whom the queued message has to be sent + * @param msg the message to queue + */ +void +GST_queue_message (struct GNUNET_SERVER_Client *client, + struct GNUNET_MessageHeader *msg) +{ + struct MessageQueue *mq_entry; + uint16_t type; + uint16_t size; + + type = ntohs (msg->type); + size = ntohs (msg->size); + GNUNET_assert ((GNUNET_MESSAGE_TYPE_TESTBED_INIT <= type) && + (GNUNET_MESSAGE_TYPE_TESTBED_MAX > type)); + mq_entry = GNUNET_malloc (sizeof (struct MessageQueue)); + mq_entry->msg = msg; + mq_entry->client = client; + GNUNET_SERVER_client_keep (client); + LOG_DEBUG ("Queueing message of type %u, size %u for sending\n", type, + ntohs (msg->size)); + GNUNET_CONTAINER_DLL_insert_tail (mq_head, mq_tail, mq_entry); + if (NULL == transmit_handle) + transmit_handle = + GNUNET_SERVER_notify_transmit_ready (client, size, + GNUNET_TIME_UNIT_FOREVER_REL, + &transmit_ready_notify, NULL); +} + + +/** + * Similar to GNUNET_array_grow(); however instead of calling GNUNET_array_grow() + * several times we call it only once. The array is also made to grow in steps + * of LIST_GROW_STEP. + * + * @param ptr the array pointer to grow + * @param size the size of array + * @param accommodate_size the size which the array has to accommdate; after + * this call the array will be big enough to accommdate sizes upto + * accommodate_size + */ +#define array_grow_large_enough(ptr, size, accommodate_size) \ + do \ + { \ + unsigned int growth_size; \ + GNUNET_assert (size <= accommodate_size); \ + growth_size = size; \ + while (growth_size <= accommodate_size) \ + growth_size += LIST_GROW_STEP; \ + GNUNET_array_grow (ptr, size, growth_size); \ + GNUNET_assert (size > accommodate_size); \ + } while (0) + + +/** + * Function to add a host to the current list of known hosts + * + * @param host the host to add + * @return GNUNET_OK on success; GNUNET_SYSERR on failure due to host-id + * already in use + */ +static int +host_list_add (struct GNUNET_TESTBED_Host *host) +{ + uint32_t host_id; + + host_id = GNUNET_TESTBED_host_get_id_ (host); + if (GST_host_list_size <= host_id) + array_grow_large_enough (GST_host_list, GST_host_list_size, host_id); + if (NULL != GST_host_list[host_id]) + { + LOG_DEBUG ("A host with id: %u already exists\n", host_id); + return GNUNET_SYSERR; + } + GST_host_list[host_id] = host; + return GNUNET_OK; +} + + +/** + * Adds a route to the route list + * + * @param route the route to add + */ +static void +route_list_add (struct Route *route) +{ + if (route->dest >= route_list_size) + array_grow_large_enough (route_list, route_list_size, route->dest); + GNUNET_assert (NULL == route_list[route->dest]); + route_list[route->dest] = route; +} + + +/** + * Adds a slave to the slave array + * + * @param slave the slave controller to add + */ +static void +slave_list_add (struct Slave *slave) +{ + if (slave->host_id >= GST_slave_list_size) + array_grow_large_enough (GST_slave_list, GST_slave_list_size, + slave->host_id); + GNUNET_assert (NULL == GST_slave_list[slave->host_id]); + GST_slave_list[slave->host_id] = slave; +} + + +/** + * Adds a peer to the peer array + * + * @param peer the peer to add + */ +static void +peer_list_add (struct Peer *peer) +{ + if (peer->id >= GST_peer_list_size) + array_grow_large_enough (GST_peer_list, GST_peer_list_size, peer->id); + GNUNET_assert (NULL == GST_peer_list[peer->id]); + GST_peer_list[peer->id] = peer; +} + + +/** + * Removes a the give peer from the peer array + * + * @param peer the peer to be removed + */ +static void +peer_list_remove (struct Peer *peer) +{ + unsigned int orig_size; + uint32_t id; + + GST_peer_list[peer->id] = NULL; + orig_size = GST_peer_list_size; + while (GST_peer_list_size >= LIST_GROW_STEP) + { + for (id = GST_peer_list_size - 1; + (id >= GST_peer_list_size - LIST_GROW_STEP) && (id != UINT32_MAX); + id--) + if (NULL != GST_peer_list[id]) + break; + if (id != ((GST_peer_list_size - LIST_GROW_STEP) - 1)) + break; + GST_peer_list_size -= LIST_GROW_STEP; + } + if (orig_size == GST_peer_list_size) + return; + GST_peer_list = + GNUNET_realloc (GST_peer_list, + sizeof (struct Peer *) * GST_peer_list_size); +} + + +/** + * Finds the route with directly connected host as destination through which + * the destination host can be reached + * + * @param host_id the id of the destination host + * @return the route with directly connected destination host; NULL if no route + * is found + */ +struct Route * +GST_find_dest_route (uint32_t host_id) +{ + struct Route *route; + + if (route_list_size <= host_id) + return NULL; + while (NULL != (route = route_list[host_id])) + { + if (route->thru == GST_context->host_id) + break; + host_id = route->thru; + } + return route; +} + + +/** + * Routes message to a host given its host_id + * + * @param host_id the id of the destination host + * @param msg the message to be routed + */ +static void +route_message (uint32_t host_id, const struct GNUNET_MessageHeader *msg) +{ + GNUNET_break (0); +} + + +/** + * Send operation failure message to client + * + * @param client the client to which the failure message has to be sent to + * @param operation_id the id of the failed operation + * @param emsg the error message; can be NULL + */ +void +GST_send_operation_fail_msg (struct GNUNET_SERVER_Client *client, + uint64_t operation_id, const char *emsg) +{ + struct GNUNET_TESTBED_OperationFailureEventMessage *msg; + uint16_t msize; + uint16_t emsg_len; + + msize = sizeof (struct GNUNET_TESTBED_OperationFailureEventMessage); + emsg_len = (NULL == emsg) ? 0 : strlen (emsg) + 1; + msize += emsg_len; + msg = GNUNET_malloc (msize); + msg->header.size = htons (msize); + msg->header.type = htons (GNUNET_MESSAGE_TYPE_TESTBED_OPERATION_FAIL_EVENT); + msg->event_type = htonl (GNUNET_TESTBED_ET_OPERATION_FINISHED); + msg->operation_id = GNUNET_htonll (operation_id); + if (0 != emsg_len) + memcpy (&msg[1], emsg, emsg_len); + GST_queue_message (client, &msg->header); +} + + +/** + * Function to send generic operation success message to given client + * + * @param client the client to send the message to + * @param operation_id the id of the operation which was successful + */ +static void +send_operation_success_msg (struct GNUNET_SERVER_Client *client, + uint64_t operation_id) +{ + struct GNUNET_TESTBED_GenericOperationSuccessEventMessage *msg; + uint16_t msize; + + msize = sizeof (struct GNUNET_TESTBED_GenericOperationSuccessEventMessage); + msg = GNUNET_malloc (msize); + msg->header.size = htons (msize); + msg->header.type = + htons (GNUNET_MESSAGE_TYPE_TESTBED_GENERIC_OPERATION_SUCCESS); + msg->operation_id = GNUNET_htonll (operation_id); + msg->event_type = htonl (GNUNET_TESTBED_ET_OPERATION_FINISHED); + GST_queue_message (client, &msg->header); +} + + +/** + * Callback which will be called to after a host registration succeeded or failed + * + * @param cls the handle to the slave at which the registration is completed + * @param emsg the error message; NULL if host registration is successful + */ +static void +hr_completion (void *cls, const char *emsg); + + +/** + * Attempts to register the next host in the host registration queue + * + * @param slave the slave controller whose host registration queue is checked + * for host registrations + */ +static void +register_next_host (struct Slave *slave) +{ + struct HostRegistration *hr; + + hr = slave->hr_dll_head; + GNUNET_assert (NULL != hr); + GNUNET_assert (NULL == slave->rhandle); + LOG (GNUNET_ERROR_TYPE_DEBUG, "Registering host %u at %u\n", + GNUNET_TESTBED_host_get_id_ (hr->host), + GNUNET_TESTBED_host_get_id_ (GST_host_list[slave->host_id])); + slave->rhandle = + GNUNET_TESTBED_register_host (slave->controller, hr->host, hr_completion, + slave); +} + + +/** + * Callback which will be called to after a host registration succeeded or failed + * + * @param cls the handle to the slave at which the registration is completed + * @param emsg the error message; NULL if host registration is successful + */ +static void +hr_completion (void *cls, const char *emsg) +{ + struct Slave *slave = cls; + struct HostRegistration *hr; + + slave->rhandle = NULL; + hr = slave->hr_dll_head; + GNUNET_assert (NULL != hr); + LOG (GNUNET_ERROR_TYPE_DEBUG, "Registering host %u at %u successful\n", + GNUNET_TESTBED_host_get_id_ (hr->host), + GNUNET_TESTBED_host_get_id_ (GST_host_list[slave->host_id])); + GNUNET_CONTAINER_DLL_remove (slave->hr_dll_head, slave->hr_dll_tail, hr); + if (NULL != hr->cb) + hr->cb (hr->cb_cls, emsg); + GNUNET_free (hr); + if (NULL != slave->hr_dll_head) + register_next_host (slave); +} + + +/** + * Adds a host registration's request to a slave's registration queue + * + * @param slave the slave controller at which the given host has to be + * registered + * @param cb the host registration completion callback + * @param cb_cls the closure for the host registration completion callback + * @param host the host which has to be registered + */ +void +GST_queue_host_registration (struct Slave *slave, + GNUNET_TESTBED_HostRegistrationCompletion cb, + void *cb_cls, struct GNUNET_TESTBED_Host *host) +{ + struct HostRegistration *hr; + int call_register; + + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Queueing host registration for host %u at %u\n", + GNUNET_TESTBED_host_get_id_ (host), + GNUNET_TESTBED_host_get_id_ (GST_host_list[slave->host_id])); + hr = GNUNET_malloc (sizeof (struct HostRegistration)); + hr->cb = cb; + hr->cb_cls = cb_cls; + hr->host = host; + call_register = (NULL == slave->hr_dll_head) ? GNUNET_YES : GNUNET_NO; + GNUNET_CONTAINER_DLL_insert_tail (slave->hr_dll_head, slave->hr_dll_tail, hr); + if (GNUNET_YES == call_register) + register_next_host (slave); +} + + +/** + * The Link Controller forwarding task + * + * @param cls the LCFContext + * @param tc the Task context from scheduler + */ +static void +lcf_proc_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc); + + +/** + * Completion callback for host registrations while forwarding Link Controller messages + * + * @param cls the LCFContext + * @param emsg the error message; NULL if host registration is successful + */ +static void +lcf_proc_cc (void *cls, const char *emsg) +{ + struct LCFContext *lcf = cls; + + GNUNET_assert (GNUNET_SCHEDULER_NO_TASK == lcf_proc_task_id); + switch (lcf->state) + { + case INIT: + if (NULL != emsg) + goto registration_error; + lcf->state = DELEGATED_HOST_REGISTERED; + lcf_proc_task_id = GNUNET_SCHEDULER_add_now (&lcf_proc_task, lcf); + break; + case DELEGATED_HOST_REGISTERED: + if (NULL != emsg) + goto registration_error; + lcf->state = SLAVE_HOST_REGISTERED; + lcf_proc_task_id = GNUNET_SCHEDULER_add_now (&lcf_proc_task, lcf); + break; + default: + GNUNET_assert (0); /* Shouldn't reach here */ + } + return; + +registration_error: + LOG (GNUNET_ERROR_TYPE_WARNING, "Host registration failed with message: %s\n", + emsg); + lcf->state = FINISHED; + lcf_proc_task_id = GNUNET_SCHEDULER_add_now (&lcf_proc_task, lcf); +} + + +/** + * Callback to relay the reply msg of a forwarded operation back to the client + * + * @param cls ForwardedOperationContext + * @param msg the message to relay + */ +void +GST_forwarded_operation_reply_relay (void *cls, + const struct GNUNET_MessageHeader *msg) +{ + struct ForwardedOperationContext *fopc = cls; + struct GNUNET_MessageHeader *dup_msg; + uint16_t msize; + + msize = ntohs (msg->size); + LOG_DEBUG ("Relaying message with type: %u, size: %u\n", ntohs (msg->type), + msize); + dup_msg = GNUNET_copy_message (msg); + GST_queue_message (fopc->client, dup_msg); + GNUNET_SERVER_client_drop (fopc->client); + GNUNET_SCHEDULER_cancel (fopc->timeout_task); + GNUNET_CONTAINER_DLL_remove (fopcq_head, fopcq_tail, fopc); + GNUNET_free (fopc); +} + + +/** + * Task to free resources when forwarded operation has been timedout + * + * @param cls the ForwardedOperationContext + * @param tc the task context from scheduler + */ +void +GST_forwarded_operation_timeout (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct ForwardedOperationContext *fopc = cls; + + GNUNET_TESTBED_forward_operation_msg_cancel_ (fopc->opc); + LOG (GNUNET_ERROR_TYPE_WARNING, "A forwarded operation has timed out\n"); + GST_send_operation_fail_msg (fopc->client, fopc->operation_id, "Timeout"); + GNUNET_SERVER_client_drop (fopc->client); + GNUNET_CONTAINER_DLL_remove (fopcq_head, fopcq_tail, fopc); + GNUNET_free (fopc); +} + + +/** + * The Link Controller forwarding task + * + * @param cls the LCFContext + * @param tc the Task context from scheduler + */ +static void +lcf_proc_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc); + + +/** + * Callback to be called when forwarded link controllers operation is + * successfull. We have to relay the reply msg back to the client + * + * @param cls the LCFContext + * @param msg the message to relay + */ +static void +lcf_forwarded_operation_reply_relay (void *cls, + const struct GNUNET_MessageHeader *msg) +{ + struct LCFContext *lcf = cls; + + GNUNET_assert (NULL != lcf->fopc); + GST_forwarded_operation_reply_relay (lcf->fopc, msg); + lcf->fopc = NULL; + GNUNET_assert (GNUNET_SCHEDULER_NO_TASK == lcf_proc_task_id); + lcf_proc_task_id = GNUNET_SCHEDULER_add_now (&lcf_proc_task, lcf); +} + + +/** + * Task to free resources when forwarded link controllers has been timedout + * + * @param cls the LCFContext + * @param tc the task context from scheduler + */ +static void +lcf_forwarded_operation_timeout (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct LCFContext *lcf = cls; + + GNUNET_assert (NULL != lcf->fopc); + lcf->fopc->timeout_task = GNUNET_SCHEDULER_NO_TASK; + GST_forwarded_operation_timeout (lcf->fopc, tc); + lcf->fopc = NULL; + GNUNET_assert (GNUNET_SCHEDULER_NO_TASK == lcf_proc_task_id); + lcf_proc_task_id = GNUNET_SCHEDULER_add_now (&lcf_proc_task, lcf); +} + + +/** + * The Link Controller forwarding task + * + * @param cls the LCFContext + * @param tc the Task context from scheduler + */ +static void +lcf_proc_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct LCFContext *lcf = cls; + struct LCFContextQueue *lcfq; + + lcf_proc_task_id = GNUNET_SCHEDULER_NO_TASK; + switch (lcf->state) + { + case INIT: + if (GNUNET_NO == + GNUNET_TESTBED_is_host_registered_ (GST_host_list + [lcf->delegated_host_id], + lcf->gateway->controller)) + { + GST_queue_host_registration (lcf->gateway, lcf_proc_cc, lcf, + GST_host_list[lcf->delegated_host_id]); + } + else + { + lcf->state = DELEGATED_HOST_REGISTERED; + lcf_proc_task_id = GNUNET_SCHEDULER_add_now (&lcf_proc_task, lcf); + } + break; + case DELEGATED_HOST_REGISTERED: + if (GNUNET_NO == + GNUNET_TESTBED_is_host_registered_ (GST_host_list[lcf->slave_host_id], + lcf->gateway->controller)) + { + GST_queue_host_registration (lcf->gateway, lcf_proc_cc, lcf, + GST_host_list[lcf->slave_host_id]); + } + else + { + lcf->state = SLAVE_HOST_REGISTERED; + lcf_proc_task_id = GNUNET_SCHEDULER_add_now (&lcf_proc_task, lcf); + } + break; + case SLAVE_HOST_REGISTERED: + lcf->fopc = GNUNET_malloc (sizeof (struct ForwardedOperationContext)); + lcf->fopc->client = lcf->client; + lcf->fopc->operation_id = lcf->operation_id; + lcf->fopc->type = OP_LINK_CONTROLLERS; + lcf->fopc->opc = + GNUNET_TESTBED_forward_operation_msg_ (lcf->gateway->controller, + lcf->operation_id, + &lcf->msg->header, + &lcf_forwarded_operation_reply_relay, + lcf); + lcf->fopc->timeout_task = + GNUNET_SCHEDULER_add_delayed (TIMEOUT, &lcf_forwarded_operation_timeout, + lcf); + GNUNET_CONTAINER_DLL_insert_tail (fopcq_head, fopcq_tail, lcf->fopc); + lcf->state = FINISHED; + break; + case FINISHED: + lcfq = lcfq_head; + GNUNET_assert (lcfq->lcf == lcf); + GNUNET_free (lcf->msg); + GNUNET_free (lcf); + GNUNET_CONTAINER_DLL_remove (lcfq_head, lcfq_tail, lcfq); + GNUNET_free (lcfq); + if (NULL != lcfq_head) + lcf_proc_task_id = + GNUNET_SCHEDULER_add_now (&lcf_proc_task, lcfq_head->lcf); + } +} + + +/** + * Callback for event from slave controllers + * + * @param cls struct Slave * + * @param event information about the event + */ +static void +slave_event_callback (void *cls, + const struct GNUNET_TESTBED_EventInformation *event) +{ + struct RegisteredHostContext *rhc; + struct GNUNET_CONFIGURATION_Handle *cfg; + struct GNUNET_TESTBED_Operation *old_op; + + /* We currently only get here when working on RegisteredHostContexts */ + GNUNET_assert (GNUNET_TESTBED_ET_OPERATION_FINISHED == event->type); + rhc = event->details.operation_finished.op_cls; + GNUNET_assert (rhc->sub_op == event->details.operation_finished.operation); + switch (rhc->state) + { + case RHC_GET_CFG: + cfg = event->details.operation_finished.generic; + old_op = rhc->sub_op; + rhc->state = RHC_LINK; + rhc->sub_op = + GNUNET_TESTBED_controller_link (rhc, rhc->gateway->controller, + rhc->reg_host, rhc->host, cfg, + GNUNET_NO); + GNUNET_TESTBED_operation_done (old_op); + break; + case RHC_LINK: + LOG_DEBUG ("OL: Linking controllers successfull\n"); + GNUNET_TESTBED_operation_done (rhc->sub_op); + rhc->sub_op = NULL; + rhc->state = RHC_OL_CONNECT; + GST_process_next_focc (rhc); + break; + default: + GNUNET_assert (0); + } +} + + +/** + * Callback to signal successfull startup of the controller process + * + * @param cls the handle to the slave whose status is to be found here + * @param cfg the configuration with which the controller has been started; + * NULL if status is not GNUNET_OK + * @param status GNUNET_OK if the startup is successfull; GNUNET_SYSERR if not, + * GNUNET_TESTBED_controller_stop() shouldn't be called in this case + */ +static void +slave_status_callback (void *cls, const struct GNUNET_CONFIGURATION_Handle *cfg, + int status) +{ + struct Slave *slave = cls; + struct LinkControllersContext *lcc; + + lcc = slave->lcc; + if (GNUNET_SYSERR == status) + { + slave->controller_proc = NULL; + GST_slave_list[slave->host_id] = NULL; + if (NULL != slave->cfg) + GNUNET_CONFIGURATION_destroy (slave->cfg); + GNUNET_free (slave); + slave = NULL; + LOG (GNUNET_ERROR_TYPE_WARNING, "Unexpected slave shutdown\n"); + GNUNET_SCHEDULER_shutdown (); /* We too shutdown */ + goto clean_lcc; + } + slave->controller = + GNUNET_TESTBED_controller_connect (cfg, GST_host_list[slave->host_id], + event_mask, &slave_event_callback, + slave); + if (NULL != slave->controller) + { + send_operation_success_msg (lcc->client, lcc->operation_id); + slave->cfg = GNUNET_CONFIGURATION_dup (cfg); + } + else + { + GST_send_operation_fail_msg (lcc->client, lcc->operation_id, + "Could not connect to delegated controller"); + GNUNET_TESTBED_controller_stop (slave->controller_proc); + GST_slave_list[slave->host_id] = NULL; + GNUNET_free (slave); + slave = NULL; + } + +clean_lcc: + if (NULL != lcc) + { + if (NULL != lcc->client) + { + GNUNET_SERVER_receive_done (lcc->client, GNUNET_OK); + GNUNET_SERVER_client_drop (lcc->client); + lcc->client = NULL; + } + GNUNET_free (lcc); + } + if (NULL != slave) + slave->lcc = NULL; +} + + +/** + * Message handler for GNUNET_MESSAGE_TYPE_TESTBED_INIT messages + * + * @param cls NULL + * @param client identification of the client + * @param message the actual message + */ +static void +handle_init (void *cls, struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) +{ + const struct GNUNET_TESTBED_InitMessage *msg; + struct GNUNET_TESTBED_Host *host; + const char *controller_hostname; + uint16_t msize; + + if (NULL != GST_context) + { + LOG_DEBUG ("We are being connected to laterally\n"); + GNUNET_SERVER_receive_done (client, GNUNET_OK); + return; + } + msg = (const struct GNUNET_TESTBED_InitMessage *) message; + msize = ntohs (message->size); + if (msize <= sizeof (struct GNUNET_TESTBED_InitMessage)) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + msize -= sizeof (struct GNUNET_TESTBED_InitMessage); + controller_hostname = (const char *) &msg[1]; + if ('\0' != controller_hostname[msize - 1]) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + GST_context = GNUNET_malloc (sizeof (struct Context)); + GNUNET_SERVER_client_keep (client); + GST_context->client = client; + GST_context->host_id = ntohl (msg->host_id); + GST_context->master_ip = GNUNET_strdup (controller_hostname); + LOG_DEBUG ("Our IP: %s\n", GST_context->master_ip); + GST_context->system = + GNUNET_TESTING_system_create ("testbed", GST_context->master_ip, + hostname); + host = + GNUNET_TESTBED_host_create_with_id (GST_context->host_id, + GST_context->master_ip, NULL, 0); + host_list_add (host); + LOG_DEBUG ("Created master context with host ID: %u\n", GST_context->host_id); + GNUNET_SERVER_receive_done (client, GNUNET_OK); +} + + +/** + * Message handler for GNUNET_MESSAGE_TYPE_TESTBED_ADDHOST messages + * + * @param cls NULL + * @param client identification of the client + * @param message the actual message + */ +static void +handle_add_host (void *cls, struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) +{ + struct GNUNET_TESTBED_Host *host; + const struct GNUNET_TESTBED_AddHostMessage *msg; + struct GNUNET_TESTBED_HostConfirmedMessage *reply; + char *username; + char *hostname; + char *emsg; + uint32_t host_id; + uint16_t username_length; + uint16_t hostname_length; + uint16_t reply_size; + uint16_t msize; + + msg = (const struct GNUNET_TESTBED_AddHostMessage *) message; + msize = ntohs (msg->header.size); + username = (char *) &msg[1]; + username_length = ntohs (msg->user_name_length); + if (0 != username_length) + username_length++; + /* msg must contain hostname */ + GNUNET_assert (msize > + (sizeof (struct GNUNET_TESTBED_AddHostMessage) + + username_length + 1)); + if (0 != username_length) + GNUNET_assert ('\0' == username[username_length - 1]); + hostname = username + username_length; + hostname_length = + msize - (sizeof (struct GNUNET_TESTBED_AddHostMessage) + username_length); + GNUNET_assert ('\0' == hostname[hostname_length - 1]); + GNUNET_assert (strlen (hostname) == hostname_length - 1); + host_id = ntohl (msg->host_id); + LOG_DEBUG ("Received ADDHOST %u message\n", host_id); + LOG_DEBUG ("-------host id: %u\n", host_id); + LOG_DEBUG ("-------hostname: %s\n", hostname); + if (0 != username_length) + LOG_DEBUG ("-------username: %s\n", username); + else + { + LOG_DEBUG ("-------username: NULL\n"); + username = NULL; + } + LOG_DEBUG ("-------ssh port: %u\n", ntohs (msg->ssh_port)); + host = + GNUNET_TESTBED_host_create_with_id (host_id, hostname, username, + ntohs (msg->ssh_port)); + GNUNET_assert (NULL != host); + reply_size = sizeof (struct GNUNET_TESTBED_HostConfirmedMessage); + if (GNUNET_OK != host_list_add (host)) + { + /* We are unable to add a host */ + emsg = "A host exists with given host-id"; + LOG_DEBUG ("%s: %u", emsg, host_id); + GNUNET_TESTBED_host_destroy (host); + reply_size += strlen (emsg) + 1; + reply = GNUNET_malloc (reply_size); + memcpy (&reply[1], emsg, strlen (emsg) + 1); + } + else + { + LOG_DEBUG ("Added host %u at %u\n", host_id, GST_context->host_id); + reply = GNUNET_malloc (reply_size); + } + reply->header.type = htons (GNUNET_MESSAGE_TYPE_TESTBED_ADD_HOST_SUCCESS); + reply->header.size = htons (reply_size); + reply->host_id = htonl (host_id); + GST_queue_message (client, &reply->header); + GNUNET_SERVER_receive_done (client, GNUNET_OK); +} + + +/** + * Iterator over hash map entries. + * + * @param cls closure + * @param key current key code + * @param value value in the hash map + * @return GNUNET_YES if we should continue to + * iterate, + * GNUNET_NO if not. + */ +int +ss_exists_iterator (void *cls, const struct GNUNET_HashCode *key, void *value) +{ + struct SharedService *queried_ss = cls; + struct SharedService *ss = value; + + if (0 == strcmp (ss->name, queried_ss->name)) + return GNUNET_NO; + else + return GNUNET_YES; +} + + +/** + * Message handler for GNUNET_MESSAGE_TYPE_TESTBED_ADDHOST messages + * + * @param cls NULL + * @param client identification of the client + * @param message the actual message + */ +static void +handle_configure_shared_service (void *cls, struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) +{ + const struct GNUNET_TESTBED_ConfigureSharedServiceMessage *msg; + struct SharedService *ss; + char *service_name; + struct GNUNET_HashCode hash; + uint16_t msg_size; + uint16_t service_name_size; + + msg = (const struct GNUNET_TESTBED_ConfigureSharedServiceMessage *) message; + msg_size = ntohs (message->size); + if (msg_size <= sizeof (struct GNUNET_TESTBED_ConfigureSharedServiceMessage)) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + service_name_size = + msg_size - sizeof (struct GNUNET_TESTBED_ConfigureSharedServiceMessage); + service_name = (char *) &msg[1]; + if ('\0' != service_name[service_name_size - 1]) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + LOG_DEBUG ("Received service sharing request for %s, with %d peers\n", + service_name, ntohl (msg->num_peers)); + if (ntohl (msg->host_id) != GST_context->host_id) + { + route_message (ntohl (msg->host_id), message); + GNUNET_SERVER_receive_done (client, GNUNET_OK); + return; + } + GNUNET_SERVER_receive_done (client, GNUNET_OK); + ss = GNUNET_malloc (sizeof (struct SharedService)); + ss->name = strdup (service_name); + ss->num_shared = ntohl (msg->num_peers); + GNUNET_CRYPTO_hash (ss->name, service_name_size, &hash); + if (GNUNET_SYSERR == + GNUNET_CONTAINER_multihashmap_get_multiple (ss_map, &hash, + &ss_exists_iterator, ss)) + { + LOG (GNUNET_ERROR_TYPE_WARNING, + "Service %s already configured as a shared service. " + "Ignoring service sharing request \n", ss->name); + GNUNET_free (ss->name); + GNUNET_free (ss); + return; + } + GNUNET_CONTAINER_multihashmap_put (ss_map, &hash, ss, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE); +} + + +/** + * Message handler for GNUNET_MESSAGE_TYPE_TESTBED_LCONTROLLERS message + * + * @param cls NULL + * @param client identification of the client + * @param message the actual message + */ +static void +handle_link_controllers (void *cls, struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) +{ + const struct GNUNET_TESTBED_ControllerLinkMessage *msg; + struct GNUNET_CONFIGURATION_Handle *cfg; + struct LCFContextQueue *lcfq; + struct Route *route; + struct Route *new_route; + char *config; + uLongf dest_size; + size_t config_size; + uint32_t delegated_host_id; + uint32_t slave_host_id; + uint16_t msize; + + if (NULL == GST_context) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + msize = ntohs (message->size); + if (sizeof (struct GNUNET_TESTBED_ControllerLinkMessage) >= msize) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + msg = (const struct GNUNET_TESTBED_ControllerLinkMessage *) message; + delegated_host_id = ntohl (msg->delegated_host_id); + if (delegated_host_id == GST_context->host_id) + { + GNUNET_break (0); + LOG (GNUNET_ERROR_TYPE_WARNING, "Trying to link ourselves\n"); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + if ((delegated_host_id >= GST_host_list_size) || + (NULL == GST_host_list[delegated_host_id])) + { + LOG (GNUNET_ERROR_TYPE_WARNING, + "Delegated host %u not registered with us\n", delegated_host_id); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + slave_host_id = ntohl (msg->slave_host_id); + if ((slave_host_id >= GST_host_list_size) || + (NULL == GST_host_list[slave_host_id])) + { + LOG (GNUNET_ERROR_TYPE_WARNING, "Slave host %u not registered with us\n", + slave_host_id); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + if (slave_host_id == delegated_host_id) + { + LOG (GNUNET_ERROR_TYPE_WARNING, "Slave and delegated host are same\n"); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + + if (slave_host_id == GST_context->host_id) /* Link from us */ + { + struct Slave *slave; + struct LinkControllersContext *lcc; + + msize -= sizeof (struct GNUNET_TESTBED_ControllerLinkMessage); + config_size = ntohs (msg->config_size); + if ((delegated_host_id < GST_slave_list_size) && (NULL != GST_slave_list[delegated_host_id])) /* We have already added */ + { + LOG (GNUNET_ERROR_TYPE_WARNING, "Host %u already connected\n", + delegated_host_id); + GNUNET_SERVER_receive_done (client, GNUNET_OK); + return; + } + config = GNUNET_malloc (config_size); + dest_size = (uLongf) config_size; + if (Z_OK != + uncompress ((Bytef *) config, &dest_size, (const Bytef *) &msg[1], + (uLong) msize)) + { + GNUNET_break (0); /* Compression error */ + GNUNET_free (config); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + if (config_size != dest_size) + { + LOG (GNUNET_ERROR_TYPE_WARNING, "Uncompressed config size mismatch\n"); + GNUNET_free (config); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + cfg = GNUNET_CONFIGURATION_create (); /* Free here or in lcfcontext */ + if (GNUNET_OK != + GNUNET_CONFIGURATION_deserialize (cfg, config, config_size, GNUNET_NO)) + { + GNUNET_break (0); /* Configuration parsing error */ + GNUNET_free (config); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + GNUNET_free (config); + if ((delegated_host_id < GST_slave_list_size) && + (NULL != GST_slave_list[delegated_host_id])) + { + GNUNET_break (0); /* Configuration parsing error */ + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + slave = GNUNET_malloc (sizeof (struct Slave)); + slave->host_id = delegated_host_id; + slave->reghost_map = GNUNET_CONTAINER_multihashmap_create (100, GNUNET_NO); + slave_list_add (slave); + if (1 != msg->is_subordinate) + { + slave->controller = + GNUNET_TESTBED_controller_connect (cfg, GST_host_list[slave->host_id], + event_mask, &slave_event_callback, + slave); + slave->cfg = cfg; + if (NULL != slave->controller) + send_operation_success_msg (client, GNUNET_ntohll (msg->operation_id)); + else + GST_send_operation_fail_msg (client, GNUNET_ntohll (msg->operation_id), + "Could not connect to delegated controller"); + GNUNET_SERVER_receive_done (client, GNUNET_OK); + return; + } + lcc = GNUNET_malloc (sizeof (struct LinkControllersContext)); + lcc->operation_id = GNUNET_ntohll (msg->operation_id); + GNUNET_SERVER_client_keep (client); + lcc->client = client; + slave->lcc = lcc; + slave->controller_proc = + GNUNET_TESTBED_controller_start (GST_context->master_ip, + GST_host_list[slave->host_id], cfg, + &slave_status_callback, slave); + GNUNET_CONFIGURATION_destroy (cfg); + new_route = GNUNET_malloc (sizeof (struct Route)); + new_route->dest = delegated_host_id; + new_route->thru = GST_context->host_id; + route_list_add (new_route); + return; + } + + /* Route the request */ + if (slave_host_id >= route_list_size) + { + LOG (GNUNET_ERROR_TYPE_WARNING, "No route towards slave host"); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + lcfq = GNUNET_malloc (sizeof (struct LCFContextQueue)); + lcfq->lcf = GNUNET_malloc (sizeof (struct LCFContext)); + lcfq->lcf->delegated_host_id = delegated_host_id; + lcfq->lcf->slave_host_id = slave_host_id; + route = GST_find_dest_route (slave_host_id); + GNUNET_assert (NULL != route); /* because we add routes carefully */ + GNUNET_assert (route->dest < GST_slave_list_size); + GNUNET_assert (NULL != GST_slave_list[route->dest]); + lcfq->lcf->state = INIT; + lcfq->lcf->operation_id = GNUNET_ntohll (msg->operation_id); + lcfq->lcf->gateway = GST_slave_list[route->dest]; + lcfq->lcf->msg = GNUNET_malloc (msize); + (void) memcpy (lcfq->lcf->msg, msg, msize); + GNUNET_SERVER_client_keep (client); + lcfq->lcf->client = client; + if (NULL == lcfq_head) + { + GNUNET_assert (GNUNET_SCHEDULER_NO_TASK == lcf_proc_task_id); + GNUNET_CONTAINER_DLL_insert_tail (lcfq_head, lcfq_tail, lcfq); + lcf_proc_task_id = GNUNET_SCHEDULER_add_now (&lcf_proc_task, lcfq->lcf); + } + else + GNUNET_CONTAINER_DLL_insert_tail (lcfq_head, lcfq_tail, lcfq); + /* FIXME: Adding a new route should happen after the controllers are linked + * successfully */ + if (1 != msg->is_subordinate) + { + GNUNET_SERVER_receive_done (client, GNUNET_OK); + return; + } + if ((delegated_host_id < route_list_size) && + (NULL != route_list[delegated_host_id])) + { + GNUNET_break_op (0); /* Are you trying to link delegated host twice + * with is subordinate flag set to GNUNET_YES? */ + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + new_route = GNUNET_malloc (sizeof (struct Route)); + new_route->dest = delegated_host_id; + new_route->thru = route->dest; + route_list_add (new_route); + GNUNET_SERVER_receive_done (client, GNUNET_OK); +} + + +/** + * The task to be executed if the forwarded peer create operation has been + * timed out + * + * @param cls the FowardedOperationContext + * @param tc the TaskContext from the scheduler + */ +static void +peer_create_forward_timeout (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct ForwardedOperationContext *fopc = cls; + + GNUNET_free (fopc->cls); + GST_forwarded_operation_timeout (fopc, tc); +} + + +/** + * Callback to be called when forwarded peer create operation is successfull. We + * have to relay the reply msg back to the client + * + * @param cls ForwardedOperationContext + * @param msg the peer create success message + */ +static void +peer_create_success_cb (void *cls, const struct GNUNET_MessageHeader *msg) +{ + struct ForwardedOperationContext *fopc = cls; + struct Peer *remote_peer; + + if (ntohs (msg->type) == GNUNET_MESSAGE_TYPE_TESTBED_CREATE_PEER_SUCCESS) + { + GNUNET_assert (NULL != fopc->cls); + remote_peer = fopc->cls; + peer_list_add (remote_peer); + } + GST_forwarded_operation_reply_relay (fopc, msg); +} + + +/** + * Function to destroy a peer + * + * @param peer the peer structure to destroy + */ +void +GST_destroy_peer (struct Peer *peer) +{ + GNUNET_break (0 == peer->reference_cnt); + if (GNUNET_YES == peer->is_remote) + { + peer_list_remove (peer); + GNUNET_free (peer); + return; + } + if (GNUNET_YES == peer->details.local.is_running) + { + GNUNET_TESTING_peer_stop (peer->details.local.peer); + peer->details.local.is_running = GNUNET_NO; + } + GNUNET_TESTING_peer_destroy (peer->details.local.peer); + GNUNET_CONFIGURATION_destroy (peer->details.local.cfg); + peer_list_remove (peer); + GNUNET_free (peer); +} + + +/** + * Callback to be called when forwarded peer destroy operation is successfull. We + * have to relay the reply msg back to the client + * + * @param cls ForwardedOperationContext + * @param msg the peer create success message + */ +static void +peer_destroy_success_cb (void *cls, const struct GNUNET_MessageHeader *msg) +{ + struct ForwardedOperationContext *fopc = cls; + struct Peer *remote_peer; + + if (GNUNET_MESSAGE_TYPE_TESTBED_GENERIC_OPERATION_SUCCESS == + ntohs (msg->type)) + { + remote_peer = fopc->cls; + GNUNET_assert (NULL != remote_peer); + remote_peer->destroy_flag = GNUNET_YES; + if (0 == remote_peer->reference_cnt) + GST_destroy_peer (remote_peer); + } + GST_forwarded_operation_reply_relay (fopc, msg); +} + + + +/** + * Handler for GNUNET_MESSAGE_TYPE_TESTBED_CREATEPEER messages + * + * @param cls NULL + * @param client identification of the client + * @param message the actual message + */ +static void +handle_peer_create (void *cls, struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) +{ + const struct GNUNET_TESTBED_PeerCreateMessage *msg; + struct GNUNET_TESTBED_PeerCreateSuccessEventMessage *reply; + struct GNUNET_CONFIGURATION_Handle *cfg; + struct ForwardedOperationContext *fo_ctxt; + struct Route *route; + struct Peer *peer; + char *config; + size_t dest_size; + int ret; + uint32_t config_size; + uint32_t host_id; + uint32_t peer_id; + uint16_t msize; + + + msize = ntohs (message->size); + if (msize <= sizeof (struct GNUNET_TESTBED_PeerCreateMessage)) + { + GNUNET_break (0); /* We need configuration */ + GNUNET_SERVER_receive_done (client, GNUNET_OK); + return; + } + msg = (const struct GNUNET_TESTBED_PeerCreateMessage *) message; + host_id = ntohl (msg->host_id); + peer_id = ntohl (msg->peer_id); + if (UINT32_MAX == peer_id) + { + GST_send_operation_fail_msg (client, GNUNET_ntohll (msg->operation_id), + "Cannot create peer with given ID"); + GNUNET_SERVER_receive_done (client, GNUNET_OK); + return; + } + if (host_id == GST_context->host_id) + { + char *emsg; + + /* We are responsible for this peer */ + msize -= sizeof (struct GNUNET_TESTBED_PeerCreateMessage); + config_size = ntohl (msg->config_size); + config = GNUNET_malloc (config_size); + dest_size = config_size; + if (Z_OK != + (ret = + uncompress ((Bytef *) config, (uLongf *) & dest_size, + (const Bytef *) &msg[1], (uLong) msize))) + { + GNUNET_break (0); /* uncompression error */ + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + if (config_size != dest_size) + { + GNUNET_break (0); /* Uncompressed config size mismatch */ + GNUNET_free (config); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + cfg = GNUNET_CONFIGURATION_create (); + if (GNUNET_OK != + GNUNET_CONFIGURATION_deserialize (cfg, config, config_size, GNUNET_NO)) + { + GNUNET_break (0); /* Configuration parsing error */ + GNUNET_free (config); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + GNUNET_free (config); + GNUNET_CONFIGURATION_set_value_number (cfg, "TESTBED", "PEERID", + (unsigned long long) peer_id); + peer = GNUNET_malloc (sizeof (struct Peer)); + peer->is_remote = GNUNET_NO; + peer->details.local.cfg = cfg; + peer->id = peer_id; + LOG_DEBUG ("Creating peer with id: %u\n", (unsigned int) peer->id); + peer->details.local.peer = + GNUNET_TESTING_peer_configure (GST_context->system, + peer->details.local.cfg, peer->id, + NULL /* Peer id */ , + &emsg); + if (NULL == peer->details.local.peer) + { + LOG (GNUNET_ERROR_TYPE_WARNING, "Configuring peer failed: %s\n", emsg); + GNUNET_free (emsg); + GNUNET_free (peer); + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + peer->details.local.is_running = GNUNET_NO; + peer_list_add (peer); + reply = + GNUNET_malloc (sizeof + (struct GNUNET_TESTBED_PeerCreateSuccessEventMessage)); + reply->header.size = + htons (sizeof (struct GNUNET_TESTBED_PeerCreateSuccessEventMessage)); + reply->header.type = + htons (GNUNET_MESSAGE_TYPE_TESTBED_CREATE_PEER_SUCCESS); + reply->peer_id = msg->peer_id; + reply->operation_id = msg->operation_id; + GST_queue_message (client, &reply->header); + GNUNET_SERVER_receive_done (client, GNUNET_OK); + return; + } + + /* Forward peer create request */ + route = GST_find_dest_route (host_id); + if (NULL == route) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_OK); + return; + } + + peer = GNUNET_malloc (sizeof (struct Peer)); + peer->is_remote = GNUNET_YES; + peer->id = peer_id; + peer->details.remote.slave = GST_slave_list[route->dest]; + peer->details.remote.remote_host_id = host_id; + fo_ctxt = GNUNET_malloc (sizeof (struct ForwardedOperationContext)); + GNUNET_SERVER_client_keep (client); + fo_ctxt->client = client; + fo_ctxt->operation_id = GNUNET_ntohll (msg->operation_id); + fo_ctxt->cls = peer; //GST_slave_list[route->dest]->controller; + fo_ctxt->type = OP_PEER_CREATE; + fo_ctxt->opc = + GNUNET_TESTBED_forward_operation_msg_ (GST_slave_list + [route->dest]->controller, + fo_ctxt->operation_id, + &msg->header, + peer_create_success_cb, fo_ctxt); + fo_ctxt->timeout_task = + GNUNET_SCHEDULER_add_delayed (TIMEOUT, &peer_create_forward_timeout, + fo_ctxt); + GNUNET_CONTAINER_DLL_insert_tail (fopcq_head, fopcq_tail, fo_ctxt); + GNUNET_SERVER_receive_done (client, GNUNET_OK); +} + + +/** + * Message handler for GNUNET_MESSAGE_TYPE_TESTBED_DESTROYPEER messages + * + * @param cls NULL + * @param client identification of the client + * @param message the actual message + */ +static void +handle_peer_destroy (void *cls, struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) +{ + const struct GNUNET_TESTBED_PeerDestroyMessage *msg; + struct ForwardedOperationContext *fopc; + struct Peer *peer; + uint32_t peer_id; + + msg = (const struct GNUNET_TESTBED_PeerDestroyMessage *) message; + peer_id = ntohl (msg->peer_id); + LOG_DEBUG ("Received peer destory on peer: %u and operation id: %ul\n", + peer_id, GNUNET_ntohll (msg->operation_id)); + if ((GST_peer_list_size <= peer_id) || (NULL == GST_peer_list[peer_id])) + { + LOG (GNUNET_ERROR_TYPE_ERROR, + "Asked to destroy a non existent peer with id: %u\n", peer_id); + GST_send_operation_fail_msg (client, GNUNET_ntohll (msg->operation_id), + "Peer doesn't exist"); + GNUNET_SERVER_receive_done (client, GNUNET_OK); + return; + } + peer = GST_peer_list[peer_id]; + if (GNUNET_YES == peer->is_remote) + { + /* Forward the destory message to sub controller */ + fopc = GNUNET_malloc (sizeof (struct ForwardedOperationContext)); + GNUNET_SERVER_client_keep (client); + fopc->client = client; + fopc->cls = peer; + fopc->type = OP_PEER_DESTROY; + fopc->operation_id = GNUNET_ntohll (msg->operation_id); + fopc->opc = + GNUNET_TESTBED_forward_operation_msg_ (peer->details.remote. + slave->controller, + fopc->operation_id, &msg->header, + &peer_destroy_success_cb, fopc); + fopc->timeout_task = + GNUNET_SCHEDULER_add_delayed (TIMEOUT, &GST_forwarded_operation_timeout, + fopc); + GNUNET_CONTAINER_DLL_insert_tail (fopcq_head, fopcq_tail, fopc); + GNUNET_SERVER_receive_done (client, GNUNET_OK); + return; + } + peer->destroy_flag = GNUNET_YES; + if (0 == peer->reference_cnt) + GST_destroy_peer (peer); + else + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Delaying peer destroy as peer is currently in use\n"); + send_operation_success_msg (client, GNUNET_ntohll (msg->operation_id)); + GNUNET_SERVER_receive_done (client, GNUNET_OK); +} + + +/** + * Message handler for GNUNET_MESSAGE_TYPE_TESTBED_DESTROYPEER messages + * + * @param cls NULL + * @param client identification of the client + * @param message the actual message + */ +static void +handle_peer_start (void *cls, struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) +{ + const struct GNUNET_TESTBED_PeerStartMessage *msg; + struct GNUNET_TESTBED_PeerEventMessage *reply; + struct ForwardedOperationContext *fopc; + struct Peer *peer; + uint32_t peer_id; + + msg = (const struct GNUNET_TESTBED_PeerStartMessage *) message; + peer_id = ntohl (msg->peer_id); + if ((peer_id >= GST_peer_list_size) || (NULL == GST_peer_list[peer_id])) + { + GNUNET_break (0); + LOG (GNUNET_ERROR_TYPE_ERROR, + "Asked to start a non existent peer with id: %u\n", peer_id); + GNUNET_SERVER_receive_done (client, GNUNET_OK); + return; + } + peer = GST_peer_list[peer_id]; + if (GNUNET_YES == peer->is_remote) + { + fopc = GNUNET_malloc (sizeof (struct ForwardedOperationContext)); + GNUNET_SERVER_client_keep (client); + fopc->client = client; + fopc->operation_id = GNUNET_ntohll (msg->operation_id); + fopc->type = OP_PEER_START; + fopc->opc = + GNUNET_TESTBED_forward_operation_msg_ (peer->details.remote. + slave->controller, + fopc->operation_id, &msg->header, + &GST_forwarded_operation_reply_relay, + fopc); + fopc->timeout_task = + GNUNET_SCHEDULER_add_delayed (TIMEOUT, &GST_forwarded_operation_timeout, + fopc); + GNUNET_CONTAINER_DLL_insert_tail (fopcq_head, fopcq_tail, fopc); + GNUNET_SERVER_receive_done (client, GNUNET_OK); + return; + } + if (GNUNET_OK != GNUNET_TESTING_peer_start (peer->details.local.peer)) + { + GST_send_operation_fail_msg (client, GNUNET_ntohll (msg->operation_id), + "Failed to start"); + GNUNET_SERVER_receive_done (client, GNUNET_OK); + return; + } + peer->details.local.is_running = GNUNET_YES; + reply = GNUNET_malloc (sizeof (struct GNUNET_TESTBED_PeerEventMessage)); + reply->header.type = htons (GNUNET_MESSAGE_TYPE_TESTBED_PEER_EVENT); + reply->header.size = htons (sizeof (struct GNUNET_TESTBED_PeerEventMessage)); + reply->event_type = htonl (GNUNET_TESTBED_ET_PEER_START); + reply->host_id = htonl (GST_context->host_id); + reply->peer_id = msg->peer_id; + reply->operation_id = msg->operation_id; + GST_queue_message (client, &reply->header); + GNUNET_SERVER_receive_done (client, GNUNET_OK); +} + + +/** + * Message handler for GNUNET_MESSAGE_TYPE_TESTBED_DESTROYPEER messages + * + * @param cls NULL + * @param client identification of the client + * @param message the actual message + */ +static void +handle_peer_stop (void *cls, struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) +{ + const struct GNUNET_TESTBED_PeerStopMessage *msg; + struct GNUNET_TESTBED_PeerEventMessage *reply; + struct ForwardedOperationContext *fopc; + struct Peer *peer; + uint32_t peer_id; + + msg = (const struct GNUNET_TESTBED_PeerStopMessage *) message; + peer_id = ntohl (msg->peer_id); + LOG (GNUNET_ERROR_TYPE_DEBUG, "Received PEER_STOP for peer %u\n", peer_id); + if ((peer_id >= GST_peer_list_size) || (NULL == GST_peer_list[peer_id])) + { + GST_send_operation_fail_msg (client, GNUNET_ntohll (msg->operation_id), + "Peer not found"); + GNUNET_SERVER_receive_done (client, GNUNET_OK); + return; + } + peer = GST_peer_list[peer_id]; + if (GNUNET_YES == peer->is_remote) + { + LOG (GNUNET_ERROR_TYPE_DEBUG, "Forwarding PEER_STOP for peer %u\n", + peer_id); + fopc = GNUNET_malloc (sizeof (struct ForwardedOperationContext)); + GNUNET_SERVER_client_keep (client); + fopc->client = client; + fopc->operation_id = GNUNET_ntohll (msg->operation_id); + fopc->type = OP_PEER_STOP; + fopc->opc = + GNUNET_TESTBED_forward_operation_msg_ (peer->details.remote. + slave->controller, + fopc->operation_id, &msg->header, + &GST_forwarded_operation_reply_relay, + fopc); + fopc->timeout_task = + GNUNET_SCHEDULER_add_delayed (TIMEOUT, &GST_forwarded_operation_timeout, + fopc); + GNUNET_CONTAINER_DLL_insert_tail (fopcq_head, fopcq_tail, fopc); + GNUNET_SERVER_receive_done (client, GNUNET_OK); + return; + } + if (GNUNET_OK != GNUNET_TESTING_peer_stop (peer->details.local.peer)) + { + LOG (GNUNET_ERROR_TYPE_WARNING, "Stopping peer %u failed\n", peer_id); + GST_send_operation_fail_msg (client, GNUNET_ntohll (msg->operation_id), + "Peer not running"); + GNUNET_SERVER_receive_done (client, GNUNET_OK); + return; + } + LOG (GNUNET_ERROR_TYPE_DEBUG, "Peer %u successfully stopped\n", peer_id); + peer->details.local.is_running = GNUNET_NO; + reply = GNUNET_malloc (sizeof (struct GNUNET_TESTBED_PeerEventMessage)); + reply->header.type = htons (GNUNET_MESSAGE_TYPE_TESTBED_PEER_EVENT); + reply->header.size = htons (sizeof (struct GNUNET_TESTBED_PeerEventMessage)); + reply->event_type = htonl (GNUNET_TESTBED_ET_PEER_STOP); + reply->host_id = htonl (GST_context->host_id); + reply->peer_id = msg->peer_id; + reply->operation_id = msg->operation_id; + GST_queue_message (client, &reply->header); + GNUNET_SERVER_receive_done (client, GNUNET_OK); +} + + +/** + * Handler for GNUNET_MESSAGE_TYPE_TESTBED_GETPEERCONFIG messages + * + * @param cls NULL + * @param client identification of the client + * @param message the actual message + */ +static void +handle_peer_get_config (void *cls, struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) +{ + const struct GNUNET_TESTBED_PeerGetConfigurationMessage *msg; + struct GNUNET_TESTBED_PeerConfigurationInformationMessage *reply; + struct Peer *peer; + char *config; + char *xconfig; + size_t c_size; + size_t xc_size; + uint32_t peer_id; + uint16_t msize; + + msg = (const struct GNUNET_TESTBED_PeerGetConfigurationMessage *) message; + peer_id = ntohl (msg->peer_id); + if ((peer_id >= GST_peer_list_size) || (NULL == GST_peer_list[peer_id])) + { + GST_send_operation_fail_msg (client, GNUNET_ntohll (msg->operation_id), + "Peer not found"); + GNUNET_SERVER_receive_done (client, GNUNET_OK); + return; + } + peer = GST_peer_list[peer_id]; + if (GNUNET_YES == peer->is_remote) + { + struct ForwardedOperationContext *fopc; + + LOG_DEBUG ("Forwarding PEER_GET_CONFIG for peer: %u\n", peer_id); + fopc = GNUNET_malloc (sizeof (struct ForwardedOperationContext)); + GNUNET_SERVER_client_keep (client); + fopc->client = client; + fopc->operation_id = GNUNET_ntohll (msg->operation_id); + fopc->type = OP_PEER_INFO; + fopc->opc = + GNUNET_TESTBED_forward_operation_msg_ (peer->details.remote. + slave->controller, + fopc->operation_id, &msg->header, + &GST_forwarded_operation_reply_relay, + fopc); + fopc->timeout_task = + GNUNET_SCHEDULER_add_delayed (TIMEOUT, &GST_forwarded_operation_timeout, + fopc); + GNUNET_CONTAINER_DLL_insert_tail (fopcq_head, fopcq_tail, fopc); + GNUNET_SERVER_receive_done (client, GNUNET_OK); + return; + } + LOG_DEBUG ("Received PEER_GET_CONFIG for peer: %u\n", peer_id); + config = + GNUNET_CONFIGURATION_serialize (GST_peer_list[peer_id]->details.local.cfg, + &c_size); + xc_size = GNUNET_TESTBED_compress_config_ (config, c_size, &xconfig); + GNUNET_free (config); + msize = + xc_size + + sizeof (struct GNUNET_TESTBED_PeerConfigurationInformationMessage); + reply = GNUNET_realloc (xconfig, msize); + (void) memmove (&reply[1], reply, xc_size); + reply->header.size = htons (msize); + reply->header.type = htons (GNUNET_MESSAGE_TYPE_TESTBED_PEER_CONFIGURATION); + reply->peer_id = msg->peer_id; + reply->operation_id = msg->operation_id; + GNUNET_TESTING_peer_get_identity (GST_peer_list[peer_id]->details.local.peer, + &reply->peer_identity); + reply->config_size = htons ((uint16_t) c_size); + GST_queue_message (client, &reply->header); + GNUNET_SERVER_receive_done (client, GNUNET_OK); +} + + +/** + * Handler for GNUNET_MESSAGE_TYPE_TESTBED_GETSLAVECONFIG messages + * + * @param cls NULL + * @param client identification of the client + * @param message the actual message + */ +static void +handle_slave_get_config (void *cls, struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) +{ + struct GNUNET_TESTBED_SlaveGetConfigurationMessage *msg; + struct Slave *slave; + struct GNUNET_TESTBED_SlaveConfiguration *reply; + char *config; + char *xconfig; + size_t config_size; + size_t xconfig_size; + size_t reply_size; + uint64_t op_id; + uint32_t slave_id; + + msg = (struct GNUNET_TESTBED_SlaveGetConfigurationMessage *) message; + slave_id = ntohl (msg->slave_id); + op_id = GNUNET_ntohll (msg->operation_id); + if ((GST_slave_list_size <= slave_id) || (NULL == GST_slave_list[slave_id])) + { + /* FIXME: Add forwardings for this type of message here.. */ + GST_send_operation_fail_msg (client, op_id, "Slave not found"); + GNUNET_SERVER_receive_done (client, GNUNET_OK); + return; + } + slave = GST_slave_list[slave_id]; + if (NULL == slave->cfg) + { + GST_send_operation_fail_msg (client, op_id, + "Configuration not found (slave not started by me)"); + GNUNET_SERVER_receive_done (client, GNUNET_OK); + return; + } + config = GNUNET_CONFIGURATION_serialize (slave->cfg, &config_size); + xconfig_size = + GNUNET_TESTBED_compress_config_ (config, config_size, &xconfig); + GNUNET_free (config); + reply_size = xconfig_size + sizeof (struct GNUNET_TESTBED_SlaveConfiguration); + GNUNET_break (reply_size <= UINT16_MAX); + GNUNET_break (config_size <= UINT16_MAX); + reply = GNUNET_realloc (xconfig, reply_size); + (void) memmove (&reply[1], reply, xconfig_size); + reply->header.type = htons (GNUNET_MESSAGE_TYPE_TESTBED_SLAVE_CONFIGURATION); + reply->header.size = htons ((uint16_t) reply_size); + reply->slave_id = msg->slave_id; + reply->operation_id = msg->operation_id; + reply->config_size = htons ((uint16_t) config_size); + GST_queue_message (client, &reply->header); + GNUNET_SERVER_receive_done (client, GNUNET_OK); +} + + +/** + * Iterator over hash map entries. + * + * @param cls closure + * @param key current key code + * @param value value in the hash map + * @return GNUNET_YES if we should continue to + * iterate, + * GNUNET_NO if not. + */ +static int +ss_map_free_iterator (void *cls, const struct GNUNET_HashCode *key, void *value) +{ + struct SharedService *ss = value; + + GNUNET_assert (GNUNET_YES == + GNUNET_CONTAINER_multihashmap_remove (ss_map, key, value)); + GNUNET_free (ss->name); + GNUNET_free (ss); + return GNUNET_YES; +} + + +/** + * Iterator for freeing hash map entries in a slave's reghost_map + * + * @param cls handle to the slave + * @param key current key code + * @param value value in the hash map + * @return GNUNET_YES if we should continue to + * iterate, + * GNUNET_NO if not. + */ +static int +reghost_free_iterator (void *cls, const struct GNUNET_HashCode *key, + void *value) +{ + struct Slave *slave = cls; + struct RegisteredHostContext *rhc = value; + struct ForwardedOverlayConnectContext *focc; + + GNUNET_assert (GNUNET_YES == + GNUNET_CONTAINER_multihashmap_remove (slave->reghost_map, key, + value)); + while (NULL != (focc = rhc->focc_dll_head)) + { + GNUNET_CONTAINER_DLL_remove (rhc->focc_dll_head, rhc->focc_dll_tail, focc); + GST_cleanup_focc (focc); + } + if (NULL != rhc->sub_op) + GNUNET_TESTBED_operation_done (rhc->sub_op); + if (NULL != rhc->client) + GNUNET_SERVER_client_drop (rhc->client); + GNUNET_free (value); + return GNUNET_YES; +} + + +/** + * Task to clean up and shutdown nicely + * + * @param cls NULL + * @param tc the TaskContext from scheduler + */ +static void +shutdown_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct LCFContextQueue *lcfq; + struct ForwardedOperationContext *fopc; + struct MessageQueue *mq_entry; + uint32_t id; + + shutdown_task_id = GNUNET_SCHEDULER_NO_TASK; + LOG (GNUNET_ERROR_TYPE_DEBUG, "Shutting down testbed service\n"); + (void) GNUNET_CONTAINER_multihashmap_iterate (ss_map, &ss_map_free_iterator, + NULL); + GNUNET_CONTAINER_multihashmap_destroy (ss_map); + /* cleanup any remaining forwarded operations */ + while (NULL != (fopc = fopcq_head)) + { + GNUNET_CONTAINER_DLL_remove (fopcq_head, fopcq_tail, fopc); + GNUNET_TESTBED_forward_operation_msg_cancel_ (fopc->opc); + if (GNUNET_SCHEDULER_NO_TASK != fopc->timeout_task) + GNUNET_SCHEDULER_cancel (fopc->timeout_task); + GNUNET_SERVER_client_drop (fopc->client); + switch (fopc->type) + { + case OP_PEER_CREATE: + GNUNET_free (fopc->cls); + break; + case OP_PEER_START: + case OP_PEER_STOP: + case OP_PEER_DESTROY: + case OP_PEER_INFO: + case OP_OVERLAY_CONNECT: + case OP_LINK_CONTROLLERS: + case OP_GET_SLAVE_CONFIG: + break; + case OP_FORWARDED: + GNUNET_assert (0); + }; + GNUNET_free (fopc); + } + if (NULL != lcfq_head) + { + if (GNUNET_SCHEDULER_NO_TASK != lcf_proc_task_id) + { + GNUNET_SCHEDULER_cancel (lcf_proc_task_id); + lcf_proc_task_id = GNUNET_SCHEDULER_NO_TASK; + } + } + GNUNET_assert (GNUNET_SCHEDULER_NO_TASK == lcf_proc_task_id); + for (lcfq = lcfq_head; NULL != lcfq; lcfq = lcfq_head) + { + GNUNET_free (lcfq->lcf->msg); + GNUNET_free (lcfq->lcf); + GNUNET_CONTAINER_DLL_remove (lcfq_head, lcfq_tail, lcfq); + GNUNET_free (lcfq); + } + GST_free_occq (); + GST_free_roccq (); + /* Clear peer list */ + for (id = 0; id < GST_peer_list_size; id++) + if (NULL != GST_peer_list[id]) + { + /* If destroy flag is set it means that this peer should have been + * destroyed by a context which we destroy before */ + GNUNET_break (GNUNET_NO == GST_peer_list[id]->destroy_flag); + /* counter should be zero as we free all contexts before */ + GNUNET_break (0 == GST_peer_list[id]->reference_cnt); + if ((GNUNET_NO == GST_peer_list[id]->is_remote) && + (GNUNET_YES == GST_peer_list[id]->details.local.is_running)) + GNUNET_TESTING_peer_kill (GST_peer_list[id]->details.local.peer); + } + for (id = 0; id < GST_peer_list_size; id++) + if (NULL != GST_peer_list[id]) + { + if (GNUNET_NO == GST_peer_list[id]->is_remote) + { + if (GNUNET_YES == GST_peer_list[id]->details.local.is_running) + GNUNET_TESTING_peer_wait (GST_peer_list[id]->details.local.peer); + GNUNET_TESTING_peer_destroy (GST_peer_list[id]->details.local.peer); + GNUNET_CONFIGURATION_destroy (GST_peer_list[id]->details.local.cfg); + } + GNUNET_free (GST_peer_list[id]); + } + GNUNET_free_non_null (GST_peer_list); + /* Clear host list */ + for (id = 0; id < GST_host_list_size; id++) + if (NULL != GST_host_list[id]) + GNUNET_TESTBED_host_destroy (GST_host_list[id]); + GNUNET_free_non_null (GST_host_list); + /* Clear route list */ + for (id = 0; id < route_list_size; id++) + if (NULL != route_list[id]) + GNUNET_free (route_list[id]); + GNUNET_free_non_null (route_list); + /* Clear GST_slave_list */ + for (id = 0; id < GST_slave_list_size; id++) + if (NULL != GST_slave_list[id]) + { + struct HostRegistration *hr_entry; + + while (NULL != (hr_entry = GST_slave_list[id]->hr_dll_head)) + { + GNUNET_CONTAINER_DLL_remove (GST_slave_list[id]->hr_dll_head, + GST_slave_list[id]->hr_dll_tail, hr_entry); + GNUNET_free (hr_entry); + } + if (NULL != GST_slave_list[id]->rhandle) + GNUNET_TESTBED_cancel_registration (GST_slave_list[id]->rhandle); + (void) + GNUNET_CONTAINER_multihashmap_iterate (GST_slave_list + [id]->reghost_map, + reghost_free_iterator, + GST_slave_list[id]); + GNUNET_CONTAINER_multihashmap_destroy (GST_slave_list[id]->reghost_map); + if (NULL != GST_slave_list[id]->cfg) + GNUNET_CONFIGURATION_destroy (GST_slave_list[id]->cfg); + if (NULL != GST_slave_list[id]->controller) + GNUNET_TESTBED_controller_disconnect (GST_slave_list[id]->controller); + if (NULL != GST_slave_list[id]->controller_proc) + GNUNET_TESTBED_controller_stop (GST_slave_list[id]->controller_proc); + GNUNET_free (GST_slave_list[id]); + } + GNUNET_free_non_null (GST_slave_list); + if (NULL != GST_context) + { + GNUNET_free_non_null (GST_context->master_ip); + if (NULL != GST_context->system) + GNUNET_TESTING_system_destroy (GST_context->system, GNUNET_YES); + GNUNET_SERVER_client_drop (GST_context->client); + GNUNET_free (GST_context); + GST_context = NULL; + } + if (NULL != transmit_handle) + GNUNET_SERVER_notify_transmit_ready_cancel (transmit_handle); + while (NULL != (mq_entry = mq_head)) + { + GNUNET_free (mq_entry->msg); + GNUNET_SERVER_client_drop (mq_entry->client); + GNUNET_CONTAINER_DLL_remove (mq_head, mq_tail, mq_entry); + GNUNET_free (mq_entry); + } + GNUNET_free_non_null (hostname); + GNUNET_CONFIGURATION_destroy (our_config); + /* Free hello cache */ + GST_cache_clear (); + GNUNET_TESTBED_operation_queue_destroy_ (GST_opq_openfds); + GST_opq_openfds = NULL; +} + + +/** + * Callback for client disconnect + * + * @param cls NULL + * @param client the client which has disconnected + */ +static void +client_disconnect_cb (void *cls, struct GNUNET_SERVER_Client *client) +{ + if (NULL == GST_context) + return; + if (client == GST_context->client) + { + LOG (GNUNET_ERROR_TYPE_DEBUG, "Master client disconnected\n"); + /* should not be needed as we're terminated by failure to read + * from stdin, but if stdin fails for some reason, this shouldn't + * hurt for now --- might need to revise this later if we ever + * decide that master connections might be temporarily down + * for some reason */ + //GNUNET_SCHEDULER_shutdown (); + } +} + + +/** + * Testbed setup + * + * @param cls closure + * @param server the initialized server + * @param cfg configuration to use + */ +static void +testbed_run (void *cls, struct GNUNET_SERVER_Handle *server, + const struct GNUNET_CONFIGURATION_Handle *cfg) +{ + static const struct GNUNET_SERVER_MessageHandler message_handlers[] = { + {&handle_init, NULL, GNUNET_MESSAGE_TYPE_TESTBED_INIT, 0}, + {&handle_add_host, NULL, GNUNET_MESSAGE_TYPE_TESTBED_ADD_HOST, 0}, + {&handle_configure_shared_service, NULL, + GNUNET_MESSAGE_TYPE_TESTBED_SHARE_SERVICE, 0}, + {&handle_link_controllers, NULL, + GNUNET_MESSAGE_TYPE_TESTBED_LINK_CONTROLLERS, 0}, + {&handle_peer_create, NULL, GNUNET_MESSAGE_TYPE_TESTBED_CREATE_PEER, 0}, + {&handle_peer_destroy, NULL, GNUNET_MESSAGE_TYPE_TESTBED_DESTROY_PEER, + sizeof (struct GNUNET_TESTBED_PeerDestroyMessage)}, + {&handle_peer_start, NULL, GNUNET_MESSAGE_TYPE_TESTBED_START_PEER, + sizeof (struct GNUNET_TESTBED_PeerStartMessage)}, + {&handle_peer_stop, NULL, GNUNET_MESSAGE_TYPE_TESTBED_STOP_PEER, + sizeof (struct GNUNET_TESTBED_PeerStopMessage)}, + {&handle_peer_get_config, NULL, + GNUNET_MESSAGE_TYPE_TESTBED_GET_PEER_CONFIGURATION, + sizeof (struct GNUNET_TESTBED_PeerGetConfigurationMessage)}, + {&GST_handle_overlay_connect, NULL, + GNUNET_MESSAGE_TYPE_TESTBED_OVERLAY_CONNECT, + sizeof (struct GNUNET_TESTBED_OverlayConnectMessage)}, + {&GST_handle_remote_overlay_connect, NULL, + GNUNET_MESSAGE_TYPE_TESTBED_REMOTE_OVERLAY_CONNECT, 0}, + {handle_slave_get_config, NULL, + GNUNET_MESSAGE_TYPE_TESTBED_GET_SLAVE_CONFIGURATION, + sizeof (struct GNUNET_TESTBED_SlaveGetConfigurationMessage)}, + {NULL} + }; + char *logfile; + unsigned long long num; + + if (GNUNET_OK == + GNUNET_CONFIGURATION_get_value_filename (cfg, "TESTBED", "LOG_FILE", + &logfile)) + { + GNUNET_break (GNUNET_OK == GNUNET_log_setup ("testbed", "DEBUG", logfile)); + GNUNET_free (logfile); + } + GNUNET_assert (GNUNET_OK == + GNUNET_CONFIGURATION_get_value_number (cfg, "TESTBED", + "CACHE_SIZE", &num)); + GST_cache_init ((unsigned int) num); + GNUNET_assert (GNUNET_OK == + GNUNET_CONFIGURATION_get_value_number (cfg, "TESTBED", + "MAX_OPEN_FDS", &num)); + GST_opq_openfds = GNUNET_TESTBED_operation_queue_create_ ((unsigned int) num); + GNUNET_assert (GNUNET_OK == + GNUNET_CONFIGURATION_get_value_string (cfg, "testbed", + "HOSTNAME", &hostname)); + our_config = GNUNET_CONFIGURATION_dup (cfg); + GNUNET_SERVER_add_handlers (server, message_handlers); + GNUNET_SERVER_disconnect_notify (server, &client_disconnect_cb, NULL); + ss_map = GNUNET_CONTAINER_multihashmap_create (5, GNUNET_NO); + shutdown_task_id = + GNUNET_SCHEDULER_add_delayed_with_priority (GNUNET_TIME_UNIT_FOREVER_REL, + GNUNET_SCHEDULER_PRIORITY_IDLE, + &shutdown_task, NULL); + LOG_DEBUG ("Testbed startup complete\n"); + event_mask = 1LL << GNUNET_TESTBED_ET_OPERATION_FINISHED; +} + + +/** + * The starting point of execution + */ +int +main (int argc, char *const *argv) +{ + //sleep (15); /* Debugging */ + return (GNUNET_OK == + GNUNET_SERVICE_run (argc, argv, "testbed", GNUNET_SERVICE_OPTION_NONE, + &testbed_run, NULL)) ? 0 : 1; +} + +/* end of gnunet-service-testbed.c */ diff --git a/src/testbed/gnunet-service-testbed.h b/src/testbed/gnunet-service-testbed.h new file mode 100644 index 0000000..ebf3c66 --- /dev/null +++ b/src/testbed/gnunet-service-testbed.h @@ -0,0 +1,911 @@ +/* + This file is part of GNUnet. + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 2, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @file testbed/gnunet-service-testbed.h + * @brief data structures shared amongst components of TESTBED service + * @author Sree Harsha Totakura + */ + +#include "platform.h" +#include "gnunet_util_lib.h" +#include "gnunet_testbed_service.h" +#include "gnunet_transport_service.h" +#include "gnunet_core_service.h" + +#include "testbed.h" +#include "testbed_api.h" +#include "testbed_api_operations.h" +#include "testbed_api_hosts.h" +#include "gnunet_testing_lib.h" + + +/** + * Generic logging + */ +#define LOG(kind,...) \ + GNUNET_log (kind, __VA_ARGS__) + +/** + * Debug logging + */ +#define LOG_DEBUG(...) \ + LOG (GNUNET_ERROR_TYPE_DEBUG, __VA_ARGS__) + +/** + * By how much should the arrays lists grow + */ +#define LIST_GROW_STEP 10 + +/** + * Default timeout for operations which may take some time + */ +#define TIMEOUT GNUNET_TIME_relative_multiply(GNUNET_TIME_UNIT_SECONDS, 15) + + +/** + * A routing entry + */ +struct Route +{ + /** + * destination host + */ + uint32_t dest; + + /** + * The destination host is reachable thru + */ + uint32_t thru; +}; + + +/** + * Context information for operations forwarded to subcontrollers + */ +struct ForwardedOperationContext +{ + /** + * The next pointer for DLL + */ + struct ForwardedOperationContext *next; + + /** + * The prev pointer for DLL + */ + struct ForwardedOperationContext *prev; + + /** + * The generated operation context + */ + struct OperationContext *opc; + + /** + * The client to which we have to reply + */ + struct GNUNET_SERVER_Client *client; + + /** + * Closure pointer + */ + void *cls; + + /** + * Task ID for the timeout task + */ + GNUNET_SCHEDULER_TaskIdentifier timeout_task; + + /** + * The id of the operation that has been forwarded + */ + uint64_t operation_id; + + /** + * The type of the operation which is forwarded + */ + enum OperationType type; + +}; + + +/** + * A DLL of host registrations to be made + */ +struct HostRegistration +{ + /** + * next registration in the DLL + */ + struct HostRegistration *next; + + /** + * previous registration in the DLL + */ + struct HostRegistration *prev; + + /** + * The callback to call after this registration's status is available + */ + GNUNET_TESTBED_HostRegistrationCompletion cb; + + /** + * The closure for the above callback + */ + void *cb_cls; + + /** + * The host that has to be registered + */ + struct GNUNET_TESTBED_Host *host; +}; + + +/** + * Context information used while linking controllers + */ +struct LinkControllersContext +{ + /** + * The client which initiated the link controller operation + */ + struct GNUNET_SERVER_Client *client; + + /** + * The ID of the operation + */ + uint64_t operation_id; + +}; + + +/** + * Structure representing a connected(directly-linked) controller + */ +struct Slave +{ + /** + * The controller process handle if we had started the controller + */ + struct GNUNET_TESTBED_ControllerProc *controller_proc; + + /** + * The controller handle + */ + struct GNUNET_TESTBED_Controller *controller; + + /** + * The configuration of the slave. Cannot be NULL + */ + struct GNUNET_CONFIGURATION_Handle *cfg; + + /** + * handle to lcc which is associated with this slave startup. Should be set to + * NULL when the slave has successfully started up + */ + struct LinkControllersContext *lcc; + + /** + * Head of the host registration DLL + */ + struct HostRegistration *hr_dll_head; + + /** + * Tail of the host registration DLL + */ + struct HostRegistration *hr_dll_tail; + + /** + * The current host registration handle + */ + struct GNUNET_TESTBED_HostRegistrationHandle *rhandle; + + /** + * Hashmap to hold Registered host contexts + */ + struct GNUNET_CONTAINER_MultiHashMap *reghost_map; + + /** + * The id of the host this controller is running on + */ + uint32_t host_id; + +}; + + +/** + * A peer + */ + +struct Peer +{ + + union + { + struct + { + /** + * The peer handle from testing API + */ + struct GNUNET_TESTING_Peer *peer; + + /** + * The modified (by GNUNET_TESTING_peer_configure) configuration this + * peer is configured with + */ + struct GNUNET_CONFIGURATION_Handle *cfg; + + /** + * Is the peer running + */ + int is_running; + + } local; + + struct + { + /** + * The slave this peer is started through + */ + struct Slave *slave; + + /** + * The id of the remote host this peer is running on + */ + uint32_t remote_host_id; + + } remote; + + } details; + + /** + * Is this peer locally created? + */ + int is_remote; + + /** + * Our local reference id for this peer + */ + uint32_t id; + + /** + * References to peers are using in forwarded overlay contexts and remote + * overlay connect contexts. A peer can only be destroyed after all such + * contexts are destroyed. For this, we maintain a reference counter. When we + * use a peer in any such context, we increment this counter. We decrement it + * when we are destroying these contexts + */ + uint32_t reference_cnt; + + /** + * While destroying a peer, due to the fact that there could be references to + * this peer, we delay the peer destroy to a further time. We do this by using + * this flag to destroy the peer while destroying a context in which this peer + * has been used. When the flag is set to 1 and reference_cnt = 0 we destroy + * the peer + */ + uint32_t destroy_flag; + +}; + + +/** + * The main context information associated with the client which started us + */ +struct Context +{ + /** + * The client handle associated with this context + */ + struct GNUNET_SERVER_Client *client; + + /** + * The network address of the master controller + */ + char *master_ip; + + /** + * The TESTING system handle for starting peers locally + */ + struct GNUNET_TESTING_System *system; + + /** + * Our host id according to this context + */ + uint32_t host_id; +}; + + +/** + * The structure for identifying a shared service + */ +struct SharedService +{ + /** + * The name of the shared service + */ + char *name; + + /** + * Number of shared peers per instance of the shared service + */ + uint32_t num_shared; + + /** + * Number of peers currently sharing the service + */ + uint32_t num_sharing; +}; + + +/** + * Context information to used during operations which forward the overlay + * connect message + */ +struct ForwardedOverlayConnectContext +{ + /** + * next ForwardedOverlayConnectContext in the DLL + */ + struct ForwardedOverlayConnectContext *next; + + /** + * previous ForwardedOverlayConnectContext in the DLL + */ + struct ForwardedOverlayConnectContext *prev; + + /** + * A copy of the original overlay connect message + */ + struct GNUNET_MessageHeader *orig_msg; + + /** + * The id of the operation which created this context information + */ + uint64_t operation_id; + + /** + * the id of peer 1 + */ + uint32_t peer1; + + /** + * The id of peer 2 + */ + uint32_t peer2; + + /** + * Id of the host where peer2 is running + */ + uint32_t peer2_host_id; +}; + + +/** + * This context information will be created for each host that is registered at + * slave controllers during overlay connects. + */ +struct RegisteredHostContext +{ + /** + * The host which is being registered + */ + struct GNUNET_TESTBED_Host *reg_host; + + /** + * The host of the controller which has to connect to the above rhost + */ + struct GNUNET_TESTBED_Host *host; + + /** + * The gateway to which this operation is forwarded to + */ + struct Slave *gateway; + + /** + * The gateway through which peer2's controller can be reached + */ + struct Slave *gateway2; + + /** + * Handle for sub-operations + */ + struct GNUNET_TESTBED_Operation *sub_op; + + /** + * The client which initiated the link controller operation + */ + struct GNUNET_SERVER_Client *client; + + /** + * Head of the ForwardedOverlayConnectContext DLL + */ + struct ForwardedOverlayConnectContext *focc_dll_head; + + /** + * Tail of the ForwardedOverlayConnectContext DLL + */ + struct ForwardedOverlayConnectContext *focc_dll_tail; + + /** + * Enumeration of states for this context + */ + enum RHCState + { + + /** + * The initial state + */ + RHC_INIT = 0, + + /** + * State where we attempt to get peer2's controller configuration + */ + RHC_GET_CFG, + + /** + * State where we attempt to link the controller of peer 1 to the controller + * of peer2 + */ + RHC_LINK, + + /** + * State where we attempt to do the overlay connection again + */ + RHC_OL_CONNECT + } state; + +}; + + +/** + * States of LCFContext + */ +enum LCFContextState +{ + /** + * The Context has been initialized; Nothing has been done on it + */ + INIT, + + /** + * Delegated host has been registered at the forwarding controller + */ + DELEGATED_HOST_REGISTERED, + + /** + * The slave host has been registred at the forwarding controller + */ + SLAVE_HOST_REGISTERED, + + /** + * The context has been finished (may have error) + */ + FINISHED +}; + + +/** + * Link controllers request forwarding context + */ +struct LCFContext +{ + /** + * The gateway which will pass the link message to delegated host + */ + struct Slave *gateway; + + /** + * The controller link message that has to be forwarded to + */ + struct GNUNET_TESTBED_ControllerLinkMessage *msg; + + /** + * The client which has asked to perform this operation + */ + struct GNUNET_SERVER_Client *client; + + /** + * Handle for operations which are forwarded while linking controllers + */ + struct ForwardedOperationContext *fopc; + + /** + * The id of the operation which created this context + */ + uint64_t operation_id; + + /** + * The state of this context + */ + enum LCFContextState state; + + /** + * The delegated host + */ + uint32_t delegated_host_id; + + /** + * The slave host + */ + uint32_t slave_host_id; + +}; + + +/** + * Structure of a queue entry in LCFContext request queue + */ +struct LCFContextQueue +{ + /** + * The LCFContext + */ + struct LCFContext *lcf; + + /** + * Head prt for DLL + */ + struct LCFContextQueue *next; + + /** + * Tail ptr for DLL + */ + struct LCFContextQueue *prev; +}; + +/** + * Our configuration + */ +struct GNUNET_CONFIGURATION_Handle *our_config; + +/** + * The master context; generated with the first INIT message + */ +extern struct Context *GST_context; + +/** + * DLL head for forwarded operation contexts + */ +extern struct ForwardedOperationContext *fopcq_head; + +/** + * DLL tail for forwarded operation contexts + */ +extern struct ForwardedOperationContext *fopcq_tail; + +/** + * A list of peers we know about + */ +extern struct Peer **GST_peer_list; + +/** + * Array of hosts + */ +extern struct GNUNET_TESTBED_Host **GST_host_list; + +/** + * A list of directly linked neighbours + */ +extern struct Slave **GST_slave_list; + +/** + * Operation queue for open file descriptors + */ +extern struct OperationQueue *GST_opq_openfds; + +/** + * The size of the peer list + */ +extern unsigned int GST_peer_list_size; + +/** + * The size of the host list + */ +extern unsigned int GST_host_list_size; + +/** + * The size of directly linked neighbours list + */ +extern unsigned int GST_slave_list_size; + + +/** + * Queues a message in send queue for sending to the service + * + * @param client the client to whom the queued message has to be sent + * @param msg the message to queue + */ +void +GST_queue_message (struct GNUNET_SERVER_Client *client, + struct GNUNET_MessageHeader *msg); + + +/** + * Function to destroy a peer + * + * @param peer the peer structure to destroy + */ +void +GST_destroy_peer (struct Peer *peer); + + +/** + * Finds the route with directly connected host as destination through which + * the destination host can be reached + * + * @param host_id the id of the destination host + * @return the route with directly connected destination host; NULL if no route + * is found + */ +struct Route * +GST_find_dest_route (uint32_t host_id); + + +/** + * Handler for GNUNET_MESSAGE_TYPE_TESTBED_OLCONNECT messages + * + * @param cls NULL + * @param client identification of the client + * @param message the actual message + */ +void +GST_handle_overlay_connect (void *cls, struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message); + + +/** + * Adds a host registration's request to a slave's registration queue + * + * @param slave the slave controller at which the given host has to be + * registered + * @param cb the host registration completion callback + * @param cb_cls the closure for the host registration completion callback + * @param host the host which has to be registered + */ +void +GST_queue_host_registration (struct Slave *slave, + GNUNET_TESTBED_HostRegistrationCompletion cb, + void *cb_cls, struct GNUNET_TESTBED_Host *host); + + +/** + * Callback to relay the reply msg of a forwarded operation back to the client + * + * @param cls ForwardedOperationContext + * @param msg the message to relay + */ +void +GST_forwarded_operation_reply_relay (void *cls, + const struct GNUNET_MessageHeader *msg); + + +/** + * Task to free resources when forwarded operation has been timedout + * + * @param cls the ForwardedOperationContext + * @param tc the task context from scheduler + */ +void +GST_forwarded_operation_timeout (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc); + + +/** + * Send operation failure message to client + * + * @param client the client to which the failure message has to be sent to + * @param operation_id the id of the failed operation + * @param emsg the error message; can be NULL + */ +void +GST_send_operation_fail_msg (struct GNUNET_SERVER_Client *client, + uint64_t operation_id, const char *emsg); + + +/** + * Handler for GNUNET_MESSAGE_TYPE_TESTBED_REQUESTCONNECT messages + * + * @param cls NULL + * @param client identification of the client + * @param message the actual message + */ +void +GST_handle_remote_overlay_connect (void *cls, + struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message); + + +/** + * Processes a forwarded overlay connect context in the queue of the given RegisteredHostContext + * + * @param rhc the RegisteredHostContext + */ +void +GST_process_next_focc (struct RegisteredHostContext *rhc); + + +/** + * Cleans up ForwardedOverlayConnectContext + * + * @param focc the ForwardedOverlayConnectContext to cleanup + */ +void +GST_cleanup_focc (struct ForwardedOverlayConnectContext *focc); + + +/** + * Clears all pending overlay connect contexts in queue + */ +void +GST_free_occq (); + + +/** + * Clears all pending remote overlay connect contexts in queue + */ +void +GST_free_roccq (); + + +/** + * Initializes the cache + * + * @param size the size of the cache + */ +void +GST_cache_init (unsigned int size); + + +/** + * Clear cache + */ +void +GST_cache_clear (); + + +/** + * Looks up in the hello cache and returns the HELLO of the given peer + * + * @param peer_id the index of the peer whose HELLO has to be looked up + * @return the HELLO message; NULL if not found + */ +const struct GNUNET_MessageHeader * +GST_cache_lookup_hello (const unsigned int peer_id); + + +/** + * Caches the HELLO of the given peer. Updates the HELLO if it was already + * cached before + * + * @param id the peer identity of the peer whose HELLO has to be cached + * @param hello the HELLO message + */ +void +GST_cache_add_hello (const unsigned int peer_id, + const struct GNUNET_MessageHeader *hello); + + +/** + * Functions of this type are called when the needed handle is available for + * usage. These functions are to be registered with either of the functions + * GST_cache_get_handle_transport() or GST_cache_get_handle_core(). The + * corresponding handles will be set and if they are not, then it signals an + * error while opening the handles. + * + * @param cls the closure passed to GST_cache_get_handle_transport() or + * GST_cache_get_handle_core() + * @param ch the handle to CORE. Can be NULL if it is not requested + * @param th the handle to TRANSPORT. Can be NULL if it is not requested + * @param peer_id the identity of the peer. Will be NULL if ch is NULL. In other + * cases, its value being NULL means that CORE connection has failed. + */ +typedef void (*GST_cache_handle_ready_cb) (void *cls, + struct GNUNET_CORE_Handle * ch, + struct GNUNET_TRANSPORT_Handle * th, + const struct GNUNET_PeerIdentity * + peer_id); + + +/** + * Callback to notify when the target peer given to + * GST_cache_get_handle_transport() is connected. Note that this callback may + * not be called if the target peer is already connected. Use + * GNUNET_TRANSPORT_check_neighbour_connected() to check if the target peer is + * already connected or not. This callback will be called only once or never (in + * case the target cannot be connected). + * + * @param cls the closure given to GST_cache_get_handle_done() for this callback + * @param target the peer identity of the target peer. The pointer should be + * valid until GST_cache_get_handle_done() is called. + */ +typedef void (*GST_cache_peer_connect_notify) (void *cls, + const struct GNUNET_PeerIdentity + * target); + + +/** + * Get a transport handle with the given configuration. If the handle is already + * cached before, it will be retured in the given callback; the peer_id is used to lookup in the + * cache. If not a new operation is started to open the transport handle and + * will be given in the callback when it is available. + * + * @param peer_id the index of the peer + * @param cfg the configuration with which the transport handle has to be + * created if it was not present in the cache + * @param cb the callback to notify when the transport handle is available + * @param cb_cls the closure for the above callback + * @param target the peer identify of the peer whose connection to our TRANSPORT + * subsystem will be notified through the connect_notify_cb. Can be NULL + * @param connect_notify_cb the callback to call when the given target peer is + * connected. This callback will only be called once or never again (in + * case the target peer cannot be connected). Can be NULL + * @param connect_notify_cb_cls the closure for the above callback + * @return the handle which can be used cancel or mark that the handle is no + * longer being used + */ +struct GSTCacheGetHandle * +GST_cache_get_handle_transport (unsigned int peer_id, + const struct GNUNET_CONFIGURATION_Handle *cfg, + GST_cache_handle_ready_cb cb, void *cb_cls, + const struct GNUNET_PeerIdentity *target, + GST_cache_peer_connect_notify connect_notify_cb, + void *connect_notify_cb_cls); + + +/** + * Get a CORE handle with the given configuration. If the handle is already + * cached before, it will be retured in the given callback; the peer_id is used + * to lookup in the cache. If the handle is not cached before, a new operation + * is started to open the CORE handle and will be given in the callback when it + * is available along with the peer identity + * + * @param peer_id the index of the peer + * @param cfg the configuration with which the transport handle has to be + * created if it was not present in the cache + * @param cb the callback to notify when the transport handle is available + * @param cb_cls the closure for the above callback + * @param target the peer identify of the peer whose connection to our CORE + * subsystem will be notified through the connect_notify_cb. Can be NULL + * @param connect_notify_cb the callback to call when the given target peer is + * connected. This callback will only be called once or never again (in + * case the target peer cannot be connected). Can be NULL + * @param connect_notify_cb_cls the closure for the above callback + * @return the handle which can be used cancel or mark that the handle is no + * longer being used + */ +struct GSTCacheGetHandle * +GST_cache_get_handle_core (unsigned int peer_id, + const struct GNUNET_CONFIGURATION_Handle *cfg, + GST_cache_handle_ready_cb cb, void *cb_cls, + const struct GNUNET_PeerIdentity *target, + GST_cache_peer_connect_notify connect_notify_cb, + void *connect_notify_cb_cls); + + +/** + * Mark the GetCacheHandle as being done if a handle has been provided already + * or as being cancelled if the callback for the handle hasn't been called. + * + * @param cgh the CacheGetHandle handle + */ +void +GST_cache_get_handle_done (struct GSTCacheGetHandle *cgh); + +/* End of gnunet-service-testbed.h */ diff --git a/src/testbed/gnunet-service-testbed_cache.c b/src/testbed/gnunet-service-testbed_cache.c new file mode 100644 index 0000000..112868e --- /dev/null +++ b/src/testbed/gnunet-service-testbed_cache.c @@ -0,0 +1,1048 @@ +/* + This file is part of GNUnet. + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 2, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @file testbed/gnunet-service-testbed_cache.h + * @brief testbed cache implementation + * @author Sree Harsha Totakura + */ +#include "gnunet-service-testbed.h" + +/** + * Redefine LOG with a changed log component string + */ +#ifdef LOG +#undef LOG +#endif +#define LOG(kind,...) \ + GNUNET_log_from (kind, "testbed-cache", __VA_ARGS__) + + +/** + * Time to expire a cache entry + */ +#define CACHE_EXPIRY \ + GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 15) + + +/** + * Type of cache-get requests + */ +enum CacheGetType +{ + /** + * Get transport handle + */ + CGT_TRANSPORT_HANDLE = 1, + + /** + * Get core handle + */ + CGT_CORE_HANDLE +}; + + +/** + * The cache-get request handle + */ +struct GSTCacheGetHandle; + + +/** + * This context structure is used to maintain a queue of notifications to check + * which of them are to be notified when a peer is connected. + */ +struct ConnectNotifyContext +{ + /** + * The next ptr for the DLL + */ + struct ConnectNotifyContext *next; + + /** + * The prev ptr for the DLL + */ + struct ConnectNotifyContext *prev; + + /** + * The peer identity of the target peer. When this target peer is connected, + * call the notify callback + */ + const struct GNUNET_PeerIdentity *target; + + /** + * The notify callback to be called when the target peer is connected + */ + GST_cache_peer_connect_notify cb; + + /** + * The closure for the notify callback + */ + void *cb_cls; + + /** + * The GSTCacheGetHandle reposible for creating this context + */ + struct GSTCacheGetHandle *cgh; + +}; + + +/** + * The cache-get request handle + */ +struct GSTCacheGetHandle +{ + /** + * The next ptr for the DLL. Used in struct CacheEntry + */ + struct GSTCacheGetHandle *next; + + /** + * The prev ptr for the DLL. Used in struct CacheEntry + */ + struct GSTCacheGetHandle *prev; + + /** + * The cache entry object this handle corresponds to + */ + struct CacheEntry *entry; + + /** + * The cache callback to call when a handle is available + */ + GST_cache_handle_ready_cb cb; + + /** + * The closure for the above callback + */ + void *cb_cls; + + /** + * The peer connect notify context created for this handle; can be NULL + */ + struct ConnectNotifyContext *nctxt; + + /** + * The type of this cache-get request + */ + enum CacheGetType type; + + /** + * Did we call the cache callback already? + */ + int notify_called; +}; + +/** + * Cache entry + */ +struct CacheEntry +{ + /** + * DLL next ptr for least recently used cache entries + */ + struct CacheEntry *next; + + /** + * DLL prev ptr for least recently used cache entries + */ + struct CacheEntry *prev; + + /** + * The transport handle to the peer corresponding to this entry; can be NULL + */ + struct GNUNET_TRANSPORT_Handle *transport_handle_; + + /** + * The operation handle for transport handle + */ + struct GNUNET_TESTBED_Operation *transport_op_; + + /** + * The core handle to the peer corresponding to this entry; can be NULL + */ + struct GNUNET_CORE_Handle *core_handle; + + /** + * The operation handle for core handle + */ + struct GNUNET_TESTBED_Operation *core_op; + + /** + * The peer identity of this peer. Will be set upon opening a connection to + * the peers CORE service. Will be NULL until then and after the CORE + * connection is closed + */ + struct GNUNET_PeerIdentity *peer_identity; + + /** + * The configuration of the peer. Should be not NULL as long as the core_handle + * or transport_handle are valid + */ + struct GNUNET_CONFIGURATION_Handle *cfg; + + /** + * The key for this entry + */ + struct GNUNET_HashCode key; + + /** + * The HELLO message + */ + struct GNUNET_MessageHeader *hello; + + /** + * the head of the CacheGetHandle queue + */ + struct GSTCacheGetHandle *cgh_qhead; + + /** + * the tail of the CacheGetHandle queue + */ + struct GSTCacheGetHandle *cgh_qtail; + + /** + * DLL head for the queue of notifications contexts to check which of them are to + * be notified when a peer is connected. + */ + struct ConnectNotifyContext *nctxt_qhead; + + /** + * DLL tail for the queue of notifications contexts to check which of them are to + * be notified when a peer is connected. + */ + struct ConnectNotifyContext *nctxt_qtail; + + /** + * The task that calls the cache callback + */ + GNUNET_SCHEDULER_TaskIdentifier notify_task; + + /** + * The task to expire this cache entry, free any handlers it has opened and + * mark their corresponding operations as done. + */ + GNUNET_SCHEDULER_TaskIdentifier expire_task; + + /** + * Number of operations this cache entry is being used + */ + unsigned int demand; + + /** + * The id of the peer this entry corresponds to + */ + unsigned int peer_id; + + /** + * Is this entry in LRU cache queue? + */ + unsigned int in_lru; +}; + + +/** + * Hashmap to maintain cache + */ +static struct GNUNET_CONTAINER_MultiHashMap *cache; + +/** + * DLL head for least recently used cache entries; least recently used + * cache items are at the head. The cache enties are added to this queue when + * their demand becomes zero. They are removed from the queue when they are + * needed by any operation. + */ +static struct CacheEntry *lru_cache_head; + +/** + * DLL tail for least recently used cache entries; recently used cache + * items are at the tail.The cache enties are added to this queue when + * their demand becomes zero. They are removed from the queue when they are + * needed by any operation. + */ +static struct CacheEntry *lru_cache_tail; + +/** + * the size of the LRU queue + */ +static unsigned int lru_cache_size; + +/** + * the threshold size for the LRU queue + */ +static unsigned int lru_cache_threshold_size; + +/** + * The total number of elements in cache + */ +static unsigned int cache_size; + + +/** + * Looks up in the cache and returns the entry + * + * @param id the peer identity of the peer whose corresponding entry has to be looked up + * @return the HELLO message; NULL if not found + */ +static struct CacheEntry * +cache_lookup (const struct GNUNET_HashCode *key) +{ + struct CacheEntry *entry; + + if (NULL == cache) + return NULL; + entry = GNUNET_CONTAINER_multihashmap_get (cache, key); + return entry; +} + + +/** + * Function to disconnect the core and transport handles; free the existing + * configuration; and remove from the LRU cache list. The entry is left to be in + * the hash table so that the HELLO can still be found later + * + * @param entry the cache entry + */ +static void +close_handles (struct CacheEntry *entry) +{ + struct ConnectNotifyContext *ctxt; + + GNUNET_assert (0 == entry->demand); + if (GNUNET_YES == entry->in_lru) + { + GNUNET_assert (0 < lru_cache_size); + if (GNUNET_SCHEDULER_NO_TASK != entry->expire_task) + { + GNUNET_SCHEDULER_cancel (entry->expire_task); + entry->expire_task = GNUNET_SCHEDULER_NO_TASK; + } + GNUNET_CONTAINER_DLL_remove (lru_cache_head, lru_cache_tail, entry); + lru_cache_size--; + entry->in_lru = GNUNET_NO; + } + GNUNET_assert (GNUNET_SCHEDULER_NO_TASK == entry->expire_task); + while (NULL != (ctxt = entry->nctxt_qhead)) + { + GNUNET_CONTAINER_DLL_remove (entry->nctxt_qhead, entry->nctxt_qtail, ctxt); + GNUNET_free (ctxt); + } + LOG_DEBUG ("Cleaning up handles from an entry in cache\n"); + if (NULL != entry->transport_handle_) + { + GNUNET_assert (NULL != entry->transport_op_); + GNUNET_TESTBED_operation_done (entry->transport_op_); + entry->transport_op_ = NULL; + } + if (NULL != entry->core_handle) + { + GNUNET_assert (NULL != entry->core_op); + GNUNET_TESTBED_operation_done (entry->core_op); + entry->core_op = NULL; + } + if (NULL != entry->cfg) + { + GNUNET_CONFIGURATION_destroy (entry->cfg); + entry->cfg = NULL; + } +} + + +/** + * The task to expire this cache entry, free any handlers it has opened and + * mark their corresponding operations as done. + * + * @param cls the CacheEntry + * @param tc the scheduler task context + */ +static void +expire_cache_entry (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct CacheEntry *entry = cls; + + GNUNET_assert (GNUNET_SCHEDULER_NO_TASK != entry->expire_task); + entry->expire_task = GNUNET_SCHEDULER_NO_TASK; + close_handles (entry); +} + + +/** + * Creates a new cache entry and then puts it into the cache's hashtable. + * + * @param key the hash code to use for inserting the newly created entry + * @param peer_id the index of the peer to tag the newly created entry + * @return the newly created entry + */ +static struct CacheEntry * +add_entry (const struct GNUNET_HashCode *key, unsigned int peer_id) +{ + struct CacheEntry *entry; + + entry = GNUNET_malloc (sizeof (struct CacheEntry)); + entry->peer_id = peer_id; + memcpy (&entry->key, key, sizeof (struct GNUNET_HashCode)); + GNUNET_assert (GNUNET_OK == + GNUNET_CONTAINER_multihashmap_put (cache, &entry->key, entry, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_FAST)); + cache_size++; + return entry; +} + + +/** + * Function to find a suitable GSTCacheGetHandle which is waiting for one of the + * handles in given entry to be available. + * + * @param entry the cache entry whose GSTCacheGetHandle list has to be searched + * @param head the starting list element in the GSTCacheGetHandle where the + * search has to be begin + * @return a suitable GSTCacheGetHandle whose handle ready notify callback + * hasn't been called yet. NULL if no such suitable GSTCacheGetHandle + * is found + */ +static struct GSTCacheGetHandle * +search_suitable_cgh (const struct CacheEntry *entry, + const struct GSTCacheGetHandle *head) +{ + const struct GSTCacheGetHandle *cgh; + + for (cgh = head; NULL != cgh; cgh = cgh->next) + { + if (GNUNET_YES == cgh->notify_called) + return NULL; + switch (cgh->type) + { + case CGT_TRANSPORT_HANDLE: + if (NULL == entry->transport_handle_) + continue; + break; + case CGT_CORE_HANDLE: + if (NULL == entry->core_handle) + continue; + break; + } + break; + } + return (struct GSTCacheGetHandle *) cgh; +} + + +/** + * Task to call the handle ready notify callback of a queued GSTCacheGetHandle + * of an entry when one or all of its handles are available. + * + * @param cls the cache entry + * @param tc the task context from scheduler + */ +static void +call_cgh_cb (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct CacheEntry *entry = cls; + struct GSTCacheGetHandle *cgh; + const struct GSTCacheGetHandle *cgh2; + + GNUNET_assert (GNUNET_SCHEDULER_NO_TASK != entry->notify_task); + entry->notify_task = GNUNET_SCHEDULER_NO_TASK; + cgh = search_suitable_cgh (entry, entry->cgh_qhead); + GNUNET_assert (NULL != cgh); + cgh2 = NULL; + if (NULL != cgh->next) + cgh2 = search_suitable_cgh (entry, cgh->next); + GNUNET_CONTAINER_DLL_remove (entry->cgh_qhead, entry->cgh_qtail, cgh); + cgh->notify_called = GNUNET_YES; + GNUNET_CONTAINER_DLL_insert_tail (entry->cgh_qhead, entry->cgh_qtail, cgh); + if (NULL != cgh2) + entry->notify_task = GNUNET_SCHEDULER_add_now (&call_cgh_cb, entry); + if (NULL != cgh->nctxt) + { /* Register the peer connect notify callback */ + GNUNET_CONTAINER_DLL_insert_tail (entry->nctxt_qhead, entry->nctxt_qtail, + cgh->nctxt); + } + LOG_DEBUG ("Calling notify for handle type %u\n", cgh->type); + cgh->cb (cgh->cb_cls, entry->core_handle, entry->transport_handle_, + entry->peer_identity); +} + + +/** + * Function called from peer connect notify callbacks from CORE and TRANSPORT + * connections. This function calls the pendning peer connect notify callbacks + * which are queued in an entry. + * + * @param cls the cache entry + * @param peer the peer that connected + * @param type the type of the handle this notification corresponds to + */ +static void +peer_connect_notify_cb (void *cls, const struct GNUNET_PeerIdentity *peer, + const enum CacheGetType type) +{ + struct CacheEntry *entry = cls; + struct ConnectNotifyContext *ctxt; + struct ConnectNotifyContext *ctxt2; + GST_cache_peer_connect_notify cb; + void *cb_cls; + + + for (ctxt = entry->nctxt_qhead; NULL != ctxt;) + { + GNUNET_assert (NULL != ctxt->cgh); + if (type != ctxt->cgh->type) + { + ctxt = ctxt->next; + continue; + } + if (0 != memcmp (ctxt->target, peer, sizeof (struct GNUNET_PeerIdentity))) + { + ctxt = ctxt->next; + continue; + } + cb = ctxt->cb; + cb_cls = ctxt->cb_cls; + ctxt->cgh->nctxt = NULL; + ctxt2 = ctxt->next; + GNUNET_CONTAINER_DLL_remove (entry->nctxt_qhead, entry->nctxt_qtail, ctxt); + GNUNET_free (ctxt); + ctxt = ctxt2; + cb (cb_cls, peer); + } + if (NULL == ctxt) + return; + +} + + +/** + * Function called to notify transport users that another + * peer connected to us. + * + * @param cls closure + * @param peer the peer that connected + * @param ats performance data + * @param ats_count number of entries in ats (excluding 0-termination) + */ +static void +transport_peer_connect_notify_cb (void *cls, + const struct GNUNET_PeerIdentity *peer, + const struct GNUNET_ATS_Information *ats, + uint32_t ats_count) +{ + peer_connect_notify_cb (cls, peer, CGT_TRANSPORT_HANDLE); +} + + +/** + * Function called when resources for opening a connection to TRANSPORT are + * available. + * + * @param cls the cache entry + */ +static void +opstart_get_handle_transport (void *cls) +{ + struct CacheEntry *entry = cls; + + GNUNET_assert (NULL != entry); + LOG_DEBUG ("Opening a transport connection to peer %u\n", entry->peer_id); + entry->transport_handle_ = + GNUNET_TRANSPORT_connect (entry->cfg, NULL, entry, NULL, + &transport_peer_connect_notify_cb, NULL); + if (NULL == entry->transport_handle_) + { + GNUNET_break (0); + return; + } + if (0 == entry->demand) + return; + if (GNUNET_SCHEDULER_NO_TASK != entry->notify_task) + return; + if (NULL != search_suitable_cgh (entry, entry->cgh_qhead)) + entry->notify_task = GNUNET_SCHEDULER_add_now (&call_cgh_cb, entry); +} + + +/** + * Function called when the operation responsible for opening a TRANSPORT + * connection is marked as done. + * + * @param cls the cache entry + */ +static void +oprelease_get_handle_transport (void *cls) +{ + struct CacheEntry *entry = cls; + + if (NULL == entry->transport_handle_) + return; + GNUNET_TRANSPORT_disconnect (entry->transport_handle_); + entry->transport_handle_ = NULL; +} + + +/** + * Function called after GNUNET_CORE_connect has succeeded (or failed + * for good). Note that the private key of the peer is intentionally + * not exposed here; if you need it, your process should try to read + * the private key file directly (which should work if you are + * authorized...). Implementations of this function must not call + * GNUNET_CORE_disconnect (other than by scheduling a new task to + * do this later). + * + * @param cls closure + * @param server handle to the server, NULL if we failed + * @param my_identity ID of this peer, NULL if we failed + */ +static void +core_startup_cb (void *cls, struct GNUNET_CORE_Handle *server, + const struct GNUNET_PeerIdentity *my_identity) +{ + struct CacheEntry *entry = cls; + + if (NULL == my_identity) + { + GNUNET_break (0); + return; + } + GNUNET_assert (NULL == entry->peer_identity); + entry->core_handle = server; + entry->peer_identity = GNUNET_malloc (sizeof (struct GNUNET_PeerIdentity)); + memcpy (entry->peer_identity, my_identity, + sizeof (struct GNUNET_PeerIdentity)); + if (0 == entry->demand) + return; + if (GNUNET_SCHEDULER_NO_TASK != entry->notify_task) + return; + if (NULL != search_suitable_cgh (entry, entry->cgh_qhead)) + entry->notify_task = GNUNET_SCHEDULER_add_now (&call_cgh_cb, entry); +} + + +/** + * Method called whenever a given peer connects at CORE level + * + * @param cls closure + * @param peer peer identity this notification is about + * @param atsi performance data for the connection + * @param atsi_count number of records in 'atsi' + */ +static void +core_peer_connect_cb (void *cls, const struct GNUNET_PeerIdentity *peer, + const struct GNUNET_ATS_Information *atsi, + unsigned int atsi_count) +{ + peer_connect_notify_cb (cls, peer, CGT_CORE_HANDLE); +} + + +/** + * Function called when resources for opening a connection to CORE are + * available. + * + * @param cls the cache entry + */ +static void +opstart_get_handle_core (void *cls) +{ + struct CacheEntry *entry = cls; + + const struct GNUNET_CORE_MessageHandler no_handlers[] = { + {NULL, 0, 0} + }; + + GNUNET_assert (NULL != entry); + LOG_DEBUG ("Opening a CORE connection to peer %u\n", entry->peer_id); + /* void?: We also get the handle when the connection to CORE is successful */ + (void) GNUNET_CORE_connect (entry->cfg, entry, /* closure */ + &core_startup_cb, /* core startup notify */ + &core_peer_connect_cb, /* peer connect notify */ + NULL, /* peer disconnect notify */ + NULL, /* inbound notify */ + GNUNET_NO, /* inbound header only? */ + NULL, /* outbound notify */ + GNUNET_NO, /* outbound header only? */ + no_handlers); +} + + +/** + * Function called when the operation responsible for opening a TRANSPORT + * connection is marked as done. + * + * @param cls the cache entry + */ +static void +oprelease_get_handle_core (void *cls) +{ + struct CacheEntry *entry = cls; + + if (NULL == entry->core_handle) + return; + GNUNET_CORE_disconnect (entry->core_handle); + entry->core_handle = NULL; + GNUNET_free_non_null (entry->peer_identity); + entry->peer_identity = NULL; +} + + +/** + * Function to get a handle with given configuration. The type of the handle is + * implicitly provided in the GSTCacheGetHandle. If the handle is already cached + * before, it will be retured in the given callback; the peer_id is used to + * lookup in the cache; if not, a new operation is started to open the transport + * handle and will be given in the callback when it is available. + * + * @param cls the cache entry + */ +static struct GSTCacheGetHandle * +cache_get_handle (unsigned int peer_id, struct GSTCacheGetHandle *cgh, + const struct GNUNET_CONFIGURATION_Handle *cfg, + const struct GNUNET_PeerIdentity *target, + GST_cache_peer_connect_notify connect_notify_cb, + void *connect_notify_cb_cls) +{ + struct GNUNET_HashCode key; + void *handle; + struct CacheEntry *entry; + struct ConnectNotifyContext *ctxt; + struct GNUNET_TESTBED_Operation *op; + + GNUNET_assert (0 != cgh->type); + GNUNET_CRYPTO_hash (&peer_id, sizeof (peer_id), &key); + handle = NULL; + entry = cache_lookup (&key); + if (NULL != entry) + { + if (GNUNET_YES == entry->in_lru) + { + GNUNET_assert (0 == entry->demand); + GNUNET_assert (0 < lru_cache_size); + if (GNUNET_SCHEDULER_NO_TASK != entry->expire_task) + { + GNUNET_SCHEDULER_cancel (entry->expire_task); + entry->expire_task = GNUNET_SCHEDULER_NO_TASK; + } + GNUNET_CONTAINER_DLL_remove (lru_cache_head, lru_cache_tail, entry); + lru_cache_size--; + entry->in_lru = GNUNET_NO; + } + switch (cgh->type) + { + case CGT_TRANSPORT_HANDLE: + handle = entry->transport_handle_; + if (NULL != handle) + LOG_DEBUG ("Found TRANSPORT handle in cache for peer %u\n", + entry->peer_id); + break; + case CGT_CORE_HANDLE: + handle = entry->core_handle; + if (NULL != handle) + LOG_DEBUG ("Found CORE handle in cache for peer %u\n", entry->peer_id); + break; + } + } + if (NULL == entry) + entry = add_entry (&key, peer_id); + if (NULL == entry->cfg) + entry->cfg = GNUNET_CONFIGURATION_dup (cfg); + entry->demand++; + cgh->entry = entry; + GNUNET_CONTAINER_DLL_insert (entry->cgh_qhead, entry->cgh_qtail, cgh); + if ((NULL != target) && (NULL != connect_notify_cb)) + { + ctxt = GNUNET_malloc (sizeof (struct ConnectNotifyContext)); + ctxt->target = target; + ctxt->cb = connect_notify_cb; + ctxt->cb_cls = connect_notify_cb_cls; + GNUNET_assert (NULL == cgh->nctxt); + cgh->nctxt = ctxt; + ctxt->cgh = cgh; + } + if (NULL != handle) + { + if (GNUNET_SCHEDULER_NO_TASK == entry->notify_task) + entry->notify_task = GNUNET_SCHEDULER_add_now (&call_cgh_cb, entry); + return cgh; + } + switch (cgh->type) + { + case CGT_TRANSPORT_HANDLE: + if (NULL != entry->transport_op_) + return cgh; + op = GNUNET_TESTBED_operation_create_ (entry, &opstart_get_handle_transport, + &oprelease_get_handle_transport); + entry->transport_op_ = op; + break; + case CGT_CORE_HANDLE: + if (NULL != entry->core_op) + return cgh; + op = GNUNET_TESTBED_operation_create_ (entry, &opstart_get_handle_core, + &oprelease_get_handle_core); + entry->core_op = op; + break; + } + GNUNET_TESTBED_operation_queue_insert_ (GST_opq_openfds, op); + GNUNET_TESTBED_operation_begin_wait_ (op); + return cgh; +} + + +/** + * Iterator over hash map entries. + * + * @param cls closure + * @param key current key code + * @param value value in the hash map + * @return GNUNET_YES if we should continue to + * iterate, + * GNUNET_NO if not. + */ +static int +cache_clear_iterator (void *cls, const struct GNUNET_HashCode *key, void *value) +{ + struct CacheEntry *entry = value; + static unsigned int ncleared; + + GNUNET_assert (NULL != entry); + GNUNET_break (0 == entry->demand); + LOG_DEBUG ("Clearing entry %u of %u\n", ++ncleared, cache_size); + GNUNET_CONTAINER_multihashmap_remove (cache, key, value); + if (0 == entry->demand) + close_handles (entry); + GNUNET_free_non_null (entry->hello); + GNUNET_break (GNUNET_SCHEDULER_NO_TASK == entry->expire_task); + GNUNET_break (NULL == entry->transport_handle_); + GNUNET_break (NULL == entry->transport_op_); + GNUNET_break (NULL == entry->core_handle); + GNUNET_break (NULL == entry->core_op); + GNUNET_break (NULL == entry->cfg); + GNUNET_assert (NULL == entry->cgh_qhead); + GNUNET_assert (NULL == entry->cgh_qtail); + GNUNET_assert (NULL == entry->nctxt_qhead); + GNUNET_assert (NULL == entry->nctxt_qtail); + GNUNET_free (entry); + return GNUNET_YES; +} + + +/** + * Clear cache + */ +void +GST_cache_clear () +{ + GNUNET_CONTAINER_multihashmap_iterate (cache, &cache_clear_iterator, NULL); + GNUNET_assert (0 == GNUNET_CONTAINER_multihashmap_size (cache)); + GNUNET_CONTAINER_multihashmap_destroy (cache); +} + + +/** + * Initializes the cache + * + * @param size the size of the cache + */ +void +GST_cache_init (unsigned int size) +{ + if (0 == size) + return; + lru_cache_threshold_size = size; + if (size > 1) + size = size / 2; + cache = GNUNET_CONTAINER_multihashmap_create (size, GNUNET_YES); +} + + +/** + * Mark the GetCacheHandle as being done if a handle has been provided already + * or as being cancelled if the callback for the handle hasn't been called. + * + * @param cgh the CacheGetHandle handle + */ +void +GST_cache_get_handle_done (struct GSTCacheGetHandle *cgh) +{ + struct CacheEntry *entry; + + entry = cgh->entry; + GNUNET_assert (NULL != entry); + GNUNET_assert (0 < entry->demand); + entry->demand--; + if (GNUNET_SCHEDULER_NO_TASK != entry->notify_task) + { + GNUNET_SCHEDULER_cancel (entry->notify_task); + entry->notify_task = GNUNET_SCHEDULER_NO_TASK; + } + GNUNET_CONTAINER_DLL_remove (entry->cgh_qhead, entry->cgh_qtail, cgh); + if (NULL != cgh->nctxt) + { + GNUNET_assert (cgh == cgh->nctxt->cgh); + if (GNUNET_YES == cgh->notify_called) + GNUNET_CONTAINER_DLL_remove (entry->nctxt_qhead, entry->nctxt_qtail, + cgh->nctxt); + GNUNET_free (cgh->nctxt); + } + GNUNET_free (cgh); + if (0 == entry->demand) + { + entry->expire_task = + GNUNET_SCHEDULER_add_delayed (CACHE_EXPIRY, &expire_cache_entry, entry); + GNUNET_CONTAINER_DLL_insert_tail (lru_cache_head, lru_cache_tail, entry); + lru_cache_size++; + entry->in_lru = GNUNET_YES; + if (lru_cache_size > lru_cache_threshold_size) + close_handles (lru_cache_head); + } + else + { + struct GSTCacheGetHandle *cgh2; + + if (NULL != (cgh2 = search_suitable_cgh (entry, entry->cgh_qhead))) + entry->notify_task = GNUNET_SCHEDULER_add_now (&call_cgh_cb, entry); + } +} + + +/** + * Get a transport handle with the given configuration. If the handle is + * already cached before, it will be retured in the given callback; the peer_id + * is used to lookup in the cache; if not, a new operation is started to open the + * transport handle and will be given in the callback when it is available. + * + * @param peer_id the index of the peer + * @param cfg the configuration with which the transport handle has to be + * created if it was not present in the cache + * @param cb the callback to notify when the transport handle is available + * @param cb_cls the closure for the above callback + * @param target the peer identify of the peer whose connection to our TRANSPORT + * subsystem will be notified through the connect_notify_cb. Can be NULL + * @param connect_notify_cb the callback to call when the given target peer is + * connected. This callback will only be called once or never again (in + * case the target peer cannot be connected). Can be NULL + * @param connect_notify_cb_cls the closure for the above callback + * @return the handle which can be used cancel or mark that the handle is no + * longer being used + */ +struct GSTCacheGetHandle * +GST_cache_get_handle_transport (unsigned int peer_id, + const struct GNUNET_CONFIGURATION_Handle *cfg, + GST_cache_handle_ready_cb cb, void *cb_cls, + const struct GNUNET_PeerIdentity *target, + GST_cache_peer_connect_notify connect_notify_cb, + void *connect_notify_cb_cls) +{ + struct GSTCacheGetHandle *cgh; + + cgh = GNUNET_malloc (sizeof (struct GSTCacheGetHandle)); + cgh->cb = cb; + cgh->cb_cls = cb_cls; + cgh->type = CGT_TRANSPORT_HANDLE; + return cache_get_handle (peer_id, cgh, cfg, target, connect_notify_cb, + connect_notify_cb_cls); +} + + +/** + * Get a CORE handle with the given configuration. If the handle is already + * cached before, it will be retured in the given callback; the peer_id is used + * to lookup in the cache. If the handle is not cached before, a new operation + * is started to open the CORE handle and will be given in the callback when it + * is available along with the peer identity + * + * @param peer_id the index of the peer + * @param cfg the configuration with which the transport handle has to be + * created if it was not present in the cache + * @param cb the callback to notify when the transport handle is available + * @param cb_cls the closure for the above callback + * @param target the peer identify of the peer whose connection to our CORE + * subsystem will be notified through the connect_notify_cb. Can be NULL + * @param connect_notify_cb the callback to call when the given target peer is + * connected. This callback will only be called once or never again (in + * case the target peer cannot be connected). Can be NULL + * @param connect_notify_cb_cls the closure for the above callback + * @return the handle which can be used cancel or mark that the handle is no + * longer being used + */ +struct GSTCacheGetHandle * +GST_cache_get_handle_core (unsigned int peer_id, + const struct GNUNET_CONFIGURATION_Handle *cfg, + GST_cache_handle_ready_cb cb, void *cb_cls, + const struct GNUNET_PeerIdentity *target, + GST_cache_peer_connect_notify connect_notify_cb, + void *connect_notify_cb_cls) +{ + struct GSTCacheGetHandle *cgh; + + cgh = GNUNET_malloc (sizeof (struct GSTCacheGetHandle)); + cgh->cb = cb; + cgh->cb_cls = cb_cls; + cgh->type = CGT_CORE_HANDLE; + return cache_get_handle (peer_id, cgh, cfg, target, connect_notify_cb, + connect_notify_cb_cls); +} + + +/** + * Looks up in the hello cache and returns the HELLO of the given peer + * + * @param peer_id the index of the peer whose HELLO has to be looked up + * @return the HELLO message; NULL if not found + */ +const struct GNUNET_MessageHeader * +GST_cache_lookup_hello (const unsigned int peer_id) +{ + struct CacheEntry *entry; + struct GNUNET_HashCode key; + + LOG_DEBUG ("Looking up HELLO for peer %u\n", peer_id); + GNUNET_CRYPTO_hash (&peer_id, sizeof (peer_id), &key); + entry = cache_lookup (&key); + if (NULL == entry) + return NULL; + if (NULL != entry->hello) + LOG_DEBUG ("HELLO found for peer %u\n", peer_id); + return entry->hello; +} + + +/** + * Caches the HELLO of the given peer. Updates the HELLO if it was already + * cached before + * + * @param id the peer identity of the peer whose HELLO has to be cached + * @param hello the HELLO message + */ +void +GST_cache_add_hello (const unsigned int peer_id, + const struct GNUNET_MessageHeader *hello) +{ + struct CacheEntry *entry; + struct GNUNET_HashCode key; + + GNUNET_CRYPTO_hash (&peer_id, sizeof (peer_id), &key); + entry = GNUNET_CONTAINER_multihashmap_get (cache, &key); + if (NULL == entry) + entry = add_entry (&key, peer_id); + GNUNET_free_non_null (entry->hello); + entry->hello = GNUNET_copy_message (hello); +} + +/* end of gnunet-service-testbed_hc.c */ diff --git a/src/testbed/gnunet-service-testbed_oc.c b/src/testbed/gnunet-service-testbed_oc.c new file mode 100644 index 0000000..9b571e3 --- /dev/null +++ b/src/testbed/gnunet-service-testbed_oc.c @@ -0,0 +1,1595 @@ +/* + This file is part of GNUnet. + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 2, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @file testbed/gnunet-service-testbed_oc.c + * @brief code for handling overlay connect operations + * @author Sree Harsha Totakura + */ + +#include "gnunet-service-testbed.h" + +/** + * Redefine LOG with a changed log component string + */ +#ifdef LOG +#undef LOG +#endif +#define LOG(kind,...) \ + GNUNET_log_from (kind, "testbed-OC", __VA_ARGS__) + + +/** + * Context information for requesting TRANSPORT to connect to a peer + */ +struct TryConnectContext +{ + /** + * The identity of the peer to which the transport has to attempt a connection + */ + struct GNUNET_PeerIdentity *pid; + + /** + * The transport handle obtained from cache. Do NOT close/disconnect. + */ + struct GNUNET_TRANSPORT_Handle *th_; + + /** + * The GetCacheHandle for the p1th transport handle + */ + struct GSTCacheGetHandle *cgh_th; + + /** + * the try connect handle + */ + struct GNUNET_TRANSPORT_TryConnectHandle *tch; + + /** + * The task handle + */ + GNUNET_SCHEDULER_TaskIdentifier task; + + /** + * The id of the operation which is resposible for this context + */ + uint64_t op_id; + + /** + * The number of times we attempted to connect + */ + unsigned int retries; + +}; + + +/** + * Context information for connecting 2 peers in overlay. + */ +struct OverlayConnectContext +{ + /** + * The next pointer for maintaining a DLL of all OverlayConnectContexts + */ + struct OverlayConnectContext *next; + + /** + * The prev pointer for maintaining a DLL of all OverlayConnectContexts + */ + struct OverlayConnectContext *prev; + + /** + * The client which has requested for overlay connection. This is used to send + * either a success of failure message + */ + struct GNUNET_SERVER_Client *client; + + /** + * the first peer which is to expect an overlay connection from the second peer. + */ + struct Peer *peer; + + /** + * Transport handle of the first peer obtained from cache to get its HELLO. Do + * NOT close/disconnect. + */ + struct GNUNET_TRANSPORT_Handle *p1th_; + + /** + * The CacheGetHandle for the p1th transport handle + */ + struct GSTCacheGetHandle *cgh_p1th; + + /** + * The GetCacheHandle for registering callback to notify CORE level peer + * connects and to get our identity. + */ + struct GSTCacheGetHandle *cgh_ch; + + /** + * HELLO of the first peer. This should be sent to the second peer. + */ + struct GNUNET_MessageHeader *hello; + + /** + * Get GetHelloHandle to acquire a HELLO of the first peer + */ + struct GNUNET_TRANSPORT_GetHelloHandle *ghh; + + /** + * The handle for offering the HELLO of the first peer to the second + * peer. This is only used if the second peer is a local peer. + */ + struct GNUNET_TRANSPORT_OfferHelloHandle *ohh; + + /** + * The error message we send if this overlay connect operation has timed out + */ + char *emsg; + + /** + * Operation context for the suboperation we start to get the identity of the + * second peer if it is a remote peer + */ + struct OperationContext *opc; + + /** + * Controller of peer 2; NULL if the peer is a local peer + */ + struct GNUNET_TESTBED_Controller *peer2_controller; + + /** + * The transport TryConnectContext. This will be NULL if the second peer is a + * remote peer + */ + struct TryConnectContext tcc; + + /** + * The peer identity of the first peer + */ + struct GNUNET_PeerIdentity peer_identity; + + /** + * The peer identity of the other peer + */ + struct GNUNET_PeerIdentity other_peer_identity; + + /** + * The id of the operation responsible for creating this context + */ + uint64_t op_id; + + /** + * The id of the task for sending HELLO of peer 2 to peer 1 and ask peer 1 to + * connect to peer 2 + */ + GNUNET_SCHEDULER_TaskIdentifier send_hello_task; + + /** + * The id of the overlay connect timeout task + */ + GNUNET_SCHEDULER_TaskIdentifier timeout_task; + + /** + * The id of the cleanup task + */ + GNUNET_SCHEDULER_TaskIdentifier cleanup_task; + + /** + * The id of peer A + */ + uint32_t peer_id; + + /** + * The id of peer B + */ + uint32_t other_peer_id; + +}; + + +/** + * Context information for remote overlay connect operations. Remote overlay + * connections are used when peers A and B reside on different hosts. In these + * operations the host controller for peer B is asked by the host controller of + * peer A to make peer B connect to peer A by sending the controller of peer B + * the HELLO of peer A. + */ +struct RemoteOverlayConnectCtx +{ + /** + * the next pointer for DLL + */ + struct RemoteOverlayConnectCtx *next; + + /** + * the prev pointer for DLL + */ + struct RemoteOverlayConnectCtx *prev; + + /** + * The peer handle of peer B + */ + struct Peer *peer; + + /** + * Peer A's HELLO + */ + struct GNUNET_MessageHeader *hello; + + /** + * The handle for offering HELLO + */ + struct GNUNET_TRANSPORT_OfferHelloHandle *ohh; + + /** + * The transport try connect context + */ + struct TryConnectContext tcc; + + /** + * The peer identity of peer A + */ + struct GNUNET_PeerIdentity a_id; + + /** + * Task for offering HELLO of A to B and doing try_connect + */ + GNUNET_SCHEDULER_TaskIdentifier attempt_connect_task_id; + + /** + * Task to timeout RequestOverlayConnect + */ + GNUNET_SCHEDULER_TaskIdentifier timeout_rocc_task_id; + + /** + * The id of the operation responsible for creating this context + */ + uint64_t op_id; +}; + + +/** + * DLL head for OverlayConnectContext DLL - to be used to clean up during shutdown + */ +static struct OverlayConnectContext *occq_head; + +/** + * DLL tail for OverlayConnectContext DLL + */ +static struct OverlayConnectContext *occq_tail; + +/** + * DLL head for RequectOverlayConnectContext DLL - to be used to clean up during + * shutdown + */ +static struct RemoteOverlayConnectCtx *roccq_head; + +/** + * DLL tail for RequectOverlayConnectContext DLL + */ +static struct RemoteOverlayConnectCtx *roccq_tail; + + +/** + * Cleans up ForwardedOverlayConnectContext + * + * @param focc the ForwardedOverlayConnectContext to cleanup + */ +void +GST_cleanup_focc (struct ForwardedOverlayConnectContext *focc) +{ + GNUNET_free_non_null (focc->orig_msg); + GNUNET_free (focc); +} + + +/** + * Timeout task for cancelling a forwarded overlay connect connect + * + * @param cls the ForwardedOverlayConnectContext + * @param tc the task context from the scheduler + */ +static void +forwarded_overlay_connect_timeout (void *cls, + const struct GNUNET_SCHEDULER_TaskContext + *tc) +{ + struct ForwardedOperationContext *fopc = cls; + struct RegisteredHostContext *rhc; + struct ForwardedOverlayConnectContext *focc; + + rhc = fopc->cls; + focc = rhc->focc_dll_head; + GNUNET_CONTAINER_DLL_remove (rhc->focc_dll_head, rhc->focc_dll_tail, focc); + GST_cleanup_focc (focc); + LOG_DEBUG ("Overlay linking between peers %u and %u failed\n", focc->peer1, + focc->peer2); + GST_forwarded_operation_timeout (cls, tc); + if (NULL != rhc->focc_dll_head) + GST_process_next_focc (rhc); +} + + +/** + * Callback to be called when forwarded overlay connection operation has a reply + * from the sub-controller successfull. We have to relay the reply msg back to + * the client + * + * @param cls ForwardedOperationContext + * @param msg the peer create success message + */ +static void +forwarded_overlay_connect_listener (void *cls, + const struct GNUNET_MessageHeader *msg) +{ + struct ForwardedOperationContext *fopc = cls; + struct RegisteredHostContext *rhc; + struct ForwardedOverlayConnectContext *focc; + + rhc = fopc->cls; + GST_forwarded_operation_reply_relay (cls, msg); + focc = rhc->focc_dll_head; + GNUNET_CONTAINER_DLL_remove (rhc->focc_dll_head, rhc->focc_dll_tail, focc); + GST_cleanup_focc (focc); + if (NULL != rhc->focc_dll_head) + GST_process_next_focc (rhc); +} + + +/** + * Processes a forwarded overlay connect context in the queue of the given RegisteredHostContext + * + * @param rhc the RegisteredHostContext + */ +void +GST_process_next_focc (struct RegisteredHostContext *rhc) +{ + struct ForwardedOperationContext *fopc; + struct ForwardedOverlayConnectContext *focc; + + focc = rhc->focc_dll_head; + GNUNET_assert (NULL != focc); + GNUNET_assert (RHC_OL_CONNECT == rhc->state); + fopc = GNUNET_malloc (sizeof (struct ForwardedOperationContext)); + GNUNET_SERVER_client_keep (rhc->client); + fopc->client = rhc->client; + fopc->operation_id = focc->operation_id; + fopc->cls = rhc; + fopc->type = OP_OVERLAY_CONNECT; + fopc->opc = + GNUNET_TESTBED_forward_operation_msg_ (rhc->gateway->controller, + focc->operation_id, focc->orig_msg, + &forwarded_overlay_connect_listener, + fopc); + GNUNET_free (focc->orig_msg); + focc->orig_msg = NULL; + fopc->timeout_task = + GNUNET_SCHEDULER_add_delayed (TIMEOUT, &forwarded_overlay_connect_timeout, + fopc); + GNUNET_CONTAINER_DLL_insert_tail (fopcq_head, fopcq_tail, fopc); +} + + +/** + * Cleanup overlay connect context structure + * + * @param occ the overlay connect context + */ +static void +cleanup_occ (struct OverlayConnectContext *occ) +{ + LOG_DEBUG ("0x%llx: Cleaning up occ\n", occ->op_id); + GNUNET_free_non_null (occ->emsg); + GNUNET_free_non_null (occ->hello); + GNUNET_SERVER_client_drop (occ->client); + if (NULL != occ->opc) + GNUNET_TESTBED_forward_operation_msg_cancel_ (occ->opc); + if (GNUNET_SCHEDULER_NO_TASK != occ->send_hello_task) + GNUNET_SCHEDULER_cancel (occ->send_hello_task); + if (GNUNET_SCHEDULER_NO_TASK != occ->cleanup_task) + GNUNET_SCHEDULER_cancel (occ->cleanup_task); + if (GNUNET_SCHEDULER_NO_TASK != occ->timeout_task) + GNUNET_SCHEDULER_cancel (occ->timeout_task); + if (NULL != occ->cgh_ch) + { + GST_cache_get_handle_done (occ->cgh_ch); + occ->peer->reference_cnt--; + } + if (NULL != occ->ghh) + GNUNET_TRANSPORT_get_hello_cancel (occ->ghh); + if (NULL != occ->ohh) + GNUNET_TRANSPORT_offer_hello_cancel (occ->ohh); + if (GNUNET_SCHEDULER_NO_TASK != occ->tcc.task) + GNUNET_SCHEDULER_cancel (occ->tcc.task); + if (NULL != occ->tcc.tch) + GNUNET_TRANSPORT_try_connect_cancel (occ->tcc.tch); + if (NULL != occ->cgh_p1th) + { + GST_cache_get_handle_done (occ->cgh_p1th); + occ->peer->reference_cnt--; + } + if (NULL != occ->tcc.cgh_th) + { + GST_cache_get_handle_done (occ->tcc.cgh_th); + GST_peer_list[occ->other_peer_id]->reference_cnt--; + } + if ((GNUNET_YES == occ->peer->destroy_flag) && + (0 == occ->peer->reference_cnt)) + GST_destroy_peer (occ->peer); + if ((NULL == occ->peer2_controller) && + (GNUNET_YES == GST_peer_list[occ->other_peer_id]->destroy_flag) && + (0 == GST_peer_list[occ->other_peer_id]->reference_cnt)) + GST_destroy_peer (GST_peer_list[occ->other_peer_id]); + GNUNET_CONTAINER_DLL_remove (occq_head, occq_tail, occ); + GNUNET_free (occ); +} + + +/** + * Task for cleaing up overlay connect context structure + * + * @param cls the overlay connect context + * @param tc the task context + */ +static void +do_cleanup_occ (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct OverlayConnectContext *occ = cls; + + occ->cleanup_task = GNUNET_SCHEDULER_NO_TASK; + cleanup_occ (occ); +} + + +/** + * Task which will be run when overlay connect request has been timed out + * + * @param cls the OverlayConnectContext + * @param tc the TaskContext + */ +static void +timeout_overlay_connect (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct OverlayConnectContext *occ = cls; + + GNUNET_assert (GNUNET_SCHEDULER_NO_TASK != occ->timeout_task); + occ->timeout_task = GNUNET_SCHEDULER_NO_TASK; + LOG (GNUNET_ERROR_TYPE_WARNING, + "0x%llx: Timeout while connecting peers %u and %u\n", occ->op_id, + occ->peer_id, occ->other_peer_id); + GST_send_operation_fail_msg (occ->client, occ->op_id, occ->emsg); + cleanup_occ (occ); +} + + +static void +send_overlay_connect_success_msg (struct OverlayConnectContext *occ) +{ + struct GNUNET_TESTBED_ConnectionEventMessage *msg; + + LOG_DEBUG ("0x%llx: Peers connected - Sending overlay connect success\n", + occ->op_id); + msg = GNUNET_malloc (sizeof (struct GNUNET_TESTBED_ConnectionEventMessage)); + msg->header.size = + htons (sizeof (struct GNUNET_TESTBED_ConnectionEventMessage)); + msg->header.type = htons (GNUNET_MESSAGE_TYPE_TESTBED_PEER_CONNECT_EVENT); + msg->event_type = htonl (GNUNET_TESTBED_ET_CONNECT); + msg->peer1 = htonl (occ->peer_id); + msg->peer2 = htonl (occ->other_peer_id); + msg->operation_id = GNUNET_htonll (occ->op_id); + GST_queue_message (occ->client, &msg->header); +} + + +/** + * Function called to notify transport users that another + * peer connected to us. + * + * @param cls closure + * @param new_peer the peer that connected + */ +static void +overlay_connect_notify (void *cls, const struct GNUNET_PeerIdentity *new_peer) +{ + struct OverlayConnectContext *occ = cls; + char *new_peer_str; + char *other_peer_str; + + //LOG_DEBUG ("Overlay connect notify\n"); + if (0 == + memcmp (new_peer, &occ->peer_identity, + sizeof (struct GNUNET_PeerIdentity))) + return; + new_peer_str = GNUNET_strdup (GNUNET_i2s (new_peer)); + other_peer_str = GNUNET_strdup (GNUNET_i2s (&occ->other_peer_identity)); + if (0 != + memcmp (new_peer, &occ->other_peer_identity, + sizeof (struct GNUNET_PeerIdentity))) + { + /* LOG_DEBUG ("Unexpected peer %4s connected when expecting peer %4s\n", */ + /* new_peer_str, other_peer_str); */ + GNUNET_free (new_peer_str); + GNUNET_free (other_peer_str); + return; + } + GNUNET_free (new_peer_str); + LOG_DEBUG ("0x%llx: Peer %4s connected to peer %4s\n", occ->op_id, + other_peer_str, GNUNET_i2s (&occ->peer_identity)); + GNUNET_free (other_peer_str); + if (GNUNET_SCHEDULER_NO_TASK != occ->send_hello_task) + { + GNUNET_SCHEDULER_cancel (occ->send_hello_task); + occ->send_hello_task = GNUNET_SCHEDULER_NO_TASK; + } + GNUNET_assert (GNUNET_SCHEDULER_NO_TASK != occ->timeout_task); + GNUNET_SCHEDULER_cancel (occ->timeout_task); + occ->timeout_task = GNUNET_SCHEDULER_NO_TASK; + if (GNUNET_SCHEDULER_NO_TASK != occ->tcc.task) + { + GNUNET_SCHEDULER_cancel (occ->tcc.task); + occ->tcc.task = GNUNET_SCHEDULER_NO_TASK; + } + GNUNET_free_non_null (occ->emsg); + occ->emsg = NULL; + send_overlay_connect_success_msg (occ); + occ->cleanup_task = GNUNET_SCHEDULER_add_now (&do_cleanup_occ, occ); + //cleanup_occ (occ); +} + + +/** + * Task to ask transport of a peer to connect to another peer + * + * @param cls the TryConnectContext + * @param tc the scheduler task context + */ +static void +try_connect_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc); + + +/** + * Callback to be called with result of the try connect request. + * + * @param cls the overlay connect context + * @param result GNUNET_OK if message was transmitted to transport service + * GNUNET_SYSERR if message was not transmitted to transport service + */ +static void +try_connect_cb (void *cls, const int result) +{ + struct TryConnectContext *tcc = cls; + + tcc->tch = NULL; + GNUNET_assert (GNUNET_SCHEDULER_NO_TASK == tcc->task); + tcc->task = + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply + (GNUNET_TIME_UNIT_MILLISECONDS, + 500 + pow (2, ++tcc->retries)), + &try_connect_task, tcc); +} + + +/** + * Task to ask transport of a peer to connect to another peer + * + * @param cls the TryConnectContext + * @param tc the scheduler task context + */ +static void +try_connect_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct TryConnectContext *tcc = cls; + + tcc->task = GNUNET_SCHEDULER_NO_TASK; + if (0 != (GNUNET_SCHEDULER_REASON_SHUTDOWN & tc->reason)) + return; + GNUNET_assert (NULL == tcc->tch); + GNUNET_assert (NULL != tcc->pid); + GNUNET_assert (NULL != tcc->th_); + GNUNET_assert (NULL != tcc->cgh_th); + LOG_DEBUG ("0x%llx: Trail %u to connect to peer %s\n", tcc->op_id, + tcc->retries, GNUNET_i2s (tcc->pid)); + tcc->tch = + GNUNET_TRANSPORT_try_connect (tcc->th_, tcc->pid, &try_connect_cb, tcc); +} + + +/** + * Task to offer HELLO of peer 1 to peer 2 and try to make peer 2 to connect to + * peer 1. + * + * @param cls the OverlayConnectContext + * @param tc the TaskContext from scheduler + */ +static void +send_hello (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc); + + +/** + * Task that is run when hello has been sent + * + * @param cls the overlay connect context + * @param tc the scheduler task context; if tc->reason = + * GNUNET_SCHEDULER_REASON_TIMEOUT then sending HELLO failed; if + * GNUNET_SCHEDULER_REASON_READ_READY is succeeded + */ +static void +occ_hello_sent_cb (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct OverlayConnectContext *occ = cls; + + occ->ohh = NULL; + GNUNET_assert (GNUNET_SCHEDULER_NO_TASK == occ->send_hello_task); + if (GNUNET_SCHEDULER_REASON_TIMEOUT == tc->reason) + { + GNUNET_free_non_null (occ->emsg); + GNUNET_asprintf (&occ->emsg, + "0x%llx: Timeout while offering HELLO to other peer", + occ->op_id); + occ->send_hello_task = GNUNET_SCHEDULER_add_now (&send_hello, occ); + return; + } + if (GNUNET_SCHEDULER_REASON_READ_READY != tc->reason) + return; + GNUNET_free_non_null (occ->emsg); + GNUNET_asprintf (&occ->emsg, "0x%llx: Timeout while try connect", occ->op_id); + occ->tcc.pid = &occ->peer_identity; + occ->tcc.op_id = occ->op_id; + occ->tcc.task = GNUNET_SCHEDULER_add_now (&try_connect_task, &occ->tcc); +} + + +/** + * Task to offer HELLO of peer 1 to peer 2 and try to make peer 2 to connect to + * peer 1. + * + * @param cls the OverlayConnectContext + * @param tc the TaskContext from scheduler + */ +static void +send_hello (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct OverlayConnectContext *occ = cls; + char *other_peer_str; + + occ->send_hello_task = GNUNET_SCHEDULER_NO_TASK; + if (0 != (tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN)) + return; + GNUNET_assert (NULL != occ->hello); + other_peer_str = GNUNET_strdup (GNUNET_i2s (&occ->other_peer_identity)); + if (NULL != occ->peer2_controller) + { + struct GNUNET_TESTBED_RemoteOverlayConnectMessage *msg; + uint16_t msize; + uint16_t hello_size; + + LOG_DEBUG ("0x%llx: Offering HELLO of %s (size: %u) to %s via Remote " + "Overlay Request\n", occ->op_id, + GNUNET_i2s (&occ->peer_identity), ntohs (occ->hello->size), + other_peer_str); + hello_size = ntohs (occ->hello->size); + msize = + sizeof (struct GNUNET_TESTBED_RemoteOverlayConnectMessage) + hello_size; + msg = GNUNET_malloc (msize); + msg->header.type = + htons (GNUNET_MESSAGE_TYPE_TESTBED_REMOTE_OVERLAY_CONNECT); + msg->header.size = htons (msize); + msg->peer = htonl (occ->other_peer_id); + msg->operation_id = GNUNET_htonll (occ->op_id); + (void) memcpy (&msg->peer_identity, &occ->peer_identity, + sizeof (struct GNUNET_PeerIdentity)); + memcpy (msg->hello, occ->hello, hello_size); + GNUNET_TESTBED_queue_message_ (occ->peer2_controller, &msg->header); + } + else + { + LOG_DEBUG ("0x%llx: Offering HELLO of %s to %s\n", occ->op_id, + GNUNET_i2s (&occ->peer_identity), other_peer_str); + occ->ohh = + GNUNET_TRANSPORT_offer_hello (occ->tcc.th_, occ->hello, + occ_hello_sent_cb, occ); + if (NULL == occ->ohh) + { + GNUNET_break (0); + occ->send_hello_task = + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply + (GNUNET_TIME_UNIT_MILLISECONDS, + 100 + + GNUNET_CRYPTO_random_u32 + (GNUNET_CRYPTO_QUALITY_WEAK, 500)), + &send_hello, occ); + } + } + GNUNET_free (other_peer_str); +} + + +/** + * Callback from cache with needed handles set + * + * @param cls the closure passed to GST_cache_get_handle_transport() + * @param ch the handle to CORE. Can be NULL if it is not requested + * @param th the handle to TRANSPORT. Can be NULL if it is not requested + * @param ignore_ peer identity which is ignored in this callback + */ +static void +p2_transport_connect_cache_callback (void *cls, struct GNUNET_CORE_Handle *ch, + struct GNUNET_TRANSPORT_Handle *th, + const struct GNUNET_PeerIdentity *ignore_) +{ + struct OverlayConnectContext *occ = cls; + + if (NULL == th) + { + GNUNET_asprintf (&occ->emsg, "0x%llx: Cannot connect to TRANSPORT of %s", + occ->op_id, GNUNET_i2s (&occ->other_peer_identity)); + GNUNET_SCHEDULER_cancel (occ->timeout_task); + occ->timeout_task = + GNUNET_SCHEDULER_add_now (&timeout_overlay_connect, occ); + return; + } + occ->tcc.th_ = th; + GNUNET_asprintf (&occ->emsg, "0x%llx: Timeout while offering HELLO to %s", + occ->op_id, GNUNET_i2s (&occ->other_peer_identity)); + occ->send_hello_task = GNUNET_SCHEDULER_add_now (&send_hello, occ); +} + + +/** + * Connects to the transport of the other peer if it is a local peer and + * schedules the send hello task + * + * @param occ the overlay connect context + */ +static void +p2_transport_connect (struct OverlayConnectContext *occ) +{ + GNUNET_assert (NULL == occ->emsg); + GNUNET_assert (NULL != occ->hello); + GNUNET_assert (NULL == occ->ghh); + GNUNET_assert (NULL == occ->p1th_); + GNUNET_assert (NULL == occ->cgh_p1th); + if (NULL == occ->peer2_controller) + { + GST_peer_list[occ->other_peer_id]->reference_cnt++; + occ->tcc.cgh_th = + GST_cache_get_handle_transport (occ->other_peer_id, + GST_peer_list[occ->other_peer_id]-> + details.local.cfg, + &p2_transport_connect_cache_callback, + occ, NULL, NULL, NULL); + return; + } + GNUNET_asprintf (&occ->emsg, "0x%llx: Timeout while offering HELLO to %s", + occ->op_id, GNUNET_i2s (&occ->other_peer_identity)); + occ->send_hello_task = GNUNET_SCHEDULER_add_now (&send_hello, occ); +} + + +/** + * Test for checking whether HELLO message is empty + * + * @param cls empty flag to set + * @param address the HELLO + * @param expiration expiration of the HELLO + * @return + */ +static int +test_address (void *cls, const struct GNUNET_HELLO_Address *address, + struct GNUNET_TIME_Absolute expiration) +{ + int *empty = cls; + + *empty = GNUNET_NO; + return GNUNET_OK; +} + + +/** + * Function called whenever there is an update to the HELLO of peers in the + * OverlayConnectClosure. If we have a valid HELLO, we connect to the peer 2's + * transport and offer peer 1's HELLO and ask peer 2 to connect to peer 1 + * + * @param cls closure + * @param hello our updated HELLO + */ +static void +hello_update_cb (void *cls, const struct GNUNET_MessageHeader *hello) +{ + struct OverlayConnectContext *occ = cls; + int empty; + uint16_t msize; + + msize = ntohs (hello->size); + empty = GNUNET_YES; + (void) GNUNET_HELLO_iterate_addresses ((const struct GNUNET_HELLO_Message *) + hello, GNUNET_NO, &test_address, + &empty); + if (GNUNET_YES == empty) + { + LOG_DEBUG ("0x%llx: HELLO of %s is empty\n", occ->op_id, + GNUNET_i2s (&occ->peer_identity)); + return; + } + LOG_DEBUG ("0x%llx: Received HELLO of %s\n", occ->op_id, + GNUNET_i2s (&occ->peer_identity)); + occ->hello = GNUNET_malloc (msize); + GST_cache_add_hello (occ->peer_id, hello); + memcpy (occ->hello, hello, msize); + GNUNET_TRANSPORT_get_hello_cancel (occ->ghh); + occ->ghh = NULL; + GST_cache_get_handle_done (occ->cgh_p1th); + occ->peer->reference_cnt--; + occ->cgh_p1th = NULL; + occ->p1th_ = NULL; + GNUNET_free_non_null (occ->emsg); + occ->emsg = NULL; + p2_transport_connect (occ); +} + + +/** + * Callback from cache with needed handles set + * + * @param cls the closure passed to GST_cache_get_handle_transport() + * @param ch the handle to CORE. Can be NULL if it is not requested + * @param th the handle to TRANSPORT. Can be NULL if it is not requested + * @param ignore_ peer identity which is ignored in this callback + */ +static void +p1_transport_connect_cache_callback (void *cls, struct GNUNET_CORE_Handle *ch, + struct GNUNET_TRANSPORT_Handle *th, + const struct GNUNET_PeerIdentity *ignore_) +{ + struct OverlayConnectContext *occ = cls; + + GNUNET_free_non_null (occ->emsg); + occ->emsg = NULL; + if (NULL == th) + { + GNUNET_asprintf (&occ->emsg, "0x%llx: Cannot connect to TRANSPORT of %s", + occ->op_id, GNUNET_i2s (&occ->peer_identity)); + GNUNET_SCHEDULER_cancel (occ->timeout_task); + occ->timeout_task = + GNUNET_SCHEDULER_add_now (&timeout_overlay_connect, occ); + return; + } + GNUNET_assert (NULL == occ->p1th_); + GNUNET_assert (NULL != occ->cgh_p1th); + occ->p1th_ = th; + GNUNET_asprintf (&occ->emsg, + "0x%llx: Timeout while acquiring HELLO of peer %4s", + occ->op_id, GNUNET_i2s (&occ->peer_identity)); + occ->ghh = GNUNET_TRANSPORT_get_hello (occ->p1th_, &hello_update_cb, occ); +} + + +/** + * Callback from cache with needed handles set + * + * @param cls the closure passed to GST_cache_get_handle_transport() + * @param ch the handle to CORE. Can be NULL if it is not requested + * @param th the handle to TRANSPORT. Can be NULL if it is not requested + * @param my_identity the identity of our peer + */ +static void +occ_cache_get_handle_core_cb (void *cls, struct GNUNET_CORE_Handle *ch, + struct GNUNET_TRANSPORT_Handle *th, + const struct GNUNET_PeerIdentity *my_identity) +{ + struct OverlayConnectContext *occ = cls; + const struct GNUNET_MessageHeader *hello; + + GNUNET_assert (GNUNET_SCHEDULER_NO_TASK != occ->timeout_task); + GNUNET_free_non_null (occ->emsg); + if ((NULL == ch) || (NULL == my_identity)) + { + (void) GNUNET_asprintf (&occ->emsg, + "0x%llx: Failed to connect to CORE of peer with" + "id: %u", occ->op_id, occ->peer_id); + GNUNET_SCHEDULER_cancel (occ->timeout_task); + occ->timeout_task = + GNUNET_SCHEDULER_add_now (&timeout_overlay_connect, occ); + return; + } + //occ->ch_ = ch; + occ->emsg = NULL; + if (GNUNET_YES == + GNUNET_CORE_is_peer_connected_sync (ch, &occ->other_peer_identity)) + { + LOG_DEBUG ("0x%llx: Target peer already connected\n", occ->op_id); + GNUNET_SCHEDULER_cancel (occ->timeout_task); + occ->timeout_task = GNUNET_SCHEDULER_NO_TASK; + send_overlay_connect_success_msg (occ); + occ->cleanup_task = GNUNET_SCHEDULER_add_now (&do_cleanup_occ, occ); + return; + } + memcpy (&occ->peer_identity, my_identity, + sizeof (struct GNUNET_PeerIdentity)); + LOG_DEBUG ("0x%llx: Acquiring HELLO of peer %s\n", occ->op_id, + GNUNET_i2s (&occ->peer_identity)); + /* Lookup for HELLO in hello cache */ + if (NULL != (hello = GST_cache_lookup_hello (occ->peer_id))) + { + LOG_DEBUG ("0x%llx: HELLO of peer %s found in cache\n", occ->op_id, + GNUNET_i2s (&occ->peer_identity)); + occ->hello = GNUNET_copy_message (hello); + p2_transport_connect (occ); + return; + } + GNUNET_asprintf (&occ->emsg, + "0x%llx: Timeout while acquiring TRANSPORT of %s from cache", + occ->op_id, GNUNET_i2s (&occ->peer_identity)); + occ->peer->reference_cnt++; + occ->cgh_p1th = + GST_cache_get_handle_transport (occ->peer_id, + occ->peer->details.local.cfg, + p1_transport_connect_cache_callback, occ, + NULL, NULL, NULL); + return; +} + + +/** + * Callback to be called when forwarded get peer config operation as part of + * overlay connect is successfull. Connection to Peer 1's core is made and is + * checked for new connection from peer 2 + * + * @param cls ForwardedOperationContext + * @param msg the peer create success message + */ +static void +overlay_connect_get_config (void *cls, const struct GNUNET_MessageHeader *msg) +{ + struct OverlayConnectContext *occ = cls; + const struct GNUNET_TESTBED_PeerConfigurationInformationMessage *cmsg; + + occ->opc = NULL; + GNUNET_assert (GNUNET_SCHEDULER_NO_TASK != occ->timeout_task); + if (GNUNET_MESSAGE_TYPE_TESTBED_PEER_CONFIGURATION != ntohs (msg->type)) + { + GNUNET_SCHEDULER_cancel (occ->timeout_task); + occ->timeout_task = + GNUNET_SCHEDULER_add_now (&timeout_overlay_connect, occ); + } + cmsg = + (const struct GNUNET_TESTBED_PeerConfigurationInformationMessage *) msg; + memcpy (&occ->other_peer_identity, &cmsg->peer_identity, + sizeof (struct GNUNET_PeerIdentity)); + GNUNET_free_non_null (occ->emsg); + GNUNET_asprintf (&occ->emsg, + "0x%llx: Timeout while connecting to CORE of peer with " + "id: %u", occ->op_id, occ->peer_id); + occ->peer->reference_cnt++; + occ->cgh_ch = + GST_cache_get_handle_core (occ->peer_id, occ->peer->details.local.cfg, + occ_cache_get_handle_core_cb, occ, + &occ->other_peer_identity, + &overlay_connect_notify, occ); + return; +} + + +/** + * Callback which will be called to after a host registration succeeded or failed + * + * @param cls the RegisteredHostContext + * @param emsg the error message; NULL if host registration is successful + */ +static void +registeredhost_registration_completion (void *cls, const char *emsg) +{ + struct RegisteredHostContext *rhc = cls; + struct GNUNET_CONFIGURATION_Handle *cfg; + uint32_t peer2_host_id; + + /* if (NULL != rhc->focc_dll_head) */ + /* TESTBED_process_next_focc (rhc); */ + peer2_host_id = GNUNET_TESTBED_host_get_id_ (rhc->reg_host); + GNUNET_assert (RHC_INIT == rhc->state); + GNUNET_assert (NULL == rhc->sub_op); + if ((NULL == rhc->gateway2) || ((peer2_host_id < GST_slave_list_size) /* Check if we have the needed config */ + && (NULL != GST_slave_list[peer2_host_id]))) + { + rhc->state = RHC_LINK; + cfg = + (NULL == + rhc->gateway2) ? our_config : GST_slave_list[peer2_host_id]->cfg; + rhc->sub_op = + GNUNET_TESTBED_controller_link (rhc, rhc->gateway->controller, + rhc->reg_host, rhc->host, cfg, + GNUNET_NO); + return; + } + rhc->state = RHC_GET_CFG; + rhc->sub_op = + GNUNET_TESTBED_get_slave_config (rhc, rhc->gateway2->controller, + rhc->reg_host); +} + + +/** + * Iterator to match a registered host context + * + * @param cls pointer 2 pointer of RegisteredHostContext + * @param key current key code + * @param value value in the hash map + * @return GNUNET_YES if we should continue to + * iterate, + * GNUNET_NO if not. + */ +static int +reghost_match_iterator (void *cls, const struct GNUNET_HashCode *key, + void *value) +{ + struct RegisteredHostContext **rh = cls; + struct RegisteredHostContext *rh_val = value; + + if ((rh_val->host == (*rh)->host) && (rh_val->reg_host == (*rh)->reg_host)) + { + GNUNET_free (*rh); + *rh = rh_val; + return GNUNET_NO; + } + return GNUNET_YES; +} + + +/** + * Function to generate the hashcode corresponding to a RegisteredHostContext + * + * @param reg_host the host which is being registered in RegisteredHostContext + * @param host the host of the controller which has to connect to the above rhost + * @return the hashcode + */ +static struct GNUNET_HashCode +hash_hosts (struct GNUNET_TESTBED_Host *reg_host, + struct GNUNET_TESTBED_Host *host) +{ + struct GNUNET_HashCode hash; + uint32_t host_ids[2]; + + host_ids[0] = GNUNET_TESTBED_host_get_id_ (reg_host); + host_ids[1] = GNUNET_TESTBED_host_get_id_ (host); + GNUNET_CRYPTO_hash (host_ids, sizeof (host_ids), &hash); + return hash; +} + + +/** + * Handler for GNUNET_MESSAGE_TYPE_TESTBED_OLCONNECT messages + * + * @param cls NULL + * @param client identification of the client + * @param message the actual message + */ +void +GST_handle_overlay_connect (void *cls, struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) +{ + const struct GNUNET_TESTBED_OverlayConnectMessage *msg; + struct Peer *peer; + struct OverlayConnectContext *occ; + struct GNUNET_TESTBED_Controller *peer2_controller; + uint64_t operation_id; + uint32_t p1; + uint32_t p2; + uint32_t peer2_host_id; + + if (sizeof (struct GNUNET_TESTBED_OverlayConnectMessage) != + ntohs (message->size)) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + msg = (const struct GNUNET_TESTBED_OverlayConnectMessage *) message; + p1 = ntohl (msg->peer1); + p2 = ntohl (msg->peer2); + if ((p1 >= GST_peer_list_size) || (NULL == GST_peer_list[p1])) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + peer = GST_peer_list[p1]; + peer2_host_id = ntohl (msg->peer2_host_id); + operation_id = GNUNET_ntohll (msg->operation_id); + LOG_DEBUG + ("Received overlay connect for peers %u and %u with op id: 0x%llx\n", p1, + p2, operation_id); + if (GNUNET_YES == peer->is_remote) + { + struct ForwardedOperationContext *fopc; + struct Route *route_to_peer2_host; + struct Route *route_to_peer1_host; + + LOG_DEBUG ("0x%llx: Forwarding overlay connect\n", operation_id); + route_to_peer2_host = NULL; + route_to_peer1_host = NULL; + route_to_peer2_host = GST_find_dest_route (peer2_host_id); + if ((NULL != route_to_peer2_host) || + (peer2_host_id == GST_context->host_id)) + { + /* Peer 2 either below us OR with us */ + route_to_peer1_host = + GST_find_dest_route (GST_peer_list[p1]->details. + remote.remote_host_id); + /* Because we get this message only if we know where peer 1 is */ + GNUNET_assert (NULL != route_to_peer1_host); + if ((peer2_host_id == GST_context->host_id) || + (route_to_peer2_host->dest != route_to_peer1_host->dest)) + { + /* Peer2 is either with us OR peer1 and peer2 can be reached through + * different gateways */ + struct GNUNET_HashCode hash; + struct RegisteredHostContext *rhc; + int skip_focc; + + rhc = GNUNET_malloc (sizeof (struct RegisteredHostContext)); + if (NULL != route_to_peer2_host) + rhc->reg_host = GST_host_list[route_to_peer2_host->dest]; + else + rhc->reg_host = GST_host_list[GST_context->host_id]; + rhc->host = GST_host_list[route_to_peer1_host->dest]; + GNUNET_assert (NULL != rhc->reg_host); + GNUNET_assert (NULL != rhc->host); + rhc->gateway = peer->details.remote.slave; + rhc->gateway2 = + (NULL == + route_to_peer2_host) ? NULL : + GST_slave_list[route_to_peer2_host->dest]; + rhc->state = RHC_INIT; + GNUNET_SERVER_client_keep (client); + rhc->client = client; + hash = hash_hosts (rhc->reg_host, rhc->host); + skip_focc = GNUNET_NO; + if ((GNUNET_NO == + GNUNET_CONTAINER_multihashmap_contains (peer->details. + remote.slave->reghost_map, + &hash)) || + (GNUNET_SYSERR != + GNUNET_CONTAINER_multihashmap_get_multiple (peer->details.remote. + slave->reghost_map, + &hash, + reghost_match_iterator, + &rhc))) + { + /* create and add a new registerd host context */ + /* add the focc to its queue */ + GNUNET_CONTAINER_multihashmap_put (peer->details.remote. + slave->reghost_map, &hash, rhc, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE); + GNUNET_assert (NULL != GST_host_list[peer2_host_id]); + GST_queue_host_registration (peer->details.remote.slave, + registeredhost_registration_completion, + rhc, GST_host_list[peer2_host_id]); + } + else + { + /* rhc is now set to the existing one from the hash map by + * reghost_match_iterator() */ + /* if queue is empty then ignore creating focc and proceed with + * normal forwarding */ + if (RHC_OL_CONNECT == rhc->state) + skip_focc = GNUNET_YES; + } + if (GNUNET_NO == skip_focc) + { + struct ForwardedOverlayConnectContext *focc; + + focc = GNUNET_malloc (sizeof (struct ForwardedOverlayConnectContext)); + focc->peer1 = p1; + focc->peer2 = p2; + focc->peer2_host_id = peer2_host_id; + focc->orig_msg = GNUNET_copy_message (message); + focc->operation_id = operation_id; + GNUNET_CONTAINER_DLL_insert_tail (rhc->focc_dll_head, + rhc->focc_dll_tail, focc); + GNUNET_SERVER_receive_done (client, GNUNET_OK); + return; + } + } + } + fopc = GNUNET_malloc (sizeof (struct ForwardedOperationContext)); + GNUNET_SERVER_client_keep (client); + fopc->client = client; + fopc->operation_id = operation_id; + fopc->type = OP_OVERLAY_CONNECT; + fopc->opc = + GNUNET_TESTBED_forward_operation_msg_ (peer->details.remote. + slave->controller, operation_id, + message, + &GST_forwarded_operation_reply_relay, + fopc); + fopc->timeout_task = + GNUNET_SCHEDULER_add_delayed (TIMEOUT, &GST_forwarded_operation_timeout, + fopc); + GNUNET_CONTAINER_DLL_insert_tail (fopcq_head, fopcq_tail, fopc); + GNUNET_SERVER_receive_done (client, GNUNET_OK); + return; + } + + peer2_controller = NULL; + if ((p2 >= GST_peer_list_size) || (NULL == GST_peer_list[p2])) + { + if ((peer2_host_id >= GST_slave_list_size) || + (NULL == GST_slave_list[peer2_host_id])) + { + LOG (GNUNET_ERROR_TYPE_WARNING, + "0x%llx: Configuration of peer2's controller missing for connecting peers" + "%u and %u\n", operation_id, p1, p2); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + peer2_controller = GST_slave_list[peer2_host_id]->controller; + if (NULL == peer2_controller) + { + GNUNET_break (0); /* What's going on? */ + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + } + else + { + if (GNUNET_YES == GST_peer_list[p2]->is_remote) + peer2_controller = GST_peer_list[p2]->details.remote.slave->controller; + } + occ = GNUNET_malloc (sizeof (struct OverlayConnectContext)); + GNUNET_CONTAINER_DLL_insert_tail (occq_head, occq_tail, occ); + GNUNET_SERVER_client_keep (client); + occ->client = client; + occ->peer_id = p1; + occ->other_peer_id = p2; + occ->peer = GST_peer_list[p1]; + occ->op_id = GNUNET_ntohll (msg->operation_id); + occ->peer2_controller = peer2_controller; + GNUNET_assert (GNUNET_SCHEDULER_NO_TASK == occ->timeout_task); + occ->timeout_task = + GNUNET_SCHEDULER_add_delayed (TIMEOUT, &timeout_overlay_connect, occ); + /* Get the identity of the second peer */ + if (NULL != occ->peer2_controller) + { + struct GNUNET_TESTBED_PeerGetConfigurationMessage cmsg; + + cmsg.header.size = + htons (sizeof (struct GNUNET_TESTBED_PeerGetConfigurationMessage)); + cmsg.header.type = + htons (GNUNET_MESSAGE_TYPE_TESTBED_GET_PEER_CONFIGURATION); + cmsg.peer_id = msg->peer2; + cmsg.operation_id = msg->operation_id; + occ->opc = + GNUNET_TESTBED_forward_operation_msg_ (occ->peer2_controller, + occ->op_id, &cmsg.header, + &overlay_connect_get_config, + occ); + GNUNET_asprintf (&occ->emsg, + "0x%llx: Timeout while getting peer identity of peer " + "with id: %u", occ->op_id, occ->other_peer_id); + GNUNET_SERVER_receive_done (client, GNUNET_OK); + return; + } + GNUNET_TESTING_peer_get_identity (GST_peer_list[occ->other_peer_id]-> + details.local.peer, + &occ->other_peer_identity); + GNUNET_asprintf (&occ->emsg, + "0x%llx: Timeout while connecting to CORE of peer with " + "id: %u", occ->op_id, occ->peer_id); + occ->peer->reference_cnt++; + occ->cgh_ch = + GST_cache_get_handle_core (occ->peer_id, occ->peer->details.local.cfg, + occ_cache_get_handle_core_cb, occ, + &occ->other_peer_identity, + &overlay_connect_notify, occ); + GNUNET_SERVER_receive_done (client, GNUNET_OK); +} + + +/** + * Function to cleanup RemoteOverlayConnectCtx and any associated tasks + * with it + * + * @param rocc the RemoteOverlayConnectCtx + */ +static void +cleanup_rocc (struct RemoteOverlayConnectCtx *rocc) +{ + LOG_DEBUG ("0x%llx: Cleaning up rocc\n", rocc->op_id); + if (GNUNET_SCHEDULER_NO_TASK != rocc->attempt_connect_task_id) + GNUNET_SCHEDULER_cancel (rocc->attempt_connect_task_id); + if (GNUNET_SCHEDULER_NO_TASK != rocc->timeout_rocc_task_id) + GNUNET_SCHEDULER_cancel (rocc->timeout_rocc_task_id); + if (NULL != rocc->ohh) + GNUNET_TRANSPORT_offer_hello_cancel (rocc->ohh); + if (NULL != rocc->tcc.tch) + GNUNET_TRANSPORT_try_connect_cancel (rocc->tcc.tch); + if (GNUNET_SCHEDULER_NO_TASK != rocc->tcc.task) + GNUNET_SCHEDULER_cancel (rocc->tcc.task); + //GNUNET_TRANSPORT_disconnect (rocc->tcc.th_); + GST_cache_get_handle_done (rocc->tcc.cgh_th); + rocc->peer->reference_cnt--; + if ((GNUNET_YES == rocc->peer->destroy_flag) && + (0 == rocc->peer->reference_cnt)) + GST_destroy_peer (rocc->peer); + GNUNET_free_non_null (rocc->hello); + GNUNET_CONTAINER_DLL_remove (roccq_head, roccq_tail, rocc); + GNUNET_free (rocc); +} + + +/** + * Task to timeout rocc and cleanit up + * + * @param cls the RemoteOverlayConnectCtx + * @param tc the TaskContext from scheduler + */ +static void +timeout_rocc_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct RemoteOverlayConnectCtx *rocc = cls; + + GNUNET_assert (rocc->timeout_rocc_task_id != GNUNET_SCHEDULER_NO_TASK); + rocc->timeout_rocc_task_id = GNUNET_SCHEDULER_NO_TASK; + LOG_DEBUG ("0x%llx: rocc timed out\n", rocc->op_id); + cleanup_rocc (rocc); +} + + +/** + * Function called to notify transport users that another + * peer connected to us. + * + * @param cls closure + * @param new_peer the peer that connected + * @param ats performance data + * @param ats_count number of entries in ats (excluding 0-termination) + */ +static void +cache_transport_peer_connect_notify (void *cls, + const struct GNUNET_PeerIdentity *new_peer) +{ + struct RemoteOverlayConnectCtx *rocc = cls; + + LOG_DEBUG ("0x%llx: Request Overlay connect notify\n", rocc->op_id); + GNUNET_assert (0 == + memcmp (new_peer, &rocc->a_id, + sizeof (struct GNUNET_PeerIdentity))); + LOG_DEBUG ("0x%llx: Peer %4s connected\n", rocc->op_id, + GNUNET_i2s (&rocc->a_id)); + cleanup_rocc (rocc); +} + + +/** + * Task to offer the HELLO message to the peer and ask it to connect to the peer + * whose identity is in RemoteOverlayConnectCtx + * + * @param cls the RemoteOverlayConnectCtx + * @param tc the TaskContext from scheduler + */ +static void +attempt_connect_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc); + + +/** + * Task that is run when hello has been sent + * + * @param cls the overlay connect context + * @param tc the scheduler task context; if tc->reason = + * GNUNET_SCHEDULER_REASON_TIMEOUT then sending HELLO failed; if + * GNUNET_SCHEDULER_REASON_READ_READY is succeeded + */ +static void +rocc_hello_sent_cb (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct RemoteOverlayConnectCtx *rocc = cls; + + rocc->ohh = NULL; + GNUNET_assert (GNUNET_SCHEDULER_NO_TASK == rocc->attempt_connect_task_id); + LOG_DEBUG ("0x%llx: HELLO of peer %4s sent to local peer with id: %u\n", + rocc->op_id, GNUNET_i2s (&rocc->a_id), rocc->peer->id); + if (GNUNET_SCHEDULER_REASON_TIMEOUT == tc->reason) + { + GNUNET_break (0); + rocc->attempt_connect_task_id = + GNUNET_SCHEDULER_add_now (&attempt_connect_task, rocc); + return; + } + if (GNUNET_SCHEDULER_REASON_READ_READY != tc->reason) + return; + rocc->tcc.task = GNUNET_SCHEDULER_add_now (&try_connect_task, &rocc->tcc); +} + + +/** + * Task to offer the HELLO message to the peer and ask it to connect to the peer + * whose identity is in RemoteOverlayConnectCtx + * + * @param cls the RemoteOverlayConnectCtx + * @param tc the TaskContext from scheduler + */ +static void +attempt_connect_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct RemoteOverlayConnectCtx *rocc = cls; + + GNUNET_assert (GNUNET_SCHEDULER_NO_TASK != rocc->attempt_connect_task_id); + rocc->attempt_connect_task_id = GNUNET_SCHEDULER_NO_TASK; + LOG_DEBUG ("0x%llx: Offering HELLO of peer %4s to local peer with id: %u\n", + rocc->op_id, GNUNET_i2s (&rocc->a_id), rocc->peer->id); + rocc->ohh = + GNUNET_TRANSPORT_offer_hello (rocc->tcc.th_, rocc->hello, + rocc_hello_sent_cb, rocc); + if (NULL == rocc->ohh) + rocc->attempt_connect_task_id = + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply + (GNUNET_TIME_UNIT_MILLISECONDS, + 100 + + GNUNET_CRYPTO_random_u32 + (GNUNET_CRYPTO_QUALITY_WEAK, 500)), + &attempt_connect_task, rocc); +} + + +/** + * Callback from cache with needed handles set + * + * @param cls the closure passed to GST_cache_get_handle_transport() + * @param ch the handle to CORE. Can be NULL if it is not requested + * @param th the handle to TRANSPORT. Can be NULL if it is not requested + * @param ignore_ peer identity which is ignored in this callback + */ +static void +rocc_cache_get_handle_transport_cb (void *cls, struct GNUNET_CORE_Handle *ch, + struct GNUNET_TRANSPORT_Handle *th, + const struct GNUNET_PeerIdentity *ignore_) +{ + struct RemoteOverlayConnectCtx *rocc = cls; + + if (NULL == th) + { + rocc->timeout_rocc_task_id = + GNUNET_SCHEDULER_add_now (&timeout_rocc_task, rocc); + return; + } + rocc->tcc.th_ = th; + rocc->tcc.pid = &rocc->a_id; + if (GNUNET_YES == + GNUNET_TRANSPORT_check_neighbour_connected (rocc->tcc.th_, rocc->tcc.pid)) + { + LOG_DEBUG ("0x%llx: Target peer %4s already connected to local peer: %u\n", + rocc->op_id, GNUNET_i2s (&rocc->a_id), rocc->peer->id); + cleanup_rocc (rocc); + return; + } + rocc->attempt_connect_task_id = + GNUNET_SCHEDULER_add_now (&attempt_connect_task, rocc); +} + + +/** + * Handler for GNUNET_MESSAGE_TYPE_TESTBED_REQUESTCONNECT messages + * + * @param cls NULL + * @param client identification of the client + * @param message the actual message + */ +void +GST_handle_remote_overlay_connect (void *cls, + struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) +{ + const struct GNUNET_TESTBED_RemoteOverlayConnectMessage *msg; + struct RemoteOverlayConnectCtx *rocc; + struct Peer *peer; + uint32_t peer_id; + uint16_t msize; + uint16_t hsize; + + msize = ntohs (message->size); + if (sizeof (struct GNUNET_TESTBED_RemoteOverlayConnectMessage) >= msize) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + msg = (const struct GNUNET_TESTBED_RemoteOverlayConnectMessage *) message; + if ((NULL == msg->hello) || + (GNUNET_MESSAGE_TYPE_HELLO != ntohs (msg->hello->type))) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + hsize = ntohs (msg->hello->size); + if ((sizeof (struct GNUNET_TESTBED_RemoteOverlayConnectMessage) + hsize) != + msize) + { + GNUNET_break (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + peer_id = ntohl (msg->peer); + if ((peer_id >= GST_peer_list_size) || + (NULL == (peer = GST_peer_list[peer_id]))) + { + GNUNET_break_op (0); + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + return; + } + if (GNUNET_YES == peer->is_remote) + { + struct GNUNET_MessageHeader *msg2; + + msg2 = GNUNET_copy_message (message); + GNUNET_TESTBED_queue_message_ (peer->details.remote.slave->controller, + msg2); + GNUNET_SERVER_receive_done (client, GNUNET_OK); + return; + } + rocc = GNUNET_malloc (sizeof (struct RemoteOverlayConnectCtx)); + rocc->op_id = GNUNET_ntohll (msg->operation_id); + GNUNET_CONTAINER_DLL_insert_tail (roccq_head, roccq_tail, rocc); + memcpy (&rocc->a_id, &msg->peer_identity, + sizeof (struct GNUNET_PeerIdentity)); + LOG_DEBUG ("Received request for overlay connection with op_id: 0x%llx " + "from local peer %u to peer %4s with hello size: %u\n", + rocc->op_id, peer_id, GNUNET_i2s (&rocc->a_id), hsize); + rocc->peer = peer; + rocc->peer->reference_cnt++; + rocc->hello = GNUNET_malloc (hsize); + memcpy (rocc->hello, msg->hello, hsize); + rocc->tcc.cgh_th = + GST_cache_get_handle_transport (peer_id, rocc->peer->details.local.cfg, + &rocc_cache_get_handle_transport_cb, rocc, + &rocc->a_id, + &cache_transport_peer_connect_notify, + rocc); + rocc->timeout_rocc_task_id = + GNUNET_SCHEDULER_add_delayed (TIMEOUT, &timeout_rocc_task, rocc); + GNUNET_SERVER_receive_done (client, GNUNET_OK); +} + + +/** + * Clears all pending overlay connect contexts in queue + */ +void +GST_free_occq () +{ + struct OverlayConnectContext *occ; + + while (NULL != (occ = occq_head)) + cleanup_occ (occ); +} + + +/** + * Clears all pending remote overlay connect contexts in queue + */ +void +GST_free_roccq () +{ + struct RemoteOverlayConnectCtx *rocc; + + while (NULL != (rocc = roccq_head)) + cleanup_rocc (rocc); +} diff --git a/src/testbed/gnunet-testbed-profiler.c b/src/testbed/gnunet-testbed-profiler.c new file mode 100644 index 0000000..ebb82df --- /dev/null +++ b/src/testbed/gnunet-testbed-profiler.c @@ -0,0 +1,283 @@ +/* + This file is part of GNUnet. + (C) 2011, 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @file testbed/gnunet-testbed-profiler.c + * @brief Profiling driver for the testbed. + * @author Sree Harsha Totakura + */ + +#include "platform.h" +#include "gnunet_common.h" +#include "gnunet_util_lib.h" +#include "gnunet_testbed_service.h" +#include "testbed_api_hosts.h" + +/** + * Generic loggins shorthand + */ +#define LOG(kind,...) \ + GNUNET_log (kind, __VA_ARGS__) + + +/** + * Handle to global configuration + */ +struct GNUNET_CONFIGURATION_Handle *cfg; + +/** + * Peer linking - topology operation + */ +struct GNUNET_TESTBED_Operation *topology_op; + +/** + * Abort task identifier + */ +static GNUNET_SCHEDULER_TaskIdentifier abort_task; + +/** + * Shutdown task identifier + */ +static GNUNET_SCHEDULER_TaskIdentifier shutdown_task; + +/** + * Global event mask for all testbed events + */ +uint64_t event_mask; + +/** + * Number of peers to be started by the profiler + */ +static unsigned int num_peers; + +/** + * Number of timeout failures to tolerate + */ +static unsigned int num_cont_fails; + +/** + * Continuous failures during overlay connect operations + */ +static unsigned int cont_fails; + +/** + * Links which are successfully established + */ +static unsigned int established_links; + +/** + * Links which are not successfully established + */ +static unsigned int failed_links; + +/** + * Global testing status + */ +static int result; + + +/** + * Shutdown nicely + * + * @param cls NULL + * @param tc the task context + */ +static void +do_shutdown (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + shutdown_task = GNUNET_SCHEDULER_NO_TASK; + if (GNUNET_SCHEDULER_NO_TASK != abort_task) + GNUNET_SCHEDULER_cancel (abort_task); + if (NULL != cfg) + GNUNET_CONFIGURATION_destroy (cfg); + GNUNET_SCHEDULER_shutdown (); /* Stop scheduler to shutdown testbed run */ +} + + +/** + * abort task to run on test timed out + * + * @param cls NULL + * @param tc the task context + */ +static void +do_abort (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + LOG (GNUNET_ERROR_TYPE_WARNING, "Aborting\n"); + abort_task = GNUNET_SCHEDULER_NO_TASK; + result = GNUNET_SYSERR; + if (GNUNET_SCHEDULER_NO_TASK != shutdown_task) + GNUNET_SCHEDULER_cancel (shutdown_task); + shutdown_task = GNUNET_SCHEDULER_add_now (&do_shutdown, NULL); +} + + +/** + * Function to print summary about how many overlay links we have made and how + * many failed + */ +static void +print_overlay_links_summary () +{ + static int printed_already; + + if (GNUNET_YES == printed_already) + return; + printed_already = GNUNET_YES; + printf ("%u links succeeded\n", established_links); + printf ("%u links failed due to timeouts\n", failed_links); +} + + +/** + * Controller event callback + * + * @param cls NULL + * @param event the controller event + */ +static void +controller_event_cb (void *cls, + const struct GNUNET_TESTBED_EventInformation *event) +{ + switch (event->type) + { + case GNUNET_TESTBED_ET_OPERATION_FINISHED: + /* Control reaches here when a peer linking operation fails */ + if (NULL != event->details.operation_finished.emsg) + { + printf ("F"); + fflush (stdout); + failed_links++; + if (++cont_fails > num_cont_fails) + { + printf ("\nAborting due to very high failure rate\n"); + print_overlay_links_summary (); + GNUNET_SCHEDULER_cancel (abort_task); + abort_task = GNUNET_SCHEDULER_add_now (&do_abort, NULL); + return; + } + } + break; + case GNUNET_TESTBED_ET_CONNECT: + { + if (0 != cont_fails) + cont_fails--; + if (0 == established_links) + printf ("Establishing links. Please wait\n"); + printf ("."); + fflush (stdout); + established_links++; + } + break; + default: + GNUNET_break (0); + } +} + + +/** + * Signature of a main function for a testcase. + * + * @param cls closure + * @param num_peers number of peers in 'peers' + * @param peers handle to peers run in the testbed + */ +static void +test_run (void *cls, unsigned int num_peers, struct GNUNET_TESTBED_Peer **peers) +{ + result = GNUNET_OK; + fprintf (stdout, "\n"); + print_overlay_links_summary (); + fprintf (stdout, "Testbed running, waiting for keystroke to shut down\n"); + fflush (stdout); + (void) getc (stdin); + fprintf (stdout, "Shutting down. Please wait\n"); + fflush (stdout); + shutdown_task = GNUNET_SCHEDULER_add_now (&do_shutdown, NULL); +} + + +/** + * Main function that will be run by the scheduler. + * + * @param cls closure + * @param args remaining command-line arguments + * @param cfgfile name of the configuration file used (for saving, can be NULL!) + * @param config configuration + */ +static void +run (void *cls, char *const *args, const char *cfgfile, + const struct GNUNET_CONFIGURATION_Handle *config) +{ + if (NULL == args[0]) + { + fprintf (stderr, _("No hosts-file specified on command line\n")); + return; + } + if (0 == num_peers) + { + result = GNUNET_OK; + return; + } + cfg = GNUNET_CONFIGURATION_dup (config); + event_mask = 0; + event_mask |= (1LL << GNUNET_TESTBED_ET_CONNECT); + event_mask |= (1LL << GNUNET_TESTBED_ET_OPERATION_FINISHED); + GNUNET_TESTBED_run (args[0], cfg, num_peers, event_mask, controller_event_cb, + NULL, &test_run, NULL); + abort_task = + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, &do_abort, + NULL); +} + + +/** + * Main function. + * + * @return 0 on success + */ +int +main (int argc, char *const *argv) +{ + static const struct GNUNET_GETOPT_CommandLineOption options[] = { + {'p', "num-peers", "COUNT", + gettext_noop ("create COUNT number of peers"), + GNUNET_YES, &GNUNET_GETOPT_set_uint, &num_peers}, + {'e', "num-errors", "COUNT", + gettext_noop ("tolerate COUNT number of continious timeout failures"), + GNUNET_YES, &GNUNET_GETOPT_set_uint, &num_cont_fails}, + GNUNET_GETOPT_OPTION_END + }; + int ret; + + if (GNUNET_OK != GNUNET_STRINGS_get_utf8_args (argc, argv, &argc, &argv)) + return 2; + result = GNUNET_SYSERR; + ret = + GNUNET_PROGRAM_run (argc, argv, + "gnunet-testbed-profiler [OPTIONS] hosts-file", + _("Profiler for testbed"), options, &run, NULL); + GNUNET_free ((void *) argv); + if (GNUNET_OK != ret) + return ret; + if (GNUNET_OK != result) + return 1; + return 0; +} diff --git a/src/testbed/gnunet_mpi_test.c b/src/testbed/gnunet_mpi_test.c new file mode 100644 index 0000000..fded9e2 --- /dev/null +++ b/src/testbed/gnunet_mpi_test.c @@ -0,0 +1,107 @@ +#include "platform.h" +#include "gnunet_util_lib.h" +#include + +/** + * Generic logging shorthand + */ +#define LOG(kind,...) \ + GNUNET_log_from (kind, "gnunet-mpi-test", __VA_ARGS__) + +int +main (int argc, char *argv[]) +{ + char *msg; + char *filename; + char **argv2; + struct GNUNET_OS_Process *proc; + unsigned long code; + pid_t pid; + enum GNUNET_OS_ProcessStatusType proc_status; + int ntasks; + int rank; + int msg_size; + int ret; + unsigned int cnt; + + ret = GNUNET_SYSERR; + if (argc < 2) + { + printf ("Need arguments: gnunet-mpi-test "); + return 1; + } + if (MPI_SUCCESS != MPI_Init (&argc, &argv)) + { + GNUNET_break (0); + return 1; + } + if (MPI_SUCCESS != MPI_Comm_size (MPI_COMM_WORLD, &ntasks)) + { + GNUNET_break (0); + goto finalize; + } + if (MPI_SUCCESS != MPI_Comm_rank (MPI_COMM_WORLD, &rank)) + { + GNUNET_break (0); + goto finalize; + } + pid = getpid (); + (void) GNUNET_asprintf (&filename, "%d-%d.mpiout", (int) pid, rank); + msg_size = GNUNET_asprintf (&msg, "My rank is: %d\n", rank); + printf ("%s", msg); + if (msg_size == + GNUNET_DISK_fn_write (filename, msg, msg_size, + GNUNET_DISK_PERM_USER_READ | + GNUNET_DISK_PERM_GROUP_READ | + GNUNET_DISK_PERM_USER_WRITE | + GNUNET_DISK_PERM_GROUP_WRITE)) + ret = GNUNET_OK; + GNUNET_free (filename); + GNUNET_free (msg); + if (GNUNET_OK != ret) + { + GNUNET_break (0); + goto finalize; + } + + ret = GNUNET_SYSERR; + argv2 = GNUNET_malloc (sizeof (char *) * (argc)); + for (cnt = 1; cnt < argc; cnt++) + argv2[cnt - 1] = argv[cnt]; + proc = + GNUNET_OS_start_process_vap (GNUNET_NO, GNUNET_OS_INHERIT_STD_ALL, NULL, + NULL, argv2[0], argv2); + if (NULL == proc) + { + printf ("Cannot exec\n"); + GNUNET_free (argv2); + goto finalize; + } + do + { + (void) sleep (1); + ret = GNUNET_OS_process_status (proc, &proc_status, &code); + } + while (GNUNET_NO == ret); + GNUNET_free (argv2); + GNUNET_assert (GNUNET_NO != ret); + if (GNUNET_OK == ret) + { + if (0 != code) + { + LOG (GNUNET_ERROR_TYPE_WARNING, "Child terminated abnormally\n"); + ret = GNUNET_SYSERR; + GNUNET_break (0); + goto finalize; + } + } + else + GNUNET_break (0); + +finalize: + (void) MPI_Finalize (); + if (GNUNET_OK == ret) + return 0; + printf ("Something went wrong\n"); + return 1; +} diff --git a/src/testbed/ll_master.c b/src/testbed/ll_master.c new file mode 100644 index 0000000..98cef42 --- /dev/null +++ b/src/testbed/ll_master.c @@ -0,0 +1,92 @@ +/* + This file is part of GNUnet + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. + */ + +/** + * @file testbed/ll_master.c + * @brief The load level master. Creates child processes through LoadLeveler + * @author Sree Harsha Totakura + */ + +#include "platform.h" +#include "gnunet_util_lib.h" +#include + +/** + * LL job information + */ +static struct LL_job job_info; + +/** + * Exit status + */ +static int status; + +/** + * Main function that will be run. + * + * @param cls closure + * @param args remaining command-line arguments + * @param cfgfile name of the configuration file used (for saving, can be NULL!) + * @param cfg configuration + */ +static void +run (void *cls, char *const *args, const char *cfgfile, + const struct GNUNET_CONFIGURATION_Handle *cfg) +{ + int ret; + + if (NULL == args[0]) + { + fprintf (stderr, _("Job command file not given. Exiting\n")); + return; + } + ret = llsubmit (args[0], NULL, //char *monitor_program, + NULL, //char *monitor_arg, + &job_info, LL_JOB_VERSION); + if (0 != ret) + return; + status = GNUNET_OK; +} + + +/** + * Main function + * + * @param argc the number of command line arguments + * @param argv command line arg array + * @return return code + */ +int +main (int argc, char **argv) +{ + struct GNUNET_GETOPT_CommandLineOption options[] = { + GNUNET_GETOPT_OPTION_END + }; + int ret; + + status = GNUNET_SYSERR; + ret = + GNUNET_PROGRAM_run (argc, argv, "ll-master", + "LoadLeveler master process for starting child processes", + options, &run, NULL); + if (GNUNET_OK != ret) + return 1; + return (GNUNET_OK == status) ? 0 : 1; +} diff --git a/src/testbed/ll_monitor.c b/src/testbed/ll_monitor.c new file mode 100644 index 0000000..3a43b49 --- /dev/null +++ b/src/testbed/ll_monitor.c @@ -0,0 +1,76 @@ +/* + This file is part of GNUnet + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. + */ + +/** + * @file testbed/ll_monitor.c + * @brief The load level monitor process. This is called whenever a job event + * happens. This file is called with the following syntax: + * "monitor_program job_id user_arg state exit_status" + * @author Sree Harsha Totakura + */ + +#include "platform.h" +#include "gnunet_common.h" +#include + + +/** + * Main function + * + * @param argc the number of command line arguments + * @param argv command line arg array + * @return return code + */ +int +main (int argc, char **argv) +{ + char *job_id; + char *user_arg; + char *state; + char *exit_status; + char *outfile; + FILE *out; + + if (5 != argc) + { + fprintf (stderr, "Invalid number of arguments\n"); + return 1; + } + job_id = argv[1]; + user_arg = argv[2]; + state = argv[3]; + exit_status = argv[4]; + PRINTF ("Job id: %s\n", job_id); + PRINTF ("\t User arg: %s \n", user_arg); + PRINTF ("\t Job state: %s \n", state); + PRINTF ("\t Exit status: %s \n", exit_status); + + if (-1 == asprintf (&outfile, "job-%s.status", job_id)) + return 1; + out = fopen (outfile, "a"); + if (NULL == out) + return 1; + fprintf (out, "Job id: %s\n", job_id); + fprintf (out, "\t User arg: %s \n", user_arg); + fprintf (out, "\t Job state: %s \n", state); + fprintf (out, "\t Exit status: %s \n", exit_status); + fclose (out); + return 0; +} diff --git a/src/testbed/overlay_topology.txt b/src/testbed/overlay_topology.txt new file mode 100644 index 0000000..420dbb6 --- /dev/null +++ b/src/testbed/overlay_topology.txt @@ -0,0 +1,5 @@ + +1:2|3 +3:4| 0| 1 +2: 3|1|0 +0: 2 diff --git a/src/testbed/sample.job b/src/testbed/sample.job new file mode 100755 index 0000000..da3ee47 --- /dev/null +++ b/src/testbed/sample.job @@ -0,0 +1,16 @@ +#!/bin/bash +# This job command file is called job.cmd +#@ job_type = parallel +#@ class = general +#@ node = 1 +#@ output = job$(jobid).out +#@ error = job$(jobid).err +#@ total_tasks=16 +#@ wall_clock_limit = 0:0:1 +#@ network.MPI = sn_all,not_shared,us +##@ ... other LoadLeveler keywords (see below) +#@ notification = always +#@ notify_user = totakura@in.tum.de +#@ queue + +#@ executable = /bin/bash diff --git a/src/testbed/sample_hosts.txt b/src/testbed/sample_hosts.txt new file mode 100644 index 0000000..5b66169 --- /dev/null +++ b/src/testbed/sample_hosts.txt @@ -0,0 +1,15 @@ +totakura@192.168.0.1:22 +totakura@192.168.0.2:22 +totakura@192.168.0.3:22 +totakura@192.168.0.4:22 +totakura@192.168.0.5:22 +totakura@192.168.0.6:22 +totakura@192.168.0.7:22 +totakura@192.168.0.8:22 +totakura@192.168.0.9:22 +totakura@192.168.0.10:22 +totakura@192.168.0.11:22 +totakura@192.168.0.12:22 +totakura@192.168.0.13:22 +totakura@192.168.0.14:22 +totakura@192.168.0.15:22 diff --git a/src/testbed/test_gnunet_helper_testbed.c b/src/testbed/test_gnunet_helper_testbed.c new file mode 100644 index 0000000..db889c1 --- /dev/null +++ b/src/testbed/test_gnunet_helper_testbed.c @@ -0,0 +1,249 @@ +/* + This file is part of GNUnet + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. + */ + +/** + * @file testbed/test_gnunet_helper_testbed.c + * @brief Testcase for testing gnunet-helper-testbed.c + * @author Sree Harsha Totakura + */ + +#include "platform.h" +#include "gnunet_util_lib.h" +#include "gnunet_testbed_service.h" +#include + +#include "testbed_api.h" +#include "testbed_helper.h" +#include "testbed_api_hosts.h" + +/** + * Generic logging shortcut + */ +#define LOG(kind,...) \ + GNUNET_log (kind, __VA_ARGS__) + + +/** + * Handle to the helper process + */ +static struct GNUNET_HELPER_Handle *helper; + +/** + * Message to helper + */ +static struct GNUNET_TESTBED_HelperInit *msg; + +/** + * Message send handle + */ +static struct GNUNET_HELPER_SendHandle *shandle; + +/** + * Abort task identifier + */ +static GNUNET_SCHEDULER_TaskIdentifier abort_task; + +/** + * Shutdown task identifier + */ +static GNUNET_SCHEDULER_TaskIdentifier shutdown_task; + +/** + * Configuratin handler + */ +static struct GNUNET_CONFIGURATION_Handle *cfg; + +/** + * Global testing status + */ +static int result; + + +/** + * Shutdown nicely + * + * @param cls NULL + * @param tc the task context + */ +static void +do_shutdown (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + if (GNUNET_SCHEDULER_NO_TASK != abort_task) + GNUNET_SCHEDULER_cancel (abort_task); + GNUNET_HELPER_stop (helper); + GNUNET_free_non_null (msg); + if (NULL != cfg) + GNUNET_CONFIGURATION_destroy (cfg); +} + + +/** + * abort task to run on test timed out + * + * @param cls NULL + * @param tc the task context + */ +static void +do_abort (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + abort_task = GNUNET_SCHEDULER_NO_TASK; + LOG (GNUNET_ERROR_TYPE_WARNING, "Test timedout -- Aborting\n"); + result = GNUNET_SYSERR; + if (NULL != shandle) + GNUNET_HELPER_send_cancel (shandle); + if (GNUNET_SCHEDULER_NO_TASK == shutdown_task) + shutdown_task = GNUNET_SCHEDULER_add_now (&do_shutdown, NULL); +} + + +/** + * Continuation function. + * + * @param cls closure + * @param result GNUNET_OK on success, + * GNUNET_NO if helper process died + * GNUNET_SYSERR during GNUNET_HELPER_stop + */ +static void +cont_cb (void *cls, int result) +{ + shandle = NULL; + LOG (GNUNET_ERROR_TYPE_DEBUG, "Message sent\n"); + GNUNET_assert (GNUNET_OK == result); +} + + +/** + * Functions with this signature are called whenever a + * complete message is received by the tokenizer. + * + * Do not call GNUNET_SERVER_mst_destroy in callback + * + * @param cls closure + * @param client identification of the client + * @param message the actual message + * + * @return GNUNET_OK on success, GNUNET_SYSERR to stop further processing + */ +static int +mst_cb (void *cls, void *client, const struct GNUNET_MessageHeader *message) +{ + const struct GNUNET_TESTBED_HelperReply *msg; + char *config; + uLongf config_size; + uLongf xconfig_size; + + msg = (const struct GNUNET_TESTBED_HelperReply *) message; + config_size = 0; + xconfig_size = 0; + GNUNET_assert (sizeof (struct GNUNET_TESTBED_HelperReply) < + ntohs (msg->header.size)); + GNUNET_assert (GNUNET_MESSAGE_TYPE_TESTBED_HELPER_REPLY == + ntohs (msg->header.type)); + config_size = (uLongf) ntohs (msg->config_size); + xconfig_size = + (uLongf) (ntohs (msg->header.size) - + sizeof (struct GNUNET_TESTBED_HelperReply)); + config = GNUNET_malloc (config_size); + GNUNET_assert (Z_OK == + uncompress ((Bytef *) config, &config_size, + (const Bytef *) &msg[1], xconfig_size)); + GNUNET_free (config); + if (GNUNET_SCHEDULER_NO_TASK == shutdown_task) + shutdown_task = + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply + (GNUNET_TIME_UNIT_SECONDS, 1), + &do_shutdown, NULL); + return GNUNET_OK; +} + + +/** + * Callback that will be called when the helper process dies. This is not called + * when the helper process is stoped using GNUNET_HELPER_stop() + * + * @param cls the closure from GNUNET_HELPER_start() + */ +static void +exp_cb (void *cls) +{ + helper = NULL; + result = GNUNET_SYSERR; +} + + +/** + * Main function that will be run. + * + * @param cls closure + * @param args remaining command-line arguments + * @param cfgfile name of the configuration file used (for saving, can be NULL!) + * @param cfg configuration + */ +static void +run (void *cls, char *const *args, const char *cfgfile, + const struct GNUNET_CONFIGURATION_Handle *cfg2) +{ + static char *const binary_argv[] = { + "gnunet-helper-testbed", + NULL + }; + const char *controller_name = "127.0.0.1"; + + helper = + GNUNET_HELPER_start (GNUNET_YES, "gnunet-helper-testbed", binary_argv, + &mst_cb, &exp_cb, NULL); + GNUNET_assert (NULL != helper); + cfg = GNUNET_CONFIGURATION_dup (cfg2); + msg = GNUNET_TESTBED_create_helper_init_msg_ (controller_name, NULL, cfg); + shandle = + GNUNET_HELPER_send (helper, &msg->header, GNUNET_NO, &cont_cb, NULL); + GNUNET_assert (NULL != shandle); + abort_task = + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply + (GNUNET_TIME_UNIT_MINUTES, 1), &do_abort, + NULL); +} + + +/** + * Main function + * + * @param argc the number of command line arguments + * @param argv command line arg array + * @return return code + */ +int +main (int argc, char **argv) +{ + struct GNUNET_GETOPT_CommandLineOption options[] = { + GNUNET_GETOPT_OPTION_END + }; + + result = GNUNET_OK; + if (GNUNET_OK != + GNUNET_PROGRAM_run (argc, argv, "test_gnunet_helper_testbed", + "Testcase for testing gnunet-helper-testbed.c", + options, &run, NULL)) + return 1; + return (GNUNET_OK == result) ? 0 : 1; +} + +/* end of test_gnunet_helper_testbed.c */ diff --git a/src/testbed/test_testbed_api.c b/src/testbed/test_testbed_api.c new file mode 100644 index 0000000..c5c4486 --- /dev/null +++ b/src/testbed/test_testbed_api.c @@ -0,0 +1,464 @@ +/* + This file is part of GNUnet + (C) 2008--2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. + */ + +/** + * @file testbed/test_testbed_api.c + * @brief testcases for the testbed api + * @author Sree Harsha Totakura + */ + +#include "platform.h" +#include "gnunet_util_lib.h" +#include "gnunet_dht_service.h" +#include "gnunet_testing_lib.h" +#include "gnunet_testbed_service.h" + +/** + * Generic logging shortcut + */ +#define LOG(kind,...) \ + GNUNET_log (kind, __VA_ARGS__) + +/** + * Relative time seconds shorthand + */ +#define TIME_REL_SECS(sec) \ + GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, sec) + +/** + * Our localhost + */ +static struct GNUNET_TESTBED_Host *host; + +/** + * The controller process + */ +static struct GNUNET_TESTBED_ControllerProc *cp; + +/** + * The controller handle + */ +static struct GNUNET_TESTBED_Controller *controller; + +/** + * A neighbouring host + */ +static struct GNUNET_TESTBED_Host *neighbour; + +/** + * Handle for neighbour registration + */ +static struct GNUNET_TESTBED_HostRegistrationHandle *reg_handle; + +/** + * Handle for a peer + */ +static struct GNUNET_TESTBED_Peer *peer; + +/** + * Handle to configuration + */ +static struct GNUNET_CONFIGURATION_Handle *cfg; + +/** + * Handle to operation + */ +static struct GNUNET_TESTBED_Operation *operation; + +/** + * Handle to peer's DHT service + */ +static struct GNUNET_DHT_Handle *dht_handle; + +/** + * Abort task identifier + */ +static GNUNET_SCHEDULER_TaskIdentifier abort_task; + +/** + * The testing result + */ +static int result; + + +/** + * Enumeration of sub testcases + */ +enum Test +{ + /** + * Test cases which are not covered by the below ones + */ + OTHER, + + /** + * Test where we get a peer config from controller + */ + PEER_GETCONFIG, + + /** + * Test where we connect to a service running on the peer + */ + PEER_SERVICE_CONNECT, + + /** + * Test where we get a peer's identity from controller + */ + PEER_DESTROY, +}; + +/** + * Testing status + */ +static enum Test sub_test; + +/** + * Shutdown nicely + * + * @param cls NULL + * @param tc the task context + */ +static void +do_shutdown (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + LOG (GNUNET_ERROR_TYPE_DEBUG, "Shutting down...\n"); + if (GNUNET_SCHEDULER_NO_TASK != abort_task) + GNUNET_SCHEDULER_cancel (abort_task); + if (NULL != reg_handle) + GNUNET_TESTBED_cancel_registration (reg_handle); + GNUNET_TESTBED_controller_disconnect (controller); + GNUNET_CONFIGURATION_destroy (cfg); + if (NULL != cp) + GNUNET_TESTBED_controller_stop (cp); + GNUNET_TESTBED_host_destroy (neighbour); + GNUNET_TESTBED_host_destroy (host); +} + + +/** + * abort task to run on test timed out + * + * @param cls NULL + * @param tc the task context + */ +static void +do_abort (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + LOG (GNUNET_ERROR_TYPE_WARNING, "Test timedout -- Aborting\n"); + abort_task = GNUNET_SCHEDULER_NO_TASK; + do_shutdown (cls, tc); +} + + +/** + * Adapter function called to establish a connection to + * a service. + * + * @param cls closure + * @param cfg configuration of the peer to connect to; will be available until + * GNUNET_TESTBED_operation_done() is called on the operation returned + * from GNUNET_TESTBED_service_connect() + * @return service handle to return in 'op_result', NULL on error + */ +static void * +dht_connect_adapter (void *cls, const struct GNUNET_CONFIGURATION_Handle *cfg) +{ + GNUNET_assert (NULL == cls); + GNUNET_assert (OTHER == sub_test); + sub_test = PEER_SERVICE_CONNECT; + dht_handle = GNUNET_DHT_connect (cfg, 10); + return dht_handle; +} + + +/** + * Adapter function called to destroy a connection to + * a service. + * + * @param cls closure + * @param op_result service handle returned from the connect adapter + */ +static void +dht_disconnect_adapter (void *cls, void *op_result) +{ + GNUNET_assert (NULL != op_result); + GNUNET_assert (op_result == dht_handle); + GNUNET_DHT_disconnect (dht_handle); + dht_handle = NULL; + GNUNET_assert (PEER_SERVICE_CONNECT == sub_test); + GNUNET_assert (NULL != operation); + operation = GNUNET_TESTBED_peer_stop (peer, NULL, NULL); + GNUNET_assert (NULL != operation); +} + + +/** + * Callback to be called when a service connect operation is completed + * + * @param cls the callback closure from functions generating an operation + * @param op the operation that has been finished + * @param ca_result the service handle returned from GNUNET_TESTBED_ConnectAdapter() + * @param emsg error message in case the operation has failed; will be NULL if + * operation has executed successfully. + */ +static void +service_connect_comp_cb (void *cls, struct GNUNET_TESTBED_Operation *op, + void *ca_result, const char *emsg) +{ + switch (sub_test) + { + case PEER_SERVICE_CONNECT: + GNUNET_assert (operation == op); + GNUNET_assert (NULL == emsg); + GNUNET_assert (NULL == cls); + GNUNET_assert (ca_result == dht_handle); + GNUNET_TESTBED_operation_done (operation); /* This results in call to + * disconnect adapter */ + break; + default: + GNUNET_assert (0); + } +} + + + +/** + * Callback to be called when the requested peer information is available + * + * @param cb_cls the closure from GNUNET_TETSBED_peer_get_information() + * @param op the operation this callback corresponds to + * @param pinfo the result; will be NULL if the operation has failed + * @param emsg error message if the operation has failed; will be NULL if the + * operation is successfull + */ +static void +peerinfo_cb (void *cb_cls, struct GNUNET_TESTBED_Operation *op, + const struct GNUNET_TESTBED_PeerInformation *pinfo, + const char *emsg) +{ + switch (sub_test) + { + case PEER_GETCONFIG: + GNUNET_assert (NULL != pinfo); + GNUNET_assert (NULL == emsg); + GNUNET_assert (NULL == cb_cls); + GNUNET_assert (operation == op); + GNUNET_assert (GNUNET_TESTBED_PIT_CONFIGURATION == pinfo->pit); + GNUNET_assert (NULL != pinfo->result.cfg); + sub_test = PEER_DESTROY; + GNUNET_TESTBED_operation_done (operation); + operation = GNUNET_TESTBED_peer_destroy (peer); + break; + default: + GNUNET_assert (0); + } +} + + +/** + * Signature of the event handler function called by the + * respective event controller. + * + * @param cls closure + * @param event information about the event + */ +static void +controller_cb (void *cls, const struct GNUNET_TESTBED_EventInformation *event) +{ + switch (event->type) + { + case GNUNET_TESTBED_ET_OPERATION_FINISHED: + switch (sub_test) + { + case PEER_DESTROY: + GNUNET_assert (event->details.operation_finished.operation == operation); + GNUNET_assert (NULL == event->details.operation_finished.op_cls); + GNUNET_assert (NULL == event->details.operation_finished.emsg); + GNUNET_assert (NULL == event->details.operation_finished.generic); + GNUNET_TESTBED_operation_done (operation); + GNUNET_SCHEDULER_add_now (&do_shutdown, NULL); + break; + case PEER_SERVICE_CONNECT: + GNUNET_assert (event->details.operation_finished.operation == operation); + GNUNET_assert (NULL == event->details.operation_finished.op_cls); + GNUNET_assert (NULL == event->details.operation_finished.emsg); + GNUNET_assert (NULL != dht_handle); + GNUNET_assert (event->details.operation_finished.generic == dht_handle); + break; + default: + GNUNET_assert (0); + break; + } + break; + case GNUNET_TESTBED_ET_PEER_START: + GNUNET_assert (event->details.peer_start.host == host); + GNUNET_assert (event->details.peer_start.peer == peer); + GNUNET_assert (OTHER == sub_test); + GNUNET_TESTBED_operation_done (operation); + operation = + GNUNET_TESTBED_service_connect (NULL, peer, "dht", + &service_connect_comp_cb, NULL, + &dht_connect_adapter, + &dht_disconnect_adapter, NULL); + GNUNET_assert (NULL != operation); + break; + case GNUNET_TESTBED_ET_PEER_STOP: + GNUNET_assert (event->details.peer_stop.peer == peer); + GNUNET_assert (PEER_SERVICE_CONNECT == sub_test); + result = GNUNET_YES; + sub_test = PEER_GETCONFIG; + GNUNET_TESTBED_operation_done (operation); + operation = + GNUNET_TESTBED_peer_get_information (peer, + GNUNET_TESTBED_PIT_CONFIGURATION, + &peerinfo_cb, NULL); + break; + default: + GNUNET_assert (0); /* We should never reach this state */ + } +} + + +/** + * Functions of this signature are called when a peer has been successfully + * created + * + * @param cls the closure from GNUNET_TESTBED_peer_create() + * @param peer the handle for the created peer; NULL on any error during + * creation + * @param emsg NULL if peer is not NULL; else MAY contain the error description + */ +static void +peer_create_cb (void *cls, struct GNUNET_TESTBED_Peer *peer, const char *emsg) +{ + struct GNUNET_TESTBED_Peer **peer_ptr; + + peer_ptr = cls; + GNUNET_assert (NULL != peer); + GNUNET_assert (NULL != peer_ptr); + *peer_ptr = peer; + GNUNET_TESTBED_operation_done (operation); + operation = GNUNET_TESTBED_peer_start (NULL, peer, NULL, NULL); + GNUNET_assert (NULL != operation); +} + + +/** + * Callback which will be called to after a host registration succeeded or failed + * + * @param cls the host which has been registered + * @param emsg the error message; NULL if host registration is successful + */ +static void +registration_comp (void *cls, const char *emsg) +{ + GNUNET_assert (cls == neighbour); + reg_handle = NULL; + operation = + GNUNET_TESTBED_peer_create (controller, host, cfg, &peer_create_cb, + &peer); + GNUNET_assert (NULL != operation); +} + + +/** + * Callback to signal successfull startup of the controller process + * + * @param cls the closure from GNUNET_TESTBED_controller_start() + * @param cfg the configuration with which the controller has been started; + * NULL if status is not GNUNET_OK + * @param status GNUNET_OK if the startup is successfull; GNUNET_SYSERR if not, + * GNUNET_TESTBED_controller_stop() shouldn't be called in this case + */ +static void +status_cb (void *cls, const struct GNUNET_CONFIGURATION_Handle *cfg, int status) +{ + uint64_t event_mask; + + GNUNET_assert (GNUNET_OK == status); + event_mask = 0; + event_mask |= (1L << GNUNET_TESTBED_ET_PEER_START); + event_mask |= (1L << GNUNET_TESTBED_ET_PEER_STOP); + event_mask |= (1L << GNUNET_TESTBED_ET_CONNECT); + event_mask |= (1L << GNUNET_TESTBED_ET_OPERATION_FINISHED); + controller = + GNUNET_TESTBED_controller_connect (cfg, host, event_mask, &controller_cb, + NULL); + GNUNET_assert (NULL != controller); + neighbour = GNUNET_TESTBED_host_create ("localhost", NULL, 0); + GNUNET_assert (NULL != neighbour); + reg_handle = + GNUNET_TESTBED_register_host (controller, neighbour, ®istration_comp, + neighbour); + GNUNET_assert (NULL != reg_handle); +} + + + +/** + * Main run function. + * + * @param cls NULL + * @param args arguments passed to GNUNET_PROGRAM_run + * @param cfgfile the path to configuration file + * @param cfg the configuration file handle + */ +static void +run (void *cls, char *const *args, const char *cfgfile, + const struct GNUNET_CONFIGURATION_Handle *config) +{ + host = GNUNET_TESTBED_host_create (NULL, NULL, 0); + GNUNET_assert (NULL != host); + cfg = GNUNET_CONFIGURATION_dup (config); + cp = GNUNET_TESTBED_controller_start ("127.0.0.1", host, cfg, status_cb, + NULL); + abort_task = + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply + (GNUNET_TIME_UNIT_MINUTES, 5), &do_abort, + NULL); +} + + +/** + * Main function + */ +int +main (int argc, char **argv) +{ + int ret; + + char *const argv2[] = { "test_testbed_api", + "-c", "test_testbed_api.conf", + NULL + }; + struct GNUNET_GETOPT_CommandLineOption options[] = { + GNUNET_GETOPT_OPTION_END + }; + + result = GNUNET_SYSERR; + ret = + GNUNET_PROGRAM_run ((sizeof (argv2) / sizeof (char *)) - 1, argv2, + "test_testbed_api", "nohelp", options, &run, NULL); + if ((GNUNET_OK != ret) || (GNUNET_OK != result)) + return 1; + return 0; +} + +/* end of test_testbed_api.c */ diff --git a/src/testbed/test_testbed_api.conf b/src/testbed/test_testbed_api.conf new file mode 100644 index 0000000..52e0c9b --- /dev/null +++ b/src/testbed/test_testbed_api.conf @@ -0,0 +1,91 @@ +[testbed] +AUTOSTART = NO +PORT = 12113 +ACCEPT_FROM = 127.0.0.1; +HOSTNAME = localhost +NEIGHBOUR_LIMIT = 100 +TOPOLOGY = RANDOM +#PREFIX = xterm -geometry 100x85 -T peer1 -e libtool --mode=execute gdb --args + +[fs] +AUTOSTART = NO + +[resolver] +AUTOSTART = NO + +[mesh] +AUTOSTART = NO + +[dht] +AUTOSTART = NO + +[block] +plugins = dht test + +[dhtcache] +QUOTA = 1 MB +DATABASE = sqlite + +[transport] +PLUGINS = tcp +ACCEPT_FROM6 = ::1; +ACCEPT_FROM = 127.0.0.1; +NEIGHBOUR_LIMIT = 50 +PORT = 12365 + +[ats] +WAN_QUOTA_OUT = 3932160 +WAN_QUOTA_IN = 3932160 + +[core] +PORT = 12092 +AUTOSTART = YES + +[arm] +DEFAULTSERVICES = core transport +PORT = 12366 + +[transport-tcp] +TIMEOUT = 300 s +PORT = 12368 + +[TESTING] +NUM_PEERS = 5 +WEAKRANDOM = YES +HOSTKEYSFILE = ../../contrib/testing_hostkeys.dat +MAX_CONCURRENT_SSH = 10 +USE_PROGRESSBARS = YES +PEERGROUP_TIMEOUT = 2400 s + +[gnunetd] +HOSTKEY = $SERVICEHOME/.hostkey + +[PATHS] +SERVICEHOME = /tmp/test-testbed/ + +[dns] +AUTOSTART = NO + +[nse] +AUTOSTART = NO + +[vpn] +AUTOSTART = NO + +[nat] +RETURN_LOCAL_ADDRESSES = YES + +[gns-helper-service-w32] +AUTOSTART = NO + +[consensus] +AUTOSTART = NO + +[gns] +AUTOSTART = NO + +[statistics] +AUTOSTART = NO + +[peerinfo] +NO_IO = YES diff --git a/src/testbed/test_testbed_api_2peers_1controller.c b/src/testbed/test_testbed_api_2peers_1controller.c new file mode 100644 index 0000000..d5616c2 --- /dev/null +++ b/src/testbed/test_testbed_api_2peers_1controller.c @@ -0,0 +1,532 @@ +/* + This file is part of GNUnet + (C) 2008--2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. + */ + +/** + * @file testbed/test_testbed_api_2peers_1controller.c + * @brief testcases for the testbed api: 2 peers are configured, started and + * connected together. The 2 peer reside on a single controller. + * @author Sree Harsha Totakura + */ + +#include "platform.h" +#include "gnunet_util_lib.h" +#include "gnunet_testing_lib.h" +#include "gnunet_testbed_service.h" + + +/** + * Generic logging shortcut + */ +#define LOG(kind,...) \ + GNUNET_log (kind, __VA_ARGS__) + +/** + * Relative time seconds shorthand + */ +#define TIME_REL_SECS(sec) \ + GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, sec) + +/** + * Peer context + */ +struct PeerContext +{ + /** + * The peer handle + */ + struct GNUNET_TESTBED_Peer *peer; + + /** + * Operations involving this peer + */ + struct GNUNET_TESTBED_Operation *operation; + + /** + * set to GNUNET_YES when peer is started + */ + int is_running; +}; + +/** + * Our localhost + */ +static struct GNUNET_TESTBED_Host *host; + +/** + * The controller process + */ +static struct GNUNET_TESTBED_ControllerProc *cp; + +/** + * The controller handle + */ +static struct GNUNET_TESTBED_Controller *controller; + +/** + * A neighbouring host + */ +static struct GNUNET_TESTBED_Host *neighbour; + +/** + * Handle for neighbour registration + */ +static struct GNUNET_TESTBED_HostRegistrationHandle *reg_handle; + +/** + * peer 1 + */ +static struct PeerContext peer1; + +/** + * peer2 + */ +static struct PeerContext peer2; + +/** + * Handle to configuration + */ +static struct GNUNET_CONFIGURATION_Handle *cfg; + +/** + * Handle to operations involving both peers + */ +static struct GNUNET_TESTBED_Operation *common_operation; + +/** + * Abort task identifier + */ +static GNUNET_SCHEDULER_TaskIdentifier abort_task; + +/** + * Delayed connect job identifier + */ +static GNUNET_SCHEDULER_TaskIdentifier delayed_connect_task; + +/** + * Different stages in testing + */ +enum Stage +{ + + /** + * Initial stage + */ + INIT, + + /** + * peers are created + */ + PEERS_CREATED, + + /** + * peers are started + */ + PEERS_STARTED, + + /** + * peers are connected + */ + PEERS_CONNECTED, + + /** + * Peers are connected once again (this should not fail as they are already connected) + */ + PEERS_CONNECTED_2, + + /** + * peers are stopped + */ + PEERS_STOPPED, + + /** + * Final success stage + */ + SUCCESS +}; + +/** + * The testing result + */ +static enum Stage result; + +/** + * shortcut to exit during failure + */ +#define FAIL_TEST(cond) do { \ + if (!(cond)) { \ + GNUNET_break(0); \ + if (GNUNET_SCHEDULER_NO_TASK != abort_task) \ + GNUNET_SCHEDULER_cancel (abort_task); \ + abort_task = GNUNET_SCHEDULER_NO_TASK; \ + GNUNET_SCHEDULER_add_now (do_shutdown, NULL); \ + return; \ + } \ + } while (0) + +/** + * Shutdown nicely + * + * @param cls NULL + * @param tc the task context + */ +static void +do_shutdown (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + if (GNUNET_SCHEDULER_NO_TASK != abort_task) + GNUNET_SCHEDULER_cancel (abort_task); + if (GNUNET_SCHEDULER_NO_TASK != delayed_connect_task) + GNUNET_SCHEDULER_cancel (delayed_connect_task); + if (NULL != reg_handle) + GNUNET_TESTBED_cancel_registration (reg_handle); + GNUNET_TESTBED_controller_disconnect (controller); + GNUNET_CONFIGURATION_destroy (cfg); + if (NULL != cp) + GNUNET_TESTBED_controller_stop (cp); + GNUNET_TESTBED_host_destroy (neighbour); + GNUNET_TESTBED_host_destroy (host); +} + + +/** + * abort task to run on test timed out + * + * @param cls NULL + * @param tc the task context + */ +static void +do_abort (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + LOG (GNUNET_ERROR_TYPE_WARNING, "Test timedout -- Aborting\n"); + abort_task = GNUNET_SCHEDULER_NO_TASK; + do_shutdown (cls, tc); +} + + +/** + * Callback to be called when an operation is completed + * + * @param cls the callback closure from functions generating an operation + * @param op the operation that has been finished + * @param emsg error message in case the operation has failed; will be NULL if + * operation has executed successfully. + */ +static void +op_comp_cb (void *cls, struct GNUNET_TESTBED_Operation *op, const char *emsg); + + +/** + * task for delaying a connect + * + * @param cls NULL + * @param tc the task context + */ +static void +do_delayed_connect (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + delayed_connect_task = GNUNET_SCHEDULER_NO_TASK; + FAIL_TEST (NULL == common_operation); + common_operation = + GNUNET_TESTBED_overlay_connect (NULL, &op_comp_cb, NULL, peer1.peer, + peer2.peer); +} + + +/** + * Callback to be called when an operation is completed + * + * @param cls the callback closure from functions generating an operation + * @param op the operation that has been finished + * @param emsg error message in case the operation has failed; will be NULL if + * operation has executed successfully. + */ +static void +op_comp_cb (void *cls, struct GNUNET_TESTBED_Operation *op, const char *emsg) +{ + FAIL_TEST (common_operation == op); + switch (result) + { + case PEERS_STARTED: + FAIL_TEST (NULL == peer1.operation); + FAIL_TEST (NULL == peer2.operation); + FAIL_TEST (NULL != common_operation); + break; + case PEERS_CONNECTED: + FAIL_TEST (NULL == peer1.operation); + FAIL_TEST (NULL == peer2.operation); + FAIL_TEST (NULL != common_operation); + break; + default: + FAIL_TEST (0); + } +} + + +/** + * Signature of the event handler function called by the + * respective event controller. + * + * @param cls closure + * @param event information about the event + */ +static void +controller_cb (void *cls, const struct GNUNET_TESTBED_EventInformation *event) +{ + switch (event->type) + { + case GNUNET_TESTBED_ET_OPERATION_FINISHED: /* Will be reached when we destroy peers */ + FAIL_TEST (PEERS_STOPPED == result); + FAIL_TEST (NULL == event->details.operation_finished.op_cls); + FAIL_TEST (NULL == event->details.operation_finished.emsg); + FAIL_TEST (NULL == event->details.operation_finished.generic); + if (event->details.operation_finished.operation == peer1.operation) + { + GNUNET_TESTBED_operation_done (peer1.operation); + peer1.operation = NULL; + peer1.peer = NULL; + } + else if (event->details.operation_finished.operation == peer2.operation) + { + GNUNET_TESTBED_operation_done (peer2.operation); + peer2.operation = NULL; + peer2.peer = NULL; + } + else + FAIL_TEST (0); + if ((NULL == peer1.peer) && (NULL == peer2.peer)) + { + result = SUCCESS; + GNUNET_SCHEDULER_add_now (&do_shutdown, NULL); + } + break; + case GNUNET_TESTBED_ET_PEER_START: + FAIL_TEST (INIT == result); + FAIL_TEST (event->details.peer_start.host == host); + if (event->details.peer_start.peer == peer1.peer) + { + peer1.is_running = GNUNET_YES; + GNUNET_TESTBED_operation_done (peer1.operation); + peer1.operation = NULL; + } + else if (event->details.peer_start.peer == peer2.peer) + { + peer2.is_running = GNUNET_YES; + GNUNET_TESTBED_operation_done (peer2.operation); + peer2.operation = NULL; + } + else + FAIL_TEST (0); + if ((GNUNET_YES == peer1.is_running) && (GNUNET_YES == peer2.is_running)) + { + result = PEERS_STARTED; + common_operation = + GNUNET_TESTBED_overlay_connect (NULL, &op_comp_cb, NULL, peer1.peer, + peer2.peer); + } + break; + case GNUNET_TESTBED_ET_PEER_STOP: + FAIL_TEST (PEERS_CONNECTED_2 == result); + if (event->details.peer_stop.peer == peer1.peer) + { + peer1.is_running = GNUNET_NO; + GNUNET_TESTBED_operation_done (peer1.operation); + peer1.operation = GNUNET_TESTBED_peer_destroy (peer1.peer); + } + else if (event->details.peer_stop.peer == peer2.peer) + { + peer2.is_running = GNUNET_NO; + GNUNET_TESTBED_operation_done (peer2.operation); + peer2.operation = GNUNET_TESTBED_peer_destroy (peer2.peer); + } + else + FAIL_TEST (0); + if ((GNUNET_NO == peer1.is_running) && (GNUNET_NO == peer2.is_running)) + result = PEERS_STOPPED; + break; + case GNUNET_TESTBED_ET_CONNECT: + switch (result) + { + case PEERS_STARTED: + FAIL_TEST (NULL == peer1.operation); + FAIL_TEST (NULL == peer2.operation); + FAIL_TEST (NULL != common_operation); + FAIL_TEST ((event->details.peer_connect.peer1 == peer1.peer) && + (event->details.peer_connect.peer2 == peer2.peer)); + GNUNET_TESTBED_operation_done (common_operation); + common_operation = NULL; + result = PEERS_CONNECTED; + LOG (GNUNET_ERROR_TYPE_DEBUG, "Peers connected\n"); + delayed_connect_task = + GNUNET_SCHEDULER_add_delayed (TIME_REL_SECS (3), &do_delayed_connect, + NULL); + break; + case PEERS_CONNECTED: + FAIL_TEST (NULL == peer1.operation); + FAIL_TEST (NULL == peer2.operation); + FAIL_TEST (NULL != common_operation); + GNUNET_TESTBED_operation_done (common_operation); + common_operation = NULL; + result = PEERS_CONNECTED_2; + LOG (GNUNET_ERROR_TYPE_DEBUG, "Peers connected again\n"); + peer1.operation = GNUNET_TESTBED_peer_stop (peer1.peer, NULL, NULL); + peer2.operation = GNUNET_TESTBED_peer_stop (peer2.peer, NULL, NULL); + break; + default: + FAIL_TEST (0); + } + break; + default: + FAIL_TEST (0); + }; +} + + +/** + * Functions of this signature are called when a peer has been successfully + * created + * + * @param cls the closure from GNUNET_TESTBED_peer_create() + * @param peer the handle for the created peer; NULL on any error during + * creation + * @param emsg NULL if peer is not NULL; else MAY contain the error description + */ +static void +peer_create_cb (void *cls, struct GNUNET_TESTBED_Peer *peer, const char *emsg) +{ + struct PeerContext *pc = cls; + + FAIL_TEST (NULL != pc->operation); + FAIL_TEST (NULL != peer); + FAIL_TEST (NULL == pc->peer); + pc->peer = peer; + GNUNET_TESTBED_operation_done (pc->operation); + pc->operation = GNUNET_TESTBED_peer_start (NULL, pc->peer, NULL, NULL); +} + + +/** + * Callback which will be called to after a host registration succeeded or failed + * + * @param cls the host which has been registered + * @param emsg the error message; NULL if host registration is successful + */ +static void +registration_comp (void *cls, const char *emsg) +{ + FAIL_TEST (cls == neighbour); + reg_handle = NULL; + peer1.operation = + GNUNET_TESTBED_peer_create (controller, host, cfg, &peer_create_cb, + &peer1); + peer2.operation = + GNUNET_TESTBED_peer_create (controller, host, cfg, &peer_create_cb, + &peer2); + FAIL_TEST (NULL != peer1.operation); + FAIL_TEST (NULL != peer2.operation); +} + + +/** + * Callback to signal successfull startup of the controller process + * + * @param cls the closure from GNUNET_TESTBED_controller_start() + * @param cfg the configuration with which the controller has been started; + * NULL if status is not GNUNET_OK + * @param status GNUNET_OK if the startup is successfull; GNUNET_SYSERR if not, + * GNUNET_TESTBED_controller_stop() shouldn't be called in this case + */ +static void +status_cb (void *cls, const struct GNUNET_CONFIGURATION_Handle *cfg, int status) +{ + uint64_t event_mask; + + if (GNUNET_OK != status) + { + cp = NULL; + FAIL_TEST (0); + } + event_mask = 0; + event_mask |= (1L << GNUNET_TESTBED_ET_PEER_START); + event_mask |= (1L << GNUNET_TESTBED_ET_PEER_STOP); + event_mask |= (1L << GNUNET_TESTBED_ET_CONNECT); + event_mask |= (1L << GNUNET_TESTBED_ET_OPERATION_FINISHED); + controller = + GNUNET_TESTBED_controller_connect (cfg, host, event_mask, &controller_cb, + NULL); + FAIL_TEST (NULL != controller); + neighbour = GNUNET_TESTBED_host_create ("localhost", NULL, 0); + FAIL_TEST (NULL != neighbour); + reg_handle = + GNUNET_TESTBED_register_host (controller, neighbour, ®istration_comp, + neighbour); + FAIL_TEST (NULL != reg_handle); +} + + + +/** + * Main run function. + * + * @param cls NULL + * @param args arguments passed to GNUNET_PROGRAM_run + * @param cfgfile the path to configuration file + * @param cfg the configuration file handle + */ +static void +run (void *cls, char *const *args, const char *cfgfile, + const struct GNUNET_CONFIGURATION_Handle *config) +{ + host = GNUNET_TESTBED_host_create (NULL, NULL, 0); + FAIL_TEST (NULL != host); + cfg = GNUNET_CONFIGURATION_dup (config); + cp = GNUNET_TESTBED_controller_start ("127.0.0.1", host, cfg, status_cb, + NULL); + abort_task = + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply + (GNUNET_TIME_UNIT_MINUTES, 3), &do_abort, + NULL); +} + + +/** + * Main function + */ +int +main (int argc, char **argv) +{ + int ret; + + char *const argv2[] = { "test_testbed_api_2peers_1controller", + "-c", "test_testbed_api.conf", + NULL + }; + struct GNUNET_GETOPT_CommandLineOption options[] = { + GNUNET_GETOPT_OPTION_END + }; + result = INIT; + ret = + GNUNET_PROGRAM_run ((sizeof (argv2) / sizeof (char *)) - 1, argv2, + "test_testbed_api_2peers_1controller", "nohelp", + options, &run, NULL); + if ((GNUNET_OK != ret) || (SUCCESS != result)) + return 1; + return 0; +} + +/* end of test_testbed_api_2peers_1controller.c */ diff --git a/src/testbed/test_testbed_api_3peers_3controllers.c b/src/testbed/test_testbed_api_3peers_3controllers.c new file mode 100644 index 0000000..47ad810 --- /dev/null +++ b/src/testbed/test_testbed_api_3peers_3controllers.c @@ -0,0 +1,946 @@ +/* + This file is part of GNUnet + (C) 2008--2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. + */ + +/** + * @file testbed/test_testbed_api_3peers_3controllers.c + * @brief testcases for the testbed api: 3 peers are configured, started and + * connected together. Each peer resides on its own controller. + * @author Sree Harsha Totakura + */ + + +/** + * The testing architecture is: + * A + * / \ + * / \ + * B === C + * A is the master controller and B, C are slave controllers. B links to C + * laterally. + * Peers are mapped to controllers in the following relations: + * Peer Controller + * 1 A + * 2 B + * 3 C + * + */ + +#include "platform.h" +#include "gnunet_util_lib.h" +#include "gnunet_testing_lib.h" +#include "gnunet_testbed_service.h" + + +/** + * Generic logging shortcut + */ +#define LOG(kind,...) \ + GNUNET_log (kind, __VA_ARGS__) + +/** + * Relative time seconds shorthand + */ +#define TIME_REL_SECS(sec) \ + GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, sec) + + +/** + * Peer context + */ +struct PeerContext +{ + /** + * The peer handle + */ + struct GNUNET_TESTBED_Peer *peer; + + /** + * Operations involving this peer + */ + struct GNUNET_TESTBED_Operation *operation; + + /** + * set to GNUNET_YES when peer is started + */ + int is_running; +}; + +/** + * Our localhost + */ +static struct GNUNET_TESTBED_Host *host; + +/** + * The controller process of one controller + */ +static struct GNUNET_TESTBED_ControllerProc *cp1; + +/** + * A neighbouring host + */ +static struct GNUNET_TESTBED_Host *neighbour1; + +/** + * Another neighbouring host + */ +static struct GNUNET_TESTBED_Host *neighbour2; + +/** + * Handle for neighbour registration + */ +static struct GNUNET_TESTBED_HostRegistrationHandle *reg_handle; + +/** + * The controller handle of one controller + */ +static struct GNUNET_TESTBED_Controller *controller1; + +/** + * peer 1 + */ +static struct PeerContext peer1; + +/** + * peer2 + */ +static struct PeerContext peer2; + +/** + * peer3 + */ +static struct PeerContext peer3; + +/** + * Handle to starting configuration + */ +static struct GNUNET_CONFIGURATION_Handle *cfg; + +/** + * Handle to slave controller C's configuration, used to establish lateral link from + * master controller + */ +static struct GNUNET_CONFIGURATION_Handle *cfg2; + +/** + * Handle to operations involving both peers + */ +static struct GNUNET_TESTBED_Operation *common_operation; + +/** + * The handle for whether a host is habitable or not + */ +struct GNUNET_TESTBED_HostHabitableCheckHandle *hc_handle; + +/** + * Abort task identifier + */ +static GNUNET_SCHEDULER_TaskIdentifier abort_task; + +/** + * Delayed connect job identifier + */ +static GNUNET_SCHEDULER_TaskIdentifier delayed_connect_task; + +/** + * Different stages in testing + */ +enum Stage +{ + + /** + * Initial stage + */ + INIT, + + /** + * Controller 1 has started + */ + CONTROLLER1_UP, + + /** + * peer1 is created + */ + PEER1_CREATED, + + /** + * peer1 is started + */ + PEER1_STARTED, + + /** + * Controller 2 has started + */ + CONTROLLER2_UP, + + /** + * peer2 is created + */ + PEER2_CREATED, + + /** + * peer2 is started + */ + PEER2_STARTED, + + /** + * Controller 3 has started + */ + CONTROLLER3_UP, + + /** + * Peer3 is created + */ + PEER3_CREATED, + + /** + * Peer3 started + */ + PEER3_STARTED, + + /** + * peer1 and peer2 are connected + */ + PEERS_1_2_CONNECTED, + + /** + * peer2 and peer3 are connected + */ + PEERS_2_3_CONNECTED, + + /** + * Peers are connected once again (this should not fail as they are already connected) + */ + PEERS_CONNECTED_2, + + /** + * peers are stopped + */ + PEERS_STOPPED, + + /** + * Final success stage + */ + SUCCESS, + + /** + * Optional stage for marking test to be skipped + */ + SKIP +}; + +/** + * The testing result + */ +static enum Stage result; + +/** + * Shutdown nicely + * + * @param cls NULL + * @param tc the task context + */ +static void +do_shutdown (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + if (GNUNET_SCHEDULER_NO_TASK != abort_task) + GNUNET_SCHEDULER_cancel (abort_task); + if (NULL != hc_handle) + GNUNET_TESTBED_is_host_habitable_cancel (hc_handle); + GNUNET_assert (GNUNET_SCHEDULER_NO_TASK == delayed_connect_task); + if (NULL != common_operation) + GNUNET_TESTBED_operation_done (common_operation); + if (NULL != reg_handle) + GNUNET_TESTBED_cancel_registration (reg_handle); + if (NULL != controller1) + GNUNET_TESTBED_controller_disconnect (controller1); + GNUNET_CONFIGURATION_destroy (cfg); + if (NULL != cfg2) + GNUNET_CONFIGURATION_destroy (cfg2); + if (NULL != cp1) + GNUNET_TESTBED_controller_stop (cp1); + if (NULL != host) + GNUNET_TESTBED_host_destroy (host); + if (NULL != neighbour1) + GNUNET_TESTBED_host_destroy (neighbour1); + if (NULL != neighbour2) + GNUNET_TESTBED_host_destroy (neighbour2); +} + + +/** + * abort task to run on test timed out + * + * @param cls NULL + * @param tc the task context + */ +static void +do_abort (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + LOG (GNUNET_ERROR_TYPE_WARNING, "Test timedout -- Aborting\n"); + abort_task = GNUNET_SCHEDULER_NO_TASK; + if (GNUNET_SCHEDULER_NO_TASK != delayed_connect_task) + { + GNUNET_SCHEDULER_cancel (delayed_connect_task); + delayed_connect_task = GNUNET_SCHEDULER_NO_TASK; + } + do_shutdown (cls, tc); +} + +static void +abort_test () +{ + if (GNUNET_SCHEDULER_NO_TASK != abort_task) + GNUNET_SCHEDULER_cancel (abort_task); + abort_task = GNUNET_SCHEDULER_add_now (&do_abort, NULL); +} + + +/** + * Callback to be called when an operation is completed + * + * @param cls the callback closure from functions generating an operation + * @param op the operation that has been finished + * @param emsg error message in case the operation has failed; will be NULL if + * operation has executed successfully. + */ +static void +op_comp_cb (void *cls, struct GNUNET_TESTBED_Operation *op, const char *emsg); + + +/** + * task for delaying a connect + * + * @param cls NULL + * @param tc the task context + */ +static void +do_delayed_connect (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + delayed_connect_task = GNUNET_SCHEDULER_NO_TASK; + if (NULL != common_operation) + { + GNUNET_break (0); + abort_test (); + return; + } + common_operation = + GNUNET_TESTBED_overlay_connect (NULL, &op_comp_cb, NULL, peer1.peer, + peer2.peer); +} + + +/** + * Callback to be called when an operation is completed + * + * @param cls the callback closure from functions generating an operation + * @param op the operation that has been finished + * @param emsg error message in case the operation has failed; will be NULL if + * operation has executed successfully. + */ +static void +op_comp_cb (void *cls, struct GNUNET_TESTBED_Operation *op, const char *emsg) +{ + if (common_operation != op) + { + GNUNET_break (0); + abort_test (); + return; + } + + switch (result) + { + case PEER3_STARTED: + case PEERS_2_3_CONNECTED: + case PEERS_1_2_CONNECTED: + break; + default: + GNUNET_break (0); + abort_test (); + return; + } + if ((NULL != peer1.operation) || (NULL != peer2.operation) || + (NULL != peer3.operation)) + { + GNUNET_break (0); + abort_test (); + return; + } +} + + +/** + * Functions of this signature are called when a peer has been successfully + * created + * + * @param cls NULL + * @param peer the handle for the created peer; NULL on any error during + * creation + * @param emsg NULL if peer is not NULL; else MAY contain the error description + */ +static void +peer_create_cb (void *cls, struct GNUNET_TESTBED_Peer *peer, const char *emsg) +{ + switch (result) + { + case CONTROLLER1_UP: + if ((NULL == peer1.operation) || (NULL == peer) || (NULL != peer1.peer)) + { + GNUNET_break (0); + abort_test (); + return; + } + peer1.peer = peer; + GNUNET_TESTBED_operation_done (peer1.operation); + result = PEER1_CREATED; + peer1.operation = GNUNET_TESTBED_peer_start (NULL, peer, NULL, NULL); + break; + case CONTROLLER2_UP: + if ((NULL == peer2.operation) || (NULL == peer) || (NULL != peer2.peer)) + { + GNUNET_break (0); + abort_test (); + return; + } + peer2.peer = peer; + GNUNET_TESTBED_operation_done (peer2.operation); + result = PEER2_CREATED; + peer2.operation = GNUNET_TESTBED_peer_start (NULL, peer, NULL, NULL); + break; + case CONTROLLER3_UP: + if ((NULL == peer3.operation) || (NULL == peer) || (NULL != peer3.peer)) + { + GNUNET_break (0); + abort_test (); + return; + } + peer3.peer = peer; + GNUNET_TESTBED_operation_done (peer3.operation); + result = PEER3_CREATED; + peer3.operation = GNUNET_TESTBED_peer_start (NULL, peer, NULL, NULL); + break; + default: + GNUNET_break (0); + abort_test (); + return; + } +} + + +/** + * Signature of the event handler function called by the + * respective event controller. + * + * @param cls closure + * @param event information about the event + */ +static void +controller_cb (void *cls, const struct GNUNET_TESTBED_EventInformation *event) +{ + switch (event->type) + { + case GNUNET_TESTBED_ET_OPERATION_FINISHED: + if ((NULL != event->details.operation_finished.op_cls) || + (NULL != event->details.operation_finished.emsg)) + { + GNUNET_break (0); + abort_test (); + return; + } + switch (result) + { + case PEERS_STOPPED: + if (NULL != event->details.operation_finished.generic) + { + GNUNET_break (0); + abort_test (); + return; + } + if (event->details.operation_finished.operation == peer1.operation) + { + GNUNET_TESTBED_operation_done (peer1.operation); + peer1.operation = NULL; + peer1.peer = NULL; + } + else if (event->details.operation_finished.operation == peer2.operation) + { + GNUNET_TESTBED_operation_done (peer2.operation); + peer2.operation = NULL; + peer2.peer = NULL; + } + else if (event->details.operation_finished.operation == peer3.operation) + { + GNUNET_TESTBED_operation_done (peer3.operation); + peer3.operation = NULL; + peer3.peer = NULL; + } + else + { + GNUNET_break (0); + abort_test (); + return; + } + if ((NULL == peer1.peer) && (NULL == peer2.peer) && (NULL == peer3.peer)) + { + result = SUCCESS; + GNUNET_SCHEDULER_add_now (&do_shutdown, NULL); + } + break; + case PEER1_STARTED: + if ((NULL != event->details.operation_finished.generic) || + (NULL == common_operation)) + { + GNUNET_break (0); + abort_test (); + return; + } + GNUNET_TESTBED_operation_done (common_operation); + common_operation = NULL; + result = CONTROLLER2_UP; + peer2.operation = + GNUNET_TESTBED_peer_create (controller1, neighbour1, cfg, + &peer_create_cb, NULL); + if (NULL == peer2.operation) + { + GNUNET_break (0); + abort_test (); + return; + } + break; + case PEER2_STARTED: + if ((NULL != event->details.operation_finished.generic) || + (NULL == common_operation)) + { + GNUNET_break (0); + abort_test (); + return; + } + GNUNET_TESTBED_operation_done (common_operation); + common_operation = NULL; + result = CONTROLLER3_UP; + peer3.operation = + GNUNET_TESTBED_peer_create (controller1, neighbour2, cfg, + &peer_create_cb, NULL); + if (NULL == peer3.operation) + { + GNUNET_break (0); + abort_test (); + return; + } + break; + default: + GNUNET_break (0); + abort_test (); + return; + } + break; + case GNUNET_TESTBED_ET_PEER_START: + switch (result) + { + case PEER1_CREATED: + if (event->details.peer_start.host != host) + { + GNUNET_break (0); + abort_test (); + return; + } + peer1.is_running = GNUNET_YES; + GNUNET_TESTBED_operation_done (peer1.operation); + peer1.operation = NULL; + result = PEER1_STARTED; + common_operation = + GNUNET_TESTBED_controller_link (NULL, controller1, neighbour1, NULL, + cfg, GNUNET_YES); + break; + case PEER2_CREATED: + if (event->details.peer_start.host != neighbour1) + { + GNUNET_break (0); + abort_test (); + return; + } + peer2.is_running = GNUNET_YES; + GNUNET_TESTBED_operation_done (peer2.operation); + peer2.operation = NULL; + result = PEER2_STARTED; + if (NULL != common_operation) + { + GNUNET_break (0); + abort_test (); + return; + } + common_operation = + GNUNET_TESTBED_controller_link (NULL, controller1, neighbour2, NULL, + cfg, GNUNET_YES); + if (NULL == common_operation) + { + GNUNET_break (0); + abort_test (); + return; + } + break; + case PEER3_CREATED: + if (event->details.peer_start.host != neighbour2) + { + GNUNET_break (0); + abort_test (); + return; + } + peer3.is_running = GNUNET_YES; + GNUNET_TESTBED_operation_done (peer3.operation); + peer3.operation = NULL; + result = PEER3_STARTED; + common_operation = + GNUNET_TESTBED_overlay_connect (NULL, &op_comp_cb, NULL, peer2.peer, + peer1.peer); + break; + default: + GNUNET_break (0); + abort_test (); + return; + } + break; + case GNUNET_TESTBED_ET_PEER_STOP: + if (PEERS_CONNECTED_2 != result) + { + GNUNET_break (0); + abort_test (); + return; + } + if (event->details.peer_stop.peer == peer1.peer) + { + peer1.is_running = GNUNET_NO; + GNUNET_TESTBED_operation_done (peer1.operation); + } + else if (event->details.peer_stop.peer == peer2.peer) + { + peer2.is_running = GNUNET_NO; + GNUNET_TESTBED_operation_done (peer2.operation); + } + else if (event->details.peer_stop.peer == peer3.peer) + { + peer3.is_running = GNUNET_NO; + GNUNET_TESTBED_operation_done (peer3.operation); + } + else + { + GNUNET_break (0); + abort_test (); + return; + } + if ((GNUNET_NO == peer1.is_running) && (GNUNET_NO == peer2.is_running) && + (GNUNET_NO == peer3.is_running)) + { + result = PEERS_STOPPED; + peer1.operation = GNUNET_TESTBED_peer_destroy (peer1.peer); + peer2.operation = GNUNET_TESTBED_peer_destroy (peer2.peer); + peer3.operation = GNUNET_TESTBED_peer_destroy (peer3.peer); + } + break; + case GNUNET_TESTBED_ET_CONNECT: + if ((NULL != peer1.operation) || (NULL != peer2.operation) || + (NULL != peer3.operation) || (NULL == common_operation)) + { + GNUNET_break (0); + abort_test (); + return; + } + switch (result) + { + case PEER3_STARTED: + if ((event->details.peer_connect.peer1 != peer2.peer) || + (event->details.peer_connect.peer2 != peer1.peer)) + { + GNUNET_break (0); + abort_test (); + return; + } + GNUNET_TESTBED_operation_done (common_operation); + common_operation = NULL; + result = PEERS_1_2_CONNECTED; + LOG (GNUNET_ERROR_TYPE_DEBUG, "Peers connected\n"); + common_operation = + GNUNET_TESTBED_overlay_connect (NULL, &op_comp_cb, NULL, peer2.peer, + peer3.peer); + break; + case PEERS_1_2_CONNECTED: + if ((event->details.peer_connect.peer1 != peer2.peer) || + (event->details.peer_connect.peer2 != peer3.peer)) + { + GNUNET_break (0); + abort_test (); + return; + } + GNUNET_TESTBED_operation_done (common_operation); + common_operation = NULL; + result = PEERS_2_3_CONNECTED; + delayed_connect_task = + GNUNET_SCHEDULER_add_delayed (TIME_REL_SECS (3), &do_delayed_connect, + NULL); + break; + case PEERS_2_3_CONNECTED: + if ((event->details.peer_connect.peer1 != peer1.peer) || + (event->details.peer_connect.peer2 != peer2.peer)) + { + GNUNET_break (0); + abort_test (); + return; + } + GNUNET_TESTBED_operation_done (common_operation); + common_operation = NULL; + result = PEERS_CONNECTED_2; + LOG (GNUNET_ERROR_TYPE_DEBUG, "Peers connected again\n"); + peer1.operation = GNUNET_TESTBED_peer_stop (peer1.peer, NULL, NULL); + peer2.operation = GNUNET_TESTBED_peer_stop (peer2.peer, NULL, NULL); + peer3.operation = GNUNET_TESTBED_peer_stop (peer3.peer, NULL, NULL); + break; + default: + GNUNET_break (0); + abort_test (); + return; + } + break; + default: + GNUNET_break (0); + abort_test (); + return; + } +} + + +/** + * Callback which will be called to after a host registration succeeded or failed + * + * @param cls the host which has been registered + * @param emsg the error message; NULL if host registration is successful + */ +static void +registration_comp (void *cls, const char *emsg) +{ + reg_handle = NULL; + if (cls == neighbour1) + { + neighbour2 = GNUNET_TESTBED_host_create ("127.0.0.1", NULL, 0); + if (NULL == neighbour2) + { + GNUNET_break (0); + abort_test (); + return; + } + reg_handle = + GNUNET_TESTBED_register_host (controller1, neighbour2, + ®istration_comp, neighbour2); + if (NULL == reg_handle) + { + GNUNET_break (0); + abort_test (); + return; + } + return; + } + if (cls != neighbour2) + { + GNUNET_break (0); + abort_test (); + return; + } + peer1.operation = + GNUNET_TESTBED_peer_create (controller1, host, cfg, &peer_create_cb, + &peer1); + if (NULL == peer1.operation) + { + GNUNET_break (0); + abort_test (); + return; + } +} + + +/** + * Callback to signal successfull startup of the controller process + * + * @param cls the closure from GNUNET_TESTBED_controller_start() + * @param cfg the configuration with which the controller has been started; + * NULL if status is not GNUNET_OK + * @param status GNUNET_OK if the startup is successfull; GNUNET_SYSERR if not, + * GNUNET_TESTBED_controller_stop() shouldn't be called in this case + */ +static void +status_cb (void *cls, const struct GNUNET_CONFIGURATION_Handle *config, + int status) +{ + uint64_t event_mask; + + if (GNUNET_OK != status) + { + GNUNET_break (0); + cp1 = NULL; + abort_test (); + return; + } + event_mask = 0; + event_mask |= (1L << GNUNET_TESTBED_ET_PEER_START); + event_mask |= (1L << GNUNET_TESTBED_ET_PEER_STOP); + event_mask |= (1L << GNUNET_TESTBED_ET_CONNECT); + event_mask |= (1L << GNUNET_TESTBED_ET_OPERATION_FINISHED); + switch (result) + { + case INIT: + controller1 = + GNUNET_TESTBED_controller_connect (config, host, event_mask, + &controller_cb, NULL); + if (NULL == controller1) + { + GNUNET_break (0); + abort_test (); + return; + } + result = CONTROLLER1_UP; + neighbour1 = GNUNET_TESTBED_host_create ("127.0.0.1", NULL, 0); + if (NULL == neighbour1) + { + GNUNET_break (0); + abort_test (); + return; + } + reg_handle = + GNUNET_TESTBED_register_host (controller1, neighbour1, + ®istration_comp, neighbour1); + if (NULL == reg_handle) + { + GNUNET_break (0); + abort_test (); + return; + } + break; + default: + GNUNET_break (0); + abort_test (); + return; + } +} + + +/** + * Callbacks of this type are called by GNUNET_TESTBED_is_host_habitable to + * inform whether the given host is habitable or not. The Handle returned by + * GNUNET_TESTBED_is_host_habitable() is invalid after this callback is called + * + * @param cls NULL + * @param host the host whose status is being reported; will be NULL if the host + * given to GNUNET_TESTBED_is_host_habitable() is NULL + * @param status GNUNET_YES if it is habitable; GNUNET_NO if not + */ +static void +host_habitable_cb (void *cls, const struct GNUNET_TESTBED_Host *_host, + int status) +{ + hc_handle = NULL; + if (GNUNET_NO == status) + { + (void) PRINTF ("%s", + "Unable to run the test as this system is not configured " + "to use password less SSH logins to localhost.\n" + "Skipping test\n"); + GNUNET_SCHEDULER_cancel (abort_task); + abort_task = GNUNET_SCHEDULER_NO_TASK; + (void) GNUNET_SCHEDULER_add_now (&do_shutdown, NULL); + result = SKIP; + return; + } + cp1 = + GNUNET_TESTBED_controller_start ("127.0.0.1", host, cfg, status_cb, NULL); +} + + +/** + * Main run function. + * + * @param cls NULL + * @param args arguments passed to GNUNET_PROGRAM_run + * @param cfgfile the path to configuration file + * @param cfg the configuration file handle + */ +static void +run (void *cls, char *const *args, const char *cfgfile, + const struct GNUNET_CONFIGURATION_Handle *config) +{ + host = GNUNET_TESTBED_host_create (NULL, NULL, 0); + if (NULL == host) + { + GNUNET_break (0); + abort_test (); + return; + } + if (NULL == + (hc_handle = + GNUNET_TESTBED_is_host_habitable (host, config, &host_habitable_cb, + NULL))) + { + GNUNET_TESTBED_host_destroy (host); + host = NULL; + (void) PRINTF ("%s", + "Unable to run the test as this system is not configured " + "to use password less SSH logins to localhost.\n" + "Skipping test\n"); + result = SKIP; + return; + } + cfg = GNUNET_CONFIGURATION_dup (config); + abort_task = + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply + (GNUNET_TIME_UNIT_MINUTES, 3), &do_abort, + NULL); +} + + +/** + * Main function + */ +int +main (int argc, char **argv) +{ + char *const argv2[] = { "test_testbed_api_3peers_3controllers", + "-c", "test_testbed_api.conf", + NULL + }; + struct GNUNET_GETOPT_CommandLineOption options[] = { + GNUNET_GETOPT_OPTION_END + }; + int ret; + + result = INIT; + ret = + GNUNET_PROGRAM_run ((sizeof (argv2) / sizeof (char *)) - 1, argv2, + "test_testbed_api_3peers_3controllers", "nohelp", + options, &run, NULL); + if (GNUNET_OK != ret) + return 1; + switch (result) + { + case SUCCESS: + return 0; + case SKIP: + return 77; /* Mark test as skipped */ + default: + return 1; + } +} + +/* end of test_testbed_api_3peers_3controllers.c */ diff --git a/src/testbed/test_testbed_api_controllerlink.c b/src/testbed/test_testbed_api_controllerlink.c new file mode 100644 index 0000000..eadc6c9 --- /dev/null +++ b/src/testbed/test_testbed_api_controllerlink.c @@ -0,0 +1,749 @@ +/* + This file is part of GNUnet + (C) 2008--2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. + */ + +/** + * @file testbed/test_testbed_api_controllerlink.c + * @brief testcase for testing controller to subcontroller linking + * @author Sree Harsha Totakura + */ + + +/** + * The controller architecture we try to achieve in this test case: + * + * Master Controller + * // \\ + * // \\ + * Slave Controller 1---------Slave Controller 3 + * || + * || + * Slave Controller 2 + */ + +#include "platform.h" +#include "gnunet_util_lib.h" +#include "gnunet_testing_lib.h" +#include "gnunet_testbed_service.h" + +/** + * Generic logging shortcut + */ +#define LOG(kind,...) \ + GNUNET_log (kind, __VA_ARGS__) + +/** + * Debug logging shorthand + */ +#define LOG_DEBUG(...) \ + LOG(GNUNET_ERROR_TYPE_DEBUG, __VA_ARGS__) + +/** + * Different stages in testing + */ +enum Stage +{ + + /** + * Initial stage + */ + INIT, + + /** + * Master controller has started + */ + MASTER_STARTED, + + /** + * A peer has been created on master + */ + MASTER_PEER_CREATE_SUCCESS, + + /** + * Peer on master controller has been started successfully. + */ + MASTER_PEER_START_SUCCESS, + + /** + * The first slave has been registered at master controller + */ + SLAVE1_REGISTERED, + + /** + * The second slave has been registered at the master controller + */ + SLAVE2_REGISTERED, + + /** + * Link from master to slave 1 has been successfully created + */ + SLAVE1_LINK_SUCCESS, + + /** + * Peer create on slave 1 successful + */ + SLAVE1_PEER_CREATE_SUCCESS, + + /** + * Peer startup on slave 1 successful + */ + SLAVE1_PEER_START_SUCCESS, + + /** + * Link from slave 1 to slave 2 has been successfully created. + */ + SLAVE2_LINK_SUCCESS, + + /** + * Peer create on slave 2 successful + */ + SLAVE2_PEER_CREATE_SUCCESS, + + /** + * Peer on slave 1 successfully stopped + */ + SLAVE1_PEER_STOP_SUCCESS, + + /** + * Peer startup on slave 2 successful + */ + SLAVE2_PEER_START_SUCCESS, + + /** + * Try to connect peers on master and slave 2. + */ + MASTER_SLAVE2_PEERS_CONNECTED, + + /** + * Peer on slave 2 successfully stopped + */ + SLAVE2_PEER_STOP_SUCCESS, + + /** + * Peer destroy on slave 1 successful + */ + SLAVE1_PEER_DESTROY_SUCCESS, + + /** + * Peer destory on slave 2 successful + */ + SLAVE2_PEER_DESTROY_SUCCESS, + + /** + * Slave 3 has successfully registered + */ + SLAVE3_REGISTERED, + + /** + * Slave 3 has successfully started + */ + SLAVE3_STARTED, + + /** + * The configuration of slave 3 is acquired + */ + SLAVE3_GET_CONFIG_SUCCESS, + + /** + * Slave 1 has linked to slave 3; + */ + SLAVE3_LINK_SUCCESS, + + /** + * Destory master peer and mark test as success + */ + SUCCESS, + + /** + * Marks test as skipped + */ + SKIP +}; + +/** + * Host for running master controller + */ +static struct GNUNET_TESTBED_Host *host; + +/** + * The master controller process + */ +static struct GNUNET_TESTBED_ControllerProc *cp; + +/** + * Handle to master controller + */ +static struct GNUNET_TESTBED_Controller *mc; + +/** + * Slave host for running slave controller + */ +static struct GNUNET_TESTBED_Host *slave; + +/** + * Another slave host for running another slave controller + */ +static struct GNUNET_TESTBED_Host *slave2; + +/** + * Host for slave 3 + */ +static struct GNUNET_TESTBED_Host *slave3; + +/** + * Slave host registration handle + */ +static struct GNUNET_TESTBED_HostRegistrationHandle *rh; + +/** + * Handle to global configuration + */ +static struct GNUNET_CONFIGURATION_Handle *cfg; + +/** + * Configuration of slave 3 controller + */ +static struct GNUNET_CONFIGURATION_Handle *cfg3; + +/** + * Abort task + */ +static GNUNET_SCHEDULER_TaskIdentifier abort_task; + +/** + * Operation handle for linking controllers + */ +static struct GNUNET_TESTBED_Operation *op; + +/** + * Handle to peer started at slave 1 + */ +static struct GNUNET_TESTBED_Peer *slave1_peer; + +/** + * Handle to peer started at slave 2 + */ +static struct GNUNET_TESTBED_Peer *slave2_peer; + +/** + * Handle to a peer started at master controller + */ +static struct GNUNET_TESTBED_Peer *master_peer; + +/** + * The handle for whether a host is habitable or not + */ +struct GNUNET_TESTBED_HostHabitableCheckHandle *hc_handle; + +/** + * Event mask + */ +uint64_t event_mask; + +/** + * Global testing status + */ +static enum Stage result; + + +/** + * Shutdown nicely + * + * @param cls NULL + * @param tc the task context + */ +static void +do_shutdown (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + if (GNUNET_SCHEDULER_NO_TASK != abort_task) + GNUNET_SCHEDULER_cancel (abort_task); + if (NULL != hc_handle) + GNUNET_TESTBED_is_host_habitable_cancel (hc_handle); + if (NULL != slave3) + GNUNET_TESTBED_host_destroy (slave3); + if (NULL != slave2) + GNUNET_TESTBED_host_destroy (slave2); + if (NULL != slave) + GNUNET_TESTBED_host_destroy (slave); + if (NULL != host) + GNUNET_TESTBED_host_destroy (host); + if (NULL != mc) + GNUNET_TESTBED_controller_disconnect (mc); + if (NULL != cfg) + GNUNET_CONFIGURATION_destroy (cfg); + if (NULL != cfg3) + GNUNET_CONFIGURATION_destroy (cfg3); + if (NULL != cp) + GNUNET_TESTBED_controller_stop (cp); + if (NULL != rh) + GNUNET_TESTBED_cancel_registration (rh); +} + + +/** + * abort task to run on test timed out + * + * @param cls NULL + * @param tc the task context + */ +static void +do_abort (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + LOG (GNUNET_ERROR_TYPE_WARNING, "Test timedout -- Aborting\n"); + abort_task = GNUNET_SCHEDULER_NO_TASK; + do_shutdown (cls, tc); +} + + +/** + * Calls abort now + * + * @param + * @return + */ +static void +do_abort_now (void *cls) +{ + if (GNUNET_SCHEDULER_NO_TASK != abort_task) + GNUNET_SCHEDULER_cancel (abort_task); + abort_task = GNUNET_SCHEDULER_add_now (&do_abort, NULL); +} + + +/** + * Task for inserting delay between tests + * + * @param + * @return + */ +static void +delay_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + switch (result) + { + case SLAVE2_PEER_CREATE_SUCCESS: + op = GNUNET_TESTBED_peer_stop (slave1_peer, NULL, NULL); + GNUNET_assert (NULL != op); + break; + case MASTER_SLAVE2_PEERS_CONNECTED: + op = GNUNET_TESTBED_peer_stop (slave2_peer, NULL, NULL); + GNUNET_assert (NULL != op); + break; + default: + GNUNET_assert (0); + } +} + + +/** + * Functions of this signature are called when a peer has been successfully + * created + * + * @param cls the closure from GNUNET_TESTBED_peer_create() + * @param peer the handle for the created peer; NULL on any error during + * creation + * @param emsg NULL if peer is not NULL; else MAY contain the error description + */ +static void +peer_create_cb (void *cls, struct GNUNET_TESTBED_Peer *peer, const char *emsg) +{ + GNUNET_assert (NULL != peer); + GNUNET_assert (NULL == emsg); + switch (result) + { + case MASTER_STARTED: + result = MASTER_PEER_CREATE_SUCCESS; + master_peer = peer; + GNUNET_TESTBED_operation_done (op); + op = GNUNET_TESTBED_peer_start (NULL, master_peer, NULL, NULL); + break; + case SLAVE1_LINK_SUCCESS: + result = SLAVE1_PEER_CREATE_SUCCESS; + slave1_peer = peer; + GNUNET_TESTBED_operation_done (op); + op = GNUNET_TESTBED_peer_start (NULL, slave1_peer, NULL, NULL); + break; + case SLAVE2_LINK_SUCCESS: + result = SLAVE2_PEER_CREATE_SUCCESS; + slave2_peer = peer; + GNUNET_TESTBED_operation_done (op); + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply + (GNUNET_TIME_UNIT_SECONDS, 1), &delay_task, + NULL); + break; + default: + GNUNET_assert (0); + } + GNUNET_assert (NULL != op); +} + + +/** + * Checks the event if it is an operation finished event and if indicates a + * successfull completion of operation + * + * @param event the event information to check + */ +static void +check_operation_success (const struct GNUNET_TESTBED_EventInformation *event) +{ + GNUNET_assert (NULL != event); + GNUNET_assert (GNUNET_TESTBED_ET_OPERATION_FINISHED == event->type); + GNUNET_assert (event->details.operation_finished.operation == op); + GNUNET_assert (NULL == event->details.operation_finished.op_cls); + GNUNET_assert (NULL == event->details.operation_finished.emsg); + GNUNET_assert (NULL == event->details.operation_finished.generic); +} + + +/** + * Callback which will be called to after a host registration succeeded or failed + * + * @param cls the host which has been registered + * @param emsg the error message; NULL if host registration is successful + */ +static void +registration_cont (void *cls, const char *emsg); + + +/** + * Signature of the event handler function called by the + * respective event controller. + * + * @param cls closure + * @param event information about the event + */ +static void +controller_cb (void *cls, const struct GNUNET_TESTBED_EventInformation *event) +{ + switch (result) + { + case SLAVE2_REGISTERED: + check_operation_success (event); + GNUNET_TESTBED_operation_done (op); + op = NULL; + result = SLAVE1_LINK_SUCCESS; + GNUNET_assert (NULL != slave2); + GNUNET_assert (NULL != slave); + op = GNUNET_TESTBED_peer_create (mc, slave, cfg, peer_create_cb, NULL); + GNUNET_assert (NULL != op); + break; + case SLAVE1_PEER_START_SUCCESS: + check_operation_success (event); + GNUNET_TESTBED_operation_done (op); + result = SLAVE2_LINK_SUCCESS; + op = GNUNET_TESTBED_peer_create (mc, slave2, cfg, peer_create_cb, NULL); + GNUNET_assert (NULL != op); + break; + case MASTER_PEER_CREATE_SUCCESS: + GNUNET_assert (GNUNET_TESTBED_ET_PEER_START == event->type); + GNUNET_assert (event->details.peer_start.host == host); + GNUNET_assert (event->details.peer_start.peer == master_peer); + GNUNET_TESTBED_operation_done (op); + result = MASTER_PEER_START_SUCCESS; + slave = GNUNET_TESTBED_host_create_with_id (1, "127.0.0.1", NULL, 0); + GNUNET_assert (NULL != slave); + rh = GNUNET_TESTBED_register_host (mc, slave, ®istration_cont, NULL); + GNUNET_assert (NULL != rh); + break; + case SLAVE1_PEER_CREATE_SUCCESS: + GNUNET_assert (GNUNET_TESTBED_ET_PEER_START == event->type); + GNUNET_assert (event->details.peer_start.host == slave); + GNUNET_assert (event->details.peer_start.peer == slave1_peer); + GNUNET_TESTBED_operation_done (op); + result = SLAVE1_PEER_START_SUCCESS; + op = GNUNET_TESTBED_controller_link (NULL, mc, slave2, slave, cfg, + GNUNET_YES); + break; + case SLAVE2_PEER_CREATE_SUCCESS: + GNUNET_assert (GNUNET_TESTBED_ET_PEER_STOP == event->type); + GNUNET_assert (event->details.peer_stop.peer == slave1_peer); + GNUNET_TESTBED_operation_done (op); + result = SLAVE1_PEER_STOP_SUCCESS; + op = GNUNET_TESTBED_peer_start (NULL, slave2_peer, NULL, NULL); + GNUNET_assert (NULL != op); + break; + case SLAVE1_PEER_STOP_SUCCESS: + GNUNET_assert (GNUNET_TESTBED_ET_PEER_START == event->type); + GNUNET_assert (event->details.peer_start.host == slave2); + GNUNET_assert (event->details.peer_start.peer == slave2_peer); + GNUNET_TESTBED_operation_done (op); + result = SLAVE2_PEER_START_SUCCESS; + op = GNUNET_TESTBED_overlay_connect (mc, NULL, NULL, master_peer, + slave2_peer); + break; + case SLAVE2_PEER_START_SUCCESS: + GNUNET_assert (NULL != event); + GNUNET_assert (GNUNET_TESTBED_ET_CONNECT == event->type); + GNUNET_assert (event->details.peer_connect.peer1 == master_peer); + GNUNET_assert (event->details.peer_connect.peer2 == slave2_peer); + result = MASTER_SLAVE2_PEERS_CONNECTED; + GNUNET_TESTBED_operation_done (op); + op = NULL; + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply + (GNUNET_TIME_UNIT_SECONDS, 1), &delay_task, + NULL); + break; + case MASTER_SLAVE2_PEERS_CONNECTED: + GNUNET_assert (GNUNET_TESTBED_ET_PEER_STOP == event->type); + GNUNET_assert (event->details.peer_stop.peer == slave2_peer); + GNUNET_TESTBED_operation_done (op); + result = SLAVE2_PEER_STOP_SUCCESS; + op = GNUNET_TESTBED_peer_destroy (slave1_peer); + GNUNET_assert (NULL != op); + break; + case SLAVE2_PEER_STOP_SUCCESS: + check_operation_success (event); + GNUNET_TESTBED_operation_done (op); + result = SLAVE1_PEER_DESTROY_SUCCESS; + op = GNUNET_TESTBED_peer_destroy (slave2_peer); + GNUNET_assert (NULL != op); + break; + case SLAVE1_PEER_DESTROY_SUCCESS: + check_operation_success (event); + GNUNET_TESTBED_operation_done (op); + op = NULL; + result = SLAVE2_PEER_DESTROY_SUCCESS; + slave3 = GNUNET_TESTBED_host_create_with_id (3, "127.0.0.1", NULL, 0); + rh = GNUNET_TESTBED_register_host (mc, slave3, ®istration_cont, NULL); + break; + case SLAVE3_REGISTERED: + check_operation_success (event); + GNUNET_TESTBED_operation_done (op); + op = NULL; + result = SLAVE3_STARTED; + op = GNUNET_TESTBED_get_slave_config (NULL, mc, slave3); + GNUNET_assert (NULL != op); + break; + case SLAVE3_STARTED: + GNUNET_assert (NULL != event); + GNUNET_assert (GNUNET_TESTBED_ET_OPERATION_FINISHED == event->type); + GNUNET_assert (event->details.operation_finished.operation == op); + GNUNET_assert (NULL == event->details.operation_finished.op_cls); + GNUNET_assert (NULL == event->details.operation_finished.emsg); + cfg3 = GNUNET_CONFIGURATION_dup (event->details.operation_finished.generic); + GNUNET_TESTBED_operation_done (op); + result = SLAVE3_GET_CONFIG_SUCCESS; + op = GNUNET_TESTBED_controller_link (NULL, mc, slave3, slave, cfg3, + GNUNET_NO); + break; + case SLAVE3_GET_CONFIG_SUCCESS: + result = SLAVE3_LINK_SUCCESS; + GNUNET_TESTBED_operation_done (op); + op = GNUNET_TESTBED_peer_destroy (master_peer); + break; + case SLAVE3_LINK_SUCCESS: + check_operation_success (event); + result = SUCCESS; + GNUNET_TESTBED_operation_done (op); + op = NULL; + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply + (GNUNET_TIME_UNIT_SECONDS, 3), &do_shutdown, + NULL); + break; + default: + GNUNET_assert (0); + } +} + + +/** + * Callback which will be called to after a host registration succeeded or failed + * + * @param cls the host which has been registered + * @param emsg the error message; NULL if host registration is successful + */ +static void +registration_cont (void *cls, const char *emsg) +{ + rh = NULL; + switch (result) + { + case MASTER_PEER_START_SUCCESS: + GNUNET_assert (NULL == emsg); + GNUNET_assert (NULL != mc); + result = SLAVE1_REGISTERED; + slave2 = GNUNET_TESTBED_host_create_with_id (2, "127.0.0.1", NULL, 0); + GNUNET_assert (NULL != slave2); + rh = GNUNET_TESTBED_register_host (mc, slave2, ®istration_cont, NULL); + GNUNET_assert (NULL != rh); + break; + case SLAVE1_REGISTERED: + GNUNET_assert (NULL == emsg); + GNUNET_assert (NULL != mc); + result = SLAVE2_REGISTERED; + GNUNET_assert (NULL != cfg); + op = GNUNET_TESTBED_controller_link (NULL, mc, slave, NULL, cfg, + GNUNET_YES); + GNUNET_assert (NULL != op); + break; + case SLAVE2_PEER_DESTROY_SUCCESS: + GNUNET_assert (NULL == emsg); + GNUNET_assert (NULL != mc); + GNUNET_assert (NULL == op); + result = SLAVE3_REGISTERED; + op = GNUNET_TESTBED_controller_link (NULL, mc, slave3, NULL, cfg, + GNUNET_YES); + GNUNET_assert (NULL != op); + break; + default: + GNUNET_break (0); + do_abort_now (NULL); + } +} + +/** + * Callback to signal successfull startup of the controller process + * + * @param cls the closure from GNUNET_TESTBED_controller_start() + * @param cfg the configuration with which the controller has been started; + * NULL if status is not GNUNET_OK + * @param status GNUNET_OK if the startup is successfull; GNUNET_SYSERR if not, + * GNUNET_TESTBED_controller_stop() shouldn't be called in this case + */ +static void +status_cb (void *cls, const struct GNUNET_CONFIGURATION_Handle *config, + int status) +{ + switch (result) + { + case INIT: + GNUNET_assert (GNUNET_OK == status); + event_mask = 0; + event_mask |= (1L << GNUNET_TESTBED_ET_PEER_START); + event_mask |= (1L << GNUNET_TESTBED_ET_PEER_STOP); + event_mask |= (1L << GNUNET_TESTBED_ET_CONNECT); + event_mask |= (1L << GNUNET_TESTBED_ET_OPERATION_FINISHED); + mc = GNUNET_TESTBED_controller_connect (config, host, event_mask, + &controller_cb, NULL); + GNUNET_assert (NULL != mc); + result = MASTER_STARTED; + op = GNUNET_TESTBED_peer_create (mc, host, cfg, peer_create_cb, NULL); + GNUNET_assert (NULL != op); + break; + default: + GNUNET_break (0); + cp = NULL; + do_abort_now (NULL); + } +} + + +/** + * Callbacks of this type are called by GNUNET_TESTBED_is_host_habitable to + * inform whether the given host is habitable or not. The Handle returned by + * GNUNET_TESTBED_is_host_habitable() is invalid after this callback is called + * + * @param cls NULL + * @param host the host whose status is being reported; will be NULL if the host + * given to GNUNET_TESTBED_is_host_habitable() is NULL + * @param status GNUNET_YES if it is habitable; GNUNET_NO if not + */ +static void +host_habitable_cb (void *cls, const struct GNUNET_TESTBED_Host *_host, + int status) +{ + hc_handle = NULL; + if (GNUNET_NO == status) + { + (void) PRINTF ("%s", + "Unable to run the test as this system is not configured " + "to use password less SSH logins to localhost.\n" + "Skipping test\n"); + GNUNET_SCHEDULER_cancel (abort_task); + abort_task = GNUNET_SCHEDULER_NO_TASK; + (void) GNUNET_SCHEDULER_add_now (&do_shutdown, NULL); + result = SKIP; + return; + } + cp = GNUNET_TESTBED_controller_start ("127.0.0.1", host, cfg, status_cb, + NULL); +} + + +/** + * Main run function. + * + * @param cls NULL + * @param args arguments passed to GNUNET_PROGRAM_run + * @param cfgfile the path to configuration file + * @param cfg the configuration file handle + */ +static void +run (void *cls, char *const *args, const char *cfgfile, + const struct GNUNET_CONFIGURATION_Handle *config) +{ + host = GNUNET_TESTBED_host_create (NULL, NULL, 0); + GNUNET_assert (NULL != host); + if (NULL == + (hc_handle = + GNUNET_TESTBED_is_host_habitable (host, config, &host_habitable_cb, + NULL))) + { + GNUNET_TESTBED_host_destroy (host); + host = NULL; + (void) PRINTF ("%s", + "Unable to run the test as this system is not configured " + "to use password less SSH logins to localhost.\n" + "Marking test as successful\n"); + result = SKIP; + return; + } + cfg = GNUNET_CONFIGURATION_dup (config); + abort_task = + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply + (GNUNET_TIME_UNIT_MINUTES, 5), &do_abort, + NULL); +} + + +/** + * Main function + */ +int +main (int argc, char **argv) +{ + char *const argv2[] = { "test_testbed_api_controllerlink", + "-c", "test_testbed_api.conf", + NULL + }; + struct GNUNET_GETOPT_CommandLineOption options[] = { + GNUNET_GETOPT_OPTION_END + }; + int ret; + + result = INIT; + ret = + GNUNET_PROGRAM_run ((sizeof (argv2) / sizeof (char *)) - 1, argv2, + "test_testbed_api_controllerlink", "nohelp", options, + &run, NULL); + if (GNUNET_OK != ret) + return 1; + switch (result) + { + case SUCCESS: + return 0; + case SKIP: + return 77; /* Mark test as skipped */ + default: + return 1; + } +} + +/* end of test_testbed_api_controllerlink.c */ diff --git a/src/testbed/test_testbed_api_hosts.c b/src/testbed/test_testbed_api_hosts.c new file mode 100644 index 0000000..51284ea --- /dev/null +++ b/src/testbed/test_testbed_api_hosts.c @@ -0,0 +1,130 @@ +/* + This file is part of GNUnet + (C) 2008--2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. + */ + +/** + * @file testbed/test_testbed_api_hosts.c + * @brief tests cases for testbed_api_hosts.c + * @author Sree Harsha Totakura + */ + +#include "platform.h" +#include "gnunet_util_lib.h" +#include "gnunet_testbed_service.h" +#include "testbed_api_hosts.h" + + +#define TIME_REL_SECS(sec) \ + GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, sec) + +/** + * Host we are creating and using + */ +static struct GNUNET_TESTBED_Host *host; + +/** + * An array of hosts which are loaded from a file + */ +static struct GNUNET_TESTBED_Host **hosts; + +/** + * Number of hosts in the above list + */ +static unsigned int num_hosts; + +/** + * Global test status + */ +static int status; + +/** + * Shutdown task identifier + */ +GNUNET_SCHEDULER_TaskIdentifier shutdown_id; + +/** + * The shutdown task + * + * @param cls NULL + * @param tc the task context + */ +static void +do_shutdown (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + GNUNET_TESTBED_host_destroy (host); + while (0 != num_hosts) + { + GNUNET_TESTBED_host_destroy (hosts[num_hosts - 1]); + num_hosts--; + } + GNUNET_free (hosts); +} + + +/** + * Main run function. + * + * @param cls NULL + * @param args arguments passed to GNUNET_PROGRAM_run + * @param cfgfile the path to configuration file + * @param cfg the configuration file handle + */ +static void +run (void *cls, char *const *args, const char *cfgfile, + const struct GNUNET_CONFIGURATION_Handle *cfg) +{ + host = GNUNET_TESTBED_host_create ("localhost", NULL, 0); + GNUNET_assert (NULL != host); + GNUNET_assert (0 != GNUNET_TESTBED_host_get_id_ (host)); + GNUNET_TESTBED_host_destroy (host); + host = GNUNET_TESTBED_host_create (NULL, NULL, 0); + GNUNET_assert (NULL != host); + GNUNET_assert (0 == GNUNET_TESTBED_host_get_id_ (host)); + GNUNET_assert (host == GNUNET_TESTBED_host_lookup_by_id_ (0)); + hosts = NULL; + num_hosts = GNUNET_TESTBED_hosts_load_from_file ("sample_hosts.txt", &hosts); + GNUNET_assert (15 == num_hosts); + GNUNET_assert (NULL != hosts); + status = GNUNET_YES; + shutdown_id = + GNUNET_SCHEDULER_add_delayed (TIME_REL_SECS (2), &do_shutdown, NULL); +} + + +int +main (int argc, char **argv) +{ + char *const argv2[] = { "test_testbed_api_hosts", + "-c", "test_testbed_api.conf", + NULL + }; + struct GNUNET_GETOPT_CommandLineOption options[] = { + GNUNET_GETOPT_OPTION_END + }; + + status = GNUNET_SYSERR; + if (GNUNET_OK != + GNUNET_PROGRAM_run ((sizeof (argv2) / sizeof (char *)) - 1, argv2, + "test_testbed_api_hosts", "nohelp", options, &run, + NULL)) + return 1; + return (GNUNET_OK == status) ? 0 : 1; +} + +/* end of test_testbed_api_hosts.c */ diff --git a/src/testbed/test_testbed_api_operations.c b/src/testbed/test_testbed_api_operations.c new file mode 100644 index 0000000..24f23be --- /dev/null +++ b/src/testbed/test_testbed_api_operations.c @@ -0,0 +1,430 @@ +/* + This file is part of GNUnet + (C) 2008--2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. + */ + +/** + * @file testbed/test_testbed_api_operations.c + * @brief tests cases for testbed_api_operations.c + * @author Sree Harsha Totakura + */ + +#include "platform.h" +#include "gnunet_util_lib.h" +#include "testbed_api_operations.h" + +/** + * Generic logging shortcut + */ +#define LOG(kind,...) \ + GNUNET_log (kind, __VA_ARGS__) + +/** + * Queue A. Initially the max active is set to 2 and then reduced to 0 - this + * should block op2 even after op1 has finished. Later the max active is set to + * 2 and this should start op2 + */ +struct OperationQueue *q1; + +/** + * Queue B. Max active set to 2 is not changed throughout the test + */ +struct OperationQueue *q2; + +/** + * This operation should go into both queues and block op2 until it is done + */ +struct GNUNET_TESTBED_Operation *op1; + +/** + * This operation should go into q1 and q2 + */ +struct GNUNET_TESTBED_Operation *op2; + +/** + * This operation should go into both queues and should consume 2 units of + * resources on both queues. Since op2 needs a resource from both queues and is + * queues before this operation, it will be blocked until op2 is released even + * though q1 has + */ +struct GNUNET_TESTBED_Operation *op3; + +/** + * Just like op3, this operation also consumes 2 units of resources on both + * queues. Since this is queued after op3 and both queues are at max active + * 2. This will be blocked until op3 is done. + */ +struct GNUNET_TESTBED_Operation *op4; + +/** + * This operation is started after op4 is released and should consume only 1 + * resource on queue q1. It should be started along with op6 and op7 + */ +struct GNUNET_TESTBED_Operation *op5; + +/** + * This operation is started after op4 is released and should consume only 1 + * resource on q2. It should be started along with op5 and op7 + */ +struct GNUNET_TESTBED_Operation *op6; + +/** + * This operation is started after op4 is released and should consume 1 resource + * on both queues q1 and q1. It should be started along with op5 and op6 + */ +struct GNUNET_TESTBED_Operation *op7; + +/** + * The delay task identifier + */ +GNUNET_SCHEDULER_TaskIdentifier step_task; + + +/** + * Enumeration of test stages + */ +enum Test +{ + /** + * Initial stage + */ + TEST_INIT, + + /** + * op1 has been started + */ + TEST_OP1_STARTED, + + /** + * op1 has been released + */ + TEST_OP1_RELEASED, + + /** + * Temporary pause where no operations should start as we set max active in q1 + * to 0 in stage TEST_OP1_STARTED + */ + TEST_PAUSE, + + /** + * op2 has started + */ + TEST_OP2_STARTED, + + /** + * op2 released + */ + TEST_OP2_RELEASED, + + /** + * op3 has started + */ + TEST_OP3_STARTED, + + /** + * op3 has finished + */ + TEST_OP3_RELEASED, + + /** + * op4 has started + */ + TEST_OP4_STARTED, + + /** + * op4 has released + */ + TEST_OP4_RELEASED, + + /** + * op5, op6, op7 started + */ + TEST_OP5_6_7_STARTED, + + /** + * op5 has released + */ + TEST_OP5_RELEASED, + + /** + * op6 has released + */ + TEST_OP6_RELEASED, + + /** + * op7 has released + */ + TEST_OP7_RELEASED +}; + +/** + * The test result + */ +enum Test result; + + +/** + * Function to call to start an operation once all + * queues the operation is part of declare that the + * operation can be activated. + */ +static void +start_cb (void *cls); + + +/** + * Function to cancel an operation (release all associated resources). This can + * be because of a call to "GNUNET_TESTBED_operation_cancel" (before the + * operation generated an event) or AFTER the operation generated an event due + * to a call to "GNUNET_TESTBED_operation_done". Thus it is not guaranteed that + * a callback to the 'OperationStart' preceeds the call to 'OperationRelease'. + * Implementations of this function are expected to clean up whatever state is + * in 'cls' and release all resources associated with the operation. + */ +static void +release_cb (void *cls); + + +/** + * Task to simulate artificial delay and change the test stage + * + * @param cls NULL + * @param tc the task context + */ +static void +step (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + GNUNET_assert (GNUNET_SCHEDULER_NO_TASK != step_task); + step_task = GNUNET_SCHEDULER_NO_TASK; + switch (result) + { + case TEST_OP1_STARTED: + GNUNET_TESTBED_operation_release_ (op1); + GNUNET_TESTBED_operation_queue_reset_max_active_ (q1, 0); + op3 = GNUNET_TESTBED_operation_create_ (&op3, &start_cb, &release_cb); + GNUNET_TESTBED_operation_queue_insert2_ (q1, op3, 2); + GNUNET_TESTBED_operation_queue_insert2_ (q2, op3, 2); + GNUNET_TESTBED_operation_begin_wait_ (op3); + op4 = GNUNET_TESTBED_operation_create_ (&op4, &start_cb, &release_cb); + GNUNET_TESTBED_operation_queue_insert2_ (q1, op4, 2); + GNUNET_TESTBED_operation_queue_insert2_ (q2, op4, 2); + GNUNET_TESTBED_operation_begin_wait_ (op4); + break; + case TEST_OP1_RELEASED: + result = TEST_PAUSE; + GNUNET_TESTBED_operation_queue_reset_max_active_ (q1, 2); + break; + case TEST_OP2_STARTED: + GNUNET_TESTBED_operation_release_ (op2); + break; + case TEST_OP3_STARTED: + GNUNET_TESTBED_operation_release_ (op3); + break; + case TEST_OP4_STARTED: + GNUNET_TESTBED_operation_release_ (op4); + break; + default: + GNUNET_assert (0); + } +} + + +/** + * Function to call to start an operation once all + * queues the operation is part of declare that the + * operation can be activated. + */ +static void +start_cb (void *cls) +{ + switch (result) + { + case TEST_INIT: + GNUNET_assert (&op1 == cls); + result = TEST_OP1_STARTED; + GNUNET_assert (GNUNET_SCHEDULER_NO_TASK == step_task); + step_task = + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_SECONDS, &step, NULL); + break; + case TEST_PAUSE: + GNUNET_assert (&op2 == cls); + result = TEST_OP2_STARTED; + GNUNET_assert (GNUNET_SCHEDULER_NO_TASK == step_task); + step_task = + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_SECONDS, &step, NULL); + break; + case TEST_OP2_RELEASED: + GNUNET_assert (&op3 == cls); + result = TEST_OP3_STARTED; + GNUNET_assert (GNUNET_SCHEDULER_NO_TASK == step_task); + step_task = + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_SECONDS, &step, NULL); + break; + case TEST_OP3_RELEASED: + GNUNET_assert (&op4 == cls); + result = TEST_OP4_STARTED; + GNUNET_assert (GNUNET_SCHEDULER_NO_TASK == step_task); + step_task = + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_SECONDS, &step, NULL); + break; + case TEST_OP4_RELEASED: + { + static int nops; + + nops++; + if (nops == 3) + { + result = TEST_OP5_6_7_STARTED; + GNUNET_TESTBED_operation_release_ (op5); + op5 = NULL; + } + } + break; + default: + GNUNET_assert (0); + } +} + + +/** + * Function to cancel an operation (release all associated resources). This can + * be because of a call to "GNUNET_TESTBED_operation_cancel" (before the + * operation generated an event) or AFTER the operation generated an event due + * to a call to "GNUNET_TESTBED_operation_done". Thus it is not guaranteed that + * a callback to the 'OperationStart' preceeds the call to 'OperationRelease'. + * Implementations of this function are expected to clean up whatever state is + * in 'cls' and release all resources associated with the operation. + */ +static void +release_cb (void *cls) +{ + switch (result) + { + case TEST_OP1_STARTED: + GNUNET_assert (&op1 == cls); + result = TEST_OP1_RELEASED; + op1 = NULL; + step_task = + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_SECONDS, &step, NULL); + break; + case TEST_OP2_STARTED: + GNUNET_assert (&op2 == cls); + result = TEST_OP2_RELEASED; + GNUNET_assert (GNUNET_SCHEDULER_NO_TASK == step_task); + //step_task = GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_SECONDS, &step, NULL); + break; + case TEST_OP3_STARTED: + GNUNET_assert (&op3 == cls); + result = TEST_OP3_RELEASED; + GNUNET_assert (GNUNET_SCHEDULER_NO_TASK == step_task); + break; + case TEST_OP4_STARTED: + GNUNET_assert (&op4 == cls); + result = TEST_OP4_RELEASED; + GNUNET_assert (GNUNET_SCHEDULER_NO_TASK == step_task); + op5 = GNUNET_TESTBED_operation_create_ (&op5, &start_cb, &release_cb); + GNUNET_TESTBED_operation_queue_insert2_ (q1, op5, 1); + GNUNET_TESTBED_operation_begin_wait_ (op5); + op6 = GNUNET_TESTBED_operation_create_ (&op6, &start_cb, &release_cb); + GNUNET_TESTBED_operation_queue_insert2_ (q2, op6, 1); + GNUNET_TESTBED_operation_begin_wait_ (op6); + op7 = GNUNET_TESTBED_operation_create_ (&op7, &start_cb, &release_cb); + GNUNET_TESTBED_operation_queue_insert2_ (q1, op7, 1); + GNUNET_TESTBED_operation_queue_insert2_ (q2, op7, 1); + GNUNET_TESTBED_operation_begin_wait_ (op7); + break; + case TEST_OP5_6_7_STARTED: + result = TEST_OP5_RELEASED; + op5 = NULL; + GNUNET_TESTBED_operation_release_ (op6); + break; + case TEST_OP5_RELEASED: + op6 = NULL; + result = TEST_OP6_RELEASED; + GNUNET_TESTBED_operation_release_ (op7); + break; + case TEST_OP6_RELEASED: + result = TEST_OP7_RELEASED; + op7 = NULL; + GNUNET_TESTBED_operation_queue_destroy_ (q1); + GNUNET_TESTBED_operation_queue_destroy_ (q2); + q1 = NULL; + q2 = NULL; + break; + default: + GNUNET_assert (0); + } +} + + +/** + * Main run function. + * + * @param cls NULL + * @param args arguments passed to GNUNET_PROGRAM_run + * @param cfgfile the path to configuration file + * @param cfg the configuration file handle + */ +static void +run (void *cls, char *const *args, const char *cfgfile, + const struct GNUNET_CONFIGURATION_Handle *config) +{ + q1 = GNUNET_TESTBED_operation_queue_create_ (1); + GNUNET_assert (NULL != q1); + q2 = GNUNET_TESTBED_operation_queue_create_ (2); + GNUNET_assert (NULL != q2); + op1 = GNUNET_TESTBED_operation_create_ (&op1, start_cb, release_cb); + GNUNET_assert (NULL != op1); + op2 = GNUNET_TESTBED_operation_create_ (&op2, start_cb, release_cb); + GNUNET_TESTBED_operation_queue_insert_ (q1, op1); + GNUNET_TESTBED_operation_queue_insert_ (q2, op1); + GNUNET_TESTBED_operation_begin_wait_ (op1); + GNUNET_TESTBED_operation_queue_insert_ (q1, op2); + GNUNET_TESTBED_operation_queue_insert_ (q2, op2); + GNUNET_TESTBED_operation_begin_wait_ (op2); + result = TEST_INIT; +} + + +/** + * Main function + */ +int +main (int argc, char **argv) +{ + int ret; + char *const argv2[] = + { "test_testbed_api_operations", "-c", "test_testbed_api.conf", NULL }; + struct GNUNET_GETOPT_CommandLineOption options[] = + { GNUNET_GETOPT_OPTION_END }; + + ret = + GNUNET_PROGRAM_run ((sizeof (argv2) / sizeof (char *)) - 1, argv2, + "test_testbed_api_operations", "nohelp", options, + &run, NULL); + if ((GNUNET_OK != ret) || (TEST_OP7_RELEASED != result)) + return 1; + op1 = NULL; + op2 = NULL; + op3 = NULL; + q1 = NULL; + q2 = NULL; + return 0; +} + +/* end of test_testbed_api_operations.c */ diff --git a/src/testbed/test_testbed_api_test.c b/src/testbed/test_testbed_api_test.c new file mode 100644 index 0000000..705f52f --- /dev/null +++ b/src/testbed/test_testbed_api_test.c @@ -0,0 +1,241 @@ +/* + This file is part of GNUnet + (C) 2008--2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @file src/testbed/test_testbed_api_test.c + * @brief testing cases for testing high level testbed api helper functions + * @author Sree Harsha Totakura + */ + +#include "platform.h" +#include "gnunet_common.h" +#include "gnunet_testbed_service.h" + + +/** + * Generic logging shortcut + */ +#define LOG(kind,...) \ + GNUNET_log (kind, __VA_ARGS__) + +/** + * Number of peers we want to start + */ +#define NUM_PEERS 25 + +/** + * Array of peers + */ +static struct GNUNET_TESTBED_Peer **peers; + +/** + * Operation handle + */ +static struct GNUNET_TESTBED_Operation *op; + +/** + * Abort task identifier + */ +static GNUNET_SCHEDULER_TaskIdentifier abort_task; + +/** + * shutdown task identifier + */ +static GNUNET_SCHEDULER_TaskIdentifier shutdown_task; + +/** + * Testing result + */ +static int result; + + +/** + * Shutdown nicely + * + * @param cls NULL + * @param tc the task context + */ +static void +do_shutdown (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + shutdown_task = GNUNET_SCHEDULER_NO_TASK; + if (GNUNET_SCHEDULER_NO_TASK != abort_task) + GNUNET_SCHEDULER_cancel (abort_task); + if (NULL != op) + GNUNET_TESTBED_operation_done (op); + GNUNET_SCHEDULER_shutdown (); +} + +/** + * shortcut to exit during failure + */ +#define FAIL_TEST(cond) do { \ + if (!(cond)) { \ + GNUNET_break(0); \ + if (GNUNET_SCHEDULER_NO_TASK != abort_task) \ + GNUNET_SCHEDULER_cancel (abort_task); \ + abort_task = GNUNET_SCHEDULER_NO_TASK; \ + if (GNUNET_SCHEDULER_NO_TASK == shutdown_task) \ + shutdown_task = GNUNET_SCHEDULER_add_now (do_shutdown, NULL); \ + return; \ + } \ + } while (0) + + +/** + * abort task to run on test timed out + * + * @param cls NULL + * @param tc the task context + */ +static void +do_abort (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + LOG (GNUNET_ERROR_TYPE_WARNING, "Test timedout -- Aborting\n"); + abort_task = GNUNET_SCHEDULER_NO_TASK; + if (GNUNET_SCHEDULER_NO_TASK != shutdown_task) + GNUNET_SCHEDULER_cancel (shutdown_task); + shutdown_task = GNUNET_SCHEDULER_add_now (do_shutdown, NULL); +} + + +/** + * Callback to be called when the requested peer information is available + * + * @param cb_cls the closure from GNUNET_TETSBED_peer_get_information() + * @param op the operation this callback corresponds to + * @param pinfo the result; will be NULL if the operation has failed + * @param emsg error message if the operation has failed; will be NULL if the + * operation is successfull + */ +static void +peerinfo_cb (void *cb_cls, struct GNUNET_TESTBED_Operation *op_, + const struct GNUNET_TESTBED_PeerInformation *pinfo, + const char *emsg) +{ + FAIL_TEST (op == op_); + FAIL_TEST (NULL == cb_cls); + FAIL_TEST (NULL == emsg); + FAIL_TEST (GNUNET_TESTBED_PIT_IDENTITY == pinfo->pit); + FAIL_TEST (NULL != pinfo->result.id); + GNUNET_TESTBED_operation_done (op); + op = NULL; + result = GNUNET_OK; + shutdown_task = GNUNET_SCHEDULER_add_now (&do_shutdown, NULL); +} + + +/** + * Callback to be called when an operation is completed + * + * @param cls the callback closure from functions generating an operation + * @param op the operation that has been finished + * @param emsg error message in case the operation has failed; will be NULL if + * operation has executed successfully. + */ +static void +op_comp_cb (void *cls, struct GNUNET_TESTBED_Operation *op_, const char *emsg) +{ + FAIL_TEST (NULL == cls); + FAIL_TEST (op == op_); + if (NULL != emsg) + { + LOG (GNUNET_ERROR_TYPE_WARNING, "%s\n", emsg); + FAIL_TEST (0); + } + GNUNET_TESTBED_operation_done (op); + op = GNUNET_TESTBED_peer_get_information (peers[0], + GNUNET_TESTBED_PIT_IDENTITY, + &peerinfo_cb, NULL); +} + + +/** + * Controller event callback + * + * @param cls NULL + * @param event the controller event + */ +static void +controller_event_cb (void *cls, + const struct GNUNET_TESTBED_EventInformation *event) +{ + switch (event->type) + { + case GNUNET_TESTBED_ET_CONNECT: + FAIL_TEST (event->details.peer_connect.peer1 == peers[0]); + FAIL_TEST (event->details.peer_connect.peer2 == peers[1]); + break; + default: + FAIL_TEST (0); + } +} + + +/** + * Signature of a main function for a testcase. + * + * @param cls closure + * @param num_peers number of peers in 'peers' + * @param peers handle to peers run in the testbed + */ +static void +test_master (void *cls, unsigned int num_peers, + struct GNUNET_TESTBED_Peer **peers_) +{ + unsigned int peer; + + FAIL_TEST (NULL == cls); + FAIL_TEST (NUM_PEERS == num_peers); + FAIL_TEST (NULL != peers_); + for (peer = 0; peer < num_peers; peer++) + FAIL_TEST (NULL != peers_[peer]); + peers = peers_; + op = GNUNET_TESTBED_overlay_connect (NULL, &op_comp_cb, NULL, peers[0], + peers[1]); + abort_task = + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply + (GNUNET_TIME_UNIT_MINUTES, 3), &do_abort, + NULL); +} + + +/** + * Main function + */ +int +main (int argc, char **argv) +{ + uint64_t event_mask; + + result = GNUNET_SYSERR; + event_mask = 0; + event_mask |= (1LL << GNUNET_TESTBED_ET_CONNECT); + event_mask |= (1LL << GNUNET_TESTBED_ET_OPERATION_FINISHED); + (void) GNUNET_TESTBED_test_run ("test_testbed_api_test", + "test_testbed_api.conf", NUM_PEERS, + event_mask, &controller_event_cb, NULL, + &test_master, NULL); + if (GNUNET_OK != result) + return 1; + return 0; +} + +/* end of test_testbed_api_test.c */ diff --git a/src/testbed/test_testbed_api_testbed_run.c b/src/testbed/test_testbed_api_testbed_run.c new file mode 100644 index 0000000..9cad74a --- /dev/null +++ b/src/testbed/test_testbed_api_testbed_run.c @@ -0,0 +1,223 @@ +/* + This file is part of GNUnet + (C) 2008--2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @file testbed/test_testbed_api_testbed_run.c + * @brief Test cases for testing high-level testbed management + * @author Sree Harsha Totakura + */ + +#include "platform.h" +#include "gnunet_common.h" +#include "gnunet_testbed_service.h" + +/** + * Number of peers we want to start + */ +#define NUM_PEERS 5 + +/** + * The array of peers; we fill this as the peers are given to us by the testbed + */ +static struct GNUNET_TESTBED_Peer *peers[NUM_PEERS]; + +/** + * Operation handle + */ +static struct GNUNET_TESTBED_Operation *op; + +/** + * Abort task identifier + */ +static GNUNET_SCHEDULER_TaskIdentifier abort_task; + +/** + * Current peer id + */ +unsigned int peer_id; + +/** + * Testing result + */ +static int result; + + +/** + * Shutdown nicely + * + * @param cls NULL + * @param tc the task context + */ +static void +do_shutdown (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + if (GNUNET_SCHEDULER_NO_TASK != abort_task) + GNUNET_SCHEDULER_cancel (abort_task); + GNUNET_SCHEDULER_shutdown (); /* Stop scheduler to shutdown testbed run */ +} + + +/** + * abort task to run on test timed out + * + * @param cls NULL + * @param tc the task context + */ +static void +do_abort (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Test timedout -- Aborting\n"); + abort_task = GNUNET_SCHEDULER_NO_TASK; + GNUNET_SCHEDULER_add_now (&do_shutdown, NULL); +} + + +/** + * Signature of a main function for a testcase. + * + * @param cls closure + * @param num_peers number of peers in 'peers' + * @param peers handle to peers run in the testbed + */ +static void +test_master (void *cls, unsigned int num_peers, + struct GNUNET_TESTBED_Peer **peers_) +{ + result = GNUNET_OK; + GNUNET_assert (NULL != peers[0]); + op = GNUNET_TESTBED_peer_stop (peers[0], NULL, NULL); + GNUNET_assert (NULL != op); +} + + +/** + * Controller event callback + * + * @param cls NULL + * @param event the controller event + */ +static void +controller_event_cb (void *cls, + const struct GNUNET_TESTBED_EventInformation *event) +{ + + switch (event->type) + { + case GNUNET_TESTBED_ET_PEER_START: + GNUNET_assert (NULL == peers[peer_id]); + GNUNET_assert (NULL != event->details.peer_start.peer); + peers[peer_id++] = event->details.peer_start.peer; + break; + case GNUNET_TESTBED_ET_PEER_STOP: + GNUNET_assert (NULL != op); + GNUNET_TESTBED_operation_done (op); + GNUNET_assert (peers[0] == event->details.peer_stop.peer); + GNUNET_SCHEDULER_add_now (&do_shutdown, NULL); + break; + default: + GNUNET_assert (0); + } +} + + +/** + * Main run function. + * + * @param cls NULL + * @param args arguments passed to GNUNET_PROGRAM_run + * @param cfgfile the path to configuration file + * @param cfg the configuration file handle + */ +static void +run (void *cls, char *const *args, const char *cfgfile, + const struct GNUNET_CONFIGURATION_Handle *config) +{ + uint64_t event_mask; + + event_mask = 0; + event_mask |= (1LL << GNUNET_TESTBED_ET_PEER_START); + event_mask |= (1LL << GNUNET_TESTBED_ET_PEER_STOP); + GNUNET_TESTBED_run (NULL, config, NUM_PEERS, event_mask, &controller_event_cb, + NULL, &test_master, NULL); + abort_task = + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply + (GNUNET_TIME_UNIT_SECONDS, 300), &do_abort, + NULL); +} + + +/** + * Main function + */ +int +main (int argc, char **argv) +{ + char *argv2[] = { + "test_testbed_api_testbed_run", + "-c", NULL, + NULL + }; + struct GNUNET_GETOPT_CommandLineOption options[] = { + GNUNET_GETOPT_OPTION_END + }; + char *testname; + char *config_filename; + int ret; + + if (NULL == (testname = strrchr (argv[0], (int) '_'))) + { + GNUNET_break (0); + return 1; + } + testname++; + testname = GNUNET_strdup (testname); +#ifdef MINGW + { + char *period; + + /* check and remove .exe extension */ + period = strrchr (testname, (int) '.'); + if (NULL != period) + *period = '\0'; + else + GNUNET_break (0); /* Windows with no .exe? */ + } +#endif + if (0 != strcmp ("run", testname)) + { + GNUNET_asprintf (&config_filename, "test_testbed_api_testbed_run_%s.conf", + testname); + } + else + config_filename = GNUNET_strdup ("test_testbed_api.conf"); + GNUNET_free (testname); + argv2[2] = config_filename; + result = GNUNET_SYSERR; + ret = + GNUNET_PROGRAM_run ((sizeof (argv2) / sizeof (char *)) - 1, argv2, + "test_testbed_api_testbed_run", "nohelp", options, + &run, NULL); + GNUNET_free (config_filename); + if ((GNUNET_OK != ret) || (GNUNET_OK != result)) + return 1; + return 0; +} + +/* end of test_testbed_api_testbed_run.c */ diff --git a/src/testbed/test_testbed_api_testbed_run_topology2dtorus.conf b/src/testbed/test_testbed_api_testbed_run_topology2dtorus.conf new file mode 100644 index 0000000..ee0480e --- /dev/null +++ b/src/testbed/test_testbed_api_testbed_run_topology2dtorus.conf @@ -0,0 +1,79 @@ +[testbed] +AUTOSTART = NO +PORT = 12113 +ACCEPT_FROM = 127.0.0.1; +HOSTNAME = localhost +NEIGHBOUR_LIMIT = 100 +OVERLAY_TOPOLOGY = 2D_TORUS +#PREFIX = xterm -geometry 100x85 -T peer1 -e libtool --mode=execute gdb --args + +[fs] +AUTOSTART = NO + +[resolver] +AUTOSTART = NO + +[mesh] +AUTOSTART = NO + +[dht] +AUTOSTART = NO + +[block] +plugins = dht test + +[dhtcache] +QUOTA = 1 MB +DATABASE = sqlite + +[transport] +PLUGINS = tcp +ACCEPT_FROM6 = ::1; +ACCEPT_FROM = 127.0.0.1; +NEIGHBOUR_LIMIT = 50 +PORT = 12365 + +[ats] +WAN_QUOTA_OUT = 3932160 +WAN_QUOTA_IN = 3932160 + +[core] +PORT = 12092 +AUTOSTART = YES + +[arm] +DEFAULTSERVICES = core transport +PORT = 12366 + +[transport-tcp] +TIMEOUT = 300 s +PORT = 12368 + +[TESTING] +NUM_PEERS = 5 +WEAKRANDOM = YES +HOSTKEYSFILE = ../../contrib/testing_hostkeys.dat +MAX_CONCURRENT_SSH = 10 +USE_PROGRESSBARS = YES +PEERGROUP_TIMEOUT = 2400 s + +[gnunetd] +HOSTKEY = $SERVICEHOME/.hostkey + +[PATHS] +SERVICEHOME = /tmp/test-testbed/ + +[dns] +AUTOSTART = NO + +[nse] +AUTOSTART = NO + +[vpn] +AUTOSTART = NO + +[nat] +RETURN_LOCAL_ADDRESSES = YES + +[gns-helper-service-w32] +AUTOSTART = NO diff --git a/src/testbed/test_testbed_api_testbed_run_topologyclique.conf b/src/testbed/test_testbed_api_testbed_run_topologyclique.conf new file mode 100644 index 0000000..4ac9266 --- /dev/null +++ b/src/testbed/test_testbed_api_testbed_run_topologyclique.conf @@ -0,0 +1,79 @@ +[testbed] +AUTOSTART = NO +PORT = 12113 +ACCEPT_FROM = 127.0.0.1; +HOSTNAME = localhost +NEIGHBOUR_LIMIT = 100 +OVERLAY_TOPOLOGY = CLIQUE +#PREFIX = xterm -geometry 100x85 -T peer1 -e libtool --mode=execute gdb --args + +[fs] +AUTOSTART = NO + +[resolver] +AUTOSTART = NO + +[mesh] +AUTOSTART = NO + +[dht] +AUTOSTART = NO + +[block] +plugins = dht test + +[dhtcache] +QUOTA = 1 MB +DATABASE = sqlite + +[transport] +PLUGINS = tcp +ACCEPT_FROM6 = ::1; +ACCEPT_FROM = 127.0.0.1; +NEIGHBOUR_LIMIT = 50 +PORT = 12365 + +[ats] +WAN_QUOTA_OUT = 3932160 +WAN_QUOTA_IN = 3932160 + +[core] +PORT = 12092 +AUTOSTART = YES + +[arm] +DEFAULTSERVICES = core transport +PORT = 12366 + +[transport-tcp] +TIMEOUT = 300 s +PORT = 12368 + +[TESTING] +NUM_PEERS = 5 +WEAKRANDOM = YES +HOSTKEYSFILE = ../../contrib/testing_hostkeys.dat +MAX_CONCURRENT_SSH = 10 +USE_PROGRESSBARS = YES +PEERGROUP_TIMEOUT = 2400 s + +[gnunetd] +HOSTKEY = $SERVICEHOME/.hostkey + +[PATHS] +SERVICEHOME = /tmp/test-testbed/ + +[dns] +AUTOSTART = NO + +[nse] +AUTOSTART = NO + +[vpn] +AUTOSTART = NO + +[nat] +RETURN_LOCAL_ADDRESSES = YES + +[gns-helper-service-w32] +AUTOSTART = NO diff --git a/src/testbed/test_testbed_api_testbed_run_topologyfromfile.conf b/src/testbed/test_testbed_api_testbed_run_topologyfromfile.conf new file mode 100644 index 0000000..b66724f --- /dev/null +++ b/src/testbed/test_testbed_api_testbed_run_topologyfromfile.conf @@ -0,0 +1,80 @@ +[testbed] +AUTOSTART = NO +PORT = 12113 +ACCEPT_FROM = 127.0.0.1; +HOSTNAME = localhost +NEIGHBOUR_LIMIT = 100 +OVERLAY_TOPOLOGY = FROM_FILE +OVERLAY_TOPOLOGY_FILE = overlay_topology.txt +#PREFIX = xterm -geometry 100x85 -T peer1 -e libtool --mode=execute gdb --args + +[fs] +AUTOSTART = NO + +[resolver] +AUTOSTART = NO + +[mesh] +AUTOSTART = NO + +[dht] +AUTOSTART = NO + +[block] +plugins = dht test + +[dhtcache] +QUOTA = 1 MB +DATABASE = sqlite + +[transport] +PLUGINS = tcp +ACCEPT_FROM6 = ::1; +ACCEPT_FROM = 127.0.0.1; +NEIGHBOUR_LIMIT = 50 +PORT = 12365 + +[ats] +WAN_QUOTA_OUT = 3932160 +WAN_QUOTA_IN = 3932160 + +[core] +PORT = 12092 +AUTOSTART = YES + +[arm] +DEFAULTSERVICES = core transport +PORT = 12366 + +[transport-tcp] +TIMEOUT = 300 s +PORT = 12368 + +[TESTING] +NUM_PEERS = 5 +WEAKRANDOM = YES +HOSTKEYSFILE = ../../contrib/testing_hostkeys.dat +MAX_CONCURRENT_SSH = 10 +USE_PROGRESSBARS = YES +PEERGROUP_TIMEOUT = 2400 s + +[gnunetd] +HOSTKEY = $SERVICEHOME/.hostkey + +[PATHS] +SERVICEHOME = /tmp/test-testbed/ + +[dns] +AUTOSTART = NO + +[nse] +AUTOSTART = NO + +[vpn] +AUTOSTART = NO + +[nat] +RETURN_LOCAL_ADDRESSES = YES + +[gns-helper-service-w32] +AUTOSTART = NO diff --git a/src/testbed/test_testbed_api_testbed_run_topologyline.conf b/src/testbed/test_testbed_api_testbed_run_topologyline.conf new file mode 100644 index 0000000..289ccba --- /dev/null +++ b/src/testbed/test_testbed_api_testbed_run_topologyline.conf @@ -0,0 +1,79 @@ +[testbed] +AUTOSTART = NO +PORT = 12113 +ACCEPT_FROM = 127.0.0.1; +HOSTNAME = localhost +NEIGHBOUR_LIMIT = 100 +OVERLAY_TOPOLOGY = LINE +#PREFIX = xterm -geometry 100x85 -T peer1 -e libtool --mode=execute gdb --args + +[fs] +AUTOSTART = NO + +[resolver] +AUTOSTART = NO + +[mesh] +AUTOSTART = NO + +[dht] +AUTOSTART = NO + +[block] +plugins = dht test + +[dhtcache] +QUOTA = 1 MB +DATABASE = sqlite + +[transport] +PLUGINS = tcp +ACCEPT_FROM6 = ::1; +ACCEPT_FROM = 127.0.0.1; +NEIGHBOUR_LIMIT = 50 +PORT = 12365 + +[ats] +WAN_QUOTA_OUT = 3932160 +WAN_QUOTA_IN = 3932160 + +[core] +PORT = 12092 +AUTOSTART = YES + +[arm] +DEFAULTSERVICES = core transport +PORT = 12366 + +[transport-tcp] +TIMEOUT = 300 s +PORT = 12368 + +[TESTING] +NUM_PEERS = 5 +WEAKRANDOM = YES +HOSTKEYSFILE = ../../contrib/testing_hostkeys.dat +MAX_CONCURRENT_SSH = 10 +USE_PROGRESSBARS = YES +PEERGROUP_TIMEOUT = 2400 s + +[gnunetd] +HOSTKEY = $SERVICEHOME/.hostkey + +[PATHS] +SERVICEHOME = /tmp/test-testbed/ + +[dns] +AUTOSTART = NO + +[nse] +AUTOSTART = NO + +[vpn] +AUTOSTART = NO + +[nat] +RETURN_LOCAL_ADDRESSES = YES + +[gns-helper-service-w32] +AUTOSTART = NO diff --git a/src/testbed/test_testbed_api_testbed_run_topologyrandom.conf b/src/testbed/test_testbed_api_testbed_run_topologyrandom.conf new file mode 100644 index 0000000..027602e --- /dev/null +++ b/src/testbed/test_testbed_api_testbed_run_topologyrandom.conf @@ -0,0 +1,79 @@ +[testbed] +AUTOSTART = NO +PORT = 12113 +ACCEPT_FROM = 127.0.0.1; +HOSTNAME = localhost +OVERLAY_TOPOLOGY = RANDOM +OVERLAY_RANDOM_LINKS = 5 +#PREFIX = xterm -geometry 100x85 -T peer1 -e libtool --mode=execute gdb --args + +[fs] +AUTOSTART = NO + +[resolver] +AUTOSTART = NO + +[mesh] +AUTOSTART = NO + +[dht] +AUTOSTART = NO + +[block] +plugins = dht test + +[dhtcache] +QUOTA = 1 MB +DATABASE = sqlite + +[transport] +PLUGINS = tcp +ACCEPT_FROM6 = ::1; +ACCEPT_FROM = 127.0.0.1; +NEIGHBOUR_LIMIT = 50 +PORT = 12365 + +[ats] +WAN_QUOTA_OUT = 3932160 +WAN_QUOTA_IN = 3932160 + +[core] +PORT = 12092 +AUTOSTART = YES + +[arm] +DEFAULTSERVICES = core transport +PORT = 12366 + +[transport-tcp] +TIMEOUT = 300 s +PORT = 12368 + +[TESTING] +NUM_PEERS = 5 +WEAKRANDOM = YES +HOSTKEYSFILE = ../../contrib/testing_hostkeys.dat +MAX_CONCURRENT_SSH = 10 +USE_PROGRESSBARS = YES +PEERGROUP_TIMEOUT = 2400 s + +[gnunetd] +HOSTKEY = $SERVICEHOME/.hostkey + +[PATHS] +SERVICEHOME = /tmp/test-testbed/ + +[dns] +AUTOSTART = NO + +[nse] +AUTOSTART = NO + +[vpn] +AUTOSTART = NO + +[nat] +RETURN_LOCAL_ADDRESSES = YES + +[gns-helper-service-w32] +AUTOSTART = NO diff --git a/src/testbed/test_testbed_api_testbed_run_topologyring.conf b/src/testbed/test_testbed_api_testbed_run_topologyring.conf new file mode 100644 index 0000000..22d934d --- /dev/null +++ b/src/testbed/test_testbed_api_testbed_run_topologyring.conf @@ -0,0 +1,79 @@ +[testbed] +AUTOSTART = NO +PORT = 12113 +ACCEPT_FROM = 127.0.0.1; +HOSTNAME = localhost +NEIGHBOUR_LIMIT = 100 +OVERLAY_TOPOLOGY = RING +#PREFIX = xterm -geometry 100x85 -T peer1 -e libtool --mode=execute gdb --args + +[fs] +AUTOSTART = NO + +[resolver] +AUTOSTART = NO + +[mesh] +AUTOSTART = NO + +[dht] +AUTOSTART = NO + +[block] +plugins = dht test + +[dhtcache] +QUOTA = 1 MB +DATABASE = sqlite + +[transport] +PLUGINS = tcp +ACCEPT_FROM6 = ::1; +ACCEPT_FROM = 127.0.0.1; +NEIGHBOUR_LIMIT = 50 +PORT = 12365 + +[ats] +WAN_QUOTA_OUT = 3932160 +WAN_QUOTA_IN = 3932160 + +[core] +PORT = 12092 +AUTOSTART = YES + +[arm] +DEFAULTSERVICES = core transport +PORT = 12366 + +[transport-tcp] +TIMEOUT = 300 s +PORT = 12368 + +[TESTING] +NUM_PEERS = 5 +WEAKRANDOM = YES +HOSTKEYSFILE = ../../contrib/testing_hostkeys.dat +MAX_CONCURRENT_SSH = 10 +USE_PROGRESSBARS = YES +PEERGROUP_TIMEOUT = 2400 s + +[gnunetd] +HOSTKEY = $SERVICEHOME/.hostkey + +[PATHS] +SERVICEHOME = /tmp/test-testbed/ + +[dns] +AUTOSTART = NO + +[nse] +AUTOSTART = NO + +[vpn] +AUTOSTART = NO + +[nat] +RETURN_LOCAL_ADDRESSES = YES + +[gns-helper-service-w32] +AUTOSTART = NO diff --git a/src/testbed/test_testbed_api_testbed_run_topologyscalefree.conf b/src/testbed/test_testbed_api_testbed_run_topologyscalefree.conf new file mode 100644 index 0000000..22d934d --- /dev/null +++ b/src/testbed/test_testbed_api_testbed_run_topologyscalefree.conf @@ -0,0 +1,79 @@ +[testbed] +AUTOSTART = NO +PORT = 12113 +ACCEPT_FROM = 127.0.0.1; +HOSTNAME = localhost +NEIGHBOUR_LIMIT = 100 +OVERLAY_TOPOLOGY = RING +#PREFIX = xterm -geometry 100x85 -T peer1 -e libtool --mode=execute gdb --args + +[fs] +AUTOSTART = NO + +[resolver] +AUTOSTART = NO + +[mesh] +AUTOSTART = NO + +[dht] +AUTOSTART = NO + +[block] +plugins = dht test + +[dhtcache] +QUOTA = 1 MB +DATABASE = sqlite + +[transport] +PLUGINS = tcp +ACCEPT_FROM6 = ::1; +ACCEPT_FROM = 127.0.0.1; +NEIGHBOUR_LIMIT = 50 +PORT = 12365 + +[ats] +WAN_QUOTA_OUT = 3932160 +WAN_QUOTA_IN = 3932160 + +[core] +PORT = 12092 +AUTOSTART = YES + +[arm] +DEFAULTSERVICES = core transport +PORT = 12366 + +[transport-tcp] +TIMEOUT = 300 s +PORT = 12368 + +[TESTING] +NUM_PEERS = 5 +WEAKRANDOM = YES +HOSTKEYSFILE = ../../contrib/testing_hostkeys.dat +MAX_CONCURRENT_SSH = 10 +USE_PROGRESSBARS = YES +PEERGROUP_TIMEOUT = 2400 s + +[gnunetd] +HOSTKEY = $SERVICEHOME/.hostkey + +[PATHS] +SERVICEHOME = /tmp/test-testbed/ + +[dns] +AUTOSTART = NO + +[nse] +AUTOSTART = NO + +[vpn] +AUTOSTART = NO + +[nat] +RETURN_LOCAL_ADDRESSES = YES + +[gns-helper-service-w32] +AUTOSTART = NO diff --git a/src/testbed/test_testbed_api_testbed_run_topologysmallworld.conf b/src/testbed/test_testbed_api_testbed_run_topologysmallworld.conf new file mode 100644 index 0000000..fabc74f --- /dev/null +++ b/src/testbed/test_testbed_api_testbed_run_topologysmallworld.conf @@ -0,0 +1,83 @@ +[testbed] +AUTOSTART = NO +PORT = 12113 +ACCEPT_FROM = 127.0.0.1; +HOSTNAME = localhost +OVERLAY_TOPOLOGY = SMALL_WORLD +OVERLAY_RANDOM_LINKS = 3 +#PREFIX = xterm -geometry 100x85 -T peer1 -e libtool --mode=execute gdb --args + +[fs] +AUTOSTART = NO + +[resolver] +AUTOSTART = NO + +[mesh] +AUTOSTART = NO + +[dht] +AUTOSTART = NO + +[block] +plugins = dht test + +[dhtcache] +QUOTA = 1 MB +DATABASE = sqlite + +[transport] +PLUGINS = tcp +ACCEPT_FROM6 = ::1; +ACCEPT_FROM = 127.0.0.1; +NEIGHBOUR_LIMIT = 50 +PORT = 12365 + +[ats] +WAN_QUOTA_OUT = 3932160 +WAN_QUOTA_IN = 3932160 + +[core] +PORT = 12092 +AUTOSTART = YES + +[arm] +DEFAULTSERVICES = core transport +PORT = 12366 + +[transport-tcp] +TIMEOUT = 300 s +PORT = 12368 + +[TESTING] +NUM_PEERS = 5 +WEAKRANDOM = YES +HOSTKEYSFILE = ../../contrib/testing_hostkeys.dat +MAX_CONCURRENT_SSH = 10 +USE_PROGRESSBARS = YES +PEERGROUP_TIMEOUT = 2400 s + +[gnunetd] +HOSTKEY = $SERVICEHOME/.hostkey + +[PATHS] +SERVICEHOME = /tmp/test-testbed/ + +[dns] +AUTOSTART = NO + +[nse] +AUTOSTART = NO + +[vpn] +AUTOSTART = NO + +[nat] +RETURN_LOCAL_ADDRESSES = YES + +[gns-helper-service-w32] +AUTOSTART = NO + +[consensus] +AUTOSTART = NO + diff --git a/src/testbed/test_testbed_api_testbed_run_topologysmallworldring.conf b/src/testbed/test_testbed_api_testbed_run_topologysmallworldring.conf new file mode 100644 index 0000000..7b26f4f --- /dev/null +++ b/src/testbed/test_testbed_api_testbed_run_topologysmallworldring.conf @@ -0,0 +1,83 @@ +[testbed] +AUTOSTART = NO +PORT = 12113 +ACCEPT_FROM = 127.0.0.1; +HOSTNAME = localhost +OVERLAY_TOPOLOGY = SMALL_WORLD_RING +OVERLAY_RANDOM_LINKS = 3 +#PREFIX = xterm -geometry 100x85 -T peer1 -e libtool --mode=execute gdb --args + +[fs] +AUTOSTART = NO + +[resolver] +AUTOSTART = NO + +[mesh] +AUTOSTART = NO + +[dht] +AUTOSTART = NO + +[block] +plugins = dht test + +[dhtcache] +QUOTA = 1 MB +DATABASE = sqlite + +[transport] +PLUGINS = tcp +ACCEPT_FROM6 = ::1; +ACCEPT_FROM = 127.0.0.1; +NEIGHBOUR_LIMIT = 50 +PORT = 12365 + +[ats] +WAN_QUOTA_OUT = 3932160 +WAN_QUOTA_IN = 3932160 + +[core] +PORT = 12092 +AUTOSTART = YES + +[arm] +DEFAULTSERVICES = core transport +PORT = 12366 + +[transport-tcp] +TIMEOUT = 300 s +PORT = 12368 + +[TESTING] +NUM_PEERS = 5 +WEAKRANDOM = YES +HOSTKEYSFILE = ../../contrib/testing_hostkeys.dat +MAX_CONCURRENT_SSH = 10 +USE_PROGRESSBARS = YES +PEERGROUP_TIMEOUT = 2400 s + +[gnunetd] +HOSTKEY = $SERVICEHOME/.hostkey + +[PATHS] +SERVICEHOME = /tmp/test-testbed/ + +[dns] +AUTOSTART = NO + +[nse] +AUTOSTART = NO + +[vpn] +AUTOSTART = NO + +[nat] +RETURN_LOCAL_ADDRESSES = YES + +[gns-helper-service-w32] +AUTOSTART = NO + +[consensus] +AUTOSTART = NO + diff --git a/src/testbed/test_testbed_api_topology.c b/src/testbed/test_testbed_api_topology.c new file mode 100644 index 0000000..0098dbe --- /dev/null +++ b/src/testbed/test_testbed_api_topology.c @@ -0,0 +1,172 @@ +/* + This file is part of GNUnet + (C) 2008--2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @file src/testbed/test_testbed_api_topology.c + * @brief testing cases for testing high level testbed api helper functions + * @author Sree Harsha Totakura + */ + +#include "platform.h" +#include "gnunet_common.h" +#include "gnunet_testbed_service.h" + +/** + * Number of peers we want to start + */ +#define NUM_PEERS 10 + +/** + * Array of peers + */ +static struct GNUNET_TESTBED_Peer **peers; + +/** + * Operation handle + */ +static struct GNUNET_TESTBED_Operation *op; + +/** + * Shutdown task + */ +static GNUNET_SCHEDULER_TaskIdentifier shutdown_task; + +/** + * Testing result + */ +static int result; + +/** + * Counter for counting overlay connections + */ +static unsigned int overlay_connects; + + +/** + * Shutdown nicely + * + * @param cls NULL + * @param tc the task context + */ +static void +do_shutdown (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + shutdown_task = GNUNET_SCHEDULER_NO_TASK; + if (NULL != op) + { + GNUNET_TESTBED_operation_done (op); + op = NULL; + } + GNUNET_SCHEDULER_shutdown (); +} + +/** + * Controller event callback + * + * @param cls NULL + * @param event the controller event + */ +static void +controller_event_cb (void *cls, + const struct GNUNET_TESTBED_EventInformation *event) +{ + switch (event->type) + { + case GNUNET_TESTBED_ET_CONNECT: + overlay_connects++; + if ((NUM_PEERS) == overlay_connects) + { + result = GNUNET_OK; + GNUNET_SCHEDULER_add_now (&do_shutdown, NULL); + } + break; + case GNUNET_TESTBED_ET_OPERATION_FINISHED: + GNUNET_assert (NULL != event->details.operation_finished.emsg); + break; + default: + GNUNET_break (0); + if ((GNUNET_TESTBED_ET_OPERATION_FINISHED == event->type) && + (NULL != event->details.operation_finished.emsg)) + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "An operation failed with error: %s\n", + event->details.operation_finished.emsg); + result = GNUNET_SYSERR; + GNUNET_SCHEDULER_cancel (shutdown_task); + shutdown_task = GNUNET_SCHEDULER_add_now (&do_shutdown, NULL); + } +} + + +/** + * Signature of a main function for a testcase. + * + * @param cls closure + * @param num_peers number of peers in 'peers' + * @param peers handle to peers run in the testbed + */ +static void +test_master (void *cls, unsigned int num_peers, + struct GNUNET_TESTBED_Peer **peers_) +{ + unsigned int peer; + + GNUNET_assert (NULL == cls); + GNUNET_assert (NUM_PEERS == num_peers); + GNUNET_assert (NULL != peers_); + for (peer = 0; peer < num_peers; peer++) + GNUNET_assert (NULL != peers_[peer]); + peers = peers_; + overlay_connects = 0; + op = GNUNET_TESTBED_overlay_configure_topology (NULL, NUM_PEERS, peers, NULL, + NULL, + NULL, + GNUNET_TESTBED_TOPOLOGY_ERDOS_RENYI, + NUM_PEERS, + GNUNET_TESTBED_TOPOLOGY_OPTION_END); + GNUNET_assert (NULL != op); + shutdown_task = + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply + (GNUNET_TIME_UNIT_SECONDS, 300), + do_shutdown, NULL); +} + + +/** + * Main function + */ +int +main (int argc, char **argv) +{ + uint64_t event_mask; + + result = GNUNET_SYSERR; + event_mask = 0; + event_mask |= (1LL << GNUNET_TESTBED_ET_CONNECT); + event_mask |= (1LL << GNUNET_TESTBED_ET_OPERATION_FINISHED); + (void) GNUNET_TESTBED_test_run ("test_testbed_api_test", + "test_testbed_api.conf", NUM_PEERS, + event_mask, &controller_event_cb, NULL, + &test_master, NULL); + if (GNUNET_OK != result) + return 1; + return 0; +} + +/* end of test_testbed_api_topology.c */ diff --git a/src/testbed/test_testbed_api_topology_clique.c b/src/testbed/test_testbed_api_topology_clique.c new file mode 100644 index 0000000..3f1ed7a --- /dev/null +++ b/src/testbed/test_testbed_api_topology_clique.c @@ -0,0 +1,168 @@ +/* + This file is part of GNUnet + (C) 2008--2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @file src/testbed/test_testbed_api_topology.c + * @brief testing cases for testing high level testbed api helper functions + * @author Sree Harsha Totakura + */ + +#include "platform.h" +#include "gnunet_common.h" +#include "gnunet_testbed_service.h" + +/** + * Number of peers we want to start + */ +#define NUM_PEERS 10 + +/** + * Array of peers + */ +static struct GNUNET_TESTBED_Peer **peers; + +/** + * Operation handle + */ +static struct GNUNET_TESTBED_Operation *op; + +/** + * Shutdown task + */ +static GNUNET_SCHEDULER_TaskIdentifier shutdown_task; + +/** + * Testing result + */ +static int result; + +/** + * Counter for counting overlay connections + */ +static unsigned int overlay_connects; + + +/** + * Shutdown nicely + * + * @param cls NULL + * @param tc the task context + */ +static void +do_shutdown (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + shutdown_task = GNUNET_SCHEDULER_NO_TASK; + if (NULL != op) + { + GNUNET_TESTBED_operation_done (op); + op = NULL; + } + GNUNET_SCHEDULER_shutdown (); +} + +/** + * Controller event callback + * + * @param cls NULL + * @param event the controller event + */ +static void +controller_event_cb (void *cls, + const struct GNUNET_TESTBED_EventInformation *event) +{ + switch (event->type) + { + case GNUNET_TESTBED_ET_CONNECT: + overlay_connects++; + if ((NUM_PEERS * (NUM_PEERS - 1)) == overlay_connects) + { + result = GNUNET_OK; + GNUNET_SCHEDULER_add_now (&do_shutdown, NULL); + } + break; + case GNUNET_TESTBED_ET_OPERATION_FINISHED: + GNUNET_assert (NULL != event->details.operation_finished.emsg); + break; + default: + GNUNET_break (0); + result = GNUNET_SYSERR; + GNUNET_SCHEDULER_cancel (shutdown_task); + shutdown_task = GNUNET_SCHEDULER_add_now (&do_shutdown, NULL); + } +} + + +/** + * Signature of a main function for a testcase. + * + * @param cls closure + * @param num_peers number of peers in 'peers' + * @param peers handle to peers run in the testbed + */ +static void +test_master (void *cls, unsigned int num_peers, + struct GNUNET_TESTBED_Peer **peers_) +{ + unsigned int peer; + + GNUNET_assert (NULL == cls); + GNUNET_assert (NUM_PEERS == num_peers); + GNUNET_assert (NULL != peers_); + for (peer = 0; peer < num_peers; peer++) + GNUNET_assert (NULL != peers_[peer]); + peers = peers_; + overlay_connects = 0; + op = GNUNET_TESTBED_overlay_configure_topology (NULL, NUM_PEERS, peers, NULL, + NULL, + NULL, + GNUNET_TESTBED_TOPOLOGY_CLIQUE, + /* GNUNET_TESTBED_TOPOLOGY_ERDOS_RENYI, */ + /* NUM_PEERS, */ + GNUNET_TESTBED_TOPOLOGY_OPTION_END); + GNUNET_assert (NULL != op); + shutdown_task = + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply + (GNUNET_TIME_UNIT_SECONDS, 300), + do_shutdown, NULL); +} + + +/** + * Main function + */ +int +main (int argc, char **argv) +{ + uint64_t event_mask; + + result = GNUNET_SYSERR; + event_mask = 0; + event_mask |= (1LL << GNUNET_TESTBED_ET_CONNECT); + event_mask |= (1LL << GNUNET_TESTBED_ET_OPERATION_FINISHED); + (void) GNUNET_TESTBED_test_run ("test_testbed_api_test", + "test_testbed_api.conf", NUM_PEERS, + event_mask, &controller_event_cb, NULL, + &test_master, NULL); + if (GNUNET_OK != result) + return 1; + return 0; +} + +/* end of test_testbed_api_topology.c */ diff --git a/src/testbed/testbed.conf b/src/testbed/testbed.conf deleted file mode 100644 index e69de29..0000000 diff --git a/src/testbed/testbed.conf.in b/src/testbed/testbed.conf.in new file mode 100644 index 0000000..ec05c76 --- /dev/null +++ b/src/testbed/testbed.conf.in @@ -0,0 +1,18 @@ +[testbed] +AUTOSTART = NO +@UNIXONLY@ PORT = 2101 +HOSTNAME = localhost +HOME = $SERVICEHOME +BINARY = gnunet-service-testbed +# Set this to the path where the testbed helper is installed +# HELPER_BINARY_PATH = @prefix@/lib/gnunet/libexec/gnunet-helper-testbed +ACCEPT_FROM = 127.0.0.1; +ACCEPT_FROM6 = ::1; +UNIXPATH = /tmp/gnunet-service-testbed.sock +UNIX_MATCH_UID = YES +UNIX_MATCH_GID = YES +MAX_PARALLEL_OPERATIONS = 1000 +MAX_PARALLEL_SERVICE_CONNECTIONS = 256 +MAX_PARALLEL_TOPOLOGY_CONFIG_OPERATIONS = 1 +CACHE_SIZE = 30 +MAX_OPEN_FDS = 512 diff --git a/src/testbed/testbed.h b/src/testbed/testbed.h index b7b10ff..180464b 100644 --- a/src/testbed/testbed.h +++ b/src/testbed/testbed.h @@ -24,28 +24,28 @@ * @author Christian Grothoff */ -#ifndef NEW_TESTING_H -#define NEW_TESTING_H +#ifndef TESTBED_H +#define TESTBED_H #include "gnunet_util_lib.h" - +GNUNET_NETWORK_STRUCT_BEGIN /** * Initial message from a client to a testing control service. */ -struct GNUNET_TESTBED_Message + struct GNUNET_TESTBED_InitMessage { /** - * Type is + * Type is GNUNET_MESSAGE_TYPE_TESTBED_INIT */ struct GNUNET_MessageHeader header; /** - * Host ID that the controller is either given - * (if this is the dominating client communicating - * via stdin) or assumed to have (for peer-connections - * between controllers). + * Host ID that the controller is either given (if this is the + * dominating client) or assumed to have (for peer-connections + * between controllers). A controller must check that all + * connections make consistent claims... */ uint32_t host_id GNUNET_PACKED; @@ -55,6 +55,7 @@ struct GNUNET_TESTBED_Message */ uint64_t event_mask GNUNET_PACKED; + /* Followed by 0-terminated hostname of the controller */ }; @@ -65,7 +66,7 @@ struct GNUNET_TESTBED_AddHostMessage { /** - * Type is + * Type is GNUNET_MESSAGE_TYPE_TESTBED_ADD_HOST */ struct GNUNET_MessageHeader header; @@ -96,12 +97,13 @@ struct GNUNET_TESTBED_AddHostMessage /** * Confirmation from the service that adding a host * worked (or failed). + * FIXME: Where is this required? */ struct GNUNET_TESTBED_HostConfirmedMessage { /** - * Type is + * Type is GNUNET_MESSAGE_TYPE_TESTBED_ADD_HOST_SUCCESS */ struct GNUNET_MessageHeader header; @@ -110,9 +112,8 @@ struct GNUNET_TESTBED_HostConfirmedMessage */ uint32_t host_id GNUNET_PACKED; - /* followed by the 0-terminated error message (on failure) - (typical errors include failure to login and - host-id already in use) */ + /* followed by the 0-terminated error message (on failure) + * (typical errors include host-id already in use) */ }; @@ -125,7 +126,7 @@ struct GNUNET_TESTBED_ConfigureSharedServiceMessage { /** - * Type is + * Type is GNUNET_MESSAGE_TYPE_TESTBED_SHARE_SERVICE */ struct GNUNET_MessageHeader header; @@ -154,7 +155,7 @@ struct GNUNET_TESTBED_ControllerLinkMessage { /** - * Type is + * Type is GNUNET_MESSAGE_TYPE_TESTBED_LINK_CONTROLLERS */ struct GNUNET_MessageHeader header; @@ -163,35 +164,50 @@ struct GNUNET_TESTBED_ControllerLinkMessage */ uint32_t delegated_host_id GNUNET_PACKED; + /** + * The id of the operation which created this message + */ + uint64_t operation_id GNUNET_PACKED; + /** * Which host is responsible for managing the delegation? NBO */ uint32_t slave_host_id GNUNET_PACKED; /** - * Is the receiving controller the master controller for - * the slave host (and thus responsible for starting it?). NBO. + * The size of the uncompressed configuration */ - int32_t is_subordinate GNUNET_PACKED; + uint16_t config_size GNUNET_PACKED; + + /** + * Set to 1 if the receiving controller is the master controller for + * the slave host (and thus responsible for starting it?). 0 if not + */ + uint8_t is_subordinate; /* followed by serialized slave configuration; - gzip'ed configuration file in INI format */ + * gzip'ed configuration file in INI format */ }; /** - * Message sent from client to testing service to + * Message sent from client to testing service to * create (configure, but not start) a peer. */ struct GNUNET_TESTBED_PeerCreateMessage { /** - * Type is + * Type is GNUNET_MESSAGE_TYPE_TESTBED_CREATE_PEER */ struct GNUNET_MessageHeader header; + /** + * Unique operation id + */ + uint64_t operation_id GNUNET_PACKED; + /** * On which host should the peer be started? */ @@ -202,21 +218,26 @@ struct GNUNET_TESTBED_PeerCreateMessage */ uint32_t peer_id GNUNET_PACKED; + /** + * Size of the uncompressed configuration + */ + uint32_t config_size GNUNET_PACKED; + /* followed by serialized peer configuration; - gzip'ed configuration file in INI format */ - + * gzip'ed configuration file in INI format */ + }; /** - * Message sent from client to testing service to + * Message sent from client to testing service to * reconfigure a (stopped) a peer. */ struct GNUNET_TESTBED_PeerReconfigureMessage { /** - * Type is + * Type is GNUNET_MESSAGE_TYPDE_TESTBED_RECONFIGURE_PEER */ struct GNUNET_MessageHeader header; @@ -231,8 +252,8 @@ struct GNUNET_TESTBED_PeerReconfigureMessage uint64_t operation_id GNUNET_PACKED; /* followed by serialized peer configuration; - gzip'ed configuration file in INI format */ - + * gzip'ed configuration file in INI format */ + }; @@ -244,7 +265,7 @@ struct GNUNET_TESTBED_PeerStartMessage { /** - * Type is + * Type is GNUNET_MESSAGE_TYPE_TESTBED_START_PEER */ struct GNUNET_MessageHeader header; @@ -269,7 +290,7 @@ struct GNUNET_TESTBED_PeerStopMessage { /** - * Type is + * Type is GNUNET_MESSAGE_TYPE_TESTBED_STOP_PEER */ struct GNUNET_MessageHeader header; @@ -294,7 +315,7 @@ struct GNUNET_TESTBED_PeerDestroyMessage { /** - * Type is + * Type is GNUNET_MESSAGE_TYPE_TESTBED_DESTROY_PEER */ struct GNUNET_MessageHeader header; @@ -319,7 +340,7 @@ struct GNUNET_TESTBED_ConfigureUnderlayLinkMessage { /** - * Type is + * Type is GNUNET_MESSAGE_TYPE_TESTBED_CONFIGURE_UNDERLAY_LINK */ struct GNUNET_MessageHeader header; @@ -356,7 +377,7 @@ struct GNUNET_TESTBED_OverlayConnectMessage { /** - * Type is + * Type is GNUNET_MESSAGE_TYPE_TESTBED_OVERLAY_CONNECT */ struct GNUNET_MessageHeader header; @@ -375,6 +396,45 @@ struct GNUNET_TESTBED_OverlayConnectMessage */ uint32_t peer2 GNUNET_PACKED; + /** + * The ID of the host which runs peer2 + */ + uint32_t peer2_host_id GNUNET_PACKED; + +}; + + +/** + * Message sent from host controller of a peer(A) to the host controller of + * another peer(B) to request B to connect to A + */ +struct GNUNET_TESTBED_RemoteOverlayConnectMessage +{ + /** + * Type is GNUNET_MESSAGE_TYPE_TESTBED_REMOTE_OVERLAY_CONNECT + */ + struct GNUNET_MessageHeader header; + + /** + * The Unique ID of B + */ + uint32_t peer GNUNET_PACKED; + + /** + * The Operation ID that is used to identify this operation + */ + uint64_t operation_id GNUNET_PACKED; + + /** + * Identity of A + */ + struct GNUNET_PeerIdentity peer_identity; + + /** + * To be followed by the HELLO message of A + */ + struct GNUNET_MessageHeader hello[0]; + }; @@ -385,7 +445,7 @@ struct GNUNET_TESTBED_PeerEventMessage { /** - * Type is + * Type is GNUNET_MESSAGE_TYPE_TESTBED_PEER_EVENT */ struct GNUNET_MessageHeader header; @@ -394,7 +454,7 @@ struct GNUNET_TESTBED_PeerEventMessage * either GNUNET_TESTBED_ET_PEER_START or GNUNET_TESTBED_ET_PEER_STOP. */ int32_t event_type GNUNET_PACKED; - + /** * Host where the peer is running. */ @@ -420,16 +480,16 @@ struct GNUNET_TESTBED_ConnectionEventMessage { /** - * Type is + * Type is GNUNET_MESSAGE_TYPE_TESTBED_PEER_CONNECT_EVENT */ struct GNUNET_MessageHeader header; /** * 'enum GNUNET_TESTBED_EventType' (in NBO); - * either GNUNET_TESTBED_ET_PEER_CONNECT or GNUNET_TESTBED_ET_PEER_DISCONNECT. + * either GNUNET_TESTBED_ET_CONNECT or GNUNET_TESTBED_ET_DISCONNECT. */ int32_t event_type GNUNET_PACKED; - + /** * First peer. */ @@ -455,7 +515,7 @@ struct GNUNET_TESTBED_OperationFailureEventMessage { /** - * Type is + * Type is GNUNET_MESSAGE_TYPE_TESTBED_OPERATION_FAIL_EVENT */ struct GNUNET_MessageHeader header; @@ -464,7 +524,7 @@ struct GNUNET_TESTBED_OperationFailureEventMessage * GNUNET_TESTBED_ET_OPERATION_FINISHED. */ int32_t event_type GNUNET_PACKED; - + /** * Operation ID of the operation that created this event. */ @@ -482,7 +542,7 @@ struct GNUNET_TESTBED_PeerCreateSuccessEventMessage { /** - * Type is + * Type is GNUNET_MESSAGE_TYPE_TESTBED_CREATE_PEER_SUCCESS */ struct GNUNET_MessageHeader header; @@ -490,19 +550,12 @@ struct GNUNET_TESTBED_PeerCreateSuccessEventMessage * Peer identity of the peer that was created. */ uint32_t peer_id GNUNET_PACKED; - + /** * Operation ID of the operation that created this event. */ uint64_t operation_id GNUNET_PACKED; - /** - * Identity of the peer. - */ - struct GNUNET_PeerIdentity peer_id; - - /* followed by gzip-compressed configuration of the peer */ - }; @@ -515,7 +568,7 @@ struct GNUNET_TESTBED_GenericOperationSuccessEventMessage { /** - * Type is + * Type is GNUNET_MESSAGE_TYPE_TESTBED_GENERIC_OPERATION_SUCCESS */ struct GNUNET_MessageHeader header; @@ -524,7 +577,7 @@ struct GNUNET_TESTBED_GenericOperationSuccessEventMessage * GNUNET_TESTBED_ET_OPERATION_FINISHED. */ int32_t event_type GNUNET_PACKED; - + /** * Operation ID of the operation that created this event. */ @@ -532,4 +585,121 @@ struct GNUNET_TESTBED_GenericOperationSuccessEventMessage }; + +/** + * Message sent from client to testing service to + * obtain the configuration of a peer. + */ +struct GNUNET_TESTBED_PeerGetConfigurationMessage +{ + + /** + * Type is GNUNET_MESSAGE_TYPE_TESTBED_GET_PEER_CONFIGURATION + */ + struct GNUNET_MessageHeader header; + + /** + * Unique ID for the peer. + */ + uint32_t peer_id GNUNET_PACKED; + + /** + * Operation ID that is used to identify this operation. + */ + uint64_t operation_id GNUNET_PACKED; + +}; + + +/** + * Peer configuration and identity reply from controller to a client. + */ +struct GNUNET_TESTBED_PeerConfigurationInformationMessage +{ + + /** + * Type is GNUNET_MESSAGE_TYPE_TESTBED_PEER_CONFIGURATION + */ + struct GNUNET_MessageHeader header; + + /** + * The id of the peer relevant to this information + */ + uint32_t peer_id GNUNET_PACKED; + + /** + * Operation ID of the operation that created this event. + */ + uint64_t operation_id GNUNET_PACKED; + + /** + * Identity of the peer. + */ + struct GNUNET_PeerIdentity peer_identity; + + /** + * The size of configuration when uncompressed + */ + uint16_t config_size GNUNET_PACKED; + + /* followed by gzip-compressed configuration of the peer */ + +}; + + +/** + * Message to request configuration of a slave controller + */ +struct GNUNET_TESTBED_SlaveGetConfigurationMessage +{ + /** + * Type is GNUNET_MESSAGE_TYPE_TESTBED_GET_SLAVE_CONFIGURATION + */ + struct GNUNET_MessageHeader header; + + /** + * The id of the slave host + */ + uint32_t slave_id GNUNET_PACKED; + + /** + * Operation ID + */ + uint64_t operation_id GNUNET_PACKED; + +}; + + +/** + * Reply to GNUNET_MESSAGE_TYPE_TESTBED_GET_SLAVE_CONFIG message + */ +struct GNUNET_TESTBED_SlaveConfiguration +{ + /** + * Type is GNUNET_MESSAGE_TYPE_TESTBED_SLAVE_CONFIGURATION + */ + struct GNUNET_MessageHeader header; + + /** + * The id of the host where the slave is running + */ + uint32_t slave_id GNUNET_PACKED; + + /** + * Operation ID + */ + uint64_t operation_id GNUNET_PACKED; + + /** + * The size of the configuration when uncompressed + */ + uint16_t config_size GNUNET_PACKED; + + /* followed by gzip-compressed configuration of the peer */ + +}; + + +GNUNET_NETWORK_STRUCT_END #endif +/* end of testbed.h */ diff --git a/src/testbed/testbed_api.c b/src/testbed/testbed_api.c index 5168081..054aa3b 100644 --- a/src/testbed/testbed_api.c +++ b/src/testbed/testbed_api.c @@ -24,15 +24,1772 @@ * This library is supposed to make it easier to write * testcases and script large-scale benchmarks. * @author Christian Grothoff + * @author Sree Harsha Totakura */ + + #include "platform.h" #include "gnunet_testbed_service.h" #include "gnunet_core_service.h" #include "gnunet_constants.h" #include "gnunet_transport_service.h" #include "gnunet_hello_lib.h" +#include + +#include "testbed.h" +#include "testbed_api.h" +#include "testbed_api_hosts.h" +#include "testbed_api_peers.h" +#include "testbed_api_operations.h" + +/** + * Generic logging shorthand + */ +#define LOG(kind, ...) \ + GNUNET_log_from (kind, "testbed-api", __VA_ARGS__); + +/** + * Debug logging + */ +#define LOG_DEBUG(...) \ + LOG (GNUNET_ERROR_TYPE_DEBUG, __VA_ARGS__); + +/** + * Relative time seconds shorthand + */ +#define TIME_REL_SECS(sec) \ + GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, sec) + + +/** + * Default server message sending retry timeout + */ +#define TIMEOUT_REL TIME_REL_SECS(1) + + +/** + * Handle for controller process + */ +struct GNUNET_TESTBED_ControllerProc +{ + /** + * The process handle + */ + struct GNUNET_HELPER_Handle *helper; + + /** + * The arguments used to start the helper + */ + char **helper_argv; + + /** + * The host where the helper is run + */ + struct GNUNET_TESTBED_Host *host; + + /** + * The controller error callback + */ + GNUNET_TESTBED_ControllerStatusCallback cb; + + /** + * The closure for the above callback + */ + void *cls; + + /** + * The send handle for the helper + */ + struct GNUNET_HELPER_SendHandle *shandle; + + /** + * The message corresponding to send handle + */ + struct GNUNET_MessageHeader *msg; + + /** + * The configuration of the running testbed service + */ + struct GNUNET_CONFIGURATION_Handle *cfg; + +}; + + +/** + * The message queue for sending messages to the controller service + */ +struct MessageQueue +{ + /** + * The message to be sent + */ + struct GNUNET_MessageHeader *msg; + + /** + * next pointer for DLL + */ + struct MessageQueue *next; + + /** + * prev pointer for DLL + */ + struct MessageQueue *prev; +}; + + +/** + * Structure for a controller link + */ +struct ControllerLink +{ + /** + * The next ptr for DLL + */ + struct ControllerLink *next; + + /** + * The prev ptr for DLL + */ + struct ControllerLink *prev; + + /** + * The host which will be referred in the peer start request. This is the + * host where the peer should be started + */ + struct GNUNET_TESTBED_Host *delegated_host; + + /** + * The host which will contacted to delegate the peer start request + */ + struct GNUNET_TESTBED_Host *slave_host; + + /** + * The configuration to be used to connect to slave host + */ + const struct GNUNET_CONFIGURATION_Handle *slave_cfg; + + /** + * GNUNET_YES if the slave should be started (and stopped) by us; GNUNET_NO + * if we are just allowed to use the slave via TCP/IP + */ + int is_subordinate; +}; + + +/** + * handle for host registration + */ +struct GNUNET_TESTBED_HostRegistrationHandle +{ + /** + * The host being registered + */ + struct GNUNET_TESTBED_Host *host; + + /** + * The controller at which this host is being registered + */ + struct GNUNET_TESTBED_Controller *c; + + /** + * The Registartion completion callback + */ + GNUNET_TESTBED_HostRegistrationCompletion cc; + + /** + * The closure for above callback + */ + void *cc_cls; +}; + + +/** + * Context data for forwarded Operation + */ +struct ForwardedOperationData +{ + + /** + * The callback to call when reply is available + */ + GNUNET_CLIENT_MessageHandler cc; + + /** + * The closure for the above callback + */ + void *cc_cls; + +}; + + +/** + * Context data for get slave config operations + */ +struct GetSlaveConfigData +{ + /** + * The id of the slave controller + */ + uint32_t slave_id; + +}; + + +/** + * Context data for controller link operations + */ +struct ControllerLinkData +{ + /** + * The controller link message + */ + struct GNUNET_TESTBED_ControllerLinkMessage *msg; + +}; + + +struct SDEntry +{ + /** + * DLL next pointer + */ + struct SDEntry *next; + + /** + * DLL prev pointer + */ + struct SDEntry *prev; + + /** + * The value to store + */ + unsigned int amount; +}; + + +struct SDHandle +{ + /** + * DLL head for storing entries + */ + struct SDEntry *head; + + /** + * DLL tail for storing entries + */ + struct SDEntry *tail; + + /** + * Squared sum of data values + */ + unsigned long long sqsum; + + /** + * Sum of the data values + */ + unsigned long sum; + + /** + * The average of data amounts + */ + float avg; + + /** + * The variance + */ + double vr; + + /** + * Number of data values; also the length of DLL containing SDEntries + */ + unsigned int cnt; + + /** + * max number of entries we can have in the DLL + */ + unsigned int max_cnt; +}; + + +/** + * This variable is set to the operation that has been last marked as done. It + * is used to verify whether the state associated with an operation is valid + * after the first notify callback is called. Such checks are necessary for + * certain operations where we have 2 notify callbacks. Examples are + * OP_PEER_CREATE, OP_PEER_START/STOP, OP_OVERLAY_CONNECT. + * + * This variable should ONLY be used to compare; it is a dangling pointer!! + */ +static const struct GNUNET_TESTBED_Operation *last_finished_operation; + +/** + * Initialize standard deviation calculation handle + * + * @param max_cnt the maximum number of readings to keep + * @return the initialized handle + */ +static struct SDHandle * +SD_init (unsigned int max_cnt) +{ + struct SDHandle *h; + + GNUNET_assert (1 < max_cnt); + h = GNUNET_malloc (sizeof (struct SDHandle)); + h->max_cnt = max_cnt; + return h; +} + + +/** + * Frees the memory allocated to the SD handle + * + * @param h the SD handle + */ +static void +SD_destroy (struct SDHandle *h) +{ + struct SDEntry *entry; + + while (NULL != (entry = h->head)) + { + GNUNET_CONTAINER_DLL_remove (h->head, h->tail, entry); + GNUNET_free (entry); + } + GNUNET_free (h); +} + + +/** + * Add a reading to SD + * + * @param h the SD handle + * @param amount the reading value + */ +static void +SD_add_data (struct SDHandle *h, unsigned int amount) +{ + struct SDEntry *entry; + double sqavg; + double sqsum_avg; + + entry = NULL; + if (h->cnt == h->max_cnt) + { + entry = h->head; + GNUNET_CONTAINER_DLL_remove (h->head, h->tail, entry); + h->sum -= entry->amount; + h->sqsum -= + ((unsigned long) entry->amount) * ((unsigned long) entry->amount); + h->cnt--; + } + GNUNET_assert (h->cnt < h->max_cnt); + if (NULL == entry) + entry = GNUNET_malloc (sizeof (struct SDEntry)); + entry->amount = amount; + GNUNET_CONTAINER_DLL_insert_tail (h->head, h->tail, entry); + h->sum += amount; + h->cnt++; + h->avg = ((float) h->sum) / ((float) h->cnt); + h->sqsum += ((unsigned long) amount) * ((unsigned long) amount); + sqsum_avg = ((double) h->sqsum) / ((double) h->cnt); + sqavg = ((double) h->avg) * ((double) h->avg); + h->vr = sqsum_avg - sqavg; +} + + +/** + * Returns the factor by which the given amount differs from the standard deviation + * + * @param h the SDhandle + * @param amount the value for which the deviation is returned + + * @return the deviation from the average; GNUNET_SYSERR if the deviation cannot + * be calculated OR 0 if the deviation is less than the average; a + * maximum of 4 is returned for deviations equal to or larger than 4 + */ +static int +SD_deviation_factor (struct SDHandle *h, unsigned int amount) +{ + double diff; + unsigned int n; + + if (h->cnt < 2) + return GNUNET_SYSERR; + if (((float) amount) > h->avg) + diff = ((float) amount) - h->avg; + else + return 0; //diff = h->avg - ((float) amount); + diff *= diff; + for (n = 1; n < 4; n++) + if (diff < (((double) (n * n)) * h->vr)) + break; + return n; +} + + +/** + * Returns the operation context with the given id if found in the Operation + * context queues of the controller + * + * @param c the controller whose queues are searched + * @param id the id which has to be checked + * @return the matching operation context; NULL if no match found + */ +static struct OperationContext * +find_opc (const struct GNUNET_TESTBED_Controller *c, const uint64_t id) +{ + struct OperationContext *opc; + + for (opc = c->ocq_head; NULL != opc; opc = opc->next) + { + if (id == opc->id) + return opc; + } + return NULL; +} + + +/** + * Handler for GNUNET_MESSAGE_TYPE_TESTBED_ADDHOSTCONFIRM message from + * controller (testbed service) + * + * @param c the controller handler + * @param msg message received + * @return GNUNET_YES if we can continue receiving from service; GNUNET_NO if + * not + */ +static int +handle_addhostconfirm (struct GNUNET_TESTBED_Controller *c, + const struct GNUNET_TESTBED_HostConfirmedMessage *msg) +{ + struct GNUNET_TESTBED_HostRegistrationHandle *rh; + char *emsg; + uint16_t msg_size; + + rh = c->rh; + if (NULL == rh) + { + return GNUNET_OK; + } + if (GNUNET_TESTBED_host_get_id_ (rh->host) != ntohl (msg->host_id)) + { + LOG_DEBUG ("Mismatch in host id's %u, %u of host confirm msg\n", + GNUNET_TESTBED_host_get_id_ (rh->host), ntohl (msg->host_id)); + return GNUNET_OK; + } + c->rh = NULL; + msg_size = ntohs (msg->header.size); + if (sizeof (struct GNUNET_TESTBED_HostConfirmedMessage) == msg_size) + { + LOG_DEBUG ("Host %u successfully registered\n", ntohl (msg->host_id)); + GNUNET_TESTBED_mark_host_registered_at_ (rh->host, c); + rh->cc (rh->cc_cls, NULL); + GNUNET_free (rh); + return GNUNET_OK; + } + /* We have an error message */ + emsg = (char *) &msg[1]; + if ('\0' != + emsg[msg_size - sizeof (struct GNUNET_TESTBED_HostConfirmedMessage)]) + { + GNUNET_break (0); + GNUNET_free (rh); + return GNUNET_NO; + } + LOG (GNUNET_ERROR_TYPE_ERROR, _("Adding host %u failed with error: %s\n"), + ntohl (msg->host_id), emsg); + rh->cc (rh->cc_cls, emsg); + GNUNET_free (rh); + return GNUNET_OK; +} + + +/** + * Handler for forwarded operations + * + * @param c the controller handle + * @param opc the opearation context + * @param msg the message + */ +static void +handle_forwarded_operation_msg (struct GNUNET_TESTBED_Controller *c, + struct OperationContext *opc, + const struct GNUNET_MessageHeader *msg) +{ + struct ForwardedOperationData *fo_data; + + fo_data = opc->data; + if (NULL != fo_data->cc) + fo_data->cc (fo_data->cc_cls, msg); + GNUNET_CONTAINER_DLL_remove (c->ocq_head, c->ocq_tail, opc); + GNUNET_free (fo_data); + GNUNET_free (opc); +} + + +/** + * Handler for GNUNET_MESSAGE_TYPE_TESTBED_ADDHOSTCONFIRM message from + * controller (testbed service) + * + * @param c the controller handler + * @param msg message received + * @return GNUNET_YES if we can continue receiving from service; GNUNET_NO if + * not + */ +static int +handle_opsuccess (struct GNUNET_TESTBED_Controller *c, + const struct + GNUNET_TESTBED_GenericOperationSuccessEventMessage *msg) +{ + struct OperationContext *opc; + struct GNUNET_TESTBED_EventInformation event; + uint64_t op_id; + + op_id = GNUNET_ntohll (msg->operation_id); + LOG_DEBUG ("Operation %lu successful\n", op_id); + if (NULL == (opc = find_opc (c, op_id))) + { + LOG_DEBUG ("Operation not found\n"); + return GNUNET_YES; + } + event.type = GNUNET_TESTBED_ET_OPERATION_FINISHED; + event.details.operation_finished.operation = opc->op; + event.details.operation_finished.op_cls = opc->op_cls; + event.details.operation_finished.emsg = NULL; + event.details.operation_finished.generic = NULL; + switch (opc->type) + { + case OP_FORWARDED: + { + handle_forwarded_operation_msg (c, opc, + (const struct GNUNET_MessageHeader *) msg); + return GNUNET_YES; + } + break; + case OP_PEER_DESTROY: + { + struct GNUNET_TESTBED_Peer *peer; + + peer = opc->data; + GNUNET_free (peer); + opc->data = NULL; + //PEERDESTROYDATA + } + break; + case OP_LINK_CONTROLLERS: + { + struct ControllerLinkData *data; + + data = opc->data; + GNUNET_assert (NULL != data); + GNUNET_free (data); + opc->data = NULL; + } + break; + default: + GNUNET_assert (0); + } + GNUNET_CONTAINER_DLL_remove (opc->c->ocq_head, opc->c->ocq_tail, opc); + opc->state = OPC_STATE_FINISHED; + if (0 != (c->event_mask & (1L << GNUNET_TESTBED_ET_OPERATION_FINISHED))) + { + if (NULL != c->cc) + c->cc (c->cc_cls, &event); + } + else + LOG_DEBUG ("Not calling callback\n"); + return GNUNET_YES; +} + + +/** + * Handler for GNUNET_MESSAGE_TYPE_TESTBED_PEERCREATESUCCESS message from + * controller (testbed service) + * + * @param c the controller handle + * @param msg message received + * @return GNUNET_YES if we can continue receiving from service; GNUNET_NO if + * not + */ +static int +handle_peer_create_success (struct GNUNET_TESTBED_Controller *c, + const struct + GNUNET_TESTBED_PeerCreateSuccessEventMessage *msg) +{ + struct OperationContext *opc; + struct PeerCreateData *data; + struct GNUNET_TESTBED_Peer *peer; + GNUNET_TESTBED_PeerCreateCallback cb; + void *cls; + uint64_t op_id; + + GNUNET_assert (sizeof (struct GNUNET_TESTBED_PeerCreateSuccessEventMessage) == + ntohs (msg->header.size)); + op_id = GNUNET_ntohll (msg->operation_id); + if (NULL == (opc = find_opc (c, op_id))) + { + LOG_DEBUG ("Operation context for PeerCreateSuccessEvent not found\n"); + return GNUNET_YES; + } + if (OP_FORWARDED == opc->type) + { + handle_forwarded_operation_msg (c, opc, + (const struct GNUNET_MessageHeader *) msg); + return GNUNET_YES; + } + GNUNET_assert (OP_PEER_CREATE == opc->type); + GNUNET_assert (NULL != opc->data); + data = opc->data; + GNUNET_assert (NULL != data->peer); + peer = data->peer; + GNUNET_assert (peer->unique_id == ntohl (msg->peer_id)); + peer->state = PS_CREATED; + cb = data->cb; + cls = data->cls; + GNUNET_free (opc->data); + GNUNET_CONTAINER_DLL_remove (opc->c->ocq_head, opc->c->ocq_tail, opc); + opc->state = OPC_STATE_FINISHED; + if (NULL != cb) + cb (cls, peer, NULL); + return GNUNET_YES; +} + + +/** + * Handler for GNUNET_MESSAGE_TYPE_TESTBED_PEEREVENT message from + * controller (testbed service) + * + * @param c the controller handler + * @param msg message received + * @return GNUNET_YES if we can continue receiving from service; GNUNET_NO if + * not + */ +static int +handle_peer_event (struct GNUNET_TESTBED_Controller *c, + const struct GNUNET_TESTBED_PeerEventMessage *msg) +{ + struct OperationContext *opc; + struct GNUNET_TESTBED_Peer *peer; + struct PeerEventData *data; + GNUNET_TESTBED_PeerChurnCallback pcc; + void *pcc_cls; + struct GNUNET_TESTBED_EventInformation event; + uint64_t op_id; + + GNUNET_assert (sizeof (struct GNUNET_TESTBED_PeerEventMessage) == + ntohs (msg->header.size)); + op_id = GNUNET_ntohll (msg->operation_id); + if (NULL == (opc = find_opc (c, op_id))) + { + LOG_DEBUG ("Operation not found\n"); + return GNUNET_YES; + } + if (OP_FORWARDED == opc->type) + { + handle_forwarded_operation_msg (c, opc, + (const struct GNUNET_MessageHeader *) msg); + return GNUNET_YES; + } + GNUNET_assert ((OP_PEER_START == opc->type) || (OP_PEER_STOP == opc->type)); + data = opc->data; + GNUNET_assert (NULL != data); + peer = data->peer; + GNUNET_assert (NULL != peer); + event.type = (enum GNUNET_TESTBED_EventType) ntohl (msg->event_type); + switch (event.type) + { + case GNUNET_TESTBED_ET_PEER_START: + peer->state = PS_STARTED; + event.details.peer_start.host = peer->host; + event.details.peer_start.peer = peer; + break; + case GNUNET_TESTBED_ET_PEER_STOP: + peer->state = PS_STOPPED; + event.details.peer_stop.peer = peer; + break; + default: + GNUNET_assert (0); /* We should never reach this state */ + } + pcc = data->pcc; + pcc_cls = data->pcc_cls; + GNUNET_free (data); + GNUNET_CONTAINER_DLL_remove (opc->c->ocq_head, opc->c->ocq_tail, opc); + opc->state = OPC_STATE_FINISHED; + if (0 != + ((GNUNET_TESTBED_ET_PEER_START | GNUNET_TESTBED_ET_PEER_STOP) & + c->event_mask)) + { + if (NULL != c->cc) + c->cc (c->cc_cls, &event); + } + if (NULL != pcc) + pcc (pcc_cls, NULL); + return GNUNET_YES; +} + + +/** + * Handler for GNUNET_MESSAGE_TYPE_TESTBED_PEERCONEVENT message from + * controller (testbed service) + * + * @param c the controller handler + * @param msg message received + * @return GNUNET_YES if we can continue receiving from service; GNUNET_NO if + * not + */ +static int +handle_peer_conevent (struct GNUNET_TESTBED_Controller *c, + const struct GNUNET_TESTBED_ConnectionEventMessage *msg) +{ + struct OperationContext *opc; + struct OverlayConnectData *data; + GNUNET_TESTBED_OperationCompletionCallback cb; + void *cb_cls; + struct GNUNET_TESTBED_EventInformation event; + uint64_t op_id; + + op_id = GNUNET_ntohll (msg->operation_id); + if (NULL == (opc = find_opc (c, op_id))) + { + LOG_DEBUG ("Operation not found\n"); + return GNUNET_YES; + } + if (OP_FORWARDED == opc->type) + { + handle_forwarded_operation_msg (c, opc, + (const struct GNUNET_MessageHeader *) msg); + return GNUNET_YES; + } + GNUNET_assert (OP_OVERLAY_CONNECT == opc->type); + data = opc->data; + GNUNET_assert (NULL != data); + GNUNET_assert ((ntohl (msg->peer1) == data->p1->unique_id) && + (ntohl (msg->peer2) == data->p2->unique_id)); + event.type = (enum GNUNET_TESTBED_EventType) ntohl (msg->event_type); + switch (event.type) + { + case GNUNET_TESTBED_ET_CONNECT: + event.details.peer_connect.peer1 = data->p1; + event.details.peer_connect.peer2 = data->p2; + break; + case GNUNET_TESTBED_ET_DISCONNECT: + GNUNET_assert (0); /* FIXME: implement */ + break; + default: + GNUNET_assert (0); /* Should never reach here */ + break; + } + cb = data->cb; + cb_cls = data->cb_cls; + GNUNET_CONTAINER_DLL_remove (opc->c->ocq_head, opc->c->ocq_tail, opc); + opc->state = OPC_STATE_FINISHED; + if (NULL != cb) + cb (cb_cls, opc->op, NULL); + if (0 != + ((GNUNET_TESTBED_ET_CONNECT | GNUNET_TESTBED_ET_DISCONNECT) & + c->event_mask)) + { + if (NULL != c->cc) + c->cc (c->cc_cls, &event); + } + return GNUNET_YES; +} + + +/** + * Handler for GNUNET_MESSAGE_TYPE_TESTBED_PEERCONFIG message from + * controller (testbed service) + * + * @param c the controller handler + * @param msg message received + * @return GNUNET_YES if we can continue receiving from service; GNUNET_NO if + * not + */ +static int +handle_peer_config (struct GNUNET_TESTBED_Controller *c, + const struct + GNUNET_TESTBED_PeerConfigurationInformationMessage *msg) +{ + struct OperationContext *opc; + struct GNUNET_TESTBED_Peer *peer; + struct PeerInfoData *data; + struct GNUNET_TESTBED_PeerInformation *pinfo; + GNUNET_TESTBED_PeerInfoCallback cb; + void *cb_cls; + uint64_t op_id; + + op_id = GNUNET_ntohll (msg->operation_id); + if (NULL == (opc = find_opc (c, op_id))) + { + LOG_DEBUG ("Operation not found\n"); + return GNUNET_YES; + } + if (OP_FORWARDED == opc->type) + { + handle_forwarded_operation_msg (c, opc, + (const struct GNUNET_MessageHeader *) msg); + return GNUNET_YES; + } + data = opc->data; + GNUNET_assert (NULL != data); + peer = data->peer; + GNUNET_assert (NULL != peer); + GNUNET_assert (ntohl (msg->peer_id) == peer->unique_id); + pinfo = GNUNET_malloc (sizeof (struct GNUNET_TESTBED_PeerInformation)); + pinfo->pit = data->pit; + cb = data->cb; + cb_cls = data->cb_cls; + GNUNET_free (data); + opc->data = NULL; + switch (pinfo->pit) + { + case GNUNET_TESTBED_PIT_IDENTITY: + pinfo->result.id = GNUNET_malloc (sizeof (struct GNUNET_PeerIdentity)); + (void) memcpy (pinfo->result.id, &msg->peer_identity, + sizeof (struct GNUNET_PeerIdentity)); + break; + case GNUNET_TESTBED_PIT_CONFIGURATION: + pinfo->result.cfg = /* Freed in oprelease_peer_getinfo */ + GNUNET_TESTBED_extract_config_ (&msg->header); + break; + case GNUNET_TESTBED_PIT_GENERIC: + GNUNET_assert (0); /* never reach here */ + break; + } + opc->data = pinfo; + GNUNET_CONTAINER_DLL_remove (opc->c->ocq_head, opc->c->ocq_tail, opc); + opc->state = OPC_STATE_FINISHED; + if (NULL != cb) + cb (cb_cls, opc->op, pinfo, NULL); + return GNUNET_YES; +} + + +/** + * Handler for GNUNET_MESSAGE_TYPE_TESTBED_OPERATIONFAILEVENT message from + * controller (testbed service) + * + * @param c the controller handler + * @param msg message received + * @return GNUNET_YES if we can continue receiving from service; GNUNET_NO if + * not + */ +static int +handle_op_fail_event (struct GNUNET_TESTBED_Controller *c, + const struct GNUNET_TESTBED_OperationFailureEventMessage + *msg) +{ + struct OperationContext *opc; + const char *emsg; + uint64_t op_id; + struct GNUNET_TESTBED_EventInformation event; + + op_id = GNUNET_ntohll (msg->operation_id); + if (NULL == (opc = find_opc (c, op_id))) + { + LOG_DEBUG ("Operation not found\n"); + return GNUNET_YES; + } + if (OP_FORWARDED == opc->type) + { + handle_forwarded_operation_msg (c, opc, + (const struct GNUNET_MessageHeader *) msg); + return GNUNET_YES; + } + GNUNET_CONTAINER_DLL_remove (opc->c->ocq_head, opc->c->ocq_tail, opc); + opc->state = OPC_STATE_FINISHED; + emsg = GNUNET_TESTBED_parse_error_string_ (msg); + if (NULL == emsg) + emsg = "Unknown error"; + if (OP_PEER_INFO == opc->type) + { + struct PeerInfoData *data; + + data = opc->data; + if (NULL != data->cb) + data->cb (data->cb_cls, opc->op, NULL, emsg); + GNUNET_free (data); + return GNUNET_YES; /* We do not call controller callback for peer info */ + } + if ((0 != (GNUNET_TESTBED_ET_OPERATION_FINISHED & c->event_mask)) && + (NULL != c->cc)) + { + event.type = GNUNET_TESTBED_ET_OPERATION_FINISHED; + event.details.operation_finished.operation = opc->op; + event.details.operation_finished.op_cls = opc->op_cls; + event.details.operation_finished.emsg = emsg; + event.details.operation_finished.generic = NULL; + c->cc (c->cc_cls, &event); + if (event.details.operation_finished.operation == last_finished_operation) + return GNUNET_YES; + } + switch (opc->type) + { + case OP_PEER_CREATE: + { + struct PeerCreateData *data; + + data = opc->data; + GNUNET_free (data->peer); + if (NULL != data->cb) + data->cb (data->cls, NULL, emsg); + GNUNET_free (data); + } + break; + case OP_PEER_START: + case OP_PEER_STOP: + { + struct PeerEventData *data; + + data = opc->data; + if (NULL != data->pcc) + data->pcc (data->pcc_cls, emsg); + GNUNET_free (data); + } + break; + case OP_PEER_DESTROY: + break; + case OP_PEER_INFO: + GNUNET_assert (0); + case OP_OVERLAY_CONNECT: + { + struct OverlayConnectData *data; + + data = opc->data; + data->failed = GNUNET_YES; + if (NULL != data->cb) + data->cb (data->cb_cls, opc->op, emsg); + } + break; + case OP_FORWARDED: + GNUNET_assert (0); + case OP_LINK_CONTROLLERS: /* No secondary callback */ + break; + default: + GNUNET_break (0); + } + return GNUNET_YES; +} + + +/** + * Function to build GET_SLAVE_CONFIG message + * + * @param op_id the id this message should contain in its operation id field + * @param slave_id the id this message should contain in its slave id field + * @return newly allocated SlaveGetConfigurationMessage + */ +static struct GNUNET_TESTBED_SlaveGetConfigurationMessage * +GNUNET_TESTBED_generate_slavegetconfig_msg_ (uint64_t op_id, uint32_t slave_id) +{ + struct GNUNET_TESTBED_SlaveGetConfigurationMessage *msg; + uint16_t msize; + + msize = sizeof (struct GNUNET_TESTBED_SlaveGetConfigurationMessage); + msg = GNUNET_malloc (msize); + msg->header.size = htons (msize); + msg->header.type = + htons (GNUNET_MESSAGE_TYPE_TESTBED_GET_SLAVE_CONFIGURATION); + msg->operation_id = GNUNET_htonll (op_id); + msg->slave_id = htonl (slave_id); + return msg; +} + + +/** + * Handler for GNUNET_MESSAGE_TYPE_TESTBED_SLAVECONFIG message from controller + * (testbed service) + * + * @param c the controller handler + * @param msg message received + * @return GNUNET_YES if we can continue receiving from service; GNUNET_NO if + * not + */ +static int +handle_slave_config (struct GNUNET_TESTBED_Controller *c, + const struct GNUNET_TESTBED_SlaveConfiguration *msg) +{ + struct OperationContext *opc; + uint64_t op_id; + struct GNUNET_TESTBED_EventInformation event; + + op_id = GNUNET_ntohll (msg->operation_id); + if (NULL == (opc = find_opc (c, op_id))) + { + LOG_DEBUG ("Operation not found\n"); + return GNUNET_YES; + } + if (OP_GET_SLAVE_CONFIG != opc->type) + { + GNUNET_break (0); + return GNUNET_YES; + } + GNUNET_free (opc->data); + opc->data = NULL; + opc->state = OPC_STATE_FINISHED; + GNUNET_CONTAINER_DLL_remove (opc->c->ocq_head, opc->c->ocq_tail, opc); + if ((0 != (GNUNET_TESTBED_ET_OPERATION_FINISHED & c->event_mask)) && + (NULL != c->cc)) + { + opc->data = GNUNET_TESTBED_extract_config_ (&msg->header); + event.type = GNUNET_TESTBED_ET_OPERATION_FINISHED; + event.details.operation_finished.generic = opc->data; + event.details.operation_finished.operation = opc->op; + event.details.operation_finished.op_cls = opc->op_cls; + event.details.operation_finished.emsg = NULL; + c->cc (c->cc_cls, &event); + } + return GNUNET_YES; +} + + +/** + * Handler for messages from controller (testbed service) + * + * @param cls the controller handler + * @param msg message received, NULL on timeout or fatal error + */ +static void +message_handler (void *cls, const struct GNUNET_MessageHeader *msg) +{ + struct GNUNET_TESTBED_Controller *c = cls; + int status; + uint16_t msize; + + c->in_receive = GNUNET_NO; + /* FIXME: Add checks for message integrity */ + if (NULL == msg) + { + LOG_DEBUG ("Receive timed out or connection to service dropped\n"); + return; + } + status = GNUNET_OK; + msize = ntohs (msg->size); + switch (ntohs (msg->type)) + { + case GNUNET_MESSAGE_TYPE_TESTBED_ADD_HOST_SUCCESS: + GNUNET_assert (msize >= + sizeof (struct GNUNET_TESTBED_HostConfirmedMessage)); + status = + handle_addhostconfirm (c, + (const struct GNUNET_TESTBED_HostConfirmedMessage + *) msg); + break; + case GNUNET_MESSAGE_TYPE_TESTBED_GENERIC_OPERATION_SUCCESS: + GNUNET_assert (msize == + sizeof (struct + GNUNET_TESTBED_GenericOperationSuccessEventMessage)); + status = + handle_opsuccess (c, + (const struct + GNUNET_TESTBED_GenericOperationSuccessEventMessage *) + msg); + break; + case GNUNET_MESSAGE_TYPE_TESTBED_CREATE_PEER_SUCCESS: + GNUNET_assert (msize == + sizeof (struct + GNUNET_TESTBED_PeerCreateSuccessEventMessage)); + status = + handle_peer_create_success (c, + (const struct + GNUNET_TESTBED_PeerCreateSuccessEventMessage + *) msg); + break; + case GNUNET_MESSAGE_TYPE_TESTBED_PEER_EVENT: + GNUNET_assert (msize == sizeof (struct GNUNET_TESTBED_PeerEventMessage)); + status = + handle_peer_event (c, + (const struct GNUNET_TESTBED_PeerEventMessage *) + msg); + + break; + case GNUNET_MESSAGE_TYPE_TESTBED_PEER_CONFIGURATION: + GNUNET_assert (msize >= + sizeof (struct + GNUNET_TESTBED_PeerConfigurationInformationMessage)); + status = + handle_peer_config (c, + (const struct + GNUNET_TESTBED_PeerConfigurationInformationMessage + *) msg); + break; + case GNUNET_MESSAGE_TYPE_TESTBED_PEER_CONNECT_EVENT: + GNUNET_assert (msize == + sizeof (struct GNUNET_TESTBED_ConnectionEventMessage)); + status = + handle_peer_conevent (c, + (const struct + GNUNET_TESTBED_ConnectionEventMessage *) msg); + break; + case GNUNET_MESSAGE_TYPE_TESTBED_OPERATION_FAIL_EVENT: + GNUNET_assert (msize >= + sizeof (struct GNUNET_TESTBED_OperationFailureEventMessage)); + status = + handle_op_fail_event (c, + (const struct + GNUNET_TESTBED_OperationFailureEventMessage *) + msg); + break; + case GNUNET_MESSAGE_TYPE_TESTBED_SLAVE_CONFIGURATION: + GNUNET_assert (msize > sizeof (struct GNUNET_TESTBED_SlaveConfiguration)); + status = + handle_slave_config (c, + (const struct GNUNET_TESTBED_SlaveConfiguration *) + msg); + break; + default: + GNUNET_assert (0); + } + if ((GNUNET_OK == status) && (GNUNET_NO == c->in_receive)) + { + c->in_receive = GNUNET_YES; + GNUNET_CLIENT_receive (c->client, &message_handler, c, + GNUNET_TIME_UNIT_FOREVER_REL); + } +} + + +/** + * Function called to notify a client about the connection begin ready to queue + * more data. "buf" will be NULL and "size" zero if the connection was closed + * for writing in the meantime. + * + * @param cls closure + * @param size number of bytes available in buf + * @param buf where the callee should write the message + * @return number of bytes written to buf + */ +static size_t +transmit_ready_notify (void *cls, size_t size, void *buf) +{ + struct GNUNET_TESTBED_Controller *c = cls; + struct MessageQueue *mq_entry; + + c->th = NULL; + mq_entry = c->mq_head; + GNUNET_assert (NULL != mq_entry); + if ((0 == size) && (NULL == buf)) /* Timeout */ + { + LOG_DEBUG ("Message sending timed out -- retrying\n"); + c->th = + GNUNET_CLIENT_notify_transmit_ready (c->client, + ntohs (mq_entry->msg->size), + TIMEOUT_REL, GNUNET_YES, + &transmit_ready_notify, c); + return 0; + } + GNUNET_assert (ntohs (mq_entry->msg->size) <= size); + size = ntohs (mq_entry->msg->size); + memcpy (buf, mq_entry->msg, size); + LOG_DEBUG ("Message of type: %u and size: %u sent\n", + ntohs (mq_entry->msg->type), size); + GNUNET_free (mq_entry->msg); + GNUNET_CONTAINER_DLL_remove (c->mq_head, c->mq_tail, mq_entry); + GNUNET_free (mq_entry); + mq_entry = c->mq_head; + if (NULL != mq_entry) + c->th = + GNUNET_CLIENT_notify_transmit_ready (c->client, + ntohs (mq_entry->msg->size), + TIMEOUT_REL, GNUNET_YES, + &transmit_ready_notify, c); + if (GNUNET_NO == c->in_receive) + { + c->in_receive = GNUNET_YES; + GNUNET_CLIENT_receive (c->client, &message_handler, c, + GNUNET_TIME_UNIT_FOREVER_REL); + } + return size; +} + + +/** + * Queues a message in send queue for sending to the service + * + * @param controller the handle to the controller + * @param msg the message to queue + */ +void +GNUNET_TESTBED_queue_message_ (struct GNUNET_TESTBED_Controller *controller, + struct GNUNET_MessageHeader *msg) +{ + struct MessageQueue *mq_entry; + uint16_t type; + uint16_t size; + + type = ntohs (msg->type); + size = ntohs (msg->size); + GNUNET_assert ((GNUNET_MESSAGE_TYPE_TESTBED_INIT <= type) && + (GNUNET_MESSAGE_TYPE_TESTBED_MAX > type)); + mq_entry = GNUNET_malloc (sizeof (struct MessageQueue)); + mq_entry->msg = msg; + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Queueing message of type %u, size %u for sending\n", type, + ntohs (msg->size)); + GNUNET_CONTAINER_DLL_insert_tail (controller->mq_head, controller->mq_tail, + mq_entry); + if (NULL == controller->th) + controller->th = + GNUNET_CLIENT_notify_transmit_ready (controller->client, size, + TIMEOUT_REL, GNUNET_YES, + &transmit_ready_notify, + controller); +} + + +/** + * Sends the given message as an operation. The given callback is called when a + * reply for the operation is available. Call + * GNUNET_TESTBED_forward_operation_msg_cancel_() to cleanup the returned + * operation context if the cc hasn't been called + * + * @param controller the controller to which the message has to be sent + * @param operation_id the operation id of the message + * @param msg the message to send + * @param cc the callback to call when reply is available + * @param cc_cls the closure for the above callback + * @return the operation context which can be used to cancel the forwarded + * operation + */ +struct OperationContext * +GNUNET_TESTBED_forward_operation_msg_ (struct GNUNET_TESTBED_Controller + *controller, uint64_t operation_id, + const struct GNUNET_MessageHeader *msg, + GNUNET_CLIENT_MessageHandler cc, + void *cc_cls) +{ + struct OperationContext *opc; + struct ForwardedOperationData *data; + struct GNUNET_MessageHeader *dup_msg; + uint16_t msize; + + data = GNUNET_malloc (sizeof (struct ForwardedOperationData)); + data->cc = cc; + data->cc_cls = cc_cls; + opc = GNUNET_malloc (sizeof (struct OperationContext)); + opc->c = controller; + opc->type = OP_FORWARDED; + opc->data = data; + opc->id = operation_id; + msize = ntohs (msg->size); + dup_msg = GNUNET_malloc (msize); + (void) memcpy (dup_msg, msg, msize); + GNUNET_TESTBED_queue_message_ (opc->c, dup_msg); + GNUNET_CONTAINER_DLL_insert_tail (controller->ocq_head, controller->ocq_tail, + opc); + return opc; +} + + +/** + * Function to cancel an operation created by simply forwarding an operation + * message. + * + * @param opc the operation context from GNUNET_TESTBED_forward_operation_msg_() + */ +void +GNUNET_TESTBED_forward_operation_msg_cancel_ (struct OperationContext *opc) +{ + GNUNET_CONTAINER_DLL_remove (opc->c->ocq_head, opc->c->ocq_tail, opc); + GNUNET_free (opc->data); + GNUNET_free (opc); +} + + +/** + * Functions with this signature are called whenever a + * complete message is received by the tokenizer. + * + * Do not call GNUNET_SERVER_mst_destroy in callback + * + * @param cls closure + * @param client identification of the client + * @param message the actual message + * + * @return GNUNET_OK on success, GNUNET_SYSERR to stop further processing + */ +static int +helper_mst (void *cls, void *client, const struct GNUNET_MessageHeader *message) +{ + struct GNUNET_TESTBED_ControllerProc *cp = cls; + const struct GNUNET_TESTBED_HelperReply *msg; + const char *hostname; + char *config; + uLongf config_size; + uLongf xconfig_size; + + msg = (const struct GNUNET_TESTBED_HelperReply *) message; + GNUNET_assert (sizeof (struct GNUNET_TESTBED_HelperReply) < + ntohs (msg->header.size)); + GNUNET_assert (GNUNET_MESSAGE_TYPE_TESTBED_HELPER_REPLY == + ntohs (msg->header.type)); + config_size = (uLongf) ntohs (msg->config_size); + xconfig_size = + (uLongf) (ntohs (msg->header.size) - + sizeof (struct GNUNET_TESTBED_HelperReply)); + config = GNUNET_malloc (config_size); + GNUNET_assert (Z_OK == + uncompress ((Bytef *) config, &config_size, + (const Bytef *) &msg[1], xconfig_size)); + GNUNET_assert (NULL == cp->cfg); + cp->cfg = GNUNET_CONFIGURATION_create (); + GNUNET_assert (GNUNET_CONFIGURATION_deserialize + (cp->cfg, config, config_size, GNUNET_NO)); + GNUNET_free (config); + if ((NULL == cp->host) || + (NULL == (hostname = GNUNET_TESTBED_host_get_hostname (cp->host)))) + hostname = "localhost"; + /* Change the hostname so that we can connect to it */ + GNUNET_CONFIGURATION_set_value_string (cp->cfg, "testbed", "hostname", + hostname); + cp->cb (cp->cls, cp->cfg, GNUNET_OK); + return GNUNET_OK; +} + + +/** + * Continuation function from GNUNET_HELPER_send() + * + * @param cls closure + * @param result GNUNET_OK on success, + * GNUNET_NO if helper process died + * GNUNET_SYSERR during GNUNET_HELPER_stop + */ +static void +clear_msg (void *cls, int result) +{ + struct GNUNET_TESTBED_ControllerProc *cp = cls; + + GNUNET_assert (NULL != cp->shandle); + cp->shandle = NULL; + GNUNET_free (cp->msg); +} + + +/** + * Callback that will be called when the helper process dies. This is not called + * when the helper process is stoped using GNUNET_HELPER_stop() + * + * @param cls the closure from GNUNET_HELPER_start() + */ +static void +helper_exp_cb (void *cls) +{ + struct GNUNET_TESTBED_ControllerProc *cp = cls; + GNUNET_TESTBED_ControllerStatusCallback cb; + void *cb_cls; + + cb = cp->cb; + cb_cls = cp->cls; + cp->helper = NULL; + GNUNET_TESTBED_controller_stop (cp); + if (NULL != cb) + cb (cb_cls, NULL, GNUNET_SYSERR); +} + + +/** + * Function to call to start a link-controllers type operation once all queues + * the operation is part of declare that the operation can be activated. + * + * @param cls the closure from GNUNET_TESTBED_operation_create_() + */ +static void +opstart_link_controllers (void *cls) +{ + struct OperationContext *opc = cls; + struct ControllerLinkData *data; + struct GNUNET_TESTBED_ControllerLinkMessage *msg; + + GNUNET_assert (NULL != opc->data); + data = opc->data; + msg = data->msg; + data->msg = NULL; + opc->state = OPC_STATE_STARTED; + GNUNET_CONTAINER_DLL_insert_tail (opc->c->ocq_head, opc->c->ocq_tail, opc); + GNUNET_TESTBED_queue_message_ (opc->c, &msg->header); +} + + +/** + * Callback which will be called when link-controllers type operation is released + * + * @param cls the closure from GNUNET_TESTBED_operation_create_() + */ +static void +oprelease_link_controllers (void *cls) +{ + struct OperationContext *opc = cls; + struct ControllerLinkData *data; + + data = opc->data; + switch (opc->state) + { + case OPC_STATE_INIT: + GNUNET_free (data->msg); + break; + case OPC_STATE_STARTED: + GNUNET_CONTAINER_DLL_remove (opc->c->ocq_head, opc->c->ocq_tail, opc); + break; + case OPC_STATE_FINISHED: + break; + } + GNUNET_free_non_null (data); + GNUNET_free (opc); +} + + +/** + * Function to be called when get slave config operation is ready + * + * @param cls the OperationContext of type OP_GET_SLAVE_CONFIG + */ +static void +opstart_get_slave_config (void *cls) +{ + struct OperationContext *opc = cls; + struct GetSlaveConfigData *data; + struct GNUNET_TESTBED_SlaveGetConfigurationMessage *msg; + + data = opc->data; + msg = GNUNET_TESTBED_generate_slavegetconfig_msg_ (opc->id, data->slave_id); + GNUNET_CONTAINER_DLL_insert_tail (opc->c->ocq_head, opc->c->ocq_tail, opc); + GNUNET_TESTBED_queue_message_ (opc->c, &msg->header); + opc->state = OPC_STATE_STARTED; +} + + +/** + * Function to be called when get slave config operation is cancelled or finished + * + * @param cls the OperationContext of type OP_GET_SLAVE_CONFIG + */ +static void +oprelease_get_slave_config (void *cls) +{ + struct OperationContext *opc = cls; + + switch (opc->state) + { + case OPC_STATE_INIT: + GNUNET_free (opc->data); + break; + case OPC_STATE_STARTED: + GNUNET_free (opc->data); + GNUNET_CONTAINER_DLL_remove (opc->c->ocq_head, opc->c->ocq_tail, opc); + break; + case OPC_STATE_FINISHED: + if (NULL != opc->data) + GNUNET_CONFIGURATION_destroy (opc->data); + break; + } + GNUNET_free (opc); +} + + +/** + * Initializes the operation queue for parallel overlay connects + * + * @param c the controller handle + * @param npoc the number of parallel overlay connects - the queue size + */ +static void +GNUNET_TESTBED_set_num_parallel_overlay_connects_ (struct + GNUNET_TESTBED_Controller *c, + unsigned int npoc) +{ + fprintf (stderr, "%d", npoc); + GNUNET_free_non_null (c->tslots); + c->tslots_filled = 0; + c->num_parallel_connects = npoc; + c->tslots = GNUNET_malloc (npoc * sizeof (struct TimeSlot)); + GNUNET_TESTBED_operation_queue_reset_max_active_ + (c->opq_parallel_overlay_connect_operations, npoc); +} + + +/** + * Function to copy NULL terminated list of arguments + * + * @param argv the NULL terminated list of arguments. Cannot be NULL. + * @return the copied NULL terminated arguments + */ +static char ** +copy_argv (const char *const *argv) +{ + char **argv_dup; + unsigned int argp; + + GNUNET_assert (NULL != argv); + for (argp = 0; NULL != argv[argp]; argp++) ; + argv_dup = GNUNET_malloc (sizeof (char *) * (argp + 1)); + for (argp = 0; NULL != argv[argp]; argp++) + argv_dup[argp] = strdup (argv[argp]); + return argv_dup; +} + + +/** + * Function to join NULL terminated list of arguments + * + * @param argv1 the NULL terminated list of arguments. Cannot be NULL. + * @param argv2 the NULL terminated list of arguments. Cannot be NULL. + * @return the joined NULL terminated arguments + */ +static char ** +join_argv (const char *const *argv1, const char *const *argv2) +{ + char **argvj; + char *argv; + unsigned int carg; + unsigned int cnt; + + carg = 0; + argvj = NULL; + for (cnt = 0; NULL != argv1[cnt]; cnt++) + { + argv = GNUNET_strdup (argv1[cnt]); + GNUNET_array_append (argvj, carg, argv); + } + for (cnt = 0; NULL != argv2[cnt]; cnt++) + { + argv = GNUNET_strdup (argv2[cnt]); + GNUNET_array_append (argvj, carg, argv); + } + GNUNET_array_append (argvj, carg, NULL); + return argvj; +} + + +/** + * Frees the given NULL terminated arguments + * + * @param argv the NULL terminated list of arguments + */ +static void +free_argv (char **argv) +{ + unsigned int argp; + + for (argp = 0; NULL != argv[argp]; argp++) + GNUNET_free (argv[argp]); + GNUNET_free (argv); +} + + +/** + * Generates arguments for opening a remote shell. Builds up the arguments + * from the environment variable GNUNET_TESTBED_RSH_CMD. The variable + * should not mention `-p' (port) option and destination address as these will + * be set locally in the function from its parameteres. If the environmental + * variable is not found then it defaults to `ssh -o BatchMode=yes -o + * NoHostAuthenticationForLocalhost=yes' + * + * @param port the destination port number + * @param dst the destination address + * @return NULL terminated list of arguments + */ +static char ** +gen_rsh_args (const char *port, const char *dst) +{ + static const char *default_ssh_args[] = { + "ssh", + "-o", + "BatchMode=yes", + "-o", + "NoHostAuthenticationForLocalhost=yes", + NULL + }; + char **ssh_args; + char *ssh_cmd; + char *ssh_cmd_cp; + char *arg; + unsigned int cnt; + + ssh_args = NULL; + if (NULL != (ssh_cmd = getenv ("GNUNET_TESTBED_RSH_CMD"))) + { + ssh_cmd = GNUNET_strdup (ssh_cmd); + ssh_cmd_cp = ssh_cmd; + for (cnt = 0; NULL != (arg = strtok (ssh_cmd, " ")); ssh_cmd = NULL) + GNUNET_array_append (ssh_args, cnt, GNUNET_strdup (arg)); + GNUNET_free (ssh_cmd_cp); + } + else + { + ssh_args = copy_argv (default_ssh_args); + cnt = (sizeof (default_ssh_args)) / (sizeof (const char *)); + GNUNET_array_grow (ssh_args, cnt, cnt - 1); + } + GNUNET_array_append (ssh_args, cnt, GNUNET_strdup ("-p")); + GNUNET_array_append (ssh_args, cnt, GNUNET_strdup (port)); + GNUNET_array_append (ssh_args, cnt, GNUNET_strdup (dst)); + GNUNET_array_append (ssh_args, cnt, NULL); + return ssh_args; +} + + +/** + * Generates the arguments needed for executing the given binary in a remote + * shell. Builds the arguments from the environmental variable + * GNUNET_TETSBED_RSH_CMD_SUFFIX. If the environmental variable is not found, + * only the given binary name will be present in the returned arguments + * + * @param helper_binary_path the path of the binary to execute + * @return NULL-terminated args + */ +static char ** +gen_rsh_suffix_args (const char *helper_binary_path) +{ + char **rshell_args; + char *rshell_cmd; + char *rshell_cmd_cp; + char *arg; + unsigned int cnt; + + rshell_args = NULL; + cnt = 0; + if (NULL != (rshell_cmd = getenv ("GNUNET_TESTBED_RSH_CMD_SUFFIX"))) + { + rshell_cmd = GNUNET_strdup (rshell_cmd); + rshell_cmd_cp = rshell_cmd; + for (; NULL != (arg = strtok (rshell_cmd, " ")); rshell_cmd = NULL) + GNUNET_array_append (rshell_args, cnt, GNUNET_strdup (arg)); + GNUNET_free (rshell_cmd_cp); + } + GNUNET_array_append (rshell_args, cnt, GNUNET_strdup (helper_binary_path)); + GNUNET_array_append (rshell_args, cnt, NULL); + return rshell_args; +} + + +/** + * Starts a controller process at the given host + * + * @param trusted_ip the ip address of the controller which will be set as TRUSTED + * HOST(all connections form this ip are permitted by the testbed) when + * starting testbed controller at host. This can either be a single ip + * address or a network address in CIDR notation. + * @param host the host where the controller has to be started; NULL for + * localhost + * @param cfg template configuration to use for the remote controller; the + * remote controller will be started with a slightly modified + * configuration (port numbers, unix domain sockets and service home + * values are changed as per TESTING library on the remote host) + * @param cb function called when the controller is successfully started or + * dies unexpectedly; GNUNET_TESTBED_controller_stop shouldn't be + * called if cb is called with GNUNET_SYSERR as status. Will never be + * called in the same task as 'GNUNET_TESTBED_controller_start' + * (synchronous errors will be signalled by returning NULL). This + * parameter cannot be NULL. + * @param cls closure for above callbacks + * @return the controller process handle, NULL on errors + */ +struct GNUNET_TESTBED_ControllerProc * +GNUNET_TESTBED_controller_start (const char *trusted_ip, + struct GNUNET_TESTBED_Host *host, + const struct GNUNET_CONFIGURATION_Handle *cfg, + GNUNET_TESTBED_ControllerStatusCallback cb, + void *cls) +{ + struct GNUNET_TESTBED_ControllerProc *cp; + struct GNUNET_TESTBED_HelperInit *msg; + const char *hostname; + + static char *const binary_argv[] = { + HELPER_TESTBED_BINARY, NULL + }; + + hostname = NULL; + cp = GNUNET_malloc (sizeof (struct GNUNET_TESTBED_ControllerProc)); + if ((NULL == host) || (0 == GNUNET_TESTBED_host_get_id_ (host))) + { + cp->helper = + GNUNET_HELPER_start (GNUNET_YES, HELPER_TESTBED_BINARY, binary_argv, + &helper_mst, &helper_exp_cb, cp); + } + else + { + char *helper_binary_path; + char **ssh_args; + char **rshell_args; + const char *username; + char *port; + char *dst; + username = GNUNET_TESTBED_host_get_username_ (host); + hostname = GNUNET_TESTBED_host_get_hostname (host); + GNUNET_asprintf (&port, "%u", GNUNET_TESTBED_host_get_ssh_port_ (host)); + if (NULL == username) + GNUNET_asprintf (&dst, "%s", hostname); + else + GNUNET_asprintf (&dst, "%s@%s", username, hostname); + LOG_DEBUG ("Starting SSH to destination %s\n", dst); + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_string (cfg, "testbed", + "HELPER_BINARY_PATH", + &helper_binary_path)) + helper_binary_path = + GNUNET_OS_get_libexec_binary_path (HELPER_TESTBED_BINARY); + ssh_args = gen_rsh_args (port, dst); + rshell_args = gen_rsh_suffix_args (helper_binary_path); + cp->helper_argv = + join_argv ((const char **) ssh_args, (const char **) rshell_args); + free_argv (ssh_args); + free_argv (rshell_args); + GNUNET_free (port); + GNUNET_free (dst); + cp->helper = + GNUNET_HELPER_start (GNUNET_NO, "ssh", cp->helper_argv, &helper_mst, + &helper_exp_cb, cp); + GNUNET_free (helper_binary_path); + } + if (NULL == cp->helper) + { + if (NULL != cp->helper_argv) + free_argv (cp->helper_argv); + GNUNET_free (cp); + return NULL; + } + cp->host = host; + cp->cb = cb; + cp->cls = cls; + msg = GNUNET_TESTBED_create_helper_init_msg_ (trusted_ip, hostname, cfg); + cp->msg = &msg->header; + cp->shandle = + GNUNET_HELPER_send (cp->helper, &msg->header, GNUNET_NO, &clear_msg, cp); + if (NULL == cp->shandle) + { + GNUNET_free (msg); + GNUNET_TESTBED_controller_stop (cp); + return NULL; + } + return cp; +} + + +/** + * Stop the controller process (also will terminate all peers and controllers + * dependent on this controller). This function blocks until the testbed has + * been fully terminated (!). The controller status cb from + * GNUNET_TESTBED_controller_start() will not be called. + * + * @param cproc the controller process handle + */ +void +GNUNET_TESTBED_controller_stop (struct GNUNET_TESTBED_ControllerProc *cproc) +{ + if (NULL != cproc->shandle) + GNUNET_HELPER_send_cancel (cproc->shandle); + if (NULL != cproc->helper) + GNUNET_HELPER_stop (cproc->helper); + if (NULL != cproc->cfg) + GNUNET_CONFIGURATION_destroy (cproc->cfg); + if (NULL != cproc->helper_argv) + free_argv (cproc->helper_argv); + GNUNET_free (cproc); +} /** @@ -40,7 +1797,9 @@ * given host. * * @param cfg configuration to use - * @param host host to run the controller on, NULL for 'localhost' + * @param host host to run the controller on; This should be the same host if + * the controller was previously started with + * GNUNET_TESTBED_controller_start; NULL for localhost * @param event_mask bit mask with set of events to call 'cc' for; * or-ed values of "1LL" shifted by the * respective 'enum GNUNET_TESTBED_EventType' @@ -50,14 +1809,101 @@ * @return handle to the controller */ struct GNUNET_TESTBED_Controller * -GNUNET_TESTBED_controller_start (const struct GNUNET_CONFIGURATION_Handle *cfg, - struct GNUNET_TESTBED_Host *host, - uint64_t event_mask, - GNUNET_TESTBED_ControllerCallback cc, - void *cc_cls) +GNUNET_TESTBED_controller_connect (const struct GNUNET_CONFIGURATION_Handle + *cfg, struct GNUNET_TESTBED_Host *host, + uint64_t event_mask, + GNUNET_TESTBED_ControllerCallback cc, + void *cc_cls) { - GNUNET_break (0); - return NULL; + struct GNUNET_TESTBED_Controller *controller; + struct GNUNET_TESTBED_InitMessage *msg; + const char *controller_hostname; + unsigned long long max_parallel_operations; + unsigned long long max_parallel_service_connections; + unsigned long long max_parallel_topology_config_operations; + + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_number (cfg, "testbed", + "MAX_PARALLEL_OPERATIONS", + &max_parallel_operations)) + { + GNUNET_break (0); + return NULL; + } + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_number (cfg, "testbed", + "MAX_PARALLEL_SERVICE_CONNECTIONS", + &max_parallel_service_connections)) + { + GNUNET_break (0); + return NULL; + } + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_number (cfg, "testbed", + "MAX_PARALLEL_TOPOLOGY_CONFIG_OPERATIONS", + &max_parallel_topology_config_operations)) + { + GNUNET_break (0); + return NULL; + } + controller = GNUNET_malloc (sizeof (struct GNUNET_TESTBED_Controller)); + controller->cc = cc; + controller->cc_cls = cc_cls; + controller->event_mask = event_mask; + controller->cfg = GNUNET_CONFIGURATION_dup (cfg); + controller->client = GNUNET_CLIENT_connect ("testbed", controller->cfg); + if (NULL == controller->client) + { + GNUNET_TESTBED_controller_disconnect (controller); + return NULL; + } + if (NULL == host) + { + host = GNUNET_TESTBED_host_create_by_id_ (0); + if (NULL == host) /* If the above host create fails */ + { + LOG (GNUNET_ERROR_TYPE_WARNING, + "Treating NULL host as localhost. Multiple references to localhost " + "may break when localhost freed before calling disconnect \n"); + host = GNUNET_TESTBED_host_lookup_by_id_ (0); + } + else + { + controller->aux_host = GNUNET_YES; + } + } + GNUNET_assert (NULL != host); + GNUNET_TESTBED_mark_host_registered_at_ (host, controller); + controller->host = host; + controller->opq_parallel_operations = + GNUNET_TESTBED_operation_queue_create_ ((unsigned int) + max_parallel_operations); + controller->opq_parallel_service_connections = + GNUNET_TESTBED_operation_queue_create_ ((unsigned int) + max_parallel_service_connections); + controller->opq_parallel_topology_config_operations = + GNUNET_TESTBED_operation_queue_create_ ((unsigned int) + max_parallel_topology_config_operations); + controller->opq_parallel_overlay_connect_operations = + GNUNET_TESTBED_operation_queue_create_ (0); + GNUNET_TESTBED_set_num_parallel_overlay_connects_ (controller, 1); + controller->poc_sd = SD_init (10); + controller_hostname = GNUNET_TESTBED_host_get_hostname (host); + if (NULL == controller_hostname) + controller_hostname = "127.0.0.1"; + msg = + GNUNET_malloc (sizeof (struct GNUNET_TESTBED_InitMessage) + + strlen (controller_hostname) + 1); + msg->header.type = htons (GNUNET_MESSAGE_TYPE_TESTBED_INIT); + msg->header.size = + htons (sizeof (struct GNUNET_TESTBED_InitMessage) + + strlen (controller_hostname) + 1); + msg->host_id = htonl (GNUNET_TESTBED_host_get_id_ (host)); + msg->event_mask = GNUNET_htonll (controller->event_mask); + strcpy ((char *) &msg[1], controller_hostname); + GNUNET_TESTBED_queue_message_ (controller, + (struct GNUNET_MessageHeader *) msg); + return controller; } @@ -67,7 +1913,7 @@ GNUNET_TESTBED_controller_start (const struct GNUNET_CONFIGURATION_Handle *cfg, * should not be run for each peer but instead be shared * across N peers on the specified host. This function * must be called before any peers are created at the host. - * + * * @param controller controller to configure * @param service_name name of the service to share * @param num_peers number of peers that should share one instance @@ -75,58 +1921,462 @@ GNUNET_TESTBED_controller_start (const struct GNUNET_CONFIGURATION_Handle *cfg, * use 0 to disable the service */ void -GNUNET_TESTBED_controller_configure_sharing (struct GNUNET_TESTBED_Controller *controller, - const char *service_name, - uint32_t num_peers) +GNUNET_TESTBED_controller_configure_sharing (struct GNUNET_TESTBED_Controller + *controller, + const char *service_name, + uint32_t num_peers) { - GNUNET_break (0); + struct GNUNET_TESTBED_ConfigureSharedServiceMessage *msg; + uint16_t service_name_size; + uint16_t msg_size; + + service_name_size = strlen (service_name) + 1; + msg_size = + sizeof (struct GNUNET_TESTBED_ConfigureSharedServiceMessage) + + service_name_size; + msg = GNUNET_malloc (msg_size); + msg->header.size = htons (msg_size); + msg->header.type = htons (GNUNET_MESSAGE_TYPE_TESTBED_SHARE_SERVICE); + msg->host_id = htonl (GNUNET_TESTBED_host_get_id_ (controller->host)); + msg->num_peers = htonl (num_peers); + memcpy (&msg[1], service_name, service_name_size); + GNUNET_TESTBED_queue_message_ (controller, + (struct GNUNET_MessageHeader *) msg); + GNUNET_break (0); /* This function is not yet implemented on the + * testbed service */ } /** - * Stop the given controller (also will terminate all peers and - * controllers dependent on this controller). This function - * blocks until the testbed has been fully terminated (!). + * disconnects from the controller. * * @param controller handle to controller to stop */ void -GNUNET_TESTBED_controller_stop (struct GNUNET_TESTBED_Controller *controller) +GNUNET_TESTBED_controller_disconnect (struct GNUNET_TESTBED_Controller + *controller) { - GNUNET_break (0); + struct MessageQueue *mq_entry; + + if (NULL != controller->th) + GNUNET_CLIENT_notify_transmit_ready_cancel (controller->th); + /* Clear the message queue */ + while (NULL != (mq_entry = controller->mq_head)) + { + GNUNET_CONTAINER_DLL_remove (controller->mq_head, controller->mq_tail, + mq_entry); + GNUNET_free (mq_entry->msg); + GNUNET_free (mq_entry); + } + if (NULL != controller->client) + GNUNET_CLIENT_disconnect (controller->client); + GNUNET_CONFIGURATION_destroy (controller->cfg); + if (GNUNET_YES == controller->aux_host) + GNUNET_TESTBED_host_destroy (controller->host); + GNUNET_TESTBED_operation_queue_destroy_ (controller->opq_parallel_operations); + GNUNET_TESTBED_operation_queue_destroy_ + (controller->opq_parallel_service_connections); + GNUNET_TESTBED_operation_queue_destroy_ + (controller->opq_parallel_topology_config_operations); + GNUNET_TESTBED_operation_queue_destroy_ + (controller->opq_parallel_overlay_connect_operations); + SD_destroy (controller->poc_sd); + GNUNET_free_non_null (controller->tslots); + GNUNET_free (controller); +} + + +/** + * Register a host with the controller + * + * @param controller the controller handle + * @param host the host to register + * @param cc the completion callback to call to inform the status of + * registration. After calling this callback the registration handle + * will be invalid. Cannot be NULL. + * @param cc_cls the closure for the cc + * @return handle to the host registration which can be used to cancel the + * registration + */ +struct GNUNET_TESTBED_HostRegistrationHandle * +GNUNET_TESTBED_register_host (struct GNUNET_TESTBED_Controller *controller, + struct GNUNET_TESTBED_Host *host, + GNUNET_TESTBED_HostRegistrationCompletion cc, + void *cc_cls) +{ + struct GNUNET_TESTBED_HostRegistrationHandle *rh; + struct GNUNET_TESTBED_AddHostMessage *msg; + const char *username; + const char *hostname; + uint16_t msg_size; + uint16_t user_name_length; + + if (NULL != controller->rh) + return NULL; + hostname = GNUNET_TESTBED_host_get_hostname (host); + if (GNUNET_YES == GNUNET_TESTBED_is_host_registered_ (host, controller)) + { + LOG (GNUNET_ERROR_TYPE_WARNING, "Host hostname: %s already registered\n", + (NULL == hostname) ? "localhost" : hostname); + return NULL; + } + rh = GNUNET_malloc (sizeof (struct GNUNET_TESTBED_HostRegistrationHandle)); + rh->host = host; + rh->c = controller; + GNUNET_assert (NULL != cc); + rh->cc = cc; + rh->cc_cls = cc_cls; + controller->rh = rh; + username = GNUNET_TESTBED_host_get_username_ (host); + msg_size = (sizeof (struct GNUNET_TESTBED_AddHostMessage)); + user_name_length = 0; + if (NULL != username) + { + user_name_length = strlen (username) + 1; + msg_size += user_name_length; + } + /* FIXME: what happens when hostname is NULL? localhost */ + GNUNET_assert (NULL != hostname); + msg_size += strlen (hostname) + 1; + msg = GNUNET_malloc (msg_size); + msg->header.size = htons (msg_size); + msg->header.type = htons (GNUNET_MESSAGE_TYPE_TESTBED_ADD_HOST); + msg->host_id = htonl (GNUNET_TESTBED_host_get_id_ (host)); + msg->ssh_port = htons (GNUNET_TESTBED_host_get_ssh_port_ (host)); + if (NULL != username) + { + msg->user_name_length = htons (user_name_length - 1); + memcpy (&msg[1], username, user_name_length); + } + else + msg->user_name_length = htons (user_name_length); + strcpy (((void *) &msg[1]) + user_name_length, hostname); + GNUNET_TESTBED_queue_message_ (controller, + (struct GNUNET_MessageHeader *) msg); + return rh; +} + + +/** + * Cancel the pending registration. Note that if the registration message is + * already sent to the service the cancellation has only the effect that the + * registration completion callback for the registration is never called. + * + * @param handle the registration handle to cancel + */ +void +GNUNET_TESTBED_cancel_registration (struct GNUNET_TESTBED_HostRegistrationHandle + *handle) +{ + if (handle != handle->c->rh) + { + GNUNET_break (0); + return; + } + handle->c->rh = NULL; + GNUNET_free (handle); +} + + +/** + * Same as the GNUNET_TESTBED_controller_link_2, but with ids for delegated host + * and slave host + * + * @param op_cls the operation closure for the event which is generated to + * signal success or failure of this operation + * @param master handle to the master controller who creates the association + * @param delegated_host_id id of the host to which requests should be delegated + * @param slave_host_id id of the host which is used to run the slave controller + * @param sxcfg serialized and compressed configuration + * @param sxcfg_size the size sxcfg + * @param scfg_size the size of uncompressed serialized configuration + * @param is_subordinate GNUNET_YES if the controller at delegated_host should + * be started by the slave controller; GNUNET_NO if the slave + * controller has to connect to the already started delegated + * controller via TCP/IP + * @return the operation handle + */ +struct GNUNET_TESTBED_Operation * +GNUNET_TESTBED_controller_link_2_ (void *op_cls, + struct GNUNET_TESTBED_Controller *master, + uint32_t delegated_host_id, + uint32_t slave_host_id, const char *sxcfg, + size_t sxcfg_size, size_t scfg_size, + int is_subordinate) +{ + struct OperationContext *opc; + struct GNUNET_TESTBED_ControllerLinkMessage *msg; + struct ControllerLinkData *data; + uint16_t msg_size; + + msg_size = sxcfg_size + sizeof (struct GNUNET_TESTBED_ControllerLinkMessage); + msg = GNUNET_malloc (msg_size); + msg->header.type = htons (GNUNET_MESSAGE_TYPE_TESTBED_LINK_CONTROLLERS); + msg->header.size = htons (msg_size); + msg->delegated_host_id = htonl (delegated_host_id); + msg->slave_host_id = htonl (slave_host_id); + msg->config_size = htons ((uint16_t) scfg_size); + msg->is_subordinate = (GNUNET_YES == is_subordinate) ? 1 : 0; + memcpy (&msg[1], sxcfg, sxcfg_size); + data = GNUNET_malloc (sizeof (struct ControllerLinkData)); + data->msg = msg; + opc = GNUNET_malloc (sizeof (struct OperationContext)); + opc->c = master; + opc->data = data; + opc->type = OP_LINK_CONTROLLERS; + opc->id = GNUNET_TESTBED_get_next_op_id (opc->c); + opc->state = OPC_STATE_INIT; + opc->op_cls = op_cls; + msg->operation_id = GNUNET_htonll (opc->id); + opc->op = + GNUNET_TESTBED_operation_create_ (opc, &opstart_link_controllers, + &oprelease_link_controllers); + GNUNET_TESTBED_operation_queue_insert_ (master->opq_parallel_operations, + opc->op); + GNUNET_TESTBED_operation_begin_wait_ (opc->op); + return opc->op; +} + + +/** + * Same as the GNUNET_TESTBED_controller_link, however expects configuration in + * serialized and compressed + * + * @param op_cls the operation closure for the event which is generated to + * signal success or failure of this operation + * @param master handle to the master controller who creates the association + * @param delegated_host requests to which host should be delegated; cannot be NULL + * @param slave_host which host is used to run the slave controller; use NULL to + * make the master controller connect to the delegated host + * @param sxcfg serialized and compressed configuration + * @param sxcfg_size the size sxcfg + * @param scfg_size the size of uncompressed serialized configuration + * @param is_subordinate GNUNET_YES if the controller at delegated_host should + * be started by the slave controller; GNUNET_NO if the slave + * controller has to connect to the already started delegated + * controller via TCP/IP + * @return the operation handle + */ +struct GNUNET_TESTBED_Operation * +GNUNET_TESTBED_controller_link_2 (void *op_cls, + struct GNUNET_TESTBED_Controller *master, + struct GNUNET_TESTBED_Host *delegated_host, + struct GNUNET_TESTBED_Host *slave_host, + const char *sxcfg, size_t sxcfg_size, + size_t scfg_size, int is_subordinate) +{ + uint32_t delegated_host_id; + uint32_t slave_host_id; + + GNUNET_assert (GNUNET_YES == + GNUNET_TESTBED_is_host_registered_ (delegated_host, master)); + delegated_host_id = GNUNET_TESTBED_host_get_id_ (delegated_host); + slave_host_id = + GNUNET_TESTBED_host_get_id_ ((NULL != + slave_host) ? slave_host : master->host); + if ((NULL != slave_host) && (0 != GNUNET_TESTBED_host_get_id_ (slave_host))) + GNUNET_assert (GNUNET_YES == + GNUNET_TESTBED_is_host_registered_ (slave_host, master)); + + return GNUNET_TESTBED_controller_link_2_ (op_cls, master, delegated_host_id, + slave_host_id, sxcfg, sxcfg_size, + scfg_size, is_subordinate); +} + + +/** + * Compresses given configuration using zlib compress + * + * @param config the serialized configuration + * @param size the size of config + * @param xconfig will be set to the compressed configuration (memory is fresly + * allocated) + * @return the size of the xconfig + */ +size_t +GNUNET_TESTBED_compress_config_ (const char *config, size_t size, + char **xconfig) +{ + size_t xsize; + + xsize = compressBound ((uLong) size); + *xconfig = GNUNET_malloc (xsize); + GNUNET_assert (Z_OK == + compress2 ((Bytef *) * xconfig, (uLongf *) & xsize, + (const Bytef *) config, (uLongf) size, + Z_BEST_SPEED)); + return xsize; } /** - * Create a link from a 'master' controller to a slave controller. - * Whenever the master controller is asked to start a peer at the - * given 'delegated_host', it will delegate the request to the - * specified slave controller. Note that the slave controller runs at - * the 'slave_host', which may or may not be the same host as the - * 'delegated_host' (for hierarchical delegations). The configuration - * of the slave controller is given and to be used to either create - * the slave controller or to connect to an existing slave controller - * process. 'is_subordinate' specifies if the given slave controller - * should be started and managed by the master controller, or if the - * slave already has a master and this is just a secondary master that - * is also allowed to use the existing slave. + * Same as the GNUNET_TESTBED_controller_link, but with ids for delegated host + * and slave host * + * @param op_cls the operation closure for the event which is generated to + * signal success or failure of this operation * @param master handle to the master controller who creates the association - * @param delegated_host requests to which host should be delegated - * @param slave_host which host is used to run the slave controller + * @param delegated_host_id id of the host to which requests should be + * delegated; cannot be NULL + * @param slave_host_id id of the host which should connect to controller + * running on delegated host ; use NULL to make the master controller + * connect to the delegated host * @param slave_cfg configuration to use for the slave controller - * @param is_subordinate GNUNET_YES if the slave should be started (and stopped) - * by the master controller; GNUNET_NO if we are just - * allowed to use the slave via TCP/IP + * @param is_subordinate GNUNET_YES if the controller at delegated_host should + * be started by the slave controller; GNUNET_NO if the slave + * controller has to connect to the already started delegated + * controller via TCP/IP + * @return the operation handle */ -void -GNUNET_TESTBED_controller_link (struct GNUNET_TESTBED_Controller *master, - struct GNUNET_TESTBED_Host *delegated_host, - struct GNUNET_TESTBED_Host *slave_host, - const struct GNUNET_CONFIGURATION_Handle *slave_cfg, - int is_subordinate) +struct GNUNET_TESTBED_Operation * +GNUNET_TESTBED_controller_link_ (void *op_cls, + struct GNUNET_TESTBED_Controller *master, + uint32_t delegated_host_id, + uint32_t slave_host_id, + const struct GNUNET_CONFIGURATION_Handle + *slave_cfg, int is_subordinate) { - GNUNET_break (0); + struct GNUNET_TESTBED_Operation *op; + char *config; + char *cconfig; + size_t cc_size; + size_t config_size; + + config = GNUNET_CONFIGURATION_serialize (slave_cfg, &config_size); + cc_size = GNUNET_TESTBED_compress_config_ (config, config_size, &cconfig); + GNUNET_free (config); + /* Configuration doesn't fit in 1 message */ + GNUNET_assert ((UINT16_MAX - + sizeof (struct GNUNET_TESTBED_ControllerLinkMessage)) >= + cc_size); + op = GNUNET_TESTBED_controller_link_2_ (op_cls, master, delegated_host_id, + slave_host_id, (const char *) cconfig, + cc_size, config_size, is_subordinate); + GNUNET_free (cconfig); + return op; +} + + +/** + * Create a link from slave controller to delegated controller. Whenever the + * master controller is asked to start a peer at the delegated controller the + * request will be routed towards slave controller (if a route exists). The + * slave controller will then route it to the delegated controller. The + * configuration of the delegated controller is given and is used to either + * create the delegated controller or to connect to an existing controller. Note + * that while starting the delegated controller the configuration will be + * modified to accommodate available free ports. the 'is_subordinate' specifies + * if the given delegated controller should be started and managed by the slave + * controller, or if the delegated controller already has a master and the slave + * controller connects to it as a non master controller. The success or failure + * of this operation will be signalled through the + * GNUNET_TESTBED_ControllerCallback() with an event of type + * GNUNET_TESTBED_ET_OPERATION_FINISHED + * + * @param op_cls the operation closure for the event which is generated to + * signal success or failure of this operation + * @param master handle to the master controller who creates the association + * @param delegated_host requests to which host should be delegated; cannot be NULL + * @param slave_host which host is used to run the slave controller; use NULL to + * make the master controller connect to the delegated host + * @param slave_cfg configuration to use for the slave controller + * @param is_subordinate GNUNET_YES if the controller at delegated_host should + * be started by the slave controller; GNUNET_NO if the slave + * controller has to connect to the already started delegated + * controller via TCP/IP + * @return the operation handle + */ +struct GNUNET_TESTBED_Operation * +GNUNET_TESTBED_controller_link (void *op_cls, + struct GNUNET_TESTBED_Controller *master, + struct GNUNET_TESTBED_Host *delegated_host, + struct GNUNET_TESTBED_Host *slave_host, + const struct GNUNET_CONFIGURATION_Handle + *slave_cfg, int is_subordinate) +{ + uint32_t slave_host_id; + uint32_t delegated_host_id; + + GNUNET_assert (GNUNET_YES == + GNUNET_TESTBED_is_host_registered_ (delegated_host, master)); + slave_host_id = + GNUNET_TESTBED_host_get_id_ ((NULL != + slave_host) ? slave_host : master->host); + delegated_host_id = GNUNET_TESTBED_host_get_id_ (delegated_host); + if ((NULL != slave_host) && (0 != slave_host_id)) + GNUNET_assert (GNUNET_YES == + GNUNET_TESTBED_is_host_registered_ (slave_host, master)); + return GNUNET_TESTBED_controller_link_ (op_cls, master, delegated_host_id, + slave_host_id, slave_cfg, + is_subordinate); + +} + + +/** + * Like GNUNET_TESTBED_get_slave_config(), however without the host registration + * check. Another difference is that this function takes the id of the slave + * host. + * + * @param op_cls the closure for the operation + * @param master the handle to master controller + * @param slave_host_id id of the host where the slave controller is running to + * the slave_host should remain valid until this operation is cancelled + * or marked as finished + * @return the operation handle; + */ +struct GNUNET_TESTBED_Operation * +GNUNET_TESTBED_get_slave_config_ (void *op_cls, + struct GNUNET_TESTBED_Controller *master, + uint32_t slave_host_id) +{ + struct OperationContext *opc; + struct GetSlaveConfigData *data; + + data = GNUNET_malloc (sizeof (struct GetSlaveConfigData)); + data->slave_id = slave_host_id; + opc = GNUNET_malloc (sizeof (struct OperationContext)); + opc->state = OPC_STATE_INIT; + opc->c = master; + opc->id = GNUNET_TESTBED_get_next_op_id (master); + opc->type = OP_GET_SLAVE_CONFIG; + opc->data = data; + opc->op_cls = op_cls; + opc->op = + GNUNET_TESTBED_operation_create_ (opc, &opstart_get_slave_config, + &oprelease_get_slave_config); + GNUNET_TESTBED_operation_queue_insert_ (master->opq_parallel_operations, + opc->op); + GNUNET_TESTBED_operation_begin_wait_ (opc->op); + return opc->op; +} + + +/** + * Function to acquire the configuration of a running slave controller. The + * completion of the operation is signalled through the controller_cb from + * GNUNET_TESTBED_controller_connect(). If the operation is successful the + * handle to the configuration is available in the generic pointer of + * operation_finished field of struct GNUNET_TESTBED_EventInformation. + * + * @param op_cls the closure for the operation + * @param master the handle to master controller + * @param slave_host the host where the slave controller is running; the handle + * to the slave_host should remain valid until this operation is + * cancelled or marked as finished + * @return the operation handle; NULL if the slave_host is not registered at + * master + */ +struct GNUNET_TESTBED_Operation * +GNUNET_TESTBED_get_slave_config (void *op_cls, + struct GNUNET_TESTBED_Controller *master, + struct GNUNET_TESTBED_Host *slave_host) +{ + if (GNUNET_NO == GNUNET_TESTBED_is_host_registered_ (slave_host, master)) + return NULL; + return GNUNET_TESTBED_get_slave_config_ (op_cls, master, + GNUNET_TESTBED_host_get_id_ + (slave_host)); } @@ -140,11 +2390,375 @@ GNUNET_TESTBED_controller_link (struct GNUNET_TESTBED_Controller *master, * be written to. */ void -GNUNET_TESTBED_overlay_write_topology_to_file (struct GNUNET_TESTBED_Controller *controller, - const char *filename) +GNUNET_TESTBED_overlay_write_topology_to_file (struct GNUNET_TESTBED_Controller + *controller, + const char *filename) +{ + GNUNET_break (0); +} + + +/** + * Creates a helper initialization message. This function is here because we + * want to use this in testing + * + * @param trusted_ip the ip address of the controller which will be set as TRUSTED + * HOST(all connections form this ip are permitted by the testbed) when + * starting testbed controller at host. This can either be a single ip + * address or a network address in CIDR notation. + * @param hostname the hostname of the destination this message is intended for + * @param cfg the configuration that has to used to start the testbed service + * thru helper + * @return the initialization message + */ +struct GNUNET_TESTBED_HelperInit * +GNUNET_TESTBED_create_helper_init_msg_ (const char *trusted_ip, + const char *hostname, + const struct GNUNET_CONFIGURATION_Handle + *cfg) +{ + struct GNUNET_TESTBED_HelperInit *msg; + char *config; + char *xconfig; + size_t config_size; + size_t xconfig_size; + uint16_t trusted_ip_len; + uint16_t hostname_len; + uint16_t msg_size; + + config = GNUNET_CONFIGURATION_serialize (cfg, &config_size); + GNUNET_assert (NULL != config); + xconfig_size = + GNUNET_TESTBED_compress_config_ (config, config_size, &xconfig); + GNUNET_free (config); + trusted_ip_len = strlen (trusted_ip); + hostname_len = (NULL == hostname) ? 0 : strlen (hostname); + msg_size = + xconfig_size + trusted_ip_len + 1 + + sizeof (struct GNUNET_TESTBED_HelperInit); + msg_size += hostname_len; + msg = GNUNET_realloc (xconfig, msg_size); + (void) memmove (((void *) &msg[1]) + trusted_ip_len + 1 + hostname_len, msg, + xconfig_size); + msg->header.size = htons (msg_size); + msg->header.type = htons (GNUNET_MESSAGE_TYPE_TESTBED_HELPER_INIT); + msg->trusted_ip_size = htons (trusted_ip_len); + msg->hostname_size = htons (hostname_len); + msg->config_size = htons (config_size); + (void) strcpy ((char *) &msg[1], trusted_ip); + if (0 != hostname_len) + (void) strncpy (((char *) &msg[1]) + trusted_ip_len + 1, hostname, + hostname_len); + return msg; +} + + +/** + * Cancel a pending operation. Releases all resources + * of the operation and will ensure that no event + * is generated for the operation. Does NOT guarantee + * that the operation will be fully undone (or that + * nothing ever happened). + * + * @param operation operation to cancel + */ +void +GNUNET_TESTBED_operation_cancel (struct GNUNET_TESTBED_Operation *operation) +{ + GNUNET_TESTBED_operation_done (operation); +} + + +/** + * Signal that the information from an operation has been fully + * processed. This function MUST be called for each event + * of type 'operation_finished' to fully remove the operation + * from the operation queue. After calling this function, the + * 'op_result' becomes invalid (!). + * + * @param operation operation to signal completion for + */ +void +GNUNET_TESTBED_operation_done (struct GNUNET_TESTBED_Operation *operation) +{ + last_finished_operation = operation; + GNUNET_TESTBED_operation_release_ (operation); +} + + +/** + * Generates configuration by uncompressing configuration in given message. The + * given message should be of the following types: + * GNUNET_MESSAGE_TYPE_TESTBED_PEERCONFIG, + * GNUNET_MESSAGE_TYPE_TESTBED_SLAVECONFIG + * + * @param msg the message containing compressed configuration + * @return handle to the parsed configuration + */ +struct GNUNET_CONFIGURATION_Handle * +GNUNET_TESTBED_extract_config_ (const struct GNUNET_MessageHeader *msg) +{ + struct GNUNET_CONFIGURATION_Handle *cfg; + Bytef *data; + const Bytef *xdata; + uLong data_len; + uLong xdata_len; + int ret; + + switch (ntohs (msg->type)) + { + case GNUNET_MESSAGE_TYPE_TESTBED_PEER_CONFIGURATION: + { + const struct GNUNET_TESTBED_PeerConfigurationInformationMessage *imsg; + + imsg = + (const struct GNUNET_TESTBED_PeerConfigurationInformationMessage *) msg; + data_len = (uLong) ntohs (imsg->config_size); + xdata_len = + ntohs (imsg->header.size) - + sizeof (struct GNUNET_TESTBED_PeerConfigurationInformationMessage); + xdata = (const Bytef *) &imsg[1]; + } + break; + case GNUNET_MESSAGE_TYPE_TESTBED_SLAVE_CONFIGURATION: + { + const struct GNUNET_TESTBED_SlaveConfiguration *imsg; + + imsg = (const struct GNUNET_TESTBED_SlaveConfiguration *) msg; + data_len = (uLong) ntohs (imsg->config_size); + xdata_len = + ntohs (imsg->header.size) - + sizeof (struct GNUNET_TESTBED_SlaveConfiguration); + xdata = (const Bytef *) &imsg[1]; + } + break; + default: + GNUNET_assert (0); + } + data = GNUNET_malloc (data_len); + if (Z_OK != (ret = uncompress (data, &data_len, xdata, xdata_len))) + GNUNET_assert (0); + cfg = GNUNET_CONFIGURATION_create (); + GNUNET_assert (GNUNET_OK == + GNUNET_CONFIGURATION_deserialize (cfg, (const char *) data, + (size_t) data_len, + GNUNET_NO)); + GNUNET_free (data); + return cfg; +} + + +/** + * Checks the integrity of the OperationFailureEventMessage and if good returns + * the error message it contains. + * + * @param msg the OperationFailureEventMessage + * @return the error message + */ +const char * +GNUNET_TESTBED_parse_error_string_ (const struct + GNUNET_TESTBED_OperationFailureEventMessage + *msg) +{ + uint16_t msize; + const char *emsg; + + msize = ntohs (msg->header.size); + if (sizeof (struct GNUNET_TESTBED_OperationFailureEventMessage) >= msize) + return NULL; + msize -= sizeof (struct GNUNET_TESTBED_OperationFailureEventMessage); + emsg = (const char *) &msg[1]; + if ('\0' != emsg[msize - 1]) + { + GNUNET_break (0); + return NULL; + } + return emsg; +} + + +/** + * Function to return the operation id for a controller. The operation id is + * created from the controllers host id and its internal operation counter. + * + * @param controller the handle to the controller whose operation id has to be incremented + * @return the incremented operation id. + */ +uint64_t +GNUNET_TESTBED_get_next_op_id (struct GNUNET_TESTBED_Controller * controller) +{ + uint64_t op_id; + + op_id = (uint64_t) GNUNET_TESTBED_host_get_id_ (controller->host); + op_id = op_id << 32; + op_id |= (uint64_t) controller->operation_counter++; + return op_id; +} + + +/** + * Returns a timing slot which will be exclusively locked + * + * @param c the controller handle + * @param key a pointer which is associated to the returned slot; should not be + * NULL. It serves as a key to determine the correct owner of the slot + * @return the time slot index in the array of time slots in the controller + * handle + */ +unsigned int +GNUNET_TESTBED_get_tslot_ (struct GNUNET_TESTBED_Controller *c, void *key) +{ + unsigned int slot; + + GNUNET_assert (NULL != c->tslots); + GNUNET_assert (NULL != key); + for (slot = 0; slot < c->num_parallel_connects; slot++) + if (NULL == c->tslots[slot].key) + { + c->tslots[slot].key = key; + return slot; + } + GNUNET_assert (0); /* We should always find a free tslot */ +} + + +/** + * Decides whether any change in the number of parallel overlay connects is + * necessary to adapt to the load on the system + * + * @param c the controller handle + */ +static void +decide_npoc (struct GNUNET_TESTBED_Controller *c) +{ + struct GNUNET_TIME_Relative avg; + int sd; + unsigned int slot; + unsigned int nvals; + + if (c->tslots_filled != c->num_parallel_connects) + return; + avg = GNUNET_TIME_UNIT_ZERO; + nvals = 0; + for (slot = 0; slot < c->num_parallel_connects; slot++) + { + avg = GNUNET_TIME_relative_add (avg, c->tslots[slot].time); + nvals += c->tslots[slot].nvals; + } + GNUNET_assert (nvals >= c->num_parallel_connects); + avg = GNUNET_TIME_relative_divide (avg, nvals); + GNUNET_assert (GNUNET_TIME_UNIT_FOREVER_REL.rel_value != avg.rel_value); + sd = SD_deviation_factor (c->poc_sd, (unsigned int) avg.rel_value); + if ( (sd <= 5) || + (0 == GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK, + c->num_parallel_connects)) ) + SD_add_data (c->poc_sd, (unsigned int) avg.rel_value); + if (GNUNET_SYSERR == sd) + { + GNUNET_TESTBED_set_num_parallel_overlay_connects_ (c, + c->num_parallel_connects); + return; + } + GNUNET_assert (0 <= sd); + if (0 == sd) + { + GNUNET_TESTBED_set_num_parallel_overlay_connects_ (c, + c->num_parallel_connects + * 2); + return; + } + if (1 == sd) + { + GNUNET_TESTBED_set_num_parallel_overlay_connects_ (c, + c->num_parallel_connects + + 1); + return; + } + if (1 == c->num_parallel_connects) + { + GNUNET_TESTBED_set_num_parallel_overlay_connects_ (c, 1); + return; + } + if (2 == sd) + { + GNUNET_TESTBED_set_num_parallel_overlay_connects_ (c, + c->num_parallel_connects + - 1); + return; + } + GNUNET_TESTBED_set_num_parallel_overlay_connects_ (c, + c->num_parallel_connects / + 2); +} + + +/** + * Releases a time slot thus making it available for be used again + * + * @param c the controller handle + * @param index the index of the the time slot + * @param key the key to prove ownership of the timeslot + * @return GNUNET_YES if the time slot is successfully removed; GNUNET_NO if the + * time slot cannot be removed - this could be because of the index + * greater than existing number of time slots or `key' being different + */ +int +GNUNET_TESTBED_release_time_slot_ (struct GNUNET_TESTBED_Controller *c, + unsigned int index, void *key) { + struct TimeSlot *slot; + + GNUNET_assert (NULL != key); + if (index >= c->num_parallel_connects) + return GNUNET_NO; + slot = &c->tslots[index]; + if (key != slot->key) + return GNUNET_NO; + slot->key = NULL; + return GNUNET_YES; } +/** + * Function to update a time slot + * + * @param c the controller handle + * @param index the index of the time slot to update + * @param key the key to identify ownership of the slot + * @param time the new time + * @param failed should this reading be treated as coming from a fail event + */ +void +GNUNET_TESTBED_update_time_slot_ (struct GNUNET_TESTBED_Controller *c, + unsigned int index, void *key, + struct GNUNET_TIME_Relative time, int failed) +{ + struct TimeSlot *slot; + + if (GNUNET_YES == failed) + { + if (1 == c->num_parallel_connects) + { + GNUNET_TESTBED_set_num_parallel_overlay_connects_ (c, 1); + return; + } + GNUNET_TESTBED_set_num_parallel_overlay_connects_ (c, + c->num_parallel_connects + - 1); + } + if (GNUNET_NO == GNUNET_TESTBED_release_time_slot_ (c, index, key)) + return; + slot = &c->tslots[index]; + slot->nvals++; + if (GNUNET_TIME_UNIT_ZERO.rel_value == slot->time.rel_value) + { + slot->time = time; + c->tslots_filled++; + decide_npoc (c); + return; + } + slot->time = GNUNET_TIME_relative_add (slot->time, time); +} + /* end of testbed_api.c */ diff --git a/src/testbed/testbed_api.h b/src/testbed/testbed_api.h new file mode 100644 index 0000000..d6c04a6 --- /dev/null +++ b/src/testbed/testbed_api.h @@ -0,0 +1,590 @@ +/* + This file is part of GNUnet + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. + */ + +/** + * @file testbed/testbed_api.h + * @brief Interface for functions internally exported from testbed_api.c + * @author Sree Harsha Totakura + */ + +#ifndef TESTBED_API_H +#define TESTBED_API_H + +#include "gnunet_testbed_service.h" +#include "testbed.h" + + +/** + * Testbed Helper binary name + */ +#define HELPER_TESTBED_BINARY "gnunet-helper-testbed" + + +/** + * Enumeration of operations + */ +enum OperationType +{ + /** + * Peer create operation + */ + OP_PEER_CREATE, + + /** + * Peer start operation + */ + OP_PEER_START, + + /** + * Peer stop operation + */ + OP_PEER_STOP, + + /** + * Peer destroy operation + */ + OP_PEER_DESTROY, + + /** + * Get peer information operation + */ + OP_PEER_INFO, + + /** + * Overlay connection operation + */ + OP_OVERLAY_CONNECT, + + /** + * Forwarded operation + */ + OP_FORWARDED, + + /** + * Link controllers operation + */ + OP_LINK_CONTROLLERS, + + /** + * Get slave config operation + */ + OP_GET_SLAVE_CONFIG +}; + + +/** + * The message queue for sending messages to the controller service + */ +struct MessageQueue; + +/** + * Structure for a controller link + */ +struct ControllerLink; + + +/** + * Enumeration of states of OperationContext + */ +enum OperationContextState +{ + /** + * The initial state where the associated operation has just been created + * and is waiting in the operation queues to be started + */ + OPC_STATE_INIT = 0, + + /** + * The operation has been started. It may occupy some resources which are to + * be freed if cancelled. + */ + OPC_STATE_STARTED, + + /** + * The operation has finished. The end results of this operation may occupy + * some resources which are to be freed by operation_done + */ + OPC_STATE_FINISHED +}; + + +/** + * Context information for GNUNET_TESTBED_Operation + */ +struct OperationContext +{ + /** + * next ptr for DLL + */ + struct OperationContext *next; + + /** + * prev ptr for DLL + */ + struct OperationContext *prev; + + /** + * The controller to which this operation context belongs to + */ + struct GNUNET_TESTBED_Controller *c; + + /** + * The operation + */ + struct GNUNET_TESTBED_Operation *op; + + /** + * The operation closure + */ + void *op_cls; + + /** + * Data relevant to the operation + */ + void *data; + + /** + * The id of the opearation + */ + uint64_t id; + + /** + * The type of operation + */ + enum OperationType type; + + /** + * The state of the operation + */ + enum OperationContextState state; +}; + + +/** + * Opaque handle for SD calculations + */ +struct SDHandle; + + +/** + * A slot to record time taken by an overlay connect operation + */ +struct TimeSlot +{ + /** + * A key to identify this timeslot + */ + void *key; + + /** + * Time + */ + struct GNUNET_TIME_Relative time; + + /** + * Number of timing values accumulated + */ + unsigned int nvals; +}; + + +/** + * Handle to interact with a GNUnet testbed controller. Each + * controller has at least one master handle which is created when the + * controller is created; this master handle interacts with the + * controller process, destroying it destroys the controller (by + * closing stdin of the controller process). Additionally, + * controllers can interact with each other (in a P2P fashion); those + * links are established via TCP/IP on the controller's service port. + */ +struct GNUNET_TESTBED_Controller +{ + /** + * The host where the controller is running + */ + struct GNUNET_TESTBED_Host *host; + + /** + * The controller callback + */ + GNUNET_TESTBED_ControllerCallback cc; + + /** + * The closure for controller callback + */ + void *cc_cls; + + /** + * The configuration to use while connecting to controller + */ + struct GNUNET_CONFIGURATION_Handle *cfg; + + /** + * The client connection handle to the controller service + */ + struct GNUNET_CLIENT_Connection *client; + + /** + * The head of the message queue + */ + struct MessageQueue *mq_head; + + /** + * The tail of the message queue + */ + struct MessageQueue *mq_tail; + + /** + * The head of the ControllerLink list + */ + struct ControllerLink *cl_head; + + /** + * The tail of the ControllerLink list + */ + struct ControllerLink *cl_tail; + + /** + * The client transmit handle + */ + struct GNUNET_CLIENT_TransmitHandle *th; + + /** + * The host registration handle; NULL if no current registration requests are + * present + */ + struct GNUNET_TESTBED_HostRegistrationHandle *rh; + + /** + * The head of the opeartion context queue + */ + struct OperationContext *ocq_head; + + /** + * The tail of the operation context queue + */ + struct OperationContext *ocq_tail; + + /** + * Operation queue for simultaneous operations + */ + struct OperationQueue *opq_parallel_operations; + + /** + * Operation queue for simultaneous service connections + */ + struct OperationQueue *opq_parallel_service_connections; + + /** + * Operation queue for simultaneous topology configuration operations + */ + struct OperationQueue *opq_parallel_topology_config_operations; + + /** + * Operation queue for simultaneous overlay connect operations + */ + struct OperationQueue *opq_parallel_overlay_connect_operations; + + /** + * An array of timing slots; size should be equal to the current number of parallel + * overlay connects + */ + struct TimeSlot *tslots; + + /** + * Handle for SD calculations amount parallel overlay connect operation finish + * times + */ + struct SDHandle *poc_sd; + + /** + * The controller event mask + */ + uint64_t event_mask; + + /** + * Did we start the receive loop yet? + */ + int in_receive; + + /** + * Did we create the host for this? + */ + int aux_host; + + /** + * The number of parallel overlay connects we do currently + */ + unsigned int num_parallel_connects; + + /** + * Counter to indicate when all the available time slots are filled + */ + unsigned int tslots_filled; + + /** + * The operation id counter. use current value and increment + */ + uint32_t operation_counter; + +}; + + +/** + * Queues a message in send queue for sending to the service + * + * @param controller the handle to the controller + * @param msg the message to queue + */ +void +GNUNET_TESTBED_queue_message_ (struct GNUNET_TESTBED_Controller *controller, + struct GNUNET_MessageHeader *msg); + + +/** + * Compresses given configuration using zlib compress + * + * @param config the serialized configuration + * @param size the size of config + * @param xconfig will be set to the compressed configuration (memory is fresly + * allocated) + * @return the size of the xconfig + */ +size_t +GNUNET_TESTBED_compress_config_ (const char *config, size_t size, + char **xconfig); + + +/** + * Adds an operation to the queue of operations + * + * @param op the operation to add + */ +void +GNUNET_TESTBED_operation_add_ (struct GNUNET_TESTBED_Operation *op); + + +/** + * Creates a helper initialization message. This function is here because we + * want to use this in testing + * + * @param trusted_ip the ip address of the controller which will be set as TRUSTED + * HOST(all connections form this ip are permitted by the testbed) when + * starting testbed controller at host. This can either be a single ip + * address or a network address in CIDR notation. + * @param hostname the hostname of the destination this message is intended for + * @param cfg the configuration that has to used to start the testbed service + * thru helper + * @return the initialization message + */ +struct GNUNET_TESTBED_HelperInit * +GNUNET_TESTBED_create_helper_init_msg_ (const char *cname, const char *hostname, + const struct GNUNET_CONFIGURATION_Handle + *cfg); + + +/** + * Sends the given message as an operation. The given callback is called when a + * reply for the operation is available. Call + * GNUNET_TESTBED_forward_operation_msg_cancel_() to cleanup the returned + * operation context if the cc hasn't been called + * + * @param controller the controller to which the message has to be sent + * @param operation_id the operation id of the message + * @param msg the message to send + * @param cc the callback to call when reply is available + * @param cc_cls the closure for the above callback + * @return the operation context which can be used to cancel the forwarded + * operation + */ +struct OperationContext * +GNUNET_TESTBED_forward_operation_msg_ (struct GNUNET_TESTBED_Controller + *controller, uint64_t operation_id, + const struct GNUNET_MessageHeader *msg, + GNUNET_CLIENT_MessageHandler cc, + void *cc_cls); + +/** + * Function to cancel an operation created by simply forwarding an operation + * message. + * + * @param opc the operation context from GNUNET_TESTBED_forward_operation_msg_() + */ +void +GNUNET_TESTBED_forward_operation_msg_cancel_ (struct OperationContext *opc); + + +/** + * Generates configuration by uncompressing configuration in given message. The + * given message should be of the following types: + * GNUNET_MESSAGE_TYPE_TESTBED_PEERCONFIG, + * GNUNET_MESSAGE_TYPE_TESTBED_SLAVECONFIG + * + * @param msg the message containing compressed configuration + * @return handle to the parsed configuration + */ +struct GNUNET_CONFIGURATION_Handle * +GNUNET_TESTBED_extract_config_ (const struct GNUNET_MessageHeader *msg); + + +/** + * Checks the integrity of the OpeationFailureEventMessage and if good returns + * the error message it contains. + * + * @param msg the OperationFailureEventMessage + * @return the error message + */ +const char * +GNUNET_TESTBED_parse_error_string_ (const struct + GNUNET_TESTBED_OperationFailureEventMessage + *msg); + + +/** + * Function to return the operation id for a controller. The operation id is + * created from the controllers host id and its internal operation counter. + * + * @param controller the handle to the controller whose operation id has to be incremented + * @return the incremented operation id. + */ +uint64_t +GNUNET_TESTBED_get_next_op_id (struct GNUNET_TESTBED_Controller *controller); + + +/** + * Like GNUNET_TESTBED_get_slave_config(), however without the host registration + * check. Another difference is that this function takes the id of the slave + * host. + * + * @param op_cls the closure for the operation + * @param master the handle to master controller + * @param slave_host_id id of the host where the slave controller is running to + * the slave_host should remain valid until this operation is cancelled + * or marked as finished + * @return the operation handle; + */ +struct GNUNET_TESTBED_Operation * +GNUNET_TESTBED_get_slave_config_ (void *op_cls, + struct GNUNET_TESTBED_Controller *master, + uint32_t slave_host_id); + + +/** + * Same as the GNUNET_TESTBED_controller_link_2, but with ids for delegated host + * and slave host + * + * @param op_cls the operation closure for the event which is generated to + * signal success or failure of this operation + * @param master handle to the master controller who creates the association + * @param delegated_host_id id of the host to which requests should be delegated + * @param slave_host_id id of the host which is used to run the slave controller + * @param sxcfg serialized and compressed configuration + * @param sxcfg_size the size sxcfg + * @param scfg_size the size of uncompressed serialized configuration + * @param is_subordinate GNUNET_YES if the controller at delegated_host should + * be started by the slave controller; GNUNET_NO if the slave + * controller has to connect to the already started delegated + * controller via TCP/IP + * @return the operation handle + */ +struct GNUNET_TESTBED_Operation * +GNUNET_TESTBED_controller_link_2_ (void *op_cls, + struct GNUNET_TESTBED_Controller *master, + uint32_t delegated_host_id, + uint32_t slave_host_id, const char *sxcfg, + size_t sxcfg_size, size_t scfg_size, + int is_subordinate); + + +/** + * Same as the GNUNET_TESTBED_controller_link, but with ids for delegated host + * and slave host + * + * @param op_cls the operation closure for the event which is generated to + * signal success or failure of this operation + * @param master handle to the master controller who creates the association + * @param delegated_host_id id of the host to which requests should be + * delegated; cannot be NULL + * @param slave_host_id id of the host which should connect to controller + * running on delegated host ; use NULL to make the master controller + * connect to the delegated host + * @param slave_cfg configuration to use for the slave controller + * @param is_subordinate GNUNET_YES if the controller at delegated_host should + * be started by the slave controller; GNUNET_NO if the slave + * controller has to connect to the already started delegated + * controller via TCP/IP + * @return the operation handle + */ +struct GNUNET_TESTBED_Operation * +GNUNET_TESTBED_controller_link_ (void *op_cls, + struct GNUNET_TESTBED_Controller *master, + uint32_t delegated_host_id, + uint32_t slave_host_id, + const struct GNUNET_CONFIGURATION_Handle + *slave_cfg, int is_subordinate); + + +/** + * Returns a timing slot which will be exclusively locked + * + * @param c the controller handle + * @param key a pointer which is associated to the returned slot; should not be + * NULL. It serves as a key to determine the correct owner of the slot + * @return the time slot index in the array of time slots in the controller + * handle + */ +unsigned int +GNUNET_TESTBED_get_tslot_ (struct GNUNET_TESTBED_Controller *c, void *key); + + +/** + * Function to update a time slot + * + * @param c the controller handle + * @param index the index of the time slot to update + * @param key the key to identify ownership of the slot + * @param time the new time + * @param failed should this reading be treated as coming from a fail event + */ +void +GNUNET_TESTBED_update_time_slot_ (struct GNUNET_TESTBED_Controller *c, + unsigned int index, void *key, + struct GNUNET_TIME_Relative time, int failed); + + +/** + * Releases a time slot thus making it available for be used again + * + * @param c the controller handle + * @param index the index of the the time slot + * @param key the key to prove ownership of the timeslot + * @return GNUNET_YES if the time slot is successfully removed; GNUNET_NO if the + * time slot cannot be removed - this could be because of the index + * greater than existing number of time slots or `key' being different + */ +int +GNUNET_TESTBED_release_time_slot_ (struct GNUNET_TESTBED_Controller *c, + unsigned int index, void *key); + + + + +#endif +/* end of testbed_api.h */ diff --git a/src/testbed/testbed_api_hosts.c b/src/testbed/testbed_api_hosts.c index 1b293b3..293f349 100644 --- a/src/testbed/testbed_api_hosts.c +++ b/src/testbed/testbed_api_hosts.c @@ -26,12 +26,46 @@ * @author Christian Grothoff */ #include "platform.h" +#include "gnunet_util_lib.h" #include "gnunet_testbed_service.h" #include "gnunet_core_service.h" -#include "gnunet_constants.h" #include "gnunet_transport_service.h" -#include "gnunet_hello_lib.h" +#include "testbed_api.h" +#include "testbed_api_hosts.h" + +/** + * Generic logging shorthand + */ +#define LOG(kind, ...) \ + GNUNET_log_from (kind, "testbed-api-hosts", __VA_ARGS__); + +/** + * Number of extra elements we create space for when we grow host list + */ +#define HOST_LIST_GROW_STEP 10 + + +/** + * A list entry for registered controllers list + */ +struct RegisteredController +{ + /** + * The controller at which this host is registered + */ + const struct GNUNET_TESTBED_Controller *controller; + + /** + * The next ptr for DLL + */ + struct RegisteredController *next; + + /** + * The prev ptr for DLL + */ + struct RegisteredController *prev; +}; /** @@ -42,32 +76,73 @@ struct GNUNET_TESTBED_Host { + /** + * The next pointer for DLL + */ + struct GNUNET_TESTBED_Host *next; + + /** + * The prev pointer for DLL + */ + struct GNUNET_TESTBED_Host *prev; + /** + * The hostname of the host; NULL for localhost + */ const char *hostname; + /** + * The username to be used for SSH login + */ const char *username; + /** + * The head for the list of controllers where this host is registered + */ + struct RegisteredController *rc_head; + + /** + * The tail for the list of controllers where this host is registered + */ + struct RegisteredController *rc_tail; + /** * Global ID we use to refer to a host on the network */ - uint32_t unique_id; + uint32_t id; + /** + * The port which is to be used for SSH + */ uint16_t port; + }; +/** + * Array of available hosts + */ +static struct GNUNET_TESTBED_Host **host_list; + +/** + * The size of the available hosts list + */ +static unsigned int host_list_size; + + /** * Lookup a host by ID. - * + * * @param id global host ID assigned to the host; 0 is * reserved to always mean 'localhost' - * @return handle to the host, NULL on error + * @return handle to the host, NULL if host not found */ struct GNUNET_TESTBED_Host * GNUNET_TESTBED_host_lookup_by_id_ (uint32_t id) { - GNUNET_break (0); - return NULL; + if (host_list_size <= id) + return NULL; + return host_list[id]; } @@ -75,7 +150,7 @@ GNUNET_TESTBED_host_lookup_by_id_ (uint32_t id) * Create a host by ID; given this host handle, we could not * run peers at the host, but we can talk about the host * internally. - * + * * @param id global host ID assigned to the host; 0 is * reserved to always mean 'localhost' * @return handle to the host, NULL on error @@ -83,28 +158,66 @@ GNUNET_TESTBED_host_lookup_by_id_ (uint32_t id) struct GNUNET_TESTBED_Host * GNUNET_TESTBED_host_create_by_id_ (uint32_t id) { - return NULL; + return GNUNET_TESTBED_host_create_with_id (id, NULL, NULL, 0); } /** - * Obtain a host's unique global ID. - * + * Obtain the host's unique global ID. + * * @param host handle to the host, NULL means 'localhost' * @return id global host ID assigned to the host (0 is * 'localhost', but then obviously not globally unique) */ uint32_t -GNUNET_TESTBED_host_get_id_ (struct GNUNET_TESTBED_Host *host) +GNUNET_TESTBED_host_get_id_ (const struct GNUNET_TESTBED_Host * host) +{ + return host->id; +} + + +/** + * Obtain the host's hostname. + * + * @param host handle to the host, NULL means 'localhost' + * @return hostname of the host + */ +const char * +GNUNET_TESTBED_host_get_hostname (const struct GNUNET_TESTBED_Host *host) { - GNUNET_break (0); - return 0; + return host->hostname; +} + + +/** + * Obtain the host's username + * + * @param host handle to the host, NULL means 'localhost' + * @return username to login to the host + */ +const char * +GNUNET_TESTBED_host_get_username_ (const struct GNUNET_TESTBED_Host *host) +{ + return host->username; +} + + +/** + * Obtain the host's ssh port + * + * @param host handle to the host, NULL means 'localhost' + * @return username to login to the host + */ +uint16_t +GNUNET_TESTBED_host_get_ssh_port_ (const struct GNUNET_TESTBED_Host * host) +{ + return host->port; } /** * Create a host to run peers and controllers on. - * + * * @param id global host ID assigned to the host; 0 is * reserved to always mean 'localhost' * @param hostname name of the host, use "NULL" for localhost @@ -113,34 +226,52 @@ GNUNET_TESTBED_host_get_id_ (struct GNUNET_TESTBED_Host *host) * @return handle to the host, NULL on error */ struct GNUNET_TESTBED_Host * -GNUNET_TESTBED_host_create_with_id_ (uint32_t id, - const char *hostname, - const char *username, - uint16_t port) +GNUNET_TESTBED_host_create_with_id (uint32_t id, const char *hostname, + const char *username, uint16_t port) { - GNUNET_break (0); - return NULL; + struct GNUNET_TESTBED_Host *host; + unsigned int new_size; + + if ((id < host_list_size) && (NULL != host_list[id])) + { + LOG (GNUNET_ERROR_TYPE_WARNING, "Host with id: %u already created\n", id); + return NULL; + } + host = GNUNET_malloc (sizeof (struct GNUNET_TESTBED_Host)); + host->hostname = (NULL != hostname) ? GNUNET_strdup (hostname) : NULL; + host->username = (NULL != username) ? GNUNET_strdup (username) : NULL; + host->id = id; + host->port = (0 == port) ? 22 : port; + new_size = host_list_size; + while (id >= new_size) + new_size += HOST_LIST_GROW_STEP; + if (new_size != host_list_size) + GNUNET_array_grow (host_list, host_list_size, new_size); + GNUNET_assert (id < host_list_size); + LOG (GNUNET_ERROR_TYPE_DEBUG, "Adding host with id: %u\n", host->id); + host_list[id] = host; + return host; } /** * Create a host to run peers and controllers on. - * + * * @param hostname name of the host, use "NULL" for localhost * @param username username to use for the login; may be NULL * @param port port number to use for ssh; use 0 to let ssh decide * @return handle to the host, NULL on error */ struct GNUNET_TESTBED_Host * -GNUNET_TESTBED_host_create (const char *hostname, - const char *username, - uint16_t port) +GNUNET_TESTBED_host_create (const char *hostname, const char *username, + uint16_t port) { static uint32_t uid_generator; - return GNUNET_TESTBED_host_create_with_id_ (++uid_generator, - hostname, username, - port); + if (NULL == hostname) + return GNUNET_TESTBED_host_create_with_id (0, hostname, username, port); + return GNUNET_TESTBED_host_create_with_id (++uid_generator, hostname, + username, port); } @@ -148,15 +279,90 @@ GNUNET_TESTBED_host_create (const char *hostname, * Load a set of hosts from a configuration file. * * @param filename file with the host specification - * @param hosts set to the hosts found in the file + * @param hosts set to the hosts found in the file; caller must free this if + * number of hosts returned is greater than 0 * @return number of hosts returned in 'hosts', 0 on error */ unsigned int GNUNET_TESTBED_hosts_load_from_file (const char *filename, - struct GNUNET_TESTBED_Host **hosts) + struct GNUNET_TESTBED_Host ***hosts) { - GNUNET_break (0); - return 0; + //struct GNUNET_TESTBED_Host **host_array; + struct GNUNET_TESTBED_Host *starting_host; + char *data; + char *buf; + char username[256]; + char hostname[256]; + uint64_t fs; + short int port; + int ret; + unsigned int offset; + unsigned int count; + + + GNUNET_assert (NULL != filename); + if (GNUNET_YES != GNUNET_DISK_file_test (filename)) + { + LOG (GNUNET_ERROR_TYPE_WARNING, _("Hosts file %s not found\n"), filename); + return 0; + } + if (GNUNET_OK != + GNUNET_DISK_file_size (filename, &fs, GNUNET_YES, GNUNET_YES)) + fs = 0; + if (0 == fs) + { + LOG (GNUNET_ERROR_TYPE_WARNING, _("Hosts file %s has no data\n"), filename); + return 0; + } + data = GNUNET_malloc (fs); + if (fs != GNUNET_DISK_fn_read (filename, data, fs)) + { + GNUNET_free (data); + LOG (GNUNET_ERROR_TYPE_WARNING, _("Hosts file %s cannot be read\n"), + filename); + return 0; + } + buf = data; + offset = 0; + starting_host = NULL; + count = 0; + while (offset < (fs - 1)) + { + offset++; + if (((data[offset] == '\n')) && (buf != &data[offset])) + { + data[offset] = '\0'; + ret = + SSCANF (buf, "%255[a-zA-Z0-9_]@%255[a-zA-Z0-9.]:%5hd", username, + hostname, &port); + if (3 == ret) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Successfully read host %s, port %d and user %s from file\n", + hostname, port, username); + /* We store hosts in a static list; hence we only require the starting + * host pointer in that list to access the newly created list of hosts */ + if (NULL == starting_host) + starting_host = GNUNET_TESTBED_host_create (hostname, username, port); + else + (void) GNUNET_TESTBED_host_create (hostname, username, port); + count++; + } + else + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + "Error reading line `%s' in hostfile\n", buf); + buf = &data[offset + 1]; + } + else if ((data[offset] == '\n') || (data[offset] == '\0')) + buf = &data[offset + 1]; + } + GNUNET_free (data); + if (NULL == starting_host) + return 0; + *hosts = GNUNET_malloc (sizeof (struct GNUNET_TESTBED_Host *) * count); + memcpy (*hosts, &host_list[GNUNET_TESTBED_host_get_id_ (starting_host)], + sizeof (struct GNUNET_TESTBED_Host *) * count); + return count; } @@ -169,32 +375,290 @@ GNUNET_TESTBED_hosts_load_from_file (const char *filename, void GNUNET_TESTBED_host_destroy (struct GNUNET_TESTBED_Host *host) { - GNUNET_break (0); + struct RegisteredController *rc; + uint32_t id; + + GNUNET_assert (host->id < host_list_size); + GNUNET_assert (host_list[host->id] == host); + host_list[host->id] = NULL; + /* clear registered controllers list */ + for (rc = host->rc_head; NULL != rc; rc = host->rc_head) + { + GNUNET_CONTAINER_DLL_remove (host->rc_head, host->rc_tail, rc); + GNUNET_free (rc); + } + GNUNET_free_non_null ((char *) host->username); + GNUNET_free_non_null ((char *) host->hostname); + GNUNET_free (host); + while (host_list_size >= HOST_LIST_GROW_STEP) + { + for (id = host_list_size - 1; id > host_list_size - HOST_LIST_GROW_STEP; + id--) + if (NULL != host_list[id]) + break; + if (id != host_list_size - HOST_LIST_GROW_STEP) + break; + if (NULL != host_list[id]) + break; + host_list_size -= HOST_LIST_GROW_STEP; + } + host_list = + GNUNET_realloc (host_list, + sizeof (struct GNUNET_TESTBED_Host *) * host_list_size); +} + + +/** + * Marks a host as registered with a controller + * + * @param host the host to mark + * @param controller the controller at which this host is registered + */ +void +GNUNET_TESTBED_mark_host_registered_at_ (struct GNUNET_TESTBED_Host *host, + const struct GNUNET_TESTBED_Controller + *const controller) +{ + struct RegisteredController *rc; + + for (rc = host->rc_head; NULL != rc; rc = rc->next) + { + if (controller == rc->controller) /* already registered at controller */ + { + GNUNET_break (0); + return; + } + } + rc = GNUNET_malloc (sizeof (struct RegisteredController)); + rc->controller = controller; + GNUNET_CONTAINER_DLL_insert_tail (host->rc_head, host->rc_tail, rc); +} + + +/** + * Checks whether a host has been registered + * + * @param host the host to check + * @param controller the controller at which host's registration is checked + * @return GNUNET_YES if registered; GNUNET_NO if not + */ +int +GNUNET_TESTBED_is_host_registered_ (const struct GNUNET_TESTBED_Host *host, + const struct GNUNET_TESTBED_Controller + *const controller) +{ + struct RegisteredController *rc; + + for (rc = host->rc_head; NULL != rc; rc = rc->next) + { + if (controller == rc->controller) /* already registered at controller */ + { + return GNUNET_YES; + } + } + return GNUNET_NO; +} + + +/** + * The handle for whether a host is habitable or not + */ +struct GNUNET_TESTBED_HostHabitableCheckHandle +{ + /** + * The host to check + */ + const struct GNUNET_TESTBED_Host *host; + + /* /\** */ + /* * the configuration handle to lookup the path of the testbed helper */ + /* *\/ */ + /* const struct GNUNET_CONFIGURATION_Handle *cfg; */ + + /** + * The callback to call once we have the status + */ + GNUNET_TESTBED_HostHabitableCallback cb; + + /** + * The callback closure + */ + void *cb_cls; + + /** + * The process handle for the SSH process + */ + struct GNUNET_OS_Process *auxp; + + /** + * The SSH destination address string + */ + char *ssh_addr; + + /** + * The destination port string + */ + char *portstr; + + /** + * The path for hte testbed helper binary + */ + char *helper_binary_path; + + /** + * Task id for the habitability check task + */ + GNUNET_SCHEDULER_TaskIdentifier habitability_check_task; + + /** + * How long we wait before checking the process status. Should grow + * exponentially + */ + struct GNUNET_TIME_Relative wait_time; + +}; + + +/** + * Task for checking whether a host is habitable or not + * + * @param cls GNUNET_TESTBED_HostHabitableCheckHandle + * @param tc the scheduler task context + */ +static void +habitability_check (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct GNUNET_TESTBED_HostHabitableCheckHandle *h = cls; + void *cb_cls; + GNUNET_TESTBED_HostHabitableCallback cb; + const struct GNUNET_TESTBED_Host *host; + unsigned long code; + enum GNUNET_OS_ProcessStatusType type; + int ret; + + h->habitability_check_task = GNUNET_SCHEDULER_NO_TASK; + ret = GNUNET_OS_process_status (h->auxp, &type, &code); + if (GNUNET_SYSERR == ret) + { + GNUNET_break (0); + ret = GNUNET_NO; + goto call_cb; + } + if (GNUNET_NO == ret) + { + h->wait_time = GNUNET_TIME_STD_BACKOFF (h->wait_time); + h->habitability_check_task = + GNUNET_SCHEDULER_add_delayed (h->wait_time, &habitability_check, h); + return; + } + GNUNET_OS_process_destroy (h->auxp); + h->auxp = NULL; + ret = (0 != code) ? GNUNET_NO : GNUNET_YES; + +call_cb: + GNUNET_free (h->ssh_addr); + GNUNET_free (h->portstr); + GNUNET_free (h->helper_binary_path); + if (NULL != h->auxp) + GNUNET_OS_process_destroy (h->auxp); + cb = h->cb; + cb_cls = h->cb_cls; + host = h->host; + GNUNET_free (h); + if (NULL != cb) + cb (cb_cls, host, ret); } /** - * Run a given helper process at the given host. Communication - * with the helper will be via GNUnet messages on stdin/stdout. - * Runs the process via 'ssh' at the specified host, or locally. - * Essentially an SSH-wrapper around the 'gnunet_helper_lib.h' API. - * - * @param host host to use, use "NULL" for localhost - * @param binary_argv binary name and command-line arguments to give to the binary - * @param cb function to call for messages received from the binary - * @param cb_cls closure for cb - * @return handle to terminate the command, NULL on error + * Checks whether a host can be used to start testbed service + * + * @param host the host to check + * @param config the configuration handle to lookup the path of the testbed + * helper + * @param cb the callback to call to inform about habitability of the given host + * @param cb_cls the closure for the callback + * @return NULL upon any error or a handle which can be passed to + * GNUNET_TESTBED_is_host_habitable_cancel() */ -struct GNUNET_HELPER_Handle * -GNUNET_TESTBED_host_run_ (struct GNUNET_TESTBED_Host *host, - char *const binary_argv[], - GNUNET_SERVER_MessageTokenizerCallback cb, void *cb_cls) +struct GNUNET_TESTBED_HostHabitableCheckHandle * +GNUNET_TESTBED_is_host_habitable (const struct GNUNET_TESTBED_Host *host, + const struct GNUNET_CONFIGURATION_Handle + *config, + GNUNET_TESTBED_HostHabitableCallback cb, + void *cb_cls) { - /* FIXME: decide on the SSH command line, prepend it and - run GNUNET_HELPER_start with the modified binary_name and binary_argv! */ - GNUNET_break (0); - return NULL; + struct GNUNET_TESTBED_HostHabitableCheckHandle *h; + char *remote_args[11]; + const char *hostname; + unsigned int argp; + + h = GNUNET_malloc (sizeof (struct GNUNET_TESTBED_HostHabitableCheckHandle)); + h->cb = cb; + h->cb_cls = cb_cls; + h->host = host; + hostname = (NULL == host->hostname) ? "127.0.0.1" : host->hostname; + if (NULL == host->username) + h->ssh_addr = GNUNET_strdup (hostname); + else + GNUNET_asprintf (&h->ssh_addr, "%s@%s", host->username, hostname); + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_string (config, "testbed", + "HELPER_BINARY_PATH", + &h->helper_binary_path)) + h->helper_binary_path = + GNUNET_OS_get_libexec_binary_path (HELPER_TESTBED_BINARY); + argp = 0; + remote_args[argp++] = "ssh"; + GNUNET_asprintf (&h->portstr, "%u", host->port); + remote_args[argp++] = "-p"; + remote_args[argp++] = h->portstr; + remote_args[argp++] = "-o"; + remote_args[argp++] = "BatchMode=yes"; + remote_args[argp++] = "-o"; + remote_args[argp++] = "NoHostAuthenticationForLocalhost=yes"; + remote_args[argp++] = h->ssh_addr; + remote_args[argp++] = "stat"; + remote_args[argp++] = h->helper_binary_path; + remote_args[argp++] = NULL; + GNUNET_assert (argp == 11); + h->auxp = + GNUNET_OS_start_process_vap (GNUNET_NO, GNUNET_OS_INHERIT_STD_ERR, NULL, + NULL, "ssh", remote_args); + if (NULL == h->auxp) + { + GNUNET_break (0); /* Cannot exec SSH? */ + GNUNET_free (h->ssh_addr); + GNUNET_free (h->portstr); + GNUNET_free (h->helper_binary_path); + GNUNET_free (h); + return NULL; + } + h->wait_time = GNUNET_TIME_STD_BACKOFF (h->wait_time); + h->habitability_check_task = + GNUNET_SCHEDULER_add_delayed (h->wait_time, &habitability_check, h); + return h; } +/** + * Function to cancel a request started using GNUNET_TESTBED_is_host_habitable() + * + * @param handle the habitability check handle + */ +void +GNUNET_TESTBED_is_host_habitable_cancel (struct + GNUNET_TESTBED_HostHabitableCheckHandle + *handle) +{ + GNUNET_SCHEDULER_cancel (handle->habitability_check_task); + (void) GNUNET_OS_process_kill (handle->auxp, SIGTERM); + (void) GNUNET_OS_process_wait (handle->auxp); + GNUNET_OS_process_destroy (handle->auxp); + GNUNET_free (handle->ssh_addr); + GNUNET_free (handle->portstr); + GNUNET_free (handle->helper_binary_path); + GNUNET_free (handle); +} + /* end of testbed_api_hosts.c */ diff --git a/src/testbed/testbed_api_hosts.h b/src/testbed/testbed_api_hosts.h index 401d4e0..c0f4290 100644 --- a/src/testbed/testbed_api_hosts.h +++ b/src/testbed/testbed_api_hosts.h @@ -23,16 +23,17 @@ * @brief internal API to access the 'hosts' subsystem * @author Christian Grothoff */ + #ifndef NEW_TESTING_API_HOSTS_H #define NEW_TESTING_API_HOSTS_H #include "gnunet_testbed_service.h" -#include "gnunet_helper_lib.h" +#include "testbed_helper.h" /** * Lookup a host by ID. - * + * * @param id global host ID assigned to the host; 0 is * reserved to always mean 'localhost' * @return handle to the host, NULL on error @@ -45,7 +46,7 @@ GNUNET_TESTBED_host_lookup_by_id_ (uint32_t id); * Create a host by ID; given this host handle, we could not * run peers at the host, but we can talk about the host * internally. - * + * * @param id global host ID assigned to the host; 0 is * reserved to always mean 'localhost' * @return handle to the host, NULL on error @@ -54,52 +55,105 @@ struct GNUNET_TESTBED_Host * GNUNET_TESTBED_host_create_by_id_ (uint32_t id); -/** - * Create a host to run peers and controllers on. This function is used - * if a peer learns about a host via IPC between controllers (and thus - * some higher-level controller has already determined the unique IDs). - * - * @param id global host ID assigned to the host; 0 is - * reserved to always mean 'localhost' - * @param hostname name of the host, use "NULL" for localhost - * @param username username to use for the login; may be NULL - * @param port port number to use for ssh; use 0 to let ssh decide - * @return handle to the host, NULL on error - */ -struct GNUNET_TESTBED_Host * -GNUNET_TESTBED_host_create_with_id_ (uint32_t id, - const char *hostname, - const char *username, - uint16_t port); - - /** * Obtain a host's unique global ID. - * + * * @param host handle to the host, NULL means 'localhost' * @return id global host ID assigned to the host (0 is * 'localhost', but then obviously not globally unique) */ uint32_t -GNUNET_TESTBED_host_get_id_ (struct GNUNET_TESTBED_Host *host); +GNUNET_TESTBED_host_get_id_ (const struct GNUNET_TESTBED_Host *host); /** - * Run a given helper process at the given host. Communication - * with the helper will be via GNUnet messages on stdin/stdout. - * Runs the process via 'ssh' at the specified host, or locally. - * Essentially an SSH-wrapper around the 'gnunet_helper_lib.h' API. - * - * @param host host to use, use "NULL" for localhost - * @param binary_argv binary name and command-line arguments to give to the binary - * @param cb function to call for messages received from the binary - * @param cb_cls closure for cb - * @return handle to terminate the command, NULL on error + * Obtain the host's username + * + * @param host handle to the host, NULL means 'localhost' + * @return username to login to the host + */ +const char * +GNUNET_TESTBED_host_get_username_ (const struct GNUNET_TESTBED_Host *host); + + +/** + * Obtain the host's ssh port + * + * @param host handle to the host, NULL means 'localhost' + * @return username to login to the host */ -struct GNUNET_HELPER_Handle * -GNUNET_TESTBED_host_run_ (struct GNUNET_TESTBED_Host *host, - char *const binary_argv[], - GNUNET_SERVER_MessageTokenizerCallback cb, void *cb_cls); +uint16_t +GNUNET_TESTBED_host_get_ssh_port_ (const struct GNUNET_TESTBED_Host *host); + + +/** + * Opaque wrapper around GNUNET_HELPER_Handle + */ +struct GNUNET_TESTBED_HelperHandle; + + +/* /\** */ +/* * Run a given helper process at the given host. Communication */ +/* * with the helper will be via GNUnet messages on stdin/stdout. */ +/* * Runs the process via 'ssh' at the specified host, or locally. */ +/* * Essentially an SSH-wrapper around the 'gnunet_helper_lib.h' API. */ +/* * */ +/* * @param controller_ip the ip address of the controller. Will be set as TRUSTED */ +/* * host when starting testbed controller at host */ +/* * @param host host to use, use "NULL" for localhost */ +/* * @param binary_argv binary name and command-line arguments to give to the */ +/* * binary */ +/* * @param cfg template configuration to use for the remote controller; the */ +/* * remote controller will be started with a slightly modified */ +/* * configuration (port numbers, unix domain sockets and service home */ +/* * values are changed as per TESTING library on the remote host) */ +/* * @param cb the callback to run when helper process dies; cannot be NULL */ +/* * @param cb_cls the closure for the above callback */ +/* * @return handle to terminate the command, NULL on error */ +/* *\/ */ +/* struct GNUNET_TESTBED_HelperHandle * */ +/* GNUNET_TESTBED_host_run_ (const char *controller_ip, */ +/* const struct GNUNET_TESTBED_Host *host, */ +/* const struct GNUNET_CONFIGURATION_Handle *cfg, */ +/* GNUNET_HELPER_ExceptionCallback cb, */ +/* void *cb_cls); */ + + + +/* /\** */ +/* * Stops a helper in the HelperHandle using GNUNET_HELPER_stop */ +/* * */ +/* * @param handle the handle returned from GNUNET_TESTBED_host_start_ */ +/* *\/ */ +/* void */ +/* GNUNET_TESTBED_host_stop_ (struct GNUNET_TESTBED_HelperHandle *handle); */ + + +/** + * Marks a host as registered with a controller + * + * @param host the host to mark + * @param controller the controller at which this host is registered + */ +void +GNUNET_TESTBED_mark_host_registered_at_ (struct GNUNET_TESTBED_Host *host, + const struct GNUNET_TESTBED_Controller + *controller); + + +/** + * Checks whether a host has been registered with the given controller + * + * @param host the host to check + * @param controller the controller at which host's registration is checked + * @return GNUNET_YES if registered; GNUNET_NO if not + */ +int +GNUNET_TESTBED_is_host_registered_ (const struct GNUNET_TESTBED_Host *host, + const struct GNUNET_TESTBED_Controller + *controller); + + #endif /* end of testbed_api_hosts.h */ diff --git a/src/testbed/testbed_api_operations.c b/src/testbed/testbed_api_operations.c index c98998b..3e7eb91 100644 --- a/src/testbed/testbed_api_operations.c +++ b/src/testbed/testbed_api_operations.c @@ -27,6 +27,89 @@ #include "testbed_api_operations.h" +/** + * An entry in the operation queue + */ +struct QueueEntry +{ + /** + * The next DLL pointer + */ + struct QueueEntry *next; + + /** + * The prev DLL pointer + */ + struct QueueEntry *prev; + + /** + * The operation this entry holds + */ + struct GNUNET_TESTBED_Operation *op; + + /** + * How many units of resources does the operation need + */ + unsigned int nres; +}; + + +/** + * Queue of operations where we can only support a certain + * number of concurrent operations of a particular type. + */ +struct OperationQueue +{ + /** + * The head of the operation queue + */ + struct QueueEntry *head; + + /** + * The tail of the operation queue + */ + struct QueueEntry *tail; + + /** + * Number of operations that are currently active in this queue. + */ + unsigned int active; + + /** + * Max number of operations which can be active at any time in this queue + */ + unsigned int max_active; + +}; + + +/** + * Operation state + */ +enum OperationState +{ + /** + * The operation is just created and is in initial state + */ + OP_STATE_INIT, + + /** + * The operation is currently waiting for resources + */ + OP_STATE_WAITING, + + /** + * The operation is ready to be started + */ + OP_STATE_READY, + + /** + * The operation has started + */ + OP_STATE_STARTED +}; + + /** * Opaque handle to an abstract operation to be executed by the testing framework. */ @@ -42,33 +125,125 @@ struct GNUNET_TESTBED_Operation * not have been started yet). */ OperationRelease release; - + /** * Closure for callbacks. */ void *cb_cls; - // FIXME! + /** + * Array of operation queues this Operation belongs to. + */ + struct OperationQueue **queues; + + /** + * Array of number resources an operation need from each queue. This numbers + * in this array should correspond to the queues array + */ + unsigned int *nres; + + /** + * The id of the task which calls OperationStart for this operation + */ + GNUNET_SCHEDULER_TaskIdentifier start_task_id; + + /** + * Number of queues in the operation queues array + */ + unsigned int nqueues; + + /** + * The state of the operation + */ + enum OperationState state; }; /** - * Queue of operations where we can only support a certain - * number of concurrent operations of a particular type. + * Task for calling OperationStart on operation + * + * @param cls the Operation + * @param tc the TaskContext from scheduler */ -struct OperationQueue +static void +call_start (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { + struct GNUNET_TESTBED_Operation *op = cls; - /** - * Maximum number of operationst that can be concurrently - * active in this queue. - */ - unsigned int max_active; + op->start_task_id = GNUNET_SCHEDULER_NO_TASK; + op->state = OP_STATE_STARTED; + if (NULL != op->start) + op->start (op->cb_cls); +} - // FIXME! -}; +/** + * Checks for the readiness of an operation and schedules a operation start task + * + * @param op the operation + */ +static void +check_readiness (struct GNUNET_TESTBED_Operation *op) +{ + unsigned int i; + + GNUNET_assert (GNUNET_SCHEDULER_NO_TASK == op->start_task_id); + for (i = 0; i < op->nqueues; i++) + { + GNUNET_assert (0 < op->nres[i]); + if ((op->queues[i]->active + op->nres[i]) > op->queues[i]->max_active) + return; + } + for (i = 0; i < op->nqueues; i++) + op->queues[i]->active += op->nres[i]; + op->state = OP_STATE_READY; + op->start_task_id = GNUNET_SCHEDULER_add_now (&call_start, op); +} + + +/** + * Defers a ready to be executed operation back to waiting + * + * @param op the operation to defer + */ +static void +defer (struct GNUNET_TESTBED_Operation *op) +{ + unsigned int i; + + GNUNET_assert (OP_STATE_READY == op->state); + GNUNET_assert (GNUNET_SCHEDULER_NO_TASK != op->start_task_id); + GNUNET_SCHEDULER_cancel (op->start_task_id); + op->start_task_id = GNUNET_SCHEDULER_NO_TASK; + for (i = 0; i < op->nqueues; i++) + op->queues[i]->active--; + op->state = OP_STATE_WAITING; +} + + +/** + * Create an 'operation' to be performed. + * + * @param cls closure for the callbacks + * @param start function to call to start the operation + * @param release function to call to close down the operation + * @return handle to the operation + */ +struct GNUNET_TESTBED_Operation * +GNUNET_TESTBED_operation_create_ (void *cls, OperationStart start, + OperationRelease release) +{ + struct GNUNET_TESTBED_Operation *op; + + op = GNUNET_malloc (sizeof (struct GNUNET_TESTBED_Operation)); + op->start = start; + op->state = OP_STATE_INIT; + op->release = release; + op->cb_cls = cls; + op->start_task_id = GNUNET_SCHEDULER_NO_TASK; + return op; +} /** @@ -98,97 +273,188 @@ GNUNET_TESTBED_operation_queue_create_ (unsigned int max_active) void GNUNET_TESTBED_operation_queue_destroy_ (struct OperationQueue *queue) { - GNUNET_break (0); + GNUNET_break (NULL == queue->head); + GNUNET_break (NULL == queue->tail); GNUNET_free (queue); } /** - * Add an operation to a queue. An operation can be in multiple - * queues at once. Once all queues permit the operation to become - * active, the operation will be activated. The actual activation - * will occur in a separate task (thus allowing multiple queue - * insertions to be made without having the first one instantly - * trigger the operation if the first queue has sufficient - * resources). + * Function to reset the maximum number of operations in the given queue. If + * max_active is lesser than the number of currently active operations, the + * active operations are not stopped immediately. + * + * @param queue the operation queue which has to be modified + * @param max_active the new maximum number of active operations + */ +void +GNUNET_TESTBED_operation_queue_reset_max_active_ (struct OperationQueue *queue, + unsigned int max_active) +{ + struct QueueEntry *entry; + + queue->max_active = max_active; + /* if (queue->active >= queue->max_active) */ + /* return; */ + + entry = queue->head; + while ((queue->active > queue->max_active) && (NULL != entry)) + { + if (entry->op->state == OP_STATE_READY) + defer (entry->op); + entry = entry->next; + } + + entry = queue->head; + while ((NULL != entry) && (queue->active < queue->max_active)) + { + if (OP_STATE_WAITING == entry->op->state) + check_readiness (entry->op); + entry = entry->next; + } +} + + +/** + * Add an operation to a queue. An operation can be in multiple queues at + * once. Once the operation is inserted into all the queues + * GNUNET_TESTBED_operation_begin_wait_() has to be called to actually start + * waiting for the operation to become active. * * @param queue queue to add the operation to * @param operation operation to add to the queue + * @param nres the number of units of the resources of queue needed by the + * operation. Should be greater than 0. */ void -GNUNET_TESTBED_operation_queue_insert_ (struct OperationQueue *queue, - struct GNUNET_TESTBED_Operation *operation) +GNUNET_TESTBED_operation_queue_insert2_ (struct OperationQueue *queue, + struct GNUNET_TESTBED_Operation + *operation, unsigned int nres) { - GNUNET_break (0); + struct QueueEntry *entry; + unsigned int qsize; + + GNUNET_assert (0 < nres); + entry = GNUNET_malloc (sizeof (struct QueueEntry)); + entry->op = operation; + entry->nres = nres; + GNUNET_CONTAINER_DLL_insert_tail (queue->head, queue->tail, entry); + qsize = operation->nqueues; + GNUNET_array_append (operation->queues, operation->nqueues, queue); + GNUNET_array_append (operation->nres, qsize, nres); + GNUNET_assert (qsize == operation->nqueues); } /** - * Remove an operation from a queue. This can be because the - * oeration was active and has completed (and the resources have - * been released), or because the operation was cancelled and - * thus scheduling the operation is no longer required. + * Add an operation to a queue. An operation can be in multiple queues at + * once. Once the operation is inserted into all the queues + * GNUNET_TESTBED_operation_begin_wait_() has to be called to actually start + * waiting for the operation to become active. The operation is assumed to take + * 1 queue resource. Use GNUNET_TESTBED_operation_queue_insert2_() if it + * requires more than 1 * * @param queue queue to add the operation to * @param operation operation to add to the queue */ void -GNUNET_TESTBED_operation_queue_remove_ (struct OperationQueue *queue, - struct GNUNET_TESTBED_Operation *operation) +GNUNET_TESTBED_operation_queue_insert_ (struct OperationQueue *queue, + struct GNUNET_TESTBED_Operation + *operation) { - GNUNET_break (0); + return GNUNET_TESTBED_operation_queue_insert2_ (queue, operation, 1); } /** - * An operation is 'done' (was cancelled or finished); remove - * it from the queues and release associated resources. + * Marks the given operation as waiting on the queues. Once all queues permit + * the operation to become active, the operation will be activated. The actual + * activation will occur in a separate task (thus allowing multiple queue + * insertions to be made without having the first one instantly trigger the + * operation if the first queue has sufficient resources). * - * @param operation operation that finished + * @param operation the operation to marks as waiting */ -static void -operation_release (struct GNUNET_TESTBED_Operation *operation) +void +GNUNET_TESTBED_operation_begin_wait_ (struct GNUNET_TESTBED_Operation + *operation) { - // call operation->release, remove from queues - GNUNET_break (0); + GNUNET_assert (GNUNET_SCHEDULER_NO_TASK == operation->start_task_id); + operation->state = OP_STATE_WAITING; + check_readiness (operation); } /** - * Cancel a pending operation. Releases all resources - * of the operation and will ensure that no event - * is generated for the operation. Does NOT guarantee - * that the operation will be fully undone (or that - * nothing ever happened). - * - * @param operation operation to cancel + * Remove an operation from a queue. This can be because the + * oeration was active and has completed (and the resources have + * been released), or because the operation was cancelled and + * thus scheduling the operation is no longer required. + * + * @param queue queue to add the operation to + * @param operation operation to add to the queue */ void -GNUNET_TESTBED_operation_cancel (struct GNUNET_TESTBED_Operation *operation) +GNUNET_TESTBED_operation_queue_remove_ (struct OperationQueue *queue, + struct GNUNET_TESTBED_Operation + *operation) { - // test that operation had not yet generated an event - GNUNET_break (0); - operation_release (operation); + struct QueueEntry *entry; + struct QueueEntry *entry2; + + for (entry = queue->head; NULL != entry; entry = entry->next) + if (entry->op == operation) + break; + GNUNET_assert (NULL != entry); + GNUNET_assert (0 < entry->nres); + switch (operation->state) + { + case OP_STATE_INIT: + case OP_STATE_WAITING: + break; + case OP_STATE_READY: + case OP_STATE_STARTED: + GNUNET_assert (0 != queue->active); + GNUNET_assert (queue->active >= entry->nres); + queue->active -= entry->nres; + break; + } + entry2 = entry->next; + GNUNET_CONTAINER_DLL_remove (queue->head, queue->tail, entry); + GNUNET_free (entry); + for (; NULL != entry2; entry2 = entry2->next) + if (OP_STATE_WAITING == entry2->op->state) + break; + if (NULL == entry2) + return; + check_readiness (entry2->op); } /** - * Signal that the information from an operation has been fully - * processed. This function MUST be called for each event - * of type 'operation_finished' to fully remove the operation - * from the operation queue. After calling this function, the - * 'op_result' becomes invalid (!). - * - * @param operation operation to signal completion for + * An operation is 'done' (was cancelled or finished); remove + * it from the queues and release associated resources. + * + * @param operation operation that finished */ void -GNUNET_TESTBED_operation_done (struct GNUNET_TESTBED_Operation *operation) +GNUNET_TESTBED_operation_release_ (struct GNUNET_TESTBED_Operation *operation) { - // test that operation was started and had generated an event - GNUNET_break (0); - operation_release (operation); + unsigned int i; + + if (GNUNET_SCHEDULER_NO_TASK != operation->start_task_id) + { + GNUNET_SCHEDULER_cancel (operation->start_task_id); + operation->start_task_id = GNUNET_SCHEDULER_NO_TASK; + } + for (i = 0; i < operation->nqueues; i++) + GNUNET_TESTBED_operation_queue_remove_ (operation->queues[i], operation); + GNUNET_free (operation->queues); + GNUNET_free (operation->nres); + if (NULL != operation->release) + operation->release (operation->cb_cls); + GNUNET_free (operation); } - /* end of testbed_api_operations.c */ diff --git a/src/testbed/testbed_api_operations.h b/src/testbed/testbed_api_operations.h index 4c888d5..61b45e2 100644 --- a/src/testbed/testbed_api_operations.h +++ b/src/testbed/testbed_api_operations.h @@ -59,20 +59,62 @@ GNUNET_TESTBED_operation_queue_destroy_ (struct OperationQueue *queue); /** - * Add an operation to a queue. An operation can be in multiple - * queues at once. Once all queues permit the operation to become - * active, the operation will be activated. The actual activation - * will occur in a separate task (thus allowing multiple queue - * insertions to be made without having the first one instantly - * trigger the operation if the first queue has sufficient - * resources). + * Function to reset the maximum number of operations in the given queue. If + * max_active is lesser than the number of currently active operations, the + * active operations are not stopped immediately. + * + * @param queue the operation queue which has to be modified + * @param max_active the new maximum number of active operations + */ +void +GNUNET_TESTBED_operation_queue_reset_max_active_ (struct OperationQueue *queue, + unsigned int max_active); + + +/** + * Add an operation to a queue. An operation can be in multiple queues at + * once. Once the operation is inserted into all the queues + * GNUNET_TESTBED_operation_begin_wait_() has to be called to actually start + * waiting for the operation to become active. + * + * @param queue queue to add the operation to + * @param operation operation to add to the queue + * @param nres the number of units of the resources of queue needed by the + * operation. Should be greater than 0. + */ +void +GNUNET_TESTBED_operation_queue_insert2_ (struct OperationQueue *queue, + struct GNUNET_TESTBED_Operation + *operation, unsigned int nres); + + +/** + * Add an operation to a queue. An operation can be in multiple queues at + * once. Once the operation is inserted into all the queues + * GNUNET_TESTBED_operation_begin_wait_() has to be called to actually start + * waiting for the operation to become active. * * @param queue queue to add the operation to * @param operation operation to add to the queue */ void GNUNET_TESTBED_operation_queue_insert_ (struct OperationQueue *queue, - struct GNUNET_TESTBED_Operation *operation); + struct GNUNET_TESTBED_Operation + *operation); + + +/** + * Marks the given operation as waiting on the queues. Once all queues permit + * the operation to become active, the operation will be activated. The actual + * activation will occur in a separate task (thus allowing multiple queue + * insertions to be made without having the first one instantly trigger the + * operation if the first queue has sufficient resources). + * + * @param operation the operation to marks as waiting + */ +void +GNUNET_TESTBED_operation_begin_wait_ (struct GNUNET_TESTBED_Operation + *operation); /** @@ -86,7 +128,8 @@ GNUNET_TESTBED_operation_queue_insert_ (struct OperationQueue *queue, */ void GNUNET_TESTBED_operation_queue_remove_ (struct OperationQueue *queue, - struct GNUNET_TESTBED_Operation *operation); + struct GNUNET_TESTBED_Operation + *operation); @@ -94,8 +137,10 @@ GNUNET_TESTBED_operation_queue_remove_ (struct OperationQueue *queue, * Function to call to start an operation once all * queues the operation is part of declare that the * operation can be activated. + * + * @param cls the closure from GNUNET_TESTBED_operation_create_() */ -typedef void (*OperationStart)(void *cls); +typedef void (*OperationStart) (void *cls); /** @@ -107,9 +152,11 @@ typedef void (*OperationStart)(void *cls); * a callback to the 'OperationStart' preceeds the call to * 'OperationRelease'. Implementations of this function are expected * to clean up whatever state is in 'cls' and release all resources - * associated with the operation. + * associated with the operation. + * + * @param cls the closure from GNUNET_TESTBED_operation_create_() */ -typedef void (*OperationRelease)(void *cls); +typedef void (*OperationRelease) (void *cls); /** @@ -118,14 +165,21 @@ typedef void (*OperationRelease)(void *cls); * @param cls closure for the callbacks * @param start function to call to start the operation * @param release function to call to close down the operation - * @param ... FIXME * @return handle to the operation */ struct GNUNET_TESTBED_Operation * -GNUNET_TESTBED_operation_create_ (void *cls, - OperationStart start, - OperationRelease release, - ...); +GNUNET_TESTBED_operation_create_ (void *cls, OperationStart start, + OperationRelease release); + + +/** + * An operation is 'done' (was cancelled or finished); remove + * it from the queues and release associated resources. + * + * @param operation operation that finished + */ +void +GNUNET_TESTBED_operation_release_ (struct GNUNET_TESTBED_Operation *operation); #endif diff --git a/src/testbed/testbed_api_peers.c b/src/testbed/testbed_api_peers.c index 7ee0dd1..908428a 100644 --- a/src/testbed/testbed_api_peers.c +++ b/src/testbed/testbed_api_peers.c @@ -23,118 +23,380 @@ * @brief management of the knowledge about peers in this library * (we know the peer ID, its host, pending operations, etc.) * @author Christian Grothoff + * @author Sree Harsha Totakura */ + #include "platform.h" #include "testbed_api_peers.h" +#include "testbed_api.h" +#include "testbed.h" +#include "testbed_api_hosts.h" +#include "testbed_api_operations.h" + +/** + * Function to call to start a peer_create type operation once all + * queues the operation is part of declare that the + * operation can be activated. + * + * @param cls the closure from GNUNET_TESTBED_operation_create_() + */ +static void +opstart_peer_create (void *cls) +{ + struct OperationContext *opc = cls; + struct PeerCreateData *data; + struct GNUNET_TESTBED_PeerCreateMessage *msg; + char *config; + char *xconfig; + size_t c_size; + size_t xc_size; + uint16_t msize; + + GNUNET_assert (OP_PEER_CREATE == opc->type); + data = opc->data; + GNUNET_assert (NULL != data); + GNUNET_assert (NULL != data->peer); + opc->state = OPC_STATE_STARTED; + config = GNUNET_CONFIGURATION_serialize (data->cfg, &c_size); + xc_size = GNUNET_TESTBED_compress_config_ (config, c_size, &xconfig); + GNUNET_free (config); + msize = xc_size + sizeof (struct GNUNET_TESTBED_PeerCreateMessage); + msg = GNUNET_realloc (xconfig, msize); + memmove (&msg[1], msg, xc_size); + msg->header.size = htons (msize); + msg->header.type = htons (GNUNET_MESSAGE_TYPE_TESTBED_CREATE_PEER); + msg->operation_id = GNUNET_htonll (opc->id); + msg->host_id = htonl (GNUNET_TESTBED_host_get_id_ (data->peer->host)); + msg->peer_id = htonl (data->peer->unique_id); + msg->config_size = htonl (c_size); + GNUNET_CONTAINER_DLL_insert_tail (opc->c->ocq_head, opc->c->ocq_tail, opc); + GNUNET_TESTBED_queue_message_ (opc->c, &msg->header); +} /** - * Details about a peer; kept in a separate struct to avoid bloating - * memory consumption everywhere... + * Callback which will be called when peer_create type operation is released + * + * @param cls the closure from GNUNET_TESTBED_operation_create_() */ -struct PeerDetails +static void +oprelease_peer_create (void *cls) { - /** - * Configuration of the peer; NULL if we are not sure what the peer's correct - * configuration actually is; non-NULL if this peer is controlled by this - * process. - */ - struct GNUNET_CONFIGURATION_Handle *cfg; + struct OperationContext *opc = cls; + + switch (opc->state) + { + case OPC_STATE_STARTED: + GNUNET_CONTAINER_DLL_remove (opc->c->ocq_head, opc->c->ocq_tail, opc); + /* No break we continue flow */ + case OPC_STATE_INIT: + GNUNET_free (((struct PeerCreateData *) opc->data)->peer); + GNUNET_free (opc->data); + break; + case OPC_STATE_FINISHED: + break; + } + GNUNET_free (opc); +} - /** - * If this process has started this peer's ARM process, this is the handle - * to the 'gnunet-service-arm' process of the peer. - */ - struct GNUNET_OS_Process *arm; - - // ... -}; +/** + * Function called when a peer destroy operation is ready + * + * @param cls the closure from GNUNET_TESTBED_operation_create_() + */ +static void +opstart_peer_destroy (void *cls) +{ + struct OperationContext *opc = cls; + struct GNUNET_TESTBED_Peer *peer; + struct GNUNET_TESTBED_PeerDestroyMessage *msg; + + GNUNET_assert (OP_PEER_DESTROY == opc->type); + peer = opc->data; + GNUNET_assert (NULL != peer); + opc->state = OPC_STATE_STARTED; + msg = GNUNET_malloc (sizeof (struct GNUNET_TESTBED_PeerDestroyMessage)); + msg->header.size = htons (sizeof (struct GNUNET_TESTBED_PeerDestroyMessage)); + msg->header.type = htons (GNUNET_MESSAGE_TYPE_TESTBED_DESTROY_PEER); + msg->peer_id = htonl (peer->unique_id); + msg->operation_id = GNUNET_htonll (opc->id); + GNUNET_CONTAINER_DLL_insert_tail (opc->c->ocq_head, opc->c->ocq_tail, opc); + GNUNET_TESTBED_queue_message_ (peer->controller, &msg->header); +} /** - * A peer controlled by the testing framework. A peer runs - * at a particular host. - */ -struct GNUNET_TESTBED_Peer + * Callback which will be called when peer_create type operation is released + * + * @param cls the closure from GNUNET_TESTBED_operation_create_() + */ +static void +oprelease_peer_destroy (void *cls) { - /** - * Our controller context (not necessarily the controller - * that is responsible for starting/running the peer!). - */ - struct GNUNET_TESTBED_Controller *controller; - - /** - * Which host does this peer run on? - */ - struct GNUENT_TESTING_Host *host; - - /** - * Globally unique ID of the peer. - */ - uint32_t unique_id; - - /** - * Internals of the peer for the controlling process; NULL if - * this process is not controlling this peer. - */ - struct PeerDetails *details; - -}; + struct OperationContext *opc = cls; + + if (OPC_STATE_FINISHED != opc->state) + GNUNET_CONTAINER_DLL_remove (opc->c->ocq_head, opc->c->ocq_tail, opc); + GNUNET_free (opc); +} /** - * Lookup a peer by ID. - * - * @param id global peer ID assigned to the peer - * @return handle to the host, NULL on error + * Function called when a peer start operation is ready + * + * @param cls the closure from GNUNET_TESTBED_operation_create_() */ -struct GNUNET_TESTBED_Peer * -GNUNET_TESTBED_peer_lookup_by_id_ (uint32_t id) +static void +opstart_peer_start (void *cls) { - GNUNET_break (0); - return NULL; + struct OperationContext *opc = cls; + struct GNUNET_TESTBED_PeerStartMessage *msg; + struct PeerEventData *data; + struct GNUNET_TESTBED_Peer *peer; + + GNUNET_assert (OP_PEER_START == opc->type); + GNUNET_assert (NULL != opc->data); + data = opc->data; + GNUNET_assert (NULL != data->peer); + peer = data->peer; + GNUNET_assert ((PS_CREATED == peer->state) || (PS_STOPPED == peer->state)); + opc->state = OPC_STATE_STARTED; + msg = GNUNET_malloc (sizeof (struct GNUNET_TESTBED_PeerStartMessage)); + msg->header.size = htons (sizeof (struct GNUNET_TESTBED_PeerStartMessage)); + msg->header.type = htons (GNUNET_MESSAGE_TYPE_TESTBED_START_PEER); + msg->peer_id = htonl (peer->unique_id); + msg->operation_id = GNUNET_htonll (opc->id); + GNUNET_CONTAINER_DLL_insert_tail (opc->c->ocq_head, opc->c->ocq_tail, opc); + GNUNET_TESTBED_queue_message_ (peer->controller, &msg->header); } /** - * Create the given peer at the specified host using the given - * controller. If the given controller is not running on the target - * host, it should find or create a controller at the target host and - * delegate creating the peer. Explicit delegation paths can be setup - * using 'GNUNET_TESTBED_controller_link'. If no explicit delegation - * path exists, a direct link with a subordinate controller is setup - * for the first delegated peer to a particular host; the subordinate - * controller is then destroyed once the last peer that was delegated - * to the remote host is stopped. This function is used in particular - * if some other controller has already assigned a unique ID to the - * peer. + * Callback which will be called when peer start type operation is released * - * Creating the peer only creates the handle to manipulate and further - * configure the peer; use "GNUNET_TESTBED_peer_start" and - * "GNUNET_TESTBED_peer_stop" to actually start/stop the peer's - * processes. + * @param cls the closure from GNUNET_TESTBED_operation_create_() + */ +static void +oprelease_peer_start (void *cls) +{ + struct OperationContext *opc = cls; + + if (OPC_STATE_FINISHED != opc->state) + { + GNUNET_free (opc->data); + GNUNET_CONTAINER_DLL_remove (opc->c->ocq_head, opc->c->ocq_tail, opc); + } + GNUNET_free (opc); +} + + +/** + * Function called when a peer stop operation is ready * - * Note that the given configuration will be adjusted by the - * controller to avoid port/path conflicts with other peers. - * The "final" configuration can be obtained using - * 'GNUNET_TESTBED_peer_get_information'. + * @param cls the closure from GNUNET_TESTBED_operation_create_() + */ +static void +opstart_peer_stop (void *cls) +{ + struct OperationContext *opc = cls; + struct GNUNET_TESTBED_PeerStopMessage *msg; + struct PeerEventData *data; + struct GNUNET_TESTBED_Peer *peer; + + GNUNET_assert (NULL != opc->data); + data = opc->data; + GNUNET_assert (NULL != data->peer); + peer = data->peer; + GNUNET_assert (PS_STARTED == peer->state); + opc->state = OPC_STATE_STARTED; + msg = GNUNET_malloc (sizeof (struct GNUNET_TESTBED_PeerStopMessage)); + msg->header.type = htons (GNUNET_MESSAGE_TYPE_TESTBED_STOP_PEER); + msg->header.size = htons (sizeof (struct GNUNET_TESTBED_PeerStopMessage)); + msg->peer_id = htonl (peer->unique_id); + msg->operation_id = GNUNET_htonll (opc->id); + GNUNET_CONTAINER_DLL_insert_tail (opc->c->ocq_head, opc->c->ocq_tail, opc); + GNUNET_TESTBED_queue_message_ (peer->controller, &msg->header); +} + + +/** + * Callback which will be called when peer stop type operation is released * - * @param unique_id unique ID for this peer - * @param controller controller process to use - * @param host host to run the peer on - * @param cfg configuration to use for the peer - * @return handle to the peer (actual startup will happen asynchronously) + * @param cls the closure from GNUNET_TESTBED_operation_create_() + */ +static void +oprelease_peer_stop (void *cls) +{ + struct OperationContext *opc = cls; + + if (OPC_STATE_FINISHED != opc->state) + { + GNUNET_free (opc->data); + GNUNET_CONTAINER_DLL_remove (opc->c->ocq_head, opc->c->ocq_tail, opc); + } + GNUNET_free (opc); +} + + +/** + * Generate PeerGetConfigurationMessage + * + * @param peer_id the id of the peer whose information we have to get + * @param operation_id the ip of the operation that should be represented in the + * message + * @return the PeerGetConfigurationMessage + */ +struct GNUNET_TESTBED_PeerGetConfigurationMessage * +GNUNET_TESTBED_generate_peergetconfig_msg_ (uint32_t peer_id, + uint64_t operation_id) +{ + struct GNUNET_TESTBED_PeerGetConfigurationMessage *msg; + + msg = + GNUNET_malloc (sizeof + (struct GNUNET_TESTBED_PeerGetConfigurationMessage)); + msg->header.size = + htons (sizeof (struct GNUNET_TESTBED_PeerGetConfigurationMessage)); + msg->header.type = htons (GNUNET_MESSAGE_TYPE_TESTBED_GET_PEER_CONFIGURATION); + msg->peer_id = htonl (peer_id); + msg->operation_id = GNUNET_htonll (operation_id); + return msg; +} + + +/** + * Function called when a peer get information operation is ready + * + * @param cls the closure from GNUNET_TESTBED_operation_create_() + */ +static void +opstart_peer_getinfo (void *cls) +{ + struct OperationContext *opc = cls; + struct PeerInfoData *data; + struct GNUNET_TESTBED_PeerGetConfigurationMessage *msg; + + data = opc->data; + GNUNET_assert (NULL != data); + opc->state = OPC_STATE_STARTED; + msg = + GNUNET_TESTBED_generate_peergetconfig_msg_ (data->peer->unique_id, + opc->id); + GNUNET_CONTAINER_DLL_insert_tail (opc->c->ocq_head, opc->c->ocq_tail, opc); + GNUNET_TESTBED_queue_message_ (opc->c, &msg->header); +} + + +/** + * Callback which will be called when peer stop type operation is released + * + * @param cls the closure from GNUNET_TESTBED_operation_create_() + */ +static void +oprelease_peer_getinfo (void *cls) +{ + struct OperationContext *opc = cls; + struct GNUNET_TESTBED_PeerInformation *data; + + if (OPC_STATE_FINISHED != opc->state) + { + GNUNET_free_non_null (opc->data); + GNUNET_CONTAINER_DLL_remove (opc->c->ocq_head, opc->c->ocq_tail, opc); + } + else + { + data = opc->data; + GNUNET_assert (NULL != data); + switch (data->pit) + { + case GNUNET_TESTBED_PIT_CONFIGURATION: + GNUNET_CONFIGURATION_destroy (data->result.cfg); + break; + case GNUNET_TESTBED_PIT_IDENTITY: + GNUNET_free (data->result.id); + break; + default: + GNUNET_assert (0); /* We should never reach here */ + } + GNUNET_free (data); + } + GNUNET_free (opc); +} + + +/** + * Function called when a overlay connect operation is ready + * + * @param cls the closure from GNUNET_TESTBED_operation_create_() + */ +static void +opstart_overlay_connect (void *cls) +{ + struct OperationContext *opc = cls; + struct GNUNET_TESTBED_OverlayConnectMessage *msg; + struct OverlayConnectData *data; + + opc->state = OPC_STATE_STARTED; + data = opc->data; + GNUNET_assert (NULL != data); + data->tslot_index = GNUNET_TESTBED_get_tslot_ (opc->c, data); + data->tstart = GNUNET_TIME_absolute_get (); + msg = GNUNET_malloc (sizeof (struct GNUNET_TESTBED_OverlayConnectMessage)); + msg->header.size = + htons (sizeof (struct GNUNET_TESTBED_OverlayConnectMessage)); + msg->header.type = htons (GNUNET_MESSAGE_TYPE_TESTBED_OVERLAY_CONNECT); + msg->peer1 = htonl (data->p1->unique_id); + msg->peer2 = htonl (data->p2->unique_id); + msg->operation_id = GNUNET_htonll (opc->id); + msg->peer2_host_id = htonl (GNUNET_TESTBED_host_get_id_ (data->p2->host)); + GNUNET_CONTAINER_DLL_insert_tail (opc->c->ocq_head, opc->c->ocq_tail, opc); + GNUNET_TESTBED_queue_message_ (opc->c, &msg->header); +} + + +/** + * Callback which will be called when overlay connect operation is released + * + * @param cls the closure from GNUNET_TESTBED_operation_create_() + */ +static void +oprelease_overlay_connect (void *cls) +{ + struct OperationContext *opc = cls; + struct GNUNET_TIME_Relative duration; + struct OverlayConnectData *data; + + data = opc->data; + switch (opc->state) + { + case OPC_STATE_INIT: + break; + case OPC_STATE_STARTED: + (void) GNUNET_TESTBED_release_time_slot_ (opc->c, data->tslot_index, data); + GNUNET_CONTAINER_DLL_remove (opc->c->ocq_head, opc->c->ocq_tail, opc); + break; + case OPC_STATE_FINISHED: + duration = GNUNET_TIME_absolute_get_duration (data->tstart); + GNUNET_TESTBED_update_time_slot_ (opc->c, data->tslot_index, data, duration, + data->failed); + } + GNUNET_free (data); + GNUNET_free (opc); +} + + +/** + * Lookup a peer by ID. + * + * @param id global peer ID assigned to the peer + * @return handle to the host, NULL on error */ struct GNUNET_TESTBED_Peer * -GNUNET_TESTBED_peer_create_with_id_ (uint32_t unique_id, - struct GNUNET_TESTBED_Controller *controller, - struct GNUNET_TESTBED_Host *host, - const struct GNUNET_CONFIGURATION_Handle *cfg) +GNUNET_TESTBED_peer_lookup_by_id_ (uint32_t id) { - // FIXME: create locally or delegate... GNUNET_break (0); - return NULL; + return NULL; } @@ -160,70 +422,164 @@ GNUNET_TESTBED_peer_create_with_id_ (uint32_t unique_id, * 'GNUNET_TESTBED_peer_get_information'. * * @param controller controller process to use - * @param host host to run the peer on - * @param cfg configuration to use for the peer - * @return handle to the peer (actual startup will happen asynchronously) + * @param host host to run the peer on; cannot be NULL + * @param cfg Template configuration to use for the peer. Should exist until + * operation is cancelled or GNUNET_TESTBED_operation_done() is called + * @param cb the callback to call when the peer has been created + * @param cls the closure to the above callback + * @return the operation handle */ -struct GNUNET_TESTBED_Peer * +struct GNUNET_TESTBED_Operation * GNUNET_TESTBED_peer_create (struct GNUNET_TESTBED_Controller *controller, - struct GNUNET_TESTBED_Host *host, - const struct GNUNET_CONFIGURATION_Handle *cfg) + struct GNUNET_TESTBED_Host *host, + const struct GNUNET_CONFIGURATION_Handle *cfg, + GNUNET_TESTBED_PeerCreateCallback cb, void *cls) { + + struct GNUNET_TESTBED_Peer *peer; + struct PeerCreateData *data; + struct OperationContext *opc; static uint32_t id_gen; - return GNUNET_TESTBED_peer_create_with_id_ (++id_gen, - controller, - host, - cfg); + peer = GNUNET_malloc (sizeof (struct GNUNET_TESTBED_Peer)); + peer->controller = controller; + peer->host = host; + peer->unique_id = id_gen++; + peer->state = PS_INVALID; + data = GNUNET_malloc (sizeof (struct PeerCreateData)); + data->host = host; + data->cfg = cfg; + data->cb = cb; + data->cls = cls; + data->peer = peer; + opc = GNUNET_malloc (sizeof (struct OperationContext)); + opc->c = controller; + opc->data = data; + opc->id = GNUNET_TESTBED_get_next_op_id (controller); + opc->type = OP_PEER_CREATE; + opc->op = + GNUNET_TESTBED_operation_create_ (opc, &opstart_peer_create, + &oprelease_peer_create); + GNUNET_TESTBED_operation_queue_insert_ (controller->opq_parallel_operations, + opc->op); + GNUNET_TESTBED_operation_begin_wait_ (opc->op); + return opc->op; } /** * Start the given peer. * + * @param op_cls the closure for this operation; will be set in + * event->details.operation_finished.op_cls when this operation fails. * @param peer peer to start + * @param pcc function to call upon completion + * @param pcc_cls closure for 'pcc' * @return handle to the operation */ struct GNUNET_TESTBED_Operation * -GNUNET_TESTBED_peer_start (struct GNUNET_TESTBED_Peer *peer) +GNUNET_TESTBED_peer_start (void *op_cls, struct GNUNET_TESTBED_Peer *peer, + GNUNET_TESTBED_PeerChurnCallback pcc, void *pcc_cls) { - // FIXME: start locally or delegate... - GNUNET_break (0); - return NULL; + struct OperationContext *opc; + struct PeerEventData *data; + + data = GNUNET_malloc (sizeof (struct PeerEventData)); + data->peer = peer; + data->pcc = pcc; + data->pcc_cls = pcc_cls; + opc = GNUNET_malloc (sizeof (struct OperationContext)); + opc->c = peer->controller; + opc->data = data; + opc->op_cls = op_cls; + opc->id = GNUNET_TESTBED_get_next_op_id (opc->c); + opc->type = OP_PEER_START; + opc->op = + GNUNET_TESTBED_operation_create_ (opc, &opstart_peer_start, + &oprelease_peer_start); + GNUNET_TESTBED_operation_queue_insert_ (opc->c->opq_parallel_operations, + opc->op); + GNUNET_TESTBED_operation_begin_wait_ (opc->op); + return opc->op; } /** * Stop the given peer. The handle remains valid (use - * "GNUNET_TESTBED_peer_destroy" to fully clean up the + * "GNUNET_TESTBED_peer_destroy" to fully clean up the * state of the peer). * * @param peer peer to stop + * @param pcc function to call upon completion + * @param pcc_cls closure for 'pcc' * @return handle to the operation */ struct GNUNET_TESTBED_Operation * -GNUNET_TESTBED_peer_stop (struct GNUNET_TESTBED_Peer *peer) +GNUNET_TESTBED_peer_stop (struct GNUNET_TESTBED_Peer *peer, + GNUNET_TESTBED_PeerChurnCallback pcc, void *pcc_cls) { - // FIXME: stop locally or delegate... - GNUNET_break (0); - return NULL; + struct OperationContext *opc; + struct PeerEventData *data; + + data = GNUNET_malloc (sizeof (struct PeerEventData)); + data->peer = peer; + data->pcc = pcc; + data->pcc_cls = pcc_cls; + opc = GNUNET_malloc (sizeof (struct OperationContext)); + opc->c = peer->controller; + opc->data = data; + opc->id = GNUNET_TESTBED_get_next_op_id (opc->c); + opc->type = OP_PEER_STOP; + opc->op = + GNUNET_TESTBED_operation_create_ (opc, &opstart_peer_stop, + &oprelease_peer_stop); + GNUNET_TESTBED_operation_queue_insert_ (opc->c->opq_parallel_operations, + opc->op); + GNUNET_TESTBED_operation_begin_wait_ (opc->op); + return opc->op; } /** - * Request information about a peer. + * Request information about a peer. The controller callback will not be called + * with event type GNUNET_TESTBED_ET_OPERATION_FINISHED when result for this + * operation is available. Instead, the GNUNET_TESTBED_PeerInfoCallback() will + * be called. * * @param peer peer to request information about * @param pit desired information + * @param cb the convenience callback to be called when results for this + * operation are available + * @param cb_cls the closure for the above callback * @return handle to the operation */ struct GNUNET_TESTBED_Operation * GNUNET_TESTBED_peer_get_information (struct GNUNET_TESTBED_Peer *peer, - enum GNUNET_TESTBED_PeerInformationType pit) + enum GNUNET_TESTBED_PeerInformationType + pit, GNUNET_TESTBED_PeerInfoCallback cb, + void *cb_cls) { - // FIXME: handle locally or delegate... - GNUNET_break (0); - return NULL; + struct OperationContext *opc; + struct PeerInfoData *data; + + GNUNET_assert (GNUNET_TESTBED_PIT_GENERIC != pit); + data = GNUNET_malloc (sizeof (struct PeerInfoData)); + data->peer = peer; + data->pit = pit; + data->cb = cb; + data->cb_cls = cb_cls; + opc = GNUNET_malloc (sizeof (struct OperationContext)); + opc->c = peer->controller; + opc->data = data; + opc->type = OP_PEER_INFO; + opc->id = GNUNET_TESTBED_get_next_op_id (opc->c); + opc->op = + GNUNET_TESTBED_operation_create_ (opc, &opstart_peer_getinfo, + &oprelease_peer_getinfo); + GNUNET_TESTBED_operation_queue_insert_ (opc->c->opq_parallel_operations, + opc->op); + GNUNET_TESTBED_operation_begin_wait_ (opc->op); + return opc->op; } @@ -239,7 +595,8 @@ GNUNET_TESTBED_peer_get_information (struct GNUNET_TESTBED_Peer *peer, */ struct GNUNET_TESTBED_Operation * GNUNET_TESTBED_peer_update_configuration (struct GNUNET_TESTBED_Peer *peer, - const struct GNUNET_CONFIGURATION_Handle *cfg) + const struct + GNUNET_CONFIGURATION_Handle *cfg) { // FIXME: handle locally or delegate... GNUNET_break (0); @@ -247,9 +604,36 @@ GNUNET_TESTBED_peer_update_configuration (struct GNUNET_TESTBED_Peer *peer, } +/** + * Destroy the given peer; the peer should have been + * stopped first (if it was started). + * + * @param peer peer to stop + * @return handle to the operation + */ +struct GNUNET_TESTBED_Operation * +GNUNET_TESTBED_peer_destroy (struct GNUNET_TESTBED_Peer *peer) +{ + struct OperationContext *opc; + + opc = GNUNET_malloc (sizeof (struct OperationContext)); + opc->data = peer; + opc->c = peer->controller; + opc->id = GNUNET_TESTBED_get_next_op_id (peer->controller); + opc->type = OP_PEER_DESTROY; + opc->op = + GNUNET_TESTBED_operation_create_ (opc, &opstart_peer_destroy, + &oprelease_peer_destroy); + GNUNET_TESTBED_operation_queue_insert_ (opc->c->opq_parallel_operations, + opc->op); + GNUNET_TESTBED_operation_begin_wait_ (opc->op); + return opc->op; +} + + /** * Manipulate the P2P underlay topology by configuring a link - * between two peers. + * between two peers. * * @param op_cls closure argument to give with the operation event * @param p1 first peer @@ -261,22 +645,24 @@ GNUNET_TESTBED_peer_update_configuration (struct GNUNET_TESTBED_Peer *peer, */ struct GNUNET_TESTBED_Operation * GNUNET_TESTBED_underlay_configure_link (void *op_cls, - struct GNUNET_TESTBED_Peer *p1, - struct GNUNET_TESTBED_Peer *p2, - enum GNUNET_TESTBED_ConnectOption co, ...) + struct GNUNET_TESTBED_Peer *p1, + struct GNUNET_TESTBED_Peer *p2, + enum GNUNET_TESTBED_ConnectOption co, + ...) { GNUNET_break (0); return NULL; } - /** * Both peers must have been started before calling this function. * This function then obtains a HELLO from 'p1', gives it to 'p2' * and asks 'p2' to connect to 'p1'. * * @param op_cls closure argument to give with the operation event + * @param cb the callback to call when this operation has finished + * @param cb_cls the closure for the above callback * @param p1 first peer * @param p2 second peer * @return handle to the operation, NULL if connecting these two @@ -285,11 +671,33 @@ GNUNET_TESTBED_underlay_configure_link (void *op_cls, */ struct GNUNET_TESTBED_Operation * GNUNET_TESTBED_overlay_connect (void *op_cls, - struct GNUNET_TESTBED_Peer *p1, - struct GNUNET_TESTBED_Peer *p2) + GNUNET_TESTBED_OperationCompletionCallback cb, + void *cb_cls, struct GNUNET_TESTBED_Peer *p1, + struct GNUNET_TESTBED_Peer *p2) { - GNUNET_break (0); - return NULL; + struct OperationContext *opc; + struct OverlayConnectData *data; + + GNUNET_assert ((PS_STARTED == p1->state) && (PS_STARTED == p2->state)); + data = GNUNET_malloc (sizeof (struct OverlayConnectData)); + data->p1 = p1; + data->p2 = p2; + data->cb = cb; + data->cb_cls = cb_cls; + opc = GNUNET_malloc (sizeof (struct OperationContext)); + opc->data = data; + opc->c = p1->controller; + opc->id = GNUNET_TESTBED_get_next_op_id (opc->c); + opc->type = OP_OVERLAY_CONNECT; + opc->op_cls = op_cls; + opc->op = + GNUNET_TESTBED_operation_create_ (opc, &opstart_overlay_connect, + &oprelease_overlay_connect); + GNUNET_TESTBED_operation_queue_insert_ (opc-> + c->opq_parallel_overlay_connect_operations, + opc->op); + GNUNET_TESTBED_operation_begin_wait_ (opc->op); + return opc->op; } diff --git a/src/testbed/testbed_api_peers.h b/src/testbed/testbed_api_peers.h index ea42c98..8598cc1 100644 --- a/src/testbed/testbed_api_peers.h +++ b/src/testbed/testbed_api_peers.h @@ -22,7 +22,9 @@ * @file testbed/testbed_api_peers.h * @brief internal API to access the 'peers' subsystem * @author Christian Grothoff + * @author Sree Harsha Totakura */ + #ifndef NEW_TESTING_API_PEERS_H #define NEW_TESTING_API_PEERS_H @@ -31,41 +33,220 @@ /** - * Create the given peer at the specified host using the given - * controller. If the given controller is not running on the target - * host, it should find or create a controller at the target host and - * delegate creating the peer. Explicit delegation paths can be setup - * using 'GNUNET_TESTBED_controller_link'. If no explicit delegation - * path exists, a direct link with a subordinate controller is setup - * for the first delegated peer to a particular host; the subordinate - * controller is then destroyed once the last peer that was delegated - * to the remote host is stopped. This function is used in particular - * if some other controller has already assigned a unique ID to the - * peer. - * - * Creating the peer only creates the handle to manipulate and further - * configure the peer; use "GNUNET_TESTBED_peer_start" and - * "GNUNET_TESTBED_peer_stop" to actually start/stop the peer's - * processes. - * - * Note that the given configuration will be adjusted by the - * controller to avoid port/path conflicts with other peers. - * The "final" configuration can be obtained using - * 'GNUNET_TESTBED_peer_get_information'. - * - * @param unique_id unique ID for this peer - * @param controller controller process to use - * @param host host to run the peer on - * @param cfg configuration to use for the peer - * @return handle to the peer (actual startup will happen asynchronously) + * Enumeration of possible states a peer could be in + */ +enum PeerState +{ + /** + * State to signify that this peer is invalid + */ + PS_INVALID, + + /** + * The peer has been created + */ + PS_CREATED, + + /** + * The peer is running + */ + PS_STARTED, + + /** + * The peer is stopped + */ + PS_STOPPED, +}; + + +/** + * A peer controlled by the testing framework. A peer runs + * at a particular host. + */ +struct GNUNET_TESTBED_Peer +{ + /** + * Our controller context (not necessarily the controller + * that is responsible for starting/running the peer!). + */ + struct GNUNET_TESTBED_Controller *controller; + + /** + * Which host does this peer run on? + */ + struct GNUNET_TESTBED_Host *host; + + /** + * Globally unique ID of the peer. + */ + uint32_t unique_id; + + /** + * Peer's state + */ + enum PeerState state; +}; + + +/** + * Data for the OperationType OP_PEER_CREATE + */ +struct PeerCreateData +{ + /** + * The host where the peer has to be created + */ + struct GNUNET_TESTBED_Host *host; + + /** + * The template configuration of the peer + */ + const struct GNUNET_CONFIGURATION_Handle *cfg; + + /** + * The call back to call when we receive peer create success message + */ + GNUNET_TESTBED_PeerCreateCallback cb; + + /** + * The closure for the above callback + */ + void *cls; + + /** + * The peer structure to return when we get success message + */ + struct GNUNET_TESTBED_Peer *peer; + +}; + + +/** + * Data for OperationType OP_PEER_START and OP_PEER_STOP + */ +struct PeerEventData +{ + /** + * The handle of the peer to start + */ + struct GNUNET_TESTBED_Peer *peer; + + /** + * The Peer churn callback to call when this operation is completed + */ + GNUNET_TESTBED_PeerChurnCallback pcc; + + /** + * Closure for the above callback + */ + void *pcc_cls; + +}; + + +/** + * Data for the OperationType OP_PEER_DESTROY; */ -struct GNUNET_TESTBED_Peer * -GNUNET_TESTBED_peer_create_with_id_ (uint32_t unique_id, - struct GNUNET_TESTBED_Controller *controller, - struct GNUNET_TESTBED_Host *host, - const struct GNUNET_CONFIGURATION_Handle *cfg); +struct PeerDestroyData +{ + /** + * The peer structure + */ + struct GNUNET_TESTBED_Peer *peer; + + //PEERDESTROYDATA +}; +/** + * Data for the OperationType OP_PEER_INFO + */ +struct PeerInfoData +{ + /** + * The peer whose information has been requested + */ + struct GNUNET_TESTBED_Peer *peer; + + /** + * The Peer info callback to call when this operation has completed + */ + GNUNET_TESTBED_PeerInfoCallback cb; + + /** + * The closure for peer info callback + */ + void *cb_cls; + + /** + * The type of peer information requested + */ + enum GNUNET_TESTBED_PeerInformationType pit; +}; + + +/** + * Data structure for OperationType OP_OVERLAY_CONNECT + */ +struct OverlayConnectData +{ + + /** + * Peer A to connect to peer B + */ + struct GNUNET_TESTBED_Peer *p1; + + /** + * Peer B + */ + struct GNUNET_TESTBED_Peer *p2; + + /** + * The operation completion callback to call once this operation is done + */ + GNUNET_TESTBED_OperationCompletionCallback cb; + + /** + * The closure for the above callback + */ + void *cb_cls; + + /** + * OperationContext for forwarded operations generated when peer1's controller doesn't have the + * configuration of peer2's controller for linking laterally to attemp an + * overlay connection between peer 1 and peer 2. + */ + struct OperationContext *sub_opc; + + /** + * The starting time of this operation + */ + struct GNUNET_TIME_Absolute tstart; + + /** + * Has this operation failed + */ + int failed; + + /** + * The timing slot index for this operation + */ + unsigned int tslot_index; + +}; + + +/** + * Generate PeerGetConfigurationMessage + * + * @param peer_id the id of the peer whose information we have to get + * @param operation_id the ip of the operation that should be represented in + * the message + * @return the PeerGetConfigurationMessage + */ +struct GNUNET_TESTBED_PeerGetConfigurationMessage * +GNUNET_TESTBED_generate_peergetconfig_msg_ (uint32_t peer_id, + uint64_t operation_id); #endif /* end of testbed_api_peers.h */ diff --git a/src/testbed/testbed_api_services.c b/src/testbed/testbed_api_services.c index 34de0fd..923caed 100644 --- a/src/testbed/testbed_api_services.c +++ b/src/testbed/testbed_api_services.c @@ -24,7 +24,211 @@ * @author Christian Grothoff */ #include "platform.h" +#include "testbed_api.h" #include "testbed_api_peers.h" +#include "testbed_api_operations.h" + + +/** + * States for Service connect operations + */ +enum State +{ + /** + * Initial state + */ + INIT, + + /** + * The configuration request has been sent + */ + CFG_REQUEST_QUEUED, + + /** + * connected to service + */ + SERVICE_CONNECTED +}; + + +/** + * Data accessed during service connections + */ +struct ServiceConnectData +{ + /** + * helper function callback to establish the connection + */ + GNUNET_TESTBED_ConnectAdapter ca; + + /** + * helper function callback to close the connection + */ + GNUNET_TESTBED_DisconnectAdapter da; + + /** + * Closure to the above callbacks + */ + void *cada_cls; + + /** + * Service name + */ + char *service_name; + + /** + * Closure for operation event + */ + void *op_cls; + + /** + * The operation which created this structure + */ + struct GNUNET_TESTBED_Operation *operation; + + /** + * The operation context from GNUNET_TESTBED_forward_operation_msg_() + */ + struct OperationContext *opc; + + /** + * The peer handle + */ + struct GNUNET_TESTBED_Peer *peer; + + /** + * The acquired configuration of the peer + */ + struct GNUNET_CONFIGURATION_Handle *cfg; + + /** + * The op_result pointer from ConnectAdapter + */ + void *op_result; + + /** + * The operation completion callback + */ + GNUNET_TESTBED_ServiceConnectCompletionCallback cb; + + /** + * The closure for operation completion callback + */ + void *cb_cls; + + /** + * State information + */ + enum State state; + +}; + + +/** + * Type of a function to call when we receive a message + * from the service. + * + * @param cls ServiceConnectData + * @param msg message received, NULL on timeout or fatal error + */ +static void +configuration_receiver (void *cls, const struct GNUNET_MessageHeader *msg) +{ + struct ServiceConnectData *data = cls; + struct GNUNET_TESTBED_Controller *c; + const char *emsg; + struct GNUNET_TESTBED_EventInformation info; + uint16_t mtype; + + c = data->peer->controller; + mtype = ntohs (msg->type); + emsg = NULL; + info.type = GNUNET_TESTBED_ET_OPERATION_FINISHED; + info.details.operation_finished.operation = data->operation; + info.details.operation_finished.op_cls = data->op_cls; + if (GNUNET_MESSAGE_TYPE_TESTBED_OPERATION_FAIL_EVENT == mtype) + { + emsg = + GNUNET_TESTBED_parse_error_string_ ((const struct + GNUNET_TESTBED_OperationFailureEventMessage + *) msg); + if (NULL == emsg) + emsg = "Unknown error"; + info.details.operation_finished.emsg = emsg; + info.details.operation_finished.generic = NULL; + goto call_cb; + } + data->cfg = GNUNET_TESTBED_extract_config_ (msg); + GNUNET_assert (NULL == data->op_result); + data->op_result = data->ca (data->cada_cls, data->cfg); + info.details.operation_finished.emsg = NULL; + info.details.operation_finished.generic = data->op_result; + data->state = SERVICE_CONNECTED; + +call_cb: + if ((0 != (GNUNET_TESTBED_ET_OPERATION_FINISHED & c->event_mask)) && + (NULL != c->cc)) + c->cc (c->cc_cls, &info); + if (NULL != data->cb) + data->cb (data->cb_cls, data->operation, data->op_result, emsg); +} + + +/** + * Function called when a service connect operation is ready + * + * @param cls the closure from GNUNET_TESTBED_operation_create_() + */ +static void +opstart_service_connect (void *cls) +{ + struct ServiceConnectData *data = cls; + struct GNUNET_TESTBED_PeerGetConfigurationMessage *msg; + struct GNUNET_TESTBED_Controller *c; + uint64_t op_id; + + GNUNET_assert (NULL != data); + GNUNET_assert (NULL != data->peer); + c = data->peer->controller; + op_id = GNUNET_TESTBED_get_next_op_id (c); + msg = + GNUNET_TESTBED_generate_peergetconfig_msg_ (data->peer->unique_id, op_id); + data->opc = + GNUNET_TESTBED_forward_operation_msg_ (c, op_id, &msg->header, + &configuration_receiver, data); + GNUNET_free (msg); + data->state = CFG_REQUEST_QUEUED; +} + + +/** + * Callback which will be called when service connect type operation is + * released + * + * @param cls the closure from GNUNET_TESTBED_operation_create_() + */ +static void +oprelease_service_connect (void *cls) +{ + struct ServiceConnectData *data = cls; + + switch (data->state) + { + case INIT: + break; + case CFG_REQUEST_QUEUED: + GNUNET_assert (NULL != data->opc); + GNUNET_TESTBED_forward_operation_msg_cancel_ (data->opc); + break; + case SERVICE_CONNECTED: + GNUNET_assert (NULL != data->cfg); + GNUNET_CONFIGURATION_destroy (data->cfg); + if (NULL != data->da) + data->da (data->cada_cls, data->op_result); + break; + } + GNUNET_free (data); +} /** @@ -33,7 +237,7 @@ * maintain connections with other systems. The actual service * handle is then returned via the 'op_result' member in the event * callback. The 'ca' callback is used to create the connection - * when the time is right; the 'da' callback will be used to + * when the time is right; the 'da' callback will be used to * destroy the connection (upon 'GNUNET_TESTBED_operation_done'). * 'GNUNET_TESTBED_operation_cancel' can be used to abort this * operation until the event callback has been called. @@ -41,21 +245,44 @@ * @param op_cls closure to pass in operation event * @param peer peer that runs the service * @param service_name name of the service to connect to + * @param cb the callback to call when this operation finishes + * @param cb_cls closure for the above callback * @param ca helper function to establish the connection * @param da helper function to close the connection * @param cada_cls closure for ca and da * @return handle for the operation */ struct GNUNET_TESTBED_Operation * -GNUNET_TESTBED_service_connect (void *op_cls, - struct GNUNET_TESTBED_Peer *peer, - const char *service_name, - GNUNET_TESTBED_ConnectAdapter ca, - GNUNET_TESTBED_DisconnectAdapter da, - void *cada_cls) +GNUNET_TESTBED_service_connect (void *op_cls, struct GNUNET_TESTBED_Peer *peer, + const char *service_name, + GNUNET_TESTBED_ServiceConnectCompletionCallback + cb, void *cb_cls, + GNUNET_TESTBED_ConnectAdapter ca, + GNUNET_TESTBED_DisconnectAdapter da, + void *cada_cls) { - GNUNET_break (0); - return NULL; + struct ServiceConnectData *data; + + data = GNUNET_malloc (sizeof (struct ServiceConnectData)); + data->ca = ca; + data->da = da; + data->cada_cls = cada_cls; + data->op_cls = op_cls; + data->peer = peer; + data->state = INIT; + data->cb = cb; + data->cb_cls = cb_cls; + data->operation = + GNUNET_TESTBED_operation_create_ (data, &opstart_service_connect, + &oprelease_service_connect); + GNUNET_TESTBED_operation_queue_insert_ (peer-> + controller->opq_parallel_service_connections, + data->operation); + GNUNET_TESTBED_operation_queue_insert_ (peer-> + controller->opq_parallel_operations, + data->operation); + GNUNET_TESTBED_operation_begin_wait_ (data->operation); + return data->operation; } /* end of testbed_api_services.c */ diff --git a/src/testbed/testbed_api_statistics.c b/src/testbed/testbed_api_statistics.c new file mode 100644 index 0000000..f013c03 --- /dev/null +++ b/src/testbed/testbed_api_statistics.c @@ -0,0 +1,56 @@ +/* + This file is part of GNUnet + (C) 2008--2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. + */ + +/** + * @file testbed/testbed_api_statistics.c + * @brief high-level statistics function + * @author Christian Grothoff + * @author Sree Harsha Totakura + */ +#include "platform.h" +#include "gnunet_testbed_service.h" + + +/** + * Convenience method that iterates over all (running) peers + * and retrieves all statistics from each peer. + * + * @param num_peers number of peers to iterate over + * @param peers array of peers to iterate over + * @param proc processing function for each statistic retrieved + * @param cont continuation to call once call is completed(?) + * @param cls closure to pass to proc and cont + * @return operation handle to cancel the operation + */ +struct GNUNET_TESTBED_Operation * +GNUNET_TESTBED_get_statistics (unsigned int num_peers, + struct GNUNET_TESTBED_Peer **peers, + GNUNET_TESTBED_StatisticsIterator proc, + GNUNET_TESTBED_OperationCompletionCallback cont, + void *cls) +{ + // FIXME: not implemented, but clients will kind-of work if we do this: + GNUNET_break (0); + cont (cls, NULL, "not implemented"); + return NULL; +} + + +/* end of testbed_api_statistics.c */ diff --git a/src/testbed/testbed_api_test.c b/src/testbed/testbed_api_test.c index 38e189b..af91cec 100644 --- a/src/testbed/testbed_api_test.c +++ b/src/testbed/testbed_api_test.c @@ -22,11 +22,66 @@ * @file testbed/testbed_api_test.c * @brief high-level test function * @author Christian Grothoff + * @author Sree Harsha Totakura */ #include "platform.h" #include "gnunet_testbed_service.h" +/** + * Context information for test run + */ +struct TestRunContext +{ + /** + * Test master callback + */ + GNUNET_TESTBED_TestMaster test_master; + + /** + * Closure for test master + */ + void *test_master_cls; + + /** + * The controller event callback + */ + GNUNET_TESTBED_ControllerCallback cc; + + /** + * Closure for the above callback + */ + void *cc_cls; + + /** + * event mask for the controller callback + */ + uint64_t event_mask; + + /** + * Number of peers to start + */ + unsigned int num_peers; +}; + + +/** + * Main run function. + * + * @param cls NULL + * @param args arguments passed to GNUNET_PROGRAM_run + * @param cfgfile the path to configuration file + * @param config the configuration file handle + */ +static void +run (void *cls, char *const *args, const char *cfgfile, + const struct GNUNET_CONFIGURATION_Handle *config) +{ + struct TestRunContext *rc = cls; + + GNUNET_TESTBED_run (NULL, config, rc->num_peers, rc->event_mask, rc->cc, + rc->cc_cls, rc->test_master, rc->test_master_cls); +} /** @@ -49,19 +104,57 @@ * @param cfg_filename configuration filename to use * (for testbed, controller and peers) * @param num_peers number of peers to start + * @param event_mask bit mask with set of events to call 'cc' for; + * or-ed values of "1LL" shifted by the + * respective 'enum GNUNET_TESTBED_EventType' + * (i.e. "(1LL << GNUNET_TESTBED_ET_CONNECT) || ...") + * @param cc controller callback to invoke on events; This callback is called + * for all peer start events even if GNUNET_TESTBED_ET_PEER_START isn't + * set in the event_mask as this is the only way get access to the + * handle of each peer + * @param cc_cls closure for cc * @param test_master task to run once the test is ready * @param test_master_cls closure for 'task'. + * @return GNUNET_SYSERR on error, GNUNET_OK on success */ -void -GNUNET_TESTBED_test_run (const char *testname, - const char *cfg_filename, - unsigned int num_peers, - GNUNET_TESTBED_TestMaster test_master, - void *test_master_cls) +int +GNUNET_TESTBED_test_run (const char *testname, const char *cfg_filename, + unsigned int num_peers, uint64_t event_mask, + GNUNET_TESTBED_ControllerCallback cc, void *cc_cls, + GNUNET_TESTBED_TestMaster test_master, + void *test_master_cls) { - GNUNET_break (0); -} - + char *argv2[] = { + NULL, + "-c", + NULL, + NULL + }; + struct GNUNET_GETOPT_CommandLineOption options[] = { + GNUNET_GETOPT_OPTION_END + }; + struct TestRunContext *rc; + int ret; + argv2[0] = GNUNET_strdup (testname); + argv2[2] = GNUNET_strdup (cfg_filename); + GNUNET_assert (NULL != test_master); + GNUNET_assert (num_peers > 0); + rc = GNUNET_malloc (sizeof (struct TestRunContext) + + (num_peers * sizeof (struct GNUNET_TESTBED_Peer *))); + rc->test_master = test_master; + rc->test_master_cls = test_master_cls; + rc->num_peers = num_peers; + rc->event_mask = event_mask; + rc->cc = cc; + rc->cc_cls = cc_cls; + ret = + GNUNET_PROGRAM_run ((sizeof (argv2) / sizeof (char *)) - 1, argv2, + testname, "nohelp", options, &run, rc); + GNUNET_free (rc); + GNUNET_free (argv2[0]); + GNUNET_free (argv2[2]); + return ret; +} /* end of testbed_api_test.c */ diff --git a/src/testbed/testbed_api_testbed.c b/src/testbed/testbed_api_testbed.c index 6311806..1c9363c 100644 --- a/src/testbed/testbed_api_testbed.c +++ b/src/testbed/testbed_api_testbed.c @@ -1,115 +1,1016 @@ /* - This file is part of GNUnet - (C) 2008--2012 Christian Grothoff (and other contributing authors) + This file is part of GNUnet + (C) 2008--2012 Christian Grothoff (and other contributing authors) - GNUnet is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published - by the Free Software Foundation; either version 3, or (at your - option) any later version. + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. - GNUnet is distributed in the hope that it will be useful, but - WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - General Public License for more details. + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. - You should have received a copy of the GNU General Public License - along with GNUnet; see the file COPYING. If not, write to the - Free Software Foundation, Inc., 59 Temple Place - Suite 330, - Boston, MA 02111-1307, USA. - */ + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ /** * @file testbed/testbed_api_testbed.c * @brief high-level testbed management * @author Christian Grothoff + * @author Sree Harsha Totakura */ + #include "platform.h" +#include "gnunet_util_lib.h" #include "gnunet_testbed_service.h" +#include "testbed_api_peers.h" +#include "testbed_api_hosts.h" +#include "testbed_api_topology.h" + +/** + * Generic loggins shorthand + */ +#define LOG(kind,...) \ + GNUNET_log_from (kind, "testbed-api-testbed", __VA_ARGS__) + +/** + * Debug logging shortcut + */ +#define DEBUG(...) \ + LOG (GNUNET_ERROR_TYPE_DEBUG, __VA_ARGS__) + +/** + * DLL of operations + */ +struct DLLOperation +{ + /** + * The testbed operation handle + */ + struct GNUNET_TESTBED_Operation *op; + + /** + * Context information for GNUNET_TESTBED_run() + */ + struct RunContext *rc; + + /** + * Closure + */ + void *cls; + + /** + * The next pointer for DLL + */ + struct DLLOperation *next; + + /** + * The prev pointer for DLL + */ + struct DLLOperation *prev; +}; /** - * Opaque handle to an abstract operation to be executed by the testing framework. + * States of RunContext */ -struct GNUNET_TESTBED_Testbed +enum State { - // FIXME! + /** + * Initial state + */ + RC_INIT = 0, + + /** + * Controllers on given hosts started and linked + */ + RC_LINKED, + + /** + * Peers are created + */ + RC_PEERS_CREATED, + + /** + * The testbed run is ready and the master callback can be called now. At this + * time the peers are all started and if a topology is provided in the + * configuration the topology would have been attempted + */ + RC_READY, + + /** + * Peers are stopped + */ + RC_PEERS_STOPPED, + + /** + * Peers are destroyed + */ + RC_PEERS_DESTROYED }; /** - * Configure and run a testbed using the given - * master controller on 'num_hosts' starting - * 'num_peers' using the given peer configuration. - * - * @param controller master controller for the testbed - * (must not be destroyed until after the - * testbed is destroyed). - * @param num_hosts number of hosts in 'hosts', 0 to only - * use 'localhost' - * @param hosts list of hosts to use for the testbed - * @param num_peers number of peers to start - * @param peer_cfg peer configuration template to use - * @param underlay_topology underlay topology to create - * @param va topology-specific options - * @return handle to the testbed - */ -struct GNUNET_TESTBED_Testbed * -GNUNET_TESTBED_create_va (struct GNUNET_TESTBED_Controller *controller, - unsigned int num_hosts, - struct GNUNET_TESTBED_Host **hosts, - unsigned int num_peers, - const struct GNUNET_CONFIGURATION_Handle *peer_cfg, - enum GNUNET_TESTBED_TopologyOption underlay_topology, - va_list va) -{ - GNUNET_break (0); - return NULL; + * Testbed Run Handle + */ +struct RunContext +{ + /** + * The controller handle + */ + struct GNUNET_TESTBED_Controller *c; + + /** + * The configuration of the controller. This is based on the cfg given to the + * function GNUNET_TESTBED_run(). We also use this config as a template while + * for peers + */ + struct GNUNET_CONFIGURATION_Handle *cfg; + + /** + * Handle to the host on which the controller runs + */ + struct GNUNET_TESTBED_Host *h; + + /** + * The handle to the controller process + */ + struct GNUNET_TESTBED_ControllerProc *cproc; + + /** + * The callback to use as controller callback + */ + GNUNET_TESTBED_ControllerCallback cc; + + /** + * The pointer to the controller callback + */ + void *cc_cls; + + /** + * The trusted IP string + */ + char *trusted_ip; + + /** + * TestMaster callback to call when testbed initialization is done + */ + GNUNET_TESTBED_TestMaster test_master; + + /** + * The closure for the TestMaster callback + */ + void *test_master_cls; + + /** + * The head element of DLL operations + */ + struct DLLOperation *dll_op_head; + + /** + * The tail element of DLL operations + */ + struct DLLOperation *dll_op_tail; + + /** + * An array of hosts loaded from the hostkeys file + */ + struct GNUNET_TESTBED_Host **hosts; + + /** + * The handle for whether a host is habitable or not + */ + struct GNUNET_TESTBED_HostHabitableCheckHandle **hc_handles; + + /** + * Array of peers which we create + */ + struct GNUNET_TESTBED_Peer **peers; + + /** + * The topology generation operation. Will be null if no topology is set in + * the configuration + */ + struct GNUNET_TESTBED_Operation *topology_operation; + + /** + * The file containing topology data. Only used if the topology is set to 'FROM_FILE' + */ + char *topo_file; + + /** + * Host registration handle + */ + struct GNUNET_TESTBED_HostRegistrationHandle *reg_handle; + + /** + * Profiling start time + */ + struct GNUNET_TIME_Absolute pstart_time; + + /** + * Host registration task + */ + GNUNET_SCHEDULER_TaskIdentifier register_hosts_task; + + /** + * Task to be run while shutting down + */ + GNUNET_SCHEDULER_TaskIdentifier shutdown_run_task; + + /** + * The event mask for the controller + */ + uint64_t event_mask; + + /** + * State of this context + */ + enum State state; + + /** + * The topology which has to be achieved with the peers started in this context + */ + enum GNUNET_TESTBED_TopologyOption topology; + + /** + * Have we already shutdown + */ + int shutdown; + + /** + * Number of hosts in the given host file + */ + unsigned int num_hosts; + + /** + * Number of registered hosts. Also used as a counter while checking + * habitabillity of hosts + */ + unsigned int reg_hosts; + + /** + * Current peer count for an operation; Set this to 0 and increment for each + * successful operation on a peer + */ + unsigned int peer_count; + + /** + * number of peers to start + */ + unsigned int num_peers; + + /** + * counter to count overlay connect attempts. This counter includes both + * successful and failed overlay connects + */ + unsigned int oc_count; + + /** + * Expected overlay connects. Should be zero if no topology is relavant + */ + unsigned int num_oc; + + /** + * Number of random links to established + */ + unsigned int random_links; + +}; + + +/** + * Function to return the string representation of the duration between current + * time and `pstart_time' in `RunContext' + * + * @param rc the RunContext + * @return the representation string; this is NOT reentrant + */ +static const char * +prof_time (struct RunContext *rc) +{ + struct GNUNET_TIME_Relative ptime; + + ptime = GNUNET_TIME_absolute_get_duration (rc->pstart_time); + return GNUNET_STRINGS_relative_time_to_string (ptime, GNUNET_YES); +} + + +/** + * Task for starting peers + * + * @param cls the RunHandle + * @param tc the task context from scheduler + */ +static void +start_peers_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct RunContext *rc = cls; + struct DLLOperation *dll_op; + unsigned int peer; + + DEBUG ("Starting Peers\n"); + rc->pstart_time = GNUNET_TIME_absolute_get (); + for (peer = 0; peer < rc->num_peers; peer++) + { + dll_op = GNUNET_malloc (sizeof (struct DLLOperation)); + dll_op->op = GNUNET_TESTBED_peer_start (NULL, rc->peers[peer], NULL, NULL); + dll_op->cls = rc->peers[peer]; + GNUNET_CONTAINER_DLL_insert_tail (rc->dll_op_head, rc->dll_op_tail, dll_op); + } + rc->peer_count = 0; } /** - * Configure and run a testbed using the given - * master controller on 'num_hosts' starting - * 'num_peers' using the given peer configuration. - * - * @param controller master controller for the testbed - * (must not be destroyed until after the - * testbed is destroyed). - * @param num_hosts number of hosts in 'hosts', 0 to only - * use 'localhost' - * @param hosts list of hosts to use for the testbed - * @param num_peers number of peers to start - * @param peer_cfg peer configuration template to use - * @param underlay_topology underlay topology to create - * @param ... topology-specific options - */ -struct GNUNET_TESTBED_Testbed * -GNUNET_TESTBED_create (struct GNUNET_TESTBED_Controller *controller, - unsigned int num_hosts, - struct GNUNET_TESTBED_Host **hosts, - unsigned int num_peers, - const struct GNUNET_CONFIGURATION_Handle *peer_cfg, - enum GNUNET_TESTBED_TopologyOption underlay_topology, - ...) -{ - GNUNET_break (0); - return NULL; + * Functions of this signature are called when a peer has been successfully + * created + * + * @param cls the closure from GNUNET_TESTBED_peer_create() + * @param peer the handle for the created peer; NULL on any error during + * creation + * @param emsg NULL if peer is not NULL; else MAY contain the error description + */ +static void +peer_create_cb (void *cls, struct GNUNET_TESTBED_Peer *peer, const char *emsg) +{ + struct DLLOperation *dll_op = cls; + struct RunContext *rc; + + GNUNET_assert (NULL != dll_op); + rc = dll_op->rc; + GNUNET_assert (NULL != rc); + GNUNET_CONTAINER_DLL_remove (rc->dll_op_head, rc->dll_op_tail, dll_op); + GNUNET_TESTBED_operation_done (dll_op->op); + GNUNET_free (dll_op); + if (NULL == peer) + { + if (NULL != emsg) + LOG (GNUNET_ERROR_TYPE_WARNING, "Error while creating a peer: %s\n", + emsg); + /* FIXME: GNUNET_TESTBED_shutdown_run()? */ + return; + } + rc->peers[rc->peer_count] = peer; + rc->peer_count++; + if (rc->peer_count < rc->num_peers) + return; + DEBUG ("%u peers created in %s\n", rc->num_peers, prof_time (rc)); + rc->state = RC_PEERS_CREATED; + GNUNET_SCHEDULER_add_now (&start_peers_task, rc); } /** - * Destroy a testbed. Stops all running peers and then - * destroys all peers. Does NOT destroy the master controller. + * Assuming all peers have been destroyed cleanup run handle * - * @param testbed testbed to destroy + * @param cls the run handle + * @param tc the task context from scheduler */ -void -GNUNET_TESTBED_destroy (struct GNUNET_TESTBED_Testbed *testbed) +static void +cleanup_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct RunContext *rc = cls; + struct DLLOperation *dll_op; + unsigned int hid; + + GNUNET_assert (GNUNET_SCHEDULER_NO_TASK == rc->register_hosts_task); + GNUNET_assert (NULL == rc->reg_handle); + GNUNET_assert (NULL == rc->peers); + GNUNET_assert (NULL == rc->hc_handles); + GNUNET_assert (RC_PEERS_DESTROYED == rc->state); + if (NULL != rc->dll_op_head) + { /* cancel our pending operations */ + while (NULL != (dll_op = rc->dll_op_head)) + { + GNUNET_TESTBED_operation_done (dll_op->op); + GNUNET_CONTAINER_DLL_remove (rc->dll_op_head, rc->dll_op_tail, dll_op); + GNUNET_free (dll_op); + } + } + if (NULL != rc->c) + GNUNET_TESTBED_controller_disconnect (rc->c); + if (NULL != rc->cproc) + GNUNET_TESTBED_controller_stop (rc->cproc); + if (NULL != rc->h) + GNUNET_TESTBED_host_destroy (rc->h); + for (hid = 0; hid < rc->num_hosts; hid++) + GNUNET_TESTBED_host_destroy (rc->hosts[hid]); + GNUNET_free_non_null (rc->hosts); + if (NULL != rc->cfg) + GNUNET_CONFIGURATION_destroy (rc->cfg); + GNUNET_free_non_null (rc->topo_file); + GNUNET_free_non_null (rc->trusted_ip); + GNUNET_free (rc); +} + + +/** + * Stops the testbed run and releases any used resources + * + * @param cls the tesbed run handle + * @param tc the task context from scheduler + */ +static void +shutdown_run (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc); + + +/** + * Function to shutdown now + * + * @param rc the RunContext + */ +static void +shutdown_now (struct RunContext *rc) +{ + if (GNUNET_YES == rc->shutdown) + return; + if (GNUNET_SCHEDULER_NO_TASK != rc->shutdown_run_task) + GNUNET_SCHEDULER_cancel (rc->shutdown_run_task); + rc->shutdown_run_task = GNUNET_SCHEDULER_add_now (&shutdown_run, rc); +} + + +/** + * Stops the testbed run and releases any used resources + * + * @param cls the tesbed run handle + * @param tc the task context from scheduler + */ +static void +shutdown_run (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { - GNUNET_break (0); + struct RunContext *rc = cls; + struct DLLOperation *dll_op; + int all_peers_destroyed; + unsigned int peer; + unsigned int nhost; + + GNUNET_assert (GNUNET_SCHEDULER_NO_TASK != rc->shutdown_run_task); + rc->shutdown_run_task = GNUNET_SCHEDULER_NO_TASK; + GNUNET_assert (GNUNET_NO == rc->shutdown); + rc->shutdown = GNUNET_YES; + if (NULL != rc->hc_handles) + { + for (nhost = 0; nhost < rc->num_hosts; nhost++) + if (NULL != rc->hc_handles[nhost]) + GNUNET_TESTBED_is_host_habitable_cancel (rc->hc_handles[nhost]); + GNUNET_free (rc->hc_handles); + rc->hc_handles = NULL; + } + /* Stop register hosts task if it is running */ + if (GNUNET_SCHEDULER_NO_TASK != rc->register_hosts_task) + { + GNUNET_SCHEDULER_cancel (rc->register_hosts_task); + rc->register_hosts_task = GNUNET_SCHEDULER_NO_TASK; + } + if (NULL != rc->reg_handle) + { + GNUNET_TESTBED_cancel_registration (rc->reg_handle); + rc->reg_handle = NULL; + } + if (NULL != rc->c) + { + if (NULL != rc->peers) + { + if (NULL != rc->topology_operation) + { + GNUNET_TESTBED_operation_done (rc->topology_operation); + rc->topology_operation = NULL; + } + if (RC_INIT == rc->state) + rc->state = RC_READY; /* Even though we haven't called the master callback */ + rc->peer_count = 0; + /* Check if some peers are stopped */ + for (peer = 0; peer < rc->num_peers; peer++) + { + if (NULL == rc->peers[peer]) + continue; + if (PS_STOPPED != rc->peers[peer]->state) + break; + } + if (peer == rc->num_peers) + { + /* All peers are stopped */ + rc->state = RC_PEERS_STOPPED; + all_peers_destroyed = GNUNET_YES; + for (peer = 0; peer < rc->num_peers; peer++) + { + if (NULL == rc->peers[peer]) + continue; + all_peers_destroyed = GNUNET_NO; + dll_op = GNUNET_malloc (sizeof (struct DLLOperation)); + dll_op->op = GNUNET_TESTBED_peer_destroy (rc->peers[peer]); + GNUNET_CONTAINER_DLL_insert_tail (rc->dll_op_head, rc->dll_op_tail, + dll_op); + } + if (all_peers_destroyed == GNUNET_NO) + { + DEBUG ("Destroying peers\n"); + rc->pstart_time = GNUNET_TIME_absolute_get (); + return; + } + } + /* Some peers are stopped */ + DEBUG ("Stopping peers\n"); + rc->pstart_time = GNUNET_TIME_absolute_get (); + for (peer = 0; peer < rc->num_peers; peer++) + { + if ((NULL == rc->peers[peer]) || (PS_STARTED != rc->peers[peer]->state)) + { + rc->peer_count++; + continue; + } + dll_op = GNUNET_malloc (sizeof (struct DLLOperation)); + dll_op->op = GNUNET_TESTBED_peer_stop (rc->peers[peer], NULL, NULL); + dll_op->cls = rc->peers[peer]; + GNUNET_CONTAINER_DLL_insert_tail (rc->dll_op_head, rc->dll_op_tail, + dll_op); + } + if (rc->peer_count != rc->num_peers) + return; + GNUNET_free (rc->peers); + rc->peers = NULL; + } + } + rc->state = RC_PEERS_DESTROYED; /* No peers are present so we consider the + * state where all peers are destroyed */ + GNUNET_SCHEDULER_add_now (&cleanup_task, rc); } +/** + * Task to call master task + * + * @param cls the run context + * @param tc the task context + */ +static void +call_master (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct RunContext *rc = cls; + + if (NULL != rc->topology_operation) + { + DEBUG ("Overlay topology generated in %s\n", prof_time (rc)); + GNUNET_TESTBED_operation_done (rc->topology_operation); + rc->topology_operation = NULL; + } + if (NULL != rc->test_master) + rc->test_master (rc->test_master_cls, rc->num_peers, rc->peers); +} + + +/** + * Function to create peers + * + * @param rc the RunContext + */ +static void +create_peers (struct RunContext *rc) +{ + struct DLLOperation *dll_op; + unsigned int peer; + + DEBUG ("Creating peers\n"); + rc->pstart_time = GNUNET_TIME_absolute_get (); + rc->peers = + GNUNET_malloc (sizeof (struct GNUNET_TESTBED_Peer *) * rc->num_peers); + GNUNET_assert (NULL != rc->c); + rc->peer_count = 0; + for (peer = 0; peer < rc->num_peers; peer++) + { + dll_op = GNUNET_malloc (sizeof (struct DLLOperation)); + dll_op->rc = rc; + dll_op->op = + GNUNET_TESTBED_peer_create (rc->c, + (0 == + rc->num_hosts) ? rc->h : rc->hosts[peer % + rc->num_hosts], + rc->cfg, peer_create_cb, dll_op); + GNUNET_CONTAINER_DLL_insert_tail (rc->dll_op_head, rc->dll_op_tail, dll_op); + } +} + + +/** + * Signature of the event handler function called by the + * respective event controller. + * + * @param cls closure + * @param event information about the event + */ +static void +event_cb (void *cls, const struct GNUNET_TESTBED_EventInformation *event) +{ + struct RunContext *rc = cls; + struct DLLOperation *dll_op; + unsigned int peer_id; + + if (RC_INIT == rc->state) + { + switch (event->type) + { + case GNUNET_TESTBED_ET_OPERATION_FINISHED: + dll_op = event->details.operation_finished.op_cls; + if (NULL != event->details.operation_finished.emsg) + { + LOG (GNUNET_ERROR_TYPE_ERROR, _("Linking controllers failed. Exiting")); + shutdown_now (rc); + } + else + rc->reg_hosts++; + GNUNET_assert (event->details.operation_finished.operation == dll_op->op); + GNUNET_CONTAINER_DLL_remove (rc->dll_op_head, rc->dll_op_tail, dll_op); + GNUNET_TESTBED_operation_done (dll_op->op); + GNUNET_free (dll_op); + if (rc->reg_hosts == rc->num_hosts) + { + rc->state = RC_LINKED; + create_peers (rc); + } + return; + default: + GNUNET_break (0); + shutdown_now (rc); + return; + } + } + if (NULL != rc->topology_operation) + { + switch (event->type) + { + case GNUNET_TESTBED_ET_OPERATION_FINISHED: + case GNUNET_TESTBED_ET_CONNECT: + rc->oc_count++; + break; + default: + GNUNET_break (0); + shutdown_now (rc); + return; + } + if (rc->oc_count == rc->num_oc) + { + rc->state = RC_READY; + GNUNET_SCHEDULER_add_continuation (&call_master, rc, + GNUNET_SCHEDULER_REASON_PREREQ_DONE); + } + goto call_cc; + } + for (dll_op = rc->dll_op_head; NULL != dll_op; dll_op = dll_op->next) + { + if ((GNUNET_TESTBED_ET_OPERATION_FINISHED == event->type) && + (event->details.operation_finished.operation == dll_op->op)) + break; + if ((GNUNET_TESTBED_ET_PEER_STOP == event->type) && + (event->details.peer_stop.peer == dll_op->cls)) + break; + } + if (NULL == dll_op) + goto call_cc; + GNUNET_CONTAINER_DLL_remove (rc->dll_op_head, rc->dll_op_tail, dll_op); + GNUNET_TESTBED_operation_done (dll_op->op); + GNUNET_free (dll_op); + rc->peer_count++; + if (rc->peer_count < rc->num_peers) + return; + switch (rc->state) + { + case RC_PEERS_CREATED: + case RC_READY: + rc->state = RC_PEERS_STOPPED; + DEBUG ("Peers stopped in %s\n", prof_time (rc)); + DEBUG ("Destroying peers\n"); + rc->pstart_time = GNUNET_TIME_absolute_get (); + rc->peer_count = 0; + for (peer_id = 0; peer_id < rc->num_peers; peer_id++) + { + dll_op = GNUNET_malloc (sizeof (struct DLLOperation)); + dll_op->op = GNUNET_TESTBED_peer_destroy (rc->peers[peer_id]); + GNUNET_CONTAINER_DLL_insert_tail (rc->dll_op_head, rc->dll_op_tail, + dll_op); + } + break; + case RC_PEERS_STOPPED: + rc->state = RC_PEERS_DESTROYED; + GNUNET_free (rc->peers); + rc->peers = NULL; + DEBUG ("Peers destroyed in %s\n", prof_time (rc)); + GNUNET_SCHEDULER_add_now (&cleanup_task, rc); + break; + default: + GNUNET_assert (0); + } + return; + +call_cc: + if ((0 != (rc->event_mask & (1LL << event->type))) && (NULL != rc->cc)) + rc->cc (rc->cc_cls, event); + if (GNUNET_TESTBED_ET_PEER_START != event->type) + return; + for (dll_op = rc->dll_op_head; NULL != dll_op; dll_op = dll_op->next) + if ((NULL != dll_op->cls) && + (event->details.peer_start.peer == dll_op->cls)) + break; + if (NULL == dll_op) /* Not our operation */ + return; + GNUNET_CONTAINER_DLL_remove (rc->dll_op_head, rc->dll_op_tail, dll_op); + GNUNET_TESTBED_operation_done (dll_op->op); + GNUNET_free (dll_op); + rc->peer_count++; + if (rc->peer_count < rc->num_peers) + return; + DEBUG ("%u peers started in %s\n", rc->num_peers, prof_time (rc)); + if (GNUNET_TESTBED_TOPOLOGY_NONE != rc->topology) + { + if ((GNUNET_TESTBED_TOPOLOGY_ERDOS_RENYI == rc->topology) || + (GNUNET_TESTBED_TOPOLOGY_SMALL_WORLD_RING == rc->topology) || + (GNUNET_TESTBED_TOPOLOGY_SMALL_WORLD == rc->topology)) + { + rc->topology_operation = + GNUNET_TESTBED_overlay_configure_topology (NULL, rc->num_peers, + rc->peers, &rc->num_oc, + NULL, + NULL, + rc->topology, + rc->random_links, + GNUNET_TESTBED_TOPOLOGY_OPTION_END); + } + else if (GNUNET_TESTBED_TOPOLOGY_FROM_FILE == rc->topology) + { + GNUNET_assert (NULL != rc->topo_file); + rc->topology_operation = + GNUNET_TESTBED_overlay_configure_topology (NULL, rc->num_peers, + rc->peers, &rc->num_oc, + NULL, + NULL, + rc->topology, + rc->topo_file, + GNUNET_TESTBED_TOPOLOGY_OPTION_END); + } + else + rc->topology_operation = + GNUNET_TESTBED_overlay_configure_topology (NULL, rc->num_peers, + rc->peers, &rc->num_oc, + NULL, + NULL, + rc->topology, + GNUNET_TESTBED_TOPOLOGY_OPTION_END); + if (NULL == rc->topology_operation) + LOG (GNUNET_ERROR_TYPE_WARNING, + "Not generating topology. Check number of peers\n"); + else + { + DEBUG ("Creating overlay topology\n"); + rc->pstart_time = GNUNET_TIME_absolute_get (); + return; + } + } + rc->state = RC_READY; + GNUNET_SCHEDULER_add_continuation (&call_master, rc, + GNUNET_SCHEDULER_REASON_PREREQ_DONE); +} + + +/** + * Task to register all hosts available in the global host list + * + * @param cls the RunContext + * @param tc the scheduler task context + */ +static void +register_hosts (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc); + + +/** + * Callback which will be called to after a host registration succeeded or failed + * + * @param cls the closure + * @param emsg the error message; NULL if host registration is successful + */ +static void +host_registration_completion (void *cls, const char *emsg) +{ + struct RunContext *rc = cls; + + rc->reg_handle = NULL; + if (NULL != emsg) + { + LOG (GNUNET_ERROR_TYPE_WARNING, + _("Host registration failed for a host. Error: %s\n"), emsg); + shutdown_now (rc); + return; + } + rc->register_hosts_task = GNUNET_SCHEDULER_add_now (®ister_hosts, rc); +} + + +/** + * Task to register all hosts available in the global host list + * + * @param cls RunContext + * @param tc the scheduler task context + */ +static void +register_hosts (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct RunContext *rc = cls; + struct DLLOperation *dll_op; + unsigned int slave; + + rc->register_hosts_task = GNUNET_SCHEDULER_NO_TASK; + if (rc->reg_hosts == rc->num_hosts) + { + DEBUG ("All hosts successfully registered\n"); + /* Start slaves */ + for (slave = 0; slave < rc->num_hosts; slave++) + { + dll_op = GNUNET_malloc (sizeof (struct DLLOperation)); + dll_op->rc = rc; + dll_op->op = + GNUNET_TESTBED_controller_link (dll_op, rc->c, rc->hosts[slave], + rc->h, rc->cfg, GNUNET_YES); + GNUNET_CONTAINER_DLL_insert_tail (rc->dll_op_head, rc->dll_op_tail, + dll_op); + } + rc->reg_hosts = 0; + return; + } + rc->reg_handle = + GNUNET_TESTBED_register_host (rc->c, rc->hosts[rc->reg_hosts], + host_registration_completion, rc); + rc->reg_hosts++; +} + + +/** + * Callback to signal successfull startup of the controller process + * + * @param cls the closure from GNUNET_TESTBED_controller_start() + * @param cfg the configuration with which the controller has been started; + * NULL if status is not GNUNET_OK + * @param status GNUNET_OK if the startup is successfull; GNUNET_SYSERR if not, + * GNUNET_TESTBED_controller_stop() shouldn't be called in this case + */ +static void +controller_status_cb (void *cls, const struct GNUNET_CONFIGURATION_Handle *cfg, + int status) +{ + struct RunContext *rc = cls; + uint64_t event_mask; + + if (status != GNUNET_OK) + { + switch (rc->state) + { + case RC_INIT: + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Testbed startup failed\n"); + return; + default: + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + "Controller crash detected. Shutting down.\n"); + rc->cproc = NULL; + shutdown_now (rc); + return; + } + } + GNUNET_CONFIGURATION_destroy (rc->cfg); + rc->cfg = GNUNET_CONFIGURATION_dup (cfg); + event_mask = rc->event_mask; + event_mask |= (1LL << GNUNET_TESTBED_ET_PEER_STOP); + event_mask |= (1LL << GNUNET_TESTBED_ET_OPERATION_FINISHED); + event_mask |= (1LL << GNUNET_TESTBED_ET_PEER_START); + if (rc->topology < GNUNET_TESTBED_TOPOLOGY_NONE) + event_mask |= GNUNET_TESTBED_ET_CONNECT; + rc->c = + GNUNET_TESTBED_controller_connect (rc->cfg, rc->h, event_mask, &event_cb, + rc); + if (0 < rc->num_hosts) + { + rc->reg_hosts = 0; + rc->register_hosts_task = GNUNET_SCHEDULER_add_now (®ister_hosts, rc); + return; + } + rc->state = RC_LINKED; + create_peers (rc); +} + + +/** + * Callback function invoked for each interface found. + * + * @param cls closure + * @param name name of the interface (can be NULL for unknown) + * @param isDefault is this presumably the default interface + * @param addr address of this interface (can be NULL for unknown or unassigned) + * @param broadcast_addr the broadcast address (can be NULL for unknown or unassigned) + * @param netmask the network mask (can be NULL for unknown or unassigned)) + * @param addrlen length of the address + * @return GNUNET_OK to continue iteration, GNUNET_SYSERR to abort + */ +static int +netint_proc (void *cls, const char *name, int isDefault, + const struct sockaddr *addr, const struct sockaddr *broadcast_addr, + const struct sockaddr *netmask, socklen_t addrlen) +{ + struct RunContext *rc = cls; + char hostip[NI_MAXHOST]; + char *buf; + + if (sizeof (struct sockaddr_in) != addrlen) + return GNUNET_OK; /* Only consider IPv4 for now */ + if (0 != + getnameinfo (addr, addrlen, hostip, NI_MAXHOST, NULL, 0, NI_NUMERICHOST)) + GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "getnameinfo"); + if (NULL == rc->trusted_ip) + { + rc->trusted_ip = GNUNET_strdup (hostip); + return GNUNET_YES; + } + (void) GNUNET_asprintf (&buf, "%s; %s", rc->trusted_ip, hostip); + GNUNET_free (rc->trusted_ip); + rc->trusted_ip = buf; + return GNUNET_YES; +} + + +/** + * Callbacks of this type are called by GNUNET_TESTBED_is_host_habitable to + * inform whether the given host is habitable or not. The Handle returned by + * GNUNET_TESTBED_is_host_habitable() is invalid after this callback is called + * + * @param cls NULL + * @param host the host whose status is being reported; will be NULL if the host + * given to GNUNET_TESTBED_is_host_habitable() is NULL + * @param status GNUNET_YES if it is habitable; GNUNET_NO if not + */ +static void +host_habitable_cb (void *cls, const struct GNUNET_TESTBED_Host *host, + int status) +{ + struct RunContext *rc = cls; + struct GNUNET_TESTBED_Host **old_hosts; + unsigned int nhost; + + for (nhost = 0; nhost < rc->num_hosts; nhost++) + { + if (host == rc->hosts[nhost]) + break; + } + GNUNET_assert (nhost != rc->num_hosts); + rc->hc_handles[nhost] = NULL; + if (GNUNET_NO == status) + { + if ((NULL != host) && (NULL != GNUNET_TESTBED_host_get_hostname (host))) + LOG (GNUNET_ERROR_TYPE_ERROR, _("Host %s cannot start testbed\n"), + GNUNET_TESTBED_host_get_hostname (host)); + else + LOG (GNUNET_ERROR_TYPE_ERROR, + _("Testbed cannot be started on localhost\n")); + shutdown_now (rc); + return; + } + rc->reg_hosts++; + if (rc->reg_hosts < rc->num_hosts) + return; + GNUNET_free (rc->hc_handles); + rc->hc_handles = NULL; + rc->h = rc->hosts[0]; + rc->num_hosts--; + if (0 < rc->num_hosts) + { + old_hosts = rc->hosts; + rc->hosts = + GNUNET_malloc (sizeof (struct GNUNET_TESTBED_Host *) * rc->num_hosts); + memcpy (rc->hosts, &old_hosts[1], + (sizeof (struct GNUNET_TESTBED_Host *) * rc->num_hosts)); + GNUNET_free (old_hosts); + } + else + { + GNUNET_free (rc->hosts); + rc->hosts = NULL; + } + GNUNET_OS_network_interfaces_list (netint_proc, rc); + if (NULL == rc->trusted_ip) + rc->trusted_ip = GNUNET_strdup ("127.0.0.1"); + rc->cproc = + GNUNET_TESTBED_controller_start (rc->trusted_ip, rc->h, rc->cfg, + &controller_status_cb, rc); + GNUNET_free (rc->trusted_ip); + rc->trusted_ip = NULL; + if (NULL == rc->cproc) + { + LOG (GNUNET_ERROR_TYPE_ERROR, _("Cannot start the master controller")); + shutdown_now (rc); + } +} + /** * Convenience method for running a testbed with @@ -130,24 +1031,150 @@ GNUNET_TESTBED_destroy (struct GNUNET_TESTBED_Testbed *testbed) * or-ed values of "1LL" shifted by the * respective 'enum GNUNET_TESTBED_EventType' * (i.e. "(1LL << GNUNET_TESTBED_ET_CONNECT) || ...") - * @param cc controller callback to invoke on events + * @param cc controller callback to invoke on events; This callback is called + * for all peer start events even if GNUNET_TESTBED_ET_PEER_START isn't + * set in the event_mask as this is the only way get access to the + * handle of each peer * @param cc_cls closure for cc - * @param master task to run once the testbed is ready - * @param master_cls closure for 'task'. + * @param test_master this callback will be called once the test is ready + * @param test_master_cls closure for 'test_master'. */ void GNUNET_TESTBED_run (const char *host_filename, - const struct GNUNET_CONFIGURATION_Handle *cfg, - unsigned int num_peers, - uint64_t event_mask, - GNUNET_TESTBED_ControllerCallback cc, - void *cc_cls, - GNUNET_SCHEDULER_Task master, - void *master_cls) -{ - GNUNET_break (0); -} + const struct GNUNET_CONFIGURATION_Handle *cfg, + unsigned int num_peers, uint64_t event_mask, + GNUNET_TESTBED_ControllerCallback cc, void *cc_cls, + GNUNET_TESTBED_TestMaster test_master, + void *test_master_cls) +{ + struct RunContext *rc; + char *topology; + unsigned long long random_links; + unsigned int hid; + unsigned int nhost; + GNUNET_assert (num_peers > 0); + rc = GNUNET_malloc (sizeof (struct RunContext)); + if (NULL != host_filename) + { + rc->num_hosts = + GNUNET_TESTBED_hosts_load_from_file (host_filename, &rc->hosts); + if (0 == rc->num_hosts) + { + LOG (GNUNET_ERROR_TYPE_WARNING, + _("No hosts loaded. Need at least one host\n")); + goto error_cleanup; + } + } + else + rc->h = GNUNET_TESTBED_host_create (NULL, NULL, 0); + rc->cfg = GNUNET_CONFIGURATION_dup (cfg); + rc->num_peers = num_peers; + rc->event_mask = event_mask; + rc->cc = cc; + rc->cc_cls = cc_cls; + rc->test_master = test_master; + rc->test_master_cls = test_master_cls; + rc->state = RC_INIT; + rc->topology = GNUNET_TESTBED_TOPOLOGY_NONE; + if (GNUNET_OK == + GNUNET_CONFIGURATION_get_value_string (rc->cfg, "testbed", + "OVERLAY_TOPOLOGY", &topology)) + { + if (GNUNET_NO == GNUNET_TESTBED_topology_get_ (&rc->topology, topology)) + { + GNUNET_log_config_invalid (GNUNET_ERROR_TYPE_ERROR, "testbed", + "OVERLAY_TOPLOGY", + _ + ("Specified topology must be supported by testbed")); + } + GNUNET_free (topology); + } + switch (rc->topology) + { + case GNUNET_TESTBED_TOPOLOGY_ERDOS_RENYI: + case GNUNET_TESTBED_TOPOLOGY_SMALL_WORLD_RING: + case GNUNET_TESTBED_TOPOLOGY_SMALL_WORLD: + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_number (rc->cfg, "testbed", + "OVERLAY_RANDOM_LINKS", + &random_links)) + { + /* OVERLAY option RANDOM & SMALL_WORLD_RING requires OVERLAY_RANDOM_LINKS + * option to be set to the number of random links to be established */ + GNUNET_log_config_missing (GNUNET_ERROR_TYPE_ERROR, "testbed", + "OVERLAY_RANDOM_LINKS"); + goto error_cleanup; + } + if (random_links > UINT32_MAX) + { + GNUNET_break (0); /* Too big number */ + goto error_cleanup; + } + rc->random_links = (unsigned int) random_links; + break; + case GNUNET_TESTBED_TOPOLOGY_FROM_FILE: + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_string (rc->cfg, "testbed", + "OVERLAY_TOPOLOGY_FILE", + &rc->topo_file)) + { + GNUNET_log_config_missing (GNUNET_ERROR_TYPE_ERROR, "testbed", + "OVERLAY_TOPOLOGY_FILE"); + goto error_cleanup; + } + default: + /* Warn if OVERLAY_RANDOM_LINKS is present that it will be ignored */ + if (GNUNET_YES == + GNUNET_CONFIGURATION_have_value (rc->cfg, "testbed", + "OVERLAY_RANDOM_LINKS")) + LOG (GNUNET_ERROR_TYPE_WARNING, + "Ignoring value of `OVERLAY_RANDOM_LINKS' in given configuration\n"); + break; + } + if (NULL != host_filename) + { + rc->hc_handles = + GNUNET_malloc (sizeof (struct GNUNET_TESTBED_HostHabitableCheckHandle *) + * rc->num_hosts); + for (nhost = 0; nhost < rc->num_hosts; nhost++) + { + if (NULL == + (rc->hc_handles[nhost] = + GNUNET_TESTBED_is_host_habitable (rc->hosts[nhost], rc->cfg, + &host_habitable_cb, rc))) + { + GNUNET_break (0); + for (nhost = 0; nhost < rc->num_hosts; nhost++) + if (NULL != rc->hc_handles[nhost]) + GNUNET_TESTBED_is_host_habitable_cancel (rc->hc_handles[nhost]); + GNUNET_free (rc->hc_handles); + rc->hc_handles = NULL; + goto error_cleanup; + } + } + } + else + rc->cproc = + GNUNET_TESTBED_controller_start ("127.0.0.1", rc->h, rc->cfg, + &controller_status_cb, rc); + rc->shutdown_run_task = + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, &shutdown_run, + rc); + return; + +error_cleanup: + if (NULL != rc->h) + GNUNET_TESTBED_host_destroy (rc->h); + if (NULL != rc->hosts) + { + for (hid = 0; hid < rc->num_hosts; hid++) + if (NULL != rc->hosts[hid]) + GNUNET_TESTBED_host_destroy (rc->hosts[hid]); + GNUNET_free (rc->hosts); + } + GNUNET_free (rc); +} /* end of testbed_api_testbed.c */ diff --git a/src/testbed/testbed_api_topology.c b/src/testbed/testbed_api_topology.c index c0e9f72..9618f98 100644 --- a/src/testbed/testbed_api_topology.c +++ b/src/testbed/testbed_api_topology.c @@ -25,6 +25,768 @@ */ #include "platform.h" #include "gnunet_testbed_service.h" +#include "testbed_api.h" +#include "testbed_api_peers.h" +#include "testbed_api_operations.h" +#include "testbed_api_topology.h" + +/** + * Generic loggins shorthand + */ +#define LOG(kind,...) \ + GNUNET_log_from (kind, "testbed-api-topology", __VA_ARGS__) + + +/** + * Default number of retires + */ +#define DEFAULT_RETRY_CNT 3 + + +/** + * Context information for topology operations + */ +struct TopologyContext; + + +/** + * Representation of an overlay link + */ +struct OverlayLink +{ + + /** + * An operation corresponding to this link + */ + struct GNUNET_TESTBED_Operation *op; + + /** + * The topology context this link is a part of + */ + struct TopologyContext *tc; + + /** + * position of peer A's handle in peers array + */ + uint32_t A; + + /** + * position of peer B's handle in peers array + */ + uint32_t B; + +}; + + +struct RetryListEntry +{ + /** + * the next pointer for the DLL + */ + struct RetryListEntry *next; + + /** + * the prev pointer for the DLL + */ + struct RetryListEntry *prev; + + /** + * The link to be retired + */ + struct OverlayLink *link; +}; + + +/** + * Context information for topology operations + */ +struct TopologyContext +{ + /** + * The array of peers + */ + struct GNUNET_TESTBED_Peer **peers; + + /** + * An array of links; this array is of size link_array_size + */ + struct OverlayLink *link_array; + + /** + * The operation closure + */ + void *op_cls; + + /** + * topology generation completion callback + */ + GNUNET_TESTBED_TopologyCompletionCallback comp_cb; + + /** + * The closure for the above callback + */ + void *comp_cb_cls; + + /** + * DLL head for retry list + */ + struct RetryListEntry *rl_head; + + /** + * DLL tail for retry list + */ + struct RetryListEntry *rl_tail; + + /** + * The number of peers + */ + unsigned int num_peers; + + /** + * The size of the link array + */ + unsigned int link_array_size; + + /** + * How many retries to do before we give up + */ + unsigned int retry_cnt; + + /** + * Number of links to try + */ + unsigned int nlinks; + + /** + * How many links have been completed + */ + unsigned int ncompleted; + + /** + * Total successfully established overlay connections + */ + unsigned int nsuccess; + + /** + * Total failed overlay connections + */ + unsigned int nfailures; +}; + + +/** + * A array of names representing topologies. Should be in sync with enum + * GNUNET_TESTBED_TopologyOption + */ +const char *topology_strings[] = { + + /** + * A clique (everyone connected to everyone else). No options. If there are N + * peers this topology results in (N * (N -1)) connections. + */ + "CLIQUE", + + /** + * Small-world network (2d torus plus random links). Followed + * by the number of random links to add (unsigned int). + */ + "SMALL_WORLD", + + /** + * Small-world network (ring plus random links). Followed + * by the number of random links to add (unsigned int). + */ + "SMALL_WORLD_RING", + + /** + * Ring topology. No options. + */ + "RING", + + /** + * 2-d torus. No options. + */ + "2D_TORUS", + + /** + * Random graph. Followed by the number of random links to be established + * (unsigned int) + */ + "RANDOM", // GNUNET_TESTBED_TOPOLOGY_ERDOS_RENYI + + /** + * Certain percentage of peers are unable to communicate directly + * replicating NAT conditions. Followed by the fraction of + * NAT'ed peers (float). + */ + "INTERNAT", + + /** + * Scale free topology. No options. + */ + "SCALE_FREE", + + /** + * Straight line topology. No options. + */ + "LINE", + + /** + * Read a topology from a given file. Followed by the name of the file (const char *). + */ + "FROM_FILE", + + /** + * All peers are disconnected. No options. + */ + "NONE", + + /** + * End of strings + */ + NULL +}; + + +/** + * Callback to be called when an overlay_link operation complete + * + * @param cls element of the link_op array which points to the corresponding operation + * @param op the operation that has been finished + * @param emsg error message in case the operation has failed; will be NULL if + * operation has executed successfully. + */ +static void +overlay_link_completed (void *cls, struct GNUNET_TESTBED_Operation *op, + const char *emsg) +{ + struct OverlayLink *link = cls; + struct TopologyContext *tc; + struct RetryListEntry *retry_entry; + + GNUNET_assert (op == link->op); + GNUNET_TESTBED_operation_done (op); + link->op = NULL; + tc = link->tc; + if (NULL != emsg) + { + tc->nfailures++; + if (0 != tc->retry_cnt) + { + LOG (GNUNET_ERROR_TYPE_WARNING, + "Error while establishing a link: %s -- Retrying\n", emsg); + retry_entry = GNUNET_malloc (sizeof (struct RetryListEntry)); + retry_entry->link = link; + GNUNET_CONTAINER_DLL_insert_tail (tc->rl_head, tc->rl_tail, retry_entry); + } + } + else + tc->nsuccess++; + tc->ncompleted++; + if (tc->ncompleted < tc->nlinks) + return; + if ((0 != tc->retry_cnt) && (NULL != tc->rl_head)) + { + tc->retry_cnt--; + tc->ncompleted = 0; + tc->nlinks = 0; + while (NULL != (retry_entry = tc->rl_head)) + { + link = retry_entry->link; + link->op = + GNUNET_TESTBED_overlay_connect (tc->op_cls, &overlay_link_completed, + link, tc->peers[link->A], + tc->peers[link->B]); + tc->nlinks++; + GNUNET_CONTAINER_DLL_remove (tc->rl_head, tc->rl_tail, retry_entry); + GNUNET_free (retry_entry); + } + return; + } + if (NULL != tc->comp_cb) + { + tc->comp_cb (tc->comp_cb_cls, tc->nsuccess, tc->nfailures); + } +} + + + +/** + * Function called when a overlay connect operation is ready + * + * @param cls the Topology context + */ +static void +opstart_overlay_configure_topology (void *cls) +{ + struct TopologyContext *tc = cls; + unsigned int p; + + tc->nlinks = tc->link_array_size; + for (p = 0; p < tc->link_array_size; p++) + { + tc->link_array[p].op = + GNUNET_TESTBED_overlay_connect (tc->op_cls, &overlay_link_completed, + &tc->link_array[p], + tc->peers[tc->link_array[p].A], + tc->peers[tc->link_array[p].B]); + } +} + + +/** + * Callback which will be called when overlay connect operation is released + * + * @param cls the Topology context + */ +static void +oprelease_overlay_configure_topology (void *cls) +{ + struct TopologyContext *tc = cls; + struct RetryListEntry *retry_entry; + unsigned int p; + + while (NULL != (retry_entry = tc->rl_head)) + { + GNUNET_CONTAINER_DLL_remove (tc->rl_head, tc->rl_tail, retry_entry); + GNUNET_free (retry_entry); + } + if (NULL != tc->link_array) + { + for (p = 0; p < tc->link_array_size; p++) + if (NULL != tc->link_array[p].op) + GNUNET_TESTBED_operation_done (tc->link_array[p].op); + GNUNET_free (tc->link_array); + } + GNUNET_free (tc); +} + + +/** + * Populates the OverlayLink structure. + * + * @param link the OverlayLink + * @param A the peer A. Should be different from B + * @param B the peer B. Should be different from A + * @param tc the TopologyContext + * @return + */ +static void +make_link (struct OverlayLink *link, uint32_t A, uint32_t B, + struct TopologyContext *tc) +{ + GNUNET_assert (A != B); + LOG (GNUNET_ERROR_TYPE_DEBUG, "Connecting peer %u to %u\n", B, A); + link->A = A; + link->B = B; + link->op = NULL; + link->tc = tc; +} + + +/** + * Generates line topology + * + * @param tc the topology context + */ +static void +gen_topo_line (struct TopologyContext *tc) +{ + unsigned int cnt; + + tc->link_array_size = tc->num_peers - 1; + tc->link_array = + GNUNET_malloc (sizeof (struct OverlayLink) * tc->link_array_size); + for (cnt = 0; cnt < (tc->num_peers - 1); cnt++) + make_link (&tc->link_array[cnt], cnt, cnt + 1, tc); +} + + +/** + * Generates ring topology + * + * @param tc the topology context + */ +static void +gen_topo_ring (struct TopologyContext *tc) +{ + gen_topo_line (tc); + tc->link_array_size++; + tc->link_array = + GNUNET_realloc (tc->link_array, + sizeof (struct OverlayLink) * tc->link_array_size); + make_link (&tc->link_array[tc->link_array_size - 1], tc->num_peers - 1, 0, + tc); +} + + +/** + * Returns the number of links that are required to generate a 2d torus for the + * given number of peers. Also returns the arrangment (number of rows and the + * length of each row) + * + * @param num_peers number of peers + * @param rows number of rows in the 2d torus. Can be NULL + * @param rows_len the length of each row. This array will be allocated + * fresh. The caller should free it. Can be NULL + */ +unsigned int +GNUNET_TESTBED_2dtorus_calc_links (unsigned int num_peers, unsigned int *rows, + unsigned int **rows_len) +{ + double sq; + unsigned int sq_floor; + unsigned int _rows; + unsigned int *_rows_len; + unsigned int x; + unsigned int y; + unsigned int _num_peers; + unsigned int cnt; + + sq = sqrt (num_peers); + sq = floor (sq); + sq_floor = (unsigned int) sq; + _rows = (sq_floor + 1); + _rows_len = GNUNET_malloc (sizeof (unsigned int) * _rows); + for (y = 0; y < _rows - 1; y++) + _rows_len[y] = sq_floor; + _num_peers = sq_floor * sq_floor; + cnt = 2 * _num_peers; + x = 0; + y = 0; + while (_num_peers < num_peers) + { + if (x < y) + _rows_len[_rows - 1] = ++x; + else + _rows_len[y++]++; + _num_peers++; + } + cnt += (x < 2) ? x : 2 * x; + cnt += (y < 2) ? y : 2 * y; + if (0 == _rows_len[_rows - 1]) + _rows--; + if (NULL != rows) + *rows = _rows; + if (NULL != rows_len) + *rows_len = _rows_len; + else + GNUNET_free (_rows_len); + return cnt; +} + + +/** + * Generates ring topology + * + * @param tc the topology context + */ +static void +gen_topo_2dtorus (struct TopologyContext *tc) +{ + unsigned int rows; + unsigned int *rows_len; + unsigned int x; + unsigned int y; + unsigned int cnt; + unsigned int offset; + + tc->link_array_size = + GNUNET_TESTBED_2dtorus_calc_links (tc->num_peers, &rows, &rows_len); + tc->link_array = + GNUNET_malloc (sizeof (struct OverlayLink) * tc->link_array_size); + cnt = 0; + offset = 0; + for (y = 0; y < rows; y++) + { + for (x = 0; x < rows_len[y] - 1; x++) + { + make_link (&tc->link_array[cnt], offset + x, offset + x + 1, tc); + cnt++; + } + if (0 == x) + break; + make_link (&tc->link_array[cnt], offset + x, offset, tc); + cnt++; + offset += rows_len[y]; + } + for (x = 0; x < rows_len[0]; x++) + { + offset = 0; + for (y = 0; y < rows - 1; y++) + { + if (x >= rows_len[y + 1]) + break; + GNUNET_assert (x < rows_len[y + 1]); + make_link (&tc->link_array[cnt], offset + x, offset + rows_len[y] + x, + tc); + offset += rows_len[y]; + cnt++; + } + if (0 == offset) + break; + make_link (&tc->link_array[cnt], offset + x, x, tc); + cnt++; + } + GNUNET_assert (cnt == tc->link_array_size); + GNUNET_free (rows_len); +} + + +/** + * Generates ring topology + * + * @param tc the topology context + * @param links the number of random links to establish + * @param append GNUNET_YES to add links to existing link array; GNUNET_NO to + * create a new link array + */ +static void +gen_topo_random (struct TopologyContext *tc, unsigned int links, int append) +{ + unsigned int cnt; + unsigned int index; + uint32_t A_rand; + uint32_t B_rand; + + if (GNUNET_YES == append) + { + GNUNET_assert ((0 < tc->link_array_size) && (NULL != tc->link_array)); + index = tc->link_array_size; + tc->link_array_size += links; + tc->link_array = + GNUNET_realloc (tc->link_array, + sizeof (struct OverlayLink) * tc->link_array_size); + } + else + { + GNUNET_assert ((0 == tc->link_array_size) && (NULL == tc->link_array)); + index = 0; + tc->link_array_size = links; + tc->link_array = + GNUNET_malloc (sizeof (struct OverlayLink) * tc->link_array_size); + } + for (cnt = 0; cnt < links; cnt++) + { + do + { + A_rand = + GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK, tc->num_peers); + B_rand = + GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK, tc->num_peers); + } + while (A_rand == B_rand); + make_link (&tc->link_array[index + cnt], A_rand, B_rand, tc); + } +} + + +/** + * Generates scale free network. Its construction is described in: + * + * "Emergence of Scaling in Random Networks." Science 286, 509-512, 1999. + * + * @param tc the topology context + */ +static void +gen_scale_free (struct TopologyContext *tc) +{ + double random; + double probability; + unsigned int cnt; + unsigned int previous_connections; + unsigned int i; + uint16_t *popularity; + + popularity = GNUNET_malloc (sizeof (uint16_t) * tc->num_peers); + /* Initially connect peer 1 to peer 0 */ + tc->link_array_size = 1; + tc->link_array = GNUNET_malloc (sizeof (struct OverlayLink)); + make_link (&tc->link_array[0], 0, 1, tc); + popularity[0]++; /* increase popularity of 0 as 1 connected to it */ + for (cnt = 1; cnt < tc->num_peers; cnt++) + { + previous_connections = tc->link_array_size; + for (i = 0; i < cnt; i++) + { + probability = ((double) popularity[i]) / ((double) previous_connections); + random = + ((double) + GNUNET_CRYPTO_random_u64 (GNUNET_CRYPTO_QUALITY_WEAK, + UINT64_MAX)) / ((double) UINT64_MAX); + if (random < probability) + { + tc->link_array_size++; + tc->link_array = + GNUNET_realloc (tc->link_array, + (sizeof (struct OverlayLink) * + tc->link_array_size)); + make_link (&tc->link_array[tc->link_array_size - 1], cnt, i, tc); + popularity[cnt]++; + } + } + } + GNUNET_free (popularity); +} + + +/** + * Generates topology from the given file + * + * @param tc the topology context + * @param filename the filename of the file containing topology data + */ +static void +gen_topo_from_file (struct TopologyContext *tc, const char *filename) +{ + char *data; + char *end; + char *buf; + uint64_t fs; + uint64_t offset; + unsigned long int peer_id; + unsigned long int other_peer_id; + enum ParseState + { + + /** + * We read the peer index + */ + PEER_INDEX, + + /** + * We read the other peer indices + */ + OTHER_PEER_INDEX, + + } state; + int status; + + status = GNUNET_SYSERR; + if (GNUNET_YES != GNUNET_DISK_file_test (filename)) + { + LOG (GNUNET_ERROR_TYPE_ERROR, _("Topology file %s not found\n"), filename); + return; + } + if (GNUNET_OK != + GNUNET_DISK_file_size (filename, &fs, GNUNET_YES, GNUNET_YES)) + { + LOG (GNUNET_ERROR_TYPE_ERROR, _("Topology file %s has no data\n"), + filename); + return; + } + data = GNUNET_malloc (fs); + if (fs != GNUNET_DISK_fn_read (filename, data, fs)) + { + LOG (GNUNET_ERROR_TYPE_ERROR, _("Topology file %s cannot be read\n"), + filename); + goto _exit; + } + + offset = 0; + peer_id = 0; + state = PEER_INDEX; + buf = data; + while (offset < fs) + { + if (0 != isspace (data[offset])) + { + offset++; + continue; + } + switch (state) + { + case PEER_INDEX: + buf = strchr (&data[offset], ':'); + if (NULL == buf) + { + LOG (GNUNET_ERROR_TYPE_ERROR, + _("Failed to read peer index from toology file: %s"), filename); + goto _exit; + } + *buf = '\0'; + errno = 0; + peer_id = (unsigned int) strtoul (&data[offset], &end, 10); + if (0 != errno) + { + LOG (GNUNET_ERROR_TYPE_ERROR, + _("Value in given topology file: %s out of range\n"), filename); + goto _exit; + } + if (&data[offset] == end) + { + LOG (GNUNET_ERROR_TYPE_ERROR, + _("Failed to read peer index from topology file: %s"), filename); + goto _exit; + } + if (tc->num_peers <= peer_id) + { + LOG (GNUNET_ERROR_TYPE_ERROR, + _("Topology file needs more peers than given ones\n"), filename); + goto _exit; + } + state = OTHER_PEER_INDEX; + offset += ((unsigned int) (buf - &data[offset])) + 1; + break; + case OTHER_PEER_INDEX: + errno = 0; + other_peer_id = (unsigned int) strtoul (&data[offset], &end, 10); + if (0 != errno) + { + LOG (GNUNET_ERROR_TYPE_ERROR, + _("Value in given topology file: %s out of range\n"), filename); + goto _exit; + } + if (&data[offset] == end) + { + LOG (GNUNET_ERROR_TYPE_ERROR, + _("Failed to read peer index from topology file: %s"), filename); + goto _exit; + } + if (tc->num_peers <= other_peer_id) + { + LOG (GNUNET_ERROR_TYPE_ERROR, + _("Topology file needs more peers than given ones\n"), filename); + goto _exit; + } + if (peer_id != other_peer_id) + { + tc->link_array_size++; + tc->link_array = + GNUNET_realloc (tc->link_array, + sizeof (struct OverlayLink) * tc->link_array_size); + offset += end - &data[offset]; + make_link (&tc->link_array[tc->link_array_size - 1], peer_id, + other_peer_id, tc); + } + else + LOG (GNUNET_ERROR_TYPE_WARNING, + _("Ignoring to connect peer %u to peer %u\n"), peer_id, + other_peer_id); + while (('\n' != data[offset]) && ('|' != data[offset]) && (offset < fs)) + offset++; + if ('\n' == data[offset]) + state = PEER_INDEX; + else if ('|' == data[offset]) + { + state = OTHER_PEER_INDEX; + offset++; + } + break; + } + } + status = GNUNET_OK; + +_exit: + GNUNET_free (data); + if (GNUNET_OK != status) + { + LOG (GNUNET_ERROR_TYPE_WARNING, "Removing link data read from the file\n"); + tc->link_array_size = 0; + GNUNET_free_non_null (tc->link_array); + tc->link_array = NULL; + } +} /** @@ -40,10 +802,12 @@ */ struct GNUNET_TESTBED_Operation * GNUNET_TESTBED_underlay_configure_topology_va (void *op_cls, - unsigned int num_peers, - struct GNUNET_TESTBED_Peer **peers, - enum GNUNET_TESTBED_TopologyOption topo, - va_list ap) + unsigned int num_peers, + struct GNUNET_TESTBED_Peer + **peers, + enum + GNUNET_TESTBED_TopologyOption + topo, va_list ap) { GNUNET_break (0); return NULL; @@ -63,10 +827,10 @@ GNUNET_TESTBED_underlay_configure_topology_va (void *op_cls, */ struct GNUNET_TESTBED_Operation * GNUNET_TESTBED_underlay_configure_topology (void *op_cls, - unsigned int num_peers, - struct GNUNET_TESTBED_Peer **peers, - enum GNUNET_TESTBED_TopologyOption topo, - ...) + unsigned int num_peers, + struct GNUNET_TESTBED_Peer **peers, + enum GNUNET_TESTBED_TopologyOption + topo, ...) { GNUNET_break (0); return NULL; @@ -78,24 +842,144 @@ GNUNET_TESTBED_underlay_configure_topology (void *op_cls, * This function then connects the given peers in the P2P overlay * using the given topology. * - * @param op_cls closure argument to give with the operation event + * @param op_cls closure argument to give with the peer connect operation events + * generated through this function * @param num_peers number of peers in 'peers' * @param peers array of 'num_peers' with the peers to configure + * @param max_connections the maximums number of overlay connections that will + * be made to achieve the given topology + * @param comp_cb the completion callback to call when the topology generation + * is completed + * @param comp_cb_cls closure for the above completion callback * @param topo desired underlay topology to use * @param va topology-specific options - * @return handle to the operation, NULL if connecting these + * @return handle to the operation, NULL if connecting these * peers is fundamentally not possible at this time (peers - * not running or underlay disallows) + * not running or underlay disallows) or if num_peers is less than 2 */ struct GNUNET_TESTBED_Operation * GNUNET_TESTBED_overlay_configure_topology_va (void *op_cls, - unsigned int num_peers, - struct GNUNET_TESTBED_Peer *peers, - enum GNUNET_TESTBED_TopologyOption topo, - va_list va) + unsigned int num_peers, + struct GNUNET_TESTBED_Peer **peers, + unsigned int *max_connections, + GNUNET_TESTBED_TopologyCompletionCallback + comp_cb, + void *comp_cb_cls, + enum GNUNET_TESTBED_TopologyOption topo, + va_list va) { - GNUNET_break (0); - return NULL; + struct TopologyContext *tc; + struct GNUNET_TESTBED_Operation *op; + struct GNUNET_TESTBED_Controller *c; + enum GNUNET_TESTBED_TopologyOption secondary_option; + unsigned int cnt; + + if (num_peers < 2) + return NULL; + c = peers[0]->controller; + tc = GNUNET_malloc (sizeof (struct TopologyContext)); + tc->peers = peers; + tc->num_peers = num_peers; + tc->op_cls = op_cls; + tc->retry_cnt = DEFAULT_RETRY_CNT; + switch (topo) + { + case GNUNET_TESTBED_TOPOLOGY_LINE: + gen_topo_line (tc); + break; + case GNUNET_TESTBED_TOPOLOGY_RING: + gen_topo_ring (tc); + break; + case GNUNET_TESTBED_TOPOLOGY_ERDOS_RENYI: + gen_topo_random (tc, va_arg (va, unsigned int), GNUNET_NO); + + break; + case GNUNET_TESTBED_TOPOLOGY_SMALL_WORLD_RING: + gen_topo_ring (tc); + gen_topo_random (tc, va_arg (va, unsigned int), GNUNET_YES); + + break; + case GNUNET_TESTBED_TOPOLOGY_CLIQUE: + tc->link_array_size = num_peers * (num_peers - 1); + tc->link_array = + GNUNET_malloc (sizeof (struct OverlayLink) * tc->link_array_size); + { + unsigned int offset; + + offset = 0; + for (cnt = 0; cnt < num_peers; cnt++) + { + unsigned int neighbour; + + for (neighbour = 0; neighbour < num_peers; neighbour++) + { + if (neighbour == cnt) + continue; + tc->link_array[offset].A = cnt; + tc->link_array[offset].B = neighbour; + tc->link_array[offset].tc = tc; + offset++; + } + } + } + break; + case GNUNET_TESTBED_TOPOLOGY_2D_TORUS: + gen_topo_2dtorus (tc); + break; + case GNUNET_TESTBED_TOPOLOGY_SMALL_WORLD: + gen_topo_2dtorus (tc); + gen_topo_random (tc, va_arg (va, unsigned int), GNUNET_YES); + + break; + case GNUNET_TESTBED_TOPOLOGY_SCALE_FREE: + gen_scale_free (tc); + break; + case GNUNET_TESTBED_TOPOLOGY_FROM_FILE: + { + const char *filename; + + filename = va_arg (va, const char *); + + GNUNET_assert (NULL != filename); + gen_topo_from_file (tc, filename); + } + break; + default: + GNUNET_break (0); + GNUNET_free (tc); + return NULL; + } + do + { + secondary_option = va_arg (va, enum GNUNET_TESTBED_TopologyOption); + + switch (secondary_option) + { + case GNUNET_TESTBED_TOPOLOGY_RETRY_CNT: + tc->retry_cnt = va_arg (va, unsigned int); + break; + case GNUNET_TESTBED_TOPOLOGY_OPTION_END: + break; + default: + GNUNET_break (0); /* Should not use any other option apart from + * the ones handled here */ + GNUNET_free_non_null (tc->link_array); + GNUNET_free (tc); + return NULL; + } + } + while (GNUNET_TESTBED_TOPOLOGY_OPTION_END != secondary_option); + op = GNUNET_TESTBED_operation_create_ (tc, + &opstart_overlay_configure_topology, + &oprelease_overlay_configure_topology); + GNUNET_TESTBED_operation_queue_insert_ + (c->opq_parallel_topology_config_operations, op); + GNUNET_TESTBED_operation_begin_wait_ (op); + LOG (GNUNET_ERROR_TYPE_DEBUG, "Generated %u connections\n", + tc->link_array_size); + if (NULL != max_connections) + *max_connections = tc->link_array_size; + return op; } @@ -104,24 +988,88 @@ GNUNET_TESTBED_overlay_configure_topology_va (void *op_cls, * This function then connects the given peers in the P2P overlay * using the given topology. * - * @param op_cls closure argument to give with the operation event + * @param op_cls closure argument to give with the peer connect operation events + * generated through this function * @param num_peers number of peers in 'peers' * @param peers array of 'num_peers' with the peers to configure + * @param max_connections the maximums number of overlay connections that will + * be made to achieve the given topology + * @param comp_cb the completion callback to call when the topology generation + * is completed + * @param comp_cb_cls closure for the above completion callback * @param topo desired underlay topology to use * @param ... topology-specific options - * @return handle to the operation, NULL if connecting these + * @return handle to the operation, NULL if connecting these * peers is fundamentally not possible at this time (peers - * not running or underlay disallows) + * not running or underlay disallows) or if num_peers is less than 2 */ struct GNUNET_TESTBED_Operation * GNUNET_TESTBED_overlay_configure_topology (void *op_cls, - unsigned int num_peers, - struct GNUNET_TESTBED_Peer *peers, - enum GNUNET_TESTBED_TopologyOption topo, - ...) + unsigned int num_peers, + struct GNUNET_TESTBED_Peer **peers, + unsigned int *max_connections, + GNUNET_TESTBED_TopologyCompletionCallback + comp_cb, + void *comp_cb_cls, + enum GNUNET_TESTBED_TopologyOption topo, + ...) { - GNUNET_break (0); - return NULL; + struct GNUNET_TESTBED_Operation *op; + va_list vargs; + + GNUNET_assert (topo < GNUNET_TESTBED_TOPOLOGY_OPTION_END); + va_start (vargs, topo); + op = GNUNET_TESTBED_overlay_configure_topology_va (op_cls, num_peers, peers, + max_connections, + comp_cb, comp_cb_cls, + topo, + vargs); + va_end (vargs); + return op; +} + + +/** + * Get a topology from a string input. + * + * @param topology where to write the retrieved topology + * @param topology_string The string to attempt to + * get a configuration value from + * @return GNUNET_YES if topology string matched a + * known topology, GNUNET_NO if not + */ +int +GNUNET_TESTBED_topology_get_ (enum GNUNET_TESTBED_TopologyOption *topology, + const char *topology_string) +{ + unsigned int cnt; + + for (cnt = 0; NULL != topology_strings[cnt]; cnt++) + { + if (0 == strcasecmp (topology_string, topology_strings[cnt])) + { + if (NULL != topology) + *topology = (enum GNUNET_TESTBED_TopologyOption) cnt; + return GNUNET_YES; + } + } + return GNUNET_NO; +} + + +/** + * Returns the string corresponding to the given topology + * + * @param topology the topology + * @return the string (freshly allocated) of given topology; NULL if topology cannot be + * expressed as a string + */ +char * +GNUNET_TESTBED_topology_to_str_ (enum GNUNET_TESTBED_TopologyOption topology) +{ + if (GNUNET_TESTBED_TOPOLOGY_OPTION_END <= topology) + return NULL; + return GNUNET_strdup (topology_strings[topology]); } /* end of testbed_api_topology.c */ diff --git a/src/testbed/testbed_api_topology.h b/src/testbed/testbed_api_topology.h new file mode 100644 index 0000000..b5f3685 --- /dev/null +++ b/src/testbed/testbed_api_topology.h @@ -0,0 +1,70 @@ +/* + This file is part of GNUnet + (C) 2008--2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. + */ + +/** + * @file testbed/testbed_api_topology.h + * @brief header for intra library exported functions + * @author Sree Harsha Totakura + */ + +#ifndef TESTBED_API_TOPOLOGY_H +#define TESTBED_API_TOPOLOGY_H + +/** + * Returns the number of links that are required to generate a 2d torus for the + * given number of peers. Also returns the arrangment (number of rows and the + * length of each row) + * + * @param num_peers number of peers + * @param rows number of rows in the 2d torus. Can be NULL. + * @param rows_len the length of each row. This array will be allocated + * fresh. The caller should free it. Can be NULL. + */ +unsigned int +GNUNET_TESTBED_2dtorus_calc_links (unsigned int num_peers, unsigned int *rows, + unsigned int **rows_len); + + +/** + * Get a topology from a string input. + * + * @param topology where to write the retrieved topology + * @param topology_string The string to attempt to + * get a configuration value from + * @return GNUNET_YES if topology string matched a + * known topology, GNUNET_NO if not + */ +int +GNUNET_TESTBED_topology_get_ (enum GNUNET_TESTBED_TopologyOption *topology, + const char *topology_string); + + +/** + * Returns the string corresponding to the given topology + * + * @param topology the topology + * @return the string (freshly allocated) of given topology; NULL if topology cannot be + * expressed as a string + */ +char * +GNUNET_TESTBED_topology_to_str_ (enum GNUNET_TESTBED_TopologyOption topology); + +#endif +/* end of testbed_api_topology.h */ diff --git a/src/testbed/testbed_helper.h b/src/testbed/testbed_helper.h new file mode 100644 index 0000000..6b476cd --- /dev/null +++ b/src/testbed/testbed_helper.h @@ -0,0 +1,89 @@ +/* + This file is part of GNUnet + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. + */ + +/** + * @file testbed/testbed_helper.h + * @brief Message formats for communication between testbed api and + * gnunet-helper-testbed process + * @author Sree Harsha Totakura + */ + +#ifndef TESTBED_HELPER_H +#define TESTBED_HELPER_H + +GNUNET_NETWORK_STRUCT_BEGIN +/** + * Initialization message for gnunet-helper-testbed to start testbed service + */ + struct GNUNET_TESTBED_HelperInit +{ + /** + * Type is GNUNET_MESSAGE_TYPE_TESTBED_HELPER_INIT + */ + struct GNUNET_MessageHeader header; + + /** + * The controller hostname size excluding the NULL termination character - + * strlen (hostname); cannot be zero + */ + uint16_t trusted_ip_size GNUNET_PACKED; + + /** + * The hostname size excluding the NULL termination character - strlen + * (hostname); cannot be zero + */ + uint16_t hostname_size GNUNET_PACKED; + + /** + * The size of the uncompressed configuration + */ + uint16_t config_size GNUNET_PACKED; + + /* Followed by NULL terminated trusted ip */ + + /* Followed by hostname of the machine on which helper runs. This is not NULL + * terminated */ + + /* Followed by serialized and compressed configuration which should be + * config_size long when un-compressed */ +}; + +/** + * Reply message from helper process + */ +struct GNUNET_TESTBED_HelperReply +{ + /** + * Type is GNUNET_MESSAGE_TYPE_TESTBED_HELPER_REPLY + */ + struct GNUNET_MessageHeader header; + + /** + * Size of the uncompressed configuration + */ + uint16_t config_size GNUNET_PACKED; + + /* Followed by compressed configuration which should be config_size long when + * un-compressed */ +}; + +GNUNET_NETWORK_STRUCT_END +#endif +/* end of testbed_helper.h */ diff --git a/src/testing/Makefile.am b/src/testing/Makefile.am index 572c033..2b0cb98 100644 --- a/src/testing/Makefile.am +++ b/src/testing/Makefile.am @@ -14,97 +14,32 @@ pkgcfgdir= $(pkgdatadir)/config.d/ dist_pkgcfg_DATA = \ testing.conf -if HAVE_EXPENSIVE_TESTS - EXPENSIVE_TESTS = \ - test_testing_topology_stability \ - test_testing_topology_clique_random \ - test_testing_topology_clique_minimum \ - test_testing_topology_clique_dfs \ - test_testing_topology_churn \ - test_testing_topology_line \ - test_testing_topology_blacklist \ - test_testing_group_remote \ - test_testing_topology_ring \ - test_testing_topology_2d_torus \ - test_testing_topology_small_world_ring \ - test_testing_topology_small_world_torus \ - test_testing_topology_erdos_renyi \ - test_testing_topology_internat \ - test_testing_topology_scale_free -endif - lib_LTLIBRARIES = \ - libgnunettesting.la \ - libgnunettesting_new.la + libgnunettesting.la libgnunettesting_la_SOURCES = \ - helper.c \ - testing.c \ - testing_group.c \ - testing_peergroup.c -libgnunettesting_la_LIBADD = $(XLIB) \ - $(top_builddir)/src/core/libgnunetcore.la \ - $(top_builddir)/src/statistics/libgnunetstatistics.la \ - $(top_builddir)/src/transport/libgnunettransport.la \ - $(top_builddir)/src/hello/libgnunethello.la \ - -lm \ - $(top_builddir)/src/util/libgnunetutil.la + testing.c +libgnunettesting_la_LIBADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(LTLIBINTL) libgnunettesting_la_LDFLAGS = \ $(GN_LIB_LDFLAGS) \ - -version-info 0:1:0 - - -libgnunettesting_new_la_SOURCES = \ - testing_new.c -libgnunettesting_new_la_LIBADD = \ - $(top_builddir)/src/util/libgnunetutil.la -libgnunettesting_new_la_LDFLAGS = \ - $(GN_LIB_LDFLAGS) \ - -version-info 0:1:0 - + -version-info 2:0:1 bin_PROGRAMS = \ + gnunet-testing-run-service \ gnunet-testing -check_PROGRAMS = \ - test_testing \ - test_testing_connect \ - test_testing_reconnect \ - test_testing_group \ - test_testing_peergroup \ - test_testing_topology_stability \ - test_testing_topology_clique \ - test_testing_topology_clique_random \ - test_testing_topology_clique_minimum \ - test_testing_topology_clique_dfs \ - test_testing_topology_churn \ - test_testing_topology_line \ - test_testing_topology_blacklist \ - test_testing_group_remote \ - test_testing_2dtorus \ - test_testing_topology_ring \ - test_testing_topology_2d_torus \ - test_testing_topology_small_world_ring \ - test_testing_topology_small_world_torus \ - test_testing_topology_erdos_renyi \ - test_testing_topology_internat \ - test_testing_topology_none \ - test_testing_topology_scale_free \ - test_testing_new_portreservation \ - test_testing_new_peerstartup \ - test_testing_new_servicestartup -if ENABLE_TEST_RUN -TESTS = \ - test_testing \ - test_testing_connect \ - test_testing_reconnect \ - test_testing_group \ - test_testing_peergroup \ - test_testing_new_portreservation \ - test_testing_new_peerstartup \ - test_testing_new_servicestartup -endif +gnunet_testing_run_service_SOURCES = \ + gnunet-testing-run-service.c + +gnunet_testing_run_service_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(GN_LIBINTL) +gnunet_testing_run_service_DEPENDENCIES = \ + libgnunettesting.la gnunet_testing_SOURCES = \ gnunet-testing.c @@ -116,197 +51,36 @@ gnunet_testing_DEPENDENCIES = \ libgnunettesting.la -test_testing_SOURCES = \ - test_testing.c -test_testing_LDADD = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/util/libgnunetutil.la - -test_testing_connect_SOURCES = \ - test_testing_connect.c -test_testing_connect_LDADD = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/util/libgnunetutil.la - -test_testing_reconnect_SOURCES = \ - test_testing_reconnect.c -test_testing_reconnect_LDADD = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/util/libgnunetutil.la - -test_testing_group_SOURCES = \ - test_testing_group.c -test_testing_group_LDADD = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/util/libgnunetutil.la - -test_testing_peergroup_SOURCES = \ - test_testing_peergroup.c -test_testing_peergroup_LDADD = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/util/libgnunetutil.la - -test_testing_topology_clique_SOURCES = \ - test_testing_topology.c -test_testing_topology_clique_LDADD = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/core/libgnunetcore.la \ - $(top_builddir)/src/util/libgnunetutil.la - -test_testing_topology_stability_SOURCES = \ - test_testing_topology.c -test_testing_topology_stability_LDADD = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/core/libgnunetcore.la \ - $(top_builddir)/src/util/libgnunetutil.la - -test_testing_topology_blacklist_SOURCES = \ - test_testing_topology_blacklist.c -test_testing_topology_blacklist_LDADD = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/util/libgnunetutil.la - -test_testing_topology_churn_SOURCES = \ - test_testing_topology_churn.c -test_testing_topology_churn_LDADD = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/util/libgnunetutil.la - -test_testing_topology_clique_random_SOURCES = \ - test_testing_topology.c -test_testing_topology_clique_random_LDADD = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/core/libgnunetcore.la \ - $(top_builddir)/src/util/libgnunetutil.la - -test_testing_topology_clique_minimum_SOURCES = \ - test_testing_topology.c -test_testing_topology_clique_minimum_LDADD = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/core/libgnunetcore.la \ - $(top_builddir)/src/util/libgnunetutil.la - -test_testing_topology_clique_dfs_SOURCES = \ - test_testing_topology.c -test_testing_topology_clique_dfs_LDADD = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/core/libgnunetcore.la \ - $(top_builddir)/src/util/libgnunetutil.la - -test_testing_topology_line_SOURCES = \ - test_testing_topology.c -test_testing_topology_line_LDADD = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/core/libgnunetcore.la \ - $(top_builddir)/src/util/libgnunetutil.la - - -test_testing_group_remote_SOURCES = \ - test_testing_group_remote.c -test_testing_group_remote_LDADD = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/util/libgnunetutil.la - -test_testing_2dtorus_SOURCES = \ - test_testing_2dtorus.c -test_testing_2dtorus_LDADD = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/util/libgnunetutil.la - -test_testing_topology_ring_SOURCES = \ - test_testing_topology.c -test_testing_topology_ring_LDADD = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/core/libgnunetcore.la \ - $(top_builddir)/src/util/libgnunetutil.la - -test_testing_topology_2d_torus_SOURCES = \ - test_testing_topology.c -test_testing_topology_2d_torus_LDADD = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/core/libgnunetcore.la \ - $(top_builddir)/src/util/libgnunetutil.la - -test_testing_topology_small_world_ring_SOURCES = \ - test_testing_topology.c -test_testing_topology_small_world_ring_LDADD = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/core/libgnunetcore.la \ - $(top_builddir)/src/util/libgnunetutil.la - -test_testing_topology_small_world_torus_SOURCES = \ - test_testing_topology.c -test_testing_topology_small_world_torus_LDADD = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/core/libgnunetcore.la \ - $(top_builddir)/src/util/libgnunetutil.la +check_PROGRAMS = \ + test_testing_portreservation \ + test_testing_peerstartup \ + test_testing_servicestartup -test_testing_topology_internat_SOURCES = \ - test_testing_topology.c -test_testing_topology_internat_LDADD = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/core/libgnunetcore.la \ - $(top_builddir)/src/util/libgnunetutil.la +if ENABLE_TEST_RUN +TESTS = \ + test_testing_portreservation \ + test_testing_peerstartup \ + test_testing_servicestartup +endif -test_testing_topology_erdos_renyi_SOURCES = \ - test_testing_topology.c -test_testing_topology_erdos_renyi_LDADD = \ +test_testing_portreservation_SOURCES = \ + test_testing_portreservation.c +test_testing_portreservation_LDADD = \ $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/core/libgnunetcore.la \ $(top_builddir)/src/util/libgnunetutil.la -test_testing_topology_scale_free_SOURCES = \ - test_testing_topology.c -test_testing_topology_scale_free_LDADD = \ +test_testing_peerstartup_SOURCES = \ + test_testing_peerstartup.c +test_testing_peerstartup_LDADD = \ $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/core/libgnunetcore.la \ $(top_builddir)/src/util/libgnunetutil.la -test_testing_topology_none_SOURCES = \ - test_testing_topology.c -test_testing_topology_none_LDADD = \ +test_testing_servicestartup_SOURCES = \ + test_testing_servicestartup.c +test_testing_servicestartup_LDADD = \ $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/core/libgnunetcore.la \ - $(top_builddir)/src/util/libgnunetutil.la - -test_testing_new_portreservation_SOURCES = \ - test_testing_new_portreservation.c -test_testing_new_portreservation_LDADD = \ - $(top_builddir)/src/testing/libgnunettesting_new.la \ - $(top_builddir)/src/util/libgnunetutil.la - -test_testing_new_peerstartup_SOURCES = \ - test_testing_new_peerstartup.c -test_testing_new_peerstartup_LDADD = \ - $(top_builddir)/src/testing/libgnunettesting_new.la \ $(top_builddir)/src/util/libgnunetutil.la -test_testing_new_servicestartup_SOURCES = \ - test_testing_new_servicestartup.c -test_testing_new_servicestartup_LDADD = \ - $(top_builddir)/src/testing/libgnunettesting_new.la \ - $(top_builddir)/src/util/libgnunetutil.la EXTRA_DIST = \ - test_testing_defaults.conf \ - test_testing_data.conf \ - test_testing_connect_peer1.conf \ - test_testing_connect_peer2.conf \ - test_testing_2dtorus.conf \ - test_testing_data_topology_clique.conf \ - test_testing_data_topology_clique_random.conf \ - test_testing_data_topology_clique_minimum.conf \ - test_testing_data_topology_clique_dfs.conf \ - test_testing_data_topology_ring.conf \ - test_testing_data_topology_2d_torus.conf \ - test_testing_data_topology_small_world_ring.conf \ - test_testing_data_topology_small_world_torus.conf \ - test_testing_data_topology_erdos_renyi.conf \ - test_testing_data_topology_internat.conf \ - test_testing_data_topology_scale_free.conf \ - test_testing_data_topology_blacklist.conf \ - test_testing_data_topology_churn.conf \ - test_testing_data_topology_none.conf \ - test_testing_data_remote.conf \ - test_testing_data_topology_stability.conf \ - test_testing_peergroup_data.conf + test_testing_defaults.conf diff --git a/src/testing/Makefile.in b/src/testing/Makefile.in index 459066f..66ee17c 100644 --- a/src/testing/Makefile.in +++ b/src/testing/Makefile.in @@ -1,9 +1,9 @@ -# Makefile.in generated by automake 1.11.1 from Makefile.am. +# Makefile.in generated by automake 1.11.6 from Makefile.am. # @configure_input@ # Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, -# 2003, 2004, 2005, 2006, 2007, 2008, 2009 Free Software Foundation, -# Inc. +# 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Free Software +# Foundation, Inc. # This Makefile.in is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. @@ -18,6 +18,23 @@ VPATH = @srcdir@ +am__make_dryrun = \ + { \ + am__dry=no; \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + echo 'am--echo: ; @echo "AM" OK' | $(MAKE) -f - 2>/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } pkgdatadir = $(datadir)/@PACKAGE@ pkgincludedir = $(includedir)/@PACKAGE@ pkglibdir = $(libdir)/@PACKAGE@ @@ -37,53 +54,29 @@ POST_UNINSTALL = : build_triplet = @build@ host_triplet = @host@ target_triplet = @target@ -bin_PROGRAMS = gnunet-testing$(EXEEXT) -check_PROGRAMS = test_testing$(EXEEXT) test_testing_connect$(EXEEXT) \ - test_testing_reconnect$(EXEEXT) test_testing_group$(EXEEXT) \ - test_testing_peergroup$(EXEEXT) \ - test_testing_topology_stability$(EXEEXT) \ - test_testing_topology_clique$(EXEEXT) \ - test_testing_topology_clique_random$(EXEEXT) \ - test_testing_topology_clique_minimum$(EXEEXT) \ - test_testing_topology_clique_dfs$(EXEEXT) \ - test_testing_topology_churn$(EXEEXT) \ - test_testing_topology_line$(EXEEXT) \ - test_testing_topology_blacklist$(EXEEXT) \ - test_testing_group_remote$(EXEEXT) \ - test_testing_2dtorus$(EXEEXT) \ - test_testing_topology_ring$(EXEEXT) \ - test_testing_topology_2d_torus$(EXEEXT) \ - test_testing_topology_small_world_ring$(EXEEXT) \ - test_testing_topology_small_world_torus$(EXEEXT) \ - test_testing_topology_erdos_renyi$(EXEEXT) \ - test_testing_topology_internat$(EXEEXT) \ - test_testing_topology_none$(EXEEXT) \ - test_testing_topology_scale_free$(EXEEXT) \ - test_testing_new_portreservation$(EXEEXT) \ - test_testing_new_peerstartup$(EXEEXT) \ - test_testing_new_servicestartup$(EXEEXT) -@ENABLE_TEST_RUN_TRUE@TESTS = test_testing$(EXEEXT) \ -@ENABLE_TEST_RUN_TRUE@ test_testing_connect$(EXEEXT) \ -@ENABLE_TEST_RUN_TRUE@ test_testing_reconnect$(EXEEXT) \ -@ENABLE_TEST_RUN_TRUE@ test_testing_group$(EXEEXT) \ -@ENABLE_TEST_RUN_TRUE@ test_testing_peergroup$(EXEEXT) \ -@ENABLE_TEST_RUN_TRUE@ test_testing_new_portreservation$(EXEEXT) \ -@ENABLE_TEST_RUN_TRUE@ test_testing_new_peerstartup$(EXEEXT) \ -@ENABLE_TEST_RUN_TRUE@ test_testing_new_servicestartup$(EXEEXT) +bin_PROGRAMS = gnunet-testing-run-service$(EXEEXT) \ + gnunet-testing$(EXEEXT) +check_PROGRAMS = test_testing_portreservation$(EXEEXT) \ + test_testing_peerstartup$(EXEEXT) \ + test_testing_servicestartup$(EXEEXT) +@ENABLE_TEST_RUN_TRUE@TESTS = test_testing_portreservation$(EXEEXT) \ +@ENABLE_TEST_RUN_TRUE@ test_testing_peerstartup$(EXEEXT) \ +@ENABLE_TEST_RUN_TRUE@ test_testing_servicestartup$(EXEEXT) subdir = src/testing DIST_COMMON = $(dist_pkgcfg_DATA) $(srcdir)/Makefile.am \ $(srcdir)/Makefile.in ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 am__aclocal_m4_deps = $(top_srcdir)/m4/absolute-header.m4 \ $(top_srcdir)/m4/align.m4 $(top_srcdir)/m4/argz.m4 \ - $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/iconv.m4 \ - $(top_srcdir)/m4/lib-ld.m4 $(top_srcdir)/m4/lib-link.m4 \ - $(top_srcdir)/m4/lib-prefix.m4 $(top_srcdir)/m4/libcurl.m4 \ - $(top_srcdir)/m4/libgcrypt.m4 $(top_srcdir)/m4/libtool.m4 \ - $(top_srcdir)/m4/libunistring.m4 $(top_srcdir)/m4/ltdl.m4 \ - $(top_srcdir)/m4/ltoptions.m4 $(top_srcdir)/m4/ltsugar.m4 \ - $(top_srcdir)/m4/ltversion.m4 $(top_srcdir)/m4/lt~obsolete.m4 \ - $(top_srcdir)/m4/nls.m4 $(top_srcdir)/m4/po.m4 \ + $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/glib-2.0.m4 \ + $(top_srcdir)/m4/iconv.m4 $(top_srcdir)/m4/lib-ld.m4 \ + $(top_srcdir)/m4/lib-link.m4 $(top_srcdir)/m4/lib-prefix.m4 \ + $(top_srcdir)/m4/libcurl.m4 $(top_srcdir)/m4/libgcrypt.m4 \ + $(top_srcdir)/m4/libtool.m4 $(top_srcdir)/m4/libunistring.m4 \ + $(top_srcdir)/m4/ltdl.m4 $(top_srcdir)/m4/ltoptions.m4 \ + $(top_srcdir)/m4/ltsugar.m4 $(top_srcdir)/m4/ltversion.m4 \ + $(top_srcdir)/m4/lt~obsolete.m4 $(top_srcdir)/m4/nls.m4 \ + $(top_srcdir)/m4/pkg.m4 $(top_srcdir)/m4/po.m4 \ $(top_srcdir)/m4/progtest.m4 $(top_srcdir)/acinclude.m4 \ $(top_srcdir)/configure.ac am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ @@ -113,221 +106,55 @@ am__nobase_list = $(am__nobase_strip_setup); \ am__base_list = \ sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \ sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g' +am__uninstall_files_from_dir = { \ + test -z "$$files" \ + || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \ + || { echo " ( cd '$$dir' && rm -f" $$files ")"; \ + $(am__cd) "$$dir" && rm -f $$files; }; \ + } am__installdirs = "$(DESTDIR)$(libdir)" "$(DESTDIR)$(bindir)" \ "$(DESTDIR)$(pkgcfgdir)" LTLIBRARIES = $(lib_LTLIBRARIES) am__DEPENDENCIES_1 = -libgnunettesting_la_DEPENDENCIES = $(am__DEPENDENCIES_1) \ - $(top_builddir)/src/core/libgnunetcore.la \ - $(top_builddir)/src/statistics/libgnunetstatistics.la \ - $(top_builddir)/src/transport/libgnunettransport.la \ - $(top_builddir)/src/hello/libgnunethello.la \ - $(top_builddir)/src/util/libgnunetutil.la -am_libgnunettesting_la_OBJECTS = helper.lo testing.lo testing_group.lo \ - testing_peergroup.lo +libgnunettesting_la_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(am__DEPENDENCIES_1) +am_libgnunettesting_la_OBJECTS = testing.lo libgnunettesting_la_OBJECTS = $(am_libgnunettesting_la_OBJECTS) -AM_V_lt = $(am__v_lt_$(V)) -am__v_lt_ = $(am__v_lt_$(AM_DEFAULT_VERBOSITY)) +AM_V_lt = $(am__v_lt_@AM_V@) +am__v_lt_ = $(am__v_lt_@AM_DEFAULT_V@) am__v_lt_0 = --silent libgnunettesting_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ $(AM_CFLAGS) $(CFLAGS) $(libgnunettesting_la_LDFLAGS) \ $(LDFLAGS) -o $@ -libgnunettesting_new_la_DEPENDENCIES = \ - $(top_builddir)/src/util/libgnunetutil.la -am_libgnunettesting_new_la_OBJECTS = testing_new.lo -libgnunettesting_new_la_OBJECTS = \ - $(am_libgnunettesting_new_la_OBJECTS) -libgnunettesting_new_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ - $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ - $(AM_CFLAGS) $(CFLAGS) $(libgnunettesting_new_la_LDFLAGS) \ - $(LDFLAGS) -o $@ PROGRAMS = $(bin_PROGRAMS) am_gnunet_testing_OBJECTS = gnunet-testing.$(OBJEXT) gnunet_testing_OBJECTS = $(am_gnunet_testing_OBJECTS) -am_test_testing_OBJECTS = test_testing.$(OBJEXT) -test_testing_OBJECTS = $(am_test_testing_OBJECTS) -test_testing_DEPENDENCIES = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/util/libgnunetutil.la -am_test_testing_2dtorus_OBJECTS = test_testing_2dtorus.$(OBJEXT) -test_testing_2dtorus_OBJECTS = $(am_test_testing_2dtorus_OBJECTS) -test_testing_2dtorus_DEPENDENCIES = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/util/libgnunetutil.la -am_test_testing_connect_OBJECTS = test_testing_connect.$(OBJEXT) -test_testing_connect_OBJECTS = $(am_test_testing_connect_OBJECTS) -test_testing_connect_DEPENDENCIES = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/util/libgnunetutil.la -am_test_testing_group_OBJECTS = test_testing_group.$(OBJEXT) -test_testing_group_OBJECTS = $(am_test_testing_group_OBJECTS) -test_testing_group_DEPENDENCIES = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/util/libgnunetutil.la -am_test_testing_group_remote_OBJECTS = \ - test_testing_group_remote.$(OBJEXT) -test_testing_group_remote_OBJECTS = \ - $(am_test_testing_group_remote_OBJECTS) -test_testing_group_remote_DEPENDENCIES = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/util/libgnunetutil.la -am_test_testing_new_peerstartup_OBJECTS = \ - test_testing_new_peerstartup.$(OBJEXT) -test_testing_new_peerstartup_OBJECTS = \ - $(am_test_testing_new_peerstartup_OBJECTS) -test_testing_new_peerstartup_DEPENDENCIES = \ - $(top_builddir)/src/testing/libgnunettesting_new.la \ - $(top_builddir)/src/util/libgnunetutil.la -am_test_testing_new_portreservation_OBJECTS = \ - test_testing_new_portreservation.$(OBJEXT) -test_testing_new_portreservation_OBJECTS = \ - $(am_test_testing_new_portreservation_OBJECTS) -test_testing_new_portreservation_DEPENDENCIES = \ - $(top_builddir)/src/testing/libgnunettesting_new.la \ - $(top_builddir)/src/util/libgnunetutil.la -am_test_testing_new_servicestartup_OBJECTS = \ - test_testing_new_servicestartup.$(OBJEXT) -test_testing_new_servicestartup_OBJECTS = \ - $(am_test_testing_new_servicestartup_OBJECTS) -test_testing_new_servicestartup_DEPENDENCIES = \ - $(top_builddir)/src/testing/libgnunettesting_new.la \ - $(top_builddir)/src/util/libgnunetutil.la -am_test_testing_peergroup_OBJECTS = test_testing_peergroup.$(OBJEXT) -test_testing_peergroup_OBJECTS = $(am_test_testing_peergroup_OBJECTS) -test_testing_peergroup_DEPENDENCIES = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/util/libgnunetutil.la -am_test_testing_reconnect_OBJECTS = test_testing_reconnect.$(OBJEXT) -test_testing_reconnect_OBJECTS = $(am_test_testing_reconnect_OBJECTS) -test_testing_reconnect_DEPENDENCIES = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/util/libgnunetutil.la -am_test_testing_topology_2d_torus_OBJECTS = \ - test_testing_topology.$(OBJEXT) -test_testing_topology_2d_torus_OBJECTS = \ - $(am_test_testing_topology_2d_torus_OBJECTS) -test_testing_topology_2d_torus_DEPENDENCIES = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/core/libgnunetcore.la \ - $(top_builddir)/src/util/libgnunetutil.la -am_test_testing_topology_blacklist_OBJECTS = \ - test_testing_topology_blacklist.$(OBJEXT) -test_testing_topology_blacklist_OBJECTS = \ - $(am_test_testing_topology_blacklist_OBJECTS) -test_testing_topology_blacklist_DEPENDENCIES = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/util/libgnunetutil.la -am_test_testing_topology_churn_OBJECTS = \ - test_testing_topology_churn.$(OBJEXT) -test_testing_topology_churn_OBJECTS = \ - $(am_test_testing_topology_churn_OBJECTS) -test_testing_topology_churn_DEPENDENCIES = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/util/libgnunetutil.la -am_test_testing_topology_clique_OBJECTS = \ - test_testing_topology.$(OBJEXT) -test_testing_topology_clique_OBJECTS = \ - $(am_test_testing_topology_clique_OBJECTS) -test_testing_topology_clique_DEPENDENCIES = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/core/libgnunetcore.la \ - $(top_builddir)/src/util/libgnunetutil.la -am_test_testing_topology_clique_dfs_OBJECTS = \ - test_testing_topology.$(OBJEXT) -test_testing_topology_clique_dfs_OBJECTS = \ - $(am_test_testing_topology_clique_dfs_OBJECTS) -test_testing_topology_clique_dfs_DEPENDENCIES = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/core/libgnunetcore.la \ - $(top_builddir)/src/util/libgnunetutil.la -am_test_testing_topology_clique_minimum_OBJECTS = \ - test_testing_topology.$(OBJEXT) -test_testing_topology_clique_minimum_OBJECTS = \ - $(am_test_testing_topology_clique_minimum_OBJECTS) -test_testing_topology_clique_minimum_DEPENDENCIES = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/core/libgnunetcore.la \ - $(top_builddir)/src/util/libgnunetutil.la -am_test_testing_topology_clique_random_OBJECTS = \ - test_testing_topology.$(OBJEXT) -test_testing_topology_clique_random_OBJECTS = \ - $(am_test_testing_topology_clique_random_OBJECTS) -test_testing_topology_clique_random_DEPENDENCIES = \ +am_gnunet_testing_run_service_OBJECTS = \ + gnunet-testing-run-service.$(OBJEXT) +gnunet_testing_run_service_OBJECTS = \ + $(am_gnunet_testing_run_service_OBJECTS) +am_test_testing_peerstartup_OBJECTS = \ + test_testing_peerstartup.$(OBJEXT) +test_testing_peerstartup_OBJECTS = \ + $(am_test_testing_peerstartup_OBJECTS) +test_testing_peerstartup_DEPENDENCIES = \ $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/core/libgnunetcore.la \ $(top_builddir)/src/util/libgnunetutil.la -am_test_testing_topology_erdos_renyi_OBJECTS = \ - test_testing_topology.$(OBJEXT) -test_testing_topology_erdos_renyi_OBJECTS = \ - $(am_test_testing_topology_erdos_renyi_OBJECTS) -test_testing_topology_erdos_renyi_DEPENDENCIES = \ +am_test_testing_portreservation_OBJECTS = \ + test_testing_portreservation.$(OBJEXT) +test_testing_portreservation_OBJECTS = \ + $(am_test_testing_portreservation_OBJECTS) +test_testing_portreservation_DEPENDENCIES = \ $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/core/libgnunetcore.la \ $(top_builddir)/src/util/libgnunetutil.la -am_test_testing_topology_internat_OBJECTS = \ - test_testing_topology.$(OBJEXT) -test_testing_topology_internat_OBJECTS = \ - $(am_test_testing_topology_internat_OBJECTS) -test_testing_topology_internat_DEPENDENCIES = \ +am_test_testing_servicestartup_OBJECTS = \ + test_testing_servicestartup.$(OBJEXT) +test_testing_servicestartup_OBJECTS = \ + $(am_test_testing_servicestartup_OBJECTS) +test_testing_servicestartup_DEPENDENCIES = \ $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/core/libgnunetcore.la \ - $(top_builddir)/src/util/libgnunetutil.la -am_test_testing_topology_line_OBJECTS = \ - test_testing_topology.$(OBJEXT) -test_testing_topology_line_OBJECTS = \ - $(am_test_testing_topology_line_OBJECTS) -test_testing_topology_line_DEPENDENCIES = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/core/libgnunetcore.la \ - $(top_builddir)/src/util/libgnunetutil.la -am_test_testing_topology_none_OBJECTS = \ - test_testing_topology.$(OBJEXT) -test_testing_topology_none_OBJECTS = \ - $(am_test_testing_topology_none_OBJECTS) -test_testing_topology_none_DEPENDENCIES = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/core/libgnunetcore.la \ - $(top_builddir)/src/util/libgnunetutil.la -am_test_testing_topology_ring_OBJECTS = \ - test_testing_topology.$(OBJEXT) -test_testing_topology_ring_OBJECTS = \ - $(am_test_testing_topology_ring_OBJECTS) -test_testing_topology_ring_DEPENDENCIES = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/core/libgnunetcore.la \ - $(top_builddir)/src/util/libgnunetutil.la -am_test_testing_topology_scale_free_OBJECTS = \ - test_testing_topology.$(OBJEXT) -test_testing_topology_scale_free_OBJECTS = \ - $(am_test_testing_topology_scale_free_OBJECTS) -test_testing_topology_scale_free_DEPENDENCIES = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/core/libgnunetcore.la \ - $(top_builddir)/src/util/libgnunetutil.la -am_test_testing_topology_small_world_ring_OBJECTS = \ - test_testing_topology.$(OBJEXT) -test_testing_topology_small_world_ring_OBJECTS = \ - $(am_test_testing_topology_small_world_ring_OBJECTS) -test_testing_topology_small_world_ring_DEPENDENCIES = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/core/libgnunetcore.la \ - $(top_builddir)/src/util/libgnunetutil.la -am_test_testing_topology_small_world_torus_OBJECTS = \ - test_testing_topology.$(OBJEXT) -test_testing_topology_small_world_torus_OBJECTS = \ - $(am_test_testing_topology_small_world_torus_OBJECTS) -test_testing_topology_small_world_torus_DEPENDENCIES = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/core/libgnunetcore.la \ - $(top_builddir)/src/util/libgnunetutil.la -am_test_testing_topology_stability_OBJECTS = \ - test_testing_topology.$(OBJEXT) -test_testing_topology_stability_OBJECTS = \ - $(am_test_testing_topology_stability_OBJECTS) -test_testing_topology_stability_DEPENDENCIES = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/core/libgnunetcore.la \ $(top_builddir)/src/util/libgnunetutil.la DEFAULT_INCLUDES = -I.@am__isrc@ -I$(top_builddir) depcomp = $(SHELL) $(top_srcdir)/depcomp @@ -339,74 +166,38 @@ LTCOMPILE = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) \ $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) \ $(AM_CFLAGS) $(CFLAGS) -AM_V_CC = $(am__v_CC_$(V)) -am__v_CC_ = $(am__v_CC_$(AM_DEFAULT_VERBOSITY)) +AM_V_CC = $(am__v_CC_@AM_V@) +am__v_CC_ = $(am__v_CC_@AM_DEFAULT_V@) am__v_CC_0 = @echo " CC " $@; -AM_V_at = $(am__v_at_$(V)) -am__v_at_ = $(am__v_at_$(AM_DEFAULT_VERBOSITY)) +AM_V_at = $(am__v_at_@AM_V@) +am__v_at_ = $(am__v_at_@AM_DEFAULT_V@) am__v_at_0 = @ CCLD = $(CC) LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ $(AM_LDFLAGS) $(LDFLAGS) -o $@ -AM_V_CCLD = $(am__v_CCLD_$(V)) -am__v_CCLD_ = $(am__v_CCLD_$(AM_DEFAULT_VERBOSITY)) +AM_V_CCLD = $(am__v_CCLD_@AM_V@) +am__v_CCLD_ = $(am__v_CCLD_@AM_DEFAULT_V@) am__v_CCLD_0 = @echo " CCLD " $@; -AM_V_GEN = $(am__v_GEN_$(V)) -am__v_GEN_ = $(am__v_GEN_$(AM_DEFAULT_VERBOSITY)) +AM_V_GEN = $(am__v_GEN_@AM_V@) +am__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@) am__v_GEN_0 = @echo " GEN " $@; -SOURCES = $(libgnunettesting_la_SOURCES) \ - $(libgnunettesting_new_la_SOURCES) $(gnunet_testing_SOURCES) \ - $(test_testing_SOURCES) $(test_testing_2dtorus_SOURCES) \ - $(test_testing_connect_SOURCES) $(test_testing_group_SOURCES) \ - $(test_testing_group_remote_SOURCES) \ - $(test_testing_new_peerstartup_SOURCES) \ - $(test_testing_new_portreservation_SOURCES) \ - $(test_testing_new_servicestartup_SOURCES) \ - $(test_testing_peergroup_SOURCES) \ - $(test_testing_reconnect_SOURCES) \ - $(test_testing_topology_2d_torus_SOURCES) \ - $(test_testing_topology_blacklist_SOURCES) \ - $(test_testing_topology_churn_SOURCES) \ - $(test_testing_topology_clique_SOURCES) \ - $(test_testing_topology_clique_dfs_SOURCES) \ - $(test_testing_topology_clique_minimum_SOURCES) \ - $(test_testing_topology_clique_random_SOURCES) \ - $(test_testing_topology_erdos_renyi_SOURCES) \ - $(test_testing_topology_internat_SOURCES) \ - $(test_testing_topology_line_SOURCES) \ - $(test_testing_topology_none_SOURCES) \ - $(test_testing_topology_ring_SOURCES) \ - $(test_testing_topology_scale_free_SOURCES) \ - $(test_testing_topology_small_world_ring_SOURCES) \ - $(test_testing_topology_small_world_torus_SOURCES) \ - $(test_testing_topology_stability_SOURCES) +SOURCES = $(libgnunettesting_la_SOURCES) $(gnunet_testing_SOURCES) \ + $(gnunet_testing_run_service_SOURCES) \ + $(test_testing_peerstartup_SOURCES) \ + $(test_testing_portreservation_SOURCES) \ + $(test_testing_servicestartup_SOURCES) DIST_SOURCES = $(libgnunettesting_la_SOURCES) \ - $(libgnunettesting_new_la_SOURCES) $(gnunet_testing_SOURCES) \ - $(test_testing_SOURCES) $(test_testing_2dtorus_SOURCES) \ - $(test_testing_connect_SOURCES) $(test_testing_group_SOURCES) \ - $(test_testing_group_remote_SOURCES) \ - $(test_testing_new_peerstartup_SOURCES) \ - $(test_testing_new_portreservation_SOURCES) \ - $(test_testing_new_servicestartup_SOURCES) \ - $(test_testing_peergroup_SOURCES) \ - $(test_testing_reconnect_SOURCES) \ - $(test_testing_topology_2d_torus_SOURCES) \ - $(test_testing_topology_blacklist_SOURCES) \ - $(test_testing_topology_churn_SOURCES) \ - $(test_testing_topology_clique_SOURCES) \ - $(test_testing_topology_clique_dfs_SOURCES) \ - $(test_testing_topology_clique_minimum_SOURCES) \ - $(test_testing_topology_clique_random_SOURCES) \ - $(test_testing_topology_erdos_renyi_SOURCES) \ - $(test_testing_topology_internat_SOURCES) \ - $(test_testing_topology_line_SOURCES) \ - $(test_testing_topology_none_SOURCES) \ - $(test_testing_topology_ring_SOURCES) \ - $(test_testing_topology_scale_free_SOURCES) \ - $(test_testing_topology_small_world_ring_SOURCES) \ - $(test_testing_topology_small_world_torus_SOURCES) \ - $(test_testing_topology_stability_SOURCES) + $(gnunet_testing_SOURCES) \ + $(gnunet_testing_run_service_SOURCES) \ + $(test_testing_peerstartup_SOURCES) \ + $(test_testing_portreservation_SOURCES) \ + $(test_testing_servicestartup_SOURCES) +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac DATA = $(dist_pkgcfg_DATA) ETAGS = etags CTAGS = ctags @@ -448,6 +239,10 @@ EXEEXT = @EXEEXT@ EXT_LIBS = @EXT_LIBS@ EXT_LIB_PATH = @EXT_LIB_PATH@ FGREP = @FGREP@ +GLIB_CFLAGS = @GLIB_CFLAGS@ +GLIB_GENMARSHAL = @GLIB_GENMARSHAL@ +GLIB_LIBS = @GLIB_LIBS@ +GLIB_MKENUMS = @GLIB_MKENUMS@ GMSGFMT = @GMSGFMT@ GMSGFMT_015 = @GMSGFMT_015@ GNUNETDNS_GROUP = @GNUNETDNS_GROUP@ @@ -458,6 +253,7 @@ GN_LIBINTL = @GN_LIBINTL@ GN_LIB_LDFLAGS = @GN_LIB_LDFLAGS@ GN_PLUGIN_LDFLAGS = @GN_PLUGIN_LDFLAGS@ GN_USER_HOME_DIR = @GN_USER_HOME_DIR@ +GOBJECT_QUERY = @GOBJECT_QUERY@ GREP = @GREP@ HAVE_LIBUNISTRING = @HAVE_LIBUNISTRING@ INCLTDL = @INCLTDL@ @@ -480,6 +276,8 @@ LIBCURL_CPPFLAGS = @LIBCURL_CPPFLAGS@ LIBGCRYPT_CFLAGS = @LIBGCRYPT_CFLAGS@ LIBGCRYPT_CONFIG = @LIBGCRYPT_CONFIG@ LIBGCRYPT_LIBS = @LIBGCRYPT_LIBS@ +LIBGTOP_CFLAGS = @LIBGTOP_CFLAGS@ +LIBGTOP_LIBS = @LIBGTOP_LIBS@ LIBICONV = @LIBICONV@ LIBINTL = @LIBINTL@ LIBLTDL = @LIBLTDL@ @@ -501,6 +299,7 @@ LT_CONFIG_H = @LT_CONFIG_H@ LT_DLLOADERS = @LT_DLLOADERS@ LT_DLPREOPEN = @LT_DLPREOPEN@ MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ MKDIR_P = @MKDIR_P@ MONKEYPREFIX = @MONKEYPREFIX@ MSGFMT = @MSGFMT@ @@ -510,6 +309,7 @@ MYSQL_CPPFLAGS = @MYSQL_CPPFLAGS@ MYSQL_LDFLAGS = @MYSQL_LDFLAGS@ NM = @NM@ NMEDIT = @NMEDIT@ +NSS_DIR = @NSS_DIR@ OBJC = @OBJC@ OBJCDEPMODE = @OBJCDEPMODE@ OBJCFLAGS = @OBJCFLAGS@ @@ -525,6 +325,7 @@ PACKAGE_TARNAME = @PACKAGE_TARNAME@ PACKAGE_URL = @PACKAGE_URL@ PACKAGE_VERSION = @PACKAGE_VERSION@ PATH_SEPARATOR = @PATH_SEPARATOR@ +PKG_CONFIG = @PKG_CONFIG@ POSTGRES_CPPFLAGS = @POSTGRES_CPPFLAGS@ POSTGRES_LDFLAGS = @POSTGRES_LDFLAGS@ POSUB = @POSUB@ @@ -556,6 +357,7 @@ abs_builddir = @abs_builddir@ abs_srcdir = @abs_srcdir@ abs_top_builddir = @abs_top_builddir@ abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ ac_ct_CC = @ac_ct_CC@ ac_ct_CXX = @ac_ct_CXX@ ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ @@ -578,6 +380,7 @@ datarootdir = @datarootdir@ docdir = @docdir@ dvidir = @dvidir@ exec_prefix = @exec_prefix@ +gitcommand = @gitcommand@ host = @host@ host_alias = @host_alias@ host_cpu = @host_cpu@ @@ -591,7 +394,6 @@ libdir = @libdir@ libexecdir = @libexecdir@ localedir = @localedir@ localstatedir = @localstatedir@ -lt_ECHO = @lt_ECHO@ ltdl_LIBOBJS = @ltdl_LIBOBJS@ ltdl_LTLIBOBJS = @ltdl_LTLIBOBJS@ mandir = @mandir@ @@ -609,6 +411,7 @@ sbindir = @sbindir@ sharedstatedir = @sharedstatedir@ srcdir = @srcdir@ subdirs = @subdirs@ +svnversioncommand = @svnversioncommand@ sys_symbol_underscore = @sys_symbol_underscore@ sysconfdir = @sysconfdir@ target = @target@ @@ -627,54 +430,30 @@ pkgcfgdir = $(pkgdatadir)/config.d/ dist_pkgcfg_DATA = \ testing.conf -@HAVE_EXPENSIVE_TESTS_TRUE@EXPENSIVE_TESTS = \ -@HAVE_EXPENSIVE_TESTS_TRUE@ test_testing_topology_stability \ -@HAVE_EXPENSIVE_TESTS_TRUE@ test_testing_topology_clique_random \ -@HAVE_EXPENSIVE_TESTS_TRUE@ test_testing_topology_clique_minimum \ -@HAVE_EXPENSIVE_TESTS_TRUE@ test_testing_topology_clique_dfs \ -@HAVE_EXPENSIVE_TESTS_TRUE@ test_testing_topology_churn \ -@HAVE_EXPENSIVE_TESTS_TRUE@ test_testing_topology_line \ -@HAVE_EXPENSIVE_TESTS_TRUE@ test_testing_topology_blacklist \ -@HAVE_EXPENSIVE_TESTS_TRUE@ test_testing_group_remote \ -@HAVE_EXPENSIVE_TESTS_TRUE@ test_testing_topology_ring \ -@HAVE_EXPENSIVE_TESTS_TRUE@ test_testing_topology_2d_torus \ -@HAVE_EXPENSIVE_TESTS_TRUE@ test_testing_topology_small_world_ring \ -@HAVE_EXPENSIVE_TESTS_TRUE@ test_testing_topology_small_world_torus \ -@HAVE_EXPENSIVE_TESTS_TRUE@ test_testing_topology_erdos_renyi \ -@HAVE_EXPENSIVE_TESTS_TRUE@ test_testing_topology_internat \ -@HAVE_EXPENSIVE_TESTS_TRUE@ test_testing_topology_scale_free - lib_LTLIBRARIES = \ - libgnunettesting.la \ - libgnunettesting_new.la + libgnunettesting.la libgnunettesting_la_SOURCES = \ - helper.c \ - testing.c \ - testing_group.c \ - testing_peergroup.c - -libgnunettesting_la_LIBADD = $(XLIB) \ - $(top_builddir)/src/core/libgnunetcore.la \ - $(top_builddir)/src/statistics/libgnunetstatistics.la \ - $(top_builddir)/src/transport/libgnunettransport.la \ - $(top_builddir)/src/hello/libgnunethello.la \ - -lm \ - $(top_builddir)/src/util/libgnunetutil.la + testing.c + +libgnunettesting_la_LIBADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(LTLIBINTL) libgnunettesting_la_LDFLAGS = \ $(GN_LIB_LDFLAGS) \ - -version-info 0:1:0 + -version-info 2:0:1 -libgnunettesting_new_la_SOURCES = \ - testing_new.c +gnunet_testing_run_service_SOURCES = \ + gnunet-testing-run-service.c -libgnunettesting_new_la_LIBADD = \ - $(top_builddir)/src/util/libgnunetutil.la +gnunet_testing_run_service_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ + $(GN_LIBINTL) -libgnunettesting_new_la_LDFLAGS = \ - $(GN_LIB_LDFLAGS) \ - -version-info 0:1:0 +gnunet_testing_run_service_DEPENDENCIES = \ + libgnunettesting.la gnunet_testing_SOURCES = \ gnunet-testing.c @@ -687,225 +466,29 @@ gnunet_testing_LDADD = \ gnunet_testing_DEPENDENCIES = \ libgnunettesting.la -test_testing_SOURCES = \ - test_testing.c - -test_testing_LDADD = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/util/libgnunetutil.la - -test_testing_connect_SOURCES = \ - test_testing_connect.c - -test_testing_connect_LDADD = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/util/libgnunetutil.la - -test_testing_reconnect_SOURCES = \ - test_testing_reconnect.c - -test_testing_reconnect_LDADD = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/util/libgnunetutil.la - -test_testing_group_SOURCES = \ - test_testing_group.c - -test_testing_group_LDADD = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/util/libgnunetutil.la - -test_testing_peergroup_SOURCES = \ - test_testing_peergroup.c +test_testing_portreservation_SOURCES = \ + test_testing_portreservation.c -test_testing_peergroup_LDADD = \ +test_testing_portreservation_LDADD = \ $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/util/libgnunetutil.la - -test_testing_topology_clique_SOURCES = \ - test_testing_topology.c - -test_testing_topology_clique_LDADD = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/core/libgnunetcore.la \ - $(top_builddir)/src/util/libgnunetutil.la - -test_testing_topology_stability_SOURCES = \ - test_testing_topology.c - -test_testing_topology_stability_LDADD = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/core/libgnunetcore.la \ - $(top_builddir)/src/util/libgnunetutil.la - -test_testing_topology_blacklist_SOURCES = \ - test_testing_topology_blacklist.c - -test_testing_topology_blacklist_LDADD = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/util/libgnunetutil.la - -test_testing_topology_churn_SOURCES = \ - test_testing_topology_churn.c - -test_testing_topology_churn_LDADD = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/util/libgnunetutil.la - -test_testing_topology_clique_random_SOURCES = \ - test_testing_topology.c - -test_testing_topology_clique_random_LDADD = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/core/libgnunetcore.la \ - $(top_builddir)/src/util/libgnunetutil.la - -test_testing_topology_clique_minimum_SOURCES = \ - test_testing_topology.c - -test_testing_topology_clique_minimum_LDADD = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/core/libgnunetcore.la \ - $(top_builddir)/src/util/libgnunetutil.la - -test_testing_topology_clique_dfs_SOURCES = \ - test_testing_topology.c - -test_testing_topology_clique_dfs_LDADD = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/core/libgnunetcore.la \ - $(top_builddir)/src/util/libgnunetutil.la - -test_testing_topology_line_SOURCES = \ - test_testing_topology.c - -test_testing_topology_line_LDADD = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/core/libgnunetcore.la \ - $(top_builddir)/src/util/libgnunetutil.la - -test_testing_group_remote_SOURCES = \ - test_testing_group_remote.c - -test_testing_group_remote_LDADD = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/util/libgnunetutil.la - -test_testing_2dtorus_SOURCES = \ - test_testing_2dtorus.c - -test_testing_2dtorus_LDADD = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/util/libgnunetutil.la - -test_testing_topology_ring_SOURCES = \ - test_testing_topology.c - -test_testing_topology_ring_LDADD = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/core/libgnunetcore.la \ - $(top_builddir)/src/util/libgnunetutil.la - -test_testing_topology_2d_torus_SOURCES = \ - test_testing_topology.c - -test_testing_topology_2d_torus_LDADD = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/core/libgnunetcore.la \ - $(top_builddir)/src/util/libgnunetutil.la - -test_testing_topology_small_world_ring_SOURCES = \ - test_testing_topology.c - -test_testing_topology_small_world_ring_LDADD = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/core/libgnunetcore.la \ - $(top_builddir)/src/util/libgnunetutil.la - -test_testing_topology_small_world_torus_SOURCES = \ - test_testing_topology.c - -test_testing_topology_small_world_torus_LDADD = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/core/libgnunetcore.la \ - $(top_builddir)/src/util/libgnunetutil.la - -test_testing_topology_internat_SOURCES = \ - test_testing_topology.c - -test_testing_topology_internat_LDADD = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/core/libgnunetcore.la \ $(top_builddir)/src/util/libgnunetutil.la -test_testing_topology_erdos_renyi_SOURCES = \ - test_testing_topology.c +test_testing_peerstartup_SOURCES = \ + test_testing_peerstartup.c -test_testing_topology_erdos_renyi_LDADD = \ +test_testing_peerstartup_LDADD = \ $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/core/libgnunetcore.la \ $(top_builddir)/src/util/libgnunetutil.la -test_testing_topology_scale_free_SOURCES = \ - test_testing_topology.c +test_testing_servicestartup_SOURCES = \ + test_testing_servicestartup.c -test_testing_topology_scale_free_LDADD = \ +test_testing_servicestartup_LDADD = \ $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/core/libgnunetcore.la \ - $(top_builddir)/src/util/libgnunetutil.la - -test_testing_topology_none_SOURCES = \ - test_testing_topology.c - -test_testing_topology_none_LDADD = \ - $(top_builddir)/src/testing/libgnunettesting.la \ - $(top_builddir)/src/core/libgnunetcore.la \ - $(top_builddir)/src/util/libgnunetutil.la - -test_testing_new_portreservation_SOURCES = \ - test_testing_new_portreservation.c - -test_testing_new_portreservation_LDADD = \ - $(top_builddir)/src/testing/libgnunettesting_new.la \ - $(top_builddir)/src/util/libgnunetutil.la - -test_testing_new_peerstartup_SOURCES = \ - test_testing_new_peerstartup.c - -test_testing_new_peerstartup_LDADD = \ - $(top_builddir)/src/testing/libgnunettesting_new.la \ - $(top_builddir)/src/util/libgnunetutil.la - -test_testing_new_servicestartup_SOURCES = \ - test_testing_new_servicestartup.c - -test_testing_new_servicestartup_LDADD = \ - $(top_builddir)/src/testing/libgnunettesting_new.la \ $(top_builddir)/src/util/libgnunetutil.la EXTRA_DIST = \ - test_testing_defaults.conf \ - test_testing_data.conf \ - test_testing_connect_peer1.conf \ - test_testing_connect_peer2.conf \ - test_testing_2dtorus.conf \ - test_testing_data_topology_clique.conf \ - test_testing_data_topology_clique_random.conf \ - test_testing_data_topology_clique_minimum.conf \ - test_testing_data_topology_clique_dfs.conf \ - test_testing_data_topology_ring.conf \ - test_testing_data_topology_2d_torus.conf \ - test_testing_data_topology_small_world_ring.conf \ - test_testing_data_topology_small_world_torus.conf \ - test_testing_data_topology_erdos_renyi.conf \ - test_testing_data_topology_internat.conf \ - test_testing_data_topology_scale_free.conf \ - test_testing_data_topology_blacklist.conf \ - test_testing_data_topology_churn.conf \ - test_testing_data_topology_none.conf \ - test_testing_data_remote.conf \ - test_testing_data_topology_stability.conf \ - test_testing_peergroup_data.conf + test_testing_defaults.conf all: all-am @@ -943,7 +526,6 @@ $(ACLOCAL_M4): $(am__aclocal_m4_deps) $(am__aclocal_m4_deps): install-libLTLIBRARIES: $(lib_LTLIBRARIES) @$(NORMAL_INSTALL) - test -z "$(libdir)" || $(MKDIR_P) "$(DESTDIR)$(libdir)" @list='$(lib_LTLIBRARIES)'; test -n "$(libdir)" || list=; \ list2=; for p in $$list; do \ if test -f $$p; then \ @@ -951,6 +533,8 @@ install-libLTLIBRARIES: $(lib_LTLIBRARIES) else :; fi; \ done; \ test -z "$$list2" || { \ + echo " $(MKDIR_P) '$(DESTDIR)$(libdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libdir)" || exit 1; \ echo " $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 '$(DESTDIR)$(libdir)'"; \ $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 "$(DESTDIR)$(libdir)"; \ } @@ -972,14 +556,15 @@ clean-libLTLIBRARIES: echo "rm -f \"$${dir}/so_locations\""; \ rm -f "$${dir}/so_locations"; \ done -libgnunettesting.la: $(libgnunettesting_la_OBJECTS) $(libgnunettesting_la_DEPENDENCIES) +libgnunettesting.la: $(libgnunettesting_la_OBJECTS) $(libgnunettesting_la_DEPENDENCIES) $(EXTRA_libgnunettesting_la_DEPENDENCIES) $(AM_V_CCLD)$(libgnunettesting_la_LINK) -rpath $(libdir) $(libgnunettesting_la_OBJECTS) $(libgnunettesting_la_LIBADD) $(LIBS) -libgnunettesting_new.la: $(libgnunettesting_new_la_OBJECTS) $(libgnunettesting_new_la_DEPENDENCIES) - $(AM_V_CCLD)$(libgnunettesting_new_la_LINK) -rpath $(libdir) $(libgnunettesting_new_la_OBJECTS) $(libgnunettesting_new_la_LIBADD) $(LIBS) install-binPROGRAMS: $(bin_PROGRAMS) @$(NORMAL_INSTALL) - test -z "$(bindir)" || $(MKDIR_P) "$(DESTDIR)$(bindir)" @list='$(bin_PROGRAMS)'; test -n "$(bindir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(bindir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(bindir)" || exit 1; \ + fi; \ for p in $$list; do echo "$$p $$p"; done | \ sed 's/$(EXEEXT)$$//' | \ while read p p1; do if test -f $$p || test -f $$p1; \ @@ -1028,87 +613,21 @@ clean-checkPROGRAMS: list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ echo " rm -f" $$list; \ rm -f $$list -gnunet-testing$(EXEEXT): $(gnunet_testing_OBJECTS) $(gnunet_testing_DEPENDENCIES) +gnunet-testing$(EXEEXT): $(gnunet_testing_OBJECTS) $(gnunet_testing_DEPENDENCIES) $(EXTRA_gnunet_testing_DEPENDENCIES) @rm -f gnunet-testing$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_testing_OBJECTS) $(gnunet_testing_LDADD) $(LIBS) -test_testing$(EXEEXT): $(test_testing_OBJECTS) $(test_testing_DEPENDENCIES) - @rm -f test_testing$(EXEEXT) - $(AM_V_CCLD)$(LINK) $(test_testing_OBJECTS) $(test_testing_LDADD) $(LIBS) -test_testing_2dtorus$(EXEEXT): $(test_testing_2dtorus_OBJECTS) $(test_testing_2dtorus_DEPENDENCIES) - @rm -f test_testing_2dtorus$(EXEEXT) - $(AM_V_CCLD)$(LINK) $(test_testing_2dtorus_OBJECTS) $(test_testing_2dtorus_LDADD) $(LIBS) -test_testing_connect$(EXEEXT): $(test_testing_connect_OBJECTS) $(test_testing_connect_DEPENDENCIES) - @rm -f test_testing_connect$(EXEEXT) - $(AM_V_CCLD)$(LINK) $(test_testing_connect_OBJECTS) $(test_testing_connect_LDADD) $(LIBS) -test_testing_group$(EXEEXT): $(test_testing_group_OBJECTS) $(test_testing_group_DEPENDENCIES) - @rm -f test_testing_group$(EXEEXT) - $(AM_V_CCLD)$(LINK) $(test_testing_group_OBJECTS) $(test_testing_group_LDADD) $(LIBS) -test_testing_group_remote$(EXEEXT): $(test_testing_group_remote_OBJECTS) $(test_testing_group_remote_DEPENDENCIES) - @rm -f test_testing_group_remote$(EXEEXT) - $(AM_V_CCLD)$(LINK) $(test_testing_group_remote_OBJECTS) $(test_testing_group_remote_LDADD) $(LIBS) -test_testing_new_peerstartup$(EXEEXT): $(test_testing_new_peerstartup_OBJECTS) $(test_testing_new_peerstartup_DEPENDENCIES) - @rm -f test_testing_new_peerstartup$(EXEEXT) - $(AM_V_CCLD)$(LINK) $(test_testing_new_peerstartup_OBJECTS) $(test_testing_new_peerstartup_LDADD) $(LIBS) -test_testing_new_portreservation$(EXEEXT): $(test_testing_new_portreservation_OBJECTS) $(test_testing_new_portreservation_DEPENDENCIES) - @rm -f test_testing_new_portreservation$(EXEEXT) - $(AM_V_CCLD)$(LINK) $(test_testing_new_portreservation_OBJECTS) $(test_testing_new_portreservation_LDADD) $(LIBS) -test_testing_new_servicestartup$(EXEEXT): $(test_testing_new_servicestartup_OBJECTS) $(test_testing_new_servicestartup_DEPENDENCIES) - @rm -f test_testing_new_servicestartup$(EXEEXT) - $(AM_V_CCLD)$(LINK) $(test_testing_new_servicestartup_OBJECTS) $(test_testing_new_servicestartup_LDADD) $(LIBS) -test_testing_peergroup$(EXEEXT): $(test_testing_peergroup_OBJECTS) $(test_testing_peergroup_DEPENDENCIES) - @rm -f test_testing_peergroup$(EXEEXT) - $(AM_V_CCLD)$(LINK) $(test_testing_peergroup_OBJECTS) $(test_testing_peergroup_LDADD) $(LIBS) -test_testing_reconnect$(EXEEXT): $(test_testing_reconnect_OBJECTS) $(test_testing_reconnect_DEPENDENCIES) - @rm -f test_testing_reconnect$(EXEEXT) - $(AM_V_CCLD)$(LINK) $(test_testing_reconnect_OBJECTS) $(test_testing_reconnect_LDADD) $(LIBS) -test_testing_topology_2d_torus$(EXEEXT): $(test_testing_topology_2d_torus_OBJECTS) $(test_testing_topology_2d_torus_DEPENDENCIES) - @rm -f test_testing_topology_2d_torus$(EXEEXT) - $(AM_V_CCLD)$(LINK) $(test_testing_topology_2d_torus_OBJECTS) $(test_testing_topology_2d_torus_LDADD) $(LIBS) -test_testing_topology_blacklist$(EXEEXT): $(test_testing_topology_blacklist_OBJECTS) $(test_testing_topology_blacklist_DEPENDENCIES) - @rm -f test_testing_topology_blacklist$(EXEEXT) - $(AM_V_CCLD)$(LINK) $(test_testing_topology_blacklist_OBJECTS) $(test_testing_topology_blacklist_LDADD) $(LIBS) -test_testing_topology_churn$(EXEEXT): $(test_testing_topology_churn_OBJECTS) $(test_testing_topology_churn_DEPENDENCIES) - @rm -f test_testing_topology_churn$(EXEEXT) - $(AM_V_CCLD)$(LINK) $(test_testing_topology_churn_OBJECTS) $(test_testing_topology_churn_LDADD) $(LIBS) -test_testing_topology_clique$(EXEEXT): $(test_testing_topology_clique_OBJECTS) $(test_testing_topology_clique_DEPENDENCIES) - @rm -f test_testing_topology_clique$(EXEEXT) - $(AM_V_CCLD)$(LINK) $(test_testing_topology_clique_OBJECTS) $(test_testing_topology_clique_LDADD) $(LIBS) -test_testing_topology_clique_dfs$(EXEEXT): $(test_testing_topology_clique_dfs_OBJECTS) $(test_testing_topology_clique_dfs_DEPENDENCIES) - @rm -f test_testing_topology_clique_dfs$(EXEEXT) - $(AM_V_CCLD)$(LINK) $(test_testing_topology_clique_dfs_OBJECTS) $(test_testing_topology_clique_dfs_LDADD) $(LIBS) -test_testing_topology_clique_minimum$(EXEEXT): $(test_testing_topology_clique_minimum_OBJECTS) $(test_testing_topology_clique_minimum_DEPENDENCIES) - @rm -f test_testing_topology_clique_minimum$(EXEEXT) - $(AM_V_CCLD)$(LINK) $(test_testing_topology_clique_minimum_OBJECTS) $(test_testing_topology_clique_minimum_LDADD) $(LIBS) -test_testing_topology_clique_random$(EXEEXT): $(test_testing_topology_clique_random_OBJECTS) $(test_testing_topology_clique_random_DEPENDENCIES) - @rm -f test_testing_topology_clique_random$(EXEEXT) - $(AM_V_CCLD)$(LINK) $(test_testing_topology_clique_random_OBJECTS) $(test_testing_topology_clique_random_LDADD) $(LIBS) -test_testing_topology_erdos_renyi$(EXEEXT): $(test_testing_topology_erdos_renyi_OBJECTS) $(test_testing_topology_erdos_renyi_DEPENDENCIES) - @rm -f test_testing_topology_erdos_renyi$(EXEEXT) - $(AM_V_CCLD)$(LINK) $(test_testing_topology_erdos_renyi_OBJECTS) $(test_testing_topology_erdos_renyi_LDADD) $(LIBS) -test_testing_topology_internat$(EXEEXT): $(test_testing_topology_internat_OBJECTS) $(test_testing_topology_internat_DEPENDENCIES) - @rm -f test_testing_topology_internat$(EXEEXT) - $(AM_V_CCLD)$(LINK) $(test_testing_topology_internat_OBJECTS) $(test_testing_topology_internat_LDADD) $(LIBS) -test_testing_topology_line$(EXEEXT): $(test_testing_topology_line_OBJECTS) $(test_testing_topology_line_DEPENDENCIES) - @rm -f test_testing_topology_line$(EXEEXT) - $(AM_V_CCLD)$(LINK) $(test_testing_topology_line_OBJECTS) $(test_testing_topology_line_LDADD) $(LIBS) -test_testing_topology_none$(EXEEXT): $(test_testing_topology_none_OBJECTS) $(test_testing_topology_none_DEPENDENCIES) - @rm -f test_testing_topology_none$(EXEEXT) - $(AM_V_CCLD)$(LINK) $(test_testing_topology_none_OBJECTS) $(test_testing_topology_none_LDADD) $(LIBS) -test_testing_topology_ring$(EXEEXT): $(test_testing_topology_ring_OBJECTS) $(test_testing_topology_ring_DEPENDENCIES) - @rm -f test_testing_topology_ring$(EXEEXT) - $(AM_V_CCLD)$(LINK) $(test_testing_topology_ring_OBJECTS) $(test_testing_topology_ring_LDADD) $(LIBS) -test_testing_topology_scale_free$(EXEEXT): $(test_testing_topology_scale_free_OBJECTS) $(test_testing_topology_scale_free_DEPENDENCIES) - @rm -f test_testing_topology_scale_free$(EXEEXT) - $(AM_V_CCLD)$(LINK) $(test_testing_topology_scale_free_OBJECTS) $(test_testing_topology_scale_free_LDADD) $(LIBS) -test_testing_topology_small_world_ring$(EXEEXT): $(test_testing_topology_small_world_ring_OBJECTS) $(test_testing_topology_small_world_ring_DEPENDENCIES) - @rm -f test_testing_topology_small_world_ring$(EXEEXT) - $(AM_V_CCLD)$(LINK) $(test_testing_topology_small_world_ring_OBJECTS) $(test_testing_topology_small_world_ring_LDADD) $(LIBS) -test_testing_topology_small_world_torus$(EXEEXT): $(test_testing_topology_small_world_torus_OBJECTS) $(test_testing_topology_small_world_torus_DEPENDENCIES) - @rm -f test_testing_topology_small_world_torus$(EXEEXT) - $(AM_V_CCLD)$(LINK) $(test_testing_topology_small_world_torus_OBJECTS) $(test_testing_topology_small_world_torus_LDADD) $(LIBS) -test_testing_topology_stability$(EXEEXT): $(test_testing_topology_stability_OBJECTS) $(test_testing_topology_stability_DEPENDENCIES) - @rm -f test_testing_topology_stability$(EXEEXT) - $(AM_V_CCLD)$(LINK) $(test_testing_topology_stability_OBJECTS) $(test_testing_topology_stability_LDADD) $(LIBS) +gnunet-testing-run-service$(EXEEXT): $(gnunet_testing_run_service_OBJECTS) $(gnunet_testing_run_service_DEPENDENCIES) $(EXTRA_gnunet_testing_run_service_DEPENDENCIES) + @rm -f gnunet-testing-run-service$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(gnunet_testing_run_service_OBJECTS) $(gnunet_testing_run_service_LDADD) $(LIBS) +test_testing_peerstartup$(EXEEXT): $(test_testing_peerstartup_OBJECTS) $(test_testing_peerstartup_DEPENDENCIES) $(EXTRA_test_testing_peerstartup_DEPENDENCIES) + @rm -f test_testing_peerstartup$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_testing_peerstartup_OBJECTS) $(test_testing_peerstartup_LDADD) $(LIBS) +test_testing_portreservation$(EXEEXT): $(test_testing_portreservation_OBJECTS) $(test_testing_portreservation_DEPENDENCIES) $(EXTRA_test_testing_portreservation_DEPENDENCIES) + @rm -f test_testing_portreservation$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_testing_portreservation_OBJECTS) $(test_testing_portreservation_LDADD) $(LIBS) +test_testing_servicestartup$(EXEEXT): $(test_testing_servicestartup_OBJECTS) $(test_testing_servicestartup_DEPENDENCIES) $(EXTRA_test_testing_servicestartup_DEPENDENCIES) + @rm -f test_testing_servicestartup$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_testing_servicestartup_OBJECTS) $(test_testing_servicestartup_LDADD) $(LIBS) mostlyclean-compile: -rm -f *.$(OBJEXT) @@ -1116,49 +635,33 @@ mostlyclean-compile: distclean-compile: -rm -f *.tab.c +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-testing-run-service.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-testing.Po@am__quote@ -@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/helper.Plo@am__quote@ -@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_testing.Po@am__quote@ -@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_testing_2dtorus.Po@am__quote@ -@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_testing_connect.Po@am__quote@ -@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_testing_group.Po@am__quote@ -@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_testing_group_remote.Po@am__quote@ -@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_testing_new_peerstartup.Po@am__quote@ -@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_testing_new_portreservation.Po@am__quote@ -@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_testing_new_servicestartup.Po@am__quote@ -@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_testing_peergroup.Po@am__quote@ -@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_testing_reconnect.Po@am__quote@ -@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_testing_topology.Po@am__quote@ -@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_testing_topology_blacklist.Po@am__quote@ -@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_testing_topology_churn.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_testing_peerstartup.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_testing_portreservation.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_testing_servicestartup.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/testing.Plo@am__quote@ -@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/testing_group.Plo@am__quote@ -@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/testing_new.Plo@am__quote@ -@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/testing_peergroup.Plo@am__quote@ .c.o: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c $< .c.obj: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'` @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c `$(CYGPATH_W) '$<'` +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c `$(CYGPATH_W) '$<'` .c.lo: @am__fastdepCC_TRUE@ $(AM_V_CC)$(LTCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LTCOMPILE) -c -o $@ $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LTCOMPILE) -c -o $@ $< mostlyclean-libtool: -rm -f *.lo @@ -1167,8 +670,11 @@ clean-libtool: -rm -rf .libs _libs install-dist_pkgcfgDATA: $(dist_pkgcfg_DATA) @$(NORMAL_INSTALL) - test -z "$(pkgcfgdir)" || $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" @list='$(dist_pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(pkgcfgdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" || exit 1; \ + fi; \ for p in $$list; do \ if test -f "$$p"; then d=; else d="$(srcdir)/"; fi; \ echo "$$d$$p"; \ @@ -1182,9 +688,7 @@ uninstall-dist_pkgcfgDATA: @$(NORMAL_UNINSTALL) @list='$(dist_pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ files=`for p in $$list; do echo $$p; done | sed -e 's|^.*/||'`; \ - test -n "$$files" || exit 0; \ - echo " ( cd '$(DESTDIR)$(pkgcfgdir)' && rm -f" $$files ")"; \ - cd "$(DESTDIR)$(pkgcfgdir)" && rm -f $$files + dir='$(DESTDIR)$(pkgcfgdir)'; $(am__uninstall_files_from_dir) ID: $(HEADERS) $(SOURCES) $(LISP) $(TAGS_FILES) list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ @@ -1319,14 +823,15 @@ check-TESTS: $(TESTS) fi; \ dashes=`echo "$$dashes" | sed s/./=/g`; \ if test "$$failed" -eq 0; then \ - echo "$$grn$$dashes"; \ + col="$$grn"; \ else \ - echo "$$red$$dashes"; \ + col="$$red"; \ fi; \ - echo "$$banner"; \ - test -z "$$skipped" || echo "$$skipped"; \ - test -z "$$report" || echo "$$report"; \ - echo "$$dashes$$std"; \ + echo "$${col}$$dashes$${std}"; \ + echo "$${col}$$banner$${std}"; \ + test -z "$$skipped" || echo "$${col}$$skipped$${std}"; \ + test -z "$$report" || echo "$${col}$$report$${std}"; \ + echo "$${col}$$dashes$${std}"; \ test "$$failed" -eq 0; \ else :; fi @@ -1381,10 +886,15 @@ install-am: all-am installcheck: installcheck-am install-strip: - $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ - install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ - `test -z '$(STRIP)' || \ - echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi mostlyclean-generic: clean-generic: diff --git a/src/testing/gnunet-testing-run-service.c b/src/testing/gnunet-testing-run-service.c new file mode 100644 index 0000000..ed60a40 --- /dev/null +++ b/src/testing/gnunet-testing-run-service.c @@ -0,0 +1,211 @@ +/* + This file is part of GNUnet. + (C) 2001, 2002, 2004, 2005, 2006, 2007, 2009 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + + +/** + * @file testing/gnunet-testing-run-service.c + * @brief tool to start a service for testing + * @author Florian Dold + * + * Start a peer, running only the service specified on the command line. + * Outputs the path to the temporary configuration file to stdout. + * + * The peer will run until this program is killed, + * or stdin is closed. When reading the character 'r' from stdin, + * the running service is restarted with the same configuration. + * + * This executable is intended to be used by gnunet-java, in order to reliably + * start and stop services for test cases. + */ +#include "platform.h" +#include "gnunet_util_lib.h" +#include "gnunet_testing_lib.h" + +#define LOG(kind,...) \ + GNUNET_log_from (kind, "gnunet-testing", __VA_ARGS__) + + +/** + * File handle to STDIN, for reading restart/quit commands. + */ +static struct GNUNET_DISK_FileHandle *fh; + +/** + * FIXME + */ +static char *tmpfilename; + +/** + * FIXME + */ +static GNUNET_SCHEDULER_TaskIdentifier tid; + +/** + * FIXME + */ +static struct GNUNET_TESTING_Peer *my_peer; + + + + +/** + * Cleanup called by signal handlers and when stdin is closed. + * Removes the temporary file. + * + * @param cls unused + * @param tc scheduler context + */ +static void +cleanup (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + if (NULL != tmpfilename) + { + if (0 != UNLINK (tmpfilename)) + GNUNET_log_strerror_file (GNUNET_ERROR_TYPE_WARNING, "unlink", tmpfilename); + } + if (GNUNET_SCHEDULER_NO_TASK != tid) + { + GNUNET_SCHEDULER_cancel (tid); + tid = GNUNET_SCHEDULER_NO_TASK; + } + if (NULL != fh) + { + GNUNET_DISK_file_close (fh); + fh = NULL; + } +} + + +/** + * Called whenever we can read stdin non-blocking + * + * @param cls unused + * @param tc scheduler context + */ +static void +stdin_cb (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + int c; + + tid = GNUNET_SCHEDULER_NO_TASK; + if (0 != (GNUNET_SCHEDULER_REASON_SHUTDOWN & tc->reason)) + return; + GNUNET_assert (0 != (GNUNET_SCHEDULER_REASON_READ_READY & tc->reason)); + c = getchar (); + switch (c) + { + case EOF: + case 'q': + GNUNET_SCHEDULER_shutdown (); + return; + case 'r': + GNUNET_TESTING_peer_stop (my_peer); + GNUNET_TESTING_peer_start (my_peer); + printf ("restarted\n"); + fflush (stdout); + break; + case '\n': + case '\r': + /* ignore whitespace */ + break; + default: + fprintf (stderr, _("Unknown command, use 'q' to quit or 'r' to restart peer\n")); + break; + } + tid = GNUNET_SCHEDULER_add_read_file (GNUNET_TIME_UNIT_FOREVER_REL, fh, + &stdin_cb, NULL); +} + + +/** + * Main function called by the testing library. + * Executed inside a running scheduler. + * + * @param cls unused + * @param cfg configuration of the peer that was started + * @param peer handle to the peer + */ +static void +testing_main (void *cls, const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) +{ + my_peer = peer; + if (NULL == (tmpfilename = GNUNET_DISK_mktemp ("gnunet-testing"))) + { + GNUNET_break (0); + GNUNET_SCHEDULER_shutdown (); + return; + } + if (GNUNET_SYSERR == + GNUNET_CONFIGURATION_write ((struct GNUNET_CONFIGURATION_Handle *) cfg, + tmpfilename)) + { + GNUNET_break (0); + return; + } + printf("ok\n%s\n", tmpfilename); + fflush(stdout); + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, &cleanup, NULL); + fh = GNUNET_DISK_get_handle_from_native (stdin); + tid = GNUNET_SCHEDULER_add_read_file (GNUNET_TIME_UNIT_FOREVER_REL, fh, + &stdin_cb, NULL); +} + + +/** + * The main function. + * + * @param argc number of arguments from the command line + * @param argv command line arguments + * @return 0 ok, 1 on error + */ +int +main (int argc, char *const *argv) +{ + static char *cfg_name; + static char *srv_name; + static const struct GNUNET_GETOPT_CommandLineOption options[] = { + {'c', "config", "FILENAME", + gettext_noop ("name of the template configuration file to use (optional)"), 1, + &GNUNET_GETOPT_set_string, &cfg_name}, + {'s', "service", "SERVICE", + gettext_noop ("name of the service to run"), 1, + &GNUNET_GETOPT_set_string, &srv_name}, + GNUNET_GETOPT_OPTION_HELP ("tool to start a service for testing"), + GNUNET_GETOPT_OPTION_END + }; + int ret; + + if (GNUNET_SYSERR == + GNUNET_GETOPT_run("gnunet-testing-run-service", options, argc, argv)) + return 1; + ret = GNUNET_TESTING_service_run ("gnunet_service_test", srv_name, + cfg_name, &testing_main, NULL); + if (0 != ret) + { + printf ("error\n"); + } + else + { + printf ("bye\n"); + } + return ret; +} + diff --git a/src/testing/gnunet-testing.c b/src/testing/gnunet-testing.c index bdbb5e8..28c5be9 100644 --- a/src/testing/gnunet-testing.c +++ b/src/testing/gnunet-testing.c @@ -24,10 +24,10 @@ * @author Christian Grothoff */ #include "platform.h" -#include "gnunet_getopt_lib.h" -#include "gnunet_program_lib.h" +#include "gnunet_util_lib.h" #include "gnunet_testing_lib.h" + #define HOSTKEYFILESIZE 914 /** @@ -35,66 +35,51 @@ */ static int ret; -static unsigned int create_hostkey; +static char *create_hostkey; -static unsigned int create_cfg; +static int create_cfg; -static int create_no; +static unsigned int create_no; -static char * create_cfg_template; +static char *create_cfg_template; -static char * create_hostkey_file; static int create_unique_cfgs (const char * template, const unsigned int no) { - int fail = GNUNET_NO; - - uint16_t port = 20000; - uint32_t upnum = 1; - uint32_t fdnum = 1; + struct GNUNET_TESTING_System *system; + int fail; + unsigned int cur; + char *cur_file; + struct GNUNET_CONFIGURATION_Handle *cfg_new; + struct GNUNET_CONFIGURATION_Handle *cfg_tmpl; if (GNUNET_NO == GNUNET_DISK_file_test(template)) { GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Configuration template `%s': file not found\n", create_cfg_template); return 1; } - - int cur = 0; - char * cur_file; - char *service_home = NULL; - char *cur_service_home = NULL; - - struct GNUNET_CONFIGURATION_Handle *cfg_new = NULL; - struct GNUNET_CONFIGURATION_Handle *cfg_tmpl = GNUNET_CONFIGURATION_create(); + cfg_tmpl = GNUNET_CONFIGURATION_create(); /* load template */ if ((create_cfg_template != NULL) && (GNUNET_OK != GNUNET_CONFIGURATION_load(cfg_tmpl, create_cfg_template))) { GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Could not load template `%s'\n", create_cfg_template); - GNUNET_CONFIGURATION_destroy(cfg_tmpl); + GNUNET_CONFIGURATION_destroy (cfg_tmpl); return 1; } /* load defaults */ - else if (GNUNET_OK != GNUNET_CONFIGURATION_load(cfg_tmpl, NULL)) + if (GNUNET_OK != GNUNET_CONFIGURATION_load (cfg_tmpl, NULL)) { - GNUNET_break (0); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Could not load template `%s'\n", create_cfg_template); + GNUNET_CONFIGURATION_destroy (cfg_tmpl); return 1; } - if (GNUNET_SYSERR == GNUNET_CONFIGURATION_get_value_string(cfg_tmpl, "PATHS", "SERVICEHOME", &service_home)) - { - GNUNET_asprintf(&service_home, "%s", "/tmp/testing"); - } - else - { - int s = strlen (service_home); - if (service_home[s-1] == DIR_SEPARATOR) - service_home[s-1] = '\0'; - } - - while (cur < no) + fail = GNUNET_NO; + system = GNUNET_TESTING_system_create ("testing", NULL /* controller */, NULL); + for (cur = 0; cur < no; cur++) { GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Creating configuration no. %u \n", cur); if (create_cfg_template != NULL) @@ -102,118 +87,72 @@ create_unique_cfgs (const char * template, const unsigned int no) else GNUNET_asprintf (&cur_file,"%04u%s",cur, ".conf"); - - GNUNET_asprintf (&cur_service_home, "%s-%04u%c",service_home, cur, DIR_SEPARATOR); - GNUNET_CONFIGURATION_set_value_string (cfg_tmpl,"PATHS","SERVICEHOME", cur_service_home); - GNUNET_CONFIGURATION_set_value_string (cfg_tmpl,"PATHS","DEFAULTCONFIG", cur_file); - GNUNET_free (cur_service_home); - - cfg_new = GNUNET_TESTING_create_cfg(cfg_tmpl, cur, &port, &upnum, NULL, &fdnum); - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Writing configuration no. %u to file `%s' \n", cur, cur_file); + cfg_new = GNUNET_CONFIGURATION_dup (cfg_tmpl); + if (GNUNET_OK != + GNUNET_TESTING_configuration_create (system, cfg_new)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Could not create another configuration\n"); + GNUNET_CONFIGURATION_destroy (cfg_new); + fail = GNUNET_YES; + break; + } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Writing configuration no. %u to file `%s' \n", cur, cur_file); if (GNUNET_OK != GNUNET_CONFIGURATION_write(cfg_new, cur_file)) { GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Failed to write configuration no. %u \n", cur); fail = GNUNET_YES; } - GNUNET_CONFIGURATION_destroy (cfg_new); GNUNET_free (cur_file); - if (fail == GNUNET_YES) + if (GNUNET_YES == fail) break; - cur ++; } - GNUNET_CONFIGURATION_destroy(cfg_tmpl); - GNUNET_free (service_home); - if (fail == GNUNET_NO) - return 0; - else + GNUNET_TESTING_system_destroy (system, GNUNET_NO); + if (GNUNET_YES == fail) return 1; + return 0; } + static int create_hostkeys (const unsigned int no) { + struct GNUNET_TESTING_System *system; + struct GNUNET_PeerIdentity id; struct GNUNET_DISK_FileHandle *fd; - int cur = 0; - uint64_t fs; - uint64_t total_hostkeys; - char *hostkey_data; - char *hostkey_src_file; - char *hostkey_dest_file; - - /* prepare hostkeys */ - if (create_hostkey_file == NULL) - hostkey_src_file = "../../contrib/testing_hostkeys.dat"; - else - { - hostkey_src_file = create_hostkey_file; - } + struct GNUNET_CRYPTO_RsaPrivateKey *pk; + struct GNUNET_CRYPTO_RsaPrivateKeyBinaryEncoded *pkb; - if (GNUNET_YES != GNUNET_DISK_file_test (hostkey_src_file)) + system = GNUNET_TESTING_system_create ("testing", NULL, NULL); + pk = GNUNET_TESTING_hostkey_get (system, create_no, &id); + if (NULL == pk) { - if (create_hostkey_file == NULL) - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("Could not read hostkeys file, specify hostkey file with -H!\n")); - else - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("Specified hostkey file `%s' not found!\n"), create_hostkey_file); + fprintf (stderr, _("Could not extract hostkey %u (offset too large?)\n"), create_no); + GNUNET_TESTING_system_destroy (system, GNUNET_YES); return 1; } - else - { - /* Check hostkey file size, read entire thing into memory */ - fd = GNUNET_DISK_file_open (hostkey_src_file, GNUNET_DISK_OPEN_READ, - GNUNET_DISK_PERM_NONE); - if (NULL == fd) - { - GNUNET_log_strerror_file (GNUNET_ERROR_TYPE_ERROR, "open", hostkey_src_file); - return 1; - } - - if (GNUNET_OK != GNUNET_DISK_file_size (hostkey_src_file, &fs, GNUNET_YES, GNUNET_YES)) - fs = 0; - - if (0 != (fs % HOSTKEYFILESIZE)) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "File size %llu seems incorrect for hostkeys...\n", fs); - } - else - { - total_hostkeys = fs / HOSTKEYFILESIZE; - hostkey_data = GNUNET_malloc_large (fs); - GNUNET_assert (fs == GNUNET_DISK_file_read (fd, hostkey_data, fs)); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Read %llu hostkeys from file\n", total_hostkeys); - } - GNUNET_assert (GNUNET_OK == GNUNET_DISK_file_close (fd)); - } - - while (cur < no) - { - GNUNET_asprintf (&hostkey_dest_file, "%04u-hostkey",cur); - GNUNET_assert (GNUNET_OK == - GNUNET_DISK_directory_create_for_file (hostkey_dest_file)); - fd = GNUNET_DISK_file_open (hostkey_dest_file, - GNUNET_DISK_OPEN_READWRITE | - GNUNET_DISK_OPEN_CREATE, - GNUNET_DISK_PERM_USER_READ | - GNUNET_DISK_PERM_USER_WRITE); - GNUNET_assert (fd != NULL); - GNUNET_assert (HOSTKEYFILESIZE == - GNUNET_DISK_file_write (fd, &hostkey_data[cur * HOSTKEYFILESIZE], HOSTKEYFILESIZE)); - GNUNET_assert (GNUNET_OK == GNUNET_DISK_file_close (fd)); - GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, "transport-testing", - "Wrote hostkey to file: `%s' \n", hostkey_dest_file); - GNUNET_free (hostkey_dest_file); - cur ++; - } - - GNUNET_free (hostkey_data); - + (void) GNUNET_DISK_directory_create_for_file (create_hostkey); + fd = GNUNET_DISK_file_open (create_hostkey, + GNUNET_DISK_OPEN_READWRITE | + GNUNET_DISK_OPEN_CREATE, + GNUNET_DISK_PERM_USER_READ | + GNUNET_DISK_PERM_USER_WRITE); + GNUNET_assert (fd != NULL); + pkb = GNUNET_CRYPTO_rsa_encode_key (pk); + GNUNET_assert (HOSTKEYFILESIZE == + GNUNET_DISK_file_write (fd, pkb, ntohs (pkb->len))); + GNUNET_assert (GNUNET_OK == GNUNET_DISK_file_close (fd)); + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, "transport-testing", + "Wrote hostkey to file: `%s'\n", create_hostkey); + GNUNET_free (pkb); + GNUNET_CRYPTO_rsa_key_free (pk); + GNUNET_TESTING_system_destroy (system, GNUNET_YES); return 0; } + /** * Main function that will be run by the scheduler. * @@ -227,11 +166,12 @@ run (void *cls, char *const *args, const char *cfgfile, const struct GNUNET_CONFIGURATION_Handle *cfg) { /* main code here */ - if (create_cfg == GNUNET_YES) + if (GNUNET_YES == create_cfg) { if (create_no > 0) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Creating %u configuration files based on template `%s'\n", create_no, create_cfg_template); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Creating %u configuration files based on template `%s'\n", create_no, create_cfg_template); ret = create_unique_cfgs (create_cfg_template, create_no); } else @@ -240,21 +180,11 @@ run (void *cls, char *const *args, const char *cfgfile, ret = 1; } } - - if (create_hostkey == GNUNET_YES) + if (NULL != create_hostkey) { - if (create_no > 0) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Creating %u hostkeys \n", create_no); - ret = create_hostkeys (create_no); - } - else - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Missing arguments! \n"); - ret = 1; - } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Extracting hostkey %u\n", create_no); + ret = create_hostkeys (create_no); } - GNUNET_free_non_null (create_cfg_template); } @@ -272,20 +202,23 @@ main (int argc, char *const *argv) static const struct GNUNET_GETOPT_CommandLineOption options[] = { {'C', "cfg", NULL, gettext_noop ("create unique configuration files"), GNUNET_NO, &GNUNET_GETOPT_set_one, &create_cfg}, - {'k', "key", NULL, gettext_noop ("create hostkey files from pre-computed hostkey list"), - GNUNET_NO, &GNUNET_GETOPT_set_one, &create_hostkey}, - {'H', "hostkeys", NULL, gettext_noop ("host key file"), - GNUNET_YES, &GNUNET_GETOPT_set_string, &create_hostkey_file}, - {'n', "number", NULL, gettext_noop ("number of unique configuration files or hostkeys to create"), + {'k', "key", "FILENAME", gettext_noop ("extract hostkey file from pre-computed hostkey list"), + GNUNET_YES, &GNUNET_GETOPT_set_string, &create_hostkey}, + {'n', "number", "NUMBER", gettext_noop ("number of unique configuration files to create, or number of the hostkey to extract"), GNUNET_YES, &GNUNET_GETOPT_set_uint, &create_no}, - {'t', "template", NULL, gettext_noop ("configuration template"), + {'t', "template", "FILENAME", gettext_noop ("configuration template"), GNUNET_YES, &GNUNET_GETOPT_set_string, &create_cfg_template}, GNUNET_GETOPT_OPTION_END }; - return (GNUNET_OK == - GNUNET_PROGRAM_run (argc, argv, "gnunet-testing", - gettext_noop ("Command line tool to access the testing library"), options, &run, - NULL)) ? ret : 1; + if (GNUNET_OK != GNUNET_STRINGS_get_utf8_args (argc, argv, &argc, &argv)) + return 2; + + ret = (GNUNET_OK == + GNUNET_PROGRAM_run (argc, argv, "gnunet-testing", + gettext_noop ("Command line tool to access the testing library"), options, &run, + NULL)) ? ret : 1; + GNUNET_free ((void*) argv); + return ret; } /* end of gnunet-testing.c */ diff --git a/src/testing/helper.c b/src/testing/helper.c deleted file mode 100644 index ebb37eb..0000000 --- a/src/testing/helper.c +++ /dev/null @@ -1,75 +0,0 @@ -/* - This file is part of GNUnet - (C) 2012 Christian Grothoff (and other contributing authors) - - GNUnet is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published - by the Free Software Foundation; either version 3, or (at your - option) any later version. - - GNUnet is distributed in the hope that it will be useful, but - WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - General Public License for more details. - - You should have received a copy of the GNU General Public License - along with GNUnet; see the file COPYING. If not, write to the - Free Software Foundation, Inc., 59 Temple Place - Suite 330, - Boston, MA 02111-1307, USA. - */ - -/** - * @file testing/helper.c - * @brief helper functions for testing - * @author Christian Grothoff - * - */ -#include "platform.h" -#include "gnunet_testing_lib.h" - - - - -/** - * Obtain the peer identity of the peer with the given configuration - * handle. This function reads the private key of the peer, obtains - * the public key and hashes it. - * - * @param cfg configuration of the peer - * @param pid where to store the peer identity - * @return GNUNET_OK on success, GNUNET_SYSERR on failure - */ -int -GNUNET_TESTING_get_peer_identity (const struct GNUNET_CONFIGURATION_Handle *cfg, - struct GNUNET_PeerIdentity *pid) -{ - char *keyfile; - struct GNUNET_CRYPTO_RsaPrivateKey *my_private_key; - struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded my_public_key; - - if (GNUNET_OK != - GNUNET_CONFIGURATION_get_value_filename (cfg, "GNUNETD", "HOSTKEY", - &keyfile)) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - _ - ("Peer is lacking HOSTKEY configuration setting.\n")); - return GNUNET_SYSERR; - } - my_private_key = GNUNET_CRYPTO_rsa_key_create_from_file (keyfile); - GNUNET_free (keyfile); - if (my_private_key == NULL) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - _("Could not access hostkey.\n")); - return GNUNET_SYSERR; - } - GNUNET_CRYPTO_rsa_key_get_public (my_private_key, &my_public_key); - GNUNET_CRYPTO_rsa_key_free (my_private_key); - GNUNET_CRYPTO_hash (&my_public_key, sizeof (my_public_key), - &pid->hashPubKey); - return GNUNET_OK; -} - - -/* end of helper.c */ diff --git a/src/testing/test_testing.c b/src/testing/test_testing.c deleted file mode 100644 index 3e2cd65..0000000 --- a/src/testing/test_testing.c +++ /dev/null @@ -1,126 +0,0 @@ -/* - This file is part of GNUnet. - (C) 2009 Christian Grothoff (and other contributing authors) - - GNUnet is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published - by the Free Software Foundation; either version 3, or (at your - option) any later version. - - GNUnet is distributed in the hope that it will be useful, but - WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - General Public License for more details. - - You should have received a copy of the GNU General Public License - along with GNUnet; see the file COPYING. If not, write to the - Free Software Foundation, Inc., 59 Temple Place - Suite 330, - Boston, MA 02111-1307, USA. -*/ -/** - * @file testing/test_testing.c - * @brief testcase for testing.c - */ -#include "platform.h" -#include "gnunet_testing_lib.h" - -#define VERBOSE GNUNET_YES - -#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 300) - -static int ok; - -static void -end_cb (void *cls, const char *emsg) -{ - if (emsg != NULL) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Ending with error: %s\n", emsg); - ok = 1; - } - else - { -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Daemon terminated, will now exit.\n"); -#endif - ok = 0; - } -} - - - -void -do_shutdown (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - struct GNUNET_TESTING_Daemon *d = cls; - - GNUNET_TESTING_daemon_stop (d, TIMEOUT, &end_cb, NULL, GNUNET_YES, GNUNET_NO); -} - - -static void -my_cb (void *cls, const struct GNUNET_PeerIdentity *id, - const struct GNUNET_CONFIGURATION_Handle *cfg, - struct GNUNET_TESTING_Daemon *d, const char *emsg) -{ - GNUNET_assert (id != NULL); -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Daemon `%s' started, will now stop it.\n", GNUNET_i2s (id)); -#endif - GNUNET_SCHEDULER_add_now (&do_shutdown, d); -} - - -static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) -{ - struct GNUNET_TESTING_Daemon *d; - - ok = 1; -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Starting daemon.\n"); -#endif - d = GNUNET_TESTING_daemon_start (cfg, TIMEOUT, GNUNET_NO, NULL, NULL, 0, NULL, - NULL, NULL, &my_cb, NULL); - GNUNET_assert (d != NULL); -} - -static int -check () -{ - char *const argv[] = { "test-testing", - "-c", - "test_testing_data.conf", -#if VERBOSE - "-L", "DEBUG", -#endif - NULL - }; - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - GNUNET_PROGRAM_run ((sizeof (argv) / sizeof (char *)) - 1, argv, - "test-testing", "nohelp", options, &run, &ok); - return ok; -} - -int -main (int argc, char *argv[]) -{ - int ret; - - GNUNET_log_setup ("test-testing", -#if VERBOSE - "DEBUG", -#else - "WARNING", -#endif - NULL); - ret = check (); - - return ret; -} - -/* end of test_testing.c */ diff --git a/src/testing/test_testing_2dtorus.c b/src/testing/test_testing_2dtorus.c deleted file mode 100644 index 00a66d6..0000000 --- a/src/testing/test_testing_2dtorus.c +++ /dev/null @@ -1,372 +0,0 @@ -/* - This file is part of GNUnet. - (C) 2011 Christian Grothoff (and other contributing authors) - - GNUnet is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published - by the Free Software Foundation; either version 3, or (at your - option) any later version. - - GNUnet is distributed in the hope that it will be useful, but - WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - General Public License for more details. - - You should have received a copy of the GNU General Public License - along with GNUnet; see the file COPYING. If not, write to the - Free Software Foundation, Inc., 59 Temple Place - Suite 330, - Boston, MA 02111-1307, USA. -*/ -/** - * @file testing/test_testing_2dtorus.c - * - * @brief Test for creating a 2dtorus. - */ -#include "platform.h" -#include "gnunet_testing_lib.h" - -#define VERBOSE GNUNET_YES -#define REMOVE_DIR GNUNET_YES - -/** - * How long until we give up on connecting the peers? - */ -#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 1500) - -/** - * Time to wait for stuff that should be rather fast - */ -#define SHORT_TIME GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 30) - - -/** - * How many events have happened - */ -static int ok; - -/** - * Be verbose - */ -static int verbose; - -/** - * Total number of peers in the test. - */ -static unsigned long long num_peers; - -/** - * Global configuration file - */ -static struct GNUNET_CONFIGURATION_Handle *testing_cfg; - -/** - * Total number of currently running peers. - */ -static unsigned long long peers_running; - -/** - * Total number of successful connections in the whole network. - */ -static unsigned int total_connections; - -/** - * Total number of counted topo connections - */ -static unsigned int topo_connections; - -/** - * Total number of failed connections in the whole network. - */ -static unsigned int failed_connections; - -/** - * The currently running peer group. - */ -static struct GNUNET_TESTING_PeerGroup *pg; - -/** - * Task called to disconnect peers - */ -static GNUNET_SCHEDULER_TaskIdentifier disconnect_task; - -/** - * Task called to shutdown test. - */ -static GNUNET_SCHEDULER_TaskIdentifier shutdown_handle; - - -/** - * Check whether peers successfully shut down. - */ -static void -shutdown_callback (void *cls, const char *emsg) -{ - if (emsg != NULL) - { -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: Shutdown of peers failed!\n"); -#endif - ok--; - } - else - { -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "test: All peers successfully shut down!\n"); -#endif - } -} - - -static void -shutdown_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: Ending test.\n"); -#endif - - GNUNET_TESTING_daemons_stop (pg, TIMEOUT, &shutdown_callback, NULL); - GNUNET_CONFIGURATION_destroy (testing_cfg); -} - - -static void -disconnect_peers (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: disconnecting peers\n"); - - if (GNUNET_SCHEDULER_NO_TASK != shutdown_handle) - { - GNUNET_SCHEDULER_cancel (shutdown_handle); - shutdown_handle = GNUNET_SCHEDULER_add_now (&shutdown_task, NULL); - } -} - - -/** - * Prototype of a callback function indicating that two peers - * are currently connected. - * - * @param cls closure - * @param first peer id for first daemon - * @param second peer id for the second daemon - * @param distance distance between the connected peers - * @param emsg error message (NULL on success) - */ -void -topo_cb (void *cls, const struct GNUNET_PeerIdentity *first, - const struct GNUNET_PeerIdentity *second, const char *emsg) -{ - topo_connections++; - if (NULL != emsg) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "test: Error by topo %u: %s\n", - topo_connections, emsg); - } - else - { - if (first == NULL || second == NULL) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: Connection %u NULL\n", - topo_connections); - if (disconnect_task != GNUNET_SCHEDULER_NO_TASK) - { - GNUNET_SCHEDULER_cancel (disconnect_task); - GNUNET_SCHEDULER_add_now (&disconnect_peers, NULL); - } - return; - } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: Connection %u ok\n", - topo_connections); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: %s\n", GNUNET_i2s (first)); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: %s\n", GNUNET_i2s (second)); - } -} - - -/** - * peergroup_ready: start test when all peers are connected - * @param cls closure - * @param emsg error message - */ -static void -peergroup_ready (void *cls, const char *emsg) -{ - if (emsg != NULL) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "test: Peergroup callback called with error, aborting test!\n"); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: Error from testing: `%s'\n", - emsg); - ok--; - GNUNET_TESTING_daemons_stop (pg, TIMEOUT, &shutdown_callback, NULL); - return; - } -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "************************************************************\n"); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "test: Peer Group started successfully!\n"); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: Have %u connections\n", - total_connections); -#endif - - peers_running = GNUNET_TESTING_daemons_running (pg); - if (0 < failed_connections) - { - ok = GNUNET_SYSERR; - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "test: %u connections have FAILED!\n", - failed_connections); - disconnect_task = GNUNET_SCHEDULER_add_now (&disconnect_peers, NULL); - - } - else - { - GNUNET_TESTING_get_topology (pg, &topo_cb, NULL); - disconnect_task = - GNUNET_SCHEDULER_add_delayed (SHORT_TIME, &disconnect_peers, NULL); - ok = GNUNET_OK; - } - -} - - -/** - * Function that will be called whenever two daemons are connected by - * the testing library. - * - * @param cls closure - * @param first peer id for first daemon - * @param second peer id for the second daemon - * @param distance distance between the connected peers - * @param first_cfg config for the first daemon - * @param second_cfg config for the second daemon - * @param first_daemon handle for the first daemon - * @param second_daemon handle for the second daemon - * @param emsg error message (NULL on success) - */ -static void -connect_cb (void *cls, const struct GNUNET_PeerIdentity *first, - const struct GNUNET_PeerIdentity *second, uint32_t distance, - const struct GNUNET_CONFIGURATION_Handle *first_cfg, - const struct GNUNET_CONFIGURATION_Handle *second_cfg, - struct GNUNET_TESTING_Daemon *first_daemon, - struct GNUNET_TESTING_Daemon *second_daemon, const char *emsg) -{ - if (emsg == NULL) - { - total_connections++; - } - else - { - failed_connections++; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "test: Problem with new connection (%s)\n", emsg); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: (%s)\n", GNUNET_i2s (first)); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: (%s)\n", GNUNET_i2s (second)); - } - -} - - -/** - * run: load configuration options and schedule test to run (start peergroup) - * @param cls closure - * @param args argv - * @param cfgfile configuration file name (can be NULL) - * @param cfg configuration handle - */ -static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) -{ - struct GNUNET_TESTING_Host *hosts; - - ok = GNUNET_NO; - total_connections = 0; - failed_connections = 0; - testing_cfg = GNUNET_CONFIGURATION_dup (cfg); - - GNUNET_log_setup ("test_testing_2dtorus", -#if VERBOSE - "DEBUG", -#else - "WARNING", -#endif - NULL); - -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: Starting daemons.\n"); - GNUNET_CONFIGURATION_set_value_string (testing_cfg, "testing", - "use_progressbars", "YES"); -#endif - - if (GNUNET_OK != - GNUNET_CONFIGURATION_get_value_number (testing_cfg, "testing", - "num_peers", &num_peers)) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "Option TESTING:NUM_PEERS is required!\n"); - return; - } - - hosts = GNUNET_TESTING_hosts_load (testing_cfg); - - pg = GNUNET_TESTING_peergroup_start (testing_cfg, num_peers, TIMEOUT, - &connect_cb, &peergroup_ready, NULL, - hosts); - GNUNET_assert (pg != NULL); - shutdown_handle = - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, - &shutdown_task, NULL); -} - - -/** - * test_testing_2dtorus command line options - */ -static struct GNUNET_GETOPT_CommandLineOption options[] = { - {'V', "verbose", NULL, - gettext_noop ("be verbose (print progress information)"), - 0, &GNUNET_GETOPT_set_one, &verbose}, - GNUNET_GETOPT_OPTION_END -}; - - -/** - * Main: start test - */ -int -main (int argc, char *argv[]) -{ - char *const argv2[] = { - argv[0], - "-c", - "test_testing_2dtorus.conf", -#if VERBOSE - "-L", - "DEBUG", -#endif - NULL - }; - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: Start\n"); - - - GNUNET_PROGRAM_run ((sizeof (argv2) / sizeof (char *)) - 1, argv2, - "test_testing_2dtorus", - gettext_noop ("Test testing 2d torus."), options, &run, - NULL); -#if REMOVE_DIR - GNUNET_DISK_directory_remove ("/tmp/test_testing_2dtorus"); -#endif - if (GNUNET_OK != ok) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "test: FAILED!\n"); - return 1; - } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test: success\n"); - return 0; -} - -/* end of test_testing_2dtorus.c */ diff --git a/src/testing/test_testing_2dtorus.conf b/src/testing/test_testing_2dtorus.conf deleted file mode 100644 index 54bb7c5..0000000 --- a/src/testing/test_testing_2dtorus.conf +++ /dev/null @@ -1,81 +0,0 @@ -@INLINE@ test_testing_defaults.conf -[PATHS] -SERVICEHOME = /tmp/test_testing_2dtorus/ -DEFAULTCONFIG = test_testing_2dtorus.conf - -[arm] -PORT = 10010 -DEFAULTSERVICES = core -#DEBUG = YES - -[statistics] -AUTOSTART = YES -PORT = 10000 - -[dht] -DEBUG = NO -AUTOSTART = YES -ACCEPT_FROM6 = ::1; -ACCEPT_FROM = 127.0.0.1; -HOSTNAME = localhost -PORT = 10001 - -[nse] -WORKBITS = 0 - -[dns] -AUTOSTART = NO -PORT = 10011 - -[transport] -PORT = 10002 -AUTOSTART = YES -PLUGINS = tcp - -[nat] -DISABLEV6 = YES -BINDTO = 127.0.0.1 -ENABLE_UPNP = NO -BEHIND_NAT = NO -ALLOW_NAT = NO -INTERNAL_ADDRESS = 127.0.0.1 -EXTERNAL_ADDRESS = 127.0.0.1 - -[ats] -WAN_QUOTA_IN = 1 GB -WAN_QUOTA_OUT = 1 GB - -[core] -AUTOSTART = YES -PORT = 10003 - -[peerinfo] -AUTOSTART = YES -PORT = 10004 - -[testing] -NUM_PEERS = 16 -WEAKRANDOM = YES -TOPOLOGY = 2D_TORUS -CONNECT_TOPOLOGY = 2D_TORUS -#TOPOLOGY_FILE = small.dat -CONNECT_TOPOLOGY = 2D_TORUS -#CONNECT_TOPOLOGY_OPTION = CONNECT_MINIMUM -#CONNECT_TOPOLOGY_OPTION_MODIFIER = 25 -#PERCENTAGE = 3 -#PROBABILITY = .1 -F2F = NO -CONNECT_TIMEOUT = 600 s -CONNECT_ATTEMPTS = 2 -DEBUG = YES -HOSTKEYSFILE = ../../contrib/testing_hostkeys.dat -MAX_CONCURRENT_SSH = 10 -USE_PROGRESSBARS = YES -PEERGROUP_TIMEOUT = 2400 s -TOPOLOGY_OUTPUT_FILE = testing_topo_initial -MAX_OUTSTANDING_CONNECTIONS = 75 -#SINGLE_PEERINFO_PER_HOST = YES -#NUM_PEERINFO_PER_HOST = 10 -#SINGLE_STATISTICS_PER_HOST = YES -#NUM_STATISTICS_PER_HOST = 10 -DELETE_FILES = YES diff --git a/src/testing/test_testing_connect.c b/src/testing/test_testing_connect.c deleted file mode 100644 index c69c203..0000000 --- a/src/testing/test_testing_connect.c +++ /dev/null @@ -1,197 +0,0 @@ -/* - This file is part of GNUnet. - (C) 2009 Christian Grothoff (and other contributing authors) - - GNUnet is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published - by the Free Software Foundation; either version 3, or (at your - option) any later version. - - GNUnet is distributed in the hope that it will be useful, but - WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - General Public License for more details. - - You should have received a copy of the GNU General Public License - along with GNUnet; see the file COPYING. If not, write to the - Free Software Foundation, Inc., 59 Temple Place - Suite 330, - Boston, MA 02111-1307, USA. -*/ -/** - * @file testing/test_testing_connect.c - * @brief testcase for functions to connect two peers in testing.c - */ -#include "platform.h" -#include "gnunet_testing_lib.h" - -#define VERBOSE GNUNET_NO - -/** - * How long until we give up on connecting the peers? - */ -#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 300) - -#define CONNECT_ATTEMPTS 3 - -static int ok; - -static struct GNUNET_TESTING_Daemon *d1; - -static struct GNUNET_TESTING_Daemon *d2; - -static struct GNUNET_CONFIGURATION_Handle *c1; - -static struct GNUNET_CONFIGURATION_Handle *c2; - -static struct GNUNET_TESTING_ConnectContext *cc; - -static void -end2_cb (void *cls, const char *emsg) -{ - - if (emsg != NULL) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Ending with error: %s\n", emsg); - ok = 1; - } - else - { -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Both daemons terminated, will now exit.\n"); -#endif - ok = 0; - } -} - -static void -end1_cb (void *cls, const char *emsg) -{ - if (emsg != NULL) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Stopping daemon 1 gave: %s\n", - emsg); - ok = 1; - } - else - { - ok = 0; - } - - GNUNET_TESTING_daemon_stop (d2, TIMEOUT, &end2_cb, NULL, GNUNET_YES, - GNUNET_NO); - d2 = NULL; -} - -static void -finish_testing (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - GNUNET_TESTING_daemon_stop (d1, TIMEOUT, &end1_cb, NULL, GNUNET_YES, - GNUNET_NO); - d1 = NULL; -} - -static void -my_connect_complete (void *cls, const struct GNUNET_PeerIdentity *first, - const struct GNUNET_PeerIdentity *second, - unsigned int distance, - const struct GNUNET_CONFIGURATION_Handle *first_cfg, - const struct GNUNET_CONFIGURATION_Handle *second_cfg, - struct GNUNET_TESTING_Daemon *first_daemon, - struct GNUNET_TESTING_Daemon *second_daemon, - const char *emsg) -{ - cc = NULL; - GNUNET_SCHEDULER_add_now (&finish_testing, NULL); -} - - -static void -my_cb2 (void *cls, const struct GNUNET_PeerIdentity *id, - const struct GNUNET_CONFIGURATION_Handle *cfg, - struct GNUNET_TESTING_Daemon *d, const char *emsg) -{ - GNUNET_assert (id != NULL); -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Daemon `%s' started.\n", - GNUNET_i2s (id)); -#endif - cc = GNUNET_TESTING_daemons_connect (d1, d2, TIMEOUT, CONNECT_ATTEMPTS, - GNUNET_YES, &my_connect_complete, NULL); -} - - -static void -my_cb1 (void *cls, const struct GNUNET_PeerIdentity *id, - const struct GNUNET_CONFIGURATION_Handle *cfg, - struct GNUNET_TESTING_Daemon *d, const char *emsg) -{ - GNUNET_assert (id != NULL); -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Daemon `%s' started.\n", - GNUNET_i2s (id)); -#endif - d2 = GNUNET_TESTING_daemon_start (c2, TIMEOUT, GNUNET_NO, NULL, NULL, 0, NULL, - NULL, NULL, &my_cb2, NULL); - GNUNET_assert (d2 != NULL); - -} - - -static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) -{ - ok = 1; -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Starting daemon.\n"); -#endif - c1 = GNUNET_CONFIGURATION_create (); - GNUNET_assert (GNUNET_OK == - GNUNET_CONFIGURATION_load (c1, - "test_testing_connect_peer1.conf")); - c2 = GNUNET_CONFIGURATION_create (); - GNUNET_assert (GNUNET_OK == - GNUNET_CONFIGURATION_load (c2, - "test_testing_connect_peer2.conf")); - d1 = GNUNET_TESTING_daemon_start (c1, TIMEOUT, GNUNET_NO, NULL, NULL, 0, NULL, - NULL, NULL, &my_cb1, NULL); - GNUNET_assert (d1 != NULL); -} - -static int -check () -{ - char *const argv[] = { "test-testing", - "-c", - "test_testing_data.conf", -#if VERBOSE - "-L", "DEBUG", -#endif - NULL - }; - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - GNUNET_PROGRAM_run ((sizeof (argv) / sizeof (char *)) - 1, argv, - "test-testing-connect", "nohelp", options, &run, &ok); - return ok; -} - -int -main (int argc, char *argv[]) -{ - int ret; - - GNUNET_log_setup ("test-testing-connect", -#if VERBOSE - "DEBUG", -#else - "WARNING", -#endif - NULL); - ret = check (); - return ret; -} - -/* end of test_testing_connect.c */ diff --git a/src/testing/test_testing_connect_peer1.conf b/src/testing/test_testing_connect_peer1.conf deleted file mode 100644 index cccda5e..0000000 --- a/src/testing/test_testing_connect_peer1.conf +++ /dev/null @@ -1,37 +0,0 @@ -@INLINE@ test_testing_defaults.conf -[PATHS] -SERVICEHOME = /tmp/test-gnunet-testing-connect-peer1/ -DEFAULTCONFIG = test_testing_connect_peer1.conf - -[transport-tcp] -PORT = 12568 - -[arm] -PORT = 12566 -DEFAULTSERVICES = core -UNIXPATH = /tmp/gnunet-p1-service-arm.sock - -[statistics] -PORT = 12567 -UNIXPATH = /tmp/gnunet-p1-service-statistics.sock - -[resolver] -PORT = 12564 -UNIXPATH = /tmp/gnunet-p1-service-resolver.sock - -[peerinfo] -PORT = 12569 -UNIXPATH = /tmp/gnunet-p1-service-peerinfo.sock - -[transport] -PORT = 12565 -UNIXPATH = /tmp/gnunet-p1-service-transport.sock - -[core] -PORT = 12570 -UNIXPATH = /tmp/gnunet-p1-service-core.sock - -[ats] -PORT = 12571 -UNIXPATH = /tmp/gnunet-p1-service-ats.sock - diff --git a/src/testing/test_testing_connect_peer2.conf b/src/testing/test_testing_connect_peer2.conf deleted file mode 100644 index 08ec551..0000000 --- a/src/testing/test_testing_connect_peer2.conf +++ /dev/null @@ -1,37 +0,0 @@ -@INLINE@ test_testing_defaults.conf -[PATHS] -SERVICEHOME = /tmp/test-gnunet-testing-connect-peer2/ -DEFAULTCONFIG = test_testing_connect_peer2.conf - -[transport-tcp] -PORT = 22568 - -[arm] -PORT = 22566 -DEFAULTSERVICES = core -UNIXPATH = /tmp/gnunet-p2-service-arm.sock - -[statistics] -PORT = 22567 -UNIXPATH = /tmp/gnunet-p2-service-statistics.sock - -[resolver] -PORT = 22564 -UNIXPATH = /tmp/gnunet-p2-service-resolver.sock - -[peerinfo] -PORT = 22569 -UNIXPATH = /tmp/gnunet-p2-service-peerinfo.sock - -[transport] -PORT = 22565 -UNIXPATH = /tmp/gnunet-p2-service-transport.sock - -[core] -PORT = 22570 -UNIXPATH = /tmp/gnunet-p2-service-core.sock - -[ats] -PORT = 22571 -UNIXPATH = /tmp/gnunet-p2-service-ats.sock - diff --git a/src/testing/test_testing_data.conf b/src/testing/test_testing_data.conf deleted file mode 100644 index c46cb0d..0000000 --- a/src/testing/test_testing_data.conf +++ /dev/null @@ -1,7 +0,0 @@ -@INLINE@ test_testing_defaults.conf -[PATHS] -DEFAULTCONFIG = test_testing_data.conf - -[arm] -DEFAULTSERVICES = core - diff --git a/src/testing/test_testing_data_remote.conf b/src/testing/test_testing_data_remote.conf deleted file mode 100644 index d58666f..0000000 --- a/src/testing/test_testing_data_remote.conf +++ /dev/null @@ -1,12 +0,0 @@ -@INLINE@ test_testing_defaults.conf -[PATHS] -DEFAULTCONFIG = test_testing_data_remote.conf - -[TESTING] -CONTROL_HOST = 127.0.0.1 -HOSTFILE = remote_hosts.txt -MAX_OUTSTANDING_SSH = 5 - -[statistics] -AUTOSTART = NO - diff --git a/src/testing/test_testing_data_topology_2d_torus.conf b/src/testing/test_testing_data_topology_2d_torus.conf deleted file mode 100644 index cbdaceb..0000000 --- a/src/testing/test_testing_data_topology_2d_torus.conf +++ /dev/null @@ -1,7 +0,0 @@ -@INLINE@ test_testing_defaults.conf -[PATHS] -DEFAULTCONFIG = test_testing_data_topology_2d_torus.conf - -[TESTING] -NUM_PEERS = 13 -TOPOLOGY = 2D_TORUS diff --git a/src/testing/test_testing_data_topology_blacklist.conf b/src/testing/test_testing_data_topology_blacklist.conf deleted file mode 100644 index 36e378d..0000000 --- a/src/testing/test_testing_data_topology_blacklist.conf +++ /dev/null @@ -1,13 +0,0 @@ -@INLINE@ test_testing_defaults.conf -[PATHS] -DEFAULTCONFIG = test_testing_data_topology_blacklist.conf - -[TESTING] -NUM_PEERS = 4 -TOPOLOGY = CLIQUE -BLACKLIST_TOPOLOGY = RING -BLACKLIST_TRANSPORTS = tcp udp http - -[transport-udp] -PORT = 2568 - diff --git a/src/testing/test_testing_data_topology_churn.conf b/src/testing/test_testing_data_topology_churn.conf deleted file mode 100644 index b337165..0000000 --- a/src/testing/test_testing_data_topology_churn.conf +++ /dev/null @@ -1,10 +0,0 @@ -@INLINE@ test_testing_defaults.conf -[PATHS] -DEFAULTCONFIG = test_testing_data_topology_churn.conf - -[TESTING] -NUM_PEERS = 12 - -[arm] -DEFAULTSERVICES = peerinfo transport core - diff --git a/src/testing/test_testing_data_topology_clique.conf b/src/testing/test_testing_data_topology_clique.conf deleted file mode 100644 index 69cecb7..0000000 --- a/src/testing/test_testing_data_topology_clique.conf +++ /dev/null @@ -1,10 +0,0 @@ -@INLINE@ test_testing_defaults.conf -[PATHS] -DEFAULTCONFIG = test_testing_data_topology_clique.conf - -[TESTING] -CONNECT_TIMEOUT = 180 s -CONNECT_ATTEMPTS = 14 -NUM_PEERS = 4 -TOPOLOGY = CLIQUE -SETTLE_TIME = 0 diff --git a/src/testing/test_testing_data_topology_clique_dfs.conf b/src/testing/test_testing_data_topology_clique_dfs.conf deleted file mode 100644 index c7abeae..0000000 --- a/src/testing/test_testing_data_topology_clique_dfs.conf +++ /dev/null @@ -1,13 +0,0 @@ -@INLINE@ test_testing_defaults.conf -[PATHS] -DEFAULTCONFIG = test_testing_data_topology_clique.conf - -[TESTING] -NUM_PEERS = 7 -TOPOLOGY = CLIQUE -CONNECT_TOPOLOGY_OPTION = CONNECT_DFS -CONNECT_TOPOLOGY_OPTION_MODIFIER = 2.0 - -[arm] -DEFAULTSERVICES = peerinfo transport core - diff --git a/src/testing/test_testing_data_topology_clique_minimum.conf b/src/testing/test_testing_data_topology_clique_minimum.conf deleted file mode 100644 index ef95cb1..0000000 --- a/src/testing/test_testing_data_topology_clique_minimum.conf +++ /dev/null @@ -1,10 +0,0 @@ -@INLINE@ test_testing_defaults.conf -[PATHS] -DEFAULTCONFIG = test_testing_data_topology_clique.conf - -[TESTING] -NUM_PEERS = 20 -TOPOLOGY = CLIQUE -CONNECT_TOPOLOGY_OPTION = CONNECT_MINIMUM -CONNECT_TOPOLOGY_OPTION_MODIFIER = 2.0 - diff --git a/src/testing/test_testing_data_topology_clique_random.conf b/src/testing/test_testing_data_topology_clique_random.conf deleted file mode 100644 index cd44b65..0000000 --- a/src/testing/test_testing_data_topology_clique_random.conf +++ /dev/null @@ -1,16 +0,0 @@ -@INLINE@ test_testing_defaults.conf -[PATHS] -DEFAULTCONFIG = test_testing_data_topology_clique.conf - -[TESTING] -NUM_PEERS = 20 -TOPOLOGY = CLIQUE -CONNECT_TOPOLOGY_OPTION = CONNECT_RANDOM_SUBSET -CONNECT_TOPOLOGY_OPTION_MODIFIER = .15 - -[statistics] -AUTOSTART = NO - -[resolver] -AUTOSTART = NO - diff --git a/src/testing/test_testing_data_topology_erdos_renyi.conf b/src/testing/test_testing_data_topology_erdos_renyi.conf deleted file mode 100644 index 8e17413..0000000 --- a/src/testing/test_testing_data_topology_erdos_renyi.conf +++ /dev/null @@ -1,7 +0,0 @@ -@INLINE@ test_testing_defaults.conf -[PATHS] -DEFAULTCONFIG = test_testing_data_topology_clique.conf - -[TESTING] -TOPOLOGY = ERDOS_RENYI - diff --git a/src/testing/test_testing_data_topology_internat.conf b/src/testing/test_testing_data_topology_internat.conf deleted file mode 100644 index af3f62f..0000000 --- a/src/testing/test_testing_data_topology_internat.conf +++ /dev/null @@ -1,7 +0,0 @@ -@INLINE@ test_testing_defaults.conf -[PATHS] -DEFAULTCONFIG = test_testing_data_topology_clique.conf - -[TESTING] -TOPOLOGY = INTERNAT - diff --git a/src/testing/test_testing_data_topology_none.conf b/src/testing/test_testing_data_topology_none.conf deleted file mode 100644 index dbee5d0..0000000 --- a/src/testing/test_testing_data_topology_none.conf +++ /dev/null @@ -1,37 +0,0 @@ -@INLINE@ test_testing_defaults.conf -[PATHS] -DEFAULTCONFIG = test_testing_data_topology_clique.conf - -[TESTING] -NUM_PEERS = 1000 -TOPOLOGY = NONE -F2F = NO -BLACKLIST_TOPOLOGY = NONE -CONNECT_TOPOLOGY = RING - -[arm] -PORT = 0 - -[statistics] -AUTOSTART = NO -PORT = 0 - -[resolver] -AUTOSTART = NO -PORT = 0 - -[peerinfo] -PORT = 0 - -[transport] -PORT = 0 - -[core] -PORT = 0 - -[topology] -PORT = 0 - -[hostlist] -PORT = 0 - diff --git a/src/testing/test_testing_data_topology_ring.conf b/src/testing/test_testing_data_topology_ring.conf deleted file mode 100644 index 6159030..0000000 --- a/src/testing/test_testing_data_topology_ring.conf +++ /dev/null @@ -1,7 +0,0 @@ -@INLINE@ test_testing_defaults.conf -[PATHS] -DEFAULTCONFIG = test_testing_data_topology_clique.conf - -[TESTING] -TOPOLOGY = RING - diff --git a/src/testing/test_testing_data_topology_scale_free.conf b/src/testing/test_testing_data_topology_scale_free.conf deleted file mode 100644 index 7690eac..0000000 --- a/src/testing/test_testing_data_topology_scale_free.conf +++ /dev/null @@ -1,11 +0,0 @@ -@INLINE@ test_testing_defaults.conf -[PATHS] -DEFAULTCONFIG = test_testing_data_topology_scale_free.conf - -[TESTING] -NUM_PEERS = 50 -TOPOLOGY = SCALE_FREE - -[arm] -DEFAULTSERVICES = peerinfo transport core - diff --git a/src/testing/test_testing_data_topology_small_world_ring.conf b/src/testing/test_testing_data_topology_small_world_ring.conf deleted file mode 100644 index 01931df..0000000 --- a/src/testing/test_testing_data_topology_small_world_ring.conf +++ /dev/null @@ -1,8 +0,0 @@ -@INLINE@ test_testing_defaults.conf -[PATHS] -DEFAULTCONFIG = test_testing_data_topology_clique.conf - -[TESTING] -NUM_PEERS = 25 -TOPOLOGY = SMALL_WORLD_RING - diff --git a/src/testing/test_testing_data_topology_small_world_torus.conf b/src/testing/test_testing_data_topology_small_world_torus.conf deleted file mode 100644 index 7c35454..0000000 --- a/src/testing/test_testing_data_topology_small_world_torus.conf +++ /dev/null @@ -1,7 +0,0 @@ -@INLINE@ test_testing_defaults.conf -[PATHS] -DEFAULTCONFIG = test_testing_data_topology_clique.conf - -[TESTING] -TOPOLOGY = SMALL_WORLD - diff --git a/src/testing/test_testing_data_topology_stability.conf b/src/testing/test_testing_data_topology_stability.conf deleted file mode 100644 index 1bfcd1b..0000000 --- a/src/testing/test_testing_data_topology_stability.conf +++ /dev/null @@ -1,9 +0,0 @@ -@INLINE@ test_testing_defaults.conf -[PATHS] -DEFAULTCONFIG = test_testing_data_topology_clique.conf - -[TESTING] -SETTLE_TIME = 600 s -NUM_PEERS = 2 -TOPOLOGY = CLIQUE - diff --git a/src/testing/test_testing_defaults.conf b/src/testing/test_testing_defaults.conf index ba7e269..1a58a31 100644 --- a/src/testing/test_testing_defaults.conf +++ b/src/testing/test_testing_defaults.conf @@ -1,6 +1,5 @@ [PATHS] SERVICEHOME = /tmp/test-gnunet-testing/ -DEFAULTCONFIG = test_testing_defaults.conf [resolver] PORT = 2564 @@ -9,6 +8,9 @@ PORT = 2564 PORT = 2565 PLUGINS = tcp +[transport-tcp] +TESTING_IGNORE_KEYS = SOMETHING;KEY1;ACCEPT_FROM; + [arm] PORT = 2566 DEFAULTSERVICES = @@ -26,12 +28,6 @@ PORT = 2569 [core] PORT = 2570 -[testing] -NUM_PEERS = 5 -WEAKRANDOM = YES -F2F = YES -HOSTKEYSFILE = ../../contrib/testing_hostkeys.dat - [dht] AUTOSTART = NO @@ -76,3 +72,7 @@ AUTOSTART = NO [lockmanager] AUTOSTART = NO + +[consensus] +AUTOSTART = NO + diff --git a/src/testing/test_testing_group.c b/src/testing/test_testing_group.c deleted file mode 100644 index f5df45b..0000000 --- a/src/testing/test_testing_group.c +++ /dev/null @@ -1,166 +0,0 @@ -/* - This file is part of GNUnet. - (C) 2009 Christian Grothoff (and other contributing authors) - - GNUnet is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published - by the Free Software Foundation; either version 3, or (at your - option) any later version. - - GNUnet is distributed in the hope that it will be useful, but - WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - General Public License for more details. - - You should have received a copy of the GNU General Public License - along with GNUnet; see the file COPYING. If not, write to the - Free Software Foundation, Inc., 59 Temple Place - Suite 330, - Boston, MA 02111-1307, USA. -*/ -/** - * @file testing/test_testing_group.c - * @brief testcase for functions to connect peers in testing.c - */ -#include "platform.h" -#include "gnunet_testing_lib.h" - -#define VERBOSE GNUNET_NO - -#define NUM_PEERS 4 - -/** - * How long until we give up on connecting the peers? - */ -#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 300) - -static int ok; - -static int peers_left; - -static int failed_peers; - -static struct GNUNET_TESTING_PeerGroup *pg; - -/** - * Check whether peers successfully shut down. - */ -void -shutdown_callback (void *cls, const char *emsg) -{ - if (emsg != NULL) - { -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Shutdown of peers failed!\n"); -#endif - if (ok == 0) - ok = 666; - } - else - { -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "All peers successfully shut down!\n"); -#endif - } -} - - -static void -my_cb (void *cls, const struct GNUNET_PeerIdentity *id, - const struct GNUNET_CONFIGURATION_Handle *cfg, - struct GNUNET_TESTING_Daemon *d, const char *emsg) -{ - if (id == NULL) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Start callback called with error (too long starting peers), aborting test!\n"); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Error from testing: `%s'\n"); - failed_peers++; - if (failed_peers == peers_left) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Too many peers failed, ending test!\n"); - ok = 1; - GNUNET_TESTING_daemons_stop (pg, TIMEOUT, &shutdown_callback, NULL); - } - return; - } - - peers_left--; - if (peers_left == 0) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "All peers started successfully, ending test!\n"); - GNUNET_TESTING_daemons_stop (pg, TIMEOUT, &shutdown_callback, NULL); - ok = 0; - } - else if (failed_peers == peers_left) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Too many peers failed, ending test!\n"); - ok = 1; - GNUNET_TESTING_daemons_stop (pg, TIMEOUT, &shutdown_callback, NULL); - } -} - - -static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) -{ - ok = 1; -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Starting daemons.\n"); -#endif - peers_left = NUM_PEERS; - pg = GNUNET_TESTING_daemons_start (cfg, peers_left, /* Total number of peers */ - peers_left, /* Number of outstanding connections */ - peers_left, /* Number of parallel ssh connections, or peers being started at once */ - TIMEOUT, NULL, NULL, &my_cb, NULL, NULL, - NULL, NULL); - GNUNET_assert (pg != NULL); -} - -static int -check () -{ - char *const argv[] = { "test-testing", - "-c", - "test_testing_data.conf", -#if VERBOSE - "-L", "DEBUG", -#endif - NULL - }; - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - GNUNET_PROGRAM_run ((sizeof (argv) / sizeof (char *)) - 1, argv, - "test-testing-group", "nohelp", options, &run, &ok); - return ok; -} - -int -main (int argc, char *argv[]) -{ - int ret; - - GNUNET_log_setup ("test-testing-group", -#if VERBOSE - "DEBUG", -#else - "WARNING", -#endif - NULL); - ret = check (); - /** - * Still need to remove the base testing directory here, - * because group starts will create subdirectories under this - * main dir. However, we no longer need to sleep, as the - * shutdown sequence won't return until everything is cleaned - * up. - */ - GNUNET_DISK_directory_remove ("/tmp/test-gnunet-testing"); - return ret; -} - -/* end of test_testing_group.c */ diff --git a/src/testing/test_testing_group_remote.c b/src/testing/test_testing_group_remote.c deleted file mode 100644 index b06655c..0000000 --- a/src/testing/test_testing_group_remote.c +++ /dev/null @@ -1,263 +0,0 @@ -/* - This file is part of GNUnet. - (C) 2009 Christian Grothoff (and other contributing authors) - - GNUnet is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published - by the Free Software Foundation; either version 3, or (at your - option) any later version. - - GNUnet is distributed in the hope that it will be useful, but - WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - General Public License for more details. - - You should have received a copy of the GNU General Public License - along with GNUnet; see the file COPYING. If not, write to the - Free Software Foundation, Inc., 59 Temple Place - Suite 330, - Boston, MA 02111-1307, USA. -*/ -/** - * @file testing/test_testing_group_remote.c - * @brief testcase for testing remote and local starting and connecting - * of hosts from the testing library. The test_testing_data_remote.conf - * file should be modified if this testcase is intended to be used. - */ -#include "platform.h" -#include "gnunet_testing_lib.h" - -#define VERBOSE GNUNET_YES - - -/** - * How long until we give up on connecting the peers? - */ -#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 300) - -#define DEFAULT_NUM_PEERS 8; - -static int ok; - -static int peers_left; - -static int peers_failed; - -static struct GNUNET_TESTING_PeerGroup *pg; - -static unsigned long long num_peers; - - -/** - * Check whether peers successfully shut down. - */ -void -shutdown_callback (void *cls, const char *emsg) -{ - if (emsg != NULL) - { -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Shutdown of peers failed (error %s)!\n", emsg); -#endif - if (ok == 0) - ok = 666; - } - else - { -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "All peers successfully shut down!\n"); -#endif - } -} - - -static void -my_cb (void *cls, const struct GNUNET_PeerIdentity *id, - const struct GNUNET_CONFIGURATION_Handle *cfg, - struct GNUNET_TESTING_Daemon *d, const char *emsg) -{ - if (emsg != NULL) - { - peers_failed++; - } - - peers_left--; - if (peers_left == 0) - { - GNUNET_TESTING_daemons_stop (pg, TIMEOUT, &shutdown_callback, NULL); - ok = 0; - } - else if (peers_failed == peers_left) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Too many peers failed, ending test!\n"); - GNUNET_TESTING_daemons_stop (pg, TIMEOUT, &shutdown_callback, NULL); - } -} - - -static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) -{ - struct GNUNET_TESTING_Host *hosts; - struct GNUNET_TESTING_Host *hostpos; - struct GNUNET_TESTING_Host *temphost; - char *hostfile; - struct stat frstat; - char *buf; - char *data; - int count; - int ret; - - ok = 1; -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Starting daemons.\n"); -#endif - - if (GNUNET_SYSERR == - GNUNET_CONFIGURATION_get_value_number (cfg, "testing", "num_peers", - &num_peers)) - num_peers = DEFAULT_NUM_PEERS; - - GNUNET_assert (num_peers > 0 && num_peers < (unsigned long long) -1); - if (GNUNET_OK != - GNUNET_CONFIGURATION_get_value_string (cfg, "testing", "hostfile", - &hostfile)) - hostfile = NULL; - - hosts = NULL; - data = NULL; - if (hostfile != NULL) - { - if (GNUNET_OK != GNUNET_DISK_file_test (hostfile)) - GNUNET_DISK_fn_write (hostfile, NULL, 0, - GNUNET_DISK_PERM_USER_READ | - GNUNET_DISK_PERM_USER_WRITE); - if ((0 != STAT (hostfile, &frstat)) || (frstat.st_size == 0)) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "Could not open file specified for host list, ending test!"); - ok = 1119; - GNUNET_free (hostfile); - return; - } - - data = GNUNET_malloc_large (frstat.st_size); - GNUNET_assert (data != NULL); - if (frstat.st_size != GNUNET_DISK_fn_read (hostfile, data, frstat.st_size)) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "Could not read file %s specified for host list, ending test!", - hostfile); - GNUNET_free (hostfile); - GNUNET_free (data); - return; - } - - GNUNET_free_non_null (hostfile); - - buf = data; - count = 0; - while (count < frstat.st_size) - { - count++; - if (count >= frstat.st_size) - break; - - /* if (((data[count] == '\n') || (data[count] == '\0')) && (buf != &data[count])) */ - if (((data[count] == '\n')) && (buf != &data[count])) - { - data[count] = '\0'; - temphost = GNUNET_malloc (sizeof (struct GNUNET_TESTING_Host)); - ret = - SSCANF (buf, "%a[a-zA-Z0-9]@%a[a-zA-Z0-9.]:%hd", - &temphost->username, &temphost->hostname, &temphost->port); - if (3 == ret) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Successfully read host %s, port %d and user %s from file\n", - temphost->hostname, temphost->port, temphost->username); - } - else - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Error reading line `%s' in hostfile\n", buf); - GNUNET_free (temphost); - buf = &data[count + 1]; - continue; - } - /* temphost->hostname = buf; */ - temphost->next = hosts; - hosts = temphost; - buf = &data[count + 1]; - } - else if ((data[count] == '\n') || (data[count] == '\0')) - buf = &data[count + 1]; - } - } - - peers_left = num_peers; - pg = GNUNET_TESTING_daemons_start (cfg, peers_left, /* Total number of peers */ - peers_left, /* Number of outstanding connections */ - peers_left, /* Number of parallel ssh connections, or peers being started at once */ - TIMEOUT, NULL, NULL, &my_cb, NULL, NULL, - NULL, hosts); - hostpos = hosts; - while (hostpos != NULL) - { - temphost = hostpos->next; - GNUNET_free (hostpos->hostname); - GNUNET_free (hostpos->username); - GNUNET_free (hostpos); - hostpos = temphost; - } - GNUNET_free_non_null (data); - GNUNET_assert (pg != NULL); - -} - -static int -check () -{ - char *const argv[] = { "test-testing", - "-c", - "test_testing_data_remote.conf", -#if VERBOSE - "-L", "DEBUG", -#endif - NULL - }; - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - GNUNET_PROGRAM_run ((sizeof (argv) / sizeof (char *)) - 1, argv, - "test-testing-group", "nohelp", options, &run, &ok); - return ok; -} - -int -main (int argc, char *argv[]) -{ - int ret; - - GNUNET_log_setup ("test-testing-group", -#if VERBOSE - "DEBUG", -#else - "WARNING", -#endif - NULL); - ret = check (); - /** - * Still need to remove the base testing directory here, - * because group starts will create subdirectories under this - * main dir. However, we no longer need to sleep, as the - * shutdown sequence won't return until everything is cleaned - * up. - */ - GNUNET_DISK_directory_remove ("/tmp/test-gnunet-testing"); - return ret; -} - -/* end of test_testing_group.c */ diff --git a/src/testing/test_testing_new_peerstartup.c b/src/testing/test_testing_new_peerstartup.c deleted file mode 100644 index 203df2f..0000000 --- a/src/testing/test_testing_new_peerstartup.c +++ /dev/null @@ -1,161 +0,0 @@ -/* - This file is part of GNUnet - (C) 2008, 2009, 2012 Christian Grothoff (and other contributing authors) - - GNUnet is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published - by the Free Software Foundation; either version 3, or (at your - option) any later version. - - GNUnet is distributed in the hope that it will be useful, but - WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - General Public License for more details. - - You should have received a copy of the GNU General Public License - along with GNUnet; see the file COPYING. If not, write to the - Free Software Foundation, Inc., 59 Temple Place - Suite 330, - Boston, MA 02111-1307, USA. - */ - -/** - * @file testing/test_testing_new_peerstartup.c - * @brief test case for testing peer startup and shutdown using new testing - * library - * @author Sree Harsha Totakura - */ - -#include "platform.h" -#include "gnunet_configuration_lib.h" -#include "gnunet_os_lib.h" -#include "gnunet_testing_lib-new.h" - -#define LOG(kind,...) \ - GNUNET_log (kind, __VA_ARGS__) - -#define TIME_REL_SEC(sec) \ - GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, sec) - -/** - * The testing context - */ -struct TestingContext -{ - /** - * The testing system - */ - struct GNUNET_TESTING_System *system; - - /** - * The peer which has been started by the testing system - */ - struct GNUNET_TESTING_Peer *peer; - - /** - * The running configuration of the peer - */ - struct GNUNET_CONFIGURATION_Handle *cfg; -}; - - -/** - * Task for shutdown - * - * @param cls the testing context - * @param tc the tast context - */ -static void -do_shutdown (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - struct TestingContext *test_ctx = cls; - - GNUNET_assert (GNUNET_OK == GNUNET_TESTING_peer_stop (test_ctx->peer)); - GNUNET_TESTING_peer_destroy (test_ctx->peer); - GNUNET_CONFIGURATION_destroy (test_ctx->cfg); - GNUNET_TESTING_hostkeys_unload (test_ctx->system); - GNUNET_TESTING_system_destroy (test_ctx->system, GNUNET_YES); - GNUNET_free (test_ctx); -} - - -/** - * Main point of test execution - */ -static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) -{ - struct GNUNET_TESTING_System *system; - struct GNUNET_TESTING_Peer *peer; - struct GNUNET_CONFIGURATION_Handle *new_cfg; - struct TestingContext *test_ctx; - char *data_dir; - char *hostkeys_file; - char *emsg; - char *_tmpdir; - char *tmpdir; -#ifdef MINGW - char *tmpdir_w; -#endif - - struct GNUNET_PeerIdentity id; - - _tmpdir = getenv ("TMP"); - if (NULL == _tmpdir) - _tmpdir = getenv ("TEMP"); - if (NULL == _tmpdir) - _tmpdir = getenv ("TMPDIR"); - if (NULL == _tmpdir) - _tmpdir = "/tmp"; - GNUNET_asprintf (&tmpdir, "%s/%s", _tmpdir, "test-gnunet-testing_new-XXXXXX"); -#ifdef MINGW - tmpdir_w = GNUNET_malloc (MAX_PATH + 1); - GNUNET_assert (ERROR_SUCCESS == plibc_conv_to_win_path (tmpdir, tmpdir_w)); - GNUNET_free (tmpdir); - tmpdir = tmpdir_w; - //GNUNET_assert (0 == _mktemp_s (tmpdir, strlen (tmpdir) + 1)); -#else - GNUNET_assert (mkdtemp (tmpdir) == tmpdir); -#endif - /* LOG (GNUNET_ERROR_TYPE_ERROR, */ - /* "Temporary directory: %s\n", tmpdir); */ - system = GNUNET_TESTING_system_create (tmpdir, - "localhost"); - GNUNET_assert (NULL != system); - GNUNET_free (tmpdir); - data_dir = GNUNET_OS_installation_get_path (GNUNET_OS_IPK_DATADIR); - GNUNET_asprintf (&hostkeys_file, "%s/testing_hostkeys.dat", data_dir); - GNUNET_free (data_dir); - GNUNET_assert (GNUNET_OK == - GNUNET_TESTING_hostkeys_load (system, hostkeys_file)); - GNUNET_free (hostkeys_file); - new_cfg = GNUNET_CONFIGURATION_dup (cfg); - emsg = NULL; - peer = GNUNET_TESTING_peer_configure (system, new_cfg, 0, &id, &emsg); - GNUNET_assert (NULL != peer); - GNUNET_assert (NULL == emsg); - GNUNET_assert (GNUNET_OK == GNUNET_TESTING_peer_start (peer)); - test_ctx = GNUNET_malloc (sizeof (struct TestingContext)); - test_ctx->system = system; - test_ctx->peer = peer; - test_ctx->cfg = new_cfg; - GNUNET_SCHEDULER_add_delayed (TIME_REL_SEC (5), - &do_shutdown, test_ctx); - -} - - -int main (int argc, char *argv[]) -{ - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - - if (GNUNET_OK != - GNUNET_PROGRAM_run (argc, argv, - "test_testing_new_peerstartup", - "test case for peerstartup using new testing library", - options, &run, NULL)) - return 1; - return 0; -} diff --git a/src/testing/test_testing_new_portreservation.c b/src/testing/test_testing_new_portreservation.c deleted file mode 100644 index 4010944..0000000 --- a/src/testing/test_testing_new_portreservation.c +++ /dev/null @@ -1,90 +0,0 @@ -/* - This file is part of GNUnet - (C) 2008, 2009, 2012 Christian Grothoff (and other contributing authors) - - GNUnet is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published - by the Free Software Foundation; either version 3, or (at your - option) any later version. - - GNUnet is distributed in the hope that it will be useful, but - WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - General Public License for more details. - - You should have received a copy of the GNU General Public License - along with GNUnet; see the file COPYING. If not, write to the - Free Software Foundation, Inc., 59 Temple Place - Suite 330, - Boston, MA 02111-1307, USA. - */ - -/** - * @file testing/test_testing_new_portreservation.c - * @brief test case for testing port reservation routines from the new testing - * library API - * @author Sree Harsha Totakura - */ - -#include "platform.h" -#include "gnunet_util_lib.h" -#include "gnunet_testing_lib-new.h" - -#define LOG(kind,...) \ - GNUNET_log (kind, __VA_ARGS__) - -/** - * Main point of test execution - */ -static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) -{ - struct GNUNET_TESTING_System *system; - uint16_t new_port1; - uint16_t new_port2; - uint16_t old_port1; - - system = GNUNET_TESTING_system_create ("/tmp/gnunet-testing-new", - "localhost"); - GNUNET_assert (NULL != system); - new_port1 = GNUNET_TESTING_reserve_port (system, GNUNET_YES); - LOG (GNUNET_ERROR_TYPE_DEBUG, - "Reserved TCP port %u\n", new_port1); - GNUNET_assert (0 != new_port1); - new_port2 = GNUNET_TESTING_reserve_port (system, GNUNET_YES); - LOG (GNUNET_ERROR_TYPE_DEBUG, - "Reserved TCP port %u\n", new_port2); - GNUNET_assert (0 != new_port2); - GNUNET_assert (new_port1 != new_port2); - GNUNET_TESTING_release_port (system, GNUNET_YES, new_port1); - old_port1 = new_port1; - new_port1 = 0; - new_port1 = GNUNET_TESTING_reserve_port (system, GNUNET_YES); - LOG (GNUNET_ERROR_TYPE_DEBUG, - "Reserved TCP port %u\n", new_port1); - GNUNET_assert (0 != new_port1); - GNUNET_assert (old_port1 == new_port1); - GNUNET_TESTING_release_port (system, GNUNET_YES, new_port1); - GNUNET_TESTING_release_port (system, GNUNET_YES, new_port2); - GNUNET_TESTING_system_destroy (system, GNUNET_NO); -} - -int main (int argc, char *argv[]) -{ - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - if (GNUNET_OK != - GNUNET_PROGRAM_run (argc, - argv, - "test_testing_new_portreservation", - "test case for testing port reservation routines" - " from the new testing library API", - options, - &run, - NULL)) - { - return 1; - } - return 0; -} diff --git a/src/testing/test_testing_new_servicestartup.c b/src/testing/test_testing_new_servicestartup.c deleted file mode 100644 index 3b98688..0000000 --- a/src/testing/test_testing_new_servicestartup.c +++ /dev/null @@ -1,110 +0,0 @@ -/* - This file is part of GNUnet - (C) 2008, 2009, 2012 Christian Grothoff (and other contributing authors) - - GNUnet is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published - by the Free Software Foundation; either version 3, or (at your - option) any later version. - - GNUnet is distributed in the hope that it will be useful, but - WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - General Public License for more details. - - You should have received a copy of the GNU General Public License - along with GNUnet; see the file COPYING. If not, write to the - Free Software Foundation, Inc., 59 Temple Place - Suite 330, - Boston, MA 02111-1307, USA. - */ - -/** - * @file testing/test_testing_new_servicestartup.c - * @brief test case for testing service startup using new testing API - * @author Sree Harsha Totakura - */ - -#include "platform.h" -#include "gnunet_testing_lib-new.h" - - -#define LOG(kind,...) \ - GNUNET_log (kind, __VA_ARGS__) - -#define TIME_REL_SEC(sec) \ - GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, sec) - -/** - * Global test status - */ -static int test_success; - -/** - * The shutdown task. Used to signal that testing is done and service has to be - * stopped - * - * @param cls NULL - */ -static void -shutdown_task(void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - test_success = GNUNET_YES; - GNUNET_SCHEDULER_shutdown (); -} - - -/** - * The testing callback function - * - * @param cls NULL - * @param cfg the configuration with which the current testing service is run - */ -static void -test_run (void *cls, const struct GNUNET_CONFIGURATION_Handle *cfg) -{ - GNUNET_assert (NULL == cls); - GNUNET_assert (NULL != cfg); - LOG (GNUNET_ERROR_TYPE_DEBUG, "Service arm started successfully\n"); - GNUNET_SCHEDULER_add_delayed (TIME_REL_SEC (3), &shutdown_task, NULL); -} - - -/** - * The main point of execution - */ -int main (int argc, char *argv[]) -{ - char *_tmpdir; - char *tmpdir; -#ifdef MINGW - char *tmpdir_w; -#endif - - GNUNET_log_setup ("test_testing_new_servicestartup", "DEBUG", NULL); - _tmpdir = getenv ("TMP"); - if (NULL == _tmpdir) - _tmpdir = getenv ("TEMP"); - if (NULL == _tmpdir) - _tmpdir = getenv ("TMPDIR"); - if (NULL == _tmpdir) - _tmpdir = "/tmp"; - GNUNET_asprintf (&tmpdir, "%s/%s", _tmpdir, "test-gnunet-testing_new-XXXXXX"); -#ifdef MINGW - tmpdir_w = GNUNET_malloc (MAX_PATH + 1); - GNUNET_assert (ERROR_SUCCESS == plibc_conv_to_win_path (tmpdir, tmpdir_w)); - GNUNET_free (tmpdir); - tmpdir = tmpdir_w; - //GNUNET_assert (0 == _mktemp_s (tmpdir, strlen (tmpdir) + 1)); -#else - GNUNET_assert (mkdtemp (tmpdir) == tmpdir); -#endif - - test_success = GNUNET_NO; - GNUNET_assert (0 == GNUNET_TESTING_service_run (tmpdir, - "arm", - "test_testing_defaults.conf", - &test_run, - NULL)); - GNUNET_free (tmpdir); - return (GNUNET_YES == test_success) ? 0 : 1; -} diff --git a/src/testing/test_testing_peergroup.c b/src/testing/test_testing_peergroup.c deleted file mode 100644 index 061a0ca..0000000 --- a/src/testing/test_testing_peergroup.c +++ /dev/null @@ -1,157 +0,0 @@ -/* - This file is part of GNUnet. - (C) 2009 Christian Grothoff (and other contributing authors) - - GNUnet is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published - by the Free Software Foundation; either version 3, or (at your - option) any later version. - - GNUnet is distributed in the hope that it will be useful, but - WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - General Public License for more details. - - You should have received a copy of the GNU General Public License - along with GNUnet; see the file COPYING. If not, write to the - Free Software Foundation, Inc., 59 Temple Place - Suite 330, - Boston, MA 02111-1307, USA. -*/ -/** - * @file testing/test_testing_peergroup.c - * @brief testcase for functions to connect peers in testing_peergroup.c - */ -#include "platform.h" -#include "gnunet_testing_lib.h" - -#define VERBOSE GNUNET_NO - -#define NUM_PEERS 4 - -/** - * How long until we give up on connecting the peers? - */ -#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 300) - -static int ok; - -static int peers_left; - -static struct GNUNET_TESTING_PeerGroup *pg; - -/** - * Check whether peers successfully shut down. - */ -void -shutdown_callback (void *cls, const char *emsg) -{ - if (emsg != NULL) - { -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Shutdown of peers failed!\n"); -#endif - if (ok == 0) - ok = 666; - } - else - { -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "All peers successfully shut down!\n"); -#endif - ok = 0; - } -} - - -static void -my_cb (void *cls, const char *emsg) -{ - if (emsg != NULL) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Peergroup callback called with error, aborting test!\n"); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Error from testing: `%s'\n"); - ok = 1; - GNUNET_TESTING_daemons_stop (pg, TIMEOUT, &shutdown_callback, NULL); - return; - } - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Peer Group started successfully, ending test!\n"); - /** - * If something is to actually be DONE with the testcase, it should - * be put in here. Usually there will be a struct declared (or global - * variables can be used) to keep track of the state, statistics, - * handles to peers, etc. The example here is the opaque "TestCaseData" - * struct that could be passed into a function "additional_code_for_testing" - * which can be used to perform actions on the peers in the peergroup. - * Also, the GNUNET_TESTING_daemons_stop call would need to be removed, - * and only called once all of the testing is complete. - */ - - /** - * struct TestcaseData *state_closure; - * GNUNET_SCHEDULER_add_now(&additional_code_for_testing, state_closure); - */ - - GNUNET_TESTING_daemons_stop (pg, TIMEOUT, &shutdown_callback, NULL); -} - - -static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) -{ - struct GNUNET_CONFIGURATION_Handle *testing_cfg; - - ok = 1; - testing_cfg = GNUNET_CONFIGURATION_create (); - GNUNET_assert (GNUNET_OK == GNUNET_CONFIGURATION_load (testing_cfg, cfgfile)); -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Starting daemons.\n"); - GNUNET_CONFIGURATION_set_value_string (testing_cfg, "testing", - "use_progressbars", "YES"); -#endif - peers_left = NUM_PEERS; - pg = GNUNET_TESTING_peergroup_start (testing_cfg, peers_left, TIMEOUT, NULL, - &my_cb, NULL, NULL); - GNUNET_assert (pg != NULL); -} - -static int -check () -{ - char *const argv[] = { "test-testing-peergroup", - "-c", - "test_testing_peergroup_data.conf", -#if VERBOSE - "-L", "DEBUG", -#endif - NULL - }; - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - GNUNET_PROGRAM_run ((sizeof (argv) / sizeof (char *)) - 1, argv, - "test-testing-peergroup", "nohelp", options, &run, &ok); - return ok; -} - -int -main (int argc, char *argv[]) -{ - int ret; - - GNUNET_log_setup ("test-testing-peergroup", -#if VERBOSE - "DEBUG", -#else - "WARNING", -#endif - NULL); - ret = check (); - GNUNET_DISK_directory_remove ("/tmp/test-gnunet-testing"); - return ret; -} - -/* end of test_testing_peergroup.c */ diff --git a/src/testing/test_testing_peergroup_data.conf b/src/testing/test_testing_peergroup_data.conf deleted file mode 100644 index 6eadede..0000000 --- a/src/testing/test_testing_peergroup_data.conf +++ /dev/null @@ -1,22 +0,0 @@ -@INLINE@ test_testing_defaults.conf -[PATHS] -DEFAULTCONFIG = test_testing_peergroup_data.conf - -[TESTING] -CONNECT_ATTEMPTS = 2 -MAX_OUTSTANDING_CONNECTIONS = 20 -MAX_CONCURRENT_SSH = 1 -PEERGROUP_TIMEOUT = 300 s -TOPOLOGY = CLIQUE -PERCENTAGE = 0.5 -PROBABILITY = 0.5 -CONNECT_TOPOLOGY = CLIQUE -CONNECT_TOPOLOGY_OPTION = CONNECT_NONE -CONNECT_TOPOLOGY_OPTION_MODIFIER = 0.0 -BLACKLIST_TOPOLOGY = NONE -BLACKLIST_TRANSPORTS = tcp udp -USE_PROGRESSBARS = NO - -[arm] -DEFAULTSERVICES = core - diff --git a/src/testing/test_testing_peerstartup.c b/src/testing/test_testing_peerstartup.c new file mode 100644 index 0000000..fb3967c --- /dev/null +++ b/src/testing/test_testing_peerstartup.c @@ -0,0 +1,143 @@ +/* + This file is part of GNUnet + (C) 2008, 2009, 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. + */ + +/** + * @file testing/test_testing_new_peerstartup.c + * @brief test case for testing peer startup and shutdown using new testing + * library + * @author Sree Harsha Totakura + */ + +#include "platform.h" +#include "gnunet_configuration_lib.h" +#include "gnunet_os_lib.h" +#include "gnunet_testing_lib.h" + +#define LOG(kind,...) \ + GNUNET_log (kind, __VA_ARGS__) + +/** + * The status of the test + */ +int status; + +/** + * The testing context + */ +struct TestingContext +{ + /** + * The testing system + */ + struct GNUNET_TESTING_System *system; + + /** + * The peer which has been started by the testing system + */ + struct GNUNET_TESTING_Peer *peer; + + /** + * The running configuration of the peer + */ + struct GNUNET_CONFIGURATION_Handle *cfg; +}; + + +/** + * Task for shutdown + * + * @param cls the testing context + * @param tc the tast context + */ +static void +do_shutdown (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct TestingContext *test_ctx = cls; + + GNUNET_assert (NULL != test_ctx); + if (NULL != test_ctx->peer) + { + (void) GNUNET_TESTING_peer_stop (test_ctx->peer); + GNUNET_TESTING_peer_destroy (test_ctx->peer); + } + if (NULL != test_ctx->cfg) + GNUNET_CONFIGURATION_destroy (test_ctx->cfg); + if (NULL != test_ctx->system) + GNUNET_TESTING_system_destroy (test_ctx->system, GNUNET_YES); + GNUNET_free (test_ctx); +} + + +/** + * Main point of test execution + */ +static void +run (void *cls, char *const *args, const char *cfgfile, + const struct GNUNET_CONFIGURATION_Handle *cfg) +{ + struct TestingContext *test_ctx; + char *emsg; + struct GNUNET_PeerIdentity id; + + test_ctx = GNUNET_malloc (sizeof (struct TestingContext)); + test_ctx->system = + GNUNET_TESTING_system_create ("test-gnunet-testing", + "127.0.0.1", NULL); + emsg = NULL; + if (NULL == test_ctx->system) + goto end; + test_ctx->cfg = GNUNET_CONFIGURATION_dup (cfg); + test_ctx->peer = + GNUNET_TESTING_peer_configure (test_ctx->system, + test_ctx->cfg, + 0, &id, &emsg); + if (NULL == test_ctx->peer) + { + if (NULL != emsg) + printf ("Test failed upon error: %s", emsg); + goto end; + } + if (GNUNET_OK != GNUNET_TESTING_peer_start (test_ctx->peer)) + goto end; + status = GNUNET_OK; + + end: + GNUNET_SCHEDULER_add_now (&do_shutdown, test_ctx); + GNUNET_free_non_null (emsg); +} + + +int main (int argc, char *argv[]) +{ + struct GNUNET_GETOPT_CommandLineOption options[] = { + GNUNET_GETOPT_OPTION_END + }; + + status = GNUNET_SYSERR; + if (GNUNET_OK != + GNUNET_PROGRAM_run (argc, argv, + "test_testing_new_peerstartup", + "test case for peerstartup using new testing library", + options, &run, NULL)) + return 1; + return (GNUNET_OK == status) ? 0 : 1; +} + +/* end of test_testing_peerstartup.c */ diff --git a/src/testing/test_testing_portreservation.c b/src/testing/test_testing_portreservation.c new file mode 100644 index 0000000..21ef51f --- /dev/null +++ b/src/testing/test_testing_portreservation.c @@ -0,0 +1,103 @@ +/* + This file is part of GNUnet + (C) 2008, 2009, 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. + */ + +/** + * @file testing/test_testing_new_portreservation.c + * @brief test case for testing port reservation routines from the new testing + * library API + * @author Sree Harsha Totakura + */ + +#include "platform.h" +#include "gnunet_util_lib.h" +#include "gnunet_testing_lib.h" + +#define LOG(kind,...) \ + GNUNET_log (kind, __VA_ARGS__) + +/** + * The status of the test + */ +int status; + +/** + * Main point of test execution + */ +static void +run (void *cls, char *const *args, const char *cfgfile, + const struct GNUNET_CONFIGURATION_Handle *cfg) +{ + struct GNUNET_TESTING_System *system; + uint16_t new_port1; + uint16_t new_port2; + uint16_t old_port1; + + system = GNUNET_TESTING_system_create ("/tmp/gnunet-testing-new", + "localhost", NULL); + GNUNET_assert (NULL != system); + new_port1 = GNUNET_TESTING_reserve_port (system, GNUNET_YES); + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Reserved TCP port %u\n", new_port1); + if (0 == new_port1) + goto end; + new_port2 = GNUNET_TESTING_reserve_port (system, GNUNET_YES); + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Reserved TCP port %u\n", new_port2); + if (0 == new_port2) + goto end; + GNUNET_assert (new_port1 != new_port2); + GNUNET_TESTING_release_port (system, GNUNET_YES, new_port1); + old_port1 = new_port1; + new_port1 = 0; + new_port1 = GNUNET_TESTING_reserve_port (system, GNUNET_YES); + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Reserved TCP port %u\n", new_port1); + GNUNET_assert (0 != new_port1); + GNUNET_assert (old_port1 == new_port1); + GNUNET_TESTING_release_port (system, GNUNET_YES, new_port1); + GNUNET_TESTING_release_port (system, GNUNET_YES, new_port2); + status = GNUNET_OK; + + end: + GNUNET_TESTING_system_destroy (system, GNUNET_YES); +} + + +int main (int argc, char *argv[]) +{ + struct GNUNET_GETOPT_CommandLineOption options[] = { + GNUNET_GETOPT_OPTION_END + }; + + status = GNUNET_SYSERR; + if (GNUNET_OK != + GNUNET_PROGRAM_run (argc, + argv, + "test_testing_new_portreservation", + "test case for testing port reservation routines" + " from the new testing library API", + options, + &run, + NULL)) + return 1; + return (GNUNET_OK == status) ? 0 : 1; +} + +/* end of test_testing_portreservation.c */ diff --git a/src/testing/test_testing_reconnect.c b/src/testing/test_testing_reconnect.c deleted file mode 100644 index bcee386..0000000 --- a/src/testing/test_testing_reconnect.c +++ /dev/null @@ -1,249 +0,0 @@ -/* - This file is part of GNUnet. - (C) 2010 Christian Grothoff (and other contributing authors) - - GNUnet is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published - by the Free Software Foundation; either version 3, or (at your - option) any later version. - - GNUnet is distributed in the hope that it will be useful, but - WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - General Public License for more details. - - You should have received a copy of the GNU General Public License - along with GNUnet; see the file COPYING. If not, write to the - Free Software Foundation, Inc., 59 Temple Place - Suite 330, - Boston, MA 02111-1307, USA. -*/ -/** - * @file testing/test_testing_reconnect.c - * @brief testcase for functions to connect two peers in testing.c - */ -#include "platform.h" -#include "gnunet_testing_lib.h" - -#define VERBOSE GNUNET_YES - -/** - * How long until we give up on connecting the peers? - */ -#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 300) - -#define CONNECT_ATTEMPTS 3 - -static int ok; - -static struct GNUNET_TESTING_Daemon *d1; - -static struct GNUNET_TESTING_Daemon *d2; - -static struct GNUNET_CONFIGURATION_Handle *c1; - -static struct GNUNET_CONFIGURATION_Handle *c2; - -static struct GNUNET_TESTING_ConnectContext *cc; - -/** - * How many start-connect-stop iterations should we do? - */ -#define NUM_PHASES 2 - -static int phase; - -/** - * Run the next phase of starting daemons, connecting them and - * stopping them again. - */ -static void -run_phase (void); - -static void -end2_cb (void *cls, const char *emsg) -{ - - if (emsg != NULL) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Ending with error: %s\n", emsg); - ok = 1; - } - else - { - if (phase < NUM_PHASES) - { - FPRINTF (stderr, "%s", "."); - run_phase (); - return; - } - FPRINTF (stderr, "%s", ".\n"); -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Both daemons terminated, will now exit.\n"); -#endif - ok = 0; - } -} - -static void -end1_cb (void *cls, const char *emsg) -{ - if (emsg != NULL) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Stopping daemon 1 gave: %s\n", - emsg); - ok = 1; - } - else - { - ok = 0; - } - if (d2 != NULL) - { - GNUNET_TESTING_daemon_stop (d2, TIMEOUT, &end2_cb, NULL, - (phase == NUM_PHASES) ? GNUNET_YES : GNUNET_NO, - GNUNET_NO); - d2 = NULL; - } -} - -static void -finish_testing (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - GNUNET_TESTING_daemon_stop (d1, TIMEOUT, &end1_cb, NULL, - (phase == NUM_PHASES) ? GNUNET_YES : GNUNET_NO, - GNUNET_NO); - d1 = NULL; -} - - -static void -my_connect_complete (void *cls, const struct GNUNET_PeerIdentity *first, - const struct GNUNET_PeerIdentity *second, - unsigned int distance, - const struct GNUNET_CONFIGURATION_Handle *first_cfg, - const struct GNUNET_CONFIGURATION_Handle *second_cfg, - struct GNUNET_TESTING_Daemon *first_daemon, - struct GNUNET_TESTING_Daemon *second_daemon, - const char *emsg) -{ - cc = NULL; -#if VERBOSE - FPRINTF (stderr, "Peer %s ", GNUNET_i2s (first)); - FPRINTF (stderr, "connected to %s\n", GNUNET_i2s (second)); -#endif - GNUNET_SCHEDULER_add_now (&finish_testing, NULL); -} - - - - -static void -my_cb2 (void *cls, const struct GNUNET_PeerIdentity *id, - const struct GNUNET_CONFIGURATION_Handle *cfg, - struct GNUNET_TESTING_Daemon *d, const char *emsg) -{ - if (emsg != NULL) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Starting daemon 2 gave: %s\n", - emsg); - GNUNET_assert (0); - return; - } - GNUNET_assert (id != NULL); -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Daemon `%s' started.\n", - GNUNET_i2s (id)); -#endif - cc = GNUNET_TESTING_daemons_connect (d1, d2, TIMEOUT, CONNECT_ATTEMPTS, - GNUNET_YES, &my_connect_complete, NULL); -} - - -static void -my_cb1 (void *cls, const struct GNUNET_PeerIdentity *id, - const struct GNUNET_CONFIGURATION_Handle *cfg, - struct GNUNET_TESTING_Daemon *d, const char *emsg) -{ - if (emsg != NULL) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Starting daemon 1 gave: %s\n", - emsg); - GNUNET_assert (0); - return; - } - GNUNET_assert (id != NULL); -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Daemon `%s' started.\n", - GNUNET_i2s (id)); -#endif - d2 = GNUNET_TESTING_daemon_start (c2, TIMEOUT, GNUNET_NO, NULL, NULL, 0, NULL, - NULL, NULL, &my_cb2, NULL); - GNUNET_assert (d2 != NULL); -} - - -static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) -{ - ok = 1; -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Starting daemon.\n"); -#endif - c1 = GNUNET_CONFIGURATION_create (); - GNUNET_assert (GNUNET_OK == - GNUNET_CONFIGURATION_load (c1, - "test_testing_connect_peer1.conf")); - c2 = GNUNET_CONFIGURATION_create (); - GNUNET_assert (GNUNET_OK == - GNUNET_CONFIGURATION_load (c2, - "test_testing_connect_peer2.conf")); - run_phase (); -} - -static void -run_phase () -{ - phase++; - d1 = GNUNET_TESTING_daemon_start (c1, TIMEOUT, GNUNET_NO, NULL, NULL, 0, NULL, - NULL, NULL, &my_cb1, NULL); - GNUNET_assert (d1 != NULL); -} - -static int -check () -{ - char *const argv[] = { "test-testing-reconnect", - "-c", - "test_testing_data.conf", -#if VERBOSE - "-L", "DEBUG", -#endif - NULL - }; - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - GNUNET_PROGRAM_run ((sizeof (argv) / sizeof (char *)) - 1, argv, - "test-testing-reconnect", "nohelp", options, &run, &ok); - return ok; -} - -int -main (int argc, char *argv[]) -{ - int ret; - - GNUNET_log_setup ("test-testing-reconnect", -#if VERBOSE - "DEBUG", -#else - "WARNING", -#endif - NULL); - ret = check (); - return ret; -} - -/* end of test_testing_reconnect.c */ diff --git a/src/testing/test_testing_servicestartup.c b/src/testing/test_testing_servicestartup.c new file mode 100644 index 0000000..adb7181 --- /dev/null +++ b/src/testing/test_testing_servicestartup.c @@ -0,0 +1,74 @@ +/* + This file is part of GNUnet + (C) 2008, 2009, 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. + */ + +/** + * @file testing/test_testing_new_servicestartup.c + * @brief test case for testing service startup using new testing API + * @author Sree Harsha Totakura + */ +#include "platform.h" +#include "gnunet_scheduler_lib.h" +#include "gnunet_testing_lib.h" + + +#define LOG(kind,...) \ + GNUNET_log (kind, __VA_ARGS__) + + +/** + * Global test status + */ +static int test_success; + + +/** + * The testing callback function + * + * @param cls NULL + * @param cfg the configuration with which the current testing service is run + */ +static void +test_run (void *cls, const struct GNUNET_CONFIGURATION_Handle *cfg, + struct GNUNET_TESTING_Peer *peer) +{ + GNUNET_assert (NULL == cls); + GNUNET_assert (NULL != cfg); + LOG (GNUNET_ERROR_TYPE_DEBUG, "Service arm started successfully\n"); + test_success = GNUNET_YES; + GNUNET_SCHEDULER_shutdown (); +} + + +/** + * The main point of execution + */ +int main (int argc, char *argv[]) +{ + test_success = GNUNET_NO; + GNUNET_assert (0 == GNUNET_TESTING_service_run ("test-testing-servicestartup", + "arm", + "test_testing_defaults.conf", + &test_run, + NULL)); + return (GNUNET_YES == test_success) ? 0 : 1; +} + +/* end of test_testing_servicestartup.c */ + diff --git a/src/testing/test_testing_topology.c b/src/testing/test_testing_topology.c deleted file mode 100644 index b216544..0000000 --- a/src/testing/test_testing_topology.c +++ /dev/null @@ -1,1220 +0,0 @@ -/* - This file is part of GNUnet. - (C) 2009 Christian Grothoff (and other contributing authors) - - GNUnet is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published - by the Free Software Foundation; either version 3, or (at your - option) any later version. - - GNUnet is distributed in the hope that it will be useful, but - WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - General Public License for more details. - - You should have received a copy of the GNU General Public License - along with GNUnet; see the file COPYING. If not, write to the - Free Software Foundation, Inc., 59 Temple Place - Suite 330, - Boston, MA 02111-1307, USA. -*/ -/** - * @file testing/test_testing_topology.c - * @brief base testcase for testing all the topologies provided - */ -#include "platform.h" -#include "gnunet_testing_lib.h" -#include "gnunet_core_service.h" -#include "gnunet_os_lib.h" - - -#define PROGRESS_BARS GNUNET_YES - -#define DELAY_FOR_LOGGING GNUNET_NO - -/** - * How long until we fail the whole testcase? - */ -#define TEST_TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 240) - -/** - * How long until we give up on starting the peers? - */ -#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 500) - -#define SECONDS_PER_PEER_START 120 - -#define DEFAULT_NUM_PEERS 4 - -#define MAX_OUTSTANDING_CONNECTIONS 100 - -static float fail_percentage = 0.05; - -static int ok; - -static unsigned long long num_peers; - -struct GNUNET_TIME_Relative connect_timeout; - -static unsigned long long connect_attempts; - -static unsigned int topology_connections; - -static unsigned int total_connections; - -static unsigned int failed_connections; - -static unsigned int total_server_connections; - -static unsigned int total_messages_received; - -static unsigned int expected_messages; - -static unsigned int expected_connections; - -static unsigned long long peers_left; - -static struct GNUNET_TESTING_PeerGroup *pg; - -const struct GNUNET_CONFIGURATION_Handle *main_cfg; - -GNUNET_SCHEDULER_TaskIdentifier die_task; - -static char *dotOutFileName; - -static struct GNUNET_TIME_Relative settle_time; - -static FILE *dotOutFile; - -static char *topology_string; - -static char *blacklist_transports; - -static int transmit_ready_scheduled; - -static int transmit_ready_failed; - -static int transmit_ready_called; - -static unsigned int modnum; - -static unsigned int dotnum; - -static enum GNUNET_TESTING_Topology topology; - -static enum GNUNET_TESTING_Topology blacklist_topology = GNUNET_TESTING_TOPOLOGY_NONE; /* Don't do any blacklisting */ - -static enum GNUNET_TESTING_Topology connection_topology = GNUNET_TESTING_TOPOLOGY_NONE; /* NONE actually means connect all allowed peers */ - -static enum GNUNET_TESTING_TopologyOption connect_topology_option = - GNUNET_TESTING_TOPOLOGY_OPTION_ALL; - -static double connect_topology_option_modifier = 0.0; - -static char *test_directory; - -#define MTYPE 12345 - -GNUNET_NETWORK_STRUCT_BEGIN - -struct GNUNET_TestMessage -{ - /** - * Header of the message - */ - struct GNUNET_MessageHeader header; - - /** - * Unique identifier for this message. - */ - uint32_t uid; -}; -GNUNET_NETWORK_STRUCT_END - -struct TestMessageContext -{ - /* This is a linked list */ - struct TestMessageContext *next; - - /* Handle to the sending peer core */ - struct GNUNET_CORE_Handle *peer1handle; - - /* Handle to the receiving peer core */ - struct GNUNET_CORE_Handle *peer2handle; - - /* Handle to the sending peer daemon */ - struct GNUNET_TESTING_Daemon *peer1; - - /* Handle to the receiving peer daemon */ - struct GNUNET_TESTING_Daemon *peer2; - - /* Identifier for this message, so we don't disconnect other peers! */ - uint32_t uid; - - /* Has peer1 been notified already of a connection to peer2? */ - int peer1notified; - - /* Has the core of peer2 been connected already? */ - int peer2connected; - - /* Task for disconnecting cores, allow task to be cancelled on shutdown */ - GNUNET_SCHEDULER_TaskIdentifier disconnect_task; - -}; - -static struct TestMessageContext *test_messages; - -/** - * Check whether peers successfully shut down. - */ -static void -shutdown_callback (void *cls, const char *emsg) -{ - if (emsg != NULL) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Shutdown of peers failed: %s!\n", - emsg); - if (ok == 0) - ok = 666; - } - else - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "All peers successfully shut down!\n"); - } -} - - -#if DELAY_FOR_LOGGING -static void -gather_log_data () -{ - char *peer_number; - char *connect_number; - struct GNUNET_OS_Process *mem_process; - - GNUNET_asprintf (&peer_number, "%llu", num_peers); - GNUNET_asprintf (&connect_number, "%llu", expected_connections); - mem_process = - GNUNET_OS_start_process (NULL, NULL, "./memsize.pl", "memsize.pl", - "totals.txt", peer_number, connect_number, NULL); - GNUNET_OS_process_wait (mem_process); - GNUNET_OS_process_destroy (mem_process); - mem_process = NULL; -} -#endif - - -static void -finish_testing () -{ - GNUNET_assert (pg != NULL); - struct TestMessageContext *pos; - struct TestMessageContext *free_pos; - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Called finish testing, stopping daemons.\n"); - pos = test_messages; - while (pos != NULL) - { - if (pos->peer1handle != NULL) - { - GNUNET_CORE_disconnect (pos->peer1handle); - pos->peer1handle = NULL; - } - if (pos->peer2handle != NULL) - { - GNUNET_CORE_disconnect (pos->peer2handle); - pos->peer2handle = NULL; - } - free_pos = pos; - pos = pos->next; - if (free_pos->disconnect_task != GNUNET_SCHEDULER_NO_TASK) - { - GNUNET_SCHEDULER_cancel (free_pos->disconnect_task); - } - GNUNET_free (free_pos); - } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Transmit_ready's scheduled %d, failed %d, transmit_ready's called %d\n", - transmit_ready_scheduled, transmit_ready_failed, - transmit_ready_called); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Calling daemons_stop\n"); - GNUNET_TESTING_daemons_stop (pg, TIMEOUT, &shutdown_callback, NULL); - - if (dotOutFile != NULL) - { - FPRINTF (dotOutFile, "%s", "}"); - FCLOSE (dotOutFile); - } - ok = 0; -} - - -static void -disconnect_cores (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - struct TestMessageContext *pos = cls; - - /* Disconnect from the respective cores */ - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Disconnecting from peer 1 `%4s'\n", - GNUNET_i2s (&pos->peer1->id)); - if (pos->peer1handle != NULL) - { - GNUNET_CORE_disconnect (pos->peer1handle); - pos->peer1handle = NULL; - } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Disconnecting from peer 2 `%4s'\n", - GNUNET_i2s (&pos->peer2->id)); - if (pos->peer2handle != NULL) - { - GNUNET_CORE_disconnect (pos->peer2handle); - pos->peer2handle = NULL; - } - pos->disconnect_task = GNUNET_SCHEDULER_NO_TASK; - /* Decrement total connections so new can be established */ - total_server_connections -= 2; -} - -#if DO_STATS -static void -stats_finished (void *cls, int result) -{ - GNUNET_SCHEDULER_add_now (&finish_testing, NULL); -} - -/** - * Callback function to process statistic values. - * - * @param cls closure - * @param peer the peer the statistics belong to - * @param subsystem name of subsystem that created the statistic - * @param name the name of the datum - * @param value the current value - * @param is_persistent GNUNET_YES if the value is persistent, GNUNET_NO if not - * @return GNUNET_OK to continue, GNUNET_SYSERR to abort iteration - */ -static int -stats_print (void *cls, const struct GNUNET_PeerIdentity *peer, - const char *subsystem, const char *name, uint64_t value, - int is_persistent) -{ - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "%s:%s:%s -- %llu\n", GNUNET_i2s (peer), - subsystem, name, value); - return GNUNET_OK; -} -#endif - - -static void -topology_cb (void *cls, const struct GNUNET_PeerIdentity *first, - const struct GNUNET_PeerIdentity *second, const char *emsg) -{ - FILE *outfile = cls; - - if (first != NULL) - { - if (outfile != NULL) - { - FPRINTF (outfile, "\t\"%s\" -- ", GNUNET_i2s (first)); - FPRINTF (outfile, "\"%s\";\n", GNUNET_i2s (second)); - } - topology_connections++; - } - else - { - FPRINTF (stderr, - "Finished iterating over topology, %d total connections!\n", - topology_connections); - if (outfile != NULL) - { - FPRINTF (outfile, "%s", "}\n"); - FCLOSE (outfile); -#if DO_STATS - GNUNET_TESTING_get_statistics (pg, &stats_finished, &stats_print, NULL); -#endif - GNUNET_SCHEDULER_add_now (&finish_testing, NULL); - } - } -} - - -static int -process_mtype (void *cls, const struct GNUNET_PeerIdentity *peer, - const struct GNUNET_MessageHeader *message, - const struct GNUNET_ATS_Information *atsi, - unsigned int atsi_count) -{ - char *dotOutFileNameFinished; - FILE *dotOutFileFinished; - struct TestMessageContext *pos = cls; - struct GNUNET_TestMessage *msg = (struct GNUNET_TestMessage *) message; - - if (pos->uid != ntohl (msg->uid)) - return GNUNET_OK; - -#if PROGRESS_BARS - if ((total_messages_received) % modnum == 0) - { - if (total_messages_received == 0) - FPRINTF (stdout, "%s", "0%%"); - else - FPRINTF (stdout, "%d%%", - (int) (((float) total_messages_received / expected_messages) * - 100)); - - } - else if (total_messages_received % dotnum == 0) - { - FPRINTF (stdout, "%s", "."); - } - fflush (stdout); -#endif - - total_messages_received++; - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Received message from `%4s', type %d.\n", GNUNET_i2s (peer), - ntohs (message->type)); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Total messages received %d, expected %d.\n", - total_messages_received, expected_messages); - - if (total_messages_received == expected_messages) - { -#if PROGRESS_BARS - FPRINTF (stdout, "%s", "100%%]\n"); -#endif - GNUNET_SCHEDULER_cancel (die_task); - GNUNET_asprintf (&dotOutFileNameFinished, "%s.dot", "final_topology"); - dotOutFileFinished = FOPEN (dotOutFileNameFinished, "w"); - GNUNET_free (dotOutFileNameFinished); - if (dotOutFileFinished != NULL) - { - FPRINTF (dotOutFileFinished, "%s", "strict graph G {\n"); - } - topology_connections = 0; - GNUNET_TESTING_get_topology (pg, &topology_cb, dotOutFileFinished); - //GNUNET_SCHEDULER_add_now (&finish_testing, NULL); - } - else - { - pos->disconnect_task = GNUNET_SCHEDULER_add_now (&disconnect_cores, pos); - } - - return GNUNET_OK; -} - - -static void -end_badly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - char *msg = cls; - - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "Ending with error: %s\n", msg); - struct TestMessageContext *pos; - struct TestMessageContext *free_pos; - - pos = test_messages; - while (pos != NULL) - { - if (pos->peer1handle != NULL) - { - GNUNET_CORE_disconnect (pos->peer1handle); - pos->peer1handle = NULL; - } - if (pos->peer2handle != NULL) - { - GNUNET_CORE_disconnect (pos->peer2handle); - pos->peer2handle = NULL; - } - free_pos = pos; - pos = pos->next; - GNUNET_free (free_pos); - } - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Transmit_ready's scheduled %d, failed %d, transmit_ready's called %d\n", - transmit_ready_scheduled, transmit_ready_failed, - transmit_ready_called); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Total messages received %d, expected %d.\n", - total_messages_received, expected_messages); - - if (pg != NULL) - { - GNUNET_TESTING_daemons_stop (pg, TIMEOUT, &shutdown_callback, NULL); - ok = 7331; /* Opposite of leet */ - } - else - ok = 401; /* Never got peers started */ - - if (dotOutFile != NULL) - { - FPRINTF (dotOutFile, "%s", "}"); - FCLOSE (dotOutFile); - } -} - - -static size_t -transmit_ready (void *cls, size_t size, void *buf) -{ - struct GNUNET_TestMessage *m; - struct TestMessageContext *pos = cls; - - GNUNET_assert (buf != NULL); - m = (struct GNUNET_TestMessage *) buf; - m->header.type = htons (MTYPE); - m->header.size = htons (sizeof (struct GNUNET_TestMessage)); - m->uid = htonl (pos->uid); - transmit_ready_called++; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "transmit ready for peer %s\ntransmit_ready's scheduled %d, transmit_ready's called %d\n", - GNUNET_i2s (&pos->peer1->id), transmit_ready_scheduled, - transmit_ready_called); - return sizeof (struct GNUNET_TestMessage); -} - - -static struct GNUNET_CORE_MessageHandler no_handlers[] = { - {NULL, 0, 0} -}; - - -static struct GNUNET_CORE_MessageHandler handlers[] = { - {&process_mtype, MTYPE, sizeof (struct GNUNET_TestMessage)}, - {NULL, 0, 0} -}; - - -static void -init_notify_peer2 (void *cls, struct GNUNET_CORE_Handle *server, - const struct GNUNET_PeerIdentity *my_identity) -{ - struct TestMessageContext *pos = cls; - - total_server_connections++; - - pos->peer2connected = GNUNET_YES; - if (pos->peer1notified == GNUNET_YES) /* Peer 1 has been notified of connection to peer 2 */ - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Scheduling message send to peer `%s' from peer `%s' (init_notify_peer2)\n", - GNUNET_i2s (my_identity), - GNUNET_h2s (&pos->peer1->id.hashPubKey)); - if (NULL == - GNUNET_CORE_notify_transmit_ready (pos->peer1handle, GNUNET_YES, 0, - TIMEOUT, &pos->peer2->id, - sizeof (struct GNUNET_TestMessage), - &transmit_ready, pos)) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "RECEIVED NULL when asking core (1) for transmission to peer `%4s'\n", - GNUNET_i2s (&pos->peer2->id)); - transmit_ready_failed++; - } - else - { - transmit_ready_scheduled++; - } - } -} - - -/** - * Method called whenever a given peer connects. - * - * @param cls closure - * @param peer peer identity this notification is about - * @param atsi performance data for the connection - * @param atsi_count number of records in 'atsi' - */ -static void -connect_notify_peers (void *cls, const struct GNUNET_PeerIdentity *peer, - const struct GNUNET_ATS_Information *atsi, - unsigned int atsi_count) -{ - struct TestMessageContext *pos = cls; - - if (0 == memcmp (peer, &pos->peer2->id, sizeof (struct GNUNET_PeerIdentity))) - { - pos->peer1notified = GNUNET_YES; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Peer `%s' notified of connection to peer `%s'\n", - GNUNET_i2s (&pos->peer1->id), GNUNET_h2s (&peer->hashPubKey)); - } - else - return; - - if (pos->peer2connected == GNUNET_YES) /* Already connected and notified of connection, send message! */ - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Scheduling message send to peer `%s' from peer `%s' (init_notify_peer2)\n", - GNUNET_i2s (&pos->peer2->id), - GNUNET_h2s (&pos->peer1->id.hashPubKey)); - if (NULL == - GNUNET_CORE_notify_transmit_ready (pos->peer1handle, GNUNET_YES, 0, - TIMEOUT, &pos->peer2->id, - sizeof (struct GNUNET_TestMessage), - &transmit_ready, pos)) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "RECEIVED NULL when asking core (1) for transmission to peer `%4s'\n", - GNUNET_i2s (&pos->peer2->id)); - transmit_ready_failed++; - } - else - { - transmit_ready_scheduled++; - } - } -} - - -static void -init_notify_peer1 (void *cls, struct GNUNET_CORE_Handle *server, - const struct GNUNET_PeerIdentity *my_identity) -{ - struct TestMessageContext *pos = cls; - - total_server_connections++; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Core connection to `%4s' established, setting up handles\n", - GNUNET_i2s (my_identity)); - /* - * Connect to the receiving peer - */ - pos->peer2handle = - GNUNET_CORE_connect (pos->peer2->cfg, 1, pos, &init_notify_peer2, NULL, - NULL, NULL, GNUNET_YES, NULL, GNUNET_YES, handlers); - -} - - -static void -send_test_messages (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - struct TestMessageContext *pos = cls; - - if ((pos == test_messages) && (settle_time.rel_value > 0)) - { - topology_connections = 0; - GNUNET_TESTING_get_topology (pg, &topology_cb, NULL); - } - if (((tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN) != 0) || (cls == NULL)) - return; - - if (die_task == GNUNET_SCHEDULER_NO_TASK) - { - die_task = - GNUNET_SCHEDULER_add_delayed (TEST_TIMEOUT, &end_badly, - "from send test messages (timeout)"); - } - - if (total_server_connections >= MAX_OUTSTANDING_CONNECTIONS) - { - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply - (GNUNET_TIME_UNIT_SECONDS, 1), - &send_test_messages, pos); - return; /* Otherwise we'll double schedule messages here! */ - } - - /* - * Connect to the sending peer - */ - pos->peer1handle = - GNUNET_CORE_connect (pos->peer1->cfg, 1, pos, &init_notify_peer1, - &connect_notify_peers, NULL, NULL, GNUNET_NO, NULL, - GNUNET_NO, no_handlers); - - GNUNET_assert (pos->peer1handle != NULL); - - if (total_server_connections < MAX_OUTSTANDING_CONNECTIONS) - { - GNUNET_SCHEDULER_add_now (&send_test_messages, pos->next); - } - else - { - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply - (GNUNET_TIME_UNIT_SECONDS, 1), - &send_test_messages, pos->next); - } -} - - -static void -topology_callback (void *cls, const struct GNUNET_PeerIdentity *first, - const struct GNUNET_PeerIdentity *second, uint32_t distance, - const struct GNUNET_CONFIGURATION_Handle *first_cfg, - const struct GNUNET_CONFIGURATION_Handle *second_cfg, - struct GNUNET_TESTING_Daemon *first_daemon, - struct GNUNET_TESTING_Daemon *second_daemon, - const char *emsg) -{ - struct TestMessageContext *temp_context; - - if (emsg == NULL) - { -#if PROGRESS_BARS - if ((total_connections) % modnum == 0) - { - if (total_connections == 0) - FPRINTF (stdout, "%s", "0%%"); - else - FPRINTF (stdout, "%d%%", - (int) (((float) total_connections / expected_connections) * - 100)); - - } - else if (total_connections % dotnum == 0) - { - FPRINTF (stdout, "%s", "."); - } - fflush (stdout); -#endif - total_connections++; - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "connected peer %s to peer %s\n", - first_daemon->shortname, second_daemon->shortname); - temp_context = GNUNET_malloc (sizeof (struct TestMessageContext)); - temp_context->peer1 = first_daemon; - temp_context->peer2 = second_daemon; - temp_context->next = test_messages; - temp_context->uid = total_connections; - temp_context->disconnect_task = GNUNET_SCHEDULER_NO_TASK; - test_messages = temp_context; - - expected_messages++; - if (dotOutFile != NULL) - FPRINTF (dotOutFile, "\tn%s -- n%s;\n", first_daemon->shortname, - second_daemon->shortname); - } - else - { - failed_connections++; - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "Failed to connect peer %s to peer %s with error :\n%s\n", - first_daemon->shortname, second_daemon->shortname, emsg); - } - - if (total_connections == expected_connections) - { -#if PROGRESS_BARS - FPRINTF (stdout, "%s", "100%%]\n"); -#endif - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Created %d total connections, which is our target number! Calling send messages.\n", - total_connections); - modnum = expected_messages / 4; - dotnum = (expected_messages / 50) + 1; - if (modnum == 0) - modnum = 1; - if (dotnum == 0) - dotnum = 1; - GNUNET_SCHEDULER_cancel (die_task); - die_task = GNUNET_SCHEDULER_NO_TASK; -#if DELAY_FOR_LOGGING - FPRINTF (stdout, "%s", "Sending test messages in 10 seconds.\n"); - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply - (GNUNET_TIME_UNIT_SECONDS, 10), - &send_test_messages, test_messages); - gather_log_data (); -#else - if (settle_time.rel_value > 0) - { - GNUNET_TESTING_get_topology (pg, &topology_cb, NULL); - } - GNUNET_SCHEDULER_add_delayed (settle_time, &send_test_messages, - test_messages); -#endif -#if PROGRESS_BARS - FPRINTF (stdout, "%s", "Test message progress: ["); -#endif - - } - else if (total_connections + failed_connections == expected_connections) - { - if (failed_connections < - (unsigned int) (fail_percentage * total_connections)) - { - GNUNET_SCHEDULER_cancel (die_task); - die_task = GNUNET_SCHEDULER_NO_TASK; - GNUNET_SCHEDULER_add_now (&send_test_messages, test_messages); - } - else - { - GNUNET_SCHEDULER_cancel (die_task); - die_task = - GNUNET_SCHEDULER_add_now (&end_badly, - "from topology_callback (too many failed connections)"); - } - } - else - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Have %d total connections, %d failed connections, Want %d (at least %d)\n", - total_connections, failed_connections, expected_connections, - expected_connections - - (unsigned int) (fail_percentage * expected_connections)); - } -} - - -static void -topology_creation_finished (void *cls, const char *emsg) -{ - if (emsg == NULL) - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "All topology connections created successfully!\n"); -} - - -static void -connect_topology () -{ - expected_connections = -1; - if ((pg != NULL) && (peers_left == 0)) - { - expected_connections = - GNUNET_TESTING_connect_topology (pg, connection_topology, - connect_topology_option, - connect_topology_option_modifier, - connect_timeout, connect_attempts, - &topology_creation_finished, NULL); -#if PROGRESS_BARS - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Have %d expected connections\n", - expected_connections); -#endif - } - - GNUNET_SCHEDULER_cancel (die_task); - if (expected_connections < 1) - { - die_task = - GNUNET_SCHEDULER_add_now (&end_badly, - "from connect topology (bad return)"); - return; - } - - die_task = - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply - (GNUNET_TIME_UNIT_SECONDS, - SECONDS_PER_PEER_START * num_peers), - &end_badly, - "from connect topology (timeout)"); - modnum = expected_connections / 4; - dotnum = (expected_connections / 50) + 1; - if (modnum == 0) - modnum = 1; - if (dotnum == 0) - dotnum = 1; -#if PROGRESS_BARS - FPRINTF (stdout, "%s", "Peer connection progress: ["); -#endif -} - -static void -create_topology () -{ - peers_left = num_peers; /* Reset counter */ - if (GNUNET_TESTING_create_topology - (pg, topology, blacklist_topology, blacklist_transports) != GNUNET_SYSERR) - { -#if PROGRESS_BARS - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Topology set up, now starting peers!\n"); - FPRINTF (stdout, "%s", "Daemon start progress ["); -#endif - GNUNET_TESTING_daemons_continue_startup (pg); - } - else - { - GNUNET_SCHEDULER_cancel (die_task); - die_task = - GNUNET_SCHEDULER_add_now (&end_badly, - "from create topology (bad return)"); - } - GNUNET_SCHEDULER_cancel (die_task); - die_task = - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply - (GNUNET_TIME_UNIT_SECONDS, - SECONDS_PER_PEER_START * num_peers), - &end_badly, - "from continue startup (timeout)"); -} - - -static void -peers_started_callback (void *cls, const struct GNUNET_PeerIdentity *id, - const struct GNUNET_CONFIGURATION_Handle *cfg, - struct GNUNET_TESTING_Daemon *d, const char *emsg) -{ - if (emsg != NULL) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Failed to start daemon with error: `%s'\n", emsg); - return; - } - GNUNET_assert (id != NULL); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Started daemon %llu out of %llu\n", - (num_peers - peers_left) + 1, num_peers); -#if PROGRESS_BARS - if ((num_peers - peers_left) % modnum == 0) - { - if (num_peers - peers_left == 0) - FPRINTF (stdout, "%s", "0%%"); - else - FPRINTF (stdout, "%d%%", - (int) (((float) (num_peers - peers_left) / num_peers) * 100)); - - } - else if ((num_peers - peers_left) % dotnum == 0) - { - FPRINTF (stdout, "%s", "."); - } - fflush (stdout); -#endif - peers_left--; - if (peers_left == 0) - { -#if PROGRESS_BARS - FPRINTF (stdout, "%s", "100%%]\n"); -#endif - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "All %d daemons started, now connecting peers!\n", num_peers); - GNUNET_SCHEDULER_cancel (die_task); - /* Set up task in case topology creation doesn't finish - * within a reasonable amount of time */ - die_task = - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply - (GNUNET_TIME_UNIT_MINUTES, 8), &end_badly, - "from peers_started_callback"); -#if DELAY_FOR_LOGGING - FPRINTF (stdout, "%s", "Connecting topology in 10 seconds\n"); - gather_log_data (); - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply - (GNUNET_TIME_UNIT_SECONDS, 10), - &connect_topology, NULL); -#else - connect_topology (); -#endif - ok = 0; - } -} - -/** - * Callback indicating that the hostkey was created for a peer. - * - * @param cls NULL - * @param id the peer identity - * @param d the daemon handle (pretty useless at this point, remove?) - * @param emsg non-null on failure - */ -void -hostkey_callback (void *cls, const struct GNUNET_PeerIdentity *id, - struct GNUNET_TESTING_Daemon *d, const char *emsg) -{ - if (emsg != NULL) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Hostkey callback received error: %s\n", emsg); - } - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Hostkey (%d/%d) created for peer `%s'\n", num_peers - peers_left, - num_peers, GNUNET_i2s (id)); -#if PROGRESS_BARS - if ((num_peers - peers_left) % modnum == 0) - { - if (num_peers - peers_left == 0) - FPRINTF (stdout, "%s", "0%%"); - else - FPRINTF (stdout, "%d%%", - (int) (((float) (num_peers - peers_left) / num_peers) * 100)); - - } - else if ((num_peers - peers_left) % dotnum == 0) - { - FPRINTF (stdout, "%s", "."); - } - fflush (stdout); -#endif - peers_left--; - if (peers_left == 0) - { -#if PROGRESS_BARS - FPRINTF (stdout, "%s", "100%%]\n"); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "All %d hostkeys created, now creating topology!\n", num_peers); -#endif - GNUNET_SCHEDULER_cancel (die_task); - /* Set up task in case topology creation doesn't finish - * within a reasonable amount of time */ - die_task = - GNUNET_SCHEDULER_add_delayed (TIMEOUT, &end_badly, - "from create_topology"); - GNUNET_SCHEDULER_add_now (&create_topology, NULL); - ok = 0; - } -} - - -static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) -{ - char *topology_str; - char *connect_topology_str; - char *blacklist_topology_str; - char *connect_topology_option_str; - char *connect_topology_option_modifier_string; - unsigned long long max_outstanding_connections; - - ok = 1; - - dotOutFile = FOPEN (dotOutFileName, "w"); - if (dotOutFile != NULL) - { - FPRINTF (dotOutFile, "%s", "strict graph G {\n"); - } - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Starting daemons based on config file %s\n", cfgfile); - if (GNUNET_YES != - GNUNET_CONFIGURATION_get_value_string (cfg, "paths", "servicehome", - &test_directory)) - { - ok = 404; - return; - } - - if ((GNUNET_YES == - GNUNET_CONFIGURATION_get_value_string (cfg, "testing", "topology", - &topology_str)) && - (GNUNET_NO == GNUNET_TESTING_topology_get (&topology, topology_str))) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Invalid topology `%s' given for section %s option %s\n", - topology_str, "TESTING", "TOPOLOGY"); - topology = GNUNET_TESTING_TOPOLOGY_CLIQUE; /* Defaults to NONE, so set better default here */ - } - - if ((GNUNET_YES == - GNUNET_CONFIGURATION_get_value_string (cfg, "testing", - "connect_topology", - &connect_topology_str)) && - (GNUNET_NO == - GNUNET_TESTING_topology_get (&connection_topology, - connect_topology_str))) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Invalid connect topology `%s' given for section %s option %s\n", - connect_topology_str, "TESTING", "CONNECT_TOPOLOGY"); - } - GNUNET_free_non_null (connect_topology_str); - if ((GNUNET_YES == - GNUNET_CONFIGURATION_get_value_string (cfg, "testing", - "connect_topology_option", - &connect_topology_option_str)) && - (GNUNET_NO == - GNUNET_TESTING_topology_option_get (&connect_topology_option, - connect_topology_option_str))) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Invalid connect topology option `%s' given for section %s option %s\n", - connect_topology_option_str, "TESTING", - "CONNECT_TOPOLOGY_OPTION"); - connect_topology_option = GNUNET_TESTING_TOPOLOGY_OPTION_ALL; /* Defaults to NONE, set to ALL */ - } - GNUNET_free_non_null (connect_topology_option_str); - if (GNUNET_YES == - GNUNET_CONFIGURATION_get_value_string (cfg, "testing", - "connect_topology_option_modifier", - &connect_topology_option_modifier_string)) - { - if (SSCANF - (connect_topology_option_modifier_string, "%lf", - &connect_topology_option_modifier) != 1) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - _ - ("Invalid value `%s' for option `%s' in section `%s': expected float\n"), - connect_topology_option_modifier_string, - "connect_topology_option_modifier", "TESTING"); - } - GNUNET_free (connect_topology_option_modifier_string); - } - - if (GNUNET_YES != - GNUNET_CONFIGURATION_get_value_string (cfg, "testing", - "blacklist_transports", - &blacklist_transports)) - blacklist_transports = NULL; - - if ((GNUNET_YES == - GNUNET_CONFIGURATION_get_value_string (cfg, "testing", - "blacklist_topology", - &blacklist_topology_str)) && - (GNUNET_NO == - GNUNET_TESTING_topology_get (&blacklist_topology, - blacklist_topology_str))) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Invalid topology `%s' given for section %s option %s\n", - topology_str, "TESTING", "BLACKLIST_TOPOLOGY"); - } - GNUNET_free_non_null (topology_str); - GNUNET_free_non_null (blacklist_topology_str); - - if (GNUNET_OK != - GNUNET_CONFIGURATION_get_value_time (cfg, "testing", "SETTLE_TIME", - &settle_time)) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Must provide option %s:%s!\n", - "testing", "SETTLE_TIME"); - return; - } - - if (GNUNET_OK != - GNUNET_CONFIGURATION_get_value_time (cfg, "testing", "CONNECT_TIMEOUT", - &connect_timeout)) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Must provide option %s:%s!\n", - "testing", "CONNECT_TIMEOUT"); - return; - } - - - if (GNUNET_OK != - GNUNET_CONFIGURATION_get_value_number (cfg, "testing", "connect_attempts", - &connect_attempts)) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Must provide option %s:%s!\n", - "testing", "connect_attempts"); - return; - } - - if (GNUNET_OK != - GNUNET_CONFIGURATION_get_value_number (cfg, "testing", - "max_outstanding_connections", - &max_outstanding_connections)) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Must provide option %s:%s!\n", - "testing", "max_outstanding_connections"); - return; - } - - if (GNUNET_SYSERR == - GNUNET_CONFIGURATION_get_value_number (cfg, "testing", "num_peers", - &num_peers)) - num_peers = DEFAULT_NUM_PEERS; - - main_cfg = cfg; - - peers_left = num_peers; - modnum = num_peers / 4; - dotnum = (num_peers / 50) + 1; - if (modnum == 0) - modnum = 1; - if (dotnum == 0) - dotnum = 1; -#if PROGRESS_BARS - FPRINTF (stdout, "%s", "Hostkey generation progress: ["); -#endif - /* Set up a task to end testing if peer start fails */ - die_task = - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply - (GNUNET_TIME_UNIT_SECONDS, - SECONDS_PER_PEER_START * num_peers), - &end_badly, - "didn't generate all hostkeys within a reasonable amount of time!!!"); - - GNUNET_assert (num_peers > 0 && num_peers < (unsigned int) -1); - pg = GNUNET_TESTING_daemons_start (cfg, peers_left, - max_outstanding_connections, peers_left, - GNUNET_TIME_relative_multiply - (GNUNET_TIME_UNIT_SECONDS, - SECONDS_PER_PEER_START * num_peers), - &hostkey_callback, NULL, - &peers_started_callback, NULL, - &topology_callback, NULL, NULL); - -} - - -static int -check () -{ - char *binary_name; - char *config_file_name; - - GNUNET_asprintf (&binary_name, "test-testing-topology-%s", topology_string); - GNUNET_asprintf (&config_file_name, "test_testing_data_topology_%s.conf", - topology_string); - int ret; - - char *const argv[] = { binary_name, - "-c", - config_file_name, - NULL - }; - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - ret = - GNUNET_PROGRAM_run ((sizeof (argv) / sizeof (char *)) - 1, argv, - binary_name, "nohelp", options, &run, &ok); - if (ret != GNUNET_OK) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "`test-testing-topology-%s': Failed with error code %d\n", - topology_string, ret); - } - GNUNET_free (binary_name); - GNUNET_free (config_file_name); - return ok; -} - - -int -main (int argc, char *argv[]) -{ - int ret; - char *binary_start_pos; - char *our_binary_name; - char *dotexe; - - binary_start_pos = strchr (argv[0], '/'); - GNUNET_assert (binary_start_pos != NULL); - topology_string = strstr (binary_start_pos, "_topology"); - GNUNET_assert (topology_string != NULL); - topology_string++; - topology_string = strstr (topology_string, "_"); - GNUNET_assert (topology_string != NULL); - topology_string++; - topology_string = GNUNET_strdup (topology_string); - if (NULL != (dotexe = strstr (topology_string, ".exe"))) - dotexe[0] = '\0'; - GNUNET_asprintf (&our_binary_name, "test-testing-topology_%s", - topology_string); - GNUNET_asprintf (&dotOutFileName, "topology_%s.dot", topology_string); - - GNUNET_log_setup (our_binary_name, - "WARNING", - NULL); - ret = check (); - GNUNET_free (topology_string); - - /** - * Need to remove base directory, subdirectories taken care - * of by the testing framework. - */ - if (GNUNET_DISK_directory_remove (test_directory) != GNUNET_OK) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Failed to remove testing directory %s\n", test_directory); - } - GNUNET_free (our_binary_name); - return ret; -} - -/* end of test_testing_topology.c */ diff --git a/src/testing/test_testing_topology_blacklist.c b/src/testing/test_testing_topology_blacklist.c deleted file mode 100644 index c90f48d..0000000 --- a/src/testing/test_testing_topology_blacklist.c +++ /dev/null @@ -1,595 +0,0 @@ -/* - This file is part of GNUnet. - (C) 2009 Christian Grothoff (and other contributing authors) - - GNUnet is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published - by the Free Software Foundation; either version 3, or (at your - option) any later version. - - GNUnet is distributed in the hope that it will be useful, but - WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - General Public License for more details. - - You should have received a copy of the GNU General Public License - along with GNUnet; see the file COPYING. If not, write to the - Free Software Foundation, Inc., 59 Temple Place - Suite 330, - Boston, MA 02111-1307, USA. -*/ -/** - * @file testing/test_testing_topology_blacklist.c - * @brief base testcase for testing transport level blacklisting - */ -#include "platform.h" -#include "gnunet_testing_lib.h" -#include "gnunet_core_service.h" - -#define VERBOSE GNUNET_NO - -/** - * How long until we fail the whole testcase? - */ -#define TEST_TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 600) - -/** - * How long until we give up on starting the peers? (Must be longer than the connect timeout!) - */ -#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 300) - -#define DEFAULT_NUM_PEERS 4 - -#define MAX_OUTSTANDING_CONNECTIONS 300 - -static int ok; - -struct GNUNET_TIME_Relative connect_timeout; - -static unsigned long long connect_attempts; - -static unsigned long long num_peers; - -static unsigned int total_connections; - -static unsigned int failed_connections; - -static unsigned int expected_connections; - -static unsigned int expected_failed_connections; - -static unsigned long long peers_left; - -static struct GNUNET_TESTING_PeerGroup *pg; - -const struct GNUNET_CONFIGURATION_Handle *main_cfg; - -GNUNET_SCHEDULER_TaskIdentifier die_task; - -static char *dotOutFileName; - -static FILE *dotOutFile; - -static char *blacklist_transports; - -static enum GNUNET_TESTING_Topology topology = GNUNET_TESTING_TOPOLOGY_CLIQUE; /* Overlay should allow all connections */ - -static enum GNUNET_TESTING_Topology blacklist_topology = GNUNET_TESTING_TOPOLOGY_RING; /* Blacklist underlay into a ring */ - -static enum GNUNET_TESTING_Topology connection_topology = GNUNET_TESTING_TOPOLOGY_NONE; /* NONE actually means connect all allowed peers */ - -static enum GNUNET_TESTING_TopologyOption connect_topology_option = GNUNET_TESTING_TOPOLOGY_OPTION_ALL; /* Try to connect all possible OVERLAY connections */ - -static double connect_topology_option_modifier = 0.0; - -static char *test_directory; - -#define MTYPE 12345 - -GNUNET_NETWORK_STRUCT_BEGIN - -struct GNUNET_TestMessage -{ - /** - * Header of the message - */ - struct GNUNET_MessageHeader header; - - /** - * Unique identifier for this message. - */ - uint32_t uid; -}; -GNUNET_NETWORK_STRUCT_END - -/** - * Check whether peers successfully shut down. - */ -void -shutdown_callback (void *cls, const char *emsg) -{ - if (emsg != NULL) - { -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Shutdown of peers failed!\n"); -#endif - if (ok == 0) - ok = 666; - } - else - { -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "All peers successfully shut down!\n"); -#endif - } -} - -static void -finish_testing () -{ - GNUNET_assert (pg != NULL); - -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Called finish testing, stopping daemons.\n"); -#endif - sleep (1); -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Calling daemons_stop\n"); -#endif - GNUNET_TESTING_daemons_stop (pg, TIMEOUT, &shutdown_callback, NULL); -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "daemons_stop finished\n"); -#endif - if (dotOutFile != NULL) - { - FPRINTF (dotOutFile, "%s", "}"); - FCLOSE (dotOutFile); - } - - ok = 0; -} - -static void -end_badly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - char *msg = cls; - - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "End badly was called (%s)... stopping daemons.\n", msg); - - if (pg != NULL) - { - GNUNET_TESTING_daemons_stop (pg, TIMEOUT, &shutdown_callback, NULL); - ok = 7331; /* Opposite of leet */ - } - else - ok = 401; /* Never got peers started */ - - if (dotOutFile != NULL) - { - FPRINTF (dotOutFile, "%s", "}"); - FCLOSE (dotOutFile); - } -} - - - -void -topology_callback (void *cls, const struct GNUNET_PeerIdentity *first, - const struct GNUNET_PeerIdentity *second, uint32_t distance, - const struct GNUNET_CONFIGURATION_Handle *first_cfg, - const struct GNUNET_CONFIGURATION_Handle *second_cfg, - struct GNUNET_TESTING_Daemon *first_daemon, - struct GNUNET_TESTING_Daemon *second_daemon, - const char *emsg) -{ - if (emsg == NULL) - { - total_connections++; -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "connected peer %s to peer %s\n", - first_daemon->shortname, second_daemon->shortname); -#endif - if (dotOutFile != NULL) - FPRINTF (dotOutFile, "\tn%s -- n%s;\n", first_daemon->shortname, - second_daemon->shortname); - } - - else - { - failed_connections++; -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Failed to connect peer %s to peer %s with error :\n%s\n", - first_daemon->shortname, second_daemon->shortname, emsg); -#endif - } - - - if (total_connections == expected_connections) - { -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Created %d total connections, which is our target number (that's bad)!\n", - total_connections); -#endif - - GNUNET_SCHEDULER_cancel (die_task); - die_task = GNUNET_SCHEDULER_NO_TASK; - die_task = - GNUNET_SCHEDULER_add_now (&end_badly, - "from topology_callback (too many successful connections)"); - } - else if (total_connections + failed_connections == expected_connections) - { - if ((failed_connections == expected_failed_connections) && - (total_connections == - expected_connections - expected_failed_connections)) - { - GNUNET_SCHEDULER_cancel (die_task); - die_task = GNUNET_SCHEDULER_NO_TASK; - die_task = GNUNET_SCHEDULER_add_now (&finish_testing, NULL); - } - else - { - GNUNET_SCHEDULER_cancel (die_task); - die_task = - GNUNET_SCHEDULER_add_now (&end_badly, - "from topology_callback (wrong number of failed connections)"); - } - } - else - { -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Have %d total connections, %d failed connections, Want %d (failed) and %d (successful)\n", - total_connections, failed_connections, - expected_failed_connections, - expected_connections - expected_failed_connections); -#endif - } -} - -static void -connect_topology () -{ - expected_connections = -1; - if ((pg != NULL) && (peers_left == 0)) - { - expected_connections = - GNUNET_TESTING_connect_topology (pg, connection_topology, - connect_topology_option, - connect_topology_option_modifier, - connect_timeout, connect_attempts, - NULL, NULL); -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Have %d expected connections\n", - expected_connections); -#endif - } - - GNUNET_SCHEDULER_cancel (die_task); - if (expected_connections == GNUNET_SYSERR) - { - die_task = - GNUNET_SCHEDULER_add_now (&end_badly, - "from connect topology (bad return)"); - } - - die_task = - GNUNET_SCHEDULER_add_delayed (TEST_TIMEOUT, &end_badly, - "from connect topology (timeout)"); -} - -static void -create_topology () -{ - peers_left = num_peers; /* Reset counter */ - if (GNUNET_TESTING_create_topology - (pg, topology, blacklist_topology, blacklist_transports) != GNUNET_SYSERR) - { -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Topology set up, now starting peers!\n"); -#endif - GNUNET_TESTING_daemons_continue_startup (pg); - } - else - { - GNUNET_SCHEDULER_cancel (die_task); - die_task = - GNUNET_SCHEDULER_add_now (&end_badly, - "from create topology (bad return)"); - } - GNUNET_SCHEDULER_cancel (die_task); - die_task = - GNUNET_SCHEDULER_add_delayed (TEST_TIMEOUT, &end_badly, - "from continue startup (timeout)"); -} - - -static void -peers_started_callback (void *cls, const struct GNUNET_PeerIdentity *id, - const struct GNUNET_CONFIGURATION_Handle *cfg, - struct GNUNET_TESTING_Daemon *d, const char *emsg) -{ - if (emsg != NULL) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Failed to start daemon with error: `%s'\n", emsg); - return; - } - GNUNET_assert (id != NULL); -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Started daemon %llu out of %llu\n", - (num_peers - peers_left) + 1, num_peers); -#endif - peers_left--; - if (peers_left == 0) - { -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "All %d daemons started, now creating topology!\n", num_peers); -#endif - GNUNET_SCHEDULER_cancel (die_task); - /* Set up task in case topology creation doesn't finish - * within a reasonable amount of time */ - die_task = - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply - (GNUNET_TIME_UNIT_MINUTES, 5), &end_badly, - "from peers_started_callback"); - connect_topology (); - ok = 0; - } -} - -/** - * Callback indicating that the hostkey was created for a peer. - * - * @param cls NULL - * @param id the peer identity - * @param d the daemon handle (pretty useless at this point, remove?) - * @param emsg non-null on failure - */ -void -hostkey_callback (void *cls, const struct GNUNET_PeerIdentity *id, - struct GNUNET_TESTING_Daemon *d, const char *emsg) -{ - if (emsg != NULL) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Hostkey callback received error: %s\n", emsg); - } - -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Hostkey created for peer `%s'\n", - GNUNET_i2s (id)); -#endif - peers_left--; - if (peers_left == 0) - { -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "All %d hostkeys created, now creating topology!\n", num_peers); -#endif - GNUNET_SCHEDULER_cancel (die_task); - /* Set up task in case topology creation doesn't finish - * within a reasonable amount of time */ - die_task = - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply - (GNUNET_TIME_UNIT_MINUTES, 5), &end_badly, - "from hostkey_callback"); - GNUNET_SCHEDULER_add_now (&create_topology, NULL); - ok = 0; - } -} - -static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) -{ - unsigned long long topology_num; - unsigned long long connect_topology_num; - unsigned long long blacklist_topology_num; - unsigned long long connect_topology_option_num; - char *connect_topology_option_modifier_string; - - ok = 1; - - dotOutFile = FOPEN (dotOutFileName, "w"); - if (dotOutFile != NULL) - { - FPRINTF (dotOutFile, "%s", "strict graph G {\n"); - } - -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Starting daemons based on config file %s\n", cfgfile); -#endif - - if (GNUNET_YES != - GNUNET_CONFIGURATION_get_value_string (cfg, "paths", "servicehome", - &test_directory)) - { - ok = 404; - if (dotOutFile != NULL) - { - FCLOSE (dotOutFile); - } - return; - } - - if (GNUNET_YES == - GNUNET_CONFIGURATION_get_value_number (cfg, "testing", "topology", - &topology_num)) - topology = topology_num; - - if (GNUNET_YES == - GNUNET_CONFIGURATION_get_value_number (cfg, "testing", "connect_topology", - &connect_topology_num)) - connection_topology = connect_topology_num; - - if (GNUNET_YES == - GNUNET_CONFIGURATION_get_value_number (cfg, "testing", - "connect_topology_option", - &connect_topology_option_num)) - connect_topology_option = connect_topology_option_num; - - if (GNUNET_YES == - GNUNET_CONFIGURATION_get_value_string (cfg, "testing", - "connect_topology_option_modifier", - &connect_topology_option_modifier_string)) - { - if (SSCANF - (connect_topology_option_modifier_string, "%lf", - &connect_topology_option_modifier) != 1) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - _ - ("Invalid value `%s' for option `%s' in section `%s': expected float\n"), - connect_topology_option_modifier_string, - "connect_topology_option_modifier", "TESTING"); - GNUNET_free (connect_topology_option_modifier_string); - ok = 707; - if (dotOutFile != NULL) - { - FCLOSE (dotOutFile); - } - return; - } - GNUNET_free (connect_topology_option_modifier_string); - } - - if (GNUNET_OK != - GNUNET_CONFIGURATION_get_value_string (cfg, "testing", - "blacklist_transports", - &blacklist_transports)) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "No transports specified for blacklisting in blacklist testcase (this shouldn't happen!)\n"); - ok = 808; - if (dotOutFile != NULL) - { - FCLOSE (dotOutFile); - } - return; - } - - if (GNUNET_YES == - GNUNET_CONFIGURATION_get_value_number (cfg, "testing", - "blacklist_topology", - &blacklist_topology_num)) - blacklist_topology = blacklist_topology_num; - - if (GNUNET_SYSERR == - GNUNET_CONFIGURATION_get_value_number (cfg, "testing", "num_peers", - &num_peers)) - num_peers = DEFAULT_NUM_PEERS; - - if (GNUNET_OK != - GNUNET_CONFIGURATION_get_value_time (cfg, "testing", "CONNECT_TIMEOUT", - &connect_timeout)) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Must provide option %s:%s!\n", - "testing", "CONNECT_TIMEOUT"); - return; - } - - - if (GNUNET_OK != - GNUNET_CONFIGURATION_get_value_number (cfg, "testing", "connect_attempts", - &connect_attempts)) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Must provide option %s:%s!\n", - "testing", "connect_attempts"); - return; - } - - main_cfg = cfg; - - GNUNET_assert (num_peers > 0 && num_peers < (unsigned int) -1); - peers_left = num_peers; - - /* For this specific test we only really want a CLIQUE topology as the - * overlay allowed topology, and a RING topology as the underlying connection - * allowed topology. So we will expect only num_peers * 2 connections to - * work, and (num_peers * (num_peers - 1)) - (num_peers * 2) to fail. - */ - expected_connections = num_peers * (num_peers - 1); - expected_failed_connections = expected_connections - (num_peers * 2); - - - /* Set up a task to end testing if peer start fails */ - die_task = - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply - (GNUNET_TIME_UNIT_MINUTES, 5), &end_badly, - "didn't start all daemons in reasonable amount of time!!!"); - - pg = GNUNET_TESTING_daemons_start (cfg, peers_left, peers_left, peers_left, - TIMEOUT, &hostkey_callback, NULL, - &peers_started_callback, NULL, - &topology_callback, NULL, NULL); - -} - -static int -check () -{ - int ret; - - char *const argv[] = { "test-testing-topology-blacklist", - "-c", - "test_testing_data_topology_blacklist.conf", -#if VERBOSE - "-L", "DEBUG", -#endif - NULL - }; - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - ret = - GNUNET_PROGRAM_run ((sizeof (argv) / sizeof (char *)) - 1, argv, - "test-testing-topology-blacklist", "nohelp", options, - &run, &ok); - if (ret != GNUNET_OK) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "`test-testing-topology-blacklist': Failed with error code %d\n", - ret); - } - - return ok; -} - -int -main (int argc, char *argv[]) -{ - int ret; - - GNUNET_log_setup ("test_testing_topology_blacklist", -#if VERBOSE - "DEBUG", -#else - "WARNING", -#endif - NULL); - ret = check (); - - /** - * Need to remove base directory, subdirectories taken care - * of by the testing framework. - */ - if (test_directory != NULL) - { - if (GNUNET_DISK_directory_remove (test_directory) != GNUNET_OK) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Failed to remove testing directory %s\n", test_directory); - } - } - - return ret; -} - -/* end of test_testing_topology_blacklist.c */ diff --git a/src/testing/test_testing_topology_churn.c b/src/testing/test_testing_topology_churn.c deleted file mode 100644 index 9c0bbf2..0000000 --- a/src/testing/test_testing_topology_churn.c +++ /dev/null @@ -1,322 +0,0 @@ -/* - This file is part of GNUnet. - (C) 2009 Christian Grothoff (and other contributing authors) - - GNUnet is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published - by the Free Software Foundation; either version 3, or (at your - option) any later version. - - GNUnet is distributed in the hope that it will be useful, but - WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - General Public License for more details. - - You should have received a copy of the GNU General Public License - along with GNUnet; see the file COPYING. If not, write to the - Free Software Foundation, Inc., 59 Temple Place - Suite 330, - Boston, MA 02111-1307, USA. -*/ -/** - * @file testing/test_testing_topology_churn.c - * @brief base testcase for testing simple churn functionality - */ -#include "platform.h" -#include "gnunet_testing_lib.h" -#include "gnunet_core_service.h" - - -/** - * How long until we fail the whole testcase? - */ -#define TEST_TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 600) - -/** - * How long until we give up on starting the peers? (Must be longer than the connect timeout!) - */ -#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 300) - -#define DEFAULT_NUM_PEERS 4 - -static int ok; - -static unsigned long long num_peers; - -static unsigned int expected_connections; - -static unsigned int expected_failed_connections; - -static unsigned long long peers_left; - -static struct GNUNET_TESTING_PeerGroup *pg; - -const struct GNUNET_CONFIGURATION_Handle *main_cfg; - -GNUNET_SCHEDULER_TaskIdentifier die_task; - -static char *test_directory; - -#define MTYPE 12345 - -GNUNET_NETWORK_STRUCT_BEGIN - -struct GNUNET_TestMessage -{ - /** - * Header of the message - */ - struct GNUNET_MessageHeader header; - - /** - * Unique identifier for this message. - */ - uint32_t uid; -}; -GNUNET_NETWORK_STRUCT_END - -/** - * Check whether peers successfully shut down. - */ -void -shutdown_callback (void *cls, const char *emsg) -{ - if (emsg != NULL) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Shutdown of peers failed!\n"); - if (ok == 0) - ok = 666; - } - else - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "All peers successfully shut down!\n"); - } -} - -static void -finish_testing () -{ - GNUNET_assert (pg != NULL); - - if (die_task != GNUNET_SCHEDULER_NO_TASK) - GNUNET_SCHEDULER_cancel (die_task); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Called finish testing, stopping daemons.\n"); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Calling daemons_stop\n"); - GNUNET_TESTING_daemons_stop (pg, TIMEOUT, &shutdown_callback, NULL); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "daemons_stop finished\n"); - ok = 0; -} - -static void -end_badly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - char *msg = cls; - - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "End badly was called (%s)... stopping daemons.\n", msg); - - if (pg != NULL) - { - GNUNET_TESTING_daemons_stop (pg, TIMEOUT, &shutdown_callback, NULL); - ok = 7331; /* Opposite of leet */ - } - else - ok = 401; /* Never got peers started */ - -} - -struct ChurnTestContext -{ - GNUNET_SCHEDULER_Task next_task; - -}; - -static struct ChurnTestContext churn_ctx; - -/** - * Churn callback, report on success or failure of churn operation. - * - * @param cls closure - * @param emsg NULL on success - */ -void -churn_callback (void *cls, const char *emsg) -{ - if (emsg == NULL) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Successfully churned peers!\n", - emsg); - GNUNET_SCHEDULER_add_now (churn_ctx.next_task, NULL); - } - else - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Failed to churn peers with error `%s'\n", emsg); - GNUNET_SCHEDULER_cancel (die_task); - die_task = GNUNET_SCHEDULER_add_now (&end_badly, NULL); - } -} - - -static void -churn_peers_both () -{ - churn_ctx.next_task = &finish_testing; - GNUNET_TESTING_daemons_churn (pg, NULL, 1, 1, TIMEOUT, &churn_callback, NULL); -} - -static void -churn_peers_off_again () -{ - churn_ctx.next_task = &churn_peers_both; - GNUNET_TESTING_daemons_churn (pg, NULL, 2, 0, TIMEOUT, &churn_callback, NULL); -} - -static void -churn_peers_on () -{ - churn_ctx.next_task = &churn_peers_off_again; - GNUNET_TESTING_daemons_churn (pg, NULL, 0, 2, TIMEOUT, &churn_callback, NULL); -} - -static void -churn_peers_off () -{ - churn_ctx.next_task = &churn_peers_on; - GNUNET_TESTING_daemons_churn (pg, NULL, 2, 0, TIMEOUT, &churn_callback, NULL); -} - -static void -peers_started_callback (void *cls, const struct GNUNET_PeerIdentity *id, - const struct GNUNET_CONFIGURATION_Handle *cfg, - struct GNUNET_TESTING_Daemon *d, const char *emsg) -{ - if (emsg != NULL) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Failed to start daemon with error: `%s'\n", emsg); - return; - } - GNUNET_assert (id != NULL); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Started daemon %llu out of %llu\n", - (num_peers - peers_left) + 1, num_peers); - peers_left--; - if (peers_left == 0) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "All %d daemons started, now testing churn!\n", num_peers); - GNUNET_SCHEDULER_cancel (die_task); - /* Set up task in case topology creation doesn't finish - * within a reasonable amount of time */ - die_task = - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply - (GNUNET_TIME_UNIT_MINUTES, 5), &end_badly, - "from peers_started_callback"); - churn_peers_off (); - ok = 0; - } -} - - -static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) -{ - ok = 1; - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Starting daemons based on config file %s\n", cfgfile); - if (GNUNET_YES != - GNUNET_CONFIGURATION_get_value_string (cfg, "paths", "servicehome", - &test_directory)) - { - ok = 404; - return; - } - - if (GNUNET_SYSERR == - GNUNET_CONFIGURATION_get_value_number (cfg, "testing", "num_peers", - &num_peers)) - num_peers = DEFAULT_NUM_PEERS; - - main_cfg = cfg; - - peers_left = num_peers; - GNUNET_assert (num_peers > 0 && num_peers < (unsigned int) -1); - - /* For this specific test we only really want a CLIQUE topology as the - * overlay allowed topology, and a RING topology as the underlying connection - * allowed topology. So we will expect only num_peers * 2 connections to - * work, and (num_peers * (num_peers - 1)) - (num_peers * 2) to fail. - */ - expected_connections = num_peers * (num_peers - 1); - expected_failed_connections = expected_connections - (num_peers * 2); - - - /* Set up a task to end testing if peer start fails */ - die_task = - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply - (GNUNET_TIME_UNIT_MINUTES, 5), &end_badly, - "didn't start all daemons in reasonable amount of time!!!"); - - pg = GNUNET_TESTING_daemons_start (cfg, peers_left, peers_left, peers_left, - TIMEOUT, NULL, NULL, - &peers_started_callback, NULL, NULL, NULL, - NULL); - -} - -static int -check () -{ - int ret; - - char *const argv[] = { "test-testing-topology-churn", - "-c", - "test_testing_data_topology_churn.conf", - NULL - }; - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - ret = - GNUNET_PROGRAM_run ((sizeof (argv) / sizeof (char *)) - 1, argv, - "test-testing-topology-churn", "nohelp", options, - &run, &ok); - if (ret != GNUNET_OK) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "`test-testing-topology-churn': Failed with error code %d\n", - ret); - } - - return ok; -} - -int -main (int argc, char *argv[]) -{ - int ret; - - GNUNET_log_setup ("test_testing_topology_churn", - "WARNING", - NULL); - ret = check (); - - /** - * Need to remove base directory, subdirectories taken care - * of by the testing framework. - */ - if (test_directory != NULL) - { - if (GNUNET_DISK_directory_remove (test_directory) != GNUNET_OK) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Failed to remove testing directory %s\n", test_directory); - } - } - - return ret; -} - -/* end of test_testing_topology_churn.c */ diff --git a/src/testing/testing.c b/src/testing/testing.c index 31bea06..dd80f6e 100644 --- a/src/testing/testing.c +++ b/src/testing/testing.c @@ -1,6 +1,6 @@ /* This file is part of GNUnet - (C) 2008, 2009 Christian Grothoff (and other contributing authors) + (C) 2008, 2009, 2012 Christian Grothoff (and other contributing authors) GNUnet is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published @@ -21,2183 +21,1286 @@ /** * @file testing/testing.c * @brief convenience API for writing testcases for GNUnet - * Many testcases need to start and stop gnunetd, + * Many testcases need to start and stop a peer/service * and this library is supposed to make that easier * for TESTCASES. Normal programs should always * use functions from gnunet_{util,arm}_lib.h. This API is - * ONLY for writing testcases! + * ONLY for writing testcases (or internal use of the testbed). * @author Christian Grothoff * */ #include "platform.h" -#include "gnunet_arm_service.h" -#include "gnunet_core_service.h" -#include "gnunet_constants.h" +#include "gnunet_util_lib.h" #include "gnunet_testing_lib.h" -#include "gnunet_transport_service.h" -#include "gnunet_hello_lib.h" -/** - * Hack to deal with initial HELLO's being often devoid of addresses. - * This hack causes 'process_hello' to ignore HELLOs without addresses. - * The correct implementation would continue with 'process_hello' until - * the connection could be established... - */ -#define EMPTY_HACK GNUNET_YES +#define LOG(kind,...) \ + GNUNET_log_from (kind, "testing-api", __VA_ARGS__) -/** - * How long do we wait after starting gnunet-service-arm - * for the core service to be alive? - */ -#define ARM_START_WAIT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 120) /** - * How many times are we willing to try to wait for "scp" or - * "gnunet-service-arm" to complete (waitpid) before giving up? + * We need pipe control only on WINDOWS */ -#define MAX_EXEC_WAIT_RUNS 250 - -static struct GNUNET_CORE_MessageHandler no_handlers[] = { {NULL, 0, 0} }; - -#if EMPTY_HACK -static int -test_address (void *cls, const struct GNUNET_HELLO_Address *address, - struct GNUNET_TIME_Absolute expiration) -{ - int *empty = cls; - - *empty = GNUNET_NO; - return GNUNET_OK; -} +#if WINDOWS +#define PIPE_CONTROL GNUNET_YES +#else +#define PIPE_CONTROL GNUNET_NO #endif + /** - * Receive the HELLO from one peer, give it to the other - * and ask them to connect. - * - * @param cls Closure (daemon whose hello is this). - * @param message HELLO message of peer + * Lowest port used for GNUnet testing. Should be high enough to not + * conflict with other applications running on the hosts but be low + * enough to not conflict with client-ports (typically starting around + * 32k). */ -static void -process_hello (void *cls, const struct GNUNET_MessageHeader *message) -{ - struct GNUNET_TESTING_Daemon *daemon = cls; - int msize; - -#if EMPTY_HACK - int empty; - - empty = GNUNET_YES; - GNUNET_assert (message != NULL); - GNUNET_HELLO_iterate_addresses ((const struct GNUNET_HELLO_Message *) message, - GNUNET_NO, &test_address, &empty); - if (GNUNET_YES == empty) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Skipping empty HELLO address of peer %s\n", - GNUNET_i2s (&daemon->id)); - return; - } -#endif - GNUNET_assert (daemon->phase == SP_GET_HELLO || - daemon->phase == SP_START_DONE); - daemon->cb = NULL; // FIXME: why??? (see fsm:SP_START_CORE, notify_daemon_started) - if (daemon->task != GNUNET_SCHEDULER_NO_TASK) /* Assertion here instead? */ - GNUNET_SCHEDULER_cancel (daemon->task); - - if (daemon->server != NULL) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Received `%s' from transport service of `%4s', disconnecting core!\n", - "HELLO", GNUNET_i2s (&daemon->id)); - GNUNET_CORE_disconnect (daemon->server); - daemon->server = NULL; - } - - msize = ntohs (message->size); - if (msize < 1) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "HELLO message of peer %s is of size 0\n", - GNUNET_i2s (&daemon->id)); - return; - } - if (daemon->ghh != NULL) - { - GNUNET_TRANSPORT_get_hello_cancel (daemon->ghh); - daemon->ghh = NULL; - } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Received `%s' from transport service of `%4s'\n", "HELLO", - GNUNET_i2s (&daemon->id)); - GNUNET_free_non_null (daemon->hello); - daemon->hello = GNUNET_malloc (msize); - memcpy (daemon->hello, message, msize); - - if (daemon->th != NULL) - { - GNUNET_TRANSPORT_disconnect (daemon->th); - daemon->th = NULL; - } - daemon->phase = SP_START_DONE; -} - +#define LOW_PORT 12000 /** - * Notify of a peer being up and running. Scheduled as a task - * so that variables which may need to be set are set before - * the connect callback can set up new operations. - * FIXME: what variables?????? where from???? - * - * @param cls the testing daemon - * @param tc task scheduler context + * Highest port used for GNUnet testing. Should be low enough to not + * conflict with the port range for "local" ports (client apps; see + * /proc/sys/net/ipv4/ip_local_port_range on Linux for example). */ -static void -notify_daemon_started (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - struct GNUNET_TESTING_Daemon *d = cls; - GNUNET_TESTING_NotifyDaemonRunning cb; - - cb = d->cb; - d->cb = NULL; - if (NULL != cb) - cb (d->cb_cls, &d->id, d->cfg, d, NULL); -} +#define HIGH_PORT 56000 /** - * Finite-state machine for starting GNUnet. - * - * @param cls our "struct GNUNET_TESTING_Daemon" - * @param tc unused + * Handle for a system on which GNUnet peers are executed; + * a system is used for reserving unique paths and ports. */ -static void -start_fsm (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +struct GNUNET_TESTING_System { - struct GNUNET_TESTING_Daemon *d = cls; - GNUNET_TESTING_NotifyDaemonRunning cb; - enum GNUNET_OS_ProcessStatusType type; - unsigned long code; - char *dst; - int bytes_read; - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Peer %s FSM is in phase %u.\n", - GNUNET_i2s (&d->id), d->phase); - d->task = GNUNET_SCHEDULER_NO_TASK; - switch (d->phase) - { - case SP_COPYING: - /* confirm copying complete */ - if (GNUNET_OK != GNUNET_OS_process_status (d->proc_arm_copying, &type, &code)) - { - if (GNUNET_TIME_absolute_get_remaining (d->max_timeout).rel_value == 0) - { - cb = d->cb; - d->cb = NULL; - if (NULL != cb) - cb (d->cb_cls, NULL, d->cfg, d, - _ - ("`scp' does not seem to terminate (timeout copying config).\n")); - return; - } - /* wait some more */ - d->task = - GNUNET_SCHEDULER_add_delayed (GNUNET_CONSTANTS_EXEC_WAIT, &start_fsm, - d); - return; - } - if ((type != GNUNET_OS_PROCESS_EXITED) || (code != 0)) - { - cb = d->cb; - d->cb = NULL; - if (NULL != cb) - cb (d->cb_cls, NULL, d->cfg, d, _("`scp' did not complete cleanly.\n")); - return; - } - GNUNET_OS_process_destroy (d->proc_arm_copying); - d->proc_arm_copying = NULL; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Successfully copied configuration file.\n"); - d->phase = SP_COPIED; - /* fall-through */ - case SP_COPIED: - /* Start create hostkey process if we don't already know the peer identity! */ - if (GNUNET_NO == d->have_hostkey) - { - GNUNET_assert (NULL == d->proc_arm_peerinfo); - d->pipe_stdout = GNUNET_DISK_pipe (GNUNET_NO, GNUNET_NO, GNUNET_NO, GNUNET_YES); - if (d->pipe_stdout == NULL) - { - cb = d->cb; - d->cb = NULL; - if (NULL != cb) - cb (d->cb_cls, NULL, d->cfg, d, - (NULL == - d->hostname) ? - _("Failed to create pipe for `gnunet-peerinfo' process.\n") : - _("Failed to create pipe for `ssh' process.\n")); - return; - } - if (NULL == d->hostname) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Starting `%s', with command `%s %s %s %s'.\n", - "gnunet-peerinfo", "gnunet-peerinfo", "-c", d->cfgfile, - "-sq"); - d->proc_arm_peerinfo = - GNUNET_OS_start_process (GNUNET_YES, NULL, d->pipe_stdout, "gnunet-peerinfo", - "gnunet-peerinfo", "-c", d->cfgfile, "-sq", - NULL); - GNUNET_DISK_pipe_close_end (d->pipe_stdout, GNUNET_DISK_PIPE_END_WRITE); - } - else - { - if (d->username != NULL) - GNUNET_asprintf (&dst, "%s@%s", d->username, d->hostname); - else - dst = GNUNET_strdup (d->hostname); - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Starting `%s', with command `%s %s %s %s %s %s'.\n", - "gnunet-peerinfo", "ssh", dst, "gnunet-peerinfo", "-c", - d->cfgfile, "-sq"); - if (d->ssh_port_str == NULL) - { - d->proc_arm_peerinfo = GNUNET_OS_start_process (GNUNET_NO, NULL, d->pipe_stdout, "ssh", "ssh", - "-q", - dst, "gnunet-peerinfo", "-c", - d->cfgfile, "-sq", NULL); - } - else - { - d->proc_arm_peerinfo = - GNUNET_OS_start_process (GNUNET_NO, NULL, d->pipe_stdout, "ssh", "ssh", "-p", - d->ssh_port_str, - "-q", - dst, "gnunet-peerinfo", "-c", d->cfgfile, - "-sq", NULL); - } - GNUNET_DISK_pipe_close_end (d->pipe_stdout, GNUNET_DISK_PIPE_END_WRITE); - GNUNET_free (dst); - } - if (NULL == d->proc_arm_peerinfo) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - _("Could not start `%s' process to create hostkey.\n"), - (NULL == d->hostname) ? "gnunet-peerinfo" : "ssh"); - cb = d->cb; - d->cb = NULL; - if (NULL != cb) - cb (d->cb_cls, NULL, d->cfg, d, - (NULL == - d->hostname) ? _("Failed to start `gnunet-peerinfo' process.\n") - : _("Failed to start `ssh' process.\n")); - GNUNET_DISK_pipe_close (d->pipe_stdout); - return; - } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Started `%s', waiting for hostkey.\n", "gnunet-peerinfo"); - d->phase = SP_HOSTKEY_CREATE; - d->task = - GNUNET_SCHEDULER_add_read_file (GNUNET_TIME_absolute_get_remaining - (d->max_timeout), - GNUNET_DISK_pipe_handle - (d->pipe_stdout, - GNUNET_DISK_PIPE_END_READ), - &start_fsm, d); - } - else /* Already have a hostkey! */ - { - if (d->hostkey_callback != NULL) - { - d->hostkey_callback (d->hostkey_cls, &d->id, d, NULL); - d->hostkey_callback = NULL; - d->phase = SP_HOSTKEY_CREATED; - } - else - d->phase = SP_TOPOLOGY_SETUP; + /** + * Prefix (i.e. "/tmp/gnunet-testing/") we prepend to each + * SERVICEHOME. */ + char *tmppath; - /* wait some more */ - d->task = GNUNET_SCHEDULER_add_now (&start_fsm, d); - } - break; - case SP_HOSTKEY_CREATE: - bytes_read = - GNUNET_DISK_file_read (GNUNET_DISK_pipe_handle - (d->pipe_stdout, GNUNET_DISK_PIPE_END_READ), - &d->hostkeybuf[d->hostkeybufpos], - sizeof (d->hostkeybuf) - d->hostkeybufpos); - if (bytes_read > 0) - d->hostkeybufpos += bytes_read; - - if ((d->hostkeybufpos < 104) && (bytes_read > 0)) - { - /* keep reading */ - d->task = - GNUNET_SCHEDULER_add_read_file (GNUNET_TIME_absolute_get_remaining - (d->max_timeout), - GNUNET_DISK_pipe_handle - (d->pipe_stdout, - GNUNET_DISK_PIPE_END_READ), - &start_fsm, d); - return; - } - d->hostkeybuf[103] = '\0'; + /** + * The trusted ip. Can either be a single ip address or a network address in + * CIDR notation. + */ + char *trusted_ip; - if ((bytes_read < 0) || - (GNUNET_OK != - GNUNET_CRYPTO_hash_from_string (d->hostkeybuf, &d->id.hashPubKey))) - { - /* error */ - if (bytes_read < 0) - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - _("Error reading from gnunet-peerinfo: %s\n"), - STRERROR (errno)); - else - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - _("Malformed output from gnunet-peerinfo!\n")); - cb = d->cb; - d->cb = NULL; - GNUNET_DISK_pipe_close (d->pipe_stdout); - d->pipe_stdout = NULL; - (void) GNUNET_OS_process_kill (d->proc_arm_peerinfo, SIGKILL); - GNUNET_break (GNUNET_OK == GNUNET_OS_process_wait (d->proc_arm_peerinfo)); - GNUNET_OS_process_destroy (d->proc_arm_peerinfo); - d->proc_arm_peerinfo = NULL; - if (NULL != cb) - cb (d->cb_cls, NULL, d->cfg, d, _("Failed to get hostkey!\n")); - return; - } - d->shortname = GNUNET_strdup (GNUNET_i2s (&d->id)); - GNUNET_DISK_pipe_close (d->pipe_stdout); - d->pipe_stdout = NULL; - (void) GNUNET_OS_process_kill (d->proc_arm_peerinfo, SIGKILL); - GNUNET_break (GNUNET_OK == GNUNET_OS_process_wait (d->proc_arm_peerinfo)); - GNUNET_OS_process_destroy (d->proc_arm_peerinfo); - d->proc_arm_peerinfo = NULL; - d->have_hostkey = GNUNET_YES; - if (d->hostkey_callback != NULL) - { - d->hostkey_callback (d->hostkey_cls, &d->id, d, NULL); - d->hostkey_callback = NULL; - d->phase = SP_HOSTKEY_CREATED; - } - else - { - d->phase = SP_TOPOLOGY_SETUP; - } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Successfully got hostkey!\n"); - /* Fall through */ - case SP_HOSTKEY_CREATED: - /* wait for topology finished */ - if ((GNUNET_YES == d->dead) || - (GNUNET_TIME_absolute_get_remaining (d->max_timeout).rel_value == 0)) - { - cb = d->cb; - d->cb = NULL; - if (NULL != cb) - cb (d->cb_cls, NULL, d->cfg, d, - _("`Failed while waiting for topology setup!\n")); - return; - } + /** + * our hostname + */ + char *hostname; - d->task = - GNUNET_SCHEDULER_add_delayed (GNUNET_CONSTANTS_EXEC_WAIT, &start_fsm, - d); - break; - case SP_TOPOLOGY_SETUP: /* Indicates topology setup has completed! */ - /* start GNUnet on remote host */ - if (NULL == d->hostname) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Starting `%s', with command `%s %s %s %s'.\n", - "gnunet-arm", "gnunet-arm", "-c", d->cfgfile, - "-s"); - d->proc_arm_start = - GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-arm", "gnunet-arm", "-c", - d->cfgfile, - "-s", "-q", "-T", - GNUNET_TIME_relative_to_string - (GNUNET_TIME_absolute_get_remaining - (d->max_timeout)), NULL); - } - else - { - if (d->username != NULL) - GNUNET_asprintf (&dst, "%s@%s", d->username, d->hostname); - else - dst = GNUNET_strdup (d->hostname); - - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Starting `%s', with command `%s %s %s %s %s %s %s'.\n", - "gnunet-arm", "ssh", dst, "gnunet-arm", "-c", d->cfgfile, - "-s", "-q"); - if (d->ssh_port_str == NULL) - { - d->proc_arm_start = GNUNET_OS_start_process (GNUNET_NO, NULL, NULL, "ssh", "ssh", - "-q", - dst, "gnunet-arm", - "-c", d->cfgfile, "-s", "-q", "-T", - GNUNET_TIME_relative_to_string - (GNUNET_TIME_absolute_get_remaining - (d->max_timeout)), NULL); - } - else - { + /** + * Hostkeys data, contains "GNUNET_TESTING_HOSTKEYFILESIZE * total_hostkeys" bytes. + */ + char *hostkeys_data; - d->proc_arm_start = - GNUNET_OS_start_process (GNUNET_NO, NULL, NULL, "ssh", "ssh", "-p", - d->ssh_port_str, - "-q", - dst, "gnunet-arm", - "-c", d->cfgfile, "-s", "-q", "-T", - GNUNET_TIME_relative_to_string - (GNUNET_TIME_absolute_get_remaining - (d->max_timeout)), NULL); - } - GNUNET_free (dst); - } - if (NULL == d->proc_arm_start) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - _("Could not start `%s' process to start GNUnet.\n"), - (NULL == d->hostname) ? "gnunet-arm" : "ssh"); - cb = d->cb; - d->cb = NULL; - if (NULL != cb) - cb (d->cb_cls, NULL, d->cfg, d, - (NULL == - d->hostname) ? _("Failed to start `gnunet-arm' process.\n") : - _("Failed to start `ssh' process.\n")); - return; - } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Started `%s', waiting for `%s' to be up.\n", "gnunet-arm", - "gnunet-service-core"); - d->phase = SP_START_ARMING; - d->task = - GNUNET_SCHEDULER_add_delayed (GNUNET_CONSTANTS_EXEC_WAIT, &start_fsm, - d); - // FIXME: busy wait? - break; - case SP_START_ARMING: - if (GNUNET_OK != GNUNET_OS_process_status (d->proc_arm_start, &type, &code)) - { - if (GNUNET_TIME_absolute_get_remaining (d->max_timeout).rel_value == 0) - { - cb = d->cb; - d->cb = NULL; - if (NULL != cb) - cb (d->cb_cls, NULL, d->cfg, d, - (NULL == - d->hostname) ? _("`gnunet-arm' does not seem to terminate.\n") : - _("`ssh' does not seem to terminate.\n")); - if (d->cfg != NULL) - { - GNUNET_CONFIGURATION_destroy (d->cfg); - d->cfg = NULL; - } - if (d->cfgfile != NULL) - { - GNUNET_free (d->cfgfile); - d->cfgfile = NULL; - } - GNUNET_free_non_null (d->hostname); - GNUNET_free_non_null (d->username); - GNUNET_OS_process_destroy (d->proc_arm_start); - d->proc_arm_start = NULL; - d->username = NULL; - d->hostname = NULL; // Quick hack to avoid crashing (testing need to be - d->cfg = NULL; // overhauled anyway, and the error managing is - // GNUNET_free (d); // FIXME (could this leak) - // pretty broken anyway. - return; - } - /* wait some more */ - d->task = - GNUNET_SCHEDULER_add_delayed (GNUNET_CONSTANTS_EXEC_WAIT, &start_fsm, - d); - // FIXME: busy wait? - return; - } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Successfully started `%s'.\n", - "gnunet-arm"); - GNUNET_OS_process_destroy (d->proc_arm_start); - d->proc_arm_start = NULL; - d->phase = SP_START_CORE; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Calling CORE_connect\n"); - /* Fall through */ - case SP_START_CORE: - if (d->server != NULL) - GNUNET_CORE_disconnect (d->server); - - d->th = GNUNET_TRANSPORT_connect (d->cfg, &d->id, d, NULL, NULL, NULL); - if (d->th == NULL) - { - if (GNUNET_YES == d->dead) - GNUNET_TESTING_daemon_stop (d, - GNUNET_TIME_absolute_get_remaining - (d->max_timeout), d->dead_cb, - d->dead_cb_cls, GNUNET_YES, GNUNET_NO); - else if (NULL != d->cb) - d->cb (d->cb_cls, &d->id, d->cfg, d, - _("Failed to connect to transport service!\n")); - return; - } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Connected to transport service `%s', getting HELLO\n", - GNUNET_i2s (&d->id)); - d->ghh = GNUNET_TRANSPORT_get_hello (d->th, &process_hello, d); - /* FIXME: store task ID somewhere! */ - GNUNET_SCHEDULER_add_now (¬ify_daemon_started, d); - /*cb = d->cb; - * d->cb = NULL; - * if (NULL != cb) - * cb (d->cb_cls, &d->id, d->cfg, d, NULL); */ - d->running = GNUNET_YES; - d->phase = SP_GET_HELLO; - break; - case SP_GET_HELLO: - if (GNUNET_TIME_absolute_get_remaining (d->max_timeout).rel_value == 0) - { - if (d->server != NULL) - GNUNET_CORE_disconnect (d->server); - if (d->th != NULL) - GNUNET_TRANSPORT_disconnect (d->th); - cb = d->cb; - d->cb = NULL; - if (NULL != cb) - cb (d->cb_cls, NULL, d->cfg, d, _("Unable to get HELLO for peer!\n")); - GNUNET_CONFIGURATION_destroy (d->cfg); - GNUNET_free (d->cfgfile); - GNUNET_free_non_null (d->hostname); - GNUNET_free_non_null (d->username); - GNUNET_free (d); - return; - } - if (d->hello != NULL) - return; - GNUNET_assert (d->task == GNUNET_SCHEDULER_NO_TASK); - d->task = - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply - (GNUNET_CONSTANTS_SERVICE_RETRY, 2), - &start_fsm, d); - break; - case SP_START_DONE: - GNUNET_break (0); - break; - case SP_SERVICE_START: - /* confirm gnunet-arm exited */ - if (GNUNET_OK != GNUNET_OS_process_status (d->proc_arm_srv_start, &type, &code)) - { - if (GNUNET_TIME_absolute_get_remaining (d->max_timeout).rel_value == 0) - { - cb = d->cb; - d->cb = NULL; - if (NULL != cb) - cb (d->cb_cls, NULL, d->cfg, d, - (NULL == - d->hostname) ? _("`gnunet-arm' does not seem to terminate.\n") : - _("`ssh' does not seem to terminate.\n")); - return; - } - /* wait some more */ - d->task = - GNUNET_SCHEDULER_add_delayed (GNUNET_CONSTANTS_EXEC_WAIT, &start_fsm, - d); - return; - } -#if EXTRA_CHECKS - if ((type != GNUNET_OS_PROCESS_EXITED) || (code != 0)) - { - cb = d->cb; - d->cb = NULL; - if (NULL != cb) - cb (d->cb_cls, NULL, d->cfg, d, - (NULL == - d->hostname) ? - _ - ("`gnunet-arm' terminated with non-zero exit status (or timed out)!\n") - : _("`ssh' does not seem to terminate.\n")); - return; - } -#endif - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Service startup complete!\n"); - cb = d->cb; - d->cb = NULL; - d->phase = SP_START_DONE; - if (NULL != cb) - cb (d->cb_cls, &d->id, d->cfg, d, NULL); - GNUNET_OS_process_destroy (d->proc_arm_srv_start); - d->proc_arm_srv_start = NULL; - break; - case SP_SERVICE_SHUTDOWN_START: - /* confirm copying complete */ - if (GNUNET_OK != GNUNET_OS_process_status (d->proc_arm_srv_stop, &type, &code)) - { - if (GNUNET_TIME_absolute_get_remaining (d->max_timeout).rel_value == 0) - { - if (NULL != d->dead_cb) - d->dead_cb (d->dead_cb_cls, - _ - ("either `gnunet-arm' or `ssh' does not seem to terminate.\n")); - return; - } - /* wait some more */ - d->task = - GNUNET_SCHEDULER_add_delayed (GNUNET_CONSTANTS_EXEC_WAIT, &start_fsm, - d); - return; - } -#if EXTRA_CHECKS - if ((type != GNUNET_OS_PROCESS_EXITED) || (code != 0)) - { - if (NULL != d->dead_cb) - d->dead_cb (d->dead_cb_cls, - _ - ("shutdown (either `gnunet-arm' or `ssh') did not complete cleanly.\n")); - return; - } -#endif - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Service shutdown complete.\n"); - if (NULL != d->dead_cb) - d->dead_cb (d->dead_cb_cls, NULL); - break; - case SP_SHUTDOWN_START: - /* confirm copying complete !??? */ - if (GNUNET_OK != GNUNET_OS_process_status (d->proc_arm_stop, &type, &code)) - { - if (GNUNET_TIME_absolute_get_remaining (d->max_timeout).rel_value == 0) - { - if (NULL != d->dead_cb) - d->dead_cb (d->dead_cb_cls, - _ - ("either `gnunet-arm' or `ssh' does not seem to terminate.\n")); - if (d->th != NULL) - { - GNUNET_TRANSPORT_get_hello_cancel (d->ghh); - d->ghh = NULL; - GNUNET_TRANSPORT_disconnect (d->th); - d->th = NULL; - } - if (d->cfg != NULL) - { - GNUNET_CONFIGURATION_destroy (d->cfg); - d->cfg = NULL; - } - if (d->cfgfile != NULL) - { - GNUNET_free (d->cfgfile); - d->cfgfile = NULL; - } - GNUNET_free_non_null (d->hello); - GNUNET_free_non_null (d->hostname); - GNUNET_free_non_null (d->username); - GNUNET_free_non_null (d->shortname); - GNUNET_OS_process_destroy (d->proc_arm_stop); - d->proc_arm_stop = NULL; - GNUNET_free (d); - return; - } - /* wait some more */ - d->task = - GNUNET_SCHEDULER_add_delayed (GNUNET_CONSTANTS_EXEC_WAIT, &start_fsm, - d); - return; - } - if ((type != GNUNET_OS_PROCESS_EXITED) || (code != 0)) - { - if (NULL != d->dead_cb) - d->dead_cb (d->dead_cb_cls, - _ - ("shutdown (either `gnunet-arm' or `ssh') did not complete cleanly.\n")); - if (d->th != NULL) - { - GNUNET_TRANSPORT_get_hello_cancel (d->ghh); - d->ghh = NULL; - GNUNET_TRANSPORT_disconnect (d->th); - d->th = NULL; - } - if (d->server != NULL) - { - GNUNET_CORE_disconnect (d->server); - d->server = NULL; - } - GNUNET_CONFIGURATION_destroy (d->cfg); - d->cfg = NULL; - GNUNET_free (d->cfgfile); - GNUNET_free_non_null (d->hello); - GNUNET_free_non_null (d->hostname); - GNUNET_free_non_null (d->username); - GNUNET_free_non_null (d->shortname); - GNUNET_OS_process_destroy (d->proc_arm_stop); - d->proc_arm_stop = NULL; - GNUNET_free (d); - return; - } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Peer shutdown complete.\n"); - if (d->server != NULL) - { - GNUNET_CORE_disconnect (d->server); - d->server = NULL; - } + /** + * memory map for 'hostkeys_data'. + */ + struct GNUNET_DISK_MapHandle *map; - if (d->th != NULL) - { - GNUNET_TRANSPORT_get_hello_cancel (d->ghh); - d->ghh = NULL; - GNUNET_TRANSPORT_disconnect (d->th); - d->th = NULL; - } + /** + * File descriptor for the map. + */ + struct GNUNET_DISK_FileHandle *map_fd; - if (NULL != d->dead_cb) - d->dead_cb (d->dead_cb_cls, NULL); + /** + * Bitmap where each TCP port that has already been reserved for + * some GNUnet peer is recorded. Note that we additionally need to + * test if a port is already in use by non-GNUnet components before + * assigning it to a peer/service. If we detect that a port is + * already in use, we also mark it in this bitmap. So all the bits + * that are zero merely indicate ports that MIGHT be available for + * peers. + */ + uint32_t reserved_tcp_ports[65536 / 32]; - /* state clean up and notifications */ - if (d->churn == GNUNET_NO) - { - GNUNET_CONFIGURATION_destroy (d->cfg); - d->cfg = NULL; - GNUNET_free (d->cfgfile); - GNUNET_free_non_null (d->hostname); - GNUNET_free_non_null (d->username); - } + /** + * Bitmap where each UDP port that has already been reserved for + * some GNUnet peer is recorded. Note that we additionally need to + * test if a port is already in use by non-GNUnet components before + * assigning it to a peer/service. If we detect that a port is + * already in use, we also mark it in this bitmap. So all the bits + * that are zero merely indicate ports that MIGHT be available for + * peers. + */ + uint32_t reserved_udp_ports[65536 / 32]; - GNUNET_free_non_null (d->hello); - d->hello = NULL; - GNUNET_free_non_null (d->shortname); - GNUNET_OS_process_destroy (d->proc_arm_stop); - d->proc_arm_stop = NULL; - d->shortname = NULL; - if (d->churn == GNUNET_NO) - GNUNET_free (d); - - break; - case SP_CONFIG_UPDATE: - /* confirm copying complete */ - if (GNUNET_OK != GNUNET_OS_process_status (d->proc_arm_copying, &type, &code)) - { - if (GNUNET_TIME_absolute_get_remaining (d->max_timeout).rel_value == 0) /* FIXME: config update should take timeout parameter! */ - { - cb = d->cb; - d->cb = NULL; - if (NULL != cb) - cb (d->cb_cls, NULL, d->cfg, d, - _("`scp' does not seem to terminate.\n")); - return; - } - /* wait some more */ - d->task = - GNUNET_SCHEDULER_add_delayed (GNUNET_CONSTANTS_EXEC_WAIT, &start_fsm, - d); - return; - } - if ((type != GNUNET_OS_PROCESS_EXITED) || (code != 0)) - { - if (NULL != d->update_cb) - d->update_cb (d->update_cb_cls, _("`scp' did not complete cleanly.\n")); - return; - } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Successfully copied configuration file.\n"); - if (NULL != d->update_cb) - d->update_cb (d->update_cb_cls, NULL); - d->phase = SP_START_DONE; - break; - } -} + /** + * Counter we use to make service home paths unique on this system; + * the full path consists of the tmppath and this number. Each + * UNIXPATH for a peer is also modified to include the respective + * path counter to ensure uniqueness. This field is incremented + * by one for each configured peer. Even if peers are destroyed, + * we never re-use path counters. + */ + uint32_t path_counter; -/** - * Continues GNUnet daemon startup when user wanted to be notified - * once a hostkey was generated (for creating friends files, blacklists, - * etc.). - * - * @param daemon the daemon to finish starting - */ -void -GNUNET_TESTING_daemon_continue_startup (struct GNUNET_TESTING_Daemon *daemon) -{ - GNUNET_assert (daemon->phase == SP_HOSTKEY_CREATED); - daemon->phase = SP_TOPOLOGY_SETUP; -} + /** + * The number of hostkeys + */ + uint32_t total_hostkeys; -/** - * Check whether the given daemon is running. - * - * @param daemon the daemon to check - * - * @return GNUNET_YES if the daemon is up, GNUNET_NO if the - * daemon is down, GNUNET_SYSERR on error. - */ -int -GNUNET_TESTING_test_daemon_running (struct GNUNET_TESTING_Daemon *daemon) -{ - if (daemon == NULL) - return GNUNET_SYSERR; + /** + * Lowest port we are allowed to use. + */ + uint16_t lowport; - if (daemon->running == GNUNET_YES) - return GNUNET_YES; - return GNUNET_NO; -} + /** + * Highest port we are allowed to use. + */ + uint16_t highport; +}; /** - * Starts a GNUnet daemon service which has been previously stopped. - * - * @param d the daemon for which the service should be started - * @param service the name of the service to start - * @param timeout how long to wait for process for shutdown to complete - * @param cb function called once the service starts - * @param cb_cls closure for cb + * Handle for a GNUnet peer controlled by testing. */ -void -GNUNET_TESTING_daemon_start_stopped_service (struct GNUNET_TESTING_Daemon *d, - char *service, - struct GNUNET_TIME_Relative - timeout, - GNUNET_TESTING_NotifyDaemonRunning - cb, void *cb_cls) +struct GNUNET_TESTING_Peer { - char *arg; - - d->cb = cb; - d->cb_cls = cb_cls; + /** + * The TESTING system associated with this peer + */ + struct GNUNET_TESTING_System *system; - GNUNET_assert (d->running == GNUNET_YES); + /** + * Path to the configuration file for this peer. + */ + char *cfgfile; - if (d->phase == SP_CONFIG_UPDATE) - { - GNUNET_SCHEDULER_cancel (d->task); - d->phase = SP_START_DONE; - } + /** + * Binary to be executed during 'GNUNET_TESTING_peer_start'. + * Typically 'gnunet-service-arm' (but can be set to a + * specific service by 'GNUNET_TESTING_service_run' if + * necessary). + */ + char *main_binary; + char *args; + + /** + * Handle to the running binary of the service, NULL if the + * peer/service is currently not running. + */ + struct GNUNET_OS_Process *main_process; - if (d->churned_services == NULL) - { - d->cb (d->cb_cls, &d->id, d->cfg, d, - "No service has been churned off yet!!"); - return; - } - d->phase = SP_SERVICE_START; - GNUNET_free (d->churned_services); - d->churned_services = NULL; - d->max_timeout = GNUNET_TIME_relative_to_absolute (timeout); - /* Check if this is a local or remote process */ - if (NULL != d->hostname) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Starting gnunet-arm with config `%s' on host `%s'.\n", - d->cfgfile, d->hostname); - if (d->username != NULL) - GNUNET_asprintf (&arg, "%s@%s", d->username, d->hostname); - else - arg = GNUNET_strdup (d->hostname); - - d->proc_arm_srv_start = GNUNET_OS_start_process (GNUNET_NO, NULL, NULL, "ssh", "ssh", - "-q", - arg, "gnunet-arm", - "-c", d->cfgfile, "-i", service, "-q", - "-T", - GNUNET_TIME_relative_to_string (timeout), - NULL); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Starting gnunet-arm with command ssh %s gnunet-arm -c %s -i %s -q\n", - arg, "gnunet-arm", d->cfgfile, service); - GNUNET_free (arg); - } - else - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Starting gnunet-arm with config `%s' locally.\n", d->cfgfile); - d->proc_arm_srv_start = GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-arm", "gnunet-arm", - "-c", d->cfgfile, "-i", service, "-q", - "-T", - GNUNET_TIME_relative_to_string (timeout), - NULL); - } + /** + * The keynumber of this peer's hostkey + */ + uint32_t key_number; +}; - d->max_timeout = GNUNET_TIME_relative_to_absolute (timeout); - d->task = GNUNET_SCHEDULER_add_now (&start_fsm, d); -} /** - * Starts a GNUnet daemon's service. + * Testing includes a number of pre-created hostkeys for faster peer + * startup. This function loads such keys into memory from a file. * - * @param d the daemon for which the service should be started - * @param service the name of the service to start - * @param timeout how long to wait for process for startup - * @param cb function called once gnunet-arm returns - * @param cb_cls closure for cb + * @param system the testing system handle + * @return GNUNET_OK on success; GNUNET_SYSERR on error */ -void -GNUNET_TESTING_daemon_start_service (struct GNUNET_TESTING_Daemon *d, - const char *service, - struct GNUNET_TIME_Relative timeout, - GNUNET_TESTING_NotifyDaemonRunning cb, - void *cb_cls) +static int +hostkeys_load (struct GNUNET_TESTING_System *system) { - char *arg; - - d->cb = cb; - d->cb_cls = cb_cls; - - GNUNET_assert (service != NULL); - GNUNET_assert (d->running == GNUNET_YES); - GNUNET_assert (d->phase == SP_START_DONE); - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - _("Starting service %s for peer `%4s'\n"), service, - GNUNET_i2s (&d->id)); - d->phase = SP_SERVICE_START; - d->max_timeout = GNUNET_TIME_relative_to_absolute (timeout); - /* Check if this is a local or remote process */ - if (NULL != d->hostname) + uint64_t fs; + char *data_dir; + char *filename; + + GNUNET_assert (NULL == system->hostkeys_data); + data_dir = GNUNET_OS_installation_get_path (GNUNET_OS_IPK_DATADIR); + GNUNET_asprintf (&filename, "%s/testing_hostkeys.dat", data_dir); + GNUNET_free (data_dir); + + if (GNUNET_YES != GNUNET_DISK_file_test (filename)) + { + LOG (GNUNET_ERROR_TYPE_ERROR, + _("Hostkeys file not found: %s\n"), filename); + GNUNET_free (filename); + return GNUNET_SYSERR; + } + /* Check hostkey file size, read entire thing into memory */ + if (GNUNET_OK != + GNUNET_DISK_file_size (filename, &fs, GNUNET_YES, GNUNET_YES)) + fs = 0; + if (0 == fs) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Starting gnunet-arm with config `%s' on host `%s'.\n", - d->cfgfile, d->hostname); - if (d->username != NULL) - GNUNET_asprintf (&arg, "%s@%s", d->username, d->hostname); - else - arg = GNUNET_strdup (d->hostname); - - d->proc_arm_srv_start = GNUNET_OS_start_process (GNUNET_NO, NULL, NULL, "ssh", "ssh", - "-q", - arg, "gnunet-arm", - "-c", d->cfgfile, "-i", service, "-q", - "-T", - GNUNET_TIME_relative_to_string (timeout), - NULL); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Starting gnunet-arm with command ssh %s gnunet-arm -c %s -i %s -q -T %s\n", - arg, "gnunet-arm", d->cfgfile, service, - GNUNET_TIME_relative_to_string (timeout)); - GNUNET_free (arg); + GNUNET_free (filename); + return GNUNET_SYSERR; /* File is empty */ } - else + if (0 != (fs % GNUNET_TESTING_HOSTKEYFILESIZE)) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Starting gnunet-arm with config `%s' locally.\n", d->cfgfile); - d->proc_arm_srv_start = GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-arm", "gnunet-arm", - "-c", d->cfgfile, "-i", service, "-q", - "-T", - GNUNET_TIME_relative_to_string (timeout), - NULL); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Starting gnunet-arm with command %s -c %s -i %s -q -T %s\n", - "gnunet-arm", d->cfgfile, service, - GNUNET_TIME_relative_to_string (timeout)); + LOG (GNUNET_ERROR_TYPE_ERROR, + _("Incorrect hostkey file format: %s\n"), filename); + GNUNET_free (filename); + return GNUNET_SYSERR; } - - d->max_timeout = GNUNET_TIME_relative_to_absolute (timeout); - d->task = GNUNET_SCHEDULER_add_now (&start_fsm, d); -} - -/** - * Start a peer that has previously been stopped using the daemon_stop - * call (and files weren't deleted and the allow restart flag) - * - * @param daemon the daemon to start (has been previously stopped) - * @param timeout how long to wait for restart - * @param cb the callback for notification when the peer is running - * @param cb_cls closure for the callback - */ -void -GNUNET_TESTING_daemon_start_stopped (struct GNUNET_TESTING_Daemon *daemon, - struct GNUNET_TIME_Relative timeout, - GNUNET_TESTING_NotifyDaemonRunning cb, - void *cb_cls) -{ - if (daemon->running == GNUNET_YES) + system->map_fd = GNUNET_DISK_file_open (filename, GNUNET_DISK_OPEN_READ, + GNUNET_DISK_PERM_NONE); + if (NULL == system->map_fd) { - cb (cb_cls, &daemon->id, daemon->cfg, daemon, - "Daemon already running, can't restart!"); - return; + GNUNET_log_strerror_file (GNUNET_ERROR_TYPE_ERROR, "open", filename); + GNUNET_free (filename); + return GNUNET_SYSERR; } - - daemon->cb = cb; - daemon->cb_cls = cb_cls; - daemon->phase = SP_TOPOLOGY_SETUP; - daemon->max_timeout = GNUNET_TIME_relative_to_absolute (timeout); - /* FIXME: why add_continuation? */ - GNUNET_SCHEDULER_add_continuation (&start_fsm, daemon, - GNUNET_SCHEDULER_REASON_PREREQ_DONE); + system->total_hostkeys = fs / GNUNET_TESTING_HOSTKEYFILESIZE; + system->hostkeys_data = GNUNET_DISK_file_map (system->map_fd, + &system->map, + GNUNET_DISK_MAP_TYPE_READ, + fs); + GNUNET_free (filename); + return GNUNET_OK; } + /** - * Starts a GNUnet daemon. GNUnet must be installed on the target - * system and available in the PATH. The machine must furthermore be - * reachable via "ssh" (unless the hostname is "NULL") without the - * need to enter a password. + * Function to remove the loaded hostkeys * - * @param cfg configuration to use - * @param timeout how long to wait starting up peers - * @param pretend GNUNET_YES to set up files but not start peer GNUNET_NO - * to really start the peer (default) - * @param hostname name of the machine where to run GNUnet - * (use NULL for localhost). - * @param ssh_username ssh username to use when connecting to hostname - * @param sshport port to pass to ssh process when connecting to hostname - * @param hostkey pointer to a hostkey to be written to disk (instead of being generated) - * @param hostkey_callback function to call once the hostkey has been - * generated for this peer, but it hasn't yet been started - * (NULL to start immediately, otherwise waits on GNUNET_TESTING_daemon_continue_start) - * @param hostkey_cls closure for hostkey callback - * @param cb function to call once peer is up, or failed to start - * @param cb_cls closure for cb - * @return handle to the daemon (actual start will be completed asynchronously) + * @param system the testing system handle */ -struct GNUNET_TESTING_Daemon * -GNUNET_TESTING_daemon_start (const struct GNUNET_CONFIGURATION_Handle *cfg, - struct GNUNET_TIME_Relative timeout, int pretend, - const char *hostname, const char *ssh_username, - uint16_t sshport, const char *hostkey, - GNUNET_TESTING_NotifyHostkeyCreated - hostkey_callback, void *hostkey_cls, - GNUNET_TESTING_NotifyDaemonRunning cb, - void *cb_cls) +static void +hostkeys_unload (struct GNUNET_TESTING_System *system) { - struct GNUNET_TESTING_Daemon *ret; - char *arg; - char *username; - char *servicehome; - char *baseservicehome; - char *slash; - char *hostkeyfile; - char *temp_file_name; - struct GNUNET_DISK_FileHandle *fn; - struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded public_key; - struct GNUNET_CRYPTO_RsaPrivateKey *private_key; - - ret = GNUNET_malloc (sizeof (struct GNUNET_TESTING_Daemon)); - ret->hostname = (hostname == NULL) ? NULL : GNUNET_strdup (hostname); - if (sshport != 0) - { - GNUNET_asprintf (&ret->ssh_port_str, "%d", sshport); - } - else - ret->ssh_port_str = NULL; - - /* Find service home and base service home directories, create it if it doesn't exist */ - GNUNET_assert (GNUNET_OK == - GNUNET_CONFIGURATION_get_value_string (cfg, "PATHS", - "SERVICEHOME", - &servicehome)); - - GNUNET_assert (GNUNET_OK == GNUNET_DISK_directory_create (servicehome)); - GNUNET_asprintf (&temp_file_name, "%s/gnunet-testing-config", servicehome); - ret->cfgfile = GNUNET_DISK_mktemp (temp_file_name); - GNUNET_free (temp_file_name); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Setting up peer with configuration file `%s'.\n", ret->cfgfile); - if (NULL == ret->cfgfile) - { - GNUNET_free_non_null (ret->ssh_port_str); - GNUNET_free_non_null (ret->hostname); - GNUNET_free (ret); - return NULL; - } - ret->hostkey_callback = hostkey_callback; - ret->hostkey_cls = hostkey_cls; - ret->cb = cb; - ret->cb_cls = cb_cls; - ret->max_timeout = GNUNET_TIME_relative_to_absolute (timeout); - ret->cfg = GNUNET_CONFIGURATION_dup (cfg); - GNUNET_CONFIGURATION_set_value_string (ret->cfg, "PATHS", "DEFAULTCONFIG", - ret->cfgfile); - - if (hostkey != NULL) /* Get the peer identity from the hostkey */ - { - private_key = GNUNET_CRYPTO_rsa_decode_key (hostkey, HOSTKEYFILESIZE); - GNUNET_assert (private_key != NULL); - GNUNET_CRYPTO_rsa_key_get_public (private_key, &public_key); - GNUNET_CRYPTO_hash (&public_key, - sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded), - &ret->id.hashPubKey); - ret->shortname = GNUNET_strdup (GNUNET_i2s (&ret->id)); - ret->have_hostkey = GNUNET_YES; - GNUNET_CRYPTO_rsa_key_free (private_key); - } - - /* Write hostkey to file, if we were given one */ - hostkeyfile = NULL; - if (hostkey != NULL) - { - GNUNET_asprintf (&hostkeyfile, "%s/.hostkey", servicehome); - fn = GNUNET_DISK_file_open (hostkeyfile, - GNUNET_DISK_OPEN_READWRITE | - GNUNET_DISK_OPEN_CREATE, - GNUNET_DISK_PERM_USER_READ | - GNUNET_DISK_PERM_USER_WRITE); - GNUNET_assert (fn != NULL); - GNUNET_assert (HOSTKEYFILESIZE == - GNUNET_DISK_file_write (fn, hostkey, HOSTKEYFILESIZE)); - GNUNET_assert (GNUNET_OK == GNUNET_DISK_file_close (fn)); - } - - /* write configuration to temporary file */ - if (GNUNET_OK != GNUNET_CONFIGURATION_write (ret->cfg, ret->cfgfile)) - { - if (0 != UNLINK (ret->cfgfile)) - GNUNET_log_strerror_file (GNUNET_ERROR_TYPE_WARNING, "unlink", - ret->cfgfile); - GNUNET_CONFIGURATION_destroy (ret->cfg); - GNUNET_free_non_null (ret->hostname); - GNUNET_free (ret->cfgfile); - GNUNET_free (ret); - return NULL; - } - if (ssh_username != NULL) - username = GNUNET_strdup (ssh_username); - if ((ssh_username == NULL) && - (GNUNET_OK != - GNUNET_CONFIGURATION_get_value_string (cfg, "TESTING", "USERNAME", - &username))) - { - if (NULL != getenv ("USER")) - username = GNUNET_strdup (getenv ("USER")); - else - username = NULL; - } - ret->username = username; - - if (GNUNET_NO == pretend) /* Copy files, enter finite state machine */ - { - /* copy directory to remote host */ - if (NULL != hostname) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Copying configuration directory to host `%s'.\n", hostname); - baseservicehome = GNUNET_strdup (servicehome); - /* Remove trailing /'s */ - while (baseservicehome[strlen (baseservicehome) - 1] == '/') - baseservicehome[strlen (baseservicehome) - 1] = '\0'; - /* Find next directory /, jump one ahead */ - slash = strrchr (baseservicehome, '/'); - if (slash != NULL) - *(++slash) = '\0'; - - ret->phase = SP_COPYING; - if (NULL != username) - GNUNET_asprintf (&arg, "%s@%s:%s", username, hostname, baseservicehome); - else - GNUNET_asprintf (&arg, "%s:%s", hostname, baseservicehome); - GNUNET_free (baseservicehome); - if (ret->ssh_port_str == NULL) - { - ret->proc_arm_copying = GNUNET_OS_start_process (GNUNET_NO, NULL, NULL, "scp", "scp", "-r", - "-q", - servicehome, arg, NULL); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "copying directory with command scp -r %s %s\n", - servicehome, arg); - } - else - { - ret->proc_arm_copying = - GNUNET_OS_start_process (GNUNET_NO, NULL, NULL, "scp", "scp", "-r", "-P", - ret->ssh_port_str, - "-q", - servicehome, arg, NULL); - } - GNUNET_free (arg); - if (NULL == ret->proc_arm_copying) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - _ - ("Could not start `%s' process to copy configuration directory.\n"), - "scp"); - if (0 != UNLINK (ret->cfgfile)) - GNUNET_log_strerror_file (GNUNET_ERROR_TYPE_WARNING, "unlink", - ret->cfgfile); - GNUNET_CONFIGURATION_destroy (ret->cfg); - GNUNET_free_non_null (ret->hostname); - GNUNET_free_non_null (ret->username); - GNUNET_free (ret->cfgfile); - GNUNET_free (ret); - if ((hostkey != NULL) && (0 != UNLINK (hostkeyfile))) - GNUNET_log_strerror_file (GNUNET_ERROR_TYPE_WARNING, "unlink", - hostkeyfile); - GNUNET_free_non_null (hostkeyfile); - GNUNET_assert (GNUNET_OK == GNUNET_DISK_directory_remove (servicehome)); - GNUNET_free (servicehome); - return NULL; - } - - ret->task = - GNUNET_SCHEDULER_add_delayed (GNUNET_CONSTANTS_EXEC_WAIT, &start_fsm, - ret); - GNUNET_free_non_null (hostkeyfile); - GNUNET_free (servicehome); - return ret; - } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "No need to copy configuration file since we are running locally.\n"); - ret->phase = SP_COPIED; - /* FIXME: why add_cont? */ - GNUNET_SCHEDULER_add_continuation (&start_fsm, ret, - GNUNET_SCHEDULER_REASON_PREREQ_DONE); - } - GNUNET_free_non_null (hostkeyfile); - GNUNET_free (servicehome); - return ret; + GNUNET_break (NULL != system->hostkeys_data); + system->hostkeys_data = NULL; + GNUNET_DISK_file_unmap (system->map); + system->map = NULL; + GNUNET_DISK_file_close (system->map_fd); + system->map_fd = NULL; + system->hostkeys_data = NULL; + system->total_hostkeys = 0; } /** - * Restart (stop and start) a GNUnet daemon. + * Create a system handle. There must only be one system + * handle per operating system. * - * @param d the daemon that should be restarted - * @param cb function called once the daemon is (re)started - * @param cb_cls closure for cb + * @param testdir only the directory name without any path. This is used for + * all service homes; the directory will be created in a temporary + * location depending on the underlying OS + * @param trusted_ip the ip address which will be set as TRUSTED HOST in all + * service configurations generated to allow control connections from + * this ip. This can either be a single ip address or a network address + * in CIDR notation. + * @param hostname the hostname of the system we are using for testing; NULL for + * localhost + * @param lowport lowest port number this system is allowed to allocate (inclusive) + * @param highport highest port number this system is allowed to allocate (exclusive) + * @return handle to this system, NULL on error */ -void -GNUNET_TESTING_daemon_restart (struct GNUNET_TESTING_Daemon *d, - GNUNET_TESTING_NotifyDaemonRunning cb, - void *cb_cls) +struct GNUNET_TESTING_System * +GNUNET_TESTING_system_create_with_portrange (const char *testdir, + const char *trusted_ip, + const char *hostname, + uint16_t lowport, + uint16_t highport) { - char *arg; - char *del_arg; - - del_arg = NULL; - if (NULL != d->cb) - { - d->dead = GNUNET_YES; - return; - } - - d->cb = cb; - d->cb_cls = cb_cls; - - if (d->phase == SP_CONFIG_UPDATE) - { - GNUNET_SCHEDULER_cancel (d->task); - d->phase = SP_START_DONE; - } - if (d->server != NULL) - { - GNUNET_CORE_disconnect (d->server); - d->server = NULL; - } - - if (d->th != NULL) - { - GNUNET_TRANSPORT_get_hello_cancel (d->ghh); - d->ghh = NULL; - GNUNET_TRANSPORT_disconnect (d->th); - d->th = NULL; - } - /* state clean up and notifications */ - GNUNET_free_non_null (d->hello); - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, _("Terminating peer `%4s'\n"), - GNUNET_i2s (&d->id)); - d->phase = SP_START_ARMING; + struct GNUNET_TESTING_System *system; - /* Check if this is a local or remote process */ - if (NULL != d->hostname) + GNUNET_assert (NULL != testdir); + system = GNUNET_malloc (sizeof (struct GNUNET_TESTING_System)); + system->tmppath = GNUNET_DISK_mkdtemp (testdir); + system->lowport = lowport; + system->highport = highport; + if (NULL == system->tmppath) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Stopping gnunet-arm with config `%s' on host `%s'.\n", - d->cfgfile, d->hostname); - if (d->username != NULL) - GNUNET_asprintf (&arg, "%s@%s", d->username, d->hostname); - else - arg = GNUNET_strdup (d->hostname); - - d->proc_arm_stop = GNUNET_OS_start_process (GNUNET_NO, NULL, NULL, "ssh", "ssh", - "-q", - arg, "gnunet-arm", - "-c", d->cfgfile, "-e", "-r", NULL); - /* Use -r to restart arm and all services */ - - GNUNET_free (arg); + GNUNET_free (system); + return NULL; } - else + if (NULL != trusted_ip) + system->trusted_ip = GNUNET_strdup (trusted_ip); + if (NULL != hostname) + system->hostname = GNUNET_strdup (hostname); + if (GNUNET_OK != hostkeys_load (system)) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Stopping gnunet-arm with config `%s' locally.\n", d->cfgfile); - d->proc_arm_stop = GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-arm", "gnunet-arm", - "-c", d->cfgfile, "-e", "-r", NULL); + GNUNET_TESTING_system_destroy (system, GNUNET_YES); + return NULL; } - - GNUNET_free_non_null (del_arg); - d->task = - GNUNET_SCHEDULER_add_delayed (GNUNET_CONSTANTS_EXEC_WAIT, &start_fsm, d); - + return system; } /** - * Stops a GNUnet daemon. + * Create a system handle. There must only be one system handle per operating + * system. Uses a default range for allowed ports. Ports are still tested for + * availability. * - * @param d the daemon that should be stopped - * @param service the name of the service to stop - * @param timeout how long to wait for process for shutdown to complete - * @param cb function called once the daemon was stopped - * @param cb_cls closure for cb + * @param testdir only the directory name without any path. This is used for all + * service homes; the directory will be created in a temporary location + * depending on the underlying OS + * @param trusted_ip the ip address which will be set as TRUSTED HOST in all + * service configurations generated to allow control connections from + * this ip. This can either be a single ip address or a network address + * in CIDR notation. + * @param hostname the hostname of the system we are using for testing; NULL for + * localhost + * @return handle to this system, NULL on error */ -void -GNUNET_TESTING_daemon_stop_service (struct GNUNET_TESTING_Daemon *d, - const char *service, - struct GNUNET_TIME_Relative timeout, - GNUNET_TESTING_NotifyCompletion cb, - void *cb_cls) +struct GNUNET_TESTING_System * +GNUNET_TESTING_system_create (const char *testdir, + const char *trusted_ip, + const char *hostname) { - char *arg; - - d->dead_cb = cb; - d->dead_cb_cls = cb_cls; - - GNUNET_assert (d->running == GNUNET_YES); - - if (d->phase == SP_CONFIG_UPDATE) - { - GNUNET_SCHEDULER_cancel (d->task); - d->phase = SP_START_DONE; - } - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, _("Terminating peer `%4s'\n"), - GNUNET_i2s (&d->id)); - if (d->churned_services != NULL) - { - d->dead_cb (d->dead_cb_cls, "A service has already been turned off!!"); - return; - } - d->phase = SP_SERVICE_SHUTDOWN_START; - d->churned_services = GNUNET_strdup (service); - d->max_timeout = GNUNET_TIME_relative_to_absolute (timeout); - /* Check if this is a local or remote process */ - if (NULL != d->hostname) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Stopping gnunet-arm with config `%s' on host `%s'.\n", - d->cfgfile, d->hostname); - if (d->username != NULL) - GNUNET_asprintf (&arg, "%s@%s", d->username, d->hostname); - else - arg = GNUNET_strdup (d->hostname); - - d->proc_arm_srv_stop = GNUNET_OS_start_process (GNUNET_NO, NULL, NULL, "ssh", "ssh", - "-q", - arg, "gnunet-arm", - "-c", d->cfgfile, "-k", service, "-q", - "-T", - GNUNET_TIME_relative_to_string (timeout), - NULL); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Stopping gnunet-arm with command ssh %s gnunet-arm -c %s -k %s -q\n", - arg, "gnunet-arm", d->cfgfile, service); - GNUNET_free (arg); - } - else - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Stopping gnunet-arm with config `%s' locally.\n", d->cfgfile); - d->proc_arm_srv_stop = GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-arm", "gnunet-arm", - "-c", d->cfgfile, "-k", service, "-q", - "-T", - GNUNET_TIME_relative_to_string (timeout), - NULL); - } - - d->max_timeout = GNUNET_TIME_relative_to_absolute (timeout); - d->task = GNUNET_SCHEDULER_add_now (&start_fsm, d); + return GNUNET_TESTING_system_create_with_portrange (testdir, + trusted_ip, + hostname, + LOW_PORT, + HIGH_PORT); } /** - * Forcefully terminate a process and clean up the child. + * Free system resources. * - * @param proc handle to process to kill + * @param system system to be freed + * @param remove_paths should the 'testdir' and all subdirectories + * be removed (clean up on shutdown)? */ -static void -kill_and_close_process (struct GNUNET_OS_Process *proc) +void +GNUNET_TESTING_system_destroy (struct GNUNET_TESTING_System *system, + int remove_paths) { - (void) GNUNET_OS_process_kill (proc, SIGKILL); - GNUNET_break (GNUNET_OK == GNUNET_OS_process_wait (proc)); - GNUNET_OS_process_destroy (proc); + if (NULL != system->hostkeys_data) + hostkeys_unload (system); + if (GNUNET_YES == remove_paths) + GNUNET_DISK_directory_remove (system->tmppath); + GNUNET_free (system->tmppath); + GNUNET_free_non_null (system->trusted_ip); + GNUNET_free_non_null (system->hostname); + GNUNET_free (system); } /** - * Stops a GNUnet daemon. + * Reserve a TCP or UDP port for a peer. * - * @param d the daemon that should be stopped - * @param timeout how long to wait for process for shutdown to complete - * @param cb function called once the daemon was stopped - * @param cb_cls closure for cb - * @param delete_files GNUNET_YES to remove files, GNUNET_NO - * to leave them - * @param allow_restart GNUNET_YES to restart peer later (using this API) - * GNUNET_NO to kill off and clean up for good + * @param system system to use for reservation tracking + * @param is_tcp GNUNET_YES for TCP ports, GNUNET_NO for UDP + * @return 0 if no free port was available */ -void -GNUNET_TESTING_daemon_stop (struct GNUNET_TESTING_Daemon *d, - struct GNUNET_TIME_Relative timeout, - GNUNET_TESTING_NotifyCompletion cb, void *cb_cls, - int delete_files, int allow_restart) +uint16_t +GNUNET_TESTING_reserve_port (struct GNUNET_TESTING_System *system, + int is_tcp) { - char *arg; - char *del_arg; - - d->dead_cb = cb; - d->dead_cb_cls = cb_cls; - - if (NULL != d->cb) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, _("Setting d->dead on peer `%4s'\n"), - GNUNET_i2s (&d->id)); - d->dead = GNUNET_YES; - return; - } - if (NULL != d->proc_arm_start) - { - kill_and_close_process (d->proc_arm_start); - d->proc_arm_start = NULL; - } - if (NULL != d->proc_arm_srv_start) - { - kill_and_close_process (d->proc_arm_srv_start); - d->proc_arm_srv_start = NULL; - } - if (NULL != d->proc_arm_srv_stop) - { - kill_and_close_process (d->proc_arm_srv_stop); - d->proc_arm_srv_stop = NULL; - } - if (NULL != d->proc_arm_copying) - { - kill_and_close_process (d->proc_arm_copying); - d->proc_arm_copying = NULL; - } - if (NULL != d->proc_arm_peerinfo) - { - kill_and_close_process (d->proc_arm_peerinfo); - d->proc_arm_peerinfo = NULL; - } - if ((d->running == GNUNET_NO) && (d->churn == GNUNET_YES)) - { - /* Peer has already been stopped in churn context! - * Free what was left from churning! */ - GNUNET_assert (d->cfg != NULL); - GNUNET_CONFIGURATION_destroy (d->cfg); - if (delete_files == GNUNET_YES) + struct GNUNET_NETWORK_Handle *socket; + struct addrinfo hint; + struct addrinfo *ret; + struct addrinfo *ai; + uint32_t *port_buckets; + char *open_port_str; + int bind_status; + uint32_t xor_image; + uint16_t index; + uint16_t open_port; + uint16_t pos; + + /* + FIXME: Instead of using getaddrinfo we should try to determine the port + status by the following heurestics. + + On systems which support both IPv4 and IPv6, only ports open on both + address families are considered open. + On system with either IPv4 or IPv6. A port is considered open if it's + open in the respective address family + */ + hint.ai_family = AF_UNSPEC; /* IPv4 and IPv6 */ + hint.ai_socktype = (GNUNET_YES == is_tcp)? SOCK_STREAM : SOCK_DGRAM; + hint.ai_protocol = 0; + hint.ai_addrlen = 0; + hint.ai_addr = NULL; + hint.ai_canonname = NULL; + hint.ai_next = NULL; + hint.ai_flags = AI_PASSIVE | AI_NUMERICSERV; /* Wild card address */ + port_buckets = (GNUNET_YES == is_tcp) ? + system->reserved_tcp_ports : system->reserved_udp_ports; + for (index = (system->lowport / 32) + 1; index < (system->highport / 32); index++) + { + xor_image = (UINT32_MAX ^ port_buckets[index]); + if (0 == xor_image) /* Ports in the bucket are full */ + continue; + pos = system->lowport % 32; + while (pos < 32) { - if (0 != UNLINK (d->cfgfile)) + if (0 == ((xor_image >> pos) & 1U)) { - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "unlink"); + pos++; + continue; } + open_port = (index * 32) + pos; + if (open_port >= system->highport) + return 0; + GNUNET_asprintf (&open_port_str, "%u", (unsigned int) open_port); + ret = NULL; + GNUNET_assert (0 == getaddrinfo (NULL, open_port_str, &hint, &ret)); + GNUNET_free (open_port_str); + bind_status = GNUNET_NO; + for (ai = ret; NULL != ai; ai = ai->ai_next) + { + socket = GNUNET_NETWORK_socket_create (ai->ai_family, + (GNUNET_YES == is_tcp) ? + SOCK_STREAM : SOCK_DGRAM, + 0); + if (NULL == socket) + continue; + bind_status = GNUNET_NETWORK_socket_bind (socket, + ai->ai_addr, + ai->ai_addrlen); + GNUNET_NETWORK_socket_close (socket); + if (GNUNET_OK != bind_status) + break; + } + port_buckets[index] |= (1U << pos); /* Set the port bit */ + freeaddrinfo (ret); + if (GNUNET_OK == bind_status) + { + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Found a free port %u\n", (unsigned int) open_port); + return open_port; + } + pos++; } - GNUNET_free (d->cfgfile); - GNUNET_free_non_null (d->hostname); - GNUNET_free_non_null (d->username); - if (NULL != d->dead_cb) - d->dead_cb (d->dead_cb_cls, NULL); - /* FIXME: this should be an assert and the test below - should not be required, but testing is broken... */ - GNUNET_break (NULL == d->proc_arm_stop); - if (NULL == d->proc_arm_stop) - GNUNET_free (d); - return; - } - - del_arg = NULL; - if (delete_files == GNUNET_YES) - { - GNUNET_asprintf (&del_arg, "-d"); - } - - if (d->phase == SP_CONFIG_UPDATE) - { - GNUNET_SCHEDULER_cancel (d->task); - d->phase = SP_START_DONE; - } - /** Move this call to scheduled shutdown as fix for CORE_connect calling daemon_stop? - if (d->server != NULL) - { - GNUNET_CORE_disconnect (d->server); - d->server = NULL; - } - */ - /* shutdown ARM process (will terminate others) */ - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Terminating peer `%4s'\n" , - GNUNET_i2s (&d->id)); - d->phase = SP_SHUTDOWN_START; - d->running = GNUNET_NO; - if (allow_restart == GNUNET_YES) - d->churn = GNUNET_YES; - if (d->th != NULL) - { - GNUNET_TRANSPORT_get_hello_cancel (d->ghh); - d->ghh = NULL; - GNUNET_TRANSPORT_disconnect (d->th); - d->th = NULL; } - /* Check if this is a local or remote process */ - - - if (NULL != d->hostname) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Stopping gnunet-arm with config `%s' on host `%s'.\n", - d->cfgfile, d->hostname); - if (d->username != NULL) - GNUNET_asprintf (&arg, "%s@%s", d->username, d->hostname); - else - arg = GNUNET_strdup (d->hostname); - - d->proc_arm_stop = GNUNET_OS_start_process (GNUNET_NO, NULL, NULL, "ssh", "ssh", - "-q", - arg, "gnunet-arm", - "-c", d->cfgfile, "-e", "-q", "-T", - GNUNET_TIME_relative_to_string (timeout), - del_arg, NULL); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Stopping gnunet-arm with command ssh %s gnunet-arm -c %s -e -q %s\n", - arg, "gnunet-arm", d->cfgfile, del_arg); - /* Use -e to end arm, and -d to remove temp files */ - GNUNET_free (arg); - } - else - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Stopping gnunet-arm with config `%s' locally.\n", d->cfgfile); - d->proc_arm_stop = GNUNET_OS_start_process (GNUNET_NO, NULL, NULL, "gnunet-arm", "gnunet-arm", - "-c", d->cfgfile, "-e", "-q", "-T", - GNUNET_TIME_relative_to_string (timeout), - del_arg, NULL); - GNUNET_assert (NULL != d->proc_arm_stop); - } - - GNUNET_free_non_null (del_arg); - d->max_timeout = GNUNET_TIME_relative_to_absolute (timeout); - if (GNUNET_SCHEDULER_NO_TASK != d->task) - GNUNET_SCHEDULER_cancel(d->task); - d->task = GNUNET_SCHEDULER_add_now (&start_fsm, d); + return 0; } /** - * Changes the configuration of a GNUnet daemon. + * Release reservation of a TCP or UDP port for a peer + * (used during GNUNET_TESTING_peer_destroy). * - * @param d the daemon that should be modified - * @param cfg the new configuration for the daemon - * @param cb function called once the configuration was changed - * @param cb_cls closure for cb + * @param system system to use for reservation tracking + * @param is_tcp GNUNET_YES for TCP ports, GNUNET_NO for UDP + * @param port reserved port to release */ void -GNUNET_TESTING_daemon_reconfigure (struct GNUNET_TESTING_Daemon *d, - struct GNUNET_CONFIGURATION_Handle *cfg, - GNUNET_TESTING_NotifyCompletion cb, - void *cb_cls) -{ - char *arg; - - if (d->phase != SP_START_DONE) - { - if (NULL != cb) - cb (cb_cls, - _ - ("Peer not yet running, can not change configuration at this point.")); - return; - } - - /* 1) write configuration to temporary file */ - if (GNUNET_OK != GNUNET_CONFIGURATION_write (cfg, d->cfgfile)) - { - if (NULL != cb) - cb (cb_cls, _("Failed to write new configuration to disk.")); - return; - } - - /* 2) copy file to remote host (if necessary) */ - if (NULL == d->hostname) - { - /* signal success */ - if (NULL != cb) - cb (cb_cls, NULL); - return; - } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Copying updated configuration file to remote host `%s'.\n", - d->hostname); - d->phase = SP_CONFIG_UPDATE; - if (NULL != d->username) - GNUNET_asprintf (&arg, "%s@%s:%s", d->username, d->hostname, d->cfgfile); - else - GNUNET_asprintf (&arg, "%s:%s", d->hostname, d->cfgfile); - d->proc_arm_copying = GNUNET_OS_start_process (GNUNET_NO, NULL, NULL, "scp", "scp", - "-q", - d->cfgfile, arg, NULL); - GNUNET_free (arg); - if (NULL == d->proc_arm_copying) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - _("Could not start `%s' process to copy configuration file.\n"), - "scp"); - if (NULL != cb) - cb (cb_cls, _("Failed to copy new configuration to remote machine.")); - d->phase = SP_START_DONE; +GNUNET_TESTING_release_port (struct GNUNET_TESTING_System *system, + int is_tcp, + uint16_t port) +{ + uint32_t *port_buckets; + uint16_t bucket; + uint16_t pos; + + port_buckets = (GNUNET_YES == is_tcp) ? + system->reserved_tcp_ports : system->reserved_udp_ports; + bucket = port / 32; + pos = port % 32; + LOG (GNUNET_ERROR_TYPE_DEBUG, "Releasing port %u\n", port); + if (0 == (port_buckets[bucket] & (1U << pos))) + { + GNUNET_break(0); /* Port was not reserved by us using reserve_port() */ return; } - d->update_cb = cb; - d->update_cb_cls = cb_cls; - d->task = - GNUNET_SCHEDULER_add_delayed (GNUNET_CONSTANTS_EXEC_WAIT, &start_fsm, d); + port_buckets[bucket] &= ~(1U << pos); } /** - * Data kept for each pair of peers that we try - * to connect. + * Reserve a SERVICEHOME path for a peer. + * + * @param system system to use for reservation tracking + * @return NULL on error, otherwise fresh unique path to use + * as the servicehome for the peer; must be freed by the caller */ -struct GNUNET_TESTING_ConnectContext +// static +char * +reserve_path (struct GNUNET_TESTING_System *system) { - /** - * Testing handle to the first daemon. - */ - struct GNUNET_TESTING_Daemon *d1; - - /** - * Handle to core of first daemon (to check connect) - */ - struct GNUNET_CORE_Handle *d1core; - - /** - * Have we actually connected to the core of the first daemon yet? - */ - int d1core_ready; - - /** - * Testing handle to the second daemon. - */ - struct GNUNET_TESTING_Daemon *d2; - - /** - * Transport handle to the first daemon (to offer the HELLO of the second daemon to). - */ - struct GNUNET_TRANSPORT_Handle *d1th; + char *reserved_path; - /** - * Function to call once we are done (or have timed out). - */ - GNUNET_TESTING_NotifyConnection cb; - - /** - * Closure for "nb". - */ - void *cb_cls; - - /** - * The relative timeout from whence this connect attempt was - * started. Allows for reconnect attempts. - */ - struct GNUNET_TIME_Relative relative_timeout; + GNUNET_asprintf (&reserved_path, + "%s/%u", system->tmppath, system->path_counter++); + return reserved_path; +} - /** - * Maximum number of connect attempts, will retry connection - * this number of times on failures. - */ - unsigned int connect_attempts; - /** - * Hello timeout task - */ - GNUNET_SCHEDULER_TaskIdentifier hello_send_task; +/** + * Testing includes a number of pre-created hostkeys for + * faster peer startup. This function can be used to + * access the n-th key of those pre-created hostkeys; note + * that these keys are ONLY useful for testing and not + * secure as the private keys are part of the public + * GNUnet source code. + * + * This is primarily a helper function used internally + * by 'GNUNET_TESTING_peer_configure'. + * + * @param system the testing system handle + * @param key_number desired pre-created hostkey to obtain + * @param id set to the peer's identity (hash of the public + * key; if NULL, GNUNET_SYSERR is returned immediately + * @return NULL on error (not enough keys) + */ +struct GNUNET_CRYPTO_RsaPrivateKey * +GNUNET_TESTING_hostkey_get (const struct GNUNET_TESTING_System *system, + uint32_t key_number, + struct GNUNET_PeerIdentity *id) +{ + struct GNUNET_CRYPTO_RsaPrivateKey *private_key; + struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded public_key; + + if ((NULL == id) || (NULL == system->hostkeys_data)) + return NULL; + if (key_number >= system->total_hostkeys) + { + LOG (GNUNET_ERROR_TYPE_ERROR, + _("Key number %u does not exist\n"), key_number); + return NULL; + } + private_key = GNUNET_CRYPTO_rsa_decode_key (system->hostkeys_data + + (key_number * + GNUNET_TESTING_HOSTKEYFILESIZE), + GNUNET_TESTING_HOSTKEYFILESIZE); + if (NULL == private_key) + { + LOG (GNUNET_ERROR_TYPE_ERROR, + _("Error while decoding key %u\n"), key_number); + return NULL; + } + GNUNET_CRYPTO_rsa_key_get_public (private_key, &public_key); + GNUNET_CRYPTO_hash (&public_key, + sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded), + &(id->hashPubKey)); + return private_key; +} - /** - * Connect timeout task - */ - GNUNET_SCHEDULER_TaskIdentifier timeout_task; +/** + * Structure for holding data to build new configurations from a configuration + * template + */ +struct UpdateContext +{ /** - * When should this operation be complete (or we must trigger - * a timeout). + * The system for which we are building configurations */ - struct GNUNET_TIME_Relative timeout_hello; - + struct GNUNET_TESTING_System *system; + /** - * Was the connection attempt successful? + * The configuration we are building */ - int connected; + struct GNUNET_CONFIGURATION_Handle *cfg; /** - * When connecting, do we need to send the HELLO? + * The customized service home path for this peer */ - int send_hello; + char *service_home; /** - * The distance between the two connected peers + * build status - to signal error while building a configuration */ - uint32_t distance; + int status; }; -/** Forward declaration **/ -static void -reattempt_daemons_connect (void *cls, - const struct GNUNET_SCHEDULER_TaskContext *tc); - - /** - * Notify callback about success or failure of the attempt - * to connect the two peers + * Function to iterate over options. Copies + * the options to the target configuration, + * updating PORT values as needed. * - * @param cls our "struct GNUNET_TESTING_ConnectContext" (freed) - * @param tc reason tells us if we succeeded or failed + * @param cls the UpdateContext + * @param section name of the section + * @param option name of the option + * @param value value of the option */ static void -notify_connect_result (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +update_config (void *cls, const char *section, const char *option, + const char *value) { - struct GNUNET_TESTING_ConnectContext *ctx = cls; - - ctx->timeout_task = GNUNET_SCHEDULER_NO_TASK; - if (ctx->hello_send_task != GNUNET_SCHEDULER_NO_TASK) - { - GNUNET_SCHEDULER_cancel (ctx->hello_send_task); - ctx->hello_send_task = GNUNET_SCHEDULER_NO_TASK; - } - - if (ctx->d1th != NULL) - GNUNET_TRANSPORT_disconnect (ctx->d1th); - ctx->d1th = NULL; - if (ctx->d1core != NULL) - GNUNET_CORE_disconnect (ctx->d1core); - ctx->d1core = NULL; - - if ((tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN) != 0) - { - GNUNET_free (ctx); + struct UpdateContext *uc = cls; + unsigned int ival; + char cval[12]; + char uval[128]; + char *single_variable; + char *per_host_variable; + unsigned long long num_per_host; + uint16_t new_port; + + if (GNUNET_OK != uc->status) return; - } - - if (ctx->connected == GNUNET_YES) - { - if (ctx->cb != NULL) + if (! ((0 == strcmp (option, "PORT")) + || (0 == strcmp (option, "UNIXPATH")) + || (0 == strcmp (option, "HOSTNAME")))) + return; + GNUNET_asprintf (&single_variable, "single_%s_per_host", section); + GNUNET_asprintf (&per_host_variable, "num_%s_per_host", section); + if ((0 == strcmp (option, "PORT")) && (1 == SSCANF (value, "%u", &ival))) + { + if ((ival != 0) && + (GNUNET_YES != + GNUNET_CONFIGURATION_get_value_yesno (uc->cfg, "testing", + single_variable))) { - ctx->cb (ctx->cb_cls, &ctx->d1->id, &ctx->d2->id, ctx->distance, - ctx->d1->cfg, ctx->d2->cfg, ctx->d1, ctx->d2, NULL); + /* FIXME: What about UDP? */ + new_port = GNUNET_TESTING_reserve_port (uc->system, GNUNET_YES); + if (0 == new_port) + { + uc->status = GNUNET_SYSERR; + GNUNET_free (single_variable); + GNUNET_free (per_host_variable); + return; + } + GNUNET_snprintf (cval, sizeof (cval), "%u", new_port); + value = cval; + } + else if ((ival != 0) && + (GNUNET_YES == + GNUNET_CONFIGURATION_get_value_yesno (uc->cfg, "testing", + single_variable)) && + GNUNET_CONFIGURATION_get_value_number (uc->cfg, "testing", + per_host_variable, + &num_per_host)) + { + /* GNUNET_snprintf (cval, sizeof (cval), "%u", */ + /* ival + ctx->fdnum % num_per_host); */ + /* value = cval; */ + GNUNET_break (0); /* FIXME */ } } - else if (ctx->connect_attempts > 0) - { - ctx->d1core_ready = GNUNET_NO; - ctx->timeout_task = - GNUNET_SCHEDULER_add_now (&reattempt_daemons_connect, ctx); - return; - } - else + if (0 == strcmp (option, "UNIXPATH")) { - if (ctx->cb != NULL) + if (GNUNET_YES != + GNUNET_CONFIGURATION_get_value_yesno (uc->cfg, "testing", + single_variable)) { - ctx->cb (ctx->cb_cls, &ctx->d1->id, &ctx->d2->id, 0, ctx->d1->cfg, - ctx->d2->cfg, ctx->d1, ctx->d2, _("Peers failed to connect")); + GNUNET_snprintf (uval, sizeof (uval), "%s/%s.sock", + uc->service_home, section); + value = uval; } + else if ((GNUNET_YES == + GNUNET_CONFIGURATION_get_value_number (uc->cfg, "testing", + per_host_variable, + &num_per_host)) && + (num_per_host > 0)) + { + GNUNET_break(0); /* FIXME */ + } + } + if (0 == strcmp (option, "HOSTNAME")) + { + value = (NULL == uc->system->hostname) ? "localhost" : uc->system->hostname; } - GNUNET_free (ctx); + GNUNET_free (single_variable); + GNUNET_free (per_host_variable); + GNUNET_CONFIGURATION_set_value_string (uc->cfg, section, option, value); } /** - * Success, connection is up. Signal client our success. - * - * @param cls our "struct GNUNET_TESTING_ConnectContext" - * @param peer identity of the peer that has connected - * @param atsi performance information - * @param atsi_count number of records in 'atsi' + * Section iterator to set ACCEPT_FROM/ACCEPT_FROM6 to include the address of + * 'trusted_hosts' in all sections * + * @param cls the UpdateContext + * @param section name of the section */ static void -connect_notify (void *cls, const struct GNUNET_PeerIdentity *peer, - const struct GNUNET_ATS_Information *atsi, - unsigned int atsi_count) +update_config_sections (void *cls, + const char *section) { - struct GNUNET_TESTING_ConnectContext *ctx = cls; - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Connected peer %s to peer %s\n", - ctx->d1->shortname, GNUNET_i2s (peer)); - if (0 != memcmp (&ctx->d2->id, peer, sizeof (struct GNUNET_PeerIdentity))) - return; - ctx->connected = GNUNET_YES; - ctx->distance = 0; /* FIXME: distance */ - if (ctx->hello_send_task != GNUNET_SCHEDULER_NO_TASK) + struct UpdateContext *uc = cls; + char **ikeys; + char *val; + char *ptr; + char *orig_allowed_hosts; + char *allowed_hosts; + char *ACCEPT_FROM_key; + uint16_t ikeys_cnt; + uint16_t key; + + ikeys_cnt = 0; + val = NULL; + if (GNUNET_YES == GNUNET_CONFIGURATION_have_value (uc->cfg, section, + "TESTING_IGNORE_KEYS")) + { + GNUNET_assert + (GNUNET_YES == + GNUNET_CONFIGURATION_get_value_string (uc->cfg, section, + "TESTING_IGNORE_KEYS", &val)); + ptr = val; + for (ikeys_cnt = 0; NULL != (ptr = strstr (ptr, ";")); ikeys_cnt++) + ptr++; + if (0 == ikeys_cnt) + GNUNET_break (0); + else + { + ikeys = GNUNET_malloc ((sizeof (char *)) * ikeys_cnt); + ptr = val; + for (key = 0; key < ikeys_cnt; key++) + { + ikeys[key] = ptr; + ptr = strstr (ptr, ";"); + *ptr = '\0'; + ptr++; + } + } + } + if (0 != ikeys_cnt) { - GNUNET_SCHEDULER_cancel (ctx->hello_send_task); - ctx->hello_send_task = GNUNET_SCHEDULER_NO_TASK; + for (key = 0; key < ikeys_cnt; key++) + { + if (NULL != strstr (ikeys[key], "ADVERTISED_PORT")) + break; + } + if ((key == ikeys_cnt) && + (GNUNET_YES == GNUNET_CONFIGURATION_have_value (uc->cfg, section, + "ADVERTISED_PORT"))) + { + if (GNUNET_OK == + GNUNET_CONFIGURATION_get_value_string (uc->cfg, section, "PORT", &ptr)) + { + GNUNET_CONFIGURATION_set_value_string (uc->cfg, section, + "ADVERTISED_PORT", ptr); + GNUNET_free (ptr); + } + } + for (key = 0; key < ikeys_cnt; key++) + { + if (NULL != strstr (ikeys[key], "ACCEPT_FROM")) + { + GNUNET_free (ikeys); + GNUNET_free (val); + return; + } + } + GNUNET_free (ikeys); } - GNUNET_SCHEDULER_cancel (ctx->timeout_task); - ctx->timeout_task = GNUNET_SCHEDULER_add_now (¬ify_connect_result, ctx); -} - - -static void -send_hello (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - struct GNUNET_TESTING_ConnectContext *ctx = cls; - struct GNUNET_MessageHeader *hello; - - ctx->hello_send_task = GNUNET_SCHEDULER_NO_TASK; - if ((tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN) != 0) - return; - if ((ctx->d1core_ready == GNUNET_YES) && (ctx->d2->hello != NULL) && - (NULL != GNUNET_HELLO_get_header (ctx->d2->hello)) && - (ctx->d1->phase == SP_START_DONE) && (ctx->d2->phase == SP_START_DONE)) + GNUNET_free_non_null (val); + ACCEPT_FROM_key = "ACCEPT_FROM"; + if ((NULL != uc->system->trusted_ip) && + (NULL != strstr (uc->system->trusted_ip, ":"))) /* IPv6 in use */ + ACCEPT_FROM_key = "ACCEPT_FROM6"; + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_string (uc->cfg, section, ACCEPT_FROM_key, + &orig_allowed_hosts)) { - hello = GNUNET_HELLO_get_header (ctx->d2->hello); - GNUNET_assert (hello != NULL); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Offering hello of %s to %s\n", - ctx->d2->shortname, ctx->d1->shortname); - GNUNET_TRANSPORT_offer_hello (ctx->d1th, hello, NULL, NULL); - GNUNET_assert (ctx->d1core != NULL); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Sending connect request to TRANSPORT of %s for peer %s\n", - GNUNET_i2s (&ctx->d1->id), - GNUNET_h2s (&ctx->d2->id.hashPubKey)); - GNUNET_TRANSPORT_try_connect (ctx->d1th, &ctx->d2->id); - ctx->timeout_hello = - GNUNET_TIME_relative_add (ctx->timeout_hello, - GNUNET_TIME_relative_multiply - (GNUNET_TIME_UNIT_MILLISECONDS, 500)); + orig_allowed_hosts = GNUNET_strdup ("127.0.0.1;"); } - ctx->hello_send_task = - GNUNET_SCHEDULER_add_delayed (ctx->timeout_hello, &send_hello, ctx); + if (NULL == uc->system->trusted_ip) + allowed_hosts = GNUNET_strdup (orig_allowed_hosts); + else + GNUNET_asprintf (&allowed_hosts, "%s%s;", orig_allowed_hosts, + uc->system->trusted_ip); + GNUNET_free (orig_allowed_hosts); + GNUNET_CONFIGURATION_set_value_string (uc->cfg, section, ACCEPT_FROM_key, + allowed_hosts); + GNUNET_free (allowed_hosts); } + /** - * Notify of a successful connection to the core service. + * Create a new configuration using the given configuration as a template; + * ports and paths will be modified to select available ports on the local + * system. The default configuration will be available in PATHS section under + * the option DEFAULTCONFIG after the call. SERVICE_HOME is also set in PATHS + * section to the temporary directory specific to this configuration. If we run + * out of "*port" numbers, return SYSERR. + * + * This is primarily a helper function used internally + * by 'GNUNET_TESTING_peer_configure'. * - * @param cls a ConnectContext - * @param server handle to the core service - * @param my_identity the peer identity of this peer + * @param system system to use to coordinate resource usage + * @param cfg template configuration to update + * @return GNUNET_OK on success, GNUNET_SYSERR on error - the configuration will + * be incomplete and should not be used there upon */ -void -core_init_notify (void *cls, struct GNUNET_CORE_Handle *server, - const struct GNUNET_PeerIdentity *my_identity) +int +GNUNET_TESTING_configuration_create (struct GNUNET_TESTING_System *system, + struct GNUNET_CONFIGURATION_Handle *cfg) { - struct GNUNET_TESTING_ConnectContext *connect_ctx = cls; - - connect_ctx->d1core_ready = GNUNET_YES; - - if (connect_ctx->send_hello == GNUNET_NO) - { - GNUNET_TRANSPORT_try_connect (connect_ctx->d1th, &connect_ctx->d2->id); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Sending connect request to TRANSPORT of %s for peer %s\n", - connect_ctx->d1->shortname, connect_ctx->d2->shortname); - } + struct UpdateContext uc; + char *default_config; + + uc.system = system; + uc.cfg = cfg; + uc.status = GNUNET_OK; + GNUNET_asprintf (&uc.service_home, "%s/%u", system->tmppath, + system->path_counter++); + GNUNET_asprintf (&default_config, "%s/config", uc.service_home); + GNUNET_CONFIGURATION_set_value_string (cfg, "PATHS", "DEFAULTCONFIG", + default_config); + GNUNET_free (default_config); + GNUNET_CONFIGURATION_set_value_string (cfg, "PATHS", "SERVICEHOME", + uc.service_home); + /* make PORTs and UNIXPATHs unique */ + GNUNET_CONFIGURATION_iterate (cfg, &update_config, &uc); + /* allow connections to services from system trusted_ip host */ + GNUNET_CONFIGURATION_iterate_sections (cfg, &update_config_sections, &uc); + /* enable loopback-based connections between peers */ + GNUNET_CONFIGURATION_set_value_string (cfg, + "nat", + "USE_LOCALADDR", "YES"); + GNUNET_free (uc.service_home); + return uc.status; } /** - * Try to connect again some peers that failed in an earlier attempt. This will - * be tried as many times as connection_attempts in the configuration file. + * Configure a GNUnet peer. GNUnet must be installed on the local + * system and available in the PATH. * - * @param cls Closure (connection context between the two peers). - * @param tc TaskContext. + * @param system system to use to coordinate resource usage + * @param cfg configuration to use; will be UPDATED (to reflect needed + * changes in port numbers and paths) + * @param key_number number of the hostkey to use for the peer + * @param id identifier for the daemon, will be set, can be NULL + * @param emsg set to freshly allocated error message (set to NULL on success), + * can be NULL + * @return handle to the peer, NULL on error */ -static void -reattempt_daemons_connect (void *cls, - const struct GNUNET_SCHEDULER_TaskContext *tc) +struct GNUNET_TESTING_Peer * +GNUNET_TESTING_peer_configure (struct GNUNET_TESTING_System *system, + struct GNUNET_CONFIGURATION_Handle *cfg, + uint32_t key_number, + struct GNUNET_PeerIdentity *id, + char **emsg) { - struct GNUNET_TESTING_ConnectContext *ctx = cls; - - ctx->timeout_task = GNUNET_SCHEDULER_NO_TASK; - if ((tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN) != 0) - return; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "re-attempting connect of peer %s to peer %s\n", - ctx->d1->shortname, ctx->d2->shortname); - ctx->connect_attempts--; - GNUNET_assert (ctx->d1core == NULL); - ctx->d1core_ready = GNUNET_NO; - ctx->d1core = - GNUNET_CORE_connect (ctx->d1->cfg, 1, ctx, &core_init_notify, - &connect_notify, NULL, NULL, GNUNET_NO, NULL, - GNUNET_NO, no_handlers); - if (ctx->d1core == NULL) - { - if (NULL != ctx->cb) - ctx->cb (ctx->cb_cls, &ctx->d1->id, &ctx->d2->id, 0, ctx->d1->cfg, - ctx->d2->cfg, ctx->d1, ctx->d2, - _("Failed to connect to core service of first peer!\n")); - GNUNET_free (ctx); - return; + struct GNUNET_TESTING_Peer *peer; + struct GNUNET_DISK_FileHandle *fd; + char *service_home; + char hostkey_filename[128]; + char *config_filename; + char *libexec_binary; + char *emsg_; + struct GNUNET_CRYPTO_RsaPrivateKey *pk; + + if (NULL != emsg) + *emsg = NULL; + if (GNUNET_OK != GNUNET_TESTING_configuration_create (system, cfg)) + { + GNUNET_asprintf (&emsg_, + _("Failed to create configuration for peer (not enough free ports?)\n")); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "%s", emsg_); + if (NULL != emsg) + *emsg = emsg_; + else + GNUNET_free (emsg_); + return NULL; } - - /* Don't know reason for initial connect failure, update the HELLO for the second peer */ - if (NULL != ctx->d2->hello) + if (key_number >= system->total_hostkeys) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "updating %s's HELLO\n", - ctx->d2->shortname); - GNUNET_free (ctx->d2->hello); - ctx->d2->hello = NULL; - if (NULL != ctx->d2->th) - { - GNUNET_TRANSPORT_get_hello_cancel (ctx->d2->ghh); - ctx->d2->ghh = NULL; - GNUNET_TRANSPORT_disconnect (ctx->d2->th); - } - ctx->d2->th = - GNUNET_TRANSPORT_connect (ctx->d2->cfg, &ctx->d2->id, NULL, NULL, NULL, - NULL); - GNUNET_assert (ctx->d2->th != NULL); - ctx->d2->ghh = - GNUNET_TRANSPORT_get_hello (ctx->d2->th, &process_hello, ctx->d2); + GNUNET_asprintf (&emsg_, + _("You attempted to create a testbed with more than %u hosts. Please precompute more hostkeys first.\n"), + (unsigned int) system->total_hostkeys); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "%s", emsg_); + if (NULL != emsg) + *emsg = emsg_; + else + GNUNET_free (emsg_); + return NULL; } - else + pk = NULL; + if ((NULL != id) && + (NULL == (pk = GNUNET_TESTING_hostkey_get (system, key_number, id)))) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "didn't have %s's HELLO\n", - ctx->d2->shortname); + GNUNET_asprintf (&emsg_, + _("Failed to initialize hostkey for peer %u\n"), + (unsigned int) key_number); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "%s", emsg_); + if (NULL != emsg) + *emsg = emsg_; + else + GNUNET_free (emsg_); + return NULL; } - - if ((NULL == ctx->d2->hello) && (ctx->d2->th == NULL)) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "didn't have %s's HELLO, trying to get it now\n", - ctx->d2->shortname); - ctx->d2->th = - GNUNET_TRANSPORT_connect (ctx->d2->cfg, &ctx->d2->id, NULL, NULL, NULL, - NULL); - if (NULL == ctx->d2->th) - { - GNUNET_CORE_disconnect (ctx->d1core); - GNUNET_free (ctx); - if (NULL != ctx->cb) - ctx->cb (ctx->cb_cls, &ctx->d1->id, &ctx->d2->id, 0, ctx->d1->cfg, - ctx->d2->cfg, ctx->d1, ctx->d2, - _("Failed to connect to transport service!\n")); - return; - } - ctx->d2->ghh = - GNUNET_TRANSPORT_get_hello (ctx->d2->th, &process_hello, ctx->d2); + if (NULL != pk) + GNUNET_CRYPTO_rsa_key_free (pk); + GNUNET_assert (GNUNET_OK == + GNUNET_CONFIGURATION_get_value_string (cfg, "PATHS", + "SERVICEHOME", + &service_home)); + GNUNET_snprintf (hostkey_filename, sizeof (hostkey_filename), "%s/.hostkey", + service_home); + GNUNET_free (service_home); + fd = GNUNET_DISK_file_open (hostkey_filename, + GNUNET_DISK_OPEN_CREATE | GNUNET_DISK_OPEN_WRITE, + GNUNET_DISK_PERM_USER_READ + | GNUNET_DISK_PERM_USER_WRITE); + if (NULL == fd) + { + GNUNET_break (0); + return NULL; } - else - { - if (NULL == ctx->d2->hello) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "didn't have %s's HELLO but th wasn't NULL, not trying!!\n", - ctx->d2->shortname); - } + if (GNUNET_TESTING_HOSTKEYFILESIZE != + GNUNET_DISK_file_write (fd, system->hostkeys_data + + (key_number * GNUNET_TESTING_HOSTKEYFILESIZE), + GNUNET_TESTING_HOSTKEYFILESIZE)) + { + GNUNET_asprintf (&emsg_, + _("Failed to write hostkey file for peer %u: %s\n"), + (unsigned int) key_number, + STRERROR (errno)); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "%s", emsg_); + if (NULL != emsg) + *emsg = emsg_; + else + GNUNET_free (emsg_); + GNUNET_DISK_file_close (fd); + return NULL; } - - if (ctx->send_hello == GNUNET_YES) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Sending %s's HELLO to %s\n", - ctx->d1->shortname, ctx->d2->shortname); - ctx->d1th = - GNUNET_TRANSPORT_connect (ctx->d1->cfg, &ctx->d1->id, ctx->d1, NULL, - NULL, NULL); - if (ctx->d1th == NULL) - { - GNUNET_CORE_disconnect (ctx->d1core); - GNUNET_free (ctx); - if (NULL != ctx->cb) - ctx->cb (ctx->cb_cls, &ctx->d1->id, &ctx->d2->id, 0, ctx->d1->cfg, - ctx->d2->cfg, ctx->d1, ctx->d2, - _("Failed to connect to transport service!\n")); - return; - } - GNUNET_assert (GNUNET_SCHEDULER_NO_TASK == ctx->hello_send_task); - ctx->hello_send_task = GNUNET_SCHEDULER_add_now (&send_hello, ctx); + GNUNET_DISK_file_close (fd); + GNUNET_assert (GNUNET_OK == + GNUNET_CONFIGURATION_get_value_string + (cfg, "PATHS", "DEFAULTCONFIG", &config_filename)); + if (GNUNET_OK != GNUNET_CONFIGURATION_write (cfg, config_filename)) + { + GNUNET_asprintf (&emsg_, + _("Failed to write configuration file `%s' for peer %u: %s\n"), + config_filename, + (unsigned int) key_number, + STRERROR (errno)); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "%s", emsg_); + if (NULL != emsg) + *emsg = emsg_; + else + GNUNET_free (emsg_); + GNUNET_free (config_filename); + return NULL; } - else + peer = GNUNET_malloc (sizeof (struct GNUNET_TESTING_Peer)); + peer->cfgfile = config_filename; /* Free in peer_destroy */ + libexec_binary = GNUNET_OS_get_libexec_binary_path ("gnunet-service-arm"); + if (GNUNET_SYSERR == GNUNET_CONFIGURATION_get_value_string(cfg, "arm", "PREFIX", &peer->main_binary)) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Trying to reconnect %s to %s\n", - ctx->d1->shortname, ctx->d2->shortname); - GNUNET_TRANSPORT_try_connect (ctx->d1th, &ctx->d2->id); + /* No prefix */ + GNUNET_asprintf(&peer->main_binary, "%s", libexec_binary); + peer->args = strdup (""); } - ctx->timeout_task = - GNUNET_SCHEDULER_add_delayed (ctx->relative_timeout, - ¬ify_connect_result, ctx); + else + peer->args = strdup (libexec_binary); + peer->system = system; + peer->key_number = key_number; + GNUNET_free (libexec_binary); + return peer; } + /** - * Iterator for currently known peers, to ensure - * that we don't try to send duplicate connect - * requests to core. - * - * @param cls our "struct GNUNET_TESTING_ConnectContext" - * @param peer identity of the peer that has connected, - * NULL when iteration has finished - * @param atsi performance information - * @param atsi_count number of records in 'atsi' + * Obtain the peer identity from a peer handle. * + * @param peer peer handle for which we want the peer's identity + * @param id identifier for the daemon, will be set */ -static void -core_initial_iteration (void *cls, const struct GNUNET_PeerIdentity *peer, - const struct GNUNET_ATS_Information *atsi, - unsigned int atsi_count) +void +GNUNET_TESTING_peer_get_identity (const struct GNUNET_TESTING_Peer *peer, + struct GNUNET_PeerIdentity *id) { - struct GNUNET_TESTING_ConnectContext *ctx = cls; + GNUNET_CRYPTO_rsa_key_free (GNUNET_TESTING_hostkey_get (peer->system, + peer->key_number, + id)); +} - if ((peer != NULL) && - (0 == memcmp (&ctx->d2->id, peer, sizeof (struct GNUNET_PeerIdentity)))) - { - ctx->connected = GNUNET_YES; - ctx->distance = 0; /* FIXME: distance */ - return; - } - if (peer != NULL) - return; /* ignore other peers */ - /* peer == NULL: End of iteration over peers */ - GNUNET_assert (GNUNET_SCHEDULER_NO_TASK == ctx->timeout_task); - if (ctx->connected == GNUNET_YES) +/** + * Start the peer. + * + * @param peer peer to start + * @return GNUNET_OK on success, GNUNET_SYSERR on error (i.e. peer already running) + */ +int +GNUNET_TESTING_peer_start (struct GNUNET_TESTING_Peer *peer) +{ + if (NULL != peer->main_process) { - ctx->timeout_task = GNUNET_SCHEDULER_add_now (¬ify_connect_result, ctx); - return; + GNUNET_break (0); + return GNUNET_SYSERR; } - - /* Peer not already connected, need to schedule connect request! */ - if (ctx->d1core == NULL) + GNUNET_assert (NULL != peer->cfgfile); + peer->main_process = GNUNET_OS_start_process (PIPE_CONTROL, + GNUNET_OS_INHERIT_STD_OUT_AND_ERR, + NULL, NULL, + peer->main_binary, + peer->main_binary, + peer->args, + "-c", + peer->cfgfile, + NULL); + if (NULL == peer->main_process) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Peers are NOT connected, connecting to core!\n"); - ctx->d1core = - GNUNET_CORE_connect (ctx->d1->cfg, 1, ctx, &core_init_notify, - &connect_notify, NULL, NULL, GNUNET_NO, NULL, - GNUNET_NO, no_handlers); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Failed to start `%s': %s\n"), + peer->main_binary, + STRERROR (errno)); + return GNUNET_SYSERR; } + return GNUNET_OK; +} - if (ctx->d1core == NULL) - { - ctx->timeout_task = GNUNET_SCHEDULER_add_now (¬ify_connect_result, ctx); - return; - } - if ((NULL == ctx->d2->hello) && (ctx->d2->th == NULL)) /* Do not yet have the second peer's hello, set up a task to get it */ +/** + * Sends SIGTERM to the peer's main process + * + * @param peer the handle to the peer + * @return GNUNET_OK if successful; GNUNET_SYSERR if the main process is NULL + * or upon any error while sending SIGTERM + */ +int +GNUNET_TESTING_peer_kill (struct GNUNET_TESTING_Peer *peer) +{ + if (NULL == peer->main_process) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Don't have d2's HELLO, trying to get it!\n"); - ctx->d2->th = - GNUNET_TRANSPORT_connect (ctx->d2->cfg, &ctx->d2->id, NULL, NULL, NULL, - NULL); - if (ctx->d2->th == NULL) - { - GNUNET_CORE_disconnect (ctx->d1core); - ctx->d1core = NULL; - ctx->timeout_task = - GNUNET_SCHEDULER_add_now (¬ify_connect_result, ctx); - return; - } - ctx->d2->ghh = - GNUNET_TRANSPORT_get_hello (ctx->d2->th, &process_hello, ctx->d2); + GNUNET_break (0); + return GNUNET_SYSERR; } + return (0 == GNUNET_OS_process_kill (peer->main_process, SIGTERM)) ? + GNUNET_OK : GNUNET_SYSERR; +} + + +/** + * Waits for a peer to terminate. The peer's main process will also be destroyed. + * + * @param peer the handle to the peer + * @return GNUNET_OK if successful; GNUNET_SYSERR if the main process is NULL + * or upon any error while waiting + */ +int +GNUNET_TESTING_peer_wait (struct GNUNET_TESTING_Peer *peer) +{ + int ret; - if (ctx->send_hello == GNUNET_YES) + if (NULL == peer->main_process) { - ctx->d1th = - GNUNET_TRANSPORT_connect (ctx->d1->cfg, &ctx->d1->id, ctx->d1, NULL, - NULL, NULL); - if (ctx->d1th == NULL) - { - GNUNET_CORE_disconnect (ctx->d1core); - ctx->d1core = NULL; - ctx->timeout_task = - GNUNET_SCHEDULER_add_now (¬ify_connect_result, ctx); - return; - } - GNUNET_assert (GNUNET_SCHEDULER_NO_TASK == ctx->hello_send_task); - ctx->hello_send_task = GNUNET_SCHEDULER_add_now (&send_hello, ctx); + GNUNET_break (0); + return GNUNET_SYSERR; } + ret = GNUNET_OS_process_wait (peer->main_process); + GNUNET_OS_process_destroy (peer->main_process); + peer->main_process = NULL; + return ret; +} - ctx->timeout_task = - GNUNET_SCHEDULER_add_delayed (ctx->relative_timeout, - ¬ify_connect_result, ctx); +/** + * Stop the peer. + * + * @param peer peer to stop + * @return GNUNET_OK on success, GNUNET_SYSERR on error + */ +int +GNUNET_TESTING_peer_stop (struct GNUNET_TESTING_Peer *peer) +{ + if (GNUNET_SYSERR == GNUNET_TESTING_peer_kill (peer)) + return GNUNET_SYSERR; + if (GNUNET_SYSERR == GNUNET_TESTING_peer_wait (peer)) + return GNUNET_SYSERR; + return GNUNET_OK; } /** - * Establish a connection between two GNUnet daemons. The daemons - * must both be running and not be stopped until either the - * 'cb' callback is called OR the connection request has been - * explicitly cancelled. + * Destroy the peer. Releases resources locked during peer configuration. + * If the peer is still running, it will be stopped AND a warning will be + * printed (users of the API should stop the peer explicitly first). * - * @param d1 handle for the first daemon - * @param d2 handle for the second daemon - * @param timeout how long is the connection attempt - * allowed to take? - * @param max_connect_attempts how many times should we try to reconnect - * (within timeout) - * @param send_hello GNUNET_YES to send the HELLO, GNUNET_NO to assume - * the HELLO has already been exchanged - * @param cb function to call at the end - * @param cb_cls closure for cb - * @return handle to cancel the request + * @param peer peer to destroy */ -struct GNUNET_TESTING_ConnectContext * -GNUNET_TESTING_daemons_connect (struct GNUNET_TESTING_Daemon *d1, - struct GNUNET_TESTING_Daemon *d2, - struct GNUNET_TIME_Relative timeout, - unsigned int max_connect_attempts, - int send_hello, - GNUNET_TESTING_NotifyConnection cb, - void *cb_cls) +void +GNUNET_TESTING_peer_destroy (struct GNUNET_TESTING_Peer *peer) { - struct GNUNET_TESTING_ConnectContext *ctx; - - if ((d1->running == GNUNET_NO) || (d2->running == GNUNET_NO)) + if (NULL != peer->main_process) { - if (NULL != cb) - cb (cb_cls, &d1->id, &d2->id, 0, d1->cfg, d2->cfg, d1, d2, - _("Peers are not fully running yet, can not connect!\n")); - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Peers are not up!\n"); - return NULL; + GNUNET_break (0); + GNUNET_TESTING_peer_stop (peer); } + GNUNET_free (peer->cfgfile); + GNUNET_free (peer->main_binary); + GNUNET_free (peer->args); + GNUNET_free (peer); +} + + +/** + * Start a single peer and run a test using the testing library. + * Starts a peer using the given configuration and then invokes the + * given callback. This function ALSO initializes the scheduler loop + * and should thus be called directly from "main". The testcase + * should self-terminate by invoking 'GNUNET_SCHEDULER_shutdown'. + * + * @param testdir only the directory name without any path. This is used for + * all service homes; the directory will be created in a temporary + * location depending on the underlying OS + * @param cfgfilename name of the configuration file to use; + * use NULL to only run with defaults + * @param tm main function of the testcase + * @param tm_cls closure for 'tm' + * @return 0 on success, 1 on error + */ +int +GNUNET_TESTING_peer_run (const char *testdir, + const char *cfgfilename, + GNUNET_TESTING_TestMain tm, + void *tm_cls) +{ + return GNUNET_TESTING_service_run (testdir, "arm", + cfgfilename, tm, tm_cls); +} + + +/** + * Structure for holding service data + */ +struct ServiceContext +{ + /** + * The configuration of the peer in which the service is run + */ + const struct GNUNET_CONFIGURATION_Handle *cfg; + + /** + * Callback to signal service startup + */ + GNUNET_TESTING_TestMain tm; + + /** + * The peer in which the service is run. + */ + struct GNUNET_TESTING_Peer *peer; + + /** + * Closure for the above callback + */ + void *tm_cls; +}; + + +/** + * Callback to be called when SCHEDULER has been started + * + * @param cls the ServiceContext + * @param tc the TaskContext + */ +static void +service_run_main (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct ServiceContext *sc = cls; - ctx = GNUNET_malloc (sizeof (struct GNUNET_TESTING_ConnectContext)); - ctx->d1 = d1; - ctx->d2 = d2; - ctx->timeout_hello = - GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MILLISECONDS, 500); - ctx->relative_timeout = - GNUNET_TIME_relative_divide (timeout, max_connect_attempts); - ctx->cb = cb; - ctx->cb_cls = cb_cls; - ctx->connect_attempts = max_connect_attempts; - ctx->connected = GNUNET_NO; - ctx->send_hello = send_hello; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Asked to connect peer %s to peer %s\n", - d1->shortname, d2->shortname); - /* Core is up! Iterate over all _known_ peers first to check if we are already connected to the peer! */ - GNUNET_assert (NULL != - GNUNET_CORE_is_peer_connected (ctx->d1->cfg, &ctx->d2->id, - &core_initial_iteration, ctx)); - return ctx; + sc->tm (sc->tm_cls, sc->cfg, sc->peer); } /** - * Cancel an attempt to connect two daemons. + * Start a single service (no ARM, except of course if the given + * service name is 'arm') and run a test using the testing library. + * Starts a service using the given configuration and then invokes the + * given callback. This function ALSO initializes the scheduler loop + * and should thus be called directly from "main". The testcase + * should self-terminate by invoking 'GNUNET_SCHEDULER_shutdown'. * - * @param cc connect context + * This function is useful if the testcase is for a single service + * and if that service doesn't itself depend on other services. + * + * @param testdir only the directory name without any path. This is used for + * all service homes; the directory will be created in a temporary + * location depending on the underlying OS + * @param service_name name of the service to run + * @param cfgfilename name of the configuration file to use; + * use NULL to only run with defaults + * @param tm main function of the testcase + * @param tm_cls closure for 'tm' + * @return 0 on success, 1 on error */ -void -GNUNET_TESTING_daemons_connect_cancel (struct GNUNET_TESTING_ConnectContext *cc) +int +GNUNET_TESTING_service_run (const char *testdir, + const char *service_name, + const char *cfgfilename, + GNUNET_TESTING_TestMain tm, + void *tm_cls) { - if (GNUNET_SCHEDULER_NO_TASK != cc->timeout_task) - { - GNUNET_SCHEDULER_cancel (cc->timeout_task); - cc->timeout_task = GNUNET_SCHEDULER_NO_TASK; + struct ServiceContext sc; + struct GNUNET_TESTING_System *system; + struct GNUNET_TESTING_Peer *peer; + struct GNUNET_CONFIGURATION_Handle *cfg; + char *binary; + char *libexec_binary; + + GNUNET_log_setup (testdir, "WARNING", NULL); + system = GNUNET_TESTING_system_create (testdir, "127.0.0.1", NULL); + if (NULL == system) + return 1; + cfg = GNUNET_CONFIGURATION_create (); + if (GNUNET_OK != GNUNET_CONFIGURATION_load (cfg, cfgfilename)) + { + LOG (GNUNET_ERROR_TYPE_ERROR, + _("Failed to load configuration from %s\n"), cfgfilename); + GNUNET_CONFIGURATION_destroy (cfg); + GNUNET_TESTING_system_destroy (system, GNUNET_YES); + return 1; + } + peer = GNUNET_TESTING_peer_configure (system, cfg, 0, NULL, NULL); + if (NULL == peer) + { + GNUNET_CONFIGURATION_destroy (cfg); + hostkeys_unload (system); + GNUNET_TESTING_system_destroy (system, GNUNET_YES); + return 1; + } + GNUNET_free (peer->main_binary); + GNUNET_free (peer->args); + GNUNET_asprintf (&binary, "gnunet-service-%s", service_name); + libexec_binary = GNUNET_OS_get_libexec_binary_path (binary); + if (GNUNET_SYSERR == GNUNET_CONFIGURATION_get_value_string(cfg, service_name, "PREFIX", &peer->main_binary)) + { + /* No prefix */ + GNUNET_asprintf(&peer->main_binary, "%s", libexec_binary); + peer->args = strdup (""); } - if (GNUNET_SCHEDULER_NO_TASK != cc->hello_send_task) - { - GNUNET_SCHEDULER_cancel (cc->hello_send_task); - cc->hello_send_task = GNUNET_SCHEDULER_NO_TASK; - } - if (NULL != cc->d1core) - { - GNUNET_CORE_disconnect (cc->d1core); - cc->d1core = NULL; - } - if (NULL != cc->d1th) - { - GNUNET_TRANSPORT_disconnect (cc->d1th); - cc->d1th = NULL; - } - GNUNET_free (cc); + else + peer->args = strdup (libexec_binary); + + GNUNET_free (libexec_binary); + GNUNET_free (binary); + if (GNUNET_OK != GNUNET_TESTING_peer_start (peer)) + { + GNUNET_TESTING_peer_destroy (peer); + GNUNET_CONFIGURATION_destroy (cfg); + GNUNET_TESTING_system_destroy (system, GNUNET_YES); + return 1; + } + sc.cfg = cfg; + sc.tm = tm; + sc.tm_cls = tm_cls; + sc.peer = peer; + GNUNET_SCHEDULER_run (&service_run_main, &sc); /* Scheduler loop */ + if ((NULL != peer->main_process) && + (GNUNET_OK != GNUNET_TESTING_peer_stop (peer))) + { + GNUNET_TESTING_peer_destroy (peer); + GNUNET_CONFIGURATION_destroy (cfg); + GNUNET_TESTING_system_destroy (system, GNUNET_YES); + return 1; + } + GNUNET_TESTING_peer_destroy (peer); + GNUNET_CONFIGURATION_destroy (cfg); + GNUNET_TESTING_system_destroy (system, GNUNET_YES); + return 0; +} + + +/** + * Sometimes we use the binary name to determine which specific + * test to run. In those cases, the string after the last "_" + * in 'argv[0]' specifies a string that determines the configuration + * file or plugin to use. + * + * This function returns the respective substring, taking care + * of issues such as binaries ending in '.exe' on W32. + * + * @param argv0 the name of the binary + * @return string between the last '_' and the '.exe' (or the end of the string), + * NULL if argv0 has no '_' + */ +char * +GNUNET_TESTING_get_testname_from_underscore (const char *argv0) +{ + size_t slen = strlen (argv0) + 1; + char sbuf[slen]; + char *ret; + char *dot; + + memcpy (sbuf, argv0, slen); + ret = strrchr (sbuf, '_'); + if (NULL == ret) + return NULL; + ret++; /* skip underscore */ + dot = strchr (ret, '.'); + if (NULL != dot) + *dot = '\0'; + return GNUNET_strdup (ret); } diff --git a/src/testing/testing_group.c b/src/testing/testing_group.c deleted file mode 100644 index 75c0e61..0000000 --- a/src/testing/testing_group.c +++ /dev/null @@ -1,7038 +0,0 @@ -/* - This file is part of GNUnet - (C) 2008, 2009 Christian Grothoff (and other contributing authors) - - GNUnet is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published - by the Free Software Foundation; either version 3, or (at your - option) any later version. - - GNUnet is distributed in the hope that it will be useful, but - WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - General Public License for more details. - - You should have received a copy of the GNU General Public License - along with GNUnet; see the file COPYING. If not, write to the - Free Software Foundation, Inc., 59 Temple Place - Suite 330, - Boston, MA 02111-1307, USA. - */ - -/** - * @file testing/testing_group.c - * @brief convenience API for writing testcases for GNUnet - * @author Nathan Evans - * @author Christian Grothoff - */ -#include "platform.h" -#include "gnunet_constants.h" -#include "gnunet_arm_service.h" -#include "gnunet_testing_lib.h" -#include "gnunet_core_service.h" - -#define USE_START_HELPER GNUNET_YES - -#define OLD 1 - -/* Before connecting peers, send all of the HELLOs */ -#define USE_SEND_HELLOS GNUNET_NO - -#define TOPOLOGY_HACK GNUNET_YES - - -/** - * Lowest port used for GNUnet testing. Should be high enough to not - * conflict with other applications running on the hosts but be low - * enough to not conflict with client-ports (typically starting around - * 32k). - */ -#define LOW_PORT 12000 - -/** - * Highest port used for GNUnet testing. Should be low enough to not - * conflict with the port range for "local" ports (client apps; see - * /proc/sys/net/ipv4/ip_local_port_range on Linux for example). - */ -#define HIGH_PORT 56000 - -/* Maximum time to delay connect attempt */ -#define MAX_CONNECT_DELAY 300 - -/** - * Which list of peers do we need to modify? - */ -enum PeerLists -{ - /** Modify allowed peers */ - ALLOWED, - - /** Modify connect peers */ - CONNECT, - - /** Modify blacklist peers */ - BLACKLIST, - - /** Modify workingset peers */ - WORKING_SET -}; - -/** - * Prototype of a function called whenever two peers would be connected - * in a certain topology. - */ -typedef unsigned int (*GNUNET_TESTING_ConnectionProcessor) (struct - GNUNET_TESTING_PeerGroup - * pg, - unsigned int first, - unsigned int second, - enum PeerLists list, - unsigned int check); - -/** - * Context for handling churning a peer group - */ -struct ChurnContext -{ - /** - * The peergroup we are dealing with. - */ - struct GNUNET_TESTING_PeerGroup *pg; - - /** - * Name of the service to churn on/off, NULL - * to churn entire peer. - */ - char *service; - - /** - * Callback used to notify of churning finished - */ - GNUNET_TESTING_NotifyCompletion cb; - - /** - * Closure for callback - */ - void *cb_cls; - - /** - * Number of peers that still need to be started - */ - unsigned int num_to_start; - - /** - * Number of peers that still need to be stopped - */ - unsigned int num_to_stop; - - /** - * Number of peers that failed to start - */ - unsigned int num_failed_start; - - /** - * Number of peers that failed to stop - */ - unsigned int num_failed_stop; -}; - -struct RestartContext -{ - /** - * The group of peers being restarted - */ - struct GNUNET_TESTING_PeerGroup *peer_group; - - /** - * How many peers have been restarted thus far - */ - unsigned int peers_restarted; - - /** - * How many peers got an error when restarting - */ - unsigned int peers_restart_failed; - - /** - * The function to call once all peers have been restarted - */ - GNUNET_TESTING_NotifyCompletion callback; - - /** - * Closure for callback function - */ - void *callback_cls; - -}; - -struct SendHelloContext -{ - /** - * Global handle to the peer group. - */ - struct GNUNET_TESTING_PeerGroup *pg; - - /** - * The data about this specific peer. - */ - struct PeerData *peer; - - /** - * The next HELLO that needs sent to this peer. - */ - struct PeerConnection *peer_pos; - - /** - * Are we connected to CORE yet? - */ - unsigned int core_ready; - - /** - * How many attempts should we make for failed connections? - */ - unsigned int connect_attempts; - - /** - * Task for scheduling core connect requests to be sent. - */ - GNUNET_SCHEDULER_TaskIdentifier core_connect_task; -}; - -struct ShutdownContext -{ - struct GNUNET_TESTING_PeerGroup *pg; - /** - * Total peers to wait for - */ - unsigned int total_peers; - - /** - * Number of peers successfully shut down - */ - unsigned int peers_down; - - /** - * Number of peers failed to shut down - */ - unsigned int peers_failed; - - /** - * Number of peers we have started shutting - * down. If too many, wait on them. - */ - unsigned int outstanding; - - /** - * Timeout for shutdown. - */ - struct GNUNET_TIME_Relative timeout; - - /** - * Callback to call when all peers either - * shutdown or failed to shutdown - */ - GNUNET_TESTING_NotifyCompletion cb; - - /** - * Closure for cb - */ - void *cb_cls; - - /** - * Should we delete all of the files from the peers? - */ - int delete_files; -}; - -/** - * Individual shutdown context for a particular peer. - */ -struct PeerShutdownContext -{ - /** - * Pointer to the high level shutdown context. - */ - struct ShutdownContext *shutdown_ctx; - - /** - * The daemon handle for the peer to shut down. - */ - struct GNUNET_TESTING_Daemon *daemon; -}; - -/** - * Individual shutdown context for a particular peer. - */ -struct PeerRestartContext -{ - /** - * Pointer to the high level restart context. - */ - struct ChurnRestartContext *churn_restart_ctx; - - /** - * The daemon handle for the peer to shut down. - */ - struct GNUNET_TESTING_Daemon *daemon; -}; - -struct ServiceStartContext -{ - struct GNUNET_TESTING_PeerGroup *pg; - unsigned int remaining; - GNUNET_TESTING_NotifyCompletion cb; - unsigned int outstanding; - char *service; - struct GNUNET_TIME_Relative timeout; - void *cb_cls; -}; - -/** - * Individual shutdown context for a particular peer. - */ -struct PeerServiceStartContext -{ - /** - * Pointer to the high level start context. - */ - struct ServiceStartContext *start_ctx; - - /** - * The daemon handle for the peer to start the service on. - */ - struct GNUNET_TESTING_Daemon *daemon; -}; - -struct CreateTopologyContext -{ - - /** - * Function to call with number of connections - */ - GNUNET_TESTING_NotifyConnections cont; - - /** - * Closure for connection notification - */ - void *cls; -}; - -enum States -{ - /** Waiting to read number of peers */ - NUM_PEERS, - - /** Should find next peer index */ - PEER_INDEX, - - /** Should find colon */ - COLON, - - /** Should read other peer index, space, or endline */ - OTHER_PEER_INDEX -}; - -#if OLD -struct PeerConnection -{ - /** - * Doubly Linked list - */ - struct PeerConnection *prev; - - /* - * Doubly Linked list - */ - struct PeerConnection *next; - - /* - * Index of daemon in pg->peers - */ - uint32_t index; - -}; -#endif - -struct InternalStartContext -{ - /** - * Pointer to peerdata - */ - struct PeerData *peer; - - /** - * Timeout for peer startup - */ - struct GNUNET_TIME_Relative timeout; - - /** - * Client callback for hostkey notification - */ - GNUNET_TESTING_NotifyHostkeyCreated hostkey_callback; - - /** - * Closure for hostkey_callback - */ - void *hostkey_cls; - - /** - * Client callback for peer start notification - */ - GNUNET_TESTING_NotifyDaemonRunning start_cb; - - /** - * Closure for cb - */ - void *start_cb_cls; - - /** - * Hostname, where to start the peer - */ - const char *hostname; - - /** - * Username to use when connecting to the - * host via ssh. - */ - const char *username; - - /** - * Pointer to starting memory location of a hostkey - */ - const char *hostkey; - - /** - * Port to use for ssh. - */ - uint16_t sshport; - -}; - -struct ChurnRestartContext -{ - /** - * PeerGroup that we are working with. - */ - struct GNUNET_TESTING_PeerGroup *pg; - - /** - * Number of restarts currently in flight. - */ - unsigned int outstanding; - - /** - * Handle to the underlying churn context. - */ - struct ChurnContext *churn_ctx; - - /** - * How long to allow the operation to take. - */ - struct GNUNET_TIME_Relative timeout; -}; - -struct OutstandingSSH -{ - struct OutstandingSSH *next; - - struct OutstandingSSH *prev; - - /** - * Number of current ssh connections. - */ - uint32_t outstanding; - - /** - * The hostname of this peer. - */ - const char *hostname; -}; - -/** - * Data we keep per peer. - */ -struct PeerData -{ - /** - * (Initial) configuration of the host. - * (initial because clients could change - * it and we would not know about those - * updates). - */ - struct GNUNET_CONFIGURATION_Handle *cfg; - - /** - * Handle for controlling the daemon. - */ - struct GNUNET_TESTING_Daemon *daemon; - - /** - * The peergroup this peer belongs to. - */ - struct GNUNET_TESTING_PeerGroup *pg; - -#if OLD - /** - * Linked list of allowed peer connections. - */ - struct PeerConnection *allowed_peers_head; - - /** - * Linked list of allowed peer connections. - */ - struct PeerConnection *allowed_peers_tail; - - /** - * Linked list of blacklisted peer connections. - */ - struct PeerConnection *blacklisted_peers_head; - - /** - * Linked list of blacklisted peer connections. - */ - struct PeerConnection *blacklisted_peers_tail; - - /** - * Linked list of connect peer connections. - */ - struct PeerConnection *connect_peers_head; - - /** - * Linked list of connect peer connections. - */ - struct PeerConnection *connect_peers_tail; - - /** - * Linked list of connect peer connections. - */ - struct PeerConnection *connect_peers_working_set_head; - - /** - * Linked list of connect peer connections. - */ - struct PeerConnection *connect_peers_working_set_tail; - -#else - /** - * Hash map of allowed peer connections (F2F created topology) - */ - struct GNUNET_CONTAINER_MultiHashMap *allowed_peers; - - /** - * Hash map of blacklisted peers - */ - struct GNUNET_CONTAINER_MultiHashMap *blacklisted_peers; - - /** - * Hash map of peer connections - */ - struct GNUNET_CONTAINER_MultiHashMap *connect_peers; - - /** - * Temporary hash map of peer connections - */ - struct GNUNET_CONTAINER_MultiHashMap *connect_peers_working_set; -#endif - - /** - * Temporary variable for topology creation, should be reset before - * creating any topology so the count is valid once finished. - */ - int num_connections; - - /** - * Context to keep track of peers being started, to - * stagger hostkey generation and peer startup. - */ - struct InternalStartContext internal_context; - - /** - * Task ID for the queued internal_continue_startup task - */ - GNUNET_SCHEDULER_TaskIdentifier startup_task; - -}; - -/** - * Linked list of per-host data. - */ -struct HostData -{ - /** - * Name of the host. - */ - char *hostname; - - /** - * SSH username to use when connecting to this host. - */ - char *username; - - /** - * SSH port to use when connecting to this host. - */ - uint16_t sshport; - - /** - * Lowest port that we have not yet used - * for GNUnet. - */ - uint16_t minport; -}; - -struct TopologyIterateContext -{ - /** - * The peergroup we are working with. - */ - struct GNUNET_TESTING_PeerGroup *pg; - - /** - * Callback for notifying of two connected peers. - */ - GNUNET_TESTING_NotifyTopology topology_cb; - - /** - * Closure for topology_cb - */ - void *cls; - - /** - * Number of peers currently connected to. - */ - unsigned int connected; - - /** - * Number of peers we have finished iterating. - */ - unsigned int completed; - - /** - * Number of peers total. - */ - unsigned int total; -}; - -struct StatsIterateContext -{ - /** - * The peergroup that we are dealing with. - */ - struct GNUNET_TESTING_PeerGroup *pg; - - /** - * Continuation to call once all stats information has been retrieved. - */ - GNUNET_STATISTICS_Callback cont; - - /** - * Proc function to call on each value received. - */ - GNUNET_TESTING_STATISTICS_Iterator proc; - - /** - * Closure for topology_cb - */ - void *cls; - - /** - * Number of peers currently connected to. - */ - unsigned int connected; - - /** - * Number of peers we have finished iterating. - */ - unsigned int completed; - - /** - * Number of peers total. - */ - unsigned int total; -}; - -struct CoreContext -{ - void *iter_context; - struct GNUNET_TESTING_Daemon *daemon; -}; - -struct StatsCoreContext -{ - void *iter_context; - struct GNUNET_TESTING_Daemon *daemon; - /** - * Handle to the statistics service. - */ - struct GNUNET_STATISTICS_Handle *stats_handle; - - /** - * Handle for getting statistics. - */ - struct GNUNET_STATISTICS_GetHandle *stats_get_handle; -}; - -struct ConnectTopologyContext -{ - /** - * How many connections are left to create. - */ - unsigned int remaining_connections; - - /** - * Handle to group of peers. - */ - struct GNUNET_TESTING_PeerGroup *pg; - - /** - * How long to try this connection before timing out. - */ - struct GNUNET_TIME_Relative connect_timeout; - - /** - * How many times to retry connecting the two peers. - */ - unsigned int connect_attempts; - - /** - * Temp value set for each iteration. - */ - //struct PeerData *first; - - /** - * Notification that all peers are connected. - */ - GNUNET_TESTING_NotifyCompletion notify_connections_done; - - /** - * Closure for notify. - */ - void *notify_cls; -}; - -struct ConnectContext; - -/** - * Handle to a group of GNUnet peers. - */ -struct GNUNET_TESTING_PeerGroup -{ - /** - * Configuration template. - */ - const struct GNUNET_CONFIGURATION_Handle *cfg; - - struct ConnectContext *cc_head; - - struct ConnectContext *cc_tail; - - /** - * Function to call on each started daemon. - */ - //GNUNET_TESTING_NotifyDaemonRunning cb; - - /** - * Closure for cb. - */ - //void *cb_cls; - - /* - * Function to call on each topology connection created - */ - GNUNET_TESTING_NotifyConnection notify_connection; - - /* - * Callback for notify_connection - */ - void *notify_connection_cls; - - /** - * Array of information about hosts. - */ - struct HostData *hosts; - - /** - * Number of hosts (size of HostData) - */ - unsigned int num_hosts; - - /** - * Array of "total" peers. - */ - struct PeerData *peers; - - /** - * Number of peers in this group. - */ - unsigned int total; - - /** - * At what time should we fail the peer startup process? - */ - struct GNUNET_TIME_Absolute max_timeout; - - /** - * How many peers are being started right now? - */ - unsigned int starting; - - /** - * How many peers have already been started? - */ - unsigned int started; - - /** - * Number of possible connections to peers - * at a time. - */ - unsigned int max_outstanding_connections; - - /** - * Number of ssh connections to peers (max). - */ - unsigned int max_concurrent_ssh; - - /** - * Number of connects we are waiting on, allows us to rate limit - * connect attempts. - */ - unsigned int outstanding_connects; - - /** - * Number of HELLOs we have yet to send. - */ - unsigned int remaining_hellos; - - /** - * How many connects have already been scheduled? - */ - unsigned int total_connects_scheduled; - - /** - * Hostkeys loaded from a file. - */ - char *hostkey_data; - - /** - * Head of DLL to keep track of the number of outstanding - * ssh connections per peer. - */ - struct OutstandingSSH *ssh_head; - - /** - * Tail of DLL to keep track of the number of outstanding - * ssh connections per peer. - */ - struct OutstandingSSH *ssh_tail; - - /** - * Stop scheduling peers connecting. - */ - unsigned int stop_connects; - - /** - * Connection context for peer group. - */ - struct ConnectTopologyContext ct_ctx; -}; - -struct UpdateContext -{ - /** - * The altered configuration. - */ - struct GNUNET_CONFIGURATION_Handle *ret; - - /** - * The original configuration to alter. - */ - const struct GNUNET_CONFIGURATION_Handle *orig; - - /** - * The hostname that this peer will run on. - */ - const char *hostname; - - /** - * The next possible port to assign. - */ - unsigned int nport; - - /** - * Unique number for unix domain sockets. - */ - unsigned int upnum; - - /** - * Unique number for this peer/host to offset - * things that are grouped by host. - */ - unsigned int fdnum; -}; - -struct ConnectContext -{ - - struct ConnectContext *next; - - struct ConnectContext *prev; - - /** - * Index of peer to connect second to. - */ - uint32_t first_index; - - /** - * Index of peer to connect first to. - */ - uint32_t second_index; - - /** - * Task associated with the attempt to connect. - */ - GNUNET_SCHEDULER_TaskIdentifier task; - - /** - * Context in 'testing.c', to cancel connection attempt. - */ - struct GNUNET_TESTING_ConnectContext *cc; - - /** - * Higher level topology connection context. - */ - struct ConnectTopologyContext *ct_ctx; - - /** - * Whether this connection has been accounted for in the schedule_connect call. - */ - int counted; -}; - -struct UnblacklistContext -{ - /** - * The peergroup - */ - struct GNUNET_TESTING_PeerGroup *pg; - - /** - * uid of the first peer - */ - uint32_t first_uid; -}; - -struct RandomContext -{ - /** - * The peergroup - */ - struct GNUNET_TESTING_PeerGroup *pg; - - /** - * uid of the first peer - */ - uint32_t first_uid; - - /** - * Peer data for first peer. - */ - struct PeerData *first; - - /** - * Random percentage to use - */ - double percentage; -}; - -struct MinimumContext -{ - /** - * The peergroup - */ - struct GNUNET_TESTING_PeerGroup *pg; - - /** - * uid of the first peer - */ - uint32_t first_uid; - - /** - * Peer data for first peer. - */ - struct PeerData *first; - - /** - * Number of conns per peer - */ - unsigned int num_to_add; - - /** - * Permuted array of all possible connections. Only add the Nth - * peer if it's in the Nth position. - */ - unsigned int *pg_array; - - /** - * What number is the current element we are iterating over? - */ - unsigned int current; -}; - -struct DFSContext -{ - /** - * The peergroup - */ - struct GNUNET_TESTING_PeerGroup *pg; - - /** - * uid of the first peer - */ - uint32_t first_uid; - - /** - * uid of the second peer - */ - uint32_t second_uid; - - /** - * Peer data for first peer. - */ - struct PeerData *first; - - /** - * Which peer has been chosen as the one to add? - */ - unsigned int chosen; - - /** - * What number is the current element we are iterating over? - */ - unsigned int current; -}; - -/** - * Simple struct to keep track of progress, and print a - * nice little percentage meter for long running tasks. - */ -struct ProgressMeter -{ - unsigned int total; - - unsigned int modnum; - - unsigned int dotnum; - - unsigned int completed; - - int print; - - char *startup_string; -}; - -#if !OLD -/** - * Convert unique ID to hash code. - * - * @param uid unique ID to convert - * @param hash set to uid (extended with zeros) - */ -static void -hash_from_uid (uint32_t uid, GNUNET_HashCode * hash) -{ - memset (hash, 0, sizeof (GNUNET_HashCode)); - *((uint32_t *) hash) = uid; -} - -/** - * Convert hash code to unique ID. - * - * @param uid unique ID to convert - * @param hash set to uid (extended with zeros) - */ -static void -uid_from_hash (const GNUNET_HashCode * hash, uint32_t * uid) -{ - memcpy (uid, hash, sizeof (uint32_t)); -} -#endif - -#if USE_SEND_HELLOS -static struct GNUNET_CORE_MessageHandler no_handlers[] = { - {NULL, 0, 0} -}; -#endif - -/** - * Create a meter to keep track of the progress of some task. - * - * @param total the total number of items to complete - * @param start_string a string to prefix the meter with (if printing) - * @param print GNUNET_YES to print the meter, GNUNET_NO to count - * internally only - * - * @return the progress meter - */ -static struct ProgressMeter * -create_meter (unsigned int total, char *start_string, int print) -{ - struct ProgressMeter *ret; - - ret = GNUNET_malloc (sizeof (struct ProgressMeter)); - ret->print = print; - ret->total = total; - ret->modnum = total / 4; - if (ret->modnum == 0) /* Divide by zero check */ - ret->modnum = 1; - ret->dotnum = (total / 50) + 1; - if (start_string != NULL) - ret->startup_string = GNUNET_strdup (start_string); - else - ret->startup_string = GNUNET_strdup (""); - - return ret; -} - -/** - * Update progress meter (increment by one). - * - * @param meter the meter to update and print info for - * - * @return GNUNET_YES if called the total requested, - * GNUNET_NO if more items expected - */ -static int -update_meter (struct ProgressMeter *meter) -{ - if (meter->print == GNUNET_YES) - { - if (meter->completed % meter->modnum == 0) - { - if (meter->completed == 0) - { - FPRINTF (stdout, "%sProgress: [0%%", meter->startup_string); - } - else - FPRINTF (stdout, "%d%%", - (int) (((float) meter->completed / meter->total) * 100)); - } - else if (meter->completed % meter->dotnum == 0) - FPRINTF (stdout, "%s", "."); - - if (meter->completed + 1 == meter->total) - FPRINTF (stdout, "%d%%]\n", 100); - fflush (stdout); - } - meter->completed++; - - if (meter->completed == meter->total) - return GNUNET_YES; - if (meter->completed > meter->total) - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Progress meter overflow!!\n"); - return GNUNET_NO; -} - -/** - * Reset progress meter. - * - * @param meter the meter to reset - * - * @return GNUNET_YES if meter reset, - * GNUNET_SYSERR on error - */ -static int -reset_meter (struct ProgressMeter *meter) -{ - if (meter == NULL) - return GNUNET_SYSERR; - - meter->completed = 0; - return GNUNET_YES; -} - -/** - * Release resources for meter - * - * @param meter the meter to free - */ -static void -free_meter (struct ProgressMeter *meter) -{ - GNUNET_free_non_null (meter->startup_string); - GNUNET_free (meter); -} - -/** - * Get a topology from a string input. - * - * @param topology where to write the retrieved topology - * @param topology_string The string to attempt to - * get a configuration value from - * @return GNUNET_YES if topology string matched a - * known topology, GNUNET_NO if not - */ -int -GNUNET_TESTING_topology_get (enum GNUNET_TESTING_Topology *topology, - const char *topology_string) -{ - /** - * Strings representing topologies in enum - */ - static const char *topology_strings[] = { - /** - * A clique (everyone connected to everyone else). - */ - "CLIQUE", - - /** - * Small-world network (2d torus plus random links). - */ - "SMALL_WORLD", - - /** - * Small-world network (ring plus random links). - */ - "SMALL_WORLD_RING", - - /** - * Ring topology. - */ - "RING", - - /** - * 2-d torus. - */ - "2D_TORUS", - - /** - * Random graph. - */ - "ERDOS_RENYI", - - /** - * Certain percentage of peers are unable to communicate directly - * replicating NAT conditions - */ - "INTERNAT", - - /** - * Scale free topology. - */ - "SCALE_FREE", - - /** - * Straight line topology. - */ - "LINE", - - /** - * All peers are disconnected. - */ - "NONE", - - /** - * Read the topology from a file. - */ - "FROM_FILE", - - NULL - }; - - int curr = 0; - - if (topology_string == NULL) - return GNUNET_NO; - while (topology_strings[curr] != NULL) - { - if (strcasecmp (topology_strings[curr], topology_string) == 0) - { - *topology = curr; - return GNUNET_YES; - } - curr++; - } - *topology = GNUNET_TESTING_TOPOLOGY_NONE; - return GNUNET_NO; -} - -/** - * Get connect topology option from string input. - * - * @param topology_option where to write the retrieved topology - * @param topology_string The string to attempt to - * get a configuration value from - * @return GNUNET_YES if string matched a known - * topology option, GNUNET_NO if not - */ -int -GNUNET_TESTING_topology_option_get (enum GNUNET_TESTING_TopologyOption - *topology_option, - const char *topology_string) -{ - /** - * Options for connecting a topology as strings. - */ - static const char *topology_option_strings[] = { - /** - * Try to connect all peers specified in the topology. - */ - "CONNECT_ALL", - - /** - * Choose a random subset of connections to create. - */ - "CONNECT_RANDOM_SUBSET", - - /** - * Create at least X connections for each peer. - */ - "CONNECT_MINIMUM", - - /** - * Using a depth first search, create one connection - * per peer. If any are missed (graph disconnected) - * start over at those peers until all have at least one - * connection. - */ - "CONNECT_DFS", - - /** - * Find the N closest peers to each allowed peer in the - * topology and make sure a connection to those peers - * exists in the connect topology. - */ - "CONNECT_CLOSEST", - - /** - * No options specified. - */ - "CONNECT_NONE", - - NULL - }; - int curr = 0; - - if (topology_string == NULL) - return GNUNET_NO; - while (NULL != topology_option_strings[curr]) - { - if (strcasecmp (topology_option_strings[curr], topology_string) == 0) - { - *topology_option = curr; - return GNUNET_YES; - } - curr++; - } - *topology_option = GNUNET_TESTING_TOPOLOGY_OPTION_NONE; - return GNUNET_NO; -} - -/** - * Function to iterate over options. Copies - * the options to the target configuration, - * updating PORT values as needed. - * - * @param cls closure - * @param section name of the section - * @param option name of the option - * @param value value of the option - */ -static void -update_config (void *cls, const char *section, const char *option, - const char *value) -{ - struct UpdateContext *ctx = cls; - unsigned int ival; - char cval[12]; - char uval[128]; - char *single_variable; - char *per_host_variable; - unsigned long long num_per_host; - - GNUNET_asprintf (&single_variable, "single_%s_per_host", section); - GNUNET_asprintf (&per_host_variable, "num_%s_per_host", section); - - if ((0 == strcmp (option, "PORT")) && (1 == SSCANF (value, "%u", &ival))) - { - if ((ival != 0) && - (GNUNET_YES != - GNUNET_CONFIGURATION_get_value_yesno (ctx->orig, "testing", - single_variable))) - { - GNUNET_snprintf (cval, sizeof (cval), "%u", ctx->nport++); - value = cval; - } - else if ((ival != 0) && - (GNUNET_YES == - GNUNET_CONFIGURATION_get_value_yesno (ctx->orig, "testing", - single_variable)) && - GNUNET_CONFIGURATION_get_value_number (ctx->orig, "testing", - per_host_variable, - &num_per_host)) - { - GNUNET_snprintf (cval, sizeof (cval), "%u", - ival + ctx->fdnum % num_per_host); - value = cval; - } - - /* FIXME: REMOVE FOREVER HACK HACK HACK */ - if (0 == strcasecmp (section, "transport-tcp")) - GNUNET_CONFIGURATION_set_value_string (ctx->ret, section, - "ADVERTISED_PORT", value); - } - - if (0 == strcmp (option, "UNIXPATH")) - { - if (GNUNET_YES != - GNUNET_CONFIGURATION_get_value_yesno (ctx->orig, "testing", - single_variable)) - { - GNUNET_snprintf (uval, sizeof (uval), "/tmp/test-service-%s-%u", section, - ctx->upnum++); - value = uval; - } - else if ((GNUNET_YES == - GNUNET_CONFIGURATION_get_value_number (ctx->orig, "testing", - per_host_variable, - &num_per_host)) && - (num_per_host > 0)) - - { - GNUNET_snprintf (uval, sizeof (uval), "/tmp/test-service-%s-%u", section, - ctx->fdnum % num_per_host); - value = uval; - } - } - - if ((0 == strcmp (option, "HOSTNAME")) && (ctx->hostname != NULL)) - { - value = ctx->hostname; - } - GNUNET_free (single_variable); - GNUNET_free (per_host_variable); - GNUNET_CONFIGURATION_set_value_string (ctx->ret, section, option, value); -} - -/** - * Create a new configuration using the given configuration - * as a template; however, each PORT in the existing cfg - * must be renumbered by incrementing "*port". If we run - * out of "*port" numbers, return NULL. - * - * @param cfg template configuration - * @param off the current peer offset - * @param port port numbers to use, update to reflect - * port numbers that were used - * @param upnum number to make unix domain socket names unique - * @param hostname hostname of the controlling host, to allow control connections from - * @param fdnum number used to offset the unix domain socket for grouped processes - * (such as statistics or peerinfo, which can be shared among others) - * - * @return new configuration, NULL on error - */ -struct GNUNET_CONFIGURATION_Handle * -GNUNET_TESTING_create_cfg (const struct GNUNET_CONFIGURATION_Handle *cfg, uint32_t off, - uint16_t * port, uint32_t * upnum, const char *hostname, - uint32_t * fdnum) -{ - struct UpdateContext uc; - uint16_t orig; - char *control_host; - char *allowed_hosts; - unsigned long long skew_variance; - unsigned long long skew_offset; - long long actual_offset; - - orig = *port; - uc.nport = *port; - uc.upnum = *upnum; - uc.fdnum = *fdnum; - uc.ret = GNUNET_CONFIGURATION_create (); - uc.hostname = hostname; - uc.orig = cfg; - - GNUNET_CONFIGURATION_iterate (cfg, &update_config, &uc); - if (uc.nport >= HIGH_PORT) - { - *port = orig; - GNUNET_CONFIGURATION_destroy (uc.ret); - return NULL; - } - - if ((GNUNET_OK == - GNUNET_CONFIGURATION_get_value_number (cfg, "testing", "skew_variance", - &skew_variance)) && - (skew_variance > 0)) - { - skew_offset = - GNUNET_CRYPTO_random_u64 (GNUNET_CRYPTO_QUALITY_WEAK, - skew_variance + 1); - actual_offset = - skew_offset - GNUNET_CRYPTO_random_u64 (GNUNET_CRYPTO_QUALITY_WEAK, - skew_variance + 1); - /* Min is -skew_variance, Max is skew_variance */ - skew_offset = skew_variance + actual_offset; /* Normal distribution around 0 */ - GNUNET_CONFIGURATION_set_value_number (uc.ret, "testing", "skew_offset", - skew_offset); - } - - if (GNUNET_CONFIGURATION_get_value_string - (cfg, "testing", "control_host", &control_host) == GNUNET_OK) - { - if (hostname != NULL) - GNUNET_asprintf (&allowed_hosts, "%s; 127.0.0.1; %s;", control_host, - hostname); - else - GNUNET_asprintf (&allowed_hosts, "%s; 127.0.0.1;", control_host); - - GNUNET_CONFIGURATION_set_value_string (uc.ret, "core", "ACCEPT_FROM", - allowed_hosts); - - GNUNET_CONFIGURATION_set_value_string (uc.ret, "nse", "ACCEPT_FROM", - allowed_hosts); - - GNUNET_CONFIGURATION_set_value_string (uc.ret, "transport", "ACCEPT_FROM", - allowed_hosts); - GNUNET_CONFIGURATION_set_value_string (uc.ret, "dht", "ACCEPT_FROM", - allowed_hosts); - GNUNET_CONFIGURATION_set_value_string (uc.ret, "statistics", "ACCEPT_FROM", - allowed_hosts); - - GNUNET_CONFIGURATION_set_value_string (uc.ret, "core", "UNIXPATH", ""); - GNUNET_CONFIGURATION_set_value_string (uc.ret, "transport", "UNIXPATH", ""); - GNUNET_CONFIGURATION_set_value_string (uc.ret, "dht", "UNIXPATH", ""); - GNUNET_CONFIGURATION_set_value_string (uc.ret, "statistics", "UNIXPATH", - ""); - GNUNET_CONFIGURATION_set_value_string (uc.ret, "nse", "UNIXPATH", ""); - - GNUNET_CONFIGURATION_set_value_string (uc.ret, "nat", - "USE_LOCALADDR", "YES"); - GNUNET_free_non_null (control_host); - GNUNET_free (allowed_hosts); - } - - /* arm needs to know to allow connections from the host on which it is running, - * otherwise gnunet-arm is unable to connect to it in some instances */ - if (hostname != NULL) - { - GNUNET_asprintf (&allowed_hosts, "%s; 127.0.0.1;", hostname); - GNUNET_CONFIGURATION_set_value_string (uc.ret, "nat", "BINDTO", hostname); - GNUNET_CONFIGURATION_set_value_string (uc.ret, "nat", "INTERNAL_ADDRESS", - hostname); - GNUNET_CONFIGURATION_set_value_string (uc.ret, "nat", "EXTERNAL_ADDRESS", - hostname); - GNUNET_CONFIGURATION_set_value_string (uc.ret, "disablev6", "BINDTO", - "YES"); - GNUNET_CONFIGURATION_set_value_string (uc.ret, "transport-tcp", - "USE_LOCALADDR", "YES"); - GNUNET_CONFIGURATION_set_value_string (uc.ret, "transport-udp", - "USE_LOCALADDR", "YES"); - GNUNET_CONFIGURATION_set_value_string (uc.ret, "arm", "ACCEPT_FROM", - allowed_hosts); - GNUNET_free (allowed_hosts); - } - else - { - GNUNET_CONFIGURATION_set_value_string (uc.ret, "nat", - "USE_LOCALADDR", "YES"); - GNUNET_CONFIGURATION_set_value_string (uc.ret, "nat", "BINDTO", - "127.0.0.1"); - GNUNET_CONFIGURATION_set_value_string (uc.ret, "nat", "INTERNAL_ADDRESS", - "127.0.0.1"); - GNUNET_CONFIGURATION_set_value_string (uc.ret, "nat", "EXTERNAL_ADDRESS", - "127.0.0.1"); - GNUNET_CONFIGURATION_set_value_string (uc.ret, "nat", "disablev6", - "YES"); - } - - *port = (uint16_t) uc.nport; - *upnum = uc.upnum; - uc.fdnum++; - *fdnum = uc.fdnum; - return uc.ret; -} - -/* - * Remove entries from the peer connection list - * - * @param pg the peer group we are working with - * @param first index of the first peer - * @param second index of the second peer - * @param list the peer list to use - * @param check UNUSED - * - * @return the number of connections added (can be 0, 1 or 2) - * - */ -static unsigned int -remove_connections (struct GNUNET_TESTING_PeerGroup *pg, unsigned int first, - unsigned int second, enum PeerLists list, - unsigned int check) -{ - int removed; - -#if OLD - struct PeerConnection **first_list; - struct PeerConnection **second_list; - struct PeerConnection *first_iter; - struct PeerConnection *second_iter; - struct PeerConnection **first_tail; - struct PeerConnection **second_tail; - -#else - GNUNET_HashCode hash_first; - GNUNET_HashCode hash_second; - - hash_from_uid (first, &hash_first); - hash_from_uid (second, &hash_second); -#endif - - removed = 0; -#if OLD - switch (list) - { - case ALLOWED: - first_list = &pg->peers[first].allowed_peers_head; - second_list = &pg->peers[second].allowed_peers_head; - first_tail = &pg->peers[first].allowed_peers_tail; - second_tail = &pg->peers[second].allowed_peers_tail; - break; - case CONNECT: - first_list = &pg->peers[first].connect_peers_head; - second_list = &pg->peers[second].connect_peers_head; - first_tail = &pg->peers[first].connect_peers_tail; - second_tail = &pg->peers[second].connect_peers_tail; - break; - case BLACKLIST: - first_list = &pg->peers[first].blacklisted_peers_head; - second_list = &pg->peers[second].blacklisted_peers_head; - first_tail = &pg->peers[first].blacklisted_peers_tail; - second_tail = &pg->peers[second].blacklisted_peers_tail; - break; - case WORKING_SET: - first_list = &pg->peers[first].connect_peers_working_set_head; - second_list = &pg->peers[second].connect_peers_working_set_head; - first_tail = &pg->peers[first].connect_peers_working_set_tail; - second_tail = &pg->peers[second].connect_peers_working_set_tail; - break; - default: - GNUNET_break (0); - return 0; - } - - first_iter = *first_list; - while (first_iter != NULL) - { - if (first_iter->index == second) - { - GNUNET_CONTAINER_DLL_remove (*first_list, *first_tail, first_iter); - GNUNET_free (first_iter); - removed++; - break; - } - first_iter = first_iter->next; - } - - second_iter = *second_list; - while (second_iter != NULL) - { - if (second_iter->index == first) - { - GNUNET_CONTAINER_DLL_remove (*second_list, *second_tail, second_iter); - GNUNET_free (second_iter); - removed++; - break; - } - second_iter = second_iter->next; - } -#else - if (GNUNET_YES == - GNUNET_CONTAINER_multihashmap_contains (pg-> - peers[first].blacklisted_peers, - &hash_second)) - { - GNUNET_CONTAINER_multihashmap_remove_all (pg-> - peers[first].blacklisted_peers, - &hash_second); - } - - if (GNUNET_YES == - GNUNET_CONTAINER_multihashmap_contains (pg-> - peers[second].blacklisted_peers, - &hash_first)) - { - GNUNET_CONTAINER_multihashmap_remove_all (pg-> - peers[second].blacklisted_peers, - &hash_first); - } -#endif - - return removed; -} - -/** - * Add entries to the some list - * - * @param pg the peer group we are working with - * @param first index of the first peer - * @param second index of the second peer - * @param list the list type that we should modify - * @param check GNUNET_YES to check lists before adding - * GNUNET_NO to force add - * - * @return the number of connections added (can be 0, 1 or 2) - * - */ -static unsigned int -add_connections (struct GNUNET_TESTING_PeerGroup *pg, unsigned int first, - unsigned int second, enum PeerLists list, unsigned int check) -{ - int added; - int add_first; - int add_second; - - struct PeerConnection **first_list; - struct PeerConnection **second_list; - struct PeerConnection *first_iter; - struct PeerConnection *second_iter; - struct PeerConnection *new_first; - struct PeerConnection *new_second; - struct PeerConnection **first_tail; - struct PeerConnection **second_tail; - - switch (list) - { - case ALLOWED: - first_list = &pg->peers[first].allowed_peers_head; - second_list = &pg->peers[second].allowed_peers_head; - first_tail = &pg->peers[first].allowed_peers_tail; - second_tail = &pg->peers[second].allowed_peers_tail; - break; - case CONNECT: - first_list = &pg->peers[first].connect_peers_head; - second_list = &pg->peers[second].connect_peers_head; - first_tail = &pg->peers[first].connect_peers_tail; - second_tail = &pg->peers[second].connect_peers_tail; - break; - case BLACKLIST: - first_list = &pg->peers[first].blacklisted_peers_head; - second_list = &pg->peers[second].blacklisted_peers_head; - first_tail = &pg->peers[first].blacklisted_peers_tail; - second_tail = &pg->peers[second].blacklisted_peers_tail; - break; - case WORKING_SET: - first_list = &pg->peers[first].connect_peers_working_set_head; - second_list = &pg->peers[second].connect_peers_working_set_head; - first_tail = &pg->peers[first].connect_peers_working_set_tail; - second_tail = &pg->peers[second].connect_peers_working_set_tail; - break; - default: - GNUNET_break (0); - return 0; - } - - add_first = GNUNET_YES; - add_second = GNUNET_YES; - - if (check == GNUNET_YES) - { - first_iter = *first_list; - while (first_iter != NULL) - { - if (first_iter->index == second) - { - add_first = GNUNET_NO; - break; - } - first_iter = first_iter->next; - } - - second_iter = *second_list; - while (second_iter != NULL) - { - if (second_iter->index == first) - { - add_second = GNUNET_NO; - break; - } - second_iter = second_iter->next; - } - } - - added = 0; - if (add_first) - { - new_first = GNUNET_malloc (sizeof (struct PeerConnection)); - new_first->index = second; - GNUNET_CONTAINER_DLL_insert (*first_list, *first_tail, new_first); - pg->peers[first].num_connections++; - added++; - } - - if (add_second) - { - new_second = GNUNET_malloc (sizeof (struct PeerConnection)); - new_second->index = first; - GNUNET_CONTAINER_DLL_insert (*second_list, *second_tail, new_second); - pg->peers[second].num_connections++; - added++; - } - - return added; -} - -/** - * Scale free network construction as described in: - * - * "Emergence of Scaling in Random Networks." Science 286, 509-512, 1999. - * - * Start with a network of "one" peer, then progressively add - * peers up to the total number. At each step, iterate over - * all possible peers and connect new peer based on number of - * existing connections of the target peer. - * - * @param pg the peer group we are dealing with - * @param proc the connection processor to use - * @param list the peer list to use - * - * @return the number of connections created - */ -static unsigned int -create_scale_free (struct GNUNET_TESTING_PeerGroup *pg, - GNUNET_TESTING_ConnectionProcessor proc, enum PeerLists list) -{ - - unsigned int total_connections; - unsigned int outer_count; - unsigned int i; - unsigned int previous_total_connections; - double random; - double probability; - - GNUNET_assert (pg->total > 1); - - /* Add a connection between the first two nodes */ - total_connections = proc (pg, 0, 1, list, GNUNET_YES); - - for (outer_count = 1; outer_count < pg->total; outer_count++) - { - previous_total_connections = total_connections; - for (i = 0; i < outer_count; i++) - { - probability = - pg->peers[i].num_connections / (double) previous_total_connections; - random = - ((double) - GNUNET_CRYPTO_random_u64 (GNUNET_CRYPTO_QUALITY_WEAK, - UINT64_MAX)) / ((double) UINT64_MAX); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Considering connecting peer %d to peer %d\n", outer_count, - i); - if (random < probability) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Connecting peer %d to peer %d\n", - outer_count, i); - total_connections += proc (pg, outer_count, i, list, GNUNET_YES); - } - } - } - - return total_connections; -} - -/** - * Create a topology given a peer group (set of running peers) - * and a connection processor. Creates a small world topology - * according to the rewired ring construction. The basic - * behavior is that a ring topology is created, but with some - * probability instead of connecting a peer to the next - * neighbor in the ring a connection will be created to a peer - * selected uniformly at random. We use the TESTING - * PERCENTAGE option to specify what number of - * connections each peer should have. Default is 2, - * which makes the ring, any given number is multiplied by - * the log of the network size; i.e. a PERCENTAGE of 2 makes - * each peer have on average 2logn connections. The additional - * connections are made at increasing distance around the ring - * from the original peer, or to random peers based on the re- - * wiring probability. The TESTING - * PROBABILITY option is used as the probability that a given - * connection is rewired. - * - * @param pg the peergroup to create the topology on - * @param proc the connection processor to call to actually set - * up connections between two peers - * @param list the peer list to use - * - * @return the number of connections that were set up - * - */ -static unsigned int -create_small_world_ring (struct GNUNET_TESTING_PeerGroup *pg, - GNUNET_TESTING_ConnectionProcessor proc, - enum PeerLists list) -{ - unsigned int i, j; - int nodeToConnect; - unsigned int natLog; - unsigned int randomPeer; - double random, logNModifier, probability; - unsigned int smallWorldConnections; - int connsPerPeer; - char *p_string; - int max; - int min; - unsigned int useAnd; - int connect_attempts; - - logNModifier = 0.5; /* FIXME: default value? */ - if (GNUNET_OK == - GNUNET_CONFIGURATION_get_value_string (pg->cfg, "TESTING", "PERCENTAGE", - &p_string)) - { - if (SSCANF (p_string, "%lf", &logNModifier) != 1) - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - _ - ("Invalid value `%s' for option `%s' in section `%s': expected float\n"), - p_string, "LOGNMODIFIER", "TESTING"); - GNUNET_free (p_string); - } - probability = 0.5; /* FIXME: default percentage? */ - if (GNUNET_OK == - GNUNET_CONFIGURATION_get_value_string (pg->cfg, "TESTING", "PROBABILITY", - &p_string)) - { - if (SSCANF (p_string, "%lf", &probability) != 1) - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - _ - ("Invalid value `%s' for option `%s' in section `%s': expected float\n"), - p_string, "PERCENTAGE", "TESTING"); - GNUNET_free (p_string); - } - natLog = log (pg->total); - connsPerPeer = ceil (natLog * logNModifier); - - if (connsPerPeer % 2 == 1) - connsPerPeer += 1; - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Target is %d connections per peer.", - connsPerPeer); - - smallWorldConnections = 0; - connect_attempts = 0; - for (i = 0; i < pg->total; i++) - { - useAnd = 0; - max = i + connsPerPeer / 2; - min = i - connsPerPeer / 2; - - if (max > pg->total - 1) - { - max = max - pg->total; - useAnd = 1; - } - - if (min < 0) - { - min = pg->total - 1 + min; - useAnd = 1; - } - - for (j = 0; j < connsPerPeer / 2; j++) - { - random = - ((double) - GNUNET_CRYPTO_random_u64 (GNUNET_CRYPTO_QUALITY_WEAK, - UINT64_MAX) / ((double) UINT64_MAX)); - if (random < probability) - { - /* Connect to uniformly selected random peer */ - randomPeer = - GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK, pg->total); - while ((((randomPeer < max) && (randomPeer > min)) && (useAnd == 0)) || - (((randomPeer > min) || (randomPeer < max)) && (useAnd == 1))) - { - randomPeer = - GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK, pg->total); - } - smallWorldConnections += proc (pg, i, randomPeer, list, GNUNET_YES); - } - else - { - nodeToConnect = i + j + 1; - if (nodeToConnect > pg->total - 1) - { - nodeToConnect = nodeToConnect - pg->total; - } - connect_attempts += proc (pg, i, nodeToConnect, list, GNUNET_YES); - } - } - - } - - connect_attempts += smallWorldConnections; - - return connect_attempts; -} - -/** - * Create a topology given a peer group (set of running peers) - * and a connection processor. - * - * @param pg the peergroup to create the topology on - * @param proc the connection processor to call to actually set - * up connections between two peers - * @param list the peer list to use - * - * @return the number of connections that were set up - * - */ -static unsigned int -create_nated_internet (struct GNUNET_TESTING_PeerGroup *pg, - GNUNET_TESTING_ConnectionProcessor proc, - enum PeerLists list) -{ - unsigned int outer_count, inner_count; - unsigned int cutoff; - int connect_attempts; - double nat_percentage; - char *p_string; - - nat_percentage = 0.6; /* FIXME: default percentage? */ - if (GNUNET_OK == - GNUNET_CONFIGURATION_get_value_string (pg->cfg, "TESTING", "PERCENTAGE", - &p_string)) - { - if (SSCANF (p_string, "%lf", &nat_percentage) != 1) - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - _ - ("Invalid value `%s' for option `%s' in section `%s': expected float\n"), - p_string, "PERCENTAGE", "TESTING"); - GNUNET_free (p_string); - } - - cutoff = (unsigned int) (nat_percentage * pg->total); - connect_attempts = 0; - for (outer_count = 0; outer_count < pg->total - 1; outer_count++) - { - for (inner_count = outer_count + 1; inner_count < pg->total; inner_count++) - { - if ((outer_count > cutoff) || (inner_count > cutoff)) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Connecting peer %d to peer %d\n", - outer_count, inner_count); - connect_attempts += - proc (pg, outer_count, inner_count, list, GNUNET_YES); - } - } - } - return connect_attempts; -} - -#if TOPOLOGY_HACK -/** - * Create a topology given a peer group (set of running peers) - * and a connection processor. - * - * @param pg the peergroup to create the topology on - * @param proc the connection processor to call to actually set - * up connections between two peers - * @param list the peer list to use - * - * @return the number of connections that were set up - * - */ -static unsigned int -create_nated_internet_copy (struct GNUNET_TESTING_PeerGroup *pg, - GNUNET_TESTING_ConnectionProcessor proc, - enum PeerLists list) -{ - unsigned int outer_count, inner_count; - unsigned int cutoff; - int connect_attempts; - double nat_percentage; - char *p_string; - unsigned int count; - struct ProgressMeter *conn_meter; - - nat_percentage = 0.6; /* FIXME: default percentage? */ - if (GNUNET_OK == - GNUNET_CONFIGURATION_get_value_string (pg->cfg, "TESTING", "PERCENTAGE", - &p_string)) - { - if (SSCANF (p_string, "%lf", &nat_percentage) != 1) - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - _ - ("Invalid value `%s' for option `%s' in section `%s': expected float\n"), - p_string, "PERCENTAGE", "TESTING"); - GNUNET_free (p_string); - } - - cutoff = (unsigned int) (nat_percentage * pg->total); - count = 0; - for (outer_count = 0; outer_count < pg->total - 1; outer_count++) - { - for (inner_count = outer_count + 1; inner_count < pg->total; inner_count++) - { - if ((outer_count > cutoff) || (inner_count > cutoff)) - { - count++; - } - } - } - conn_meter = create_meter (count, "NAT COPY", GNUNET_YES); - connect_attempts = 0; - for (outer_count = 0; outer_count < pg->total - 1; outer_count++) - { - for (inner_count = outer_count + 1; inner_count < pg->total; inner_count++) - { - if ((outer_count > cutoff) || (inner_count > cutoff)) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Connecting peer %d to peer %d\n", - outer_count, inner_count); - connect_attempts += - proc (pg, outer_count, inner_count, list, GNUNET_YES); - add_connections (pg, outer_count, inner_count, ALLOWED, GNUNET_NO); - update_meter (conn_meter); - } - } - } - free_meter (conn_meter); - - return connect_attempts; -} -#endif - -/** - * Create a topology given a peer group (set of running peers) - * and a connection processor. - * - * @param pg the peergroup to create the topology on - * @param proc the connection processor to call to actually set - * up connections between two peers - * @param list the peer list to use - * - * @return the number of connections that were set up - * - */ -static unsigned int -create_small_world (struct GNUNET_TESTING_PeerGroup *pg, - GNUNET_TESTING_ConnectionProcessor proc, - enum PeerLists list) -{ - unsigned int i, j, k; - unsigned int square; - unsigned int rows; - unsigned int cols; - unsigned int toggle = 1; - unsigned int nodeToConnect; - unsigned int natLog; - unsigned int node1Row; - unsigned int node1Col; - unsigned int node2Row; - unsigned int node2Col; - unsigned int distance; - double probability, random, percentage; - unsigned int smallWorldConnections; - unsigned int small_world_it; - char *p_string; - int connect_attempts; - - square = floor (sqrt (pg->total)); - rows = square; - cols = square; - - percentage = 0.5; /* FIXME: default percentage? */ - if (GNUNET_OK == - GNUNET_CONFIGURATION_get_value_string (pg->cfg, "TESTING", "PERCENTAGE", - &p_string)) - { - if (SSCANF (p_string, "%lf", &percentage) != 1) - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - _ - ("Invalid value `%s' for option `%s' in section `%s': expected float\n"), - p_string, "PERCENTAGE", "TESTING"); - GNUNET_free (p_string); - } - if (percentage < 0.0) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - _ - ("Invalid value `%s' for option `%s' in section `%s': got %f, needed value greater than 0\n"), - "PERCENTAGE", "TESTING", percentage); - percentage = 0.5; - } - probability = 0.5; /* FIXME: default percentage? */ - if (GNUNET_OK == - GNUNET_CONFIGURATION_get_value_string (pg->cfg, "TESTING", "PROBABILITY", - &p_string)) - { - if (SSCANF (p_string, "%lf", &probability) != 1) - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - _ - ("Invalid value `%s' for option `%s' in section `%s': expected float\n"), - p_string, "PROBABILITY", "TESTING"); - GNUNET_free (p_string); - } - if (square * square != pg->total) - { - while (rows * cols < pg->total) - { - if (toggle % 2 == 0) - rows++; - else - cols++; - - toggle++; - } - } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Connecting nodes in 2d torus topology: %u rows %u columns\n", - rows, cols); - connect_attempts = 0; - /* Rows and columns are all sorted out, now iterate over all nodes and connect each - * to the node to its right and above. Once this is over, we'll have our torus! - * Special case for the last node (if the rows and columns are not equal), connect - * to the first in the row to maintain topology. - */ - for (i = 0; i < pg->total; i++) - { - /* First connect to the node to the right */ - if (((i + 1) % cols != 0) && (i + 1 != pg->total)) - nodeToConnect = i + 1; - else if (i + 1 == pg->total) - nodeToConnect = rows * cols - cols; - else - nodeToConnect = i - cols + 1; - - connect_attempts += proc (pg, i, nodeToConnect, list, GNUNET_YES); - - if (i < cols) - { - nodeToConnect = (rows * cols) - cols + i; - if (nodeToConnect >= pg->total) - nodeToConnect -= cols; - } - else - nodeToConnect = i - cols; - - if (nodeToConnect < pg->total) - connect_attempts += proc (pg, i, nodeToConnect, list, GNUNET_YES); - } - natLog = log (pg->total); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "natural log of %d is %d, will run %d iterations\n", pg->total, - natLog, (int) (natLog * percentage)); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Total connections added thus far: %u!\n", connect_attempts); - smallWorldConnections = 0; - small_world_it = (unsigned int) (natLog * percentage); - if (small_world_it < 1) - small_world_it = 1; - GNUNET_assert (small_world_it > 0 && small_world_it < (unsigned int) -1); - for (i = 0; i < small_world_it; i++) - { - for (j = 0; j < pg->total; j++) - { - /* Determine the row and column of node at position j on the 2d torus */ - node1Row = j / cols; - node1Col = j - (node1Row * cols); - for (k = 0; k < pg->total; k++) - { - /* Determine the row and column of node at position k on the 2d torus */ - node2Row = k / cols; - node2Col = k - (node2Row * cols); - /* Simple Cartesian distance */ - distance = abs (node1Row - node2Row) + abs (node1Col - node2Col); - if (distance > 1) - { - /* Calculate probability as 1 over the square of the distance */ - probability = 1.0 / (distance * distance); - /* Choose a random value between 0 and 1 */ - random = - ((double) - GNUNET_CRYPTO_random_u64 (GNUNET_CRYPTO_QUALITY_WEAK, - UINT64_MAX)) / ((double) UINT64_MAX); - /* If random < probability, then connect the two nodes */ - if (random < probability) - smallWorldConnections += proc (pg, j, k, list, GNUNET_YES); - - } - } - } - } - connect_attempts += smallWorldConnections; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Total connections added for small world: %d!\n", - smallWorldConnections); - return connect_attempts; -} - -/** - * Create a topology given a peer group (set of running peers) - * and a connection processor. - * - * @param pg the peergroup to create the topology on - * @param proc the connection processor to call to actually set - * up connections between two peers - * @param list the peer list to use - * - * @return the number of connections that were set up - * - */ -static unsigned int -create_erdos_renyi (struct GNUNET_TESTING_PeerGroup *pg, - GNUNET_TESTING_ConnectionProcessor proc, - enum PeerLists list) -{ - double temp_rand; - unsigned int outer_count; - unsigned int inner_count; - int connect_attempts; - double probability; - char *p_string; - - probability = 0.5; /* FIXME: default percentage? */ - if (GNUNET_OK == - GNUNET_CONFIGURATION_get_value_string (pg->cfg, "TESTING", "PROBABILITY", - &p_string)) - { - if (SSCANF (p_string, "%lf", &probability) != 1) - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - _ - ("Invalid value `%s' for option `%s' in section `%s': expected float\n"), - p_string, "PROBABILITY", "TESTING"); - GNUNET_free (p_string); - } - connect_attempts = 0; - for (outer_count = 0; outer_count < pg->total - 1; outer_count++) - { - for (inner_count = outer_count + 1; inner_count < pg->total; inner_count++) - { - temp_rand = - ((double) - GNUNET_CRYPTO_random_u64 (GNUNET_CRYPTO_QUALITY_WEAK, - UINT64_MAX)) / ((double) UINT64_MAX); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "rand is %f probability is %f\n", - temp_rand, probability); - if (temp_rand < probability) - { - connect_attempts += - proc (pg, outer_count, inner_count, list, GNUNET_YES); - } - } - } - - return connect_attempts; -} - -/** - * Create a topology given a peer group (set of running peers) - * and a connection processor. This particular function creates - * the connections for a 2d-torus, plus additional "closest" - * connections per peer. - * - * @param pg the peergroup to create the topology on - * @param proc the connection processor to call to actually set - * up connections between two peers - * @param list the peer list to use - * - * @return the number of connections that were set up - * - */ -static unsigned int -create_2d_torus (struct GNUNET_TESTING_PeerGroup *pg, - GNUNET_TESTING_ConnectionProcessor proc, enum PeerLists list) -{ - unsigned int i; - unsigned int square; - unsigned int rows; - unsigned int cols; - unsigned int toggle = 1; - unsigned int nodeToConnect; - int connect_attempts; - - connect_attempts = 0; - - square = floor (sqrt (pg->total)); - rows = square; - cols = square; - - if (square * square != pg->total) - { - while (rows * cols < pg->total) - { - if (toggle % 2 == 0) - rows++; - else - cols++; - - toggle++; - } - } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Connecting nodes in 2d torus topology: %u rows %u columns\n", - rows, cols); - /* Rows and columns are all sorted out, now iterate over all nodes and connect each - * to the node to its right and above. Once this is over, we'll have our torus! - * Special case for the last node (if the rows and columns are not equal), connect - * to the first in the row to maintain topology. - */ - for (i = 0; i < pg->total; i++) - { - /* First connect to the node to the right */ - if (((i + 1) % cols != 0) && (i + 1 != pg->total)) - nodeToConnect = i + 1; - else if (i + 1 == pg->total) - nodeToConnect = rows * cols - cols; - else - nodeToConnect = i - cols + 1; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Connecting peer %d to peer %d\n", i, - nodeToConnect); - connect_attempts += proc (pg, i, nodeToConnect, list, GNUNET_YES); - - /* Second connect to the node immediately above */ - if (i < cols) - { - nodeToConnect = (rows * cols) - cols + i; - if (nodeToConnect >= pg->total) - nodeToConnect -= cols; - } - else - nodeToConnect = i - cols; - - if (nodeToConnect < pg->total) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Connecting peer %d to peer %d\n", i, - nodeToConnect); - connect_attempts += proc (pg, i, nodeToConnect, list, GNUNET_YES); - } - - } - - return connect_attempts; -} - -/** - * Create a topology given a peer group (set of running peers) - * and a connection processor. - * - * @param pg the peergroup to create the topology on - * @param proc the connection processor to call to actually set - * up connections between two peers - * @param list the peer list to use - * @param check does the connection processor need to check before - * performing an action on the list? - * - * @return the number of connections that were set up - * - */ -static unsigned int -create_clique (struct GNUNET_TESTING_PeerGroup *pg, - GNUNET_TESTING_ConnectionProcessor proc, enum PeerLists list, - unsigned int check) -{ - unsigned int outer_count; - unsigned int inner_count; - int connect_attempts; - struct ProgressMeter *conn_meter; - - connect_attempts = 0; - - conn_meter = - create_meter ((((pg->total * pg->total) + pg->total) / 2) - pg->total, - "Create Clique ", GNUNET_NO); - for (outer_count = 0; outer_count < pg->total - 1; outer_count++) - { - for (inner_count = outer_count + 1; inner_count < pg->total; inner_count++) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Connecting peer %d to peer %d\n", - outer_count, inner_count); - connect_attempts += proc (pg, outer_count, inner_count, list, check); - update_meter (conn_meter); - } - } - reset_meter (conn_meter); - free_meter (conn_meter); - return connect_attempts; -} - -#if !OLD -/** - * Iterator over hash map entries. - * - * @param cls closure the peer group - * @param key the key stored in the hashmap is the - * index of the peer to connect to - * @param value value in the hash map, handle to the peer daemon - * @return GNUNET_YES if we should continue to - * iterate, - * GNUNET_NO if not. - */ -static int -unblacklist_iterator (void *cls, const GNUNET_HashCode * key, void *value) -{ - struct UnblacklistContext *un_ctx = cls; - uint32_t second_pos; - - uid_from_hash (key, &second_pos); - - unblacklist_connections (un_ctx->pg, un_ctx->first_uid, second_pos); - - return GNUNET_YES; -} -#endif - -#if !OLD -/** - * Create a blacklist topology based on the allowed topology - * which disallows any connections not in the allowed topology - * at the transport level. - * - * @param pg the peergroup to create the topology on - * @param proc the connection processor to call to allow - * up connections between two peers - * - * @return the number of connections that were set up - * - */ -static unsigned int -copy_allowed (struct GNUNET_TESTING_PeerGroup *pg, - GNUNET_TESTING_ConnectionProcessor proc) -{ - unsigned int count; - unsigned int total; - struct PeerConnection *iter; - -#if !OLD - struct UnblacklistContext un_ctx; - - un_ctx.pg = pg; -#endif - total = 0; - for (count = 0; count < pg->total - 1; count++) - { -#if OLD - iter = pg->peers[count].allowed_peers_head; - while (iter != NULL) - { - remove_connections (pg, count, iter->index, BLACKLIST, GNUNET_YES); - //unblacklist_connections(pg, count, iter->index); - iter = iter->next; - } -#else - un_ctx.first_uid = count; - total += - GNUNET_CONTAINER_multihashmap_iterate (pg->peers[count].allowed_peers, - &unblacklist_iterator, &un_ctx); -#endif - } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Unblacklisted %u peers\n", total); - return total; -} -#endif - -/** - * Create a topology given a peer group (set of running peers) - * and a connection processor. - * - * @param pg the peergroup to create the topology on - * @param proc the connection processor to call to actually set - * up connections between two peers - * @param list which list should be modified - * - * @return the number of connections that were set up - * - */ -static unsigned int -create_line (struct GNUNET_TESTING_PeerGroup *pg, - GNUNET_TESTING_ConnectionProcessor proc, enum PeerLists list) -{ - unsigned int count; - unsigned int connect_attempts; - - connect_attempts = 0; - /* Connect each peer to the next highest numbered peer */ - for (count = 0; count < pg->total - 1; count++) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Connecting peer %d to peer %d\n", - count, count + 1); - connect_attempts += proc (pg, count, count + 1, list, GNUNET_YES); - } - - return connect_attempts; -} - -/** - * Create a topology given a peer group (set of running peers) - * and a connection processor. - * - * @param pg the peergroup to create the topology on - * @param filename the file to read topology information from - * @param proc the connection processor to call to actually set - * up connections between two peers - * @param list the peer list to use - * - * @return the number of connections that were set up - * - */ -static unsigned int -create_from_file (struct GNUNET_TESTING_PeerGroup *pg, char *filename, - GNUNET_TESTING_ConnectionProcessor proc, enum PeerLists list) -{ - int connect_attempts; - unsigned int first_peer_index; - unsigned int second_peer_index; - struct stat frstat; - int count; - char *data; - const char *buf; - unsigned int total_peers; - enum States curr_state; - - connect_attempts = 0; - if (GNUNET_OK != GNUNET_DISK_file_test (filename)) - GNUNET_DISK_fn_write (filename, NULL, 0, GNUNET_DISK_PERM_USER_READ); - - if ((0 != STAT (filename, &frstat)) || (frstat.st_size == 0)) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "Could not open file `%s' specified for topology!", filename); - return connect_attempts; - } - - data = GNUNET_malloc_large (frstat.st_size); - GNUNET_assert (data != NULL); - if (frstat.st_size != GNUNET_DISK_fn_read (filename, data, frstat.st_size)) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "Could not read file %s specified for host list, ending test!", - filename); - GNUNET_free (data); - return connect_attempts; - } - - buf = data; - count = 0; - first_peer_index = 0; - /* First line should contain a single integer, specifying the number of peers */ - /* Each subsequent line should contain this format PEER_INDEX:OTHER_PEER_INDEX[,...] */ - curr_state = NUM_PEERS; - while (count < frstat.st_size - 1) - { - if ((buf[count] == '\n') || (buf[count] == ' ')) - { - count++; - continue; - } - - switch (curr_state) - { - case NUM_PEERS: - errno = 0; - total_peers = strtoul (&buf[count], NULL, 10); - if (errno != 0) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Failed to read number of peers from topology file!\n"); - GNUNET_free (data); - return connect_attempts; - } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Found %u total peers in topology\n", - total_peers); - GNUNET_assert (total_peers == pg->total); - curr_state = PEER_INDEX; - while ((buf[count] != '\n') && (count < frstat.st_size - 1)) - count++; - count++; - break; - case PEER_INDEX: - errno = 0; - first_peer_index = strtoul (&buf[count], NULL, 10); - if (errno != 0) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Failed to read peer index from topology file!\n"); - GNUNET_free (data); - return connect_attempts; - } - while ((buf[count] != ':') && (count < frstat.st_size - 1)) - count++; - count++; - curr_state = OTHER_PEER_INDEX; - break; - case COLON: - if (1 == sscanf (&buf[count], ":")) - curr_state = OTHER_PEER_INDEX; - count++; - break; - case OTHER_PEER_INDEX: - errno = 0; - second_peer_index = strtoul (&buf[count], NULL, 10); - if (errno != 0) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Failed to peer index from topology file!\n"); - GNUNET_free (data); - return connect_attempts; - } - /* Assume file is written with first peer 1, but array index is 0 */ - connect_attempts += - proc (pg, first_peer_index - 1, second_peer_index - 1, list, - GNUNET_YES); - while ((buf[count] != '\n') && (buf[count] != ',') && - (count < frstat.st_size - 1)) - count++; - if (buf[count] == '\n') - { - curr_state = PEER_INDEX; - } - else if (buf[count] != ',') - { - curr_state = OTHER_PEER_INDEX; - } - count++; - break; - default: - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "Found bad data in topology file while in state %d!\n", - curr_state); - GNUNET_break (0); - GNUNET_free (data); - return connect_attempts; - } - } - GNUNET_free (data); - return connect_attempts; -} - -/** - * Create a topology given a peer group (set of running peers) - * and a connection processor. - * - * @param pg the peergroup to create the topology on - * @param proc the connection processor to call to actually set - * up connections between two peers - * @param list the peer list to use - * - * @return the number of connections that were set up - * - */ -static unsigned int -create_ring (struct GNUNET_TESTING_PeerGroup *pg, - GNUNET_TESTING_ConnectionProcessor proc, enum PeerLists list) -{ - unsigned int count; - int connect_attempts; - - connect_attempts = 0; - - /* Connect each peer to the next highest numbered peer */ - for (count = 0; count < pg->total - 1; count++) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Connecting peer %d to peer %d\n", - count, count + 1); - connect_attempts += proc (pg, count, count + 1, list, GNUNET_YES); - } - - /* Connect the last peer to the first peer */ - connect_attempts += proc (pg, pg->total - 1, 0, list, GNUNET_YES); - - return connect_attempts; -} - -#if !OLD -/** - * Iterator for writing friends of a peer to a file. - * - * @param cls closure, an open writable file handle - * @param key the key the daemon was stored under - * @param value the GNUNET_TESTING_Daemon that needs to be written. - * - * @return GNUNET_YES to continue iteration - * - * TODO: Could replace friend_file_iterator and blacklist_file_iterator - * with a single file_iterator that takes a closure which contains - * the prefix to write before the peer. Then this could be used - * for blacklisting multiple transports and writing the friend - * file. I'm sure *someone* will complain loudly about other - * things that negate these functions even existing so no point in - * "fixing" now. - */ -static int -friend_file_iterator (void *cls, const GNUNET_HashCode * key, void *value) -{ - FILE *temp_friend_handle = cls; - struct GNUNET_TESTING_Daemon *peer = value; - struct GNUNET_PeerIdentity *temppeer; - struct GNUNET_CRYPTO_HashAsciiEncoded peer_enc; - - temppeer = &peer->id; - GNUNET_CRYPTO_hash_to_enc (&temppeer->hashPubKey, &peer_enc); - FPRINTF (temp_friend_handle, "%s\n", (char *) &peer_enc); - - return GNUNET_YES; -} - -struct BlacklistContext -{ - /* - * The (open) file handle to write to - */ - FILE *temp_file_handle; - - /* - * The transport that this peer will be blacklisted on. - */ - char *transport; -}; - -/** - * Iterator for writing blacklist data to appropriate files. - * - * @param cls closure, an open writable file handle - * @param key the key the daemon was stored under - * @param value the GNUNET_TESTING_Daemon that needs to be written. - * - * @return GNUNET_YES to continue iteration - */ -static int -blacklist_file_iterator (void *cls, const GNUNET_HashCode * key, void *value) -{ - struct BlacklistContext *blacklist_ctx = cls; - struct GNUNET_TESTING_Daemon *peer = value; - struct GNUNET_PeerIdentity *temppeer; - struct GNUNET_CRYPTO_HashAsciiEncoded peer_enc; - - temppeer = &peer->id; - GNUNET_CRYPTO_hash_to_enc (&temppeer->hashPubKey, &peer_enc); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Writing entry %s:%s to file\n", - blacklist_ctx->transport, (char *) &peer_enc); - FPRINTF (blacklist_ctx->temp_file_handle, "%s:%s\n", blacklist_ctx->transport, - (char *) &peer_enc); - - return GNUNET_YES; -} -#endif - -/* - * Create the friend files based on the PeerConnection's - * of each peer in the peer group, and copy the files - * to the appropriate place - * - * @param pg the peer group we are dealing with - */ -static int -create_and_copy_friend_files (struct GNUNET_TESTING_PeerGroup *pg) -{ - FILE *temp_friend_handle; - unsigned int pg_iter; - char *temp_service_path; - struct GNUNET_OS_Process **procarr; - char *arg; - char *mytemp; - -#if NOT_STUPID - enum GNUNET_OS_ProcessStatusType type; - unsigned long return_code; - int count; - int max_wait = 10; -#endif - int ret; - - ret = GNUNET_OK; -#if OLD - struct GNUNET_CRYPTO_HashAsciiEncoded peer_enc; - struct PeerConnection *conn_iter; -#endif - procarr = GNUNET_malloc (sizeof (struct GNUNET_OS_Process *) * pg->total); - for (pg_iter = 0; pg_iter < pg->total; pg_iter++) - { - mytemp = GNUNET_DISK_mktemp ("friends"); - GNUNET_assert (mytemp != NULL); - temp_friend_handle = FOPEN (mytemp, "wt"); - GNUNET_assert (temp_friend_handle != NULL); -#if OLD - conn_iter = pg->peers[pg_iter].allowed_peers_head; - while (conn_iter != NULL) - { - GNUNET_CRYPTO_hash_to_enc (&pg->peers[conn_iter->index].daemon-> - id.hashPubKey, &peer_enc); - FPRINTF (temp_friend_handle, "%s\n", (char *) &peer_enc); - conn_iter = conn_iter->next; - } -#else - GNUNET_CONTAINER_multihashmap_iterate (pg->peers[pg_iter].allowed_peers, - &friend_file_iterator, - temp_friend_handle); -#endif - FCLOSE (temp_friend_handle); - - if (GNUNET_OK != - GNUNET_CONFIGURATION_get_value_string (pg->peers[pg_iter].daemon->cfg, - "PATHS", "SERVICEHOME", - &temp_service_path)) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - _ - ("No `%s' specified in peer configuration in section `%s', cannot copy friends file!\n"), - "SERVICEHOME", "PATHS"); - if (UNLINK (mytemp) != 0) - GNUNET_log_strerror_file (GNUNET_ERROR_TYPE_WARNING, "unlink", mytemp); - GNUNET_free (mytemp); - break; - } - - if (pg->peers[pg_iter].daemon->hostname == NULL) /* Local, just copy the file */ - { - GNUNET_asprintf (&arg, "%s/friends", temp_service_path); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Copying file with RENAME(%s,%s)\n", mytemp, arg); - RENAME (mytemp, arg); - procarr[pg_iter] = NULL; - GNUNET_free (arg); - } - else /* Remote, scp the file to the correct place */ - { - if (NULL != pg->peers[pg_iter].daemon->username) - GNUNET_asprintf (&arg, "%s@%s:%s/friends", - pg->peers[pg_iter].daemon->username, - pg->peers[pg_iter].daemon->hostname, - temp_service_path); - else - GNUNET_asprintf (&arg, "%s:%s/friends", - pg->peers[pg_iter].daemon->hostname, - temp_service_path); - procarr[pg_iter] = - GNUNET_OS_start_process (GNUNET_NO, NULL, NULL, "scp", "scp", mytemp, arg, NULL); - GNUNET_assert (procarr[pg_iter] != NULL); - ret = GNUNET_OS_process_wait (procarr[pg_iter]); /* FIXME: schedule this, throttle! */ - GNUNET_OS_process_destroy (procarr[pg_iter]); - if (ret != GNUNET_OK) - { - /* FIXME: free contents of 'procarr' array */ - GNUNET_free (procarr); - GNUNET_free (temp_service_path); - GNUNET_free (mytemp); - GNUNET_free (arg); - return ret; - } - procarr[pg_iter] = NULL; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Copying file with command scp %s %s\n", mytemp, arg); - GNUNET_free (arg); - } - GNUNET_free (temp_service_path); - GNUNET_free (mytemp); - } - -#if NOT_STUPID - count = 0; - ret = GNUNET_SYSERR; - while ((count < max_wait) && (ret != GNUNET_OK)) - { - ret = GNUNET_OK; - for (pg_iter = 0; pg_iter < pg->total; pg_iter++) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Checking copy status of file %d\n", - pg_iter); - if (procarr[pg_iter] != NULL) /* Check for already completed! */ - { - if (GNUNET_OS_process_status (procarr[pg_iter], &type, &return_code) != - GNUNET_OK) - { - ret = GNUNET_SYSERR; - } - else if ((type != GNUNET_OS_PROCESS_EXITED) || (return_code != 0)) - { - ret = GNUNET_SYSERR; - } - else - { - GNUNET_OS_process_destroy (procarr[pg_iter]); - procarr[pg_iter] = NULL; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "File %d copied\n", pg_iter); - } - } - } - count++; - if (ret == GNUNET_SYSERR) - { - /* FIXME: why sleep here? -CG */ - sleep (1); - } - } - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Finished copying all friend files!\n"); -#endif - GNUNET_free (procarr); - return ret; -} - -/* - * Create the blacklist files based on the PeerConnection's - * of each peer in the peer group, and copy the files - * to the appropriate place. - * - * @param pg the peer group we are dealing with - * @param transports space delimited list of transports to blacklist - */ -static int -create_and_copy_blacklist_files (struct GNUNET_TESTING_PeerGroup *pg, - const char *transports) -{ - FILE *temp_file_handle; - unsigned int pg_iter; - char *temp_service_path; - struct GNUNET_OS_Process **procarr; - char *arg; - char *mytemp; - enum GNUNET_OS_ProcessStatusType type; - unsigned long return_code; - int count; - int ret; - int max_wait = 10; - int transport_len; - unsigned int i; - char *pos; - char *temp_transports; - -#if OLD - struct GNUNET_CRYPTO_HashAsciiEncoded peer_enc; - struct PeerConnection *conn_iter; -#else - static struct BlacklistContext blacklist_ctx; -#endif - - procarr = GNUNET_malloc (sizeof (struct GNUNET_OS_Process *) * pg->total); - for (pg_iter = 0; pg_iter < pg->total; pg_iter++) - { - mytemp = GNUNET_DISK_mktemp ("blacklist"); - GNUNET_assert (mytemp != NULL); - temp_file_handle = FOPEN (mytemp, "wt"); - GNUNET_assert (temp_file_handle != NULL); - temp_transports = GNUNET_strdup (transports); -#if !OLD - blacklist_ctx.temp_file_handle = temp_file_handle; -#endif - transport_len = strlen (temp_transports) + 1; - pos = NULL; - - for (i = 0; i < transport_len; i++) - { - if ((temp_transports[i] == ' ') && (pos == NULL)) - continue; /* At start of string (whitespace) */ - else if ((temp_transports[i] == ' ') || (temp_transports[i] == '\0')) /* At end of string */ - { - temp_transports[i] = '\0'; -#if OLD - conn_iter = pg->peers[pg_iter].blacklisted_peers_head; - while (conn_iter != NULL) - { - GNUNET_CRYPTO_hash_to_enc (&pg->peers[conn_iter->index].daemon-> - id.hashPubKey, &peer_enc); - FPRINTF (temp_file_handle, "%s:%s\n", pos, (char *) &peer_enc); - conn_iter = conn_iter->next; - } -#else - blacklist_ctx.transport = pos; - (void) GNUNET_CONTAINER_multihashmap_iterate (pg-> - peers - [pg_iter].blacklisted_peers, - &blacklist_file_iterator, - &blacklist_ctx); -#endif - pos = NULL; - } /* At beginning of actual string */ - else if (pos == NULL) - { - pos = &temp_transports[i]; - } - } - - GNUNET_free (temp_transports); - FCLOSE (temp_file_handle); - - if (GNUNET_OK != - GNUNET_CONFIGURATION_get_value_string (pg->peers[pg_iter].daemon->cfg, - "PATHS", "SERVICEHOME", - &temp_service_path)) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - _ - ("No `%s' specified in peer configuration in section `%s', cannot copy friends file!\n"), - "SERVICEHOME", "PATHS"); - if (UNLINK (mytemp) != 0) - GNUNET_log_strerror_file (GNUNET_ERROR_TYPE_WARNING, "unlink", mytemp); - GNUNET_free (mytemp); - break; - } - - if (pg->peers[pg_iter].daemon->hostname == NULL) /* Local, just copy the file */ - { - GNUNET_asprintf (&arg, "%s/blacklist", temp_service_path); - RENAME (mytemp, arg); - procarr[pg_iter] = NULL; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Copying file with RENAME (%s,%s)\n", mytemp, arg); - GNUNET_free (arg); - } - else /* Remote, scp the file to the correct place */ - { - if (NULL != pg->peers[pg_iter].daemon->username) - GNUNET_asprintf (&arg, "%s@%s:%s/blacklist", - pg->peers[pg_iter].daemon->username, - pg->peers[pg_iter].daemon->hostname, - temp_service_path); - else - GNUNET_asprintf (&arg, "%s:%s/blacklist", - pg->peers[pg_iter].daemon->hostname, - temp_service_path); - procarr[pg_iter] = - GNUNET_OS_start_process (GNUNET_NO, NULL, NULL, "scp", "scp", mytemp, arg, NULL); - GNUNET_assert (procarr[pg_iter] != NULL); - GNUNET_OS_process_wait (procarr[pg_iter]); /* FIXME: add scheduled blacklist file copy that parallelizes file copying! */ - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Copying file with command scp %s %s\n", mytemp, arg); - GNUNET_free (arg); - } - GNUNET_free (temp_service_path); - GNUNET_free (mytemp); - } - - count = 0; - ret = GNUNET_SYSERR; - while ((count < max_wait) && (ret != GNUNET_OK)) - { - ret = GNUNET_OK; - for (pg_iter = 0; pg_iter < pg->total; pg_iter++) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Checking copy status of file %d\n", pg_iter); - if (procarr[pg_iter] != NULL) /* Check for already completed! */ - { - if (GNUNET_OS_process_status (procarr[pg_iter], &type, &return_code) != - GNUNET_OK) - { - ret = GNUNET_SYSERR; - } - else if ((type != GNUNET_OS_PROCESS_EXITED) || (return_code != 0)) - { - ret = GNUNET_SYSERR; - } - else - { - GNUNET_OS_process_destroy (procarr[pg_iter]); - procarr[pg_iter] = NULL; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "File %d copied\n", pg_iter); - } - } - } - count++; - if (ret == GNUNET_SYSERR) - { - /* FIXME: why sleep here? -CG */ - sleep (1); - } - } - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Finished copying all blacklist files!\n"); - GNUNET_free (procarr); - return ret; -} - -/* Forward Declaration */ -static void -schedule_connect (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc); - -/** - * Choose a random peer's next connection to create, and - * call schedule_connect to set up the connect task. - * - * @param pg the peer group to connect - */ -static void -preschedule_connect (struct GNUNET_TESTING_PeerGroup *pg) -{ - struct ConnectTopologyContext *ct_ctx = &pg->ct_ctx; - struct PeerConnection *connection_iter; - struct ConnectContext *connect_context; - uint32_t random_peer; - - if (ct_ctx->remaining_connections == 0) - return; - random_peer = - GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK, pg->total); - while (pg->peers[random_peer].connect_peers_head == NULL) - random_peer = - GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK, pg->total); - - connection_iter = pg->peers[random_peer].connect_peers_head; - connect_context = GNUNET_malloc (sizeof (struct ConnectContext)); - connect_context->first_index = random_peer; - connect_context->second_index = connection_iter->index; - connect_context->ct_ctx = ct_ctx; - connect_context->task = - GNUNET_SCHEDULER_add_now (&schedule_connect, connect_context); - GNUNET_CONTAINER_DLL_insert (pg->cc_head, pg->cc_tail, connect_context); - GNUNET_CONTAINER_DLL_remove (pg->peers[random_peer].connect_peers_head, - pg->peers[random_peer].connect_peers_tail, - connection_iter); - GNUNET_free (connection_iter); - ct_ctx->remaining_connections--; -} - -#if USE_SEND_HELLOS -/* Forward declaration */ -static void -schedule_send_hellos (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc); - -/** - * Close connections and free the hello context. - * - * @param cls the 'struct SendHelloContext *' - * @param tc scheduler context - */ -static void -free_hello_context (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - struct SendHelloContext *send_hello_context = cls; - - if (send_hello_context->peer->daemon->server != NULL) - { - GNUNET_CORE_disconnect (send_hello_context->peer->daemon->server); - send_hello_context->peer->daemon->server = NULL; - } - if (send_hello_context->peer->daemon->th != NULL) - { - GNUNET_TRANSPORT_disconnect (send_hello_context->peer->daemon->th); - send_hello_context->peer->daemon->th = NULL; - } - if (send_hello_context->core_connect_task != GNUNET_SCHEDULER_NO_TASK) - { - GNUNET_SCHEDULER_cancel (send_hello_context->core_connect_task); - send_hello_context->core_connect_task = GNUNET_SCHEDULER_NO_TASK; - } - send_hello_context->pg->outstanding_connects--; - GNUNET_free (send_hello_context); -} - -/** - * For peers that haven't yet connected, notify - * the caller that they have failed (timeout). - * - * @param cls the 'struct SendHelloContext *' - * @param tc scheduler context - */ -static void -notify_remaining_connections_failed (void *cls, - const struct GNUNET_SCHEDULER_TaskContext - *tc) -{ - struct SendHelloContext *send_hello_context = cls; - struct GNUNET_TESTING_PeerGroup *pg = send_hello_context->pg; - struct PeerConnection *connection; - - GNUNET_CORE_disconnect (send_hello_context->peer->daemon->server); - send_hello_context->peer->daemon->server = NULL; - - connection = send_hello_context->peer->connect_peers_head; - - while (connection != NULL) - { - if (pg->notify_connection != NULL) - { - pg->notify_connection (pg->notify_connection_cls, &send_hello_context->peer->daemon->id, &pg->peers[connection->index].daemon->id, 0, /* FIXME */ - send_hello_context->peer->daemon->cfg, - pg->peers[connection->index].daemon->cfg, - send_hello_context->peer->daemon, - pg->peers[connection->index].daemon, - "Peers failed to connect (timeout)"); - } - GNUNET_CONTAINER_DLL_remove (send_hello_context->peer->connect_peers_head, - send_hello_context->peer->connect_peers_tail, - connection); - GNUNET_free (connection); - connection = connection->next; - } - GNUNET_SCHEDULER_add_now (&free_hello_context, send_hello_context); -#if BAD - other_peer = &pg->peers[connection->index]; -#endif -} - -/** - * For peers that haven't yet connected, send - * CORE connect requests. - * - * @param cls the 'struct SendHelloContext *' - * @param tc scheduler context - */ -static void -send_core_connect_requests (void *cls, - const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - struct SendHelloContext *send_hello_context = cls; - struct PeerConnection *conn; - - GNUNET_assert (send_hello_context->peer->daemon->server != NULL); - - send_hello_context->core_connect_task = GNUNET_SCHEDULER_NO_TASK; - - send_hello_context->connect_attempts++; - if (send_hello_context->connect_attempts < - send_hello_context->pg->ct_ctx.connect_attempts) - { - conn = send_hello_context->peer->connect_peers_head; - while (conn != NULL) - { - GNUNET_TRANSPORT_try_connect (send_hello_context->peer->daemon->th, - &send_hello_context->pg->peers[conn-> - index].daemon-> - id); - conn = conn->next; - } - send_hello_context->core_connect_task = - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_divide - (send_hello_context->pg-> - ct_ctx.connect_timeout, - send_hello_context->pg-> - ct_ctx.connect_attempts), - &send_core_connect_requests, - send_hello_context); - } - else - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Timeout before all connections created, marking rest as failed!\n"); - GNUNET_SCHEDULER_add_now (¬ify_remaining_connections_failed, - send_hello_context); - } - -} - -/** - * Success, connection is up. Signal client our success. - * - * @param cls our "struct SendHelloContext" - * @param peer identity of the peer that has connected - * @param atsi performance information - * - * FIXME: remove peers from BOTH lists, call notify twice, should - * double the speed of connections as long as the list iteration - * doesn't take too long! - */ -static void -core_connect_notify (void *cls, const struct GNUNET_PeerIdentity *peer, - const struct GNUNET_ATS_Information *atsi) -{ - struct SendHelloContext *send_hello_context = cls; - struct PeerConnection *connection; - struct GNUNET_TESTING_PeerGroup *pg = send_hello_context->pg; - -#if BAD - struct PeerData *other_peer; -#endif - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Connected peer %s to peer %s\n", - ctx->d1->shortname, GNUNET_i2s (peer)); - if (0 == - memcmp (&send_hello_context->peer->daemon->id, peer, - sizeof (struct GNUNET_PeerIdentity))) - return; - - connection = send_hello_context->peer->connect_peers_head; -#if BAD - other_peer = NULL; -#endif - - while ((connection != NULL) && - (0 != - memcmp (&pg->peers[connection->index].daemon->id, peer, - sizeof (struct GNUNET_PeerIdentity)))) - { - connection = connection->next; - } - - if (connection == NULL) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Connected peer %s to %s, not in list (no problem(?))\n", - GNUNET_i2s (peer), send_hello_context->peer->daemon->shortname); - } - else - { -#if BAD - other_peer = &pg->peers[connection->index]; -#endif - if (pg->notify_connection != NULL) - { - pg->notify_connection (pg->notify_connection_cls, &send_hello_context->peer->daemon->id, peer, 0, /* FIXME */ - send_hello_context->peer->daemon->cfg, - pg->peers[connection->index].daemon->cfg, - send_hello_context->peer->daemon, - pg->peers[connection->index].daemon, NULL); - } - GNUNET_CONTAINER_DLL_remove (send_hello_context->peer->connect_peers_head, - send_hello_context->peer->connect_peers_tail, - connection); - GNUNET_free (connection); - } - -#if BAD - /* Notify of reverse connection and remove from other peers list of outstanding */ - if (other_peer != NULL) - { - connection = other_peer->connect_peers_head; - while ((connection != NULL) && - (0 != - memcmp (&send_hello_context->peer->daemon->id, - &pg->peers[connection->index].daemon->id, - sizeof (struct GNUNET_PeerIdentity)))) - { - connection = connection->next; - } - if (connection != NULL) - { - if (pg->notify_connection != NULL) - { - pg->notify_connection (pg->notify_connection_cls, peer, &send_hello_context->peer->daemon->id, 0, /* FIXME */ - pg->peers[connection->index].daemon->cfg, - send_hello_context->peer->daemon->cfg, - pg->peers[connection->index].daemon, - send_hello_context->peer->daemon, NULL); - } - - GNUNET_CONTAINER_DLL_remove (other_peer->connect_peers_head, - other_peer->connect_peers_tail, connection); - GNUNET_free (connection); - } - } -#endif - - if (send_hello_context->peer->connect_peers_head == NULL) - { - GNUNET_SCHEDULER_add_now (&free_hello_context, send_hello_context); - } -} - -/** - * Notify of a successful connection to the core service. - * - * @param cls a struct SendHelloContext * - * @param server handle to the core service - * @param my_identity the peer identity of this peer - */ -void -core_init (void *cls, struct GNUNET_CORE_Handle *server, - struct GNUNET_PeerIdentity *my_identity) -{ - struct SendHelloContext *send_hello_context = cls; - - send_hello_context->core_ready = GNUNET_YES; -} - -/** - * Function called once a hello has been sent - * to the transport, move on to the next one - * or go away forever. - * - * @param cls the 'struct SendHelloContext *' - * @param tc scheduler context - */ -static void -hello_sent_callback (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - struct SendHelloContext *send_hello_context = cls; - - //unsigned int pg_iter; - if ((tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN) != 0) - { - GNUNET_free (send_hello_context); - return; - } - - send_hello_context->pg->remaining_hellos--; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Sent HELLO, have %d remaining!\n", - send_hello_context->pg->remaining_hellos); - if (send_hello_context->peer_pos == NULL) /* All HELLOs (for this peer!) have been transmitted! */ - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "All hellos for this peer sent, disconnecting transport!\n"); - GNUNET_assert (send_hello_context->peer->daemon->th != NULL); - GNUNET_TRANSPORT_disconnect (send_hello_context->peer->daemon->th); - send_hello_context->peer->daemon->th = NULL; - GNUNET_assert (send_hello_context->peer->daemon->server == NULL); - send_hello_context->peer->daemon->server = - GNUNET_CORE_connect (send_hello_context->peer->cfg, 1, - send_hello_context, &core_init, - &core_connect_notify, NULL, NULL, NULL, GNUNET_NO, - NULL, GNUNET_NO, no_handlers); - - send_hello_context->core_connect_task = - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_divide - (send_hello_context->pg-> - ct_ctx.connect_timeout, - send_hello_context->pg-> - ct_ctx.connect_attempts), - &send_core_connect_requests, - send_hello_context); - } - else - GNUNET_SCHEDULER_add_now (&schedule_send_hellos, send_hello_context); -} - -/** - * Connect to a peer, give it all the HELLO's of those peers - * we will later ask it to connect to. - * - * @param ct_ctx the overall connection context - */ -static void -schedule_send_hellos (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - struct SendHelloContext *send_hello_context = cls; - struct GNUNET_TESTING_PeerGroup *pg = send_hello_context->pg; - - if ((tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN) != 0) - { - GNUNET_free (send_hello_context); - return; - } - - GNUNET_assert (send_hello_context->peer_pos != NULL); /* All of the HELLO sends to be scheduled have been scheduled! */ - - if (((send_hello_context->peer->daemon->th == NULL) && - (pg->outstanding_connects > pg->max_outstanding_connections)) || - (pg->stop_connects == GNUNET_YES)) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Delaying connect, we have too many outstanding connections!\n"); - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply - (GNUNET_TIME_UNIT_MILLISECONDS, 100), - &schedule_send_hellos, send_hello_context); - } - else - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Creating connection, outstanding_connections is %d\n", - outstanding_connects); - if (send_hello_context->peer->daemon->th == NULL) - { - pg->outstanding_connects++; /* Actual TRANSPORT, CORE connections! */ - send_hello_context->peer->daemon->th = - GNUNET_TRANSPORT_connect (send_hello_context->peer->cfg, NULL, - send_hello_context, NULL, NULL, NULL); - } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Offering HELLO of peer %s to peer %s\n", - send_hello_context->peer->daemon->shortname, - pg->peers[send_hello_context->peer_pos->index]. - daemon->shortname); - GNUNET_TRANSPORT_offer_hello (send_hello_context->peer->daemon->th, - (const struct GNUNET_MessageHeader *) - pg->peers[send_hello_context->peer_pos-> - index].daemon->hello, - &hello_sent_callback, send_hello_context); - send_hello_context->peer_pos = send_hello_context->peer_pos->next; - GNUNET_assert (send_hello_context->peer->daemon->th != NULL); - } -} -#endif - -/** - * Internal notification of a connection, kept so that we can ensure some connections - * happen instead of flooding all testing daemons with requests to connect. - */ -static void -internal_connect_notify (void *cls, const struct GNUNET_PeerIdentity *first, - const struct GNUNET_PeerIdentity *second, - uint32_t distance, - const struct GNUNET_CONFIGURATION_Handle *first_cfg, - const struct GNUNET_CONFIGURATION_Handle *second_cfg, - struct GNUNET_TESTING_Daemon *first_daemon, - struct GNUNET_TESTING_Daemon *second_daemon, - const char *emsg) -{ - struct ConnectContext *connect_ctx = cls; - struct ConnectTopologyContext *ct_ctx = connect_ctx->ct_ctx; - struct GNUNET_TESTING_PeerGroup *pg = ct_ctx->pg; - struct PeerConnection *connection; - - GNUNET_assert (NULL != connect_ctx->cc); - connect_ctx->cc = NULL; - GNUNET_assert (0 < pg->outstanding_connects); - pg->outstanding_connects--; - GNUNET_CONTAINER_DLL_remove (pg->cc_head, pg->cc_tail, connect_ctx); - /* - * Check whether the inverse connection has been scheduled yet, - * if not, we can remove it from the other peers list and avoid - * even trying to connect them again! - */ - connection = pg->peers[connect_ctx->second_index].connect_peers_head; -#if BAD - other_peer = NULL; -#endif - - while ((connection != NULL) && - (0 != - memcmp (first, &pg->peers[connection->index].daemon->id, - sizeof (struct GNUNET_PeerIdentity)))) - connection = connection->next; - - if (connection != NULL) /* Can safely remove! */ - { - GNUNET_assert (0 < ct_ctx->remaining_connections); - ct_ctx->remaining_connections--; - if (pg->notify_connection != NULL) /* Notify of reverse connection */ - pg->notify_connection (pg->notify_connection_cls, second, first, distance, - second_cfg, first_cfg, second_daemon, first_daemon, - emsg); - - GNUNET_CONTAINER_DLL_remove (pg-> - peers[connect_ctx-> - second_index].connect_peers_head, - pg->peers[connect_ctx-> - second_index].connect_peers_tail, - connection); - GNUNET_free (connection); - } - - if (ct_ctx->remaining_connections == 0) - { - if (ct_ctx->notify_connections_done != NULL) - { - ct_ctx->notify_connections_done (ct_ctx->notify_cls, NULL); - ct_ctx->notify_connections_done = NULL; - } - } - else - preschedule_connect (pg); - - if (pg->notify_connection != NULL) - pg->notify_connection (pg->notify_connection_cls, first, second, distance, - first_cfg, second_cfg, first_daemon, second_daemon, - emsg); - GNUNET_free (connect_ctx); -} - -/** - * Either delay a connection (because there are too many outstanding) - * or schedule it for right now. - * - * @param cls a connection context - * @param tc the task runtime context - */ -static void -schedule_connect (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - struct ConnectContext *connect_context = cls; - struct GNUNET_TESTING_PeerGroup *pg = connect_context->ct_ctx->pg; - - connect_context->task = GNUNET_SCHEDULER_NO_TASK; - if ((tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN) != 0) - return; - - if ((pg->outstanding_connects > pg->max_outstanding_connections) || - (pg->stop_connects == GNUNET_YES)) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Delaying connect, we have too many outstanding connections!\n"); - connect_context->task = - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply - (GNUNET_TIME_UNIT_MILLISECONDS, 100), - &schedule_connect, connect_context); - return; - } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Creating connection, outstanding_connections is %d (max %d)\n", - pg->outstanding_connects, pg->max_outstanding_connections); - pg->outstanding_connects++; - pg->total_connects_scheduled++; - GNUNET_assert (NULL == connect_context->cc); - connect_context->cc = - GNUNET_TESTING_daemons_connect (pg-> - peers[connect_context-> - first_index].daemon, - pg->peers[connect_context-> - second_index].daemon, - connect_context->ct_ctx->connect_timeout, - connect_context->ct_ctx->connect_attempts, -#if USE_SEND_HELLOS - GNUNET_NO, -#else - GNUNET_YES, -#endif - &internal_connect_notify, - connect_context); - -} - -#if !OLD -/** - * Iterator for actually scheduling connections to be created - * between two peers. - * - * @param cls closure, a GNUNET_TESTING_Daemon - * @param key the key the second Daemon was stored under - * @param value the GNUNET_TESTING_Daemon that the first is to connect to - * - * @return GNUNET_YES to continue iteration - */ -static int -connect_iterator (void *cls, const GNUNET_HashCode * key, void *value) -{ - struct ConnectTopologyContext *ct_ctx = cls; - struct PeerData *first = ct_ctx->first; - struct GNUNET_TESTING_Daemon *second = value; - struct ConnectContext *connect_context; - - connect_context = GNUNET_malloc (sizeof (struct ConnectContext)); - connect_context->first = first->daemon; - connect_context->second = second; - connect_context->ct_ctx = ct_ctx; - connect_context->task = - GNUNET_SCHEDULER_add_now (&schedule_connect, connect_context); - GNUNET_CONTAINER_DLL_insert (ct_ctx->pg->cc_head, ct_ctx->pg->cc_tail, - connect_context); - return GNUNET_YES; -} -#endif - -#if !OLD -/** - * Iterator for copying all entries in the allowed hashmap to the - * connect hashmap. - * - * @param cls closure, a GNUNET_TESTING_Daemon - * @param key the key the second Daemon was stored under - * @param value the GNUNET_TESTING_Daemon that the first is to connect to - * - * @return GNUNET_YES to continue iteration - */ -static int -copy_topology_iterator (void *cls, const GNUNET_HashCode * key, void *value) -{ - struct PeerData *first = cls; - - GNUNET_assert (GNUNET_OK == - GNUNET_CONTAINER_multihashmap_put (first->connect_peers, key, - value, - GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY)); - - return GNUNET_YES; -} -#endif - -/** - * Make the peers to connect the same as those that are allowed to be - * connected. - * - * @param pg the peer group - */ -static int -copy_allowed_topology (struct GNUNET_TESTING_PeerGroup *pg) -{ - unsigned int pg_iter; - int ret; - int total; - -#if OLD - struct PeerConnection *iter; -#endif - total = 0; - ret = 0; - for (pg_iter = 0; pg_iter < pg->total; pg_iter++) - { -#if OLD - iter = pg->peers[pg_iter].allowed_peers_head; - while (iter != NULL) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Creating connection between %d and %d\n", pg_iter, - iter->index); - total += add_connections (pg, pg_iter, iter->index, CONNECT, GNUNET_YES); - //total += add_actual_connections(pg, pg_iter, iter->index); - iter = iter->next; - } -#else - ret = - GNUNET_CONTAINER_multihashmap_iterate (pg->peers[pg_iter].allowed_peers, - ©_topology_iterator, - &pg->peers[pg_iter]); -#endif - if (GNUNET_SYSERR == ret) - return GNUNET_SYSERR; - - total = total + ret; - } - - return total; -} - -/** - * Connect the topology as specified by the PeerConnection's - * of each peer in the peer group - * - * @param pg the peer group we are dealing with - * @param connect_timeout how long try connecting two peers - * @param connect_attempts how many times (max) to attempt - * @param notify_callback callback to notify when finished - * @param notify_cls closure for notify callback - * - * @return the number of connections that will be attempted - */ -static int -connect_topology (struct GNUNET_TESTING_PeerGroup *pg, - struct GNUNET_TIME_Relative connect_timeout, - unsigned int connect_attempts, - GNUNET_TESTING_NotifyCompletion notify_callback, - void *notify_cls) -{ - unsigned int pg_iter; - unsigned int total; - -#if OLD - struct PeerConnection *connection_iter; -#endif -#if USE_SEND_HELLOS - struct SendHelloContext *send_hello_context; -#endif - - total = 0; - pg->ct_ctx.notify_connections_done = notify_callback; - pg->ct_ctx.notify_cls = notify_cls; - pg->ct_ctx.pg = pg; - - for (pg_iter = 0; pg_iter < pg->total; pg_iter++) - { -#if OLD - connection_iter = pg->peers[pg_iter].connect_peers_head; - while (connection_iter != NULL) - { - connection_iter = connection_iter->next; - total++; - } -#else - total += - GNUNET_CONTAINER_multihashmap_size (pg->peers[pg_iter].connect_peers); -#endif - } - - if (total == 0) - return total; - - pg->ct_ctx.connect_timeout = connect_timeout; - pg->ct_ctx.connect_attempts = connect_attempts; - pg->ct_ctx.remaining_connections = total; - -#if USE_SEND_HELLOS - /* First give all peers the HELLO's of other peers (connect to first peer's transport service, give HELLO's of other peers, continue...) */ - pg->remaining_hellos = total; - for (pg_iter = 0; pg_iter < pg->total; pg_iter++) - { - send_hello_context = GNUNET_malloc (sizeof (struct SendHelloContext)); - send_hello_context->peer = &pg->peers[pg_iter]; - send_hello_context->peer_pos = pg->peers[pg_iter].connect_peers_head; - send_hello_context->pg = pg; - GNUNET_SCHEDULER_add_now (&schedule_send_hellos, send_hello_context); - } -#else - for (pg_iter = 0; pg_iter < pg->max_outstanding_connections; pg_iter++) - { - preschedule_connect (pg); - } -#endif - return total; - -} - -/** - * Takes a peer group and creates a topology based on the - * one specified. Creates a topology means generates friend - * files for the peers so they can only connect to those allowed - * by the topology. This will only have an effect once peers - * are started if the FRIENDS_ONLY option is set in the base - * config. Also takes an optional restrict topology which - * disallows connections based on particular transports - * UNLESS they are specified in the restricted topology. - * - * @param pg the peer group struct representing the running peers - * @param topology which topology to connect the peers in - * @param restrict_topology disallow restrict_transports transport - * connections to peers NOT in this topology - * use GNUNET_TESTING_TOPOLOGY_NONE for no restrictions - * @param restrict_transports space delimited list of transports to blacklist - * to create restricted topology - * - * @return the maximum number of connections were all allowed peers - * connected to each other - */ -unsigned int -GNUNET_TESTING_create_topology (struct GNUNET_TESTING_PeerGroup *pg, - enum GNUNET_TESTING_Topology topology, - enum GNUNET_TESTING_Topology restrict_topology, - const char *restrict_transports) -{ - int ret; - - unsigned int num_connections; - int unblacklisted_connections; - char *filename; - struct PeerConnection *conn_iter; - struct PeerConnection *temp_conn; - unsigned int off; - -#if !OLD - unsigned int i; - - for (i = 0; i < pg->total; i++) - { - pg->peers[i].allowed_peers = GNUNET_CONTAINER_multihashmap_create (100); - pg->peers[i].connect_peers = GNUNET_CONTAINER_multihashmap_create (100); - pg->peers[i].blacklisted_peers = GNUNET_CONTAINER_multihashmap_create (100); - pg->peers[i].pg = pg; - } -#endif - - switch (topology) - { - case GNUNET_TESTING_TOPOLOGY_CLIQUE: - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Creating clique topology\n"); - num_connections = create_clique (pg, &add_connections, ALLOWED, GNUNET_NO); - break; - case GNUNET_TESTING_TOPOLOGY_SMALL_WORLD_RING: - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Creating small world (ring) topology\n"); - num_connections = create_small_world_ring (pg, &add_connections, ALLOWED); - break; - case GNUNET_TESTING_TOPOLOGY_SMALL_WORLD: - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Creating small world (2d-torus) topology\n"); - num_connections = create_small_world (pg, &add_connections, ALLOWED); - break; - case GNUNET_TESTING_TOPOLOGY_RING: - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Creating ring topology\n"); - num_connections = create_ring (pg, &add_connections, ALLOWED); - break; - case GNUNET_TESTING_TOPOLOGY_2D_TORUS: - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Creating 2d torus topology\n"); - num_connections = create_2d_torus (pg, &add_connections, ALLOWED); - break; - case GNUNET_TESTING_TOPOLOGY_ERDOS_RENYI: - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Creating Erdos-Renyi topology\n"); - num_connections = create_erdos_renyi (pg, &add_connections, ALLOWED); - break; - case GNUNET_TESTING_TOPOLOGY_INTERNAT: - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Creating InterNAT topology\n"); - num_connections = create_nated_internet (pg, &add_connections, ALLOWED); - break; - case GNUNET_TESTING_TOPOLOGY_SCALE_FREE: - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Creating Scale Free topology\n"); - num_connections = create_scale_free (pg, &add_connections, ALLOWED); - break; - case GNUNET_TESTING_TOPOLOGY_LINE: - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Creating straight line topology\n"); - num_connections = create_line (pg, &add_connections, ALLOWED); - break; - case GNUNET_TESTING_TOPOLOGY_FROM_FILE: - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Creating topology from file!\n"); - if (GNUNET_OK == - GNUNET_CONFIGURATION_get_value_string (pg->cfg, "testing", - "topology_file", &filename)) - num_connections = - create_from_file (pg, filename, &add_connections, ALLOWED); - else - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Missing configuration option TESTING:TOPOLOGY_FILE for creating topology from file!\n"); - num_connections = 0; - } - break; - case GNUNET_TESTING_TOPOLOGY_NONE: - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - _ - ("Creating no allowed topology (all peers can connect at core level)\n")); - num_connections = pg->total * pg->total; /* Clique is allowed! */ - break; - default: - num_connections = 0; - break; - } - - if (GNUNET_YES == - GNUNET_CONFIGURATION_get_value_yesno (pg->cfg, "TESTING", "F2F")) - { - ret = create_and_copy_friend_files (pg); - if (ret != GNUNET_OK) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Failed during friend file copying!\n"); - return GNUNET_SYSERR; - } - else - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Friend files created/copied successfully!\n"); - } - } - - /* Use the create clique method to initially set all connections as blacklisted. */ - if ((restrict_topology != GNUNET_TESTING_TOPOLOGY_NONE) && - (restrict_topology != GNUNET_TESTING_TOPOLOGY_FROM_FILE)) - create_clique (pg, &add_connections, BLACKLIST, GNUNET_NO); - else - return num_connections; - - unblacklisted_connections = 0; - /* Un-blacklist connections as per the topology specified */ - switch (restrict_topology) - { - case GNUNET_TESTING_TOPOLOGY_CLIQUE: - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Blacklisting all but clique topology\n"); - unblacklisted_connections = - create_clique (pg, &remove_connections, BLACKLIST, GNUNET_NO); - break; - case GNUNET_TESTING_TOPOLOGY_SMALL_WORLD_RING: - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Blacklisting all but small world (ring) topology\n"); - unblacklisted_connections = - create_small_world_ring (pg, &remove_connections, BLACKLIST); - break; - case GNUNET_TESTING_TOPOLOGY_SMALL_WORLD: - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Blacklisting all but small world (2d-torus) topology\n"); - unblacklisted_connections = - create_small_world (pg, &remove_connections, BLACKLIST); - break; - case GNUNET_TESTING_TOPOLOGY_RING: - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Blacklisting all but ring topology\n"); - unblacklisted_connections = - create_ring (pg, &remove_connections, BLACKLIST); - break; - case GNUNET_TESTING_TOPOLOGY_2D_TORUS: - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Blacklisting all but 2d torus topology\n"); - unblacklisted_connections = - create_2d_torus (pg, &remove_connections, BLACKLIST); - break; - case GNUNET_TESTING_TOPOLOGY_ERDOS_RENYI: - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Blacklisting all but Erdos-Renyi topology\n"); - unblacklisted_connections = - create_erdos_renyi (pg, &remove_connections, BLACKLIST); - break; - case GNUNET_TESTING_TOPOLOGY_INTERNAT: - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Blacklisting all but InterNAT topology\n"); - -#if TOPOLOGY_HACK - for (off = 0; off < pg->total; off++) - { - conn_iter = pg->peers[off].allowed_peers_head; - while (conn_iter != NULL) - { - temp_conn = conn_iter->next; - GNUNET_free (conn_iter); - conn_iter = temp_conn; - } - pg->peers[off].allowed_peers_head = NULL; - pg->peers[off].allowed_peers_tail = NULL; - - conn_iter = pg->peers[off].connect_peers_head; - while (conn_iter != NULL) - { - temp_conn = conn_iter->next; - GNUNET_free (conn_iter); - conn_iter = temp_conn; - } - pg->peers[off].connect_peers_head = NULL; - pg->peers[off].connect_peers_tail = NULL; - } - unblacklisted_connections = - create_nated_internet_copy (pg, &remove_connections, BLACKLIST); -#else - unblacklisted_connections = - create_nated_internet (pg, &remove_connections, BLACKLIST); -#endif - - break; - case GNUNET_TESTING_TOPOLOGY_SCALE_FREE: - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Blacklisting all but Scale Free topology\n"); - unblacklisted_connections = - create_scale_free (pg, &remove_connections, BLACKLIST); - break; - case GNUNET_TESTING_TOPOLOGY_LINE: - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Blacklisting all but straight line topology\n"); - unblacklisted_connections = - create_line (pg, &remove_connections, BLACKLIST); - default: - break; - } - - if ((unblacklisted_connections > 0) && (restrict_transports != NULL)) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Creating blacklist with `%s'\n", - restrict_transports); - ret = create_and_copy_blacklist_files (pg, restrict_transports); - if (ret != GNUNET_OK) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Failed during blacklist file copying!\n"); - return 0; - } - else - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Blacklist files created/copied successfully!\n"); - } - } - return num_connections; -} - -#if !OLD -/** - * Iterator for choosing random peers to connect. - * - * @param cls closure, a RandomContext - * @param key the key the second Daemon was stored under - * @param value the GNUNET_TESTING_Daemon that the first is to connect to - * - * @return GNUNET_YES to continue iteration - */ -static int -random_connect_iterator (void *cls, const GNUNET_HashCode * key, void *value) -{ - struct RandomContext *random_ctx = cls; - double random_number; - uint32_t second_pos; - GNUNET_HashCode first_hash; - - random_number = - ((double) - GNUNET_CRYPTO_random_u64 (GNUNET_CRYPTO_QUALITY_WEAK, - UINT64_MAX)) / ((double) UINT64_MAX); - if (random_number < random_ctx->percentage) - { - GNUNET_assert (GNUNET_OK == - GNUNET_CONTAINER_multihashmap_put (random_ctx-> - first->connect_peers_working_set, - key, value, - GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY)); - } - - /* Now we have considered this particular connection, remove it from the second peer so it's not double counted */ - uid_from_hash (key, &second_pos); - hash_from_uid (random_ctx->first_uid, &first_hash); - GNUNET_assert (random_ctx->pg->total > second_pos); - GNUNET_assert (GNUNET_YES == - GNUNET_CONTAINER_multihashmap_remove (random_ctx-> - pg->peers - [second_pos].connect_peers, - &first_hash, - random_ctx-> - first->daemon)); - - return GNUNET_YES; -} - -/** - * Iterator for adding at least X peers to a peers connection set. - * - * @param cls closure, MinimumContext - * @param key the key the second Daemon was stored under - * @param value the GNUNET_TESTING_Daemon that the first is to connect to - * - * @return GNUNET_YES to continue iteration - */ -static int -minimum_connect_iterator (void *cls, const GNUNET_HashCode * key, void *value) -{ - struct MinimumContext *min_ctx = cls; - uint32_t second_pos; - GNUNET_HashCode first_hash; - unsigned int i; - - if (GNUNET_CONTAINER_multihashmap_size - (min_ctx->first->connect_peers_working_set) < min_ctx->num_to_add) - { - for (i = 0; i < min_ctx->num_to_add; i++) - { - if (min_ctx->pg_array[i] == min_ctx->current) - { - GNUNET_assert (GNUNET_OK == - GNUNET_CONTAINER_multihashmap_put (min_ctx-> - first->connect_peers_working_set, - key, value, - GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY)); - uid_from_hash (key, &second_pos); - hash_from_uid (min_ctx->first_uid, &first_hash); - GNUNET_assert (min_ctx->pg->total > second_pos); - GNUNET_assert (GNUNET_OK == - GNUNET_CONTAINER_multihashmap_put (min_ctx-> - pg->peers - [second_pos].connect_peers_working_set, - &first_hash, - min_ctx->first-> - daemon, - GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY)); - /* Now we have added this particular connection, remove it from the second peer's map so it's not double counted */ - GNUNET_assert (GNUNET_YES == - GNUNET_CONTAINER_multihashmap_remove (min_ctx-> - pg->peers - [second_pos].connect_peers, - &first_hash, - min_ctx-> - first->daemon)); - } - } - min_ctx->current++; - return GNUNET_YES; - } - else - return GNUNET_NO; /* We can stop iterating, we have enough peers! */ - -} - -/** - * Iterator for adding peers to a connection set based on a depth first search. - * - * @param cls closure, MinimumContext - * @param key the key the second daemon was stored under - * @param value the GNUNET_TESTING_Daemon that the first is to connect to - * - * @return GNUNET_YES to continue iteration - */ -static int -dfs_connect_iterator (void *cls, const GNUNET_HashCode * key, void *value) -{ - struct DFSContext *dfs_ctx = cls; - GNUNET_HashCode first_hash; - - if (dfs_ctx->current == dfs_ctx->chosen) - { - GNUNET_assert (GNUNET_OK == - GNUNET_CONTAINER_multihashmap_put (dfs_ctx-> - first->connect_peers_working_set, - key, value, - GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY)); - uid_from_hash (key, &dfs_ctx->second_uid); - hash_from_uid (dfs_ctx->first_uid, &first_hash); - GNUNET_assert (GNUNET_OK == - GNUNET_CONTAINER_multihashmap_put (dfs_ctx-> - pg->peers[dfs_ctx-> - second_uid].connect_peers_working_set, - &first_hash, - dfs_ctx->first->daemon, - GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY)); - GNUNET_assert (GNUNET_YES == - GNUNET_CONTAINER_multihashmap_remove (dfs_ctx-> - pg->peers - [dfs_ctx->second_uid].connect_peers, - &first_hash, - dfs_ctx-> - first->daemon)); - /* Can't remove second from first yet because we are currently iterating, hence the return value in the DFSContext! */ - return GNUNET_NO; /* We have found our peer, don't iterate more */ - } - - dfs_ctx->current++; - return GNUNET_YES; -} -#endif - -/** - * From the set of connections possible, choose percentage percent of connections - * to actually connect. - * - * @param pg the peergroup we are dealing with - * @param percentage what percent of total connections to make - */ -void -choose_random_connections (struct GNUNET_TESTING_PeerGroup *pg, - double percentage) -{ - uint32_t pg_iter; - -#if OLD - struct PeerConnection *conn_iter; - double random_number; -#else - struct RandomContext random_ctx; -#endif - - for (pg_iter = 0; pg_iter < pg->total; pg_iter++) - { -#if OLD - conn_iter = pg->peers[pg_iter].connect_peers_head; - while (conn_iter != NULL) - { - random_number = - ((double) - GNUNET_CRYPTO_random_u64 (GNUNET_CRYPTO_QUALITY_WEAK, - UINT64_MAX)) / ((double) UINT64_MAX); - if (random_number < percentage) - { - add_connections (pg, pg_iter, conn_iter->index, WORKING_SET, - GNUNET_YES); - } - conn_iter = conn_iter->next; - } -#else - random_ctx.first_uid = pg_iter; - random_ctx.first = &pg->peers[pg_iter]; - random_ctx.percentage = percentage; - random_ctx.pg = pg; - pg->peers[pg_iter].connect_peers_working_set = - GNUNET_CONTAINER_multihashmap_create (pg->total); - GNUNET_CONTAINER_multihashmap_iterate (pg->peers[pg_iter].connect_peers, - &random_connect_iterator, - &random_ctx); - /* Now remove the old connections */ - GNUNET_CONTAINER_multihashmap_destroy (pg->peers[pg_iter].connect_peers); - /* And replace with the random set */ - pg->peers[pg_iter].connect_peers = - pg->peers[pg_iter].connect_peers_working_set; -#endif - } - - for (pg_iter = 0; pg_iter < pg->total; pg_iter++) - { - conn_iter = pg->peers[pg_iter].connect_peers_head; - while (pg->peers[pg_iter].connect_peers_head != NULL) - remove_connections (pg, pg_iter, - pg->peers[pg_iter].connect_peers_head->index, CONNECT, - GNUNET_YES); - - pg->peers[pg_iter].connect_peers_head = - pg->peers[pg_iter].connect_peers_working_set_head; - pg->peers[pg_iter].connect_peers_tail = - pg->peers[pg_iter].connect_peers_working_set_tail; - pg->peers[pg_iter].connect_peers_working_set_head = NULL; - pg->peers[pg_iter].connect_peers_working_set_tail = NULL; - } -} - -/** - * Count the number of connections in a linked list of connections. - * - * @param conn_list the connection list to get the count of - * - * @return the number of elements in the list - */ -static unsigned int -count_connections (struct PeerConnection *conn_list) -{ - struct PeerConnection *iter; - unsigned int count; - - count = 0; - iter = conn_list; - while (iter != NULL) - { - iter = iter->next; - count++; - } - return count; -} - -static unsigned int -count_workingset_connections (struct GNUNET_TESTING_PeerGroup *pg) -{ - unsigned int count; - unsigned int pg_iter; - -#if OLD - struct PeerConnection *conn_iter; -#endif - count = 0; - - for (pg_iter = 0; pg_iter < pg->total; pg_iter++) - { -#if OLD - conn_iter = pg->peers[pg_iter].connect_peers_working_set_head; - while (conn_iter != NULL) - { - count++; - conn_iter = conn_iter->next; - } -#else - count += - GNUNET_CONTAINER_multihashmap_size (pg-> - peers - [pg_iter].connect_peers_working_set); -#endif - } - - return count; -} - -static unsigned int -count_allowed_connections (struct GNUNET_TESTING_PeerGroup *pg) -{ - unsigned int count; - unsigned int pg_iter; - -#if OLD - struct PeerConnection *conn_iter; -#endif - - count = 0; - for (pg_iter = 0; pg_iter < pg->total; pg_iter++) - { -#if OLD - conn_iter = pg->peers[pg_iter].allowed_peers_head; - while (conn_iter != NULL) - { - count++; - conn_iter = conn_iter->next; - } -#else - count += - GNUNET_CONTAINER_multihashmap_size (pg->peers[pg_iter].allowed_peers); -#endif - } - - return count; -} - -/** - * From the set of connections possible, choose at least num connections per - * peer. - * - * @param pg the peergroup we are dealing with - * @param num how many connections at least should each peer have (if possible)? - */ -static void -choose_minimum (struct GNUNET_TESTING_PeerGroup *pg, unsigned int num) -{ -#if !OLD - struct MinimumContext minimum_ctx; -#else - struct PeerConnection *conn_iter; - unsigned int temp_list_size; - unsigned int i; - unsigned int count; - uint32_t random; /* Random list entry to connect peer to */ -#endif - uint32_t pg_iter; - -#if OLD - for (pg_iter = 0; pg_iter < pg->total; pg_iter++) - { - temp_list_size = count_connections (pg->peers[pg_iter].connect_peers_head); - if (temp_list_size == 0) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Peer %d has 0 connections!?!?\n", - pg_iter); - break; - } - for (i = 0; i < num; i++) - { - random = - GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK, temp_list_size); - conn_iter = pg->peers[pg_iter].connect_peers_head; - for (count = 0; count < random; count++) - conn_iter = conn_iter->next; - /* We now have a random connection, connect it! */ - GNUNET_assert (conn_iter != NULL); - add_connections (pg, pg_iter, conn_iter->index, WORKING_SET, GNUNET_YES); - } - } -#else - for (pg_iter = 0; pg_iter < pg->total; pg_iter++) - { - pg->peers[pg_iter].connect_peers_working_set = - GNUNET_CONTAINER_multihashmap_create (num); - } - - for (pg_iter = 0; pg_iter < pg->total; pg_iter++) - { - minimum_ctx.first_uid = pg_iter; - minimum_ctx.pg_array = - GNUNET_CRYPTO_random_permute (GNUNET_CRYPTO_QUALITY_WEAK, - GNUNET_CONTAINER_multihashmap_size - (pg->peers[pg_iter].connect_peers)); - minimum_ctx.first = &pg->peers[pg_iter]; - minimum_ctx.pg = pg; - minimum_ctx.num_to_add = num; - minimum_ctx.current = 0; - GNUNET_CONTAINER_multihashmap_iterate (pg->peers[pg_iter].connect_peers, - &minimum_connect_iterator, - &minimum_ctx); - } - - for (pg_iter = 0; pg_iter < pg->total; pg_iter++) - { - /* Remove the "old" connections */ - GNUNET_CONTAINER_multihashmap_destroy (pg->peers[pg_iter].connect_peers); - /* And replace with the working set */ - pg->peers[pg_iter].connect_peers = - pg->peers[pg_iter].connect_peers_working_set; - } -#endif - for (pg_iter = 0; pg_iter < pg->total; pg_iter++) - { - while (pg->peers[pg_iter].connect_peers_head != NULL) - { - conn_iter = pg->peers[pg_iter].connect_peers_head; - GNUNET_CONTAINER_DLL_remove (pg->peers[pg_iter].connect_peers_head, - pg->peers[pg_iter].connect_peers_tail, - conn_iter); - GNUNET_free (conn_iter); - /*remove_connections(pg, pg_iter, pg->peers[pg_iter].connect_peers_head->index, CONNECT, GNUNET_YES); */ - } - - pg->peers[pg_iter].connect_peers_head = - pg->peers[pg_iter].connect_peers_working_set_head; - pg->peers[pg_iter].connect_peers_tail = - pg->peers[pg_iter].connect_peers_working_set_tail; - pg->peers[pg_iter].connect_peers_working_set_head = NULL; - pg->peers[pg_iter].connect_peers_working_set_tail = NULL; - } -} - -#if !OLD -struct FindClosestContext -{ - /** - * The currently known closest peer. - */ - struct GNUNET_TESTING_Daemon *closest; - - /** - * The info for the peer we are adding connections for. - */ - struct PeerData *curr_peer; - - /** - * The distance (bits) between the current - * peer and the currently known closest. - */ - unsigned int closest_dist; - - /** - * The offset of the closest known peer in - * the peer group. - */ - unsigned int closest_num; -}; - -/** - * Iterator over hash map entries of the allowed - * peer connections. Find the closest, not already - * connected peer and return it. - * - * @param cls closure (struct FindClosestContext) - * @param key current key code (hash of offset in pg) - * @param value value in the hash map - a GNUNET_TESTING_Daemon - * @return GNUNET_YES if we should continue to - * iterate, - * GNUNET_NO if not. - */ -static int -find_closest_peers (void *cls, const GNUNET_HashCode * key, void *value) -{ - struct FindClosestContext *closest_ctx = cls; - struct GNUNET_TESTING_Daemon *daemon = value; - - if (((closest_ctx->closest == NULL) || - (GNUNET_CRYPTO_hash_matching_bits - (&daemon->id.hashPubKey, - &closest_ctx->curr_peer->daemon->id.hashPubKey) > - closest_ctx->closest_dist)) && - (GNUNET_YES != - GNUNET_CONTAINER_multihashmap_contains (closest_ctx-> - curr_peer->connect_peers, key))) - { - closest_ctx->closest_dist = - GNUNET_CRYPTO_hash_matching_bits (&daemon->id.hashPubKey, - &closest_ctx->curr_peer->daemon-> - id.hashPubKey); - closest_ctx->closest = daemon; - uid_from_hash (key, &closest_ctx->closest_num); - } - return GNUNET_YES; -} - -/** - * From the set of connections possible, choose at num connections per - * peer based on depth which are closest out of those allowed. Guaranteed - * to add num peers to connect to, provided there are that many peers - * in the underlay topology to connect to. - * - * @param pg the peergroup we are dealing with - * @param num how many connections at least should each peer have (if possible)? - * @param proc processor to actually add the connections - * @param list the peer list to use - */ -void -add_closest (struct GNUNET_TESTING_PeerGroup *pg, unsigned int num, - GNUNET_TESTING_ConnectionProcessor proc, enum PeerLists list) -{ -#if OLD - -#else - struct FindClosestContext closest_ctx; -#endif - uint32_t pg_iter; - uint32_t i; - - for (i = 0; i < num; i++) /* Each time find a closest peer (from those available) */ - { - for (pg_iter = 0; pg_iter < pg->total; pg_iter++) - { - closest_ctx.curr_peer = &pg->peers[pg_iter]; - closest_ctx.closest = NULL; - closest_ctx.closest_dist = 0; - closest_ctx.closest_num = 0; - GNUNET_CONTAINER_multihashmap_iterate (pg->peers[pg_iter].allowed_peers, - &find_closest_peers, &closest_ctx); - if (closest_ctx.closest != NULL) - { - GNUNET_assert (closest_ctx.closest_num < pg->total); - proc (pg, pg_iter, closest_ctx.closest_num, list); - } - } - } -} -#endif - -/** - * From the set of connections possible, choose at least num connections per - * peer based on depth first traversal of peer connections. If DFS leaves - * peers unconnected, ensure those peers get connections. - * - * @param pg the peergroup we are dealing with - * @param num how many connections at least should each peer have (if possible)? - */ -void -perform_dfs (struct GNUNET_TESTING_PeerGroup *pg, unsigned int num) -{ - uint32_t pg_iter; - uint32_t dfs_count; - uint32_t starting_peer; - uint32_t least_connections; - uint32_t random_connection; - -#if OLD - unsigned int temp_count; - struct PeerConnection *peer_iter; -#else - struct DFSContext dfs_ctx; - GNUNET_HashCode second_hash; -#endif - -#if OLD - starting_peer = 0; - dfs_count = 0; - while ((count_workingset_connections (pg) < num * pg->total) && - (count_allowed_connections (pg) > 0)) - { - if (dfs_count % pg->total == 0) /* Restart the DFS at some weakly connected peer */ - { - least_connections = -1; /* Set to very high number */ - for (pg_iter = 0; pg_iter < pg->total; pg_iter++) - { - temp_count = - count_connections (pg-> - peers[pg_iter].connect_peers_working_set_head); - if (temp_count < least_connections) - { - starting_peer = pg_iter; - least_connections = temp_count; - } - } - } - - temp_count = - count_connections (pg->peers[starting_peer].connect_peers_head); - if (temp_count == 0) - continue; /* FIXME: infinite loop? */ - - random_connection = - GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK, temp_count); - temp_count = 0; - peer_iter = pg->peers[starting_peer].connect_peers_head; - while (temp_count < random_connection) - { - peer_iter = peer_iter->next; - temp_count++; - } - GNUNET_assert (peer_iter != NULL); - add_connections (pg, starting_peer, peer_iter->index, WORKING_SET, - GNUNET_NO); - remove_connections (pg, starting_peer, peer_iter->index, CONNECT, - GNUNET_YES); - starting_peer = peer_iter->index; - dfs_count++; - } - -#else - for (pg_iter = 0; pg_iter < pg->total; pg_iter++) - { - pg->peers[pg_iter].connect_peers_working_set = - GNUNET_CONTAINER_multihashmap_create (num); - } - - starting_peer = 0; - dfs_count = 0; - while ((count_workingset_connections (pg) < num * pg->total) && - (count_allowed_connections (pg) > 0)) - { - if (dfs_count % pg->total == 0) /* Restart the DFS at some weakly connected peer */ - { - least_connections = -1; /* Set to very high number */ - for (pg_iter = 0; pg_iter < pg->total; pg_iter++) - { - if (GNUNET_CONTAINER_multihashmap_size - (pg->peers[pg_iter].connect_peers_working_set) < least_connections) - { - starting_peer = pg_iter; - least_connections = - GNUNET_CONTAINER_multihashmap_size (pg-> - peers - [pg_iter].connect_peers_working_set); - } - } - } - - if (GNUNET_CONTAINER_multihashmap_size (pg->peers[starting_peer].connect_peers) == 0) /* Ensure there is at least one peer left to connect! */ - { - dfs_count = 0; - continue; - } - - /* Choose a random peer from the chosen peers set of connections to add */ - dfs_ctx.chosen = - GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK, - GNUNET_CONTAINER_multihashmap_size (pg->peers - [starting_peer].connect_peers)); - dfs_ctx.first_uid = starting_peer; - dfs_ctx.first = &pg->peers[starting_peer]; - dfs_ctx.pg = pg; - dfs_ctx.current = 0; - - GNUNET_CONTAINER_multihashmap_iterate (pg-> - peers[starting_peer].connect_peers, - &dfs_connect_iterator, &dfs_ctx); - /* Remove the second from the first, since we will be continuing the search and may encounter the first peer again! */ - hash_from_uid (dfs_ctx.second_uid, &second_hash); - GNUNET_assert (GNUNET_YES == - GNUNET_CONTAINER_multihashmap_remove (pg->peers - [starting_peer].connect_peers, - &second_hash, - pg-> - peers - [dfs_ctx.second_uid].daemon)); - starting_peer = dfs_ctx.second_uid; - } - - for (pg_iter = 0; pg_iter < pg->total; pg_iter++) - { - /* Remove the "old" connections */ - GNUNET_CONTAINER_multihashmap_destroy (pg->peers[pg_iter].connect_peers); - /* And replace with the working set */ - pg->peers[pg_iter].connect_peers = - pg->peers[pg_iter].connect_peers_working_set; - } -#endif -} - -/** - * Internal callback for topology information for a particular peer. - */ -static void -internal_topology_callback (void *cls, const struct GNUNET_PeerIdentity *peer, - const struct GNUNET_ATS_Information *atsi, - unsigned int atsi_count) -{ - struct CoreContext *core_ctx = cls; - struct TopologyIterateContext *iter_ctx = core_ctx->iter_context; - - if (peer == NULL) /* Either finished, or something went wrong */ - { - iter_ctx->completed++; - iter_ctx->connected--; - /* One core context allocated per iteration, must free! */ - GNUNET_free (core_ctx); - } - else - { - iter_ctx->topology_cb (iter_ctx->cls, &core_ctx->daemon->id, peer, NULL); - } - - if (iter_ctx->completed == iter_ctx->total) - { - iter_ctx->topology_cb (iter_ctx->cls, NULL, NULL, NULL); - /* Once all are done, free the iteration context */ - GNUNET_free (iter_ctx); - } -} - -/** - * Check running topology iteration tasks, if below max start a new one, otherwise - * schedule for some time in the future. - */ -static void -schedule_get_topology (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - struct CoreContext *core_context = cls; - struct TopologyIterateContext *topology_context = - (struct TopologyIterateContext *) core_context->iter_context; - if ((tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN) != 0) - return; - - if (topology_context->connected > - topology_context->pg->max_outstanding_connections) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Delaying connect, we have too many outstanding connections!\n"); - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply - (GNUNET_TIME_UNIT_MILLISECONDS, 100), - &schedule_get_topology, core_context); - } - else - { - topology_context->connected++; - - if (GNUNET_OK != - GNUNET_CORE_iterate_peers (core_context->daemon->cfg, - &internal_topology_callback, core_context)) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Topology iteration failed.\n"); - internal_topology_callback (core_context, NULL, NULL, 0); - } - } -} - -/** - * Iterate over all (running) peers in the peer group, retrieve - * all connections that each currently has. - */ -void -GNUNET_TESTING_get_topology (struct GNUNET_TESTING_PeerGroup *pg, - GNUNET_TESTING_NotifyTopology cb, void *cls) -{ - struct TopologyIterateContext *topology_context; - struct CoreContext *core_ctx; - unsigned int i; - unsigned int total_count; - - /* Allocate a single topology iteration context */ - topology_context = GNUNET_malloc (sizeof (struct TopologyIterateContext)); - topology_context->topology_cb = cb; - topology_context->cls = cls; - topology_context->pg = pg; - total_count = 0; - for (i = 0; i < pg->total; i++) - { - if (pg->peers[i].daemon->running == GNUNET_YES) - { - /* Allocate one core context per core we need to connect to */ - core_ctx = GNUNET_malloc (sizeof (struct CoreContext)); - core_ctx->daemon = pg->peers[i].daemon; - /* Set back pointer to topology iteration context */ - core_ctx->iter_context = topology_context; - GNUNET_SCHEDULER_add_now (&schedule_get_topology, core_ctx); - total_count++; - } - } - if (total_count == 0) - { - cb (cls, NULL, NULL, "Cannot iterate over topology, no running peers!"); - GNUNET_free (topology_context); - } - else - topology_context->total = total_count; - return; -} - -/** - * Callback function to process statistic values. - * This handler is here only really to insert a peer - * identity (or daemon) so the statistics can be uniquely - * tied to a single running peer. - * - * @param cls closure - * @param subsystem name of subsystem that created the statistic - * @param name the name of the datum - * @param value the current value - * @param is_persistent GNUNET_YES if the value is persistent, GNUNET_NO if not - * @return GNUNET_OK to continue, GNUNET_SYSERR to abort iteration - */ -static int -internal_stats_callback (void *cls, const char *subsystem, const char *name, - uint64_t value, int is_persistent) -{ - struct StatsCoreContext *core_context = cls; - struct StatsIterateContext *stats_context = - (struct StatsIterateContext *) core_context->iter_context; - - return stats_context->proc (stats_context->cls, &core_context->daemon->id, - subsystem, name, value, is_persistent); -} - - -/** - * We don't need the statistics handle anymore, destroy it. - * - * @param cls Closure (the statistics handle to destroy) - * @param tc Task Context - */ -static void -internal_destroy_statistics (void *cls, - const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - struct GNUNET_STATISTICS_Handle *h = cls; - - GNUNET_STATISTICS_destroy (h, GNUNET_NO); -} - - -/** - * Internal continuation call for statistics iteration. - * - * @param cls closure, the CoreContext for this iteration - * @param success whether or not the statistics iterations - * was canceled or not (we don't care) - */ -static void -internal_stats_cont (void *cls, int success) -{ - struct StatsCoreContext *core_context = cls; - struct StatsIterateContext *stats_context = - (struct StatsIterateContext *) core_context->iter_context; - - stats_context->connected--; - stats_context->completed++; - - if (stats_context->completed == stats_context->total) - { - stats_context->cont (stats_context->cls, GNUNET_YES); - GNUNET_free (stats_context); - } - - if (core_context->stats_handle != NULL) - /* Cannot destroy handle inside the continuation */ - GNUNET_SCHEDULER_add_now (&internal_destroy_statistics, - core_context->stats_handle); - - GNUNET_free (core_context); -} - -/** - * Check running topology iteration tasks, if below max start a new one, otherwise - * schedule for some time in the future. - */ -static void -schedule_get_statistics (void *cls, - const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - struct StatsCoreContext *core_context = cls; - struct StatsIterateContext *stats_context = - (struct StatsIterateContext *) core_context->iter_context; - - if ((tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN) != 0) - return; - - if (stats_context->connected > stats_context->pg->max_outstanding_connections) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Delaying connect, we have too many outstanding connections!\n"); - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply - (GNUNET_TIME_UNIT_MILLISECONDS, 100), - &schedule_get_statistics, core_context); - } - else - { - stats_context->connected++; - core_context->stats_handle = - GNUNET_STATISTICS_create ("testing", core_context->daemon->cfg); - if (core_context->stats_handle == NULL) - { - internal_stats_cont (core_context, GNUNET_NO); - return; - } - - core_context->stats_get_handle = - GNUNET_STATISTICS_get (core_context->stats_handle, NULL, NULL, - GNUNET_TIME_UNIT_FOREVER_REL, - &internal_stats_cont, &internal_stats_callback, - core_context); - if (core_context->stats_get_handle == NULL) - internal_stats_cont (core_context, GNUNET_NO); - - } -} - -struct DuplicateStats -{ - /** - * Next item in the list - */ - struct DuplicateStats *next; - - /** - * Nasty string, concatenation of relevant information. - */ - char *unique_string; -}; - -/** - * Check whether the combination of port/host/unix domain socket - * already exists in the list of peers being checked for statistics. - * - * @param pg the peergroup in question - * @param specific_peer the peer we're concerned with - * @param stats_list the list to return to the caller - * - * @return GNUNET_YES if the statistics instance has been seen already, - * GNUNET_NO if not (and we may have added it to the list) - */ -static int -stats_check_existing (struct GNUNET_TESTING_PeerGroup *pg, - struct PeerData *specific_peer, - struct DuplicateStats **stats_list) -{ - struct DuplicateStats *pos; - char *unix_domain_socket; - unsigned long long port; - char *to_match; - - if (GNUNET_YES != - GNUNET_CONFIGURATION_get_value_yesno (pg->cfg, "testing", - "single_statistics_per_host")) - return GNUNET_NO; /* Each peer has its own statistics instance, do nothing! */ - - pos = *stats_list; - if (GNUNET_OK != - GNUNET_CONFIGURATION_get_value_string (specific_peer->cfg, "statistics", - "unixpath", &unix_domain_socket)) - return GNUNET_NO; - - if (GNUNET_OK != - GNUNET_CONFIGURATION_get_value_number (specific_peer->cfg, "statistics", - "port", &port)) - { - GNUNET_free (unix_domain_socket); - return GNUNET_NO; - } - - if (specific_peer->daemon->hostname != NULL) - GNUNET_asprintf (&to_match, "%s%s%llu", specific_peer->daemon->hostname, - unix_domain_socket, port); - else - GNUNET_asprintf (&to_match, "%s%llu", unix_domain_socket, port); - - while (pos != NULL) - { - if (0 == strcmp (to_match, pos->unique_string)) - { - GNUNET_free (unix_domain_socket); - GNUNET_free (to_match); - return GNUNET_YES; - } - pos = pos->next; - } - pos = GNUNET_malloc (sizeof (struct DuplicateStats)); - pos->unique_string = to_match; - pos->next = *stats_list; - *stats_list = pos; - GNUNET_free (unix_domain_socket); - return GNUNET_NO; -} - -/** - * Iterate over all (running) peers in the peer group, retrieve - * all statistics from each. - * - * @param pg the peergroup to iterate statistics of - * @param cont continuation to call once all stats have been retrieved - * @param proc processing function for each statistic from each peer - * @param cls closure to pass to proc - * - */ -void -GNUNET_TESTING_get_statistics (struct GNUNET_TESTING_PeerGroup *pg, - GNUNET_STATISTICS_Callback cont, - GNUNET_TESTING_STATISTICS_Iterator proc, - void *cls) -{ - struct StatsIterateContext *stats_context; - struct StatsCoreContext *core_ctx; - unsigned int i; - unsigned int total_count; - struct DuplicateStats *stats_list; - struct DuplicateStats *pos; - - stats_list = NULL; - - /* Allocate a single stats iteration context */ - stats_context = GNUNET_malloc (sizeof (struct StatsIterateContext)); - stats_context->cont = cont; - stats_context->proc = proc; - stats_context->cls = cls; - stats_context->pg = pg; - total_count = 0; - - for (i = 0; i < pg->total; i++) - { - if ((pg->peers[i].daemon->running == GNUNET_YES) && - (GNUNET_NO == stats_check_existing (pg, &pg->peers[i], &stats_list))) - { - /* Allocate one core context per core we need to connect to */ - core_ctx = GNUNET_malloc (sizeof (struct StatsCoreContext)); - core_ctx->daemon = pg->peers[i].daemon; - /* Set back pointer to topology iteration context */ - core_ctx->iter_context = stats_context; - GNUNET_SCHEDULER_add_now (&schedule_get_statistics, core_ctx); - total_count++; - } - } - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Retrieving stats from %u total instances.\n", total_count); - if (0 != total_count) - stats_context->total = total_count; - else - GNUNET_free (stats_context); - if (stats_list != NULL) - { - pos = stats_list; - while (pos != NULL) - { - GNUNET_free (pos->unique_string); - stats_list = pos->next; - GNUNET_free (pos); - pos = stats_list->next; - } - } - return; -} - -/** - * Stop the connection process temporarily. - * - * @param pg the peer group to stop connecting - */ -void -GNUNET_TESTING_stop_connections (struct GNUNET_TESTING_PeerGroup *pg) -{ - pg->stop_connects = GNUNET_YES; -} - -/** - * Resume the connection process temporarily. - * - * @param pg the peer group to resume connecting - */ -void -GNUNET_TESTING_resume_connections (struct GNUNET_TESTING_PeerGroup *pg) -{ - pg->stop_connects = GNUNET_NO; -} - -/** - * There are many ways to connect peers that are supported by this function. - * To connect peers in the same topology that was created via the - * GNUNET_TESTING_create_topology, the topology variable must be set to - * GNUNET_TESTING_TOPOLOGY_NONE. If the topology variable is specified, - * a new instance of that topology will be generated and attempted to be - * connected. This could result in some connections being impossible, - * because some topologies are non-deterministic. - * - * @param pg the peer group struct representing the running peers - * @param topology which topology to connect the peers in - * @param options options for connecting the topology - * @param option_modifier modifier for options that take a parameter - * @param connect_timeout how long to wait before giving up on connecting - * two peers - * @param connect_attempts how many times to attempt to connect two peers - * over the connect_timeout duration - * @param notify_callback notification to be called once all connections completed - * @param notify_cls closure for notification callback - * - * @return the number of connections that will be attempted, GNUNET_SYSERR on error - */ -int -GNUNET_TESTING_connect_topology (struct GNUNET_TESTING_PeerGroup *pg, - enum GNUNET_TESTING_Topology topology, - enum GNUNET_TESTING_TopologyOption options, - double option_modifier, - struct GNUNET_TIME_Relative connect_timeout, - unsigned int connect_attempts, - GNUNET_TESTING_NotifyCompletion - notify_callback, void *notify_cls) -{ - switch (topology) - { - case GNUNET_TESTING_TOPOLOGY_CLIQUE: - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Creating clique CONNECT topology\n"); - create_clique (pg, &add_connections, CONNECT, GNUNET_NO); - break; - case GNUNET_TESTING_TOPOLOGY_SMALL_WORLD_RING: - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Creating small world (ring) CONNECT topology\n"); - create_small_world_ring (pg, &add_connections, CONNECT); - break; - case GNUNET_TESTING_TOPOLOGY_SMALL_WORLD: - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Creating small world (2d-torus) CONNECT topology\n"); - create_small_world (pg, &add_connections, CONNECT); - break; - case GNUNET_TESTING_TOPOLOGY_RING: - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Creating ring CONNECT topology\n"); - create_ring (pg, &add_connections, CONNECT); - break; - case GNUNET_TESTING_TOPOLOGY_2D_TORUS: - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Creating 2d torus CONNECT topology\n"); - create_2d_torus (pg, &add_connections, CONNECT); - break; - case GNUNET_TESTING_TOPOLOGY_ERDOS_RENYI: - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Creating Erdos-Renyi CONNECT topology\n"); - create_erdos_renyi (pg, &add_connections, CONNECT); - break; - case GNUNET_TESTING_TOPOLOGY_INTERNAT: - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Creating InterNAT CONNECT topology\n"); - create_nated_internet (pg, &add_connections, CONNECT); - break; - case GNUNET_TESTING_TOPOLOGY_SCALE_FREE: - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Creating Scale Free CONNECT topology\n"); - create_scale_free (pg, &add_connections, CONNECT); - break; - case GNUNET_TESTING_TOPOLOGY_LINE: - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Creating straight line CONNECT topology\n"); - create_line (pg, &add_connections, CONNECT); - break; - case GNUNET_TESTING_TOPOLOGY_NONE: - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Creating no CONNECT topology\n"); - copy_allowed_topology (pg); - break; - default: - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - _("Unknown topology specification, can't connect peers!\n")); - return GNUNET_SYSERR; - } - - switch (options) - { - case GNUNET_TESTING_TOPOLOGY_OPTION_RANDOM: - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Connecting random subset (%'.2f percent) of possible peers\n", - 100 * option_modifier); - choose_random_connections (pg, option_modifier); - break; - case GNUNET_TESTING_TOPOLOGY_OPTION_MINIMUM: - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Connecting a minimum of %u peers each (if possible)\n", - (unsigned int) option_modifier); - choose_minimum (pg, (unsigned int) option_modifier); - break; - case GNUNET_TESTING_TOPOLOGY_OPTION_DFS: - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Using DFS to connect a minimum of %u peers each (if possible)\n", - (unsigned int) option_modifier); -#if FIXME - perform_dfs (pg, (int) option_modifier); -#endif - break; - case GNUNET_TESTING_TOPOLOGY_OPTION_ADD_CLOSEST: - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Finding additional %u closest peers each (if possible)\n", - (unsigned int) option_modifier); -#if FIXME - add_closest (pg, (unsigned int) option_modifier, &add_connections, CONNECT); -#endif - break; - case GNUNET_TESTING_TOPOLOGY_OPTION_NONE: - break; - case GNUNET_TESTING_TOPOLOGY_OPTION_ALL: - break; - default: - break; - } - - return connect_topology (pg, connect_timeout, connect_attempts, - notify_callback, notify_cls); -} - -/** - * Lookup and return the number of SSH connections to a host. - * - * @param hostname the hostname to lookup in the list - * @param pg the peergroup that the host belongs to - * - * @return the number of current ssh connections to the host - */ -static unsigned int -count_outstanding_at_host (const char *hostname, - struct GNUNET_TESTING_PeerGroup *pg) -{ - struct OutstandingSSH *pos; - - pos = pg->ssh_head; - while ((pos != NULL) && (strcmp (pos->hostname, hostname) != 0)) - pos = pos->next; - GNUNET_assert (pos != NULL); - return pos->outstanding; -} - -/** - * Increment the number of SSH connections to a host by one. - * - * @param hostname the hostname to lookup in the list - * @param pg the peergroup that the host belongs to - * - */ -static void -increment_outstanding_at_host (const char *hostname, - struct GNUNET_TESTING_PeerGroup *pg) -{ - struct OutstandingSSH *pos; - - pos = pg->ssh_head; - while ((NULL != pos) && (strcmp (pos->hostname, hostname) != 0)) - pos = pos->next; - GNUNET_assert (NULL != pos); - pos->outstanding++; -} - -/** - * Decrement the number of SSH connections to a host by one. - * - * @param hostname the hostname to lookup in the list - * @param pg the peergroup that the host belongs to - * - */ -static void -decrement_outstanding_at_host (const char *hostname, - struct GNUNET_TESTING_PeerGroup *pg) -{ - struct OutstandingSSH *pos; - - pos = pg->ssh_head; - while ((pos != NULL) && (strcmp (pos->hostname, hostname) != 0)) - pos = pos->next; - GNUNET_assert (pos != NULL); - pos->outstanding--; -} - -/** - * Callback that is called whenever a hostkey is generated - * for a peer. Call the real callback and decrement the - * starting counter for the peergroup. - * - * @param cls closure - * @param id identifier for the daemon, NULL on error - * @param d handle for the daemon - * @param emsg error message (NULL on success) - */ -static void -internal_hostkey_callback (void *cls, const struct GNUNET_PeerIdentity *id, - struct GNUNET_TESTING_Daemon *d, const char *emsg) -{ - struct InternalStartContext *internal_context = cls; - - internal_context->peer->pg->starting--; - internal_context->peer->pg->started++; - if (internal_context->hostname != NULL) - decrement_outstanding_at_host (internal_context->hostname, - internal_context->peer->pg); - if (internal_context->hostkey_callback != NULL) - internal_context->hostkey_callback (internal_context->hostkey_cls, id, d, - emsg); - else if (internal_context->peer->pg->started == - internal_context->peer->pg->total) - { - internal_context->peer->pg->started = 0; /* Internal startup may use this counter! */ - GNUNET_TESTING_daemons_continue_startup (internal_context->peer->pg); - } -} - -/** - * Callback that is called whenever a peer has finished starting. - * Call the real callback and decrement the starting counter - * for the peergroup. - * - * @param cls closure - * @param id identifier for the daemon, NULL on error - * @param cfg config - * @param d handle for the daemon - * @param emsg error message (NULL on success) - */ -static void -internal_startup_callback (void *cls, const struct GNUNET_PeerIdentity *id, - const struct GNUNET_CONFIGURATION_Handle *cfg, - struct GNUNET_TESTING_Daemon *d, const char *emsg) -{ - struct InternalStartContext *internal_context = cls; - - internal_context->peer->pg->starting--; - if (internal_context->hostname != NULL) - decrement_outstanding_at_host (internal_context->hostname, - internal_context->peer->pg); - if (internal_context->start_cb != NULL) - internal_context->start_cb (internal_context->start_cb_cls, id, cfg, d, - emsg); -} - - -/** - * Calls GNUNET_TESTING_daemon_continue_startup to set the daemon's state - * from HOSTKEY_CREATED to TOPOLOGY_SETUP. Makes sure not to saturate a host - * with requests delaying them when needed. - * - * @param cls closure: internal context of the daemon. - * @param tc TaskContext - */ -static void -internal_continue_startup (void *cls, - const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - struct InternalStartContext *internal_context = cls; - - internal_context->peer->startup_task = GNUNET_SCHEDULER_NO_TASK; - - if ((tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN) != 0) - { - return; - } - - if ((internal_context->peer->pg->starting < - internal_context->peer->pg->max_concurrent_ssh) || - ((internal_context->hostname != NULL) && - (count_outstanding_at_host - (internal_context->hostname, - internal_context->peer->pg) < - internal_context->peer->pg->max_concurrent_ssh))) - { - if (internal_context->hostname != NULL) - increment_outstanding_at_host (internal_context->hostname, - internal_context->peer->pg); - internal_context->peer->pg->starting++; - GNUNET_TESTING_daemon_continue_startup (internal_context->peer->daemon); - } - else - { - internal_context->peer->startup_task = - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply - (GNUNET_TIME_UNIT_MILLISECONDS, 100), - &internal_continue_startup, - internal_context); - } -} - -/** - * Callback for informing us about a successful - * or unsuccessful churn start call. - * - * @param cls a ChurnContext - * @param id the peer identity of the started peer - * @param cfg the handle to the configuration of the peer - * @param d handle to the daemon for the peer - * @param emsg NULL on success, non-NULL on failure - * - */ -void -churn_start_callback (void *cls, const struct GNUNET_PeerIdentity *id, - const struct GNUNET_CONFIGURATION_Handle *cfg, - struct GNUNET_TESTING_Daemon *d, const char *emsg) -{ - struct ChurnRestartContext *startup_ctx = cls; - struct ChurnContext *churn_ctx = startup_ctx->churn_ctx; - - unsigned int total_left; - char *error_message; - - error_message = NULL; - if (emsg != NULL) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Churn stop callback failed with error `%s'\n", emsg); - churn_ctx->num_failed_start++; - } - else - { - churn_ctx->num_to_start--; - } - - total_left = - (churn_ctx->num_to_stop - churn_ctx->num_failed_stop) + - (churn_ctx->num_to_start - churn_ctx->num_failed_start); - - if (total_left == 0) - { - if ((churn_ctx->num_failed_stop > 0) || (churn_ctx->num_failed_start > 0)) - GNUNET_asprintf (&error_message, - "Churn didn't complete successfully, %u peers failed to start %u peers failed to be stopped!", - churn_ctx->num_failed_start, churn_ctx->num_failed_stop); - churn_ctx->cb (churn_ctx->cb_cls, error_message); - GNUNET_free_non_null (error_message); - GNUNET_free (churn_ctx); - GNUNET_free (startup_ctx); - } -} - -static void -schedule_churn_restart (void *cls, - const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - struct PeerRestartContext *peer_restart_ctx = cls; - struct ChurnRestartContext *startup_ctx = peer_restart_ctx->churn_restart_ctx; - - if (startup_ctx->outstanding > startup_ctx->pg->max_concurrent_ssh) - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply - (GNUNET_TIME_UNIT_MILLISECONDS, 100), - &schedule_churn_restart, peer_restart_ctx); - else - { - if (startup_ctx->churn_ctx->service != NULL) - GNUNET_TESTING_daemon_start_stopped_service (peer_restart_ctx->daemon, - startup_ctx-> - churn_ctx->service, - startup_ctx->timeout, - &churn_start_callback, - startup_ctx); - else - GNUNET_TESTING_daemon_start_stopped (peer_restart_ctx->daemon, - startup_ctx->timeout, - &churn_start_callback, startup_ctx); - GNUNET_free (peer_restart_ctx); - } -} - -/** - * Callback for informing us about a successful - * or unsuccessful churn start call. - * - * @param cls a struct ServiceStartContext *startup_ctx - * @param id the peer identity of the started peer - * @param cfg the handle to the configuration of the peer - * @param d handle to the daemon for the peer - * @param emsg NULL on success, non-NULL on failure - * - */ -void -service_start_callback (void *cls, const struct GNUNET_PeerIdentity *id, - const struct GNUNET_CONFIGURATION_Handle *cfg, - struct GNUNET_TESTING_Daemon *d, const char *emsg) -{ - struct ServiceStartContext *startup_ctx = (struct ServiceStartContext *) cls; - - if (emsg != NULL) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Service start failed with error `%s'\n", emsg); - } - - startup_ctx->outstanding--; - startup_ctx->remaining--; - - if (startup_ctx->remaining == 0) - { - startup_ctx->cb (startup_ctx->cb_cls, NULL); - GNUNET_free (startup_ctx->service); - GNUNET_free (startup_ctx); - } -} - -static void -schedule_service_start (void *cls, - const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - struct PeerServiceStartContext *peer_ctx = cls; - struct ServiceStartContext *startup_ctx = peer_ctx->start_ctx; - - if (startup_ctx->outstanding > startup_ctx->pg->max_concurrent_ssh) - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply - (GNUNET_TIME_UNIT_MILLISECONDS, 100), - &schedule_service_start, peer_ctx); - else - { - - GNUNET_TESTING_daemon_start_service (peer_ctx->daemon, startup_ctx->service, - startup_ctx->timeout, - &service_start_callback, startup_ctx); - GNUNET_free (peer_ctx); - } -} - - -static void -internal_start (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - struct InternalStartContext *internal_context = cls; - - if ((tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN) != 0) - { - return; - } - - if ((internal_context->peer->pg->starting < - internal_context->peer->pg->max_concurrent_ssh) || - ((internal_context->hostname != NULL) && - (count_outstanding_at_host - (internal_context->hostname, - internal_context->peer->pg) < - internal_context->peer->pg->max_concurrent_ssh))) - { - if (internal_context->hostname != NULL) - increment_outstanding_at_host (internal_context->hostname, - internal_context->peer->pg); - internal_context->peer->pg->starting++; - internal_context->peer->daemon = - GNUNET_TESTING_daemon_start (internal_context->peer->cfg, - internal_context->timeout, GNUNET_NO, - internal_context->hostname, - internal_context->username, - internal_context->sshport, - internal_context->hostkey, - &internal_hostkey_callback, - internal_context, - &internal_startup_callback, - internal_context); - } - else - { - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply - (GNUNET_TIME_UNIT_MILLISECONDS, 100), - &internal_start, internal_context); - } -} - -#if USE_START_HELPER - -struct PeerStartHelperContext -{ - struct GNUNET_TESTING_PeerGroup *pg; - - struct HostData *host; - - struct GNUNET_OS_Process *proc; -}; - -static void -check_peers_started (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - struct PeerStartHelperContext *helper = cls; - enum GNUNET_OS_ProcessStatusType type; - unsigned long code; - unsigned int i; - GNUNET_TESTING_NotifyDaemonRunning cb; - - if (GNUNET_NO == GNUNET_OS_process_status (helper->proc, &type, &code)) /* Still running, wait some more! */ - { - GNUNET_SCHEDULER_add_delayed (GNUNET_CONSTANTS_EXEC_WAIT, - &check_peers_started, helper); - return; - } - - helper->pg->starting--; - if (helper->pg->starting == 0) /* All peers have finished starting! */ - { - /* Call the peer started callback for each peer, set proper FSM state (?) */ - for (i = 0; i < helper->pg->total; i++) - { - cb = helper->pg->peers[i].daemon->cb; - helper->pg->peers[i].daemon->cb = NULL; - helper->pg->peers[i].daemon->running = GNUNET_YES; - helper->pg->peers[i].daemon->phase = SP_START_DONE; - if (NULL != cb) - { - if ((type != GNUNET_OS_PROCESS_EXITED) || (code != 0)) - cb (helper->pg->peers[i].daemon->cb_cls, - &helper->pg->peers[i].daemon->id, - helper->pg->peers[i].daemon->cfg, helper->pg->peers[i].daemon, - "Failed to execute peerStartHelper.pl, or return code bad!"); - else - cb (helper->pg->peers[i].daemon->cb_cls, - &helper->pg->peers[i].daemon->id, - helper->pg->peers[i].daemon->cfg, helper->pg->peers[i].daemon, - NULL); - - } - - } - } - GNUNET_OS_process_destroy (helper->proc); -} - -static void -start_peer_helper (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - struct PeerStartHelperContext *helper = cls; - char *baseservicehome; - char *tempdir; - char *arg; - - /* ssh user@host peerStartHelper /path/to/basedirectory */ - GNUNET_assert (GNUNET_OK == - GNUNET_CONFIGURATION_get_value_string (helper->pg->cfg, - "PATHS", "SERVICEHOME", - &baseservicehome)); - GNUNET_asprintf (&tempdir, "%s/%s/", baseservicehome, helper->host->hostname); - if (NULL != helper->host->username) - GNUNET_asprintf (&arg, "%s@%s", helper->host->username, - helper->host->hostname); - else - GNUNET_asprintf (&arg, "%s", helper->host->hostname); - - /* FIXME: Doesn't support ssh_port option! */ - helper->proc = - GNUNET_OS_start_process (GNUNET_NO, NULL, NULL, "ssh", "ssh", arg, - "peerStartHelper.pl", tempdir, NULL); - GNUNET_assert (helper->proc != NULL); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "starting peers with cmd ssh %s %s %s\n", - arg, "peerStartHelper.pl", tempdir); - GNUNET_SCHEDULER_add_now (&check_peers_started, helper); - GNUNET_free (tempdir); - GNUNET_free (baseservicehome); - GNUNET_free (arg); -} -#endif - -/** - * Function which continues a peer group starting up - * after successfully generating hostkeys for each peer. - * - * @param pg the peer group to continue starting - * - */ -void -GNUNET_TESTING_daemons_continue_startup (struct GNUNET_TESTING_PeerGroup *pg) -{ - unsigned int i; - -#if USE_START_HELPER - if ((pg->num_hosts > 0) && (pg->hostkey_data != NULL)) - { - struct PeerStartHelperContext *helper; - - pg->starting = pg->num_hosts; - for (i = 0; i < pg->num_hosts; i++) - { - helper = GNUNET_malloc (sizeof (struct PeerStartHelperContext)); - helper->pg = pg; - helper->host = &pg->hosts[i]; - GNUNET_SCHEDULER_add_now (&start_peer_helper, helper); - } - } - else - { - pg->starting = 0; - for (i = 0; i < pg->total; i++) - { - pg->peers[i].startup_task = - GNUNET_SCHEDULER_add_now (&internal_continue_startup, - &pg->peers[i].internal_context); - } - } -#else - pg->starting = 0; - for (i = 0; i < pg->total; i++) - { - pg->peers[i].startup_task = - GNUNET_SCHEDULER_add_now (&internal_continue_startup, - &pg->peers[i].internal_context); - } -#endif -} - -#if USE_START_HELPER -static void -call_hostkey_callbacks (void *cls, - const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - struct GNUNET_TESTING_PeerGroup *pg = cls; - unsigned int i; - - for (i = 0; i < pg->total; i++) - { - if (pg->peers[i].internal_context.hostkey_callback != NULL) - pg->peers[i].internal_context.hostkey_callback (pg->peers[i]. - internal_context.hostkey_cls, - &pg->peers[i].daemon->id, - pg->peers[i].daemon, - NULL); - } - - if (pg->peers[0].internal_context.hostkey_callback == NULL) - GNUNET_TESTING_daemons_continue_startup (pg); -} -#endif - -/** - * Start count gnunet instances with the same set of transports and - * applications. The port numbers (any option called "PORT") will be - * adjusted to ensure that no two peers running on the same system - * have the same port(s) in their respective configurations. - * - * @param cfg configuration template to use - * @param total number of daemons to start - * @param max_concurrent_connections for testing, how many peers can - * we connect to simultaneously - * @param max_concurrent_ssh when starting with ssh, how many ssh - * connections will we allow at once (based on remote hosts allowed!) - * @param timeout total time allowed for peers to start - * @param hostkey_callback function to call on each peers hostkey generation - * if NULL, peers will be started by this call, if non-null, - * GNUNET_TESTING_daemons_continue_startup must be called after - * successful hostkey generation - * @param hostkey_cls closure for hostkey callback - * @param cb function to call on each daemon that was started - * @param cb_cls closure for cb - * @param connect_callback function to call each time two hosts are connected - * @param connect_callback_cls closure for connect_callback - * @param hostnames linked list of host structs to use to start peers on - * (NULL to run on localhost only) - * - * @return NULL on error, otherwise handle to control peer group - */ -struct GNUNET_TESTING_PeerGroup * -GNUNET_TESTING_daemons_start (const struct GNUNET_CONFIGURATION_Handle *cfg, - unsigned int total, - unsigned int max_concurrent_connections, - unsigned int max_concurrent_ssh, - struct GNUNET_TIME_Relative timeout, - GNUNET_TESTING_NotifyHostkeyCreated - hostkey_callback, void *hostkey_cls, - GNUNET_TESTING_NotifyDaemonRunning cb, - void *cb_cls, - GNUNET_TESTING_NotifyConnection connect_callback, - void *connect_callback_cls, - const struct GNUNET_TESTING_Host *hostnames) -{ - struct GNUNET_TESTING_PeerGroup *pg; - const struct GNUNET_TESTING_Host *hostpos; - const char *hostname; - const char *username; - char *baseservicehome; - char *newservicehome; - char *tmpdir; - char *hostkeys_file; - char *arg; - char *ssh_port_str; - struct GNUNET_DISK_FileHandle *fd; - struct GNUNET_CONFIGURATION_Handle *pcfg; - unsigned int off; - struct OutstandingSSH *ssh_entry; - unsigned int hostcnt; - unsigned int i; - uint16_t minport; - uint16_t sshport; - uint32_t upnum; - uint32_t fdnum; - uint64_t fs; - uint64_t total_hostkeys; - struct GNUNET_OS_Process *proc; - - username = NULL; - if (0 == total) - { - GNUNET_break (0); - return NULL; - } - - upnum = 0; - fdnum = 0; - pg = GNUNET_malloc (sizeof (struct GNUNET_TESTING_PeerGroup)); - pg->cfg = cfg; - pg->notify_connection = connect_callback; - pg->notify_connection_cls = connect_callback_cls; - pg->total = total; - pg->max_timeout = GNUNET_TIME_relative_to_absolute (timeout); - pg->peers = GNUNET_malloc (total * sizeof (struct PeerData)); - pg->max_outstanding_connections = max_concurrent_connections; - pg->max_concurrent_ssh = max_concurrent_ssh; - if (NULL != hostnames) - { - off = 0; - hostpos = hostnames; - while (hostpos != NULL) - { - hostpos = hostpos->next; - off++; - } - pg->hosts = GNUNET_malloc (off * sizeof (struct HostData)); - off = 0; - - hostpos = hostnames; - while (hostpos != NULL) - { - pg->hosts[off].minport = LOW_PORT; - pg->hosts[off].hostname = GNUNET_strdup (hostpos->hostname); - if (hostpos->username != NULL) - pg->hosts[off].username = GNUNET_strdup (hostpos->username); - pg->hosts[off].sshport = hostpos->port; - hostpos = hostpos->next; - off++; - } - - if (off == 0) - { - pg->hosts = NULL; - } - hostcnt = off; - minport = 0; - pg->num_hosts = off; - } - else - { - hostcnt = 0; - minport = LOW_PORT; - } - - /* Create the servicehome directory for each remote peer */ - GNUNET_assert (GNUNET_OK == - GNUNET_CONFIGURATION_get_value_string (cfg, "PATHS", - "SERVICEHOME", - &baseservicehome)); - for (i = 0; i < pg->num_hosts; i++) - { - ssh_entry = GNUNET_malloc (sizeof (struct OutstandingSSH)); - ssh_entry->hostname = pg->hosts[i].hostname; /* Don't free! */ - GNUNET_CONTAINER_DLL_insert (pg->ssh_head, pg->ssh_tail, ssh_entry); - GNUNET_asprintf (&tmpdir, "%s/%s", baseservicehome, pg->hosts[i].hostname); - if (NULL != pg->hosts[i].username) - GNUNET_asprintf (&arg, "%s@%s", pg->hosts[i].username, - pg->hosts[i].hostname); - else - GNUNET_asprintf (&arg, "%s", pg->hosts[i].hostname); - if (pg->hosts[i].sshport != 0) - { - GNUNET_asprintf (&ssh_port_str, "%d", pg->hosts[i].sshport); - proc = - GNUNET_OS_start_process (GNUNET_NO, NULL, NULL, "ssh", "ssh", "-P", ssh_port_str, - "-q", - arg, "mkdir -p", tmpdir, NULL); - } - else - proc = - GNUNET_OS_start_process (GNUNET_NO, NULL, NULL, "ssh", "ssh", arg, "mkdir -p", - tmpdir, NULL); - GNUNET_assert (proc != NULL); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Creating remote dir with command ssh %s %s %s\n", arg, - " mkdir -p ", tmpdir); - GNUNET_free (tmpdir); - GNUNET_free (arg); - GNUNET_OS_process_wait (proc); - GNUNET_OS_process_destroy (proc); - } - GNUNET_free (baseservicehome); - baseservicehome = NULL; - - if (GNUNET_YES == - GNUNET_CONFIGURATION_get_value_string (cfg, "TESTING", "HOSTKEYSFILE", - &hostkeys_file)) - { - if (GNUNET_YES != GNUNET_DISK_file_test (hostkeys_file)) - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - _("Could not read hostkeys file!\n")); - else - { - /* Check hostkey file size, read entire thing into memory */ - fd = GNUNET_DISK_file_open (hostkeys_file, GNUNET_DISK_OPEN_READ, - GNUNET_DISK_PERM_NONE); - if (NULL == fd) - { - GNUNET_log_strerror_file (GNUNET_ERROR_TYPE_ERROR, "open", - hostkeys_file); - GNUNET_free (hostkeys_file); - for (i = 0; i < pg->num_hosts; i++) - { - GNUNET_free (pg->hosts[i].hostname); - GNUNET_free_non_null (pg->hosts[i].username); - } - GNUNET_free (pg->peers); - GNUNET_free (pg->hosts); - GNUNET_free (pg); - return NULL; - } - - if (GNUNET_OK != GNUNET_DISK_file_size (hostkeys_file, &fs, GNUNET_YES, GNUNET_YES)) - fs = 0; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Found file size %llu for hostkeys\n", fs); - if (0 != (fs % HOSTKEYFILESIZE)) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "File size %llu seems incorrect for hostkeys...\n", fs); - } - else - { - total_hostkeys = fs / HOSTKEYFILESIZE; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Will read %llu hostkeys from file\n", total_hostkeys); - pg->hostkey_data = GNUNET_malloc_large (fs); - GNUNET_assert (fs == GNUNET_DISK_file_read (fd, pg->hostkey_data, fs)); - } - GNUNET_assert (GNUNET_OK == GNUNET_DISK_file_close (fd)); - } - GNUNET_free (hostkeys_file); - } - - for (off = 0; off < total; off++) - { - if (hostcnt > 0) - { - hostname = pg->hosts[off % hostcnt].hostname; - username = pg->hosts[off % hostcnt].username; - sshport = pg->hosts[off % hostcnt].sshport; - pcfg = - GNUNET_TESTING_create_cfg (cfg, off, &pg->hosts[off % hostcnt].minport, &upnum, - hostname, &fdnum); - } - else - { - hostname = NULL; - username = NULL; - sshport = 0; - pcfg = GNUNET_TESTING_create_cfg (cfg, off, &minport, &upnum, hostname, &fdnum); - } - - if (NULL == pcfg) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - _ - ("Could not create configuration for peer number %u on `%s'!\n"), - off, hostname == NULL ? "localhost" : hostname); - continue; - } - - if (GNUNET_YES == - GNUNET_CONFIGURATION_get_value_string (pcfg, "PATHS", "SERVICEHOME", - &baseservicehome)) - { - if (hostname != NULL) - GNUNET_asprintf (&newservicehome, "%s/%s/%d/", baseservicehome, - hostname, off); - else - GNUNET_asprintf (&newservicehome, "%s/%d/", baseservicehome, off); - GNUNET_free (baseservicehome); - baseservicehome = NULL; - } - else - { - tmpdir = getenv ("TMPDIR"); - tmpdir = tmpdir ? tmpdir : "/tmp"; - if (hostname != NULL) - GNUNET_asprintf (&newservicehome, "%s/%s/%s/%d/", tmpdir, hostname, - "gnunet-testing-test-test", off); - else - GNUNET_asprintf (&newservicehome, "%s/%s/%d/", tmpdir, - "gnunet-testing-test-test", off); - } - GNUNET_CONFIGURATION_set_value_string (pcfg, "PATHS", "SERVICEHOME", - newservicehome); - GNUNET_free (newservicehome); - pg->peers[off].cfg = pcfg; - pg->peers[off].pg = pg; - pg->peers[off].internal_context.peer = &pg->peers[off]; - pg->peers[off].internal_context.timeout = timeout; - pg->peers[off].internal_context.hostname = hostname; - pg->peers[off].internal_context.username = username; - pg->peers[off].internal_context.sshport = sshport; - if (pg->hostkey_data != NULL) - pg->peers[off].internal_context.hostkey = - &pg->hostkey_data[off * HOSTKEYFILESIZE]; - pg->peers[off].internal_context.hostkey_callback = hostkey_callback; - pg->peers[off].internal_context.hostkey_cls = hostkey_cls; - pg->peers[off].internal_context.start_cb = cb; - pg->peers[off].internal_context.start_cb_cls = cb_cls; -#if !USE_START_HELPER - GNUNET_SCHEDULER_add_now (&internal_start, - &pg->peers[off].internal_context); -#else - if ((pg->hostkey_data != NULL) && (hostcnt > 0)) - { - pg->peers[off].daemon = - GNUNET_TESTING_daemon_start (pcfg, timeout, GNUNET_YES, hostname, - username, sshport, - pg->peers[off].internal_context.hostkey, - &internal_hostkey_callback, - &pg->peers[off].internal_context, - &internal_startup_callback, - &pg->peers[off].internal_context); - /** - * At this point, given that we had a hostkeyfile, - * we can call the hostkey callback! - * But first, we should copy (rsync) all of the configs - * and hostkeys to the remote peers. Then let topology - * creation happen, then call the peer start helper processes, - * then set pg->whatever_phase for each peer and let them - * enter the fsm to get the HELLO's for peers and start connecting. - */ - } - else - { - GNUNET_SCHEDULER_add_now (&internal_start, - &pg->peers[off].internal_context); - } - -#endif - } - -#if USE_START_HELPER /* Now the peergroup has been set up, hostkeys and configs written to files. */ - if ((pg->hostkey_data != NULL) && (hostcnt > 0)) - { - for (off = 0; off < hostcnt; off++) - { - - if (hostcnt > 0) - { - hostname = pg->hosts[off % hostcnt].hostname; - username = pg->hosts[off % hostcnt].username; - sshport = pg->hosts[off % hostcnt].sshport; - } - else - { - hostname = NULL; - username = NULL; - sshport = 0; - } - - if (GNUNET_YES == - GNUNET_CONFIGURATION_get_value_string (cfg, "PATHS", "SERVICEHOME", - &baseservicehome)) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "baseservice home is %s\n", - baseservicehome); - if (hostname != NULL) - GNUNET_asprintf (&newservicehome, "%s/%s/", baseservicehome, - hostname); - else - GNUNET_asprintf (&newservicehome, "%s/", baseservicehome); - GNUNET_free (baseservicehome); - baseservicehome = NULL; - } - else - { - tmpdir = getenv ("TMPDIR"); - tmpdir = tmpdir ? tmpdir : "/tmp"; - if (hostname != NULL) - GNUNET_asprintf (&newservicehome, "%s/%s/%s/", tmpdir, hostname, - "gnunet-testing-test-test"); - else - GNUNET_asprintf (&newservicehome, "%s/%s/", tmpdir, - "gnunet-testing-test-test", off); - } - - if (NULL != username) - GNUNET_asprintf (&arg, "%s@%s:%s", username, pg->hosts[off].hostname, - newservicehome); - else - GNUNET_asprintf (&arg, "%s:%s", pg->hosts[off].hostname, - newservicehome); - - /* FIXME: Doesn't support ssh_port option! */ - proc = - GNUNET_OS_start_process (GNUNET_NO, NULL, NULL, "rsync", "rsync", "-r", - newservicehome, arg, NULL); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "copying directory with command rsync -r %s %s\n", - newservicehome, arg); - GNUNET_free (newservicehome); - GNUNET_free (arg); - if (NULL == proc) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - _ - ("Could not start `%s' process to copy configuration directory.\n"), - "scp"); - GNUNET_assert (0); - } - GNUNET_OS_process_wait (proc); - GNUNET_OS_process_destroy (proc); - } - /* Now all the configuration files and hostkeys are copied to the remote host. Call the hostkey callback for each peer! */ - GNUNET_SCHEDULER_add_now (&call_hostkey_callbacks, pg); - } -#endif - return pg; -} - -/* - * Get a daemon by number, so callers don't have to do nasty - * offsetting operation. - */ -struct GNUNET_TESTING_Daemon * -GNUNET_TESTING_daemon_get (struct GNUNET_TESTING_PeerGroup *pg, - unsigned int position) -{ - if (position < pg->total) - return pg->peers[position].daemon; - return NULL; -} - -/* - * Get a daemon by peer identity, so callers can - * retrieve the daemon without knowing it's offset. - * - * @param pg the peer group to retrieve the daemon from - * @param peer_id the peer identity of the daemon to retrieve - * - * @return the daemon on success, or NULL if no such peer identity is found - */ -struct GNUNET_TESTING_Daemon * -GNUNET_TESTING_daemon_get_by_id (struct GNUNET_TESTING_PeerGroup *pg, - const struct GNUNET_PeerIdentity *peer_id) -{ - unsigned int i; - - for (i = 0; i < pg->total; i++) - { - if (0 == - memcmp (&pg->peers[i].daemon->id, peer_id, - sizeof (struct GNUNET_PeerIdentity))) - return pg->peers[i].daemon; - } - return NULL; -} - -/** - * Prototype of a function that will be called when a - * particular operation was completed the testing library. - * - * @param cls closure (a struct RestartContext) - * @param id id of the peer that was restarted - * @param cfg handle to the configuration of the peer - * @param d handle to the daemon that was restarted - * @param emsg NULL on success - */ -static void -restart_callback (void *cls, const struct GNUNET_PeerIdentity *id, - const struct GNUNET_CONFIGURATION_Handle *cfg, - struct GNUNET_TESTING_Daemon *d, const char *emsg) -{ - struct RestartContext *restart_context = cls; - - if (emsg == NULL) - { - restart_context->peers_restarted++; - } - else - { - restart_context->peers_restart_failed++; - } - - if (restart_context->peers_restarted == restart_context->peer_group->total) - { - restart_context->callback (restart_context->callback_cls, NULL); - GNUNET_free (restart_context); - } - else if (restart_context->peers_restart_failed + - restart_context->peers_restarted == - restart_context->peer_group->total) - { - restart_context->callback (restart_context->callback_cls, - "Failed to restart peers!"); - GNUNET_free (restart_context); - } - -} - -/** - * Callback for informing us about a successful - * or unsuccessful churn stop call. - * - * @param cls a ChurnContext - * @param emsg NULL on success, non-NULL on failure - * - */ -static void -churn_stop_callback (void *cls, const char *emsg) -{ - struct ShutdownContext *shutdown_ctx = cls; - struct ChurnContext *churn_ctx = shutdown_ctx->cb_cls; - unsigned int total_left; - char *error_message; - - error_message = NULL; - shutdown_ctx->outstanding--; - - if (emsg != NULL) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Churn stop callback failed with error `%s'\n", emsg); - churn_ctx->num_failed_stop++; - } - else - { - churn_ctx->num_to_stop--; - } - - total_left = - (churn_ctx->num_to_stop - churn_ctx->num_failed_stop) + - (churn_ctx->num_to_start - churn_ctx->num_failed_start); - - if (total_left == 0) - { - if ((churn_ctx->num_failed_stop > 0) || (churn_ctx->num_failed_start > 0)) - { - GNUNET_asprintf (&error_message, - "Churn didn't complete successfully, %u peers failed to start %u peers failed to be stopped!", - churn_ctx->num_failed_start, churn_ctx->num_failed_stop); - } - churn_ctx->cb (churn_ctx->cb_cls, error_message); - GNUNET_free_non_null (error_message); - GNUNET_free (churn_ctx); - GNUNET_free (shutdown_ctx); - } -} - -/** - * Count the number of running peers. - * - * @param pg handle for the peer group - * - * @return the number of currently running peers in the peer group - */ -unsigned int -GNUNET_TESTING_daemons_running (struct GNUNET_TESTING_PeerGroup *pg) -{ - unsigned int i; - unsigned int running = 0; - - for (i = 0; i < pg->total; i++) - { - if (pg->peers[i].daemon->running == GNUNET_YES) - { - GNUNET_assert (running != -1); - running++; - } - } - return running; -} - -/** - * Task to rate limit the number of outstanding peer shutdown - * requests. This is necessary for making sure we don't do - * too many ssh connections at once, but is generally nicer - * to any system as well (graduated task starts, as opposed - * to calling gnunet-arm N times all at once). - */ -static void -schedule_churn_shutdown_task (void *cls, - const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - struct PeerShutdownContext *peer_shutdown_ctx = cls; - struct ShutdownContext *shutdown_ctx; - struct ChurnContext *churn_ctx; - - GNUNET_assert (peer_shutdown_ctx != NULL); - shutdown_ctx = peer_shutdown_ctx->shutdown_ctx; - GNUNET_assert (shutdown_ctx != NULL); - churn_ctx = (struct ChurnContext *) shutdown_ctx->cb_cls; - if (shutdown_ctx->outstanding > churn_ctx->pg->max_concurrent_ssh) - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply - (GNUNET_TIME_UNIT_MILLISECONDS, 100), - &schedule_churn_shutdown_task, - peer_shutdown_ctx); - else - { - shutdown_ctx->outstanding++; - if (churn_ctx->service != NULL) - GNUNET_TESTING_daemon_stop_service (peer_shutdown_ctx->daemon, - churn_ctx->service, - shutdown_ctx->timeout, - shutdown_ctx->cb, shutdown_ctx); - else - GNUNET_TESTING_daemon_stop (peer_shutdown_ctx->daemon, - shutdown_ctx->timeout, shutdown_ctx->cb, - shutdown_ctx, GNUNET_NO, GNUNET_YES); - GNUNET_free (peer_shutdown_ctx); - } -} - - -/** - * Simulate churn by stopping some peers (and possibly - * re-starting others if churn is called multiple times). This - * function can only be used to create leave-join churn (peers "never" - * leave for good). First "voff" random peers that are currently - * online will be taken offline; then "von" random peers that are then - * offline will be put back online. No notifications will be - * generated for any of these operations except for the callback upon - * completion. - * - * @param pg handle for the peer group - * @param service the service to churn off/on, NULL to churn peer - * @param voff number of peers that should go offline - * @param von number of peers that should come back online; - * must be zero on first call (since "testbed_start" - * always starts all of the peers) - * @param timeout how long to wait for operations to finish before - * giving up - * @param cb function to call at the end - * @param cb_cls closure for cb - */ -void -GNUNET_TESTING_daemons_churn (struct GNUNET_TESTING_PeerGroup *pg, - char *service, unsigned int voff, - unsigned int von, - struct GNUNET_TIME_Relative timeout, - GNUNET_TESTING_NotifyCompletion cb, void *cb_cls) -{ - struct ChurnContext *churn_ctx; - struct ShutdownContext *shutdown_ctx; - struct PeerShutdownContext *peer_shutdown_ctx; - struct PeerRestartContext *peer_restart_ctx; - struct ChurnRestartContext *churn_startup_ctx; - - unsigned int running; - unsigned int stopped; - unsigned int total_running; - unsigned int total_stopped; - unsigned int i; - unsigned int *running_arr; - unsigned int *stopped_arr; - unsigned int *running_permute; - unsigned int *stopped_permute; - char *pos; - - shutdown_ctx = NULL; - peer_shutdown_ctx = NULL; - peer_restart_ctx = NULL; - churn_startup_ctx = NULL; - - running = 0; - stopped = 0; - - if ((von == 0) && (voff == 0)) /* No peers at all? */ - { - cb (cb_cls, NULL); - return; - } - - for (i = 0; i < pg->total; i++) - { - if (service == NULL) - { - if (pg->peers[i].daemon->running == GNUNET_YES) - { - GNUNET_assert (running != -1); - running++; - } - else - { - GNUNET_assert (stopped != -1); - stopped++; - } - } - else - { - /* FIXME: make churned services a list! */ - pos = pg->peers[i].daemon->churned_services; - /* FIXME: while (pos != NULL) */ - if (pos != NULL) - { -#if FIXME - if (0 == strcasecmp (pos, service)) - { - - break; - } -#endif - GNUNET_assert (stopped != -1); - stopped++; - /* FIXME: pos = pos->next; */ - } - if (pos == NULL) - { - GNUNET_assert (running != -1); - running++; - } - } - } - - if (voff > running) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Trying to stop more peers (%d) than are currently running (%d)!\n", - voff, running); - cb (cb_cls, "Trying to stop more peers than are currently running!"); - return; - } - - if (von > stopped) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Trying to start more peers (%d) than are currently stopped (%d)!\n", - von, stopped); - cb (cb_cls, "Trying to start more peers than are currently stopped!"); - return; - } - - churn_ctx = GNUNET_malloc (sizeof (struct ChurnContext)); - - if (service != NULL) - churn_ctx->service = GNUNET_strdup (service); - running_arr = NULL; - if (running > 0) - running_arr = GNUNET_malloc (running * sizeof (unsigned int)); - - stopped_arr = NULL; - if (stopped > 0) - stopped_arr = GNUNET_malloc (stopped * sizeof (unsigned int)); - - running_permute = NULL; - stopped_permute = NULL; - - if (running > 0) - running_permute = - GNUNET_CRYPTO_random_permute (GNUNET_CRYPTO_QUALITY_WEAK, running); - if (stopped > 0) - stopped_permute = - GNUNET_CRYPTO_random_permute (GNUNET_CRYPTO_QUALITY_WEAK, stopped); - - total_running = running; - total_stopped = stopped; - running = 0; - stopped = 0; - - churn_ctx->num_to_start = von; - churn_ctx->num_to_stop = voff; - churn_ctx->cb = cb; - churn_ctx->cb_cls = cb_cls; - churn_ctx->pg = pg; - - for (i = 0; i < pg->total; i++) - { - if (service == NULL) - { - if (pg->peers[i].daemon->running == GNUNET_YES) - { - GNUNET_assert ((running_arr != NULL) && (total_running > running)); - running_arr[running] = i; - running++; - } - else - { - GNUNET_assert ((stopped_arr != NULL) && (total_stopped > stopped)); - stopped_arr[stopped] = i; - stopped++; - } - } - else - { - /* FIXME: make churned services a list! */ - pos = pg->peers[i].daemon->churned_services; - /* FIXME: while (pos != NULL) */ - if (pos != NULL) - { - GNUNET_assert ((stopped_arr != NULL) && (total_stopped > stopped)); - stopped_arr[stopped] = i; - stopped++; - /* FIXME: pos = pos->next; */ - } - if (pos == NULL) - { - GNUNET_assert ((running_arr != NULL) && (total_running > running)); - running_arr[running] = i; - running++; - } - } - } - - GNUNET_assert (running >= voff); - if (voff > 0) - { - shutdown_ctx = GNUNET_malloc (sizeof (struct ShutdownContext)); - shutdown_ctx->cb = &churn_stop_callback; - shutdown_ctx->cb_cls = churn_ctx; - shutdown_ctx->total_peers = voff; - shutdown_ctx->timeout = timeout; - } - - for (i = 0; i < voff; i++) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stopping peer %d!\n", - running_arr[running_permute[i]]); - GNUNET_assert (running_arr != NULL); - peer_shutdown_ctx = GNUNET_malloc (sizeof (struct PeerShutdownContext)); - peer_shutdown_ctx->daemon = - pg->peers[running_arr[running_permute[i]]].daemon; - peer_shutdown_ctx->shutdown_ctx = shutdown_ctx; - GNUNET_SCHEDULER_add_now (&schedule_churn_shutdown_task, peer_shutdown_ctx); - } - - GNUNET_assert (stopped >= von); - if (von > 0) - { - churn_startup_ctx = GNUNET_malloc (sizeof (struct ChurnRestartContext)); - churn_startup_ctx->churn_ctx = churn_ctx; - churn_startup_ctx->timeout = timeout; - churn_startup_ctx->pg = pg; - } - for (i = 0; i < von; i++) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Starting up peer %d!\n", - stopped_arr[stopped_permute[i]]); - GNUNET_assert (stopped_arr != NULL); - peer_restart_ctx = GNUNET_malloc (sizeof (struct PeerRestartContext)); - peer_restart_ctx->churn_restart_ctx = churn_startup_ctx; - peer_restart_ctx->daemon = - pg->peers[stopped_arr[stopped_permute[i]]].daemon; - GNUNET_SCHEDULER_add_now (&schedule_churn_restart, peer_restart_ctx); - } - - GNUNET_free_non_null (running_arr); - GNUNET_free_non_null (stopped_arr); - GNUNET_free_non_null (running_permute); - GNUNET_free_non_null (stopped_permute); -} - -/* - * Start a given service for each of the peers in the peer group. - * - * @param pg handle for the peer group - * @param service the service to start - * @param timeout how long to wait for operations to finish before - * giving up - * @param cb function to call once finished - * @param cb_cls closure for cb - * - */ -void -GNUNET_TESTING_daemons_start_service (struct GNUNET_TESTING_PeerGroup *pg, - char *service, - struct GNUNET_TIME_Relative timeout, - GNUNET_TESTING_NotifyCompletion cb, - void *cb_cls) -{ - struct ServiceStartContext *start_ctx; - struct PeerServiceStartContext *peer_start_ctx; - unsigned int i; - - GNUNET_assert (service != NULL); - - start_ctx = GNUNET_malloc (sizeof (struct ServiceStartContext)); - start_ctx->pg = pg; - start_ctx->remaining = pg->total; - start_ctx->cb = cb; - start_ctx->cb_cls = cb_cls; - start_ctx->service = GNUNET_strdup (service); - start_ctx->timeout = timeout; - - for (i = 0; i < pg->total; i++) - { - peer_start_ctx = GNUNET_malloc (sizeof (struct PeerServiceStartContext)); - peer_start_ctx->start_ctx = start_ctx; - peer_start_ctx->daemon = pg->peers[i].daemon; - GNUNET_SCHEDULER_add_now (&schedule_service_start, peer_start_ctx); - } -} - -/** - * Restart all peers in the given group. - * - * @param pg the handle to the peer group - * @param callback function to call on completion (or failure) - * @param callback_cls closure for the callback function - */ -void -GNUNET_TESTING_daemons_restart (struct GNUNET_TESTING_PeerGroup *pg, - GNUNET_TESTING_NotifyCompletion callback, - void *callback_cls) -{ - struct RestartContext *restart_context; - unsigned int off; - - if (pg->total > 0) - { - restart_context = GNUNET_malloc (sizeof (struct RestartContext)); - restart_context->peer_group = pg; - restart_context->peers_restarted = 0; - restart_context->callback = callback; - restart_context->callback_cls = callback_cls; - - for (off = 0; off < pg->total; off++) - { - GNUNET_TESTING_daemon_restart (pg->peers[off].daemon, &restart_callback, - restart_context); - } - } -} - - -/** - * Start or stop an individual peer from the given group. - * - * @param pg handle to the peer group - * @param offset which peer to start or stop - * @param desired_status GNUNET_YES to have it running, GNUNET_NO to stop it - * @param timeout how long to wait for shutdown - * @param cb function to call at the end - * @param cb_cls closure for cb - */ -void -GNUNET_TESTING_daemons_vary (struct GNUNET_TESTING_PeerGroup *pg, - unsigned int offset, int desired_status, - struct GNUNET_TIME_Relative timeout, - GNUNET_TESTING_NotifyCompletion cb, void *cb_cls) -{ - struct ShutdownContext *shutdown_ctx; - struct ChurnRestartContext *startup_ctx; - struct ChurnContext *churn_ctx; - - if (GNUNET_NO == desired_status) - { - if (NULL != pg->peers[offset].daemon) - { - shutdown_ctx = GNUNET_malloc (sizeof (struct ShutdownContext)); - churn_ctx = GNUNET_malloc (sizeof (struct ChurnContext)); - churn_ctx->num_to_start = 0; - churn_ctx->num_to_stop = 1; - churn_ctx->cb = cb; - churn_ctx->cb_cls = cb_cls; - shutdown_ctx->cb_cls = churn_ctx; - GNUNET_TESTING_daemon_stop (pg->peers[offset].daemon, timeout, - &churn_stop_callback, shutdown_ctx, GNUNET_NO, - GNUNET_YES); - } - } - else if (GNUNET_YES == desired_status) - { - if (NULL == pg->peers[offset].daemon) - { - startup_ctx = GNUNET_malloc (sizeof (struct ChurnRestartContext)); - churn_ctx = GNUNET_malloc (sizeof (struct ChurnContext)); - churn_ctx->num_to_start = 1; - churn_ctx->num_to_stop = 0; - churn_ctx->cb = cb; - churn_ctx->cb_cls = cb_cls; - startup_ctx->churn_ctx = churn_ctx; - GNUNET_TESTING_daemon_start_stopped (pg->peers[offset].daemon, timeout, - &churn_start_callback, startup_ctx); - } - } - else - GNUNET_break (0); -} - - -/** - * Callback for shutting down peers in a peer group. - * - * @param cls closure (struct ShutdownContext) - * @param emsg NULL on success - */ -static void -internal_shutdown_callback (void *cls, const char *emsg) -{ - struct PeerShutdownContext *peer_shutdown_ctx = cls; - struct ShutdownContext *shutdown_ctx = peer_shutdown_ctx->shutdown_ctx; - unsigned int off; - int i; - struct OutstandingSSH *ssh_pos; - - shutdown_ctx->outstanding--; - if (peer_shutdown_ctx->daemon->hostname != NULL) - decrement_outstanding_at_host (peer_shutdown_ctx->daemon->hostname, - shutdown_ctx->pg); - - if (emsg == NULL) - { - shutdown_ctx->peers_down++; - } - else - { - GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, "internal_shutdown_callback", - "Failed to stop a peer: %s\n", emsg); - shutdown_ctx->peers_failed++; - } - - if ((shutdown_ctx->cb != NULL) && - (shutdown_ctx->peers_down + shutdown_ctx->peers_failed == - shutdown_ctx->total_peers)) - { - if (shutdown_ctx->peers_failed > 0) - shutdown_ctx->cb (shutdown_ctx->cb_cls, - "Not all peers successfully shut down!"); - else - shutdown_ctx->cb (shutdown_ctx->cb_cls, NULL); - - for (i = 0; i < shutdown_ctx->pg->total; i++) - { - if (shutdown_ctx->pg->peers[i].startup_task != GNUNET_SCHEDULER_NO_TASK) - GNUNET_SCHEDULER_cancel (shutdown_ctx->pg->peers[i].startup_task); - } - GNUNET_free (shutdown_ctx->pg->peers); - GNUNET_free_non_null (shutdown_ctx->pg->hostkey_data); - for (off = 0; off < shutdown_ctx->pg->num_hosts; off++) - { - GNUNET_free (shutdown_ctx->pg->hosts[off].hostname); - GNUNET_free_non_null (shutdown_ctx->pg->hosts[off].username); - } - GNUNET_free_non_null (shutdown_ctx->pg->hosts); - while (NULL != (ssh_pos = shutdown_ctx->pg->ssh_head)) - { - GNUNET_CONTAINER_DLL_remove (shutdown_ctx->pg->ssh_head, - shutdown_ctx->pg->ssh_tail, ssh_pos); - GNUNET_free (ssh_pos); - } - GNUNET_free (shutdown_ctx->pg); - GNUNET_free (shutdown_ctx); - } - GNUNET_free (peer_shutdown_ctx); -} - - -/** - * Task to rate limit the number of outstanding peer shutdown - * requests. This is necessary for making sure we don't do - * too many ssh connections at once, but is generally nicer - * to any system as well (graduated task starts, as opposed - * to calling gnunet-arm N times all at once). - */ -static void -schedule_shutdown_task (void *cls, - const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - struct PeerShutdownContext *peer_shutdown_ctx = cls; - struct ShutdownContext *shutdown_ctx; - struct GNUNET_TESTING_Daemon *d; - - GNUNET_assert (peer_shutdown_ctx != NULL); - d = peer_shutdown_ctx->daemon; - shutdown_ctx = peer_shutdown_ctx->shutdown_ctx; - GNUNET_assert (shutdown_ctx != NULL); - - if ((shutdown_ctx->outstanding < shutdown_ctx->pg->max_concurrent_ssh) || - ((d->hostname != NULL) && - (count_outstanding_at_host - (d->hostname, - shutdown_ctx->pg) < shutdown_ctx->pg->max_concurrent_ssh))) - { - if (d->hostname != NULL) - increment_outstanding_at_host (d->hostname, - shutdown_ctx->pg); - shutdown_ctx->outstanding++; - GNUNET_TESTING_daemon_stop (d, - shutdown_ctx->timeout, - &internal_shutdown_callback, peer_shutdown_ctx, - shutdown_ctx->delete_files, GNUNET_NO); - } - else - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply - (GNUNET_TIME_UNIT_MILLISECONDS, 100), - &schedule_shutdown_task, peer_shutdown_ctx); - -} - -/** - * Read a testing hosts file based on a configuration. - * Returns a DLL of hosts (caller must free!) on success - * or NULL on failure. - * - * @param cfg a configuration with a testing section - * - * @return DLL of hosts on success, NULL on failure - */ -struct GNUNET_TESTING_Host * -GNUNET_TESTING_hosts_load (const struct GNUNET_CONFIGURATION_Handle *cfg) -{ - struct GNUNET_TESTING_Host *hosts; - struct GNUNET_TESTING_Host *temphost; - char *data; - char *buf; - char *hostfile; - struct stat frstat; - int count; - int ret; - - /* Check for a hostfile containing user@host:port triples */ - if (GNUNET_OK != - GNUNET_CONFIGURATION_get_value_string (cfg, "testing", "hostfile", - &hostfile)) - return NULL; - - hosts = NULL; - temphost = NULL; - data = NULL; - if (hostfile != NULL) - { - if (GNUNET_OK != GNUNET_DISK_file_test (hostfile)) - GNUNET_DISK_fn_write (hostfile, NULL, 0, - GNUNET_DISK_PERM_USER_READ | - GNUNET_DISK_PERM_USER_WRITE); - if ((0 != STAT (hostfile, &frstat)) || (frstat.st_size == 0)) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "Could not open file specified for host list, ending test!"); - GNUNET_free (hostfile); - return NULL; - } - - data = GNUNET_malloc_large (frstat.st_size); - GNUNET_assert (data != NULL); - if (frstat.st_size != GNUNET_DISK_fn_read (hostfile, data, frstat.st_size)) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "Could not read file %s specified for host list, ending test!", - hostfile); - GNUNET_free (hostfile); - GNUNET_free (data); - return NULL; - } - - GNUNET_free_non_null (hostfile); - - buf = data; - count = 0; - while (count < frstat.st_size - 1) - { - count++; - if (((data[count] == '\n')) && (buf != &data[count])) - { - data[count] = '\0'; - temphost = GNUNET_malloc (sizeof (struct GNUNET_TESTING_Host)); - ret = - SSCANF (buf, "%a[a-zA-Z0-9_]@%a[a-zA-Z0-9.]:%hd", - &temphost->username, &temphost->hostname, &temphost->port); - if (3 == ret) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Successfully read host %s, port %d and user %s from file\n", - temphost->hostname, temphost->port, temphost->username); - } - else - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Error reading line `%s' in hostfile\n", buf); - GNUNET_free (temphost); - buf = &data[count + 1]; - continue; - } - temphost->next = hosts; - hosts = temphost; - buf = &data[count + 1]; - } - else if ((data[count] == '\n') || (data[count] == '\0')) - buf = &data[count + 1]; - } - } - GNUNET_free_non_null (data); - - return hosts; -} - -/** - * Shutdown all peers started in the given group. - * - * @param pg handle to the peer group - * @param timeout how long to wait for shutdown - * @param cb callback to notify upon success or failure - * @param cb_cls closure for cb - */ -void -GNUNET_TESTING_daemons_stop (struct GNUNET_TESTING_PeerGroup *pg, - struct GNUNET_TIME_Relative timeout, - GNUNET_TESTING_NotifyCompletion cb, void *cb_cls) -{ - unsigned int off; - struct ShutdownContext *shutdown_ctx; - struct PeerShutdownContext *peer_shutdown_ctx; - -#if OLD - struct PeerConnection *conn_iter; - struct PeerConnection *temp_conn; -#endif - struct ConnectContext *cc; - - GNUNET_assert (pg->total > 0); - while (NULL != (cc = pg->cc_head)) - { - GNUNET_CONTAINER_DLL_remove (pg->cc_head, pg->cc_tail, cc); - if (GNUNET_SCHEDULER_NO_TASK != cc->task) - GNUNET_SCHEDULER_cancel (cc->task); - if (NULL != cc->cc) - GNUNET_TESTING_daemons_connect_cancel (cc->cc); - GNUNET_free (cc); - } - - shutdown_ctx = GNUNET_malloc (sizeof (struct ShutdownContext)); - shutdown_ctx->delete_files = - GNUNET_CONFIGURATION_get_value_yesno (pg->cfg, "TESTING", "DELETE_FILES"); - shutdown_ctx->cb = cb; - shutdown_ctx->cb_cls = cb_cls; - shutdown_ctx->total_peers = pg->total; - shutdown_ctx->timeout = timeout; - shutdown_ctx->pg = pg; - - for (off = 0; off < pg->total; off++) - { - GNUNET_assert (NULL != pg->peers[off].daemon); - peer_shutdown_ctx = GNUNET_malloc (sizeof (struct PeerShutdownContext)); - peer_shutdown_ctx->daemon = pg->peers[off].daemon; - peer_shutdown_ctx->shutdown_ctx = shutdown_ctx; - GNUNET_SCHEDULER_add_now (&schedule_shutdown_task, peer_shutdown_ctx); - - if (NULL != pg->peers[off].cfg) - { - GNUNET_CONFIGURATION_destroy (pg->peers[off].cfg); - pg->peers[off].cfg = NULL; - } -#if OLD -// FIXME Do DLL remove for all pg->peers[off].LIST - conn_iter = pg->peers[off].allowed_peers_head; - while (conn_iter != NULL) - { - temp_conn = conn_iter->next; - GNUNET_free (conn_iter); - conn_iter = temp_conn; - } - pg->peers[off].allowed_peers_head = NULL; - - conn_iter = pg->peers[off].connect_peers_head; - while (conn_iter != NULL) - { - temp_conn = conn_iter->next; - GNUNET_free (conn_iter); - conn_iter = temp_conn; - } - pg->peers[off].connect_peers_head = NULL; - - conn_iter = pg->peers[off].blacklisted_peers_head; - while (conn_iter != NULL) - { - temp_conn = conn_iter->next; - GNUNET_free (conn_iter); - conn_iter = temp_conn; - } - pg->peers[off].blacklisted_peers_head = NULL; - - conn_iter = pg->peers[off].connect_peers_working_set_head; - while (conn_iter != NULL) - { - temp_conn = conn_iter->next; - GNUNET_free (conn_iter); - conn_iter = temp_conn; - } - pg->peers[off].connect_peers_working_set_head = NULL; -#else - if (pg->peers[off].allowed_peers != NULL) - GNUNET_CONTAINER_multihashmap_destroy (pg->peers[off].allowed_peers); - if (pg->peers[off].connect_peers != NULL) - GNUNET_CONTAINER_multihashmap_destroy (pg->peers[off].connect_peers); - if (pg->peers[off].blacklisted_peers != NULL) - GNUNET_CONTAINER_multihashmap_destroy (pg->peers[off].blacklisted_peers); -#endif - } -} - -/* end of testing_group.c */ diff --git a/src/testing/testing_new.c b/src/testing/testing_new.c deleted file mode 100644 index c45b89e..0000000 --- a/src/testing/testing_new.c +++ /dev/null @@ -1,1000 +0,0 @@ -/* - This file is part of GNUnet - (C) 2008, 2009, 2012 Christian Grothoff (and other contributing authors) - - GNUnet is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published - by the Free Software Foundation; either version 3, or (at your - option) any later version. - - GNUnet is distributed in the hope that it will be useful, but - WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - General Public License for more details. - - You should have received a copy of the GNU General Public License - along with GNUnet; see the file COPYING. If not, write to the - Free Software Foundation, Inc., 59 Temple Place - Suite 330, - Boston, MA 02111-1307, USA. - */ - -/** - * @file testing/testing_new.c - * @brief convenience API for writing testcases for GNUnet - * Many testcases need to start and stop a peer/service - * and this library is supposed to make that easier - * for TESTCASES. Normal programs should always - * use functions from gnunet_{util,arm}_lib.h. This API is - * ONLY for writing testcases (or internal use of the testbed). - * @author Christian Grothoff - * - */ -#include "platform.h" -#include "gnunet_util_lib.h" -#include "gnunet_testing_lib-new.h" - -#define LOG(kind,...) \ - GNUNET_log_from (kind, "gnunettestingnew", __VA_ARGS__) - - -/** - * Size of a hostkey when written to a file - */ -#define HOSTKEYFILESIZE 914 - - -/** - * Handle for a system on which GNUnet peers are executed; - * a system is used for reserving unique paths and ports. - */ -struct GNUNET_TESTING_System -{ - /** - * Prefix (i.e. "/tmp/gnunet-testing/") we prepend to each - * SERVICEHOME. - */ - char *tmppath; - - /** - * The hostname of the controller - */ - char *controller; - - /** - * Hostkeys data, contains "HOSTKEYFILESIZE * total_hostkeys" bytes. - */ - char *hostkeys_data; - - /** - * Bitmap where each TCP port that has already been reserved for - * some GNUnet peer is recorded. Note that we additionally need to - * test if a port is already in use by non-GNUnet components before - * assigning it to a peer/service. If we detect that a port is - * already in use, we also mark it in this bitmap. So all the bits - * that are zero merely indicate ports that MIGHT be available for - * peers. - */ - uint32_t reserved_tcp_ports[65536 / 32]; - - /** - * Bitmap where each UDP port that has already been reserved for - * some GNUnet peer is recorded. Note that we additionally need to - * test if a port is already in use by non-GNUnet components before - * assigning it to a peer/service. If we detect that a port is - * already in use, we also mark it in this bitmap. So all the bits - * that are zero merely indicate ports that MIGHT be available for - * peers. - */ - uint32_t reserved_udp_ports[65536 / 32]; - - /** - * Counter we use to make service home paths unique on this system; - * the full path consists of the tmppath and this number. Each - * UNIXPATH for a peer is also modified to include the respective - * path counter to ensure uniqueness. This field is incremented - * by one for each configured peer. Even if peers are destroyed, - * we never re-use path counters. - */ - uint32_t path_counter; - - /** - * The number of hostkeys - */ - uint32_t total_hostkeys; -}; - - -/** - * Handle for a GNUnet peer controlled by testing. - */ -struct GNUNET_TESTING_Peer -{ - - /** - * Path to the configuration file for this peer. - */ - char *cfgfile; - - /** - * Binary to be executed during 'GNUNET_TESTING_peer_start'. - * Typically 'gnunet-service-arm' (but can be set to a - * specific service by 'GNUNET_TESTING_service_run' if - * necessary). - */ - char *main_binary; - - /** - * Handle to the running binary of the service, NULL if the - * peer/service is currently not running. - */ - struct GNUNET_OS_Process *main_process; -}; - - -/** - * Lowest port used for GNUnet testing. Should be high enough to not - * conflict with other applications running on the hosts but be low - * enough to not conflict with client-ports (typically starting around - * 32k). - */ -#define LOW_PORT 12000 - - -/** - * Highest port used for GNUnet testing. Should be low enough to not - * conflict with the port range for "local" ports (client apps; see - * /proc/sys/net/ipv4/ip_local_port_range on Linux for example). - */ -#define HIGH_PORT 56000 - - -/** - * Create a system handle. There must only be one system - * handle per operating system. - * - * @param tmppath prefix path to use for all service homes - * @param controller hostname of the controlling host, - * service configurations are modified to allow - * control connections from this host; can be NULL - * @return handle to this system, NULL on error - */ -struct GNUNET_TESTING_System * -GNUNET_TESTING_system_create (const char *tmppath, - const char *controller) -{ - struct GNUNET_TESTING_System *system; - - if (NULL == tmppath) - { - LOG (GNUNET_ERROR_TYPE_ERROR, _("tmppath cannot be NULL\n")); - return NULL; - } - system = GNUNET_malloc (sizeof (struct GNUNET_TESTING_System)); - system->tmppath = GNUNET_strdup (tmppath); - if (NULL != controller) - system->controller = GNUNET_strdup (controller); - return system; -} - - -/** - * Free system resources. - * - * @param system system to be freed - * @param remove_paths should the 'tmppath' and all subdirectories - * be removed (clean up on shutdown)? - */ -void -GNUNET_TESTING_system_destroy (struct GNUNET_TESTING_System *system, - int remove_paths) -{ - if (NULL != system->hostkeys_data) - { - GNUNET_break (0); /* Use GNUNET_TESTING_hostkeys_unload() */ - GNUNET_TESTING_hostkeys_unload (system); - } - if (GNUNET_YES == remove_paths) - GNUNET_DISK_directory_remove (system->tmppath); - GNUNET_free (system->tmppath); - GNUNET_free_non_null (system->controller); - GNUNET_free (system); -} - - -/** - * Reserve a TCP or UDP port for a peer. - * - * @param system system to use for reservation tracking - * @param is_tcp GNUNET_YES for TCP ports, GNUNET_NO for UDP - * @return 0 if no free port was available - */ -uint16_t -GNUNET_TESTING_reserve_port (struct GNUNET_TESTING_System *system, - int is_tcp) -{ - struct GNUNET_NETWORK_Handle *socket; - struct addrinfo hint; - struct addrinfo *ret; - uint32_t *port_buckets; - char *open_port_str; - int bind_status; - uint32_t xor_image; - uint16_t index; - uint16_t open_port; - uint16_t pos; - - /* - FIXME: Instead of using getaddrinfo we should try to determine the port - status by the following heurestics. - - On systems which support both IPv4 and IPv6, only ports open on both - address families are considered open. - On system with either IPv4 or IPv6. A port is considered open if it's - open in the respective address family - */ - hint.ai_family = AF_UNSPEC; /* IPv4 and IPv6 */ - hint.ai_socktype = (GNUNET_YES == is_tcp)? SOCK_STREAM : SOCK_DGRAM; - hint.ai_protocol = 0; - hint.ai_addrlen = 0; - hint.ai_addr = NULL; - hint.ai_canonname = NULL; - hint.ai_next = NULL; - hint.ai_flags = AI_PASSIVE | AI_NUMERICSERV; /* Wild card address */ - port_buckets = (GNUNET_YES == is_tcp) ? - system->reserved_tcp_ports : system->reserved_udp_ports; - for (index = (LOW_PORT / 32) + 1; index < (HIGH_PORT / 32); index++) - { - xor_image = (UINT32_MAX ^ port_buckets[index]); - if (0 == xor_image) /* Ports in the bucket are full */ - continue; - pos = 0; - while (pos < 32) - { - if (0 == ((xor_image >> pos) & 1U)) - { - pos++; - continue; - } - open_port = (index * 32) + pos; - GNUNET_asprintf (&open_port_str, "%u", (unsigned int) open_port); - ret = NULL; - GNUNET_assert (0 == getaddrinfo (NULL, open_port_str, &hint, &ret)); - GNUNET_free (open_port_str); - socket = GNUNET_NETWORK_socket_create (ret->ai_family, - (GNUNET_YES == is_tcp) ? - SOCK_STREAM : SOCK_DGRAM, - 0); - GNUNET_assert (NULL != socket); - bind_status = GNUNET_NETWORK_socket_bind (socket, - ret->ai_addr, - ret->ai_addrlen); - freeaddrinfo (ret); - GNUNET_NETWORK_socket_close (socket); - socket = NULL; - port_buckets[index] |= (1U << pos); /* Set the port bit */ - if (GNUNET_OK == bind_status) - { - LOG (GNUNET_ERROR_TYPE_DEBUG, - "Found a free port %u\n", (unsigned int) open_port); - return open_port; - } - pos++; - } - } - return 0; -} - - -/** - * Release reservation of a TCP or UDP port for a peer - * (used during GNUNET_TESTING_peer_destroy). - * - * @param system system to use for reservation tracking - * @param is_tcp GNUNET_YES for TCP ports, GNUNET_NO for UDP - * @param port reserved port to release - */ -void -GNUNET_TESTING_release_port (struct GNUNET_TESTING_System *system, - int is_tcp, - uint16_t port) -{ - uint32_t *port_buckets; - uint16_t bucket; - uint16_t pos; - - port_buckets = (GNUNET_YES == is_tcp) ? - system->reserved_tcp_ports : system->reserved_udp_ports; - bucket = port / 32; - pos = port % 32; - LOG (GNUNET_ERROR_TYPE_DEBUG, "Releasing port %u\n", port); - if (0 == (port_buckets[bucket] & (1U << pos))) - { - GNUNET_break(0); /* Port was not reserved by us using reserve_port() */ - return; - } - port_buckets[bucket] &= ~(1U << pos); -} - - -/** - * Reserve a SERVICEHOME path for a peer. - * - * @param system system to use for reservation tracking - * @return NULL on error, otherwise fresh unique path to use - * as the servicehome for the peer; must be freed by the caller - */ -// static -char * -reserve_path (struct GNUNET_TESTING_System *system) -{ - char *reserved_path; - - GNUNET_asprintf (&reserved_path, - "%s/%u", system->tmppath, system->path_counter++); - return reserved_path; -} - - -/** - * Testing includes a number of pre-created hostkeys for faster peer - * startup. This function loads such keys into memory from a file. - * - * @param system the testing system handle - * @param filename the path of the hostkeys file - * @return GNUNET_OK on success; GNUNET_SYSERR on error - */ -int -GNUNET_TESTING_hostkeys_load (struct GNUNET_TESTING_System *system, - const char *filename) -{ - struct GNUNET_DISK_FileHandle *fd; - uint64_t fs; - - if (GNUNET_YES != GNUNET_DISK_file_test (filename)) - { - LOG (GNUNET_ERROR_TYPE_ERROR, - _("Hostkeys file not found: %s\n"), filename); - return GNUNET_SYSERR; - } - /* Check hostkey file size, read entire thing into memory */ - fd = GNUNET_DISK_file_open (filename, GNUNET_DISK_OPEN_READ, - GNUNET_DISK_PERM_NONE); - if (NULL == fd) - { - LOG (GNUNET_ERROR_TYPE_ERROR, - _("Could not open hostkeys file: %s\n"), filename); - return GNUNET_SYSERR; - } - if (GNUNET_OK != - GNUNET_DISK_file_size (filename, &fs, GNUNET_YES, GNUNET_YES)) - fs = 0; - if (0 == fs) - { - GNUNET_DISK_file_close (fd); - return GNUNET_SYSERR; /* File is empty */ - } - if (0 != (fs % HOSTKEYFILESIZE)) - { - GNUNET_DISK_file_close (fd); - LOG (GNUNET_ERROR_TYPE_ERROR, - _("Incorrect hostkey file format: %s\n"), filename); - return GNUNET_SYSERR; - } - GNUNET_break (NULL == system->hostkeys_data); - system->total_hostkeys = fs / HOSTKEYFILESIZE; - system->hostkeys_data = GNUNET_malloc_large (fs); /* free in hostkeys_unload */ - GNUNET_assert (fs == GNUNET_DISK_file_read (fd, system->hostkeys_data, fs)); - GNUNET_DISK_file_close (fd); - return GNUNET_OK; -} - - -/** - * Function to remove the loaded hostkeys - * - * @param system the testing system handle - */ -void -GNUNET_TESTING_hostkeys_unload (struct GNUNET_TESTING_System *system) -{ - GNUNET_break (NULL != system->hostkeys_data); - GNUNET_free_non_null (system->hostkeys_data); - system->hostkeys_data = NULL; - system->total_hostkeys = 0; -} - - -/** - * Testing includes a number of pre-created hostkeys for - * faster peer startup. This function can be used to - * access the n-th key of those pre-created hostkeys; note - * that these keys are ONLY useful for testing and not - * secure as the private keys are part of the public - * GNUnet source code. - * - * This is primarily a helper function used internally - * by 'GNUNET_TESTING_peer_configure'. - * - * @param system the testing system handle - * @param key_number desired pre-created hostkey to obtain - * @param id set to the peer's identity (hash of the public - * key; if NULL, GNUNET_SYSERR is returned immediately - * @return GNUNET_SYSERR on error (not enough keys) - */ -int -GNUNET_TESTING_hostkey_get (const struct GNUNET_TESTING_System *system, - uint32_t key_number, - struct GNUNET_PeerIdentity *id) -{ - struct GNUNET_CRYPTO_RsaPrivateKey *private_key; - struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded public_key; - - if ((NULL == id) || (NULL == system->hostkeys_data)) - return GNUNET_SYSERR; - if (key_number >= system->total_hostkeys) - { - LOG (GNUNET_ERROR_TYPE_ERROR, - _("Key number %u does not exist\n"), key_number); - return GNUNET_SYSERR; - } - private_key = GNUNET_CRYPTO_rsa_decode_key (system->hostkeys_data + - (key_number * HOSTKEYFILESIZE), - HOSTKEYFILESIZE); - if (NULL == private_key) - { - LOG (GNUNET_ERROR_TYPE_ERROR, - _("Error while decoding key %u\n"), key_number); - return GNUNET_SYSERR; - } - GNUNET_CRYPTO_rsa_key_get_public (private_key, &public_key); - GNUNET_CRYPTO_hash (&public_key, - sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded), - &(id->hashPubKey)); - GNUNET_CRYPTO_rsa_key_free (private_key); - return GNUNET_OK; -} - - -/** - * Structure for holding data to build new configurations from a configuration - * template - */ -struct UpdateContext -{ - /** - * The system for which we are building configurations - */ - struct GNUNET_TESTING_System *system; - - /** - * The configuration we are building - */ - struct GNUNET_CONFIGURATION_Handle *cfg; - - /** - * The customized service home path for this peer - */ - char *service_home; - - /** - * build status - to signal error while building a configuration - */ - int status; -}; - - -/** - * Function to iterate over options. Copies - * the options to the target configuration, - * updating PORT values as needed. - * - * @param cls the UpdateContext - * @param section name of the section - * @param option name of the option - * @param value value of the option - */ -static void -update_config (void *cls, const char *section, const char *option, - const char *value) -{ - struct UpdateContext *uc = cls; - unsigned int ival; - char cval[12]; - char uval[128]; - char *single_variable; - char *per_host_variable; - unsigned long long num_per_host; - uint16_t new_port; - - if (GNUNET_OK != uc->status) - return; - if (! ((0 == strcmp (option, "PORT")) - || (0 == strcmp (option, "UNIXPATH")) - || (0 == strcmp (option, "HOSTNAME")))) - return; - GNUNET_asprintf (&single_variable, "single_%s_per_host", section); - GNUNET_asprintf (&per_host_variable, "num_%s_per_host", section); - if ((0 == strcmp (option, "PORT")) && (1 == SSCANF (value, "%u", &ival))) - { - if ((ival != 0) && - (GNUNET_YES != - GNUNET_CONFIGURATION_get_value_yesno (uc->cfg, "testing", - single_variable))) - { - /* FIXME: What about UDP? */ - new_port = GNUNET_TESTING_reserve_port (uc->system, GNUNET_YES); - if (0 == new_port) - { - uc->status = GNUNET_SYSERR; - return; - } - GNUNET_snprintf (cval, sizeof (cval), "%u", new_port); - value = cval; - } - else if ((ival != 0) && - (GNUNET_YES == - GNUNET_CONFIGURATION_get_value_yesno (uc->cfg, "testing", - single_variable)) && - GNUNET_CONFIGURATION_get_value_number (uc->cfg, "testing", - per_host_variable, - &num_per_host)) - { - /* GNUNET_snprintf (cval, sizeof (cval), "%u", */ - /* ival + ctx->fdnum % num_per_host); */ - /* value = cval; */ - GNUNET_break (0); /* FIXME */ - } - } - if (0 == strcmp (option, "UNIXPATH")) - { - if (GNUNET_YES != - GNUNET_CONFIGURATION_get_value_yesno (uc->cfg, "testing", - single_variable)) - { - GNUNET_snprintf (uval, sizeof (uval), "%s/%s.sock", - uc->service_home, section); - value = uval; - } - else if ((GNUNET_YES == - GNUNET_CONFIGURATION_get_value_number (uc->cfg, "testing", - per_host_variable, - &num_per_host)) && - (num_per_host > 0)) - { - GNUNET_break(0); /* FIXME */ - } - } - if ((0 == strcmp (option, "HOSTNAME")) && (NULL != uc->system->controller)) - { - value = uc->system->controller; - } - GNUNET_free (single_variable); - GNUNET_free (per_host_variable); - GNUNET_CONFIGURATION_set_value_string (uc->cfg, section, option, value); -} - - -/** - * Section iterator to set ACCEPT_FROM in all sections - * - * @param cls the UpdateContext - * @param section name of the section - */ -static void -update_config_sections (void *cls, - const char *section) -{ - struct UpdateContext *uc = cls; - char *orig_allowed_hosts; - char *allowed_hosts; - - if (GNUNET_OK != - GNUNET_CONFIGURATION_get_value_string (uc->cfg, section, "ACCEPT_FROM", - &orig_allowed_hosts)) - { - orig_allowed_hosts = GNUNET_strdup ("127.0.0.1;"); - } - if (NULL == uc->system->controller) - allowed_hosts = GNUNET_strdup (orig_allowed_hosts); - else - GNUNET_asprintf (&allowed_hosts, "%s %s;", orig_allowed_hosts, - uc->system->controller); - GNUNET_free (orig_allowed_hosts); - GNUNET_CONFIGURATION_set_value_string (uc->cfg, section, "ACCEPT_FROM", - allowed_hosts); - GNUNET_free (allowed_hosts); -} - - -/** - * Create a new configuration using the given configuration - * as a template; ports and paths will be modified to select - * available ports on the local system. If we run - * out of "*port" numbers, return SYSERR. - * - * This is primarily a helper function used internally - * by 'GNUNET_TESTING_peer_configure'. - * - * @param system system to use to coordinate resource usage - * @param cfg template configuration to update - * @return GNUNET_OK on success, GNUNET_SYSERR on error - the configuration will - * be incomplete and should not be used there upon - */ -int -GNUNET_TESTING_configuration_create (struct GNUNET_TESTING_System *system, - struct GNUNET_CONFIGURATION_Handle *cfg) -{ - struct UpdateContext uc; - - uc.system = system; - uc.cfg = cfg; - uc.status = GNUNET_OK; - GNUNET_asprintf (&uc.service_home, "%s/%u", system->tmppath, - system->path_counter++); - GNUNET_CONFIGURATION_set_value_string (cfg, "PATHS", "SERVICEHOME", - uc.service_home); - /* make PORTs and UNIXPATHs unique */ - GNUNET_CONFIGURATION_iterate (cfg, &update_config, &uc); - /* allow connections to services from system controller host */ - GNUNET_CONFIGURATION_iterate_sections (cfg, &update_config_sections, &uc); - /* enable loopback-based connections between peers */ - GNUNET_CONFIGURATION_set_value_string (cfg, - "nat", - "USE_LOCALADDR", "YES"); - GNUNET_free (uc.service_home); - return uc.status; -} - - -/** - * Configure a GNUnet peer. GNUnet must be installed on the local - * system and available in the PATH. - * - * @param system system to use to coordinate resource usage - * @param cfg configuration to use; will be UPDATED (to reflect needed - * changes in port numbers and paths) - * @param key_number number of the hostkey to use for the peer - * @param id identifier for the daemon, will be set, can be NULL - * @param emsg set to error message (set to NULL on success), can be NULL - * @return handle to the peer, NULL on error - */ -struct GNUNET_TESTING_Peer * -GNUNET_TESTING_peer_configure (struct GNUNET_TESTING_System *system, - struct GNUNET_CONFIGURATION_Handle *cfg, - uint32_t key_number, - struct GNUNET_PeerIdentity *id, - char **emsg) -{ - struct GNUNET_TESTING_Peer *peer; - struct GNUNET_DISK_FileHandle *fd; - char *service_home; - char hostkey_filename[128]; - char *config_filename; - char *emsg_; - - if (NULL != emsg) - *emsg = NULL; - if (GNUNET_OK != GNUNET_TESTING_configuration_create (system, cfg)) - { - GNUNET_asprintf (&emsg_, - _("Failed to create configuration for peer (not enough free ports?)\n")); - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "%s", *emsg_); - if (NULL != emsg) - *emsg = emsg_; - else - GNUNET_free (emsg_); - return NULL; - } - if (key_number >= system->total_hostkeys) - { - GNUNET_asprintf (&emsg_, - _("You attempted to create a testbed with more than %u hosts. Please precompute more hostkeys first.\n"), - (unsigned int) system->total_hostkeys); - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "%s", *emsg_); - if (NULL != emsg) - *emsg = emsg_; - else - GNUNET_free (emsg_); - return NULL; - } - if ((NULL != id) && - (GNUNET_SYSERR == GNUNET_TESTING_hostkey_get (system, key_number, id))) - { - GNUNET_asprintf (&emsg_, - _("Failed to initialize hostkey for peer %u\n"), - (unsigned int) key_number); - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "%s", *emsg_); - if (NULL != emsg) - *emsg = emsg_; - else - GNUNET_free (emsg_); - return NULL; - } - GNUNET_assert (GNUNET_OK == - GNUNET_CONFIGURATION_get_value_string (cfg, "PATHS", - "SERVICEHOME", - &service_home)); - GNUNET_snprintf (hostkey_filename, sizeof (hostkey_filename), "%s/.hostkey", - service_home); - fd = GNUNET_DISK_file_open (hostkey_filename, - GNUNET_DISK_OPEN_CREATE | GNUNET_DISK_OPEN_WRITE, - GNUNET_DISK_PERM_USER_READ - | GNUNET_DISK_PERM_USER_WRITE); - if (NULL == fd) - { - GNUNET_break (0); - return NULL; - } - if (HOSTKEYFILESIZE != - GNUNET_DISK_file_write (fd, system->hostkeys_data - + (key_number * HOSTKEYFILESIZE), - HOSTKEYFILESIZE)) - { - GNUNET_asprintf (&emsg_, - _("Failed to write hostkey file for peer %u: %s\n"), - (unsigned int) key_number, - STRERROR (errno)); - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "%s", *emsg_); - if (NULL != emsg) - *emsg = emsg_; - else - GNUNET_free (emsg_); - GNUNET_DISK_file_close (fd); - return NULL; - } - GNUNET_DISK_file_close (fd); - GNUNET_asprintf (&config_filename, "%s/config", service_home); - GNUNET_free (service_home); - if (GNUNET_OK != GNUNET_CONFIGURATION_write (cfg, config_filename)) - { - GNUNET_asprintf (&emsg_, - _("Failed to write configuration file `%s' for peer %u: %s\n"), - config_filename, - (unsigned int) key_number, - STRERROR (errno)); - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "%s", *emsg_); - if (NULL != emsg) - *emsg = emsg_; - else - GNUNET_free (emsg_); - return NULL; - } - peer = GNUNET_malloc (sizeof (struct GNUNET_TESTING_Peer)); - peer->cfgfile = config_filename; /* Free in peer_destroy */ - peer->main_binary = GNUNET_strdup ("gnunet-service-arm"); - return peer; -} - - -/** - * Start the peer. - * - * @param peer peer to start - * @return GNUNET_OK on success, GNUNET_SYSERR on error (i.e. peer already running) - */ -int -GNUNET_TESTING_peer_start (struct GNUNET_TESTING_Peer *peer) -{ - if (NULL != peer->main_process) - { - GNUNET_break (0); - return GNUNET_SYSERR; - } - GNUNET_assert (NULL != peer->cfgfile); - peer->main_process = GNUNET_OS_start_process (GNUNET_NO, NULL, NULL, - peer->main_binary, "-c", - peer->cfgfile, - NULL); - if (NULL == peer->main_process) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - _("Failed to start `%s': %s\n"), - peer->main_binary, - STRERROR (errno)); - return GNUNET_SYSERR; - } - return GNUNET_OK; -} - - -/** - * Stop the peer. - * - * @param peer peer to stop - * @return GNUNET_OK on success, GNUNET_SYSERR on error (i.e. peer not running) - */ -int -GNUNET_TESTING_peer_stop (struct GNUNET_TESTING_Peer *peer) -{ - if (NULL == peer->main_process) - { - GNUNET_break (0); - return GNUNET_SYSERR; - } - (void) GNUNET_OS_process_kill (peer->main_process, SIGTERM); - GNUNET_assert (GNUNET_OK == GNUNET_OS_process_wait (peer->main_process)); - GNUNET_OS_process_destroy (peer->main_process); - peer->main_process = NULL; - return GNUNET_OK; -} - - -/** - * Destroy the peer. Releases resources locked during peer configuration. - * If the peer is still running, it will be stopped AND a warning will be - * printed (users of the API should stop the peer explicitly first). - * - * @param peer peer to destroy - */ -void -GNUNET_TESTING_peer_destroy (struct GNUNET_TESTING_Peer *peer) -{ - if (NULL != peer->main_process) - { - GNUNET_break (0); - GNUNET_TESTING_peer_stop (peer); - } - GNUNET_free (peer->cfgfile); - GNUNET_free (peer->main_binary); - GNUNET_free (peer); -} - - -/** - * Start a single peer and run a test using the testing library. - * Starts a peer using the given configuration and then invokes the - * given callback. This function ALSO initializes the scheduler loop - * and should thus be called directly from "main". The testcase - * should self-terminate by invoking 'GNUNET_SCHEDULER_shutdown'. - * - * @param tmppath path for storing temporary data for the test - * @param cfgfilename name of the configuration file to use; - * use NULL to only run with defaults - * @param tm main function of the testcase - * @param tm_cls closure for 'tm' - * @return 0 on success, 1 on error - */ -int -GNUNET_TESTING_peer_run (const char *tmppath, - const char *cfgfilename, - GNUNET_TESTING_TestMain tm, - void *tm_cls) -{ - return GNUNET_TESTING_service_run (tmppath, "arm", - cfgfilename, tm, tm_cls); -} - - -/** - * Structure for holding service data - */ -struct ServiceContext -{ - /** - * The configuration of the peer in which the service is run - */ - const struct GNUNET_CONFIGURATION_Handle *cfg; - - /** - * Callback to signal service startup - */ - GNUNET_TESTING_TestMain tm; - - /** - * Closure for the above callback - */ - void *tm_cls; -}; - - -/** - * Callback to be called when SCHEDULER has been started - * - * @param cls the ServiceContext - * @param tc the TaskContext - */ -static void -service_run_main (void *cls, - const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - struct ServiceContext *sc = cls; - - sc->tm (sc->tm_cls, sc->cfg); -} - - -/** - * Start a single service (no ARM, except of course if the given - * service name is 'arm') and run a test using the testing library. - * Starts a service using the given configuration and then invokes the - * given callback. This function ALSO initializes the scheduler loop - * and should thus be called directly from "main". The testcase - * should self-terminate by invoking 'GNUNET_SCHEDULER_shutdown'. - * - * This function is useful if the testcase is for a single service - * and if that service doesn't itself depend on other services. - * - * @param tmppath path for storing temporary data for the test - * @param service_name name of the service to run - * @param cfgfilename name of the configuration file to use; - * use NULL to only run with defaults - * @param tm main function of the testcase - * @param tm_cls closure for 'tm' - * @return 0 on success, 1 on error - */ -int -GNUNET_TESTING_service_run (const char *tmppath, - const char *service_name, - const char *cfgfilename, - GNUNET_TESTING_TestMain tm, - void *tm_cls) -{ - struct ServiceContext sc; - struct GNUNET_TESTING_System *system; - struct GNUNET_TESTING_Peer *peer; - struct GNUNET_CONFIGURATION_Handle *cfg; - char *data_dir; - char *hostkeys_file; - - data_dir = GNUNET_OS_installation_get_path (GNUNET_OS_IPK_DATADIR); - GNUNET_asprintf (&hostkeys_file, "%s/testing_hostkeys.dat", data_dir); - GNUNET_free (data_dir); - system = GNUNET_TESTING_system_create (tmppath, "localhost"); - if (NULL == system) - { - GNUNET_free (hostkeys_file); - return 1; - } - if (GNUNET_OK != GNUNET_TESTING_hostkeys_load (system, hostkeys_file)) - { - GNUNET_free (hostkeys_file); - GNUNET_TESTING_system_destroy (system, GNUNET_YES); - return 1; - } - GNUNET_free (hostkeys_file); - cfg = GNUNET_CONFIGURATION_create (); - if (GNUNET_OK != GNUNET_CONFIGURATION_load (cfg, cfgfilename)) - { - LOG (GNUNET_ERROR_TYPE_ERROR, - _("Failed to load configuration from %s\n"), cfgfilename); - GNUNET_CONFIGURATION_destroy (cfg); - GNUNET_TESTING_system_destroy (system, GNUNET_YES); - return 1; - } - peer = GNUNET_TESTING_peer_configure (system, cfg, 0, NULL, NULL); - if (NULL == peer) - { - GNUNET_CONFIGURATION_destroy (cfg); - GNUNET_TESTING_hostkeys_unload (system); - GNUNET_TESTING_system_destroy (system, GNUNET_YES); - return 1; - } - GNUNET_TESTING_hostkeys_unload (system); - GNUNET_free (peer->main_binary); - GNUNET_asprintf (&peer->main_binary, "gnunet-service-%s", service_name); - if (GNUNET_OK != GNUNET_TESTING_peer_start (peer)) - { - GNUNET_TESTING_peer_destroy (peer); - GNUNET_CONFIGURATION_destroy (cfg); - GNUNET_TESTING_system_destroy (system, GNUNET_YES); - return 1; - } - sc.cfg = cfg; - sc.tm = tm; - sc.tm_cls = tm_cls; - GNUNET_SCHEDULER_run (&service_run_main, &sc); /* Scheduler loop */ - if (GNUNET_OK != GNUNET_TESTING_peer_stop (peer)) - { - GNUNET_TESTING_peer_destroy (peer); - GNUNET_CONFIGURATION_destroy (cfg); - GNUNET_TESTING_system_destroy (system, GNUNET_YES); - return 1; - } - GNUNET_TESTING_peer_destroy (peer); - GNUNET_CONFIGURATION_destroy (cfg); - GNUNET_TESTING_system_destroy (system, GNUNET_YES); - return 0; -} - - -/* end of testing_new.c */ diff --git a/src/testing/testing_peergroup.c b/src/testing/testing_peergroup.c deleted file mode 100644 index 87504ed..0000000 --- a/src/testing/testing_peergroup.c +++ /dev/null @@ -1,1017 +0,0 @@ -/* - This file is part of GNUnet - (C) 2008-2011 Christian Grothoff (and other contributing authors) - - GNUnet is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published - by the Free Software Foundation; either version 3, or (at your - option) any later version. - - GNUnet is distributed in the hope that it will be useful, but - WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - General Public License for more details. - - You should have received a copy of the GNU General Public License - along with GNUnet; see the file COPYING. If not, write to the - Free Software Foundation, Inc., 59 Temple Place - Suite 330, - Boston, MA 02111-1307, USA. - */ - -/** - * @file testing/testing_peergroup.c - * @brief API implementation for easy peer group creation - * @author Nathan Evans - * @author Christian Grothoff - * - */ -#include "platform.h" -#include "gnunet_constants.h" -#include "gnunet_arm_service.h" -#include "gnunet_testing_lib.h" -#include "gnunet_core_service.h" -#include "gnunet_disk_lib.h" - -/** Globals **/ -#define DEFAULT_CONNECT_TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 30) - -#define DEFAULT_CONNECT_ATTEMPTS 2 - -/** Struct definitions **/ - -struct PeerGroupStartupContext -{ - struct GNUNET_TESTING_PeerGroup *pg; - const struct GNUNET_CONFIGURATION_Handle *cfg; - unsigned int total; - unsigned int peers_left; - unsigned long long max_concurrent_connections; - - /** - * Maximum attemps to connect two daemons. - */ - unsigned long long connect_attempts; - - /** - * How long to spend trying to establish all the connections? - */ - struct GNUNET_TIME_Relative connect_timeout; - - unsigned long long max_concurrent_ssh; - struct GNUNET_TIME_Absolute timeout; - GNUNET_TESTING_NotifyConnection connect_cb; - GNUNET_TESTING_NotifyCompletion peergroup_cb; - - /** - * Closure for all peergroup callbacks. - */ - void *cls; - - const struct GNUNET_TESTING_Host *hostnames; - - /** - * FIXME document - */ - enum GNUNET_TESTING_Topology topology; - - float topology_percentage; - - float topology_probability; - - /** - * FIXME document - */ - enum GNUNET_TESTING_Topology restrict_topology; - - /** - * FIXME document - */ - char *restrict_transports; - - /** - * Initial connections - */ - enum GNUNET_TESTING_Topology connect_topology; - enum GNUNET_TESTING_TopologyOption connect_topology_option; - double connect_topology_option_modifier; - int verbose; - - struct ProgressMeter *hostkey_meter; - struct ProgressMeter *peer_start_meter; - struct ProgressMeter *connect_meter; - - /** - * Task used to kill the peergroup. - */ - GNUNET_SCHEDULER_TaskIdentifier die_task; - - char *fail_reason; - - /** - * Variable used to store the number of connections we should wait for. - */ - unsigned int expected_connections; - - /** - * Time when the connecting peers was started. - */ - struct GNUNET_TIME_Absolute connect_start_time; - - /** - * The total number of connections that have been created so far. - */ - unsigned int total_connections; - - /** - * The total number of connections that have failed so far. - */ - unsigned int failed_connections; - - /** - * File handle to write out topology in dot format. - */ - struct GNUNET_DISK_FileHandle *topology_output_file; -}; - -struct TopologyOutputContext -{ - struct GNUNET_DISK_FileHandle *file; - GNUNET_TESTING_NotifyCompletion notify_cb; - void *notify_cb_cls; -}; - -/** - * Simple struct to keep track of progress, and print a - * percentage meter for long running tasks. - */ -struct ProgressMeter -{ - /** - * Total number of tasks to complete. - */ - unsigned int total; - - /** - * Print percentage done after modnum tasks. - */ - unsigned int modnum; - - /** - * Print a . each dotnum tasks. - */ - unsigned int dotnum; - - /** - * Total number completed thus far. - */ - unsigned int completed; - - /** - * Whether or not to print. - */ - int print; - - /** - * Startup string for progress meter. - */ - char *startup_string; -}; - - -/** Utility functions **/ - -/** - * Create a meter to keep track of the progress of some task. - * - * @param total the total number of items to complete - * @param start_string a string to prefix the meter with (if printing) - * @param print GNUNET_YES to print the meter, GNUNET_NO to count - * internally only - * - * @return the progress meter - */ -static struct ProgressMeter * -create_meter (unsigned int total, char *start_string, int print) -{ - struct ProgressMeter *ret; - - ret = GNUNET_malloc (sizeof (struct ProgressMeter)); - ret->print = print; - ret->total = total; - ret->modnum = (total / 4 == 0) ? 1 : (total / 4); - ret->dotnum = (total / 50) + 1; - if (start_string != NULL) - ret->startup_string = GNUNET_strdup (start_string); - else - ret->startup_string = GNUNET_strdup (""); - - return ret; -} - -/** - * Update progress meter (increment by one). - * - * @param meter the meter to update and print info for - * - * @return GNUNET_YES if called the total requested, - * GNUNET_NO if more items expected - */ -static int -update_meter (struct ProgressMeter *meter) -{ - if (meter->print == GNUNET_YES) - { - if (meter->completed % meter->modnum == 0) - { - if (meter->completed == 0) - { - FPRINTF (stdout, "%sProgress: [0%%", meter->startup_string); - } - else - FPRINTF (stdout, "%d%%", - (int) (((float) meter->completed / meter->total) * 100)); - } - else if (meter->completed % meter->dotnum == 0) - FPRINTF (stdout, "%s", "."); - - if (meter->completed + 1 == meter->total) - FPRINTF (stdout, "%d%%]\n", 100); - fflush (stdout); - } - meter->completed++; - - if (meter->completed == meter->total) - return GNUNET_YES; - return GNUNET_NO; -} - -/** - * Reset progress meter. - * - * @param meter the meter to reset - * - * @return GNUNET_YES if meter reset, - * GNUNET_SYSERR on error - */ -static int -reset_meter (struct ProgressMeter *meter) -{ - if (meter == NULL) - return GNUNET_SYSERR; - - meter->completed = 0; - return GNUNET_YES; -} - -/** - * Release resources for meter - * - * @param meter the meter to free - */ -static void -free_meter (struct ProgressMeter *meter) -{ - GNUNET_free_non_null (meter->startup_string); - GNUNET_free (meter); -} - - -/** Functions for creating, starting and connecting the peergroup **/ - -/** - * Check whether peers successfully shut down. - */ -static void -internal_shutdown_callback (void *cls, const char *emsg) -{ - struct PeerGroupStartupContext *pg_start_ctx = cls; - - if (emsg != NULL) - pg_start_ctx->peergroup_cb (pg_start_ctx->cls, emsg); - else - pg_start_ctx->peergroup_cb (pg_start_ctx->cls, pg_start_ctx->fail_reason); -} - -/** - * Check if the get_handle is being used, if so stop the request. Either - * way, schedule the end_badly_cont function which actually shuts down the - * test. - */ -static void -end_badly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - struct PeerGroupStartupContext *pg_start_ctx = cls; - - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Failing peer group startup with error: `%s'!\n", - pg_start_ctx->fail_reason); - - GNUNET_TESTING_daemons_stop (pg_start_ctx->pg, - GNUNET_TIME_absolute_get_remaining - (pg_start_ctx->timeout), - &internal_shutdown_callback, pg_start_ctx); - - if (pg_start_ctx->hostkey_meter != NULL) - { - free_meter (pg_start_ctx->hostkey_meter); - pg_start_ctx->hostkey_meter = NULL; - } - if (pg_start_ctx->peer_start_meter != NULL) - { - free_meter (pg_start_ctx->peer_start_meter); - pg_start_ctx->peer_start_meter = NULL; - } - if (pg_start_ctx->connect_meter != NULL) - { - free_meter (pg_start_ctx->connect_meter); - pg_start_ctx->connect_meter = NULL; - } -} - -/** - * This function is called whenever a connection attempt is finished between two of - * the started peers (started with GNUNET_TESTING_daemons_start). The total - * number of times this function is called should equal the number returned - * from the GNUNET_TESTING_connect_topology call. - * - * The emsg variable is NULL on success (peers connected), and non-NULL on - * failure (peers failed to connect). - */ -static void -internal_topology_callback (void *cls, const struct GNUNET_PeerIdentity *first, - const struct GNUNET_PeerIdentity *second, - uint32_t distance, - const struct GNUNET_CONFIGURATION_Handle *first_cfg, - const struct GNUNET_CONFIGURATION_Handle - *second_cfg, - struct GNUNET_TESTING_Daemon *first_daemon, - struct GNUNET_TESTING_Daemon *second_daemon, - const char *emsg) -{ - struct PeerGroupStartupContext *pg_start_ctx = cls; - char *temp_str; - char *second_str; - int temp; - -#if TIMING - unsigned long long duration; - unsigned long long total_duration; - unsigned int new_connections; - unsigned int new_failed_connections; - double conns_per_sec_recent; - double conns_per_sec_total; - double failed_conns_per_sec_recent; - double failed_conns_per_sec_total; -#endif - -#if TIMING - if (GNUNET_TIME_absolute_get_difference - (connect_last_time, - GNUNET_TIME_absolute_get ()).rel_value > - GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, - CONN_UPDATE_DURATION).rel_value) - { - /* Get number of new connections */ - new_connections = total_connections - previous_connections; - - /* Get number of new FAILED connections */ - new_failed_connections = failed_connections - previous_failed_connections; - - /* Get duration in seconds */ - duration = - GNUNET_TIME_absolute_get_difference (connect_last_time, - GNUNET_TIME_absolute_get - ()).rel_value / 1000; - total_duration = - GNUNET_TIME_absolute_get_difference (connect_start_time, - GNUNET_TIME_absolute_get - ()).rel_value / 1000; - - failed_conns_per_sec_recent = (double) new_failed_connections / duration; - failed_conns_per_sec_total = (double) failed_connections / total_duration; - conns_per_sec_recent = (double) new_connections / duration; - conns_per_sec_total = (double) total_connections / total_duration; - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Recent: %.2f/s, Total: %.2f/s, Recent failed: %.2f/s, total failed %.2f/s\n", - conns_per_sec_recent, CONN_UPDATE_DURATION, conns_per_sec_total, - failed_conns_per_sec_recent, failed_conns_per_sec_total); - connect_last_time = GNUNET_TIME_absolute_get (); - previous_connections = total_connections; - previous_failed_connections = failed_connections; - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "have %u total_connections, %u failed\n", total_connections, - failed_connections); - } -#endif - - - if (emsg == NULL) - { - pg_start_ctx->total_connections++; -#if VERBOSE > 1 - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "connected peer %s to peer %s, distance %u\n", - first_daemon->shortname, second_daemon->shortname, distance); -#endif - if (pg_start_ctx->topology_output_file != NULL) - { - second_str = GNUNET_strdup (GNUNET_i2s (second)); - temp = - GNUNET_asprintf (&temp_str, "\t\"%s\" -- \"%s\"\n", - GNUNET_i2s (first), second_str); - GNUNET_free (second_str); - if (temp > 0) - GNUNET_DISK_file_write (pg_start_ctx->topology_output_file, temp_str, - temp); - GNUNET_free (temp_str); - } - } - else - { - pg_start_ctx->failed_connections++; -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Failed to connect peer %s to peer %s with error :\n%s\n", - first_daemon->shortname, second_daemon->shortname, emsg); - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Failed to connect peer %s to peer %s with error :\n%s\n", - first_daemon->shortname, second_daemon->shortname, emsg); -#endif - } - - GNUNET_assert (pg_start_ctx->connect_meter != NULL); - if (pg_start_ctx->connect_cb != NULL) - pg_start_ctx->connect_cb (pg_start_ctx->cls, first, second, distance, - first_cfg, second_cfg, first_daemon, - second_daemon, emsg); - if (GNUNET_YES != update_meter (pg_start_ctx->connect_meter)) - { - /* No finished yet */ - return; - } -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Created %d total connections, which is our target number! Starting next phase of testing.\n", - pg_start_ctx->total_connections); -#endif - -#if TIMING - total_duration = - GNUNET_TIME_absolute_get_difference (connect_start_time, - GNUNET_TIME_absolute_get - ()).rel_value / 1000; - failed_conns_per_sec_total = (double) failed_connections / total_duration; - conns_per_sec_total = (double) total_connections / total_duration; - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Overall connection info --- Total: %u, Total Failed %u/s\n", - total_connections, failed_connections); - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Overall connection info --- Total: %.2f/s, Total Failed %.2f/s\n", - conns_per_sec_total, failed_conns_per_sec_total); -#endif - - GNUNET_assert (pg_start_ctx->die_task != GNUNET_SCHEDULER_NO_TASK); - GNUNET_SCHEDULER_cancel (pg_start_ctx->die_task); - - /* Call final callback, signifying that the peer group has been started and connected */ - if (pg_start_ctx->peergroup_cb != NULL) - pg_start_ctx->peergroup_cb (pg_start_ctx->cls, NULL); - - if (pg_start_ctx->topology_output_file != NULL) - { - temp = GNUNET_asprintf (&temp_str, "}\n"); - if (temp > 0) - GNUNET_DISK_file_write (pg_start_ctx->topology_output_file, temp_str, - temp); - GNUNET_free (temp_str); - GNUNET_DISK_file_close (pg_start_ctx->topology_output_file); - } - GNUNET_free_non_null (pg_start_ctx->fail_reason); - if (NULL != pg_start_ctx->hostkey_meter) - free_meter(pg_start_ctx->hostkey_meter); - if (NULL != pg_start_ctx->peer_start_meter) - free_meter(pg_start_ctx->peer_start_meter); - if (NULL != pg_start_ctx->connect_meter) - free_meter(pg_start_ctx->connect_meter); - GNUNET_free (pg_start_ctx); -} - - -/** - * Callback called for each started daemon. - * - * @param cls Clause (PG Context). - * @param id PeerIdentidy of started daemon. - * @param cfg Configuration used by the daemon. - * @param d Handle for the daemon. - * @param emsg Error message, NULL on success. - */ -static void -internal_peers_started_callback (void *cls, - const struct GNUNET_PeerIdentity *id, - const struct GNUNET_CONFIGURATION_Handle *cfg, - struct GNUNET_TESTING_Daemon *d, - const char *emsg) -{ - struct PeerGroupStartupContext *pg_start_ctx = cls; - - if (emsg != NULL) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Failed to start daemon with error: `%s'\n", emsg); - return; - } - GNUNET_assert (id != NULL); - -#if VERBOSE > 1 - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Started daemon %llu out of %llu\n", - (pg_start_ctx->total - pg_start_ctx->peers_left) + 1, - pg_start_ctx->total); -#endif - - pg_start_ctx->peers_left--; - - if (NULL == pg_start_ctx->peer_start_meter) - { - /* Cancelled Ctrl-C or error */ - return; - } - if (GNUNET_YES == update_meter (pg_start_ctx->peer_start_meter)) - { -#if VERBOSE - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "All %d daemons started, now connecting peers!\n", - pg_start_ctx->total); -#endif - GNUNET_assert (pg_start_ctx->die_task != GNUNET_SCHEDULER_NO_TASK); - GNUNET_SCHEDULER_cancel (pg_start_ctx->die_task); - - pg_start_ctx->expected_connections = UINT_MAX; - // FIXME: why whould peers_left be != 0?? Or pg NULL? - if ((pg_start_ctx->pg != NULL) && (pg_start_ctx->peers_left == 0)) - { - pg_start_ctx->connect_start_time = GNUNET_TIME_absolute_get (); - pg_start_ctx->expected_connections = - GNUNET_TESTING_connect_topology (pg_start_ctx->pg, - pg_start_ctx->connect_topology, - pg_start_ctx->connect_topology_option, - pg_start_ctx->connect_topology_option_modifier, - pg_start_ctx->connect_timeout, - pg_start_ctx->connect_attempts, NULL, - NULL); - - pg_start_ctx->connect_meter = - create_meter (pg_start_ctx->expected_connections, "Peer connection ", - pg_start_ctx->verbose); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Have %d expected connections\n", - pg_start_ctx->expected_connections); - } - - if (pg_start_ctx->expected_connections == 0) - { - GNUNET_free_non_null (pg_start_ctx->fail_reason); - pg_start_ctx->fail_reason = - GNUNET_strdup ("from connect topology (bad return)"); - pg_start_ctx->die_task = - GNUNET_SCHEDULER_add_now (&end_badly, pg_start_ctx); - return; - } - - GNUNET_free_non_null (pg_start_ctx->fail_reason); - pg_start_ctx->fail_reason = - GNUNET_strdup ("from connect topology (timeout)"); - pg_start_ctx->die_task = - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_absolute_get_remaining - (pg_start_ctx->timeout), &end_badly, - pg_start_ctx); - } -} - -/** - * Callback indicating that the hostkey was created for a peer. - * - * @param cls NULL - * @param id the peer identity - * @param d the daemon handle (pretty useless at this point, remove?) - * @param emsg non-null on failure - */ -static void -internal_hostkey_callback (void *cls, const struct GNUNET_PeerIdentity *id, - struct GNUNET_TESTING_Daemon *d, const char *emsg) -{ - struct PeerGroupStartupContext *pg_start_ctx = cls; - unsigned int create_expected_connections; - - if (emsg != NULL) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Hostkey callback received error: %s\n", emsg); - } - -#if VERBOSE > 1 - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Hostkey (%d/%d) created for peer `%s'\n", - pg_start_ctx->total - pg_start_ctx->peers_left + 1, - pg_start_ctx->total, GNUNET_i2s (id)); -#endif - - pg_start_ctx->peers_left--; - if (GNUNET_YES == update_meter (pg_start_ctx->hostkey_meter)) - { - GNUNET_SCHEDULER_cancel (pg_start_ctx->die_task); - GNUNET_free_non_null (pg_start_ctx->fail_reason); - /* Set up task in case topology creation doesn't finish - * within a reasonable amount of time */ - pg_start_ctx->fail_reason = GNUNET_strdup ("from create_topology"); - pg_start_ctx->die_task = - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_absolute_get_remaining - (pg_start_ctx->timeout), &end_badly, - pg_start_ctx); - pg_start_ctx->peers_left = pg_start_ctx->total; /* Reset counter */ - create_expected_connections = - GNUNET_TESTING_create_topology (pg_start_ctx->pg, - pg_start_ctx->topology, - pg_start_ctx->restrict_topology, - pg_start_ctx->restrict_transports); - if (create_expected_connections > 0) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Topology set up, have %u expected connections, now starting peers!\n", - create_expected_connections); - GNUNET_TESTING_daemons_continue_startup (pg_start_ctx->pg); - } - else - { - GNUNET_SCHEDULER_cancel (pg_start_ctx->die_task); - GNUNET_free_non_null (pg_start_ctx->fail_reason); - pg_start_ctx->fail_reason = - GNUNET_strdup ("from create topology (bad return)"); - pg_start_ctx->die_task = - GNUNET_SCHEDULER_add_now (&end_badly, pg_start_ctx); - return; - } - - GNUNET_SCHEDULER_cancel (pg_start_ctx->die_task); - GNUNET_free_non_null (pg_start_ctx->fail_reason); - pg_start_ctx->fail_reason = - GNUNET_strdup ("from continue startup (timeout)"); - pg_start_ctx->die_task = - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_absolute_get_remaining - (pg_start_ctx->timeout), &end_badly, - pg_start_ctx); - } -} - - -/** - * Prototype of a callback function indicating that two peers - * are currently connected. - * - * @param cls closure - * @param first peer id for first daemon - * @param second peer id for the second daemon - * @param emsg error message (NULL on success) - */ -void -write_topology_cb (void *cls, const struct GNUNET_PeerIdentity *first, - const struct GNUNET_PeerIdentity *second, const char *emsg) -{ - struct TopologyOutputContext *topo_ctx; - int temp; - char *temp_str; - char *temp_pid2; - - topo_ctx = (struct TopologyOutputContext *) cls; - GNUNET_assert (topo_ctx->file != NULL); - if ((emsg == NULL) && (first != NULL) && (second != NULL)) - { - GNUNET_assert (first != NULL); - GNUNET_assert (second != NULL); - temp_pid2 = GNUNET_strdup (GNUNET_i2s (second)); - temp = - GNUNET_asprintf (&temp_str, "\t\"%s\" -- \"%s\"\n", GNUNET_i2s (first), - temp_pid2); - GNUNET_free (temp_pid2); - GNUNET_DISK_file_write (topo_ctx->file, temp_str, temp); - } - else if ((emsg == NULL) && (first == NULL) && (second == NULL)) - { - temp = GNUNET_asprintf (&temp_str, "}\n"); - GNUNET_DISK_file_write (topo_ctx->file, temp_str, temp); - GNUNET_DISK_file_close (topo_ctx->file); - topo_ctx->notify_cb (topo_ctx->notify_cb_cls, NULL); - GNUNET_free (topo_ctx); - } - else - { - temp = GNUNET_asprintf (&temp_str, "}\n"); - GNUNET_DISK_file_write (topo_ctx->file, temp_str, temp); - GNUNET_DISK_file_close (topo_ctx->file); - topo_ctx->notify_cb (topo_ctx->notify_cb_cls, emsg); - GNUNET_free (topo_ctx); - } -} - -/** - * Print current topology to a graphviz readable file. - * - * @param pg a currently running peergroup to print to file - * @param output_filename the file to write the topology to - * @param notify_cb callback to call upon completion or failure - * @param notify_cb_cls closure for notify_cb - * - */ -void -GNUNET_TESTING_peergroup_topology_to_file (struct GNUNET_TESTING_PeerGroup *pg, - const char *output_filename, - GNUNET_TESTING_NotifyCompletion - notify_cb, void *notify_cb_cls) -{ - struct TopologyOutputContext *topo_ctx; - int temp; - char *temp_str; - - topo_ctx = GNUNET_malloc (sizeof (struct TopologyOutputContext)); - - topo_ctx->notify_cb = notify_cb; - topo_ctx->notify_cb_cls = notify_cb_cls; - topo_ctx->file = - GNUNET_DISK_file_open (output_filename, - GNUNET_DISK_OPEN_READWRITE | - GNUNET_DISK_OPEN_CREATE, - GNUNET_DISK_PERM_USER_READ | - GNUNET_DISK_PERM_USER_WRITE); - if (topo_ctx->file == NULL) - { - notify_cb (notify_cb_cls, "Failed to open output file!"); - GNUNET_free (topo_ctx); - return; - } - - temp = GNUNET_asprintf (&temp_str, "strict graph G {\n"); - if (temp > 0) - GNUNET_DISK_file_write (topo_ctx->file, temp_str, temp); - GNUNET_free_non_null (temp_str); - GNUNET_TESTING_get_topology (pg, &write_topology_cb, topo_ctx); -} - -/** - * Start a peer group with a given number of peers. Notify - * on completion of peer startup and connection based on given - * topological constraints. Optionally notify on each - * established connection. - * - * @param cfg configuration template to use - * @param total number of daemons to start - * @param timeout total time allowed for peers to start - * @param connect_cb function to call each time two daemons are connected - * @param peergroup_cb function to call once all peers are up and connected - * @param peergroup_cls closure for peergroup callbacks - * @param hostnames linked list of host structs to use to start peers on - * (NULL to run on localhost only) - * - * @return NULL on error, otherwise handle to control peer group - */ -struct GNUNET_TESTING_PeerGroup * -GNUNET_TESTING_peergroup_start (const struct GNUNET_CONFIGURATION_Handle *cfg, - unsigned int total, - struct GNUNET_TIME_Relative timeout, - GNUNET_TESTING_NotifyConnection connect_cb, - GNUNET_TESTING_NotifyCompletion peergroup_cb, - void *peergroup_cls, - const struct GNUNET_TESTING_Host *hostnames) -{ - struct PeerGroupStartupContext *pg_start_ctx; - char *temp_str; - int temp; - struct GNUNET_TIME_Relative rtimeout; - - GNUNET_assert (total > 0); - GNUNET_assert (cfg != NULL); - - pg_start_ctx = GNUNET_malloc (sizeof (struct PeerGroupStartupContext)); - - if (GNUNET_OK != - GNUNET_CONFIGURATION_get_value_number (cfg, "testing", "connect_attempts", - &pg_start_ctx->connect_attempts)) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Must provide option %s:%s!\n", - "testing", "connect_attempts"); - GNUNET_free (pg_start_ctx); - return NULL; - } - - if (GNUNET_OK != - GNUNET_CONFIGURATION_get_value_time (cfg, "testing", "CONNECT_TIMEOUT", - &pg_start_ctx->connect_timeout)) - { - pg_start_ctx->connect_timeout = DEFAULT_CONNECT_TIMEOUT; - } - - if (GNUNET_OK != - GNUNET_CONFIGURATION_get_value_number (cfg, "testing", - "max_outstanding_connections", - &pg_start_ctx->max_concurrent_connections)) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Must provide option %s:%s!\n", - "testing", "max_outstanding_connections"); - GNUNET_free (pg_start_ctx); - return NULL; - } - - if (GNUNET_OK != - GNUNET_CONFIGURATION_get_value_number (cfg, "testing", - "max_concurrent_ssh", - &pg_start_ctx->max_concurrent_ssh)) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Must provide option %s:%s!\n", - "testing", "max_concurrent_ssh"); - GNUNET_free (pg_start_ctx); - return NULL; - } - - if (GNUNET_SYSERR == - (pg_start_ctx->verbose = - GNUNET_CONFIGURATION_get_value_yesno (cfg, "testing", - "use_progressbars"))) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Must provide option %s:%s!\n", - "testing", "use_progressbars"); - GNUNET_free (pg_start_ctx); - return NULL; - } - - if (GNUNET_OK != - GNUNET_CONFIGURATION_get_value_time (cfg, "testing", "PEERGROUP_TIMEOUT", - &rtimeout)) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Must provide option %s:%s!\n", - "testing", "PEERGROUP_TIMEOUT"); - GNUNET_free (pg_start_ctx); - return NULL; - } - pg_start_ctx->timeout = GNUNET_TIME_relative_to_absolute (rtimeout); - - - /* Read topology related options from the configuration file */ - temp_str = NULL; - if ((GNUNET_YES == - GNUNET_CONFIGURATION_get_value_string (cfg, "testing", "topology", - &temp_str)) && - (GNUNET_NO == - GNUNET_TESTING_topology_get (&pg_start_ctx->topology, temp_str))) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Invalid topology `%s' given for section %s option %s\n", - temp_str, "TESTING", "TOPOLOGY"); - pg_start_ctx->topology = GNUNET_TESTING_TOPOLOGY_CLIQUE; /* Defaults to NONE, so set better default here */ - } - GNUNET_free_non_null (temp_str); - - if (GNUNET_YES == - GNUNET_CONFIGURATION_get_value_string (cfg, "testing", - "topology_output_file", &temp_str)) - { - pg_start_ctx->topology_output_file = - GNUNET_DISK_file_open (temp_str, - GNUNET_DISK_OPEN_READWRITE | - GNUNET_DISK_OPEN_CREATE, - GNUNET_DISK_PERM_USER_READ | - GNUNET_DISK_PERM_USER_WRITE); - if (pg_start_ctx->topology_output_file != NULL) - { - GNUNET_free (temp_str); - temp = GNUNET_asprintf (&temp_str, "strict graph G {\n"); - if (temp > 0) - GNUNET_DISK_file_write (pg_start_ctx->topology_output_file, temp_str, - temp); - } - GNUNET_free (temp_str); - } - - if (GNUNET_OK != - GNUNET_CONFIGURATION_get_value_string (cfg, "testing", "percentage", - &temp_str)) - pg_start_ctx->topology_percentage = 0.5; - else - { - pg_start_ctx->topology_percentage = atof (temp_str); - GNUNET_free (temp_str); - } - - if (GNUNET_OK != - GNUNET_CONFIGURATION_get_value_string (cfg, "testing", "probability", - &temp_str)) - pg_start_ctx->topology_probability = 0.5; - else - { - pg_start_ctx->topology_probability = atof (temp_str); - GNUNET_free (temp_str); - } - - if ((GNUNET_YES == - GNUNET_CONFIGURATION_get_value_string (cfg, "testing", - "connect_topology", &temp_str)) && - (GNUNET_NO == - GNUNET_TESTING_topology_get (&pg_start_ctx->connect_topology, temp_str))) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Invalid connect topology `%s' given for section %s option %s\n", - temp_str, "TESTING", "CONNECT_TOPOLOGY"); - } - GNUNET_free_non_null (temp_str); - - if ((GNUNET_YES == - GNUNET_CONFIGURATION_get_value_string (cfg, "testing", - "connect_topology_option", - &temp_str)) && - (GNUNET_NO == - GNUNET_TESTING_topology_option_get - (&pg_start_ctx->connect_topology_option, temp_str))) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Invalid connect topology option `%s' given for section %s option %s\n", - temp_str, "TESTING", "CONNECT_TOPOLOGY_OPTION"); - pg_start_ctx->connect_topology_option = GNUNET_TESTING_TOPOLOGY_OPTION_ALL; /* Defaults to NONE, set to ALL */ - } - GNUNET_free_non_null (temp_str); - - if (GNUNET_YES == - GNUNET_CONFIGURATION_get_value_string (cfg, "testing", - "connect_topology_option_modifier", - &temp_str)) - { - if (SSCANF - (temp_str, "%lf", &pg_start_ctx->connect_topology_option_modifier) != 1) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - _ - ("Invalid value `%s' for option `%s' in section `%s': expected float\n"), - temp_str, "connect_topology_option_modifier", "TESTING"); - GNUNET_free (temp_str); - GNUNET_free (pg_start_ctx); - return NULL; - } - GNUNET_free (temp_str); - } - - if (GNUNET_YES != - GNUNET_CONFIGURATION_get_value_string (cfg, "testing", - "blacklist_transports", - &pg_start_ctx->restrict_transports)) - pg_start_ctx->restrict_transports = NULL; - - pg_start_ctx->restrict_topology = GNUNET_TESTING_TOPOLOGY_NONE; - if ((GNUNET_YES == - GNUNET_CONFIGURATION_get_value_string (cfg, "testing", - "blacklist_topology", &temp_str)) - && (GNUNET_NO == - GNUNET_TESTING_topology_get (&pg_start_ctx->restrict_topology, - temp_str))) - { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - "Invalid topology `%s' given for section %s option %s\n", - temp_str, "TESTING", "BLACKLIST_TOPOLOGY"); - } - - GNUNET_free_non_null (temp_str); - - pg_start_ctx->cfg = cfg; - pg_start_ctx->total = total; - pg_start_ctx->peers_left = total; - pg_start_ctx->connect_cb = connect_cb; - pg_start_ctx->peergroup_cb = peergroup_cb; - pg_start_ctx->cls = peergroup_cls; - pg_start_ctx->hostnames = hostnames; - pg_start_ctx->hostkey_meter = - create_meter (pg_start_ctx->peers_left, "Hostkeys created ", - pg_start_ctx->verbose); - pg_start_ctx->peer_start_meter = - create_meter (pg_start_ctx->peers_left, "Peers started ", - pg_start_ctx->verbose); - /* Make compilers happy */ - reset_meter (pg_start_ctx->peer_start_meter); - pg_start_ctx->fail_reason = - GNUNET_strdup - ("didn't generate all hostkeys within allowed startup time!"); - pg_start_ctx->die_task = - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_absolute_get_remaining - (pg_start_ctx->timeout), &end_badly, - pg_start_ctx); - - pg_start_ctx->pg = - GNUNET_TESTING_daemons_start (pg_start_ctx->cfg, pg_start_ctx->peers_left, - pg_start_ctx->max_concurrent_connections, - pg_start_ctx->max_concurrent_ssh, - GNUNET_TIME_absolute_get_remaining - (pg_start_ctx->timeout), - &internal_hostkey_callback, pg_start_ctx, - &internal_peers_started_callback, - pg_start_ctx, &internal_topology_callback, - pg_start_ctx, pg_start_ctx->hostnames); - - return pg_start_ctx->pg; -} - -/* end of testing_peergroup.c */ diff --git a/src/topology/Makefile.am b/src/topology/Makefile.am index 261be86..91a5384 100644 --- a/src/topology/Makefile.am +++ b/src/topology/Makefile.am @@ -6,11 +6,13 @@ endif pkgcfgdir= $(pkgdatadir)/config.d/ +libexecdir= $(pkglibdir)/libexec/ + dist_pkgcfg_DATA = \ topology.conf -bin_PROGRAMS = \ +libexec_PROGRAMS = \ gnunet-daemon-topology gnunet_daemon_topology_SOURCES = \ @@ -36,7 +38,7 @@ endif test_gnunet_daemon_topology_SOURCES = \ test_gnunet_daemon_topology.c test_gnunet_daemon_topology_LDADD = \ - $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la \ $(top_builddir)/src/util/libgnunetutil.la EXTRA_DIST = \ diff --git a/src/topology/Makefile.in b/src/topology/Makefile.in index 7cde7ff..2707053 100644 --- a/src/topology/Makefile.in +++ b/src/topology/Makefile.in @@ -1,9 +1,9 @@ -# Makefile.in generated by automake 1.11.1 from Makefile.am. +# Makefile.in generated by automake 1.11.6 from Makefile.am. # @configure_input@ # Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, -# 2003, 2004, 2005, 2006, 2007, 2008, 2009 Free Software Foundation, -# Inc. +# 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Free Software +# Foundation, Inc. # This Makefile.in is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. @@ -17,6 +17,23 @@ VPATH = @srcdir@ +am__make_dryrun = \ + { \ + am__dry=no; \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + echo 'am--echo: ; @echo "AM" OK' | $(MAKE) -f - 2>/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } pkgdatadir = $(datadir)/@PACKAGE@ pkgincludedir = $(includedir)/@PACKAGE@ pkglibdir = $(libdir)/@PACKAGE@ @@ -36,7 +53,7 @@ POST_UNINSTALL = : build_triplet = @build@ host_triplet = @host@ target_triplet = @target@ -bin_PROGRAMS = gnunet-daemon-topology$(EXEEXT) +libexec_PROGRAMS = gnunet-daemon-topology$(EXEEXT) check_PROGRAMS = test_gnunet_daemon_topology$(EXEEXT) subdir = src/topology DIST_COMMON = $(dist_pkgcfg_DATA) $(srcdir)/Makefile.am \ @@ -44,14 +61,15 @@ DIST_COMMON = $(dist_pkgcfg_DATA) $(srcdir)/Makefile.am \ ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 am__aclocal_m4_deps = $(top_srcdir)/m4/absolute-header.m4 \ $(top_srcdir)/m4/align.m4 $(top_srcdir)/m4/argz.m4 \ - $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/iconv.m4 \ - $(top_srcdir)/m4/lib-ld.m4 $(top_srcdir)/m4/lib-link.m4 \ - $(top_srcdir)/m4/lib-prefix.m4 $(top_srcdir)/m4/libcurl.m4 \ - $(top_srcdir)/m4/libgcrypt.m4 $(top_srcdir)/m4/libtool.m4 \ - $(top_srcdir)/m4/libunistring.m4 $(top_srcdir)/m4/ltdl.m4 \ - $(top_srcdir)/m4/ltoptions.m4 $(top_srcdir)/m4/ltsugar.m4 \ - $(top_srcdir)/m4/ltversion.m4 $(top_srcdir)/m4/lt~obsolete.m4 \ - $(top_srcdir)/m4/nls.m4 $(top_srcdir)/m4/po.m4 \ + $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/glib-2.0.m4 \ + $(top_srcdir)/m4/iconv.m4 $(top_srcdir)/m4/lib-ld.m4 \ + $(top_srcdir)/m4/lib-link.m4 $(top_srcdir)/m4/lib-prefix.m4 \ + $(top_srcdir)/m4/libcurl.m4 $(top_srcdir)/m4/libgcrypt.m4 \ + $(top_srcdir)/m4/libtool.m4 $(top_srcdir)/m4/libunistring.m4 \ + $(top_srcdir)/m4/ltdl.m4 $(top_srcdir)/m4/ltoptions.m4 \ + $(top_srcdir)/m4/ltsugar.m4 $(top_srcdir)/m4/ltversion.m4 \ + $(top_srcdir)/m4/lt~obsolete.m4 $(top_srcdir)/m4/nls.m4 \ + $(top_srcdir)/m4/pkg.m4 $(top_srcdir)/m4/po.m4 \ $(top_srcdir)/m4/progtest.m4 $(top_srcdir)/acinclude.m4 \ $(top_srcdir)/configure.ac am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ @@ -60,8 +78,8 @@ mkinstalldirs = $(install_sh) -d CONFIG_HEADER = $(top_builddir)/gnunet_config.h CONFIG_CLEAN_FILES = CONFIG_CLEAN_VPATH_FILES = -am__installdirs = "$(DESTDIR)$(bindir)" "$(DESTDIR)$(pkgcfgdir)" -PROGRAMS = $(bin_PROGRAMS) +am__installdirs = "$(DESTDIR)$(libexecdir)" "$(DESTDIR)$(pkgcfgdir)" +PROGRAMS = $(libexec_PROGRAMS) am_gnunet_daemon_topology_OBJECTS = gnunet-daemon-topology.$(OBJEXT) gnunet_daemon_topology_OBJECTS = $(am_gnunet_daemon_topology_OBJECTS) am__DEPENDENCIES_1 = @@ -73,15 +91,15 @@ gnunet_daemon_topology_DEPENDENCIES = \ $(top_builddir)/src/hello/libgnunethello.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(am__DEPENDENCIES_1) -AM_V_lt = $(am__v_lt_$(V)) -am__v_lt_ = $(am__v_lt_$(AM_DEFAULT_VERBOSITY)) +AM_V_lt = $(am__v_lt_@AM_V@) +am__v_lt_ = $(am__v_lt_@AM_DEFAULT_V@) am__v_lt_0 = --silent am_test_gnunet_daemon_topology_OBJECTS = \ test_gnunet_daemon_topology.$(OBJEXT) test_gnunet_daemon_topology_OBJECTS = \ $(am_test_gnunet_daemon_topology_OBJECTS) test_gnunet_daemon_topology_DEPENDENCIES = \ - $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la \ $(top_builddir)/src/util/libgnunetutil.la DEFAULT_INCLUDES = -I.@am__isrc@ -I$(top_builddir) depcomp = $(SHELL) $(top_srcdir)/depcomp @@ -93,26 +111,31 @@ LTCOMPILE = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) \ $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) \ $(AM_CFLAGS) $(CFLAGS) -AM_V_CC = $(am__v_CC_$(V)) -am__v_CC_ = $(am__v_CC_$(AM_DEFAULT_VERBOSITY)) +AM_V_CC = $(am__v_CC_@AM_V@) +am__v_CC_ = $(am__v_CC_@AM_DEFAULT_V@) am__v_CC_0 = @echo " CC " $@; -AM_V_at = $(am__v_at_$(V)) -am__v_at_ = $(am__v_at_$(AM_DEFAULT_VERBOSITY)) +AM_V_at = $(am__v_at_@AM_V@) +am__v_at_ = $(am__v_at_@AM_DEFAULT_V@) am__v_at_0 = @ CCLD = $(CC) LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ $(AM_LDFLAGS) $(LDFLAGS) -o $@ -AM_V_CCLD = $(am__v_CCLD_$(V)) -am__v_CCLD_ = $(am__v_CCLD_$(AM_DEFAULT_VERBOSITY)) +AM_V_CCLD = $(am__v_CCLD_@AM_V@) +am__v_CCLD_ = $(am__v_CCLD_@AM_DEFAULT_V@) am__v_CCLD_0 = @echo " CCLD " $@; -AM_V_GEN = $(am__v_GEN_$(V)) -am__v_GEN_ = $(am__v_GEN_$(AM_DEFAULT_VERBOSITY)) +AM_V_GEN = $(am__v_GEN_@AM_V@) +am__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@) am__v_GEN_0 = @echo " GEN " $@; SOURCES = $(gnunet_daemon_topology_SOURCES) \ $(test_gnunet_daemon_topology_SOURCES) DIST_SOURCES = $(gnunet_daemon_topology_SOURCES) \ $(test_gnunet_daemon_topology_SOURCES) +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac am__vpath_adj_setup = srcdirstrip=`echo "$(srcdir)" | sed 's|.|.|g'`; am__vpath_adj = case $$p in \ $(srcdir)/*) f=`echo "$$p" | sed "s|^$$srcdirstrip/||"`;; \ @@ -134,6 +157,12 @@ am__nobase_list = $(am__nobase_strip_setup); \ am__base_list = \ sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \ sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g' +am__uninstall_files_from_dir = { \ + test -z "$$files" \ + || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \ + || { echo " ( cd '$$dir' && rm -f" $$files ")"; \ + $(am__cd) "$$dir" && rm -f $$files; }; \ + } DATA = $(dist_pkgcfg_DATA) ETAGS = etags CTAGS = ctags @@ -175,6 +204,10 @@ EXEEXT = @EXEEXT@ EXT_LIBS = @EXT_LIBS@ EXT_LIB_PATH = @EXT_LIB_PATH@ FGREP = @FGREP@ +GLIB_CFLAGS = @GLIB_CFLAGS@ +GLIB_GENMARSHAL = @GLIB_GENMARSHAL@ +GLIB_LIBS = @GLIB_LIBS@ +GLIB_MKENUMS = @GLIB_MKENUMS@ GMSGFMT = @GMSGFMT@ GMSGFMT_015 = @GMSGFMT_015@ GNUNETDNS_GROUP = @GNUNETDNS_GROUP@ @@ -185,6 +218,7 @@ GN_LIBINTL = @GN_LIBINTL@ GN_LIB_LDFLAGS = @GN_LIB_LDFLAGS@ GN_PLUGIN_LDFLAGS = @GN_PLUGIN_LDFLAGS@ GN_USER_HOME_DIR = @GN_USER_HOME_DIR@ +GOBJECT_QUERY = @GOBJECT_QUERY@ GREP = @GREP@ HAVE_LIBUNISTRING = @HAVE_LIBUNISTRING@ INCLTDL = @INCLTDL@ @@ -207,6 +241,8 @@ LIBCURL_CPPFLAGS = @LIBCURL_CPPFLAGS@ LIBGCRYPT_CFLAGS = @LIBGCRYPT_CFLAGS@ LIBGCRYPT_CONFIG = @LIBGCRYPT_CONFIG@ LIBGCRYPT_LIBS = @LIBGCRYPT_LIBS@ +LIBGTOP_CFLAGS = @LIBGTOP_CFLAGS@ +LIBGTOP_LIBS = @LIBGTOP_LIBS@ LIBICONV = @LIBICONV@ LIBINTL = @LIBINTL@ LIBLTDL = @LIBLTDL@ @@ -228,6 +264,7 @@ LT_CONFIG_H = @LT_CONFIG_H@ LT_DLLOADERS = @LT_DLLOADERS@ LT_DLPREOPEN = @LT_DLPREOPEN@ MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ MKDIR_P = @MKDIR_P@ MONKEYPREFIX = @MONKEYPREFIX@ MSGFMT = @MSGFMT@ @@ -237,6 +274,7 @@ MYSQL_CPPFLAGS = @MYSQL_CPPFLAGS@ MYSQL_LDFLAGS = @MYSQL_LDFLAGS@ NM = @NM@ NMEDIT = @NMEDIT@ +NSS_DIR = @NSS_DIR@ OBJC = @OBJC@ OBJCDEPMODE = @OBJCDEPMODE@ OBJCFLAGS = @OBJCFLAGS@ @@ -252,6 +290,7 @@ PACKAGE_TARNAME = @PACKAGE_TARNAME@ PACKAGE_URL = @PACKAGE_URL@ PACKAGE_VERSION = @PACKAGE_VERSION@ PATH_SEPARATOR = @PATH_SEPARATOR@ +PKG_CONFIG = @PKG_CONFIG@ POSTGRES_CPPFLAGS = @POSTGRES_CPPFLAGS@ POSTGRES_LDFLAGS = @POSTGRES_LDFLAGS@ POSUB = @POSUB@ @@ -283,6 +322,7 @@ abs_builddir = @abs_builddir@ abs_srcdir = @abs_srcdir@ abs_top_builddir = @abs_top_builddir@ abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ ac_ct_CC = @ac_ct_CC@ ac_ct_CXX = @ac_ct_CXX@ ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ @@ -305,6 +345,7 @@ datarootdir = @datarootdir@ docdir = @docdir@ dvidir = @dvidir@ exec_prefix = @exec_prefix@ +gitcommand = @gitcommand@ host = @host@ host_alias = @host_alias@ host_cpu = @host_cpu@ @@ -315,10 +356,9 @@ includedir = @includedir@ infodir = @infodir@ install_sh = @install_sh@ libdir = @libdir@ -libexecdir = @libexecdir@ +libexecdir = $(pkglibdir)/libexec/ localedir = @localedir@ localstatedir = @localstatedir@ -lt_ECHO = @lt_ECHO@ ltdl_LIBOBJS = @ltdl_LIBOBJS@ ltdl_LTLIBOBJS = @ltdl_LTLIBOBJS@ mandir = @mandir@ @@ -336,6 +376,7 @@ sbindir = @sbindir@ sharedstatedir = @sharedstatedir@ srcdir = @srcdir@ subdirs = @subdirs@ +svnversioncommand = @svnversioncommand@ sys_symbol_underscore = @sys_symbol_underscore@ sysconfdir = @sysconfdir@ target = @target@ @@ -369,7 +410,7 @@ test_gnunet_daemon_topology_SOURCES = \ test_gnunet_daemon_topology.c test_gnunet_daemon_topology_LDADD = \ - $(top_builddir)/src/testing/libgnunettesting.la \ + $(top_builddir)/src/testbed/libgnunettestbed.la \ $(top_builddir)/src/util/libgnunetutil.la EXTRA_DIST = \ @@ -409,10 +450,22 @@ $(top_srcdir)/configure: $(am__configure_deps) $(ACLOCAL_M4): $(am__aclocal_m4_deps) cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh $(am__aclocal_m4_deps): -install-binPROGRAMS: $(bin_PROGRAMS) + +clean-checkPROGRAMS: + @list='$(check_PROGRAMS)'; test -n "$$list" || exit 0; \ + echo " rm -f" $$list; \ + rm -f $$list || exit $$?; \ + test -n "$(EXEEXT)" || exit 0; \ + list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ + echo " rm -f" $$list; \ + rm -f $$list +install-libexecPROGRAMS: $(libexec_PROGRAMS) @$(NORMAL_INSTALL) - test -z "$(bindir)" || $(MKDIR_P) "$(DESTDIR)$(bindir)" - @list='$(bin_PROGRAMS)'; test -n "$(bindir)" || list=; \ + @list='$(libexec_PROGRAMS)'; test -n "$(libexecdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(libexecdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libexecdir)" || exit 1; \ + fi; \ for p in $$list; do echo "$$p $$p"; done | \ sed 's/$(EXEEXT)$$//' | \ while read p p1; do if test -f $$p || test -f $$p1; \ @@ -429,42 +482,33 @@ install-binPROGRAMS: $(bin_PROGRAMS) while read type dir files; do \ if test "$$dir" = .; then dir=; else dir=/$$dir; fi; \ test -z "$$files" || { \ - echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files '$(DESTDIR)$(bindir)$$dir'"; \ - $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files "$(DESTDIR)$(bindir)$$dir" || exit $$?; \ + echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files '$(DESTDIR)$(libexecdir)$$dir'"; \ + $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files "$(DESTDIR)$(libexecdir)$$dir" || exit $$?; \ } \ ; done -uninstall-binPROGRAMS: +uninstall-libexecPROGRAMS: @$(NORMAL_UNINSTALL) - @list='$(bin_PROGRAMS)'; test -n "$(bindir)" || list=; \ + @list='$(libexec_PROGRAMS)'; test -n "$(libexecdir)" || list=; \ files=`for p in $$list; do echo "$$p"; done | \ sed -e 'h;s,^.*/,,;s/$(EXEEXT)$$//;$(transform)' \ -e 's/$$/$(EXEEXT)/' `; \ test -n "$$list" || exit 0; \ - echo " ( cd '$(DESTDIR)$(bindir)' && rm -f" $$files ")"; \ - cd "$(DESTDIR)$(bindir)" && rm -f $$files + echo " ( cd '$(DESTDIR)$(libexecdir)' && rm -f" $$files ")"; \ + cd "$(DESTDIR)$(libexecdir)" && rm -f $$files -clean-binPROGRAMS: - @list='$(bin_PROGRAMS)'; test -n "$$list" || exit 0; \ +clean-libexecPROGRAMS: + @list='$(libexec_PROGRAMS)'; test -n "$$list" || exit 0; \ echo " rm -f" $$list; \ rm -f $$list || exit $$?; \ test -n "$(EXEEXT)" || exit 0; \ list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ echo " rm -f" $$list; \ rm -f $$list - -clean-checkPROGRAMS: - @list='$(check_PROGRAMS)'; test -n "$$list" || exit 0; \ - echo " rm -f" $$list; \ - rm -f $$list || exit $$?; \ - test -n "$(EXEEXT)" || exit 0; \ - list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ - echo " rm -f" $$list; \ - rm -f $$list -gnunet-daemon-topology$(EXEEXT): $(gnunet_daemon_topology_OBJECTS) $(gnunet_daemon_topology_DEPENDENCIES) +gnunet-daemon-topology$(EXEEXT): $(gnunet_daemon_topology_OBJECTS) $(gnunet_daemon_topology_DEPENDENCIES) $(EXTRA_gnunet_daemon_topology_DEPENDENCIES) @rm -f gnunet-daemon-topology$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_daemon_topology_OBJECTS) $(gnunet_daemon_topology_LDADD) $(LIBS) -test_gnunet_daemon_topology$(EXEEXT): $(test_gnunet_daemon_topology_OBJECTS) $(test_gnunet_daemon_topology_DEPENDENCIES) +test_gnunet_daemon_topology$(EXEEXT): $(test_gnunet_daemon_topology_OBJECTS) $(test_gnunet_daemon_topology_DEPENDENCIES) $(EXTRA_test_gnunet_daemon_topology_DEPENDENCIES) @rm -f test_gnunet_daemon_topology$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_gnunet_daemon_topology_OBJECTS) $(test_gnunet_daemon_topology_LDADD) $(LIBS) @@ -480,26 +524,23 @@ distclean-compile: .c.o: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c $< .c.obj: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'` @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c `$(CYGPATH_W) '$<'` +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c `$(CYGPATH_W) '$<'` .c.lo: @am__fastdepCC_TRUE@ $(AM_V_CC)$(LTCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LTCOMPILE) -c -o $@ $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LTCOMPILE) -c -o $@ $< mostlyclean-libtool: -rm -f *.lo @@ -508,8 +549,11 @@ clean-libtool: -rm -rf .libs _libs install-dist_pkgcfgDATA: $(dist_pkgcfg_DATA) @$(NORMAL_INSTALL) - test -z "$(pkgcfgdir)" || $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" @list='$(dist_pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(pkgcfgdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" || exit 1; \ + fi; \ for p in $$list; do \ if test -f "$$p"; then d=; else d="$(srcdir)/"; fi; \ echo "$$d$$p"; \ @@ -523,9 +567,7 @@ uninstall-dist_pkgcfgDATA: @$(NORMAL_UNINSTALL) @list='$(dist_pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ files=`for p in $$list; do echo $$p; done | sed -e 's|^.*/||'`; \ - test -n "$$files" || exit 0; \ - echo " ( cd '$(DESTDIR)$(pkgcfgdir)' && rm -f" $$files ")"; \ - cd "$(DESTDIR)$(pkgcfgdir)" && rm -f $$files + dir='$(DESTDIR)$(pkgcfgdir)'; $(am__uninstall_files_from_dir) ID: $(HEADERS) $(SOURCES) $(LISP) $(TAGS_FILES) list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ @@ -660,14 +702,15 @@ check-TESTS: $(TESTS) fi; \ dashes=`echo "$$dashes" | sed s/./=/g`; \ if test "$$failed" -eq 0; then \ - echo "$$grn$$dashes"; \ + col="$$grn"; \ else \ - echo "$$red$$dashes"; \ + col="$$red"; \ fi; \ - echo "$$banner"; \ - test -z "$$skipped" || echo "$$skipped"; \ - test -z "$$report" || echo "$$report"; \ - echo "$$dashes$$std"; \ + echo "$${col}$$dashes$${std}"; \ + echo "$${col}$$banner$${std}"; \ + test -z "$$skipped" || echo "$${col}$$skipped$${std}"; \ + test -z "$$report" || echo "$${col}$$report$${std}"; \ + echo "$${col}$$dashes$${std}"; \ test "$$failed" -eq 0; \ else :; fi @@ -707,7 +750,7 @@ check-am: all-am check: check-am all-am: Makefile $(PROGRAMS) $(DATA) installdirs: - for dir in "$(DESTDIR)$(bindir)" "$(DESTDIR)$(pkgcfgdir)"; do \ + for dir in "$(DESTDIR)$(libexecdir)" "$(DESTDIR)$(pkgcfgdir)"; do \ test -z "$$dir" || $(MKDIR_P) "$$dir"; \ done install: install-am @@ -720,10 +763,15 @@ install-am: all-am installcheck: installcheck-am install-strip: - $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ - install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ - `test -z '$(STRIP)' || \ - echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi mostlyclean-generic: clean-generic: @@ -737,7 +785,7 @@ maintainer-clean-generic: @echo "it deletes files that may require special tools to rebuild." clean: clean-am -clean-am: clean-binPROGRAMS clean-checkPROGRAMS clean-generic \ +clean-am: clean-checkPROGRAMS clean-generic clean-libexecPROGRAMS \ clean-libtool mostlyclean-am distclean: distclean-am @@ -764,7 +812,7 @@ install-dvi: install-dvi-am install-dvi-am: -install-exec-am: install-binPROGRAMS +install-exec-am: install-libexecPROGRAMS install-html: install-html-am @@ -804,25 +852,25 @@ ps: ps-am ps-am: -uninstall-am: uninstall-binPROGRAMS uninstall-dist_pkgcfgDATA +uninstall-am: uninstall-dist_pkgcfgDATA uninstall-libexecPROGRAMS .MAKE: check-am install-am install-strip .PHONY: CTAGS GTAGS all all-am check check-TESTS check-am clean \ - clean-binPROGRAMS clean-checkPROGRAMS clean-generic \ + clean-checkPROGRAMS clean-generic clean-libexecPROGRAMS \ clean-libtool ctags distclean distclean-compile \ distclean-generic distclean-libtool distclean-tags distdir dvi \ dvi-am html html-am info info-am install install-am \ - install-binPROGRAMS install-data install-data-am \ - install-dist_pkgcfgDATA install-dvi install-dvi-am \ - install-exec install-exec-am install-html install-html-am \ - install-info install-info-am install-man install-pdf \ - install-pdf-am install-ps install-ps-am install-strip \ - installcheck installcheck-am installdirs maintainer-clean \ + install-data install-data-am install-dist_pkgcfgDATA \ + install-dvi install-dvi-am install-exec install-exec-am \ + install-html install-html-am install-info install-info-am \ + install-libexecPROGRAMS install-man install-pdf install-pdf-am \ + install-ps install-ps-am install-strip installcheck \ + installcheck-am installdirs maintainer-clean \ maintainer-clean-generic mostlyclean mostlyclean-compile \ mostlyclean-generic mostlyclean-libtool pdf pdf-am ps ps-am \ - tags uninstall uninstall-am uninstall-binPROGRAMS \ - uninstall-dist_pkgcfgDATA + tags uninstall uninstall-am uninstall-dist_pkgcfgDATA \ + uninstall-libexecPROGRAMS # Tell versions [3.59,3.63) of GNU make to not export all variables. diff --git a/src/topology/gnunet-daemon-topology.c b/src/topology/gnunet-daemon-topology.c index 382c9f3..499f7f8 100644 --- a/src/topology/gnunet-daemon-topology.c +++ b/src/topology/gnunet-daemon-topology.c @@ -233,11 +233,6 @@ static unsigned int target_connection_count; */ static unsigned int friend_count; -/** - * Should the topology daemon try to establish connections? - */ -static int autoconnect; - /** * Function that decides if a connection is acceptable or not. @@ -316,7 +311,7 @@ is_connection_allowed (struct Peer *peer) * @return GNUNET_YES (always: continue to iterate) */ static int -free_peer (void *cls, const GNUNET_HashCode * pid, void *value) +free_peer (void *cls, const struct GNUNET_HashCode * pid, void *value) { struct Peer *pos = value; @@ -391,7 +386,7 @@ attempt_connect (struct Peer *pos) gettext_noop ("# connect requests issued to transport"), 1, GNUNET_NO); - GNUNET_TRANSPORT_try_connect (transport, &pos->pid); + GNUNET_TRANSPORT_try_connect (transport, &pos->pid, NULL, NULL); /*FIXME TRY_CONNECT change */ } @@ -573,7 +568,7 @@ struct FindAdvHelloContext * @return GNUNET_YES (continue iteration) */ static int -find_advertisable_hello (void *cls, const GNUNET_HashCode * pid, void *value) +find_advertisable_hello (void *cls, const struct GNUNET_HashCode * pid, void *value) { struct FindAdvHelloContext *fah = cls; struct Peer *pos = value; @@ -659,7 +654,7 @@ schedule_next_hello (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) * @return GNUNET_YES (always) */ static int -reschedule_hellos (void *cls, const GNUNET_HashCode * pid, void *value) +reschedule_hellos (void *cls, const struct GNUNET_HashCode * pid, void *value) { struct Peer *peer = value; struct Peer *skip = cls; @@ -743,7 +738,7 @@ connect_notify (void *cls, const struct GNUNET_PeerIdentity *peer, * @return GNUNET_YES (continue to iterate) */ static int -try_add_peers (void *cls, const GNUNET_HashCode * pid, void *value) +try_add_peers (void *cls, const struct GNUNET_HashCode * pid, void *value) { struct Peer *pos = value; @@ -1022,15 +1017,15 @@ read_friends_file (const struct GNUNET_CONFIGURATION_Handle *cfg) if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_filename (cfg, "TOPOLOGY", "FRIENDS", &fn)) { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - _("Option `%s' in section `%s' not specified!\n"), "FRIENDS", - "TOPOLOGY"); + GNUNET_log_config_missing (GNUNET_ERROR_TYPE_ERROR, + "topology", "FRIENDS"); return; } - if (GNUNET_OK != GNUNET_DISK_file_test (fn)) - GNUNET_DISK_fn_write (fn, NULL, 0, - GNUNET_DISK_PERM_USER_READ | - GNUNET_DISK_PERM_USER_WRITE); + if ( (GNUNET_OK != GNUNET_DISK_file_test (fn)) && + (GNUNET_OK != GNUNET_DISK_fn_write (fn, NULL, 0, + GNUNET_DISK_PERM_USER_READ | + GNUNET_DISK_PERM_USER_WRITE)) ) + GNUNET_log_strerror_file (GNUNET_ERROR_TYPE_WARNING, "write", fn); if (GNUNET_OK != GNUNET_DISK_file_size (fn, &fsize, GNUNET_NO, GNUNET_YES)) { @@ -1293,8 +1288,6 @@ run (void *cls, char *const *args, const char *cfgfile, cfg = c; stats = GNUNET_STATISTICS_create ("topology", cfg); - autoconnect = - GNUNET_CONFIGURATION_get_value_yesno (cfg, "TOPOLOGY", "AUTOCONNECT"); friends_only = GNUNET_CONFIGURATION_get_value_yesno (cfg, "TOPOLOGY", "FRIENDS-ONLY"); if (GNUNET_OK != @@ -1307,19 +1300,18 @@ run (void *cls, char *const *args, const char *cfgfile, "TARGET-CONNECTION-COUNT", &opt)) opt = 16; target_connection_count = (unsigned int) opt; - peers = GNUNET_CONTAINER_multihashmap_create (target_connection_count * 2); + peers = GNUNET_CONTAINER_multihashmap_create (target_connection_count * 2, GNUNET_NO); if ((friends_only == GNUNET_YES) || (minimum_friend_count > 0)) read_friends_file (cfg); GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Topology would like %u connections with at least %u friends (%s)\n", - target_connection_count, minimum_friend_count, - autoconnect ? "autoconnect enabled" : "autoconnect disabled"); + "Topology would like %u connections with at least %u friends\n", + target_connection_count, minimum_friend_count); if ((friend_count < minimum_friend_count) && (blacklist == NULL)) blacklist = GNUNET_TRANSPORT_blacklist (cfg, &blacklist_check, NULL); transport = GNUNET_TRANSPORT_connect (cfg, NULL, NULL, NULL, NULL, NULL); handle = - GNUNET_CORE_connect (cfg, 1, NULL, &core_init, &connect_notify, + GNUNET_CORE_connect (cfg, NULL, &core_init, &connect_notify, &disconnect_notify, NULL, GNUNET_NO, NULL, GNUNET_NO, handlers); GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, &cleaning_task, @@ -1356,13 +1348,32 @@ main (int argc, char *const *argv) }; int ret; + if (GNUNET_OK != GNUNET_STRINGS_get_utf8_args (argc, argv, &argc, &argv)) + return 2; + ret = (GNUNET_OK == GNUNET_PROGRAM_run (argc, argv, "gnunet-daemon-topology", _ ("GNUnet topology control (maintaining P2P mesh and F2F constraints)"), options, &run, NULL)) ? 0 : 1; + GNUNET_free ((void*) argv); return ret; } + +#ifdef LINUX +#include + +/** + * MINIMIZE heap size (way below 128k) since this process doesn't need much. + */ +void __attribute__ ((constructor)) GNUNET_ARM_memory_init () +{ + mallopt (M_TRIM_THRESHOLD, 4 * 1024); + mallopt (M_TOP_PAD, 1 * 1024); + malloc_trim (0); +} +#endif + /* end of gnunet-daemon-topology.c */ diff --git a/src/topology/test_gnunet_daemon_topology.c b/src/topology/test_gnunet_daemon_topology.c index 35225e4..99734ca 100644 --- a/src/topology/test_gnunet_daemon_topology.c +++ b/src/topology/test_gnunet_daemon_topology.c @@ -1,6 +1,6 @@ /* This file is part of GNUnet. - (C) 2009 Christian Grothoff (and other contributing authors) + (C) 2009, 2012 Christian Grothoff (and other contributing authors) GNUnet is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published @@ -22,183 +22,73 @@ * @brief testcase for topology maintenance code */ #include "platform.h" -#include "gnunet_testing_lib.h" +#include "gnunet_testbed_service.h" -#define NUM_PEERS 2 +#define NUM_PEERS 8 /** * How long until we give up on connecting the peers? */ #define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 600) -#define CONNECT_ATTEMPTS 3 - static int ok; -static int peers_left; - -static int connect_left; - -static struct GNUNET_TESTING_PeerGroup *pg; - -static struct GNUNET_TESTING_Daemon *first; - -static struct GNUNET_TESTING_Daemon *last; - -/** - * Active connection attempt. - */ -struct GNUNET_TESTING_ConnectContext *cc[NUM_PEERS]; - -/** - * Check whether peers successfully shut down. - */ -static void -shutdown_callback (void *cls, const char *emsg) -{ - if (emsg != NULL) - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Shutdown of peers failed!\n"); - if (ok == 0) - ok = 666; - } - else - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "All peers successfully shut down!\n"); - } -} - - -static void -clean_up_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - unsigned int i; - - for (i = 0; i < NUM_PEERS; i++) - { - if (NULL != cc[i]) - { - GNUNET_TESTING_daemons_connect_cancel (cc[i]); - cc[i] = NULL; - } - } - GNUNET_TESTING_daemons_stop (pg, TIMEOUT, &shutdown_callback, NULL); - ok = 0; -} +static unsigned int connect_left; static void -notify_connect_complete (void *cls, const struct GNUNET_PeerIdentity *first, - const struct GNUNET_PeerIdentity *second, - unsigned int distance, - const struct GNUNET_CONFIGURATION_Handle *first_cfg, - const struct GNUNET_CONFIGURATION_Handle *second_cfg, - struct GNUNET_TESTING_Daemon *first_daemon, - struct GNUNET_TESTING_Daemon *second_daemon, - const char *emsg) +notify_connect_complete (void *cls, + struct GNUNET_TESTBED_Operation *op, + const char *emsg) { - struct GNUNET_TESTING_ConnectContext **cc = cls; - unsigned int i; - - *cc = NULL; + GNUNET_TESTBED_operation_done (op); if (NULL != emsg) { FPRINTF (stderr, "Failed to connect two peers: %s\n", emsg); - for (i = 0; i < NUM_PEERS; i++) - if (NULL != cc[i]) - { - GNUNET_TESTING_daemons_connect_cancel (cc[i]); - cc[i] = NULL; - } - GNUNET_TESTING_daemons_stop (pg, TIMEOUT, &shutdown_callback, NULL); - GNUNET_assert (0); + GNUNET_SCHEDULER_shutdown (); + ok = 1; return; } connect_left--; - if (connect_left == 0) + if (0 == connect_left) { /* FIXME: check that topology adds a few more links * in addition to those that were seeded */ - GNUNET_SCHEDULER_add_now (&clean_up_task, NULL); + GNUNET_SCHEDULER_shutdown (); } } static void -my_cb (void *cls, const struct GNUNET_PeerIdentity *id, - const struct GNUNET_CONFIGURATION_Handle *cfg, - struct GNUNET_TESTING_Daemon *d, const char *emsg) +do_connect (void *cls, + unsigned int num_peers, + struct GNUNET_TESTBED_Peer **peers) { - GNUNET_assert (id != NULL); - peers_left--; - if (first == NULL) - { - connect_left = NUM_PEERS; - first = d; - last = d; - return; - } - cc[peers_left] = - GNUNET_TESTING_daemons_connect (last, d, TIMEOUT, CONNECT_ATTEMPTS, - GNUNET_YES, ¬ify_connect_complete, - &cc[peers_left]); - if (peers_left == 0) - { - /* close circle */ - cc[NUM_PEERS - 1] = - GNUNET_TESTING_daemons_connect (d, first, TIMEOUT, CONNECT_ATTEMPTS, - GNUNET_YES, ¬ify_connect_complete, - &cc[NUM_PEERS - 1]); - } -} - - -static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) -{ - ok = 1; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Starting daemons.\n"); - peers_left = NUM_PEERS; - pg = GNUNET_TESTING_daemons_start (cfg, peers_left, peers_left, peers_left, - TIMEOUT, NULL, NULL, &my_cb, NULL, NULL, - NULL, NULL); - GNUNET_assert (pg != NULL); -} - + unsigned int i; -static int -check () -{ - char *const argv[] = { - "test-gnunet-daemon-topology", - "-c", - "test_gnunet_daemon_topology_data.conf", - NULL - }; - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - GNUNET_PROGRAM_run ((sizeof (argv) / sizeof (char *)) - 1, argv, - "test-gnunet-daemon-topology", "nohelp", options, &run, - &ok); - return ok; + GNUNET_assert (NUM_PEERS == num_peers); + for (i=0;i/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } pkgdatadir = $(datadir)/@PACKAGE@ pkgincludedir = $(includedir)/@PACKAGE@ pkglibdir = $(libdir)/@PACKAGE@ @@ -37,12 +54,18 @@ POST_UNINSTALL = : build_triplet = @build@ host_triplet = @host@ target_triplet = @target@ -noinst_PROGRAMS = $(am__EXEEXT_22) -bin_PROGRAMS = gnunet-transport$(EXEEXT) $(am__EXEEXT_1) \ - $(am__EXEEXT_2) gnunet-service-transport$(EXEEXT) \ +noinst_PROGRAMS = $(am__EXEEXT_26) $(am__EXEEXT_27) +libexec_PROGRAMS = $(am__EXEEXT_24) $(am__EXEEXT_25) \ + gnunet-service-transport$(EXEEXT) +bin_PROGRAMS = gnunet-transport$(EXEEXT) \ gnunet-transport-certificate-creation$(EXEEXT) -check_PROGRAMS = test_transport_testing$(EXEEXT) \ - test_transport_startonly$(EXEEXT) \ +check_PROGRAMS = test_transport_testing_startstop$(EXEEXT) \ + test_transport_testing_restart$(EXEEXT) \ + test_transport_testing$(EXEEXT) \ + test_transport_startonly$(EXEEXT) test_plugin_tcp$(EXEEXT) \ + test_plugin_udp$(EXEEXT) $(am__EXEEXT_1) $(am__EXEEXT_2) \ + test_http_common$(EXEEXT) $(am__EXEEXT_3) $(am__EXEEXT_4) \ + $(am__EXEEXT_5) $(am__EXEEXT_6) \ test_transport_api_blacklisting$(EXEEXT) \ test_transport_api_disconnect_tcp$(EXEEXT) \ test_transport_api_bidirectional_connect$(EXEEXT) \ @@ -53,24 +76,30 @@ check_PROGRAMS = test_transport_testing$(EXEEXT) \ test_transport_api_limited_sockets_tcp$(EXEEXT) \ test_transport_api_tcp_nat$(EXEEXT) \ test_transport_api_udp$(EXEEXT) \ - test_transport_api_timeout_udp$(EXEEXT) $(am__EXEEXT_3) \ - $(am__EXEEXT_4) test_transport_api_udp_nat$(EXEEXT) \ - $(am__EXEEXT_5) $(am__EXEEXT_6) $(am__EXEEXT_7) \ - $(am__EXEEXT_8) $(am__EXEEXT_9) $(am__EXEEXT_10) \ + test_transport_api_timeout_udp$(EXEEXT) $(am__EXEEXT_7) \ + $(am__EXEEXT_8) test_transport_api_udp_nat$(EXEEXT) \ + $(am__EXEEXT_9) $(am__EXEEXT_10) $(am__EXEEXT_11) \ + $(am__EXEEXT_12) $(am__EXEEXT_13) $(am__EXEEXT_14) \ test_transport_api_multi$(EXEEXT) \ + test_transport_api_manipulation_send_tcp$(EXEEXT) \ + test_transport_api_manipulation_recv_tcp$(EXEEXT) \ test_transport_api_reliability_tcp$(EXEEXT) \ test_transport_api_reliability_tcp_nat$(EXEEXT) \ test_transport_api_unreliability_udp$(EXEEXT) \ test_transport_api_unreliability_constant_udp$(EXEEXT) \ - $(am__EXEEXT_11) $(am__EXEEXT_12) $(am__EXEEXT_13) \ - $(am__EXEEXT_14) $(am__EXEEXT_15) \ + $(am__EXEEXT_15) $(am__EXEEXT_16) $(am__EXEEXT_17) \ + $(am__EXEEXT_18) $(am__EXEEXT_19) \ test_quota_compliance_tcp$(EXEEXT) \ test_quota_compliance_tcp_asymmetric$(EXEEXT) \ - test_quota_compliance_udp$(EXEEXT) $(am__EXEEXT_16) \ - $(am__EXEEXT_17) $(am__EXEEXT_18) $(am__EXEEXT_19) \ - $(am__EXEEXT_20) $(am__EXEEXT_21) -@ENABLE_TEST_RUN_TRUE@TESTS = test_transport_testing$(EXEEXT) \ + test_quota_compliance_udp$(EXEEXT) $(am__EXEEXT_20) \ + $(am__EXEEXT_21) $(am__EXEEXT_22) $(am__EXEEXT_23) +@ENABLE_TEST_RUN_TRUE@TESTS = test_transport_testing_startstop$(EXEEXT) \ +@ENABLE_TEST_RUN_TRUE@ test_transport_testing_restart$(EXEEXT) \ +@ENABLE_TEST_RUN_TRUE@ test_transport_testing$(EXEEXT) \ @ENABLE_TEST_RUN_TRUE@ test_transport_startonly$(EXEEXT) \ +@ENABLE_TEST_RUN_TRUE@ test_plugin_tcp$(EXEEXT) \ +@ENABLE_TEST_RUN_TRUE@ test_plugin_udp$(EXEEXT) $(am__EXEEXT_1) \ +@ENABLE_TEST_RUN_TRUE@ $(am__EXEEXT_2) \ @ENABLE_TEST_RUN_TRUE@ test_transport_api_blacklisting$(EXEEXT) \ @ENABLE_TEST_RUN_TRUE@ test_transport_api_disconnect_tcp$(EXEEXT) \ @ENABLE_TEST_RUN_TRUE@ test_transport_api_bidirectional_connect$(EXEEXT) \ @@ -82,39 +111,41 @@ check_PROGRAMS = test_transport_testing$(EXEEXT) \ @ENABLE_TEST_RUN_TRUE@ test_transport_api_tcp_nat$(EXEEXT) \ @ENABLE_TEST_RUN_TRUE@ test_transport_api_udp$(EXEEXT) \ @ENABLE_TEST_RUN_TRUE@ test_transport_api_timeout_udp$(EXEEXT) \ -@ENABLE_TEST_RUN_TRUE@ $(am__EXEEXT_3) $(am__EXEEXT_4) \ -@ENABLE_TEST_RUN_TRUE@ test_transport_api_udp_nat$(EXEEXT) \ -@ENABLE_TEST_RUN_TRUE@ $(am__EXEEXT_5) $(am__EXEEXT_6) \ @ENABLE_TEST_RUN_TRUE@ $(am__EXEEXT_7) $(am__EXEEXT_8) \ -@ENABLE_TEST_RUN_TRUE@ $(am__EXEEXT_9) $(am__EXEEXT_10) \ +@ENABLE_TEST_RUN_TRUE@ test_transport_api_udp_nat$(EXEEXT) \ +@ENABLE_TEST_RUN_TRUE@ $(am__EXEEXT_9) $(am__EXEEXT_11) \ +@ENABLE_TEST_RUN_TRUE@ $(am__EXEEXT_12) $(am__EXEEXT_13) \ +@ENABLE_TEST_RUN_TRUE@ $(am__EXEEXT_14) \ @ENABLE_TEST_RUN_TRUE@ test_transport_api_multi$(EXEEXT) \ +@ENABLE_TEST_RUN_TRUE@ test_transport_api_manipulation_send_tcp$(EXEEXT) \ +@ENABLE_TEST_RUN_TRUE@ test_transport_api_manipulation_recv_tcp$(EXEEXT) \ @ENABLE_TEST_RUN_TRUE@ test_transport_api_reliability_tcp$(EXEEXT) \ @ENABLE_TEST_RUN_TRUE@ test_transport_api_reliability_tcp_nat$(EXEEXT) \ @ENABLE_TEST_RUN_TRUE@ test_transport_api_unreliability_udp$(EXEEXT) \ @ENABLE_TEST_RUN_TRUE@ test_transport_api_unreliability_constant_udp$(EXEEXT) \ -@ENABLE_TEST_RUN_TRUE@ $(am__EXEEXT_11) $(am__EXEEXT_12) \ -@ENABLE_TEST_RUN_TRUE@ $(am__EXEEXT_13) $(am__EXEEXT_14) \ -@ENABLE_TEST_RUN_TRUE@ $(am__EXEEXT_15) \ +@ENABLE_TEST_RUN_TRUE@ $(am__EXEEXT_15) $(am__EXEEXT_16) \ +@ENABLE_TEST_RUN_TRUE@ $(am__EXEEXT_17) $(am__EXEEXT_18) \ +@ENABLE_TEST_RUN_TRUE@ $(am__EXEEXT_19) \ @ENABLE_TEST_RUN_TRUE@ test_quota_compliance_tcp$(EXEEXT) \ @ENABLE_TEST_RUN_TRUE@ test_quota_compliance_tcp_asymmetric$(EXEEXT) \ @ENABLE_TEST_RUN_TRUE@ test_quota_compliance_udp$(EXEEXT) \ -@ENABLE_TEST_RUN_TRUE@ $(am__EXEEXT_16) $(am__EXEEXT_17) \ -@ENABLE_TEST_RUN_TRUE@ $(am__EXEEXT_18) $(am__EXEEXT_19) \ -@ENABLE_TEST_RUN_TRUE@ $(am__EXEEXT_20) $(am__EXEEXT_21) +@ENABLE_TEST_RUN_TRUE@ $(am__EXEEXT_20) $(am__EXEEXT_21) \ +@ENABLE_TEST_RUN_TRUE@ $(am__EXEEXT_22) subdir = src/transport DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in \ $(srcdir)/transport.conf.in ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 am__aclocal_m4_deps = $(top_srcdir)/m4/absolute-header.m4 \ $(top_srcdir)/m4/align.m4 $(top_srcdir)/m4/argz.m4 \ - $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/iconv.m4 \ - $(top_srcdir)/m4/lib-ld.m4 $(top_srcdir)/m4/lib-link.m4 \ - $(top_srcdir)/m4/lib-prefix.m4 $(top_srcdir)/m4/libcurl.m4 \ - $(top_srcdir)/m4/libgcrypt.m4 $(top_srcdir)/m4/libtool.m4 \ - $(top_srcdir)/m4/libunistring.m4 $(top_srcdir)/m4/ltdl.m4 \ - $(top_srcdir)/m4/ltoptions.m4 $(top_srcdir)/m4/ltsugar.m4 \ - $(top_srcdir)/m4/ltversion.m4 $(top_srcdir)/m4/lt~obsolete.m4 \ - $(top_srcdir)/m4/nls.m4 $(top_srcdir)/m4/po.m4 \ + $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/glib-2.0.m4 \ + $(top_srcdir)/m4/iconv.m4 $(top_srcdir)/m4/lib-ld.m4 \ + $(top_srcdir)/m4/lib-link.m4 $(top_srcdir)/m4/lib-prefix.m4 \ + $(top_srcdir)/m4/libcurl.m4 $(top_srcdir)/m4/libgcrypt.m4 \ + $(top_srcdir)/m4/libtool.m4 $(top_srcdir)/m4/libunistring.m4 \ + $(top_srcdir)/m4/ltdl.m4 $(top_srcdir)/m4/ltoptions.m4 \ + $(top_srcdir)/m4/ltsugar.m4 $(top_srcdir)/m4/ltversion.m4 \ + $(top_srcdir)/m4/lt~obsolete.m4 $(top_srcdir)/m4/nls.m4 \ + $(top_srcdir)/m4/pkg.m4 $(top_srcdir)/m4/po.m4 \ $(top_srcdir)/m4/progtest.m4 $(top_srcdir)/acinclude.m4 \ $(top_srcdir)/configure.ac am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ @@ -144,55 +175,97 @@ am__nobase_list = $(am__nobase_strip_setup); \ am__base_list = \ sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \ sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g' +am__uninstall_files_from_dir = { \ + test -z "$$files" \ + || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \ + || { echo " ( cd '$$dir' && rm -f" $$files ")"; \ + $(am__cd) "$$dir" && rm -f $$files; }; \ + } am__installdirs = "$(DESTDIR)$(libdir)" "$(DESTDIR)$(plugindir)" \ - "$(DESTDIR)$(bindir)" "$(DESTDIR)$(pkgcfgdir)" + "$(DESTDIR)$(bindir)" "$(DESTDIR)$(libexecdir)" \ + "$(DESTDIR)$(pkgcfgdir)" LTLIBRARIES = $(lib_LTLIBRARIES) $(plugin_LTLIBRARIES) -libgnunet_plugin_transport_http_la_DEPENDENCIES = \ +libgnunet_plugin_transport_http_client_la_DEPENDENCIES = \ $(top_builddir)/src/hello/libgnunethello.la \ $(top_builddir)/src/statistics/libgnunetstatistics.la \ $(top_builddir)/src/peerinfo/libgnunetpeerinfo.la \ $(top_builddir)/src/nat/libgnunetnat.la \ $(top_builddir)/src/util/libgnunetutil.la -am_libgnunet_plugin_transport_http_la_OBJECTS = \ - libgnunet_plugin_transport_http_la-plugin_transport_http.lo \ - libgnunet_plugin_transport_http_la-plugin_transport_http_client.lo \ - libgnunet_plugin_transport_http_la-plugin_transport_http_server.lo -libgnunet_plugin_transport_http_la_OBJECTS = \ - $(am_libgnunet_plugin_transport_http_la_OBJECTS) -AM_V_lt = $(am__v_lt_$(V)) -am__v_lt_ = $(am__v_lt_$(AM_DEFAULT_VERBOSITY)) +am_libgnunet_plugin_transport_http_client_la_OBJECTS = libgnunet_plugin_transport_http_client_la-plugin_transport_http_client.lo \ + libgnunet_plugin_transport_http_client_la-plugin_transport_http_common.lo +libgnunet_plugin_transport_http_client_la_OBJECTS = \ + $(am_libgnunet_plugin_transport_http_client_la_OBJECTS) +AM_V_lt = $(am__v_lt_@AM_V@) +am__v_lt_ = $(am__v_lt_@AM_DEFAULT_V@) am__v_lt_0 = --silent -libgnunet_plugin_transport_http_la_LINK = $(LIBTOOL) $(AM_V_lt) \ +libgnunet_plugin_transport_http_client_la_LINK = $(LIBTOOL) $(AM_V_lt) \ --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link \ - $(CCLD) $(libgnunet_plugin_transport_http_la_CFLAGS) $(CFLAGS) \ - $(libgnunet_plugin_transport_http_la_LDFLAGS) $(LDFLAGS) -o $@ -@HAVE_MHD_TRUE@am_libgnunet_plugin_transport_http_la_rpath = -rpath \ -@HAVE_MHD_TRUE@ $(plugindir) -libgnunet_plugin_transport_https_la_DEPENDENCIES = \ + $(CCLD) $(libgnunet_plugin_transport_http_client_la_CFLAGS) \ + $(CFLAGS) $(libgnunet_plugin_transport_http_client_la_LDFLAGS) \ + $(LDFLAGS) -o $@ +@HAVE_LIBCURL_TRUE@am_libgnunet_plugin_transport_http_client_la_rpath = \ +@HAVE_LIBCURL_TRUE@ -rpath $(plugindir) +libgnunet_plugin_transport_http_server_la_DEPENDENCIES = \ $(top_builddir)/src/hello/libgnunethello.la \ $(top_builddir)/src/statistics/libgnunetstatistics.la \ $(top_builddir)/src/peerinfo/libgnunetpeerinfo.la \ $(top_builddir)/src/nat/libgnunetnat.la \ $(top_builddir)/src/util/libgnunetutil.la -am_libgnunet_plugin_transport_https_la_OBJECTS = \ - libgnunet_plugin_transport_https_la-plugin_transport_http.lo \ - libgnunet_plugin_transport_https_la-plugin_transport_http_client.lo \ - libgnunet_plugin_transport_https_la-plugin_transport_http_server.lo -libgnunet_plugin_transport_https_la_OBJECTS = \ - $(am_libgnunet_plugin_transport_https_la_OBJECTS) -libgnunet_plugin_transport_https_la_LINK = $(LIBTOOL) $(AM_V_lt) \ +am_libgnunet_plugin_transport_http_server_la_OBJECTS = libgnunet_plugin_transport_http_server_la-plugin_transport_http_server.lo \ + libgnunet_plugin_transport_http_server_la-plugin_transport_http_common.lo +libgnunet_plugin_transport_http_server_la_OBJECTS = \ + $(am_libgnunet_plugin_transport_http_server_la_OBJECTS) +libgnunet_plugin_transport_http_server_la_LINK = $(LIBTOOL) $(AM_V_lt) \ --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link \ - $(CCLD) $(libgnunet_plugin_transport_https_la_CFLAGS) \ - $(CFLAGS) $(libgnunet_plugin_transport_https_la_LDFLAGS) \ + $(CCLD) $(libgnunet_plugin_transport_http_server_la_CFLAGS) \ + $(CFLAGS) $(libgnunet_plugin_transport_http_server_la_LDFLAGS) \ $(LDFLAGS) -o $@ -@HAVE_MHD_TRUE@am_libgnunet_plugin_transport_https_la_rpath = -rpath \ -@HAVE_MHD_TRUE@ $(plugindir) -libgnunet_plugin_transport_tcp_la_DEPENDENCIES = \ +@HAVE_MHD_TRUE@am_libgnunet_plugin_transport_http_server_la_rpath = \ +@HAVE_MHD_TRUE@ -rpath $(plugindir) +libgnunet_plugin_transport_https_client_la_DEPENDENCIES = \ + $(top_builddir)/src/hello/libgnunethello.la \ + $(top_builddir)/src/statistics/libgnunetstatistics.la \ + $(top_builddir)/src/peerinfo/libgnunetpeerinfo.la \ + $(top_builddir)/src/nat/libgnunetnat.la \ + $(top_builddir)/src/util/libgnunetutil.la +am_libgnunet_plugin_transport_https_client_la_OBJECTS = libgnunet_plugin_transport_https_client_la-plugin_transport_http_client.lo \ + libgnunet_plugin_transport_https_client_la-plugin_transport_http_common.lo +libgnunet_plugin_transport_https_client_la_OBJECTS = \ + $(am_libgnunet_plugin_transport_https_client_la_OBJECTS) +libgnunet_plugin_transport_https_client_la_LINK = $(LIBTOOL) \ + $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) \ + --mode=link $(CCLD) \ + $(libgnunet_plugin_transport_https_client_la_CFLAGS) $(CFLAGS) \ + $(libgnunet_plugin_transport_https_client_la_LDFLAGS) \ + $(LDFLAGS) -o $@ +@HAVE_LIBCURL_TRUE@am_libgnunet_plugin_transport_https_client_la_rpath = \ +@HAVE_LIBCURL_TRUE@ -rpath $(plugindir) +libgnunet_plugin_transport_https_server_la_DEPENDENCIES = \ $(top_builddir)/src/hello/libgnunethello.la \ $(top_builddir)/src/statistics/libgnunetstatistics.la \ $(top_builddir)/src/peerinfo/libgnunetpeerinfo.la \ $(top_builddir)/src/nat/libgnunetnat.la \ $(top_builddir)/src/util/libgnunetutil.la +am_libgnunet_plugin_transport_https_server_la_OBJECTS = libgnunet_plugin_transport_https_server_la-plugin_transport_http_server.lo \ + libgnunet_plugin_transport_https_server_la-plugin_transport_http_common.lo +libgnunet_plugin_transport_https_server_la_OBJECTS = \ + $(am_libgnunet_plugin_transport_https_server_la_OBJECTS) +libgnunet_plugin_transport_https_server_la_LINK = $(LIBTOOL) \ + $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) \ + --mode=link $(CCLD) \ + $(libgnunet_plugin_transport_https_server_la_CFLAGS) $(CFLAGS) \ + $(libgnunet_plugin_transport_https_server_la_LDFLAGS) \ + $(LDFLAGS) -o $@ +@HAVE_MHD_TRUE@am_libgnunet_plugin_transport_https_server_la_rpath = \ +@HAVE_MHD_TRUE@ -rpath $(plugindir) +am__DEPENDENCIES_1 = +libgnunet_plugin_transport_tcp_la_DEPENDENCIES = \ + $(top_builddir)/src/hello/libgnunethello.la \ + $(top_builddir)/src/statistics/libgnunetstatistics.la \ + $(top_builddir)/src/peerinfo/libgnunetpeerinfo.la \ + $(top_builddir)/src/nat/libgnunetnat.la \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(am__DEPENDENCIES_1) am_libgnunet_plugin_transport_tcp_la_OBJECTS = \ plugin_transport_tcp.lo libgnunet_plugin_transport_tcp_la_OBJECTS = \ @@ -202,7 +275,8 @@ libgnunet_plugin_transport_tcp_la_LINK = $(LIBTOOL) $(AM_V_lt) \ $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ $(libgnunet_plugin_transport_tcp_la_LDFLAGS) $(LDFLAGS) -o $@ libgnunet_plugin_transport_template_la_DEPENDENCIES = \ - $(top_builddir)/src/util/libgnunetutil.la + $(top_builddir)/src/util/libgnunetutil.la \ + $(am__DEPENDENCIES_1) am_libgnunet_plugin_transport_template_la_OBJECTS = \ plugin_transport_template.lo libgnunet_plugin_transport_template_la_OBJECTS = \ @@ -218,7 +292,8 @@ libgnunet_plugin_transport_udp_la_DEPENDENCIES = \ $(top_builddir)/src/statistics/libgnunetstatistics.la \ $(top_builddir)/src/peerinfo/libgnunetpeerinfo.la \ $(top_builddir)/src/nat/libgnunetnat.la \ - $(top_builddir)/src/util/libgnunetutil.la + $(top_builddir)/src/util/libgnunetutil.la \ + $(am__DEPENDENCIES_1) am_libgnunet_plugin_transport_udp_la_OBJECTS = \ plugin_transport_udp.lo plugin_transport_udp_broadcasting.lo libgnunet_plugin_transport_udp_la_OBJECTS = \ @@ -231,7 +306,8 @@ libgnunet_plugin_transport_unix_la_DEPENDENCIES = \ $(top_builddir)/src/hello/libgnunethello.la \ $(top_builddir)/src/statistics/libgnunetstatistics.la \ $(top_builddir)/src/peerinfo/libgnunetpeerinfo.la \ - $(top_builddir)/src/util/libgnunetutil.la + $(top_builddir)/src/util/libgnunetutil.la \ + $(am__DEPENDENCIES_1) am_libgnunet_plugin_transport_unix_la_OBJECTS = \ plugin_transport_unix.lo libgnunet_plugin_transport_unix_la_OBJECTS = \ @@ -258,7 +334,6 @@ libgnunet_plugin_transport_wlan_la_LINK = $(LIBTOOL) $(AM_V_lt) \ $(libgnunet_plugin_transport_wlan_la_LDFLAGS) $(LDFLAGS) -o $@ @LINUX_TRUE@am_libgnunet_plugin_transport_wlan_la_rpath = -rpath \ @LINUX_TRUE@ $(plugindir) -am__DEPENDENCIES_1 = libgnunettransport_la_DEPENDENCIES = \ $(top_builddir)/src/hello/libgnunethello.la \ $(top_builddir)/src/util/libgnunetutil.la \ @@ -278,40 +353,42 @@ libgnunettransporttesting_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ $(AM_CFLAGS) $(CFLAGS) $(libgnunettransporttesting_la_LDFLAGS) \ $(LDFLAGS) -o $@ -@LINUX_TRUE@am__EXEEXT_1 = gnunet-helper-transport-wlan$(EXEEXT) -@LINUX_TRUE@am__EXEEXT_2 = \ -@LINUX_TRUE@ gnunet-helper-transport-wlan-dummy$(EXEEXT) -@MINGW_FALSE@am__EXEEXT_3 = test_transport_api_unix$(EXEEXT) -@MINGW_FALSE@am__EXEEXT_4 = test_transport_api_timeout_unix$(EXEEXT) -@HAVE_MHD_TRUE@am__EXEEXT_5 = test_transport_api_http$(EXEEXT) -@HAVE_MHD_TRUE@am__EXEEXT_6 = test_transport_api_http_nat$(EXEEXT) -@HAVE_MHD_TRUE@am__EXEEXT_7 = \ -@HAVE_MHD_TRUE@ test_transport_api_timeout_http$(EXEEXT) -@HAVE_MHD_TRUE@am__EXEEXT_8 = test_transport_api_https$(EXEEXT) -@HAVE_MHD_TRUE@am__EXEEXT_9 = test_transport_api_https_nat$(EXEEXT) -@HAVE_MHD_TRUE@am__EXEEXT_10 = \ -@HAVE_MHD_TRUE@ test_transport_api_timeout_https$(EXEEXT) -@MINGW_FALSE@am__EXEEXT_11 = \ +@MINGW_FALSE@am__EXEEXT_1 = test_plugin_unix$(EXEEXT) +@LINUX_TRUE@am__EXEEXT_2 = test_plugin_wlan$(EXEEXT) +@HAVE_LIBCURL_TRUE@am__EXEEXT_3 = test_plugin_http_client$(EXEEXT) +@HAVE_LIBCURL_TRUE@am__EXEEXT_4 = test_plugin_https_client$(EXEEXT) +@HAVE_MHD_TRUE@am__EXEEXT_5 = test_plugin_http_server$(EXEEXT) +@HAVE_MHD_TRUE@am__EXEEXT_6 = test_plugin_https_server$(EXEEXT) +@MINGW_FALSE@am__EXEEXT_7 = test_transport_api_unix$(EXEEXT) +@MINGW_FALSE@am__EXEEXT_8 = test_transport_api_timeout_unix$(EXEEXT) +@HAVE_LIBCURL_TRUE@@HAVE_MHD_TRUE@am__EXEEXT_9 = test_transport_api_http$(EXEEXT) +@HAVE_LIBCURL_TRUE@@HAVE_MHD_TRUE@am__EXEEXT_10 = test_transport_api_http_reverse$(EXEEXT) +@HAVE_LIBCURL_TRUE@@HAVE_MHD_TRUE@am__EXEEXT_11 = test_transport_api_timeout_http$(EXEEXT) +@HAVE_LIBCURL_TRUE@@HAVE_MHD_TRUE@am__EXEEXT_12 = test_transport_api_https$(EXEEXT) +@HAVE_LIBCURL_TRUE@@HAVE_MHD_TRUE@am__EXEEXT_13 = test_transport_api_timeout_https$(EXEEXT) +@LINUX_TRUE@am__EXEEXT_14 = test_transport_api_wlan$(EXEEXT) +@MINGW_FALSE@am__EXEEXT_15 = \ @MINGW_FALSE@ test_transport_api_unreliability_unix$(EXEEXT) -@HAVE_MHD_TRUE@am__EXEEXT_12 = \ -@HAVE_MHD_TRUE@ test_transport_api_reliability_http$(EXEEXT) -@HAVE_MHD_TRUE@am__EXEEXT_13 = test_transport_api_reliability_http_nat$(EXEEXT) -@HAVE_MHD_TRUE@am__EXEEXT_14 = \ -@HAVE_MHD_TRUE@ test_transport_api_reliability_https$(EXEEXT) -@HAVE_MHD_TRUE@am__EXEEXT_15 = test_transport_api_reliability_https_nat$(EXEEXT) -@MINGW_FALSE@am__EXEEXT_16 = test_quota_compliance_unix$(EXEEXT) \ -@MINGW_FALSE@ test_quota_compliance_unix_asymmetric$(EXEEXT) -@HAVE_MHD_TRUE@am__EXEEXT_17 = test_quota_compliance_http$(EXEEXT) \ -@HAVE_MHD_TRUE@ test_quota_compliance_http_asymmetric$(EXEEXT) -@HAVE_MHD_TRUE@am__EXEEXT_18 = test_quota_compliance_https$(EXEEXT) \ -@HAVE_MHD_TRUE@ test_quota_compliance_https_asymmetric$(EXEEXT) -@LINUX_TRUE@am__EXEEXT_19 = test_transport_api_wlan$(EXEEXT) -@LINUX_TRUE@am__EXEEXT_20 = \ +@HAVE_LIBCURL_TRUE@@HAVE_MHD_TRUE@am__EXEEXT_16 = test_transport_api_reliability_http$(EXEEXT) +@HAVE_LIBCURL_TRUE@@HAVE_MHD_TRUE@am__EXEEXT_17 = test_transport_api_reliability_https$(EXEEXT) +@LINUX_TRUE@am__EXEEXT_18 = \ @LINUX_TRUE@ test_transport_api_reliability_wlan$(EXEEXT) -@LINUX_TRUE@am__EXEEXT_21 = \ +@LINUX_TRUE@am__EXEEXT_19 = \ @LINUX_TRUE@ test_transport_api_unreliability_wlan$(EXEEXT) -@LINUX_TRUE@am__EXEEXT_22 = gnunet-transport-wlan-sender$(EXEEXT) -PROGRAMS = $(bin_PROGRAMS) $(noinst_PROGRAMS) +@MINGW_FALSE@am__EXEEXT_20 = test_quota_compliance_unix$(EXEEXT) \ +@MINGW_FALSE@ test_quota_compliance_unix_asymmetric$(EXEEXT) +@HAVE_LIBCURL_TRUE@@HAVE_MHD_TRUE@am__EXEEXT_21 = test_quota_compliance_http$(EXEEXT) \ +@HAVE_LIBCURL_TRUE@@HAVE_MHD_TRUE@ test_quota_compliance_http_asymmetric$(EXEEXT) +@HAVE_LIBCURL_TRUE@@HAVE_MHD_TRUE@am__EXEEXT_22 = test_quota_compliance_https$(EXEEXT) \ +@HAVE_LIBCURL_TRUE@@HAVE_MHD_TRUE@ test_quota_compliance_https_asymmetric$(EXEEXT) +@LINUX_TRUE@am__EXEEXT_23 = test_quota_compliance_wlan$(EXEEXT) \ +@LINUX_TRUE@ test_quota_compliance_wlan_asymmetric$(EXEEXT) +@LINUX_TRUE@am__EXEEXT_24 = gnunet-helper-transport-wlan$(EXEEXT) +@LINUX_TRUE@am__EXEEXT_25 = \ +@LINUX_TRUE@ gnunet-helper-transport-wlan-dummy$(EXEEXT) +@LINUX_TRUE@am__EXEEXT_26 = gnunet-transport-wlan-sender$(EXEEXT) +@LINUX_TRUE@am__EXEEXT_27 = gnunet-transport-wlan-receiver$(EXEEXT) +PROGRAMS = $(bin_PROGRAMS) $(libexec_PROGRAMS) $(noinst_PROGRAMS) am_gnunet_helper_transport_wlan_OBJECTS = \ gnunet-helper-transport-wlan.$(OBJEXT) gnunet_helper_transport_wlan_OBJECTS = \ @@ -324,13 +401,14 @@ gnunet_helper_transport_wlan_dummy_OBJECTS = \ gnunet_helper_transport_wlan_dummy_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la am_gnunet_service_transport_OBJECTS = \ - gnunet-service-transport.$(OBJEXT) \ - gnunet-service-transport_blacklist.$(OBJEXT) \ - gnunet-service-transport_clients.$(OBJEXT) \ - gnunet-service-transport_hello.$(OBJEXT) \ - gnunet-service-transport_neighbours.$(OBJEXT) \ - gnunet-service-transport_plugins.$(OBJEXT) \ - gnunet-service-transport_validation.$(OBJEXT) + gnunet_service_transport-gnunet-service-transport.$(OBJEXT) \ + gnunet_service_transport-gnunet-service-transport_blacklist.$(OBJEXT) \ + gnunet_service_transport-gnunet-service-transport_clients.$(OBJEXT) \ + gnunet_service_transport-gnunet-service-transport_hello.$(OBJEXT) \ + gnunet_service_transport-gnunet-service-transport_neighbours.$(OBJEXT) \ + gnunet_service_transport-gnunet-service-transport_plugins.$(OBJEXT) \ + gnunet_service_transport-gnunet-service-transport_validation.$(OBJEXT) \ + gnunet_service_transport-gnunet-service-transport_manipulation.$(OBJEXT) gnunet_service_transport_OBJECTS = \ $(am_gnunet_service_transport_OBJECTS) gnunet_service_transport_DEPENDENCIES = \ @@ -340,6 +418,10 @@ gnunet_service_transport_DEPENDENCIES = \ $(top_builddir)/src/statistics/libgnunetstatistics.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(am__DEPENDENCIES_1) +gnunet_service_transport_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ + $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ + $(gnunet_service_transport_CFLAGS) $(CFLAGS) $(AM_LDFLAGS) \ + $(LDFLAGS) -o $@ am_gnunet_transport_OBJECTS = gnunet-transport.$(OBJEXT) gnunet_transport_OBJECTS = $(am_gnunet_transport_OBJECTS) am_gnunet_transport_certificate_creation_OBJECTS = \ @@ -348,12 +430,95 @@ gnunet_transport_certificate_creation_OBJECTS = \ $(am_gnunet_transport_certificate_creation_OBJECTS) gnunet_transport_certificate_creation_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la +am_gnunet_transport_wlan_receiver_OBJECTS = \ + gnunet-transport-wlan-receiver.$(OBJEXT) +gnunet_transport_wlan_receiver_OBJECTS = \ + $(am_gnunet_transport_wlan_receiver_OBJECTS) +gnunet_transport_wlan_receiver_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la am_gnunet_transport_wlan_sender_OBJECTS = \ gnunet-transport-wlan-sender.$(OBJEXT) gnunet_transport_wlan_sender_OBJECTS = \ $(am_gnunet_transport_wlan_sender_OBJECTS) gnunet_transport_wlan_sender_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la +am_test_http_common_OBJECTS = test_http_common.$(OBJEXT) \ + plugin_transport_http_common.$(OBJEXT) +test_http_common_OBJECTS = $(am_test_http_common_OBJECTS) +test_http_common_DEPENDENCIES = \ + $(top_builddir)/src/transport/libgnunettransport.la \ + $(top_builddir)/src/statistics/libgnunetstatistics.la \ + $(top_builddir)/src/hello/libgnunethello.la \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/transport/libgnunettransporttesting.la +am_test_plugin_http_client_OBJECTS = test_plugin_transport.$(OBJEXT) +test_plugin_http_client_OBJECTS = \ + $(am_test_plugin_http_client_OBJECTS) +test_plugin_http_client_DEPENDENCIES = \ + $(top_builddir)/src/transport/libgnunettransport.la \ + $(top_builddir)/src/statistics/libgnunetstatistics.la \ + $(top_builddir)/src/hello/libgnunethello.la \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/transport/libgnunettransporttesting.la +am_test_plugin_http_server_OBJECTS = test_plugin_transport.$(OBJEXT) +test_plugin_http_server_OBJECTS = \ + $(am_test_plugin_http_server_OBJECTS) +test_plugin_http_server_DEPENDENCIES = \ + $(top_builddir)/src/transport/libgnunettransport.la \ + $(top_builddir)/src/statistics/libgnunetstatistics.la \ + $(top_builddir)/src/hello/libgnunethello.la \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/transport/libgnunettransporttesting.la +am_test_plugin_https_client_OBJECTS = test_plugin_transport.$(OBJEXT) +test_plugin_https_client_OBJECTS = \ + $(am_test_plugin_https_client_OBJECTS) +test_plugin_https_client_DEPENDENCIES = \ + $(top_builddir)/src/transport/libgnunettransport.la \ + $(top_builddir)/src/statistics/libgnunetstatistics.la \ + $(top_builddir)/src/hello/libgnunethello.la \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/transport/libgnunettransporttesting.la +am_test_plugin_https_server_OBJECTS = test_plugin_transport.$(OBJEXT) +test_plugin_https_server_OBJECTS = \ + $(am_test_plugin_https_server_OBJECTS) +test_plugin_https_server_DEPENDENCIES = \ + $(top_builddir)/src/transport/libgnunettransport.la \ + $(top_builddir)/src/statistics/libgnunetstatistics.la \ + $(top_builddir)/src/hello/libgnunethello.la \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/transport/libgnunettransporttesting.la +am_test_plugin_tcp_OBJECTS = test_plugin_transport.$(OBJEXT) +test_plugin_tcp_OBJECTS = $(am_test_plugin_tcp_OBJECTS) +test_plugin_tcp_DEPENDENCIES = \ + $(top_builddir)/src/transport/libgnunettransport.la \ + $(top_builddir)/src/statistics/libgnunetstatistics.la \ + $(top_builddir)/src/hello/libgnunethello.la \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/transport/libgnunettransporttesting.la +am_test_plugin_udp_OBJECTS = test_plugin_transport.$(OBJEXT) +test_plugin_udp_OBJECTS = $(am_test_plugin_udp_OBJECTS) +test_plugin_udp_DEPENDENCIES = \ + $(top_builddir)/src/transport/libgnunettransport.la \ + $(top_builddir)/src/statistics/libgnunetstatistics.la \ + $(top_builddir)/src/hello/libgnunethello.la \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/transport/libgnunettransporttesting.la +am_test_plugin_unix_OBJECTS = test_plugin_transport.$(OBJEXT) +test_plugin_unix_OBJECTS = $(am_test_plugin_unix_OBJECTS) +test_plugin_unix_DEPENDENCIES = \ + $(top_builddir)/src/transport/libgnunettransport.la \ + $(top_builddir)/src/statistics/libgnunetstatistics.la \ + $(top_builddir)/src/hello/libgnunethello.la \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/transport/libgnunettransporttesting.la +am_test_plugin_wlan_OBJECTS = test_plugin_transport.$(OBJEXT) +test_plugin_wlan_OBJECTS = $(am_test_plugin_wlan_OBJECTS) +test_plugin_wlan_DEPENDENCIES = \ + $(top_builddir)/src/transport/libgnunettransport.la \ + $(top_builddir)/src/statistics/libgnunetstatistics.la \ + $(top_builddir)/src/hello/libgnunethello.la \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/transport/libgnunettransporttesting.la am_test_quota_compliance_http_OBJECTS = \ test_quota_compliance.$(OBJEXT) test_quota_compliance_http_OBJECTS = \ @@ -435,6 +600,24 @@ test_quota_compliance_unix_asymmetric_DEPENDENCIES = \ $(top_builddir)/src/hello/libgnunethello.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/transport/libgnunettransporttesting.la +am_test_quota_compliance_wlan_OBJECTS = \ + test_quota_compliance.$(OBJEXT) +test_quota_compliance_wlan_OBJECTS = \ + $(am_test_quota_compliance_wlan_OBJECTS) +test_quota_compliance_wlan_DEPENDENCIES = \ + $(top_builddir)/src/transport/libgnunettransport.la \ + $(top_builddir)/src/hello/libgnunethello.la \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/transport/libgnunettransporttesting.la +am_test_quota_compliance_wlan_asymmetric_OBJECTS = \ + test_quota_compliance.$(OBJEXT) +test_quota_compliance_wlan_asymmetric_OBJECTS = \ + $(am_test_quota_compliance_wlan_asymmetric_OBJECTS) +test_quota_compliance_wlan_asymmetric_DEPENDENCIES = \ + $(top_builddir)/src/transport/libgnunettransport.la \ + $(top_builddir)/src/hello/libgnunethello.la \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/transport/libgnunettransporttesting.la am_test_transport_api_bidirectional_connect_OBJECTS = \ test_transport_api_bidirectional_connect.$(OBJEXT) test_transport_api_bidirectional_connect_OBJECTS = \ @@ -472,10 +655,11 @@ test_transport_api_http_DEPENDENCIES = \ $(top_builddir)/src/hello/libgnunethello.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/transport/libgnunettransporttesting.la -am_test_transport_api_http_nat_OBJECTS = test_transport_api.$(OBJEXT) -test_transport_api_http_nat_OBJECTS = \ - $(am_test_transport_api_http_nat_OBJECTS) -test_transport_api_http_nat_DEPENDENCIES = \ +am_test_transport_api_http_reverse_OBJECTS = \ + test_transport_api.$(OBJEXT) +test_transport_api_http_reverse_OBJECTS = \ + $(am_test_transport_api_http_reverse_OBJECTS) +test_transport_api_http_reverse_DEPENDENCIES = \ $(top_builddir)/src/transport/libgnunettransport.la \ $(top_builddir)/src/hello/libgnunethello.la \ $(top_builddir)/src/util/libgnunetutil.la \ @@ -488,15 +672,6 @@ test_transport_api_https_DEPENDENCIES = \ $(top_builddir)/src/hello/libgnunethello.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/transport/libgnunettransporttesting.la -am_test_transport_api_https_nat_OBJECTS = \ - test_transport_api.$(OBJEXT) -test_transport_api_https_nat_OBJECTS = \ - $(am_test_transport_api_https_nat_OBJECTS) -test_transport_api_https_nat_DEPENDENCIES = \ - $(top_builddir)/src/transport/libgnunettransport.la \ - $(top_builddir)/src/hello/libgnunethello.la \ - $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/transport/libgnunettransporttesting.la am_test_transport_api_limited_sockets_tcp_OBJECTS = \ test_transport_api_limited_sockets.$(OBJEXT) test_transport_api_limited_sockets_tcp_OBJECTS = \ @@ -506,6 +681,24 @@ test_transport_api_limited_sockets_tcp_DEPENDENCIES = \ $(top_builddir)/src/hello/libgnunethello.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/transport/libgnunettransporttesting.la +am_test_transport_api_manipulation_recv_tcp_OBJECTS = \ + test_transport_api_manipulation_recv_tcp.$(OBJEXT) +test_transport_api_manipulation_recv_tcp_OBJECTS = \ + $(am_test_transport_api_manipulation_recv_tcp_OBJECTS) +test_transport_api_manipulation_recv_tcp_DEPENDENCIES = \ + $(top_builddir)/src/transport/libgnunettransport.la \ + $(top_builddir)/src/hello/libgnunethello.la \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/transport/libgnunettransporttesting.la +am_test_transport_api_manipulation_send_tcp_OBJECTS = \ + test_transport_api_manipulation_send_tcp.$(OBJEXT) +test_transport_api_manipulation_send_tcp_OBJECTS = \ + $(am_test_transport_api_manipulation_send_tcp_OBJECTS) +test_transport_api_manipulation_send_tcp_DEPENDENCIES = \ + $(top_builddir)/src/transport/libgnunettransport.la \ + $(top_builddir)/src/hello/libgnunethello.la \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/transport/libgnunettransporttesting.la am_test_transport_api_multi_OBJECTS = test_transport_api.$(OBJEXT) test_transport_api_multi_OBJECTS = \ $(am_test_transport_api_multi_OBJECTS) @@ -523,15 +716,6 @@ test_transport_api_reliability_http_DEPENDENCIES = \ $(top_builddir)/src/hello/libgnunethello.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/transport/libgnunettransporttesting.la -am_test_transport_api_reliability_http_nat_OBJECTS = \ - test_transport_api_reliability.$(OBJEXT) -test_transport_api_reliability_http_nat_OBJECTS = \ - $(am_test_transport_api_reliability_http_nat_OBJECTS) -test_transport_api_reliability_http_nat_DEPENDENCIES = \ - $(top_builddir)/src/transport/libgnunettransport.la \ - $(top_builddir)/src/hello/libgnunethello.la \ - $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/transport/libgnunettransporttesting.la am_test_transport_api_reliability_https_OBJECTS = \ test_transport_api_reliability.$(OBJEXT) test_transport_api_reliability_https_OBJECTS = \ @@ -541,15 +725,6 @@ test_transport_api_reliability_https_DEPENDENCIES = \ $(top_builddir)/src/hello/libgnunethello.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/transport/libgnunettransporttesting.la -am_test_transport_api_reliability_https_nat_OBJECTS = \ - test_transport_api_reliability.$(OBJEXT) -test_transport_api_reliability_https_nat_OBJECTS = \ - $(am_test_transport_api_reliability_https_nat_OBJECTS) -test_transport_api_reliability_https_nat_DEPENDENCIES = \ - $(top_builddir)/src/transport/libgnunettransport.la \ - $(top_builddir)/src/hello/libgnunethello.la \ - $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/transport/libgnunettransporttesting.la am_test_transport_api_reliability_tcp_OBJECTS = \ test_transport_api_reliability.$(OBJEXT) test_transport_api_reliability_tcp_OBJECTS = \ @@ -742,6 +917,24 @@ test_transport_testing_DEPENDENCIES = \ $(top_builddir)/src/transport/libgnunettransport.la \ $(top_builddir)/src/hello/libgnunethello.la \ $(top_builddir)/src/transport/libgnunettransporttesting.la +am_test_transport_testing_restart_OBJECTS = \ + test_transport_testing_restart.$(OBJEXT) +test_transport_testing_restart_OBJECTS = \ + $(am_test_transport_testing_restart_OBJECTS) +test_transport_testing_restart_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/transport/libgnunettransport.la \ + $(top_builddir)/src/hello/libgnunethello.la \ + $(top_builddir)/src/transport/libgnunettransporttesting.la +am_test_transport_testing_startstop_OBJECTS = \ + test_transport_testing_startstop.$(OBJEXT) +test_transport_testing_startstop_OBJECTS = \ + $(am_test_transport_testing_startstop_OBJECTS) +test_transport_testing_startstop_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/transport/libgnunettransport.la \ + $(top_builddir)/src/hello/libgnunethello.la \ + $(top_builddir)/src/transport/libgnunettransporttesting.la DEFAULT_INCLUDES = -I.@am__isrc@ -I$(top_builddir) depcomp = $(SHELL) $(top_srcdir)/depcomp am__depfiles_maybe = depfiles @@ -752,24 +945,26 @@ LTCOMPILE = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) \ $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) \ $(AM_CFLAGS) $(CFLAGS) -AM_V_CC = $(am__v_CC_$(V)) -am__v_CC_ = $(am__v_CC_$(AM_DEFAULT_VERBOSITY)) +AM_V_CC = $(am__v_CC_@AM_V@) +am__v_CC_ = $(am__v_CC_@AM_DEFAULT_V@) am__v_CC_0 = @echo " CC " $@; -AM_V_at = $(am__v_at_$(V)) -am__v_at_ = $(am__v_at_$(AM_DEFAULT_VERBOSITY)) +AM_V_at = $(am__v_at_@AM_V@) +am__v_at_ = $(am__v_at_@AM_DEFAULT_V@) am__v_at_0 = @ CCLD = $(CC) LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ $(AM_LDFLAGS) $(LDFLAGS) -o $@ -AM_V_CCLD = $(am__v_CCLD_$(V)) -am__v_CCLD_ = $(am__v_CCLD_$(AM_DEFAULT_VERBOSITY)) +AM_V_CCLD = $(am__v_CCLD_@AM_V@) +am__v_CCLD_ = $(am__v_CCLD_@AM_DEFAULT_V@) am__v_CCLD_0 = @echo " CCLD " $@; -AM_V_GEN = $(am__v_GEN_$(V)) -am__v_GEN_ = $(am__v_GEN_$(AM_DEFAULT_VERBOSITY)) +AM_V_GEN = $(am__v_GEN_@AM_V@) +am__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@) am__v_GEN_0 = @echo " GEN " $@; -SOURCES = $(libgnunet_plugin_transport_http_la_SOURCES) \ - $(libgnunet_plugin_transport_https_la_SOURCES) \ +SOURCES = $(libgnunet_plugin_transport_http_client_la_SOURCES) \ + $(libgnunet_plugin_transport_http_server_la_SOURCES) \ + $(libgnunet_plugin_transport_https_client_la_SOURCES) \ + $(libgnunet_plugin_transport_https_server_la_SOURCES) \ $(libgnunet_plugin_transport_tcp_la_SOURCES) \ $(libgnunet_plugin_transport_template_la_SOURCES) \ $(libgnunet_plugin_transport_udp_la_SOURCES) \ @@ -782,7 +977,14 @@ SOURCES = $(libgnunet_plugin_transport_http_la_SOURCES) \ $(gnunet_service_transport_SOURCES) \ $(gnunet_transport_SOURCES) \ $(gnunet_transport_certificate_creation_SOURCES) \ + $(gnunet_transport_wlan_receiver_SOURCES) \ $(gnunet_transport_wlan_sender_SOURCES) \ + $(test_http_common_SOURCES) $(test_plugin_http_client_SOURCES) \ + $(test_plugin_http_server_SOURCES) \ + $(test_plugin_https_client_SOURCES) \ + $(test_plugin_https_server_SOURCES) $(test_plugin_tcp_SOURCES) \ + $(test_plugin_udp_SOURCES) $(test_plugin_unix_SOURCES) \ + $(test_plugin_wlan_SOURCES) \ $(test_quota_compliance_http_SOURCES) \ $(test_quota_compliance_http_asymmetric_SOURCES) \ $(test_quota_compliance_https_SOURCES) \ @@ -792,19 +994,20 @@ SOURCES = $(libgnunet_plugin_transport_http_la_SOURCES) \ $(test_quota_compliance_udp_SOURCES) \ $(test_quota_compliance_unix_SOURCES) \ $(test_quota_compliance_unix_asymmetric_SOURCES) \ + $(test_quota_compliance_wlan_SOURCES) \ + $(test_quota_compliance_wlan_asymmetric_SOURCES) \ $(test_transport_api_bidirectional_connect_SOURCES) \ $(test_transport_api_blacklisting_SOURCES) \ $(test_transport_api_disconnect_tcp_SOURCES) \ $(test_transport_api_http_SOURCES) \ - $(test_transport_api_http_nat_SOURCES) \ + $(test_transport_api_http_reverse_SOURCES) \ $(test_transport_api_https_SOURCES) \ - $(test_transport_api_https_nat_SOURCES) \ $(test_transport_api_limited_sockets_tcp_SOURCES) \ + $(test_transport_api_manipulation_recv_tcp_SOURCES) \ + $(test_transport_api_manipulation_send_tcp_SOURCES) \ $(test_transport_api_multi_SOURCES) \ $(test_transport_api_reliability_http_SOURCES) \ - $(test_transport_api_reliability_http_nat_SOURCES) \ $(test_transport_api_reliability_https_SOURCES) \ - $(test_transport_api_reliability_https_nat_SOURCES) \ $(test_transport_api_reliability_tcp_SOURCES) \ $(test_transport_api_reliability_tcp_nat_SOURCES) \ $(test_transport_api_reliability_wlan_SOURCES) \ @@ -826,9 +1029,13 @@ SOURCES = $(libgnunet_plugin_transport_http_la_SOURCES) \ $(test_transport_api_unreliability_wlan_SOURCES) \ $(test_transport_api_wlan_SOURCES) \ $(test_transport_startonly_SOURCES) \ - $(test_transport_testing_SOURCES) -DIST_SOURCES = $(libgnunet_plugin_transport_http_la_SOURCES) \ - $(libgnunet_plugin_transport_https_la_SOURCES) \ + $(test_transport_testing_SOURCES) \ + $(test_transport_testing_restart_SOURCES) \ + $(test_transport_testing_startstop_SOURCES) +DIST_SOURCES = $(libgnunet_plugin_transport_http_client_la_SOURCES) \ + $(libgnunet_plugin_transport_http_server_la_SOURCES) \ + $(libgnunet_plugin_transport_https_client_la_SOURCES) \ + $(libgnunet_plugin_transport_https_server_la_SOURCES) \ $(libgnunet_plugin_transport_tcp_la_SOURCES) \ $(libgnunet_plugin_transport_template_la_SOURCES) \ $(libgnunet_plugin_transport_udp_la_SOURCES) \ @@ -841,7 +1048,14 @@ DIST_SOURCES = $(libgnunet_plugin_transport_http_la_SOURCES) \ $(gnunet_service_transport_SOURCES) \ $(gnunet_transport_SOURCES) \ $(gnunet_transport_certificate_creation_SOURCES) \ + $(gnunet_transport_wlan_receiver_SOURCES) \ $(gnunet_transport_wlan_sender_SOURCES) \ + $(test_http_common_SOURCES) $(test_plugin_http_client_SOURCES) \ + $(test_plugin_http_server_SOURCES) \ + $(test_plugin_https_client_SOURCES) \ + $(test_plugin_https_server_SOURCES) $(test_plugin_tcp_SOURCES) \ + $(test_plugin_udp_SOURCES) $(test_plugin_unix_SOURCES) \ + $(test_plugin_wlan_SOURCES) \ $(test_quota_compliance_http_SOURCES) \ $(test_quota_compliance_http_asymmetric_SOURCES) \ $(test_quota_compliance_https_SOURCES) \ @@ -851,19 +1065,20 @@ DIST_SOURCES = $(libgnunet_plugin_transport_http_la_SOURCES) \ $(test_quota_compliance_udp_SOURCES) \ $(test_quota_compliance_unix_SOURCES) \ $(test_quota_compliance_unix_asymmetric_SOURCES) \ + $(test_quota_compliance_wlan_SOURCES) \ + $(test_quota_compliance_wlan_asymmetric_SOURCES) \ $(test_transport_api_bidirectional_connect_SOURCES) \ $(test_transport_api_blacklisting_SOURCES) \ $(test_transport_api_disconnect_tcp_SOURCES) \ $(test_transport_api_http_SOURCES) \ - $(test_transport_api_http_nat_SOURCES) \ + $(test_transport_api_http_reverse_SOURCES) \ $(test_transport_api_https_SOURCES) \ - $(test_transport_api_https_nat_SOURCES) \ $(test_transport_api_limited_sockets_tcp_SOURCES) \ + $(test_transport_api_manipulation_recv_tcp_SOURCES) \ + $(test_transport_api_manipulation_send_tcp_SOURCES) \ $(test_transport_api_multi_SOURCES) \ $(test_transport_api_reliability_http_SOURCES) \ - $(test_transport_api_reliability_http_nat_SOURCES) \ $(test_transport_api_reliability_https_SOURCES) \ - $(test_transport_api_reliability_https_nat_SOURCES) \ $(test_transport_api_reliability_tcp_SOURCES) \ $(test_transport_api_reliability_tcp_nat_SOURCES) \ $(test_transport_api_reliability_wlan_SOURCES) \ @@ -885,7 +1100,14 @@ DIST_SOURCES = $(libgnunet_plugin_transport_http_la_SOURCES) \ $(test_transport_api_unreliability_wlan_SOURCES) \ $(am__test_transport_api_wlan_SOURCES_DIST) \ $(test_transport_startonly_SOURCES) \ - $(test_transport_testing_SOURCES) + $(test_transport_testing_SOURCES) \ + $(test_transport_testing_restart_SOURCES) \ + $(test_transport_testing_startstop_SOURCES) +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac DATA = $(pkgcfg_DATA) ETAGS = etags CTAGS = ctags @@ -927,6 +1149,10 @@ EXEEXT = @EXEEXT@ EXT_LIBS = @EXT_LIBS@ EXT_LIB_PATH = @EXT_LIB_PATH@ FGREP = @FGREP@ +GLIB_CFLAGS = @GLIB_CFLAGS@ +GLIB_GENMARSHAL = @GLIB_GENMARSHAL@ +GLIB_LIBS = @GLIB_LIBS@ +GLIB_MKENUMS = @GLIB_MKENUMS@ GMSGFMT = @GMSGFMT@ GMSGFMT_015 = @GMSGFMT_015@ GNUNETDNS_GROUP = @GNUNETDNS_GROUP@ @@ -937,6 +1163,7 @@ GN_LIBINTL = @GN_LIBINTL@ GN_LIB_LDFLAGS = @GN_LIB_LDFLAGS@ GN_PLUGIN_LDFLAGS = @GN_PLUGIN_LDFLAGS@ GN_USER_HOME_DIR = @GN_USER_HOME_DIR@ +GOBJECT_QUERY = @GOBJECT_QUERY@ GREP = @GREP@ HAVE_LIBUNISTRING = @HAVE_LIBUNISTRING@ INCLTDL = @INCLTDL@ @@ -959,6 +1186,8 @@ LIBCURL_CPPFLAGS = @LIBCURL_CPPFLAGS@ LIBGCRYPT_CFLAGS = @LIBGCRYPT_CFLAGS@ LIBGCRYPT_CONFIG = @LIBGCRYPT_CONFIG@ LIBGCRYPT_LIBS = @LIBGCRYPT_LIBS@ +LIBGTOP_CFLAGS = @LIBGTOP_CFLAGS@ +LIBGTOP_LIBS = @LIBGTOP_LIBS@ LIBICONV = @LIBICONV@ LIBINTL = @LIBINTL@ LIBLTDL = @LIBLTDL@ @@ -980,6 +1209,7 @@ LT_CONFIG_H = @LT_CONFIG_H@ LT_DLLOADERS = @LT_DLLOADERS@ LT_DLPREOPEN = @LT_DLPREOPEN@ MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ MKDIR_P = @MKDIR_P@ MONKEYPREFIX = @MONKEYPREFIX@ MSGFMT = @MSGFMT@ @@ -989,6 +1219,7 @@ MYSQL_CPPFLAGS = @MYSQL_CPPFLAGS@ MYSQL_LDFLAGS = @MYSQL_LDFLAGS@ NM = @NM@ NMEDIT = @NMEDIT@ +NSS_DIR = @NSS_DIR@ OBJC = @OBJC@ OBJCDEPMODE = @OBJCDEPMODE@ OBJCFLAGS = @OBJCFLAGS@ @@ -1004,6 +1235,7 @@ PACKAGE_TARNAME = @PACKAGE_TARNAME@ PACKAGE_URL = @PACKAGE_URL@ PACKAGE_VERSION = @PACKAGE_VERSION@ PATH_SEPARATOR = @PATH_SEPARATOR@ +PKG_CONFIG = @PKG_CONFIG@ POSTGRES_CPPFLAGS = @POSTGRES_CPPFLAGS@ POSTGRES_LDFLAGS = @POSTGRES_LDFLAGS@ POSUB = @POSUB@ @@ -1035,6 +1267,7 @@ abs_builddir = @abs_builddir@ abs_srcdir = @abs_srcdir@ abs_top_builddir = @abs_top_builddir@ abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ ac_ct_CC = @ac_ct_CC@ ac_ct_CXX = @ac_ct_CXX@ ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ @@ -1057,6 +1290,7 @@ datarootdir = @datarootdir@ docdir = @docdir@ dvidir = @dvidir@ exec_prefix = @exec_prefix@ +gitcommand = @gitcommand@ host = @host@ host_alias = @host_alias@ host_cpu = @host_cpu@ @@ -1067,10 +1301,9 @@ includedir = @includedir@ infodir = @infodir@ install_sh = @install_sh@ libdir = @libdir@ -libexecdir = @libexecdir@ +libexecdir = $(pkglibdir)/libexec/ localedir = @localedir@ localstatedir = @localstatedir@ -lt_ECHO = @lt_ECHO@ ltdl_LIBOBJS = @ltdl_LIBOBJS@ ltdl_LTLIBOBJS = @ltdl_LTLIBOBJS@ mandir = @mandir@ @@ -1088,6 +1321,7 @@ sbindir = @sbindir@ sharedstatedir = @sharedstatedir@ srcdir = @srcdir@ subdirs = @subdirs@ +svnversioncommand = @svnversioncommand@ sys_symbol_underscore = @sys_symbol_underscore@ sysconfdir = @sysconfdir@ target = @target@ @@ -1105,40 +1339,48 @@ pkgcfg_DATA = \ transport.conf @HAVE_MHD_TRUE@GN_LIBMHD = -lmicrohttpd -@HAVE_MHD_TRUE@HTTP_PLUGIN_LA = libgnunet_plugin_transport_http.la -@HAVE_MHD_TRUE@HTTP_API_TEST = test_transport_api_http -@HAVE_MHD_TRUE@HTTP_NAT_API_TEST = test_transport_api_http_nat -@HAVE_MHD_TRUE@HTTP_API_TIMEOUT_TEST = test_transport_api_timeout_http -@HAVE_MHD_TRUE@HTTP_REL_TEST = test_transport_api_reliability_http -@HAVE_MHD_TRUE@HTTP_NAT_REL_TEST = test_transport_api_reliability_http_nat -@HAVE_MHD_TRUE@HTTP_QUOTA_TEST = test_quota_compliance_http \ -@HAVE_MHD_TRUE@ test_quota_compliance_http_asymmetric - -@HAVE_MHD_TRUE@HTTPS_PLUGIN_LA = libgnunet_plugin_transport_https.la -@HAVE_MHD_TRUE@HTTPS_API_TEST = test_transport_api_https -@HAVE_MHD_TRUE@HTTPS_NAT_API_TEST = test_transport_api_https_nat -@HAVE_MHD_TRUE@HTTPS_API_TIMEOUT_TEST = test_transport_api_timeout_https -@HAVE_MHD_TRUE@HTTPS_REL_TEST = test_transport_api_reliability_https -@HAVE_MHD_TRUE@HTTPS_NAT_REL_TEST = test_transport_api_reliability_https_nat -@HAVE_MHD_TRUE@HTTPS_QUOTA_TEST = test_quota_compliance_https \ -@HAVE_MHD_TRUE@ test_quota_compliance_https_asymmetric +@HAVE_MHD_TRUE@HTTP_SERVER_PLUGIN_LA = libgnunet_plugin_transport_http_server.la +@HAVE_MHD_TRUE@HTTPS_SERVER_PLUGIN_LA = libgnunet_plugin_transport_https_server.la +@HAVE_MHD_TRUE@HTTP_SERVER_PLUGIN_TEST = test_plugin_http_server +@HAVE_MHD_TRUE@HTTPS_SERVER_PLUGIN_TEST = test_plugin_https_server +@HAVE_LIBCURL_TRUE@HTTP_CLIENT_PLUGIN_TEST = test_plugin_http_client +@HAVE_LIBCURL_TRUE@HTTPS_CLIENT_PLUGIN_TEST = test_plugin_https_client +@HAVE_LIBCURL_TRUE@HTTP_CLIENT_PLUGIN_LA = libgnunet_plugin_transport_http_client.la +@HAVE_LIBCURL_TRUE@HTTPS_CLIENT_PLUGIN_LA = libgnunet_plugin_transport_https_client.la +@HAVE_LIBCURL_TRUE@@HAVE_MHD_TRUE@HTTP_API_TEST = test_transport_api_http +@HAVE_LIBCURL_TRUE@@HAVE_MHD_TRUE@HTTP_REVERSE_API_TEST = test_transport_api_http_reverse +@HAVE_LIBCURL_TRUE@@HAVE_MHD_TRUE@HTTP_API_TIMEOUT_TEST = test_transport_api_timeout_http +@HAVE_LIBCURL_TRUE@@HAVE_MHD_TRUE@HTTP_REL_TEST = test_transport_api_reliability_http +@HAVE_LIBCURL_TRUE@@HAVE_MHD_TRUE@HTTP_QUOTA_TEST = test_quota_compliance_http \ +@HAVE_LIBCURL_TRUE@@HAVE_MHD_TRUE@ test_quota_compliance_http_asymmetric + +@HAVE_LIBCURL_TRUE@@HAVE_MHD_TRUE@HTTPS_API_TEST = test_transport_api_https +@HAVE_LIBCURL_TRUE@@HAVE_MHD_TRUE@HTTPS_API_TIMEOUT_TEST = test_transport_api_timeout_https +@HAVE_LIBCURL_TRUE@@HAVE_MHD_TRUE@HTTPS_REL_TEST = test_transport_api_reliability_https +@HAVE_LIBCURL_TRUE@@HAVE_MHD_TRUE@HTTPS_QUOTA_TEST = test_quota_compliance_https \ +@HAVE_LIBCURL_TRUE@@HAVE_MHD_TRUE@ test_quota_compliance_https_asymmetric @USE_COVERAGE_TRUE@AM_CFLAGS = --coverage -O0 @LINUX_TRUE@WLAN_BIN = gnunet-helper-transport-wlan @LINUX_TRUE@WLAN_BIN_DUMMY = gnunet-helper-transport-wlan-dummy @LINUX_TRUE@WLAN_BIN_SENDER = gnunet-transport-wlan-sender +@LINUX_TRUE@WLAN_BIN_RECEIVER = gnunet-transport-wlan-receiver @LINUX_TRUE@WLAN_PLUGIN_LA = libgnunet_plugin_transport_wlan.la +@LINUX_TRUE@WLAN_PLUGIN_TEST = test_plugin_wlan @LINUX_TRUE@WLAN_API_TEST = test_transport_api_wlan @LINUX_TRUE@WLAN_REL_TEST = test_transport_api_reliability_wlan @LINUX_TRUE@WLAN_UREL_TEST = test_transport_api_unreliability_wlan +@LINUX_TRUE@WLAN_QUOTA_TEST = test_quota_compliance_wlan \ +@LINUX_TRUE@ test_quota_compliance_wlan_asymmetric + @MINGW_FALSE@UNIX_PLUGIN_LA = libgnunet_plugin_transport_unix.la @MINGW_FALSE@UNIX_PLUGIN_TEST = test_transport_api_unix +@MINGW_FALSE@UNIX_TEST = test_plugin_unix @MINGW_FALSE@UNIX_PLUGIN_TIMEOUT_TEST = test_transport_api_timeout_unix @MINGW_FALSE@UNIX_REL_TEST = test_transport_api_unreliability_unix @MINGW_FALSE@UNIX_QUOTA_TEST = test_quota_compliance_unix \ @MINGW_FALSE@ test_quota_compliance_unix_asymmetric -# gnunet-transport-connect-running-peers lib_LTLIBRARIES = \ libgnunettransport.la \ libgnunettransporttesting.la @@ -1150,6 +1392,7 @@ libgnunettransporttesting_la_LIBADD = \ $(top_builddir)/src/transport/libgnunettransport.la \ $(top_builddir)/src/hello/libgnunethello.la \ $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/testing/libgnunettesting.la \ $(GN_LIBINTL) libgnunettransporttesting_la_DEPENDENCIES = \ @@ -1171,7 +1414,7 @@ libgnunettransport_la_LIBADD = \ libgnunettransport_la_LDFLAGS = \ $(GN_LIB_LDFLAGS) $(WINFLAGS) \ - -version-info 1:0:0 + -version-info 3:0:1 #bin_SCRIPTS = \ @@ -1197,6 +1440,12 @@ gnunet_transport_wlan_sender_SOURCES = \ gnunet_transport_wlan_sender_LDADD = \ $(top_builddir)/src/util/libgnunetutil.la +gnunet_transport_wlan_receiver_SOURCES = \ + gnunet-transport-wlan-receiver.c + +gnunet_transport_wlan_receiver_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la + gnunet_transport_SOURCES = \ gnunet-transport.c @@ -1217,7 +1466,8 @@ gnunet_service_transport_SOURCES = \ gnunet-service-transport_hello.h gnunet-service-transport_hello.c \ gnunet-service-transport_neighbours.h gnunet-service-transport_neighbours.c \ gnunet-service-transport_plugins.h gnunet-service-transport_plugins.c \ - gnunet-service-transport_validation.h gnunet-service-transport_validation.c + gnunet-service-transport_validation.h gnunet-service-transport_validation.c \ + gnunet-service-transport_manipulation.h gnunet-service-transport_manipulation.c gnunet_service_transport_LDADD = \ $(top_builddir)/src/ats/libgnunetats.la \ @@ -1228,12 +1478,18 @@ gnunet_service_transport_LDADD = \ $(GN_GLPK) \ $(GN_LIBINTL) +gnunet_service_transport_CFLAGS = \ + $(CFLAGS) + +# -DANALYZE plugin_LTLIBRARIES = \ libgnunet_plugin_transport_tcp.la \ libgnunet_plugin_transport_udp.la \ $(UNIX_PLUGIN_LA) \ - $(HTTP_PLUGIN_LA) \ - $(HTTPS_PLUGIN_LA) \ + $(HTTP_CLIENT_PLUGIN_LA) \ + $(HTTPS_CLIENT_PLUGIN_LA) \ + $(HTTP_SERVER_PLUGIN_LA) \ + $(HTTPS_SERVER_PLUGIN_LA) \ $(WLAN_PLUGIN_LA) \ libgnunet_plugin_transport_template.la @@ -1245,7 +1501,8 @@ libgnunet_plugin_transport_tcp_la_LIBADD = \ $(top_builddir)/src/statistics/libgnunetstatistics.la \ $(top_builddir)/src/peerinfo/libgnunetpeerinfo.la \ $(top_builddir)/src/nat/libgnunetnat.la \ - $(top_builddir)/src/util/libgnunetutil.la + $(top_builddir)/src/util/libgnunetutil.la \ + $(LTLIBINTL) libgnunet_plugin_transport_tcp_la_LDFLAGS = \ $(GN_PLUGIN_LDFLAGS) @@ -1254,7 +1511,8 @@ libgnunet_plugin_transport_template_la_SOURCES = \ plugin_transport_template.c libgnunet_plugin_transport_template_la_LIBADD = \ - $(top_builddir)/src/util/libgnunetutil.la + $(top_builddir)/src/util/libgnunetutil.la \ + $(LTLIBINTL) libgnunet_plugin_transport_template_la_LDFLAGS = \ $(GN_PLUGIN_LDFLAGS) @@ -1282,7 +1540,8 @@ libgnunet_plugin_transport_udp_la_LIBADD = \ $(top_builddir)/src/statistics/libgnunetstatistics.la \ $(top_builddir)/src/peerinfo/libgnunetpeerinfo.la \ $(top_builddir)/src/nat/libgnunetnat.la \ - $(top_builddir)/src/util/libgnunetutil.la + $(top_builddir)/src/util/libgnunetutil.la \ + $(LTLIBINTL) libgnunet_plugin_transport_udp_la_LDFLAGS = \ $(GN_PLUGIN_LDFLAGS) @@ -1294,16 +1553,16 @@ libgnunet_plugin_transport_unix_la_LIBADD = \ $(top_builddir)/src/hello/libgnunethello.la \ $(top_builddir)/src/statistics/libgnunetstatistics.la \ $(top_builddir)/src/peerinfo/libgnunetpeerinfo.la \ - $(top_builddir)/src/util/libgnunetutil.la + $(top_builddir)/src/util/libgnunetutil.la \ + $(LTLIBINTL) libgnunet_plugin_transport_unix_la_LDFLAGS = \ $(GN_PLUGIN_LDFLAGS) -libgnunet_plugin_transport_http_la_SOURCES = \ - plugin_transport_http.c plugin_transport_http.h \ - plugin_transport_http_client.c plugin_transport_http_server.c +libgnunet_plugin_transport_http_client_la_SOURCES = \ + plugin_transport_http_client.c plugin_transport_http_common.c plugin_transport_http_common.h -libgnunet_plugin_transport_http_la_LIBADD = \ +libgnunet_plugin_transport_http_client_la_LIBADD = \ $(top_builddir)/src/hello/libgnunethello.la \ $(top_builddir)/src/statistics/libgnunetstatistics.la \ $(top_builddir)/src/peerinfo/libgnunetpeerinfo.la \ @@ -1311,38 +1570,87 @@ libgnunet_plugin_transport_http_la_LIBADD = \ $(top_builddir)/src/nat/libgnunetnat.la \ $(top_builddir)/src/util/libgnunetutil.la -libgnunet_plugin_transport_http_la_LDFLAGS = \ - $(GN_LIBMHD) \ +libgnunet_plugin_transport_http_client_la_LDFLAGS = \ $(GN_PLUGIN_LDFLAGS) -libgnunet_plugin_transport_http_la_CFLAGS = \ +libgnunet_plugin_transport_http_client_la_CFLAGS = \ $(CFLAGS) -libgnunet_plugin_transport_http_la_CPPFLAGS = \ +libgnunet_plugin_transport_http_client_la_CPPFLAGS = \ @LIBCURL_CPPFLAGS@ -libgnunet_plugin_transport_https_la_SOURCES = \ - plugin_transport_http.c plugin_transport_http.h \ - plugin_transport_http_client.c plugin_transport_http_server.c +libgnunet_plugin_transport_http_server_la_SOURCES = \ + plugin_transport_http_server.c plugin_transport_http_common.c -libgnunet_plugin_transport_https_la_LIBADD = \ +libgnunet_plugin_transport_http_server_la_LIBADD = \ $(top_builddir)/src/hello/libgnunethello.la \ $(top_builddir)/src/statistics/libgnunetstatistics.la \ $(top_builddir)/src/peerinfo/libgnunetpeerinfo.la \ - @LIBCURL@ \ $(top_builddir)/src/nat/libgnunetnat.la \ $(top_builddir)/src/util/libgnunetutil.la -libgnunet_plugin_transport_https_la_LDFLAGS = \ +libgnunet_plugin_transport_http_server_la_LDFLAGS = \ $(GN_LIBMHD) \ $(GN_PLUGIN_LDFLAGS) -libgnunet_plugin_transport_https_la_CFLAGS = \ +libgnunet_plugin_transport_http_server_la_CFLAGS = \ + $(CFLAGS) + +libgnunet_plugin_transport_https_client_la_SOURCES = \ + plugin_transport_http_client.c plugin_transport_http_common.c + +libgnunet_plugin_transport_https_client_la_LIBADD = \ + $(top_builddir)/src/hello/libgnunethello.la \ + $(top_builddir)/src/statistics/libgnunetstatistics.la \ + $(top_builddir)/src/peerinfo/libgnunetpeerinfo.la \ + @LIBCURL@ \ + $(top_builddir)/src/nat/libgnunetnat.la \ + $(top_builddir)/src/util/libgnunetutil.la + +libgnunet_plugin_transport_https_client_la_LDFLAGS = \ + $(GN_PLUGIN_LDFLAGS) + +libgnunet_plugin_transport_https_client_la_CFLAGS = \ $(CFLAGS) -DBUILD_HTTPS -libgnunet_plugin_transport_https_la_CPPFLAGS = \ +libgnunet_plugin_transport_https_client_la_CPPFLAGS = \ @LIBCURL_CPPFLAGS@ +libgnunet_plugin_transport_https_server_la_SOURCES = \ + plugin_transport_http_server.c plugin_transport_http_common.c + +libgnunet_plugin_transport_https_server_la_LIBADD = \ + $(top_builddir)/src/hello/libgnunethello.la \ + $(top_builddir)/src/statistics/libgnunetstatistics.la \ + $(top_builddir)/src/peerinfo/libgnunetpeerinfo.la \ + $(top_builddir)/src/nat/libgnunetnat.la \ + $(top_builddir)/src/util/libgnunetutil.la + +libgnunet_plugin_transport_https_server_la_LDFLAGS = \ + $(GN_LIBMHD) \ + $(GN_PLUGIN_LDFLAGS) + +libgnunet_plugin_transport_https_server_la_CFLAGS = \ + $(CFLAGS) -DBUILD_HTTPS + +test_transport_testing_startstop_SOURCES = \ + test_transport_testing_startstop.c + +test_transport_testing_startstop_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/transport/libgnunettransport.la \ + $(top_builddir)/src/hello/libgnunethello.la \ + $(top_builddir)/src/transport/libgnunettransporttesting.la + +test_transport_testing_restart_SOURCES = \ + test_transport_testing_restart.c + +test_transport_testing_restart_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/transport/libgnunettransport.la \ + $(top_builddir)/src/hello/libgnunethello.la \ + $(top_builddir)/src/transport/libgnunettransporttesting.la + test_transport_testing_SOURCES = \ test_transport_testing.c @@ -1352,14 +1660,6 @@ test_transport_testing_LDADD = \ $(top_builddir)/src/hello/libgnunethello.la \ $(top_builddir)/src/transport/libgnunettransporttesting.la - -#gnunet_transport_connect_running_peers_SOURCES = \ -# gnunet-transport-connect-running-peers.c -#gnunet_transport_connect_running_peers_LDADD = \ -# $(top_builddir)/src/transport/libgnunettransport.la \ -# $(top_builddir)/src/hello/libgnunethello.la \ -# $(top_builddir)/src/util/libgnunetutil.la \ -# $(top_builddir)/src/transport/libgnunettransporttesting.la test_transport_api_blacklisting_SOURCES = \ test_transport_api_blacklisting.c @@ -1390,6 +1690,96 @@ test_transport_startonly_LDADD = \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/transport/libgnunettransporttesting.la +test_plugin_tcp_SOURCES = \ + test_plugin_transport.c + +test_plugin_tcp_LDADD = \ + $(top_builddir)/src/transport/libgnunettransport.la \ + $(top_builddir)/src/statistics/libgnunetstatistics.la \ + $(top_builddir)/src/hello/libgnunethello.la \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/transport/libgnunettransporttesting.la + +test_plugin_udp_SOURCES = \ + test_plugin_transport.c + +test_plugin_udp_LDADD = \ + $(top_builddir)/src/transport/libgnunettransport.la \ + $(top_builddir)/src/statistics/libgnunetstatistics.la \ + $(top_builddir)/src/hello/libgnunethello.la \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/transport/libgnunettransporttesting.la + +test_plugin_unix_SOURCES = \ + test_plugin_transport.c + +test_plugin_unix_LDADD = \ + $(top_builddir)/src/transport/libgnunettransport.la \ + $(top_builddir)/src/statistics/libgnunetstatistics.la \ + $(top_builddir)/src/hello/libgnunethello.la \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/transport/libgnunettransporttesting.la + +test_plugin_wlan_SOURCES = \ + test_plugin_transport.c + +test_plugin_wlan_LDADD = \ + $(top_builddir)/src/transport/libgnunettransport.la \ + $(top_builddir)/src/statistics/libgnunetstatistics.la \ + $(top_builddir)/src/hello/libgnunethello.la \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/transport/libgnunettransporttesting.la + +test_http_common_SOURCES = \ + test_http_common.c plugin_transport_http_common.c + +test_http_common_LDADD = \ + $(top_builddir)/src/transport/libgnunettransport.la \ + $(top_builddir)/src/statistics/libgnunetstatistics.la \ + $(top_builddir)/src/hello/libgnunethello.la \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/transport/libgnunettransporttesting.la + +test_plugin_http_server_SOURCES = \ + test_plugin_transport.c + +test_plugin_http_server_LDADD = \ + $(top_builddir)/src/transport/libgnunettransport.la \ + $(top_builddir)/src/statistics/libgnunetstatistics.la \ + $(top_builddir)/src/hello/libgnunethello.la \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/transport/libgnunettransporttesting.la + +test_plugin_https_server_SOURCES = \ + test_plugin_transport.c + +test_plugin_https_server_LDADD = \ + $(top_builddir)/src/transport/libgnunettransport.la \ + $(top_builddir)/src/statistics/libgnunetstatistics.la \ + $(top_builddir)/src/hello/libgnunethello.la \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/transport/libgnunettransporttesting.la + +test_plugin_http_client_SOURCES = \ + test_plugin_transport.c + +test_plugin_http_client_LDADD = \ + $(top_builddir)/src/transport/libgnunettransport.la \ + $(top_builddir)/src/statistics/libgnunetstatistics.la \ + $(top_builddir)/src/hello/libgnunethello.la \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/transport/libgnunettransporttesting.la + +test_plugin_https_client_SOURCES = \ + test_plugin_transport.c + +test_plugin_https_client_LDADD = \ + $(top_builddir)/src/transport/libgnunettransport.la \ + $(top_builddir)/src/statistics/libgnunetstatistics.la \ + $(top_builddir)/src/hello/libgnunethello.la \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/transport/libgnunettransporttesting.la + test_transport_api_tcp_SOURCES = \ test_transport_api.c @@ -1446,46 +1836,46 @@ test_transport_api_tcp_nat_LDADD = \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/transport/libgnunettransporttesting.la -test_transport_api_reliability_tcp_SOURCES = \ - test_transport_api_reliability.c +test_transport_api_manipulation_send_tcp_SOURCES = \ + test_transport_api_manipulation_send_tcp.c -test_transport_api_reliability_tcp_LDADD = \ +test_transport_api_manipulation_send_tcp_LDADD = \ $(top_builddir)/src/transport/libgnunettransport.la \ $(top_builddir)/src/hello/libgnunethello.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/transport/libgnunettransporttesting.la -test_transport_api_timeout_tcp_SOURCES = \ - test_transport_api_timeout.c +test_transport_api_manipulation_recv_tcp_SOURCES = \ + test_transport_api_manipulation_recv_tcp.c -test_transport_api_timeout_tcp_LDADD = \ +test_transport_api_manipulation_recv_tcp_LDADD = \ $(top_builddir)/src/transport/libgnunettransport.la \ $(top_builddir)/src/hello/libgnunethello.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/transport/libgnunettransporttesting.la -test_transport_api_timeout_unix_SOURCES = \ - test_transport_api_timeout.c +test_transport_api_reliability_tcp_SOURCES = \ + test_transport_api_reliability.c -test_transport_api_timeout_unix_LDADD = \ +test_transport_api_reliability_tcp_LDADD = \ $(top_builddir)/src/transport/libgnunettransport.la \ $(top_builddir)/src/hello/libgnunethello.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/transport/libgnunettransporttesting.la -test_transport_api_timeout_http_SOURCES = \ +test_transport_api_timeout_tcp_SOURCES = \ test_transport_api_timeout.c -test_transport_api_timeout_http_LDADD = \ +test_transport_api_timeout_tcp_LDADD = \ $(top_builddir)/src/transport/libgnunettransport.la \ $(top_builddir)/src/hello/libgnunethello.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/transport/libgnunettransporttesting.la -test_transport_api_timeout_https_SOURCES = \ +test_transport_api_timeout_unix_SOURCES = \ test_transport_api_timeout.c -test_transport_api_timeout_https_LDADD = \ +test_transport_api_timeout_unix_LDADD = \ $(top_builddir)/src/transport/libgnunettransport.la \ $(top_builddir)/src/hello/libgnunethello.la \ $(top_builddir)/src/util/libgnunetutil.la \ @@ -1554,6 +1944,8 @@ test_transport_api_unix_LDADD = \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/transport/libgnunettransporttesting.la + +# HTTP tests test_transport_api_http_SOURCES = \ test_transport_api.c @@ -1561,16 +1953,25 @@ test_transport_api_http_LDADD = \ $(top_builddir)/src/transport/libgnunettransport.la \ $(top_builddir)/src/hello/libgnunethello.la \ $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/transport/libgnunettransporttesting.la + $(top_builddir)/src/transport/libgnunettransporttesting.la -test_transport_api_http_nat_SOURCES = \ +test_transport_api_http_reverse_SOURCES = \ test_transport_api.c -test_transport_api_http_nat_LDADD = \ +test_transport_api_http_reverse_LDADD = \ $(top_builddir)/src/transport/libgnunettransport.la \ $(top_builddir)/src/hello/libgnunethello.la \ $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/transport/libgnunettransporttesting.la + $(top_builddir)/src/transport/libgnunettransporttesting.la + +test_transport_api_timeout_http_SOURCES = \ + test_transport_api_timeout.c + +test_transport_api_timeout_http_LDADD = \ + $(top_builddir)/src/transport/libgnunettransport.la \ + $(top_builddir)/src/hello/libgnunethello.la \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/transport/libgnunettransporttesting.la test_transport_api_reliability_http_SOURCES = \ test_transport_api_reliability.c @@ -1581,15 +1982,44 @@ test_transport_api_reliability_http_LDADD = \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/transport/libgnunettransporttesting.la -test_transport_api_reliability_http_nat_SOURCES = \ - test_transport_api_reliability.c +test_quota_compliance_http_SOURCES = \ + test_quota_compliance.c -test_transport_api_reliability_http_nat_LDADD = \ +test_quota_compliance_http_LDADD = \ $(top_builddir)/src/transport/libgnunettransport.la \ $(top_builddir)/src/hello/libgnunethello.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/transport/libgnunettransporttesting.la +test_quota_compliance_http_asymmetric_SOURCES = \ + test_quota_compliance.c + +test_quota_compliance_http_asymmetric_LDADD = \ + $(top_builddir)/src/transport/libgnunettransport.la \ + $(top_builddir)/src/hello/libgnunethello.la \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/transport/libgnunettransporttesting.la + +test_quota_compliance_https_SOURCES = \ + test_quota_compliance.c + +test_quota_compliance_https_LDADD = \ + $(top_builddir)/src/transport/libgnunettransport.la \ + $(top_builddir)/src/hello/libgnunethello.la \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/transport/libgnunettransporttesting.la + +test_quota_compliance_https_asymmetric_SOURCES = \ + test_quota_compliance.c + +test_quota_compliance_https_asymmetric_LDADD = \ + $(top_builddir)/src/transport/libgnunettransport.la \ + $(top_builddir)/src/hello/libgnunethello.la \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(top_builddir)/src/transport/libgnunettransporttesting.la + + +# HTTPS tests test_transport_api_https_SOURCES = \ test_transport_api.c @@ -1599,14 +2029,14 @@ test_transport_api_https_LDADD = \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/transport/libgnunettransporttesting.la -test_transport_api_https_nat_SOURCES = \ - test_transport_api.c +test_transport_api_timeout_https_SOURCES = \ + test_transport_api_timeout.c -test_transport_api_https_nat_LDADD = \ +test_transport_api_timeout_https_LDADD = \ $(top_builddir)/src/transport/libgnunettransport.la \ $(top_builddir)/src/hello/libgnunethello.la \ $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/transport/libgnunettransporttesting.la + $(top_builddir)/src/transport/libgnunettransporttesting.la test_transport_api_reliability_https_SOURCES = \ test_transport_api_reliability.c @@ -1617,15 +2047,6 @@ test_transport_api_reliability_https_LDADD = \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/transport/libgnunettransporttesting.la -test_transport_api_reliability_https_nat_SOURCES = \ - test_transport_api_reliability.c - -test_transport_api_reliability_https_nat_LDADD = \ - $(top_builddir)/src/transport/libgnunettransport.la \ - $(top_builddir)/src/hello/libgnunethello.la \ - $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/transport/libgnunettransporttesting.la - test_transport_api_unreliability_unix_SOURCES = \ test_transport_api_unreliability.c @@ -1680,82 +2101,46 @@ test_quota_compliance_tcp_asymmetric_LDADD = \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/transport/libgnunettransporttesting.la - -#test_quota_compliance_tcp_asymmetric_send_constant_SOURCES = \ -# test_quota_compliance.c -#test_quota_compliance_tcp_asymmetric_send_constant_LDADD = \ -# $(top_builddir)/src/transport/libgnunettransport.la \ -# $(top_builddir)/src/util/libgnunetutil.la -test_quota_compliance_http_SOURCES = \ - test_quota_compliance.c - -test_quota_compliance_http_LDADD = \ - $(top_builddir)/src/transport/libgnunettransport.la \ - $(top_builddir)/src/hello/libgnunethello.la \ - $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/transport/libgnunettransporttesting.la - -test_quota_compliance_http_asymmetric_SOURCES = \ - test_quota_compliance.c - -test_quota_compliance_http_asymmetric_LDADD = \ - $(top_builddir)/src/transport/libgnunettransport.la \ - $(top_builddir)/src/hello/libgnunethello.la \ - $(top_builddir)/src/util/libgnunetutil.la \ - $(top_builddir)/src/transport/libgnunettransporttesting.la - - -#test_quota_compliance_http_asymmetric_send_constant_SOURCES = \ -# test_quota_compliance.c -#test_quota_compliance_http_asymmetric_send_constant_LDADD = \ -# $(top_builddir)/src/transport/libgnunettransport.la \ -# $(top_builddir)/src/util/libgnunetutil.la -test_quota_compliance_https_SOURCES = \ +test_quota_compliance_udp_SOURCES = \ test_quota_compliance.c -test_quota_compliance_https_LDADD = \ +test_quota_compliance_udp_LDADD = \ $(top_builddir)/src/transport/libgnunettransport.la \ $(top_builddir)/src/hello/libgnunethello.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/transport/libgnunettransporttesting.la -test_quota_compliance_https_asymmetric_SOURCES = \ +test_quota_compliance_unix_SOURCES = \ test_quota_compliance.c -test_quota_compliance_https_asymmetric_LDADD = \ +test_quota_compliance_unix_LDADD = \ $(top_builddir)/src/transport/libgnunettransport.la \ $(top_builddir)/src/hello/libgnunethello.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/transport/libgnunettransporttesting.la - -#test_quota_compliance_https_asymmetric_send_constant_SOURCES = \ -# test_quota_compliance.c -#test_quota_compliance_https_asymmetric_send_constant_LDADD = \ -# $(top_builddir)/src/transport/libgnunettransport.la \ -# $(top_builddir)/src/util/libgnunetutil.la -test_quota_compliance_udp_SOURCES = \ +test_quota_compliance_unix_asymmetric_SOURCES = \ test_quota_compliance.c -test_quota_compliance_udp_LDADD = \ +test_quota_compliance_unix_asymmetric_LDADD = \ $(top_builddir)/src/transport/libgnunettransport.la \ $(top_builddir)/src/hello/libgnunethello.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/transport/libgnunettransporttesting.la -test_quota_compliance_unix_SOURCES = \ +test_quota_compliance_wlan_SOURCES = \ test_quota_compliance.c -test_quota_compliance_unix_LDADD = \ +test_quota_compliance_wlan_LDADD = \ $(top_builddir)/src/transport/libgnunettransport.la \ $(top_builddir)/src/hello/libgnunethello.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/transport/libgnunettransporttesting.la -test_quota_compliance_unix_asymmetric_SOURCES = \ +test_quota_compliance_wlan_asymmetric_SOURCES = \ test_quota_compliance.c -test_quota_compliance_unix_asymmetric_LDADD = \ +test_quota_compliance_wlan_asymmetric_LDADD = \ $(top_builddir)/src/transport/libgnunettransport.la \ $(top_builddir)/src/hello/libgnunethello.la \ $(top_builddir)/src/util/libgnunetutil.la \ @@ -1771,7 +2156,8 @@ test_transport_api_multi_LDADD = \ $(top_builddir)/src/transport/libgnunettransporttesting.la EXTRA_DIST = \ -gnunet-transport-certificate-creation \ +test_plugin_hostkey \ +test_plugin_hostkey.ecc \ template_cfg_peer1.conf\ template_cfg_peer2.conf\ test_plugin_transport_data.conf\ @@ -1787,6 +2173,8 @@ test_quota_compliance_udp_peer1.conf\ test_quota_compliance_udp_peer2.conf\ test_quota_compliance_unix_peer1.conf\ test_quota_compliance_unix_peer2.conf\ +test_quota_compliance_wlan_peer1.conf\ +test_quota_compliance_wlan_peer2.conf\ test_quota_compliance_http_asymmetric_peer1.conf\ test_quota_compliance_http_asymmetric_peer2.conf\ test_quota_compliance_https_asymmetric_peer1.conf\ @@ -1795,6 +2183,8 @@ test_quota_compliance_tcp_asymmetric_peer1.conf\ test_quota_compliance_tcp_asymmetric_peer2.conf\ test_quota_compliance_unix_asymmetric_peer1.conf\ test_quota_compliance_unix_asymmetric_peer2.conf\ +test_quota_compliance_wlan_asymmetric_peer1.conf\ +test_quota_compliance_wlan_asymmetric_peer2.conf\ test_transport_api_data.conf\ test_transport_api_http_peer1.conf\ test_transport_api_http_peer2.conf\ @@ -1818,6 +2208,10 @@ test_transport_api_reliability_wlan_peer1.conf\ test_transport_api_reliability_wlan_peer2.conf\ test_transport_api_bidirectional_connect_peer1.conf\ test_transport_api_bidirectional_connect_peer2.conf\ +test_transport_api_manipulation_send_tcp_peer1.conf\ +test_transport_api_manipulation_send_tcp_peer2.conf\ +test_transport_api_manipulation_recv_tcp_peer1.conf\ +test_transport_api_manipulation_recv_tcp_peer2.conf\ test_transport_api_tcp_nat_peer1.conf\ test_transport_api_tcp_nat_peer2.conf\ test_transport_api_tcp_peer1.conf\ @@ -1844,20 +2238,14 @@ test_transport_defaults.conf\ test_transport_startonly.conf\ test_transport_api_disconnect_tcp_peer1.conf\ test_transport_api_disconnect_tcp_peer2.conf\ -test_transport_api_http_nat_peer1.conf\ -test_transport_api_http_nat_peer2.conf\ -test_transport_api_https_nat_peer1.conf\ -test_transport_api_https_nat_peer2.conf\ -test_transport_api_reliability_http_nat_peer1.conf\ -test_transport_api_reliability_http_nat_peer2.conf\ -test_transport_api_reliability_https_nat_peer1.conf\ -test_transport_api_reliability_https_nat_peer2.conf\ test_transport_api_timeout_http_peer1.conf\ test_transport_api_timeout_http_peer2.conf\ test_transport_api_timeout_https_peer1.conf\ test_transport_api_timeout_https_peer2.conf\ test_transport_api_unreliability_constant_udp_peer1.conf\ -test_transport_api_unreliability_constant_udp_peer2.conf +test_transport_api_unreliability_constant_udp_peer2.conf\ +test_transport_api_http_reverse_peer1.conf \ +test_transport_api_http_reverse_peer2.conf all: all-am @@ -1897,7 +2285,6 @@ transport.conf: $(top_builddir)/config.status $(srcdir)/transport.conf.in cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ install-libLTLIBRARIES: $(lib_LTLIBRARIES) @$(NORMAL_INSTALL) - test -z "$(libdir)" || $(MKDIR_P) "$(DESTDIR)$(libdir)" @list='$(lib_LTLIBRARIES)'; test -n "$(libdir)" || list=; \ list2=; for p in $$list; do \ if test -f $$p; then \ @@ -1905,6 +2292,8 @@ install-libLTLIBRARIES: $(lib_LTLIBRARIES) else :; fi; \ done; \ test -z "$$list2" || { \ + echo " $(MKDIR_P) '$(DESTDIR)$(libdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libdir)" || exit 1; \ echo " $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 '$(DESTDIR)$(libdir)'"; \ $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 "$(DESTDIR)$(libdir)"; \ } @@ -1928,7 +2317,6 @@ clean-libLTLIBRARIES: done install-pluginLTLIBRARIES: $(plugin_LTLIBRARIES) @$(NORMAL_INSTALL) - test -z "$(plugindir)" || $(MKDIR_P) "$(DESTDIR)$(plugindir)" @list='$(plugin_LTLIBRARIES)'; test -n "$(plugindir)" || list=; \ list2=; for p in $$list; do \ if test -f $$p; then \ @@ -1936,6 +2324,8 @@ install-pluginLTLIBRARIES: $(plugin_LTLIBRARIES) else :; fi; \ done; \ test -z "$$list2" || { \ + echo " $(MKDIR_P) '$(DESTDIR)$(plugindir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(plugindir)" || exit 1; \ echo " $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 '$(DESTDIR)$(plugindir)'"; \ $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 "$(DESTDIR)$(plugindir)"; \ } @@ -1957,28 +2347,35 @@ clean-pluginLTLIBRARIES: echo "rm -f \"$${dir}/so_locations\""; \ rm -f "$${dir}/so_locations"; \ done -libgnunet_plugin_transport_http.la: $(libgnunet_plugin_transport_http_la_OBJECTS) $(libgnunet_plugin_transport_http_la_DEPENDENCIES) - $(AM_V_CCLD)$(libgnunet_plugin_transport_http_la_LINK) $(am_libgnunet_plugin_transport_http_la_rpath) $(libgnunet_plugin_transport_http_la_OBJECTS) $(libgnunet_plugin_transport_http_la_LIBADD) $(LIBS) -libgnunet_plugin_transport_https.la: $(libgnunet_plugin_transport_https_la_OBJECTS) $(libgnunet_plugin_transport_https_la_DEPENDENCIES) - $(AM_V_CCLD)$(libgnunet_plugin_transport_https_la_LINK) $(am_libgnunet_plugin_transport_https_la_rpath) $(libgnunet_plugin_transport_https_la_OBJECTS) $(libgnunet_plugin_transport_https_la_LIBADD) $(LIBS) -libgnunet_plugin_transport_tcp.la: $(libgnunet_plugin_transport_tcp_la_OBJECTS) $(libgnunet_plugin_transport_tcp_la_DEPENDENCIES) +libgnunet_plugin_transport_http_client.la: $(libgnunet_plugin_transport_http_client_la_OBJECTS) $(libgnunet_plugin_transport_http_client_la_DEPENDENCIES) $(EXTRA_libgnunet_plugin_transport_http_client_la_DEPENDENCIES) + $(AM_V_CCLD)$(libgnunet_plugin_transport_http_client_la_LINK) $(am_libgnunet_plugin_transport_http_client_la_rpath) $(libgnunet_plugin_transport_http_client_la_OBJECTS) $(libgnunet_plugin_transport_http_client_la_LIBADD) $(LIBS) +libgnunet_plugin_transport_http_server.la: $(libgnunet_plugin_transport_http_server_la_OBJECTS) $(libgnunet_plugin_transport_http_server_la_DEPENDENCIES) $(EXTRA_libgnunet_plugin_transport_http_server_la_DEPENDENCIES) + $(AM_V_CCLD)$(libgnunet_plugin_transport_http_server_la_LINK) $(am_libgnunet_plugin_transport_http_server_la_rpath) $(libgnunet_plugin_transport_http_server_la_OBJECTS) $(libgnunet_plugin_transport_http_server_la_LIBADD) $(LIBS) +libgnunet_plugin_transport_https_client.la: $(libgnunet_plugin_transport_https_client_la_OBJECTS) $(libgnunet_plugin_transport_https_client_la_DEPENDENCIES) $(EXTRA_libgnunet_plugin_transport_https_client_la_DEPENDENCIES) + $(AM_V_CCLD)$(libgnunet_plugin_transport_https_client_la_LINK) $(am_libgnunet_plugin_transport_https_client_la_rpath) $(libgnunet_plugin_transport_https_client_la_OBJECTS) $(libgnunet_plugin_transport_https_client_la_LIBADD) $(LIBS) +libgnunet_plugin_transport_https_server.la: $(libgnunet_plugin_transport_https_server_la_OBJECTS) $(libgnunet_plugin_transport_https_server_la_DEPENDENCIES) $(EXTRA_libgnunet_plugin_transport_https_server_la_DEPENDENCIES) + $(AM_V_CCLD)$(libgnunet_plugin_transport_https_server_la_LINK) $(am_libgnunet_plugin_transport_https_server_la_rpath) $(libgnunet_plugin_transport_https_server_la_OBJECTS) $(libgnunet_plugin_transport_https_server_la_LIBADD) $(LIBS) +libgnunet_plugin_transport_tcp.la: $(libgnunet_plugin_transport_tcp_la_OBJECTS) $(libgnunet_plugin_transport_tcp_la_DEPENDENCIES) $(EXTRA_libgnunet_plugin_transport_tcp_la_DEPENDENCIES) $(AM_V_CCLD)$(libgnunet_plugin_transport_tcp_la_LINK) -rpath $(plugindir) $(libgnunet_plugin_transport_tcp_la_OBJECTS) $(libgnunet_plugin_transport_tcp_la_LIBADD) $(LIBS) -libgnunet_plugin_transport_template.la: $(libgnunet_plugin_transport_template_la_OBJECTS) $(libgnunet_plugin_transport_template_la_DEPENDENCIES) +libgnunet_plugin_transport_template.la: $(libgnunet_plugin_transport_template_la_OBJECTS) $(libgnunet_plugin_transport_template_la_DEPENDENCIES) $(EXTRA_libgnunet_plugin_transport_template_la_DEPENDENCIES) $(AM_V_CCLD)$(libgnunet_plugin_transport_template_la_LINK) -rpath $(plugindir) $(libgnunet_plugin_transport_template_la_OBJECTS) $(libgnunet_plugin_transport_template_la_LIBADD) $(LIBS) -libgnunet_plugin_transport_udp.la: $(libgnunet_plugin_transport_udp_la_OBJECTS) $(libgnunet_plugin_transport_udp_la_DEPENDENCIES) +libgnunet_plugin_transport_udp.la: $(libgnunet_plugin_transport_udp_la_OBJECTS) $(libgnunet_plugin_transport_udp_la_DEPENDENCIES) $(EXTRA_libgnunet_plugin_transport_udp_la_DEPENDENCIES) $(AM_V_CCLD)$(libgnunet_plugin_transport_udp_la_LINK) -rpath $(plugindir) $(libgnunet_plugin_transport_udp_la_OBJECTS) $(libgnunet_plugin_transport_udp_la_LIBADD) $(LIBS) -libgnunet_plugin_transport_unix.la: $(libgnunet_plugin_transport_unix_la_OBJECTS) $(libgnunet_plugin_transport_unix_la_DEPENDENCIES) +libgnunet_plugin_transport_unix.la: $(libgnunet_plugin_transport_unix_la_OBJECTS) $(libgnunet_plugin_transport_unix_la_DEPENDENCIES) $(EXTRA_libgnunet_plugin_transport_unix_la_DEPENDENCIES) $(AM_V_CCLD)$(libgnunet_plugin_transport_unix_la_LINK) $(am_libgnunet_plugin_transport_unix_la_rpath) $(libgnunet_plugin_transport_unix_la_OBJECTS) $(libgnunet_plugin_transport_unix_la_LIBADD) $(LIBS) -libgnunet_plugin_transport_wlan.la: $(libgnunet_plugin_transport_wlan_la_OBJECTS) $(libgnunet_plugin_transport_wlan_la_DEPENDENCIES) +libgnunet_plugin_transport_wlan.la: $(libgnunet_plugin_transport_wlan_la_OBJECTS) $(libgnunet_plugin_transport_wlan_la_DEPENDENCIES) $(EXTRA_libgnunet_plugin_transport_wlan_la_DEPENDENCIES) $(AM_V_CCLD)$(libgnunet_plugin_transport_wlan_la_LINK) $(am_libgnunet_plugin_transport_wlan_la_rpath) $(libgnunet_plugin_transport_wlan_la_OBJECTS) $(libgnunet_plugin_transport_wlan_la_LIBADD) $(LIBS) -libgnunettransport.la: $(libgnunettransport_la_OBJECTS) $(libgnunettransport_la_DEPENDENCIES) +libgnunettransport.la: $(libgnunettransport_la_OBJECTS) $(libgnunettransport_la_DEPENDENCIES) $(EXTRA_libgnunettransport_la_DEPENDENCIES) $(AM_V_CCLD)$(libgnunettransport_la_LINK) -rpath $(libdir) $(libgnunettransport_la_OBJECTS) $(libgnunettransport_la_LIBADD) $(LIBS) -libgnunettransporttesting.la: $(libgnunettransporttesting_la_OBJECTS) $(libgnunettransporttesting_la_DEPENDENCIES) +libgnunettransporttesting.la: $(libgnunettransporttesting_la_OBJECTS) $(libgnunettransporttesting_la_DEPENDENCIES) $(EXTRA_libgnunettransporttesting_la_DEPENDENCIES) $(AM_V_CCLD)$(libgnunettransporttesting_la_LINK) -rpath $(libdir) $(libgnunettransporttesting_la_OBJECTS) $(libgnunettransporttesting_la_LIBADD) $(LIBS) install-binPROGRAMS: $(bin_PROGRAMS) @$(NORMAL_INSTALL) - test -z "$(bindir)" || $(MKDIR_P) "$(DESTDIR)$(bindir)" @list='$(bin_PROGRAMS)'; test -n "$(bindir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(bindir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(bindir)" || exit 1; \ + fi; \ for p in $$list; do echo "$$p $$p"; done | \ sed 's/$(EXEEXT)$$//' | \ while read p p1; do if test -f $$p || test -f $$p1; \ @@ -2027,6 +2424,52 @@ clean-checkPROGRAMS: list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ echo " rm -f" $$list; \ rm -f $$list +install-libexecPROGRAMS: $(libexec_PROGRAMS) + @$(NORMAL_INSTALL) + @list='$(libexec_PROGRAMS)'; test -n "$(libexecdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(libexecdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libexecdir)" || exit 1; \ + fi; \ + for p in $$list; do echo "$$p $$p"; done | \ + sed 's/$(EXEEXT)$$//' | \ + while read p p1; do if test -f $$p || test -f $$p1; \ + then echo "$$p"; echo "$$p"; else :; fi; \ + done | \ + sed -e 'p;s,.*/,,;n;h' -e 's|.*|.|' \ + -e 'p;x;s,.*/,,;s/$(EXEEXT)$$//;$(transform);s/$$/$(EXEEXT)/' | \ + sed 'N;N;N;s,\n, ,g' | \ + $(AWK) 'BEGIN { files["."] = ""; dirs["."] = 1 } \ + { d=$$3; if (dirs[d] != 1) { print "d", d; dirs[d] = 1 } \ + if ($$2 == $$4) files[d] = files[d] " " $$1; \ + else { print "f", $$3 "/" $$4, $$1; } } \ + END { for (d in files) print "f", d, files[d] }' | \ + while read type dir files; do \ + if test "$$dir" = .; then dir=; else dir=/$$dir; fi; \ + test -z "$$files" || { \ + echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files '$(DESTDIR)$(libexecdir)$$dir'"; \ + $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files "$(DESTDIR)$(libexecdir)$$dir" || exit $$?; \ + } \ + ; done + +uninstall-libexecPROGRAMS: + @$(NORMAL_UNINSTALL) + @list='$(libexec_PROGRAMS)'; test -n "$(libexecdir)" || list=; \ + files=`for p in $$list; do echo "$$p"; done | \ + sed -e 'h;s,^.*/,,;s/$(EXEEXT)$$//;$(transform)' \ + -e 's/$$/$(EXEEXT)/' `; \ + test -n "$$list" || exit 0; \ + echo " ( cd '$(DESTDIR)$(libexecdir)' && rm -f" $$files ")"; \ + cd "$(DESTDIR)$(libexecdir)" && rm -f $$files + +clean-libexecPROGRAMS: + @list='$(libexec_PROGRAMS)'; test -n "$$list" || exit 0; \ + echo " rm -f" $$list; \ + rm -f $$list || exit $$?; \ + test -n "$(EXEEXT)" || exit 0; \ + list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ + echo " rm -f" $$list; \ + rm -f $$list clean-noinstPROGRAMS: @list='$(noinst_PROGRAMS)'; test -n "$$list" || exit 0; \ @@ -2036,156 +2479,195 @@ clean-noinstPROGRAMS: list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ echo " rm -f" $$list; \ rm -f $$list -gnunet-helper-transport-wlan$(EXEEXT): $(gnunet_helper_transport_wlan_OBJECTS) $(gnunet_helper_transport_wlan_DEPENDENCIES) +gnunet-helper-transport-wlan$(EXEEXT): $(gnunet_helper_transport_wlan_OBJECTS) $(gnunet_helper_transport_wlan_DEPENDENCIES) $(EXTRA_gnunet_helper_transport_wlan_DEPENDENCIES) @rm -f gnunet-helper-transport-wlan$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_helper_transport_wlan_OBJECTS) $(gnunet_helper_transport_wlan_LDADD) $(LIBS) -gnunet-helper-transport-wlan-dummy$(EXEEXT): $(gnunet_helper_transport_wlan_dummy_OBJECTS) $(gnunet_helper_transport_wlan_dummy_DEPENDENCIES) +gnunet-helper-transport-wlan-dummy$(EXEEXT): $(gnunet_helper_transport_wlan_dummy_OBJECTS) $(gnunet_helper_transport_wlan_dummy_DEPENDENCIES) $(EXTRA_gnunet_helper_transport_wlan_dummy_DEPENDENCIES) @rm -f gnunet-helper-transport-wlan-dummy$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_helper_transport_wlan_dummy_OBJECTS) $(gnunet_helper_transport_wlan_dummy_LDADD) $(LIBS) -gnunet-service-transport$(EXEEXT): $(gnunet_service_transport_OBJECTS) $(gnunet_service_transport_DEPENDENCIES) +gnunet-service-transport$(EXEEXT): $(gnunet_service_transport_OBJECTS) $(gnunet_service_transport_DEPENDENCIES) $(EXTRA_gnunet_service_transport_DEPENDENCIES) @rm -f gnunet-service-transport$(EXEEXT) - $(AM_V_CCLD)$(LINK) $(gnunet_service_transport_OBJECTS) $(gnunet_service_transport_LDADD) $(LIBS) -gnunet-transport$(EXEEXT): $(gnunet_transport_OBJECTS) $(gnunet_transport_DEPENDENCIES) + $(AM_V_CCLD)$(gnunet_service_transport_LINK) $(gnunet_service_transport_OBJECTS) $(gnunet_service_transport_LDADD) $(LIBS) +gnunet-transport$(EXEEXT): $(gnunet_transport_OBJECTS) $(gnunet_transport_DEPENDENCIES) $(EXTRA_gnunet_transport_DEPENDENCIES) @rm -f gnunet-transport$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_transport_OBJECTS) $(gnunet_transport_LDADD) $(LIBS) -gnunet-transport-certificate-creation$(EXEEXT): $(gnunet_transport_certificate_creation_OBJECTS) $(gnunet_transport_certificate_creation_DEPENDENCIES) +gnunet-transport-certificate-creation$(EXEEXT): $(gnunet_transport_certificate_creation_OBJECTS) $(gnunet_transport_certificate_creation_DEPENDENCIES) $(EXTRA_gnunet_transport_certificate_creation_DEPENDENCIES) @rm -f gnunet-transport-certificate-creation$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_transport_certificate_creation_OBJECTS) $(gnunet_transport_certificate_creation_LDADD) $(LIBS) -gnunet-transport-wlan-sender$(EXEEXT): $(gnunet_transport_wlan_sender_OBJECTS) $(gnunet_transport_wlan_sender_DEPENDENCIES) +gnunet-transport-wlan-receiver$(EXEEXT): $(gnunet_transport_wlan_receiver_OBJECTS) $(gnunet_transport_wlan_receiver_DEPENDENCIES) $(EXTRA_gnunet_transport_wlan_receiver_DEPENDENCIES) + @rm -f gnunet-transport-wlan-receiver$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(gnunet_transport_wlan_receiver_OBJECTS) $(gnunet_transport_wlan_receiver_LDADD) $(LIBS) +gnunet-transport-wlan-sender$(EXEEXT): $(gnunet_transport_wlan_sender_OBJECTS) $(gnunet_transport_wlan_sender_DEPENDENCIES) $(EXTRA_gnunet_transport_wlan_sender_DEPENDENCIES) @rm -f gnunet-transport-wlan-sender$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_transport_wlan_sender_OBJECTS) $(gnunet_transport_wlan_sender_LDADD) $(LIBS) -test_quota_compliance_http$(EXEEXT): $(test_quota_compliance_http_OBJECTS) $(test_quota_compliance_http_DEPENDENCIES) +test_http_common$(EXEEXT): $(test_http_common_OBJECTS) $(test_http_common_DEPENDENCIES) $(EXTRA_test_http_common_DEPENDENCIES) + @rm -f test_http_common$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_http_common_OBJECTS) $(test_http_common_LDADD) $(LIBS) +test_plugin_http_client$(EXEEXT): $(test_plugin_http_client_OBJECTS) $(test_plugin_http_client_DEPENDENCIES) $(EXTRA_test_plugin_http_client_DEPENDENCIES) + @rm -f test_plugin_http_client$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_plugin_http_client_OBJECTS) $(test_plugin_http_client_LDADD) $(LIBS) +test_plugin_http_server$(EXEEXT): $(test_plugin_http_server_OBJECTS) $(test_plugin_http_server_DEPENDENCIES) $(EXTRA_test_plugin_http_server_DEPENDENCIES) + @rm -f test_plugin_http_server$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_plugin_http_server_OBJECTS) $(test_plugin_http_server_LDADD) $(LIBS) +test_plugin_https_client$(EXEEXT): $(test_plugin_https_client_OBJECTS) $(test_plugin_https_client_DEPENDENCIES) $(EXTRA_test_plugin_https_client_DEPENDENCIES) + @rm -f test_plugin_https_client$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_plugin_https_client_OBJECTS) $(test_plugin_https_client_LDADD) $(LIBS) +test_plugin_https_server$(EXEEXT): $(test_plugin_https_server_OBJECTS) $(test_plugin_https_server_DEPENDENCIES) $(EXTRA_test_plugin_https_server_DEPENDENCIES) + @rm -f test_plugin_https_server$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_plugin_https_server_OBJECTS) $(test_plugin_https_server_LDADD) $(LIBS) +test_plugin_tcp$(EXEEXT): $(test_plugin_tcp_OBJECTS) $(test_plugin_tcp_DEPENDENCIES) $(EXTRA_test_plugin_tcp_DEPENDENCIES) + @rm -f test_plugin_tcp$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_plugin_tcp_OBJECTS) $(test_plugin_tcp_LDADD) $(LIBS) +test_plugin_udp$(EXEEXT): $(test_plugin_udp_OBJECTS) $(test_plugin_udp_DEPENDENCIES) $(EXTRA_test_plugin_udp_DEPENDENCIES) + @rm -f test_plugin_udp$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_plugin_udp_OBJECTS) $(test_plugin_udp_LDADD) $(LIBS) +test_plugin_unix$(EXEEXT): $(test_plugin_unix_OBJECTS) $(test_plugin_unix_DEPENDENCIES) $(EXTRA_test_plugin_unix_DEPENDENCIES) + @rm -f test_plugin_unix$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_plugin_unix_OBJECTS) $(test_plugin_unix_LDADD) $(LIBS) +test_plugin_wlan$(EXEEXT): $(test_plugin_wlan_OBJECTS) $(test_plugin_wlan_DEPENDENCIES) $(EXTRA_test_plugin_wlan_DEPENDENCIES) + @rm -f test_plugin_wlan$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_plugin_wlan_OBJECTS) $(test_plugin_wlan_LDADD) $(LIBS) +test_quota_compliance_http$(EXEEXT): $(test_quota_compliance_http_OBJECTS) $(test_quota_compliance_http_DEPENDENCIES) $(EXTRA_test_quota_compliance_http_DEPENDENCIES) @rm -f test_quota_compliance_http$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_quota_compliance_http_OBJECTS) $(test_quota_compliance_http_LDADD) $(LIBS) -test_quota_compliance_http_asymmetric$(EXEEXT): $(test_quota_compliance_http_asymmetric_OBJECTS) $(test_quota_compliance_http_asymmetric_DEPENDENCIES) +test_quota_compliance_http_asymmetric$(EXEEXT): $(test_quota_compliance_http_asymmetric_OBJECTS) $(test_quota_compliance_http_asymmetric_DEPENDENCIES) $(EXTRA_test_quota_compliance_http_asymmetric_DEPENDENCIES) @rm -f test_quota_compliance_http_asymmetric$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_quota_compliance_http_asymmetric_OBJECTS) $(test_quota_compliance_http_asymmetric_LDADD) $(LIBS) -test_quota_compliance_https$(EXEEXT): $(test_quota_compliance_https_OBJECTS) $(test_quota_compliance_https_DEPENDENCIES) +test_quota_compliance_https$(EXEEXT): $(test_quota_compliance_https_OBJECTS) $(test_quota_compliance_https_DEPENDENCIES) $(EXTRA_test_quota_compliance_https_DEPENDENCIES) @rm -f test_quota_compliance_https$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_quota_compliance_https_OBJECTS) $(test_quota_compliance_https_LDADD) $(LIBS) -test_quota_compliance_https_asymmetric$(EXEEXT): $(test_quota_compliance_https_asymmetric_OBJECTS) $(test_quota_compliance_https_asymmetric_DEPENDENCIES) +test_quota_compliance_https_asymmetric$(EXEEXT): $(test_quota_compliance_https_asymmetric_OBJECTS) $(test_quota_compliance_https_asymmetric_DEPENDENCIES) $(EXTRA_test_quota_compliance_https_asymmetric_DEPENDENCIES) @rm -f test_quota_compliance_https_asymmetric$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_quota_compliance_https_asymmetric_OBJECTS) $(test_quota_compliance_https_asymmetric_LDADD) $(LIBS) -test_quota_compliance_tcp$(EXEEXT): $(test_quota_compliance_tcp_OBJECTS) $(test_quota_compliance_tcp_DEPENDENCIES) +test_quota_compliance_tcp$(EXEEXT): $(test_quota_compliance_tcp_OBJECTS) $(test_quota_compliance_tcp_DEPENDENCIES) $(EXTRA_test_quota_compliance_tcp_DEPENDENCIES) @rm -f test_quota_compliance_tcp$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_quota_compliance_tcp_OBJECTS) $(test_quota_compliance_tcp_LDADD) $(LIBS) -test_quota_compliance_tcp_asymmetric$(EXEEXT): $(test_quota_compliance_tcp_asymmetric_OBJECTS) $(test_quota_compliance_tcp_asymmetric_DEPENDENCIES) +test_quota_compliance_tcp_asymmetric$(EXEEXT): $(test_quota_compliance_tcp_asymmetric_OBJECTS) $(test_quota_compliance_tcp_asymmetric_DEPENDENCIES) $(EXTRA_test_quota_compliance_tcp_asymmetric_DEPENDENCIES) @rm -f test_quota_compliance_tcp_asymmetric$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_quota_compliance_tcp_asymmetric_OBJECTS) $(test_quota_compliance_tcp_asymmetric_LDADD) $(LIBS) -test_quota_compliance_udp$(EXEEXT): $(test_quota_compliance_udp_OBJECTS) $(test_quota_compliance_udp_DEPENDENCIES) +test_quota_compliance_udp$(EXEEXT): $(test_quota_compliance_udp_OBJECTS) $(test_quota_compliance_udp_DEPENDENCIES) $(EXTRA_test_quota_compliance_udp_DEPENDENCIES) @rm -f test_quota_compliance_udp$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_quota_compliance_udp_OBJECTS) $(test_quota_compliance_udp_LDADD) $(LIBS) -test_quota_compliance_unix$(EXEEXT): $(test_quota_compliance_unix_OBJECTS) $(test_quota_compliance_unix_DEPENDENCIES) +test_quota_compliance_unix$(EXEEXT): $(test_quota_compliance_unix_OBJECTS) $(test_quota_compliance_unix_DEPENDENCIES) $(EXTRA_test_quota_compliance_unix_DEPENDENCIES) @rm -f test_quota_compliance_unix$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_quota_compliance_unix_OBJECTS) $(test_quota_compliance_unix_LDADD) $(LIBS) -test_quota_compliance_unix_asymmetric$(EXEEXT): $(test_quota_compliance_unix_asymmetric_OBJECTS) $(test_quota_compliance_unix_asymmetric_DEPENDENCIES) +test_quota_compliance_unix_asymmetric$(EXEEXT): $(test_quota_compliance_unix_asymmetric_OBJECTS) $(test_quota_compliance_unix_asymmetric_DEPENDENCIES) $(EXTRA_test_quota_compliance_unix_asymmetric_DEPENDENCIES) @rm -f test_quota_compliance_unix_asymmetric$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_quota_compliance_unix_asymmetric_OBJECTS) $(test_quota_compliance_unix_asymmetric_LDADD) $(LIBS) -test_transport_api_bidirectional_connect$(EXEEXT): $(test_transport_api_bidirectional_connect_OBJECTS) $(test_transport_api_bidirectional_connect_DEPENDENCIES) +test_quota_compliance_wlan$(EXEEXT): $(test_quota_compliance_wlan_OBJECTS) $(test_quota_compliance_wlan_DEPENDENCIES) $(EXTRA_test_quota_compliance_wlan_DEPENDENCIES) + @rm -f test_quota_compliance_wlan$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_quota_compliance_wlan_OBJECTS) $(test_quota_compliance_wlan_LDADD) $(LIBS) +test_quota_compliance_wlan_asymmetric$(EXEEXT): $(test_quota_compliance_wlan_asymmetric_OBJECTS) $(test_quota_compliance_wlan_asymmetric_DEPENDENCIES) $(EXTRA_test_quota_compliance_wlan_asymmetric_DEPENDENCIES) + @rm -f test_quota_compliance_wlan_asymmetric$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_quota_compliance_wlan_asymmetric_OBJECTS) $(test_quota_compliance_wlan_asymmetric_LDADD) $(LIBS) +test_transport_api_bidirectional_connect$(EXEEXT): $(test_transport_api_bidirectional_connect_OBJECTS) $(test_transport_api_bidirectional_connect_DEPENDENCIES) $(EXTRA_test_transport_api_bidirectional_connect_DEPENDENCIES) @rm -f test_transport_api_bidirectional_connect$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_transport_api_bidirectional_connect_OBJECTS) $(test_transport_api_bidirectional_connect_LDADD) $(LIBS) -test_transport_api_blacklisting$(EXEEXT): $(test_transport_api_blacklisting_OBJECTS) $(test_transport_api_blacklisting_DEPENDENCIES) +test_transport_api_blacklisting$(EXEEXT): $(test_transport_api_blacklisting_OBJECTS) $(test_transport_api_blacklisting_DEPENDENCIES) $(EXTRA_test_transport_api_blacklisting_DEPENDENCIES) @rm -f test_transport_api_blacklisting$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_transport_api_blacklisting_OBJECTS) $(test_transport_api_blacklisting_LDADD) $(LIBS) -test_transport_api_disconnect_tcp$(EXEEXT): $(test_transport_api_disconnect_tcp_OBJECTS) $(test_transport_api_disconnect_tcp_DEPENDENCIES) +test_transport_api_disconnect_tcp$(EXEEXT): $(test_transport_api_disconnect_tcp_OBJECTS) $(test_transport_api_disconnect_tcp_DEPENDENCIES) $(EXTRA_test_transport_api_disconnect_tcp_DEPENDENCIES) @rm -f test_transport_api_disconnect_tcp$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_transport_api_disconnect_tcp_OBJECTS) $(test_transport_api_disconnect_tcp_LDADD) $(LIBS) -test_transport_api_http$(EXEEXT): $(test_transport_api_http_OBJECTS) $(test_transport_api_http_DEPENDENCIES) +test_transport_api_http$(EXEEXT): $(test_transport_api_http_OBJECTS) $(test_transport_api_http_DEPENDENCIES) $(EXTRA_test_transport_api_http_DEPENDENCIES) @rm -f test_transport_api_http$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_transport_api_http_OBJECTS) $(test_transport_api_http_LDADD) $(LIBS) -test_transport_api_http_nat$(EXEEXT): $(test_transport_api_http_nat_OBJECTS) $(test_transport_api_http_nat_DEPENDENCIES) - @rm -f test_transport_api_http_nat$(EXEEXT) - $(AM_V_CCLD)$(LINK) $(test_transport_api_http_nat_OBJECTS) $(test_transport_api_http_nat_LDADD) $(LIBS) -test_transport_api_https$(EXEEXT): $(test_transport_api_https_OBJECTS) $(test_transport_api_https_DEPENDENCIES) +test_transport_api_http_reverse$(EXEEXT): $(test_transport_api_http_reverse_OBJECTS) $(test_transport_api_http_reverse_DEPENDENCIES) $(EXTRA_test_transport_api_http_reverse_DEPENDENCIES) + @rm -f test_transport_api_http_reverse$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_transport_api_http_reverse_OBJECTS) $(test_transport_api_http_reverse_LDADD) $(LIBS) +test_transport_api_https$(EXEEXT): $(test_transport_api_https_OBJECTS) $(test_transport_api_https_DEPENDENCIES) $(EXTRA_test_transport_api_https_DEPENDENCIES) @rm -f test_transport_api_https$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_transport_api_https_OBJECTS) $(test_transport_api_https_LDADD) $(LIBS) -test_transport_api_https_nat$(EXEEXT): $(test_transport_api_https_nat_OBJECTS) $(test_transport_api_https_nat_DEPENDENCIES) - @rm -f test_transport_api_https_nat$(EXEEXT) - $(AM_V_CCLD)$(LINK) $(test_transport_api_https_nat_OBJECTS) $(test_transport_api_https_nat_LDADD) $(LIBS) -test_transport_api_limited_sockets_tcp$(EXEEXT): $(test_transport_api_limited_sockets_tcp_OBJECTS) $(test_transport_api_limited_sockets_tcp_DEPENDENCIES) +test_transport_api_limited_sockets_tcp$(EXEEXT): $(test_transport_api_limited_sockets_tcp_OBJECTS) $(test_transport_api_limited_sockets_tcp_DEPENDENCIES) $(EXTRA_test_transport_api_limited_sockets_tcp_DEPENDENCIES) @rm -f test_transport_api_limited_sockets_tcp$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_transport_api_limited_sockets_tcp_OBJECTS) $(test_transport_api_limited_sockets_tcp_LDADD) $(LIBS) -test_transport_api_multi$(EXEEXT): $(test_transport_api_multi_OBJECTS) $(test_transport_api_multi_DEPENDENCIES) +test_transport_api_manipulation_recv_tcp$(EXEEXT): $(test_transport_api_manipulation_recv_tcp_OBJECTS) $(test_transport_api_manipulation_recv_tcp_DEPENDENCIES) $(EXTRA_test_transport_api_manipulation_recv_tcp_DEPENDENCIES) + @rm -f test_transport_api_manipulation_recv_tcp$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_transport_api_manipulation_recv_tcp_OBJECTS) $(test_transport_api_manipulation_recv_tcp_LDADD) $(LIBS) +test_transport_api_manipulation_send_tcp$(EXEEXT): $(test_transport_api_manipulation_send_tcp_OBJECTS) $(test_transport_api_manipulation_send_tcp_DEPENDENCIES) $(EXTRA_test_transport_api_manipulation_send_tcp_DEPENDENCIES) + @rm -f test_transport_api_manipulation_send_tcp$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_transport_api_manipulation_send_tcp_OBJECTS) $(test_transport_api_manipulation_send_tcp_LDADD) $(LIBS) +test_transport_api_multi$(EXEEXT): $(test_transport_api_multi_OBJECTS) $(test_transport_api_multi_DEPENDENCIES) $(EXTRA_test_transport_api_multi_DEPENDENCIES) @rm -f test_transport_api_multi$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_transport_api_multi_OBJECTS) $(test_transport_api_multi_LDADD) $(LIBS) -test_transport_api_reliability_http$(EXEEXT): $(test_transport_api_reliability_http_OBJECTS) $(test_transport_api_reliability_http_DEPENDENCIES) +test_transport_api_reliability_http$(EXEEXT): $(test_transport_api_reliability_http_OBJECTS) $(test_transport_api_reliability_http_DEPENDENCIES) $(EXTRA_test_transport_api_reliability_http_DEPENDENCIES) @rm -f test_transport_api_reliability_http$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_transport_api_reliability_http_OBJECTS) $(test_transport_api_reliability_http_LDADD) $(LIBS) -test_transport_api_reliability_http_nat$(EXEEXT): $(test_transport_api_reliability_http_nat_OBJECTS) $(test_transport_api_reliability_http_nat_DEPENDENCIES) - @rm -f test_transport_api_reliability_http_nat$(EXEEXT) - $(AM_V_CCLD)$(LINK) $(test_transport_api_reliability_http_nat_OBJECTS) $(test_transport_api_reliability_http_nat_LDADD) $(LIBS) -test_transport_api_reliability_https$(EXEEXT): $(test_transport_api_reliability_https_OBJECTS) $(test_transport_api_reliability_https_DEPENDENCIES) +test_transport_api_reliability_https$(EXEEXT): $(test_transport_api_reliability_https_OBJECTS) $(test_transport_api_reliability_https_DEPENDENCIES) $(EXTRA_test_transport_api_reliability_https_DEPENDENCIES) @rm -f test_transport_api_reliability_https$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_transport_api_reliability_https_OBJECTS) $(test_transport_api_reliability_https_LDADD) $(LIBS) -test_transport_api_reliability_https_nat$(EXEEXT): $(test_transport_api_reliability_https_nat_OBJECTS) $(test_transport_api_reliability_https_nat_DEPENDENCIES) - @rm -f test_transport_api_reliability_https_nat$(EXEEXT) - $(AM_V_CCLD)$(LINK) $(test_transport_api_reliability_https_nat_OBJECTS) $(test_transport_api_reliability_https_nat_LDADD) $(LIBS) -test_transport_api_reliability_tcp$(EXEEXT): $(test_transport_api_reliability_tcp_OBJECTS) $(test_transport_api_reliability_tcp_DEPENDENCIES) +test_transport_api_reliability_tcp$(EXEEXT): $(test_transport_api_reliability_tcp_OBJECTS) $(test_transport_api_reliability_tcp_DEPENDENCIES) $(EXTRA_test_transport_api_reliability_tcp_DEPENDENCIES) @rm -f test_transport_api_reliability_tcp$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_transport_api_reliability_tcp_OBJECTS) $(test_transport_api_reliability_tcp_LDADD) $(LIBS) -test_transport_api_reliability_tcp_nat$(EXEEXT): $(test_transport_api_reliability_tcp_nat_OBJECTS) $(test_transport_api_reliability_tcp_nat_DEPENDENCIES) +test_transport_api_reliability_tcp_nat$(EXEEXT): $(test_transport_api_reliability_tcp_nat_OBJECTS) $(test_transport_api_reliability_tcp_nat_DEPENDENCIES) $(EXTRA_test_transport_api_reliability_tcp_nat_DEPENDENCIES) @rm -f test_transport_api_reliability_tcp_nat$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_transport_api_reliability_tcp_nat_OBJECTS) $(test_transport_api_reliability_tcp_nat_LDADD) $(LIBS) -test_transport_api_reliability_wlan$(EXEEXT): $(test_transport_api_reliability_wlan_OBJECTS) $(test_transport_api_reliability_wlan_DEPENDENCIES) +test_transport_api_reliability_wlan$(EXEEXT): $(test_transport_api_reliability_wlan_OBJECTS) $(test_transport_api_reliability_wlan_DEPENDENCIES) $(EXTRA_test_transport_api_reliability_wlan_DEPENDENCIES) @rm -f test_transport_api_reliability_wlan$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_transport_api_reliability_wlan_OBJECTS) $(test_transport_api_reliability_wlan_LDADD) $(LIBS) -test_transport_api_restart_1peer$(EXEEXT): $(test_transport_api_restart_1peer_OBJECTS) $(test_transport_api_restart_1peer_DEPENDENCIES) +test_transport_api_restart_1peer$(EXEEXT): $(test_transport_api_restart_1peer_OBJECTS) $(test_transport_api_restart_1peer_DEPENDENCIES) $(EXTRA_test_transport_api_restart_1peer_DEPENDENCIES) @rm -f test_transport_api_restart_1peer$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_transport_api_restart_1peer_OBJECTS) $(test_transport_api_restart_1peer_LDADD) $(LIBS) -test_transport_api_restart_2peers$(EXEEXT): $(test_transport_api_restart_2peers_OBJECTS) $(test_transport_api_restart_2peers_DEPENDENCIES) +test_transport_api_restart_2peers$(EXEEXT): $(test_transport_api_restart_2peers_OBJECTS) $(test_transport_api_restart_2peers_DEPENDENCIES) $(EXTRA_test_transport_api_restart_2peers_DEPENDENCIES) @rm -f test_transport_api_restart_2peers$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_transport_api_restart_2peers_OBJECTS) $(test_transport_api_restart_2peers_LDADD) $(LIBS) -test_transport_api_tcp$(EXEEXT): $(test_transport_api_tcp_OBJECTS) $(test_transport_api_tcp_DEPENDENCIES) +test_transport_api_tcp$(EXEEXT): $(test_transport_api_tcp_OBJECTS) $(test_transport_api_tcp_DEPENDENCIES) $(EXTRA_test_transport_api_tcp_DEPENDENCIES) @rm -f test_transport_api_tcp$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_transport_api_tcp_OBJECTS) $(test_transport_api_tcp_LDADD) $(LIBS) -test_transport_api_tcp_nat$(EXEEXT): $(test_transport_api_tcp_nat_OBJECTS) $(test_transport_api_tcp_nat_DEPENDENCIES) +test_transport_api_tcp_nat$(EXEEXT): $(test_transport_api_tcp_nat_OBJECTS) $(test_transport_api_tcp_nat_DEPENDENCIES) $(EXTRA_test_transport_api_tcp_nat_DEPENDENCIES) @rm -f test_transport_api_tcp_nat$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_transport_api_tcp_nat_OBJECTS) $(test_transport_api_tcp_nat_LDADD) $(LIBS) -test_transport_api_timeout_http$(EXEEXT): $(test_transport_api_timeout_http_OBJECTS) $(test_transport_api_timeout_http_DEPENDENCIES) +test_transport_api_timeout_http$(EXEEXT): $(test_transport_api_timeout_http_OBJECTS) $(test_transport_api_timeout_http_DEPENDENCIES) $(EXTRA_test_transport_api_timeout_http_DEPENDENCIES) @rm -f test_transport_api_timeout_http$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_transport_api_timeout_http_OBJECTS) $(test_transport_api_timeout_http_LDADD) $(LIBS) -test_transport_api_timeout_https$(EXEEXT): $(test_transport_api_timeout_https_OBJECTS) $(test_transport_api_timeout_https_DEPENDENCIES) +test_transport_api_timeout_https$(EXEEXT): $(test_transport_api_timeout_https_OBJECTS) $(test_transport_api_timeout_https_DEPENDENCIES) $(EXTRA_test_transport_api_timeout_https_DEPENDENCIES) @rm -f test_transport_api_timeout_https$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_transport_api_timeout_https_OBJECTS) $(test_transport_api_timeout_https_LDADD) $(LIBS) -test_transport_api_timeout_tcp$(EXEEXT): $(test_transport_api_timeout_tcp_OBJECTS) $(test_transport_api_timeout_tcp_DEPENDENCIES) +test_transport_api_timeout_tcp$(EXEEXT): $(test_transport_api_timeout_tcp_OBJECTS) $(test_transport_api_timeout_tcp_DEPENDENCIES) $(EXTRA_test_transport_api_timeout_tcp_DEPENDENCIES) @rm -f test_transport_api_timeout_tcp$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_transport_api_timeout_tcp_OBJECTS) $(test_transport_api_timeout_tcp_LDADD) $(LIBS) -test_transport_api_timeout_udp$(EXEEXT): $(test_transport_api_timeout_udp_OBJECTS) $(test_transport_api_timeout_udp_DEPENDENCIES) +test_transport_api_timeout_udp$(EXEEXT): $(test_transport_api_timeout_udp_OBJECTS) $(test_transport_api_timeout_udp_DEPENDENCIES) $(EXTRA_test_transport_api_timeout_udp_DEPENDENCIES) @rm -f test_transport_api_timeout_udp$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_transport_api_timeout_udp_OBJECTS) $(test_transport_api_timeout_udp_LDADD) $(LIBS) -test_transport_api_timeout_unix$(EXEEXT): $(test_transport_api_timeout_unix_OBJECTS) $(test_transport_api_timeout_unix_DEPENDENCIES) +test_transport_api_timeout_unix$(EXEEXT): $(test_transport_api_timeout_unix_OBJECTS) $(test_transport_api_timeout_unix_DEPENDENCIES) $(EXTRA_test_transport_api_timeout_unix_DEPENDENCIES) @rm -f test_transport_api_timeout_unix$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_transport_api_timeout_unix_OBJECTS) $(test_transport_api_timeout_unix_LDADD) $(LIBS) -test_transport_api_udp$(EXEEXT): $(test_transport_api_udp_OBJECTS) $(test_transport_api_udp_DEPENDENCIES) +test_transport_api_udp$(EXEEXT): $(test_transport_api_udp_OBJECTS) $(test_transport_api_udp_DEPENDENCIES) $(EXTRA_test_transport_api_udp_DEPENDENCIES) @rm -f test_transport_api_udp$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_transport_api_udp_OBJECTS) $(test_transport_api_udp_LDADD) $(LIBS) -test_transport_api_udp_nat$(EXEEXT): $(test_transport_api_udp_nat_OBJECTS) $(test_transport_api_udp_nat_DEPENDENCIES) +test_transport_api_udp_nat$(EXEEXT): $(test_transport_api_udp_nat_OBJECTS) $(test_transport_api_udp_nat_DEPENDENCIES) $(EXTRA_test_transport_api_udp_nat_DEPENDENCIES) @rm -f test_transport_api_udp_nat$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_transport_api_udp_nat_OBJECTS) $(test_transport_api_udp_nat_LDADD) $(LIBS) -test_transport_api_unix$(EXEEXT): $(test_transport_api_unix_OBJECTS) $(test_transport_api_unix_DEPENDENCIES) +test_transport_api_unix$(EXEEXT): $(test_transport_api_unix_OBJECTS) $(test_transport_api_unix_DEPENDENCIES) $(EXTRA_test_transport_api_unix_DEPENDENCIES) @rm -f test_transport_api_unix$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_transport_api_unix_OBJECTS) $(test_transport_api_unix_LDADD) $(LIBS) -test_transport_api_unreliability_constant_udp$(EXEEXT): $(test_transport_api_unreliability_constant_udp_OBJECTS) $(test_transport_api_unreliability_constant_udp_DEPENDENCIES) +test_transport_api_unreliability_constant_udp$(EXEEXT): $(test_transport_api_unreliability_constant_udp_OBJECTS) $(test_transport_api_unreliability_constant_udp_DEPENDENCIES) $(EXTRA_test_transport_api_unreliability_constant_udp_DEPENDENCIES) @rm -f test_transport_api_unreliability_constant_udp$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_transport_api_unreliability_constant_udp_OBJECTS) $(test_transport_api_unreliability_constant_udp_LDADD) $(LIBS) -test_transport_api_unreliability_udp$(EXEEXT): $(test_transport_api_unreliability_udp_OBJECTS) $(test_transport_api_unreliability_udp_DEPENDENCIES) +test_transport_api_unreliability_udp$(EXEEXT): $(test_transport_api_unreliability_udp_OBJECTS) $(test_transport_api_unreliability_udp_DEPENDENCIES) $(EXTRA_test_transport_api_unreliability_udp_DEPENDENCIES) @rm -f test_transport_api_unreliability_udp$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_transport_api_unreliability_udp_OBJECTS) $(test_transport_api_unreliability_udp_LDADD) $(LIBS) -test_transport_api_unreliability_unix$(EXEEXT): $(test_transport_api_unreliability_unix_OBJECTS) $(test_transport_api_unreliability_unix_DEPENDENCIES) +test_transport_api_unreliability_unix$(EXEEXT): $(test_transport_api_unreliability_unix_OBJECTS) $(test_transport_api_unreliability_unix_DEPENDENCIES) $(EXTRA_test_transport_api_unreliability_unix_DEPENDENCIES) @rm -f test_transport_api_unreliability_unix$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_transport_api_unreliability_unix_OBJECTS) $(test_transport_api_unreliability_unix_LDADD) $(LIBS) -test_transport_api_unreliability_wlan$(EXEEXT): $(test_transport_api_unreliability_wlan_OBJECTS) $(test_transport_api_unreliability_wlan_DEPENDENCIES) +test_transport_api_unreliability_wlan$(EXEEXT): $(test_transport_api_unreliability_wlan_OBJECTS) $(test_transport_api_unreliability_wlan_DEPENDENCIES) $(EXTRA_test_transport_api_unreliability_wlan_DEPENDENCIES) @rm -f test_transport_api_unreliability_wlan$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_transport_api_unreliability_wlan_OBJECTS) $(test_transport_api_unreliability_wlan_LDADD) $(LIBS) -test_transport_api_wlan$(EXEEXT): $(test_transport_api_wlan_OBJECTS) $(test_transport_api_wlan_DEPENDENCIES) +test_transport_api_wlan$(EXEEXT): $(test_transport_api_wlan_OBJECTS) $(test_transport_api_wlan_DEPENDENCIES) $(EXTRA_test_transport_api_wlan_DEPENDENCIES) @rm -f test_transport_api_wlan$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_transport_api_wlan_OBJECTS) $(test_transport_api_wlan_LDADD) $(LIBS) -test_transport_startonly$(EXEEXT): $(test_transport_startonly_OBJECTS) $(test_transport_startonly_DEPENDENCIES) +test_transport_startonly$(EXEEXT): $(test_transport_startonly_OBJECTS) $(test_transport_startonly_DEPENDENCIES) $(EXTRA_test_transport_startonly_DEPENDENCIES) @rm -f test_transport_startonly$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_transport_startonly_OBJECTS) $(test_transport_startonly_LDADD) $(LIBS) -test_transport_testing$(EXEEXT): $(test_transport_testing_OBJECTS) $(test_transport_testing_DEPENDENCIES) +test_transport_testing$(EXEEXT): $(test_transport_testing_OBJECTS) $(test_transport_testing_DEPENDENCIES) $(EXTRA_test_transport_testing_DEPENDENCIES) @rm -f test_transport_testing$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_transport_testing_OBJECTS) $(test_transport_testing_LDADD) $(LIBS) +test_transport_testing_restart$(EXEEXT): $(test_transport_testing_restart_OBJECTS) $(test_transport_testing_restart_DEPENDENCIES) $(EXTRA_test_transport_testing_restart_DEPENDENCIES) + @rm -f test_transport_testing_restart$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_transport_testing_restart_OBJECTS) $(test_transport_testing_restart_LDADD) $(LIBS) +test_transport_testing_startstop$(EXEEXT): $(test_transport_testing_startstop_OBJECTS) $(test_transport_testing_startstop_DEPENDENCIES) $(EXTRA_test_transport_testing_startstop_DEPENDENCIES) + @rm -f test_transport_testing_startstop$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_transport_testing_startstop_OBJECTS) $(test_transport_testing_startstop_LDADD) $(LIBS) mostlyclean-compile: -rm -f *.$(OBJEXT) @@ -2195,34 +2677,43 @@ distclean-compile: @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-helper-transport-wlan-dummy.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-helper-transport-wlan.Po@am__quote@ -@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-service-transport.Po@am__quote@ -@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-service-transport_blacklist.Po@am__quote@ -@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-service-transport_clients.Po@am__quote@ -@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-service-transport_hello.Po@am__quote@ -@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-service-transport_neighbours.Po@am__quote@ -@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-service-transport_plugins.Po@am__quote@ -@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-service-transport_validation.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-transport-certificate-creation.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-transport-wlan-receiver.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-transport-wlan-sender.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-transport.Po@am__quote@ -@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libgnunet_plugin_transport_http_la-plugin_transport_http.Plo@am__quote@ -@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libgnunet_plugin_transport_http_la-plugin_transport_http_client.Plo@am__quote@ -@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libgnunet_plugin_transport_http_la-plugin_transport_http_server.Plo@am__quote@ -@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libgnunet_plugin_transport_https_la-plugin_transport_http.Plo@am__quote@ -@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libgnunet_plugin_transport_https_la-plugin_transport_http_client.Plo@am__quote@ -@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libgnunet_plugin_transport_https_la-plugin_transport_http_server.Plo@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet_service_transport-gnunet-service-transport.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet_service_transport-gnunet-service-transport_blacklist.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet_service_transport-gnunet-service-transport_clients.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet_service_transport-gnunet-service-transport_hello.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet_service_transport-gnunet-service-transport_manipulation.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet_service_transport-gnunet-service-transport_neighbours.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet_service_transport-gnunet-service-transport_plugins.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet_service_transport-gnunet-service-transport_validation.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libgnunet_plugin_transport_http_client_la-plugin_transport_http_client.Plo@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libgnunet_plugin_transport_http_client_la-plugin_transport_http_common.Plo@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libgnunet_plugin_transport_http_server_la-plugin_transport_http_common.Plo@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libgnunet_plugin_transport_http_server_la-plugin_transport_http_server.Plo@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libgnunet_plugin_transport_https_client_la-plugin_transport_http_client.Plo@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libgnunet_plugin_transport_https_client_la-plugin_transport_http_common.Plo@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libgnunet_plugin_transport_https_server_la-plugin_transport_http_common.Plo@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libgnunet_plugin_transport_https_server_la-plugin_transport_http_server.Plo@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/plugin_transport_http_common.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/plugin_transport_tcp.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/plugin_transport_template.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/plugin_transport_udp.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/plugin_transport_udp_broadcasting.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/plugin_transport_unix.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/plugin_transport_wlan.Plo@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_http_common.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_plugin_transport.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_quota_compliance.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_transport_api.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_transport_api_bidirectional_connect.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_transport_api_blacklisting.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_transport_api_disconnect.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_transport_api_limited_sockets.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_transport_api_manipulation_recv_tcp.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_transport_api_manipulation_send_tcp.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_transport_api_reliability.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_transport_api_restart_1peer.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_transport_api_restart_2peers.Po@am__quote@ @@ -2231,6 +2722,8 @@ distclean-compile: @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_transport_api_unreliability_constant.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_transport_startonly.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_transport_testing.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_transport_testing_restart.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_transport_testing_startstop.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/transport-testing.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/transport_api.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/transport_api_address_lookup.Plo@am__quote@ @@ -2240,74 +2733,191 @@ distclean-compile: .c.o: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c $< .c.obj: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'` @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c `$(CYGPATH_W) '$<'` +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c `$(CYGPATH_W) '$<'` .c.lo: @am__fastdepCC_TRUE@ $(AM_V_CC)$(LTCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LTCOMPILE) -c -o $@ $< + +libgnunet_plugin_transport_http_client_la-plugin_transport_http_client.lo: plugin_transport_http_client.c +@am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(libgnunet_plugin_transport_http_client_la_CPPFLAGS) $(CPPFLAGS) $(libgnunet_plugin_transport_http_client_la_CFLAGS) $(CFLAGS) -MT libgnunet_plugin_transport_http_client_la-plugin_transport_http_client.lo -MD -MP -MF $(DEPDIR)/libgnunet_plugin_transport_http_client_la-plugin_transport_http_client.Tpo -c -o libgnunet_plugin_transport_http_client_la-plugin_transport_http_client.lo `test -f 'plugin_transport_http_client.c' || echo '$(srcdir)/'`plugin_transport_http_client.c +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/libgnunet_plugin_transport_http_client_la-plugin_transport_http_client.Tpo $(DEPDIR)/libgnunet_plugin_transport_http_client_la-plugin_transport_http_client.Plo +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='plugin_transport_http_client.c' object='libgnunet_plugin_transport_http_client_la-plugin_transport_http_client.lo' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(libgnunet_plugin_transport_http_client_la_CPPFLAGS) $(CPPFLAGS) $(libgnunet_plugin_transport_http_client_la_CFLAGS) $(CFLAGS) -c -o libgnunet_plugin_transport_http_client_la-plugin_transport_http_client.lo `test -f 'plugin_transport_http_client.c' || echo '$(srcdir)/'`plugin_transport_http_client.c + +libgnunet_plugin_transport_http_client_la-plugin_transport_http_common.lo: plugin_transport_http_common.c +@am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(libgnunet_plugin_transport_http_client_la_CPPFLAGS) $(CPPFLAGS) $(libgnunet_plugin_transport_http_client_la_CFLAGS) $(CFLAGS) -MT libgnunet_plugin_transport_http_client_la-plugin_transport_http_common.lo -MD -MP -MF $(DEPDIR)/libgnunet_plugin_transport_http_client_la-plugin_transport_http_common.Tpo -c -o libgnunet_plugin_transport_http_client_la-plugin_transport_http_common.lo `test -f 'plugin_transport_http_common.c' || echo '$(srcdir)/'`plugin_transport_http_common.c +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/libgnunet_plugin_transport_http_client_la-plugin_transport_http_common.Tpo $(DEPDIR)/libgnunet_plugin_transport_http_client_la-plugin_transport_http_common.Plo +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='plugin_transport_http_common.c' object='libgnunet_plugin_transport_http_client_la-plugin_transport_http_common.lo' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(libgnunet_plugin_transport_http_client_la_CPPFLAGS) $(CPPFLAGS) $(libgnunet_plugin_transport_http_client_la_CFLAGS) $(CFLAGS) -c -o libgnunet_plugin_transport_http_client_la-plugin_transport_http_common.lo `test -f 'plugin_transport_http_common.c' || echo '$(srcdir)/'`plugin_transport_http_common.c + +libgnunet_plugin_transport_http_server_la-plugin_transport_http_server.lo: plugin_transport_http_server.c +@am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libgnunet_plugin_transport_http_server_la_CFLAGS) $(CFLAGS) -MT libgnunet_plugin_transport_http_server_la-plugin_transport_http_server.lo -MD -MP -MF $(DEPDIR)/libgnunet_plugin_transport_http_server_la-plugin_transport_http_server.Tpo -c -o libgnunet_plugin_transport_http_server_la-plugin_transport_http_server.lo `test -f 'plugin_transport_http_server.c' || echo '$(srcdir)/'`plugin_transport_http_server.c +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/libgnunet_plugin_transport_http_server_la-plugin_transport_http_server.Tpo $(DEPDIR)/libgnunet_plugin_transport_http_server_la-plugin_transport_http_server.Plo +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='plugin_transport_http_server.c' object='libgnunet_plugin_transport_http_server_la-plugin_transport_http_server.lo' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libgnunet_plugin_transport_http_server_la_CFLAGS) $(CFLAGS) -c -o libgnunet_plugin_transport_http_server_la-plugin_transport_http_server.lo `test -f 'plugin_transport_http_server.c' || echo '$(srcdir)/'`plugin_transport_http_server.c + +libgnunet_plugin_transport_http_server_la-plugin_transport_http_common.lo: plugin_transport_http_common.c +@am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libgnunet_plugin_transport_http_server_la_CFLAGS) $(CFLAGS) -MT libgnunet_plugin_transport_http_server_la-plugin_transport_http_common.lo -MD -MP -MF $(DEPDIR)/libgnunet_plugin_transport_http_server_la-plugin_transport_http_common.Tpo -c -o libgnunet_plugin_transport_http_server_la-plugin_transport_http_common.lo `test -f 'plugin_transport_http_common.c' || echo '$(srcdir)/'`plugin_transport_http_common.c +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/libgnunet_plugin_transport_http_server_la-plugin_transport_http_common.Tpo $(DEPDIR)/libgnunet_plugin_transport_http_server_la-plugin_transport_http_common.Plo +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='plugin_transport_http_common.c' object='libgnunet_plugin_transport_http_server_la-plugin_transport_http_common.lo' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libgnunet_plugin_transport_http_server_la_CFLAGS) $(CFLAGS) -c -o libgnunet_plugin_transport_http_server_la-plugin_transport_http_common.lo `test -f 'plugin_transport_http_common.c' || echo '$(srcdir)/'`plugin_transport_http_common.c + +libgnunet_plugin_transport_https_client_la-plugin_transport_http_client.lo: plugin_transport_http_client.c +@am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(libgnunet_plugin_transport_https_client_la_CPPFLAGS) $(CPPFLAGS) $(libgnunet_plugin_transport_https_client_la_CFLAGS) $(CFLAGS) -MT libgnunet_plugin_transport_https_client_la-plugin_transport_http_client.lo -MD -MP -MF $(DEPDIR)/libgnunet_plugin_transport_https_client_la-plugin_transport_http_client.Tpo -c -o libgnunet_plugin_transport_https_client_la-plugin_transport_http_client.lo `test -f 'plugin_transport_http_client.c' || echo '$(srcdir)/'`plugin_transport_http_client.c +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/libgnunet_plugin_transport_https_client_la-plugin_transport_http_client.Tpo $(DEPDIR)/libgnunet_plugin_transport_https_client_la-plugin_transport_http_client.Plo +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='plugin_transport_http_client.c' object='libgnunet_plugin_transport_https_client_la-plugin_transport_http_client.lo' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(libgnunet_plugin_transport_https_client_la_CPPFLAGS) $(CPPFLAGS) $(libgnunet_plugin_transport_https_client_la_CFLAGS) $(CFLAGS) -c -o libgnunet_plugin_transport_https_client_la-plugin_transport_http_client.lo `test -f 'plugin_transport_http_client.c' || echo '$(srcdir)/'`plugin_transport_http_client.c + +libgnunet_plugin_transport_https_client_la-plugin_transport_http_common.lo: plugin_transport_http_common.c +@am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(libgnunet_plugin_transport_https_client_la_CPPFLAGS) $(CPPFLAGS) $(libgnunet_plugin_transport_https_client_la_CFLAGS) $(CFLAGS) -MT libgnunet_plugin_transport_https_client_la-plugin_transport_http_common.lo -MD -MP -MF $(DEPDIR)/libgnunet_plugin_transport_https_client_la-plugin_transport_http_common.Tpo -c -o libgnunet_plugin_transport_https_client_la-plugin_transport_http_common.lo `test -f 'plugin_transport_http_common.c' || echo '$(srcdir)/'`plugin_transport_http_common.c +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/libgnunet_plugin_transport_https_client_la-plugin_transport_http_common.Tpo $(DEPDIR)/libgnunet_plugin_transport_https_client_la-plugin_transport_http_common.Plo +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='plugin_transport_http_common.c' object='libgnunet_plugin_transport_https_client_la-plugin_transport_http_common.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LTCOMPILE) -c -o $@ $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(libgnunet_plugin_transport_https_client_la_CPPFLAGS) $(CPPFLAGS) $(libgnunet_plugin_transport_https_client_la_CFLAGS) $(CFLAGS) -c -o libgnunet_plugin_transport_https_client_la-plugin_transport_http_common.lo `test -f 'plugin_transport_http_common.c' || echo '$(srcdir)/'`plugin_transport_http_common.c -libgnunet_plugin_transport_http_la-plugin_transport_http.lo: plugin_transport_http.c -@am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(libgnunet_plugin_transport_http_la_CPPFLAGS) $(CPPFLAGS) $(libgnunet_plugin_transport_http_la_CFLAGS) $(CFLAGS) -MT libgnunet_plugin_transport_http_la-plugin_transport_http.lo -MD -MP -MF $(DEPDIR)/libgnunet_plugin_transport_http_la-plugin_transport_http.Tpo -c -o libgnunet_plugin_transport_http_la-plugin_transport_http.lo `test -f 'plugin_transport_http.c' || echo '$(srcdir)/'`plugin_transport_http.c -@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/libgnunet_plugin_transport_http_la-plugin_transport_http.Tpo $(DEPDIR)/libgnunet_plugin_transport_http_la-plugin_transport_http.Plo -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='plugin_transport_http.c' object='libgnunet_plugin_transport_http_la-plugin_transport_http.lo' libtool=yes @AMDEPBACKSLASH@ +libgnunet_plugin_transport_https_server_la-plugin_transport_http_server.lo: plugin_transport_http_server.c +@am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libgnunet_plugin_transport_https_server_la_CFLAGS) $(CFLAGS) -MT libgnunet_plugin_transport_https_server_la-plugin_transport_http_server.lo -MD -MP -MF $(DEPDIR)/libgnunet_plugin_transport_https_server_la-plugin_transport_http_server.Tpo -c -o libgnunet_plugin_transport_https_server_la-plugin_transport_http_server.lo `test -f 'plugin_transport_http_server.c' || echo '$(srcdir)/'`plugin_transport_http_server.c +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/libgnunet_plugin_transport_https_server_la-plugin_transport_http_server.Tpo $(DEPDIR)/libgnunet_plugin_transport_https_server_la-plugin_transport_http_server.Plo +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='plugin_transport_http_server.c' object='libgnunet_plugin_transport_https_server_la-plugin_transport_http_server.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(libgnunet_plugin_transport_http_la_CPPFLAGS) $(CPPFLAGS) $(libgnunet_plugin_transport_http_la_CFLAGS) $(CFLAGS) -c -o libgnunet_plugin_transport_http_la-plugin_transport_http.lo `test -f 'plugin_transport_http.c' || echo '$(srcdir)/'`plugin_transport_http.c +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libgnunet_plugin_transport_https_server_la_CFLAGS) $(CFLAGS) -c -o libgnunet_plugin_transport_https_server_la-plugin_transport_http_server.lo `test -f 'plugin_transport_http_server.c' || echo '$(srcdir)/'`plugin_transport_http_server.c -libgnunet_plugin_transport_http_la-plugin_transport_http_client.lo: plugin_transport_http_client.c -@am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(libgnunet_plugin_transport_http_la_CPPFLAGS) $(CPPFLAGS) $(libgnunet_plugin_transport_http_la_CFLAGS) $(CFLAGS) -MT libgnunet_plugin_transport_http_la-plugin_transport_http_client.lo -MD -MP -MF $(DEPDIR)/libgnunet_plugin_transport_http_la-plugin_transport_http_client.Tpo -c -o libgnunet_plugin_transport_http_la-plugin_transport_http_client.lo `test -f 'plugin_transport_http_client.c' || echo '$(srcdir)/'`plugin_transport_http_client.c -@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/libgnunet_plugin_transport_http_la-plugin_transport_http_client.Tpo $(DEPDIR)/libgnunet_plugin_transport_http_la-plugin_transport_http_client.Plo -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='plugin_transport_http_client.c' object='libgnunet_plugin_transport_http_la-plugin_transport_http_client.lo' libtool=yes @AMDEPBACKSLASH@ +libgnunet_plugin_transport_https_server_la-plugin_transport_http_common.lo: plugin_transport_http_common.c +@am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libgnunet_plugin_transport_https_server_la_CFLAGS) $(CFLAGS) -MT libgnunet_plugin_transport_https_server_la-plugin_transport_http_common.lo -MD -MP -MF $(DEPDIR)/libgnunet_plugin_transport_https_server_la-plugin_transport_http_common.Tpo -c -o libgnunet_plugin_transport_https_server_la-plugin_transport_http_common.lo `test -f 'plugin_transport_http_common.c' || echo '$(srcdir)/'`plugin_transport_http_common.c +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/libgnunet_plugin_transport_https_server_la-plugin_transport_http_common.Tpo $(DEPDIR)/libgnunet_plugin_transport_https_server_la-plugin_transport_http_common.Plo +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='plugin_transport_http_common.c' object='libgnunet_plugin_transport_https_server_la-plugin_transport_http_common.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(libgnunet_plugin_transport_http_la_CPPFLAGS) $(CPPFLAGS) $(libgnunet_plugin_transport_http_la_CFLAGS) $(CFLAGS) -c -o libgnunet_plugin_transport_http_la-plugin_transport_http_client.lo `test -f 'plugin_transport_http_client.c' || echo '$(srcdir)/'`plugin_transport_http_client.c +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libgnunet_plugin_transport_https_server_la_CFLAGS) $(CFLAGS) -c -o libgnunet_plugin_transport_https_server_la-plugin_transport_http_common.lo `test -f 'plugin_transport_http_common.c' || echo '$(srcdir)/'`plugin_transport_http_common.c -libgnunet_plugin_transport_http_la-plugin_transport_http_server.lo: plugin_transport_http_server.c -@am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(libgnunet_plugin_transport_http_la_CPPFLAGS) $(CPPFLAGS) $(libgnunet_plugin_transport_http_la_CFLAGS) $(CFLAGS) -MT libgnunet_plugin_transport_http_la-plugin_transport_http_server.lo -MD -MP -MF $(DEPDIR)/libgnunet_plugin_transport_http_la-plugin_transport_http_server.Tpo -c -o libgnunet_plugin_transport_http_la-plugin_transport_http_server.lo `test -f 'plugin_transport_http_server.c' || echo '$(srcdir)/'`plugin_transport_http_server.c -@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/libgnunet_plugin_transport_http_la-plugin_transport_http_server.Tpo $(DEPDIR)/libgnunet_plugin_transport_http_la-plugin_transport_http_server.Plo -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='plugin_transport_http_server.c' object='libgnunet_plugin_transport_http_la-plugin_transport_http_server.lo' libtool=yes @AMDEPBACKSLASH@ +gnunet_service_transport-gnunet-service-transport.o: gnunet-service-transport.c +@am__fastdepCC_TRUE@ $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_transport_CFLAGS) $(CFLAGS) -MT gnunet_service_transport-gnunet-service-transport.o -MD -MP -MF $(DEPDIR)/gnunet_service_transport-gnunet-service-transport.Tpo -c -o gnunet_service_transport-gnunet-service-transport.o `test -f 'gnunet-service-transport.c' || echo '$(srcdir)/'`gnunet-service-transport.c +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/gnunet_service_transport-gnunet-service-transport.Tpo $(DEPDIR)/gnunet_service_transport-gnunet-service-transport.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='gnunet-service-transport.c' object='gnunet_service_transport-gnunet-service-transport.o' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(libgnunet_plugin_transport_http_la_CPPFLAGS) $(CPPFLAGS) $(libgnunet_plugin_transport_http_la_CFLAGS) $(CFLAGS) -c -o libgnunet_plugin_transport_http_la-plugin_transport_http_server.lo `test -f 'plugin_transport_http_server.c' || echo '$(srcdir)/'`plugin_transport_http_server.c +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_transport_CFLAGS) $(CFLAGS) -c -o gnunet_service_transport-gnunet-service-transport.o `test -f 'gnunet-service-transport.c' || echo '$(srcdir)/'`gnunet-service-transport.c -libgnunet_plugin_transport_https_la-plugin_transport_http.lo: plugin_transport_http.c -@am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(libgnunet_plugin_transport_https_la_CPPFLAGS) $(CPPFLAGS) $(libgnunet_plugin_transport_https_la_CFLAGS) $(CFLAGS) -MT libgnunet_plugin_transport_https_la-plugin_transport_http.lo -MD -MP -MF $(DEPDIR)/libgnunet_plugin_transport_https_la-plugin_transport_http.Tpo -c -o libgnunet_plugin_transport_https_la-plugin_transport_http.lo `test -f 'plugin_transport_http.c' || echo '$(srcdir)/'`plugin_transport_http.c -@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/libgnunet_plugin_transport_https_la-plugin_transport_http.Tpo $(DEPDIR)/libgnunet_plugin_transport_https_la-plugin_transport_http.Plo -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='plugin_transport_http.c' object='libgnunet_plugin_transport_https_la-plugin_transport_http.lo' libtool=yes @AMDEPBACKSLASH@ +gnunet_service_transport-gnunet-service-transport.obj: gnunet-service-transport.c +@am__fastdepCC_TRUE@ $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_transport_CFLAGS) $(CFLAGS) -MT gnunet_service_transport-gnunet-service-transport.obj -MD -MP -MF $(DEPDIR)/gnunet_service_transport-gnunet-service-transport.Tpo -c -o gnunet_service_transport-gnunet-service-transport.obj `if test -f 'gnunet-service-transport.c'; then $(CYGPATH_W) 'gnunet-service-transport.c'; else $(CYGPATH_W) '$(srcdir)/gnunet-service-transport.c'; fi` +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/gnunet_service_transport-gnunet-service-transport.Tpo $(DEPDIR)/gnunet_service_transport-gnunet-service-transport.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='gnunet-service-transport.c' object='gnunet_service_transport-gnunet-service-transport.obj' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(libgnunet_plugin_transport_https_la_CPPFLAGS) $(CPPFLAGS) $(libgnunet_plugin_transport_https_la_CFLAGS) $(CFLAGS) -c -o libgnunet_plugin_transport_https_la-plugin_transport_http.lo `test -f 'plugin_transport_http.c' || echo '$(srcdir)/'`plugin_transport_http.c +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_transport_CFLAGS) $(CFLAGS) -c -o gnunet_service_transport-gnunet-service-transport.obj `if test -f 'gnunet-service-transport.c'; then $(CYGPATH_W) 'gnunet-service-transport.c'; else $(CYGPATH_W) '$(srcdir)/gnunet-service-transport.c'; fi` -libgnunet_plugin_transport_https_la-plugin_transport_http_client.lo: plugin_transport_http_client.c -@am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(libgnunet_plugin_transport_https_la_CPPFLAGS) $(CPPFLAGS) $(libgnunet_plugin_transport_https_la_CFLAGS) $(CFLAGS) -MT libgnunet_plugin_transport_https_la-plugin_transport_http_client.lo -MD -MP -MF $(DEPDIR)/libgnunet_plugin_transport_https_la-plugin_transport_http_client.Tpo -c -o libgnunet_plugin_transport_https_la-plugin_transport_http_client.lo `test -f 'plugin_transport_http_client.c' || echo '$(srcdir)/'`plugin_transport_http_client.c -@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/libgnunet_plugin_transport_https_la-plugin_transport_http_client.Tpo $(DEPDIR)/libgnunet_plugin_transport_https_la-plugin_transport_http_client.Plo -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='plugin_transport_http_client.c' object='libgnunet_plugin_transport_https_la-plugin_transport_http_client.lo' libtool=yes @AMDEPBACKSLASH@ +gnunet_service_transport-gnunet-service-transport_blacklist.o: gnunet-service-transport_blacklist.c +@am__fastdepCC_TRUE@ $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_transport_CFLAGS) $(CFLAGS) -MT gnunet_service_transport-gnunet-service-transport_blacklist.o -MD -MP -MF $(DEPDIR)/gnunet_service_transport-gnunet-service-transport_blacklist.Tpo -c -o gnunet_service_transport-gnunet-service-transport_blacklist.o `test -f 'gnunet-service-transport_blacklist.c' || echo '$(srcdir)/'`gnunet-service-transport_blacklist.c +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/gnunet_service_transport-gnunet-service-transport_blacklist.Tpo $(DEPDIR)/gnunet_service_transport-gnunet-service-transport_blacklist.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='gnunet-service-transport_blacklist.c' object='gnunet_service_transport-gnunet-service-transport_blacklist.o' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(libgnunet_plugin_transport_https_la_CPPFLAGS) $(CPPFLAGS) $(libgnunet_plugin_transport_https_la_CFLAGS) $(CFLAGS) -c -o libgnunet_plugin_transport_https_la-plugin_transport_http_client.lo `test -f 'plugin_transport_http_client.c' || echo '$(srcdir)/'`plugin_transport_http_client.c +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_transport_CFLAGS) $(CFLAGS) -c -o gnunet_service_transport-gnunet-service-transport_blacklist.o `test -f 'gnunet-service-transport_blacklist.c' || echo '$(srcdir)/'`gnunet-service-transport_blacklist.c -libgnunet_plugin_transport_https_la-plugin_transport_http_server.lo: plugin_transport_http_server.c -@am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(libgnunet_plugin_transport_https_la_CPPFLAGS) $(CPPFLAGS) $(libgnunet_plugin_transport_https_la_CFLAGS) $(CFLAGS) -MT libgnunet_plugin_transport_https_la-plugin_transport_http_server.lo -MD -MP -MF $(DEPDIR)/libgnunet_plugin_transport_https_la-plugin_transport_http_server.Tpo -c -o libgnunet_plugin_transport_https_la-plugin_transport_http_server.lo `test -f 'plugin_transport_http_server.c' || echo '$(srcdir)/'`plugin_transport_http_server.c -@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/libgnunet_plugin_transport_https_la-plugin_transport_http_server.Tpo $(DEPDIR)/libgnunet_plugin_transport_https_la-plugin_transport_http_server.Plo -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='plugin_transport_http_server.c' object='libgnunet_plugin_transport_https_la-plugin_transport_http_server.lo' libtool=yes @AMDEPBACKSLASH@ +gnunet_service_transport-gnunet-service-transport_blacklist.obj: gnunet-service-transport_blacklist.c +@am__fastdepCC_TRUE@ $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_transport_CFLAGS) $(CFLAGS) -MT gnunet_service_transport-gnunet-service-transport_blacklist.obj -MD -MP -MF $(DEPDIR)/gnunet_service_transport-gnunet-service-transport_blacklist.Tpo -c -o gnunet_service_transport-gnunet-service-transport_blacklist.obj `if test -f 'gnunet-service-transport_blacklist.c'; then $(CYGPATH_W) 'gnunet-service-transport_blacklist.c'; else $(CYGPATH_W) '$(srcdir)/gnunet-service-transport_blacklist.c'; fi` +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/gnunet_service_transport-gnunet-service-transport_blacklist.Tpo $(DEPDIR)/gnunet_service_transport-gnunet-service-transport_blacklist.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='gnunet-service-transport_blacklist.c' object='gnunet_service_transport-gnunet-service-transport_blacklist.obj' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(libgnunet_plugin_transport_https_la_CPPFLAGS) $(CPPFLAGS) $(libgnunet_plugin_transport_https_la_CFLAGS) $(CFLAGS) -c -o libgnunet_plugin_transport_https_la-plugin_transport_http_server.lo `test -f 'plugin_transport_http_server.c' || echo '$(srcdir)/'`plugin_transport_http_server.c +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_transport_CFLAGS) $(CFLAGS) -c -o gnunet_service_transport-gnunet-service-transport_blacklist.obj `if test -f 'gnunet-service-transport_blacklist.c'; then $(CYGPATH_W) 'gnunet-service-transport_blacklist.c'; else $(CYGPATH_W) '$(srcdir)/gnunet-service-transport_blacklist.c'; fi` + +gnunet_service_transport-gnunet-service-transport_clients.o: gnunet-service-transport_clients.c +@am__fastdepCC_TRUE@ $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_transport_CFLAGS) $(CFLAGS) -MT gnunet_service_transport-gnunet-service-transport_clients.o -MD -MP -MF $(DEPDIR)/gnunet_service_transport-gnunet-service-transport_clients.Tpo -c -o gnunet_service_transport-gnunet-service-transport_clients.o `test -f 'gnunet-service-transport_clients.c' || echo '$(srcdir)/'`gnunet-service-transport_clients.c +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/gnunet_service_transport-gnunet-service-transport_clients.Tpo $(DEPDIR)/gnunet_service_transport-gnunet-service-transport_clients.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='gnunet-service-transport_clients.c' object='gnunet_service_transport-gnunet-service-transport_clients.o' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_transport_CFLAGS) $(CFLAGS) -c -o gnunet_service_transport-gnunet-service-transport_clients.o `test -f 'gnunet-service-transport_clients.c' || echo '$(srcdir)/'`gnunet-service-transport_clients.c + +gnunet_service_transport-gnunet-service-transport_clients.obj: gnunet-service-transport_clients.c +@am__fastdepCC_TRUE@ $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_transport_CFLAGS) $(CFLAGS) -MT gnunet_service_transport-gnunet-service-transport_clients.obj -MD -MP -MF $(DEPDIR)/gnunet_service_transport-gnunet-service-transport_clients.Tpo -c -o gnunet_service_transport-gnunet-service-transport_clients.obj `if test -f 'gnunet-service-transport_clients.c'; then $(CYGPATH_W) 'gnunet-service-transport_clients.c'; else $(CYGPATH_W) '$(srcdir)/gnunet-service-transport_clients.c'; fi` +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/gnunet_service_transport-gnunet-service-transport_clients.Tpo $(DEPDIR)/gnunet_service_transport-gnunet-service-transport_clients.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='gnunet-service-transport_clients.c' object='gnunet_service_transport-gnunet-service-transport_clients.obj' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_transport_CFLAGS) $(CFLAGS) -c -o gnunet_service_transport-gnunet-service-transport_clients.obj `if test -f 'gnunet-service-transport_clients.c'; then $(CYGPATH_W) 'gnunet-service-transport_clients.c'; else $(CYGPATH_W) '$(srcdir)/gnunet-service-transport_clients.c'; fi` + +gnunet_service_transport-gnunet-service-transport_hello.o: gnunet-service-transport_hello.c +@am__fastdepCC_TRUE@ $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_transport_CFLAGS) $(CFLAGS) -MT gnunet_service_transport-gnunet-service-transport_hello.o -MD -MP -MF $(DEPDIR)/gnunet_service_transport-gnunet-service-transport_hello.Tpo -c -o gnunet_service_transport-gnunet-service-transport_hello.o `test -f 'gnunet-service-transport_hello.c' || echo '$(srcdir)/'`gnunet-service-transport_hello.c +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/gnunet_service_transport-gnunet-service-transport_hello.Tpo $(DEPDIR)/gnunet_service_transport-gnunet-service-transport_hello.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='gnunet-service-transport_hello.c' object='gnunet_service_transport-gnunet-service-transport_hello.o' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_transport_CFLAGS) $(CFLAGS) -c -o gnunet_service_transport-gnunet-service-transport_hello.o `test -f 'gnunet-service-transport_hello.c' || echo '$(srcdir)/'`gnunet-service-transport_hello.c + +gnunet_service_transport-gnunet-service-transport_hello.obj: gnunet-service-transport_hello.c +@am__fastdepCC_TRUE@ $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_transport_CFLAGS) $(CFLAGS) -MT gnunet_service_transport-gnunet-service-transport_hello.obj -MD -MP -MF $(DEPDIR)/gnunet_service_transport-gnunet-service-transport_hello.Tpo -c -o gnunet_service_transport-gnunet-service-transport_hello.obj `if test -f 'gnunet-service-transport_hello.c'; then $(CYGPATH_W) 'gnunet-service-transport_hello.c'; else $(CYGPATH_W) '$(srcdir)/gnunet-service-transport_hello.c'; fi` +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/gnunet_service_transport-gnunet-service-transport_hello.Tpo $(DEPDIR)/gnunet_service_transport-gnunet-service-transport_hello.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='gnunet-service-transport_hello.c' object='gnunet_service_transport-gnunet-service-transport_hello.obj' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_transport_CFLAGS) $(CFLAGS) -c -o gnunet_service_transport-gnunet-service-transport_hello.obj `if test -f 'gnunet-service-transport_hello.c'; then $(CYGPATH_W) 'gnunet-service-transport_hello.c'; else $(CYGPATH_W) '$(srcdir)/gnunet-service-transport_hello.c'; fi` + +gnunet_service_transport-gnunet-service-transport_neighbours.o: gnunet-service-transport_neighbours.c +@am__fastdepCC_TRUE@ $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_transport_CFLAGS) $(CFLAGS) -MT gnunet_service_transport-gnunet-service-transport_neighbours.o -MD -MP -MF $(DEPDIR)/gnunet_service_transport-gnunet-service-transport_neighbours.Tpo -c -o gnunet_service_transport-gnunet-service-transport_neighbours.o `test -f 'gnunet-service-transport_neighbours.c' || echo '$(srcdir)/'`gnunet-service-transport_neighbours.c +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/gnunet_service_transport-gnunet-service-transport_neighbours.Tpo $(DEPDIR)/gnunet_service_transport-gnunet-service-transport_neighbours.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='gnunet-service-transport_neighbours.c' object='gnunet_service_transport-gnunet-service-transport_neighbours.o' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_transport_CFLAGS) $(CFLAGS) -c -o gnunet_service_transport-gnunet-service-transport_neighbours.o `test -f 'gnunet-service-transport_neighbours.c' || echo '$(srcdir)/'`gnunet-service-transport_neighbours.c + +gnunet_service_transport-gnunet-service-transport_neighbours.obj: gnunet-service-transport_neighbours.c +@am__fastdepCC_TRUE@ $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_transport_CFLAGS) $(CFLAGS) -MT gnunet_service_transport-gnunet-service-transport_neighbours.obj -MD -MP -MF $(DEPDIR)/gnunet_service_transport-gnunet-service-transport_neighbours.Tpo -c -o gnunet_service_transport-gnunet-service-transport_neighbours.obj `if test -f 'gnunet-service-transport_neighbours.c'; then $(CYGPATH_W) 'gnunet-service-transport_neighbours.c'; else $(CYGPATH_W) '$(srcdir)/gnunet-service-transport_neighbours.c'; fi` +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/gnunet_service_transport-gnunet-service-transport_neighbours.Tpo $(DEPDIR)/gnunet_service_transport-gnunet-service-transport_neighbours.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='gnunet-service-transport_neighbours.c' object='gnunet_service_transport-gnunet-service-transport_neighbours.obj' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_transport_CFLAGS) $(CFLAGS) -c -o gnunet_service_transport-gnunet-service-transport_neighbours.obj `if test -f 'gnunet-service-transport_neighbours.c'; then $(CYGPATH_W) 'gnunet-service-transport_neighbours.c'; else $(CYGPATH_W) '$(srcdir)/gnunet-service-transport_neighbours.c'; fi` + +gnunet_service_transport-gnunet-service-transport_plugins.o: gnunet-service-transport_plugins.c +@am__fastdepCC_TRUE@ $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_transport_CFLAGS) $(CFLAGS) -MT gnunet_service_transport-gnunet-service-transport_plugins.o -MD -MP -MF $(DEPDIR)/gnunet_service_transport-gnunet-service-transport_plugins.Tpo -c -o gnunet_service_transport-gnunet-service-transport_plugins.o `test -f 'gnunet-service-transport_plugins.c' || echo '$(srcdir)/'`gnunet-service-transport_plugins.c +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/gnunet_service_transport-gnunet-service-transport_plugins.Tpo $(DEPDIR)/gnunet_service_transport-gnunet-service-transport_plugins.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='gnunet-service-transport_plugins.c' object='gnunet_service_transport-gnunet-service-transport_plugins.o' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_transport_CFLAGS) $(CFLAGS) -c -o gnunet_service_transport-gnunet-service-transport_plugins.o `test -f 'gnunet-service-transport_plugins.c' || echo '$(srcdir)/'`gnunet-service-transport_plugins.c + +gnunet_service_transport-gnunet-service-transport_plugins.obj: gnunet-service-transport_plugins.c +@am__fastdepCC_TRUE@ $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_transport_CFLAGS) $(CFLAGS) -MT gnunet_service_transport-gnunet-service-transport_plugins.obj -MD -MP -MF $(DEPDIR)/gnunet_service_transport-gnunet-service-transport_plugins.Tpo -c -o gnunet_service_transport-gnunet-service-transport_plugins.obj `if test -f 'gnunet-service-transport_plugins.c'; then $(CYGPATH_W) 'gnunet-service-transport_plugins.c'; else $(CYGPATH_W) '$(srcdir)/gnunet-service-transport_plugins.c'; fi` +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/gnunet_service_transport-gnunet-service-transport_plugins.Tpo $(DEPDIR)/gnunet_service_transport-gnunet-service-transport_plugins.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='gnunet-service-transport_plugins.c' object='gnunet_service_transport-gnunet-service-transport_plugins.obj' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_transport_CFLAGS) $(CFLAGS) -c -o gnunet_service_transport-gnunet-service-transport_plugins.obj `if test -f 'gnunet-service-transport_plugins.c'; then $(CYGPATH_W) 'gnunet-service-transport_plugins.c'; else $(CYGPATH_W) '$(srcdir)/gnunet-service-transport_plugins.c'; fi` + +gnunet_service_transport-gnunet-service-transport_validation.o: gnunet-service-transport_validation.c +@am__fastdepCC_TRUE@ $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_transport_CFLAGS) $(CFLAGS) -MT gnunet_service_transport-gnunet-service-transport_validation.o -MD -MP -MF $(DEPDIR)/gnunet_service_transport-gnunet-service-transport_validation.Tpo -c -o gnunet_service_transport-gnunet-service-transport_validation.o `test -f 'gnunet-service-transport_validation.c' || echo '$(srcdir)/'`gnunet-service-transport_validation.c +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/gnunet_service_transport-gnunet-service-transport_validation.Tpo $(DEPDIR)/gnunet_service_transport-gnunet-service-transport_validation.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='gnunet-service-transport_validation.c' object='gnunet_service_transport-gnunet-service-transport_validation.o' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_transport_CFLAGS) $(CFLAGS) -c -o gnunet_service_transport-gnunet-service-transport_validation.o `test -f 'gnunet-service-transport_validation.c' || echo '$(srcdir)/'`gnunet-service-transport_validation.c + +gnunet_service_transport-gnunet-service-transport_validation.obj: gnunet-service-transport_validation.c +@am__fastdepCC_TRUE@ $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_transport_CFLAGS) $(CFLAGS) -MT gnunet_service_transport-gnunet-service-transport_validation.obj -MD -MP -MF $(DEPDIR)/gnunet_service_transport-gnunet-service-transport_validation.Tpo -c -o gnunet_service_transport-gnunet-service-transport_validation.obj `if test -f 'gnunet-service-transport_validation.c'; then $(CYGPATH_W) 'gnunet-service-transport_validation.c'; else $(CYGPATH_W) '$(srcdir)/gnunet-service-transport_validation.c'; fi` +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/gnunet_service_transport-gnunet-service-transport_validation.Tpo $(DEPDIR)/gnunet_service_transport-gnunet-service-transport_validation.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='gnunet-service-transport_validation.c' object='gnunet_service_transport-gnunet-service-transport_validation.obj' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_transport_CFLAGS) $(CFLAGS) -c -o gnunet_service_transport-gnunet-service-transport_validation.obj `if test -f 'gnunet-service-transport_validation.c'; then $(CYGPATH_W) 'gnunet-service-transport_validation.c'; else $(CYGPATH_W) '$(srcdir)/gnunet-service-transport_validation.c'; fi` + +gnunet_service_transport-gnunet-service-transport_manipulation.o: gnunet-service-transport_manipulation.c +@am__fastdepCC_TRUE@ $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_transport_CFLAGS) $(CFLAGS) -MT gnunet_service_transport-gnunet-service-transport_manipulation.o -MD -MP -MF $(DEPDIR)/gnunet_service_transport-gnunet-service-transport_manipulation.Tpo -c -o gnunet_service_transport-gnunet-service-transport_manipulation.o `test -f 'gnunet-service-transport_manipulation.c' || echo '$(srcdir)/'`gnunet-service-transport_manipulation.c +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/gnunet_service_transport-gnunet-service-transport_manipulation.Tpo $(DEPDIR)/gnunet_service_transport-gnunet-service-transport_manipulation.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='gnunet-service-transport_manipulation.c' object='gnunet_service_transport-gnunet-service-transport_manipulation.o' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_transport_CFLAGS) $(CFLAGS) -c -o gnunet_service_transport-gnunet-service-transport_manipulation.o `test -f 'gnunet-service-transport_manipulation.c' || echo '$(srcdir)/'`gnunet-service-transport_manipulation.c + +gnunet_service_transport-gnunet-service-transport_manipulation.obj: gnunet-service-transport_manipulation.c +@am__fastdepCC_TRUE@ $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_transport_CFLAGS) $(CFLAGS) -MT gnunet_service_transport-gnunet-service-transport_manipulation.obj -MD -MP -MF $(DEPDIR)/gnunet_service_transport-gnunet-service-transport_manipulation.Tpo -c -o gnunet_service_transport-gnunet-service-transport_manipulation.obj `if test -f 'gnunet-service-transport_manipulation.c'; then $(CYGPATH_W) 'gnunet-service-transport_manipulation.c'; else $(CYGPATH_W) '$(srcdir)/gnunet-service-transport_manipulation.c'; fi` +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/gnunet_service_transport-gnunet-service-transport_manipulation.Tpo $(DEPDIR)/gnunet_service_transport-gnunet-service-transport_manipulation.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='gnunet-service-transport_manipulation.c' object='gnunet_service_transport-gnunet-service-transport_manipulation.obj' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_transport_CFLAGS) $(CFLAGS) -c -o gnunet_service_transport-gnunet-service-transport_manipulation.obj `if test -f 'gnunet-service-transport_manipulation.c'; then $(CYGPATH_W) 'gnunet-service-transport_manipulation.c'; else $(CYGPATH_W) '$(srcdir)/gnunet-service-transport_manipulation.c'; fi` mostlyclean-libtool: -rm -f *.lo @@ -2316,8 +2926,11 @@ clean-libtool: -rm -rf .libs _libs install-pkgcfgDATA: $(pkgcfg_DATA) @$(NORMAL_INSTALL) - test -z "$(pkgcfgdir)" || $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" @list='$(pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(pkgcfgdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" || exit 1; \ + fi; \ for p in $$list; do \ if test -f "$$p"; then d=; else d="$(srcdir)/"; fi; \ echo "$$d$$p"; \ @@ -2331,9 +2944,7 @@ uninstall-pkgcfgDATA: @$(NORMAL_UNINSTALL) @list='$(pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ files=`for p in $$list; do echo $$p; done | sed -e 's|^.*/||'`; \ - test -n "$$files" || exit 0; \ - echo " ( cd '$(DESTDIR)$(pkgcfgdir)' && rm -f" $$files ")"; \ - cd "$(DESTDIR)$(pkgcfgdir)" && rm -f $$files + dir='$(DESTDIR)$(pkgcfgdir)'; $(am__uninstall_files_from_dir) ID: $(HEADERS) $(SOURCES) $(LISP) $(TAGS_FILES) list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ @@ -2468,14 +3079,15 @@ check-TESTS: $(TESTS) fi; \ dashes=`echo "$$dashes" | sed s/./=/g`; \ if test "$$failed" -eq 0; then \ - echo "$$grn$$dashes"; \ + col="$$grn"; \ else \ - echo "$$red$$dashes"; \ + col="$$red"; \ fi; \ - echo "$$banner"; \ - test -z "$$skipped" || echo "$$skipped"; \ - test -z "$$report" || echo "$$report"; \ - echo "$$dashes$$std"; \ + echo "$${col}$$dashes$${std}"; \ + echo "$${col}$$banner$${std}"; \ + test -z "$$skipped" || echo "$${col}$$skipped$${std}"; \ + test -z "$$report" || echo "$${col}$$report$${std}"; \ + echo "$${col}$$dashes$${std}"; \ test "$$failed" -eq 0; \ else :; fi @@ -2517,7 +3129,7 @@ all-am: Makefile $(LTLIBRARIES) $(PROGRAMS) $(DATA) install-binPROGRAMS: install-libLTLIBRARIES installdirs: - for dir in "$(DESTDIR)$(libdir)" "$(DESTDIR)$(plugindir)" "$(DESTDIR)$(bindir)" "$(DESTDIR)$(pkgcfgdir)"; do \ + for dir in "$(DESTDIR)$(libdir)" "$(DESTDIR)$(plugindir)" "$(DESTDIR)$(bindir)" "$(DESTDIR)$(libexecdir)" "$(DESTDIR)$(pkgcfgdir)"; do \ test -z "$$dir" || $(MKDIR_P) "$$dir"; \ done install: install-am @@ -2530,10 +3142,15 @@ install-am: all-am installcheck: installcheck-am install-strip: - $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ - install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ - `test -z '$(STRIP)' || \ - echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi mostlyclean-generic: clean-generic: @@ -2548,8 +3165,8 @@ maintainer-clean-generic: clean: clean-am clean-am: clean-binPROGRAMS clean-checkPROGRAMS clean-generic \ - clean-libLTLIBRARIES clean-libtool clean-noinstPROGRAMS \ - clean-pluginLTLIBRARIES mostlyclean-am + clean-libLTLIBRARIES clean-libexecPROGRAMS clean-libtool \ + clean-noinstPROGRAMS clean-pluginLTLIBRARIES mostlyclean-am distclean: distclean-am -rm -rf ./$(DEPDIR) @@ -2575,7 +3192,8 @@ install-dvi: install-dvi-am install-dvi-am: -install-exec-am: install-binPROGRAMS install-libLTLIBRARIES +install-exec-am: install-binPROGRAMS install-libLTLIBRARIES \ + install-libexecPROGRAMS @$(NORMAL_INSTALL) $(MAKE) $(AM_MAKEFLAGS) install-exec-hook install-html: install-html-am @@ -2617,32 +3235,34 @@ ps: ps-am ps-am: uninstall-am: uninstall-binPROGRAMS uninstall-libLTLIBRARIES \ - uninstall-pkgcfgDATA uninstall-pluginLTLIBRARIES + uninstall-libexecPROGRAMS uninstall-pkgcfgDATA \ + uninstall-pluginLTLIBRARIES .MAKE: check-am install-am install-exec-am install-strip .PHONY: CTAGS GTAGS all all-am check check-TESTS check-am clean \ clean-binPROGRAMS clean-checkPROGRAMS clean-generic \ - clean-libLTLIBRARIES clean-libtool clean-noinstPROGRAMS \ - clean-pluginLTLIBRARIES ctags distclean distclean-compile \ - distclean-generic distclean-libtool distclean-tags distdir dvi \ - dvi-am html html-am info info-am install install-am \ - install-binPROGRAMS install-data install-data-am install-dvi \ - install-dvi-am install-exec install-exec-am install-exec-hook \ - install-html install-html-am install-info install-info-am \ - install-libLTLIBRARIES install-man install-pdf install-pdf-am \ + clean-libLTLIBRARIES clean-libexecPROGRAMS clean-libtool \ + clean-noinstPROGRAMS clean-pluginLTLIBRARIES ctags distclean \ + distclean-compile distclean-generic distclean-libtool \ + distclean-tags distdir dvi dvi-am html html-am info info-am \ + install install-am install-binPROGRAMS install-data \ + install-data-am install-dvi install-dvi-am install-exec \ + install-exec-am install-exec-hook install-html install-html-am \ + install-info install-info-am install-libLTLIBRARIES \ + install-libexecPROGRAMS install-man install-pdf install-pdf-am \ install-pkgcfgDATA install-pluginLTLIBRARIES install-ps \ install-ps-am install-strip installcheck installcheck-am \ installdirs maintainer-clean maintainer-clean-generic \ mostlyclean mostlyclean-compile mostlyclean-generic \ mostlyclean-libtool pdf pdf-am ps ps-am tags uninstall \ uninstall-am uninstall-binPROGRAMS uninstall-libLTLIBRARIES \ - uninstall-pkgcfgDATA uninstall-pluginLTLIBRARIES + uninstall-libexecPROGRAMS uninstall-pkgcfgDATA \ + uninstall-pluginLTLIBRARIES @LINUX_TRUE@install-exec-hook: -@LINUX_TRUE@ $(SUDO_BINARY) chown root:root $(bindir)/gnunet-helper-transport-wlan || true -@LINUX_TRUE@ $(SUDO_BINARY) chmod u+s $(bindir)/gnunet-helper-transport-wlan || true +@LINUX_TRUE@ $(top_srcdir)/src/transport/install-wlan-helper.sh $(libexecdir) $(SUDO_BINARY) || true @LINUX_FALSE@install-exec-hook: # Tell versions [3.59,3.63) of GNU make to not export all variables. diff --git a/src/transport/gnunet-helper-transport-wlan.c b/src/transport/gnunet-helper-transport-wlan.c index 363925c..3ad4d64 100644 --- a/src/transport/gnunet-helper-transport-wlan.c +++ b/src/transport/gnunet-helper-transport-wlan.c @@ -109,8 +109,7 @@ /* * parts taken from aircrack-ng, parts changend. */ - -#define _GNU_SOURCE +#include "gnunet_config.h" #include #include #include @@ -138,6 +137,14 @@ #include "gnunet_protocols.h" #include "plugin_transport_wlan.h" +/** + * Packet format type for the messages we receive from + * the kernel. This is for Ethernet 10Mbps format (no + * performance information included). + */ +#define ARPHRD_ETHER 1 + + /** * Packet format type for the messages we receive from * the kernel. This is for plain messages (with no @@ -145,6 +152,7 @@ */ #define ARPHRD_IEEE80211 801 + /** * Packet format type for the messages we receive from * the kernel. This is for the PRISM format. @@ -1589,6 +1597,15 @@ linux_read (struct HardwareInfos *dev, case ARPHRD_IEEE80211: n = 0; /* no header */ break; + case ARPHRD_ETHER: + { + if (sizeof (struct GNUNET_TRANSPORT_WLAN_Ieee8023Frame) > caplen) + return 0; /* invalid */ + memcpy (&buf[sizeof (struct GNUNET_TRANSPORT_WLAN_Ieee80211Frame)], + tmpbuf + sizeof (struct GNUNET_TRANSPORT_WLAN_Ieee8023Frame), + caplen - sizeof (struct GNUNET_TRANSPORT_WLAN_Ieee8023Frame) - 4 /* 4 byte FCS */); + return caplen - sizeof (struct GNUNET_TRANSPORT_WLAN_Ieee8023Frame) - 4; + } default: errno = ENOTSUP; /* unsupported format */ return -1; @@ -1652,6 +1669,16 @@ open_device_raw (struct HardwareInfos *dev) IFNAMSIZ, dev->iface, strerror (errno)); return 1; } + if (((ifr.ifr_hwaddr.sa_family != ARPHRD_IEEE80211) && + (ifr.ifr_hwaddr.sa_family != ARPHRD_ETHER) && + (ifr.ifr_hwaddr.sa_family != ARPHRD_IEEE80211_PRISM) && + (ifr.ifr_hwaddr.sa_family != ARPHRD_IEEE80211_FULL)) ) + { + fprintf (stderr, "Error: interface `%.*s' is not using a supported hardware address family (got %d)\n", + IFNAMSIZ, dev->iface, + ifr.ifr_hwaddr.sa_family); + return 1; + } /* lookup iw mode */ memset (&wrq, 0, sizeof (struct iwreq)); @@ -1663,13 +1690,12 @@ open_device_raw (struct HardwareInfos *dev) wrq.u.mode = IW_MODE_MONITOR; } - if (((ifr.ifr_hwaddr.sa_family != ARPHRD_IEEE80211) && - (ifr.ifr_hwaddr.sa_family != ARPHRD_IEEE80211_PRISM) && - (ifr.ifr_hwaddr.sa_family != ARPHRD_IEEE80211_FULL)) || - (wrq.u.mode != IW_MODE_MONITOR)) + if ( (wrq.u.mode != IW_MODE_MONITOR) && + (wrq.u.mode != IW_MODE_ADHOC) ) { - fprintf (stderr, "Error: interface `%.*s' is not in monitor mode\n", - IFNAMSIZ, dev->iface); + fprintf (stderr, "Error: interface `%.*s' is not in monitor or ad-hoc mode (got %d)\n", + IFNAMSIZ, dev->iface, + wrq.u.mode); return 1; } @@ -1705,7 +1731,8 @@ open_device_raw (struct HardwareInfos *dev) memcpy (&dev->pl_mac, ifr.ifr_hwaddr.sa_data, MAC_ADDR_SIZE); dev->arptype_in = ifr.ifr_hwaddr.sa_family; - if ((ifr.ifr_hwaddr.sa_family != ARPHRD_IEEE80211) && + if ((ifr.ifr_hwaddr.sa_family != ARPHRD_ETHER) && + (ifr.ifr_hwaddr.sa_family != ARPHRD_IEEE80211) && (ifr.ifr_hwaddr.sa_family != ARPHRD_IEEE80211_PRISM) && (ifr.ifr_hwaddr.sa_family != ARPHRD_IEEE80211_FULL)) { @@ -1771,6 +1798,12 @@ static int mac_test (const struct GNUNET_TRANSPORT_WLAN_Ieee80211Frame *taIeeeHeader, const struct HardwareInfos *dev) { + static struct GNUNET_TRANSPORT_WLAN_MacAddress all_zeros; + + if ( (0 == memcmp (&taIeeeHeader->addr3, &all_zeros, MAC_ADDR_SIZE)) || + (0 == memcmp (&taIeeeHeader->addr1, &all_zeros, MAC_ADDR_SIZE)) ) + return 0; /* some drivers set no Macs, then assume it is all for us! */ + if (0 != memcmp (&taIeeeHeader->addr3, &mac_bssid_gnunet, MAC_ADDR_SIZE)) return 1; /* not a GNUnet ad-hoc package */ if ( (0 == memcmp (&taIeeeHeader->addr1, &dev->pl_mac, MAC_ADDR_SIZE)) || @@ -1812,6 +1845,7 @@ stdin_send_hw (void *cls, const struct GNUNET_MessageHeader *hdr) struct GNUNET_TRANSPORT_WLAN_Ieee80211Frame *wlanheader; size_t sendsize; struct RadiotapTransmissionHeader rtheader; + struct GNUNET_TRANSPORT_WLAN_Ieee8023Frame etheader; sendsize = ntohs (hdr->size); if ( (sendsize < @@ -1828,21 +1862,41 @@ stdin_send_hw (void *cls, const struct GNUNET_MessageHeader *hdr) exit (1); } header = (const struct GNUNET_TRANSPORT_WLAN_RadiotapSendMessage *) hdr; - rtheader.header.it_version = 0; - rtheader.header.it_pad = 0; - rtheader.header.it_len = GNUNET_htole16 (sizeof (rtheader)); - rtheader.header.it_present = GNUNET_htole16 (IEEE80211_RADIOTAP_OUR_TRANSMISSION_HEADER_MASK); - rtheader.rate = header->rate; - rtheader.pad1 = 0; - rtheader.txflags = GNUNET_htole16 (IEEE80211_RADIOTAP_F_TX_NOACK | IEEE80211_RADIOTAP_F_TX_NOSEQ); - memcpy (write_pout.buf, &rtheader, sizeof (rtheader)); - memcpy (&write_pout.buf[sizeof (rtheader)], &header->frame, sendsize); - wlanheader = (struct GNUNET_TRANSPORT_WLAN_Ieee80211Frame *) &write_pout.buf[sizeof (rtheader)]; - - /* payload contains MAC address, but we don't trust it, so we'll - * overwrite it with OUR MAC address to prevent mischief */ - mac_set (wlanheader, dev); - write_pout.size = sendsize + sizeof (rtheader); + switch (dev->arptype_in) + { + case ARPHRD_IEEE80211_PRISM: + case ARPHRD_IEEE80211_FULL: + case ARPHRD_IEEE80211: + rtheader.header.it_version = 0; + rtheader.header.it_pad = 0; + rtheader.header.it_len = GNUNET_htole16 (sizeof (rtheader)); + rtheader.header.it_present = GNUNET_htole16 (IEEE80211_RADIOTAP_OUR_TRANSMISSION_HEADER_MASK); + rtheader.rate = header->rate; + rtheader.pad1 = 0; + rtheader.txflags = GNUNET_htole16 (IEEE80211_RADIOTAP_F_TX_NOACK | IEEE80211_RADIOTAP_F_TX_NOSEQ); + memcpy (write_pout.buf, &rtheader, sizeof (rtheader)); + memcpy (&write_pout.buf[sizeof (rtheader)], &header->frame, sendsize); + wlanheader = (struct GNUNET_TRANSPORT_WLAN_Ieee80211Frame *) &write_pout.buf[sizeof (rtheader)]; + + /* payload contains MAC address, but we don't trust it, so we'll + * overwrite it with OUR MAC address to prevent mischief */ + mac_set (wlanheader, dev); + write_pout.size = sendsize + sizeof (rtheader); + break; + case ARPHRD_ETHER: + etheader.dst = header->frame.addr1; + /* etheader.src = header->frame.addr2; --- untrusted input */ + etheader.src = dev->pl_mac; + etheader.type = htons (ETH_P_IP); + memcpy (write_pout.buf, ðeader, sizeof (etheader)); + memcpy (&write_pout.buf[sizeof (etheader)], &header[1], sendsize - sizeof (struct GNUNET_TRANSPORT_WLAN_Ieee80211Frame)); + write_pout.size = sendsize - sizeof (struct GNUNET_TRANSPORT_WLAN_Ieee80211Frame) + sizeof (etheader); + break; + default: + fprintf (stderr, + "Unsupported ARPTYPE!\n"); + break; + } } @@ -1867,33 +1921,29 @@ main (int argc, char *argv[]) int stdin_open; struct MessageStreamTokenizer *stdin_mst; int raw_eno; + uid_t uid; - memset (&dev, 0, sizeof (dev)); - dev.fd_raw = socket (PF_PACKET, SOCK_RAW, htons (ETH_P_ALL)); - raw_eno = errno; /* remember for later */ - - /* drop privs */ - { - uid_t uid = getuid (); + /* assert privs so we can modify the firewall rules! */ + uid = getuid (); #ifdef HAVE_SETRESUID - if (0 != setresuid (uid, uid, uid)) - { - fprintf (stderr, "Failed to setresuid: %s\n", strerror (errno)); - if (-1 != dev.fd_raw) - (void) close (dev.fd_raw); - return 1; - } + if (0 != setresuid (uid, 0, 0)) + { + fprintf (stderr, "Failed to setresuid to root: %s\n", strerror (errno)); + return 254; + } #else - if (0 != (setuid (uid) | seteuid (uid))) - { - fprintf (stderr, "Failed to setuid: %s\n", strerror (errno)); - if (-1 != dev.fd_raw) - (void) close (dev.fd_raw); - return 1; - } + if (0 != seteuid (0)) + { + fprintf (stderr, "Failed to seteuid back to root: %s\n", strerror (errno)); + return 254; } #endif + /* make use of SGID capabilities on POSIX */ + memset (&dev, 0, sizeof (dev)); + dev.fd_raw = socket (PF_PACKET, SOCK_RAW, htons (ETH_P_ALL)); + raw_eno = errno; /* remember for later */ + /* now that we've dropped root rights, we can do error checking */ if (2 != argc) { @@ -1928,6 +1978,29 @@ main (int argc, char *argv[]) return 1; } + /* drop privs */ + { + uid_t uid = getuid (); +#ifdef HAVE_SETRESUID + if (0 != setresuid (uid, uid, uid)) + { + fprintf (stderr, "Failed to setresuid: %s\n", strerror (errno)); + if (-1 != dev.fd_raw) + (void) close (dev.fd_raw); + return 1; + } +#else + if (0 != (setuid (uid) | seteuid (uid))) + { + fprintf (stderr, "Failed to setuid: %s\n", strerror (errno)); + if (-1 != dev.fd_raw) + (void) close (dev.fd_raw); + return 1; + } +#endif + } + + /* send MAC address of the WLAN interface to STDOUT first */ { struct GNUNET_TRANSPORT_WLAN_HelperControlMessage macmsg; diff --git a/src/transport/gnunet-service-transport.c b/src/transport/gnunet-service-transport.c index c200cb5..e64cbfb 100644 --- a/src/transport/gnunet-service-transport.c +++ b/src/transport/gnunet-service-transport.c @@ -37,6 +37,7 @@ #include "gnunet-service-transport_neighbours.h" #include "gnunet-service-transport_plugins.h" #include "gnunet-service-transport_validation.h" +#include "gnunet-service-transport_manipulation.h" #include "transport.h" /* globals */ @@ -61,6 +62,16 @@ struct GNUNET_PeerIdentity GST_my_identity; */ struct GNUNET_PEERINFO_Handle *GST_peerinfo; +/** + * Hostkey generation context + */ +struct GNUNET_CRYPTO_RsaKeyGenerationContext *GST_keygen; + +/** + * Handle to our service's server. + */ +static struct GNUNET_SERVER_Handle *GST_server; + /** * Our public key. */ @@ -81,6 +92,11 @@ struct GNUNET_ATS_SchedulingHandle *GST_ats; */ static int connections; +/** + * Hello address expiration + */ +struct GNUNET_TIME_Relative hello_expiration; + /** * Transmit our HELLO message to the given (connected) neighbour. @@ -90,17 +106,21 @@ static int connections; * @param ats performance information (unused) * @param ats_count number of records in ats (unused) * @param address the address + * @param bandwidth_in inbound quota in NBO + * @param bandwidth_out outbound quota in NBO */ static void transmit_our_hello (void *cls, const struct GNUNET_PeerIdentity *target, const struct GNUNET_ATS_Information *ats, uint32_t ats_count, - const struct GNUNET_HELLO_Address *address) + const struct GNUNET_HELLO_Address *address, + struct GNUNET_BANDWIDTH_Value32NBO bandwidth_in, + struct GNUNET_BANDWIDTH_Value32NBO bandwidth_out) { const struct GNUNET_MessageHeader *hello = cls; GST_neighbours_send (target, (const char *) hello, ntohs (hello->size), - GNUNET_CONSTANTS_HELLO_ADDRESS_EXPIRATION, NULL, NULL); + hello_expiration, NULL, NULL); } @@ -179,6 +199,7 @@ process_payload (const struct GNUNET_PeerIdentity *peer, htonl ((uint32_t) GST_neighbour_get_latency (peer).rel_value); memcpy (&ap[ats_count + 1], message, ntohs (message->size)); + GNUNET_ATS_address_add (GST_ats, address, session, ap, ats_count + 1); GNUNET_ATS_address_update (GST_ats, address, session, ap, ats_count + 1); GST_clients_broadcast (&im->header, GNUNET_YES); @@ -209,8 +230,8 @@ process_payload (const struct GNUNET_PeerIdentity *peer, * @return how long the plugin should wait until receiving more data * (plugins that do not support this, can ignore the return value) */ -static struct GNUNET_TIME_Relative -plugin_env_receive_callback (void *cls, const struct GNUNET_PeerIdentity *peer, +struct GNUNET_TIME_Relative +GST_receive_callback (void *cls, const struct GNUNET_PeerIdentity *peer, const struct GNUNET_MessageHeader *message, const struct GNUNET_ATS_Information *ats, uint32_t ats_count, struct Session *session, @@ -287,11 +308,6 @@ plugin_env_receive_callback (void *cls, const struct GNUNET_PeerIdentity *peer, break; } end: -#if 1 - /* FIXME: this should not be needed, and not sure it's good to have it, but without - * this connections seem to go extra-slow */ - GNUNET_ATS_address_update (GST_ats, &address, session, ats, ats_count); -#endif GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Allowing receive from peer %s to continue in %llu ms\n", GNUNET_i2s (peer), (unsigned long long) ret.rel_value); @@ -309,16 +325,17 @@ end: * @param addr one of the addresses of the host * the specific address format depends on the transport * @param addrlen length of the address + * @param dest_plugin destination plugin to use this address with */ static void plugin_env_address_change_notification (void *cls, int add_remove, - const void *addr, size_t addrlen) + const void *addr, size_t addrlen, + const char *dest_plugin) { - const char *plugin_name = cls; struct GNUNET_HELLO_Address address; address.peer = GST_my_identity; - address.transport_name = plugin_name; + address.transport_name = dest_plugin; address.address = addr; address.address_length = addrlen; GST_hello_modify_addresses (add_remove, &address); @@ -346,7 +363,7 @@ plugin_env_session_end (void *cls, const struct GNUNET_PeerIdentity *peer, struct GNUNET_HELLO_Address address; GNUNET_assert (strlen (transport_name) > 0); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Session %X to peer `%s' ended \n", + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Session %p to peer `%s' ended \n", session, GNUNET_i2s (peer)); if (NULL != session) GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG | GNUNET_ERROR_TYPE_BULK, @@ -358,6 +375,8 @@ plugin_env_session_end (void *cls, const struct GNUNET_PeerIdentity *peer, address.address_length = 0; address.transport_name = transport_name; GST_neighbours_session_terminated (peer, session); + + /* Tell ATS that session has ended */ GNUNET_ATS_address_destroyed (GST_ats, &address, session); } @@ -392,7 +411,7 @@ plugin_env_address_to_type (void *cls, addrlen, GNUNET_a2s(addr, addrlen)); GNUNET_break (0); - return (const struct GNUNET_ATS_Information) ats; + return ats; } return GNUNET_ATS_address_get_type(GST_ats, addr, addrlen); } @@ -448,12 +467,16 @@ ats_request_address_change (void *cls, * @param peer the peer that connected * @param ats performance data * @param ats_count number of entries in ats + * @param bandwidth_in inbound bandwidth in NBO + * @param bandwidth_out outbound bandwidth in NBO */ static void neighbours_connect_notification (void *cls, const struct GNUNET_PeerIdentity *peer, const struct GNUNET_ATS_Information *ats, - uint32_t ats_count) + uint32_t ats_count, + struct GNUNET_BANDWIDTH_Value32NBO bandwidth_in, + struct GNUNET_BANDWIDTH_Value32NBO bandwidth_out) { size_t len = sizeof (struct ConnectInfoMessage) + @@ -471,6 +494,8 @@ neighbours_connect_notification (void *cls, connect_msg->header.type = htons (GNUNET_MESSAGE_TYPE_TRANSPORT_CONNECT); connect_msg->ats_count = htonl (ats_count); connect_msg->id = *peer; + connect_msg->quota_in = bandwidth_in; + connect_msg->quota_out = bandwidth_out; ap = (struct GNUNET_ATS_Information *) &connect_msg[1]; memcpy (ap, ats, ats_count * sizeof (struct GNUNET_ATS_Information)); GST_clients_broadcast (&connect_msg->header, GNUNET_NO); @@ -530,6 +555,11 @@ neighbours_address_notification (void *cls, static void shutdown_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { + if (NULL != GST_keygen) + { + GNUNET_CRYPTO_rsa_key_create_stop (GST_keygen); + GST_keygen = NULL; + } GST_neighbours_stop (); GST_validation_stop (); GST_plugins_unload (); @@ -539,61 +569,64 @@ shutdown_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) GST_clients_stop (); GST_blacklist_stop (); GST_hello_stop (); + GST_manipulation_stop (); - if (GST_peerinfo != NULL) + if (NULL != GST_peerinfo) { GNUNET_PEERINFO_disconnect (GST_peerinfo); GST_peerinfo = NULL; } - if (GST_stats != NULL) + if (NULL != GST_stats) { GNUNET_STATISTICS_destroy (GST_stats, GNUNET_NO); GST_stats = NULL; } - if (GST_my_private_key != NULL) + if (NULL != GST_my_private_key) { GNUNET_CRYPTO_rsa_key_free (GST_my_private_key); GST_my_private_key = NULL; } + GST_server = NULL; } /** - * Initiate transport service. + * Callback for hostkey read/generation * - * @param cls closure - * @param server the initialized server - * @param c configuration to use + * @param cls NULL + * @param pk the private key + * @param emsg error message */ static void -run (void *cls, struct GNUNET_SERVER_Handle *server, - const struct GNUNET_CONFIGURATION_Handle *c) +key_generation_cb (void *cls, + struct GNUNET_CRYPTO_RsaPrivateKey *pk, + const char *emsg) { - char *keyfile; struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded tmp; - /* setup globals */ - GST_cfg = c; - if (GNUNET_OK != - GNUNET_CONFIGURATION_get_value_filename (c, "GNUNETD", "HOSTKEY", - &keyfile)) + long long unsigned int max_fd_cfg; + int max_fd_rlimit; + int max_fd; + + GST_keygen = NULL; + if (NULL == pk) { GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - _ - ("Transport service is lacking key configuration settings. Exiting.\n")); + _("Transport service could not access hostkey: %s. Exiting.\n"), + emsg); GNUNET_SCHEDULER_shutdown (); return; } - GST_my_private_key = GNUNET_CRYPTO_rsa_key_create_from_file (keyfile); - GNUNET_free (keyfile); - if (GST_my_private_key == NULL) + GST_my_private_key = pk; + + GST_stats = GNUNET_STATISTICS_create ("transport", GST_cfg); + if (NULL == GST_stats) { GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - _("Transport service could not access hostkey. Exiting.\n")); + _("Could not access STATISTICS service. Exiting.\n")); GNUNET_SCHEDULER_shutdown (); return; } - GST_stats = GNUNET_STATISTICS_create ("transport", c); - GST_peerinfo = GNUNET_PEERINFO_connect (c); + GST_peerinfo = GNUNET_PEERINFO_connect (GST_cfg); memset (&GST_my_public_key, '\0', sizeof (GST_my_public_key)); memset (&tmp, '\0', sizeof (tmp)); GNUNET_CRYPTO_rsa_key_get_public (GST_my_private_key, &GST_my_public_key); @@ -605,7 +638,7 @@ run (void *cls, struct GNUNET_SERVER_Handle *server, GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, &shutdown_task, NULL); - if (GST_peerinfo == NULL) + if (NULL == GST_peerinfo) { GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("Could not access PEERINFO service. Exiting.\n")); @@ -613,22 +646,97 @@ run (void *cls, struct GNUNET_SERVER_Handle *server, return; } + max_fd_rlimit = 0; + max_fd_cfg = 0; + max_fd = 0; +#if HAVE_GETRLIMIT + struct rlimit r_file; + if (0 == getrlimit (RLIMIT_NOFILE, &r_file)) + { + max_fd_rlimit = r_file.rlim_cur; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Maximum number of open files was: %u/%u\n", r_file.rlim_cur, + r_file.rlim_max); + } + max_fd_rlimit = (9 * max_fd_rlimit) / 10; /* Keep 10% for rest of transport */ +#endif + GNUNET_CONFIGURATION_get_value_number (GST_cfg, "transport", "MAX_FD", &max_fd_cfg); + + if (max_fd_cfg > max_fd_rlimit) + max_fd = max_fd_cfg; + else + max_fd = max_fd_rlimit; + if (max_fd < DEFAULT_MAX_FDS) + max_fd = DEFAULT_MAX_FDS; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Limiting number of sockets to %u: validation %u, neighbors: %u\n", + max_fd, (max_fd / 3) , (max_fd / 3) * 2); + /* start subsystems */ GST_hello_start (&process_hello_update, NULL); GNUNET_assert (NULL != GST_hello_get()); - GST_blacklist_start (server); + GST_blacklist_start (GST_server); GST_ats = GNUNET_ATS_scheduling_init (GST_cfg, &ats_request_address_change, NULL); - GST_plugins_load (&plugin_env_receive_callback, + GST_manipulation_init (); + GST_plugins_load (&GST_manipulation_recv, &plugin_env_address_change_notification, &plugin_env_session_end, &plugin_env_address_to_type); GST_neighbours_start (NULL, &neighbours_connect_notification, &neighbours_disconnect_notification, - &neighbours_address_notification); - GST_clients_start (server); - GST_validation_start (); + &neighbours_address_notification, + (max_fd / 3) * 2); + GST_clients_start (GST_server); + GST_validation_start ((max_fd / 3)); + if (NULL != GST_server) + GNUNET_SERVER_resume (GST_server); +} + + +/** + * Initiate transport service. + * + * @param cls closure + * @param server the initialized server + * @param c configuration to use + */ +static void +run (void *cls, struct GNUNET_SERVER_Handle *server, + const struct GNUNET_CONFIGURATION_Handle *c) +{ + char *keyfile; + + /* setup globals */ + GST_cfg = c; + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_filename (c, "GNUNETD", "HOSTKEY", + &keyfile)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _ + ("Transport service is lacking key configuration settings. Exiting.\n")); + GNUNET_SCHEDULER_shutdown (); + return; + } + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_time (c, "transport", "HELLO_EXPIRATION", + &hello_expiration)) + { + hello_expiration = GNUNET_CONSTANTS_HELLO_ADDRESS_EXPIRATION; + } + GST_server = server; + GNUNET_SERVER_suspend (server); + GST_keygen = GNUNET_CRYPTO_rsa_key_create_start (keyfile, &key_generation_cb, NULL); + GNUNET_free (keyfile); + if (NULL == GST_keygen) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Transport service is unable to access hostkey. Exiting.\n")); + GNUNET_SCHEDULER_shutdown (); + } } diff --git a/src/transport/gnunet-service-transport.h b/src/transport/gnunet-service-transport.h index adc28ba..abc473e 100644 --- a/src/transport/gnunet-service-transport.h +++ b/src/transport/gnunet-service-transport.h @@ -67,6 +67,37 @@ extern struct GNUNET_CRYPTO_RsaPrivateKey *GST_my_private_key; */ extern struct GNUNET_ATS_SchedulingHandle *GST_ats; +/** + * Function called by the transport for each received message. + * This function should also be called with "NULL" for the + * message to signal that the other peer disconnected. + * + * @param cls closure, const char* with the name of the plugin we received the message from + * @param peer (claimed) identity of the other peer + * @param message the message, NULL if we only care about + * learning about the delay until we should receive again -- FIXME! + * @param ats performance information + * @param ats_count number of records in ats + * @param session identifier used for this session (NULL for plugins + * that do not offer bi-directional communication to the sender + * using the same "connection") + * @param sender_address binary address of the sender (if we established the + * connection or are otherwise sure of it; should be NULL + * for inbound TCP/UDP connections since it it not clear + * that we could establish ourselves a connection to that + * IP address and get the same system) + * @param sender_address_len number of bytes in sender_address + * @return how long the plugin should wait until receiving more data + * (plugins that do not support this, can ignore the return value) + */ +struct GNUNET_TIME_Relative +GST_receive_callback (void *cls, const struct GNUNET_PeerIdentity *peer, + const struct GNUNET_MessageHeader *message, + const struct GNUNET_ATS_Information *ats, + uint32_t ats_count, struct Session *session, + const char *sender_address, + uint16_t sender_address_len); + #endif /* end of file gnunet-service-transport_plugins.h */ diff --git a/src/transport/gnunet-service-transport_blacklist.c b/src/transport/gnunet-service-transport_blacklist.c index 8c36888..479b30e 100644 --- a/src/transport/gnunet-service-transport_blacklist.c +++ b/src/transport/gnunet-service-transport_blacklist.c @@ -230,15 +230,15 @@ read_blacklist_file () GNUNET_CONFIGURATION_get_value_filename (GST_cfg, "TRANSPORT", "BLACKLIST_FILE", &fn)) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Option `%s' in section `%s' not specified!\n", - "BLACKLIST_FILE", "TRANSPORT"); + GNUNET_log_config_missing (GNUNET_ERROR_TYPE_DEBUG, + "transport", "BLACKLIST_FILE"); return; } if (GNUNET_OK != GNUNET_DISK_file_test (fn)) - GNUNET_DISK_fn_write (fn, NULL, 0, - GNUNET_DISK_PERM_USER_READ | - GNUNET_DISK_PERM_USER_WRITE); + { + GNUNET_free (fn); + return; /* no blacklist */ + } if (GNUNET_OK != GNUNET_DISK_file_size (fn, &fsize, GNUNET_NO, GNUNET_YES)) { @@ -247,9 +247,9 @@ read_blacklist_file () GNUNET_free (fn); return; } - if (fsize == 0) + if (0 == fsize) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, _("Blacklist file `%s' is empty.\n"), + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Blacklist file `%s' is empty.\n", fn); GNUNET_free (fn); return; @@ -395,7 +395,7 @@ GST_blacklist_start (struct GNUNET_SERVER_Handle *server) * @return GNUNET_OK (continue to iterate) */ static int -free_blacklist_entry (void *cls, const GNUNET_HashCode * key, void *value) +free_blacklist_entry (void *cls, const struct GNUNET_HashCode * key, void *value) { char *be = value; @@ -543,12 +543,16 @@ struct TestConnectionContext * @param ats performance data * @param ats_count number of entries in ats (excluding 0-termination) * @param address the address + * @param bandwidth_in inbound quota in NBO + * @param bandwidth_out outbound quota in NBO */ static void test_connection_ok (void *cls, const struct GNUNET_PeerIdentity *neighbour, const struct GNUNET_ATS_Information *ats, uint32_t ats_count, - const struct GNUNET_HELLO_Address *address) + const struct GNUNET_HELLO_Address *address, + struct GNUNET_BANDWIDTH_Value32NBO bandwidth_in, + struct GNUNET_BANDWIDTH_Value32NBO bandwidth_out) { struct TestConnectionContext *tcc = cls; struct GST_BlacklistCheck *bc; @@ -684,7 +688,8 @@ GST_blacklist_add_peer (const struct GNUNET_PeerIdentity *peer, GNUNET_i2s (peer), transport_name); if (blacklist == NULL) blacklist = - GNUNET_CONTAINER_multihashmap_create (TRANSPORT_BLACKLIST_HT_SIZE); + GNUNET_CONTAINER_multihashmap_create (TRANSPORT_BLACKLIST_HT_SIZE, + GNUNET_NO); GNUNET_CONTAINER_multihashmap_put (blacklist, &peer->hashPubKey, GNUNET_strdup (transport_name), GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE); @@ -701,7 +706,7 @@ GST_blacklist_add_peer (const struct GNUNET_PeerIdentity *peer, * @return GNUNET_OK if the entry does not match, GNUNET_NO if it matches */ static int -test_blacklisted (void *cls, const GNUNET_HashCode * key, void *value) +test_blacklisted (void *cls, const struct GNUNET_HashCode * key, void *value) { const char *transport_name = cls; char *be = value; diff --git a/src/transport/gnunet-service-transport_clients.c b/src/transport/gnunet-service-transport_clients.c index b298195..23fc727 100644 --- a/src/transport/gnunet-service-transport_clients.c +++ b/src/transport/gnunet-service-transport_clients.c @@ -30,9 +30,11 @@ #include "gnunet-service-transport_neighbours.h" #include "gnunet-service-transport_plugins.h" #include "gnunet-service-transport_validation.h" +#include "gnunet-service-transport_manipulation.h" #include "gnunet-service-transport.h" #include "transport.h" + /** * How many messages can we have pending for a given client process * before we start to drop incoming messages? We typically should @@ -115,6 +117,26 @@ struct TransportClient int send_payload; }; +/** + * Context for address to string operations + */ +struct AddressToStringContext +{ + /** + * This is a doubly-linked list. + */ + struct AddressToStringContext *next; + + /** + * This is a doubly-linked list. + */ + struct AddressToStringContext *prev; + + /** + * Transmission context + */ + struct GNUNET_SERVER_TransmitContext* tc; +}; /** * Client monitoring changes of active addresses of our neighbours. @@ -155,6 +177,16 @@ static struct TransportClient *clients_head; */ static struct TransportClient *clients_tail; +/** + * Head of linked list of all pending address iterations + */ +struct AddressToStringContext *a2s_head; + +/** + * Tail of linked list of all pending address iterations + */ +struct AddressToStringContext *a2s_tail; + /** * Head of linked list of monitoring clients. */ @@ -250,6 +282,7 @@ setup_monitoring_client (struct GNUNET_SERVER_Client *client, struct GNUNET_PeerIdentity *peer) { struct MonitoringClient *mc; + static struct GNUNET_PeerIdentity all_zeros; GNUNET_assert (lookup_monitoring_client (client) == NULL); mc = GNUNET_malloc (sizeof (struct MonitoringClient)); @@ -260,9 +293,13 @@ setup_monitoring_client (struct GNUNET_SERVER_Client *client, mc); GNUNET_SERVER_notification_context_add (nc, client); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Client %p started monitoring of the peer `%s'\n", - mc, GNUNET_i2s (peer)); + if (0 != memcmp (peer, &all_zeros, sizeof (struct GNUNET_PeerIdentity))) + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Client %p started monitoring of the peer `%s'\n", + mc, GNUNET_i2s (peer)); + else + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Client %p started monitoring all peers\n", mc); return mc; } @@ -431,13 +468,17 @@ client_disconnect_notification (void *cls, struct GNUNET_SERVER_Client *client) * @param ats performance data * @param ats_count number of entries in ats (excluding 0-termination) * @param address the address + * @param bandwidth_in inbound bandwidth in NBO + * @param bandwidth_out outbound bandwidth in NBO */ static void notify_client_about_neighbour (void *cls, const struct GNUNET_PeerIdentity *peer, const struct GNUNET_ATS_Information *ats, uint32_t ats_count, - const struct GNUNET_HELLO_Address *address) + const struct GNUNET_HELLO_Address *address, + struct GNUNET_BANDWIDTH_Value32NBO bandwidth_in, + struct GNUNET_BANDWIDTH_Value32NBO bandwidth_out) { struct TransportClient *tc = cls; struct ConnectInfoMessage *cim; @@ -453,6 +494,8 @@ notify_client_about_neighbour (void *cls, cim->header.type = htons (GNUNET_MESSAGE_TYPE_TRANSPORT_CONNECT); cim->ats_count = htonl (ats_count); cim->id = *peer; + cim->quota_in = bandwidth_in; + cim->quota_out = bandwidth_out; ap = (struct GNUNET_ATS_Information *) &cim[1]; memcpy (ap, ats, ats_count * sizeof (struct GNUNET_ATS_Information)); unicast (tc, &cim->header, GNUNET_NO); @@ -553,15 +596,28 @@ struct SendTransmitContinuationContext * * @param cls closure * @param success GNUNET_OK on success, GNUNET_NO on failure, GNUNET_SYSERR if we're not connected + * @param bytes_payload bytes payload sent + * @param bytes_on_wire bytes sent on wire */ static void -handle_send_transmit_continuation (void *cls, int success) +handle_send_transmit_continuation (void *cls, int success, + size_t bytes_payload, size_t bytes_on_wire) { struct SendTransmitContinuationContext *stcc = cls; struct SendOkMessage send_ok_msg; + //GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Payload: %u, On wire %u result: %i\n", bytes_payload, bytes_on_wire, success); + /* + if (GNUNET_OK == success) + GNUNET_assert (bytes_on_wire >= bytes_payload); + + else + GNUNET_assert (bytes_on_wire <= bytes_payload); +*/ send_ok_msg.header.size = htons (sizeof (send_ok_msg)); send_ok_msg.header.type = htons (GNUNET_MESSAGE_TYPE_TRANSPORT_SEND_OK); + send_ok_msg.bytes_msg = htonl (bytes_payload); + send_ok_msg.bytes_physical = htonl (bytes_on_wire); send_ok_msg.success = htonl (success); send_ok_msg.latency = GNUNET_TIME_relative_hton (GNUNET_TIME_UNIT_FOREVER_REL); @@ -638,7 +694,7 @@ clients_handle_send (void *cls, struct GNUNET_SERVER_Client *client, stcc->target = obm->peer; stcc->client = client; GNUNET_SERVER_client_keep (client); - GST_neighbours_send (&obm->peer, obmm, msize, + GST_manipulation_send (&obm->peer, obmm, msize, GNUNET_TIME_relative_ntoh (obm->timeout), &handle_send_transmit_continuation, stcc); } @@ -700,16 +756,17 @@ clients_handle_request_connect (void *cls, struct GNUNET_SERVER_Client *client, static void transmit_address_to_client (void *cls, const char *buf) { - struct GNUNET_SERVER_TransmitContext *tc = cls; - + struct AddressToStringContext *actx = cls; if (NULL == buf) { - GNUNET_SERVER_transmit_context_append_data (tc, NULL, 0, + GNUNET_SERVER_transmit_context_append_data (actx->tc, NULL, 0, GNUNET_MESSAGE_TYPE_TRANSPORT_ADDRESS_TO_STRING_REPLY); - GNUNET_SERVER_transmit_context_run (tc, GNUNET_TIME_UNIT_FOREVER_REL); + GNUNET_SERVER_transmit_context_run (actx->tc, GNUNET_TIME_UNIT_FOREVER_REL); + GNUNET_CONTAINER_DLL_remove (a2s_head, a2s_tail, actx); + GNUNET_free (actx); return; } - GNUNET_SERVER_transmit_context_append_data (tc, buf, strlen (buf) + 1, + GNUNET_SERVER_transmit_context_append_data (actx->tc, buf, strlen (buf) + 1, GNUNET_MESSAGE_TYPE_TRANSPORT_ADDRESS_TO_STRING_REPLY); } @@ -733,6 +790,7 @@ clients_handle_address_to_string (void *cls, uint32_t address_len; uint16_t size; struct GNUNET_SERVER_TransmitContext *tc; + struct AddressToStringContext *actx; struct GNUNET_TIME_Relative rtimeout; int32_t numeric; @@ -763,7 +821,7 @@ clients_handle_address_to_string (void *cls, rtimeout = GNUNET_TIME_relative_ntoh (alum->timeout); numeric = ntohs (alum->numeric_only); tc = GNUNET_SERVER_transmit_context_create (client); - papi = GST_plugins_find (plugin_name); + papi = GST_plugins_printer_find (plugin_name); if (NULL == papi) { GNUNET_SERVER_transmit_context_append_data (tc, NULL, 0, @@ -771,10 +829,13 @@ clients_handle_address_to_string (void *cls, GNUNET_SERVER_transmit_context_run (tc, rtimeout); return; } + actx = GNUNET_malloc (sizeof (struct AddressToStringContext)); + actx->tc = tc; + GNUNET_CONTAINER_DLL_insert (a2s_head, a2s_tail, actx); GNUNET_SERVER_disable_receive_done_warning (client); papi->address_pretty_printer (papi->cls, plugin_name, address, address_len, numeric, rtimeout, &transmit_address_to_client, - tc); + actx); } @@ -832,11 +893,15 @@ compose_address_iterate_response_message (const struct GNUNET_PeerIdentity * @param ats performance data * @param ats_count number of entries in ats (excluding 0-termination) * @param address the address + * @param bandwidth_in inbound quota in NBO + * @param bandwidth_out outbound quota in NBO */ static void output_address (void *cls, const struct GNUNET_PeerIdentity *peer, const struct GNUNET_ATS_Information *ats, uint32_t ats_count, - const struct GNUNET_HELLO_Address *address) + const struct GNUNET_HELLO_Address *address, + struct GNUNET_BANDWIDTH_Value32NBO bandwidth_in, + struct GNUNET_BANDWIDTH_Value32NBO bandwidth_out) { struct GNUNET_SERVER_TransmitContext *tc = cls; struct AddressIterateResponseMessage *msg; @@ -900,7 +965,9 @@ clients_handle_address_iterate (void *cls, struct GNUNET_SERVER_Client *client, /* just return one neighbour */ address = GST_neighbour_get_current_address (&msg->peer); if (address != NULL) - output_address (tc, &msg->peer, NULL, 0, address); + output_address (tc, &msg->peer, NULL, 0, address, + GNUNET_CONSTANTS_DEFAULT_BW_IN_OUT, + GNUNET_CONSTANTS_DEFAULT_BW_IN_OUT); } if (GNUNET_YES != ntohl (msg->one_shot)) setup_monitoring_client (client, &msg->peer); @@ -940,6 +1007,8 @@ GST_clients_start (struct GNUNET_SERVER_Handle *server) {&GST_blacklist_handle_reply, NULL, GNUNET_MESSAGE_TYPE_TRANSPORT_BLACKLIST_REPLY, sizeof (struct BlacklistMessage)}, + {&GST_manipulation_set_metric, NULL, + GNUNET_MESSAGE_TYPE_TRANSPORT_TRAFFIC_METRIC, 0}, {NULL, NULL, 0, 0} }; nc = GNUNET_SERVER_notification_context_create (server, 0); @@ -955,6 +1024,15 @@ GST_clients_start (struct GNUNET_SERVER_Handle *server) void GST_clients_stop () { + struct AddressToStringContext *cur; + + while (NULL != (cur = a2s_head)) + { + GNUNET_SERVER_transmit_context_destroy (cur->tc, GNUNET_NO); + GNUNET_CONTAINER_DLL_remove (a2s_head, a2s_tail, cur); + GNUNET_free (cur); + } + if (NULL != nc) { GNUNET_SERVER_notification_context_destroy (nc); @@ -962,7 +1040,6 @@ GST_clients_stop () } } - /** * Broadcast the given message to all of our clients. * @@ -1018,7 +1095,6 @@ GST_clients_broadcast_address_notification (const struct GNUNET_PeerIdentity struct AddressIterateResponseMessage *msg; struct MonitoringClient *mc; static struct GNUNET_PeerIdentity all_zeros; - msg = compose_address_iterate_response_message (peer, address); mc = monitoring_clients_head; while (mc != NULL) diff --git a/src/transport/gnunet-service-transport_clients.h b/src/transport/gnunet-service-transport_clients.h index 9556620..25d0758 100644 --- a/src/transport/gnunet-service-transport_clients.h +++ b/src/transport/gnunet-service-transport_clients.h @@ -31,6 +31,7 @@ #include "gnunet_hello_lib.h" + /** * Start handling requests from clients. * diff --git a/src/transport/gnunet-service-transport_hello.c b/src/transport/gnunet-service-transport_hello.c index 870c083..247fbc8 100644 --- a/src/transport/gnunet-service-transport_hello.c +++ b/src/transport/gnunet-service-transport_hello.c @@ -38,6 +38,11 @@ */ #define HELLO_REFRESH_PERIOD GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_HOURS, 6) +/** + * Hello address expiration + */ +extern struct GNUNET_TIME_Relative hello_expiration; + /** * Entry in linked list of network addresses for ourselves. Also @@ -159,9 +164,7 @@ refresh_hello_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) hello_task = GNUNET_SCHEDULER_NO_TASK; gc.addr_pos = oal_head; - gc.expiration = - GNUNET_TIME_relative_to_absolute - (GNUNET_CONSTANTS_HELLO_ADDRESS_EXPIRATION); + gc.expiration = GNUNET_TIME_relative_to_absolute (hello_expiration); GNUNET_free (our_hello); our_hello = GNUNET_HELLO_create (&GST_my_public_key, &address_generator, &gc); diff --git a/src/transport/gnunet-service-transport_manipulation.c b/src/transport/gnunet-service-transport_manipulation.c new file mode 100644 index 0000000..34c8ab1 --- /dev/null +++ b/src/transport/gnunet-service-transport_manipulation.c @@ -0,0 +1,336 @@ +/* + This file is part of GNUnet. + (C) 2010,2011 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @file transport/gnunet-service-transport_manipulation.c + * @brief transport component manipulation traffic for simulation + * @author Christian Grothoff + * @author Matthias Wachs + */ +#include "platform.h" +#include "gnunet-service-transport_blacklist.h" +#include "gnunet-service-transport_clients.h" +#include "gnunet-service-transport_hello.h" +#include "gnunet-service-transport_neighbours.h" +#include "gnunet-service-transport_plugins.h" +#include "gnunet-service-transport_validation.h" +#include "gnunet-service-transport.h" +#include "transport.h" + +static struct GNUNET_CONTAINER_MultiHashMap *peers; + +#define DELAY 0 +#define DISTANCE 1 + +struct TM_Peer; + +struct DelayQueueEntry +{ + struct DelayQueueEntry *prev; + struct DelayQueueEntry *next; + struct TM_Peer *tmp; + struct GNUNET_TIME_Absolute sent_at; + void *msg; + size_t msg_size; + struct GNUNET_TIME_Relative timeout; + GST_NeighbourSendContinuation cont; + void *cont_cls; +}; + +struct TM_Peer +{ + struct GNUNET_PeerIdentity peer; + uint32_t metrics [TM_BOTH][GNUNET_ATS_QualityPropertiesCount]; + GNUNET_SCHEDULER_TaskIdentifier send_delay_task; + struct DelayQueueEntry *send_head; + struct DelayQueueEntry *send_tail; +}; + + + +static void +set_delay(struct TM_Peer *tmp, struct GNUNET_PeerIdentity *peer, int direction, uint32_t value) +{ + uint32_t val; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Set traffic metrics %s for peer `%s' in direction %s to %u\n", + "DELAY", GNUNET_i2s(peer), + (TM_BOTH == direction) ? "BOTH" : (TM_SEND == direction) ? "SEND": "RECEIVE", value); + + if (UINT32_MAX == value) + val = UINT32_MAX - 1; /* prevent overflow */ + else if (0 == value) + val = UINT32_MAX; /* disable */ + else + val = value; + + switch (direction) { + case TM_BOTH: + tmp->metrics[TM_SEND][DELAY] = val; + tmp->metrics[TM_RECEIVE][DELAY] = val; + break; + case TM_SEND: + tmp->metrics[TM_SEND][DELAY] = val; + break; + case TM_RECEIVE: + tmp->metrics[TM_RECEIVE][DELAY] = val; + break; + default: + break; + } + +} + +static void +set_distance (struct TM_Peer *tmp, struct GNUNET_PeerIdentity *peer, int direction, uint32_t value) +{ + uint32_t val; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Set traffic metrics %s for peer `%s' in direction %s to %u\n", + "DISTANCE", GNUNET_i2s(peer), + (TM_BOTH == direction) ? "BOTH" : (TM_SEND == direction) ? "SEND": "RECEIVE", value); + + if (UINT32_MAX == value) + val = UINT32_MAX - 1; /* prevent overflow */ + else if (0 == value) + val = UINT32_MAX; /* disable */ + else + val = value; + + switch (direction) { + case TM_BOTH: + tmp->metrics[TM_SEND][DISTANCE] = val; + tmp->metrics[TM_RECEIVE][DISTANCE] = val; + break; + case TM_SEND: + tmp->metrics[TM_SEND][DISTANCE] = val; + break; + case TM_RECEIVE: + tmp->metrics[TM_RECEIVE][DISTANCE] = val; + break; + default: + break; + } +} + +void +GST_manipulation_set_metric (void *cls, struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) +{ + struct TrafficMetricMessage *tm = (struct TrafficMetricMessage *) message; + struct GNUNET_ATS_Information *ats; + struct TM_Peer *tmp; + uint32_t type; + uint32_t value; + int c; + int c2; + + if (0 == ntohs (tm->ats_count)) + GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received traffic metrics for peer `%s'\n", + GNUNET_i2s(&tm->peer)); + + if (NULL == (tmp = GNUNET_CONTAINER_multihashmap_get (peers, &tm->peer.hashPubKey))) + { + tmp = GNUNET_malloc (sizeof (struct TM_Peer)); + tmp->peer = (tm->peer); + for (c = 0; c < TM_BOTH; c++) + { + for (c2 = 0; c2 < GNUNET_ATS_QualityPropertiesCount; c2++) + { + tmp->metrics[c][c2] = UINT32_MAX; + } + } + GNUNET_CONTAINER_multihashmap_put (peers, &tm->peer.hashPubKey, tmp, GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_FAST); + } + + ats = (struct GNUNET_ATS_Information *) &tm[1]; + for (c = 0; c < ntohs (tm->ats_count); c++) + { + type = htonl (ats[c].type); + value = htonl (ats[c].value); + switch (type) { + case GNUNET_ATS_QUALITY_NET_DELAY: + set_delay (tmp, &tm->peer, ntohs (tm->direction), value); + break; + case GNUNET_ATS_QUALITY_NET_DISTANCE: + set_distance (tmp, &tm->peer, ntohs (tm->direction), value); + break; + default: + break; + } + } + + GNUNET_SERVER_receive_done (client, GNUNET_OK); +} + +static void +send_delayed (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct DelayQueueEntry *dqe = cls; + struct DelayQueueEntry *next; + struct TM_Peer *tmp = dqe->tmp; + struct GNUNET_TIME_Relative delay; + tmp->send_delay_task = GNUNET_SCHEDULER_NO_TASK; + GNUNET_CONTAINER_DLL_remove (tmp->send_head, tmp->send_tail, dqe); + GST_neighbours_send (&tmp->peer, dqe->msg, dqe->msg_size, dqe->timeout, dqe->cont, dqe->cont_cls); + + next = tmp->send_head; + if (NULL != next) + { + /* More delayed messages */ + delay = GNUNET_TIME_absolute_get_remaining (next->sent_at); + tmp->send_delay_task = GNUNET_SCHEDULER_add_delayed (delay, &send_delayed, dqe); + } + + GNUNET_free (dqe); +} + +void +GST_manipulation_send (const struct GNUNET_PeerIdentity *target, const void *msg, + size_t msg_size, struct GNUNET_TIME_Relative timeout, + GST_NeighbourSendContinuation cont, void *cont_cls) +{ + struct TM_Peer *tmp; + struct DelayQueueEntry *dqe; + struct GNUNET_TIME_Relative delay; + + if (NULL != (tmp = GNUNET_CONTAINER_multihashmap_get (peers, &target->hashPubKey))) + { + /* Manipulate here */ + /* Delay */ + if (UINT32_MAX != tmp->metrics[TM_SEND][DELAY]) + { + /* We have a delay */ + delay.rel_value = tmp->metrics[TM_SEND][DELAY]; + dqe = GNUNET_malloc (sizeof (struct DelayQueueEntry) + msg_size); + dqe->tmp = tmp; + dqe->sent_at = GNUNET_TIME_absolute_add (GNUNET_TIME_absolute_get(), delay); + dqe->cont = cont; + dqe->cont_cls = cont_cls; + dqe->msg = &dqe[1]; + dqe->msg_size = msg_size; + dqe->timeout = timeout; + memcpy (dqe->msg, msg, msg_size); + GNUNET_CONTAINER_DLL_insert_tail (tmp->send_head, tmp->send_tail, dqe); + if (GNUNET_SCHEDULER_NO_TASK == tmp->send_delay_task) + tmp->send_delay_task =GNUNET_SCHEDULER_add_delayed (delay, &send_delayed, dqe); + return; + } + } + /* Normal sending */ + GST_neighbours_send (target, msg, msg_size, timeout, cont, cont_cls); +} + +struct GNUNET_TIME_Relative +GST_manipulation_recv (void *cls, const struct GNUNET_PeerIdentity *peer, + const struct GNUNET_MessageHeader *message, + const struct GNUNET_ATS_Information *ats, + uint32_t ats_count, struct Session *session, + const char *sender_address, + uint16_t sender_address_len) +{ + struct TM_Peer *tmp; + int d; + struct GNUNET_ATS_Information ats_new[ats_count]; + struct GNUNET_TIME_Relative q_delay; + struct GNUNET_TIME_Relative m_delay; + + for (d = 0; d < ats_count; d++) + + if (NULL != (tmp = GNUNET_CONTAINER_multihashmap_get (peers, &peer->hashPubKey))) + { + /* Manipulate distance */ + for (d = 0; d < ats_count; d++) + { + ats_new[d] = ats[d]; + /* Set distance */ + if ((ntohl(ats[d].type) == GNUNET_ATS_QUALITY_NET_DISTANCE) && + (UINT32_MAX != tmp->metrics[TM_RECEIVE][DISTANCE])) + ats_new[d].value = htonl(tmp->metrics[TM_RECEIVE][DISTANCE]); + } + /* Manipulate receive delay */ + if (UINT32_MAX != tmp->metrics[TM_RECEIVE][DELAY]) + { + m_delay.rel_value = tmp->metrics[TM_RECEIVE][DELAY]; + q_delay = GST_receive_callback (cls, peer, message, &ats_new[0], ats_count, + session, sender_address, sender_address_len); + + if (q_delay.rel_value >= m_delay.rel_value) + { + return q_delay; + } + else + { + return m_delay; + } + } + else + return GST_receive_callback (cls, peer, message, &ats_new[0], ats_count, + session, sender_address, sender_address_len); + } + + return GST_receive_callback (cls, peer, message, ats, ats_count, + session, sender_address, sender_address_len); +} + +void +GST_manipulation_init () +{ + peers = GNUNET_CONTAINER_multihashmap_create (10, GNUNET_NO); +} + +int free_tmps (void *cls, + const struct GNUNET_HashCode * key, + void *value) +{ + struct DelayQueueEntry *dqe; + struct DelayQueueEntry *next; + if (NULL != value) + { + struct TM_Peer *tmp = (struct TM_Peer *) value; + GNUNET_CONTAINER_multihashmap_remove (peers, key, value); + next = tmp->send_head; + while (NULL != (dqe = next)) + { + next = dqe->next; + GNUNET_CONTAINER_DLL_remove (tmp->send_head, tmp->send_tail, dqe); + GNUNET_free (dqe); + } + if (GNUNET_SCHEDULER_NO_TASK != tmp->send_delay_task) + { + GNUNET_SCHEDULER_cancel (tmp->send_delay_task); + tmp->send_delay_task = GNUNET_SCHEDULER_NO_TASK; + } + GNUNET_free (tmp); + } + return GNUNET_OK; +} + +void +GST_manipulation_stop () +{ + GNUNET_CONTAINER_multihashmap_iterate (peers, &free_tmps,NULL); + + GNUNET_CONTAINER_multihashmap_destroy (peers); + peers = NULL; +} + + +/* end of file gnunet-service-transport_manipulation.c */ diff --git a/src/transport/gnunet-service-transport_manipulation.h b/src/transport/gnunet-service-transport_manipulation.h new file mode 100644 index 0000000..f8faa85 --- /dev/null +++ b/src/transport/gnunet-service-transport_manipulation.h @@ -0,0 +1,63 @@ +/* + This file is part of GNUnet. + (C) 2010,2011 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @file transport/gnunet-service-transport_neighbours.h + * @brief neighbour management API + * @author Christian Grothoff + */ +#ifndef GNUNET_SERVICE_TRANSPORT_MANIPULATION_H +#define GNUNET_SERVICE_TRANSPORT_MANIPULATION_H + +#include "platform.h" +#include "gnunet-service-transport_blacklist.h" +#include "gnunet-service-transport_clients.h" +#include "gnunet-service-transport_hello.h" +#include "gnunet-service-transport_neighbours.h" +#include "gnunet-service-transport_plugins.h" +#include "gnunet-service-transport_validation.h" +#include "gnunet-service-transport.h" +#include "transport.h" + +void +GST_manipulation_set_metric (void *cls, struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message); + +void +GST_manipulation_send (const struct GNUNET_PeerIdentity *target, const void *msg, + size_t msg_size, struct GNUNET_TIME_Relative timeout, + GST_NeighbourSendContinuation cont, void *cont_cls); + +struct GNUNET_TIME_Relative +GST_manipulation_recv (void *cls, const struct GNUNET_PeerIdentity *peer, + const struct GNUNET_MessageHeader *message, + const struct GNUNET_ATS_Information *ats, + uint32_t ats_count, struct Session *session, + const char *sender_address, + uint16_t sender_address_len); + +void +GST_manipulation_init (); + +void +GST_manipulation_stop (); + +#endif +/* end of file gnunet-service-transport_neighbours.h */ diff --git a/src/transport/gnunet-service-transport_neighbours.c b/src/transport/gnunet-service-transport_neighbours.c index c580168..cad325d 100644 --- a/src/transport/gnunet-service-transport_neighbours.c +++ b/src/transport/gnunet-service-transport_neighbours.c @@ -40,6 +40,7 @@ #include "transport.h" + /** * Size of the neighbour hash map. */ @@ -91,6 +92,177 @@ */ #define BLACKLIST_RESPONSE_TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MILLISECONDS, 500) +#define DEBUG_MALLOC GNUNET_NO + +#if DEBUG_MALLOC + +struct Allocator +{ + struct Allocator *prev; + struct Allocator *next; + + unsigned int bytes_alloced; + unsigned int max_alloced; + unsigned int diff; + unsigned int line; + + struct GNUNET_TIME_Absolute max_alloced_when; + struct GNUNET_TIME_Absolute last_alloced_when; + +}; + +struct Allocator *aehead; +struct Allocator *aetail; + +struct Allocation +{ + struct Allocation *prev; + struct Allocation *next; + + struct Allocator *alloc; + unsigned int bytes_alloced; + void *p; + unsigned int line; +}; + +struct Allocation *ahead; +struct Allocation *atail; + +static int bytes_alloced; + +static struct Allocator * +find_allocator (int line) +{ + struct Allocator *cur = aehead; + while (NULL != cur) + { + if (line == cur->line) + return cur; + cur = cur->next; + } + return cur; +} + +static void +print_allocators () +{ + static int start = GNUNET_YES; + static struct GNUNET_TIME_Absolute next; + static struct GNUNET_TIME_Relative rem; + struct Allocator *cur = aehead; + if (start) + { + next = GNUNET_TIME_UNIT_ZERO_ABS; + start = GNUNET_NO; + } + if (0 == (rem = GNUNET_TIME_absolute_get_remaining(next)).rel_value) + { + fprintf (stderr, "Allocated in `%s' total: %5u bytes\n", __FILE__, bytes_alloced); + while (NULL != cur) + { + char *last_alloc = GNUNET_strdup (GNUNET_STRINGS_absolute_time_to_string(cur->max_alloced_when)); + fprintf (stderr, "Allocated from line %4u :%5u bytes (diff %5i bytes, max alloc: %5u @ %s, last alloc %s)\n", + cur->line, cur->bytes_alloced, cur->diff, cur->max_alloced, + last_alloc, + GNUNET_STRINGS_absolute_time_to_string(cur->last_alloced_when)); + GNUNET_free (last_alloc); + cur->diff = 0; + cur = cur->next; + } + fprintf (stderr, "\n"); + next = GNUNET_TIME_absolute_add(GNUNET_TIME_absolute_get(), GNUNET_TIME_UNIT_SECONDS); + } +} + +#endif + +static void +MEMDEBUG_add_alloc (void *p, size_t size, int line) +{ +#if DEBUG_MALLOC + struct Allocation *alloc = GNUNET_malloc (sizeof (struct Allocation)); + struct Allocator *allocator = find_allocator(line); + if (NULL == allocator) + { + allocator = GNUNET_malloc (sizeof (struct Allocator)); + allocator->line = line; + GNUNET_CONTAINER_DLL_insert (aehead, aetail, allocator); + } + alloc->alloc = allocator; + alloc->p = p; + alloc->line = line; + alloc->bytes_alloced = size; + allocator->bytes_alloced += size; + allocator->last_alloced_when = GNUNET_TIME_absolute_get(); + if (allocator->bytes_alloced >= allocator->max_alloced) + { + allocator->max_alloced = allocator->bytes_alloced; + allocator->max_alloced_when = allocator->last_alloced_when; + } + allocator->diff += size; + GNUNET_CONTAINER_DLL_insert (ahead, atail, alloc); + print_allocators (); + bytes_alloced += size; +#endif +} + + +static void * +MEMDEBUG_malloc (size_t size, int line) +{ + void * ret; + + ret = GNUNET_malloc (size); +#if DEBUG_MALLOC + if (NULL != ret) + MEMDEBUG_add_alloc (ret, size, line); +#endif + return ret; + +} + +static void +MEMDEBUG_free (void * alloc, int line) +{ +#if DEBUG_MALLOC + struct Allocation *cur; + struct Allocator *allocator; + cur = ahead; + while (NULL != cur) + { + if (alloc == cur->p) + break; + cur = cur->next; + } + if (NULL == cur) + { + fprintf (stderr, "Unmonitored free from line %4u\n", line); + GNUNET_break (0); + return; + } + allocator = cur->alloc; + if (NULL == allocator) + { + GNUNET_break (0); + } + GNUNET_CONTAINER_DLL_remove (ahead, atail, cur); + allocator->bytes_alloced -= cur->bytes_alloced; + allocator->diff -= cur->bytes_alloced; + GNUNET_assert (allocator->bytes_alloced >= 0); + bytes_alloced -= cur->bytes_alloced; + GNUNET_assert (bytes_alloced >= 0); + GNUNET_free (cur); +#endif + GNUNET_free (alloc); +} + +static void +MEMDEBUG_free_non_null (void * alloc, int line) +{ + if (alloc != NULL) + MEMDEBUG_free (alloc, line); +} + GNUNET_NETWORK_STRUCT_BEGIN @@ -221,10 +393,10 @@ struct MessageQueue * Possible state of a neighbour. Initially, we are S_NOT_CONNECTED. * * Then, there are two main paths. If we receive a CONNECT message, we - * first run a check against the blacklist and ask ATS for a - * suggestion. (S_CONNECT_RECV_ATS). If the blacklist comes back - * positive, we give the address to ATS. If ATS makes a suggestion, - * we ALSO give that suggestion to the blacklist + * first run a check against the blacklist (S_CONNECT_RECV_BLACKLIST_INBOUND). + * If this check is successful, we give the inbound address to ATS. + * After the check we ask ATS for a suggestion (S_CONNECT_RECV_ATS). + * If ATS makes a suggestion, we ALSO give that suggestion to the blacklist * (S_CONNECT_RECV_BLACKLIST). Once the blacklist approves the * address we got from ATS, we send our CONNECT_ACK and go to * S_CONNECT_RECV_ACK. If we receive a SESSION_ACK, we go to @@ -301,6 +473,11 @@ enum State */ S_CONNECT_SENT, + /** + * Received a CONNECT, do a blacklist check for inbound address + */ + S_CONNECT_RECV_BLACKLIST_INBOUND, + /** * Received a CONNECT, asking ATS about address suggestions. */ @@ -363,7 +540,13 @@ enum State S_DISCONNECT, /** - * We're finished with the disconnect; clean up state now! + * We're finished with the disconnect; and are cleaning up the state + * now! We put the struct into this state when we are really in the + * task that calls 'free' on it and are about to remove the record + * from the map. We should never find a 'struct NeighbourMapEntry' + * in this state in the map. Accessing a 'struct NeighbourMapEntry' + * in this state virtually always means using memory that has been + * freed (the exception being the cleanup code in 'free_neighbour'). */ S_DISCONNECT_FINISHED }; @@ -473,6 +656,11 @@ struct NeighbourMapEntry */ struct GNUNET_TIME_Absolute connect_ack_timestamp; + /** + * ATS address suggest handle + */ + struct GNUNET_ATS_SuggestHandle *suggest_handle; + /** * Time where we should cut the connection (timeout) if we don't * make progress in the state machine (or get a KEEPALIVE_RESPONSE @@ -584,7 +772,7 @@ static void *callback_cls; /** * Function to call when we connected to a neighbour. */ -static GNUNET_TRANSPORT_NotifyConnect connect_notify_cb; +static NotifyConnect connect_notify_cb; /** * Function to call when we disconnected from a neighbour. @@ -629,56 +817,40 @@ print_state (int state) { case S_NOT_CONNECTED: return "S_NOT_CONNECTED"; - break; case S_INIT_ATS: return "S_INIT_ATS"; - break; case S_INIT_BLACKLIST: return "S_INIT_BLACKLIST"; - break; case S_CONNECT_SENT: return "S_CONNECT_SENT"; - break; + case S_CONNECT_RECV_BLACKLIST_INBOUND: + return "S_CONNECT_RECV_BLACKLIST_INBOUND"; case S_CONNECT_RECV_ATS: return "S_CONNECT_RECV_ATS"; - break; case S_CONNECT_RECV_BLACKLIST: return "S_CONNECT_RECV_BLACKLIST"; - break; case S_CONNECT_RECV_ACK: return "S_CONNECT_RECV_ACK"; - break; case S_CONNECTED: return "S_CONNECTED"; - break; case S_RECONNECT_ATS: return "S_RECONNECT_ATS"; - break; case S_RECONNECT_BLACKLIST: return "S_RECONNECT_BLACKLIST"; - break; case S_RECONNECT_SENT: return "S_RECONNECT_SENT"; - break; case S_CONNECTED_SWITCHING_BLACKLIST: return "S_CONNECTED_SWITCHING_BLACKLIST"; - break; case S_CONNECTED_SWITCHING_CONNECT_SENT: return "S_CONNECTED_SWITCHING_CONNECT_SENT"; - break; case S_DISCONNECT: return "S_DISCONNECT"; - break; case S_DISCONNECT_FINISHED: return "S_DISCONNECT_FINISHED"; - break; default: - return "UNDEFINED"; GNUNET_break (0); - break; + return "UNDEFINED"; } - GNUNET_break (0); - return "UNDEFINED"; } /** @@ -698,6 +870,7 @@ test_connected (struct NeighbourMapEntry *n) case S_INIT_ATS: case S_INIT_BLACKLIST: case S_CONNECT_SENT: + case S_CONNECT_RECV_BLACKLIST_INBOUND: case S_CONNECT_RECV_ATS: case S_CONNECT_RECV_BLACKLIST: case S_CONNECT_RECV_ACK: @@ -757,11 +930,14 @@ free_address (struct NeighbourAddress *na) { GST_validation_set_address_use (na->address, na->session, GNUNET_NO, __LINE__); GNUNET_ATS_address_in_use (GST_ats, na->address, na->session, GNUNET_NO); + address_change_cb (NULL, &na->address->peer, NULL); } + na->ats_active = GNUNET_NO; if (NULL != na->address) { - GNUNET_HELLO_address_free (na->address); + MEMDEBUG_free (na->address, __LINE__); + //GNUNET_HELLO_address_free (na->address); na->address = NULL; } na->session = NULL; @@ -789,7 +965,6 @@ set_address (struct NeighbourAddress *na, int is_active) { struct GNUNET_TRANSPORT_PluginFunctions *papi; - if (NULL == (papi = GST_plugins_find (address->transport_name))) { GNUNET_break (0); @@ -804,6 +979,8 @@ set_address (struct NeighbourAddress *na, na->ats_active = is_active; GNUNET_ATS_address_in_use (GST_ats, na->address, na->session, is_active); GST_validation_set_address_use (na->address, na->session, is_active, __LINE__); + if (is_active) + address_change_cb (NULL, &address->peer, address); } if (GNUNET_YES == is_active) { @@ -825,6 +1002,7 @@ set_address (struct NeighbourAddress *na, return; } na->address = GNUNET_HELLO_address_copy (address); + MEMDEBUG_add_alloc (na->address, GNUNET_HELLO_address_get_size (na->address), __LINE__); na->bandwidth_in = bandwidth_in; na->bandwidth_out = bandwidth_out; na->session = session; @@ -832,10 +1010,9 @@ set_address (struct NeighbourAddress *na, if (GNUNET_YES == is_active) { /* Telling ATS about new session */ - GNUNET_ATS_address_update (GST_ats, na->address, na->session, NULL, 0); GNUNET_ATS_address_in_use (GST_ats, na->address, na->session, GNUNET_YES); GST_validation_set_address_use (na->address, na->session, GNUNET_YES, __LINE__); - + address_change_cb (NULL, &address->peer, address); /* FIXME: is this the right place to set quotas? */ GST_neighbours_set_incoming_quota (&address->peer, bandwidth_in); send_outbound_quota (&address->peer, bandwidth_out); @@ -855,6 +1032,7 @@ free_neighbour (struct NeighbourMapEntry *n, int keep_sessions) { struct MessageQueue *mq; struct GNUNET_TRANSPORT_PluginFunctions *papi; + struct GNUNET_HELLO_Address *backup_primary; n->is_active = NULL; /* always free'd by its own continuation! */ @@ -863,8 +1041,8 @@ free_neighbour (struct NeighbourMapEntry *n, int keep_sessions) { GNUNET_CONTAINER_DLL_remove (n->messages_head, n->messages_tail, mq); if (NULL != mq->cont) - mq->cont (mq->cont_cls, GNUNET_SYSERR); - GNUNET_free (mq); + mq->cont (mq->cont_cls, GNUNET_SYSERR, mq->message_buf_size, 0); + MEMDEBUG_free (mq, __LINE__); } /* It is too late to send other peer disconnect notifications, but at least internally we need to get clean... */ @@ -877,6 +1055,20 @@ free_neighbour (struct NeighbourMapEntry *n, int keep_sessions) disconnect_notify_cb (callback_cls, &n->id); } + n->state = S_DISCONNECT_FINISHED; + + if (NULL != n->primary_address.address) + { + backup_primary = GNUNET_HELLO_address_copy(n->primary_address.address); + MEMDEBUG_add_alloc (backup_primary, GNUNET_HELLO_address_get_size(backup_primary), __LINE__); + } + else + backup_primary = NULL; + + /* free addresses and mark as unused */ + free_address (&n->primary_address); + free_address (&n->alternative_address); + /* FIXME-PLUGIN-API: This does not seem to guarantee that all transport sessions eventually get killed due to inactivity; they MUST have their own timeout logic (but at least TCP doesn't have @@ -886,26 +1078,28 @@ free_neighbour (struct NeighbourMapEntry *n, int keep_sessions) API gives us not even the means to selectively kill only one of them! Killing all sessions like this seems to be very, very wrong. */ + + /* cut transport-level connection */ if ((GNUNET_NO == keep_sessions) && - (NULL != n->primary_address.address) && - (NULL != (papi = GST_plugins_find (n->primary_address.address->transport_name)))) + (NULL != backup_primary) && + (NULL != (papi = GST_plugins_find (backup_primary->transport_name)))) papi->disconnect (papi->cls, &n->id); - n->state = S_DISCONNECT_FINISHED; + MEMDEBUG_free_non_null (backup_primary, __LINE__); GNUNET_assert (GNUNET_YES == GNUNET_CONTAINER_multihashmap_remove (neighbours, &n->id.hashPubKey, n)); - /* cut transport-level connection */ - free_address (&n->primary_address); - free_address (&n->alternative_address); - // FIXME-ATS-API: we might want to be more specific about // which states we do this from in the future (ATS should // have given us a 'suggest_address' handle, and if we have // such a handle, we should cancel the operation here! - GNUNET_ATS_suggest_address_cancel (GST_ats, &n->id); + if (NULL != n->suggest_handle) + { + GNUNET_ATS_suggest_address_cancel (GST_ats, &n->id); + n->suggest_handle = NULL; + } if (GNUNET_SCHEDULER_NO_TASK != n->task) { @@ -913,10 +1107,9 @@ free_neighbour (struct NeighbourMapEntry *n, int keep_sessions) n->task = GNUNET_SCHEDULER_NO_TASK; } /* free rest of memory */ - GNUNET_free (n); + MEMDEBUG_free (n, __LINE__); } - /** * Transmit a message using the current session of the given * neighbour. @@ -940,15 +1133,15 @@ send_with_session (struct NeighbourMapEntry *n, struct GNUNET_TRANSPORT_PluginFunctions *papi; GNUNET_assert (n->primary_address.session != NULL); - if ( ( (NULL == (papi = GST_plugins_find (n->primary_address.address->transport_name))) || + if ( ((NULL == (papi = GST_plugins_find (n->primary_address.address->transport_name)) || (-1 == papi->send (papi->cls, n->primary_address.session, msgbuf, msgbuf_size, priority, timeout, - cont, cont_cls))) && - (NULL != cont) ) - cont (cont_cls, &n->id, GNUNET_SYSERR); + cont, cont_cls)))) && + (NULL != cont)) + cont (cont_cls, &n->id, GNUNET_SYSERR, msgbuf_size, 0); GNUNET_break (NULL != papi); } @@ -973,10 +1166,12 @@ master_task (void *cls, * @param cls NULL * @param target identity of the neighbour that was disconnected * @param result GNUNET_OK if the disconnect got out successfully + * @param payload bytes payload + * @param physical bytes physical */ static void send_disconnect_cont (void *cls, const struct GNUNET_PeerIdentity *target, - int result) + int result, size_t payload, size_t physical) { struct NeighbourMapEntry *n; @@ -1056,7 +1251,8 @@ disconnect_neighbour (struct NeighbourMapEntry *n) case S_CONNECT_SENT: send_disconnect (n); n->state = S_DISCONNECT; - break; + break; + case S_CONNECT_RECV_BLACKLIST_INBOUND: case S_CONNECT_RECV_ATS: case S_CONNECT_RECV_BLACKLIST: /* we never ACK'ed the other peer's request, no need to send DISCONNECT */ @@ -1118,18 +1314,20 @@ disconnect_neighbour (struct NeighbourMapEntry *n) * @param cls the 'struct MessageQueue' of the message * @param receiver intended receiver * @param success whether it worked or not + * @param size_payload bytes payload sent + * @param physical bytes sent on wire */ static void transmit_send_continuation (void *cls, const struct GNUNET_PeerIdentity *receiver, - int success) + int success, size_t size_payload, size_t physical) { struct MessageQueue *mq = cls; struct NeighbourMapEntry *n; if (NULL == (n = lookup_neighbour (receiver))) { - GNUNET_free (mq); + MEMDEBUG_free (mq, __LINE__); return; /* disconnect or other error while transmitting, can happen */ } if (n->is_active == mq) @@ -1141,7 +1339,18 @@ transmit_send_continuation (void *cls, GNUNET_SCHEDULER_cancel (n->task); n->task = GNUNET_SCHEDULER_add_now (&master_task, n); } - GNUNET_assert (bytes_in_send_queue >= mq->message_buf_size); + if (bytes_in_send_queue < mq->message_buf_size) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Bytes_in_send_queue `%u', Message_size %u, result: %s, payload %u, on wire %u\n", + bytes_in_send_queue, mq->message_buf_size, + (GNUNET_OK == success) ? "OK" : "FAIL", + size_payload, physical); + GNUNET_break (0); + } + + + GNUNET_break (size_payload == mq->message_buf_size); bytes_in_send_queue -= mq->message_buf_size; GNUNET_STATISTICS_set (GST_stats, gettext_noop @@ -1163,8 +1372,8 @@ transmit_send_continuation (void *cls, ntohs (((struct GNUNET_MessageHeader *) mq->message_buf)->type), (success == GNUNET_OK) ? "success" : "FAILURE"); if (NULL != mq->cont) - mq->cont (mq->cont_cls, success); - GNUNET_free (mq); + mq->cont (mq->cont_cls, success, size_payload, physical); + MEMDEBUG_free (mq, __LINE__); } @@ -1216,7 +1425,7 @@ try_transmission_to_peer (struct NeighbourMapEntry *n) 1, GNUNET_NO); GNUNET_CONTAINER_DLL_remove (n->messages_head, n->messages_tail, mq); n->is_active = mq; - transmit_send_continuation (mq, &n->id, GNUNET_SYSERR); /* timeout */ + transmit_send_continuation (mq, &n->id, GNUNET_SYSERR, mq->message_buf_size, 0); /* timeout */ } if (NULL == mq) return; /* no more messages */ @@ -1231,8 +1440,9 @@ try_transmission_to_peer (struct NeighbourMapEntry *n) /** * Send keepalive message to the neighbour. Must only be called - * if we are on 'connected' state. Will internally determine - * if a keepalive is truly needed (so can always be called). + * if we are on 'connected' state or while trying to switch addresses. + * Will internally determine if a keepalive is truly needed (so can + * always be called). * * @param n neighbour that went idle and needs a keepalive */ @@ -1241,7 +1451,9 @@ send_keepalive (struct NeighbourMapEntry *n) { struct GNUNET_MessageHeader m; - GNUNET_assert (S_CONNECTED == n->state); + GNUNET_assert ((S_CONNECTED == n->state) || + (S_CONNECTED_SWITCHING_BLACKLIST == n->state) || + (S_CONNECTED_SWITCHING_CONNECT_SENT)); if (GNUNET_TIME_absolute_get_remaining (n->keep_alive_time).rel_value > 0) return; /* no keepalive needed at this time */ m.size = htons (sizeof (struct GNUNET_MessageHeader)); @@ -1336,7 +1548,7 @@ GST_neighbours_keepalive_response (const struct GNUNET_PeerIdentity *neighbour, n->expect_latency_response = GNUNET_NO; n->latency = GNUNET_TIME_absolute_get_duration (n->last_keep_alive_time); n->timeout = GNUNET_TIME_relative_to_absolute (GNUNET_CONSTANTS_IDLE_CONNECTION_TIMEOUT); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Latency for peer `%s' is %llu ms\n", GNUNET_i2s (&n->id), n->latency.rel_value); memcpy (ats_new, ats, sizeof (struct GNUNET_ATS_Information) * ats_count); @@ -1466,14 +1678,14 @@ GST_neighbours_send (const struct GNUNET_PeerIdentity *target, const void *msg, { GNUNET_break (0); if (NULL != cont) - cont (cont_cls, GNUNET_SYSERR); + cont (cont_cls, GNUNET_SYSERR, msg_size, 0); return; } if (GNUNET_YES != test_connected (n)) { GNUNET_break (0); if (NULL != cont) - cont (cont_cls, GNUNET_SYSERR); + cont (cont_cls, GNUNET_SYSERR, msg_size, 0); return; } bytes_in_send_queue += msg_size; @@ -1481,7 +1693,7 @@ GST_neighbours_send (const struct GNUNET_PeerIdentity *target, const void *msg, gettext_noop ("# bytes in message queue for other peers"), bytes_in_send_queue, GNUNET_NO); - mq = GNUNET_malloc (sizeof (struct MessageQueue) + msg_size); + mq = MEMDEBUG_malloc (sizeof (struct MessageQueue) + msg_size, __LINE__); mq->cont = cont; mq->cont_cls = cont_cls; memcpy (&mq[1], msg, msg_size); @@ -1508,7 +1720,7 @@ send_session_connect (struct NeighbourAddress *na) { struct GNUNET_TRANSPORT_PluginFunctions *papi; struct SessionConnectMessage connect_msg; - + if (NULL == (papi = GST_plugins_find (na->address->transport_name))) { GNUNET_break (0); @@ -1532,6 +1744,7 @@ send_session_connect (struct NeighbourAddress *na) UINT_MAX, GNUNET_TIME_UNIT_FOREVER_REL, NULL, NULL); + } @@ -1549,7 +1762,7 @@ send_session_connect_ack_message (const struct GNUNET_HELLO_Address *address, { struct GNUNET_TRANSPORT_PluginFunctions *papi; struct SessionConnectMessage connect_msg; - + if (NULL == (papi = GST_plugins_find (address->transport_name))) { GNUNET_break (0); @@ -1572,6 +1785,7 @@ send_session_connect_ack_message (const struct GNUNET_HELLO_Address *address, UINT_MAX, GNUNET_TIME_UNIT_FOREVER_REL, NULL, NULL); + } @@ -1589,7 +1803,7 @@ setup_neighbour (const struct GNUNET_PeerIdentity *peer) GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Creating new neighbour entry for `%s'\n", GNUNET_i2s (peer)); - n = GNUNET_malloc (sizeof (struct NeighbourMapEntry)); + n = MEMDEBUG_malloc (sizeof (struct NeighbourMapEntry), __LINE__); n->id = *peer; n->state = S_NOT_CONNECTED; n->latency = GNUNET_TIME_UNIT_FOREVER_REL; @@ -1668,6 +1882,7 @@ GST_neighbours_try_connect (const struct GNUNET_PeerIdentity *target) case S_INIT_ATS: case S_INIT_BLACKLIST: case S_CONNECT_SENT: + case S_CONNECT_RECV_BLACKLIST_INBOUND: case S_CONNECT_RECV_ATS: case S_CONNECT_RECV_BLACKLIST: case S_CONNECT_RECV_ACK: @@ -1704,7 +1919,7 @@ GST_neighbours_try_connect (const struct GNUNET_PeerIdentity *target) n->timeout = GNUNET_TIME_relative_to_absolute (ATS_RESPONSE_TIMEOUT); GNUNET_ATS_reset_backoff (GST_ats, target); - GNUNET_ATS_suggest_address (GST_ats, target); + n->suggest_handle = GNUNET_ATS_suggest_address (GST_ats, target); } @@ -1728,14 +1943,6 @@ handle_test_blacklist_cont (void *cls, "Connection to new address of peer `%s' based on blacklist is `%s'\n", GNUNET_i2s (peer), (GNUNET_OK == result) ? "allowed" : "FORBIDDEN"); - if (GNUNET_OK == result) - { - /* valid new address, let ATS know! */ - GNUNET_ATS_address_update (GST_ats, - bcc->na.address, - bcc->na.session, - bcc->ats, bcc->ats_count); - } if (NULL == (n = lookup_neighbour (peer))) goto cleanup; /* nobody left to care about new address */ switch (n->state) @@ -1777,7 +1984,7 @@ handle_test_blacklist_cont (void *cls, n->state = S_INIT_ATS; n->timeout = GNUNET_TIME_relative_to_absolute (ATS_RESPONSE_TIMEOUT); // FIXME: do we need to ask ATS again for suggestions? - GNUNET_ATS_suggest_address (GST_ats, &n->id); + n->suggest_handle = GNUNET_ATS_suggest_address (GST_ats, &n->id); } break; case S_CONNECT_SENT: @@ -1791,9 +1998,23 @@ handle_test_blacklist_cont (void *cls, n->connect_ack_timestamp); } break; + case S_CONNECT_RECV_BLACKLIST_INBOUND: + if (GNUNET_OK == result) + { + /* valid new address, let ATS know! */ + GNUNET_ATS_address_add (GST_ats, + bcc->na.address, + bcc->na.session, + bcc->ats, bcc->ats_count); + } + n->state = S_CONNECT_RECV_ATS; + n->timeout = GNUNET_TIME_relative_to_absolute (ATS_RESPONSE_TIMEOUT); + GNUNET_ATS_reset_backoff (GST_ats, peer); + n->suggest_handle = GNUNET_ATS_suggest_address (GST_ats, peer); + break; case S_CONNECT_RECV_ATS: /* still waiting on ATS suggestion, don't care about blacklist */ - break; + break; case S_CONNECT_RECV_BLACKLIST: if (GNUNET_YES != address_matches (&bcc->na, &n->primary_address)) break; /* result for an address we currently don't care about */ @@ -1818,7 +2039,7 @@ handle_test_blacklist_cont (void *cls, n->timeout = GNUNET_TIME_relative_to_absolute (ATS_RESPONSE_TIMEOUT); // FIXME: do we need to ask ATS again for suggestions? GNUNET_ATS_reset_backoff (GST_ats, peer); - GNUNET_ATS_suggest_address (GST_ats, &n->id); + n->suggest_handle = GNUNET_ATS_suggest_address (GST_ats, &n->id); } break; case S_CONNECT_RECV_ACK: @@ -1863,7 +2084,7 @@ handle_test_blacklist_cont (void *cls, n->state = S_RECONNECT_ATS; n->timeout = GNUNET_TIME_relative_to_absolute (ATS_RESPONSE_TIMEOUT); // FIXME: do we need to ask ATS again for suggestions? - GNUNET_ATS_suggest_address (GST_ats, &n->id); + n->suggest_handle = GNUNET_ATS_suggest_address (GST_ats, &n->id); } break; case S_RECONNECT_SENT: @@ -1919,11 +2140,12 @@ handle_test_blacklist_cont (void *cls, break; } cleanup: - GNUNET_HELLO_address_free (bcc->na.address); + MEMDEBUG_free (bcc->na.address, __LINE__); + //GNUNET_HELLO_address_free (bcc->na.address); GNUNET_CONTAINER_DLL_remove (bc_head, bc_tail, bcc); - GNUNET_free (bcc); + MEMDEBUG_free (bcc, __LINE__); } @@ -1951,10 +2173,11 @@ check_blacklist (const struct GNUNET_PeerIdentity *peer, struct GST_BlacklistCheck *bc; bcc = - GNUNET_malloc (sizeof (struct BlackListCheckContext) + - sizeof (struct GNUNET_ATS_Information) * ats_count); + MEMDEBUG_malloc (sizeof (struct BlackListCheckContext) + + sizeof (struct GNUNET_ATS_Information) * ats_count, __LINE__); bcc->ats_count = ats_count; bcc->na.address = GNUNET_HELLO_address_copy (address); + MEMDEBUG_add_alloc (bcc->na.address, GNUNET_HELLO_address_get_size (address), __LINE__); bcc->na.session = session; bcc->na.connect_timestamp = ts; bcc->ats = (struct GNUNET_ATS_Information *) &bcc[1]; @@ -1998,6 +2221,7 @@ GST_neighbours_handle_connect (const struct GNUNET_MessageHeader *message, GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received CONNECT message from peer `%s'\n", GNUNET_i2s (peer)); + if (ntohs (message->size) != sizeof (struct SessionConnectMessage)) { GNUNET_break_op (0); @@ -2013,18 +2237,21 @@ GST_neighbours_handle_connect (const struct GNUNET_MessageHeader *message, n = setup_neighbour (peer); n->send_connect_ack = 1; n->connect_ack_timestamp = ts; + switch (n->state) { case S_NOT_CONNECTED: - n->state = S_CONNECT_RECV_ATS; - n->timeout = GNUNET_TIME_relative_to_absolute (ATS_RESPONSE_TIMEOUT); - GNUNET_ATS_reset_backoff (GST_ats, peer); - GNUNET_ATS_suggest_address (GST_ats, peer); + n->state = S_CONNECT_RECV_BLACKLIST_INBOUND; + /* Do a blacklist check for the new address */ check_blacklist (peer, ts, address, session, ats, ats_count); break; case S_INIT_ATS: + /* CONNECT message takes priority over us asking ATS for address */ + n->state = S_CONNECT_RECV_BLACKLIST_INBOUND; + /* fallthrough */ case S_INIT_BLACKLIST: case S_CONNECT_SENT: + case S_CONNECT_RECV_BLACKLIST_INBOUND: case S_CONNECT_RECV_ATS: case S_CONNECT_RECV_BLACKLIST: case S_CONNECT_RECV_ACK: @@ -2068,7 +2295,7 @@ GST_neighbours_handle_connect (const struct GNUNET_MessageHeader *message, n = setup_neighbour (peer); n->state = S_CONNECT_RECV_ATS; GNUNET_ATS_reset_backoff (GST_ats, peer); - GNUNET_ATS_suggest_address (GST_ats, peer); + n->suggest_handle = GNUNET_ATS_suggest_address (GST_ats, peer); break; case S_DISCONNECT_FINISHED: /* should not be possible */ @@ -2118,6 +2345,8 @@ GST_neighbours_switch_to_address (const struct GNUNET_PeerIdentity *peer, if (NULL == (papi = GST_plugins_find (address->transport_name))) { /* we don't have the plugin for this address */ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "2348 : `%s' \n", address->transport_name); GNUNET_ATS_address_destroyed (GST_ats, address, NULL); return; } @@ -2125,11 +2354,27 @@ GST_neighbours_switch_to_address (const struct GNUNET_PeerIdentity *peer, { GNUNET_break (0); if (strlen (address->transport_name) > 0) - GNUNET_ATS_address_destroyed (GST_ats, address, session); + GNUNET_ATS_address_destroyed (GST_ats, address, NULL); return; } + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "ATS tells us to switch to address '%s' session %p for " + "peer `%s' in state %s (quota in/out %u %u )\n", + (address->address_length != 0) ? GST_plugins_a2s (address): "", + session, + GNUNET_i2s (peer), + print_state (n->state), + ntohl (bandwidth_in.value__), + ntohl (bandwidth_out.value__)); + if (NULL == session) + { session = papi->get_session (papi->cls, address); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Obtained new session for peer `%s' and address '%s': %p\n", + GNUNET_i2s (&address->peer), GST_plugins_a2s (address), session); + } if (NULL == session) { GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, @@ -2138,10 +2383,6 @@ GST_neighbours_switch_to_address (const struct GNUNET_PeerIdentity *peer, GNUNET_ATS_address_destroyed (GST_ats, address, NULL); return; } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "ATS tells us to switch to address '%s' for peer `%s'\n", - (address->address_length != 0) ? GST_plugins_a2s (address): "", - GNUNET_i2s (peer)); switch (n->state) { case S_NOT_CONNECTED: @@ -2185,6 +2426,12 @@ GST_neighbours_switch_to_address (const struct GNUNET_PeerIdentity *peer, n->connect_ack_timestamp, address, session, ats, ats_count); break; + case S_CONNECT_RECV_BLACKLIST_INBOUND: + n->timeout = GNUNET_TIME_relative_to_absolute (BLACKLIST_RESPONSE_TIMEOUT); + check_blacklist (&n->id, + n->connect_ack_timestamp, + address, session, ats, ats_count); + break; case S_CONNECT_RECV_BLACKLIST: case S_CONNECT_RECV_ACK: /* ATS asks us to switch while we were trying to connect; switch to new @@ -2308,9 +2555,9 @@ master_task (void *cls, n->task = GNUNET_SCHEDULER_NO_TASK; delay = GNUNET_TIME_absolute_get_remaining (n->timeout); GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "master task runs for neighbour `%s' in state %d with timeout in %llu ms\n", + "Master task runs for neighbour `%s' in state %s with timeout in %llu ms\n", GNUNET_i2s (&n->id), - n->state, + print_state(n->state), (unsigned long long) delay.rel_value); switch (n->state) { @@ -2352,6 +2599,17 @@ master_task (void *cls, return; } break; + case S_CONNECT_RECV_BLACKLIST_INBOUND: + if (0 == delay.rel_value) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Connection to `%s' timed out waiting BLACKLIST to approve address to use for received CONNECT\n", + GNUNET_i2s (&n->id)); + n->state = S_DISCONNECT_FINISHED; + free_neighbour (n, GNUNET_NO); + return; + } + break; case S_CONNECT_RECV_ATS: if (0 == delay.rel_value) { @@ -2454,7 +2712,6 @@ master_task (void *cls, GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Cleaning up connection to `%s' after sending DISCONNECT\n", GNUNET_i2s (&n->id)); - n->state = S_DISCONNECT_FINISHED; free_neighbour (n, GNUNET_NO); return; case S_DISCONNECT_FINISHED: @@ -2530,6 +2787,7 @@ GST_neighbours_handle_connect_ack (const struct GNUNET_MessageHeader *message, GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received CONNECT_ACK message from peer `%s'\n", GNUNET_i2s (peer)); + if (ntohs (message->size) != sizeof (struct SessionConnectMessage)) { GNUNET_break_op (0); @@ -2568,7 +2826,14 @@ GST_neighbours_handle_connect_ack (const struct GNUNET_MessageHeader *message, gettext_noop ("# peers connected"), ++neighbours_connected, GNUNET_NO); - connect_notify_cb (callback_cls, &n->id, ats, ats_count); + connect_notify_cb (callback_cls, &n->id, ats, ats_count, + n->primary_address.bandwidth_in, + n->primary_address.bandwidth_out); + /* Tell ATS that the outbound session we created to send CONNECT was successfull */ + GNUNET_ATS_address_add (GST_ats, + n->primary_address.address, + n->primary_address.session, + ats, ats_count); set_address (&n->primary_address, n->primary_address.address, n->primary_address.session, @@ -2577,6 +2842,7 @@ GST_neighbours_handle_connect_ack (const struct GNUNET_MessageHeader *message, GNUNET_YES); send_session_ack_message (n); break; + case S_CONNECT_RECV_BLACKLIST_INBOUND: case S_CONNECT_RECV_ATS: case S_CONNECT_RECV_BLACKLIST: case S_CONNECT_RECV_ACK: @@ -2612,6 +2878,10 @@ GST_neighbours_handle_connect_ack (const struct GNUNET_MessageHeader *message, n->state = S_CONNECTED; n->timeout = GNUNET_TIME_relative_to_absolute (GNUNET_CONSTANTS_IDLE_CONNECTION_TIMEOUT); GNUNET_break (GNUNET_NO == n->alternative_address.ats_active); + GNUNET_ATS_address_add(GST_ats, + n->alternative_address.address, + n->alternative_address.session, + ats, ats_count); set_address (&n->primary_address, n->alternative_address.address, n->alternative_address.session, @@ -2644,8 +2914,10 @@ GST_neighbours_handle_connect_ack (const struct GNUNET_MessageHeader *message, * * @param peer identity of the peer where the session died * @param session session that is gone + * @return GNUNET_YES if this was a session used, GNUNET_NO if + * this session was not in use */ -void +int GST_neighbours_session_terminated (const struct GNUNET_PeerIdentity *peer, struct Session *session) { @@ -2661,15 +2933,16 @@ GST_neighbours_session_terminated (const struct GNUNET_PeerIdentity *peer, if (bcc->na.session == session) { GST_blacklist_test_cancel (bcc->bc); - GNUNET_HELLO_address_free (bcc->na.address); + MEMDEBUG_free (bcc->na.address, __LINE__); + //GNUNET_HELLO_address_free (bcc->na.address); GNUNET_CONTAINER_DLL_remove (bc_head, bc_tail, bcc); - GNUNET_free (bcc); + MEMDEBUG_free (bcc, __LINE__); } } if (NULL == (n = lookup_neighbour (peer))) - return; /* can't affect us */ + return GNUNET_NO; /* can't affect us */ if (session != n->primary_address.session) { if (session == n->alternative_address.session) @@ -2681,42 +2954,42 @@ GST_neighbours_session_terminated (const struct GNUNET_PeerIdentity *peer, else GNUNET_break (0); } - return; /* doesn't affect us further */ + return GNUNET_NO; /* doesn't affect us further */ } n->expect_latency_response = GNUNET_NO; - switch (n->state) { case S_NOT_CONNECTED: GNUNET_break (0); free_neighbour (n, GNUNET_NO); - return; + return GNUNET_YES; case S_INIT_ATS: GNUNET_break (0); free_neighbour (n, GNUNET_NO); - return; + return GNUNET_YES; case S_INIT_BLACKLIST: case S_CONNECT_SENT: free_address (&n->primary_address); n->state = S_INIT_ATS; n->timeout = GNUNET_TIME_relative_to_absolute (ATS_RESPONSE_TIMEOUT); // FIXME: need to ask ATS for suggestions again? - GNUNET_ATS_suggest_address (GST_ats, &n->id); + n->suggest_handle = GNUNET_ATS_suggest_address (GST_ats, &n->id); break; + case S_CONNECT_RECV_BLACKLIST_INBOUND: case S_CONNECT_RECV_ATS: case S_CONNECT_RECV_BLACKLIST: case S_CONNECT_RECV_ACK: /* error on inbound session; free neighbour entirely */ free_address (&n->primary_address); free_neighbour (n, GNUNET_NO); - return; + return GNUNET_YES; case S_CONNECTED: free_address (&n->primary_address); n->state = S_RECONNECT_ATS; n->timeout = GNUNET_TIME_relative_to_absolute (ATS_RESPONSE_TIMEOUT); /* FIXME: is this ATS call needed? */ - GNUNET_ATS_suggest_address (GST_ats, &n->id); + n->suggest_handle = GNUNET_ATS_suggest_address (GST_ats, &n->id); break; case S_RECONNECT_ATS: /* we don't have an address, how can it go down? */ @@ -2727,7 +3000,7 @@ GST_neighbours_session_terminated (const struct GNUNET_PeerIdentity *peer, n->state = S_RECONNECT_ATS; n->timeout = GNUNET_TIME_relative_to_absolute (ATS_RESPONSE_TIMEOUT); // FIXME: need to ask ATS for suggestions again? - GNUNET_ATS_suggest_address (GST_ats, &n->id); + n->suggest_handle = GNUNET_ATS_suggest_address (GST_ats, &n->id); break; case S_CONNECTED_SWITCHING_BLACKLIST: /* primary went down while we were checking secondary against @@ -2752,6 +3025,7 @@ GST_neighbours_session_terminated (const struct GNUNET_PeerIdentity *peer, break; case S_DISCONNECT_FINISHED: /* neighbour was freed and plugins told to terminate session */ + return GNUNET_NO; break; default: GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Unhandled state `%s' \n",print_state (n->state)); @@ -2761,6 +3035,7 @@ GST_neighbours_session_terminated (const struct GNUNET_PeerIdentity *peer, if (GNUNET_SCHEDULER_NO_TASK != n->task) GNUNET_SCHEDULER_cancel (n->task); n->task = GNUNET_SCHEDULER_add_now (&master_task, n); + return GNUNET_YES; } @@ -2814,7 +3089,13 @@ GST_neighbours_handle_session_ack (const struct GNUNET_MessageHeader *message, gettext_noop ("# peers connected"), ++neighbours_connected, GNUNET_NO); - connect_notify_cb (callback_cls, &n->id, ats, ats_count); + connect_notify_cb (callback_cls, &n->id, ats, ats_count, + n->primary_address.bandwidth_in, + n->primary_address.bandwidth_out); + GNUNET_ATS_address_add(GST_ats, + n->primary_address.address, + n->primary_address.session, + ats, ats_count); set_address (&n->primary_address, n->primary_address.address, n->primary_address.session, @@ -2888,7 +3169,7 @@ GST_neighbours_handle_disconnect_message (const struct GNUNET_PeerIdentity { struct NeighbourMapEntry *n; const struct SessionDisconnectMessage *sdm; - GNUNET_HashCode hc; + struct GNUNET_HashCode hc; GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received DISCONNECT message from peer `%s'\n", @@ -2972,13 +3253,31 @@ struct IteratorContext * @return GNUNET_OK (continue to iterate) */ static int -neighbours_iterate (void *cls, const GNUNET_HashCode * key, void *value) +neighbours_iterate (void *cls, const struct GNUNET_HashCode * key, void *value) { struct IteratorContext *ic = cls; struct NeighbourMapEntry *n = value; if (GNUNET_YES == test_connected (n)) - ic->cb (ic->cb_cls, &n->id, NULL, 0, n->primary_address.address); + { + struct GNUNET_BANDWIDTH_Value32NBO bandwidth_in; + struct GNUNET_BANDWIDTH_Value32NBO bandwidth_out; + + if (NULL != n->primary_address.address) + { + bandwidth_in = n->primary_address.bandwidth_in; + bandwidth_out = n->primary_address.bandwidth_out; + } + else + { + bandwidth_in = GNUNET_CONSTANTS_DEFAULT_BW_IN_OUT; + bandwidth_out = GNUNET_CONSTANTS_DEFAULT_BW_IN_OUT; + } + + ic->cb (ic->cb_cls, &n->id, NULL, 0, + n->primary_address.address, + bandwidth_in, bandwidth_out); + } return GNUNET_OK; } @@ -3041,14 +3340,20 @@ GST_neighbour_get_latency (const struct GNUNET_PeerIdentity *peer) switch (n->state) { case S_CONNECTED: + case S_CONNECTED_SWITCHING_CONNECT_SENT: + case S_CONNECTED_SWITCHING_BLACKLIST: case S_RECONNECT_SENT: case S_RECONNECT_ATS: + case S_RECONNECT_BLACKLIST: return n->latency; case S_NOT_CONNECTED: case S_INIT_BLACKLIST: case S_INIT_ATS: - case S_CONNECT_SENT: + case S_CONNECT_RECV_BLACKLIST_INBOUND: + case S_CONNECT_RECV_ATS: case S_CONNECT_RECV_BLACKLIST: + case S_CONNECT_RECV_ACK: + case S_CONNECT_SENT: case S_DISCONNECT: case S_DISCONNECT_FINISHED: return GNUNET_TIME_UNIT_FOREVER_REL; @@ -3087,18 +3392,20 @@ GST_neighbour_get_current_address (const struct GNUNET_PeerIdentity *peer) * @param disconnect_cb function to call if we disconnect from a peer * @param peer_address_cb function to call if we change an active address * of a neighbour + * @param max_fds maximum number of fds to use */ void GST_neighbours_start (void *cls, - GNUNET_TRANSPORT_NotifyConnect connect_cb, + NotifyConnect connect_cb, GNUNET_TRANSPORT_NotifyDisconnect disconnect_cb, - GNUNET_TRANSPORT_PeerIterateCallback peer_address_cb) + GNUNET_TRANSPORT_PeerIterateCallback peer_address_cb, + unsigned int max_fds) { callback_cls = cls; connect_notify_cb = connect_cb; disconnect_notify_cb = disconnect_cb; address_change_cb = peer_address_cb; - neighbours = GNUNET_CONTAINER_multihashmap_create (NEIGHBOUR_TABLE_SIZE); + neighbours = GNUNET_CONTAINER_multihashmap_create (NEIGHBOUR_TABLE_SIZE, GNUNET_NO); } @@ -3111,7 +3418,7 @@ GST_neighbours_start (void *cls, * @return GNUNET_OK (continue to iterate) */ static int -disconnect_all_neighbours (void *cls, const GNUNET_HashCode * key, void *value) +disconnect_all_neighbours (void *cls, const struct GNUNET_HashCode * key, void *value) { struct NeighbourMapEntry *n = value; diff --git a/src/transport/gnunet-service-transport_neighbours.h b/src/transport/gnunet-service-transport_neighbours.h index 23091b7..f6e3387 100644 --- a/src/transport/gnunet-service-transport_neighbours.h +++ b/src/transport/gnunet-service-transport_neighbours.h @@ -29,6 +29,7 @@ #include "gnunet_statistics_service.h" #include "gnunet_transport_service.h" #include "gnunet_transport_plugin.h" +#include "transport.h" #include "gnunet_util_lib.h" // TODO: @@ -43,12 +44,14 @@ * @param connect_cb function to call if we connect to a peer * @param disconnect_cb function to call if we disconnect from a peer * @param peer_address_cb function to call if a neighbour's active address changes + * @param max_fds maximum number of fds to use */ void GST_neighbours_start (void *cls, - GNUNET_TRANSPORT_NotifyConnect connect_cb, + NotifyConnect connect_cb, GNUNET_TRANSPORT_NotifyDisconnect disconnect_cb, - GNUNET_TRANSPORT_PeerIterateCallback peer_address_cb); + GNUNET_TRANSPORT_PeerIterateCallback peer_address_cb, + unsigned int max_fds); /** @@ -83,7 +86,9 @@ GST_neighbours_test_connected (const struct GNUNET_PeerIdentity *target); * @param cls closure * @param success GNUNET_OK on success, GNUNET_NO on failure, GNUNET_SYSERR if we're not connected */ -typedef void (*GST_NeighbourSendContinuation) (void *cls, int success); +typedef void (*GST_NeighbourSendContinuation) (void *cls, int success, + size_t bytes_payload, + size_t bytes_on_wire); /** @@ -170,6 +175,8 @@ GST_neighbours_force_disconnect (const struct GNUNET_PeerIdentity *target); * @param ats performance data * @param ats_count number of entries in ats (including 0-termination) * @param address the address (or NULL) + * @param bandwidth_in inbound quota in NBO + * @param bandwidth_out outbound quota in NBO */ typedef void (*GST_NeighbourIterator) (void *cls, const struct GNUNET_PeerIdentity * @@ -177,7 +184,9 @@ typedef void (*GST_NeighbourIterator) (void *cls, const struct GNUNET_ATS_Information * ats, uint32_t ats_count, const struct GNUNET_HELLO_Address * - address); + address, + struct GNUNET_BANDWIDTH_Value32NBO bandwidth_in, + struct GNUNET_BANDWIDTH_Value32NBO bandwidth_out); /** @@ -195,8 +204,10 @@ GST_neighbours_iterate (GST_NeighbourIterator cb, void *cb_cls); * * @param peer identity of the peer where the session died * @param session session that is gone + * @return GNUNET_YES if this was a session used, GNUNET_NO if + * this session was not in use */ -void +int GST_neighbours_session_terminated (const struct GNUNET_PeerIdentity *peer, struct Session *session); diff --git a/src/transport/gnunet-service-transport_plugins.c b/src/transport/gnunet-service-transport_plugins.c index fc14b6e..1f3727b 100644 --- a/src/transport/gnunet-service-transport_plugins.c +++ b/src/transport/gnunet-service-transport_plugins.c @@ -196,6 +196,39 @@ GST_plugins_find (const char *name) } +/** + * Obtain the plugin API based on a the stripped plugin name after the underscore. + * + * Example: GST_plugins_printer_find (http_client) will return all plugins + * starting with the prefix "http": + * http_client or server if loaded + * + * @param name name of the plugin + * @return the plugin's API, NULL if the plugin is not loaded + */ +struct GNUNET_TRANSPORT_PluginFunctions * +GST_plugins_printer_find (const char *name) +{ + struct TransportPlugin *head = plugins_head; + + char *stripped = GNUNET_strdup (name); + char *sep = strchr (stripped, '_'); + if (NULL != sep) + sep[0] = '\0'; + + while (head != NULL) + { + if (head->short_name == strstr (head->short_name, stripped)) + break; + head = head->next; + } + GNUNET_free (stripped); + if (NULL == head) + return NULL; + return head->api; +} + + /** * Convert a given address to a human-readable format. Note that the * return value will be overwritten on the next call to this function. @@ -211,7 +244,7 @@ GST_plugins_a2s (const struct GNUNET_HELLO_Address *address) if (address == NULL) return ""; - api = GST_plugins_find (address->transport_name); + api = GST_plugins_printer_find (address->transport_name); if (NULL == api) return ""; if (0 == address->address_length) diff --git a/src/transport/gnunet-service-transport_plugins.h b/src/transport/gnunet-service-transport_plugins.h index 04bb5ea..97e8f4c 100644 --- a/src/transport/gnunet-service-transport_plugins.h +++ b/src/transport/gnunet-service-transport_plugins.h @@ -66,6 +66,19 @@ GST_plugins_unload (void); struct GNUNET_TRANSPORT_PluginFunctions * GST_plugins_find (const char *name); +/** + * Obtain the plugin API based on a the stripped plugin name after the underscore. + * + * Example: GST_plugins_printer_find (http_client) will return all plugins + * starting with the prefix "http": + * http_client or server if loaded + * + * @param name name of the plugin + * @return the plugin's API, NULL if the plugin is not loaded + */ +struct GNUNET_TRANSPORT_PluginFunctions * +GST_plugins_printer_find (const char *name); + /** * Convert a given address to a human-readable format. Note that the diff --git a/src/transport/gnunet-service-transport_validation.c b/src/transport/gnunet-service-transport_validation.c index 8421969..3598a34 100644 --- a/src/transport/gnunet-service-transport_validation.c +++ b/src/transport/gnunet-service-transport_validation.c @@ -34,6 +34,7 @@ #include "gnunet_peerinfo_service.h" #include "gnunet_signatures.h" +#define KEEP_093_COMPATIBILITY GNUNET_NO /** * How long is a PONG signature valid? We'll recycle a signature until @@ -306,6 +307,16 @@ static struct GNUNET_CONTAINER_MultiHashMap *validation_map; static struct GNUNET_PEERINFO_NotifyContext *pnc; +/** + * Minimum delay between to validations + */ +static struct GNUNET_TIME_Relative validation_delay; + +/** + * When is next validation allowed + */ +static struct GNUNET_TIME_Absolute validation_next; + /** * Context for the validation entry match function. */ @@ -334,7 +345,7 @@ struct ValidationEntryMatchContext * GNUNET_NO if the entry does match */ static int -validation_entry_match (void *cls, const GNUNET_HashCode * key, void *value) +validation_entry_match (void *cls, const struct GNUNET_HashCode * key, void *value) { struct ValidationEntryMatchContext *vemc = cls; struct ValidationEntry *ve = value; @@ -357,7 +368,7 @@ validation_entry_match (void *cls, const GNUNET_HashCode * key, void *value) * @return GNUNET_YES (continue to iterate) */ static int -cleanup_validation_entry (void *cls, const GNUNET_HashCode * key, void *value) +cleanup_validation_entry (void *cls, const struct GNUNET_HashCode * key, void *value) { struct ValidationEntry *ve = value; @@ -432,6 +443,7 @@ transmit_ping_if_allowed (void *cls, const struct GNUNET_PeerIdentity *pid, struct ValidationEntry *ve = cls; struct TransportPingMessage ping; struct GNUNET_TRANSPORT_PluginFunctions *papi; + struct GNUNET_TIME_Absolute next; const struct GNUNET_MessageHeader *hello; ssize_t ret; size_t tsize; @@ -439,8 +451,20 @@ transmit_ping_if_allowed (void *cls, const struct GNUNET_PeerIdentity *pid, uint16_t hsize; ve->bc = NULL; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Transmitting plain PING to `%s' %s\n", - GNUNET_i2s (pid), GST_plugins_a2s (ve->address)); + + if (GNUNET_NO == result) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Blacklist denies to send PING to `%s' %s %s\n", + GNUNET_i2s (pid), GST_plugins_a2s (ve->address), ve->address->transport_name); + return; + } + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Transmitting plain PING to `%s' %s %s\n", + GNUNET_i2s (pid), GST_plugins_a2s (ve->address), ve->address->transport_name); + + next = GNUNET_TIME_absolute_add(GNUNET_TIME_absolute_get(), validation_delay); + if (next.abs_value > validation_next.abs_value) + validation_next = next; /* We're going to send a PING so delay next validation */ slen = strlen (ve->address->transport_name) + 1; hello = GST_hello_get (); @@ -478,7 +502,7 @@ transmit_ping_if_allowed (void *cls, const struct GNUNET_PeerIdentity *pid, memcpy (&message_buf[sizeof (struct TransportPingMessage) + hsize], ve->address->transport_name, slen); memcpy (&message_buf[sizeof (struct TransportPingMessage) + slen + hsize], - ve->address, ve->address->address_length); + ve->address->address, ve->address->address_length); papi = GST_plugins_find (ve->address->transport_name); if (papi == NULL) ret = -1; @@ -528,6 +552,7 @@ revalidate_address (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) struct ValidationEntry *ve = cls; struct GNUNET_TIME_Relative canonical_delay; struct GNUNET_TIME_Relative delay; + struct GNUNET_TIME_Relative blocked_for; struct GST_BlacklistCheck *bc; uint32_t rdelay; @@ -552,16 +577,39 @@ revalidate_address (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) GNUNET_SCHEDULER_add_delayed (delay, &revalidate_address, ve); return; } + blocked_for = GNUNET_TIME_absolute_get_remaining(validation_next); + if ((blocked_for.rel_value) > 0) + { + /* Validations are blocked, have to wait for blocked_for ms */ + ve->revalidation_task = + GNUNET_SCHEDULER_add_delayed (blocked_for, &revalidate_address, ve); + return; + } ve->revalidation_block = GNUNET_TIME_relative_to_absolute (canonical_delay); /* schedule next PINGing with some extra random delay to avoid synchronous re-validations */ rdelay = GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK, canonical_delay.rel_value); - delay = - GNUNET_TIME_relative_add (canonical_delay, + + /* Debug code for mantis 0002726*/ + if (GNUNET_TIME_UNIT_FOREVER_REL.rel_value == + GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MILLISECONDS, rdelay).rel_value) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Revalidation interval for peer `%s' for is FOREVER (debug: rdelay: %llu, canonical delay %llu)\n", + GNUNET_i2s (&ve->pid), + (unsigned long long) delay.rel_value, + (unsigned long long) canonical_delay.rel_value); + delay = canonical_delay; + } + else + { + delay = GNUNET_TIME_relative_add (canonical_delay, GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MILLISECONDS, rdelay)); + } + /* End debug code for mantis 0002726*/ ve->revalidation_task = GNUNET_SCHEDULER_add_delayed (delay, &revalidate_address, ve); @@ -661,7 +709,7 @@ add_valid_address (void *cls, const struct GNUNET_HELLO_Address *address, if (GNUNET_SCHEDULER_NO_TASK == ve->revalidation_task) ve->revalidation_task = GNUNET_SCHEDULER_add_now (&revalidate_address, ve); - GNUNET_ATS_address_update (GST_ats, address, NULL, NULL, 0); + GNUNET_ATS_address_add (GST_ats, address, NULL, NULL, 0); return GNUNET_OK; } @@ -691,11 +739,17 @@ process_peerinfo_hello (void *cls, const struct GNUNET_PeerIdentity *peer, /** * Start the validation subsystem. + * + * @param max_fds maximum number of fds to use */ void -GST_validation_start () +GST_validation_start (unsigned int max_fds) { - validation_map = GNUNET_CONTAINER_multihashmap_create (VALIDATION_MAP_SIZE); + validation_next = GNUNET_TIME_absolute_get(); + validation_delay.rel_value = (GNUNET_CONSTANTS_IDLE_CONNECTION_TIMEOUT.rel_value) / max_fds; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Delay between validations: %u ms\n ", validation_delay.rel_value); + validation_map = GNUNET_CONTAINER_multihashmap_create (VALIDATION_MAP_SIZE, + GNUNET_NO); pnc = GNUNET_PEERINFO_notify (GST_cfg, &process_peerinfo_hello, NULL); } @@ -788,6 +842,7 @@ GST_validation_handle_ping (const struct GNUNET_PeerIdentity *sender, size_t alen; size_t slen; ssize_t ret; + int buggy = GNUNET_NO; struct GNUNET_HELLO_Address address; if (ntohs (hdr->size) < sizeof (struct TransportPingMessage)) @@ -817,7 +872,7 @@ GST_validation_handle_ping (const struct GNUNET_PeerIdentity *sender, sig_cache = NULL; sig_cache_exp = NULL; - if (0 < alen) + if (alen > 0) { addrend = memchr (addr, '\0', alen); if (NULL == addrend) @@ -831,15 +886,45 @@ GST_validation_handle_ping (const struct GNUNET_PeerIdentity *sender, address.address = addrend; address.address_length = alen; address.transport_name = addr; - address.peer = *sender; - if (GNUNET_YES != - GST_hello_test_address (&address, &sig_cache, &sig_cache_exp)) + address.peer = GST_my_identity; + + + if (GNUNET_YES != GST_hello_test_address (&address, &sig_cache, &sig_cache_exp)) { - GNUNET_log (GNUNET_ERROR_TYPE_INFO, - _ - ("Not confirming PING with address `%s' since I cannot confirm having this address.\n"), - GST_plugins_a2s (&address)); - return; +#if KEEP_093_COMPATIBILITY + int idsize = sizeof (GST_my_identity); + if (alen <= idsize) + { + if (0 == memcmp (address.address, &GST_my_identity, alen)) + buggy = GNUNET_YES; + } + else if (alen <= (idsize + strlen (address.transport_name))) + { + char *achar = (char *) &address.address; + if ((0 == memcmp (address.address, &GST_my_identity, idsize)) && + (0 == memcmp (&achar[idsize], address.transport_name, alen - idsize))) + buggy = GNUNET_YES; + } + else + { + /* Not predicatable */ + return; + } +#endif + if (GNUNET_NO == buggy) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Not confirming PING from peer `%s' with address `%s' since I cannot confirm having this address.\n", + GNUNET_i2s (sender), + GST_plugins_a2s (&address)); + return; + } + else + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + _("Received a PING message with validation bug from `%s'\n"), + GNUNET_i2s (sender)); + } } } else @@ -853,6 +938,14 @@ GST_validation_handle_ping (const struct GNUNET_PeerIdentity *sender, sig_cache_exp = &no_address_signature_expiration; } + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "I am `%s', sending PONG to peer `%s'\n", + GNUNET_h2s (&GST_my_identity.hashPubKey), + GNUNET_i2s (sender)); + + /* message with structure: + * [TransportPongMessage][Transport name][Address] */ + pong = GNUNET_malloc (sizeof (struct TransportPongMessage) + alen + slen); pong->header.size = htons (sizeof (struct TransportPongMessage) + alen + slen); @@ -862,27 +955,64 @@ GST_validation_handle_ping (const struct GNUNET_PeerIdentity *sender, sizeof (uint32_t) + sizeof (struct GNUNET_TIME_AbsoluteNBO) + alen + slen); pong->purpose.purpose = htonl (GNUNET_SIGNATURE_PURPOSE_TRANSPORT_PONG_OWN); - pong->challenge = ping->challenge; + memcpy (&pong->challenge, &ping->challenge, sizeof (ping->challenge)); pong->addrlen = htonl (alen + slen); - memcpy (&pong[1], addr, slen); - memcpy (&((char *) &pong[1])[slen], addrend, alen); - if (GNUNET_TIME_absolute_get_remaining (*sig_cache_exp).rel_value < - PONG_SIGNATURE_LIFETIME.rel_value / 4) + memcpy (&pong[1], addr, slen); /* Copy transport plugin */ +#if KEEP_093_COMPATIBILITY + if (GNUNET_YES == buggy) { - /* create / update cached sig */ - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Creating PONG signature to indicate ownership.\n"); - *sig_cache_exp = GNUNET_TIME_relative_to_absolute (PONG_SIGNATURE_LIFETIME); - pong->expiration = GNUNET_TIME_absolute_hton (*sig_cache_exp); + int idsize = sizeof (GST_my_identity); + if (alen <= idsize) + { + memcpy (&((char *) &pong[1])[slen], &GST_my_identity, alen); + } + else if (alen <= (idsize + strlen (address.transport_name) + 1)) + { + memcpy (&((char *) &pong[1])[slen], &GST_my_identity, idsize); + memcpy (&((char *) &pong[1])[slen + idsize], address.transport_name, alen-idsize); + } + else + { + /* If this would happen, we would have a inconsistent PING we cannot reproduce */ + GNUNET_free (pong); + return; + } + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Creating buggy PONG signature to indicate ownership.\n"); + pong->expiration = GNUNET_TIME_absolute_hton (GNUNET_TIME_relative_to_absolute (PONG_SIGNATURE_LIFETIME)); GNUNET_assert (GNUNET_OK == GNUNET_CRYPTO_rsa_sign (GST_my_private_key, &pong->purpose, - sig_cache)); + &pong->signature)); } else { - pong->expiration = GNUNET_TIME_absolute_hton (*sig_cache_exp); +#endif + if (alen > 0) + { + GNUNET_assert (NULL != addrend); + memcpy (&((char *) &pong[1])[slen], addrend, alen); + } + if (GNUNET_TIME_absolute_get_remaining (*sig_cache_exp).rel_value < + PONG_SIGNATURE_LIFETIME.rel_value / 4) + { + /* create / update cached sig */ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Creating PONG signature to indicate ownership.\n"); + *sig_cache_exp = GNUNET_TIME_relative_to_absolute (PONG_SIGNATURE_LIFETIME); + pong->expiration = GNUNET_TIME_absolute_hton (*sig_cache_exp); + GNUNET_assert (GNUNET_OK == + GNUNET_CRYPTO_rsa_sign (GST_my_private_key, &pong->purpose, + sig_cache)); + } + else + { + pong->expiration = GNUNET_TIME_absolute_hton (*sig_cache_exp); + } + pong->signature = *sig_cache; + +#if KEEP_093_COMPATIBILITY } - pong->signature = *sig_cache; +#endif GNUNET_assert (sender_address != NULL); @@ -1031,6 +1161,9 @@ GST_validation_handle_pong (const struct GNUNET_PeerIdentity *sender, gettext_noop ("# PONG messages received"), 1, GNUNET_NO); + /* message with structure: + * [TransportPongMessage][Transport name][Address] */ + pong = (const struct TransportPongMessage *) hdr; tname = (const char *) &pong[1]; size = ntohs (hdr->size) - sizeof (struct TransportPongMessage); @@ -1068,7 +1201,10 @@ GST_validation_handle_pong (const struct GNUNET_PeerIdentity *sender, &pong->purpose, &pong->signature, &ve->public_key)) { - GNUNET_break_op (0); + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + "Invalid signature on address %s:%s from peer `%s'\n", + tname, GST_plugins_a2s (ve->address), + GNUNET_i2s (sender)); return; } @@ -1083,7 +1219,6 @@ GST_validation_handle_pong (const struct GNUNET_PeerIdentity *sender, } GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Address validated for peer `%s' with plugin `%s': `%s'\n", - GNUNET_i2s (sender), tname, GST_plugins_a2s (ve->address)); /* validity achieved, remember it! */ ve->expecting_pong = GNUNET_NO; @@ -1091,10 +1226,9 @@ GST_validation_handle_pong (const struct GNUNET_PeerIdentity *sender, ve->latency = GNUNET_TIME_absolute_get_duration (ve->send_time); { struct GNUNET_ATS_Information ats; - ats.type = htonl (GNUNET_ATS_QUALITY_NET_DELAY); ats.value = htonl ((uint32_t) ve->latency.rel_value); - GNUNET_ATS_address_update (GST_ats, ve->address, NULL, &ats, 1); + GNUNET_ATS_address_add (GST_ats, ve->address, NULL, &ats, 1); } /* build HELLO to store in PEERINFO */ ve->copied = GNUNET_NO; @@ -1131,11 +1265,11 @@ GST_validation_handle_hello (const struct GNUNET_MessageHeader *hello) /* Add peer identity without addresses to peerinfo service */ h = GNUNET_HELLO_create (&vac.public_key, NULL, NULL); GNUNET_PEERINFO_add_peer (GST_peerinfo, h, NULL, NULL); -#if VERBOSE_VALIDATION + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, _("Adding `%s' without addresses for peer `%s'\n"), "HELLO", GNUNET_i2s (&vac.pid)); -#endif + GNUNET_free (h); GNUNET_assert (NULL == GNUNET_HELLO_iterate_addresses (hm, GNUNET_NO, @@ -1171,7 +1305,7 @@ struct IteratorContext * @return GNUNET_OK (continue to iterate) */ static int -iterate_addresses (void *cls, const GNUNET_HashCode * key, void *value) +iterate_addresses (void *cls, const struct GNUNET_HashCode * key, void *value) { struct IteratorContext *ic = cls; struct ValidationEntry *ve = value; diff --git a/src/transport/gnunet-service-transport_validation.h b/src/transport/gnunet-service-transport_validation.h index dd5bcd6..6f1206f 100644 --- a/src/transport/gnunet-service-transport_validation.h +++ b/src/transport/gnunet-service-transport_validation.h @@ -34,9 +34,11 @@ /** * Start the validation subsystem. + * + * @param max_fds maximum number of fds to use */ void -GST_validation_start (void); +GST_validation_start (unsigned int max_fds); /** diff --git a/src/transport/gnunet-transport-certificate-creation b/src/transport/gnunet-transport-certificate-creation deleted file mode 100755 index b5cffb2..0000000 --- a/src/transport/gnunet-transport-certificate-creation +++ /dev/null @@ -1,148 +0,0 @@ -#! /bin/bash - -# gnunet-transport-certificate-creation - temporary wrapper script for .libs/gnunet-transport-certificate-creation -# Generated by ltmain.sh (GNU libtool) 2.2.6b Debian-2.2.6b-2 -# -# The gnunet-transport-certificate-creation program cannot be directly executed until all the libtool -# libraries that it depends on are installed. -# -# This wrapper script should never be moved out of the build directory. -# If it is, it will not operate correctly. - -# Sed substitution that helps us do robust quoting. It backslashifies -# metacharacters that are still active within double-quoted strings. -Xsed='/bin/sed -e 1s/^X//' -sed_quote_subst='s/\([`"$\\]\)/\\\1/g' - -# Be Bourne compatible -if test -n "${ZSH_VERSION+set}" && (emulate sh) >/dev/null 2>&1; then - emulate sh - NULLCMD=: - # Zsh 3.x and 4.x performs word splitting on ${1+"$@"}, which - # is contrary to our usage. Disable this feature. - alias -g '${1+"$@"}'='"$@"' - setopt NO_GLOB_SUBST -else - case `(set -o) 2>/dev/null` in *posix*) set -o posix;; esac -fi -BIN_SH=xpg4; export BIN_SH # for Tru64 -DUALCASE=1; export DUALCASE # for MKS sh - -# The HP-UX ksh and POSIX shell print the target directory to stdout -# if CDPATH is set. -(unset CDPATH) >/dev/null 2>&1 && unset CDPATH - -relink_command="(cd /home/grothoff/gnunet-0.9.3/src/transport; { test -z \"\${LIBRARY_PATH+set}\" || unset LIBRARY_PATH || { LIBRARY_PATH=; export LIBRARY_PATH; }; }; { test -z \"\${COMPILER_PATH+set}\" || unset COMPILER_PATH || { COMPILER_PATH=; export COMPILER_PATH; }; }; { test -z \"\${GCC_EXEC_PREFIX+set}\" || unset GCC_EXEC_PREFIX || { GCC_EXEC_PREFIX=; export GCC_EXEC_PREFIX; }; }; { test -z \"\${LD_RUN_PATH+set}\" || unset LD_RUN_PATH || { LD_RUN_PATH=; export LD_RUN_PATH; }; }; LD_LIBRARY_PATH=/usr/lib/debug:/home/grothoff/lib; export LD_LIBRARY_PATH; PATH=/opt/jdk1.6.0_22/bin:/usr/lib/jvm/java-6-sun//bin:.:/home/grothoff/bin:/usr/local/bin:/usr/bin:/bin:/usr/local/games:/usr/games; export PATH; gcc -fno-strict-aliasing -Wall -g -Wall -Werror -O0 -I/home/grothoff//include -o \$progdir/\$file gnunet-transport-certificate-creation.o -L/home/grothoff//lib ../../src/util/.libs/libgnunetutil.so -ldl -Wl,-rpath -Wl,/home/grothoff/gnunet-0.9.3/src/util/.libs)" - -# This environment variable determines our operation mode. -if test "$libtool_install_magic" = "%%%MAGIC variable%%%"; then - # install mode needs the following variables: - generated_by_libtool_version='2.2.6b' - notinst_deplibs=' ../../src/util/libgnunetutil.la' -else - # When we are sourced in execute mode, $file and $ECHO are already set. - if test "$libtool_execute_magic" != "%%%MAGIC variable%%%"; then - ECHO="echo" - file="$0" - # Make sure echo works. - if test "X$1" = X--no-reexec; then - # Discard the --no-reexec flag, and continue. - shift - elif test "X`{ $ECHO '\t'; } 2>/dev/null`" = 'X\t'; then - # Yippee, $ECHO works! - : - else - # Restart under the correct shell, and then maybe $ECHO will work. - exec /bin/bash "$0" --no-reexec ${1+"$@"} - fi - fi - - # Find the directory that this script lives in. - thisdir=`$ECHO "X$file" | $Xsed -e 's%/[^/]*$%%'` - test "x$thisdir" = "x$file" && thisdir=. - - # Follow symbolic links until we get to the real thisdir. - file=`ls -ld "$file" | /bin/sed -n 's/.*-> //p'` - while test -n "$file"; do - destdir=`$ECHO "X$file" | $Xsed -e 's%/[^/]*$%%'` - - # If there was a directory component, then change thisdir. - if test "x$destdir" != "x$file"; then - case "$destdir" in - [\\/]* | [A-Za-z]:[\\/]*) thisdir="$destdir" ;; - *) thisdir="$thisdir/$destdir" ;; - esac - fi - - file=`$ECHO "X$file" | $Xsed -e 's%^.*/%%'` - file=`ls -ld "$thisdir/$file" | /bin/sed -n 's/.*-> //p'` - done - - - # Usually 'no', except on cygwin/mingw when embedded into - # the cwrapper. - WRAPPER_SCRIPT_BELONGS_IN_OBJDIR=no - if test "$WRAPPER_SCRIPT_BELONGS_IN_OBJDIR" = "yes"; then - # special case for '.' - if test "$thisdir" = "."; then - thisdir=`pwd` - fi - # remove .libs from thisdir - case "$thisdir" in - *[\\/].libs ) thisdir=`$ECHO "X$thisdir" | $Xsed -e 's%[\\/][^\\/]*$%%'` ;; - .libs ) thisdir=. ;; - esac - fi - - # Try to get the absolute directory name. - absdir=`cd "$thisdir" && pwd` - test -n "$absdir" && thisdir="$absdir" - - program=lt-'gnunet-transport-certificate-creation' - progdir="$thisdir/.libs" - - if test ! -f "$progdir/$program" || - { file=`ls -1dt "$progdir/$program" "$progdir/../$program" 2>/dev/null | /bin/sed 1q`; \ - test "X$file" != "X$progdir/$program"; }; then - - file="$$-$program" - - if test ! -d "$progdir"; then - mkdir "$progdir" - else - rm -f "$progdir/$file" - fi - - # relink executable if necessary - if test -n "$relink_command"; then - if relink_command_output=`eval $relink_command 2>&1`; then : - else - echo "$relink_command_output" >&2 - rm -f "$progdir/$file" - exit 1 - fi - fi - - mv -f "$progdir/$file" "$progdir/$program" 2>/dev/null || - { rm -f "$progdir/$program"; - mv -f "$progdir/$file" "$progdir/$program"; } - rm -f "$progdir/$file" - fi - - if test -f "$progdir/$program"; then - if test "$libtool_execute_magic" != "%%%MAGIC variable%%%"; then - # Run the actual program with our arguments. - - exec "$progdir/$program" ${1+"$@"} - - $ECHO "$0: cannot exec $program $*" 1>&2 - exit 1 - fi - else - # The program doesn't exist. - $ECHO "$0: error: \`$progdir/$program' does not exist" 1>&2 - $ECHO "This script is just a wrapper for $program." 1>&2 - echo "See the libtool documentation for more information." 1>&2 - exit 1 - fi -fi diff --git a/src/transport/gnunet-transport-certificate-creation.c b/src/transport/gnunet-transport-certificate-creation.c index c4c13dc..5ecc7de 100644 --- a/src/transport/gnunet-transport-certificate-creation.c +++ b/src/transport/gnunet-transport-certificate-creation.c @@ -22,7 +22,6 @@ * @file transport/gnunet-transport-certificate-creation.c * @brief create certificate for HTTPS transport * @author LRN - * */ #include "platform.h" #include "gnunet_disk_lib.h" @@ -32,15 +31,19 @@ static void removecerts (const char *file1, const char *file2) { - if (GNUNET_DISK_file_test (file1) == GNUNET_YES) + if (GNUNET_YES == GNUNET_DISK_file_test (file1)) { - CHMOD (file1, S_IWUSR | S_IRUSR); - REMOVE (file1); + if (0 != CHMOD (file1, S_IWUSR | S_IRUSR)) + GNUNET_log_strerror_file (GNUNET_ERROR_TYPE_WARNING, "chmod", file1); + if (0 != REMOVE (file1)) + GNUNET_log_strerror_file (GNUNET_ERROR_TYPE_WARNING, "remove", file1); } - if (GNUNET_DISK_file_test (file2) == GNUNET_YES) + if (GNUNET_YES == GNUNET_DISK_file_test (file2)) { - CHMOD (file2, S_IWUSR | S_IRUSR); - REMOVE (file2); + if (0 != CHMOD (file2, S_IWUSR | S_IRUSR)) + GNUNET_log_strerror_file (GNUNET_ERROR_TYPE_WARNING, "chmod", file2); + if (0 != REMOVE (file2)) + GNUNET_log_strerror_file (GNUNET_ERROR_TYPE_WARNING, "remove", file2); } } @@ -50,32 +53,34 @@ main (int argc, char **argv) { struct GNUNET_OS_Process *openssl; - if (argc != 3) + if (3 != argc) return 1; removecerts (argv[1], argv[2]); - close (2); /* eliminate stderr */ + (void) close (2); /* eliminate stderr */ /* Create RSA Private Key */ /* openssl genrsa -out $1 1024 2> /dev/null */ openssl = - GNUNET_OS_start_process (GNUNET_NO, NULL, NULL, "openssl", "openssl", "genrsa", + GNUNET_OS_start_process (GNUNET_NO, GNUNET_OS_INHERIT_STD_OUT_AND_ERR, NULL, NULL, "openssl", "openssl", "genrsa", "-out", argv[1], "1024", NULL); - if (openssl == NULL) + if (NULL == openssl) return 2; - GNUNET_assert (GNUNET_OS_process_wait (openssl) == GNUNET_OK); + GNUNET_assert (GNUNET_OK == GNUNET_OS_process_wait (openssl)); GNUNET_OS_process_destroy (openssl); /* Create a self-signed certificate in batch mode using rsa key */ /* openssl req -batch -days 365 -out $2 -new -x509 -key $1 2> /dev/null */ openssl = - GNUNET_OS_start_process (GNUNET_NO, NULL, NULL, "openssl", "openssl", "req", + GNUNET_OS_start_process (GNUNET_NO, GNUNET_OS_INHERIT_STD_OUT_AND_ERR, NULL, NULL, "openssl", "openssl", "req", "-batch", "-days", "365", "-out", argv[2], "-new", "-x509", "-key", argv[1], NULL); - if (openssl == NULL) + if (NULL == openssl) return 3; - GNUNET_assert (GNUNET_OS_process_wait (openssl) == GNUNET_OK); + GNUNET_assert (GNUNET_OK == GNUNET_OS_process_wait (openssl)); GNUNET_OS_process_destroy (openssl); - CHMOD (argv[1], S_IRUSR); - CHMOD (argv[2], S_IRUSR); + if (0 != CHMOD (argv[1], S_IRUSR)) + GNUNET_log_strerror_file (GNUNET_ERROR_TYPE_WARNING, "chmod", argv[1]); + if (0 != CHMOD (argv[2], S_IRUSR)) + GNUNET_log_strerror_file (GNUNET_ERROR_TYPE_WARNING, "chmod", argv[2]); return 0; } diff --git a/src/transport/gnunet-transport-wlan-receiver.c b/src/transport/gnunet-transport-wlan-receiver.c new file mode 100644 index 0000000..ccc1d29 --- /dev/null +++ b/src/transport/gnunet-transport-wlan-receiver.c @@ -0,0 +1,116 @@ +/* + This file is part of GNUnet + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. + */ + +/** + * @file transport/gnunet-transport-wlan-receiver.c + * @brief program to send via WLAN as much as possible (to test physical/theoretical throughput) + * @author David Brodski + */ +#include "platform.h" +#include "gnunet_protocols.h" +#include "plugin_transport_wlan.h" + +int +main (int argc, char *argv[]) +{ + char msg_buf[65536]; + unsigned long long count; + double bytes_per_s; + time_t start; + time_t akt; + ssize_t ret; + pid_t pid; + int commpipe[2]; /* This holds the fd for the input & output of the pipe */ + + if (2 != argc) + { + fprintf (stderr, + "This program must be started with the interface name as argument.\n"); + fprintf (stderr, + "Usage: %s interface-name\n" + "e.g. %s mon0\n", + argv[0], argv[0]); + return 1; + } + + /* Setup communication pipeline first */ + if (pipe (commpipe)) + { + fprintf (stderr, + "Failed to create pipe: %s\n", + STRERROR (errno)); + exit (1); + } + + /* Attempt to fork and check for errors */ + if ((pid = fork ()) == -1) + { + fprintf (stderr, "Failed to fork: %s\n", + STRERROR (errno)); + exit (1); + } + + if (pid) + { + /* A positive (non-negative) PID indicates the parent process */ + if (0 != close (commpipe[1])) /* Close unused side of pipe (in side) */ + fprintf (stderr, + "Failed to close fd: %s\n", + strerror (errno)); + start = time (NULL); + count = 0; + while (1) + { + ret = read (commpipe[0], msg_buf, sizeof (msg_buf)); + if (0 > ret) + { + fprintf (stderr, "read failed: %s\n", strerror (errno)); + break; + } + count += ret; + akt = time (NULL); + if (akt - start > 30) + { + bytes_per_s = count / (akt - start); + bytes_per_s /= 1024; + printf ("recv %f kb/s\n", bytes_per_s); + start = akt; + count = 0; + } + } + } + else + { + /* A zero PID indicates that this is the child process */ + (void) close (1); + if (-1 == dup2 (commpipe[1], 1)) /* Replace stdin with the in side of the pipe */ + fprintf (stderr, "dup2 failed: %s\n", strerror (errno)); + (void) close (commpipe[0]); /* Close unused side of pipe (in side) */ + /* Replace the child fork with a new process */ + if (execlp + ("gnunet-helper-transport-wlan", "gnunet-helper-transport-wlan", + argv[1], NULL) == -1) + { + fprintf (stderr, "Could not start gnunet-helper-transport-wlan!"); + _exit (1); + } + } + return 0; +} diff --git a/src/transport/gnunet-transport-wlan-sender.c b/src/transport/gnunet-transport-wlan-sender.c index daa8f02..05d1d1e 100644 --- a/src/transport/gnunet-transport-wlan-sender.c +++ b/src/transport/gnunet-transport-wlan-sender.c @@ -101,47 +101,49 @@ main (int argc, char *argv[]) unsigned int temp[6]; struct GNUNET_TRANSPORT_WLAN_MacAddress inmac; struct GNUNET_TRANSPORT_WLAN_MacAddress outmac; - int pos; - long long count; + struct GNUNET_TRANSPORT_WLAN_HelperControlMessage hcm; + unsigned long long count; double bytes_per_s; time_t start; time_t akt; int i; + ssize_t ret; + pid_t pid; + int commpipe[2]; /* This holds the fd for the input & output of the pipe */ + int macpipe[2]; /* This holds the fd for the input & output of the pipe */ if (4 != argc) { fprintf (stderr, "This program must be started with the interface and the targets and source mac as argument.\n"); fprintf (stderr, - "Usage: interface-name mac-target mac-source\n" + "Usage: interface-name mac-DST mac-SRC\n" "e.g. mon0 11-22-33-44-55-66 12-34-56-78-90-ab\n"); return 1; } if (6 != - SSCANF (argv[3], "%x-%x-%x-%x-%x-%x", &temp[0], &temp[1], &temp[2], + SSCANF (argv[2], "%x-%x-%x-%x-%x-%x", &temp[0], &temp[1], &temp[2], &temp[3], &temp[4], &temp[5])) { fprintf (stderr, - "Usage: interface-name mac-target mac-source\n" + "Usage: interface-name mac-DST mac-SRC\n" "e.g. mon0 11-22-33-44-55-66 12-34-56-78-90-ab\n"); return 1; } for (i = 0; i < 6; i++) outmac.mac[i] = temp[i]; if (6 != - SSCANF (argv[2], "%x-%x-%x-%x-%x-%x", &temp[0], &temp[1], &temp[2], + SSCANF (argv[3], "%x-%x-%x-%x-%x-%x", &temp[0], &temp[1], &temp[2], &temp[3], &temp[4], &temp[5])) { fprintf (stderr, - "Usage: interface-name mac-target mac-source\n" + "Usage: interface-name mac-DST mac-SRC\n" "e.g. mon0 11-22-33-44-55-66 12-34-56-78-90-ab\n"); return 1; } for (i = 0; i < 6; i++) inmac.mac[i] = temp[i]; - pid_t pid; - int commpipe[2]; /* This holds the fd for the input & output of the pipe */ /* Setup communication pipeline first */ if (pipe (commpipe)) @@ -151,6 +153,13 @@ main (int argc, char *argv[]) STRERROR (errno)); exit (1); } + if (pipe (macpipe)) + { + fprintf (stderr, + "Failed to create pipe: %s\n", + STRERROR (errno)); + exit (1); + } /* Attempt to fork and check for errors */ if ((pid = fork ()) == -1) @@ -159,49 +168,66 @@ main (int argc, char *argv[]) STRERROR (errno)); exit (1); } - + memset (msg_buf, 0x42, sizeof (msg_buf)); if (pid) { /* A positive (non-negative) PID indicates the parent process */ - close (commpipe[0]); /* Close unused side of pipe (in side) */ + if (0 != close (commpipe[0])) /* Close unused side of pipe (in side) */ + fprintf (stderr, + "Failed to close fd: %s\n", + strerror (errno)); setvbuf (stdout, (char *) NULL, _IONBF, 0); /* Set non-buffered output on stdout */ - + if (0 != close (macpipe[1])) + fprintf (stderr, + "Failed to close fd: %s\n", + strerror (errno)); + if (sizeof (hcm) != read (macpipe[0], &hcm, sizeof (hcm))) + fprintf (stderr, + "Failed to read hcm...\n"); + fprintf (stderr, + "Got MAC %.2X:%.2X:%.2X:%.2X:%.2X:%.2X\n", + hcm.mac.mac[0], hcm.mac.mac[1], + hcm.mac.mac[2], hcm.mac.mac[3], hcm.mac.mac[4], hcm.mac.mac[5]); radiotap = (struct GNUNET_TRANSPORT_WLAN_RadiotapSendMessage *) msg_buf; getRadiotapHeader (radiotap, WLAN_MTU); - pos = 0; getWlanHeader (&radiotap->frame, &outmac, &inmac, WLAN_MTU); start = time (NULL); count = 0; while (1) { - pos += write (commpipe[1], msg_buf, WLAN_MTU - pos); - if (pos % WLAN_MTU == 0) + ret = write (commpipe[1], msg_buf, WLAN_MTU); + if (0 > ret) { - pos = 0; - count++; - - if (count % 1000 == 0) - { - akt = time (NULL); - bytes_per_s = count * WLAN_MTU / (akt - start); - bytes_per_s /= 1024; - printf ("send %f kbytes/s\n", bytes_per_s); - } + fprintf (stderr, "write failed: %s\n", strerror (errno)); + break; } - + count += ret; + akt = time (NULL); + if (akt - start > 30) + { + bytes_per_s = count / (akt - start); + bytes_per_s /= 1024; + printf ("send %f kbytes/s\n", bytes_per_s); + start = akt; + count = 0; + } } } else { /* A zero PID indicates that this is the child process */ (void) close (0); + (void) close (1); if (-1 == dup2 (commpipe[0], 0)) /* Replace stdin with the in side of the pipe */ fprintf (stderr, "dup2 failed: %s\n", strerror (errno)); + if (-1 == dup2 (macpipe[1], 1)) /* Replace stdout with the out side of the pipe */ + fprintf (stderr, "dup2 failed: %s\n", strerror (errno)); (void) close (commpipe[1]); /* Close unused side of pipe (out side) */ + (void) close (macpipe[0]); /* Close unused side of pipe (in side) */ /* Replace the child fork with a new process */ - if (execl + if (execlp ("gnunet-helper-transport-wlan", "gnunet-helper-transport-wlan", argv[1], NULL) == -1) { diff --git a/src/transport/gnunet-transport.c b/src/transport/gnunet-transport.c index 3b6b7e4..8dd7bda 100644 --- a/src/transport/gnunet-transport.c +++ b/src/transport/gnunet-transport.c @@ -39,8 +39,15 @@ * How long do we wait for the NAT test to report success? * Should match NAT_SERVER_TIMEOUT in 'nat_test.c'. */ -#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 30) -#define RESOLUTION_TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 10) +#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 60) +#define RESOLUTION_TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 30) +#define OP_TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 30) + +/** + * Benchmarking block size in KB + */ +#define BLOCKSIZE 4 + /** * Which peer should we connect to? @@ -52,6 +59,16 @@ static char *cpid; */ static struct GNUNET_TRANSPORT_Handle *handle; +/** + * Configuration handle + */ +static struct GNUNET_CONFIGURATION_Handle *cfg; + +/** + * Try_connect handle + */ +struct GNUNET_TRANSPORT_TryConnectHandle * tc_handle; + /** * Option -s. */ @@ -77,11 +94,21 @@ static int iterate_connections; */ static int test_configuration; +/** + * Option -c. + */ +static int monitor_connects; + /** * Option -m. */ static int monitor_connections; +/** + * Option -C. + */ +static int try_connect; + /** * Option -n. */ @@ -92,6 +119,11 @@ static int numeric; */ static int ret; +/** + * Current number of connections in monitor mode + */ +static int monitor_connect_counter; + /** * Number of bytes of traffic we received so far. */ @@ -112,6 +144,11 @@ static struct GNUNET_TIME_Absolute start_time; */ static struct GNUNET_TRANSPORT_TransmitHandle *th; +/** + * + */ +struct GNUNET_TRANSPORT_PeerIterateContext *pic; + /** * Identity of the peer we transmit to / connect to. * (equivalent to 'cpid' string). @@ -123,6 +160,12 @@ static struct GNUNET_PeerIdentity pid; */ static GNUNET_SCHEDULER_TaskIdentifier end; +/** + * Task for operation timeout + */ +static GNUNET_SCHEDULER_TaskIdentifier op_timeout; + + static struct GNUNET_CONTAINER_MultiHashMap *peers; /** @@ -140,6 +183,15 @@ struct GNUNET_OS_Process *resolver; */ static unsigned int resolver_users; +/** + * Number of address resolutions pending + */ +static unsigned int address_resolutions; + +/** + * Address resolutions pending in progress + */ +static unsigned int address_resolution_in_progress; /** * Context for a plugin test. @@ -165,6 +217,123 @@ struct TestContext }; +/** + * Task run in monitor mode when the user presses CTRL-C to abort. + * Stops monitoring activity. + * + * @param cls the 'struct GNUNET_TRANSPORT_PeerIterateContext *' + * @param tc scheduler context + */ +static void +shutdown_task (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct GNUNET_TIME_Relative duration; + end = GNUNET_SCHEDULER_NO_TASK; + if (GNUNET_SCHEDULER_NO_TASK != op_timeout) + { + GNUNET_SCHEDULER_cancel (op_timeout); + op_timeout = GNUNET_SCHEDULER_NO_TASK; + } + if (NULL != tc_handle) + { + GNUNET_TRANSPORT_try_connect_cancel (tc_handle); + tc_handle = NULL; + } + if (NULL != pic) + { + GNUNET_TRANSPORT_peer_get_active_addresses_cancel (pic); + pic = NULL; + } + if (NULL != th) + { + GNUNET_TRANSPORT_notify_transmit_ready_cancel(th); + th = NULL; + } + if (NULL != handle) + { + GNUNET_TRANSPORT_disconnect(handle); + handle = NULL; + } + if (NULL != peers) + { + GNUNET_CONTAINER_multihashmap_destroy (peers); + peers = NULL; + } + if (benchmark_send) + { + duration = GNUNET_TIME_absolute_get_duration (start_time); + FPRINTF (stdout, _("Transmitted %llu bytes/s (%llu bytes in %s)\n"), + 1000 * traffic_sent / (1 + duration.rel_value), traffic_sent, + GNUNET_STRINGS_relative_time_to_string (duration, GNUNET_YES)); + } + if (benchmark_receive) + { + duration = GNUNET_TIME_absolute_get_duration (start_time); + FPRINTF (stdout, _("Received %llu bytes/s (%llu bytes in %s)\n"), + 1000 * traffic_received / (1 + duration.rel_value), + traffic_received, + GNUNET_STRINGS_relative_time_to_string (duration, GNUNET_YES)); + } +} + +struct ResolutionContext *rc_head; +struct ResolutionContext *rc_tail; + +struct ResolutionContext +{ + struct ResolutionContext *next; + struct ResolutionContext *prev; + struct GNUNET_HELLO_Address *addrcp; + struct GNUNET_TRANSPORT_AddressToStringContext *asc; + int printed; +}; + + +static void +operation_timeout (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct ResolutionContext *cur; + struct ResolutionContext *next; + op_timeout = GNUNET_SCHEDULER_NO_TASK; + if ((try_connect) || (benchmark_send) || + (benchmark_receive)) + { + FPRINTF (stdout, _("Failed to connect to `%s'\n"), GNUNET_h2s_full (&pid.hashPubKey)); + if (GNUNET_SCHEDULER_NO_TASK != end) + GNUNET_SCHEDULER_cancel (end); + end = GNUNET_SCHEDULER_add_now (&shutdown_task, NULL); + ret = 1; + return; + } + if (iterate_connections) + { + next = rc_head; + while (NULL != (cur = next)) + { + next = cur->next; + FPRINTF (stdout, _("Failed to resolve address for peer `%s'\n"), + GNUNET_i2s (&cur->addrcp->peer)); + + GNUNET_CONTAINER_DLL_remove (rc_head, rc_tail, cur); + GNUNET_TRANSPORT_address_to_string_cancel (cur->asc); + GNUNET_free (cur->addrcp); + GNUNET_free (cur); + + } + FPRINTF (stdout, "%s", _("Failed to list connections, timeout occured\n")); + if (GNUNET_SCHEDULER_NO_TASK != end) + GNUNET_SCHEDULER_cancel (end); + end = GNUNET_SCHEDULER_add_now (&shutdown_task, NULL); + ret = 1; + return; + } + +} + + + /** * Display the result of the test. * @@ -279,7 +448,7 @@ do_test_configuration (const struct GNUNET_CONFIGURATION_Handle *cfg) adv_port = bnd_port; if (NULL == resolver) resolver = - GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-resolver", + GNUNET_OS_start_process (GNUNET_YES, GNUNET_OS_INHERIT_STD_OUT_AND_ERR, NULL, NULL, "gnunet-service-resolver", "gnunet-service-resolver", NULL); resolver_users++; GNUNET_RESOLVER_connect (cfg); @@ -302,38 +471,6 @@ do_test_configuration (const struct GNUNET_CONFIGURATION_Handle *cfg) GNUNET_free (plugins); } - -/** - * Shutdown, print statistics. - */ -static void -do_disconnect (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - struct GNUNET_TIME_Relative duration; - - if (NULL != th) - { - GNUNET_TRANSPORT_notify_transmit_ready_cancel (th); - th = NULL; - } - GNUNET_TRANSPORT_disconnect (handle); - if (benchmark_receive) - { - duration = GNUNET_TIME_absolute_get_duration (start_time); - FPRINTF (stdout, _("Received %llu bytes/s (%llu bytes in %llu ms)\n"), - 1000 * traffic_received / (1 + duration.rel_value), - traffic_received, (unsigned long long) duration.rel_value); - } - if (benchmark_send) - { - duration = GNUNET_TIME_absolute_get_duration (start_time); - FPRINTF (stdout, _("Transmitted %llu bytes/s (%llu bytes in %llu ms)\n"), - 1000 * traffic_sent / (1 + duration.rel_value), traffic_sent, - (unsigned long long) duration.rel_value); - } -} - - /** * Function called to notify a client about the socket * begin ready to queue more data. "buf" will be @@ -350,13 +487,19 @@ transmit_data (void *cls, size_t size, void *buf) { struct GNUNET_MessageHeader *m = buf; + if ((NULL == buf) && (0 == size)) + { + th = NULL; + return 0; + } + GNUNET_assert (size >= sizeof (struct GNUNET_MessageHeader)); GNUNET_assert (size < GNUNET_SERVER_MAX_MESSAGE_SIZE); m->size = ntohs (size); m->type = ntohs (GNUNET_MESSAGE_TYPE_DUMMY); memset (&m[1], 52, size - sizeof (struct GNUNET_MessageHeader)); traffic_sent += size; - th = GNUNET_TRANSPORT_notify_transmit_ready (handle, &pid, 32 * 1024, 0, + th = GNUNET_TRANSPORT_notify_transmit_ready (handle, &pid, BLOCKSIZE * 1024, 0, GNUNET_TIME_UNIT_FOREVER_REL, &transmit_data, NULL); if (verbosity > 0) @@ -379,23 +522,45 @@ static void notify_connect (void *cls, const struct GNUNET_PeerIdentity *peer, const struct GNUNET_ATS_Information *ats, uint32_t ats_count) { - if (verbosity > 0) - FPRINTF (stdout, _("Connected to %s\n"), GNUNET_i2s (peer)); if (0 != memcmp (&pid, peer, sizeof (struct GNUNET_PeerIdentity))) return; ret = 0; - if (benchmark_send) + if (try_connect) { - start_time = GNUNET_TIME_absolute_get (); - th = GNUNET_TRANSPORT_notify_transmit_ready (handle, peer, 32 * 1024, 0, - GNUNET_TIME_UNIT_FOREVER_REL, - &transmit_data, NULL); + /* all done, terminate instantly */ + FPRINTF (stdout, _("Successfully connected to `%s'\n"), GNUNET_h2s_full (&peer->hashPubKey)); + ret = 0; + + if (GNUNET_SCHEDULER_NO_TASK != op_timeout) + { + GNUNET_SCHEDULER_cancel (op_timeout); + op_timeout = GNUNET_SCHEDULER_NO_TASK; + } + + if (GNUNET_SCHEDULER_NO_TASK != end) + GNUNET_SCHEDULER_cancel (end); + end = GNUNET_SCHEDULER_add_now (&shutdown_task, NULL); + return; } - else + if (benchmark_send) { - /* all done, terminate instantly */ - GNUNET_SCHEDULER_cancel (end); - end = GNUNET_SCHEDULER_add_now (&do_disconnect, NULL); + if (GNUNET_SCHEDULER_NO_TASK != op_timeout) + { + GNUNET_SCHEDULER_cancel (op_timeout); + op_timeout = GNUNET_SCHEDULER_NO_TASK; + } + if (verbosity > 0) + FPRINTF (stdout, _("Successfully connected to `%s', starting to send benchmark data in %u Kb blocks\n"), + GNUNET_i2s (&pid), BLOCKSIZE); + start_time = GNUNET_TIME_absolute_get (); + if (NULL == th) + th = GNUNET_TRANSPORT_notify_transmit_ready (handle, peer, + BLOCKSIZE * 1024, 0, + GNUNET_TIME_UNIT_FOREVER_REL, + &transmit_data, NULL); + else + GNUNET_break (0); + return; } } @@ -410,19 +575,73 @@ notify_connect (void *cls, const struct GNUNET_PeerIdentity *peer, static void notify_disconnect (void *cls, const struct GNUNET_PeerIdentity *peer) { - if (verbosity > 0) - FPRINTF (stdout, _("Disconnected from %s\n"), GNUNET_i2s (peer)); - if ((0 == memcmp (&pid, peer, sizeof (struct GNUNET_PeerIdentity))) && - (NULL != th)) + if (0 != memcmp (&pid, peer, sizeof (struct GNUNET_PeerIdentity))) + return; + + if (NULL != th) { GNUNET_TRANSPORT_notify_transmit_ready_cancel (th); th = NULL; - GNUNET_SCHEDULER_cancel (end); - end = GNUNET_SCHEDULER_add_now (&do_disconnect, NULL); } + if (benchmark_send) + { + FPRINTF (stdout, _("Disconnected from peer `%s' while benchmarking\n"), GNUNET_i2s (&pid)); + if (GNUNET_SCHEDULER_NO_TASK != end) + GNUNET_SCHEDULER_cancel (end); + return; + } +} + +/** + * Function called to notify transport users that another + * peer connected to us. + * + * @param cls closure + * @param peer the peer that connected + * @param ats performance data + * @param ats_count number of entries in ats (excluding 0-termination) + */ +static void +monitor_notify_connect (void *cls, const struct GNUNET_PeerIdentity *peer, + const struct GNUNET_ATS_Information *ats, uint32_t ats_count) +{ + monitor_connect_counter ++; + struct GNUNET_TIME_Absolute now = GNUNET_TIME_absolute_get(); + const char *now_str = GNUNET_STRINGS_absolute_time_to_string (now); + + FPRINTF (stdout, _("%24s: %-17s %4s (%u connections in total)\n"), + now_str, + _("Connected to"), + GNUNET_i2s (peer), + monitor_connect_counter); +} + + +/** + * Function called to notify transport users that another + * peer disconnected from us. + * + * @param cls closure + * @param peer the peer that disconnected + */ +static void +monitor_notify_disconnect (void *cls, const struct GNUNET_PeerIdentity *peer) +{ + struct GNUNET_TIME_Absolute now = GNUNET_TIME_absolute_get(); + const char *now_str = GNUNET_STRINGS_absolute_time_to_string (now); + + GNUNET_assert (monitor_connect_counter > 0); + monitor_connect_counter --; + + FPRINTF (stdout, _("%24s: %-17s %4s (%u connections in total)\n"), + now_str, + _("Disconnected from"), + GNUNET_i2s (peer), + monitor_connect_counter); } + /** * Function called by the transport for each received message. * @@ -437,22 +656,24 @@ notify_receive (void *cls, const struct GNUNET_PeerIdentity *peer, const struct GNUNET_MessageHeader *message, const struct GNUNET_ATS_Information *ats, uint32_t ats_count) { - if (!benchmark_receive) + if (benchmark_receive) + { + if (GNUNET_MESSAGE_TYPE_DUMMY != ntohs (message->type)) + return; + if (verbosity > 0) + FPRINTF (stdout, _("Received %u bytes from %s\n"), + (unsigned int) ntohs (message->size), GNUNET_i2s (peer)); + + if (traffic_received == 0) + start_time = GNUNET_TIME_absolute_get (); + traffic_received += ntohs (message->size); return; - if (verbosity > 0) - FPRINTF (stdout, _("Received %u bytes from %s\n"), - (unsigned int) ntohs (message->size), GNUNET_i2s (peer)); - if (traffic_received == 0) - start_time = GNUNET_TIME_absolute_get (); - traffic_received += ntohs (message->size); + } } -struct ResolutionContext -{ - struct GNUNET_HELLO_Address *addrcp; - int printed; -}; +static void resolve_address (const struct GNUNET_HELLO_Address *address, + int numeric); static void @@ -469,13 +690,56 @@ process_string (void *cls, const char *address) else { /* done */ + GNUNET_assert (address_resolutions > 0); + address_resolutions --; if (GNUNET_NO == rc->printed) - FPRINTF (stdout, _("Peer `%s': %s \n"), GNUNET_i2s (&addrcp->peer), addrcp->transport_name); + { + if (numeric == GNUNET_NO) + { + resolve_address (rc->addrcp, GNUNET_YES ); /* Failed to resolve address, try numeric lookup */ + } + else + FPRINTF (stdout, _("Peer `%s': %s \n"), GNUNET_i2s (&addrcp->peer), addrcp->transport_name); + } GNUNET_free (rc->addrcp); + GNUNET_CONTAINER_DLL_remove (rc_head, rc_tail, rc); GNUNET_free (rc); + if ((0 == address_resolutions) && (iterate_connections)) + { + if (GNUNET_SCHEDULER_NO_TASK != end) + { + GNUNET_SCHEDULER_cancel (end); + end = GNUNET_SCHEDULER_NO_TASK; + } + if (GNUNET_SCHEDULER_NO_TASK != op_timeout) + { + GNUNET_SCHEDULER_cancel (op_timeout); + op_timeout = GNUNET_SCHEDULER_NO_TASK; + } + ret = 0; + end = GNUNET_SCHEDULER_add_now (&shutdown_task, NULL); + } } } +static void resolve_address (const struct GNUNET_HELLO_Address *address, + int numeric) +{ + struct ResolutionContext *rc; + + rc = GNUNET_malloc(sizeof (struct ResolutionContext)); + GNUNET_assert (NULL != rc); + GNUNET_CONTAINER_DLL_insert (rc_head, rc_tail, rc); + address_resolutions ++; + + rc->addrcp = GNUNET_HELLO_address_copy(address); + rc->printed = GNUNET_NO; + /* Resolve address to string */ + rc->asc = GNUNET_TRANSPORT_address_to_string (cfg, address, numeric, + RESOLUTION_TIMEOUT, &process_string, + rc); +} + /** * Function to call with a binary address * @@ -487,148 +751,268 @@ static void process_address (void *cls, const struct GNUNET_PeerIdentity *peer, const struct GNUNET_HELLO_Address *address) { - const struct GNUNET_CONFIGURATION_Handle *cfg = cls; - struct ResolutionContext *rc; - if (peer == NULL) { /* done */ + address_resolution_in_progress = GNUNET_NO; + pic = NULL; + if (GNUNET_SCHEDULER_NO_TASK != end) + GNUNET_SCHEDULER_cancel (end); + end = GNUNET_SCHEDULER_add_now (&shutdown_task, NULL); return; } - if (address == NULL) { FPRINTF (stdout, _("Peer `%s' disconnected\n"), GNUNET_i2s (peer)); return; } - rc = GNUNET_malloc(sizeof (struct ResolutionContext)); - rc->addrcp = GNUNET_HELLO_address_copy(address); - rc->printed = GNUNET_NO; + if (GNUNET_SCHEDULER_NO_TASK != op_timeout) + GNUNET_SCHEDULER_cancel (op_timeout); + op_timeout = GNUNET_SCHEDULER_add_delayed (OP_TIMEOUT, + &operation_timeout, NULL); - GNUNET_assert (NULL != rc); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received address for peer `%s': %s\n", + GNUNET_i2s (peer), address->transport_name); + resolve_address (address, numeric); +} - /* Resolve address to string */ - GNUNET_TRANSPORT_address_to_string (cfg, address, numeric, - RESOLUTION_TIMEOUT, &process_string, - rc); +void try_connect_cb (void *cls, + const int result) +{ + static int retries = 0; + if (GNUNET_OK == result) + { + tc_handle = NULL; + return; + } + retries ++; + if (retries < 10) + tc_handle = GNUNET_TRANSPORT_try_connect (handle, &pid, try_connect_cb, NULL); + else + { + FPRINTF (stderr, "%s", _("Failed to send connect request to transport service\n")); + if (GNUNET_SCHEDULER_NO_TASK != end) + GNUNET_SCHEDULER_cancel (end); + ret = 1; + end = GNUNET_SCHEDULER_add_now (&shutdown_task, NULL); + return; + } } -/** - * Task run in monitor mode when the user presses CTRL-C to abort. - * Stops monitoring activity. - * - * @param cls the 'struct GNUNET_TRANSPORT_PeerIterateContext *' - * @param tc scheduler context - */ static void -shutdown_task (void *cls, - const struct GNUNET_SCHEDULER_TaskContext *tc) +testservice_task (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) { - struct GNUNET_TRANSPORT_PeerIterateContext *pic = cls; + int counter = 0; + ret = 1; - GNUNET_TRANSPORT_peer_get_active_addresses_cancel (pic); - - if (NULL != peers) + if (0 != (tc->reason & GNUNET_SCHEDULER_REASON_TIMEOUT)) { - GNUNET_CONTAINER_multihashmap_destroy (peers); - peers = NULL; + FPRINTF (stderr, _("Service `%s' is not running\n"), "transport"); + return; } -} + if ((NULL != cpid) && (GNUNET_OK != GNUNET_CRYPTO_hash_from_string (cpid, &pid.hashPubKey))) + { + FPRINTF (stderr, _("Failed to parse peer identity `%s'\n"), cpid); + return; + } + counter = benchmark_send + benchmark_receive + iterate_connections + + monitor_connections + monitor_connects + try_connect; -/** - * Main function that will be run by the scheduler. - * - * @param cls closure - * @param args remaining command-line arguments - * @param cfgfile name of the configuration file used (for saving, can be NULL!) - * @param cfg configuration - */ -static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) -{ - if (test_configuration) + if (1 < counter) { - do_test_configuration (cfg); + FPRINTF (stderr, _("Multiple operations given. Please choose only one operation: %s, %s, %s, %s, %s, %s\n"), + "connect", "benchmark send", "benchmark receive", "information", "monitor", "events"); + return; } - if (benchmark_send && (NULL == cpid)) + if (0 == counter) { - FPRINTF (stderr, _("Option `%s' makes no sense without option `%s'.\n"), - "-s", "-C"); + FPRINTF (stderr, _("No operation given. Please choose one operation: %s, %s, %s, %s, %s, %s\n"), + "connect", "benchmark send", "benchmark receive", "information", "monitor", "events"); return; } - if (NULL != cpid) + + if (try_connect) /* -C: Connect to peer */ { - ret = 1; - if (GNUNET_OK != GNUNET_CRYPTO_hash_from_string (cpid, &pid.hashPubKey)) + if (NULL == cpid) { - FPRINTF (stderr, _("Failed to parse peer identity `%s'\n"), cpid); + FPRINTF (stderr, _("Option `%s' makes no sense without option `%s'.\n"), + "-C", "-p"); + ret = 1; return; } - handle = - GNUNET_TRANSPORT_connect (cfg, NULL, NULL, ¬ify_receive, - ¬ify_connect, ¬ify_disconnect); - GNUNET_TRANSPORT_try_connect (handle, &pid); - end = - GNUNET_SCHEDULER_add_delayed (benchmark_send ? - GNUNET_TIME_UNIT_FOREVER_REL : - GNUNET_TIME_UNIT_SECONDS, &do_disconnect, - NULL); + handle = GNUNET_TRANSPORT_connect (cfg, NULL, NULL, + ¬ify_receive, + ¬ify_connect, + ¬ify_disconnect); + if (NULL == handle) + { + FPRINTF (stderr, "%s", _("Failed to connect to transport service\n")); + ret = 1; + return; + } + tc_handle = GNUNET_TRANSPORT_try_connect (handle, &pid, try_connect_cb, NULL); + if (NULL == tc_handle) + { + FPRINTF (stderr, "%s", _("Failed to send request to transport service\n")); + ret = 1; + return; + } + op_timeout = GNUNET_SCHEDULER_add_delayed (OP_TIMEOUT, + &operation_timeout, NULL); + } - else if (benchmark_receive) + else if (benchmark_send) /* -s: Benchmark sending */ + { + if (NULL == cpid) + { + FPRINTF (stderr, _("Option `%s' makes no sense without option `%s'.\n"), + "-s", "-p"); + ret = 1; + return; + } + handle = GNUNET_TRANSPORT_connect (cfg, NULL, NULL, + ¬ify_receive, + ¬ify_connect, + ¬ify_disconnect); + if (NULL == handle) + { + FPRINTF (stderr, "%s", _("Failed to connect to transport service\n")); + ret = 1; + return; + } + tc_handle = GNUNET_TRANSPORT_try_connect (handle, &pid, try_connect_cb, NULL); + if (NULL == tc_handle) + { + FPRINTF (stderr, "%s", _("Failed to send request to transport service\n")); + ret = 1; + return; + } + start_time = GNUNET_TIME_absolute_get (); + op_timeout = GNUNET_SCHEDULER_add_delayed (OP_TIMEOUT, + &operation_timeout, NULL); + } + else if (benchmark_receive) /* -b: Benchmark receiving */ { handle = GNUNET_TRANSPORT_connect (cfg, NULL, NULL, ¬ify_receive, - ¬ify_connect, ¬ify_disconnect); - GNUNET_TRANSPORT_try_connect (handle, &pid); - end = - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, - &do_disconnect, NULL); + NULL, NULL); + if (NULL == handle) + { + FPRINTF (stderr, "%s", _("Failed to connect to transport service\n")); + ret = 1; + return; + } + if (verbosity > 0) + FPRINTF (stdout, "%s", _("Starting to receive benchmark data\n")); + start_time = GNUNET_TIME_absolute_get (); + } - if (iterate_connections) + else if (iterate_connections) /* -i: List all active addresses once */ + { + peers = GNUNET_CONTAINER_multihashmap_create (20, GNUNET_NO); + address_resolution_in_progress = GNUNET_YES; + pic = GNUNET_TRANSPORT_peer_get_active_addresses (cfg, + (NULL == cpid) ? NULL : &pid, + GNUNET_YES, + TIMEOUT, + &process_address, (void *) cfg); + op_timeout = GNUNET_SCHEDULER_add_delayed (OP_TIMEOUT, + &operation_timeout, NULL); + } + else if (monitor_connections) /* -m: List all active addresses continously */ { - peers = GNUNET_CONTAINER_multihashmap_create (20); - GNUNET_TRANSPORT_peer_get_active_addresses (cfg, NULL, GNUNET_YES, + peers = GNUNET_CONTAINER_multihashmap_create (20, GNUNET_NO); + address_resolution_in_progress = GNUNET_YES; + pic = GNUNET_TRANSPORT_peer_get_active_addresses (cfg, + (NULL == cpid) ? NULL : &pid, + GNUNET_NO, TIMEOUT, &process_address, (void *) cfg); } - if (monitor_connections) + else if (monitor_connects) /* -e : Monitor (dis)connect events continously */ { - struct GNUNET_TRANSPORT_PeerIterateContext *pic; + monitor_connect_counter = 0; + handle = GNUNET_TRANSPORT_connect (cfg, NULL, NULL, NULL, + &monitor_notify_connect, + &monitor_notify_disconnect); + if (NULL == handle) + { + FPRINTF (stderr, "%s", _("Failed to connect to transport service\n")); + ret = 1; + return; + } + ret = 0; + } + else + { + GNUNET_break (0); + return; + } + + end = GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, + &shutdown_task, + NULL); + +} + - pic = GNUNET_TRANSPORT_peer_get_active_addresses (cfg, NULL, GNUNET_NO, - GNUNET_TIME_UNIT_FOREVER_REL, - &process_address, (void *) cfg); - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, - &shutdown_task, - pic); +/** + * Main function that will be run by the scheduler. + * + * @param cls closure + * @param args remaining command-line arguments + * @param cfgfile name of the configuration file used (for saving, can be NULL!) + * @param cfg configuration + */ +static void +run (void *cls, char *const *args, const char *cfgfile, + const struct GNUNET_CONFIGURATION_Handle *mycfg) +{ + cfg = (struct GNUNET_CONFIGURATION_Handle *) mycfg; + if (test_configuration) + { + do_test_configuration (cfg); + return; } + + GNUNET_CLIENT_service_test ("transport", cfg, + GNUNET_TIME_UNIT_SECONDS, + &testservice_task, + (void *) cfg); } int main (int argc, char *const *argv) { + int res; static const struct GNUNET_GETOPT_CommandLineOption options[] = { {'b', "benchmark", NULL, - gettext_noop ("measure how fast we are receiving data (until CTRL-C)"), + gettext_noop ("measure how fast we are receiving data from all peers (until CTRL-C)"), 0, &GNUNET_GETOPT_set_one, &benchmark_receive}, - {'C', "connect", "PEER", - gettext_noop ("try to connect to the given peer"), - 1, &GNUNET_GETOPT_set_string, &cpid}, + {'C', "connect", NULL, + gettext_noop ("connect to a peer"), + 0, &GNUNET_GETOPT_set_one, &try_connect}, {'i', "information", NULL, gettext_noop ("provide information about all current connections (once)"), 0, &GNUNET_GETOPT_set_one, &iterate_connections}, {'m', "monitor", NULL, gettext_noop ("provide information about all current connections (continuously)"), 0, &GNUNET_GETOPT_set_one, &monitor_connections}, + {'e', "events", NULL, + gettext_noop ("provide information about all connects and disconnect events (continuously)"), + 0, &GNUNET_GETOPT_set_one, &monitor_connects}, {'n', "numeric", NULL, gettext_noop ("do not resolve hostnames"), 0, &GNUNET_GETOPT_set_one, &numeric}, + {'p', "peer", "PEER", + gettext_noop ("peer identity"), + 1, &GNUNET_GETOPT_set_string, &cpid}, {'s', "send", NULL, gettext_noop ("send data for benchmarking to the other peer (until CTRL-C)"), @@ -639,11 +1023,18 @@ main (int argc, char *const *argv) GNUNET_GETOPT_OPTION_VERBOSE (&verbosity), GNUNET_GETOPT_OPTION_END }; - return (GNUNET_OK == - GNUNET_PROGRAM_run (argc, argv, "gnunet-transport", + + if (GNUNET_OK != GNUNET_STRINGS_get_utf8_args (argc, argv, &argc, &argv)) + return 2; + + res = GNUNET_PROGRAM_run (argc, argv, "gnunet-transport", gettext_noop ("Direct access to transport service."), options, - &run, NULL)) ? ret : 1; + &run, NULL); + GNUNET_free ((void *) argv); + if (GNUNET_OK == res) + return ret; + return 1; } diff --git a/src/transport/plugin_transport_http.c b/src/transport/plugin_transport_http.c deleted file mode 100644 index d99f531..0000000 --- a/src/transport/plugin_transport_http.c +++ /dev/null @@ -1,1743 +0,0 @@ -/* - This file is part of GNUnet - (C) 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009 Christian Grothoff (and other contributing authors) - - GNUnet is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published - by the Free Software Foundation; either version 3, or (at your - option) any later version. - - GNUnet is distributed in the hope that it will be useful, but - WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - General Public License for more details. - - You should have received a copy of the GNU General Public License - along with GNUnet; see the file COPYING. If not, write to the - Free Software Foundation, Inc., 59 Temple Place - Suite 330, - Boston, MA 02111-1307, USA. -*/ - -/** - * @file transport/plugin_transport_http.c - * @brief http transport service plugin - * @author Matthias Wachs - */ - -#include "plugin_transport_http.h" - -/** - * After how long do we expire an address that we - * learned from another peer if it is not reconfirmed - * by anyone? - */ -#define LEARNED_ADDRESS_EXPIRATION GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_HOURS, 6) - -/** - * Wrapper to manage IPv4 addresses - */ -struct IPv4HttpAddressWrapper -{ - /** - * Linked list next - */ - struct IPv4HttpAddressWrapper *next; - - /** - * Linked list previous - */ - struct IPv4HttpAddressWrapper *prev; - - struct IPv4HttpAddress addr; -}; - -/** - * Wrapper for IPv4 addresses. - */ -struct IPv6HttpAddressWrapper -{ - /** - * Linked list next - */ - struct IPv6HttpAddressWrapper *next; - - /** - * Linked list previous - */ - struct IPv6HttpAddressWrapper *prev; - - struct IPv6HttpAddress addr6; -}; - - -/** - * Context for address to string conversion. - */ -struct PrettyPrinterContext -{ - /** - * Function to call with the result. - */ - GNUNET_TRANSPORT_AddressStringCallback asc; - - /** - * Plugin - */ - struct Plugin *plugin; - - /** - * Clsoure for 'asc'. - */ - void *asc_cls; - - /** - * Port to add after the IP address. - */ - uint16_t port; - - uint32_t addrlen; - - int numeric; -}; - - -/** - * Encapsulation of all of the state of the plugin. - */ -struct Plugin; - -/** - * Start session timeout - */ -static void -start_session_timeout (struct Session *s); - -/** - * Increment session timeout due to activity - */ -static void -reschedule_session_timeout (struct Session *s); - -/** - * Cancel timeout - */ -static void -stop_session_timeout (struct Session *s); - -/** - * Append our port and forward the result. - * - * @param cls the 'struct PrettyPrinterContext*' - * @param hostname hostname part of the address - */ -static void -append_port (void *cls, const char *hostname) -{ - struct PrettyPrinterContext *ppc = cls; - static char rbuf[INET6_ADDRSTRLEN + 13]; - - if (hostname == NULL) - { - ppc->asc (ppc->asc_cls, NULL); - GNUNET_free (ppc); - return; - } - -#if !BUILD_HTTPS - const char *protocol = "http"; -#else - const char *protocol = "https"; -#endif - GNUNET_assert ((strlen (hostname) + 7) < (INET6_ADDRSTRLEN + 13)); - if (ppc->addrlen == sizeof (struct IPv6HttpAddress)) - { - if (ppc->numeric == GNUNET_YES) - GNUNET_snprintf (rbuf, sizeof (rbuf), "%s://[%s]:%u/", protocol, hostname, ppc->port); - else - { - if (strchr(hostname, ':') != NULL) - GNUNET_snprintf (rbuf, sizeof (rbuf), "%s://[%s]:%u/", protocol, hostname, ppc->port); - else - GNUNET_snprintf (rbuf, sizeof (rbuf), "%s://%s:%u/", protocol, hostname, ppc->port); - } - } - else if (ppc->addrlen == sizeof (struct IPv4HttpAddress)) - GNUNET_snprintf (rbuf, sizeof (rbuf), "%s://%s:%u/", protocol, hostname, ppc->port); - ppc->asc (ppc->asc_cls, rbuf); -} - - - - - -/** - * Convert the transports address to a nice, human-readable - * format. - * - * @param cls closure - * @param type name of the transport that generated the address - * @param addr one of the addresses of the host, NULL for the last address - * the specific address format depends on the transport - * @param addrlen length of the address - * @param numeric should (IP) addresses be displayed in numeric form? - * @param timeout after how long should we give up? - * @param asc function to call on each string - * @param asc_cls closure for asc - */ -static void -http_plugin_address_pretty_printer (void *cls, const char *type, - const void *addr, size_t addrlen, - int numeric, - struct GNUNET_TIME_Relative timeout, - GNUNET_TRANSPORT_AddressStringCallback asc, - void *asc_cls) -{ - GNUNET_assert (cls != NULL); - struct PrettyPrinterContext *ppc; - const void *sb; - struct sockaddr_in s4; - struct sockaddr_in6 s6; - size_t sbs; - uint16_t port = 0; - - if ((addrlen == sizeof (struct IPv6HttpAddress)) && (addr != NULL)) - { - struct IPv6HttpAddress *a6 = (struct IPv6HttpAddress *) addr; - s6.sin6_family = AF_INET6; - s6.sin6_addr = a6->ipv6_addr; - s6.sin6_port = a6->u6_port; -#if HAVE_SOCKADDR_IN_SIN_LEN - s6.sin6_len = sizeof (struct sockaddr_in6); -#endif - sb = &s6; - sbs = sizeof (struct sockaddr_in6); - port = ntohs (a6->u6_port); - - } - else if ((addrlen == sizeof (struct IPv4HttpAddress)) && (addr != NULL)) - { - struct IPv4HttpAddress *a4 = (struct IPv4HttpAddress *) addr; - - s4.sin_family = AF_INET; - s4.sin_addr.s_addr = a4->ipv4_addr; - s4.sin_port = a4->u4_port; -#if HAVE_SOCKADDR_IN_SIN_LEN - s4.sin_len = sizeof (struct sockaddr_in); -#endif - sb = &s4; - sbs = sizeof (struct sockaddr_in); - port = ntohs (a4->u4_port); - } - else if (0 == addrlen) - { - asc (asc_cls, ""); - asc (asc_cls, NULL); - return; - } - else - { - /* invalid address */ - GNUNET_break_op (0); - asc (asc_cls, NULL); - return; - } - ppc = GNUNET_malloc (sizeof (struct PrettyPrinterContext)); - ppc->asc = asc; - ppc->asc_cls = asc_cls; - ppc->port = port; - ppc->plugin = cls; - ppc->addrlen = addrlen; - ppc->numeric = numeric; - GNUNET_RESOLVER_hostname_get (sb, sbs, !numeric, timeout, &append_port, ppc); -} - - - -/** - * Another peer has suggested an address for this - * peer and transport plugin. Check that this could be a valid - * address. If so, consider adding it to the list - * of addresses. - * - * @param cls closure - * @param addr pointer to the address - * @param addrlen length of addr - * @return GNUNET_OK if this is a plausible address for this peer - * and transport - */ -static int -http_plugin_address_suggested (void *cls, const void *addr, size_t addrlen) -{ - struct Plugin *plugin = cls; - struct IPv4HttpAddressWrapper *w_tv4 = plugin->ipv4_addr_head; - struct IPv6HttpAddressWrapper *w_tv6 = plugin->ipv6_addr_head; - - GNUNET_assert (cls != NULL); - if ((addrlen != sizeof (struct sockaddr_in)) || - (addrlen != sizeof (struct sockaddr_in6))) - return GNUNET_SYSERR; - - if (addrlen == sizeof (struct IPv4HttpAddress)) - { - struct IPv4HttpAddress *a4 = (struct IPv4HttpAddress *) addr; - - while (w_tv4 != NULL) - { - if ((0 == - memcmp (&w_tv4->addr.ipv4_addr, &a4->ipv4_addr, - sizeof (struct in_addr))) && - (w_tv4->addr.u4_port == a4->u4_port)) - break; - w_tv4 = w_tv4->next; - } - if (w_tv4 != NULL) - return GNUNET_OK; - else - return GNUNET_SYSERR; - } - if (addrlen == sizeof (struct sockaddr_in6)) - { - struct IPv6HttpAddress *a6 = (struct IPv6HttpAddress *) addr; - - while (w_tv6 != NULL) - { - if ((0 == - memcmp (&w_tv6->addr6.ipv6_addr, &a6->ipv6_addr, - sizeof (struct in6_addr))) && - (w_tv6->addr6.u6_port == a6->u6_port)) - break; - w_tv6 = w_tv6->next; - } - if (w_tv6 != NULL) - return GNUNET_OK; - else - return GNUNET_SYSERR; - } - return GNUNET_OK; -} - -struct GNUNET_TIME_Relative -http_plugin_receive (void *cls, const struct GNUNET_PeerIdentity *peer, - const struct GNUNET_MessageHeader *message, - struct Session *session, const char *sender_address, - uint16_t sender_address_len) -{ - struct Session *s = cls; - struct Plugin *plugin = s->plugin; - struct GNUNET_TIME_Relative delay; - struct GNUNET_ATS_Information atsi[2]; - - atsi[0].type = htonl (GNUNET_ATS_QUALITY_NET_DISTANCE); - atsi[0].value = htonl (1); - atsi[1].type = htonl (GNUNET_ATS_NETWORK_TYPE); - atsi[1].value = session->ats_address_network_type; - GNUNET_break (session->ats_address_network_type != ntohl (GNUNET_ATS_NET_UNSPECIFIED)); - - reschedule_session_timeout (session); - - delay = - plugin->env->receive (plugin->env->cls, &s->target, message, - (const struct GNUNET_ATS_Information *) &atsi, - 2, s, s->addr, s->addrlen); - return delay; -} - - -/** - * Function called to convert a string address to - * a binary address. - * - * @param cls closure ('struct Plugin*') - * @param addr string address - * @param addrlen length of the address - * @param buf location to store the buffer - * If the function returns GNUNET_SYSERR, its contents are undefined. - * @param added length of created address - * @return GNUNET_OK on success, GNUNET_SYSERR on failure - */ -int -http_string_to_address (void *cls, - const char *addr, - uint16_t addrlen, - void **buf, - size_t *added) -{ -#if !BUILD_HTTPS - char *protocol = "http"; -#else - char *protocol = "https"; -#endif - char *addr_str = NULL; - struct sockaddr_in addr_4; - struct sockaddr_in6 addr_6; - struct IPv4HttpAddress * http_4addr; - struct IPv6HttpAddress * http_6addr; - - if ((NULL == addr) || (addrlen == 0)) - { - GNUNET_break (0); - return GNUNET_SYSERR; - } - - if ('\0' != addr[addrlen - 1]) - { - GNUNET_break (0); - return GNUNET_SYSERR; - } - - if (strlen (addr) != addrlen - 1) - { - GNUNET_break (0); - return GNUNET_SYSERR; - } - - /* protocoll + "://" + ":" */ - if (addrlen <= (strlen (protocol) + 4)) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "Invalid address string `%s' to convert to address\n", - addr); - GNUNET_break (0); - return GNUNET_SYSERR; - } - - if (NULL == (addr_str = strstr(addr, "://"))) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "Invalid address string `%s' to convert to address\n", - addr); - GNUNET_break (0); - return GNUNET_SYSERR; - } - addr_str = &addr_str[3]; - - if (addr_str[strlen(addr_str)-1] == '/') - addr_str[strlen(addr_str)-1] = '\0'; - - if (GNUNET_OK == GNUNET_STRINGS_to_address_ipv4(addr_str, strlen(addr_str), &addr_4)) - { - http_4addr = GNUNET_malloc (sizeof (struct IPv4HttpAddress)); - http_4addr->u4_port = addr_4.sin_port; - http_4addr->ipv4_addr = (uint32_t) addr_4.sin_addr.s_addr; - (*buf) = http_4addr; - (*added) = sizeof (struct IPv4HttpAddress); - return GNUNET_OK; - } - if (GNUNET_OK == GNUNET_STRINGS_to_address_ipv6(addr_str, strlen(addr_str), &addr_6)) - { - http_6addr = GNUNET_malloc (sizeof (struct IPv6HttpAddress)); - http_6addr->u6_port = addr_6.sin6_port; - http_6addr->ipv6_addr = addr_6.sin6_addr; - (*buf) = http_6addr; - (*added) = sizeof (struct IPv6HttpAddress); - return GNUNET_OK; - } - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "Invalid address string `%s' to convert to address\n", - addr_str); - GNUNET_break (0); - return GNUNET_SYSERR; -} - - -/** - * Function called for a quick conversion of the binary address to - * a numeric address. Note that the caller must not free the - * address and that the next call to this function is allowed - * to override the address again. - * - * @param cls closure - * @param addr binary address - * @param addrlen length of the address - * @return string representing the same address - */ -const char * -http_plugin_address_to_string (void *cls, const void *addr, size_t addrlen) -{ - - struct IPv4HttpAddress *a4; - struct IPv6HttpAddress *a6; - char *address; - static char rbuf[INET6_ADDRSTRLEN + 13]; - uint16_t port; - int res = 0; - - if (addrlen == sizeof (struct IPv6HttpAddress)) - { - a6 = (struct IPv6HttpAddress *) addr; - address = GNUNET_malloc (INET6_ADDRSTRLEN); - GNUNET_assert (NULL != - inet_ntop (AF_INET6, &a6->ipv6_addr, address, - INET6_ADDRSTRLEN)); - port = ntohs (a6->u6_port); - } - else if (addrlen == sizeof (struct IPv4HttpAddress)) - { - a4 = (struct IPv4HttpAddress *) addr; - address = GNUNET_malloc (INET_ADDRSTRLEN); - GNUNET_assert (NULL != - inet_ntop (AF_INET, &(a4->ipv4_addr), address, - INET_ADDRSTRLEN)); - port = ntohs (a4->u4_port); - } - else - { - /* invalid address */ - GNUNET_break (0); - return NULL; - } -#if !BUILD_HTTPS - char *protocol = "http"; -#else - char *protocol = "https"; -#endif - - GNUNET_assert (strlen (address) + 7 < (INET6_ADDRSTRLEN + 13)); - if (addrlen == sizeof (struct IPv6HttpAddress)) - res = - GNUNET_snprintf (rbuf, sizeof (rbuf), "%s://[%s]:%u/", protocol, - address, port); - else if (addrlen == sizeof (struct IPv4HttpAddress)) - res = - GNUNET_snprintf (rbuf, sizeof (rbuf), "%s://%s:%u/", protocol, address, - port); - - GNUNET_free (address); - GNUNET_assert (res != 0); - return rbuf; -} - - -struct Session * -lookup_session_old (struct Plugin *plugin, const struct GNUNET_PeerIdentity *target, - struct Session *session, const void *addr, size_t addrlen, - int force_address) -{ - struct Session *t; - int e_peer; - int e_addr; - - for (t = plugin->head; NULL != t; t = t->next) - { -#if 0 - GNUNET_log_from (GNUNET_ERROR_TYPE_ERROR, plugin->name, - "Comparing peer `%s' address `%s' len %i session %p to \n", - GNUNET_i2s (target), GNUNET_a2s (addr, addrlen), addrlen, - session); - GNUNET_log_from (GNUNET_ERROR_TYPE_ERROR, plugin->name, - "peer `%s' address `%s' len %i session %p \n\n", - GNUNET_i2s (&t->target), GNUNET_a2s (t->addr, t->addrlen), - t->addrlen, t); - GNUNET_log_from (GNUNET_ERROR_TYPE_ERROR, plugin->name, "memcmp %i \n", - memcmp (addr, t->addr, addrlen)); -#endif - e_peer = GNUNET_NO; - e_addr = GNUNET_NO; - if (0 == memcmp (target, &t->target, sizeof (struct GNUNET_PeerIdentity))) - { - e_peer = GNUNET_YES; - if ( (addrlen == t->addrlen) && - (0 == memcmp (addr, t->addr, addrlen)) ) - e_addr = GNUNET_YES; - if ( (t == session) && - (t->addrlen == session->addrlen) && - (0 == memcmp (session->addr, t->addr, t->addrlen)) ) - e_addr = GNUNET_YES; - } - - if ( ((e_peer == GNUNET_YES) && (force_address == GNUNET_NO)) || - ((e_peer == GNUNET_YES) && (force_address == GNUNET_YES) && (e_addr == GNUNET_YES)) || - ((e_peer == GNUNET_YES) && (force_address == GNUNET_SYSERR)) ) - return t; - } - return NULL; -} - - -struct Session * -lookup_session (struct Plugin *plugin, - const struct GNUNET_HELLO_Address *address) -{ - struct Session *pos; - - for (pos = plugin->head; NULL != pos; pos = pos->next) - if ( (0 == memcmp (&address->peer, &pos->target, sizeof (struct GNUNET_PeerIdentity))) && - (address->address_length == pos->addrlen) && - (0 == memcmp (address->address, pos->addr, pos->addrlen)) ) - return pos; - return NULL; -} - - -int -exist_session (struct Plugin *plugin, struct Session *s) -{ - struct Session * head; - - GNUNET_assert (NULL != plugin); - GNUNET_assert (NULL != s); - - for (head = plugin->head; head != NULL; head = head->next) - { - if (head == s) - return GNUNET_YES; - } - return GNUNET_NO; -} - - -void -delete_session (struct Session *s) -{ - stop_session_timeout(s); - - if (s->msg_tk != NULL) - { - GNUNET_SERVER_mst_destroy (s->msg_tk); - s->msg_tk = NULL; - } - GNUNET_free (s->addr); - GNUNET_free_non_null (s->server_recv); - GNUNET_free_non_null (s->server_send); - GNUNET_free (s); -} - - -struct Session * -create_session (struct Plugin *plugin, const struct GNUNET_PeerIdentity *target, - const void *addr, size_t addrlen) -{ - struct Session *s = NULL; - - GNUNET_assert ((addrlen == sizeof (struct IPv6HttpAddress)) || - (addrlen == sizeof (struct IPv4HttpAddress))); - s = GNUNET_malloc (sizeof (struct Session)); - memcpy (&s->target, target, sizeof (struct GNUNET_PeerIdentity)); - s->plugin = plugin; - s->addr = GNUNET_malloc (addrlen); - memcpy (s->addr, addr, addrlen); - s->addrlen = addrlen; - s->ats_address_network_type = htonl (GNUNET_ATS_NET_UNSPECIFIED); - start_session_timeout(s); - return s; -} - - -void -notify_session_end (void *cls, const struct GNUNET_PeerIdentity *peer, - struct Session *s) -{ - struct Plugin *plugin = cls; - - plugin->env->session_end (plugin->env->cls, peer, s); - GNUNET_CONTAINER_DLL_remove (plugin->head, plugin->tail, s); - delete_session (s); -} - - -/** - * Creates a new outbound session the transport service will use to send data to the - * peer - * - * @param cls the plugin - * @param address the address - * @return the session or NULL of max connections exceeded - */ -static struct Session * -http_get_session (void *cls, - const struct GNUNET_HELLO_Address *address) -{ - struct Plugin *plugin = cls; - struct Session * s = NULL; - struct GNUNET_ATS_Information ats; - size_t addrlen; - - GNUNET_assert (plugin != NULL); - GNUNET_assert (address != NULL); - GNUNET_assert (address->address != NULL); - - ats.type = htonl (GNUNET_ATS_ARRAY_TERMINATOR); - ats.value = htonl (GNUNET_ATS_ARRAY_TERMINATOR); - - /* find existing session */ - s = lookup_session (plugin, address); - if (s != NULL) - return s; - - if (plugin->max_connections <= plugin->cur_connections) - { - GNUNET_log_from (GNUNET_ERROR_TYPE_WARNING, plugin->name, - "Maximum number of connections reached, " - "cannot connect to peer `%s'\n", GNUNET_i2s (&address->peer)); - return NULL; - } - - /* create new session */ - addrlen = address->address_length; - - GNUNET_assert ((addrlen == sizeof (struct IPv6HttpAddress)) || - (addrlen == sizeof (struct IPv4HttpAddress))); - - s = create_session (plugin, &address->peer, address->address, address->address_length); - - /* Get ATS type */ - if (addrlen == sizeof (struct IPv4HttpAddress)) - { - struct IPv4HttpAddress *a4 = (struct IPv4HttpAddress *) address->address; - struct sockaddr_in s4; - - s4.sin_family = AF_INET; - s4.sin_addr.s_addr = a4->ipv4_addr; - s4.sin_port = a4->u4_port; -#if HAVE_SOCKADDR_IN_SIN_LEN - s4.sin_len = sizeof (struct sockaddr_in); -#endif - ats = plugin->env->get_address_type (plugin->env->cls, (const struct sockaddr *) &s4, sizeof (struct sockaddr_in)); - } - if (addrlen == sizeof (struct IPv6HttpAddress)) - { - struct IPv6HttpAddress *a6 = (struct IPv6HttpAddress *) address->address; - struct sockaddr_in6 s6; - - s6.sin6_family = AF_INET6; - s6.sin6_addr = a6->ipv6_addr; - s6.sin6_port = a6->u6_port; -#if HAVE_SOCKADDR_IN_SIN_LEN - s6.sin6_len = sizeof (struct sockaddr_in6); -#endif - ats = plugin->env->get_address_type (plugin->env->cls, (const struct sockaddr *) &s6, sizeof (struct sockaddr_in6)); - } - s->ats_address_network_type = ats.value; - - /* add new session */ - GNUNET_CONTAINER_DLL_insert (plugin->head, plugin->tail, s); - /* initiate new connection */ - if (GNUNET_SYSERR == client_connect (s)) - { - GNUNET_log_from (GNUNET_ERROR_TYPE_ERROR, plugin->name, - "Cannot connect to peer `%s' address `%s''\n", - http_plugin_address_to_string(NULL, s->addr, s->addrlen), - GNUNET_i2s (&s->target)); - GNUNET_CONTAINER_DLL_remove (plugin->head, plugin->tail, s); - delete_session (s); - return NULL; - } - - return s; -} - - -/** - * Function that can be used by the transport service to transmit - * a message using the plugin. Note that in the case of a - * peer disconnecting, the continuation MUST be called - * prior to the disconnect notification itself. This function - * will be called with this peer's HELLO message to initiate - * a fresh connection to another peer. - * - * @param cls closure - * @param session which session must be used - * @param msgbuf the message to transmit - * @param msgbuf_size number of bytes in 'msgbuf' - * @param priority how important is the message (most plugins will - * ignore message priority and just FIFO) - * @param to how long to wait at most for the transmission (does not - * require plugins to discard the message after the timeout, - * just advisory for the desired delay; most plugins will ignore - * this as well) - * @param cont continuation to call once the message has - * been transmitted (or if the transport is ready - * for the next transmission call; or if the - * peer disconnected...); can be NULL - * @param cont_cls closure for cont - * @return number of bytes used (on the physical network, with overheads); - * -1 on hard errors (i.e. address invalid); 0 is a legal value - * and does NOT mean that the message was not transmitted (DV) - */ -static ssize_t -http_plugin_send (void *cls, - struct Session *session, - const char *msgbuf, size_t msgbuf_size, - unsigned int priority, - struct GNUNET_TIME_Relative to, - GNUNET_TRANSPORT_TransmitContinuation cont, void *cont_cls) -{ - struct Plugin *plugin = cls; - struct HTTP_Message *msg; - struct Session *tmp; - size_t res = -1; - - GNUNET_assert (plugin != NULL); - GNUNET_assert (session != NULL); - - /* lookup if session is really existing */ - tmp = plugin->head; - while (tmp != NULL) - { - if ((tmp == session) && - (0 == memcmp (&session->target, &tmp->target, sizeof (struct GNUNET_PeerIdentity))) && - (session->addrlen == tmp->addrlen) && - (0 == memcmp (session->addr, tmp->addr, tmp->addrlen))) - break; - tmp = tmp->next; - } - if (tmp == NULL) - { - GNUNET_break_op (0); - return res; - } - - /* create new message and schedule */ - msg = GNUNET_malloc (sizeof (struct HTTP_Message) + msgbuf_size); - msg->next = NULL; - msg->size = msgbuf_size; - msg->pos = 0; - msg->buf = (char *) &msg[1]; - msg->transmit_cont = cont; - msg->transmit_cont_cls = cont_cls; - memcpy (msg->buf, msgbuf, msgbuf_size); - - reschedule_session_timeout (session); - - if (session->inbound == GNUNET_NO) - { - GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, - "Using outbound client session %p to send to `%s'\n", session, - GNUNET_i2s (&session->target)); - client_send (session, msg); - res = msgbuf_size; - } - if (session->inbound == GNUNET_YES) - { - GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, - "Using inbound server %p session to send to `%s'\n", session, - GNUNET_i2s (&session->target)); - server_send (session, msg); - res = msgbuf_size; - } - return res; - -} - - -/** - * Function that can be used to force the plugin to disconnect - * from the given peer and cancel all previous transmissions - * (and their continuationc). - * - * @param cls closure - * @param target peer from which to disconnect - */ -static void -http_plugin_disconnect (void *cls, const struct GNUNET_PeerIdentity *target) -{ - struct Plugin *plugin = cls; - struct Session *next = NULL; - struct Session *s = plugin->head; - - GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, - "Transport tells me to disconnect `%s'\n", - GNUNET_i2s (target)); - while (s != NULL) - { - next = s->next; - if (0 == memcmp (target, &s->target, sizeof (struct GNUNET_PeerIdentity))) - { - if (s->inbound == GNUNET_NO) - GNUNET_assert (GNUNET_OK == client_disconnect (s)); - else - GNUNET_assert (GNUNET_OK == server_disconnect (s)); - GNUNET_CONTAINER_DLL_remove (plugin->head, plugin->tail, s); - - struct HTTP_Message *msg = s->msg_head; - struct HTTP_Message *tmp = NULL; - - while (msg != NULL) - { - tmp = msg->next; - - GNUNET_CONTAINER_DLL_remove (s->msg_head, s->msg_tail, msg); - if (msg->transmit_cont != NULL) - { - msg->transmit_cont (msg->transmit_cont_cls, target, GNUNET_SYSERR); - } - GNUNET_free (msg); - msg = tmp; - } - - delete_session (s); - } - s = next; - } -} - - -static void * -find_address (struct Plugin *plugin, const struct sockaddr *addr, socklen_t addrlen) -{ - int af; - struct IPv4HttpAddressWrapper *w_t4 = NULL; - struct IPv6HttpAddressWrapper *w_t6 = NULL; - - af = addr->sa_family; - switch (af) - { - case AF_INET: - w_t4 = plugin->ipv4_addr_head; - struct sockaddr_in *a4 = (struct sockaddr_in *) addr; - - while (w_t4 != NULL) - { - int res = memcmp (&w_t4->addr.ipv4_addr, - &a4->sin_addr, - sizeof (struct in_addr)); - - if (res == 0) - { - if (a4->sin_port != w_t4->addr.u4_port) - res = -1; - } - - if (0 == res) - break; - w_t4 = w_t4->next; - } - return w_t4; - break; - case AF_INET6: - w_t6 = plugin->ipv6_addr_head; - struct sockaddr_in6 *a6 = (struct sockaddr_in6 *) addr; - - while (w_t6) - { - int res = memcmp (&w_t6->addr6.ipv6_addr, &a6->sin6_addr, - sizeof (struct in6_addr)); - - if (res == 0) - { - if (a6->sin6_port != w_t6->addr6.u6_port) - res = -1; - } - if (0 == res) - break; - w_t6 = w_t6->next; - } - return w_t6; - break; - default: - return NULL; - } - return NULL; -} - - -static void -nat_add_address (void *cls, int add_remove, const struct sockaddr *addr, - socklen_t addrlen) -{ - struct Plugin *plugin = cls; - struct IPv4HttpAddressWrapper *w_t4 = NULL; - struct IPv6HttpAddressWrapper *w_t6 = NULL; - int af; - - af = addr->sa_family; - switch (af) - { - case AF_INET: - w_t4 = find_address (plugin, addr, addrlen); - if (w_t4 == NULL) - { - struct sockaddr_in *a4 = (struct sockaddr_in *) addr; - w_t4 = GNUNET_malloc (sizeof (struct IPv4HttpAddressWrapper)); - memcpy (&w_t4->addr.ipv4_addr, &a4->sin_addr, sizeof (struct in_addr)); - w_t4->addr.u4_port = a4->sin_port; - - GNUNET_CONTAINER_DLL_insert (plugin->ipv4_addr_head, - plugin->ipv4_addr_tail, w_t4); - - GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, - "Notifying transport to add IPv4 address `%s'\n", - http_plugin_address_to_string (NULL, &w_t4->addr, - sizeof (struct - IPv4HttpAddress))); - plugin->env->notify_address (plugin->env->cls, add_remove, &w_t4->addr, - sizeof (struct IPv4HttpAddress)); - } - break; - case AF_INET6: - w_t6 = find_address (plugin, addr, addrlen); - if (w_t6 == NULL) - { - w_t6 = GNUNET_malloc (sizeof (struct IPv6HttpAddressWrapper)); - struct sockaddr_in6 *a6 = (struct sockaddr_in6 *) addr; - memcpy (&w_t6->addr6.ipv6_addr, &a6->sin6_addr, sizeof (struct in6_addr)); - w_t6->addr6.u6_port = a6->sin6_port; - - GNUNET_CONTAINER_DLL_insert (plugin->ipv6_addr_head, - plugin->ipv6_addr_tail, w_t6); - - GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, - "Notifying transport to add IPv6 address `%s'\n", - http_plugin_address_to_string (NULL, &w_t6->addr6, - sizeof (struct - IPv6HttpAddress))); - plugin->env->notify_address (plugin->env->cls, add_remove, &w_t6->addr6, - sizeof (struct IPv6HttpAddress)); - } - break; - default: - return; - } - -} - - -static void -nat_remove_address (void *cls, int add_remove, const struct sockaddr *addr, - socklen_t addrlen) -{ - struct Plugin *plugin = cls; - struct IPv4HttpAddressWrapper *w_t4 = NULL; - struct IPv6HttpAddressWrapper *w_t6 = NULL; - int af; - - af = addr->sa_family; - switch (af) - { - case AF_INET: - w_t4 = find_address (plugin, addr, addrlen); - if (w_t4 == NULL) - return; - - - GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, - "Notifying transport to remove IPv4 address `%s'\n", - http_plugin_address_to_string (NULL, &w_t4->addr, - sizeof (struct - IPv4HttpAddress))); - plugin->env->notify_address (plugin->env->cls, add_remove, &w_t4->addr, - sizeof (struct IPv4HttpAddress)); - - GNUNET_CONTAINER_DLL_remove (plugin->ipv4_addr_head, plugin->ipv4_addr_tail, - w_t4); - GNUNET_free (w_t4); - break; - case AF_INET6: - w_t6 = find_address (plugin, addr, addrlen); - if (w_t6 == NULL) - return; - - GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, - "Notifying transport to remove IPv6 address `%s'\n", - http_plugin_address_to_string (NULL, &w_t6->addr6, - sizeof (struct - IPv6HttpAddress))); - - plugin->env->notify_address (plugin->env->cls, add_remove, &w_t6->addr6, - sizeof (struct IPv6HttpAddress)); - - GNUNET_CONTAINER_DLL_remove (plugin->ipv6_addr_head, plugin->ipv6_addr_tail, - w_t6); - GNUNET_free (w_t6); - break; - default: - return; - } -} - - -/** - * Our external IP address/port mapping has changed. - * - * @param cls closure, the 'struct LocalAddrList' - * @param add_remove GNUNET_YES to mean the new public IP address, GNUNET_NO to mean - * the previous (now invalid) one - * @param addr either the previous or the new public IP address - * @param addrlen actual lenght of the address - */ -static void -nat_port_map_callback (void *cls, int add_remove, const struct sockaddr *addr, - socklen_t addrlen) -{ - GNUNET_assert (cls != NULL); - struct Plugin *plugin = cls; - - GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, - "NPMC called %s to address `%s'\n", - (add_remove == GNUNET_NO) ? "remove" : "add", - GNUNET_a2s (addr, addrlen)); - - switch (add_remove) - { - case GNUNET_YES: - nat_add_address (cls, add_remove, addr, addrlen); - break; - case GNUNET_NO: - nat_remove_address (cls, add_remove, addr, addrlen); - break; - } -} - - -void -http_check_ipv6 (struct Plugin *plugin) -{ - struct GNUNET_NETWORK_Handle *desc = NULL; - - if (plugin->ipv6 == GNUNET_YES) - { - /* probe IPv6 support */ - desc = GNUNET_NETWORK_socket_create (PF_INET6, SOCK_STREAM, 0); - if (NULL == desc) - { - if ((errno == ENOBUFS) || (errno == ENOMEM) || (errno == ENFILE) || - (errno == EACCES)) - { - GNUNET_log_strerror (GNUNET_ERROR_TYPE_ERROR, "socket"); - } - GNUNET_log_from (GNUNET_ERROR_TYPE_WARNING, plugin->name, - _ - ("Disabling IPv6 since it is not supported on this system!\n")); - plugin->ipv6 = GNUNET_NO; - } - else - { - GNUNET_break (GNUNET_OK == GNUNET_NETWORK_socket_close (desc)); - desc = NULL; - } - - GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, - "Testing IPv6 on this system: %s\n", - (plugin->ipv6 == GNUNET_YES) ? "successful" : "failed"); - } -} - - -int -http_get_addresses (struct Plugin *plugin, const char *serviceName, - const struct GNUNET_CONFIGURATION_Handle *cfg, - struct sockaddr ***addrs, socklen_t ** addr_lens) -{ - int disablev6; - unsigned long long port; - struct addrinfo hints; - struct addrinfo *res; - struct addrinfo *pos; - struct addrinfo *next; - unsigned int i; - int resi; - int ret; - struct sockaddr **saddrs; - socklen_t *saddrlens; - char *hostname; - - *addrs = NULL; - *addr_lens = NULL; - - disablev6 = !plugin->ipv6; - - port = 0; - if (GNUNET_CONFIGURATION_have_value (cfg, serviceName, "PORT")) - { - GNUNET_break (GNUNET_OK == - GNUNET_CONFIGURATION_get_value_number (cfg, serviceName, - "PORT", &port)); - if (port > 65535) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - _ - ("Require valid port number for service in configuration!\n")); - return GNUNET_SYSERR; - } - } - - if (GNUNET_CONFIGURATION_have_value (cfg, serviceName, "BINDTO")) - { - GNUNET_break (GNUNET_OK == - GNUNET_CONFIGURATION_get_value_string (cfg, serviceName, - "BINDTO", &hostname)); - } - else - hostname = NULL; - - if (hostname != NULL) - { - GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, - "Resolving `%s' since that is where `%s' will bind to.\n", - hostname, serviceName); - memset (&hints, 0, sizeof (struct addrinfo)); - if (disablev6) - hints.ai_family = AF_INET; - if ((0 != (ret = getaddrinfo (hostname, NULL, &hints, &res))) || - (res == NULL)) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("Failed to resolve `%s': %s\n"), - hostname, gai_strerror (ret)); - GNUNET_free (hostname); - return GNUNET_SYSERR; - } - next = res; - i = 0; - while (NULL != (pos = next)) - { - next = pos->ai_next; - if ((disablev6) && (pos->ai_family == AF_INET6)) - continue; - i++; - } - if (0 == i) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - _("Failed to find %saddress for `%s'.\n"), - disablev6 ? "IPv4 " : "", hostname); - freeaddrinfo (res); - GNUNET_free (hostname); - return GNUNET_SYSERR; - } - resi = i; - saddrs = GNUNET_malloc ((resi + 1) * sizeof (struct sockaddr *)); - saddrlens = GNUNET_malloc ((resi + 1) * sizeof (socklen_t)); - i = 0; - next = res; - while (NULL != (pos = next)) - { - next = pos->ai_next; - if ((disablev6) && (pos->ai_family == AF_INET6)) - continue; - if ((pos->ai_protocol != IPPROTO_TCP) && (pos->ai_protocol != 0)) - continue; /* not TCP */ - if ((pos->ai_socktype != SOCK_STREAM) && (pos->ai_socktype != 0)) - continue; /* huh? */ - GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, - "Service will bind to `%s'\n", GNUNET_a2s (pos->ai_addr, - pos->ai_addrlen)); - if (pos->ai_family == AF_INET) - { - GNUNET_assert (pos->ai_addrlen == sizeof (struct sockaddr_in)); - saddrlens[i] = pos->ai_addrlen; - saddrs[i] = GNUNET_malloc (saddrlens[i]); - memcpy (saddrs[i], pos->ai_addr, saddrlens[i]); - ((struct sockaddr_in *) saddrs[i])->sin_port = htons (port); - } - else - { - GNUNET_assert (pos->ai_family == AF_INET6); - GNUNET_assert (pos->ai_addrlen == sizeof (struct sockaddr_in6)); - saddrlens[i] = pos->ai_addrlen; - saddrs[i] = GNUNET_malloc (saddrlens[i]); - memcpy (saddrs[i], pos->ai_addr, saddrlens[i]); - ((struct sockaddr_in6 *) saddrs[i])->sin6_port = htons (port); - } - i++; - } - GNUNET_free (hostname); - freeaddrinfo (res); - resi = i; - } - else - { - /* will bind against everything, just set port */ - if (disablev6) - { - /* V4-only */ - resi = 1; - i = 0; - saddrs = GNUNET_malloc ((resi + 1) * sizeof (struct sockaddr *)); - saddrlens = GNUNET_malloc ((resi + 1) * sizeof (socklen_t)); - - saddrlens[i] = sizeof (struct sockaddr_in); - saddrs[i] = GNUNET_malloc (saddrlens[i]); -#if HAVE_SOCKADDR_IN_SIN_LEN - ((struct sockaddr_in *) saddrs[i])->sin_len = saddrlens[i]; -#endif - ((struct sockaddr_in *) saddrs[i])->sin_family = AF_INET; - ((struct sockaddr_in *) saddrs[i])->sin_port = htons (port); - } - else - { - /* dual stack */ - resi = 2; - saddrs = GNUNET_malloc ((resi + 1) * sizeof (struct sockaddr *)); - saddrlens = GNUNET_malloc ((resi + 1) * sizeof (socklen_t)); - i = 0; - saddrlens[i] = sizeof (struct sockaddr_in6); - saddrs[i] = GNUNET_malloc (saddrlens[i]); -#if HAVE_SOCKADDR_IN_SIN_LEN - ((struct sockaddr_in6 *) saddrs[i])->sin6_len = saddrlens[0]; -#endif - ((struct sockaddr_in6 *) saddrs[i])->sin6_family = AF_INET6; - ((struct sockaddr_in6 *) saddrs[i])->sin6_port = htons (port); - i++; - saddrlens[i] = sizeof (struct sockaddr_in); - saddrs[i] = GNUNET_malloc (saddrlens[i]); -#if HAVE_SOCKADDR_IN_SIN_LEN - ((struct sockaddr_in *) saddrs[i])->sin_len = saddrlens[1]; -#endif - ((struct sockaddr_in *) saddrs[i])->sin_family = AF_INET; - ((struct sockaddr_in *) saddrs[i])->sin_port = htons (port); - } - } - *addrs = saddrs; - *addr_lens = saddrlens; - return resi; -} - -static void -start_report_addresses (struct Plugin *plugin) -{ - int res = GNUNET_OK; - struct sockaddr **addrs; - socklen_t *addrlens; - - res = - http_get_addresses (plugin, plugin->name, plugin->env->cfg, &addrs, - &addrlens); - GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, - _("Found %u addresses to report to NAT service\n"), res); - - if (res != GNUNET_SYSERR) - { - plugin->nat = - GNUNET_NAT_register (plugin->env->cfg, GNUNET_YES, plugin->port, - (unsigned int) res, - (const struct sockaddr **) addrs, addrlens, - &nat_port_map_callback, NULL, plugin); - while (res > 0) - { - res--; -#if 0 - GNUNET_log_from (GNUNET_ERROR_TYPE_ERROR, plugin->name, _("FREEING %s\n"), - GNUNET_a2s (addrs[res], addrlens[res])); -#endif - GNUNET_assert (addrs[res] != NULL); - GNUNET_free (addrs[res]); - } - GNUNET_free_non_null (addrs); - GNUNET_free_non_null (addrlens); - } - else - { - plugin->nat = - GNUNET_NAT_register (plugin->env->cfg, GNUNET_YES, 0, 0, NULL, NULL, - NULL, NULL, plugin); - } -} - - -static void -stop_report_addresses (struct Plugin *plugin) -{ - /* Stop NAT handle */ - GNUNET_NAT_unregister (plugin->nat); - - /* Clean up addresses */ - struct IPv4HttpAddressWrapper *w_t4; - struct IPv6HttpAddressWrapper *w_t6; - - while (plugin->ipv4_addr_head != NULL) - { - w_t4 = plugin->ipv4_addr_head; - GNUNET_CONTAINER_DLL_remove (plugin->ipv4_addr_head, plugin->ipv4_addr_tail, - w_t4); - GNUNET_free (w_t4); - } - - while (plugin->ipv6_addr_head != NULL) - { - w_t6 = plugin->ipv6_addr_head; - GNUNET_CONTAINER_DLL_remove (plugin->ipv6_addr_head, plugin->ipv6_addr_tail, - w_t6); - GNUNET_free (w_t6); - } -} - - -static int -configure_plugin (struct Plugin *plugin) -{ - int res = GNUNET_OK; - - /* Use IPv4? */ - if (GNUNET_CONFIGURATION_have_value - (plugin->env->cfg, plugin->name, "USE_IPv4")) - { - plugin->ipv4 = - GNUNET_CONFIGURATION_get_value_yesno (plugin->env->cfg, plugin->name, - "USE_IPv4"); - } - else - plugin->ipv4 = GNUNET_YES; - - /* Use IPv6? */ - if (GNUNET_CONFIGURATION_have_value - (plugin->env->cfg, plugin->name, "USE_IPv6")) - { - plugin->ipv6 = - GNUNET_CONFIGURATION_get_value_yesno (plugin->env->cfg, plugin->name, - "USE_IPv6"); - } - else - plugin->ipv6 = GNUNET_YES; - - if ((plugin->ipv4 == GNUNET_NO) && (plugin->ipv6 == GNUNET_NO)) - { - GNUNET_log_from (GNUNET_ERROR_TYPE_ERROR, plugin->name, - _ - ("Neither IPv4 nor IPv6 are enabled! Fix in configuration\n"), - plugin->name); - res = GNUNET_SYSERR; - } - - /* Reading port number from config file */ - unsigned long long port; - - if ((GNUNET_OK != - GNUNET_CONFIGURATION_get_value_number (plugin->env->cfg, plugin->name, - "PORT", &port)) || (port > 65535)) - { - GNUNET_log_from (GNUNET_ERROR_TYPE_ERROR, plugin->name, - _("Port is required! Fix in configuration\n"), - plugin->name); - res = GNUNET_SYSERR; - goto fail; - } - plugin->port = port; - - plugin->client_only = GNUNET_NO; - if (plugin->port == 0) - { - GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, - _("Port 0, client only mode\n")); - plugin->client_only = GNUNET_YES; - } - - char *bind4_address = NULL; - - if ((plugin->ipv4 == GNUNET_YES) && - (GNUNET_YES == - GNUNET_CONFIGURATION_get_value_string (plugin->env->cfg, plugin->name, - "BINDTO", &bind4_address))) - { - GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, - "Binding %s plugin to specific IPv4 address: `%s'\n", - plugin->protocol, bind4_address); - plugin->server_addr_v4 = GNUNET_malloc (sizeof (struct sockaddr_in)); - if (1 != - inet_pton (AF_INET, bind4_address, &plugin->server_addr_v4->sin_addr)) - { - GNUNET_log_from (GNUNET_ERROR_TYPE_ERROR, plugin->name, - _ - ("Specific IPv4 address `%s' for plugin %s in configuration file is invalid! Binding to all addresses!\n"), - bind4_address, plugin->protocol); - GNUNET_free (plugin->server_addr_v4); - plugin->server_addr_v4 = NULL; - } - else - { - plugin->server_addr_v4->sin_family = AF_INET; - plugin->server_addr_v4->sin_port = htons (plugin->port); - } - GNUNET_free (bind4_address); - } - - - char *bind6_address = NULL; - - if ((plugin->ipv6 == GNUNET_YES) && - (GNUNET_YES == - GNUNET_CONFIGURATION_get_value_string (plugin->env->cfg, plugin->name, - "BINDTO6", &bind6_address))) - { - GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, - "Binding %s plugin to specific IPv6 address: `%s'\n", - plugin->protocol, bind6_address); - plugin->server_addr_v6 = GNUNET_malloc (sizeof (struct sockaddr_in6)); - if (1 != - inet_pton (AF_INET6, bind6_address, &plugin->server_addr_v6->sin6_addr)) - { - GNUNET_log_from (GNUNET_ERROR_TYPE_ERROR, plugin->name, - _ - ("Specific IPv6 address `%s' for plugin %s in configuration file is invalid! Binding to all addresses!\n"), - bind6_address, plugin->protocol); - GNUNET_free (plugin->server_addr_v6); - plugin->server_addr_v6 = NULL; - } - else - { - plugin->server_addr_v6->sin6_family = AF_INET6; - plugin->server_addr_v6->sin6_port = htons (plugin->port); - } - GNUNET_free (bind6_address); - } - - - /* Optional parameters */ - unsigned long long maxneigh; - - if (GNUNET_OK != - GNUNET_CONFIGURATION_get_value_number (plugin->env->cfg, plugin->name, - "MAX_CONNECTIONS", &maxneigh)) - maxneigh = 128; - plugin->max_connections = maxneigh; - -fail: - return res; -} - - -/** - * Session was idle, so disconnect it - */ -static void -session_timeout (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - GNUNET_assert (NULL != cls); - struct Session *s = cls; - - s->timeout_task = GNUNET_SCHEDULER_NO_TASK; - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Session %p was idle for %llu, disconnecting\n", - s, GNUNET_CONSTANTS_IDLE_CONNECTION_TIMEOUT.rel_value); - - /* call session destroy function */ - if (s->inbound == GNUNET_NO) - GNUNET_assert (GNUNET_OK == client_disconnect (s)); - else - GNUNET_assert (GNUNET_OK == server_disconnect (s)); - -} - - -/** - * Start session timeout - */ -static void -start_session_timeout (struct Session *s) -{ - GNUNET_assert (NULL != s); - GNUNET_assert (GNUNET_SCHEDULER_NO_TASK == s->timeout_task); - - s->timeout_task = GNUNET_SCHEDULER_add_delayed (GNUNET_CONSTANTS_IDLE_CONNECTION_TIMEOUT, - &session_timeout, - s); - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Timeout for session %p set to %llu\n", - s, GNUNET_CONSTANTS_IDLE_CONNECTION_TIMEOUT.rel_value); -} - - -/** - * Increment session timeout due to activity - */ -static void -reschedule_session_timeout (struct Session *s) -{ - GNUNET_assert (NULL != s); - GNUNET_assert (GNUNET_SCHEDULER_NO_TASK != s->timeout_task); - - GNUNET_SCHEDULER_cancel (s->timeout_task); - s->timeout_task = GNUNET_SCHEDULER_add_delayed (GNUNET_CONSTANTS_IDLE_CONNECTION_TIMEOUT, - &session_timeout, - s); - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Timeout rescheduled for session %p set to %llu\n", - s, GNUNET_CONSTANTS_IDLE_CONNECTION_TIMEOUT.rel_value); -} - - -/** - * Cancel timeout - */ -static void -stop_session_timeout (struct Session *s) -{ - GNUNET_assert (NULL != s); - - if (GNUNET_SCHEDULER_NO_TASK != s->timeout_task) - { - GNUNET_SCHEDULER_cancel (s->timeout_task); - s->timeout_task = GNUNET_SCHEDULER_NO_TASK; - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Timeout rescheduled for session %p canceled\n", - s, GNUNET_CONSTANTS_IDLE_CONNECTION_TIMEOUT.rel_value); - } - else - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Timeout for session %p was not active\n", - s); - } -} - - -/** - * Entry point for the plugin. - */ -void * -LIBGNUNET_PLUGIN_TRANSPORT_INIT (void *cls) -{ - struct GNUNET_TRANSPORT_PluginEnvironment *env = cls; - struct GNUNET_TRANSPORT_PluginFunctions *api; - struct Plugin *plugin; - int res; - - if (NULL == env->receive) - { - /* run in 'stub' mode (i.e. as part of gnunet-peerinfo), don't fully - initialze the plugin or the API */ - api = GNUNET_malloc (sizeof (struct GNUNET_TRANSPORT_PluginFunctions)); - api->cls = NULL; - api->address_pretty_printer = &http_plugin_address_pretty_printer; - api->address_to_string = &http_plugin_address_to_string; - api->string_to_address = &http_string_to_address; - return api; - } - - plugin = GNUNET_malloc (sizeof (struct Plugin)); - plugin->env = env; - plugin->outbound_sessions = 0; - plugin->inbound_sessions = 0; - api = GNUNET_malloc (sizeof (struct GNUNET_TRANSPORT_PluginFunctions)); - api->cls = plugin; - api->disconnect = &http_plugin_disconnect; - api->address_pretty_printer = &http_plugin_address_pretty_printer; - api->check_address = &http_plugin_address_suggested; - api->address_to_string = &http_plugin_address_to_string; - api->string_to_address = &http_string_to_address; - api->get_session = &http_get_session; - api->send = &http_plugin_send; - -#if BUILD_HTTPS - plugin->name = "transport-https"; - plugin->protocol = "https"; -#else - plugin->name = "transport-http"; - plugin->protocol = "http"; -#endif - /* Configure plugin from configuration */ - res = configure_plugin (plugin); - if (res == GNUNET_SYSERR) - { - GNUNET_free_non_null (plugin->server_addr_v4); - GNUNET_free_non_null (plugin->server_addr_v6); - GNUNET_free (plugin); - GNUNET_free (api); - return NULL; - } - - /* checking IPv6 support */ - http_check_ipv6 (plugin); - - /* Start client */ - res = client_start (plugin); - if (res == GNUNET_SYSERR) - { - GNUNET_free_non_null (plugin->server_addr_v4); - GNUNET_free_non_null (plugin->server_addr_v6); - GNUNET_free (plugin); - GNUNET_free (api); - return NULL; - } - - /* Start server */ - if (plugin->client_only == GNUNET_NO) - { - res = server_start (plugin); - if (res == GNUNET_SYSERR) - { - server_stop (plugin); - client_stop (plugin); - - GNUNET_free_non_null (plugin->server_addr_v4); - GNUNET_free_non_null (plugin->server_addr_v6); - GNUNET_free (plugin); - GNUNET_free (api); - return NULL; - } - } - /* Report addresses to transport service */ - start_report_addresses (plugin); - - GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, - "Plugin `%s' loaded\n", plugin->name); - return api; -} - - -/** - * Exit point from the plugin. - */ -void * -LIBGNUNET_PLUGIN_TRANSPORT_DONE (void *cls) -{ - struct GNUNET_TRANSPORT_PluginFunctions *api = cls; - struct Plugin *plugin = api->cls; - struct Session *s; - - if (NULL == plugin) - { - GNUNET_free (api); - return NULL; - } - - /* Stop reporting addresses to transport service */ - stop_report_addresses (plugin); - - /* cleaning up sessions */ - s = plugin->head; - while (s != NULL) - { - GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, - "Disconnecting `%s' \n", GNUNET_i2s (&s->target)); - if (s->inbound == GNUNET_NO) - GNUNET_assert (GNUNET_OK == client_disconnect (s)); - else - GNUNET_assert (GNUNET_OK == server_disconnect (s)); - s = s->next; - } - - GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, "Stopping server\n"); - /* Stop server */ - server_stop (plugin); - - GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, "Stopping client\n"); - /* Stop client */ - client_stop (plugin); - - /* deleting up sessions */ - s = plugin->head; - while (s != NULL) - { - struct Session *t = s->next; - - GNUNET_CONTAINER_DLL_remove (plugin->head, plugin->tail, s); - - struct HTTP_Message *msg = s->msg_head; - struct HTTP_Message *tmp = NULL; - - while (msg != NULL) - { - tmp = msg->next; - - GNUNET_CONTAINER_DLL_remove (s->msg_head, s->msg_tail, msg); - if (msg->transmit_cont != NULL) - { - msg->transmit_cont (msg->transmit_cont_cls, &s->target, GNUNET_SYSERR); - } - GNUNET_free (msg); - msg = tmp; - } - - delete_session (s); - s = t; - } - - GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, - "Plugin `%s' unloaded\n", plugin->name); - GNUNET_free_non_null (plugin->server_addr_v4); - GNUNET_free_non_null (plugin->server_addr_v6); - GNUNET_free (plugin); - GNUNET_free (api); - return NULL; -} - -/* end of plugin_transport_http.c */ diff --git a/src/transport/plugin_transport_http.h b/src/transport/plugin_transport_http.h deleted file mode 100644 index 986d7d7..0000000 --- a/src/transport/plugin_transport_http.h +++ /dev/null @@ -1,553 +0,0 @@ -/* - This file is part of GNUnet - (C) 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009 Christian Grothoff (and other contributing authors) - - GNUnet is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published - by the Free Software Foundation; either version 3, or (at your - option) any later version. - - GNUnet is distributed in the hope that it will be useful, but - WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - General Public License for more details. - - You should have received a copy of the GNU General Public License - along with GNUnet; see the file COPYING. If not, write to the - Free Software Foundation, Inc., 59 Temple Place - Suite 330, - Boston, MA 02111-1307, USA. -*/ - -/** - * @file transport/plugin_transport_http.h - * @brief http transport service plugin - * @author Matthias Wachs - */ - -#include "platform.h" -#include "gnunet_common.h" -#include "gnunet_constants.h" -#include "gnunet_protocols.h" -#include "gnunet_connection_lib.h" -#include "gnunet_service_lib.h" -#include "gnunet_statistics_service.h" -#include "gnunet_transport_service.h" -#include "gnunet_resolver_service.h" -#include "gnunet_server_lib.h" -#include "gnunet_container_lib.h" -#include "gnunet_transport_plugin.h" -#include "gnunet_os_lib.h" -#include "gnunet_nat_lib.h" -#include "microhttpd.h" -#include - - -#define DEBUG_HTTP GNUNET_EXTRA_LOGGING -#define VERBOSE_SERVER GNUNET_EXTRA_LOGGING -#define VERBOSE_CLIENT GNUNET_EXTRA_LOGGING -#define VERBOSE_CURL GNUNET_NO - -#if BUILD_HTTPS -#define LIBGNUNET_PLUGIN_TRANSPORT_INIT libgnunet_plugin_transport_https_init -#define LIBGNUNET_PLUGIN_TRANSPORT_DONE libgnunet_plugin_transport_https_done -#else -#define LIBGNUNET_PLUGIN_TRANSPORT_INIT libgnunet_plugin_transport_http_init -#define LIBGNUNET_PLUGIN_TRANSPORT_DONE libgnunet_plugin_transport_http_done -#endif - -#define INBOUND GNUNET_YES -#define OUTBOUND GNUNET_NO - - -#define HTTP_NOT_VALIDATED_TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 15) - -/** - * Encapsulation of all of the state of the plugin. - */ -struct Plugin -{ - /** - * General handles - * --------------- - */ - - /** - * Our environment. - */ - struct GNUNET_TRANSPORT_PluginEnvironment *env; - - /** - * Linked list of open sessions. - */ - - struct Session *head; - - struct Session *tail; - - /** - * NAT handle & address management - */ - struct GNUNET_NAT_Handle *nat; - - /** - * List of own addresses - */ - - /** - * IPv4 addresses DLL head - */ - struct IPv4HttpAddressWrapper *ipv4_addr_head; - - /** - * IPv4 addresses DLL tail - */ - struct IPv4HttpAddressWrapper *ipv4_addr_tail; - - /** - * IPv6 addresses DLL head - */ - struct IPv6HttpAddressWrapper *ipv6_addr_head; - - /** - * IPv6 addresses DLL tail - */ - struct IPv6HttpAddressWrapper *ipv6_addr_tail; - - /** - * Plugin configuration - * -------------------- - */ - - /** - * Plugin name - * Equals configuration section: transport-http, transport-https - */ - char *name; - - /** - * Plugin protocol - * http, https - */ - char *protocol; - - /** - * Use IPv4? - * GNUNET_YES or GNUNET_NO - */ - int ipv4; - - /** - * Use IPv6? - * GNUNET_YES or GNUNET_NO - */ - int ipv6; - - /** - * Does plugin just use outbound connections and not accept inbound? - */ - - int client_only; - - /** - * Port used - */ - uint16_t port; - - /** - * Maximum number of sockets the plugin can use - * Each http inbound /outbound connections are two connections - */ - int max_connections; - - /** - * Number of outbound sessions - */ - unsigned int outbound_sessions; - - /** - * Number of inbound sessions - */ - unsigned int inbound_sessions; - - /** - * Plugin HTTPS SSL/TLS options - * ---------------------------- - */ - - /** - * libCurl TLS crypto init string, can be set to enhance performance - * - * Example: - * - * Use RC4-128 instead of AES: - * NONE:+VERS-TLS1.0:+ARCFOUR-128:+SHA1:+RSA:+COMP-NULL - * - */ - char *crypto_init; - - /** - * TLS key - */ - char *key; - - /** - * TLS certificate - */ - char *cert; - - /** - * Plugin values - * ------------- - */ - - /** - * Current number of establishes connections - */ - int cur_connections; - - /** - * Last used unique HTTP connection tag - */ - uint32_t last_tag; - - /** - * Server handles - * -------------- - */ - - /** - * MHD IPv4 daemon - */ - struct MHD_Daemon *server_v4; - - /** - * MHD IPv4 task - */ - GNUNET_SCHEDULER_TaskIdentifier server_v4_task; - - /** - * The IPv4 server is scheduled to run asap - */ - int server_v4_immediately; - - /** - * MHD IPv6 daemon - */ - struct MHD_Daemon *server_v6; - - /** - * MHD IPv4 task - */ - GNUNET_SCHEDULER_TaskIdentifier server_v6_task; - - /** - * The IPv6 server is scheduled to run asap - */ - - int server_v6_immediately; - - /** - * IPv4 server socket to bind to - */ - struct sockaddr_in *server_addr_v4; - - /** - * IPv6 server socket to bind to - */ - struct sockaddr_in6 *server_addr_v6; - - /** - * Server semi connections - * A full session consists of 2 semi-connections: send and receive - * If not both directions are established the server keeps this sessions here - */ - struct Session *server_semi_head; - - struct Session *server_semi_tail; - - /* - * Client handles - */ - - /** - * cURL Multihandle - */ - CURLM *client_mh; - - /** - * curl perform task - */ - GNUNET_SCHEDULER_TaskIdentifier client_perform_task; - -}; - -GNUNET_NETWORK_STRUCT_BEGIN - -/** - * IPv4 addresses - */ -struct IPv4HttpAddress -{ - /** - * IPv4 address, in network byte order. - */ - uint32_t ipv4_addr GNUNET_PACKED; - - /** - * Port number, in network byte order. - */ - uint16_t u4_port GNUNET_PACKED; -}; - -/** - * IPv4 addresses - */ -struct IPv6HttpAddress -{ - /** - * IPv6 address. - */ - struct in6_addr ipv6_addr GNUNET_PACKED; - - /** - * Port number, in network byte order. - */ - uint16_t u6_port GNUNET_PACKED; -}; -GNUNET_NETWORK_STRUCT_END - - -struct ServerConnection -{ - /* _RECV or _SEND */ - int direction; - - /* Should this connection get disconnected? GNUNET_YES/NO */ - int disconnect; - - /* The session this server connection belongs to */ - struct Session *session; - - /* The MHD connection */ - struct MHD_Connection *mhd_conn; -}; - - - -/** - * Session handle for connections. - */ -struct Session -{ - - /** - * Stored in a linked list. - */ - struct Session *next; - - /** - * Stored in a linked list. - */ - struct Session *prev; - - /** - * Pointer to the global plugin struct. - */ - struct Plugin *plugin; - - /** - * Address - */ - void *addr; - - /** - * Address length - */ - size_t addrlen; - - /** - * ATS network type in NBO - */ - uint32_t ats_address_network_type; - - /** - * To whom are we talking to - */ - struct GNUNET_PeerIdentity target; - - /** - * next pointer for double linked list - */ - struct HTTP_Message *msg_head; - - /** - * previous pointer for double linked list - */ - struct HTTP_Message *msg_tail; - - - /** - * Message stream tokenizer for incoming data - */ - struct GNUNET_SERVER_MessageStreamTokenizer *msg_tk; - - /** - * Absolute time when to receive data again - * Used for receive throttling - */ - struct GNUNET_TIME_Absolute next_receive; - - /** - * Inbound or outbound connection - * Outbound: GNUNET_NO (client is used to send and receive) - * Inbound : GNUNET_YES (server is used to send and receive) - */ - int inbound; - - /** - * Unique HTTP/S connection tag for this connection - */ - uint32_t tag; - - /** - * Client handles - */ - - /** - * Client send handle - */ - void *client_put; - - /** - * Client receive handle - */ - void *client_get; - - /** - * Task to wake up client receive handle when receiving is allowed again - */ - GNUNET_SCHEDULER_TaskIdentifier recv_wakeup_task; - - /** - * Session timeout task - */ - GNUNET_SCHEDULER_TaskIdentifier timeout_task; - - /** - * Is client send handle paused since there are no data to send? - * GNUNET_YES/NO - */ - int client_put_paused; - - /** - * Server handles - */ - - /** - * Client send handle - */ - struct ServerConnection *server_recv; - - /** - * Client send handle - */ - struct ServerConnection *server_send; -}; - -/** - * Message to send using http - */ -struct HTTP_Message -{ - /** - * next pointer for double linked list - */ - struct HTTP_Message *next; - - /** - * previous pointer for double linked list - */ - struct HTTP_Message *prev; - - /** - * buffer containing data to send - */ - char *buf; - - /** - * amount of data already sent - */ - size_t pos; - - /** - * buffer length - */ - size_t size; - - /** - * Continuation function to call once the transmission buffer - * has again space available. NULL if there is no - * continuation to call. - */ - GNUNET_TRANSPORT_TransmitContinuation transmit_cont; - - /** - * Closure for transmit_cont. - */ - void *transmit_cont_cls; -}; - -struct Session * -create_session (struct Plugin *plugin, const struct GNUNET_PeerIdentity *target, - const void *addr, size_t addrlen); - -int -exist_session (struct Plugin *plugin, struct Session *s); - -void -delete_session (struct Session *s); - -int -exist_session (struct Plugin *plugin, struct Session *s); - -struct GNUNET_TIME_Relative -http_plugin_receive (void *cls, const struct GNUNET_PeerIdentity *peer, - const struct GNUNET_MessageHeader *message, - struct Session *session, const char *sender_address, - uint16_t sender_address_len); - -const char * -http_plugin_address_to_string (void *cls, const void *addr, size_t addrlen); - -int -client_disconnect (struct Session *s); - -int -client_connect (struct Session *s); - -int -client_send (struct Session *s, struct HTTP_Message *msg); - -int -client_start (struct Plugin *plugin); - -void -client_stop (struct Plugin *plugin); - -int -server_disconnect (struct Session *s); - -int -server_send (struct Session *s, struct HTTP_Message *msg); - -int -server_start (struct Plugin *plugin); - -void -server_stop (struct Plugin *plugin); - -void -notify_session_end (void *cls, const struct GNUNET_PeerIdentity *peer, - struct Session *s); - -/* end of plugin_transport_http.h */ diff --git a/src/transport/plugin_transport_http_client.c b/src/transport/plugin_transport_http_client.c index f55311f..e7bf704 100644 --- a/src/transport/plugin_transport_http_client.c +++ b/src/transport/plugin_transport_http_client.c @@ -1,6 +1,6 @@ /* This file is part of GNUnet - (C) 2002--2012 Christian Grothoff (and other contributing authors) + (C) 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009 Christian Grothoff (and other contributing authors) GNUnet is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published @@ -20,31 +20,418 @@ /** * @file transport/plugin_transport_http_client.c - * @brief http transport service plugin + * @brief HTTP/S client transport plugin * @author Matthias Wachs */ -#include "plugin_transport_http.h" +#if BUILD_HTTPS +#define LIBGNUNET_PLUGIN_TRANSPORT_INIT libgnunet_plugin_transport_https_client_init +#define LIBGNUNET_PLUGIN_TRANSPORT_DONE libgnunet_plugin_transport_https_client_done +#else +#define LIBGNUNET_PLUGIN_TRANSPORT_INIT libgnunet_plugin_transport_http_client_init +#define LIBGNUNET_PLUGIN_TRANSPORT_DONE libgnunet_plugin_transport_http_client_done +#endif + +#define VERBOSE_CURL GNUNET_YES + +#define PUT_DISCONNECT_TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 1) + +#define ENABLE_PUT GNUNET_YES +#define ENABLE_GET GNUNET_YES + +#include "platform.h" +#include "gnunet_protocols.h" +#include "gnunet_common.h" +#include "gnunet_server_lib.h" +#include "gnunet_transport_plugin.h" +#include "plugin_transport_http_common.h" +#include + + + +/** + * Encapsulation of all of the state of the plugin. + */ +struct HTTP_Client_Plugin; + + +/** + * Message to send using http + */ +struct HTTP_Message +{ + /** + * next pointer for double linked list + */ + struct HTTP_Message *next; + + /** + * previous pointer for double linked list + */ + struct HTTP_Message *prev; + + /** + * buffer containing data to send + */ + char *buf; + + /** + * amount of data already sent + */ + size_t pos; + + /** + * buffer length + */ + size_t size; + + /** + * Continuation function to call once the transmission buffer + * has again space available. NULL if there is no + * continuation to call. + */ + GNUNET_TRANSPORT_TransmitContinuation transmit_cont; + + /** + * Closure for transmit_cont. + */ + void *transmit_cont_cls; +}; + + +/** + * Session handle for connections. + */ +struct Session; + +/** + * A connection handle + * + */ +struct ConnectionHandle +{ + /** + * The curl easy handle + */ + CURL *easyhandle; + + /** + * The related session + */ + struct Session *s; +}; + + + +/** + * Session handle for connections. + */ +struct Session +{ + /** + * To whom are we talking to (set to our identity + * if we are still waiting for the welcome message) + */ + struct GNUNET_PeerIdentity target; + + /** + * Stored in a linked list. + */ + struct Session *next; + + /** + * Stored in a linked list. + */ + struct Session *prev; + + /** + * The URL to connect to + */ + char *url; + + /** + * Address + */ + void *addr; + + /** + * Address length + */ + size_t addrlen; + + /** + * ATS network type in NBO + */ + uint32_t ats_address_network_type; + + /** + * Pointer to the global plugin struct. + */ + struct HTTP_Client_Plugin *plugin; + + /** + * Client send handle + */ + void *client_put; + + struct ConnectionHandle put; + struct ConnectionHandle get; + + /** + * Is the client PUT handle currently paused + */ + int put_paused; + + /** + * Is the client PUT handle disconnect in progress? + */ + int put_tmp_disconnecting; + + /** + * Is the client PUT handle temporarily disconnected? + */ + int put_tmp_disconnected; + + /** + * We received data to send while disconnecting, reconnect immediately + */ + int put_reconnect_required; + + /** + * Client receive handle + */ + void *client_get; + + /** + * Outbound overhead due to HTTP connection + * Add to next message of this session when calling callback + */ + size_t overhead; + + /** + * next pointer for double linked list + */ + struct HTTP_Message *msg_head; + + /** + * previous pointer for double linked list + */ + struct HTTP_Message *msg_tail; + + /** + * Message stream tokenizer for incoming data + */ + struct GNUNET_SERVER_MessageStreamTokenizer *msg_tk; + + /** + * Session timeout task + */ + GNUNET_SCHEDULER_TaskIdentifier put_disconnect_task; + + /** + * Session timeout task + */ + GNUNET_SCHEDULER_TaskIdentifier timeout_task; + + /** + * Task to wake up client receive handle when receiving is allowed again + */ + GNUNET_SCHEDULER_TaskIdentifier recv_wakeup_task; + + /** + * Absolute time when to receive data again + * Used for receive throttling + */ + struct GNUNET_TIME_Absolute next_receive; +}; + + +/** + * Encapsulation of all of the state of the plugin. + */ +struct HTTP_Client_Plugin +{ + /** + * Our environment. + */ + struct GNUNET_TRANSPORT_PluginEnvironment *env; + + /** + * Linked list head of open sessions. + */ + struct Session *head; + + /** + * Linked list tail of open sessions. + */ + struct Session *tail; + + /** + * Plugin name + */ + char *name; + + /** + * Protocol + */ + char *protocol; + + /** + * Maximum number of sockets the plugin can use + * Each http inbound /outbound connections are two connections + */ + unsigned int max_connections; + + /** + * Current number of sockets the plugin can use + * Each http inbound /outbound connections are two connections + */ + unsigned int cur_connections; + + /** + * Last used unique HTTP connection tag + */ + uint32_t last_tag; + + /** + * use IPv6 + */ + uint16_t use_ipv6; + + /** + * use IPv4 + */ + uint16_t use_ipv4; + + /** + * cURL Multihandle + */ + CURLM *curl_multi_handle; + + /** + * curl perform task + */ + GNUNET_SCHEDULER_TaskIdentifier client_perform_task; +}; + + +/** + * Encapsulation of all of the state of the plugin. + */ +struct HTTP_Client_Plugin *p; + + +/** + * Start session timeout for a session + * @param s the session + */ +static void +client_start_session_timeout (struct Session *s); + + +/** + * Increment session timeout due to activity for a session + * @param s the session + */ +static void +client_reschedule_session_timeout (struct Session *s); + + +/** + * Cancel timeout for a session + * @param s the session + */ +static void +client_stop_session_timeout (struct Session *s); + + +/** + * Function setting up file descriptors and scheduling task to run + * + * @param plugin plugin as closure + * @param now schedule task in 1ms, regardless of what curl may say + * @return GNUNET_SYSERR for hard failure, GNUNET_OK for ok + */ +static int +client_schedule (struct HTTP_Client_Plugin *plugin, int now); + + +/** + * Connect a HTTP put connection + * + * @param s the session to connect + * @return GNUNET_SYSERR for hard failure, GNUNET_OK for success + */ +static int +client_connect_put (struct Session *s); + + +/** + * Does a session s exists? + * + * @param plugin the plugin + * @param s desired session + * @return GNUNET_YES or GNUNET_NO + */ +static int +client_exist_session (struct HTTP_Client_Plugin *plugin, struct Session *s) +{ + struct Session * head; + + GNUNET_assert (NULL != plugin); + GNUNET_assert (NULL != s); + + for (head = plugin->head; head != NULL; head = head->next) + { + if (head == s) + return GNUNET_YES; + } + return GNUNET_NO; +} -static struct Plugin * p; -#if VERBOSE_CURL /** - * Function to log curl debug messages with GNUNET_log - * @param curl handle - * @param type curl_infotype - * @param data data - * @param size size - * @param cls closure - * @return 0 + * Loggging function + * + * @param curl the curl easy handle + * @param type message type + * @param data data to log, NOT a 0-terminated string + * @param size data length + * @param cls the closure + * @return always 0 */ static int -client_log (CURL * curl, curl_infotype type, char *data, size_t size, void *cls) +client_log (CURL *curl, curl_infotype type, + const char *data, size_t size, void *cls) { - if (type == CURLINFO_TEXT) + struct ConnectionHandle *ch = cls; + const char *ttype = "UNSPECIFIED"; + + if ((type == CURLINFO_TEXT) || (type == CURLINFO_HEADER_IN) || (type == CURLINFO_HEADER_OUT)) { char text[size + 2]; + switch (type) { + case CURLINFO_TEXT: + ttype = "TEXT"; + break; + case CURLINFO_HEADER_IN: + ttype = "HEADER_IN"; + break; + case CURLINFO_HEADER_OUT: + ttype = "HEADER_OUT"; + /* Overhead*/ + + GNUNET_assert (NULL != ch); + GNUNET_assert (NULL != ch->easyhandle); + GNUNET_assert (NULL != ch->s); + ch->s->overhead += size; + break; + default: + ttype = "UNSPECIFIED"; + break; + } + memcpy (text, data, size); if (text[size - 1] == '\n') text[size] = '\0'; @@ -54,210 +441,192 @@ client_log (CURL * curl, curl_infotype type, char *data, size_t size, void *cls) text[size + 1] = '\0'; } #if BUILD_HTTPS - GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, "transport-https", - "Client: %p - %s", cls, text); + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, "transport-https_client", + "Connection %p %s: %s", ch->easyhandle, ttype, text); #else - GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, "transport-http", - "Client: %p - %s", cls, text); + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, "transport-http_client", + "Connection %p %s: %s", ch->easyhandle, ttype, text); #endif } return 0; } -#endif - -/** - * Task performing curl operations - * @param cls plugin as closure - * @param tc gnunet scheduler task context - */ -static void -client_run (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc); /** - * Function setting up file descriptors and scheduling task to run + * Function that can be used by the transport service to transmit + * a message using the plugin. Note that in the case of a + * peer disconnecting, the continuation MUST be called + * prior to the disconnect notification itself. This function + * will be called with this peer's HELLO message to initiate + * a fresh connection to another peer. * - * @param plugin plugin as closure - * @param now schedule task in 1ms, regardless of what curl may say - * @return GNUNET_SYSERR for hard failure, GNUNET_OK for ok + * @param cls closure + * @param s which session must be used + * @param msgbuf the message to transmit + * @param msgbuf_size number of bytes in 'msgbuf' + * @param priority how important is the message (most plugins will + * ignore message priority and just FIFO) + * @param to how long to wait at most for the transmission (does not + * require plugins to discard the message after the timeout, + * just advisory for the desired delay; most plugins will ignore + * this as well) + * @param cont continuation to call once the message has + * been transmitted (or if the transport is ready + * for the next transmission call; or if the + * peer disconnected...); can be NULL + * @param cont_cls closure for cont + * @return number of bytes used (on the physical network, with overheads); + * -1 on hard errors (i.e. address invalid); 0 is a legal value + * and does NOT mean that the message was not transmitted (DV) */ -static int -client_schedule (struct Plugin *plugin, int now) +static ssize_t +http_client_plugin_send (void *cls, + struct Session *s, + const char *msgbuf, size_t msgbuf_size, + unsigned int priority, + struct GNUNET_TIME_Relative to, + GNUNET_TRANSPORT_TransmitContinuation cont, + void *cont_cls) { - fd_set rs; - fd_set ws; - fd_set es; - int max; - struct GNUNET_NETWORK_FDSet *grs; - struct GNUNET_NETWORK_FDSet *gws; - long to; - CURLMcode mret; - struct GNUNET_TIME_Relative timeout; + struct HTTP_Client_Plugin *plugin = cls; + struct HTTP_Message *msg; + char *stat_txt; - /* Cancel previous scheduled task */ - if (plugin->client_perform_task != GNUNET_SCHEDULER_NO_TASK) - { - GNUNET_SCHEDULER_cancel (plugin->client_perform_task); - plugin->client_perform_task = GNUNET_SCHEDULER_NO_TASK; - } - max = -1; - FD_ZERO (&rs); - FD_ZERO (&ws); - FD_ZERO (&es); - mret = curl_multi_fdset (plugin->client_mh, &rs, &ws, &es, &max); - if (mret != CURLM_OK) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("%s failed at %s:%d: `%s'\n"), - "curl_multi_fdset", __FILE__, __LINE__, - curl_multi_strerror (mret)); - return GNUNET_SYSERR; - } - mret = curl_multi_timeout (plugin->client_mh, &to); - if (to == -1) - timeout = GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 1); - else - timeout = GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MILLISECONDS, to); - if (now == GNUNET_YES) - timeout = GNUNET_TIME_UNIT_MILLISECONDS; + GNUNET_assert (plugin != NULL); + GNUNET_assert (s != NULL); - if (mret != CURLM_OK) + /* lookup if session is really existing */ + if (GNUNET_YES != client_exist_session (plugin, s)) { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("%s failed at %s:%d: `%s'\n"), - "curl_multi_timeout", __FILE__, __LINE__, - curl_multi_strerror (mret)); + GNUNET_break (0); return GNUNET_SYSERR; } - grs = GNUNET_NETWORK_fdset_create (); - gws = GNUNET_NETWORK_fdset_create (); - GNUNET_NETWORK_fdset_copy_native (grs, &rs, max + 1); - GNUNET_NETWORK_fdset_copy_native (gws, &ws, max + 1); - - plugin->client_perform_task = - GNUNET_SCHEDULER_add_select (GNUNET_SCHEDULER_PRIORITY_DEFAULT, - timeout, grs, gws, - &client_run, plugin); - GNUNET_NETWORK_fdset_destroy (gws); - GNUNET_NETWORK_fdset_destroy (grs); - return GNUNET_OK; -} + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, s->plugin->name, + "Session %p/connection %p: Sending message with %u to peer `%s' \n", + s, s->client_put, + msgbuf_size, GNUNET_i2s (&s->target)); + + /* create new message and schedule */ + msg = GNUNET_malloc (sizeof (struct HTTP_Message) + msgbuf_size); + msg->next = NULL; + msg->size = msgbuf_size; + msg->pos = 0; + msg->buf = (char *) &msg[1]; + msg->transmit_cont = cont; + msg->transmit_cont_cls = cont_cls; + memcpy (msg->buf, msgbuf, msgbuf_size); + GNUNET_CONTAINER_DLL_insert_tail (s->msg_head, s->msg_tail, msg); + GNUNET_asprintf (&stat_txt, "# bytes currently in %s_client buffers", plugin->protocol); + GNUNET_STATISTICS_update (plugin->env->stats, + stat_txt, msgbuf_size, GNUNET_NO); -int -client_send (struct Session *s, struct HTTP_Message *msg) -{ - GNUNET_assert (s != NULL); - GNUNET_CONTAINER_DLL_insert_tail (s->msg_head, s->msg_tail, msg); + GNUNET_free (stat_txt); - if (GNUNET_YES != exist_session(p, s)) + if (GNUNET_YES == s->put_tmp_disconnecting) { - GNUNET_break (0); - return GNUNET_SYSERR; + /* PUT connection is currently getting disconnected */ + s->put_reconnect_required = GNUNET_YES; + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, s->plugin->name, + "Session %p/connection %jp: currently disconnecting, reconnecting immediately\n", + s, s->client_put); + return msgbuf_size; } - if (s->client_put_paused == GNUNET_YES) + else if (GNUNET_YES == s->put_paused) { + /* PUT connection was paused, unpause */ + GNUNET_assert (s->put_disconnect_task != GNUNET_SCHEDULER_NO_TASK); + GNUNET_SCHEDULER_cancel (s->put_disconnect_task); + s->put_disconnect_task = GNUNET_SCHEDULER_NO_TASK; GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, s->plugin->name, - "Client: %p was suspended, unpausing\n", s->client_put); - s->client_put_paused = GNUNET_NO; + "Session %p/connection %p: unpausing connection\n", + s, s->client_put); + s->put_paused = GNUNET_NO; curl_easy_pause (s->client_put, CURLPAUSE_CONT); } - client_schedule (s->plugin, GNUNET_YES); + else if (GNUNET_YES == s->put_tmp_disconnected) + { + /* PUT connection was disconnected, reconnect */ + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, s->plugin->name, + "Session %p: Reconnecting PUT connection\n", + s); + s->put_tmp_disconnected = GNUNET_NO; + GNUNET_break (s->client_put == NULL); + if (GNUNET_SYSERR == client_connect_put (s)) + { + return GNUNET_SYSERR; + } + } - return GNUNET_OK; + client_schedule (s->plugin, GNUNET_YES); + client_reschedule_session_timeout (s); + return msgbuf_size; } /** - * Task performing curl operations + * Delete session s * - * @param cls plugin as closure - * @param tc gnunet scheduler task context + * @param s the session to delete */ static void -client_run (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +client_delete_session (struct Session *s) { - struct Plugin *plugin = cls; - int running; - CURLMcode mret; - - GNUNET_assert (cls != NULL); + struct HTTP_Client_Plugin *plugin = s->plugin; + struct HTTP_Message *pos; + struct HTTP_Message *next; - plugin->client_perform_task = GNUNET_SCHEDULER_NO_TASK; - if (0 != (tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN)) - return; + client_stop_session_timeout (s); - do + if (GNUNET_SCHEDULER_NO_TASK != s->put_disconnect_task) { - running = 0; - mret = curl_multi_perform (plugin->client_mh, &running); - - CURLMsg *msg; - int msgs_left; - - while ((msg = curl_multi_info_read (plugin->client_mh, &msgs_left))) - { - CURL *easy_h = msg->easy_handle; - struct Session *s = NULL; - char *d = (char *) s; - - - //GNUNET_assert (easy_h != NULL); - if (easy_h == NULL) - { - GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, - "Client: connection to ended with reason %i: `%s', %i handles running\n", - msg->data.result, - curl_easy_strerror (msg->data.result), running); - continue; - } - - GNUNET_assert (CURLE_OK == - curl_easy_getinfo (easy_h, CURLINFO_PRIVATE, &d)); - s = (struct Session *) d; + GNUNET_SCHEDULER_cancel (s->put_disconnect_task); + s->put_disconnect_task = GNUNET_SCHEDULER_NO_TASK; + } - if (GNUNET_YES != exist_session(plugin, s)) - { - GNUNET_break (0); - return; - } + GNUNET_CONTAINER_DLL_remove (plugin->head, plugin->tail, s); - GNUNET_assert (s != NULL); + next = s->msg_head; + while (NULL != (pos = next)) + { + next = pos->next; + GNUNET_CONTAINER_DLL_remove (s->msg_head, s->msg_tail, pos); + if (pos->transmit_cont != NULL) + pos->transmit_cont (pos->transmit_cont_cls, &s->target, GNUNET_SYSERR, + pos->size, pos->pos + s->overhead); + s->overhead = 0; + GNUNET_free (pos); + } - if (msg->msg == CURLMSG_DONE) - { - GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, - "Client: %p connection to '%s' %s ended with reason %i: `%s'\n", - msg->easy_handle, GNUNET_i2s (&s->target), - http_plugin_address_to_string (NULL, s->addr, - s->addrlen), - msg->data.result, - curl_easy_strerror (msg->data.result)); - - client_disconnect (s); - GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, - plugin->name, - "Notifying about ended session to peer `%s' `%s'\n", - GNUNET_i2s (&s->target), - http_plugin_address_to_string (plugin, s->addr, s->addrlen)); - notify_session_end (plugin, &s->target, s); - } - } + if (s->msg_tk != NULL) + { + GNUNET_SERVER_mst_destroy (s->msg_tk); + s->msg_tk = NULL; } - while (mret == CURLM_CALL_MULTI_PERFORM); - client_schedule (plugin, GNUNET_NO); + GNUNET_free (s->addr); + GNUNET_free (s->url); + GNUNET_free (s); } -int + +/** + * Disconnect a session + * + * @param s session + * @return GNUNET_OK on success, GNUNET_SYSERR on error + */ +static int client_disconnect (struct Session *s) { - int res = GNUNET_OK; - CURLMcode mret; - struct Plugin *plugin = s->plugin; + struct HTTP_Client_Plugin *plugin = s->plugin; struct HTTP_Message *msg; struct HTTP_Message *t; + int res = GNUNET_OK; + CURLMcode mret; - if (GNUNET_YES != exist_session(plugin, s)) + if (GNUNET_YES != client_exist_session (plugin, s)) { GNUNET_break (0); return GNUNET_SYSERR; @@ -266,13 +635,14 @@ client_disconnect (struct Session *s) if (s->client_put != NULL) { GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, - "Client: %p Deleting outbound PUT session to peer `%s'\n", - s->client_put, GNUNET_i2s (&s->target)); + "Session %p/connection %p: disconnecting PUT connection to peer `%s'\n", + s, s->client_put, GNUNET_i2s (&s->target)); - mret = curl_multi_remove_handle (plugin->client_mh, s->client_put); + /* remove curl handle from multi handle */ + mret = curl_multi_remove_handle (plugin->curl_multi_handle, s->client_put); if (mret != CURLM_OK) { - curl_easy_cleanup (s->client_put); + /* clean up easy handle, handle is now invalid and free'd */ res = GNUNET_SYSERR; GNUNET_break (0); } @@ -289,14 +659,15 @@ client_disconnect (struct Session *s) if (s->client_get != NULL) { - GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, - "Client: %p Deleting outbound GET session to peer `%s'\n", - s->client_get, GNUNET_i2s (&s->target)); + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + "Session %p/connection %p: disconnecting GET connection to peer `%s'\n", + s, s->client_get, GNUNET_i2s (&s->target)); - mret = curl_multi_remove_handle (plugin->client_mh, s->client_get); + /* remove curl handle from multi handle */ + mret = curl_multi_remove_handle (plugin->curl_multi_handle, s->client_get); if (mret != CURLM_OK) { - curl_easy_cleanup (s->client_get); + /* clean up easy handle, handle is now invalid and free'd */ res = GNUNET_SYSERR; GNUNET_break (0); } @@ -309,69 +680,200 @@ client_disconnect (struct Session *s) { t = msg->next; if (NULL != msg->transmit_cont) - msg->transmit_cont (msg->transmit_cont_cls, &s->target, GNUNET_SYSERR); + msg->transmit_cont (msg->transmit_cont_cls, &s->target, GNUNET_SYSERR, + msg->size, msg->pos + s->overhead); + s->overhead = 0; GNUNET_CONTAINER_DLL_remove (s->msg_head, s->msg_tail, msg); GNUNET_free (msg); msg = t; } + GNUNET_assert (plugin->cur_connections >= 2); plugin->cur_connections -= 2; - - GNUNET_assert (plugin->outbound_sessions > 0); - plugin->outbound_sessions --; GNUNET_STATISTICS_set (plugin->env->stats, - "# HTTP outbound sessions", - plugin->outbound_sessions, + "# HTTP client sessions", + plugin->cur_connections, GNUNET_NO); + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + "Session %p: notifying transport about ending session\n",s); + + plugin->env->session_end (plugin->env->cls, &s->target, s); + client_delete_session (s); + /* Re-schedule since handles have changed */ if (plugin->client_perform_task != GNUNET_SCHEDULER_NO_TASK) { GNUNET_SCHEDULER_cancel (plugin->client_perform_task); plugin->client_perform_task = GNUNET_SCHEDULER_NO_TASK; } - client_schedule (plugin, GNUNET_YES); return res; } -static int -client_receive_mst_cb (void *cls, void *client, - const struct GNUNET_MessageHeader *message) + +/** + * Function that can be used to force the plugin to disconnect + * from the given peer and cancel all previous transmissions + * (and their continuationc). + * + * @param cls closure + * @param target peer from which to disconnect + */ +static void +http_client_plugin_disconnect (void *cls, const struct GNUNET_PeerIdentity *target) { - struct Session *s = cls; - struct GNUNET_TIME_Relative delay; + struct HTTP_Client_Plugin *plugin = cls; + struct Session *next = NULL; + struct Session *pos = NULL; + + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + "Transport tells me to disconnect `%s'\n", + GNUNET_i2s (target)); - if (GNUNET_YES != exist_session(p, s)) + next = plugin->head; + while (NULL != (pos = next)) { - GNUNET_break (0); - return GNUNET_OK; + next = pos->next; + if (0 == memcmp (target, &pos->target, sizeof (struct GNUNET_PeerIdentity))) + { + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + "Disconnecting session %p to `%pos'\n", + pos, GNUNET_i2s (target)); + GNUNET_assert (GNUNET_OK == client_disconnect (pos)); + } } - delay = http_plugin_receive (s, &s->target, message, s, s->addr, s->addrlen); - s->next_receive = - GNUNET_TIME_absolute_add (GNUNET_TIME_absolute_get (), delay); +} - if (GNUNET_TIME_absolute_get ().abs_value < s->next_receive.abs_value) +/** + * Check if a sessions exists for an specific address + * + * @param plugin the plugin + * @param address the address + * @return the session or NULL + */ +static struct Session * +client_lookup_session (struct HTTP_Client_Plugin *plugin, + const struct GNUNET_HELLO_Address *address) +{ + struct Session *pos; + + for (pos = plugin->head; NULL != pos; pos = pos->next) + if ((0 == memcmp (&address->peer, &pos->target, sizeof (struct GNUNET_PeerIdentity))) && + (address->address_length == pos->addrlen) && + (0 == memcmp (address->address, pos->addr, pos->addrlen))) + return pos; + return NULL; +} + +static void +client_put_disconnect (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct Session *s = cls; + s->put_disconnect_task = GNUNET_SCHEDULER_NO_TASK; + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, s->plugin->name, + "Session %p/connection %p: will be disconnected due to no activity\n", + s, s->client_put); + s->put_paused = GNUNET_NO; + s->put_tmp_disconnecting = GNUNET_YES; + curl_easy_pause (s->client_put, CURLPAUSE_CONT); + client_schedule (s->plugin, GNUNET_YES); +} + + + +/** + * Callback method used with libcurl + * Method is called when libcurl needs to read data during sending + * + * @param stream pointer where to write data + * @param size size of an individual element + * @param nmemb count of elements that can be written to the buffer + * @param cls source pointer, passed to the libcurl handle + * @return bytes written to stream, returning 0 will terminate connection! + */ +static size_t +client_send_cb (void *stream, size_t size, size_t nmemb, void *cls) +{ + struct Session *s = cls; + struct HTTP_Client_Plugin *plugin = s->plugin; + struct HTTP_Message *msg = s->msg_head; + size_t len; + char *stat_txt; + + if (GNUNET_YES != client_exist_session (plugin, s)) + { + GNUNET_break (0); + return 0; + } + if (GNUNET_YES == s->put_tmp_disconnecting) { - struct Plugin *plugin = s->plugin; + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, s->plugin->name, + "Session %p/connection %p: disconnect due to inactivity\n", + s, s->client_put); + return 0; + } + + if (NULL == msg) + { GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, - "Client: peer `%s' address `%s' next read delayed for %llu ms\n", - GNUNET_i2s (&s->target), GNUNET_a2s (s->addr, s->addrlen), - delay); + "Session %p/connection %p: nothing to send, suspending\n", + s, s->client_put); + s->put_disconnect_task = GNUNET_SCHEDULER_add_delayed (PUT_DISCONNECT_TIMEOUT, &client_put_disconnect, s); + s->put_paused = GNUNET_YES; + return CURL_READFUNC_PAUSE; } - return GNUNET_OK; + /* data to send */ + GNUNET_assert (msg->pos < msg->size); + /* calculate how much fits in buffer */ + len = GNUNET_MIN (msg->size - msg->pos, + size * nmemb); + memcpy (stream, &msg->buf[msg->pos], len); + msg->pos += len; + if (msg->pos == msg->size) + { + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + "Session %p/connection %p: sent message with %u bytes sent, removing message from queue\n", + s, s->client_put, msg->size, msg->pos); + /* Calling transmit continuation */ + GNUNET_CONTAINER_DLL_remove (s->msg_head, s->msg_tail, msg); + if (NULL != msg->transmit_cont) + msg->transmit_cont (msg->transmit_cont_cls, &s->target, GNUNET_OK, + msg->size, msg->size + s->overhead); + s->overhead = 0; + GNUNET_free (msg); + } + + GNUNET_asprintf (&stat_txt, "# bytes currently in %s_client buffers", plugin->protocol); + GNUNET_STATISTICS_update (plugin->env->stats, + stat_txt, -len, GNUNET_NO); + GNUNET_free (stat_txt); + + GNUNET_asprintf (&stat_txt, "# bytes transmitted via %s_client", plugin->protocol); + GNUNET_STATISTICS_update (plugin->env->stats, + stat_txt, len, GNUNET_NO); + GNUNET_free (stat_txt); + + client_reschedule_session_timeout (s); + return len; } +/** + * Wake up a curl handle which was suspended + * + * @param cls the session + * @param tc task context + */ static void client_wake_up (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { struct Session *s = cls; - if (GNUNET_YES != exist_session(p, s)) + if (GNUNET_YES != client_exist_session(p, s)) { GNUNET_break (0); return; @@ -380,15 +882,87 @@ client_wake_up (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) if (0 != (tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN)) return; GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, s->plugin->name, - "Client: %p Waking up receive handle\n", s->client_get); + "Session %p/connection %p: Waking up GET handle\n", s, s->client_get); if (s->client_get != NULL) curl_easy_pause (s->client_get, CURLPAUSE_CONT); } /** - * Callback method used with libcurl - * Method is called when libcurl needs to write data during sending + * Callback for message stream tokenizer + * + * @param cls the session + * @param client not used + * @param message the message received + * @return always GNUNET_OK + */ +static int +client_receive_mst_cb (void *cls, void *client, + const struct GNUNET_MessageHeader *message) +{ + struct Session *s = cls; + struct HTTP_Client_Plugin *plugin; + struct GNUNET_TIME_Relative delay; + struct GNUNET_ATS_Information atsi[2]; + char *stat_txt; + if (GNUNET_YES != client_exist_session(p, s)) + { + GNUNET_break (0); + return GNUNET_OK; + } + plugin = s->plugin; + + atsi[0].type = htonl (GNUNET_ATS_QUALITY_NET_DISTANCE); + atsi[0].value = htonl (1); + atsi[1].type = htonl (GNUNET_ATS_NETWORK_TYPE); + atsi[1].value = s->ats_address_network_type; + GNUNET_break (s->ats_address_network_type != ntohl (GNUNET_ATS_NET_UNSPECIFIED)); + + delay = s->plugin->env->receive (plugin->env->cls, &s->target, message, + (const struct GNUNET_ATS_Information *) &atsi, 2, + s, s->addr, s->addrlen); + + GNUNET_asprintf (&stat_txt, "# bytes received via %s_client", plugin->protocol); + GNUNET_STATISTICS_update (plugin->env->stats, + stat_txt, ntohs(message->size), GNUNET_NO); + GNUNET_free (stat_txt); + + s->next_receive = + GNUNET_TIME_absolute_add (GNUNET_TIME_absolute_get (), delay); + + if (GNUNET_TIME_absolute_get ().abs_value < s->next_receive.abs_value) + { + + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + "Client: peer `%s' address `%s' next read delayed for %llu ms\n", + GNUNET_i2s (&s->target), GNUNET_a2s (s->addr, s->addrlen), + delay); + } + client_reschedule_session_timeout (s); + return GNUNET_OK; +} + + +/** + * Callback method used with libcurl when data for a PUT connection are + * received. We do not expect data here, so we just dismiss it + * + * @param stream pointer where to write data + * @param size size of an individual element + * @param nmemb count of elements that can be written to the buffer + * @param cls destination pointer, passed to the libcurl handle + * @return bytes read from stream + */ +static size_t +client_receive_put (void *stream, size_t size, size_t nmemb, void *cls) +{ + return size * nmemb; +} + + +/** + * Callback method used with libcurl when data for a GET connection are + * received. Forward to MST * * @param stream pointer where to write data * @param size size of an individual element @@ -402,20 +976,20 @@ client_receive (void *stream, size_t size, size_t nmemb, void *cls) struct Session *s = cls; struct GNUNET_TIME_Absolute now; size_t len = size * nmemb; - struct Plugin *plugin = s->plugin; - GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, - "Client: Received %Zu bytes from peer `%s'\n", len, - GNUNET_i2s (&s->target)); + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, s->plugin->name, + "Session %p / connection %p: Received %u bytes from peer `%s'\n", + s, s->client_get, + len, GNUNET_i2s (&s->target)); now = GNUNET_TIME_absolute_get (); if (now.abs_value < s->next_receive.abs_value) { struct GNUNET_TIME_Absolute now = GNUNET_TIME_absolute_get (); struct GNUNET_TIME_Relative delta = GNUNET_TIME_absolute_get_difference (now, s->next_receive); - GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, - "Client: %p No inbound bandwidth available! Next read was delayed for %llu ms\n", - s->client_get, delta.rel_value); + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, s->plugin->name, + "Session %p / connection %p: No inbound bandwidth available! Next read was delayed for %llu ms\n", + s, s->client_get, delta.rel_value); if (s->recv_wakeup_task != GNUNET_SCHEDULER_NO_TASK) { GNUNET_SCHEDULER_cancel (s->recv_wakeup_task); @@ -423,7 +997,7 @@ client_receive (void *stream, size_t size, size_t nmemb, void *cls) } s->recv_wakeup_task = GNUNET_SCHEDULER_add_delayed (delta, &client_wake_up, s); - return CURLPAUSE_ALL; + return CURL_WRITEFUNC_PAUSE; } if (NULL == s->msg_tk) s->msg_tk = GNUNET_SERVER_mst_create (&client_receive_mst_cb, s); @@ -433,167 +1007,383 @@ client_receive (void *stream, size_t size, size_t nmemb, void *cls) /** - * Callback method used with libcurl - * Method is called when libcurl needs to read data during sending + * Task performing curl operations * - * @param stream pointer where to write data - * @param size size of an individual element - * @param nmemb count of elements that can be written to the buffer - * @param cls source pointer, passed to the libcurl handle - * @return bytes written to stream, returning 0 will terminate connection! + * @param cls plugin as closure + * @param tc gnunet scheduler task context */ -static size_t -client_send_cb (void *stream, size_t size, size_t nmemb, void *cls) +static void +client_run (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc); + + +/** + * Function setting up file descriptors and scheduling task to run + * + * @param plugin the plugin as closure + * @param now schedule task in 1ms, regardless of what curl may say + * @return GNUNET_SYSERR for hard failure, GNUNET_OK for ok + */ +static int +client_schedule (struct HTTP_Client_Plugin *plugin, int now) { - struct Session *s = cls; - struct Plugin *plugin = s->plugin; - struct HTTP_Message *msg = s->msg_head; - size_t len; + fd_set rs; + fd_set ws; + fd_set es; + int max; + struct GNUNET_NETWORK_FDSet *grs; + struct GNUNET_NETWORK_FDSet *gws; + long to; + CURLMcode mret; + struct GNUNET_TIME_Relative timeout; - if (GNUNET_YES != exist_session(plugin, s)) + /* Cancel previous scheduled task */ + if (plugin->client_perform_task != GNUNET_SCHEDULER_NO_TASK) { - GNUNET_break (0); - return 0; + GNUNET_SCHEDULER_cancel (plugin->client_perform_task); + plugin->client_perform_task = GNUNET_SCHEDULER_NO_TASK; } - if (NULL == msg) + max = -1; + FD_ZERO (&rs); + FD_ZERO (&ws); + FD_ZERO (&es); + mret = curl_multi_fdset (plugin->curl_multi_handle, &rs, &ws, &es, &max); + if (mret != CURLM_OK) { - GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, - "Client: %p Nothing to send! Suspending PUT handle!\n", - s->client_put); - s->client_put_paused = GNUNET_YES; - return CURL_READFUNC_PAUSE; + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("%s failed at %s:%d: `%s'\n"), + "curl_multi_fdset", __FILE__, __LINE__, + curl_multi_strerror (mret)); + return GNUNET_SYSERR; } - /* data to send */ - GNUNET_assert (msg->pos < msg->size); - /* calculate how much fits in buffer */ - len = GNUNET_MIN (msg->size - msg->pos, - size * nmemb); - memcpy (stream, &msg->buf[msg->pos], len); - msg->pos += len; - if (msg->pos == msg->size) + mret = curl_multi_timeout (plugin->curl_multi_handle, &to); + if (to == -1) + timeout = GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 1); + else + timeout = GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MILLISECONDS, to); + if (now == GNUNET_YES) + timeout = GNUNET_TIME_UNIT_MILLISECONDS; + + if (mret != CURLM_OK) { - GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, - "Client: %p Message with %u bytes sent, removing message from queue\n", - s->client_put, msg->size, msg->pos); - /* Calling transmit continuation */ - GNUNET_CONTAINER_DLL_remove (s->msg_head, s->msg_tail, msg); - if (NULL != msg->transmit_cont) - msg->transmit_cont (msg->transmit_cont_cls, &s->target, GNUNET_OK); - GNUNET_free (msg); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("%s failed at %s:%d: `%s'\n"), + "curl_multi_timeout", __FILE__, __LINE__, + curl_multi_strerror (mret)); + return GNUNET_SYSERR; } - return len; + + grs = GNUNET_NETWORK_fdset_create (); + gws = GNUNET_NETWORK_fdset_create (); + GNUNET_NETWORK_fdset_copy_native (grs, &rs, max + 1); + GNUNET_NETWORK_fdset_copy_native (gws, &ws, max + 1); + + plugin->client_perform_task = + GNUNET_SCHEDULER_add_select (GNUNET_SCHEDULER_PRIORITY_DEFAULT, + timeout, grs, gws, + &client_run, plugin); + GNUNET_NETWORK_fdset_destroy (gws); + GNUNET_NETWORK_fdset_destroy (grs); + return GNUNET_OK; } -int -client_connect (struct Session *s) +/** + * Task performing curl operations + * + * @param cls plugin as closure + * @param tc gnunet scheduler task context + */ +static void +client_run (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { - struct Plugin *plugin = s->plugin; - int res = GNUNET_OK; - char *url; + struct HTTP_Client_Plugin *plugin = cls; + int running; + long http_statuscode; CURLMcode mret; - GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, - "Initiating outbound session peer `%s'\n", - GNUNET_i2s (&s->target)); - s->inbound = GNUNET_NO; - plugin->last_tag++; - /* create url */ - GNUNET_asprintf (&url, "%s%s;%u", - http_plugin_address_to_string (plugin, s->addr, s->addrlen), - GNUNET_h2s_full (&plugin->env->my_identity->hashPubKey), - plugin->last_tag); -#if 0 - GNUNET_log_from (GNUNET_ERROR_TYPE_ERROR, plugin->name, "URL `%s'\n", url); -#endif + GNUNET_assert (cls != NULL); + + plugin->client_perform_task = GNUNET_SCHEDULER_NO_TASK; + if (0 != (tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN)) + return; + + do + { + running = 0; + mret = curl_multi_perform (plugin->curl_multi_handle, &running); + + CURLMsg *msg; + int msgs_left; + + while ((msg = curl_multi_info_read (plugin->curl_multi_handle, &msgs_left))) + { + CURL *easy_h = msg->easy_handle; + struct Session *s = NULL; + char *d = (char *) s; + + if (easy_h == NULL) + { + GNUNET_break (0); + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + "Client: connection to ended with reason %i: `%s', %i handles running\n", + msg->data.result, + curl_easy_strerror (msg->data.result), running); + continue; + } + + GNUNET_assert (CURLE_OK == + curl_easy_getinfo (easy_h, CURLINFO_PRIVATE, &d)); + s = (struct Session *) d; + + if (GNUNET_YES != client_exist_session(plugin, s)) + { + GNUNET_break (0); + return; + } + + GNUNET_assert (s != NULL); + if (msg->msg == CURLMSG_DONE) + { + curl_easy_getinfo (easy_h, CURLINFO_RESPONSE_CODE, &http_statuscode); + if (easy_h == s->client_put) + { + if ((0 != msg->data.result) || (http_statuscode != 200)) + { + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + "Session %p/connection %p: PUT connection to `%s' ended with status %i reason %i: `%s'\n", + s, msg->easy_handle, GNUNET_i2s (&s->target), + http_statuscode, + msg->data.result, + curl_easy_strerror (msg->data.result)); + } + else + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + "Session %p/connection %p: PUT connection to `%s' ended normal\n", + s, msg->easy_handle, GNUNET_i2s (&s->target)); + if (s->client_get == NULL) + { + /* Disconnect other transmission direction and tell transport */ + } + curl_multi_remove_handle (plugin->curl_multi_handle, easy_h); + curl_easy_cleanup (easy_h); + s->put_tmp_disconnecting = GNUNET_NO; + s->put_tmp_disconnected = GNUNET_YES; + s->client_put = NULL; + s->put.easyhandle = NULL; + s->put.s = NULL; + + /* + * Handling a rare case: + * plugin_send was called during temporary put disconnect, + * reconnect required after connection was disconnected + */ + if (GNUNET_YES == s->put_reconnect_required) + { + s->put_reconnect_required = GNUNET_NO; + if (GNUNET_SYSERR == client_connect_put(s)) + { + GNUNET_break (s->client_put == NULL); + GNUNET_break (s->put_tmp_disconnected == GNUNET_NO); + } + } + } + if (easy_h == s->client_get) + { + if ((0 != msg->data.result) || (http_statuscode != 200)) + { + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + "Session %p/connection %p: GET connection to `%s' ended with status %i reason %i: `%s'\n", + s, msg->easy_handle, GNUNET_i2s (&s->target), + http_statuscode, + msg->data.result, + curl_easy_strerror (msg->data.result)); + + } + else + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + "Session %p/connection %p: GET connection to `%s' ended normal\n", + s, msg->easy_handle, GNUNET_i2s (&s->target)); + /* Disconnect other transmission direction and tell transport */ + s->get.easyhandle = NULL; + s->get.s = NULL; + client_disconnect (s); + } + } + } + } + while (mret == CURLM_CALL_MULTI_PERFORM); + client_schedule (plugin, GNUNET_NO); +} + + +/** + * Connect GET connection for a session + * + * @param s the session to connect + * @return GNUNET_OK on success, GNUNET_SYSERR otherwise + */ +static int +client_connect_get (struct Session *s) +{ + CURLMcode mret; /* create get connection */ s->client_get = curl_easy_init (); + s->get.s = s; + s->get.easyhandle = s->client_get; #if VERBOSE_CURL curl_easy_setopt (s->client_get, CURLOPT_VERBOSE, 1L); curl_easy_setopt (s->client_get, CURLOPT_DEBUGFUNCTION, &client_log); - curl_easy_setopt (s->client_get, CURLOPT_DEBUGDATA, s->client_get); + curl_easy_setopt (s->client_get, CURLOPT_DEBUGDATA, &s->get); #endif #if BUILD_HTTPS curl_easy_setopt (s->client_get, CURLOPT_SSLVERSION, CURL_SSLVERSION_TLSv1); curl_easy_setopt (s->client_get, CURLOPT_SSL_VERIFYPEER, 0); curl_easy_setopt (s->client_get, CURLOPT_SSL_VERIFYHOST, 0); #endif - curl_easy_setopt (s->client_get, CURLOPT_URL, url); + curl_easy_setopt (s->client_get, CURLOPT_URL, s->url); //curl_easy_setopt (s->client_get, CURLOPT_HEADERFUNCTION, &curl_get_header_cb); //curl_easy_setopt (s->client_get, CURLOPT_WRITEHEADER, ps); curl_easy_setopt (s->client_get, CURLOPT_READFUNCTION, client_send_cb); curl_easy_setopt (s->client_get, CURLOPT_READDATA, s); curl_easy_setopt (s->client_get, CURLOPT_WRITEFUNCTION, client_receive); curl_easy_setopt (s->client_get, CURLOPT_WRITEDATA, s); - curl_easy_setopt (s->client_get, CURLOPT_TIMEOUT_MS, - (long) GNUNET_CONSTANTS_IDLE_CONNECTION_TIMEOUT.rel_value); + /* No timeout by default, timeout done with session timeout */ + curl_easy_setopt (s->client_get, CURLOPT_TIMEOUT, 0); curl_easy_setopt (s->client_get, CURLOPT_PRIVATE, s); curl_easy_setopt (s->client_get, CURLOPT_CONNECTTIMEOUT_MS, - (long) HTTP_NOT_VALIDATED_TIMEOUT.rel_value); + (long) HTTP_CLIENT_NOT_VALIDATED_TIMEOUT.rel_value); curl_easy_setopt (s->client_get, CURLOPT_BUFFERSIZE, 2 * GNUNET_SERVER_MAX_MESSAGE_SIZE); #if CURL_TCP_NODELAY curl_easy_setopt (ps->recv_endpoint, CURLOPT_TCP_NODELAY, 1); #endif + mret = curl_multi_add_handle (s->plugin->curl_multi_handle, s->client_get); + if (mret != CURLM_OK) + { + GNUNET_log_from (GNUNET_ERROR_TYPE_ERROR, s->plugin->name, + "Session %p : Failed to add GET handle to multihandle: `%s'\n", + s, curl_multi_strerror (mret)); + curl_easy_cleanup (s->client_get); + s->client_get = NULL; + s->get.s = NULL; + s->get.easyhandle = NULL; + GNUNET_break (0); + return GNUNET_SYSERR; + } + + return GNUNET_OK; +} +/** + * Connect a HTTP put connection + * + * @param s the session to connect + * @return GNUNET_SYSERR for hard failure, GNUNET_OK for ok + */ +static int +client_connect_put (struct Session *s) +{ + CURLMcode mret; /* create put connection */ + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, s->plugin->name, + "Session %p : Init PUT handle \n", s); s->client_put = curl_easy_init (); + s->put.s = s; + s->put.easyhandle = s->client_put; #if VERBOSE_CURL curl_easy_setopt (s->client_put, CURLOPT_VERBOSE, 1L); curl_easy_setopt (s->client_put, CURLOPT_DEBUGFUNCTION, &client_log); - curl_easy_setopt (s->client_put, CURLOPT_DEBUGDATA, s->client_put); + curl_easy_setopt (s->client_put, CURLOPT_DEBUGDATA, &s->put); #endif #if BUILD_HTTPS curl_easy_setopt (s->client_put, CURLOPT_SSLVERSION, CURL_SSLVERSION_TLSv1); curl_easy_setopt (s->client_put, CURLOPT_SSL_VERIFYPEER, 0); curl_easy_setopt (s->client_put, CURLOPT_SSL_VERIFYHOST, 0); #endif - curl_easy_setopt (s->client_put, CURLOPT_URL, url); - curl_easy_setopt (s->client_put, CURLOPT_PUT, 1L); - //curl_easy_setopt (s->client_put, CURLOPT_HEADERFUNCTION, &curl_put_header_cb); + curl_easy_setopt (s->client_put, CURLOPT_URL, s->url); + curl_easy_setopt (s->client_put, CURLOPT_UPLOAD, 1L); + //curl_easy_setopt (s->client_put, CURLOPT_HEADERFUNCTION, &client_curl_header); //curl_easy_setopt (s->client_put, CURLOPT_WRITEHEADER, ps); curl_easy_setopt (s->client_put, CURLOPT_READFUNCTION, client_send_cb); curl_easy_setopt (s->client_put, CURLOPT_READDATA, s); - curl_easy_setopt (s->client_put, CURLOPT_WRITEFUNCTION, client_receive); + curl_easy_setopt (s->client_put, CURLOPT_WRITEFUNCTION, client_receive_put); curl_easy_setopt (s->client_put, CURLOPT_WRITEDATA, s); - curl_easy_setopt (s->client_put, CURLOPT_TIMEOUT_MS, - (long) GNUNET_CONSTANTS_IDLE_CONNECTION_TIMEOUT.rel_value); + /* No timeout by default, timeout done with session timeout */ + curl_easy_setopt (s->client_put, CURLOPT_TIMEOUT, 0); curl_easy_setopt (s->client_put, CURLOPT_PRIVATE, s); curl_easy_setopt (s->client_put, CURLOPT_CONNECTTIMEOUT_MS, - (long) HTTP_NOT_VALIDATED_TIMEOUT.rel_value); + (long) HTTP_CLIENT_NOT_VALIDATED_TIMEOUT.rel_value); curl_easy_setopt (s->client_put, CURLOPT_BUFFERSIZE, 2 * GNUNET_SERVER_MAX_MESSAGE_SIZE); #if CURL_TCP_NODELAY curl_easy_setopt (s->client_put, CURLOPT_TCP_NODELAY, 1); #endif + mret = curl_multi_add_handle (s->plugin->curl_multi_handle, s->client_put); + if (mret != CURLM_OK) + { + GNUNET_log_from (GNUNET_ERROR_TYPE_ERROR, s->plugin->name, + "Session %p : Failed to add PUT handle to multihandle: `%s'\n", + s, curl_multi_strerror (mret)); + curl_easy_cleanup (s->client_put); + s->client_put = NULL; + s->put.easyhandle = NULL; + s->put.s = NULL; + s->put_tmp_disconnected = GNUNET_YES; + return GNUNET_SYSERR; + } + s->put_tmp_disconnected = GNUNET_NO; + return GNUNET_OK; +} - GNUNET_free (url); - mret = curl_multi_add_handle (plugin->client_mh, s->client_get); - if (mret != CURLM_OK) +/** + * Connect both PUT and GET connection for a session + * + * @param s the session to connect + * @return GNUNET_OK on success, GNUNET_SYSERR otherwise + */ +static int +client_connect (struct Session *s) +{ + + struct HTTP_Client_Plugin *plugin = s->plugin; + int res = GNUNET_OK; + + + /* create url */ + if (NULL == http_common_plugin_address_to_string (NULL, s->addr, s->addrlen)) { - curl_easy_cleanup (s->client_get); - res = GNUNET_SYSERR; - GNUNET_break (0); + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + "Invalid address peer `%s'\n", + GNUNET_i2s (&s->target)); + return GNUNET_SYSERR; } - mret = curl_multi_add_handle (plugin->client_mh, s->client_put); - if (mret != CURLM_OK) + GNUNET_asprintf (&s->url, "%s/%s;%u", + http_common_plugin_address_to_string (plugin, s->addr, s->addrlen), + GNUNET_h2s_full (&plugin->env->my_identity->hashPubKey), + plugin->last_tag); + + plugin->last_tag++; + + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + "Initiating outbound session peer `%s' using address `%s'\n", + GNUNET_i2s (&s->target), s->url); + + if ((GNUNET_SYSERR == client_connect_get (s)) || + (GNUNET_SYSERR == client_connect_put (s))) { - curl_multi_remove_handle (plugin->client_mh, s->client_get); - curl_easy_cleanup (s->client_get); - curl_easy_cleanup (s->client_put); - res = GNUNET_SYSERR; - GNUNET_break (0); + GNUNET_break (0); + return GNUNET_SYSERR; } + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + "Session %p: connected with connections GET %p and PUT %p\n", + s, s->client_get, s->client_put); + /* Perform connect */ plugin->cur_connections += 2; - - plugin->outbound_sessions ++; GNUNET_STATISTICS_set (plugin->env->stats, - "# HTTP outbound sessions", - plugin->outbound_sessions, + "# HTTP client connections", + plugin->cur_connections, GNUNET_NO); /* Re-schedule since handles have changed */ @@ -603,46 +1393,373 @@ client_connect (struct Session *s) plugin->client_perform_task = GNUNET_SCHEDULER_NO_TASK; } plugin->client_perform_task = GNUNET_SCHEDULER_add_now (client_run, plugin); - return res; } -int -client_start (struct Plugin *plugin) +/** + * Creates a new outbound session the transport service will use to send data to the + * peer + * + * @param cls the plugin + * @param address the address + * @return the session or NULL of max connections exceeded + */ +static struct Session * +http_client_plugin_get_session (void *cls, + const struct GNUNET_HELLO_Address *address) { - int res = GNUNET_OK; - p = plugin; + struct HTTP_Client_Plugin *plugin = cls; + struct Session * s = NULL; + struct sockaddr *sa; + struct GNUNET_ATS_Information ats; + size_t salen = 0; + int res; + + GNUNET_assert (plugin != NULL); + GNUNET_assert (address != NULL); + GNUNET_assert (address->address != NULL); + + /* find existing session */ + s = client_lookup_session (plugin, address); + if (s != NULL) + return s; + + if (plugin->max_connections <= plugin->cur_connections) + { + GNUNET_log_from (GNUNET_ERROR_TYPE_WARNING, plugin->name, + "Maximum number of connections (%u) reached: " + "cannot connect to peer `%s'\n", + plugin->max_connections, + GNUNET_i2s (&address->peer)); + return NULL; + } + ats.type = htonl (GNUNET_ATS_NETWORK_TYPE); + ats.value = htonl (GNUNET_ATS_NET_UNSPECIFIED); + sa = http_common_socket_from_address (address->address, address->address_length, &res); + + if (GNUNET_SYSERR == res) + { + return NULL; + } + else if (GNUNET_YES == res) + { + GNUNET_assert (NULL != sa); + if (AF_INET == sa->sa_family) + { + salen = sizeof (struct sockaddr_in); + } + else if (AF_INET6 == sa->sa_family) + { + salen = sizeof (struct sockaddr_in6); + } + ats = plugin->env->get_address_type (plugin->env->cls, sa, salen); + //fprintf (stderr, "Address %s is in %s\n", GNUNET_a2s (sa,salen), GNUNET_ATS_print_network_type(ntohl(ats.value))); + GNUNET_free (sa); + } + else if (GNUNET_NO == res) + { + ats.value = htonl (GNUNET_ATS_COST_WAN); + } + + if (GNUNET_ATS_NET_UNSPECIFIED == ntohl(ats.value)) + { + GNUNET_break (0); + return NULL; + } + + s = GNUNET_malloc (sizeof (struct Session)); + memcpy (&s->target, &address->peer, sizeof (struct GNUNET_PeerIdentity)); + s->plugin = plugin; + s->addr = GNUNET_malloc (address->address_length); + memcpy (s->addr, address->address, address->address_length); + s->addrlen = address->address_length; + s->ats_address_network_type = ats.value; + s->put_paused = GNUNET_NO; + s->put_tmp_disconnecting = GNUNET_NO; + s->put_tmp_disconnected = GNUNET_NO; + client_start_session_timeout (s); + + /* add new session */ + GNUNET_CONTAINER_DLL_insert (plugin->head, plugin->tail, s); + + /* initiate new connection */ + if (GNUNET_SYSERR == client_connect (s)) + { + GNUNET_log_from (GNUNET_ERROR_TYPE_ERROR, plugin->name, + "Cannot connect to peer `%s' address `%s''\n", + http_common_plugin_address_to_string (NULL, s->addr, s->addrlen), + GNUNET_i2s (&s->target)); + client_delete_session (s); + return NULL; + } + return s; +} + + +/** + * Setup http_client plugin + * + * @param plugin the plugin handle + * @return GNUNET_OK on success, GNUNET_SYSERR on error + */ +static int +client_start (struct HTTP_Client_Plugin *plugin) +{ curl_global_init (CURL_GLOBAL_ALL); - plugin->client_mh = curl_multi_init (); + plugin->curl_multi_handle = curl_multi_init (); - if (NULL == plugin->client_mh) + if (NULL == plugin->curl_multi_handle) { GNUNET_log_from (GNUNET_ERROR_TYPE_ERROR, plugin->name, - _ - ("Could not initialize curl multi handle, failed to start %s plugin!\n"), - plugin->name); - res = GNUNET_SYSERR; + _("Could not initialize curl multi handle, failed to start %s plugin!\n"), + plugin->name); + return GNUNET_SYSERR; } - return res; + return GNUNET_OK; } +/** + * Session was idle, so disconnect it + */ +static void +client_session_timeout (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + GNUNET_assert (NULL != cls); + struct Session *s = cls; -void -client_stop (struct Plugin *plugin) + s->timeout_task = GNUNET_SCHEDULER_NO_TASK; + GNUNET_log (TIMEOUT_LOG, + "Session %p was idle for %llu ms, disconnecting\n", + s, (unsigned long long) CLIENT_SESSION_TIMEOUT.rel_value); + + /* call session destroy function */ + GNUNET_assert (GNUNET_OK == client_disconnect (s)); +} + + +/** + * Start session timeout for session s + * + * @param s the session + */ +static void +client_start_session_timeout (struct Session *s) { - p = NULL; - if (plugin->client_perform_task != GNUNET_SCHEDULER_NO_TASK) + + GNUNET_assert (NULL != s); + GNUNET_assert (GNUNET_SCHEDULER_NO_TASK == s->timeout_task); + s->timeout_task = GNUNET_SCHEDULER_add_delayed (CLIENT_SESSION_TIMEOUT, + &client_session_timeout, + s); + GNUNET_log (TIMEOUT_LOG, + "Timeout for session %p set to %llu ms\n", + s, (unsigned long long) CLIENT_SESSION_TIMEOUT.rel_value); +} + + +/** + * Increment session timeout due to activity for session s + * + * param s the session + */ +static void +client_reschedule_session_timeout (struct Session *s) +{ + + GNUNET_assert (NULL != s); + GNUNET_assert (GNUNET_SCHEDULER_NO_TASK != s->timeout_task); + + GNUNET_SCHEDULER_cancel (s->timeout_task); + s->timeout_task = GNUNET_SCHEDULER_add_delayed (CLIENT_SESSION_TIMEOUT, + &client_session_timeout, + s); + GNUNET_log (TIMEOUT_LOG, + "Timeout rescheduled for session %p set to %llu ms\n", + s, (unsigned long long) CLIENT_SESSION_TIMEOUT.rel_value); +} + + +/** + * Cancel timeout due to activity for session s + * + * param s the session + */ +static void +client_stop_session_timeout (struct Session *s) +{ + GNUNET_assert (NULL != s); + + if (GNUNET_SCHEDULER_NO_TASK != s->timeout_task) + { + GNUNET_SCHEDULER_cancel (s->timeout_task); + s->timeout_task = GNUNET_SCHEDULER_NO_TASK; + GNUNET_log (TIMEOUT_LOG, "Timeout stopped for session %p\n", s); + } +} + + +/** + * Another peer has suggested an address for this + * peer and transport plugin. Check that this could be a valid + * address. If so, consider adding it to the list + * of addresses. + * + * @param cls closure + * @param addr pointer to the address + * @param addrlen length of addr + * @return GNUNET_OK if this is a plausible address for this peer + * and transport + */ +static int +http_client_plugin_address_suggested (void *cls, const void *addr, size_t addrlen) +{ + /* struct Plugin *plugin = cls; */ + + /* A HTTP/S client does not have any valid address so:*/ + return GNUNET_NO; +} + + +/** + * Exit point from the plugin. + * + * @param cls api as closure + * @return NULL + */ +void * +LIBGNUNET_PLUGIN_TRANSPORT_DONE (void *cls) +{ + struct GNUNET_TRANSPORT_PluginFunctions *api = cls; + struct HTTP_Client_Plugin *plugin = api->cls; + struct Session *pos; + struct Session *next; + + if (NULL == api->cls) { - GNUNET_SCHEDULER_cancel (plugin->client_perform_task); - plugin->client_perform_task = GNUNET_SCHEDULER_NO_TASK; + /* Stub shutdown */ + GNUNET_free (api); + return NULL; } - curl_multi_cleanup (plugin->client_mh); + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + _("Shutting down plugin `%s'\n"), + plugin->name); + + + next = plugin->head; + while (NULL != (pos = next)) + { + next = pos->next; + client_disconnect (pos); + } + if (GNUNET_SCHEDULER_NO_TASK != plugin->client_perform_task) + { + GNUNET_SCHEDULER_cancel (plugin->client_perform_task); + plugin->client_perform_task = GNUNET_SCHEDULER_NO_TASK; + } + + + if (NULL != plugin->curl_multi_handle) + { + curl_multi_cleanup (plugin->curl_multi_handle); + plugin->curl_multi_handle = NULL; + } curl_global_cleanup (); + + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + _("Shutdown for plugin `%s' complete\n"), + plugin->name); + + GNUNET_free (plugin); + GNUNET_free (api); + return NULL; +} + + +/** + * Configure plugin + * + * @param plugin the plugin handle + * @return GNUNET_OK on success, GNUNET_SYSERR on failure + */ +static int +client_configure_plugin (struct HTTP_Client_Plugin *plugin) +{ + unsigned long long max_connections; + + /* Optional parameters */ + if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_number (plugin->env->cfg, + plugin->name, + "MAX_CONNECTIONS", &max_connections)) + max_connections = 128; + plugin->max_connections = max_connections; + + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + _("Maximum number of connections is %u\n"), + plugin->max_connections); + return GNUNET_OK; } +/** + * Entry point for the plugin. + */ +void * +LIBGNUNET_PLUGIN_TRANSPORT_INIT (void *cls) +{ + struct GNUNET_TRANSPORT_PluginEnvironment *env = cls; + struct GNUNET_TRANSPORT_PluginFunctions *api; + struct HTTP_Client_Plugin *plugin; + if (NULL == env->receive) + { + /* run in 'stub' mode (i.e. as part of gnunet-peerinfo), don't fully + initialze the plugin or the API */ + api = GNUNET_malloc (sizeof (struct GNUNET_TRANSPORT_PluginFunctions)); + api->cls = NULL; + api->address_to_string = &http_common_plugin_address_to_string; + api->string_to_address = &http_common_plugin_string_to_address; + api->address_pretty_printer = &http_common_plugin_address_pretty_printer; + return api; + } + + plugin = GNUNET_malloc (sizeof (struct HTTP_Client_Plugin)); + p = plugin; + plugin->env = env; + api = GNUNET_malloc (sizeof (struct GNUNET_TRANSPORT_PluginFunctions)); + api->cls = plugin; + api->send = &http_client_plugin_send; + api->disconnect = &http_client_plugin_disconnect; + api->check_address = &http_client_plugin_address_suggested; + api->get_session = &http_client_plugin_get_session; + api->address_to_string = &http_common_plugin_address_to_string; + api->string_to_address = &http_common_plugin_string_to_address; + api->address_pretty_printer = &http_common_plugin_address_pretty_printer; + + +#if BUILD_HTTPS + plugin->name = "transport-https_client"; + plugin->protocol = "https"; +#else + plugin->name = "transport-http_client"; + plugin->protocol = "http"; +#endif + plugin->last_tag = 1; + + if (GNUNET_SYSERR == client_configure_plugin (plugin)) + { + LIBGNUNET_PLUGIN_TRANSPORT_DONE (api); + return NULL; + } + + /* Start client */ + if (GNUNET_SYSERR == client_start (plugin)) + { + LIBGNUNET_PLUGIN_TRANSPORT_DONE (api); + return NULL; + } + return api; +} /* end of plugin_transport_http_client.c */ diff --git a/src/transport/plugin_transport_http_common.c b/src/transport/plugin_transport_http_common.c new file mode 100644 index 0000000..bf98330 --- /dev/null +++ b/src/transport/plugin_transport_http_common.c @@ -0,0 +1,408 @@ +/* + This file is part of GNUnet + (C) 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @file transport/plugin_transport_http_common.c + * @brief functionality shared by http client and server transport service plugin + * @author Matthias Wachs + */ + +#include "platform.h" +#include "gnunet_common.h" +#include "gnunet_transport_plugin.h" +#include "plugin_transport_http_common.h" + +struct SplittedHTTPAddress +{ + char *protocol; + char *host; + char *path; + int port; +}; + +static void +http_clean_splitted (struct SplittedHTTPAddress *spa) +{ + if (NULL != spa) + { + GNUNET_free_non_null (spa->protocol); + GNUNET_free_non_null (spa->host); + GNUNET_free_non_null (spa->path); + GNUNET_free_non_null (spa); + } +} + +struct SplittedHTTPAddress * +http_split_address (const char * addr) +{ + struct SplittedHTTPAddress *sp; + char *src = GNUNET_strdup (addr); + char *protocol_start = NULL; + char *host_start = NULL; + char *v6_end = NULL; + char *port_start = NULL; + char *path_start = NULL; + protocol_start = src; + sp = GNUNET_malloc (sizeof (struct SplittedHTTPAddress)); + + /* Address string consists of protocol://host[:port]path*/ + + host_start = strstr (src, "://"); + if (NULL == host_start) + { + GNUNET_free (src); + GNUNET_free (sp); + return NULL; + } + + host_start[0] = '\0'; + sp->protocol = GNUNET_strdup (protocol_start); + + host_start += strlen ("://"); + if (strlen (host_start) == 0) + { + GNUNET_free (src); + GNUNET_free (sp->protocol); + GNUNET_free (sp); + return NULL; + } + + /* Find path start */ + path_start = strchr (host_start, '/'); + if (NULL != path_start) + { + sp->path = GNUNET_strdup (path_start); + path_start[0] = '\0'; + } + else + sp->path = GNUNET_strdup (""); + + if (strlen(host_start) < 1) + { + GNUNET_free (src); + GNUNET_free (sp->protocol); + GNUNET_free (sp->path); + GNUNET_free (sp); + return NULL; + } + + if (NULL != (port_start = strrchr (host_start, ':'))) + { + /* *We COULD have a port, but also an IPv6 address! */ + if (NULL != (v6_end = strchr(host_start, ']'))) + { + if (v6_end < port_start) + { + /* IPv6 address + port */ + port_start[0] = '\0'; + port_start ++; + sp->port = atoi (port_start); + if ((0 == sp->port) || (65535 < sp->port)) + { + GNUNET_free (src); + GNUNET_free (sp->protocol); + GNUNET_free (sp->path); + GNUNET_free (sp); + return NULL; + } + } + else + { + /* IPv6 address + no port */ + if (0 == strcmp(sp->protocol, "https")) + sp->port = HTTPS_DEFAULT_PORT; + else if (0 == strcmp(sp->protocol, "http")) + sp->port = HTTP_DEFAULT_PORT; + } + } + else + { + /* No IPv6 address */ + port_start[0] = '\0'; + port_start ++; + sp->port = atoi (port_start); + if ((0 == sp->port) || (65535 < sp->port)) + { + GNUNET_free (src); + GNUNET_free (sp->protocol); + GNUNET_free (sp->path); + GNUNET_free (sp); + return NULL; + } + } + } + else + { + /* No ':' as port separator, default port for protocol */ + if (0 == strcmp(sp->protocol, "https")) + sp->port = HTTPS_DEFAULT_PORT; + else if (0 == strcmp(sp->protocol, "http")) + sp->port = HTTP_DEFAULT_PORT; + else + { + GNUNET_break (0); + GNUNET_free (src); + GNUNET_free (sp->protocol); + GNUNET_free (sp->path); + GNUNET_free (sp); + return NULL; + } + } + if (strlen (host_start) > 0) + sp->host = GNUNET_strdup (host_start); + else + { + GNUNET_break (0); + GNUNET_free (src); + GNUNET_free (sp->protocol); + GNUNET_free (sp->path); + GNUNET_free (sp); + return NULL; + } + GNUNET_free (src); + return sp; +} + +/** + * Convert the transports address to a nice, human-readable + * format. + * + * @param cls closure + * @param type name of the transport that generated the address + * @param addr one of the addresses of the host, NULL for the last address + * the specific address format depends on the transport + * @param addrlen length of the address + * @param numeric should (IP) addresses be displayed in numeric form? + * @param timeout after how long should we give up? + * @param asc function to call on each string + * @param asc_cls closure for asc + */ +void +http_common_plugin_address_pretty_printer (void *cls, const char *type, + const void *addr, size_t addrlen, + int numeric, + struct GNUNET_TIME_Relative timeout, + GNUNET_TRANSPORT_AddressStringCallback + asc, void *asc_cls) +{ + const char *saddr = (const char *) addr; + + if ( (NULL == saddr) || + (0 >= addrlen) || + ('\0' != saddr[addrlen-1]) ) + { + asc (asc_cls, NULL); + return; + } + asc (asc_cls, saddr); + asc (asc_cls, NULL); +} + + +/** + * Function called for a quick conversion of the binary address to + * a numeric address. Note that the caller must not free the + * address and that the next call to this function is allowed + * to override the address again. + * + * @param cls closure + * @param addr binary address + * @param addrlen length of the address + * @return string representing the same address + */ +const char * +http_common_plugin_address_to_string (void *cls, const void *addr, size_t addrlen) +{ + const char *saddr = (const char *) addr; + if (NULL == saddr) + return NULL; + if (0 >= addrlen) + return NULL; + if (saddr[addrlen-1] != '\0') + return NULL; + return saddr; +} + +/** + * Function called to convert a string address to + * a binary address. + * + * @param cls closure ('struct Plugin*') + * @param addr string address + * @param addrlen length of the address + * @param buf location to store the buffer + * If the function returns GNUNET_SYSERR, its contents are undefined. + * @param added length of created address + * @return GNUNET_OK on success, GNUNET_SYSERR on failure + */ +int +http_common_plugin_string_to_address (void *cls, + const char *addr, + uint16_t addrlen, + void **buf, + size_t *added) +{ + if (NULL == addr) + return GNUNET_SYSERR; + if (0 >= addrlen) + return GNUNET_SYSERR; + if (addr[addrlen-1] != '\0') + return GNUNET_SYSERR; + + (*buf) = strdup (addr); + (*added) = strlen (addr) + 1; + return GNUNET_OK; +} + +/** + * Create a HTTP address from a socketaddr + * + * @param protocol protocol + * @param addr sockaddr * address + * @param addrlen length of the address + * @return the string + */ +char * +http_common_address_from_socket (const char *protocol, const struct sockaddr *addr, socklen_t addrlen) +{ + char *res; + GNUNET_asprintf(&res, "%s://%s", protocol, GNUNET_a2s (addr, addrlen)); + return res; +} + +/** + * Create a socketaddr from a HTTP address + * + * @param addr sockaddr * address + * @param addrlen length of the address + * @param res the result: + * GNUNET_SYSERR, invalid input, + * GNUNET_YES: could convert to ip, + * GNUNET_NO: valid input but could not convert to ip (hostname?) + * @return the string + */ +struct sockaddr * +http_common_socket_from_address (const void *addr, size_t addrlen, int *res) +{ + struct SplittedHTTPAddress * spa; + struct sockaddr_storage *s; + (*res) = GNUNET_SYSERR; + char * to_conv; + + if (NULL == addr) + { + GNUNET_break (0); + return NULL; + } + if (0 >= addrlen) + { + GNUNET_break (0); + return NULL; + } + if (((char *) addr)[addrlen-1] != '\0') + { + GNUNET_break (0); + return NULL; + } + + spa = http_split_address (addr); + if (NULL == spa) + { + (*res) = GNUNET_SYSERR; + return NULL; + } + + s = GNUNET_malloc (sizeof (struct sockaddr_storage)); + GNUNET_asprintf (&to_conv, "%s:%u", spa->host, spa->port); + if (GNUNET_SYSERR == GNUNET_STRINGS_to_address_ip (to_conv, strlen(to_conv), s)) + { + /* could be a hostname */ + GNUNET_free (s); + (*res) = GNUNET_NO; + s = NULL; + } + else if ((AF_INET != s->ss_family) && (AF_INET6 != s->ss_family)) + { + + GNUNET_free (s); + (*res) = GNUNET_SYSERR; + s = NULL; + } + else + { + (*res) = GNUNET_YES; + } + http_clean_splitted (spa); + GNUNET_free (to_conv); + return (struct sockaddr *) s; +} + +/** + * Get the length of an address + * + * @param addr address + * @return the size + */ +size_t +http_common_address_get_size (const void *addr) +{ + return strlen (addr) + 1; +} + +/** + * Compare addr1 to addr2 + * + * @param addr1 address1 + * @param addrlen1 address 1 length + * @param addr2 address2 + * @param addrlen2 address 2 length + * @return GNUNET_YES if equal, GNUNET_NO if not, GNUNET_SYSERR on error + */ +size_t +http_common_cmp_addresses (const void *addr1, size_t addrlen1, const void *addr2, size_t addrlen2) +{ + const char *a1 = (const char *) addr1; + const char *a2 = (const char *) addr2; + + if (NULL == a1) + return GNUNET_SYSERR; + if (0 >= addrlen1) + return GNUNET_SYSERR; + if (a1[addrlen1-1] != '\0') + return GNUNET_SYSERR; + + if (NULL == a2) + return GNUNET_SYSERR; + if (0 >= addrlen2) + return GNUNET_SYSERR; + if (a2[addrlen2-1] != '\0') + return GNUNET_SYSERR; + + if (addrlen1 != addrlen2) + return GNUNET_NO; + + if (0 == strcmp (addr1, addr2)) + return GNUNET_YES; + return GNUNET_NO; +} + + + +/* end of plugin_transport_http_common.c */ diff --git a/src/transport/plugin_transport_http_common.h b/src/transport/plugin_transport_http_common.h new file mode 100644 index 0000000..31676c2 --- /dev/null +++ b/src/transport/plugin_transport_http_common.h @@ -0,0 +1,168 @@ +/* + This file is part of GNUnet + (C) 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @file transport/plugin_transport_http_common.c + * @brief functionality shared by http client and server transport service plugin + * @author Matthias Wachs + */ + +#include "platform.h" +#include "gnunet_common.h" +#include "gnunet_transport_plugin.h" +/** + * Timeout values for testing + */ +#define TESTING GNUNET_NO + +#if TESTING + +#define HTTP_SERVER_NOT_VALIDATED_TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 3) +#define HTTP_CLIENT_NOT_VALIDATED_TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 3) +#define CLIENT_SESSION_TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 7) +#define SERVER_SESSION_TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 7) +#define TIMEOUT_LOG GNUNET_ERROR_TYPE_DEBUG + +#else + +#define HTTP_SERVER_NOT_VALIDATED_TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 15) +#define HTTP_CLIENT_NOT_VALIDATED_TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 15) +#define CLIENT_SESSION_TIMEOUT GNUNET_CONSTANTS_IDLE_CONNECTION_TIMEOUT +#define SERVER_SESSION_TIMEOUT GNUNET_CONSTANTS_IDLE_CONNECTION_TIMEOUT +#define TIMEOUT_LOG GNUNET_ERROR_TYPE_DEBUG + +#endif + +#define HTTP_DEFAULT_PORT 80 +#define HTTPS_DEFAULT_PORT 443 + + +struct SplittedHTTPAddress; + +struct SplittedHTTPAddress * +http_split_address (const char * addr); + +/** + * Convert the transports address to a nice, human-readable + * format. + * + * @param cls closure + * @param type name of the transport that generated the address + * @param addr one of the addresses of the host, NULL for the last address + * the specific address format depends on the transport + * @param addrlen length of the address + * @param numeric should (IP) addresses be displayed in numeric form? + * @param timeout after how long should we give up? + * @param asc function to call on each string + * @param asc_cls closure for asc + */ +void +http_common_plugin_address_pretty_printer (void *cls, const char *type, + const void *addr, size_t addrlen, + int numeric, + struct GNUNET_TIME_Relative timeout, + GNUNET_TRANSPORT_AddressStringCallback + asc, void *asc_cls); + +/** + * Function called for a quick conversion of the binary address to + * a numeric address. Note that the caller must not free the + * address and that the next call to this function is allowed + * to override the address again. + * + * @param cls closure + * @param addr binary address + * @param addrlen length of the address + * @return string representing the same address + */ +const char * +http_common_plugin_address_to_string (void *cls, + const void *addr, + size_t addrlen); + +/** + * Function called to convert a string address to + * a binary address. + * + * @param cls closure ('struct Plugin*') + * @param addr string address + * @param addrlen length of the address + * @param buf location to store the buffer + * If the function returns GNUNET_SYSERR, its contents are undefined. + * @param added length of created address + * @return GNUNET_OK on success, GNUNET_SYSERR on failure + */ +int +http_common_plugin_string_to_address (void *cls, + const char *addr, + uint16_t addrlen, + void **buf, + size_t *added); + + +/** + * Create a HTTP address from a socketaddr + * + * @param protocol protocol + * @param addr sockaddr * address + * @param addrlen length of the address + * @return the string + */ +char * +http_common_address_from_socket (const char *protocol, + const struct sockaddr *addr, + socklen_t addrlen); + +/** + * Create a socketaddr from a HTTP address + * + * @param addr sockaddr * address + * @param addrlen length of the address + * @param res the result: + * GNUNET_SYSERR, invalid input, + * GNUNET_YES: could convert to ip, + * GNUNET_NO: valid input but could not convert to ip (hostname?) + * @return the string + */ +struct sockaddr * +http_common_socket_from_address (const void *addr, size_t addrlen, int *res); + +/** + * Get the length of an address + * + * @param addr address + * @return the size + */ +size_t +http_common_address_get_size (const void *addr); + + +/** + * Compare addr1 to addr2 + * + * @param addr1 address1 + * @param addrlen1 address 1 length + * @param addr2 address2 + * @param addrlen2 address 2 length + * @return GNUNET_YES if equal, GNUNET_NO else + */ +size_t +http_common_cmp_addresses (const void *addr1, size_t addrlen1, const void *addr2, size_t addrlen2); +/* end of plugin_transport_http_common.c */ diff --git a/src/transport/plugin_transport_http_server.c b/src/transport/plugin_transport_http_server.c index 4b4f504..97a28b6 100644 --- a/src/transport/plugin_transport_http_server.c +++ b/src/transport/plugin_transport_http_server.c @@ -19,206 +19,460 @@ */ /** - * @file transport/plugin_transport_http.c - * @brief http transport service plugin + * @file transport/plugin_transport_http_server.c + * @brief HTTP/S server transport plugin * @author Matthias Wachs */ -#include "plugin_transport_http.h" +#include "platform.h" +#include "gnunet_common.h" +#include "gnunet_server_lib.h" +#include "gnunet_statistics_service.h" +#include "gnunet_transport_plugin.h" +#include "gnunet_nat_lib.h" +#include "plugin_transport_http_common.h" +#include "microhttpd.h" + +#if BUILD_HTTPS +#define LIBGNUNET_PLUGIN_TRANSPORT_INIT libgnunet_plugin_transport_https_server_init +#define LIBGNUNET_PLUGIN_TRANSPORT_DONE libgnunet_plugin_transport_https_server_done +#else +#define LIBGNUNET_PLUGIN_TRANSPORT_INIT libgnunet_plugin_transport_http_server_init +#define LIBGNUNET_PLUGIN_TRANSPORT_DONE libgnunet_plugin_transport_http_server_done +#endif #define HTTP_ERROR_RESPONSE "404 Not Found

Not Found

The requested URL was not found on this server.


" #define _RECEIVE 0 #define _SEND 1 -static struct Plugin * p; + +/* Enable output for debbuging URL's of incoming requests */ +#define DEBUG_URL_PARSE GNUNET_NO + /** - * Function that queries MHD's select sets and - * starts the task waiting for them. - * @param plugin plugin - * @param daemon_handle the MHD daemon handle - * @param now schedule now or with MHD delay - * @return gnunet task identifier + * Encapsulation of all of the state of the plugin. */ -static GNUNET_SCHEDULER_TaskIdentifier -server_schedule (struct Plugin *plugin, - struct MHD_Daemon *daemon_handle, - int now); - -static void -server_log (void *arg, const char *fmt, va_list ap) -{ - char text[1024]; +struct Plugin; - vsnprintf (text, sizeof (text), fmt, ap); - va_end (ap); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Server: %s\n", text); -} /** - * Check if incoming connection is accepted. - * NOTE: Here every connection is accepted - * @param cls plugin as closure - * @param addr address of incoming connection - * @param addr_len address length of incoming connection - * @return MHD_YES if connection is accepted, MHD_NO if connection is rejected - * + * Session handle for connections. */ -static int -server_accept_cb (void *cls, const struct sockaddr *addr, socklen_t addr_len) +struct Session +{ + /** + * Stored in a linked list. + */ + struct Session *next; + + /** + * Stored in a linked list. + */ + struct Session *prev; + + /** + * To whom are we talking to (set to our identity + * if we are still waiting for the welcome message) + */ + struct GNUNET_PeerIdentity target; + + /** + * Pointer to the global plugin struct. + */ + struct HTTP_Server_Plugin *plugin; + + /** + * next pointer for double linked list + */ + struct HTTP_Message *msg_head; + + /** + * previous pointer for double linked list + */ + struct HTTP_Message *msg_tail; + + /** + * Message stream tokenizer for incoming data + */ + struct GNUNET_SERVER_MessageStreamTokenizer *msg_tk; + + /** + * Client send handle + */ + struct ServerConnection *server_recv; + + /** + * Client send handle + */ + struct ServerConnection *server_send; + + /** + * Address + */ + void *addr; + + /** + * Address length + */ + size_t addrlen; + + /** + * Unique HTTP/S connection tag for this connection + */ + uint32_t tag; + + /** + * ATS network type in NBO + */ + uint32_t ats_address_network_type; + + /** + * Was session given to transport service? + */ + int session_passed; + + /** + * Did we immediately end the session in disconnect_cb + */ + int session_ended; + + /** + * Are incoming connection established at the moment + */ + int connect_in_progress; + + /** + * Absolute time when to receive data again + * Used for receive throttling + */ + struct GNUNET_TIME_Absolute next_receive; + + /** + * Session timeout task + */ + GNUNET_SCHEDULER_TaskIdentifier timeout_task; +}; + + +struct ServerConnection { - struct Plugin *plugin = cls; + /* _RECV or _SEND */ + int direction; - if (plugin->cur_connections <= plugin->max_connections) - return MHD_YES; - else - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "Server: Cannot accept new connections\n"); - return MHD_NO; - } -} + /* Should this connection get disconnected? GNUNET_YES/NO */ + int disconnect; + /* For PUT connections: Is this the first or last callback with size 0 */ + int connected; -#if BUILD_HTTPS -static char * -server_load_file (const char *file) + /* The session this server connection belongs to */ + struct Session *session; + + /* The MHD connection */ + struct MHD_Connection *mhd_conn; + + /* The MHD daemon */ + struct MHD_Daemon *mhd_daemon; +}; + + +/** + * Encapsulation of all of the state of the plugin. + */ +struct HTTP_Server_Plugin { - struct GNUNET_DISK_FileHandle *gn_file; - uint64_t fsize; - char *text = NULL; + /** + * Our environment. + */ + struct GNUNET_TRANSPORT_PluginEnvironment *env; + + /** + * Linked list head of open sessions. + */ + + struct Session *head; + + /** + * Linked list tail of open sessions. + */ + struct Session *tail; + + /** + * Plugin name + */ + char *name; + + /** + * Protocol + */ + char *protocol; + + /** + * External address + */ + char *external_hostname; + + /** + * Maximum number of sockets the plugin can use + * Each http inbound /outbound connections are two connections + */ + unsigned int max_connections; + + /** + * Current number of sockets the plugin can use + * Each http inbound /outbound connections are two connections + */ + unsigned int cur_connections; + + /** + * Did we immediately end the session in disconnect_cb + */ + int in_shutdown; + + /** + * Length of peer id + */ + int peer_id_length; + + /** + * External hostname the plugin can be connected to, can be different to + * the host's FQDN, used e.g. for reverse proxying + */ + char *ext_addr; + + /** + * Notify transport only about external address + */ + unsigned int external_only; + + /** + * External address length + */ + size_t ext_addr_len; + + /** + * use IPv6 + */ + uint16_t use_ipv6; + + /** + * use IPv4 + */ + uint16_t use_ipv4; + + /** + * Port used + */ + uint16_t port; + + /** + * Task calling transport service about external address + */ + GNUNET_SCHEDULER_TaskIdentifier notify_ext_task; + + /** + * NAT handle & address management + */ + struct GNUNET_NAT_Handle *nat; + + /** + * List of own addresses + */ + + /** + * IPv4 addresses DLL head + */ + struct HttpAddressWrapper *addr_head; + + /** + * IPv4 addresses DLL tail + */ + struct HttpAddressWrapper *addr_tail; + + /** + * IPv4 server socket to bind to + */ + struct sockaddr_in *server_addr_v4; + + /** + * IPv6 server socket to bind to + */ + struct sockaddr_in6 *server_addr_v6; + + /** + * MHD IPv4 task + */ + GNUNET_SCHEDULER_TaskIdentifier server_v4_task; + + /** + * MHD IPv6 task + */ + GNUNET_SCHEDULER_TaskIdentifier server_v6_task; + + /** + * The IPv4 server is scheduled to run asap + */ + int server_v4_immediately; + + /** + * The IPv6 server is scheduled to run asap + */ + int server_v6_immediately; + + /** + * MHD IPv4 daemon + */ + struct MHD_Daemon *server_v4; + + /** + * MHD IPv4 daemon + */ + struct MHD_Daemon *server_v6; - if (GNUNET_OK != GNUNET_DISK_file_size (file, - &fsize, GNUNET_NO, GNUNET_YES)) - return NULL; - text = GNUNET_malloc (fsize + 1); - gn_file = - GNUNET_DISK_file_open (file, GNUNET_DISK_OPEN_READ, - GNUNET_DISK_PERM_USER_READ); - if (gn_file == NULL) - { - GNUNET_free (text); - return NULL; - } - if (GNUNET_SYSERR == GNUNET_DISK_file_read (gn_file, text, fsize)) - { - GNUNET_free (text); - GNUNET_DISK_file_close (gn_file); - return NULL; - } - text[fsize] = '\0'; - GNUNET_DISK_file_close (gn_file); - return text; -} +#if BUILD_HTTPS + /** + * Crypto related + * + * Example: + * + * Use RC4-128 instead of AES: + * NONE:+VERS-TLS1.0:+ARCFOUR-128:+SHA1:+RSA:+COMP-NULL + * + */ + char *crypto_init; + + /** + * TLS key + */ + char *key; + + /** + * TLS certificate + */ + char *cert; #endif +}; -#if BUILD_HTTPS -static int -server_load_certificate (struct Plugin *plugin) +/** + * Wrapper to manage addresses + */ +struct HttpAddressWrapper { - int res = GNUNET_OK; + /** + * Linked list next + */ + struct HttpAddressWrapper *next; - char *key_file; - char *cert_file; + /** + * Linked list previous + */ + struct HttpAddressWrapper *prev; - /* Get crypto init string from config - * If not present just use default values */ + void *addr; - GNUNET_assert (GNUNET_OK == - GNUNET_CONFIGURATION_get_value_string (plugin->env->cfg, - plugin->name, - "CRYPTO_INIT", - &plugin->crypto_init)); + size_t addrlen; +}; - if (GNUNET_OK != - GNUNET_CONFIGURATION_get_value_filename (plugin->env->cfg, plugin->name, - "KEY_FILE", &key_file)) - { - key_file = GNUNET_strdup ("https_key.key"); - } - if (GNUNET_OK != - GNUNET_CONFIGURATION_get_value_filename (plugin->env->cfg, plugin->name, - "CERT_FILE", &cert_file)) - { - GNUNET_asprintf (&cert_file, "%s", "https_cert.crt"); - } +/** + * Message to send using http + */ +struct HTTP_Message +{ + /** + * next pointer for double linked list + */ + struct HTTP_Message *next; + + /** + * previous pointer for double linked list + */ + struct HTTP_Message *prev; + + /** + * buffer containing data to send + */ + char *buf; + + /** + * amount of data already sent + */ + size_t pos; + + /** + * buffer length + */ + size_t size; + + /** + * HTTP/S specific overhead + */ + size_t overhead; + + /** + * Continuation function to call once the transmission buffer + * has again space available. NULL if there is no + * continuation to call. + */ + GNUNET_TRANSPORT_TransmitContinuation transmit_cont; + + /** + * Closure for transmit_cont. + */ + void *transmit_cont_cls; +}; - /* read key & certificates from file */ - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Loading TLS certificate from key-file `%s' cert-file`%s'\n", - key_file, cert_file); - plugin->key = server_load_file (key_file); - plugin->cert = server_load_file (cert_file); +/** + * The http_server plugin handle + */ +static struct HTTP_Server_Plugin * p; - if ((plugin->key == NULL) || (plugin->cert == NULL)) - { - struct GNUNET_OS_Process *cert_creation; - GNUNET_free_non_null (plugin->key); - plugin->key = NULL; - GNUNET_free_non_null (plugin->cert); - plugin->cert = NULL; +/** + * Start session timeout for session s + * @param s the session + */ +static void +server_start_session_timeout (struct Session *s); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "No usable TLS certificate found, creating certificate\n"); - errno = 0; - cert_creation = - GNUNET_OS_start_process (GNUNET_NO, NULL, NULL, - "gnunet-transport-certificate-creation", - "gnunet-transport-certificate-creation", - key_file, cert_file, NULL); - if (cert_creation == NULL) - { - GNUNET_log_from (GNUNET_ERROR_TYPE_ERROR, plugin->name, - _ - ("Could not create a new TLS certificate, program `gnunet-transport-certificate-creation' could not be started!\n")); - GNUNET_free (key_file); - GNUNET_free (cert_file); - GNUNET_free_non_null (plugin->key); - plugin->key = NULL; - GNUNET_free_non_null (plugin->cert); - plugin->cert = NULL; - GNUNET_free_non_null (plugin->crypto_init); - plugin->crypto_init = NULL; +/** + * Increment session timeout due to activity for session s + * @param s the session + */ +static void +server_reschedule_session_timeout (struct Session *s); - return GNUNET_SYSERR; - } - GNUNET_assert (GNUNET_OK == GNUNET_OS_process_wait (cert_creation)); - GNUNET_OS_process_destroy (cert_creation); - plugin->key = server_load_file (key_file); - plugin->cert = server_load_file (cert_file); - } +/** + * Cancel timeout for session s + * @param s the session + */ +static void +server_stop_session_timeout (struct Session *s); - if ((plugin->key == NULL) || (plugin->cert == NULL)) - { - GNUNET_log_from (GNUNET_ERROR_TYPE_ERROR, plugin->name, - _ - ("No usable TLS certificate found and creating one failed!\n"), - "transport-https"); - GNUNET_free (key_file); - GNUNET_free (cert_file); - GNUNET_free_non_null (plugin->key); - plugin->key = NULL; - GNUNET_free_non_null (plugin->cert); - plugin->cert = NULL; - GNUNET_free_non_null (plugin->crypto_init); - plugin->crypto_init = NULL; +/** + * Disconnect a session s + * @param s the session + */ +static int +server_disconnect (struct Session *s); - return GNUNET_SYSERR; - } - GNUNET_free (key_file); - GNUNET_free (cert_file); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "TLS certificate loaded\n"); - return res; -} -#endif + +/** + * Does session s exist? + * + * @param plugin the plugin handle + * @param s the session + * @return GNUNET_YES on success, GNUNET_NO on error + */ +static int +server_exist_session (struct HTTP_Server_Plugin *plugin, struct Session *s); /** @@ -229,369 +483,847 @@ server_load_certificate (struct Plugin *plugin) * until timeout */ static void -server_reschedule (struct Plugin *plugin, struct MHD_Daemon *server, int now) +server_reschedule (struct HTTP_Server_Plugin *plugin, struct MHD_Daemon *server, + int now); + + +/** + * Function that can be used by the transport service to transmit + * a message using the plugin. Note that in the case of a + * peer disconnecting, the continuation MUST be called + * prior to the disconnect notification itself. This function + * will be called with this peer's HELLO message to initiate + * a fresh connection to another peer. + * + * @param cls closure + * @param session which session must be used + * @param msgbuf the message to transmit + * @param msgbuf_size number of bytes in 'msgbuf' + * @param priority how important is the message (most plugins will + * ignore message priority and just FIFO) + * @param to how long to wait at most for the transmission (does not + * require plugins to discard the message after the timeout, + * just advisory for the desired delay; most plugins will ignore + * this as well) + * @param cont continuation to call once the message has + * been transmitted (or if the transport is ready + * for the next transmission call; or if the + * peer disconnected...); can be NULL + * @param cont_cls closure for cont + * @return number of bytes used (on the physical network, with overheads); + * -1 on hard errors (i.e. address invalid); 0 is a legal value + * and does NOT mean that the message was not transmitted (DV) + */ +static ssize_t +http_server_plugin_send (void *cls, + struct Session *session, + const char *msgbuf, size_t msgbuf_size, + unsigned int priority, + struct GNUNET_TIME_Relative to, + GNUNET_TRANSPORT_TransmitContinuation cont, void *cont_cls) { - if ((server == plugin->server_v4) && (plugin->server_v4 != NULL)) - { - if (GNUNET_YES == plugin->server_v4_immediately) - return; /* No rescheduling, server will run asap */ + struct HTTP_Server_Plugin *plugin = cls; + struct HTTP_Message *msg; + int bytes_sent = 0; + char *stat_txt; - if (GNUNET_YES == now) - plugin->server_v4_immediately = GNUNET_YES; + GNUNET_assert (plugin != NULL); + GNUNET_assert (session != NULL); - if (plugin->server_v4_task != GNUNET_SCHEDULER_NO_TASK) - { - GNUNET_SCHEDULER_cancel (plugin->server_v4_task); - plugin->server_v4_task = GNUNET_SCHEDULER_NO_TASK; - } - plugin->server_v4_task = server_schedule (plugin, plugin->server_v4, now); + if (GNUNET_NO == server_exist_session (plugin, session)) + { + GNUNET_break (0); + return GNUNET_SYSERR; + } + if (NULL == session->server_send) + { + if (GNUNET_NO == session->connect_in_progress) + { + GNUNET_log_from (GNUNET_ERROR_TYPE_ERROR, session->plugin->name, + "Session %p/connection %p: Sending message with %u bytes to peer `%s' with FAILED\n", + session, session->server_send, + msgbuf_size, GNUNET_i2s (&session->target)); + GNUNET_break (0); + return GNUNET_SYSERR; + } + } + else + { + if (GNUNET_YES == session->server_send->disconnect) + return GNUNET_SYSERR; } - if ((server == plugin->server_v6) && (plugin->server_v6 != NULL)) + + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, session->plugin->name, + "Session %p/connection %p: Sending message with %u to peer `%s' with \n", + session, session->server_send, + msgbuf_size, GNUNET_i2s (&session->target)); + + /* create new message and schedule */ + bytes_sent = sizeof (struct HTTP_Message) + msgbuf_size; + msg = GNUNET_malloc (bytes_sent); + msg->next = NULL; + msg->size = msgbuf_size; + msg->pos = 0; + msg->buf = (char *) &msg[1]; + msg->transmit_cont = cont; + msg->transmit_cont_cls = cont_cls; + memcpy (msg->buf, msgbuf, msgbuf_size); + + GNUNET_CONTAINER_DLL_insert_tail (session->msg_head, session->msg_tail, msg); + + GNUNET_asprintf (&stat_txt, "# bytes currently in %s_server buffers", plugin->protocol); + GNUNET_STATISTICS_update (plugin->env->stats, + stat_txt, msgbuf_size, GNUNET_NO); + GNUNET_free (stat_txt); + + if (NULL != session->server_send) { - if (GNUNET_YES == plugin->server_v6_immediately) - return; /* No rescheduling, server will run asap */ + server_reschedule (session->plugin, + session->server_send->mhd_daemon, + GNUNET_YES); + server_reschedule_session_timeout (session); + } + return bytes_sent; +} - if (GNUNET_YES == now) - plugin->server_v6_immediately = GNUNET_YES; - if (plugin->server_v6_task != GNUNET_SCHEDULER_NO_TASK) + +/** + * Function that can be used to force the plugin to disconnect + * from the given peer and cancel all previous transmissions + * (and their continuationc). + * + * @param cls closure + * @param target peer from which to disconnect + */ +static void +http_server_plugin_disconnect (void *cls, const struct GNUNET_PeerIdentity *target) +{ + struct HTTP_Server_Plugin *plugin = cls; + struct Session *next = NULL; + struct Session *pos = NULL; + + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + "Transport tells me to disconnect `%s'\n", + GNUNET_i2s (target)); + + next = plugin->head; + while (NULL != (pos = next)) + { + next = pos->next; + if (0 == memcmp (target, &pos->target, sizeof (struct GNUNET_PeerIdentity))) { - GNUNET_SCHEDULER_cancel (plugin->server_v6_task); - plugin->server_v6_task = GNUNET_SCHEDULER_NO_TASK; + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + "Disconnecting session %p to `%s'\n", + pos, GNUNET_i2s (target)); + server_disconnect (pos); } - plugin->server_v6_task = server_schedule (plugin, plugin->server_v6, now); } + } + /** - * Callback called by MessageStreamTokenizer when a message has arrived - * @param cls current session as closure - * @param client clien - * @param message the message to be forwarded to transport service + * Another peer has suggested an address for this + * peer and transport plugin. Check that this could be a valid + * address. If so, consider adding it to the list + * of addresses. + * + * @param cls closure + * @param addr pointer to the address + * @param addrlen length of addr + * @return GNUNET_OK if this is a plausible address for this peer + * and transport */ static int -server_receive_mst_cb (void *cls, void *client, - const struct GNUNET_MessageHeader *message) +http_server_plugin_address_suggested (void *cls, const void *addr, + size_t addrlen) { - struct Session *s = cls; + struct HTTP_Server_Plugin *plugin = cls; + struct HttpAddressWrapper *next; + struct HttpAddressWrapper *pos; - GNUNET_assert (NULL != p); - if (GNUNET_NO == exist_session(p, s)) + + if ((NULL != plugin->ext_addr) && + GNUNET_YES == (http_common_cmp_addresses (addr, addrlen, + plugin->ext_addr, plugin->ext_addr_len))) return GNUNET_OK; - struct Plugin *plugin = s->plugin; - struct GNUNET_TIME_Relative delay; + next = plugin->addr_head; + while (NULL != (pos = next)) + { + next = pos->next; + if (GNUNET_YES == (http_common_cmp_addresses(addr, + addrlen, + pos->addr, + pos->addrlen))) + return GNUNET_OK; - delay = http_plugin_receive (s, &s->target, message, s, s->addr, s->addrlen); + } - s->next_receive = - GNUNET_TIME_absolute_add (GNUNET_TIME_absolute_get (), delay); + return GNUNET_NO; +} - if (delay.rel_value > 0) - { - GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, - "Server: peer `%s' address `%s' next read delayed for %llu ms\n", - GNUNET_i2s (&s->target), - http_plugin_address_to_string (NULL, s->addr, s->addrlen), - delay); - } - return GNUNET_OK; + +/** + * Creates a new outbound session the transport + * service will use to send data to the peer + * + * Since HTTP/S server cannot create sessions, always return NULL + * + * @param cls the plugin + * @param address the address + * @return always NULL + */ +static struct Session * +http_server_plugin_get_session (void *cls, + const struct GNUNET_HELLO_Address *address) +{ + return NULL; } /** - * Callback called by MHD when it needs data to send - * @param cls current session - * @param pos position in buffer - * @param buf the buffer to write data to - * @param max max number of bytes available in buffer - * @return bytes written to buffer + * Deleting the session + * Must not be used afterwards + * + * @param s the session to delete */ -static ssize_t -server_send_callback (void *cls, uint64_t pos, char *buf, size_t max) +static void +server_delete_session (struct Session *s) { - struct Session *s = cls; - ssize_t bytes_read = 0; - struct HTTP_Message *msg; + struct HTTP_Server_Plugin *plugin = s->plugin; + server_stop_session_timeout(s); - GNUNET_assert (NULL != p); - if (GNUNET_NO == exist_session(p, s)) - return 0; - msg = s->msg_head; - if (NULL != msg) + GNUNET_CONTAINER_DLL_remove (plugin->head, plugin->tail, s); + struct HTTP_Message *msg = s->msg_head; + struct HTTP_Message *tmp = NULL; + + while (msg != NULL) { - /* sending */ - bytes_read = GNUNET_MIN (msg->size - msg->pos, - max); - memcpy (buf, &msg->buf[msg->pos], bytes_read); - msg->pos += bytes_read; + tmp = msg->next; - /* removing message */ - if (msg->pos == msg->size) + GNUNET_CONTAINER_DLL_remove (s->msg_head, s->msg_tail, msg); + if (msg->transmit_cont != NULL) { - GNUNET_CONTAINER_DLL_remove (s->msg_head, s->msg_tail, msg); - if (NULL != msg->transmit_cont) - msg->transmit_cont (msg->transmit_cont_cls, &s->target, GNUNET_OK); - GNUNET_free (msg); + msg->transmit_cont (msg->transmit_cont_cls, &s->target, GNUNET_SYSERR, + msg->size, msg->pos + msg->overhead); } + GNUNET_free (msg); + msg = tmp; } - GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, s->plugin->name, - "Server: %p: sent %u bytes\n", s, bytes_read); - return bytes_read; + + if (s->msg_tk != NULL) + { + GNUNET_SERVER_mst_destroy (s->msg_tk); + s->msg_tk = NULL; + } + GNUNET_free (s->addr); + GNUNET_free_non_null (s->server_recv); + GNUNET_free_non_null (s->server_send); + GNUNET_free (s); + + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + "Session %p destroyed\n", s); } -static struct Session * -server_lookup_session (struct Plugin *plugin, - struct ServerConnection * sc) +/** +* Cancel timeout for session s +* +* @param s the session +*/ +static void +server_stop_session_timeout (struct Session *s) { - struct Session *s; + GNUNET_assert (NULL != s); + + if (GNUNET_SCHEDULER_NO_TASK != s->timeout_task) + { + GNUNET_SCHEDULER_cancel (s->timeout_task); + s->timeout_task = GNUNET_SCHEDULER_NO_TASK; + GNUNET_log (TIMEOUT_LOG, "Timeout stopped for session %p\n", s); + } +} - for (s = plugin->head; NULL != s; s = s->next) - if ((s->server_recv == sc) || (s->server_send == sc)) - return s; - for (s = plugin->server_semi_head; NULL != s; s = s->next) - if ((s->server_recv == sc) || (s->server_send == sc)) - return s; - return NULL; + +/** + * Function that queries MHD's select sets and + * starts the task waiting for them. + * @param plugin plugin + * @param daemon_handle the MHD daemon handle + * @param now schedule immediately + * @return gnunet task identifier + */ +static GNUNET_SCHEDULER_TaskIdentifier +server_schedule (struct HTTP_Server_Plugin *plugin, + struct MHD_Daemon *daemon_handle, + int now); + + +/** + * Reschedule the execution of both IPv4 and IPv6 server + * @param plugin the plugin + * @param server which server to schedule v4 or v6? + * @param now GNUNET_YES to schedule execution immediately, GNUNET_NO to wait + * until timeout + */ +static void +server_reschedule (struct HTTP_Server_Plugin *plugin, struct MHD_Daemon *server, + int now) +{ + if ((server == plugin->server_v4) && (plugin->server_v4 != NULL)) + { + if (GNUNET_YES == plugin->server_v4_immediately) + return; /* No rescheduling, server will run asap */ + + if (GNUNET_YES == now) + plugin->server_v4_immediately = GNUNET_YES; + + if (plugin->server_v4_task != GNUNET_SCHEDULER_NO_TASK) + { + GNUNET_SCHEDULER_cancel (plugin->server_v4_task); + plugin->server_v4_task = GNUNET_SCHEDULER_NO_TASK; + } + plugin->server_v4_task = server_schedule (plugin, plugin->server_v4, now); + } + + if ((server == plugin->server_v6) && (plugin->server_v6 != NULL)) + { + if (GNUNET_YES == plugin->server_v6_immediately) + return; /* No rescheduling, server will run asap */ + + if (GNUNET_YES == now) + plugin->server_v6_immediately = GNUNET_YES; + + if (plugin->server_v6_task != GNUNET_SCHEDULER_NO_TASK) + { + GNUNET_SCHEDULER_cancel (plugin->server_v6_task); + plugin->server_v6_task = GNUNET_SCHEDULER_NO_TASK; + } + plugin->server_v6_task = server_schedule (plugin, plugin->server_v6, now); + } +} + + +/** + * Disconnect session s + * + * @param s the session + * @return GNUNET_OK on success + */ +static int +server_disconnect (struct Session *s) +{ + struct ServerConnection * send = NULL; + struct ServerConnection * recv = NULL; + + if (GNUNET_NO == server_exist_session (p, s)) + { + GNUNET_break (0); + return GNUNET_SYSERR; + } + + send = (struct ServerConnection *) s->server_send; + if (s->server_send != NULL) + { + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, s->plugin->name, + "Server: %p / %p Terminating inbound PUT session to peer `%s'\n", + s, s->server_send, GNUNET_i2s (&s->target)); + + send->disconnect = GNUNET_YES; +#if MHD_VERSION >= 0x00090E00 + MHD_set_connection_option (send->mhd_conn, MHD_CONNECTION_OPTION_TIMEOUT, + 1); +#endif + server_reschedule (s->plugin, send->mhd_daemon, GNUNET_YES); + } + + recv = (struct ServerConnection *) s->server_recv; + if (recv != NULL) + { + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, s->plugin->name, + "Server: %p / %p Terminating inbound GET session to peer `%s'\n", + s, s->server_recv, GNUNET_i2s (&s->target)); + + recv->disconnect = GNUNET_YES; +#if MHD_VERSION >= 0x00090E00 + MHD_set_connection_option (recv->mhd_conn, MHD_CONNECTION_OPTION_TIMEOUT, + 1); +#endif + server_reschedule (s->plugin, recv->mhd_daemon, GNUNET_YES); + } + return GNUNET_OK; +} + +static void +server_mhd_connection_timeout (struct HTTP_Server_Plugin *plugin, struct Session *s, int to) +{ +#if MHD_VERSION >= 0x00090E00 + /* Setting timeouts for other connections */ + if (s->server_recv != NULL) + { + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + "Setting timeout for %p to %u sec.\n", s->server_recv, to); + MHD_set_connection_option (s->server_recv->mhd_conn, + MHD_CONNECTION_OPTION_TIMEOUT, + to); + server_reschedule (plugin, s->server_recv->mhd_daemon, GNUNET_NO); + } + if (s->server_send != NULL) + { + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + "Setting timeout for %p to %u sec.\n", s->server_send, to); + MHD_set_connection_option (s->server_send->mhd_conn, + MHD_CONNECTION_OPTION_TIMEOUT, + to); + server_reschedule (plugin, s->server_send->mhd_daemon, GNUNET_NO); + } +#endif +} + +/** + * Parse incoming URL for tag and target + * + * @param plugin plugin + * @param url incoming url + * @param target where to store the target + * @param tag where to store the tag + * @return GNUNET_OK on success, GNUNET_SYSERR on error + */ + +static int +server_parse_url (struct HTTP_Server_Plugin *plugin, const char * url, struct GNUNET_PeerIdentity * target, uint32_t *tag) +{ + char * tag_start = NULL; + char * tag_end = NULL; + char * target_start = NULL; + char * separator = NULL; + char hash[plugin->peer_id_length+1]; + int hash_length; + unsigned long int ctag; + + /* URL parsing + * URL is valid if it is in the form [prefix with (multiple) '/'][peerid[103];tag]*/ + + if (NULL == url) + { + GNUNET_break (0); + return GNUNET_SYSERR; + } + /* convert tag */ + + /* find separator */ + separator = strrchr (url, ';'); + + if (NULL == separator) + { + if (DEBUG_URL_PARSE) GNUNET_break (0); + return GNUNET_SYSERR; + } + tag_start = separator + 1; + + if (strlen (tag_start) == 0) + { + /* No tag after separator */ + if (DEBUG_URL_PARSE) GNUNET_break (0); + return GNUNET_SYSERR; + } + ctag = strtoul (tag_start, &tag_end, 10); + if (ctag == 0) + { + /* tag == 0 , invalid */ + if (DEBUG_URL_PARSE) GNUNET_break (0); + return GNUNET_SYSERR; + } + if ((ctag == ULONG_MAX) && (ERANGE == errno)) + { + /* out of range: > ULONG_MAX */ + if (DEBUG_URL_PARSE) GNUNET_break (0); + return GNUNET_SYSERR; + } + if (ctag > UINT32_MAX) + { + /* out of range: > UINT32_MAX */ + if (DEBUG_URL_PARSE) GNUNET_break (0); + return GNUNET_SYSERR; + } + (*tag) = (uint32_t) ctag; + if (NULL == tag_end) + { + /* no char after tag */ + if (DEBUG_URL_PARSE) GNUNET_break (0); + return GNUNET_SYSERR; + } + if (url[strlen(url)] != tag_end[0]) + { + /* there are more not converted chars after tag */ + if (DEBUG_URL_PARSE) GNUNET_break (0); + return GNUNET_SYSERR; + } + if (DEBUG_URL_PARSE) + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + "Found tag `%u' in url\n", (*tag)); + + /* convert peer id */ + target_start = strrchr (url, '/'); + if (NULL == target_start) + { + /* no leading '/' */ + target_start = (char *) url; + } + target_start++; + hash_length = separator - target_start; + if (hash_length != plugin->peer_id_length) + { + /* no char after tag */ + if (DEBUG_URL_PARSE) GNUNET_break (0); + return GNUNET_SYSERR; + } + memcpy (hash, target_start, hash_length); + hash[hash_length] = '\0'; + + if (GNUNET_OK != GNUNET_CRYPTO_hash_from_string ((const char *) hash, &(target->hashPubKey))) + { + /* hash conversion failed */ + if (DEBUG_URL_PARSE) GNUNET_break (0); + return GNUNET_SYSERR; + } + + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + "Found target `%s' in url\n", GNUNET_h2s_full(&target->hashPubKey)); + return GNUNET_OK; } +/** + * Lookup a mhd connection and create one if none is found + * + * @param plugin the plugin handle + * @param mhd_connection the incoming mhd_connection + * @param url incoming requested URL + * @param method PUT or GET + * @return the server connecetion + */ static struct ServerConnection * -server_lookup_serverconnection (struct Plugin *plugin, +server_lookup_connection (struct HTTP_Server_Plugin *plugin, struct MHD_Connection *mhd_connection, const char *url, const char *method) { struct Session *s = NULL; - struct Session *t; struct ServerConnection *sc = NULL; const union MHD_ConnectionInfo *conn_info; struct GNUNET_ATS_Information ats; - struct IPv4HttpAddress a4; - struct IPv6HttpAddress a6; - struct sockaddr_in *s4; - struct sockaddr_in6 *s6; - void *a; - size_t a_len; + + char *addr; + size_t addr_len; + struct GNUNET_PeerIdentity target; - int check = GNUNET_NO; uint32_t tag = 0; int direction = GNUNET_SYSERR; + int to; conn_info = MHD_get_connection_info (mhd_connection, - MHD_CONNECTION_INFO_CLIENT_ADDRESS); + MHD_CONNECTION_INFO_CLIENT_ADDRESS); if ((conn_info->client_addr->sa_family != AF_INET) && (conn_info->client_addr->sa_family != AF_INET6)) return NULL; + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + "New %s connection from %s\n", method, url); - if ((strlen (&url[1]) >= 105) && (url[104] == ';')) + if (GNUNET_SYSERR == server_parse_url (plugin, url, &target, &tag)) { - char hash[104]; - char *tagc = (char *) &url[105]; - - memcpy (&hash, &url[1], 103); - hash[103] = '\0'; - if (GNUNET_OK == - GNUNET_CRYPTO_hash_from_string ((const char *) &hash, - &(target.hashPubKey))) - { - tag = strtoul (tagc, NULL, 10); - if (tagc > 0) - check = GNUNET_YES; - } + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + "Invalid url %s\n", url); + return NULL; } - if (0 == strcmp (MHD_HTTP_METHOD_PUT, method)) direction = _RECEIVE; else if (0 == strcmp (MHD_HTTP_METHOD_GET, method)) direction = _SEND; else { - GNUNET_break_op (0); - goto error; + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + "Invalid method %s connection from %s\n", method, url); + return NULL; } - - if (check == GNUNET_NO) - goto error; - plugin->cur_connections++; GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, - "Server: New %s connection from %s with tag %u\n", + "New %s connection from %s with tag %u (%u of %u)\n", method, - GNUNET_i2s (&target), tag); - + GNUNET_i2s (&target), tag, + plugin->cur_connections, plugin->max_connections); /* find duplicate session */ - t = plugin->head; - while (t != NULL) - { - if ((t->inbound) && - (0 == memcmp (&t->target, &target, sizeof (struct GNUNET_PeerIdentity))) - && - /* FIXME add source address comparison */ - (t->tag == tag)) + s = plugin->head; + while (s != NULL) + { + if ((0 == memcmp (&s->target, &target, sizeof (struct GNUNET_PeerIdentity))) && + (s->tag == tag)) break; - t = t->next; + s = s->next; } - if (t != NULL) + if (s != NULL) { - GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, - "Server: Duplicate session, dismissing new connection from peer `%s'\n", - GNUNET_i2s (&target)); - goto error; - } - - /* find semi-session */ - t = plugin->server_semi_head; + if ((_RECEIVE == direction) && (NULL != s->server_recv)) + { + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + "Duplicate PUT connection from `%s' tag %u, dismissing new connection\n", + GNUNET_i2s (&target), + tag); + return NULL; - while (t != NULL) - { - /* FIXME add source address comparison */ - if ((0 == memcmp (&t->target, &target, sizeof (struct GNUNET_PeerIdentity))) - && (t->tag == tag)) + } + if ((_SEND == direction) && (NULL != s->server_send)) { - break; + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + "Duplicate GET connection from `%s' tag %u, dismissing new connection\n", + GNUNET_i2s (&target), + tag); + return NULL; } - t = t->next; - } - - if (t == NULL) - goto create; - GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, - "Server: Found existing semi-session for `%s'\n", - GNUNET_i2s (&target)); - - if ((direction == _SEND) && (t->server_send != NULL)) - { - GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, - "Server: Duplicate GET session, dismissing new connection from peer `%s'\n", - GNUNET_i2s (&target)); - goto error; } else { - s = t; - GNUNET_CONTAINER_DLL_remove (plugin->server_semi_head, - plugin->server_semi_tail, s); - GNUNET_CONTAINER_DLL_insert (plugin->head, plugin->tail, s); - GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, - "Server: Found matching semi-session, merging session for peer `%s'\n", - GNUNET_i2s (&target)); - - plugin->inbound_sessions ++; - GNUNET_STATISTICS_set (plugin->env->stats, - "# HTTP inbound sessions", - plugin->inbound_sessions, - GNUNET_NO); - GNUNET_assert (NULL != s); - goto found; - } - if ((direction == _RECEIVE) && (t->server_recv != NULL)) - { + /* create new session */ + switch (conn_info->client_addr->sa_family) + { + case (AF_INET): + addr = http_common_address_from_socket (plugin->protocol, conn_info->client_addr, sizeof (struct sockaddr_in)); + addr_len = http_common_address_get_size (addr); + ats = plugin->env->get_address_type (plugin->env->cls, conn_info->client_addr, sizeof (struct sockaddr_in)); + break; + case (AF_INET6): + addr = http_common_address_from_socket (plugin->protocol, conn_info->client_addr, sizeof (struct sockaddr_in6)); + addr_len = http_common_address_get_size (addr); + ats = plugin->env->get_address_type (plugin->env->cls, conn_info->client_addr, sizeof (struct sockaddr_in6)); + break; + default: + GNUNET_break (0); + return NULL; + } GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, - "Server: Duplicate PUT session, dismissing new connection from peer `%s'\n", - GNUNET_i2s (&target)); - goto error; - } - else - { - s = t; - GNUNET_CONTAINER_DLL_remove (plugin->server_semi_head, - plugin->server_semi_tail, s); + "Creating new session for peer `%s' connecting from `%s'\n", + GNUNET_i2s (&target), + http_common_plugin_address_to_string (NULL, addr, addr_len)); + + s = GNUNET_malloc (sizeof (struct Session)); + memcpy (&s->target, &target, sizeof (struct GNUNET_PeerIdentity)); + s->plugin = plugin; + s->addr = addr; + s->addrlen = addr_len; + s->ats_address_network_type = ats.value; + s->next_receive = GNUNET_TIME_UNIT_ZERO_ABS; + s->tag = tag; + s->server_recv = NULL; + s->server_send = NULL; + s->session_passed = GNUNET_NO; + s->session_ended = GNUNET_NO; + s->connect_in_progress = GNUNET_YES; + server_start_session_timeout(s); GNUNET_CONTAINER_DLL_insert (plugin->head, plugin->tail, s); - GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, - "Server: Found matching semi-session, merging session for peer `%s'\n", - GNUNET_i2s (&target)); - plugin->inbound_sessions ++; - GNUNET_STATISTICS_set (plugin->env->stats, - "# HTTP inbound sessions", - plugin->inbound_sessions, - GNUNET_NO); - GNUNET_assert (NULL != s); - goto found; - } - -create: -/* create new session */ - GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, - "Server: Creating new session for peer `%s' \n", - GNUNET_i2s (&target)); - switch (conn_info->client_addr->sa_family) - { - case (AF_INET): - s4 = ((struct sockaddr_in *) conn_info->client_addr); - a4.u4_port = s4->sin_port; - memcpy (&a4.ipv4_addr, &s4->sin_addr, sizeof (struct in_addr)); - a = &a4; - a_len = sizeof (struct IPv4HttpAddress); - ats = plugin->env->get_address_type (plugin->env->cls, (const struct sockaddr *) s4, sizeof (struct sockaddr_in)); - break; - case (AF_INET6): - s6 = ((struct sockaddr_in6 *) conn_info->client_addr); - a6.u6_port = s6->sin6_port; - memcpy (&a6.ipv6_addr, &s6->sin6_addr, sizeof (struct in6_addr)); - a = &a6; - a_len = sizeof (struct IPv6HttpAddress); - ats = plugin->env->get_address_type (plugin->env->cls, (const struct sockaddr *) s6, sizeof (struct sockaddr_in6)); - break; - default: - GNUNET_break (0); - goto error; } - s = create_session (plugin, &target, a, a_len); - GNUNET_assert (NULL != s); - s->ats_address_network_type = ats.value; - s->inbound = GNUNET_YES; - s->next_receive = GNUNET_TIME_UNIT_ZERO_ABS; - s->tag = tag; - s->server_recv = NULL; - s->server_send = NULL; - - GNUNET_CONTAINER_DLL_insert (plugin->server_semi_head, - plugin->server_semi_tail, s); - goto found; - -error: - GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, - "Server: Invalid connection request\n"); - return NULL; - -found: sc = GNUNET_malloc (sizeof (struct ServerConnection)); + if (conn_info->client_addr->sa_family == AF_INET) + sc->mhd_daemon = plugin->server_v4; + if (conn_info->client_addr->sa_family == AF_INET6) + sc->mhd_daemon = plugin->server_v6; sc->mhd_conn = mhd_connection; sc->direction = direction; + sc->connected = GNUNET_NO; sc->session = s; if (direction == _SEND) s->server_send = sc; if (direction == _RECEIVE) s->server_recv = sc; -#if MHD_VERSION >= 0x00090E00 - int to = (GNUNET_CONSTANTS_IDLE_CONNECTION_TIMEOUT.rel_value / 1000); + if ((NULL != s->server_send) && (NULL != s->server_recv)) + s->connect_in_progress = GNUNET_NO; /* PUT and GET are connected */ - GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, - "Server: Setting timeout for %p to %u sec.\n", sc, to); - MHD_set_connection_option (mhd_connection, MHD_CONNECTION_OPTION_TIMEOUT, to); - - struct MHD_Daemon *d = NULL; - - if (s->addrlen == sizeof (struct IPv6HttpAddress)) - d = plugin->server_v6; - if (s->addrlen == sizeof (struct IPv4HttpAddress)) - d = plugin->server_v4; +#if MHD_VERSION >= 0x00090E00 + if ((NULL == s->server_recv) || (NULL == s->server_send)) + { + to = (HTTP_SERVER_NOT_VALIDATED_TIMEOUT.rel_value / 1000); + MHD_set_connection_option (mhd_connection, MHD_CONNECTION_OPTION_TIMEOUT, to); + server_reschedule (plugin, sc->mhd_daemon, GNUNET_NO); + } + else + { + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + "Session %p for peer `%s' fully connected\n", + s, GNUNET_i2s (&target)); + to = (SERVER_SESSION_TIMEOUT.rel_value / 1000); + server_mhd_connection_timeout (plugin, s, to); + } - server_reschedule (plugin, d, GNUNET_NO); + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + "Setting timeout for %p to %u sec.\n", sc, to); #endif return sc; } + +/** + * Lookup a session for a server connection + * + * @param plugin the plugin + * @param sc the server connection + * @return the session found or NULL + */ +static struct Session * +server_lookup_session (struct HTTP_Server_Plugin *plugin, + struct ServerConnection * sc) +{ + struct Session *s; + + for (s = plugin->head; NULL != s; s = s->next) + if ((s->server_recv == sc) || (s->server_send == sc)) + return s; + return NULL; +} + +int +server_exist_session (struct HTTP_Server_Plugin *plugin, struct Session *s) +{ + struct Session * head; + + GNUNET_assert (NULL != plugin); + GNUNET_assert (NULL != s); + + for (head = plugin->head; head != NULL; head = head->next) + { + if (head == s) + return GNUNET_YES; + } + return GNUNET_NO; +} + + +/** + * Callback called by MHD when it needs data to send + * + * @param cls current session + * @param pos position in buffer + * @param buf the buffer to write data to + * @param max max number of bytes available in buffer + * @return bytes written to buffer + */ +static ssize_t +server_send_callback (void *cls, uint64_t pos, char *buf, size_t max) +{ + struct Session *s = cls; + ssize_t bytes_read = 0; + struct HTTP_Message *msg; + char *stat_txt; + + GNUNET_assert (NULL != p); + if (GNUNET_NO == server_exist_session (p, s)) + return 0; + msg = s->msg_head; + if (NULL != msg) + { + /* sending */ + bytes_read = GNUNET_MIN (msg->size - msg->pos, + max); + memcpy (buf, &msg->buf[msg->pos], bytes_read); + msg->pos += bytes_read; + + /* removing message */ + if (msg->pos == msg->size) + { + GNUNET_CONTAINER_DLL_remove (s->msg_head, s->msg_tail, msg); + if (NULL != msg->transmit_cont) + msg->transmit_cont (msg->transmit_cont_cls, &s->target, GNUNET_OK, + msg->size, msg->size + msg->overhead); + GNUNET_free (msg); + } + } + if (0 < bytes_read) + { + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, s->plugin->name, + "Sent %u bytes to peer `%s' with session %p \n", bytes_read, GNUNET_i2s (&s->target), s); + GNUNET_asprintf (&stat_txt, "# bytes currently in %s_server buffers", p->protocol); + GNUNET_STATISTICS_update (p->env->stats, + stat_txt, -bytes_read, GNUNET_NO); + GNUNET_free (stat_txt); + GNUNET_asprintf (&stat_txt, "# bytes transmitted via %s_server", p->protocol); + GNUNET_STATISTICS_update (p->env->stats, + stat_txt, bytes_read, GNUNET_NO); + GNUNET_free (stat_txt); + } + return bytes_read; +} + + +/** + * Callback called by MessageStreamTokenizer when a message has arrived + * + * @param cls current session as closure + * @param client client + * @param message the message to be forwarded to transport service + * @return GNUNET_OK + */ +static int +server_receive_mst_cb (void *cls, void *client, + const struct GNUNET_MessageHeader *message) +{ + struct Session *s = cls; + struct GNUNET_ATS_Information atsi[2]; + struct GNUNET_TIME_Relative delay; + char *stat_txt; + + GNUNET_assert (NULL != p); + if (GNUNET_NO == server_exist_session(p, s)) + return GNUNET_OK; + + struct HTTP_Server_Plugin *plugin = s->plugin; + + atsi[0].type = htonl (GNUNET_ATS_QUALITY_NET_DISTANCE); + atsi[0].value = htonl (1); + atsi[1].type = htonl (GNUNET_ATS_NETWORK_TYPE); + atsi[1].value = s->ats_address_network_type; + GNUNET_break (s->ats_address_network_type != ntohl (GNUNET_ATS_NET_UNSPECIFIED)); + + + delay = plugin->env->receive (plugin->env->cls, + &s->target, + message, + (const struct GNUNET_ATS_Information *) &atsi, 2, + s, s->addr, s->addrlen); + + GNUNET_asprintf (&stat_txt, "# bytes received via %s_server", plugin->protocol); + GNUNET_STATISTICS_update (plugin->env->stats, + stat_txt, ntohs (message->size), GNUNET_NO); + GNUNET_free (stat_txt); + + s->session_passed = GNUNET_YES; + s->next_receive = GNUNET_TIME_absolute_add (GNUNET_TIME_absolute_get (), delay); + if (delay.rel_value > 0) + { + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + "Peer `%s' address `%s' next read delayed for %llu ms\n", + GNUNET_i2s (&s->target), + http_common_plugin_address_to_string (NULL, s->addr, s->addrlen), + delay); + } + server_reschedule_session_timeout (s); + return GNUNET_OK; +} + + /** - * Process GET or PUT request received via MHD. For - * GET, queue response that will send back our pending - * messages. For PUT, process incoming data and send - * to GNUnet core. In either case, check if a session - * already exists and create a new one if not. + * MHD callback for a new incoming connection + * + * @param cls the plugin handle + * @param mhd_connection the mhd connection + * @param url the requested URL + * @param method GET or PUT + * @param version HTTP version + * @param upload_data upload data + * @param upload_data_size sizeof upload data + * @param httpSessionCache the session cache to remember the connection + * @return MHD_YES if connection is accepted, MHD_NO on reject */ static int server_access_cb (void *cls, struct MHD_Connection *mhd_connection, @@ -599,24 +1331,34 @@ server_access_cb (void *cls, struct MHD_Connection *mhd_connection, const char *upload_data, size_t * upload_data_size, void **httpSessionCache) { - struct Plugin *plugin = cls; + struct HTTP_Server_Plugin *plugin = cls; + int res = MHD_YES; + struct ServerConnection *sc = *httpSessionCache; struct Session *s; struct MHD_Response *response; - int res = MHD_YES; + + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + _("Access from connection %p (%u of %u) for `%s' `%s' url `%s' with upload data size %u\n"), + sc, + plugin->cur_connections, plugin->max_connections, + method, version, url, (*upload_data_size)); GNUNET_assert (cls != NULL); if (sc == NULL) { /* new connection */ - sc = server_lookup_serverconnection (plugin, mhd_connection, url, method); + sc = server_lookup_connection (plugin, mhd_connection, url, method); if (sc != NULL) + { (*httpSessionCache) = sc; + } else { - response = - MHD_create_response_from_data (strlen (HTTP_ERROR_RESPONSE), - HTTP_ERROR_RESPONSE, MHD_NO, MHD_NO); + response = MHD_create_response_from_data (strlen (HTTP_ERROR_RESPONSE), HTTP_ERROR_RESPONSE, MHD_NO, MHD_NO); + MHD_add_response_header (response, + MHD_HTTP_HEADER_CONTENT_TYPE, + "text/html"); res = MHD_queue_response (mhd_connection, MHD_HTTP_NOT_FOUND, response); MHD_destroy_response (response); return res; @@ -635,65 +1377,81 @@ server_access_cb (void *cls, struct MHD_Connection *mhd_connection, /* existing connection */ sc = (*httpSessionCache); s = sc->session; - GNUNET_assert (NULL != s); - /* connection is to be disconnected */ if (sc->disconnect == GNUNET_YES) { - /* Sent HTTP/1.1: 200 OK as PUT Response\ */ - response = - MHD_create_response_from_data (strlen ("Thank you!"), "Thank you!", + /* Sent HTTP/1.1: 200 OK as response */ + response = MHD_create_response_from_data (strlen ("Thank you!"), + "Thank you!", MHD_NO, MHD_NO); res = MHD_queue_response (mhd_connection, MHD_HTTP_OK, response); MHD_destroy_response (response); return MHD_YES; } - GNUNET_assert (s != NULL); - /* Check if both directions are connected */ - if ((sc->session->server_recv == NULL) || (sc->session->server_send == NULL)) - { - /* Delayed read from since not both semi-connections are connected */ - return MHD_YES; - } if (sc->direction == _SEND) { - response = - MHD_create_response_from_callback (-1, 32 * 1024, &server_send_callback, - s, NULL); + response = MHD_create_response_from_callback (MHD_SIZE_UNKNOWN, + 32 * 1024, + &server_send_callback, s, + NULL); MHD_queue_response (mhd_connection, MHD_HTTP_OK, response); MHD_destroy_response (response); return MHD_YES; } if (sc->direction == _RECEIVE) { - if (*upload_data_size == 0) + if ((*upload_data_size == 0) && (sc->connected == GNUNET_NO)) { + /* (*upload_data_size == 0) first callback when header are passed */ GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, - "Server: Peer `%s' PUT on address `%s' connected\n", + "Session %p / Connection %p: Peer `%s' PUT on address `%s' connected\n", + s, sc, GNUNET_i2s (&s->target), - http_plugin_address_to_string (NULL, s->addr, - s->addrlen)); + http_common_plugin_address_to_string (NULL, + s->addr, + s->addrlen)); + sc->connected = GNUNET_YES; return MHD_YES; } - - /* Receiving data */ - if ((*upload_data_size > 0)) + else if ((*upload_data_size == 0) && (sc->connected == GNUNET_YES)) + { + /* (*upload_data_size == 0) when upload is complete */ + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + "Session %p / Connection %p: Peer `%s' PUT on address `%s' finished upload\n", + s, sc, + GNUNET_i2s (&s->target), + http_common_plugin_address_to_string (NULL, + s->addr, + s->addrlen)); + sc->connected = GNUNET_NO; + /* Sent HTTP/1.1: 200 OK as PUT Response\ */ + response = MHD_create_response_from_data (strlen ("Thank you!"), + "Thank you!", + MHD_NO, MHD_NO); + res = MHD_queue_response (mhd_connection, MHD_HTTP_OK, response); + MHD_destroy_response (response); + return MHD_YES; + } + else if ((*upload_data_size > 0) && (sc->connected == GNUNET_YES)) { + /* (*upload_data_size > 0) for every segment received */ GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, - "Server: peer `%s' PUT on address `%s' received %u bytes\n", + "Session %p / Connection %p: Peer `%s' PUT on address `%s' received %u bytes\n", + s, sc, GNUNET_i2s (&s->target), - http_plugin_address_to_string (NULL, s->addr, - s->addrlen), + http_common_plugin_address_to_string (NULL, + s->addr, + s->addrlen), *upload_data_size); struct GNUNET_TIME_Absolute now = GNUNET_TIME_absolute_get (); if ((s->next_receive.abs_value <= now.abs_value)) { GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, - "Server: %p: PUT with %u bytes forwarded to MST\n", s, + "PUT with %u bytes forwarded to MST\n", *upload_data_size); if (s->msg_tk == NULL) { @@ -701,65 +1459,47 @@ server_access_cb (void *cls, struct MHD_Connection *mhd_connection, } GNUNET_SERVER_mst_receive (s->msg_tk, s, upload_data, *upload_data_size, GNUNET_NO, GNUNET_NO); - #if MHD_VERSION >= 0x00090E00 - int to = (GNUNET_CONSTANTS_IDLE_CONNECTION_TIMEOUT.rel_value / 1000); - struct ServerConnection *t = NULL; - - GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, - "Server: Received %u bytes\n", *upload_data_size); - /* Setting timeouts for other connections */ - if (s->server_recv != NULL) - { - t = s->server_recv; - GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, - "Server: Setting timeout for %p to %u sec.\n", t, - to); - MHD_set_connection_option (t->mhd_conn, MHD_CONNECTION_OPTION_TIMEOUT, - to); - } - if (s->server_send != NULL) - { - t = s->server_send; - GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, - "Server: Setting timeout for %p to %u sec.\n", t, - to); - MHD_set_connection_option (t->mhd_conn, MHD_CONNECTION_OPTION_TIMEOUT, - to); - } - struct MHD_Daemon *d = NULL; - - if (s->addrlen == sizeof (struct IPv6HttpAddress)) - d = plugin->server_v6; - if (s->addrlen == sizeof (struct IPv4HttpAddress)) - d = plugin->server_v4; - server_reschedule (plugin, d, GNUNET_NO); + server_mhd_connection_timeout (plugin, s, GNUNET_CONSTANTS_IDLE_CONNECTION_TIMEOUT.rel_value / 1000); #endif (*upload_data_size) = 0; } else { GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Server: %p no inbound bandwidth available! Next read was delayed by %llu ms\n", - s, now.abs_value - s->next_receive.abs_value); + "Session %p / Connection %p: no inbound bandwidth available! Next read was delayed by %llu ms\n", + s, sc, now.abs_value - s->next_receive.abs_value); } return MHD_YES; } else + { + GNUNET_break (0); return MHD_NO; + } } return res; } + +/** + * Callback from MHD when a connection disconnects + * + * @param cls closure + * @param connection the disconnected MHD connection + * @param httpSessionCache the pointer to distinguish + */ static void server_disconnect_cb (void *cls, struct MHD_Connection *connection, void **httpSessionCache) { struct ServerConnection *sc = *httpSessionCache; - struct ServerConnection *tc = NULL; struct Session *s = NULL; struct Session *t = NULL; - struct Plugin *plugin = NULL; + struct HTTP_Server_Plugin *plugin = NULL; + + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, p->name, + "Disconnect for connection %p \n", sc); if (sc == NULL) return; @@ -768,7 +1508,12 @@ server_disconnect_cb (void *cls, struct MHD_Connection *connection, return; GNUNET_assert (NULL != p); - if (GNUNET_NO == exist_session(p, s)) + for (t = p->head; t != NULL; t = t->next) + { + if (t == s) + break; + } + if (NULL == t) return; plugin = s->plugin; @@ -776,36 +1521,39 @@ server_disconnect_cb (void *cls, struct MHD_Connection *connection, { GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, - "Server: %p peer `%s' GET on address `%s' disconnected\n", - s->server_send, GNUNET_i2s (&s->target), - http_plugin_address_to_string (NULL, s->addr, s->addrlen)); + "Peer `%s' connection %p, GET on address `%s' disconnected\n", + GNUNET_i2s (&s->target), s->server_send, + http_common_plugin_address_to_string (NULL, s->addr, s->addrlen)); s->server_send = NULL; - if (NULL != (tc = s->server_recv)) + if (NULL != (s->server_recv)) { - tc->disconnect = GNUNET_YES; - GNUNET_assert (NULL != tc->mhd_conn); + s->server_recv->disconnect = GNUNET_YES; + GNUNET_assert (NULL != s->server_recv->mhd_conn); #if MHD_VERSION >= 0x00090E00 - MHD_set_connection_option (tc->mhd_conn, MHD_CONNECTION_OPTION_TIMEOUT, + MHD_set_connection_option (s->server_recv->mhd_conn, MHD_CONNECTION_OPTION_TIMEOUT, 1); #endif + server_reschedule (plugin, s->server_recv->mhd_daemon, GNUNET_NO); } } if (sc->direction == _RECEIVE) { GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, - "Server: %p peer `%s' PUT on address `%s' disconnected\n", - s->server_recv, GNUNET_i2s (&s->target), - http_plugin_address_to_string (NULL, s->addr, s->addrlen)); + "Peer `%s' connection %p PUT on address `%s' disconnected\n", + GNUNET_i2s (&s->target), s->server_recv, + http_common_plugin_address_to_string (NULL, s->addr, s->addrlen)); s->server_recv = NULL; - if (NULL != (tc = s->server_send)) + /* Do not terminate session when PUT disconnects + if (NULL != (s->server_send)) { - tc->disconnect = GNUNET_YES; - GNUNET_assert (NULL != tc->mhd_conn); + s->server_send->disconnect = GNUNET_YES; + GNUNET_assert (NULL != s->server_send->mhd_conn); #if MHD_VERSION >= 0x00090E00 - MHD_set_connection_option (tc->mhd_conn, MHD_CONNECTION_OPTION_TIMEOUT, + MHD_set_connection_option (s->server_send->mhd_conn, MHD_CONNECTION_OPTION_TIMEOUT, 1); #endif - } + server_reschedule (plugin, s->server_send->mhd_daemon, GNUNET_NO); + }*/ if (s->msg_tk != NULL) { GNUNET_SERVER_mst_destroy (s->msg_tk); @@ -814,84 +1562,67 @@ server_disconnect_cb (void *cls, struct MHD_Connection *connection, } GNUNET_free (sc); - - t = plugin->server_semi_head; - while (t != NULL) - { - if (t == s) - { - GNUNET_CONTAINER_DLL_remove (plugin->server_semi_head, - plugin->server_semi_tail, s); - GNUNET_CONTAINER_DLL_insert (plugin->head, plugin->tail, s); - break; - } - t = t->next; - } plugin->cur_connections--; - struct MHD_Daemon *d = NULL; - - if (s->addrlen == sizeof (struct IPv6HttpAddress)) - d = plugin->server_v6; - if (s->addrlen == sizeof (struct IPv4HttpAddress)) - d = plugin->server_v4; - server_reschedule (plugin, d, GNUNET_NO); - if ((s->server_send == NULL) && (s->server_recv == NULL)) { GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, - "Server: peer `%s' on address `%s' disconnected\n", + "Peer `%s' on address `%s' disconnected\n", GNUNET_i2s (&s->target), - http_plugin_address_to_string (NULL, s->addr, s->addrlen)); - if (s->msg_tk != NULL) + http_common_plugin_address_to_string (NULL, s->addr, s->addrlen)); + + if ((GNUNET_YES == s->session_passed) && (GNUNET_NO == s->session_ended)) { - GNUNET_SERVER_mst_destroy (s->msg_tk); - s->msg_tk = NULL; + /* Notify transport immediately that this session is invalid */ + s->session_ended = GNUNET_YES; + plugin->env->session_end (plugin->env->cls, &s->target, s); } - - GNUNET_assert (plugin->inbound_sessions > 0); - plugin->inbound_sessions --; - GNUNET_STATISTICS_set (plugin->env->stats, - "# HTTP inbound sessions", - plugin->inbound_sessions, GNUNET_NO); - - notify_session_end (s->plugin, &s->target, s); + server_delete_session (s); } + } -int -server_disconnect (struct Session *s) -{ - if (s->server_send != NULL) - { - ((struct ServerConnection *) s->server_send)->disconnect = GNUNET_YES; - } - if (s->server_recv != NULL) - { - ((struct ServerConnection *) s->server_recv)->disconnect = GNUNET_YES; - } - return GNUNET_OK; -} +/** + * Check if incoming connection is accepted. -int -server_send (struct Session *s, struct HTTP_Message *msg) + * @param cls plugin as closure + * @param addr address of incoming connection + * @param addr_len address length of incoming connection + * @return MHD_YES if connection is accepted, MHD_NO if connection is rejected + * + */ +static int +server_accept_cb (void *cls, const struct sockaddr *addr, socklen_t addr_len) { - GNUNET_CONTAINER_DLL_insert_tail (s->msg_head, s->msg_tail, msg); + struct HTTP_Server_Plugin *plugin = cls; - if (s->addrlen == sizeof (struct IPv4HttpAddress)) + if (plugin->cur_connections <= plugin->max_connections) { - server_reschedule (s->plugin, s->plugin->server_v4, GNUNET_YES); + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + _("Accepting connection (%u of %u) from `%s'\n"), + plugin->cur_connections, plugin->max_connections, + GNUNET_a2s (addr, addr_len)); + return MHD_YES; } - else if (s->addrlen == sizeof (struct IPv6HttpAddress)) + else { - server_reschedule (s->plugin, s->plugin->server_v6, GNUNET_YES); + GNUNET_log_from (GNUNET_ERROR_TYPE_WARNING, plugin->name, + _("Server reached maximum number connections (%u), rejecting new connection\n"), + plugin->max_connections); + return MHD_NO; } - else - return GNUNET_SYSERR; - return GNUNET_OK; } +static void +server_log (void *arg, const char *fmt, va_list ap) +{ + char text[1024]; + + vsnprintf (text, sizeof (text), fmt, ap); + va_end (ap); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Server: %s\n", text); +} /** @@ -903,7 +1634,7 @@ server_send (struct Session *s, struct HTTP_Message *msg) static void server_v4_run (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { - struct Plugin *plugin = cls; + struct HTTP_Server_Plugin *plugin = cls; GNUNET_assert (cls != NULL); @@ -929,7 +1660,7 @@ server_v4_run (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) static void server_v6_run (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { - struct Plugin *plugin = cls; + struct HTTP_Server_Plugin *plugin = cls; GNUNET_assert (cls != NULL); plugin->server_v6_task = GNUNET_SCHEDULER_NO_TASK; @@ -944,15 +1675,20 @@ server_v6_run (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) server_reschedule (plugin, plugin->server_v6, GNUNET_NO); } + +#define UNSIGNED_MHD_LONG_LONG unsigned MHD_LONG_LONG + /** * Function that queries MHD's select sets and * starts the task waiting for them. + * * @param plugin plugin * @param daemon_handle the MHD daemon handle * @return gnunet task identifier */ static GNUNET_SCHEDULER_TaskIdentifier -server_schedule (struct Plugin *plugin, struct MHD_Daemon *daemon_handle, +server_schedule (struct HTTP_Server_Plugin *plugin, + struct MHD_Daemon *daemon_handle, int now) { GNUNET_SCHEDULER_TaskIdentifier ret; @@ -963,12 +1699,15 @@ server_schedule (struct Plugin *plugin, struct MHD_Daemon *daemon_handle, struct GNUNET_NETWORK_FDSet *wws; struct GNUNET_NETWORK_FDSet *wes; int max; - unsigned MHD_LONG_LONG timeout; + UNSIGNED_MHD_LONG_LONG timeout; static unsigned long long last_timeout = 0; int haveto; struct GNUNET_TIME_Relative tv; + if (GNUNET_YES == plugin->in_shutdown) + return GNUNET_SCHEDULER_NO_TASK; + ret = GNUNET_SCHEDULER_NO_TASK; FD_ZERO (&rs); FD_ZERO (&ws); @@ -983,14 +1722,16 @@ server_schedule (struct Plugin *plugin, struct MHD_Daemon *daemon_handle, { if (timeout != last_timeout) { -#if VERBOSE_SERVER + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, "SELECT Timeout changed from %llu to %llu\n", last_timeout, timeout); -#endif last_timeout = timeout; } - tv.rel_value = (uint64_t) timeout; + if (timeout <= GNUNET_TIME_UNIT_SECONDS.rel_value) + tv.rel_value = (uint64_t) timeout; + else + tv = GNUNET_TIME_UNIT_SECONDS; } else tv = GNUNET_TIME_UNIT_SECONDS; @@ -1039,38 +1780,216 @@ server_schedule (struct Plugin *plugin, struct MHD_Daemon *daemon_handle, return ret; } -int -server_start (struct Plugin *plugin) -{ - int res = GNUNET_OK; - unsigned int timeout; - p = plugin; - GNUNET_assert (NULL != plugin); #if BUILD_HTTPS - res = server_load_certificate (plugin); - if (res == GNUNET_SYSERR) +/** + * Load ssl certificate from file + * + * @param file filename + * @return content of the file + */ +static char * +server_load_file (const char *file) +{ + struct GNUNET_DISK_FileHandle *gn_file; + uint64_t fsize; + char *text = NULL; + + if (GNUNET_OK != GNUNET_DISK_file_size (file, + &fsize, GNUNET_NO, GNUNET_YES)) + return NULL; + text = GNUNET_malloc (fsize + 1); + gn_file = + GNUNET_DISK_file_open (file, GNUNET_DISK_OPEN_READ, + GNUNET_DISK_PERM_USER_READ); + if (gn_file == NULL) { - GNUNET_log_from (GNUNET_ERROR_TYPE_ERROR, plugin->name, - "Could not load or create server certificate! Loading plugin failed!\n"); - return res; + GNUNET_free (text); + return NULL; } + if (GNUNET_SYSERR == GNUNET_DISK_file_read (gn_file, text, fsize)) + { + GNUNET_free (text); + GNUNET_DISK_file_close (gn_file); + return NULL; + } + text[fsize] = '\0'; + GNUNET_DISK_file_close (gn_file); + return text; +} #endif -#if MHD_VERSION >= 0x00090E00 - timeout = HTTP_NOT_VALIDATED_TIMEOUT.rel_value / 1000; - GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, - "MHD can set timeout per connection! Default time out %u sec.\n", - timeout); -#else - timeout = GNUNET_CONSTANTS_IDLE_CONNECTION_TIMEOUT.rel_value / 1000; - GNUNET_log_from (GNUNET_ERROR_TYPE_WARNING, plugin->name, +#if BUILD_HTTPS +/** + * Load ssl certificate + * + * @param plugin the plugin + * @return GNUNET_OK on success, GNUNET_SYSERR on failure + */ +static int +server_load_certificate (struct HTTP_Server_Plugin *plugin) +{ + int res = GNUNET_OK; + + char *sh; + char *key_file; + char *cert_file; + + /* Get crypto init string from config + * If not present just use default values */ + + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_string (plugin->env->cfg, + "PATHS", + "SERVICEHOME", + &sh)) + { + GNUNET_log_from (GNUNET_ERROR_TYPE_ERROR, plugin->name, + "Failed to get servicehome!\n"); + return GNUNET_SYSERR; + } + + + if (GNUNET_OK == + GNUNET_CONFIGURATION_get_value_string (plugin->env->cfg, + plugin->name, + "CRYPTO_INIT", + &plugin->crypto_init)) + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + "Using crypto init string `%s'\n", + plugin->crypto_init); + else + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + "Using default crypto init string \n"); + + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_filename (plugin->env->cfg, plugin->name, + "KEY_FILE", &key_file)) + { + GNUNET_break (0); + GNUNET_asprintf (&key_file, "%s/%s", sh, "https_key.key"); + } + + + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_filename (plugin->env->cfg, plugin->name, + "CERT_FILE", &cert_file)) + { + GNUNET_break (0); + GNUNET_asprintf (&cert_file, "%s/%s", sh, "https_cert.crt"); + } + GNUNET_free (sh); + /* read key & certificates from file */ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Trying to loading TLS certificate from key-file `%s' cert-file`%s'\n", + key_file, cert_file); + + plugin->key = server_load_file (key_file); + plugin->cert = server_load_file (cert_file); + + if ((plugin->key == NULL) || (plugin->cert == NULL)) + { + struct GNUNET_OS_Process *cert_creation; + + GNUNET_free_non_null (plugin->key); + plugin->key = NULL; + GNUNET_free_non_null (plugin->cert); + plugin->cert = NULL; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "No usable TLS certificate found, creating certificate\n"); + errno = 0; + cert_creation = + GNUNET_OS_start_process (GNUNET_NO, GNUNET_OS_INHERIT_STD_OUT_AND_ERR, NULL, NULL, + "gnunet-transport-certificate-creation", + "gnunet-transport-certificate-creation", + key_file, cert_file, NULL); + if (cert_creation == NULL) + { + GNUNET_log_from (GNUNET_ERROR_TYPE_ERROR, plugin->name, + _ + ("Could not create a new TLS certificate, program `gnunet-transport-certificate-creation' could not be started!\n")); + GNUNET_free (key_file); + GNUNET_free (cert_file); + + GNUNET_free_non_null (plugin->key); + plugin->key = NULL; + GNUNET_free_non_null (plugin->cert); + plugin->cert = NULL; + GNUNET_free_non_null (plugin->crypto_init); + plugin->crypto_init = NULL; + + return GNUNET_SYSERR; + } + GNUNET_assert (GNUNET_OK == GNUNET_OS_process_wait (cert_creation)); + GNUNET_OS_process_destroy (cert_creation); + + plugin->key = server_load_file (key_file); + plugin->cert = server_load_file (cert_file); + } + + if ((plugin->key == NULL) || (plugin->cert == NULL)) + { + GNUNET_log_from (GNUNET_ERROR_TYPE_ERROR, plugin->name, + _ + ("No usable TLS certificate found and creating one failed!\n"), + "transport-https"); + GNUNET_free (key_file); + GNUNET_free (cert_file); + + GNUNET_free_non_null (plugin->key); + plugin->key = NULL; + GNUNET_free_non_null (plugin->cert); + plugin->cert = NULL; + GNUNET_free_non_null (plugin->crypto_init); + plugin->crypto_init = NULL; + + return GNUNET_SYSERR; + } + GNUNET_free (key_file); + GNUNET_free (cert_file); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "TLS certificate loaded\n"); + return res; +} +#endif + + +/** + * Start the HTTP server + * + * @param plugin the plugin handle + * @return GNUNET_OK on success, GNUNET_SYSERR on failure + */ +static int +server_start (struct HTTP_Server_Plugin *plugin) +{ + unsigned int timeout; + GNUNET_assert (NULL != plugin); + +#if BUILD_HTTPS + if (GNUNET_SYSERR == server_load_certificate (plugin)) + { + GNUNET_log_from (GNUNET_ERROR_TYPE_ERROR, plugin->name, + "Could not load or create server certificate! Loading plugin failed!\n"); + return GNUNET_SYSERR; + } +#endif + + +#if MHD_VERSION >= 0x00090E00 + timeout = HTTP_SERVER_NOT_VALIDATED_TIMEOUT.rel_value / 1000; + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + "MHD can set timeout per connection! Default time out %u sec.\n", + timeout); +#else + timeout = SERVER_SESSION_TIMEOUT.rel_value / 1000; + GNUNET_log_from (GNUNET_ERROR_TYPE_WARNING, plugin->name, "MHD cannot set timeout per connection! Default time out %u sec.\n", timeout); #endif plugin->server_v4 = NULL; - if (plugin->ipv4 == GNUNET_YES) + if (plugin->use_ipv4 == GNUNET_YES) { plugin->server_v4 = MHD_start_daemon ( #if VERBOSE_SERVER @@ -1107,7 +2026,7 @@ server_start (struct Plugin *plugin) server_log, NULL, MHD_OPTION_END); } plugin->server_v6 = NULL; - if (plugin->ipv6 == GNUNET_YES) + if (plugin->use_ipv6 == GNUNET_YES) { plugin->server_v6 = MHD_start_daemon ( #if VERBOSE_SERVER @@ -1145,7 +2064,7 @@ server_start (struct Plugin *plugin) } - if ((plugin->ipv4 == GNUNET_YES) && (plugin->server_v4 == NULL)) + if ((plugin->use_ipv4 == GNUNET_YES) && (plugin->server_v4 == NULL)) { GNUNET_log_from (GNUNET_ERROR_TYPE_ERROR, plugin->name, "Failed to start %s IPv4 server component on port %u\n", @@ -1154,7 +2073,7 @@ server_start (struct Plugin *plugin) } server_reschedule (plugin, plugin->server_v4, GNUNET_NO); - if ((plugin->ipv6 == GNUNET_YES) && (plugin->server_v6 == NULL)) + if ((plugin->use_ipv6 == GNUNET_YES) && (plugin->server_v6 == NULL)) { GNUNET_log_from (GNUNET_ERROR_TYPE_ERROR, plugin->name, "Failed to start %s IPv6 server component on port %u\n", @@ -1165,21 +2084,24 @@ server_start (struct Plugin *plugin) GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, "%s server component started on port %u\n", plugin->name, plugin->port); - return res; + return GNUNET_OK; } + void -server_stop (struct Plugin *plugin) +server_stop (struct HTTP_Server_Plugin *plugin) { - struct Session *s = NULL; - struct Session *t = NULL; - - struct MHD_Daemon *server_v4_tmp = plugin->server_v4; - - plugin->server_v4 = NULL; - struct MHD_Daemon *server_v6_tmp = plugin->server_v6; + if (plugin->server_v4 != NULL) + { + MHD_stop_daemon (plugin->server_v4); + plugin->server_v4 = NULL; + } + if ( plugin->server_v6 != NULL) + { + MHD_stop_daemon (plugin->server_v6); + plugin->server_v6 = NULL; + } - plugin->server_v6 = NULL; if (plugin->server_v4_task != GNUNET_SCHEDULER_NO_TASK) { @@ -1192,57 +2114,896 @@ server_stop (struct Plugin *plugin) GNUNET_SCHEDULER_cancel (plugin->server_v6_task); plugin->server_v6_task = GNUNET_SCHEDULER_NO_TASK; } + p = NULL; - if (server_v6_tmp != NULL) +#if BUILD_HTTPS + GNUNET_free_non_null (plugin->crypto_init); + GNUNET_free_non_null (plugin->cert); + GNUNET_free_non_null (plugin->key); +#endif + + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + "%s server component stopped\n", plugin->name); +} + + +/** + * Add an address to the server's set of addresses and notify transport + * + * @param cls the plugin handle + * @param add_remove GNUNET_YES on add, GNUNET_NO on remove + * @param addr the address + * @param addrlen address length + */ +static void +server_add_address (void *cls, int add_remove, const struct sockaddr *addr, + socklen_t addrlen) +{ + struct HTTP_Server_Plugin *plugin = cls; + struct HttpAddressWrapper *w = NULL; + + w = GNUNET_malloc (sizeof (struct HttpAddressWrapper)); + w->addr = http_common_address_from_socket (plugin->protocol, addr, addrlen); + if (NULL == w->addr) { - MHD_stop_daemon (server_v4_tmp); + GNUNET_free (w); + return; } - if (server_v6_tmp != NULL) + w->addrlen = http_common_address_get_size (w->addr); + + GNUNET_CONTAINER_DLL_insert(plugin->addr_head, plugin->addr_tail, w); + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + "Notifying transport to add address `%s'\n", + http_common_plugin_address_to_string(NULL, w->addr, w->addrlen)); +#if BUILD_HTTPS + plugin->env->notify_address (plugin->env->cls, add_remove, w->addr, w->addrlen, "https_client"); +#else + plugin->env->notify_address (plugin->env->cls, add_remove, w->addr, w->addrlen, "http_client"); +#endif +} + + +/** + * Remove an address from the server's set of addresses and notify transport + * + * @param cls the plugin handle + * @param add_remove GNUNET_YES on add, GNUNET_NO on remove + * @param addr the address + * @param addrlen address length + */ +static void +server_remove_address (void *cls, int add_remove, const struct sockaddr *addr, + socklen_t addrlen) +{ + struct HTTP_Server_Plugin *plugin = cls; + struct HttpAddressWrapper *w = plugin->addr_head; + size_t saddr_len; + void * saddr = http_common_address_from_socket (plugin->protocol, addr, addrlen); + if (NULL == saddr) + return; + saddr_len = http_common_address_get_size (saddr); + + while (NULL != w) { - MHD_stop_daemon (server_v6_tmp); + if (GNUNET_YES == http_common_cmp_addresses(w->addr, w->addrlen, saddr, saddr_len)) + break; + w = w->next; } + GNUNET_free (saddr); - /* cleaning up semi-sessions never propagated */ - s = plugin->server_semi_head; - while (s != NULL) + if (NULL == w) + return; + + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + "Notifying transport to remove address `%s'\n", + http_common_plugin_address_to_string (NULL, w->addr, w->addrlen)); + GNUNET_CONTAINER_DLL_remove (plugin->addr_head, plugin->addr_tail, w); +#if BUILD_HTTPS + plugin->env->notify_address (plugin->env->cls, add_remove, w->addr, w->addrlen, "https_client"); +#else + plugin->env->notify_address (plugin->env->cls, add_remove, w->addr, w->addrlen, "http_client"); +#endif + GNUNET_free (w->addr); + GNUNET_free (w); +} + + + +/** + * Our external IP address/port mapping has changed. + * + * @param cls closure, the 'struct LocalAddrList' + * @param add_remove GNUNET_YES to mean the new public IP address, GNUNET_NO to mean + * the previous (now invalid) one + * @param addr either the previous or the new public IP address + * @param addrlen actual lenght of the address + */ +static void +server_nat_port_map_callback (void *cls, int add_remove, const struct sockaddr *addr, + socklen_t addrlen) +{ + GNUNET_assert (cls != NULL); + struct HTTP_Server_Plugin *plugin = cls; + + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + "NAT called to %s address `%s'\n", + (add_remove == GNUNET_NO) ? "remove" : "add", + GNUNET_a2s (addr, addrlen)); + + if (AF_INET == addr->sa_family) + { + struct sockaddr_in *s4 = (struct sockaddr_in *) addr; + + if (GNUNET_NO == plugin->use_ipv4) + return; + + if ((NULL != plugin->server_addr_v4) && + (0 != memcmp (&plugin->server_addr_v4->sin_addr, + &s4->sin_addr, sizeof (struct in_addr)))) + { + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + "Skipping address `%s' (not bindto address)\n", + GNUNET_a2s (addr, addrlen)); + return; + } + } + + if (AF_INET6 == addr->sa_family) + { + struct sockaddr_in6 *s6 = (struct sockaddr_in6 *) addr; + if (GNUNET_NO == plugin->use_ipv6) + return; + + if ((NULL != plugin->server_addr_v6) && + (0 != memcmp (&plugin->server_addr_v6->sin6_addr, + &s6->sin6_addr, sizeof (struct in6_addr)))) + { + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + "Skipping address `%s' (not bindto address)\n", + GNUNET_a2s (addr, addrlen)); + return; + } + } + + switch (add_remove) + { + case GNUNET_YES: + server_add_address (cls, add_remove, addr, addrlen); + break; + case GNUNET_NO: + server_remove_address (cls, add_remove, addr, addrlen); + break; + } +} + + +/** + * Get valid server addresses + * + * @param plugin the plugin handle + * @param serviceName the servicename + * @param cfg configuration handle + * @param addrs addresses + * @param addr_lens address length + * @return number of addresses + */ +static int +server_get_addresses (struct HTTP_Server_Plugin *plugin, + const char *serviceName, + const struct GNUNET_CONFIGURATION_Handle *cfg, + struct sockaddr ***addrs, socklen_t ** addr_lens) +{ + int disablev6; + unsigned long long port; + struct addrinfo hints; + struct addrinfo *res; + struct addrinfo *pos; + struct addrinfo *next; + unsigned int i; + int resi; + int ret; + struct sockaddr **saddrs; + socklen_t *saddrlens; + char *hostname; + + *addrs = NULL; + *addr_lens = NULL; + + disablev6 = !plugin->use_ipv6; + + port = 0; + if (GNUNET_CONFIGURATION_have_value (cfg, serviceName, "PORT")) + { + GNUNET_break (GNUNET_OK == + GNUNET_CONFIGURATION_get_value_number (cfg, serviceName, + "PORT", &port)); + if (port > 65535) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _ + ("Require valid port number for service in configuration!\n")); + return GNUNET_SYSERR; + } + } + if (0 == port) + { + GNUNET_log_from (GNUNET_ERROR_TYPE_INFO, plugin->name, + "Starting in listen only mode\n"); + return -1; /* listen only */ + } + + + if (GNUNET_CONFIGURATION_have_value (cfg, serviceName, "BINDTO")) + { + GNUNET_break (GNUNET_OK == + GNUNET_CONFIGURATION_get_value_string (cfg, serviceName, + "BINDTO", &hostname)); + } + else + hostname = NULL; + + if (hostname != NULL) { -#if VERBOSE_SERVER GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, - "Deleting semi-sessions %p\n", s); + "Resolving `%s' since that is where `%s' will bind to.\n", + hostname, serviceName); + memset (&hints, 0, sizeof (struct addrinfo)); + if (disablev6) + hints.ai_family = AF_INET; + if ((0 != (ret = getaddrinfo (hostname, NULL, &hints, &res))) || + (res == NULL)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("Failed to resolve `%s': %s\n"), + hostname, gai_strerror (ret)); + GNUNET_free (hostname); + return GNUNET_SYSERR; + } + next = res; + i = 0; + while (NULL != (pos = next)) + { + next = pos->ai_next; + if ((disablev6) && (pos->ai_family == AF_INET6)) + continue; + i++; + } + if (0 == i) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Failed to find %saddress for `%s'.\n"), + disablev6 ? "IPv4 " : "", hostname); + freeaddrinfo (res); + GNUNET_free (hostname); + return GNUNET_SYSERR; + } + resi = i; + saddrs = GNUNET_malloc ((resi + 1) * sizeof (struct sockaddr *)); + saddrlens = GNUNET_malloc ((resi + 1) * sizeof (socklen_t)); + i = 0; + next = res; + while (NULL != (pos = next)) + { + next = pos->ai_next; + if ((disablev6) && (pos->ai_family == AF_INET6)) + continue; + if ((pos->ai_protocol != IPPROTO_TCP) && (pos->ai_protocol != 0)) + continue; /* not TCP */ + if ((pos->ai_socktype != SOCK_STREAM) && (pos->ai_socktype != 0)) + continue; /* huh? */ + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + "Service will bind to `%s'\n", GNUNET_a2s (pos->ai_addr, + pos->ai_addrlen)); + if (pos->ai_family == AF_INET) + { + GNUNET_assert (pos->ai_addrlen == sizeof (struct sockaddr_in)); + saddrlens[i] = pos->ai_addrlen; + saddrs[i] = GNUNET_malloc (saddrlens[i]); + memcpy (saddrs[i], pos->ai_addr, saddrlens[i]); + ((struct sockaddr_in *) saddrs[i])->sin_port = htons (port); + } + else + { + GNUNET_assert (pos->ai_family == AF_INET6); + GNUNET_assert (pos->ai_addrlen == sizeof (struct sockaddr_in6)); + saddrlens[i] = pos->ai_addrlen; + saddrs[i] = GNUNET_malloc (saddrlens[i]); + memcpy (saddrs[i], pos->ai_addr, saddrlens[i]); + ((struct sockaddr_in6 *) saddrs[i])->sin6_port = htons (port); + } + i++; + } + GNUNET_free (hostname); + freeaddrinfo (res); + resi = i; + } + else + { + /* will bind against everything, just set port */ + if (disablev6) + { + /* V4-only */ + resi = 1; + i = 0; + saddrs = GNUNET_malloc ((resi + 1) * sizeof (struct sockaddr *)); + saddrlens = GNUNET_malloc ((resi + 1) * sizeof (socklen_t)); + + saddrlens[i] = sizeof (struct sockaddr_in); + saddrs[i] = GNUNET_malloc (saddrlens[i]); +#if HAVE_SOCKADDR_IN_SIN_LEN + ((struct sockaddr_in *) saddrs[i])->sin_len = saddrlens[i]; +#endif + ((struct sockaddr_in *) saddrs[i])->sin_family = AF_INET; + ((struct sockaddr_in *) saddrs[i])->sin_port = htons (port); + } + else + { + /* dual stack */ + resi = 2; + saddrs = GNUNET_malloc ((resi + 1) * sizeof (struct sockaddr *)); + saddrlens = GNUNET_malloc ((resi + 1) * sizeof (socklen_t)); + i = 0; + saddrlens[i] = sizeof (struct sockaddr_in6); + saddrs[i] = GNUNET_malloc (saddrlens[i]); +#if HAVE_SOCKADDR_IN_SIN_LEN + ((struct sockaddr_in6 *) saddrs[i])->sin6_len = saddrlens[0]; +#endif + ((struct sockaddr_in6 *) saddrs[i])->sin6_family = AF_INET6; + ((struct sockaddr_in6 *) saddrs[i])->sin6_port = htons (port); + i++; + saddrlens[i] = sizeof (struct sockaddr_in); + saddrs[i] = GNUNET_malloc (saddrlens[i]); +#if HAVE_SOCKADDR_IN_SIN_LEN + ((struct sockaddr_in *) saddrs[i])->sin_len = saddrlens[1]; #endif - t = s->next; - struct HTTP_Message *msg = s->msg_head; - struct HTTP_Message *tmp = NULL; + ((struct sockaddr_in *) saddrs[i])->sin_family = AF_INET; + ((struct sockaddr_in *) saddrs[i])->sin_port = htons (port); + } + } + *addrs = saddrs; + *addr_lens = saddrlens; + return resi; +} + - while (msg != NULL) +/** + * Ask NAT for addresses + * + * @param plugin the plugin handle + */ +static void +server_start_report_addresses (struct HTTP_Server_Plugin *plugin) +{ + int res = GNUNET_OK; + struct sockaddr **addrs; + socklen_t *addrlens; + + res = server_get_addresses (plugin, + plugin->name, plugin->env->cfg, + &addrs, &addrlens); + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + _("Found %u addresses to report to NAT service\n"), res); + + if (GNUNET_SYSERR == res) + { + plugin->nat = NULL; + return; + } + + plugin->nat = + GNUNET_NAT_register (plugin->env->cfg, GNUNET_YES, plugin->port, + (unsigned int) res, + (const struct sockaddr **) addrs, addrlens, + &server_nat_port_map_callback, NULL, plugin); + while (res > 0) + { + res--; + GNUNET_assert (addrs[res] != NULL); + GNUNET_free (addrs[res]); + } + GNUNET_free_non_null (addrs); + GNUNET_free_non_null (addrlens); +} + + +/** + * Stop NAT for addresses + * + * @param plugin the plugin handle + */ +static void +server_stop_report_addresses (struct HTTP_Server_Plugin *plugin) +{ + /* Stop NAT handle */ + if (NULL != plugin->nat) + GNUNET_NAT_unregister (plugin->nat); + + /* Clean up addresses */ + struct HttpAddressWrapper *w; + + while (plugin->addr_head != NULL) + { + w = plugin->addr_head; + GNUNET_CONTAINER_DLL_remove (plugin->addr_head, plugin->addr_tail, w); + GNUNET_free (w->addr); + GNUNET_free (w); + } +} + + +/** + * Check if IPv6 supported on this system + * + * @param plugin the plugin handle + * @return GNUNET_YES on success, else GNUNET_NO + */ +static int +server_check_ipv6_support (struct HTTP_Server_Plugin *plugin) +{ + struct GNUNET_NETWORK_Handle *desc = NULL; + int res = GNUNET_NO; + + /* Probe IPv6 support */ + desc = GNUNET_NETWORK_socket_create (PF_INET6, SOCK_STREAM, 0); + if (NULL == desc) + { + if ((errno == ENOBUFS) || (errno == ENOMEM) || (errno == ENFILE) || + (errno == EACCES)) { - tmp = msg->next; + GNUNET_log_strerror (GNUNET_ERROR_TYPE_ERROR, "socket"); + } + GNUNET_log_from (GNUNET_ERROR_TYPE_WARNING, plugin->name, + _ + ("Disabling IPv6 since it is not supported on this system!\n")); + res = GNUNET_NO; + } + else + { + GNUNET_break (GNUNET_OK == GNUNET_NETWORK_socket_close (desc)); + desc = NULL; + res = GNUNET_YES; + } + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + "Testing IPv6 on this system: %s\n", + (res == GNUNET_YES) ? "successful" : "failed"); + return res; +} - GNUNET_CONTAINER_DLL_remove (s->msg_head, s->msg_tail, msg); - if (msg->transmit_cont != NULL) + +/** + * Function called when the service shuts down. Unloads our plugins + * and cancels pending validations. + * + * @param cls closure, unused + * @param tc task context (unused) + */ +static void +server_notify_external_hostname (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct HTTP_Server_Plugin *plugin = cls; + + plugin->notify_ext_task = GNUNET_SCHEDULER_NO_TASK; + + if (0 != (tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN)) + return; + + GNUNET_asprintf(&plugin->ext_addr, "%s://%s", plugin->protocol, plugin->external_hostname); + plugin->ext_addr_len = strlen (plugin->ext_addr) + 1; + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + "Notifying transport about external hostname address `%s'\n", plugin->ext_addr); + +#if BUILD_HTTPS + plugin->env->notify_address (plugin->env->cls, GNUNET_YES, + plugin->ext_addr, plugin->ext_addr_len, + "https_client"); +#else + plugin->env->notify_address (plugin->env->cls, GNUNET_YES, + plugin->ext_addr, plugin->ext_addr_len, + "http_client"); +#endif +} + + +/** + * Configure the plugin + * + * @param plugin plugin handle + * @return GNUNET_OK on success, GNUNET_SYSERR on failure + */ +static int +server_configure_plugin (struct HTTP_Server_Plugin *plugin) +{ + unsigned long long port; + unsigned long long max_connections; + char *bind4_address = NULL; + char *bind6_address = NULL; + + /* Use IPv4? */ + if (GNUNET_CONFIGURATION_have_value + (plugin->env->cfg, plugin->name, "USE_IPv4")) + { + plugin->use_ipv4 = + GNUNET_CONFIGURATION_get_value_yesno (plugin->env->cfg, plugin->name, + "USE_IPv4"); + } + else + plugin->use_ipv4 = GNUNET_YES; + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + _("IPv4 support is %s\n"), + (plugin->use_ipv4 == GNUNET_YES) ? "enabled" : "disabled"); + + /* Use IPv6? */ + if (GNUNET_CONFIGURATION_have_value + (plugin->env->cfg, plugin->name, "USE_IPv6")) + { + plugin->use_ipv6 = + GNUNET_CONFIGURATION_get_value_yesno (plugin->env->cfg, plugin->name, + "USE_IPv6"); + } + else + plugin->use_ipv6 = GNUNET_YES; + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + _("IPv6 support is %s\n"), + (plugin->use_ipv6 == GNUNET_YES) ? "enabled" : "disabled"); + + if ((plugin->use_ipv4 == GNUNET_NO) && (plugin->use_ipv6 == GNUNET_NO)) + { + GNUNET_log_from (GNUNET_ERROR_TYPE_ERROR, plugin->name, + _ + ("Neither IPv4 nor IPv6 are enabled! Fix in configuration\n"), + plugin->name); + return GNUNET_SYSERR; + } + + /* Reading port number from config file */ + if ((GNUNET_OK != + GNUNET_CONFIGURATION_get_value_number (plugin->env->cfg, plugin->name, + "PORT", &port)) || (port > 65535)) + { + GNUNET_log_from (GNUNET_ERROR_TYPE_ERROR, plugin->name, + _("Port is required! Fix in configuration\n"), + plugin->name); + return GNUNET_SYSERR; + } + plugin->port = port; + + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + _("Using port %u\n"), plugin->port); + + if ((plugin->use_ipv4 == GNUNET_YES) && + (GNUNET_YES == GNUNET_CONFIGURATION_get_value_string (plugin->env->cfg, + plugin->name, "BINDTO", &bind4_address))) + { + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + "Binding %s plugin to specific IPv4 address: `%s'\n", + plugin->protocol, bind4_address); + plugin->server_addr_v4 = GNUNET_malloc (sizeof (struct sockaddr_in)); + if (1 != inet_pton (AF_INET, bind4_address, + &plugin->server_addr_v4->sin_addr)) + { + GNUNET_log_from (GNUNET_ERROR_TYPE_ERROR, plugin->name, + _ + ("Specific IPv4 address `%s' in configuration file is invalid!\n"), + bind4_address); + GNUNET_free (bind4_address); + GNUNET_free (plugin->server_addr_v4); + plugin->server_addr_v4 = NULL; + return GNUNET_SYSERR; + } + else + { + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + _("Binding to IPv4 address %s\n"), bind4_address); + plugin->server_addr_v4->sin_family = AF_INET; + plugin->server_addr_v4->sin_port = htons (plugin->port); + } + GNUNET_free (bind4_address); + } + + if ((plugin->use_ipv6 == GNUNET_YES) && + (GNUNET_YES == + GNUNET_CONFIGURATION_get_value_string (plugin->env->cfg, plugin->name, + "BINDTO6", &bind6_address))) + { + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + "Binding %s plugin to specific IPv6 address: `%s'\n", + plugin->protocol, bind6_address); + plugin->server_addr_v6 = GNUNET_malloc (sizeof (struct sockaddr_in6)); + if (1 != + inet_pton (AF_INET6, bind6_address, &plugin->server_addr_v6->sin6_addr)) + { + GNUNET_log_from (GNUNET_ERROR_TYPE_ERROR, plugin->name, + _ + ("Specific IPv6 address `%s' in configuration file is invalid!\n"), + bind6_address); + GNUNET_free (bind6_address); + GNUNET_free (plugin->server_addr_v6); + plugin->server_addr_v6 = NULL; + return GNUNET_SYSERR; + } + else + { + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + _("Binding to IPv6 address %s\n"), bind6_address); + plugin->server_addr_v6->sin6_family = AF_INET6; + plugin->server_addr_v6->sin6_port = htons (plugin->port); + } + GNUNET_free (bind6_address); + } + + if (GNUNET_YES == GNUNET_CONFIGURATION_get_value_string (plugin->env->cfg, plugin->name, + "EXTERNAL_HOSTNAME", &plugin->external_hostname)) + { + char * tmp = NULL; + if (NULL != strstr(plugin->external_hostname, "://")) { - msg->transmit_cont (msg->transmit_cont_cls, &s->target, GNUNET_SYSERR); + tmp = strdup(&strstr(plugin->external_hostname, "://")[3]); + GNUNET_free (plugin->external_hostname); + plugin->external_hostname = tmp; + } - GNUNET_free (msg); - msg = tmp; - } + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + _("Using external hostname `%s'\n"), plugin->external_hostname); + plugin->notify_ext_task = GNUNET_SCHEDULER_add_now (&server_notify_external_hostname, plugin); - delete_session (s); - s = t; + /* Use only configured external hostname */ + if (GNUNET_CONFIGURATION_have_value + (plugin->env->cfg, plugin->name, "EXTERNAL_HOSTNAME_ONLY")) + { + plugin->external_only = + GNUNET_CONFIGURATION_get_value_yesno (plugin->env->cfg, plugin->name, + "EXTERNAL_HOSTNAME_ONLY"); + } + else + plugin->external_only = GNUNET_NO; + + if (GNUNET_YES == plugin->external_only) + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + _("Notifying transport only about hostname `%s'\n"), plugin->external_hostname); } + else + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + "No external hostname configured\n"); - p = NULL; + /* Optional parameters */ + if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_number (plugin->env->cfg, + plugin->name, + "MAX_CONNECTIONS", &max_connections)) + max_connections = 128; + plugin->max_connections = max_connections; + + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + _("Maximum number of connections is %u\n"), + plugin->max_connections); + + + plugin->peer_id_length = strlen (GNUNET_h2s_full (&plugin->env->my_identity->hashPubKey)); + + return GNUNET_OK; +} + + +/** + * Session was idle, so disconnect it + * + * @param cls the session + * @param tc task context + */ +static void +server_session_timeout (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + GNUNET_assert (NULL != cls); + struct Session *s = cls; + + s->timeout_task = GNUNET_SCHEDULER_NO_TASK; + GNUNET_log (TIMEOUT_LOG, + "Session %p was idle for %llu ms, disconnecting\n", + s, (unsigned long long) SERVER_SESSION_TIMEOUT.rel_value); + + /* call session destroy function */ + GNUNET_assert (GNUNET_OK == server_disconnect (s)); +} + + +/** +* Start session timeout for session s +* +* @param s the session +*/ +static void +server_start_session_timeout (struct Session *s) +{ + GNUNET_assert (NULL != s); + GNUNET_assert (GNUNET_SCHEDULER_NO_TASK == s->timeout_task); + s->timeout_task = GNUNET_SCHEDULER_add_delayed (SERVER_SESSION_TIMEOUT, + &server_session_timeout, + s); + GNUNET_log (TIMEOUT_LOG, + "Timeout for session %p set to %llu ms\n", + s, (unsigned long long) SERVER_SESSION_TIMEOUT.rel_value); +} + + +/** +* Increment session timeout due to activity session s +* +* @param s the session +*/ +static void +server_reschedule_session_timeout (struct Session *s) +{ + GNUNET_assert (NULL != s); + GNUNET_assert (GNUNET_SCHEDULER_NO_TASK != s->timeout_task); + + GNUNET_SCHEDULER_cancel (s->timeout_task); + s->timeout_task = GNUNET_SCHEDULER_add_delayed (SERVER_SESSION_TIMEOUT, + &server_session_timeout, + s); + GNUNET_log (TIMEOUT_LOG, + "Timeout rescheduled for session %p set to %llu ms\n", + s, (unsigned long long) SERVER_SESSION_TIMEOUT.rel_value); +} + + +/** + * Exit point from the plugin. + * + * @param cls api + * @return NULL + */ +void * +LIBGNUNET_PLUGIN_TRANSPORT_DONE (void *cls) +{ + struct GNUNET_TRANSPORT_PluginFunctions *api = cls; + struct HTTP_Server_Plugin *plugin = api->cls; + struct Session *pos; + struct Session *next; + + if (NULL == api->cls) + { + /* Free for stub mode */ + GNUNET_free (api); + return NULL; + } + plugin->in_shutdown = GNUNET_YES; + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + _("Shutting down plugin `%s'\n"), + plugin->name); + if (GNUNET_SCHEDULER_NO_TASK != plugin->notify_ext_task) + { + GNUNET_SCHEDULER_cancel (plugin->notify_ext_task); + plugin->notify_ext_task = GNUNET_SCHEDULER_NO_TASK; + } + + if (NULL != plugin->ext_addr) + { + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + "Notifying transport to remove address `%s'\n", + http_common_plugin_address_to_string (NULL, + plugin->ext_addr, + plugin->ext_addr_len)); #if BUILD_HTTPS - GNUNET_free_non_null (plugin->crypto_init); - GNUNET_free_non_null (plugin->cert); - GNUNET_free_non_null (plugin->key); + plugin->env->notify_address (plugin->env->cls, + GNUNET_NO, + plugin->ext_addr, + plugin->ext_addr_len, + "https_client"); +#else + plugin->env->notify_address (plugin->env->cls, + GNUNET_NO, + plugin->ext_addr, + plugin->ext_addr_len, + "http_client"); #endif + } + + /* Stop to report addresses to transport service */ + server_stop_report_addresses (plugin); + server_stop (plugin); + next = plugin->head; + while (NULL != (pos = next)) + { + next = pos->next; + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, + "Removing left over session %p\n", pos); + + if ((GNUNET_YES == pos->session_passed) && (GNUNET_NO == pos->session_ended)) + { + /* Notify transport immediately that this session is invalid */ + pos->session_ended = GNUNET_YES; + plugin->env->session_end (plugin->env->cls, &pos->target, pos); + } + + server_delete_session (pos); + } + + /* Clean up */ + GNUNET_free_non_null (plugin->external_hostname); + GNUNET_free_non_null (plugin->ext_addr); + GNUNET_free_non_null (plugin->server_addr_v4); + GNUNET_free_non_null (plugin->server_addr_v6); + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, plugin->name, - "%s server component stopped\n", plugin->name); + _("Shutdown for plugin `%s' complete\n"), + plugin->name); + + GNUNET_free (plugin); + GNUNET_free (api); + return NULL; } +/** + * Entry point for the plugin. + * + * @param cls env + * @return api + */ +void * +LIBGNUNET_PLUGIN_TRANSPORT_INIT (void *cls) +{ + struct GNUNET_TRANSPORT_PluginEnvironment *env = cls; + struct GNUNET_TRANSPORT_PluginFunctions *api; + struct HTTP_Server_Plugin *plugin; + + plugin = GNUNET_malloc (sizeof (struct HTTP_Server_Plugin)); + plugin->env = env; + p = plugin; + + if (NULL == env->receive) + { + /* run in 'stub' mode (i.e. as part of gnunet-peerinfo), don't fully + initialze the plugin or the API */ + api = GNUNET_malloc (sizeof (struct GNUNET_TRANSPORT_PluginFunctions)); + api->cls = NULL; + api->address_to_string = &http_common_plugin_address_to_string; + api->string_to_address = &http_common_plugin_string_to_address; + api->address_pretty_printer = &http_common_plugin_address_pretty_printer; + return api; + } + + api = GNUNET_malloc (sizeof (struct GNUNET_TRANSPORT_PluginFunctions)); + api->cls = plugin; + api->send = &http_server_plugin_send; + api->disconnect = &http_server_plugin_disconnect; + api->check_address = &http_server_plugin_address_suggested; + api->get_session = &http_server_plugin_get_session; + + api->address_to_string = &http_common_plugin_address_to_string; + api->string_to_address = &http_common_plugin_string_to_address; + api->address_pretty_printer = &http_common_plugin_address_pretty_printer; + +#if BUILD_HTTPS + plugin->name = "transport-https_server"; + plugin->protocol = "https"; +#else + plugin->name = "transport-http_server"; + plugin->protocol = "http"; +#endif + + /* Configure plugin */ + if (GNUNET_SYSERR == server_configure_plugin (plugin)) + { + LIBGNUNET_PLUGIN_TRANSPORT_DONE (api); + return NULL; + } + + /* Check IPv6 support */ + if (GNUNET_YES == plugin->use_ipv6) + plugin->use_ipv6 = server_check_ipv6_support (plugin); + + /* Report addresses to transport service */ + if (GNUNET_NO == plugin->external_only) + server_start_report_addresses (plugin); + + if (GNUNET_SYSERR == server_start (plugin)) + { + LIBGNUNET_PLUGIN_TRANSPORT_DONE (api); + return NULL; + } + + return api; +} -/* end of plugin_transport_http.c */ +/* end of plugin_transport_http_server.c */ diff --git a/src/transport/plugin_transport_tcp.c b/src/transport/plugin_transport_tcp.c index af5c715..07abc46 100644 --- a/src/transport/plugin_transport_tcp.c +++ b/src/transport/plugin_transport_tcp.c @@ -223,6 +223,11 @@ struct PendingMessage */ struct Session { + /** + * To whom are we talking to (set to our identity + * if we are still waiting for the welcome message) + */ + struct GNUNET_PeerIdentity target; /** * API requirement. @@ -261,12 +266,6 @@ struct Session */ struct GNUNET_SERVER_TransmitHandle *transmit_handle; - /** - * To whom are we talking to (set to our identity - * if we are still waiting for the welcome message) - */ - struct GNUNET_PeerIdentity target; - /** * ID of task used to delay receiving more to throttle sender. */ @@ -385,6 +384,11 @@ struct Plugin */ unsigned long long max_connections; + /** + * How many more TCP sessions do we have right now? + */ + unsigned long long cur_connections; + /** * ID of task used to update our addresses when one expires. */ @@ -487,12 +491,12 @@ plugin_tcp_access_check (void *cls, const struct sockaddr *addr, socklen_t addrlen) { struct Plugin *plugin = cls; - LOG (GNUNET_ERROR_TYPE_DEBUG, - "Accepting new incoming TCP connection\n"); - if (0 == plugin->max_connections) + "Accepting new incoming TCP connection from `%s'\n", + GNUNET_a2s (addr, addrlen)); + if (plugin->cur_connections >= plugin->max_connections) return GNUNET_NO; - plugin->max_connections--; + plugin->cur_connections ++; return GNUNET_YES; } @@ -542,7 +546,7 @@ tcp_nat_port_map_callback (void *cls, int add_remove, return; } /* modify our published address list */ - plugin->env->notify_address (plugin->env->cls, add_remove, arg, args); + plugin->env->notify_address (plugin->env->cls, add_remove, arg, args, "tcp"); } @@ -684,7 +688,7 @@ struct SessionClientCtx static int session_lookup_by_client_it (void *cls, - const GNUNET_HashCode * key, + const struct GNUNET_HashCode * key, void *value) { struct SessionClientCtx *sc_ctx = cls; @@ -734,7 +738,7 @@ static struct Session * create_session (struct Plugin *plugin, const struct GNUNET_PeerIdentity *target, struct GNUNET_SERVER_Client *client, int is_nat) { - struct Session *ret; + struct Session *session; struct PendingMessage *pm; struct WelcomeMessage welcome; @@ -746,14 +750,14 @@ create_session (struct Plugin *plugin, const struct GNUNET_PeerIdentity *target, LOG (GNUNET_ERROR_TYPE_DEBUG, "Creating new session for peer `%4s'\n", GNUNET_i2s (target)); - ret = GNUNET_malloc (sizeof (struct Session)); - ret->last_activity = GNUNET_TIME_absolute_get (); - ret->plugin = plugin; - ret->is_nat = is_nat; - ret->client = client; - ret->target = *target; - ret->expecting_welcome = GNUNET_YES; - ret->ats_address_network_type = htonl (GNUNET_ATS_NET_UNSPECIFIED); + session = GNUNET_malloc (sizeof (struct Session)); + session->last_activity = GNUNET_TIME_absolute_get (); + session->plugin = plugin; + session->is_nat = is_nat; + session->client = client; + session->target = *target; + session->expecting_welcome = GNUNET_YES; + session->ats_address_network_type = htonl (GNUNET_ATS_NET_UNSPECIFIED); pm = GNUNET_malloc (sizeof (struct PendingMessage) + sizeof (struct WelcomeMessage)); pm->msg = (const char *) &pm[1]; @@ -766,17 +770,17 @@ create_session (struct Plugin *plugin, const struct GNUNET_PeerIdentity *target, GNUNET_STATISTICS_update (plugin->env->stats, gettext_noop ("# bytes currently in TCP buffers"), pm->message_size, GNUNET_NO); - GNUNET_CONTAINER_DLL_insert (ret->pending_messages_head, - ret->pending_messages_tail, pm); + GNUNET_CONTAINER_DLL_insert (session->pending_messages_head, + session->pending_messages_tail, pm); if (GNUNET_YES != is_nat) { GNUNET_STATISTICS_update (plugin->env->stats, gettext_noop ("# TCP sessions active"), 1, GNUNET_NO); } - start_session_timeout (ret); + start_session_timeout (session); - return ret; + return session; } @@ -849,7 +853,7 @@ do_transmit (void *cls, size_t size, void *buf) { GNUNET_CONTAINER_DLL_remove (hd, tl, pos); if (pos->transmit_cont != NULL) - pos->transmit_cont (pos->transmit_cont_cls, &pid, GNUNET_SYSERR); + pos->transmit_cont (pos->transmit_cont_cls, &pid, GNUNET_SYSERR, pos->message_size, 0); GNUNET_free (pos); } GNUNET_STATISTICS_update (plugin->env->stats, @@ -895,7 +899,7 @@ do_transmit (void *cls, size_t size, void *buf) { GNUNET_CONTAINER_DLL_remove (hd, tl, pos); if (pos->transmit_cont != NULL) - pos->transmit_cont (pos->transmit_cont_cls, &pid, GNUNET_OK); + pos->transmit_cont (pos->transmit_cont_cls, &pid, GNUNET_OK, pos->message_size, pos->message_size); /* FIXME: include TCP overhead */ GNUNET_free (pos); } GNUNET_assert (hd == NULL); @@ -999,7 +1003,7 @@ disconnect_session (struct Session *session) session->pending_messages_tail, pm); if (NULL != pm->transmit_cont) pm->transmit_cont (pm->transmit_cont_cls, &session->target, - GNUNET_SYSERR); + GNUNET_SYSERR, pm->message_size, 0); GNUNET_free (pm); } if (session->receive_delay_task != GNUNET_SCHEDULER_NO_TASK) @@ -1020,6 +1024,48 @@ disconnect_session (struct Session *session) } +struct FindSessionContext +{ + struct Session *s; + int res; +}; + +int session_it (void *cls, + const struct GNUNET_HashCode * key, + void *value) +{ + struct FindSessionContext *res = cls; + if (res->s == value) + { + res->res = GNUNET_OK; + return GNUNET_NO; + } + else + return GNUNET_YES; +} + +int find_session (struct Plugin *plugin, struct Session *session) +{ + struct FindSessionContext session_map_res; + struct FindSessionContext nat_map_res; + + session_map_res.s = session; + session_map_res.res = GNUNET_SYSERR; + GNUNET_CONTAINER_multihashmap_iterate (plugin->sessionmap, &session_it, &session_map_res); + + nat_map_res.s = session; + nat_map_res.res = GNUNET_SYSERR; + GNUNET_CONTAINER_multihashmap_iterate (plugin->nat_wait_conns, &session_it, &nat_map_res); + + if ((session_map_res.res == GNUNET_SYSERR) && (nat_map_res.res == GNUNET_SYSERR)) + { + GNUNET_break (0); + return GNUNET_SYSERR; + } + return GNUNET_OK; +} + + /** * Function that can be used by the transport service to transmit * a message using the plugin. Note that in the case of a @@ -1061,6 +1107,13 @@ tcp_plugin_send (void *cls, GNUNET_assert (NULL != plugin); GNUNET_assert (NULL != session); + if (GNUNET_SYSERR == find_session(plugin, session)) + { + LOG (GNUNET_ERROR_TYPE_ERROR, + _("Trying to send with invalid session %p\n")); + return GNUNET_SYSERR; + } + /* create new message entry */ pm = GNUNET_malloc (sizeof (struct PendingMessage) + msgbuf_size); pm->msg = (const char *) &pm[1]; @@ -1074,12 +1127,12 @@ tcp_plugin_send (void *cls, "Asked to transmit %u bytes to `%s', added message to list.\n", msgbuf_size, GNUNET_i2s (&session->target)); - reschedule_session_timeout (session); - - if (GNUNET_YES == GNUNET_CONTAINER_multihashmap_contains_value(plugin->sessionmap, &session->target.hashPubKey, session)) + if (GNUNET_YES == GNUNET_CONTAINER_multihashmap_contains_value (plugin->sessionmap, + &session->target.hashPubKey, + session)) { GNUNET_assert (session->client != NULL); - + reschedule_session_timeout (session); GNUNET_SERVER_client_set_timeout (session->client, GNUNET_CONSTANTS_IDLE_CONNECTION_TIMEOUT); GNUNET_STATISTICS_update (plugin->env->stats, @@ -1098,7 +1151,7 @@ tcp_plugin_send (void *cls, LOG (GNUNET_ERROR_TYPE_DEBUG, "This NAT WAIT session for peer `%s' is not yet ready!\n", GNUNET_i2s (&session->target)); - + reschedule_session_timeout (session); GNUNET_STATISTICS_update (plugin->env->stats, gettext_noop ("# bytes currently in TCP buffers"), msgbuf_size, GNUNET_NO); @@ -1110,8 +1163,10 @@ tcp_plugin_send (void *cls, } else { + LOG (GNUNET_ERROR_TYPE_ERROR, + "Invalid session %p\n", session); if (NULL != cont) - cont (cont_cls, &session->target, GNUNET_SYSERR); + cont (cont_cls, &session->target, GNUNET_SYSERR, pm->message_size, 0); GNUNET_break (0); GNUNET_free (pm); return GNUNET_SYSERR; /* session does not exist here */ @@ -1129,7 +1184,7 @@ struct SessionItCtx static int session_lookup_it (void *cls, - const GNUNET_HashCode *key, + const struct GNUNET_HashCode *key, void *value) { struct SessionItCtx * si_ctx = cls; @@ -1180,6 +1235,7 @@ nat_connect_timeout (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { struct Session *session = cls; + session->nat_connection_timeout = GNUNET_SCHEDULER_NO_TASK; LOG (GNUNET_ERROR_TYPE_DEBUG, "NAT WAIT connection to `%4s' at `%s' could not be established, removing session\n", GNUNET_i2s (&session->target), tcp_address_to_string(NULL, session->addr, session->addrlen)); @@ -1200,8 +1256,8 @@ static struct Session * tcp_plugin_get_session (void *cls, const struct GNUNET_HELLO_Address *address) { - struct Plugin * plugin = cls; - struct Session * session = NULL; + struct Plugin *plugin = cls; + struct Session *session = NULL; int af; const void *sb; size_t sbs; @@ -1224,7 +1280,8 @@ tcp_plugin_get_session (void *cls, /* look for existing session */ if (GNUNET_YES == - GNUNET_CONTAINER_multihashmap_contains(plugin->sessionmap, &address->peer.hashPubKey)) + GNUNET_CONTAINER_multihashmap_contains (plugin->sessionmap, + &address->peer.hashPubKey)) { struct SessionItCtx si_ctx; @@ -1233,7 +1290,9 @@ tcp_plugin_get_session (void *cls, si_ctx.result = NULL; - GNUNET_CONTAINER_multihashmap_get_multiple(plugin->sessionmap, &address->peer.hashPubKey, &session_lookup_it, &si_ctx); + GNUNET_CONTAINER_multihashmap_get_multiple (plugin->sessionmap, + &address->peer.hashPubKey, + &session_lookup_it, &si_ctx); if (si_ctx.result != NULL) { session = si_ctx.result; @@ -1300,7 +1359,7 @@ tcp_plugin_get_session (void *cls, return NULL; } - if (0 == plugin->max_connections) + if (plugin->cur_connections >= plugin->max_connections) { /* saturated */ return NULL; @@ -1326,13 +1385,15 @@ tcp_plugin_get_session (void *cls, session->addrlen = 0; session->addr = NULL; session->ats_address_network_type = ats.value; - session->nat_connection_timeout = GNUNET_SCHEDULER_add_delayed(NAT_TIMEOUT, - &nat_connect_timeout, - session); + session->nat_connection_timeout = GNUNET_SCHEDULER_add_delayed (NAT_TIMEOUT, + &nat_connect_timeout, + session); GNUNET_assert (session != NULL); - GNUNET_assert (GNUNET_CONTAINER_multihashmap_put - (plugin->nat_wait_conns, &address->peer.hashPubKey, session, - GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY) == GNUNET_OK); + GNUNET_assert (GNUNET_OK == + GNUNET_CONTAINER_multihashmap_put (plugin->nat_wait_conns, + &session->target.hashPubKey, + session, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY)); LOG (GNUNET_ERROR_TYPE_DEBUG, "Created NAT WAIT connection to `%4s' at `%s'\n", @@ -1351,16 +1412,18 @@ tcp_plugin_get_session (void *cls, } /* create new outbound session */ - GNUNET_assert (0 != plugin->max_connections); + GNUNET_assert (plugin->cur_connections <= plugin->max_connections); sa = GNUNET_CONNECTION_create_from_sockaddr (af, sb, sbs); if (sa == NULL) { LOG (GNUNET_ERROR_TYPE_DEBUG, "Failed to create connection to `%4s' at `%s'\n", - GNUNET_i2s (&session->target), GNUNET_a2s (sb, sbs)); + GNUNET_i2s (&address->peer), GNUNET_a2s (sb, sbs)); return NULL; } - plugin->max_connections--; + plugin->cur_connections++; + if (plugin->cur_connections == plugin->max_connections) + GNUNET_SERVER_suspend (plugin->server); /* Maximum number of connections rechead */ LOG (GNUNET_ERROR_TYPE_DEBUG, "Asked to transmit to `%4s', creating fresh session using address `%s'.\n", @@ -1375,9 +1438,11 @@ tcp_plugin_get_session (void *cls, session->addrlen = addrlen; session->ats_address_network_type = ats.value; - GNUNET_CONTAINER_multihashmap_put(plugin->sessionmap, &address->peer.hashPubKey, session, GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE); + GNUNET_CONTAINER_multihashmap_put (plugin->sessionmap, + &session->target.hashPubKey, + session, GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE); inc_sessions (plugin, session, __LINE__); - LOG (GNUNET_ERROR_TYPE_DEBUG, + LOG (GNUNET_ERROR_TYPE_DEBUG, "Creating new session for `%s' address `%s' session %p\n", GNUNET_i2s (&address->peer), tcp_address_to_string(NULL, address->address, address->address_length), @@ -1391,7 +1456,7 @@ tcp_plugin_get_session (void *cls, static int session_disconnect_it (void *cls, - const GNUNET_HashCode * key, + const struct GNUNET_HashCode * key, void *value) { struct Session *session = value; @@ -1661,7 +1726,7 @@ handle_tcp_nat_probe (void *cls, struct GNUNET_SERVER_Client *client, const struct sockaddr_in *s4; const struct sockaddr_in6 *s6; - LOG (GNUNET_ERROR_TYPE_DEBUG, "received NAT probe\n"); + LOG (GNUNET_ERROR_TYPE_DEBUG, "Received NAT probe\n"); /* We have received a TCP NAT probe, meaning we (hopefully) initiated * a connection to this peer by running gnunet-nat-client. This peer @@ -1717,9 +1782,9 @@ handle_tcp_nat_probe (void *cls, struct GNUNET_SERVER_Client *client, (plugin->nat_wait_conns, &tcp_nat_probe->clientIdentity.hashPubKey, session) == GNUNET_YES); - GNUNET_CONTAINER_multihashmap_put(plugin->sessionmap, - &session->target.hashPubKey, session, - GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE); + GNUNET_CONTAINER_multihashmap_put (plugin->sessionmap, + &session->target.hashPubKey, session, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE); session->last_activity = GNUNET_TIME_absolute_get (); session->inbound = GNUNET_NO; LOG (GNUNET_ERROR_TYPE_DEBUG, @@ -1816,6 +1881,11 @@ handle_tcp_welcome (void *cls, struct GNUNET_SERVER_Client *client, else { GNUNET_SERVER_client_keep (client); + if (plugin->service != NULL) /* Otherwise value is incremented in tcp_access_check */ + plugin->cur_connections++; + if (plugin->cur_connections == plugin->max_connections) + GNUNET_SERVER_suspend (plugin->server); /* Maximum number of connections rechead */ + session = create_session (plugin, &wm->clientIdentity, client, GNUNET_NO); session->inbound = GNUNET_YES; if (GNUNET_OK == GNUNET_SERVER_client_get_address (client, &vaddr, &alen)) @@ -1850,7 +1920,10 @@ handle_tcp_welcome (void *cls, struct GNUNET_SERVER_Client *client, LOG (GNUNET_ERROR_TYPE_DEBUG, "Did not obtain TCP socket address for incoming connection\n"); } - GNUNET_CONTAINER_multihashmap_put(plugin->sessionmap, &wm->clientIdentity.hashPubKey, session, GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE); + GNUNET_CONTAINER_multihashmap_put (plugin->sessionmap, + &session->target.hashPubKey, + session, + GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE); inc_sessions (plugin, session, __LINE__); } @@ -1988,7 +2061,7 @@ handle_tcp_data (void *cls, struct GNUNET_SERVER_Client *client, &session->target, message, (const struct GNUNET_ATS_Information *) &distance, - 1, session, + 2, session, (GNUNET_YES == session->inbound) ? NULL : session->addr, (GNUNET_YES == session->inbound) ? 0 : session->addrlen); @@ -2026,11 +2099,10 @@ disconnect_notify (void *cls, struct GNUNET_SERVER_Client *client) if (client == NULL) return; - plugin->max_connections++; session = lookup_session_by_client (plugin, client); if (session == NULL) return; /* unknown, nothing to do */ - LOG (GNUNET_ERROR_TYPE_DEBUG, + LOG (GNUNET_ERROR_TYPE_DEBUG, "Destroying session of `%4s' with %s due to network-level disconnect.\n", GNUNET_i2s (&session->target), (session->addr != @@ -2038,6 +2110,15 @@ disconnect_notify (void *cls, struct GNUNET_SERVER_Client *client) session->addr, session->addrlen) : "*"); + + if (plugin->cur_connections == plugin->max_connections) + GNUNET_SERVER_resume (plugin->server); /* Resume server */ + + if (plugin->cur_connections < 1) + GNUNET_break (0); + else + plugin->cur_connections--; + GNUNET_STATISTICS_update (session->plugin->env->stats, gettext_noop ("# network-level TCP disconnect events"), 1, @@ -2143,8 +2224,8 @@ session_timeout (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) s->timeout_task = GNUNET_SCHEDULER_NO_TASK; GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Session %p was idle for %llu, disconnecting\n", - s, GNUNET_CONSTANTS_IDLE_CONNECTION_TIMEOUT.rel_value); + "Session %p was idle for %llu ms, disconnecting\n", + s, (unsigned long long) GNUNET_CONSTANTS_IDLE_CONNECTION_TIMEOUT.rel_value); /* call session destroy function */ disconnect_session(s); } @@ -2161,10 +2242,9 @@ start_session_timeout (struct Session *s) s->timeout_task = GNUNET_SCHEDULER_add_delayed (GNUNET_CONSTANTS_IDLE_CONNECTION_TIMEOUT, &session_timeout, s); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Timeout for session %p set to %llu\n", - s, - GNUNET_CONSTANTS_IDLE_CONNECTION_TIMEOUT.rel_value); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Timeout for session %p set to %llu ms\n", + s, (unsigned long long) GNUNET_CONSTANTS_IDLE_CONNECTION_TIMEOUT.rel_value); } @@ -2175,21 +2255,15 @@ static void reschedule_session_timeout (struct Session *s) { GNUNET_assert (NULL != s); - if (GNUNET_SCHEDULER_NO_TASK == s->timeout_task) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, - "Timeout for peer `%s' %s not scheduled\n", - GNUNET_i2s (&s->target), - tcp_address_to_string(NULL, s->addr, s->addrlen)); - return; - } + GNUNET_assert (GNUNET_SCHEDULER_NO_TASK != s->timeout_task); + GNUNET_SCHEDULER_cancel (s->timeout_task); s->timeout_task = GNUNET_SCHEDULER_add_delayed (GNUNET_CONSTANTS_IDLE_CONNECTION_TIMEOUT, &session_timeout, s); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Timeout rescheduled for session %p set to %llu\n", - s, - (unsigned long long) GNUNET_CONSTANTS_IDLE_CONNECTION_TIMEOUT.rel_value); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Timeout rescheduled for session %p set to %llu ms\n", + s, (unsigned long long) GNUNET_CONSTANTS_IDLE_CONNECTION_TIMEOUT.rel_value); } @@ -2200,19 +2274,14 @@ static void stop_session_timeout (struct Session *s) { GNUNET_assert (NULL != s); + if (GNUNET_SCHEDULER_NO_TASK != s->timeout_task) { GNUNET_SCHEDULER_cancel (s->timeout_task); s->timeout_task = GNUNET_SCHEDULER_NO_TASK; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Timeout rescheduled for session %p canceled\n", - s, GNUNET_CONSTANTS_IDLE_CONNECTION_TIMEOUT.rel_value); - } - else - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Timeout for session %p was not active\n", - s); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Timeout stopped for session %p canceled\n", + s, (unsigned long long) GNUNET_CONSTANTS_IDLE_CONNECTION_TIMEOUT.rel_value); } } @@ -2259,6 +2328,8 @@ libgnunet_plugin_transport_tcp_init (void *cls) return api; } + GNUNET_assert (NULL != env->cfg); + GNUNET_assert (NULL != env->stats); if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_number (env->cfg, "transport-tcp", "MAX_CONNECTIONS", @@ -2298,8 +2369,9 @@ libgnunet_plugin_transport_tcp_init (void *cls) service = NULL; plugin = GNUNET_malloc (sizeof (struct Plugin)); - plugin->sessionmap = GNUNET_CONTAINER_multihashmap_create(max_connections); + plugin->sessionmap = GNUNET_CONTAINER_multihashmap_create (max_connections, GNUNET_YES); plugin->max_connections = max_connections; + plugin->cur_connections = 0; plugin->open_port = bport; plugin->adv_port = aport; plugin->env = env; @@ -2326,8 +2398,8 @@ libgnunet_plugin_transport_tcp_init (void *cls) } else { - plugin->nat = - GNUNET_NAT_register (env->cfg, GNUNET_YES, 0, 0, NULL, NULL, NULL, + plugin->nat = GNUNET_NAT_register (plugin->env->cfg, + GNUNET_YES, 0, 0, NULL, NULL, NULL, &try_connection_reversal, plugin); } api = GNUNET_malloc (sizeof (struct GNUNET_TRANSPORT_PluginFunctions)); @@ -2351,9 +2423,8 @@ libgnunet_plugin_transport_tcp_init (void *cls) GNUNET_CONFIGURATION_get_value_time (env->cfg, "transport-tcp", "TIMEOUT", &idle_timeout)) { - LOG (GNUNET_ERROR_TYPE_ERROR, - _("Failed to find option %s in section %s!\n"), - "TIMEOUT", "transport-tcp"); + GNUNET_log_config_missing (GNUNET_ERROR_TYPE_ERROR, + "transport-tcp", "TIMEOUT"); if (plugin->nat != NULL) GNUNET_NAT_unregister (plugin->nat); GNUNET_free (plugin); @@ -2370,9 +2441,10 @@ libgnunet_plugin_transport_tcp_init (void *cls) i < sizeof (my_handlers) / sizeof (struct GNUNET_SERVER_MessageHandler); i++) plugin->handlers[i].callback_cls = plugin; + GNUNET_SERVER_add_handlers (plugin->server, plugin->handlers); GNUNET_SERVER_disconnect_notify (plugin->server, &disconnect_notify, plugin); - plugin->nat_wait_conns = GNUNET_CONTAINER_multihashmap_create (16); + plugin->nat_wait_conns = GNUNET_CONTAINER_multihashmap_create (16, GNUNET_YES); if (bport != 0) LOG (GNUNET_ERROR_TYPE_INFO, _("TCP transport listening on port %llu\n"), bport); diff --git a/src/transport/plugin_transport_template.c b/src/transport/plugin_transport_template.c index d307262..8c15f87 100644 --- a/src/transport/plugin_transport_template.c +++ b/src/transport/plugin_transport_template.c @@ -54,6 +54,11 @@ struct Plugin; */ struct Session { + /** + * To whom are we talking to (set to our identity + * if we are still waiting for the welcome message) + */ + struct GNUNET_PeerIdentity sender; /** * Stored in a linked list. @@ -82,12 +87,6 @@ struct Session */ void *transmit_cont_cls; - /** - * To whom are we talking to (set to our identity - * if we are still waiting for the welcome message) - */ - struct GNUNET_PeerIdentity sender; - /** * At what time did we reset last_received last? */ @@ -257,7 +256,43 @@ template_plugin_address_to_string (void *cls, const void *addr, size_t addrlen) } +/** + * Function called to convert a string address to + * a binary address. + * + * @param cls closure ('struct Plugin*') + * @param addr string address + * @param addrlen length of the address + * @param buf location to store the buffer + * @param added location to store the number of bytes in the buffer. + * If the function returns GNUNET_SYSERR, its contents are undefined. + * @return GNUNET_OK on success, GNUNET_SYSERR on failure + */ +static int +template_plugin_string_to_address (void *cls, const char *addr, uint16_t addrlen, + void **buf, size_t *added) +{ + GNUNET_break (0); + return GNUNET_SYSERR; +} + +/** + * Create a new session to transmit data to the target + * This session will used to send data to this peer and the plugin will + * notify us by calling the env->session_end function + * + * @param cls closure + * @param address pointer to the GNUNET_HELLO_Address + * @return the session if the address is valid, NULL otherwise + */ +static struct Session * +template_plugin_get_session (void *cls, + const struct GNUNET_HELLO_Address *address) +{ + GNUNET_break (0); + return NULL; +} /** * Entry point for the plugin. @@ -269,6 +304,18 @@ gnunet_plugin_transport_template_init (void *cls) struct GNUNET_TRANSPORT_PluginFunctions *api; struct Plugin *plugin; + if (NULL == env->receive) + { + /* run in 'stub' mode (i.e. as part of gnunet-peerinfo), don't fully + initialze the plugin or the API */ + api = GNUNET_malloc (sizeof (struct GNUNET_TRANSPORT_PluginFunctions)); + api->cls = NULL; + api->address_to_string = &template_plugin_address_to_string; + api->string_to_address = &template_plugin_string_to_address; + api->address_pretty_printer = &template_plugin_address_pretty_printer; + return api; + } + plugin = GNUNET_malloc (sizeof (struct Plugin)); plugin->env = env; api = GNUNET_malloc (sizeof (struct GNUNET_TRANSPORT_PluginFunctions)); @@ -278,6 +325,9 @@ gnunet_plugin_transport_template_init (void *cls) api->address_pretty_printer = &template_plugin_address_pretty_printer; api->check_address = &template_plugin_address_suggested; api->address_to_string = &template_plugin_address_to_string; + api->string_to_address = &template_plugin_string_to_address; + api->get_session = &template_plugin_get_session; + return api; } diff --git a/src/transport/plugin_transport_udp.c b/src/transport/plugin_transport_udp.c index c5a4c7b..c57ec98 100644 --- a/src/transport/plugin_transport_udp.c +++ b/src/transport/plugin_transport_udp.c @@ -63,6 +63,7 @@ #define UDP_MAX_SENDER_ADDRESSES_WITH_DEFRAG 128 +#define DEBUG_MALLOC GNUNET_NO /** * Closure for 'append_port'. @@ -86,6 +87,16 @@ struct PrettyPrinterContext }; +enum UDP_MessageType +{ + UNDEFINED = 0, + MSG_FRAGMENTED = 1, + MSG_FRAGMENTED_COMPLETE = 2, + MSG_UNFRAGMENTED = 3, + MSG_ACK = 4, + MSG_BEACON = 5 +}; + struct Session { /** @@ -93,7 +104,7 @@ struct Session */ struct GNUNET_PeerIdentity target; - struct FragmentationContext * frag_ctx; + struct UDP_FragmentationContext * frag_ctx; /** * Address of the other peer @@ -118,7 +129,12 @@ struct Session /** * expected delay for ACKs */ - struct GNUNET_TIME_Relative last_expected_delay; + struct GNUNET_TIME_Relative last_expected_ack_delay; + + /** + * desired delay between UDP messages + */ + struct GNUNET_TIME_Relative last_expected_msg_delay; struct GNUNET_ATS_Information ats; @@ -225,15 +241,33 @@ struct DefragContext /** - * Closure for 'process_inbound_tokenized_messages' + * Context to send fragmented messages */ -struct FragmentationContext +struct UDP_FragmentationContext { - struct FragmentationContext * next; - struct FragmentationContext * prev; + /** + * Next in linked list + */ + struct UDP_FragmentationContext * next; + /** + * Previous in linked list + */ + struct UDP_FragmentationContext * prev; + + /** + * The plugin + */ struct Plugin * plugin; + + /** + * Handle for GNUNET_FRAGMENT context + */ struct GNUNET_FRAGMENT_Context * frag; + + /** + * The session this fragmentation context belongs to + */ struct Session * session; /** @@ -246,34 +280,87 @@ struct FragmentationContext */ void *cont_cls; + /** + * Message timeout + */ struct GNUNET_TIME_Absolute timeout; - size_t bytes_to_send; + /** + * Payload size of original unfragmented message + */ + size_t payload_size; + + /** + * Bytes used to send all fragments on wire including UDP overhead + */ + size_t on_wire_size; + + unsigned int fragments_used; + }; -struct UDPMessageWrapper +struct UDP_MessageWrapper { + /** + * Session this message belongs to + */ struct Session *session; - struct UDPMessageWrapper *prev; - struct UDPMessageWrapper *next; - char *udp; /** - * Function to call upon completion of the transmission. + * DLL of messages + * previous element */ - GNUNET_TRANSPORT_TransmitContinuation cont; + struct UDP_MessageWrapper *prev; /** - * Closure for 'cont'. + * DLL of messages + * previous element */ - void *cont_cls; + struct UDP_MessageWrapper *next; - struct FragmentationContext *frag_ctx; + /** + * Message type + * According to UDP_MessageType + */ + int msg_type; + /** + * Message with size msg_size including UDP specific overhead + */ + char *msg_buf; + + /** + * Size of UDP message to send including UDP specific overhead + */ size_t msg_size; + /** + * Payload size of original message + */ + size_t payload_size; + + /** + * Message timeout + */ struct GNUNET_TIME_Absolute timeout; + + /** + * Function to call upon completion of the transmission. + */ + GNUNET_TRANSPORT_TransmitContinuation cont; + + /** + * Closure for 'cont'. + */ + void *cont_cls; + + /** + * Fragmentation context + * frag_ctx == NULL if transport <= MTU + * frag_ctx != NULL if transport > MTU + */ + struct UDP_FragmentationContext *frag_ctx; }; @@ -347,6 +434,226 @@ reschedule_session_timeout (struct Session *s); static void stop_session_timeout (struct Session *s); +#if DEBUG_MALLOC + +struct Allocator +{ + struct Allocator *prev; + struct Allocator *next; + + unsigned int bytes_alloced; + unsigned int max_alloced; + unsigned int diff; + unsigned int line; + + struct GNUNET_TIME_Absolute max_alloced_when; + struct GNUNET_TIME_Absolute last_alloced_when; + +}; + +struct Allocator *aehead; +struct Allocator *aetail; + +struct Allocation +{ + struct Allocation *prev; + struct Allocation *next; + + struct Allocator *alloc; + unsigned int bytes_alloced; + void *p; + unsigned int line; +}; + +struct Allocation *ahead; +struct Allocation *atail; + +static int bytes_alloced; + +static struct Allocator * +find_allocator (int line) +{ + struct Allocator *cur = aehead; + while (NULL != cur) + { + if (line == cur->line) + return cur; + cur = cur->next; + } + return cur; +} + +static void +print_allocators () +{ + static int start = GNUNET_YES; + static struct GNUNET_TIME_Absolute next; + static struct GNUNET_TIME_Relative rem; + struct Allocator *cur = aehead; + if (start) + { + next = GNUNET_TIME_UNIT_ZERO_ABS; + start = GNUNET_NO; + } + if (0 == (rem = GNUNET_TIME_absolute_get_remaining(next)).rel_value) + { + fprintf (stderr, "Allocated in `%s' total: %5u bytes\n", __FILE__, bytes_alloced); + while (NULL != cur) + { + char *last_alloc = GNUNET_strdup (GNUNET_STRINGS_absolute_time_to_string(cur->max_alloced_when)); + fprintf (stderr, "Allocated from line %4u :%5u bytes (diff %5i bytes, max alloc: %5u @ %s, last alloc %s)\n", + cur->line, cur->bytes_alloced, cur->diff, cur->max_alloced, + last_alloc, + GNUNET_STRINGS_absolute_time_to_string(cur->last_alloced_when)); + GNUNET_free (last_alloc); + cur->diff = 0; + cur = cur->next; + } + fprintf (stderr, "\n"); + next = GNUNET_TIME_absolute_add(GNUNET_TIME_absolute_get(), GNUNET_TIME_UNIT_SECONDS); + } +} + +#endif + +static void +MEMDEBUG_add_alloc (void *p, size_t size, int line) +{ +#if DEBUG_MALLOC + struct Allocation *alloc = GNUNET_malloc (sizeof (struct Allocation)); + struct Allocator *allocator = find_allocator(line); + if (NULL == allocator) + { + allocator = GNUNET_malloc (sizeof (struct Allocator)); + allocator->line = line; + GNUNET_CONTAINER_DLL_insert (aehead, aetail, allocator); + } + alloc->alloc = allocator; + alloc->p = p; + alloc->line = line; + alloc->bytes_alloced = size; + allocator->bytes_alloced += size; + allocator->last_alloced_when = GNUNET_TIME_absolute_get(); + if (allocator->bytes_alloced >= allocator->max_alloced) + { + allocator->max_alloced = allocator->bytes_alloced; + allocator->max_alloced_when = allocator->last_alloced_when; + } + allocator->diff += size; + GNUNET_CONTAINER_DLL_insert (ahead, atail, alloc); + print_allocators (); + bytes_alloced += size; +#endif +} + + +static void * +MEMDEBUG_malloc (size_t size, int line) +{ + void * ret; + + ret = GNUNET_malloc (size); +#if DEBUG_MALLOC + if (NULL != ret) + MEMDEBUG_add_alloc (ret, size, line); +#endif + return ret; + +} + +static void +MEMDEBUG_free (void * alloc, int line) +{ +#if DEBUG_MALLOC + struct Allocation *cur; + struct Allocator *allocator; + cur = ahead; + while (NULL != cur) + { + if (alloc == cur->p) + break; + cur = cur->next; + } + if (NULL == cur) + { + fprintf (stderr, "Unmonitored free from line %4u\n", line); + GNUNET_break (0); + return; + } + allocator = cur->alloc; + if (NULL == allocator) + { + GNUNET_break (0); + } + GNUNET_CONTAINER_DLL_remove (ahead, atail, cur); + allocator->bytes_alloced -= cur->bytes_alloced; + allocator->diff -= cur->bytes_alloced; + GNUNET_assert (allocator->bytes_alloced >= 0); + bytes_alloced -= cur->bytes_alloced; + GNUNET_assert (bytes_alloced >= 0); + GNUNET_free (cur); +#endif + GNUNET_free (alloc); +} + +static void +MEMDEBUG_free_non_null (void * alloc, int line) +{ + if (alloc != NULL) + MEMDEBUG_free (alloc, line); +} + + +/** + * (re)schedule select tasks for this plugin. + * + * @param plugin plugin to reschedule + */ +static void +schedule_select (struct Plugin *plugin) +{ + struct GNUNET_TIME_Relative min_delay; + struct UDP_MessageWrapper *udpw; + + if (NULL != plugin->sockv4) + { + /* Find a message ready to send: + * Flow delay from other peer is expired or not set (0) */ + min_delay = GNUNET_TIME_UNIT_FOREVER_REL; + for (udpw = plugin->ipv4_queue_head; NULL != udpw; udpw = udpw->next) + min_delay = GNUNET_TIME_relative_min (min_delay, + GNUNET_TIME_absolute_get_remaining (udpw->session->flow_delay_from_other_peer)); + + if (plugin->select_task != GNUNET_SCHEDULER_NO_TASK) + GNUNET_SCHEDULER_cancel(plugin->select_task); + + /* Schedule with: + * - write active set if message is ready + * - timeout minimum delay */ + plugin->select_task = + GNUNET_SCHEDULER_add_select (GNUNET_SCHEDULER_PRIORITY_DEFAULT, + (0 == min_delay.rel_value) ? GNUNET_TIME_UNIT_FOREVER_REL : min_delay, + plugin->rs_v4, + (0 == min_delay.rel_value) ? plugin->ws_v4 : NULL, + &udp_plugin_select, plugin); + } + if (NULL != plugin->sockv6) + { + min_delay = GNUNET_TIME_UNIT_FOREVER_REL; + for (udpw = plugin->ipv6_queue_head; NULL != udpw; udpw = udpw->next) + min_delay = GNUNET_TIME_relative_min (min_delay, + GNUNET_TIME_absolute_get_remaining (udpw->session->flow_delay_from_other_peer)); + + if (GNUNET_SCHEDULER_NO_TASK != plugin->select_task_v6) + GNUNET_SCHEDULER_cancel(plugin->select_task_v6); + plugin->select_task_v6 = + GNUNET_SCHEDULER_add_select (GNUNET_SCHEDULER_PRIORITY_DEFAULT, + (0 == min_delay.rel_value) ? GNUNET_TIME_UNIT_FOREVER_REL : min_delay, + plugin->rs_v6, + (0 == min_delay.rel_value) ? plugin->ws_v6 : NULL, + &udp_plugin_select_v6, plugin); + } +} /** @@ -447,7 +754,7 @@ udp_string_to_address (void *cls, const char *addr, uint16_t addrlen, { struct IPv4UdpAddress *u4; struct sockaddr_in *in4 = (struct sockaddr_in *) &socket_address; - u4 = GNUNET_malloc (sizeof (struct IPv4UdpAddress)); + u4 = MEMDEBUG_malloc (sizeof (struct IPv4UdpAddress), __LINE__ ); u4->ipv4_addr = in4->sin_addr.s_addr; u4->u4_port = in4->sin_port; *buf = u4; @@ -458,7 +765,7 @@ udp_string_to_address (void *cls, const char *addr, uint16_t addrlen, { struct IPv6UdpAddress *u6; struct sockaddr_in6 *in6 = (struct sockaddr_in6 *) &socket_address; - u6 = GNUNET_malloc (sizeof (struct IPv6UdpAddress)); + u6 = MEMDEBUG_malloc (sizeof (struct IPv6UdpAddress), __LINE__ ); u6->ipv6_addr = in6->sin6_addr; u6->u6_port = in6->sin6_port; *buf = u6; @@ -487,12 +794,13 @@ append_port (void *cls, const char *hostname) if (hostname == NULL) { ppc->asc (ppc->asc_cls, NULL); - GNUNET_free (ppc); + MEMDEBUG_free (ppc, __LINE__); return; } GNUNET_asprintf (&ret, "%s:%d", hostname, ppc->port); + MEMDEBUG_add_alloc (ret, strlen (ret)+ 1, __LINE__); ppc->asc (ppc->asc_cls, ret); - GNUNET_free (ret); + MEMDEBUG_free (ret, __LINE__); } @@ -568,7 +876,7 @@ udp_plugin_address_pretty_printer (void *cls, const char *type, asc (asc_cls, NULL); return; } - ppc = GNUNET_malloc (sizeof (struct PrettyPrinterContext)); + ppc = MEMDEBUG_malloc (sizeof (struct PrettyPrinterContext), __LINE__ ); ppc->asc = asc; ppc->asc_cls = asc_cls; ppc->port = port; @@ -577,17 +885,171 @@ udp_plugin_address_pretty_printer (void *cls, const char *type, static void -call_continuation (struct UDPMessageWrapper *udpw, int result) +call_continuation (struct UDP_MessageWrapper *udpw, int result) { + size_t overhead; + LOG (GNUNET_ERROR_TYPE_DEBUG, "Calling continuation for %u byte message to `%s' with result %s\n", - udpw->msg_size, GNUNET_i2s (&udpw->session->target), + udpw->payload_size, GNUNET_i2s (&udpw->session->target), (GNUNET_OK == result) ? "OK" : "SYSERR"); - if (NULL != udpw->cont) - { - udpw->cont (udpw->cont_cls, &udpw->session->target,result); - } + if (udpw->msg_size >= udpw->payload_size) + overhead = udpw->msg_size - udpw->payload_size; + else + overhead = udpw->msg_size; + + switch (result) { + case GNUNET_OK: + switch (udpw->msg_type) { + case MSG_UNFRAGMENTED: + if (NULL != udpw->cont) + { + /* Transport continuation */ + udpw->cont (udpw->cont_cls, &udpw->session->target, result, + udpw->payload_size, udpw->msg_size); + } + GNUNET_STATISTICS_update (plugin->env->stats, + "# UDP, unfragmented msgs, messages, sent, success", + 1, GNUNET_NO); + GNUNET_STATISTICS_update (plugin->env->stats, + "# UDP, unfragmented msgs, bytes payload, sent, success", + udpw->payload_size, GNUNET_NO); + GNUNET_STATISTICS_update (plugin->env->stats, + "# UDP, unfragmented msgs, bytes overhead, sent, success", + overhead, GNUNET_NO); + GNUNET_STATISTICS_update (plugin->env->stats, + "# UDP, total, bytes overhead, sent", + overhead, GNUNET_NO); + GNUNET_STATISTICS_update (plugin->env->stats, + "# UDP, total, bytes payload, sent", + udpw->payload_size, GNUNET_NO); + break; + case MSG_FRAGMENTED_COMPLETE: + GNUNET_assert (NULL != udpw->frag_ctx); + if (udpw->frag_ctx->cont != NULL) + udpw->frag_ctx->cont (udpw->frag_ctx->cont_cls, &udpw->session->target, GNUNET_OK, + udpw->frag_ctx->payload_size, udpw->frag_ctx->on_wire_size); + GNUNET_STATISTICS_update (plugin->env->stats, + "# UDP, fragmented msgs, messages, sent, success", + 1, GNUNET_NO); + GNUNET_STATISTICS_update (plugin->env->stats, + "# UDP, fragmented msgs, bytes payload, sent, success", + udpw->payload_size, GNUNET_NO); + GNUNET_STATISTICS_update (plugin->env->stats, + "# UDP, fragmented msgs, bytes overhead, sent, success", + overhead, GNUNET_NO); + GNUNET_STATISTICS_update (plugin->env->stats, + "# UDP, total, bytes overhead, sent", + overhead, GNUNET_NO); + GNUNET_STATISTICS_update (plugin->env->stats, + "# UDP, total, bytes payload, sent", + udpw->payload_size, GNUNET_NO); + GNUNET_STATISTICS_update (plugin->env->stats, + "# UDP, fragmented msgs, messages, pending", + -1, GNUNET_NO); + break; + case MSG_FRAGMENTED: + /* Fragmented message: enqueue next fragment */ + if (NULL != udpw->cont) + udpw->cont (udpw->cont_cls, &udpw->session->target, result, + udpw->payload_size, udpw->msg_size); + GNUNET_STATISTICS_update (plugin->env->stats, + "# UDP, fragmented msgs, fragments, sent, success", + 1, GNUNET_NO); + GNUNET_STATISTICS_update (plugin->env->stats, + "# UDP, fragmented msgs, fragments bytes, sent, success", + udpw->msg_size, GNUNET_NO); + break; + case MSG_ACK: + /* No continuation */ + GNUNET_STATISTICS_update (plugin->env->stats, + "# UDP, ACK msgs, messages, sent, success", + 1, GNUNET_NO); + GNUNET_STATISTICS_update (plugin->env->stats, + "# UDP, ACK msgs, bytes overhead, sent, success", + overhead, GNUNET_NO); + GNUNET_STATISTICS_update (plugin->env->stats, + "# UDP, total, bytes overhead, sent", + overhead, GNUNET_NO); + break; + case MSG_BEACON: + GNUNET_break (0); + break; + default: + LOG (GNUNET_ERROR_TYPE_ERROR, + "ERROR: %u\n", udpw->msg_type); + GNUNET_break (0); + break; + } + break; + case GNUNET_SYSERR: + switch (udpw->msg_type) { + case MSG_UNFRAGMENTED: + /* Unfragmented message: failed to send */ + if (NULL != udpw->cont) + udpw->cont (udpw->cont_cls, &udpw->session->target, result, + udpw->payload_size, overhead); + GNUNET_STATISTICS_update (plugin->env->stats, + "# UDP, unfragmented msgs, messages, sent, failure", + 1, GNUNET_NO); + GNUNET_STATISTICS_update (plugin->env->stats, + "# UDP, unfragmented msgs, bytes payload, sent, failure", + udpw->payload_size, GNUNET_NO); + GNUNET_STATISTICS_update (plugin->env->stats, + "# UDP, unfragmented msgs, bytes overhead, sent, failure", + overhead, GNUNET_NO); + break; + case MSG_FRAGMENTED_COMPLETE: + GNUNET_assert (NULL != udpw->frag_ctx); + if (udpw->frag_ctx->cont != NULL) + udpw->frag_ctx->cont (udpw->frag_ctx->cont_cls, &udpw->session->target, GNUNET_SYSERR, + udpw->frag_ctx->payload_size, udpw->frag_ctx->on_wire_size); + GNUNET_STATISTICS_update (plugin->env->stats, + "# UDP, fragmented msgs, messages, sent, failure", + 1, GNUNET_NO); + GNUNET_STATISTICS_update (plugin->env->stats, + "# UDP, fragmented msgs, bytes payload, sent, failure", + udpw->payload_size, GNUNET_NO); + GNUNET_STATISTICS_update (plugin->env->stats, + "# UDP, fragmented msgs, bytes payload, sent, failure", + overhead, GNUNET_NO); + GNUNET_STATISTICS_update (plugin->env->stats, + "# UDP, fragmented msgs, bytes payload, sent, failure", + overhead, GNUNET_NO); + GNUNET_STATISTICS_update (plugin->env->stats, + "# UDP, fragmented msgs, messages, pending", + -1, GNUNET_NO); + break; + case MSG_FRAGMENTED: + GNUNET_assert (NULL != udpw->frag_ctx); + /* Fragmented message: failed to send */ + GNUNET_STATISTICS_update (plugin->env->stats, + "# UDP, fragmented msgs, fragments, sent, failure", + 1, GNUNET_NO); + GNUNET_STATISTICS_update (plugin->env->stats, + "# UDP, fragmented msgs, fragments bytes, sent, failure", + udpw->msg_size, GNUNET_NO); + break; + case MSG_ACK: + /* ACK message: failed to send */ + GNUNET_STATISTICS_update (plugin->env->stats, + "# UDP, ACK msgs, messages, sent, failure", + 1, GNUNET_NO); + break; + case MSG_BEACON: + /* Beacon message: failed to send */ + GNUNET_break (0); + break; + default: + GNUNET_break (0); + break; + } + break; + default: + GNUNET_break (0); + break; + } } @@ -675,16 +1137,101 @@ udp_plugin_check_address (void *cls, const void *addr, size_t addrlen) static void free_session (struct Session *s) { - if (s->frag_ctx != NULL) + if (NULL != s->frag_ctx) { - GNUNET_FRAGMENT_context_destroy(s->frag_ctx->frag); - GNUNET_free (s->frag_ctx); + GNUNET_FRAGMENT_context_destroy(s->frag_ctx->frag, NULL, NULL); + MEMDEBUG_free (s->frag_ctx, __LINE__); s->frag_ctx = NULL; } - GNUNET_free (s); + MEMDEBUG_free (s, __LINE__); } +static void +dequeue (struct Plugin *plugin, struct UDP_MessageWrapper * udpw) +{ + if (plugin->bytes_in_buffer < udpw->msg_size) + GNUNET_break (0); + else + { + GNUNET_STATISTICS_update (plugin->env->stats, + "# UDP, total, bytes in buffers", + - (long long) udpw->msg_size, GNUNET_NO); + plugin->bytes_in_buffer -= udpw->msg_size; + } + GNUNET_STATISTICS_update (plugin->env->stats, + "# UDP, total, msgs in buffers", + -1, GNUNET_NO); + if (udpw->session->addrlen == sizeof (struct sockaddr_in)) + GNUNET_CONTAINER_DLL_remove (plugin->ipv4_queue_head, + plugin->ipv4_queue_tail, udpw); + if (udpw->session->addrlen == sizeof (struct sockaddr_in6)) + GNUNET_CONTAINER_DLL_remove (plugin->ipv6_queue_head, + plugin->ipv6_queue_tail, udpw); +} + +static void +fragmented_message_done (struct UDP_FragmentationContext *fc, int result) +{ + struct UDP_MessageWrapper *udpw; + struct UDP_MessageWrapper *tmp; + struct UDP_MessageWrapper dummy; + struct Session *s = fc->session; + + LOG (GNUNET_ERROR_TYPE_DEBUG, "%p : Fragmented message removed with result %s\n", fc, (result == GNUNET_SYSERR) ? "FAIL" : "SUCCESS"); + + /* Call continuation for fragmented message */ + memset (&dummy, 0, sizeof (dummy)); + dummy.msg_type = MSG_FRAGMENTED_COMPLETE; + dummy.msg_size = s->frag_ctx->on_wire_size; + dummy.payload_size = s->frag_ctx->payload_size; + dummy.frag_ctx = s->frag_ctx; + dummy.cont = NULL; + dummy.cont_cls = NULL; + dummy.session = s; + + call_continuation (&dummy, result); + + /* Remove leftover fragments from queue */ + if (s->addrlen == sizeof (struct sockaddr_in6)) + { + udpw = plugin->ipv6_queue_head; + while (NULL != udpw) + { + tmp = udpw->next; + if ((udpw->frag_ctx != NULL) && (udpw->frag_ctx == s->frag_ctx)) + { + dequeue (plugin, udpw); + call_continuation (udpw, GNUNET_SYSERR); + MEMDEBUG_free (udpw, __LINE__); + } + udpw = tmp; + } + } + if (s->addrlen == sizeof (struct sockaddr_in)) + { + udpw = plugin->ipv4_queue_head; + while (udpw!= NULL) + { + tmp = udpw->next; + if ((NULL != udpw->frag_ctx) && (udpw->frag_ctx == s->frag_ctx)) + { + dequeue (plugin, udpw); + call_continuation (udpw, GNUNET_SYSERR); + MEMDEBUG_free (udpw, __LINE__); + } + udpw = tmp; + } + } + + /* Destroy fragmentation context */ + GNUNET_FRAGMENT_context_destroy (fc->frag, + &s->last_expected_msg_delay, + &s->last_expected_ack_delay); + s->frag_ctx = NULL; + MEMDEBUG_free (fc , __LINE__); +} + /** * Functions with this signature are called whenever we need * to close a session due to a disconnect or failure to @@ -695,8 +1242,8 @@ free_session (struct Session *s) static void disconnect_session (struct Session *s) { - struct UDPMessageWrapper *udpw; - struct UDPMessageWrapper *next; + struct UDP_MessageWrapper *udpw; + struct UDP_MessageWrapper *next; GNUNET_assert (GNUNET_YES != s->in_destroy); LOG (GNUNET_ERROR_TYPE_DEBUG, @@ -704,16 +1251,23 @@ disconnect_session (struct Session *s) s, GNUNET_i2s (&s->target), GNUNET_a2s (s->sock_addr, s->addrlen)); - stop_session_timeout(s); + stop_session_timeout (s); + + if (NULL != s->frag_ctx) + { + /* Remove fragmented message due to disconnect */ + fragmented_message_done (s->frag_ctx, GNUNET_SYSERR); + } + next = plugin->ipv4_queue_head; while (NULL != (udpw = next)) { next = udpw->next; if (udpw->session == s) { - GNUNET_CONTAINER_DLL_remove(plugin->ipv4_queue_head, plugin->ipv4_queue_tail, udpw); + dequeue (plugin, udpw); call_continuation(udpw, GNUNET_SYSERR); - GNUNET_free (udpw); + MEMDEBUG_free (udpw, __LINE__); } } next = plugin->ipv6_queue_head; @@ -722,9 +1276,9 @@ disconnect_session (struct Session *s) next = udpw->next; if (udpw->session == s) { - GNUNET_CONTAINER_DLL_remove(plugin->ipv6_queue_head, plugin->ipv6_queue_tail, udpw); + dequeue (plugin, udpw); call_continuation(udpw, GNUNET_SYSERR); - GNUNET_free (udpw); + MEMDEBUG_free (udpw, __LINE__); } udpw = next; } @@ -734,7 +1288,8 @@ disconnect_session (struct Session *s) { if (NULL != s->frag_ctx->cont) { - s->frag_ctx->cont (s->frag_ctx->cont_cls, &s->target, GNUNET_SYSERR); + s->frag_ctx->cont (s->frag_ctx->cont_cls, &s->target, GNUNET_SYSERR, + s->frag_ctx->payload_size, s->frag_ctx->on_wire_size); LOG (GNUNET_ERROR_TYPE_DEBUG, "Calling continuation for fragemented message to `%s' with result SYSERR\n", GNUNET_i2s (&s->target)); @@ -746,7 +1301,7 @@ disconnect_session (struct Session *s) &s->target.hashPubKey, s)); GNUNET_STATISTICS_set(plugin->env->stats, - "# UDP sessions active", + "# UDP, sessions active", GNUNET_CONTAINER_multihashmap_size(plugin->sessions), GNUNET_NO); if (s->rc > 0) @@ -764,7 +1319,7 @@ disconnect_session (struct Session *s) * @return GNUNET_OK (continue to iterate) */ static int -disconnect_and_free_it (void *cls, const GNUNET_HashCode * key, void *value) +disconnect_and_free_it (void *cls, const struct GNUNET_HashCode * key, void *value) { disconnect_session(value); return GNUNET_OK; @@ -792,6 +1347,79 @@ udp_disconnect (void *cls, const struct GNUNET_PeerIdentity *target) } +/** + * Session was idle, so disconnect it + */ +static void +session_timeout (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + GNUNET_assert (NULL != cls); + struct Session *s = cls; + + s->timeout_task = GNUNET_SCHEDULER_NO_TASK; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Session %p was idle for %llu ms, disconnecting\n", + s, (unsigned long long) GNUNET_CONSTANTS_IDLE_CONNECTION_TIMEOUT.rel_value); + /* call session destroy function */ + disconnect_session (s); +} + + +/** + * Start session timeout + */ +static void +start_session_timeout (struct Session *s) +{ + GNUNET_assert (NULL != s); + GNUNET_assert (GNUNET_SCHEDULER_NO_TASK == s->timeout_task); + s->timeout_task = GNUNET_SCHEDULER_add_delayed (GNUNET_CONSTANTS_IDLE_CONNECTION_TIMEOUT, + &session_timeout, + s); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Timeout for session %p set to %llu ms\n", + s, (unsigned long long) GNUNET_CONSTANTS_IDLE_CONNECTION_TIMEOUT.rel_value); +} + + +/** + * Increment session timeout due to activity + */ +static void +reschedule_session_timeout (struct Session *s) +{ + GNUNET_assert (NULL != s); + GNUNET_assert (GNUNET_SCHEDULER_NO_TASK != s->timeout_task); + + GNUNET_SCHEDULER_cancel (s->timeout_task); + s->timeout_task = GNUNET_SCHEDULER_add_delayed (GNUNET_CONSTANTS_IDLE_CONNECTION_TIMEOUT, + &session_timeout, + s); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Timeout rescheduled for session %p set to %llu ms\n", + s, (unsigned long long) GNUNET_CONSTANTS_IDLE_CONNECTION_TIMEOUT.rel_value); +} + + +/** + * Cancel timeout + */ +static void +stop_session_timeout (struct Session *s) +{ + GNUNET_assert (NULL != s); + + if (GNUNET_SCHEDULER_NO_TASK != s->timeout_task) + { + GNUNET_SCHEDULER_cancel (s->timeout_task); + s->timeout_task = GNUNET_SCHEDULER_NO_TASK; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Timeout stopped for session %p canceled\n", + s, (unsigned long long) GNUNET_CONSTANTS_IDLE_CONNECTION_TIMEOUT.rel_value); + } +} + + static struct Session * create_session (struct Plugin *plugin, const struct GNUNET_PeerIdentity *target, const void *addr, size_t addrlen, @@ -812,7 +1440,7 @@ create_session (struct Plugin *plugin, const struct GNUNET_PeerIdentity *target, return NULL; } t4 = addr; - s = GNUNET_malloc (sizeof (struct Session) + sizeof (struct sockaddr_in)); + s = MEMDEBUG_malloc (sizeof (struct Session) + sizeof (struct sockaddr_in), __LINE__ ); len = sizeof (struct sockaddr_in); v4 = (struct sockaddr_in *) &s[1]; v4->sin_family = AF_INET; @@ -830,7 +1458,7 @@ create_session (struct Plugin *plugin, const struct GNUNET_PeerIdentity *target, } t6 = addr; s = - GNUNET_malloc (sizeof (struct Session) + sizeof (struct sockaddr_in6)); + MEMDEBUG_malloc (sizeof (struct Session) + sizeof (struct sockaddr_in6), __LINE__ ); len = sizeof (struct sockaddr_in6); v6 = (struct sockaddr_in6 *) &s[1]; v6->sin6_family = AF_INET6; @@ -849,15 +1477,18 @@ create_session (struct Plugin *plugin, const struct GNUNET_PeerIdentity *target, s->addrlen = len; s->target = *target; s->sock_addr = (const struct sockaddr *) &s[1]; - s->last_expected_delay = GNUNET_TIME_UNIT_SECONDS; - start_session_timeout(s); + s->last_expected_ack_delay = GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MILLISECONDS, 250); + s->last_expected_msg_delay = GNUNET_TIME_UNIT_MILLISECONDS; + s->flow_delay_from_other_peer = GNUNET_TIME_UNIT_ZERO_ABS; + s->flow_delay_for_other_peer = GNUNET_TIME_UNIT_ZERO; + start_session_timeout (s); return s; } static int session_cmp_it (void *cls, - const GNUNET_HashCode * key, + const struct GNUNET_HashCode * key, void *value) { struct SessionCompareContext * cctx = cls; @@ -978,27 +1609,38 @@ udp_plugin_get_session (void *cls, &s->target.hashPubKey, s, GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE)); - GNUNET_STATISTICS_set(plugin->env->stats, - "# UDP sessions active", + "# UDP, sessions active", GNUNET_CONTAINER_multihashmap_size(plugin->sessions), GNUNET_NO); - return s; } - static void -enqueue (struct Plugin *plugin, struct UDPMessageWrapper * udpw) +enqueue (struct Plugin *plugin, struct UDP_MessageWrapper * udpw) { - + if (plugin->bytes_in_buffer + udpw->msg_size > INT64_MAX) + GNUNET_break (0); + else + { + GNUNET_STATISTICS_update (plugin->env->stats, + "# UDP, total, bytes in buffers", + udpw->msg_size, GNUNET_NO); + plugin->bytes_in_buffer += udpw->msg_size; + } + GNUNET_STATISTICS_update (plugin->env->stats, + "# UDP, total, msgs in buffers", + 1, GNUNET_NO); if (udpw->session->addrlen == sizeof (struct sockaddr_in)) - GNUNET_CONTAINER_DLL_insert(plugin->ipv4_queue_head, plugin->ipv4_queue_tail, udpw); + GNUNET_CONTAINER_DLL_insert (plugin->ipv4_queue_head, + plugin->ipv4_queue_tail, udpw); if (udpw->session->addrlen == sizeof (struct sockaddr_in6)) - GNUNET_CONTAINER_DLL_insert(plugin->ipv6_queue_head, plugin->ipv6_queue_tail, udpw); + GNUNET_CONTAINER_DLL_insert (plugin->ipv6_queue_head, + plugin->ipv6_queue_tail, udpw); } + /** * Fragment message was transmitted via UDP, let fragmentation know * to send the next fragment now. @@ -1006,14 +1648,15 @@ enqueue (struct Plugin *plugin, struct UDPMessageWrapper * udpw) * @param cls the 'struct UDPMessageWrapper' of the fragment * @param target destination peer (ignored) * @param result GNUNET_OK on success (ignored) + * @param payload bytes payload sent + * @param physical bytes physical sent */ static void send_next_fragment (void *cls, const struct GNUNET_PeerIdentity *target, - int result) + int result, size_t payload, size_t physical) { - struct UDPMessageWrapper *udpw = cls; - + struct UDP_MessageWrapper *udpw = cls; GNUNET_FRAGMENT_context_transmission_done (udpw->frag_ctx->frag); } @@ -1030,59 +1673,27 @@ send_next_fragment (void *cls, static void enqueue_fragment (void *cls, const struct GNUNET_MessageHeader *msg) { - struct FragmentationContext *frag_ctx = cls; + struct UDP_FragmentationContext *frag_ctx = cls; struct Plugin *plugin = frag_ctx->plugin; - struct UDPMessageWrapper * udpw; - struct Session *s; + struct UDP_MessageWrapper * udpw; size_t msg_len = ntohs (msg->size); - + LOG (GNUNET_ERROR_TYPE_DEBUG, - "Enqueuing fragment with %u bytes %u\n", msg_len , sizeof (struct UDPMessageWrapper)); - udpw = GNUNET_malloc (sizeof (struct UDPMessageWrapper) + msg_len); + "Enqueuing fragment with %u bytes\n", msg_len); + frag_ctx->fragments_used ++; + udpw = MEMDEBUG_malloc (sizeof (struct UDP_MessageWrapper) + msg_len, __LINE__ ); udpw->session = frag_ctx->session; - s = udpw->session; - udpw->udp = (char *) &udpw[1]; - + udpw->msg_buf = (char *) &udpw[1]; udpw->msg_size = msg_len; + udpw->payload_size = msg_len; /*FIXME: minus fragment overhead */ udpw->cont = &send_next_fragment; udpw->cont_cls = udpw; udpw->timeout = frag_ctx->timeout; udpw->frag_ctx = frag_ctx; - memcpy (udpw->udp, msg, msg_len); + udpw->msg_type = MSG_FRAGMENTED; + memcpy (udpw->msg_buf, msg, msg_len); enqueue (plugin, udpw); - - if (s->addrlen == sizeof (struct sockaddr_in)) - { - if (plugin->with_v4_ws == GNUNET_NO) - { - if (plugin->select_task != GNUNET_SCHEDULER_NO_TASK) - GNUNET_SCHEDULER_cancel(plugin->select_task); - - plugin->select_task = - GNUNET_SCHEDULER_add_select (GNUNET_SCHEDULER_PRIORITY_DEFAULT, - GNUNET_TIME_UNIT_FOREVER_REL, - plugin->rs_v4, - plugin->ws_v4, - &udp_plugin_select, plugin); - plugin->with_v4_ws = GNUNET_YES; - } - } - else if (s->addrlen == sizeof (struct sockaddr_in6)) - { - if (plugin->with_v6_ws == GNUNET_NO) - { - if (plugin->select_task_v6 != GNUNET_SCHEDULER_NO_TASK) - GNUNET_SCHEDULER_cancel(plugin->select_task_v6); - - plugin->select_task_v6 = - GNUNET_SCHEDULER_add_select (GNUNET_SCHEDULER_PRIORITY_DEFAULT, - GNUNET_TIME_UNIT_FOREVER_REL, - plugin->rs_v6, - plugin->ws_v6, - &udp_plugin_select_v6, plugin); - plugin->with_v6_ws = GNUNET_YES; - } - } + schedule_select (plugin); } @@ -1122,10 +1733,11 @@ udp_plugin_send (void *cls, GNUNET_TRANSPORT_TransmitContinuation cont, void *cont_cls) { struct Plugin *plugin = cls; - size_t mlen = msgbuf_size + sizeof (struct UDPMessage); - struct UDPMessageWrapper * udpw; + size_t udpmlen = msgbuf_size + sizeof (struct UDPMessage); + struct UDP_FragmentationContext * frag_ctx; + struct UDP_MessageWrapper * udpw; struct UDPMessage *udp; - char mbuf[mlen]; + char mbuf[udpmlen]; GNUNET_assert (plugin != NULL); GNUNET_assert (s != NULL); @@ -1133,7 +1745,7 @@ udp_plugin_send (void *cls, return GNUNET_SYSERR; if ((s->addrlen == sizeof (struct sockaddr_in)) && (plugin->sockv4 == NULL)) return GNUNET_SYSERR; - if (mlen >= GNUNET_SERVER_MAX_MESSAGE_SIZE) + if (udpmlen >= GNUNET_SERVER_MAX_MESSAGE_SIZE) { GNUNET_break (0); return GNUNET_SYSERR; @@ -1145,93 +1757,78 @@ udp_plugin_send (void *cls, } LOG (GNUNET_ERROR_TYPE_DEBUG, "UDP transmits %u-byte message to `%s' using address `%s'\n", - mlen, + udpmlen, GNUNET_i2s (&s->target), GNUNET_a2s(s->sock_addr, s->addrlen)); - + + /* Message */ udp = (struct UDPMessage *) mbuf; - udp->header.size = htons (mlen); + udp->header.size = htons (udpmlen); udp->header.type = htons (GNUNET_MESSAGE_TYPE_TRANSPORT_UDP_MESSAGE); udp->reserved = htonl (0); udp->sender = *plugin->env->my_identity; reschedule_session_timeout(s); - if (mlen <= UDP_MTU) + if (udpmlen <= UDP_MTU) { - udpw = GNUNET_malloc (sizeof (struct UDPMessageWrapper) + mlen); + /* unfragmented message */ + udpw = MEMDEBUG_malloc (sizeof (struct UDP_MessageWrapper) + udpmlen, __LINE__ ); udpw->session = s; - udpw->udp = (char *) &udpw[1]; - udpw->msg_size = mlen; + udpw->msg_buf = (char *) &udpw[1]; + udpw->msg_size = udpmlen; /* message size with UDP overhead */ + udpw->payload_size = msgbuf_size; /* message size without UDP overhead */ udpw->timeout = GNUNET_TIME_absolute_add(GNUNET_TIME_absolute_get(), to); udpw->cont = cont; udpw->cont_cls = cont_cls; udpw->frag_ctx = NULL; - memcpy (udpw->udp, udp, sizeof (struct UDPMessage)); - memcpy (&udpw->udp[sizeof (struct UDPMessage)], msgbuf, msgbuf_size); - + udpw->msg_type = MSG_UNFRAGMENTED; + memcpy (udpw->msg_buf, udp, sizeof (struct UDPMessage)); + memcpy (&udpw->msg_buf[sizeof (struct UDPMessage)], msgbuf, msgbuf_size); enqueue (plugin, udpw); + + GNUNET_STATISTICS_update (plugin->env->stats, + "# UDP, unfragmented msgs, messages, attempt", + 1, GNUNET_NO); + GNUNET_STATISTICS_update (plugin->env->stats, + "# UDP, unfragmented msgs, bytes payload, attempt", + udpw->payload_size, GNUNET_NO); } else { - LOG (GNUNET_ERROR_TYPE_DEBUG, - "UDP has to fragment message \n"); + /* fragmented message */ if (s->frag_ctx != NULL) return GNUNET_SYSERR; memcpy (&udp[1], msgbuf, msgbuf_size); - struct FragmentationContext * frag_ctx = GNUNET_malloc(sizeof (struct FragmentationContext)); - + frag_ctx = MEMDEBUG_malloc (sizeof (struct UDP_FragmentationContext), __LINE__ ); frag_ctx->plugin = plugin; frag_ctx->session = s; frag_ctx->cont = cont; frag_ctx->cont_cls = cont_cls; frag_ctx->timeout = GNUNET_TIME_absolute_add(GNUNET_TIME_absolute_get(), to); - frag_ctx->bytes_to_send = mlen; + frag_ctx->payload_size = msgbuf_size; /* unfragmented message size without UDP overhead */ + frag_ctx->on_wire_size = 0; /* bytes with UDP and fragmentation overhead */ frag_ctx->frag = GNUNET_FRAGMENT_context_create (plugin->env->stats, - UDP_MTU, - &plugin->tracker, - s->last_expected_delay, - &udp->header, - &enqueue_fragment, - frag_ctx); - + UDP_MTU, + &plugin->tracker, + s->last_expected_msg_delay, + s->last_expected_ack_delay, + &udp->header, + &enqueue_fragment, + frag_ctx); s->frag_ctx = frag_ctx; - } - - if (s->addrlen == sizeof (struct sockaddr_in)) - { - if (plugin->with_v4_ws == GNUNET_NO) - { - if (plugin->select_task != GNUNET_SCHEDULER_NO_TASK) - GNUNET_SCHEDULER_cancel(plugin->select_task); - - plugin->select_task = - GNUNET_SCHEDULER_add_select (GNUNET_SCHEDULER_PRIORITY_DEFAULT, - GNUNET_TIME_UNIT_FOREVER_REL, - plugin->rs_v4, - plugin->ws_v4, - &udp_plugin_select, plugin); - plugin->with_v4_ws = GNUNET_YES; - } - } - else if (s->addrlen == sizeof (struct sockaddr_in6)) - { - if (plugin->with_v6_ws == GNUNET_NO) - { - if (plugin->select_task_v6 != GNUNET_SCHEDULER_NO_TASK) - GNUNET_SCHEDULER_cancel(plugin->select_task_v6); - - plugin->select_task_v6 = - GNUNET_SCHEDULER_add_select (GNUNET_SCHEDULER_PRIORITY_DEFAULT, - GNUNET_TIME_UNIT_FOREVER_REL, - plugin->rs_v6, - plugin->ws_v6, - &udp_plugin_select_v6, plugin); - plugin->with_v6_ws = GNUNET_YES; - } - } - - return mlen; + GNUNET_STATISTICS_update (plugin->env->stats, + "# UDP, fragmented msgs, messages, pending", + 1, GNUNET_NO); + GNUNET_STATISTICS_update (plugin->env->stats, + "# UDP, fragmented msgs, messages, attempt", + 1, GNUNET_NO); + GNUNET_STATISTICS_update (plugin->env->stats, + "# UDP, fragmented msgs, bytes payload, attempt", + frag_ctx->payload_size, GNUNET_NO); + } + schedule_select (plugin); + return udpmlen; } @@ -1277,7 +1874,7 @@ udp_nat_port_map_callback (void *cls, int add_remove, return; } /* modify our published address list */ - plugin->env->notify_address (plugin->env->cls, add_remove, arg, args); + plugin->env->notify_address (plugin->env->cls, add_remove, arg, args, "udp"); } @@ -1311,7 +1908,7 @@ process_inbound_tokenized_messages (void *cls, void *client, &si->sender, hdr, (const struct GNUNET_ATS_Information *) &ats, 2, - NULL, + si->session, si->arg, si->args); si->session->flow_delay_for_other_peer = delay; @@ -1379,8 +1976,9 @@ process_udp_message (struct Plugin *plugin, const struct UDPMessage *msg, GNUNET_a2s (sender_addr, sender_addr_len)); struct GNUNET_HELLO_Address * address = GNUNET_HELLO_address_allocate(&msg->sender, "udp", arg, args); + MEMDEBUG_add_alloc (address, GNUNET_HELLO_address_get_size(address), __LINE__); s = udp_plugin_get_session(plugin, address); - GNUNET_free (address); + MEMDEBUG_free (address, __LINE__); /* iterate over all embedded messages */ si.session = s; @@ -1461,7 +2059,7 @@ struct LookupContext static int -lookup_session_by_addr_it (void *cls, const GNUNET_HashCode * key, void *value) +lookup_session_by_addr_it (void *cls, const struct GNUNET_HashCode * key, void *value) { struct LookupContext *l_ctx = cls; struct Session * s = value; @@ -1490,10 +2088,10 @@ ack_proc (void *cls, uint32_t id, const struct GNUNET_MessageHeader *msg) size_t msize = sizeof (struct UDP_ACK_Message) + ntohs (msg->size); struct UDP_ACK_Message *udp_ack; uint32_t delay = 0; - struct UDPMessageWrapper *udpw; + struct UDP_MessageWrapper *udpw; struct Session *s; - struct LookupContext l_ctx; + l_ctx.addr = rc->src_addr; l_ctx.addrlen = rc->addr_len; l_ctx.res = NULL; @@ -1515,18 +2113,19 @@ ack_proc (void *cls, uint32_t id, const struct GNUNET_MessageHeader *msg) AF_INET) ? sizeof (struct sockaddr_in) : sizeof (struct sockaddr_in6)), delay); - udpw = GNUNET_malloc (sizeof (struct UDPMessageWrapper) + msize); + udpw = MEMDEBUG_malloc (sizeof (struct UDP_MessageWrapper) + msize, __LINE__ ); udpw->msg_size = msize; + udpw->payload_size = 0; udpw->session = s; udpw->timeout = GNUNET_TIME_UNIT_FOREVER_ABS; - udpw->udp = (char *)&udpw[1]; - udp_ack = (struct UDP_ACK_Message *) udpw->udp; + udpw->msg_buf = (char *)&udpw[1]; + udpw->msg_type = MSG_ACK; + udp_ack = (struct UDP_ACK_Message *) udpw->msg_buf; udp_ack->header.size = htons ((uint16_t) msize); udp_ack->header.type = htons (GNUNET_MESSAGE_TYPE_TRANSPORT_UDP_ACK); udp_ack->delay = htonl (delay); udp_ack->sender = *rc->plugin->env->my_identity; memcpy (&udp_ack[1], msg, ntohs (msg->size)); - enqueue (rc->plugin, udpw); } @@ -1570,15 +2169,18 @@ read_process_ack (struct Plugin *plugin, l_ctx.addrlen = fromlen; l_ctx.res = NULL; GNUNET_CONTAINER_multihashmap_iterate (plugin->sessions, - &lookup_session_by_addr_it, - &l_ctx); + &lookup_session_by_addr_it, + &l_ctx); s = l_ctx.res; - if ((s == NULL) || (s->frag_ctx == NULL)) + if ((NULL == s) || (NULL == s->frag_ctx)) + { return; + } flow_delay.rel_value = (uint64_t) ntohl (udp_ack->delay); - LOG (GNUNET_ERROR_TYPE_DEBUG, "We received a sending delay of %llu\n", + LOG (GNUNET_ERROR_TYPE_DEBUG, + "We received a sending delay of %llu\n", flow_delay.rel_value); s->flow_delay_from_other_peer = GNUNET_TIME_relative_to_absolute (flow_delay); @@ -1591,62 +2193,25 @@ read_process_ack (struct Plugin *plugin, return; } + if (0 != memcmp (&l_ctx.res->target, &udp_ack->sender, sizeof (struct GNUNET_PeerIdentity))) + GNUNET_break (0); if (GNUNET_OK != GNUNET_FRAGMENT_process_ack (s->frag_ctx->frag, ack)) { LOG (GNUNET_ERROR_TYPE_DEBUG, "UDP processes %u-byte acknowledgement from `%s' at `%s'\n", (unsigned int) ntohs (msg->size), GNUNET_i2s (&udp_ack->sender), GNUNET_a2s ((const struct sockaddr *) addr, fromlen)); + /* Expect more ACKs to arrive */ return; } LOG (GNUNET_ERROR_TYPE_DEBUG, - "FULL MESSAGE ACKed\n", + "Message full ACK'ed\n", (unsigned int) ntohs (msg->size), GNUNET_i2s (&udp_ack->sender), GNUNET_a2s ((const struct sockaddr *) addr, fromlen)); - s->last_expected_delay = GNUNET_FRAGMENT_context_destroy (s->frag_ctx->frag); - - struct UDPMessageWrapper * udpw; - struct UDPMessageWrapper * tmp; - if (s->addrlen == sizeof (struct sockaddr_in6)) - { - udpw = plugin->ipv6_queue_head; - while (NULL != udpw) - { - tmp = udpw->next; - if ((udpw->frag_ctx != NULL) && (udpw->frag_ctx == s->frag_ctx)) - { - GNUNET_CONTAINER_DLL_remove(plugin->ipv6_queue_head, plugin->ipv6_queue_tail, udpw); - GNUNET_free (udpw); - } - udpw = tmp; - } - } - if (s->addrlen == sizeof (struct sockaddr_in)) - { - udpw = plugin->ipv4_queue_head; - while (udpw!= NULL) - { - tmp = udpw->next; - if ((udpw->frag_ctx != NULL) && (udpw->frag_ctx == s->frag_ctx)) - { - GNUNET_CONTAINER_DLL_remove(plugin->ipv4_queue_head, plugin->ipv4_queue_tail, udpw); - GNUNET_free (udpw); - } - udpw = tmp; - } - } - - if (s->frag_ctx->cont != NULL) - { - LOG (GNUNET_ERROR_TYPE_DEBUG, - "Calling continuation for fragmented message to `%s' with result %s\n", - GNUNET_i2s (&s->target), "OK"); - s->frag_ctx->cont (s->frag_ctx->cont_cls, &udp_ack->sender, GNUNET_OK); - } - GNUNET_free (s->frag_ctx); - s->frag_ctx = NULL; + /* Remove fragmented message after successful sending */ + fragmented_message_done (s->frag_ctx, GNUNET_OK); } @@ -1677,7 +2242,7 @@ read_process_fragment (struct Plugin *plugin, if (d_ctx == NULL) { /* Create a new defragmentation context */ - d_ctx = GNUNET_malloc (sizeof (struct DefragContext) + fromlen); + d_ctx = MEMDEBUG_malloc (sizeof (struct DefragContext) + fromlen, __LINE__ ); memcpy (&d_ctx[1], addr, fromlen); d_ctx->src_addr = (const struct sockaddr *) &d_ctx[1]; d_ctx->addr_len = fromlen; @@ -1717,7 +2282,7 @@ read_process_fragment (struct Plugin *plugin, d_ctx = GNUNET_CONTAINER_heap_remove_root (plugin->defrag_ctxs); GNUNET_assert (NULL != d_ctx); GNUNET_DEFRAGMENT_context_destroy (d_ctx->defrag); - GNUNET_free (d_ctx); + MEMDEBUG_free (d_ctx, __LINE__); } } @@ -1741,9 +2306,34 @@ udp_select_read (struct Plugin *plugin, struct GNUNET_NETWORK_Handle *rsock) memset (&addr, 0, sizeof (addr)); size = GNUNET_NETWORK_socket_recvfrom (rsock, buf, sizeof (buf), (struct sockaddr *) &addr, &fromlen); - +#if MINGW + /* On SOCK_DGRAM UDP sockets recvfrom might fail with a + * WSAECONNRESET error to indicate that previous sendto() (yes, sendto!) + * on this socket has failed. + * Quote from MSDN: + * WSAECONNRESET - The virtual circuit was reset by the remote side + * executing a hard or abortive close. The application should close + * the socket; it is no longer usable. On a UDP-datagram socket this + * error indicates a previous send operation resulted in an ICMP Port + * Unreachable message. + */ + if ( (-1 == size) && (ECONNRESET == errno) ) + return; +#endif + if (-1 == size) + { + LOG (GNUNET_ERROR_TYPE_DEBUG, + "UDP failed to receive data: %s\n", STRERROR (errno)); + /* Connection failure or something. Not a protocol violation. */ + return; + } if (size < sizeof (struct GNUNET_MessageHeader)) { + LOG (GNUNET_ERROR_TYPE_WARNING, + "UDP got %u bytes, which is not enough for a GNUnet message header\n", + (unsigned int) size); + /* _MAY_ be a connection failure (got partial message) */ + /* But it _MAY_ also be that the other side uses non-GNUnet protocol. */ GNUNET_break_op (0); return; } @@ -1759,6 +2349,10 @@ udp_select_read (struct Plugin *plugin, struct GNUNET_NETWORK_Handle *rsock) return; } + GNUNET_STATISTICS_update (plugin->env->stats, + "# UDP, total, bytes, received", + size, GNUNET_NO); + switch (ntohs (msg->type)) { case GNUNET_MESSAGE_TYPE_TRANSPORT_BROADCAST_BEACON: @@ -1783,143 +2377,222 @@ udp_select_read (struct Plugin *plugin, struct GNUNET_NETWORK_Handle *rsock) } } - -static size_t -udp_select_send (struct Plugin *plugin, struct GNUNET_NETWORK_Handle *sock) +static struct UDP_MessageWrapper * +remove_timeout_messages_and_select (struct UDP_MessageWrapper *head, + struct GNUNET_NETWORK_Handle *sock) { - ssize_t sent; - size_t slen; - struct GNUNET_TIME_Absolute max; - struct UDPMessageWrapper *udpw = NULL; - - if (sock == plugin->sockv4) - { - udpw = plugin->ipv4_queue_head; - } - else if (sock == plugin->sockv6) - { - udpw = plugin->ipv6_queue_head; - } - else - { - GNUNET_break (0); - return 0; - } - - const struct sockaddr * sa = udpw->session->sock_addr; - slen = udpw->session->addrlen; - - max = GNUNET_TIME_absolute_max(udpw->timeout, GNUNET_TIME_absolute_get()); + struct UDP_MessageWrapper *udpw = NULL; + struct GNUNET_TIME_Relative remaining; + udpw = head; while (udpw != NULL) { - if (max.abs_value != udpw->timeout.abs_value) + /* Find messages with timeout */ + remaining = GNUNET_TIME_absolute_get_remaining (udpw->timeout); + if (GNUNET_TIME_UNIT_ZERO.rel_value == remaining.rel_value) { /* Message timed out */ - call_continuation(udpw, GNUNET_SYSERR); - if (udpw->frag_ctx != NULL) - { - LOG (GNUNET_ERROR_TYPE_DEBUG, - "Fragmented message for peer `%s' with size %u timed out\n", - GNUNET_i2s(&udpw->session->target), udpw->frag_ctx->bytes_to_send); - udpw->session->last_expected_delay = GNUNET_FRAGMENT_context_destroy(udpw->frag_ctx->frag); - GNUNET_free (udpw->frag_ctx); - udpw->session->frag_ctx = NULL; - } - else - { - LOG (GNUNET_ERROR_TYPE_DEBUG, - "Message for peer `%s' with size %u timed out\n", - GNUNET_i2s(&udpw->session->target), udpw->msg_size); + switch (udpw->msg_type) { + case MSG_UNFRAGMENTED: + GNUNET_STATISTICS_update (plugin->env->stats, + "# UDP, total, bytes, sent, timeout", + udpw->msg_size, GNUNET_NO); + GNUNET_STATISTICS_update (plugin->env->stats, + "# UDP, total, messages, sent, timeout", + 1, GNUNET_NO); + GNUNET_STATISTICS_update (plugin->env->stats, + "# UDP, unfragmented msgs, messages, sent, timeout", + 1, GNUNET_NO); + GNUNET_STATISTICS_update (plugin->env->stats, + "# UDP, unfragmented msgs, bytes, sent, timeout", + udpw->payload_size, GNUNET_NO); + /* Not fragmented message */ + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Message for peer `%s' with size %u timed out\n", + GNUNET_i2s(&udpw->session->target), udpw->payload_size); + call_continuation (udpw, GNUNET_SYSERR); + /* Remove message */ + dequeue (plugin, udpw); + MEMDEBUG_free (udpw, __LINE__); + break; + case MSG_FRAGMENTED: + /* Fragmented message */ + GNUNET_STATISTICS_update (plugin->env->stats, + "# UDP, total, bytes, sent, timeout", + udpw->frag_ctx->on_wire_size, GNUNET_NO); + GNUNET_STATISTICS_update (plugin->env->stats, + "# UDP, total, messages, sent, timeout", + 1, GNUNET_NO); + call_continuation (udpw, GNUNET_SYSERR); + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Fragment for message for peer `%s' with size %u timed out\n", + GNUNET_i2s(&udpw->session->target), udpw->frag_ctx->payload_size); + + + GNUNET_STATISTICS_update (plugin->env->stats, + "# UDP, fragmented msgs, messages, sent, timeout", + 1, GNUNET_NO); + GNUNET_STATISTICS_update (plugin->env->stats, + "# UDP, fragmented msgs, bytes, sent, timeout", + udpw->frag_ctx->payload_size, GNUNET_NO); + /* Remove fragmented message due to timeout */ + fragmented_message_done (udpw->frag_ctx, GNUNET_SYSERR); + break; + case MSG_ACK: + GNUNET_STATISTICS_update (plugin->env->stats, + "# UDP, total, bytes, sent, timeout", + udpw->msg_size, GNUNET_NO); + GNUNET_STATISTICS_update (plugin->env->stats, + "# UDP, total, messages, sent, timeout", + 1, GNUNET_NO); + LOG (GNUNET_ERROR_TYPE_DEBUG, + "ACK Message for peer `%s' with size %u timed out\n", + GNUNET_i2s(&udpw->session->target), udpw->payload_size); + call_continuation (udpw, GNUNET_SYSERR); + dequeue (plugin, udpw); + MEMDEBUG_free (udpw, __LINE__); + break; + default: + break; } - if (sock == plugin->sockv4) - { - GNUNET_CONTAINER_DLL_remove(plugin->ipv4_queue_head, plugin->ipv4_queue_tail, udpw); - GNUNET_free (udpw); udpw = plugin->ipv4_queue_head; - } else if (sock == plugin->sockv6) - { - GNUNET_CONTAINER_DLL_remove(plugin->ipv6_queue_head, plugin->ipv6_queue_tail, udpw); - GNUNET_free (udpw); udpw = plugin->ipv6_queue_head; + else + { + GNUNET_break (0); /* should never happen */ + udpw = NULL; } + GNUNET_STATISTICS_update (plugin->env->stats, + "# messages dismissed due to timeout", + 1, GNUNET_NO); } else { - struct GNUNET_TIME_Relative delta = GNUNET_TIME_absolute_get_remaining (udpw->session->flow_delay_from_other_peer); - if (delta.rel_value == 0) + /* Message did not time out, check flow delay */ + remaining = GNUNET_TIME_absolute_get_remaining (udpw->session->flow_delay_from_other_peer); + if (GNUNET_TIME_UNIT_ZERO.rel_value == remaining.rel_value) { /* this message is not delayed */ LOG (GNUNET_ERROR_TYPE_DEBUG, - "Message for peer `%s' (%u bytes) is not delayed \n", - GNUNET_i2s(&udpw->session->target), udpw->msg_size); - break; + "Message for peer `%s' (%u bytes) is not delayed \n", + GNUNET_i2s(&udpw->session->target), udpw->payload_size); + break; /* Found message to send, break */ } else { - /* this message is delayed, try next */ + /* Message is delayed, try next */ LOG (GNUNET_ERROR_TYPE_DEBUG, - "Message for peer `%s' (%u bytes) is delayed for %llu \n", - GNUNET_i2s(&udpw->session->target), udpw->msg_size, - delta); + "Message for peer `%s' (%u bytes) is delayed for %llu \n", + GNUNET_i2s(&udpw->session->target), udpw->payload_size, remaining.rel_value); udpw = udpw->next; } } } + return udpw; +} - if (udpw == NULL) - { - /* No message left */ - return 0; - } - sent = GNUNET_NETWORK_socket_sendto (sock, udpw->udp, udpw->msg_size, sa, slen); +static void +analyze_send_error (struct Plugin *plugin, + const struct sockaddr * sa, + socklen_t slen, + int error) +{ + static int network_down_error; + struct GNUNET_ATS_Information type; + + type = plugin->env->get_address_type (plugin->env->cls,sa, slen); + if (((GNUNET_ATS_NET_LAN == ntohl(type.value)) || (GNUNET_ATS_NET_WAN == ntohl(type.value))) && + ((ENETUNREACH == errno) || (ENETDOWN == errno))) + { + if ((network_down_error == GNUNET_NO) && (slen == sizeof (struct sockaddr_in))) + { + /* IPv4: "Network unreachable" or "Network down" + * + * This indicates we do not have connectivity + */ + LOG (GNUNET_ERROR_TYPE_WARNING | GNUNET_ERROR_TYPE_BULK, + _("UDP could not transmit message to `%s': " + "Network seems down, please check your network configuration\n"), + GNUNET_a2s (sa, slen)); + } + if ((network_down_error == GNUNET_NO) && (slen == sizeof (struct sockaddr_in6))) + { + /* IPv6: "Network unreachable" or "Network down" + * + * This indicates that this system is IPv6 enabled, but does not + * have a valid global IPv6 address assigned or we do not have + * connectivity + */ + + LOG (GNUNET_ERROR_TYPE_WARNING | GNUNET_ERROR_TYPE_BULK, + _("UDP could not transmit message to `%s': " + "Please check your network configuration and disable IPv6 if your " + "connection does not have a global IPv6 address\n"), + GNUNET_a2s (sa, slen)); + } + } + else + { + LOG (GNUNET_ERROR_TYPE_WARNING, + "UDP could not transmit message to `%s': `%s'\n", + GNUNET_a2s (sa, slen), STRERROR (error)); + } +} + +static size_t +udp_select_send (struct Plugin *plugin, struct GNUNET_NETWORK_Handle *sock) +{ + const struct sockaddr * sa; + ssize_t sent; + socklen_t slen; + + struct UDP_MessageWrapper *udpw = NULL; + + /* Find message to send */ + udpw = remove_timeout_messages_and_select ((sock == plugin->sockv4) ? plugin->ipv4_queue_head : plugin->ipv6_queue_head, + sock); + if (NULL == udpw) + return 0; /* No message to send */ + + sa = udpw->session->sock_addr; + slen = udpw->session->addrlen; + + sent = GNUNET_NETWORK_socket_sendto (sock, udpw->msg_buf, udpw->msg_size, sa, slen); if (GNUNET_SYSERR == sent) { - const struct GNUNET_ATS_Information type = plugin->env->get_address_type - (plugin->env->cls,sa, slen); - - if ((GNUNET_ATS_NET_WAN == type.value) && - ((ENETUNREACH == errno) || (ENETDOWN == errno))) - { - /* "Network unreachable" or "Network down" */ - /* - * This indicates that this system is IPv6 enabled, but does not - * have a valid global IPv6 address assigned - */ - LOG (GNUNET_ERROR_TYPE_ERROR | GNUNET_ERROR_TYPE_BULK, - _("UDP could not message to `%s': `%s'. " - "Please check your network configuration and disable IPv6 if your " - "connection does not have a global IPv6 address\n"), - GNUNET_a2s (sa, slen), - STRERROR (errno)); - } - else - { - LOG (GNUNET_ERROR_TYPE_ERROR, - "UDP could not transmit %u-byte message to `%s': `%s'\n", - (unsigned int) (udpw->msg_size), GNUNET_a2s (sa, slen), - STRERROR (errno)); - } + /* Failure */ + analyze_send_error (plugin, sa, slen, errno); call_continuation(udpw, GNUNET_SYSERR); + GNUNET_STATISTICS_update (plugin->env->stats, + "# UDP, total, bytes, sent, failure", + sent, GNUNET_NO); + GNUNET_STATISTICS_update (plugin->env->stats, + "# UDP, total, messages, sent, failure", + 1, GNUNET_NO); } else { + /* Success */ LOG (GNUNET_ERROR_TYPE_DEBUG, - "UDP transmitted %u-byte message to `%s' (%d: %s)\n", - (unsigned int) (udpw->msg_size), GNUNET_a2s (sa, slen), (int) sent, + "UDP transmitted %u-byte message to `%s' `%s' (%d: %s)\n", + (unsigned int) (udpw->msg_size), GNUNET_i2s(&udpw->session->target) ,GNUNET_a2s (sa, slen), (int) sent, (sent < 0) ? STRERROR (errno) : "ok"); - call_continuation(udpw, GNUNET_OK); - } - - if (sock == plugin->sockv4) - GNUNET_CONTAINER_DLL_remove(plugin->ipv4_queue_head, plugin->ipv4_queue_tail, udpw); - else if (sock == plugin->sockv6) - GNUNET_CONTAINER_DLL_remove(plugin->ipv6_queue_head, plugin->ipv6_queue_tail, udpw); - GNUNET_free (udpw); + GNUNET_STATISTICS_update (plugin->env->stats, + "# UDP, total, bytes, sent, success", + sent, GNUNET_NO); + GNUNET_STATISTICS_update (plugin->env->stats, + "# UDP, total, messages, sent, success", + 1, GNUNET_NO); + if (NULL != udpw->frag_ctx) + udpw->frag_ctx->on_wire_size += udpw->msg_size; + call_continuation (udpw, GNUNET_OK); + } + dequeue (plugin, udpw); + MEMDEBUG_free (udpw, __LINE__); udpw = NULL; return sent; @@ -1940,38 +2613,18 @@ udp_plugin_select (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) struct Plugin *plugin = cls; plugin->select_task = GNUNET_SCHEDULER_NO_TASK; - if ((tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN) != 0) + if (0 != (tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN)) return; - plugin->with_v4_ws = GNUNET_NO; - - if ((tc->reason & GNUNET_SCHEDULER_REASON_READ_READY) != 0) - { - if ((NULL != plugin->sockv4) && - (GNUNET_NETWORK_fdset_isset (tc->read_ready, plugin->sockv4))) - udp_select_read (plugin, plugin->sockv4); - - } - - if ((tc->reason & GNUNET_SCHEDULER_REASON_WRITE_READY) != 0) - { - if ((NULL != plugin->sockv4) && (plugin->ipv4_queue_head != NULL) && - (GNUNET_NETWORK_fdset_isset (tc->write_ready, plugin->sockv4))) - { - udp_select_send (plugin, plugin->sockv4); - } - } - - if (plugin->select_task != GNUNET_SCHEDULER_NO_TASK) - GNUNET_SCHEDULER_cancel (plugin->select_task); - plugin->select_task = GNUNET_SCHEDULER_add_select (GNUNET_SCHEDULER_PRIORITY_DEFAULT, - GNUNET_TIME_UNIT_FOREVER_REL, - plugin->rs_v4, - (plugin->ipv4_queue_head != NULL) ? plugin->ws_v4 : NULL, - &udp_plugin_select, plugin); - if (plugin->ipv4_queue_head != NULL) - plugin->with_v4_ws = GNUNET_YES; - else - plugin->with_v4_ws = GNUNET_NO; + if ( (0 != (tc->reason & GNUNET_SCHEDULER_REASON_READ_READY)) && + (NULL != plugin->sockv4) && + (GNUNET_NETWORK_fdset_isset (tc->read_ready, plugin->sockv4)) ) + udp_select_read (plugin, plugin->sockv4); + if ( (0 != (tc->reason & GNUNET_SCHEDULER_REASON_WRITE_READY)) && + (NULL != plugin->sockv4) && + (NULL != plugin->ipv4_queue_head) && + (GNUNET_NETWORK_fdset_isset (tc->write_ready, plugin->sockv4)) ) + udp_select_send (plugin, plugin->sockv4); + schedule_select (plugin); } @@ -1989,36 +2642,17 @@ udp_plugin_select_v6 (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) struct Plugin *plugin = cls; plugin->select_task_v6 = GNUNET_SCHEDULER_NO_TASK; - if ((tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN) != 0) + if (0 != (tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN)) return; - - plugin->with_v6_ws = GNUNET_NO; - if ((tc->reason & GNUNET_SCHEDULER_REASON_READ_READY) != 0) - { - if ((NULL != plugin->sockv6) && - (GNUNET_NETWORK_fdset_isset (tc->read_ready, plugin->sockv6))) - udp_select_read (plugin, plugin->sockv6); - } - - if ((tc->reason & GNUNET_SCHEDULER_REASON_WRITE_READY) != 0) - { - if ((NULL != plugin->sockv6) && (plugin->ipv6_queue_head != NULL) && - (GNUNET_NETWORK_fdset_isset (tc->write_ready, plugin->sockv6))) - { - udp_select_send (plugin, plugin->sockv6); - } - } - if (plugin->select_task_v6 != GNUNET_SCHEDULER_NO_TASK) - GNUNET_SCHEDULER_cancel (plugin->select_task_v6); - plugin->select_task_v6 = GNUNET_SCHEDULER_add_select (GNUNET_SCHEDULER_PRIORITY_DEFAULT, - GNUNET_TIME_UNIT_FOREVER_REL, - plugin->rs_v6, - (plugin->ipv6_queue_head != NULL) ? plugin->ws_v6 : NULL, - &udp_plugin_select_v6, plugin); - if (plugin->ipv6_queue_head != NULL) - plugin->with_v6_ws = GNUNET_YES; - else - plugin->with_v6_ws = GNUNET_NO; + if ( ((tc->reason & GNUNET_SCHEDULER_REASON_READ_READY) != 0) && + (NULL != plugin->sockv6) && + (GNUNET_NETWORK_fdset_isset (tc->read_ready, plugin->sockv6)) ) + udp_select_read (plugin, plugin->sockv6); + if ( (0 != (tc->reason & GNUNET_SCHEDULER_REASON_WRITE_READY)) && + (NULL != plugin->sockv6) && (plugin->ipv6_queue_head != NULL) && + (GNUNET_NETWORK_fdset_isset (tc->write_ready, plugin->sockv6)) ) + udp_select_send (plugin, plugin->sockv6); + schedule_select (plugin); } @@ -2134,17 +2768,8 @@ setup_sockets (struct Plugin *plugin, struct sockaddr_in6 *serverAddrv6, struct GNUNET_NETWORK_fdset_set (plugin->ws_v4, plugin->sockv4); } - if (sockets_created == 0) + if (0 == sockets_created) LOG (GNUNET_ERROR_TYPE_WARNING, _("Failed to open UDP sockets\n")); - - plugin->select_task = - GNUNET_SCHEDULER_add_select (GNUNET_SCHEDULER_PRIORITY_DEFAULT, - GNUNET_TIME_UNIT_FOREVER_REL, - plugin->rs_v4, - NULL, - &udp_plugin_select, plugin); - plugin->with_v4_ws = GNUNET_NO; - if (plugin->enable_ipv6 == GNUNET_YES) { plugin->rs_v6 = GNUNET_NETWORK_fdset_create (); @@ -2156,16 +2781,8 @@ setup_sockets (struct Plugin *plugin, struct sockaddr_in6 *serverAddrv6, struct GNUNET_NETWORK_fdset_set (plugin->rs_v6, plugin->sockv6); GNUNET_NETWORK_fdset_set (plugin->ws_v6, plugin->sockv6); } - - plugin->select_task_v6 = - GNUNET_SCHEDULER_add_select (GNUNET_SCHEDULER_PRIORITY_DEFAULT, - GNUNET_TIME_UNIT_FOREVER_REL, - plugin->rs_v6, - NULL, - &udp_plugin_select_v6, plugin); - plugin->with_v6_ws = GNUNET_NO; } - + schedule_select (plugin); plugin->nat = GNUNET_NAT_register (plugin->env->cfg, GNUNET_NO, plugin->port, sockets_created, @@ -2175,82 +2792,6 @@ setup_sockets (struct Plugin *plugin, struct sockaddr_in6 *serverAddrv6, struct return sockets_created; } -/** - * Session was idle, so disconnect it - */ -static void -session_timeout (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - GNUNET_assert (NULL != cls); - struct Session *s = cls; - - s->timeout_task = GNUNET_SCHEDULER_NO_TASK; - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Session %p was idle for %llu, disconnecting\n", - s, GNUNET_CONSTANTS_IDLE_CONNECTION_TIMEOUT.rel_value); - - /* call session destroy function */ - disconnect_session(s); - -} - -/** - * Start session timeout - */ -static void -start_session_timeout (struct Session *s) -{ - GNUNET_assert (NULL != s); - GNUNET_assert (GNUNET_SCHEDULER_NO_TASK == s->timeout_task); - - s->timeout_task = GNUNET_SCHEDULER_add_delayed (GNUNET_CONSTANTS_IDLE_CONNECTION_TIMEOUT, - &session_timeout, - s); - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Timeout for session %p set to %llu\n", - s, GNUNET_CONSTANTS_IDLE_CONNECTION_TIMEOUT.rel_value); -} - -/** - * Increment session timeout due to activity - */ -static void -reschedule_session_timeout (struct Session *s) -{ - GNUNET_assert (NULL != s); - GNUNET_assert (GNUNET_SCHEDULER_NO_TASK != s->timeout_task); - - GNUNET_SCHEDULER_cancel (s->timeout_task); - s->timeout_task = GNUNET_SCHEDULER_add_delayed (GNUNET_CONSTANTS_IDLE_CONNECTION_TIMEOUT, - &session_timeout, - s); - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Timeout rescheduled for session %p set to %llu\n", - s, GNUNET_CONSTANTS_IDLE_CONNECTION_TIMEOUT.rel_value); -} - -/** - * Cancel timeout - */ -static void -stop_session_timeout (struct Session *s) -{ - GNUNET_assert (NULL != s); - - if (GNUNET_SCHEDULER_NO_TASK != s->timeout_task) - { - GNUNET_SCHEDULER_cancel (s->timeout_task); - s->timeout_task = GNUNET_SCHEDULER_NO_TASK; - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Timeout rescheduled for session %p canceled\n", - s, GNUNET_CONSTANTS_IDLE_CONNECTION_TIMEOUT.rel_value); - } - else - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Timeout for session %p was not active\n", - s); - } -} /** * The exported method. Makes the core api available via a global and @@ -2272,6 +2813,7 @@ libgnunet_plugin_transport_udp_init (void *cls) unsigned long long enable_v6; char * bind4_address; char * bind6_address; + char * fancy_interval; struct GNUNET_TIME_Relative interval; struct sockaddr_in serverAddrv4; struct sockaddr_in6 serverAddrv6; @@ -2281,7 +2823,7 @@ libgnunet_plugin_transport_udp_init (void *cls) { /* run in 'stub' mode (i.e. as part of gnunet-peerinfo), don't fully initialze the plugin or the API */ - api = GNUNET_malloc (sizeof (struct GNUNET_TRANSPORT_PluginFunctions)); + api = MEMDEBUG_malloc (sizeof (struct GNUNET_TRANSPORT_PluginFunctions), __LINE__ ); api->cls = NULL; api->address_pretty_printer = &udp_plugin_address_pretty_printer; api->address_to_string = &udp_address_to_string; @@ -2331,7 +2873,7 @@ libgnunet_plugin_transport_udp_init (void *cls) bind4_address); if (1 != inet_pton (AF_INET, bind4_address, &serverAddrv4.sin_addr)) { - GNUNET_free (bind4_address); + MEMDEBUG_free (bind4_address, __LINE__); return NULL; } } @@ -2348,8 +2890,8 @@ libgnunet_plugin_transport_udp_init (void *cls) { LOG (GNUNET_ERROR_TYPE_ERROR, _("Invalid IPv6 address: `%s'\n"), bind6_address); - GNUNET_free_non_null (bind4_address); - GNUNET_free (bind6_address); + MEMDEBUG_free_non_null (bind4_address, __LINE__); + MEMDEBUG_free (bind6_address, __LINE__); return NULL; } } @@ -2360,11 +2902,20 @@ libgnunet_plugin_transport_udp_init (void *cls) if (broadcast == GNUNET_SYSERR) broadcast = GNUNET_NO; - if (GNUNET_SYSERR == GNUNET_CONFIGURATION_get_value_time (env->cfg, "transport-udp", - "BROADCAST_INTERVAL", &interval)) + if (GNUNET_SYSERR == GNUNET_CONFIGURATION_get_value_string (env->cfg, "transport-udp", + "BROADCAST_INTERVAL", &fancy_interval)) { interval = GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 10); } + else + { + MEMDEBUG_add_alloc (fancy_interval, strlen (fancy_interval)+ 1, __LINE__); + if (GNUNET_SYSERR == GNUNET_STRINGS_fancy_time_to_relative(fancy_interval, &interval)) + { + interval = GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 30); + } + MEMDEBUG_free (fancy_interval, __LINE__); + } /* Maximum datarate */ if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_number (env->cfg, "transport-udp", @@ -2373,12 +2924,12 @@ libgnunet_plugin_transport_udp_init (void *cls) udp_max_bps = 1024 * 1024 * 50; /* 50 MB/s == infinity for practical purposes */ } - p = GNUNET_malloc (sizeof (struct Plugin)); - api = GNUNET_malloc (sizeof (struct GNUNET_TRANSPORT_PluginFunctions)); + p = MEMDEBUG_malloc (sizeof (struct Plugin), __LINE__ ); + api = MEMDEBUG_malloc (sizeof (struct GNUNET_TRANSPORT_PluginFunctions), __LINE__ ); GNUNET_BANDWIDTH_tracker_init (&p->tracker, GNUNET_BANDWIDTH_value_init ((uint32_t)udp_max_bps), 30); - p->sessions = GNUNET_CONTAINER_multihashmap_create (10); + p->sessions = GNUNET_CONTAINER_multihashmap_create (10, GNUNET_NO); p->defrag_ctxs = GNUNET_CONTAINER_heap_create (GNUNET_CONTAINER_HEAP_ORDER_MIN); p->mst = GNUNET_SERVER_mst_create (&process_inbound_tokenized_messages, p); p->port = port; @@ -2404,8 +2955,8 @@ libgnunet_plugin_transport_udp_init (void *cls) if ((res == 0) || ((p->sockv4 == NULL) && (p->sockv6 == NULL))) { LOG (GNUNET_ERROR_TYPE_ERROR, "Failed to create network sockets, plugin failed\n"); - GNUNET_free (p); - GNUNET_free (api); + MEMDEBUG_free (p, __LINE__); + MEMDEBUG_free (api, __LINE__); return NULL; } @@ -2415,8 +2966,8 @@ libgnunet_plugin_transport_udp_init (void *cls) setup_broadcast (p, &serverAddrv6, &serverAddrv4); } - GNUNET_free_non_null (bind4_address); - GNUNET_free_non_null (bind6_address); + MEMDEBUG_free_non_null (bind4_address, __LINE__); + MEMDEBUG_free_non_null (bind6_address, __LINE__); return api; } @@ -2432,7 +2983,7 @@ heap_cleanup_iterator (void *cls, GNUNET_CONTAINER_heap_remove_node (node); GNUNET_DEFRAGMENT_context_destroy(d_ctx->defrag); - GNUNET_free (d_ctx); + MEMDEBUG_free (d_ctx, __LINE__); return GNUNET_YES; } @@ -2453,12 +3004,11 @@ libgnunet_plugin_transport_udp_done (void *cls) if (NULL == plugin) { - GNUNET_free (api); + MEMDEBUG_free (api, __LINE__); return NULL; } stop_broadcast (plugin); - if (plugin->select_task != GNUNET_SCHEDULER_NO_TASK) { GNUNET_SCHEDULER_cancel (plugin->select_task); @@ -2504,23 +3054,25 @@ libgnunet_plugin_transport_udp_done (void *cls) } /* Clean up leftover messages */ - struct UDPMessageWrapper * udpw; + struct UDP_MessageWrapper * udpw; udpw = plugin->ipv4_queue_head; while (udpw != NULL) { - struct UDPMessageWrapper *tmp = udpw->next; - GNUNET_CONTAINER_DLL_remove(plugin->ipv4_queue_head, plugin->ipv4_queue_tail, udpw); + struct UDP_MessageWrapper *tmp = udpw->next; + dequeue (plugin, udpw); call_continuation(udpw, GNUNET_SYSERR); - GNUNET_free (udpw); + MEMDEBUG_free (udpw, __LINE__); + udpw = tmp; } udpw = plugin->ipv6_queue_head; while (udpw != NULL) { - struct UDPMessageWrapper *tmp = udpw->next; - GNUNET_CONTAINER_DLL_remove(plugin->ipv6_queue_head, plugin->ipv6_queue_tail, udpw); + struct UDP_MessageWrapper *tmp = udpw->next; + dequeue (plugin, udpw); call_continuation(udpw, GNUNET_SYSERR); - GNUNET_free (udpw); + MEMDEBUG_free (udpw, __LINE__); + udpw = tmp; } @@ -2531,8 +3083,24 @@ libgnunet_plugin_transport_udp_done (void *cls) GNUNET_CONTAINER_multihashmap_destroy (plugin->sessions); plugin->nat = NULL; - GNUNET_free (plugin); - GNUNET_free (api); + MEMDEBUG_free (plugin, __LINE__); + MEMDEBUG_free (api, __LINE__); +#if DEBUG_MALLOC + struct Allocation *allocation; + while (NULL != ahead) + { + allocation = ahead; + GNUNET_CONTAINER_DLL_remove (ahead, atail, allocation); + GNUNET_free (allocation); + } + struct Allocator *allocator; + while (NULL != aehead) + { + allocator = aehead; + GNUNET_CONTAINER_DLL_remove (aehead, aetail, allocator); + GNUNET_free (allocator); + } +#endif return NULL; } diff --git a/src/transport/plugin_transport_udp.h b/src/transport/plugin_transport_udp.h index 5637524..bab8e6c 100644 --- a/src/transport/plugin_transport_udp.h +++ b/src/transport/plugin_transport_udp.h @@ -159,6 +159,12 @@ struct Plugin */ char *bind6_address; + + /** + * Bytes currently in buffer + */ + int64_t bytes_in_buffer; + /** * Handle to NAT traversal support. */ @@ -175,8 +181,6 @@ struct Plugin struct GNUNET_NETWORK_FDSet *ws_v4; - int with_v4_ws; - /** * The read socket for IPv4 */ @@ -193,8 +197,6 @@ struct Plugin */ struct GNUNET_NETWORK_FDSet *ws_v6; - int with_v6_ws; - /** * The read socket for IPv6 */ @@ -268,11 +270,11 @@ struct Plugin */ uint16_t aport; - struct UDPMessageWrapper *ipv4_queue_head; - struct UDPMessageWrapper *ipv4_queue_tail; + struct UDP_MessageWrapper *ipv4_queue_head; + struct UDP_MessageWrapper *ipv4_queue_tail; - struct UDPMessageWrapper *ipv6_queue_head; - struct UDPMessageWrapper *ipv6_queue_tail; + struct UDP_MessageWrapper *ipv6_queue_head; + struct UDP_MessageWrapper *ipv6_queue_tail; }; diff --git a/src/transport/plugin_transport_udp_broadcasting.c b/src/transport/plugin_transport_udp_broadcasting.c index baabf45..db6c1fe 100644 --- a/src/transport/plugin_transport_udp_broadcasting.c +++ b/src/transport/plugin_transport_udp_broadcasting.c @@ -228,6 +228,8 @@ prepare_beacon (struct Plugin *plugin, struct UDP_Beacon_Message *msg) const struct GNUNET_MessageHeader *hello; hello = plugin->env->get_our_hello (); + if (NULL == hello) + return 0; hello_size = GNUNET_HELLO_size ((struct GNUNET_HELLO_Message *) hello); msg_size = hello_size + sizeof (struct UDP_Beacon_Message); @@ -258,7 +260,7 @@ udp_ipv4_broadcast_send (void *cls, sent = 0; baddr = plugin->ipv4_broadcast_head; /* just IPv4 */ - while ((baddr != NULL) && (baddr->addrlen == sizeof (struct sockaddr_in))) + while ((msg_size > 0) && (baddr != NULL) && (baddr->addrlen == sizeof (struct sockaddr_in))) { struct sockaddr_in *addr = (struct sockaddr_in *) baddr->addr; @@ -268,7 +270,19 @@ udp_ipv4_broadcast_send (void *cls, (const struct sockaddr *) addr, baddr->addrlen); if (sent == GNUNET_SYSERR) - GNUNET_log_strerror (GNUNET_ERROR_TYPE_ERROR, "sendto"); + { + if ((ENETUNREACH == errno) || (ENETDOWN == errno)) + { + /* "Network unreachable" or "Network down" + * + * This indicates that we just do not have network connectivity + */ + GNUNET_log (GNUNET_ERROR_TYPE_BULK | GNUNET_ERROR_TYPE_WARNING, + "Network connectivity is down, cannot send beacon!\n"); + } + else + GNUNET_log_strerror (GNUNET_ERROR_TYPE_ERROR, "sendto"); + } else { LOG (GNUNET_ERROR_TYPE_DEBUG, @@ -301,7 +315,20 @@ udp_ipv6_broadcast_send (void *cls, &plugin->ipv6_multicast_address, sizeof (struct sockaddr_in6)); if (sent == GNUNET_SYSERR) - GNUNET_log_strerror (GNUNET_ERROR_TYPE_ERROR, "sendto"); + { + if ((ENETUNREACH == errno) || (ENETDOWN == errno)) + { + /* "Network unreachable" or "Network down" + * + * This indicates that this system is IPv6 enabled, but does not + * have a valid global IPv6 address assigned + */ + GNUNET_log (GNUNET_ERROR_TYPE_BULK | GNUNET_ERROR_TYPE_WARNING, + "Network connectivity is down, cannot send beacon!\n"); + } + else + GNUNET_log_strerror (GNUNET_ERROR_TYPE_ERROR, "sendto"); + } else { LOG (GNUNET_ERROR_TYPE_DEBUG, diff --git a/src/transport/plugin_transport_unix.c b/src/transport/plugin_transport_unix.c index 057479d..940582d 100644 --- a/src/transport/plugin_transport_unix.c +++ b/src/transport/plugin_transport_unix.c @@ -43,6 +43,10 @@ #include "transport.h" #define MAX_PROBES 20 +#define MAX_RETRIES 3 +#define RETRY 0 + +#define LOG(kind,...) GNUNET_log_from (kind, "transport-unix",__VA_ARGS__) /* * Transport cost to peer, always 1 for UNIX (direct connection) @@ -82,9 +86,10 @@ struct UNIXMessage struct Session { + struct GNUNET_PeerIdentity target; + void *addr; size_t addrlen; - struct GNUNET_PeerIdentity target; /** * Session timeout task @@ -101,8 +106,9 @@ struct UNIXMessageWrapper struct UNIXMessage * msg; size_t msgsize; + size_t payload; - struct GNUNET_TIME_Relative timeout; + struct GNUNET_TIME_Absolute timeout; unsigned int priority; struct Session *session; @@ -310,7 +316,7 @@ struct LookupCtx }; int lookup_session_it (void *cls, - const GNUNET_HashCode * key, + const struct GNUNET_HashCode * key, void *value) { struct LookupCtx *lctx = cls; @@ -359,7 +365,7 @@ disconnect_session (struct Session *s) GNUNET_assert (plugin != NULL); GNUNET_assert (s != NULL); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Disconnecting session for peer `%s' `%s' \n", GNUNET_i2s (&s->target), s->addr); + LOG (GNUNET_ERROR_TYPE_DEBUG, "Disconnecting session for peer `%s' `%s' \n", GNUNET_i2s (&s->target), s->addr); stop_session_timeout (s); plugin->env->session_end (plugin->env->cls, &s->target, s); @@ -374,7 +380,8 @@ disconnect_session (struct Session *s) continue; GNUNET_CONTAINER_DLL_remove (plugin->msg_head, plugin->msg_tail, msgw); if (NULL != msgw->cont) - msgw->cont (msgw->cont_cls, &msgw->session->target, GNUNET_SYSERR); + msgw->cont (msgw->cont_cls, &msgw->session->target, GNUNET_SYSERR, + msgw->payload, 0); GNUNET_free (msgw->msg); GNUNET_free (msgw); removed = GNUNET_YES; @@ -394,7 +401,7 @@ disconnect_session (struct Session *s) } static int -get_session_delete_it (void *cls, const GNUNET_HashCode * key, void *value) +get_session_delete_it (void *cls, const struct GNUNET_HashCode * key, void *value) { struct Session *s = value; disconnect_session (s); @@ -432,14 +439,14 @@ static int unix_transport_server_stop (void *cls) { struct Plugin *plugin = cls; - - struct UNIXMessageWrapper * msgw = plugin->msg_head; + struct UNIXMessageWrapper * msgw; while (NULL != (msgw = plugin->msg_head)) { GNUNET_CONTAINER_DLL_remove (plugin->msg_head, plugin->msg_tail, msgw); if (msgw->cont != NULL) - msgw->cont (msgw->cont_cls, &msgw->session->target, GNUNET_SYSERR); + msgw->cont (msgw->cont_cls, &msgw->session->target, GNUNET_SYSERR, + msgw->payload, 0); GNUNET_free (msgw->msg); GNUNET_free (msgw); } @@ -474,21 +481,25 @@ unix_transport_server_stop (void *cls) * @param timeout when should we time out (give up) if we can not transmit? * @param addr the addr to send the message to, needs to be a sockaddr for us * @param addrlen the len of addr + * @param payload bytes payload to send * @param cont continuation to call once the message has * been transmitted (or if the transport is ready * for the next transmission call; or if the * peer disconnected...) * @param cont_cls closure for cont * - * @return the number of bytes written, -1 on errors + * @return on success : the number of bytes written, 0 n retry, -1 on errors */ static ssize_t unix_real_send (void *cls, struct GNUNET_NETWORK_Handle *send_handle, const struct GNUNET_PeerIdentity *target, const char *msgbuf, size_t msgbuf_size, unsigned int priority, - struct GNUNET_TIME_Relative timeout, const void *addr, - size_t addrlen, GNUNET_TRANSPORT_TransmitContinuation cont, + struct GNUNET_TIME_Absolute timeout, + const void *addr, + size_t addrlen, + size_t payload, + GNUNET_TRANSPORT_TransmitContinuation cont, void *cont_cls) { struct Plugin *plugin = cls; @@ -497,25 +508,18 @@ unix_real_send (void *cls, size_t sbs; struct sockaddr_un un; size_t slen; - int retry; GNUNET_assert (NULL != plugin); if (send_handle == NULL) { - /* We do not have a send handle */ - GNUNET_break (0); - if (cont != NULL) - cont (cont_cls, target, GNUNET_SYSERR); - return -1; + GNUNET_break (0); /* We do not have a send handle */ + return GNUNET_SYSERR; } if ((addr == NULL) || (addrlen == 0)) { - /* Can never send if we don't have an address */ - GNUNET_break (0); - if (cont != NULL) - cont (cont_cls, target, GNUNET_SYSERR); - return -1; + GNUNET_break (0); /* Can never send if we don't have an address */ + return GNUNET_SYSERR; } /* Prepare address */ @@ -537,88 +541,61 @@ unix_real_send (void *cls, sb = (struct sockaddr *) &un; sbs = slen; +resend: /* Send the data */ sent = 0; - retry = GNUNET_NO; sent = GNUNET_NETWORK_socket_sendto (send_handle, msgbuf, msgbuf_size, sb, sbs); - if ((GNUNET_SYSERR == sent) && ((errno == EAGAIN) || (errno == ENOBUFS))) + if (GNUNET_SYSERR == sent) { - /* We have to retry later: retry */ - return 0; - } - - if ((GNUNET_SYSERR == sent) && (errno == EMSGSIZE)) - { - socklen_t size = 0; - socklen_t len = sizeof (size); - - GNUNET_NETWORK_socket_getsockopt ((struct GNUNET_NETWORK_Handle *) - send_handle, SOL_SOCKET, SO_SNDBUF, &size, - &len); - - if (size < msgbuf_size) + if (errno == EAGAIN) + { + return RETRY; /* We have to retry later */ + } + if (errno == ENOBUFS) + { + return RETRY; /* We have to retry later */ + } + if (errno == EMSGSIZE) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Trying to increase socket buffer size from %i to %i for message size %i\n", - size, - ((msgbuf_size / 1000) + 2) * 1000, - msgbuf_size); - size = ((msgbuf_size / 1000) + 2) * 1000; - if (GNUNET_NETWORK_socket_setsockopt - ((struct GNUNET_NETWORK_Handle *) send_handle, SOL_SOCKET, SO_SNDBUF, - &size, sizeof (size)) == GNUNET_OK) + socklen_t size = 0; + socklen_t len = sizeof (size); + + GNUNET_NETWORK_socket_getsockopt ((struct GNUNET_NETWORK_Handle *) + send_handle, SOL_SOCKET, SO_SNDBUF, &size, + &len); + if (size < msgbuf_size) { - /* Increased buffer size, retry sending */ - return 0; + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Trying to increase socket buffer size from %i to %i for message size %i\n", + size, ((msgbuf_size / 1000) + 2) * 1000, msgbuf_size); + size = ((msgbuf_size / 1000) + 2) * 1000; + if (GNUNET_OK == GNUNET_NETWORK_socket_setsockopt + ((struct GNUNET_NETWORK_Handle *) send_handle, SOL_SOCKET, SO_SNDBUF, + &size, sizeof (size))) + goto resend; /* Increased buffer size, retry sending */ + else + { + /* Could not increase buffer size: error, no retry */ + GNUNET_log_strerror (GNUNET_ERROR_TYPE_ERROR, "setsockopt"); + return GNUNET_SYSERR; + } } else { - /* Could not increase buffer size: error, no retry */ - GNUNET_log_strerror (GNUNET_ERROR_TYPE_ERROR, "setsockopt"); - return -1; + /* Buffer is bigger than message: error, no retry + * This should never happen!*/ + GNUNET_break (0); + return GNUNET_SYSERR; } } - else - { - /* Buffer is bigger than message: error, no retry - * This should never happen!*/ - GNUNET_break (0); - return -1; - } } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + LOG (GNUNET_ERROR_TYPE_DEBUG, "UNIX transmit %u-byte message to %s (%d: %s)\n", (unsigned int) msgbuf_size, GNUNET_a2s (sb, sbs), (int) sent, (sent < 0) ? STRERROR (errno) : "ok"); - - /* Calling continuation */ - if (cont != NULL) - { - if ((sent == GNUNET_SYSERR) && (retry == GNUNET_NO)) - cont (cont_cls, target, GNUNET_SYSERR); - if (sent > 0) - cont (cont_cls, target, GNUNET_OK); - } - - /* return number of bytes successfully sent */ - if (sent > 0) - return sent; - if (sent == 0) - { - /* That should never happen */ - GNUNET_break (0); - return -1; - } - /* failed and retry: return 0 */ - if ((GNUNET_SYSERR == sent) && (retry == GNUNET_YES)) - return 0; - /* failed and no retry: return -1 */ - if ((GNUNET_SYSERR == sent) && (retry == GNUNET_NO)) - return -1; - /* default */ - return -1; + return sent; } struct gsi_ctx @@ -630,12 +607,12 @@ struct gsi_ctx static int -get_session_it (void *cls, const GNUNET_HashCode * key, void *value) +get_session_it (void *cls, const struct GNUNET_HashCode * key, void *value) { struct gsi_ctx *gsi = cls; struct Session *s = value; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Comparing session %s %s\n", gsi->address, s->addr); + LOG (GNUNET_ERROR_TYPE_DEBUG, "Comparing session %s %s\n", gsi->address, s->addr); if ((gsi->addrlen == s->addrlen) && (0 == memcmp (gsi->address, s->addr, s->addrlen))) { @@ -672,7 +649,7 @@ unix_plugin_get_session (void *cls, GNUNET_CONTAINER_multihashmap_get_multiple (plugin->session_map, &address->peer.hashPubKey, &get_session_it, &gsi); if (gsi.res != NULL) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Found existing session\n"); + LOG (GNUNET_ERROR_TYPE_DEBUG, "Found existing session\n"); return gsi.res; } @@ -694,7 +671,7 @@ unix_plugin_get_session (void *cls, "# UNIX sessions active", GNUNET_CONTAINER_multihashmap_size(plugin->session_map), GNUNET_NO); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Creating new session\n"); + LOG (GNUNET_ERROR_TYPE_DEBUG, "Creating new session\n"); return s; } @@ -749,20 +726,24 @@ unix_plugin_send (void *cls, struct UNIXMessageWrapper *wrapper; struct UNIXMessage *message; int ssize; - + GNUNET_assert (plugin != NULL); GNUNET_assert (session != NULL); if (GNUNET_OK != GNUNET_CONTAINER_multihashmap_contains_value(plugin->session_map, &session->target.hashPubKey, session)) { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Invalid session for peer `%s' `%s'\n", + LOG (GNUNET_ERROR_TYPE_ERROR, "Invalid session for peer `%s' `%s'\n", GNUNET_i2s (&session->target), (char *) session->addr); GNUNET_break (0); return GNUNET_SYSERR; } + LOG (GNUNET_ERROR_TYPE_DEBUG, "Sending %u bytes with session for peer `%s' `%s'\n", + msgbuf_size, + GNUNET_i2s (&session->target), + (char *) session->addr); ssize = sizeof (struct UNIXMessage) + msgbuf_size; message = GNUNET_malloc (sizeof (struct UNIXMessage) + msgbuf_size); @@ -777,8 +758,9 @@ unix_plugin_send (void *cls, wrapper = GNUNET_malloc (sizeof (struct UNIXMessageWrapper)); wrapper->msg = message; wrapper->msgsize = ssize; + wrapper->payload = msgbuf_size; wrapper->priority = priority; - wrapper->timeout = to; + wrapper->timeout = GNUNET_TIME_absolute_add (GNUNET_TIME_absolute_get(), to); wrapper->cont = cont; wrapper->cont_cls = cont_cls; wrapper->session = session; @@ -786,15 +768,16 @@ unix_plugin_send (void *cls, GNUNET_CONTAINER_DLL_insert(plugin->msg_head, plugin->msg_tail, wrapper); plugin->bytes_in_queue += ssize; - GNUNET_STATISTICS_set (plugin->env->stats,"# UNIX bytes in send queue", + GNUNET_STATISTICS_set (plugin->env->stats,"# bytes currently in UNIX buffers", plugin->bytes_in_queue, GNUNET_NO); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Sent %d bytes to `%s'\n", ssize, + LOG (GNUNET_ERROR_TYPE_DEBUG, "Sent %d bytes to `%s'\n", ssize, (char *) session->addr); if (plugin->with_ws == GNUNET_NO) { reschedule_select (plugin); } + return ssize; } @@ -824,11 +807,13 @@ unix_demultiplexer (struct Plugin *plugin, struct GNUNET_PeerIdentity *sender, GNUNET_assert (fromlen >= sizeof (struct sockaddr_un)); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received message from %s\n", + LOG (GNUNET_ERROR_TYPE_DEBUG, "Received message from %s\n", un->sun_path); + + plugin->bytes_in_recv += ntohs(currhdr->size); - GNUNET_STATISTICS_set (plugin->env->stats,"# UNIX bytes received", + GNUNET_STATISTICS_set (plugin->env->stats,"# bytes received via UNIX", plugin->bytes_in_recv, GNUNET_NO); addr = GNUNET_HELLO_address_allocate(sender, "unix", un->sun_path, strlen (un->sun_path) + 1); @@ -879,7 +864,7 @@ unix_plugin_select_read (struct Plugin * plugin) #if LINUX un.sun_path[0] = '/'; #endif - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Read %d bytes from socket %s\n", ret, + LOG (GNUNET_ERROR_TYPE_DEBUG, "Read %d bytes from socket %s\n", ret, &un.sun_path[0]); } @@ -916,9 +901,37 @@ unix_plugin_select_read (struct Plugin * plugin) static void unix_plugin_select_write (struct Plugin * plugin) { - static int retry_counter; int sent = 0; - struct UNIXMessageWrapper * msgw = plugin->msg_head; + + struct UNIXMessageWrapper * msgw = plugin->msg_tail; + while (NULL != msgw) + { + if (GNUNET_TIME_absolute_get_remaining (msgw->timeout).rel_value > 0) + break; /* Message is ready for sending */ + else + { + /* Message has a timeout */ + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Timeout for message with %llu bytes \n", msgw->msgsize); + GNUNET_CONTAINER_DLL_remove (plugin->msg_head, plugin->msg_tail, msgw); + if (NULL != msgw->cont) + msgw->cont (msgw->cont_cls, &msgw->session->target, GNUNET_SYSERR, msgw->payload, 0); + + plugin->bytes_in_queue -= msgw->msgsize; + GNUNET_STATISTICS_set (plugin->env->stats, "# bytes currently in UNIX buffers", + plugin->bytes_in_queue, GNUNET_NO); + + plugin->bytes_discarded += msgw->msgsize; + GNUNET_STATISTICS_set (plugin->env->stats,"# UNIX bytes discarded", + plugin->bytes_discarded, GNUNET_NO); + + GNUNET_free (msgw->msg); + GNUNET_free (msgw); + } + msgw = plugin->msg_tail; + } + if (NULL == msgw) + return; /* Nothing to send at the moment */ sent = unix_real_send (plugin, plugin->unix_sock.desc, @@ -929,33 +942,26 @@ unix_plugin_select_write (struct Plugin * plugin) msgw->timeout, msgw->session->addr, msgw->session->addrlen, + msgw->payload, msgw->cont, msgw->cont_cls); - if (sent == 0) + if (RETRY == sent) { - /* failed and retry */ - retry_counter++; - GNUNET_STATISTICS_set (plugin->env->stats,"# UNIX retry attempt", - retry_counter, GNUNET_NO); - return; - } + GNUNET_STATISTICS_update (plugin->env->stats,"# UNIX retry attempts", + 1, GNUNET_NO); - if (retry_counter > 0 ) - { - /* no retry: reset counter */ - retry_counter = 0; - GNUNET_STATISTICS_set (plugin->env->stats,"# UNIX retry attempt", - retry_counter, GNUNET_NO); } - - if (sent == -1) + else if (GNUNET_SYSERR == sent) { /* failed and no retry */ + if (NULL != msgw->cont) + msgw->cont (msgw->cont_cls, &msgw->session->target, GNUNET_SYSERR, msgw->payload, 0); + GNUNET_CONTAINER_DLL_remove(plugin->msg_head, plugin->msg_tail, msgw); GNUNET_assert (plugin->bytes_in_queue >= msgw->msgsize); plugin->bytes_in_queue -= msgw->msgsize; - GNUNET_STATISTICS_set (plugin->env->stats,"# UNIX bytes in send queue", + GNUNET_STATISTICS_set (plugin->env->stats, "# bytes currently in UNIX buffers", plugin->bytes_in_queue, GNUNET_NO); plugin->bytes_discarded += msgw->msgsize; GNUNET_STATISTICS_set (plugin->env->stats,"# UNIX bytes discarded", @@ -965,25 +971,26 @@ unix_plugin_select_write (struct Plugin * plugin) GNUNET_free (msgw); return; } - - if (sent > 0) + else if (sent > 0) { /* successfully sent bytes */ + if (NULL != msgw->cont) + msgw->cont (msgw->cont_cls, &msgw->session->target, GNUNET_OK, msgw->payload, msgw->msgsize); + GNUNET_CONTAINER_DLL_remove(plugin->msg_head, plugin->msg_tail, msgw); GNUNET_assert (plugin->bytes_in_queue >= msgw->msgsize); plugin->bytes_in_queue -= msgw->msgsize; - GNUNET_STATISTICS_set (plugin->env->stats,"# UNIX bytes in send queue", + GNUNET_STATISTICS_set (plugin->env->stats,"# bytes currently in UNIX buffers", plugin->bytes_in_queue, GNUNET_NO); plugin->bytes_in_sent += msgw->msgsize; - GNUNET_STATISTICS_set (plugin->env->stats,"# UNIX bytes sent", + GNUNET_STATISTICS_set (plugin->env->stats,"# bytes transmitted via UNIX", plugin->bytes_in_sent, GNUNET_NO); GNUNET_free (msgw->msg); GNUNET_free (msgw); return; } - } @@ -1074,8 +1081,7 @@ unix_transport_server_start (void *cls) plugin->unix_sock.desc = NULL; return GNUNET_SYSERR; } - GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, "unix", "Bound to `%s'\n", - &un.sun_path[0]); + LOG (GNUNET_ERROR_TYPE_DEBUG, "Bound to `%s'\n", plugin->unix_socket_path); plugin->rs = GNUNET_NETWORK_fdset_create (); plugin->ws = GNUNET_NETWORK_fdset_create (); GNUNET_NETWORK_fdset_zero (plugin->rs); @@ -1108,7 +1114,7 @@ unix_transport_server_start (void *cls) static int unix_check_address (void *cls, const void *addr, size_t addrlen) { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + LOG (GNUNET_ERROR_TYPE_DEBUG, "Informing transport service about my address `%s'\n", (char *) addr); return GNUNET_OK; @@ -1223,7 +1229,8 @@ address_notification (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) plugin->env->notify_address (plugin->env->cls, GNUNET_YES, plugin->unix_socket_path, - strlen (plugin->unix_socket_path) + 1); + strlen (plugin->unix_socket_path) + 1, + "unix"); } @@ -1237,15 +1244,14 @@ session_timeout (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) struct Session *s = cls; s->timeout_task = GNUNET_SCHEDULER_NO_TASK; - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Session %p was idle for %llu, disconnecting\n", - s, GNUNET_CONSTANTS_IDLE_CONNECTION_TIMEOUT.rel_value); - + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Session %p was idle for %llu ms, disconnecting\n", + s, (unsigned long long) GNUNET_CONSTANTS_IDLE_CONNECTION_TIMEOUT.rel_value); /* call session destroy function */ disconnect_session(s); - } + /** * Start session timeout */ @@ -1254,15 +1260,15 @@ start_session_timeout (struct Session *s) { GNUNET_assert (NULL != s); GNUNET_assert (GNUNET_SCHEDULER_NO_TASK == s->timeout_task); - s->timeout_task = GNUNET_SCHEDULER_add_delayed (GNUNET_CONSTANTS_IDLE_CONNECTION_TIMEOUT, &session_timeout, s); - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Timeout for session %p set to %llu\n", - s, GNUNET_CONSTANTS_IDLE_CONNECTION_TIMEOUT.rel_value); + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Timeout for session %p set to %llu ms\n", + s, (unsigned long long) GNUNET_CONSTANTS_IDLE_CONNECTION_TIMEOUT.rel_value); } + /** * Increment session timeout due to activity */ @@ -1276,11 +1282,12 @@ reschedule_session_timeout (struct Session *s) s->timeout_task = GNUNET_SCHEDULER_add_delayed (GNUNET_CONSTANTS_IDLE_CONNECTION_TIMEOUT, &session_timeout, s); - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Timeout rescheduled for session %p set to %llu\n", - s, GNUNET_CONSTANTS_IDLE_CONNECTION_TIMEOUT.rel_value); + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Timeout rescheduled for session %p set to %llu ms\n", + s, (unsigned long long) GNUNET_CONSTANTS_IDLE_CONNECTION_TIMEOUT.rel_value); } + /** * Cancel timeout */ @@ -1293,18 +1300,12 @@ stop_session_timeout (struct Session *s) { GNUNET_SCHEDULER_cancel (s->timeout_task); s->timeout_task = GNUNET_SCHEDULER_NO_TASK; - - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Timeout rescheduled for session %p canceled\n", - s, GNUNET_CONSTANTS_IDLE_CONNECTION_TIMEOUT.rel_value); - } - else - { - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Timeout for session %p was not active\n", - s); + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Timeout stopped for session %p canceled\n", + s, (unsigned long long) GNUNET_CONSTANTS_IDLE_CONNECTION_TIMEOUT.rel_value); } } - /** * The exported method. Makes the core api available via a global and * returns the unix transport API. @@ -1353,9 +1354,9 @@ libgnunet_plugin_transport_unix_init (void *cls) api->string_to_address = &unix_string_to_address; sockets_created = unix_transport_server_start (plugin); if (sockets_created == 0) - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, _("Failed to open UNIX sockets\n")); + LOG (GNUNET_ERROR_TYPE_WARNING, _("Failed to open UNIX sockets\n")); - plugin->session_map = GNUNET_CONTAINER_multihashmap_create(10); + plugin->session_map = GNUNET_CONTAINER_multihashmap_create (10, GNUNET_NO); GNUNET_SCHEDULER_add_now (address_notification, plugin); return api; @@ -1372,11 +1373,19 @@ libgnunet_plugin_transport_unix_done (void *cls) GNUNET_free (api); return NULL; } + + plugin->env->notify_address (plugin->env->cls, GNUNET_NO, + plugin->unix_socket_path, + strlen (plugin->unix_socket_path) + 1, + "unix"); + unix_transport_server_stop (plugin); + GNUNET_CONTAINER_multihashmap_iterate (plugin->session_map, &get_session_delete_it, plugin); GNUNET_CONTAINER_multihashmap_destroy (plugin->session_map); + if (NULL != plugin->rs) GNUNET_NETWORK_fdset_destroy (plugin->rs); if (NULL != plugin->ws) diff --git a/src/transport/plugin_transport_wlan.c b/src/transport/plugin_transport_wlan.c index aed4b22..5fed7a7 100644 --- a/src/transport/plugin_transport_wlan.c +++ b/src/transport/plugin_transport_wlan.c @@ -152,6 +152,11 @@ struct PendingMessage */ struct Session { + /** + * To whom are we talking to (set to our identity + * if we are still waiting for the welcome message) + */ + struct GNUNET_PeerIdentity target; /** * API requirement (must be first). @@ -185,12 +190,6 @@ struct Session */ struct PendingMessage *pending_message_tail; - /** - * To whom are we talking to (set to our identity - * if we are still waiting for the welcome message) - */ - struct GNUNET_PeerIdentity target; - /** * When should this session time out? */ @@ -261,6 +260,16 @@ struct FragmentMessage */ void *cont_cls; + /** + * Size of original message + */ + size_t size_payload; + + /** + * Number of bytes used to transmit message + */ + size_t size_on_wire; + }; @@ -330,6 +339,16 @@ struct MacEndpoint */ struct GNUNET_TRANSPORT_WLAN_MacAddress addr; + /** + * Message delay for fragmentation context + */ + struct GNUNET_TIME_Relative msg_delay; + + /** + * ACK delay for fragmentation context + */ + struct GNUNET_TIME_Relative ack_delay; + /** * Desired transmission power for this MAC */ @@ -707,6 +726,7 @@ fragment_transmission_done (void *cls, { struct FragmentMessage *fm = cls; + fm->sh = NULL; GNUNET_FRAGMENT_context_transmission_done (fm->fragcontext); } @@ -745,11 +765,18 @@ transmit_fragment (void *cls, &radio_header->header, GNUNET_NO, &fragment_transmission_done, fm); + fm->size_on_wire += size; if (NULL != fm->sh) GNUNET_STATISTICS_update (endpoint->plugin->env->stats, _("# WLAN message fragments sent"), 1, GNUNET_NO); else GNUNET_FRAGMENT_context_transmission_done (fm->fragcontext); + GNUNET_STATISTICS_update (endpoint->plugin->env->stats, + "# bytes currently in WLAN buffers", + -msize, GNUNET_NO); + GNUNET_STATISTICS_update (endpoint->plugin->env->stats, + "# bytes transmitted via WLAN", + msize, GNUNET_NO); } } @@ -773,7 +800,9 @@ free_fragment_message (struct FragmentMessage *fm) GNUNET_HELPER_send_cancel (fm->sh); fm->sh = NULL; } - GNUNET_FRAGMENT_context_destroy (fm->fragcontext); + GNUNET_FRAGMENT_context_destroy (fm->fragcontext, + &endpoint->msg_delay, + &endpoint->ack_delay); if (fm->timeout_task != GNUNET_SCHEDULER_NO_TASK) { GNUNET_SCHEDULER_cancel (fm->timeout_task); @@ -798,7 +827,7 @@ fragmentmessage_timeout (void *cls, fm->timeout_task = GNUNET_SCHEDULER_NO_TASK; if (NULL != fm->cont) { - fm->cont (fm->cont_cls, &fm->target, GNUNET_SYSERR); + fm->cont (fm->cont_cls, &fm->target, GNUNET_SYSERR, fm->size_payload, fm->size_on_wire); fm->cont = NULL; } free_fragment_message (fm); @@ -812,6 +841,7 @@ fragmentmessage_timeout (void *cls, * @param timeout how long can the message wait? * @param target peer that should receive the message * @param msg message to transmit + * @param payload_size bytes of payload * @param cont continuation to call once the message has * been transmitted (or if the transport is ready * for the next transmission call; or if the @@ -823,6 +853,7 @@ send_with_fragmentation (struct MacEndpoint *endpoint, struct GNUNET_TIME_Relative timeout, const struct GNUNET_PeerIdentity *target, const struct GNUNET_MessageHeader *msg, + size_t payload_size, GNUNET_TRANSPORT_TransmitContinuation cont, void *cont_cls) { @@ -833,13 +864,17 @@ send_with_fragmentation (struct MacEndpoint *endpoint, fm = GNUNET_malloc (sizeof (struct FragmentMessage)); fm->macendpoint = endpoint; fm->target = *target; + fm->size_payload = payload_size; + fm->size_on_wire = 0; fm->timeout = GNUNET_TIME_relative_to_absolute (timeout); fm->cont = cont; fm->cont_cls = cont_cls; + /* 1 MBit/s typical data rate, 1430 byte fragments => ~100 ms per message */ fm->fragcontext = GNUNET_FRAGMENT_context_create (plugin->env->stats, WLAN_MTU, &plugin->tracker, - GNUNET_TIME_UNIT_SECONDS, + endpoint->msg_delay, + endpoint->ack_delay, msg, &transmit_fragment, fm); fm->timeout_task = @@ -939,6 +974,10 @@ create_macendpoint (struct Plugin *plugin, pos, &wlan_data_message_handler, &send_ack); + + pos->msg_delay = GNUNET_TIME_UNIT_MILLISECONDS; + pos->ack_delay = GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MILLISECONDS, + 100); pos->timeout = GNUNET_TIME_relative_to_absolute (MACENDPOINT_TIMEOUT); pos->timeout_task = GNUNET_SCHEDULER_add_delayed (MACENDPOINT_TIMEOUT, &macendpoint_timeout, @@ -1064,10 +1103,16 @@ wlan_plugin_send (void *cls, wlanheader->target = session->target; wlanheader->crc = htonl (GNUNET_CRYPTO_crc32_n (msgbuf, msgbuf_size)); memcpy (&wlanheader[1], msgbuf, msgbuf_size); + + GNUNET_STATISTICS_update (plugin->env->stats, + "# bytes currently in WLAN buffers", + msgbuf_size, GNUNET_NO); + send_with_fragmentation (session->mac, to, &session->target, &wlanheader->header, + msgbuf_size, cont, cont_cls); return size; } @@ -1100,6 +1145,11 @@ process_data (void *cls, void *client, const struct GNUNET_MessageHeader *hdr) ats[1].type = htonl (GNUNET_ATS_NETWORK_TYPE); ats[1].value = htonl (GNUNET_ATS_NET_WLAN); msize = ntohs (hdr->size); + + GNUNET_STATISTICS_update (plugin->env->stats, + "# bytes received via WLAN", + msize, GNUNET_NO); + switch (ntohs (hdr->type)) { case GNUNET_MESSAGE_TYPE_HELLO: @@ -1161,7 +1211,7 @@ process_data (void *cls, void *client, const struct GNUNET_MessageHeader *hdr) mas->endpoint->timeout = GNUNET_TIME_relative_to_absolute (MACENDPOINT_TIMEOUT); if (NULL != fm->cont) { - fm->cont (fm->cont_cls, &fm->target, GNUNET_OK); + fm->cont (fm->cont_cls, &fm->target, GNUNET_OK, fm->size_payload, fm->size_on_wire); fm->cont = NULL; } free_fragment_message (fm); @@ -1286,7 +1336,8 @@ handle_helper_message (void *cls, void *client, /* remove old address */ plugin->env->notify_address (plugin->env->cls, GNUNET_NO, &plugin->mac_address, - sizeof (struct GNUNET_TRANSPORT_WLAN_MacAddress)); + sizeof (struct GNUNET_TRANSPORT_WLAN_MacAddress), + "wlan"); } plugin->mac_address = cm->mac; plugin->have_mac = GNUNET_YES; @@ -1296,7 +1347,8 @@ handle_helper_message (void *cls, void *client, GNUNET_i2s (plugin->env->my_identity)); plugin->env->notify_address (plugin->env->cls, GNUNET_YES, &plugin->mac_address, - sizeof (struct GNUNET_TRANSPORT_WLAN_MacAddress)); + sizeof (struct GNUNET_TRANSPORT_WLAN_MacAddress), + "wlan"); break; case GNUNET_MESSAGE_TYPE_WLAN_DATA_FROM_HELPER: LOG (GNUNET_ERROR_TYPE_DEBUG, @@ -1476,7 +1528,7 @@ wlan_plugin_address_to_string (void *cls, const void *addr, size_t addrlen) return NULL; } mac = addr; - return GNUNET_strdup (mac_to_string (mac)); + return mac_to_string (mac); } @@ -1538,6 +1590,16 @@ libgnunet_plugin_transport_wlan_done (void *cls) GNUNET_free (api); return NULL; } + + if (GNUNET_YES == plugin->have_mac) + { + plugin->env->notify_address (plugin->env->cls, GNUNET_NO, + &plugin->mac_address, + sizeof (struct GNUNET_TRANSPORT_WLAN_MacAddress), + "wlan"); + plugin->have_mac = GNUNET_NO; + } + if (GNUNET_SCHEDULER_NO_TASK != plugin->beacon_task) { GNUNET_SCHEDULER_cancel (plugin->beacon_task); @@ -1641,6 +1703,7 @@ libgnunet_plugin_transport_wlan_init (void *cls) struct Plugin *plugin; char *interface; unsigned long long testmode; + char *binary; /* check for 'special' mode */ if (NULL == env->receive) @@ -1663,30 +1726,29 @@ libgnunet_plugin_transport_wlan_init (void *cls) GNUNET_CONFIGURATION_get_value_number (env->cfg, "transport-wlan", "TESTMODE", &testmode)) || (testmode > 2) ) ) - { - LOG (GNUNET_ERROR_TYPE_ERROR, - _("Invalid configuration option `%s' in section `%s'\n"), - "TESTMODE", - "transport-wlan"); + { + GNUNET_log_config_missing (GNUNET_ERROR_TYPE_ERROR, + "transport-wlan", "TESTMODE"); return NULL; } + binary = GNUNET_OS_get_libexec_binary_path ("gnunet-helper-transport-wlan"); if ( (0 == testmode) && - (GNUNET_YES != GNUNET_OS_check_helper_binary ("gnunet-helper-transport-wlan")) ) + (GNUNET_YES != GNUNET_OS_check_helper_binary (binary)) ) { LOG (GNUNET_ERROR_TYPE_ERROR, _("Helper binary `%s' not SUID, cannot run WLAN transport\n"), "gnunet-helper-transport-wlan"); + GNUNET_free (binary); return NULL; } + GNUNET_free (binary); if (GNUNET_YES != GNUNET_CONFIGURATION_get_value_string (env->cfg, "transport-wlan", "INTERFACE", &interface)) { - LOG (GNUNET_ERROR_TYPE_ERROR, - _("Missing configuration option `%s' in section `%s'\n"), - "INTERFACE", - "transport-wlan"); + GNUNET_log_config_missing (GNUNET_ERROR_TYPE_ERROR, + "transport-wlan", "INTERFACE"); return NULL; } @@ -1705,33 +1767,40 @@ libgnunet_plugin_transport_wlan_init (void *cls) plugin->helper_payload_tokenizer = GNUNET_SERVER_mst_create (&process_data, plugin); plugin->beacon_task = GNUNET_SCHEDULER_add_now (&send_hello_beacon, plugin); - switch (testmode) + /* some compilers do not like switch on 'long long'... */ + switch ((unsigned int) testmode) { case 0: /* normal */ plugin->helper_argv[0] = (char *) "gnunet-helper-transport-wlan"; plugin->helper_argv[1] = interface; plugin->helper_argv[2] = NULL; - plugin->suid_helper = GNUNET_HELPER_start ("gnunet-helper-transport-wlan", + plugin->suid_helper = GNUNET_HELPER_start (GNUNET_NO, + "gnunet-helper-transport-wlan", plugin->helper_argv, &handle_helper_message, + NULL, plugin); break; case 1: /* testmode, peer 1 */ plugin->helper_argv[0] = (char *) "gnunet-helper-transport-wlan-dummy"; plugin->helper_argv[1] = (char *) "1"; plugin->helper_argv[2] = NULL; - plugin->suid_helper = GNUNET_HELPER_start ("gnunet-helper-transport-wlan-dummy", + plugin->suid_helper = GNUNET_HELPER_start (GNUNET_NO, + "gnunet-helper-transport-wlan-dummy", plugin->helper_argv, &handle_helper_message, + NULL, plugin); break; case 2: /* testmode, peer 2 */ plugin->helper_argv[0] = (char *) "gnunet-helper-transport-wlan-dummy"; plugin->helper_argv[1] = (char *) "2"; plugin->helper_argv[2] = NULL; - plugin->suid_helper = GNUNET_HELPER_start ("gnunet-helper-transport-wlan-dummy", + plugin->suid_helper = GNUNET_HELPER_start (GNUNET_NO, + "gnunet-helper-transport-wlan-dummy", plugin->helper_argv, &handle_helper_message, + NULL, plugin); break; default: diff --git a/src/transport/plugin_transport_wlan.h b/src/transport/plugin_transport_wlan.h index 2b70fc0..b7f22de 100644 --- a/src/transport/plugin_transport_wlan.h +++ b/src/transport/plugin_transport_wlan.h @@ -80,6 +80,29 @@ struct GNUNET_TRANSPORT_WLAN_HelperControlMessage struct GNUNET_TRANSPORT_WLAN_MacAddress mac; }; +/** + * generic definitions for IEEE 802.3 frames + */ +struct GNUNET_TRANSPORT_WLAN_Ieee8023Frame +{ + + /** + * Address 1: destination address in ad-hoc mode or AP, BSSID if station, + */ + struct GNUNET_TRANSPORT_WLAN_MacAddress dst; + + /** + * Address 2: source address if in ad-hoc-mode or station, BSSID if AP + */ + struct GNUNET_TRANSPORT_WLAN_MacAddress src; + + /** + * Packet type ID. + */ + uint16_t type; + +}; + /** * generic definitions for IEEE 802.11 frames diff --git a/src/transport/template_cfg_peer1.conf b/src/transport/template_cfg_peer1.conf index 2b8e9b2..8856418 100644 --- a/src/transport/template_cfg_peer1.conf +++ b/src/transport/template_cfg_peer1.conf @@ -1,7 +1,6 @@ @INLINE@ test_transport_defaults.conf [PATHS] SERVICEHOME = /tmp/test-transport/api-tcp-p1/ -DEFAULTCONFIG = template_cfg_peer1.conf [gnunetd] HOSTKEY = $SERVICEHOME/.hostkey @@ -40,13 +39,11 @@ UNIXPATH = /tmp/gnunet-p1-service-peerinfo.sock [transport] #PREFIX = valgrind --leak-check=full PORT = 12001 -#DEBUG = YES UNIXPATH = /tmp/gnunet-p1-service-transport.sock [ats] -#DEBUG = YES -WAN_QUOTA_IN = 1 GB -WAN_QUOTA_OUT = 1 GB +WAN_QUOTA_IN = unlimited +WAN_QUOTA_OUT = unlimited PORT = 12006 UNIXPATH = /tmp/gnunet-p1-service-ats.sock diff --git a/src/transport/template_cfg_peer2.conf b/src/transport/template_cfg_peer2.conf index 3b86137..54636ca 100644 --- a/src/transport/template_cfg_peer2.conf +++ b/src/transport/template_cfg_peer2.conf @@ -1,7 +1,6 @@ @INLINE@ test_transport_defaults.conf [PATHS] SERVICEHOME = /tmp/test-transport/api-tcp-p2/ -DEFAULTCONFIG = template_cfg_peer2.conf [gnunetd] HOSTKEY = $SERVICEHOME/.hostkey @@ -44,9 +43,8 @@ PORT = 12010 UNIXPATH = /tmp/gnunet-p2-service-transport.sock [ats] -#DEBUG = YES -WAN_QUOTA_IN = 1 GB -WAN_QUOTA_OUT = 1 GB +WAN_QUOTA_IN = unlimited +WAN_QUOTA_OUT = unlimited PORT = 12016 UNIXPATH = /tmp/gnunet-p2-service-ats.sock diff --git a/src/transport/test_http_common.c b/src/transport/test_http_common.c new file mode 100644 index 0000000..c97ae17 --- /dev/null +++ b/src/transport/test_http_common.c @@ -0,0 +1,264 @@ +/* + This file is part of GNUnet. + (C) 2009, 2010 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ +/** + * @file transport/test_http_common.c + * @brief base test case for common http functionality + */ +#include "platform.h" +#include "gnunet_transport_service.h" +#include "transport-testing.h" +#include "plugin_transport_http_common.h" + +struct SplittedHTTPAddress +{ + char *protocol; + char *host; + char *path; + int port; +}; + +void +clean (struct SplittedHTTPAddress *addr) +{ + if (NULL != addr) + { + GNUNET_free_non_null (addr->host); + GNUNET_free_non_null (addr->path); + GNUNET_free_non_null (addr->protocol); + GNUNET_free_non_null (addr); + } +} + + +int +check (struct SplittedHTTPAddress *addr, + char * protocol, + char * host, + int port, + char * path) +{ + + if (NULL == addr) + return GNUNET_NO; + if (((NULL == addr->protocol) && (NULL != protocol)) || + ((NULL != addr->protocol) && (NULL == protocol))) + { + GNUNET_break (0); + return GNUNET_NO; + } + else if ((NULL != addr->protocol) && (NULL != protocol)) + { + if (0 != strcmp(addr->protocol, protocol)) + { + GNUNET_break (0); + return GNUNET_NO; + } + } + + if (((NULL == addr->host) && (NULL != host)) || + ((NULL != addr->host) && (NULL == host))) + { + GNUNET_break (0); + return GNUNET_NO; + } + else if ((NULL != addr->host) && (NULL != host)) + { + if (0 != strcmp(addr->host, host)) + { + GNUNET_break (0); + return GNUNET_NO; + } + } + + + if (((NULL == addr->path) && (NULL != path)) || + ((NULL != addr->path) && (NULL == path))) + { + GNUNET_break (0); + return GNUNET_NO; + } + else if ((NULL != addr->path) && (NULL != path)) + { + if (0 != strcmp(addr->path, path)) + { + GNUNET_break (0); + return GNUNET_NO; + } + } + + if ((addr->port != port)) + { + GNUNET_break (0); + return GNUNET_NO; + } + + return GNUNET_OK; +} + +int +check_pass (char *src, + char * protocol, + char * host, + int port, + char * path) +{ + struct SplittedHTTPAddress * spa; + spa = http_split_address (src); + if (NULL == spa) + { + GNUNET_break (0); + return GNUNET_SYSERR; + } + else + { + if (GNUNET_OK != check(spa, protocol, host, port, path)) + { + clean (spa); + GNUNET_break (0); + return GNUNET_SYSERR; + } + clean (spa); + } + return GNUNET_OK; +} + +int +check_fail (char *src) +{ + struct SplittedHTTPAddress * spa; + spa = http_split_address (src); + if (NULL != spa) + { + GNUNET_break (0); + clean (spa); + return GNUNET_SYSERR; + } + return GNUNET_OK; +} + + +void +test_pass_hostname () +{ + check_pass("http://test.local", "http", "test.local", HTTP_DEFAULT_PORT, ""); + check_pass("http://test.local/", "http", "test.local", HTTP_DEFAULT_PORT, "/"); + check_pass("http://test.local/path", "http", "test.local", HTTP_DEFAULT_PORT, "/path"); + check_pass("http://test.local/path/", "http", "test.local", HTTP_DEFAULT_PORT, "/path/"); + check_pass("http://test.local/path/more", "http", "test.local", HTTP_DEFAULT_PORT, "/path/more"); + check_pass("http://test.local:81", "http", "test.local", 81, ""); + check_pass("http://test.local:81/", "http", "test.local", 81, "/"); + check_pass("http://test.local:81/path", "http", "test.local", 81, "/path"); + check_pass("http://test.local:81/path/", "http", "test.local", 81, "/path/"); + check_pass("http://test.local:81/path/more", "http", "test.local", 81, "/path/more"); + +} + + +void +test_pass_ipv4 () +{ + check_pass("http://127.0.0.1", "http", "127.0.0.1", HTTP_DEFAULT_PORT, ""); + check_pass("http://127.0.0.1/", "http", "127.0.0.1", HTTP_DEFAULT_PORT, "/"); + check_pass("http://127.0.0.1/path", "http", "127.0.0.1", HTTP_DEFAULT_PORT, "/path"); + check_pass("http://127.0.0.1/path/", "http", "127.0.0.1", HTTP_DEFAULT_PORT, "/path/"); + check_pass("http://127.0.0.1:81", "http", "127.0.0.1", 81, ""); + check_pass("http://127.0.0.1:81/", "http", "127.0.0.1", 81, "/"); + check_pass("http://127.0.0.1:81/path", "http", "127.0.0.1", 81, "/path"); + check_pass("http://127.0.0.1:81/path/", "http", "127.0.0.1", 81, "/path/"); + check_pass("http://127.0.0.1:81/path/more", "http", "127.0.0.1", 81, "/path/more"); +} + +void +test_fail_ipv6 () +{ + check_pass("http://[::1]", "http", "[::1]", HTTP_DEFAULT_PORT, ""); + check_pass("http://[::1]/", "http", "[::1]", HTTP_DEFAULT_PORT, "/"); + check_pass("http://[::1]/path", "http", "[::1]", HTTP_DEFAULT_PORT, "/path"); + check_pass("http://[::1]/path/", "http", "[::1]", HTTP_DEFAULT_PORT, "/path/"); + check_pass("http://[::1]:81", "http", "[::1]", 81, ""); + check_pass("http://[::1]:81/", "http", "[::1]", 81, "/"); + check_pass("http://[::1]:81/path", "http", "[::1]", 81, "/path"); + check_pass("http://[::1]:81/path/", "http", "[::1]", 81, "/path/"); + check_pass("http://[::1]:81/path/more", "http", "[::1]", 81, "/path/more"); +} + + +void +test_fail () +{ + if (GNUNET_SYSERR == check_fail ("")) + GNUNET_break (0); + if (GNUNET_SYSERR == check_fail ("http")) + GNUNET_break (0); + if (GNUNET_SYSERR == check_fail ("://")) + GNUNET_break (0); + if (GNUNET_SYSERR == check_fail ("http://")) + GNUNET_break (0); + if (GNUNET_SYSERR == check_fail ("//localhost")) + GNUNET_break (0); + if (GNUNET_SYSERR == check_fail ("//:80")) + GNUNET_break (0); + if (GNUNET_SYSERR == check_fail ("//:80/")) + GNUNET_break (0); + if (GNUNET_SYSERR == check_fail ("//:80:")) + GNUNET_break (0); + if (GNUNET_SYSERR == check_fail ("http://localhost:a/")) + GNUNET_break (0); + if (GNUNET_SYSERR == check_fail ("http://127.0.0.1:a/")) + GNUNET_break (0); +} + +int +main (int argc, char *argv[]) +{ + int ret = 0; + struct SplittedHTTPAddress * spa; + GNUNET_log_setup ("test", "DEBUG", NULL); + + spa = http_split_address (""); + if (NULL != spa) + { + clean (spa); + GNUNET_break (0); + } + + http_split_address ("http://"); + if (NULL != spa) + { + clean (spa); + GNUNET_break (0); + } + + http_split_address ("://"); + if (NULL != spa) + { + clean (spa); + GNUNET_break (0); + } + + test_pass_hostname (); + test_pass_ipv4 (); + test_fail_ipv6 (); + test_fail (); + + return ret; +} + +/* end of test_http_common.c */ diff --git a/src/transport/test_plugin_hostkey b/src/transport/test_plugin_hostkey new file mode 100644 index 0000000..13f1dc9 Binary files /dev/null and b/src/transport/test_plugin_hostkey differ diff --git a/src/transport/test_plugin_hostkey.ecc b/src/transport/test_plugin_hostkey.ecc new file mode 100644 index 0000000..c56a08e Binary files /dev/null and b/src/transport/test_plugin_hostkey.ecc differ diff --git a/src/transport/test_plugin_transport.c b/src/transport/test_plugin_transport.c new file mode 100644 index 0000000..f0dbc41 --- /dev/null +++ b/src/transport/test_plugin_transport.c @@ -0,0 +1,728 @@ +/* + This file is part of GNUnet. + (C) 2009 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ +/** + * @file transport/test_plugin_transport.c + * @brief testcase for transport_api.c + * @author Sailor Siraj + * @author Christian Grothoff + */ + +#include "platform.h" +#include "gnunet_common.h" +#include "gnunet_constants.h" +#include "gnunet_util_lib.h" +#include "gnunet_hello_lib.h" +#include "gnunet_peerinfo_service.h" +#include "gnunet_statistics_service.h" +#include "gnunet_protocols.h" +#include "gnunet_signatures.h" +#include "gnunet_transport_plugin.h" + +#include "transport.h" + +/** + * How long until we give up on transmitting the message? + */ +#define WAIT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 5) +#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 30) + +#define HOSTKEY_FILE "test_plugin_hostkey" + +/** + * Our public key. + */ +static struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded my_public_key; + +/** + * Our identity. + */ +static struct GNUNET_PeerIdentity my_identity; + +/** + * Our private key. + */ +static struct GNUNET_CRYPTO_RsaPrivateKey *my_private_key; + +/** + * Our configuration. + */ +const struct GNUNET_CONFIGURATION_Handle *cfg; + +/** + * Our configuration. + */ +struct GNUNET_STATISTICS_Handle *stats; + +/** + * Our HELLO + */ +struct GNUNET_HELLO_Message *hello; + +/** + * Number of neighbours we'd like to have. + */ +static uint32_t max_connect_per_transport; + +/** + * Environment for this plugin. + */ +struct GNUNET_TRANSPORT_PluginEnvironment env; + +/** + *handle for the api provided by this plugin + */ +struct GNUNET_TRANSPORT_PluginFunctions *api; + +/** + * Helper handler + */ +struct GNUNET_HELPER_Handle *suid_helper; + +/** + * Timeout task + */ +static GNUNET_SCHEDULER_TaskIdentifier timeout_endbadly; + +/** + * Timeout task + */ +static GNUNET_SCHEDULER_TaskIdentifier timeout_wait; + +/** + * Library name + */ +static char *libname; + +/** + * Plugin addresses head + */ +struct AddressWrapper *head; + +/** + * Plugin addresses tail + */ +struct AddressWrapper *tail; + +unsigned int addresses_reported; + +unsigned int pretty_printers_running; + +/** + * Did the test pass or fail? + */ +static int ok; + + +struct AddressWrapper +{ + struct AddressWrapper *next; + + struct AddressWrapper *prev; + + void *addr; + + size_t addrlen; + + char *addrstring; +}; + + +static void +end () +{ + struct AddressWrapper *w; + int c = 0; + ok = 0; + + if (GNUNET_SCHEDULER_NO_TASK != timeout_endbadly) + { + GNUNET_SCHEDULER_cancel (timeout_endbadly); + timeout_endbadly = GNUNET_SCHEDULER_NO_TASK; + } + if (NULL != api) + GNUNET_PLUGIN_unload (libname, api); + + while (NULL != head) + { + w = head; + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Plugin did not remove address `%s' \n"), w->addrstring); + GNUNET_CONTAINER_DLL_remove (head, tail, w); + c ++; + GNUNET_free (w->addr); + GNUNET_free (w->addrstring); + GNUNET_free (w); + } + if (c > 0) + { + GNUNET_break (0); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Plugin did not remove %u addresses \n"), c); + ok = 1; + } + + + GNUNET_free (libname); + libname = NULL; + GNUNET_STATISTICS_destroy (stats, GNUNET_NO); + stats = NULL; + + if (NULL != suid_helper) + { + GNUNET_HELPER_stop (suid_helper); + suid_helper = NULL; + } +} + + +static void +end_badly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct AddressWrapper *w; + int c = 0; + timeout_endbadly = GNUNET_SCHEDULER_NO_TASK; + if (GNUNET_SCHEDULER_NO_TASK != timeout_wait) + { + GNUNET_SCHEDULER_cancel (timeout_wait); + timeout_wait = GNUNET_SCHEDULER_NO_TASK; + } + + if (pretty_printers_running > 0) + { + timeout_endbadly = GNUNET_SCHEDULER_add_delayed(GNUNET_TIME_UNIT_SECONDS, &end_badly, &ok); + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + _("Have pending calls to pretty_printer ... deferring shutdown\n")); + return; + } + + if (NULL != cls) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Test took too long to execute, timeout .... \n")); + } + + if (NULL != libname) + { + if (NULL != api) + GNUNET_PLUGIN_unload (libname, api); + GNUNET_free (libname); + libname = NULL; + } + + while (NULL != head) + { + w = head; + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Plugin did not remove address `%s' \n"), w->addrstring); + GNUNET_CONTAINER_DLL_remove (head, tail, w); + c ++; + GNUNET_free (w->addr); + GNUNET_free (w->addrstring); + GNUNET_free (w); + } + if (c > 0) + { + GNUNET_break (0); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Plugin did not remove %u addresses \n"), c); + } + + if (NULL != stats) + { + GNUNET_STATISTICS_destroy (stats, GNUNET_NO); + stats = NULL; + } + + if (NULL != suid_helper) + { + GNUNET_HELPER_stop (suid_helper); + suid_helper = NULL; + } + + ok = 1; +} + + +static void +wait_end (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + timeout_wait = GNUNET_SCHEDULER_NO_TASK; + if (0 == addresses_reported) + GNUNET_log (GNUNET_ERROR_TYPE_WARNING, + _("Plugin did not report any addresses, could not check address conversion functions\n")); + end (); +} + + +static void +end_badly_now () +{ + if (GNUNET_SCHEDULER_NO_TASK != timeout_wait) + { + GNUNET_SCHEDULER_cancel (timeout_wait); + timeout_wait = GNUNET_SCHEDULER_NO_TASK; + } + if (GNUNET_SCHEDULER_NO_TASK != timeout_endbadly) + { + GNUNET_SCHEDULER_cancel (timeout_endbadly); + timeout_endbadly = GNUNET_SCHEDULER_NO_TASK; + } + timeout_endbadly = GNUNET_SCHEDULER_add_now (&end_badly, NULL); +} + + +static struct GNUNET_TIME_Relative +env_receive (void *cls, + const struct GNUNET_PeerIdentity *peer, + const struct GNUNET_MessageHeader *message, + const struct GNUNET_ATS_Information *ats, + uint32_t ats_count, + struct Session * session, + const char *sender_address, + uint16_t sender_address_len) +{ + /* do nothing */ + return GNUNET_TIME_relative_get_zero_(); +} + + +static int got_reply; + + +/** + * Take the given address and append it to the set of results sent back to + * the client. + * + * @param cls the transmission context used ('struct GNUNET_SERVER_TransmitContext*') + * @param buf text to transmit + */ +static void +address_pretty_printer_cb (void *cls, const char *buf) +{ + if (NULL != buf) + { + got_reply = GNUNET_YES; + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + "Pretty address : `%s'\n", buf); + pretty_printers_running --; + } + else + { + if (GNUNET_NO == got_reply) + { + pretty_printers_running --; + GNUNET_break (0); + end_badly_now (); + } + } +} + + +static void +env_notify_address (void *cls, + int add_remove, + const void *addr, + size_t addrlen, + const char *plugin) +{ + struct AddressWrapper *w; + char *a2s; + void *s2a; + size_t s2a_len; + + if (GNUNET_YES == add_remove) + { + addresses_reported ++; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + _("Adding address of length %u\n"), addrlen); + + w = GNUNET_malloc (sizeof (struct AddressWrapper)); + w->addr = GNUNET_malloc (addrlen); + w->addrlen = addrlen; + memcpy (w->addr, addr, addrlen); + GNUNET_CONTAINER_DLL_insert(head, tail, w); + got_reply = GNUNET_NO; + pretty_printers_running ++; + api->address_pretty_printer (api->cls, plugin, addr, addrlen, + GNUNET_YES, GNUNET_TIME_UNIT_MINUTES, + &address_pretty_printer_cb, + w); + + a2s = strdup (api->address_to_string (api, w->addr, w->addrlen)); + if (NULL == a2s) + { + GNUNET_break (0); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Plugin cannot convert address to string!\n")); + end_badly_now(); + return; + } + w->addrstring = strdup (api->address_to_string (api, w->addr, w->addrlen)); + GNUNET_log (GNUNET_ERROR_TYPE_INFO, + _("Plugin added address `%s'\n"), a2s); + + if ((GNUNET_OK != api->string_to_address (api, a2s, strlen (a2s)+1, &s2a, &s2a_len)) || (NULL == s2a)) + { + GNUNET_break (0); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Plugin cannot convert string to address!\n")); + end_badly_now(); + return; + } + + if (s2a_len != w->addrlen) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Plugin creates different address length when converting address->string->address: %u != %u\n"), w->addrlen, s2a_len); + } + else + { + if (0 != memcmp (s2a, w->addr, s2a_len)) + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Plugin creates different address length when connecting back and forth!\n")); + } + GNUNET_free (s2a); + GNUNET_free (a2s); + if (GNUNET_OK != api->check_address (api->cls, w->addr, w->addrlen)) + { + GNUNET_break (0); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Plugin refuses added address!\n")); + end_badly_now(); + return; + } + if (GNUNET_SCHEDULER_NO_TASK != timeout_wait) + { + GNUNET_SCHEDULER_cancel (timeout_wait); + timeout_wait = GNUNET_SCHEDULER_NO_TASK; + } + + timeout_wait = GNUNET_SCHEDULER_add_delayed (WAIT, &wait_end, NULL); + + } + else if (GNUNET_NO == add_remove) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + _("Removing address of length %u\n"), addrlen); + + w = head; + while (NULL != w) + { + if ((addrlen == w->addrlen) && (0 == memcmp (w->addr, addr, addrlen))) + { + break; + } + w = w->next; + } + + if (w == NULL) + { + GNUNET_break (0); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Plugin removes address never added!\n")); + end_badly_now(); + return; + } + + GNUNET_CONTAINER_DLL_remove (head, tail, w); + GNUNET_free (w->addr); + GNUNET_free (w->addrstring); + GNUNET_free (w); + } + else + { + GNUNET_break (0); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Invalid operation: %u \n"), add_remove); + end_badly_now (); + return; + } +} + + +static struct GNUNET_ATS_Information +env_get_address_type (void *cls, + const struct sockaddr *addr, + size_t addrlen) +{ + struct GNUNET_ATS_Information ats; + ats.type = htonl (GNUNET_ATS_NETWORK_TYPE); + ats.value = htonl (GNUNET_ATS_NET_LOOPBACK); + return ats; +} + + +static const struct GNUNET_MessageHeader * +env_get_our_hello () +{ + return (const struct GNUNET_MessageHeader *) hello; +} + + +static void +env_session_end (void *cls, + const struct GNUNET_PeerIdentity *peer, + struct Session * session) +{ +} + + +static void +setup_plugin_environment () +{ + env.cfg = cfg; + env.cls = &env; + env.my_identity = &my_identity; + env.max_connections = max_connect_per_transport; + env.stats = stats; + + env.receive = &env_receive; + env.notify_address = &env_notify_address; + env.get_address_type = &env_get_address_type; + env.get_our_hello = &env_get_our_hello; + env.session_end = &env_session_end; +} + +static int +handle_helper_message (void *cls, void *client, + const struct GNUNET_MessageHeader *hdr) +{ + return GNUNET_OK; +} + + +/** + * Runs the test. + * + * @param cls closure + * @param c configuration to use + */ +static void +run (void *cls, char *const *args, const char *cfgfile, + const struct GNUNET_CONFIGURATION_Handle *c) +{ + char *const *argv = cls; + unsigned long long tneigh; + char *keyfile; + char *plugin; + char *sep; + + timeout_endbadly = GNUNET_SCHEDULER_add_delayed (TIMEOUT, end_badly, &ok); + + cfg = c; + /* parse configuration */ + if ( (GNUNET_OK != GNUNET_CONFIGURATION_get_value_number (c, + "TRANSPORT", + "NEIGHBOUR_LIMIT", + &tneigh)) || + (GNUNET_OK != GNUNET_CONFIGURATION_get_value_filename (c, + "GNUNETD", "HOSTKEY", + &keyfile))) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Transport service is lacking key configuration settings. Exiting.\n")); + return; + } + + if (NULL == (stats = GNUNET_STATISTICS_create ("transport", cfg))) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Could not create statistics. Exiting.\n")); + end_badly_now (); + return; + } + + if (GNUNET_OK != GNUNET_DISK_file_test (HOSTKEY_FILE)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Hostkey `%s' missing. Exiting.\n"), + HOSTKEY_FILE); + } + + if (GNUNET_OK != GNUNET_DISK_directory_create_for_file (keyfile)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Could not create a directory for hostkey `%s'. Exiting.\n"), + keyfile); + end_badly_now (); + return; + } + + if (GNUNET_OK != GNUNET_DISK_file_copy (HOSTKEY_FILE, keyfile)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Could not copy hostkey `%s' to destination `%s'. Exiting.\n"), + HOSTKEY_FILE, keyfile); + end_badly_now (); + return; + } + + + max_connect_per_transport = (uint32_t) tneigh; + my_private_key = GNUNET_CRYPTO_rsa_key_create_from_file (keyfile); + GNUNET_free (keyfile); + if (NULL == my_private_key) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Transport service could not access hostkey. Exiting.\n")); + end_badly_now (); + return; + } + GNUNET_CRYPTO_rsa_key_get_public (my_private_key, &my_public_key); + GNUNET_CRYPTO_hash (&my_public_key, sizeof (my_public_key), + &my_identity.hashPubKey); + + + hello = GNUNET_HELLO_create(&my_public_key, NULL, NULL); + + /* load plugins... */ + setup_plugin_environment (); + + GNUNET_assert (strlen (argv[0]) > strlen ("test_plugin_")); + plugin = strstr(argv[0],"test_plugin_"); + sep = strrchr(argv[0],'.'); + if (NULL == plugin) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("Not a valid test name\n")); + end_badly_now (); + return; + } + plugin += strlen ("test_plugin_"); + if (NULL != sep) + sep[0] = '\0'; + + /* Hack for WLAN: start a second helper */ + if (0 == strcmp (plugin, "wlan")) + { + char * helper_argv[3]; + helper_argv[0] = (char *) "gnunet-helper-transport-wlan-dummy"; + helper_argv[1] = (char *) "2"; + helper_argv[2] = NULL; + suid_helper = GNUNET_HELPER_start (GNUNET_NO, + "gnunet-helper-transport-wlan-dummy", + helper_argv, + &handle_helper_message, + NULL, + NULL); + } + + /* Loading plugin */ + GNUNET_log (GNUNET_ERROR_TYPE_INFO, _("Loading transport plugin %s\n"), plugin); + GNUNET_asprintf (&libname, "libgnunet_plugin_transport_%s", plugin); + api = GNUNET_PLUGIN_load (libname, &env); + if (api == NULL) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Failed to load transport plugin for %s\n"), plugin); + end_badly_now (); + return; + } + + timeout_wait = GNUNET_SCHEDULER_add_delayed (WAIT, &wait_end, NULL); + + /* Check if all functions are implemented */ + if (NULL == api->address_pretty_printer) + { + GNUNET_break (0); + end_badly_now (); + return; + } + if (NULL == api->address_to_string) + { + GNUNET_break (0); + end_badly_now (); + return; + } + GNUNET_assert (NULL != api->check_address); + if (NULL == api->check_address) + { + GNUNET_break (0); + end_badly_now (); + return; + } + GNUNET_assert (NULL != api->disconnect); + if (NULL == api->disconnect) + { + GNUNET_break (0); + end_badly_now (); + return; + } + GNUNET_assert (NULL != api->get_session); + if (NULL == api->get_session) + { + GNUNET_break (0); + end_badly_now (); + return; + } + if (NULL == api->address_pretty_printer) + { + GNUNET_break (0); + end_badly_now (); + return; + } + if (NULL == api->string_to_address) + { + GNUNET_break (0); + end_badly_now (); + return; + } + +} + + +/** + * The main function for the test + * + * @param argc number of arguments from the command line + * @param argv command line arguments + * @return 0 ok, 1 on error + */ +int +main (int argc, char *const *argv) +{ + static struct GNUNET_GETOPT_CommandLineOption options[] = { + GNUNET_GETOPT_OPTION_END + }; + int ret; + + GNUNET_DISK_directory_remove ("/tmp/test-gnunetd-plugin-transport"); + + char *const argv_prog[] = { + "test_plugin_transport", + "-c", + "test_plugin_transport_data.conf", + NULL + }; + GNUNET_log_setup ("test-plugin-transport", + "WARNING", + NULL); + ok = 1; /* set to fail */ + ret = (GNUNET_OK == GNUNET_PROGRAM_run (3, + argv_prog, + "test-plugin-transport", + "testcase", + options, + &run, + (void *) argv)) ? ok : 1; + GNUNET_DISK_directory_remove ("/tmp/test-gnunetd-plugin-transport"); + return ret; +} + +/* end of test_plugin_transport.c */ diff --git a/src/transport/test_plugin_transport_data.conf b/src/transport/test_plugin_transport_data.conf index adc7a59..189238c 100644 --- a/src/transport/test_plugin_transport_data.conf +++ b/src/transport/test_plugin_transport_data.conf @@ -1,25 +1,49 @@ @INLINE@ test_transport_defaults.conf [PATHS] SERVICEHOME = /tmp/test-gnunetd-plugin-transport/ -DEFAULTCONFIG = test_plugin_transport_data.conf [transport-tcp] -PORT = 2368 -TIMEOUT = 5 s +PORT = 2400 + +[transport-udp] +PORT = 2401 + +[transport-unix] + +[transport-wlan] +INTERFACE = mon0 +TESTMODE = 1 + +[transport-http_client] + +[transport-http_server] +PORT = 2402 + +[transport-https_client] + +[transport-https_server] +PORT = 2403 [arm] -PORT = 2366 +PORT = 2360 +UNIXPATH = /tmp/gnunet-service-arm.sock [statistics] -PORT = 2367 +PORT = 2361 +UNIXPATH = /tmp/gnunet-service-statistics.sock [resolver] -PORT = 2364 +PORT = 2362 +UNIXPATH = /tmp/gnunet-service-resolver.sock [peerinfo] -PORT = 2369 +PORT = 2363 +UNIXPATH = /tmp/gnunet-service-peerinfo.sock [transport] -PORT = 2365 - +PORT = 2364 +UNIXPATH = /tmp/gnunet-service-transport.sock +[nat] +RETURN_LOCAL_ADDRESSES = YES +DISABLEV6 = NO diff --git a/src/transport/test_quota_compliance.c b/src/transport/test_quota_compliance.c index 8f4db53..7f0247e 100644 --- a/src/transport/test_quota_compliance.c +++ b/src/transport/test_quota_compliance.c @@ -24,24 +24,11 @@ * This test case tests quota compliance both on transport level */ #include "platform.h" -#include "gnunet_common.h" -#include "gnunet_hello_lib.h" -#include "gnunet_getopt_lib.h" -#include "gnunet_os_lib.h" -#include "gnunet_program_lib.h" -#include "gnunet_scheduler_lib.h" -#include "gnunet_server_lib.h" #include "gnunet_transport_service.h" +#include "gnunet_ats_service.h" #include "gauger.h" -#include "transport.h" #include "transport-testing.h" -#define VERBOSE GNUNET_NO - -#define VERBOSE_ARM GNUNET_NO - -#define START_ARM GNUNET_YES - /** * Testcase timeout */ @@ -60,8 +47,6 @@ static char *test_plugin; static char *test_name; -static int ok; - static GNUNET_SCHEDULER_TaskIdentifier die_task; static GNUNET_SCHEDULER_TaskIdentifier measure_task; @@ -212,7 +197,7 @@ end_badly () if (p2 != NULL) GNUNET_TRANSPORT_TESTING_stop_peer (tth, p2); - ok = GNUNET_SYSERR; + test_failed = GNUNET_YES; } @@ -311,7 +296,7 @@ notify_ready (void *cls, size_t size, void *buf) if (GNUNET_SCHEDULER_NO_TASK != die_task) GNUNET_SCHEDULER_cancel (die_task); die_task = GNUNET_SCHEDULER_add_now (&end_badly, NULL); - ok = 42; + test_failed = 1; return 0; } @@ -466,11 +451,10 @@ start_cb (struct PeerContext *p, void *cls) receiver = p1; char *sender_c = GNUNET_strdup (GNUNET_i2s (&sender->id)); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Test tries to send from %u (%s) -> peer %u (%s)\n", sender->no, sender_c, receiver->no, GNUNET_i2s (&receiver->id)); - + GNUNET_free (sender_c); cc = GNUNET_TRANSPORT_TESTING_connect_peers (tth, p1, p2, &testing_connect_cb, NULL); @@ -480,16 +464,28 @@ static char * generate_config (char *cfg_file, unsigned long long quota_in, unsigned long long quota_out) { + char *networks[GNUNET_ATS_NetworkTypeCount] = GNUNET_ATS_NetworkTypeString; + char *in_name; + char *out_name; char *fname = NULL; struct GNUNET_CONFIGURATION_Handle *cfg = GNUNET_CONFIGURATION_create (); + int c; GNUNET_assert (GNUNET_OK == GNUNET_CONFIGURATION_load (cfg, cfg_file)); GNUNET_asprintf (&fname, "q_in_%llu_q_out_%llu_%s", quota_in, quota_out, cfg_file); + GNUNET_CONFIGURATION_set_value_string (cfg, "PATHS", "DEFAULTCONFIG", fname); - GNUNET_CONFIGURATION_set_value_number (cfg, "ats", "WAN_QUOTA_IN", quota_in); - GNUNET_CONFIGURATION_set_value_number (cfg, "ats", "WAN_QUOTA_OUT", - quota_out); + + for (c = 0; c < GNUNET_ATS_NetworkTypeCount; c++) + { + GNUNET_asprintf (&in_name, "%s_QUOTA_IN", networks[c]); + GNUNET_asprintf (&out_name, "%s_QUOTA_OUT", networks[c]); + GNUNET_CONFIGURATION_set_value_number (cfg, "ats", in_name, quota_in); + GNUNET_CONFIGURATION_set_value_number (cfg, "ats", out_name, quota_out); + GNUNET_free (in_name); + GNUNET_free (out_name); + } GNUNET_assert (GNUNET_OK == GNUNET_CONFIGURATION_write (cfg, fname)); GNUNET_CONFIGURATION_destroy (cfg); return fname; @@ -564,20 +560,15 @@ check () static char *argv[] = { "test_transport-quota-compliance", "-c", "test_quota_compliance_data.conf", -#if VERBOSE - "-L", "DEBUG", -#endif NULL }; static struct GNUNET_GETOPT_CommandLineOption options[] = { GNUNET_GETOPT_OPTION_END }; - ok = 1; GNUNET_PROGRAM_run ((sizeof (argv) / sizeof (char *)) - 1, argv, test_name, - "nohelp", options, &run, &ok); - - return ok; + "nohelp", options, &run, NULL); + return test_failed; } int @@ -586,11 +577,7 @@ main (int argc, char *argv[]) GNUNET_TRANSPORT_TESTING_get_test_name (argv[0], &test_name); GNUNET_log_setup (test_name, -#if VERBOSE - "DEBUG", -#else "WARNING", -#endif NULL); GNUNET_TRANSPORT_TESTING_get_test_source_name (__FILE__, &test_source); diff --git a/src/transport/test_quota_compliance_data.conf b/src/transport/test_quota_compliance_data.conf index 93f75dd..b0fb0e0 100644 --- a/src/transport/test_quota_compliance_data.conf +++ b/src/transport/test_quota_compliance_data.conf @@ -1,7 +1,6 @@ @INLINE@ test_transport_defaults.conf [PATHS] SERVICEHOME = /tmp/test-gnunetd-plugin-transport/ -DEFAULTCONFIG = test_quota_compliance_data.conf [transport-tcp] PORT = 2368 diff --git a/src/transport/test_quota_compliance_http_asymmetric_peer1.conf b/src/transport/test_quota_compliance_http_asymmetric_peer1.conf index f56b157..885bcba 100644 --- a/src/transport/test_quota_compliance_http_asymmetric_peer1.conf +++ b/src/transport/test_quota_compliance_http_asymmetric_peer1.conf @@ -1,10 +1,8 @@ @INLINE@ template_cfg_peer1.conf [PATHS] SERVICEHOME = /tmp/test_quota_compliance_peer1 -DEFAULTCONFIG = test_quota_compliance_http_peer1.conf -[transport-http] -PORT = 4010 +[transport-http_client] [arm] PORT = 4015 @@ -24,7 +22,7 @@ UNIXPATH = /tmp/test_quota_compliance_http_peerinfo_peer1.sock [transport] PORT = 4011 -PLUGINS = http +PLUGINS = http_client UNIXPATH = /tmp/test_quota_compliance_http_transport_peer1.sock diff --git a/src/transport/test_quota_compliance_http_asymmetric_peer2.conf b/src/transport/test_quota_compliance_http_asymmetric_peer2.conf index 20ef582..33f8be5 100644 --- a/src/transport/test_quota_compliance_http_asymmetric_peer2.conf +++ b/src/transport/test_quota_compliance_http_asymmetric_peer2.conf @@ -1,10 +1,12 @@ @INLINE@ template_cfg_peer2.conf [PATHS] SERVICEHOME = /tmp/test_quota_compliance_peer2 -DEFAULTCONFIG = test_quota_compliance_http_peer2.conf -[transport-http] +[transport-http_server] PORT = 3010 +USE_IPv6 = NO +BINDTO = 127.0.0.1 + [arm] PORT = 3015 @@ -24,7 +26,7 @@ UNIXPATH = /tmp/test_quota_compliance_http_peerinfo_peer2.sock [transport] PORT = 3011 -PLUGINS = http +PLUGINS = http_server UNIXPATH = /tmp/test_quota_compliance_http_transport_peer2.sock diff --git a/src/transport/test_quota_compliance_http_peer1.conf b/src/transport/test_quota_compliance_http_peer1.conf index f56b157..885bcba 100644 --- a/src/transport/test_quota_compliance_http_peer1.conf +++ b/src/transport/test_quota_compliance_http_peer1.conf @@ -1,10 +1,8 @@ @INLINE@ template_cfg_peer1.conf [PATHS] SERVICEHOME = /tmp/test_quota_compliance_peer1 -DEFAULTCONFIG = test_quota_compliance_http_peer1.conf -[transport-http] -PORT = 4010 +[transport-http_client] [arm] PORT = 4015 @@ -24,7 +22,7 @@ UNIXPATH = /tmp/test_quota_compliance_http_peerinfo_peer1.sock [transport] PORT = 4011 -PLUGINS = http +PLUGINS = http_client UNIXPATH = /tmp/test_quota_compliance_http_transport_peer1.sock diff --git a/src/transport/test_quota_compliance_http_peer2.conf b/src/transport/test_quota_compliance_http_peer2.conf index 20ef582..33f8be5 100644 --- a/src/transport/test_quota_compliance_http_peer2.conf +++ b/src/transport/test_quota_compliance_http_peer2.conf @@ -1,10 +1,12 @@ @INLINE@ template_cfg_peer2.conf [PATHS] SERVICEHOME = /tmp/test_quota_compliance_peer2 -DEFAULTCONFIG = test_quota_compliance_http_peer2.conf -[transport-http] +[transport-http_server] PORT = 3010 +USE_IPv6 = NO +BINDTO = 127.0.0.1 + [arm] PORT = 3015 @@ -24,7 +26,7 @@ UNIXPATH = /tmp/test_quota_compliance_http_peerinfo_peer2.sock [transport] PORT = 3011 -PLUGINS = http +PLUGINS = http_server UNIXPATH = /tmp/test_quota_compliance_http_transport_peer2.sock diff --git a/src/transport/test_quota_compliance_https_asymmetric_peer1.conf b/src/transport/test_quota_compliance_https_asymmetric_peer1.conf index ad4aab0..271bbe0 100644 --- a/src/transport/test_quota_compliance_https_asymmetric_peer1.conf +++ b/src/transport/test_quota_compliance_https_asymmetric_peer1.conf @@ -1,12 +1,8 @@ @INLINE@ template_cfg_peer1.conf [PATHS] SERVICEHOME = /tmp/test_quota_compliance_peer1/ -DEFAULTCONFIG = test_quota_compliance_https_peer1.conf -[transport-https] -PORT = 4001 -KEY_FILE = https_key_quota_p1.key -CERT_FILE = https_cert_quota_p1.crt +[transport-https_client] [arm] PORT = 4006 @@ -26,7 +22,7 @@ UNIXPATH = /tmp/test_quota_compliance_https_peerinfo_peer1.sock [transport] PORT = 4002 -PLUGINS = https +PLUGINS = https_client UNIXPATH = /tmp/test_quota_compliance_https_transport_peer1.sock diff --git a/src/transport/test_quota_compliance_https_asymmetric_peer2.conf b/src/transport/test_quota_compliance_https_asymmetric_peer2.conf index 94d7412..8e07ff3 100644 --- a/src/transport/test_quota_compliance_https_asymmetric_peer2.conf +++ b/src/transport/test_quota_compliance_https_asymmetric_peer2.conf @@ -1,9 +1,8 @@ @INLINE@ template_cfg_peer2.conf [PATHS] SERVICEHOME = /tmp/test_quota_compliance_peer2 -DEFAULTCONFIG = test_quota_compliance_https_peer2.conf -[transport-https] +[transport-https_server] PORT = 3001 KEY_FILE = https_key_quota_p2.key CERT_FILE = https_cert_qutoa_p2.crt @@ -26,7 +25,7 @@ UNIXPATH = /tmp/test_quota_compliance_https_peerinfo_peer2.sock [transport] PORT = 3002 -PLUGINS = https +PLUGINS = https_server UNIXPATH = /tmp/https_transport_peer2.sock diff --git a/src/transport/test_quota_compliance_https_peer1.conf b/src/transport/test_quota_compliance_https_peer1.conf index ad4aab0..271bbe0 100644 --- a/src/transport/test_quota_compliance_https_peer1.conf +++ b/src/transport/test_quota_compliance_https_peer1.conf @@ -1,12 +1,8 @@ @INLINE@ template_cfg_peer1.conf [PATHS] SERVICEHOME = /tmp/test_quota_compliance_peer1/ -DEFAULTCONFIG = test_quota_compliance_https_peer1.conf -[transport-https] -PORT = 4001 -KEY_FILE = https_key_quota_p1.key -CERT_FILE = https_cert_quota_p1.crt +[transport-https_client] [arm] PORT = 4006 @@ -26,7 +22,7 @@ UNIXPATH = /tmp/test_quota_compliance_https_peerinfo_peer1.sock [transport] PORT = 4002 -PLUGINS = https +PLUGINS = https_client UNIXPATH = /tmp/test_quota_compliance_https_transport_peer1.sock diff --git a/src/transport/test_quota_compliance_https_peer2.conf b/src/transport/test_quota_compliance_https_peer2.conf index 94d7412..8e07ff3 100644 --- a/src/transport/test_quota_compliance_https_peer2.conf +++ b/src/transport/test_quota_compliance_https_peer2.conf @@ -1,9 +1,8 @@ @INLINE@ template_cfg_peer2.conf [PATHS] SERVICEHOME = /tmp/test_quota_compliance_peer2 -DEFAULTCONFIG = test_quota_compliance_https_peer2.conf -[transport-https] +[transport-https_server] PORT = 3001 KEY_FILE = https_key_quota_p2.key CERT_FILE = https_cert_qutoa_p2.crt @@ -26,7 +25,7 @@ UNIXPATH = /tmp/test_quota_compliance_https_peerinfo_peer2.sock [transport] PORT = 3002 -PLUGINS = https +PLUGINS = https_server UNIXPATH = /tmp/https_transport_peer2.sock diff --git a/src/transport/test_quota_compliance_tcp_asymmetric_peer1.conf b/src/transport/test_quota_compliance_tcp_asymmetric_peer1.conf index 8a1dad5..b7eb287 100644 --- a/src/transport/test_quota_compliance_tcp_asymmetric_peer1.conf +++ b/src/transport/test_quota_compliance_tcp_asymmetric_peer1.conf @@ -1,7 +1,6 @@ @INLINE@ template_cfg_peer1.conf [PATHS] SERVICEHOME = /tmp/test-transport/quota-tcp-p1/ -DEFAULTCONFIG = test_quota_compliance_tcp_asymmetric_peer1.conf [transport-tcp] PORT = 4094 diff --git a/src/transport/test_quota_compliance_tcp_asymmetric_peer2.conf b/src/transport/test_quota_compliance_tcp_asymmetric_peer2.conf index bbfa8ec..cc949df 100644 --- a/src/transport/test_quota_compliance_tcp_asymmetric_peer2.conf +++ b/src/transport/test_quota_compliance_tcp_asymmetric_peer2.conf @@ -1,7 +1,6 @@ @INLINE@ template_cfg_peer2.conf [PATHS] SERVICEHOME = /tmp/test-transport/quota-tcp-p2/ -DEFAULTCONFIG = test_quota_compliance_tcp_asymmetric_peer2.conf [transport-tcp] PORT = 12015 diff --git a/src/transport/test_quota_compliance_tcp_peer1.conf b/src/transport/test_quota_compliance_tcp_peer1.conf index 29e56fe..b7eb287 100644 --- a/src/transport/test_quota_compliance_tcp_peer1.conf +++ b/src/transport/test_quota_compliance_tcp_peer1.conf @@ -1,7 +1,6 @@ @INLINE@ template_cfg_peer1.conf [PATHS] SERVICEHOME = /tmp/test-transport/quota-tcp-p1/ -DEFAULTCONFIG = test_quota_compliance_tcp_peer1.conf [transport-tcp] PORT = 4094 diff --git a/src/transport/test_quota_compliance_tcp_peer2.conf b/src/transport/test_quota_compliance_tcp_peer2.conf index 5da60d0..67f171e 100644 --- a/src/transport/test_quota_compliance_tcp_peer2.conf +++ b/src/transport/test_quota_compliance_tcp_peer2.conf @@ -1,7 +1,6 @@ @INLINE@ template_cfg_peer2.conf [PATHS] SERVICEHOME = /tmp/test-transport/api-tcp-p2/ -DEFAULTCONFIG = test_quota_compliance_tcp_peer2.conf [transport-tcp] PORT = 12015 diff --git a/src/transport/test_quota_compliance_udp_peer1.conf b/src/transport/test_quota_compliance_udp_peer1.conf index fceee7b..0d49d4e 100644 --- a/src/transport/test_quota_compliance_udp_peer1.conf +++ b/src/transport/test_quota_compliance_udp_peer1.conf @@ -1,7 +1,6 @@ @INLINE@ template_cfg_peer1.conf [PATHS] SERVICEHOME = /tmp/test_quota_compliance_peer1/ -DEFAULTCONFIG = test_quota_compliance_udp_peer1.conf [transport-udp] PORT = 4368 diff --git a/src/transport/test_quota_compliance_udp_peer2.conf b/src/transport/test_quota_compliance_udp_peer2.conf index 4b58c93..3c57fe5 100644 --- a/src/transport/test_quota_compliance_udp_peer2.conf +++ b/src/transport/test_quota_compliance_udp_peer2.conf @@ -1,7 +1,6 @@ @INLINE@ template_cfg_peer2.conf [PATHS] SERVICEHOME = /tmp/test_quota_compliance_peer2 -DEFAULTCONFIG = test_quota_compliance_udp_peer2.conf [transport-udp] PORT = 3368 diff --git a/src/transport/test_quota_compliance_unix_asymmetric_peer1.conf b/src/transport/test_quota_compliance_unix_asymmetric_peer1.conf index 649cf1c..1e4afce 100644 --- a/src/transport/test_quota_compliance_unix_asymmetric_peer1.conf +++ b/src/transport/test_quota_compliance_unix_asymmetric_peer1.conf @@ -1,7 +1,6 @@ @INLINE@ template_cfg_peer1.conf [PATHS] SERVICEHOME = /tmp/test_quota_compliance_peer1/ -DEFAULTCONFIG = test_quota_compliance_unix_asymmetric_peer1.conf [arm] PORT = 4087 diff --git a/src/transport/test_quota_compliance_unix_asymmetric_peer2.conf b/src/transport/test_quota_compliance_unix_asymmetric_peer2.conf index a2d1bdd..f732e98 100644 --- a/src/transport/test_quota_compliance_unix_asymmetric_peer2.conf +++ b/src/transport/test_quota_compliance_unix_asymmetric_peer2.conf @@ -1,7 +1,6 @@ @INLINE@ template_cfg_peer2.conf [PATHS] SERVICEHOME = /tmp/test_quota_compliance_peer2 -DEFAULTCONFIG = test_quota_compliance_unix_asymmetric_peer2.conf [arm] PORT = 3087 diff --git a/src/transport/test_quota_compliance_unix_peer1.conf b/src/transport/test_quota_compliance_unix_peer1.conf index 60e656b..bde7846 100644 --- a/src/transport/test_quota_compliance_unix_peer1.conf +++ b/src/transport/test_quota_compliance_unix_peer1.conf @@ -1,7 +1,6 @@ @INLINE@ template_cfg_peer1.conf [PATHS] SERVICEHOME = /tmp/test_quota_compliance_peer1/ -DEFAULTCONFIG = test_quota_compliance_unix_peer1.conf [transport-unix] PORT = 12120 diff --git a/src/transport/test_quota_compliance_unix_peer2.conf b/src/transport/test_quota_compliance_unix_peer2.conf index b4f0b64..0b803cc 100644 --- a/src/transport/test_quota_compliance_unix_peer2.conf +++ b/src/transport/test_quota_compliance_unix_peer2.conf @@ -1,7 +1,6 @@ @INLINE@ template_cfg_peer2.conf [PATHS] SERVICEHOME = /tmp/test_quota_compliance_peer2 -DEFAULTCONFIG = test_quota_compliance_unix_peer2.conf [transport-unix] PORT = 12136 diff --git a/src/transport/test_quota_compliance_wlan_asymmetric_peer1.conf b/src/transport/test_quota_compliance_wlan_asymmetric_peer1.conf new file mode 100644 index 0000000..e81a3f9 --- /dev/null +++ b/src/transport/test_quota_compliance_wlan_asymmetric_peer1.conf @@ -0,0 +1,29 @@ +@INLINE@ template_cfg_peer1.conf +[PATHS] +SERVICEHOME = /tmp/test-transport/api-wlan-p1/ + +[transport-wlan] +TESTMODE = 1 + +[arm] +PORT = 12164 +UNIXPATH = /tmp/gnunet-p1-service-arm.sock + +[statistics] +PORT = 12163 +UNIXPATH = /tmp/gnunet-p1-service-statistics.sock + +[resolver] +PORT = 12162 +UNIXPATH = /tmp/gnunet-p1-service-resolver.sock + +[peerinfo] +PORT = 12161 +UNIXPATH = /tmp/gnunet-p1-service-peerinfo.sock + +[transport] +PORT = 12160 +PLUGINS = wlan +UNIXPATH = /tmp/gnunet-p1-service-transport.sock + + diff --git a/src/transport/test_quota_compliance_wlan_asymmetric_peer2.conf b/src/transport/test_quota_compliance_wlan_asymmetric_peer2.conf new file mode 100644 index 0000000..bd53876 --- /dev/null +++ b/src/transport/test_quota_compliance_wlan_asymmetric_peer2.conf @@ -0,0 +1,29 @@ +@INLINE@ template_cfg_peer2.conf +[PATHS] +SERVICEHOME = /tmp/test-transport/api-wlan-p2/ + +[transport-wlan] +INTERFACE = mon1 +TESTMODE = 2 + +[arm] +PORT = 12174 +UNIXPATH = /tmp/gnunet-p2-service-arm.sock + +[statistics] +PORT = 12173 +UNIXPATH = /tmp/gnunet-p2-service-statistics.sock + +[resolver] +PORT = 12172 +UNIXPATH = /tmp/gnunet-p2-service-resolver.sock + +[peerinfo] +PORT = 12171 +UNIXPATH = /tmp/gnunet-p2-service-peerinfo.sock + +[transport] +PORT = 12170 +PLUGINS = wlan +UNIXPATH = /tmp/gnunet-p2-service-transport.sock + diff --git a/src/transport/test_quota_compliance_wlan_peer1.conf b/src/transport/test_quota_compliance_wlan_peer1.conf new file mode 100644 index 0000000..e81a3f9 --- /dev/null +++ b/src/transport/test_quota_compliance_wlan_peer1.conf @@ -0,0 +1,29 @@ +@INLINE@ template_cfg_peer1.conf +[PATHS] +SERVICEHOME = /tmp/test-transport/api-wlan-p1/ + +[transport-wlan] +TESTMODE = 1 + +[arm] +PORT = 12164 +UNIXPATH = /tmp/gnunet-p1-service-arm.sock + +[statistics] +PORT = 12163 +UNIXPATH = /tmp/gnunet-p1-service-statistics.sock + +[resolver] +PORT = 12162 +UNIXPATH = /tmp/gnunet-p1-service-resolver.sock + +[peerinfo] +PORT = 12161 +UNIXPATH = /tmp/gnunet-p1-service-peerinfo.sock + +[transport] +PORT = 12160 +PLUGINS = wlan +UNIXPATH = /tmp/gnunet-p1-service-transport.sock + + diff --git a/src/transport/test_quota_compliance_wlan_peer2.conf b/src/transport/test_quota_compliance_wlan_peer2.conf new file mode 100644 index 0000000..bd53876 --- /dev/null +++ b/src/transport/test_quota_compliance_wlan_peer2.conf @@ -0,0 +1,29 @@ +@INLINE@ template_cfg_peer2.conf +[PATHS] +SERVICEHOME = /tmp/test-transport/api-wlan-p2/ + +[transport-wlan] +INTERFACE = mon1 +TESTMODE = 2 + +[arm] +PORT = 12174 +UNIXPATH = /tmp/gnunet-p2-service-arm.sock + +[statistics] +PORT = 12173 +UNIXPATH = /tmp/gnunet-p2-service-statistics.sock + +[resolver] +PORT = 12172 +UNIXPATH = /tmp/gnunet-p2-service-resolver.sock + +[peerinfo] +PORT = 12171 +UNIXPATH = /tmp/gnunet-p2-service-peerinfo.sock + +[transport] +PORT = 12170 +PLUGINS = wlan +UNIXPATH = /tmp/gnunet-p2-service-transport.sock + diff --git a/src/transport/test_transport_api.c b/src/transport/test_transport_api.c index f944fac..1316efe 100644 --- a/src/transport/test_transport_api.c +++ b/src/transport/test_transport_api.c @@ -27,19 +27,9 @@ * C code apparently. */ #include "platform.h" -#include "gnunet_common.h" -#include "gnunet_hello_lib.h" -#include "gnunet_getopt_lib.h" -#include "gnunet_os_lib.h" -#include "gnunet_program_lib.h" -#include "gnunet_scheduler_lib.h" #include "gnunet_transport_service.h" -#include "transport.h" #include "transport-testing.h" - -#define START_ARM GNUNET_YES - /** * How long until we give up on transmitting the message? */ @@ -383,9 +373,6 @@ check () GNUNET_GETOPT_OPTION_END }; -#if WRITECONFIG - setTransportOptions ("test_transport_api_data.conf"); -#endif send_task = GNUNET_SCHEDULER_NO_TASK; ok = 1; diff --git a/src/transport/test_transport_api_bidirectional_connect.c b/src/transport/test_transport_api_bidirectional_connect.c index 2c4eeab..3923216 100644 --- a/src/transport/test_transport_api_bidirectional_connect.c +++ b/src/transport/test_transport_api_bidirectional_connect.c @@ -25,14 +25,7 @@ * (almost) the same time */ #include "platform.h" -#include "gnunet_common.h" -#include "gnunet_hello_lib.h" -#include "gnunet_getopt_lib.h" -#include "gnunet_os_lib.h" -#include "gnunet_program_lib.h" -#include "gnunet_scheduler_lib.h" #include "gnunet_transport_service.h" -#include "transport.h" #include "transport-testing.h" diff --git a/src/transport/test_transport_api_bidirectional_connect_peer1.conf b/src/transport/test_transport_api_bidirectional_connect_peer1.conf index 49fc662..ba6afbe 100644 --- a/src/transport/test_transport_api_bidirectional_connect_peer1.conf +++ b/src/transport/test_transport_api_bidirectional_connect_peer1.conf @@ -1,7 +1,6 @@ @INLINE@ template_cfg_peer1.conf [PATHS] SERVICEHOME = /tmp/test-transport/api-tcp-p1/ -DEFAULTCONFIG = test_transport_api_bidirectional_connect_peer1.conf [arm] PORT = 12000 @@ -23,7 +22,6 @@ UNIXPATH = /tmp/gnunet-p1-service-peerinfo.sock [transport] PORT = 12004 UNIXPATH = /tmp/gnunet-p1-service-transport.sock -#DEBUG = YES [transport-tcp] PORT = 12005 @@ -43,4 +41,4 @@ TIMEOUT = 5 s [transport-https] PORT = 12009 -TIMEOUT = 5 s \ No newline at end of file +TIMEOUT = 5 s diff --git a/src/transport/test_transport_api_bidirectional_connect_peer2.conf b/src/transport/test_transport_api_bidirectional_connect_peer2.conf index 2d64351..4aeee7c 100644 --- a/src/transport/test_transport_api_bidirectional_connect_peer2.conf +++ b/src/transport/test_transport_api_bidirectional_connect_peer2.conf @@ -1,7 +1,6 @@ @INLINE@ template_cfg_peer2.conf [PATHS] SERVICEHOME = /tmp/test-transport/api-tcp-p2/ -DEFAULTCONFIG = test_transport_api_bidirectional_connect_peer2.conf [arm] PORT = 12010 @@ -42,4 +41,4 @@ TIMEOUT = 5 s [transport-https] PORT = 12019 -TIMEOUT = 5 s \ No newline at end of file +TIMEOUT = 5 s diff --git a/src/transport/test_transport_api_blacklisting.c b/src/transport/test_transport_api_blacklisting.c index 909ea57..55adb5b 100644 --- a/src/transport/test_transport_api_blacklisting.c +++ b/src/transport/test_transport_api_blacklisting.c @@ -25,22 +25,9 @@ * */ #include "platform.h" -#include "gnunet_common.h" -#include "gnunet_hello_lib.h" -#include "gnunet_getopt_lib.h" -#include "gnunet_os_lib.h" -#include "gnunet_program_lib.h" -#include "gnunet_scheduler_lib.h" #include "gnunet_transport_service.h" -#include "transport.h" #include "transport-testing.h" -#define VERBOSE GNUNET_NO -#define VERBOSE_ARM GNUNET_NO - -#define START_ARM GNUNET_YES - - struct PeerContext *p1; struct PeerContext *p2; @@ -435,19 +422,12 @@ check () static char *const argv[] = { "test-transport-api-blacklisting", "-c", "test_transport_api_data.conf", -#if VERBOSE - "-L", "DEBUG", -#endif NULL }; static struct GNUNET_GETOPT_CommandLineOption options[] = { GNUNET_GETOPT_OPTION_END }; -#if WRITECONFIG - setTransportOptions ("test_transport_api_data.conf"); -#endif - ok = 1; GNUNET_PROGRAM_run ((sizeof (argv) / sizeof (char *)) - 1, argv, "test-transport-api-blacklisting", "nohelp", options, &run, &ok); @@ -461,11 +441,7 @@ main (int argc, char *argv[]) int ret; GNUNET_log_setup ("test-transport-api-blacklisting", -#if VERBOSE - "DEBUG", -#else "WARNING", -#endif NULL); tth = GNUNET_TRANSPORT_TESTING_init (); diff --git a/src/transport/test_transport_api_data.conf b/src/transport/test_transport_api_data.conf index 3955246..164a38f 100644 --- a/src/transport/test_transport_api_data.conf +++ b/src/transport/test_transport_api_data.conf @@ -1,6 +1,5 @@ @INLINE@ test_transport_defaults.conf [PATHS] -DEFAULTCONFIG = test_transport_api_data.conf [transport-tcp] PORT = 2094 diff --git a/src/transport/test_transport_api_disconnect.c b/src/transport/test_transport_api_disconnect.c index 973c4cf..7a26c7e 100644 --- a/src/transport/test_transport_api_disconnect.c +++ b/src/transport/test_transport_api_disconnect.c @@ -24,21 +24,9 @@ * This test case tests disconnect notifications in peer shutdown */ #include "platform.h" -#include "gnunet_common.h" -#include "gnunet_hello_lib.h" -#include "gnunet_getopt_lib.h" -#include "gnunet_os_lib.h" -#include "gnunet_program_lib.h" -#include "gnunet_scheduler_lib.h" #include "gnunet_transport_service.h" -#include "transport.h" #include "transport-testing.h" -#define VERBOSE GNUNET_NO -#define VERBOSE_ARM GNUNET_NO - -#define START_ARM GNUNET_YES - /** * How long until we give up on transmitting the message? */ @@ -374,18 +362,12 @@ check () static char *const argv[] = { "test-transport-api", "-c", "test_transport_api_data.conf", -#if VERBOSE - "-L", "DEBUG", -#endif NULL }; static struct GNUNET_GETOPT_CommandLineOption options[] = { GNUNET_GETOPT_OPTION_END }; -#if WRITECONFIG - setTransportOptions ("test_transport_api_data.conf"); -#endif send_task = GNUNET_SCHEDULER_NO_TASK; ok = 1; @@ -403,11 +385,7 @@ main (int argc, char *argv[]) GNUNET_TRANSPORT_TESTING_get_test_name (argv[0], &test_name); GNUNET_log_setup (test_name, -#if VERBOSE - "DEBUG", -#else "WARNING", -#endif NULL); GNUNET_TRANSPORT_TESTING_get_test_source_name (__FILE__, &test_source); diff --git a/src/transport/test_transport_api_disconnect_tcp_peer1.conf b/src/transport/test_transport_api_disconnect_tcp_peer1.conf index ebb4fd4..5f1d693 100644 --- a/src/transport/test_transport_api_disconnect_tcp_peer1.conf +++ b/src/transport/test_transport_api_disconnect_tcp_peer1.conf @@ -1,7 +1,6 @@ @INLINE@ template_cfg_peer1.conf [PATHS] SERVICEHOME = /tmp/test-transport/api-tcp-p1/ -DEFAULTCONFIG = test_transport_api_tcp_peer1.conf [transport-tcp] PORT = 12000 @@ -28,5 +27,4 @@ UNIXPATH = /tmp/gnunet-p1-service-peerinfo.sock PORT = 12001 PLUGINS = tcp UNIXPATH = /tmp/gnunet-p1-service-transport.sock -#DEBUG = YES diff --git a/src/transport/test_transport_api_disconnect_tcp_peer2.conf b/src/transport/test_transport_api_disconnect_tcp_peer2.conf index fe6d19b..67f171e 100644 --- a/src/transport/test_transport_api_disconnect_tcp_peer2.conf +++ b/src/transport/test_transport_api_disconnect_tcp_peer2.conf @@ -1,7 +1,6 @@ @INLINE@ template_cfg_peer2.conf [PATHS] SERVICEHOME = /tmp/test-transport/api-tcp-p2/ -DEFAULTCONFIG = test_transport_api_tcp_peer2.conf [transport-tcp] PORT = 12015 diff --git a/src/transport/test_transport_api_http_nat_peer1.conf b/src/transport/test_transport_api_http_nat_peer1.conf deleted file mode 100644 index 447508c..0000000 --- a/src/transport/test_transport_api_http_nat_peer1.conf +++ /dev/null @@ -1,38 +0,0 @@ -@INLINE@ template_cfg_peer1.conf -[PATHS] -SERVICEHOME = /tmp/test-transport/api-http-p1/ -DEFAULTCONFIG = test_transport_api_http_nat_peer1.conf - -[nat] -BEHIND_NAT = YES -ENABLE_NAT_SERVER = YES - -[transport-http] -PORT = 0 - -[arm] -PORT = 12085 -DEFAULTSERVICES = transport -UNIXPATH = /tmp/gnunet-p1-service-arm.sock - -[statistics] -PORT = 12084 -UNIXPATH = /tmp/gnunet-p1-service-statistics.sock - -[resolver] -PORT = 12083 -UNIXPATH = /tmp/gnunet-p1-service-resolver.sock - -[peerinfo] -PORT = 12082 -UNIXPATH = /tmp/gnunet-p1-service-peerinfo.sock - -[transport] -#DEBUG = YES -PORT = 12081 -PLUGINS = http -#BINARY = .libs/gnunet-service-transport -UNIXPATH = /tmp/gnunet-p1-service-transport.sock -#PREFIX = valgrind --leak-check=full -#PREFIX = xterm -geometry 100x85 -T peer1 -e gdb --args - diff --git a/src/transport/test_transport_api_http_nat_peer2.conf b/src/transport/test_transport_api_http_nat_peer2.conf deleted file mode 100644 index 2f56eab..0000000 --- a/src/transport/test_transport_api_http_nat_peer2.conf +++ /dev/null @@ -1,31 +0,0 @@ -@INLINE@ template_cfg_peer2.conf -[PATHS] -SERVICEHOME = /tmp/test-transport/api-http-p2/ -DEFAULTCONFIG = test_transport_api_http_nat_peer2.conf - -[transport-http] -PORT = 12090 - -[arm] -PORT = 12095 -DEFAULTSERVICES = transport -UNIXPATH = /tmp/gnunet-p2-service-arm.sock - -[statistics] -PORT = 12094 -UNIXPATH = /tmp/gnunet-p2-service-statistics.sock - -[resolver] -PORT = 12093 -UNIXPATH = /tmp/gnunet-p2-service-resolver.sock - -[peerinfo] -PORT = 12092 -UNIXPATH = /tmp/gnunet-p2-service-peerinfo.sock - -[transport] -#DEBUG = YES -PORT = 12091 -PLUGINS = http -UNIXPATH = /tmp/gnunet-p2-service-transport.sock -#PREFIX = valgrind --leak-check=full diff --git a/src/transport/test_transport_api_http_peer1.conf b/src/transport/test_transport_api_http_peer1.conf index 26c2969..3c1b41d 100644 --- a/src/transport/test_transport_api_http_peer1.conf +++ b/src/transport/test_transport_api_http_peer1.conf @@ -1,10 +1,8 @@ @INLINE@ template_cfg_peer1.conf [PATHS] SERVICEHOME = /tmp/test-transport/api-http-p1/ -DEFAULTCONFIG = test_transport_api_http_peer1.conf -[transport-http] -PORT = 12080 +[transport-http_client] [arm] PORT = 12085 @@ -24,9 +22,8 @@ PORT = 12082 UNIXPATH = /tmp/gnunet-p1-service-peerinfo.sock [transport] -#DEBUG = YES PORT = 12081 -PLUGINS = http +PLUGINS = http_client #BINARY = .libs/gnunet-service-transport UNIXPATH = /tmp/gnunet-p1-service-transport.sock #PREFIX = valgrind --leak-check=full diff --git a/src/transport/test_transport_api_http_peer2.conf b/src/transport/test_transport_api_http_peer2.conf index fa7aa3b..f348bf4 100644 --- a/src/transport/test_transport_api_http_peer2.conf +++ b/src/transport/test_transport_api_http_peer2.conf @@ -1,10 +1,11 @@ @INLINE@ template_cfg_peer2.conf [PATHS] SERVICEHOME = /tmp/test-transport/api-http-p2/ -DEFAULTCONFIG = test_transport_api_http_peer2.conf -[transport-http] +[transport-http_server] PORT = 12090 +USE_IPv6 = YES +#BINDTO = 127.0.0.1 [arm] PORT = 12095 @@ -24,8 +25,7 @@ PORT = 12092 UNIXPATH = /tmp/gnunet-p2-service-peerinfo.sock [transport] -#DEBUG = YES PORT = 12091 -PLUGINS = http +PLUGINS = http_server UNIXPATH = /tmp/gnunet-p2-service-transport.sock #PREFIX = valgrind --leak-check=full diff --git a/src/transport/test_transport_api_http_reverse_peer1.conf b/src/transport/test_transport_api_http_reverse_peer1.conf new file mode 100644 index 0000000..93d8bd3 --- /dev/null +++ b/src/transport/test_transport_api_http_reverse_peer1.conf @@ -0,0 +1,39 @@ +INLINE@ template_cfg_peer1.conf +[PATHS] +SERVICEHOME = /tmp/test-transport/api-http-p1/ + + +[transport-http_client] + +[arm] +PORT = 12095 +DEFAULTSERVICES = transport +UNIXPATH = /tmp/gnunet-p1-service-arm.sock + +[statistics] +PORT = 12094 +UNIXPATH = /tmp/gnunet-p1-service-statistics.sock + +[resolver] +PORT = 12093 +UNIXPATH = /tmp/gnunet-p1-service-resolver.sock + +[peerinfo] +PORT = 12092 +UNIXPATH = /tmp/gnunet-p1-service-peerinfo.sock + +[transport] +PORT = 12091 +PLUGINS = http_client +#BINARY = .libs/gnunet-service-transport +UNIXPATH = /tmp/gnunet-p1-service-transport.sock +PREFIX = valgrind --leak-check=full +#PREFIX = xterm -geometry 100x85 -T peer1 -e gdb --args + + +[ats] +WAN_QUOTA_IN = unlimited +WAN_QUOTA_OUT = unlimited +PORT = 12006 +UNIXPATH = /tmp/gnunet-http_reserver_p1-service-ats.sock + diff --git a/src/transport/test_transport_api_http_reverse_peer2.conf b/src/transport/test_transport_api_http_reverse_peer2.conf new file mode 100644 index 0000000..b73921f --- /dev/null +++ b/src/transport/test_transport_api_http_reverse_peer2.conf @@ -0,0 +1,40 @@ +INLINE@ template_cfg_peer2.conf +[PATHS] +SERVICEHOME = /tmp/test-transport/api-http-p2/ + + +[transport-http_client] + +[transport-http_server] +PORT = 8080 +EXTERNAL_HOSTNAME = fulcrum.net.in.tum.de/gnunet +EXTERNAL_HOSTNAME_ONLY = YES +#USE_IPV4 = YES +#USE_IPV6 = YES +#BINDTO = 127.0.0.1 +#BINDTO6 = ::1 + +[arm] +PORT = 12085 +DEFAULTSERVICES = transport +UNIXPATH = /tmp/gnunet-p2-service-arm.sock + +[statistics] +PORT = 12084 +UNIXPATH = /tmp/gnunet-p2-service-statistics.sock + +[resolver] +PORT = 12083 +UNIXPATH = /tmp/gnunet-p2-service-resolver.sock + +[peerinfo] +PORT = 12082 +UNIXPATH = /tmp/gnunet-p2-service-peerinfo.sock + +[transport] +PORT = 12081 +PLUGINS = http_server +UNIXPATH = /tmp/gnunet-p2-service-transport.sock +PREFIX = valgrind --leak-check=full +#PREFIX = xterm -geometry 100x85 -T peer1 -e gdb --args + diff --git a/src/transport/test_transport_api_https_nat_peer1.conf b/src/transport/test_transport_api_https_nat_peer1.conf deleted file mode 100644 index e97b473..0000000 --- a/src/transport/test_transport_api_https_nat_peer1.conf +++ /dev/null @@ -1,36 +0,0 @@ -@INLINE@ template_cfg_peer1.conf -[PATHS] -SERVICEHOME = /tmp/test-transport/api-https-p1/ -DEFAULTCONFIG = test_transport_api_https_nat_peer1.conf - -[nat] -BEHIND_NAT = YES -ENABLE_NAT_SERVER = YES - -[transport-https] -PORT = 0 -KEY_FILE = $SERVICEHOME/https_key_p1.key -CERT_FILE = $SERVICEHOME/https_cert_p1.crt - -[arm] -PORT = 12105 - -[statistics] -PORT = 12104 -UNIXPATH = /tmp/gnunet-p1-service-statistics.sock - -[resolver] -PORT = 12103 -UNIXPATH = /tmp/gnunet-p1-service-resolver.sock - -[peerinfo] -PORT = 12102 -UNIXPATH = /tmp/gnunet-p1-service-peerinfo.sock - -[transport] -PORT = 12101 -PLUGINS = https -UNIXPATH = /tmp/gnunet-p1-service-transport.sock -DEBUG = NO - - diff --git a/src/transport/test_transport_api_https_nat_peer2.conf b/src/transport/test_transport_api_https_nat_peer2.conf deleted file mode 100644 index a23f3a5..0000000 --- a/src/transport/test_transport_api_https_nat_peer2.conf +++ /dev/null @@ -1,33 +0,0 @@ -@INLINE@ template_cfg_peer2.conf -[PATHS] -SERVICEHOME = /tmp/test-transport/api-https-p2/ -DEFAULTCONFIG = test_transport_api_https_nat_peer2.conf - -[transport-https] -PORT = 12110 -KEY_FILE = $SERVICEHOME/https_key_p2.key -CERT_FILE = $SERVICEHOME/https_cert_p2.crt - -[arm] -PORT = 12115 -UNIXPATH = /tmp/gnunet-p2-service-arm.sock - -[statistics] -PORT = 12114 -UNIXPATH = /tmp/gnunet-p2-service-statistics.sock - -[resolver] -PORT = 12113 -UNIXPATH = /tmp/gnunet-p2-service-resolver.sock - -[peerinfo] -PORT = 12112 -UNIXPATH = /tmp/gnunet-p2-service-peerinfo.sock - -[transport] -PORT = 12111 -PLUGINS = https -UNIXPATH = /tmp/gnunet-p2-service-transport.sock -DEBUG = NO - - diff --git a/src/transport/test_transport_api_https_peer1.conf b/src/transport/test_transport_api_https_peer1.conf index 8a93ca1..48302a6 100644 --- a/src/transport/test_transport_api_https_peer1.conf +++ b/src/transport/test_transport_api_https_peer1.conf @@ -1,9 +1,8 @@ @INLINE@ template_cfg_peer1.conf [PATHS] SERVICEHOME = /tmp/test-transport/api-https-p1/ -DEFAULTCONFIG = test_transport_api_https_peer1.conf -[transport-https] +[transport-https_client] PORT = 12100 KEY_FILE = $SERVICEHOME/https_key_p1.key CERT_FILE = $SERVICEHOME/https_cert_p1.crt @@ -25,8 +24,7 @@ UNIXPATH = /tmp/gnunet-p1-service-peerinfo.sock [transport] PORT = 12101 -PLUGINS = https +PLUGINS = https_client UNIXPATH = /tmp/gnunet-p1-service-transport.sock -DEBUG = NO diff --git a/src/transport/test_transport_api_https_peer2.conf b/src/transport/test_transport_api_https_peer2.conf index 0710f41..566997f 100644 --- a/src/transport/test_transport_api_https_peer2.conf +++ b/src/transport/test_transport_api_https_peer2.conf @@ -1,10 +1,11 @@ @INLINE@ template_cfg_peer2.conf [PATHS] SERVICEHOME = /tmp/test-transport/api-https-p2/ -DEFAULTCONFIG = test_transport_api_https_peer2.conf -[transport-https] +[transport-https_server] PORT = 12110 +USE_IPv6 = YES +#BINDTO = 127.0.0.1 KEY_FILE = $SERVICEHOME/https_key_p2.key CERT_FILE = $SERVICEHOME/https_cert_p2.crt @@ -26,8 +27,7 @@ UNIXPATH = /tmp/gnunet-p2-service-peerinfo.sock [transport] PORT = 12111 -PLUGINS = https +PLUGINS = https_server UNIXPATH = /tmp/gnunet-p2-service-transport.sock -DEBUG = NO diff --git a/src/transport/test_transport_api_limited_sockets.c b/src/transport/test_transport_api_limited_sockets.c index e6ad84a..69a5100 100644 --- a/src/transport/test_transport_api_limited_sockets.c +++ b/src/transport/test_transport_api_limited_sockets.c @@ -27,22 +27,9 @@ * C code apparently. */ #include "platform.h" -#include "gnunet_common.h" -#include "gnunet_hello_lib.h" -#include "gnunet_getopt_lib.h" -#include "gnunet_os_lib.h" -#include "gnunet_program_lib.h" -#include "gnunet_scheduler_lib.h" #include "gnunet_transport_service.h" -#include "transport.h" #include "transport-testing.h" -#define VERBOSE GNUNET_NO - -#define VERBOSE_ARM GNUNET_NO - -#define START_ARM GNUNET_YES - /** * How long until we give up on transmitting the message? */ @@ -57,6 +44,9 @@ #define MAX_FILES 50 + +#if HAVE_SETRLIMIT + static char *test_source; static char *test_plugin; @@ -107,6 +97,8 @@ end () GNUNET_TRANSPORT_TESTING_stop_peer (tth, p1); GNUNET_TRANSPORT_TESTING_stop_peer (tth, p2); + GNUNET_TRANSPORT_TESTING_done (tth); + } static void @@ -131,6 +123,9 @@ end_badly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) if (p2 != NULL) GNUNET_TRANSPORT_TESTING_stop_peer (tth, p2); + if (NULL != th) + GNUNET_TRANSPORT_TESTING_done (tth); + ok = GNUNET_SYSERR; } @@ -241,7 +236,7 @@ start_cb (struct PeerContext *p, void *cls) if (started != 2) return; - cc = GNUNET_TRANSPORT_TESTING_connect_peers (tth, p1, p2, &testing_connect_cb, + cc = GNUNET_TRANSPORT_TESTING_connect_peers (tth, p2, p1, &testing_connect_cb, NULL); } @@ -279,9 +274,6 @@ check () static char *const argv[] = { "test-transport-api", "-c", "test_transport_api_data.conf", -#if VERBOSE - "-L", "DEBUG", -#endif NULL }; static struct GNUNET_GETOPT_CommandLineOption options[] = { @@ -300,39 +292,24 @@ check () return ok; } + int main (int argc, char *argv[]) { + struct rlimit r_file_old; + struct rlimit r_file_new; + int res; int ret = 0; test_plugin = NULL; - GNUNET_TRANSPORT_TESTING_get_test_source_name (__FILE__, &test_source); GNUNET_TRANSPORT_TESTING_get_test_plugin_name (argv[0], test_source, &test_plugin); GNUNET_TRANSPORT_TESTING_get_test_name (argv[0], &test_name); - GNUNET_log_setup (test_name, -#if VERBOSE - "DEBUG", -#else "WARNING", -#endif NULL); -#if !HAVE_SETRLIMIT - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Cannot run test on this system\n"); - - GNUNET_free (test_source); - GNUNET_free (test_plugin); - GNUNET_free (test_name); - - return 0; -#else - struct rlimit r_file_old; - struct rlimit r_file_new; - int res; - res = getrlimit (RLIMIT_NOFILE, &r_file_old); GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Maximum number of open files was: %u/%u\n", r_file_old.rlim_cur, @@ -355,27 +332,27 @@ main (int argc, char *argv[]) GNUNET_TRANSPORT_TESTING_get_config_name (argv[0], &cfg_file_p1, 1); GNUNET_TRANSPORT_TESTING_get_config_name (argv[0], &cfg_file_p2, 2); ret = check (); -#endif - GNUNET_free (cfg_file_p1); GNUNET_free (cfg_file_p2); - GNUNET_free (test_source); GNUNET_free (test_plugin); GNUNET_free (test_name); - -#if HAVE_SETRLIMIT - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Restoring previous value maximum number of open files\n"); - res = setrlimit (RLIMIT_NOFILE, &r_file_old); - if (res != 0) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Restoring limit failed!\n"); - return 0; - } -#endif return ret; } +#else +/* cannot setrlimit */ + + +int +main (int argc, char *argv[]) +{ + fprintf (stderr, "Cannot run test on this system\n"); + return 0; +} + +#endif + /* end of test_transport_api_limited_sockets.c */ + diff --git a/src/transport/test_transport_api_limited_sockets_tcp_peer1.conf b/src/transport/test_transport_api_limited_sockets_tcp_peer1.conf index d29b946..dceeccb 100644 --- a/src/transport/test_transport_api_limited_sockets_tcp_peer1.conf +++ b/src/transport/test_transport_api_limited_sockets_tcp_peer1.conf @@ -1,7 +1,6 @@ @INLINE@ template_cfg_peer1.conf [PATHS] SERVICEHOME = /tmp/test-transport/api-tcp-p1/ -DEFAULTCONFIG = test_transport_api_tcp_peer1.conf [transport-tcp] PORT = 12000 diff --git a/src/transport/test_transport_api_limited_sockets_tcp_peer2.conf b/src/transport/test_transport_api_limited_sockets_tcp_peer2.conf index 3c0e496..caaddde 100644 --- a/src/transport/test_transport_api_limited_sockets_tcp_peer2.conf +++ b/src/transport/test_transport_api_limited_sockets_tcp_peer2.conf @@ -1,7 +1,6 @@ @INLINE@ template_cfg_peer2.conf [PATHS] SERVICEHOME = /tmp/test-transport/api-tcp-p2/ -DEFAULTCONFIG = test_transport_api_tcp_peer2.conf [transport-tcp] PORT = 0 diff --git a/src/transport/test_transport_api_manipulation_recv_tcp.c b/src/transport/test_transport_api_manipulation_recv_tcp.c new file mode 100644 index 0000000..4621507 --- /dev/null +++ b/src/transport/test_transport_api_manipulation_recv_tcp.c @@ -0,0 +1,493 @@ +/* + This file is part of GNUnet. + (C) 2009, 2010 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ +/** + * @file transport/test_transport_api_manipulation_recv_tcp.c + * @brief base test case for transport traffic manipulation implementation + * + * This test case will setup 2 peers and connect them, the first message + * will be sent without manipulation, then a receive delay of 1 second will + * be configured and 2 more message will be sent. Time will be measured + * + * In addition the distance on receiver side will be manipulated to be 10 + */ +#include "platform.h" +#include "gnunet_transport_service.h" +#include "transport-testing.h" + +/** + * How long until we give up on transmitting the message? + */ +#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 120) + +/** + * How long until we give up on transmitting the message? + */ +#define TIMEOUT_TRANSMIT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 30) + +#define TEST_MESSAGE_SIZE 2600 + +#define TEST_MESSAGE_TYPE 12345 + +static char *test_source; + +static char *test_plugin; + +static char *test_name; + +static int ok; + +static int s_started; + +static int s_connected; + +static int s_sending; + +static GNUNET_SCHEDULER_TaskIdentifier die_task; + +static GNUNET_SCHEDULER_TaskIdentifier send_task; + +static struct PeerContext *p1; + +static struct PeerContext *p2; + +static GNUNET_TRANSPORT_TESTING_ConnectRequest cc; + +static struct GNUNET_TRANSPORT_TransmitHandle *th; + +static struct GNUNET_TRANSPORT_TESTING_handle *tth; + +static char *cfg_file_p1; + +static char *cfg_file_p2; + +static int messages_recv; + +static struct GNUNET_TIME_Absolute start_normal; +static struct GNUNET_TIME_Relative dur_normal; + +static struct GNUNET_TIME_Absolute start_delayed; +static struct GNUNET_TIME_Relative dur_delayed; + +static void +end () +{ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stopping peers\n"); + + if (send_task != GNUNET_SCHEDULER_NO_TASK) + GNUNET_SCHEDULER_cancel (send_task); + + if (die_task != GNUNET_SCHEDULER_NO_TASK) + GNUNET_SCHEDULER_cancel (die_task); + + if (th != NULL) + GNUNET_TRANSPORT_notify_transmit_ready_cancel (th); + th = NULL; + + GNUNET_TRANSPORT_TESTING_stop_peer (tth, p1); + GNUNET_TRANSPORT_TESTING_stop_peer (tth, p2); +} + +static void +end_badly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + die_task = GNUNET_SCHEDULER_NO_TASK; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Fail! Stopping peers\n"); + + + if (send_task != GNUNET_SCHEDULER_NO_TASK) + GNUNET_SCHEDULER_cancel (send_task); + + if (cc != NULL) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("Fail! Could not connect peers\n")); + GNUNET_TRANSPORT_TESTING_connect_peers_cancel (tth, cc); + cc = NULL; + } + + if (th != NULL) + GNUNET_TRANSPORT_notify_transmit_ready_cancel (th); + else + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("Peer were not ready to send data\n")); + + if (s_started == GNUNET_NO) + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("Peers were not started \n")); + else + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("Peers were started \n")); + + if (s_connected == GNUNET_NO) + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("Peer were not connected\n")); + else + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("Peer were connected\n")); + + if (s_sending == GNUNET_NO) + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("Peer were not ready to send data\n")); + else + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("Peer were ready to send data\n")); + + th = NULL; + + if (p1 != NULL) + GNUNET_TRANSPORT_TESTING_stop_peer (tth, p1); + else + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("Peer 1 was not started\n")); + if (p2 != NULL) + GNUNET_TRANSPORT_TESTING_stop_peer (tth, p2); + else + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("Peer 2 was not started\n")); + + ok = GNUNET_SYSERR; +} + + +static void +sendtask (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc); + +static void +notify_receive (void *cls, const struct GNUNET_PeerIdentity *peer, + const struct GNUNET_MessageHeader *message, + const struct GNUNET_ATS_Information *ats, uint32_t ats_count) +{ + struct PeerContext *p = cls; + struct PeerContext *t = NULL; + int c; + + if (0 == memcmp (peer, &p1->id, sizeof (struct GNUNET_PeerIdentity))) + t = p1; + if (0 == memcmp (peer, &p2->id, sizeof (struct GNUNET_PeerIdentity))) + t = p2; + GNUNET_assert (t != NULL); + + char *ps = GNUNET_strdup (GNUNET_i2s (&p->id)); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Peer %u (`%4s') received message of type %d and size %u size from peer %u (`%4s')!\n", + p->no, ps, ntohs (message->type), ntohs (message->size), t->no, + GNUNET_i2s (&t->id)); + GNUNET_free (ps); + + if ((TEST_MESSAGE_TYPE == ntohs (message->type)) && + (TEST_MESSAGE_SIZE == ntohs (message->size))) + { + ok = 0; + + } + else + { + GNUNET_break (0); + ok = 1; + end (); + return; + } + + if (messages_recv <= 1) + { + /* Received non-delayed message */ + dur_normal = GNUNET_TIME_absolute_get_duration(start_normal); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Received non-delayed message %u after %llu\n", + messages_recv, + (long long unsigned int) dur_normal.rel_value); + + struct GNUNET_ATS_Information ats[2]; + ats[0].type = htonl (GNUNET_ATS_QUALITY_NET_DELAY); + ats[0].value = htonl (1000); + ats[1].type = htonl (GNUNET_ATS_QUALITY_NET_DISTANCE); + ats[1].value = htonl (10); + + GNUNET_TRANSPORT_set_traffic_metric (p1->th, &p2->id, TM_RECEIVE, ats, 2); + send_task = GNUNET_SCHEDULER_add_now (&sendtask, NULL); + } + if (2 == messages_recv) + { + /* Received manipulated message */ + dur_delayed = GNUNET_TIME_absolute_get_duration(start_delayed); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Received delayed message %u after %llu\n", + messages_recv, + (long long unsigned int) dur_delayed.rel_value); + if (dur_delayed.rel_value < 1000) + { + GNUNET_break (0); + ok += 1; + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Delayed message was not delayed correctly: took only %llu\n", + (long long unsigned int) dur_delayed.rel_value); + } + for (c = 0; c < ats_count; c++) + { + if (ntohl (ats[c].type) == GNUNET_ATS_QUALITY_NET_DISTANCE) + { + if (ntohl (ats[c].value) == 10) + ok += 0; + else + { + GNUNET_break (0); + ok += 1; + } + } + } + /* shutdown */ + end (); + } + + messages_recv ++; +} + + +static size_t +notify_ready (void *cls, size_t size, void *buf) +{ + struct PeerContext *p = cls; + struct GNUNET_MessageHeader *hdr; + + th = NULL; + + if (buf == NULL) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Timeout occurred while waiting for transmit_ready\n"); + if (GNUNET_SCHEDULER_NO_TASK != die_task) + GNUNET_SCHEDULER_cancel (die_task); + die_task = GNUNET_SCHEDULER_add_now (&end_badly, NULL); + ok = 42; + return 0; + } + + GNUNET_assert (size >= TEST_MESSAGE_SIZE); + if (buf != NULL) + { + memset (buf, '\0', TEST_MESSAGE_SIZE); + hdr = buf; + hdr->size = htons (TEST_MESSAGE_SIZE); + hdr->type = htons (TEST_MESSAGE_TYPE); + } + + char *ps = GNUNET_strdup (GNUNET_i2s (&p2->id)); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Peer %u (`%4s') sending message with type %u and size %u bytes to peer %u (`%4s')\n", + p2->no, ps, ntohs (hdr->type), ntohs (hdr->size), p->no, + GNUNET_i2s (&p->id)); + GNUNET_free (ps); + + return TEST_MESSAGE_SIZE; +} + + +static void +sendtask (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + send_task = GNUNET_SCHEDULER_NO_TASK; + + if ((tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN) != 0) + return; + char *receiver_s = GNUNET_strdup (GNUNET_i2s (&p1->id)); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Sending message from peer %u (`%4s') -> peer %u (`%s') !\n", + p2->no, GNUNET_i2s (&p2->id), p1->no, receiver_s); + GNUNET_free (receiver_s); + + + if (0 == messages_recv) + { + start_normal = GNUNET_TIME_absolute_get(); + } + if (1 == messages_recv) + { + start_delayed = GNUNET_TIME_absolute_get(); + } + + s_sending = GNUNET_YES; + th = GNUNET_TRANSPORT_notify_transmit_ready (p2->th, &p1->id, TEST_MESSAGE_SIZE, 0, + TIMEOUT_TRANSMIT, ¬ify_ready, + p1); +} + + +static void +notify_connect (void *cls, const struct GNUNET_PeerIdentity *peer, + const struct GNUNET_ATS_Information *ats, uint32_t ats_count) +{ + static int c; + + c++; + struct PeerContext *p = cls; + struct PeerContext *t = NULL; + + if (0 == memcmp (peer, &p1->id, sizeof (struct GNUNET_PeerIdentity))) + t = p1; + if (0 == memcmp (peer, &p2->id, sizeof (struct GNUNET_PeerIdentity))) + t = p2; + GNUNET_assert (t != NULL); + + char *ps = GNUNET_strdup (GNUNET_i2s (&p->id)); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Peer %u (`%4s'): peer %u (`%s') connected to me!\n", p->no, ps, + t->no, GNUNET_i2s (peer)); + GNUNET_free (ps); +} + + +static void +notify_disconnect (void *cls, const struct GNUNET_PeerIdentity *peer) +{ + struct PeerContext *p = cls; + char *ps = GNUNET_strdup (GNUNET_i2s (&p->id)); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Peer %u (`%4s'): peer (`%s') disconnected from me!\n", p->no, ps, + GNUNET_i2s (peer)); + + GNUNET_free (ps); + + if (th != NULL) + GNUNET_TRANSPORT_notify_transmit_ready_cancel (th); + th = NULL; +} + + +static void +testing_connect_cb (struct PeerContext *p1, struct PeerContext *p2, void *cls) +{ + cc = NULL; + char *p1_c = GNUNET_strdup (GNUNET_i2s (&p1->id)); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Peers connected: %u (%s) <-> %u (%s)\n", + p1->no, p1_c, p2->no, GNUNET_i2s (&p2->id)); + GNUNET_free (p1_c); + + s_connected = GNUNET_YES; + send_task = GNUNET_SCHEDULER_add_now (&sendtask, NULL); +} + + +static void +start_cb (struct PeerContext *p, void *cls) +{ + static int started; + started++; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Peer %u (`%s') started\n", p->no, + GNUNET_i2s (&p->id)); + + if (started != 2) + return; + else + s_started = GNUNET_YES; + char *sender_c = GNUNET_strdup (GNUNET_i2s (&p1->id)); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Test tries to connect peer %u (`%s') -> peer %u (`%s')\n", + p1->no, sender_c, p2->no, GNUNET_i2s (&p2->id)); + GNUNET_free (sender_c); + + cc = GNUNET_TRANSPORT_TESTING_connect_peers (tth, p1, p2, &testing_connect_cb, + NULL); + +} + + +static void +run (void *cls, char *const *args, const char *cfgfile, + const struct GNUNET_CONFIGURATION_Handle *cfg) +{ + die_task = GNUNET_SCHEDULER_add_delayed (TIMEOUT, &end_badly, NULL); + + s_started = GNUNET_NO; + s_connected = GNUNET_NO; + s_sending = GNUNET_NO; + + p1 = GNUNET_TRANSPORT_TESTING_start_peer (tth, cfg_file_p1, 1, + ¬ify_receive, ¬ify_connect, + ¬ify_disconnect, &start_cb, + NULL); + + p2 = GNUNET_TRANSPORT_TESTING_start_peer (tth, cfg_file_p2, 2, + ¬ify_receive, ¬ify_connect, + ¬ify_disconnect, &start_cb, + NULL); + + if ((p1 == NULL) || (p2 == NULL)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Fail! Could not start peers!\n"); + if (die_task != GNUNET_SCHEDULER_NO_TASK) + GNUNET_SCHEDULER_cancel (die_task); + die_task = GNUNET_SCHEDULER_add_now (&end_badly, NULL); + return; + } +} + + +static int +check () +{ + static char *const argv[] = { "test-transport-api-manipulation", + "-c", + "test_transport_api_data.conf", + NULL + }; + static struct GNUNET_GETOPT_CommandLineOption options[] = { + GNUNET_GETOPT_OPTION_END + }; + + send_task = GNUNET_SCHEDULER_NO_TASK; + + ok = 1; + GNUNET_PROGRAM_run ((sizeof (argv) / sizeof (char *)) - 1, argv, test_name, + "nohelp", options, &run, &ok); + + return ok; +} + +int +main (int argc, char *argv[]) +{ + int ret; + + GNUNET_TRANSPORT_TESTING_get_test_name (argv[0], &test_name); + GNUNET_TRANSPORT_TESTING_get_test_source_name (__FILE__, &test_source); + GNUNET_TRANSPORT_TESTING_get_test_plugin_name (argv[0], test_source, + &test_plugin); + + GNUNET_log_setup (test_name, + "WARNING", + NULL); + tth = GNUNET_TRANSPORT_TESTING_init (); + + GNUNET_TRANSPORT_TESTING_get_config_name (argv[0], &cfg_file_p1, 1); + GNUNET_TRANSPORT_TESTING_get_config_name (argv[0], &cfg_file_p2, 2); + + ret = check (); + + GNUNET_free (cfg_file_p1); + GNUNET_free (cfg_file_p2); + + GNUNET_free (test_source); + GNUNET_free (test_plugin); + GNUNET_free (test_name); + + GNUNET_TRANSPORT_TESTING_done (tth); + + return ret; +} + +/* end of test_transport_api_manipulation_recv_tcp.c */ diff --git a/src/transport/test_transport_api_manipulation_recv_tcp_peer1.conf b/src/transport/test_transport_api_manipulation_recv_tcp_peer1.conf new file mode 100644 index 0000000..db66282 --- /dev/null +++ b/src/transport/test_transport_api_manipulation_recv_tcp_peer1.conf @@ -0,0 +1,30 @@ +@INLINE@ template_cfg_peer1.conf +[PATHS] +SERVICEHOME = /tmp/test-transport/api-tcp-p1/ + +[transport-tcp] +PORT = 12000 +TIMEOUT = 5 s + +[arm] +PORT = 12005 +DEFAULTSERVICES = transport +UNIXPATH = /tmp/gnunet-p1-service-arm.sock + +[statistics] +PORT = 12004 +UNIXPATH = /tmp/gnunet-p1-service-statistics.sock + +[resolver] +PORT = 12003 +UNIXPATH = /tmp/gnunet-p1-service-resolver.sock + +[peerinfo] +PORT = 12002 +UNIXPATH = /tmp/gnunet-p1-service-peerinfo.sock + +[transport] +PORT = 12001 +UNIXPATH = /tmp/gnunet-p1-service-transport.sock +PLUGINS = tcp + diff --git a/src/transport/test_transport_api_manipulation_recv_tcp_peer2.conf b/src/transport/test_transport_api_manipulation_recv_tcp_peer2.conf new file mode 100644 index 0000000..67f171e --- /dev/null +++ b/src/transport/test_transport_api_manipulation_recv_tcp_peer2.conf @@ -0,0 +1,30 @@ +@INLINE@ template_cfg_peer2.conf +[PATHS] +SERVICEHOME = /tmp/test-transport/api-tcp-p2/ + +[transport-tcp] +PORT = 12015 +TIMEOUT = 5 s + +[arm] +PORT = 12014 +DEFAULTSERVICES = transport +UNIXPATH = /tmp/gnunet-p2-service-arm.sock + +[statistics] +PORT = 12013 +UNIXPATH = /tmp/gnunet-p2-service-statistics.sock + +[resolver] +PORT = 12012 +UNIXPATH = /tmp/gnunet-p2-service-resolver.sock + +[peerinfo] +PORT = 12011 +UNIXPATH = /tmp/gnunet-p2-service-peerinfo.sock + +[transport] +PORT = 12010 +PLUGINS = tcp +UNIXPATH = /tmp/gnunet-p2-service-transport.sock + diff --git a/src/transport/test_transport_api_manipulation_send_tcp.c b/src/transport/test_transport_api_manipulation_send_tcp.c new file mode 100644 index 0000000..2e40e9f --- /dev/null +++ b/src/transport/test_transport_api_manipulation_send_tcp.c @@ -0,0 +1,500 @@ +/* + This file is part of GNUnet. + (C) 2009, 2010 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ +/** + * @file transport/test_transport_api_manipulation_send_tcp.c + * @brief base test case for transport traffic manipulation implementation + * + * This test case will setup 2 peers and connect them, the first message + * will be sent without manipulation, then a send delay of 1 second will + * be configured and 1 more message will be sent. Time will be measured. + * + * In addition the distance on receiver side will be manipulated to be 10 + */ +#include "platform.h" +#include "gnunet_transport_service.h" +#include "transport-testing.h" + +/** + * How long until we give up on transmitting the message? + */ +#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 120) + +/** + * How long until we give up on transmitting the message? + */ +#define TIMEOUT_TRANSMIT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 30) + +#define TEST_MESSAGE_SIZE 2600 + +#define TEST_MESSAGE_TYPE 12345 + +static char *test_source; + +static char *test_plugin; + +static char *test_name; + +static int ok; + +static int s_started; + +static int s_connected; + +static int s_sending; + +static GNUNET_SCHEDULER_TaskIdentifier die_task; + +static GNUNET_SCHEDULER_TaskIdentifier send_task; + +static struct PeerContext *p1; + +static struct PeerContext *p2; + +static GNUNET_TRANSPORT_TESTING_ConnectRequest cc; + +static struct GNUNET_TRANSPORT_TransmitHandle *th; + +static struct GNUNET_TRANSPORT_TESTING_handle *tth; + +static char *cfg_file_p1; + +static char *cfg_file_p2; + +static int messages_recv; + +static struct GNUNET_TIME_Absolute start_normal; +static struct GNUNET_TIME_Relative dur_normal; + +static struct GNUNET_TIME_Absolute start_delayed; +static struct GNUNET_TIME_Relative dur_delayed; + +static void +end () +{ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stopping peers\n"); + + if (send_task != GNUNET_SCHEDULER_NO_TASK) + GNUNET_SCHEDULER_cancel (send_task); + + if (die_task != GNUNET_SCHEDULER_NO_TASK) + GNUNET_SCHEDULER_cancel (die_task); + + if (th != NULL) + GNUNET_TRANSPORT_notify_transmit_ready_cancel (th); + th = NULL; + + GNUNET_TRANSPORT_TESTING_stop_peer (tth, p1); + GNUNET_TRANSPORT_TESTING_stop_peer (tth, p2); +} + +static void +end_badly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + die_task = GNUNET_SCHEDULER_NO_TASK; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Fail! Stopping peers\n"); + + + if (send_task != GNUNET_SCHEDULER_NO_TASK) + GNUNET_SCHEDULER_cancel (send_task); + + if (cc != NULL) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("Fail! Could not connect peers\n")); + GNUNET_TRANSPORT_TESTING_connect_peers_cancel (tth, cc); + cc = NULL; + } + + if (th != NULL) + GNUNET_TRANSPORT_notify_transmit_ready_cancel (th); + else + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("Peer were not ready to send data\n")); + + if (s_started == GNUNET_NO) + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("Peers were not started \n")); + else + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("Peers were started \n")); + + if (s_connected == GNUNET_NO) + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("Peer were not connected\n")); + else + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("Peer were connected\n")); + + if (s_sending == GNUNET_NO) + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("Peer were not ready to send data\n")); + else + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("Peer were ready to send data\n")); + + th = NULL; + + if (p1 != NULL) + GNUNET_TRANSPORT_TESTING_stop_peer (tth, p1); + else + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("Peer 1 was not started\n")); + if (p2 != NULL) + GNUNET_TRANSPORT_TESTING_stop_peer (tth, p2); + else + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("Peer 2 was not started\n")); + + ok = GNUNET_SYSERR; +} + + +static void +sendtask (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc); + +static void +notify_receive (void *cls, const struct GNUNET_PeerIdentity *peer, + const struct GNUNET_MessageHeader *message, + const struct GNUNET_ATS_Information *ats, uint32_t ats_count) +{ + struct PeerContext *p = cls; + struct PeerContext *t = NULL; + int c; + + if (0 == memcmp (peer, &p1->id, sizeof (struct GNUNET_PeerIdentity))) + t = p1; + if (0 == memcmp (peer, &p2->id, sizeof (struct GNUNET_PeerIdentity))) + t = p2; + GNUNET_assert (t != NULL); + + char *ps = GNUNET_strdup (GNUNET_i2s (&p->id)); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Peer %u (`%4s') received message of type %d and size %u size from peer %u (`%4s')!\n", + p->no, ps, ntohs (message->type), ntohs (message->size), t->no, + GNUNET_i2s (&t->id)); + GNUNET_free (ps); + + if ((TEST_MESSAGE_TYPE == ntohs (message->type)) && + (TEST_MESSAGE_SIZE == ntohs (message->size))) + { + ok = 0; + + } + else + { + GNUNET_break (0); + ok = 1; + end (); + return; + } + + if (0 == messages_recv) + { + /* Received non-delayed message */ + dur_normal = GNUNET_TIME_absolute_get_duration(start_normal); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Received non-delayed message %u after %llu\n", + messages_recv, + (long long unsigned int) dur_normal.rel_value); + send_task = GNUNET_SCHEDULER_add_now (&sendtask, NULL); + } + if (1 == messages_recv) + { + /* Received manipulated message */ + dur_delayed = GNUNET_TIME_absolute_get_duration(start_delayed); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Received delayed message %u after %llu\n", + messages_recv, + (long long unsigned int) dur_delayed.rel_value); + if (dur_delayed.rel_value < 1000) + { + GNUNET_break (0); + ok += 1; + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Delayed message was not delayed correctly: took only %llu\n", + (long long unsigned int) dur_delayed.rel_value); + } + for (c = 0; c < ats_count; c++) + { + if (ntohl (ats[c].type) == GNUNET_ATS_QUALITY_NET_DISTANCE) + { + if (ntohl (ats[c].value) == 10) + ok += 0; + else + { + GNUNET_break (0); + ok += 1; + } + } + } + /* shutdown */ + end (); + } + messages_recv ++; +} + + +static size_t +notify_ready (void *cls, size_t size, void *buf) +{ + struct PeerContext *p = cls; + struct GNUNET_MessageHeader *hdr; + + th = NULL; + + if (buf == NULL) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Timeout occurred while waiting for transmit_ready\n"); + if (GNUNET_SCHEDULER_NO_TASK != die_task) + GNUNET_SCHEDULER_cancel (die_task); + die_task = GNUNET_SCHEDULER_add_now (&end_badly, NULL); + ok = 42; + return 0; + } + + GNUNET_assert (size >= TEST_MESSAGE_SIZE); + if (buf != NULL) + { + memset (buf, '\0', TEST_MESSAGE_SIZE); + hdr = buf; + hdr->size = htons (TEST_MESSAGE_SIZE); + hdr->type = htons (TEST_MESSAGE_TYPE); + } + + char *ps = GNUNET_strdup (GNUNET_i2s (&p2->id)); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Peer %u (`%4s') sending message with type %u and size %u bytes to peer %u (`%4s')\n", + p2->no, ps, ntohs (hdr->type), ntohs (hdr->size), p->no, + GNUNET_i2s (&p->id)); + GNUNET_free (ps); + + return TEST_MESSAGE_SIZE; +} + + +static void +sendtask (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct GNUNET_ATS_Information ats[1]; + send_task = GNUNET_SCHEDULER_NO_TASK; + + if ((tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN) != 0) + return; + char *receiver_s = GNUNET_strdup (GNUNET_i2s (&p1->id)); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Sending message from peer %u (`%4s') -> peer %u (`%s') !\n", + p2->no, GNUNET_i2s (&p2->id), p1->no, receiver_s); + GNUNET_free (receiver_s); + + + if (0 == messages_recv) + { + start_normal = GNUNET_TIME_absolute_get(); + } + if (1 == messages_recv) + { + ats[0].type = htonl (GNUNET_ATS_QUALITY_NET_DELAY); + ats[0].value = htonl (1000); + GNUNET_TRANSPORT_set_traffic_metric (p2->th, &p1->id, TM_SEND, ats, 1); + ats[0].type = htonl (GNUNET_ATS_QUALITY_NET_DISTANCE); + ats[0].value = htonl (10); + GNUNET_TRANSPORT_set_traffic_metric (p1->th, &p2->id, TM_BOTH, ats, 1); + + start_delayed = GNUNET_TIME_absolute_get(); + } + + s_sending = GNUNET_YES; + th = GNUNET_TRANSPORT_notify_transmit_ready (p2->th, &p1->id, TEST_MESSAGE_SIZE, 0, + TIMEOUT_TRANSMIT, ¬ify_ready, + p1); +} + + +static void +notify_connect (void *cls, const struct GNUNET_PeerIdentity *peer, + const struct GNUNET_ATS_Information *ats, uint32_t ats_count) +{ + static int c; + + c++; + struct PeerContext *p = cls; + struct PeerContext *t = NULL; + + if (0 == memcmp (peer, &p1->id, sizeof (struct GNUNET_PeerIdentity))) + t = p1; + if (0 == memcmp (peer, &p2->id, sizeof (struct GNUNET_PeerIdentity))) + t = p2; + GNUNET_assert (t != NULL); + + char *ps = GNUNET_strdup (GNUNET_i2s (&p->id)); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Peer %u (`%4s'): peer %u (`%s') connected to me!\n", p->no, ps, + t->no, GNUNET_i2s (peer)); + GNUNET_free (ps); +} + + +static void +notify_disconnect (void *cls, const struct GNUNET_PeerIdentity *peer) +{ + struct PeerContext *p = cls; + char *ps = GNUNET_strdup (GNUNET_i2s (&p->id)); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Peer %u (`%4s'): peer (`%s') disconnected from me!\n", p->no, ps, + GNUNET_i2s (peer)); + + GNUNET_free (ps); + + if (th != NULL) + GNUNET_TRANSPORT_notify_transmit_ready_cancel (th); + th = NULL; +} + + +static void +testing_connect_cb (struct PeerContext *p1, struct PeerContext *p2, void *cls) +{ + cc = NULL; + char *p1_c = GNUNET_strdup (GNUNET_i2s (&p1->id)); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Peers connected: %u (%s) <-> %u (%s)\n", + p1->no, p1_c, p2->no, GNUNET_i2s (&p2->id)); + GNUNET_free (p1_c); + + s_connected = GNUNET_YES; + send_task = GNUNET_SCHEDULER_add_now (&sendtask, NULL); +} + + +static void +start_cb (struct PeerContext *p, void *cls) +{ + static int started; + started++; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Peer %u (`%s') started\n", p->no, + GNUNET_i2s (&p->id)); + + if (started != 2) + return; + else + s_started = GNUNET_YES; + char *sender_c = GNUNET_strdup (GNUNET_i2s (&p1->id)); + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Test tries to connect peer %u (`%s') -> peer %u (`%s')\n", + p1->no, sender_c, p2->no, GNUNET_i2s (&p2->id)); + GNUNET_free (sender_c); + /* + struct GNUNET_ATS_Information ats[2]; + ats[0].type = htonl (GNUNET_ATS_QUALITY_NET_DELAY); + ats[0].value = htonl (1000); + ats[1].type = htonl (GNUNET_ATS_QUALITY_NET_DISTANCE); + ats[1].value = htonl (10); + + GNUNET_TRANSPORT_set_traffic_metric (p1->th, &p2->id, TM_RECEIVE, ats, 2); +*/ + cc = GNUNET_TRANSPORT_TESTING_connect_peers (tth, p1, p2, &testing_connect_cb, + NULL); + +} + + +static void +run (void *cls, char *const *args, const char *cfgfile, + const struct GNUNET_CONFIGURATION_Handle *cfg) +{ + die_task = GNUNET_SCHEDULER_add_delayed (TIMEOUT, &end_badly, NULL); + + s_started = GNUNET_NO; + s_connected = GNUNET_NO; + s_sending = GNUNET_NO; + + p1 = GNUNET_TRANSPORT_TESTING_start_peer (tth, cfg_file_p1, 1, + ¬ify_receive, ¬ify_connect, + ¬ify_disconnect, &start_cb, + NULL); + + p2 = GNUNET_TRANSPORT_TESTING_start_peer (tth, cfg_file_p2, 2, + ¬ify_receive, ¬ify_connect, + ¬ify_disconnect, &start_cb, + NULL); + + if ((p1 == NULL) || (p2 == NULL)) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Fail! Could not start peers!\n"); + if (die_task != GNUNET_SCHEDULER_NO_TASK) + GNUNET_SCHEDULER_cancel (die_task); + die_task = GNUNET_SCHEDULER_add_now (&end_badly, NULL); + return; + } +} + + +static int +check () +{ + static char *const argv[] = { "test-transport-api-manipulation", + "-c", + "test_transport_api_data.conf", + NULL + }; + static struct GNUNET_GETOPT_CommandLineOption options[] = { + GNUNET_GETOPT_OPTION_END + }; + + send_task = GNUNET_SCHEDULER_NO_TASK; + + ok = 1; + GNUNET_PROGRAM_run ((sizeof (argv) / sizeof (char *)) - 1, argv, test_name, + "nohelp", options, &run, &ok); + + return ok; +} + +int +main (int argc, char *argv[]) +{ + int ret; + + GNUNET_TRANSPORT_TESTING_get_test_name (argv[0], &test_name); + GNUNET_TRANSPORT_TESTING_get_test_source_name (__FILE__, &test_source); + GNUNET_TRANSPORT_TESTING_get_test_plugin_name (argv[0], test_source, + &test_plugin); + + GNUNET_log_setup (test_name, + "WARNING", + NULL); + tth = GNUNET_TRANSPORT_TESTING_init (); + + GNUNET_TRANSPORT_TESTING_get_config_name (argv[0], &cfg_file_p1, 1); + GNUNET_TRANSPORT_TESTING_get_config_name (argv[0], &cfg_file_p2, 2); + + ret = check (); + + GNUNET_free (cfg_file_p1); + GNUNET_free (cfg_file_p2); + + GNUNET_free (test_source); + GNUNET_free (test_plugin); + GNUNET_free (test_name); + + GNUNET_TRANSPORT_TESTING_done (tth); + + return ret; +} + +/* end of test_transport_api.c */ diff --git a/src/transport/test_transport_api_manipulation_send_tcp_peer1.conf b/src/transport/test_transport_api_manipulation_send_tcp_peer1.conf new file mode 100644 index 0000000..db66282 --- /dev/null +++ b/src/transport/test_transport_api_manipulation_send_tcp_peer1.conf @@ -0,0 +1,30 @@ +@INLINE@ template_cfg_peer1.conf +[PATHS] +SERVICEHOME = /tmp/test-transport/api-tcp-p1/ + +[transport-tcp] +PORT = 12000 +TIMEOUT = 5 s + +[arm] +PORT = 12005 +DEFAULTSERVICES = transport +UNIXPATH = /tmp/gnunet-p1-service-arm.sock + +[statistics] +PORT = 12004 +UNIXPATH = /tmp/gnunet-p1-service-statistics.sock + +[resolver] +PORT = 12003 +UNIXPATH = /tmp/gnunet-p1-service-resolver.sock + +[peerinfo] +PORT = 12002 +UNIXPATH = /tmp/gnunet-p1-service-peerinfo.sock + +[transport] +PORT = 12001 +UNIXPATH = /tmp/gnunet-p1-service-transport.sock +PLUGINS = tcp + diff --git a/src/transport/test_transport_api_manipulation_send_tcp_peer2.conf b/src/transport/test_transport_api_manipulation_send_tcp_peer2.conf new file mode 100644 index 0000000..67f171e --- /dev/null +++ b/src/transport/test_transport_api_manipulation_send_tcp_peer2.conf @@ -0,0 +1,30 @@ +@INLINE@ template_cfg_peer2.conf +[PATHS] +SERVICEHOME = /tmp/test-transport/api-tcp-p2/ + +[transport-tcp] +PORT = 12015 +TIMEOUT = 5 s + +[arm] +PORT = 12014 +DEFAULTSERVICES = transport +UNIXPATH = /tmp/gnunet-p2-service-arm.sock + +[statistics] +PORT = 12013 +UNIXPATH = /tmp/gnunet-p2-service-statistics.sock + +[resolver] +PORT = 12012 +UNIXPATH = /tmp/gnunet-p2-service-resolver.sock + +[peerinfo] +PORT = 12011 +UNIXPATH = /tmp/gnunet-p2-service-peerinfo.sock + +[transport] +PORT = 12010 +PLUGINS = tcp +UNIXPATH = /tmp/gnunet-p2-service-transport.sock + diff --git a/src/transport/test_transport_api_multi_peer1.conf b/src/transport/test_transport_api_multi_peer1.conf index a7c57fc..61b0f56 100644 --- a/src/transport/test_transport_api_multi_peer1.conf +++ b/src/transport/test_transport_api_multi_peer1.conf @@ -1,7 +1,6 @@ @INLINE@ template_cfg_peer1.conf [PATHS] SERVICEHOME = /tmp/test-transport/api-multi-p1/ -DEFAULTCONFIG = test_transport_api_multi_peer1.conf [transport-tcp] PORT = 12140 @@ -35,7 +34,7 @@ UNIXPATH = /tmp/gnunet-p1-service-peerinfo.sock [transport] PORT = 12145 -PLUGINS = tcp udp unix +PLUGINS = tcp udp UNIXPATH = /tmp/gnunet-p1-service-transport.sock [transport-unix] diff --git a/src/transport/test_transport_api_multi_peer2.conf b/src/transport/test_transport_api_multi_peer2.conf index 8008e7f..c660c3c 100644 --- a/src/transport/test_transport_api_multi_peer2.conf +++ b/src/transport/test_transport_api_multi_peer2.conf @@ -1,7 +1,6 @@ @INLINE@ template_cfg_peer2.conf [PATHS] SERVICEHOME = /tmp/test-transport/api-multi-p2/ -DEFAULTCONFIG = test_transport_api_multi_peer2.conf [nat] ALLOW_NAT = NO @@ -38,7 +37,7 @@ UNIXPATH = /tmp/gnunet-p2-service-peerinfo.sock [transport] PORT = 12155 -PLUGINS = tcp udp unix +PLUGINS = tcp udp UNIXPATH = /tmp/gnunet-p2-service-transport.sock [transport-unix] diff --git a/src/transport/test_transport_api_reliability.c b/src/transport/test_transport_api_reliability.c index 759241c..bef2d0f 100644 --- a/src/transport/test_transport_api_reliability.c +++ b/src/transport/test_transport_api_reliability.c @@ -26,24 +26,9 @@ * achieve reliable message delivery. */ #include "platform.h" -#include "gnunet_common.h" -#include "gnunet_hello_lib.h" -#include "gnunet_getopt_lib.h" -#include "gnunet_os_lib.h" -#include "gnunet_program_lib.h" -#include "gnunet_scheduler_lib.h" -#include "gnunet_server_lib.h" #include "gnunet_transport_service.h" #include "gauger.h" -#include "transport.h" #include "transport-testing.h" - -#define VERBOSE GNUNET_NO - -#define VERBOSE_ARM GNUNET_NO - -#define START_ARM GNUNET_YES - /** * Testcase timeout */ @@ -479,18 +464,12 @@ check () static char *argv[] = { "test_transport", "-c", "test_transport_api_data.conf", -#if VERBOSE - "-L", "DEBUG", -#endif NULL }; static struct GNUNET_GETOPT_CommandLineOption options[] = { GNUNET_GETOPT_OPTION_END }; -#if WRITECONFIG - setTransportOptions ("test_transport_api_data.conf"); -#endif ok = 1; GNUNET_PROGRAM_run ((sizeof (argv) / sizeof (char *)) - 1, argv, test_name, "nohelp", options, &run, &ok); @@ -506,11 +485,7 @@ main (int argc, char *argv[]) GNUNET_TRANSPORT_TESTING_get_test_name (argv[0], &test_name); GNUNET_log_setup (test_name, -#if VERBOSE - "DEBUG", -#else "WARNING", -#endif NULL); GNUNET_TRANSPORT_TESTING_get_test_source_name (__FILE__, &test_source); diff --git a/src/transport/test_transport_api_reliability_http_nat_peer1.conf b/src/transport/test_transport_api_reliability_http_nat_peer1.conf deleted file mode 100644 index cd841a3..0000000 --- a/src/transport/test_transport_api_reliability_http_nat_peer1.conf +++ /dev/null @@ -1,38 +0,0 @@ -@INLINE@ template_cfg_peer1.conf -[PATHS] -SERVICEHOME = /tmp/test-transport/api-http-p1/ -DEFAULTCONFIG = test_transport_api_reliability_http_nat_peer1.conf - -[nat] -BEHIND_NAT = YES -ENABLE_NAT_SERVER = YES - -[transport-http] -PORT = 0 - -[arm] -PORT = 12085 -DEFAULTSERVICES = transport -UNIXPATH = /tmp/gnunet-p1-service-arm.sock - -[statistics] -PORT = 12084 -UNIXPATH = /tmp/gnunet-p1-service-statistics.sock - -[resolver] -PORT = 12083 -UNIXPATH = /tmp/gnunet-p1-service-resolver.sock - -[peerinfo] -PORT = 12082 -UNIXPATH = /tmp/gnunet-p1-service-peerinfo.sock - -[transport] -#DEBUG = YES -PORT = 12081 -PLUGINS = http -#BINARY = .libs/gnunet-service-transport -UNIXPATH = /tmp/gnunet-p1-service-transport.sock -#PREFIX = valgrind --leak-check=full -#PREFIX = xterm -geometry 100x85 -T peer1 -e gdb --args - diff --git a/src/transport/test_transport_api_reliability_http_nat_peer2.conf b/src/transport/test_transport_api_reliability_http_nat_peer2.conf deleted file mode 100644 index c87a256..0000000 --- a/src/transport/test_transport_api_reliability_http_nat_peer2.conf +++ /dev/null @@ -1,35 +0,0 @@ -@INLINE@ template_cfg_peer2.conf -[PATHS] -SERVICEHOME = /tmp/test-transport/api-http-p2/ -DEFAULTCONFIG = test_transport_api_reliability_http_nat_peer2.conf - -[ats] -WAN_QUOTA_OUT = 1073741824 -WAN_QUOTA_IN = 1073741824 - -[transport-http] -PORT = 12090 - -[arm] -PORT = 12095 -DEFAULTSERVICES = transport -UNIXPATH = /tmp/gnunet-p2-service-arm.sock - -[statistics] -PORT = 12094 -UNIXPATH = /tmp/gnunet-p2-service-statistics.sock - -[resolver] -PORT = 12093 -UNIXPATH = /tmp/gnunet-p2-service-resolver.sock - -[peerinfo] -PORT = 12092 -UNIXPATH = /tmp/gnunet-p2-service-peerinfo.sock - -[transport] -#DEBUG = YES -PORT = 12091 -PLUGINS = http -UNIXPATH = /tmp/gnunet-p2-service-transport.sock -#PREFIX = valgrind --leak-check=full diff --git a/src/transport/test_transport_api_reliability_http_peer1.conf b/src/transport/test_transport_api_reliability_http_peer1.conf index ebb6e43..ea5de0b 100644 --- a/src/transport/test_transport_api_reliability_http_peer1.conf +++ b/src/transport/test_transport_api_reliability_http_peer1.conf @@ -1,7 +1,8 @@ @INLINE@ template_cfg_peer1.conf [PATHS] SERVICEHOME = /tmp/test-transport/api-http-p1/ -DEFAULTCONFIG = test_transport_api_reliability_http_peer1.conf + +[transport-http_client] [transport-tcp] TIMEOUT = 5 s @@ -27,7 +28,6 @@ UNIXPATH = /tmp/gnunet-p1-service-peerinfo.sock [transport] PORT = 12181 -PLUGINS = http +PLUGINS = http_client UNIXPATH = /tmp/gnunet-p1-service-transport.sock -#DEBUG = YES diff --git a/src/transport/test_transport_api_reliability_http_peer2.conf b/src/transport/test_transport_api_reliability_http_peer2.conf index c21fa1d..083cd4d 100644 --- a/src/transport/test_transport_api_reliability_http_peer2.conf +++ b/src/transport/test_transport_api_reliability_http_peer2.conf @@ -1,10 +1,11 @@ @INLINE@ template_cfg_peer2.conf [PATHS] SERVICEHOME = /tmp/test-transport/api-http-p2/ -DEFAULTCONFIG = test_transport_api_reliability_http_peer2.conf -[transport-http] -PORT = 12190 +[transport-http_server] +PORT = 12090 +USE_IPv6 = NO +BINDTO = 127.0.0.1 [arm] PORT = 12195 @@ -24,7 +25,6 @@ UNIXPATH = /tmp/gnunet-p2-service-peerinfo.sock [transport] PORT = 12191 -PLUGINS = http +PLUGINS = http_server UNIXPATH = /tmp/gnunet-p2-service-transport.sock -#DEBUG = YES diff --git a/src/transport/test_transport_api_reliability_https_nat_peer1.conf b/src/transport/test_transport_api_reliability_https_nat_peer1.conf deleted file mode 100644 index ca14c72..0000000 --- a/src/transport/test_transport_api_reliability_https_nat_peer1.conf +++ /dev/null @@ -1,36 +0,0 @@ -@INLINE@ template_cfg_peer1.conf -[PATHS] -SERVICEHOME = /tmp/test-transport/api-https-p1/ -DEFAULTCONFIG = test_transport_api_reliability_https_nat_peer1.conf - -[nat] -BEHIND_NAT = YES -ENABLE_NAT_SERVER = YES - -[transport-https] -PORT = 0 -KEY_FILE = $SERVICEHOME/https_key_p1.key -CERT_FILE = $SERVICEHOME/https_cert_p1.crt - -[arm] -PORT = 12105 - -[statistics] -PORT = 12104 -UNIXPATH = /tmp/gnunet-p1-service-statistics.sock - -[resolver] -PORT = 12103 -UNIXPATH = /tmp/gnunet-p1-service-resolver.sock - -[peerinfo] -PORT = 12102 -UNIXPATH = /tmp/gnunet-p1-service-peerinfo.sock - -[transport] -PORT = 12101 -PLUGINS = https -UNIXPATH = /tmp/gnunet-p1-service-transport.sock -DEBUG = NO - - diff --git a/src/transport/test_transport_api_reliability_https_nat_peer2.conf b/src/transport/test_transport_api_reliability_https_nat_peer2.conf deleted file mode 100644 index b7c2e97..0000000 --- a/src/transport/test_transport_api_reliability_https_nat_peer2.conf +++ /dev/null @@ -1,33 +0,0 @@ -@INLINE@ template_cfg_peer2.conf -[PATHS] -SERVICEHOME = /tmp/test-transport/api-https-p2/ -DEFAULTCONFIG = test_transport_api_reliability_https_nat_peer2.conf - -[transport-https] -PORT = 12110 -KEY_FILE = $SERVICEHOME/https_key_p2.key -CERT_FILE = $SERVICEHOME/https_cert_p2.crt - -[arm] -PORT = 12115 -UNIXPATH = /tmp/gnunet-p2-service-arm.sock - -[statistics] -PORT = 12114 -UNIXPATH = /tmp/gnunet-p2-service-statistics.sock - -[resolver] -PORT = 12113 -UNIXPATH = /tmp/gnunet-p2-service-resolver.sock - -[peerinfo] -PORT = 12112 -UNIXPATH = /tmp/gnunet-p2-service-peerinfo.sock - -[transport] -PORT = 12111 -PLUGINS = https -UNIXPATH = /tmp/gnunet-p2-service-transport.sock -DEBUG = NO - - diff --git a/src/transport/test_transport_api_reliability_https_peer1.conf b/src/transport/test_transport_api_reliability_https_peer1.conf index 0699f69..d5e8826 100644 --- a/src/transport/test_transport_api_reliability_https_peer1.conf +++ b/src/transport/test_transport_api_reliability_https_peer1.conf @@ -1,12 +1,8 @@ @INLINE@ template_cfg_peer1.conf [PATHS] SERVICEHOME = /tmp/test-transport/api-https-p1/ -DEFAULTCONFIG = test_transport_api_reliability_https_peer1.conf -[transport-https] -PORT = 12300 -KEY_FILE = $SERVICEHOME/https_key_p1.key -CERT_FILE = $SERVICEHOME/https_cert_p1.crt +[transport-https_client] [arm] PORT = 12305 @@ -26,6 +22,6 @@ UNIXPATH = /tmp/gnunet-p1-service-peerinfo.sock [transport] PORT = 12301 -PLUGINS = https +PLUGINS = https_client UNIXPATH = /tmp/gnunet-p1-service-transport.sock diff --git a/src/transport/test_transport_api_reliability_https_peer2.conf b/src/transport/test_transport_api_reliability_https_peer2.conf index bd344ab..5cc0d24 100644 --- a/src/transport/test_transport_api_reliability_https_peer2.conf +++ b/src/transport/test_transport_api_reliability_https_peer2.conf @@ -1,9 +1,8 @@ @INLINE@ template_cfg_peer2.conf [PATHS] SERVICEHOME = /tmp/test-transport/api-https-p2/ -DEFAULTCONFIG = test_transport_api_reliability_https_peer2.conf -[transport-https] +[transport-https_server] PORT = 12310 KEY_FILE = $SERVICEHOME/https_key_p2.key CERT_FILE = $SERVICEHOME/https_cert_p2.crt @@ -26,7 +25,7 @@ UNIXPATH = /tmp/gnunet-p2-service-peerinfo.sock [transport] PORT = 12311 -PLUGINS = https +PLUGINS = https_server UNIXPATH = /tmp/gnunet-p2-service-transport.sock diff --git a/src/transport/test_transport_api_reliability_tcp_nat_peer1.conf b/src/transport/test_transport_api_reliability_tcp_nat_peer1.conf index ffd3d2f..9490d40 100644 --- a/src/transport/test_transport_api_reliability_tcp_nat_peer1.conf +++ b/src/transport/test_transport_api_reliability_tcp_nat_peer1.conf @@ -1,7 +1,6 @@ @INLINE@ template_cfg_peer1.conf [PATHS] SERVICEHOME = /tmp/test-transport/api-reliability-tcp-nat-p1/ -DEFAULTCONFIG = test_transport_api_reliability_tcp_nat_peer1.conf [nat] BEHIND_NAT = YES diff --git a/src/transport/test_transport_api_reliability_tcp_nat_peer2.conf b/src/transport/test_transport_api_reliability_tcp_nat_peer2.conf index c6020ff..b59916b 100644 --- a/src/transport/test_transport_api_reliability_tcp_nat_peer2.conf +++ b/src/transport/test_transport_api_reliability_tcp_nat_peer2.conf @@ -1,7 +1,6 @@ @INLINE@ template_cfg_peer2.conf [PATHS] SERVICEHOME = /tmp/test-transport/api-reliability-tcp-nat-p2/ -DEFAULTCONFIG = test_transport_api_reliability_tcp_nat_peer2.conf [nat] DISABLEV6 = YES diff --git a/src/transport/test_transport_api_reliability_tcp_peer1.conf b/src/transport/test_transport_api_reliability_tcp_peer1.conf index 3be982d..5f1d693 100644 --- a/src/transport/test_transport_api_reliability_tcp_peer1.conf +++ b/src/transport/test_transport_api_reliability_tcp_peer1.conf @@ -1,7 +1,6 @@ @INLINE@ template_cfg_peer1.conf [PATHS] SERVICEHOME = /tmp/test-transport/api-tcp-p1/ -DEFAULTCONFIG = test_transport_api_reliability_tcp_peer1.conf [transport-tcp] PORT = 12000 diff --git a/src/transport/test_transport_api_reliability_tcp_peer2.conf b/src/transport/test_transport_api_reliability_tcp_peer2.conf index 62575a9..181aab3 100644 --- a/src/transport/test_transport_api_reliability_tcp_peer2.conf +++ b/src/transport/test_transport_api_reliability_tcp_peer2.conf @@ -1,7 +1,6 @@ @INLINE@ template_cfg_peer2.conf [PATHS] SERVICEHOME = /tmp/test-transport/api-tcp-p2/ -DEFAULTCONFIG = test_transport_api_reliability_tcp_peer2.conf [transport-tcp] PORT = 12015 @@ -28,4 +27,3 @@ UNIXPATH = /tmp/gnunet-p2-service-peerinfo.sock PORT = 12010 PLUGINS = tcp UNIXPATH = /tmp/gnunet-p2-service-transport.sock -#DEBUG = YES diff --git a/src/transport/test_transport_api_reliability_wlan_peer1.conf b/src/transport/test_transport_api_reliability_wlan_peer1.conf index 9dd9d1b..e81a3f9 100644 --- a/src/transport/test_transport_api_reliability_wlan_peer1.conf +++ b/src/transport/test_transport_api_reliability_wlan_peer1.conf @@ -1,7 +1,6 @@ @INLINE@ template_cfg_peer1.conf [PATHS] SERVICEHOME = /tmp/test-transport/api-wlan-p1/ -DEFAULTCONFIG = test_transport_api_wlan_peer1.conf [transport-wlan] TESTMODE = 1 diff --git a/src/transport/test_transport_api_reliability_wlan_peer2.conf b/src/transport/test_transport_api_reliability_wlan_peer2.conf index bc868d7..bd53876 100644 --- a/src/transport/test_transport_api_reliability_wlan_peer2.conf +++ b/src/transport/test_transport_api_reliability_wlan_peer2.conf @@ -1,7 +1,6 @@ @INLINE@ template_cfg_peer2.conf [PATHS] SERVICEHOME = /tmp/test-transport/api-wlan-p2/ -DEFAULTCONFIG = test_transport_api_wlan_peer2.conf [transport-wlan] INTERFACE = mon1 diff --git a/src/transport/test_transport_api_restart_1peer.c b/src/transport/test_transport_api_restart_1peer.c index b7fc7ab..9927946 100644 --- a/src/transport/test_transport_api_restart_1peer.c +++ b/src/transport/test_transport_api_restart_1peer.c @@ -26,19 +26,9 @@ * C code apparently. */ #include "platform.h" -#include "gnunet_common.h" -#include "gnunet_hello_lib.h" -#include "gnunet_getopt_lib.h" -#include "gnunet_os_lib.h" -#include "gnunet_program_lib.h" -#include "gnunet_scheduler_lib.h" #include "gnunet_transport_service.h" -#include "transport.h" #include "transport-testing.h" - -#define START_ARM GNUNET_YES - /** * How long until we give up on transmitting the message? */ @@ -156,7 +146,7 @@ reconnect (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) reconnect_task = GNUNET_SCHEDULER_NO_TASK; - GNUNET_TRANSPORT_try_connect (p->th, &p2->id); + GNUNET_TRANSPORT_try_connect (p->th, &p2->id, NULL, NULL); /*FIXME TRY_CONNECT change */ reconnect_task = GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_SECONDS, &reconnect, p); } @@ -437,9 +427,6 @@ check () GNUNET_GETOPT_OPTION_END }; -#if WRITECONFIG - setTransportOptions ("test_transport_api_data.conf"); -#endif send_task = GNUNET_SCHEDULER_NO_TASK; ok = 1; diff --git a/src/transport/test_transport_api_restart_2peers.c b/src/transport/test_transport_api_restart_2peers.c index 1d7790c..6e55f57 100644 --- a/src/transport/test_transport_api_restart_2peers.c +++ b/src/transport/test_transport_api_restart_2peers.c @@ -26,18 +26,9 @@ * C code apparently. */ #include "platform.h" -#include "gnunet_common.h" -#include "gnunet_hello_lib.h" -#include "gnunet_getopt_lib.h" -#include "gnunet_os_lib.h" -#include "gnunet_program_lib.h" -#include "gnunet_scheduler_lib.h" #include "gnunet_transport_service.h" -#include "transport.h" #include "transport-testing.h" -#define START_ARM GNUNET_YES - /** * How long until we give up on transmitting the message? */ @@ -147,7 +138,7 @@ reconnect (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) struct PeerContext *p = cls; reconnect_task = GNUNET_SCHEDULER_NO_TASK; - GNUNET_TRANSPORT_try_connect (p1->th, &p2->id); + GNUNET_TRANSPORT_try_connect (p1->th, &p2->id, NULL, NULL); /*FIXME TRY_CONNECT change */ reconnect_task = GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_SECONDS, &reconnect, p); } @@ -417,9 +408,6 @@ check () GNUNET_GETOPT_OPTION_END }; -#if WRITECONFIG - setTransportOptions ("test_transport_api_data.conf"); -#endif send_task = GNUNET_SCHEDULER_NO_TASK; ok = 1; diff --git a/src/transport/test_transport_api_tcp_nat_peer1.conf b/src/transport/test_transport_api_tcp_nat_peer1.conf index 73f36f3..8e33f27 100644 --- a/src/transport/test_transport_api_tcp_nat_peer1.conf +++ b/src/transport/test_transport_api_tcp_nat_peer1.conf @@ -1,7 +1,6 @@ @INLINE@ template_cfg_peer1.conf [PATHS] SERVICEHOME = /tmp/test-transport/api-tcp-nat-p1/ -DEFAULTCONFIG = test_transport_api_tcp_nat_peer1.conf [nat] BEHIND_NAT = YES @@ -33,5 +32,4 @@ UNIXPATH = /tmp/gnunet-p1-service-peerinfo.sock PORT = 29542 PLUGINS = tcp UNIXPATH = /tmp/gnunet-p1-service-transport.sock -#DEBUG = YES diff --git a/src/transport/test_transport_api_tcp_nat_peer2.conf b/src/transport/test_transport_api_tcp_nat_peer2.conf index 0bf50fd..f8b8b01 100644 --- a/src/transport/test_transport_api_tcp_nat_peer2.conf +++ b/src/transport/test_transport_api_tcp_nat_peer2.conf @@ -1,7 +1,6 @@ @INLINE@ template_cfg_peer2.conf [PATHS] SERVICEHOME = /tmp/test-transport/api-tcp-nat-p2/ -DEFAULTCONFIG = test_transport_api_tcp_nat_peer2.conf [nat] DISABLEV6 = YES @@ -32,4 +31,3 @@ UNIXPATH = /tmp/gnunet-p2-service-peerinfo.sock PORT = 45923 PLUGINS = tcp UNIXPATH = /tmp/gnunet-p2-service-transport.sock -#DEBUG = YES diff --git a/src/transport/test_transport_api_tcp_peer1.conf b/src/transport/test_transport_api_tcp_peer1.conf index 9532b73..db66282 100644 --- a/src/transport/test_transport_api_tcp_peer1.conf +++ b/src/transport/test_transport_api_tcp_peer1.conf @@ -1,7 +1,6 @@ @INLINE@ template_cfg_peer1.conf [PATHS] SERVICEHOME = /tmp/test-transport/api-tcp-p1/ -DEFAULTCONFIG = test_transport_api_tcp_peer1.conf [transport-tcp] PORT = 12000 @@ -28,5 +27,4 @@ UNIXPATH = /tmp/gnunet-p1-service-peerinfo.sock PORT = 12001 UNIXPATH = /tmp/gnunet-p1-service-transport.sock PLUGINS = tcp -#DEBUG = YES diff --git a/src/transport/test_transport_api_tcp_peer2.conf b/src/transport/test_transport_api_tcp_peer2.conf index fe6d19b..67f171e 100644 --- a/src/transport/test_transport_api_tcp_peer2.conf +++ b/src/transport/test_transport_api_tcp_peer2.conf @@ -1,7 +1,6 @@ @INLINE@ template_cfg_peer2.conf [PATHS] SERVICEHOME = /tmp/test-transport/api-tcp-p2/ -DEFAULTCONFIG = test_transport_api_tcp_peer2.conf [transport-tcp] PORT = 12015 diff --git a/src/transport/test_transport_api_timeout.c b/src/transport/test_transport_api_timeout.c index 8b92dce..2645739 100644 --- a/src/transport/test_transport_api_timeout.c +++ b/src/transport/test_transport_api_timeout.c @@ -28,20 +28,9 @@ */ #include "platform.h" -#include "gnunet_common.h" -#include "gnunet_hello_lib.h" -#include "gnunet_getopt_lib.h" -#include "gnunet_os_lib.h" -#include "gnunet_program_lib.h" -#include "gnunet_scheduler_lib.h" #include "gnunet_transport_service.h" -#include "transport.h" #include "transport-testing.h" -#define VERBOSE GNUNET_NO - -#define START_ARM GNUNET_YES - /** * How long until we give up on transmitting the message? */ @@ -305,9 +294,6 @@ check () GNUNET_GETOPT_OPTION_END }; -#if WRITECONFIG - setTransportOptions ("test_transport_api_data.conf"); -#endif timer_task = GNUNET_SCHEDULER_NO_TASK; ok = 1; diff --git a/src/transport/test_transport_api_timeout_http_peer1.conf b/src/transport/test_transport_api_timeout_http_peer1.conf index a28750a..665527b 100644 --- a/src/transport/test_transport_api_timeout_http_peer1.conf +++ b/src/transport/test_transport_api_timeout_http_peer1.conf @@ -1,12 +1,10 @@ @INLINE@ template_cfg_peer1.conf [PATHS] SERVICEHOME = /tmp/test-transport/api-http-p1/ -DEFAULTCONFIG = test_transport_api_http_peer1.conf [nat] -[transport-http] -PORT = 12080 +[transport-http_client] [arm] PORT = 12085 @@ -26,9 +24,8 @@ PORT = 12082 UNIXPATH = /tmp/gnunet-p1-service-peerinfo.sock [transport] -#DEBUG = YES PORT = 12081 -PLUGINS = http +PLUGINS = http_client #BINARY = .libs/gnunet-service-transport UNIXPATH = /tmp/gnunet-p1-service-transport.sock #PREFIX = valgrind --leak-check=full diff --git a/src/transport/test_transport_api_timeout_http_peer2.conf b/src/transport/test_transport_api_timeout_http_peer2.conf index 1269358..1fdc947 100644 --- a/src/transport/test_transport_api_timeout_http_peer2.conf +++ b/src/transport/test_transport_api_timeout_http_peer2.conf @@ -1,12 +1,14 @@ @INLINE@ template_cfg_peer2.conf [PATHS] SERVICEHOME = /tmp/test-transport/api-http-p2/ -DEFAULTCONFIG = test_transport_api_http_peer2.conf [nat] -[transport-http] +[transport-http_server] PORT = 12090 +USE_IPv6 = NO +BINDTO = 127.0.0.1 + [arm] PORT = 12095 @@ -26,8 +28,7 @@ PORT = 12092 UNIXPATH = /tmp/gnunet-p2-service-peerinfo.sock [transport] -#DEBUG = YES PORT = 12091 -PLUGINS = http +PLUGINS = http_server UNIXPATH = /tmp/gnunet-p2-service-transport.sock #PREFIX = valgrind --leak-check=full diff --git a/src/transport/test_transport_api_timeout_https_peer1.conf b/src/transport/test_transport_api_timeout_https_peer1.conf index 8a93ca1..fda69ae 100644 --- a/src/transport/test_transport_api_timeout_https_peer1.conf +++ b/src/transport/test_transport_api_timeout_https_peer1.conf @@ -1,12 +1,8 @@ @INLINE@ template_cfg_peer1.conf [PATHS] SERVICEHOME = /tmp/test-transport/api-https-p1/ -DEFAULTCONFIG = test_transport_api_https_peer1.conf -[transport-https] -PORT = 12100 -KEY_FILE = $SERVICEHOME/https_key_p1.key -CERT_FILE = $SERVICEHOME/https_cert_p1.crt +[transport-https_client] [arm] PORT = 12105 @@ -25,8 +21,7 @@ UNIXPATH = /tmp/gnunet-p1-service-peerinfo.sock [transport] PORT = 12101 -PLUGINS = https +PLUGINS = https_client UNIXPATH = /tmp/gnunet-p1-service-transport.sock -DEBUG = NO diff --git a/src/transport/test_transport_api_timeout_https_peer2.conf b/src/transport/test_transport_api_timeout_https_peer2.conf index 0710f41..ca54e17 100644 --- a/src/transport/test_transport_api_timeout_https_peer2.conf +++ b/src/transport/test_transport_api_timeout_https_peer2.conf @@ -1,9 +1,8 @@ @INLINE@ template_cfg_peer2.conf [PATHS] SERVICEHOME = /tmp/test-transport/api-https-p2/ -DEFAULTCONFIG = test_transport_api_https_peer2.conf -[transport-https] +[transport-https_server] PORT = 12110 KEY_FILE = $SERVICEHOME/https_key_p2.key CERT_FILE = $SERVICEHOME/https_cert_p2.crt @@ -26,8 +25,7 @@ UNIXPATH = /tmp/gnunet-p2-service-peerinfo.sock [transport] PORT = 12111 -PLUGINS = https +PLUGINS = https_server UNIXPATH = /tmp/gnunet-p2-service-transport.sock -DEBUG = NO diff --git a/src/transport/test_transport_api_timeout_tcp_peer1.conf b/src/transport/test_transport_api_timeout_tcp_peer1.conf index ecb599f..dceeccb 100644 --- a/src/transport/test_transport_api_timeout_tcp_peer1.conf +++ b/src/transport/test_transport_api_timeout_tcp_peer1.conf @@ -1,7 +1,6 @@ @INLINE@ template_cfg_peer1.conf [PATHS] SERVICEHOME = /tmp/test-transport/api-tcp-p1/ -DEFAULTCONFIG = test_transport_api_timeout_tcp_peer1.conf [transport-tcp] PORT = 12000 diff --git a/src/transport/test_transport_api_timeout_tcp_peer2.conf b/src/transport/test_transport_api_timeout_tcp_peer2.conf index ba2e27e..f89c3a3 100644 --- a/src/transport/test_transport_api_timeout_tcp_peer2.conf +++ b/src/transport/test_transport_api_timeout_tcp_peer2.conf @@ -1,7 +1,6 @@ @INLINE@ template_cfg_peer2.conf [PATHS] SERVICEHOME = /tmp/test-transport/api-tcp-p2/ -DEFAULTCONFIG = test_transport_api_timeout_tcp_peer2.conf [nat] ALLOW_NAT = NO diff --git a/src/transport/test_transport_api_timeout_udp_peer1.conf b/src/transport/test_transport_api_timeout_udp_peer1.conf index a1216e4..7c3e33a 100644 --- a/src/transport/test_transport_api_timeout_udp_peer1.conf +++ b/src/transport/test_transport_api_timeout_udp_peer1.conf @@ -1,7 +1,6 @@ @INLINE@ template_cfg_peer1.conf [PATHS] SERVICEHOME = /tmp/test-transport/api-udp-p1/ -DEFAULTCONFIG = test_transport_api_udp_peer1.conf [transport-udp] PORT = 12040 diff --git a/src/transport/test_transport_api_timeout_udp_peer2.conf b/src/transport/test_transport_api_timeout_udp_peer2.conf index 3e487a6..9b79c3b 100644 --- a/src/transport/test_transport_api_timeout_udp_peer2.conf +++ b/src/transport/test_transport_api_timeout_udp_peer2.conf @@ -1,7 +1,6 @@ @INLINE@ template_cfg_peer2.conf [PATHS] SERVICEHOME = /tmp/test-transport/api-udp-p2/ -DEFAULTCONFIG = test_transport_api_udp_peer2.conf [transport-udp] PORT = 12050 diff --git a/src/transport/test_transport_api_timeout_unix_peer1.conf b/src/transport/test_transport_api_timeout_unix_peer1.conf index b1ace7d..5d0235f 100644 --- a/src/transport/test_transport_api_timeout_unix_peer1.conf +++ b/src/transport/test_transport_api_timeout_unix_peer1.conf @@ -1,7 +1,6 @@ @INLINE@ template_cfg_peer1.conf [PATHS] SERVICEHOME = /tmp/test-transport/api-unix-p1/ -DEFAULTCONFIG = test_transport_api_unix_peer1.conf [arm] PORT = 12125 diff --git a/src/transport/test_transport_api_timeout_unix_peer2.conf b/src/transport/test_transport_api_timeout_unix_peer2.conf index a153588..255c7e2 100644 --- a/src/transport/test_transport_api_timeout_unix_peer2.conf +++ b/src/transport/test_transport_api_timeout_unix_peer2.conf @@ -1,7 +1,6 @@ @INLINE@ template_cfg_peer2.conf [PATHS] SERVICEHOME = /tmp/test-transport/api-unix-p2/ -DEFAULTCONFIG = test_transport_api_unix_peer2.conf [arm] PORT = 12135 diff --git a/src/transport/test_transport_api_udp_nat_peer1.conf b/src/transport/test_transport_api_udp_nat_peer1.conf index 16a4e62..e406883 100644 --- a/src/transport/test_transport_api_udp_nat_peer1.conf +++ b/src/transport/test_transport_api_udp_nat_peer1.conf @@ -1,7 +1,6 @@ @INLINE@ template_cfg_peer1.conf [PATHS] SERVICEHOME = /tmp/test-transport/api-udp-nat-p1/ -DEFAULTCONFIG = test_transport_api_udp_nat_peer1.conf [nat] BEHIND_NAT = YES @@ -32,6 +31,5 @@ UNIXPATH = /tmp/gnunet-p1-service-peerinfo.sock PORT = 12061 PLUGINS = udp UNIXPATH = /tmp/gnunet-p1-service-transport.sock -DEBUG = NO diff --git a/src/transport/test_transport_api_udp_nat_peer2.conf b/src/transport/test_transport_api_udp_nat_peer2.conf index 0852b25..43ed3a9 100644 --- a/src/transport/test_transport_api_udp_nat_peer2.conf +++ b/src/transport/test_transport_api_udp_nat_peer2.conf @@ -1,7 +1,6 @@ @INLINE@ template_cfg_peer2.conf [PATHS] SERVICEHOME = /tmp/test-transport/api-udp-nat-p2/ -DEFAULTCONFIG = test_transport_api_udp_nat_peer2.conf [nat] ALLOW_NAT = YES @@ -30,6 +29,5 @@ UNIXPATH = /tmp/gnunet-p2-service-peerinfo.sock PORT = 12071 PLUGINS = udp UNIXPATH = /tmp/gnunet-p2-service-transport.sock -DEBUG = NO diff --git a/src/transport/test_transport_api_udp_peer1.conf b/src/transport/test_transport_api_udp_peer1.conf index a1216e4..7c3e33a 100644 --- a/src/transport/test_transport_api_udp_peer1.conf +++ b/src/transport/test_transport_api_udp_peer1.conf @@ -1,7 +1,6 @@ @INLINE@ template_cfg_peer1.conf [PATHS] SERVICEHOME = /tmp/test-transport/api-udp-p1/ -DEFAULTCONFIG = test_transport_api_udp_peer1.conf [transport-udp] PORT = 12040 diff --git a/src/transport/test_transport_api_udp_peer2.conf b/src/transport/test_transport_api_udp_peer2.conf index 3e487a6..9b79c3b 100644 --- a/src/transport/test_transport_api_udp_peer2.conf +++ b/src/transport/test_transport_api_udp_peer2.conf @@ -1,7 +1,6 @@ @INLINE@ template_cfg_peer2.conf [PATHS] SERVICEHOME = /tmp/test-transport/api-udp-p2/ -DEFAULTCONFIG = test_transport_api_udp_peer2.conf [transport-udp] PORT = 12050 diff --git a/src/transport/test_transport_api_unix_peer1.conf b/src/transport/test_transport_api_unix_peer1.conf index b1ace7d..5d0235f 100644 --- a/src/transport/test_transport_api_unix_peer1.conf +++ b/src/transport/test_transport_api_unix_peer1.conf @@ -1,7 +1,6 @@ @INLINE@ template_cfg_peer1.conf [PATHS] SERVICEHOME = /tmp/test-transport/api-unix-p1/ -DEFAULTCONFIG = test_transport_api_unix_peer1.conf [arm] PORT = 12125 diff --git a/src/transport/test_transport_api_unix_peer2.conf b/src/transport/test_transport_api_unix_peer2.conf index a153588..255c7e2 100644 --- a/src/transport/test_transport_api_unix_peer2.conf +++ b/src/transport/test_transport_api_unix_peer2.conf @@ -1,7 +1,6 @@ @INLINE@ template_cfg_peer2.conf [PATHS] SERVICEHOME = /tmp/test-transport/api-unix-p2/ -DEFAULTCONFIG = test_transport_api_unix_peer2.conf [arm] PORT = 12135 diff --git a/src/transport/test_transport_api_unreliability.c b/src/transport/test_transport_api_unreliability.c index 53de91a..3658198 100644 --- a/src/transport/test_transport_api_unreliability.c +++ b/src/transport/test_transport_api_unreliability.c @@ -27,24 +27,10 @@ * achieve reliable message delivery. */ #include "platform.h" -#include "gnunet_common.h" -#include "gnunet_hello_lib.h" -#include "gnunet_getopt_lib.h" -#include "gnunet_os_lib.h" -#include "gnunet_program_lib.h" -#include "gnunet_scheduler_lib.h" -#include "gnunet_server_lib.h" #include "gnunet_transport_service.h" #include "gauger.h" -#include "transport.h" #include "transport-testing.h" -#define VERBOSE GNUNET_NO - -#define VERBOSE_ARM GNUNET_NO - -#define START_ARM GNUNET_YES - /** * Testcase timeout */ @@ -85,6 +71,8 @@ struct GNUNET_TRANSPORT_TESTING_handle *tth; */ /** + * Total number of messages to send + * * Note that this value must not significantly exceed * 'MAX_PENDING' in 'gnunet-service-transport.c', otherwise * messages may be dropped even for a reliable transport. @@ -175,7 +163,7 @@ end () { if (get_bit (bitmap, i) == 0) { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Did not receive message %d\n", i); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Did not receive message %d\n", i); ok = -1; } } @@ -203,6 +191,16 @@ end_badly () GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Test had timeout while waiting to send data\n"); + int i; + + for (i = 0; i < TOTAL_MSGS; i++) + { + if (get_bit (bitmap, i) == 0) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Did not receive message %d\n", i); + ok = -1; + } + } if (th != NULL) GNUNET_TRANSPORT_notify_transmit_ready_cancel (th); @@ -244,8 +242,9 @@ get_size (unsigned int iter) * Sets a bit active in the bitmap. * * @param bitIdx which bit to set + * @return GNUNET_SYSERR on error, GNUNET_OK on success */ -static void +static int set_bit (unsigned int bitIdx) { size_t arraySlot; @@ -253,13 +252,14 @@ set_bit (unsigned int bitIdx) if (bitIdx >= sizeof (bitmap) * 8) { - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "tried to set bit %d of %d(!?!?)\n", + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "tried to set bit %d of %d(!?!?)\n", bitIdx, sizeof (bitmap) * 8); - return; + return GNUNET_SYSERR; } arraySlot = bitIdx / 8; targetBit = (1L << (bitIdx % 8)); bitmap[arraySlot] |= targetBit; + return GNUNET_OK; } /** @@ -272,7 +272,7 @@ set_bit (unsigned int bitIdx) static int get_bit (const char *map, unsigned int bit) { - if (bit >= TOTAL_MSGS) + if (bit > TOTAL_MSGS) { GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "get bit %d of %d(!?!?)\n", bit, sizeof (bitmap) * 8); @@ -333,7 +333,12 @@ notify_receive (void *cls, const struct GNUNET_PeerIdentity *peer, } #endif n++; - set_bit (ntohl (hdr->num)); + if (GNUNET_SYSERR == set_bit (ntohl (hdr->num))) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Message id %u is bigger than maxmimum number of messages %u expected\n"), + ntohl (hdr->num), TOTAL_MSGS); + } test_sending = GNUNET_YES; if (0 == (n % (TOTAL_MSGS / 100))) { @@ -376,9 +381,11 @@ notify_ready (void *cls, size_t size, void *buf) s = get_size (n); GNUNET_assert (size >= s); GNUNET_assert (buf != NULL); + GNUNET_assert (n < TOTAL_MSGS); cbuf = buf; do { + GNUNET_assert (n < TOTAL_MSGS); hdr.header.size = htons (s); hdr.header.type = htons (MTYPE); hdr.num = htonl (n); @@ -387,20 +394,20 @@ notify_ready (void *cls, size_t size, void *buf) ret += sizeof (struct TestMessage); memset (&cbuf[ret], n, s - sizeof (struct TestMessage)); ret += s - sizeof (struct TestMessage); + #if VERBOSE if (n % 5000 == 0) { GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Sending message %u of size %u\n", n, s); } - #endif n++; s = get_size (n); if (0 == GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK, 16)) break; /* sometimes pack buffer full, sometimes not */ } - while (size - ret >= s); + while ((size - ret >= s) && (n < TOTAL_MSGS)); if (n < TOTAL_MSGS) { th = GNUNET_TRANSPORT_notify_transmit_ready (p2->th, &p1->id, s, 0, @@ -450,6 +457,8 @@ static void sendtask () { start_time = GNUNET_TIME_absolute_get (); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Starting to send %u messages\n", + TOTAL_MSGS); th = GNUNET_TRANSPORT_notify_transmit_ready (p2->th, &p1->id, get_size (0), 0, TIMEOUT_TRANSMIT, ¬ify_ready, NULL); @@ -525,9 +534,6 @@ check () static char *const argv[] = { "test-transport-api-unreliability", "-c", "test_transport_api_data.conf", -#if VERBOSE - "-L", "DEBUG", -#endif NULL }; static struct GNUNET_GETOPT_CommandLineOption options[] = { @@ -553,11 +559,7 @@ main (int argc, char *argv[]) GNUNET_TRANSPORT_TESTING_get_test_name (argv[0], &test_name); GNUNET_log_setup (test_name, -#if VERBOSE - "DEBUG", -#else "WARNING", -#endif NULL); GNUNET_TRANSPORT_TESTING_get_test_source_name (__FILE__, &test_source); diff --git a/src/transport/test_transport_api_unreliability_constant.c b/src/transport/test_transport_api_unreliability_constant.c index fb72b0f..cb24675 100644 --- a/src/transport/test_transport_api_unreliability_constant.c +++ b/src/transport/test_transport_api_unreliability_constant.c @@ -27,24 +27,10 @@ * achieve reliable message delivery. */ #include "platform.h" -#include "gnunet_common.h" -#include "gnunet_hello_lib.h" -#include "gnunet_getopt_lib.h" -#include "gnunet_os_lib.h" -#include "gnunet_program_lib.h" -#include "gnunet_scheduler_lib.h" -#include "gnunet_server_lib.h" #include "gnunet_transport_service.h" #include "gauger.h" -#include "transport.h" #include "transport-testing.h" -#define VERBOSE GNUNET_NO - -#define VERBOSE_ARM GNUNET_NO - -#define START_ARM GNUNET_YES - /** * Testcase timeout */ @@ -464,18 +450,12 @@ check () static char *const argv[] = { "test-transport-api-unreliability-constant", "-c", "test_transport_api_data.conf", -#if VERBOSE - "-L", "DEBUG", -#endif NULL }; static struct GNUNET_GETOPT_CommandLineOption options[] = { GNUNET_GETOPT_OPTION_END }; -#if WRITECONFIG - setTransportOptions ("test_transport_api_data.conf"); -#endif ok = GNUNET_SYSERR; GNUNET_PROGRAM_run ((sizeof (argv) / sizeof (char *)) - 1, argv, test_name, @@ -492,11 +472,7 @@ main (int argc, char *argv[]) GNUNET_TRANSPORT_TESTING_get_test_name (argv[0], &test_name); GNUNET_log_setup (test_name, -#if VERBOSE - "DEBUG", -#else "WARNING", -#endif NULL); GNUNET_TRANSPORT_TESTING_get_test_source_name (__FILE__, &test_source); diff --git a/src/transport/test_transport_api_unreliability_constant_udp_peer1.conf b/src/transport/test_transport_api_unreliability_constant_udp_peer1.conf index d872f02..a4fd104 100644 --- a/src/transport/test_transport_api_unreliability_constant_udp_peer1.conf +++ b/src/transport/test_transport_api_unreliability_constant_udp_peer1.conf @@ -1,7 +1,6 @@ @INLINE@ template_cfg_peer1.conf [PATHS] SERVICEHOME = /tmp/test-transport/api-udp-p1/ -DEFAULTCONFIG = test_transport_api_unreliability_constant_udp_peer1.conf [transport-udp] PORT = 12040 diff --git a/src/transport/test_transport_api_unreliability_constant_udp_peer2.conf b/src/transport/test_transport_api_unreliability_constant_udp_peer2.conf index 50ee65a..755e65d 100644 --- a/src/transport/test_transport_api_unreliability_constant_udp_peer2.conf +++ b/src/transport/test_transport_api_unreliability_constant_udp_peer2.conf @@ -1,7 +1,6 @@ @INLINE@ template_cfg_peer2.conf [PATHS] SERVICEHOME = /tmp/test-transport/api-udp-p2/ -DEFAULTCONFIG = test_transport_api_unreliability_constant_udp_peer2.conf [transport-udp] PORT = 12050 diff --git a/src/transport/test_transport_api_unreliability_udp_peer1.conf b/src/transport/test_transport_api_unreliability_udp_peer1.conf index 8a5a405..b9669bf 100644 --- a/src/transport/test_transport_api_unreliability_udp_peer1.conf +++ b/src/transport/test_transport_api_unreliability_udp_peer1.conf @@ -1,7 +1,6 @@ @INLINE@ template_cfg_peer1.conf [PATHS] SERVICEHOME = /tmp/test-transport/api-udp-p1/ -DEFAULTCONFIG = test_transport_api_unreliability_udp_peer1.conf [transport-udp] PORT = 12040 diff --git a/src/transport/test_transport_api_unreliability_udp_peer2.conf b/src/transport/test_transport_api_unreliability_udp_peer2.conf index d240c42..46ad017 100644 --- a/src/transport/test_transport_api_unreliability_udp_peer2.conf +++ b/src/transport/test_transport_api_unreliability_udp_peer2.conf @@ -1,7 +1,6 @@ @INLINE@ template_cfg_peer2.conf [PATHS] SERVICEHOME = /tmp/test-transport/api-udp-p2/ -DEFAULTCONFIG = test_transport_api_unreliability_udp_peer2.conf [transport-udp] PORT = 12050 diff --git a/src/transport/test_transport_api_unreliability_unix_peer1.conf b/src/transport/test_transport_api_unreliability_unix_peer1.conf index 8689e41..5d0235f 100644 --- a/src/transport/test_transport_api_unreliability_unix_peer1.conf +++ b/src/transport/test_transport_api_unreliability_unix_peer1.conf @@ -1,7 +1,6 @@ @INLINE@ template_cfg_peer1.conf [PATHS] SERVICEHOME = /tmp/test-transport/api-unix-p1/ -DEFAULTCONFIG = test_transport_api_unreliability_unix_peer1.conf [arm] PORT = 12125 diff --git a/src/transport/test_transport_api_unreliability_unix_peer2.conf b/src/transport/test_transport_api_unreliability_unix_peer2.conf index 7c3cc19..c9dab48 100644 --- a/src/transport/test_transport_api_unreliability_unix_peer2.conf +++ b/src/transport/test_transport_api_unreliability_unix_peer2.conf @@ -1,7 +1,6 @@ @INLINE@ template_cfg_peer2.conf [PATHS] SERVICEHOME = /tmp/test-transport/api-unix-p2/ -DEFAULTCONFIG = test_transport_api_unreliability_unix_peer2.conf [arm] PORT = 12135 diff --git a/src/transport/test_transport_api_unreliability_wlan_peer1.conf b/src/transport/test_transport_api_unreliability_wlan_peer1.conf index 9dd9d1b..e81a3f9 100644 --- a/src/transport/test_transport_api_unreliability_wlan_peer1.conf +++ b/src/transport/test_transport_api_unreliability_wlan_peer1.conf @@ -1,7 +1,6 @@ @INLINE@ template_cfg_peer1.conf [PATHS] SERVICEHOME = /tmp/test-transport/api-wlan-p1/ -DEFAULTCONFIG = test_transport_api_wlan_peer1.conf [transport-wlan] TESTMODE = 1 diff --git a/src/transport/test_transport_api_unreliability_wlan_peer2.conf b/src/transport/test_transport_api_unreliability_wlan_peer2.conf index bc868d7..bd53876 100644 --- a/src/transport/test_transport_api_unreliability_wlan_peer2.conf +++ b/src/transport/test_transport_api_unreliability_wlan_peer2.conf @@ -1,7 +1,6 @@ @INLINE@ template_cfg_peer2.conf [PATHS] SERVICEHOME = /tmp/test-transport/api-wlan-p2/ -DEFAULTCONFIG = test_transport_api_wlan_peer2.conf [transport-wlan] INTERFACE = mon1 diff --git a/src/transport/test_transport_api_wlan_peer1.conf b/src/transport/test_transport_api_wlan_peer1.conf index e379cf0..3f12ce5 100644 --- a/src/transport/test_transport_api_wlan_peer1.conf +++ b/src/transport/test_transport_api_wlan_peer1.conf @@ -1,14 +1,12 @@ @INLINE@ template_cfg_peer1.conf [PATHS] SERVICEHOME = /tmp/test-transport/api-wlan-p1/ -DEFAULTCONFIG = test_transport_api_wlan_peer1.conf [transport-wlan] INTERFACE = mon0 TESTMODE = 1 [arm] -DEBUG = YES PORT = 12164 UNIXPATH = /tmp/gnunet-p1-service-arm.sock @@ -27,7 +25,6 @@ UNIXPATH = /tmp/gnunet-p1-service-peerinfo.sock [transport] PORT = 12160 PLUGINS = wlan -#DEBUG = YES UNIXPATH = /tmp/gnunet-p1-service-transport.sock #PREFIX = xterm -T transport2 -e gdb --command=cmd --args #PREFIX = valgrind --leak-check=full --show-reachable=yes --main-stacksize=104857600 diff --git a/src/transport/test_transport_api_wlan_peer2.conf b/src/transport/test_transport_api_wlan_peer2.conf index 3e0ce27..451a2a6 100644 --- a/src/transport/test_transport_api_wlan_peer2.conf +++ b/src/transport/test_transport_api_wlan_peer2.conf @@ -1,7 +1,6 @@ @INLINE@ template_cfg_peer2.conf [PATHS] SERVICEHOME = /tmp/test-transport/api-wlan-p2/ -DEFAULTCONFIG = test_transport_api_wlan_peer2.conf [transport-wlan] INTERFACE = mon1 @@ -9,7 +8,6 @@ TESTMODE = 2 [arm] PORT = 12174 -DEBUG = YES UNIXPATH = /tmp/gnunet-p2-service-arm.sock [statistics] @@ -27,7 +25,6 @@ UNIXPATH = /tmp/gnunet-p2-service-peerinfo.sock [transport] PORT = 12170 PLUGINS = wlan -#DEBUG = YES UNIXPATH = /tmp/gnunet-p2-service-transport.sock #PREFIX = xterm -T transport2 -e gdb --command=cmd --args #PREFIX = valgrind --leak-check=full --show-reachable=yes --main-stacksize=104857600 diff --git a/src/transport/test_transport_defaults.conf b/src/transport/test_transport_defaults.conf index 0939a79..48814b7 100644 --- a/src/transport/test_transport_defaults.conf +++ b/src/transport/test_transport_defaults.conf @@ -1,6 +1,5 @@ [PATHS] SERVICEHOME = /tmp/test-transport-api/ -DEFAULTCONFIG = test_transport_defaults.conf [transport-tcp] TIMEOUT = 300 s @@ -50,6 +49,9 @@ AUTOSTART = NO [lockmanager] AUTOSTART = NO +[consensus] +AUTOSTART = NO + [nat] DISABLEV6 = YES BINDTO = 127.0.0.1 diff --git a/src/transport/test_transport_startonly.c b/src/transport/test_transport_startonly.c index 79578ab..8a8fef1 100644 --- a/src/transport/test_transport_startonly.c +++ b/src/transport/test_transport_startonly.c @@ -27,22 +27,9 @@ * C code apparently. */ #include "platform.h" -#include "gnunet_common.h" -#include "gnunet_hello_lib.h" -#include "gnunet_getopt_lib.h" -#include "gnunet_os_lib.h" -#include "gnunet_program_lib.h" -#include "gnunet_scheduler_lib.h" #include "gnunet_transport_service.h" -#include "transport.h" #include "transport-testing.h" -#define VERBOSE GNUNET_NO - -#define VERBOSE_ARM GNUNET_NO - -#define START_ARM GNUNET_YES - /** * How long until we give up on transmitting the message? */ @@ -72,6 +59,7 @@ end () GNUNET_SCHEDULER_cancel (timeout_task); timeout_task = GNUNET_SCHEDULER_NO_TASK; } + GNUNET_TRANSPORT_TESTING_done (tth); GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Exiting\n"); } @@ -86,7 +74,8 @@ end_badly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) if (p1 != NULL) GNUNET_TRANSPORT_TESTING_stop_peer (tth, p1); - + if (NULL != tth) + GNUNET_TRANSPORT_TESTING_done (tth); ret = GNUNET_SYSERR; } @@ -150,8 +139,6 @@ run (void *cls, char *const *args, const char *cfgfile, FPRINTF (stderr, "..%i", i); } - tth = GNUNET_TRANSPORT_TESTING_init (); - FPRINTF (stderr, "%s", "\n"); end (); } @@ -160,19 +147,13 @@ int main (int argc, char *argv[]) { GNUNET_log_setup ("test_transport_testing", -#if VERBOSE - "DEBUG", -#else "WARNING", -#endif + NULL); char *const argv_1[] = { "test_transport_testing", "-c", "test_transport_api_data.conf", -#if VERBOSE - "-L", "DEBUG", -#endif NULL }; diff --git a/src/transport/test_transport_startonly.conf b/src/transport/test_transport_startonly.conf index 255df4c..8e16138 100644 --- a/src/transport/test_transport_startonly.conf +++ b/src/transport/test_transport_startonly.conf @@ -1,6 +1,5 @@ @INLINE@ test_transport_defaults.conf [PATHS] -DEFAULTCONFIG = test_transport_api_data.conf [arm] DEFAULTSERVICES = transport diff --git a/src/transport/test_transport_testing.c b/src/transport/test_transport_testing.c index 842d686..9db5913 100644 --- a/src/transport/test_transport_testing.c +++ b/src/transport/test_transport_testing.c @@ -27,22 +27,8 @@ * C code apparently. */ #include "platform.h" -#include "gnunet_common.h" -#include "gnunet_hello_lib.h" -#include "gnunet_getopt_lib.h" -#include "gnunet_os_lib.h" -#include "gnunet_program_lib.h" -#include "gnunet_scheduler_lib.h" #include "gnunet_transport_service.h" -#include "transport.h" #include "transport-testing.h" - -#define VERBOSE GNUNET_NO - -#define VERBOSE_ARM GNUNET_NO - -#define START_ARM GNUNET_YES - /** * How long until we give up on transmitting the message? */ @@ -81,12 +67,19 @@ end_badly () timeout_task = GNUNET_SCHEDULER_NO_TASK; GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Fail! Stopping peers\n"); + if (NULL != cc) + { + GNUNET_TRANSPORT_TESTING_connect_peers_cancel (tth, cc); + cc = NULL; + } + if (p1 != NULL) GNUNET_TRANSPORT_TESTING_stop_peer (tth, p1); if (p2 != NULL) GNUNET_TRANSPORT_TESTING_stop_peer (tth, p2); - GNUNET_TRANSPORT_TESTING_done (tth); + if (NULL != tth) + GNUNET_TRANSPORT_TESTING_done (tth); ret = GNUNET_SYSERR; } @@ -167,15 +160,11 @@ run (void *cls, char *const *args, const char *cfgfile, 1, ¬ify_receive, ¬ify_connect, ¬ify_disconnect, &start_cb, p1); - GNUNET_assert (p1->hostkeyfile != NULL); - p2 = GNUNET_TRANSPORT_TESTING_start_peer (tth, "test_transport_api_tcp_peer2.conf", 2, ¬ify_receive, ¬ify_connect, ¬ify_disconnect, &start_cb, p2); - GNUNET_assert (p2->hostkeyfile != NULL); - if (p1 == NULL) { GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, @@ -198,19 +187,12 @@ int main (int argc, char *argv[]) { GNUNET_log_setup ("test_transport_testing", -#if VERBOSE - "DEBUG", -#else "WARNING", -#endif NULL); char *const argv_1[] = { "test_transport_testing", "-c", "test_transport_api_data.conf", -#if VERBOSE - "-L", "DEBUG", -#endif NULL }; diff --git a/src/transport/test_transport_testing_restart.c b/src/transport/test_transport_testing_restart.c new file mode 100644 index 0000000..8ca18f9 --- /dev/null +++ b/src/transport/test_transport_testing_restart.c @@ -0,0 +1,151 @@ +/* + This file is part of GNUnet. + (C) 2009, 2010 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ +/** + * @file transport/test_transport_testing_restart.c + * @brief test case for transport testing library: + * start the peer, get the HELLO message, restart and stop the peer + * + */ +#include "platform.h" +#include "gnunet_transport_service.h" +#include "transport-testing.h" + +/** + * How long until we give up on transmitting the message? + */ +#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 30) + +GNUNET_SCHEDULER_TaskIdentifier timeout_task; + +static struct PeerContext *p; + +struct GNUNET_TRANSPORT_TESTING_handle *tth; + +static int ret = 0; + +static void +end () +{ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stopping peers\n"); + + if (timeout_task != GNUNET_SCHEDULER_NO_TASK) + GNUNET_SCHEDULER_cancel (timeout_task); + + GNUNET_TRANSPORT_TESTING_stop_peer (tth, p); + GNUNET_TRANSPORT_TESTING_done (tth); +} + +static void +end_badly () +{ + timeout_task = GNUNET_SCHEDULER_NO_TASK; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Fail! Stopping peers\n"); + + if (NULL != p) + GNUNET_TRANSPORT_TESTING_stop_peer (tth, p); + + if (NULL != tth) + GNUNET_TRANSPORT_TESTING_done (tth); + + ret = GNUNET_SYSERR; +} + +static void +restart_cb (struct PeerContext *p, void *cls) +{ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Peer %u (`%s') successfully restarted\n", + p->no, + GNUNET_i2s (&p->id)); + + ret = 0; + GNUNET_SCHEDULER_add_now (&end, NULL); +} + + +static void +restart_task () +{ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Peer %u (`%s') restarting, \n", + p->no, + GNUNET_i2s (&p->id)); + GNUNET_TRANSPORT_TESTING_restart_peer (tth, p, NULL, restart_cb, p); +} + +static void +start_cb (struct PeerContext *p, void *cls) +{ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Peer %u (`%s') successfully started\n", + p->no, + GNUNET_i2s (&p->id)); + + GNUNET_SCHEDULER_add_now (&restart_task, NULL); +} + + +static void +run (void *cls, char *const *args, const char *cfgfile, + const struct GNUNET_CONFIGURATION_Handle *cfg) +{ + ret = 1; + tth = GNUNET_TRANSPORT_TESTING_init (); + GNUNET_assert (NULL != tth); + + timeout_task = + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_MINUTES, &end_badly, NULL); + + p = GNUNET_TRANSPORT_TESTING_start_peer(tth, cfgfile, 1, + NULL, /* receive cb */ + NULL, /* connect cb */ + NULL, /* disconnect cb */ + start_cb, /* startup cb */ + NULL); /* closure */ + if (NULL == p) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Failed to start peer\n"); + if (timeout_task != GNUNET_SCHEDULER_NO_TASK) + GNUNET_SCHEDULER_cancel (timeout_task); + timeout_task = GNUNET_SCHEDULER_add_now (&end_badly, NULL); + } +} + +int +main (int argc, char *argv[]) +{ + GNUNET_log_setup ("test_transport_testing_restart", + "WARNING", + NULL); + + char *const argv_1[] = { "test_transport_testing_restart", + "-c", + "test_transport_api_data.conf", + NULL + }; + + struct GNUNET_GETOPT_CommandLineOption options[] = { + GNUNET_GETOPT_OPTION_END + }; + + GNUNET_PROGRAM_run ((sizeof (argv_1) / sizeof (char *)) - 1, argv_1, + "test_transport_testing_restart", "nohelp", options, &run, &ret); + + return ret; +} + +/* end of test_transport_testing_restart.c */ diff --git a/src/transport/test_transport_testing_startstop.c b/src/transport/test_transport_testing_startstop.c new file mode 100644 index 0000000..22a4e51 --- /dev/null +++ b/src/transport/test_transport_testing_startstop.c @@ -0,0 +1,132 @@ +/* + This file is part of GNUnet. + (C) 2009, 2010 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ +/** + * @file transport/test_transport_testing_startstop.c + * @brief test case for transport testing library: + * start the peer, get the HELLO message and stop the peer + * + */ +#include "platform.h" +#include "gnunet_transport_service.h" +#include "transport-testing.h" + +/** + * How long until we give up on transmitting the message? + */ +#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 30) + +GNUNET_SCHEDULER_TaskIdentifier timeout_task; + +static struct PeerContext *p; + +struct GNUNET_TRANSPORT_TESTING_handle *tth; + +static int ret = 0; + +static void +end () +{ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stopping peers\n"); + + if (timeout_task != GNUNET_SCHEDULER_NO_TASK) + GNUNET_SCHEDULER_cancel (timeout_task); + + GNUNET_TRANSPORT_TESTING_stop_peer (tth, p); + GNUNET_TRANSPORT_TESTING_done (tth); +} + +static void +end_badly () +{ + timeout_task = GNUNET_SCHEDULER_NO_TASK; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Fail! Stopping peers\n"); + + if (NULL != p) + GNUNET_TRANSPORT_TESTING_stop_peer (tth, p); + + if (NULL != tth) + GNUNET_TRANSPORT_TESTING_done (tth); + + ret = GNUNET_SYSERR; +} + + +static void +start_cb (struct PeerContext *p, void *cls) +{ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Peer %u (`%s') successfully started\n", + p->no, + GNUNET_i2s (&p->id)); + + ret = 0; + GNUNET_SCHEDULER_add_now (&end, NULL); +} + + +static void +run (void *cls, char *const *args, const char *cfgfile, + const struct GNUNET_CONFIGURATION_Handle *cfg) +{ + ret = 1; + tth = GNUNET_TRANSPORT_TESTING_init (); + GNUNET_assert (NULL != tth); + + timeout_task = + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_MINUTES, &end_badly, NULL); + + p = GNUNET_TRANSPORT_TESTING_start_peer(tth, cfgfile, 1, + NULL, /* receive cb */ + NULL, /* connect cb */ + NULL, /* disconnect cb */ + start_cb, /* startup cb */ + NULL); /* closure */ + if (NULL == p) + { + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Failed to start peer\n"); + if (timeout_task != GNUNET_SCHEDULER_NO_TASK) + GNUNET_SCHEDULER_cancel (timeout_task); + timeout_task = GNUNET_SCHEDULER_add_now (&end_badly, NULL); + } +} + +int +main (int argc, char *argv[]) +{ + GNUNET_log_setup ("test_transport_testing_startstop", + "WARNING", + NULL); + + char *const argv_1[] = { "test_transport_testing", + "-c", + "test_transport_api_data.conf", + NULL + }; + + struct GNUNET_GETOPT_CommandLineOption options[] = { + GNUNET_GETOPT_OPTION_END + }; + + GNUNET_PROGRAM_run ((sizeof (argv_1) / sizeof (char *)) - 1, argv_1, + "test_transport_testing_startstop", "nohelp", options, &run, &ret); + + return ret; +} + +/* end of test_transport_testing_startstop.c */ diff --git a/src/transport/transport-testing.c b/src/transport/transport-testing.c index 695c048..32331d9 100644 --- a/src/transport/transport-testing.c +++ b/src/transport/transport-testing.c @@ -27,31 +27,6 @@ #include "transport-testing.h" -#define HOSTKEYFILESIZE 914 - -static const char * -get_host_key (struct GNUNET_TRANSPORT_TESTING_handle *tth) -{ - if (tth->hostkey_data == NULL) - { - GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, "transport-testing", - "No precomputed hostkeys available\n"); - return NULL; - } - if (tth->hostkeys_total > tth->hostkeys_last) - { - tth->hostkeys_last++; - GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, "transport-testing", - "Used hostkey %u of %u available hostkeys\n", - tth->hostkeys_last, tth->hostkeys_total); - return &tth->hostkey_data[(tth->hostkeys_last - 1) * HOSTKEYFILESIZE]; - } - GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, "transport-testing", - "No hostkey available (%u of %u already used)\n", - tth->hostkeys_last, tth->hostkeys_total); - return NULL; -} - static struct PeerContext * find_peer_context (struct GNUNET_TRANSPORT_TESTING_handle *tth, @@ -96,19 +71,15 @@ notify_connect (void *cls, const struct GNUNET_PeerIdentity *peer, const struct GNUNET_ATS_Information *ats, uint32_t ats_count) { struct PeerContext *p = cls; + char *p2_s; + struct PeerContext *p2; - /* Find PeerContext */ - GNUNET_assert (p != 0); - GNUNET_assert (p->tth != NULL); - struct PeerContext *p2 = find_peer_context (p->tth, peer); - - if (p == NULL) - return; + GNUNET_assert (NULL != p); + GNUNET_assert (NULL != p->tth); + p2 = find_peer_context (p->tth, peer); if (p->nc != NULL) p->nc (p->cb_cls, peer, ats, ats_count); - char *p2_s; - if (p2 != NULL) GNUNET_asprintf (&p2_s, "%u (`%s')", p2->no, GNUNET_i2s (&p2->id)); else @@ -190,20 +161,21 @@ static void get_hello (void *cb_cls, const struct GNUNET_MessageHeader *message) { struct PeerContext *p = cb_cls; + struct GNUNET_PeerIdentity hello_id; GNUNET_assert (message != NULL); GNUNET_assert (GNUNET_OK == GNUNET_HELLO_get_id ((const struct GNUNET_HELLO_Message *) - message, &p->id)); + message, &hello_id)); + GNUNET_assert (0 == memcmp (&hello_id, &p->id, sizeof (hello_id))); GNUNET_free_non_null (p->hello); p->hello = (struct GNUNET_HELLO_Message *) GNUNET_copy_message (message); - if (p->start_cb != NULL) + if (NULL != p->start_cb) { GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, "transport-testing", "Peer %u (`%s') successfully started\n", p->no, GNUNET_i2s (&p->id)); - p->start_cb (p, p->cb_cls); p->start_cb = NULL; } @@ -236,7 +208,7 @@ try_connect (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) GNUNET_TRANSPORT_offer_hello (cc->th_p1, (const struct GNUNET_MessageHeader *) cc-> p2->hello, NULL, NULL); - GNUNET_TRANSPORT_try_connect (cc->th_p1, &p2->id); + GNUNET_TRANSPORT_try_connect (cc->th_p1, &p2->id, NULL, NULL); /*FIXME TRY_CONNECT change */ cc->tct = GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_SECONDS, &try_connect, cc); @@ -247,7 +219,7 @@ try_connect (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) * Start a peer with the given configuration * @param tth the testing handle * @param cfgname configuration file - * @param peer_id the peer_id + * @param peer_id a unique number to identify the peer * @param rec receive callback * @param nc connect callback * @param nd disconnect callback @@ -256,18 +228,20 @@ try_connect (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) * @return the peer context */ struct PeerContext * -GNUNET_TRANSPORT_TESTING_start_peer (struct GNUNET_TRANSPORT_TESTING_handle - *tth, const char *cfgname, int peer_id, +GNUNET_TRANSPORT_TESTING_start_peer (struct GNUNET_TRANSPORT_TESTING_handle *tth, + const char *cfgname, int peer_id, GNUNET_TRANSPORT_ReceiveCallback rec, GNUNET_TRANSPORT_NotifyConnect nc, GNUNET_TRANSPORT_NotifyDisconnect nd, GNUNET_TRANSPORT_TESTING_start_cb start_cb, void *cb_cls) { - const char *hostkey = NULL; - struct GNUNET_DISK_FileHandle *fn; + char *emsg = NULL; + struct GNUNET_PeerIdentity *dummy; + + GNUNET_assert (NULL != tth); + GNUNET_assert (NULL != tth->tl_system); - GNUNET_assert (tth != NULL); if (GNUNET_DISK_file_test (cfgname) == GNUNET_NO) { GNUNET_log_from (GNUNET_ERROR_TYPE_ERROR, "transport-testing", @@ -276,47 +250,61 @@ GNUNET_TRANSPORT_TESTING_start_peer (struct GNUNET_TRANSPORT_TESTING_handle } struct PeerContext *p = GNUNET_malloc (sizeof (struct PeerContext)); + GNUNET_CONTAINER_DLL_insert (tth->p_head, tth->p_tail, p); + /* Create configuration and call testing lib to modify it */ p->cfg = GNUNET_CONFIGURATION_create (); GNUNET_assert (GNUNET_OK == GNUNET_CONFIGURATION_load (p->cfg, cfgname)); - if (GNUNET_CONFIGURATION_have_value (p->cfg, "PATHS", "SERVICEHOME")) - GNUNET_assert (GNUNET_OK == - GNUNET_CONFIGURATION_get_value_string (p->cfg, "PATHS", - "SERVICEHOME", - &p->servicehome)); - - if (NULL != p->servicehome) - GNUNET_DISK_directory_remove (p->servicehome); + if (GNUNET_SYSERR == GNUNET_TESTING_configuration_create (tth->tl_system, p->cfg)) + { + GNUNET_log_from (GNUNET_ERROR_TYPE_ERROR, "transport-testing", + "Testing library failed to create unique configuration based on `%s'\n", + cfgname); + GNUNET_free (p); + return NULL; + } - hostkey = get_host_key (tth); - if (hostkey != NULL) + p->no = peer_id; + /* Configure peer with configuration */ + p->peer = GNUNET_TESTING_peer_configure (tth->tl_system, p->cfg, p->no, NULL, &emsg); + if (NULL == p->peer) + { + GNUNET_log_from (GNUNET_ERROR_TYPE_ERROR, "transport-testing", + "Testing library failed to create unique configuration based on `%s': `%s'\n", + cfgname, emsg); + GNUNET_TRANSPORT_TESTING_stop_peer (tth, p); + GNUNET_free_non_null (emsg); + return NULL; + } + GNUNET_free_non_null (emsg); + if (GNUNET_OK != GNUNET_TESTING_peer_start (p->peer)) { + GNUNET_log_from (GNUNET_ERROR_TYPE_ERROR, "transport-testing", + "Testing library failed to create unique configuration based on `%s'\n", + cfgname); + GNUNET_TRANSPORT_TESTING_stop_peer (tth, p); + return NULL; + } - GNUNET_asprintf (&p->hostkeyfile, "%s/.hostkey", p->servicehome); - GNUNET_assert (GNUNET_OK == - GNUNET_DISK_directory_create_for_file (p->hostkeyfile)); - fn = GNUNET_DISK_file_open (p->hostkeyfile, - GNUNET_DISK_OPEN_READWRITE | - GNUNET_DISK_OPEN_CREATE, - GNUNET_DISK_PERM_USER_READ | - GNUNET_DISK_PERM_USER_WRITE); - GNUNET_assert (fn != NULL); - GNUNET_assert (HOSTKEYFILESIZE == - GNUNET_DISK_file_write (fn, hostkey, HOSTKEYFILESIZE)); - GNUNET_assert (GNUNET_OK == GNUNET_DISK_file_close (fn)); + memset(&dummy, '\0', sizeof (dummy)); + GNUNET_TESTING_peer_get_identity (p->peer, &p->id); + if (0 == memcmp (&dummy, &p->id, sizeof (struct GNUNET_PeerIdentity))) + { + GNUNET_log_from (GNUNET_ERROR_TYPE_ERROR, "transport-testing", + "Testing library failed to obtain peer identity for peer %u\n", + p->no); + GNUNET_TRANSPORT_TESTING_stop_peer (tth, p); + return NULL; + } + else + { GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, "transport-testing", - "Wrote hostkey to file: `%s' \n", p->hostkeyfile); + "Peer %u configured with identity `%s'\n", + p->no, + GNUNET_i2s (&p->id)); } - p->arm_proc = - GNUNET_OS_start_process (GNUNET_YES, - NULL, NULL, "gnunet-service-arm", - "gnunet-service-arm", "-c", cfgname, - "-L", "ERROR", - NULL); - - p->no = peer_id; p->tth = tth; p->nc = nc; p->nd = nd; @@ -327,15 +315,21 @@ GNUNET_TRANSPORT_TESTING_start_peer (struct GNUNET_TRANSPORT_TESTING_handle else p->cb_cls = p; - p->th = - GNUNET_TRANSPORT_connect (p->cfg, NULL, p, ¬ify_receive, - ¬ify_connect, ¬ify_disconnect); - GNUNET_assert (p->th != NULL); + p->th = GNUNET_TRANSPORT_connect (p->cfg, NULL, p, + ¬ify_receive, + ¬ify_connect, ¬ify_disconnect); + if (NULL == p->th) + { + GNUNET_log_from (GNUNET_ERROR_TYPE_ERROR, "transport-testing", + "Failed to connect to transport service for peer `%s': `%s'\n", + cfgname, emsg); + GNUNET_TRANSPORT_TESTING_stop_peer (tth, p); + return NULL; + } p->ghh = GNUNET_TRANSPORT_get_hello (p->th, &get_hello, p); GNUNET_assert (p->ghh != NULL); - GNUNET_CONTAINER_DLL_insert (tth->p_head, tth->p_tail, p); return p; } @@ -355,93 +349,55 @@ GNUNET_TRANSPORT_TESTING_restart_peer (struct GNUNET_TRANSPORT_TESTING_handle GNUNET_TRANSPORT_TESTING_start_cb restart_cb, void *cb_cls) { - struct GNUNET_DISK_FileHandle *fn; - GNUNET_assert (tth != NULL); GNUNET_assert (p != NULL); - GNUNET_assert (p->hostkeyfile != NULL); - GNUNET_assert (p->servicehome != NULL); + GNUNET_assert (NULL != p->peer); + + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, "transport-testing", + "Restarting peer %u (`%s')\n", p->no, GNUNET_i2s (&p->id)); /* shutdown */ GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, "transport-testing", "Stopping peer %u (`%s')\n", p->no, GNUNET_i2s (&p->id)); - if (p->ghh != NULL) + if (NULL != p->ghh) GNUNET_TRANSPORT_get_hello_cancel (p->ghh); p->ghh = NULL; - if (p->th != NULL) + if (NULL != p->th) GNUNET_TRANSPORT_disconnect (p->th); - if (NULL != p->arm_proc) + if (GNUNET_SYSERR == GNUNET_TESTING_peer_stop(p->peer)) { - if (0 != GNUNET_OS_process_kill (p->arm_proc, SIGTERM)) - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); - GNUNET_OS_process_wait (p->arm_proc); - GNUNET_OS_process_destroy (p->arm_proc); - p->arm_proc = NULL; + GNUNET_log_from (GNUNET_ERROR_TYPE_ERROR, "transport-testing", + "Failed to stop peer %u (`%s')\n", p->no, GNUNET_i2s (&p->id)); + return GNUNET_SYSERR; } - if (p->hello != NULL) - GNUNET_free (p->hello); - p->hello = NULL; - if (p->cfg != NULL) - GNUNET_CONFIGURATION_destroy (p->cfg); - p->cfg = NULL; + sleep (5); - - /* start */ - GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, "transport-testing", - "Restarting peer %u (`%s')\n", p->no, GNUNET_i2s (&p->id)); - sleep (5); // YUCK! - - if (GNUNET_DISK_file_test (cfgname) == GNUNET_NO) + /* restart */ + if (GNUNET_SYSERR == GNUNET_TESTING_peer_start(p->peer)) { GNUNET_log_from (GNUNET_ERROR_TYPE_ERROR, "transport-testing", - "File not found: `%s' \n", cfgname); - goto fail; + "Failed to restart peer %u (`%s')\n", + p->no, GNUNET_i2s (&p->id)); + return GNUNET_SYSERR; } - p->cfg = GNUNET_CONFIGURATION_create (); - GNUNET_assert (GNUNET_OK == GNUNET_CONFIGURATION_load (p->cfg, cfgname)); - - if (!GNUNET_CONFIGURATION_have_value (p->cfg, "PATHS", "SERVICEHOME")) - goto fail; - - fn = GNUNET_DISK_file_open (p->hostkeyfile, - GNUNET_DISK_OPEN_READWRITE | - GNUNET_DISK_OPEN_CREATE, - GNUNET_DISK_PERM_USER_READ | - GNUNET_DISK_PERM_USER_WRITE); - if (fn == NULL) - goto fail; - if (GNUNET_OK != GNUNET_DISK_file_close (fn)) - goto fail; - - p->arm_proc = - GNUNET_OS_start_process (GNUNET_YES, - NULL, NULL, "gnunet-service-arm", - "gnunet-service-arm", "-c", cfgname, - "-L", "ERROR", - NULL); - - p->th = - GNUNET_TRANSPORT_connect (p->cfg, NULL, p, ¬ify_receive, - ¬ify_connect, ¬ify_disconnect); GNUNET_assert (p->th != NULL); - + GNUNET_assert (p->start_cb == NULL); p->start_cb = restart_cb; p->cb_cls = cb_cls; + p->th = GNUNET_TRANSPORT_connect (p->cfg, NULL, p, + ¬ify_receive, + ¬ify_connect, + ¬ify_disconnect); + GNUNET_assert (NULL != p->th); + p->ghh = GNUNET_TRANSPORT_get_hello (p->th, &get_hello, p); GNUNET_assert (p->ghh != NULL); return GNUNET_OK; - -fail: - GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, "transport-testing", - "Restarting peer %u (`%s') failed, removing peer\n", p->no, - GNUNET_i2s (&p->id)); - GNUNET_TRANSPORT_TESTING_stop_peer (tth, p); - return GNUNET_SYSERR; } @@ -461,25 +417,23 @@ GNUNET_TRANSPORT_TESTING_stop_peer (struct GNUNET_TRANSPORT_TESTING_handle *tth, p->ghh = NULL; } if (p->th != NULL) - GNUNET_TRANSPORT_disconnect (p->th); - if (NULL != p->arm_proc) - { - if (0 != GNUNET_OS_process_kill (p->arm_proc, SIGTERM)) - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); - GNUNET_OS_process_wait (p->arm_proc); - GNUNET_OS_process_destroy (p->arm_proc); - p->arm_proc = NULL; - } - if (p->hostkeyfile != NULL) { - GNUNET_DISK_directory_remove (p->hostkeyfile); - GNUNET_free (p->hostkeyfile); + GNUNET_TRANSPORT_disconnect (p->th); + p->th = NULL; } - if (p->servicehome != NULL) + + if (p->peer != NULL) { - GNUNET_DISK_directory_remove (p->servicehome); - GNUNET_free (p->servicehome); + if (GNUNET_OK != GNUNET_TESTING_peer_stop (p->peer)) + { + GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, "transport-testing", + "Testing lib failed to stop peer %u (`%s') \n", p->no, + GNUNET_i2s (&p->id)); + } + GNUNET_TESTING_peer_destroy (p->peer); + p->peer = NULL; } + if (p->hello != NULL) { GNUNET_free (p->hello); @@ -499,9 +453,9 @@ GNUNET_TRANSPORT_TESTING_stop_peer (struct GNUNET_TRANSPORT_TESTING_handle *tth, /** - * Connect the given peers and call the callback when both peers report the - * inbound connection. Remarks: start_peer's notify_connect callback can be called - * before. + * Initiate a connection from p1 to p2 by offering p1 p2's HELLO message + * + * Remarks: start_peer's notify_connect callback can be called before. * * @param tth transport testing handle * @param p1 peer 1 @@ -538,7 +492,7 @@ GNUNET_TRANSPORT_TESTING_connect_peers (struct GNUNET_TRANSPORT_TESTING_handle * GNUNET_CONTAINER_DLL_insert (tth->cc_head, tth->cc_tail, cc); cc->tct = GNUNET_SCHEDULER_add_now (&try_connect, cc); GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, "transport-testing", - "New connect request %X\n", cc); + "New connect request %p\n", cc); return cc; } @@ -563,7 +517,7 @@ GNUNET_TRANSPORT_TESTING_connect_peers_cancel (struct GNUNET_assert (tth != NULL); GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, "transport-testing", - "Canceling connect request %X!\n", cc); + "Canceling connect request %p!\n", cc); if (cc->tct != GNUNET_SCHEDULER_NO_TASK) GNUNET_SCHEDULER_cancel (cc->tct); @@ -592,7 +546,7 @@ GNUNET_TRANSPORT_TESTING_done (struct GNUNET_TRANSPORT_TESTING_handle *tth) { ct = cc->next; GNUNET_log_from (GNUNET_ERROR_TYPE_ERROR, "transport-testing", - "Developer forgot to cancel connect request %X!\n", cc); + "Developer forgot to cancel connect request %p!\n", cc); GNUNET_TRANSPORT_TESTING_connect_peers_cancel (tth, cc); cc = ct; } @@ -606,7 +560,7 @@ GNUNET_TRANSPORT_TESTING_done (struct GNUNET_TRANSPORT_TESTING_handle *tth) p = t; } - GNUNET_free_non_null (tth->hostkey_data); + GNUNET_TESTING_system_destroy (tth->tl_system, GNUNET_YES); GNUNET_free (tth); tth = NULL; @@ -621,50 +575,17 @@ struct GNUNET_TRANSPORT_TESTING_handle * GNUNET_TRANSPORT_TESTING_init () { struct GNUNET_TRANSPORT_TESTING_handle *tth; - struct GNUNET_DISK_FileHandle *fd; - uint64_t fs; - uint64_t total_hostkeys; - /* prepare hostkeys */ tth = GNUNET_malloc (sizeof (struct GNUNET_TRANSPORT_TESTING_handle)); - tth->hostkey_data = NULL; - const char *hostkeys_file = "../../contrib/testing_hostkeys.dat"; - if (GNUNET_YES != GNUNET_DISK_file_test (hostkeys_file)) - { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("Could not read hostkeys file!\n")); - } - else + /* Init testing the testing lib */ + tth->tl_system = GNUNET_TESTING_system_create ("transport-testing", NULL, NULL); + if (NULL == tth->tl_system) { - /* Check hostkey file size, read entire thing into memory */ - fd = GNUNET_DISK_file_open (hostkeys_file, GNUNET_DISK_OPEN_READ, - GNUNET_DISK_PERM_NONE); - if (NULL == fd) - { - GNUNET_log_strerror_file (GNUNET_ERROR_TYPE_ERROR, "open", hostkeys_file); - GNUNET_free (tth); - return NULL; - } - - if (GNUNET_OK != GNUNET_DISK_file_size (hostkeys_file, &fs, GNUNET_YES, GNUNET_YES)) - fs = 0; - - if (0 != (fs % HOSTKEYFILESIZE)) - { - GNUNET_log_from (GNUNET_ERROR_TYPE_ERROR, "transport-testing", - "File size %llu seems incorrect for hostkeys...\n", fs); - } - else - { - total_hostkeys = fs / HOSTKEYFILESIZE; - tth->hostkey_data = GNUNET_malloc_large (fs); - GNUNET_assert (fs == GNUNET_DISK_file_read (fd, tth->hostkey_data, fs)); - GNUNET_log_from (GNUNET_ERROR_TYPE_DEBUG, "transport-testing", - "Read %llu hostkeys from file\n", total_hostkeys); - tth->hostkeys_total = total_hostkeys; - } - GNUNET_assert (GNUNET_OK == GNUNET_DISK_file_close (fd)); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("Failed to initialize testing library!\n")); + GNUNET_free (tth); + return NULL; } return tth; @@ -687,7 +608,25 @@ extract_filename (const char *file) char *backup = pch; char *filename = NULL; char *res; - +#if WINDOWS + if ((strlen (pch) >= 3) && pch[1] == ':') + { + if (NULL != strstr (pch, "\\")) + { + pch = strtok (pch, "\\"); + while (pch != NULL) + { + pch = strtok (NULL, "\\"); + if (pch != NULL) + filename = pch; + } + } + } + if (filename != NULL) + pch = filename; /* If we miss the next condition, filename = pch will + * not harm us. + */ +#endif if (NULL != strstr (pch, "/")) { pch = strtok (pch, "/"); @@ -845,5 +784,4 @@ fail: } - /* end of transport-testing.c */ diff --git a/src/transport/transport-testing.h b/src/transport/transport-testing.h index 20e802d..d064ac5 100644 --- a/src/transport/transport-testing.h +++ b/src/transport/transport-testing.h @@ -27,12 +27,11 @@ #include "platform.h" #include "gnunet_common.h" -#include "gnunet_getopt_lib.h" #include "gnunet_hello_lib.h" -#include "gnunet_os_lib.h" #include "gnunet_program_lib.h" #include "gnunet_container_lib.h" #include "gnunet_transport_service.h" +#include "gnunet_testing_lib.h" #define GNUNET_TRANSPORT_TESTING_ConnectRequest void * @@ -59,7 +58,9 @@ typedef void (*GNUNET_TRANSPORT_TESTING_connect_cb) (struct PeerContext * p1, void *cls); - +/** + * Definition for a transport testing handle + */ struct GNUNET_TRANSPORT_TESTING_handle; /** @@ -67,37 +68,84 @@ struct GNUNET_TRANSPORT_TESTING_handle; */ struct PeerContext { + /** + * Next element in the DLL + */ struct PeerContext *next; + + /** + * Previous element in the DLL + */ struct PeerContext *prev; + /** + * Transport testing handle this peer belongs to + */ struct GNUNET_TRANSPORT_TESTING_handle *tth; + /** + * Peer's configuration + */ struct GNUNET_CONFIGURATION_Handle *cfg; + /** + * Peer's transport service handle + */ struct GNUNET_TRANSPORT_Handle *th; + /** + * Peer's transport get hello handle to retrieve peer's HELLO message + */ struct GNUNET_TRANSPORT_GetHelloHandle *ghh; + /** + * Peer's testing handle + */ + struct GNUNET_TESTING_Peer *peer; + + /** + * Peer identity + */ struct GNUNET_PeerIdentity id; + /** + * Handle for the peer's ARM process + */ struct GNUNET_OS_Process *arm_proc; + /** + * Receive callback + */ GNUNET_TRANSPORT_ReceiveCallback rec; + /** + * Notify connect callback + */ GNUNET_TRANSPORT_NotifyConnect nc; + /** + * Notify disconnect callback + */ GNUNET_TRANSPORT_NotifyDisconnect nd; + /** + * Startup completed callback + */ GNUNET_TRANSPORT_TESTING_start_cb start_cb; + /** + * Peers HELLO Message + */ struct GNUNET_HELLO_Message *hello; + /** + * Closure for the callbacks + */ void *cb_cls; - char *servicehome; - - char *hostkeyfile; - + /** + * An unique number to identify the peer + */ unsigned int no; }; @@ -119,14 +167,29 @@ struct ConnectingContext struct GNUNET_TRANSPORT_TESTING_handle { + /** + * Testing library system handle + */ + struct GNUNET_TESTING_System *tl_system; + + /** + * head DLL of connect contexts + */ struct ConnectingContext *cc_head; - struct ConnectingContext *cc_tail; - char *hostkey_data; - int hostkeys_total; - int hostkeys_last; + /** + * head DLL of connect contexts + */ + struct ConnectingContext *cc_tail; + /** + * head DLL of peers + */ struct PeerContext *p_head; + + /** + * tail DLL of peers + */ struct PeerContext *p_tail; }; diff --git a/src/transport/transport.conf.in b/src/transport/transport.conf.in index 9a6f5d9..e8786be 100644 --- a/src/transport/transport.conf.in +++ b/src/transport/transport.conf.in @@ -3,7 +3,6 @@ AUTOSTART = YES @UNIXONLY@ PORT = 2091 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-transport #PREFIX = valgrind NEIGHBOUR_LIMIT = 50 @@ -27,11 +26,13 @@ UNIX_MATCH_GID = YES [transport-unix] PORT = 22086 +TESTING_IGNORE_KEYS = ACCEPT_FROM; [transport-tcp] # Use 0 to ONLY advertise as a peer behind NAT (no port binding) PORT = 2086 ADVERTISED_PORT = 2086 +TESTING_IGNORE_KEYS = ACCEPT_FROM; # Maximum number of open TCP connections allowed MAX_CONNECTIONS = 128 @@ -47,23 +48,37 @@ MAX_CONNECTIONS = 128 [transport-udp] PORT = 2086 BROADCAST = YES -BROADCAST_INTERVAL = 30000 +BROADCAST_INTERVAL = 30 s MAX_BPS = 1000000 +TESTING_IGNORE_KEYS = ACCEPT_FROM; -[transport-http] +[transport-http_client] +MAX_CONNECTIONS = 128 +TESTING_IGNORE_KEYS = ACCEPT_FROM; + +[transport-http_server] +#EXTERNAL_HOSTNAME = PORT = 1080 +ADVERTISED_PORT = 1080 MAX_CONNECTIONS = 128 +TESTING_IGNORE_KEYS = ACCEPT_FROM; -[transport-https] +[transport-https_client] +MAX_CONNECTIONS = 128 +TESTING_IGNORE_KEYS = ACCEPT_FROM; + +[transport-https_server] PORT = 4433 +ADVERTISED_PORT = 4433 CRYPTO_INIT = NORMAL -KEY_FILE = https.key -CERT_FILE = https.cert +KEY_FILE = $SERVICEHOME/https.key +CERT_FILE = $SERVICEHOME/https.cert MAX_CONNECTIONS = 128 +TESTING_IGNORE_KEYS = ACCEPT_FROM; [transport-wlan] # Name of the interface in monitor mode (typically monX) INTERFACE = mon0 # Real hardware, no testing TESTMODE = 0 - +TESTING_IGNORE_KEYS = ACCEPT_FROM; diff --git a/src/transport/transport.h b/src/transport/transport.h index e0b8819..be31f0a 100644 --- a/src/transport/transport.h +++ b/src/transport/transport.h @@ -46,6 +46,12 @@ */ #define MIN_QUOTA_REFRESH_TIME 2000 +/** + * What's the maximum number of sockets transport uses for validation and + * neighbors + */ +#define DEFAULT_MAX_FDS 256 + /** * Maximum frequency for re-evaluating latencies for all transport addresses. */ @@ -56,6 +62,26 @@ */ #define CONNECTED_LATENCY_EVALUATION_MAX_DELAY GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MINUTES, 1) +/** + * Similiar to GNUNET_TRANSPORT_NotifyDisconnect but in and out quotas are + * included here. These values are not required outside transport_api + * + * @param cls closure + * @param peer the peer that connected + * @param ats performance data + * @param ats_count number of entries in ats (excluding 0-termination) + * @param bandwidth_in inbound bandwidth in NBO + * @param bandwidth_out outbound bandwidth in NBO + * + */ + +typedef void (*NotifyConnect) (void *cls, + const struct GNUNET_PeerIdentity *peer, + const struct GNUNET_ATS_Information *ats, + uint32_t ats_count, + struct GNUNET_BANDWIDTH_Value32NBO bandwidth_in, + struct GNUNET_BANDWIDTH_Value32NBO bandwidth_out); + GNUNET_NETWORK_STRUCT_BEGIN /** @@ -109,6 +135,16 @@ struct ConnectInfoMessage * Identity of the new neighbour. */ struct GNUNET_PeerIdentity id; + + /** + * Current inbound quota for this peer + */ + struct GNUNET_BANDWIDTH_Value32NBO quota_in; + + /** + * Current outbound quota for this peer + */ + struct GNUNET_BANDWIDTH_Value32NBO quota_out; }; @@ -232,6 +268,18 @@ struct SendOkMessage */ uint32_t success GNUNET_PACKED; + + /** + * Size of message sent + */ + uint32_t bytes_msg GNUNET_PACKED; + + /** + * Size of message sent over wire + * Includes plugin and protocol specific overhead + */ + uint32_t bytes_physical GNUNET_PACKED; + /** * Latency estimate. */ @@ -366,6 +414,34 @@ struct AddressIterateMessage }; +/** + * Message from the library to the transport service + * asking for binary addresses known for a peer. + */ +struct TrafficMetricMessage +{ + /** + * Type will be GNUNET_MESSAGE_TYPE_TRANSPORT_TRAFFIC_METRIC + */ + struct GNUNET_MessageHeader header; + + /** + * SEND, RECEIVE or BOTH? + */ + uint16_t direction; + + /** + * Traffic metrics count + */ + uint16_t ats_count; + + /** + * The identity of the peer to look up. + */ + struct GNUNET_PeerIdentity peer; +}; + + /** * Message from the transport service to the library * containing binary addresses known for a peer. diff --git a/src/transport/transport_api.c b/src/transport/transport_api.c index b97a245..7f0bc92 100644 --- a/src/transport/transport_api.c +++ b/src/transport/transport_api.c @@ -146,6 +146,11 @@ struct Neighbour */ int is_ready; + /** + * Sending consumed more bytes on wire than payload was announced + * This overhead is added to the delay of next sending operation + */ + size_t traffic_overhead; }; @@ -175,6 +180,11 @@ struct GNUNET_TRANSPORT_GetHelloHandle */ GNUNET_TRANSPORT_HelloUpdateCallback rec; + /** + * Task for calling the HelloUpdateCallback when we already have a HELLO + */ + GNUNET_SCHEDULER_TaskIdentifier notify_task; + /** * Closure for rec. */ @@ -182,6 +192,41 @@ struct GNUNET_TRANSPORT_GetHelloHandle }; +/** + * Linked list for all try-connect requests + */ +struct GNUNET_TRANSPORT_TryConnectHandle +{ + struct GNUNET_TRANSPORT_TryConnectHandle *prev; + struct GNUNET_TRANSPORT_TryConnectHandle *next; + + struct GNUNET_PeerIdentity pid; + + struct GNUNET_TRANSPORT_Handle *th; + struct GNUNET_TRANSPORT_TransmitHandle *tth; + GNUNET_TRANSPORT_TryConnectCallback cb; + void *cb_cls; +}; + + +/** + * Linked list for all try-connect requests + */ +struct GNUNET_TRANSPORT_OfferHelloHandle +{ + struct GNUNET_TRANSPORT_OfferHelloHandle *prev; + struct GNUNET_TRANSPORT_OfferHelloHandle *next; + + struct GNUNET_TRANSPORT_Handle *th; + + struct GNUNET_TRANSPORT_TransmitHandle *tth; + GNUNET_SCHEDULER_Task cont; + + void *cls; + + struct GNUNET_MessageHeader *msg; +}; + /** * Handle for the transport service (includes all of the @@ -246,6 +291,26 @@ struct GNUNET_TRANSPORT_Handle */ struct GNUNET_TRANSPORT_GetHelloHandle *hwl_tail; + /** + * Linked list of pending try connect requests head + */ + struct GNUNET_TRANSPORT_TryConnectHandle *tc_head; + + /** + * Linked list of pending try connect requests tail + */ + struct GNUNET_TRANSPORT_TryConnectHandle *tc_tail; + + /** + * Linked list of pending offer HELLO requests head + */ + struct GNUNET_TRANSPORT_OfferHelloHandle *oh_head; + + /** + * Linked list of pending offer HELLO requests tail + */ + struct GNUNET_TRANSPORT_OfferHelloHandle *oh_tail; + /** * My configuration. */ @@ -293,9 +358,15 @@ struct GNUNET_TRANSPORT_Handle * (if GNUNET_NO, then 'self' is all zeros!). */ int check_self; + + /** + * Reconnect in progress + */ + int reconnecting; }; + /** * Schedule the task to send one message, either from the control * list or the peer message queues to the service. @@ -348,12 +419,13 @@ neighbour_add (struct GNUNET_TRANSPORT_Handle *h, n->id = *pid; n->h = h; n->is_ready = GNUNET_YES; + n->traffic_overhead = 0; GNUNET_BANDWIDTH_tracker_init (&n->out_tracker, GNUNET_CONSTANTS_DEFAULT_BW_IN_OUT, MAX_BANDWIDTH_CARRY_S); GNUNET_assert (GNUNET_OK == GNUNET_CONTAINER_multihashmap_put (h->neighbours, - &pid->hashPubKey, n, + &n->id.hashPubKey, n, GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY)); return n; } @@ -370,7 +442,7 @@ neighbour_add (struct GNUNET_TRANSPORT_Handle *h, * GNUNET_NO if not. */ static int -neighbour_delete (void *cls, const GNUNET_HashCode * key, void *value) +neighbour_delete (void *cls, const struct GNUNET_HashCode * key, void *value) { struct GNUNET_TRANSPORT_Handle *handle = cls; struct Neighbour *n = value; @@ -410,6 +482,8 @@ demultiplexer (void *cls, const struct GNUNET_MessageHeader *msg) struct GNUNET_PeerIdentity me; uint16_t size; uint32_t ats_count; + uint32_t bytes_msg; + uint32_t bytes_physical; GNUNET_assert (h->client != NULL); if (msg == NULL) @@ -477,6 +551,9 @@ demultiplexer (void *cls, const struct GNUNET_MessageHeader *msg) break; } n = neighbour_add (h, &cim->id); + LOG (GNUNET_ERROR_TYPE_DEBUG, "Receiving `%s' message for `%4s' with quota %u\n", + "CONNECT", GNUNET_i2s (&cim->id), ntohl (cim->quota_out.value__)); + GNUNET_BANDWIDTH_tracker_update_quota (&n->out_tracker, cim->quota_out); if (h->nc_cb != NULL) h->nc_cb (h->cls, &n->id, ats, ats_count); break; @@ -505,11 +582,21 @@ demultiplexer (void *cls, const struct GNUNET_MessageHeader *msg) break; } okm = (const struct SendOkMessage *) msg; + bytes_msg = ntohl (okm->bytes_msg); + bytes_physical = ntohl (okm->bytes_physical); LOG (GNUNET_ERROR_TYPE_DEBUG, "Receiving `%s' message, transmission %s.\n", "SEND_OK", ntohl (okm->success) == GNUNET_OK ? "succeeded" : "failed"); + n = neighbour_find (h, &okm->peer); if (n == NULL) break; + + if (bytes_physical >= bytes_msg) + { + LOG (GNUNET_ERROR_TYPE_DEBUG, "Overhead for %u byte message: %u \n", + bytes_msg, bytes_physical - bytes_msg); + n->traffic_overhead += bytes_physical - bytes_msg; + } GNUNET_break (GNUNET_NO == n->is_ready); n->is_ready = GNUNET_YES; if ((n->th != NULL) && (n->hn == NULL)) @@ -563,6 +650,8 @@ demultiplexer (void *cls, const struct GNUNET_MessageHeader *msg) n = neighbour_find (h, &qm->peer); if (n == NULL) break; + LOG (GNUNET_ERROR_TYPE_DEBUG, "Receiving `%s' message for `%4s' with quota %u\n", + "SET_QUOTA", GNUNET_i2s (&qm->peer), ntohl (qm->quota.value__)); GNUNET_BANDWIDTH_tracker_update_quota (&n->out_tracker, qm->quota); break; default: @@ -778,9 +867,12 @@ schedule_transmission (struct GNUNET_TRANSPORT_Handle *h) if (NULL != h->control_head) delay = GNUNET_TIME_UNIT_ZERO; else if (NULL != (n = GNUNET_CONTAINER_heap_peek (h->ready_heap))) + { delay = GNUNET_BANDWIDTH_tracker_get_delay (&n->out_tracker, - n->th->notify_size); + n->th->notify_size + n->traffic_overhead); + n->traffic_overhead = 0; + } else return; /* no work to be done */ LOG (GNUNET_ERROR_TYPE_DEBUG, @@ -799,8 +891,9 @@ schedule_transmission (struct GNUNET_TRANSPORT_Handle *h) * @param size number of bytes to be transmitted * @param notify function to call to get the content * @param notify_cls closure for notify + * @return a GNUNET_TRANSPORT_TransmitHandle */ -static void +static struct GNUNET_TRANSPORT_TransmitHandle * schedule_control_transmit (struct GNUNET_TRANSPORT_Handle *h, size_t size, GNUNET_CONNECTION_TransmitReadyNotify notify, void *notify_cls) @@ -815,6 +908,7 @@ schedule_control_transmit (struct GNUNET_TRANSPORT_Handle *h, size_t size, th->notify_size = size; GNUNET_CONTAINER_DLL_insert_tail (h->control_head, h->control_tail, th); schedule_transmission (h); + return th; } @@ -925,19 +1019,30 @@ disconnect_and_schedule_reconnect (struct GNUNET_TRANSPORT_Handle *h) h->reconnect_delay.rel_value); h->reconnect_task = GNUNET_SCHEDULER_add_delayed (h->reconnect_delay, &reconnect, h); - if (h->reconnect_delay.rel_value == 0) - { - h->reconnect_delay = GNUNET_TIME_UNIT_MILLISECONDS; - } - else - { - h->reconnect_delay = GNUNET_TIME_relative_multiply (h->reconnect_delay, 2); - h->reconnect_delay = - GNUNET_TIME_relative_min (GNUNET_TIME_UNIT_SECONDS, h->reconnect_delay); - } + h->reconnect_delay = GNUNET_TIME_STD_BACKOFF (h->reconnect_delay); +} + + +/** + * Cancel control request for transmission to the transport service. + * + * @param th handle to the transport service + * @param tth transmit handle to cancel + */ +static void +cancel_control_transmit (struct GNUNET_TRANSPORT_Handle *th, struct GNUNET_TRANSPORT_TransmitHandle *tth) +{ + GNUNET_assert (NULL != th); + GNUNET_assert (NULL != tth); + + LOG (GNUNET_ERROR_TYPE_DEBUG, "Canceling transmit of contral transmission requested\n"); + + GNUNET_CONTAINER_DLL_remove (th->control_head, th->control_tail, tth); + GNUNET_free (tth); } + /** * Send REQUEST_CONNECT message to the service. * @@ -949,51 +1054,87 @@ disconnect_and_schedule_reconnect (struct GNUNET_TRANSPORT_Handle *h) static size_t send_try_connect (void *cls, size_t size, void *buf) { - struct GNUNET_PeerIdentity *pid = cls; + struct GNUNET_TRANSPORT_TryConnectHandle *tch = cls; struct TransportRequestConnectMessage msg; if (buf == NULL) { - GNUNET_free (pid); + if (NULL != tch->cb) + tch->cb (tch->cb_cls, GNUNET_SYSERR); + GNUNET_CONTAINER_DLL_remove (tch->th->tc_head, tch->th->tc_tail, tch); + GNUNET_free (tch); return 0; } LOG (GNUNET_ERROR_TYPE_DEBUG, "Transmitting `%s' request with respect to `%4s'.\n", "REQUEST_CONNECT", - GNUNET_i2s (pid)); + GNUNET_i2s (&tch->pid)); GNUNET_assert (size >= sizeof (struct TransportRequestConnectMessage)); msg.header.size = htons (sizeof (struct TransportRequestConnectMessage)); msg.header.type = htons (GNUNET_MESSAGE_TYPE_TRANSPORT_REQUEST_CONNECT); msg.reserved = htonl (0); - msg.peer = *pid; + msg.peer = tch->pid; memcpy (buf, &msg, sizeof (msg)); - GNUNET_free (pid); + if (NULL != tch->cb) + tch->cb (tch->cb_cls, GNUNET_OK); + GNUNET_CONTAINER_DLL_remove (tch->th->tc_head, tch->th->tc_tail, tch); + GNUNET_free (tch); return sizeof (struct TransportRequestConnectMessage); } - /** * Ask the transport service to establish a connection to * the given peer. * * @param handle connection to transport service * @param target who we should try to connect to + * @param cb callback to be called when request was transmitted to transport + * service + * @param cb_cls closure for the callback + * @return a GNUNET_TRANSPORT_TryConnectHandle handle or + * NULL on failure (cb will not be called) */ -void +struct GNUNET_TRANSPORT_TryConnectHandle * GNUNET_TRANSPORT_try_connect (struct GNUNET_TRANSPORT_Handle *handle, - const struct GNUNET_PeerIdentity *target) + const struct GNUNET_PeerIdentity *target, + GNUNET_TRANSPORT_TryConnectCallback cb, + void *cb_cls) { - struct GNUNET_PeerIdentity *pid; + struct GNUNET_TRANSPORT_TryConnectHandle *tch = NULL; if (NULL == handle->client) - return; - pid = GNUNET_malloc (sizeof (struct GNUNET_PeerIdentity)); - *pid = *target; - schedule_control_transmit (handle, + return NULL; + + tch = GNUNET_malloc (sizeof (struct GNUNET_TRANSPORT_TryConnectHandle)); + tch->th = handle; + tch->pid = *(target); + tch->cb = cb; + tch->cb_cls = cb_cls; + tch->tth = schedule_control_transmit (handle, sizeof (struct TransportRequestConnectMessage), - &send_try_connect, pid); + &send_try_connect, tch); + GNUNET_CONTAINER_DLL_insert(handle->tc_head, handle->tc_tail, tch); + return tch; } +/** + * Cancel the request to transport to try a connect + * Callback will not be called + * + * @param tch GNUNET_TRANSPORT_TryConnectHandle handle to cancel + */ +void +GNUNET_TRANSPORT_try_connect_cancel (struct GNUNET_TRANSPORT_TryConnectHandle *tch) +{ + struct GNUNET_TRANSPORT_Handle *th; + GNUNET_assert (NULL != tch); + + th = tch->th; + cancel_control_transmit (th, tch->tth); + GNUNET_CONTAINER_DLL_remove (th->tc_head, th->tc_tail, tch); + GNUNET_free (tch); +} + /** * Send HELLO message to the service. * @@ -1005,14 +1146,23 @@ GNUNET_TRANSPORT_try_connect (struct GNUNET_TRANSPORT_Handle *handle, static size_t send_hello (void *cls, size_t size, void *buf) { - struct GNUNET_MessageHeader *msg = cls; + struct GNUNET_TRANSPORT_OfferHelloHandle *ohh = cls; + struct GNUNET_MessageHeader *msg = ohh->msg; uint16_t ssize; + struct GNUNET_SCHEDULER_TaskContext tc; + tc.read_ready = NULL; + tc.write_ready = NULL; + tc.reason = GNUNET_SCHEDULER_REASON_TIMEOUT; if (buf == NULL) { LOG (GNUNET_ERROR_TYPE_DEBUG, "Timeout while trying to transmit `%s' request.\n", "HELLO"); + if (NULL != ohh->cont) + ohh->cont (ohh->cls, &tc); GNUNET_free (msg); + GNUNET_CONTAINER_DLL_remove (ohh->th->oh_head, ohh->th->oh_tail, ohh); + GNUNET_free (ohh); return 0; } LOG (GNUNET_ERROR_TYPE_DEBUG, "Transmitting `%s' request.\n", "HELLO"); @@ -1020,10 +1170,101 @@ send_hello (void *cls, size_t size, void *buf) GNUNET_assert (size >= ssize); memcpy (buf, msg, ssize); GNUNET_free (msg); + tc.reason = GNUNET_SCHEDULER_REASON_READ_READY; + if (NULL != ohh->cont) + ohh->cont (ohh->cls, &tc); + GNUNET_CONTAINER_DLL_remove (ohh->th->oh_head, ohh->th->oh_tail, ohh); + GNUNET_free (ohh); return ssize; } +/** + * Send traffic metric message to the service. + * + * @param cls the message to send + * @param size number of bytes available in buf + * @param buf where to copy the message + * @return number of bytes copied to buf + */ +static size_t +send_metric (void *cls, size_t size, void *buf) +{ + struct TrafficMetricMessage *msg = cls; + uint16_t ssize; + if (buf == NULL) + { + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Timeout while trying to transmit `%s' request.\n", "TRAFFIC_METRIC"); + GNUNET_free (msg); + return 0; + } + LOG (GNUNET_ERROR_TYPE_DEBUG, "Transmitting `%s' request.\n", "TRAFFIC_METRIC"); + ssize = ntohs (msg->header.size); + GNUNET_assert (size >= ssize); + memcpy (buf, msg, ssize); + GNUNET_free (msg); + return ssize; +} + + +/** + * Set transport metrics for a peer and a direction + * + * @param handle transport handle + * @param peer the peer to set the metric for + * @param direction can be: TM_SEND, TM_RECV, TM_BOTH + * @param ats the metric as ATS information + * @param ats_count the number of metrics + * + * Supported ATS values: + * GNUNET_ATS_QUALITY_NET_DELAY (value in ms) + * GNUNET_ATS_QUALITY_NET_DISTANCE (value in #hops) + * + * Example + * To enforce a delay of 10 ms for peer p1 in sending direction use: + * + * struct GNUNET_ATS_Information ats; + * ats.type = ntohl (GNUNET_ATS_QUALITY_NET_DELAY); + * ats.value = ntohl (10); + * GNUNET_TRANSPORT_set_traffic_metric (th, p1, TM_SEND, &ats, 1); + * + * Note: + * Delay restrictions in receiving direction will be enforced with + * 1 message delay. + */ +void +GNUNET_TRANSPORT_set_traffic_metric (struct GNUNET_TRANSPORT_Handle *handle, + const struct GNUNET_PeerIdentity *peer, + int direction, + const struct GNUNET_ATS_Information *ats, + size_t ats_count) +{ + struct TrafficMetricMessage *msg; + + GNUNET_assert (NULL != handle); + GNUNET_assert (NULL != peer); + GNUNET_assert (direction >= TM_SEND); + GNUNET_assert (direction <= TM_BOTH); + + if (0 == ats_count) + return; + + size_t len = sizeof (struct TrafficMetricMessage) + + ats_count * sizeof (struct GNUNET_ATS_Information); + + msg = GNUNET_malloc (len); + msg->header.size = htons (len); + msg->header.type = htons (GNUNET_MESSAGE_TYPE_TRANSPORT_TRAFFIC_METRIC); + msg->direction = htons (direction); + msg->ats_count = htons (ats_count); + msg->peer = (*peer); + memcpy (&msg[1], ats, ats_count * sizeof (struct GNUNET_ATS_Information)); + schedule_control_transmit (handle, len, &send_metric, msg); +} + + + /** * Offer the transport service the HELLO of another peer. Note that * the transport service may just ignore this message if the HELLO is @@ -1031,21 +1272,30 @@ send_hello (void *cls, size_t size, void *buf) * * @param handle connection to transport service * @param hello the hello message - * @param cont continuation to call when HELLO has been sent + * @param cont continuation to call when HELLO has been sent, + * tc reason GNUNET_SCHEDULER_REASON_TIMEOUT for fail + * tc reasong GNUNET_SCHEDULER_REASON_READ_READY for success * @param cls closure for continuation + * @return a GNUNET_TRANSPORT_OfferHelloHandle handle or NULL on failure, + * in case of failure cont will not be called * */ -void +struct GNUNET_TRANSPORT_OfferHelloHandle * GNUNET_TRANSPORT_offer_hello (struct GNUNET_TRANSPORT_Handle *handle, const struct GNUNET_MessageHeader *hello, GNUNET_SCHEDULER_Task cont, void *cls) { - uint16_t size; - struct GNUNET_PeerIdentity peer; + struct GNUNET_TRANSPORT_OfferHelloHandle *ohh; struct GNUNET_MessageHeader *msg; + struct GNUNET_PeerIdentity peer; + uint16_t size; + + GNUNET_assert (NULL != handle); + GNUNET_assert (NULL != hello); if (NULL == handle->client) - return; + return NULL; + GNUNET_break (ntohs (hello->type) == GNUNET_MESSAGE_TYPE_HELLO); size = ntohs (hello->size); GNUNET_break (size >= sizeof (struct GNUNET_MessageHeader)); @@ -1053,19 +1303,80 @@ GNUNET_TRANSPORT_offer_hello (struct GNUNET_TRANSPORT_Handle *handle, GNUNET_HELLO_get_id ((const struct GNUNET_HELLO_Message *) hello, &peer)) { GNUNET_break (0); - return; + return NULL; } + msg = GNUNET_malloc (size); memcpy (msg, hello, size); LOG (GNUNET_ERROR_TYPE_DEBUG, "Offering `%s' message of `%4s' to transport for validation.\n", "HELLO", GNUNET_i2s (&peer)); - schedule_control_transmit (handle, size, &send_hello, msg); + + ohh = GNUNET_malloc (sizeof (struct GNUNET_TRANSPORT_OfferHelloHandle)); + ohh->th = handle; + ohh->cont = cont; + ohh->cls = cls; + ohh->msg = msg; + ohh->tth = schedule_control_transmit (handle, size, &send_hello, ohh); + GNUNET_CONTAINER_DLL_insert (handle->oh_head, handle->oh_tail, ohh); + return ohh; } /** - * Obtain the HELLO message for this peer. + * Cancel the request to transport to offer the HELLO message + * + * @param ohh the GNUNET_TRANSPORT_OfferHelloHandle to cancel + */ +void +GNUNET_TRANSPORT_offer_hello_cancel (struct GNUNET_TRANSPORT_OfferHelloHandle *ohh) +{ + struct GNUNET_TRANSPORT_Handle *th = ohh->th; + GNUNET_assert (NULL != ohh); + + cancel_control_transmit (ohh->th, ohh->tth); + GNUNET_CONTAINER_DLL_remove (th->oh_head, th->oh_tail, ohh); + GNUNET_free (ohh->msg); + GNUNET_free (ohh); +} + +int +GNUNET_TRANSPORT_check_neighbour_connected (struct GNUNET_TRANSPORT_Handle *handle, + const struct GNUNET_PeerIdentity *peer) +{ + GNUNET_assert (NULL != handle); + GNUNET_assert (NULL != peer); + + if (GNUNET_YES == GNUNET_CONTAINER_multihashmap_contains(handle->neighbours, &peer->hashPubKey)) + return GNUNET_YES; + else + return GNUNET_NO; +} + + +/** + * Task to call the HelloUpdateCallback of the GetHelloHandle + * + * @param cls the GetHelloHandle + * @param tc the scheduler task context + */ +static void +call_hello_update_cb_async (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct GNUNET_TRANSPORT_GetHelloHandle *ghh = cls; + + GNUNET_assert (NULL != ghh->handle->my_hello); + GNUNET_assert (GNUNET_SCHEDULER_NO_TASK != ghh->notify_task); + ghh->notify_task = GNUNET_SCHEDULER_NO_TASK; + ghh->rec (ghh->rec_cls, + (const struct GNUNET_MessageHeader *) ghh->handle->my_hello); +} + + +/** + * Obtain the HELLO message for this peer. The callback given in this function + * is never called synchronously. * * @param handle connection to transport service * @param rec function to call with the HELLO, sender will be our peer @@ -1088,7 +1399,8 @@ GNUNET_TRANSPORT_get_hello (struct GNUNET_TRANSPORT_Handle *handle, hwl->handle = handle; GNUNET_CONTAINER_DLL_insert (handle->hwl_head, handle->hwl_tail, hwl); if (handle->my_hello != NULL) - rec (rec_cls, (const struct GNUNET_MessageHeader *) handle->my_hello); + hwl->notify_task = GNUNET_SCHEDULER_add_now (&call_hello_update_cb_async, + hwl); return hwl; } @@ -1103,6 +1415,8 @@ GNUNET_TRANSPORT_get_hello_cancel (struct GNUNET_TRANSPORT_GetHelloHandle *ghh) { struct GNUNET_TRANSPORT_Handle *handle = ghh->handle; + if (GNUNET_SCHEDULER_NO_TASK != ghh->notify_task) + GNUNET_SCHEDULER_cancel (ghh->notify_task); GNUNET_CONTAINER_DLL_remove (handle->hwl_head, handle->hwl_tail, ghh); GNUNET_free (ghh); } @@ -1142,10 +1456,17 @@ GNUNET_TRANSPORT_connect (const struct GNUNET_CONFIGURATION_Handle *cfg, ret->nd_cb = nd; ret->reconnect_delay = GNUNET_TIME_UNIT_ZERO; ret->neighbours = - GNUNET_CONTAINER_multihashmap_create (STARTING_NEIGHBOURS_SIZE); + GNUNET_CONTAINER_multihashmap_create (STARTING_NEIGHBOURS_SIZE, GNUNET_YES); ret->ready_heap = GNUNET_CONTAINER_heap_create (GNUNET_CONTAINER_HEAP_ORDER_MIN); - ret->reconnect_task = GNUNET_SCHEDULER_add_now (&reconnect, ret); + LOG (GNUNET_ERROR_TYPE_DEBUG, "Connecting to transport service.\n"); + ret->client = GNUNET_CLIENT_connect ("transport", cfg); + if (ret->client == NULL) + { + GNUNET_free (ret); + return NULL; + } + schedule_control_transmit (ret, sizeof (struct StartMessage), &send_start, ret); return ret; } @@ -1177,6 +1498,8 @@ GNUNET_TRANSPORT_disconnect (struct GNUNET_TRANSPORT_Handle *handle) } GNUNET_free_non_null (handle->my_hello); handle->my_hello = NULL; + GNUNET_assert (handle->tc_head == NULL); + GNUNET_assert (handle->tc_tail == NULL); GNUNET_assert (handle->hwl_head == NULL); GNUNET_assert (handle->hwl_tail == NULL); GNUNET_CONTAINER_heap_destroy (handle->ready_heap); @@ -1240,7 +1563,8 @@ GNUNET_TRANSPORT_notify_transmit_ready (struct GNUNET_TRANSPORT_Handle *handle, th->priority = priority; n->th = th; /* calculate when our transmission should be ready */ - delay = GNUNET_BANDWIDTH_tracker_get_delay (&n->out_tracker, size); + delay = GNUNET_BANDWIDTH_tracker_get_delay (&n->out_tracker, size + n->traffic_overhead); + n->traffic_overhead = 0; if (delay.rel_value > timeout.rel_value) delay.rel_value = 0; /* notify immediately (with failure) */ LOG (GNUNET_ERROR_TYPE_DEBUG, diff --git a/src/transport/transport_api_address_lookup.c b/src/transport/transport_api_address_lookup.c index 655be83..217aecd 100644 --- a/src/transport/transport_api_address_lookup.c +++ b/src/transport/transport_api_address_lookup.c @@ -157,9 +157,7 @@ reconnect (struct GNUNET_TRANSPORT_PeerIterateContext *pal_ctx) GNUNET_assert (GNUNET_NO == pal_ctx->one_shot); GNUNET_CLIENT_disconnect (pal_ctx->client); pal_ctx->client = NULL; - pal_ctx->backoff = GNUNET_TIME_relative_max (GNUNET_TIME_UNIT_MILLISECONDS, - GNUNET_TIME_relative_min (GNUNET_TIME_relative_multiply (pal_ctx->backoff, 2), - GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 30))); + pal_ctx->backoff = GNUNET_TIME_STD_BACKOFF (pal_ctx->backoff); pal_ctx->reconnect_task = GNUNET_SCHEDULER_add_delayed (pal_ctx->backoff, &do_connect, pal_ctx); diff --git a/src/tun/Makefile.am b/src/tun/Makefile.am index 390ce9e..3b2b573 100644 --- a/src/tun/Makefile.am +++ b/src/tun/Makefile.am @@ -14,7 +14,8 @@ lib_LTLIBRARIES = libgnunettun.la libgnunettun_la_SOURCES = \ tun.c libgnunettun_la_LIBADD = \ - $(top_builddir)/src/util/libgnunetutil.la $(XLIB) + $(top_builddir)/src/util/libgnunetutil.la $(XLIB) \ + $(LTLIBINTL) libgnunettun_la_LDFLAGS = \ $(GN_LIB_LDFLAGS) \ -version-info 0:0:0 diff --git a/src/tun/Makefile.in b/src/tun/Makefile.in index 896280a..78af750 100644 --- a/src/tun/Makefile.in +++ b/src/tun/Makefile.in @@ -1,9 +1,9 @@ -# Makefile.in generated by automake 1.11.1 from Makefile.am. +# Makefile.in generated by automake 1.11.6 from Makefile.am. # @configure_input@ # Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, -# 2003, 2004, 2005, 2006, 2007, 2008, 2009 Free Software Foundation, -# Inc. +# 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Free Software +# Foundation, Inc. # This Makefile.in is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. @@ -16,6 +16,23 @@ @SET_MAKE@ VPATH = @srcdir@ +am__make_dryrun = \ + { \ + am__dry=no; \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + echo 'am--echo: ; @echo "AM" OK' | $(MAKE) -f - 2>/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } pkgdatadir = $(datadir)/@PACKAGE@ pkgincludedir = $(includedir)/@PACKAGE@ pkglibdir = $(libdir)/@PACKAGE@ @@ -41,14 +58,15 @@ DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 am__aclocal_m4_deps = $(top_srcdir)/m4/absolute-header.m4 \ $(top_srcdir)/m4/align.m4 $(top_srcdir)/m4/argz.m4 \ - $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/iconv.m4 \ - $(top_srcdir)/m4/lib-ld.m4 $(top_srcdir)/m4/lib-link.m4 \ - $(top_srcdir)/m4/lib-prefix.m4 $(top_srcdir)/m4/libcurl.m4 \ - $(top_srcdir)/m4/libgcrypt.m4 $(top_srcdir)/m4/libtool.m4 \ - $(top_srcdir)/m4/libunistring.m4 $(top_srcdir)/m4/ltdl.m4 \ - $(top_srcdir)/m4/ltoptions.m4 $(top_srcdir)/m4/ltsugar.m4 \ - $(top_srcdir)/m4/ltversion.m4 $(top_srcdir)/m4/lt~obsolete.m4 \ - $(top_srcdir)/m4/nls.m4 $(top_srcdir)/m4/po.m4 \ + $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/glib-2.0.m4 \ + $(top_srcdir)/m4/iconv.m4 $(top_srcdir)/m4/lib-ld.m4 \ + $(top_srcdir)/m4/lib-link.m4 $(top_srcdir)/m4/lib-prefix.m4 \ + $(top_srcdir)/m4/libcurl.m4 $(top_srcdir)/m4/libgcrypt.m4 \ + $(top_srcdir)/m4/libtool.m4 $(top_srcdir)/m4/libunistring.m4 \ + $(top_srcdir)/m4/ltdl.m4 $(top_srcdir)/m4/ltoptions.m4 \ + $(top_srcdir)/m4/ltsugar.m4 $(top_srcdir)/m4/ltversion.m4 \ + $(top_srcdir)/m4/lt~obsolete.m4 $(top_srcdir)/m4/nls.m4 \ + $(top_srcdir)/m4/pkg.m4 $(top_srcdir)/m4/po.m4 \ $(top_srcdir)/m4/progtest.m4 $(top_srcdir)/acinclude.m4 \ $(top_srcdir)/configure.ac am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ @@ -78,16 +96,22 @@ am__nobase_list = $(am__nobase_strip_setup); \ am__base_list = \ sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \ sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g' +am__uninstall_files_from_dir = { \ + test -z "$$files" \ + || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \ + || { echo " ( cd '$$dir' && rm -f" $$files ")"; \ + $(am__cd) "$$dir" && rm -f $$files; }; \ + } am__installdirs = "$(DESTDIR)$(libdir)" LTLIBRARIES = $(lib_LTLIBRARIES) am__DEPENDENCIES_1 = libgnunettun_la_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la \ - $(am__DEPENDENCIES_1) + $(am__DEPENDENCIES_1) $(am__DEPENDENCIES_1) am_libgnunettun_la_OBJECTS = tun.lo libgnunettun_la_OBJECTS = $(am_libgnunettun_la_OBJECTS) -AM_V_lt = $(am__v_lt_$(V)) -am__v_lt_ = $(am__v_lt_$(AM_DEFAULT_VERBOSITY)) +AM_V_lt = $(am__v_lt_@AM_V@) +am__v_lt_ = $(am__v_lt_@AM_DEFAULT_V@) am__v_lt_0 = --silent libgnunettun_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ @@ -107,24 +131,29 @@ LTCOMPILE = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) \ $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) \ $(AM_CFLAGS) $(CFLAGS) -AM_V_CC = $(am__v_CC_$(V)) -am__v_CC_ = $(am__v_CC_$(AM_DEFAULT_VERBOSITY)) +AM_V_CC = $(am__v_CC_@AM_V@) +am__v_CC_ = $(am__v_CC_@AM_DEFAULT_V@) am__v_CC_0 = @echo " CC " $@; -AM_V_at = $(am__v_at_$(V)) -am__v_at_ = $(am__v_at_$(AM_DEFAULT_VERBOSITY)) +AM_V_at = $(am__v_at_@AM_V@) +am__v_at_ = $(am__v_at_@AM_DEFAULT_V@) am__v_at_0 = @ CCLD = $(CC) LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ $(AM_LDFLAGS) $(LDFLAGS) -o $@ -AM_V_CCLD = $(am__v_CCLD_$(V)) -am__v_CCLD_ = $(am__v_CCLD_$(AM_DEFAULT_VERBOSITY)) +AM_V_CCLD = $(am__v_CCLD_@AM_V@) +am__v_CCLD_ = $(am__v_CCLD_@AM_DEFAULT_V@) am__v_CCLD_0 = @echo " CCLD " $@; -AM_V_GEN = $(am__v_GEN_$(V)) -am__v_GEN_ = $(am__v_GEN_$(AM_DEFAULT_VERBOSITY)) +AM_V_GEN = $(am__v_GEN_@AM_V@) +am__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@) am__v_GEN_0 = @echo " GEN " $@; SOURCES = $(libgnunettun_la_SOURCES) $(test_tun_SOURCES) DIST_SOURCES = $(libgnunettun_la_SOURCES) $(test_tun_SOURCES) +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac ETAGS = etags CTAGS = ctags am__tty_colors = \ @@ -165,6 +194,10 @@ EXEEXT = @EXEEXT@ EXT_LIBS = @EXT_LIBS@ EXT_LIB_PATH = @EXT_LIB_PATH@ FGREP = @FGREP@ +GLIB_CFLAGS = @GLIB_CFLAGS@ +GLIB_GENMARSHAL = @GLIB_GENMARSHAL@ +GLIB_LIBS = @GLIB_LIBS@ +GLIB_MKENUMS = @GLIB_MKENUMS@ GMSGFMT = @GMSGFMT@ GMSGFMT_015 = @GMSGFMT_015@ GNUNETDNS_GROUP = @GNUNETDNS_GROUP@ @@ -175,6 +208,7 @@ GN_LIBINTL = @GN_LIBINTL@ GN_LIB_LDFLAGS = @GN_LIB_LDFLAGS@ GN_PLUGIN_LDFLAGS = @GN_PLUGIN_LDFLAGS@ GN_USER_HOME_DIR = @GN_USER_HOME_DIR@ +GOBJECT_QUERY = @GOBJECT_QUERY@ GREP = @GREP@ HAVE_LIBUNISTRING = @HAVE_LIBUNISTRING@ INCLTDL = @INCLTDL@ @@ -197,6 +231,8 @@ LIBCURL_CPPFLAGS = @LIBCURL_CPPFLAGS@ LIBGCRYPT_CFLAGS = @LIBGCRYPT_CFLAGS@ LIBGCRYPT_CONFIG = @LIBGCRYPT_CONFIG@ LIBGCRYPT_LIBS = @LIBGCRYPT_LIBS@ +LIBGTOP_CFLAGS = @LIBGTOP_CFLAGS@ +LIBGTOP_LIBS = @LIBGTOP_LIBS@ LIBICONV = @LIBICONV@ LIBINTL = @LIBINTL@ LIBLTDL = @LIBLTDL@ @@ -218,6 +254,7 @@ LT_CONFIG_H = @LT_CONFIG_H@ LT_DLLOADERS = @LT_DLLOADERS@ LT_DLPREOPEN = @LT_DLPREOPEN@ MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ MKDIR_P = @MKDIR_P@ MONKEYPREFIX = @MONKEYPREFIX@ MSGFMT = @MSGFMT@ @@ -227,6 +264,7 @@ MYSQL_CPPFLAGS = @MYSQL_CPPFLAGS@ MYSQL_LDFLAGS = @MYSQL_LDFLAGS@ NM = @NM@ NMEDIT = @NMEDIT@ +NSS_DIR = @NSS_DIR@ OBJC = @OBJC@ OBJCDEPMODE = @OBJCDEPMODE@ OBJCFLAGS = @OBJCFLAGS@ @@ -242,6 +280,7 @@ PACKAGE_TARNAME = @PACKAGE_TARNAME@ PACKAGE_URL = @PACKAGE_URL@ PACKAGE_VERSION = @PACKAGE_VERSION@ PATH_SEPARATOR = @PATH_SEPARATOR@ +PKG_CONFIG = @PKG_CONFIG@ POSTGRES_CPPFLAGS = @POSTGRES_CPPFLAGS@ POSTGRES_LDFLAGS = @POSTGRES_LDFLAGS@ POSUB = @POSUB@ @@ -273,6 +312,7 @@ abs_builddir = @abs_builddir@ abs_srcdir = @abs_srcdir@ abs_top_builddir = @abs_top_builddir@ abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ ac_ct_CC = @ac_ct_CC@ ac_ct_CXX = @ac_ct_CXX@ ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ @@ -295,6 +335,7 @@ datarootdir = @datarootdir@ docdir = @docdir@ dvidir = @dvidir@ exec_prefix = @exec_prefix@ +gitcommand = @gitcommand@ host = @host@ host_alias = @host_alias@ host_cpu = @host_cpu@ @@ -308,7 +349,6 @@ libdir = @libdir@ libexecdir = @libexecdir@ localedir = @localedir@ localstatedir = @localstatedir@ -lt_ECHO = @lt_ECHO@ ltdl_LIBOBJS = @ltdl_LIBOBJS@ ltdl_LTLIBOBJS = @ltdl_LTLIBOBJS@ mandir = @mandir@ @@ -326,6 +366,7 @@ sbindir = @sbindir@ sharedstatedir = @sharedstatedir@ srcdir = @srcdir@ subdirs = @subdirs@ +svnversioncommand = @svnversioncommand@ sys_symbol_underscore = @sys_symbol_underscore@ sysconfdir = @sysconfdir@ target = @target@ @@ -345,7 +386,8 @@ libgnunettun_la_SOURCES = \ tun.c libgnunettun_la_LIBADD = \ - $(top_builddir)/src/util/libgnunetutil.la $(XLIB) + $(top_builddir)/src/util/libgnunetutil.la $(XLIB) \ + $(LTLIBINTL) libgnunettun_la_LDFLAGS = \ $(GN_LIB_LDFLAGS) \ @@ -395,7 +437,6 @@ $(ACLOCAL_M4): $(am__aclocal_m4_deps) $(am__aclocal_m4_deps): install-libLTLIBRARIES: $(lib_LTLIBRARIES) @$(NORMAL_INSTALL) - test -z "$(libdir)" || $(MKDIR_P) "$(DESTDIR)$(libdir)" @list='$(lib_LTLIBRARIES)'; test -n "$(libdir)" || list=; \ list2=; for p in $$list; do \ if test -f $$p; then \ @@ -403,6 +444,8 @@ install-libLTLIBRARIES: $(lib_LTLIBRARIES) else :; fi; \ done; \ test -z "$$list2" || { \ + echo " $(MKDIR_P) '$(DESTDIR)$(libdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libdir)" || exit 1; \ echo " $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 '$(DESTDIR)$(libdir)'"; \ $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 "$(DESTDIR)$(libdir)"; \ } @@ -424,7 +467,7 @@ clean-libLTLIBRARIES: echo "rm -f \"$${dir}/so_locations\""; \ rm -f "$${dir}/so_locations"; \ done -libgnunettun.la: $(libgnunettun_la_OBJECTS) $(libgnunettun_la_DEPENDENCIES) +libgnunettun.la: $(libgnunettun_la_OBJECTS) $(libgnunettun_la_DEPENDENCIES) $(EXTRA_libgnunettun_la_DEPENDENCIES) $(AM_V_CCLD)$(libgnunettun_la_LINK) -rpath $(libdir) $(libgnunettun_la_OBJECTS) $(libgnunettun_la_LIBADD) $(LIBS) clean-checkPROGRAMS: @@ -435,7 +478,7 @@ clean-checkPROGRAMS: list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ echo " rm -f" $$list; \ rm -f $$list -test_tun$(EXEEXT): $(test_tun_OBJECTS) $(test_tun_DEPENDENCIES) +test_tun$(EXEEXT): $(test_tun_OBJECTS) $(test_tun_DEPENDENCIES) $(EXTRA_test_tun_DEPENDENCIES) @rm -f test_tun$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_tun_OBJECTS) $(test_tun_LDADD) $(LIBS) @@ -451,26 +494,23 @@ distclean-compile: .c.o: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c $< .c.obj: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'` @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c `$(CYGPATH_W) '$<'` +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c `$(CYGPATH_W) '$<'` .c.lo: @am__fastdepCC_TRUE@ $(AM_V_CC)$(LTCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LTCOMPILE) -c -o $@ $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LTCOMPILE) -c -o $@ $< mostlyclean-libtool: -rm -f *.lo @@ -611,14 +651,15 @@ check-TESTS: $(TESTS) fi; \ dashes=`echo "$$dashes" | sed s/./=/g`; \ if test "$$failed" -eq 0; then \ - echo "$$grn$$dashes"; \ + col="$$grn"; \ else \ - echo "$$red$$dashes"; \ + col="$$red"; \ fi; \ - echo "$$banner"; \ - test -z "$$skipped" || echo "$$skipped"; \ - test -z "$$report" || echo "$$report"; \ - echo "$$dashes$$std"; \ + echo "$${col}$$dashes$${std}"; \ + echo "$${col}$$banner$${std}"; \ + test -z "$$skipped" || echo "$${col}$$skipped$${std}"; \ + test -z "$$report" || echo "$${col}$$report$${std}"; \ + echo "$${col}$$dashes$${std}"; \ test "$$failed" -eq 0; \ else :; fi @@ -671,10 +712,15 @@ install-am: all-am installcheck: installcheck-am install-strip: - $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ - install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ - `test -z '$(STRIP)' || \ - echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi mostlyclean-generic: clean-generic: diff --git a/src/util/Makefile.am b/src/util/Makefile.am index 8414ef2..425cc8c 100644 --- a/src/util/Makefile.am +++ b/src/util/Makefile.am @@ -2,6 +2,8 @@ INCLUDES = -I$(top_srcdir)/src/include -I$(top_builddir)/src/include plugindir = $(libdir)/gnunet +libexecdir= $(pkglibdir)/libexec/ + pkgcfgdir= $(pkgdatadir)/config.d/ dist_pkgcfg_DATA = \ @@ -14,7 +16,7 @@ if MINGW noinst_LTLIBRARIES = \ libgnunetutilwin.la libgnunetutilwin_la_SOURCES = \ - win.cc \ + win.c \ winproc.c libgnunetutilwin_la_LDFLAGS = \ -no-undefined -Wl,--export-all-symbols @@ -22,6 +24,7 @@ libgnunetutilwin_la_LIBADD = \ -lshell32 -liconv -lstdc++ \ -lcomdlg32 -lgdi32 -liphlpapi WINLIB = libgnunetutilwin.la +W32CAT = w32cat endif if !MINGW @@ -33,8 +36,11 @@ if USE_COVERAGE XLIB = -lgcov endif +w32cat_SOURCES = w32cat.c + noinst_PROGRAMS = \ gnunet-config-diff \ + $(W32CAT) \ test_common_logging_dummy @@ -70,6 +76,7 @@ libgnunetutil_la_SOURCES = \ container_slist.c \ crypto_aes.c \ crypto_crc.c \ + crypto_ecc.c \ crypto_hash.c \ crypto_hkdf.c \ crypto_kdf.c \ @@ -107,17 +114,23 @@ libgnunetutil_la_LIBADD = \ $(GCLIBADD) $(WINLIB) \ $(LIBGCRYPT_LIBS) \ $(LTLIBICONV) \ + $(LTLIBINTL) \ -lltdl -lz -lunistring $(XLIB) libgnunetutil_la_LDFLAGS = \ $(GN_LIB_LDFLAGS) \ - -version-info 8:0:0 + -version-info 11:0:2 + +libexec_PROGRAMS = \ + gnunet-service-resolver bin_PROGRAMS = \ - gnunet-service-resolver \ gnunet-resolver \ - gnunet-rsa + gnunet-config \ + gnunet-ecc \ + gnunet-rsa \ + gnunet-uri gnunet_service_resolver_SOURCES = \ @@ -142,10 +155,37 @@ gnunet_rsa_SOURCES = \ gnunet-rsa.c gnunet_rsa_LDADD = \ $(top_builddir)/src/util/libgnunetutil.la \ - $(GN_LIBINTL) + $(GN_LIBINTL) -lgcrypt gnunet_rsa_DEPENDENCIES = \ libgnunetutil.la + +gnunet_ecc_SOURCES = \ + gnunet-ecc.c +gnunet_ecc_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(GN_LIBINTL) -lgcrypt +gnunet_ecc_DEPENDENCIES = \ + libgnunetutil.la + + +gnunet_config_SOURCES = \ + gnunet-config.c +gnunet_config_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(GN_LIBINTL) +gnunet_config_DEPENDENCIES = \ + libgnunetutil.la + + +gnunet_uri_SOURCES = \ + gnunet-uri.c +gnunet_uri_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(GN_LIBINTL) +gnunet_uri_DEPENDENCIES = \ + libgnunetutil.la + plugin_LTLIBRARIES = \ libgnunet_plugin_test.la @@ -156,7 +196,8 @@ libgnunet_plugin_test_la_LDFLAGS = \ if HAVE_BENCHMARKS BENCHMARKS = \ - perf_crypto_hash + perf_crypto_hash \ + perf_malloc endif check_PROGRAMS = \ @@ -174,6 +215,7 @@ check_PROGRAMS = \ test_crypto_aes \ test_crypto_aes_weak \ test_crypto_crc \ + test_crypto_ecc \ test_crypto_hash \ test_crypto_hkdf \ test_crypto_ksk \ @@ -223,6 +265,8 @@ test_os_start_process_SOURCES = \ test_os_start_process.c test_os_start_process_LDADD = \ $(top_builddir)/src/util/libgnunetutil.la +test_os_start_process_DEPENDENCIES = \ + $(WINCAT) test_client_SOURCES = \ test_client.c @@ -295,6 +339,11 @@ test_crypto_crc_SOURCES = \ test_crypto_crc_LDADD = \ $(top_builddir)/src/util/libgnunetutil.la +test_crypto_ecc_SOURCES = \ + test_crypto_ecc.c +test_crypto_ecc_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la + test_crypto_hash_SOURCES = \ test_crypto_hash.c test_crypto_hash_LDADD = \ @@ -456,6 +505,11 @@ perf_crypto_hash_SOURCES = \ perf_crypto_hash_LDADD = \ $(top_builddir)/src/util/libgnunetutil.la +perf_malloc_SOURCES = \ + perf_malloc.c +perf_malloc_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la + EXTRA_DIST = \ test_configuration_data.conf \ diff --git a/src/util/Makefile.in b/src/util/Makefile.in index 5ea0157..9406228 100644 --- a/src/util/Makefile.in +++ b/src/util/Makefile.in @@ -1,9 +1,9 @@ -# Makefile.in generated by automake 1.11.1 from Makefile.am. +# Makefile.in generated by automake 1.11.6 from Makefile.am. # @configure_input@ # Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, -# 2003, 2004, 2005, 2006, 2007, 2008, 2009 Free Software Foundation, -# Inc. +# 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Free Software +# Foundation, Inc. # This Makefile.in is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. @@ -18,6 +18,23 @@ VPATH = @srcdir@ +am__make_dryrun = \ + { \ + am__dry=no; \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + echo 'am--echo: ; @echo "AM" OK' | $(MAKE) -f - 2>/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } pkgdatadir = $(datadir)/@PACKAGE@ pkgincludedir = $(includedir)/@PACKAGE@ pkglibdir = $(libdir)/@PACKAGE@ @@ -37,10 +54,11 @@ POST_UNINSTALL = : build_triplet = @build@ host_triplet = @host@ target_triplet = @target@ -noinst_PROGRAMS = gnunet-config-diff$(EXEEXT) \ +noinst_PROGRAMS = gnunet-config-diff$(EXEEXT) $(am__EXEEXT_3) \ test_common_logging_dummy$(EXEEXT) -bin_PROGRAMS = gnunet-service-resolver$(EXEEXT) \ - gnunet-resolver$(EXEEXT) gnunet-rsa$(EXEEXT) +libexec_PROGRAMS = gnunet-service-resolver$(EXEEXT) +bin_PROGRAMS = gnunet-resolver$(EXEEXT) gnunet-config$(EXEEXT) \ + gnunet-ecc$(EXEEXT) gnunet-rsa$(EXEEXT) gnunet-uri$(EXEEXT) check_PROGRAMS = test_bio$(EXEEXT) test_client$(EXEEXT) \ test_common_allocation$(EXEEXT) test_common_endian$(EXEEXT) \ test_common_logging$(EXEEXT) test_configuration$(EXEEXT) \ @@ -49,11 +67,12 @@ check_PROGRAMS = test_bio$(EXEEXT) test_client$(EXEEXT) \ test_container_multihashmap$(EXEEXT) \ test_container_heap$(EXEEXT) test_container_slist$(EXEEXT) \ test_crypto_aes$(EXEEXT) test_crypto_aes_weak$(EXEEXT) \ - test_crypto_crc$(EXEEXT) test_crypto_hash$(EXEEXT) \ - test_crypto_hkdf$(EXEEXT) test_crypto_ksk$(EXEEXT) \ - test_crypto_random$(EXEEXT) test_crypto_rsa$(EXEEXT) \ - test_disk$(EXEEXT) test_getopt$(EXEEXT) \ - test_connection$(EXEEXT) test_connection_addressing$(EXEEXT) \ + test_crypto_crc$(EXEEXT) test_crypto_ecc$(EXEEXT) \ + test_crypto_hash$(EXEEXT) test_crypto_hkdf$(EXEEXT) \ + test_crypto_ksk$(EXEEXT) test_crypto_random$(EXEEXT) \ + test_crypto_rsa$(EXEEXT) test_disk$(EXEEXT) \ + test_getopt$(EXEEXT) test_connection$(EXEEXT) \ + test_connection_addressing$(EXEEXT) \ test_connection_receive_cancel$(EXEEXT) \ test_connection_timeout$(EXEEXT) \ test_connection_timeout_no_connect$(EXEEXT) \ @@ -75,14 +94,15 @@ DIST_COMMON = $(dist_pkgcfg_DATA) $(srcdir)/Makefile.am \ ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 am__aclocal_m4_deps = $(top_srcdir)/m4/absolute-header.m4 \ $(top_srcdir)/m4/align.m4 $(top_srcdir)/m4/argz.m4 \ - $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/iconv.m4 \ - $(top_srcdir)/m4/lib-ld.m4 $(top_srcdir)/m4/lib-link.m4 \ - $(top_srcdir)/m4/lib-prefix.m4 $(top_srcdir)/m4/libcurl.m4 \ - $(top_srcdir)/m4/libgcrypt.m4 $(top_srcdir)/m4/libtool.m4 \ - $(top_srcdir)/m4/libunistring.m4 $(top_srcdir)/m4/ltdl.m4 \ - $(top_srcdir)/m4/ltoptions.m4 $(top_srcdir)/m4/ltsugar.m4 \ - $(top_srcdir)/m4/ltversion.m4 $(top_srcdir)/m4/lt~obsolete.m4 \ - $(top_srcdir)/m4/nls.m4 $(top_srcdir)/m4/po.m4 \ + $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/glib-2.0.m4 \ + $(top_srcdir)/m4/iconv.m4 $(top_srcdir)/m4/lib-ld.m4 \ + $(top_srcdir)/m4/lib-link.m4 $(top_srcdir)/m4/lib-prefix.m4 \ + $(top_srcdir)/m4/libcurl.m4 $(top_srcdir)/m4/libgcrypt.m4 \ + $(top_srcdir)/m4/libtool.m4 $(top_srcdir)/m4/libunistring.m4 \ + $(top_srcdir)/m4/ltdl.m4 $(top_srcdir)/m4/ltoptions.m4 \ + $(top_srcdir)/m4/ltsugar.m4 $(top_srcdir)/m4/ltversion.m4 \ + $(top_srcdir)/m4/lt~obsolete.m4 $(top_srcdir)/m4/nls.m4 \ + $(top_srcdir)/m4/pkg.m4 $(top_srcdir)/m4/po.m4 \ $(top_srcdir)/m4/progtest.m4 $(top_srcdir)/acinclude.m4 \ $(top_srcdir)/configure.ac am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ @@ -112,17 +132,23 @@ am__nobase_list = $(am__nobase_strip_setup); \ am__base_list = \ sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \ sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g' +am__uninstall_files_from_dir = { \ + test -z "$$files" \ + || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \ + || { echo " ( cd '$$dir' && rm -f" $$files ")"; \ + $(am__cd) "$$dir" && rm -f $$files; }; \ + } am__installdirs = "$(DESTDIR)$(libdir)" "$(DESTDIR)$(plugindir)" \ - "$(DESTDIR)$(bindir)" "$(DESTDIR)$(pkgcfgdir)" \ - "$(DESTDIR)$(pkgcfgdir)" + "$(DESTDIR)$(bindir)" "$(DESTDIR)$(libexecdir)" \ + "$(DESTDIR)$(pkgcfgdir)" "$(DESTDIR)$(pkgcfgdir)" LTLIBRARIES = $(lib_LTLIBRARIES) $(noinst_LTLIBRARIES) \ $(plugin_LTLIBRARIES) libgnunet_plugin_test_la_LIBADD = am_libgnunet_plugin_test_la_OBJECTS = test_plugin_plug.lo libgnunet_plugin_test_la_OBJECTS = \ $(am_libgnunet_plugin_test_la_OBJECTS) -AM_V_lt = $(am__v_lt_$(V)) -am__v_lt_ = $(am__v_lt_$(AM_DEFAULT_VERBOSITY)) +AM_V_lt = $(am__v_lt_@AM_V@) +am__v_lt_ = $(am__v_lt_@AM_DEFAULT_V@) am__v_lt_0 = --silent libgnunet_plugin_test_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ @@ -130,38 +156,45 @@ libgnunet_plugin_test_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ $(LDFLAGS) -o $@ am__DEPENDENCIES_1 = libgnunetutil_la_DEPENDENCIES = $(WINLIB) $(am__DEPENDENCIES_1) \ - $(am__DEPENDENCIES_1) $(am__DEPENDENCIES_1) + $(am__DEPENDENCIES_1) $(am__DEPENDENCIES_1) \ + $(am__DEPENDENCIES_1) am_libgnunetutil_la_OBJECTS = bandwidth.lo bio.lo client.lo \ common_allocation.lo common_endian.lo common_logging.lo \ configuration.lo connection.lo container_bloomfilter.lo \ container_heap.lo container_meta_data.lo \ container_multihashmap.lo container_slist.lo crypto_aes.lo \ - crypto_crc.lo crypto_hash.lo crypto_hkdf.lo crypto_kdf.lo \ - crypto_ksk.lo crypto_random.lo crypto_rsa.lo disk.lo getopt.lo \ - getopt_helpers.lo helper.lo load.lo network.lo \ - os_installation.lo os_network.lo os_priority.lo peer.lo \ - plugin.lo program.lo pseudonym.lo resolver_api.lo scheduler.lo \ - server.lo server_mst.lo server_nc.lo server_tc.lo service.lo \ - signal.lo strings.lo time.lo speedup.lo + crypto_crc.lo crypto_ecc.lo crypto_hash.lo crypto_hkdf.lo \ + crypto_kdf.lo crypto_ksk.lo crypto_random.lo crypto_rsa.lo \ + disk.lo getopt.lo getopt_helpers.lo helper.lo load.lo \ + network.lo os_installation.lo os_network.lo os_priority.lo \ + peer.lo plugin.lo program.lo pseudonym.lo resolver_api.lo \ + scheduler.lo server.lo server_mst.lo server_nc.lo server_tc.lo \ + service.lo signal.lo strings.lo time.lo speedup.lo libgnunetutil_la_OBJECTS = $(am_libgnunetutil_la_OBJECTS) libgnunetutil_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ $(AM_CFLAGS) $(CFLAGS) $(libgnunetutil_la_LDFLAGS) $(LDFLAGS) \ -o $@ libgnunetutilwin_la_DEPENDENCIES = -am__libgnunetutilwin_la_SOURCES_DIST = win.cc winproc.c +am__libgnunetutilwin_la_SOURCES_DIST = win.c winproc.c @MINGW_TRUE@am_libgnunetutilwin_la_OBJECTS = win.lo winproc.lo libgnunetutilwin_la_OBJECTS = $(am_libgnunetutilwin_la_OBJECTS) -libgnunetutilwin_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CXX \ - $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CXXLD) \ - $(AM_CXXFLAGS) $(CXXFLAGS) $(libgnunetutilwin_la_LDFLAGS) \ +libgnunetutilwin_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ + $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ + $(AM_CFLAGS) $(CFLAGS) $(libgnunetutilwin_la_LDFLAGS) \ $(LDFLAGS) -o $@ @MINGW_TRUE@am_libgnunetutilwin_la_rpath = @MINGW_FALSE@am__EXEEXT_1 = test_server_with_client_unix$(EXEEXT) -@HAVE_BENCHMARKS_TRUE@am__EXEEXT_2 = perf_crypto_hash$(EXEEXT) -PROGRAMS = $(bin_PROGRAMS) $(noinst_PROGRAMS) +@HAVE_BENCHMARKS_TRUE@am__EXEEXT_2 = perf_crypto_hash$(EXEEXT) \ +@HAVE_BENCHMARKS_TRUE@ perf_malloc$(EXEEXT) +@MINGW_TRUE@am__EXEEXT_3 = w32cat$(EXEEXT) +PROGRAMS = $(bin_PROGRAMS) $(libexec_PROGRAMS) $(noinst_PROGRAMS) +am_gnunet_config_OBJECTS = gnunet-config.$(OBJEXT) +gnunet_config_OBJECTS = $(am_gnunet_config_OBJECTS) am_gnunet_config_diff_OBJECTS = gnunet-config-diff.$(OBJEXT) gnunet_config_diff_OBJECTS = $(am_gnunet_config_diff_OBJECTS) +am_gnunet_ecc_OBJECTS = gnunet-ecc.$(OBJEXT) +gnunet_ecc_OBJECTS = $(am_gnunet_ecc_OBJECTS) am_gnunet_resolver_OBJECTS = gnunet-resolver.$(OBJEXT) gnunet_resolver_OBJECTS = $(am_gnunet_resolver_OBJECTS) am_gnunet_rsa_OBJECTS = gnunet-rsa.$(OBJEXT) @@ -170,10 +203,15 @@ am_gnunet_service_resolver_OBJECTS = \ gnunet-service-resolver.$(OBJEXT) gnunet_service_resolver_OBJECTS = \ $(am_gnunet_service_resolver_OBJECTS) +am_gnunet_uri_OBJECTS = gnunet-uri.$(OBJEXT) +gnunet_uri_OBJECTS = $(am_gnunet_uri_OBJECTS) am_perf_crypto_hash_OBJECTS = perf_crypto_hash.$(OBJEXT) perf_crypto_hash_OBJECTS = $(am_perf_crypto_hash_OBJECTS) perf_crypto_hash_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la +am_perf_malloc_OBJECTS = perf_malloc.$(OBJEXT) +perf_malloc_OBJECTS = $(am_perf_malloc_OBJECTS) +perf_malloc_DEPENDENCIES = $(top_builddir)/src/util/libgnunetutil.la am_test_bio_OBJECTS = test_bio.$(OBJEXT) test_bio_OBJECTS = $(am_test_bio_OBJECTS) test_bio_DEPENDENCIES = $(top_builddir)/src/util/libgnunetutil.la @@ -279,6 +317,10 @@ am_test_crypto_crc_OBJECTS = test_crypto_crc.$(OBJEXT) test_crypto_crc_OBJECTS = $(am_test_crypto_crc_OBJECTS) test_crypto_crc_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la +am_test_crypto_ecc_OBJECTS = test_crypto_ecc.$(OBJEXT) +test_crypto_ecc_OBJECTS = $(am_test_crypto_ecc_OBJECTS) +test_crypto_ecc_DEPENDENCIES = \ + $(top_builddir)/src/util/libgnunetutil.la am_test_crypto_hash_OBJECTS = test_crypto_hash.$(OBJEXT) test_crypto_hash_OBJECTS = $(am_test_crypto_hash_OBJECTS) test_crypto_hash_DEPENDENCIES = \ @@ -315,8 +357,6 @@ test_os_priority_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la am_test_os_start_process_OBJECTS = test_os_start_process.$(OBJEXT) test_os_start_process_OBJECTS = $(am_test_os_start_process_OBJECTS) -test_os_start_process_DEPENDENCIES = \ - $(top_builddir)/src/util/libgnunetutil.la am_test_peer_OBJECTS = test_peer.$(OBJEXT) test_peer_OBJECTS = $(am_test_peer_OBJECTS) test_peer_DEPENDENCIES = $(top_builddir)/src/util/libgnunetutil.la @@ -379,6 +419,9 @@ test_strings_DEPENDENCIES = $(top_builddir)/src/util/libgnunetutil.la am_test_time_OBJECTS = test_time.$(OBJEXT) test_time_OBJECTS = $(am_test_time_OBJECTS) test_time_DEPENDENCIES = $(top_builddir)/src/util/libgnunetutil.la +am_w32cat_OBJECTS = w32cat.$(OBJEXT) +w32cat_OBJECTS = $(am_w32cat_OBJECTS) +w32cat_LDADD = $(LDADD) DEFAULT_INCLUDES = -I.@am__isrc@ -I$(top_builddir) depcomp = $(SHELL) $(top_srcdir)/depcomp am__depfiles_maybe = depfiles @@ -389,43 +432,29 @@ LTCOMPILE = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) \ $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) \ $(AM_CFLAGS) $(CFLAGS) -AM_V_CC = $(am__v_CC_$(V)) -am__v_CC_ = $(am__v_CC_$(AM_DEFAULT_VERBOSITY)) +AM_V_CC = $(am__v_CC_@AM_V@) +am__v_CC_ = $(am__v_CC_@AM_DEFAULT_V@) am__v_CC_0 = @echo " CC " $@; -AM_V_at = $(am__v_at_$(V)) -am__v_at_ = $(am__v_at_$(AM_DEFAULT_VERBOSITY)) +AM_V_at = $(am__v_at_@AM_V@) +am__v_at_ = $(am__v_at_@AM_DEFAULT_V@) am__v_at_0 = @ CCLD = $(CC) LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ $(AM_LDFLAGS) $(LDFLAGS) -o $@ -AM_V_CCLD = $(am__v_CCLD_$(V)) -am__v_CCLD_ = $(am__v_CCLD_$(AM_DEFAULT_VERBOSITY)) +AM_V_CCLD = $(am__v_CCLD_@AM_V@) +am__v_CCLD_ = $(am__v_CCLD_@AM_DEFAULT_V@) am__v_CCLD_0 = @echo " CCLD " $@; -CXXCOMPILE = $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) \ - $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -LTCXXCOMPILE = $(LIBTOOL) $(AM_V_lt) --tag=CXX $(AM_LIBTOOLFLAGS) \ - $(LIBTOOLFLAGS) --mode=compile $(CXX) $(DEFS) \ - $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) \ - $(AM_CXXFLAGS) $(CXXFLAGS) -AM_V_CXX = $(am__v_CXX_$(V)) -am__v_CXX_ = $(am__v_CXX_$(AM_DEFAULT_VERBOSITY)) -am__v_CXX_0 = @echo " CXX " $@; -CXXLD = $(CXX) -CXXLINK = $(LIBTOOL) $(AM_V_lt) --tag=CXX $(AM_LIBTOOLFLAGS) \ - $(LIBTOOLFLAGS) --mode=link $(CXXLD) $(AM_CXXFLAGS) \ - $(CXXFLAGS) $(AM_LDFLAGS) $(LDFLAGS) -o $@ -AM_V_CXXLD = $(am__v_CXXLD_$(V)) -am__v_CXXLD_ = $(am__v_CXXLD_$(AM_DEFAULT_VERBOSITY)) -am__v_CXXLD_0 = @echo " CXXLD " $@; -AM_V_GEN = $(am__v_GEN_$(V)) -am__v_GEN_ = $(am__v_GEN_$(AM_DEFAULT_VERBOSITY)) +AM_V_GEN = $(am__v_GEN_@AM_V@) +am__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@) am__v_GEN_0 = @echo " GEN " $@; SOURCES = $(libgnunet_plugin_test_la_SOURCES) \ $(libgnunetutil_la_SOURCES) $(libgnunetutilwin_la_SOURCES) \ - $(gnunet_config_diff_SOURCES) $(gnunet_resolver_SOURCES) \ + $(gnunet_config_SOURCES) $(gnunet_config_diff_SOURCES) \ + $(gnunet_ecc_SOURCES) $(gnunet_resolver_SOURCES) \ $(gnunet_rsa_SOURCES) $(gnunet_service_resolver_SOURCES) \ - $(perf_crypto_hash_SOURCES) $(test_bio_SOURCES) \ + $(gnunet_uri_SOURCES) $(perf_crypto_hash_SOURCES) \ + $(perf_malloc_SOURCES) $(test_bio_SOURCES) \ $(test_client_SOURCES) $(test_common_allocation_SOURCES) \ $(test_common_endian_SOURCES) $(test_common_logging_SOURCES) \ $(test_common_logging_dummy_SOURCES) \ @@ -442,27 +471,29 @@ SOURCES = $(libgnunet_plugin_test_la_SOURCES) \ $(test_container_multihashmap_SOURCES) \ $(test_container_slist_SOURCES) $(test_crypto_aes_SOURCES) \ $(test_crypto_aes_weak_SOURCES) $(test_crypto_crc_SOURCES) \ - $(test_crypto_hash_SOURCES) $(test_crypto_hkdf_SOURCES) \ - $(test_crypto_ksk_SOURCES) $(test_crypto_random_SOURCES) \ - $(test_crypto_rsa_SOURCES) $(test_disk_SOURCES) \ - $(test_getopt_SOURCES) $(test_os_network_SOURCES) \ - $(test_os_priority_SOURCES) $(test_os_start_process_SOURCES) \ - $(test_peer_SOURCES) $(test_plugin_SOURCES) \ - $(test_program_SOURCES) $(test_pseudonym_SOURCES) \ - $(test_resolver_api_SOURCES) $(test_scheduler_SOURCES) \ - $(test_scheduler_delay_SOURCES) $(test_server_SOURCES) \ - $(test_server_disconnect_SOURCES) \ + $(test_crypto_ecc_SOURCES) $(test_crypto_hash_SOURCES) \ + $(test_crypto_hkdf_SOURCES) $(test_crypto_ksk_SOURCES) \ + $(test_crypto_random_SOURCES) $(test_crypto_rsa_SOURCES) \ + $(test_disk_SOURCES) $(test_getopt_SOURCES) \ + $(test_os_network_SOURCES) $(test_os_priority_SOURCES) \ + $(test_os_start_process_SOURCES) $(test_peer_SOURCES) \ + $(test_plugin_SOURCES) $(test_program_SOURCES) \ + $(test_pseudonym_SOURCES) $(test_resolver_api_SOURCES) \ + $(test_scheduler_SOURCES) $(test_scheduler_delay_SOURCES) \ + $(test_server_SOURCES) $(test_server_disconnect_SOURCES) \ $(test_server_mst_interrupt_SOURCES) \ $(test_server_with_client_SOURCES) \ $(test_server_with_client_unix_SOURCES) \ $(test_service_SOURCES) $(test_speedup_SOURCES) \ - $(test_strings_SOURCES) $(test_time_SOURCES) + $(test_strings_SOURCES) $(test_time_SOURCES) $(w32cat_SOURCES) DIST_SOURCES = $(libgnunet_plugin_test_la_SOURCES) \ $(libgnunetutil_la_SOURCES) \ $(am__libgnunetutilwin_la_SOURCES_DIST) \ - $(gnunet_config_diff_SOURCES) $(gnunet_resolver_SOURCES) \ + $(gnunet_config_SOURCES) $(gnunet_config_diff_SOURCES) \ + $(gnunet_ecc_SOURCES) $(gnunet_resolver_SOURCES) \ $(gnunet_rsa_SOURCES) $(gnunet_service_resolver_SOURCES) \ - $(perf_crypto_hash_SOURCES) $(test_bio_SOURCES) \ + $(gnunet_uri_SOURCES) $(perf_crypto_hash_SOURCES) \ + $(perf_malloc_SOURCES) $(test_bio_SOURCES) \ $(test_client_SOURCES) $(test_common_allocation_SOURCES) \ $(test_common_endian_SOURCES) $(test_common_logging_SOURCES) \ $(test_common_logging_dummy_SOURCES) \ @@ -479,21 +510,26 @@ DIST_SOURCES = $(libgnunet_plugin_test_la_SOURCES) \ $(test_container_multihashmap_SOURCES) \ $(test_container_slist_SOURCES) $(test_crypto_aes_SOURCES) \ $(test_crypto_aes_weak_SOURCES) $(test_crypto_crc_SOURCES) \ - $(test_crypto_hash_SOURCES) $(test_crypto_hkdf_SOURCES) \ - $(test_crypto_ksk_SOURCES) $(test_crypto_random_SOURCES) \ - $(test_crypto_rsa_SOURCES) $(test_disk_SOURCES) \ - $(test_getopt_SOURCES) $(test_os_network_SOURCES) \ - $(test_os_priority_SOURCES) $(test_os_start_process_SOURCES) \ - $(test_peer_SOURCES) $(test_plugin_SOURCES) \ - $(test_program_SOURCES) $(test_pseudonym_SOURCES) \ - $(test_resolver_api_SOURCES) $(test_scheduler_SOURCES) \ - $(test_scheduler_delay_SOURCES) $(test_server_SOURCES) \ - $(test_server_disconnect_SOURCES) \ + $(test_crypto_ecc_SOURCES) $(test_crypto_hash_SOURCES) \ + $(test_crypto_hkdf_SOURCES) $(test_crypto_ksk_SOURCES) \ + $(test_crypto_random_SOURCES) $(test_crypto_rsa_SOURCES) \ + $(test_disk_SOURCES) $(test_getopt_SOURCES) \ + $(test_os_network_SOURCES) $(test_os_priority_SOURCES) \ + $(test_os_start_process_SOURCES) $(test_peer_SOURCES) \ + $(test_plugin_SOURCES) $(test_program_SOURCES) \ + $(test_pseudonym_SOURCES) $(test_resolver_api_SOURCES) \ + $(test_scheduler_SOURCES) $(test_scheduler_delay_SOURCES) \ + $(test_server_SOURCES) $(test_server_disconnect_SOURCES) \ $(test_server_mst_interrupt_SOURCES) \ $(test_server_with_client_SOURCES) \ $(test_server_with_client_unix_SOURCES) \ $(test_service_SOURCES) $(test_speedup_SOURCES) \ - $(test_strings_SOURCES) $(test_time_SOURCES) + $(test_strings_SOURCES) $(test_time_SOURCES) $(w32cat_SOURCES) +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac DATA = $(dist_pkgcfg_DATA) $(pkgcfg_DATA) ETAGS = etags CTAGS = ctags @@ -535,6 +571,10 @@ EXEEXT = @EXEEXT@ EXT_LIBS = @EXT_LIBS@ EXT_LIB_PATH = @EXT_LIB_PATH@ FGREP = @FGREP@ +GLIB_CFLAGS = @GLIB_CFLAGS@ +GLIB_GENMARSHAL = @GLIB_GENMARSHAL@ +GLIB_LIBS = @GLIB_LIBS@ +GLIB_MKENUMS = @GLIB_MKENUMS@ GMSGFMT = @GMSGFMT@ GMSGFMT_015 = @GMSGFMT_015@ GNUNETDNS_GROUP = @GNUNETDNS_GROUP@ @@ -545,6 +585,7 @@ GN_LIBINTL = @GN_LIBINTL@ GN_LIB_LDFLAGS = @GN_LIB_LDFLAGS@ GN_PLUGIN_LDFLAGS = @GN_PLUGIN_LDFLAGS@ GN_USER_HOME_DIR = @GN_USER_HOME_DIR@ +GOBJECT_QUERY = @GOBJECT_QUERY@ GREP = @GREP@ HAVE_LIBUNISTRING = @HAVE_LIBUNISTRING@ INCLTDL = @INCLTDL@ @@ -567,6 +608,8 @@ LIBCURL_CPPFLAGS = @LIBCURL_CPPFLAGS@ LIBGCRYPT_CFLAGS = @LIBGCRYPT_CFLAGS@ LIBGCRYPT_CONFIG = @LIBGCRYPT_CONFIG@ LIBGCRYPT_LIBS = @LIBGCRYPT_LIBS@ +LIBGTOP_CFLAGS = @LIBGTOP_CFLAGS@ +LIBGTOP_LIBS = @LIBGTOP_LIBS@ LIBICONV = @LIBICONV@ LIBINTL = @LIBINTL@ LIBLTDL = @LIBLTDL@ @@ -588,6 +631,7 @@ LT_CONFIG_H = @LT_CONFIG_H@ LT_DLLOADERS = @LT_DLLOADERS@ LT_DLPREOPEN = @LT_DLPREOPEN@ MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ MKDIR_P = @MKDIR_P@ MONKEYPREFIX = @MONKEYPREFIX@ MSGFMT = @MSGFMT@ @@ -597,6 +641,7 @@ MYSQL_CPPFLAGS = @MYSQL_CPPFLAGS@ MYSQL_LDFLAGS = @MYSQL_LDFLAGS@ NM = @NM@ NMEDIT = @NMEDIT@ +NSS_DIR = @NSS_DIR@ OBJC = @OBJC@ OBJCDEPMODE = @OBJCDEPMODE@ OBJCFLAGS = @OBJCFLAGS@ @@ -612,6 +657,7 @@ PACKAGE_TARNAME = @PACKAGE_TARNAME@ PACKAGE_URL = @PACKAGE_URL@ PACKAGE_VERSION = @PACKAGE_VERSION@ PATH_SEPARATOR = @PATH_SEPARATOR@ +PKG_CONFIG = @PKG_CONFIG@ POSTGRES_CPPFLAGS = @POSTGRES_CPPFLAGS@ POSTGRES_LDFLAGS = @POSTGRES_LDFLAGS@ POSUB = @POSUB@ @@ -643,6 +689,7 @@ abs_builddir = @abs_builddir@ abs_srcdir = @abs_srcdir@ abs_top_builddir = @abs_top_builddir@ abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ ac_ct_CC = @ac_ct_CC@ ac_ct_CXX = @ac_ct_CXX@ ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ @@ -665,6 +712,7 @@ datarootdir = @datarootdir@ docdir = @docdir@ dvidir = @dvidir@ exec_prefix = @exec_prefix@ +gitcommand = @gitcommand@ host = @host@ host_alias = @host_alias@ host_cpu = @host_cpu@ @@ -675,10 +723,9 @@ includedir = @includedir@ infodir = @infodir@ install_sh = @install_sh@ libdir = @libdir@ -libexecdir = @libexecdir@ +libexecdir = $(pkglibdir)/libexec/ localedir = @localedir@ localstatedir = @localstatedir@ -lt_ECHO = @lt_ECHO@ ltdl_LIBOBJS = @ltdl_LIBOBJS@ ltdl_LTLIBOBJS = @ltdl_LTLIBOBJS@ mandir = @mandir@ @@ -696,6 +743,7 @@ sbindir = @sbindir@ sharedstatedir = @sharedstatedir@ srcdir = @srcdir@ subdirs = @subdirs@ +svnversioncommand = @svnversioncommand@ sys_symbol_underscore = @sys_symbol_underscore@ sysconfdir = @sysconfdir@ target = @target@ @@ -719,7 +767,7 @@ pkgcfg_DATA = \ @MINGW_TRUE@ libgnunetutilwin.la @MINGW_TRUE@libgnunetutilwin_la_SOURCES = \ -@MINGW_TRUE@ win.cc \ +@MINGW_TRUE@ win.c \ @MINGW_TRUE@ winproc.c @MINGW_TRUE@libgnunetutilwin_la_LDFLAGS = \ @@ -730,9 +778,11 @@ pkgcfg_DATA = \ @MINGW_TRUE@ -lcomdlg32 -lgdi32 -liphlpapi @MINGW_TRUE@WINLIB = libgnunetutilwin.la +@MINGW_TRUE@W32CAT = w32cat @MINGW_FALSE@SERVER_CLIENT_UNIX = test_server_with_client_unix @USE_COVERAGE_TRUE@AM_CFLAGS = --coverage -O0 @USE_COVERAGE_TRUE@XLIB = -lgcov +w32cat_SOURCES = w32cat.c gnunet_config_diff_SOURCES = \ gnunet-config-diff.c @@ -768,6 +818,7 @@ libgnunetutil_la_SOURCES = \ container_slist.c \ crypto_aes.c \ crypto_crc.c \ + crypto_ecc.c \ crypto_hash.c \ crypto_hkdf.c \ crypto_kdf.c \ @@ -804,11 +855,12 @@ libgnunetutil_la_LIBADD = \ $(GCLIBADD) $(WINLIB) \ $(LIBGCRYPT_LIBS) \ $(LTLIBICONV) \ + $(LTLIBINTL) \ -lltdl -lz -lunistring $(XLIB) libgnunetutil_la_LDFLAGS = \ $(GN_LIB_LDFLAGS) \ - -version-info 8:0:0 + -version-info 11:0:2 gnunet_service_resolver_SOURCES = \ gnunet-service-resolver.c @@ -835,11 +887,41 @@ gnunet_rsa_SOURCES = \ gnunet_rsa_LDADD = \ $(top_builddir)/src/util/libgnunetutil.la \ - $(GN_LIBINTL) + $(GN_LIBINTL) -lgcrypt gnunet_rsa_DEPENDENCIES = \ libgnunetutil.la +gnunet_ecc_SOURCES = \ + gnunet-ecc.c + +gnunet_ecc_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(GN_LIBINTL) -lgcrypt + +gnunet_ecc_DEPENDENCIES = \ + libgnunetutil.la + +gnunet_config_SOURCES = \ + gnunet-config.c + +gnunet_config_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(GN_LIBINTL) + +gnunet_config_DEPENDENCIES = \ + libgnunetutil.la + +gnunet_uri_SOURCES = \ + gnunet-uri.c + +gnunet_uri_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la \ + $(GN_LIBINTL) + +gnunet_uri_DEPENDENCIES = \ + libgnunetutil.la + plugin_LTLIBRARIES = \ libgnunet_plugin_test.la @@ -850,7 +932,8 @@ libgnunet_plugin_test_la_LDFLAGS = \ $(GN_PLUGIN_LDFLAGS) @HAVE_BENCHMARKS_TRUE@BENCHMARKS = \ -@HAVE_BENCHMARKS_TRUE@ perf_crypto_hash +@HAVE_BENCHMARKS_TRUE@ perf_crypto_hash \ +@HAVE_BENCHMARKS_TRUE@ perf_malloc @ENABLE_TEST_RUN_TRUE@TESTS = $(check_PROGRAMS) test_bio_SOURCES = \ @@ -865,6 +948,9 @@ test_os_start_process_SOURCES = \ test_os_start_process_LDADD = \ $(top_builddir)/src/util/libgnunetutil.la +test_os_start_process_DEPENDENCIES = \ + $(WINCAT) + test_client_SOURCES = \ test_client.c @@ -950,6 +1036,12 @@ test_crypto_crc_SOURCES = \ test_crypto_crc_LDADD = \ $(top_builddir)/src/util/libgnunetutil.la +test_crypto_ecc_SOURCES = \ + test_crypto_ecc.c + +test_crypto_ecc_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la + test_crypto_hash_SOURCES = \ test_crypto_hash.c @@ -1142,6 +1234,12 @@ perf_crypto_hash_SOURCES = \ perf_crypto_hash_LDADD = \ $(top_builddir)/src/util/libgnunetutil.la +perf_malloc_SOURCES = \ + perf_malloc.c + +perf_malloc_LDADD = \ + $(top_builddir)/src/util/libgnunetutil.la + EXTRA_DIST = \ test_configuration_data.conf \ test_program_data.conf \ @@ -1153,7 +1251,7 @@ EXTRA_DIST = \ all: all-am .SUFFIXES: -.SUFFIXES: .c .cc .lo .o .obj +.SUFFIXES: .c .lo .o .obj $(srcdir)/Makefile.in: $(srcdir)/Makefile.am $(am__configure_deps) @for dep in $?; do \ case '$(am__configure_deps)' in \ @@ -1188,7 +1286,6 @@ resolver.conf: $(top_builddir)/config.status $(srcdir)/resolver.conf.in cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ install-libLTLIBRARIES: $(lib_LTLIBRARIES) @$(NORMAL_INSTALL) - test -z "$(libdir)" || $(MKDIR_P) "$(DESTDIR)$(libdir)" @list='$(lib_LTLIBRARIES)'; test -n "$(libdir)" || list=; \ list2=; for p in $$list; do \ if test -f $$p; then \ @@ -1196,6 +1293,8 @@ install-libLTLIBRARIES: $(lib_LTLIBRARIES) else :; fi; \ done; \ test -z "$$list2" || { \ + echo " $(MKDIR_P) '$(DESTDIR)$(libdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libdir)" || exit 1; \ echo " $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 '$(DESTDIR)$(libdir)'"; \ $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 "$(DESTDIR)$(libdir)"; \ } @@ -1228,7 +1327,6 @@ clean-noinstLTLIBRARIES: done install-pluginLTLIBRARIES: $(plugin_LTLIBRARIES) @$(NORMAL_INSTALL) - test -z "$(plugindir)" || $(MKDIR_P) "$(DESTDIR)$(plugindir)" @list='$(plugin_LTLIBRARIES)'; test -n "$(plugindir)" || list=; \ list2=; for p in $$list; do \ if test -f $$p; then \ @@ -1236,6 +1334,8 @@ install-pluginLTLIBRARIES: $(plugin_LTLIBRARIES) else :; fi; \ done; \ test -z "$$list2" || { \ + echo " $(MKDIR_P) '$(DESTDIR)$(plugindir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(plugindir)" || exit 1; \ echo " $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 '$(DESTDIR)$(plugindir)'"; \ $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 "$(DESTDIR)$(plugindir)"; \ } @@ -1257,16 +1357,19 @@ clean-pluginLTLIBRARIES: echo "rm -f \"$${dir}/so_locations\""; \ rm -f "$${dir}/so_locations"; \ done -libgnunet_plugin_test.la: $(libgnunet_plugin_test_la_OBJECTS) $(libgnunet_plugin_test_la_DEPENDENCIES) +libgnunet_plugin_test.la: $(libgnunet_plugin_test_la_OBJECTS) $(libgnunet_plugin_test_la_DEPENDENCIES) $(EXTRA_libgnunet_plugin_test_la_DEPENDENCIES) $(AM_V_CCLD)$(libgnunet_plugin_test_la_LINK) -rpath $(plugindir) $(libgnunet_plugin_test_la_OBJECTS) $(libgnunet_plugin_test_la_LIBADD) $(LIBS) -libgnunetutil.la: $(libgnunetutil_la_OBJECTS) $(libgnunetutil_la_DEPENDENCIES) +libgnunetutil.la: $(libgnunetutil_la_OBJECTS) $(libgnunetutil_la_DEPENDENCIES) $(EXTRA_libgnunetutil_la_DEPENDENCIES) $(AM_V_CCLD)$(libgnunetutil_la_LINK) -rpath $(libdir) $(libgnunetutil_la_OBJECTS) $(libgnunetutil_la_LIBADD) $(LIBS) -libgnunetutilwin.la: $(libgnunetutilwin_la_OBJECTS) $(libgnunetutilwin_la_DEPENDENCIES) - $(AM_V_CXXLD)$(libgnunetutilwin_la_LINK) $(am_libgnunetutilwin_la_rpath) $(libgnunetutilwin_la_OBJECTS) $(libgnunetutilwin_la_LIBADD) $(LIBS) +libgnunetutilwin.la: $(libgnunetutilwin_la_OBJECTS) $(libgnunetutilwin_la_DEPENDENCIES) $(EXTRA_libgnunetutilwin_la_DEPENDENCIES) + $(AM_V_CCLD)$(libgnunetutilwin_la_LINK) $(am_libgnunetutilwin_la_rpath) $(libgnunetutilwin_la_OBJECTS) $(libgnunetutilwin_la_LIBADD) $(LIBS) install-binPROGRAMS: $(bin_PROGRAMS) @$(NORMAL_INSTALL) - test -z "$(bindir)" || $(MKDIR_P) "$(DESTDIR)$(bindir)" @list='$(bin_PROGRAMS)'; test -n "$(bindir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(bindir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(bindir)" || exit 1; \ + fi; \ for p in $$list; do echo "$$p $$p"; done | \ sed 's/$(EXEEXT)$$//' | \ while read p p1; do if test -f $$p || test -f $$p1; \ @@ -1315,6 +1418,52 @@ clean-checkPROGRAMS: list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ echo " rm -f" $$list; \ rm -f $$list +install-libexecPROGRAMS: $(libexec_PROGRAMS) + @$(NORMAL_INSTALL) + @list='$(libexec_PROGRAMS)'; test -n "$(libexecdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(libexecdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libexecdir)" || exit 1; \ + fi; \ + for p in $$list; do echo "$$p $$p"; done | \ + sed 's/$(EXEEXT)$$//' | \ + while read p p1; do if test -f $$p || test -f $$p1; \ + then echo "$$p"; echo "$$p"; else :; fi; \ + done | \ + sed -e 'p;s,.*/,,;n;h' -e 's|.*|.|' \ + -e 'p;x;s,.*/,,;s/$(EXEEXT)$$//;$(transform);s/$$/$(EXEEXT)/' | \ + sed 'N;N;N;s,\n, ,g' | \ + $(AWK) 'BEGIN { files["."] = ""; dirs["."] = 1 } \ + { d=$$3; if (dirs[d] != 1) { print "d", d; dirs[d] = 1 } \ + if ($$2 == $$4) files[d] = files[d] " " $$1; \ + else { print "f", $$3 "/" $$4, $$1; } } \ + END { for (d in files) print "f", d, files[d] }' | \ + while read type dir files; do \ + if test "$$dir" = .; then dir=; else dir=/$$dir; fi; \ + test -z "$$files" || { \ + echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files '$(DESTDIR)$(libexecdir)$$dir'"; \ + $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files "$(DESTDIR)$(libexecdir)$$dir" || exit $$?; \ + } \ + ; done + +uninstall-libexecPROGRAMS: + @$(NORMAL_UNINSTALL) + @list='$(libexec_PROGRAMS)'; test -n "$(libexecdir)" || list=; \ + files=`for p in $$list; do echo "$$p"; done | \ + sed -e 'h;s,^.*/,,;s/$(EXEEXT)$$//;$(transform)' \ + -e 's/$$/$(EXEEXT)/' `; \ + test -n "$$list" || exit 0; \ + echo " ( cd '$(DESTDIR)$(libexecdir)' && rm -f" $$files ")"; \ + cd "$(DESTDIR)$(libexecdir)" && rm -f $$files + +clean-libexecPROGRAMS: + @list='$(libexec_PROGRAMS)'; test -n "$$list" || exit 0; \ + echo " rm -f" $$list; \ + rm -f $$list || exit $$?; \ + test -n "$(EXEEXT)" || exit 0; \ + list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ + echo " rm -f" $$list; \ + rm -f $$list clean-noinstPROGRAMS: @list='$(noinst_PROGRAMS)'; test -n "$$list" || exit 0; \ @@ -1324,165 +1473,183 @@ clean-noinstPROGRAMS: list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ echo " rm -f" $$list; \ rm -f $$list -gnunet-config-diff$(EXEEXT): $(gnunet_config_diff_OBJECTS) $(gnunet_config_diff_DEPENDENCIES) +gnunet-config$(EXEEXT): $(gnunet_config_OBJECTS) $(gnunet_config_DEPENDENCIES) $(EXTRA_gnunet_config_DEPENDENCIES) + @rm -f gnunet-config$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(gnunet_config_OBJECTS) $(gnunet_config_LDADD) $(LIBS) +gnunet-config-diff$(EXEEXT): $(gnunet_config_diff_OBJECTS) $(gnunet_config_diff_DEPENDENCIES) $(EXTRA_gnunet_config_diff_DEPENDENCIES) @rm -f gnunet-config-diff$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_config_diff_OBJECTS) $(gnunet_config_diff_LDADD) $(LIBS) -gnunet-resolver$(EXEEXT): $(gnunet_resolver_OBJECTS) $(gnunet_resolver_DEPENDENCIES) +gnunet-ecc$(EXEEXT): $(gnunet_ecc_OBJECTS) $(gnunet_ecc_DEPENDENCIES) $(EXTRA_gnunet_ecc_DEPENDENCIES) + @rm -f gnunet-ecc$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(gnunet_ecc_OBJECTS) $(gnunet_ecc_LDADD) $(LIBS) +gnunet-resolver$(EXEEXT): $(gnunet_resolver_OBJECTS) $(gnunet_resolver_DEPENDENCIES) $(EXTRA_gnunet_resolver_DEPENDENCIES) @rm -f gnunet-resolver$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_resolver_OBJECTS) $(gnunet_resolver_LDADD) $(LIBS) -gnunet-rsa$(EXEEXT): $(gnunet_rsa_OBJECTS) $(gnunet_rsa_DEPENDENCIES) +gnunet-rsa$(EXEEXT): $(gnunet_rsa_OBJECTS) $(gnunet_rsa_DEPENDENCIES) $(EXTRA_gnunet_rsa_DEPENDENCIES) @rm -f gnunet-rsa$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_rsa_OBJECTS) $(gnunet_rsa_LDADD) $(LIBS) -gnunet-service-resolver$(EXEEXT): $(gnunet_service_resolver_OBJECTS) $(gnunet_service_resolver_DEPENDENCIES) +gnunet-service-resolver$(EXEEXT): $(gnunet_service_resolver_OBJECTS) $(gnunet_service_resolver_DEPENDENCIES) $(EXTRA_gnunet_service_resolver_DEPENDENCIES) @rm -f gnunet-service-resolver$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_service_resolver_OBJECTS) $(gnunet_service_resolver_LDADD) $(LIBS) -perf_crypto_hash$(EXEEXT): $(perf_crypto_hash_OBJECTS) $(perf_crypto_hash_DEPENDENCIES) +gnunet-uri$(EXEEXT): $(gnunet_uri_OBJECTS) $(gnunet_uri_DEPENDENCIES) $(EXTRA_gnunet_uri_DEPENDENCIES) + @rm -f gnunet-uri$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(gnunet_uri_OBJECTS) $(gnunet_uri_LDADD) $(LIBS) +perf_crypto_hash$(EXEEXT): $(perf_crypto_hash_OBJECTS) $(perf_crypto_hash_DEPENDENCIES) $(EXTRA_perf_crypto_hash_DEPENDENCIES) @rm -f perf_crypto_hash$(EXEEXT) $(AM_V_CCLD)$(LINK) $(perf_crypto_hash_OBJECTS) $(perf_crypto_hash_LDADD) $(LIBS) -test_bio$(EXEEXT): $(test_bio_OBJECTS) $(test_bio_DEPENDENCIES) +perf_malloc$(EXEEXT): $(perf_malloc_OBJECTS) $(perf_malloc_DEPENDENCIES) $(EXTRA_perf_malloc_DEPENDENCIES) + @rm -f perf_malloc$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(perf_malloc_OBJECTS) $(perf_malloc_LDADD) $(LIBS) +test_bio$(EXEEXT): $(test_bio_OBJECTS) $(test_bio_DEPENDENCIES) $(EXTRA_test_bio_DEPENDENCIES) @rm -f test_bio$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_bio_OBJECTS) $(test_bio_LDADD) $(LIBS) -test_client$(EXEEXT): $(test_client_OBJECTS) $(test_client_DEPENDENCIES) +test_client$(EXEEXT): $(test_client_OBJECTS) $(test_client_DEPENDENCIES) $(EXTRA_test_client_DEPENDENCIES) @rm -f test_client$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_client_OBJECTS) $(test_client_LDADD) $(LIBS) -test_common_allocation$(EXEEXT): $(test_common_allocation_OBJECTS) $(test_common_allocation_DEPENDENCIES) +test_common_allocation$(EXEEXT): $(test_common_allocation_OBJECTS) $(test_common_allocation_DEPENDENCIES) $(EXTRA_test_common_allocation_DEPENDENCIES) @rm -f test_common_allocation$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_common_allocation_OBJECTS) $(test_common_allocation_LDADD) $(LIBS) -test_common_endian$(EXEEXT): $(test_common_endian_OBJECTS) $(test_common_endian_DEPENDENCIES) +test_common_endian$(EXEEXT): $(test_common_endian_OBJECTS) $(test_common_endian_DEPENDENCIES) $(EXTRA_test_common_endian_DEPENDENCIES) @rm -f test_common_endian$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_common_endian_OBJECTS) $(test_common_endian_LDADD) $(LIBS) -test_common_logging$(EXEEXT): $(test_common_logging_OBJECTS) $(test_common_logging_DEPENDENCIES) +test_common_logging$(EXEEXT): $(test_common_logging_OBJECTS) $(test_common_logging_DEPENDENCIES) $(EXTRA_test_common_logging_DEPENDENCIES) @rm -f test_common_logging$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_common_logging_OBJECTS) $(test_common_logging_LDADD) $(LIBS) -test_common_logging_dummy$(EXEEXT): $(test_common_logging_dummy_OBJECTS) $(test_common_logging_dummy_DEPENDENCIES) +test_common_logging_dummy$(EXEEXT): $(test_common_logging_dummy_OBJECTS) $(test_common_logging_dummy_DEPENDENCIES) $(EXTRA_test_common_logging_dummy_DEPENDENCIES) @rm -f test_common_logging_dummy$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_common_logging_dummy_OBJECTS) $(test_common_logging_dummy_LDADD) $(LIBS) -test_common_logging_runtime_loglevels$(EXEEXT): $(test_common_logging_runtime_loglevels_OBJECTS) $(test_common_logging_runtime_loglevels_DEPENDENCIES) +test_common_logging_runtime_loglevels$(EXEEXT): $(test_common_logging_runtime_loglevels_OBJECTS) $(test_common_logging_runtime_loglevels_DEPENDENCIES) $(EXTRA_test_common_logging_runtime_loglevels_DEPENDENCIES) @rm -f test_common_logging_runtime_loglevels$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_common_logging_runtime_loglevels_OBJECTS) $(test_common_logging_runtime_loglevels_LDADD) $(LIBS) -test_configuration$(EXEEXT): $(test_configuration_OBJECTS) $(test_configuration_DEPENDENCIES) +test_configuration$(EXEEXT): $(test_configuration_OBJECTS) $(test_configuration_DEPENDENCIES) $(EXTRA_test_configuration_DEPENDENCIES) @rm -f test_configuration$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_configuration_OBJECTS) $(test_configuration_LDADD) $(LIBS) -test_connection$(EXEEXT): $(test_connection_OBJECTS) $(test_connection_DEPENDENCIES) +test_connection$(EXEEXT): $(test_connection_OBJECTS) $(test_connection_DEPENDENCIES) $(EXTRA_test_connection_DEPENDENCIES) @rm -f test_connection$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_connection_OBJECTS) $(test_connection_LDADD) $(LIBS) -test_connection_addressing$(EXEEXT): $(test_connection_addressing_OBJECTS) $(test_connection_addressing_DEPENDENCIES) +test_connection_addressing$(EXEEXT): $(test_connection_addressing_OBJECTS) $(test_connection_addressing_DEPENDENCIES) $(EXTRA_test_connection_addressing_DEPENDENCIES) @rm -f test_connection_addressing$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_connection_addressing_OBJECTS) $(test_connection_addressing_LDADD) $(LIBS) -test_connection_receive_cancel$(EXEEXT): $(test_connection_receive_cancel_OBJECTS) $(test_connection_receive_cancel_DEPENDENCIES) +test_connection_receive_cancel$(EXEEXT): $(test_connection_receive_cancel_OBJECTS) $(test_connection_receive_cancel_DEPENDENCIES) $(EXTRA_test_connection_receive_cancel_DEPENDENCIES) @rm -f test_connection_receive_cancel$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_connection_receive_cancel_OBJECTS) $(test_connection_receive_cancel_LDADD) $(LIBS) -test_connection_timeout$(EXEEXT): $(test_connection_timeout_OBJECTS) $(test_connection_timeout_DEPENDENCIES) +test_connection_timeout$(EXEEXT): $(test_connection_timeout_OBJECTS) $(test_connection_timeout_DEPENDENCIES) $(EXTRA_test_connection_timeout_DEPENDENCIES) @rm -f test_connection_timeout$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_connection_timeout_OBJECTS) $(test_connection_timeout_LDADD) $(LIBS) -test_connection_timeout_no_connect$(EXEEXT): $(test_connection_timeout_no_connect_OBJECTS) $(test_connection_timeout_no_connect_DEPENDENCIES) +test_connection_timeout_no_connect$(EXEEXT): $(test_connection_timeout_no_connect_OBJECTS) $(test_connection_timeout_no_connect_DEPENDENCIES) $(EXTRA_test_connection_timeout_no_connect_DEPENDENCIES) @rm -f test_connection_timeout_no_connect$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_connection_timeout_no_connect_OBJECTS) $(test_connection_timeout_no_connect_LDADD) $(LIBS) -test_connection_transmit_cancel$(EXEEXT): $(test_connection_transmit_cancel_OBJECTS) $(test_connection_transmit_cancel_DEPENDENCIES) +test_connection_transmit_cancel$(EXEEXT): $(test_connection_transmit_cancel_OBJECTS) $(test_connection_transmit_cancel_DEPENDENCIES) $(EXTRA_test_connection_transmit_cancel_DEPENDENCIES) @rm -f test_connection_transmit_cancel$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_connection_transmit_cancel_OBJECTS) $(test_connection_transmit_cancel_LDADD) $(LIBS) -test_container_bloomfilter$(EXEEXT): $(test_container_bloomfilter_OBJECTS) $(test_container_bloomfilter_DEPENDENCIES) +test_container_bloomfilter$(EXEEXT): $(test_container_bloomfilter_OBJECTS) $(test_container_bloomfilter_DEPENDENCIES) $(EXTRA_test_container_bloomfilter_DEPENDENCIES) @rm -f test_container_bloomfilter$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_container_bloomfilter_OBJECTS) $(test_container_bloomfilter_LDADD) $(LIBS) -test_container_heap$(EXEEXT): $(test_container_heap_OBJECTS) $(test_container_heap_DEPENDENCIES) +test_container_heap$(EXEEXT): $(test_container_heap_OBJECTS) $(test_container_heap_DEPENDENCIES) $(EXTRA_test_container_heap_DEPENDENCIES) @rm -f test_container_heap$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_container_heap_OBJECTS) $(test_container_heap_LDADD) $(LIBS) -test_container_meta_data$(EXEEXT): $(test_container_meta_data_OBJECTS) $(test_container_meta_data_DEPENDENCIES) +test_container_meta_data$(EXEEXT): $(test_container_meta_data_OBJECTS) $(test_container_meta_data_DEPENDENCIES) $(EXTRA_test_container_meta_data_DEPENDENCIES) @rm -f test_container_meta_data$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_container_meta_data_OBJECTS) $(test_container_meta_data_LDADD) $(LIBS) -test_container_multihashmap$(EXEEXT): $(test_container_multihashmap_OBJECTS) $(test_container_multihashmap_DEPENDENCIES) +test_container_multihashmap$(EXEEXT): $(test_container_multihashmap_OBJECTS) $(test_container_multihashmap_DEPENDENCIES) $(EXTRA_test_container_multihashmap_DEPENDENCIES) @rm -f test_container_multihashmap$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_container_multihashmap_OBJECTS) $(test_container_multihashmap_LDADD) $(LIBS) -test_container_slist$(EXEEXT): $(test_container_slist_OBJECTS) $(test_container_slist_DEPENDENCIES) +test_container_slist$(EXEEXT): $(test_container_slist_OBJECTS) $(test_container_slist_DEPENDENCIES) $(EXTRA_test_container_slist_DEPENDENCIES) @rm -f test_container_slist$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_container_slist_OBJECTS) $(test_container_slist_LDADD) $(LIBS) -test_crypto_aes$(EXEEXT): $(test_crypto_aes_OBJECTS) $(test_crypto_aes_DEPENDENCIES) +test_crypto_aes$(EXEEXT): $(test_crypto_aes_OBJECTS) $(test_crypto_aes_DEPENDENCIES) $(EXTRA_test_crypto_aes_DEPENDENCIES) @rm -f test_crypto_aes$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_crypto_aes_OBJECTS) $(test_crypto_aes_LDADD) $(LIBS) -test_crypto_aes_weak$(EXEEXT): $(test_crypto_aes_weak_OBJECTS) $(test_crypto_aes_weak_DEPENDENCIES) +test_crypto_aes_weak$(EXEEXT): $(test_crypto_aes_weak_OBJECTS) $(test_crypto_aes_weak_DEPENDENCIES) $(EXTRA_test_crypto_aes_weak_DEPENDENCIES) @rm -f test_crypto_aes_weak$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_crypto_aes_weak_OBJECTS) $(test_crypto_aes_weak_LDADD) $(LIBS) -test_crypto_crc$(EXEEXT): $(test_crypto_crc_OBJECTS) $(test_crypto_crc_DEPENDENCIES) +test_crypto_crc$(EXEEXT): $(test_crypto_crc_OBJECTS) $(test_crypto_crc_DEPENDENCIES) $(EXTRA_test_crypto_crc_DEPENDENCIES) @rm -f test_crypto_crc$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_crypto_crc_OBJECTS) $(test_crypto_crc_LDADD) $(LIBS) -test_crypto_hash$(EXEEXT): $(test_crypto_hash_OBJECTS) $(test_crypto_hash_DEPENDENCIES) +test_crypto_ecc$(EXEEXT): $(test_crypto_ecc_OBJECTS) $(test_crypto_ecc_DEPENDENCIES) $(EXTRA_test_crypto_ecc_DEPENDENCIES) + @rm -f test_crypto_ecc$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(test_crypto_ecc_OBJECTS) $(test_crypto_ecc_LDADD) $(LIBS) +test_crypto_hash$(EXEEXT): $(test_crypto_hash_OBJECTS) $(test_crypto_hash_DEPENDENCIES) $(EXTRA_test_crypto_hash_DEPENDENCIES) @rm -f test_crypto_hash$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_crypto_hash_OBJECTS) $(test_crypto_hash_LDADD) $(LIBS) -test_crypto_hkdf$(EXEEXT): $(test_crypto_hkdf_OBJECTS) $(test_crypto_hkdf_DEPENDENCIES) +test_crypto_hkdf$(EXEEXT): $(test_crypto_hkdf_OBJECTS) $(test_crypto_hkdf_DEPENDENCIES) $(EXTRA_test_crypto_hkdf_DEPENDENCIES) @rm -f test_crypto_hkdf$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_crypto_hkdf_OBJECTS) $(test_crypto_hkdf_LDADD) $(LIBS) -test_crypto_ksk$(EXEEXT): $(test_crypto_ksk_OBJECTS) $(test_crypto_ksk_DEPENDENCIES) +test_crypto_ksk$(EXEEXT): $(test_crypto_ksk_OBJECTS) $(test_crypto_ksk_DEPENDENCIES) $(EXTRA_test_crypto_ksk_DEPENDENCIES) @rm -f test_crypto_ksk$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_crypto_ksk_OBJECTS) $(test_crypto_ksk_LDADD) $(LIBS) -test_crypto_random$(EXEEXT): $(test_crypto_random_OBJECTS) $(test_crypto_random_DEPENDENCIES) +test_crypto_random$(EXEEXT): $(test_crypto_random_OBJECTS) $(test_crypto_random_DEPENDENCIES) $(EXTRA_test_crypto_random_DEPENDENCIES) @rm -f test_crypto_random$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_crypto_random_OBJECTS) $(test_crypto_random_LDADD) $(LIBS) -test_crypto_rsa$(EXEEXT): $(test_crypto_rsa_OBJECTS) $(test_crypto_rsa_DEPENDENCIES) +test_crypto_rsa$(EXEEXT): $(test_crypto_rsa_OBJECTS) $(test_crypto_rsa_DEPENDENCIES) $(EXTRA_test_crypto_rsa_DEPENDENCIES) @rm -f test_crypto_rsa$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_crypto_rsa_OBJECTS) $(test_crypto_rsa_LDADD) $(LIBS) -test_disk$(EXEEXT): $(test_disk_OBJECTS) $(test_disk_DEPENDENCIES) +test_disk$(EXEEXT): $(test_disk_OBJECTS) $(test_disk_DEPENDENCIES) $(EXTRA_test_disk_DEPENDENCIES) @rm -f test_disk$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_disk_OBJECTS) $(test_disk_LDADD) $(LIBS) -test_getopt$(EXEEXT): $(test_getopt_OBJECTS) $(test_getopt_DEPENDENCIES) +test_getopt$(EXEEXT): $(test_getopt_OBJECTS) $(test_getopt_DEPENDENCIES) $(EXTRA_test_getopt_DEPENDENCIES) @rm -f test_getopt$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_getopt_OBJECTS) $(test_getopt_LDADD) $(LIBS) -test_os_network$(EXEEXT): $(test_os_network_OBJECTS) $(test_os_network_DEPENDENCIES) +test_os_network$(EXEEXT): $(test_os_network_OBJECTS) $(test_os_network_DEPENDENCIES) $(EXTRA_test_os_network_DEPENDENCIES) @rm -f test_os_network$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_os_network_OBJECTS) $(test_os_network_LDADD) $(LIBS) -test_os_priority$(EXEEXT): $(test_os_priority_OBJECTS) $(test_os_priority_DEPENDENCIES) +test_os_priority$(EXEEXT): $(test_os_priority_OBJECTS) $(test_os_priority_DEPENDENCIES) $(EXTRA_test_os_priority_DEPENDENCIES) @rm -f test_os_priority$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_os_priority_OBJECTS) $(test_os_priority_LDADD) $(LIBS) -test_os_start_process$(EXEEXT): $(test_os_start_process_OBJECTS) $(test_os_start_process_DEPENDENCIES) +test_os_start_process$(EXEEXT): $(test_os_start_process_OBJECTS) $(test_os_start_process_DEPENDENCIES) $(EXTRA_test_os_start_process_DEPENDENCIES) @rm -f test_os_start_process$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_os_start_process_OBJECTS) $(test_os_start_process_LDADD) $(LIBS) -test_peer$(EXEEXT): $(test_peer_OBJECTS) $(test_peer_DEPENDENCIES) +test_peer$(EXEEXT): $(test_peer_OBJECTS) $(test_peer_DEPENDENCIES) $(EXTRA_test_peer_DEPENDENCIES) @rm -f test_peer$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_peer_OBJECTS) $(test_peer_LDADD) $(LIBS) -test_plugin$(EXEEXT): $(test_plugin_OBJECTS) $(test_plugin_DEPENDENCIES) +test_plugin$(EXEEXT): $(test_plugin_OBJECTS) $(test_plugin_DEPENDENCIES) $(EXTRA_test_plugin_DEPENDENCIES) @rm -f test_plugin$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_plugin_OBJECTS) $(test_plugin_LDADD) $(LIBS) -test_program$(EXEEXT): $(test_program_OBJECTS) $(test_program_DEPENDENCIES) +test_program$(EXEEXT): $(test_program_OBJECTS) $(test_program_DEPENDENCIES) $(EXTRA_test_program_DEPENDENCIES) @rm -f test_program$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_program_OBJECTS) $(test_program_LDADD) $(LIBS) -test_pseudonym$(EXEEXT): $(test_pseudonym_OBJECTS) $(test_pseudonym_DEPENDENCIES) +test_pseudonym$(EXEEXT): $(test_pseudonym_OBJECTS) $(test_pseudonym_DEPENDENCIES) $(EXTRA_test_pseudonym_DEPENDENCIES) @rm -f test_pseudonym$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_pseudonym_OBJECTS) $(test_pseudonym_LDADD) $(LIBS) -test_resolver_api$(EXEEXT): $(test_resolver_api_OBJECTS) $(test_resolver_api_DEPENDENCIES) +test_resolver_api$(EXEEXT): $(test_resolver_api_OBJECTS) $(test_resolver_api_DEPENDENCIES) $(EXTRA_test_resolver_api_DEPENDENCIES) @rm -f test_resolver_api$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_resolver_api_OBJECTS) $(test_resolver_api_LDADD) $(LIBS) -test_scheduler$(EXEEXT): $(test_scheduler_OBJECTS) $(test_scheduler_DEPENDENCIES) +test_scheduler$(EXEEXT): $(test_scheduler_OBJECTS) $(test_scheduler_DEPENDENCIES) $(EXTRA_test_scheduler_DEPENDENCIES) @rm -f test_scheduler$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_scheduler_OBJECTS) $(test_scheduler_LDADD) $(LIBS) -test_scheduler_delay$(EXEEXT): $(test_scheduler_delay_OBJECTS) $(test_scheduler_delay_DEPENDENCIES) +test_scheduler_delay$(EXEEXT): $(test_scheduler_delay_OBJECTS) $(test_scheduler_delay_DEPENDENCIES) $(EXTRA_test_scheduler_delay_DEPENDENCIES) @rm -f test_scheduler_delay$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_scheduler_delay_OBJECTS) $(test_scheduler_delay_LDADD) $(LIBS) -test_server$(EXEEXT): $(test_server_OBJECTS) $(test_server_DEPENDENCIES) +test_server$(EXEEXT): $(test_server_OBJECTS) $(test_server_DEPENDENCIES) $(EXTRA_test_server_DEPENDENCIES) @rm -f test_server$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_server_OBJECTS) $(test_server_LDADD) $(LIBS) -test_server_disconnect$(EXEEXT): $(test_server_disconnect_OBJECTS) $(test_server_disconnect_DEPENDENCIES) +test_server_disconnect$(EXEEXT): $(test_server_disconnect_OBJECTS) $(test_server_disconnect_DEPENDENCIES) $(EXTRA_test_server_disconnect_DEPENDENCIES) @rm -f test_server_disconnect$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_server_disconnect_OBJECTS) $(test_server_disconnect_LDADD) $(LIBS) -test_server_mst_interrupt$(EXEEXT): $(test_server_mst_interrupt_OBJECTS) $(test_server_mst_interrupt_DEPENDENCIES) +test_server_mst_interrupt$(EXEEXT): $(test_server_mst_interrupt_OBJECTS) $(test_server_mst_interrupt_DEPENDENCIES) $(EXTRA_test_server_mst_interrupt_DEPENDENCIES) @rm -f test_server_mst_interrupt$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_server_mst_interrupt_OBJECTS) $(test_server_mst_interrupt_LDADD) $(LIBS) -test_server_with_client$(EXEEXT): $(test_server_with_client_OBJECTS) $(test_server_with_client_DEPENDENCIES) +test_server_with_client$(EXEEXT): $(test_server_with_client_OBJECTS) $(test_server_with_client_DEPENDENCIES) $(EXTRA_test_server_with_client_DEPENDENCIES) @rm -f test_server_with_client$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_server_with_client_OBJECTS) $(test_server_with_client_LDADD) $(LIBS) -test_server_with_client_unix$(EXEEXT): $(test_server_with_client_unix_OBJECTS) $(test_server_with_client_unix_DEPENDENCIES) +test_server_with_client_unix$(EXEEXT): $(test_server_with_client_unix_OBJECTS) $(test_server_with_client_unix_DEPENDENCIES) $(EXTRA_test_server_with_client_unix_DEPENDENCIES) @rm -f test_server_with_client_unix$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_server_with_client_unix_OBJECTS) $(test_server_with_client_unix_LDADD) $(LIBS) -test_service$(EXEEXT): $(test_service_OBJECTS) $(test_service_DEPENDENCIES) +test_service$(EXEEXT): $(test_service_OBJECTS) $(test_service_DEPENDENCIES) $(EXTRA_test_service_DEPENDENCIES) @rm -f test_service$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_service_OBJECTS) $(test_service_LDADD) $(LIBS) -test_speedup$(EXEEXT): $(test_speedup_OBJECTS) $(test_speedup_DEPENDENCIES) +test_speedup$(EXEEXT): $(test_speedup_OBJECTS) $(test_speedup_DEPENDENCIES) $(EXTRA_test_speedup_DEPENDENCIES) @rm -f test_speedup$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_speedup_OBJECTS) $(test_speedup_LDADD) $(LIBS) -test_strings$(EXEEXT): $(test_strings_OBJECTS) $(test_strings_DEPENDENCIES) +test_strings$(EXEEXT): $(test_strings_OBJECTS) $(test_strings_DEPENDENCIES) $(EXTRA_test_strings_DEPENDENCIES) @rm -f test_strings$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_strings_OBJECTS) $(test_strings_LDADD) $(LIBS) -test_time$(EXEEXT): $(test_time_OBJECTS) $(test_time_DEPENDENCIES) +test_time$(EXEEXT): $(test_time_OBJECTS) $(test_time_DEPENDENCIES) $(EXTRA_test_time_DEPENDENCIES) @rm -f test_time$(EXEEXT) $(AM_V_CCLD)$(LINK) $(test_time_OBJECTS) $(test_time_LDADD) $(LIBS) +w32cat$(EXEEXT): $(w32cat_OBJECTS) $(w32cat_DEPENDENCIES) $(EXTRA_w32cat_DEPENDENCIES) + @rm -f w32cat$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(w32cat_OBJECTS) $(w32cat_LDADD) $(LIBS) mostlyclean-compile: -rm -f *.$(OBJEXT) @@ -1505,6 +1672,7 @@ distclean-compile: @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/container_slist.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/crypto_aes.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/crypto_crc.Plo@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/crypto_ecc.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/crypto_hash.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/crypto_hkdf.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/crypto_kdf.Plo@am__quote@ @@ -1515,9 +1683,12 @@ distclean-compile: @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/getopt.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/getopt_helpers.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-config-diff.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-config.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-ecc.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-resolver.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-rsa.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-service-resolver.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-uri.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/helper.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/load.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/network.Plo@am__quote@ @@ -1526,6 +1697,7 @@ distclean-compile: @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/os_priority.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/peer.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/perf_crypto_hash.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/perf_malloc.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/plugin.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/program.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/pseudonym.Plo@am__quote@ @@ -1561,6 +1733,7 @@ distclean-compile: @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_crypto_aes.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_crypto_aes_weak.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_crypto_crc.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_crypto_ecc.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_crypto_hash.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_crypto_hkdf.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_crypto_ksk.Po@am__quote@ @@ -1589,56 +1762,30 @@ distclean-compile: @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_strings.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_time.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/time.Plo@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/w32cat.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/win.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/winproc.Plo@am__quote@ .c.o: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c $< .c.obj: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'` @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c `$(CYGPATH_W) '$<'` +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c `$(CYGPATH_W) '$<'` .c.lo: @am__fastdepCC_TRUE@ $(AM_V_CC)$(LTCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LTCOMPILE) -c -o $@ $< - -.cc.o: -@am__fastdepCXX_TRUE@ $(AM_V_CXX)$(CXXCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< -@am__fastdepCXX_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCXX_FALSE@ $(AM_V_CXX) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCXX_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ -@AMDEP_TRUE@@am__fastdepCXX_FALSE@ DEPDIR=$(DEPDIR) $(CXXDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCXX_FALSE@ $(CXXCOMPILE) -c -o $@ $< - -.cc.obj: -@am__fastdepCXX_TRUE@ $(AM_V_CXX)$(CXXCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'` -@am__fastdepCXX_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCXX_FALSE@ $(AM_V_CXX) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCXX_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ -@AMDEP_TRUE@@am__fastdepCXX_FALSE@ DEPDIR=$(DEPDIR) $(CXXDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCXX_FALSE@ $(CXXCOMPILE) -c -o $@ `$(CYGPATH_W) '$<'` - -.cc.lo: -@am__fastdepCXX_TRUE@ $(AM_V_CXX)$(LTCXXCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< -@am__fastdepCXX_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo -@am__fastdepCXX_FALSE@ $(AM_V_CXX) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCXX_FALSE@ source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ -@AMDEP_TRUE@@am__fastdepCXX_FALSE@ DEPDIR=$(DEPDIR) $(CXXDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCXX_FALSE@ $(LTCXXCOMPILE) -c -o $@ $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LTCOMPILE) -c -o $@ $< mostlyclean-libtool: -rm -f *.lo @@ -1647,8 +1794,11 @@ clean-libtool: -rm -rf .libs _libs install-dist_pkgcfgDATA: $(dist_pkgcfg_DATA) @$(NORMAL_INSTALL) - test -z "$(pkgcfgdir)" || $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" @list='$(dist_pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(pkgcfgdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" || exit 1; \ + fi; \ for p in $$list; do \ if test -f "$$p"; then d=; else d="$(srcdir)/"; fi; \ echo "$$d$$p"; \ @@ -1662,13 +1812,14 @@ uninstall-dist_pkgcfgDATA: @$(NORMAL_UNINSTALL) @list='$(dist_pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ files=`for p in $$list; do echo $$p; done | sed -e 's|^.*/||'`; \ - test -n "$$files" || exit 0; \ - echo " ( cd '$(DESTDIR)$(pkgcfgdir)' && rm -f" $$files ")"; \ - cd "$(DESTDIR)$(pkgcfgdir)" && rm -f $$files + dir='$(DESTDIR)$(pkgcfgdir)'; $(am__uninstall_files_from_dir) install-pkgcfgDATA: $(pkgcfg_DATA) @$(NORMAL_INSTALL) - test -z "$(pkgcfgdir)" || $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" @list='$(pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(pkgcfgdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" || exit 1; \ + fi; \ for p in $$list; do \ if test -f "$$p"; then d=; else d="$(srcdir)/"; fi; \ echo "$$d$$p"; \ @@ -1682,9 +1833,7 @@ uninstall-pkgcfgDATA: @$(NORMAL_UNINSTALL) @list='$(pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ files=`for p in $$list; do echo $$p; done | sed -e 's|^.*/||'`; \ - test -n "$$files" || exit 0; \ - echo " ( cd '$(DESTDIR)$(pkgcfgdir)' && rm -f" $$files ")"; \ - cd "$(DESTDIR)$(pkgcfgdir)" && rm -f $$files + dir='$(DESTDIR)$(pkgcfgdir)'; $(am__uninstall_files_from_dir) ID: $(HEADERS) $(SOURCES) $(LISP) $(TAGS_FILES) list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ @@ -1819,14 +1968,15 @@ check-TESTS: $(TESTS) fi; \ dashes=`echo "$$dashes" | sed s/./=/g`; \ if test "$$failed" -eq 0; then \ - echo "$$grn$$dashes"; \ + col="$$grn"; \ else \ - echo "$$red$$dashes"; \ + col="$$red"; \ fi; \ - echo "$$banner"; \ - test -z "$$skipped" || echo "$$skipped"; \ - test -z "$$report" || echo "$$report"; \ - echo "$$dashes$$std"; \ + echo "$${col}$$dashes$${std}"; \ + echo "$${col}$$banner$${std}"; \ + test -z "$$skipped" || echo "$${col}$$skipped$${std}"; \ + test -z "$$report" || echo "$${col}$$report$${std}"; \ + echo "$${col}$$dashes$${std}"; \ test "$$failed" -eq 0; \ else :; fi @@ -1868,7 +2018,7 @@ all-am: Makefile $(LTLIBRARIES) $(PROGRAMS) $(DATA) install-binPROGRAMS: install-libLTLIBRARIES installdirs: - for dir in "$(DESTDIR)$(libdir)" "$(DESTDIR)$(plugindir)" "$(DESTDIR)$(bindir)" "$(DESTDIR)$(pkgcfgdir)" "$(DESTDIR)$(pkgcfgdir)"; do \ + for dir in "$(DESTDIR)$(libdir)" "$(DESTDIR)$(plugindir)" "$(DESTDIR)$(bindir)" "$(DESTDIR)$(libexecdir)" "$(DESTDIR)$(pkgcfgdir)" "$(DESTDIR)$(pkgcfgdir)"; do \ test -z "$$dir" || $(MKDIR_P) "$$dir"; \ done install: install-am @@ -1881,10 +2031,15 @@ install-am: all-am installcheck: installcheck-am install-strip: - $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ - install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ - `test -z '$(STRIP)' || \ - echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi mostlyclean-generic: clean-generic: @@ -1899,8 +2054,9 @@ maintainer-clean-generic: clean: clean-am clean-am: clean-binPROGRAMS clean-checkPROGRAMS clean-generic \ - clean-libLTLIBRARIES clean-libtool clean-noinstLTLIBRARIES \ - clean-noinstPROGRAMS clean-pluginLTLIBRARIES mostlyclean-am + clean-libLTLIBRARIES clean-libexecPROGRAMS clean-libtool \ + clean-noinstLTLIBRARIES clean-noinstPROGRAMS \ + clean-pluginLTLIBRARIES mostlyclean-am distclean: distclean-am -rm -rf ./$(DEPDIR) @@ -1927,7 +2083,8 @@ install-dvi: install-dvi-am install-dvi-am: -install-exec-am: install-binPROGRAMS install-libLTLIBRARIES +install-exec-am: install-binPROGRAMS install-libLTLIBRARIES \ + install-libexecPROGRAMS install-html: install-html-am @@ -1968,30 +2125,31 @@ ps: ps-am ps-am: uninstall-am: uninstall-binPROGRAMS uninstall-dist_pkgcfgDATA \ - uninstall-libLTLIBRARIES uninstall-pkgcfgDATA \ - uninstall-pluginLTLIBRARIES + uninstall-libLTLIBRARIES uninstall-libexecPROGRAMS \ + uninstall-pkgcfgDATA uninstall-pluginLTLIBRARIES .MAKE: check-am install-am install-strip .PHONY: CTAGS GTAGS all all-am check check-TESTS check-am clean \ clean-binPROGRAMS clean-checkPROGRAMS clean-generic \ - clean-libLTLIBRARIES clean-libtool clean-noinstLTLIBRARIES \ - clean-noinstPROGRAMS clean-pluginLTLIBRARIES ctags distclean \ - distclean-compile distclean-generic distclean-libtool \ - distclean-tags distdir dvi dvi-am html html-am info info-am \ - install install-am install-binPROGRAMS install-data \ - install-data-am install-dist_pkgcfgDATA install-dvi \ - install-dvi-am install-exec install-exec-am install-html \ - install-html-am install-info install-info-am \ - install-libLTLIBRARIES install-man install-pdf install-pdf-am \ + clean-libLTLIBRARIES clean-libexecPROGRAMS clean-libtool \ + clean-noinstLTLIBRARIES clean-noinstPROGRAMS \ + clean-pluginLTLIBRARIES ctags distclean distclean-compile \ + distclean-generic distclean-libtool distclean-tags distdir dvi \ + dvi-am html html-am info info-am install install-am \ + install-binPROGRAMS install-data install-data-am \ + install-dist_pkgcfgDATA install-dvi install-dvi-am \ + install-exec install-exec-am install-html install-html-am \ + install-info install-info-am install-libLTLIBRARIES \ + install-libexecPROGRAMS install-man install-pdf install-pdf-am \ install-pkgcfgDATA install-pluginLTLIBRARIES install-ps \ install-ps-am install-strip installcheck installcheck-am \ installdirs maintainer-clean maintainer-clean-generic \ mostlyclean mostlyclean-compile mostlyclean-generic \ mostlyclean-libtool pdf pdf-am ps ps-am tags uninstall \ uninstall-am uninstall-binPROGRAMS uninstall-dist_pkgcfgDATA \ - uninstall-libLTLIBRARIES uninstall-pkgcfgDATA \ - uninstall-pluginLTLIBRARIES + uninstall-libLTLIBRARIES uninstall-libexecPROGRAMS \ + uninstall-pkgcfgDATA uninstall-pluginLTLIBRARIES # Tell versions [3.59,3.63) of GNU make to not export all variables. diff --git a/src/util/bandwidth.c b/src/util/bandwidth.c index 9d67949..60cb505 100644 --- a/src/util/bandwidth.c +++ b/src/util/bandwidth.c @@ -24,8 +24,7 @@ * @author Christian Grothoff */ #include "platform.h" -#include "gnunet_bandwidth_lib.h" -#include "gnunet_server_lib.h" +#include "gnunet_util_lib.h" #define LOG(kind,...) GNUNET_log_from (kind, "util-bandwidth", __VA_ARGS__) @@ -83,9 +82,9 @@ GNUNET_BANDWIDTH_value_get_available_until (struct GNUNET_BANDWIDTH_Value32NBO b = ntohl (bps.value__); LOG (GNUNET_ERROR_TYPE_DEBUG, - "Bandwidth has %llu bytes available until deadline in %llums\n", + "Bandwidth has %llu bytes available until deadline in %s\n", (unsigned long long) ((b * deadline.rel_value + 500LL) / 1000LL), - deadline.rel_value); + GNUNET_STRINGS_relative_time_to_string (deadline, GNUNET_YES)); return (b * deadline.rel_value + 500LL) / 1000LL; } diff --git a/src/util/client.c b/src/util/client.c index c29b48e..69380c9 100644 --- a/src/util/client.c +++ b/src/util/client.c @@ -27,11 +27,8 @@ * connections between clients and service providers. */ #include "platform.h" -#include "gnunet_common.h" -#include "gnunet_client_lib.h" #include "gnunet_protocols.h" -#include "gnunet_server_lib.h" -#include "gnunet_scheduler_lib.h" +#include "gnunet_util_lib.h" /** @@ -239,6 +236,11 @@ struct GNUNET_CLIENT_Connection */ int in_receive; + /** + * Is this the first message we are sending to the service? + */ + int first_message; + /** * How often have we tried to connect? */ @@ -261,12 +263,22 @@ try_unixpath (const char *service_name, #if AF_UNIX struct GNUNET_CONNECTION_Handle *connection; char *unixpath; + struct sockaddr_un s_un; unixpath = NULL; if ((GNUNET_OK == GNUNET_CONFIGURATION_get_value_string (cfg, service_name, "UNIXPATH", &unixpath)) && (0 < strlen (unixpath))) { /* We have a non-NULL unixpath, need to validate it */ + if (strlen (unixpath) >= sizeof (s_un.sun_path)) + { + LOG (GNUNET_ERROR_TYPE_WARNING, + _("UNIXPATH `%s' too long, maximum length is %llu\n"), unixpath, + (unsigned long long) sizeof (s_un.sun_path)); + unixpath = GNUNET_NETWORK_shorten_unixpath (unixpath); + LOG (GNUNET_ERROR_TYPE_INFO, + _("Using `%s' instead\n"), unixpath); + } connection = GNUNET_CONNECTION_create_from_connect_to_unixpath (cfg, unixpath); if (NULL != connection) { @@ -412,6 +424,7 @@ GNUNET_CLIENT_connect (const char *service_name, return NULL; connection = do_connect (service_name, cfg, 0); client = GNUNET_malloc (sizeof (struct GNUNET_CLIENT_Connection)); + client->first_message = GNUNET_YES; client->attempts = 1; client->connection = connection; client->service_name = GNUNET_strdup (service_name); @@ -738,40 +751,43 @@ GNUNET_CLIENT_service_test (const char *service, { LOG (GNUNET_ERROR_TYPE_WARNING, _("UNIXPATH `%s' too long, maximum length is %llu\n"), unixpath, - sizeof (s_un.sun_path)); + (unsigned long long) sizeof (s_un.sun_path)); + unixpath = GNUNET_NETWORK_shorten_unixpath (unixpath); + LOG (GNUNET_ERROR_TYPE_INFO, + _("Using `%s' instead\n"), unixpath); } - else + } + if (NULL != unixpath) + { + sock = GNUNET_NETWORK_socket_create (PF_UNIX, SOCK_STREAM, 0); + if (NULL != sock) { - sock = GNUNET_NETWORK_socket_create (PF_UNIX, SOCK_STREAM, 0); - if (NULL != sock) - { - memset (&s_un, 0, sizeof (s_un)); - s_un.sun_family = AF_UNIX; - slen = strlen (unixpath) + 1; - if (slen >= sizeof (s_un.sun_path)) - slen = sizeof (s_un.sun_path) - 1; - memcpy (s_un.sun_path, unixpath, slen); - s_un.sun_path[slen] = '\0'; - slen = sizeof (struct sockaddr_un); + memset (&s_un, 0, sizeof (s_un)); + s_un.sun_family = AF_UNIX; + slen = strlen (unixpath) + 1; + if (slen >= sizeof (s_un.sun_path)) + slen = sizeof (s_un.sun_path) - 1; + memcpy (s_un.sun_path, unixpath, slen); + s_un.sun_path[slen] = '\0'; + slen = sizeof (struct sockaddr_un); #if LINUX - s_un.sun_path[0] = '\0'; + s_un.sun_path[0] = '\0'; #endif #if HAVE_SOCKADDR_IN_SIN_LEN - s_un.sun_len = (u_char) slen; + s_un.sun_len = (u_char) slen; #endif - if (GNUNET_OK != - GNUNET_NETWORK_socket_bind (sock, (const struct sockaddr *) &s_un, - slen)) - { - /* failed to bind => service must be running */ - GNUNET_free (unixpath); - (void) GNUNET_NETWORK_socket_close (sock); - GNUNET_SCHEDULER_add_continuation (task, task_cls, - GNUNET_SCHEDULER_REASON_PREREQ_DONE); - return; - } - (void) GNUNET_NETWORK_socket_close (sock); - } + if (GNUNET_OK != + GNUNET_NETWORK_socket_bind (sock, (const struct sockaddr *) &s_un, + slen)) + { + /* failed to bind => service must be running */ + GNUNET_free (unixpath); + (void) GNUNET_NETWORK_socket_close (sock); + GNUNET_SCHEDULER_add_continuation (task, task_cls, + GNUNET_SCHEDULER_REASON_PREREQ_DONE); + return; + } + (void) GNUNET_NETWORK_socket_close (sock); /* let's try IP */ } } @@ -927,10 +943,19 @@ client_delayed_retry (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { struct GNUNET_CLIENT_TransmitHandle *th = cls; struct GNUNET_TIME_Relative delay; - + th->reconnect_task = GNUNET_SCHEDULER_NO_TASK; + if (0 != (tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN)) + { + /* give up, was shutdown */ + th->client->th = NULL; + th->notify (th->notify_cls, 0, NULL); + GNUNET_free (th); + return; + } th->client->connection = do_connect (th->client->service_name, th->client->cfg, th->client->attempts++); + th->client->first_message = GNUNET_YES; if (NULL == th->client->connection) { /* could happen if we're out of sockets */ @@ -942,9 +967,9 @@ client_delayed_retry (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) (th->client->back_off, 2), GNUNET_TIME_UNIT_SECONDS); LOG (GNUNET_ERROR_TYPE_DEBUG, - "Transmission failed %u times, trying again in %llums.\n", + "Transmission failed %u times, trying again in %s.\n", MAX_ATTEMPTS - th->attempts_left, - (unsigned long long) delay.rel_value); + GNUNET_STRINGS_relative_time_to_string (delay, GNUNET_YES)); th->reconnect_task = GNUNET_SCHEDULER_add_delayed (delay, &client_delayed_retry, th); return; @@ -989,7 +1014,8 @@ client_notify (void *cls, size_t size, void *buf) delay = GNUNET_TIME_absolute_get_remaining (th->timeout); delay.rel_value /= 2; if ((GNUNET_YES != th->auto_retry) || (0 == --th->attempts_left) || - (delay.rel_value < 1)) + (delay.rel_value < 1)|| + (0 != (GNUNET_SCHEDULER_get_reason() & GNUNET_SCHEDULER_REASON_SHUTDOWN))) { LOG (GNUNET_ERROR_TYPE_DEBUG, "Transmission failed %u times, giving up.\n", @@ -1015,9 +1041,9 @@ client_notify (void *cls, size_t size, void *buf) (client->back_off, 2), GNUNET_TIME_UNIT_SECONDS); LOG (GNUNET_ERROR_TYPE_DEBUG, - "Transmission failed %u times, trying again in %llums.\n", + "Transmission failed %u times, trying again in %s.\n", MAX_ATTEMPTS - th->attempts_left, - (unsigned long long) delay.rel_value); + GNUNET_STRINGS_relative_time_to_string (delay, GNUNET_YES)); client->th = th; th->reconnect_task = GNUNET_SCHEDULER_add_delayed (delay, &client_delayed_retry, th); @@ -1070,7 +1096,9 @@ GNUNET_CLIENT_notify_transmit_ready (struct GNUNET_CLIENT_Connection *client, th->client = client; th->size = size; th->timeout = GNUNET_TIME_relative_to_absolute (timeout); - th->auto_retry = auto_retry; + /* always auto-retry on first message to service */ + th->auto_retry = (GNUNET_YES == client->first_message) ? GNUNET_YES : auto_retry; + client->first_message = GNUNET_NO; th->notify = notify; th->notify_cls = notify_cls; th->attempts_left = MAX_ATTEMPTS; diff --git a/src/util/common_allocation.c b/src/util/common_allocation.c index 5e1f75e..dfa65d5 100644 --- a/src/util/common_allocation.c +++ b/src/util/common_allocation.c @@ -23,9 +23,14 @@ * @brief wrapper around malloc/free * @author Christian Grothoff */ - #include "platform.h" #include "gnunet_common.h" +#if HAVE_MALLOC_H +#include +#endif +#if HAVE_MALLOC_MALLOC_H +#include +#endif #define LOG(kind,...) GNUNET_log_from (kind, "util",__VA_ARGS__) @@ -182,6 +187,22 @@ GNUNET_xrealloc_ (void *ptr, size_t n, const char *filename, int linenumber) } +# if __BYTE_ORDER == __LITTLE_ENDIAN +#define BAADFOOD_STR "\x0D\xF0\xAD\xBA" +#endif +# if __BYTE_ORDER == __BIG_ENDIAN +#define BAADFOOD_STR "\xBA\xAD\xF0\x0D" +#endif + +#if WINDOWS +#define M_SIZE(p) _msize (p) +#endif +#if HAVE_MALLOC_USABLE_SIZE +#define M_SIZE(p) malloc_usable_size (p) +#elif HAVE_MALLOC_SIZE +#define M_SIZE(p) malloc_size (p) +#endif + /** * Free memory. Merely a wrapper for the case that we * want to keep track of allocations. @@ -197,6 +218,20 @@ GNUNET_xfree_ (void *ptr, const char *filename, int linenumber) #ifdef W32_MEM_LIMIT ptr = &((size_t *) ptr)[-1]; mem_used -= *((size_t *) ptr); +#endif +#if defined(M_SIZE) +#if ENABLE_POISONING + { + const uint64_t baadfood = GNUNET_ntohll (0xBAADF00DBAADF00DLL); + uint64_t *base = ptr; + size_t s = M_SIZE (ptr); + size_t i; + + for (i=0;i= 0 && gnunet_force_log_present == GNUNET_NO) + if ( (min_level >= 0) && (GNUNET_NO == gnunet_force_log_present) ) return caller_level <= min_level; /* Only look for forced definitions? */ @@ -365,11 +491,11 @@ GNUNET_get_log_call_status (int caller_level, const char *comp, for (i = 0; i < logdefs_len; i++) { ld = &logdefs[i]; - if ((!force_only || ld->force) && + if (( (!force_only) || ld->force) && (line >= ld->from_line && line <= ld->to_line) && - (regexec (&ld->component_regex, comp, 0, NULL, 0) == 0) && - (regexec (&ld->file_regex, file, 0, NULL, 0) == 0) && - (regexec (&ld->function_regex, function, 0, NULL, 0) == 0)) + (0 == regexec (&ld->component_regex, comp, 0, NULL, 0)) && + (0 == regexec (&ld->file_regex, file, 0, NULL, 0)) && + (0 == regexec (&ld->function_regex, function, 0, NULL, 0))) { /* We're finished */ return caller_level <= ld->level; @@ -426,7 +552,7 @@ parse_definitions (const char *constname, int force) int keep_looking = 1; tmp = getenv (constname); - if (tmp == NULL) + if (NULL == tmp) return 0; def = GNUNET_strdup (tmp); from_line = 0; @@ -454,17 +580,17 @@ parse_definitions (const char *constname, int force) { errno = 0; from_line = strtol (start, &t, 10); - if (errno != 0 || from_line < 0) + if ( (0 != errno) || (from_line < 0) ) { GNUNET_free (def); return counter; } - if (t < p && t[0] == '-') + if ( (t < p) && ('-' == t[0]) ) { errno = 0; start = t + 1; to_line = strtol (start, &t, 10); - if (errno != 0 || to_line < 0 || t != p) + if ( (0 != errno) || (to_line < 0) || (t != p) ) { GNUNET_free (def); return counter; @@ -481,7 +607,7 @@ parse_definitions (const char *constname, int force) break; } start = p + 1; - state += 1; + state++; break; case '\0': /* found EOL */ keep_looking = 0; @@ -493,15 +619,15 @@ parse_definitions (const char *constname, int force) p[0] = '\0'; state = 0; level = get_type ((const char *) start); - if (level == GNUNET_ERROR_TYPE_INVALID || - level == GNUNET_ERROR_TYPE_UNSPECIFIED || - 0 != add_definition (comp, file, function, from_line, to_line, - level, force)) + if ( (GNUNET_ERROR_TYPE_INVALID == level) || + (GNUNET_ERROR_TYPE_UNSPECIFIED == level) || + (0 != add_definition (comp, file, function, from_line, to_line, + level, force)) ) { GNUNET_free (def); return counter; } - counter += 1; + counter++; start = p + 1; break; default: @@ -515,16 +641,17 @@ parse_definitions (const char *constname, int force) return counter; } + /** * Utility function - parses GNUNET_LOG and GNUNET_FORCE_LOG. */ static void parse_all_definitions () { - if (gnunet_log_parsed == GNUNET_NO) + if (GNUNET_NO == gnunet_log_parsed) parse_definitions ("GNUNET_LOG", 0); gnunet_log_parsed = GNUNET_YES; - if (gnunet_force_log_parsed == GNUNET_NO) + if (GNUNET_NO == gnunet_force_log_parsed) gnunet_force_log_present = parse_definitions ("GNUNET_FORCE_LOG", 1) > 0 ? GNUNET_YES : GNUNET_NO; gnunet_force_log_parsed = GNUNET_YES; @@ -543,11 +670,9 @@ parse_all_definitions () int GNUNET_log_setup (const char *comp, const char *loglevel, const char *logfile) { - FILE *altlog; - int dirwarn; - char *fn; - const char *env_logfile = NULL; - int altlog_fd; + const char *env_logfile; + const struct tm *tm; + time_t t; min_level = get_type (loglevel); #if !defined(GNUNET_CULL_LOGGING) @@ -562,61 +687,20 @@ GNUNET_log_setup (const char *comp, const char *loglevel, const char *logfile) component_nopid = GNUNET_strdup (comp); env_logfile = getenv ("GNUNET_FORCE_LOGFILE"); - if ((env_logfile != NULL) && (strlen (env_logfile) > 0)) + if ((NULL != env_logfile) && (strlen (env_logfile) > 0)) logfile = env_logfile; - - if (logfile == NULL) + if (NULL == logfile) return GNUNET_OK; - fn = GNUNET_STRINGS_filename_expand (logfile); - if (NULL == fn) + GNUNET_free_non_null (log_file_name); + log_file_name = GNUNET_STRINGS_filename_expand (logfile); + if (NULL == log_file_name) return GNUNET_SYSERR; - dirwarn = (GNUNET_OK != GNUNET_DISK_directory_create_for_file (fn)); -#if WINDOWS - altlog_fd = OPEN (fn, O_APPEND | - O_BINARY | - O_WRONLY | O_CREAT, - _S_IREAD | _S_IWRITE); -#else - altlog_fd = OPEN (fn, O_APPEND | - O_WRONLY | O_CREAT, - S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH); -#endif - if (altlog_fd != -1) - { - int dup_return; - if (GNUNET_stderr != NULL) - fclose (GNUNET_stderr); - dup_return = dup2 (altlog_fd, 2); - (void) close (altlog_fd); - if (dup_return != -1) - { - altlog = fdopen (2, "ab"); - if (altlog == NULL) - { - (void) close (2); - altlog_fd = -1; - } - } - else - { - altlog_fd = -1; - } - } - if (altlog_fd == -1) - { - GNUNET_log_strerror_file (GNUNET_ERROR_TYPE_ERROR, "open", fn); - if (dirwarn) - GNUNET_log (GNUNET_ERROR_TYPE_WARNING, - _("Failed to create or access directory for log file `%s'\n"), - fn); - GNUNET_free (fn); - return GNUNET_SYSERR; - } - GNUNET_free (fn); - GNUNET_stderr = altlog; - return GNUNET_OK; + t = time (NULL); + tm = gmtime (&t); + return setup_log_file (tm); } + /** * Add a custom logger. * @@ -635,6 +719,7 @@ GNUNET_logger_add (GNUNET_Logger logger, void *logger_cls) loggers = entry; } + /** * Remove a custom logger. * @@ -663,6 +748,10 @@ GNUNET_logger_remove (GNUNET_Logger logger, void *logger_cls) GNUNET_free (pos); } +#if WINDOWS +CRITICAL_SECTION output_message_cs; +#endif + /** * Actually output the log message. @@ -677,8 +766,10 @@ output_message (enum GNUNET_ErrorType kind, const char *comp, const char *datestr, const char *msg) { struct CustomLogger *pos; - - if (GNUNET_stderr != NULL) +#if WINDOWS + EnterCriticalSection (&output_message_cs); +#endif + if (NULL != GNUNET_stderr) { FPRINTF (GNUNET_stderr, "%s %s %s %s", datestr, comp, GNUNET_error_type_to_string (kind), msg); @@ -690,6 +781,9 @@ output_message (enum GNUNET_ErrorType kind, const char *comp, pos->logger (pos->logger_cls, kind, comp, datestr, msg); pos = pos->next; } +#if WINDOWS + LeaveCriticalSection (&output_message_cs); +#endif } @@ -704,7 +798,7 @@ flush_bulk (const char *datestr) char msg[DATE_STR_SIZE + BULK_TRACK_SIZE + 256]; int rev; char *last; - char *ft; + const char *ft; if ((last_bulk_time.abs_value == 0) || (last_bulk_repeat == 0)) return; @@ -720,11 +814,10 @@ flush_bulk (const char *datestr) last[0] = '\0'; } ft = GNUNET_STRINGS_relative_time_to_string (GNUNET_TIME_absolute_get_duration - (last_bulk_time)); + (last_bulk_time), GNUNET_YES); snprintf (msg, sizeof (msg), _("Message `%.*s' repeated %u times in the last %s\n"), BULK_TRACK_SIZE, last_bulk, last_bulk_repeat, ft); - GNUNET_free (ft); if (rev == 1) last[0] = '\n'; output_message (last_bulk_kind, last_bulk_comp, datestr, msg); @@ -736,25 +829,37 @@ flush_bulk (const char *datestr) /** * Ignore the next n calls to the log function. * - * @param n number of log calls to ignore + * @param n number of log calls to ignore (could be negative) * @param check_reset GNUNET_YES to assert that the log skip counter is currently zero */ void -GNUNET_log_skip (unsigned int n, int check_reset) +GNUNET_log_skip (int n, int check_reset) { - if (n == 0) - { - int ok; + int ok; + if (0 == n) + { ok = (0 == skip_log); skip_log = 0; if (check_reset) - GNUNET_assert (ok); + GNUNET_break (ok); } else + { skip_log += n; + } } +/** + * Get the number of log calls that are going to be skipped + * + * @return number of log calls to be ignored + */ +int +GNUNET_get_log_skip () +{ + return skip_log; +} /** * Output a log message using the default mechanism. @@ -770,8 +875,6 @@ mylog (enum GNUNET_ErrorType kind, const char *comp, const char *message, { char date[DATE_STR_SIZE]; char date2[DATE_STR_SIZE]; - time_t timetmp; - struct timeval timeofday; struct tm *tmptr; size_t size; va_list vacp; @@ -780,32 +883,46 @@ mylog (enum GNUNET_ErrorType kind, const char *comp, const char *message, size = VSNPRINTF (NULL, 0, message, vacp) + 1; GNUNET_assert (0 != size); va_end (vacp); + memset (date, 0, DATE_STR_SIZE); { char buf[size]; +#ifdef WINDOWS + LARGE_INTEGER pc; + time_t timetmp; - VSNPRINTF (buf, size, message, va); time (&timetmp); - memset (date, 0, DATE_STR_SIZE); tmptr = localtime (&timetmp); - gettimeofday (&timeofday, NULL); - if (NULL != tmptr) + pc.QuadPart = 0; + QueryPerformanceCounter (&pc); + if (NULL == tmptr) + { + strcpy (date, "localtime error"); + } + else { -#ifdef WINDOWS - LARGE_INTEGER pc; - - pc.QuadPart = 0; - QueryPerformanceCounter (&pc); strftime (date2, DATE_STR_SIZE, "%b %d %H:%M:%S-%%020llu", tmptr); snprintf (date, sizeof (date), date2, - (long long) (pc.QuadPart / - (performance_frequency.QuadPart / 1000))); + (long long) (pc.QuadPart / + (performance_frequency.QuadPart / 1000))); + } #else + struct timeval timeofday; + + gettimeofday (&timeofday, NULL); + tmptr = localtime (&timeofday.tv_sec); + if (NULL == tmptr) + { + strcpy (date, "localtime error"); + } + else + { strftime (date2, DATE_STR_SIZE, "%b %d %H:%M:%S-%%06u", tmptr); snprintf (date, sizeof (date), date2, timeofday.tv_usec); -#endif } - else - strcpy (date, "localtime error"); +#endif + VSNPRINTF (buf, size, message, va); + if (NULL != tmptr) + (void) setup_log_file (tmptr); if ((0 != (kind & GNUNET_ERROR_TYPE_BULK)) && (last_bulk_time.abs_value != 0) && (0 == strncmp (buf, last_bulk, sizeof (last_bulk)))) @@ -894,6 +1011,43 @@ GNUNET_error_type_to_string (enum GNUNET_ErrorType kind) } +/** + * Convert a short hash to a string (for printing debug messages). + * This is one of the very few calls in the entire API that is + * NOT reentrant! + * + * @param hc the short hash code + * @return string form; will be overwritten by next call to GNUNET_h2s. + */ +const char * +GNUNET_short_h2s (const struct GNUNET_CRYPTO_ShortHashCode * hc) +{ + static struct GNUNET_CRYPTO_ShortHashAsciiEncoded ret; + + GNUNET_CRYPTO_short_hash_to_enc (hc, &ret); + ret.short_encoding[8] = '\0'; + return (const char *) ret.short_encoding; +} + + +/** + * Convert a short hash to a string (for printing debug messages). + * This is one of the very few calls in the entire API that is + * NOT reentrant! + * + * @param hc the short hash code + * @return string form; will be overwritten by next call to GNUNET_h2s_full. + */ +const char * +GNUNET_short_h2s_full (const struct GNUNET_CRYPTO_ShortHashCode * hc) +{ + static struct GNUNET_CRYPTO_ShortHashAsciiEncoded ret; + + GNUNET_CRYPTO_short_hash_to_enc (hc, &ret); + ret.short_encoding[sizeof (ret) - 1] = '\0'; + return (const char *) ret.short_encoding; +} + /** * Convert a hash to a string (for printing debug messages). * This is one of the very few calls in the entire API that is @@ -903,7 +1057,7 @@ GNUNET_error_type_to_string (enum GNUNET_ErrorType kind) * @return string form; will be overwritten by next call to GNUNET_h2s. */ const char * -GNUNET_h2s (const GNUNET_HashCode * hc) +GNUNET_h2s (const struct GNUNET_HashCode * hc) { static struct GNUNET_CRYPTO_HashAsciiEncoded ret; @@ -912,6 +1066,7 @@ GNUNET_h2s (const GNUNET_HashCode * hc) return (const char *) ret.encoding; } + /** * Convert a hash to a string (for printing debug messages). * This is one of the very few calls in the entire API that is @@ -921,7 +1076,7 @@ GNUNET_h2s (const GNUNET_HashCode * hc) * @return string form; will be overwritten by next call to GNUNET_h2s_full. */ const char * -GNUNET_h2s_full (const GNUNET_HashCode * hc) +GNUNET_h2s_full (const struct GNUNET_HashCode * hc) { static struct GNUNET_CRYPTO_HashAsciiEncoded ret; @@ -930,6 +1085,7 @@ GNUNET_h2s_full (const GNUNET_HashCode * hc) return (const char *) ret.encoding; } + /** * Convert a peer identity to a string (for printing debug messages). * This is one of the very few calls in the entire API that is @@ -949,6 +1105,7 @@ GNUNET_i2s (const struct GNUNET_PeerIdentity *pid) return (const char *) ret.encoding; } + /** * Convert a peer identity to a string (for printing debug messages). * This is one of the very few calls in the entire API that is @@ -1032,6 +1189,45 @@ GNUNET_a2s (const struct sockaddr *addr, socklen_t addrlen) } +/** + * Log error message about missing configuration option. + * + * @param kind log level + * @param section section with missing option + * @param option name of missing option + */ +void +GNUNET_log_config_missing (enum GNUNET_ErrorType kind, + const char *section, + const char *option) +{ + GNUNET_log (kind, + _("Configuration fails to specify option `%s' in section `%s'!\n"), + option, + section); +} + + +/** + * Log error message about invalid configuration option value. + * + * @param kind log level + * @param section section with invalid option + * @param option name of invalid option + * @param required what is required that is invalid about the option + */ +void +GNUNET_log_config_invalid (enum GNUNET_ErrorType kind, + const char *section, + const char *option, + const char *required) +{ + GNUNET_log (kind, + _("Configuration specifies invalid value for option `%s' in section `%s': %s\n"), + option, section, required); +} + + /** * Initializer */ @@ -1041,6 +1237,10 @@ void __attribute__ ((constructor)) GNUNET_util_cl_init () #ifdef MINGW GNInitWinEnv (NULL); #endif +#if WINDOWS + if (!InitializeCriticalSectionAndSpinCount (&output_message_cs, 0x00000400)) + GNUNET_abort (); +#endif } @@ -1049,6 +1249,9 @@ void __attribute__ ((constructor)) GNUNET_util_cl_init () */ void __attribute__ ((destructor)) GNUNET_util_cl_fini () { +#if WINDOWS + DeleteCriticalSection (&output_message_cs); +#endif #ifdef MINGW GNShutdownWinEnv (); #endif diff --git a/src/util/configuration.c b/src/util/configuration.c index 308672f..72fe0e7 100644 --- a/src/util/configuration.c +++ b/src/util/configuration.c @@ -140,118 +140,223 @@ GNUNET_CONFIGURATION_destroy (struct GNUNET_CONFIGURATION_Handle *cfg) /** - * Parse a configuration file, add all of the options in the - * file to the configuration environment. + * De-serializes configuration * * @param cfg configuration to update - * @param filename name of the configuration file - * @return GNUNET_OK on success, GNUNET_SYSERR on error + * @param mem the memory block of serialized configuration + * @param size the size of the memory block + * @param allow_inline set to GNUNET_YES if we recursively load configuration + * from inlined configurations; GNUNET_NO if not and raise warnings + * when we come across them + * @return GNUNET_OK on success, GNUNET_ERROR on error */ int -GNUNET_CONFIGURATION_parse (struct GNUNET_CONFIGURATION_Handle *cfg, - const char *filename) +GNUNET_CONFIGURATION_deserialize (struct GNUNET_CONFIGURATION_Handle *cfg, + const char *mem, + const size_t size, + int allow_inline) { - int dirty; - char line[256]; - char tag[64]; - char value[192]; - FILE *fp; + char *line; + char *line_orig; + size_t line_size; + char *pos; unsigned int nr; - int i; + size_t r_bytes; + size_t to_read; + size_t i; int emptyline; int ret; char *section; - char *fn; + char *eq; + char *tag; + char *value; - fn = GNUNET_STRINGS_filename_expand (filename); - if (fn == NULL) - return GNUNET_SYSERR; - dirty = cfg->dirty; /* back up value! */ - if (NULL == (fp = FOPEN (fn, "r"))) - { - LOG_STRERROR_FILE (GNUNET_ERROR_TYPE_WARNING, "fopen", fn); - GNUNET_free (fn); - return GNUNET_SYSERR; - } - GNUNET_free (fn); + LOG (GNUNET_ERROR_TYPE_DEBUG, "Deserializing config file\n"); ret = GNUNET_OK; section = GNUNET_strdup (""); - memset (line, 0, 256); nr = 0; - while (NULL != fgets (line, 255, fp)) + r_bytes = 0; + line_orig = NULL; + while (r_bytes < size) { + GNUNET_free_non_null (line_orig); + /* fgets-like behaviour on buffer */ + to_read = size - r_bytes; + pos = memchr (&mem[r_bytes], '\n', to_read); + if (NULL == pos) + { + line_orig = GNUNET_strndup (&mem[r_bytes], line_size = to_read); + r_bytes += line_size; + } + else + { + line_orig = GNUNET_strndup (&mem[r_bytes], line_size = (pos - &mem[r_bytes])); + r_bytes += line_size + 1; + } + line = line_orig; + /* increment line number */ nr++; - for (i = 0; i < 255; i++) + /* tabs and '\r' are whitespace */ + emptyline = GNUNET_YES; + for (i = 0; i < line_size; i++) + { if (line[i] == '\t') line[i] = ' '; - if (line[0] == '\n' || line[0] == '#' || line[0] == '%' || line[0] == '\r') - continue; - emptyline = 1; - for (i = 0; (i < 255 && line[i] != 0); i++) - if (line[i] != ' ' && line[i] != '\n' && line[i] != '\r') - emptyline = 0; - if (emptyline == 1) + if (line[i] == '\r') + line[i] = ' '; + if (' ' != line[i]) + emptyline = GNUNET_NO; + } + /* ignore empty lines */ + if (GNUNET_YES == emptyline) continue; + /* remove tailing whitespace */ - for (i = strlen (line) - 1; (i >= 0) && (isspace ((unsigned char) line[i])); - i--) + for (i = line_size - 1; (i >= 1) && (isspace ((unsigned char) line[i]));i--) line[i] = '\0'; - if (1 == SSCANF (line, "@INLINE@ %191[^\n]", value)) - { + + /* remove leading whitespace */ + for (; line[0] != '\0' && (isspace ((unsigned char) line[0])); line++); + + /* ignore comments */ + if ( ('#' == line[0]) || ('%' == line[0]) ) + continue; + + /* handle special "@INLINE@" directive */ + if (0 == strncasecmp (line, + "@INLINE@ ", + strlen ("@INLINE@ "))) + { /* @INLINE@ value */ - if (GNUNET_OK != GNUNET_CONFIGURATION_parse (cfg, value)) - ret = GNUNET_SYSERR; /* failed to parse included config */ + value = &line[strlen ("@INLINE@ ")]; + if (GNUNET_YES == allow_inline) + { + if (GNUNET_OK != GNUNET_CONFIGURATION_parse (cfg, value)) + { + ret = GNUNET_SYSERR; /* failed to parse included config */ + break; + } + } + else + { + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Ignoring parsing @INLINE@ configurations, not allowed!\n"); + ret = GNUNET_SYSERR; + break; + } + continue; } - else if (1 == SSCANF (line, "[%99[^]]]", value)) + if ( ('[' == line[0]) && (']' == line[line_size - 1]) ) { /* [value] */ + line[line_size - 1] = '\0'; + value = &line[1]; GNUNET_free (section); section = GNUNET_strdup (value); + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Config section `%s'\n", + section); + continue; } - else if (2 == SSCANF (line, " %63[^= ] = %191[^\n]", tag, value)) + if (NULL != (eq = strchr (line, '='))) { /* tag = value */ - /* Strip LF */ - i = strlen (value) - 1; - while ((i >= 0) && (isspace ((unsigned char) value[i]))) - value[i--] = '\0'; + tag = GNUNET_strndup (line, eq - line); + /* remove tailing whitespace */ + for (i = strlen (tag) - 1; (i >= 1) && (isspace ((unsigned char) tag[i]));i--) + tag[i] = '\0'; + + /* Strip whitespace */ + value = eq + 1; + while (isspace ((unsigned char) value[0])) + value++; + for (i = strlen (value) - 1; (i >= 1) && (isspace ((unsigned char) value[i]));i--) + value[i] = '\0'; + /* remove quotes */ i = 0; - if (value[0] == '"') + if ( ('"' == value[0]) && + ('"' == value[strlen (value) - 1]) ) { - i = 1; - while ((value[i] != '\0') && (value[i] != '"')) - i++; - if (value[i] == '"') - { - value[i] = '\0'; - i = 1; - } - else - i = 0; + value[strlen (value) - 1] = '\0'; + value++; } + LOG (GNUNET_ERROR_TYPE_DEBUG, "Config value %s=\"%s\"\n", tag, value); GNUNET_CONFIGURATION_set_value_string (cfg, section, tag, &value[i]); + GNUNET_free (tag); + continue; } - else if (1 == SSCANF (line, " %63[^= ] =[^\n]", tag)) - { - /* tag = */ - GNUNET_CONFIGURATION_set_value_string (cfg, section, tag, ""); - } - else - { - /* parse error */ - LOG (GNUNET_ERROR_TYPE_WARNING, - _("Syntax error in configuration file `%s' at line %u.\n"), filename, - nr); - ret = GNUNET_SYSERR; - break; - } + /* parse error */ + LOG (GNUNET_ERROR_TYPE_WARNING, + _("Syntax error while deserializing in line %u\n"), + nr); + ret = GNUNET_SYSERR; + break; + } + LOG (GNUNET_ERROR_TYPE_DEBUG, "Finished deserializing config\n"); + GNUNET_free_non_null (line_orig); + GNUNET_free (section); + GNUNET_assert ( (GNUNET_OK != ret) || (r_bytes == size) ); + return ret; +} + + +/** + * Parse a configuration file, add all of the options in the + * file to the configuration environment. + * + * @param cfg configuration to update + * @param filename name of the configuration file + * @return GNUNET_OK on success, GNUNET_SYSERR on error + */ +int +GNUNET_CONFIGURATION_parse (struct GNUNET_CONFIGURATION_Handle *cfg, + const char *filename) +{ + uint64_t fs64; + size_t fs; + char *fn; + char *mem; + int dirty; + int ret; + + LOG (GNUNET_ERROR_TYPE_DEBUG, "Asked to parse config file `%s'\n", filename); + fn = GNUNET_STRINGS_filename_expand (filename); + LOG (GNUNET_ERROR_TYPE_DEBUG, "Config file name expanded to `%s'\n", fn); + if (fn == NULL) + return GNUNET_SYSERR; + dirty = cfg->dirty; /* back up value! */ + if (GNUNET_SYSERR == + GNUNET_DISK_file_size (fn, &fs64, GNUNET_YES, GNUNET_YES)) + { + LOG (GNUNET_ERROR_TYPE_WARNING, + "Error while determining the file size of %s\n", fn); + GNUNET_free (fn); + return GNUNET_SYSERR; + } + if (fs64 > SIZE_MAX) + { + GNUNET_break (0); /* File size is more than the heap size */ + GNUNET_free (fn); + return GNUNET_SYSERR; + } + fs = fs64; + mem = GNUNET_malloc (fs); + if (fs != GNUNET_DISK_fn_read (fn, mem, fs)) + { + LOG (GNUNET_ERROR_TYPE_WARNING, + "Error while reading file %s\n", fn); + GNUNET_free (fn); + GNUNET_free (mem); + return GNUNET_SYSERR; } - GNUNET_assert (0 == FCLOSE (fp)); + LOG (GNUNET_ERROR_TYPE_DEBUG, "Deserializing contents of file `%s'\n", fn); + GNUNET_free (fn); + ret = GNUNET_CONFIGURATION_deserialize (cfg, mem, fs, GNUNET_YES); + GNUNET_free (mem); /* restore dirty flag - anything we set in the meantime * came from disk */ cfg->dirty = dirty; - GNUNET_free (section); return ret; } @@ -271,88 +376,140 @@ GNUNET_CONFIGURATION_is_dirty (const struct GNUNET_CONFIGURATION_Handle *cfg) /** - * Write configuration file. + * Serializes the given configuration. * - * @param cfg configuration to write - * @param filename where to write the configuration - * @return GNUNET_OK on success, GNUNET_SYSERR on error + * @param cfg configuration to serialize + * @param size will be set to the size of the serialized memory block + * @return the memory block where the serialized configuration is + * present. This memory should be freed by the caller */ -int -GNUNET_CONFIGURATION_write (struct GNUNET_CONFIGURATION_Handle *cfg, - const char *filename) +char * +GNUNET_CONFIGURATION_serialize (const struct GNUNET_CONFIGURATION_Handle *cfg, + size_t *size) { struct ConfigSection *sec; struct ConfigEntry *ent; - FILE *fp; - int error; - char *fn; + char *mem; + char *cbuf; char *val; char *pos; + int len; + size_t m_size; + size_t c_size; - fn = GNUNET_STRINGS_filename_expand (filename); - if (fn == NULL) - return GNUNET_SYSERR; - if (GNUNET_OK != GNUNET_DISK_directory_create_for_file (fn)) - { - GNUNET_free (fn); - return GNUNET_SYSERR; - } - if (NULL == (fp = FOPEN (fn, "w"))) - { - LOG_STRERROR_FILE (GNUNET_ERROR_TYPE_WARNING, "fopen", fn); - GNUNET_free (fn); - return GNUNET_SYSERR; - } - GNUNET_free (fn); - error = 0; + + /* Pass1 : calculate the buffer size required */ + m_size = 0; sec = cfg->sections; - while (sec != NULL) + while (NULL != sec) { - if (0 > FPRINTF (fp, "[%s]\n", sec->name)) + /* For each section we need to add 3 charaters: {'[',']','\n'} */ + m_size += strlen (sec->name) + 3; + ent = sec->entries; + while (NULL != ent) { - error = 1; - break; + if (NULL != ent->val) + { + /* if val has any '\n' then they occupy +1 character as '\n'->'\\','n' */ + pos = ent->val; + while (NULL != (pos = strstr (pos, "\n"))) + { + m_size++; + pos++; + } + /* For each key = value pair we need to add 4 characters (2 + spaces and 1 equal-to character and 1 new line) */ + m_size += strlen (ent->key) + strlen (ent->val) + 4; + } + ent = ent->next; } + /* A new line after section end */ + m_size++; + sec = sec->next; + } + + /* Pass2: Allocate memory and write the configuration to it */ + mem = GNUNET_malloc (m_size); + sec = cfg->sections; + c_size = 0; + *size = c_size; + while (NULL != sec) + { + len = GNUNET_asprintf (&cbuf, "[%s]\n", sec->name); + GNUNET_assert (0 < len); + memcpy (mem + c_size, cbuf, len); + c_size += len; + GNUNET_free (cbuf); ent = sec->entries; - while (ent != NULL) + while (NULL != ent) { - if (ent->val != NULL) + if (NULL != ent->val) { - val = GNUNET_malloc (strlen (ent->val) * 2 + 1); - strcpy (val, ent->val); + val = GNUNET_malloc (strlen (ent->val) * 2 + 1); + strcpy (val, ent->val); while (NULL != (pos = strstr (val, "\n"))) { memmove (&pos[2], &pos[1], strlen (&pos[1])); pos[0] = '\\'; pos[1] = 'n'; } - if (0 > FPRINTF (fp, "%s = %s\n", ent->key, val)) - { - error = 1; - GNUNET_free (val); - break; - } - GNUNET_free (val); + len = GNUNET_asprintf (&cbuf, "%s = %s\n", ent->key, val); + GNUNET_free (val); + memcpy (mem + c_size, cbuf, len); + c_size += len; + GNUNET_free (cbuf); } ent = ent->next; } - if (error != 0) - break; - if (0 > FPRINTF (fp, "%s\n", "")) - { - error = 1; - break; - } + memcpy (mem + c_size, "\n", 1); + c_size ++; sec = sec->next; } - if (error != 0) - LOG_STRERROR_FILE (GNUNET_ERROR_TYPE_WARNING, "fprintf", filename); - GNUNET_assert (0 == FCLOSE (fp)); - if (error != 0) + GNUNET_assert (c_size == m_size); + *size = c_size; + return mem; +} + + +/** + * Write configuration file. + * + * @param cfg configuration to write + * @param filename where to write the configuration + * @return GNUNET_OK on success, GNUNET_SYSERR on error + */ +int +GNUNET_CONFIGURATION_write (struct GNUNET_CONFIGURATION_Handle *cfg, + const char *filename) +{ + char *fn; + char *cfg_buf; + size_t size; + + fn = GNUNET_STRINGS_filename_expand (filename); + if (fn == NULL) + return GNUNET_SYSERR; + if (GNUNET_OK != GNUNET_DISK_directory_create_for_file (fn)) { + GNUNET_free (fn); + return GNUNET_SYSERR; + } + cfg_buf = GNUNET_CONFIGURATION_serialize (cfg, &size); + if (size != GNUNET_DISK_fn_write (fn, cfg_buf, size, + GNUNET_DISK_PERM_USER_READ + | GNUNET_DISK_PERM_USER_WRITE + | GNUNET_DISK_PERM_GROUP_READ + | GNUNET_DISK_PERM_GROUP_WRITE)) + { + GNUNET_free (fn); + GNUNET_free (cfg_buf); + LOG (GNUNET_ERROR_TYPE_WARNING, + "Writing configration to file: %s failed\n", filename); cfg->dirty = GNUNET_SYSERR; /* last write failed */ return GNUNET_SYSERR; } + GNUNET_free (fn); + GNUNET_free (cfg_buf); cfg->dirty = GNUNET_NO; /* last write succeeded */ return GNUNET_OK; } @@ -579,8 +736,8 @@ findEntry (const struct GNUNET_CONFIGURATION_Handle *cfg, const char *section, * @param value value to copy (of the default conf.) */ static void -compareEntries (void *cls, const char *section, const char *option, - const char *value) +compare_entries (void *cls, const char *section, const char *option, + const char *value) { struct DiffHandle *dh = cls; struct ConfigEntry *entNew; @@ -592,6 +749,28 @@ compareEntries (void *cls, const char *section, const char *option, } +/** + * Compute configuration with only entries that have been changed + * + * @param cfgDefault original configuration + * @param cfgNew new configuration + * @return configuration with only the differences, never NULL + */ +struct GNUNET_CONFIGURATION_Handle * +GNUNET_CONFIGURATION_get_diff (const struct GNUNET_CONFIGURATION_Handle + *cfgDefault, + const struct GNUNET_CONFIGURATION_Handle + *cfgNew) +{ + struct DiffHandle diffHandle; + + diffHandle.cfgDiff = GNUNET_CONFIGURATION_create (); + diffHandle.cfgDefault = cfgDefault; + GNUNET_CONFIGURATION_iterate (cfgNew, &compare_entries, &diffHandle); + return diffHandle.cfgDiff; +} + + /** * Write only configuration entries that have been changed to configuration file * @param cfgDefault default configuration @@ -606,13 +785,11 @@ GNUNET_CONFIGURATION_write_diffs (const struct GNUNET_CONFIGURATION_Handle *cfgNew, const char *filename) { int ret; - struct DiffHandle diffHandle; + struct GNUNET_CONFIGURATION_Handle *diff; - diffHandle.cfgDiff = GNUNET_CONFIGURATION_create (); - diffHandle.cfgDefault = cfgDefault; - GNUNET_CONFIGURATION_iterate (cfgNew, compareEntries, &diffHandle); - ret = GNUNET_CONFIGURATION_write (diffHandle.cfgDiff, filename); - GNUNET_CONFIGURATION_destroy (diffHandle.cfgDiff); + diff = GNUNET_CONFIGURATION_get_diff (cfgDefault, cfgNew); + ret = GNUNET_CONFIGURATION_write (diff, filename); + GNUNET_CONFIGURATION_destroy (diff); return ret; } @@ -632,12 +809,14 @@ GNUNET_CONFIGURATION_set_value_string (struct GNUNET_CONFIGURATION_Handle *cfg, { struct ConfigSection *sec; struct ConfigEntry *e; + char *nv; e = findEntry (cfg, section, option); if (e != NULL) { + nv = GNUNET_strdup (value); GNUNET_free_non_null (e->val); - e->val = GNUNET_strdup (value); + e->val = nv; return; } sec = findSection (cfg, section); @@ -768,13 +947,16 @@ GNUNET_CONFIGURATION_get_value_string (const struct GNUNET_CONFIGURATION_Handle { struct ConfigEntry *e; + LOG (GNUNET_ERROR_TYPE_DEBUG, "Asked to retrieve string `%s' in section `%s'\n", option, section); e = findEntry (cfg, section, option); if ((e == NULL) || (e->val == NULL)) { + LOG (GNUNET_ERROR_TYPE_DEBUG, "Failed to retrieve the string\n"); *value = NULL; return GNUNET_SYSERR; } *value = GNUNET_strdup (e->val); + LOG (GNUNET_ERROR_TYPE_DEBUG, "Retrieved string `%s'\n", e->val); return GNUNET_OK; } @@ -861,8 +1043,13 @@ GNUNET_CONFIGURATION_expand_dollar (const struct GNUNET_CONFIGURATION_Handle const char *post; const char *env; + LOG (GNUNET_ERROR_TYPE_DEBUG, "Asked to $-expand %s\n", orig); + if (orig[0] != '$') + { + LOG (GNUNET_ERROR_TYPE_DEBUG, "Doesn't start with $ - not expanding\n"); return orig; + } i = 0; while ((orig[i] != '/') && (orig[i] != '\\') && (orig[i] != '\0')) i++; @@ -875,16 +1062,21 @@ GNUNET_CONFIGURATION_expand_dollar (const struct GNUNET_CONFIGURATION_Handle orig[i] = '\0'; post = &orig[i + 1]; } + LOG (GNUNET_ERROR_TYPE_DEBUG, "Split into `%s' and `%s'\n", orig, post); if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_filename (cfg, "PATHS", &orig[1], &prefix)) { + LOG (GNUNET_ERROR_TYPE_DEBUG, "Filename for `%s' is not in PATHS config section\n", &orig[1]); if (NULL == (env = getenv (&orig[1]))) { + LOG (GNUNET_ERROR_TYPE_DEBUG, "`%s' is not an environment variable\n", &orig[1]); orig[i] = DIR_SEPARATOR; + LOG (GNUNET_ERROR_TYPE_DEBUG, "Expanded to `%s' (returning orig)\n", orig); return orig; } prefix = GNUNET_strdup (env); } + LOG (GNUNET_ERROR_TYPE_DEBUG, "Prefix is `%s'\n", prefix); result = GNUNET_malloc (strlen (prefix) + strlen (post) + 2); strcpy (result, prefix); if ((strlen (prefix) == 0) || @@ -893,6 +1085,7 @@ GNUNET_CONFIGURATION_expand_dollar (const struct GNUNET_CONFIGURATION_Handle strcat (result, post); GNUNET_free (prefix); GNUNET_free (orig); + LOG (GNUNET_ERROR_TYPE_DEBUG, "Expanded to `%s'\n", result); return result; } @@ -914,16 +1107,21 @@ GNUNET_CONFIGURATION_get_value_filename (const struct const char *option, char **value) { char *tmp; - + + LOG (GNUNET_ERROR_TYPE_DEBUG, "Asked to retrieve filename `%s' in section `%s'\n", option, section); if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_string (cfg, section, option, &tmp)) { + LOG (GNUNET_ERROR_TYPE_DEBUG, "Failed to retrieve filename\n"); *value = NULL; return GNUNET_SYSERR; } + LOG (GNUNET_ERROR_TYPE_DEBUG, "Retrieved filename `%s', $-expanding\n", tmp); tmp = GNUNET_CONFIGURATION_expand_dollar (cfg, tmp); + LOG (GNUNET_ERROR_TYPE_DEBUG, "Expanded to filename `%s', *nix-expanding\n", tmp); *value = GNUNET_STRINGS_filename_expand (tmp); GNUNET_free (tmp); + LOG (GNUNET_ERROR_TYPE_DEBUG, "Filename result is `%s'\n", *value); if (*value == NULL) return GNUNET_SYSERR; return GNUNET_OK; diff --git a/src/util/connection.c b/src/util/connection.c index 31e6399..c4795ce 100644 --- a/src/util/connection.c +++ b/src/util/connection.c @@ -247,7 +247,14 @@ struct GNUNET_CONNECTION_Handle * termination as a signal (because only then will the leaked * socket be freed!) */ - int16_t persist; + int8_t persist; + + /** + * Usually 0. Set to 1 if this handle is in used and should + * 'GNUNET_CONNECTION_destroy' be called right now, the action needs + * to be deferred by setting it to -1. + */ + int8_t destroy_later; }; @@ -556,6 +563,7 @@ connect_fail_continuation (struct GNUNET_CONNECTION_Handle *connection) GNUNET_assert (GNUNET_SCHEDULER_NO_TASK == connection->write_task); /* signal errors for jobs that used to wait on the connection */ + connection->destroy_later = 1; if (NULL != connection->receiver) signal_receive_error (connection, ECONNREFUSED); if (NULL != connection->nth.notify_ready) @@ -565,6 +573,14 @@ connect_fail_continuation (struct GNUNET_CONNECTION_Handle *connection) connection->nth.timeout_task = GNUNET_SCHEDULER_NO_TASK; signal_transmit_error (connection, ECONNREFUSED); } + if (-1 == connection->destroy_later) + { + /* do it now */ + connection->destroy_later = 0; + GNUNET_CONNECTION_destroy (connection); + return; + } + connection->destroy_later = 0; } @@ -744,10 +760,6 @@ try_connect_using_address (void *cls, const struct sockaddr *addr, { /* maybe refused / unsupported address, try next */ LOG_STRERROR (GNUNET_ERROR_TYPE_INFO, "connect"); -#if 0 - LOG (GNUNET_ERROR_TYPE_INFO, _("Failed to connect to `%s' (%p)\n"), - GNUNET_a2s (ap->addr, ap->addrlen), connection); -#endif GNUNET_break (GNUNET_OK == GNUNET_NETWORK_socket_close (ap->sock)); GNUNET_free (ap); return; @@ -852,8 +864,9 @@ GNUNET_CONNECTION_create_from_connect_to_unixpath (const struct GNUNET_free (connection); return NULL; } - if (GNUNET_OK != - GNUNET_NETWORK_socket_connect (connection->sock, connection->addr, connection->addrlen)) + if ( (GNUNET_OK != + GNUNET_NETWORK_socket_connect (connection->sock, connection->addr, connection->addrlen)) && + (EINPROGRESS != errno) ) { /* Just return; we expect everything to work eventually so don't fail HARD */ GNUNET_break (GNUNET_OK == GNUNET_NETWORK_socket_close (connection->sock)); @@ -941,6 +954,11 @@ GNUNET_CONNECTION_destroy (struct GNUNET_CONNECTION_Handle *connection) { struct AddressProbe *pos; + if (0 != connection->destroy_later) + { + connection->destroy_later = -1; + return; + } LOG (GNUNET_ERROR_TYPE_DEBUG, "Shutting down connection (%p)\n", connection); GNUNET_assert (NULL == connection->nth.notify_ready); GNUNET_assert (NULL == connection->receiver); diff --git a/src/util/container_bloomfilter.c b/src/util/container_bloomfilter.c index 8c226f6..1a2c876 100644 --- a/src/util/container_bloomfilter.c +++ b/src/util/container_bloomfilter.c @@ -231,7 +231,7 @@ static void decrementBit (char *bitArray, unsigned int bitIdx, const struct GNUNET_DISK_FileHandle *fh) { - OFF_T fileSlot; + OFF_T fileslot; unsigned char value; unsigned int high; unsigned int low; @@ -240,9 +240,13 @@ decrementBit (char *bitArray, unsigned int bitIdx, if (GNUNET_DISK_handle_invalid (fh)) return; /* cannot decrement! */ /* Each char slot in the counter file holds two 4 bit counters */ - fileSlot = bitIdx / 2; + fileslot = bitIdx / 2; targetLoc = bitIdx % 2; - GNUNET_DISK_file_seek (fh, fileSlot, GNUNET_DISK_SEEK_SET); + if (GNUNET_SYSERR == GNUNET_DISK_file_seek (fh, fileslot, GNUNET_DISK_SEEK_SET)) + { + GNUNET_log_strerror (GNUNET_ERROR_TYPE_ERROR, "seek"); + return; + } if (1 != GNUNET_DISK_file_read (fh, &value, 1)) value = 0; low = value & 0xF; @@ -268,7 +272,11 @@ decrementBit (char *bitArray, unsigned int bitIdx, } } value = ((high << 4) | low); - GNUNET_DISK_file_seek (fh, fileSlot, GNUNET_DISK_SEEK_SET); + if (GNUNET_SYSERR == GNUNET_DISK_file_seek (fh, fileslot, GNUNET_DISK_SEEK_SET)) + { + GNUNET_log_strerror (GNUNET_ERROR_TYPE_ERROR, "seek"); + return; + } GNUNET_assert (1 == GNUNET_DISK_file_write (fh, &value, 1)); } @@ -340,9 +348,9 @@ typedef int (*BitIterator) (void *cls, */ static void iterateBits (const struct GNUNET_CONTAINER_BloomFilter *bf, - BitIterator callback, void *arg, const GNUNET_HashCode * key) + BitIterator callback, void *arg, const struct GNUNET_HashCode * key) { - GNUNET_HashCode tmp[2]; + struct GNUNET_HashCode tmp[2]; int bitCount; unsigned int round; unsigned int slot = 0; @@ -354,7 +362,7 @@ iterateBits (const struct GNUNET_CONTAINER_BloomFilter *bf, GNUNET_assert (bf->bitArraySize * 8LL > bf->bitArraySize); while (bitCount > 0) { - while (slot < (sizeof (GNUNET_HashCode) / sizeof (uint32_t))) + while (slot < (sizeof (struct GNUNET_HashCode) / sizeof (uint32_t))) { if (GNUNET_YES != callback (arg, bf, @@ -368,7 +376,7 @@ iterateBits (const struct GNUNET_CONTAINER_BloomFilter *bf, } if (bitCount > 0) { - GNUNET_CRYPTO_hash (&tmp[round & 1], sizeof (GNUNET_HashCode), + GNUNET_CRYPTO_hash (&tmp[round & 1], sizeof (struct GNUNET_HashCode), &tmp[(round + 1) & 1]); round++; slot = 0; @@ -696,7 +704,7 @@ GNUNET_CONTAINER_bloomfilter_clear (struct GNUNET_CONTAINER_BloomFilter *bf) */ int GNUNET_CONTAINER_bloomfilter_test (const struct GNUNET_CONTAINER_BloomFilter - *bf, const GNUNET_HashCode * e) + *bf, const struct GNUNET_HashCode * e) { int res; @@ -716,7 +724,7 @@ GNUNET_CONTAINER_bloomfilter_test (const struct GNUNET_CONTAINER_BloomFilter */ void GNUNET_CONTAINER_bloomfilter_add (struct GNUNET_CONTAINER_BloomFilter *bf, - const GNUNET_HashCode * e) + const struct GNUNET_HashCode * e) { if (NULL == bf) return; @@ -801,7 +809,7 @@ GNUNET_CONTAINER_bloomfilter_or2 (struct GNUNET_CONTAINER_BloomFilter *bf, */ void GNUNET_CONTAINER_bloomfilter_remove (struct GNUNET_CONTAINER_BloomFilter *bf, - const GNUNET_HashCode * e) + const struct GNUNET_HashCode * e) { if (NULL == bf) return; @@ -827,7 +835,7 @@ GNUNET_CONTAINER_bloomfilter_resize (struct GNUNET_CONTAINER_BloomFilter *bf, void *iterator_cls, size_t size, unsigned int k) { - GNUNET_HashCode hc; + struct GNUNET_HashCode hc; unsigned int i; GNUNET_free (bf->bitArray); diff --git a/src/util/container_heap.c b/src/util/container_heap.c index b9cab1e..e2a2700 100644 --- a/src/util/container_heap.c +++ b/src/util/container_heap.c @@ -400,6 +400,8 @@ GNUNET_CONTAINER_heap_remove_root (struct GNUNET_CONTAINER_Heap *heap) heap->root = root->left_child; insert_node (heap, heap->root, root->right_child); } + if (heap->walk_pos == root) + heap->walk_pos = heap->root; GNUNET_free (root); #if EXTRA_CHECKS GNUNET_assert (((heap->size == 0) && (heap->root == NULL)) || diff --git a/src/util/container_meta_data.c b/src/util/container_meta_data.c index b1051c8..a868e81 100644 --- a/src/util/container_meta_data.c +++ b/src/util/container_meta_data.c @@ -40,10 +40,15 @@ struct MetaItem { /** - * This is a linked list. + * This is a doubly linked list. */ struct MetaItem *next; + /** + * This is a doubly linked list. + */ + struct MetaItem *prev; + /** * Name of the extracting plugin. */ @@ -82,9 +87,14 @@ struct MetaItem struct GNUNET_CONTAINER_MetaData { /** - * Linked list of the meta data items. + * Head of linked list of the meta data items. */ - struct MetaItem *items; + struct MetaItem *items_head; + + /** + * Tail of linked list of the meta data items. + */ + struct MetaItem *items_tail; /** * Complete serialized and compressed buffer of the items. @@ -120,15 +130,15 @@ GNUNET_CONTAINER_meta_data_create () /** * Free meta data item. * - * @param item item to free + * @param mi item to free */ static void -meta_item_free (struct MetaItem *item) +meta_item_free (struct MetaItem *mi) { - GNUNET_free_non_null (item->plugin_name); - GNUNET_free_non_null (item->mime_type); - GNUNET_free_non_null (item->data); - GNUNET_free (item); + GNUNET_free_non_null (mi->plugin_name); + GNUNET_free_non_null (mi->mime_type); + GNUNET_free_non_null (mi->data); + GNUNET_free (mi); } @@ -141,7 +151,7 @@ meta_item_free (struct MetaItem *item) static void invalidate_sbuf (struct GNUNET_CONTAINER_MetaData *md) { - if (md->sbuf == NULL) + if (NULL == md->sbuf) return; GNUNET_free (md->sbuf); md->sbuf = NULL; @@ -157,14 +167,14 @@ invalidate_sbuf (struct GNUNET_CONTAINER_MetaData *md) void GNUNET_CONTAINER_meta_data_destroy (struct GNUNET_CONTAINER_MetaData *md) { - struct MetaItem *item; + struct MetaItem *pos; - if (md == NULL) + if (NULL == md) return; - while (NULL != (item = md->items)) + while (NULL != (pos = md->items_head)) { - md->items = item->next; - meta_item_free (item); + GNUNET_CONTAINER_DLL_remove (md->items_head, md->items_tail, pos); + meta_item_free (pos); } GNUNET_free_non_null (md->sbuf); GNUNET_free (md); @@ -179,21 +189,20 @@ GNUNET_CONTAINER_meta_data_destroy (struct GNUNET_CONTAINER_MetaData *md) void GNUNET_CONTAINER_meta_data_clear (struct GNUNET_CONTAINER_MetaData *md) { - struct MetaItem *item; + struct MetaItem *mi; - if (md == NULL) + if (NULL == md) return; - while (NULL != (item = md->items)) + while (NULL != (mi = md->items_head)) { - md->items = item->next; - meta_item_free (item); + GNUNET_CONTAINER_DLL_remove (md->items_head, md->items_tail, mi); + meta_item_free (mi); } GNUNET_free_non_null (md->sbuf); memset (md, 0, sizeof (struct GNUNET_CONTAINER_MetaData)); } - /** * Test if two MDs are equal. We consider them equal if * the meta types, formats and content match (we do not @@ -218,13 +227,10 @@ GNUNET_CONTAINER_meta_data_test_equal (const struct GNUNET_CONTAINER_MetaData return GNUNET_YES; if (md1->item_count != md2->item_count) return GNUNET_NO; - - i = md1->items; - while (NULL != i) + for (i = md1->items_head; NULL != i; i = i->next) { found = GNUNET_NO; - j = md2->items; - while (NULL != j) + for (j = md2->items_head; NULL != j; j = j->next) { if ((i->type == j->type) && (i->format == j->format) && (i->data_size == j->data_size) && @@ -233,11 +239,11 @@ GNUNET_CONTAINER_meta_data_test_equal (const struct GNUNET_CONTAINER_MetaData found = GNUNET_YES; break; } - j = j->next; + if (j->data_size < i->data_size) + break; /* elements are sorted by (decreasing) size... */ } - if (found == GNUNET_NO) + if (GNUNET_NO == found) return GNUNET_NO; - i = i->next; } return GNUNET_YES; } @@ -257,7 +263,7 @@ GNUNET_CONTAINER_meta_data_test_equal (const struct GNUNET_CONTAINER_MetaData * @param data_mime_type mime-type of data (not of the original file); * can be NULL (if mime-type is not known) * @param data actual meta-data found - * @param data_len number of bytes in data + * @param data_size number of bytes in data * @return GNUNET_OK on success, GNUNET_SYSERR if this entry already exists * data_mime_type and plugin_name are not considered for "exists" checks */ @@ -267,64 +273,61 @@ GNUNET_CONTAINER_meta_data_insert (struct GNUNET_CONTAINER_MetaData *md, enum EXTRACTOR_MetaType type, enum EXTRACTOR_MetaFormat format, const char *data_mime_type, const char *data, - size_t data_len) + size_t data_size) { - struct MetaItem *prev; struct MetaItem *pos; - struct MetaItem *i; + struct MetaItem *mi; char *p; - prev = NULL; - pos = md->items; - while (NULL != pos) + for (pos = md->items_head; NULL != pos; pos = pos->next) { - if (pos->data_size < data_len) - break; - if ((pos->type == type) && (pos->data_size == data_len) && - (0 == memcmp (pos->data, data, data_len))) + if (pos->data_size < data_size) + break; /* elements are sorted by size in the list */ + if ((pos->type == type) && (pos->data_size == data_size) && + (0 == memcmp (pos->data, data, data_size))) { - if ((pos->mime_type == NULL) && (data_mime_type != NULL)) + if ((NULL == pos->mime_type) && (NULL != data_mime_type)) { pos->mime_type = GNUNET_strdup (data_mime_type); invalidate_sbuf (md); } - if ((pos->format == EXTRACTOR_METAFORMAT_C_STRING) && - (format == EXTRACTOR_METAFORMAT_UTF8)) + if ((EXTRACTOR_METAFORMAT_C_STRING == pos->format) && + (EXTRACTOR_METAFORMAT_UTF8 == format)) { pos->format = EXTRACTOR_METAFORMAT_UTF8; invalidate_sbuf (md); } return GNUNET_SYSERR; } - prev = pos; - pos = pos->next; } md->item_count++; - i = GNUNET_malloc (sizeof (struct MetaItem)); - i->type = type; - i->format = format; - i->data_size = data_len; - i->next = pos; - if (prev == NULL) - md->items = i; + mi = GNUNET_malloc (sizeof (struct MetaItem)); + mi->type = type; + mi->format = format; + mi->data_size = data_size; + if (NULL == pos) + GNUNET_CONTAINER_DLL_insert_tail (md->items_head, + md->items_tail, + mi); else - prev->next = i; - i->mime_type = - (data_mime_type == NULL) ? NULL : GNUNET_strdup (data_mime_type); - i->plugin_name = (plugin_name == NULL) ? NULL : GNUNET_strdup (plugin_name); - i->data = GNUNET_malloc (data_len); - memcpy (i->data, data, data_len); - /* change OS native dir separators to unix '/' and others to '_' */ - if ( (type == EXTRACTOR_METATYPE_FILENAME) || - (type == EXTRACTOR_METATYPE_GNUNET_ORIGINAL_FILENAME) ) + GNUNET_CONTAINER_DLL_insert_after (md->items_head, + md->items_tail, + pos->prev, + mi); + mi->mime_type = + (NULL == data_mime_type) ? NULL : GNUNET_strdup (data_mime_type); + mi->plugin_name = (NULL == plugin_name) ? NULL : GNUNET_strdup (plugin_name); + mi->data = GNUNET_malloc (data_size); + memcpy (mi->data, data, data_size); + /* change all dir separators to POSIX style ('/') */ + if ( (EXTRACTOR_METATYPE_FILENAME == type) || + (EXTRACTOR_METATYPE_GNUNET_ORIGINAL_FILENAME == type) ) { - p = i->data; - while ((*p != '\0') && (p < i->data + data_len)) + p = mi->data; + while (('\0' != *p) && (p < mi->data + data_size)) { - if (*p == DIR_SEPARATOR) + if ('\\' == *p) *p = '/'; - else if (*p == '\\') - *p = '_'; p++; } } @@ -346,18 +349,18 @@ GNUNET_CONTAINER_meta_data_insert (struct GNUNET_CONTAINER_MetaData *md, * @param data_mime_type mime-type of data (not of the original file); * can be NULL (if mime-type is not known) * @param data actual meta-data found - * @param data_len number of bytes in data + * @param data_size number of bytes in data * @return 0 (to continue) */ static int merge_helper (void *cls, const char *plugin_name, enum EXTRACTOR_MetaType type, enum EXTRACTOR_MetaFormat format, const char *data_mime_type, - const char *data, size_t data_len) + const char *data, size_t data_size) { struct GNUNET_CONTAINER_MetaData *md = cls; (void) GNUNET_CONTAINER_meta_data_insert (md, plugin_name, type, format, - data_mime_type, data, data_len); + data_mime_type, data, data_size); return 0; } @@ -384,37 +387,31 @@ GNUNET_CONTAINER_meta_data_merge (struct GNUNET_CONTAINER_MetaData *md, * @param type type of the item to remove * @param data specific value to remove, NULL to remove all * entries of the given type - * @param data_len number of bytes in data + * @param data_size number of bytes in data * @return GNUNET_OK on success, GNUNET_SYSERR if the item does not exist in md */ int GNUNET_CONTAINER_meta_data_delete (struct GNUNET_CONTAINER_MetaData *md, enum EXTRACTOR_MetaType type, - const char *data, size_t data_len) + const char *data, size_t data_size) { struct MetaItem *pos; - struct MetaItem *prev; - prev = NULL; - pos = md->items; - while (NULL != pos) + for (pos = md->items_head; NULL != pos; pos = pos->next) { + if (pos->data_size < data_size) + break; /* items are sorted by (decreasing) size */ if ((pos->type == type) && - ((data == NULL) || - ((pos->data_size == data_len) && - (0 == memcmp (pos->data, data, data_len))))) + ((NULL == data) || + ((pos->data_size == data_size) && + (0 == memcmp (pos->data, data, data_size))))) { - if (prev == NULL) - md->items = pos->next; - else - prev->next = pos->next; + GNUNET_CONTAINER_DLL_remove (md->items_head, md->items_tail, pos); meta_item_free (pos); md->item_count--; invalidate_sbuf (md); return GNUNET_OK; } - prev = pos; - pos = pos->next; } return GNUNET_SYSERR; } @@ -430,7 +427,7 @@ void GNUNET_CONTAINER_meta_data_add_publication_date (struct GNUNET_CONTAINER_MetaData *md) { - char *dat; + const char *dat; struct GNUNET_TIME_Absolute t; t = GNUNET_TIME_absolute_get (); @@ -441,7 +438,6 @@ GNUNET_CONTAINER_meta_data_add_publication_date (struct EXTRACTOR_METATYPE_PUBLICATION_DATE, EXTRACTOR_METAFORMAT_UTF8, "text/plain", dat, strlen (dat) + 1); - GNUNET_free (dat); } @@ -460,19 +456,15 @@ GNUNET_CONTAINER_meta_data_iterate (const struct GNUNET_CONTAINER_MetaData *md, { struct MetaItem *pos; - if (md == NULL) + if (NULL == md) return 0; - if (iter == NULL) + if (NULL == iter) return md->item_count; - pos = md->items; - while (NULL != pos) - { + for (pos = md->items_head; NULL != pos; pos = pos->next) if (0 != iter (iter_cls, pos->plugin_name, pos->type, pos->format, pos->mime_type, pos->data, pos->data_size)) return md->item_count; - pos = pos->next; - } return md->item_count; } @@ -493,17 +485,13 @@ GNUNET_CONTAINER_meta_data_get_by_type (const struct GNUNET_CONTAINER_MetaData { struct MetaItem *pos; - if (md == NULL) + if (NULL == md) return NULL; - pos = md->items; - while (NULL != pos) - { + for (pos = md->items_head; NULL != pos; pos = pos->next) if ((type == pos->type) && ((pos->format == EXTRACTOR_METAFORMAT_UTF8) || (pos->format == EXTRACTOR_METAFORMAT_C_STRING))) return GNUNET_strdup (pos->data); - pos = pos->next; - } return NULL; } @@ -528,18 +516,16 @@ GNUNET_CONTAINER_meta_data_get_first_by_types (const struct va_list args; enum EXTRACTOR_MetaType type; - if (md == NULL) + if (NULL == md) return NULL; ret = NULL; va_start (args, md); while (1) { type = va_arg (args, enum EXTRACTOR_MetaType); - - if (type == -1) + if (-1 == type) break; - ret = GNUNET_CONTAINER_meta_data_get_by_type (md, type); - if (ret != NULL) + if (NULL != (ret = GNUNET_CONTAINER_meta_data_get_by_type (md, type))) break; } va_end (args); @@ -562,25 +548,23 @@ GNUNET_CONTAINER_meta_data_get_thumbnail (const struct GNUNET_CONTAINER_MetaData struct MetaItem *pos; struct MetaItem *match; - if (md == NULL) + if (NULL == md) return 0; match = NULL; - pos = md->items; - while (NULL != pos) + for (pos = md->items_head; NULL != pos; pos = pos->next) { if ((NULL != pos->mime_type) && (0 == strncasecmp ("image/", pos->mime_type, strlen ("image/"))) && - (pos->format == EXTRACTOR_METAFORMAT_BINARY)) + (EXTRACTOR_METAFORMAT_BINARY == pos->format)) { - if (match == NULL) + if (NULL == match) match = pos; else if ((match->type != EXTRACTOR_METATYPE_THUMBNAIL) && (pos->type == EXTRACTOR_METATYPE_THUMBNAIL)) match = pos; } - pos = pos->next; } - if ((match == NULL) || (match->data_size == 0)) + if ((NULL == match) || (0 == match->data_size)) return 0; *thumb = GNUNET_malloc (match->data_size); memcpy (*thumb, match->data, match->data_size); @@ -601,17 +585,13 @@ GNUNET_CONTAINER_meta_data_duplicate (const struct GNUNET_CONTAINER_MetaData struct GNUNET_CONTAINER_MetaData *ret; struct MetaItem *pos; - if (md == NULL) + if (NULL == md) return NULL; ret = GNUNET_CONTAINER_meta_data_create (); - pos = md->items; - while (NULL != pos) - { + for (pos = md->items_tail; NULL != pos; pos = pos->prev) GNUNET_CONTAINER_meta_data_insert (ret, pos->plugin_name, pos->type, pos->format, pos->mime_type, pos->data, pos->data_size); - pos = pos->next; - } return ret; } @@ -781,10 +761,10 @@ GNUNET_CONTAINER_meta_data_serialize (const struct GNUNET_CONTAINER_MetaData if (max < sizeof (struct MetaDataHeader)) return GNUNET_SYSERR; /* far too small */ - if (md == NULL) + if (NULL == md) return 0; - if (md->sbuf != NULL) + if (NULL != md->sbuf) { /* try to use serialization cache */ if (md->sbuf_size <= max) @@ -800,16 +780,14 @@ GNUNET_CONTAINER_meta_data_serialize (const struct GNUNET_CONTAINER_MetaData } dst = NULL; msize = 0; - pos = md->items; - while (NULL != pos) + for (pos = md->items_tail; NULL != pos; pos = pos->prev) { msize += sizeof (struct MetaDataEntry); msize += pos->data_size; - if (pos->plugin_name != NULL) + if (NULL != pos->plugin_name) msize += strlen (pos->plugin_name) + 1; - if (pos->mime_type != NULL) + if (NULL != pos->mime_type) msize += strlen (pos->mime_type) + 1; - pos = pos->next; } size = (size_t) msize; if (size != msize) @@ -826,8 +804,7 @@ GNUNET_CONTAINER_meta_data_serialize (const struct GNUNET_CONTAINER_MetaData mdata = (char *) &ent[md->item_count]; off = size - (md->item_count * sizeof (struct MetaDataEntry)); i = 0; - pos = md->items; - while (NULL != pos) + for (pos = md->items_head; NULL != pos; pos = pos->next) { ent[i].type = htonl ((uint32_t) pos->type); ent[i].format = htonl ((uint32_t) pos->format); @@ -851,22 +828,20 @@ GNUNET_CONTAINER_meta_data_serialize (const struct GNUNET_CONTAINER_MetaData if (pos->mime_type != NULL) memcpy (&mdata[off], pos->mime_type, mlen); i++; - pos = pos->next; } - GNUNET_assert (off == 0); + GNUNET_assert (0 == off); clen = 0; cdata = NULL; left = size; i = 0; - pos = md->items; - while (pos != NULL) + for (pos = md->items_head; NULL != pos; pos = pos->next) { comp = GNUNET_NO; if (0 == (opt & GNUNET_CONTAINER_META_DATA_SERIALIZE_NO_COMPRESS)) comp = try_compression ((const char *) &ent[i], left, &cdata, &clen); - if ((md->sbuf == NULL) && (i == 0)) + if ((NULL == md->sbuf) && (0 == i)) { /* fill 'sbuf'; this "modifies" md, but since this is only * an internal cache we will cast away the 'const' instead @@ -892,12 +867,12 @@ GNUNET_CONTAINER_meta_data_serialize (const struct GNUNET_CONTAINER_MetaData } if (((left + sizeof (struct MetaDataHeader)) <= max) || - ((comp == GNUNET_YES) && (clen <= max))) + ((GNUNET_YES == comp) && (clen <= max))) { /* success, this now fits! */ if (GNUNET_YES == comp) { - if (dst == NULL) + if (NULL == dst) dst = GNUNET_malloc (clen + sizeof (struct MetaDataHeader)); hdr = (struct MetaDataHeader *) dst; hdr->version = htonl (2 | HEADER_COMPRESSED); @@ -905,12 +880,13 @@ GNUNET_CONTAINER_meta_data_serialize (const struct GNUNET_CONTAINER_MetaData hdr->entries = htonl (md->item_count - i); memcpy (&dst[sizeof (struct MetaDataHeader)], cdata, clen); GNUNET_free (cdata); + cdata = NULL; GNUNET_free (ent); rlen = clen + sizeof (struct MetaDataHeader); } else { - if (dst == NULL) + if (NULL == dst) dst = GNUNET_malloc (left + sizeof (struct MetaDataHeader)); hdr = (struct MetaDataHeader *) dst; hdr->version = htonl (2); @@ -922,7 +898,10 @@ GNUNET_CONTAINER_meta_data_serialize (const struct GNUNET_CONTAINER_MetaData } if (NULL != *target) { - memcpy (*target, dst, clen + sizeof (struct MetaDataHeader)); + if (GNUNET_YES == comp) + memcpy (*target, dst, clen + sizeof (struct MetaDataHeader)); + else + memcpy (*target, dst, left + sizeof (struct MetaDataHeader)); GNUNET_free (dst); } else @@ -943,11 +922,14 @@ GNUNET_CONTAINER_meta_data_serialize (const struct GNUNET_CONTAINER_MetaData * end and try again without it */ left -= sizeof (struct MetaDataEntry); left -= pos->data_size; - if (pos->plugin_name != NULL) + if (NULL != pos->plugin_name) left -= strlen (pos->plugin_name) + 1; - if (pos->mime_type != NULL) + if (NULL != pos->mime_type) left -= strlen (pos->mime_type) + 1; - pos = pos->next; + + GNUNET_free_non_null (cdata); + cdata = NULL; + i++; } GNUNET_free (ent); @@ -956,7 +938,7 @@ GNUNET_CONTAINER_meta_data_serialize (const struct GNUNET_CONTAINER_MetaData ihdr.version = htonl (2); ihdr.entries = htonl (0); ihdr.size = htonl (0); - if (*target == NULL) + if (NULL == *target) *target = GNUNET_malloc (sizeof (struct MetaDataHeader)); memcpy (*target, &ihdr, sizeof (struct MetaDataHeader)); return sizeof (struct MetaDataHeader); @@ -976,13 +958,13 @@ GNUNET_CONTAINER_meta_data_get_serialized_size (const struct ssize_t ret; char *ptr; - if (md->sbuf != NULL) + if (NULL != md->sbuf) return md->sbuf_size; ptr = NULL; ret = GNUNET_CONTAINER_meta_data_serialize (md, &ptr, GNUNET_MAX_MALLOC_CHECKED, GNUNET_CONTAINER_META_DATA_SERIALIZE_FULL); - if (ret != -1) + if (-1 != ret) GNUNET_free (ptr); return ret; } @@ -1008,14 +990,9 @@ decompress (const char *input, size_t inputSize, size_t outputSize) output = GNUNET_malloc (olen); if (Z_OK == uncompress ((Bytef *) output, &olen, (const Bytef *) input, inputSize)) - { return output; - } - else - { - GNUNET_free (output); - return NULL; - } + GNUNET_free (output); + return NULL; } @@ -1056,9 +1033,9 @@ GNUNET_CONTAINER_meta_data_deserialize (const char *input, size_t size) version = ntohl (hdr.version) & HEADER_VERSION_MASK; compressed = (ntohl (hdr.version) & HEADER_COMPRESSED) != 0; - if (version == 1) + if (1 == version) return NULL; /* null pointer */ - if (version != 2) + if (2 != version) { GNUNET_break_op (0); /* unsupported version */ return NULL; @@ -1084,7 +1061,7 @@ GNUNET_CONTAINER_meta_data_deserialize (const char *input, size_t size) data = decompress ((const char *) &input[sizeof (struct MetaDataHeader)], size - sizeof (struct MetaDataHeader), dataSize); - if (data == NULL) + if (NULL == data) { GNUNET_break_op (0); return NULL; @@ -1110,9 +1087,9 @@ GNUNET_CONTAINER_meta_data_deserialize (const char *input, size_t size) memcpy (&ent, &cdata[i * sizeof (struct MetaDataEntry)], sizeof (struct MetaDataEntry)); format = (enum EXTRACTOR_MetaFormat) ntohl (ent.format); - if ((format != EXTRACTOR_METAFORMAT_UTF8) && - (format != EXTRACTOR_METAFORMAT_C_STRING) && - (format != EXTRACTOR_METAFORMAT_BINARY)) + if ((EXTRACTOR_METAFORMAT_UTF8 != format) && + (EXTRACTOR_METAFORMAT_C_STRING != format) && + (EXTRACTOR_METAFORMAT_BINARY != format)) { GNUNET_break_op (0); break; @@ -1127,10 +1104,10 @@ GNUNET_CONTAINER_meta_data_deserialize (const char *input, size_t size) } left -= dlen; meta_data = &mdata[left]; - if ((format == EXTRACTOR_METAFORMAT_UTF8) || - (format == EXTRACTOR_METAFORMAT_C_STRING)) + if ((EXTRACTOR_METAFORMAT_UTF8 == format) || + (EXTRACTOR_METAFORMAT_C_STRING == format)) { - if ((dlen == 0) || (mdata[left + dlen - 1] != '\0')) + if ((0 == dlen) || ('\0' != mdata[left + dlen - 1])) { GNUNET_break_op (0); break; @@ -1142,12 +1119,12 @@ GNUNET_CONTAINER_meta_data_deserialize (const char *input, size_t size) break; } left -= plen; - if ((plen > 0) && (mdata[left + plen - 1] != '\0')) + if ((plen > 0) && ('\0' != mdata[left + plen - 1])) { GNUNET_break_op (0); break; } - if (plen == 0) + if (0 == plen) plugin_name = NULL; else plugin_name = &mdata[left]; @@ -1158,12 +1135,12 @@ GNUNET_CONTAINER_meta_data_deserialize (const char *input, size_t size) break; } left -= mlen; - if ((mlen > 0) && (mdata[left + mlen - 1] != '\0')) + if ((mlen > 0) && ('\0' != mdata[left + mlen - 1])) { GNUNET_break_op (0); break; } - if (mlen == 0) + if (0 == mlen) mime_type = NULL; else mime_type = &mdata[left]; diff --git a/src/util/container_multihashmap.c b/src/util/container_multihashmap.c index 7e53a64..a23f967 100644 --- a/src/util/container_multihashmap.c +++ b/src/util/container_multihashmap.c @@ -1,6 +1,6 @@ /* This file is part of GNUnet. - (C) 2008 Christian Grothoff (and other contributing authors) + (C) 2008, 2012 Christian Grothoff (and other contributing authors) GNUnet is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published @@ -31,15 +31,34 @@ #define LOG(kind,...) GNUNET_log_from (kind, "util", __VA_ARGS__) /** - * An entry in the hash map. + * An entry in the hash map with the full key. */ -struct MapEntry +struct BigMapEntry { + /** + * Value of the entry. + */ + void *value; + + /** + * If there is a hash collision, we create a linked list. + */ + struct BigMapEntry *next; + /** * Key for the entry. */ - GNUNET_HashCode key; + struct GNUNET_HashCode key; + +}; + + +/** + * An entry in the hash map with just a pointer to the key. + */ +struct SmallMapEntry +{ /** * Value of the entry. @@ -49,10 +68,33 @@ struct MapEntry /** * If there is a hash collision, we create a linked list. */ - struct MapEntry *next; + struct SmallMapEntry *next; + + /** + * Key for the entry. + */ + const struct GNUNET_HashCode *key; }; + +/** + * Entry in the map. + */ +union MapEntry +{ + /** + * Variant used if map entries only contain a pointer to the key. + */ + struct SmallMapEntry *sme; + + /** + * Variant used if map entries contain the full key. + */ + struct BigMapEntry *bme; +}; + + /** * Internal representation of the hash map. */ @@ -62,7 +104,7 @@ struct GNUNET_CONTAINER_MultiHashMap /** * All of our buckets. */ - struct MapEntry **map; + union MapEntry *map; /** * Number of entries in the map. @@ -73,6 +115,12 @@ struct GNUNET_CONTAINER_MultiHashMap * Length of the "map" array. */ unsigned int map_length; + + /** + * GNUNET_NO if the map entries are of type 'struct BigMapEntry', + * GNUNET_YES if the map entries are of type 'struct SmallMapEntry'. + */ + int use_small_entries; }; @@ -80,18 +128,29 @@ struct GNUNET_CONTAINER_MultiHashMap * Create a multi hash map. * * @param len initial size (map will grow as needed) + * @param do_not_copy_keys GNUNET_NO is always safe and should be used by default; + * GNUNET_YES means that on 'put', the 'key' does not have + * to be copied as the destination of the pointer is + * guaranteed to be life as long as the value is stored in + * the hashmap. This can significantly reduce memory + * consumption, but of course is also a recipie for + * heap corruption if the assumption is not true. Only + * use this if (1) memory use is important in this case and + * (2) you have triple-checked that the invariant holds * @return NULL on error */ struct GNUNET_CONTAINER_MultiHashMap * -GNUNET_CONTAINER_multihashmap_create (unsigned int len) +GNUNET_CONTAINER_multihashmap_create (unsigned int len, + int do_not_copy_keys) { - struct GNUNET_CONTAINER_MultiHashMap *ret; + struct GNUNET_CONTAINER_MultiHashMap *map; GNUNET_assert (len > 0); - ret = GNUNET_malloc (sizeof (struct GNUNET_CONTAINER_MultiHashMap)); - ret->map = GNUNET_malloc (len * sizeof (struct MapEntry *)); - ret->map_length = len; - return ret; + map = GNUNET_malloc (sizeof (struct GNUNET_CONTAINER_MultiHashMap)); + map->map = GNUNET_malloc (len * sizeof (union MapEntry)); + map->map_length = len; + map->use_small_entries = do_not_copy_keys; + return map; } @@ -106,14 +165,36 @@ GNUNET_CONTAINER_multihashmap_destroy (struct GNUNET_CONTAINER_MultiHashMap *map) { unsigned int i; - struct MapEntry *e; + union MapEntry me; for (i = 0; i < map->map_length; i++) { - while (NULL != (e = map->map[i])) + me = map->map[i]; + if (map->use_small_entries) + { + struct SmallMapEntry *sme; + struct SmallMapEntry *nxt; + + nxt = me.sme; + while (NULL != (sme = nxt)) + { + nxt = sme->next; + GNUNET_free (sme); + } + me.sme = NULL; + } + else { - map->map[i] = e->next; - GNUNET_free (e); + struct BigMapEntry *bme; + struct BigMapEntry *nxt; + + nxt = me.bme; + while (NULL != (bme = nxt)) + { + nxt = bme->next; + GNUNET_free (bme); + } + me.bme = NULL; } } GNUNET_free (map->map); @@ -124,16 +205,16 @@ GNUNET_CONTAINER_multihashmap_destroy (struct GNUNET_CONTAINER_MultiHashMap /** * Compute the index of the bucket for the given key. * - * @param m hash map for which to compute the index + * @param map hash map for which to compute the index * @param key what key should the index be computed for - * @return offset into the "map" array of "m" + * @return offset into the "map" array of "map" */ static unsigned int -idx_of (const struct GNUNET_CONTAINER_MultiHashMap *m, - const GNUNET_HashCode * key) +idx_of (const struct GNUNET_CONTAINER_MultiHashMap *map, + const struct GNUNET_HashCode *key) { - GNUNET_assert (m != NULL); - return (*(unsigned int *) key) % m->map_length; + GNUNET_assert (map != NULL); + return (*(unsigned int *) key) % map->map_length; } @@ -163,16 +244,26 @@ GNUNET_CONTAINER_multihashmap_size (const struct GNUNET_CONTAINER_MultiHashMap */ void * GNUNET_CONTAINER_multihashmap_get (const struct GNUNET_CONTAINER_MultiHashMap - *map, const GNUNET_HashCode * key) + *map, const struct GNUNET_HashCode *key) { - struct MapEntry *e; + union MapEntry me; - e = map->map[idx_of (map, key)]; - while (e != NULL) + me = map->map[idx_of (map, key)]; + if (map->use_small_entries) { - if (0 == memcmp (key, &e->key, sizeof (GNUNET_HashCode))) - return e->value; - e = e->next; + struct SmallMapEntry *sme; + + for (sme = me.sme; NULL != sme; sme = sme->next) + if (0 == memcmp (key, sme->key, sizeof (struct GNUNET_HashCode))) + return sme->value; + } + else + { + struct BigMapEntry *bme; + + for (bme = me.bme; NULL != bme; bme = bme->next) + if (0 == memcmp (key, &bme->key, sizeof (struct GNUNET_HashCode))) + return bme->value; } return NULL; } @@ -195,25 +286,48 @@ GNUNET_CONTAINER_multihashmap_iterate (const struct { int count; unsigned int i; - struct MapEntry *e; - struct MapEntry *n; - GNUNET_HashCode kc; + union MapEntry me; + struct GNUNET_HashCode kc; count = 0; - GNUNET_assert (map != NULL); + GNUNET_assert (NULL != map); for (i = 0; i < map->map_length; i++) { - n = map->map[i]; - while (NULL != (e = n)) + me = map->map[i]; + if (map->use_small_entries) { - n = e->next; - if (NULL != it) + struct SmallMapEntry *sme; + struct SmallMapEntry *nxt; + + nxt = me.sme; + while (NULL != (sme = nxt)) { - kc = e->key; - if (GNUNET_OK != it (it_cls, &kc, e->value)) - return GNUNET_SYSERR; + nxt = sme->next; + if (NULL != it) + { + if (GNUNET_OK != it (it_cls, sme->key, sme->value)) + return GNUNET_SYSERR; + } + count++; + } + } + else + { + struct BigMapEntry *bme; + struct BigMapEntry *nxt; + + nxt = me.bme; + while (NULL != (bme = nxt)) + { + nxt = bme->next; + if (NULL != it) + { + kc = bme->key; + if (GNUNET_OK != it (it_cls, &kc, bme->value)) + return GNUNET_SYSERR; + } + count++; } - count++; } } return count; @@ -233,30 +347,57 @@ GNUNET_CONTAINER_multihashmap_iterate (const struct */ int GNUNET_CONTAINER_multihashmap_remove (struct GNUNET_CONTAINER_MultiHashMap *map, - const GNUNET_HashCode * key, void *value) + const struct GNUNET_HashCode *key, + void *value) { - struct MapEntry *e; - struct MapEntry *p; + union MapEntry me; unsigned int i; i = idx_of (map, key); - p = NULL; - e = map->map[i]; - while (e != NULL) + me = map->map[i]; + if (map->use_small_entries) + { + struct SmallMapEntry *sme; + struct SmallMapEntry *p; + + p = NULL; + for (sme = me.sme; NULL != sme; sme = sme->next) + { + if ((0 == memcmp (key, sme->key, sizeof (struct GNUNET_HashCode))) && + (value == sme->value)) + { + if (NULL == p) + map->map[i].sme = sme->next; + else + p->next = sme->next; + GNUNET_free (sme); + map->size--; + return GNUNET_YES; + } + p = sme; + } + } + else { - if ((0 == memcmp (key, &e->key, sizeof (GNUNET_HashCode))) && - (value == e->value)) + struct BigMapEntry *bme; + struct BigMapEntry *p; + + p = NULL; + for (bme = me.bme; NULL != bme; bme = bme->next) { - if (p == NULL) - map->map[i] = e->next; - else - p->next = e->next; - GNUNET_free (e); - map->size--; - return GNUNET_YES; + if ((0 == memcmp (key, &bme->key, sizeof (struct GNUNET_HashCode))) && + (value == bme->value)) + { + if (NULL == p) + map->map[i].bme = bme->next; + else + p->next = bme->next; + GNUNET_free (bme); + map->size--; + return GNUNET_YES; + } + p = bme; } - p = e; - e = e->next; } return GNUNET_NO; } @@ -272,37 +413,73 @@ GNUNET_CONTAINER_multihashmap_remove (struct GNUNET_CONTAINER_MultiHashMap *map, */ int GNUNET_CONTAINER_multihashmap_remove_all (struct GNUNET_CONTAINER_MultiHashMap - *map, const GNUNET_HashCode * key) + *map, const struct GNUNET_HashCode *key) { - struct MapEntry *e; - struct MapEntry *p; + union MapEntry me; unsigned int i; int ret; ret = 0; i = idx_of (map, key); - p = NULL; - e = map->map[i]; - while (e != NULL) - { - if (0 == memcmp (key, &e->key, sizeof (GNUNET_HashCode))) + me = map->map[i]; + if (map->use_small_entries) + { + struct SmallMapEntry *sme; + struct SmallMapEntry *p; + + p = NULL; + sme = me.sme; + while (NULL != sme) { - if (p == NULL) - map->map[i] = e->next; - else - p->next = e->next; - GNUNET_free (e); - map->size--; - if (p == NULL) - e = map->map[i]; + if (0 == memcmp (key, sme->key, sizeof (struct GNUNET_HashCode))) + { + if (NULL == p) + map->map[i].sme = sme->next; + else + p->next = sme->next; + GNUNET_free (sme); + map->size--; + if (NULL == p) + sme = map->map[i].sme; + else + sme = p->next; + ret++; + } else - e = p->next; - ret++; + { + p = sme; + sme = sme->next; + } } - else + } + else + { + struct BigMapEntry *bme; + struct BigMapEntry *p; + + p = NULL; + bme = me.bme; + while (NULL != bme) { - p = e; - e = e->next; + if (0 == memcmp (key, &bme->key, sizeof (struct GNUNET_HashCode))) + { + if (NULL == p) + map->map[i].bme = bme->next; + else + p->next = bme->next; + GNUNET_free (bme); + map->size--; + if (NULL == p) + bme = map->map[i].bme; + else + bme = p->next; + ret++; + } + else + { + p = bme; + bme = bme->next; + } } } return ret; @@ -321,16 +498,26 @@ GNUNET_CONTAINER_multihashmap_remove_all (struct GNUNET_CONTAINER_MultiHashMap int GNUNET_CONTAINER_multihashmap_contains (const struct GNUNET_CONTAINER_MultiHashMap *map, - const GNUNET_HashCode * key) + const struct GNUNET_HashCode *key) { - struct MapEntry *e; + union MapEntry me; - e = map->map[idx_of (map, key)]; - while (e != NULL) + me = map->map[idx_of (map, key)]; + if (map->use_small_entries) { - if (0 == memcmp (key, &e->key, sizeof (GNUNET_HashCode))) - return GNUNET_YES; - e = e->next; + struct SmallMapEntry *sme; + + for (sme = me.sme; NULL != sme; sme = sme->next) + if (0 == memcmp (key, sme->key, sizeof (struct GNUNET_HashCode))) + return GNUNET_YES; + } + else + { + struct BigMapEntry *bme; + + for (bme = me.bme; NULL != bme; bme = bme->next) + if (0 == memcmp (key, &bme->key, sizeof (struct GNUNET_HashCode))) + return GNUNET_YES; } return GNUNET_NO; } @@ -349,18 +536,29 @@ GNUNET_CONTAINER_multihashmap_contains (const struct int GNUNET_CONTAINER_multihashmap_contains_value (const struct GNUNET_CONTAINER_MultiHashMap - *map, const GNUNET_HashCode * key, + *map, const struct GNUNET_HashCode *key, const void *value) { - struct MapEntry *e; + union MapEntry me; - e = map->map[idx_of (map, key)]; - while (e != NULL) + me = map->map[idx_of (map, key)]; + if (map->use_small_entries) { - if ((0 == memcmp (key, &e->key, sizeof (GNUNET_HashCode))) && - (e->value == value)) - return GNUNET_YES; - e = e->next; + struct SmallMapEntry *sme; + + for (sme = me.sme; NULL != sme; sme = sme->next) + if ( (0 == memcmp (key, sme->key, sizeof (struct GNUNET_HashCode))) && + (sme->value == value) ) + return GNUNET_YES; + } + else + { + struct BigMapEntry *bme; + + for (bme = me.bme; NULL != bme; bme = bme->next) + if ( (0 == memcmp (key, &bme->key, sizeof (struct GNUNET_HashCode))) && + (bme->value == value) ) + return GNUNET_YES; } return GNUNET_NO; } @@ -374,9 +572,8 @@ GNUNET_CONTAINER_multihashmap_contains_value (const struct static void grow (struct GNUNET_CONTAINER_MultiHashMap *map) { - struct MapEntry **old_map; - struct MapEntry **new_map; - struct MapEntry *e; + union MapEntry *old_map; + union MapEntry *new_map; unsigned int old_len; unsigned int new_len; unsigned int idx; @@ -385,17 +582,34 @@ grow (struct GNUNET_CONTAINER_MultiHashMap *map) old_map = map->map; old_len = map->map_length; new_len = old_len * 2; - new_map = GNUNET_malloc (sizeof (struct MapEntry *) * new_len); + new_map = GNUNET_malloc (sizeof (union MapEntry) * new_len); map->map_length = new_len; map->map = new_map; for (i = 0; i < old_len; i++) { - while (NULL != (e = old_map[i])) + if (map->use_small_entries) + { + struct SmallMapEntry *sme; + + while (NULL != (sme = old_map[i].sme)) + { + old_map[i].sme = sme->next; + idx = idx_of (map, sme->key); + sme->next = new_map[idx].sme; + new_map[idx].sme = sme; + } + } + else { - old_map[i] = e->next; - idx = idx_of (map, &e->key); - e->next = new_map[idx]; - new_map[idx] = e; + struct BigMapEntry *bme; + + while (NULL != (bme = old_map[i].bme)) + { + old_map[i].bme = bme->next; + idx = idx_of (map, &bme->key); + bme->next = new_map[idx].bme; + new_map[idx].bme = bme; + } } } GNUNET_free (old_map); @@ -416,27 +630,43 @@ grow (struct GNUNET_CONTAINER_MultiHashMap *map) */ int GNUNET_CONTAINER_multihashmap_put (struct GNUNET_CONTAINER_MultiHashMap *map, - const GNUNET_HashCode * key, void *value, + const struct GNUNET_HashCode *key, + void *value, enum GNUNET_CONTAINER_MultiHashMapOption opt) { - struct MapEntry *e; + union MapEntry me; unsigned int i; i = idx_of (map, key); if ((opt != GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE) && (opt != GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_FAST)) { - e = map->map[i]; - while (e != NULL) + me = map->map[i]; + if (map->use_small_entries) { - if (0 == memcmp (key, &e->key, sizeof (GNUNET_HashCode))) - { - if (opt == GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY) - return GNUNET_SYSERR; - e->value = value; - return GNUNET_NO; - } - e = e->next; + struct SmallMapEntry *sme; + + for (sme = me.sme; NULL != sme; sme = sme->next) + if (0 == memcmp (key, sme->key, sizeof (struct GNUNET_HashCode))) + { + if (opt == GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY) + return GNUNET_SYSERR; + sme->value = value; + return GNUNET_NO; + } + } + else + { + struct BigMapEntry *bme; + + for (bme = me.bme; NULL != bme; bme = bme->next) + if (0 == memcmp (key, &bme->key, sizeof (struct GNUNET_HashCode))) + { + if (opt == GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY) + return GNUNET_SYSERR; + bme->value = value; + return GNUNET_NO; + } } } if (map->size / 3 >= map->map_length / 4) @@ -444,11 +674,26 @@ GNUNET_CONTAINER_multihashmap_put (struct GNUNET_CONTAINER_MultiHashMap *map, grow (map); i = idx_of (map, key); } - e = GNUNET_malloc (sizeof (struct MapEntry)); - e->key = *key; - e->value = value; - e->next = map->map[i]; - map->map[i] = e; + if (map->use_small_entries) + { + struct SmallMapEntry *sme; + + sme = GNUNET_malloc (sizeof (struct SmallMapEntry)); + sme->key = key; + sme->value = value; + sme->next = map->map[i].sme; + map->map[i].sme = sme; + } + else + { + struct BigMapEntry *bme; + + bme = GNUNET_malloc (sizeof (struct BigMapEntry)); + bme->key = *key; + bme->value = value; + bme->next = map->map[i].bme; + map->map[i].bme = bme; + } map->size++; return GNUNET_OK; } @@ -467,24 +712,46 @@ GNUNET_CONTAINER_multihashmap_put (struct GNUNET_CONTAINER_MultiHashMap *map, int GNUNET_CONTAINER_multihashmap_get_multiple (const struct GNUNET_CONTAINER_MultiHashMap *map, - const GNUNET_HashCode * key, + const struct GNUNET_HashCode *key, GNUNET_CONTAINER_HashMapIterator it, void *it_cls) { int count; - struct MapEntry *e; - struct MapEntry *n; + union MapEntry me; count = 0; - n = map->map[idx_of (map, key)]; - while (NULL != (e = n)) + me = map->map[idx_of (map, key)]; + if (map->use_small_entries) + { + struct SmallMapEntry *sme; + struct SmallMapEntry *nxt; + + nxt = me.sme; + while (NULL != (sme = nxt)) + { + nxt = sme->next; + if (0 != memcmp (key, sme->key, sizeof (struct GNUNET_HashCode))) + continue; + if ((it != NULL) && (GNUNET_OK != it (it_cls, key, sme->value))) + return GNUNET_SYSERR; + count++; + } + } + else { - n = e->next; - if (0 != memcmp (key, &e->key, sizeof (GNUNET_HashCode))) - continue; - if ((it != NULL) && (GNUNET_OK != it (it_cls, key, e->value))) - return GNUNET_SYSERR; - count++; + struct BigMapEntry *bme; + struct BigMapEntry *nxt; + + nxt = me.bme; + while (NULL != (bme = nxt)) + { + nxt = bme->next; + if (0 != memcmp (key, &bme->key, sizeof (struct GNUNET_HashCode))) + continue; + if ((it != NULL) && (GNUNET_OK != it (it_cls, key, bme->value))) + return GNUNET_SYSERR; + count++; + } } return count; } diff --git a/src/util/crypto_crc.c b/src/util/crypto_crc.c index 8bccf6b..ea50b63 100644 --- a/src/util/crypto_crc.c +++ b/src/util/crypto_crc.c @@ -27,7 +27,6 @@ * @brief implementation of CRC16 and CRC32 * @author Christian Grothoff */ - #include "platform.h" #include "gnunet_common.h" #include "gnunet_crypto_lib.h" @@ -51,7 +50,7 @@ static uLong crc_table[256]; /* * This routine writes each crc_table entry exactly once, - * with the ccorrect final value. Thus, it is safe to call + * with the correct final value. Thus, it is safe to call * even on a table that someone else is using concurrently. */ static void diff --git a/src/util/crypto_ecc.c b/src/util/crypto_ecc.c new file mode 100644 index 0000000..7f88c3e --- /dev/null +++ b/src/util/crypto_ecc.c @@ -0,0 +1,1082 @@ +/* + This file is part of GNUnet. + (C) 2001, 2002, 2003, 2004, 2005, 2006, 2009, 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 2, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @file util/crypto_ecc.c + * @brief public key cryptography (ECC) with libgcrypt + * @author Christian Grothoff + */ +#include "platform.h" +#include +#include "gnunet_common.h" +#include "gnunet_util_lib.h" + +#define EXTRA_CHECKS ALLOW_EXTRA_CHECKS || 1 + +#define CURVE "NIST P-521" + +#define LOG(kind,...) GNUNET_log_from (kind, "util", __VA_ARGS__) + +#define LOG_STRERROR(kind,syscall) GNUNET_log_from_strerror (kind, "util", syscall) + +#define LOG_STRERROR_FILE(kind,syscall,filename) GNUNET_log_from_strerror_file (kind, "util", syscall, filename) + +/** + * Log an error message at log-level 'level' that indicates + * a failure of the command 'cmd' with the message given + * by gcry_strerror(rc). + */ +#define LOG_GCRY(level, cmd, rc) do { LOG(level, _("`%s' failed at %s:%d with error: %s\n"), cmd, __FILE__, __LINE__, gcry_strerror(rc)); } while(0); + + +/** + * The private information of an ECC private key. + */ +struct GNUNET_CRYPTO_EccPrivateKey +{ + + /** + * Libgcrypt S-expression for the ECC key. + */ + gcry_sexp_t sexp; +}; + + +/** + * Free memory occupied by ECC key + * + * @param privatekey pointer to the memory to free + */ +void +GNUNET_CRYPTO_ecc_key_free (struct GNUNET_CRYPTO_EccPrivateKey *privatekey) +{ + gcry_sexp_release (privatekey->sexp); + GNUNET_free (privatekey); +} + + +/** + * Extract values from an S-expression. + * + * @param array where to store the result(s) + * @param sexp S-expression to parse + * @param topname top-level name in the S-expression that is of interest + * @param elems names of the elements to extract + * @return 0 on success + */ +static int +key_from_sexp (gcry_mpi_t * array, gcry_sexp_t sexp, const char *topname, + const char *elems) +{ + gcry_sexp_t list; + gcry_sexp_t l2; + const char *s; + unsigned int i; + unsigned int idx; + + list = gcry_sexp_find_token (sexp, topname, 0); + if (! list) + return 1; + l2 = gcry_sexp_cadr (list); + gcry_sexp_release (list); + list = l2; + if (! list) + return 2; + + idx = 0; + for (s = elems; *s; s++, idx++) + { + l2 = gcry_sexp_find_token (list, s, 1); + if (! l2) + { + for (i = 0; i < idx; i++) + { + gcry_free (array[i]); + array[i] = NULL; + } + gcry_sexp_release (list); + return 3; /* required parameter not found */ + } + array[idx] = gcry_sexp_nth_mpi (l2, 1, GCRYMPI_FMT_USG); + gcry_sexp_release (l2); + if (! array[idx]) + { + for (i = 0; i < idx; i++) + { + gcry_free (array[i]); + array[i] = NULL; + } + gcry_sexp_release (list); + return 4; /* required parameter is invalid */ + } + } + gcry_sexp_release (list); + return 0; +} + + +/** + * Extract the public key for the given private key. + * + * @param priv the private key + * @param pub where to write the public key + */ +void +GNUNET_CRYPTO_ecc_key_get_public (const struct GNUNET_CRYPTO_EccPrivateKey *priv, + struct GNUNET_CRYPTO_EccPublicKeyBinaryEncoded *pub) +{ + gcry_mpi_t skey; + size_t size; + int rc; + + memset (pub, 0, sizeof (struct GNUNET_CRYPTO_EccPublicKeyBinaryEncoded)); + rc = key_from_sexp (&skey, priv->sexp, "public-key", "q"); + if (rc) + rc = key_from_sexp (&skey, priv->sexp, "private-key", "q"); + if (rc) + rc = key_from_sexp (&skey, priv->sexp, "ecc", "q"); + GNUNET_assert (0 == rc); + pub->size = htons (sizeof (struct GNUNET_CRYPTO_EccPublicKeyBinaryEncoded)); + size = GNUNET_CRYPTO_ECC_MAX_PUBLIC_KEY_LENGTH; + GNUNET_assert (0 == + gcry_mpi_print (GCRYMPI_FMT_USG, pub->key, size, &size, + skey)); + pub->len = htons (size); + gcry_mpi_release (skey); +} + + +/** + * Convert a public key to a string. + * + * @param pub key to convert + * @return string representing 'pub' + */ +char * +GNUNET_CRYPTO_ecc_public_key_to_string (struct GNUNET_CRYPTO_EccPublicKeyBinaryEncoded *pub) +{ + char *pubkeybuf; + size_t keylen = (sizeof (struct GNUNET_CRYPTO_EccPublicKeyBinaryEncoded)) * 8; + char *end; + + if (keylen % 5 > 0) + keylen += 5 - keylen % 5; + keylen /= 5; + pubkeybuf = GNUNET_malloc (keylen + 1); + end = GNUNET_STRINGS_data_to_string ((unsigned char *) pub, + sizeof (struct GNUNET_CRYPTO_EccPublicKeyBinaryEncoded), + pubkeybuf, + keylen); + if (NULL == end) + { + GNUNET_free (pubkeybuf); + return NULL; + } + *end = '\0'; + return pubkeybuf; +} + + +/** + * Convert a string representing a public key to a public key. + * + * @param enc encoded public key + * @param enclen number of bytes in enc (without 0-terminator) + * @param pub where to store the public key + * @return GNUNET_OK on success + */ +int +GNUNET_CRYPTO_ecc_public_key_from_string (const char *enc, + size_t enclen, + struct GNUNET_CRYPTO_EccPublicKeyBinaryEncoded *pub) +{ + size_t keylen = (sizeof (struct GNUNET_CRYPTO_EccPublicKeyBinaryEncoded)) * 8; + + if (keylen % 5 > 0) + keylen += 5 - keylen % 5; + keylen /= 5; + if (enclen != keylen) + return GNUNET_SYSERR; + + if (GNUNET_OK != GNUNET_STRINGS_string_to_data (enc, enclen, + (unsigned char*) pub, + sizeof (struct GNUNET_CRYPTO_EccPublicKeyBinaryEncoded))) + return GNUNET_SYSERR; + if ( (ntohs (pub->size) != sizeof (struct GNUNET_CRYPTO_EccPublicKeyBinaryEncoded)) || + (ntohs (pub->len) > GNUNET_CRYPTO_ECC_SIGNATURE_DATA_ENCODING_LENGTH) ) + return GNUNET_SYSERR; + return GNUNET_OK; +} + + +/** + * Convert the given public key from the network format to the + * S-expression that can be used by libgcrypt. + * + * @param publicKey public key to decode + * @return NULL on error + */ +static gcry_sexp_t +decode_public_key (const struct GNUNET_CRYPTO_EccPublicKeyBinaryEncoded *publicKey) +{ + gcry_sexp_t result; + gcry_mpi_t q; + size_t size; + size_t erroff; + int rc; + + if (ntohs (publicKey->len) > GNUNET_CRYPTO_ECC_SIGNATURE_DATA_ENCODING_LENGTH) + { + GNUNET_break (0); + return NULL; + } + size = ntohs (publicKey->len); + if (0 != (rc = gcry_mpi_scan (&q, GCRYMPI_FMT_USG, publicKey->key, size, &size))) + { + LOG_GCRY (GNUNET_ERROR_TYPE_ERROR, "gcry_mpi_scan", rc); + return NULL; + } + + rc = gcry_sexp_build (&result, &erroff, + "(public-key(ecdsa(curve \"" CURVE "\")(q %m)))", + q); + gcry_mpi_release (q); + if (0 != rc) + { + LOG_GCRY (GNUNET_ERROR_TYPE_ERROR, "gcry_sexp_build", rc); /* erroff gives more info */ + return NULL; + } + // FIXME: is this key expected to pass pk_testkey? +#if 0 +#if EXTRA_CHECKS + if (0 != (rc = gcry_pk_testkey (result))) + { + LOG_GCRY (GNUNET_ERROR_TYPE_ERROR, "gcry_pk_testkey", rc); + gcry_sexp_release (result); + return NULL; + } +#endif +#endif + return result; +} + + +/** + * Encode the private key in a format suitable for + * storing it into a file. + * + * @param key key to encode + * @return encoding of the private key. + * The first 4 bytes give the size of the array, as usual. + */ +struct GNUNET_CRYPTO_EccPrivateKeyBinaryEncoded * +GNUNET_CRYPTO_ecc_encode_key (const struct GNUNET_CRYPTO_EccPrivateKey *key) +{ + struct GNUNET_CRYPTO_EccPrivateKeyBinaryEncoded *retval; + char buf[65536]; + uint16_t be; + size_t size; + +#if EXTRA_CHECKS + if (0 != gcry_pk_testkey (key->sexp)) + { + GNUNET_break (0); + return NULL; + } +#endif + size = gcry_sexp_sprint (key->sexp, + GCRYSEXP_FMT_DEFAULT, + &buf[2], sizeof (buf) - sizeof (uint16_t)); + if (0 == size) + { + GNUNET_break (0); + return NULL; + } + GNUNET_assert (size < 65536 - sizeof (uint16_t)); + be = htons ((uint16_t) size + (sizeof (be))); + memcpy (buf, &be, sizeof (be)); + size += sizeof (be); + retval = GNUNET_malloc (size); + memcpy (retval, buf, size); + return retval; +} + + +/** + * Decode the private key from the file-format back + * to the "normal", internal format. + * + * @param buf the buffer where the private key data is stored + * @param len the length of the data in 'buffer' + * @return NULL on error + */ +struct GNUNET_CRYPTO_EccPrivateKey * +GNUNET_CRYPTO_ecc_decode_key (const char *buf, + size_t len) +{ + struct GNUNET_CRYPTO_EccPrivateKey *ret; + uint16_t be; + gcry_sexp_t sexp; + int rc; + size_t erroff; + + if (len < sizeof (uint16_t)) + return NULL; + memcpy (&be, buf, sizeof (be)); + if (len != ntohs (be)) + return NULL; + if (0 != (rc = gcry_sexp_sscan (&sexp, + &erroff, + &buf[2], + len - sizeof (uint16_t)))) + { + LOG_GCRY (GNUNET_ERROR_TYPE_ERROR, "gcry_sexp_scan", rc); + return NULL; + } + if (0 != (rc = gcry_pk_testkey (sexp))) + { + LOG_GCRY (GNUNET_ERROR_TYPE_ERROR, "gcry_pk_testkey", rc); + return NULL; + } + ret = GNUNET_malloc (sizeof (struct GNUNET_CRYPTO_EccPrivateKey)); + ret->sexp = sexp; + return ret; +} + + +/** + * Create a new private key. Caller must free return value. + * + * @return fresh private key + */ +struct GNUNET_CRYPTO_EccPrivateKey * +GNUNET_CRYPTO_ecc_key_create () +{ + struct GNUNET_CRYPTO_EccPrivateKey *ret; + gcry_sexp_t s_key; + gcry_sexp_t s_keyparam; + int rc; + + if (0 != (rc = gcry_sexp_build (&s_keyparam, NULL, + "(genkey(ecdsa(curve \"" CURVE "\")))"))) + { + LOG_GCRY (GNUNET_ERROR_TYPE_ERROR, "gcry_sexp_build", rc); + return NULL; + } + if (0 != (rc = gcry_pk_genkey (&s_key, s_keyparam))) + { + LOG_GCRY (GNUNET_ERROR_TYPE_ERROR, "gcry_pk_genkey", rc); + gcry_sexp_release (s_keyparam); + return NULL; + } + gcry_sexp_release (s_keyparam); +#if EXTRA_CHECKS + if (0 != (rc = gcry_pk_testkey (s_key))) + { + LOG_GCRY (GNUNET_ERROR_TYPE_ERROR, "gcry_pk_testkey", rc); + gcry_sexp_release (s_key); + return NULL; + } +#endif + ret = GNUNET_malloc (sizeof (struct GNUNET_CRYPTO_EccPrivateKey)); + ret->sexp = s_key; + return ret; +} + + +/** + * Try to read the private key from the given file. + * + * @param filename file to read the key from + * @return NULL on error + */ +static struct GNUNET_CRYPTO_EccPrivateKey * +try_read_key (const char *filename) +{ + struct GNUNET_CRYPTO_EccPrivateKey *ret; + struct GNUNET_DISK_FileHandle *fd; + OFF_T fs; + + if (GNUNET_YES != GNUNET_DISK_file_test (filename)) + return NULL; + + /* key file exists already, read it! */ + if (NULL == (fd = GNUNET_DISK_file_open (filename, GNUNET_DISK_OPEN_READ, + GNUNET_DISK_PERM_NONE))) + { + LOG_STRERROR_FILE (GNUNET_ERROR_TYPE_ERROR, "open", filename); + return NULL; + } + if (GNUNET_OK != (GNUNET_DISK_file_handle_size (fd, &fs))) + { + LOG_STRERROR_FILE (GNUNET_ERROR_TYPE_ERROR, "stat", filename); + (void) GNUNET_DISK_file_close (fd); + return NULL; + } + if (0 == fs) + { + GNUNET_break (GNUNET_OK == GNUNET_DISK_file_close (fd)); + return NULL; + } + if (fs > UINT16_MAX) + { + LOG (GNUNET_ERROR_TYPE_ERROR, + _("File `%s' does not contain a valid private key (too long, %llu bytes). Deleting it.\n"), + filename, + (unsigned long long) fs); + GNUNET_break (GNUNET_OK == GNUNET_DISK_file_close (fd)); + if (0 != UNLINK (filename)) + LOG_STRERROR_FILE (GNUNET_ERROR_TYPE_WARNING, "unlink", filename); + return NULL; + } + { + char enc[fs]; + + GNUNET_break (fs == GNUNET_DISK_file_read (fd, enc, fs)); + if (NULL == (ret = GNUNET_CRYPTO_ecc_decode_key ((char *) enc, fs))) + { + LOG (GNUNET_ERROR_TYPE_ERROR, + _("File `%s' does not contain a valid private key (failed decode, %llu bytes). Deleting it.\n"), + filename, + (unsigned long long) fs); + GNUNET_break (GNUNET_OK == GNUNET_DISK_file_close (fd)); + if (0 != UNLINK (filename)) + LOG_STRERROR_FILE (GNUNET_ERROR_TYPE_WARNING, "unlink", filename); + return NULL; + } + } + GNUNET_break (GNUNET_OK == GNUNET_DISK_file_close (fd)); + return ret; +} + + +/** + * Wait for a short time (we're trying to lock a file or want + * to give another process a shot at finishing a disk write, etc.). + * Sleeps for 100ms (as that should be long enough for virtually all + * modern systems to context switch and allow another process to do + * some 'real' work). + */ +static void +short_wait () +{ + struct GNUNET_TIME_Relative timeout; + + timeout = GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MILLISECONDS, 100); + (void) GNUNET_NETWORK_socket_select (NULL, NULL, NULL, timeout); +} + + +/** + * Create a new private key by reading it from a file. If the + * files does not exist, create a new key and write it to the + * file. Caller must free return value. Note that this function + * can not guarantee that another process might not be trying + * the same operation on the same file at the same time. + * If the contents of the file + * are invalid the old file is deleted and a fresh key is + * created. + * + * @return new private key, NULL on error (for example, + * permission denied) + */ +struct GNUNET_CRYPTO_EccPrivateKey * +GNUNET_CRYPTO_ecc_key_create_from_file (const char *filename) +{ + struct GNUNET_CRYPTO_EccPrivateKey *ret; + struct GNUNET_CRYPTO_EccPrivateKeyBinaryEncoded *enc; + uint16_t len; + struct GNUNET_DISK_FileHandle *fd; + unsigned int cnt; + int ec; + uint64_t fs; + struct GNUNET_CRYPTO_EccPublicKeyBinaryEncoded pub; + struct GNUNET_PeerIdentity pid; + + if (GNUNET_SYSERR == GNUNET_DISK_directory_create_for_file (filename)) + return NULL; + while (GNUNET_YES != GNUNET_DISK_file_test (filename)) + { + fd = GNUNET_DISK_file_open (filename, + GNUNET_DISK_OPEN_WRITE | GNUNET_DISK_OPEN_CREATE + | GNUNET_DISK_OPEN_FAILIFEXISTS, + GNUNET_DISK_PERM_USER_READ | + GNUNET_DISK_PERM_USER_WRITE); + if (NULL == fd) + { + if (errno == EEXIST) + { + if (GNUNET_YES != GNUNET_DISK_file_test (filename)) + { + /* must exist but not be accessible, fail for good! */ + if (0 != ACCESS (filename, R_OK)) + LOG_STRERROR_FILE (GNUNET_ERROR_TYPE_ERROR, "access", filename); + else + GNUNET_break (0); /* what is going on!? */ + return NULL; + } + continue; + } + LOG_STRERROR_FILE (GNUNET_ERROR_TYPE_ERROR, "open", filename); + return NULL; + } + cnt = 0; + + while (GNUNET_YES != + GNUNET_DISK_file_lock (fd, 0, + sizeof (struct GNUNET_CRYPTO_EccPrivateKeyBinaryEncoded), + GNUNET_YES)) + { + short_wait (); + if (0 == ++cnt % 10) + { + ec = errno; + LOG (GNUNET_ERROR_TYPE_ERROR, + _("Could not acquire lock on file `%s': %s...\n"), filename, + STRERROR (ec)); + } + } + LOG (GNUNET_ERROR_TYPE_INFO, + _("Creating a new private key. This may take a while.\n")); + ret = GNUNET_CRYPTO_ecc_key_create (); + GNUNET_assert (ret != NULL); + enc = GNUNET_CRYPTO_ecc_encode_key (ret); + GNUNET_assert (enc != NULL); + GNUNET_assert (ntohs (enc->size) == + GNUNET_DISK_file_write (fd, enc, ntohs (enc->size))); + GNUNET_free (enc); + + GNUNET_DISK_file_sync (fd); + if (GNUNET_YES != + GNUNET_DISK_file_unlock (fd, 0, + sizeof (struct GNUNET_CRYPTO_EccPrivateKeyBinaryEncoded))) + LOG_STRERROR_FILE (GNUNET_ERROR_TYPE_WARNING, "fcntl", filename); + GNUNET_assert (GNUNET_YES == GNUNET_DISK_file_close (fd)); + GNUNET_CRYPTO_ecc_key_get_public (ret, &pub); + GNUNET_CRYPTO_hash (&pub, sizeof (pub), &pid.hashPubKey); + return ret; + } + /* key file exists already, read it! */ + fd = GNUNET_DISK_file_open (filename, GNUNET_DISK_OPEN_READ, + GNUNET_DISK_PERM_NONE); + if (NULL == fd) + { + LOG_STRERROR_FILE (GNUNET_ERROR_TYPE_ERROR, "open", filename); + return NULL; + } + cnt = 0; + while (1) + { + if (GNUNET_YES != + GNUNET_DISK_file_lock (fd, 0, + sizeof (struct GNUNET_CRYPTO_EccPrivateKeyBinaryEncoded), + GNUNET_NO)) + { + if (0 == ++cnt % 60) + { + ec = errno; + LOG (GNUNET_ERROR_TYPE_ERROR, + _("Could not acquire lock on file `%s': %s...\n"), filename, + STRERROR (ec)); + LOG (GNUNET_ERROR_TYPE_ERROR, + _ + ("This may be ok if someone is currently generating a private key.\n")); + } + short_wait (); + continue; + } + if (GNUNET_YES != GNUNET_DISK_file_test (filename)) + { + /* eh, what!? File we opened is now gone!? */ + LOG_STRERROR_FILE (GNUNET_ERROR_TYPE_WARNING, "stat", filename); + if (GNUNET_YES != + GNUNET_DISK_file_unlock (fd, 0, + sizeof (struct GNUNET_CRYPTO_EccPrivateKeyBinaryEncoded))) + LOG_STRERROR_FILE (GNUNET_ERROR_TYPE_WARNING, "fcntl", filename); + GNUNET_assert (GNUNET_OK == GNUNET_DISK_file_close (fd)); + + return NULL; + } + if (GNUNET_OK != GNUNET_DISK_file_size (filename, &fs, GNUNET_YES, GNUNET_YES)) + fs = 0; + if (fs < sizeof (struct GNUNET_CRYPTO_EccPrivateKeyBinaryEncoded)) + { + /* maybe we got the read lock before the key generating + * process had a chance to get the write lock; give it up! */ + if (GNUNET_YES != + GNUNET_DISK_file_unlock (fd, 0, + sizeof (struct GNUNET_CRYPTO_EccPrivateKeyBinaryEncoded))) + LOG_STRERROR_FILE (GNUNET_ERROR_TYPE_WARNING, "fcntl", filename); + if (0 == ++cnt % 10) + { + LOG (GNUNET_ERROR_TYPE_ERROR, + _ + ("When trying to read key file `%s' I found %u bytes but I need at least %u.\n"), + filename, (unsigned int) fs, + (unsigned int) sizeof (struct GNUNET_CRYPTO_EccPrivateKeyBinaryEncoded)); + LOG (GNUNET_ERROR_TYPE_ERROR, + _ + ("This may be ok if someone is currently generating a key.\n")); + } + short_wait (); /* wait a bit longer! */ + continue; + } + break; + } + enc = GNUNET_malloc (fs); + GNUNET_assert (fs == GNUNET_DISK_file_read (fd, enc, fs)); + len = ntohs (enc->size); + ret = NULL; + if ((len != fs) || + (NULL == (ret = GNUNET_CRYPTO_ecc_decode_key ((char *) enc, len)))) + { + LOG (GNUNET_ERROR_TYPE_ERROR, + _("File `%s' does not contain a valid private key. Deleting it.\n"), + filename); + if (0 != UNLINK (filename)) + { + LOG_STRERROR_FILE (GNUNET_ERROR_TYPE_WARNING, "unlink", filename); + } + } + GNUNET_free (enc); + if (GNUNET_YES != + GNUNET_DISK_file_unlock (fd, 0, + sizeof (struct GNUNET_CRYPTO_EccPrivateKeyBinaryEncoded))) + LOG_STRERROR_FILE (GNUNET_ERROR_TYPE_WARNING, "fcntl", filename); + GNUNET_assert (GNUNET_YES == GNUNET_DISK_file_close (fd)); + if (ret != NULL) + { + GNUNET_CRYPTO_ecc_key_get_public (ret, &pub); + GNUNET_CRYPTO_hash (&pub, sizeof (pub), &pid.hashPubKey); + } + return ret; +} + + +/** + * Handle to cancel private key generation and state for the + * key generation operation. + */ +struct GNUNET_CRYPTO_EccKeyGenerationContext +{ + + /** + * Continuation to call upon completion. + */ + GNUNET_CRYPTO_EccKeyCallback cont; + + /** + * Closure for 'cont'. + */ + void *cont_cls; + + /** + * Name of the file. + */ + char *filename; + + /** + * Handle to the helper process which does the key generation. + */ + struct GNUNET_OS_Process *gnunet_ecc; + + /** + * Handle to 'stdout' of gnunet-ecc. We 'read' on stdout to detect + * process termination (instead of messing with SIGCHLD). + */ + struct GNUNET_DISK_PipeHandle *gnunet_ecc_out; + + /** + * Location where we store the private key if it already existed. + * (if this is used, 'filename', 'gnunet_ecc' and 'gnunet_ecc_out' will + * not be used). + */ + struct GNUNET_CRYPTO_EccPrivateKey *pk; + + /** + * Task reading from 'gnunet_ecc_out' to wait for process termination. + */ + GNUNET_SCHEDULER_TaskIdentifier read_task; + +}; + + +/** + * Abort ECC key generation. + * + * @param gc key generation context to abort + */ +void +GNUNET_CRYPTO_ecc_key_create_stop (struct GNUNET_CRYPTO_EccKeyGenerationContext *gc) +{ + if (GNUNET_SCHEDULER_NO_TASK != gc->read_task) + { + GNUNET_SCHEDULER_cancel (gc->read_task); + gc->read_task = GNUNET_SCHEDULER_NO_TASK; + } + if (NULL != gc->gnunet_ecc) + { + (void) GNUNET_OS_process_kill (gc->gnunet_ecc, SIGKILL); + GNUNET_break (GNUNET_OK == + GNUNET_OS_process_wait (gc->gnunet_ecc)); + GNUNET_OS_process_destroy (gc->gnunet_ecc); + GNUNET_DISK_pipe_close (gc->gnunet_ecc_out); + } + + if (NULL != gc->filename) + { + if (0 != UNLINK (gc->filename)) + GNUNET_log_strerror_file (GNUNET_ERROR_TYPE_WARNING, "unlink", gc->filename); + GNUNET_free (gc->filename); + } + if (NULL != gc->pk) + GNUNET_CRYPTO_ecc_key_free (gc->pk); + GNUNET_free (gc); +} + + +/** + * Task called upon shutdown or process termination of 'gnunet-ecc' during + * ECC key generation. Check where we are and perform the appropriate + * action. + * + * @param cls the 'struct GNUNET_CRYPTO_EccKeyGenerationContext' + * @param tc scheduler context + */ +static void +check_key_generation_completion (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct GNUNET_CRYPTO_EccKeyGenerationContext *gc = cls; + struct GNUNET_CRYPTO_EccPrivateKey *pk; + + gc->read_task = GNUNET_SCHEDULER_NO_TASK; + if (0 != (tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN)) + { + gc->cont (gc->cont_cls, NULL, _("interrupted by shutdown")); + GNUNET_CRYPTO_ecc_key_create_stop (gc); + return; + } + GNUNET_assert (GNUNET_OK == + GNUNET_OS_process_wait (gc->gnunet_ecc)); + GNUNET_OS_process_destroy (gc->gnunet_ecc); + gc->gnunet_ecc = NULL; + if (NULL == (pk = try_read_key (gc->filename))) + { + GNUNET_break (0); + gc->cont (gc->cont_cls, NULL, _("gnunet-ecc failed")); + GNUNET_CRYPTO_ecc_key_create_stop (gc); + return; + } + gc->cont (gc->cont_cls, pk, NULL); + GNUNET_DISK_pipe_close (gc->gnunet_ecc_out); + GNUNET_free (gc->filename); + GNUNET_free (gc); +} + + +/** + * Return the private ECC key which already existed on disk + * (asynchronously) to the caller. + * + * @param cls the 'struct GNUNET_CRYPTO_EccKeyGenerationContext' + * @param tc scheduler context (unused) + */ +static void +async_return_key (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct GNUNET_CRYPTO_EccKeyGenerationContext *gc = cls; + + gc->cont (gc->cont_cls, + gc->pk, + NULL); + GNUNET_free (gc); +} + + +/** + * Create a new private key by reading it from a file. If the files + * does not exist, create a new key and write it to the file. If the + * contents of the file are invalid the old file is deleted and a + * fresh key is created. + * + * @param filename name of file to use for storage + * @param cont function to call when done (or on errors) + * @param cont_cls closure for 'cont' + * @return handle to abort operation, NULL on fatal errors (cont will not be called if NULL is returned) + */ +struct GNUNET_CRYPTO_EccKeyGenerationContext * +GNUNET_CRYPTO_ecc_key_create_start (const char *filename, + GNUNET_CRYPTO_EccKeyCallback cont, + void *cont_cls) +{ + struct GNUNET_CRYPTO_EccKeyGenerationContext *gc; + struct GNUNET_CRYPTO_EccPrivateKey *pk; + const char *weak_random; + + if (NULL != (pk = try_read_key (filename))) + { + /* quick happy ending: key already exists! */ + gc = GNUNET_malloc (sizeof (struct GNUNET_CRYPTO_EccKeyGenerationContext)); + gc->pk = pk; + gc->cont = cont; + gc->cont_cls = cont_cls; + gc->read_task = GNUNET_SCHEDULER_add_now (&async_return_key, + gc); + return gc; + } + gc = GNUNET_malloc (sizeof (struct GNUNET_CRYPTO_EccKeyGenerationContext)); + gc->filename = GNUNET_strdup (filename); + gc->cont = cont; + gc->cont_cls = cont_cls; + gc->gnunet_ecc_out = GNUNET_DISK_pipe (GNUNET_NO, + GNUNET_NO, + GNUNET_NO, + GNUNET_YES); + if (NULL == gc->gnunet_ecc_out) + { + GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "pipe"); + GNUNET_free (gc->filename); + GNUNET_free (gc); + return NULL; + } + weak_random = NULL; + if (GNUNET_YES == + GNUNET_CRYPTO_random_is_weak ()) + weak_random = "-w"; + gc->gnunet_ecc = GNUNET_OS_start_process (GNUNET_NO, + GNUNET_OS_INHERIT_STD_ERR, + NULL, + gc->gnunet_ecc_out, + "gnunet-ecc", + "gnunet-ecc", + gc->filename, + weak_random, + NULL); + if (NULL == gc->gnunet_ecc) + { + GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "fork"); + GNUNET_DISK_pipe_close (gc->gnunet_ecc_out); + GNUNET_free (gc->filename); + GNUNET_free (gc); + return NULL; + } + GNUNET_assert (GNUNET_OK == + GNUNET_DISK_pipe_close_end (gc->gnunet_ecc_out, + GNUNET_DISK_PIPE_END_WRITE)); + gc->read_task = GNUNET_SCHEDULER_add_read_file (GNUNET_TIME_UNIT_FOREVER_REL, + GNUNET_DISK_pipe_handle (gc->gnunet_ecc_out, + GNUNET_DISK_PIPE_END_READ), + &check_key_generation_completion, + gc); + return gc; +} + + +/** + * Setup a key file for a peer given the name of the + * configuration file (!). This function is used so that + * at a later point code can be certain that reading a + * key is fast (for example in time-dependent testcases). + * + * @param cfg_name name of the configuration file to use + */ +void +GNUNET_CRYPTO_ecc_setup_key (const char *cfg_name) +{ + struct GNUNET_CONFIGURATION_Handle *cfg; + struct GNUNET_CRYPTO_EccPrivateKey *pk; + char *fn; + + cfg = GNUNET_CONFIGURATION_create (); + (void) GNUNET_CONFIGURATION_load (cfg, cfg_name); + if (GNUNET_OK == + GNUNET_CONFIGURATION_get_value_filename (cfg, "PEER", "PRIVATE_KEY", &fn)) + { + pk = GNUNET_CRYPTO_ecc_key_create_from_file (fn); + if (NULL != pk) + GNUNET_CRYPTO_ecc_key_free (pk); + GNUNET_free (fn); + } + GNUNET_CONFIGURATION_destroy (cfg); +} + + +/** + * Convert the data specified in the given purpose argument to an + * S-expression suitable for signature operations. + * + * @param purpose data to convert + * @return converted s-expression + */ +static gcry_sexp_t +data_to_pkcs1 (const struct GNUNET_CRYPTO_EccSignaturePurpose *purpose) +{ + struct GNUNET_CRYPTO_ShortHashCode hc; + size_t bufSize; + gcry_sexp_t data; + + GNUNET_CRYPTO_short_hash (purpose, ntohl (purpose->size), &hc); +#define FORMATSTRING "(4:data(5:flags3:raw)(5:value32:01234567890123456789012345678901))" +#define FORMATSTRING2 "(4:data(4:hash6:sha25632:01234567890123456789012345678901))" + bufSize = strlen (FORMATSTRING) + 1; + { + char buff[bufSize]; + + memcpy (buff, FORMATSTRING, bufSize); + memcpy (&buff + [bufSize - + strlen + ("01234567890123456789012345678901))") + - 1], &hc, sizeof (struct GNUNET_CRYPTO_ShortHashCode)); + GNUNET_assert (0 == gcry_sexp_new (&data, buff, bufSize, 0)); + } +#undef FORMATSTRING + return data; +} + + +/** + * Sign a given block. + * + * @param key private key to use for the signing + * @param purpose what to sign (size, purpose) + * @param sig where to write the signature + * @return GNUNET_SYSERR on error, GNUNET_OK on success + */ +int +GNUNET_CRYPTO_ecc_sign (const struct GNUNET_CRYPTO_EccPrivateKey *key, + const struct GNUNET_CRYPTO_EccSignaturePurpose *purpose, + struct GNUNET_CRYPTO_EccSignature *sig) +{ + gcry_sexp_t result; + gcry_sexp_t data; + size_t ssize; + int rc; + + data = data_to_pkcs1 (purpose); + if (0 != (rc = gcry_pk_sign (&result, data, key->sexp))) + { + LOG (GNUNET_ERROR_TYPE_WARNING, + _("ECC signing failed at %s:%d: %s\n"), __FILE__, + __LINE__, gcry_strerror (rc)); + } + gcry_sexp_release (data); + ssize = gcry_sexp_sprint (result, + GCRYSEXP_FMT_DEFAULT, + sig->sexpr, + GNUNET_CRYPTO_ECC_SIGNATURE_DATA_ENCODING_LENGTH); + if (0 == ssize) + { + GNUNET_break (0); + return GNUNET_SYSERR; + } + sig->size = htons ((uint16_t) (ssize + sizeof (uint16_t))); + /* padd with zeros */ + memset (&sig->sexpr[ssize], 0, GNUNET_CRYPTO_ECC_SIGNATURE_DATA_ENCODING_LENGTH - ssize); + gcry_sexp_release (result); + return GNUNET_OK; +} + + +/** + * Verify signature. + * + * @param purpose what is the purpose that the signature should have? + * @param validate block to validate (size, purpose, data) + * @param sig signature that is being validated + * @param publicKey public key of the signer + * @returns GNUNET_OK if ok, GNUNET_SYSERR if invalid + */ +int +GNUNET_CRYPTO_ecc_verify (uint32_t purpose, + const struct GNUNET_CRYPTO_EccSignaturePurpose + *validate, + const struct GNUNET_CRYPTO_EccSignature *sig, + const struct GNUNET_CRYPTO_EccPublicKeyBinaryEncoded + *publicKey) +{ + gcry_sexp_t data; + gcry_sexp_t sigdata; + size_t size; + gcry_sexp_t psexp; + size_t erroff; + int rc; + + if (purpose != ntohl (validate->purpose)) + return GNUNET_SYSERR; /* purpose mismatch */ + size = ntohs (sig->size); + if ( (size < sizeof (uint16_t)) || + (size > GNUNET_CRYPTO_ECC_SIGNATURE_DATA_ENCODING_LENGTH - sizeof (uint16_t)) ) + return GNUNET_SYSERR; /* size out of range */ + data = data_to_pkcs1 (validate); + GNUNET_assert (0 == + gcry_sexp_sscan (&sigdata, &erroff, + sig->sexpr, size - sizeof (uint16_t))); + if (! (psexp = decode_public_key (publicKey))) + { + gcry_sexp_release (data); + gcry_sexp_release (sigdata); + return GNUNET_SYSERR; + } + rc = gcry_pk_verify (sigdata, data, psexp); + gcry_sexp_release (psexp); + gcry_sexp_release (data); + gcry_sexp_release (sigdata); + if (0 != rc) + { + LOG (GNUNET_ERROR_TYPE_WARNING, + _("ECC signature verification failed at %s:%d: %s\n"), __FILE__, + __LINE__, gcry_strerror (rc)); + return GNUNET_SYSERR; + } + return GNUNET_OK; +} + + +/** + * Derive key material from a public and a private ECC key. + * + * @param key private key to use for the ECDH (x) + * @param pub public key to use for the ECDY (yG) + * @param key_material where to write the key material (xyG) + * @return GNUNET_SYSERR on error, GNUNET_OK on success + */ +int +GNUNET_CRYPTO_ecc_ecdh (const struct GNUNET_CRYPTO_EccPrivateKey *key, + const struct GNUNET_CRYPTO_EccPublicKeyBinaryEncoded *pub, + struct GNUNET_HashCode *key_material) +{ + gcry_sexp_t psexp; + + if (! (psexp = decode_public_key (pub))) + return GNUNET_SYSERR; + + + gcry_sexp_release (psexp); + GNUNET_break (0); // not implemented + /* FIXME: this totally breaks security ... */ + memset (key_material, 42, sizeof (struct GNUNET_HashCode)); + return GNUNET_OK; +} + + +/* end of crypto_ecc.c */ diff --git a/src/util/crypto_hash.c b/src/util/crypto_hash.c index 4d957c0..04225b3 100644 --- a/src/util/crypto_hash.c +++ b/src/util/crypto_hash.c @@ -49,7 +49,7 @@ * @param ret pointer to where to write the hashcode */ void -GNUNET_CRYPTO_hash (const void *block, size_t size, GNUNET_HashCode * ret) +GNUNET_CRYPTO_hash (const void *block, size_t size, struct GNUNET_HashCode * ret) { gcry_md_hash_buffer (GCRY_MD_SHA512, ret, block, size); } @@ -140,7 +140,7 @@ struct GNUNET_CRYPTO_FileHashContext */ static void file_hash_finish (struct GNUNET_CRYPTO_FileHashContext *fhc, - const GNUNET_HashCode * res) + const struct GNUNET_HashCode * res) { fhc->callback (fhc->callback_cls, res); GNUNET_free (fhc->filename); @@ -161,7 +161,7 @@ static void file_hash_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { struct GNUNET_CRYPTO_FileHashContext *fhc = cls; - GNUNET_HashCode *res; + struct GNUNET_HashCode *res; size_t delta; fhc->task = GNUNET_SCHEDULER_NO_TASK; @@ -179,7 +179,7 @@ file_hash_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) fhc->offset += delta; if (fhc->offset == fhc->fsize) { - res = (GNUNET_HashCode *) gcry_md_read (fhc->md, GCRY_MD_SHA512); + res = (struct GNUNET_HashCode *) gcry_md_read (fhc->md, GCRY_MD_SHA512); file_hash_finish (fhc, res); return; } @@ -272,7 +272,7 @@ GNUNET_CRYPTO_hash_file_cancel (struct GNUNET_CRYPTO_FileHashContext *fhc) * safely cast to char*, a '\\0' termination is set). */ void -GNUNET_CRYPTO_hash_to_enc (const GNUNET_HashCode * block, +GNUNET_CRYPTO_hash_to_enc (const struct GNUNET_HashCode * block, struct GNUNET_CRYPTO_HashAsciiEncoded *result) { char *np; @@ -296,7 +296,7 @@ GNUNET_CRYPTO_hash_to_enc (const GNUNET_HashCode * block, */ int GNUNET_CRYPTO_hash_from_string2 (const char *enc, size_t enclen, - GNUNET_HashCode * result) + struct GNUNET_HashCode * result) { char upper_enc[enclen]; char* up_ptr = upper_enc; @@ -321,8 +321,8 @@ GNUNET_CRYPTO_hash_from_string2 (const char *enc, size_t enclen, * hashcode proximity. */ unsigned int -GNUNET_CRYPTO_hash_distance_u32 (const GNUNET_HashCode * a, - const GNUNET_HashCode * b) +GNUNET_CRYPTO_hash_distance_u32 (const struct GNUNET_HashCode * a, + const struct GNUNET_HashCode * b) { unsigned int x1 = (a->bits[1] - b->bits[1]) >> 16; unsigned int x2 = (b->bits[1] - a->bits[1]) >> 16; @@ -339,11 +339,11 @@ GNUNET_CRYPTO_hash_distance_u32 (const GNUNET_HashCode * a, */ void GNUNET_CRYPTO_hash_create_random (enum GNUNET_CRYPTO_Quality mode, - GNUNET_HashCode * result) + struct GNUNET_HashCode * result) { int i; - for (i = (sizeof (GNUNET_HashCode) / sizeof (uint32_t)) - 1; i >= 0; i--) + for (i = (sizeof (struct GNUNET_HashCode) / sizeof (uint32_t)) - 1; i >= 0; i--) result->bits[i] = GNUNET_CRYPTO_random_u32 (mode, UINT32_MAX); } @@ -356,13 +356,13 @@ GNUNET_CRYPTO_hash_create_random (enum GNUNET_CRYPTO_Quality mode, * @param result set to b - a */ void -GNUNET_CRYPTO_hash_difference (const GNUNET_HashCode * a, - const GNUNET_HashCode * b, - GNUNET_HashCode * result) +GNUNET_CRYPTO_hash_difference (const struct GNUNET_HashCode * a, + const struct GNUNET_HashCode * b, + struct GNUNET_HashCode * result) { int i; - for (i = (sizeof (GNUNET_HashCode) / sizeof (unsigned int)) - 1; i >= 0; i--) + for (i = (sizeof (struct GNUNET_HashCode) / sizeof (unsigned int)) - 1; i >= 0; i--) result->bits[i] = b->bits[i] - a->bits[i]; } @@ -375,12 +375,12 @@ GNUNET_CRYPTO_hash_difference (const GNUNET_HashCode * a, * @param result set to a + delta */ void -GNUNET_CRYPTO_hash_sum (const GNUNET_HashCode * a, - const GNUNET_HashCode * delta, GNUNET_HashCode * result) +GNUNET_CRYPTO_hash_sum (const struct GNUNET_HashCode * a, + const struct GNUNET_HashCode * delta, struct GNUNET_HashCode * result) { int i; - for (i = (sizeof (GNUNET_HashCode) / sizeof (unsigned int)) - 1; i >= 0; i--) + for (i = (sizeof (struct GNUNET_HashCode) / sizeof (unsigned int)) - 1; i >= 0; i--) result->bits[i] = delta->bits[i] + a->bits[i]; } @@ -393,12 +393,12 @@ GNUNET_CRYPTO_hash_sum (const GNUNET_HashCode * a, * @param result set to a ^ b */ void -GNUNET_CRYPTO_hash_xor (const GNUNET_HashCode * a, const GNUNET_HashCode * b, - GNUNET_HashCode * result) +GNUNET_CRYPTO_hash_xor (const struct GNUNET_HashCode * a, const struct GNUNET_HashCode * b, + struct GNUNET_HashCode * result) { int i; - for (i = (sizeof (GNUNET_HashCode) / sizeof (unsigned int)) - 1; i >= 0; i--) + for (i = (sizeof (struct GNUNET_HashCode) / sizeof (unsigned int)) - 1; i >= 0; i--) result->bits[i] = a->bits[i] ^ b->bits[i]; } @@ -411,11 +411,11 @@ GNUNET_CRYPTO_hash_xor (const GNUNET_HashCode * a, const GNUNET_HashCode * b, * @param iv set to a valid initialization vector */ void -GNUNET_CRYPTO_hash_to_aes_key (const GNUNET_HashCode * hc, +GNUNET_CRYPTO_hash_to_aes_key (const struct GNUNET_HashCode * hc, struct GNUNET_CRYPTO_AesSessionKey *skey, struct GNUNET_CRYPTO_AesInitializationVector *iv) { - GNUNET_assert (sizeof (GNUNET_HashCode) >= + GNUNET_assert (sizeof (struct GNUNET_HashCode) >= GNUNET_CRYPTO_AES_KEY_LENGTH + sizeof (struct GNUNET_CRYPTO_AesInitializationVector)); memcpy (skey, hc, GNUNET_CRYPTO_AES_KEY_LENGTH); @@ -433,16 +433,16 @@ GNUNET_CRYPTO_hash_to_aes_key (const GNUNET_HashCode * hc, * @return Bit \a bit from hashcode \a code, -1 for invalid index */ int -GNUNET_CRYPTO_hash_get_bit (const GNUNET_HashCode * code, unsigned int bit) +GNUNET_CRYPTO_hash_get_bit (const struct GNUNET_HashCode * code, unsigned int bit) { - GNUNET_assert (bit < 8 * sizeof (GNUNET_HashCode)); + GNUNET_assert (bit < 8 * sizeof (struct GNUNET_HashCode)); return (((unsigned char *) code)[bit >> 3] & (1 << (bit & 7))) > 0; } /** * Determine how many low order bits match in two - * GNUNET_HashCodes. i.e. - 010011 and 011111 share + * struct GNUNET_HashCodes. i.e. - 010011 and 011111 share * the first two lowest order bits, and therefore the * return value is two (NOT XOR distance, nor how many * bits match absolutely!). @@ -453,16 +453,16 @@ GNUNET_CRYPTO_hash_get_bit (const GNUNET_HashCode * code, unsigned int bit) * @return the number of bits that match */ unsigned int -GNUNET_CRYPTO_hash_matching_bits (const GNUNET_HashCode * first, - const GNUNET_HashCode * second) +GNUNET_CRYPTO_hash_matching_bits (const struct GNUNET_HashCode * first, + const struct GNUNET_HashCode * second) { unsigned int i; - for (i = 0; i < sizeof (GNUNET_HashCode) * 8; i++) + for (i = 0; i < sizeof (struct GNUNET_HashCode) * 8; i++) if (GNUNET_CRYPTO_hash_get_bit (first, i) != GNUNET_CRYPTO_hash_get_bit (second, i)) return i; - return sizeof (GNUNET_HashCode) * 8; + return sizeof (struct GNUNET_HashCode) * 8; } @@ -475,7 +475,7 @@ GNUNET_CRYPTO_hash_matching_bits (const GNUNET_HashCode * first, * @return 1 if h1 > h2, -1 if h1 < h2 and 0 if h1 == h2. */ int -GNUNET_CRYPTO_hash_cmp (const GNUNET_HashCode * h1, const GNUNET_HashCode * h2) +GNUNET_CRYPTO_hash_cmp (const struct GNUNET_HashCode * h1, const struct GNUNET_HashCode * h2) { unsigned int *i1; unsigned int *i2; @@ -483,7 +483,7 @@ GNUNET_CRYPTO_hash_cmp (const GNUNET_HashCode * h1, const GNUNET_HashCode * h2) i1 = (unsigned int *) h1; i2 = (unsigned int *) h2; - for (i = (sizeof (GNUNET_HashCode) / sizeof (unsigned int)) - 1; i >= 0; i--) + for (i = (sizeof (struct GNUNET_HashCode) / sizeof (unsigned int)) - 1; i >= 0; i--) { if (i1[i] > i2[i]) return 1; @@ -504,15 +504,15 @@ GNUNET_CRYPTO_hash_cmp (const GNUNET_HashCode * h1, const GNUNET_HashCode * h2) * @return -1 if h1 is closer, 1 if h2 is closer and 0 if h1==h2. */ int -GNUNET_CRYPTO_hash_xorcmp (const GNUNET_HashCode * h1, - const GNUNET_HashCode * h2, - const GNUNET_HashCode * target) +GNUNET_CRYPTO_hash_xorcmp (const struct GNUNET_HashCode * h1, + const struct GNUNET_HashCode * h2, + const struct GNUNET_HashCode * target) { int i; unsigned int d1; unsigned int d2; - for (i = sizeof (GNUNET_HashCode) / sizeof (unsigned int) - 1; i >= 0; i--) + for (i = sizeof (struct GNUNET_HashCode) / sizeof (unsigned int) - 1; i >= 0; i--) { d1 = ((unsigned int *) h1)[i] ^ ((unsigned int *) target)[i]; d2 = ((unsigned int *) h2)[i] ^ ((unsigned int *) target)[i]; @@ -576,7 +576,7 @@ GNUNET_CRYPTO_hmac_derive_key_v (struct GNUNET_CRYPTO_AuthKey *key, void GNUNET_CRYPTO_hmac (const struct GNUNET_CRYPTO_AuthKey *key, const void *plaintext, size_t plaintext_len, - GNUNET_HashCode * hmac) + struct GNUNET_HashCode * hmac) { gcry_md_hd_t md; const unsigned char *mc; diff --git a/src/util/crypto_ksk.c b/src/util/crypto_ksk.c index 274457b..0c09109 100644 --- a/src/util/crypto_ksk.c +++ b/src/util/crypto_ksk.c @@ -70,11 +70,11 @@ struct GNUNET_CRYPTO_RsaPrivateKey static void -mpz_randomize (gcry_mpi_t n, unsigned int nbits, GNUNET_HashCode * rnd) +mpz_randomize (gcry_mpi_t n, unsigned int nbits, struct GNUNET_HashCode * rnd) { - GNUNET_HashCode hc; - GNUNET_HashCode tmp; - int bits_per_hc = sizeof (GNUNET_HashCode) * 8; + struct GNUNET_HashCode hc; + struct GNUNET_HashCode tmp; + int bits_per_hc = sizeof (struct GNUNET_HashCode) * 8; int cnt; int i; @@ -88,8 +88,8 @@ mpz_randomize (gcry_mpi_t n, unsigned int nbits, GNUNET_HashCode * rnd) int j; if (i > 0) - GNUNET_CRYPTO_hash (&hc, sizeof (GNUNET_HashCode), &tmp); - for (j = 0; j < sizeof (GNUNET_HashCode) / sizeof (uint32_t); j++) + GNUNET_CRYPTO_hash (&hc, sizeof (struct GNUNET_HashCode), &tmp); + for (j = 0; j < sizeof (struct GNUNET_HashCode) / sizeof (uint32_t); j++) { #if HAVE_GCRY_MPI_LSHIFT gcry_mpi_lshift (n, n, sizeof (uint32_t) * 8); @@ -101,7 +101,7 @@ mpz_randomize (gcry_mpi_t n, unsigned int nbits, GNUNET_HashCode * rnd) } hc = tmp; } - GNUNET_CRYPTO_hash (&hc, sizeof (GNUNET_HashCode), rnd); + GNUNET_CRYPTO_hash (&hc, sizeof (struct GNUNET_HashCode), rnd); i = gcry_mpi_get_nbits (n); while (i > nbits) gcry_mpi_clear_bit (n, --i); @@ -137,7 +137,7 @@ mpz_tdiv_q_2exp (gcry_mpi_t q, gcry_mpi_t n, unsigned int b) * Return true if n is probably a prime */ static int -is_prime (gcry_mpi_t n, int steps, GNUNET_HashCode * hc) +is_prime (gcry_mpi_t n, int steps, struct GNUNET_HashCode * hc) { gcry_mpi_t x; gcry_mpi_t y; @@ -218,7 +218,7 @@ adjust (unsigned char *buf, size_t size, size_t target) static void -gen_prime (gcry_mpi_t * ptest, unsigned int nbits, GNUNET_HashCode * hc) +gen_prime (gcry_mpi_t * ptest, unsigned int nbits, struct GNUNET_HashCode * hc) { /* Note: 2 is not included because it can be tested more easily by * looking at bit 0. The last entry in this list is marked by a zero */ @@ -400,7 +400,7 @@ gen_prime (gcry_mpi_t * ptest, unsigned int nbits, GNUNET_HashCode * hc) */ static void generate_kblock_key (KBlock_secret_key *sk, unsigned int nbits, - GNUNET_HashCode * hc) + struct GNUNET_HashCode * hc) { gcry_mpi_t t1, t2; gcry_mpi_t phi; /* helper: (p-1)(q-1) */ @@ -490,10 +490,10 @@ GNUNET_NETWORK_STRUCT_END * given HashCode as input to the PRNG. */ static struct KskRsaPrivateKeyBinaryEncoded * -makeKblockKeyInternal (const GNUNET_HashCode * hc) +makeKblockKeyInternal (const struct GNUNET_HashCode * hc) { KBlock_secret_key sk; - GNUNET_HashCode hx; + struct GNUNET_HashCode hx; unsigned char *pbu[6]; gcry_mpi_t *pkv[6]; size_t sizes[6]; @@ -564,7 +564,7 @@ struct KBlockKeyCacheLine /** * Hash from which the key was generated. */ - GNUNET_HashCode hc; + struct GNUNET_HashCode hc; /** * The encoded key. @@ -594,13 +594,13 @@ static unsigned int cacheSize; * @return corresponding private key; must not be freed! */ struct GNUNET_CRYPTO_RsaPrivateKey * -GNUNET_CRYPTO_rsa_key_create_from_hash (const GNUNET_HashCode * hc) +GNUNET_CRYPTO_rsa_key_create_from_hash (const struct GNUNET_HashCode * hc) { struct KBlockKeyCacheLine *line; unsigned int i; for (i = 0; i < cacheSize; i++) - if (0 == memcmp (hc, &cache[i]->hc, sizeof (GNUNET_HashCode))) + if (0 == memcmp (hc, &cache[i]->hc, sizeof (struct GNUNET_HashCode))) return GNUNET_CRYPTO_rsa_decode_key ((const char*) cache[i]->pke, ntohs (cache[i]->pke->len)); line = GNUNET_malloc (sizeof (struct KBlockKeyCacheLine)); diff --git a/src/util/crypto_random.c b/src/util/crypto_random.c index 35d3c41..b61d596 100644 --- a/src/util/crypto_random.c +++ b/src/util/crypto_random.c @@ -1,6 +1,6 @@ /* This file is part of GNUnet. - (C) 2001, 2002, 2003, 2004, 2005, 2006 Christian Grothoff (and other contributing authors) + (C) 2001, 2002, 2003, 2004, 2005, 2006, 2012 Christian Grothoff (and other contributing authors) GNUnet is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published @@ -34,6 +34,14 @@ #define LOG_STRERROR(kind,syscall) GNUNET_log_from_strerror (kind, "util", syscall) + +/** + * GNUNET_YES if we are using a 'weak' (low-entropy) PRNG. + */ +static int weak_random; + + + /* TODO: ndurner, move this to plibc? */ /* The code is derived from glibc, obviously */ #if MINGW @@ -45,14 +53,22 @@ #endif #define RANDOM() glibc_weak_rand32() #define SRANDOM(s) glibc_weak_srand32(s) +#if defined(RAND_MAX) +#undef RAND_MAX +#endif +#define RAND_MAX 0x7fffffff /* Hopefully this is correct */ + + static int32_t glibc_weak_rand32_state = 1; + void glibc_weak_srand32 (int32_t s) { glibc_weak_rand32_state = s; } + int32_t glibc_weak_rand32 () { @@ -70,11 +86,12 @@ glibc_weak_rand32 () * @return number between 0 and 1. */ static double -weak_random () +get_weak_random () { return ((double) RANDOM () / RAND_MAX); } + /** * Seed a weak random generator. Only GNUNET_CRYPTO_QUALITY_WEAK-mode generator * can be seeded. @@ -87,6 +104,7 @@ GNUNET_CRYPTO_seed_weak_random (int32_t seed) SRANDOM (seed); } + /** * Produce a random value. * @@ -130,7 +148,7 @@ GNUNET_CRYPTO_random_u32 (enum GNUNET_CRYPTO_Quality mode, uint32_t i) while (ret >= ul); return ret % i; case GNUNET_CRYPTO_QUALITY_WEAK: - ret = i * weak_random (); + ret = i * get_weak_random (); if (ret >= i) ret = i - 1; return ret; @@ -207,7 +225,7 @@ GNUNET_CRYPTO_random_u64 (enum GNUNET_CRYPTO_Quality mode, uint64_t max) return ret % max; case GNUNET_CRYPTO_QUALITY_WEAK: - ret = max * weak_random (); + ret = max * get_weak_random (); if (ret >= max) ret = max - 1; return ret; @@ -217,6 +235,19 @@ GNUNET_CRYPTO_random_u64 (enum GNUNET_CRYPTO_Quality mode, uint64_t max) return 0; } + +/** + * Check if we are using weak random number generation. + * + * @return GNUNET_YES if weak number generation is on + */ +int +GNUNET_CRYPTO_random_is_weak () +{ + return weak_random; +} + + /** * This function should only be called in testcases * where strong entropy gathering is not desired @@ -225,6 +256,7 @@ GNUNET_CRYPTO_random_u64 (enum GNUNET_CRYPTO_Quality mode, uint64_t max) void GNUNET_CRYPTO_random_disable_entropy_gathering () { + weak_random = GNUNET_YES; gcry_control (GCRYCTL_ENABLE_QUICK_RANDOM, 0); } @@ -235,6 +267,7 @@ GNUNET_CRYPTO_random_disable_entropy_gathering () */ static struct GNUNET_OS_Process *genproc; + /** * Function called by libgcrypt whenever we are * blocked gathering entropy. @@ -253,7 +286,7 @@ entropy_generator (void *cls, const char *what, int printchar, int current, { if (genproc != NULL) { - if (0 != GNUNET_OS_process_kill (genproc, SIGTERM)) + if (0 != GNUNET_OS_process_kill (genproc, SIGKILL)) LOG_STRERROR (GNUNET_ERROR_TYPE_ERROR, "kill"); GNUNET_break (GNUNET_OK == GNUNET_OS_process_wait (genproc)); GNUNET_OS_process_destroy (genproc); @@ -271,7 +304,7 @@ entropy_generator (void *cls, const char *what, int printchar, int current, GNUNET_break (0); return; } - if (0 != GNUNET_OS_process_kill (genproc, SIGTERM)) + if (0 != GNUNET_OS_process_kill (genproc, SIGKILL)) LOG_STRERROR (GNUNET_ERROR_TYPE_ERROR, "kill"); GNUNET_break (GNUNET_OK == GNUNET_OS_process_wait (genproc)); GNUNET_OS_process_destroy (genproc); @@ -280,7 +313,7 @@ entropy_generator (void *cls, const char *what, int printchar, int current, LOG (GNUNET_ERROR_TYPE_INFO, _("Starting `%s' process to generate entropy\n"), "find"); genproc = - GNUNET_OS_start_process (GNUNET_NO, + GNUNET_OS_start_process (GNUNET_NO, 0, NULL, NULL, "sh", "sh", "-c", "exec find / -mount -type f -exec cp {} /dev/null \\; 2>/dev/null", NULL); @@ -302,12 +335,12 @@ killfind () void __attribute__ ((constructor)) GNUNET_CRYPTO_random_init () { gcry_control (GCRYCTL_DISABLE_SECMEM, 0); - if (!gcry_check_version (GCRYPT_VERSION)) + if (!gcry_check_version (NEED_LIBGCRYPT_VERSION)) { FPRINTF (stderr, _ ("libgcrypt has not the expected version (version %s is required).\n"), - GCRYPT_VERSION); + NEED_LIBGCRYPT_VERSION); GNUNET_abort (); } #ifdef GCRYCTL_INITIALIZATION_FINISHED diff --git a/src/util/crypto_rsa.c b/src/util/crypto_rsa.c index 0106f43..cd9a33f 100644 --- a/src/util/crypto_rsa.c +++ b/src/util/crypto_rsa.c @@ -22,21 +22,11 @@ * @file util/crypto_rsa.c * @brief public key cryptography (RSA) with libgcrypt * @author Christian Grothoff - * - * Note that the code locks often needlessly on the gcrypt-locking api. - * One would think that simple MPI operations should not require locking - * (since only global operations on the random pool must be locked, - * strictly speaking). But libgcrypt does sometimes require locking in - * unexpected places, so the safe solution is to always lock even if it - * is not required. The performance impact is minimal anyway. */ - #include "platform.h" #include #include "gnunet_common.h" -#include "gnunet_crypto_lib.h" -#include "gnunet_disk_lib.h" -#include "gnunet_strings_lib.h" +#include "gnunet_util_lib.h" #define LOG(kind,...) GNUNET_log_from (kind, "util", __VA_ARGS__) @@ -44,21 +34,23 @@ #define LOG_STRERROR_FILE(kind,syscall,filename) GNUNET_log_from_strerror_file (kind, "util", syscall, filename) +#define HOSTKEY_LEN 2048 + +#define EXTRA_CHECKS ALLOW_EXTRA_CHECKS + + /** * The private information of an RSA key pair. - * NOTE: this must match the definition in crypto_ksk.c + * NOTE: this must match the definition in crypto_ksk.c and gnunet-rsa.c! */ struct GNUNET_CRYPTO_RsaPrivateKey { + /** + * Libgcrypt S-expression for the ECC key. + */ gcry_sexp_t sexp; }; - -#define HOSTKEY_LEN 2048 - -#define EXTRA_CHECKS ALLOW_EXTRA_CHECKS - - /** * Log an error message at log-level 'level' that indicates * a failure of the command 'cmd' with the message given @@ -70,6 +62,10 @@ struct GNUNET_CRYPTO_RsaPrivateKey * If target != size, move target bytes to the * end of the size-sized buffer and zero out the * first target-size bytes. + * + * @param buf original buffer + * @param size number of bytes in the buffer + * @param target target size of the buffer */ static void adjust (unsigned char *buf, size_t size, size_t target) @@ -81,69 +77,50 @@ adjust (unsigned char *buf, size_t size, size_t target) } } + /** - * Create a new private key. Caller must free return value. + * Free memory occupied by RSA private key. * - * @return fresh private key + * @param key pointer to the memory to free */ -struct GNUNET_CRYPTO_RsaPrivateKey * -GNUNET_CRYPTO_rsa_key_create () +void +GNUNET_CRYPTO_rsa_key_free (struct GNUNET_CRYPTO_RsaPrivateKey *key) { - struct GNUNET_CRYPTO_RsaPrivateKey *ret; - gcry_sexp_t s_key; - gcry_sexp_t s_keyparam; - - GNUNET_assert (0 == - gcry_sexp_build (&s_keyparam, NULL, - "(genkey(rsa(nbits %d)(rsa-use-e 3:257)))", - HOSTKEY_LEN)); - GNUNET_assert (0 == gcry_pk_genkey (&s_key, s_keyparam)); - gcry_sexp_release (s_keyparam); -#if EXTRA_CHECKS - GNUNET_assert (0 == gcry_pk_testkey (s_key)); -#endif - ret = GNUNET_malloc (sizeof (struct GNUNET_CRYPTO_RsaPrivateKey)); - ret->sexp = s_key; - return ret; + gcry_sexp_release (key->sexp); + GNUNET_free (key); } + /** - * Free memory occupied by hostkey - * @param hostkey pointer to the memory to free + * Extract values from an S-expression. + * + * @param array where to store the result(s) + * @param sexp S-expression to parse + * @param topname top-level name in the S-expression that is of interest + * @param elems names of the elements to extract + * @return 0 on success */ -void -GNUNET_CRYPTO_rsa_key_free (struct GNUNET_CRYPTO_RsaPrivateKey *hostkey) -{ - gcry_sexp_release (hostkey->sexp); - GNUNET_free (hostkey); -} - static int key_from_sexp (gcry_mpi_t * array, gcry_sexp_t sexp, const char *topname, const char *elems) { - gcry_sexp_t list, l2; + gcry_sexp_t list; + gcry_sexp_t l2; const char *s; - int i, idx; + unsigned int i; + unsigned int idx; - list = gcry_sexp_find_token (sexp, topname, 0); - if (!list) - { - return 1; - } + if (! (list = gcry_sexp_find_token (sexp, topname, 0))) + return 1; l2 = gcry_sexp_cadr (list); gcry_sexp_release (list); list = l2; - if (!list) - { + if (! list) return 2; - } - idx = 0; for (s = elems; *s; s++, idx++) { - l2 = gcry_sexp_find_token (list, s, 1); - if (!l2) + if (! (l2 = gcry_sexp_find_token (list, s, 1))) { for (i = 0; i < idx; i++) { @@ -155,7 +132,7 @@ key_from_sexp (gcry_mpi_t * array, gcry_sexp_t sexp, const char *topname, } array[idx] = gcry_sexp_nth_mpi (l2, 1, GCRYMPI_FMT_USG); gcry_sexp_release (l2); - if (!array[idx]) + if (! array[idx]) { for (i = 0; i < idx; i++) { @@ -170,8 +147,10 @@ key_from_sexp (gcry_mpi_t * array, gcry_sexp_t sexp, const char *topname, return 0; } + /** * Extract the public key of the host. + * * @param priv the private key * @param pub where to write the public key */ @@ -186,9 +165,9 @@ GNUNET_CRYPTO_rsa_key_get_public (const struct GNUNET_CRYPTO_RsaPrivateKey int rc; rc = key_from_sexp (skey, priv->sexp, "public-key", "ne"); - if (rc) + if (0 != rc) rc = key_from_sexp (skey, priv->sexp, "private-key", "ne"); - if (rc) + if (0 != rc) rc = key_from_sexp (skey, priv->sexp, "rsa", "ne"); GNUNET_assert (0 == rc); pub->len = @@ -222,7 +201,7 @@ GNUNET_CRYPTO_rsa_key_get_public (const struct GNUNET_CRYPTO_RsaPrivateKey * @return string representing 'pub' */ char * -GNUNET_CRYPTO_rsa_public_key_to_string (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *pub) +GNUNET_CRYPTO_rsa_public_key_to_string (const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *pub) { char *pubkeybuf; size_t keylen = (sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded)) * 8; @@ -280,16 +259,15 @@ GNUNET_CRYPTO_rsa_public_key_from_string (const char *enc, /** - * Internal: publicKey => RSA-Key. + * Convert the given public key from the network format to the + * S-expression that can be used by libgcrypt. * - * Note that the return type is not actually a private - * key but rather an sexpression for the public key! + * @param publicKey public key to decode + * @return NULL on error */ -static struct GNUNET_CRYPTO_RsaPrivateKey * -public2PrivateKey (const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded - *publicKey) +static gcry_sexp_t +decode_public_key (const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *publicKey) { - struct GNUNET_CRYPTO_RsaPrivateKey *ret; gcry_sexp_t result; gcry_mpi_t n; gcry_mpi_t e; @@ -306,17 +284,15 @@ public2PrivateKey (const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded return NULL; } size = GNUNET_CRYPTO_RSA_DATA_ENCODING_LENGTH; - rc = gcry_mpi_scan (&n, GCRYMPI_FMT_USG, &publicKey->key[0], size, &size); - if (rc) + if (0 != (rc = gcry_mpi_scan (&n, GCRYMPI_FMT_USG, &publicKey->key[0], size, &size))) { LOG_GCRY (GNUNET_ERROR_TYPE_ERROR, "gcry_mpi_scan", rc); return NULL; } size = GNUNET_CRYPTO_RSA_KEY_LENGTH - GNUNET_CRYPTO_RSA_DATA_ENCODING_LENGTH; - rc = gcry_mpi_scan (&e, GCRYMPI_FMT_USG, - &publicKey->key[GNUNET_CRYPTO_RSA_DATA_ENCODING_LENGTH], - size, &size); - if (rc) + if (0 != (rc = gcry_mpi_scan (&e, GCRYMPI_FMT_USG, + &publicKey->key[GNUNET_CRYPTO_RSA_DATA_ENCODING_LENGTH], + size, &size))) { LOG_GCRY (GNUNET_ERROR_TYPE_ERROR, "gcry_mpi_scan", rc); gcry_mpi_release (n); @@ -326,21 +302,20 @@ public2PrivateKey (const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded e); gcry_mpi_release (n); gcry_mpi_release (e); - if (rc) + if (0 != rc) { LOG_GCRY (GNUNET_ERROR_TYPE_ERROR, "gcry_sexp_build", rc); /* erroff gives more info */ return NULL; } - ret = GNUNET_malloc (sizeof (struct GNUNET_CRYPTO_RsaPrivateKey)); - ret->sexp = result; - return ret; + return result; } /** * Encode the private key in a format suitable for * storing it into a file. - * @returns encoding of the private key. + * + * @return encoding of the private key. * The first 4 bytes give the size of the array, as usual. */ struct GNUNET_CRYPTO_RsaPrivateKeyBinaryEncoded * @@ -378,7 +353,7 @@ GNUNET_CRYPTO_rsa_encode_key (const struct GNUNET_CRYPTO_RsaPrivateKey *hostkey) size = sizeof (struct GNUNET_CRYPTO_RsaPrivateKeyBinaryEncoded); for (i = 0; i < 6; i++) { - if (pkv[i] != NULL) + if (NULL != pkv[i]) { GNUNET_assert (0 == gcry_mpi_aprint (GCRYMPI_FMT_USG, @@ -432,6 +407,7 @@ GNUNET_CRYPTO_rsa_encode_key (const struct GNUNET_CRYPTO_RsaPrivateKey *hostkey) * * @param buf the buffer where the private key data is stored * @param len the length of the data in 'buffer' + * @return NULL on error */ struct GNUNET_CRYPTO_RsaPrivateKey * GNUNET_CRYPTO_rsa_decode_key (const char *buf, uint16_t len) @@ -440,11 +416,17 @@ GNUNET_CRYPTO_rsa_decode_key (const char *buf, uint16_t len) const struct GNUNET_CRYPTO_RsaPrivateKeyBinaryEncoded *encoding = (const struct GNUNET_CRYPTO_RsaPrivateKeyBinaryEncoded *) buf; gcry_sexp_t res; - gcry_mpi_t n, e, d, p, q, u; + gcry_mpi_t n; + gcry_mpi_t e; + gcry_mpi_t d; + gcry_mpi_t p; + gcry_mpi_t q; + gcry_mpi_t u; int rc; size_t size; - int pos; + size_t pos; uint16_t enc_len; + size_t erroff; enc_len = ntohs (encoding->len); if (len != enc_len) @@ -456,7 +438,7 @@ GNUNET_CRYPTO_rsa_decode_key (const char *buf, uint16_t len) &((const unsigned char *) (&encoding[1]))[pos], size, &size); pos += ntohs (encoding->sizen); - if (rc) + if (0 != rc) { LOG_GCRY (GNUNET_ERROR_TYPE_ERROR, "gcry_mpi_scan", rc); return NULL; @@ -466,7 +448,7 @@ GNUNET_CRYPTO_rsa_decode_key (const char *buf, uint16_t len) &((const unsigned char *) (&encoding[1]))[pos], size, &size); pos += ntohs (encoding->sizee); - if (rc) + if (0 != rc) { LOG_GCRY (GNUNET_ERROR_TYPE_ERROR, "gcry_mpi_scan", rc); gcry_mpi_release (n); @@ -477,7 +459,7 @@ GNUNET_CRYPTO_rsa_decode_key (const char *buf, uint16_t len) &((const unsigned char *) (&encoding[1]))[pos], size, &size); pos += ntohs (encoding->sized); - if (rc) + if (0 != rc) { LOG_GCRY (GNUNET_ERROR_TYPE_ERROR, "gcry_mpi_scan", rc); gcry_mpi_release (n); @@ -492,7 +474,7 @@ GNUNET_CRYPTO_rsa_decode_key (const char *buf, uint16_t len) &((const unsigned char *) (&encoding[1]))[pos], size, &size); pos += ntohs (encoding->sizep); - if (rc) + if (0 != rc) { LOG_GCRY (GNUNET_ERROR_TYPE_ERROR, "gcry_mpi_scan", rc); gcry_mpi_release (n); @@ -510,13 +492,13 @@ GNUNET_CRYPTO_rsa_decode_key (const char *buf, uint16_t len) &((const unsigned char *) (&encoding[1]))[pos], size, &size); pos += ntohs (encoding->sizeq); - if (rc) + if (0 != rc) { LOG_GCRY (GNUNET_ERROR_TYPE_ERROR, "gcry_mpi_scan", rc); gcry_mpi_release (n); gcry_mpi_release (e); gcry_mpi_release (d); - if (q != NULL) + if (NULL != q) gcry_mpi_release (q); return NULL; } @@ -532,15 +514,15 @@ GNUNET_CRYPTO_rsa_decode_key (const char *buf, uint16_t len) rc = gcry_mpi_scan (&u, GCRYMPI_FMT_USG, &((const unsigned char *) (&encoding[1]))[pos], size, &size); - if (rc) + if (0 != rc) { LOG_GCRY (GNUNET_ERROR_TYPE_ERROR, "gcry_mpi_scan", rc); gcry_mpi_release (n); gcry_mpi_release (e); gcry_mpi_release (d); - if (p != NULL) + if (NULL != p) gcry_mpi_release (p); - if (q != NULL) + if (NULL != q) gcry_mpi_release (q); return NULL; } @@ -548,40 +530,40 @@ GNUNET_CRYPTO_rsa_decode_key (const char *buf, uint16_t len) else u = NULL; - if ((p != NULL) && (q != NULL) && (u != NULL)) + if ((NULL != p) && (NULL != q) && (NULL != u)) { - rc = gcry_sexp_build (&res, &size, /* erroff */ + rc = gcry_sexp_build (&res, &erroff, "(private-key(rsa(n %m)(e %m)(d %m)(p %m)(q %m)(u %m)))", n, e, d, p, q, u); } else { - if ((p != NULL) && (q != NULL)) + if ((NULL != p) && (NULL != q)) { - rc = gcry_sexp_build (&res, &size, /* erroff */ + rc = gcry_sexp_build (&res, &erroff, "(private-key(rsa(n %m)(e %m)(d %m)(p %m)(q %m)))", n, e, d, p, q); } else { - rc = gcry_sexp_build (&res, &size, /* erroff */ + rc = gcry_sexp_build (&res, &erroff, "(private-key(rsa(n %m)(e %m)(d %m)))", n, e, d); } } gcry_mpi_release (n); gcry_mpi_release (e); gcry_mpi_release (d); - if (p != NULL) + if (NULL != p) gcry_mpi_release (p); - if (q != NULL) + if (NULL != q) gcry_mpi_release (q); - if (u != NULL) + if (NULL != u) gcry_mpi_release (u); - if (rc) + if (0 != rc) LOG_GCRY (GNUNET_ERROR_TYPE_ERROR, "gcry_sexp_build", rc); #if EXTRA_CHECKS - if (gcry_pk_testkey (res)) + if (0 != (rc = gcry_pk_testkey (res))) { LOG_GCRY (GNUNET_ERROR_TYPE_ERROR, "gcry_pk_testkey", rc); return NULL; @@ -593,6 +575,120 @@ GNUNET_CRYPTO_rsa_decode_key (const char *buf, uint16_t len) } +/** + * Create a new private key. Caller must free return value. + * + * @return fresh private key + */ +static struct GNUNET_CRYPTO_RsaPrivateKey * +rsa_key_create () +{ + struct GNUNET_CRYPTO_RsaPrivateKey *ret; + gcry_sexp_t s_key; + gcry_sexp_t s_keyparam; + + GNUNET_assert (0 == + gcry_sexp_build (&s_keyparam, NULL, + "(genkey(rsa(nbits %d)(rsa-use-e 3:257)))", + HOSTKEY_LEN)); + GNUNET_assert (0 == gcry_pk_genkey (&s_key, s_keyparam)); + gcry_sexp_release (s_keyparam); +#if EXTRA_CHECKS + GNUNET_assert (0 == gcry_pk_testkey (s_key)); +#endif + ret = GNUNET_malloc (sizeof (struct GNUNET_CRYPTO_RsaPrivateKey)); + ret->sexp = s_key; + return ret; +} + + +/** + * Try to read the private key from the given file. + * + * @param filename file to read the key from + * @return NULL on error + */ +static struct GNUNET_CRYPTO_RsaPrivateKey * +try_read_key (const char *filename) +{ + struct GNUNET_CRYPTO_RsaPrivateKey *ret; + struct GNUNET_CRYPTO_RsaPrivateKeyBinaryEncoded *enc; + struct GNUNET_DISK_FileHandle *fd; + OFF_T fs; + uint16_t len; + + if (GNUNET_YES != GNUNET_DISK_file_test (filename)) + return NULL; + + /* hostkey file exists already, read it! */ + if (NULL == (fd = GNUNET_DISK_file_open (filename, GNUNET_DISK_OPEN_READ, + GNUNET_DISK_PERM_NONE))) + { + LOG_STRERROR_FILE (GNUNET_ERROR_TYPE_ERROR, "open", filename); + return NULL; + } + if (GNUNET_OK != (GNUNET_DISK_file_handle_size (fd, &fs))) + { + LOG_STRERROR_FILE (GNUNET_ERROR_TYPE_ERROR, "stat", filename); + (void) GNUNET_DISK_file_close (fd); + return NULL; + } + if (0 == fs) + { + GNUNET_break (GNUNET_OK == GNUNET_DISK_file_close (fd)); + return NULL; + } + if (fs > UINT16_MAX) + { + LOG (GNUNET_ERROR_TYPE_ERROR, + _("File `%s' does not contain a valid private key (too long, %llu bytes). Renaming it.\n"), + filename, + (unsigned long long) fs); + GNUNET_break (GNUNET_OK == GNUNET_DISK_file_close (fd)); + GNUNET_DISK_file_backup (filename); + return NULL; + } + + enc = GNUNET_malloc (fs); + GNUNET_break (fs == GNUNET_DISK_file_read (fd, enc, fs)); + len = ntohs (enc->len); + ret = NULL; + if ((len != fs) || + (NULL == (ret = GNUNET_CRYPTO_rsa_decode_key ((char *) enc, len)))) + { + LOG (GNUNET_ERROR_TYPE_ERROR, + _("File `%s' does not contain a valid private key (failed decode, %llu bytes). Deleting it.\n"), + filename, + (unsigned long long) fs); + GNUNET_break (GNUNET_OK == GNUNET_DISK_file_close (fd)); + GNUNET_DISK_file_backup (filename); + GNUNET_free (enc); + return NULL; + } + GNUNET_free (enc); + + GNUNET_break (GNUNET_OK == GNUNET_DISK_file_close (fd)); + return ret; +} + + +/** + * Wait for a short time (we're trying to lock a file or want + * to give another process a shot at finishing a disk write, etc.). + * Sleeps for 100ms (as that should be long enough for virtually all + * modern systems to context switch and allow another process to do + * some 'real' work). + */ +static void +short_wait () +{ + struct GNUNET_TIME_Relative timeout; + + timeout = GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MILLISECONDS, 100); + (void) GNUNET_NETWORK_socket_select (NULL, NULL, NULL, timeout); +} + + /** * Create a new private key by reading it from a file. If the * files does not exist, create a new key and write it to the @@ -630,7 +726,7 @@ GNUNET_CRYPTO_rsa_key_create_from_file (const char *filename) GNUNET_DISK_PERM_USER_WRITE); if (NULL == fd) { - if (errno == EEXIST) + if (EEXIST == errno) { if (GNUNET_YES != GNUNET_DISK_file_test (filename)) { @@ -653,18 +749,18 @@ GNUNET_CRYPTO_rsa_key_create_from_file (const char *filename) sizeof (struct GNUNET_CRYPTO_RsaPrivateKeyBinaryEncoded), GNUNET_YES)) { - sleep (1); + short_wait (); if (0 == ++cnt % 10) { ec = errno; LOG (GNUNET_ERROR_TYPE_ERROR, - _("Could not aquire lock on file `%s': %s...\n"), filename, + _("Could not acquire lock on file `%s': %s...\n"), filename, STRERROR (ec)); } } LOG (GNUNET_ERROR_TYPE_INFO, _("Creating a new private key. This may take a while.\n")); - ret = GNUNET_CRYPTO_rsa_key_create (); + ret = rsa_key_create (); GNUNET_assert (ret != NULL); enc = GNUNET_CRYPTO_rsa_encode_key (ret); GNUNET_assert (enc != NULL); @@ -680,9 +776,6 @@ GNUNET_CRYPTO_rsa_key_create_from_file (const char *filename) GNUNET_assert (GNUNET_YES == GNUNET_DISK_file_close (fd)); GNUNET_CRYPTO_rsa_key_get_public (ret, &pub); GNUNET_CRYPTO_hash (&pub, sizeof (pub), &pid.hashPubKey); - LOG (GNUNET_ERROR_TYPE_INFO, - _("I am host `%s'. Stored new private key in `%s'.\n"), - GNUNET_i2s (&pid), filename); return ret; } /* hostkey file exists already, read it! */ @@ -705,13 +798,13 @@ GNUNET_CRYPTO_rsa_key_create_from_file (const char *filename) { ec = errno; LOG (GNUNET_ERROR_TYPE_ERROR, - _("Could not aquire lock on file `%s': %s...\n"), filename, + _("Could not acquire lock on file `%s': %s...\n"), filename, STRERROR (ec)); LOG (GNUNET_ERROR_TYPE_ERROR, _ - ("This may be ok if someone is currently generating a hostkey.\n")); + ("This may be ok if someone is currently generating a private key.\n")); } - sleep (1); + short_wait (); continue; } if (GNUNET_YES != GNUNET_DISK_file_test (filename)) @@ -730,7 +823,7 @@ GNUNET_CRYPTO_rsa_key_create_from_file (const char *filename) fs = 0; if (fs < sizeof (struct GNUNET_CRYPTO_RsaPrivateKeyBinaryEncoded)) { - /* maybe we got the read lock before the hostkey generating + /* maybe we got the read lock before the key generating * process had a chance to get the write lock; give it up! */ if (GNUNET_YES != GNUNET_DISK_file_unlock (fd, 0, @@ -740,14 +833,14 @@ GNUNET_CRYPTO_rsa_key_create_from_file (const char *filename) { LOG (GNUNET_ERROR_TYPE_ERROR, _ - ("When trying to read hostkey file `%s' I found %u bytes but I need at least %u.\n"), + ("When trying to read key file `%s' I found %u bytes but I need at least %u.\n"), filename, (unsigned int) fs, (unsigned int) sizeof (struct GNUNET_CRYPTO_RsaPrivateKeyBinaryEncoded)); LOG (GNUNET_ERROR_TYPE_ERROR, _ - ("This may be ok if someone is currently generating a hostkey.\n")); + ("This may be ok if someone is currently generating a private key.\n")); } - sleep (2); /* wait a bit longer! */ + short_wait (); /* wait a bit longer! */ continue; } break; @@ -762,10 +855,7 @@ GNUNET_CRYPTO_rsa_key_create_from_file (const char *filename) LOG (GNUNET_ERROR_TYPE_ERROR, _("File `%s' does not contain a valid private key. Deleting it.\n"), filename); - if (0 != UNLINK (filename)) - { - LOG_STRERROR_FILE (GNUNET_ERROR_TYPE_WARNING, "unlink", filename); - } + GNUNET_DISK_file_backup (filename); } GNUNET_free (enc); if (GNUNET_YES != @@ -777,24 +867,242 @@ GNUNET_CRYPTO_rsa_key_create_from_file (const char *filename) { GNUNET_CRYPTO_rsa_key_get_public (ret, &pub); GNUNET_CRYPTO_hash (&pub, sizeof (pub), &pid.hashPubKey); - LOG (GNUNET_ERROR_TYPE_INFO, - _("I am host `%s'. Read private key from `%s'.\n"), GNUNET_i2s (&pid), - filename); } return ret; } /** - * Setup a hostkey file for a peer given the name of the + * Handle to cancel private key generation and state for the + * key generation operation. + */ +struct GNUNET_CRYPTO_RsaKeyGenerationContext +{ + + /** + * Continuation to call upon completion. + */ + GNUNET_CRYPTO_RsaKeyCallback cont; + + /** + * Closure for 'cont'. + */ + void *cont_cls; + + /** + * Name of the file. + */ + char *filename; + + /** + * Handle to the helper process which does the key generation. + */ + struct GNUNET_OS_Process *gnunet_rsa; + + /** + * Handle to 'stdout' of gnunet-rsa. We 'read' on stdout to detect + * process termination (instead of messing with SIGCHLD). + */ + struct GNUNET_DISK_PipeHandle *gnunet_rsa_out; + + /** + * Location where we store the private key if it already existed. + * (if this is used, 'filename', 'gnunet_rsa' and 'gnunet_rsa_out' will + * not be used). + */ + struct GNUNET_CRYPTO_RsaPrivateKey *pk; + + /** + * Task reading from 'gnunet_rsa_out' to wait for process termination. + */ + GNUNET_SCHEDULER_TaskIdentifier read_task; + +}; + + +/** + * Task called upon shutdown or process termination of 'gnunet-rsa' during + * RSA key generation. Check where we are and perform the appropriate + * action. + * + * @param cls the 'struct GNUNET_CRYPTO_RsaKeyGenerationContext' + * @param tc scheduler context + */ +static void +check_key_generation_completion (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct GNUNET_CRYPTO_RsaKeyGenerationContext *gc = cls; + struct GNUNET_CRYPTO_RsaPrivateKey *pk; + + gc->read_task = GNUNET_SCHEDULER_NO_TASK; + if (0 != (tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN)) + { + gc->cont (gc->cont_cls, NULL, _("interrupted by shutdown")); + GNUNET_CRYPTO_rsa_key_create_stop (gc); + return; + } + GNUNET_assert (GNUNET_OK == + GNUNET_OS_process_wait (gc->gnunet_rsa)); + GNUNET_OS_process_destroy (gc->gnunet_rsa); + gc->gnunet_rsa = NULL; + if (NULL == (pk = try_read_key (gc->filename))) + { + GNUNET_break (0); + gc->cont (gc->cont_cls, NULL, _("gnunet-rsa failed")); + GNUNET_CRYPTO_rsa_key_create_stop (gc); + return; + } + gc->cont (gc->cont_cls, pk, NULL); + GNUNET_DISK_pipe_close (gc->gnunet_rsa_out); + GNUNET_free (gc->filename); + GNUNET_free (gc); +} + + +/** + * Return the private RSA key which already existed on disk + * (asynchronously) to the caller. + * + * @param cls the 'struct GNUNET_CRYPTO_RsaKeyGenerationContext' + * @param tc scheduler context (unused) + */ +static void +async_return_key (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct GNUNET_CRYPTO_RsaKeyGenerationContext *gc = cls; + + gc->cont (gc->cont_cls, + gc->pk, + NULL); + GNUNET_free (gc); +} + + +/** + * Create a new private key by reading it from a file. If the files + * does not exist, create a new key and write it to the file. If the + * contents of the file are invalid the old file is deleted and a + * fresh key is created. + * + * @param filename name of file to use for storage + * @param cont function to call when done (or on errors) + * @param cont_cls closure for 'cont' + * @return handle to abort operation, NULL on fatal errors (cont will not be called if NULL is returned) + */ +struct GNUNET_CRYPTO_RsaKeyGenerationContext * +GNUNET_CRYPTO_rsa_key_create_start (const char *filename, + GNUNET_CRYPTO_RsaKeyCallback cont, + void *cont_cls) +{ + struct GNUNET_CRYPTO_RsaKeyGenerationContext *gc; + struct GNUNET_CRYPTO_RsaPrivateKey *pk; + const char *weak_random; + + if (NULL != (pk = try_read_key (filename))) + { + /* quick happy ending: key already exists! */ + gc = GNUNET_malloc (sizeof (struct GNUNET_CRYPTO_RsaKeyGenerationContext)); + gc->pk = pk; + gc->cont = cont; + gc->cont_cls = cont_cls; + gc->read_task = GNUNET_SCHEDULER_add_now (&async_return_key, + gc); + return gc; + } + gc = GNUNET_malloc (sizeof (struct GNUNET_CRYPTO_RsaKeyGenerationContext)); + gc->filename = GNUNET_strdup (filename); + gc->cont = cont; + gc->cont_cls = cont_cls; + gc->gnunet_rsa_out = GNUNET_DISK_pipe (GNUNET_NO, + GNUNET_NO, + GNUNET_NO, + GNUNET_YES); + if (NULL == gc->gnunet_rsa_out) + { + GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "pipe"); + GNUNET_free (gc->filename); + GNUNET_free (gc); + return NULL; + } + weak_random = NULL; + if (GNUNET_YES == + GNUNET_CRYPTO_random_is_weak ()) + weak_random = "-w"; + gc->gnunet_rsa = GNUNET_OS_start_process (GNUNET_NO, + GNUNET_OS_INHERIT_STD_ERR, + NULL, + gc->gnunet_rsa_out, + "gnunet-rsa", + "gnunet-rsa", + gc->filename, + weak_random, + NULL); + if (NULL == gc->gnunet_rsa) + { + GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "fork"); + GNUNET_DISK_pipe_close (gc->gnunet_rsa_out); + GNUNET_free (gc->filename); + GNUNET_free (gc); + return NULL; + } + GNUNET_assert (GNUNET_OK == + GNUNET_DISK_pipe_close_end (gc->gnunet_rsa_out, + GNUNET_DISK_PIPE_END_WRITE)); + gc->read_task = GNUNET_SCHEDULER_add_read_file (GNUNET_TIME_UNIT_FOREVER_REL, + GNUNET_DISK_pipe_handle (gc->gnunet_rsa_out, + GNUNET_DISK_PIPE_END_READ), + &check_key_generation_completion, + gc); + return gc; +} + + +/** + * Abort RSA key generation. + * + * @param gc key generation context to abort + */ +void +GNUNET_CRYPTO_rsa_key_create_stop (struct GNUNET_CRYPTO_RsaKeyGenerationContext *gc) +{ + if (GNUNET_SCHEDULER_NO_TASK != gc->read_task) + { + GNUNET_SCHEDULER_cancel (gc->read_task); + gc->read_task = GNUNET_SCHEDULER_NO_TASK; + } + if (NULL != gc->gnunet_rsa) + { + (void) GNUNET_OS_process_kill (gc->gnunet_rsa, SIGKILL); + GNUNET_break (GNUNET_OK == + GNUNET_OS_process_wait (gc->gnunet_rsa)); + GNUNET_OS_process_destroy (gc->gnunet_rsa); + GNUNET_DISK_pipe_close (gc->gnunet_rsa_out); + } + + if (NULL != gc->filename) + { + if (0 != UNLINK (gc->filename)) + GNUNET_log_strerror_file (GNUNET_ERROR_TYPE_WARNING, "unlink", gc->filename); + GNUNET_free (gc->filename); + } + if (NULL != gc->pk) + GNUNET_CRYPTO_rsa_key_free (gc->pk); + GNUNET_free (gc); +} + + +/** + * Setup a key file for a peer given the name of the * configuration file (!). This function is used so that * at a later point code can be certain that reading a - * hostkey is fast (for example in time-dependent testcases). + * key is fast (for example in time-dependent testcases). * * @param cfg_name name of the configuration file to use */ void -GNUNET_CRYPTO_setup_hostkey (const char *cfg_name) +GNUNET_CRYPTO_rsa_setup_hostkey (const char *cfg_name) { struct GNUNET_CONFIGURATION_Handle *cfg; struct GNUNET_CRYPTO_RsaPrivateKey *pk; @@ -832,15 +1140,14 @@ GNUNET_CRYPTO_rsa_encrypt (const void *block, size_t size, { gcry_sexp_t result; gcry_sexp_t data; - struct GNUNET_CRYPTO_RsaPrivateKey *pubkey; + gcry_sexp_t psexp; gcry_mpi_t val; gcry_mpi_t rval; size_t isize; size_t erroff; - GNUNET_assert (size <= sizeof (GNUNET_HashCode)); - pubkey = public2PrivateKey (publicKey); - if (pubkey == NULL) + GNUNET_assert (size <= sizeof (struct GNUNET_HashCode)); + if (! (psexp = decode_public_key (publicKey))) return GNUNET_SYSERR; isize = size; GNUNET_assert (0 == @@ -849,10 +1156,9 @@ GNUNET_CRYPTO_rsa_encrypt (const void *block, size_t size, gcry_sexp_build (&data, &erroff, "(data (flags pkcs1)(value %m))", val)); gcry_mpi_release (val); - GNUNET_assert (0 == gcry_pk_encrypt (&result, data, pubkey->sexp)); + GNUNET_assert (0 == gcry_pk_encrypt (&result, data, psexp)); gcry_sexp_release (data); - GNUNET_CRYPTO_rsa_key_free (pubkey); - + gcry_sexp_release (psexp); GNUNET_assert (0 == key_from_sexp (&rval, result, "rsa", "a")); gcry_sexp_release (result); isize = sizeof (struct GNUNET_CRYPTO_RsaEncryptedData); @@ -867,7 +1173,7 @@ GNUNET_CRYPTO_rsa_encrypt (const void *block, size_t size, /** - * Decrypt a given block with the hostkey. + * Decrypt a given block with the key. * * @param key the key with which to decrypt this block * @param block the data to decrypt, encoded as returned by encrypt @@ -919,6 +1225,39 @@ GNUNET_CRYPTO_rsa_decrypt (const struct GNUNET_CRYPTO_RsaPrivateKey * key, } +/** + * Convert the data specified in the given purpose argument to an + * S-expression suitable for signature operations. + * + * @param purpose data to convert + * @return converted s-expression + */ +static gcry_sexp_t +data_to_pkcs1 (const struct GNUNET_CRYPTO_RsaSignaturePurpose *purpose) +{ + struct GNUNET_HashCode hc; + size_t bufSize; + gcry_sexp_t data; + + GNUNET_CRYPTO_hash (purpose, ntohl (purpose->size), &hc); +#define FORMATSTRING "(4:data(5:flags5:pkcs1)(4:hash6:sha51264:0123456789012345678901234567890123456789012345678901234567890123))" + bufSize = strlen (FORMATSTRING) + 1; + { + char buff[bufSize]; + + memcpy (buff, FORMATSTRING, bufSize); + memcpy (&buff + [bufSize - + strlen + ("0123456789012345678901234567890123456789012345678901234567890123))") + - 1], &hc, sizeof (struct GNUNET_HashCode)); + GNUNET_assert (0 == gcry_sexp_new (&data, buff, bufSize, 0)); + } +#undef FORMATSTRING + return data; +} + + /** * Sign a given block. * @@ -936,22 +1275,8 @@ GNUNET_CRYPTO_rsa_sign (const struct GNUNET_CRYPTO_RsaPrivateKey *key, gcry_sexp_t data; size_t ssize; gcry_mpi_t rval; - GNUNET_HashCode hc; - char *buff; - int bufSize; - GNUNET_CRYPTO_hash (purpose, ntohl (purpose->size), &hc); -#define FORMATSTRING "(4:data(5:flags5:pkcs1)(4:hash6:sha51264:0123456789012345678901234567890123456789012345678901234567890123))" - bufSize = strlen (FORMATSTRING) + 1; - buff = GNUNET_malloc (bufSize); - memcpy (buff, FORMATSTRING, bufSize); - memcpy (&buff - [bufSize - - strlen - ("0123456789012345678901234567890123456789012345678901234567890123))") - - 1], &hc, sizeof (GNUNET_HashCode)); - GNUNET_assert (0 == gcry_sexp_new (&data, buff, bufSize, 0)); - GNUNET_free (buff); + data = data_to_pkcs1 (purpose); GNUNET_assert (0 == gcry_pk_sign (&result, data, key->sexp)); gcry_sexp_release (data); GNUNET_assert (0 == key_from_sexp (&rval, result, "rsa", "s")); @@ -987,16 +1312,12 @@ GNUNET_CRYPTO_rsa_verify (uint32_t purpose, gcry_sexp_t sigdata; size_t size; gcry_mpi_t val; - struct GNUNET_CRYPTO_RsaPrivateKey *hostkey; - GNUNET_HashCode hc; - char *buff; - int bufSize; + gcry_sexp_t psexp; size_t erroff; int rc; if (purpose != ntohl (validate->purpose)) return GNUNET_SYSERR; /* purpose mismatch */ - GNUNET_CRYPTO_hash (validate, ntohl (validate->size), &hc); size = sizeof (struct GNUNET_CRYPTO_RsaSignature); GNUNET_assert (0 == gcry_mpi_scan (&val, GCRYMPI_FMT_USG, @@ -1005,25 +1326,15 @@ GNUNET_CRYPTO_rsa_verify (uint32_t purpose, gcry_sexp_build (&sigdata, &erroff, "(sig-val(rsa(s %m)))", val)); gcry_mpi_release (val); - bufSize = strlen (FORMATSTRING) + 1; - buff = GNUNET_malloc (bufSize); - memcpy (buff, FORMATSTRING, bufSize); - memcpy (&buff - [strlen (FORMATSTRING) - - strlen - ("0123456789012345678901234567890123456789012345678901234567890123))")], - &hc, sizeof (GNUNET_HashCode)); - GNUNET_assert (0 == gcry_sexp_new (&data, buff, bufSize, 0)); - GNUNET_free (buff); - hostkey = public2PrivateKey (publicKey); - if (hostkey == NULL) + data = data_to_pkcs1 (validate); + if (! (psexp = decode_public_key (publicKey))) { gcry_sexp_release (data); gcry_sexp_release (sigdata); return GNUNET_SYSERR; } - rc = gcry_pk_verify (sigdata, data, hostkey->sexp); - GNUNET_CRYPTO_rsa_key_free (hostkey); + rc = gcry_pk_verify (sigdata, data, psexp); + gcry_sexp_release (psexp); gcry_sexp_release (data); gcry_sexp_release (sigdata); if (rc) diff --git a/src/util/disk.c b/src/util/disk.c index cba0d44..5cd85b6 100644 --- a/src/util/disk.c +++ b/src/util/disk.c @@ -47,7 +47,7 @@ -#if defined(LINUX) || defined(CYGWIN) +#if defined(LINUX) || defined(CYGWIN) || defined(GNU) #include #else #if defined(SOMEBSD) || defined(DARWIN) @@ -274,9 +274,7 @@ GNUNET_DISK_file_seek (const struct GNUNET_DISK_FileHandle * h, OFF_T offset, LARGE_INTEGER new_pos; BOOL b; - static DWORD t[] = {[GNUNET_DISK_SEEK_SET] = FILE_BEGIN, - [GNUNET_DISK_SEEK_CUR] = FILE_CURRENT,[GNUNET_DISK_SEEK_END] = FILE_END - }; + static DWORD t[] = { FILE_BEGIN, FILE_CURRENT, FILE_END }; li.QuadPart = offset; b = SetFilePointerEx (h->h, li, &new_pos, t[whence]); @@ -287,9 +285,7 @@ GNUNET_DISK_file_seek (const struct GNUNET_DISK_FileHandle * h, OFF_T offset, } return (OFF_T) new_pos.QuadPart; #else - static int t[] = {[GNUNET_DISK_SEEK_SET] = SEEK_SET, - [GNUNET_DISK_SEEK_CUR] = SEEK_CUR,[GNUNET_DISK_SEEK_END] = SEEK_END - }; + static int t[] = { SEEK_SET, SEEK_CUR, SEEK_END }; return lseek (h->fd, offset, t[whence]); #endif @@ -393,21 +389,15 @@ GNUNET_DISK_file_get_identifiers (const char *filename, uint64_t * dev, /** - * Create an (empty) temporary file on disk. If the given name is not - * an absolute path, the current 'TMPDIR' will be prepended. In any case, - * 6 random characters will be appended to the name to create a unique - * filename. + * Create the name for a temporary file or directory from a template. * - * @param t component to use for the name; - * does NOT contain "XXXXXX" or "/tmp/". - * @return NULL on error, otherwise name of fresh - * file on disk in directory for temporary files + * @param t template (without XXXXX or "/tmp/") + * @return name ready for passing to 'mktemp' or 'mkdtemp', NULL on error */ -char * -GNUNET_DISK_mktemp (const char *t) +static char * +mktemp_name (const char *t) { const char *tmpdir; - int fd; char *tmpl; char *fn; @@ -419,7 +409,12 @@ GNUNET_DISK_mktemp (const char *t) { /* FIXME: This uses system codepage on W32, not UTF-8 */ tmpdir = getenv ("TMPDIR"); - tmpdir = tmpdir ? tmpdir : "/tmp"; + if (NULL == tmpdir) + tmpdir = getenv ("TMP"); + if (NULL == tmpdir) + tmpdir = getenv ("TEMP"); + if (NULL == tmpdir) + tmpdir = "/tmp"; GNUNET_asprintf (&tmpl, "%s/%s%s", tmpdir, t, "XXXXXX"); } else @@ -438,12 +433,120 @@ GNUNET_DISK_mktemp (const char *t) #else fn = tmpl; #endif - /* FIXME: why is this not MKSTEMP()? This function is implemented in plibc. - * CG: really? If I put MKSTEMP here, I get a compilation error... - * It will assume that fn is UTF-8-encoded, if compiled with UTF-8 support. - */ - fd = mkstemp (fn); - if (fd == -1) + return fn; +} + + +#if WINDOWS +static char * +mkdtemp (char *fn) +{ + char *random_fn; + char *tfn; + + while (1) + { + tfn = GNUNET_strdup (fn); + random_fn = _mktemp (tfn); + if (NULL == random_fn) + { + GNUNET_free (tfn); + return NULL; + } + /* FIXME: assume fn to be UTF-8-encoded and do the right thing */ + if (0 == CreateDirectoryA (tfn, NULL)) + { + DWORD error = GetLastError (); + GNUNET_free (tfn); + if (ERROR_ALREADY_EXISTS == error) + continue; + return NULL; + } + break; + } + strcpy (fn, tfn); + return fn; +} +#endif + +/** + * Create an (empty) temporary directory on disk. If the given name is not + * an absolute path, the current 'TMPDIR' will be prepended. In any case, + * 6 random characters will be appended to the name to create a unique + * filename. + * + * @param t component to use for the name; + * does NOT contain "XXXXXX" or "/tmp/". + * @return NULL on error, otherwise name of fresh + * file on disk in directory for temporary files + */ +char * +GNUNET_DISK_mkdtemp (const char *t) +{ + char *fn; + + fn = mktemp_name (t); + if (fn != mkdtemp (fn)) + { + LOG_STRERROR_FILE (GNUNET_ERROR_TYPE_ERROR, "mkstemp", fn); + GNUNET_free (fn); + return NULL; + } + return fn; +} + + +/** + * Move a file out of the way (create a backup) by + * renaming it to "orig.NUM~" where NUM is the smallest + * number that is not used yet. + * + * @param fil name of the file to back up + */ +void +GNUNET_DISK_file_backup (const char *fil) +{ + size_t slen; + char *target; + unsigned int num; + + slen = strlen (fil) + 20; + target = GNUNET_malloc (slen); + num = 0; + do + { + GNUNET_snprintf (target, slen, + "%s.%u~", + fil, + num++); + } while (0 == access (target, F_OK)); + if (0 != rename (fil, target)) + GNUNET_log_strerror_file (GNUNET_ERROR_TYPE_ERROR, + "rename", + fil); + GNUNET_free (target); +} + + +/** + * Create an (empty) temporary file on disk. If the given name is not + * an absolute path, the current 'TMPDIR' will be prepended. In any case, + * 6 random characters will be appended to the name to create a unique + * filename. + * + * @param t component to use for the name; + * does NOT contain "XXXXXX" or "/tmp/". + * @return NULL on error, otherwise name of fresh + * file on disk in directory for temporary files + */ +char * +GNUNET_DISK_mktemp (const char *t) +{ + int fd; + char *fn; + + fn = mktemp_name (t); + if (-1 == (fd = mkstemp (fn))) { LOG_STRERROR_FILE (GNUNET_ERROR_TYPE_ERROR, "mkstemp", fn); GNUNET_free (fn); @@ -515,17 +618,19 @@ GNUNET_DISK_get_blocks_available (const char *part) /** - * Test if "fil" is a directory. - * Will not print an error message if the directory - * does not exist. Will log errors if GNUNET_SYSERR is - * returned (i.e., a file exists with the same name). + * Test if "fil" is a directory and listable. Optionally, also check if the + * directory is readable. Will not print an error message if the directory does + * not exist. Will log errors if GNUNET_SYSERR is returned (i.e., a file exists + * with the same name). * * @param fil filename to test - * @return GNUNET_YES if yes, GNUNET_NO if not, GNUNET_SYSERR if it - * does not exist + * @param is_readable GNUNET_YES to additionally check if "fil" is readable; + * GNUNET_NO to disable this check + * @return GNUNET_YES if yes, GNUNET_NO if not; GNUNET_SYSERR if it + * does not exist or stat'ed */ int -GNUNET_DISK_directory_test (const char *fil) +GNUNET_DISK_directory_test (const char *fil, int is_readable) { struct stat filestat; int ret; @@ -534,18 +639,23 @@ GNUNET_DISK_directory_test (const char *fil) if (ret != 0) { if (errno != ENOENT) - { LOG_STRERROR_FILE (GNUNET_ERROR_TYPE_WARNING, "stat", fil); - return GNUNET_SYSERR; - } - return GNUNET_NO; + return GNUNET_SYSERR; } if (!S_ISDIR (filestat.st_mode)) + { + LOG (GNUNET_ERROR_TYPE_WARNING, + "A file already exits with the same name %s\n", fil); return GNUNET_NO; - if (ACCESS (fil, R_OK | X_OK) < 0) + } + if (GNUNET_YES == is_readable) + ret = ACCESS (fil, R_OK | X_OK); + else + ret = ACCESS (fil, X_OK); + if (ret < 0) { LOG_STRERROR_FILE (GNUNET_ERROR_TYPE_WARNING, "access", fil); - return GNUNET_SYSERR; + return GNUNET_NO; } return GNUNET_YES; } @@ -587,7 +697,7 @@ GNUNET_DISK_file_test (const char *fil) GNUNET_free (rdir); return GNUNET_NO; } - if (ACCESS (rdir, R_OK) < 0) + if (ACCESS (rdir, F_OK) < 0) { LOG_STRERROR_FILE (GNUNET_ERROR_TYPE_WARNING, "access", rdir); GNUNET_free (rdir); @@ -607,8 +717,9 @@ int GNUNET_DISK_directory_create (const char *dir) { char *rdir; - int len; - int pos; + unsigned int len; + unsigned int pos; + unsigned int pos2; int ret = GNUNET_OK; rdir = GNUNET_STRINGS_filename_expand (dir); @@ -638,18 +749,45 @@ GNUNET_DISK_directory_create (const char *dir) pos = 3; /* strlen("C:\\") */ } #endif + /* Check which low level directories already exist */ + pos2 = len; + rdir[len] = DIR_SEPARATOR; + while (pos <= pos2) + { + if (DIR_SEPARATOR == rdir[pos2]) + { + rdir[pos2] = '\0'; + ret = GNUNET_DISK_directory_test (rdir, GNUNET_NO); + if (GNUNET_NO == ret) + { + GNUNET_free (rdir); + return GNUNET_SYSERR; + } + rdir[pos2] = DIR_SEPARATOR; + if (GNUNET_YES == ret) + { + pos2++; + break; + } + } + pos2--; + } + rdir[len] = '\0'; + if (pos < pos2) + pos = pos2; + /* Start creating directories */ while (pos <= len) { if ((rdir[pos] == DIR_SEPARATOR) || (pos == len)) { rdir[pos] = '\0'; - ret = GNUNET_DISK_directory_test (rdir); - if (ret == GNUNET_SYSERR) + ret = GNUNET_DISK_directory_test (rdir, GNUNET_NO); + if (GNUNET_NO == ret) { GNUNET_free (rdir); return GNUNET_SYSERR; } - if (ret == GNUNET_NO) + if (GNUNET_SYSERR == ret) { #ifndef MINGW ret = mkdir (rdir, S_IRUSR | S_IWUSR | S_IXUSR | S_IRGRP | S_IXGRP | S_IROTH | S_IXOTH); /* 755 */ @@ -728,7 +866,7 @@ GNUNET_DISK_file_read (const struct GNUNET_DISK_FileHandle * h, void *result, #ifdef MINGW DWORD bytesRead; - if (h->type != GNUNET_PIPE) + if (h->type != GNUNET_DISK_HANLDE_TYPE_PIPE) { if (!ReadFile (h->h, result, len, &bytesRead, NULL)) { @@ -770,7 +908,8 @@ GNUNET_DISK_file_read (const struct GNUNET_DISK_FileHandle * h, void *result, */ ssize_t GNUNET_DISK_file_read_non_blocking (const struct GNUNET_DISK_FileHandle * h, - void *result, size_t len) + void *result, + size_t len) { if (h == NULL) { @@ -781,7 +920,7 @@ GNUNET_DISK_file_read_non_blocking (const struct GNUNET_DISK_FileHandle * h, #ifdef MINGW DWORD bytesRead; - if (h->type != GNUNET_PIPE) + if (h->type != GNUNET_DISK_HANLDE_TYPE_PIPE) { if (!ReadFile (h->h, result, len, &bytesRead, NULL)) { @@ -818,10 +957,14 @@ GNUNET_DISK_file_read_non_blocking (const struct GNUNET_DISK_FileHandle * h, /* set to non-blocking, read, then set back */ flags = fcntl (h->fd, F_GETFL); if (0 == (flags & O_NONBLOCK)) - fcntl (h->fd, F_SETFL, flags | O_NONBLOCK); + (void) fcntl (h->fd, F_SETFL, flags | O_NONBLOCK); ret = read (h->fd, result, len); if (0 == (flags & O_NONBLOCK)) - fcntl (h->fd, F_SETFL, flags); + { + int eno = errno; + (void) fcntl (h->fd, F_SETFL, flags); + errno = eno; + } return ret; #endif } @@ -871,7 +1014,7 @@ GNUNET_DISK_file_write (const struct GNUNET_DISK_FileHandle * h, #ifdef MINGW DWORD bytesWritten; - if (h->type != GNUNET_PIPE) + if (h->type != GNUNET_DISK_HANLDE_TYPE_PIPE) { if (!WriteFile (h->h, buffer, n, &bytesWritten, NULL)) { @@ -984,10 +1127,10 @@ GNUNET_DISK_file_write_blocking (const struct GNUNET_DISK_FileHandle * h, /* set to blocking, write, then set back */ flags = fcntl (h->fd, F_GETFL); if (0 != (flags & O_NONBLOCK)) - fcntl (h->fd, F_SETFL, flags - O_NONBLOCK); + (void) fcntl (h->fd, F_SETFL, flags - O_NONBLOCK); ret = write (h->fd, buffer, n); if (0 == (flags & O_NONBLOCK)) - fcntl (h->fd, F_SETFL, flags); + (void) fcntl (h->fd, F_SETFL, flags); return ret; #endif } @@ -1274,34 +1417,34 @@ remove_helper (void *unused, const char *fn) * caution. * * - * @param fileName the file to remove + * @param filename the file to remove * @return GNUNET_OK on success, GNUNET_SYSERR on error */ int -GNUNET_DISK_directory_remove (const char *fileName) +GNUNET_DISK_directory_remove (const char *filename) { struct stat istat; - if (0 != LSTAT (fileName, &istat)) + if (0 != LSTAT (filename, &istat)) return GNUNET_NO; /* file may not exist... */ - CHMOD (fileName, S_IWUSR | S_IRUSR | S_IXUSR); - if (UNLINK (fileName) == 0) + (void) CHMOD (filename, S_IWUSR | S_IRUSR | S_IXUSR); + if (UNLINK (filename) == 0) return GNUNET_OK; if ((errno != EISDIR) && /* EISDIR is not sufficient in all cases, e.g. * sticky /tmp directory may result in EPERM on BSD. * So we also explicitly check "isDirectory" */ - (GNUNET_YES != GNUNET_DISK_directory_test (fileName))) + (GNUNET_YES != GNUNET_DISK_directory_test (filename, GNUNET_YES))) { - LOG_STRERROR_FILE (GNUNET_ERROR_TYPE_WARNING, "rmdir", fileName); + LOG_STRERROR_FILE (GNUNET_ERROR_TYPE_WARNING, "rmdir", filename); return GNUNET_SYSERR; } if (GNUNET_SYSERR == - GNUNET_DISK_directory_scan (fileName, &remove_helper, NULL)) + GNUNET_DISK_directory_scan (filename, &remove_helper, NULL)) return GNUNET_SYSERR; - if (0 != RMDIR (fileName)) + if (0 != RMDIR (filename)) { - LOG_STRERROR_FILE (GNUNET_ERROR_TYPE_WARNING, "rmdir", fileName); + LOG_STRERROR_FILE (GNUNET_ERROR_TYPE_WARNING, "rmdir", filename); return GNUNET_SYSERR; } return GNUNET_OK; @@ -1635,9 +1778,12 @@ GNUNET_DISK_file_open (const char *fn, enum GNUNET_DISK_OpenFlags flags, h = INVALID_HANDLE_VALUE; if (h == INVALID_HANDLE_VALUE) { + int err; SetErrnoFromWinError (GetLastError ()); - LOG_STRERROR_FILE (GNUNET_ERROR_TYPE_WARNING, "open", expfn); + err = errno; + LOG_STRERROR_FILE (GNUNET_ERROR_TYPE_INFO, "open", expfn); GNUNET_free (expfn); + errno = err; return NULL; } @@ -1655,7 +1801,7 @@ GNUNET_DISK_file_open (const char *fn, enum GNUNET_DISK_OpenFlags flags, ret = GNUNET_malloc (sizeof (struct GNUNET_DISK_FileHandle)); #ifdef MINGW ret->h = h; - ret->type = GNUNET_DISK_FILE; + ret->type = GNUNET_DISK_HANLDE_TYPE_FILE; #else ret->fd = fd; #endif @@ -1701,6 +1847,57 @@ GNUNET_DISK_file_close (struct GNUNET_DISK_FileHandle *h) } +/** + * Get a handle from a native FD. + * + * @param fd native file descriptor + * @return file handle corresponding to the descriptor + */ +struct GNUNET_DISK_FileHandle * +GNUNET_DISK_get_handle_from_native (FILE *fd) +{ + struct GNUNET_DISK_FileHandle *fh; + int fno; +#if MINGW + intptr_t osfh; +#endif + + fno = fileno (fd); + if (-1 == fno) + return NULL; + +#if MINGW + osfh = _get_osfhandle (fno); + if (INVALID_HANDLE_VALUE == (HANDLE) osfh) + return NULL; +#endif + + fh = GNUNET_malloc (sizeof (struct GNUNET_DISK_FileHandle)); + +#if MINGW + fh->h = (HANDLE) osfh; + /* Assume it to be a pipe. TODO: use some kind of detection + * function to figure out handle type. + * Note that we can't make it overlapped if it isn't already. + * (ReOpenFile() is only available in 2003/Vista). + * The process that opened this file in the first place (usually a parent + * process, if this is stdin/stdout/stderr) must make it overlapped, + * otherwise we're screwed, as selecting on non-overlapped handle + * will block. + */ + fh->type = GNUNET_DISK_HANLDE_TYPE_PIPE; + fh->oOverlapRead = GNUNET_malloc (sizeof (OVERLAPPED)); + fh->oOverlapWrite = GNUNET_malloc (sizeof (OVERLAPPED)); + fh->oOverlapRead->hEvent = CreateEvent (NULL, FALSE, FALSE, NULL); + fh->oOverlapWrite->hEvent = CreateEvent (NULL, FALSE, FALSE, NULL); +#else + fh->fd = fno; +#endif + + return fh; +} + + /** * Construct full path to a file inside of the private * directory used by GNUnet. Also creates the corresponding @@ -1966,7 +2163,8 @@ create_selectable_pipe (PHANDLE read_pipe_ptr, PHANDLE write_pipe_ptr, /* Default to error. */ *read_pipe_ptr = *write_pipe_ptr = INVALID_HANDLE_VALUE; - HANDLE read_pipe = INVALID_HANDLE_VALUE, write_pipe = INVALID_HANDLE_VALUE; + HANDLE read_pipe; + HANDLE write_pipe; /* Ensure that there is enough pipe buffer space for atomic writes. */ if (psize < PIPE_BUF) @@ -2147,8 +2345,8 @@ GNUNET_DISK_pipe (int blocking_read, int blocking_write, int inherit_read, int i CloseHandle (p->fd[1]->h); p->fd[1]->h = tmp_handle; - p->fd[0]->type = GNUNET_PIPE; - p->fd[1]->type = GNUNET_PIPE; + p->fd[0]->type = GNUNET_DISK_HANLDE_TYPE_PIPE; + p->fd[1]->type = GNUNET_DISK_HANLDE_TYPE_PIPE; p->fd[0]->oOverlapRead = GNUNET_malloc (sizeof (OVERLAPPED)); p->fd[0]->oOverlapWrite = GNUNET_malloc (sizeof (OVERLAPPED)); @@ -2250,17 +2448,17 @@ GNUNET_DISK_pipe_from_fd (int blocking_read, int blocking_write, int fd[2]) } #else if (fd[0] >= 0) - p->fd[0]->h = _get_osfhandle (fd[0]); + p->fd[0]->h = (HANDLE) _get_osfhandle (fd[0]); else p->fd[0]->h = INVALID_HANDLE_VALUE; if (fd[1] >= 0) - p->fd[1]->h = _get_osfhandle (fd[1]); + p->fd[1]->h = (HANDLE) _get_osfhandle (fd[1]); else p->fd[1]->h = INVALID_HANDLE_VALUE; if (p->fd[0]->h != INVALID_HANDLE_VALUE) { - p->fd[0]->type = GNUNET_PIPE; + p->fd[0]->type = GNUNET_DISK_HANLDE_TYPE_PIPE; p->fd[0]->oOverlapRead = GNUNET_malloc (sizeof (OVERLAPPED)); p->fd[0]->oOverlapWrite = GNUNET_malloc (sizeof (OVERLAPPED)); p->fd[0]->oOverlapRead->hEvent = CreateEvent (NULL, FALSE, FALSE, NULL); @@ -2269,7 +2467,7 @@ GNUNET_DISK_pipe_from_fd (int blocking_read, int blocking_write, int fd[2]) if (p->fd[1]->h != INVALID_HANDLE_VALUE) { - p->fd[1]->type = GNUNET_PIPE; + p->fd[1]->type = GNUNET_DISK_HANLDE_TYPE_PIPE; p->fd[1]->oOverlapRead = GNUNET_malloc (sizeof (OVERLAPPED)); p->fd[1]->oOverlapWrite = GNUNET_malloc (sizeof (OVERLAPPED)); p->fd[1]->oOverlapRead->hEvent = CreateEvent (NULL, FALSE, FALSE, NULL); diff --git a/src/util/getopt.c b/src/util/getopt.c index 572e534..64e4341 100644 --- a/src/util/getopt.c +++ b/src/util/getopt.c @@ -238,45 +238,7 @@ strlen (const char *); static int first_nonopt; static int last_nonopt; -#ifdef _LIBC -/* Bash 2.0 gives us an environment variable containing flags - indicating ARGV elements that should not be considered arguments. */ - -/* Defined in getopt_init.c */ -extern char *__getopt_nonoption_flags; - -static int nonoption_flags_max_len; -static int nonoption_flags_len; - -static int original_argc; -static char *const *original_argv; - -extern pid_t __libc_pid; - -/* Make sure the environment variable bash 2.0 puts in the environment - is valid for the getopt call we must make sure that the ARGV passed - to getopt is that one passed to the process. */ -static void GNUNET_UNUSED -store_args_and_env (int argc, char *const *argv) -{ - /* XXX This is no good solution. We should rather copy the args so - * that we can compare them later. But we must not use malloc(3). */ - original_argc = argc; - original_argv = argv; -} - -text_set_element (__libc_subinit, store_args_and_env); - -#define SWAP_FLAGS(ch1, ch2) \ - if (nonoption_flags_len > 0) \ - { \ - char __tmp = __getopt_nonoption_flags[ch1]; \ - __getopt_nonoption_flags[ch1] = __getopt_nonoption_flags[ch2]; \ - __getopt_nonoption_flags[ch2] = __tmp; \ - } -#else /* !_LIBC */ #define SWAP_FLAGS(ch1, ch2) -#endif /* _LIBC */ /* Exchange two adjacent subsequences of ARGV. One subsequence is elements [first_nonopt,last_nonopt) @@ -305,29 +267,6 @@ exchange (char **argv) * It leaves the longer segment in the right place overall, * but it consists of two parts that need to be swapped next. */ -#ifdef _LIBC - /* First make sure the handling of the `__getopt_nonoption_flags' - * string can work normally. Our top argument must be in the range - * of the string. */ - if (nonoption_flags_len > 0 && top >= nonoption_flags_max_len) - { - /* We must extend the array. The user plays games with us and - * presents new arguments. */ - char *new_str = malloc (top + 1); - - if (new_str == NULL) - nonoption_flags_len = nonoption_flags_max_len = 0; - else - { - memcpy (new_str, __getopt_nonoption_flags, nonoption_flags_max_len); - memset (&new_str[nonoption_flags_max_len], '\0', - top + 1 - nonoption_flags_max_len); - nonoption_flags_max_len = top + 1; - __getopt_nonoption_flags = new_str; - } - } -#endif - while (top > middle && middle > bottom) { if (top - middle > middle - bottom) @@ -410,41 +349,9 @@ _getopt_initialize (int argc, else ordering = PERMUTE; -#ifdef _LIBC - if (posixly_correct == NULL && argc == original_argc && argv == original_argv) - { - if (nonoption_flags_max_len == 0) - { - if (__getopt_nonoption_flags == NULL || - __getopt_nonoption_flags[0] == '\0') - nonoption_flags_max_len = -1; - else - { - const char *orig_str = __getopt_nonoption_flags; - int len = nonoption_flags_max_len = strlen (orig_str); - - if (nonoption_flags_max_len < argc) - nonoption_flags_max_len = argc; - __getopt_nonoption_flags = (char *) malloc (nonoption_flags_max_len); - if (__getopt_nonoption_flags == NULL) - nonoption_flags_max_len = -1; - else - { - memcpy (__getopt_nonoption_flags, orig_str, len); - memset (&__getopt_nonoption_flags[len], '\0', - nonoption_flags_max_len - len); - } - } - } - nonoption_flags_len = nonoption_flags_max_len; - } - else - nonoption_flags_len = 0; -#endif - return optstring; } - + /* Scan elements of ARGV (whose length is ARGC) for option characters given in OPTSTRING. @@ -523,13 +430,7 @@ GN_getopt_internal (int argc, char *const *argv, const char *optstring, * Either it does not have option syntax, or there is an environment flag * from the shell indicating it is not an option. The later information * is only used when the used in the GNU libc. */ -#ifdef _LIBC -#define NONOPTION_P (argv[GNoptind][0] != '-' || argv[GNoptind][1] == '\0' \ - || (GNoptind < nonoption_flags_len \ - && __getopt_nonoption_flags[GNoptind] == '1')) -#else #define NONOPTION_P (argv[GNoptind][0] != '-' || argv[GNoptind][1] == '\0') -#endif if (nextchar == NULL || *nextchar == '\0') { @@ -866,8 +767,7 @@ GN_getopt_internal (int argc, char *const *argv, const char *optstring, else { if (GNopterr) - FPRINTF (stderr, _("\ -%s: option `-W %s' does not allow an argument\n"), argv[0], pfound->name); + FPRINTF (stderr, _("%s: option `-W %s' does not allow an argument\n"), argv[0], pfound->name); nextchar += strlen (nextchar); return '?'; @@ -1039,8 +939,10 @@ GNUNET_GETOPT_run (const char *binaryOptions, GNUNET_free (shorts); GNUNET_free (long_options); - if (cont == GNUNET_SYSERR) - return GNUNET_SYSERR; + if (cont != GNUNET_OK) + { + return cont; + } return GNoptind; } diff --git a/src/util/getopt_helpers.c b/src/util/getopt_helpers.c index a31080f..5940c3f 100644 --- a/src/util/getopt_helpers.c +++ b/src/util/getopt_helpers.c @@ -26,7 +26,7 @@ #include "platform.h" #include "gnunet_common.h" -#include "gnunet_getopt_lib.h" +#include "gnunet_util_lib.h" #define LOG(kind,...) GNUNET_log_from (kind, "util", __VA_ARGS__) @@ -38,7 +38,7 @@ * @param scls additional closure (points to version string) * @param option name of the option * @param value not used (NULL) - * @return GNUNET_SYSERR (do not continue) + * @return GNUNET_NO (do not continue, not an error) */ int GNUNET_GETOPT_print_version_ (struct GNUNET_GETOPT_CommandLineProcessorContext @@ -48,7 +48,7 @@ GNUNET_GETOPT_print_version_ (struct GNUNET_GETOPT_CommandLineProcessorContext const char *version = scls; printf ("%s v%s\n", ctx->binaryName, version); - return GNUNET_SYSERR; + return GNUNET_NO; } @@ -62,7 +62,7 @@ GNUNET_GETOPT_print_version_ (struct GNUNET_GETOPT_CommandLineProcessorContext * @param scls additional closure (points to about text) * @param option name of the option * @param value not used (NULL) - * @return GNUNET_SYSERR (do not continue) + * @return GNUNET_NO (do not continue, not an error) */ int GNUNET_GETOPT_format_help_ (struct GNUNET_GETOPT_CommandLineProcessorContext @@ -152,7 +152,7 @@ OUTER: printf ("Report bugs to gnunet-developers@gnu.org.\n" "GNUnet home page: http://www.gnu.org/software/gnunet/\n" "General help using GNU software: http://www.gnu.org/gethelp/\n"); - return GNUNET_SYSERR; + return GNUNET_NO; } @@ -212,7 +212,7 @@ GNUNET_GETOPT_set_one (struct GNUNET_GETOPT_CommandLineProcessorContext *ctx, * A pointer to this function should be passed as part of the * 'struct GNUNET_GETOPT_CommandLineOption' array to initialize options * of this type. It should be followed by a pointer to a value of - * type 'char *'. + * type 'char *', which will be allocated with the requested string. * * @param ctx command line processing context * @param scls additional closure (will point to the 'char *', @@ -262,6 +262,36 @@ GNUNET_GETOPT_set_ulong (struct GNUNET_GETOPT_CommandLineProcessorContext *ctx, } +/** + * Set an option of type 'struct GNUNET_TIME_Relative' from the command line. + * A pointer to this function should be passed as part of the + * 'struct GNUNET_GETOPT_CommandLineOption' array to initialize options + * of this type. It should be followed by a pointer to a value of + * type 'struct GNUNET_TIME_Relative'. + * + * @param ctx command line processing context + * @param scls additional closure (will point to the 'struct GNUNET_TIME_Relative') + * @param option name of the option + * @param value actual value of the option as a string. + * @return GNUNET_OK if parsing the value worked + */ +int +GNUNET_GETOPT_set_relative_time (struct GNUNET_GETOPT_CommandLineProcessorContext *ctx, + void *scls, const char *option, const char *value) +{ + struct GNUNET_TIME_Relative *val = scls; + + if (GNUNET_OK != + GNUNET_STRINGS_fancy_time_to_relative (value, + val)) + { + FPRINTF (stderr, _("You must pass relative time to the `%s' option.\n"), option); + return GNUNET_SYSERR; + } + return GNUNET_OK; +} + + /** * Set an option of type 'unsigned int' from the command line. * A pointer to this function should be passed as part of the diff --git a/src/util/gnunet-config.c b/src/util/gnunet-config.c new file mode 100644 index 0000000..e1aa94a --- /dev/null +++ b/src/util/gnunet-config.c @@ -0,0 +1,184 @@ +/* + This file is part of GNUnet. + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @file util/gnunet-config.c + * @brief tool to access and manipulate GNUnet configuration files + * @author Christian Grothoff + */ +#include "platform.h" +#include "gnunet_util_lib.h" + + +/** + * Name of the section + */ +static char *section; + +/** + * Name of the option + */ +static char *option; + +/** + * Value to set + */ +static char *value; + +/** + * Treat option as a filename. + */ +static int is_filename; + +/** + * Return value from 'main'. + */ +static int ret; + + +/** + * Print each option in a given section. + * + * @param cls closure + * @param section name of the section + * @param option name of the option + * @param value value of the option + */ +static void +print_option (void *cls, const char *section, + const char *option, + const char *value) +{ + fprintf (stdout, + "%s = %s\n", option, value); +} + + +/** + * Main function that will be run by the scheduler. + * + * @param cls closure + * @param args remaining command-line arguments + * @param cfgfile name of the configuration file used (for saving, can be NULL!) + * @param cfg configuration + */ +static void +run (void *cls, char *const *args, const char *cfgfile, + const struct GNUNET_CONFIGURATION_Handle *cfg) +{ + struct GNUNET_CONFIGURATION_Handle *out; + + if (NULL == section) + { + fprintf (stderr, _("--section argument is required\n")); + ret = 1; + return; + } + + if (NULL == value) + { + if (NULL == option) + { + GNUNET_CONFIGURATION_iterate_section_values (cfg, section, + &print_option, NULL); + } + else + { + if (is_filename) + { + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_filename (cfg, section, option, &value)) + { + GNUNET_log_config_missing (GNUNET_ERROR_TYPE_ERROR, + section, option); + ret = 3; + return; + } + } + else + { + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_string (cfg, section, option, &value)) + { + GNUNET_log_config_missing (GNUNET_ERROR_TYPE_ERROR, + section, option); + ret = 3; + return; + } + } + fprintf (stdout, "%s\n", value); + } + } + else + { + if (NULL == option) + { + fprintf (stderr, _("--option argument required to set value\n")); + ret = 1; + return; + } + out = GNUNET_CONFIGURATION_dup (cfg); + GNUNET_CONFIGURATION_set_value_string (out, section, option, value); + if (GNUNET_OK != + GNUNET_CONFIGURATION_write (out, cfgfile)) + ret = 2; + GNUNET_CONFIGURATION_destroy (out); + return; + } +} + + +/** + * Program to manipulate configuration files. + * + * @param argc number of arguments from the command line + * @param argv command line arguments + * @return 0 ok, 1 on error + */ +int +main (int argc, char *const *argv) +{ + static const struct GNUNET_GETOPT_CommandLineOption options[] = { + { 'f', "filename", NULL, + gettext_noop ("obtain option of value as a filename (with $-expansion)"), + 0, &GNUNET_GETOPT_set_one, &is_filename }, + { 's', "section", "SECTION", + gettext_noop ("name of the section to access"), + 1, &GNUNET_GETOPT_set_string, §ion }, + { 'o', "option", "OPTION", + gettext_noop ("name of the option to access"), + 1, &GNUNET_GETOPT_set_string, &option }, + { 'V', "value", "VALUE", + gettext_noop ("value to set"), + 1, &GNUNET_GETOPT_set_string, &value }, + GNUNET_GETOPT_OPTION_END + }; + if (GNUNET_OK != GNUNET_STRINGS_get_utf8_args (argc, argv, &argc, &argv)) + return 2; + + ret = (GNUNET_OK == + GNUNET_PROGRAM_run (argc, argv, "gnunet-config [OPTIONS]", + gettext_noop ("Manipulate GNUnet configuration files"), + options, &run, NULL)) ? 0 : ret; + GNUNET_free ((void*) argv); + return ret; +} + +/* end of gnunet-config.c */ diff --git a/src/util/gnunet-ecc.c b/src/util/gnunet-ecc.c new file mode 100644 index 0000000..b19fc19 --- /dev/null +++ b/src/util/gnunet-ecc.c @@ -0,0 +1,249 @@ +/* + This file is part of GNUnet. + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @file util/gnunet-ecc.c + * @brief tool to manipulate ECC key files + * @author Christian Grothoff + */ +#include "platform.h" +#include "gnunet_util_lib.h" +#include "gnunet_testing_lib.h" +#include + + +/** + * Flag for printing public key. + */ +static int print_public_key; + +/** + * Flag for printing hash of public key. + */ +static int print_peer_identity; + +/** + * Flag for printing short hash of public key. + */ +static int print_short_identity; + +/** + * Use weak random number generator for key generation. + */ +static int weak_random; + +/** + * Option set to create a bunch of keys at once. + */ +static unsigned int make_keys; + +/** + * The private information of an ECC key pair. + * NOTE: this must match the definition in crypto_ksk.c and crypto_ecc.c! + */ +struct GNUNET_CRYPTO_EccPrivateKey +{ + gcry_sexp_t sexp; +}; + + +/** + * Create a new private key. Caller must free return value. + * + * @return fresh private key + */ +static struct GNUNET_CRYPTO_EccPrivateKey * +ecc_key_create () +{ + struct GNUNET_CRYPTO_EccPrivateKey *ret; + gcry_sexp_t s_key; + gcry_sexp_t s_keyparam; + + GNUNET_assert (0 == + gcry_sexp_build (&s_keyparam, NULL, + "(genkey(ecc(nbits %d)(ecc-use-e 3:257)))", + 2048)); + GNUNET_assert (0 == gcry_pk_genkey (&s_key, s_keyparam)); + gcry_sexp_release (s_keyparam); +#if EXTRA_CHECKS + GNUNET_assert (0 == gcry_pk_testkey (s_key)); +#endif + ret = GNUNET_malloc (sizeof (struct GNUNET_CRYPTO_EccPrivateKey)); + ret->sexp = s_key; + return ret; +} + + +/** + * Create a flat file with a large number of key pairs for testing. + */ +static void +create_keys (const char *fn) +{ + FILE *f; + struct GNUNET_CRYPTO_EccPrivateKey *pk; + struct GNUNET_CRYPTO_EccPrivateKeyBinaryEncoded *enc; + + if (NULL == (f = fopen (fn, "w+"))) + { + fprintf (stderr, + _("Failed to open `%s': %s\n"), + fn, + STRERROR (errno)); + return; + } + fprintf (stderr, + _("Generating %u keys, please wait"), + make_keys); + while (0 < make_keys--) + { + fprintf (stderr, + "."); + if (NULL == (pk = ecc_key_create ())) + { + GNUNET_break (0); + break; + } + enc = GNUNET_CRYPTO_ecc_encode_key (pk); + if (htons (enc->size) != fwrite (enc, 1, htons (enc->size), f)) + { + fprintf (stderr, + _("\nFailed to write to `%s': %s\n"), + fn, + STRERROR (errno)); + GNUNET_CRYPTO_ecc_key_free (pk); + GNUNET_free (enc); + break; + } + GNUNET_CRYPTO_ecc_key_free (pk); + GNUNET_free (enc); + } + if (0 == make_keys) + fprintf (stderr, + _("Finished!\n")); + fclose (f); +} + + +/** + * Main function that will be run by the scheduler. + * + * @param cls closure + * @param args remaining command-line arguments + * @param cfgfile name of the configuration file used (for saving, can be NULL!) + * @param cfg configuration + */ +static void +run (void *cls, char *const *args, const char *cfgfile, + const struct GNUNET_CONFIGURATION_Handle *cfg) +{ + struct GNUNET_CRYPTO_EccPrivateKey *pk; + struct GNUNET_CRYPTO_EccPublicKeyBinaryEncoded pub; + struct GNUNET_PeerIdentity pid; + + if (NULL == args[0]) + { + fprintf (stderr, _("No hostkey file specified on command line\n")); + return; + } + if (0 != weak_random) + GNUNET_CRYPTO_random_disable_entropy_gathering (); + if (make_keys > 0) + { + create_keys (args[0]); + return; + } + pk = GNUNET_CRYPTO_ecc_key_create_from_file (args[0]); + if (NULL == pk) + return; + if (print_public_key) + { + char *s; + + GNUNET_CRYPTO_ecc_key_get_public (pk, &pub); + s = GNUNET_CRYPTO_ecc_public_key_to_string (&pub); + fprintf (stdout, "%s\n", s); + GNUNET_free (s); + } + if (print_peer_identity) + { + struct GNUNET_CRYPTO_HashAsciiEncoded enc; + + GNUNET_CRYPTO_ecc_key_get_public (pk, &pub); + GNUNET_CRYPTO_hash (&pub, sizeof (pub), &pid.hashPubKey); + GNUNET_CRYPTO_hash_to_enc (&pid.hashPubKey, &enc); + fprintf (stdout, "%s\n", enc.encoding); + } + if (print_short_identity) + { + struct GNUNET_CRYPTO_ShortHashAsciiEncoded enc; + struct GNUNET_CRYPTO_ShortHashCode sh; + + GNUNET_CRYPTO_ecc_key_get_public (pk, &pub); + GNUNET_CRYPTO_short_hash (&pub, sizeof (pub), &sh); + GNUNET_CRYPTO_short_hash_to_enc (&sh, &enc); + fprintf (stdout, "%s\n", enc.short_encoding); + } + GNUNET_CRYPTO_ecc_key_free (pk); +} + + +/** + * Program to manipulate ECC key files. + * + * @param argc number of arguments from the command line + * @param argv command line arguments + * @return 0 ok, 1 on error + */ +int +main (int argc, char *const *argv) +{ + static const struct GNUNET_GETOPT_CommandLineOption options[] = { + { 'g', "generate-keys", "COUNT", + gettext_noop ("create COUNT public-private key pairs (for testing)"), + 1, &GNUNET_GETOPT_set_uint, &make_keys }, + { 'p', "print-public-key", NULL, + gettext_noop ("print the public key in ASCII format"), + 0, &GNUNET_GETOPT_set_one, &print_public_key }, + { 'P', "print-peer-identity", NULL, + gettext_noop ("print the hash of the public key in ASCII format"), + 0, &GNUNET_GETOPT_set_one, &print_peer_identity }, + { 's', "print-short-identity", NULL, + gettext_noop ("print the short hash of the public key in ASCII format"), + 0, &GNUNET_GETOPT_set_one, &print_short_identity }, + { 'w', "weak-random", NULL, + gettext_noop ("use insecure, weak random number generator for key generation (for testing only)"), + 0, &GNUNET_GETOPT_set_one, &weak_random }, + GNUNET_GETOPT_OPTION_END + }; + int ret; + + if (GNUNET_OK != GNUNET_STRINGS_get_utf8_args (argc, argv, &argc, &argv)) + return 2; + + ret = (GNUNET_OK == + GNUNET_PROGRAM_run (argc, argv, "gnunet-ecc [OPTIONS] keyfile", + gettext_noop ("Manipulate GNUnet private ECC key files"), + options, &run, NULL)) ? 0 : 1; + GNUNET_free ((void*) argv); + return ret; +} + +/* end of gnunet-ecc.c */ diff --git a/src/util/gnunet-resolver.c b/src/util/gnunet-resolver.c index 142dd0d..6cb6ac5 100644 --- a/src/util/gnunet-resolver.c +++ b/src/util/gnunet-resolver.c @@ -149,10 +149,17 @@ main (int argc, char *const *argv) 0, &GNUNET_GETOPT_set_one, &reverse }, GNUNET_GETOPT_OPTION_END }; - return (GNUNET_OK == - GNUNET_PROGRAM_run (argc, argv, "gnunet-resolver [hostname]", - gettext_noop ("Use build-in GNUnet stub resolver"), - options, &run, NULL)) ? 0 : 1; + int ret; + + if (GNUNET_OK != GNUNET_STRINGS_get_utf8_args (argc, argv, &argc, &argv)) + return 2; + + ret = (GNUNET_OK == + GNUNET_PROGRAM_run (argc, argv, "gnunet-resolver [hostname]", + gettext_noop ("Use build-in GNUnet stub resolver"), + options, &run, NULL)) ? 0 : 1; + GNUNET_free ((void*) argv); + return ret; } /* end of gnunet-resolver.c */ diff --git a/src/util/gnunet-rsa.c b/src/util/gnunet-rsa.c index f3cd83a..917ee50 100644 --- a/src/util/gnunet-rsa.c +++ b/src/util/gnunet-rsa.c @@ -25,6 +25,8 @@ */ #include "platform.h" #include "gnunet_util_lib.h" +#include "gnunet_testing_lib.h" +#include /** @@ -42,6 +44,112 @@ static int print_peer_identity; */ static int print_short_identity; +/** + * Use weak random number generator for key generation. + */ +static int weak_random; + +/** + * Option set to create a bunch of keys at once. + */ +static unsigned int make_keys; + +/** + * The private information of an RSA key pair. + * NOTE: this must match the definition in crypto_ksk.c and crypto_rsa.c! + */ +struct GNUNET_CRYPTO_RsaPrivateKey +{ + gcry_sexp_t sexp; +}; + + +/** + * Create a new private key. Caller must free return value. + * + * @return fresh private key + */ +static struct GNUNET_CRYPTO_RsaPrivateKey * +rsa_key_create () +{ + struct GNUNET_CRYPTO_RsaPrivateKey *ret; + gcry_sexp_t s_key; + gcry_sexp_t s_keyparam; + + GNUNET_assert (0 == + gcry_sexp_build (&s_keyparam, NULL, + "(genkey(rsa(nbits %d)(rsa-use-e 3:257)))", + 2048)); + GNUNET_assert (0 == gcry_pk_genkey (&s_key, s_keyparam)); + gcry_sexp_release (s_keyparam); +#if EXTRA_CHECKS + GNUNET_assert (0 == gcry_pk_testkey (s_key)); +#endif + ret = GNUNET_malloc (sizeof (struct GNUNET_CRYPTO_RsaPrivateKey)); + ret->sexp = s_key; + return ret; +} + + +/** + * Create a flat file with a large number of key pairs for testing. + */ +static void +create_keys (const char *fn) +{ + FILE *f; + struct GNUNET_CRYPTO_RsaPrivateKey *pk; + struct GNUNET_CRYPTO_RsaPrivateKeyBinaryEncoded *enc; + + if (NULL == (f = fopen (fn, "w+"))) + { + fprintf (stderr, + _("Failed to open `%s': %s\n"), + fn, + STRERROR (errno)); + return; + } + fprintf (stderr, + _("Generating %u keys, please wait"), + make_keys); + while (0 < make_keys--) + { + fprintf (stderr, + "."); + if (NULL == (pk = rsa_key_create ())) + { + GNUNET_break (0); + break; + } + enc = GNUNET_CRYPTO_rsa_encode_key (pk); + if (GNUNET_TESTING_HOSTKEYFILESIZE != htons (enc->len)) + { + /* sometimes we get a different key length because 'd' or 'u' start + with leading bits; skip those... */ + GNUNET_CRYPTO_rsa_key_free (pk); + GNUNET_free (enc); + make_keys++; + continue; + } + if (htons (enc->len) != fwrite (enc, 1, htons (enc->len), f)) + { + fprintf (stderr, + _("\nFailed to write to `%s': %s\n"), + fn, + STRERROR (errno)); + GNUNET_CRYPTO_rsa_key_free (pk); + GNUNET_free (enc); + break; + } + GNUNET_CRYPTO_rsa_key_free (pk); + GNUNET_free (enc); + } + if (0 == make_keys) + fprintf (stderr, + _("Finished!\n")); + fclose (f); +} + /** * Main function that will be run by the scheduler. @@ -64,7 +172,16 @@ run (void *cls, char *const *args, const char *cfgfile, fprintf (stderr, _("No hostkey file specified on command line\n")); return; } + if (0 != weak_random) + GNUNET_CRYPTO_random_disable_entropy_gathering (); + if (make_keys > 0) + { + create_keys (args[0]); + return; + } pk = GNUNET_CRYPTO_rsa_key_create_from_file (args[0]); + if (NULL == pk) + return; if (print_public_key) { char *s; @@ -98,16 +215,19 @@ run (void *cls, char *const *args, const char *cfgfile, /** - * The main function to obtain statistics in GNUnet. + * Program to manipulate RSA key files. * * @param argc number of arguments from the command line * @param argv command line arguments * @return 0 ok, 1 on error */ int -main (int argc, char *const *argv) +main (int argc, char *const*argv) { static const struct GNUNET_GETOPT_CommandLineOption options[] = { + { 'g', "generate-keys", "COUNT", + gettext_noop ("create COUNT public-private key pairs (for testing)"), + 1, &GNUNET_GETOPT_set_uint, &make_keys }, { 'p', "print-public-key", NULL, gettext_noop ("print the public key in ASCII format"), 0, &GNUNET_GETOPT_set_one, &print_public_key }, @@ -117,12 +237,22 @@ main (int argc, char *const *argv) { 's', "print-short-identity", NULL, gettext_noop ("print the short hash of the public key in ASCII format"), 0, &GNUNET_GETOPT_set_one, &print_short_identity }, + { 'w', "weak-random", NULL, + gettext_noop ("use insecure, weak random number generator for key generation (for testing only)"), + 0, &GNUNET_GETOPT_set_one, &weak_random }, GNUNET_GETOPT_OPTION_END }; - return (GNUNET_OK == - GNUNET_PROGRAM_run (argc, argv, "gnunet-rsa [OPTIONS] keyfile", - gettext_noop ("Manipulate GNUnet private RSA key files"), - options, &run, NULL)) ? 0 : 1; + int ret; + + if (GNUNET_OK != GNUNET_STRINGS_get_utf8_args (argc, argv, &argc, &argv)) + return 2; + + ret = (GNUNET_OK == + GNUNET_PROGRAM_run (argc, argv, "gnunet-rsa [OPTIONS] keyfile", + gettext_noop ("Manipulate GNUnet private RSA key files"), + options, &run, NULL)) ? 0 : 1; + GNUNET_free ((void*) argv); + return ret; } /* end of gnunet-rsa.c */ diff --git a/src/util/gnunet-service-resolver.c b/src/util/gnunet-service-resolver.c index 97eba6d..507ecf6 100644 --- a/src/util/gnunet-service-resolver.c +++ b/src/util/gnunet-service-resolver.c @@ -577,4 +577,19 @@ main (int argc, char *const *argv) return ret; } +#ifdef LINUX +#include + +/** + * MINIMIZE heap size (way below 128k) since this process doesn't need much. + */ +void __attribute__ ((constructor)) GNUNET_ARM_memory_init () +{ + mallopt (M_TRIM_THRESHOLD, 4 * 1024); + mallopt (M_TOP_PAD, 1 * 1024); + malloc_trim (0); +} +#endif + + /* end of gnunet-service-resolver.c */ diff --git a/src/util/gnunet-uri.c b/src/util/gnunet-uri.c new file mode 100644 index 0000000..5ca1f4e --- /dev/null +++ b/src/util/gnunet-uri.c @@ -0,0 +1,184 @@ +/* + This file is part of GNUnet. + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @file util/gnunet-uri.c + * @brief tool to dispatch URIs to the appropriate GNUnet helper process + * @author Christian Grothoff + */ +#include "platform.h" +#include "gnunet_util_lib.h" + + +/** + * Global return value. + */ +static int ret = 1; + +/** + * Helper process we started. + */ +static struct GNUNET_OS_Process *p; + +/** + * Pipe used to communicate shutdown via signal. + */ +static struct GNUNET_DISK_PipeHandle *sigpipe; + + +/** + * Task triggered whenever we receive a SIGCHLD (child + * process died) or when user presses CTRL-C. + * + * @param cls closure, NULL + * @param tc scheduler context + */ +static void +maint_child_death (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + enum GNUNET_OS_ProcessStatusType type; + unsigned long code; + + if ( (GNUNET_OK == + GNUNET_OS_process_status (p, &type, &code)) && + (type == GNUNET_OS_PROCESS_EXITED) && + (0 == code) ) + ret = 0; + else + GNUNET_break (0 == GNUNET_OS_process_kill (p, SIGTERM)); + GNUNET_OS_process_destroy (p); +} + + +/** + * Main function that will be run by the scheduler. + * + * @param cls closure + * @param args remaining command-line arguments + * @param cfgfile name of the configuration file used (for saving, can be NULL!) + * @param cfg configuration + */ +static void +run (void *cls, char *const *args, const char *cfgfile, + const struct GNUNET_CONFIGURATION_Handle *cfg) +{ + const char *uri; + const char *slash; + char *subsystem; + char *program; + GNUNET_SCHEDULER_TaskIdentifier rt; + + if (NULL == (uri = args[0])) + { + fprintf (stderr, _("No URI specified on command line\n")); + return; + } + if (0 != strncasecmp ("gnunet://", uri, strlen ("gnunet://"))) + { + fprintf (stderr, _("Invalid URI: does not start with `%s'\n"), + "gnunet://"); + return; + } + uri += strlen ("gnunet://"); + if (NULL == (slash = strchr (uri, '/'))) + { + fprintf (stderr, _("Invalid URI: fails to specify subsystem\n")); + return; + } + subsystem = GNUNET_strndup (uri, slash - uri); + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_string (cfg, + "uri", + subsystem, + &program)) + { + fprintf (stderr, _("No handler known for subsystem `%s'\n"), subsystem); + GNUNET_free (subsystem); + return; + } + GNUNET_free (subsystem); + rt = GNUNET_SCHEDULER_add_read_file (GNUNET_TIME_UNIT_FOREVER_REL, + GNUNET_DISK_pipe_handle (sigpipe, + GNUNET_DISK_PIPE_END_READ), + &maint_child_death, NULL); + p = GNUNET_OS_start_process (GNUNET_NO, 0, + NULL, NULL, + program, + program, + args[0], + NULL); + GNUNET_free (program); + if (NULL == p) + GNUNET_SCHEDULER_cancel (rt); +} + + +/** + * Signal handler called for SIGCHLD. Triggers the + * respective handler by writing to the trigger pipe. + */ +static void +sighandler_child_death () +{ + static char c; + int old_errno = errno; /* back-up errno */ + + GNUNET_break (1 == + GNUNET_DISK_file_write (GNUNET_DISK_pipe_handle + (sigpipe, GNUNET_DISK_PIPE_END_WRITE), + &c, sizeof (c))); + errno = old_errno; /* restore errno */ +} + + +/** + * The main function to handle gnunet://-URIs. + * + * @param argc number of arguments from the command line + * @param argv command line arguments + * @return 0 ok, 1 on error + */ +int +main (int argc, char *const *argv) +{ + static const struct GNUNET_GETOPT_CommandLineOption options[] = { + GNUNET_GETOPT_OPTION_END + }; + struct GNUNET_SIGNAL_Context *shc_chld; + int ret; + + if (GNUNET_OK != GNUNET_STRINGS_get_utf8_args (argc, argv, &argc, &argv)) + return 2; + sigpipe = GNUNET_DISK_pipe (GNUNET_NO, GNUNET_NO, GNUNET_NO, GNUNET_NO); + GNUNET_assert (sigpipe != NULL); + shc_chld = + GNUNET_SIGNAL_handler_install (GNUNET_SIGCHLD, &sighandler_child_death); + ret = GNUNET_PROGRAM_run (argc, argv, "gnunet-uri URI", + gettext_noop ("Perform default-actions for GNUnet URIs"), + options, &run, NULL); + GNUNET_SIGNAL_handler_uninstall (shc_chld); + shc_chld = NULL; + GNUNET_DISK_pipe_close (sigpipe); + sigpipe = NULL; + GNUNET_free ((void *) argv); + return (GNUNET_OK == ret) ? 0 : 1; +} + +/* end of gnunet-uri.c */ diff --git a/src/util/helper.c b/src/util/helper.c index 6a84ff3..0810fe1 100644 --- a/src/util/helper.c +++ b/src/util/helper.c @@ -108,6 +108,16 @@ struct GNUNET_HELPER_Handle */ struct GNUNET_SERVER_MessageStreamTokenizer *mst; + /** + * The exception callback + */ + GNUNET_HELPER_ExceptionCallback exp_cb; + + /** + * The closure for callbacks + */ + void *cb_cls; + /** * First message queued for transmission to helper. */ @@ -121,12 +131,12 @@ struct GNUNET_HELPER_Handle /** * Binary to run. */ - const char *binary_name; + char *binary_name; /** * NULL-terminated list of command-line arguments. */ - char *const *binary_argv; + char **binary_argv; /** * Task to read from the helper. @@ -142,6 +152,12 @@ struct GNUNET_HELPER_Handle * Restart task. */ GNUNET_SCHEDULER_TaskIdentifier restart_task; + + /** + * Does the helper support the use of a control pipe for signalling? + */ + int with_control_pipe; + }; @@ -244,20 +260,31 @@ helper_read (void *cls, _("Error reading from `%s': %s\n"), h->binary_name, STRERROR (errno)); + if (NULL != h->exp_cb) + { + h->exp_cb (h->cb_cls); + GNUNET_HELPER_stop (h); + return; + } stop_helper (h); /* Restart the helper */ h->restart_task = - GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_SECONDS, - &restart_task, h); + GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_SECONDS, &restart_task, h); return; } if (0 == t) { /* this happens if the helper is shut down via a signal, so it is not a "hard" error */ - GNUNET_log (GNUNET_ERROR_TYPE_INFO, - _("Got 0 bytes from helper `%s' (EOF)\n"), + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Got 0 bytes from helper `%s' (EOF)\n", h->binary_name); + if (NULL != h->exp_cb) + { + h->exp_cb (h->cb_cls); + GNUNET_HELPER_stop (h); + return; + } stop_helper (h); /* Restart the helper */ h->restart_task = @@ -265,8 +292,8 @@ helper_read (void *cls, &restart_task, h); return; } - GNUNET_log (GNUNET_ERROR_TYPE_INFO, - _("Got %u bytes from helper `%s'\n"), + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Got %u bytes from helper `%s'\n", (unsigned int) t, h->binary_name); h->read_task = GNUNET_SCHEDULER_add_read_file (GNUNET_TIME_UNIT_FOREVER_REL, @@ -277,6 +304,12 @@ helper_read (void *cls, GNUNET_log (GNUNET_ERROR_TYPE_WARNING, _("Failed to parse inbound message from helper `%s'\n"), h->binary_name); + if (NULL != h->exp_cb) + { + h->exp_cb (h->cb_cls); + GNUNET_HELPER_stop (h); + return; + } stop_helper (h); /* Restart the helper */ h->restart_task = @@ -306,18 +339,18 @@ start_helper (struct GNUNET_HELPER_Handle *h) &restart_task, h); return; } - GNUNET_log (GNUNET_ERROR_TYPE_INFO, - _("Starting HELPER process `%s'\n"), + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Starting HELPER process `%s'\n", h->binary_name); h->fh_from_helper = GNUNET_DISK_pipe_handle (h->helper_out, GNUNET_DISK_PIPE_END_READ); h->fh_to_helper = GNUNET_DISK_pipe_handle (h->helper_in, GNUNET_DISK_PIPE_END_WRITE); h->helper_proc = - GNUNET_OS_start_process_vap (GNUNET_NO, - h->helper_in, h->helper_out, - h->binary_name, - h->binary_argv); + GNUNET_OS_start_process_vap (h->with_control_pipe, GNUNET_OS_INHERIT_STD_ERR, + h->helper_in, h->helper_out, + h->binary_name, + h->binary_argv); if (NULL == h->helper_proc) { /* failed to start process? try again later... */ @@ -354,27 +387,47 @@ restart_task (void *cls, /** - * @brief Starts a helper and begins reading from it + * Starts a helper and begins reading from it. The helper process is + * restarted when it dies except when it is stopped using GNUNET_HELPER_stop() + * or when the exp_cb callback is not NULL. * + * @param with_control_pipe does the helper support the use of a control pipe for signalling? * @param binary_name name of the binary to run * @param binary_argv NULL-terminated list of arguments to give when starting the binary (this * argument must not be modified by the client for - * the lifetime of the helper h) + * the lifetime of the helper handle) * @param cb function to call if we get messages from the helper - * @param cb_cls Closure for the callback - * @return the new H, NULL on error + * @param exp_cb the exception callback to call. Set this to NULL if the helper + * process has to be restarted automatically when it dies/crashes + * @param cb_cls closure for the above callback + * @return the new Handle, NULL on error */ -struct GNUNET_HELPER_Handle* -GNUNET_HELPER_start (const char *binary_name, +struct GNUNET_HELPER_Handle * +GNUNET_HELPER_start (int with_control_pipe, + const char *binary_name, char *const binary_argv[], - GNUNET_SERVER_MessageTokenizerCallback cb, void *cb_cls) + GNUNET_SERVER_MessageTokenizerCallback cb, + GNUNET_HELPER_ExceptionCallback exp_cb, + void *cb_cls) { - struct GNUNET_HELPER_Handle*h; - - h = GNUNET_malloc (sizeof (struct GNUNET_HELPER_Handle)); - h->binary_name = binary_name; - h->binary_argv = binary_argv; - h->mst = GNUNET_SERVER_mst_create (cb, cb_cls); + struct GNUNET_HELPER_Handle *h; + unsigned int c; + + h = GNUNET_malloc (sizeof (struct GNUNET_HELPER_Handle)); + h->with_control_pipe = with_control_pipe; + /* Lookup in libexec path only if we are starting gnunet helpers */ + if (NULL != strstr (binary_name, "gnunet")) + h->binary_name = GNUNET_OS_get_libexec_binary_path (binary_name); + else + h->binary_name = strdup (binary_name); + for (c = 0; NULL != binary_argv[c]; c++); + h->binary_argv = GNUNET_malloc (sizeof (char *) * (c + 1)); + for (c = 0; NULL != binary_argv[c]; c++) + h->binary_argv[c] = GNUNET_strdup (binary_argv[c]); + h->binary_argv[c] = NULL; + h->cb_cls = cb_cls; + h->mst = GNUNET_SERVER_mst_create (cb, h->cb_cls); + h->exp_cb = exp_cb; start_helper (h); return h; } @@ -389,7 +442,9 @@ void GNUNET_HELPER_stop (struct GNUNET_HELPER_Handle *h) { struct GNUNET_HELPER_SendHandle *sh; + unsigned int c; + h->exp_cb = NULL; /* signal pending writes that we were stopped */ while (NULL != (sh = h->sh_head)) { @@ -402,6 +457,10 @@ GNUNET_HELPER_stop (struct GNUNET_HELPER_Handle *h) } stop_helper (h); GNUNET_SERVER_mst_destroy (h->mst); + GNUNET_free (h->binary_name); + for (c = 0; h->binary_argv[c] != NULL; c++) + GNUNET_free (h->binary_argv[c]); + GNUNET_free (h->binary_argv); GNUNET_free (h); } @@ -440,6 +499,12 @@ helper_write (void *cls, _("Error writing to `%s': %s\n"), h->binary_name, STRERROR (errno)); + if (NULL != h->exp_cb) + { + h->exp_cb (h->cb_cls); + GNUNET_HELPER_stop (h); + return; + } stop_helper (h); /* Restart the helper */ h->restart_task = diff --git a/src/util/network.c b/src/util/network.c index 972f938..bea6bfb 100644 --- a/src/util/network.c +++ b/src/util/network.c @@ -22,12 +22,11 @@ * @file util/network.c * @brief basic, low-level networking interface * @author Nils Durner + * @author Christian Grothoff */ - #include "platform.h" -#include "gnunet_disk_lib.h" #include "disk.h" -#include "gnunet_container_lib.h" +#include "gnunet_util_lib.h" #define LOG(kind,...) GNUNET_log_from (kind, "util", __VA_ARGS__) #define LOG_STRERROR_FILE(kind,syscall,filename) GNUNET_log_from_strerror_file (kind, "util", syscall, filename) @@ -67,6 +66,77 @@ struct GNUNET_NETWORK_Handle }; +/** + * Test if the given protocol family is supported by this system. + * + * @param pf protocol family to test (PF_INET, PF_INET6, PF_UNIX) + * @return GNUNET_OK if the PF is supported + */ +int +GNUNET_NETWORK_test_pf (int pf) +{ + int s; + + s = socket (pf, SOCK_STREAM, 0); + if (-1 == s) + { + if (EAFNOSUPPORT == errno) + return GNUNET_NO; + fprintf (stderr, "Failed to create test socket: %s\n", STRERROR (errno)); + return GNUNET_SYSERR; + } +#if WINDOWS + closesocket (s); +#else + close (s); +#endif + return GNUNET_OK; +} + + +/** + * Given a unixpath that is too long (larger than UNIX_PATH_MAX), + * shorten it to an acceptable length while keeping it unique + * and making sure it remains a valid filename (if possible). + * + * @param unixpath long path, will be freed (or same pointer returned + * with moved 0-termination). + * @return shortened unixpath, NULL on error + */ +char * +GNUNET_NETWORK_shorten_unixpath (char *unixpath) +{ + struct sockaddr_un dummy; + size_t slen; + char *end; + struct GNUNET_CRYPTO_ShortHashCode sh; + struct GNUNET_CRYPTO_ShortHashAsciiEncoded ae; + size_t upm; + + upm = sizeof (dummy.sun_path); + slen = strlen (unixpath); + if (slen < upm) + return unixpath; /* no shortening required */ + GNUNET_CRYPTO_short_hash (unixpath, slen, &sh); + while (sizeof (struct GNUNET_CRYPTO_ShortHashAsciiEncoded) + + strlen (unixpath) >= upm) + { + if (NULL == (end = strrchr (unixpath, '/'))) + { + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Unable to shorten unix path `%s' while keeping name unique\n"), + unixpath); + GNUNET_free (unixpath); + return NULL; + } + *end = '\0'; + } + GNUNET_CRYPTO_short_hash_to_enc (&sh, &ae); + strcat (unixpath, (char*) ae.short_encoding); + return unixpath; +} + + #ifndef FD_COPY #define FD_COPY(s, d) (memcpy ((d), (s), sizeof (fd_set))) #endif @@ -74,12 +144,13 @@ struct GNUNET_NETWORK_Handle /** * Set if a socket should use blocking or non-blocking IO. + * * @param fd socket * @param doBlock blocking mode * @return GNUNET_OK on success, GNUNET_SYSERR on error */ -static int -socket_set_blocking (struct GNUNET_NETWORK_Handle *fd, int doBlock) +int +GNUNET_NETWORK_socket_set_blocking (struct GNUNET_NETWORK_Handle *fd, int doBlock) { #if MINGW @@ -121,7 +192,6 @@ socket_set_blocking (struct GNUNET_NETWORK_Handle *fd, int doBlock) } -#ifndef MINGW /** * Make a socket non-inheritable to child processes * @@ -132,8 +202,8 @@ socket_set_blocking (struct GNUNET_NETWORK_Handle *fd, int doBlock) static int socket_set_inheritable (const struct GNUNET_NETWORK_Handle *h) { +#ifndef MINGW int i; - i = fcntl (h->fd, F_GETFD); if (i < 0) return GNUNET_SYSERR; @@ -142,9 +212,18 @@ socket_set_inheritable (const struct GNUNET_NETWORK_Handle *h) i |= FD_CLOEXEC; if (fcntl (h->fd, F_SETFD, i) < 0) return GNUNET_SYSERR; +#else + BOOL b; + SetLastError (0); + b = SetHandleInformation (h->fd, HANDLE_FLAG_INHERIT, 0); + if (!b) + { + SetErrnoFromWinsockError (WSAGetLastError ()); + return GNUNET_SYSERR; + } +#endif return GNUNET_OK; } -#endif #ifdef DARWIN @@ -224,11 +303,12 @@ initialize_network_handle (struct GNUNET_NETWORK_Handle *h, errno = EMFILE; return GNUNET_SYSERR; } +#endif if (GNUNET_OK != socket_set_inheritable (h)) LOG_STRERROR (GNUNET_ERROR_TYPE_ERROR | GNUNET_ERROR_TYPE_BULK, "socket_set_inheritable"); -#endif - if (GNUNET_SYSERR == socket_set_blocking (h, GNUNET_NO)) + + if (GNUNET_SYSERR == GNUNET_NETWORK_socket_set_blocking (h, GNUNET_NO)) { GNUNET_break (0); GNUNET_break (GNUNET_OK == GNUNET_NETWORK_socket_close (h)); @@ -817,6 +897,7 @@ void GNUNET_NETWORK_fdset_add (struct GNUNET_NETWORK_FDSet *dst, const struct GNUNET_NETWORK_FDSet *src) { +#ifndef MINGW int nfds; for (nfds = src->nsds; nfds > 0; nfds--) @@ -827,7 +908,18 @@ GNUNET_NETWORK_fdset_add (struct GNUNET_NETWORK_FDSet *dst, if (nfds + 1 > dst->nsds) dst->nsds = nfds + 1; } -#ifdef MINGW +#else + /* This is MinGW32-specific implementation that relies on the code that + * winsock2.h defines for FD_SET. Namely, it relies on FD_SET checking + * that fd being added is not already in the set. + * Also relies on us knowing what's inside fd_set (fd_count and fd_array). + */ + int i; + for (i = 0; i < src->sds.fd_count; i++) + FD_SET (src->sds.fd_array[i], &dst->sds); + if (src->nsds > dst->nsds) + dst->nsds = src->nsds; + GNUNET_CONTAINER_slist_append (dst->handles, src->handles); #endif } @@ -1087,13 +1179,47 @@ GNUNET_NETWORK_fdset_destroy (struct GNUNET_NETWORK_FDSet *fds) GNUNET_free (fds); } +#if MINGW +struct _select_params +{ + fd_set *r; + fd_set *w; + fd_set *e; + struct timeval *tv; + HANDLE wakeup; + HANDLE standby; + SOCKET wakeup_socket; + int status; +}; + +static DWORD WINAPI +_selector (LPVOID p) +{ + struct _select_params *sp = p; + int i; + while (1) + { + WaitForSingleObject (sp->standby, INFINITE); + ResetEvent (sp->standby); + sp->status = select (1, sp->r, sp->w, sp->e, sp->tv); + if (FD_ISSET (sp->wakeup_socket, sp->r)) + { + FD_CLR (sp->wakeup_socket, sp->r); + sp->status -= 1; + } + SetEvent (sp->wakeup); + } + return 0; +} +#endif + /** - * Check if sockets meet certain conditions - * @param rfds set of sockets to be checked for readability - * @param wfds set of sockets to be checked for writability - * @param efds set of sockets to be checked for exceptions + * Check if sockets or pipes meet certain conditions + * @param rfds set of sockets or pipes to be checked for readability + * @param wfds set of sockets or pipes to be checked for writability + * @param efds set of sockets or pipes to be checked for exceptions * @param timeout relative value when to return - * @return number of selected sockets, GNUNET_SYSERR on error + * @return number of selected sockets or pipes, GNUNET_SYSERR on error */ int GNUNET_NETWORK_socket_select (struct GNUNET_NETWORK_FDSet *rfds, @@ -1112,28 +1238,32 @@ GNUNET_NETWORK_socket_select (struct GNUNET_NETWORK_FDSet *rfds, int retcode = 0; DWORD ms_total = 0; - int nsock = 0; int nhandles = 0; - int nSockEvents = 0; - static HANDLE hEventRead = 0; - static HANDLE hEventWrite = 0; - static HANDLE hEventException = 0; static HANDLE hEventPipeWrite = 0; static HANDLE hEventReadReady = 0; + static struct _select_params sp; + static HANDLE select_thread = NULL; + static HANDLE select_finished_event = NULL; + static HANDLE select_standby_event = NULL; + static SOCKET select_wakeup_socket = -1; + static SOCKET select_send_socket = -1; + static struct timeval select_timeout; + int readPipes = 0; int writePipePos = 0; HANDLE handle_array[FD_SETSIZE + 2]; int returncode = -1; - DWORD newretcode = 0; int returnedpos = 0; struct GNUNET_CONTAINER_SList *handles_read; struct GNUNET_CONTAINER_SList *handles_write; struct GNUNET_CONTAINER_SList *handles_except; + int selectret = 0; + fd_set aread; fd_set awrite; fd_set aexcept; @@ -1195,11 +1325,11 @@ GNUNET_NETWORK_socket_select (struct GNUNET_NETWORK_FDSet *rfds, #endif ) { + GNUNET_break (0); LOG (GNUNET_ERROR_TYPE_ERROR, _ ("Fatal internal logic error, process hangs in `%s' (abort with CTRL-C)!\n"), "select"); - GNUNET_break (0); } #ifndef MINGW tv.tv_sec = timeout.rel_value / GNUNET_TIME_UNIT_SECONDS.rel_value; @@ -1218,7 +1348,14 @@ GNUNET_NETWORK_socket_select (struct GNUNET_NETWORK_FDSet *rfds, if (timeout.rel_value == GNUNET_TIME_UNIT_FOREVER_REL.rel_value) ms_total = INFINITE; else + { ms_total = timeout.rel_value / GNUNET_TIME_UNIT_MILLISECONDS.rel_value; + if (timeout.rel_value / GNUNET_TIME_UNIT_MILLISECONDS.rel_value > 0xFFFFFFFFLL - 1) + { + GNUNET_break (0); + ms_total = 0xFFFFFFFF - 1; + } + } /* select() may be used as a portable way to sleep */ if (!(rfds || wfds || efds)) { @@ -1226,31 +1363,244 @@ GNUNET_NETWORK_socket_select (struct GNUNET_NETWORK_FDSet *rfds, return 0; } - /* Events for sockets */ - if (!hEventRead) - hEventRead = CreateEvent (NULL, TRUE, FALSE, NULL); + if (select_thread == NULL) + { + SOCKET select_listening_socket = -1; + struct sockaddr_in s_in; + int alen; + int res; + unsigned long p; + + select_standby_event = CreateEvent (NULL, TRUE, FALSE, NULL); + select_finished_event = CreateEvent (NULL, TRUE, FALSE, NULL); + + select_wakeup_socket = WSASocket (AF_INET, SOCK_STREAM, IPPROTO_TCP, NULL, 0, WSA_FLAG_OVERLAPPED); + + select_listening_socket = WSASocket (AF_INET, SOCK_STREAM, IPPROTO_TCP, NULL, 0, WSA_FLAG_OVERLAPPED); + + p = 1; + res = ioctlsocket (select_wakeup_socket, FIONBIO, &p); + + alen = sizeof (s_in); + s_in.sin_family = AF_INET; + s_in.sin_port = 0; + s_in.sin_addr.S_un.S_un_b.s_b1 = 127; + s_in.sin_addr.S_un.S_un_b.s_b2 = 0; + s_in.sin_addr.S_un.S_un_b.s_b3 = 0; + s_in.sin_addr.S_un.S_un_b.s_b4 = 1; + res = bind (select_listening_socket, (const struct sockaddr *) &s_in, sizeof (s_in)); + + res = getsockname (select_listening_socket, (struct sockaddr *) &s_in, &alen); + + res = listen (select_listening_socket, SOMAXCONN); + + res = connect (select_wakeup_socket, (const struct sockaddr *) &s_in, sizeof (s_in)); + + select_send_socket = accept (select_listening_socket, (struct sockaddr *) &s_in, &alen); + + closesocket (select_listening_socket); + + sp.wakeup = select_finished_event; + sp.standby = select_standby_event; + sp.wakeup_socket = select_wakeup_socket; + + select_thread = CreateThread (NULL, 0, _selector, &sp, 0, NULL); + } + + + handles_read = GNUNET_CONTAINER_slist_create (); + handles_write = GNUNET_CONTAINER_slist_create (); + handles_except = GNUNET_CONTAINER_slist_create (); + FD_ZERO (&aread); + FD_ZERO (&awrite); + FD_ZERO (&aexcept); +#if DEBUG_NETWORK + FD_ZERO (&bread); + FD_ZERO (&bwrite); + FD_ZERO (&bexcept); +#endif + if (rfds) + { + FD_COPY (&rfds->sds, &aread); +#if DEBUG_NETWORK + FD_COPY (&rfds->sds, &bread); +#endif + } + if (wfds) + { + FD_COPY (&wfds->sds, &awrite); +#if DEBUG_NETWORK + FD_COPY (&wfds->sds, &bwrite); +#endif + } + if (efds) + { + FD_COPY (&efds->sds, &aexcept); +#if DEBUG_NETWORK + FD_COPY (&efds->sds, &bexcept); +#endif + } + + /* Start by doing a fast check on sockets and pipes (without waiting). It is cheap, and is sufficient most of the time. + By profiling we detected that to be true in 90% of the cases. + */ + + /* Do the select now */ + select_timeout.tv_sec = 0; + select_timeout.tv_usec = 0; + + /* Copy all the writes to the except, so we can detect connect() errors */ + for (i = 0; i < awrite.fd_count; i++) + FD_SET (awrite.fd_array[i], &aexcept); + if (aread.fd_count > 0 || awrite.fd_count > 0 || aexcept.fd_count > 0) + selectret = select (1, (rfds != NULL) ? &aread : NULL, + (wfds != NULL) ? &awrite : NULL, &aexcept, &select_timeout); else - ResetEvent (hEventRead); + selectret = 0; + if (selectret == -1) + { + /* Throw an error early on, while we still have the context. */ + LOG (GNUNET_ERROR_TYPE_ERROR, "W32 select(%d, %d, %d) failed: %lu\n", + rfds ? aread.fd_count : 0, wfds ? awrite.fd_count : 0, aexcept.fd_count, GetLastError ()); + GNUNET_abort (); + } + + /* Check aexcept, add its contents to awrite + This is technically wrong (aexcept might have its own descriptors), we should + have checked that descriptors were in awrite originally before re-adding them from + aexcept. Luckily, GNUnet never uses aexcept for anything, so this does not become a problem (yet). */ + for (i = 0; i < aexcept.fd_count; i++) + FD_SET (aexcept.fd_array[i], &awrite); + + /* If our select returned something or is a 0-timed request, then also check the pipes and get out of here! */ + /* Sadly, it means code duplication :( */ + if ((selectret > 0) || (ms_total == 0)) + { + /* Read Pipes */ + if (rfds && read_handles) + { + struct GNUNET_CONTAINER_SList_Iterator i; + + for (i = GNUNET_CONTAINER_slist_begin (rfds->handles); + GNUNET_CONTAINER_slist_end (&i) != GNUNET_YES; + GNUNET_CONTAINER_slist_next (&i)) + { + struct GNUNET_DISK_FileHandle *fh; + + fh = (struct GNUNET_DISK_FileHandle *) GNUNET_CONTAINER_slist_get (&i,NULL); + if (fh->type == GNUNET_DISK_HANLDE_TYPE_PIPE) + { + DWORD error; + BOOL bret; + + SetLastError (0); + DWORD waitstatus = 0; + bret = PeekNamedPipe (fh->h, NULL, 0, NULL, &waitstatus, NULL); + error = GetLastError (); + LOG (GNUNET_ERROR_TYPE_DEBUG, "Peek at read pipe %d (0x%x) returned %d (%d bytes available) GLE %u\n", + i, fh->h, bret, waitstatus, error); + if (bret == 0) + { + /* TODO: either add more errors to this condition, or eliminate it + * entirely (failed to peek -> pipe is in serious trouble, should + * be selected as readable). + */ + if (error != ERROR_BROKEN_PIPE && error != ERROR_INVALID_HANDLE) + continue; + } + else if (waitstatus <= 0) + continue; + GNUNET_CONTAINER_slist_add (handles_read, GNUNET_CONTAINER_SLIST_DISPOSITION_TRANSIENT, + fh, sizeof (struct GNUNET_DISK_FileHandle)); + retcode++; + LOG (GNUNET_ERROR_TYPE_DEBUG, "Added read Pipe 0x%x (0x%x)\n", + fh, fh->h); + } + else + { + GNUNET_CONTAINER_slist_add (handles_read, GNUNET_CONTAINER_SLIST_DISPOSITION_TRANSIENT, + fh, sizeof (struct GNUNET_DISK_FileHandle)); + retcode++; + } + } + } + if (wfds && write_handles) + { + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Adding the write ready event to the array as %d\n", nhandles); + GNUNET_CONTAINER_slist_append (handles_write, wfds->handles); + retcode += write_handles; + } + if (efds && ex_handles) + { + struct GNUNET_CONTAINER_SList_Iterator i; + + for (i = GNUNET_CONTAINER_slist_begin (efds->handles); + GNUNET_CONTAINER_slist_end (&i) != GNUNET_YES; + GNUNET_CONTAINER_slist_next (&i)) + { + struct GNUNET_DISK_FileHandle *fh; + DWORD dwBytes; + + fh = (struct GNUNET_DISK_FileHandle *) GNUNET_CONTAINER_slist_get (&i, NULL); + if (fh->type == GNUNET_DISK_HANLDE_TYPE_PIPE) + { + if (PeekNamedPipe (fh->h, NULL, 0, NULL, &dwBytes, NULL)) + continue; + GNUNET_CONTAINER_slist_add (handles_except, GNUNET_CONTAINER_SLIST_DISPOSITION_TRANSIENT, + fh, sizeof (struct GNUNET_DISK_FileHandle)); + retcode++; + } + } + } + + /* Add our select() result.*/ + if (selectret >= 0) + retcode += selectret; + + if (rfds) + { + GNUNET_NETWORK_fdset_zero (rfds); + if (selectret != -1) + GNUNET_NETWORK_fdset_copy_native (rfds, &aread, selectret); + GNUNET_CONTAINER_slist_append (rfds->handles, handles_read); + } + if (wfds) + { + GNUNET_NETWORK_fdset_zero (wfds); + if (selectret != -1) + GNUNET_NETWORK_fdset_copy_native (wfds, &awrite, selectret); + GNUNET_CONTAINER_slist_append (wfds->handles, handles_write); + } + if (efds) + { + GNUNET_NETWORK_fdset_zero (efds); + if (selectret != -1) + GNUNET_NETWORK_fdset_copy_native (efds, &aexcept, selectret); + GNUNET_CONTAINER_slist_append (efds->handles, handles_except); + } + GNUNET_CONTAINER_slist_destroy (handles_read); + GNUNET_CONTAINER_slist_destroy (handles_write); + GNUNET_CONTAINER_slist_destroy (handles_except); + + if (selectret == -1) + return -1; + return retcode; + } + + /* If we got this far, use slower implementation that is able to do a waiting select + on both sockets and pipes simultaneously */ + + /* Events for pipes */ if (!hEventReadReady) hEventReadReady = CreateEvent (NULL, TRUE, TRUE, NULL); - if (!hEventWrite) - hEventWrite = CreateEvent (NULL, TRUE, FALSE, NULL); - else - ResetEvent (hEventWrite); - if (!hEventException) - hEventException = CreateEvent (NULL, TRUE, FALSE, NULL); - else - ResetEvent (hEventException); - - /* Event for pipes */ if (!hEventPipeWrite) hEventPipeWrite = CreateEvent (NULL, TRUE, TRUE, NULL); readPipes = 0; writePipePos = -1; - handles_read = GNUNET_CONTAINER_slist_create (); - handles_write = GNUNET_CONTAINER_slist_create (); - handles_except = GNUNET_CONTAINER_slist_create (); + retcode = 0; + FD_ZERO (&aread); FD_ZERO (&awrite); FD_ZERO (&aexcept); @@ -1294,7 +1644,7 @@ GNUNET_NETWORK_socket_select (struct GNUNET_NETWORK_FDSet *rfds, fh = (struct GNUNET_DISK_FileHandle *) GNUNET_CONTAINER_slist_get (&i, NULL); - if (fh->type == GNUNET_PIPE) + if (fh->type == GNUNET_DISK_HANLDE_TYPE_PIPE) { /* Read zero bytes to check the status of the pipe */ LOG (GNUNET_ERROR_TYPE_DEBUG, "Reading 0 bytes from the pipe 0x%x\n", @@ -1355,7 +1705,7 @@ GNUNET_NETWORK_socket_select (struct GNUNET_NETWORK_FDSet *rfds, fh = (struct GNUNET_DISK_FileHandle *) GNUNET_CONTAINER_slist_get (&i, NULL); - if (fh->type == GNUNET_PIPE) + if (fh->type == GNUNET_DISK_HANLDE_TYPE_PIPE) { if (!PeekNamedPipe (fh->h, NULL, 0, NULL, &dwBytes, NULL)) { @@ -1363,103 +1713,97 @@ GNUNET_NETWORK_socket_select (struct GNUNET_NETWORK_FDSet *rfds, GNUNET_CONTAINER_SLIST_DISPOSITION_TRANSIENT, fh, sizeof (struct GNUNET_DISK_FileHandle)); - newretcode++; } } } } - if (nfds > 0) - { - if (rfds) - { - LOG (GNUNET_ERROR_TYPE_DEBUG, - "Adding the socket read event to the array as %d\n", nhandles); - handle_array[nhandles++] = hEventRead; - nSockEvents++; - for (i = 0; i < rfds->sds.fd_count; i++) - { - WSAEventSelect (rfds->sds.fd_array[i], hEventRead, - FD_ACCEPT | FD_READ | FD_CLOSE); - nsock++; - } - } - if (wfds) - { - int wakeup = 0; - LOG (GNUNET_ERROR_TYPE_DEBUG, - "Adding the socket write event to the array as %d\n", nhandles); - handle_array[nhandles++] = hEventWrite; - nSockEvents++; - for (i = 0; i < wfds->sds.fd_count; i++) - { - DWORD error; - int status; + sp.status = 0; - status = send (wfds->sds.fd_array[i], NULL, 0, 0); - error = GetLastError (); - LOG (GNUNET_ERROR_TYPE_DEBUG, - "pre-send to the socket %d returned %d (%u)\n", i, status, error); - if (status == 0 || (error != WSAEWOULDBLOCK && error != WSAENOTCONN)) - wakeup = 1; - WSAEventSelect (wfds->sds.fd_array[i], hEventWrite, - FD_WRITE | FD_CONNECT | FD_CLOSE); - nsock++; - } - if (wakeup) - SetEvent (hEventWrite); - } - if (efds) + if (nfds > 0) + { + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Adding the socket event to the array as %d\n", nhandles); + handle_array[nhandles++] = select_finished_event; + if (timeout.rel_value == GNUNET_TIME_UNIT_FOREVER_REL.rel_value) + sp.tv = NULL; + else { - LOG (GNUNET_ERROR_TYPE_DEBUG, - "Adding the socket error event to the array as %d\n", nhandles); - handle_array[nhandles++] = hEventException; - nSockEvents++; - for (i = 0; i < efds->sds.fd_count; i++) - { - WSAEventSelect (efds->sds.fd_array[i], hEventException, - FD_OOB | FD_CLOSE); - nsock++; - } + select_timeout.tv_sec = timeout.rel_value / GNUNET_TIME_UNIT_SECONDS.rel_value; + select_timeout.tv_usec = 1000 * (timeout.rel_value - + (select_timeout.tv_sec * GNUNET_TIME_UNIT_SECONDS.rel_value)); + sp.tv = &select_timeout; } + FD_SET (select_wakeup_socket, &aread); + sp.r = &aread; + sp.w = &awrite; + sp.e = &aexcept; + /* Failed connections cause sockets to be set in errorfds on W32, + * but on POSIX it should set them in writefds. + * First copy all awrite sockets to aexcept, later we'll + * check aexcept and set its contents in awrite as well + * Sockets are also set in errorfds when OOB data is available, + * but we don't use OOB data. + */ + for (i = 0; i < awrite.fd_count; i++) + FD_SET (awrite.fd_array[i], &aexcept); + ResetEvent (select_finished_event); + SetEvent (select_standby_event); } handle_array[nhandles] = NULL; - LOG (GNUNET_ERROR_TYPE_DEBUG, - "Number nfds: %d, handles: %d, return code: %u will wait: %d ms\n", - nfds, nhandles, newretcode, ms_total); + LOG (GNUNET_ERROR_TYPE_DEBUG, "nfds: %d, handles: %d, will wait: %llu ms\n", + nfds, nhandles, (unsigned long long) ms_total); if (nhandles) + { returncode = WaitForMultipleObjects (nhandles, handle_array, FALSE, ms_total); - LOG (GNUNET_ERROR_TYPE_DEBUG, "WaitForMultipleObjects Returned : %d\n", - returncode); + LOG (GNUNET_ERROR_TYPE_DEBUG, "WaitForMultipleObjects Returned : %d\n", + returncode); + } + else if (nfds > 0) + { + i = (int) WaitForSingleObject (select_finished_event, INFINITE); + returncode = WAIT_TIMEOUT; + } + else + { + /* Shouldn't come this far. If it does - investigate. */ + GNUNET_assert (0); + } + + if (nfds > 0) + { + /* Don't wake up select-thread when delay is 0, it should return immediately + * and wake up by itself. + */ + if (ms_total != 0) + i = send (select_send_socket, (const char *) &returnedpos, 1, 0); + i = (int) WaitForSingleObject (select_finished_event, INFINITE); + LOG (GNUNET_ERROR_TYPE_DEBUG, "Finished waiting for the select thread: %d %d\n", i, sp.status); + if (ms_total != 0) + { + do + { + i = recv (select_wakeup_socket, (char *) &returnedpos, 1, 0); + } while (i == 1); + } + /* Check aexcept, add its contents to awrite */ + for (i = 0; i < aexcept.fd_count; i++) + FD_SET (aexcept.fd_array[i], &awrite); + } returnedpos = returncode - WAIT_OBJECT_0; LOG (GNUNET_ERROR_TYPE_DEBUG, "return pos is : %d\n", returnedpos); - /* FIXME: THIS LINE IS WRONG !! We should add to handles only handles that fired the events, not all ! */ - /* - * if(rfds) - * GNUNET_CONTAINER_slist_append (handles_read, rfds->handles); - */ if (nhandles && (returnedpos < nhandles)) { DWORD waitstatus; - /* Do the select */ - if (nfds) - { - struct timeval tvslice; - - tvslice.tv_sec = 0; - tvslice.tv_usec = 0; - retcode = select (nfds, &aread, &awrite, &aexcept, &tvslice); - if (retcode == -1) - retcode = 0; - LOG (GNUNET_ERROR_TYPE_DEBUG, "Select retcode : %d\n", retcode); - } - /* FIXME: <= writePipePos? Really? */ - if ((writePipePos != -1) && (returnedpos <= writePipePos)) + if (sp.status > 0) + retcode += sp.status; + + if ((writePipePos != -1) && (returnedpos < writePipePos)) { GNUNET_CONTAINER_slist_append (handles_write, wfds->handles); retcode += write_handles; @@ -1467,24 +1811,8 @@ GNUNET_NETWORK_socket_select (struct GNUNET_NETWORK_FDSet *rfds, } LOG (GNUNET_ERROR_TYPE_DEBUG, "ReadPipes is : %d\n", readPipes); /* We have some pipes ready for read. */ - /* FIXME: it is supposed to work !! Only choose the Pipes who fired the event, but it is not working */ - if (returnedpos < readPipes) { - /* - * for (i = 0; i < readPipes; i++) - * { - * waitstatus = WaitForSingleObject (handle_array[i], 0); - * LOG (GNUNET_ERROR_TYPE_DEBUG, "Read pipe %d wait status is : %d\n", i, waitstatus); - * if (waitstatus != WAIT_OBJECT_0) - * continue; - * GNUNET_CONTAINER_slist_add (handles_read, - * GNUNET_CONTAINER_SLIST_DISPOSITION_TRANSIENT, - * readArray[i], sizeof (struct GNUNET_DISK_FileHandle)); - * retcode++; - * LOG (GNUNET_ERROR_TYPE_DEBUG, "Added read Pipe\n"); - * } - */ for (i = 0; i < readPipes; i++) { DWORD error; @@ -1500,7 +1828,11 @@ GNUNET_NETWORK_socket_select (struct GNUNET_NETWORK_FDSet *rfds, i, readArray[i]->h, bret, waitstatus, error); if (bret == 0) { - if (error != ERROR_BROKEN_PIPE) + /* TODO: either add more errors to this condition, or eliminate it + * entirely (failed to peek -> pipe is in serious trouble, should + * be selected as readable). + */ + if (error != ERROR_BROKEN_PIPE && error != ERROR_INVALID_HANDLE) continue; } else if (waitstatus <= 0) @@ -1514,34 +1846,6 @@ GNUNET_NETWORK_socket_select (struct GNUNET_NETWORK_FDSet *rfds, readArray[i], readArray[i]->h); } } - waitstatus = WaitForSingleObject (hEventWrite, 0); - LOG (GNUNET_ERROR_TYPE_DEBUG, "Wait for the write event returned %d\n", - waitstatus); - if (waitstatus == WAIT_OBJECT_0) - { - for (i = 0; i < wfds->sds.fd_count; i++) - { - DWORD error; - int status; - int so_error = 0; - int sizeof_so_error = sizeof (so_error); - int gso_result = - getsockopt (wfds->sds.fd_array[i], SOL_SOCKET, SO_ERROR, - (char *) &so_error, &sizeof_so_error); - - status = send (wfds->sds.fd_array[i], NULL, 0, 0); - error = GetLastError (); - LOG (GNUNET_ERROR_TYPE_DEBUG, - "send to the socket %d returned %d (%u)\n", i, status, error); - if (status == 0 || (error != WSAEWOULDBLOCK && error != WSAENOTCONN) || - (status == -1 && gso_result == 0 && error == WSAENOTCONN && - so_error == WSAECONNREFUSED)) - { - FD_SET (wfds->sds.fd_array[i], &awrite); - retcode += 1; - } - } - } } if (!nhandles || (returnedpos >= nhandles)) LOG (GNUNET_ERROR_TYPE_DEBUG, "Returning from _select() with nothing!\n"); @@ -1549,11 +1853,6 @@ GNUNET_NETWORK_socket_select (struct GNUNET_NETWORK_FDSet *rfds, { struct GNUNET_CONTAINER_SList_Iterator t; - for (i = 0; i < rfds->sds.fd_count; i++) - { - WSAEventSelect (rfds->sds.fd_array[i], hEventRead, 0); - nsock++; - } for (t = GNUNET_CONTAINER_slist_begin (rfds->handles); GNUNET_CONTAINER_slist_end (&t) != GNUNET_YES; GNUNET_CONTAINER_slist_next (&t)) @@ -1562,12 +1861,12 @@ GNUNET_NETWORK_socket_select (struct GNUNET_NETWORK_FDSet *rfds, fh = (struct GNUNET_DISK_FileHandle *) GNUNET_CONTAINER_slist_get (&t, NULL); - if (fh->type == GNUNET_PIPE) + if (fh->type == GNUNET_DISK_HANLDE_TYPE_PIPE) { CancelIo (fh->h); } } - LOG (GNUNET_ERROR_TYPE_DEBUG, "Zeroing rfds\n"); + LOG (GNUNET_ERROR_TYPE_DEBUG, "Zeroing rfds%s\n", (retcode != -1 && nhandles && (returnedpos < nhandles)) ? ", copying fdset" : ""); GNUNET_NETWORK_fdset_zero (rfds); if (retcode != -1 && nhandles && (returnedpos < nhandles)) GNUNET_NETWORK_fdset_copy_native (rfds, &aread, retcode); @@ -1575,12 +1874,7 @@ GNUNET_NETWORK_socket_select (struct GNUNET_NETWORK_FDSet *rfds, } if (wfds) { - for (i = 0; i < wfds->sds.fd_count; i++) - { - WSAEventSelect (wfds->sds.fd_array[i], hEventWrite, 0); - nsock++; - } - LOG (GNUNET_ERROR_TYPE_DEBUG, "Zeroing wfds\n"); + LOG (GNUNET_ERROR_TYPE_DEBUG, "Zeroing wfds%s\n", (retcode != -1 && nhandles && (returnedpos < nhandles)) ? ", copying fdset" : ""); GNUNET_NETWORK_fdset_zero (wfds); if (retcode != -1 && nhandles && (returnedpos < nhandles)) GNUNET_NETWORK_fdset_copy_native (wfds, &awrite, retcode); @@ -1588,12 +1882,7 @@ GNUNET_NETWORK_socket_select (struct GNUNET_NETWORK_FDSet *rfds, } if (efds) { - for (i = 0; i < efds->sds.fd_count; i++) - { - WSAEventSelect (efds->sds.fd_array[i], hEventException, 0); - nsock++; - } - LOG (GNUNET_ERROR_TYPE_DEBUG, "Zeroing efds\n"); + LOG (GNUNET_ERROR_TYPE_DEBUG, "Zeroing efds%s\n", (retcode != -1 && nhandles && (returnedpos < nhandles)) ? ", copying fdset" : ""); GNUNET_NETWORK_fdset_zero (efds); if (retcode != -1 && nhandles && (returnedpos < nhandles)) GNUNET_NETWORK_fdset_copy_native (efds, &aexcept, retcode); @@ -1607,12 +1896,10 @@ GNUNET_NETWORK_socket_select (struct GNUNET_NETWORK_FDSet *rfds, { struct GNUNET_CONTAINER_SList_Iterator t; - for (i = 0; i < bread.fd_count; i++) + LOG (GNUNET_ERROR_TYPE_DEBUG, "rfds:\n"); + for (i = 0; i < rfds->sds.fd_count; i++) { - if (bread.fd_array[i] != 0) - LOG (GNUNET_ERROR_TYPE_DEBUG, "FD 0x%x is %s in rfds\n", - bread.fd_array[i], - (SAFE_FD_ISSET (bread.fd_array[i], rfds)) ? "SET" : "NOT SET"); + LOG (GNUNET_ERROR_TYPE_DEBUG, "%d\n", rfds->sds.fd_array[i]); } for (t = GNUNET_CONTAINER_slist_begin (rfds->handles); GNUNET_CONTAINER_slist_end (&t) != GNUNET_YES; @@ -1622,27 +1909,23 @@ GNUNET_NETWORK_socket_select (struct GNUNET_NETWORK_FDSet *rfds, fh = (struct GNUNET_DISK_FileHandle *) GNUNET_CONTAINER_slist_get (&t, NULL); - LOG (GNUNET_ERROR_TYPE_DEBUG, "FD 0x%x is SET in rfds\n", fh->h); + LOG (GNUNET_ERROR_TYPE_DEBUG, "%d\n", fh->h); } } if (wfds) { - for (i = 0; i < bwrite.fd_count; i++) + LOG (GNUNET_ERROR_TYPE_DEBUG, "wfds:\n"); + for (i = 0; i < wfds->sds.fd_count; i++) { - if (bwrite.fd_array[i] != 0) - LOG (GNUNET_ERROR_TYPE_DEBUG, "FD 0x%x is %s in wfds\n", - bwrite.fd_array[i], - (SAFE_FD_ISSET (bwrite.fd_array[i], rfds)) ? "SET" : "NOT SET"); + LOG (GNUNET_ERROR_TYPE_DEBUG, "%d\n", wfds->sds.fd_array[i]); } } if (efds) { - for (i = 0; i < bexcept.fd_count; i++) + LOG (GNUNET_ERROR_TYPE_DEBUG, "efds:\n"); + for (i = 0; i < efds->sds.fd_count; i++) { - if (bexcept.fd_array[i] != 0) - LOG (GNUNET_ERROR_TYPE_DEBUG, "FD 0x%x is %s in efds\n", - bexcept.fd_array[i], - (SAFE_FD_ISSET (bexcept.fd_array[i], rfds)) ? "SET" : "NOT SET"); + LOG (GNUNET_ERROR_TYPE_DEBUG, "%d\n", efds->sds.fd_array[i]); } } LOG (GNUNET_ERROR_TYPE_DEBUG, "Returning %d or 0\n", retcode); diff --git a/src/util/os_installation.c b/src/util/os_installation.c index e790ce1..e35f86c 100644 --- a/src/util/os_installation.c +++ b/src/util/os_installation.c @@ -27,12 +27,14 @@ #include #include #include +#include /* for u16_to_u8 */ #include "platform.h" #include "gnunet_common.h" #include "gnunet_configuration_lib.h" #include "gnunet_disk_lib.h" #include "gnunet_os_lib.h" +#include "gnunet_strings_lib.h" #if DARWIN #include #include @@ -45,6 +47,8 @@ #if LINUX /** * Try to determine path by reading /proc/PID/exe + * + * @return NULL on error */ static char * get_path_from_proc_maps () @@ -56,13 +60,12 @@ get_path_from_proc_maps () char *lgu; GNUNET_snprintf (fn, sizeof (fn), "/proc/%u/maps", getpid ()); - f = FOPEN (fn, "r"); - if (f == NULL) + if (NULL == (f = FOPEN (fn, "r"))) return NULL; while (NULL != fgets (line, sizeof (line), f)) { if ((1 == - SSCANF (line, "%*x-%*x %*c%*c%*c%*c %*x %*2u:%*2u %*u%*[ ]%s", dir)) && + SSCANF (line, "%*x-%*x %*c%*c%*c%*c %*x %*2u:%*2u %*u%*[ ]%1023s", dir)) && (NULL != (lgu = strstr (dir, "libgnunetutil")))) { lgu[0] = '\0'; @@ -74,8 +77,11 @@ get_path_from_proc_maps () return NULL; } + /** * Try to determine path by reading /proc/PID/exe + * + * @return NULL on error */ static char * get_path_from_proc_exe () @@ -95,6 +101,11 @@ get_path_from_proc_exe () lnk[size] = '\0'; while ((lnk[size] != '/') && (size > 0)) size--; + /* test for being in lib/gnunet/libexec/ */ + if ( (size > strlen ("/gnunet/libexec/")) && + (0 == strcmp ("/gnunet/libexec/", + &lnk[size - strlen ("/gnunet/libexec/")])) ) + size -= strlen ("gnunet/libexec/"); if ((size < 4) || (lnk[size - 4] != '/')) { /* not installed in "/bin/" -- binary path probably useless */ @@ -106,31 +117,132 @@ get_path_from_proc_exe () #endif #if WINDOWS + +static HINSTANCE dll_instance; + + +/* GNUNET_util_cl_init() in common_logging.c is preferred. + * This function is only for thread-local storage (not used in GNUnet) + * and hInstance saving. + */ +BOOL WINAPI +DllMain (HINSTANCE hinstDLL, DWORD fdwReason, LPVOID lpvReserved) +{ + switch (fdwReason) + { + case DLL_PROCESS_ATTACH: + dll_instance = hinstDLL; + break; + case DLL_THREAD_ATTACH: + break; + case DLL_THREAD_DETACH: + break; + case DLL_PROCESS_DETACH: + break; + } + return TRUE; +} + + /** * Try to determine path with win32-specific function + * + * @return NULL on error */ static char * get_path_from_module_filename () { - wchar_t path[4097]; - char upath[4097]; + size_t pathlen = 512; + DWORD real_pathlen; wchar_t *idx; - - GetModuleFileNameW (NULL, path, sizeof (path) - 1); - idx = path + wcslen (path); - while ((idx > path) && (*idx != L'\\') && (*idx != L'/')) + wchar_t *modulepath = NULL; + char *upath; + uint8_t *u8_string; + size_t u8_string_length; + + /* This braindead function won't tell us how much space it needs, so + * we start at 1024 and double the space up if it doesn't fit, until + * it fits, or we exceed the threshold. + */ + do + { + pathlen = pathlen * 2; + modulepath = GNUNET_realloc (modulepath, pathlen * sizeof (wchar_t)); + SetLastError (0); + real_pathlen = GetModuleFileNameW (dll_instance, modulepath, pathlen * sizeof (wchar_t)); + } while (real_pathlen >= pathlen && pathlen < 16*1024); + if (real_pathlen >= pathlen) + GNUNET_abort (); + /* To be safe */ + modulepath[real_pathlen] = '\0'; + + idx = modulepath + real_pathlen; + while ((idx > modulepath) && (*idx != L'\\') && (*idx != L'/')) idx--; *idx = L'\0'; - upath[0] = '\0'; - WideCharToMultiByte (CP_UTF8, 0, path, -1, upath, 4097, NULL, NULL); - return GNUNET_strdup (upath); + /* Now modulepath holds full path to the directory where libgnunetutil is. + * This directory should look like /bin or . + */ + if (wcschr (modulepath, L'/') || wcschr (modulepath, L'\\')) + { + /* At least one directory component (i.e. we're not in a root directory) */ + wchar_t *dirname = idx; + while ((dirname > modulepath) && (*dirname != L'\\') && (*dirname != L'/')) + dirname--; + *dirname = L'\0'; + if (dirname > modulepath) + { + dirname++; + /* Now modulepath holds full path to the parent directory of the directory + * where libgnunetutil is. + * dirname holds the name of the directory where libgnunetutil is. + */ + if (wcsicmp (dirname, L"bin") == 0) + { + /* pass */ + } + else + { + /* Roll back our changes to modulepath */ + dirname--; + *dirname = L'/'; + } + } + } + + /* modulepath is GNUNET_PREFIX */ + u8_string = u16_to_u8 (modulepath, wcslen (modulepath), NULL, &u8_string_length); + if (NULL == u8_string) + GNUNET_abort (); + + upath = GNUNET_malloc (u8_string_length + 1); + memcpy (upath, u8_string, u8_string_length); + upath[u8_string_length] = '\0'; + + free (u8_string); + GNUNET_free (modulepath); + + return upath; } #endif #if DARWIN +/** + * Signature of the '_NSGetExecutablePath" function. + * + * @param buf where to write the path + * @param number of bytes available in 'buf' + * @return 0 on success, otherwise desired number of bytes is stored in 'bufsize' + */ typedef int (*MyNSGetExecutablePathProto) (char *buf, size_t * bufsize); + +/** + * Try to obtain the path of our executable using '_NSGetExecutablePath'. + * + * @return NULL on error + */ static char * get_path_from_NSGetExecutablePath () { @@ -138,22 +250,19 @@ get_path_from_NSGetExecutablePath () char *path; size_t len; MyNSGetExecutablePathProto func; - int ret; path = NULL; - func = - (MyNSGetExecutablePathProto) dlsym (RTLD_DEFAULT, "_NSGetExecutablePath"); - if (!func) + if (NULL == (func = + (MyNSGetExecutablePathProto) dlsym (RTLD_DEFAULT, "_NSGetExecutablePath"))) return NULL; path = &zero; len = 0; /* get the path len, including the trailing \0 */ - func (path, &len); - if (len == 0) + (void) func (path, &len); + if (0 == len) return NULL; path = GNUNET_malloc (len); - ret = func (path, &len); - if (ret != 0) + if (0 != func (path, &len)) { GNUNET_free (path); return NULL; @@ -165,37 +274,42 @@ get_path_from_NSGetExecutablePath () return path; } + +/** + * Try to obtain the path of our executable using '_dyld_image' API. + * + * @return NULL on error + */ static char * get_path_from_dyld_image () { const char *path; - char *p, *s; - int i; + char *p; + char *s; + unsigned int i; int c; - p = NULL; c = _dyld_image_count (); for (i = 0; i < c; i++) { - if (_dyld_get_image_header (i) == &_mh_dylib_header) - { - path = _dyld_get_image_name (i); - if (path != NULL && strlen (path) > 0) - { - p = GNUNET_strdup (path); - s = p + strlen (p); - while ((s > p) && (*s != '/')) - s--; - s++; - *s = '\0'; - } - break; - } + if (_dyld_get_image_header (i) != &_mh_dylib_header) + continue; + path = _dyld_get_image_name (i); + if ( (NULL == path) || (0 == strlen (path)) ) + continue; + p = GNUNET_strdup (path); + s = p + strlen (p); + while ((s > p) && ('/' != *s)) + s--; + s++; + *s = '\0'; + return p; } - return p; + return NULL; } #endif + /** * Return the actual path to a file found in the current * PATH environment variable. @@ -212,11 +326,15 @@ get_path_from_PATH (const char *binary) char *buf; const char *p; - p = getenv ("PATH"); - if (p == NULL) + if (NULL == (p = getenv ("PATH"))) return NULL; +#if WINDOWS + /* On W32 look in CWD first. */ + GNUNET_asprintf (&path, ".%c%s", PATH_SEPARATOR, p); +#else path = GNUNET_strdup (p); /* because we write on it */ - buf = GNUNET_malloc (strlen (path) + 20); +#endif + buf = GNUNET_malloc (strlen (path) + strlen (binary) + 1 + 1); pos = path; while (NULL != (end = strchr (pos, PATH_SEPARATOR))) { @@ -232,7 +350,7 @@ get_path_from_PATH (const char *binary) pos = end + 1; } sprintf (buf, "%s/%s", pos, binary); - if (GNUNET_DISK_file_test (buf) == GNUNET_YES) + if (GNUNET_YES == GNUNET_DISK_file_test (buf)) { pos = GNUNET_strdup (pos); GNUNET_free (buf); @@ -244,17 +362,24 @@ get_path_from_PATH (const char *binary) return NULL; } + +/** + * Try to obtain the installation path using the "GNUNET_PREFIX" environment + * variable. + * + * @return NULL on error (environment variable not set) + */ static char * get_path_from_GNUNET_PREFIX () { const char *p; - p = getenv ("GNUNET_PREFIX"); - if (p != NULL) + if (NULL != (p = getenv ("GNUNET_PREFIX"))) return GNUNET_strdup (p); return NULL; } + /** * @brief get the path to GNUnet bin/ or lib/, prefering the lib/ path * @author Milan @@ -266,32 +391,28 @@ os_get_gnunet_path () { char *ret; - ret = get_path_from_GNUNET_PREFIX (); - if (ret != NULL) + if (NULL != (ret = get_path_from_GNUNET_PREFIX ())) return ret; #if LINUX - ret = get_path_from_proc_maps (); - if (ret != NULL) + if (NULL != (ret = get_path_from_proc_maps ())) + return ret; + /* try path *first*, before /proc/exe, as /proc/exe can be wrong */ + if (NULL != (ret = get_path_from_PATH ("gnunet-arm"))) return ret; - ret = get_path_from_proc_exe (); - if (ret != NULL) + if (NULL != (ret = get_path_from_proc_exe ())) return ret; #endif #if WINDOWS - ret = get_path_from_module_filename (); - if (ret != NULL) + if (NULL != (ret = get_path_from_module_filename ())) return ret; #endif #if DARWIN - ret = get_path_from_dyld_image (); - if (ret != NULL) + if (NULL != (ret = get_path_from_dyld_image ())) return ret; - ret = get_path_from_NSGetExecutablePath (); - if (ret != NULL) + if (NULL != (ret = get_path_from_NSGetExecutablePath ())) return ret; #endif - ret = get_path_from_PATH ("gnunet-arm"); - if (ret != NULL) + if (NULL != (ret = get_path_from_PATH ("gnunet-arm"))) return ret; /* other attempts here */ LOG (GNUNET_ERROR_TYPE_ERROR, @@ -301,7 +422,8 @@ os_get_gnunet_path () return NULL; } -/* + +/** * @brief get the path to current app's bin/ * @author Milan * @@ -310,22 +432,18 @@ os_get_gnunet_path () static char * os_get_exec_path () { - char *ret; + char *ret = NULL; - ret = NULL; #if LINUX - ret = get_path_from_proc_exe (); - if (ret != NULL) + if (NULL != (ret = get_path_from_proc_exe ())) return ret; #endif #if WINDOWS - ret = get_path_from_module_filename (); - if (ret != NULL) + if (NULL != (ret = get_path_from_module_filename ())) return ret; #endif #if DARWIN - ret = get_path_from_NSGetExecutablePath (); - if (ret != NULL) + if (NULL != (ret = get_path_from_NSGetExecutablePath ())) return ret; #endif /* other attempts here */ @@ -333,7 +451,6 @@ os_get_exec_path () } - /** * @brief get the path to a specific GNUnet installation directory or, * with GNUNET_IPK_SELF_PREFIX, the current running apps installation directory @@ -355,21 +472,21 @@ GNUNET_OS_installation_get_path (enum GNUNET_OS_InstallationPathKind dirkind) /* try to get GNUnet's bin/ or lib/, or if previous was unsuccessful some * guess for the current app */ - if (execpath == NULL) + if (NULL == execpath) execpath = os_get_gnunet_path (); - if (execpath == NULL) + if (NULL == execpath) return NULL; n = strlen (execpath); - if (n == 0) + if (0 == n) { /* should never happen, but better safe than sorry */ GNUNET_free (execpath); return NULL; } /* remove filename itself */ - while ((n > 1) && (execpath[n - 1] == DIR_SEPARATOR)) + while ((n > 1) && (DIR_SEPARATOR == execpath[n - 1])) execpath[--n] = '\0'; isbasedir = 1; @@ -377,7 +494,8 @@ GNUNET_OS_installation_get_path (enum GNUNET_OS_InstallationPathKind dirkind) ((0 == strcasecmp (&execpath[n - 5], "lib32")) || (0 == strcasecmp (&execpath[n - 5], "lib64")))) { - if (dirkind != GNUNET_OS_IPK_LIBDIR) + if ( (GNUNET_OS_IPK_LIBDIR != dirkind) && + (GNUNET_OS_IPK_LIBEXECDIR != dirkind) ) { /* strip '/lib32' or '/lib64' */ execpath[n - 5] = '\0'; @@ -408,8 +526,30 @@ GNUNET_OS_installation_get_path (enum GNUNET_OS_InstallationPathKind dirkind) break; case GNUNET_OS_IPK_LIBDIR: if (isbasedir) + { dirname = DIR_SEPARATOR_STR "lib" DIR_SEPARATOR_STR "gnunet" DIR_SEPARATOR_STR; + tmp = GNUNET_malloc (strlen (execpath) + strlen (dirname) + 1); + sprintf (tmp, "%s%s", execpath, dirname); + if ( (GNUNET_YES != + GNUNET_DISK_directory_test (tmp, GNUNET_YES)) && + (4 == sizeof (void *)) ) + { + GNUNET_free (tmp); + dirname = + DIR_SEPARATOR_STR "lib32" DIR_SEPARATOR_STR "gnunet" DIR_SEPARATOR_STR; + tmp = GNUNET_malloc (strlen (execpath) + strlen (dirname) + 1); + sprintf (tmp, "%s%s", execpath, dirname); + } + if ( (GNUNET_YES != + GNUNET_DISK_directory_test (tmp, GNUNET_YES)) && + (8 == sizeof (void *)) ) + { + dirname = + DIR_SEPARATOR_STR "lib64" DIR_SEPARATOR_STR "gnunet" DIR_SEPARATOR_STR; + } + GNUNET_free (tmp); + } else dirname = DIR_SEPARATOR_STR "gnunet" DIR_SEPARATOR_STR; break; @@ -430,6 +570,40 @@ GNUNET_OS_installation_get_path (enum GNUNET_OS_InstallationPathKind dirkind) DIR_SEPARATOR_STR "share" DIR_SEPARATOR_STR "doc" DIR_SEPARATOR_STR \ "gnunet" DIR_SEPARATOR_STR; break; + case GNUNET_OS_IPK_LIBEXECDIR: + if (isbasedir) + { + dirname = + DIR_SEPARATOR_STR "lib" DIR_SEPARATOR_STR "gnunet" DIR_SEPARATOR_STR \ + "libexec" DIR_SEPARATOR_STR; + tmp = GNUNET_malloc (strlen (execpath) + strlen (dirname) + 1); + sprintf (tmp, "%s%s", execpath, dirname); + if ( (GNUNET_YES != + GNUNET_DISK_directory_test (tmp, GNUNET_YES)) && + (4 == sizeof (void *)) ) + { + GNUNET_free (tmp); + dirname = + DIR_SEPARATOR_STR "lib32" DIR_SEPARATOR_STR "gnunet" DIR_SEPARATOR_STR \ + "libexec" DIR_SEPARATOR_STR; + tmp = GNUNET_malloc (strlen (execpath) + strlen (dirname) + 1); + sprintf (tmp, "%s%s", execpath, dirname); + } + if ( (GNUNET_YES != + GNUNET_DISK_directory_test (tmp, GNUNET_YES)) && + (8 == sizeof (void *)) ) + { + dirname = + DIR_SEPARATOR_STR "lib64" DIR_SEPARATOR_STR "gnunet" DIR_SEPARATOR_STR \ + "libexec" DIR_SEPARATOR_STR; + } + GNUNET_free (tmp); + } + else + dirname = + DIR_SEPARATOR_STR "gnunet" DIR_SEPARATOR_STR \ + "libexec" DIR_SEPARATOR_STR; + break; default: GNUNET_free (execpath); return NULL; @@ -441,13 +615,42 @@ GNUNET_OS_installation_get_path (enum GNUNET_OS_InstallationPathKind dirkind) } +/** + * Given the name of a gnunet-helper, gnunet-service or gnunet-daemon + * binary, try to prefix it with the libexec/-directory to get the + * full path. + * + * @param progname name of the binary + * @return full path to the binary, if possible, otherwise copy of 'progname' + */ +char * +GNUNET_OS_get_libexec_binary_path (const char *progname) +{ + char *libexecdir; + char *binary; + + if (DIR_SEPARATOR == progname[0]) + return GNUNET_strdup (progname); + libexecdir = GNUNET_OS_installation_get_path (GNUNET_OS_IPK_LIBEXECDIR); + if (NULL == libexecdir) + return GNUNET_strdup (progname); + GNUNET_asprintf (&binary, + "%s%s", + libexecdir, + progname); + GNUNET_free (libexecdir); + return binary; +} + + /** * Check whether an executable exists and possibly * if the suid bit is set on the file. * Attempts to find the file using the current * PATH environment variable as a search path. * - * @param binary the name of the file to check + * @param binary the name of the file to check. + * W32: must not have an .exe suffix. * @return GNUNET_YES if the file is SUID, * GNUNET_NO if not SUID (but binary exists) * GNUNET_SYSERR on error (no such binary or not executable) @@ -458,30 +661,43 @@ GNUNET_OS_check_helper_binary (const char *binary) struct stat statbuf; char *p; char *pf; - #ifdef MINGW SOCKET rawsock; char *binaryexe; GNUNET_asprintf (&binaryexe, "%s.exe", binary); - p = get_path_from_PATH (binaryexe); - if (p != NULL) + if ( (GNUNET_YES == GNUNET_STRINGS_path_is_absolute (binaryexe, GNUNET_NO, + NULL, NULL)) || + (0 == strncmp (binary, "./", 2)) ) + p = GNUNET_strdup (binaryexe); + else { - GNUNET_asprintf (&pf, "%s/%s", p, binaryexe); - GNUNET_free (p); - p = pf; + p = get_path_from_PATH (binaryexe); + if (NULL != p) + { + GNUNET_asprintf (&pf, "%s/%s", p, binaryexe); + GNUNET_free (p); + p = pf; + } } GNUNET_free (binaryexe); #else - p = get_path_from_PATH (binary); - if (p != NULL) + if ( (GNUNET_YES == GNUNET_STRINGS_path_is_absolute (binary, GNUNET_NO, + NULL, NULL)) || + (0 == strncmp (binary, "./", 2)) ) + p = GNUNET_strdup (binary); + else { - GNUNET_asprintf (&pf, "%s/%s", p, binary); - GNUNET_free (p); - p = pf; + p = get_path_from_PATH (binary); + if (NULL != p) + { + GNUNET_asprintf (&pf, "%s/%s", p, binary); + GNUNET_free (p); + p = pf; + } } #endif - if (p == NULL) + if (NULL == p) { LOG (GNUNET_ERROR_TYPE_INFO, _("Could not find binary `%s' in PATH!\n"), binary); @@ -489,8 +705,7 @@ GNUNET_OS_check_helper_binary (const char *binary) } if (0 != ACCESS (p, X_OK)) { - LOG (GNUNET_ERROR_TYPE_WARNING, _("access (%s, X_OK) failed: %s\n"), p, - STRERROR (errno)); + LOG_STRERROR_FILE (GNUNET_ERROR_TYPE_WARNING, "access", p); GNUNET_free (p); return GNUNET_SYSERR; } @@ -504,13 +719,12 @@ GNUNET_OS_check_helper_binary (const char *binary) #endif if (0 != STAT (p, &statbuf)) { - LOG (GNUNET_ERROR_TYPE_WARNING, _("stat (%s) failed: %s\n"), p, - STRERROR (errno)); + LOG_STRERROR_FILE (GNUNET_ERROR_TYPE_WARNING, "stat", p); GNUNET_free (p); return GNUNET_SYSERR; } #ifndef MINGW - if ((0 != (statbuf.st_mode & S_ISUID)) && (statbuf.st_uid == 0)) + if ((0 != (statbuf.st_mode & S_ISUID)) && (0 == statbuf.st_uid)) { GNUNET_free (p); return GNUNET_YES; @@ -520,17 +734,28 @@ GNUNET_OS_check_helper_binary (const char *binary) return GNUNET_NO; #else GNUNET_free (p); - rawsock = socket (AF_INET, SOCK_RAW, IPPROTO_ICMP); - if (INVALID_SOCKET == rawsock) { - DWORD err = GetLastError (); + static int once; /* remember result from previous runs... */ - LOG (GNUNET_ERROR_TYPE_INFO, - "socket (AF_INET, SOCK_RAW, IPPROTO_ICMP) failed! GLE = %d\n", err); - return GNUNET_NO; /* not running as administrator */ + if (0 == once) + { + rawsock = socket (AF_INET, SOCK_RAW, IPPROTO_ICMP); + if (INVALID_SOCKET == rawsock) + { + DWORD err = GetLastError (); + + LOG (GNUNET_ERROR_TYPE_DEBUG, + "socket (AF_INET, SOCK_RAW, IPPROTO_ICMP) failed! GLE = %d\n", err); + once = -1; + return GNUNET_NO; /* not running as administrator */ + } + once = 1; + closesocket (rawsock); + } + if (-1 == once) + return GNUNET_NO; + return GNUNET_YES; } - closesocket (rawsock); - return GNUNET_YES; #endif } diff --git a/src/util/os_priority.c b/src/util/os_priority.c index b8b1ba1..ba2034c 100644 --- a/src/util/os_priority.c +++ b/src/util/os_priority.c @@ -41,6 +41,7 @@ #define GNUNET_OS_CONTROL_PIPE "GNUNET_OS_CONTROL_PIPE" + struct GNUNET_OS_Process { /** @@ -78,7 +79,8 @@ static struct GNUNET_OS_Process current_process; /** * Creates a named pipe/FIFO and opens it * - * @param fn pointer to the name of the named pipe or to NULL + * @param fn pointer to the name of the named pipe or to NULL, + * possibly updated to the new name (or free'd) * @param flags open flags * @param perm access permissions * @return pipe handle on success, NULL on error @@ -102,12 +104,12 @@ npipe_create (char **fn, enum GNUNET_DISK_OpenFlags flags, if (flags & GNUNET_DISK_OPEN_FAILIFEXISTS) openMode |= FILE_FLAG_FIRST_PIPE_INSTANCE; - while (h == NULL) + while (NULL == h) { DWORD error_code; name = NULL; - if (*fn != NULL) + if (NULL != *fn) { GNUNET_asprintf (&name, "\\\\.\\pipe\\%.246s", fn); LOG (GNUNET_ERROR_TYPE_DEBUG, @@ -133,25 +135,22 @@ npipe_create (char **fn, enum GNUNET_DISK_OpenFlags flags, NULL); } error_code = GetLastError (); - if (name) - GNUNET_free (name); + GNUNET_free_non_null (name); /* don't re-set name to NULL yet */ - if (h == INVALID_HANDLE_VALUE) + if (INVALID_HANDLE_VALUE == h) { SetErrnoFromWinError (error_code); LOG (GNUNET_ERROR_TYPE_DEBUG, "Pipe creation have failed because of %d, errno is %d\n", error_code, errno); - if (name == NULL) + if (NULL != *fn) { LOG (GNUNET_ERROR_TYPE_DEBUG, "Pipe was to be unique, considering re-creation\n"); GNUNET_free (*fn); *fn = NULL; - if (error_code != ERROR_ACCESS_DENIED && error_code != ERROR_PIPE_BUSY) - { - return NULL; - } + if ( (ERROR_ACCESS_DENIED != error_code) && (ERROR_PIPE_BUSY != error_code) ) + return NULL; LOG (GNUNET_ERROR_TYPE_DEBUG, "Pipe name was not unique, trying again\n"); h = NULL; @@ -160,11 +159,9 @@ npipe_create (char **fn, enum GNUNET_DISK_OpenFlags flags, return NULL; } } - errno = 0; - - ret = GNUNET_malloc (sizeof (*ret)); + ret = GNUNET_malloc (sizeof (struct GNUNET_DISK_FileHandle)); ret->h = h; - ret->type = GNUNET_PIPE; + ret->type = GNUNET_DISK_HANLDE_TYPE_PIPE; ret->oOverlapRead = GNUNET_malloc (sizeof (OVERLAPPED)); ret->oOverlapWrite = GNUNET_malloc (sizeof (OVERLAPPED)); ret->oOverlapRead->hEvent = CreateEvent (NULL, FALSE, FALSE, NULL); @@ -197,15 +194,15 @@ npipe_open (const char *fn, enum GNUNET_DISK_OpenFlags flags) h = CreateFile (fn, openMode, 0, NULL, OPEN_EXISTING, FILE_FLAG_OVERLAPPED | FILE_READ_ATTRIBUTES, NULL); - if (h == INVALID_HANDLE_VALUE) + if (INVALID_HANDLE_VALUE == h) { SetErrnoFromWinError (GetLastError ()); return NULL; } - ret = GNUNET_malloc (sizeof (*ret)); + ret = GNUNET_malloc (sizeof (struct GNUNET_DISK_FileHandle)); ret->h = h; - ret->type = GNUNET_PIPE; + ret->type = GNUNET_DISK_HANLDE_TYPE_PIPE; ret->oOverlapRead = GNUNET_malloc (sizeof (OVERLAPPED)); ret->oOverlapWrite = GNUNET_malloc (sizeof (OVERLAPPED)); ret->oOverlapRead->hEvent = CreateEvent (NULL, FALSE, FALSE, NULL); @@ -326,6 +323,7 @@ parent_control_handler (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { struct GNUNET_DISK_FileHandle *control_pipe = cls; + char *pipe_name; char sig; ssize_t ret; @@ -343,11 +341,15 @@ parent_control_handler (void *cls, { if (-1 == ret) LOG_STRERROR (GNUNET_ERROR_TYPE_ERROR, "GNUNET_DISK_file_read"); + LOG (GNUNET_ERROR_TYPE_WARNING, "Closing control pipe\n"); GNUNET_DISK_file_close (control_pipe); control_pipe = NULL; return; } - LOG (GNUNET_ERROR_TYPE_DEBUG, "Got control code %d from parent\n", sig); + pipe_name = getenv (GNUNET_OS_CONTROL_PIPE); + GNUNET_assert ( (NULL == pipe_name) || (strlen (pipe_name) <= 0) ); + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Got control code %d from parent via pipe %s\n", sig, pipe_name); GNUNET_SCHEDULER_add_read_file (GNUNET_TIME_UNIT_FOREVER_REL, control_pipe, &parent_control_handler, control_pipe); @@ -373,7 +375,7 @@ GNUNET_OS_install_parent_control_handler (void *cls, struct GNUNET_DISK_FileHandle *control_pipe; env_buf = getenv (GNUNET_OS_CONTROL_PIPE); - if ( (env_buf == NULL) || (strlen (env_buf) <= 0) ) + if ( (NULL == env_buf) || (strlen (env_buf) <= 0) ) { LOG (GNUNET_ERROR_TYPE_DEBUG, "Not installing a handler because $%s is empty\n", @@ -440,8 +442,9 @@ GNUNET_OS_process_kill (struct GNUNET_OS_Process *proc, int sig) #endif if (NULL != proc->control_pipe) { + LOG (GNUNET_ERROR_TYPE_DEBUG, "Sending signal %d to pid: %u via pipe\n", sig, proc->pid); ret = GNUNET_DISK_file_write (proc->control_pipe, &csig, sizeof (csig)); - if (ret == sizeof (csig)) + if (sizeof (csig) == ret) return 0; } /* pipe failed or non-existent, try other methods */ @@ -454,13 +457,42 @@ GNUNET_OS_process_kill (struct GNUNET_OS_Process *proc, int sig) case SIGKILL: case SIGTERM: #if WINDOWS && !defined(__CYGWIN__) - if (0 == TerminateProcess (proc->handle, 0)) { - /* FIXME: set 'errno' */ - return -1; + DWORD exitcode; + int must_kill = GNUNET_YES; + if (0 != GetExitCodeProcess (proc->handle, &exitcode)) + must_kill = (exitcode == STILL_ACTIVE) ? GNUNET_YES : GNUNET_NO; + if (GNUNET_YES == must_kill) + if (0 == SafeTerminateProcess (proc->handle, 0, 0)) + { + DWORD error_code = GetLastError (); + if ((error_code != WAIT_TIMEOUT) && (error_code != ERROR_PROCESS_ABORTED)) + { + LOG ((error_code == ERROR_ACCESS_DENIED) ? + GNUNET_ERROR_TYPE_INFO : GNUNET_ERROR_TYPE_WARNING, + "SafeTermiateProcess failed with code %lu\n", error_code); + /* The problem here is that a process that is already dying + * might cause SafeTerminateProcess to fail with + * ERROR_ACCESS_DENIED, but the process WILL die eventually. + * If we really had a permissions problem, hanging up (which + * is what will happen in process_wait() in that case) is + * a valid option. + */ + if (ERROR_ACCESS_DENIED == error_code) + { + errno = 0; + } + else + { + SetErrnoFromWinError (error_code); + return -1; + } + } + } } return 0; #else + LOG (GNUNET_ERROR_TYPE_DEBUG, "Sending signal %d to pid: %u via system call\n", sig, proc->pid); return PLIBC_KILL (proc->pid, sig); #endif default: @@ -468,6 +500,7 @@ GNUNET_OS_process_kill (struct GNUNET_OS_Process *proc, int sig) errno = EINVAL; return -1; #else + LOG (GNUNET_ERROR_TYPE_DEBUG, "Sending signal %d to pid: %u via system call\n", sig, proc->pid); return PLIBC_KILL (proc->pid, sig); #endif } @@ -541,6 +574,7 @@ child_wait_thread (void *arg) } #endif + /** * Set process priority * @@ -555,7 +589,7 @@ GNUNET_OS_set_process_priority (struct GNUNET_OS_Process *proc, int rprio; GNUNET_assert (prio < GNUNET_SCHEDULER_PRIORITY_COUNT); - if (prio == GNUNET_SCHEDULER_PRIORITY_KEEP) + if (GNUNET_SCHEDULER_PRIORITY_KEEP == prio) return GNUNET_OK; /* convert to MINGW/Unix values */ @@ -646,6 +680,7 @@ GNUNET_OS_set_process_priority (struct GNUNET_OS_Process *proc, return GNUNET_OK; } + #if MINGW static char * CreateCustomEnvTable (char **vars) @@ -666,7 +701,7 @@ CreateCustomEnvTable (char **vars) char *val; win32_env_table = GetEnvironmentStringsA (); - if (win32_env_table == NULL) + if (NULL == win32_env_table) return NULL; for (c = 0, var_ptr = vars; *var_ptr; var_ptr += 2, c++) ; n_var = c; @@ -751,6 +786,38 @@ CreateCustomEnvTable (char **vars) *result_ptr = 0; return result; } + +#else + +/** + * Open '/dev/null' and make the result the given + * file descriptor. + * + * @param target_fd desired FD to point to /dev/null + * @param flags open flags (O_RDONLY, O_WRONLY) + */ +static void +open_dev_null (int target_fd, + int flags) +{ + int fd; + + fd = open ("/dev/null", flags); + if (-1 == fd) + { + GNUNET_log_strerror_file (GNUNET_ERROR_TYPE_ERROR, "open", "/dev/null"); + return; + } + if (fd == target_fd) + return; + if (-1 == dup2 (fd, target_fd)) + { + GNUNET_log_strerror (GNUNET_ERROR_TYPE_ERROR, "dup2"); + (void) close (fd); + return; + } + GNUNET_break (0 == close (fd)); +} #endif @@ -758,33 +825,54 @@ CreateCustomEnvTable (char **vars) * Start a process. * * @param pipe_control should a pipe be used to send signals to the child? + * @param std_inheritance a set of GNUNET_OS_INHERIT_STD_* flags controlling which + * std handles of the parent are inherited by the child. + * pipe_stdin and pipe_stdout take priority over std_inheritance + * (when they are non-NULL). * @param pipe_stdin pipe to use to send input to child process (or NULL) * @param pipe_stdout pipe to use to get output from child process (or NULL) + * @param lsocks array of listen sockets to dup systemd-style (or NULL); + * must be NULL on platforms where dup is not supported * @param filename name of the binary - * @param argv NULL-terminated array of arguments to the process - * @return pointer to process structure of the new process, NULL on error + * @param argv NULL-terminated list of arguments to the process + * @return process ID of the new process, -1 on error */ -struct GNUNET_OS_Process * -GNUNET_OS_start_process_vap (int pipe_control, - struct GNUNET_DISK_PipeHandle *pipe_stdin, - struct GNUNET_DISK_PipeHandle *pipe_stdout, - const char *filename, - char *const argv[]) +static struct GNUNET_OS_Process * +start_process (int pipe_control, + enum GNUNET_OS_InheritStdioFlags std_inheritance, + struct GNUNET_DISK_PipeHandle *pipe_stdin, + struct GNUNET_DISK_PipeHandle *pipe_stdout, + const SOCKTYPE *lsocks, + const char *filename, + char *const argv[]) { #ifndef MINGW - char *childpipename = NULL; - struct GNUNET_OS_Process *gnunet_proc = NULL; pid_t ret; + char lpid[16]; + char fds[16]; + struct GNUNET_OS_Process *gnunet_proc; + char *childpipename = NULL; + int i; + int j; + int k; + int tgt; + int flags; + int *lscp; + unsigned int ls; int fd_stdout_write; int fd_stdout_read; int fd_stdin_read; int fd_stdin_write; + if (GNUNET_SYSERR == GNUNET_OS_check_helper_binary (filename)) + return NULL; /* not executable */ if ( (GNUNET_YES == pipe_control) && - (GNUNET_OK != - npipe_setup (&childpipename)) ) - return NULL; - if (pipe_stdout != NULL) + (GNUNET_OK != npipe_setup (&childpipename)) ) + { + GNUNET_free (childpipename); + return NULL; + } + if (NULL != pipe_stdout) { GNUNET_assert (GNUNET_OK == GNUNET_DISK_internal_file_handle_ (GNUNET_DISK_pipe_handle @@ -796,7 +884,7 @@ GNUNET_OS_start_process_vap (int pipe_control, (pipe_stdout, GNUNET_DISK_PIPE_END_READ), &fd_stdout_read, sizeof (int))); } - if (pipe_stdin != NULL) + if (NULL != pipe_stdin) { GNUNET_assert (GNUNET_OK == GNUNET_DISK_internal_file_handle_ (GNUNET_DISK_pipe_handle @@ -807,14 +895,28 @@ GNUNET_OS_start_process_vap (int pipe_control, (pipe_stdin, GNUNET_DISK_PIPE_END_WRITE), &fd_stdin_write, sizeof (int))); } - + lscp = NULL; + ls = 0; + if (NULL != lsocks) + { + i = 0; + while (-1 != (k = lsocks[i++])) + GNUNET_array_append (lscp, ls, k); + GNUNET_array_append (lscp, ls, -1); + } +#if DARWIN + /* see https://gnunet.org/vfork */ + ret = vfork (); +#else ret = fork (); +#endif if (-1 == ret) { int eno = errno; LOG_STRERROR (GNUNET_ERROR_TYPE_ERROR, "fork"); GNUNET_free_non_null (childpipename); + GNUNET_array_grow (lscp, ls, 0); errno = eno; return NULL; } @@ -822,62 +924,141 @@ GNUNET_OS_start_process_vap (int pipe_control, { gnunet_proc = GNUNET_malloc (sizeof (struct GNUNET_OS_Process)); gnunet_proc->pid = ret; - gnunet_proc->childpipename = childpipename; + gnunet_proc->childpipename = childpipename; + GNUNET_array_grow (lscp, ls, 0); return gnunet_proc; } if (NULL != childpipename) { setenv (GNUNET_OS_CONTROL_PIPE, childpipename, 1); +#ifndef DARWIN + /* due to vfork, we must NOT free memory on DARWIN! */ GNUNET_free (childpipename); +#endif + } + if (NULL != pipe_stdin) + { + GNUNET_break (0 == close (fd_stdin_write)); + if (-1 == dup2 (fd_stdin_read, 0)) + LOG_STRERROR (GNUNET_ERROR_TYPE_ERROR, "dup2"); + GNUNET_break (0 == close (fd_stdin_read)); } - if (pipe_stdout != NULL) + else if (0 == (std_inheritance & GNUNET_OS_INHERIT_STD_IN)) + { + GNUNET_break (0 == close (0)); + open_dev_null (0, O_RDONLY); + } + if (NULL != pipe_stdout) { GNUNET_break (0 == close (fd_stdout_read)); if (-1 == dup2 (fd_stdout_write, 1)) LOG_STRERROR (GNUNET_ERROR_TYPE_ERROR, "dup2"); GNUNET_break (0 == close (fd_stdout_write)); } - - if (pipe_stdin != NULL) + else if (0 == (std_inheritance & GNUNET_OS_INHERIT_STD_OUT)) { - - GNUNET_break (0 == close (fd_stdin_write)); - if (-1 == dup2 (fd_stdin_read, 0)) - LOG_STRERROR (GNUNET_ERROR_TYPE_ERROR, "dup2"); - GNUNET_break (0 == close (fd_stdin_read)); + GNUNET_break (0 == close (1)); + open_dev_null (1, O_WRONLY); + } + if (0 == (std_inheritance & GNUNET_OS_INHERIT_STD_ERR)) + { + GNUNET_break (0 == close (2)); + open_dev_null (2, O_WRONLY); + } + if (NULL != lscp) + { + /* read systemd documentation... */ + GNUNET_snprintf (lpid, sizeof (lpid), "%u", getpid ()); + setenv ("LISTEN_PID", lpid, 1); + i = 0; + tgt = 3; + while (-1 != lscp[i]) + { + j = i + 1; + while (-1 != lscp[j]) + { + if (lscp[j] == tgt) + { + /* dup away */ + k = dup (lscp[j]); + GNUNET_assert (-1 != k); + GNUNET_assert (0 == close (lscp[j])); + lscp[j] = k; + break; + } + j++; + } + if (lscp[i] != tgt) + { + /* Bury any existing FD, no matter what; they should all be closed + * on exec anyway and the important onces have been dup'ed away */ + (void) close (tgt); + GNUNET_assert (-1 != dup2 (lscp[i], tgt)); + } + /* unset close-on-exec flag */ + flags = fcntl (tgt, F_GETFD); + GNUNET_assert (flags >= 0); + flags &= ~FD_CLOEXEC; + fflush (stderr); + (void) fcntl (tgt, F_SETFD, flags); + tgt++; + i++; + } + GNUNET_snprintf (fds, sizeof (fds), "%u", i); + setenv ("LISTEN_FDS", fds, 1); } +#ifndef DARWIN + /* due to vfork, we must NOT free memory on DARWIN! */ + GNUNET_array_grow (lscp, ls, 0); +#endif execvp (filename, argv); LOG_STRERROR_FILE (GNUNET_ERROR_TYPE_ERROR, "execvp", filename); _exit (1); #else + struct GNUNET_DISK_FileHandle *control_pipe; char *childpipename = NULL; - struct GNUNET_OS_Process *gnunet_proc = NULL; - char *arg; + char **arg; + char **non_const_argv; unsigned int cmdlen; - char *cmd, *idx; + char *cmd; + char *idx; STARTUPINFOW start; PROCESS_INFORMATION proc; - int argc, arg_count; - HANDLE stdin_handle; - HANDLE stdout_handle; - struct GNUNET_DISK_FileHandle *control_pipe; - + int argcount = 0; + struct GNUNET_OS_Process *gnunet_proc; char path[MAX_PATH + 1]; - - char *our_env[3] = { NULL, NULL, NULL }; + char *our_env[5] = { NULL, NULL, NULL, NULL, NULL }; char *env_block = NULL; char *pathbuf; - DWORD pathbuf_len, alloc_len; + DWORD pathbuf_len; + DWORD alloc_len; char *self_prefix; char *bindir; char *libdir; char *ptr; char *non_const_filename; char win_path[MAX_PATH + 1]; - wchar_t *wpath, *wcmd; - size_t wpath_len, wcmd_len; + struct GNUNET_DISK_PipeHandle *lsocks_pipe; + const struct GNUNET_DISK_FileHandle *lsocks_write_fd; + HANDLE lsocks_read; + HANDLE lsocks_write; + wchar_t *wpath; + wchar_t *wcmd; + size_t wpath_len; + size_t wcmd_len; + int env_off; + int fail; long lRet; - + HANDLE stdin_handle; + HANDLE stdout_handle; + HANDLE stdih, stdoh, stdeh; + DWORD stdif, stdof, stdef; + BOOL bresult; + DWORD error_code; + + if (GNUNET_SYSERR == GNUNET_OS_check_helper_binary (filename)) + return NULL; /* not executable */ + /* Search in prefix dir (hopefully - the directory from which * the current module was loaded), bindir and libdir, then in PATH */ @@ -900,10 +1081,15 @@ GNUNET_OS_start_process_vap (int pipe_control, GNUNET_free (libdir); alloc_len = GetEnvironmentVariableA ("PATH", ptr, pathbuf_len); - GNUNET_assert (alloc_len == (pathbuf_len - 1)); + if (alloc_len != pathbuf_len - 1) + { + GNUNET_free (pathbuf); + errno = ENOSYS; /* PATH changed on the fly. What kind of error is that? */ + return NULL; + } cmdlen = strlen (filename); - if (cmdlen < 5 || strcmp (&filename[cmdlen - 4], ".exe") != 0) + if ( (cmdlen < 5) || (0 != strcmp (&filename[cmdlen - 4], ".exe")) ) GNUNET_asprintf (&non_const_filename, "%s.exe", filename); else GNUNET_asprintf (&non_const_filename, "%s", filename); @@ -911,16 +1097,16 @@ GNUNET_OS_start_process_vap (int pipe_control, /* It could be in POSIX form, convert it to a DOS path early on */ if (ERROR_SUCCESS != (lRet = plibc_conv_to_win_path (non_const_filename, win_path))) { - SetErrnoFromWinError (lRet); - LOG_STRERROR_FILE (GNUNET_ERROR_TYPE_ERROR, "plibc_conv_to_win_path", - non_const_filename); - GNUNET_free (non_const_filename); - GNUNET_free (pathbuf); - return NULL; + SetErrnoFromWinError (lRet); + LOG_STRERROR_FILE (GNUNET_ERROR_TYPE_ERROR, "plibc_conv_to_win_path", + non_const_filename); + GNUNET_free (non_const_filename); + GNUNET_free (pathbuf); + return NULL; } GNUNET_free (non_const_filename); non_const_filename = GNUNET_strdup (win_path); - /* Check that this is the full path. If it isn't, search. */ + /* Check that this is the full path. If it isn't, search. */ /* FIXME: convert it to wchar_t and use SearchPathW? * Remember: arguments to _start_process() are technically in UTF-8... */ @@ -940,37 +1126,62 @@ GNUNET_OS_start_process_vap (int pipe_control, GNUNET_free (pathbuf); GNUNET_free (non_const_filename); - cmdlen = 0; - argc = 0; - while (NULL != (arg = argv[argc++])) + /* Count the number of arguments */ + arg = (char **) argv; + while (*arg) { - if (cmdlen == 0) - cmdlen = cmdlen + strlen (path) + 4; - else - cmdlen = cmdlen + strlen (arg) + 4; + arg++; + argcount++; } - arg_count = argc; - cmd = idx = GNUNET_malloc (sizeof (char) * (cmdlen + 1)); - argc = 0; - while (NULL != (arg = argv[argc++])) + /* Allocate a copy argv */ + non_const_argv = GNUNET_malloc (sizeof (char *) * (argcount + 1)); + + /* Copy all argv strings */ + argcount = 0; + arg = (char **) argv; + while (*arg) { - /* This is to escape trailing slash */ - char arg_lastchar = arg[strlen (arg) - 1]; - if (idx == cmd) - idx += sprintf (idx, "\"%s%s\"%s", path, - arg_lastchar == '\\' ? "\\" : "", argc + 1 == arg_count ? "" : " "); + if (arg == argv) + non_const_argv[argcount] = GNUNET_strdup (path); else - idx += sprintf (idx, "\"%s%s\"%s", arg, - arg_lastchar == '\\' ? "\\" : "", argc + 1 == arg_count ? "" : " "); + non_const_argv[argcount] = GNUNET_strdup (*arg); + arg++; + argcount++; + } + non_const_argv[argcount] = NULL; + + /* Count cmd len */ + cmdlen = 1; + arg = non_const_argv; + while (*arg) + { + cmdlen = cmdlen + strlen (*arg) + 4; + arg++; + } + + /* Allocate and create cmd */ + cmd = idx = GNUNET_malloc (sizeof (char) * cmdlen); + arg = non_const_argv; + while (*arg) + { + char arg_last_char = (*arg)[strlen (*arg) - 1]; + idx += sprintf (idx, "\"%s%s\"%s", *arg, + arg_last_char == '\\' ? "\\" : "", *(arg + 1) ? " " : ""); + arg++; } + while (argcount > 0) + GNUNET_free (non_const_argv[--argcount]); + GNUNET_free (non_const_argv); + memset (&start, 0, sizeof (start)); start.cb = sizeof (start); - - if ((pipe_stdin != NULL) || (pipe_stdout != NULL)) + if ((pipe_stdin != NULL) || (pipe_stdout != NULL) || (std_inheritance != 0)) start.dwFlags |= STARTF_USESTDHANDLES; + stdih = GetStdHandle (STD_INPUT_HANDLE); + GetHandleInformation (stdih, &stdif); if (pipe_stdin != NULL) { GNUNET_DISK_internal_file_handle_ (GNUNET_DISK_pipe_handle @@ -978,8 +1189,22 @@ GNUNET_OS_start_process_vap (int pipe_control, &stdin_handle, sizeof (HANDLE)); start.hStdInput = stdin_handle; } + if (stdih) + { + if (std_inheritance & GNUNET_OS_INHERIT_STD_IN) + { + SetHandleInformation (stdih, HANDLE_FLAG_INHERIT, 1); + if (pipe_stdin == NULL) + start.hStdInput = stdih; + } + else + SetHandleInformation (stdih, HANDLE_FLAG_INHERIT, 0); + } + - if (pipe_stdout != NULL) + stdoh = GetStdHandle (STD_OUTPUT_HANDLE); + GetHandleInformation (stdoh, &stdof); + if (NULL != pipe_stdout) { GNUNET_DISK_internal_file_handle_ (GNUNET_DISK_pipe_handle (pipe_stdout, @@ -987,6 +1212,31 @@ GNUNET_OS_start_process_vap (int pipe_control, &stdout_handle, sizeof (HANDLE)); start.hStdOutput = stdout_handle; } + if (stdoh) + { + if (std_inheritance & GNUNET_OS_INHERIT_STD_OUT) + { + SetHandleInformation (stdoh, HANDLE_FLAG_INHERIT, 1); + if (pipe_stdout == NULL) + start.hStdOutput = stdoh; + } + else + SetHandleInformation (stdoh, HANDLE_FLAG_INHERIT, 0); + } + + stdeh = GetStdHandle (STD_ERROR_HANDLE); + GetHandleInformation (stdeh, &stdef); + if (stdeh) + { + if (std_inheritance & GNUNET_OS_INHERIT_STD_ERR) + { + SetHandleInformation (stdeh, HANDLE_FLAG_INHERIT, 1); + start.hStdError = stdeh; + } + else + SetHandleInformation (stdeh, HANDLE_FLAG_INHERIT, 0); + } + if (GNUNET_YES == pipe_control) { control_pipe = @@ -1002,457 +1252,40 @@ GNUNET_OS_start_process_vap (int pipe_control, } else control_pipe = NULL; + if (lsocks != NULL && lsocks[0] != INVALID_SOCKET) + { + lsocks_pipe = GNUNET_DISK_pipe (GNUNET_YES, GNUNET_YES, GNUNET_YES, GNUNET_NO); + + if (lsocks_pipe == NULL) + { + GNUNET_free (cmd); + GNUNET_free (path); + GNUNET_DISK_pipe_close (lsocks_pipe); + return NULL; + } + lsocks_write_fd = GNUNET_DISK_pipe_handle (lsocks_pipe, + GNUNET_DISK_PIPE_END_WRITE); + GNUNET_DISK_internal_file_handle_ (lsocks_write_fd, + &lsocks_write, sizeof (HANDLE)); + GNUNET_DISK_internal_file_handle_ (GNUNET_DISK_pipe_handle + (lsocks_pipe, GNUNET_DISK_PIPE_END_READ), + &lsocks_read, sizeof (HANDLE)); + } + + env_off = 0; if (NULL != childpipename) { LOG (GNUNET_ERROR_TYPE_DEBUG, "Opened the parent end of the pipe `%s'\n", childpipename); - GNUNET_asprintf (&our_env[0], "%s=", GNUNET_OS_CONTROL_PIPE); - GNUNET_asprintf (&our_env[1], "%s", childpipename); - our_env[2] = NULL; + GNUNET_asprintf (&our_env[env_off++], "%s=", GNUNET_OS_CONTROL_PIPE); + GNUNET_asprintf (&our_env[env_off++], "%s", childpipename); + GNUNET_free (childpipename); } - else + if ( (lsocks != NULL) && (lsocks[0] != INVALID_SOCKET)) { - our_env[0] = NULL; - } - env_block = CreateCustomEnvTable (our_env); - GNUNET_free_non_null (our_env[0]); - GNUNET_free_non_null (our_env[1]); - - wpath_len = 0; - if (NULL == (wpath = u8_to_u16 ((uint8_t *) path, 1 + strlen (path), NULL, &wpath_len))) - { - LOG (GNUNET_ERROR_TYPE_DEBUG, - "Failed to convert `%s' from UTF-8 to UTF-16: %d\n", path, errno); - GNUNET_free (env_block); - GNUNET_free (cmd); - return NULL; - } - - wcmd_len = 0; - if (NULL == (wcmd = u8_to_u16 ((uint8_t *) cmd, 1 + strlen (cmd), NULL, &wcmd_len))) - { - LOG (GNUNET_ERROR_TYPE_DEBUG, - "Failed to convert `%s' from UTF-8 to UTF-16: %d\n", cmd, errno); - GNUNET_free (env_block); - GNUNET_free (cmd); - free (wpath); - return NULL; - } - - if (!CreateProcessW (wpath, wcmd, NULL, NULL, TRUE, - DETACHED_PROCESS | CREATE_SUSPENDED, env_block, NULL, &start, &proc)) - { - SetErrnoFromWinError (GetLastError ()); - LOG_STRERROR_FILE (GNUNET_ERROR_TYPE_ERROR, "CreateProcess", path); - GNUNET_free (env_block); - GNUNET_free (cmd); - free (wpath); - free (wcmd); - return NULL; - } - - GNUNET_free (env_block); - - gnunet_proc = GNUNET_malloc (sizeof (struct GNUNET_OS_Process)); - gnunet_proc->pid = proc.dwProcessId; - gnunet_proc->handle = proc.hProcess; - gnunet_proc->control_pipe = control_pipe; - - CreateThread (NULL, 64000, &child_wait_thread, (void *) gnunet_proc, 0, NULL); - - ResumeThread (proc.hThread); - CloseHandle (proc.hThread); - - GNUNET_free (cmd); - free (wpath); - free (wcmd); - return gnunet_proc; -#endif -} - - -/** - * Start a process. - * - * @param pipe_control should a pipe be used to send signals to the child? - * @param pipe_stdin pipe to use to send input to child process (or NULL) - * @param pipe_stdout pipe to use to get output from child process (or NULL) - * @param filename name of the binary - * @param va NULL-terminated list of arguments to the process - * @return pointer to process structure of the new process, NULL on error - */ -struct GNUNET_OS_Process * -GNUNET_OS_start_process_va (int pipe_control, - struct GNUNET_DISK_PipeHandle *pipe_stdin, - struct GNUNET_DISK_PipeHandle *pipe_stdout, - const char *filename, va_list va) -{ - struct GNUNET_OS_Process *ret; - va_list ap; - char **argv; - int argc; - - argc = 0; - va_copy (ap, va); - while (NULL != va_arg (ap, char *)) - argc++; - va_end (ap); - argv = GNUNET_malloc (sizeof (char *) * (argc + 1)); - argc = 0; - va_copy (ap, va); - while (NULL != (argv[argc] = va_arg (ap, char *))) - argc++; - va_end (ap); - ret = GNUNET_OS_start_process_vap (pipe_control, - pipe_stdin, - pipe_stdout, - filename, - argv); - GNUNET_free (argv); - return ret; -} - - - -/** - * Start a process. - * - * @param pipe_control should a pipe be used to send signals to the child? - * @param pipe_stdin pipe to use to send input to child process (or NULL) - * @param pipe_stdout pipe to use to get output from child process (or NULL) - * @param filename name of the binary - * @param ... NULL-terminated list of arguments to the process - * - * @return pointer to process structure of the new process, NULL on error - * - */ -struct GNUNET_OS_Process * -GNUNET_OS_start_process (int pipe_control, - struct GNUNET_DISK_PipeHandle *pipe_stdin, - struct GNUNET_DISK_PipeHandle *pipe_stdout, - const char *filename, ...) -{ - struct GNUNET_OS_Process *ret; - va_list ap; - - va_start (ap, filename); - ret = GNUNET_OS_start_process_va (pipe_control, pipe_stdin, pipe_stdout, filename, ap); - va_end (ap); - return ret; -} - - -/** - * Start a process. - * - * @param pipe_control should a pipe be used to send signals to the child? - * @param lsocks array of listen sockets to dup systemd-style (or NULL); - * must be NULL on platforms where dup is not supported - * @param filename name of the binary - * @param argv NULL-terminated list of arguments to the process - * @return process ID of the new process, -1 on error - */ -struct GNUNET_OS_Process * -GNUNET_OS_start_process_v (int pipe_control, - const SOCKTYPE *lsocks, - const char *filename, - char *const argv[]) -{ -#ifndef MINGW - pid_t ret; - char lpid[16]; - char fds[16]; - struct GNUNET_OS_Process *gnunet_proc = NULL; - char *childpipename = NULL; - int i; - int j; - int k; - int tgt; - int flags; - int *lscp; - unsigned int ls; - - if ( (GNUNET_YES == pipe_control) && - (GNUNET_OK != npipe_setup (&childpipename)) ) - return NULL; - lscp = NULL; - ls = 0; - if (lsocks != NULL) - { - i = 0; - while (-1 != (k = lsocks[i++])) - GNUNET_array_append (lscp, ls, k); - GNUNET_array_append (lscp, ls, -1); - } - ret = fork (); - if (-1 == ret) - { - int eno = errno; - - LOG_STRERROR (GNUNET_ERROR_TYPE_ERROR, "fork"); - GNUNET_free_non_null (childpipename); - GNUNET_array_grow (lscp, ls, 0); - errno = eno; - return NULL; - } - if (0 != ret) - { - gnunet_proc = GNUNET_malloc (sizeof (struct GNUNET_OS_Process)); - gnunet_proc->pid = ret; - gnunet_proc->childpipename = childpipename; - GNUNET_array_grow (lscp, ls, 0); - return gnunet_proc; - } - if (NULL != childpipename) - { - setenv (GNUNET_OS_CONTROL_PIPE, childpipename, 1); - GNUNET_free (childpipename); - } - if (lscp != NULL) - { - /* read systemd documentation... */ - GNUNET_snprintf (lpid, sizeof (lpid), "%u", getpid ()); - setenv ("LISTEN_PID", lpid, 1); - i = 0; - tgt = 3; - while (-1 != lscp[i]) - { - j = i + 1; - while (-1 != lscp[j]) - { - if (lscp[j] == tgt) - { - /* dup away */ - k = dup (lscp[j]); - GNUNET_assert (-1 != k); - GNUNET_assert (0 == close (lscp[j])); - lscp[j] = k; - break; - } - j++; - } - if (lscp[i] != tgt) - { - /* Bury any existing FD, no matter what; they should all be closed - * on exec anyway and the important onces have been dup'ed away */ - (void) close (tgt); - GNUNET_assert (-1 != dup2 (lscp[i], tgt)); - } - /* unset close-on-exec flag */ - flags = fcntl (tgt, F_GETFD); - GNUNET_assert (flags >= 0); - flags &= ~FD_CLOEXEC; - fflush (stderr); - (void) fcntl (tgt, F_SETFD, flags); - tgt++; - i++; - } - GNUNET_snprintf (fds, sizeof (fds), "%u", i); - setenv ("LISTEN_FDS", fds, 1); - } - GNUNET_array_grow (lscp, ls, 0); - execvp (filename, argv); - LOG_STRERROR_FILE (GNUNET_ERROR_TYPE_ERROR, "execvp", filename); - _exit (1); -#else - struct GNUNET_DISK_FileHandle *control_pipe = NULL; - char *childpipename = NULL; - char **arg, **non_const_argv; - unsigned int cmdlen; - char *cmd, *idx; - STARTUPINFOW start; - PROCESS_INFORMATION proc; - int argcount = 0; - struct GNUNET_OS_Process *gnunet_proc = NULL; - char path[MAX_PATH + 1]; - char *our_env[5] = { NULL, NULL, NULL, NULL, NULL }; - char *env_block = NULL; - char *pathbuf; - DWORD pathbuf_len, alloc_len; - char *self_prefix; - char *bindir; - char *libdir; - char *ptr; - char *non_const_filename; - char win_path[MAX_PATH + 1]; - struct GNUNET_DISK_PipeHandle *lsocks_pipe; - const struct GNUNET_DISK_FileHandle *lsocks_write_fd; - HANDLE lsocks_read; - HANDLE lsocks_write; - wchar_t *wpath, *wcmd; - size_t wpath_len, wcmd_len; - int env_off; - int fail; - long lRet; - - /* Search in prefix dir (hopefully - the directory from which - * the current module was loaded), bindir and libdir, then in PATH - */ - self_prefix = GNUNET_OS_installation_get_path (GNUNET_OS_IPK_SELF_PREFIX); - bindir = GNUNET_OS_installation_get_path (GNUNET_OS_IPK_BINDIR); - libdir = GNUNET_OS_installation_get_path (GNUNET_OS_IPK_LIBDIR); - - pathbuf_len = GetEnvironmentVariableA ("PATH", (char *) &pathbuf, 0); - - alloc_len = - pathbuf_len + 1 + strlen (self_prefix) + 1 + strlen (bindir) + 1 + - strlen (libdir); - - pathbuf = GNUNET_malloc (alloc_len * sizeof (char)); - - ptr = pathbuf; - ptr += sprintf (pathbuf, "%s;%s;%s;", self_prefix, bindir, libdir); - GNUNET_free (self_prefix); - GNUNET_free (bindir); - GNUNET_free (libdir); - - alloc_len = GetEnvironmentVariableA ("PATH", ptr, pathbuf_len); - if (alloc_len != pathbuf_len - 1) - { - GNUNET_free (pathbuf); - errno = ENOSYS; /* PATH changed on the fly. What kind of error is that? */ - return NULL; - } - - cmdlen = strlen (filename); - if (cmdlen < 5 || strcmp (&filename[cmdlen - 4], ".exe") != 0) - GNUNET_asprintf (&non_const_filename, "%s.exe", filename); - else - GNUNET_asprintf (&non_const_filename, "%s", filename); - - /* It could be in POSIX form, convert it to a DOS path early on */ - if (ERROR_SUCCESS != (lRet = plibc_conv_to_win_path (non_const_filename, win_path))) - { - SetErrnoFromWinError (lRet); - LOG_STRERROR_FILE (GNUNET_ERROR_TYPE_ERROR, "plibc_conv_to_win_path", - non_const_filename); - GNUNET_free (non_const_filename); - GNUNET_free (pathbuf); - return NULL; - } - GNUNET_free (non_const_filename); - non_const_filename = GNUNET_strdup (win_path); - /* Check that this is the full path. If it isn't, search. */ - /* FIXME: convert it to wchar_t and use SearchPathW? - * Remember: arguments to _start_process() are technically in UTF-8... - */ - if (non_const_filename[1] == ':') - snprintf (path, sizeof (path) / sizeof (char), "%s", non_const_filename); - else if (!SearchPathA - (pathbuf, non_const_filename, NULL, sizeof (path) / sizeof (char), - path, NULL)) - { - SetErrnoFromWinError (GetLastError ()); - LOG_STRERROR_FILE (GNUNET_ERROR_TYPE_ERROR, "SearchPath", - non_const_filename); - GNUNET_free (non_const_filename); - GNUNET_free (pathbuf); - return NULL; - } - GNUNET_free (pathbuf); - GNUNET_free (non_const_filename); - - /* Count the number of arguments */ - arg = (char **) argv; - while (*arg) - { - arg++; - argcount++; - } - - /* Allocate a copy argv */ - non_const_argv = GNUNET_malloc (sizeof (char *) * (argcount + 1)); - - /* Copy all argv strings */ - argcount = 0; - arg = (char **) argv; - while (*arg) - { - if (arg == argv) - non_const_argv[argcount] = GNUNET_strdup (path); - else - non_const_argv[argcount] = GNUNET_strdup (*arg); - arg++; - argcount++; - } - non_const_argv[argcount] = NULL; - - /* Count cmd len */ - cmdlen = 1; - arg = non_const_argv; - while (*arg) - { - cmdlen = cmdlen + strlen (*arg) + 4; - arg++; - } - - /* Allocate and create cmd */ - cmd = idx = GNUNET_malloc (sizeof (char) * cmdlen); - arg = non_const_argv; - while (*arg) - { - char arg_last_char = (*arg)[strlen (*arg) - 1]; - idx += sprintf (idx, "\"%s%s\"%s", *arg, - arg_last_char == '\\' ? "\\" : "", *(arg + 1) ? " " : ""); - arg++; - } - - while (argcount > 0) - GNUNET_free (non_const_argv[--argcount]); - GNUNET_free (non_const_argv); - - memset (&start, 0, sizeof (start)); - start.cb = sizeof (start); - - if (GNUNET_YES == pipe_control) - { - control_pipe = - npipe_create (&childpipename, GNUNET_DISK_OPEN_WRITE, - GNUNET_DISK_PERM_USER_READ | - GNUNET_DISK_PERM_USER_WRITE); - if (control_pipe == NULL) - { - GNUNET_free (cmd); - GNUNET_free (path); - return NULL; - } - } - else - control_pipe = NULL; - if (lsocks != NULL && lsocks[0] != INVALID_SOCKET) - { - lsocks_pipe = GNUNET_DISK_pipe (GNUNET_YES, GNUNET_YES, GNUNET_YES, GNUNET_NO); - - if (lsocks_pipe == NULL) - { - GNUNET_free (cmd); - GNUNET_free (path); - GNUNET_DISK_pipe_close (lsocks_pipe); - return NULL; - } - lsocks_write_fd = GNUNET_DISK_pipe_handle (lsocks_pipe, - GNUNET_DISK_PIPE_END_WRITE); - GNUNET_DISK_internal_file_handle_ (lsocks_write_fd, - &lsocks_write, sizeof (HANDLE)); - GNUNET_DISK_internal_file_handle_ (GNUNET_DISK_pipe_handle - (lsocks_pipe, GNUNET_DISK_PIPE_END_READ), - &lsocks_read, sizeof (HANDLE)); - } - - env_off = 0; - if (NULL != childpipename) - { - LOG (GNUNET_ERROR_TYPE_DEBUG, "Opened the parent end of the pipe `%s'\n", - childpipename); - GNUNET_asprintf (&our_env[env_off++], "%s=", GNUNET_OS_CONTROL_PIPE); - GNUNET_asprintf (&our_env[env_off++], "%s", childpipename); - GNUNET_free (childpipename); - } - if ( (lsocks != NULL) && (lsocks[0] != INVALID_SOCKET)) - { - /*This will tell the child that we're going to send lsocks over the pipe*/ - GNUNET_asprintf (&our_env[env_off++], "%s=", "GNUNET_OS_READ_LSOCKS"); - GNUNET_asprintf (&our_env[env_off++], "%lu", lsocks_read); + /*This will tell the child that we're going to send lsocks over the pipe*/ + GNUNET_asprintf (&our_env[env_off++], "%s=", "GNUNET_OS_READ_LSOCKS"); + GNUNET_asprintf (&our_env[env_off++], "%lu", lsocks_read); } our_env[env_off++] = NULL; env_block = CreateCustomEnvTable (our_env); @@ -1480,24 +1313,36 @@ GNUNET_OS_start_process_v (int pipe_control, return NULL; } - if (!CreateProcessW (wpath, wcmd, NULL, NULL, TRUE, - DETACHED_PROCESS | CREATE_SUSPENDED, env_block, NULL, &start, &proc)) + bresult = CreateProcessW (wpath, wcmd, NULL, NULL, TRUE, + DETACHED_PROCESS | CREATE_SUSPENDED, env_block, NULL, &start, &proc); + error_code = GetLastError (); + + if ((NULL == pipe_stdin) && (stdih)) + SetHandleInformation (stdih, HANDLE_FLAG_INHERIT, stdif); + + + if ((NULL == pipe_stdout) && (stdoh)) + SetHandleInformation (stdoh, HANDLE_FLAG_INHERIT, stdof); + + if (stdeh) + SetHandleInformation (stdeh, HANDLE_FLAG_INHERIT, stdef); + + GNUNET_free (env_block); + GNUNET_free (cmd); + free (wpath); + free (wcmd); + + if (!bresult) { - SetErrnoFromWinError (GetLastError ()); + SetErrnoFromWinError (error_code); LOG_STRERROR (GNUNET_ERROR_TYPE_ERROR, "CreateProcess"); if (NULL != control_pipe) GNUNET_DISK_file_close (control_pipe); if (NULL != lsocks) GNUNET_DISK_pipe_close (lsocks_pipe); - GNUNET_free (env_block); - GNUNET_free (cmd); - free (wpath); - free (wcmd); return NULL; } - GNUNET_free (env_block); - gnunet_proc = GNUNET_malloc (sizeof (struct GNUNET_OS_Process)); gnunet_proc->pid = proc.dwProcessId; gnunet_proc->handle = proc.hProcess; @@ -1507,11 +1352,8 @@ GNUNET_OS_start_process_v (int pipe_control, ResumeThread (proc.hThread); CloseHandle (proc.hThread); - GNUNET_free (cmd); - free (wpath); - free (wcmd); - if (lsocks == NULL || lsocks[0] == INVALID_SOCKET) + if ( (NULL == lsocks) || (INVALID_SOCKET == lsocks[0]) ) return gnunet_proc; GNUNET_DISK_pipe_close_end (lsocks_pipe, GNUNET_DISK_PIPE_END_READ); @@ -1520,16 +1362,20 @@ GNUNET_OS_start_process_v (int pipe_control, fail = 1; do { - int wrote; - uint64_t size, count, i; + ssize_t wrote; + uint64_t size; + uint64_t count; + unsigned int i; /* Tell the number of sockets */ for (count = 0; lsocks && lsocks[count] != INVALID_SOCKET; count++); wrote = GNUNET_DISK_file_write (lsocks_write_fd, &count, sizeof (count)); - if (wrote != sizeof (count)) + if (sizeof (count) != wrote) { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Failed to write %u count bytes to the child: %u\n", sizeof (count), GetLastError ()); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Failed to write %u count bytes to the child: %u\n", + sizeof (count), GetLastError ()); break; } for (i = 0; lsocks && lsocks[i] != INVALID_SOCKET; i++) @@ -1538,8 +1384,9 @@ GNUNET_OS_start_process_v (int pipe_control, /* Get a socket duplication info */ if (SOCKET_ERROR == WSADuplicateSocketA (lsocks[i], gnunet_proc->pid, &pi)) { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Failed to duplicate an socket[%llu]: %u\n", i, GetLastError ()); - LOG_STRERROR (GNUNET_ERROR_TYPE_ERROR, "CreateProcess"); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Failed to duplicate an socket[%llu]: %u\n", i, + GetLastError ()); break; } /* Synchronous I/O is not nice, but we can't schedule this: @@ -1552,16 +1399,20 @@ GNUNET_OS_start_process_v (int pipe_control, */ size = sizeof (pi); wrote = GNUNET_DISK_file_write (lsocks_write_fd, &size, sizeof (size)); - if (wrote != sizeof (size)) + if (sizeof (size) != wrote) { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Failed to write %u size[%llu] bytes to the child: %u\n", sizeof (size), i, GetLastError ()); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Failed to write %u size[%llu] bytes to the child: %u\n", + sizeof (size), i, GetLastError ()); break; } /* Finally! Send the data */ wrote = GNUNET_DISK_file_write (lsocks_write_fd, &pi, sizeof (pi)); - if (wrote != sizeof (pi)) + if (sizeof (pi) != wrote) { - GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Failed to write %u socket[%llu] bytes to the child: %u\n", sizeof (pi), i, GetLastError ()); + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + "Failed to write %u socket[%llu] bytes to the child: %u\n", + sizeof (pi), i, GetLastError ()); break; } } @@ -1583,7 +1434,7 @@ GNUNET_OS_start_process_v (int pipe_control, /* If we can't pass on the socket(s), the child will block forever, * better put it out of its misery. */ - TerminateProcess (gnunet_proc->handle, 0); + SafeTerminateProcess (gnunet_proc->handle, 0, 0); CloseHandle (gnunet_proc->handle); if (NULL != gnunet_proc->control_pipe) GNUNET_DISK_file_close (gnunet_proc->control_pipe); @@ -1595,6 +1446,142 @@ GNUNET_OS_start_process_v (int pipe_control, } + + +/** + * Start a process. + * + * @param pipe_control should a pipe be used to send signals to the child? + * @param std_inheritance a set of GNUNET_OS_INHERIT_STD_* flags + * @param pipe_stdin pipe to use to send input to child process (or NULL) + * @param pipe_stdout pipe to use to get output from child process (or NULL) + * @param filename name of the binary + * @param argv NULL-terminated array of arguments to the process + * @return pointer to process structure of the new process, NULL on error + */ +struct GNUNET_OS_Process * +GNUNET_OS_start_process_vap (int pipe_control, + enum GNUNET_OS_InheritStdioFlags std_inheritance, + struct GNUNET_DISK_PipeHandle *pipe_stdin, + struct GNUNET_DISK_PipeHandle *pipe_stdout, + const char *filename, + char *const argv[]) +{ + return start_process (pipe_control, + std_inheritance, + pipe_stdin, + pipe_stdout, + NULL, + filename, + argv); +} + + +/** + * Start a process. + * + * @param pipe_control should a pipe be used to send signals to the child? + * @param std_inheritance a set of GNUNET_OS_INHERIT_STD_* flags + * @param pipe_stdin pipe to use to send input to child process (or NULL) + * @param pipe_stdout pipe to use to get output from child process (or NULL) + * @param filename name of the binary + * @param va NULL-terminated list of arguments to the process + * @return pointer to process structure of the new process, NULL on error + */ +struct GNUNET_OS_Process * +GNUNET_OS_start_process_va (int pipe_control, + enum GNUNET_OS_InheritStdioFlags std_inheritance, + struct GNUNET_DISK_PipeHandle *pipe_stdin, + struct GNUNET_DISK_PipeHandle *pipe_stdout, + const char *filename, va_list va) +{ + struct GNUNET_OS_Process *ret; + va_list ap; + char **argv; + int argc; + + argc = 0; + va_copy (ap, va); + while (NULL != va_arg (ap, char *)) + argc++; + va_end (ap); + argv = GNUNET_malloc (sizeof (char *) * (argc + 1)); + argc = 0; + va_copy (ap, va); + while (NULL != (argv[argc] = va_arg (ap, char *))) + argc++; + va_end (ap); + ret = GNUNET_OS_start_process_vap (pipe_control, + std_inheritance, + pipe_stdin, + pipe_stdout, + filename, + argv); + GNUNET_free (argv); + return ret; +} + + +/** + * Start a process. + * + * @param pipe_control should a pipe be used to send signals to the child? + * @param std_inheritance a set of GNUNET_OS_INHERIT_STD_* flags + * @param pipe_stdin pipe to use to send input to child process (or NULL) + * @param pipe_stdout pipe to use to get output from child process (or NULL) + * @param filename name of the binary + * @param ... NULL-terminated list of arguments to the process + * @return pointer to process structure of the new process, NULL on error + */ +struct GNUNET_OS_Process * +GNUNET_OS_start_process (int pipe_control, + enum GNUNET_OS_InheritStdioFlags std_inheritance, + struct GNUNET_DISK_PipeHandle *pipe_stdin, + struct GNUNET_DISK_PipeHandle *pipe_stdout, + const char *filename, ...) +{ + struct GNUNET_OS_Process *ret; + va_list ap; + + va_start (ap, filename); + ret = GNUNET_OS_start_process_va (pipe_control, std_inheritance, pipe_stdin, + pipe_stdout, filename, ap); + va_end (ap); + return ret; +} + + +/** + * Start a process. + * + * @param pipe_control should a pipe be used to send signals to the child? + * @param std_inheritance a set of GNUNET_OS_INHERIT_STD_* flags controlling which + * std handles of the parent are inherited by the child. + * pipe_stdin and pipe_stdout take priority over std_inheritance + * (when they are non-NULL). + * @param lsocks array of listen sockets to dup systemd-style (or NULL); + * must be NULL on platforms where dup is not supported + * @param filename name of the binary + * @param argv NULL-terminated list of arguments to the process + * @return process ID of the new process, -1 on error + */ +struct GNUNET_OS_Process * +GNUNET_OS_start_process_v (int pipe_control, + enum GNUNET_OS_InheritStdioFlags std_inheritance, + const SOCKTYPE *lsocks, + const char *filename, + char *const argv[]) +{ + return start_process (pipe_control, + std_inheritance, + NULL, + NULL, + lsocks, + filename, + argv); +} + + /** * Retrieve the status of a process, waiting on him if dead. * Nonblocking version. @@ -1698,13 +1685,13 @@ GNUNET_OS_process_status (struct GNUNET_OS_Process *proc, /** * Wait for a process + * * @param proc pointer to process structure * @return GNUNET_OK on success, GNUNET_SYSERR otherwise */ int GNUNET_OS_process_wait (struct GNUNET_OS_Process *proc) { - #ifndef MINGW pid_t pid = proc->pid; pid_t ret; @@ -1719,7 +1706,6 @@ GNUNET_OS_process_wait (struct GNUNET_OS_Process *proc) return GNUNET_OK; #else HANDLE h; - int ret; h = proc->handle; if (NULL == h) @@ -1728,18 +1714,15 @@ GNUNET_OS_process_wait (struct GNUNET_OS_Process *proc) proc->pid, h); return GNUNET_SYSERR; } - if (h == NULL) + if (NULL == h) h = GetCurrentProcess (); if (WAIT_OBJECT_0 != WaitForSingleObject (h, INFINITE)) { SetErrnoFromWinError (GetLastError ()); - ret = GNUNET_SYSERR; + return GNUNET_SYSERR; } - else - ret = GNUNET_OK; - - return ret; + return GNUNET_OK; #endif } @@ -1807,8 +1790,7 @@ struct GNUNET_OS_CommandHandle void GNUNET_OS_command_stop (struct GNUNET_OS_CommandHandle *cmd) { - - if (cmd->proc != NULL) + if (NULL != cmd->proc) { GNUNET_assert (GNUNET_SCHEDULER_NO_TASK != cmd->rtask); GNUNET_SCHEDULER_cancel (cmd->rtask); @@ -1861,7 +1843,7 @@ cmd_read (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) } end = memchr (&cmd->buf[cmd->off], '\n', ret); cmd->off += ret; - while (end != NULL) + while (NULL != end) { *end = '\0'; cmd->proc (cmd->proc_cls, cmd->buf); @@ -1900,7 +1882,8 @@ GNUNET_OS_command_run (GNUNET_OS_LineProcessor proc, void *proc_cls, if (NULL == opipe) return NULL; va_start (ap, binary); - eip = GNUNET_OS_start_process_va (GNUNET_NO, NULL, opipe, binary, ap); + /* redirect stdout, don't inherit stderr/stdin */ + eip = GNUNET_OS_start_process_va (GNUNET_NO, 0, NULL, opipe, binary, ap); va_end (ap); if (NULL == eip) { @@ -1920,6 +1903,4 @@ GNUNET_OS_command_run (GNUNET_OS_LineProcessor proc, void *proc_cls, } - - /* end of os_priority.c */ diff --git a/src/util/peer.c b/src/util/peer.c index 2444cb9..1ad3ee2 100644 --- a/src/util/peer.c +++ b/src/util/peer.c @@ -53,7 +53,7 @@ struct PeerEntry /** * Table with our interned peer IDs. */ -static struct PeerEntry *table; +static struct PeerEntry **table; /** * Hashmap of PeerIdentities to "struct PeerEntry" @@ -84,15 +84,13 @@ GNUNET_PEER_Id GNUNET_PEER_search (const struct GNUNET_PeerIdentity *pid) { struct PeerEntry *e; - long off; - if (pid == NULL) + if (NULL == pid) return 0; if (NULL == map) return 0; - off = (long) GNUNET_CONTAINER_multihashmap_get (map, &pid->hashPubKey); - e = (off == 0) ? NULL : &table[off]; - if (e == NULL) + e = GNUNET_CONTAINER_multihashmap_get (map, &pid->hashPubKey); + if (NULL == e) return 0; GNUNET_assert (e->rc > 0); return e->pid; @@ -112,15 +110,13 @@ GNUNET_PEER_intern (const struct GNUNET_PeerIdentity *pid) GNUNET_PEER_Id ret; struct PeerEntry *e; unsigned int i; - long off; - if (pid == NULL) + if (NULL == pid) return 0; if (NULL == map) - map = GNUNET_CONTAINER_multihashmap_create (32); - off = (long) GNUNET_CONTAINER_multihashmap_get (map, &pid->hashPubKey); - e = (off == 0) ? NULL : &table[off]; - if (e != NULL) + map = GNUNET_CONTAINER_multihashmap_create (32, GNUNET_YES); + e = GNUNET_CONTAINER_multihashmap_get (map, &pid->hashPubKey); + if (NULL != e) { GNUNET_assert (e->rc > 0); e->rc++; @@ -131,23 +127,27 @@ GNUNET_PEER_intern (const struct GNUNET_PeerIdentity *pid) { GNUNET_array_grow (table, size, size + 16); for (i = ret; i < size; i++) - table[i].pid = i + 1; + { + table[i] = GNUNET_malloc (sizeof (struct PeerEntry)); + table[i]->pid = i + 1; + } } - if (ret == 0) + if (0 == ret) { - table[0].pid = 0; - table[0].rc = 1; + table[0]->pid = 0; + table[0]->rc = 1; ret = 1; } GNUNET_assert (ret < size); - GNUNET_assert (table[ret].rc == 0); - free_list_start = table[ret].pid; - table[ret].id = *pid; - table[ret].rc = 1; - table[ret].pid = ret; + GNUNET_assert (0 == table[ret]->rc); + free_list_start = table[ret]->pid; + table[ret]->id = *pid; + table[ret]->rc = 1; + table[ret]->pid = ret; GNUNET_break (GNUNET_OK == - GNUNET_CONTAINER_multihashmap_put (map, &pid->hashPubKey, - (void *) (long) ret, + GNUNET_CONTAINER_multihashmap_put (map, + &table[ret]->id.hashPubKey, + table[ret], GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY)); return ret; } @@ -165,24 +165,23 @@ GNUNET_PEER_decrement_rcs (const GNUNET_PEER_Id *ids, unsigned int count) int i; GNUNET_PEER_Id id; - if (count == 0) + if (0 == count) return; for (i = count - 1; i >= 0; i--) { id = ids[i]; - if (id == 0) + if (0 == id) continue; GNUNET_assert (id < size); - GNUNET_assert (table[id].rc > 0); - table[id].rc--; - if (table[id].rc == 0) + GNUNET_assert (table[id]->rc > 0); + table[id]->rc--; + if (0 == table[id]->rc) { GNUNET_break (GNUNET_OK == GNUNET_CONTAINER_multihashmap_remove (map, - &table[id]. - id.hashPubKey, - (void *) (long) id)); - table[id].pid = free_list_start; + &table[id]->id.hashPubKey, + table[id])); + table[id]->pid = free_list_start; free_list_start = id; } } @@ -198,20 +197,19 @@ GNUNET_PEER_decrement_rcs (const GNUNET_PEER_Id *ids, unsigned int count) void GNUNET_PEER_change_rc (GNUNET_PEER_Id id, int delta) { - if (id == 0) + if (0 == id) return; GNUNET_assert (id < size); - GNUNET_assert (table[id].rc > 0); - GNUNET_assert ((delta >= 0) || (table[id].rc >= -delta)); - table[id].rc += delta; - if (table[id].rc == 0) + GNUNET_assert (table[id]->rc > 0); + GNUNET_assert ((delta >= 0) || (table[id]->rc >= -delta)); + table[id]->rc += delta; + if (0 == table[id]->rc) { GNUNET_break (GNUNET_OK == GNUNET_CONTAINER_multihashmap_remove (map, - &table[id]. - id.hashPubKey, - (void *) (long) id)); - table[id].pid = free_list_start; + &table[id]->id.hashPubKey, + table[id])); + table[id]->pid = free_list_start; free_list_start = id; } } @@ -226,16 +224,30 @@ GNUNET_PEER_change_rc (GNUNET_PEER_Id id, int delta) void GNUNET_PEER_resolve (GNUNET_PEER_Id id, struct GNUNET_PeerIdentity *pid) { - if (id == 0) + if (0 == id) { memset (pid, 0, sizeof (struct GNUNET_PeerIdentity)); GNUNET_break (0); return; } GNUNET_assert (id < size); - GNUNET_assert (table[id].rc > 0); - *pid = table[id].id; + GNUNET_assert (table[id]->rc > 0); + *pid = table[id]->id; +} + + +/** + * Convert an interned PID to a normal peer identity. + * + * @param id interned PID to convert + * @return pointer to peer identity, valid as long 'id' is valid + */ +const struct GNUNET_PeerIdentity * +GNUNET_PEER_resolve2 (GNUNET_PEER_Id id) +{ + return &table[id]->id; } + /* end of peer.c */ diff --git a/src/util/perf_crypto_hash.c b/src/util/perf_crypto_hash.c index d883776..d1f4c9d 100644 --- a/src/util/perf_crypto_hash.c +++ b/src/util/perf_crypto_hash.c @@ -32,9 +32,9 @@ static void perfHash () { - GNUNET_HashCode hc1; - GNUNET_HashCode hc2; - GNUNET_HashCode hc3; + struct GNUNET_HashCode hc1; + struct GNUNET_HashCode hc2; + struct GNUNET_HashCode hc3; int i; char *buf; @@ -43,8 +43,8 @@ perfHash () GNUNET_CRYPTO_hash ("foo", 3, &hc1); for (i = 0; i < 1024; i++) { - GNUNET_CRYPTO_hash (&hc1, sizeof (GNUNET_HashCode), &hc2); - GNUNET_CRYPTO_hash (&hc2, sizeof (GNUNET_HashCode), &hc1); + GNUNET_CRYPTO_hash (&hc1, sizeof (struct GNUNET_HashCode), &hc2); + GNUNET_CRYPTO_hash (&hc2, sizeof (struct GNUNET_HashCode), &hc1); GNUNET_CRYPTO_hash (buf, 1024 * 64, &hc3); } GNUNET_free (buf); diff --git a/src/util/perf_malloc.c b/src/util/perf_malloc.c new file mode 100644 index 0000000..31f08df --- /dev/null +++ b/src/util/perf_malloc.c @@ -0,0 +1,66 @@ +/* + This file is part of GNUnet. + (C) 2012 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 2, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @author Christian Grothoff + * @file util/perf_malloc.c + * @brief measure performance of allocation functions + */ +#include "platform.h" +#include "gnunet_common.h" +#include "gnunet_crypto_lib.h" +#include "gnunet_time_lib.h" +#include + +static uint64_t +perfMalloc () +{ + size_t i; + uint64_t ret; + + ret = 0; + for (i=1;i<1024 * 1024;i+=1024) + { + ret += i; + GNUNET_free (GNUNET_malloc (i)); + } + return ret; +} + + +int +main (int argc, char *argv[]) +{ + struct GNUNET_TIME_Absolute start; + uint64_t kb; + + start = GNUNET_TIME_absolute_get (); + kb = perfMalloc (); + printf ("Malloc perf took %llu ms\n", + (unsigned long long) + GNUNET_TIME_absolute_get_duration (start).rel_value); + GAUGER ("UTIL", "Allocation", + kb / 1024 / (1 + + GNUNET_TIME_absolute_get_duration + (start).rel_value), "kb/s"); + return 0; +} + +/* end of perf_malloc.c */ diff --git a/src/util/program.c b/src/util/program.c index 9e1a83d..5cd129b 100644 --- a/src/util/program.c +++ b/src/util/program.c @@ -9,7 +9,7 @@ GNUnet is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPROSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License @@ -78,6 +78,7 @@ GNUNET_SPEEDUP_start_ (const struct GNUNET_CONFIGURATION_Handle *cfg); int GNUNET_SPEEDUP_stop_ (void); + /** * Initial task called by the scheduler for each * program. Runs the program-specific main task. @@ -86,8 +87,10 @@ static void program_main (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { struct CommandContext *cc = cls; - GNUNET_SPEEDUP_start_(cc->cfg); + if (0 != (GNUNET_SCHEDULER_REASON_SHUTDOWN & tc->reason)) + return; + GNUNET_SPEEDUP_start_(cc->cfg); GNUNET_RESOLVER_connect (cc->cfg); cc->task (cc->task_cls, cc->args, cc->cfgfile, cc->cfg); } @@ -158,7 +161,7 @@ GNUNET_PROGRAM_run2 (int argc, char *const *argv, const char *binaryName, GNUNET_GETOPT_OPTION_HELP (binaryHelp), GNUNET_GETOPT_OPTION_LOGLEVEL (&loglev), GNUNET_GETOPT_OPTION_LOGFILE (&logfile), - GNUNET_GETOPT_OPTION_VERSION (PACKAGE_VERSION) + GNUNET_GETOPT_OPTION_VERSION (PACKAGE_VERSION " " VCS_VERSION) }; struct GNUNET_GETOPT_CommandLineOption *allopts; const char *gargs; @@ -228,9 +231,8 @@ GNUNET_PROGRAM_run2 (int argc, char *const *argv, const char *binaryName, lpfx = GNUNET_strdup (binaryName); if (NULL != (spc = strstr (lpfx, " "))) *spc = '\0'; - if ((-1 == - (ret = - GNUNET_GETOPT_run (binaryName, allopts, (unsigned int) argc, argv))) || + ret = GNUNET_GETOPT_run (binaryName, allopts, (unsigned int) argc, argv); + if ((GNUNET_OK > ret) || (GNUNET_OK != GNUNET_log_setup (lpfx, loglev, logfile))) { GNUNET_CONFIGURATION_destroy (cfg); @@ -239,9 +241,19 @@ GNUNET_PROGRAM_run2 (int argc, char *const *argv, const char *binaryName, GNUNET_free_non_null (logfile); GNUNET_free (allopts); GNUNET_free (lpfx); - return GNUNET_SYSERR; + return (ret == GNUNET_SYSERR) ? GNUNET_SYSERR : GNUNET_OK; + } + if (GNUNET_YES == + GNUNET_DISK_file_test (cc.cfgfile)) + (void) GNUNET_CONFIGURATION_load (cfg, cc.cfgfile); + else + { + (void) GNUNET_CONFIGURATION_load (cfg, NULL); + if (0 != strcmp (cc.cfgfile, GNUNET_DEFAULT_USER_CONFIG_FILE)) + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Could not access configuration file `%s'\n"), + cc.cfgfile); } - (void) GNUNET_CONFIGURATION_load (cfg, cc.cfgfile); GNUNET_free (allopts); GNUNET_free (lpfx); if (GNUNET_OK == diff --git a/src/util/pseudonym.c b/src/util/pseudonym.c index 0165738..fa48e19 100644 --- a/src/util/pseudonym.c +++ b/src/util/pseudonym.c @@ -88,7 +88,7 @@ static struct DiscoveryCallback *head; * @param rating rating of pseudonym */ static void -internal_notify (const GNUNET_HashCode * id, +internal_notify (const struct GNUNET_HashCode * id, const struct GNUNET_CONTAINER_MetaData *md, int rating) { struct DiscoveryCallback *pos; @@ -169,7 +169,7 @@ GNUNET_PSEUDONYM_discovery_callback_unregister (GNUNET_PSEUDONYM_Iterator */ static char * get_data_filename (const struct GNUNET_CONFIGURATION_Handle *cfg, - const char *prefix, const GNUNET_HashCode * psid) + const char *prefix, const struct GNUNET_HashCode * psid) { struct GNUNET_CRYPTO_HashAsciiEncoded enc; @@ -192,7 +192,7 @@ get_data_filename (const struct GNUNET_CONFIGURATION_Handle *cfg, */ static void write_pseudonym_info (const struct GNUNET_CONFIGURATION_Handle *cfg, - const GNUNET_HashCode * nsid, + const struct GNUNET_HashCode * nsid, const struct GNUNET_CONTAINER_MetaData *meta, int32_t ranking, const char *ns_name) { @@ -238,7 +238,7 @@ write_pseudonym_info (const struct GNUNET_CONFIGURATION_Handle *cfg, */ static int read_info (const struct GNUNET_CONFIGURATION_Handle *cfg, - const GNUNET_HashCode * nsid, + const struct GNUNET_HashCode * nsid, struct GNUNET_CONTAINER_MetaData **meta, int32_t * ranking, char **ns_name) { @@ -248,6 +248,12 @@ read_info (const struct GNUNET_CONFIGURATION_Handle *cfg, fn = get_data_filename (cfg, PS_METADATA_DIR, nsid); GNUNET_assert (fn != NULL); + if (GNUNET_YES != + GNUNET_DISK_file_test (fn)) + { + GNUNET_free (fn); + return GNUNET_SYSERR; + } fileR = GNUNET_BIO_read_open (fn); if (fileR == NULL) { @@ -303,9 +309,9 @@ read_info (const struct GNUNET_CONFIGURATION_Handle *cfg, */ char * GNUNET_PSEUDONYM_name_uniquify (const struct GNUNET_CONFIGURATION_Handle *cfg, - const GNUNET_HashCode * nsid, const char *name, unsigned int *suffix) + const struct GNUNET_HashCode * nsid, const char *name, unsigned int *suffix) { - GNUNET_HashCode nh; + struct GNUNET_HashCode nh; uint64_t len; char *fn; struct GNUNET_DISK_FileHandle *fh; @@ -328,23 +334,23 @@ GNUNET_PSEUDONYM_name_uniquify (const struct GNUNET_CONFIGURATION_Handle *cfg, GNUNET_DISK_PERM_USER_WRITE); i = 0; idx = -1; - while ((len >= sizeof (GNUNET_HashCode)) && - (sizeof (GNUNET_HashCode) == - GNUNET_DISK_file_read (fh, &nh, sizeof (GNUNET_HashCode)))) + while ((len >= sizeof (struct GNUNET_HashCode)) && + (sizeof (struct GNUNET_HashCode) == + GNUNET_DISK_file_read (fh, &nh, sizeof (struct GNUNET_HashCode)))) { - if (0 == memcmp (&nh, nsid, sizeof (GNUNET_HashCode))) + if (0 == memcmp (&nh, nsid, sizeof (struct GNUNET_HashCode))) { idx = i; break; } i++; - len -= sizeof (GNUNET_HashCode); + len -= sizeof (struct GNUNET_HashCode); } if (idx == -1) { idx = i; - if (sizeof (GNUNET_HashCode) != - GNUNET_DISK_file_write (fh, nsid, sizeof (GNUNET_HashCode))) + if (sizeof (struct GNUNET_HashCode) != + GNUNET_DISK_file_write (fh, nsid, sizeof (struct GNUNET_HashCode))) LOG_STRERROR_FILE (GNUNET_ERROR_TYPE_WARNING, "write", fn); } GNUNET_DISK_file_close (fh); @@ -376,7 +382,7 @@ GNUNET_PSEUDONYM_name_uniquify (const struct GNUNET_CONFIGURATION_Handle *cfg, */ int GNUNET_PSEUDONYM_get_info (const struct GNUNET_CONFIGURATION_Handle *cfg, - const GNUNET_HashCode * nsid, struct GNUNET_CONTAINER_MetaData **ret_meta, + const struct GNUNET_HashCode * nsid, struct GNUNET_CONTAINER_MetaData **ret_meta, int32_t *ret_rank, char **ret_name, int *name_is_a_dup) { struct GNUNET_CONTAINER_MetaData *meta; @@ -450,13 +456,13 @@ GNUNET_PSEUDONYM_get_info (const struct GNUNET_CONFIGURATION_Handle *cfg, */ int GNUNET_PSEUDONYM_name_to_id (const struct GNUNET_CONFIGURATION_Handle *cfg, - const char *ns_uname, GNUNET_HashCode * nsid) + const char *ns_uname, struct GNUNET_HashCode * nsid) { size_t slen; uint64_t len; unsigned int idx; char *name; - GNUNET_HashCode nh; + struct GNUNET_HashCode nh; char *fn; struct GNUNET_DISK_FileHandle *fh; @@ -476,7 +482,7 @@ GNUNET_PSEUDONYM_name_to_id (const struct GNUNET_CONFIGURATION_Handle *cfg, if ((GNUNET_OK != GNUNET_DISK_file_test (fn) || (GNUNET_OK != GNUNET_DISK_file_size (fn, &len, GNUNET_YES, GNUNET_YES))) || - ((idx + 1) * sizeof (GNUNET_HashCode) > len)) + ((idx + 1) * sizeof (struct GNUNET_HashCode) > len)) { GNUNET_free (fn); return GNUNET_SYSERR; @@ -487,10 +493,15 @@ GNUNET_PSEUDONYM_name_to_id (const struct GNUNET_CONFIGURATION_Handle *cfg, GNUNET_DISK_PERM_USER_READ | GNUNET_DISK_PERM_USER_WRITE); GNUNET_free (fn); - GNUNET_DISK_file_seek (fh, idx * sizeof (GNUNET_HashCode), - GNUNET_DISK_SEEK_SET); - if (sizeof (GNUNET_HashCode) != - GNUNET_DISK_file_read (fh, nsid, sizeof (GNUNET_HashCode))) + if (GNUNET_SYSERR == + GNUNET_DISK_file_seek (fh, idx * sizeof (struct GNUNET_HashCode), + GNUNET_DISK_SEEK_SET)) + { + GNUNET_DISK_file_close (fh); + return GNUNET_SYSERR; + } + if (sizeof (struct GNUNET_HashCode) != + GNUNET_DISK_file_read (fh, nsid, sizeof (struct GNUNET_HashCode))) { GNUNET_DISK_file_close (fh); return GNUNET_SYSERR; @@ -535,7 +546,7 @@ list_pseudonym_helper (void *cls, const char *fullname) { struct ListPseudonymClosure *c = cls; int ret; - GNUNET_HashCode id; + struct GNUNET_HashCode id; int32_t rating; struct GNUNET_CONTAINER_MetaData *meta; const char *fn; @@ -612,7 +623,7 @@ GNUNET_PSEUDONYM_list_all (const struct GNUNET_CONFIGURATION_Handle *cfg, */ int GNUNET_PSEUDONYM_rank (const struct GNUNET_CONFIGURATION_Handle *cfg, - const GNUNET_HashCode * nsid, int delta) + const struct GNUNET_HashCode * nsid, int delta) { struct GNUNET_CONTAINER_MetaData *meta; int ret; @@ -648,7 +659,7 @@ GNUNET_PSEUDONYM_rank (const struct GNUNET_CONFIGURATION_Handle *cfg, */ int GNUNET_PSEUDONYM_set_info (const struct GNUNET_CONFIGURATION_Handle *cfg, - const GNUNET_HashCode * nsid, const char *name, + const struct GNUNET_HashCode * nsid, const char *name, const struct GNUNET_CONTAINER_MetaData *md, int rank) { GNUNET_assert (cfg != NULL); @@ -670,7 +681,7 @@ GNUNET_PSEUDONYM_set_info (const struct GNUNET_CONFIGURATION_Handle *cfg, */ void GNUNET_PSEUDONYM_add (const struct GNUNET_CONFIGURATION_Handle *cfg, - const GNUNET_HashCode * id, + const struct GNUNET_HashCode * id, const struct GNUNET_CONTAINER_MetaData *meta) { char *name; diff --git a/src/util/resolver.conf.in b/src/util/resolver.conf.in index 7abe1c9..cccb60c 100644 --- a/src/util/resolver.conf.in +++ b/src/util/resolver.conf.in @@ -3,7 +3,6 @@ AUTOSTART = YES @JAVAPORT@PORT = 2089 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-resolver ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; diff --git a/src/util/resolver_api.c b/src/util/resolver_api.c index 87b76f1..2247b49 100644 --- a/src/util/resolver_api.c +++ b/src/util/resolver_api.c @@ -707,7 +707,7 @@ reconnect () (unsigned long long) backoff.rel_value); GNUNET_assert (NULL != resolver_cfg); r_task = GNUNET_SCHEDULER_add_delayed (backoff, &reconnect_task, NULL); - backoff = GNUNET_TIME_relative_multiply (backoff, 2); + backoff = GNUNET_TIME_STD_BACKOFF (backoff); } diff --git a/src/util/scheduler.c b/src/util/scheduler.c index 45cc020..0adf9f0 100644 --- a/src/util/scheduler.c +++ b/src/util/scheduler.c @@ -36,7 +36,7 @@ #define LOG_STRERROR(kind,syscall) GNUNET_log_from_strerror (kind, "util-scheduler", syscall) -#ifdef LINUX +#if HAVE_EXECINFO_H #include "execinfo.h" /** @@ -565,22 +565,17 @@ run_ready (struct GNUNET_NETWORK_FDSet *rs, struct GNUNET_NETWORK_FDSet *ws) GNUNET_assert (pos != NULL); /* ready_count wrong? */ ready[p] = pos->next; ready_count--; - if (current_priority != pos->priority) - { - current_priority = pos->priority; - (void) GNUNET_OS_set_process_priority (GNUNET_OS_process_current (), - pos->priority); - } + current_priority = pos->priority; current_lifeness = pos->lifeness; active_task = pos; #if PROFILE_DELAYS if (GNUNET_TIME_absolute_get_duration (pos->start_time).rel_value > DELAY_THRESHOLD.rel_value) { - LOG (GNUNET_ERROR_TYPE_ERROR, "Task %llu took %llums to be scheduled\n", - pos->id, - (unsigned long long) - GNUNET_TIME_absolute_get_duration (pos->start_time).rel_value); + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Task %llu took %s to be scheduled\n", + (unsigned long long) pos->id, + GNUNET_STRINGS_relative_time_to_string (GNUNET_TIME_absolute_get_duration (pos->start_time), GNUNET_YES)); } #endif tc.reason = pos->reason; @@ -727,6 +722,7 @@ GNUNET_SCHEDULER_run (GNUNET_SCHEDULER_Task task, void *task_cls) GNUNET_DISK_PIPE_END_READ); GNUNET_assert (pr != NULL); my_pid = getpid (); + LOG (GNUNET_ERROR_TYPE_DEBUG, "Registering signal handlers\n"); shc_int = GNUNET_SIGNAL_handler_install (SIGINT, &sighandler_shutdown); shc_term = GNUNET_SIGNAL_handler_install (SIGTERM, &sighandler_shutdown); #ifndef MINGW diff --git a/src/util/server.c b/src/util/server.c index 409e89f..fc5f263 100644 --- a/src/util/server.c +++ b/src/util/server.c @@ -296,11 +296,6 @@ struct GNUNET_SERVER_Client */ int receive_pending; - /** - * Finish pending write when disconnecting? - */ - int finish_pending_write; - /** * Persist the file handle for this client no matter what happens, * force the OS to close once the process actually dies. Should only @@ -333,43 +328,6 @@ static void process_listen_socket (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc); -/** - * Add a listen task with the scheduler for this server. - * - * @param server handle to our server for which we are adding the listen - * socket - */ -static void -schedule_listen_task (struct GNUNET_SERVER_Handle *server) -{ - struct GNUNET_NETWORK_FDSet *r; - unsigned int i; - - if (NULL == server->listen_sockets[0]) - return; /* nothing to do, no listen sockets! */ - if (NULL == server->listen_sockets[1]) - { - /* simplified method: no fd set needed; this is then much simpler and - much more efficient */ - server->listen_task = - GNUNET_SCHEDULER_add_read_net_with_priority (GNUNET_TIME_UNIT_FOREVER_REL, - GNUNET_SCHEDULER_PRIORITY_HIGH, - server->listen_sockets[0], - &process_listen_socket, server); - return; - } - r = GNUNET_NETWORK_fdset_create (); - i = 0; - while (NULL != server->listen_sockets[i]) - GNUNET_NETWORK_fdset_set (r, server->listen_sockets[i++]); - server->listen_task = - GNUNET_SCHEDULER_add_select (GNUNET_SCHEDULER_PRIORITY_HIGH, - GNUNET_TIME_UNIT_FOREVER_REL, r, NULL, - &process_listen_socket, server); - GNUNET_NETWORK_fdset_destroy (r); -} - - /** * Scheduler says our listen socket is ready. Process it! * @@ -389,7 +347,7 @@ process_listen_socket (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) if (0 != (tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN)) { /* ignore shutdown, someone else will take care of it! */ - schedule_listen_task (server); + GNUNET_SERVER_resume (server); return; } i = 0; @@ -412,7 +370,7 @@ process_listen_socket (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) i++; } /* listen for more! */ - schedule_listen_task (server); + GNUNET_SERVER_resume (server); } @@ -426,7 +384,6 @@ process_listen_socket (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) static struct GNUNET_NETWORK_Handle * open_listen_socket (const struct sockaddr *serverAddr, socklen_t socklen) { - static int on = 1; struct GNUNET_NETWORK_Handle *sock; uint16_t port; int eno; @@ -454,20 +411,6 @@ open_listen_socket (const struct sockaddr *serverAddr, socklen_t socklen) errno = 0; return NULL; } - if (0 != port) - { - if (GNUNET_NETWORK_socket_setsockopt - (sock, SOL_SOCKET, SO_REUSEADDR, &on, sizeof (on)) != GNUNET_OK) - LOG_STRERROR (GNUNET_ERROR_TYPE_ERROR | GNUNET_ERROR_TYPE_BULK, - "setsockopt"); -#ifdef IPV6_V6ONLY - if ((AF_INET6 == serverAddr->sa_family) && - (GNUNET_NETWORK_socket_setsockopt - (sock, IPPROTO_IPV6, IPV6_V6ONLY, &on, sizeof (on)) != GNUNET_OK)) - LOG_STRERROR (GNUNET_ERROR_TYPE_ERROR | GNUNET_ERROR_TYPE_BULK, - "setsockopt"); -#endif - } /* bind the socket */ if (GNUNET_OK != GNUNET_NETWORK_socket_bind (sock, serverAddr, socklen)) { @@ -493,10 +436,17 @@ open_listen_socket (const struct sockaddr *serverAddr, socklen_t socklen) "bind", port, (AF_INET == serverAddr->sa_family) ? "IPv4" : "IPv6"); else if (AF_UNIX == serverAddr->sa_family) - LOG (GNUNET_ERROR_TYPE_WARNING, - _("`%s' failed for `%s': address already in use\n"), "bind", - ((const struct sockaddr_un *) serverAddr)->sun_path); + { + const struct sockaddr_un *un = (const struct sockaddr_un *) serverAddr; + unsigned int off = 0; + if ('\0' == un->sun_path[0]) + off = 1; /* some UNIXPATHs start with 0 */ + LOG (GNUNET_ERROR_TYPE_WARNING, + _("`%s' failed for `%.*s': address already in use\n"), "bind", + (int) ((sizeof (un->sun_path) - off)), + (&un->sun_path[off])); + } } GNUNET_break (GNUNET_OK == GNUNET_NETWORK_socket_close (sock)); errno = eno; @@ -544,7 +494,7 @@ GNUNET_SERVER_create_with_sockets (GNUNET_CONNECTION_AccessCheck access, server->access_cls = access_cls; server->require_found = require_found; if (NULL != lsocks) - schedule_listen_task (server); + GNUNET_SERVER_resume (server); return server; } @@ -678,6 +628,60 @@ test_monitor_clients (struct GNUNET_SERVER_Handle *server) } +/** + * Suspend accepting connections from the listen socket temporarily. + * + * @param server server to stop accepting connections. + */ +void +GNUNET_SERVER_suspend (struct GNUNET_SERVER_Handle *server) +{ + if (GNUNET_SCHEDULER_NO_TASK != server->listen_task) + { + GNUNET_SCHEDULER_cancel (server->listen_task); + server->listen_task = GNUNET_SCHEDULER_NO_TASK; + } +} + + +/** + * Resume accepting connections from the listen socket. + * + * @param server server to stop accepting connections. + */ +void +GNUNET_SERVER_resume (struct GNUNET_SERVER_Handle *server) +{ + struct GNUNET_NETWORK_FDSet *r; + unsigned int i; + + if (NULL == server->listen_sockets) + return; + if (NULL == server->listen_sockets[0]) + return; /* nothing to do, no listen sockets! */ + if (NULL == server->listen_sockets[1]) + { + /* simplified method: no fd set needed; this is then much simpler and + much more efficient */ + server->listen_task = + GNUNET_SCHEDULER_add_read_net_with_priority (GNUNET_TIME_UNIT_FOREVER_REL, + GNUNET_SCHEDULER_PRIORITY_HIGH, + server->listen_sockets[0], + &process_listen_socket, server); + return; + } + r = GNUNET_NETWORK_fdset_create (); + i = 0; + while (NULL != server->listen_sockets[i]) + GNUNET_NETWORK_fdset_set (r, server->listen_sockets[i++]); + server->listen_task = + GNUNET_SCHEDULER_add_select (GNUNET_SCHEDULER_PRIORITY_HIGH, + GNUNET_TIME_UNIT_FOREVER_REL, r, NULL, + &process_listen_socket, server); + GNUNET_NETWORK_fdset_destroy (r); +} + + /** * Stop the listen socket and get ready to shutdown the server * once only 'monitor' clients are left. @@ -823,11 +827,9 @@ warn_no_receive_done (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) &warn_no_receive_done, client); if (0 == (GNUNET_SCHEDULER_REASON_SHUTDOWN & tc->reason)) LOG (GNUNET_ERROR_TYPE_WARNING, - _ - ("Processing code for message of type %u did not call GNUNET_SERVER_receive_done after %llums\n"), + _("Processing code for message of type %u did not call `GNUNET_SERVER_receive_done' after %s\n"), (unsigned int) client->warn_type, - (unsigned long long) - GNUNET_TIME_absolute_get_duration (client->warn_start).rel_value); + GNUNET_STRINGS_relative_time_to_string (GNUNET_TIME_absolute_get_duration (client->warn_start), GNUNET_YES)); } diff --git a/src/util/service.c b/src/util/service.c index 6a6fb6c..b9050f8 100644 --- a/src/util/service.c +++ b/src/util/service.c @@ -36,6 +36,12 @@ #include "gnunet_server_lib.h" #include "gnunet_service_lib.h" +#if HAVE_MALLINFO +#include +#include "gauger.h" +#endif + + #define LOG(kind,...) GNUNET_log_from (kind, "util", __VA_ARGS__) #define LOG_STRERROR(kind,syscall) GNUNET_log_from_strerror (kind, "util", syscall) @@ -62,6 +68,7 @@ struct IPv4NetworkSet }; /** + * @brief network in CIDR notation for IPV6. */ struct IPv6NetworkSet @@ -653,10 +660,12 @@ check_access (void *cls, const struct GNUNET_CONNECTION_Credentials *uc, if (GNUNET_YES == sctx->match_uid) { /* UID match required */ - ret = (NULL != uc) && (uc->uid == geteuid ()); + ret = (NULL != uc) && ( (0 == uc->uid) || (uc->uid == geteuid ()) ); } else if ( (GNUNET_YES == sctx->match_gid) && - ( (NULL == uc) || (uc->uid != geteuid ()) ) ) + ( (NULL == uc) || + ( (0 != uc->uid) && + (uc->uid != geteuid ()) ) ) ) { /* group match required and UID does not match */ if (NULL == uc) @@ -931,9 +940,14 @@ GNUNET_SERVICE_get_server_addresses (const char *service_name, port = 0; if (GNUNET_CONFIGURATION_have_value (cfg, service_name, "PORT")) { - GNUNET_break (GNUNET_OK == - GNUNET_CONFIGURATION_get_value_number (cfg, service_name, - "PORT", &port)); + if (GNUNET_OK != + GNUNET_CONFIGURATION_get_value_number (cfg, service_name, + "PORT", &port)) + { + LOG (GNUNET_ERROR_TYPE_ERROR, + _("Require valid port number for service `%s' in configuration!\n"), + service_name); + } if (port > 65535) { LOG (GNUNET_ERROR_TYPE_ERROR, @@ -968,12 +982,15 @@ GNUNET_SERVICE_get_server_addresses (const char *service_name, { LOG (GNUNET_ERROR_TYPE_WARNING, _("UNIXPATH `%s' too long, maximum length is %llu\n"), unixpath, - sizeof (s_un.sun_path)); - GNUNET_free_non_null (hostname); - GNUNET_free (unixpath); - return GNUNET_SYSERR; - } + (unsigned long long) sizeof (s_un.sun_path)); + unixpath = GNUNET_NETWORK_shorten_unixpath (unixpath); + LOG (GNUNET_ERROR_TYPE_INFO, + _("Using `%s' instead\n"), unixpath); + } + } + if (NULL != unixpath) + { desc = GNUNET_NETWORK_socket_create (AF_UNIX, SOCK_STREAM, 0); if (NULL == desc) { @@ -1487,6 +1504,8 @@ service_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) struct GNUNET_SERVICE_Context *sctx = cls; unsigned int i; + if (0 != (GNUNET_SCHEDULER_REASON_SHUTDOWN & tc->reason)) + return; GNUNET_RESOLVER_connect (sctx->cfg); if (NULL != sctx->lsocks) sctx->server = @@ -1712,6 +1731,7 @@ GNUNET_SERVICE_run (int argc, char *const *argv, const char *service_name, #define HANDLE_ERROR do { GNUNET_break (0); goto shutdown; } while (0) int err; + int ret; char *cfg_fn; char *loglev; char *logfile; @@ -1731,7 +1751,7 @@ GNUNET_SERVICE_run (int argc, char *const *argv, const char *service_name, GNUNET_GETOPT_OPTION_HELP (NULL), GNUNET_GETOPT_OPTION_LOGLEVEL (&loglev), GNUNET_GETOPT_OPTION_LOGFILE (&logfile), - GNUNET_GETOPT_OPTION_VERSION (PACKAGE_VERSION), + GNUNET_GETOPT_OPTION_VERSION (PACKAGE_VERSION " " VCS_VERSION), GNUNET_GETOPT_OPTION_END }; err = 1; @@ -1748,14 +1768,29 @@ GNUNET_SERVICE_run (int argc, char *const *argv, const char *service_name, sctx.task_cls = task_cls; sctx.service_name = service_name; sctx.cfg = cfg = GNUNET_CONFIGURATION_create (); + /* setup subsystems */ - if (GNUNET_SYSERR == - GNUNET_GETOPT_run (service_name, service_options, argc, argv)) + ret = GNUNET_GETOPT_run (service_name, service_options, argc, argv); + if (GNUNET_SYSERR == ret) goto shutdown; + if (GNUNET_NO == ret) + { + err = 0; + goto shutdown; + } if (GNUNET_OK != GNUNET_log_setup (service_name, loglev, logfile)) HANDLE_ERROR; - if (GNUNET_OK != GNUNET_CONFIGURATION_load (cfg, cfg_fn)) - goto shutdown; + if (GNUNET_YES == + GNUNET_DISK_file_test (cfg_fn)) + (void) GNUNET_CONFIGURATION_load (cfg, cfg_fn); + else + { + (void) GNUNET_CONFIGURATION_load (cfg, NULL); + if (0 != strcmp (cfg_fn, GNUNET_DEFAULT_USER_CONFIG_FILE)) + GNUNET_log (GNUNET_ERROR_TYPE_ERROR, + _("Could not access configuration file `%s'\n"), + cfg_fn); + } if (GNUNET_OK != setup_service (&sctx)) goto shutdown; if ((1 == do_daemonize) && (GNUNET_OK != detach_terminal (&sctx))) @@ -1791,7 +1826,26 @@ shutdown: LOG_STRERROR (GNUNET_ERROR_TYPE_WARNING, "write"); GNUNET_break (0 == CLOSE (sctx.ready_confirm_fd)); } - +#if HAVE_MALLINFO + { + char *counter; + + if ( (GNUNET_YES == + GNUNET_CONFIGURATION_have_value (sctx.cfg, service_name, + "GAUGER_HEAP")) && + (GNUNET_OK == + GNUNET_CONFIGURATION_get_value_string (sctx.cfg, service_name, + "GAUGER_HEAP", + &counter)) ) + { + struct mallinfo mi; + + mi = mallinfo (); + GAUGER (service_name, counter, mi.usmblks, "blocks"); + GNUNET_free (counter); + } + } +#endif GNUNET_SPEEDUP_stop_ (); GNUNET_CONFIGURATION_destroy (cfg); i = 0; @@ -1891,6 +1945,26 @@ GNUNET_SERVICE_stop (struct GNUNET_SERVICE_Context *sctx) { unsigned int i; +#if HAVE_MALLINFO + { + char *counter; + + if ( (GNUNET_YES == + GNUNET_CONFIGURATION_have_value (sctx->cfg, sctx->service_name, + "GAUGER_HEAP")) && + (GNUNET_OK == + GNUNET_CONFIGURATION_get_value_string (sctx->cfg, sctx->service_name, + "GAUGER_HEAP", + &counter)) ) + { + struct mallinfo mi; + + mi = mallinfo (); + GAUGER (sctx->service_name, counter, mi.usmblks, "blocks"); + GNUNET_free (counter); + } + } +#endif if (GNUNET_SCHEDULER_NO_TASK != sctx->shutdown_task) { GNUNET_SCHEDULER_cancel (sctx->shutdown_task); diff --git a/src/util/speedup.c b/src/util/speedup.c index 0a005c0..e5f71d0 100644 --- a/src/util/speedup.c +++ b/src/util/speedup.c @@ -83,8 +83,9 @@ GNUNET_SPEEDUP_stop_ ( ) GNUNET_SCHEDULER_cancel (speedup_task); speedup_task = GNUNET_SCHEDULER_NO_TASK; } - LOG (GNUNET_ERROR_TYPE_DEBUG, - "Stopped execution speed up\n"); + if ((0 != interval.rel_value) && (0 != delta.rel_value)) + LOG (GNUNET_ERROR_TYPE_DEBUG, + "Stopped execution speed up\n"); } diff --git a/src/util/strings.c b/src/util/strings.c index 11134f1..70986a9 100644 --- a/src/util/strings.c +++ b/src/util/strings.c @@ -32,6 +32,8 @@ #include "gnunet_common.h" #include "gnunet_strings_lib.h" #include +#include +#include #define LOG(kind,...) GNUNET_log_from (kind, "util", __VA_ARGS__) @@ -289,17 +291,25 @@ GNUNET_STRINGS_fancy_time_to_relative (const char *fancy_time, { "ms", 1}, { "s", 1000}, { "\"", 1000}, + { "m", 60 * 1000}, { "min", 60 * 1000}, { "minutes", 60 * 1000}, { "'", 60 * 1000}, { "h", 60 * 60 * 1000}, { "d", 24 * 60 * 60 * 1000}, + { "day", 24 * 60 * 60 * 1000}, + { "days", 24 * 60 * 60 * 1000}, { "a", 31536000000LL /* year */ }, { NULL, 0} }; int ret; unsigned long long val; + if (0 == strcasecmp ("forever", fancy_time)) + { + *rtime = GNUNET_TIME_UNIT_FOREVER_REL; + return GNUNET_OK; + } ret = convert_with_table (fancy_time, table, &val); @@ -307,6 +317,48 @@ GNUNET_STRINGS_fancy_time_to_relative (const char *fancy_time, return ret; } + +/** + * Convert a given fancy human-readable time to our internal + * representation. + * + * @param fancy_time human readable string (i.e. %Y-%m-%d %H:%M:%S) + * @param atime set to the absolute time + * @return GNUNET_OK on success, GNUNET_SYSERR on error + */ +int +GNUNET_STRINGS_fancy_time_to_absolute (const char *fancy_time, + struct GNUNET_TIME_Absolute *atime) +{ + struct tm tv; + time_t t; + + if (0 == strcasecmp ("end of time", fancy_time)) + { + *atime = GNUNET_TIME_UNIT_FOREVER_ABS; + return GNUNET_OK; + } + memset (&tv, 0, sizeof (tv)); + if ( (NULL == strptime (fancy_time, "%a %b %d %H:%M:%S %Y", &tv)) && + (NULL == strptime (fancy_time, "%c", &tv)) && + (NULL == strptime (fancy_time, "%Ec", &tv)) && + (NULL == strptime (fancy_time, "%Y-%m-%d %H:%M:%S", &tv)) && + (NULL == strptime (fancy_time, "%Y-%m-%d %H:%M", &tv)) && + (NULL == strptime (fancy_time, "%x", &tv)) && + (NULL == strptime (fancy_time, "%Ex", &tv)) && + (NULL == strptime (fancy_time, "%Y-%m-%d", &tv)) && + (NULL == strptime (fancy_time, "%Y-%m", &tv)) && + (NULL == strptime (fancy_time, "%Y", &tv)) ) + return GNUNET_SYSERR; + t = mktime (&tv); + atime->abs_value = (uint64_t) ((uint64_t) t * 1000LL); +#if LINUX + atime->abs_value -= 1000LL * timezone; +#endif + return GNUNET_OK; +} + + /** * Convert the len characters long character sequence * given in input that is in the given input charset @@ -319,58 +371,51 @@ char * GNUNET_STRINGS_conv (const char *input, size_t len, const char *input_charset, const char *output_charset) { char *ret; - -#if ENABLE_NLS && HAVE_ICONV - size_t tmpSize; - size_t finSize; - char *tmp; - char *itmp; - iconv_t cd; - - cd = iconv_open (output_charset, input_charset); - if (cd == (iconv_t) - 1) + uint8_t *u8_string; + char *encoded_string; + size_t u8_string_length; + size_t encoded_string_length; + + u8_string = u8_conv_from_encoding (input_charset, + iconveh_error, + input, len, + NULL, NULL, + &u8_string_length); + if (NULL == u8_string) { - LOG_STRERROR (GNUNET_ERROR_TYPE_WARNING, "iconv_open"); - LOG (GNUNET_ERROR_TYPE_WARNING, _("Character sets requested were `%s'->`%s'\n"), - input_charset, output_charset); - ret = GNUNET_malloc (len + 1); - memcpy (ret, input, len); - ret[len] = '\0'; - return ret; + LOG_STRERROR (GNUNET_ERROR_TYPE_WARNING, "u8_conv_from_encoding"); + goto fail; } - tmpSize = 3 * len + 4; - tmp = GNUNET_malloc (tmpSize); - itmp = tmp; - finSize = tmpSize; - if (iconv (cd, -#if FREEBSD || DARWIN || WINDOWS - (const char **) &input, -#else - (char **) &input, -#endif - &len, &itmp, &finSize) == SIZE_MAX) + if (0 == strcmp (output_charset, "UTF-8")) { - LOG_STRERROR (GNUNET_ERROR_TYPE_WARNING, "iconv"); - iconv_close (cd); - GNUNET_free (tmp); - ret = GNUNET_malloc (len + 1); - memcpy (ret, input, len); - ret[len] = '\0'; + ret = GNUNET_malloc (u8_string_length + 1); + memcpy (ret, u8_string, u8_string_length); + ret[u8_string_length] = '\0'; + free (u8_string); return ret; } - ret = GNUNET_malloc (tmpSize - finSize + 1); - memcpy (ret, tmp, tmpSize - finSize); - ret[tmpSize - finSize] = '\0'; - GNUNET_free (tmp); - if (0 != iconv_close (cd)) - LOG_STRERROR (GNUNET_ERROR_TYPE_WARNING, "iconv_close"); + encoded_string = u8_conv_to_encoding (output_charset, iconveh_error, + u8_string, u8_string_length, + NULL, NULL, + &encoded_string_length); + free (u8_string); + if (NULL == encoded_string) + { + LOG_STRERROR (GNUNET_ERROR_TYPE_WARNING, "u8_conv_to_encoding"); + goto fail; + } + ret = GNUNET_malloc (encoded_string_length + 1); + memcpy (ret, encoded_string, encoded_string_length); + ret[encoded_string_length] = '\0'; + free (encoded_string); return ret; -#else + fail: + LOG (GNUNET_ERROR_TYPE_WARNING, _("Character sets requested were `%s'->`%s'\n"), + "UTF-8", output_charset); ret = GNUNET_malloc (len + 1); memcpy (ret, input, len); ret[len] = '\0'; return ret; -#endif } @@ -388,10 +433,11 @@ GNUNET_STRINGS_to_utf8 (const char *input, size_t len, const char *charset) return GNUNET_STRINGS_conv (input, len, charset, "UTF-8"); } + /** * Convert the len bytes-long UTF-8 string * given in input to the given charset. - + * * @return the converted string (0-terminated), * if conversion fails, a copy of the orignal * string is returned. @@ -402,6 +448,7 @@ GNUNET_STRINGS_from_utf8 (const char *input, size_t len, const char *charset) return GNUNET_STRINGS_conv (input, len, "UTF-8", charset); } + /** * Convert the utf-8 input string to lowercase * Output needs to be allocated appropriately @@ -422,6 +469,7 @@ GNUNET_STRINGS_utf8_tolower(const char* input, char** output) free(tmp_in); } + /** * Convert the utf-8 input string to uppercase * Output needs to be allocated appropriately @@ -454,7 +502,6 @@ char * GNUNET_STRINGS_filename_expand (const char *fil) { char *buffer; - #ifndef MINGW size_t len; size_t n; @@ -563,67 +610,83 @@ GNUNET_STRINGS_filename_expand (const char *fil) /** * Give relative time in human-readable fancy format. + * This is one of the very few calls in the entire API that is + * NOT reentrant! * * @param delta time in milli seconds + * @param do_round are we allowed to round a bit? * @return time as human-readable string */ -char * -GNUNET_STRINGS_relative_time_to_string (struct GNUNET_TIME_Relative delta) +const char * +GNUNET_STRINGS_relative_time_to_string (struct GNUNET_TIME_Relative delta, + int do_round) { + static char buf[128]; const char *unit = _( /* time unit */ "ms"); - char *ret; uint64_t dval = delta.rel_value; - if (delta.rel_value == GNUNET_TIME_UNIT_FOREVER_REL.rel_value) - return GNUNET_strdup (_("eternity")); - if (dval > 5 * 1000) + if (GNUNET_TIME_UNIT_FOREVER_REL.rel_value == delta.rel_value) + return _("forever"); + if (0 == delta.rel_value) + return _("0 ms"); + if ( ( (GNUNET_YES == do_round) && + (dval > 5 * 1000) ) || + (0 == (dval % 1000) )) { dval = dval / 1000; unit = _( /* time unit */ "s"); - if (dval > 5 * 60) + if ( ( (GNUNET_YES == do_round) && + (dval > 5 * 60) ) || + (0 == (dval % 60) ) ) { dval = dval / 60; unit = _( /* time unit */ "m"); - if (dval > 5 * 60) + if ( ( (GNUNET_YES == do_round) && + (dval > 5 * 60) ) || + (0 == (dval % 60) )) { dval = dval / 60; unit = _( /* time unit */ "h"); - if (dval > 5 * 24) - { + if ( ( (GNUNET_YES == do_round) && + (dval > 5 * 24) ) || + (0 == (dval % 24)) ) + { dval = dval / 24; - unit = _( /* time unit */ " days"); + if (1 == dval) + unit = _( /* time unit */ "day"); + else + unit = _( /* time unit */ "days"); } } } } - GNUNET_asprintf (&ret, "%llu %s", dval, unit); - return ret; + GNUNET_snprintf (buf, sizeof (buf), + "%llu %s", dval, unit); + return buf; } /** - * "man ctime_r", except for GNUnet time; also, unlike ctime, the - * return value does not include the newline character. + * "asctime", except for GNUnet time. + * This is one of the very few calls in the entire API that is + * NOT reentrant! * * @param t time to convert * @return absolute time in human-readable format */ -char * +const char * GNUNET_STRINGS_absolute_time_to_string (struct GNUNET_TIME_Absolute t) { + static char buf[255]; time_t tt; - char *ret; + struct tm *tp; if (t.abs_value == GNUNET_TIME_UNIT_FOREVER_ABS.abs_value) - return GNUNET_strdup (_("end of time")); + return _("end of time"); tt = t.abs_value / 1000; -#ifdef ctime_r - ret = ctime_r (&tt, GNUNET_malloc (32)); -#else - ret = GNUNET_strdup (ctime (&tt)); -#endif - ret[strlen (ret) - 1] = '\0'; - return ret; + tp = gmtime (&tt); + strftime (buf, sizeof (buf), "%a %b %d %H:%M:%S %Y", tp); + return buf; } @@ -919,7 +982,6 @@ GNUNET_STRINGS_path_is_absolute (const char *filename, int can_be_uri, } else { - is_uri = GNUNET_NO; if (r_is_uri) *r_is_uri = GNUNET_NO; } @@ -981,7 +1043,6 @@ GNUNET_STRINGS_check_filename (const char *filename, } - /** * Tries to convert 'zt_addr' string to an IPv6 address. * The string is expected to have the format "[ABCD::01]:80". @@ -1113,4 +1174,95 @@ GNUNET_STRINGS_to_address_ip (const char *addr, return GNUNET_STRINGS_to_address_ipv4 (addr, addrlen, (struct sockaddr_in *) r_buf); } + +/** + * Makes a copy of argv that consists of a single memory chunk that can be + * freed with a single call to GNUNET_free (); + */ +static char *const * +_make_continuous_arg_copy (int argc, char *const *argv) +{ + size_t argvsize = 0; + int i; + char **new_argv; + char *p; + for (i = 0; i < argc; i++) + argvsize += strlen (argv[i]) + 1 + sizeof (char *); + new_argv = GNUNET_malloc (argvsize + sizeof (char *)); + p = (char *) &new_argv[argc + 1]; + for (i = 0; i < argc; i++) + { + new_argv[i] = p; + strcpy (p, argv[i]); + p += strlen (argv[i]) + 1; + } + new_argv[argc] = NULL; + return (char *const *) new_argv; +} + + +/** + * Returns utf-8 encoded arguments. + * Does nothing (returns a copy of argc and argv) on any platform + * other than W32. + * Returned argv has u8argv[u8argc] == NULL. + * Returned argv is a single memory block, and can be freed with a single + * GNUNET_free () call. + * + * @param argc argc (as given by main()) + * @param argv argv (as given by main()) + * @param u8argc a location to store new argc in (though it's th same as argc) + * @param u8argv a location to store new argv in + * @return GNUNET_OK on success, GNUNET_SYSERR on failure + */ +int +GNUNET_STRINGS_get_utf8_args (int argc, char *const *argv, int *u8argc, char *const **u8argv) +{ +#if WINDOWS + wchar_t *wcmd; + wchar_t **wargv; + int wargc; + int i; + char **split_u8argv; + + wcmd = GetCommandLineW (); + if (NULL == wcmd) + return GNUNET_SYSERR; + wargv = CommandLineToArgvW (wcmd, &wargc); + if (NULL == wargv) + return GNUNET_SYSERR; + + split_u8argv = GNUNET_malloc (argc * sizeof (char *)); + + for (i = 0; i < wargc; i++) + { + size_t strl; + /* Hopefully it will allocate us NUL-terminated strings... */ + split_u8argv[i] = (char *) u16_to_u8 (wargv[i], wcslen (wargv[i]) + 1, NULL, &strl); + if (split_u8argv == NULL) + { + int j; + for (j = 0; j < i; j++) + free (split_u8argv[j]); + GNUNET_free (split_u8argv); + LocalFree (wargv); + return GNUNET_SYSERR; + } + } + + *u8argv = _make_continuous_arg_copy (wargc, split_u8argv); + *u8argc = wargc; + + for (i = 0; i < wargc; i++) + free (split_u8argv[i]); + free (split_u8argv); + return GNUNET_OK; +#else + char *const *new_argv = (char *const *) _make_continuous_arg_copy (argc, argv); + *u8argv = new_argv; + *u8argc = argc; + return GNUNET_OK; +#endif +} + /* end of strings.c */ diff --git a/src/util/test_client.c b/src/util/test_client.c index 54881b2..7d7ec8c 100644 --- a/src/util/test_client.c +++ b/src/util/test_client.c @@ -29,7 +29,6 @@ #include "gnunet_server_lib.h" #include "gnunet_time_lib.h" -#define VERBOSE GNUNET_NO #define PORT 14325 @@ -174,15 +173,14 @@ task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) } -/** - * Main method, starts scheduler with task1, - * checks that "ok" is correct at the end. - */ -static int -check () +int +main (int argc, char *argv[]) { int ok; + GNUNET_log_setup ("test_client", + "WARNING", + NULL); cfg = GNUNET_CONFIGURATION_create (); GNUNET_CONFIGURATION_set_value_number (cfg, MYNAME, "PORT", PORT); GNUNET_CONFIGURATION_set_value_string (cfg, MYNAME, "HOSTNAME", "localhost"); @@ -194,21 +192,4 @@ check () return ok; } -int -main (int argc, char *argv[]) -{ - int ret = 0; - - GNUNET_log_setup ("test_client", -#if VERBOSE - "DEBUG", -#else - "WARNING", -#endif - NULL); - ret += check (); - - return ret; -} - /* end of test_client.c */ diff --git a/src/util/test_common_logging_runtime_loglevels.c b/src/util/test_common_logging_runtime_loglevels.c index b914ae1..58b722b 100644 --- a/src/util/test_common_logging_runtime_loglevels.c +++ b/src/util/test_common_logging_runtime_loglevels.c @@ -42,6 +42,8 @@ static struct GNUNET_DISK_PipeHandle *pipe_stdout; static GNUNET_SCHEDULER_TaskIdentifier die_task; +static GNUNET_SCHEDULER_TaskIdentifier read_task; + static void runone (void); @@ -50,13 +52,21 @@ end_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Ending phase %d, ok is %d\n", phase, ok); - if (0 != GNUNET_OS_process_kill (proc, SIGTERM)) + if (NULL != proc) + { + if (0 != GNUNET_OS_process_kill (proc, SIGTERM)) + { + GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); + } + GNUNET_OS_process_wait (proc); + GNUNET_OS_process_destroy (proc); + proc = NULL; + } + if (GNUNET_SCHEDULER_NO_TASK != read_task) { - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); + GNUNET_SCHEDULER_cancel (read_task); + read_task = GNUNET_SCHEDULER_NO_TASK; } - GNUNET_OS_process_wait (proc); - GNUNET_OS_process_destroy (proc); - proc = NULL; GNUNET_DISK_pipe_close (pipe_stdout); if (ok == 1) { @@ -158,12 +168,13 @@ int bytes; static void read_call (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { - struct GNUNET_DISK_FileHandle *stdout_read_handle = cls; + const struct GNUNET_DISK_FileHandle *stdout_read_handle = cls; char level[8]; long delay; long delays[8]; int rd; + read_task = GNUNET_SCHEDULER_NO_TASK; rd = GNUNET_DISK_file_read (stdout_read_handle, buf_ptr, sizeof (buf) - bytes); if (rd > 0) @@ -173,9 +184,9 @@ read_call (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) #if VERBOSE FPRINTF (stderr, "got %d bytes, reading more\n", rd); #endif - GNUNET_SCHEDULER_add_read_file (GNUNET_TIME_UNIT_FOREVER_REL, - stdout_read_handle, &read_call, - (void *) stdout_read_handle); + read_task = GNUNET_SCHEDULER_add_read_file (GNUNET_TIME_UNIT_FOREVER_REL, + stdout_read_handle, &read_call, + (void*) stdout_read_handle); return; } @@ -314,13 +325,14 @@ runone () break; } - proc = GNUNET_OS_start_process (GNUNET_NO, NULL, pipe_stdout, + proc = GNUNET_OS_start_process (GNUNET_NO, GNUNET_OS_INHERIT_STD_OUT_AND_ERR, NULL, pipe_stdout, #if MINGW "test_common_logging_dummy", #else "./test_common_logging_dummy", #endif "test_common_logging_dummy", NULL); + GNUNET_assert (NULL != proc); putenv ("GNUNET_FORCE_LOG="); putenv ("GNUNET_LOG="); @@ -339,9 +351,9 @@ runone () buf_ptr = buf; memset (&buf, 0, sizeof (buf)); - GNUNET_SCHEDULER_add_read_file (GNUNET_TIME_UNIT_FOREVER_REL, - stdout_read_handle, &read_call, - (void *) stdout_read_handle); + read_task = GNUNET_SCHEDULER_add_read_file (GNUNET_TIME_UNIT_FOREVER_REL, + stdout_read_handle, &read_call, + (void*) stdout_read_handle); } static void @@ -351,34 +363,16 @@ task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) runone (); } -/** - * Main method, starts scheduler with task1, - * checks that "ok" is correct at the end. - */ -static int -check () -{ - ok = 1; - GNUNET_SCHEDULER_run (&task, &ok); - return ok; -} - int main (int argc, char *argv[]) { - int ret; - GNUNET_log_setup ("test-common-logging-runtime-loglevels", -#if VERBOSE - "DEBUG", -#else "WARNING", -#endif NULL); - ret = check (); - - return ret; + ok = 1; + GNUNET_SCHEDULER_run (&task, &ok); + return ok; } /* end of test_common_logging_runtime_loglevels.c */ diff --git a/src/util/test_configuration.c b/src/util/test_configuration.c index 1242a5c..62ad5fa 100644 --- a/src/util/test_configuration.c +++ b/src/util/test_configuration.c @@ -231,7 +231,8 @@ checkDiffs (struct GNUNET_CONFIGURATION_Handle *cfgDefault, int option) /* Compare the dumped configuration with modifications done */ cfg = GNUNET_CONFIGURATION_create (); GNUNET_assert (GNUNET_OK == GNUNET_CONFIGURATION_parse (cfg, diffsFileName)); - remove (diffsFileName); + if (0 != remove (diffsFileName)) + GNUNET_log_strerror_file (GNUNET_ERROR_TYPE_WARNING, "remove", diffsFileName); cbData.callBackOption = COMPARE; cbData.cfgDiffs = cfgDiffs; GNUNET_CONFIGURATION_iterate (cfg, diffsCallBack, &cbData); diff --git a/src/util/test_connection.c b/src/util/test_connection.c index 4568f8e..e129c80 100644 --- a/src/util/test_connection.c +++ b/src/util/test_connection.c @@ -27,8 +27,6 @@ #include "gnunet_scheduler_lib.h" #include "gnunet_time_lib.h" -#define VERBOSE GNUNET_NO - #define PORT 12435 @@ -80,17 +78,13 @@ receive_check (void *cls, const void *buf, size_t available, { int *ok = cls; -#if VERBOSE GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Receive validates incoming data\n"); -#endif GNUNET_assert (buf != NULL); /* no timeout */ if (0 == memcmp (&"Hello World"[sofar], buf, available)) sofar += available; if (sofar < 12) { -#if VERBOSE GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Receive needs more data\n"); -#endif GNUNET_CONNECTION_receive (asock, 1024, GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 5), &receive_check, @@ -98,9 +92,7 @@ receive_check (void *cls, const void *buf, size_t available, } else { -#if VERBOSE GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Receive closes accepted socket\n"); -#endif *ok = 0; GNUNET_CONNECTION_destroy (asock); GNUNET_CONNECTION_destroy (csock); @@ -111,41 +103,33 @@ receive_check (void *cls, const void *buf, size_t available, static void run_accept (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { -#if VERBOSE GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Test accepts connection\n"); -#endif asock = GNUNET_CONNECTION_create_from_accept (NULL, NULL, ls); GNUNET_assert (asock != NULL); GNUNET_assert (GNUNET_YES == GNUNET_CONNECTION_check (asock)); -#if VERBOSE GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Test destroys listen socket\n"); -#endif GNUNET_CONNECTION_destroy (lsock); -#if VERBOSE GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Test asks to receive on accepted socket\n"); -#endif GNUNET_CONNECTION_receive (asock, 1024, GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 5), &receive_check, cls); } + static size_t make_hello (void *cls, size_t size, void *buf) { -#if VERBOSE GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Test prepares to transmit on connect socket\n"); -#endif GNUNET_assert (size >= 12); strcpy ((char *) buf, "Hello World"); -#if VERBOSE GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Test destroys client socket\n"); -#endif return 12; } + static void task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { @@ -154,30 +138,26 @@ task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) GNUNET_assert (lsock != NULL); csock = GNUNET_CONNECTION_create_from_connect (cfg, "localhost", PORT); GNUNET_assert (csock != NULL); -#if VERBOSE GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Test asks for write notification\n"); -#endif GNUNET_assert (NULL != GNUNET_CONNECTION_notify_transmit_ready (csock, 12, GNUNET_TIME_UNIT_SECONDS, &make_hello, NULL)); -#if VERBOSE GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Test prepares to accept\n"); -#endif GNUNET_SCHEDULER_add_read_net (GNUNET_TIME_UNIT_FOREVER_REL, ls, &run_accept, cls); } -/** - * Main method, starts scheduler with task , - * checks that "ok" is correct at the end. - */ -static int -check () +int +main (int argc, char *argv[]) { int ok; + GNUNET_log_setup ("test_connection", + "WARNING", + NULL); + ok = 1; cfg = GNUNET_CONFIGURATION_create (); GNUNET_CONFIGURATION_set_value_string (cfg, "resolver", "HOSTNAME", @@ -187,22 +167,4 @@ check () return ok; } - - -int -main (int argc, char *argv[]) -{ - int ret = 0; - - GNUNET_log_setup ("test_connection", -#if VERBOSE - "DEBUG", -#else - "WARNING", -#endif - NULL); - ret += check (); - return ret; -} - /* end of test_connection.c */ diff --git a/src/util/test_connection_addressing.c b/src/util/test_connection_addressing.c index ba7acae..e5c8ede 100644 --- a/src/util/test_connection_addressing.c +++ b/src/util/test_connection_addressing.c @@ -27,7 +27,6 @@ #include "gnunet_scheduler_lib.h" #include "gnunet_time_lib.h" -#define VERBOSE GNUNET_NO #define PORT 12435 @@ -174,36 +173,17 @@ task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) } -/** - * Main method, starts scheduler with task , - * checks that "ok" is correct at the end. - */ -static int -check () -{ - int ok; - - ok = 1; - GNUNET_SCHEDULER_run (&task, &ok); - return ok; -} - - - int main (int argc, char *argv[]) { - int ret = 0; + int ok; GNUNET_log_setup ("test_connection_addressing", -#if VERBOSE - "DEBUG", -#else "WARNING", -#endif NULL); - ret += check (); - return ret; + ok = 1; + GNUNET_SCHEDULER_run (&task, &ok); + return ok; } /* end of test_connection_addressing.c */ diff --git a/src/util/test_connection_receive_cancel.c b/src/util/test_connection_receive_cancel.c index 93fcd5f..9049034 100644 --- a/src/util/test_connection_receive_cancel.c +++ b/src/util/test_connection_receive_cancel.c @@ -27,8 +27,6 @@ #include "gnunet_scheduler_lib.h" #include "gnunet_time_lib.h" -#define VERBOSE GNUNET_NO - #define PORT 12435 diff --git a/src/util/test_connection_timeout.c b/src/util/test_connection_timeout.c index c0597b2..8d3f775 100644 --- a/src/util/test_connection_timeout.c +++ b/src/util/test_connection_timeout.c @@ -27,8 +27,6 @@ #include "gnunet_scheduler_lib.h" #include "gnunet_time_lib.h" -#define VERBOSE GNUNET_NO - #define PORT 12435 static struct GNUNET_CONNECTION_Handle *csock; @@ -78,18 +76,14 @@ send_kilo (void *cls, size_t size, void *buf) if (size == 0) { -#if VERBOSE GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Got the desired timeout!\n"); -#endif GNUNET_assert (buf == NULL); *ok = 0; GNUNET_CONNECTION_destroy (lsock); GNUNET_CONNECTION_destroy (csock); return 0; } -#if VERBOSE GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Sending kilo to fill buffer.\n"); -#endif GNUNET_assert (size >= 1024); memset (buf, 42, 1024); @@ -117,15 +111,15 @@ task_timeout (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) } - -/** - * Main method, starts scheduler with task_timeout. - */ -static int -check_timeout () +int +main (int argc, char *argv[]) { int ok; + GNUNET_log_setup ("test_connection_timeout", + "WARNING", + NULL); + ok = 1; cfg = GNUNET_CONFIGURATION_create (); GNUNET_CONFIGURATION_set_value_string (cfg, "resolver", "HOSTNAME", @@ -135,20 +129,4 @@ check_timeout () return ok; } -int -main (int argc, char *argv[]) -{ - int ret = 0; - - GNUNET_log_setup ("test_connection_timeout", -#if VERBOSE - "DEBUG", -#else - "WARNING", -#endif - NULL); - ret += check_timeout (); - return ret; -} - /* end of test_connection_timeout.c */ diff --git a/src/util/test_connection_timeout_no_connect.c b/src/util/test_connection_timeout_no_connect.c index 2e8f9be..50eaf70 100644 --- a/src/util/test_connection_timeout_no_connect.c +++ b/src/util/test_connection_timeout_no_connect.c @@ -27,8 +27,6 @@ #include "gnunet_scheduler_lib.h" #include "gnunet_time_lib.h" -#define VERBOSE GNUNET_NO - #define PORT 13425 static struct GNUNET_CONNECTION_Handle *csock; @@ -40,10 +38,7 @@ handle_timeout (void *cls, size_t size, void *buf) { int *ok = cls; -#if VERBOSE GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received timeout signal.\n"); -#endif - GNUNET_assert (size == 0); GNUNET_assert (buf == NULL); *ok = 0; @@ -64,15 +59,14 @@ task_timeout (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) } - -/** - * Main method, starts scheduler with task_timeout. - */ -static int -check_timeout () +int +main (int argc, char *argv[]) { int ok; + GNUNET_log_setup ("test_connection_timeout_no_connect", + "WARNING", + NULL); ok = 1; cfg = GNUNET_CONFIGURATION_create (); GNUNET_CONFIGURATION_set_value_string (cfg, "resolver", "HOSTNAME", @@ -82,20 +76,4 @@ check_timeout () return ok; } -int -main (int argc, char *argv[]) -{ - int ret = 0; - - GNUNET_log_setup ("test_connection_timeout_no_connect", -#if VERBOSE - "DEBUG", -#else - "WARNING", -#endif - NULL); - ret += check_timeout (); - return ret; -} - /* end of test_connection_timeout_no_connect.c */ diff --git a/src/util/test_connection_transmit_cancel.c b/src/util/test_connection_transmit_cancel.c index fec72d2..195ac68 100644 --- a/src/util/test_connection_transmit_cancel.c +++ b/src/util/test_connection_transmit_cancel.c @@ -27,8 +27,6 @@ #include "gnunet_scheduler_lib.h" #include "gnunet_time_lib.h" -#define VERBOSE GNUNET_NO - #define PORT 12435 static struct GNUNET_CONFIGURATION_Handle *cfg; @@ -61,16 +59,14 @@ task_transmit_cancel (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) } - - -/** - * Main method, starts scheduler with task_timeout. - */ -static int -check_transmit_cancel () +int +main (int argc, char *argv[]) { int ok; + GNUNET_log_setup ("test_connection_transmit_cancel", + "WARNING", + NULL); ok = 1; cfg = GNUNET_CONFIGURATION_create (); GNUNET_CONFIGURATION_set_value_string (cfg, "resolver", "HOSTNAME", @@ -80,22 +76,4 @@ check_transmit_cancel () return ok; } - -int -main (int argc, char *argv[]) -{ - int ret = 0; - - GNUNET_log_setup ("test_connection_transmit_cancel", -#if VERBOSE - "DEBUG", -#else - "WARNING", -#endif - NULL); - ret += check_transmit_cancel (); - - return ret; -} - /* end of test_connection_transmit_cancel.c */ diff --git a/src/util/test_container_bloomfilter.c b/src/util/test_container_bloomfilter.c index f881bb3..f9743bd 100644 --- a/src/util/test_container_bloomfilter.c +++ b/src/util/test_container_bloomfilter.c @@ -36,16 +36,16 @@ * Generate a random hashcode. */ static void -nextHC (GNUNET_HashCode * hc) +nextHC (struct GNUNET_HashCode * hc) { GNUNET_CRYPTO_hash_create_random (GNUNET_CRYPTO_QUALITY_WEAK, hc); } static int -add_iterator (void *cls, GNUNET_HashCode * next) +add_iterator (void *cls, struct GNUNET_HashCode * next) { int *ret = cls; - GNUNET_HashCode pos; + struct GNUNET_HashCode pos; if (0 == (*ret)--) return GNUNET_NO; @@ -59,7 +59,7 @@ main (int argc, char *argv[]) { struct GNUNET_CONTAINER_BloomFilter *bf; struct GNUNET_CONTAINER_BloomFilter *bfi; - GNUNET_HashCode tmp; + struct GNUNET_HashCode tmp; int i; int ok1; int ok2; diff --git a/src/util/test_container_multihashmap.c b/src/util/test_container_multihashmap.c index ba621c1..ff50df1 100644 --- a/src/util/test_container_multihashmap.c +++ b/src/util/test_container_multihashmap.c @@ -35,12 +35,12 @@ static int testMap (int i) { struct GNUNET_CONTAINER_MultiHashMap *m; - GNUNET_HashCode k1; - GNUNET_HashCode k2; + struct GNUNET_HashCode k1; + struct GNUNET_HashCode k2; const char *ret; int j; - CHECK (NULL != (m = GNUNET_CONTAINER_multihashmap_create (i))); + CHECK (NULL != (m = GNUNET_CONTAINER_multihashmap_create (i, GNUNET_NO))); memset (&k1, 0, sizeof (k1)); memset (&k2, 1, sizeof (k2)); CHECK (GNUNET_NO == GNUNET_CONTAINER_multihashmap_contains (m, &k1)); diff --git a/src/util/test_crypto_ecc.c b/src/util/test_crypto_ecc.c new file mode 100644 index 0000000..6dac176 --- /dev/null +++ b/src/util/test_crypto_ecc.c @@ -0,0 +1,241 @@ +/* + This file is part of GNUnet. + (C) 2002, 2003, 2004, 2006, 2009 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. + +*/ +/** + * @file util/test_crypto_ecc.c + * @brief testcase for ECC public key crypto + * @author Christian Grothoff + */ +#include "platform.h" +#include "gnunet_common.h" +#include "gnunet_util_lib.h" +#include "gnunet_signatures.h" +#include + +#define TESTSTRING "Hello World\0" +#define MAX_TESTVAL sizeof(struct GNUNET_CRYPTO_AesSessionKey) +#define ITER 25 +#define KEYFILE "/tmp/test-gnunet-crypto-ecc.key" + +#define PERF GNUNET_YES + +static struct GNUNET_CRYPTO_EccPrivateKey *key; + + +static int +testSignVerify () +{ + struct GNUNET_CRYPTO_EccSignature sig; + struct GNUNET_CRYPTO_EccSignaturePurpose purp; + struct GNUNET_CRYPTO_EccPublicKeyBinaryEncoded pkey; + int i; + struct GNUNET_TIME_Absolute start; + int ok = GNUNET_OK; + + FPRINTF (stderr, "%s", "W"); + GNUNET_CRYPTO_ecc_key_get_public (key, &pkey); + start = GNUNET_TIME_absolute_get (); + purp.size = htonl (sizeof (struct GNUNET_CRYPTO_EccSignaturePurpose)); + purp.purpose = htonl (GNUNET_SIGNATURE_PURPOSE_TEST); + + for (i = 0; i < ITER; i++) + { + FPRINTF (stderr, "%s", "."); + if (GNUNET_SYSERR == GNUNET_CRYPTO_ecc_sign (key, &purp, &sig)) + { + FPRINTF (stderr, "%s", "GNUNET_CRYPTO_ecc_sign returned SYSERR\n"); + ok = GNUNET_SYSERR; + continue; + } + if (GNUNET_SYSERR == + GNUNET_CRYPTO_ecc_verify (GNUNET_SIGNATURE_PURPOSE_TEST, &purp, &sig, + &pkey)) + { + printf ("GNUNET_CRYPTO_ecc_verify failed!\n"); + ok = GNUNET_SYSERR; + continue; + } + if (GNUNET_SYSERR != + GNUNET_CRYPTO_ecc_verify (GNUNET_SIGNATURE_PURPOSE_TRANSPORT_PONG_OWN, + &purp, &sig, &pkey)) + { + printf ("GNUNET_CRYPTO_ecc_verify failed to fail!\n"); + ok = GNUNET_SYSERR; + continue; + } + } + printf ("%d ECC sign/verify operations %s\n", ITER, + GNUNET_STRINGS_relative_time_to_string (GNUNET_TIME_absolute_get_duration (start), GNUNET_YES)); + return ok; +} + + +#if PERF +static int +testSignPerformance () +{ + struct GNUNET_CRYPTO_EccSignaturePurpose purp; + struct GNUNET_CRYPTO_EccSignature sig; + struct GNUNET_CRYPTO_EccPublicKeyBinaryEncoded pkey; + int i; + struct GNUNET_TIME_Absolute start; + int ok = GNUNET_OK; + + purp.size = htonl (sizeof (struct GNUNET_CRYPTO_EccSignaturePurpose)); + purp.purpose = htonl (GNUNET_SIGNATURE_PURPOSE_TEST); + FPRINTF (stderr, "%s", "W"); + GNUNET_CRYPTO_ecc_key_get_public (key, &pkey); + start = GNUNET_TIME_absolute_get (); + for (i = 0; i < ITER; i++) + { + FPRINTF (stderr, "%s", "."); + if (GNUNET_SYSERR == GNUNET_CRYPTO_ecc_sign (key, &purp, &sig)) + { + FPRINTF (stderr, "%s", "GNUNET_CRYPTO_ecc_sign returned SYSERR\n"); + ok = GNUNET_SYSERR; + continue; + } + } + printf ("%d ECC sign operations %llu ms\n", ITER, + (unsigned long long) + GNUNET_TIME_absolute_get_duration (start).rel_value); + return ok; +} +#endif + + +static int +testCreateFromFile () +{ + struct GNUNET_CRYPTO_EccPublicKeyBinaryEncoded p1; + struct GNUNET_CRYPTO_EccPublicKeyBinaryEncoded p2; + + key = GNUNET_CRYPTO_ecc_key_create_from_file (KEYFILE); + GNUNET_assert (NULL != key); + GNUNET_CRYPTO_ecc_key_get_public (key, &p1); + GNUNET_CRYPTO_ecc_key_free (key); + key = GNUNET_CRYPTO_ecc_key_create_from_file (KEYFILE); + GNUNET_assert (NULL != key); + GNUNET_CRYPTO_ecc_key_get_public (key, &p2); + GNUNET_assert (0 == memcmp (&p1, &p2, sizeof (p1))); + GNUNET_CRYPTO_ecc_key_free (key); + GNUNET_assert (0 == UNLINK (KEYFILE)); + key = GNUNET_CRYPTO_ecc_key_create_from_file (KEYFILE); + GNUNET_assert (NULL != key); + GNUNET_CRYPTO_ecc_key_get_public (key, &p2); + GNUNET_assert (0 != memcmp (&p1, &p2, sizeof (p1))); + return GNUNET_OK; +} + + +static void +key_cont (void *cls, + struct GNUNET_CRYPTO_EccPrivateKey *pk, + const char *emsg) +{ + const char *txt = cls; + struct GNUNET_CRYPTO_EccPublicKeyBinaryEncoded pub1; + struct GNUNET_CRYPTO_EccPublicKeyBinaryEncoded pub2; + + GNUNET_assert (0 == strcmp ("ok", txt)); + GNUNET_CRYPTO_ecc_key_get_public (pk, &pub1); + GNUNET_CRYPTO_ecc_key_get_public (key, &pub2); + GNUNET_assert (0 == memcmp (&pub1, &pub2, + sizeof (pub1))); + GNUNET_CRYPTO_ecc_key_free (pk); +} + + +static void +test_async_creation (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct GNUNET_CRYPTO_EccKeyGenerationContext *gc; + + gc = GNUNET_CRYPTO_ecc_key_create_start (KEYFILE, + &key_cont, + (void*) "bug"); + GNUNET_CRYPTO_ecc_key_create_stop (gc); + gc = GNUNET_CRYPTO_ecc_key_create_start (KEYFILE, + &key_cont, + (void*) "ok"); +} + + +static void +test_ecdh () +{ + struct GNUNET_CRYPTO_EccPrivateKey *priv1; + struct GNUNET_CRYPTO_EccPrivateKey *priv2; + struct GNUNET_CRYPTO_EccPublicKeyBinaryEncoded pub1; + struct GNUNET_CRYPTO_EccPublicKeyBinaryEncoded pub2; + struct GNUNET_HashCode ecdh1; + struct GNUNET_HashCode ecdh2; + + priv1 = GNUNET_CRYPTO_ecc_key_create (); + priv2 = GNUNET_CRYPTO_ecc_key_create (); + GNUNET_CRYPTO_ecc_key_get_public (priv1, &pub1); + GNUNET_CRYPTO_ecc_key_get_public (priv2, &pub2); + GNUNET_CRYPTO_ecc_ecdh (priv1, &pub2, &ecdh1); + GNUNET_CRYPTO_ecc_ecdh (priv2, &pub1, &ecdh2); + GNUNET_CRYPTO_ecc_key_free (priv1); + GNUNET_CRYPTO_ecc_key_free (priv2); + GNUNET_assert (0 == memcmp (&ecdh1, &ecdh2, + sizeof (struct GNUNET_HashCode))); +} + + +int +main (int argc, char *argv[]) +{ + int failureCount = 0; + + if (!gcry_check_version ("1.5.0")) + { + FPRINTF (stderr, + _ + ("libgcrypt has not the expected version (version %s is required).\n"), + "1.5.0"); + return 0; + } + GNUNET_log_setup ("test-crypto-ecc", "WARNING", NULL); + GNUNET_CRYPTO_random_disable_entropy_gathering (); + if (GNUNET_OK != testCreateFromFile ()) + failureCount++; + GNUNET_SCHEDULER_run (&test_async_creation, NULL); +#if PERF + if (GNUNET_OK != testSignPerformance ()) + failureCount++; +#endif + if (GNUNET_OK != testSignVerify ()) + failureCount++; + GNUNET_CRYPTO_ecc_key_free (key); + GNUNET_assert (0 == UNLINK (KEYFILE)); + test_ecdh (); + + if (failureCount != 0) + { + printf ("\n\n%d TESTS FAILED!\n\n", failureCount); + return -1; + } + return 0; +} + +/* end of test_crypto_ecc.c */ diff --git a/src/util/test_crypto_hash.c b/src/util/test_crypto_hash.c index bc04114..a8ef39a 100644 --- a/src/util/test_crypto_hash.c +++ b/src/util/test_crypto_hash.c @@ -35,18 +35,18 @@ static char block[65536]; static int test (int number) { - GNUNET_HashCode h1; - GNUNET_HashCode h2; + struct GNUNET_HashCode h1; + struct GNUNET_HashCode h2; struct GNUNET_CRYPTO_HashAsciiEncoded enc; - memset (&h1, number, sizeof (GNUNET_HashCode)); + memset (&h1, number, sizeof (struct GNUNET_HashCode)); GNUNET_CRYPTO_hash_to_enc (&h1, &enc); if (GNUNET_OK != GNUNET_CRYPTO_hash_from_string ((char *) &enc, &h2)) { printf ("enc2hash failed!\n"); return 1; } - if (0 != memcmp (&h1, &h2, sizeof (GNUNET_HashCode))) + if (0 != memcmp (&h1, &h2, sizeof (struct GNUNET_HashCode))) return 1; return 0; } @@ -67,10 +67,10 @@ testArithmetic () { static struct GNUNET_CRYPTO_AesSessionKey zskey; static struct GNUNET_CRYPTO_AesInitializationVector ziv; - GNUNET_HashCode h1; - GNUNET_HashCode h2; - GNUNET_HashCode d; - GNUNET_HashCode s; + struct GNUNET_HashCode h1; + struct GNUNET_HashCode h2; + struct GNUNET_HashCode d; + struct GNUNET_HashCode s; struct GNUNET_CRYPTO_AesSessionKey skey; struct GNUNET_CRYPTO_AesInitializationVector iv; @@ -107,10 +107,10 @@ testArithmetic () } static void -finished_task (void *cls, const GNUNET_HashCode * res) +finished_task (void *cls, const struct GNUNET_HashCode * res) { int *ret = cls; - GNUNET_HashCode want; + struct GNUNET_HashCode want; GNUNET_CRYPTO_hash (block, sizeof (block), &want); if (0 != memcmp (res, &want, sizeof (want))) diff --git a/src/util/test_crypto_ksk.c b/src/util/test_crypto_ksk.c index 58c4595..f062e31 100644 --- a/src/util/test_crypto_ksk.c +++ b/src/util/test_crypto_ksk.c @@ -25,9 +25,9 @@ */ #include "platform.h" #include "gnunet_common.h" -#include "gnunet_crypto_lib.h" +#include "gnunet_util_lib.h" #include "gnunet_signatures.h" -#include "gnunet_time_lib.h" + #define TESTSTRING "Hello World\0" #define MAX_TESTVAL 20 @@ -40,7 +40,7 @@ testCorrectKey () { const char *want = "010601000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000b73c215f7a5e6b09bec55713c901786c09324a150980e014bdb0d04426934929c3b4971a9711af5455536cd6eeb8bfa004ee904972a737455f53c752987d8c82b755bc02882b44950c4acdc1672ba74c3b94d81a4c1ea3d74e7700ae5594c3a4f3c559e4bff2df6844fac302e4b66175e14dc8bad3ce44281d2fec1a1abef06301010000"; - GNUNET_HashCode in; + struct GNUNET_HashCode in; struct GNUNET_CRYPTO_RsaPrivateKey *hostkey; struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded pkey; int i; @@ -79,7 +79,7 @@ testCorrectKey () static int testMultiKey (const char *word) { - GNUNET_HashCode in; + struct GNUNET_HashCode in; struct GNUNET_CRYPTO_RsaPrivateKey *hostkey; struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded pkey; struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded pkey1; @@ -167,9 +167,10 @@ testEncryptDecrypt (struct GNUNET_CRYPTO_RsaPrivateKey *hostkey) continue; } } - printf ("%d RSA encrypt/decrypt operations %llums (%d failures)\n", ITER, - (unsigned long long) - GNUNET_TIME_absolute_get_duration (start).rel_value, ok); + printf ("%d RSA encrypt/decrypt operations %s (%d failures)\n", + ITER, + GNUNET_STRINGS_relative_time_to_string (GNUNET_TIME_absolute_get_duration (start), GNUNET_YES), + ok); if (ok == 0) return GNUNET_OK; else @@ -217,9 +218,9 @@ testSignVerify (struct GNUNET_CRYPTO_RsaPrivateKey *hostkey) continue; } } - printf ("%d RSA sign/verify operations %llums\n", ITER, - (unsigned long long) - GNUNET_TIME_absolute_get_duration (start).rel_value); + printf ("%d RSA sign/verify operations %s\n", + ITER, + GNUNET_STRINGS_relative_time_to_string (GNUNET_TIME_absolute_get_duration (start), GNUNET_YES)); return ok; } @@ -228,7 +229,7 @@ int main (int argc, char *argv[]) { int failureCount = 0; - GNUNET_HashCode in; + struct GNUNET_HashCode in; struct GNUNET_CRYPTO_RsaPrivateKey *hostkey; GNUNET_log_setup ("test-crypto-ksk", "WARNING", NULL); diff --git a/src/util/test_crypto_rsa.c b/src/util/test_crypto_rsa.c index f6800af..ee67378 100644 --- a/src/util/test_crypto_rsa.c +++ b/src/util/test_crypto_rsa.c @@ -25,9 +25,8 @@ */ #include "platform.h" #include "gnunet_common.h" -#include "gnunet_crypto_lib.h" +#include "gnunet_util_lib.h" #include "gnunet_signatures.h" -#include "gnunet_time_lib.h" #define TESTSTRING "Hello World\0" #define MAX_TESTVAL sizeof(struct GNUNET_CRYPTO_AesSessionKey) @@ -36,10 +35,12 @@ #define PERF GNUNET_YES +static struct GNUNET_CRYPTO_RsaPrivateKey *key; + + static int testEncryptDecrypt () { - struct GNUNET_CRYPTO_RsaPrivateKey *hostkey; struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded pkey; struct GNUNET_CRYPTO_RsaEncryptedData target; char result[MAX_TESTVAL]; @@ -48,9 +49,7 @@ testEncryptDecrypt () int ok; FPRINTF (stderr, "%s", "W"); - hostkey = GNUNET_CRYPTO_rsa_key_create (); - GNUNET_CRYPTO_rsa_key_get_public (hostkey, &pkey); - + GNUNET_CRYPTO_rsa_key_get_public (key, &pkey); ok = 0; start = GNUNET_TIME_absolute_get (); for (i = 0; i < ITER; i++) @@ -65,7 +64,7 @@ testEncryptDecrypt () continue; } if (-1 == - GNUNET_CRYPTO_rsa_decrypt (hostkey, &target, result, + GNUNET_CRYPTO_rsa_decrypt (key, &target, result, strlen (TESTSTRING) + 1)) { FPRINTF (stderr, "%s", "GNUNET_CRYPTO_rsa_decrypt returned SYSERR\n"); @@ -81,21 +80,20 @@ testEncryptDecrypt () continue; } } - printf ("%d RSA encrypt/decrypt operations %llums (%d failures)\n", ITER, - (unsigned long long) - GNUNET_TIME_absolute_get_duration (start).rel_value, ok); - GNUNET_CRYPTO_rsa_key_free (hostkey); + printf ("%d RSA encrypt/decrypt operations %s (%d failures)\n", + ITER, + GNUNET_STRINGS_relative_time_to_string (GNUNET_TIME_absolute_get_duration (start), GNUNET_YES), + ok); if (ok == 0) return GNUNET_OK; - else - return GNUNET_SYSERR; + return GNUNET_SYSERR; } + #if PERF static int testEncryptPerformance () { - struct GNUNET_CRYPTO_RsaPrivateKey *hostkey; struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded pkey; struct GNUNET_CRYPTO_RsaEncryptedData target; int i; @@ -103,9 +101,7 @@ testEncryptPerformance () int ok; FPRINTF (stderr, "%s", "W"); - hostkey = GNUNET_CRYPTO_rsa_key_create (); - GNUNET_CRYPTO_rsa_key_get_public (hostkey, &pkey); - + GNUNET_CRYPTO_rsa_key_get_public (key, &pkey); ok = 0; start = GNUNET_TIME_absolute_get (); for (i = 0; i < ITER; i++) @@ -123,7 +119,6 @@ testEncryptPerformance () printf ("%d RSA encrypt operations %llu ms (%d failures)\n", ITER, (unsigned long long) GNUNET_TIME_absolute_get_duration (start).rel_value, ok); - GNUNET_CRYPTO_rsa_key_free (hostkey); if (ok != 0) return GNUNET_SYSERR; return GNUNET_OK; @@ -133,7 +128,6 @@ testEncryptPerformance () static int testEncryptDecryptSK () { - struct GNUNET_CRYPTO_RsaPrivateKey *hostkey; struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded pkey; struct GNUNET_CRYPTO_RsaEncryptedData target; struct GNUNET_CRYPTO_AesSessionKey insk; @@ -143,9 +137,7 @@ testEncryptDecryptSK () int ok; FPRINTF (stderr, "%s", "W"); - hostkey = GNUNET_CRYPTO_rsa_key_create (); - GNUNET_CRYPTO_rsa_key_get_public (hostkey, &pkey); - + GNUNET_CRYPTO_rsa_key_get_public (key, &pkey); ok = 0; start = GNUNET_TIME_absolute_get (); for (i = 0; i < ITER; i++) @@ -162,7 +154,7 @@ testEncryptDecryptSK () continue; } if (-1 == - GNUNET_CRYPTO_rsa_decrypt (hostkey, &target, &outsk, + GNUNET_CRYPTO_rsa_decrypt (key, &target, &outsk, sizeof (struct GNUNET_CRYPTO_AesSessionKey))) { FPRINTF (stderr, "%s", "GNUNET_CRYPTO_rsa_decrypt returned SYSERR\n"); @@ -177,10 +169,10 @@ testEncryptDecryptSK () continue; } } - printf ("%d RSA encrypt/decrypt SK operations %llums (%d failures)\n", ITER, - (unsigned long long) - GNUNET_TIME_absolute_get_duration (start).rel_value, ok); - GNUNET_CRYPTO_rsa_key_free (hostkey); + printf ("%d RSA encrypt/decrypt SK operations %s (%d failures)\n", + ITER, + GNUNET_STRINGS_relative_time_to_string (GNUNET_TIME_absolute_get_duration (start), GNUNET_YES), + ok); if (ok != 0) return GNUNET_SYSERR; return GNUNET_OK; @@ -190,7 +182,6 @@ testEncryptDecryptSK () static int testSignVerify () { - struct GNUNET_CRYPTO_RsaPrivateKey *hostkey; struct GNUNET_CRYPTO_RsaSignature sig; struct GNUNET_CRYPTO_RsaSignaturePurpose purp; struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded pkey; @@ -199,8 +190,7 @@ testSignVerify () int ok = GNUNET_OK; FPRINTF (stderr, "%s", "W"); - hostkey = GNUNET_CRYPTO_rsa_key_create (); - GNUNET_CRYPTO_rsa_key_get_public (hostkey, &pkey); + GNUNET_CRYPTO_rsa_key_get_public (key, &pkey); start = GNUNET_TIME_absolute_get (); purp.size = htonl (sizeof (struct GNUNET_CRYPTO_RsaSignaturePurpose)); purp.purpose = htonl (GNUNET_SIGNATURE_PURPOSE_TEST); @@ -208,7 +198,7 @@ testSignVerify () for (i = 0; i < ITER; i++) { FPRINTF (stderr, "%s", "."); - if (GNUNET_SYSERR == GNUNET_CRYPTO_rsa_sign (hostkey, &purp, &sig)) + if (GNUNET_SYSERR == GNUNET_CRYPTO_rsa_sign (key, &purp, &sig)) { FPRINTF (stderr, "%s", "GNUNET_CRYPTO_rsa_sign returned SYSERR\n"); ok = GNUNET_SYSERR; @@ -231,10 +221,8 @@ testSignVerify () continue; } } - printf ("%d RSA sign/verify operations %llums\n", ITER, - (unsigned long long) - GNUNET_TIME_absolute_get_duration (start).rel_value); - GNUNET_CRYPTO_rsa_key_free (hostkey); + printf ("%d RSA sign/verify operations %s\n", ITER, + GNUNET_STRINGS_relative_time_to_string (GNUNET_TIME_absolute_get_duration (start), GNUNET_YES)); return ok; } @@ -243,7 +231,6 @@ testSignVerify () static int testSignPerformance () { - struct GNUNET_CRYPTO_RsaPrivateKey *hostkey; struct GNUNET_CRYPTO_RsaSignaturePurpose purp; struct GNUNET_CRYPTO_RsaSignature sig; struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded pkey; @@ -254,13 +241,12 @@ testSignPerformance () purp.size = htonl (sizeof (struct GNUNET_CRYPTO_RsaSignaturePurpose)); purp.purpose = htonl (GNUNET_SIGNATURE_PURPOSE_TEST); FPRINTF (stderr, "%s", "W"); - hostkey = GNUNET_CRYPTO_rsa_key_create (); - GNUNET_CRYPTO_rsa_key_get_public (hostkey, &pkey); + GNUNET_CRYPTO_rsa_key_get_public (key, &pkey); start = GNUNET_TIME_absolute_get (); for (i = 0; i < ITER; i++) { FPRINTF (stderr, "%s", "."); - if (GNUNET_SYSERR == GNUNET_CRYPTO_rsa_sign (hostkey, &purp, &sig)) + if (GNUNET_SYSERR == GNUNET_CRYPTO_rsa_sign (key, &purp, &sig)) { FPRINTF (stderr, "%s", "GNUNET_CRYPTO_rsa_sign returned SYSERR\n"); ok = GNUNET_SYSERR; @@ -270,7 +256,6 @@ testSignPerformance () printf ("%d RSA sign operations %llu ms\n", ITER, (unsigned long long) GNUNET_TIME_absolute_get_duration (start).rel_value); - GNUNET_CRYPTO_rsa_key_free (hostkey); return ok; } #endif @@ -279,7 +264,6 @@ testSignPerformance () static int testCreateFromFile () { - struct GNUNET_CRYPTO_RsaPrivateKey *key; struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded p1; struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded p2; @@ -297,12 +281,44 @@ testCreateFromFile () GNUNET_assert (NULL != key); GNUNET_CRYPTO_rsa_key_get_public (key, &p2); GNUNET_assert (0 != memcmp (&p1, &p2, sizeof (p1))); - GNUNET_CRYPTO_rsa_key_free (key); - GNUNET_assert (0 == UNLINK (KEYFILE)); return GNUNET_OK; } +static void +key_cont (void *cls, + struct GNUNET_CRYPTO_RsaPrivateKey *pk, + const char *emsg) +{ + const char *txt = cls; + struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded pub1; + struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded pub2; + + GNUNET_assert (0 == strcmp ("ok", txt)); + GNUNET_CRYPTO_rsa_key_get_public (pk, &pub1); + GNUNET_CRYPTO_rsa_key_get_public (key, &pub2); + GNUNET_assert (0 == memcmp (&pub1, &pub2, + sizeof (pub1))); + GNUNET_CRYPTO_rsa_key_free (pk); +} + + +static void +test_async_creation (void *cls, + const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct GNUNET_CRYPTO_RsaKeyGenerationContext *gc; + + gc = GNUNET_CRYPTO_rsa_key_create_start (KEYFILE, + &key_cont, + (void*) "bug"); + GNUNET_CRYPTO_rsa_key_create_stop (gc); + gc = GNUNET_CRYPTO_rsa_key_create_start (KEYFILE, + &key_cont, + (void*) "ok"); +} + + int main (int argc, char *argv[]) { @@ -312,6 +328,7 @@ main (int argc, char *argv[]) GNUNET_CRYPTO_random_disable_entropy_gathering (); if (GNUNET_OK != testCreateFromFile ()) failureCount++; + GNUNET_SCHEDULER_run (&test_async_creation, NULL); #if PERF if (GNUNET_OK != testEncryptPerformance ()) failureCount++; @@ -324,6 +341,8 @@ main (int argc, char *argv[]) failureCount++; if (GNUNET_OK != testSignVerify ()) failureCount++; + GNUNET_CRYPTO_rsa_key_free (key); + GNUNET_assert (0 == UNLINK (KEYFILE)); if (failureCount != 0) { diff --git a/src/util/test_disk.c b/src/util/test_disk.c index 149cec0..804a870 100644 --- a/src/util/test_disk.c +++ b/src/util/test_disk.c @@ -250,7 +250,7 @@ testDirMani () return 1; if (GNUNET_OK != GNUNET_DISK_directory_create ("test")) return 1; - if (GNUNET_YES != GNUNET_DISK_directory_test ("test")) + if (GNUNET_YES != GNUNET_DISK_directory_test ("test", GNUNET_YES)) return 1; if (GNUNET_OK != GNUNET_DISK_directory_remove ("test")) return 1; diff --git a/src/util/test_getopt.c b/src/util/test_getopt.c index a517887..313167d 100644 --- a/src/util/test_getopt.c +++ b/src/util/test_getopt.c @@ -26,7 +26,6 @@ #include "gnunet_configuration_lib.h" #include "gnunet_getopt_lib.h" -#define VERBOSE 0 static int testMinimal () @@ -45,6 +44,7 @@ testMinimal () return 0; } + static int testVerbose () { @@ -75,6 +75,7 @@ testVerbose () return 0; } + static int testVersion () { @@ -84,11 +85,11 @@ testVersion () NULL }; const struct GNUNET_GETOPT_CommandLineOption versionoptionlist[] = { - GNUNET_GETOPT_OPTION_VERSION (PACKAGE_VERSION), + GNUNET_GETOPT_OPTION_VERSION (PACKAGE_VERSION " " VCS_VERSION), GNUNET_GETOPT_OPTION_END }; - if (-1 != GNUNET_GETOPT_run ("test_getopt", versionoptionlist, 2, myargv)) + if (0 != GNUNET_GETOPT_run ("test_getopt", versionoptionlist, 2, myargv)) { GNUNET_break (0); return 1; @@ -96,6 +97,7 @@ testVersion () return 0; } + static int testAbout () { @@ -109,7 +111,7 @@ testAbout () GNUNET_GETOPT_OPTION_END }; - if (-1 != GNUNET_GETOPT_run ("test_getopt", aboutoptionlist, 2, myargv)) + if (0 != GNUNET_GETOPT_run ("test_getopt", aboutoptionlist, 2, myargv)) { GNUNET_break (0); return 1; @@ -117,6 +119,7 @@ testAbout () return 0; } + static int testLogOpts () { @@ -153,6 +156,7 @@ testLogOpts () return 0; } + static int testFlagNum () { @@ -190,6 +194,7 @@ testFlagNum () return 0; } + int main (int argc, char *argv[]) { diff --git a/src/util/test_os_network.c b/src/util/test_os_network.c index 4486e6a..2cdd750 100644 --- a/src/util/test_os_network.c +++ b/src/util/test_os_network.c @@ -26,7 +26,6 @@ #include "gnunet_configuration_lib.h" #include "gnunet_os_lib.h" -#define VERBOSE 1 /** * Check if the address we got is IPv4 or IPv6 loopback (which should @@ -40,20 +39,20 @@ proc (void *cls, const char *name, int isDefault, const struct sockaddr *addr, { int *ok = cls; char buf[INET6_ADDRSTRLEN]; + const char * protocol; if (NULL == addr) return GNUNET_OK; -#if VERBOSE - const char * protocol; if (addrlen == sizeof (struct sockaddr_in)) protocol = "IPv4"; else protocol = "IPv6"; - printf ("%s Address `%s'\n", protocol, GNUNET_a2s ((const struct sockaddr *) addr,addrlen) ); - printf (" Netmask `%s'\n", GNUNET_a2s ((const struct sockaddr *) netmask, addrlen) ); - printf (" Broadcast `%s'\n", GNUNET_a2s ((const struct sockaddr *) broadcast_addr,addrlen) ); -#endif - + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "%s Address `%s'\n", protocol, GNUNET_a2s ((const struct sockaddr *) addr,addrlen) ); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Netmask `%s'\n", GNUNET_a2s ((const struct sockaddr *) netmask, addrlen) ); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "`%s'\n", GNUNET_a2s ((const struct sockaddr *) broadcast_addr,addrlen) ); inet_ntop (addr->sa_family, (addr->sa_family == AF_INET) ? (void *) &((struct sockaddr_in *) addr)->sin_addr @@ -64,23 +63,16 @@ proc (void *cls, const char *name, int isDefault, const struct sockaddr *addr, return GNUNET_OK; } -static int -testifcs () + +int +main (int argc, char *argv[]) { int ret; + GNUNET_log_setup ("test-os-network", "WARNING", NULL); ret = 1; GNUNET_OS_network_interfaces_list (&proc, &ret); return ret; } -int -main (int argc, char *argv[]) -{ - int errCnt = 0; - - GNUNET_log_setup ("test-os-network", "WARNING", NULL); - if (0 != testifcs ()) - errCnt++; - return errCnt; -} +/* end of test_os_network.c */ diff --git a/src/util/test_os_priority.c b/src/util/test_os_priority.c index 94e2719..bb740db 100644 --- a/src/util/test_os_priority.c +++ b/src/util/test_os_priority.c @@ -25,7 +25,6 @@ #include "gnunet_common.h" #include "gnunet_os_lib.h" -#define VERBOSE 0 static int testprio () diff --git a/src/util/test_os_start_process.c b/src/util/test_os_start_process.c index 0d14818..5994518 100644 --- a/src/util/test_os_start_process.c +++ b/src/util/test_os_start_process.c @@ -33,21 +33,26 @@ #include "gnunet_scheduler_lib.h" #include "disk.h" -#define VERBOSE GNUNET_NO -static char *test_phrase = "HELLO WORLD"; +static const char *test_phrase = "HELLO WORLD"; + static int ok; static struct GNUNET_OS_Process *proc; -/* Pipe to write to started processes stdin (on write end) */ +/** + * Pipe to write to started processes stdin (on write end) + */ static struct GNUNET_DISK_PipeHandle *hello_pipe_stdin; -/* Pipe to read from started processes stdout (on read end) */ +/** + * Pipe to read from started processes stdout (on read end) + */ static struct GNUNET_DISK_PipeHandle *hello_pipe_stdout; static GNUNET_SCHEDULER_TaskIdentifier die_task; + static void end_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { @@ -62,6 +67,7 @@ end_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) GNUNET_DISK_pipe_close (hello_pipe_stdin); } + static void read_call (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { @@ -73,9 +79,7 @@ read_call (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) bytes = GNUNET_DISK_file_read (stdout_read_handle, &buf, sizeof (buf)); -#if VERBOSE - FPRINTF (stderr, "bytes is %d\n", bytes); -#endif + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "bytes is %d\n", bytes); if (bytes < 1) { @@ -87,10 +91,8 @@ read_call (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) } ok = strncmp (&buf[0], test_phrase, strlen (test_phrase)); -#if VERBOSE - FPRINTF (stderr, "read %s\n", &buf[0]); -#endif - if (ok == 0) + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "read %s\n", &buf[0]); + if (0 == ok) { GNUNET_SCHEDULER_cancel (die_task); GNUNET_SCHEDULER_add_now (&end_task, NULL); @@ -111,7 +113,11 @@ run_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) const struct GNUNET_DISK_FileHandle *stdout_read_handle; const struct GNUNET_DISK_FileHandle *wh; +#if !WINDOWS GNUNET_asprintf (&fn, "cat"); +#else + GNUNET_asprintf (&fn, "w32cat"); +#endif hello_pipe_stdin = GNUNET_DISK_pipe (GNUNET_YES, GNUNET_YES, GNUNET_YES, GNUNET_NO); hello_pipe_stdout = GNUNET_DISK_pipe (GNUNET_YES, GNUNET_YES, GNUNET_NO, GNUNET_YES); @@ -125,7 +131,7 @@ run_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) } proc = - GNUNET_OS_start_process (GNUNET_NO, hello_pipe_stdin, hello_pipe_stdout, fn, + GNUNET_OS_start_process (GNUNET_NO, GNUNET_OS_INHERIT_STD_ERR, hello_pipe_stdin, hello_pipe_stdout, fn, "test_gnunet_echo_hello", "-", NULL); GNUNET_free (fn); @@ -181,20 +187,26 @@ check_run () static int check_kill () { + char *fn; +#if !WINDOWS + GNUNET_asprintf (&fn, "cat"); +#else + GNUNET_asprintf (&fn, "w32cat"); +#endif hello_pipe_stdin = GNUNET_DISK_pipe (GNUNET_YES, GNUNET_YES, GNUNET_YES, GNUNET_NO); hello_pipe_stdout = GNUNET_DISK_pipe (GNUNET_YES, GNUNET_YES, GNUNET_NO, GNUNET_YES); if ((hello_pipe_stdout == NULL) || (hello_pipe_stdin == NULL)) { + GNUNET_free (fn); return 1; } proc = - GNUNET_OS_start_process (GNUNET_YES, hello_pipe_stdin, hello_pipe_stdout, "cat", + GNUNET_OS_start_process (GNUNET_YES, GNUNET_OS_INHERIT_STD_ERR, hello_pipe_stdin, hello_pipe_stdout, fn, "gnunet-service-resolver", "-", NULL); - sleep (1); /* give process time to start and open pipe */ + sleep (1); /* give process time to start, so we actually use the pipe-kill mechanism! */ + GNUNET_free (fn); if (0 != GNUNET_OS_process_kill (proc, SIGTERM)) - { GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); - } GNUNET_assert (GNUNET_OK == GNUNET_OS_process_wait (proc)); GNUNET_OS_process_destroy (proc); proc = NULL; @@ -210,19 +222,27 @@ check_kill () static int check_instant_kill () { + char *fn; +#if !WINDOWS + GNUNET_asprintf (&fn, "cat"); +#else + GNUNET_asprintf (&fn, "w32cat"); +#endif hello_pipe_stdin = GNUNET_DISK_pipe (GNUNET_YES, GNUNET_YES, GNUNET_YES, GNUNET_NO); hello_pipe_stdout = GNUNET_DISK_pipe (GNUNET_YES, GNUNET_YES, GNUNET_NO, GNUNET_YES); if ((hello_pipe_stdout == NULL) || (hello_pipe_stdin == NULL)) { + GNUNET_free (fn); return 1; } proc = - GNUNET_OS_start_process (GNUNET_YES, hello_pipe_stdin, hello_pipe_stdout, "cat", + GNUNET_OS_start_process (GNUNET_YES, GNUNET_OS_INHERIT_STD_ERR, hello_pipe_stdin, hello_pipe_stdout, fn, "gnunet-service-resolver", "-", NULL); if (0 != GNUNET_OS_process_kill (proc, SIGTERM)) { GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); } + GNUNET_free (fn); GNUNET_assert (GNUNET_OK == GNUNET_OS_process_wait (proc)); GNUNET_OS_process_destroy (proc); proc = NULL; @@ -238,16 +258,13 @@ main (int argc, char *argv[]) int ret; GNUNET_log_setup ("test-os-start-process", -#if VERBOSE - "DEBUG", -#else "WARNING", -#endif NULL); ret = 0; ret |= check_run (); ret |= check_kill (); ret |= check_instant_kill (); - return ret; } + +/* end of test_os_start_process.c */ diff --git a/src/util/test_peer.c b/src/util/test_peer.c index 2a48401..fa4d31b 100644 --- a/src/util/test_peer.c +++ b/src/util/test_peer.c @@ -29,8 +29,6 @@ #define NUMBER_OF_PEERS 10 -#define VERBOSE GNUNET_NO - /** * A list of Peer ID's to play with */ @@ -46,9 +44,8 @@ generatePeerIdList () { GNUNET_CRYPTO_hash_create_random (GNUNET_CRYPTO_QUALITY_WEAK, &pidArr[i].hashPubKey); -#if VERBOSE - printf ("Peer %d: %s\n", i, GNUNET_i2s (&pidArr[i])); -#endif + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Peer %d: %s\n", i, GNUNET_i2s (&pidArr[i])); } } @@ -124,7 +121,7 @@ check () int main () { - int i; + unsigned int i; GNUNET_log_setup ("test-peer", "ERROR", NULL); for (i = 0; i < 1; i++) diff --git a/src/util/test_plugin.c b/src/util/test_plugin.c index 428cdaf..f2abfa7 100644 --- a/src/util/test_plugin.c +++ b/src/util/test_plugin.c @@ -24,7 +24,6 @@ #include "platform.h" #include "gnunet_plugin_lib.h" -#define VERBOSE GNUNET_NO static void test_cb (void *cls, const char *libname, void *lib_ret) @@ -36,14 +35,16 @@ test_cb (void *cls, const char *libname, void *lib_ret) ret = GNUNET_PLUGIN_unload (libname, "out"); GNUNET_assert (NULL != ret); GNUNET_assert (0 == strcmp (ret, "World")); + GNUNET_free (ret); } -static int -check () +int +main (int argc, char *argv[]) { void *ret; + GNUNET_log_setup ("test-plugin", "WARNING", NULL); GNUNET_log_skip (1, GNUNET_NO); ret = GNUNET_PLUGIN_load ("libgnunet_plugin_missing", NULL); GNUNET_log_skip (0, GNUNET_NO); @@ -52,7 +53,7 @@ check () ret = GNUNET_PLUGIN_load ("libgnunet_plugin_test", "in"); if (ret == NULL) return 1; - if (0 != strcmp (ret, "Hello")) + if (0 != strcmp (ret, "Hello")) return 2; ret = GNUNET_PLUGIN_unload ("libgnunet_plugin_test", "out"); if (ret == NULL) @@ -60,20 +61,8 @@ check () if (0 != strcmp (ret, "World")) return 4; free (ret); - GNUNET_PLUGIN_load_all ("libgnunet_plugin_tes", "in", &test_cb, "test"); return 0; } -int -main (int argc, char *argv[]) -{ - int ret; - - GNUNET_log_setup ("test-plugin", "WARNING", NULL); - ret = check (); - - return ret; -} - /* end of test_plugin.c */ diff --git a/src/util/test_pseudonym.c b/src/util/test_pseudonym.c index 4ce8b38..9b5085b 100644 --- a/src/util/test_pseudonym.c +++ b/src/util/test_pseudonym.c @@ -35,16 +35,16 @@ static struct GNUNET_CONTAINER_MetaData *meta; -static GNUNET_HashCode id1; +static struct GNUNET_HashCode id1; static int -iter (void *cls, const GNUNET_HashCode * pseudonym, +iter (void *cls, const struct GNUNET_HashCode * pseudonym, const char *name, const char *unique_name, const struct GNUNET_CONTAINER_MetaData *md, int rating) { int *ok = cls; - if ((0 == memcmp (pseudonym, &id1, sizeof (GNUNET_HashCode))) && + if ((0 == memcmp (pseudonym, &id1, sizeof (struct GNUNET_HashCode))) && (!GNUNET_CONTAINER_meta_data_test_equal (md, meta))) { *ok = GNUNET_NO; @@ -54,7 +54,7 @@ iter (void *cls, const GNUNET_HashCode * pseudonym, } static int -noti_callback (void *cls, const GNUNET_HashCode * pseudonym, +noti_callback (void *cls, const struct GNUNET_HashCode * pseudonym, const char *name, const char *unique_name, const struct GNUNET_CONTAINER_MetaData *md, int rating) { @@ -65,7 +65,7 @@ noti_callback (void *cls, const GNUNET_HashCode * pseudonym, } static int -fake_noti_callback (void *cls, const GNUNET_HashCode * pseudonym, +fake_noti_callback (void *cls, const struct GNUNET_HashCode * pseudonym, const char *name, const char *unique_name, const struct GNUNET_CONTAINER_MetaData *md, int rating) { @@ -76,7 +76,7 @@ fake_noti_callback (void *cls, const GNUNET_HashCode * pseudonym, } static int -false_callback (void *cls, const GNUNET_HashCode * pseudonym, +false_callback (void *cls, const struct GNUNET_HashCode * pseudonym, const char *name, const char *unique_name, const struct GNUNET_CONTAINER_MetaData *md, int rating) { @@ -87,11 +87,11 @@ int main (int argc, char *argv[]) { int ok; - GNUNET_HashCode rid1; - GNUNET_HashCode id2; - GNUNET_HashCode rid2; - GNUNET_HashCode fid; - GNUNET_HashCode id3; + struct GNUNET_HashCode rid1; + struct GNUNET_HashCode id2; + struct GNUNET_HashCode rid2; + struct GNUNET_HashCode fid; + struct GNUNET_HashCode id3; int old; int newVal; @@ -174,13 +174,13 @@ main (int argc, char *argv[]) CHECK (GNUNET_SYSERR == GNUNET_PSEUDONYM_name_to_id (cfg, name1, &rid1)); CHECK (GNUNET_OK == GNUNET_PSEUDONYM_name_to_id (cfg, name2_unique, &rid2)); CHECK (GNUNET_OK == GNUNET_PSEUDONYM_name_to_id (cfg, name1_unique, &rid1)); - CHECK (0 == memcmp (&id1, &rid1, sizeof (GNUNET_HashCode))); - CHECK (0 == memcmp (&id2, &rid2, sizeof (GNUNET_HashCode))); + CHECK (0 == memcmp (&id1, &rid1, sizeof (struct GNUNET_HashCode))); + CHECK (0 == memcmp (&id2, &rid2, sizeof (struct GNUNET_HashCode))); GNUNET_CRYPTO_hash_create_random (GNUNET_CRYPTO_QUALITY_WEAK, &fid); GNUNET_log_skip (1, GNUNET_NO); CHECK (0 == GNUNET_PSEUDONYM_rank (cfg, &fid, 0)); - GNUNET_log_skip (0, GNUNET_YES); + GNUNET_log_skip (0, GNUNET_NO); CHECK (GNUNET_OK == GNUNET_PSEUDONYM_get_info (cfg, &fid, NULL, NULL, &noname, &noname_is_a_dup)); CHECK (noname != NULL); CHECK (noname_is_a_dup == GNUNET_YES); diff --git a/src/util/test_resolver_api.c b/src/util/test_resolver_api.c index 4a3a203..ea18629 100644 --- a/src/util/test_resolver_api.c +++ b/src/util/test_resolver_api.c @@ -22,15 +22,10 @@ * @brief testcase for resolver_api.c */ #include "platform.h" -#include "gnunet_common.h" -#include "gnunet_getopt_lib.h" -#include "gnunet_os_lib.h" -#include "gnunet_program_lib.h" -#include "gnunet_scheduler_lib.h" +#include "gnunet_util_lib.h" #include "gnunet_resolver_service.h" #include "resolver.h" -#define VERBOSE GNUNET_NO /** * Using DNS root servers to check gnunet's resolver service @@ -40,12 +35,13 @@ #define ROOTSERVER_NAME "a.root-servers.net" #define ROOTSERVER_IP "198.41.0.4" + static void check_hostname (void *cls, const struct sockaddr *sa, socklen_t salen) { int *ok = cls; - if (salen == 0) + if (0 == salen) { (*ok) &= ~8; return; @@ -82,7 +78,7 @@ check_localhost (void *cls, const char *hostname) { int *ok = cls; - if (hostname == NULL) + if (NULL == hostname) return; if (0 == strcmp (hostname, "localhost")) { @@ -98,13 +94,14 @@ check_localhost (void *cls, const char *hostname) } } + static void check_127 (void *cls, const struct sockaddr *sa, socklen_t salen) { int *ok = cls; const struct sockaddr_in *sai = (const struct sockaddr_in *) sa; - if (sa == NULL) + if (NULL == sa) return; GNUNET_assert (sizeof (struct sockaddr_in) == salen); if (sai->sin_addr.s_addr == htonl (INADDR_LOOPBACK)) @@ -122,6 +119,7 @@ check_127 (void *cls, const struct sockaddr *sa, socklen_t salen) } } + static void check_local_fqdn (void *cls, const char *gnunet_fqdn) { @@ -159,14 +157,13 @@ check_local_fqdn (void *cls, const char *gnunet_fqdn) } - static void check_rootserver_ip (void *cls, const struct sockaddr *sa, socklen_t salen) { int *ok = cls; const struct sockaddr_in *sai = (const struct sockaddr_in *) sa; - if (sa == NULL) + if (NULL == sa) return; GNUNET_assert (sizeof (struct sockaddr_in) == salen); @@ -184,12 +181,13 @@ check_rootserver_ip (void *cls, const struct sockaddr *sa, socklen_t salen) } } + static void check_rootserver_name (void *cls, const char *hostname) { int *ok = cls; - if (hostname == NULL) + if (NULL == hostname) return; if (0 == strcmp (hostname, ROOTSERVER_NAME)) @@ -206,6 +204,7 @@ check_rootserver_name (void *cls, const char *hostname) } } + static void run (void *cls, char *const *args, const char *cfgfile, const struct GNUNET_CONFIGURATION_Handle *cfg) @@ -347,36 +346,33 @@ run (void *cls, char *const *args, const char *cfgfile, } -static int -check () + +int +main (int argc, char *argv[]) { int ok = 1 + 2 + 4 + 8; char *fn; - char *pfx; struct GNUNET_OS_Process *proc; - - char *const argv[] = - { "test-resolver-api", "-c", "test_resolver_api_data.conf", -#if VERBOSE - "-L", "DEBUG", -#endif - NULL + char *const argvx[] = { + "test-resolver-api", "-c", "test_resolver_api_data.conf", NULL }; struct GNUNET_GETOPT_CommandLineOption options[] = { GNUNET_GETOPT_OPTION_END }; - pfx = GNUNET_OS_installation_get_path (GNUNET_OS_IPK_BINDIR); - GNUNET_asprintf (&fn, "%s%cgnunet-service-resolver", pfx, DIR_SEPARATOR); - GNUNET_free (pfx); - proc = GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, fn, "gnunet-service-resolver", -#if VERBOSE - "-L", "DEBUG", -#endif + + GNUNET_log_setup ("test-resolver-api", + "WARNING", + NULL); + fn = GNUNET_OS_get_libexec_binary_path ("gnunet-service-resolver"); + proc = GNUNET_OS_start_process (GNUNET_YES, + GNUNET_OS_INHERIT_STD_OUT_AND_ERR, + NULL, NULL, fn, + "gnunet-service-resolver", "-c", "test_resolver_api_data.conf", NULL); GNUNET_assert (NULL != proc); GNUNET_free (fn); GNUNET_assert (GNUNET_OK == - GNUNET_PROGRAM_run ((sizeof (argv) / sizeof (char *)) - 1, - argv, "test-resolver-api", "nohelp", + GNUNET_PROGRAM_run ((sizeof (argvx) / sizeof (char *)) - 1, + argvx, "test-resolver-api", "nohelp", options, &run, &ok)); if (0 != GNUNET_OS_process_kill (proc, SIGTERM)) { @@ -386,26 +382,10 @@ check () GNUNET_OS_process_wait (proc); GNUNET_OS_process_destroy (proc); proc = NULL; - if (ok != 0) + if (0 != ok) FPRINTF (stderr, "Missed some resolutions: %u\n", ok); return ok; } -int -main (int argc, char *argv[]) -{ - int ret; - - GNUNET_log_setup ("test-resolver-api", -#if VERBOSE - "DEBUG", -#else - "WARNING", -#endif - NULL); - ret = check (); - - return ret; -} /* end of test_resolver_api.c */ diff --git a/src/util/test_resolver_api_data.conf b/src/util/test_resolver_api_data.conf index 745cb7b..3e264eb 100644 --- a/src/util/test_resolver_api_data.conf +++ b/src/util/test_resolver_api_data.conf @@ -4,5 +4,4 @@ SERVICEHOME = /tmp/test-gnunetd-statistics/ [resolver] PORT = 22354 HOSTNAME = localhost -DEBUG = YES diff --git a/src/util/test_scheduler.c b/src/util/test_scheduler.c index 9832ade..2a9ed2d 100644 --- a/src/util/test_scheduler.c +++ b/src/util/test_scheduler.c @@ -27,7 +27,11 @@ #include "gnunet_time_lib.h" #include "gnunet_disk_lib.h" -#define VERBOSE GNUNET_NO + +struct GNUNET_DISK_PipeHandle *p; + +static const struct GNUNET_DISK_FileHandle *fds[2]; + static void task2 (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) @@ -51,9 +55,6 @@ task3 (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) (*ok) = 4; } -struct GNUNET_DISK_PipeHandle *p; -static const struct GNUNET_DISK_FileHandle *fds[2]; - static void taskWrt (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) @@ -74,6 +75,7 @@ taskNeverRun (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) GNUNET_assert (0); } + static void taskLast (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { @@ -84,6 +86,7 @@ taskLast (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) (*ok) = 0; } + static void taskRd (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { @@ -132,7 +135,6 @@ task1 (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) } - /** * Main method, starts scheduler with task1, * checks that "ok" is correct at the end. @@ -229,7 +231,6 @@ checkCancel () } - int main (int argc, char *argv[]) { diff --git a/src/util/test_scheduler_delay.c b/src/util/test_scheduler_delay.c index 8ba35f5..1320669 100644 --- a/src/util/test_scheduler_delay.c +++ b/src/util/test_scheduler_delay.c @@ -28,8 +28,6 @@ #include "gnunet_scheduler_lib.h" #include "gnunet_time_lib.h" -#define VERBOSE GNUNET_NO - static struct GNUNET_TIME_Absolute target; static int i; @@ -71,9 +69,11 @@ test_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) i += INCR; } -static int -check () + +int +main (int argc, char *argv[]) { + GNUNET_log_setup ("test-scheduler-delay", "WARNING", NULL); target = GNUNET_TIME_absolute_get (); GNUNET_SCHEDULER_run (&test_task, NULL); FPRINTF (stdout, "Sleep precision: %llu ms. ", @@ -89,15 +89,4 @@ check () return 0; } -int -main (int argc, char *argv[]) -{ - int ret; - - GNUNET_log_setup ("test-scheduler-delay", "WARNING", NULL); - ret = check (); - - return ret; -} - /* end of test_scheduler_delay.c */ diff --git a/src/util/test_server.c b/src/util/test_server.c index 0faf61b..19f9932 100644 --- a/src/util/test_server.c +++ b/src/util/test_server.c @@ -28,8 +28,6 @@ #include "gnunet_server_lib.h" #include "gnunet_time_lib.h" -#define VERBOSE GNUNET_NO - #define PORT 12435 #define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 2) diff --git a/src/util/test_server_disconnect.c b/src/util/test_server_disconnect.c index c54f9cb..b54df48 100644 --- a/src/util/test_server_disconnect.c +++ b/src/util/test_server_disconnect.c @@ -28,7 +28,6 @@ #include "gnunet_server_lib.h" #include "gnunet_time_lib.h" -#define VERBOSE GNUNET_NO #define PORT 12435 diff --git a/src/util/test_server_mst_interrupt.c b/src/util/test_server_mst_interrupt.c index fd34bd0..8fd7a2b 100644 --- a/src/util/test_server_mst_interrupt.c +++ b/src/util/test_server_mst_interrupt.c @@ -30,7 +30,7 @@ #include "gnunet_time_lib.h" static struct GNUNET_SERVER_MessageStreamTokenizer * mst; -static int ret; + /* Callback destroying mst with data in buffer */ static int @@ -42,40 +42,23 @@ mst_cb (void *cls, void *client, return GNUNET_SYSERR; } -/** - * Main method - */ -static int -check () -{ +int +main (int argc, char *argv[]) +{ struct GNUNET_PeerIdentity id; struct GNUNET_MessageHeader msg[2]; - /* Prepare */ - memset (&id, sizeof (id), '\0'); + GNUNET_log_setup ("test_server_mst_interrupt", "WARNING", NULL); + memset (&id, 0, sizeof (id)); msg[0].size = htons (sizeof (msg)); msg[0].type = htons (sizeof (GNUNET_MESSAGE_TYPE_DUMMY)); - mst = GNUNET_SERVER_mst_create(mst_cb, NULL); - - GNUNET_SERVER_mst_receive(mst, &id, (const char *) &msg, 2 * sizeof (msg), GNUNET_NO, GNUNET_NO); - + GNUNET_SERVER_mst_receive (mst, &id, + (const char *) &msg, 2 * sizeof (msg), + GNUNET_NO, GNUNET_NO); /* If we reach this line, it did not crash */ - ret = 0; - - return ret; -} - -int -main (int argc, char *argv[]) -{ - ret = 1; - - GNUNET_log_setup ("test_server", "WARNING", NULL); - check (); - - return ret; + return 0; } /* end of test_server_mst_interrupt.c */ diff --git a/src/util/test_server_with_client.c b/src/util/test_server_with_client.c index ad56071..c494563 100644 --- a/src/util/test_server_with_client.c +++ b/src/util/test_server_with_client.c @@ -30,8 +30,6 @@ #include "gnunet_server_lib.h" #include "gnunet_time_lib.h" -#define VERBOSE GNUNET_NO - #define PORT 22335 #define MY_TYPE 128 @@ -190,35 +188,15 @@ task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) } -/** - * Main method, starts scheduler with task1, - * checks that "ok" is correct at the end. - */ -static int -check () -{ - - ok = 1; - GNUNET_SCHEDULER_run (&task, NULL); - return ok; -} - - int main (int argc, char *argv[]) { - int ret = 0; - GNUNET_log_setup ("test_server_with_client", -#if VERBOSE - "DEBUG", -#else "WARNING", -#endif NULL); - ret += check (); - - return ret; + ok = 1; + GNUNET_SCHEDULER_run (&task, NULL); + return ok; } /* end of test_server_with_client.c */ diff --git a/src/util/test_server_with_client_unix.c b/src/util/test_server_with_client_unix.c index eae80e4..57a67d3 100644 --- a/src/util/test_server_with_client_unix.c +++ b/src/util/test_server_with_client_unix.c @@ -30,8 +30,6 @@ #include "gnunet_server_lib.h" #include "gnunet_time_lib.h" -#define VERBOSE GNUNET_NO - #define MY_TYPE 128 @@ -43,6 +41,7 @@ static struct GNUNET_CONFIGURATION_Handle *cfg; static int ok; + static void send_done (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { @@ -150,7 +149,6 @@ task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) un.sun_path[0] = '\0'; #endif - sap[0] = (struct sockaddr *) &un; slens[0] = sizeof (un); sap[1] = NULL; @@ -178,35 +176,15 @@ task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) } -/** - * Main method, starts scheduler with task1, - * checks that "ok" is correct at the end. - */ -static int -check () -{ - - ok = 1; - GNUNET_SCHEDULER_run (&task, NULL); - return ok; -} - - int main (int argc, char *argv[]) { - int ret = 0; - GNUNET_log_setup ("test_server_with_client_unix", -#if VERBOSE - "DEBUG", -#else "WARNING", -#endif NULL); - ret += check (); - - return ret; + ok = 1; + GNUNET_SCHEDULER_run (&task, NULL); + return ok; } /* end of test_server_with_client_unix.c */ diff --git a/src/util/test_service.c b/src/util/test_service.c index 5547249..be49d18 100644 --- a/src/util/test_service.c +++ b/src/util/test_service.c @@ -31,8 +31,6 @@ #include "gnunet_time_lib.h" -#define VERBOSE GNUNET_NO - #define PORT 12435 #define MY_TYPE 256 @@ -148,17 +146,11 @@ check () "test_service", "-c", "test_service_data.conf", - "-L", -#if VERBOSE - "DEBUG", -#else - "WARNING", -#endif NULL }; GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Starting service\n"); GNUNET_assert (GNUNET_OK == - GNUNET_SERVICE_run (5, argv, "test_service", + GNUNET_SERVICE_run (3, argv, "test_service", GNUNET_SERVICE_OPTION_NONE, &runner, &ok)); GNUNET_assert (0 == ok); return ok; @@ -201,17 +193,11 @@ check6 () "test_service6", "-c", "test_service_data.conf", - "-L", -#if VERBOSE - "DEBUG", -#else - "WARNING", -#endif NULL }; GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Starting v6 service\n"); GNUNET_assert (GNUNET_OK == - GNUNET_SERVICE_run (5, argv, "test_service6", + GNUNET_SERVICE_run (3, argv, "test_service6", GNUNET_SERVICE_OPTION_NONE, &runner6, &ok)); GNUNET_assert (0 == ok); @@ -241,12 +227,6 @@ check_start_stop () "test-service-program", "-c", "test_service_data.conf", - "-L", -#if VERBOSE - "DEBUG", -#else - "WARNING", -#endif NULL }; const struct GNUNET_GETOPT_CommandLineOption options[] = { @@ -255,9 +235,9 @@ check_start_stop () int ret = 1; GNUNET_assert (GNUNET_OK == - GNUNET_PROGRAM_run (5, argv, "test-service-program", "no help", + GNUNET_PROGRAM_run (3, argv, "test-service-program", "no help", options, &start_stop_main, &ret)); - + GNUNET_break (0 == ret); return ret; } @@ -270,11 +250,7 @@ main (int argc, char *argv[]) struct GNUNET_NETWORK_Handle *s = NULL; GNUNET_log_setup ("test-service", -#if VERBOSE - "DEBUG", -#else "WARNING", -#endif NULL); ret += check (); ret += check (); diff --git a/src/util/test_strings.c b/src/util/test_strings.c index b662623..bc41694 100644 --- a/src/util/test_strings.c +++ b/src/util/test_strings.c @@ -25,20 +25,23 @@ #include "gnunet_common.h" #include "gnunet_strings_lib.h" -#define VERBOSE GNUNET_NO #define WANT(a,b) if (0 != strcmp(a,b)) { fprintf(stderr, "Got `%s', wanted `%s'\n", b, a); GNUNET_free(b); GNUNET_break(0); return 1;} else { GNUNET_free (b); } +#define WANTNF(a,b) do { if (0 != strcmp(a,b)) { fprintf(stderr, "Got `%s', wanted `%s'\n", b, a); GNUNET_break(0); return 1;} } while (0) #define WANTB(a,b,l) if (0 != memcmp(a,b,l)) { GNUNET_break(0); return 1;} else { } -static int -check () +int +main (int argc, char *argv[]) { char buf[128]; char *r; char *b; + const char *bc; struct GNUNET_TIME_Absolute at; + struct GNUNET_TIME_Absolute atx; const char *hdir; + GNUNET_log_setup ("test_strings", "ERROR", NULL); sprintf (buf, "4 %s", _( /* size unit */ "b")); b = GNUNET_STRINGS_byte_size_fancy (4); WANT (buf, b); @@ -49,20 +52,20 @@ check () b = GNUNET_STRINGS_byte_size_fancy (10240LL * 1024LL * 1024LL * 1024LL); WANT (buf, b); sprintf (buf, "4 %s", _( /* time unit */ "ms")); - b = GNUNET_STRINGS_relative_time_to_string (GNUNET_TIME_relative_multiply - (GNUNET_TIME_UNIT_MILLISECONDS, - 4)); - WANT (buf, b); + bc = GNUNET_STRINGS_relative_time_to_string (GNUNET_TIME_relative_multiply + (GNUNET_TIME_UNIT_MILLISECONDS, + 4), GNUNET_YES); + WANTNF (buf, bc); sprintf (buf, "7 %s", _( /* time unit */ "s")); - b = GNUNET_STRINGS_relative_time_to_string (GNUNET_TIME_relative_multiply - (GNUNET_TIME_UNIT_MILLISECONDS, - 7 * 1000)); - WANT (buf, b); + bc = GNUNET_STRINGS_relative_time_to_string (GNUNET_TIME_relative_multiply + (GNUNET_TIME_UNIT_MILLISECONDS, + 7 * 1000), GNUNET_YES); + WANTNF (buf, bc); sprintf (buf, "7 %s", _( /* time unit */ "h")); - b = GNUNET_STRINGS_relative_time_to_string (GNUNET_TIME_relative_multiply + bc = GNUNET_STRINGS_relative_time_to_string (GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MILLISECONDS, - 7 * 60 * 60 * 1000)); - WANT (buf, b); + 7 * 60 * 60 * 1000), GNUNET_YES); + WANTNF (buf, bc); #ifndef MINGW hdir = getenv ("HOME"); #else @@ -83,37 +86,31 @@ check () if (0 != GNUNET_STRINGS_buffer_tokenize (buf, 2, 2, &r, &b)) return 1; at.abs_value = 5000; - r = GNUNET_STRINGS_absolute_time_to_string (at); - /* r should be something like "Wed Dec 31 17:00:05 1969" + bc = GNUNET_STRINGS_absolute_time_to_string (at); + /* bc should be something like "Wed Dec 31 17:00:05 1969" * where the details of the day and hour depend on the timezone; * however, the "0:05 19" should always be there; hence: */ - if (NULL == strstr (r, "0:05 19")) + if (NULL == strstr (bc, "0:05 19")) { - FPRINTF (stderr, "Got %s\n", r); + FPRINTF (stderr, "Got %s\n", bc); GNUNET_break (0); - GNUNET_free (r); return 1; } - GNUNET_free (r); b = GNUNET_STRINGS_to_utf8 ("TEST", 4, "ASCII"); WANT ("TEST", b); -#if ENABLE_NLS && HAVE_ICONV + + at = GNUNET_TIME_UNIT_FOREVER_ABS; + bc = GNUNET_STRINGS_absolute_time_to_string (at); + GNUNET_assert (GNUNET_OK == + GNUNET_STRINGS_fancy_time_to_absolute (bc, &atx)); + GNUNET_assert (atx.abs_value == at.abs_value); + GNUNET_log_skip (2, GNUNET_NO); b = GNUNET_STRINGS_to_utf8 ("TEST", 4, "unknown"); GNUNET_log_skip (0, GNUNET_YES); WANT ("TEST", b); -#endif return 0; } -int -main (int argc, char *argv[]) -{ - int ret; - - GNUNET_log_setup ("test_strings", "ERROR", NULL); - ret = check (); - return ret; -} /* end of test_strings.c */ diff --git a/src/util/test_time.c b/src/util/test_time.c index b4c7233..cd11754 100644 --- a/src/util/test_time.c +++ b/src/util/test_time.c @@ -25,10 +25,9 @@ #include "gnunet_common.h" #include "gnunet_time_lib.h" -#define VERBOSE GNUNET_NO -static int -check () +int +main (int argc, char *argv[]) { struct GNUNET_TIME_Absolute now; struct GNUNET_TIME_AbsoluteNBO nown; @@ -43,6 +42,7 @@ check () struct GNUNET_TIME_RelativeNBO reln; unsigned int i; + GNUNET_log_setup ("test-time", "WARNING", NULL); forever = GNUNET_TIME_UNIT_FOREVER_ABS; relForever = GNUNET_TIME_UNIT_FOREVER_REL; relUnit = GNUNET_TIME_UNIT_MILLISECONDS; @@ -230,15 +230,5 @@ check () return 0; } -int -main (int argc, char *argv[]) -{ - int ret; - - GNUNET_log_setup ("test-time", "WARNING", NULL); - ret = check (); - - return ret; -} /* end of test_time.c */ diff --git a/src/util/time.c b/src/util/time.c index 7467b44..afb0c00 100644 --- a/src/util/time.c +++ b/src/util/time.c @@ -484,6 +484,7 @@ GNUNET_TIME_relative_hton (struct GNUNET_TIME_Relative a) return ret; } + /** * Convert relative time from network byte order. * @@ -500,6 +501,7 @@ GNUNET_TIME_relative_ntoh (struct GNUNET_TIME_RelativeNBO a) } + /** * Convert absolute time to network byte order. * @@ -515,6 +517,7 @@ GNUNET_TIME_absolute_hton (struct GNUNET_TIME_Absolute a) return ret; } + /** * Convert absolute time from network byte order. * @@ -531,26 +534,5 @@ GNUNET_TIME_absolute_ntoh (struct GNUNET_TIME_AbsoluteNBO a) } -/** - * Convert a relative time to a string. - * This is one of the very few calls in the entire API that is - * NOT reentrant! - * - * @param time the time to print - * - * @return string form of the time (as milliseconds) - */ -const char * -GNUNET_TIME_relative_to_string (struct GNUNET_TIME_Relative time) -{ - static char time_string[21]; - - memset (time_string, 0, sizeof (time_string)); - - sprintf (time_string, "%llu", (unsigned long long) time.rel_value); - return (const char *) time_string; -} - - /* end of time.c */ diff --git a/src/util/util.conf b/src/util/util.conf index f3d301e..ea8ddc0 100644 --- a/src/util/util.conf +++ b/src/util/util.conf @@ -9,6 +9,9 @@ SERVICEHOME = ~/.gnunet/ [gnunetd] HOSTKEY = $SERVICEHOME/.hostkey +[PEER] +PRIVATE_KEY = $SERVICEHOME/private.ecc + [client] HOME = $SERVICEHOME diff --git a/src/util/w32cat.c b/src/util/w32cat.c new file mode 100644 index 0000000..292bd6d --- /dev/null +++ b/src/util/w32cat.c @@ -0,0 +1,108 @@ +/* + W32 version of 'cat' program + (C) 2012 LRN + + cat is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + cat is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with cat; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +#include +#include + +int +main (int argc, char **argv) +{ + HANDLE stdi, stdo; + BOOL b; + wchar_t *commandlinew, **argvw; + int argcw; + int i; + + stdo = GetStdHandle (STD_OUTPUT_HANDLE); + if (stdo == INVALID_HANDLE_VALUE || stdo == NULL) + return 1; + + commandlinew = GetCommandLineW (); + argvw = CommandLineToArgvW (commandlinew, &argcw); + if (argvw == NULL) + return 1; + + for (i = 1; i < argcw || argcw == 1; i++) + { + DWORD r, w; + int is_dash = wcscmp (argvw[i], L"-") == 0; + if (argcw == 1 || is_dash) + { + stdi = GetStdHandle (STD_INPUT_HANDLE); + if (stdi == INVALID_HANDLE_VALUE) + { + fprintf (stderr, "cat: Failed to obtain stdin handle.\n"); + return 4; + } + if (stdi == NULL) + { + fprintf (stderr, "cat: Have no stdin.\n"); + return 5; + } + } + else + { + stdi = CreateFileW (argvw[i], GENERIC_READ, FILE_SHARE_DELETE | FILE_SHARE_READ | FILE_SHARE_WRITE, NULL, OPEN_EXISTING, FILE_FLAG_SEQUENTIAL_SCAN, NULL); + if (stdi == INVALID_HANDLE_VALUE) + { + wchar_t *msgbuf; + DWORD le = GetLastError (); + if (0 < FormatMessageW (FORMAT_MESSAGE_ALLOCATE_BUFFER | FORMAT_MESSAGE_FROM_SYSTEM, 0, le, 0, (wchar_t *) &msgbuf, 0, NULL)) + { + fprintf (stderr, "cat: Failed to open file `%S'. Error %lu.\n", argvw[i], le); + return 3; + } + fprintf (stderr, "cat: Failed to open file `%S'. Error %lu: %S\n", argvw[i], le, msgbuf); + if (msgbuf != NULL) + LocalFree (msgbuf); + return 2; + } + } + do + { + unsigned char c; + b = ReadFile (stdi, &c, 1, &r, NULL); + if (b && r > 0) + { + b = WriteFile (stdo, &c, 1, &w, NULL); + if (b == 0) + { + wchar_t *msgbuf; + DWORD le = GetLastError (); + if (0 < FormatMessageW (FORMAT_MESSAGE_ALLOCATE_BUFFER | FORMAT_MESSAGE_FROM_SYSTEM, 0, le, 0, (wchar_t *) &msgbuf, 0, NULL)) + { + fprintf (stderr, "cat: Failed to write into stdout. Error %lu.\n", le); + return 3; + } + fprintf (stderr, "cat: Failed to write into stdout. Error %lu: %S\n", le, msgbuf); + if (msgbuf != NULL) + LocalFree (msgbuf); + return 6; + } + } + } while (b && r > 0); + if (argcw == 1) + break; + if (!is_dash) + CloseHandle (stdi); + } + LocalFree (argvw); + return 0; +} diff --git a/src/util/win.c b/src/util/win.c new file mode 100644 index 0000000..99b8b69 --- /dev/null +++ b/src/util/win.c @@ -0,0 +1,1329 @@ +/* + This file is part of GNUnet. + (C) 2001, 2002, 2003, 2004, 2005, 2006 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 2, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +/** + * @file util/win.c + * @brief Helper functions for MS Windows in C++ + * @author Nils Durner + */ + +#ifndef _WIN_C +#define _WIN_C + +#include "winproc.h" +#include "platform.h" +#include "gnunet_common.h" +#include "gnunet_connection_lib.h" + +#include + +#ifndef INHERITED_ACE +#define INHERITED_ACE 0x10 +#endif + +int plibc_conv_to_win_path(const char *pszUnix, char *pszWindows); + +#define _IP_ADAPTER_UNICAST_ADDRESS_HEAD \ + union { \ + struct { \ + ULONG Length; \ + DWORD Flags; \ + }; \ + }; + +#define _IP_ADAPTER_UNICAST_ADDRESS_BASE \ + SOCKET_ADDRESS Address; \ + IP_PREFIX_ORIGIN PrefixOrigin; \ + IP_SUFFIX_ORIGIN SuffixOrigin; \ + IP_DAD_STATE DadState; \ + ULONG ValidLifetime; \ + ULONG PreferredLifetime; \ + ULONG LeaseLifetime; + +#define _IP_ADAPTER_UNICAST_ADDRESS_ADD_VISTA \ + UINT8 OnLinkPrefixLength; + + +#define _IP_ADAPTER_UNICAST_ADDRESS_DEFINE(suffix,addition) \ +typedef struct _IP_ADAPTER_UNICAST_ADDRESS##suffix { \ + _IP_ADAPTER_UNICAST_ADDRESS_HEAD \ + struct _IP_ADAPTER_UNICAST_ADDRESS##suffix *Next; \ + _IP_ADAPTER_UNICAST_ADDRESS_BASE \ + addition \ +} IP_ADAPTER_UNICAST_ADDRESS##suffix, *PIP_ADAPTER_UNICAST_ADDRESS##suffix; + +/* _IP_ADAPTER_UNICAST_ADDRESS_DEFINE(,) defined in w32api headers */ +_IP_ADAPTER_UNICAST_ADDRESS_DEFINE(_VISTA,_IP_ADAPTER_UNICAST_ADDRESS_ADD_VISTA) + + +typedef struct _IP_ADAPTER_WINS_SERVER_ADDRESS { + union { + ULONGLONG Alignment; + struct { + ULONG Length; + DWORD Reserved; + }; + }; + struct _IP_ADAPTER_WINS_SERVER_ADDRESS *Next; + SOCKET_ADDRESS Address; +} IP_ADAPTER_WINS_SERVER_ADDRESS, *PIP_ADAPTER_WINS_SERVER_ADDRESS, *PIP_ADAPTER_WINS_SERVER_ADDRESS_LH; + +typedef struct _IP_ADAPTER_GATEWAY_ADDRESS { + union { + ULONGLONG Alignment; + struct { + ULONG Length; + DWORD Reserved; + }; + }; + struct _IP_ADAPTER_GATEWAY_ADDRESS *Next; + SOCKET_ADDRESS Address; +} IP_ADAPTER_GATEWAY_ADDRESS, *PIP_ADAPTER_GATEWAY_ADDRESS, *PIP_ADAPTER_GATEWAY_ADDRESS_LH; + +typedef UINT32 NET_IF_COMPARTMENT_ID; +typedef GUID NET_IF_NETWORK_GUID; + +typedef enum _NET_IF_CONNECTION_TYPE { + NET_IF_CONNECTION_DEDICATED = 1, + NET_IF_CONNECTION_PASSIVE, + NET_IF_CONNECTION_DEMAND, + NET_IF_CONNECTION_MAXIMUM +} NET_IF_CONNECTION_TYPE, *PNET_IF_CONNECTION_TYPE; + +typedef enum { + TUNNEL_TYPE_NONE = 0, + TUNNEL_TYPE_OTHER, + TUNNEL_TYPE_DIRECT, + TUNNEL_TYPE_6TO4, + TUNNEL_TYPE_ISATAP, + TUNNEL_TYPE_TEREDO, + TUNNEL_TYPE_IPHTTPS +} TUNNEL_TYPE, *PTUNNEL_TYPE; + +/* +A DUID consists of a two-octet type code represented in network byte + order, followed by a variable number of octets that make up the + actual identifier. A DUID can be no more than 128 octets long (not + including the type code). +*/ +#define MAX_DHCPV6_DUID_LENGTH 130 + +typedef union _NET_LUID { + ULONG64 Value; + struct { + ULONG64 Reserved :24; + ULONG64 NetLuidIndex :24; + ULONG64 IfType :16; + } Info; +} NET_LUID, *PNET_LUID, IF_LUID; + +#define MAX_DNS_SUFFIX_STRING_LENGTH 246 + +typedef struct _IP_ADAPTER_DNS_SUFFIX { + struct _IP_ADAPTER_DNS_SUFFIX *Next; + WCHAR String[MAX_DNS_SUFFIX_STRING_LENGTH]; +} IP_ADAPTER_DNS_SUFFIX, *PIP_ADAPTER_DNS_SUFFIX; + + + +#define _IP_ADAPTER_ADDRESSES_HEAD \ + union { \ + ULONGLONG Alignment; \ + struct { \ + ULONG Length; \ + DWORD IfIndex; \ + }; \ + }; + +#define _IP_ADAPTER_ADDRESSES_BASE \ + PCHAR AdapterName; \ + PIP_ADAPTER_UNICAST_ADDRESS FirstUnicastAddress; \ + PIP_ADAPTER_ANYCAST_ADDRESS FirstAnycastAddress; \ + PIP_ADAPTER_MULTICAST_ADDRESS FirstMulticastAddress; \ + PIP_ADAPTER_DNS_SERVER_ADDRESS FirstDnsServerAddress; \ + PWCHAR DnsSuffix; \ + PWCHAR Description; \ + PWCHAR FriendlyName; \ + BYTE PhysicalAddress[MAX_ADAPTER_ADDRESS_LENGTH]; \ + DWORD PhysicalAddressLength; \ + DWORD Flags; \ + DWORD Mtu; \ + DWORD IfType; \ + IF_OPER_STATUS OperStatus; + +#define _IP_ADAPTER_ADDRESSES_ADD_XPSP1 \ + DWORD Ipv6IfIndex; \ + DWORD ZoneIndices[16]; \ + PIP_ADAPTER_PREFIX FirstPrefix; \ + + +#define _IP_ADAPTER_ADDRESSES_ADD_VISTA \ + _IP_ADAPTER_ADDRESSES_ADD_XPSP1 \ + ULONG64 TransmitLinkSpeed; \ + ULONG64 ReceiveLinkSpeed; \ + PIP_ADAPTER_WINS_SERVER_ADDRESS_LH FirstWinsServerAddress; \ + PIP_ADAPTER_GATEWAY_ADDRESS_LH FirstGatewayAddress; \ + ULONG Ipv4Metric; \ + ULONG Ipv6Metric; \ + IF_LUID Luid; \ + SOCKET_ADDRESS Dhcpv4Server; \ + NET_IF_COMPARTMENT_ID CompartmentId; \ + NET_IF_NETWORK_GUID NetworkGuid; \ + NET_IF_CONNECTION_TYPE ConnectionType; \ + TUNNEL_TYPE TunnelType; \ + SOCKET_ADDRESS Dhcpv6Server; \ + BYTE Dhcpv6ClientDuid[MAX_DHCPV6_DUID_LENGTH]; \ + ULONG Dhcpv6ClientDuidLength; \ + ULONG Dhcpv6Iaid; + +#define _IP_ADAPTER_ADDRESSES_ADD_2008_OR_VISTASP1 \ + _IP_ADAPTER_ADDRESSES_ADD_VISTA \ + PIP_ADAPTER_DNS_SUFFIX FirstDnsSuffix; + +#define _IP_ADAPTER_ADDRESSES_DEFINE(suffix,addition) \ +typedef struct _IP_ADAPTER_ADDRESSES##suffix { \ + _IP_ADAPTER_ADDRESSES_HEAD \ + struct _IP_ADAPTER_ADDRESSES##suffix *Next; \ + _IP_ADAPTER_ADDRESSES_BASE \ + addition \ +} IP_ADAPTER_ADDRESSES##suffix, *PIP_ADAPTER_ADDRESSES##suffix; + + +/* _IP_ADAPTER_ADDRESSES_DEFINE(,) defined in w32api headers */ +_IP_ADAPTER_ADDRESSES_DEFINE(_XPSP1,_IP_ADAPTER_ADDRESSES_ADD_XPSP1) +_IP_ADAPTER_ADDRESSES_DEFINE(_VISTA,_IP_ADAPTER_ADDRESSES_ADD_VISTA) +_IP_ADAPTER_ADDRESSES_DEFINE(_2008_OR_VISTASP1,_IP_ADAPTER_ADDRESSES_ADD_2008_OR_VISTASP1) + +static int +EnumNICs_IPv6_get_ifs_count (SOCKET s) +{ + DWORD dwret = 0, err; + int iret; + iret = WSAIoctl (s, SIO_ADDRESS_LIST_QUERY, NULL, 0, NULL, 0, + &dwret, NULL, NULL); + err = GetLastError (); + if (iret == SOCKET_ERROR && err == WSAEFAULT) + return dwret; + else if (iret == 0) + return 0; + return GNUNET_SYSERR; +} + +static int +EnumNICs_IPv6_get_ifs (SOCKET s, SOCKET_ADDRESS_LIST *inf, int size) +{ + int iret; + DWORD dwret = 0; + iret = WSAIoctl (s, SIO_ADDRESS_LIST_QUERY, NULL, 0, inf, size, + &dwret, NULL, NULL); + + if (iret != 0 || dwret != size) + { + /* It's supposed to succeed! And size should be the same */ + return GNUNET_SYSERR; + } + return GNUNET_OK; +} + +#undef GNUNET_malloc +#define GNUNET_malloc(a) HeapAlloc(GetProcessHeap (), HEAP_ZERO_MEMORY | \ + HEAP_GENERATE_EXCEPTIONS, a) + +#undef GNUNET_free +#define GNUNET_free(a) HeapFree(GetProcessHeap (), 0, a) + +#undef GNUNET_free_non_null +#define GNUNET_free_non_null(a) do { if ((a) != NULL) GNUNET_free(a); } while (0) + +static int +EnumNICs_IPv4_get_ifs (SOCKET s, INTERFACE_INFO **inf, int *size) +{ + int iret; + DWORD dwret = 0; + DWORD error; + INTERFACE_INFO *ii = NULL; + DWORD ii_size = sizeof (INTERFACE_INFO) * 15; + while (TRUE) + { + if (ii_size >= sizeof (INTERFACE_INFO) * 1000) + return GNUNET_SYSERR; + ii = (INTERFACE_INFO *) GNUNET_malloc (ii_size); + dwret = 0; + iret = WSAIoctl (s, SIO_GET_INTERFACE_LIST, NULL, 0, ii, ii_size, + &dwret, NULL, NULL); + error = GetLastError (); + if (iret == SOCKET_ERROR) + { + if (error == WSAEFAULT) + { + GNUNET_free (ii); + ii_size *= 2; + continue; + } + GNUNET_free (ii); + return GNUNET_SYSERR; + } + else + { + *inf = ii; + *size = dwret; + return GNUNET_OK; + } + } + return GNUNET_SYSERR; +} + +int +EnumNICs2 (INTERFACE_INFO **ifs4, int *ifs4_len, SOCKET_ADDRESS_LIST **ifs6) +{ + int result = 0; + SOCKET s4 = INVALID_SOCKET, s6 = INVALID_SOCKET; + DWORD dwret1 = 0, dwret2; + DWORD err1, err2; + int ifs4len = 0, ifs6len = 0; + INTERFACE_INFO *interfaces4 = NULL; + SOCKET_ADDRESS_LIST *interfaces6 = NULL; + SetLastError (0); + s4 = socket (AF_INET, SOCK_STREAM, IPPROTO_TCP); + err1 = GetLastError (); + SetLastError (0); + s6 = socket (AF_INET6, SOCK_STREAM, IPPROTO_TCP); + err2 = GetLastError (); + if (s6 != INVALID_SOCKET) + { + ifs6len = EnumNICs_IPv6_get_ifs_count (s6); + if (ifs6len > 0) + { + interfaces6 = (SOCKET_ADDRESS_LIST *) GNUNET_malloc (ifs6len); + result = EnumNICs_IPv6_get_ifs (s6, interfaces6, ifs6len) || result; + } + closesocket (s6); + s6 = INVALID_SOCKET; + } + + if (s4 != INVALID_SOCKET) + { + result = EnumNICs_IPv4_get_ifs (s4, &interfaces4, &ifs4len) || result; + closesocket (s4); + s4 = INVALID_SOCKET; + } + if (ifs6len + ifs4len == 0) + goto error; + + if (!result) + { + *ifs4 = interfaces4; + *ifs4_len = ifs4len; + *ifs6 = interfaces6; + return GNUNET_OK; + } +error: + if (interfaces4 != NULL) + GNUNET_free (interfaces4); + if (interfaces6 != NULL) + GNUNET_free (interfaces6); + if (s4 != INVALID_SOCKET) + closesocket (s4); + if (s6 != INVALID_SOCKET) + closesocket (s6); + return GNUNET_SYSERR; +} + +/** + * Returns GNUNET_OK on OK, GNUNET_SYSERR on error + */ +int +EnumNICs3 (struct EnumNICs3_results **results, int *results_count) +{ + DWORD dwRetVal = 0; + int count = 0; + ULONG flags = /*GAA_FLAG_INCLUDE_PREFIX |*/ GAA_FLAG_SKIP_ANYCAST | + GAA_FLAG_SKIP_MULTICAST | GAA_FLAG_SKIP_DNS_SERVER; + struct sockaddr_in6 examplecom6; + IPAddr examplecom; + DWORD best_interface = 0; + DWORD best_interface6 = 0; + + int use_enum2 = 0; + INTERFACE_INFO *interfaces4 = NULL; + int interfaces4_len = 0; + SOCKET_ADDRESS_LIST *interfaces6 = NULL; + + unsigned long outBufLen = sizeof (IP_ADAPTER_ADDRESSES); + IP_ADAPTER_ADDRESSES *pCurrentAddress = NULL; + IP_ADAPTER_ADDRESSES *pAddresses = (IP_ADAPTER_ADDRESSES *) GNUNET_malloc (outBufLen); + + if (GetAdaptersAddresses (AF_UNSPEC, flags, NULL, pAddresses, &outBufLen) + == ERROR_BUFFER_OVERFLOW) + { + GNUNET_free (pAddresses); + pAddresses = (IP_ADAPTER_ADDRESSES *) GNUNET_malloc (outBufLen); + } + + dwRetVal = GetAdaptersAddresses (AF_UNSPEC, flags, NULL, pAddresses, &outBufLen); + + if (dwRetVal != NO_ERROR) + { + GNUNET_free (pAddresses); + return GNUNET_SYSERR; + } + + if (pAddresses->Length < sizeof (IP_ADAPTER_ADDRESSES_VISTA)) + { + use_enum2 = 1; + + /* Enumerate NICs using WSAIoctl() */ + if (GNUNET_OK != EnumNICs2 (&interfaces4, &interfaces4_len, &interfaces6)) + { + GNUNET_free (pAddresses); + return GNUNET_SYSERR; + } + } + + examplecom = inet_addr("192.0.34.166"); /* www.example.com */ + if (GetBestInterface (examplecom, &best_interface) != NO_ERROR) + best_interface = 0; + + if (GNGetBestInterfaceEx != NULL) + { + examplecom6.sin6_family = AF_INET6; + examplecom6.sin6_port = 0; + examplecom6.sin6_flowinfo = 0; + examplecom6.sin6_scope_id = 0; + inet_pton (AF_INET6, "2001:500:88:200:0:0:0:10", + (struct sockaddr *) &examplecom6.sin6_addr); + dwRetVal = GNGetBestInterfaceEx ((struct sockaddr *) &examplecom6, + &best_interface6); + if (dwRetVal != NO_ERROR) + best_interface6 = 0; + } + + /* Give IPv6 a priority */ + if (best_interface6 != 0) + best_interface = best_interface6; + + count = 0; + for (pCurrentAddress = pAddresses; + pCurrentAddress != NULL; pCurrentAddress = pCurrentAddress->Next) + { + if (pCurrentAddress->OperStatus == IfOperStatusUp) + { + IP_ADAPTER_UNICAST_ADDRESS *unicast = NULL; + for (unicast = pCurrentAddress->FirstUnicastAddress; unicast != NULL; + unicast = unicast->Next) + { + if ((unicast->Address.lpSockaddr->sa_family == AF_INET || + unicast->Address.lpSockaddr->sa_family == AF_INET6) && + (unicast->DadState == IpDadStateDeprecated || + unicast->DadState == IpDadStatePreferred)) + count += 1; + } + } + } + + if (count == 0) + { + *results = NULL; + *results_count = 0; + GNUNET_free (pAddresses); + GNUNET_free_non_null (interfaces4); + GNUNET_free_non_null (interfaces6); + return GNUNET_OK; + } + + *results = (struct EnumNICs3_results *) GNUNET_malloc ( + sizeof (struct EnumNICs3_results) * count); + *results_count = count; + + count = 0; + for (pCurrentAddress = pAddresses; + pCurrentAddress != NULL; pCurrentAddress = pCurrentAddress->Next) + { + struct EnumNICs3_results *r; + IP_ADAPTER_UNICAST_ADDRESS *unicast = NULL; + if (pCurrentAddress->OperStatus != IfOperStatusUp) + continue; + for (unicast = pCurrentAddress->FirstUnicastAddress; unicast != NULL; + unicast = unicast->Next) + { + int i, j; + int mask_length = -1; + char dst[INET6_ADDRSTRLEN + 1]; + + if ((unicast->Address.lpSockaddr->sa_family != AF_INET && + unicast->Address.lpSockaddr->sa_family != AF_INET6) || + (unicast->DadState != IpDadStateDeprecated && + unicast->DadState != IpDadStatePreferred)) + continue; + + r = &(*results)[count]; + r->flags = 0; + if (pCurrentAddress->IfIndex > 0 && + pCurrentAddress->IfIndex == best_interface && + unicast->Address.lpSockaddr->sa_family == AF_INET) + r->is_default = 1; + else if (pCurrentAddress->Ipv6IfIndex > 0 && + pCurrentAddress->Ipv6IfIndex == best_interface6 && + unicast->Address.lpSockaddr->sa_family == AF_INET6) + r->is_default = 1; + else + r->is_default = 0; + + /* Don't choose default interface twice */ + if (r->is_default) + best_interface = best_interface6 = 0; + + if (!use_enum2) + { + memcpy (&r->address, unicast->Address.lpSockaddr, + unicast->Address.iSockaddrLength); + memset (&r->mask, 0, sizeof (struct sockaddr)); + mask_length = ((IP_ADAPTER_UNICAST_ADDRESS_VISTA *) unicast)-> + OnLinkPrefixLength; + /* OnLinkPrefixLength is the number of leading 1s in the mask. + * OnLinkPrefixLength is available on Vista and later (hence use_enum2). + */ + if (unicast->Address.lpSockaddr->sa_family == AF_INET) + { + struct sockaddr_in *m = (struct sockaddr_in *) &r->mask; + for (i = 0; i < mask_length; i++) + ((unsigned char *) &m->sin_addr)[i / 8] |= 0x80 >> (i % 8); + } + else if (unicast->Address.lpSockaddr->sa_family == AF_INET6) + { + struct sockaddr_in6 *m = (struct sockaddr_in6 *) &r->mask; + struct sockaddr_in6 *b = (struct sockaddr_in6 *) &r->broadcast; + for (i = 0; i < mask_length; i++) + ((unsigned char *) &m->sin6_addr)[i / 8] |= 0x80 >> (i % 8); + memcpy (&r->broadcast, &r->address, unicast->Address.iSockaddrLength); + for (i = mask_length; i < 128; i++) + ((unsigned char *) &b->sin6_addr)[i / 8] |= 0x80 >> (i % 8); + } + r->flags |= ENUMNICS3_MASK_OK; + } + else + { + int found = 0; + if (unicast->Address.lpSockaddr->sa_family == AF_INET) + { + for (i = 0; !found && i < interfaces4_len / sizeof (INTERFACE_INFO); i++) + { + struct sockaddr_in *m = (struct sockaddr_in *) &r->mask; + if (memcpy (&interfaces4[i].iiAddress.Address, + unicast->Address.lpSockaddr, + unicast->Address.iSockaddrLength) != 0) + continue; + found = 1; + memcpy (&r->address, &interfaces4[i].iiAddress.Address, + sizeof (struct sockaddr_in)); + memcpy (&r->mask, &interfaces4[i].iiNetmask.Address, + sizeof (struct sockaddr_in)); + for (mask_length = 0; + ((unsigned char *) &m->sin_addr)[mask_length / 8] & + 0x80 >> (mask_length % 8); mask_length++) + { + } + r->flags |= ENUMNICS3_MASK_OK; + } + } + else if (unicast->Address.lpSockaddr->sa_family == AF_INET6) + { + for (i = 0; + interfaces6 != NULL && !found && i < interfaces6->iAddressCount; + i++) + { + if (memcpy (interfaces6->Address[i].lpSockaddr, + unicast->Address.lpSockaddr, + unicast->Address.iSockaddrLength) != 0) + continue; + found = 1; + memcpy (&r->address, interfaces6->Address[i].lpSockaddr, + sizeof (struct sockaddr_in6)); + /* TODO: Find a way to reliably get network mask for IPv6 on XP */ + memset (&r->mask, 0, sizeof (struct sockaddr)); + r->flags &= ~ENUMNICS3_MASK_OK; + } + } + if (!found) + { + DebugBreak (); + } + } + if (unicast->Address.lpSockaddr->sa_family == AF_INET) + { + struct sockaddr_in *m = (struct sockaddr_in *) &r->mask; + struct sockaddr_in *a = (struct sockaddr_in *) &r->address; + /* copy address to broadcast, then flip all the trailing bits not + * falling under netmask to 1, + * so we get, 192.168.0.255 from, say, 192.168.0.43 with mask == 24. + */ + memcpy (&r->broadcast, &r->address, unicast->Address.iSockaddrLength); + for (i = mask_length; i < 32; i++) + ((unsigned char *) &m->sin_addr)[i / 8] |= 0x80 >> (i % 8); + r->flags |= ENUMNICS3_BCAST_OK; + r->addr_size = sizeof (struct sockaddr_in); + inet_ntop (AF_INET, &a->sin_addr, dst, INET_ADDRSTRLEN); + } + else if (unicast->Address.lpSockaddr->sa_family == AF_INET6) + { + struct sockaddr_in6 *a = (struct sockaddr_in6 *) &r->address; + /* for IPv6 broadcast is not defined, zero it down */ + memset (&r->broadcast, 0, sizeof (struct sockaddr)); + r->flags &= ~ENUMNICS3_BCAST_OK; + r->addr_size = sizeof (struct sockaddr_in6); + inet_ntop (AF_INET6, &a->sin6_addr, dst, INET6_ADDRSTRLEN); + } + + i = 0; + i += snprintf (&r->pretty_name[i], 1000 - i > 0 ? 1000 - i : 0, + "%S (%s", pCurrentAddress->FriendlyName, dst); + for (j = 0; j < pCurrentAddress->PhysicalAddressLength; j++) + i += snprintf (&r->pretty_name[i], 1000 - i > 0 ? 1000 - i : 0, + "%s%02X",j > 0 ? ":" : " - ", pCurrentAddress->PhysicalAddress[j]); + i += snprintf (&r->pretty_name[i], 1000 - i > 0 ? 1000 - i : 0, ")"); + r->pretty_name[1000] = '\0'; + count += 1; + } + } + + if (use_enum2) + { + GNUNET_free_non_null (interfaces4); + GNUNET_free_non_null (interfaces6); + } + + GNUNET_free (pAddresses); + return GNUNET_OK; +} + +void +EnumNICs3_free (struct EnumNICs3_results *r) +{ + GNUNET_free_non_null (r); +} + + +/** + * Lists all network interfaces in a combo box + * Used by the basic GTK configurator + * + * @param callback function to call for each NIC + * @param callback_cls closure for callback + */ +int +ListNICs (void (*callback) (void *, const char *, int), void * callback_cls) +{ + int r; + int i; + struct EnumNICs3_results *results = NULL; + int results_count; + + r = EnumNICs3 (&results, &results_count); + if (r != GNUNET_OK) + return GNUNET_NO; + + for (i = 0; i < results_count; i++) + callback (callback_cls, results[i].pretty_name, results[i].is_default); + GNUNET_free_non_null (results); + return GNUNET_YES; +} + +/** + * @brief Installs the Windows service + * @param servicename name of the service as diplayed by the SCM + * @param application path to the application binary + * @param username the name of the service's user account + * @returns 0 on success + * 1 if the Windows version doesn't support services + * 2 if the SCM could not be opened + * 3 if the service could not be created + */ +int InstallAsService(char *servicename, char *application, char *username) +{ + SC_HANDLE hManager, hService; + char szEXE[_MAX_PATH + 17] = "\""; + char *user = NULL; + + if (! GNOpenSCManager) + return 1; + + plibc_conv_to_win_path(application, szEXE + 1); + strcat(szEXE, "\" --win-service"); + hManager = GNOpenSCManager(NULL, NULL, SC_MANAGER_CREATE_SERVICE); + if (! hManager) + return 2; + + if (username) + { + user = (char *) malloc(strlen(username) + 3); + sprintf(user, ".\\%s", username); + } + + hService = GNCreateService(hManager, (LPCTSTR) servicename, (LPCTSTR) servicename, 0, + SERVICE_WIN32_OWN_PROCESS, SERVICE_AUTO_START, SERVICE_ERROR_NORMAL, (LPCTSTR) szEXE, + NULL, NULL, NULL, (LPCTSTR) user, (LPCTSTR) username); + + if (user) + free(user); + + if (! hService) + return 3; + + GNCloseServiceHandle(hService); + + return 0; +} + +/** + * @brief Uninstall Windows service + * @param servicename name of the service to delete + * @returns 0 on success + * 1 if the Windows version doesn't support services + * 2 if the SCM could not be openend + * 3 if the service cannot be accessed + * 4 if the service cannot be deleted + */ +int UninstallService(char *servicename) +{ + SC_HANDLE hManager, hService; + + if (! GNOpenSCManager) + return 1; + + hManager = GNOpenSCManager(NULL, NULL, SC_MANAGER_CONNECT); + if (! hManager) + return 2; + + if (! (hService = GNOpenService(hManager, (LPCTSTR) servicename, DELETE))) + if (GetLastError() != ERROR_SERVICE_DOES_NOT_EXIST) + return 3; + else + goto closeSCM; + + if (! GNDeleteService(hService)) + if (GetLastError() != ERROR_SERVICE_MARKED_FOR_DELETE) + return 4; + +closeSCM: + GNCloseServiceHandle(hService); + + return 0; +} + +/** + * @author Scott Field, Microsoft + * @see http://support.microsoft.com/?scid=kb;en-us;132958 + * @date 12-Jul-95 + */ +void _InitLsaString(PLSA_UNICODE_STRING LsaString, LPWSTR String) +{ + DWORD StringLength; + + if(String == NULL) + { + LsaString->Buffer = NULL; + LsaString->Length = 0; + LsaString->MaximumLength = 0; + return; + } + + StringLength = wcslen(String); + LsaString->Buffer = String; + LsaString->Length = (USHORT) StringLength *sizeof(WCHAR); + LsaString->MaximumLength = (USHORT) (StringLength + 1) * sizeof(WCHAR); +} + + +/** + * @author Scott Field, Microsoft + * @see http://support.microsoft.com/?scid=kb;en-us;132958 + * @date 12-Jul-95 + */ +NTSTATUS _OpenPolicy(LPWSTR ServerName, DWORD DesiredAccess, PLSA_HANDLE PolicyHandle) +{ + LSA_OBJECT_ATTRIBUTES ObjectAttributes; + LSA_UNICODE_STRING ServerString; + PLSA_UNICODE_STRING Server = NULL; + + /* Always initialize the object attributes to all zeroes. */ + ZeroMemory(&ObjectAttributes, sizeof(ObjectAttributes)); + + if(ServerName != NULL) + { + /* Make a LSA_UNICODE_STRING out of the LPWSTR passed in */ + _InitLsaString(&ServerString, ServerName); + Server = &ServerString; + } + + /* Attempt to open the policy. */ + return GNLsaOpenPolicy(Server, + &ObjectAttributes, DesiredAccess, PolicyHandle); +} + +/** + * @brief Obtain a SID representing the supplied account on the supplied system + * @return TRUE on success, FALSE on failure + * @author Scott Field, Microsoft + * @date 12-Jul-95 + * @remarks A buffer is allocated which contains the SID representing the + * supplied account. This buffer should be freed when it is no longer + * needed by calling\n + * HeapFree(GetProcessHeap(), 0, buffer) + * @remarks Call GetLastError() to obtain extended error information. + * @see http://support.microsoft.com/?scid=kb;en-us;132958 + */ +BOOL _GetAccountSid(LPCTSTR SystemName, LPCTSTR AccountName, PSID * Sid) +{ + LPTSTR ReferencedDomain = NULL; + DWORD cbSid = 128; /* initial allocation attempt */ + DWORD cchReferencedDomain = 16; /* initial allocation size */ + SID_NAME_USE peUse; + BOOL bSuccess = FALSE; /* assume this function will fail */ + + /* initial memory allocations */ + if ((*Sid = HeapAlloc (GetProcessHeap (), 0, cbSid)) == NULL) + return FALSE; + + if ((ReferencedDomain = (LPTSTR) HeapAlloc (GetProcessHeap (), + 0, + cchReferencedDomain * + sizeof (TCHAR))) == NULL) + return FALSE; + + /* Obtain the SID of the specified account on the specified system. */ + while (!GNLookupAccountName(SystemName, /* machine to lookup account on */ + AccountName, /* account to lookup */ + *Sid, /* SID of interest */ + &cbSid, /* size of SID */ + ReferencedDomain, /* domain account was found on */ + &cchReferencedDomain, &peUse)) + { + if (GetLastError() == ERROR_INSUFFICIENT_BUFFER) + { + /* reallocate memory */ + if ((*Sid = HeapReAlloc (GetProcessHeap (), 0, *Sid, cbSid)) == NULL) + return FALSE; + + if ((ReferencedDomain = (LPTSTR) HeapReAlloc (GetProcessHeap (), + 0, + ReferencedDomain, + cchReferencedDomain + * sizeof (TCHAR))) == NULL) + return FALSE; + } + else + goto end; + } + + /* Indicate success. */ + bSuccess = TRUE; + +end: + /* Cleanup and indicate failure, if appropriate. */ + HeapFree (GetProcessHeap (), 0, ReferencedDomain); + + if (!bSuccess) + { + if (*Sid != NULL) + { + HeapFree (GetProcessHeap (), 0, *Sid); + *Sid = NULL; + } + } + + return bSuccess; +} + +/** + * @author Scott Field, Microsoft + * @see http://support.microsoft.com/?scid=kb;en-us;132958 + * @date 12-Jul-95 + */ +NTSTATUS _SetPrivilegeOnAccount(LSA_HANDLE PolicyHandle,/* open policy handle */ + PSID AccountSid, /* SID to grant privilege to */ + LPWSTR PrivilegeName, /* privilege to grant (Unicode) */ + BOOL bEnable /* enable or disable */ + ) +{ + LSA_UNICODE_STRING PrivilegeString; + + /* Create a LSA_UNICODE_STRING for the privilege name. */ + _InitLsaString(&PrivilegeString, PrivilegeName); + + /* grant or revoke the privilege, accordingly */ + if(bEnable) + { + NTSTATUS i; + + i = GNLsaAddAccountRights(PolicyHandle, /* open policy handle */ + AccountSid, /* target SID */ + &PrivilegeString, /* privileges */ + 1 /* privilege count */ + ); + } + else + { + return GNLsaRemoveAccountRights(PolicyHandle, /* open policy handle */ + AccountSid, /* target SID */ + FALSE, /* do not disable all rights */ + &PrivilegeString, /* privileges */ + 1 /* privilege count */ + ); + } +} + +/** + * @brief Create a Windows service account + * @return 0 on success, > 0 otherwise + * @param pszName the name of the account + * @param pszDesc description of the account + */ +int CreateServiceAccount(const char *pszName, const char *pszDesc) +{ + USER_INFO_1 ui; + USER_INFO_1008 ui2; + NET_API_STATUS nStatus; + wchar_t wszName[MAX_NAME_LENGTH], wszDesc[MAX_NAME_LENGTH]; + DWORD dwErr; + LSA_HANDLE hPolicy; + PSID pSID; + + if (! GNNetUserAdd) + return 1; + mbstowcs(wszName, pszName, strlen(pszName) + 1); + mbstowcs(wszDesc, pszDesc, strlen(pszDesc) + 1); + + memset(&ui, 0, sizeof(ui)); + ui.usri1_name = wszName; + ui.usri1_password = wszName; /* account is locked anyway */ + ui.usri1_priv = USER_PRIV_USER; + ui.usri1_comment = wszDesc; + ui.usri1_flags = UF_SCRIPT; + + nStatus = GNNetUserAdd(NULL, 1, (LPBYTE)&ui, NULL); + + if (nStatus != NERR_Success && nStatus != NERR_UserExists) + return 2; + + ui2.usri1008_flags = UF_PASSWD_CANT_CHANGE | UF_DONT_EXPIRE_PASSWD; + GNNetUserSetInfo(NULL, wszName, 1008, (LPBYTE)&ui2, NULL); + + if (_OpenPolicy(NULL, POLICY_ALL_ACCESS, &hPolicy) != + STATUS_SUCCESS) + return 3; + + _GetAccountSid(NULL, (LPCTSTR) pszName, &pSID); + + if (_SetPrivilegeOnAccount(hPolicy, pSID, (LPWSTR) L"SeServiceLogonRight", TRUE) != STATUS_SUCCESS) + return 4; + + _SetPrivilegeOnAccount(hPolicy, pSID, (LPWSTR) L"SeDenyInteractiveLogonRight", TRUE); + _SetPrivilegeOnAccount(hPolicy, pSID, (LPWSTR) L"SeDenyBatchLogonRight", TRUE); + _SetPrivilegeOnAccount(hPolicy, pSID, (LPWSTR) L"SeDenyNetworkLogonRight", TRUE); + + GNLsaClose(hPolicy); + + return 0; +} + +/** + * @brief Grant permission to a file + * @param lpszFileName the name of the file or directory + * @param lpszAccountName the user account + * @param dwAccessMask the desired access (e.g. GENERIC_ALL) + * @return TRUE on success + * @remark based on http://support.microsoft.com/default.aspx?scid=KB;EN-US;Q102102& + */ +BOOL AddPathAccessRights(char *lpszFileName, char *lpszAccountName, + DWORD dwAccessMask) +{ + /* SID variables. */ + SID_NAME_USE snuType; + TCHAR * szDomain = NULL; + DWORD cbDomain = 0; + LPVOID pUserSID = NULL; + DWORD cbUserSID = 0; + + /* File SD variables. */ + PSECURITY_DESCRIPTOR pFileSD = NULL; + DWORD cbFileSD = 0; + + /* New SD variables. */ + SECURITY_DESCRIPTOR newSD; + + /* ACL variables. */ + PACL pACL = NULL; + BOOL fDaclPresent; + BOOL fDaclDefaulted; + ACL_SIZE_INFORMATION AclInfo; + + /* New ACL variables. */ + PACL pNewACL = NULL; + DWORD cbNewACL = 0; + + /* Temporary ACE. */ + LPVOID pTempAce = NULL; + UINT CurrentAceIndex = 0; + + UINT newAceIndex = 0; + + /* Assume function will fail. */ + BOOL fResult = FALSE; + BOOL fAPISuccess; + + SECURITY_INFORMATION secInfo = DACL_SECURITY_INFORMATION; + + /** + * STEP 1: Get SID of the account name specified. + */ + fAPISuccess = GNLookupAccountName(NULL, (LPCTSTR) lpszAccountName, + pUserSID, &cbUserSID, (LPTSTR) szDomain, &cbDomain, &snuType); + + /* API should have failed with insufficient buffer. */ + if (fAPISuccess) + goto end; + else if (GetLastError() != ERROR_INSUFFICIENT_BUFFER) { + goto end; + } + + pUserSID = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, cbUserSID); + if (!pUserSID) { + goto end; + } + + szDomain = (TCHAR *) HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, cbDomain * sizeof(TCHAR)); + if (!szDomain) { + goto end; + } + + fAPISuccess = GNLookupAccountName(NULL, (LPCTSTR) lpszAccountName, + pUserSID, &cbUserSID, (LPTSTR) szDomain, &cbDomain, &snuType); + if (!fAPISuccess) { + goto end; + } + + /** + * STEP 2: Get security descriptor (SD) of the file specified. + */ + fAPISuccess = GNGetFileSecurity((LPCTSTR) lpszFileName, + secInfo, pFileSD, 0, &cbFileSD); + + /* API should have failed with insufficient buffer. */ + if (fAPISuccess) + goto end; + else if (GetLastError() != ERROR_INSUFFICIENT_BUFFER) { + goto end; + } + + pFileSD = (PSECURITY_DESCRIPTOR) HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, + cbFileSD); + if (!pFileSD) { + goto end; + } + + fAPISuccess = GNGetFileSecurity((LPCTSTR) lpszFileName, + secInfo, pFileSD, cbFileSD, &cbFileSD); + if (!fAPISuccess) { + goto end; + } + + /** + * STEP 3: Initialize new SD. + */ + if (!GNInitializeSecurityDescriptor(&newSD, + SECURITY_DESCRIPTOR_REVISION)) { + goto end; + } + + /** + * STEP 4: Get DACL from the old SD. + */ + if (!GNGetSecurityDescriptorDacl(pFileSD, &fDaclPresent, &pACL, + &fDaclDefaulted)) { + goto end; + } + + /** + * STEP 5: Get size information for DACL. + */ + AclInfo.AceCount = 0; // Assume NULL DACL. + AclInfo.AclBytesFree = 0; + AclInfo.AclBytesInUse = sizeof(ACL); + + if (pACL == NULL) + fDaclPresent = FALSE; + + /* If not NULL DACL, gather size information from DACL. */ + if (fDaclPresent) { + + if (!GNGetAclInformation(pACL, &AclInfo, + sizeof(ACL_SIZE_INFORMATION), AclSizeInformation)) { + goto end; + } + } + + /** + * STEP 6: Compute size needed for the new ACL. + */ + cbNewACL = AclInfo.AclBytesInUse + sizeof(ACCESS_ALLOWED_ACE) + + GetLengthSid(pUserSID) - sizeof(DWORD); + + /** + * STEP 7: Allocate memory for new ACL. + */ + pNewACL = (PACL) HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, cbNewACL); + if (!pNewACL) { + goto end; + } + + /** + * STEP 8: Initialize the new ACL. + */ + if (!GNInitializeAcl(pNewACL, cbNewACL, ACL_REVISION2)) { + goto end; + } + + /** + * STEP 9 If DACL is present, copy all the ACEs from the old DACL + * to the new DACL. + * + * The following code assumes that the old DACL is + * already in Windows 2000 preferred order. To conform + * to the new Windows 2000 preferred order, first we will + * copy all non-inherited ACEs from the old DACL to the + * new DACL, irrespective of the ACE type. + */ + + newAceIndex = 0; + + if (fDaclPresent && AclInfo.AceCount) { + + for (CurrentAceIndex = 0; + CurrentAceIndex < AclInfo.AceCount; + CurrentAceIndex++) { + + /** + * TEP 10: Get an ACE. + */ + if (!GNGetAce(pACL, CurrentAceIndex, &pTempAce)) { + goto end; + } + + /** + * STEP 11: Check if it is a non-inherited ACE. + * If it is an inherited ACE, break from the loop so + * that the new access allowed non-inherited ACE can + * be added in the correct position, immediately after + * all non-inherited ACEs. + */ + if (((ACCESS_ALLOWED_ACE *)pTempAce)->Header.AceFlags + & INHERITED_ACE) + break; + + /** + * STEP 12: Skip adding the ACE, if the SID matches + * with the account specified, as we are going to + * add an access allowed ACE with a different access + * mask. + */ + if (GNEqualSid(pUserSID, + &(((ACCESS_ALLOWED_ACE *)pTempAce)->SidStart))) + continue; + + /** + * STEP 13: Add the ACE to the new ACL. + */ + if (!GNAddAce(pNewACL, ACL_REVISION, MAXDWORD, pTempAce, + ((PACE_HEADER) pTempAce)->AceSize)) { + goto end; + } + + newAceIndex++; + } + } + + /** + * STEP 14: Add the access-allowed ACE to the new DACL. + * The new ACE added here will be in the correct position, + * immediately after all existing non-inherited ACEs. + */ + if (!GNAddAccessAllowedAce(pNewACL, ACL_REVISION2, dwAccessMask, + pUserSID)) { + goto end; + } + + /** + * STEP 14.5: Make new ACE inheritable + */ + if (!GetAce(pNewACL, newAceIndex, &pTempAce)) + goto end; + ((ACCESS_ALLOWED_ACE *)pTempAce)->Header.AceFlags |= + (CONTAINER_INHERIT_ACE | OBJECT_INHERIT_ACE); + + /** + * STEP 15: To conform to the new Windows 2000 preferred order, + * we will now copy the rest of inherited ACEs from the + * old DACL to the new DACL. + */ + if (fDaclPresent && AclInfo.AceCount) { + + for (; + CurrentAceIndex < AclInfo.AceCount; + CurrentAceIndex++) { + + /** + * STEP 16: Get an ACE. + */ + if (!GNGetAce(pACL, CurrentAceIndex, &pTempAce)) { + goto end; + } + + /** + * STEP 17: Add the ACE to the new ACL. + */ + if (!GNAddAce(pNewACL, ACL_REVISION, MAXDWORD, pTempAce, + ((PACE_HEADER) pTempAce)->AceSize)) { + goto end; + } + } + } + + /** + * STEP 18: Set permissions + */ + if (GNSetNamedSecurityInfo((LPTSTR) lpszFileName, SE_FILE_OBJECT, + DACL_SECURITY_INFORMATION, NULL, NULL, pNewACL, NULL) != ERROR_SUCCESS) { + goto end; + } + + fResult = TRUE; + +end: + + /** + * STEP 19: Free allocated memory + */ + if (pUserSID) + HeapFree(GetProcessHeap(), 0, pUserSID); + + if (szDomain) + HeapFree(GetProcessHeap(), 0, szDomain); + + if (pFileSD) + HeapFree(GetProcessHeap(), 0, pFileSD); + + if (pNewACL) + HeapFree(GetProcessHeap(), 0, pNewACL); + + return fResult; +} + +char *winErrorStr(const char *prefix, int dwErr) +{ + char *err, *ret; + int mem; + + if (! FormatMessage(FORMAT_MESSAGE_ALLOCATE_BUFFER | FORMAT_MESSAGE_FROM_SYSTEM, + NULL, (DWORD) dwErr, MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT), (LPTSTR) &err, + 0, NULL )) + { + err = (char *) LocalAlloc (LMEM_FIXED | LMEM_ZEROINIT, 1); + } + + mem = strlen(err) + strlen(prefix) + 20; + ret = (char *) malloc(mem); + + snprintf(ret, mem, "%s: %s (#%u)", prefix, err, dwErr); + + LocalFree(err); + + return ret; +} + +/** + * Terminate a process by creating a remote thread within it, + * which proceeds to call ExitProcess() inside that process. + * Safer than TerminateProcess (). + * + * Code is from From http://private-storm.de/2009/08/11/case-terminateprocess/ + * + * @param hProcess handle of a process to terminate + * @param uExitCode exit code to use for ExitProcess() + * @param dwTimeout number of ms to wait for the process to terminate + * @return TRUE on success, FALSE on failure (check last error for the code) + */ +BOOL +SafeTerminateProcess (HANDLE hProcess, UINT uExitCode, DWORD dwTimeout) +{ + DWORD dwTID, dwCode, dwErr = 0; + HANDLE hProcessDup = INVALID_HANDLE_VALUE; + HANDLE hRT = NULL; + HINSTANCE hKernel = GetModuleHandle ("Kernel32"); + BOOL bSuccess = FALSE; + + BOOL bDup = DuplicateHandle (GetCurrentProcess (), hProcess, + GetCurrentProcess (), &hProcessDup, PROCESS_ALL_ACCESS, + FALSE, 0); + + /* Detect the special case where the process is + * already dead... + */ + if (GetExitCodeProcess (bDup ? hProcessDup : hProcess, &dwCode) && + (STILL_ACTIVE == dwCode)) + { + FARPROC pfnExitProc; + + pfnExitProc = GetProcAddress (hKernel, "ExitProcess"); + + hRT = CreateRemoteThread ((bDup) ? hProcessDup : hProcess, NULL, 0, + (LPTHREAD_START_ROUTINE) pfnExitProc, (PVOID) uExitCode, 0, &dwTID); + + dwErr = GetLastError (); + } + else + { + dwErr = ERROR_PROCESS_ABORTED; + } + + if (hRT) + { + /* Must wait process to terminate to + * guarantee that it has exited... + */ + DWORD dwWaitResult = WaitForSingleObject ((bDup) ? hProcessDup : hProcess, + dwTimeout); + if (dwWaitResult == WAIT_TIMEOUT) + dwErr = WAIT_TIMEOUT; + else + dwErr = GetLastError (); + + CloseHandle (hRT); + bSuccess = dwErr == NO_ERROR; + } + + if (bDup) + CloseHandle (hProcessDup); + + SetLastError (dwErr); + + return bSuccess; +} + +#endif diff --git a/src/util/win.cc b/src/util/win.cc deleted file mode 100644 index 1f66072..0000000 --- a/src/util/win.cc +++ /dev/null @@ -1,1266 +0,0 @@ -/* - This file is part of GNUnet. - (C) 2001, 2002, 2003, 2004, 2005, 2006 Christian Grothoff (and other contributing authors) - - GNUnet is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published - by the Free Software Foundation; either version 2, or (at your - option) any later version. - - GNUnet is distributed in the hope that it will be useful, but - WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - General Public License for more details. - - You should have received a copy of the GNU General Public License - along with GNUnet; see the file COPYING. If not, write to the - Free Software Foundation, Inc., 59 Temple Place - Suite 330, - Boston, MA 02111-1307, USA. -*/ - -/** - * @file util/win.cc - * @brief Helper functions for MS Windows in C++ - * @author Nils Durner - */ - -#ifndef _WIN_CC -#define _WIN_CC - -#include "winproc.h" -#include "platform.h" -#include "gnunet_common.h" -#include "gnunet_connection_lib.h" - -#include -using namespace std; -#include - -#ifndef INHERITED_ACE -#define INHERITED_ACE 0x10 -#endif - -extern "C" { - -int plibc_conv_to_win_path(const char *pszUnix, char *pszWindows); - -#define _IP_ADAPTER_UNICAST_ADDRESS_HEAD \ - union { \ - struct { \ - ULONG Length; \ - DWORD Flags; \ - }; \ - }; \ - -#define _IP_ADAPTER_UNICAST_ADDRESS_BASE \ - SOCKET_ADDRESS Address; \ - IP_PREFIX_ORIGIN PrefixOrigin; \ - IP_SUFFIX_ORIGIN SuffixOrigin; \ - IP_DAD_STATE DadState; \ - ULONG ValidLifetime; \ - ULONG PreferredLifetime; \ - ULONG LeaseLifetime; - -#define _IP_ADAPTER_UNICAST_ADDRESS_ADD_VISTA \ - UINT8 OnLinkPrefixLength; - - -#define _IP_ADAPTER_UNICAST_ADDRESS_DEFINE(suffix,addition) \ -typedef struct _IP_ADAPTER_UNICAST_ADDRESS##suffix { \ - _IP_ADAPTER_UNICAST_ADDRESS_HEAD \ - struct _IP_ADAPTER_UNICAST_ADDRESS##suffix *Next; \ - _IP_ADAPTER_UNICAST_ADDRESS_BASE \ - addition \ -} IP_ADAPTER_UNICAST_ADDRESS##suffix, *PIP_ADAPTER_UNICAST_ADDRESS##suffix; - -/* _IP_ADAPTER_UNICAST_ADDRESS_DEFINE(,) defined in w32api headers */ -_IP_ADAPTER_UNICAST_ADDRESS_DEFINE(_VISTA,_IP_ADAPTER_UNICAST_ADDRESS_ADD_VISTA) - - -typedef struct _IP_ADAPTER_WINS_SERVER_ADDRESS { - union { - ULONGLONG Alignment; - struct { - ULONG Length; - DWORD Reserved; - }; - }; - struct _IP_ADAPTER_WINS_SERVER_ADDRESS *Next; - SOCKET_ADDRESS Address; -} IP_ADAPTER_WINS_SERVER_ADDRESS, *PIP_ADAPTER_WINS_SERVER_ADDRESS, *PIP_ADAPTER_WINS_SERVER_ADDRESS_LH; - -typedef struct _IP_ADAPTER_GATEWAY_ADDRESS { - union { - ULONGLONG Alignment; - struct { - ULONG Length; - DWORD Reserved; - }; - }; - struct _IP_ADAPTER_GATEWAY_ADDRESS *Next; - SOCKET_ADDRESS Address; -} IP_ADAPTER_GATEWAY_ADDRESS, *PIP_ADAPTER_GATEWAY_ADDRESS, *PIP_ADAPTER_GATEWAY_ADDRESS_LH; - -typedef UINT32 NET_IF_COMPARTMENT_ID; -typedef GUID NET_IF_NETWORK_GUID; - -typedef enum _NET_IF_CONNECTION_TYPE { - NET_IF_CONNECTION_DEDICATED = 1, - NET_IF_CONNECTION_PASSIVE, - NET_IF_CONNECTION_DEMAND, - NET_IF_CONNECTION_MAXIMUM -} NET_IF_CONNECTION_TYPE, *PNET_IF_CONNECTION_TYPE; - -typedef enum { - TUNNEL_TYPE_NONE = 0, - TUNNEL_TYPE_OTHER, - TUNNEL_TYPE_DIRECT, - TUNNEL_TYPE_6TO4, - TUNNEL_TYPE_ISATAP, - TUNNEL_TYPE_TEREDO, - TUNNEL_TYPE_IPHTTPS -} TUNNEL_TYPE, *PTUNNEL_TYPE; - -/* -A DUID consists of a two-octet type code represented in network byte - order, followed by a variable number of octets that make up the - actual identifier. A DUID can be no more than 128 octets long (not - including the type code). -*/ -#define MAX_DHCPV6_DUID_LENGTH 130 - -typedef union _NET_LUID { - ULONG64 Value; - struct { - ULONG64 Reserved :24; - ULONG64 NetLuidIndex :24; - ULONG64 IfType :16; - } Info; -} NET_LUID, *PNET_LUID, IF_LUID; - -#define MAX_DNS_SUFFIX_STRING_LENGTH 246 - -typedef struct _IP_ADAPTER_DNS_SUFFIX { - struct _IP_ADAPTER_DNS_SUFFIX *Next; - WCHAR String[MAX_DNS_SUFFIX_STRING_LENGTH]; -} IP_ADAPTER_DNS_SUFFIX, *PIP_ADAPTER_DNS_SUFFIX; - - - -#define _IP_ADAPTER_ADDRESSES_HEAD \ - union { \ - ULONGLONG Alignment; \ - struct { \ - ULONG Length; \ - DWORD IfIndex; \ - }; \ - }; - -#define _IP_ADAPTER_ADDRESSES_BASE \ - PCHAR AdapterName; \ - PIP_ADAPTER_UNICAST_ADDRESS FirstUnicastAddress; \ - PIP_ADAPTER_ANYCAST_ADDRESS FirstAnycastAddress; \ - PIP_ADAPTER_MULTICAST_ADDRESS FirstMulticastAddress; \ - PIP_ADAPTER_DNS_SERVER_ADDRESS FirstDnsServerAddress; \ - PWCHAR DnsSuffix; \ - PWCHAR Description; \ - PWCHAR FriendlyName; \ - BYTE PhysicalAddress[MAX_ADAPTER_ADDRESS_LENGTH]; \ - DWORD PhysicalAddressLength; \ - DWORD Flags; \ - DWORD Mtu; \ - DWORD IfType; \ - IF_OPER_STATUS OperStatus; - -#define _IP_ADAPTER_ADDRESSES_ADD_XPSP1 \ - DWORD Ipv6IfIndex; \ - DWORD ZoneIndices[16]; \ - PIP_ADAPTER_PREFIX FirstPrefix; \ - - -#define _IP_ADAPTER_ADDRESSES_ADD_VISTA \ - _IP_ADAPTER_ADDRESSES_ADD_XPSP1 \ - ULONG64 TransmitLinkSpeed; \ - ULONG64 ReceiveLinkSpeed; \ - PIP_ADAPTER_WINS_SERVER_ADDRESS_LH FirstWinsServerAddress; \ - PIP_ADAPTER_GATEWAY_ADDRESS_LH FirstGatewayAddress; \ - ULONG Ipv4Metric; \ - ULONG Ipv6Metric; \ - IF_LUID Luid; \ - SOCKET_ADDRESS Dhcpv4Server; \ - NET_IF_COMPARTMENT_ID CompartmentId; \ - NET_IF_NETWORK_GUID NetworkGuid; \ - NET_IF_CONNECTION_TYPE ConnectionType; \ - TUNNEL_TYPE TunnelType; \ - SOCKET_ADDRESS Dhcpv6Server; \ - BYTE Dhcpv6ClientDuid[MAX_DHCPV6_DUID_LENGTH]; \ - ULONG Dhcpv6ClientDuidLength; \ - ULONG Dhcpv6Iaid; - -#define _IP_ADAPTER_ADDRESSES_ADD_2008_OR_VISTASP1 \ - _IP_ADAPTER_ADDRESSES_ADD_VISTA \ - PIP_ADAPTER_DNS_SUFFIX FirstDnsSuffix; - -#define _IP_ADAPTER_ADDRESSES_DEFINE(suffix,addition) \ -typedef struct _IP_ADAPTER_ADDRESSES##suffix { \ - _IP_ADAPTER_ADDRESSES_HEAD \ - struct _IP_ADAPTER_ADDRESSES##suffix *Next; \ - _IP_ADAPTER_ADDRESSES_BASE \ - addition \ -} IP_ADAPTER_ADDRESSES##suffix, *PIP_ADAPTER_ADDRESSES##suffix; - - -/* _IP_ADAPTER_ADDRESSES_DEFINE(,) defined in w32api headers */ -_IP_ADAPTER_ADDRESSES_DEFINE(_XPSP1,_IP_ADAPTER_ADDRESSES_ADD_XPSP1) -_IP_ADAPTER_ADDRESSES_DEFINE(_VISTA,_IP_ADAPTER_ADDRESSES_ADD_VISTA) -_IP_ADAPTER_ADDRESSES_DEFINE(_2008_OR_VISTASP1,_IP_ADAPTER_ADDRESSES_ADD_2008_OR_VISTASP1) - -static int -EnumNICs_IPv6_get_ifs_count (SOCKET s) -{ - DWORD dwret = 0, err; - int iret; - iret = WSAIoctl (s, SIO_ADDRESS_LIST_QUERY, NULL, 0, NULL, 0, - &dwret, NULL, NULL); - err = GetLastError (); - if (iret == SOCKET_ERROR && err == WSAEFAULT) - return dwret; - else if (iret == 0) - return 0; - return GNUNET_SYSERR; -} - -static int -EnumNICs_IPv6_get_ifs (SOCKET s, SOCKET_ADDRESS_LIST *inf, int size) -{ - int iret; - DWORD dwret = 0; - iret = WSAIoctl (s, SIO_ADDRESS_LIST_QUERY, NULL, 0, inf, size, - &dwret, NULL, NULL); - - if (iret != 0 || dwret != size) - { - /* It's supposed to succeed! And size should be the same */ - return GNUNET_SYSERR; - } - return GNUNET_OK; -} - -#undef GNUNET_malloc -#define GNUNET_malloc(a) HeapAlloc(GetProcessHeap (), HEAP_ZERO_MEMORY | \ - HEAP_GENERATE_EXCEPTIONS, a) - -#undef GNUNET_free -#define GNUNET_free(a) HeapFree(GetProcessHeap (), 0, a) - -#undef GNUNET_free_non_null -#define GNUNET_free_non_null(a) do { if ((a) != NULL) GNUNET_free(a); } while (0) - -static int -EnumNICs_IPv4_get_ifs (SOCKET s, INTERFACE_INFO **inf, int *size) -{ - int iret; - DWORD dwret = 0; - DWORD error; - INTERFACE_INFO *ii = NULL; - DWORD ii_size = sizeof (INTERFACE_INFO) * 15; - while (TRUE) - { - if (ii_size >= sizeof (INTERFACE_INFO) * 1000) - return GNUNET_SYSERR; - ii = (INTERFACE_INFO *) GNUNET_malloc (ii_size); - dwret = 0; - iret = WSAIoctl (s, SIO_GET_INTERFACE_LIST, NULL, 0, ii, ii_size, - &dwret, NULL, NULL); - error = GetLastError (); - if (iret == SOCKET_ERROR) - { - if (error == WSAEFAULT) - { - GNUNET_free (ii); - ii_size *= 2; - continue; - } - GNUNET_free (ii); - return GNUNET_SYSERR; - } - else - { - *inf = ii; - *size = dwret; - return GNUNET_OK; - } - } - return GNUNET_SYSERR; -} - -int -EnumNICs2 (INTERFACE_INFO **ifs4, int *ifs4_len, SOCKET_ADDRESS_LIST **ifs6) -{ - int result = 0; - SOCKET s4 = INVALID_SOCKET, s6 = INVALID_SOCKET; - DWORD dwret1 = 0, dwret2; - DWORD err1, err2; - int ifs4len = 0, ifs6len = 0; - INTERFACE_INFO *interfaces4 = NULL; - SOCKET_ADDRESS_LIST *interfaces6 = NULL; - SetLastError (0); - s4 = socket (AF_INET, SOCK_STREAM, IPPROTO_TCP); - err1 = GetLastError (); - SetLastError (0); - s6 = socket (AF_INET6, SOCK_STREAM, IPPROTO_TCP); - err2 = GetLastError (); - if (s6 != INVALID_SOCKET) - { - ifs6len = EnumNICs_IPv6_get_ifs_count (s6); - if (ifs6len > 0) - { - interfaces6 = (SOCKET_ADDRESS_LIST *) GNUNET_malloc (ifs6len); - result = EnumNICs_IPv6_get_ifs (s6, interfaces6, ifs6len) || result; - } - closesocket (s6); - s6 = INVALID_SOCKET; - } - - if (s4 != INVALID_SOCKET) - { - result = EnumNICs_IPv4_get_ifs (s4, &interfaces4, &ifs4len) || result; - closesocket (s4); - s4 = INVALID_SOCKET; - } - if (ifs6len + ifs4len == 0) - goto error; - - if (!result) - { - *ifs4 = interfaces4; - *ifs4_len = ifs4len; - *ifs6 = interfaces6; - return GNUNET_OK; - } -error: - if (interfaces4 != NULL) - GNUNET_free (interfaces4); - if (interfaces6 != NULL) - GNUNET_free (interfaces6); - if (s4 != INVALID_SOCKET) - closesocket (s4); - if (s6 != INVALID_SOCKET) - closesocket (s6); - return GNUNET_SYSERR; -} - -/** - * Returns GNUNET_OK on OK, GNUNET_SYSERR on error - */ -int -EnumNICs3 (struct EnumNICs3_results **results, int *results_count) -{ - DWORD dwRetVal = 0; - int count = 0; - ULONG flags = /*GAA_FLAG_INCLUDE_PREFIX |*/ GAA_FLAG_SKIP_ANYCAST | - GAA_FLAG_SKIP_MULTICAST | GAA_FLAG_SKIP_DNS_SERVER; - struct sockaddr_in6 examplecom6; - IPAddr examplecom; - DWORD best_interface = 0; - DWORD best_interface6 = 0; - - int use_enum2 = 0; - INTERFACE_INFO *interfaces4 = NULL; - int interfaces4_len = 0; - SOCKET_ADDRESS_LIST *interfaces6 = NULL; - - unsigned long outBufLen = sizeof (IP_ADAPTER_ADDRESSES); - IP_ADAPTER_ADDRESSES *pCurrentAddress = NULL; - IP_ADAPTER_ADDRESSES *pAddresses = (IP_ADAPTER_ADDRESSES *) GNUNET_malloc (outBufLen); - - if (GetAdaptersAddresses (AF_UNSPEC, flags, NULL, pAddresses, &outBufLen) - == ERROR_BUFFER_OVERFLOW) - { - GNUNET_free (pAddresses); - pAddresses = (IP_ADAPTER_ADDRESSES *) GNUNET_malloc (outBufLen); - } - - dwRetVal = GetAdaptersAddresses (AF_UNSPEC, flags, NULL, pAddresses, &outBufLen); - - if (dwRetVal != NO_ERROR) - { - GNUNET_free (pAddresses); - return GNUNET_SYSERR; - } - - if (pAddresses->Length < sizeof (IP_ADAPTER_ADDRESSES_VISTA)) - { - use_enum2 = 1; - - /* Enumerate NICs using WSAIoctl() */ - if (GNUNET_OK != EnumNICs2 (&interfaces4, &interfaces4_len, &interfaces6)) - { - GNUNET_free (pAddresses); - return GNUNET_SYSERR; - } - } - - examplecom = inet_addr("192.0.34.166"); /* www.example.com */ - if (GetBestInterface (examplecom, &best_interface) != NO_ERROR) - best_interface = 0; - - if (GNGetBestInterfaceEx != NULL) - { - examplecom6.sin6_family = AF_INET6; - examplecom6.sin6_port = 0; - examplecom6.sin6_flowinfo = 0; - examplecom6.sin6_scope_id = 0; - inet_pton (AF_INET6, "2001:500:88:200:0:0:0:10", - (struct sockaddr *) &examplecom6.sin6_addr); - dwRetVal = GNGetBestInterfaceEx ((struct sockaddr *) &examplecom6, - &best_interface6); - if (dwRetVal != NO_ERROR) - best_interface6 = 0; - } - - /* Give IPv6 a priority */ - if (best_interface6 != 0) - best_interface = best_interface6; - - count = 0; - for (pCurrentAddress = pAddresses; - pCurrentAddress != NULL; pCurrentAddress = pCurrentAddress->Next) - { - if (pCurrentAddress->OperStatus == IfOperStatusUp) - { - IP_ADAPTER_UNICAST_ADDRESS *unicast = NULL; - for (unicast = pCurrentAddress->FirstUnicastAddress; unicast != NULL; - unicast = unicast->Next) - { - if ((unicast->Address.lpSockaddr->sa_family == AF_INET || - unicast->Address.lpSockaddr->sa_family == AF_INET6) && - (unicast->DadState == IpDadStateDeprecated || - unicast->DadState == IpDadStatePreferred)) - count += 1; - } - } - } - - if (count == 0) - { - *results = NULL; - *results_count = 0; - GNUNET_free (pAddresses); - GNUNET_free_non_null (interfaces4); - GNUNET_free_non_null (interfaces6); - return GNUNET_OK; - } - - *results = (struct EnumNICs3_results *) GNUNET_malloc ( - sizeof (struct EnumNICs3_results) * count); - *results_count = count; - - count = 0; - for (pCurrentAddress = pAddresses; - pCurrentAddress != NULL; pCurrentAddress = pCurrentAddress->Next) - { - struct EnumNICs3_results *r; - IP_ADAPTER_UNICAST_ADDRESS *unicast = NULL; - if (pCurrentAddress->OperStatus != IfOperStatusUp) - continue; - for (unicast = pCurrentAddress->FirstUnicastAddress; unicast != NULL; - unicast = unicast->Next) - { - int i, j; - int mask_length = -1; - char dst[INET6_ADDRSTRLEN + 1]; - - if ((unicast->Address.lpSockaddr->sa_family != AF_INET && - unicast->Address.lpSockaddr->sa_family != AF_INET6) || - (unicast->DadState != IpDadStateDeprecated && - unicast->DadState != IpDadStatePreferred)) - continue; - - r = &(*results)[count]; - r->flags = 0; - if (pCurrentAddress->IfIndex > 0 && - pCurrentAddress->IfIndex == best_interface && - unicast->Address.lpSockaddr->sa_family == AF_INET) - r->is_default = 1; - else if (pCurrentAddress->Ipv6IfIndex > 0 && - pCurrentAddress->Ipv6IfIndex == best_interface6 && - unicast->Address.lpSockaddr->sa_family == AF_INET6) - r->is_default = 1; - else - r->is_default = 0; - - /* Don't choose default interface twice */ - if (r->is_default) - best_interface = best_interface6 = 0; - - if (!use_enum2) - { - memcpy (&r->address, unicast->Address.lpSockaddr, - unicast->Address.iSockaddrLength); - memset (&r->mask, 0, sizeof (struct sockaddr)); - mask_length = ((IP_ADAPTER_UNICAST_ADDRESS_VISTA *) unicast)-> - OnLinkPrefixLength; - /* OnLinkPrefixLength is the number of leading 1s in the mask. - * OnLinkPrefixLength is available on Vista and later (hence use_enum2). - */ - if (unicast->Address.lpSockaddr->sa_family == AF_INET) - { - struct sockaddr_in *m = (struct sockaddr_in *) &r->mask; - for (i = 0; i < mask_length; i++) - ((unsigned char *) &m->sin_addr)[i / 8] |= 0x80 >> (i % 8); - } - else if (unicast->Address.lpSockaddr->sa_family == AF_INET6) - { - struct sockaddr_in6 *m = (struct sockaddr_in6 *) &r->mask; - struct sockaddr_in6 *b = (struct sockaddr_in6 *) &r->broadcast; - for (i = 0; i < mask_length; i++) - ((unsigned char *) &m->sin6_addr)[i / 8] |= 0x80 >> (i % 8); - memcpy (&r->broadcast, &r->address, unicast->Address.iSockaddrLength); - for (i = mask_length; i < 128; i++) - ((unsigned char *) &b->sin6_addr)[i / 8] |= 0x80 >> (i % 8); - } - r->flags |= ENUMNICS3_MASK_OK; - } - else - { - int found = 0; - if (unicast->Address.lpSockaddr->sa_family == AF_INET) - { - for (i = 0; !found && i < interfaces4_len / sizeof (INTERFACE_INFO); i++) - { - struct sockaddr_in *m = (struct sockaddr_in *) &r->mask; - if (memcpy (&interfaces4[i].iiAddress.Address, - unicast->Address.lpSockaddr, - unicast->Address.iSockaddrLength) != 0) - continue; - found = 1; - memcpy (&r->address, &interfaces4[i].iiAddress.Address, - sizeof (struct sockaddr_in)); - memcpy (&r->mask, &interfaces4[i].iiNetmask.Address, - sizeof (struct sockaddr_in)); - for (mask_length = 0; - ((unsigned char *) &m->sin_addr)[mask_length / 8] & - 0x80 >> (mask_length % 8); mask_length++) - { - } - r->flags |= ENUMNICS3_MASK_OK; - } - } - else if (unicast->Address.lpSockaddr->sa_family == AF_INET6) - { - for (i = 0; - interfaces6 != NULL && !found && i < interfaces6->iAddressCount; - i++) - { - if (memcpy (interfaces6->Address[i].lpSockaddr, - unicast->Address.lpSockaddr, - unicast->Address.iSockaddrLength) != 0) - continue; - found = 1; - memcpy (&r->address, interfaces6->Address[i].lpSockaddr, - sizeof (struct sockaddr_in6)); - /* TODO: Find a way to reliably get network mask for IPv6 on XP */ - memset (&r->mask, 0, sizeof (struct sockaddr)); - r->flags &= ~ENUMNICS3_MASK_OK; - } - } - if (!found) - { - DebugBreak (); - } - } - if (unicast->Address.lpSockaddr->sa_family == AF_INET) - { - struct sockaddr_in *m = (struct sockaddr_in *) &r->mask; - struct sockaddr_in *a = (struct sockaddr_in *) &r->address; - /* copy address to broadcast, then flip all the trailing bits not - * falling under netmask to 1, - * so we get, 192.168.0.255 from, say, 192.168.0.43 with mask == 24. - */ - memcpy (&r->broadcast, &r->address, unicast->Address.iSockaddrLength); - for (i = mask_length; i < 32; i++) - ((unsigned char *) &m->sin_addr)[i / 8] |= 0x80 >> (i % 8); - r->flags |= ENUMNICS3_BCAST_OK; - r->addr_size = sizeof (struct sockaddr_in); - inet_ntop (AF_INET, &a->sin_addr, dst, INET_ADDRSTRLEN); - } - else if (unicast->Address.lpSockaddr->sa_family == AF_INET6) - { - struct sockaddr_in6 *a = (struct sockaddr_in6 *) &r->address; - /* for IPv6 broadcast is not defined, zero it down */ - memset (&r->broadcast, 0, sizeof (struct sockaddr)); - r->flags &= ~ENUMNICS3_BCAST_OK; - r->addr_size = sizeof (struct sockaddr_in6); - inet_ntop (AF_INET6, &a->sin6_addr, dst, INET6_ADDRSTRLEN); - } - - i = 0; - i += snprintf (&r->pretty_name[i], 1000 - i > 0 ? 1000 - i : 0, - "%S (%s", pCurrentAddress->FriendlyName, dst); - for (j = 0; j < pCurrentAddress->PhysicalAddressLength; j++) - i += snprintf (&r->pretty_name[i], 1000 - i > 0 ? 1000 - i : 0, - "%s%02X",j > 0 ? ":" : " - ", pCurrentAddress->PhysicalAddress[j]); - i += snprintf (&r->pretty_name[i], 1000 - i > 0 ? 1000 - i : 0, ")"); - r->pretty_name[1000] = '\0'; - count += 1; - } - } - - if (use_enum2) - { - GNUNET_free_non_null (interfaces4); - GNUNET_free_non_null (interfaces6); - } - - GNUNET_free (pAddresses); - return GNUNET_OK; -} - -void -EnumNICs3_free (struct EnumNICs3_results *r) -{ - GNUNET_free_non_null (r); -} - - -/** - * Lists all network interfaces in a combo box - * Used by the basic GTK configurator - * - * @param callback function to call for each NIC - * @param callback_cls closure for callback - */ -int -ListNICs (void (*callback) (void *, const char *, int), void * callback_cls) -{ - int r; - int i; - struct EnumNICs3_results *results = NULL; - int results_count; - - r = EnumNICs3 (&results, &results_count); - if (r != GNUNET_OK) - return GNUNET_NO; - - for (i = 0; i < results_count; i++) - callback (callback_cls, results[i].pretty_name, results[i].is_default); - GNUNET_free_non_null (results); - return GNUNET_YES; -} - -/** - * @brief Installs the Windows service - * @param servicename name of the service as diplayed by the SCM - * @param application path to the application binary - * @param username the name of the service's user account - * @returns 0 on success - * 1 if the Windows version doesn't support services - * 2 if the SCM could not be opened - * 3 if the service could not be created - */ -int InstallAsService(char *servicename, char *application, char *username) -{ - SC_HANDLE hManager, hService; - char szEXE[_MAX_PATH + 17] = "\""; - char *user = NULL; - - if (! GNOpenSCManager) - return 1; - - plibc_conv_to_win_path(application, szEXE + 1); - strcat(szEXE, "\" --win-service"); - hManager = GNOpenSCManager(NULL, NULL, SC_MANAGER_CREATE_SERVICE); - if (! hManager) - return 2; - - if (username) - { - user = (char *) malloc(strlen(username) + 3); - sprintf(user, ".\\%s", username); - } - - hService = GNCreateService(hManager, (LPCTSTR) servicename, (LPCTSTR) servicename, 0, - SERVICE_WIN32_OWN_PROCESS, SERVICE_AUTO_START, SERVICE_ERROR_NORMAL, (LPCTSTR) szEXE, - NULL, NULL, NULL, (LPCTSTR) user, (LPCTSTR) username); - - if (user) - free(user); - - if (! hService) - return 3; - - GNCloseServiceHandle(hService); - - return 0; -} - -/** - * @brief Uninstall Windows service - * @param servicename name of the service to delete - * @returns 0 on success - * 1 if the Windows version doesn't support services - * 2 if the SCM could not be openend - * 3 if the service cannot be accessed - * 4 if the service cannot be deleted - */ -int UninstallService(char *servicename) -{ - SC_HANDLE hManager, hService; - - if (! GNOpenSCManager) - return 1; - - hManager = GNOpenSCManager(NULL, NULL, SC_MANAGER_CONNECT); - if (! hManager) - return 2; - - if (! (hService = GNOpenService(hManager, (LPCTSTR) servicename, DELETE))) - if (GetLastError() != ERROR_SERVICE_DOES_NOT_EXIST) - return 3; - else - goto closeSCM; - - if (! GNDeleteService(hService)) - if (GetLastError() != ERROR_SERVICE_MARKED_FOR_DELETE) - return 4; - -closeSCM: - GNCloseServiceHandle(hService); - - return 0; -} - -/** - * @author Scott Field, Microsoft - * @see http://support.microsoft.com/?scid=kb;en-us;132958 - * @date 12-Jul-95 - */ -void _InitLsaString(PLSA_UNICODE_STRING LsaString, LPWSTR String) -{ - DWORD StringLength; - - if(String == NULL) - { - LsaString->Buffer = NULL; - LsaString->Length = 0; - LsaString->MaximumLength = 0; - return; - } - - StringLength = wcslen(String); - LsaString->Buffer = String; - LsaString->Length = (USHORT) StringLength *sizeof(WCHAR); - LsaString->MaximumLength = (USHORT) (StringLength + 1) * sizeof(WCHAR); -} - - -/** - * @author Scott Field, Microsoft - * @see http://support.microsoft.com/?scid=kb;en-us;132958 - * @date 12-Jul-95 - */ -NTSTATUS _OpenPolicy(LPWSTR ServerName, DWORD DesiredAccess, PLSA_HANDLE PolicyHandle) -{ - LSA_OBJECT_ATTRIBUTES ObjectAttributes; - LSA_UNICODE_STRING ServerString; - PLSA_UNICODE_STRING Server = NULL; - - /* Always initialize the object attributes to all zeroes. */ - ZeroMemory(&ObjectAttributes, sizeof(ObjectAttributes)); - - if(ServerName != NULL) - { - /* Make a LSA_UNICODE_STRING out of the LPWSTR passed in */ - _InitLsaString(&ServerString, ServerName); - Server = &ServerString; - } - - /* Attempt to open the policy. */ - return GNLsaOpenPolicy(Server, - &ObjectAttributes, DesiredAccess, PolicyHandle); -} - -/** - * @brief Obtain a SID representing the supplied account on the supplied system - * @return TRUE on success, FALSE on failure - * @author Scott Field, Microsoft - * @date 12-Jul-95 - * @remarks A buffer is allocated which contains the SID representing the - * supplied account. This buffer should be freed when it is no longer - * needed by calling\n - * HeapFree(GetProcessHeap(), 0, buffer) - * @remarks Call GetLastError() to obtain extended error information. - * @see http://support.microsoft.com/?scid=kb;en-us;132958 - */ -BOOL _GetAccountSid(LPCTSTR SystemName, LPCTSTR AccountName, PSID * Sid) -{ - LPTSTR ReferencedDomain = NULL; - DWORD cbSid = 128; /* initial allocation attempt */ - DWORD cchReferencedDomain = 16; /* initial allocation size */ - SID_NAME_USE peUse; - BOOL bSuccess = FALSE; /* assume this function will fail */ - - /* initial memory allocations */ - if ((*Sid = HeapAlloc (GetProcessHeap (), 0, cbSid)) == NULL) - return FALSE; - - if ((ReferencedDomain = (LPTSTR) HeapAlloc (GetProcessHeap (), - 0, - cchReferencedDomain * - sizeof (TCHAR))) == NULL) - return FALSE; - - /* Obtain the SID of the specified account on the specified system. */ - while (!GNLookupAccountName(SystemName, /* machine to lookup account on */ - AccountName, /* account to lookup */ - *Sid, /* SID of interest */ - &cbSid, /* size of SID */ - ReferencedDomain, /* domain account was found on */ - &cchReferencedDomain, &peUse)) - { - if (GetLastError() == ERROR_INSUFFICIENT_BUFFER) - { - /* reallocate memory */ - if ((*Sid = HeapReAlloc (GetProcessHeap (), 0, *Sid, cbSid)) == NULL) - return FALSE; - - if ((ReferencedDomain = (LPTSTR) HeapReAlloc (GetProcessHeap (), - 0, - ReferencedDomain, - cchReferencedDomain - * sizeof (TCHAR))) == NULL) - return FALSE; - } - else - goto end; - } - - /* Indicate success. */ - bSuccess = TRUE; - -end: - /* Cleanup and indicate failure, if appropriate. */ - HeapFree (GetProcessHeap (), 0, ReferencedDomain); - - if (!bSuccess) - { - if (*Sid != NULL) - { - HeapFree (GetProcessHeap (), 0, *Sid); - *Sid = NULL; - } - } - - return bSuccess; -} - -/** - * @author Scott Field, Microsoft - * @see http://support.microsoft.com/?scid=kb;en-us;132958 - * @date 12-Jul-95 - */ -NTSTATUS _SetPrivilegeOnAccount(LSA_HANDLE PolicyHandle,/* open policy handle */ - PSID AccountSid, /* SID to grant privilege to */ - LPWSTR PrivilegeName, /* privilege to grant (Unicode) */ - BOOL bEnable /* enable or disable */ - ) -{ - LSA_UNICODE_STRING PrivilegeString; - - /* Create a LSA_UNICODE_STRING for the privilege name. */ - _InitLsaString(&PrivilegeString, PrivilegeName); - - /* grant or revoke the privilege, accordingly */ - if(bEnable) - { - NTSTATUS i; - - i = GNLsaAddAccountRights(PolicyHandle, /* open policy handle */ - AccountSid, /* target SID */ - &PrivilegeString, /* privileges */ - 1 /* privilege count */ - ); - } - else - { - return GNLsaRemoveAccountRights(PolicyHandle, /* open policy handle */ - AccountSid, /* target SID */ - FALSE, /* do not disable all rights */ - &PrivilegeString, /* privileges */ - 1 /* privilege count */ - ); - } -} - -/** - * @brief Create a Windows service account - * @return 0 on success, > 0 otherwise - * @param pszName the name of the account - * @param pszDesc description of the account - */ -int CreateServiceAccount(const char *pszName, const char *pszDesc) -{ - USER_INFO_1 ui; - USER_INFO_1008 ui2; - NET_API_STATUS nStatus; - wchar_t wszName[MAX_NAME_LENGTH], wszDesc[MAX_NAME_LENGTH]; - DWORD dwErr; - LSA_HANDLE hPolicy; - PSID pSID; - - if (! GNNetUserAdd) - return 1; - mbstowcs(wszName, pszName, strlen(pszName) + 1); - mbstowcs(wszDesc, pszDesc, strlen(pszDesc) + 1); - - memset(&ui, 0, sizeof(ui)); - ui.usri1_name = wszName; - ui.usri1_password = wszName; /* account is locked anyway */ - ui.usri1_priv = USER_PRIV_USER; - ui.usri1_comment = wszDesc; - ui.usri1_flags = UF_SCRIPT; - - nStatus = GNNetUserAdd(NULL, 1, (LPBYTE)&ui, NULL); - - if (nStatus != NERR_Success && nStatus != NERR_UserExists) - return 2; - - ui2.usri1008_flags = UF_PASSWD_CANT_CHANGE | UF_DONT_EXPIRE_PASSWD; - GNNetUserSetInfo(NULL, wszName, 1008, (LPBYTE)&ui2, NULL); - - if (_OpenPolicy(NULL, POLICY_ALL_ACCESS, &hPolicy) != - STATUS_SUCCESS) - return 3; - - _GetAccountSid(NULL, (LPCTSTR) pszName, &pSID); - - if (_SetPrivilegeOnAccount(hPolicy, pSID, (LPWSTR) L"SeServiceLogonRight", TRUE) != STATUS_SUCCESS) - return 4; - - _SetPrivilegeOnAccount(hPolicy, pSID, (LPWSTR) L"SeDenyInteractiveLogonRight", TRUE); - _SetPrivilegeOnAccount(hPolicy, pSID, (LPWSTR) L"SeDenyBatchLogonRight", TRUE); - _SetPrivilegeOnAccount(hPolicy, pSID, (LPWSTR) L"SeDenyNetworkLogonRight", TRUE); - - GNLsaClose(hPolicy); - - return 0; -} - -/** - * @brief Grant permission to a file - * @param lpszFileName the name of the file or directory - * @param lpszAccountName the user account - * @param dwAccessMask the desired access (e.g. GENERIC_ALL) - * @return TRUE on success - * @remark based on http://support.microsoft.com/default.aspx?scid=KB;EN-US;Q102102& - */ -BOOL AddPathAccessRights(char *lpszFileName, char *lpszAccountName, - DWORD dwAccessMask) -{ - /* SID variables. */ - SID_NAME_USE snuType; - TCHAR * szDomain = NULL; - DWORD cbDomain = 0; - LPVOID pUserSID = NULL; - DWORD cbUserSID = 0; - - /* File SD variables. */ - PSECURITY_DESCRIPTOR pFileSD = NULL; - DWORD cbFileSD = 0; - - /* New SD variables. */ - SECURITY_DESCRIPTOR newSD; - - /* ACL variables. */ - PACL pACL = NULL; - BOOL fDaclPresent; - BOOL fDaclDefaulted; - ACL_SIZE_INFORMATION AclInfo; - - /* New ACL variables. */ - PACL pNewACL = NULL; - DWORD cbNewACL = 0; - - /* Temporary ACE. */ - LPVOID pTempAce = NULL; - UINT CurrentAceIndex = 0; - - UINT newAceIndex = 0; - - /* Assume function will fail. */ - BOOL fResult = FALSE; - BOOL fAPISuccess; - - SECURITY_INFORMATION secInfo = DACL_SECURITY_INFORMATION; - - /** - * STEP 1: Get SID of the account name specified. - */ - fAPISuccess = GNLookupAccountName(NULL, (LPCTSTR) lpszAccountName, - pUserSID, &cbUserSID, (LPTSTR) szDomain, &cbDomain, &snuType); - - /* API should have failed with insufficient buffer. */ - if (fAPISuccess) - goto end; - else if (GetLastError() != ERROR_INSUFFICIENT_BUFFER) { - goto end; - } - - pUserSID = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, cbUserSID); - if (!pUserSID) { - goto end; - } - - szDomain = (TCHAR *) HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, cbDomain * sizeof(TCHAR)); - if (!szDomain) { - goto end; - } - - fAPISuccess = GNLookupAccountName(NULL, (LPCTSTR) lpszAccountName, - pUserSID, &cbUserSID, (LPTSTR) szDomain, &cbDomain, &snuType); - if (!fAPISuccess) { - goto end; - } - - /** - * STEP 2: Get security descriptor (SD) of the file specified. - */ - fAPISuccess = GNGetFileSecurity((LPCTSTR) lpszFileName, - secInfo, pFileSD, 0, &cbFileSD); - - /* API should have failed with insufficient buffer. */ - if (fAPISuccess) - goto end; - else if (GetLastError() != ERROR_INSUFFICIENT_BUFFER) { - goto end; - } - - pFileSD = (PSECURITY_DESCRIPTOR) HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, - cbFileSD); - if (!pFileSD) { - goto end; - } - - fAPISuccess = GNGetFileSecurity((LPCTSTR) lpszFileName, - secInfo, pFileSD, cbFileSD, &cbFileSD); - if (!fAPISuccess) { - goto end; - } - - /** - * STEP 3: Initialize new SD. - */ - if (!GNInitializeSecurityDescriptor(&newSD, - SECURITY_DESCRIPTOR_REVISION)) { - goto end; - } - - /** - * STEP 4: Get DACL from the old SD. - */ - if (!GNGetSecurityDescriptorDacl(pFileSD, &fDaclPresent, &pACL, - &fDaclDefaulted)) { - goto end; - } - - /** - * STEP 5: Get size information for DACL. - */ - AclInfo.AceCount = 0; // Assume NULL DACL. - AclInfo.AclBytesFree = 0; - AclInfo.AclBytesInUse = sizeof(ACL); - - if (pACL == NULL) - fDaclPresent = FALSE; - - /* If not NULL DACL, gather size information from DACL. */ - if (fDaclPresent) { - - if (!GNGetAclInformation(pACL, &AclInfo, - sizeof(ACL_SIZE_INFORMATION), AclSizeInformation)) { - goto end; - } - } - - /** - * STEP 6: Compute size needed for the new ACL. - */ - cbNewACL = AclInfo.AclBytesInUse + sizeof(ACCESS_ALLOWED_ACE) - + GetLengthSid(pUserSID) - sizeof(DWORD); - - /** - * STEP 7: Allocate memory for new ACL. - */ - pNewACL = (PACL) HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, cbNewACL); - if (!pNewACL) { - goto end; - } - - /** - * STEP 8: Initialize the new ACL. - */ - if (!GNInitializeAcl(pNewACL, cbNewACL, ACL_REVISION2)) { - goto end; - } - - /** - * STEP 9 If DACL is present, copy all the ACEs from the old DACL - * to the new DACL. - * - * The following code assumes that the old DACL is - * already in Windows 2000 preferred order. To conform - * to the new Windows 2000 preferred order, first we will - * copy all non-inherited ACEs from the old DACL to the - * new DACL, irrespective of the ACE type. - */ - - newAceIndex = 0; - - if (fDaclPresent && AclInfo.AceCount) { - - for (CurrentAceIndex = 0; - CurrentAceIndex < AclInfo.AceCount; - CurrentAceIndex++) { - - /** - * TEP 10: Get an ACE. - */ - if (!GNGetAce(pACL, CurrentAceIndex, &pTempAce)) { - goto end; - } - - /** - * STEP 11: Check if it is a non-inherited ACE. - * If it is an inherited ACE, break from the loop so - * that the new access allowed non-inherited ACE can - * be added in the correct position, immediately after - * all non-inherited ACEs. - */ - if (((ACCESS_ALLOWED_ACE *)pTempAce)->Header.AceFlags - & INHERITED_ACE) - break; - - /** - * STEP 12: Skip adding the ACE, if the SID matches - * with the account specified, as we are going to - * add an access allowed ACE with a different access - * mask. - */ - if (GNEqualSid(pUserSID, - &(((ACCESS_ALLOWED_ACE *)pTempAce)->SidStart))) - continue; - - /** - * STEP 13: Add the ACE to the new ACL. - */ - if (!GNAddAce(pNewACL, ACL_REVISION, MAXDWORD, pTempAce, - ((PACE_HEADER) pTempAce)->AceSize)) { - goto end; - } - - newAceIndex++; - } - } - - /** - * STEP 14: Add the access-allowed ACE to the new DACL. - * The new ACE added here will be in the correct position, - * immediately after all existing non-inherited ACEs. - */ - if (!GNAddAccessAllowedAce(pNewACL, ACL_REVISION2, dwAccessMask, - pUserSID)) { - goto end; - } - - /** - * STEP 14.5: Make new ACE inheritable - */ - if (!GetAce(pNewACL, newAceIndex, &pTempAce)) - goto end; - ((ACCESS_ALLOWED_ACE *)pTempAce)->Header.AceFlags |= - (CONTAINER_INHERIT_ACE | OBJECT_INHERIT_ACE); - - /** - * STEP 15: To conform to the new Windows 2000 preferred order, - * we will now copy the rest of inherited ACEs from the - * old DACL to the new DACL. - */ - if (fDaclPresent && AclInfo.AceCount) { - - for (; - CurrentAceIndex < AclInfo.AceCount; - CurrentAceIndex++) { - - /** - * STEP 16: Get an ACE. - */ - if (!GNGetAce(pACL, CurrentAceIndex, &pTempAce)) { - goto end; - } - - /** - * STEP 17: Add the ACE to the new ACL. - */ - if (!GNAddAce(pNewACL, ACL_REVISION, MAXDWORD, pTempAce, - ((PACE_HEADER) pTempAce)->AceSize)) { - goto end; - } - } - } - - /** - * STEP 18: Set permissions - */ - if (GNSetNamedSecurityInfo((LPTSTR) lpszFileName, SE_FILE_OBJECT, - DACL_SECURITY_INFORMATION, NULL, NULL, pNewACL, NULL) != ERROR_SUCCESS) { - goto end; - } - - fResult = TRUE; - -end: - - /** - * STEP 19: Free allocated memory - */ - if (pUserSID) - HeapFree(GetProcessHeap(), 0, pUserSID); - - if (szDomain) - HeapFree(GetProcessHeap(), 0, szDomain); - - if (pFileSD) - HeapFree(GetProcessHeap(), 0, pFileSD); - - if (pNewACL) - HeapFree(GetProcessHeap(), 0, pNewACL); - - return fResult; -} - -char *winErrorStr(const char *prefix, int dwErr) -{ - char *err, *ret; - int mem; - - if (! FormatMessage(FORMAT_MESSAGE_ALLOCATE_BUFFER | FORMAT_MESSAGE_FROM_SYSTEM, - NULL, (DWORD) dwErr, MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT), (LPTSTR) &err, - 0, NULL )) - { - err = (char *) LocalAlloc (LMEM_FIXED | LMEM_ZEROINIT, 1); - } - - mem = strlen(err) + strlen(prefix) + 20; - ret = (char *) malloc(mem); - - snprintf(ret, mem, "%s: %s (#%u)", prefix, err, dwErr); - - LocalFree(err); - - return ret; -} - -} /* extern "C" */ - -#endif diff --git a/src/vpn/Makefile.am b/src/vpn/Makefile.am index 2af34f8..8b67a33 100644 --- a/src/vpn/Makefile.am +++ b/src/vpn/Makefile.am @@ -1,7 +1,8 @@ -INCLUDES = -I$(top_srcdir)/src/include +INCLUDES = -I$(top_srcdir)/src/include -I$(top_builddir)/src/include if MINGW - WINFLAGS = -Wl,--no-undefined -Wl,--export-all-symbols + WINFLAGS = -Wl,--no-undefined,--export-all-symbols + VPNBIN = gnunet-helper-vpn endif if USE_COVERAGE @@ -10,6 +11,8 @@ endif pkgcfgdir= $(pkgdatadir)/config.d/ +libexecdir= $(pkglibdir)/libexec/ + plugindir = $(libdir)/gnunet pkgcfg_DATA = \ @@ -18,15 +21,7 @@ pkgcfg_DATA = \ if LINUX VPNBIN = gnunet-helper-vpn install-exec-hook: - $(SUDO_BINARY) chown root:root $(bindir)/gnunet-helper-vpn || true - $(SUDO_BINARY) chmod u+s $(bindir)/gnunet-helper-vpn || true -if HAVE_MHD - VPN_TEST = \ - test_gnunet_vpn-4_to_6 \ - test_gnunet_vpn-6_to_4 \ - test_gnunet_vpn-6_over \ - test_gnunet_vpn-4_over -endif + $(top_srcdir)/src/vpn/install-vpn-helper.sh $(libexecdir) $(SUDO_BINARY) || true else install-exec-hook: endif @@ -36,23 +31,27 @@ lib_LTLIBRARIES = \ libgnunetvpn.la -bin_PROGRAMS = \ - $(VPNBIN) gnunet-service-vpn gnunet-vpn - - +libexec_PROGRAMS = \ + $(VPNBIN) \ + gnunet-service-vpn -check_PROGRAMS = $(VPN_TEST) +bin_PROGRAMS = \ + gnunet-vpn -if ENABLE_TEST_RUN -TESTS = $(check_PROGRAMS) +if MINGW + gnunet_helper_vpn_LDFLAGS = \ + -no-undefined -Wl,--export-all-symbols + + gnunet_helper_vpn_LDADD = \ + -lsetupapi -lnewdev -lshell32 -liconv -lstdc++ \ + -lcomdlg32 -lgdi32 -liphlpapi + + gnunet_helper_vpn_SOURCES = \ + gnunet-helper-vpn-windows.c +else + gnunet_helper_vpn_SOURCES = \ + gnunet-helper-vpn.c endif - -EXTRA_DIST = \ - test_gnunet_vpn.conf - -gnunet_helper_vpn_SOURCES = \ - gnunet-helper-vpn.c - gnunet_service_vpn_SOURCES = \ gnunet-service-vpn.c gnunet_service_vpn_LDADD = \ @@ -60,6 +59,7 @@ gnunet_service_vpn_LDADD = \ $(top_builddir)/src/tun/libgnunettun.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/mesh/libgnunetmesh.la \ + $(top_builddir)/src/regex/libgnunetregex.la \ $(GN_LIBINTL) gnunet_service_vpn_CFLAGS = \ -I$(top_srcdir)/src/exit $(CFLAGS) @@ -81,30 +81,3 @@ libgnunetvpn_la_LDFLAGS = \ $(GN_LIB_LDFLAGS) -test_gnunet_vpn_4_over_SOURCES = \ - test_gnunet_vpn.c -test_gnunet_vpn_4_over_LDADD = -lmicrohttpd @LIBCURL@ \ - $(top_builddir)/src/vpn/libgnunetvpn.la \ - $(top_builddir)/src/arm/libgnunetarm.la \ - $(top_builddir)/src/util/libgnunetutil.la - -test_gnunet_vpn_6_over_SOURCES = \ - test_gnunet_vpn.c -test_gnunet_vpn_6_over_LDADD = -lmicrohttpd @LIBCURL@ \ - $(top_builddir)/src/vpn/libgnunetvpn.la \ - $(top_builddir)/src/arm/libgnunetarm.la \ - $(top_builddir)/src/util/libgnunetutil.la - -test_gnunet_vpn_4_to_6_SOURCES = \ - test_gnunet_vpn.c -test_gnunet_vpn_4_to_6_LDADD = -lmicrohttpd @LIBCURL@ \ - $(top_builddir)/src/vpn/libgnunetvpn.la \ - $(top_builddir)/src/arm/libgnunetarm.la \ - $(top_builddir)/src/util/libgnunetutil.la - -test_gnunet_vpn_6_to_4_SOURCES = \ - test_gnunet_vpn.c -test_gnunet_vpn_6_to_4_LDADD = -lmicrohttpd @LIBCURL@ \ - $(top_builddir)/src/vpn/libgnunetvpn.la \ - $(top_builddir)/src/arm/libgnunetarm.la \ - $(top_builddir)/src/util/libgnunetutil.la diff --git a/src/vpn/Makefile.in b/src/vpn/Makefile.in index 54ca311..c753cfd 100644 --- a/src/vpn/Makefile.in +++ b/src/vpn/Makefile.in @@ -1,9 +1,9 @@ -# Makefile.in generated by automake 1.11.1 from Makefile.am. +# Makefile.in generated by automake 1.11.6 from Makefile.am. # @configure_input@ # Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, -# 2003, 2004, 2005, 2006, 2007, 2008, 2009 Free Software Foundation, -# Inc. +# 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Free Software +# Foundation, Inc. # This Makefile.in is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. @@ -18,6 +18,23 @@ VPATH = @srcdir@ +am__make_dryrun = \ + { \ + am__dry=no; \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + echo 'am--echo: ; @echo "AM" OK' | $(MAKE) -f - 2>/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } pkgdatadir = $(datadir)/@PACKAGE@ pkgincludedir = $(includedir)/@PACKAGE@ pkglibdir = $(libdir)/@PACKAGE@ @@ -37,23 +54,23 @@ POST_UNINSTALL = : build_triplet = @build@ host_triplet = @host@ target_triplet = @target@ -bin_PROGRAMS = $(am__EXEEXT_1) gnunet-service-vpn$(EXEEXT) \ - gnunet-vpn$(EXEEXT) -check_PROGRAMS = $(am__EXEEXT_2) +libexec_PROGRAMS = $(am__EXEEXT_1) gnunet-service-vpn$(EXEEXT) +bin_PROGRAMS = gnunet-vpn$(EXEEXT) subdir = src/vpn DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in \ $(srcdir)/vpn.conf.in ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 am__aclocal_m4_deps = $(top_srcdir)/m4/absolute-header.m4 \ $(top_srcdir)/m4/align.m4 $(top_srcdir)/m4/argz.m4 \ - $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/iconv.m4 \ - $(top_srcdir)/m4/lib-ld.m4 $(top_srcdir)/m4/lib-link.m4 \ - $(top_srcdir)/m4/lib-prefix.m4 $(top_srcdir)/m4/libcurl.m4 \ - $(top_srcdir)/m4/libgcrypt.m4 $(top_srcdir)/m4/libtool.m4 \ - $(top_srcdir)/m4/libunistring.m4 $(top_srcdir)/m4/ltdl.m4 \ - $(top_srcdir)/m4/ltoptions.m4 $(top_srcdir)/m4/ltsugar.m4 \ - $(top_srcdir)/m4/ltversion.m4 $(top_srcdir)/m4/lt~obsolete.m4 \ - $(top_srcdir)/m4/nls.m4 $(top_srcdir)/m4/po.m4 \ + $(top_srcdir)/m4/gettext.m4 $(top_srcdir)/m4/glib-2.0.m4 \ + $(top_srcdir)/m4/iconv.m4 $(top_srcdir)/m4/lib-ld.m4 \ + $(top_srcdir)/m4/lib-link.m4 $(top_srcdir)/m4/lib-prefix.m4 \ + $(top_srcdir)/m4/libcurl.m4 $(top_srcdir)/m4/libgcrypt.m4 \ + $(top_srcdir)/m4/libtool.m4 $(top_srcdir)/m4/libunistring.m4 \ + $(top_srcdir)/m4/ltdl.m4 $(top_srcdir)/m4/ltoptions.m4 \ + $(top_srcdir)/m4/ltsugar.m4 $(top_srcdir)/m4/ltversion.m4 \ + $(top_srcdir)/m4/lt~obsolete.m4 $(top_srcdir)/m4/nls.m4 \ + $(top_srcdir)/m4/pkg.m4 $(top_srcdir)/m4/po.m4 \ $(top_srcdir)/m4/progtest.m4 $(top_srcdir)/acinclude.m4 \ $(top_srcdir)/configure.ac am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ @@ -83,30 +100,41 @@ am__nobase_list = $(am__nobase_strip_setup); \ am__base_list = \ sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \ sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g' +am__uninstall_files_from_dir = { \ + test -z "$$files" \ + || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \ + || { echo " ( cd '$$dir' && rm -f" $$files ")"; \ + $(am__cd) "$$dir" && rm -f $$files; }; \ + } am__installdirs = "$(DESTDIR)$(libdir)" "$(DESTDIR)$(bindir)" \ - "$(DESTDIR)$(pkgcfgdir)" + "$(DESTDIR)$(libexecdir)" "$(DESTDIR)$(pkgcfgdir)" LTLIBRARIES = $(lib_LTLIBRARIES) libgnunetvpn_la_DEPENDENCIES = \ $(top_builddir)/src/util/libgnunetutil.la am_libgnunetvpn_la_OBJECTS = vpn_api.lo libgnunetvpn_la_OBJECTS = $(am_libgnunetvpn_la_OBJECTS) -AM_V_lt = $(am__v_lt_$(V)) -am__v_lt_ = $(am__v_lt_$(AM_DEFAULT_VERBOSITY)) +AM_V_lt = $(am__v_lt_@AM_V@) +am__v_lt_ = $(am__v_lt_@AM_DEFAULT_V@) am__v_lt_0 = --silent libgnunetvpn_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ $(AM_CFLAGS) $(CFLAGS) $(libgnunetvpn_la_LDFLAGS) $(LDFLAGS) \ -o $@ +@LINUX_FALSE@@MINGW_TRUE@am__EXEEXT_1 = gnunet-helper-vpn$(EXEEXT) @LINUX_TRUE@am__EXEEXT_1 = gnunet-helper-vpn$(EXEEXT) -@HAVE_MHD_TRUE@@LINUX_TRUE@am__EXEEXT_2 = \ -@HAVE_MHD_TRUE@@LINUX_TRUE@ test_gnunet_vpn-4_to_6$(EXEEXT) \ -@HAVE_MHD_TRUE@@LINUX_TRUE@ test_gnunet_vpn-6_to_4$(EXEEXT) \ -@HAVE_MHD_TRUE@@LINUX_TRUE@ test_gnunet_vpn-6_over$(EXEEXT) \ -@HAVE_MHD_TRUE@@LINUX_TRUE@ test_gnunet_vpn-4_over$(EXEEXT) -PROGRAMS = $(bin_PROGRAMS) -am_gnunet_helper_vpn_OBJECTS = gnunet-helper-vpn.$(OBJEXT) +PROGRAMS = $(bin_PROGRAMS) $(libexec_PROGRAMS) +am__gnunet_helper_vpn_SOURCES_DIST = gnunet-helper-vpn.c \ + gnunet-helper-vpn-windows.c +@MINGW_FALSE@am_gnunet_helper_vpn_OBJECTS = \ +@MINGW_FALSE@ gnunet-helper-vpn.$(OBJEXT) +@MINGW_TRUE@am_gnunet_helper_vpn_OBJECTS = \ +@MINGW_TRUE@ gnunet-helper-vpn-windows.$(OBJEXT) gnunet_helper_vpn_OBJECTS = $(am_gnunet_helper_vpn_OBJECTS) -gnunet_helper_vpn_LDADD = $(LDADD) +gnunet_helper_vpn_DEPENDENCIES = +gnunet_helper_vpn_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ + $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ + $(AM_CFLAGS) $(CFLAGS) $(gnunet_helper_vpn_LDFLAGS) $(LDFLAGS) \ + -o $@ am_gnunet_service_vpn_OBJECTS = \ gnunet_service_vpn-gnunet-service-vpn.$(OBJEXT) gnunet_service_vpn_OBJECTS = $(am_gnunet_service_vpn_OBJECTS) @@ -116,6 +144,7 @@ gnunet_service_vpn_DEPENDENCIES = \ $(top_builddir)/src/tun/libgnunettun.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/mesh/libgnunetmesh.la \ + $(top_builddir)/src/regex/libgnunetregex.la \ $(am__DEPENDENCIES_1) gnunet_service_vpn_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ @@ -123,30 +152,6 @@ gnunet_service_vpn_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ $(LDFLAGS) -o $@ am_gnunet_vpn_OBJECTS = gnunet-vpn.$(OBJEXT) gnunet_vpn_OBJECTS = $(am_gnunet_vpn_OBJECTS) -am_test_gnunet_vpn_4_over_OBJECTS = test_gnunet_vpn.$(OBJEXT) -test_gnunet_vpn_4_over_OBJECTS = $(am_test_gnunet_vpn_4_over_OBJECTS) -test_gnunet_vpn_4_over_DEPENDENCIES = \ - $(top_builddir)/src/vpn/libgnunetvpn.la \ - $(top_builddir)/src/arm/libgnunetarm.la \ - $(top_builddir)/src/util/libgnunetutil.la -am_test_gnunet_vpn_4_to_6_OBJECTS = test_gnunet_vpn.$(OBJEXT) -test_gnunet_vpn_4_to_6_OBJECTS = $(am_test_gnunet_vpn_4_to_6_OBJECTS) -test_gnunet_vpn_4_to_6_DEPENDENCIES = \ - $(top_builddir)/src/vpn/libgnunetvpn.la \ - $(top_builddir)/src/arm/libgnunetarm.la \ - $(top_builddir)/src/util/libgnunetutil.la -am_test_gnunet_vpn_6_over_OBJECTS = test_gnunet_vpn.$(OBJEXT) -test_gnunet_vpn_6_over_OBJECTS = $(am_test_gnunet_vpn_6_over_OBJECTS) -test_gnunet_vpn_6_over_DEPENDENCIES = \ - $(top_builddir)/src/vpn/libgnunetvpn.la \ - $(top_builddir)/src/arm/libgnunetarm.la \ - $(top_builddir)/src/util/libgnunetutil.la -am_test_gnunet_vpn_6_to_4_OBJECTS = test_gnunet_vpn.$(OBJEXT) -test_gnunet_vpn_6_to_4_OBJECTS = $(am_test_gnunet_vpn_6_to_4_OBJECTS) -test_gnunet_vpn_6_to_4_DEPENDENCIES = \ - $(top_builddir)/src/vpn/libgnunetvpn.la \ - $(top_builddir)/src/arm/libgnunetarm.la \ - $(top_builddir)/src/util/libgnunetutil.la DEFAULT_INCLUDES = -I.@am__isrc@ -I$(top_builddir) depcomp = $(SHELL) $(top_srcdir)/depcomp am__depfiles_maybe = depfiles @@ -157,39 +162,35 @@ LTCOMPILE = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) \ $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) \ $(AM_CFLAGS) $(CFLAGS) -AM_V_CC = $(am__v_CC_$(V)) -am__v_CC_ = $(am__v_CC_$(AM_DEFAULT_VERBOSITY)) +AM_V_CC = $(am__v_CC_@AM_V@) +am__v_CC_ = $(am__v_CC_@AM_DEFAULT_V@) am__v_CC_0 = @echo " CC " $@; -AM_V_at = $(am__v_at_$(V)) -am__v_at_ = $(am__v_at_$(AM_DEFAULT_VERBOSITY)) +AM_V_at = $(am__v_at_@AM_V@) +am__v_at_ = $(am__v_at_@AM_DEFAULT_V@) am__v_at_0 = @ CCLD = $(CC) LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ $(AM_LDFLAGS) $(LDFLAGS) -o $@ -AM_V_CCLD = $(am__v_CCLD_$(V)) -am__v_CCLD_ = $(am__v_CCLD_$(AM_DEFAULT_VERBOSITY)) +AM_V_CCLD = $(am__v_CCLD_@AM_V@) +am__v_CCLD_ = $(am__v_CCLD_@AM_DEFAULT_V@) am__v_CCLD_0 = @echo " CCLD " $@; -AM_V_GEN = $(am__v_GEN_$(V)) -am__v_GEN_ = $(am__v_GEN_$(AM_DEFAULT_VERBOSITY)) +AM_V_GEN = $(am__v_GEN_@AM_V@) +am__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@) am__v_GEN_0 = @echo " GEN " $@; SOURCES = $(libgnunetvpn_la_SOURCES) $(gnunet_helper_vpn_SOURCES) \ - $(gnunet_service_vpn_SOURCES) $(gnunet_vpn_SOURCES) \ - $(test_gnunet_vpn_4_over_SOURCES) \ - $(test_gnunet_vpn_4_to_6_SOURCES) \ - $(test_gnunet_vpn_6_over_SOURCES) \ - $(test_gnunet_vpn_6_to_4_SOURCES) -DIST_SOURCES = $(libgnunetvpn_la_SOURCES) $(gnunet_helper_vpn_SOURCES) \ - $(gnunet_service_vpn_SOURCES) $(gnunet_vpn_SOURCES) \ - $(test_gnunet_vpn_4_over_SOURCES) \ - $(test_gnunet_vpn_4_to_6_SOURCES) \ - $(test_gnunet_vpn_6_over_SOURCES) \ - $(test_gnunet_vpn_6_to_4_SOURCES) + $(gnunet_service_vpn_SOURCES) $(gnunet_vpn_SOURCES) +DIST_SOURCES = $(libgnunetvpn_la_SOURCES) \ + $(am__gnunet_helper_vpn_SOURCES_DIST) \ + $(gnunet_service_vpn_SOURCES) $(gnunet_vpn_SOURCES) +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac DATA = $(pkgcfg_DATA) ETAGS = etags CTAGS = ctags -am__tty_colors = \ -red=; grn=; lgn=; blu=; std= DISTFILES = $(DIST_COMMON) $(DIST_SOURCES) $(TEXINFOS) $(EXTRA_DIST) ACLOCAL = @ACLOCAL@ AMTAR = @AMTAR@ @@ -226,6 +227,10 @@ EXEEXT = @EXEEXT@ EXT_LIBS = @EXT_LIBS@ EXT_LIB_PATH = @EXT_LIB_PATH@ FGREP = @FGREP@ +GLIB_CFLAGS = @GLIB_CFLAGS@ +GLIB_GENMARSHAL = @GLIB_GENMARSHAL@ +GLIB_LIBS = @GLIB_LIBS@ +GLIB_MKENUMS = @GLIB_MKENUMS@ GMSGFMT = @GMSGFMT@ GMSGFMT_015 = @GMSGFMT_015@ GNUNETDNS_GROUP = @GNUNETDNS_GROUP@ @@ -236,6 +241,7 @@ GN_LIBINTL = @GN_LIBINTL@ GN_LIB_LDFLAGS = @GN_LIB_LDFLAGS@ GN_PLUGIN_LDFLAGS = @GN_PLUGIN_LDFLAGS@ GN_USER_HOME_DIR = @GN_USER_HOME_DIR@ +GOBJECT_QUERY = @GOBJECT_QUERY@ GREP = @GREP@ HAVE_LIBUNISTRING = @HAVE_LIBUNISTRING@ INCLTDL = @INCLTDL@ @@ -258,6 +264,8 @@ LIBCURL_CPPFLAGS = @LIBCURL_CPPFLAGS@ LIBGCRYPT_CFLAGS = @LIBGCRYPT_CFLAGS@ LIBGCRYPT_CONFIG = @LIBGCRYPT_CONFIG@ LIBGCRYPT_LIBS = @LIBGCRYPT_LIBS@ +LIBGTOP_CFLAGS = @LIBGTOP_CFLAGS@ +LIBGTOP_LIBS = @LIBGTOP_LIBS@ LIBICONV = @LIBICONV@ LIBINTL = @LIBINTL@ LIBLTDL = @LIBLTDL@ @@ -279,6 +287,7 @@ LT_CONFIG_H = @LT_CONFIG_H@ LT_DLLOADERS = @LT_DLLOADERS@ LT_DLPREOPEN = @LT_DLPREOPEN@ MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ MKDIR_P = @MKDIR_P@ MONKEYPREFIX = @MONKEYPREFIX@ MSGFMT = @MSGFMT@ @@ -288,6 +297,7 @@ MYSQL_CPPFLAGS = @MYSQL_CPPFLAGS@ MYSQL_LDFLAGS = @MYSQL_LDFLAGS@ NM = @NM@ NMEDIT = @NMEDIT@ +NSS_DIR = @NSS_DIR@ OBJC = @OBJC@ OBJCDEPMODE = @OBJCDEPMODE@ OBJCFLAGS = @OBJCFLAGS@ @@ -303,6 +313,7 @@ PACKAGE_TARNAME = @PACKAGE_TARNAME@ PACKAGE_URL = @PACKAGE_URL@ PACKAGE_VERSION = @PACKAGE_VERSION@ PATH_SEPARATOR = @PATH_SEPARATOR@ +PKG_CONFIG = @PKG_CONFIG@ POSTGRES_CPPFLAGS = @POSTGRES_CPPFLAGS@ POSTGRES_LDFLAGS = @POSTGRES_LDFLAGS@ POSUB = @POSUB@ @@ -334,6 +345,7 @@ abs_builddir = @abs_builddir@ abs_srcdir = @abs_srcdir@ abs_top_builddir = @abs_top_builddir@ abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ ac_ct_CC = @ac_ct_CC@ ac_ct_CXX = @ac_ct_CXX@ ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ @@ -356,6 +368,7 @@ datarootdir = @datarootdir@ docdir = @docdir@ dvidir = @dvidir@ exec_prefix = @exec_prefix@ +gitcommand = @gitcommand@ host = @host@ host_alias = @host_alias@ host_cpu = @host_cpu@ @@ -366,10 +379,9 @@ includedir = @includedir@ infodir = @infodir@ install_sh = @install_sh@ libdir = @libdir@ -libexecdir = @libexecdir@ +libexecdir = $(pkglibdir)/libexec/ localedir = @localedir@ localstatedir = @localstatedir@ -lt_ECHO = @lt_ECHO@ ltdl_LIBOBJS = @ltdl_LIBOBJS@ ltdl_LTLIBOBJS = @ltdl_LTLIBOBJS@ mandir = @mandir@ @@ -387,6 +399,7 @@ sbindir = @sbindir@ sharedstatedir = @sharedstatedir@ srcdir = @srcdir@ subdirs = @subdirs@ +svnversioncommand = @svnversioncommand@ sys_symbol_underscore = @sys_symbol_underscore@ sysconfdir = @sysconfdir@ target = @target@ @@ -397,30 +410,31 @@ target_vendor = @target_vendor@ top_build_prefix = @top_build_prefix@ top_builddir = @top_builddir@ top_srcdir = @top_srcdir@ -INCLUDES = -I$(top_srcdir)/src/include -@MINGW_TRUE@WINFLAGS = -Wl,--no-undefined -Wl,--export-all-symbols +INCLUDES = -I$(top_srcdir)/src/include -I$(top_builddir)/src/include +@MINGW_TRUE@WINFLAGS = -Wl,--no-undefined,--export-all-symbols +@LINUX_TRUE@VPNBIN = gnunet-helper-vpn +@MINGW_TRUE@VPNBIN = gnunet-helper-vpn @USE_COVERAGE_TRUE@AM_CFLAGS = --coverage -O0 pkgcfgdir = $(pkgdatadir)/config.d/ plugindir = $(libdir)/gnunet pkgcfg_DATA = \ vpn.conf -@LINUX_TRUE@VPNBIN = gnunet-helper-vpn -@HAVE_MHD_TRUE@@LINUX_TRUE@VPN_TEST = \ -@HAVE_MHD_TRUE@@LINUX_TRUE@ test_gnunet_vpn-4_to_6 \ -@HAVE_MHD_TRUE@@LINUX_TRUE@ test_gnunet_vpn-6_to_4 \ -@HAVE_MHD_TRUE@@LINUX_TRUE@ test_gnunet_vpn-6_over \ -@HAVE_MHD_TRUE@@LINUX_TRUE@ test_gnunet_vpn-4_over - lib_LTLIBRARIES = \ libgnunetvpn.la -@ENABLE_TEST_RUN_TRUE@TESTS = $(check_PROGRAMS) -EXTRA_DIST = \ - test_gnunet_vpn.conf +@MINGW_TRUE@gnunet_helper_vpn_LDFLAGS = \ +@MINGW_TRUE@ -no-undefined -Wl,--export-all-symbols + +@MINGW_TRUE@gnunet_helper_vpn_LDADD = \ +@MINGW_TRUE@ -lsetupapi -lnewdev -lshell32 -liconv -lstdc++ \ +@MINGW_TRUE@ -lcomdlg32 -lgdi32 -liphlpapi -gnunet_helper_vpn_SOURCES = \ - gnunet-helper-vpn.c +@MINGW_FALSE@gnunet_helper_vpn_SOURCES = \ +@MINGW_FALSE@ gnunet-helper-vpn.c + +@MINGW_TRUE@gnunet_helper_vpn_SOURCES = \ +@MINGW_TRUE@ gnunet-helper-vpn-windows.c gnunet_service_vpn_SOURCES = \ gnunet-service-vpn.c @@ -430,6 +444,7 @@ gnunet_service_vpn_LDADD = \ $(top_builddir)/src/tun/libgnunettun.la \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/mesh/libgnunetmesh.la \ + $(top_builddir)/src/regex/libgnunetregex.la \ $(GN_LIBINTL) gnunet_service_vpn_CFLAGS = \ @@ -455,38 +470,6 @@ libgnunetvpn_la_LIBADD = \ libgnunetvpn_la_LDFLAGS = \ $(GN_LIB_LDFLAGS) -test_gnunet_vpn_4_over_SOURCES = \ - test_gnunet_vpn.c - -test_gnunet_vpn_4_over_LDADD = -lmicrohttpd @LIBCURL@ \ - $(top_builddir)/src/vpn/libgnunetvpn.la \ - $(top_builddir)/src/arm/libgnunetarm.la \ - $(top_builddir)/src/util/libgnunetutil.la - -test_gnunet_vpn_6_over_SOURCES = \ - test_gnunet_vpn.c - -test_gnunet_vpn_6_over_LDADD = -lmicrohttpd @LIBCURL@ \ - $(top_builddir)/src/vpn/libgnunetvpn.la \ - $(top_builddir)/src/arm/libgnunetarm.la \ - $(top_builddir)/src/util/libgnunetutil.la - -test_gnunet_vpn_4_to_6_SOURCES = \ - test_gnunet_vpn.c - -test_gnunet_vpn_4_to_6_LDADD = -lmicrohttpd @LIBCURL@ \ - $(top_builddir)/src/vpn/libgnunetvpn.la \ - $(top_builddir)/src/arm/libgnunetarm.la \ - $(top_builddir)/src/util/libgnunetutil.la - -test_gnunet_vpn_6_to_4_SOURCES = \ - test_gnunet_vpn.c - -test_gnunet_vpn_6_to_4_LDADD = -lmicrohttpd @LIBCURL@ \ - $(top_builddir)/src/vpn/libgnunetvpn.la \ - $(top_builddir)/src/arm/libgnunetarm.la \ - $(top_builddir)/src/util/libgnunetutil.la - all: all-am .SUFFIXES: @@ -525,7 +508,6 @@ vpn.conf: $(top_builddir)/config.status $(srcdir)/vpn.conf.in cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ install-libLTLIBRARIES: $(lib_LTLIBRARIES) @$(NORMAL_INSTALL) - test -z "$(libdir)" || $(MKDIR_P) "$(DESTDIR)$(libdir)" @list='$(lib_LTLIBRARIES)'; test -n "$(libdir)" || list=; \ list2=; for p in $$list; do \ if test -f $$p; then \ @@ -533,6 +515,8 @@ install-libLTLIBRARIES: $(lib_LTLIBRARIES) else :; fi; \ done; \ test -z "$$list2" || { \ + echo " $(MKDIR_P) '$(DESTDIR)$(libdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libdir)" || exit 1; \ echo " $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 '$(DESTDIR)$(libdir)'"; \ $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 "$(DESTDIR)$(libdir)"; \ } @@ -554,12 +538,15 @@ clean-libLTLIBRARIES: echo "rm -f \"$${dir}/so_locations\""; \ rm -f "$${dir}/so_locations"; \ done -libgnunetvpn.la: $(libgnunetvpn_la_OBJECTS) $(libgnunetvpn_la_DEPENDENCIES) +libgnunetvpn.la: $(libgnunetvpn_la_OBJECTS) $(libgnunetvpn_la_DEPENDENCIES) $(EXTRA_libgnunetvpn_la_DEPENDENCIES) $(AM_V_CCLD)$(libgnunetvpn_la_LINK) -rpath $(libdir) $(libgnunetvpn_la_OBJECTS) $(libgnunetvpn_la_LIBADD) $(LIBS) install-binPROGRAMS: $(bin_PROGRAMS) @$(NORMAL_INSTALL) - test -z "$(bindir)" || $(MKDIR_P) "$(DESTDIR)$(bindir)" @list='$(bin_PROGRAMS)'; test -n "$(bindir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(bindir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(bindir)" || exit 1; \ + fi; \ for p in $$list; do echo "$$p $$p"; done | \ sed 's/$(EXEEXT)$$//' | \ while read p p1; do if test -f $$p || test -f $$p1; \ @@ -599,36 +586,61 @@ clean-binPROGRAMS: list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ echo " rm -f" $$list; \ rm -f $$list +install-libexecPROGRAMS: $(libexec_PROGRAMS) + @$(NORMAL_INSTALL) + @list='$(libexec_PROGRAMS)'; test -n "$(libexecdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(libexecdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(libexecdir)" || exit 1; \ + fi; \ + for p in $$list; do echo "$$p $$p"; done | \ + sed 's/$(EXEEXT)$$//' | \ + while read p p1; do if test -f $$p || test -f $$p1; \ + then echo "$$p"; echo "$$p"; else :; fi; \ + done | \ + sed -e 'p;s,.*/,,;n;h' -e 's|.*|.|' \ + -e 'p;x;s,.*/,,;s/$(EXEEXT)$$//;$(transform);s/$$/$(EXEEXT)/' | \ + sed 'N;N;N;s,\n, ,g' | \ + $(AWK) 'BEGIN { files["."] = ""; dirs["."] = 1 } \ + { d=$$3; if (dirs[d] != 1) { print "d", d; dirs[d] = 1 } \ + if ($$2 == $$4) files[d] = files[d] " " $$1; \ + else { print "f", $$3 "/" $$4, $$1; } } \ + END { for (d in files) print "f", d, files[d] }' | \ + while read type dir files; do \ + if test "$$dir" = .; then dir=; else dir=/$$dir; fi; \ + test -z "$$files" || { \ + echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files '$(DESTDIR)$(libexecdir)$$dir'"; \ + $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files "$(DESTDIR)$(libexecdir)$$dir" || exit $$?; \ + } \ + ; done + +uninstall-libexecPROGRAMS: + @$(NORMAL_UNINSTALL) + @list='$(libexec_PROGRAMS)'; test -n "$(libexecdir)" || list=; \ + files=`for p in $$list; do echo "$$p"; done | \ + sed -e 'h;s,^.*/,,;s/$(EXEEXT)$$//;$(transform)' \ + -e 's/$$/$(EXEEXT)/' `; \ + test -n "$$list" || exit 0; \ + echo " ( cd '$(DESTDIR)$(libexecdir)' && rm -f" $$files ")"; \ + cd "$(DESTDIR)$(libexecdir)" && rm -f $$files -clean-checkPROGRAMS: - @list='$(check_PROGRAMS)'; test -n "$$list" || exit 0; \ +clean-libexecPROGRAMS: + @list='$(libexec_PROGRAMS)'; test -n "$$list" || exit 0; \ echo " rm -f" $$list; \ rm -f $$list || exit $$?; \ test -n "$(EXEEXT)" || exit 0; \ list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ echo " rm -f" $$list; \ rm -f $$list -gnunet-helper-vpn$(EXEEXT): $(gnunet_helper_vpn_OBJECTS) $(gnunet_helper_vpn_DEPENDENCIES) +gnunet-helper-vpn$(EXEEXT): $(gnunet_helper_vpn_OBJECTS) $(gnunet_helper_vpn_DEPENDENCIES) $(EXTRA_gnunet_helper_vpn_DEPENDENCIES) @rm -f gnunet-helper-vpn$(EXEEXT) - $(AM_V_CCLD)$(LINK) $(gnunet_helper_vpn_OBJECTS) $(gnunet_helper_vpn_LDADD) $(LIBS) -gnunet-service-vpn$(EXEEXT): $(gnunet_service_vpn_OBJECTS) $(gnunet_service_vpn_DEPENDENCIES) + $(AM_V_CCLD)$(gnunet_helper_vpn_LINK) $(gnunet_helper_vpn_OBJECTS) $(gnunet_helper_vpn_LDADD) $(LIBS) +gnunet-service-vpn$(EXEEXT): $(gnunet_service_vpn_OBJECTS) $(gnunet_service_vpn_DEPENDENCIES) $(EXTRA_gnunet_service_vpn_DEPENDENCIES) @rm -f gnunet-service-vpn$(EXEEXT) $(AM_V_CCLD)$(gnunet_service_vpn_LINK) $(gnunet_service_vpn_OBJECTS) $(gnunet_service_vpn_LDADD) $(LIBS) -gnunet-vpn$(EXEEXT): $(gnunet_vpn_OBJECTS) $(gnunet_vpn_DEPENDENCIES) +gnunet-vpn$(EXEEXT): $(gnunet_vpn_OBJECTS) $(gnunet_vpn_DEPENDENCIES) $(EXTRA_gnunet_vpn_DEPENDENCIES) @rm -f gnunet-vpn$(EXEEXT) $(AM_V_CCLD)$(LINK) $(gnunet_vpn_OBJECTS) $(gnunet_vpn_LDADD) $(LIBS) -test_gnunet_vpn-4_over$(EXEEXT): $(test_gnunet_vpn_4_over_OBJECTS) $(test_gnunet_vpn_4_over_DEPENDENCIES) - @rm -f test_gnunet_vpn-4_over$(EXEEXT) - $(AM_V_CCLD)$(LINK) $(test_gnunet_vpn_4_over_OBJECTS) $(test_gnunet_vpn_4_over_LDADD) $(LIBS) -test_gnunet_vpn-4_to_6$(EXEEXT): $(test_gnunet_vpn_4_to_6_OBJECTS) $(test_gnunet_vpn_4_to_6_DEPENDENCIES) - @rm -f test_gnunet_vpn-4_to_6$(EXEEXT) - $(AM_V_CCLD)$(LINK) $(test_gnunet_vpn_4_to_6_OBJECTS) $(test_gnunet_vpn_4_to_6_LDADD) $(LIBS) -test_gnunet_vpn-6_over$(EXEEXT): $(test_gnunet_vpn_6_over_OBJECTS) $(test_gnunet_vpn_6_over_DEPENDENCIES) - @rm -f test_gnunet_vpn-6_over$(EXEEXT) - $(AM_V_CCLD)$(LINK) $(test_gnunet_vpn_6_over_OBJECTS) $(test_gnunet_vpn_6_over_LDADD) $(LIBS) -test_gnunet_vpn-6_to_4$(EXEEXT): $(test_gnunet_vpn_6_to_4_OBJECTS) $(test_gnunet_vpn_6_to_4_DEPENDENCIES) - @rm -f test_gnunet_vpn-6_to_4$(EXEEXT) - $(AM_V_CCLD)$(LINK) $(test_gnunet_vpn_6_to_4_OBJECTS) $(test_gnunet_vpn_6_to_4_LDADD) $(LIBS) mostlyclean-compile: -rm -f *.$(OBJEXT) @@ -636,51 +648,46 @@ mostlyclean-compile: distclean-compile: -rm -f *.tab.c +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-helper-vpn-windows.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-helper-vpn.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet-vpn.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/gnunet_service_vpn-gnunet-service-vpn.Po@am__quote@ -@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/test_gnunet_vpn.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/vpn_api.Plo@am__quote@ .c.o: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c $< .c.obj: @am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'` @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(COMPILE) -c `$(CYGPATH_W) '$<'` +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c `$(CYGPATH_W) '$<'` .c.lo: @am__fastdepCC_TRUE@ $(AM_V_CC)$(LTCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(LTCOMPILE) -c -o $@ $< +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LTCOMPILE) -c -o $@ $< gnunet_service_vpn-gnunet-service-vpn.o: gnunet-service-vpn.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_vpn_CFLAGS) $(CFLAGS) -MT gnunet_service_vpn-gnunet-service-vpn.o -MD -MP -MF $(DEPDIR)/gnunet_service_vpn-gnunet-service-vpn.Tpo -c -o gnunet_service_vpn-gnunet-service-vpn.o `test -f 'gnunet-service-vpn.c' || echo '$(srcdir)/'`gnunet-service-vpn.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/gnunet_service_vpn-gnunet-service-vpn.Tpo $(DEPDIR)/gnunet_service_vpn-gnunet-service-vpn.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='gnunet-service-vpn.c' object='gnunet_service_vpn-gnunet-service-vpn.o' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='gnunet-service-vpn.c' object='gnunet_service_vpn-gnunet-service-vpn.o' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_vpn_CFLAGS) $(CFLAGS) -c -o gnunet_service_vpn-gnunet-service-vpn.o `test -f 'gnunet-service-vpn.c' || echo '$(srcdir)/'`gnunet-service-vpn.c +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_vpn_CFLAGS) $(CFLAGS) -c -o gnunet_service_vpn-gnunet-service-vpn.o `test -f 'gnunet-service-vpn.c' || echo '$(srcdir)/'`gnunet-service-vpn.c gnunet_service_vpn-gnunet-service-vpn.obj: gnunet-service-vpn.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_vpn_CFLAGS) $(CFLAGS) -MT gnunet_service_vpn-gnunet-service-vpn.obj -MD -MP -MF $(DEPDIR)/gnunet_service_vpn-gnunet-service-vpn.Tpo -c -o gnunet_service_vpn-gnunet-service-vpn.obj `if test -f 'gnunet-service-vpn.c'; then $(CYGPATH_W) 'gnunet-service-vpn.c'; else $(CYGPATH_W) '$(srcdir)/gnunet-service-vpn.c'; fi` @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/gnunet_service_vpn-gnunet-service-vpn.Tpo $(DEPDIR)/gnunet_service_vpn-gnunet-service-vpn.Po -@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@ -@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='gnunet-service-vpn.c' object='gnunet_service_vpn-gnunet-service-vpn.obj' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='gnunet-service-vpn.c' object='gnunet_service_vpn-gnunet-service-vpn.obj' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ -@am__fastdepCC_FALSE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_vpn_CFLAGS) $(CFLAGS) -c -o gnunet_service_vpn-gnunet-service-vpn.obj `if test -f 'gnunet-service-vpn.c'; then $(CYGPATH_W) 'gnunet-service-vpn.c'; else $(CYGPATH_W) '$(srcdir)/gnunet-service-vpn.c'; fi` +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(gnunet_service_vpn_CFLAGS) $(CFLAGS) -c -o gnunet_service_vpn-gnunet-service-vpn.obj `if test -f 'gnunet-service-vpn.c'; then $(CYGPATH_W) 'gnunet-service-vpn.c'; else $(CYGPATH_W) '$(srcdir)/gnunet-service-vpn.c'; fi` mostlyclean-libtool: -rm -f *.lo @@ -689,8 +696,11 @@ clean-libtool: -rm -rf .libs _libs install-pkgcfgDATA: $(pkgcfg_DATA) @$(NORMAL_INSTALL) - test -z "$(pkgcfgdir)" || $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" @list='$(pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(pkgcfgdir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(pkgcfgdir)" || exit 1; \ + fi; \ for p in $$list; do \ if test -f "$$p"; then d=; else d="$(srcdir)/"; fi; \ echo "$$d$$p"; \ @@ -704,9 +714,7 @@ uninstall-pkgcfgDATA: @$(NORMAL_UNINSTALL) @list='$(pkgcfg_DATA)'; test -n "$(pkgcfgdir)" || list=; \ files=`for p in $$list; do echo $$p; done | sed -e 's|^.*/||'`; \ - test -n "$$files" || exit 0; \ - echo " ( cd '$(DESTDIR)$(pkgcfgdir)' && rm -f" $$files ")"; \ - cd "$(DESTDIR)$(pkgcfgdir)" && rm -f $$files + dir='$(DESTDIR)$(pkgcfgdir)'; $(am__uninstall_files_from_dir) ID: $(HEADERS) $(SOURCES) $(LISP) $(TAGS_FILES) list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ @@ -760,98 +768,6 @@ GTAGS: distclean-tags: -rm -f TAGS ID GTAGS GRTAGS GSYMS GPATH tags -check-TESTS: $(TESTS) - @failed=0; all=0; xfail=0; xpass=0; skip=0; \ - srcdir=$(srcdir); export srcdir; \ - list=' $(TESTS) '; \ - $(am__tty_colors); \ - if test -n "$$list"; then \ - for tst in $$list; do \ - if test -f ./$$tst; then dir=./; \ - elif test -f $$tst; then dir=; \ - else dir="$(srcdir)/"; fi; \ - if $(TESTS_ENVIRONMENT) $${dir}$$tst; then \ - all=`expr $$all + 1`; \ - case " $(XFAIL_TESTS) " in \ - *[\ \ ]$$tst[\ \ ]*) \ - xpass=`expr $$xpass + 1`; \ - failed=`expr $$failed + 1`; \ - col=$$red; res=XPASS; \ - ;; \ - *) \ - col=$$grn; res=PASS; \ - ;; \ - esac; \ - elif test $$? -ne 77; then \ - all=`expr $$all + 1`; \ - case " $(XFAIL_TESTS) " in \ - *[\ \ ]$$tst[\ \ ]*) \ - xfail=`expr $$xfail + 1`; \ - col=$$lgn; res=XFAIL; \ - ;; \ - *) \ - failed=`expr $$failed + 1`; \ - col=$$red; res=FAIL; \ - ;; \ - esac; \ - else \ - skip=`expr $$skip + 1`; \ - col=$$blu; res=SKIP; \ - fi; \ - echo "$${col}$$res$${std}: $$tst"; \ - done; \ - if test "$$all" -eq 1; then \ - tests="test"; \ - All=""; \ - else \ - tests="tests"; \ - All="All "; \ - fi; \ - if test "$$failed" -eq 0; then \ - if test "$$xfail" -eq 0; then \ - banner="$$All$$all $$tests passed"; \ - else \ - if test "$$xfail" -eq 1; then failures=failure; else failures=failures; fi; \ - banner="$$All$$all $$tests behaved as expected ($$xfail expected $$failures)"; \ - fi; \ - else \ - if test "$$xpass" -eq 0; then \ - banner="$$failed of $$all $$tests failed"; \ - else \ - if test "$$xpass" -eq 1; then passes=pass; else passes=passes; fi; \ - banner="$$failed of $$all $$tests did not behave as expected ($$xpass unexpected $$passes)"; \ - fi; \ - fi; \ - dashes="$$banner"; \ - skipped=""; \ - if test "$$skip" -ne 0; then \ - if test "$$skip" -eq 1; then \ - skipped="($$skip test was not run)"; \ - else \ - skipped="($$skip tests were not run)"; \ - fi; \ - test `echo "$$skipped" | wc -c` -le `echo "$$banner" | wc -c` || \ - dashes="$$skipped"; \ - fi; \ - report=""; \ - if test "$$failed" -ne 0 && test -n "$(PACKAGE_BUGREPORT)"; then \ - report="Please report to $(PACKAGE_BUGREPORT)"; \ - test `echo "$$report" | wc -c` -le `echo "$$banner" | wc -c` || \ - dashes="$$report"; \ - fi; \ - dashes=`echo "$$dashes" | sed s/./=/g`; \ - if test "$$failed" -eq 0; then \ - echo "$$grn$$dashes"; \ - else \ - echo "$$red$$dashes"; \ - fi; \ - echo "$$banner"; \ - test -z "$$skipped" || echo "$$skipped"; \ - test -z "$$report" || echo "$$report"; \ - echo "$$dashes$$std"; \ - test "$$failed" -eq 0; \ - else :; fi - distdir: $(DISTFILES) @srcdirstrip=`echo "$(srcdir)" | sed 's/[].[^$$\\*]/\\\\&/g'`; \ topsrcdirstrip=`echo "$(top_srcdir)" | sed 's/[].[^$$\\*]/\\\\&/g'`; \ @@ -883,14 +799,12 @@ distdir: $(DISTFILES) fi; \ done check-am: all-am - $(MAKE) $(AM_MAKEFLAGS) $(check_PROGRAMS) - $(MAKE) $(AM_MAKEFLAGS) check-TESTS check: check-am all-am: Makefile $(LTLIBRARIES) $(PROGRAMS) $(DATA) install-binPROGRAMS: install-libLTLIBRARIES installdirs: - for dir in "$(DESTDIR)$(libdir)" "$(DESTDIR)$(bindir)" "$(DESTDIR)$(pkgcfgdir)"; do \ + for dir in "$(DESTDIR)$(libdir)" "$(DESTDIR)$(bindir)" "$(DESTDIR)$(libexecdir)" "$(DESTDIR)$(pkgcfgdir)"; do \ test -z "$$dir" || $(MKDIR_P) "$$dir"; \ done install: install-am @@ -903,10 +817,15 @@ install-am: all-am installcheck: installcheck-am install-strip: - $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ - install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ - `test -z '$(STRIP)' || \ - echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi mostlyclean-generic: clean-generic: @@ -920,8 +839,8 @@ maintainer-clean-generic: @echo "it deletes files that may require special tools to rebuild." clean: clean-am -clean-am: clean-binPROGRAMS clean-checkPROGRAMS clean-generic \ - clean-libLTLIBRARIES clean-libtool mostlyclean-am +clean-am: clean-binPROGRAMS clean-generic clean-libLTLIBRARIES \ + clean-libexecPROGRAMS clean-libtool mostlyclean-am distclean: distclean-am -rm -rf ./$(DEPDIR) @@ -947,7 +866,8 @@ install-dvi: install-dvi-am install-dvi-am: -install-exec-am: install-binPROGRAMS install-libLTLIBRARIES +install-exec-am: install-binPROGRAMS install-libLTLIBRARIES \ + install-libexecPROGRAMS @$(NORMAL_INSTALL) $(MAKE) $(AM_MAKEFLAGS) install-exec-hook install-html: install-html-am @@ -989,30 +909,29 @@ ps: ps-am ps-am: uninstall-am: uninstall-binPROGRAMS uninstall-libLTLIBRARIES \ - uninstall-pkgcfgDATA - -.MAKE: check-am install-am install-exec-am install-strip - -.PHONY: CTAGS GTAGS all all-am check check-TESTS check-am clean \ - clean-binPROGRAMS clean-checkPROGRAMS clean-generic \ - clean-libLTLIBRARIES clean-libtool ctags distclean \ - distclean-compile distclean-generic distclean-libtool \ - distclean-tags distdir dvi dvi-am html html-am info info-am \ - install install-am install-binPROGRAMS install-data \ - install-data-am install-dvi install-dvi-am install-exec \ - install-exec-am install-exec-hook install-html install-html-am \ - install-info install-info-am install-libLTLIBRARIES \ - install-man install-pdf install-pdf-am install-pkgcfgDATA \ - install-ps install-ps-am install-strip installcheck \ - installcheck-am installdirs maintainer-clean \ - maintainer-clean-generic mostlyclean mostlyclean-compile \ - mostlyclean-generic mostlyclean-libtool pdf pdf-am ps ps-am \ - tags uninstall uninstall-am uninstall-binPROGRAMS \ - uninstall-libLTLIBRARIES uninstall-pkgcfgDATA + uninstall-libexecPROGRAMS uninstall-pkgcfgDATA + +.MAKE: install-am install-exec-am install-strip + +.PHONY: CTAGS GTAGS all all-am check check-am clean clean-binPROGRAMS \ + clean-generic clean-libLTLIBRARIES clean-libexecPROGRAMS \ + clean-libtool ctags distclean distclean-compile \ + distclean-generic distclean-libtool distclean-tags distdir dvi \ + dvi-am html html-am info info-am install install-am \ + install-binPROGRAMS install-data install-data-am install-dvi \ + install-dvi-am install-exec install-exec-am install-exec-hook \ + install-html install-html-am install-info install-info-am \ + install-libLTLIBRARIES install-libexecPROGRAMS install-man \ + install-pdf install-pdf-am install-pkgcfgDATA install-ps \ + install-ps-am install-strip installcheck installcheck-am \ + installdirs maintainer-clean maintainer-clean-generic \ + mostlyclean mostlyclean-compile mostlyclean-generic \ + mostlyclean-libtool pdf pdf-am ps ps-am tags uninstall \ + uninstall-am uninstall-binPROGRAMS uninstall-libLTLIBRARIES \ + uninstall-libexecPROGRAMS uninstall-pkgcfgDATA @LINUX_TRUE@install-exec-hook: -@LINUX_TRUE@ $(SUDO_BINARY) chown root:root $(bindir)/gnunet-helper-vpn || true -@LINUX_TRUE@ $(SUDO_BINARY) chmod u+s $(bindir)/gnunet-helper-vpn || true +@LINUX_TRUE@ $(top_srcdir)/src/vpn/install-vpn-helper.sh $(libexecdir) $(SUDO_BINARY) || true @LINUX_FALSE@install-exec-hook: # Tell versions [3.59,3.63) of GNU make to not export all variables. diff --git a/src/vpn/gnunet-helper-vpn-windows.c b/src/vpn/gnunet-helper-vpn-windows.c new file mode 100644 index 0000000..b810dc7 --- /dev/null +++ b/src/vpn/gnunet-helper-vpn-windows.c @@ -0,0 +1,1557 @@ +/* + This file is part of GNUnet. + (C) 2010, 2012 Christian Grothoff + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. + */ + +/** + * @file vpn/gnunet-helper-vpn-windows.c + * @brief the helper for the VPN service in win32 builds. + * Opens a virtual network-interface, sends data received on the if to stdout, + * sends data received on stdin to the interface + * @author Christian M. Fuchs + * + * The following list of people have reviewed this code and considered + * it safe since the last modification (if you reviewed it, please + * have your name added to the list): + * + */ + +#include +#include +#include +#include +#include +#include +#include +#include "platform.h" +#include "tap-windows.h" +/** + * Need 'struct GNUNET_MessageHeader'. + */ +#include "gnunet_common.h" + +/** + * Need VPN message types. + */ +#include "gnunet_protocols.h" + +/** + * Should we print (interesting|debug) messages that can happen during + * normal operation? + */ +#define DEBUG GNUNET_NO + +#if DEBUG +/* FIXME: define with varargs... */ +#define LOG_DEBUG(msg) fprintf (stderr, "%s", msg); +#else +#define LOG_DEBUG(msg) do {} while (0) +#endif + + +/** + * Maximum size of a GNUnet message (GNUNET_SERVER_MAX_MESSAGE_SIZE) + */ +#define MAX_SIZE 65536 + +/** + * Name or Path+Name of our win32 driver. + * The .sys and .cat files HAVE to be in the same location as this file! + */ +#define INF_FILE "share/gnunet/tapw32/OemWin2k.inf" + +/** + * Name or Path+Name of our win64 driver. + * The .sys and .cat files HAVE to be in the same location as this file! + */ +#define INF_FILE64 "share/gnunet/tapw64/OemWin2k.inf" + +/** + * Hardware ID used in the inf-file. + * This might change over time, as openvpn advances their driver + */ +#define HARDWARE_ID "tap0901" + +/** + * Minimum major-id of the driver version we can work with + */ +#define TAP_WIN_MIN_MAJOR 9 + +/** + * Minimum minor-id of the driver version we can work with. + * v <= 7 has buggy IPv6. + * v == 8 is broken for small IPv4 Packets + */ +#define TAP_WIN_MIN_MINOR 9 + +/** + * Time in seconds to wait for our virtual device to go up after telling it to do so. + * + * openvpn doesn't specify a value, 4 seems sane for testing, even for openwrt + * (in fact, 4 was chosen by a fair dice roll...) + */ +#define TAP32_POSTUP_WAITTIME 4 + +/** + * Location of the network interface list resides in registry. + */ +#define INTERFACE_REGISTRY_LOCATION "SYSTEM\\CurrentControlSet\\Control\\Network\\{4D36E972-E325-11CE-BFC1-08002BE10318}" + +/** + * Our local process' PID. Used for creating a sufficiently unique additional + * hardware ID for our device. + */ +static char secondary_hwid[LINE_LEN / 2]; + +/** + * Device's visible Name, used to identify a network device in netsh. + * eg: "Local Area Connection 9" + */ +static char device_visible_name[256]; + +/** + * This is our own local instance of a virtual network interface + * It is (somewhat) equivalent to using tun/tap in unixoid systems + * + * Upon initialization, we create such an device node. + * Upon termination, we remove it again. + * + * If we crash this device might stay around. + */ +static HDEVINFO DeviceInfo = INVALID_HANDLE_VALUE; + +/** + * Registry Key we hand over to windows to spawn a new virtual interface + */ +static SP_DEVINFO_DATA DeviceNode; + +/** + * GUID of our virtual device in the form of + * {12345678-1234-1234-1234-123456789abc} - in hex + */ +static char device_guid[256]; + + +/** + * Possible states of an IO facility. + */ +enum IO_State +{ + + /** + * overlapped I/O is ready for work + */ + IOSTATE_READY = 0, + + /** + * overlapped I/O has been queued + */ + IOSTATE_QUEUED, + + /** + * overlapped I/O has finished, but is waiting for it's write-partner + */ + IOSTATE_WAITING, + + /** + * there is a full buffer waiting + */ + IOSTATE_RESUME, + + /** + * Operlapped IO states for facility objects + * overlapped I/O has failed, stop processing + */ + IOSTATE_FAILED + +}; + + +/** + * A IO Object + read/writebuffer + buffer-size for windows asynchronous IO handling + */ +struct io_facility +{ + /** + * The mode the state machine associated with this object is in. + */ + enum IO_State facility_state; + + /** + * If the path is open or blocked in general (used for quickly checking) + */ + BOOL path_open; // BOOL is winbool (int), NOT boolean (unsigned char)! + + /** + * Windows Object-Handle (used for accessing TAP and STDIN/STDOUT) + */ + HANDLE handle; + + /** + * Overlaped IO structure used for asynchronous IO in windows. + */ + OVERLAPPED overlapped; + + /** + * Buffer for reading things to and writing from... + */ + unsigned char buffer[MAX_SIZE]; + + /** + * How much of this buffer was used when reading or how much data can be written + */ + DWORD buffer_size; + + /** + * Amount of data actually written or read by readfile/writefile. + */ + DWORD buffer_size_processed; + + /** + * How much of this buffer we have writte in total + */ + DWORD buffer_size_written; +}; + +/** + * ReOpenFile is only available as of XP SP2 and 2003 SP1 + */ +WINBASEAPI HANDLE WINAPI ReOpenFile (HANDLE, DWORD, DWORD, DWORD); + +/** + * IsWow64Process definition for our is_win64, as this is a kernel function + */ +typedef BOOL (WINAPI *LPFN_ISWOW64PROCESS) (HANDLE, PBOOL); + +/** + * Determines if the host OS is win32 or win64 + * + * @return true if + */ +BOOL +is_win64 () +{ +#if defined(_WIN64) + //this is a win64 binary, + return TRUE; +#elif defined(_WIN32) + //this is a 32bit binary, and we need to check if we are running in WOW64 + BOOL success = FALSE; + BOOL on_wow64 = FALSE; + LPFN_ISWOW64PROCESS IsWow64Process = (LPFN_ISWOW64PROCESS) GetProcAddress (GetModuleHandle ("kernel32"), "IsWow64Process"); + + if (NULL != IsWow64Process) + success = IsWow64Process (GetCurrentProcess (), &on_wow64); + + return success && on_wow64; +#endif +} +/** + * Wrapper for executing a shellcommand in windows. + * + * @param command - the command + parameters to execute + * @return * exitcode of the program executed, + * * EINVAL (cmd/file not found) + * * EPIPE (could not read STDOUT) + */ +static int +execute_shellcommand (const char *command) +{ + FILE *pipe; + + if ( (NULL == command) || + (NULL == (pipe = _popen (command, "rt"))) ) + return EINVAL; + +#if DEBUG + fprintf (stderr, "DEBUG: Command output: \n"); + char output[LINE_LEN]; + while (NULL != fgets (output, sizeof (output), pipe)) + fprintf (stderr, "%s", output); +#endif + + return _pclose (pipe); +} + + +/** + * @brief Sets the IPv6-Address given in address on the interface dev + * + * @param address the IPv6-Address + * @param prefix_len the length of the network-prefix + */ +static int +set_address6 (const char *address, unsigned long prefix_len) +{ + int ret = EINVAL; + char command[LINE_LEN]; + struct sockaddr_in6 sa6; + + /* + * parse the new address + */ + memset (&sa6, 0, sizeof (struct sockaddr_in6)); + sa6.sin6_family = AF_INET6; + if (1 != inet_pton (AF_INET6, address, &sa6.sin6_addr.s6_addr)) + { + fprintf (stderr, "ERROR: Failed to parse address `%s': %s\n", address, + strerror (errno)); + return -1; + } + + /* + * prepare the command + */ + snprintf (command, LINE_LEN, + "netsh interface ipv6 add address \"%s\" %s/%d store=active", + device_visible_name, address, prefix_len); + /* + * Set the address + */ + ret = execute_shellcommand (command); + + /* Did it work?*/ + if (0 != ret) + fprintf (stderr, "FATAL: Setting IPv6 address failed: %s\n", strerror (ret)); + return ret; +} + + +/** + * @brief Removes the IPv6-Address given in address from the interface dev + * + * @param dev the interface to remove + * @param address the IPv4-Address + * @param mask the netmask + */ +static void +remove_address6 (const char *address) +{ + char command[LINE_LEN]; + int ret = EINVAL; + + // sanity checking was already done in set_address6 + /* + * prepare the command + */ + snprintf (command, LINE_LEN, + "netsh interface ipv6 delete address \"%s\" store=persistent", + device_visible_name, address); + /* + * Set the address + */ + ret = execute_shellcommand (command); + + /* Did it work?*/ + if (0 != ret) + fprintf (stderr, "FATAL: removing IPv6 address failed: %s\n", strerror (ret)); +} + + +/** + * @brief Sets the IPv4-Address given in address on the interface dev + * + * @param dev the interface to configure + * @param address the IPv4-Address + * @param mask the netmask + */ +static int +set_address4 (const char *address, const char *mask) +{ + int ret = EINVAL; + char command[LINE_LEN]; + + struct sockaddr_in addr; + addr.sin_family = AF_INET; + + /* + * Parse the address + */ + if (1 != inet_pton (AF_INET, address, &addr.sin_addr.s_addr)) + { + fprintf (stderr, "ERROR: Failed to parse address `%s': %s\n", address, + strerror (errno)); + return -1; + } + // Set Device to Subnet-Mode? + // do we really need tun.c:2925 ? + + /* + * prepare the command + */ + snprintf (command, LINE_LEN, + "netsh interface ipv4 add address \"%s\" %s %s store=active", + device_visible_name, address, mask); + /* + * Set the address + */ + ret = execute_shellcommand (command); + + /* Did it work?*/ + if (0 != ret) + fprintf (stderr, "FATAL: Setting IPv4 address failed: %s\n", strerror (ret)); + return ret; +} + + +/** + * @brief Removes the IPv4-Address given in address from the interface dev + * + * @param dev the interface to remove + * @param address the IPv4-Address + * @param mask the netmask + */ +static void +remove_address4 (const char *address) +{ + char command[LINE_LEN]; + int ret = EINVAL; + + // sanity checking was already done in set_address4 + + /* + * prepare the command + */ + snprintf (command, LINE_LEN, + "netsh interface ipv4 delete address \"%s\" gateway=all store=persistent", + device_visible_name, address); + /* + * Set the address + */ + ret = execute_shellcommand (command); + + /* Did it work?*/ + if (0 != ret) + fprintf (stderr, "FATAL: removing IPv4 address failed: %s\n", strerror (ret)); +} + + +/** + * Setup a new virtual interface to use for tunneling. + * + * @return: TRUE if setup was successful, else FALSE + */ +static BOOL +setup_interface () +{ + /* + * where to find our inf-file. (+ the "full" path, after windows found") + * + * We do not directly input all the props here, because openvpn will update + * these details over time. + */ + char inf_file_path[MAX_PATH]; + char * temp_inf_filename; + char hwidlist[LINE_LEN + 4]; + char class_name[128]; + GUID class_guid; + int str_length = 0; + + /** + * Set the device's hardware ID and add it to a list. + * This information will later on identify this device in registry. + */ + strncpy (hwidlist, HARDWARE_ID, LINE_LEN); + /** + * this is kind of over-complicated, but allows keeps things independent of + * how the openvpn-hwid is actually stored. + * + * A HWID list is double-\0 terminated and \0 separated + */ + str_length = strlen (hwidlist) + 1; + strncpy (&hwidlist[str_length], secondary_hwid, LINE_LEN); + str_length += strlen (&hwidlist[str_length]) + 1; + + /** + * Locate the inf-file, we need to store it somewhere where the system can + * find it. We need to pick the correct driver for win32/win64. + */ + if (is_win64()) + GetFullPathNameA (INF_FILE64, MAX_PATH, inf_file_path, &temp_inf_filename); + else + GetFullPathNameA (INF_FILE, MAX_PATH, inf_file_path, &temp_inf_filename); + + fprintf (stderr, "INFO: Located our driver's .inf file at %s\n", inf_file_path); + /** + * Bootstrap our device info using the drivers inf-file + */ + if ( ! SetupDiGetINFClassA (inf_file_path, + &class_guid, + class_name, sizeof (class_name) / sizeof (char), + NULL)) + return FALSE; + + /** + * Collect all the other needed information... + * let the system fill our this form + */ + DeviceInfo = SetupDiCreateDeviceInfoList (&class_guid, NULL); + if (DeviceInfo == INVALID_HANDLE_VALUE) + return FALSE; + + DeviceNode.cbSize = sizeof (SP_DEVINFO_DATA); + if ( ! SetupDiCreateDeviceInfoA (DeviceInfo, + class_name, + &class_guid, + NULL, + 0, + DICD_GENERATE_ID, + &DeviceNode)) + return FALSE; + + /* Deploy all the information collected into the registry */ + if ( ! SetupDiSetDeviceRegistryPropertyA (DeviceInfo, + &DeviceNode, + SPDRP_HARDWAREID, + (LPBYTE) hwidlist, + str_length * sizeof (char))) + return FALSE; + + /* Install our new class(=device) into the system */ + if ( ! SetupDiCallClassInstaller (DIF_REGISTERDEVICE, + DeviceInfo, + &DeviceNode)) + return FALSE; + + /* This system call tends to take a while (several seconds!) on + "modern" Windoze systems */ + if ( ! UpdateDriverForPlugAndPlayDevicesA (NULL, + secondary_hwid, + inf_file_path, + INSTALLFLAG_FORCE | INSTALLFLAG_NONINTERACTIVE, + NULL)) //reboot required? NEVER! + return FALSE; + + fprintf (stderr, "DEBUG: successfully created a network device\n"); + return TRUE; +} + + +/** + * Remove our new virtual interface to use for tunneling. + * This function must be called AFTER setup_interface! + * + * @return: TRUE if destruction was successful, else FALSE + */ +static BOOL +remove_interface () +{ + SP_REMOVEDEVICE_PARAMS remove; + + if (INVALID_HANDLE_VALUE == DeviceInfo) + return FALSE; + + remove.ClassInstallHeader.cbSize = sizeof (SP_CLASSINSTALL_HEADER); + remove.HwProfile = 0; + remove.Scope = DI_REMOVEDEVICE_GLOBAL; + remove.ClassInstallHeader.InstallFunction = DIF_REMOVE; + /* + * 1. Prepare our existing device information set, and place the + * uninstall related information into the structure + */ + if ( ! SetupDiSetClassInstallParamsA (DeviceInfo, + (PSP_DEVINFO_DATA) & DeviceNode, + &remove.ClassInstallHeader, + sizeof (remove))) + return FALSE; + /* + * 2. Uninstall the virtual interface using the class installer + */ + if ( ! SetupDiCallClassInstaller (DIF_REMOVE, + DeviceInfo, + (PSP_DEVINFO_DATA) & DeviceNode)) + return FALSE; + + SetupDiDestroyDeviceInfoList (DeviceInfo); + + fprintf (stderr, "DEBUG: removed interface successfully\n"); + + return TRUE; +} + + +/** + * Do all the lookup necessary to retrieve the inteface's actual name + * off the registry. + * + * @return: TRUE if we were able to lookup the interface's name, else FALSE + */ +static BOOL +resolve_interface_name () +{ + SP_DEVINFO_LIST_DETAIL_DATA device_details; + char pnp_instance_id [MAX_DEVICE_ID_LEN]; + HKEY adapter_key_handle; + LONG status; + DWORD len; + int i = 0; + int retrys; + BOOL retval = FALSE; + char adapter[] = INTERFACE_REGISTRY_LOCATION; + + /* We can obtain the PNP instance ID from our setupapi handle */ + device_details.cbSize = sizeof (device_details); + if (CR_SUCCESS != CM_Get_Device_ID_ExA (DeviceNode.DevInst, + (PCHAR) pnp_instance_id, + MAX_DEVICE_ID_LEN, + 0, //must be 0 + NULL)) //hMachine, we are local + return FALSE; + + fprintf (stderr, "DEBUG: Resolving interface name for network device %s\n",pnp_instance_id); + + /* Registry is incredibly slow, retry for up to 30 seconds to allow registry to refresh */ + for (retrys = 0; retrys < 120 && !retval; retrys++) + { + /* sleep for 250ms*/ + Sleep (250); + + /* Now we can use this ID to locate the correct networks interface in registry */ + if (ERROR_SUCCESS != RegOpenKeyExA ( + HKEY_LOCAL_MACHINE, + adapter, + 0, + KEY_READ, + &adapter_key_handle)) + return FALSE; + + /* Of course there is a multitude of entries here, with arbitrary names, + * thus we need to iterate through there. + */ + while (!retval) + { + char instance_key[256]; + char query_key [256]; + HKEY instance_key_handle; + char pnpinstanceid_name[] = "PnpInstanceID"; + char pnpinstanceid_value[256]; + char adaptername_name[] = "Name"; + DWORD data_type; + + len = 256 * sizeof (char); + /* optain a subkey of {4D36E972-E325-11CE-BFC1-08002BE10318} */ + status = RegEnumKeyExA ( + adapter_key_handle, + i, + instance_key, + &len, + NULL, + NULL, + NULL, + NULL); + + /* this may fail due to one of two reasons: + * we are at the end of the list*/ + if (ERROR_NO_MORE_ITEMS == status) + break; + // * we found a broken registry key, continue with the next key. + if (ERROR_SUCCESS != status) + goto cleanup; + + /* prepare our new query string: */ + snprintf (query_key, 256, "%s\\%s\\Connection", + adapter, + instance_key); + + /* look inside instance_key\\Connection */ + if (ERROR_SUCCESS != RegOpenKeyExA ( + HKEY_LOCAL_MACHINE, + query_key, + 0, + KEY_READ, + &instance_key_handle)) + goto cleanup; + + /* now, read our PnpInstanceID */ + len = sizeof (pnpinstanceid_value); + status = RegQueryValueExA (instance_key_handle, + pnpinstanceid_name, + NULL, //reserved, always NULL according to MSDN + &data_type, + (LPBYTE) pnpinstanceid_value, + &len); + + if (status != ERROR_SUCCESS || data_type != REG_SZ) + goto cleanup; + + /* compare the value we got to our devices PNPInstanceID*/ + if (0 != strncmp (pnpinstanceid_value, pnp_instance_id, + sizeof (pnpinstanceid_value) / sizeof (char))) + goto cleanup; + + len = sizeof (device_visible_name); + status = RegQueryValueExA ( + instance_key_handle, + adaptername_name, + NULL, //reserved, always NULL according to MSDN + &data_type, + (LPBYTE) device_visible_name, + &len); + + if (status != ERROR_SUCCESS || data_type != REG_SZ) + goto cleanup; + + /* + * we have successfully found OUR instance, + * save the device GUID before exiting + */ + + strncpy (device_guid, instance_key, 256); + retval = TRUE; + fprintf (stderr, "DEBUG: Interface Name lookup succeeded on retry %d, got \"%s\" %s\n", retrys, device_visible_name, device_guid); + +cleanup: + RegCloseKey (instance_key_handle); + + ++i; + } + + RegCloseKey (adapter_key_handle); + } + return retval; +} + + +/** + * Determines the version of the installed TAP32 driver and checks if it's sufficiently new for GNUNET + * + * @param handle the handle to our tap device + * @return TRUE if the version is sufficient, else FALSE + */ +static BOOL +check_tapw32_version (HANDLE handle) +{ + ULONG version[3]; + DWORD len; + memset (&(version), 0, sizeof (version)); + + if (DeviceIoControl (handle, TAP_WIN_IOCTL_GET_VERSION, + &version, sizeof (version), + &version, sizeof (version), &len, NULL)) + fprintf (stderr, "INFO: TAP-Windows Driver Version %d.%d %s\n", + (int) version[0], + (int) version[1], + (version[2] ? "(DEBUG)" : "")); + + if ((version[0] != TAP_WIN_MIN_MAJOR) || + (version[1] < TAP_WIN_MIN_MINOR )){ + fprintf (stderr, "FATAL: This version of gnunet requires a TAP-Windows driver that is at least version %d.%d\n", + TAP_WIN_MIN_MAJOR, + TAP_WIN_MIN_MINOR); + return FALSE; + } + + return TRUE; +} + + +/** + * Creates a tun-interface called dev; + * + * @return the fd to the tun or -1 on error + */ +static HANDLE +init_tun () +{ + char device_path[256]; + HANDLE handle; + + if (! setup_interface ()) + { + errno = ENODEV; + return INVALID_HANDLE_VALUE; + } + + if (! resolve_interface_name ()) + { + errno = ENODEV; + return INVALID_HANDLE_VALUE; + } + + /* Open Windows TAP-Windows adapter */ + snprintf (device_path, sizeof (device_path), "%s%s%s", + USERMODEDEVICEDIR, + device_guid, + TAP_WIN_SUFFIX); + + handle = CreateFile ( + device_path, + GENERIC_READ | GENERIC_WRITE, + 0, /* was: FILE_SHARE_READ */ + 0, + OPEN_EXISTING, + FILE_ATTRIBUTE_SYSTEM | FILE_FLAG_OVERLAPPED, + 0 + ); + + if (INVALID_HANDLE_VALUE == handle) + { + fprintf (stderr, "FATAL: CreateFile failed on TAP device: %s\n", device_path); + return handle; + } + + /* get driver version info */ + if (! check_tapw32_version (handle)) + { + CloseHandle (handle); + return INVALID_HANDLE_VALUE; + } + + /* TODO (opt?): get MTU-Size */ + + fprintf (stderr, "DEBUG: successfully opened TAP device\n"); + return handle; +} + + +/** + * Brings a TAP device up and sets it to connected state. + * + * @param handle the handle to our TAP device + * @return True if the operation succeeded, else false + */ +static BOOL +tun_up (HANDLE handle) +{ + ULONG status = TRUE; + DWORD len; + if (! DeviceIoControl (handle, TAP_WIN_IOCTL_SET_MEDIA_STATUS, + &status, sizeof (status), + &status, sizeof (status), &len, NULL)) + { + fprintf (stderr, "FATAL: TAP driver ignored request to UP interface (DeviceIoControl call)\n"); + return FALSE; + } + + /* Wait for the device to go UP, might take some time. */ + Sleep (TAP32_POSTUP_WAITTIME * 1000); + fprintf (stderr, "DEBUG: successfully set TAP device to UP\n"); + + return TRUE; +} + + +/** + * Attempts to read off an input facility (tap or named pipe) in overlapped mode. + * + * 1. + * If the input facility is in IOSTATE_READY, it will issue a new read operation to the + * input handle. Then it goes into IOSTATE_QUEUED state. + * In case the read succeeded instantly the input facility enters 3. + * + * 2. + * If the input facility is in IOSTATE_QUEUED state, it will check if the queued read has finished already. + * If it has finished, go to state 3. + * If it has failed, set IOSTATE_FAILED + * + * 3. + * If the output facility is in state IOSTATE_READY, the read-buffer is copied to the output buffer. + * The input facility enters state IOSTATE_READY + * The output facility enters state IOSTATE_READY + * If the output facility is in state IOSTATE_QUEUED, the input facility enters IOSTATE_WAITING + * + * IOSTATE_WAITING is reset by the output facility, once it has completed. + * + * @param input_facility input named pipe or file to work with. + * @param output_facility output pipe or file to hand over data to. + * @return false if an event reset was impossible (OS error), else true + */ +static BOOL +attempt_read_tap (struct io_facility * input_facility, + struct io_facility * output_facility) +{ + struct GNUNET_MessageHeader * hdr; + unsigned short size; + + switch (input_facility->facility_state) + { + case IOSTATE_READY: + { + if (! ResetEvent (input_facility->overlapped.hEvent)) + { + return FALSE; + } + + input_facility->buffer_size = 0; + + /* Check how the task is handled */ + if (ReadFile (input_facility->handle, + input_facility->buffer, + sizeof (input_facility->buffer) - sizeof (struct GNUNET_MessageHeader), + &input_facility->buffer_size, + &input_facility->overlapped)) + {/* async event processed immediately*/ + + /* reset event manually*/ + if (! SetEvent (input_facility->overlapped.hEvent)) + return FALSE; + + fprintf (stderr, "DEBUG: tap read succeeded immediately\n"); + + /* we successfully read something from the TAP and now need to + * send it our via STDOUT. Is that possible at the moment? */ + if ((IOSTATE_READY == output_facility->facility_state || + IOSTATE_WAITING == output_facility->facility_state) + && (0 < input_facility->buffer_size)) + { /* hand over this buffers content and apply message header for gnunet */ + hdr = (struct GNUNET_MessageHeader *) output_facility->buffer; + size = input_facility->buffer_size + sizeof (struct GNUNET_MessageHeader); + + memcpy (output_facility->buffer + sizeof (struct GNUNET_MessageHeader), + input_facility->buffer, + input_facility->buffer_size); + + output_facility->buffer_size = size; + hdr->size = htons (size); + hdr->type = htons (GNUNET_MESSAGE_TYPE_VPN_HELPER); + output_facility->facility_state = IOSTATE_READY; + } + else if (0 < input_facility->buffer_size) + /* If we have have read our buffer, wait for our write-partner*/ + input_facility->facility_state = IOSTATE_WAITING; + } + else /* operation was either queued or failed*/ + { + int err = GetLastError (); + if (ERROR_IO_PENDING == err) + { /* operation queued */ + input_facility->facility_state = IOSTATE_QUEUED; + } + else + { /* error occurred, let the rest of the elements finish */ + input_facility->path_open = FALSE; + input_facility->facility_state = IOSTATE_FAILED; + if (IOSTATE_WAITING == output_facility->facility_state) + output_facility->path_open = FALSE; + + fprintf (stderr, "FATAL: Read from handle failed, allowing write to finish\n"); + } + } + } + return TRUE; + // We are queued and should check if the read has finished + case IOSTATE_QUEUED: + { + // there was an operation going on already, check if that has completed now. + + if (GetOverlappedResult (input_facility->handle, + &input_facility->overlapped, + &input_facility->buffer_size, + FALSE)) + {/* successful return for a queued operation */ + if (! ResetEvent (input_facility->overlapped.hEvent)) + return FALSE; + + fprintf (stderr, "DEBUG: tap read succeeded delayed\n"); + + /* we successfully read something from the TAP and now need to + * send it our via STDOUT. Is that possible at the moment? */ + if ((IOSTATE_READY == output_facility->facility_state || + IOSTATE_WAITING == output_facility->facility_state) + && 0 < input_facility->buffer_size) + { /* hand over this buffers content and apply message header for gnunet */ + hdr = (struct GNUNET_MessageHeader *) output_facility->buffer; + size = input_facility->buffer_size + sizeof (struct GNUNET_MessageHeader); + + memcpy (output_facility->buffer + sizeof (struct GNUNET_MessageHeader), + input_facility->buffer, + input_facility->buffer_size); + + output_facility->buffer_size = size; + hdr->size = htons(size); + hdr->type = htons (GNUNET_MESSAGE_TYPE_VPN_HELPER); + output_facility->facility_state = IOSTATE_READY; + input_facility->facility_state = IOSTATE_READY; + } + else if (0 < input_facility->buffer_size) + { /* If we have have read our buffer, wait for our write-partner*/ + input_facility->facility_state = IOSTATE_WAITING; + // TODO: shall we attempt to fill our buffer or should we wait for our write-partner to finish? + } + } + else + { /* operation still pending/queued or failed? */ + int err = GetLastError (); + if ((ERROR_IO_INCOMPLETE != err) && (ERROR_IO_PENDING != err)) + { /* error occurred, let the rest of the elements finish */ + input_facility->path_open = FALSE; + input_facility->facility_state = IOSTATE_FAILED; + if (IOSTATE_WAITING == output_facility->facility_state) + output_facility->path_open = FALSE; + fprintf (stderr, "FATAL: Read from handle failed, allowing write to finish\n"); + } + } + } + return TRUE; + case IOSTATE_RESUME: + hdr = (struct GNUNET_MessageHeader *) output_facility->buffer; + size = input_facility->buffer_size + sizeof (struct GNUNET_MessageHeader); + + memcpy (output_facility->buffer + sizeof (struct GNUNET_MessageHeader), + input_facility->buffer, + input_facility->buffer_size); + + output_facility->buffer_size = size; + hdr->size = htons (size); + hdr->type = htons (GNUNET_MESSAGE_TYPE_VPN_HELPER); + output_facility->facility_state = IOSTATE_READY; + input_facility->facility_state = IOSTATE_READY; + return TRUE; + default: + return TRUE; + } +} + + +/** + * Attempts to read off an input facility (tap or named pipe) in overlapped mode. + * + * 1. + * If the input facility is in IOSTATE_READY, it will issue a new read operation to the + * input handle. Then it goes into IOSTATE_QUEUED state. + * In case the read succeeded instantly the input facility enters 3. + * + * 2. + * If the input facility is in IOSTATE_QUEUED state, it will check if the queued read has finished already. + * If it has finished, go to state 3. + * If it has failed, set IOSTATE_FAILED + * + * 3. + * If the facility is finished with ready + * The read-buffer is copied to the output buffer, except for the GNUNET_MessageHeader. + * The input facility enters state IOSTATE_READY + * The output facility enters state IOSTATE_READY + * If the output facility is in state IOSTATE_QUEUED, the input facility enters IOSTATE_WAITING + * + * IOSTATE_WAITING is reset by the output facility, once it has completed. + * + * @param input_facility input named pipe or file to work with. + * @param output_facility output pipe or file to hand over data to. + * @return false if an event reset was impossible (OS error), else true + */ +static BOOL +attempt_read_stdin (struct io_facility * input_facility, + struct io_facility * output_facility) +{ + struct GNUNET_MessageHeader * hdr; + + switch (input_facility->facility_state) + { + case IOSTATE_READY: + { + input_facility->buffer_size = 0; + +partial_read_iostate_ready: + if (! ResetEvent (input_facility->overlapped.hEvent)) + return FALSE; + + /* Check how the task is handled */ + if (ReadFile (input_facility->handle, + input_facility->buffer + input_facility->buffer_size, + sizeof (input_facility->buffer) - input_facility->buffer_size, + &input_facility->buffer_size_processed, + &input_facility->overlapped)) + {/* async event processed immediately*/ + hdr = (struct GNUNET_MessageHeader *) input_facility->buffer; + + /* reset event manually*/ + if (!SetEvent (input_facility->overlapped.hEvent)) + return FALSE; + + fprintf (stderr, "DEBUG: stdin read succeeded immediately\n"); + input_facility->buffer_size += input_facility->buffer_size_processed; + + if (ntohs (hdr->type) != GNUNET_MESSAGE_TYPE_VPN_HELPER || + ntohs (hdr->size) > sizeof (input_facility->buffer)) + { + fprintf (stderr, "WARNING: Protocol violation, got GNUnet Message type %h, size %h\n", ntohs (hdr->type), ntohs (hdr->size)); + input_facility->facility_state = IOSTATE_READY; + return TRUE; + } + /* we got the a part of a packet */ + if (ntohs (hdr->size) > input_facility->buffer_size) + goto partial_read_iostate_ready; + + /* have we read more than 0 bytes of payload? (sizeread > header)*/ + if (input_facility->buffer_size > sizeof (struct GNUNET_MessageHeader) && + ((IOSTATE_READY == output_facility->facility_state) || + (IOSTATE_WAITING == output_facility->facility_state))) + {/* we successfully read something from the TAP and now need to + * send it our via STDOUT. Is that possible at the moment? */ + + /* hand over this buffers content and strip gnunet message header */ + memcpy (output_facility->buffer, + input_facility->buffer + sizeof (struct GNUNET_MessageHeader), + input_facility->buffer_size - sizeof (struct GNUNET_MessageHeader)); + output_facility->buffer_size = input_facility->buffer_size - sizeof (struct GNUNET_MessageHeader); + output_facility->facility_state = IOSTATE_READY; + input_facility->facility_state = IOSTATE_READY; + } + else if (input_facility->buffer_size > sizeof (struct GNUNET_MessageHeader)) + /* If we have have read our buffer, wait for our write-partner*/ + input_facility->facility_state = IOSTATE_WAITING; + else /* we read nothing */ + input_facility->facility_state = IOSTATE_READY; + } + else /* operation was either queued or failed*/ + { + int err = GetLastError (); + if (ERROR_IO_PENDING == err) /* operation queued */ + input_facility->facility_state = IOSTATE_QUEUED; + else + { /* error occurred, let the rest of the elements finish */ + input_facility->path_open = FALSE; + input_facility->facility_state = IOSTATE_FAILED; + if (IOSTATE_WAITING == output_facility->facility_state) + output_facility->path_open = FALSE; + + fprintf (stderr, "FATAL: Read from handle failed, allowing write to finish\n"); + } + } + } + return TRUE; + // We are queued and should check if the read has finished + case IOSTATE_QUEUED: + { + // there was an operation going on already, check if that has completed now. + if (GetOverlappedResult (input_facility->handle, + &input_facility->overlapped, + &input_facility->buffer_size_processed, + FALSE)) + {/* successful return for a queued operation */ + hdr = (struct GNUNET_MessageHeader *) input_facility->buffer; + + if (! ResetEvent (input_facility->overlapped.hEvent)) + return FALSE; + + fprintf (stderr, "DEBUG: stdin read succeeded delayed\n"); + input_facility->buffer_size += input_facility->buffer_size_processed; + + if ((ntohs (hdr->type) != GNUNET_MESSAGE_TYPE_VPN_HELPER) || + (ntohs (hdr->size) > sizeof (input_facility->buffer))) + { + fprintf (stderr, "WARNING: Protocol violation, got GNUnet Message type %h, size %h\n", ntohs (hdr->type), ntohs (hdr->size)); + input_facility->facility_state = IOSTATE_READY; + return TRUE; + } + /* we got the a part of a packet */ + if (ntohs (hdr->size) > input_facility->buffer_size ); + goto partial_read_iostate_ready; + + /* we successfully read something from the TAP and now need to + * send it our via STDOUT. Is that possible at the moment? */ + if ((IOSTATE_READY == output_facility->facility_state || + IOSTATE_WAITING == output_facility->facility_state) + && input_facility->buffer_size > sizeof(struct GNUNET_MessageHeader)) + { /* hand over this buffers content and strip gnunet message header */ + memcpy (output_facility->buffer, + input_facility->buffer + sizeof(struct GNUNET_MessageHeader), + input_facility->buffer_size - sizeof(struct GNUNET_MessageHeader)); + output_facility->buffer_size = input_facility->buffer_size - sizeof(struct GNUNET_MessageHeader); + output_facility->facility_state = IOSTATE_READY; + input_facility->facility_state = IOSTATE_READY; + } + else if (input_facility->buffer_size > sizeof(struct GNUNET_MessageHeader)) + input_facility->facility_state = IOSTATE_WAITING; + else + input_facility->facility_state = IOSTATE_READY; + } + else + { /* operation still pending/queued or failed? */ + int err = GetLastError (); + if ((ERROR_IO_INCOMPLETE != err) && (ERROR_IO_PENDING != err)) + { /* error occurred, let the rest of the elements finish */ + input_facility->path_open = FALSE; + input_facility->facility_state = IOSTATE_FAILED; + if (IOSTATE_WAITING == output_facility->facility_state) + output_facility->path_open = FALSE; + fprintf (stderr, "FATAL: Read from handle failed, allowing write to finish\n"); + } + } + } + return TRUE; + case IOSTATE_RESUME: /* Our buffer was filled already but our write facility was busy. */ + memcpy (output_facility->buffer, + input_facility->buffer + sizeof (struct GNUNET_MessageHeader), + input_facility->buffer_size - sizeof (struct GNUNET_MessageHeader)); + output_facility->buffer_size = input_facility->buffer_size - sizeof (struct GNUNET_MessageHeader); + output_facility->facility_state = IOSTATE_READY; + input_facility->facility_state = IOSTATE_READY; + return TRUE; + default: + return TRUE; + } +} + + +/** + * Attempts to write to an output facility (tap or named pipe) in overlapped mode. + * + * TODO: high level description + * + * @param output_facility output pipe or file to hand over data to. + * @param input_facility input named pipe or file to work with. + * @return false if an event reset was impossible (OS error), else true + */ +static BOOL +attempt_write (struct io_facility * output_facility, + struct io_facility * input_facility) +{ + switch (output_facility->facility_state) + { + case IOSTATE_READY: + output_facility->buffer_size_written = 0; + +continue_partial_write: + if (! ResetEvent (output_facility->overlapped.hEvent)) + return FALSE; + + /* Check how the task was handled */ + if (WriteFile (output_facility->handle, + output_facility->buffer + output_facility->buffer_size_written, + output_facility->buffer_size - output_facility->buffer_size_written, + &output_facility->buffer_size_processed, + &output_facility->overlapped)) + {/* async event processed immediately*/ + + fprintf (stderr, "DEBUG: write succeeded immediately\n"); + output_facility->buffer_size_written += output_facility->buffer_size_processed; + + /* reset event manually*/ + if (! SetEvent (output_facility->overlapped.hEvent)) + return FALSE; + + /* partial write */ + if (output_facility->buffer_size_written < output_facility->buffer_size) + goto continue_partial_write; + + /* we are now waiting for our buffer to be filled*/ + output_facility->facility_state = IOSTATE_WAITING; + + /* we successfully wrote something and now need to reset our reader */ + if (IOSTATE_WAITING == input_facility->facility_state) + input_facility->facility_state = IOSTATE_RESUME; + else if (IOSTATE_FAILED == input_facility->facility_state) + output_facility->path_open = FALSE; + } + else /* operation was either queued or failed*/ + { + int err = GetLastError (); + if (ERROR_IO_PENDING == err) + { /* operation queued */ + output_facility->facility_state = IOSTATE_QUEUED; + } + else + { /* error occurred, close this path */ + output_facility->path_open = FALSE; + output_facility->facility_state = IOSTATE_FAILED; + fprintf (stderr, "FATAL: Write to handle failed, exiting\n"); + } + } + return TRUE; + case IOSTATE_QUEUED: + // there was an operation going on already, check if that has completed now. + + if (GetOverlappedResult (output_facility->handle, + &output_facility->overlapped, + &output_facility->buffer_size_processed, + FALSE)) + {/* successful return for a queued operation */ + if (! ResetEvent (output_facility->overlapped.hEvent)) + return FALSE; + + fprintf (stderr, "DEBUG: write succeeded delayed\n"); + output_facility->buffer_size_written += output_facility->buffer_size_processed; + + /* partial write */ + if (output_facility->buffer_size_written < output_facility->buffer_size) + goto continue_partial_write; + + /* we are now waiting for our buffer to be filled*/ + output_facility->facility_state = IOSTATE_WAITING; + + /* we successfully wrote something and now need to reset our reader */ + if (IOSTATE_WAITING == input_facility->facility_state) + input_facility->facility_state = IOSTATE_RESUME; + else if (IOSTATE_FAILED == input_facility->facility_state) + output_facility->path_open = FALSE; + } + else + { /* operation still pending/queued or failed? */ + int err = GetLastError (); + if ((ERROR_IO_INCOMPLETE != err) && (ERROR_IO_PENDING != err)) + { /* error occurred, close this path */ + output_facility->path_open = FALSE; + output_facility->facility_state = IOSTATE_FAILED; + fprintf (stderr, "FATAL: Write to handle failed, exiting\n"); + } + } + default: + return TRUE; + } +} + + +/** + * Initialize a overlapped structure + * + * @param elem the element to initilize + * @param initial_state the initial state for this instance + * @param signaled if the hEvent created should default to signaled or not + * @return true on success, else false + */ +static BOOL +initialize_io_facility (struct io_facility * elem, + int initial_state, + BOOL signaled) +{ + elem->path_open = TRUE; + elem->handle = INVALID_HANDLE_VALUE; + elem->facility_state = initial_state; + elem->buffer_size = 0; + elem->overlapped.hEvent = CreateEvent (NULL, TRUE, signaled, NULL); + if (NULL == elem->overlapped.hEvent) + return FALSE; + + return TRUE; +} + + +/** + * Start forwarding to and from the tunnel. + * + * @param fd_tun tunnel FD + */ +static void +run (HANDLE tap_handle) +{ + /* IO-Facility for reading from our virtual interface */ + struct io_facility tap_read; + /* IO-Facility for writing to our virtual interface */ + struct io_facility tap_write; + /* IO-Facility for reading from stdin */ + struct io_facility std_in; + /* IO-Facility for writing to stdout */ + struct io_facility std_out; + + HANDLE parent_std_in_handle = GetStdHandle (STD_INPUT_HANDLE); + HANDLE parent_std_out_handle = GetStdHandle (STD_OUTPUT_HANDLE); + + /* tun up: */ + /* we do this HERE and not beforehand (in init_tun()), in contrast to openvpn + * to remove the need to flush the arp cache, handle DHCP and wrong IPs. + * + * DHCP and such are all features we will never use in gnunet afaik. + * But for openvpn those are essential. + */ + if (! tun_up (tap_handle)) + return; + + /* Initialize our overlapped IO structures*/ + if (! (initialize_io_facility (&tap_read, IOSTATE_READY, FALSE) + && initialize_io_facility (&tap_write, IOSTATE_WAITING, TRUE) + && initialize_io_facility (&std_in, IOSTATE_READY, FALSE) + && initialize_io_facility (&std_out, IOSTATE_WAITING, TRUE))) + goto teardown_final; + + /* Handles for STDIN and STDOUT */ + tap_read.handle = tap_handle; + tap_write.handle = tap_handle; + +#ifdef DEBUG_TO_CONSOLE + /* Debug output to console STDIN/STDOUT*/ + std_in.handle = parent_std_in_handle; + std_out.handle = parent_std_out_handle; + +#else + fprintf (stderr, "DEBUG: reopening stdin/out for overlapped IO\n"); + /* + * Find out the types of our handles. + * This part is a problem, because in windows we need to handle files, + * pipes and the console differently. + */ + if ((FILE_TYPE_PIPE != GetFileType (parent_std_in_handle)) || + (FILE_TYPE_PIPE != GetFileType (parent_std_out_handle))) + { + fprintf (stderr, "ERROR: stdin/stdout must be named pipes\n"); + goto teardown; + } + + std_in.handle = ReOpenFile (parent_std_in_handle, + GENERIC_READ, + FILE_SHARE_WRITE | FILE_SHARE_READ, + FILE_FLAG_OVERLAPPED); + + if (INVALID_HANDLE_VALUE == std_in.handle) + { + fprintf (stderr, "FATAL: Could not reopen stdin for in overlapped mode, has to be a named pipe\n"); + goto teardown; + } + + std_out.handle = ReOpenFile (parent_std_out_handle, + GENERIC_WRITE, + FILE_SHARE_READ, + FILE_FLAG_OVERLAPPED); + + if (INVALID_HANDLE_VALUE == std_out.handle) + { + fprintf (stderr, "FATAL: Could not reopen stdout for in overlapped mode, has to be a named pipe\n"); + goto teardown; + } +#endif + + fprintf (stderr, "DEBUG: mainloop has begun\n"); + + while (std_out.path_open || tap_write.path_open) + { + /* perform READ from stdin if possible */ + if (std_in.path_open && (! attempt_read_stdin (&std_in, &tap_write))) + break; + + /* perform READ from tap if possible */ + if (tap_read.path_open && (! attempt_read_tap (&tap_read, &std_out))) + break; + + /* perform WRITE to tap if possible */ + if (tap_write.path_open && (! attempt_write (&tap_write, &std_in))) + break; + + /* perform WRITE to STDOUT if possible */ + if (std_out.path_open && (! attempt_write (&std_out, &tap_read))) + break; + } + +teardown: + + fprintf (stderr, "DEBUG: teardown initiated\n"); + + CancelIo (tap_handle); + CancelIo (std_in.handle); + CancelIo (std_out.handle); + +teardown_final: + + CloseHandle (tap_handle); +} + + +/** + * Open VPN tunnel interface. + * + * @param argc must be 6 + * @param argv 0: binary name (gnunet-helper-vpn) + * 1: tunnel interface prefix (gnunet-vpn) + * 2: IPv6 address (::1), "-" to disable + * 3: IPv6 netmask length in bits (64), ignored if #2 is "-" + * 4: IPv4 address (1.2.3.4), "-" to disable + * 5: IPv4 netmask (255.255.0.0), ignored if #4 is "-" + */ +int +main (int argc, char **argv) +{ + char hwid[LINE_LEN]; + HANDLE handle; + int global_ret = 0; + BOOL have_ip4 = FALSE; + BOOL have_ip6 = FALSE; + + if (6 != argc) + { + fprintf (stderr, "FATAL: must supply 5 arguments\nUsage:\ngnunet-helper-vpn \n", argv[0]); + return 1; + } + + strncpy (hwid, argv[1], LINE_LEN); + hwid[LINE_LEN - 1] = '\0'; + + /* + * We use our PID for finding/resolving the control-panel name of our virtual + * device. PIDs are (of course) unique at runtime, thus we can safely use it + * as additional hardware-id for our device. + */ + snprintf (secondary_hwid, LINE_LEN / 2, "%s-%d", + hwid, + _getpid ()); + + if (INVALID_HANDLE_VALUE == (handle = init_tun ())) + { + fprintf (stderr, "FATAL: could not initialize virtual-interface %s with IPv6 %s/%s and IPv4 %s/%s\n", + hwid, + argv[2], + argv[3], + argv[4], + argv[5]); + global_ret = -1; + goto cleanup; + } + + fprintf (stderr, "DEBUG: Setting IPs, if needed\n"); + if (0 != strcmp (argv[2], "-")) + { + const char *address = argv[2]; + long prefix_len = atol (argv[3]); + + if ((prefix_len < 1) || (prefix_len > 127)) + { + fprintf (stderr, "FATAL: ipv6 prefix_len out of range\n"); + global_ret = -1; + goto cleanup; + } + + fprintf (stderr, "DEBUG: Setting IP6 address: %s/%d\n",address,prefix_len); + if (0 != (global_ret = set_address6 (address, prefix_len))) + goto cleanup; + + have_ip6 = TRUE; + } + + if (0 != strcmp (argv[4], "-")) + { + const char *address = argv[4]; + const char *mask = argv[5]; + + fprintf (stderr, "DEBUG: Setting IP4 address: %s/%s\n",address,mask); + if (0 != (global_ret = set_address4 (address, mask))) + goto cleanup; + + have_ip4 = TRUE; + } + + run (handle); + global_ret = 0; +cleanup: + + if (have_ip4) + { + const char *address = argv[4]; + fprintf (stderr, "DEBUG: Removing IP4 address\n"); + remove_address4 (address); + } + if (have_ip6) + { + const char *address = argv[2]; + fprintf (stderr, "DEBUG: Removing IP6 address\n"); + remove_address6 (address); + } + + fprintf (stderr, "DEBUG: removing interface\n"); + remove_interface (); + fprintf (stderr, "DEBUG: graceful exit completed\n"); + + return global_ret; +} diff --git a/src/vpn/gnunet-service-vpn.c b/src/vpn/gnunet-service-vpn.c index b7756a3..1a46f0b 100644 --- a/src/vpn/gnunet-service-vpn.c +++ b/src/vpn/gnunet-service-vpn.c @@ -35,6 +35,7 @@ #include "gnunet_statistics_service.h" #include "gnunet_constants.h" #include "gnunet_tun_lib.h" +#include "gnunet_regex_lib.h" #include "vpn.h" #include "exit.h" @@ -62,7 +63,7 @@ struct DestinationEntry * Key under which this entry is in the 'destination_map' (only valid * if 'heap_node != NULL'). */ - GNUNET_HashCode key; + struct GNUNET_HashCode key; /** * Pre-allocated tunnel for this destination, or NULL for none. @@ -91,7 +92,7 @@ struct DestinationEntry /** * The description of the service (only used for service tunnels). */ - GNUNET_HashCode service_descriptor; + struct GNUNET_HashCode service_descriptor; /** * Peer offering the service. @@ -371,7 +372,7 @@ static unsigned long long max_tunnel_mappings; static void get_destination_key_from_ip (int af, const void *address, - GNUNET_HashCode *key) + struct GNUNET_HashCode *key) { switch (af) { @@ -411,11 +412,11 @@ get_tunnel_key_from_ips (int af, uint16_t source_port, const void *destination_ip, uint16_t destination_port, - GNUNET_HashCode *key) + struct GNUNET_HashCode *key) { char *off; - memset (key, 0, sizeof (GNUNET_HashCode)); + memset (key, 0, sizeof (struct GNUNET_HashCode)); /* the GNUnet hashmap only uses the first sizeof(unsigned int) of the hash, so we put the ports in there (and hope for few collisions) */ off = (char*) key; @@ -501,7 +502,7 @@ send_client_reply (struct GNUNET_SERVER_Client *client, static void free_tunnel_state (struct TunnelState *ts) { - GNUNET_HashCode key; + struct GNUNET_HashCode key; struct TunnelMessageQueueEntry *tnq; struct GNUNET_MESH_Tunnel *tunnel; @@ -689,7 +690,6 @@ send_to_peer_notify_callback (void *cls, size_t size, void *buf) if (NULL != (tnq = ts->tmq_head)) ts->th = GNUNET_MESH_notify_transmit_ready (ts->tunnel, GNUNET_NO /* cork */, - 42 /* priority */, GNUNET_TIME_UNIT_FOREVER_REL, NULL, tnq->len, @@ -742,7 +742,6 @@ send_to_tunnel (struct TunnelMessageQueueEntry *tnq, if (NULL == ts->th) ts->th = GNUNET_MESH_notify_transmit_ready (ts->tunnel, GNUNET_NO /* cork */, - 42 /* priority */, GNUNET_TIME_UNIT_FOREVER_REL, NULL, tnq->len, @@ -809,27 +808,45 @@ create_tunnel_to_destination (struct DestinationEntry *de, } else { + char *policy; + switch (de->details.exit_destination.af) { case AF_INET: - GNUNET_MESH_peer_request_connect_by_type (ts->tunnel, - GNUNET_APPLICATION_TYPE_IPV4_GATEWAY); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Creating tunnel to exit peer for %s\n", - "IPv4"); - break; + { + char address[GNUNET_REGEX_IPV4_REGEXLEN]; + GNUNET_REGEX_ipv4toregex (&de->details.exit_destination.ip.v4, + "255.255.255.255", address); + GNUNET_asprintf (&policy, "%s%s%s", + GNUNET_APPLICATION_TYPE_EXIT_REGEX_PREFIX, + "4", + address); + break; + } case AF_INET6: - GNUNET_MESH_peer_request_connect_by_type (ts->tunnel, - GNUNET_APPLICATION_TYPE_IPV6_GATEWAY); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, - "Creating tunnel to exit peer for %s\n", - "IPv6"); + { + char address[GNUNET_REGEX_IPV6_REGEXLEN]; + GNUNET_REGEX_ipv6toregex (&de->details.exit_destination.ip.v6, + 128, address); + GNUNET_asprintf (&policy, "%s%s%s", + GNUNET_APPLICATION_TYPE_EXIT_REGEX_PREFIX, + "6", + address); break; + } default: GNUNET_assert (0); break; } - } + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Requesting connect by string: %s\n", policy); + + GNUNET_MESH_peer_request_connect_by_string (ts->tunnel, policy); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Creating tunnel to exit peer for policy `%s'\n", + policy); + GNUNET_free (policy); + } return ts; } @@ -872,7 +889,7 @@ route_packet (struct DestinationEntry *destination, const void *payload, size_t payload_length) { - GNUNET_HashCode key; + struct GNUNET_HashCode key; struct TunnelState *ts; struct TunnelMessageQueueEntry *tnq; size_t alen; @@ -1510,7 +1527,7 @@ message_token (void *cls GNUNET_UNUSED, void *client GNUNET_UNUSED, { const struct GNUNET_TUN_Layer2PacketHeader *tun; size_t mlen; - GNUNET_HashCode key; + struct GNUNET_HashCode key; struct DestinationEntry *de; GNUNET_STATISTICS_update (stats, @@ -2336,7 +2353,7 @@ allocate_v4_address (struct in_addr *v4) struct in_addr addr; struct in_addr mask; struct in_addr rnd; - GNUNET_HashCode key; + struct GNUNET_HashCode key; unsigned int tries; GNUNET_assert (1 == inet_pton (AF_INET, ipv4addr, &addr)); @@ -2387,7 +2404,7 @@ allocate_v6_address (struct in6_addr *v6) struct in6_addr mask; struct in6_addr rnd; int i; - GNUNET_HashCode key; + struct GNUNET_HashCode key; unsigned int tries; GNUNET_assert (1 == inet_pton (AF_INET6, ipv6addr, &addr)); @@ -2564,7 +2581,7 @@ service_redirect_to_ip (void *cls GNUNET_UNUSED, struct GNUNET_SERVER_Client *cl struct in6_addr v6; void *addr; struct DestinationEntry *de; - GNUNET_HashCode key; + struct GNUNET_HashCode key; struct TunnelState *ts; /* validate and parse request */ @@ -2703,7 +2720,7 @@ service_redirect_to_service (void *cls GNUNET_UNUSED, struct GNUNET_SERVER_Clien struct in6_addr v6; void *addr; struct DestinationEntry *de; - GNUNET_HashCode key; + struct GNUNET_HashCode key; struct TunnelState *ts; /* parse request */ @@ -2835,7 +2852,7 @@ tunnel_cleaner (void *cls, const struct GNUNET_MESH_Tunnel *tunnel, void *tunnel */ static int cleanup_destination (void *cls, - const GNUNET_HashCode *key, + const struct GNUNET_HashCode *key, void *value) { struct DestinationEntry *de = value; @@ -2855,7 +2872,7 @@ cleanup_destination (void *cls, */ static int cleanup_tunnel (void *cls, - const GNUNET_HashCode *key, + const struct GNUNET_HashCode *key, void *value) { struct TunnelState *ts = value; @@ -2940,7 +2957,7 @@ cleanup (void *cls GNUNET_UNUSED, */ static int cleanup_tunnel_client (void *cls, - const GNUNET_HashCode *key, + const struct GNUNET_HashCode *key, void *value) { struct GNUNET_SERVER_Client *client = cls; @@ -2965,7 +2982,7 @@ cleanup_tunnel_client (void *cls, */ static int cleanup_destination_client (void *cls, - const GNUNET_HashCode *key, + const struct GNUNET_HashCode *key, void *value) { struct GNUNET_SERVER_Client *client = cls; @@ -3004,31 +3021,6 @@ client_disconnect (void *cls, struct GNUNET_SERVER_Client *client) } -/** - * Test if the given AF is supported by this system. - * - * @param af to test - * @return GNUNET_OK if the AF is supported - */ -static int -test_af (int af) -{ - int s; - - s = socket (af, SOCK_STREAM, 0); - if (-1 == s) - { - if (EAFNOSUPPORT == errno) - return GNUNET_NO; - GNUNET_log_strerror (GNUNET_ERROR_TYPE_ERROR, - "socket"); - return GNUNET_SYSERR; - } - close (s); - return GNUNET_OK; -} - - /** * Main function that will be run by the scheduler. * @@ -3065,16 +3057,21 @@ run (void *cls, char *ipv4mask; struct in_addr v4; struct in6_addr v6; + char *binary; + + binary = GNUNET_OS_get_libexec_binary_path ("gnunet-helper-vpn"); if (GNUNET_YES != - GNUNET_OS_check_helper_binary ("gnunet-helper-vpn")) + GNUNET_OS_check_helper_binary (binary)) { fprintf (stderr, "`%s' is not SUID, refusing to run.\n", "gnunet-helper-vpn"); + GNUNET_free (binary); global_ret = 1; return; } + GNUNET_free (binary); cfg = cfg_; stats = GNUNET_STATISTICS_create ("vpn", cfg); if (GNUNET_OK != @@ -3086,9 +3083,9 @@ run (void *cls, &max_tunnel_mappings)) max_tunnel_mappings = 200; - destination_map = GNUNET_CONTAINER_multihashmap_create (max_destination_mappings * 2); + destination_map = GNUNET_CONTAINER_multihashmap_create (max_destination_mappings * 2, GNUNET_NO); destination_heap = GNUNET_CONTAINER_heap_create (GNUNET_CONTAINER_HEAP_ORDER_MIN); - tunnel_map = GNUNET_CONTAINER_multihashmap_create (max_tunnel_mappings * 2); + tunnel_map = GNUNET_CONTAINER_multihashmap_create (max_tunnel_mappings * 2, GNUNET_NO); tunnel_heap = GNUNET_CONTAINER_heap_create (GNUNET_CONTAINER_HEAP_ORDER_MIN); @@ -3102,7 +3099,7 @@ run (void *cls, return; } vpn_argv[1] = ifname; - if (GNUNET_OK == test_af (AF_INET6)) + if (GNUNET_OK == GNUNET_NETWORK_test_pf (PF_INET6)) { if ( (GNUNET_SYSERR == GNUNET_CONFIGURATION_get_value_string (cfg, "vpn", "IPV6ADDR", @@ -3142,7 +3139,7 @@ run (void *cls, vpn_argv[2] = GNUNET_strdup ("-"); vpn_argv[3] = GNUNET_strdup ("-"); } - if (GNUNET_OK == test_af (AF_INET)) + if (GNUNET_OK == GNUNET_NETWORK_test_pf (PF_INET)) { if ( (GNUNET_SYSERR == GNUNET_CONFIGURATION_get_value_string (cfg, "vpn", "IPV4ADDR", @@ -3177,13 +3174,14 @@ run (void *cls, vpn_argv[6] = NULL; mesh_handle = - GNUNET_MESH_connect (cfg_, 42 /* queue length */, NULL, + GNUNET_MESH_connect (cfg_, NULL, &inbound_tunnel_cb, &tunnel_cleaner, mesh_handlers, types); - helper_handle = GNUNET_HELPER_start ("gnunet-helper-vpn", vpn_argv, - &message_token, NULL); + helper_handle = GNUNET_HELPER_start (GNUNET_NO, + "gnunet-helper-vpn", vpn_argv, + &message_token, NULL, NULL); nc = GNUNET_SERVER_notification_context_create (server, 1); GNUNET_SERVER_add_handlers (server, service_handlers); GNUNET_SERVER_disconnect_notify (server, &client_disconnect, NULL); diff --git a/src/vpn/gnunet-vpn.c b/src/vpn/gnunet-vpn.c index ecc0442..6402e10 100644 --- a/src/vpn/gnunet-vpn.c +++ b/src/vpn/gnunet-vpn.c @@ -92,7 +92,7 @@ static int ret; /** * Option '-d': duration of the mapping */ -static unsigned long long duration = 5 * 60; +static struct GNUNET_TIME_Relative duration = { 5 * 60 * 1000} ; /** @@ -173,15 +173,14 @@ run (void *cls, char *const *args, const char *cfgfile, int dst_af; int req_af; struct GNUNET_PeerIdentity peer; - GNUNET_HashCode sd; + struct GNUNET_HashCode sd; const void *addr; struct in_addr v4; struct in6_addr v6; uint8_t protocol; struct GNUNET_TIME_Absolute etime; - etime = GNUNET_TIME_relative_to_absolute (GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, - (unsigned int) duration)); + etime = GNUNET_TIME_relative_to_absolute (duration); GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, &do_disconnect, NULL); handle = GNUNET_VPN_connect (cfg); @@ -301,9 +300,9 @@ main (int argc, char *const *argv) {'a', "after-connect", NULL, gettext_noop ("print IP address only after mesh tunnel has been created"), 0, &GNUNET_GETOPT_set_one, &ipv6}, - {'d', "duration", "SECONDS", + {'d', "duration", "TIME", gettext_noop ("how long should the mapping be valid for new tunnels?"), - 1, &GNUNET_GETOPT_set_ulong, &duration}, + 1, &GNUNET_GETOPT_set_relative_time, &duration}, {'i', "ip", "IP", gettext_noop ("destination IP for the tunnel"), 1, &GNUNET_GETOPT_set_string, &target_ip}, @@ -323,11 +322,16 @@ main (int argc, char *const *argv) GNUNET_GETOPT_OPTION_VERBOSE (&verbosity), GNUNET_GETOPT_OPTION_END }; - return (GNUNET_OK == - GNUNET_PROGRAM_run (argc, argv, "gnunet-vpn", - gettext_noop - ("Setup tunnels via VPN."), options, + if (GNUNET_OK != GNUNET_STRINGS_get_utf8_args (argc, argv, &argc, &argv)) + return 2; + + ret = (GNUNET_OK == + GNUNET_PROGRAM_run (argc, argv, "gnunet-vpn", + gettext_noop + ("Setup tunnels via VPN."), options, &run, NULL)) ? ret : 1; + GNUNET_free ((void *) argv); + return ret; } diff --git a/src/vpn/test_gnunet_vpn.c b/src/vpn/test_gnunet_vpn.c deleted file mode 100644 index 4c941bd..0000000 --- a/src/vpn/test_gnunet_vpn.c +++ /dev/null @@ -1,599 +0,0 @@ -/* - This file is part of GNUnet - (C) 2007, 2009, 2011, 2012 Christian Grothoff - - GNUnet is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published - by the Free Software Foundation; either version 2, or (at your - option) any later version. - - GNUnet is distributed in the hope that it will be useful, but - WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - General Public License for more details. - - You should have received a copy of the GNU General Public License - along with GNUnet; see the file COPYING. If not, write to the - Free Software Foundation, Inc., 59 Temple Place - Suite 330, - Boston, MA 02111-1307, USA. -*/ - -/** - * @file test_gnunet_vpn.c - * @brief testcase for tunneling HTTP over the GNUnet VPN - * @author Christian Grothoff - */ -#include "platform.h" -#include -#include -#include "gnunet_vpn_service.h" -#include "gnunet_arm_service.h" - -#define PORT 48080 - -#define START_ARM GNUNET_YES - -#define VERBOSE GNUNET_NO - -#define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 300) - -struct PeerContext -{ - struct GNUNET_CONFIGURATION_Handle *cfg; - struct GNUNET_PeerIdentity id; -#if START_ARM - struct GNUNET_OS_Process *arm_proc; -#endif -}; - -static struct PeerContext p1; - -/** - * Return value for 'main'. - */ -static int global_ret; - -static struct GNUNET_VPN_Handle *vpn; - -static struct MHD_Daemon *mhd; - -static GNUNET_SCHEDULER_TaskIdentifier mhd_task_id; - -static GNUNET_SCHEDULER_TaskIdentifier curl_task_id; - -static GNUNET_SCHEDULER_TaskIdentifier ctrl_c_task_id; - -static struct GNUNET_VPN_RedirectionRequest *rr; - -static CURL *curl; - -static CURLM *multi; - -static char *url; - -/** - * IP address of the ultimate destination. - */ -static const char *dest_ip; - -/** - * Address family of the dest_ip. - */ -static int dest_af; - -/** - * Address family to use by the curl client. - */ -static int src_af; - - -struct CBC -{ - char buf[1024]; - size_t pos; -}; - -static struct CBC cbc; - - - -static size_t -copy_buffer (void *ptr, size_t size, size_t nmemb, void *ctx) -{ - struct CBC *cbc = ctx; - - if (cbc->pos + size * nmemb > sizeof(cbc->buf)) - return 0; /* overflow */ - memcpy (&cbc->buf[cbc->pos], ptr, size * nmemb); - cbc->pos += size * nmemb; - return size * nmemb; -} - - -static int -mhd_ahc (void *cls, - struct MHD_Connection *connection, - const char *url, - const char *method, - const char *version, - const char *upload_data, size_t *upload_data_size, - void **unused) -{ - static int ptr; - struct MHD_Response *response; - int ret; - - if (0 != strcmp ("GET", method)) - return MHD_NO; /* unexpected method */ - if (&ptr != *unused) - { - *unused = &ptr; - return MHD_YES; - } - *unused = NULL; - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "MHD sends respose for request to URL `%s'\n", url); - response = MHD_create_response_from_buffer (strlen (url), - (void *) url, - MHD_RESPMEM_MUST_COPY); - ret = MHD_queue_response (connection, MHD_HTTP_OK, response); - MHD_destroy_response (response); - if (ret == MHD_NO) - abort (); - return ret; -} - - -static void -do_shutdown () -{ - if (mhd_task_id != GNUNET_SCHEDULER_NO_TASK) - { - GNUNET_SCHEDULER_cancel (mhd_task_id); - mhd_task_id = GNUNET_SCHEDULER_NO_TASK; - } - if (curl_task_id != GNUNET_SCHEDULER_NO_TASK) - { - GNUNET_SCHEDULER_cancel (curl_task_id); - curl_task_id = GNUNET_SCHEDULER_NO_TASK; - } - if (ctrl_c_task_id != GNUNET_SCHEDULER_NO_TASK) - { - GNUNET_SCHEDULER_cancel (ctrl_c_task_id); - ctrl_c_task_id = GNUNET_SCHEDULER_NO_TASK; - } - if (NULL != mhd) - { - MHD_stop_daemon (mhd); - mhd = NULL; - } - if (NULL != rr) - { - GNUNET_VPN_cancel_request (rr); - rr = NULL; - } - if (NULL != vpn) - { - GNUNET_VPN_disconnect (vpn); - vpn = NULL; - } - GNUNET_free_non_null (url); - url = NULL; -} - - -/** - * Function to run the HTTP client. - */ -static void -curl_main (void); - - -static void -curl_task (void *cls, - const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - curl_task_id = GNUNET_SCHEDULER_NO_TASK; - curl_main (); -} - - -static void -curl_main () -{ - fd_set rs; - fd_set ws; - fd_set es; - int max; - struct GNUNET_NETWORK_FDSet nrs; - struct GNUNET_NETWORK_FDSet nws; - struct GNUNET_TIME_Relative delay; - long timeout; - int running; - struct CURLMsg *msg; - - max = 0; - FD_ZERO (&rs); - FD_ZERO (&ws); - FD_ZERO (&es); - curl_multi_perform (multi, &running); - if (running == 0) - { - GNUNET_assert (NULL != (msg = curl_multi_info_read (multi, &running))); - if (msg->msg == CURLMSG_DONE) - { - if (msg->data.result != CURLE_OK) - { - fprintf (stderr, - "%s failed at %s:%d: `%s'\n", - "curl_multi_perform", - __FILE__, - __LINE__, curl_easy_strerror (msg->data.result)); - global_ret = 1; - } - } - curl_multi_remove_handle (multi, curl); - curl_multi_cleanup (multi); - curl_easy_cleanup (curl); - curl = NULL; - multi = NULL; - if (cbc.pos != strlen ("/hello_world")) - { - GNUNET_break (0); - global_ret = 2; - } - if (0 != strncmp ("/hello_world", cbc.buf, strlen ("/hello_world"))) - { - GNUNET_break (0); - global_ret = 3; - } - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Download complete, shutting down!\n"); - do_shutdown (); - return; - } - GNUNET_assert (CURLM_OK == curl_multi_fdset (multi, &rs, &ws, &es, &max)); - if ( (CURLM_OK != curl_multi_timeout (multi, &timeout)) || - (-1 == timeout) ) - delay = GNUNET_TIME_UNIT_SECONDS; - else - delay = GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MILLISECONDS, (unsigned int) timeout); - GNUNET_NETWORK_fdset_copy_native (&nrs, - &rs, - max + 1); - GNUNET_NETWORK_fdset_copy_native (&nws, - &ws, - max + 1); - curl_task_id = GNUNET_SCHEDULER_add_select (GNUNET_SCHEDULER_PRIORITY_DEFAULT, - delay, - &nrs, - &nws, - &curl_task, - NULL); -} - - -/** - * Callback invoked from the VPN service once a redirection is - * available. Provides the IP address that can now be used to - * reach the requested destination (in our case, the MHD server) - * - * @param cls closure - * @param af address family, AF_INET or AF_INET6; AF_UNSPEC on error; - * will match 'result_af' from the request - * @param address IP address (struct in_addr or struct in_addr6, depending on 'af') - * that the VPN allocated for the redirection; - * traffic to this IP will now be redirected to the - * specified target peer; NULL on error - */ -static void -allocation_cb (void *cls, - int af, - const void *address) -{ - char ips[INET6_ADDRSTRLEN]; - - rr = NULL; - if (src_af != af) - { - fprintf (stderr, - "VPN failed to allocate appropriate address\n"); - GNUNET_SCHEDULER_shutdown (); - return; - } - GNUNET_asprintf (&url, - "http://%s:%u/hello_world", - inet_ntop (af, address, ips, sizeof (ips)), - (unsigned int) PORT); - curl = curl_easy_init (); - curl_easy_setopt (curl, CURLOPT_URL, url); - curl_easy_setopt (curl, CURLOPT_WRITEFUNCTION, ©_buffer); - curl_easy_setopt (curl, CURLOPT_WRITEDATA, &cbc); - curl_easy_setopt (curl, CURLOPT_FAILONERROR, 1); - curl_easy_setopt (curl, CURLOPT_TIMEOUT, 150L); - curl_easy_setopt (curl, CURLOPT_CONNECTTIMEOUT, 15L); - curl_easy_setopt (curl, CURLOPT_NOSIGNAL, 1); - - multi = curl_multi_init (); - GNUNET_assert (multi != NULL); - GNUNET_assert (CURLM_OK == curl_multi_add_handle (multi, curl)); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Beginning HTTP download from `%s'\n", url); - curl_main (); -} - - -/** - * Function to keep the HTTP server running. - */ -static void -mhd_main (void); - - -static void -mhd_task (void *cls, - const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - mhd_task_id = GNUNET_SCHEDULER_NO_TASK; - MHD_run (mhd); - mhd_main (); -} - - -static void -ctrl_c_shutdown (void *cls, - const struct GNUNET_SCHEDULER_TaskContext *tc) -{ - ctrl_c_task_id = GNUNET_SCHEDULER_NO_TASK; - do_shutdown (); - GNUNET_break (0); - global_ret = 1; -} - - -static void -mhd_main () -{ - struct GNUNET_NETWORK_FDSet nrs; - struct GNUNET_NETWORK_FDSet nws; - fd_set rs; - fd_set ws; - fd_set es; - int max_fd; - unsigned MHD_LONG_LONG timeout; - struct GNUNET_TIME_Relative delay; - - GNUNET_assert (GNUNET_SCHEDULER_NO_TASK == mhd_task_id); - FD_ZERO (&rs); - FD_ZERO (&ws); - FD_ZERO (&es); - max_fd = -1; - GNUNET_assert (MHD_YES == - MHD_get_fdset (mhd, &rs, &ws, &es, &max_fd)); - if (MHD_YES == MHD_get_timeout (mhd, &timeout)) - delay = GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MILLISECONDS, - (unsigned int) timeout); - else - delay = GNUNET_TIME_UNIT_FOREVER_REL; - GNUNET_NETWORK_fdset_copy_native (&nrs, - &rs, - max_fd + 1); - GNUNET_NETWORK_fdset_copy_native (&nws, - &ws, - max_fd + 1); - mhd_task_id = GNUNET_SCHEDULER_add_select (GNUNET_SCHEDULER_PRIORITY_DEFAULT, - delay, - &nrs, - &nws, - &mhd_task, - NULL); -} - - -static void -run (void *cls, char *const *args, const char *cfgfile, - const struct GNUNET_CONFIGURATION_Handle *cfg) -{ - struct in_addr v4; - struct in6_addr v6; - void *addr; - enum MHD_FLAG flags; - - vpn = GNUNET_VPN_connect (cfg); - GNUNET_assert (NULL != vpn); - flags = MHD_USE_DEBUG; - if (AF_INET6 == dest_af) - flags |= MHD_USE_IPv6; - mhd = MHD_start_daemon (flags, - PORT, - NULL, NULL, - &mhd_ahc, NULL, - MHD_OPTION_END); - GNUNET_assert (NULL != mhd); - mhd_main (); - addr = NULL; - switch (dest_af) - { - case AF_INET: - GNUNET_assert (1 == inet_pton (dest_af, dest_ip, &v4)); - addr = &v4; - break; - case AF_INET6: - GNUNET_assert (1 == inet_pton (dest_af, dest_ip, &v6)); - addr = &v6; - break; - default: - GNUNET_assert (0); - } - rr = GNUNET_VPN_redirect_to_ip (vpn, - src_af, - dest_af, - addr, - GNUNET_YES, - GNUNET_TIME_UNIT_FOREVER_ABS, - &allocation_cb, NULL); - ctrl_c_task_id = GNUNET_SCHEDULER_add_delayed (TIMEOUT, - &ctrl_c_shutdown, - NULL); -} - - -static void -setup_peer (struct PeerContext *p, const char *cfgname) -{ - p->cfg = GNUNET_CONFIGURATION_create (); -#if START_ARM - p->arm_proc = - GNUNET_OS_start_process (GNUNET_YES, NULL, NULL, "gnunet-service-arm", - "gnunet-service-arm", - "-c", cfgname, NULL); -#endif - GNUNET_assert (NULL != p->arm_proc); - GNUNET_assert (GNUNET_OK == GNUNET_CONFIGURATION_load (p->cfg, cfgname)); -} - - -static void -stop_peer (struct PeerContext *p) -{ -#if START_ARM - if (NULL != p->arm_proc) - { - if (0 != GNUNET_OS_process_kill (p->arm_proc, SIGTERM)) - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); - if (GNUNET_OS_process_wait (p->arm_proc) != GNUNET_OK) - GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "waitpid"); - GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "ARM process %u stopped\n", - GNUNET_OS_process_get_pid (p->arm_proc)); - GNUNET_OS_process_destroy (p->arm_proc); - p->arm_proc = NULL; - } -#endif - GNUNET_CONFIGURATION_destroy (p->cfg); -} - - -/** - * Test if the given AF is supported by this system. - * - * @param af to test - * @return GNUNET_OK if the AF is supported - */ -static int -test_af (int af) -{ - int s; - - s = socket (af, SOCK_STREAM, 0); - if (-1 == s) - { - if (EAFNOSUPPORT == errno) - return GNUNET_NO; - fprintf (stderr, "Failed to create test socket: %s\n", STRERROR (errno)); - return GNUNET_SYSERR; - } - close (s); - return GNUNET_OK; -} - - - -int -main (int argc, char *const *argv) -{ - const char *type; - const char *bin; - char *const argvx[] = { - "test_gnunet_vpn", - "-c", - "test_gnunet_vpn.conf", - NULL - }; - struct GNUNET_GETOPT_CommandLineOption options[] = { - GNUNET_GETOPT_OPTION_END - }; - - if (0 != ACCESS ("/dev/net/tun", R_OK)) - { - GNUNET_log_strerror_file (GNUNET_ERROR_TYPE_ERROR, - "access", - "/dev/net/tun"); - fprintf (stderr, - "WARNING: System unable to run test, skipping.\n"); - return 0; - } - if ( (GNUNET_YES != - GNUNET_OS_check_helper_binary ("gnunet-helper-vpn")) || - (GNUNET_YES != - GNUNET_OS_check_helper_binary ("gnunet-helper-exit")) ) - { - fprintf (stderr, - "WARNING: gnunet-helper-{exit,vpn} binaries in $PATH are not SUID, refusing to run test (as it would have to fail).\n"); - fprintf (stderr, - "Change $PATH ('.' in $PATH before $GNUNET_PREFIX/bin is problematic) or permissions (run 'make install' as root) to fix this!\n"); - return 0; - } - GNUNET_CRYPTO_setup_hostkey ("test_gnunet_vpn.conf"); - bin = argv[0]; - if (NULL != strstr (bin, "lt-")) - bin = strstr (bin, "lt-") + 4; - type = strstr (bin, "-"); - if (NULL == type) - { - fprintf (stderr, "invalid binary name\n"); - return 1; - } - type++; - if (0 == strcmp (type, "4_to_6")) - { - dest_ip = "FC5A:04E1:C2BA::1"; - dest_af = AF_INET6; - src_af = AF_INET; - } - else if (0 == strcmp (type, "6_to_4")) - { - dest_ip = "169.254.86.1"; - dest_af = AF_INET; - src_af = AF_INET6; - } - else if (0 == strcmp (type, "4_over")) - { - dest_ip = "169.254.86.1"; - dest_af = AF_INET; - src_af = AF_INET; - } - else if (0 == strcmp (type, "6_over")) - { - dest_ip = "FC5A:04E1:C2BA::1"; - dest_af = AF_INET6; - src_af = AF_INET6; - } - else - { - fprintf (stderr, "invalid binary suffix `%s'\n", type); - return 1; - } - if ( (GNUNET_OK != test_af (src_af)) || - (GNUNET_OK != test_af (dest_af)) ) - { - fprintf (stderr, - "Required address families not supported by this system, skipping test.\n"); - return 0; - } - - - if (0 != curl_global_init (CURL_GLOBAL_WIN32)) - { - fprintf (stderr, "failed to initialize curl\n"); - return 2; - } - setup_peer (&p1, "test_gnunet_vpn.conf"); - GNUNET_log_setup ("test_gnunet_vpn", - "WARNING", - NULL); - GNUNET_PROGRAM_run ((sizeof (argvx) / sizeof (char *)) - 1, argvx, - "test_gnunet_vpn", "nohelp", options, &run, NULL); - stop_peer (&p1); - GNUNET_DISK_directory_remove ("/tmp/gnunet-test-vpn"); - return global_ret; -} - -/* end of test_gnunet_vpn.c */ - diff --git a/src/vpn/test_gnunet_vpn.conf b/src/vpn/test_gnunet_vpn.conf deleted file mode 100644 index bdac1a5..0000000 --- a/src/vpn/test_gnunet_vpn.conf +++ /dev/null @@ -1,43 +0,0 @@ -[PATHS] -SERVICEHOME = /tmp/gnunet-test-vpn/ -DEFAULTCONFIG = test_gnunet_vpn.conf - -[transport] -PLUGINS = tcp - -[arm] -DEFAULTSERVICES = statistics exit vpn -PORT = 0 -ALLOW_SHUTDOWN = YES - -[exit] -EXIT_IPV4 = YES -EXIT_IPV6 = YES - -# FIXME: can we use 'lo'? -EXIT_IFNAME = eth1 - -[testing] -WEAKRANDOM = YES -HOSTKEYSFILE = ../../contrib/testing_hostkeys.dat - -[nse] -WORKBITS = 1 - -# repeating some values from the default configurations -# here as the respective network addresses are also -# hard-wired in the tests and the MUST match (!) -[vpn] -IPV6ADDR = FC2D:FDAA:6A26::1 -IPV6PREFIX = 64 -IPV4ADDR = 169.254.20.1 -IPV4MASK = 255.255.255.0 - -[exit] -IPV6ADDR = FC5A:04E1:C2BA::1 -IPV6PREFIX = 96 -IPV4ADDR = 169.254.86.1 -IPV4MASK = 255.255.255.0 - -[gns] -AUTOSTART = NO diff --git a/src/vpn/vpn.conf.in b/src/vpn/vpn.conf.in index f5eb224..57657b9 100644 --- a/src/vpn/vpn.conf.in +++ b/src/vpn/vpn.conf.in @@ -1,9 +1,8 @@ [vpn] AUTOSTART = YES -@UNIXONLY@ PORT = 0 +@UNIXONLY@ PORT = 2105 HOSTNAME = localhost HOME = $SERVICEHOME -CONFIG = $DEFAULTCONFIG BINARY = gnunet-service-vpn ACCEPT_FROM = 127.0.0.1; ACCEPT_FROM6 = ::1; diff --git a/src/vpn/vpn.h b/src/vpn/vpn.h index bec3a5b..e1ae130 100644 --- a/src/vpn/vpn.h +++ b/src/vpn/vpn.h @@ -82,7 +82,7 @@ struct RedirectToIpRequestMessage struct RedirectToServiceRequestMessage { /** - * Type is GNUNET_MESSAGE_TYPE_VPN_CLIENT_REDIRECT_TO_IP + * Type is GNUNET_MESSAGE_TYPE_VPN_CLIENT_REDIRECT_TO_SERVICE */ struct GNUNET_MessageHeader header; @@ -115,7 +115,7 @@ struct RedirectToServiceRequestMessage /** * Service descriptor identifying the service. */ - GNUNET_HashCode service_descriptor; + struct GNUNET_HashCode service_descriptor; /** * Unique ID to match a future response to this request. diff --git a/src/vpn/vpn_api.c b/src/vpn/vpn_api.c index 5b70d19..e4da5fa 100644 --- a/src/vpn/vpn_api.c +++ b/src/vpn/vpn_api.c @@ -120,7 +120,7 @@ struct GNUNET_VPN_RedirectionRequest /** * For service redirection, service descriptor. */ - GNUNET_HashCode serv; + struct GNUNET_HashCode serv; /** * At what time should the created service mapping expire? @@ -464,7 +464,7 @@ GNUNET_VPN_redirect_to_peer (struct GNUNET_VPN_Handle *vh, int result_af, uint8_t protocol, const struct GNUNET_PeerIdentity *peer, - const GNUNET_HashCode *serv, + const struct GNUNET_HashCode *serv, int nac, struct GNUNET_TIME_Absolute expiration_time, GNUNET_VPN_AllocationCallback cb, -- cgit v1.2.3-18-g5258